From 1dde989919d2c272ca7fcaa5c4b2d9ee02c490a0 Mon Sep 17 00:00:00 2001
From: Ram N <axe@fb.com>
Date: Mon, 12 Mar 2018 14:47:50 -0700
Subject: [PATCH 0001/1109] Add support for springDamping in SpringInterpolator

Reviewed By: mdvacca

Differential Revision: D7201334

fbshipit-source-id: 50929b4294188cd5a2a8ffa2080c38c0a9983535
---
 .../AbstractLayoutAnimation.java              | 28 +++++++++++--------
 .../SimpleSpringInterpolator.java             | 24 +++++++++++++++-
 2 files changed, 40 insertions(+), 12 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
index 4fbd6938a9c5..1ad6ccab3946 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
@@ -2,21 +2,20 @@
 
 package com.facebook.react.uimanager.layoutanimation;
 
-import javax.annotation.Nullable;
-
-import java.util.Map;
-
+import android.os.Build;
 import android.view.View;
 import android.view.animation.AccelerateDecelerateInterpolator;
 import android.view.animation.AccelerateInterpolator;
 import android.view.animation.Animation;
+import android.view.animation.BaseInterpolator;
 import android.view.animation.DecelerateInterpolator;
 import android.view.animation.Interpolator;
 import android.view.animation.LinearInterpolator;
-
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.uimanager.IllegalViewOperationException;
+import java.util.Map;
+import javax.annotation.Nullable;
 
 /**
  * Class responsible for parsing and converting layout animation data into native {@link Animation}
@@ -36,12 +35,11 @@
    */
   abstract @Nullable Animation createAnimationImpl(View view, int x, int y, int width, int height);
 
-  private static final Map<InterpolatorType, Interpolator> INTERPOLATOR = MapBuilder.of(
+  private static final Map<InterpolatorType, BaseInterpolator> INTERPOLATOR = MapBuilder.of(
       InterpolatorType.LINEAR, new LinearInterpolator(),
       InterpolatorType.EASE_IN, new AccelerateInterpolator(),
       InterpolatorType.EASE_OUT, new DecelerateInterpolator(),
-      InterpolatorType.EASE_IN_EASE_OUT, new AccelerateDecelerateInterpolator(),
-      InterpolatorType.SPRING, new SimpleSpringInterpolator());
+      InterpolatorType.EASE_IN_EASE_OUT, new AccelerateDecelerateInterpolator());
 
   private @Nullable Interpolator mInterpolator;
   private int mDelayMs;
@@ -64,7 +62,7 @@ public void initializeFromConfig(ReadableMap data, int globalDuration) {
     if (!data.hasKey("type")) {
       throw new IllegalArgumentException("Missing interpolation type.");
     }
-    mInterpolator = getInterpolator(InterpolatorType.fromString(data.getString("type")));
+    mInterpolator = getInterpolator(InterpolatorType.fromString(data.getString("type")), data);
 
     if (!isValid()) {
       throw new IllegalViewOperationException("Invalid layout animation : " + data);
@@ -100,8 +98,16 @@ public void initializeFromConfig(ReadableMap data, int globalDuration) {
     return animation;
   }
 
-  private static Interpolator getInterpolator(InterpolatorType type) {
-    Interpolator interpolator = INTERPOLATOR.get(type);
+  private static Interpolator getInterpolator(InterpolatorType type, ReadableMap params) {
+     Interpolator interpolator = null;
+     if (type.equals(InterpolatorType.SPRING)) {
+       interpolator = new SimpleSpringInterpolator(SimpleSpringInterpolator.getSpringDamping(params));
+     } else {
+       if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP_MR1) {
+         // Conversion from BaseInterpolator to Interpolator is only possible on this Android versions
+         interpolator = INTERPOLATOR.get(type);
+       }
+     }
     if (interpolator == null) {
       throw new IllegalArgumentException("Missing interpolator for type : " + type);
     }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/SimpleSpringInterpolator.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/SimpleSpringInterpolator.java
index 9696fe90a1a3..7ca2de98a060 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/SimpleSpringInterpolator.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/SimpleSpringInterpolator.java
@@ -3,6 +3,8 @@
 package com.facebook.react.uimanager.layoutanimation;
 
 import android.view.animation.Interpolator;
+import com.facebook.react.bridge.ReadableMap;
+import com.facebook.react.bridge.ReadableType;
 
 /**
  * Simple spring interpolator
@@ -11,10 +13,30 @@
 /* package */  class SimpleSpringInterpolator implements Interpolator {
 
   private static final float FACTOR = 0.5f;
+  public static final String PARAM_SPRING_DAMPING = "springDamping";
+  private final float mSpringDamping;
+
+  public static float getSpringDamping(ReadableMap params){
+    if (params.getType(PARAM_SPRING_DAMPING).equals(ReadableType.Number)){
+      return (float) params.getDouble(PARAM_SPRING_DAMPING);
+    } else {
+      return FACTOR;
+    }
+  }
+
+  public SimpleSpringInterpolator() {
+    mSpringDamping = FACTOR;
+  }
+
+  public SimpleSpringInterpolator(float springDamping){
+    mSpringDamping = springDamping;
+  }
 
   @Override
   public float getInterpolation(float input) {
+    // Using mSpringDamping in this equation is not really the exact mathematical springDamping, but a good approximation
+    // We need to replace this equation with the right Factor that accounts for damping and friction
     return (float)
-        (1 + Math.pow(2, -10 * input) * Math.sin((input - FACTOR / 4) * Math.PI * 2 / FACTOR));
+        (1 + Math.pow(2, -10 * input) * Math.sin((input - mSpringDamping / 4) * Math.PI * 2 / mSpringDamping));
   }
 }

From 0459e4ffaadb161598ce1a5b14c08d49a9257c9c Mon Sep 17 00:00:00 2001
From: Moti Zilberman <motiz88@gmail.com>
Date: Mon, 12 Mar 2018 16:05:40 -0700
Subject: [PATCH 0002/1109] Support Image resizeMode=repeat on Android

Summary:
`<Image resizeMode="repeat" />` for Android, matching the iOS implementation (#7968). (Non-goal: changing the component's API for finer-grained control / feature parity with CSS - this would be nice in the future)

As requested in e.g. #14158.

Given https://github.com/facebook/fresco/issues/1575, and lacking the context to follow the specific recommendations in https://github.com/facebook/fresco/issues/1575#issuecomment-267004303, I've opted for a minimal change within RN itself.

It's likely that performance can be improved by offloading this work to Fresco in some clever way; but I'm assuming that the present naive approach is still an improvement over a userland implementation with `onLayout` and multiple `<Image>` instances.

- Picking up on a TODO note in the existing code, I implemented `MultiPostprocessor` to allow arbitrary chaining of Fresco-compatible postprocessors inside `ReactImageView`.
- Rather than extensively refactor `ImageResizeMode`, `ReactImageManager` and `ReactImageView`, I mostly preserved the existing API that maps `resizeMode` values to [`ScaleType`](http://frescolib.org/javadoc/reference/com/facebook/drawee/drawable/ScalingUtils.ScaleType.html) instances, and simply added a second mapping, to [`TileMode`](https://developer.android.com/reference/android/graphics/Shader.TileMode.html).
- To match the iOS rendering exactly for oversized images, I found that scaling with a custom `ScaleType` was required - a kind of combination of `CENTER_INSIDE` and `FIT_START` which Fresco doesn't provide - so I implemented that as `ScaleTypeStartInside`. (This is, frankly, questionable as the default behaviour on iOS to begin with - but I am aiming for parity here)
- `resizeMode="repeat"` is therefore unpacked by the view manager to the effect of:
  ```js
     view.setScaleType(ScaleTypeStartInside.INSTANCE);
     view.setTileMode(Shader.TileMode.REPEAT);
   ```
  And the added postprocessing in the view (in case of a non-`CLAMP` tile mode) consists of waiting for layout, allocating a destination bitmap and painting the source bitmap with the requested tile mode and scale type.

Note that as in https://github.com/facebook/react-native/pull/17398#issue-285235247, I have neither updated nor tested the "Flat" UI implementation - everything compiles but I've taken [this comment](https://github.com/facebook/react-native/issues/12770#issuecomment-294052694) to mean there's no point in trying to wade through it on my own right now; I'm happy to tackle it if given some pointers.

Also, I'm happy to address any code style issues or other feedback; I'm new to this codebase and a very infrequent Android/Java coder.

Tested by enabling the relevant case in RNTester on Android.

| iOS | Android |
|-|-|
| <img src=https://user-images.githubusercontent.com/2246565/34461897-4e12008e-ee2f-11e7-8581-1dc0cc8f2779.png width=300>| <img src=https://user-images.githubusercontent.com/2246565/34461894-40b2c8ec-ee2f-11e7-8a8f-96704f3c8caa.png width=300> |

Docs update: https://github.com/facebook/react-native-website/pull/106

[ANDROID] [FEATURE] [Image] - Implement resizeMode=repeat
Closes https://github.com/facebook/react-native/pull/17404

Reviewed By: achen1

Differential Revision: D7070329

Pulled By: mdvacca

fbshipit-source-id: 6a72fcbdcc7c7c2daf293dc1d8b6728f54ad0249
---
 Libraries/Image/Image.android.js              |  2 +-
 RNTester/js/ImageExample.js                   | 22 +++---
 .../react/views/image/ImageResizeMode.java    | 32 ++++++++
 .../react/views/image/MultiPostprocessor.java | 79 +++++++++++++++++++
 .../react/views/image/ReactImageManager.java  |  1 +
 .../react/views/image/ReactImageView.java     | 70 ++++++++++++++--
 .../views/image/ScaleTypeStartInside.java     | 40 ++++++++++
 7 files changed, 227 insertions(+), 19 deletions(-)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/views/image/MultiPostprocessor.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/views/image/ScaleTypeStartInside.java

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index bdb29ab8fe89..4e218487c9b5 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -119,7 +119,7 @@ var Image = createReactClass({
      *
      * See https://facebook.github.io/react-native/docs/image.html#resizemode
      */
-    resizeMode: PropTypes.oneOf(['cover', 'contain', 'stretch', 'center']),
+    resizeMode: PropTypes.oneOf(['cover', 'contain', 'stretch', 'repeat', 'center']),
   },
 
   statics: {
diff --git a/RNTester/js/ImageExample.js b/RNTester/js/ImageExample.js
index d30a24ca7c93..37f36b697de3 100644
--- a/RNTester/js/ImageExample.js
+++ b/RNTester/js/ImageExample.js
@@ -558,18 +558,16 @@ exports.examples = [
                     source={image}
                   />
                 </View>
-                { Platform.OS === 'ios' ?
-                  <View style={styles.leftMargin}>
-                    <Text style={[styles.resizeModeText]}>
-                      Repeat
-                    </Text>
-                    <Image
-                      style={styles.resizeMode}
-                      resizeMode={Image.resizeMode.repeat}
-                      source={image}
-                    />
-                  </View>
-                : null }
+                <View style={styles.leftMargin}>
+                  <Text style={[styles.resizeModeText]}>
+                    Repeat
+                  </Text>
+                  <Image
+                    style={styles.resizeMode}
+                    resizeMode={Image.resizeMode.repeat}
+                    source={image}
+                  />
+                </View>
                 <View style={styles.leftMargin}>
                   <Text style={[styles.resizeModeText]}>
                     Center
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ImageResizeMode.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ImageResizeMode.java
index 3cff8b9667a2..3f98058feedd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ImageResizeMode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ImageResizeMode.java
@@ -9,6 +9,7 @@
 
 import javax.annotation.Nullable;
 
+import android.graphics.Shader;
 import com.facebook.react.bridge.JSApplicationIllegalArgumentException;
 import com.facebook.drawee.drawable.ScalingUtils;
 
@@ -34,6 +35,10 @@ public static ScalingUtils.ScaleType toScaleType(@Nullable String resizeModeValu
     if ("center".equals(resizeModeValue)) {
       return ScalingUtils.ScaleType.CENTER_INSIDE;
     }
+    if ("repeat".equals(resizeModeValue)) {
+      // Handled via a combination of ScaleType and TileMode
+      return ScaleTypeStartInside.INSTANCE;
+    }
     if (resizeModeValue == null) {
       // Use the default. Never use null.
       return defaultValue();
@@ -42,6 +47,29 @@ public static ScalingUtils.ScaleType toScaleType(@Nullable String resizeModeValu
         "Invalid resize mode: '" + resizeModeValue + "'");
   }
 
+  /**
+   * Converts JS resize modes into {@code Shader.TileMode}.
+   * See {@code ImageResizeMode.js}.
+   */
+  public static Shader.TileMode toTileMode(@Nullable String resizeModeValue) {
+    if ("contain".equals(resizeModeValue)
+        || "cover".equals(resizeModeValue)
+        || "stretch".equals(resizeModeValue)
+        || "center".equals(resizeModeValue)) {
+      return Shader.TileMode.CLAMP;
+    }
+    if ("repeat".equals(resizeModeValue)) {
+      // Handled via a combination of ScaleType and TileMode
+      return Shader.TileMode.REPEAT;
+    }
+    if (resizeModeValue == null) {
+      // Use the default. Never use null.
+      return defaultTileMode();
+    }
+    throw new JSApplicationIllegalArgumentException(
+        "Invalid resize mode: '" + resizeModeValue + "'");
+  }
+
   /**
    * This is the default as per web and iOS.
    * We want to be consistent across platforms.
@@ -49,4 +77,8 @@ public static ScalingUtils.ScaleType toScaleType(@Nullable String resizeModeValu
   public static ScalingUtils.ScaleType defaultValue() {
     return ScalingUtils.ScaleType.CENTER_CROP;
   }
+
+  public static Shader.TileMode defaultTileMode() {
+    return Shader.TileMode.CLAMP;
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/MultiPostprocessor.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/MultiPostprocessor.java
new file mode 100644
index 000000000000..d6cf6a3ca8d6
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/MultiPostprocessor.java
@@ -0,0 +1,79 @@
+/**
+ * Copyright (c) 2017-present, Facebook, Inc.
+ * All rights reserved.
+ *
+ * This source code is licensed under the BSD-style license found in the
+ * LICENSE file in the root directory of this source tree. An additional grant
+ * of patent rights can be found in the PATENTS file in the same directory.
+ */
+
+package com.facebook.react.views.image;
+
+import android.graphics.Bitmap;
+
+import com.facebook.cache.common.CacheKey;
+import com.facebook.cache.common.MultiCacheKey;
+import com.facebook.common.references.CloseableReference;
+import com.facebook.imagepipeline.bitmaps.PlatformBitmapFactory;
+import com.facebook.imagepipeline.request.Postprocessor;
+
+import java.util.LinkedList;
+import java.util.List;
+
+public class MultiPostprocessor implements Postprocessor {
+  private final List<Postprocessor> mPostprocessors;
+
+  public static Postprocessor from(List<Postprocessor> postprocessors) {
+    switch (postprocessors.size()) {
+      case 0:
+        return null;
+      case 1:
+        return postprocessors.get(0);
+      default:
+        return new MultiPostprocessor(postprocessors);
+    }
+  }
+
+  private MultiPostprocessor(List<Postprocessor> postprocessors) {
+     mPostprocessors = new LinkedList<>(postprocessors);
+  }
+
+  @Override
+  public String getName () {
+    StringBuilder name = new StringBuilder();
+    for (Postprocessor p: mPostprocessors) {
+      if (name.length() > 0) {
+        name.append(",");
+      }
+      name.append(p.getName());
+    }
+    name.insert(0, "MultiPostProcessor (");
+    name.append(")");
+    return name.toString();
+  }
+
+  @Override
+  public CacheKey getPostprocessorCacheKey () {
+    LinkedList<CacheKey> keys = new LinkedList<>();
+    for (Postprocessor p: mPostprocessors) {
+      keys.push(p.getPostprocessorCacheKey());
+    }
+    return new MultiCacheKey(keys);
+  }
+
+  @Override
+  public CloseableReference<Bitmap>	process(Bitmap sourceBitmap, PlatformBitmapFactory bitmapFactory) {
+    CloseableReference<Bitmap> prevBitmap = null, nextBitmap = null;
+
+    try {
+      for (Postprocessor p : mPostprocessors) {
+        nextBitmap = p.process(prevBitmap != null ? prevBitmap.get() : sourceBitmap, bitmapFactory);
+        CloseableReference.closeSafely(prevBitmap);
+        prevBitmap = nextBitmap.clone();
+      }
+      return nextBitmap.clone();
+    } finally {
+      CloseableReference.closeSafely(nextBitmap);
+    }
+  }
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageManager.java
index 21014c5c7b0f..938524d30121 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageManager.java
@@ -139,6 +139,7 @@ public void setBorderRadius(ReactImageView view, int index, float borderRadius)
   @ReactProp(name = ViewProps.RESIZE_MODE)
   public void setResizeMode(ReactImageView view, @Nullable String resizeMode) {
     view.setScaleType(ImageResizeMode.toScaleType(resizeMode));
+    view.setTileMode(ImageResizeMode.toTileMode(resizeMode));
   }
 
   @ReactProp(name = ViewProps.RESIZE_METHOD)
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index 3fa2e66eb82e..9396cac1c5c1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -22,6 +22,7 @@
 import android.graphics.drawable.Drawable;
 import android.net.Uri;
 import android.widget.Toast;
+import com.facebook.common.references.CloseableReference;
 import com.facebook.common.util.UriUtil;
 import com.facebook.drawee.controller.AbstractDraweeControllerBuilder;
 import com.facebook.drawee.controller.BaseControllerListener;
@@ -33,6 +34,7 @@
 import com.facebook.drawee.generic.GenericDraweeHierarchyBuilder;
 import com.facebook.drawee.generic.RoundingParams;
 import com.facebook.drawee.view.GenericDraweeView;
+import com.facebook.imagepipeline.bitmaps.PlatformBitmapFactory;
 import com.facebook.imagepipeline.common.ResizeOptions;
 import com.facebook.imagepipeline.image.ImageInfo;
 import com.facebook.imagepipeline.postprocessors.IterativeBoxBlurPostProcessor;
@@ -49,6 +51,7 @@
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
+import com.facebook.react.views.image.ImageResizeMode;
 import com.facebook.react.views.imagehelper.ImageSource;
 import com.facebook.react.views.imagehelper.MultiSourceHelper;
 import com.facebook.react.views.imagehelper.MultiSourceHelper.MultiSourceResult;
@@ -141,6 +144,40 @@ public void process(Bitmap output, Bitmap source) {
     }
   }
 
+  // Fresco lacks support for repeating images, see https://github.com/facebook/fresco/issues/1575
+  // We implement it here as a postprocessing step.
+  private static final Matrix sTileMatrix = new Matrix();
+
+  private class TilePostprocessor extends BasePostprocessor {
+    @Override
+    public CloseableReference<Bitmap> process(Bitmap source, PlatformBitmapFactory bitmapFactory) {
+      final Rect destRect = new Rect(0, 0, getWidth(), getHeight());
+
+      mScaleType.getTransform(
+        sTileMatrix,
+        destRect,
+        source.getWidth(),
+        source.getHeight(),
+        0.0f,
+        0.0f);
+
+      Paint paint = new Paint();
+      paint.setAntiAlias(true);
+      Shader shader = new BitmapShader(source, mTileMode, mTileMode);
+      shader.setLocalMatrix(sTileMatrix);
+      paint.setShader(shader);
+
+      CloseableReference<Bitmap> output = bitmapFactory.createBitmap(getWidth(), getHeight());
+      try {
+        Canvas canvas = new Canvas(output.get());
+        canvas.drawRect(destRect, paint);
+        return output.clone();
+      } finally {
+        CloseableReference.closeSafely(output);
+      }
+    }
+  }
+
   private final List<ImageSource> mSources;
 
   private @Nullable ImageSource mImageSource;
@@ -152,9 +189,11 @@ public void process(Bitmap output, Bitmap source) {
   private float mBorderRadius = YogaConstants.UNDEFINED;
   private @Nullable float[] mBorderCornerRadii;
   private ScalingUtils.ScaleType mScaleType;
+  private Shader.TileMode mTileMode = ImageResizeMode.defaultTileMode();
   private boolean mIsDirty;
   private final AbstractDraweeControllerBuilder mDraweeControllerBuilder;
   private final RoundedCornerPostprocessor mRoundedCornerPostprocessor;
+  private final TilePostprocessor mTilePostprocessor;
   private @Nullable IterativeBoxBlurPostProcessor mIterativeBoxBlurPostProcessor;
   private @Nullable ControllerListener mControllerListener;
   private @Nullable ControllerListener mControllerForTesting;
@@ -180,6 +219,7 @@ public ReactImageView(
     mScaleType = ImageResizeMode.defaultValue();
     mDraweeControllerBuilder = draweeControllerBuilder;
     mRoundedCornerPostprocessor = new RoundedCornerPostprocessor();
+    mTilePostprocessor = new TilePostprocessor();
     mGlobalImageLoadListener = globalImageLoadListener;
     mCallerContext = callerContext;
     mSources = new LinkedList<>();
@@ -275,6 +315,11 @@ public void setScaleType(ScalingUtils.ScaleType scaleType) {
     mIsDirty = true;
   }
 
+  public void setTileMode(Shader.TileMode tileMode) {
+    mTileMode = tileMode;
+    mIsDirty = true;
+  }
+
   public void setResizeMethod(ImageResizeMethod resizeMethod) {
     mResizeMethod = resizeMethod;
     mIsDirty = true;
@@ -362,6 +407,11 @@ public void maybeUpdateView() {
       return;
     }
 
+    if (isTiled() && (getWidth() <= 0 || getHeight() <= 0)) {
+      // If need to tile and the size is not yet set, wait until the layout pass provides one
+      return;
+    }
+
     GenericDraweeHierarchy hierarchy = getHierarchy();
     hierarchy.setActualImageScaleType(mScaleType);
 
@@ -396,13 +446,17 @@ public void maybeUpdateView() {
             ? mFadeDurationMs
             : mImageSource.isResource() ? 0 : REMOTE_IMAGE_FADE_DURATION_MS);
 
-    // TODO: t13601664 Support multiple PostProcessors
-    Postprocessor postprocessor = null;
+    List<Postprocessor> postprocessors = new LinkedList<>();
     if (usePostprocessorScaling) {
-      postprocessor = mRoundedCornerPostprocessor;
-    } else if (mIterativeBoxBlurPostProcessor != null) {
-      postprocessor = mIterativeBoxBlurPostProcessor;
+      postprocessors.add(mRoundedCornerPostprocessor);
+    }
+    if (mIterativeBoxBlurPostProcessor != null) {
+      postprocessors.add(mIterativeBoxBlurPostProcessor);
+    }
+    if (isTiled()) {
+      postprocessors.add(mTilePostprocessor);
     }
+    Postprocessor postprocessor = MultiPostprocessor.from(postprocessors);
 
     ResizeOptions resizeOptions = doResize ? new ResizeOptions(getWidth(), getHeight()) : null;
 
@@ -468,7 +522,7 @@ public void setControllerListener(ControllerListener controllerListener) {
   protected void onSizeChanged(int w, int h, int oldw, int oldh) {
     super.onSizeChanged(w, h, oldw, oldh);
     if (w > 0 && h > 0) {
-      mIsDirty = mIsDirty || hasMultipleSources();
+      mIsDirty = mIsDirty || hasMultipleSources() || isTiled();
       maybeUpdateView();
     }
   }
@@ -485,6 +539,10 @@ private boolean hasMultipleSources() {
     return mSources.size() > 1;
   }
 
+  private boolean isTiled() {
+    return mTileMode != Shader.TileMode.CLAMP;
+  }
+
   private void setSourceImage() {
     mImageSource = null;
     if (mSources.isEmpty()) {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ScaleTypeStartInside.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ScaleTypeStartInside.java
new file mode 100644
index 000000000000..e2b902b2c524
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ScaleTypeStartInside.java
@@ -0,0 +1,40 @@
+/**
+ * Copyright (c) 2017-present, Facebook, Inc.
+ * All rights reserved.
+ *
+ * This source code is licensed under the BSD-style license found in the
+ * LICENSE file in the root directory of this source tree. An additional grant
+ * of patent rights can be found in the PATENTS file in the same directory.
+ */
+
+package com.facebook.react.views.image;
+
+import android.graphics.Matrix;
+import android.graphics.Rect;
+import com.facebook.drawee.drawable.ScalingUtils;
+
+public class ScaleTypeStartInside extends ScalingUtils.AbstractScaleType {
+  public static final ScalingUtils.ScaleType INSTANCE = new ScaleTypeStartInside();
+
+  @Override
+  public void getTransformImpl(
+      Matrix outTransform,
+      Rect parentRect,
+      int childWidth,
+      int childHeight,
+      float focusX,
+      float focusY,
+      float scaleX,
+      float scaleY) {
+    float scale = Math.min(Math.min(scaleX, scaleY), 1.0f);
+    float dx = parentRect.left;
+    float dy = parentRect.top;
+    outTransform.setScale(scale, scale);
+    outTransform.postTranslate((int) (dx + 0.5f), (int) (dy + 0.5f));
+  }
+
+  @Override
+  public String toString() {
+    return "start_inside";
+  }
+}

From ab92c00245c0ce717819ddb0ab8b9204d4c13c34 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 12 Mar 2018 17:39:54 -0700
Subject: [PATCH 0003/1109] Convert Text to ES6 Class

Summary: Utilizing ES6 Classes instead of createReactClass lets us actually enforce the way Text is used via Flow.

Reviewed By: fkgozali

Differential Revision: D7227755

fbshipit-source-id: 8e8285f9ebb3783a0dc4837c37c163178910ff9f
---
 Libraries/Text/Text.js | 107 +++++++++++++++++++++++------------------
 1 file changed, 59 insertions(+), 48 deletions(-)

diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index 866f46819e9b..83b02877b883 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -10,19 +10,35 @@
  */
 'use strict';
 
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const React = require('React');
+const ReactNative = require('ReactNative');
 const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const TextPropTypes = require('TextPropTypes');
 const Touchable = require('Touchable');
 const UIManager = require('UIManager');
 
-const createReactClass = require('create-react-class');
 const createReactNativeComponentClass = require('createReactNativeComponentClass');
 const mergeFast = require('mergeFast');
 const processColor = require('processColor');
 const {ViewContextTypes} = require('ViewContext');
 
+import type {PressEvent} from 'CoreEventTypes';
+import type {TextProps} from 'TextProps';
+import type {ViewChildContext} from 'ViewContext';
+
+type State = {
+  isHighlighted: boolean,
+};
+
+type RectOffset = {
+  top: number,
+  left: number,
+  right: number,
+  bottom: number,
+};
+
+const PRESS_RECT_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
+
 const viewConfig = {
   validAttributes: mergeFast(ReactNativeViewAttributes.UIView, {
     isHighlighted: true,
@@ -39,54 +55,54 @@ const viewConfig = {
   uiViewClassName: 'RCTText',
 };
 
-import type {ViewChildContext} from 'ViewContext';
-
 /**
  * A React component for displaying text.
  *
  * See https://facebook.github.io/react-native/docs/text.html
  */
+class Text extends ReactNative.NativeComponent<TextProps, State> {
+  static propTypes = TextPropTypes;
+  static childContextTypes = ViewContextTypes;
+  static contextTypes = ViewContextTypes;
+
+  static defaultProps = {
+    accessible: true,
+    allowFontScaling: true,
+    ellipsizeMode: 'tail',
+  };
+
+  state = mergeFast(Touchable.Mixin.touchableGetInitialState(), {
+    isHighlighted: false,
+  });
+
+  viewConfig = viewConfig;
 
-const Text = createReactClass({
-  displayName: 'Text',
-  propTypes: TextPropTypes,
-  getDefaultProps(): Object {
-    return {
-      accessible: true,
-      allowFontScaling: true,
-      ellipsizeMode: 'tail',
-    };
-  },
-  getInitialState: function(): Object {
-    return mergeFast(Touchable.Mixin.touchableGetInitialState(), {
-      isHighlighted: false,
-    });
-  },
-  mixins: [NativeMethodsMixin],
-  viewConfig: viewConfig,
   getChildContext(): ViewChildContext {
     return {
       isInAParentText: true,
     };
-  },
-  childContextTypes: ViewContextTypes,
-  contextTypes: ViewContextTypes,
-  /**
-   * Only assigned if touch is needed.
-   */
-  _handlers: (null: ?Object),
+  }
+
+  _handlers: ?Object;
+
   _hasPressHandler(): boolean {
     return !!this.props.onPress || !!this.props.onLongPress;
-  },
+  }
   /**
    * These are assigned lazily the first time the responder is set to make plain
    * text nodes as cheap as possible.
    */
-  touchableHandleActivePressIn: (null: ?Function),
-  touchableHandleActivePressOut: (null: ?Function),
-  touchableHandlePress: (null: ?Function),
-  touchableHandleLongPress: (null: ?Function),
-  touchableGetPressRectOffset: (null: ?Function),
+  touchableHandleActivePressIn: ?Function;
+  touchableHandleActivePressOut: ?Function;
+  touchableHandlePress: ?Function;
+  touchableHandleLongPress: ?Function;
+  touchableHandleResponderGrant: ?Function;
+  touchableHandleResponderMove: ?Function;
+  touchableHandleResponderRelease: ?Function;
+  touchableHandleResponderTerminate: ?Function;
+  touchableHandleResponderTerminationRequest: ?Function;
+  touchableGetPressRectOffset: ?Function;
+
   render(): React.Element<any> {
     let newProps = this.props;
     if (this.props.onStartShouldSetResponder || this._hasPressHandler()) {
@@ -95,7 +111,6 @@ const Text = createReactClass({
           onStartShouldSetResponder: (): boolean => {
             const shouldSetFromProps =
               this.props.onStartShouldSetResponder &&
-              // $FlowFixMe(>=0.41.0)
               this.props.onStartShouldSetResponder();
             const setResponder = shouldSetFromProps || this._hasPressHandler();
             if (setResponder && !this.touchableHandleActivePressIn) {
@@ -130,11 +145,11 @@ const Text = createReactClass({
                 });
               };
 
-              this.touchableHandlePress = (e: SyntheticEvent<>) => {
+              this.touchableHandlePress = (e: PressEvent) => {
                 this.props.onPress && this.props.onPress(e);
               };
 
-              this.touchableHandleLongPress = (e: SyntheticEvent<>) => {
+              this.touchableHandleLongPress = (e: PressEvent) => {
                 this.props.onLongPress && this.props.onLongPress(e);
               };
 
@@ -145,21 +160,25 @@ const Text = createReactClass({
             return setResponder;
           },
           onResponderGrant: function(e: SyntheticEvent<>, dispatchID: string) {
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
             this.touchableHandleResponderGrant(e, dispatchID);
             this.props.onResponderGrant &&
               this.props.onResponderGrant.apply(this, arguments);
           }.bind(this),
           onResponderMove: function(e: SyntheticEvent<>) {
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
             this.touchableHandleResponderMove(e);
             this.props.onResponderMove &&
               this.props.onResponderMove.apply(this, arguments);
           }.bind(this),
           onResponderRelease: function(e: SyntheticEvent<>) {
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
             this.touchableHandleResponderRelease(e);
             this.props.onResponderRelease &&
               this.props.onResponderRelease.apply(this, arguments);
           }.bind(this),
           onResponderTerminate: function(e: SyntheticEvent<>) {
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
             this.touchableHandleResponderTerminate(e);
             this.props.onResponderTerminate &&
               this.props.onResponderTerminate.apply(this, arguments);
@@ -167,6 +186,7 @@ const Text = createReactClass({
           onResponderTerminationRequest: function(): boolean {
             // Allow touchable or props.onResponderTerminationRequest to deny
             // the request
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
             var allowTermination = this.touchableHandleResponderTerminationRequest();
             if (allowTermination && this.props.onResponderTerminationRequest) {
               allowTermination = this.props.onResponderTerminationRequest.apply(
@@ -201,17 +221,8 @@ const Text = createReactClass({
     } else {
       return <RCTText {...newProps} />;
     }
-  },
-});
-
-type RectOffset = {
-  top: number,
-  left: number,
-  right: number,
-  bottom: number,
-};
-
-var PRESS_RECT_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
+  }
+}
 
 var RCTText = createReactNativeComponentClass(
   viewConfig.uiViewClassName,

From 7a1c618de6a222f90f6525e7756a018e83b9134a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Mon, 12 Mar 2018 20:20:21 -0700
Subject: [PATCH 0004/1109] Change newly imported file to MIT license

Summary:
The project at large switched to MIT last month. A PR that was opened prior to the change was merged, this PR updates the file to use the correct license.

None, trivial PR

[ANDROID] [MINOR] [Image] Update license
Closes https://github.com/facebook/react-native/pull/18343

Differential Revision: D7252836

Pulled By: hramos

fbshipit-source-id: b7c207c782f4bf19c12d121e86f394e52326a5ab
---
 .../com/facebook/react/views/image/MultiPostprocessor.java  | 6 ++----
 1 file changed, 2 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/MultiPostprocessor.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/MultiPostprocessor.java
index d6cf6a3ca8d6..03ad027c2618 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/MultiPostprocessor.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/MultiPostprocessor.java
@@ -1,10 +1,8 @@
 /**
  * Copyright (c) 2017-present, Facebook, Inc.
- * All rights reserved.
  *
- * This source code is licensed under the BSD-style license found in the
- * LICENSE file in the root directory of this source tree. An additional grant
- * of patent rights can be found in the PATENTS file in the same directory.
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
  */
 
 package com.facebook.react.views.image;

From aa323d4aa9d87874f45eda8a4798086fa91fd08e Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 13 Mar 2018 10:28:43 -0700
Subject: [PATCH 0005/1109] Use MIT license

Summary: Closes https://github.com/facebook/react-native/pull/18352

Differential Revision: D7257144

Pulled By: hramos

fbshipit-source-id: 477ff82f74cfa3fd0681c9522cc5199a60b24921
---
 .../facebook/react/views/image/ScaleTypeStartInside.java    | 6 ++----
 1 file changed, 2 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ScaleTypeStartInside.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ScaleTypeStartInside.java
index e2b902b2c524..96640d044d5a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ScaleTypeStartInside.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ScaleTypeStartInside.java
@@ -1,10 +1,8 @@
 /**
  * Copyright (c) 2017-present, Facebook, Inc.
- * All rights reserved.
  *
- * This source code is licensed under the BSD-style license found in the
- * LICENSE file in the root directory of this source tree. An additional grant
- * of patent rights can be found in the PATENTS file in the same directory.
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
  */
 
 package com.facebook.react.views.image;

From c136c54ff0211e2bf149fab600cd6e295f9d19dd Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Tue, 13 Mar 2018 11:05:53 -0700
Subject: [PATCH 0006/1109] Refactor RCTInputAccessoryView view hierarchy and
 names

Reviewed By: shergin

Differential Revision: D7196162

fbshipit-source-id: 07a5c13d4cdb876f5a632d7d53859eab5e235f49
---
 .../Text/TextInput/RCTBaseTextInputView.m     |  2 +-
 .../Text/TextInput/RCTInputAccessoryView.h    |  2 -
 .../Text/TextInput/RCTInputAccessoryView.m    | 38 +++++++-----
 .../TextInput/RCTInputAccessoryViewContent.h  |  2 -
 .../TextInput/RCTInputAccessoryViewContent.m  | 58 +++++++++----------
 .../TextInput/RCTInputAccessoryViewManager.m  |  2 +-
 6 files changed, 52 insertions(+), 52 deletions(-)

diff --git a/Libraries/Text/TextInput/RCTBaseTextInputView.m b/Libraries/Text/TextInput/RCTBaseTextInputView.m
index d9c47ff16311..65885a4882a6 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputView.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputView.m
@@ -419,7 +419,7 @@ - (void)setCustomInputAccessoryViewWithNativeID:(NSString *)nativeID
       UIView *accessoryView = [strongSelf->_bridge.uiManager viewForNativeID:nativeID
                                                                  withRootTag:rootView.reactTag];
       if (accessoryView && [accessoryView isKindOfClass:[RCTInputAccessoryView class]]) {
-        strongSelf.backedTextInputView.inputAccessoryView = ((RCTInputAccessoryView *)accessoryView).content.inputAccessoryView;
+        strongSelf.backedTextInputView.inputAccessoryView = ((RCTInputAccessoryView *)accessoryView).inputAccessoryView;
         [strongSelf reloadInputViewsIfNecessary];
       }
     }
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryView.h b/Libraries/Text/TextInput/RCTInputAccessoryView.h
index b2517534baf3..207203fc2232 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryView.h
+++ b/Libraries/Text/TextInput/RCTInputAccessoryView.h
@@ -14,6 +14,4 @@
 
 - (instancetype)initWithBridge:(RCTBridge *)bridge;
 
-@property (nonatomic, readonly, strong) RCTInputAccessoryViewContent *content;
-
 @end
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryView.m b/Libraries/Text/TextInput/RCTInputAccessoryView.m
index a1902a80ea5f..1f66e473966c 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryView.m
+++ b/Libraries/Text/TextInput/RCTInputAccessoryView.m
@@ -13,56 +13,66 @@
 
 #import "RCTInputAccessoryViewContent.h"
 
+@interface RCTInputAccessoryView()
+
+// Overriding `inputAccessoryView` to `readwrite`.
+@property (nonatomic, readwrite, retain) UIView *inputAccessoryView;
+
+@end
+
 @implementation RCTInputAccessoryView
 {
-  BOOL _contentShouldBeFirstResponder;
+  BOOL _shouldBecomeFirstResponder;
 }
 
 - (instancetype)initWithBridge:(RCTBridge *)bridge
 {
   if (self = [super init]) {
-    _content = [RCTInputAccessoryViewContent new];
+    _inputAccessoryView = [RCTInputAccessoryViewContent new];
     RCTTouchHandler *const touchHandler = [[RCTTouchHandler alloc] initWithBridge:bridge];
-    [touchHandler attachToView:_content.inputAccessoryView];
-    [self addSubview:_content];
+    [touchHandler attachToView:_inputAccessoryView];
   }
   return self;
 }
 
+- (BOOL)canBecomeFirstResponder
+{
+  return true;
+}
+
 - (void)reactSetFrame:(CGRect)frame
 {
-  [_content.inputAccessoryView setFrame:frame];
-  [_content.contentView setFrame:frame];
+  [_inputAccessoryView setFrame:frame];
 
-  if (_contentShouldBeFirstResponder) {
-    _contentShouldBeFirstResponder = NO;
-    [_content becomeFirstResponder];
+  if (_shouldBecomeFirstResponder) {
+    _shouldBecomeFirstResponder = NO;
+    [self becomeFirstResponder];
   }
 }
 
 - (void)insertReactSubview:(UIView *)subview atIndex:(NSInteger)index
 {
   [super insertReactSubview:subview atIndex:index];
-  [_content insertReactSubview:subview atIndex:index];
+  [_inputAccessoryView insertReactSubview:subview atIndex:index];
 }
 
 - (void)removeReactSubview:(UIView *)subview
 {
   [super removeReactSubview:subview];
-  [_content removeReactSubview:subview];
+  [_inputAccessoryView removeReactSubview:subview];
 }
 
 - (void)didUpdateReactSubviews
 {
-  // Do nothing, as subviews are managed by `insertReactSubview:atIndex:`
+  // Do nothing, as subviews are managed by `insertReactSubview:atIndex:`.
 }
 
 - (void)didSetProps:(NSArray<NSString *> *)changedProps
 {
   // If the accessory view is not linked to a text input via nativeID, assume it is
-  // a standalone component that should get focus whenever it is rendered
+  // a standalone component that should get focus whenever it is rendered.
   if (![changedProps containsObject:@"nativeID"] && !self.nativeID) {
-    _contentShouldBeFirstResponder = YES;
+    _shouldBecomeFirstResponder = YES;
   }
 }
 
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryViewContent.h b/Libraries/Text/TextInput/RCTInputAccessoryViewContent.h
index 7c24d010e2d2..7dca711a648d 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryViewContent.h
+++ b/Libraries/Text/TextInput/RCTInputAccessoryViewContent.h
@@ -9,6 +9,4 @@
 
 @interface RCTInputAccessoryViewContent : UIView
 
-@property (nonatomic, readwrite, retain) UIView *contentView;
-
 @end
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryViewContent.m b/Libraries/Text/TextInput/RCTInputAccessoryViewContent.m
index 3fb7fca715c6..73ec648ad8e1 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryViewContent.m
+++ b/Libraries/Text/TextInput/RCTInputAccessoryViewContent.m
@@ -9,65 +9,59 @@
 
 #import <React/UIView+React.h>
 
-@interface RCTInputAccessoryViewContent()
-
-// Overriding `inputAccessoryView` to `readwrite`.
-@property (nonatomic, readwrite, retain) UIView *inputAccessoryView;
-
-@end
-
 @implementation RCTInputAccessoryViewContent
+{
+  UIView *_safeAreaContainer;
+}
 
-- (BOOL)canBecomeFirstResponder
+- (instancetype)init
 {
-  return true;
+  if (self = [super init]) {
+    _safeAreaContainer = [UIView new];
+    [self addSubview:_safeAreaContainer];
+  }
+  return self;
 }
 
-- (BOOL)becomeFirstResponder
+- (void)didMoveToSuperview
 {
-  const BOOL becameFirstResponder = [super becomeFirstResponder];
 
-  #if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
-  // Avoiding the home pill and notch (landscape mode) on iphoneX.
-  if (becameFirstResponder) {
-    if (@available(iOS 11.0, *)) {
-      [_contentView.bottomAnchor
-       constraintLessThanOrEqualToSystemSpacingBelowAnchor:_contentView.window.safeAreaLayoutGuide.bottomAnchor
+#if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
+  // Avoid the home pill (in portrait mode) and notch (in landscape mode) on iPhoneX.
+  if (@available(iOS 11.0, *)) {
+    if (self.window) {
+      [_safeAreaContainer.bottomAnchor
+       constraintLessThanOrEqualToSystemSpacingBelowAnchor:self.window.safeAreaLayoutGuide.bottomAnchor
        multiplier:1.0f].active = YES;
-      [_contentView.leftAnchor
-       constraintLessThanOrEqualToSystemSpacingAfterAnchor:_contentView.window.safeAreaLayoutGuide.leftAnchor
+      [_safeAreaContainer.leftAnchor
+       constraintGreaterThanOrEqualToSystemSpacingAfterAnchor:self.window.safeAreaLayoutGuide.leftAnchor
        multiplier:1.0f].active = YES;
-      [_contentView.rightAnchor
-       constraintLessThanOrEqualToSystemSpacingAfterAnchor:_contentView.window.safeAreaLayoutGuide.rightAnchor
+      [_safeAreaContainer.rightAnchor
+       constraintLessThanOrEqualToSystemSpacingAfterAnchor:self.window.safeAreaLayoutGuide.rightAnchor
        multiplier:1.0f].active = YES;
     }
   }
-  #endif
+#endif
 
-  return becameFirstResponder;
 }
 
-- (UIView *)inputAccessoryView
+- (void)setFrame:(CGRect)frame
 {
-  if (!_inputAccessoryView) {
-    _inputAccessoryView = [UIView new];
-    _contentView = [UIView new];
-    [_inputAccessoryView addSubview:_contentView];
-  }
-  return _inputAccessoryView;
+  [super setFrame:frame];
+  [_safeAreaContainer setFrame:frame];
 }
 
 - (void)insertReactSubview:(UIView *)subview atIndex:(NSInteger)index
 {
   [super insertReactSubview:subview atIndex:index];
-  [_contentView insertSubview:subview atIndex:index];
+  [_safeAreaContainer insertSubview:subview atIndex:index];
 }
 
 - (void)removeReactSubview:(UIView *)subview
 {
   [super removeReactSubview:subview];
   [subview removeFromSuperview];
-  if ([[_inputAccessoryView subviews] count] == 0 && [self isFirstResponder]) {
+  if ([[_safeAreaContainer subviews] count] == 0 && [self isFirstResponder]) {
     [self resignFirstResponder];
   }
 }
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryViewManager.m b/Libraries/Text/TextInput/RCTInputAccessoryViewManager.m
index b293889eb6de..aeeff835e844 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryViewManager.m
+++ b/Libraries/Text/TextInput/RCTInputAccessoryViewManager.m
@@ -23,6 +23,6 @@ - (UIView *)view
   return [[RCTInputAccessoryView alloc] initWithBridge:self.bridge];
 }
 
-RCT_REMAP_VIEW_PROPERTY(backgroundColor, content.inputAccessoryView.backgroundColor, UIColor)
+RCT_REMAP_VIEW_PROPERTY(backgroundColor, inputAccessoryView.backgroundColor, UIColor)
 
 @end

From ca898f4367083e0943603521a41c48dec403e6c9 Mon Sep 17 00:00:00 2001
From: Teddy Martin <ejmartin504@gmail.com>
Date: Tue, 13 Mar 2018 15:17:28 -0700
Subject: [PATCH 0007/1109] Add docs for Swift usage to RCTBridgeModule.h

Summary:
Clarifies how to get a reference to RCTBridge from a Swift RCTBridgeModule.

<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

In writing native modules for Swift, I have run into issues where the documentation applies only to Objective-C and does not supply adequate information for how one might accomplish something in Swift.

This is a good example, where the `synthesize` method simply does not apply to Swift code.

[IOS][ENHANCEMENT][Base/RCTBridgeModule.h] Add documentation for Swift usage.
<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[CATEGORY] [TYPE] [LOCATION] - MESSAGE

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18231

Differential Revision: D7262850

Pulled By: hramos

fbshipit-source-id: c6babb3edd786be8571eb49258d594f2fb99141d
---
 React/Base/RCTBridgeModule.h | 1 +
 1 file changed, 1 insertion(+)

diff --git a/React/Base/RCTBridgeModule.h b/React/Base/RCTBridgeModule.h
index 07116bb80ef9..75908a1b0f79 100644
--- a/React/Base/RCTBridgeModule.h
+++ b/React/Base/RCTBridgeModule.h
@@ -83,6 +83,7 @@ RCT_EXTERN void RCTRegisterModule(Class); \
  * to bridge features, such as sending events or making JS calls. This
  * will be set automatically by the bridge when it initializes the module.
  * To implement this in your module, just add `@synthesize bridge = _bridge;`
+ * If using Swift, add `@objc var bridge: RCTBridge!` to your module.
  */
 @property (nonatomic, weak, readonly) RCTBridge *bridge;
 

From 41acb0a75b1ed5b4cf2feb74c64113a06a284e85 Mon Sep 17 00:00:00 2001
From: Naris Siamwalla <naris@fb.com>
Date: Tue, 13 Mar 2018 16:16:27 -0700
Subject: [PATCH 0008/1109] Fix clang-6 compile error (virtual destructor)

Reviewed By: smeenai

Differential Revision: D7264312

fbshipit-source-id: f0567452127ceba6cfa13d05bb2a00a5af7aac05
---
 React/Fabric/RCTFabricPlatformUIOperationManager.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/Fabric/RCTFabricPlatformUIOperationManager.h b/React/Fabric/RCTFabricPlatformUIOperationManager.h
index 2e9df3c77044..2043959760ea 100644
--- a/React/Fabric/RCTFabricPlatformUIOperationManager.h
+++ b/React/Fabric/RCTFabricPlatformUIOperationManager.h
@@ -24,7 +24,7 @@ namespace react {
 class RCTFabricPlatformUIOperationManagerConnector : public IFabricPlatformUIOperationManager {
 public:
   RCTFabricPlatformUIOperationManagerConnector();
-  ~RCTFabricPlatformUIOperationManagerConnector();
+  virtual ~RCTFabricPlatformUIOperationManagerConnector();
 
   void performUIOperation();
 

From 9737774b965d1b4e875f697b9c004fdcbafe7698 Mon Sep 17 00:00:00 2001
From: Ram N <axe@fb.com>
Date: Tue, 13 Mar 2018 17:56:33 -0700
Subject: [PATCH 0009/1109] Fix crash in Sapienz bot for Interpolator type

Reviewed By: mdvacca

Differential Revision: D7252818

fbshipit-source-id: 30c585a2e6f6c2d7a7e7013c26c6228d8ef29aa6
---
 .../layoutanimation/AbstractLayoutAnimation.java          | 8 ++------
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
index 1ad6ccab3946..67e7f19d2c3f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
@@ -2,7 +2,6 @@
 
 package com.facebook.react.uimanager.layoutanimation;
 
-import android.os.Build;
 import android.view.View;
 import android.view.animation.AccelerateDecelerateInterpolator;
 import android.view.animation.AccelerateInterpolator;
@@ -99,14 +98,11 @@ public void initializeFromConfig(ReadableMap data, int globalDuration) {
   }
 
   private static Interpolator getInterpolator(InterpolatorType type, ReadableMap params) {
-     Interpolator interpolator = null;
+     Interpolator interpolator;
      if (type.equals(InterpolatorType.SPRING)) {
        interpolator = new SimpleSpringInterpolator(SimpleSpringInterpolator.getSpringDamping(params));
      } else {
-       if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP_MR1) {
-         // Conversion from BaseInterpolator to Interpolator is only possible on this Android versions
-         interpolator = INTERPOLATOR.get(type);
-       }
+       interpolator = INTERPOLATOR.get(type);
      }
     if (interpolator == null) {
       throw new IllegalArgumentException("Missing interpolator for type : " + type);

From db061ea8c7b78d7e9df4a450c9e7a24d9b2382b4 Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Tue, 13 Mar 2018 17:57:36 -0700
Subject: [PATCH 0010/1109] Don't wrap ListEmptyComponent in an extra view

Summary:
A common UI pattern for list empty states is some text/images centered inside the visible part of the list. This is pretty hard to do currently because we wrap ListEmptyComponent with an extra view with no way to style it so we cannot just use `flex: 1` to make it fill the available space.

- Added an example of ListEmptyComponent in the FlatList example in RNTester

Before (no way to make ListEmptyComponent fill the space):
<img width="377" alt="screen shot 2018-03-05 at 5 24 15 pm" src="https://user-images.githubusercontent.com/2677334/37003152-129db3ac-209a-11e8-9600-110f10d57144.png">

After:
<img width="377" alt="screen shot 2018-03-05 at 5 09 20 pm" src="https://user-images.githubusercontent.com/2677334/37002809-e6971178-2098-11e8-8cf7-74bfb2f6a992.png">

- Tested some edge cases like returning null from the ListEmptyComponent

- Tested in an app that uses FlatList + ListEmptyComponent

[GENERAL] [MINOR] [VirtualizedList] - Don't wrap ListEmptyComponent in an extra view
Closes https://github.com/facebook/react-native/pull/18206

Differential Revision: D7266274

Pulled By: sahrens

fbshipit-source-id: 4636d2418474a4c86ac63e5e18a9afc391a518c5
---
 Libraries/Lists/VirtualizedList.js            | 26 ++++++++++---------
 .../VirtualizedList-test.js.snap              |  7 +----
 RNTester/js/FlatListExample.js                |  9 +++++--
 RNTester/js/ListExampleShared.js              | 16 ++++++++++++
 4 files changed, 38 insertions(+), 20 deletions(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 58fe055a373c..8ee3da2ea4f4 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -850,23 +850,25 @@ class VirtualizedList extends React.PureComponent<Props, State> {
         );
       }
     } else if (ListEmptyComponent) {
-      const element = React.isValidElement(ListEmptyComponent) ? (
+      const element: React.Element<any> = (React.isValidElement(
+        ListEmptyComponent,
+      ) ? (
         ListEmptyComponent
       ) : (
         // $FlowFixMe
         <ListEmptyComponent />
-      );
+      ): any);
       cells.push(
-        <View
-          key="$empty"
-          onLayout={this._onLayoutEmpty}
-          style={inversionStyle}>
-          {/*
-            Flow doesn't know this is a React.Element and not a React.Component
-            $FlowFixMe https://fburl.com/b9xmtm09
-          */}
-          {element}
-        </View>,
+        React.cloneElement(element, {
+          key: '$empty',
+          onLayout: event => {
+            this._onLayoutEmpty(event);
+            if (element.props.onLayout) {
+              element.props.onLayout(event);
+            }
+          },
+          style: [element.props.style, inversionStyle],
+        }),
       );
     }
     if (ListFooterComponent) {
diff --git a/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap b/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
index 7ebe23df2318..9cf5c2d9ea29 100644
--- a/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
+++ b/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
@@ -683,12 +683,7 @@ exports[`VirtualizedList renders empty list with empty component 1`] = `
     >
       <header />
     </View>
-    <View
-      onLayout={[Function]}
-      style={null}
-    >
-      <empty />
-    </View>
+    <empty />
     <View
       onLayout={[Function]}
       style={null}
diff --git a/RNTester/js/FlatListExample.js b/RNTester/js/FlatListExample.js
index 9effcf9396c9..9ec623fc86aa 100644
--- a/RNTester/js/FlatListExample.js
+++ b/RNTester/js/FlatListExample.js
@@ -27,6 +27,7 @@ const {
   FooterComponent,
   HeaderComponent,
   ItemComponent,
+  ListEmptyComponent,
   ItemSeparatorComponent,
   PlainInput,
   SeparatorComponent,
@@ -58,6 +59,7 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
     fixedHeight: true,
     logViewable: false,
     virtualized: true,
+    empty: false,
   };
 
   _onChangeFilterText = (filterText) => {
@@ -109,8 +111,9 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
               {renderSmallSwitchOption(this, 'virtualized')}
               {renderSmallSwitchOption(this, 'horizontal')}
               {renderSmallSwitchOption(this, 'fixedHeight')}
-              {renderSmallSwitchOption(this, 'logViewable')}
+              {renderSmallSwitchOption(this, 'log')}
               {renderSmallSwitchOption(this, 'inverted')}
+              {renderSmallSwitchOption(this, 'empty')}
               {renderSmallSwitchOption(this, 'debug')}
               <Spindicator value={this._scrollPos} />
             </View>
@@ -120,7 +123,8 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
             ItemSeparatorComponent={ItemSeparatorComponent}
             ListHeaderComponent={<HeaderComponent />}
             ListFooterComponent={FooterComponent}
-            data={filteredData}
+            ListEmptyComponent={ListEmptyComponent}
+            data={this.state.empty ? [] : filteredData}
             debug={this.state.debug}
             disableVirtualization={!this.state.virtualized}
             getItemLayout={this.state.fixedHeight ?
@@ -210,6 +214,7 @@ const styles = StyleSheet.create({
   },
   list: {
     backgroundColor: 'white',
+    flexGrow: 1,
   },
   options: {
     flexDirection: 'row',
diff --git a/RNTester/js/ListExampleShared.js b/RNTester/js/ListExampleShared.js
index c5eef14dbac9..75ef6bb4b65c 100644
--- a/RNTester/js/ListExampleShared.js
+++ b/RNTester/js/ListExampleShared.js
@@ -117,6 +117,16 @@ class HeaderComponent extends React.PureComponent<{}> {
   }
 }
 
+class ListEmptyComponent extends React.PureComponent<{}> {
+  render() {
+    return (
+      <View style={styles.listEmpty}>
+        <Text>The list is empty :o</Text>
+      </View>
+    );
+  }
+}
+
 class SeparatorComponent extends React.PureComponent<{}> {
   render() {
     return <View style={styles.separator} />;
@@ -240,6 +250,11 @@ const styles = StyleSheet.create({
   headerFooterContainer: {
     backgroundColor: 'rgb(239, 239, 244)',
   },
+  listEmpty: {
+    alignItems: 'center',
+    justifyContent: 'center',
+    flexGrow: 1,
+  },
   horizItem: {
     alignSelf: 'flex-start', // Necessary for touch highlight
   },
@@ -317,6 +332,7 @@ const styles = StyleSheet.create({
 module.exports = {
   FooterComponent,
   HeaderComponent,
+  ListEmptyComponent,
   ItemComponent,
   ItemSeparatorComponent,
   PlainInput,

From 8466db0fd355aea778ff71cfb10c927cfd18a551 Mon Sep 17 00:00:00 2001
From: Sahil Ohri <sahilohri@fb.com>
Date: Tue, 13 Mar 2018 19:14:18 -0700
Subject: [PATCH 0011/1109] Revert #17927

Summary:
This change is a revert of [#17927](https://github.com/facebook/react-native/pull/17927) pull-request.
The pull-request caused an issue with the keyboard covering the text field at the bottom of the scroll view.

Reviewed By: shergin

Differential Revision: D7246609

fbshipit-source-id: 149f825274c4fa79ab593f1bae3602667d16ddee
---
 React/Views/ScrollView/RCTScrollView.m | 3 ---
 1 file changed, 3 deletions(-)

diff --git a/React/Views/ScrollView/RCTScrollView.m b/React/Views/ScrollView/RCTScrollView.m
index 6a8f33539426..f146ba0d2369 100644
--- a/React/Views/ScrollView/RCTScrollView.m
+++ b/React/Views/ScrollView/RCTScrollView.m
@@ -575,9 +575,6 @@ - (void)scrollToOffset:(CGPoint)offset
 - (void)scrollToOffset:(CGPoint)offset animated:(BOOL)animated
 {
   if (!CGPointEqualToPoint(_scrollView.contentOffset, offset)) {
-    CGFloat maxOffsetX = _scrollView.contentSize.width - _scrollView.bounds.size.width + _scrollView.contentInset.right;
-    CGFloat maxOffsetY = _scrollView.contentSize.height - _scrollView.bounds.size.height + _scrollView.contentInset.bottom;
-    offset = CGPointMake(MAX(0, MIN(maxOffsetX, offset.x)), MAX(0, MIN(maxOffsetY, offset.y)));
     // Ensure at least one scroll event will fire
     _allowNextScrollNoMatterWhat = YES;
     [_scrollView setContentOffset:offset animated:animated];

From af4a36337de8befbf26017a9d0773a18d300477d Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 14 Mar 2018 04:17:05 -0700
Subject: [PATCH 0012/1109] Remove the usage of YGUndefined in the default
 values of Border in YGStyle

Reviewed By: emilsjolander

Differential Revision: D7195115

fbshipit-source-id: e635cf55ac94d8a90caef6cafce281579da2cbfc
---
 ReactCommon/yoga/yoga/Utils.cpp   |  4 ++++
 ReactCommon/yoga/yoga/Utils.h     |  3 +++
 ReactCommon/yoga/yoga/YGStyle.cpp |  2 +-
 ReactCommon/yoga/yoga/Yoga.cpp    | 30 +++++++++++++++++++++++++++++-
 ReactCommon/yoga/yoga/Yoga.h      |  5 +++++
 5 files changed, 42 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.cpp b/ReactCommon/yoga/yoga/Utils.cpp
index 412845723b22..5ca834c84b5f 100644
--- a/ReactCommon/yoga/yoga/Utils.cpp
+++ b/ReactCommon/yoga/yoga/Utils.cpp
@@ -49,3 +49,7 @@ bool YGFloatsEqual(const float a, const float b) {
   }
   return YGFloatIsUndefined(a) && YGFloatIsUndefined(b);
 }
+
+float YGFloatSanitize(const float& val) {
+  return YGFloatIsUndefined(val) ? 0 : val;
+}
diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index 6ebeb86fc6b2..44cfd300f1c4 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -86,6 +86,9 @@ bool YGFloatArrayEqual(
   return areEqual;
 }
 
+// This function returns 0 if YGFloatIsUndefined(val) is true and val otherwise
+float YGFloatSanitize(const float& val);
+
 YGFlexDirection YGFlexDirectionCross(
     const YGFlexDirection flexDirection,
     const YGDirection direction);
diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index f3bc16fe1cc2..c4ccf7770e98 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -7,7 +7,7 @@
 
 #include "YGStyle.h"
 
-const YGValue kYGValueUndefined = {YGUndefined, YGUnitUndefined};
+const YGValue kYGValueUndefined = {0, YGUnitUndefined};
 
 const YGValue kYGValueAuto = {YGUndefined, YGUnitAuto};
 
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 41f89e877e4c..61ceee7750fa 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -760,7 +760,35 @@ YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Position, position, position);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Margin, margin, margin);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Margin, margin);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Padding, padding, padding);
-YG_NODE_STYLE_EDGE_PROPERTY_IMPL(float, Border, border, border);
+
+// TODO: Change the API to accept YGFloatOptional.
+void YGNodeStyleSetBorder(
+    const YGNodeRef node,
+    const YGEdge edge,
+    const float border) {
+  YGValue value = {
+      .value = YGFloatSanitize(border),
+      .unit = YGFloatIsUndefined(border) ? YGUnitUndefined : YGUnitPoint,
+  };
+  if ((node->getStyle().border[edge].value != value.value &&
+       value.unit != YGUnitUndefined) ||
+      node->getStyle().border[edge].unit != value.unit) {
+    YGStyle style = node->getStyle();
+    style.border[edge] = value;
+    node->setStyle(style);
+    node->markDirtyAndPropogate();
+  }
+}
+
+float YGNodeStyleGetBorder(const YGNodeRef node, const YGEdge edge) {
+  if (node->getStyle().border[edge].unit == YGUnitUndefined) {
+    // TODO: Rather than returning YGUndefined, change the api to return
+    // YGFloatOptional.
+    return YGUndefined;
+  }
+
+  return node->getStyle().border[edge].value;
+}
 
 YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Width, width, dimensions[YGDimensionWidth]);
 YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Height, height, dimensions[YGDimensionHeight]);
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index a632917af859..56fe95ff2ec2 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -42,6 +42,11 @@ typedef struct YGValue {
   YGUnit unit;
 } YGValue;
 
+struct YGFloatOptional {
+  bool isUndefined;
+  float value;
+};
+
 extern const YGValue YGValueUndefined;
 extern const YGValue YGValueAuto;
 

From 9f7e70363a36807f0113fb958b0438cc5003a66a Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 14 Mar 2018 04:17:07 -0700
Subject: [PATCH 0013/1109] Changed the return type of YGResolveValue

Reviewed By: emilsjolander

Differential Revision: D7195099

fbshipit-source-id: 72c4163cd08691cf6e40df05394cc52e83b0de14
---
 ReactCommon/yoga/yoga/Utils.cpp  |   4 ++
 ReactCommon/yoga/yoga/Utils.h    |  17 +++--
 ReactCommon/yoga/yoga/YGNode.cpp |  30 ++++-----
 ReactCommon/yoga/yoga/Yoga.cpp   | 106 +++++++++++++++----------------
 4 files changed, 79 insertions(+), 78 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.cpp b/ReactCommon/yoga/yoga/Utils.cpp
index 5ca834c84b5f..c57e5af3fa82 100644
--- a/ReactCommon/yoga/yoga/Utils.cpp
+++ b/ReactCommon/yoga/yoga/Utils.cpp
@@ -53,3 +53,7 @@ bool YGFloatsEqual(const float a, const float b) {
 float YGFloatSanitize(const float& val) {
   return YGFloatIsUndefined(val) ? 0 : val;
 }
+
+float YGUnwrapFloatOptional(const YGFloatOptional& op) {
+  return op.isUndefined ? YGUndefined : op.value;
+}
diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index 44cfd300f1c4..6fbd33a44db4 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -89,6 +89,11 @@ bool YGFloatArrayEqual(
 // This function returns 0 if YGFloatIsUndefined(val) is true and val otherwise
 float YGFloatSanitize(const float& val);
 
+// This function unwraps optional and returns YGUndefined if not defined or
+// op.value otherwise
+// TODO: Get rid off this function
+float YGUnwrapFloatOptional(const YGFloatOptional& op);
+
 YGFlexDirection YGFlexDirectionCross(
     const YGFlexDirection flexDirection,
     const YGDirection direction);
@@ -98,17 +103,17 @@ inline bool YGFlexDirectionIsRow(const YGFlexDirection flexDirection) {
       flexDirection == YGFlexDirectionRowReverse;
 }
 
-inline float YGResolveValue(const YGValue value, const float parentSize) {
+inline YGFloatOptional YGResolveValue(const YGValue value, const float parentSize) {
   switch (value.unit) {
     case YGUnitUndefined:
     case YGUnitAuto:
-      return YGUndefined;
+      return {true, 0};
     case YGUnitPoint:
-      return value.value;
+      return {false, value.value};
     case YGUnitPercent:
-      return value.value * parentSize * 0.01;
+      return {false, static_cast<float>(value.value * parentSize * 0.01)};
   }
-  return YGUndefined;
+  return {true, 0};
 }
 
 inline bool YGFlexDirectionIsColumn(const YGFlexDirection flexDirection) {
@@ -133,5 +138,5 @@ inline YGFlexDirection YGResolveFlexDirection(
 static inline float YGResolveValueMargin(
     const YGValue value,
     const float parentSize) {
-  return value.unit == YGUnitAuto ? 0 : YGResolveValue(value, parentSize);
+  return value.unit == YGUnitAuto ? 0 : YGUnwrapFloatOptional(YGResolveValue(value, parentSize));
 }
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index ae7fce26e8ce..6b02eeb45429 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -92,7 +92,7 @@ float YGNode::getLeadingPosition(
     const YGValue* leadingPosition =
         YGComputedEdgeValue(style_.position, YGEdgeStart, &YGValueUndefined);
     if (leadingPosition->unit != YGUnitUndefined) {
-      return YGResolveValue(*leadingPosition, axisSize);
+      return YGUnwrapFloatOptional(YGResolveValue(*leadingPosition, axisSize));
     }
   }
 
@@ -101,7 +101,7 @@ float YGNode::getLeadingPosition(
 
   return leadingPosition->unit == YGUnitUndefined
       ? 0.0f
-      : YGResolveValue(*leadingPosition, axisSize);
+      : YGUnwrapFloatOptional(YGResolveValue(*leadingPosition, axisSize));
 }
 
 float YGNode::getTrailingPosition(
@@ -111,7 +111,7 @@ float YGNode::getTrailingPosition(
     const YGValue* trailingPosition =
         YGComputedEdgeValue(style_.position, YGEdgeEnd, &YGValueUndefined);
     if (trailingPosition->unit != YGUnitUndefined) {
-      return YGResolveValue(*trailingPosition, axisSize);
+      return YGUnwrapFloatOptional(YGResolveValue(*trailingPosition, axisSize));
     }
   }
 
@@ -120,7 +120,7 @@ float YGNode::getTrailingPosition(
 
   return trailingPosition->unit == YGUnitUndefined
       ? 0.0f
-      : YGResolveValue(*trailingPosition, axisSize);
+      : YGUnwrapFloatOptional(YGResolveValue(*trailingPosition, axisSize));
 }
 
 bool YGNode::isLeadingPositionDefined(const YGFlexDirection axis) {
@@ -653,15 +653,14 @@ float YGNode::getLeadingPadding(
     const float widthSize) {
   if (YGFlexDirectionIsRow(axis) &&
       style_.padding[YGEdgeStart].unit != YGUnitUndefined &&
-      !YGFloatIsUndefined(
-          YGResolveValue(style_.padding[YGEdgeStart], widthSize)) &&
-      YGResolveValue(style_.padding[YGEdgeStart], widthSize) > 0.0f) {
-    return YGResolveValue(style_.padding[YGEdgeStart], widthSize);
+          !YGResolveValue(style_.padding[YGEdgeStart], widthSize).isUndefined &&
+      YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeStart], widthSize)) > 0.0f) {
+    return YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeStart], widthSize));
   }
 
-  float resolvedValue = YGResolveValue(
+  float resolvedValue = YGUnwrapFloatOptional(YGResolveValue(
       *YGComputedEdgeValue(style_.padding, leading[axis], &YGValueZero),
-      widthSize);
+      widthSize));
   return YGFloatMax(resolvedValue, 0.0f);
 }
 
@@ -670,15 +669,14 @@ float YGNode::getTrailingPadding(
     const float widthSize) {
   if (YGFlexDirectionIsRow(axis) &&
       style_.padding[YGEdgeEnd].unit != YGUnitUndefined &&
-      !YGFloatIsUndefined(
-          YGResolveValue(style_.padding[YGEdgeEnd], widthSize)) &&
-      YGResolveValue(style_.padding[YGEdgeEnd], widthSize) >= 0.0f) {
-    return YGResolveValue(style_.padding[YGEdgeEnd], widthSize);
+      !YGResolveValue(style_.padding[YGEdgeEnd], widthSize).isUndefined &&
+      YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeEnd], widthSize)) >= 0.0f) {
+    return YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeEnd], widthSize));
   }
 
-  float resolvedValue = YGResolveValue(
+  float resolvedValue = YGUnwrapFloatOptional(YGResolveValue(
       *YGComputedEdgeValue(style_.padding, trailing[axis], &YGValueZero),
-      widthSize);
+      widthSize));
 
   return YGFloatMax(resolvedValue, 0.0f);
 }
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 61ceee7750fa..7b4719f3aeba 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -6,6 +6,7 @@
  */
 
 #include "Yoga.h"
+#include <float.h>
 #include <string.h>
 #include <algorithm>
 #include "Utils.h"
@@ -967,15 +968,15 @@ static float YGNodeBoundAxisWithinMinAndMax(const YGNodeRef node,
   float max = YGUndefined;
 
   if (YGFlexDirectionIsColumn(axis)) {
-    min = YGResolveValue(
-        node->getStyle().minDimensions[YGDimensionHeight], axisSize);
-    max = YGResolveValue(
-        node->getStyle().maxDimensions[YGDimensionHeight], axisSize);
+    min = YGUnwrapFloatOptional(YGResolveValue(
+        node->getStyle().minDimensions[YGDimensionHeight], axisSize));
+    max = YGUnwrapFloatOptional(YGResolveValue(
+        node->getStyle().maxDimensions[YGDimensionHeight], axisSize));
   } else if (YGFlexDirectionIsRow(axis)) {
-    min = YGResolveValue(
-        node->getStyle().minDimensions[YGDimensionWidth], axisSize);
-    max = YGResolveValue(
-        node->getStyle().maxDimensions[YGDimensionWidth], axisSize);
+    min = YGUnwrapFloatOptional(YGResolveValue(
+        node->getStyle().minDimensions[YGDimensionWidth], axisSize));
+    max = YGUnwrapFloatOptional(YGResolveValue(
+        node->getStyle().maxDimensions[YGDimensionWidth], axisSize));
   }
 
   float boundValue = value;
@@ -1021,8 +1022,8 @@ static void YGConstrainMaxSizeForMode(const YGNodeRef node,
                                       YGMeasureMode *mode,
                                       float *size) {
   const float maxSize =
-      YGResolveValue(
-          node->getStyle().maxDimensions[dim[axis]], parentAxisSize) +
+      YGUnwrapFloatOptional(YGResolveValue(
+          node->getStyle().maxDimensions[dim[axis]], parentAxisSize)) +
       node->getMarginForAxis(axis, parentWidth);
   switch (*mode) {
     case YGMeasureModeExactly:
@@ -1060,7 +1061,7 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
   YGMeasureMode childHeightMeasureMode;
 
   const float resolvedFlexBasis =
-      YGResolveValue(child->resolveFlexBasisPtr(), mainAxisParentSize);
+      YGUnwrapFloatOptional(YGResolveValue(child->resolveFlexBasisPtr(), mainAxisParentSize));
   const bool isRowStyleDimDefined = YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, parentWidth);
   const bool isColumnStyleDimDefined =
       YGNodeIsStyleDimDefined(child, YGFlexDirectionColumn, parentHeight);
@@ -1078,14 +1079,14 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
   } else if (isMainAxisRow && isRowStyleDimDefined) {
     // The width is definite, so use that as the flex basis.
     child->setLayoutComputedFlexBasis(YGFloatMax(
-        YGResolveValue(
-            child->getResolvedDimension(YGDimensionWidth), parentWidth),
+        YGUnwrapFloatOptional(YGResolveValue(
+            child->getResolvedDimension(YGDimensionWidth), parentWidth)),
         YGNodePaddingAndBorderForAxis(child, YGFlexDirectionRow, parentWidth)));
   } else if (!isMainAxisRow && isColumnStyleDimDefined) {
     // The height is definite, so use that as the flex basis.
     child->setLayoutComputedFlexBasis(YGFloatMax(
-        YGResolveValue(
-            child->getResolvedDimension(YGDimensionHeight), parentHeight),
+        YGUnwrapFloatOptional(YGResolveValue(
+            child->getResolvedDimension(YGDimensionHeight), parentHeight)),
         YGNodePaddingAndBorderForAxis(
             child, YGFlexDirectionColumn, parentWidth)));
   } else {
@@ -1103,15 +1104,15 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
 
     if (isRowStyleDimDefined) {
       childWidth =
-          YGResolveValue(
-              child->getResolvedDimension(YGDimensionWidth), parentWidth) +
+          YGUnwrapFloatOptional(YGResolveValue(
+              child->getResolvedDimension(YGDimensionWidth), parentWidth)) +
           marginRow;
       childWidthMeasureMode = YGMeasureModeExactly;
     }
     if (isColumnStyleDimDefined) {
       childHeight =
-          YGResolveValue(
-              child->getResolvedDimension(YGDimensionHeight), parentHeight) +
+          YGUnwrapFloatOptional(YGResolveValue(
+              child->getResolvedDimension(YGDimensionHeight), parentHeight)) +
           marginColumn;
       childHeightMeasureMode = YGMeasureModeExactly;
     }
@@ -1228,7 +1229,7 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
 
   if (YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, width)) {
     childWidth =
-        YGResolveValue(child->getResolvedDimension(YGDimensionWidth), width) +
+        YGUnwrapFloatOptional(YGResolveValue(child->getResolvedDimension(YGDimensionWidth), width)) +
         marginRow;
   } else {
     // If the child doesn't have a specified width, compute the width based
@@ -1247,7 +1248,7 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
 
   if (YGNodeIsStyleDimDefined(child, YGFlexDirectionColumn, height)) {
     childHeight =
-        YGResolveValue(child->getResolvedDimension(YGDimensionHeight), height) +
+        YGUnwrapFloatOptional(YGResolveValue(child->getResolvedDimension(YGDimensionHeight), height)) +
         marginColumn;
   } else {
     // If the child doesn't have a specified height, compute the height
@@ -1584,15 +1585,14 @@ static float YGNodeCalculateAvailableInnerDim(
   if (!YGFloatIsUndefined(availableInnerDim)) {
     // We want to make sure our available height does not violate min and max
     // constraints
-    const float minInnerDim =
-        YGFloatIsUndefined(YGResolveValue(
-            node->getStyle().minDimensions[dimension], parentDim))
+    const YGFloatOptional minDimensionOptional = YGResolveValue(node->getStyle().minDimensions[dimension], parentDim);
+    const float minInnerDim = minDimensionOptional.isUndefined
         ? 0.0f
-        : YGResolveValue(node->getStyle().minDimensions[dimension], parentDim) -
-            paddingAndBorder;
-    const float maxInnerDim =
-        YGResolveValue(node->getStyle().maxDimensions[dimension], parentDim) -
-        paddingAndBorder;
+        : minDimensionOptional.value - paddingAndBorder;
+
+    const YGFloatOptional maxDimensionOptional = YGResolveValue(node->getStyle().maxDimensions[dimension], parentDim) ;
+
+    const float maxInnerDim = maxDimensionOptional.isUndefined ? FLT_MAX : maxDimensionOptional.value - paddingAndBorder;
     availableInnerDim =
         YGFloatMax(YGFloatMin(availableInnerDim, maxInnerDim), minInnerDim);
   }
@@ -1881,9 +1881,9 @@ static float YGDistributeFreeSpaceSecondPass(
           : YGMeasureModeAtMost;
     } else {
       childCrossSize =
-          YGResolveValue(
+          YGUnwrapFloatOptional(YGResolveValue(
               currentRelativeChild->getResolvedDimension(dim[crossAxis]),
-              availableInnerCrossDim) +
+              availableInnerCrossDim)) +
           marginCross;
       const bool isLoosePercentageMeasurement =
           currentRelativeChild->getResolvedDimension(dim[crossAxis]).unit ==
@@ -2124,12 +2124,11 @@ static void YGJustifyMainAxis(
   if (measureModeMainDim == YGMeasureModeAtMost &&
       collectedFlexItemsValues.remainingFreeSpace > 0) {
     if (style.minDimensions[dim[mainAxis]].unit != YGUnitUndefined &&
-        !YGFloatIsUndefined(YGResolveValue(
-            style.minDimensions[dim[mainAxis]], mainAxisParentSize))) {
+        !YGResolveValue(style.minDimensions[dim[mainAxis]], mainAxisParentSize).isUndefined) {
       collectedFlexItemsValues.remainingFreeSpace = YGFloatMax(
           0,
-          YGResolveValue(
-              style.minDimensions[dim[mainAxis]], mainAxisParentSize) -
+          YGUnwrapFloatOptional(YGResolveValue(
+              style.minDimensions[dim[mainAxis]], mainAxisParentSize)) -
               (availableInnerMainDim -
                collectedFlexItemsValues.remainingFreeSpace));
     } else {
@@ -2487,20 +2486,17 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       node->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
 
   const float minInnerWidth =
-      YGResolveValue(
-          node->getStyle().minDimensions[YGDimensionWidth], parentWidth) -
+      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionWidth], parentWidth)) -
       paddingAndBorderAxisRow;
   const float maxInnerWidth =
-      YGResolveValue(
-          node->getStyle().maxDimensions[YGDimensionWidth], parentWidth) -
+      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionWidth], parentWidth)) -
       paddingAndBorderAxisRow;
   const float minInnerHeight =
-      YGResolveValue(
-          node->getStyle().minDimensions[YGDimensionHeight], parentHeight) -
+      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionHeight], parentHeight)) -
       paddingAndBorderAxisColumn;
   const float maxInnerHeight =
-      YGResolveValue(
-          node->getStyle().maxDimensions[YGDimensionHeight], parentHeight) -
+      YGUnwrapFloatOptional(YGResolveValue(
+          node->getStyle().maxDimensions[YGDimensionHeight], parentHeight)) -
       paddingAndBorderAxisColumn;
 
   const float minInnerMainDim = isMainAxisRow ? minInnerWidth : minInnerHeight;
@@ -3629,15 +3625,15 @@ void YGNodeCalculateLayout(
   YGMeasureMode widthMeasureMode = YGMeasureModeUndefined;
   if (YGNodeIsStyleDimDefined(node, YGFlexDirectionRow, parentWidth)) {
     width =
-        YGResolveValue(
-            node->getResolvedDimension(dim[YGFlexDirectionRow]), parentWidth) +
+        YGUnwrapFloatOptional(YGResolveValue(
+            node->getResolvedDimension(dim[YGFlexDirectionRow]), parentWidth)) +
         node->getMarginForAxis(YGFlexDirectionRow, parentWidth);
     widthMeasureMode = YGMeasureModeExactly;
-  } else if (!YGFloatIsUndefined(YGResolveValue(
+  } else if (!YGResolveValue(
                  node->getStyle().maxDimensions[YGDimensionWidth],
-                 parentWidth))) {
-    width = YGResolveValue(
-        node->getStyle().maxDimensions[YGDimensionWidth], parentWidth);
+                 parentWidth).isUndefined) {
+    width = YGUnwrapFloatOptional(YGResolveValue(
+        node->getStyle().maxDimensions[YGDimensionWidth], parentWidth));
     widthMeasureMode = YGMeasureModeAtMost;
   } else {
     width = parentWidth;
@@ -3648,16 +3644,14 @@ void YGNodeCalculateLayout(
   float height = YGUndefined;
   YGMeasureMode heightMeasureMode = YGMeasureModeUndefined;
   if (YGNodeIsStyleDimDefined(node, YGFlexDirectionColumn, parentHeight)) {
-    height = YGResolveValue(
+    height = YGUnwrapFloatOptional(YGResolveValue(
                  node->getResolvedDimension(dim[YGFlexDirectionColumn]),
-                 parentHeight) +
+                 parentHeight)) +
         node->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
     heightMeasureMode = YGMeasureModeExactly;
-  } else if (!YGFloatIsUndefined(YGResolveValue(
-                 node->getStyle().maxDimensions[YGDimensionHeight],
-                 parentHeight))) {
-    height = YGResolveValue(
-        node->getStyle().maxDimensions[YGDimensionHeight], parentHeight);
+  } else if (!YGResolveValue(node->getStyle().maxDimensions[YGDimensionHeight],
+                 parentHeight).isUndefined) {
+    height = YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionHeight], parentHeight));
     heightMeasureMode = YGMeasureModeAtMost;
   } else {
     height = parentHeight;

From 5b3d59598a27bb200c06e7df3105420eb1ffd950 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 14 Mar 2018 04:17:09 -0700
Subject: [PATCH 0014/1109] Change the type of flex to YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7211327

fbshipit-source-id: 0d979b6ba00317317b98bbc6e63979c7f1feb2da
---
 ReactCommon/yoga/yoga/Utils.cpp       |  6 ++++++
 ReactCommon/yoga/yoga/Utils.h         |  6 ++++++
 ReactCommon/yoga/yoga/YGNode.cpp      | 12 ++++++------
 ReactCommon/yoga/yoga/YGNodePrint.cpp | 11 ++++++++++-
 ReactCommon/yoga/yoga/YGStyle.cpp     | 12 +++++++++---
 ReactCommon/yoga/yoga/YGStyle.h       |  2 +-
 ReactCommon/yoga/yoga/Yoga.cpp        | 27 +++++++++++++++++++++++----
 ReactCommon/yoga/yoga/Yoga.h          |  1 -
 8 files changed, 61 insertions(+), 16 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.cpp b/ReactCommon/yoga/yoga/Utils.cpp
index c57e5af3fa82..8c6e91cce6ee 100644
--- a/ReactCommon/yoga/yoga/Utils.cpp
+++ b/ReactCommon/yoga/yoga/Utils.cpp
@@ -57,3 +57,9 @@ float YGFloatSanitize(const float& val) {
 float YGUnwrapFloatOptional(const YGFloatOptional& op) {
   return op.isUndefined ? YGUndefined : op.value;
 }
+
+bool YGFloatOptionalFloatEquals(
+    const YGFloatOptional& optional,
+    const float& val) {
+  return YGUnwrapFloatOptional(optional) == val;
+}
diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index 6fbd33a44db4..311030e23f0c 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -94,6 +94,12 @@ float YGFloatSanitize(const float& val);
 // TODO: Get rid off this function
 float YGUnwrapFloatOptional(const YGFloatOptional& op);
 
+// This function returns true if val and optional both are undefined or if val
+// and optional.val is true, otherwise its false.
+bool YGFloatOptionalFloatEquals(
+    const YGFloatOptional& optional,
+    const float& val);
+
 YGFlexDirection YGFlexDirectionCross(
     const YGFlexDirection flexDirection,
     const YGDirection direction);
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 6b02eeb45429..e7b1472aaec6 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -500,7 +500,7 @@ YGValue YGNode::resolveFlexBasisPtr() const {
   if (flexBasis.unit != YGUnitAuto && flexBasis.unit != YGUnitUndefined) {
     return flexBasis;
   }
-  if (!YGFloatIsUndefined(style_.flex) && style_.flex > 0.0f) {
+  if (!style_.flex.isUndefined && style_.flex.value > 0.0f) {
     return config_->useWebDefaults ? YGValueAuto : YGValueZero;
   }
   return YGValueAuto;
@@ -595,8 +595,8 @@ float YGNode::resolveFlexGrow() {
   if (!YGFloatIsUndefined(style_.flexGrow)) {
     return style_.flexGrow;
   }
-  if (!YGFloatIsUndefined(style_.flex) && style_.flex > 0.0f) {
-    return style_.flex;
+  if (!style_.flex.isUndefined && style_.flex.value > 0.0f) {
+    return style_.flex.value;
   }
   return kDefaultFlexGrow;
 }
@@ -608,9 +608,9 @@ float YGNode::resolveFlexShrink() {
   if (!YGFloatIsUndefined(style_.flexShrink)) {
     return style_.flexShrink;
   }
-  if (!config_->useWebDefaults && !YGFloatIsUndefined(style_.flex) &&
-      style_.flex < 0.0f) {
-    return -style_.flex;
+  if (!config_->useWebDefaults && !style_.flex.isUndefined &&
+      style_.flex.value < 0.0f) {
+    return -style_.flex.value;
   }
   return config_->useWebDefaults ? kWebDefaultFlexShrink : kDefaultFlexShrink;
 }
diff --git a/ReactCommon/yoga/yoga/YGNodePrint.cpp b/ReactCommon/yoga/yoga/YGNodePrint.cpp
index 395fe1819ad0..2a7a11df8c7c 100644
--- a/ReactCommon/yoga/yoga/YGNodePrint.cpp
+++ b/ReactCommon/yoga/yoga/YGNodePrint.cpp
@@ -39,6 +39,15 @@ static void appendFormatedString(string* str, const char* fmt, ...) {
   str->append(result);
 }
 
+static void appendFloatOptionalIfDefined(
+    string* base,
+    const string key,
+    const YGFloatOptional num) {
+  if (!num.isUndefined) {
+    appendFormatedString(base, "%s: %g; ", key.c_str(), num.value);
+  }
+}
+
 static void
 appendFloatIfNotUndefined(string* base, const string key, const float num) {
   if (!YGFloatIsUndefined(num)) {
@@ -155,7 +164,7 @@ void YGNodeToString(
     appendFloatIfNotUndefined(str, "flex-grow", node->getStyle().flexGrow);
     appendFloatIfNotUndefined(str, "flex-shrink", node->getStyle().flexShrink);
     appendNumberIfNotAuto(str, "flex-basis", node->getStyle().flexBasis);
-    appendFloatIfNotUndefined(str, "flex", node->getStyle().flex);
+    appendFloatOptionalIfDefined(str, "flex", node->getStyle().flex);
 
     if (node->getStyle().flexWrap != YGNode().getStyle().flexWrap) {
       appendFormatedString(
diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index c4ccf7770e98..2ac3da93e123 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -7,6 +7,9 @@
 
 #include "YGStyle.h"
 
+#define YGFloatOptionalUndefined \
+  { true, 0 }
+
 const YGValue kYGValueUndefined = {0, YGUnitUndefined};
 
 const YGValue kYGValueAuto = {YGUndefined, YGUnitAuto};
@@ -39,7 +42,7 @@ YGStyle::YGStyle()
       flexWrap(YGWrapNoWrap),
       overflow(YGOverflowVisible),
       display(YGDisplayFlex),
-      flex(YGUndefined),
+      flex(YGFloatOptionalUndefined),
       flexGrow(YGUndefined),
       flexShrink(YGUndefined),
       flexBasis(kYGValueAuto),
@@ -69,8 +72,11 @@ bool YGStyle::operator==(const YGStyle& style) {
       YGValueArrayEqual(minDimensions, style.minDimensions) &&
       YGValueArrayEqual(maxDimensions, style.maxDimensions);
 
-  if (!(YGFloatIsUndefined(flex) && YGFloatIsUndefined(style.flex))) {
-    areNonFloatValuesEqual = areNonFloatValuesEqual && flex == style.flex;
+  areNonFloatValuesEqual =
+      areNonFloatValuesEqual && flex.isUndefined == style.flex.isUndefined;
+  if (areNonFloatValuesEqual && !flex.isUndefined && !style.flex.isUndefined) {
+    areNonFloatValuesEqual =
+        areNonFloatValuesEqual && flex.value == style.flex.value;
   }
 
   if (!(YGFloatIsUndefined(flexGrow) && YGFloatIsUndefined(style.flexGrow))) {
diff --git a/ReactCommon/yoga/yoga/YGStyle.h b/ReactCommon/yoga/yoga/YGStyle.h
index 74b9d6e0baa3..99e1f18cf3fd 100644
--- a/ReactCommon/yoga/yoga/YGStyle.h
+++ b/ReactCommon/yoga/yoga/YGStyle.h
@@ -20,7 +20,7 @@ struct YGStyle {
   YGWrap flexWrap;
   YGOverflow overflow;
   YGDisplay display;
-  float flex;
+  YGFloatOptional flex;
   float flexGrow;
   float flexShrink;
   YGValue flexBasis;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 7b4719f3aeba..bc80a63679b2 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -752,7 +752,26 @@ YG_NODE_STYLE_PROPERTY_IMPL(YGWrap, FlexWrap, flexWrap, flexWrap);
 YG_NODE_STYLE_PROPERTY_IMPL(YGOverflow, Overflow, overflow, overflow);
 YG_NODE_STYLE_PROPERTY_IMPL(YGDisplay, Display, display, display);
 
-YG_NODE_STYLE_PROPERTY_IMPL(float, Flex, flex, flex);
+// TODO(T26792433): Change the API to accept YGFloatOptional.
+void YGNodeStyleSetFlex(const YGNodeRef node, const float flex) {
+  if (!YGFloatOptionalFloatEquals(node->getStyle().flex, flex)) {
+    YGStyle style = node->getStyle();
+    if (YGFloatIsUndefined(flex)) {
+      style.flex = {true, 0};
+    } else {
+      style.flex = {false, flex};
+    }
+    node->setStyle(style);
+    node->markDirtyAndPropogate();
+  }
+}
+
+// TODO(T26792433): Change the API to accept YGFloatOptional.
+float YGNodeStyleGetFlex(const YGNodeRef node) {
+  return node->getStyle().flex.isUndefined ? YGUndefined
+                                           : node->getStyle().flex.value;
+}
+
 YG_NODE_STYLE_PROPERTY_SETTER_IMPL(float, FlexGrow, flexGrow, flexGrow);
 YG_NODE_STYLE_PROPERTY_SETTER_IMPL(float, FlexShrink, flexShrink, flexShrink);
 YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, FlexBasis, flexBasis, flexBasis);
@@ -762,7 +781,7 @@ YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Margin, margin, margin);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Margin, margin);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Padding, padding, padding);
 
-// TODO: Change the API to accept YGFloatOptional.
+// TODO(T26792433): Change the API to accept YGFloatOptional.
 void YGNodeStyleSetBorder(
     const YGNodeRef node,
     const YGEdge edge,
@@ -783,8 +802,8 @@ void YGNodeStyleSetBorder(
 
 float YGNodeStyleGetBorder(const YGNodeRef node, const YGEdge edge) {
   if (node->getStyle().border[edge].unit == YGUnitUndefined) {
-    // TODO: Rather than returning YGUndefined, change the api to return
-    // YGFloatOptional.
+    // TODO(T26792433): Rather than returning YGUndefined, change the api to
+    // return YGFloatOptional.
     return YGUndefined;
   }
 
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index 56fe95ff2ec2..baeb28e2219c 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -195,7 +195,6 @@ YG_NODE_STYLE_PROPERTY(YGPositionType, PositionType, positionType);
 YG_NODE_STYLE_PROPERTY(YGWrap, FlexWrap, flexWrap);
 YG_NODE_STYLE_PROPERTY(YGOverflow, Overflow, overflow);
 YG_NODE_STYLE_PROPERTY(YGDisplay, Display, display);
-
 YG_NODE_STYLE_PROPERTY(float, Flex, flex);
 YG_NODE_STYLE_PROPERTY(float, FlexGrow, flexGrow);
 YG_NODE_STYLE_PROPERTY(float, FlexShrink, flexShrink);

From 3274e9fa519abf411304c82e6450dc6e4346d826 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 14 Mar 2018 04:17:11 -0700
Subject: [PATCH 0015/1109] Change the type of flexGrow to YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7215355

fbshipit-source-id: 1298ee332551d44e4d070169a1e4103d005c4f43
---
 ReactCommon/yoga/yoga/YGNode.cpp      |  4 ++--
 ReactCommon/yoga/yoga/YGNodePrint.cpp |  2 +-
 ReactCommon/yoga/yoga/YGStyle.cpp     |  8 +++++---
 ReactCommon/yoga/yoga/YGStyle.h       |  2 +-
 ReactCommon/yoga/yoga/Yoga.cpp        | 20 +++++++++++++++++---
 5 files changed, 26 insertions(+), 10 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index e7b1472aaec6..e3e44e720061 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -592,8 +592,8 @@ float YGNode::resolveFlexGrow() {
   if (parent_ == nullptr) {
     return 0.0;
   }
-  if (!YGFloatIsUndefined(style_.flexGrow)) {
-    return style_.flexGrow;
+  if (!style_.flexGrow.isUndefined) {
+    return style_.flexGrow.value;
   }
   if (!style_.flex.isUndefined && style_.flex.value > 0.0f) {
     return style_.flex.value;
diff --git a/ReactCommon/yoga/yoga/YGNodePrint.cpp b/ReactCommon/yoga/yoga/YGNodePrint.cpp
index 2a7a11df8c7c..fd515b51d784 100644
--- a/ReactCommon/yoga/yoga/YGNodePrint.cpp
+++ b/ReactCommon/yoga/yoga/YGNodePrint.cpp
@@ -161,7 +161,7 @@ void YGNodeToString(
       appendFormatedString(
           str, "align-self: %s; ", YGAlignToString(node->getStyle().alignSelf));
     }
-    appendFloatIfNotUndefined(str, "flex-grow", node->getStyle().flexGrow);
+    appendFloatOptionalIfDefined(str, "flex-grow", node->getStyle().flexGrow);
     appendFloatIfNotUndefined(str, "flex-shrink", node->getStyle().flexShrink);
     appendNumberIfNotAuto(str, "flex-basis", node->getStyle().flexBasis);
     appendFloatOptionalIfDefined(str, "flex", node->getStyle().flex);
diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index 2ac3da93e123..d3c18e0ec3a0 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -43,7 +43,7 @@ YGStyle::YGStyle()
       overflow(YGOverflowVisible),
       display(YGDisplayFlex),
       flex(YGFloatOptionalUndefined),
-      flexGrow(YGUndefined),
+      flexGrow(YGFloatOptionalUndefined),
       flexShrink(YGUndefined),
       flexBasis(kYGValueAuto),
       margin(kYGDefaultEdgeValuesUnit),
@@ -79,9 +79,11 @@ bool YGStyle::operator==(const YGStyle& style) {
         areNonFloatValuesEqual && flex.value == style.flex.value;
   }
 
-  if (!(YGFloatIsUndefined(flexGrow) && YGFloatIsUndefined(style.flexGrow))) {
+  areNonFloatValuesEqual = areNonFloatValuesEqual &&
+      flexGrow.isUndefined == style.flexGrow.isUndefined;
+  if (areNonFloatValuesEqual && !flexGrow.isUndefined) {
     areNonFloatValuesEqual =
-        areNonFloatValuesEqual && flexGrow == style.flexGrow;
+        areNonFloatValuesEqual && flexGrow.value == style.flexGrow.value;
   }
 
   if (!(YGFloatIsUndefined(flexShrink) &&
diff --git a/ReactCommon/yoga/yoga/YGStyle.h b/ReactCommon/yoga/yoga/YGStyle.h
index 99e1f18cf3fd..0da5b77fdb5f 100644
--- a/ReactCommon/yoga/yoga/YGStyle.h
+++ b/ReactCommon/yoga/yoga/YGStyle.h
@@ -21,7 +21,7 @@ struct YGStyle {
   YGOverflow overflow;
   YGDisplay display;
   YGFloatOptional flex;
-  float flexGrow;
+  YGFloatOptional flexGrow;
   float flexShrink;
   YGValue flexBasis;
   std::array<YGValue, YGEdgeCount> margin;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index bc80a63679b2..fd3a88a2d115 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -511,9 +511,9 @@ void YGNodeCopyStyle(const YGNodeRef dstNode, const YGNodeRef srcNode) {
 }
 
 float YGNodeStyleGetFlexGrow(const YGNodeRef node) {
-  return YGFloatIsUndefined(node->getStyle().flexGrow)
+  return node->getStyle().flexGrow.isUndefined
       ? kDefaultFlexGrow
-      : node->getStyle().flexGrow;
+      : node->getStyle().flexGrow.value;
 }
 
 float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
@@ -772,7 +772,21 @@ float YGNodeStyleGetFlex(const YGNodeRef node) {
                                            : node->getStyle().flex.value;
 }
 
-YG_NODE_STYLE_PROPERTY_SETTER_IMPL(float, FlexGrow, flexGrow, flexGrow);
+// TODO(T26792433): Change the API to accept YGFloatOptional.
+void YGNodeStyleSetFlexGrow(const YGNodeRef node, const float flexGrow) {
+  if (!YGFloatOptionalFloatEquals(node->getStyle().flexGrow, flexGrow)) {
+    YGStyle style = node->getStyle();
+    if (YGFloatIsUndefined(flexGrow)) {
+      style.flexGrow = {true, 0};
+    } else {
+      style.flexGrow = {false, flexGrow};
+    }
+    node->setStyle(style);
+    node->markDirtyAndPropogate();
+  }
+}
+
+// YG_NODE_STYLE_PROPERTY_SETTER_IMPL(float, FlexGrow, flexGrow, flexGrow);
 YG_NODE_STYLE_PROPERTY_SETTER_IMPL(float, FlexShrink, flexShrink, flexShrink);
 YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, FlexBasis, flexBasis, flexBasis);
 

From e3af1508c8ec4e68ab85d8a881952ebf637dd5f4 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 14 Mar 2018 04:17:16 -0700
Subject: [PATCH 0016/1109] Change the type of flexShrink to YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7232171

fbshipit-source-id: 3111119d3d74a7035c01132bff61b30cf44e120a
---
 ReactCommon/yoga/yoga/YGNode.cpp      |  4 ++--
 ReactCommon/yoga/yoga/YGNodePrint.cpp | 10 ++--------
 ReactCommon/yoga/yoga/YGStyle.cpp     |  9 +++++----
 ReactCommon/yoga/yoga/YGStyle.h       |  2 +-
 ReactCommon/yoga/yoga/Yoga.cpp        | 21 ++++++++++++++++-----
 5 files changed, 26 insertions(+), 20 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index e3e44e720061..df61b14a8966 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -605,8 +605,8 @@ float YGNode::resolveFlexShrink() {
   if (parent_ == nullptr) {
     return 0.0;
   }
-  if (!YGFloatIsUndefined(style_.flexShrink)) {
-    return style_.flexShrink;
+  if (!style_.flexShrink.isUndefined) {
+    return style_.flexShrink.value;
   }
   if (!config_->useWebDefaults && !style_.flex.isUndefined &&
       style_.flex.value < 0.0f) {
diff --git a/ReactCommon/yoga/yoga/YGNodePrint.cpp b/ReactCommon/yoga/yoga/YGNodePrint.cpp
index fd515b51d784..8585b725171f 100644
--- a/ReactCommon/yoga/yoga/YGNodePrint.cpp
+++ b/ReactCommon/yoga/yoga/YGNodePrint.cpp
@@ -48,13 +48,6 @@ static void appendFloatOptionalIfDefined(
   }
 }
 
-static void
-appendFloatIfNotUndefined(string* base, const string key, const float num) {
-  if (!YGFloatIsUndefined(num)) {
-    appendFormatedString(base, "%s: %g; ", key.c_str(), num);
-  }
-}
-
 static void appendNumberIfNotUndefined(
     string* base,
     const string key,
@@ -162,7 +155,8 @@ void YGNodeToString(
           str, "align-self: %s; ", YGAlignToString(node->getStyle().alignSelf));
     }
     appendFloatOptionalIfDefined(str, "flex-grow", node->getStyle().flexGrow);
-    appendFloatIfNotUndefined(str, "flex-shrink", node->getStyle().flexShrink);
+    appendFloatOptionalIfDefined(
+        str, "flex-shrink", node->getStyle().flexShrink);
     appendNumberIfNotAuto(str, "flex-basis", node->getStyle().flexBasis);
     appendFloatOptionalIfDefined(str, "flex", node->getStyle().flex);
 
diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index d3c18e0ec3a0..c1f60bb5741a 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -44,7 +44,7 @@ YGStyle::YGStyle()
       display(YGDisplayFlex),
       flex(YGFloatOptionalUndefined),
       flexGrow(YGFloatOptionalUndefined),
-      flexShrink(YGUndefined),
+      flexShrink(YGFloatOptionalUndefined),
       flexBasis(kYGValueAuto),
       margin(kYGDefaultEdgeValuesUnit),
       position(kYGDefaultEdgeValuesUnit),
@@ -86,10 +86,11 @@ bool YGStyle::operator==(const YGStyle& style) {
         areNonFloatValuesEqual && flexGrow.value == style.flexGrow.value;
   }
 
-  if (!(YGFloatIsUndefined(flexShrink) &&
-        YGFloatIsUndefined(style.flexShrink))) {
+  areNonFloatValuesEqual = areNonFloatValuesEqual &&
+      flexShrink.isUndefined == style.flexShrink.isUndefined;
+  if (areNonFloatValuesEqual && !style.flexShrink.isUndefined) {
     areNonFloatValuesEqual =
-        areNonFloatValuesEqual && flexShrink == style.flexShrink;
+        areNonFloatValuesEqual && flexShrink.value == style.flexShrink.value;
   }
 
   if (!(YGFloatIsUndefined(aspectRatio) &&
diff --git a/ReactCommon/yoga/yoga/YGStyle.h b/ReactCommon/yoga/yoga/YGStyle.h
index 0da5b77fdb5f..3abc4c084d4d 100644
--- a/ReactCommon/yoga/yoga/YGStyle.h
+++ b/ReactCommon/yoga/yoga/YGStyle.h
@@ -22,7 +22,7 @@ struct YGStyle {
   YGDisplay display;
   YGFloatOptional flex;
   YGFloatOptional flexGrow;
-  float flexShrink;
+  YGFloatOptional flexShrink;
   YGValue flexBasis;
   std::array<YGValue, YGEdgeCount> margin;
   std::array<YGValue, YGEdgeCount> position;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index fd3a88a2d115..107e39c8c5f0 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -517,10 +517,10 @@ float YGNodeStyleGetFlexGrow(const YGNodeRef node) {
 }
 
 float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
-  return YGFloatIsUndefined(node->getStyle().flexShrink)
+  return node->getStyle().flexShrink.isUndefined
       ? (node->getConfig()->useWebDefaults ? kWebDefaultFlexShrink
                                            : kDefaultFlexShrink)
-      : node->getStyle().flexShrink;
+      : node->getStyle().flexShrink.value;
 }
 
 #define YG_NODE_STYLE_PROPERTY_SETTER_IMPL(                               \
@@ -786,10 +786,21 @@ void YGNodeStyleSetFlexGrow(const YGNodeRef node, const float flexGrow) {
   }
 }
 
-// YG_NODE_STYLE_PROPERTY_SETTER_IMPL(float, FlexGrow, flexGrow, flexGrow);
-YG_NODE_STYLE_PROPERTY_SETTER_IMPL(float, FlexShrink, flexShrink, flexShrink);
-YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, FlexBasis, flexBasis, flexBasis);
+// TODO(T26792433): Change the API to accept YGFloatOptional.
+void YGNodeStyleSetFlexShrink(const YGNodeRef node, const float flexShrink) {
+  if (!YGFloatOptionalFloatEquals(node->getStyle().flexShrink, flexShrink)) {
+    YGStyle style = node->getStyle();
+    if (YGFloatIsUndefined(flexShrink)) {
+      style.flexGrow = {true, 0};
+    } else {
+      style.flexShrink = {false, flexShrink};
+    }
+    node->setStyle(style);
+    node->markDirtyAndPropogate();
+  }
+}
 
+YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, FlexBasis, flexBasis, flexBasis);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Position, position, position);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Margin, margin, margin);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Margin, margin);

From f3ef8f85103938162d77622a2730790dfb3f2d7d Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 14 Mar 2018 04:17:18 -0700
Subject: [PATCH 0017/1109] Remove the use of YGUndefined for flex-basis

Reviewed By: emilsjolander

Differential Revision: D7243924

fbshipit-source-id: 2bfaca1a5e3da40d5292a273cabf705f59c9d666
---
 ReactCommon/yoga/yoga/YGStyle.cpp |  2 +-
 ReactCommon/yoga/yoga/Yoga.cpp    | 49 ++++++++++++++++++++++++++++++-
 2 files changed, 49 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index c1f60bb5741a..031443c8cbf5 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -45,7 +45,7 @@ YGStyle::YGStyle()
       flex(YGFloatOptionalUndefined),
       flexGrow(YGFloatOptionalUndefined),
       flexShrink(YGFloatOptionalUndefined),
-      flexBasis(kYGValueAuto),
+      flexBasis({0, YGUnitAuto}),
       margin(kYGDefaultEdgeValuesUnit),
       position(kYGDefaultEdgeValuesUnit),
       padding(kYGDefaultEdgeValuesUnit),
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 107e39c8c5f0..b3f3e2206a13 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -800,7 +800,54 @@ void YGNodeStyleSetFlexShrink(const YGNodeRef node, const float flexShrink) {
   }
 }
 
-YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, FlexBasis, flexBasis, flexBasis);
+YGValue YGNodeStyleGetFlexBasis(const YGNodeRef node) {
+  YGValue flexBasis = node->getStyle().flexBasis;
+  if (flexBasis.unit == YGUnitUndefined || flexBasis.unit == YGUnitAuto) {
+    // TODO(T26792433): Get rid off the use of YGUndefined at client side
+    flexBasis.value = YGUndefined;
+  }
+  return flexBasis;
+}
+
+void YGNodeStyleSetFlexBasis(const YGNodeRef node, const float flexBasis) {
+  YGValue value = {
+      .value = YGFloatSanitize(flexBasis),
+      .unit = YGFloatIsUndefined(flexBasis) ? YGUnitUndefined : YGUnitPoint,
+  };
+  if ((node->getStyle().flexBasis.value != value.value &&
+       value.unit != YGUnitUndefined) ||
+      node->getStyle().flexBasis.unit != value.unit) {
+    YGStyle style = node->getStyle();
+    style.flexBasis = value;
+    node->setStyle(style);
+    node->markDirtyAndPropogate();
+  }
+}
+
+void YGNodeStyleSetFlexBasisPercent(
+    const YGNodeRef node,
+    const float flexBasisPercent) {
+  if (node->getStyle().flexBasis.value != flexBasisPercent ||
+      node->getStyle().flexBasis.unit != YGUnitPercent) {
+    YGStyle style = node->getStyle();
+    style.flexBasis.value = YGFloatSanitize(flexBasisPercent);
+    style.flexBasis.unit =
+        YGFloatIsUndefined(flexBasisPercent) ? YGUnitAuto : YGUnitPercent;
+    node->setStyle(style);
+    node->markDirtyAndPropogate();
+  }
+}
+
+void YGNodeStyleSetFlexBasisAuto(const YGNodeRef node) {
+  if (node->getStyle().flexBasis.unit != YGUnitAuto) {
+    YGStyle style = node->getStyle();
+    style.flexBasis.value = 0;
+    style.flexBasis.unit = YGUnitAuto;
+    node->setStyle(style);
+    node->markDirtyAndPropogate();
+  }
+}
+
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Position, position, position);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(YGValue, Margin, margin, margin);
 YG_NODE_STYLE_EDGE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Margin, margin);

From 321b107685e8f5d3bd36f673d81041ec3876b34e Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 14 Mar 2018 08:37:55 -0700
Subject: [PATCH 0018/1109] Expose layout diffing flag to java

Reviewed By: emilsjolander

Differential Revision: D7272067

fbshipit-source-id: e67e82eb057e4c7124904c715f9dca4dcfea21ea
---
 .../java/com/facebook/yoga/YogaConfig.java    | 13 +++++
 .../main/java/com/facebook/yoga/YogaNode.java |  6 +++
 .../jni/first-party/yogajni/jni/YGJNI.cpp     | 51 +++++++++++++------
 ReactCommon/yoga/yoga/Yoga.cpp                | 10 ++++
 ReactCommon/yoga/yoga/Yoga.h                  |  5 +-
 5 files changed, 69 insertions(+), 16 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
index e68c512140f0..2d90eec9de9d 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
@@ -74,6 +74,19 @@ public void setUseLegacyStretchBehaviour(boolean useLegacyStretchBehaviour) {
     jni_YGConfigSetUseLegacyStretchBehaviour(mNativePointer, useLegacyStretchBehaviour);
   }
 
+  private native void jni_YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
+      long nativePointer, boolean shouldDiffLayoutWithoutLegacyStretchBehaviour);
+  /**
+   * If this flag is set then yoga would diff the layout without legacy flag and would set a bool in
+   * YogaNode(mDoesLegacyStretchFlagAffectsLayout) with true if the layouts were different and false
+   * if not
+   */
+  public void setShouldDiffLayoutWithoutLegacyStretchBehaviour(
+      boolean shouldDiffLayoutWithoutLegacyStretchBehaviour) {
+    jni_YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
+        mNativePointer, shouldDiffLayoutWithoutLegacyStretchBehaviour);
+  }
+
   private native void jni_YGConfigSetLogger(long nativePointer, Object logger);
   public void setLogger(YogaLogger logger) {
     mLogger = logger;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index df5fae917128..1c6e67a55eb9 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -82,6 +82,7 @@ public class YogaNode implements Cloneable {
   private int mLayoutDirection = 0;
   @DoNotStrip
   private boolean mHasNewLayout = true;
+  @DoNotStrip private boolean mDoesLegacyStretchFlagAffectsLayout = false;
 
   private native long jni_YGNodeNew();
   public YogaNode() {
@@ -136,6 +137,7 @@ public void reset() {
     mMeasureFunction = null;
     mBaselineFunction = null;
     mData = null;
+    mDoesLegacyStretchFlagAffectsLayout = false;
 
     jni_YGNodeReset(mNativePointer);
   }
@@ -573,6 +575,10 @@ public float getLayoutHeight() {
     return mHeight;
   }
 
+  public boolean getDoesLegacyStretchFlagAffectsLayout() {
+    return mDoesLegacyStretchFlagAffectsLayout;
+  }
+
   public float getLayoutMargin(YogaEdge edge) {
     switch (edge) {
       case LEFT:
diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
index 46d73b44b4d7..cc75df96a151 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
@@ -67,6 +67,9 @@ static void YGTransferLayoutOutputsRecursive(YGNodeRef root) {
 
       static auto edgeSetFlagField = obj->getClass()->getField<jint>("mEdgeSetFlag");
       static auto hasNewLayoutField = obj->getClass()->getField<jboolean>("mHasNewLayout");
+      static auto doesLegacyStretchBehaviour =
+          obj->getClass()->getField<jboolean>(
+              "mDoesLegacyStretchFlagAffectsLayout");
 
       /* Those flags needs be in sync with YogaNode.java */
       const int MARGIN = 1;
@@ -79,12 +82,19 @@ static void YGTransferLayoutOutputsRecursive(YGNodeRef root) {
       obj->setFieldValue(heightField, YGNodeLayoutGetHeight(root));
       obj->setFieldValue(leftField, YGNodeLayoutGetLeft(root));
       obj->setFieldValue(topField, YGNodeLayoutGetTop(root));
+      obj->setFieldValue<jboolean>(
+          doesLegacyStretchBehaviour,
+          YGNodeLayoutGetDidLegacyStretchFlagAffectLayout(root));
 
       if ((hasEdgeSetFlag & MARGIN) == MARGIN) {
-        obj->setFieldValue(marginLeftField, YGNodeLayoutGetMargin(root, YGEdgeLeft));
-        obj->setFieldValue(marginTopField, YGNodeLayoutGetMargin(root, YGEdgeTop));
-        obj->setFieldValue(marginRightField, YGNodeLayoutGetMargin(root, YGEdgeRight));
-        obj->setFieldValue(marginBottomField, YGNodeLayoutGetMargin(root, YGEdgeBottom));
+        obj->setFieldValue(
+            marginLeftField, YGNodeLayoutGetMargin(root, YGEdgeLeft));
+        obj->setFieldValue(
+            marginTopField, YGNodeLayoutGetMargin(root, YGEdgeTop));
+        obj->setFieldValue(
+            marginRightField, YGNodeLayoutGetMargin(root, YGEdgeRight));
+        obj->setFieldValue(
+            marginBottomField, YGNodeLayoutGetMargin(root, YGEdgeBottom));
       }
 
       if ((hasEdgeSetFlag & PADDING) == PADDING) {
@@ -467,6 +477,14 @@ void jni_YGConfigSetExperimentalFeatureEnabled(alias_ref<jobject>,
                                         enabled);
 }
 
+void jni_YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jboolean enabled) {
+  const YGConfigRef config = _jlong2YGConfigRef(nativePointer);
+  YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(config, enabled);
+}
+
 void jni_YGConfigSetUseWebDefaults(alias_ref<jobject>,
                                    jlong nativePointer,
                                    jboolean useWebDefaults) {
@@ -624,16 +642,19 @@ jint JNI_OnLoad(JavaVM *vm, void *) {
             YGMakeNativeMethod(jni_YGNodePrint),
             YGMakeNativeMethod(jni_YGNodeClone),
         });
-    registerNatives("com/facebook/yoga/YogaConfig",
-                    {
-                        YGMakeNativeMethod(jni_YGConfigNew),
-                        YGMakeNativeMethod(jni_YGConfigFree),
-                        YGMakeNativeMethod(jni_YGConfigSetExperimentalFeatureEnabled),
-                        YGMakeNativeMethod(jni_YGConfigSetUseWebDefaults),
-                        YGMakeNativeMethod(jni_YGConfigSetPointScaleFactor),
-                        YGMakeNativeMethod(jni_YGConfigSetUseLegacyStretchBehaviour),
-                        YGMakeNativeMethod(jni_YGConfigSetLogger),
-                        YGMakeNativeMethod(jni_YGConfigSetHasNodeClonedFunc),
-                    });
+    registerNatives(
+        "com/facebook/yoga/YogaConfig",
+        {
+            YGMakeNativeMethod(jni_YGConfigNew),
+            YGMakeNativeMethod(jni_YGConfigFree),
+            YGMakeNativeMethod(jni_YGConfigSetExperimentalFeatureEnabled),
+            YGMakeNativeMethod(jni_YGConfigSetUseWebDefaults),
+            YGMakeNativeMethod(jni_YGConfigSetPointScaleFactor),
+            YGMakeNativeMethod(jni_YGConfigSetUseLegacyStretchBehaviour),
+            YGMakeNativeMethod(jni_YGConfigSetLogger),
+            YGMakeNativeMethod(jni_YGConfigSetHasNodeClonedFunc),
+            YGMakeNativeMethod(
+                jni_YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour),
+        });
   });
 }
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index b3f3e2206a13..b5e1e4c044f5 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -905,6 +905,10 @@ YG_NODE_LAYOUT_RESOLVED_PROPERTY_IMPL(float, Margin, margin);
 YG_NODE_LAYOUT_RESOLVED_PROPERTY_IMPL(float, Border, border);
 YG_NODE_LAYOUT_RESOLVED_PROPERTY_IMPL(float, Padding, padding);
 
+bool YGNodeLayoutGetDidLegacyStretchFlagAffectLayout(const YGNodeRef node) {
+  return node->getLayout().doesLegacyStretchFlagAffectsLayout;
+}
+
 uint32_t gCurrentGenerationCount = 0;
 
 bool YGLayoutNodeInternal(const YGNodeRef node,
@@ -3842,6 +3846,12 @@ void YGConfigSetLogger(const YGConfigRef config, YGLogger logger) {
   }
 }
 
+void YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
+    const YGConfigRef config,
+    const bool shouldDiffLayout) {
+  config->shouldDiffLayoutWithoutLegacyStretchBehaviour = shouldDiffLayout;
+}
+
 static void YGVLog(const YGConfigRef config,
                    const YGNodeRef node,
                    YGLogLevel level,
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index baeb28e2219c..83eefa026893 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -236,6 +236,7 @@ YG_NODE_LAYOUT_PROPERTY(float, Width);
 YG_NODE_LAYOUT_PROPERTY(float, Height);
 YG_NODE_LAYOUT_PROPERTY(YGDirection, Direction);
 YG_NODE_LAYOUT_PROPERTY(bool, HadOverflow);
+bool YGNodeLayoutGetDidLegacyStretchFlagAffectLayout(const YGNodeRef node);
 
 // Get the computed values for these nodes after performing layout. If they were set using
 // point values then the returned value will be the same as YGNodeStyleGetXXX. However if
@@ -253,10 +254,12 @@ WIN_EXPORT void YGAssertWithNode(const YGNodeRef node, const bool condition, con
 WIN_EXPORT void YGAssertWithConfig(const YGConfigRef config,
                                    const bool condition,
                                    const char *message);
-
 // Set this to number of pixels in 1 point to round calculation results
 // If you want to avoid rounding - set PointScaleFactor to 0
 WIN_EXPORT void YGConfigSetPointScaleFactor(const YGConfigRef config, const float pixelsInPoint);
+void YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
+    const YGConfigRef config,
+    const bool shouldDiffLayout);
 
 // Yoga previously had an error where containers would take the maximum space possible instead of
 // the minimum

From a01ae8b68a789e9b6fadf5e0707432e3667c6e7b Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Wed, 14 Mar 2018 08:45:02 -0700
Subject: [PATCH 0019/1109] Bump metro@0.30.1

Reviewed By: BYK

Differential Revision: D7259632

fbshipit-source-id: ef713d35a953cd829d6a8684d2fa9cfa30e69ac4
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index 33f5268f1542..5c554719e5f0 100644
--- a/package.json
+++ b/package.json
@@ -175,8 +175,8 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.30.0",
-    "metro-core": "^0.30.0",
+    "metro": "^0.30.1",
+    "metro-core": "^0.30.1",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 4f8328bf2fb71b104baa70178a1e1f9636773c6a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Wed, 14 Mar 2018 08:47:36 -0700
Subject: [PATCH 0020/1109] React sync for revisions ab4280b...ad9544f

Reviewed By: bvaughn

Differential Revision: D7256390

fbshipit-source-id: 9fe1324da93cb8f4a7f478e1037944774b9b95ff
---
 Libraries/Renderer/REVISION                   |   2 +-
 Libraries/Renderer/ReactFabric-dev.js         | 157 +++++++++------
 Libraries/Renderer/ReactFabric-prod.js        | 189 +++++++++++-------
 Libraries/Renderer/ReactNativeRenderer-dev.js | 157 +++++++++------
 .../Renderer/ReactNativeRenderer-prod.js      | 189 +++++++++++-------
 Libraries/Renderer/shims/ReactFabric.js       |   4 -
 Libraries/Renderer/shims/ReactNativeTypes.js  |  17 +-
 Libraries/Renderer/shims/ReactTypes.js        |  10 +-
 8 files changed, 436 insertions(+), 289 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index bb434f321ae3..824ff8c33a4c 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-ab4280b3e98dbb97d3e753083dab19879167c3f5
\ No newline at end of file
+ad9544f48e58f2599a8ea0de1e9f4dd104db30bb
\ No newline at end of file
diff --git a/Libraries/Renderer/ReactFabric-dev.js b/Libraries/Renderer/ReactFabric-dev.js
index 9a30ceeda703..867873cd41d5 100644
--- a/Libraries/Renderer/ReactFabric-dev.js
+++ b/Libraries/Renderer/ReactFabric-dev.js
@@ -3622,6 +3622,11 @@ var ReactNativeComponent = (function(_React$Component) {
   /**
    * Removes focus. This is the opposite of `focus()`.
    */
+
+  /**
+   * Due to bugs in Flow's handling of React.createClass, some fields already
+   * declared in the base class need to be redeclared below.
+   */
   ReactNativeComponent.prototype.blur = function blur() {
     TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
   };
@@ -8327,11 +8332,11 @@ var rendererSigil = void 0;
 function pushProvider(providerFiber) {
   var context = providerFiber.type.context;
   index$1 += 1;
-  changedBitsStack[index$1] = context.changedBits;
-  currentValueStack[index$1] = context.currentValue;
+  changedBitsStack[index$1] = context._changedBits;
+  currentValueStack[index$1] = context._currentValue;
   stack[index$1] = providerFiber;
-  context.currentValue = providerFiber.pendingProps.value;
-  context.changedBits = providerFiber.stateNode;
+  context._currentValue = providerFiber.pendingProps.value;
+  context._changedBits = providerFiber.stateNode;
 
   {
     warning(
@@ -8358,16 +8363,16 @@ function popProvider(providerFiber) {
   stack[index$1] = null;
   index$1 -= 1;
   var context = providerFiber.type.context;
-  context.currentValue = currentValue;
-  context.changedBits = changedBits;
+  context._currentValue = currentValue;
+  context._changedBits = changedBits;
 }
 
 function resetProviderStack() {
   for (var i = index$1; i > -1; i--) {
     var providerFiber = stack[i];
     var context = providerFiber.type.context;
-    context.currentValue = context.defaultValue;
-    context.changedBits = 0;
+    context._currentValue = context._defaultValue;
+    context._changedBits = 0;
     changedBitsStack[i] = null;
     currentValueStack[i] = null;
     stack[i] = null;
@@ -9149,48 +9154,70 @@ var ReactFiberBeginWork = function(
       pushProvider(workInProgress);
       return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
-    workInProgress.memoizedProps = newProps;
 
     var newValue = newProps.value;
+    workInProgress.memoizedProps = newProps;
 
     var changedBits = void 0;
     if (oldProps === null) {
       // Initial render
       changedBits = MAX_SIGNED_31_BIT_INT;
     } else {
-      var oldValue = oldProps.value;
-      // Use Object.is to compare the new context value to the old value.
-      // Inlined Object.is polyfill.
-      // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
-      if (
-        (oldValue === newValue &&
-          (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
-        (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
-      ) {
-        // No change.
+      if (oldProps.value === newProps.value) {
+        // No change. Bailout early if children are the same.
+        if (oldProps.children === newProps.children) {
+          workInProgress.stateNode = 0;
+          pushProvider(workInProgress);
+          return bailoutOnAlreadyFinishedWork(current, workInProgress);
+        }
         changedBits = 0;
       } else {
-        changedBits =
-          typeof context.calculateChangedBits === "function"
-            ? context.calculateChangedBits(oldValue, newValue)
-            : MAX_SIGNED_31_BIT_INT;
-        {
-          warning(
-            (changedBits & MAX_SIGNED_31_BIT_INT) === changedBits,
-            "calculateChangedBits: Expected the return value to be a " +
-              "31-bit integer. Instead received: %s",
-            changedBits
-          );
-        }
-        changedBits |= 0;
-
-        if (changedBits !== 0) {
-          propagateContextChange(
-            workInProgress,
-            context,
-            changedBits,
-            renderExpirationTime
-          );
+        var oldValue = oldProps.value;
+        // Use Object.is to compare the new context value to the old value.
+        // Inlined Object.is polyfill.
+        // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+        if (
+          (oldValue === newValue &&
+            (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
+          (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
+        ) {
+          // No change. Bailout early if children are the same.
+          if (oldProps.children === newProps.children) {
+            workInProgress.stateNode = 0;
+            pushProvider(workInProgress);
+            return bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+          changedBits = 0;
+        } else {
+          changedBits =
+            typeof context._calculateChangedBits === "function"
+              ? context._calculateChangedBits(oldValue, newValue)
+              : MAX_SIGNED_31_BIT_INT;
+          {
+            warning(
+              (changedBits & MAX_SIGNED_31_BIT_INT) === changedBits,
+              "calculateChangedBits: Expected the return value to be a " +
+                "31-bit integer. Instead received: %s",
+              changedBits
+            );
+          }
+          changedBits |= 0;
+
+          if (changedBits === 0) {
+            // No change. Bailout early if children are the same.
+            if (oldProps.children === newProps.children) {
+              workInProgress.stateNode = 0;
+              pushProvider(workInProgress);
+              return bailoutOnAlreadyFinishedWork(current, workInProgress);
+            }
+          } else {
+            propagateContextChange(
+              workInProgress,
+              context,
+              changedBits,
+              renderExpirationTime
+            );
+          }
         }
       }
     }
@@ -9198,9 +9225,6 @@ var ReactFiberBeginWork = function(
     workInProgress.stateNode = changedBits;
     pushProvider(workInProgress);
 
-    if (oldProps !== null && oldProps.children === newProps.children) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
     var newChildren = newProps.children;
     reconcileChildren(current, workInProgress, newChildren);
     return workInProgress.child;
@@ -9213,11 +9237,28 @@ var ReactFiberBeginWork = function(
   ) {
     var context = workInProgress.type;
     var newProps = workInProgress.pendingProps;
+    var oldProps = workInProgress.memoizedProps;
+
+    var newValue = context._currentValue;
+    var changedBits = context._changedBits;
+
+    if (hasContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (changedBits === 0 && oldProps === newProps) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    workInProgress.memoizedProps = newProps;
 
-    var newValue = context.currentValue;
-    var changedBits = context.changedBits;
+    var observedBits = newProps.unstable_observedBits;
+    if (observedBits === undefined || observedBits === null) {
+      // Subscribe to all changes by default
+      observedBits = MAX_SIGNED_31_BIT_INT;
+    }
+    // Store the observedBits on the fiber's stateNode for quick access.
+    workInProgress.stateNode = observedBits;
 
-    if (changedBits !== 0) {
+    if ((changedBits & observedBits) !== 0) {
       // Context change propagation stops at matching consumers, for time-
       // slicing. Continue the propagation here.
       propagateContextChange(
@@ -9226,24 +9267,20 @@ var ReactFiberBeginWork = function(
         changedBits,
         renderExpirationTime
       );
+    } else if (oldProps !== null && oldProps.children === newProps.children) {
+      // No change. Bailout early if children are the same.
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
 
-    // Store the observedBits on the fiber's stateNode for quick access.
-    var observedBits = newProps.observedBits;
-    if (observedBits === undefined || observedBits === null) {
-      // Subscribe to all changes by default
-      observedBits = MAX_SIGNED_31_BIT_INT;
-    }
-    workInProgress.stateNode = observedBits;
-
     var render = newProps.children;
 
-    if (typeof render !== "function") {
-      invariant(
-        false,
-        "A context consumer was rendered with multiple children, or a child that isn't a function. " +
-          "A context consumer expects a single child that is a function. " +
-          "If you did pass a function, make sure there is no trailing or leading whitespace around it."
+    {
+      warning(
+        typeof render === "function",
+        "A context consumer was rendered with multiple children, or a child " +
+          "that isn't a function. A context consumer expects a single child " +
+          "that is a function. If you did pass a function, make sure there " +
+          "is no trailing or leading whitespace around it."
       );
     }
 
diff --git a/Libraries/Renderer/ReactFabric-prod.js b/Libraries/Renderer/ReactFabric-prod.js
index 9605c98520cd..950e09890f82 100644
--- a/Libraries/Renderer/ReactFabric-prod.js
+++ b/Libraries/Renderer/ReactFabric-prod.js
@@ -3122,11 +3122,11 @@ var reconcileChildFibers = ChildReconciler(!0),
 function pushProvider(providerFiber) {
   var context = providerFiber.type.context;
   index$1 += 1;
-  changedBitsStack[index$1] = context.changedBits;
-  currentValueStack[index$1] = context.currentValue;
+  changedBitsStack[index$1] = context._changedBits;
+  currentValueStack[index$1] = context._currentValue;
   stack[index$1] = providerFiber;
-  context.currentValue = providerFiber.pendingProps.value;
-  context.changedBits = providerFiber.stateNode;
+  context._currentValue = providerFiber.pendingProps.value;
+  context._changedBits = providerFiber.stateNode;
 }
 function popProvider(providerFiber) {
   var changedBits = changedBitsStack[index$1],
@@ -3136,8 +3136,8 @@ function popProvider(providerFiber) {
   stack[index$1] = null;
   --index$1;
   providerFiber = providerFiber.type.context;
-  providerFiber.currentValue = currentValue;
-  providerFiber.changedBits = changedBits;
+  providerFiber._currentValue = currentValue;
+  providerFiber._changedBits = changedBits;
 }
 function ReactFiberBeginWork(
   config,
@@ -3289,6 +3289,72 @@ function ReactFiberBeginWork(
       fiber = nextFiber;
     }
   }
+  function updateContextProvider(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var context = workInProgress.type.context,
+      newProps = workInProgress.pendingProps,
+      oldProps = workInProgress.memoizedProps;
+    if (!didPerformWorkStackCursor.current && oldProps === newProps)
+      return (
+        (workInProgress.stateNode = 0),
+        pushProvider(workInProgress),
+        bailoutOnAlreadyFinishedWork(current, workInProgress)
+      );
+    var newValue = newProps.value;
+    workInProgress.memoizedProps = newProps;
+    if (null === oldProps) newValue = 1073741823;
+    else if (oldProps.value === newProps.value) {
+      if (oldProps.children === newProps.children)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+      newValue = 0;
+    } else {
+      var oldValue = oldProps.value;
+      if (
+        (oldValue === newValue &&
+          (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
+        (oldValue !== oldValue && newValue !== newValue)
+      ) {
+        if (oldProps.children === newProps.children)
+          return (
+            (workInProgress.stateNode = 0),
+            pushProvider(workInProgress),
+            bailoutOnAlreadyFinishedWork(current, workInProgress)
+          );
+        newValue = 0;
+      } else if (
+        ((newValue =
+          "function" === typeof context._calculateChangedBits
+            ? context._calculateChangedBits(oldValue, newValue)
+            : 1073741823),
+        (newValue |= 0),
+        0 === newValue)
+      ) {
+        if (oldProps.children === newProps.children)
+          return (
+            (workInProgress.stateNode = 0),
+            pushProvider(workInProgress),
+            bailoutOnAlreadyFinishedWork(current, workInProgress)
+          );
+      } else
+        propagateContextChange(
+          workInProgress,
+          context,
+          newValue,
+          renderExpirationTime
+        );
+    }
+    workInProgress.stateNode = newValue;
+    pushProvider(workInProgress);
+    reconcileChildren(current, workInProgress, newProps.children);
+    return workInProgress.child;
+  }
   function bailoutOnAlreadyFinishedWork(current, workInProgress) {
     invariant(
       null === current || workInProgress.child === current.child,
@@ -3641,71 +3707,50 @@ function ReactFiberBeginWork(
             current
           );
         case 13:
-          props = workInProgress.type.context;
-          fn = workInProgress.pendingProps;
-          unmaskedContext = workInProgress.memoizedProps;
-          if (didPerformWorkStackCursor.current || unmaskedContext !== fn) {
-            workInProgress.memoizedProps = fn;
-            updateQueue = fn.value;
-            if (null === unmaskedContext) updateQueue = 1073741823;
-            else {
-              var oldValue = unmaskedContext.value;
-              (oldValue === updateQueue &&
-                (0 !== oldValue || 1 / oldValue === 1 / updateQueue)) ||
-              (oldValue !== oldValue && updateQueue !== updateQueue)
-                ? (updateQueue = 0)
-                : ((updateQueue =
-                    "function" === typeof props.calculateChangedBits
-                      ? props.calculateChangedBits(oldValue, updateQueue)
-                      : 1073741823),
-                  (updateQueue |= 0),
-                  0 !== updateQueue &&
-                    propagateContextChange(
-                      workInProgress,
-                      props,
-                      updateQueue,
-                      renderExpirationTime
-                    ));
-            }
-            workInProgress.stateNode = updateQueue;
-            pushProvider(workInProgress);
-            null !== unmaskedContext && unmaskedContext.children === fn.children
-              ? (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                ))
-              : (reconcileChildren(current, workInProgress, fn.children),
-                (current = workInProgress.child));
-          } else
-            (workInProgress.stateNode = 0),
-              pushProvider(workInProgress),
-              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
-          return current;
+          return updateContextProvider(
+            current,
+            workInProgress,
+            renderExpirationTime
+          );
         case 12:
-          unmaskedContext = workInProgress.type;
-          fn = workInProgress.pendingProps;
-          props = unmaskedContext.currentValue;
-          updateQueue = unmaskedContext.changedBits;
-          0 !== updateQueue &&
-            propagateContextChange(
-              workInProgress,
-              unmaskedContext,
-              updateQueue,
-              renderExpirationTime
-            );
-          renderExpirationTime = fn.observedBits;
-          if (void 0 === renderExpirationTime || null === renderExpirationTime)
-            renderExpirationTime = 1073741823;
-          workInProgress.stateNode = renderExpirationTime;
-          renderExpirationTime = fn.children;
-          "function" !== typeof renderExpirationTime &&
-            invariant(
-              !1,
-              "A context consumer was rendered with multiple children, or a child that isn't a function. A context consumer expects a single child that is a function. If you did pass a function, make sure there is no trailing or leading whitespace around it."
-            );
-          renderExpirationTime = renderExpirationTime(props);
-          reconcileChildren(current, workInProgress, renderExpirationTime);
-          return workInProgress.child;
+          a: {
+            fn = workInProgress.type;
+            unmaskedContext = workInProgress.pendingProps;
+            updateQueue = workInProgress.memoizedProps;
+            props = fn._currentValue;
+            var changedBits = fn._changedBits;
+            if (
+              didPerformWorkStackCursor.current ||
+              0 !== changedBits ||
+              updateQueue !== unmaskedContext
+            ) {
+              workInProgress.memoizedProps = unmaskedContext;
+              var observedBits = unmaskedContext.unstable_observedBits;
+              if (void 0 === observedBits || null === observedBits)
+                observedBits = 1073741823;
+              workInProgress.stateNode = observedBits;
+              if (0 !== (changedBits & observedBits))
+                propagateContextChange(
+                  workInProgress,
+                  fn,
+                  changedBits,
+                  renderExpirationTime
+                );
+              else if (
+                null !== updateQueue &&
+                updateQueue.children === unmaskedContext.children
+              ) {
+                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+                break a;
+              }
+              renderExpirationTime = unmaskedContext.children;
+              renderExpirationTime = renderExpirationTime(props);
+              reconcileChildren(current, workInProgress, renderExpirationTime);
+              current = workInProgress.child;
+            } else
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+          return current;
         default:
           invariant(
             !1,
@@ -4581,8 +4626,8 @@ function ReactFiberScheduler(config) {
     resetHostContainer();
     for (var i = index$1; -1 < i; i--) {
       var context = stack[i].type.context;
-      context.currentValue = context.defaultValue;
-      context.changedBits = 0;
+      context._currentValue = context._defaultValue;
+      context._changedBits = 0;
       changedBitsStack[i] = null;
       currentValueStack[i] = null;
       stack[i] = null;
diff --git a/Libraries/Renderer/ReactNativeRenderer-dev.js b/Libraries/Renderer/ReactNativeRenderer-dev.js
index fc98f17e176f..400472d29a38 100644
--- a/Libraries/Renderer/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/ReactNativeRenderer-dev.js
@@ -3968,6 +3968,11 @@ var ReactNativeComponent = (function(_React$Component) {
   /**
    * Removes focus. This is the opposite of `focus()`.
    */
+
+  /**
+   * Due to bugs in Flow's handling of React.createClass, some fields already
+   * declared in the base class need to be redeclared below.
+   */
   ReactNativeComponent.prototype.blur = function blur() {
     TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
   };
@@ -8585,11 +8590,11 @@ var rendererSigil = void 0;
 function pushProvider(providerFiber) {
   var context = providerFiber.type.context;
   index$1 += 1;
-  changedBitsStack[index$1] = context.changedBits;
-  currentValueStack[index$1] = context.currentValue;
+  changedBitsStack[index$1] = context._changedBits;
+  currentValueStack[index$1] = context._currentValue;
   stack[index$1] = providerFiber;
-  context.currentValue = providerFiber.pendingProps.value;
-  context.changedBits = providerFiber.stateNode;
+  context._currentValue = providerFiber.pendingProps.value;
+  context._changedBits = providerFiber.stateNode;
 
   {
     warning(
@@ -8616,16 +8621,16 @@ function popProvider(providerFiber) {
   stack[index$1] = null;
   index$1 -= 1;
   var context = providerFiber.type.context;
-  context.currentValue = currentValue;
-  context.changedBits = changedBits;
+  context._currentValue = currentValue;
+  context._changedBits = changedBits;
 }
 
 function resetProviderStack() {
   for (var i = index$1; i > -1; i--) {
     var providerFiber = stack[i];
     var context = providerFiber.type.context;
-    context.currentValue = context.defaultValue;
-    context.changedBits = 0;
+    context._currentValue = context._defaultValue;
+    context._changedBits = 0;
     changedBitsStack[i] = null;
     currentValueStack[i] = null;
     stack[i] = null;
@@ -9407,48 +9412,70 @@ var ReactFiberBeginWork = function(
       pushProvider(workInProgress);
       return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
-    workInProgress.memoizedProps = newProps;
 
     var newValue = newProps.value;
+    workInProgress.memoizedProps = newProps;
 
     var changedBits = void 0;
     if (oldProps === null) {
       // Initial render
       changedBits = MAX_SIGNED_31_BIT_INT;
     } else {
-      var oldValue = oldProps.value;
-      // Use Object.is to compare the new context value to the old value.
-      // Inlined Object.is polyfill.
-      // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
-      if (
-        (oldValue === newValue &&
-          (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
-        (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
-      ) {
-        // No change.
+      if (oldProps.value === newProps.value) {
+        // No change. Bailout early if children are the same.
+        if (oldProps.children === newProps.children) {
+          workInProgress.stateNode = 0;
+          pushProvider(workInProgress);
+          return bailoutOnAlreadyFinishedWork(current, workInProgress);
+        }
         changedBits = 0;
       } else {
-        changedBits =
-          typeof context.calculateChangedBits === "function"
-            ? context.calculateChangedBits(oldValue, newValue)
-            : MAX_SIGNED_31_BIT_INT;
-        {
-          warning(
-            (changedBits & MAX_SIGNED_31_BIT_INT) === changedBits,
-            "calculateChangedBits: Expected the return value to be a " +
-              "31-bit integer. Instead received: %s",
-            changedBits
-          );
-        }
-        changedBits |= 0;
-
-        if (changedBits !== 0) {
-          propagateContextChange(
-            workInProgress,
-            context,
-            changedBits,
-            renderExpirationTime
-          );
+        var oldValue = oldProps.value;
+        // Use Object.is to compare the new context value to the old value.
+        // Inlined Object.is polyfill.
+        // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+        if (
+          (oldValue === newValue &&
+            (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
+          (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
+        ) {
+          // No change. Bailout early if children are the same.
+          if (oldProps.children === newProps.children) {
+            workInProgress.stateNode = 0;
+            pushProvider(workInProgress);
+            return bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+          changedBits = 0;
+        } else {
+          changedBits =
+            typeof context._calculateChangedBits === "function"
+              ? context._calculateChangedBits(oldValue, newValue)
+              : MAX_SIGNED_31_BIT_INT;
+          {
+            warning(
+              (changedBits & MAX_SIGNED_31_BIT_INT) === changedBits,
+              "calculateChangedBits: Expected the return value to be a " +
+                "31-bit integer. Instead received: %s",
+              changedBits
+            );
+          }
+          changedBits |= 0;
+
+          if (changedBits === 0) {
+            // No change. Bailout early if children are the same.
+            if (oldProps.children === newProps.children) {
+              workInProgress.stateNode = 0;
+              pushProvider(workInProgress);
+              return bailoutOnAlreadyFinishedWork(current, workInProgress);
+            }
+          } else {
+            propagateContextChange(
+              workInProgress,
+              context,
+              changedBits,
+              renderExpirationTime
+            );
+          }
         }
       }
     }
@@ -9456,9 +9483,6 @@ var ReactFiberBeginWork = function(
     workInProgress.stateNode = changedBits;
     pushProvider(workInProgress);
 
-    if (oldProps !== null && oldProps.children === newProps.children) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
     var newChildren = newProps.children;
     reconcileChildren(current, workInProgress, newChildren);
     return workInProgress.child;
@@ -9471,11 +9495,28 @@ var ReactFiberBeginWork = function(
   ) {
     var context = workInProgress.type;
     var newProps = workInProgress.pendingProps;
+    var oldProps = workInProgress.memoizedProps;
+
+    var newValue = context._currentValue;
+    var changedBits = context._changedBits;
+
+    if (hasContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (changedBits === 0 && oldProps === newProps) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    workInProgress.memoizedProps = newProps;
 
-    var newValue = context.currentValue;
-    var changedBits = context.changedBits;
+    var observedBits = newProps.unstable_observedBits;
+    if (observedBits === undefined || observedBits === null) {
+      // Subscribe to all changes by default
+      observedBits = MAX_SIGNED_31_BIT_INT;
+    }
+    // Store the observedBits on the fiber's stateNode for quick access.
+    workInProgress.stateNode = observedBits;
 
-    if (changedBits !== 0) {
+    if ((changedBits & observedBits) !== 0) {
       // Context change propagation stops at matching consumers, for time-
       // slicing. Continue the propagation here.
       propagateContextChange(
@@ -9484,24 +9525,20 @@ var ReactFiberBeginWork = function(
         changedBits,
         renderExpirationTime
       );
+    } else if (oldProps !== null && oldProps.children === newProps.children) {
+      // No change. Bailout early if children are the same.
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
 
-    // Store the observedBits on the fiber's stateNode for quick access.
-    var observedBits = newProps.observedBits;
-    if (observedBits === undefined || observedBits === null) {
-      // Subscribe to all changes by default
-      observedBits = MAX_SIGNED_31_BIT_INT;
-    }
-    workInProgress.stateNode = observedBits;
-
     var render = newProps.children;
 
-    if (typeof render !== "function") {
-      invariant(
-        false,
-        "A context consumer was rendered with multiple children, or a child that isn't a function. " +
-          "A context consumer expects a single child that is a function. " +
-          "If you did pass a function, make sure there is no trailing or leading whitespace around it."
+    {
+      warning(
+        typeof render === "function",
+        "A context consumer was rendered with multiple children, or a child " +
+          "that isn't a function. A context consumer expects a single child " +
+          "that is a function. If you did pass a function, make sure there " +
+          "is no trailing or leading whitespace around it."
       );
     }
 
diff --git a/Libraries/Renderer/ReactNativeRenderer-prod.js b/Libraries/Renderer/ReactNativeRenderer-prod.js
index dd0cd8b9cb53..ca27b720b33d 100644
--- a/Libraries/Renderer/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/ReactNativeRenderer-prod.js
@@ -3376,11 +3376,11 @@ var reconcileChildFibers = ChildReconciler(!0),
 function pushProvider(providerFiber) {
   var context = providerFiber.type.context;
   index$1 += 1;
-  changedBitsStack[index$1] = context.changedBits;
-  currentValueStack[index$1] = context.currentValue;
+  changedBitsStack[index$1] = context._changedBits;
+  currentValueStack[index$1] = context._currentValue;
   stack[index$1] = providerFiber;
-  context.currentValue = providerFiber.pendingProps.value;
-  context.changedBits = providerFiber.stateNode;
+  context._currentValue = providerFiber.pendingProps.value;
+  context._changedBits = providerFiber.stateNode;
 }
 function popProvider(providerFiber) {
   var changedBits = changedBitsStack[index$1],
@@ -3390,8 +3390,8 @@ function popProvider(providerFiber) {
   stack[index$1] = null;
   --index$1;
   providerFiber = providerFiber.type.context;
-  providerFiber.currentValue = currentValue;
-  providerFiber.changedBits = changedBits;
+  providerFiber._currentValue = currentValue;
+  providerFiber._changedBits = changedBits;
 }
 function ReactFiberBeginWork(
   config,
@@ -3552,6 +3552,72 @@ function ReactFiberBeginWork(
       fiber = nextFiber;
     }
   }
+  function updateContextProvider(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var context = workInProgress.type.context,
+      newProps = workInProgress.pendingProps,
+      oldProps = workInProgress.memoizedProps;
+    if (!didPerformWorkStackCursor.current && oldProps === newProps)
+      return (
+        (workInProgress.stateNode = 0),
+        pushProvider(workInProgress),
+        bailoutOnAlreadyFinishedWork(current, workInProgress)
+      );
+    var newValue = newProps.value;
+    workInProgress.memoizedProps = newProps;
+    if (null === oldProps) newValue = 1073741823;
+    else if (oldProps.value === newProps.value) {
+      if (oldProps.children === newProps.children)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+      newValue = 0;
+    } else {
+      var oldValue = oldProps.value;
+      if (
+        (oldValue === newValue &&
+          (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
+        (oldValue !== oldValue && newValue !== newValue)
+      ) {
+        if (oldProps.children === newProps.children)
+          return (
+            (workInProgress.stateNode = 0),
+            pushProvider(workInProgress),
+            bailoutOnAlreadyFinishedWork(current, workInProgress)
+          );
+        newValue = 0;
+      } else if (
+        ((newValue =
+          "function" === typeof context._calculateChangedBits
+            ? context._calculateChangedBits(oldValue, newValue)
+            : 1073741823),
+        (newValue |= 0),
+        0 === newValue)
+      ) {
+        if (oldProps.children === newProps.children)
+          return (
+            (workInProgress.stateNode = 0),
+            pushProvider(workInProgress),
+            bailoutOnAlreadyFinishedWork(current, workInProgress)
+          );
+      } else
+        propagateContextChange(
+          workInProgress,
+          context,
+          newValue,
+          renderExpirationTime
+        );
+    }
+    workInProgress.stateNode = newValue;
+    pushProvider(workInProgress);
+    reconcileChildren(current, workInProgress, newProps.children);
+    return workInProgress.child;
+  }
   function bailoutOnAlreadyFinishedWork(current, workInProgress) {
     invariant(
       null === current || workInProgress.child === current.child,
@@ -3904,71 +3970,50 @@ function ReactFiberBeginWork(
             current
           );
         case 13:
-          props = workInProgress.type.context;
-          fn = workInProgress.pendingProps;
-          unmaskedContext = workInProgress.memoizedProps;
-          if (didPerformWorkStackCursor.current || unmaskedContext !== fn) {
-            workInProgress.memoizedProps = fn;
-            updateQueue = fn.value;
-            if (null === unmaskedContext) updateQueue = 1073741823;
-            else {
-              var oldValue = unmaskedContext.value;
-              (oldValue === updateQueue &&
-                (0 !== oldValue || 1 / oldValue === 1 / updateQueue)) ||
-              (oldValue !== oldValue && updateQueue !== updateQueue)
-                ? (updateQueue = 0)
-                : ((updateQueue =
-                    "function" === typeof props.calculateChangedBits
-                      ? props.calculateChangedBits(oldValue, updateQueue)
-                      : 1073741823),
-                  (updateQueue |= 0),
-                  0 !== updateQueue &&
-                    propagateContextChange(
-                      workInProgress,
-                      props,
-                      updateQueue,
-                      renderExpirationTime
-                    ));
-            }
-            workInProgress.stateNode = updateQueue;
-            pushProvider(workInProgress);
-            null !== unmaskedContext && unmaskedContext.children === fn.children
-              ? (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                ))
-              : (reconcileChildren(current, workInProgress, fn.children),
-                (current = workInProgress.child));
-          } else
-            (workInProgress.stateNode = 0),
-              pushProvider(workInProgress),
-              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
-          return current;
+          return updateContextProvider(
+            current,
+            workInProgress,
+            renderExpirationTime
+          );
         case 12:
-          unmaskedContext = workInProgress.type;
-          fn = workInProgress.pendingProps;
-          props = unmaskedContext.currentValue;
-          updateQueue = unmaskedContext.changedBits;
-          0 !== updateQueue &&
-            propagateContextChange(
-              workInProgress,
-              unmaskedContext,
-              updateQueue,
-              renderExpirationTime
-            );
-          renderExpirationTime = fn.observedBits;
-          if (void 0 === renderExpirationTime || null === renderExpirationTime)
-            renderExpirationTime = 1073741823;
-          workInProgress.stateNode = renderExpirationTime;
-          renderExpirationTime = fn.children;
-          "function" !== typeof renderExpirationTime &&
-            invariant(
-              !1,
-              "A context consumer was rendered with multiple children, or a child that isn't a function. A context consumer expects a single child that is a function. If you did pass a function, make sure there is no trailing or leading whitespace around it."
-            );
-          renderExpirationTime = renderExpirationTime(props);
-          reconcileChildren(current, workInProgress, renderExpirationTime);
-          return workInProgress.child;
+          a: {
+            fn = workInProgress.type;
+            unmaskedContext = workInProgress.pendingProps;
+            updateQueue = workInProgress.memoizedProps;
+            props = fn._currentValue;
+            var changedBits = fn._changedBits;
+            if (
+              didPerformWorkStackCursor.current ||
+              0 !== changedBits ||
+              updateQueue !== unmaskedContext
+            ) {
+              workInProgress.memoizedProps = unmaskedContext;
+              var observedBits = unmaskedContext.unstable_observedBits;
+              if (void 0 === observedBits || null === observedBits)
+                observedBits = 1073741823;
+              workInProgress.stateNode = observedBits;
+              if (0 !== (changedBits & observedBits))
+                propagateContextChange(
+                  workInProgress,
+                  fn,
+                  changedBits,
+                  renderExpirationTime
+                );
+              else if (
+                null !== updateQueue &&
+                updateQueue.children === unmaskedContext.children
+              ) {
+                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+                break a;
+              }
+              renderExpirationTime = unmaskedContext.children;
+              renderExpirationTime = renderExpirationTime(props);
+              reconcileChildren(current, workInProgress, renderExpirationTime);
+              current = workInProgress.child;
+            } else
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+          return current;
         default:
           invariant(
             !1,
@@ -4977,8 +5022,8 @@ function ReactFiberScheduler(config) {
     resetHostContainer();
     for (var i = index$1; -1 < i; i--) {
       var context = stack[i].type.context;
-      context.currentValue = context.defaultValue;
-      context.changedBits = 0;
+      context._currentValue = context._defaultValue;
+      context._changedBits = 0;
       changedBitsStack[i] = null;
       currentValueStack[i] = null;
       stack[i] = null;
diff --git a/Libraries/Renderer/shims/ReactFabric.js b/Libraries/Renderer/shims/ReactFabric.js
index 4162ca62fef7..4a396c224cd4 100644
--- a/Libraries/Renderer/shims/ReactFabric.js
+++ b/Libraries/Renderer/shims/ReactFabric.js
@@ -9,8 +9,6 @@
  */
 'use strict';
 
-const BatchedBridge = require('BatchedBridge');
-
 // TODO @sema: Adjust types
 import type {ReactNativeType} from 'ReactNativeTypes';
 
@@ -22,6 +20,4 @@ if (__DEV__) {
   ReactFabric = require('ReactFabric-prod');
 }
 
-BatchedBridge.registerCallableModule('ReactFabric', ReactFabric);
-
 module.exports = (ReactFabric: ReactNativeType);
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index 121a2fdd4d3d..f20bb30faa79 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -86,27 +86,12 @@ type SecretInternalsType = {
   // And how much information to fill in for the above types.
 };
 
-declare class ReactNativeComponent<Props, State = void>
-  extends React$Component<Props, State> {
-
-  blur(): void,
-  focus(): void,
-  measure(callback: MeasureOnSuccessCallback): void,
-  measureInWindow(callback: MeasureInWindowOnSuccessCallback): void,
-  measureLayout(
-    relativeToNativeNode: number,
-    onSuccess: MeasureLayoutOnSuccessCallback,
-    onFail: () => void,
-  ): void,
-  setNativeProps(nativeProps: Object): void,
-}
-
 /**
  * Flat ReactNative renderer bundles are too big for Flow to parse efficiently.
  * Provide minimal Flow typing for the high-level RN API and call it a day.
  */
 export type ReactNativeType = {
-  NativeComponent: typeof ReactNativeComponent,
+  NativeComponent: any,
   findNodeHandle(componentOrHandle: any): ?number,
   render(
     element: React$Element<any>,
diff --git a/Libraries/Renderer/shims/ReactTypes.js b/Libraries/Renderer/shims/ReactTypes.js
index 26ada3c5e842..bede9f00e300 100644
--- a/Libraries/Renderer/shims/ReactTypes.js
+++ b/Libraries/Renderer/shims/ReactTypes.js
@@ -80,10 +80,12 @@ export type ReactContext<T> = {
   $$typeof: Symbol | number,
   Consumer: ReactContext<T>,
   Provider: ReactProviderType<T>,
-  calculateChangedBits: ((a: T, b: T) => number) | null,
-  defaultValue: T,
-  currentValue: T,
-  changedBits: number,
+
+  _calculateChangedBits: ((a: T, b: T) => number) | null,
+  _defaultValue: T,
+
+  _currentValue: T,
+  _changedBits: number,
 
   // DEV only
   _currentRenderer?: Object | null,

From bec97dc24312ed59377888672fa821b2276a8a9f Mon Sep 17 00:00:00 2001
From: Eric Czarny <eczarny@fb.com>
Date: Wed, 14 Mar 2018 11:04:56 -0700
Subject: [PATCH 0021/1109] Expose native show message method in header

Reviewed By: mmmulani

Differential Revision: D7201691

fbshipit-source-id: b5f74351a9be7e6e9a7fc7145a09ba9854efc002
---
 React/DevSupport/RCTDevLoadingView.h | 3 +++
 React/DevSupport/RCTDevLoadingView.m | 1 +
 2 files changed, 4 insertions(+)

diff --git a/React/DevSupport/RCTDevLoadingView.h b/React/DevSupport/RCTDevLoadingView.h
index dae01f045771..61a7121c5476 100644
--- a/React/DevSupport/RCTDevLoadingView.h
+++ b/React/DevSupport/RCTDevLoadingView.h
@@ -5,6 +5,8 @@
  * LICENSE file in the root directory of this source tree.
  */
 
+#import <UIKit/UIKit.h>
+
 #import <React/RCTBridgeModule.h>
 
 @class RCTLoadingProgress;
@@ -12,6 +14,7 @@
 @interface RCTDevLoadingView : NSObject <RCTBridgeModule>
 
 + (void)setEnabled:(BOOL)enabled;
+- (void)showMessage:(NSString *)message color:(UIColor *)color backgroundColor:(UIColor *)backgroundColor;
 - (void)showWithURL:(NSURL *)URL;
 - (void)updateProgress:(RCTLoadingProgress *)progress;
 - (void)hide;
diff --git a/React/DevSupport/RCTDevLoadingView.m b/React/DevSupport/RCTDevLoadingView.m
index e7614a896489..9382c91caa6e 100644
--- a/React/DevSupport/RCTDevLoadingView.m
+++ b/React/DevSupport/RCTDevLoadingView.m
@@ -161,6 +161,7 @@ @implementation RCTDevLoadingView
 
 + (NSString *)moduleName { return nil; }
 + (void)setEnabled:(BOOL)enabled { }
+- (void)showMessage:(NSString *)message color:(UIColor *)color backgroundColor:(UIColor *)backgroundColor { }
 - (void)showWithURL:(NSURL *)URL { }
 - (void)updateProgress:(RCTLoadingProgress *)progress { }
 - (void)hide { }

From 3a2bdf5c50d48305d1538256a816420a6ebcaa48 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 14 Mar 2018 11:31:27 -0700
Subject: [PATCH 0022/1109] Move Fabric JSC bindings to oss

Reviewed By: mdvacca

Differential Revision: D7205065

fbshipit-source-id: 5876cb3e08ee96e39b80e6b377c60600f404ca21
---
 .../java/com/facebook/react/fabric/jsc/BUCK   |  24 ++
 .../react/fabric/jsc/FabricJSCBinding.java    |  35 +++
 .../com/facebook/react/fabric/jsc/jni/BUCK    |  20 ++
 .../react/fabric/jsc/jni/FabricJSCBinding.cpp | 296 ++++++++++++++++++
 .../react/fabric/jsc/jni/FabricJSCBinding.h   |  29 ++
 .../facebook/react/fabric/jsc/jni/OnLoad.cpp  |  12 +
 6 files changed, 416 insertions(+)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
new file mode 100644
index 000000000000..ac6ce3d53025
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
@@ -0,0 +1,24 @@
+load("@xplat//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library", "IS_OSS_BUILD")
+
+rn_android_library(
+    name = "jsc",
+    srcs = glob(["**/*.java"]),
+    exported_deps = [
+        react_native_dep("java/com/facebook/jni:jni"),
+        react_native_dep("java/com/facebook/proguard/annotations:annotations"),
+    ],
+    provided_deps = [
+        react_native_dep("third-party/android/support/v4:lib-support-v4"),
+    ],
+    required_for_source_only_abi = True,
+    visibility = [
+        "PUBLIC",
+    ],
+    deps = [
+        react_native_dep("libraries/soloader/java/com/facebook/soloader:soloader"),
+        react_native_dep("third-party/java/infer-annotations:infer-annotations"),
+        react_native_target("java/com/facebook/react/bridge:bridge"),
+        react_native_target("java/com/facebook/react/fabric:fabric"),
+        react_native_target("java/com/facebook/react/fabric/jsc/jni:jni"),
+    ],
+)
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
new file mode 100644
index 000000000000..ab7352f9ede0
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
@@ -0,0 +1,35 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+package com.facebook.react.fabric.jsc;
+
+import com.facebook.jni.HybridData;
+import com.facebook.proguard.annotations.DoNotStrip;
+import com.facebook.react.bridge.JavaScriptContextHolder;
+import com.facebook.react.fabric.FabricBinding;
+import com.facebook.react.fabric.FabricUIManager;
+import com.facebook.soloader.SoLoader;
+
+@DoNotStrip
+public class FabricJSCBinding implements FabricBinding {
+
+  static {
+    SoLoader.loadLibrary("fabricjscjni");
+  }
+
+  // used from native
+  @SuppressWarnings("unused")
+  private final HybridData mHybridData;
+
+  private static native HybridData initHybrid();
+
+  private native void installFabric(long jsContextNativePointer, Object fabricModule);
+
+  public FabricJSCBinding() {
+    mHybridData = initHybrid();
+  }
+
+  @Override
+  public void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule) {
+    installFabric(jsContext.get(), fabricModule);
+  }
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
new file mode 100644
index 000000000000..cbf088f2d277
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
@@ -0,0 +1,20 @@
+load("@xplat//ReactNative:DEFS.bzl", "react_native_target", "react_native_xplat_target", "rn_xplat_cxx_library", "FBJNI_TARGET", "ANDROID")
+
+rn_xplat_cxx_library(
+    name = "jni",
+    srcs = glob(["*.cpp"]),
+    headers = glob(["*.h"]),
+    compiler_flags = [
+        "-Wall",
+        "-fexceptions",
+        "-std=gnu++1y",
+    ],
+    platforms = ANDROID,
+    soname = "libfabricjscjni.$(ext)",
+    visibility = ["PUBLIC"],
+    deps = [
+        FBJNI_TARGET,
+        react_native_xplat_target("jschelpers:jschelpers"),
+        react_native_target("jni/react/jni:jni"),
+    ],
+)
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
new file mode 100644
index 000000000000..044143210b1c
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
@@ -0,0 +1,296 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include "FabricJSCBinding.h"
+#include <fb/fbjni.h>
+#include <react/jni/ReadableNativeMap.h>
+#include <jschelpers/JavaScriptCore.h>
+#include <jschelpers/Unicode.h>
+
+using namespace facebook::jni;
+
+namespace facebook {
+namespace react {
+
+namespace {
+
+bool useCustomJSC = false;
+
+struct JList : public JavaClass<JList> {
+  static constexpr auto kJavaDescriptor = "Ljava/util/List;";
+};
+
+struct JShadowNode : public JavaClass<JShadowNode> {
+  static constexpr auto kJavaDescriptor = "Lcom/facebook/react/uimanager/ReactShadowNode;";
+};
+
+typedef struct FabricJSCUIManager {
+  FabricJSCUIManager(alias_ref<jobject> module, JSClassRef classRef, bool customJSC)
+    : wrapperObjectClassRef(classRef)
+    , useCustomJSC(customJSC) {
+    fabricUiManager = make_global(module);
+  }
+  global_ref<jobject> fabricUiManager;
+  JSClassRef wrapperObjectClassRef;
+  bool useCustomJSC;
+} FabricJSCUIManager;
+
+jobject makePlainGlobalRef(jobject object) {
+  // When storing the global reference we need it to be a plain
+  // pointer. That's why we use plain jni instead of fbjni here.
+  return Environment::current()->NewGlobalRef(object);
+}
+
+local_ref<JString> JSValueToJString(JSContextRef ctx, JSValueRef value) {
+  JSStringRef strRef = JSC_JSValueToStringCopy(ctx, value, NULL);
+  const size_t size = JSStringGetMaximumUTF8CStringSize(strRef);
+  char buffer[size];
+  JSStringGetUTF8CString(strRef, buffer, size);
+  JSC_JSStringRelease(ctx, strRef);
+  return make_jstring(buffer);
+}
+
+local_ref<JShadowNode> JSValueToJShadowNode(JSContextRef ctx, JSValueRef value) {
+  JSObjectRef obj = JSC_JSValueToObject(ctx, value, NULL);
+  auto node = static_cast<JShadowNode::javaobject>(JSC_JSObjectGetPrivate(useCustomJSC, obj));
+  return make_local(node);
+}
+
+local_ref<JList> JSValueToJList(JSContextRef ctx, JSValueRef value) {
+  JSObjectRef obj = JSC_JSValueToObject(ctx, value, NULL);
+  auto node = static_cast<JList::javaobject>(JSC_JSObjectGetPrivate(useCustomJSC, obj));
+  return make_local(node);
+}
+
+local_ref<ReadableNativeMap::jhybridobject> JSValueToReadableMapViaJSON(JSContextRef ctx, JSValueRef value) {
+  JSStringRef jsonRef = JSC_JSValueCreateJSONString(ctx, value, 0, NULL);
+  size_t size = JSC_JSStringGetLength(ctx, jsonRef);
+  const JSChar* utf16 = JSC_JSStringGetCharactersPtr(ctx, jsonRef);
+  std::string json = unicode::utf16toUTF8(utf16, size);
+  JSC_JSStringRelease(ctx, jsonRef);
+  folly::dynamic dynamicValue = folly::parseJson(json);
+  return ReadableNativeMap::newObjectCxxArgs(std::move(dynamicValue));
+}
+
+JSValueRef createNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+  JSClassRef classRef = managerWrapper->wrapperObjectClassRef;
+
+  static auto createNode =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<alias_ref<JShadowNode>(jint, jstring, jint, ReadableNativeMap::javaobject)>("createNode");
+
+  int reactTag = (int)JSC_JSValueToNumber(ctx, arguments[0], NULL);
+  auto viewName = JSValueToJString(ctx, arguments[1]);
+  int rootTag = (int)JSC_JSValueToNumber(ctx, arguments[2], NULL);
+  auto props = JSC_JSValueIsNull(ctx, arguments[3]) ? local_ref<ReadableNativeMap::jhybridobject>(nullptr) :
+               JSValueToReadableMapViaJSON(ctx, arguments[3]);;
+
+  // TODO: Retain object in arguments[4] using a weak ref.
+
+  auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get());
+
+  return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(node.get()));
+}
+
+JSValueRef cloneNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+  JSClassRef classRef = managerWrapper->wrapperObjectClassRef;
+
+  static auto cloneNode =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject)>("cloneNode");
+
+  auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
+  auto newNode = cloneNode(manager, previousNode.get());
+
+  return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
+}
+
+JSValueRef cloneNodeWithNewChildren(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+  JSClassRef classRef = managerWrapper->wrapperObjectClassRef;
+
+  static auto cloneNodeWithNewChildren =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject)>("cloneNodeWithNewChildren");
+
+  auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
+  auto newNode = cloneNodeWithNewChildren(manager, previousNode.get());
+
+  return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
+}
+
+JSValueRef cloneNodeWithNewProps(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+  JSClassRef classRef = managerWrapper->wrapperObjectClassRef;
+
+  static auto cloneNodeWithNewProps =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject)>("cloneNodeWithNewProps");
+
+  auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
+  auto props = JSValueToReadableMapViaJSON(ctx, arguments[1]);
+  auto newNode = cloneNodeWithNewProps(manager, previousNode.get(), props.get());
+
+  return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
+}
+
+JSValueRef cloneNodeWithNewChildrenAndProps(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+  JSClassRef classRef = managerWrapper->wrapperObjectClassRef;
+
+  static auto cloneNodeWithNewChildrenAndProps =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject)>("cloneNodeWithNewChildrenAndProps");
+
+  auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
+  auto props = JSValueToReadableMapViaJSON(ctx, arguments[1]);
+  auto newNode = cloneNodeWithNewChildrenAndProps(manager, previousNode.get(), props.get());
+
+  return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
+}
+
+JSValueRef appendChild(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+
+  static auto appendChild =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<void(JShadowNode::javaobject, JShadowNode::javaobject)>("appendChild");
+
+  auto parentNode = JSValueToJShadowNode(ctx, arguments[0]);
+  auto childNode = JSValueToJShadowNode(ctx, arguments[1]);
+
+  appendChild(manager, parentNode.get(), childNode.get());
+
+  return JSC_JSValueMakeUndefined(ctx);
+}
+
+JSValueRef createChildSet(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+  JSClassRef classRef = managerWrapper->wrapperObjectClassRef;
+
+  static auto createChildSet =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<alias_ref<JList>(jint)>("createChildSet");
+
+  int rootTag = (int)JSC_JSValueToNumber(ctx, arguments[0], NULL);
+  auto childSet = createChildSet(manager, rootTag);
+
+  return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(childSet.get()));
+}
+
+JSValueRef appendChildToSet(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+
+  static auto appendChildToSet =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<void(JList::javaobject, JShadowNode::javaobject)>("appendChildToSet");
+
+  auto childSet = JSValueToJList(ctx, arguments[0]);
+  auto childNode = JSValueToJShadowNode(ctx, arguments[1]);
+
+  appendChildToSet(manager, childSet.get(), childNode.get());
+
+  return JSC_JSValueMakeUndefined(ctx);
+}
+
+JSValueRef completeRoot(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+
+  static auto completeRoot =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<void(jint, JList::javaobject)>("completeRoot");
+
+  int rootTag = (int)JSC_JSValueToNumber(ctx, arguments[0], NULL);
+  auto childSet = JSValueToJList(ctx, arguments[1]);
+
+  completeRoot(manager, rootTag, childSet.get());
+
+  return JSC_JSValueMakeUndefined(ctx);
+}
+
+void finalizeJNIObject(JSObjectRef object) {
+  // Release whatever global ref object we're storing here.
+  jobject globalRef = (jobject)JSC_JSObjectGetPrivate(useCustomJSC, object);
+  Environment::current()->DeleteGlobalRef(globalRef);
+}
+
+void finalizeWrapper(JSObjectRef object) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, object);
+  delete managerWrapper;
+}
+
+void addFabricMethod(
+  JSContextRef context,
+  jni::alias_ref<jobject> fabricModule,
+  JSClassRef nodeClassRef,
+  JSObjectRef module,
+  const char *name,
+  JSObjectCallAsFunctionCallback callback
+) {
+  JSClassDefinition definition = kJSClassDefinitionEmpty;
+  definition.callAsFunction = callback;
+  definition.finalize = finalizeWrapper;
+  JSClassRef classRef = JSC_JSClassCreate(useCustomJSC, &definition);
+  FabricJSCUIManager *managerWrapper = new FabricJSCUIManager(fabricModule, nodeClassRef, useCustomJSC);
+  JSObjectRef functionRef = JSC_JSObjectMake(context, classRef, managerWrapper);
+  JSC_JSClassRelease(useCustomJSC, classRef);
+
+  JSStringRef nameStr = JSC_JSStringCreateWithUTF8CString(context, name);
+  JSC_JSObjectSetProperty(context, module, nameStr, functionRef, kJSPropertyAttributeNone, NULL);
+  JSC_JSStringRelease(context, nameStr);
+}
+
+}
+
+jni::local_ref<FabricJSCBinding::jhybriddata> FabricJSCBinding::initHybrid(
+    jni::alias_ref<jclass>) {
+  return makeCxxInstance();
+}
+
+void FabricJSCBinding::installFabric(jlong jsContextNativePointer,
+    jni::alias_ref<jobject> fabricModule) {
+  JSContextRef context = (JSContextRef)jsContextNativePointer;
+  useCustomJSC = facebook::react::isCustomJSCPtr(context);
+
+  JSObjectRef module = JSC_JSObjectMake(context, NULL, NULL);
+
+  // Class definition for wrapper objects around nodes and sets
+  JSClassDefinition definition = kJSClassDefinitionEmpty;
+  definition.finalize = finalizeJNIObject;
+  JSClassRef classRef = JSC_JSClassCreate(useCustomJSC, &definition);
+
+  addFabricMethod(context, fabricModule, classRef, module, "createNode", createNode);
+  addFabricMethod(context, fabricModule, classRef, module, "cloneNode", cloneNode);
+  addFabricMethod(context, fabricModule, classRef, module, "cloneNodeWithNewChildren", cloneNodeWithNewChildren);
+  addFabricMethod(context, fabricModule, classRef, module, "cloneNodeWithNewProps", cloneNodeWithNewProps);
+  addFabricMethod(context, fabricModule, classRef, module, "cloneNodeWithNewChildrenAndProps", cloneNodeWithNewChildrenAndProps);
+  addFabricMethod(context, fabricModule, classRef, module, "appendChild", appendChild);
+  addFabricMethod(context, fabricModule, classRef, module, "createChildSet", createChildSet);
+  addFabricMethod(context, fabricModule, classRef, module, "appendChildToSet", appendChildToSet);
+  addFabricMethod(context, fabricModule, classRef, module, "completeRoot", completeRoot);
+
+  JSObjectRef globalObject = JSC_JSContextGetGlobalObject(context);
+  JSStringRef globalName = JSC_JSStringCreateWithUTF8CString(context, "nativeFabricUIManager");
+  JSC_JSObjectSetProperty(context, globalObject, globalName, module, kJSPropertyAttributeNone, NULL);
+  JSC_JSStringRelease(context, globalName);
+}
+
+void FabricJSCBinding::registerNatives() {
+  registerHybrid({
+    makeNativeMethod("initHybrid", FabricJSCBinding::initHybrid),
+    makeNativeMethod("installFabric", FabricJSCBinding::installFabric),
+  });
+}
+
+}
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
new file mode 100644
index 000000000000..e23c9524ef20
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
@@ -0,0 +1,29 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <memory>
+#include <fb/fbjni.h>
+
+namespace facebook {
+namespace react {
+
+class Instance;
+
+class FabricJSCBinding : public jni::HybridClass<FabricJSCBinding> {
+public:
+  constexpr static const char *const kJavaDescriptor =
+    "Lcom/facebook/react/fabric/jsc/FabricJSCBinding;";
+
+  static void registerNatives();
+
+private:
+
+  static jni::local_ref<jhybriddata> initHybrid(jni::alias_ref<jclass>);
+
+  void installFabric(jlong jsContextNativePointer, jni::alias_ref<jobject> fabricModule);
+
+};
+
+}
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp
new file mode 100644
index 000000000000..1ca90c4e9d93
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp
@@ -0,0 +1,12 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include <fb/fbjni.h>
+#include <fb/xplat_init.h>
+
+#include "FabricJSCBinding.h"
+
+JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *vm, void *) {
+  return facebook::xplat::initialize(vm, [] {
+    facebook::react::FabricJSCBinding::registerNatives();
+  });
+}

From 7ce943ef3bf6e3c3b74bbcdbe0e125e3843e8924 Mon Sep 17 00:00:00 2001
From: Alejandro Paredes Alva <aparedes@aparedes.net>
Date: Wed, 14 Mar 2018 13:04:41 -0700
Subject: [PATCH 0023/1109] Adds _lineHeight = NAN; to RCTTextAttributes

Summary:
<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

On iOS, when the parent Text contains the `lineHeight` style prop, and the children are also Text components they don't inherit the lineHeight prop.

This is for **iOS** only.
Create a react-native project with React Native 0.54.0 or 0.54.1 and change the app to:
```js
import React, { Component } from 'react';
import { StyleSheet, Text, View } from 'react-native';

type Props = {};
export default class App extends Component<Props> {
  render() {
    return (
      <View style={styles.container}>
        <Text style={{ fontWeight: 'bold', lineHeight: 40 }}>
          <Text style={{ color: 'orange' }}>I am bold and orange, </Text>
          <Text style={{ color: 'red' }}>I am bold and red, </Text>
          <Text style={{ color: 'blue' }}>I am bold and blue, </Text>
          <Text style={{ color: 'purple' }}>I am bold and purple, </Text>
          <Text style={{ color: 'yellow' }}>I am bold and yellow, </Text>
          <Text style={{ color: 'pink' }}>I am bold and pink</Text>
        </Text>
      </View>
    );
  }
}

const styles = StyleSheet.create({
  container: {
    backgroundColor: 'black',
    flex: 1,
    justifyContent: 'center',
    padding: 50,
  },
});
```
It displays:
![iphone - 2018-03-12 at 21 51 53](https://user-images.githubusercontent.com/480605/37308941-b56f082e-263f-11e8-9c23-892f77077169.png)

But should look like:
![iphone - 2018-03-12 at 21 48 15](https://user-images.githubusercontent.com/480605/37308784-4efaddf2-263f-11e8-992b-ee0b6bb9a97b.png)

New &lt;Text> iOS https://github.com/facebook/react-native/commit/2716f53

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[CATEGORY] [TYPE] [LOCATION] - MESSAGE

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
[IOS] [MINOR] [Text] - Inherit lineheight
Closes https://github.com/facebook/react-native/pull/18340

Differential Revision: D7276655

Pulled By: shergin

fbshipit-source-id: 0fe26536bb74da77be8405911fc699a622bc0b2f
---
 Libraries/Text/RCTTextAttributes.m | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Libraries/Text/RCTTextAttributes.m b/Libraries/Text/RCTTextAttributes.m
index 6427e303158b..d74e0ab7611b 100644
--- a/Libraries/Text/RCTTextAttributes.m
+++ b/Libraries/Text/RCTTextAttributes.m
@@ -21,6 +21,7 @@ - (instancetype)init
   if (self = [super init]) {
     _fontSize = NAN;
     _letterSpacing = NAN;
+    _lineHeight = NAN;
     _textDecorationStyle = NSUnderlineStyleSingle;
     _fontSizeMultiplier = NAN;
     _alignment = NSTextAlignmentNatural;

From 67656991b32075e8b4a99c6409b0a131206c6941 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 14 Mar 2018 14:04:19 -0700
Subject: [PATCH 0024/1109] Move Image PropTypes to a new file

Reviewed By: yungsters

Differential Revision: D7270058

fbshipit-source-id: 91ad7700b7e89c393c6977bfd82494d2febda4a4
---
 Libraries/Image/Image.ios.js  | 118 +-----------------------------
 Libraries/Image/ImageProps.js | 134 ++++++++++++++++++++++++++++++++++
 2 files changed, 136 insertions(+), 116 deletions(-)
 create mode 100644 Libraries/Image/ImageProps.js

diff --git a/Libraries/Image/Image.ios.js b/Libraries/Image/Image.ios.js
index 173d78704f66..c3e9ad5359c1 100644
--- a/Libraries/Image/Image.ios.js
+++ b/Libraries/Image/Image.ios.js
@@ -11,6 +11,7 @@
 'use strict';
 
 const EdgeInsetsPropType = require('EdgeInsetsPropType');
+const ImageProps = require('ImageProps');
 const ImageResizeMode = require('ImageResizeMode');
 const ImageSourcePropType = require('ImageSourcePropType');
 const ImageStylePropTypes = require('ImageStylePropTypes');
@@ -38,122 +39,7 @@ const ImageViewManager = NativeModules.ImageViewManager;
  */
 const Image = createReactClass({
   displayName: 'Image',
-  propTypes: {
-    /**
-     * See https://facebook.github.io/react-native/docs/image.html#style
-     */
-    style: StyleSheetPropType(ImageStylePropTypes),
-    /**
-     * The image source (either a remote URL or a local file resource).
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#source
-     */
-    source: ImageSourcePropType,
-    /**
-     * A static image to display while loading the image source.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#defaultsource
-     */
-    defaultSource: PropTypes.oneOfType([
-      PropTypes.shape({
-        uri: PropTypes.string,
-        width: PropTypes.number,
-        height: PropTypes.number,
-        scale: PropTypes.number,
-      }),
-      PropTypes.number,
-    ]),
-    /**
-     * When true, indicates the image is an accessibility element.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#accessible
-     */
-    accessible: PropTypes.bool,
-    /**
-     * The text that's read by the screen reader when the user interacts with
-     * the image.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#accessibilitylabel
-     */
-    accessibilityLabel: PropTypes.node,
-    /**
-     * blurRadius: the blur radius of the blur filter added to the image
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#blurradius
-     */
-    blurRadius: PropTypes.number,
-    /**
-     * See https://facebook.github.io/react-native/docs/image.html#capinsets
-     */
-    capInsets: EdgeInsetsPropType,
-    /**
-     * See https://facebook.github.io/react-native/docs/image.html#resizemethod
-     */
-    resizeMethod: PropTypes.oneOf(['auto', 'resize', 'scale']),
-    /**
-     * Determines how to resize the image when the frame doesn't match the raw
-     * image dimensions.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#resizemode
-     */
-    resizeMode: PropTypes.oneOf([
-      'cover',
-      'contain',
-      'stretch',
-      'repeat',
-      'center',
-    ]),
-    /**
-     * A unique identifier for this element to be used in UI Automation
-     * testing scripts.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#testid
-     */
-    testID: PropTypes.string,
-    /**
-     * Invoked on mount and layout changes with
-     * `{nativeEvent: {layout: {x, y, width, height}}}`.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#onlayout
-     */
-    onLayout: PropTypes.func,
-    /**
-     * Invoked on load start.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#onloadstart
-     */
-    onLoadStart: PropTypes.func,
-    /**
-     * Invoked on download progress with `{nativeEvent: {loaded, total}}`.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#onprogress
-     */
-    onProgress: PropTypes.func,
-    /**
-     * Invoked on load error with `{nativeEvent: {error}}`.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#onerror
-     */
-    onError: PropTypes.func,
-    /**
-     * Invoked when a partial load of the image is complete.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#onpartialload
-     */
-    onPartialLoad: PropTypes.func,
-    /**
-     * Invoked when load completes successfully.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#onload
-     */
-    onLoad: PropTypes.func,
-    /**
-     * Invoked when load either succeeds or fails.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#onloadend
-     */
-    onLoadEnd: PropTypes.func,
-  },
+  propTypes: ImageProps,
 
   statics: {
     resizeMode: ImageResizeMode,
diff --git a/Libraries/Image/ImageProps.js b/Libraries/Image/ImageProps.js
new file mode 100644
index 000000000000..eb09ccd8e4ea
--- /dev/null
+++ b/Libraries/Image/ImageProps.js
@@ -0,0 +1,134 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @providesModule ImageProps
+ * @flow
+ */
+
+'use strict';
+
+const EdgeInsetsPropType = require('EdgeInsetsPropType');
+const ImageSourcePropType = require('ImageSourcePropType');
+const ImageStylePropTypes = require('ImageStylePropTypes');
+const PropTypes = require('prop-types');
+const StyleSheetPropType = require('StyleSheetPropType');
+
+module.exports = {
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#style
+   */
+  style: StyleSheetPropType(ImageStylePropTypes),
+  /**
+   * The image source (either a remote URL or a local file resource).
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#source
+   */
+  source: ImageSourcePropType,
+  /**
+   * A static image to display while loading the image source.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#defaultsource
+   */
+  defaultSource: PropTypes.oneOfType([
+    PropTypes.shape({
+      uri: PropTypes.string,
+      width: PropTypes.number,
+      height: PropTypes.number,
+      scale: PropTypes.number,
+    }),
+    PropTypes.number,
+  ]),
+  /**
+   * When true, indicates the image is an accessibility element.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#accessible
+   */
+  accessible: PropTypes.bool,
+  /**
+   * The text that's read by the screen reader when the user interacts with
+   * the image.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#accessibilitylabel
+   */
+  accessibilityLabel: PropTypes.node,
+  /**
+   * blurRadius: the blur radius of the blur filter added to the image
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#blurradius
+   */
+  blurRadius: PropTypes.number,
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#capinsets
+   */
+  capInsets: EdgeInsetsPropType,
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#resizemethod
+   */
+  resizeMethod: PropTypes.oneOf(['auto', 'resize', 'scale']),
+  /**
+   * Determines how to resize the image when the frame doesn't match the raw
+   * image dimensions.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#resizemode
+   */
+  resizeMode: PropTypes.oneOf([
+    'cover',
+    'contain',
+    'stretch',
+    'repeat',
+    'center',
+  ]),
+  /**
+   * A unique identifier for this element to be used in UI Automation
+   * testing scripts.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#testid
+   */
+  testID: PropTypes.string,
+  /**
+   * Invoked on mount and layout changes with
+   * `{nativeEvent: {layout: {x, y, width, height}}}`.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#onlayout
+   */
+  onLayout: PropTypes.func,
+  /**
+   * Invoked on load start.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#onloadstart
+   */
+  onLoadStart: PropTypes.func,
+  /**
+   * Invoked on download progress with `{nativeEvent: {loaded, total}}`.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#onprogress
+   */
+  onProgress: PropTypes.func,
+  /**
+   * Invoked on load error with `{nativeEvent: {error}}`.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#onerror
+   */
+  onError: PropTypes.func,
+  /**
+   * Invoked when a partial load of the image is complete.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#onpartialload
+   */
+  onPartialLoad: PropTypes.func,
+  /**
+   * Invoked when load completes successfully.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#onload
+   */
+  onLoad: PropTypes.func,
+  /**
+   * Invoked when load either succeeds or fails.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#onloadend
+   */
+  onLoadEnd: PropTypes.func,
+};

From 8bac869f5d1f2ef42e707d0ec817afc6ac98b3b2 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 14 Mar 2018 14:04:21 -0700
Subject: [PATCH 0025/1109] Create Flow Props for Image

Reviewed By: yungsters

Differential Revision: D7270057

fbshipit-source-id: 1ecac28e4060fe0e85a4f0698406f8986ae16caf
---
 Libraries/Image/ImageProps.js | 31 +++++++++++++++++++++++++++++++
 1 file changed, 31 insertions(+)

diff --git a/Libraries/Image/ImageProps.js b/Libraries/Image/ImageProps.js
index eb09ccd8e4ea..f075d9cceced 100644
--- a/Libraries/Image/ImageProps.js
+++ b/Libraries/Image/ImageProps.js
@@ -6,6 +6,7 @@
  *
  * @providesModule ImageProps
  * @flow
+ * @format
  */
 
 'use strict';
@@ -16,6 +17,36 @@ const ImageStylePropTypes = require('ImageStylePropTypes');
 const PropTypes = require('prop-types');
 const StyleSheetPropType = require('StyleSheetPropType');
 
+import type {ImageSource} from 'ImageSource';
+import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
+import type {LayoutEvent} from 'CoreEventTypes';
+import type {SyntheticEvent} from 'CoreEventTypes';
+
+export type ImageProps = {
+  accessible?: boolean,
+  accessibilityLabel?: ?(string | Array<any> | any),
+  blurRadius?: number,
+  capInsets?: ?EdgeInsetsProp,
+
+  onError?: ?(event: SyntheticEvent<$ReadOnly<{||}>>) => void,
+  onLayout?: ?(event: LayoutEvent) => void,
+  onLoad?: ?() => void,
+  onLoadEnd?: ?() => void,
+  onLoadStart?: ?() => void,
+  resizeMethod?: ?('auto' | 'resize' | 'scale'),
+  resizeMode?: ?('cover' | 'contain' | 'stretch' | 'repeat' | 'center'),
+  source?: ?ImageSource,
+  style?: typeof ImageStylePropTypes,
+  testID?: ?string,
+
+  // ios
+  defaultSource?: ?ImageSource,
+  onPartialLoad?: ?() => void,
+  onProgress?: ?(
+    event: SyntheticEvent<$ReadOnly<{|loaded: number, total: number|}>>,
+  ) => void,
+};
+
 module.exports = {
   /**
    * See https://facebook.github.io/react-native/docs/image.html#style

From 28c9c68cfa51ea224466d9e0f1aac5ec39d220e0 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 14 Mar 2018 14:30:44 -0700
Subject: [PATCH 0026/1109] Adding documentation to new StyleSheet Flow Types

Summary: Adding some explanation and examples of when to use these types.

Reviewed By: yungsters

Differential Revision: D7270185

fbshipit-source-id: c82f061ffb77e33133a59d268a08f7a95fd02fb6
---
 Libraries/StyleSheet/StyleSheet.js | 36 +++++++++++++++++++++++++++++-
 1 file changed, 35 insertions(+), 1 deletion(-)

diff --git a/Libraries/StyleSheet/StyleSheet.js b/Libraries/StyleSheet/StyleSheet.js
index 3320c459b68c..f2552f3e66d1 100644
--- a/Libraries/StyleSheet/StyleSheet.js
+++ b/Libraries/StyleSheet/StyleSheet.js
@@ -27,11 +27,45 @@ import type {
   LayoutStyle,
 } from 'StyleSheetTypes';
 
-export type DangerouslyImpreciseStyleProp = ____DangerouslyImpreciseStyleProp_Internal;
+/**
+ * This type should be used as the type for a prop that is passed through
+ * to a <View>'s `style` prop. This ensures call sites of the component
+ * can't pass styles that View doesn't support such as `fontSize`.`
+ *
+ * type Props = {style: ViewStyleProp}
+ * const MyComponent = (props: Props) => <View style={props.style} />
+ */
 export type ViewStyleProp = ____ViewStyleProp_Internal;
+
+/**
+ * This type should be used as the type for a prop that is passed through
+ * to a <Text>'s `style` prop. This ensures call sites of the component
+ * can't pass styles that Text doesn't support such as `resizeMode`.`
+ *
+ * type Props = {style: TextStyleProp}
+ * const MyComponent = (props: Props) => <Text style={props.style} />
+ */
 export type TextStyleProp = ____TextStyleProp_Internal;
+
+/**
+ * This type should be used as the type for a prop that is passed through
+ * to an <Image>'s `style` prop. This ensures call sites of the component
+ * can't pass styles that Image doesn't support such as `fontSize`.`
+ *
+ * type Props = {style: ImageStyleProp}
+ * const MyComponent = (props: Props) => <Image style={props.style} />
+ */
 export type ImageStyleProp = ____ImageStyleProp_Internal;
 
+/**
+ * WARNING: You probably shouldn't be using this type. This type
+ * is similar to the ones above except it allows styles that are accepted
+ * by all of View, Text, or Image. It is therefore very unsafe to pass this
+ * through to an underlying component. Using this is almost always a mistake
+ * and using one of the other more restrictive types is likely the right choice.
+ */
+export type DangerouslyImpreciseStyleProp = ____DangerouslyImpreciseStyleProp_Internal;
+
 let hairlineWidth = PixelRatio.roundToNearestPixel(0.4);
 if (hairlineWidth === 0) {
   hairlineWidth = 1 / PixelRatio.get();

From c595509048cc5f6cab360cd2ccbe7c86405baf92 Mon Sep 17 00:00:00 2001
From: Khaer Ansori <khaer.ansori@traveloka.com>
Date: Wed, 14 Mar 2018 14:41:58 -0700
Subject: [PATCH 0027/1109] Add number-pad keyboardType

Summary:
On Android there's no number-pad but numeric instead, for my use-case I need number only (without decimal and sign, for PIN input)

I write it so there's no breaking change for those already using the `TextInput` Component

None

[ANDROID][ENHANCEMENT][Component] Add number-pad keyboardType
Closes https://github.com/facebook/react-native/pull/18350

Reviewed By: achen1

Differential Revision: D7269721

Pulled By: mdvacca

fbshipit-source-id: 82571dce948e0cf2e4354dc46c69198ec69ba65a
---
 Libraries/Components/TextInput/TextInput.js               | 4 ++--
 .../react/views/textinput/ReactTextInputManager.java      | 8 ++++++--
 2 files changed, 8 insertions(+), 4 deletions(-)

diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index deb3b40e48bd..2c6c4f8ef19b 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -244,6 +244,7 @@ const TextInput = createReactClass({
      *
      * - `default`
      * - `numeric`
+     * - `number-pad`
      * - `email-address`
      * - `phone-pad`
      *
@@ -254,7 +255,6 @@ const TextInput = createReactClass({
      * - `ascii-capable`
      * - `numbers-and-punctuation`
      * - `url`
-     * - `number-pad`
      * - `name-phone-pad`
      * - `decimal-pad`
      * - `twitter`
@@ -272,11 +272,11 @@ const TextInput = createReactClass({
       'email-address',
       'numeric',
       'phone-pad',
+      'number-pad',
       // iOS-only
       'ascii-capable',
       'numbers-and-punctuation',
       'url',
-      'number-pad',
       'name-phone-pad',
       'decimal-pad',
       'twitter',
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
index 637027140ec0..2c5013a7e712 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
@@ -68,8 +68,9 @@ public class ReactTextInputManager extends BaseViewManager<ReactEditText, Layout
   private static final int FOCUS_TEXT_INPUT = 1;
   private static final int BLUR_TEXT_INPUT = 2;
 
-  private static final int INPUT_TYPE_KEYBOARD_NUMBERED =
-      InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_FLAG_DECIMAL |
+  private static final int INPUT_TYPE_KEYBOARD_NUMBER_PAD = InputType.TYPE_CLASS_NUMBER; 
+  private static final int INPUT_TYPE_KEYBOARD_NUMBERED = INPUT_TYPE_KEYBOARD_NUMBER_PAD |
+          InputType.TYPE_NUMBER_FLAG_DECIMAL |
           InputType.TYPE_NUMBER_FLAG_SIGNED;
   private static final int PASSWORD_VISIBILITY_FLAG = InputType.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD &
         ~InputType.TYPE_TEXT_VARIATION_PASSWORD;
@@ -80,6 +81,7 @@ public class ReactTextInputManager extends BaseViewManager<ReactEditText, Layout
 
   private static final String KEYBOARD_TYPE_EMAIL_ADDRESS = "email-address";
   private static final String KEYBOARD_TYPE_NUMERIC = "numeric";
+  private static final String KEYBOARD_TYPE_NUMBER_PAD = "number-pad";
   private static final String KEYBOARD_TYPE_PHONE_PAD = "phone-pad";
   private static final String KEYBOARD_TYPE_VISIBLE_PASSWORD = "visible-password";
   private static final InputFilter[] EMPTY_FILTERS = new InputFilter[0];
@@ -557,6 +559,8 @@ public void setKeyboardType(ReactEditText view, @Nullable String keyboardType) {
     int flagsToSet = InputType.TYPE_CLASS_TEXT;
     if (KEYBOARD_TYPE_NUMERIC.equalsIgnoreCase(keyboardType)) {
       flagsToSet = INPUT_TYPE_KEYBOARD_NUMBERED;
+    } else if (KEYBOARD_TYPE_NUMBER_PAD.equalsIgnoreCase(keyboardType)) {
+      flagsToSet = INPUT_TYPE_KEYBOARD_NUMBER_PAD;
     } else if (KEYBOARD_TYPE_EMAIL_ADDRESS.equalsIgnoreCase(keyboardType)) {
       flagsToSet = InputType.TYPE_TEXT_VARIATION_EMAIL_ADDRESS | InputType.TYPE_CLASS_TEXT;
     } else if (KEYBOARD_TYPE_PHONE_PAD.equalsIgnoreCase(keyboardType)) {

From 304db5cb65af38cde030057c9fa3988f8a777778 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 14 Mar 2018 15:38:35 -0700
Subject: [PATCH 0028/1109] Add MIT license to Fabric

Reviewed By: fkgozali

Differential Revision: D7278262

fbshipit-source-id: 39f4c73b8f693162eb037125bf64fecc7eb0cf8b
---
 .../main/java/com/facebook/react/fabric/FabricBinding.java | 7 +++++++
 .../java/com/facebook/react/fabric/FabricUIManager.java    | 7 ++++++-
 .../com/facebook/react/fabric/RootShadowNodeRegistry.java  | 7 +++++++
 .../com/facebook/react/fabric/jsc/FabricJSCBinding.java    | 7 ++++++-
 .../com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp | 7 ++++++-
 .../com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h   | 7 ++++++-
 .../main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp | 7 ++++++-
 7 files changed, 44 insertions(+), 5 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
index 37a943afac69..97535f0a0d74 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
@@ -1,3 +1,10 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
 package com.facebook.react.fabric;
 
 import com.facebook.react.bridge.JavaScriptContextHolder;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 6fd4c1ae2d69..38eea630d4bb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -1,4 +1,9 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
 
 package com.facebook.react.fabric;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/RootShadowNodeRegistry.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/RootShadowNodeRegistry.java
index 95f2c1cedaee..49884cfc1f24 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/RootShadowNodeRegistry.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/RootShadowNodeRegistry.java
@@ -1,3 +1,10 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
 package com.facebook.react.fabric;
 
 import android.util.SparseArray;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
index ab7352f9ede0..8ae05ff65808 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
@@ -1,4 +1,9 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
 
 package com.facebook.react.fabric.jsc;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
index 044143210b1c..6ce8b9976e34 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
@@ -1,4 +1,9 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
 
 #include "FabricJSCBinding.h"
 #include <fb/fbjni.h>
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
index e23c9524ef20..6327ec690a42 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
@@ -1,4 +1,9 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp
index 1ca90c4e9d93..e6b84dd24c9b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/OnLoad.cpp
@@ -1,4 +1,9 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
 
 #include <fb/fbjni.h>
 #include <fb/xplat_init.h>

From d678058402bd2faad3f6503182386a92109392a9 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 14 Mar 2018 16:01:32 -0700
Subject: [PATCH 0029/1109] Add Fabric integration test

Reviewed By: fkgozali

Differential Revision: D7207630

fbshipit-source-id: 69cc10d7d45031eec9f3d934b981a5e4bb62a0ef
---
 Libraries/ReactNative/AppRegistry.js          | 26 +++++++--
 .../java/com/facebook/react/testing/BUCK      |  2 +
 .../ReactAppInstrumentationTestCase.java      | 17 +++---
 .../react/testing/ReactAppTestActivity.java   | 54 +++++++++++++++++++
 4 files changed, 90 insertions(+), 9 deletions(-)

diff --git a/Libraries/ReactNative/AppRegistry.js b/Libraries/ReactNative/AppRegistry.js
index 87bd07a6dd14..21fdca68a43d 100644
--- a/Libraries/ReactNative/AppRegistry.js
+++ b/Libraries/ReactNative/AppRegistry.js
@@ -20,6 +20,10 @@ const infoLog = require('infoLog');
 const invariant = require('fbjs/lib/invariant');
 const renderApplication = require('renderApplication');
 
+// Renderer provider must be supplied by each app. If none, traditional
+// renderApplication() will be used.
+let fabricRendererProvider: ?() => typeof renderApplication = null;
+
 type Task = (taskData: any) => Promise<void>;
 type TaskProvider = () => Task;
 export type ComponentProvider = () => React$ComponentType<any>;
@@ -31,6 +35,7 @@ export type AppConfig = {
   component?: ComponentProvider,
   run?: Function,
   section?: boolean,
+  fabric?: boolean,
 };
 export type Runnable = {
   component?: ComponentProvider,
@@ -80,6 +85,7 @@ const AppRegistry = {
           appConfig.appKey,
           appConfig.component,
           appConfig.section,
+          appConfig.fabric,
         );
       }
     });
@@ -94,16 +100,26 @@ const AppRegistry = {
     appKey: string,
     componentProvider: ComponentProvider,
     section?: boolean,
+    fabric?: boolean,
   ): string {
     runnables[appKey] = {
       componentProvider,
-      run: appParameters =>
-        renderApplication(
+      run: appParameters => {
+        let renderFunc = renderApplication;
+        if (fabric) {
+          invariant(
+            fabricRendererProvider != null,
+            'A Fabric renderer provider must be set to render Fabric components',
+          );
+          renderFunc = fabricRendererProvider();
+        }
+        renderFunc(
           componentProviderInstrumentationHook(componentProvider),
           appParameters.initialProps,
           appParameters.rootTag,
           wrapperComponentProvider && wrapperComponentProvider(appParameters),
-        ),
+        );
+      },
     };
     if (section) {
       sections[appKey] = runnables[appKey];
@@ -236,6 +252,10 @@ const AppRegistry = {
         NativeModules.HeadlessJsTaskSupport.notifyTaskFinished(taskId);
       });
   },
+
+  setFabricRendererProvider(provider: () => typeof renderApplication): void {
+    fabricRendererProvider = provider;
+  },
 };
 
 BatchedBridge.registerCallableModule('AppRegistry', AppRegistry);
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
index 9654ee54083e..7d96b9b3bb53 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
@@ -27,6 +27,8 @@ rn_android_library(
         react_native_target("java/com/facebook/react/bridge:bridge"),
         react_native_target("java/com/facebook/react/common:common"),
         react_native_target("java/com/facebook/react/devsupport:interfaces"),
+        react_native_target("java/com/facebook/react/fabric:fabric"),
+        react_native_target("java/com/facebook/react/fabric/jsc:jsc"),
         react_native_target("java/com/facebook/react/module/annotations:annotations"),
         react_native_target("java/com/facebook/react/module/model:model"),
         react_native_target("java/com/facebook/react/modules/core:core"),
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppInstrumentationTestCase.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppInstrumentationTestCase.java
index 8b93eeb8b19a..863e249cbfe3 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppInstrumentationTestCase.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppInstrumentationTestCase.java
@@ -7,19 +7,17 @@
 
 package com.facebook.react.testing;
 
-import javax.annotation.Nullable;
-
-import java.util.concurrent.CountDownLatch;
-import java.util.concurrent.TimeUnit;
-
+import android.content.Intent;
 import android.graphics.Bitmap;
 import android.test.ActivityInstrumentationTestCase2;
 import android.view.View;
 import android.view.ViewGroup;
-
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.testing.idledetection.IdleWaiter;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
+import javax.annotation.Nullable;
 
 /**
  * Base class for instrumentation tests that runs React based react application in UI mode
@@ -35,6 +33,9 @@ public ReactAppInstrumentationTestCase() {
   protected void setUp() throws Exception {
     super.setUp();
 
+    Intent intent = new Intent();
+    intent.putExtra(ReactAppTestActivity.EXTRA_IS_FABRIC_TEST, isFabricTest());
+    setActivityIntent(intent);
     final ReactAppTestActivity activity = getActivity();
     try {
       runTestOnUiThread(new Runnable() {
@@ -144,6 +145,10 @@ protected boolean getEnableDevSupport() {
     return false;
   }
 
+  protected boolean isFabricTest() {
+    return false;
+  }
+
   /**
    * Override this method to provide extra native modules to be loaded before the app starts
    */
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index 96c180306350..0a68ad1ed5df 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -7,6 +7,7 @@
 
 package com.facebook.react.testing;
 
+import android.content.Intent;
 import android.graphics.Bitmap;
 import android.os.Bundle;
 import android.support.v4.app.FragmentActivity;
@@ -17,8 +18,16 @@
 import com.facebook.react.ReactInstanceManager;
 import com.facebook.react.ReactInstanceManagerBuilder;
 import com.facebook.react.ReactRootView;
+import com.facebook.react.bridge.JSIModule;
+import com.facebook.react.bridge.JSIModuleHolder;
+import com.facebook.react.bridge.JSIModulesProvider;
+import com.facebook.react.bridge.JavaScriptContextHolder;
+import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReactContext;
+import com.facebook.react.bridge.UIManager;
 import com.facebook.react.common.LifecycleState;
+import com.facebook.react.fabric.FabricUIManager;
+import com.facebook.react.fabric.jsc.FabricJSCBinding;
 import com.facebook.react.modules.core.DefaultHardwareBackBtnHandler;
 import com.facebook.react.modules.core.PermissionAwareActivity;
 import com.facebook.react.modules.core.PermissionListener;
@@ -26,6 +35,10 @@
 import com.facebook.react.testing.idledetection.ReactBridgeIdleSignaler;
 import com.facebook.react.testing.idledetection.ReactIdleDetectionUtil;
 import com.facebook.react.uimanager.UIImplementationProvider;
+import com.facebook.react.uimanager.ViewManager;
+import com.facebook.react.uimanager.ViewManagerRegistry;
+import java.util.ArrayList;
+import java.util.List;
 import java.util.concurrent.CountDownLatch;
 import java.util.concurrent.TimeUnit;
 import javax.annotation.Nullable;
@@ -33,6 +46,8 @@
 public class ReactAppTestActivity extends FragmentActivity
     implements DefaultHardwareBackBtnHandler, PermissionAwareActivity {
 
+  public static final String EXTRA_IS_FABRIC_TEST = "is_fabric_test";
+
   private static final String DEFAULT_BUNDLE_NAME = "AndroidTestBundle.js";
   private static final int ROOT_VIEW_ID = 8675309;
   // we need a bigger timeout for CI builds because they run on a slow emulator
@@ -62,6 +77,11 @@ protected void onCreate(Bundle savedInstanceState) {
     rootView.addView(mScreenshotingFrameLayout);
 
     mReactRootView = new ReactRootView(this);
+    Intent intent = getIntent();
+    if (intent != null && intent.getBooleanExtra(EXTRA_IS_FABRIC_TEST, false)) {
+      mReactRootView.setIsFabric(true);
+    }
+
     mScreenshotingFrameLayout.addView(mReactRootView);
   }
 
@@ -179,6 +199,36 @@ public void loadApp(
         .setUseDeveloperSupport(useDevSupport)
         .setBridgeIdleDebugListener(mBridgeIdleSignaler)
         .setInitialLifecycleState(mLifecycleState)
+        .setJSIModulesProvider(
+          new JSIModulesProvider() {
+            @Override
+            public List<JSIModuleHolder> getJSIModules(
+              final ReactApplicationContext reactApplicationContext,
+              final JavaScriptContextHolder jsContext) {
+
+              List<JSIModuleHolder> modules = new ArrayList<>();
+              modules.add(
+                new JSIModuleHolder() {
+
+                  @Override
+                  public Class<? extends JSIModule> getJSIModuleClass() {
+                    return UIManager.class;
+                  }
+
+                  @Override
+                  public FabricUIManager getJSIModule() {
+                    List<ViewManager> viewManagers =
+                      getReactInstanceManager().getOrCreateViewManagers(reactApplicationContext);
+                    FabricUIManager fabricUIManager =
+                      new FabricUIManager(
+                        reactApplicationContext, new ViewManagerRegistry(viewManagers));
+                    new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
+                    return fabricUIManager;
+                  }
+                });
+
+              return modules;
+            }})
         .setUIImplementationProvider(uiImplementationProvider);
 
     mReactInstanceManager = builder.build();
@@ -195,6 +245,10 @@ public void onGlobalLayout() {
         .startReactApplication(mReactInstanceManager, appKey, initialProps);
   }
 
+  private ReactInstanceManager getReactInstanceManager() {
+    return mReactInstanceManager;
+  }
+
   public boolean waitForLayout(long millis) throws InterruptedException {
     return mLayoutEvent.await(millis, TimeUnit.MILLISECONDS);
   }

From 22004db81912f66650e9f9776d0045b88df61b5b Mon Sep 17 00:00:00 2001
From: Brian Vaughn <bvaughn@fb.com>
Date: Wed, 14 Mar 2018 23:23:11 -0700
Subject: [PATCH 0030/1109] React sync for revisions ad9544f...ced176e

Reviewed By: sebmarkbage

Differential Revision: D7281277

fbshipit-source-id: 75a638114cf2a65a5c973dbdf218f6d3ba042cc4
---
 Libraries/Renderer/REVISION                   |  2 +-
 Libraries/Renderer/ReactFabric-dev.js         | 55 +++++++++++++++----
 Libraries/Renderer/ReactFabric-prod.js        | 51 ++++++++++-------
 Libraries/Renderer/ReactNativeRenderer-dev.js | 55 +++++++++++++++----
 .../Renderer/ReactNativeRenderer-prod.js      | 49 ++++++++++-------
 Libraries/Renderer/shims/ReactTypes.js        |  2 +-
 package.json                                  |  6 +-
 7 files changed, 153 insertions(+), 67 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index 824ff8c33a4c..321055318423 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-ad9544f48e58f2599a8ea0de1e9f4dd104db30bb
\ No newline at end of file
+ced176edb7605a25e916895fd060f3943c647fee
\ No newline at end of file
diff --git a/Libraries/Renderer/ReactFabric-dev.js b/Libraries/Renderer/ReactFabric-dev.js
index 867873cd41d5..e485c5621823 100644
--- a/Libraries/Renderer/ReactFabric-dev.js
+++ b/Libraries/Renderer/ReactFabric-dev.js
@@ -810,6 +810,7 @@ var Fragment = 10;
 var Mode = 11;
 var ContextConsumer = 12;
 var ContextProvider = 13;
+var ForwardRef = 14;
 
 function getParent(inst) {
   do {
@@ -2356,6 +2357,9 @@ var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
 var REACT_ASYNC_MODE_TYPE = hasSymbol
   ? Symbol["for"]("react.async_mode")
   : 0xeacf;
+var REACT_FORWARD_REF_TYPE = hasSymbol
+  ? Symbol["for"]("react.forward_ref")
+  : 0xead0;
 
 var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
 var FAUX_ITERATOR_SYMBOL = "@@iterator";
@@ -2637,7 +2641,7 @@ var TouchHistoryMath = {
 
 // TODO: this is special because it gets imported during build.
 
-var ReactVersion = "16.3.0-alpha.1";
+var ReactVersion = "16.3.0-alpha.2";
 
 function _classCallCheck(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
@@ -5242,6 +5246,9 @@ function createFiberFromElement(element, mode, expirationTime) {
               // This is a consumer
               fiberTag = ContextConsumer;
               break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = ForwardRef;
+              break;
             default:
               if (typeof type.tag === "number") {
                 // Currently assumed to be a continuation and therefore is a
@@ -6834,20 +6841,20 @@ var ReactFiberClassComponent = function(
       // In order to support react-lifecycles-compat polyfilled components,
       // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
       if (
-        (typeof instance.UNSAFE_componentWillUpdate === "function" ||
-          typeof instance.componentWillUpdate === "function") &&
+        (typeof instance.UNSAFE_componentWillMount === "function" ||
+          typeof instance.componentWillMount === "function") &&
         typeof ctor.getDerivedStateFromProps !== "function"
       ) {
-        startPhaseTimer(workInProgress, "componentWillUpdate");
-        if (typeof instance.componentWillUpdate === "function") {
-          instance.componentWillUpdate(newProps, newState, newContext);
+        startPhaseTimer(workInProgress, "componentWillMount");
+        if (typeof instance.componentWillMount === "function") {
+          instance.componentWillMount();
         }
-        if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
+        if (typeof instance.UNSAFE_componentWillMount === "function") {
+          instance.UNSAFE_componentWillMount();
         }
         stopPhaseTimer();
       }
-      if (typeof instance.componentDidUpdate === "function") {
+      if (typeof instance.componentDidMount === "function") {
         workInProgress.effectTag |= Update;
       }
     } else {
@@ -8467,6 +8474,14 @@ var ReactFiberBeginWork = function(
     }
   }
 
+  function updateForwardRef(current, workInProgress) {
+    var render = workInProgress.type.render;
+    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+    return workInProgress.child;
+  }
+
   function updateFragment(current, workInProgress) {
     var nextChildren = workInProgress.pendingProps;
     if (hasContextChanged()) {
@@ -9420,6 +9435,8 @@ var ReactFiberBeginWork = function(
           workInProgress,
           renderExpirationTime
         );
+      case ForwardRef:
+        return updateForwardRef(current, workInProgress);
       case Fragment:
         return updateFragment(current, workInProgress);
       case Mode:
@@ -9972,6 +9989,8 @@ var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
       case ReturnComponent:
         // Does nothing.
         return null;
+      case ForwardRef:
+        return null;
       case Fragment:
         return null;
       case Mode:
@@ -10277,7 +10296,7 @@ var ReactFiberCommitWork = function(
           }
         }
       } else {
-        ref.value = null;
+        ref.current = null;
       }
     }
   }
@@ -10442,7 +10461,19 @@ var ReactFiberCommitWork = function(
       if (typeof ref === "function") {
         ref(instanceToUse);
       } else {
-        ref.value = instanceToUse;
+        {
+          if (!ref.hasOwnProperty("current")) {
+            warning(
+              false,
+              "Unexpected ref object provided for %s. " +
+                "Use either a ref-setter function or Reacte.createRef().%s",
+              getComponentName(finishedWork),
+              getStackAddendumByWorkInProgressFiber(finishedWork)
+            );
+          }
+        }
+
+        ref.current = instanceToUse;
       }
     }
   }
@@ -10453,7 +10484,7 @@ var ReactFiberCommitWork = function(
       if (typeof currentRef === "function") {
         currentRef(null);
       } else {
-        currentRef.value = null;
+        currentRef.current = null;
       }
     }
   }
diff --git a/Libraries/Renderer/ReactFabric-prod.js b/Libraries/Renderer/ReactFabric-prod.js
index 950e09890f82..637481f04146 100644
--- a/Libraries/Renderer/ReactFabric-prod.js
+++ b/Libraries/Renderer/ReactFabric-prod.js
@@ -945,6 +945,9 @@ var hasSymbol = "function" === typeof Symbol && Symbol["for"],
   REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
   REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
   REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol
+    ? Symbol["for"]("react.forward_ref")
+    : 60112,
   MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
 function getIteratorFn(maybeIterable) {
   if (null === maybeIterable || "undefined" === typeof maybeIterable)
@@ -1843,6 +1846,9 @@ function createFiberFromElement(element, mode, expirationTime) {
             case REACT_CONTEXT_TYPE:
               fiberTag = 12;
               break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = 14;
+              break;
             default:
               if ("number" === typeof type.tag)
                 return (
@@ -2312,22 +2318,14 @@ function ReactFiberClassComponent(
         renderExpirationTime,
         newUnmaskedContext
       ))
-        ? (("function" !== typeof instance.UNSAFE_componentWillUpdate &&
-            "function" !== typeof instance.componentWillUpdate) ||
+        ? (("function" !== typeof instance.UNSAFE_componentWillMount &&
+            "function" !== typeof instance.componentWillMount) ||
             "function" === typeof ctor.getDerivedStateFromProps ||
-            ("function" === typeof instance.componentWillUpdate &&
-              instance.componentWillUpdate(
-                newProps,
-                renderExpirationTime,
-                newUnmaskedContext
-              ),
-            "function" === typeof instance.UNSAFE_componentWillUpdate &&
-              instance.UNSAFE_componentWillUpdate(
-                newProps,
-                renderExpirationTime,
-                newUnmaskedContext
-              )),
-          "function" === typeof instance.componentDidUpdate &&
+            ("function" === typeof instance.componentWillMount &&
+              instance.componentWillMount(),
+            "function" === typeof instance.UNSAFE_componentWillMount &&
+              instance.UNSAFE_componentWillMount()),
+          "function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4))
         : ("function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
@@ -3669,6 +3667,17 @@ function ReactFiberBeginWork(
                 )),
             current
           );
+        case 14:
+          return (
+            (renderExpirationTime = workInProgress.type.render),
+            (renderExpirationTime = renderExpirationTime(
+              workInProgress.pendingProps,
+              workInProgress.ref
+            )),
+            reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            workInProgress.child
+          );
         case 10:
           return (
             (renderExpirationTime = workInProgress.pendingProps),
@@ -4058,6 +4067,8 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
           return (workInProgress.tag = 7), null;
         case 9:
           return null;
+        case 14:
+          return null;
         case 10:
           return null;
         case 11:
@@ -4191,7 +4202,7 @@ function ReactFiberCommitWork(
         } catch (refError) {
           captureError(current, refError);
         }
-      else ref.value = null;
+      else ref.current = null;
   }
   function commitLifeCycles(finishedRoot, current, finishedWork) {
     switch (finishedWork.tag) {
@@ -4305,13 +4316,15 @@ function ReactFiberCommitWork(
       }
       "function" === typeof ref
         ? ref(finishedWork)
-        : (ref.value = finishedWork);
+        : (ref.current = finishedWork);
     }
   }
   function commitDetachRef(current) {
     current = current.ref;
     null !== current &&
-      ("function" === typeof current ? current(null) : (current.value = null));
+      ("function" === typeof current
+        ? current(null)
+        : (current.current = null));
   }
   function commitNestedUnmounts(root) {
     for (var node = root; ; ) {
@@ -5891,7 +5904,7 @@ ReactFabricRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
-  version: "16.3.0-alpha.1",
+  version: "16.3.0-alpha.2",
   rendererPackageName: "react-native-renderer"
 });
 var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
diff --git a/Libraries/Renderer/ReactNativeRenderer-dev.js b/Libraries/Renderer/ReactNativeRenderer-dev.js
index 400472d29a38..d54c9f31c6cd 100644
--- a/Libraries/Renderer/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/ReactNativeRenderer-dev.js
@@ -965,6 +965,7 @@ var Fragment = 10;
 var Mode = 11;
 var ContextConsumer = 12;
 var ContextProvider = 13;
+var ForwardRef = 14;
 
 function getParent(inst) {
   do {
@@ -2802,6 +2803,9 @@ var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
 var REACT_ASYNC_MODE_TYPE = hasSymbol
   ? Symbol["for"]("react.async_mode")
   : 0xeacf;
+var REACT_FORWARD_REF_TYPE = hasSymbol
+  ? Symbol["for"]("react.forward_ref")
+  : 0xead0;
 
 var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
 var FAUX_ITERATOR_SYMBOL = "@@iterator";
@@ -2983,7 +2987,7 @@ var TouchHistoryMath = {
 
 // TODO: this is special because it gets imported during build.
 
-var ReactVersion = "16.3.0-alpha.1";
+var ReactVersion = "16.3.0-alpha.2";
 
 function _classCallCheck(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
@@ -5500,6 +5504,9 @@ function createFiberFromElement(element, mode, expirationTime) {
               // This is a consumer
               fiberTag = ContextConsumer;
               break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = ForwardRef;
+              break;
             default:
               if (typeof type.tag === "number") {
                 // Currently assumed to be a continuation and therefore is a
@@ -7092,20 +7099,20 @@ var ReactFiberClassComponent = function(
       // In order to support react-lifecycles-compat polyfilled components,
       // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
       if (
-        (typeof instance.UNSAFE_componentWillUpdate === "function" ||
-          typeof instance.componentWillUpdate === "function") &&
+        (typeof instance.UNSAFE_componentWillMount === "function" ||
+          typeof instance.componentWillMount === "function") &&
         typeof ctor.getDerivedStateFromProps !== "function"
       ) {
-        startPhaseTimer(workInProgress, "componentWillUpdate");
-        if (typeof instance.componentWillUpdate === "function") {
-          instance.componentWillUpdate(newProps, newState, newContext);
+        startPhaseTimer(workInProgress, "componentWillMount");
+        if (typeof instance.componentWillMount === "function") {
+          instance.componentWillMount();
         }
-        if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
+        if (typeof instance.UNSAFE_componentWillMount === "function") {
+          instance.UNSAFE_componentWillMount();
         }
         stopPhaseTimer();
       }
-      if (typeof instance.componentDidUpdate === "function") {
+      if (typeof instance.componentDidMount === "function") {
         workInProgress.effectTag |= Update;
       }
     } else {
@@ -8725,6 +8732,14 @@ var ReactFiberBeginWork = function(
     }
   }
 
+  function updateForwardRef(current, workInProgress) {
+    var render = workInProgress.type.render;
+    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+    return workInProgress.child;
+  }
+
   function updateFragment(current, workInProgress) {
     var nextChildren = workInProgress.pendingProps;
     if (hasContextChanged()) {
@@ -9678,6 +9693,8 @@ var ReactFiberBeginWork = function(
           workInProgress,
           renderExpirationTime
         );
+      case ForwardRef:
+        return updateForwardRef(current, workInProgress);
       case Fragment:
         return updateFragment(current, workInProgress);
       case Mode:
@@ -10230,6 +10247,8 @@ var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
       case ReturnComponent:
         // Does nothing.
         return null;
+      case ForwardRef:
+        return null;
       case Fragment:
         return null;
       case Mode:
@@ -10569,7 +10588,7 @@ var ReactFiberCommitWork = function(
           }
         }
       } else {
-        ref.value = null;
+        ref.current = null;
       }
     }
   }
@@ -10734,7 +10753,19 @@ var ReactFiberCommitWork = function(
       if (typeof ref === "function") {
         ref(instanceToUse);
       } else {
-        ref.value = instanceToUse;
+        {
+          if (!ref.hasOwnProperty("current")) {
+            warning(
+              false,
+              "Unexpected ref object provided for %s. " +
+                "Use either a ref-setter function or Reacte.createRef().%s",
+              getComponentName(finishedWork),
+              getStackAddendumByWorkInProgressFiber(finishedWork)
+            );
+          }
+        }
+
+        ref.current = instanceToUse;
       }
     }
   }
@@ -10745,7 +10776,7 @@ var ReactFiberCommitWork = function(
       if (typeof currentRef === "function") {
         currentRef(null);
       } else {
-        currentRef.value = null;
+        currentRef.current = null;
       }
     }
   }
diff --git a/Libraries/Renderer/ReactNativeRenderer-prod.js b/Libraries/Renderer/ReactNativeRenderer-prod.js
index ca27b720b33d..258608b7f31a 100644
--- a/Libraries/Renderer/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/ReactNativeRenderer-prod.js
@@ -1174,6 +1174,9 @@ var hasSymbol = "function" === typeof Symbol && Symbol["for"],
   REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
   REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
   REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol
+    ? Symbol["for"]("react.forward_ref")
+    : 60112,
   MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
 function getIteratorFn(maybeIterable) {
   if (null === maybeIterable || "undefined" === typeof maybeIterable)
@@ -2037,6 +2040,9 @@ function createFiberFromElement(element, mode, expirationTime) {
             case REACT_CONTEXT_TYPE:
               fiberTag = 12;
               break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = 14;
+              break;
             default:
               if ("number" === typeof type.tag)
                 return (
@@ -2551,22 +2557,14 @@ function ReactFiberClassComponent(
         renderExpirationTime,
         newUnmaskedContext
       ))
-        ? (("function" !== typeof instance.UNSAFE_componentWillUpdate &&
-            "function" !== typeof instance.componentWillUpdate) ||
+        ? (("function" !== typeof instance.UNSAFE_componentWillMount &&
+            "function" !== typeof instance.componentWillMount) ||
             "function" === typeof ctor.getDerivedStateFromProps ||
-            ("function" === typeof instance.componentWillUpdate &&
-              instance.componentWillUpdate(
-                newProps,
-                renderExpirationTime,
-                newUnmaskedContext
-              ),
-            "function" === typeof instance.UNSAFE_componentWillUpdate &&
-              instance.UNSAFE_componentWillUpdate(
-                newProps,
-                renderExpirationTime,
-                newUnmaskedContext
-              )),
-          "function" === typeof instance.componentDidUpdate &&
+            ("function" === typeof instance.componentWillMount &&
+              instance.componentWillMount(),
+            "function" === typeof instance.UNSAFE_componentWillMount &&
+              instance.UNSAFE_componentWillMount()),
+          "function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4))
         : ("function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
@@ -3932,6 +3930,17 @@ function ReactFiberBeginWork(
                 )),
             current
           );
+        case 14:
+          return (
+            (renderExpirationTime = workInProgress.type.render),
+            (renderExpirationTime = renderExpirationTime(
+              workInProgress.pendingProps,
+              workInProgress.ref
+            )),
+            reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            workInProgress.child
+          );
         case 10:
           return (
             (renderExpirationTime = workInProgress.pendingProps),
@@ -4263,6 +4272,8 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
           return (workInProgress.tag = 7), null;
         case 9:
           return null;
+        case 14:
+          return null;
         case 10:
           return null;
         case 11:
@@ -4415,7 +4426,7 @@ function ReactFiberCommitWork(
         } catch (refError) {
           captureError(current, refError);
         }
-      else ref.value = null;
+      else ref.current = null;
   }
   function commitUnmount(current) {
     "function" === typeof onCommitUnmount && onCommitUnmount(current);
@@ -4795,7 +4806,7 @@ function ReactFiberCommitWork(
         }
         "function" === typeof ref
           ? ref(finishedWork)
-          : (ref.value = finishedWork);
+          : (ref.current = finishedWork);
       }
     },
     commitDetachRef: function(current) {
@@ -4803,7 +4814,7 @@ function ReactFiberCommitWork(
       null !== current &&
         ("function" === typeof current
           ? current(null)
-          : (current.value = null));
+          : (current.current = null));
     }
   };
 }
@@ -6352,7 +6363,7 @@ NativeRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
-  version: "16.3.0-alpha.1",
+  version: "16.3.0-alpha.2",
   rendererPackageName: "react-native-renderer"
 });
 var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
diff --git a/Libraries/Renderer/shims/ReactTypes.js b/Libraries/Renderer/shims/ReactTypes.js
index bede9f00e300..f6a56ccc96ed 100644
--- a/Libraries/Renderer/shims/ReactTypes.js
+++ b/Libraries/Renderer/shims/ReactTypes.js
@@ -101,5 +101,5 @@ export type ReactPortal = {
 };
 
 export type RefObject = {|
-  value: any,
+  current: any,
 |};
diff --git a/package.json b/package.json
index 5c554719e5f0..bc2e7cd11a03 100644
--- a/package.json
+++ b/package.json
@@ -142,7 +142,7 @@
     "react-native": "local-cli/wrong-react-native.js"
   },
   "peerDependencies": {
-    "react": "^16.3.0-alpha.0"
+    "react": "^16.3.0-alpha.2"
   },
   "dependencies": {
     "absolute-path": "^0.0.0",
@@ -219,8 +219,8 @@
     "jest": "22.4.2",
     "jest-junit": "3.6.0",
     "prettier": "1.9.1",
-    "react": "^16.3.0-alpha.1",
-    "react-test-renderer": "^16.3.0-alpha.1",
+    "react": "^16.3.0-alpha.2",
+    "react-test-renderer": "^16.3.0-alpha.2",
     "shelljs": "^0.7.8",
     "sinon": "^2.2.0"
   }

From 6b1dc7174082a78a283c922ac975642bb2862fba Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 15 Mar 2018 06:46:12 -0700
Subject: [PATCH 0031/1109] Refactor resolvePlugins out to prepare for babel 7

Reviewed By: BYK

Differential Revision: D7287074

fbshipit-source-id: ec703f7292b63b679dbad055a6e43ac907729bfe
---
 babel-preset/configs/main.js | 64 ++++++++++++++++--------------------
 1 file changed, 29 insertions(+), 35 deletions(-)

diff --git a/babel-preset/configs/main.js b/babel-preset/configs/main.js
index dca6ddebd8e2..96405f002f95 100644
--- a/babel-preset/configs/main.js
+++ b/babel-preset/configs/main.js
@@ -4,47 +4,41 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  */
-'use strict';
 
-const resolvePlugins = require('../lib/resolvePlugins');
-const resolvePlugin = resolvePlugins.resolvePlugin;
+'use strict';
 
-const defaultPlugins = resolvePlugins([
-  'syntax-class-properties',
-  'syntax-trailing-function-commas',
-  'transform-class-properties',
-  'transform-es2015-block-scoping',
-  'transform-es2015-computed-properties',
-  'transform-es2015-destructuring',
-  'transform-es2015-function-name',
-  'transform-es2015-literals',
-  'transform-es2015-parameters',
-  'transform-es2015-shorthand-properties',
-  'transform-flow-strip-types',
-  'transform-react-jsx',
-  'transform-regenerator',
+const defaultPlugins = [
+  [require('babel-plugin-syntax-class-properties')],
+  [require('babel-plugin-syntax-trailing-function-commas')],
+  [require('babel-plugin-transform-class-properties')],
+  [require('babel-plugin-transform-es2015-block-scoping')],
+  [require('babel-plugin-transform-es2015-computed-properties')],
+  [require('babel-plugin-transform-es2015-destructuring')],
+  [require('babel-plugin-transform-es2015-function-name')],
+  [require('babel-plugin-transform-es2015-literals')],
+  [require('babel-plugin-transform-es2015-parameters')],
+  [require('babel-plugin-transform-es2015-shorthand-properties')],
+  [require('babel-plugin-transform-flow-strip-types')],
+  [require('babel-plugin-transform-react-jsx')],
+  [require('babel-plugin-transform-regenerator')],
   [
-    'transform-es2015-modules-commonjs',
+    require('babel-plugin-transform-es2015-modules-commonjs'),
     {strict: false, allowTopLevelThis: true},
   ],
-]);
+];
 
-const checkES2015Constants = resolvePlugin('check-es2015-constants');
-const es2015ArrowFunctions = resolvePlugin('transform-es2015-arrow-functions');
-const es2015Classes = resolvePlugin('transform-es2015-classes');
-const es2015ForOf = resolvePlugin(['transform-es2015-for-of', {loose: true}]);
-const es2015Spread = resolvePlugin('transform-es2015-spread');
-const es2015TemplateLiterals = resolvePlugin(
-  'transform-es2015-template-literals'
-);
-const asyncFunctions = resolvePlugin('syntax-async-functions');
-const exponentiationOperator = resolvePlugin(
-  'transform-exponentiation-operator'
-);
-const objectAssign = resolvePlugin('transform-object-assign');
-const objectRestSpread = resolvePlugin('transform-object-rest-spread');
-const reactDisplayName = resolvePlugin('transform-react-display-name');
-const reactJsxSource = resolvePlugin('transform-react-jsx-source');
+const checkES2015Constants = [require('babel-plugin-check-es2015-constants')];
+const es2015ArrowFunctions = [require('babel-plugin-transform-es2015-arrow-functions')];
+const es2015Classes = [require('babel-plugin-transform-es2015-classes')];
+const es2015ForOf = [require('babel-plugin-transform-es2015-for-of'), {loose: true}];
+const es2015Spread = [require('babel-plugin-transform-es2015-spread')];
+const es2015TemplateLiterals = [require('babel-plugin-transform-es2015-template-literals')];
+const asyncFunctions = [require('babel-plugin-syntax-async-functions')];
+const exponentiationOperator = [require('babel-plugin-transform-exponentiation-operator')];
+const objectAssign = [require('babel-plugin-transform-object-assign')];
+const objectRestSpread = [require('babel-plugin-transform-object-rest-spread')];
+const reactDisplayName = [require('babel-plugin-transform-react-display-name')];
+const reactJsxSource = [require('babel-plugin-transform-react-jsx-source')];
 const symbolMember = [require('../transforms/transform-symbol-member')];
 
 const getPreset = (src, options) => {

From 040642dba3a64c7ab650e4968feeca03a0c01639 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Thu, 15 Mar 2018 07:13:02 -0700
Subject: [PATCH 0032/1109] Fix setter and getter of margin, position, border
 and padding

Reviewed By: emilsjolander

Differential Revision: D7274115

fbshipit-source-id: 942a91e6562ef789ae79102a828f397889468fa7
---
 ReactCommon/yoga/yoga/YGNodePrint.cpp |  5 +++-
 ReactCommon/yoga/yoga/Yoga.cpp        | 34 +++++++--------------------
 2 files changed, 13 insertions(+), 26 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNodePrint.cpp b/ReactCommon/yoga/yoga/YGNodePrint.cpp
index 8585b725171f..ab0666d07eb5 100644
--- a/ReactCommon/yoga/yoga/YGNodePrint.cpp
+++ b/ReactCommon/yoga/yoga/YGNodePrint.cpp
@@ -72,7 +72,10 @@ appendNumberIfNotAuto(string* base, const string& key, const YGValue number) {
 
 static void
 appendNumberIfNotZero(string* base, const string& str, const YGValue number) {
-  if (!YGFloatsEqual(number.value, 0)) {
+
+  if (number.unit == YGUnitAuto) {
+    base->append(str + ": auto; ");
+  } else if (!YGFloatsEqual(number.value, 0)) {
     appendNumberIfNotUndefined(base, str, number);
   }
 }
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index b5e1e4c044f5..5ccb6b1eff3d 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -637,7 +637,7 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
   void YGNodeStyleSet##name##Auto(const YGNodeRef node, const YGEdge edge) { \
     if (node->getStyle().instanceName[edge].unit != YGUnitAuto) {            \
       YGStyle style = node->getStyle();                                      \
-      style.instanceName[edge].value = YGUndefined;                          \
+      style.instanceName[edge].value = 0;                                    \
       style.instanceName[edge].unit = YGUnitAuto;                            \
       node->setStyle(style);                                                 \
       node->markDirtyAndPropogate();                                         \
@@ -649,7 +649,7 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
   void YGNodeStyleSet##name(                                                   \
       const YGNodeRef node, const YGEdge edge, const float paramName) {        \
     YGValue value = {                                                          \
-        .value = paramName,                                                    \
+        .value = YGFloatSanitize(paramName),                                   \
         .unit = YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint, \
     };                                                                         \
     if ((node->getStyle().instanceName[edge].value != value.value &&           \
@@ -665,7 +665,7 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
   void YGNodeStyleSet##name##Percent(                                          \
       const YGNodeRef node, const YGEdge edge, const float paramName) {        \
     YGValue value = {                                                          \
-        .value = paramName,                                                    \
+        .value = YGFloatSanitize(paramName),                                   \
         .unit =                                                                \
             YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPercent,   \
     };                                                                         \
@@ -681,28 +681,11 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
                                                                                \
   WIN_STRUCT(type)                                                             \
   YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge) {              \
-    return WIN_STRUCT_REF(node->getStyle().instanceName[edge]);                \
-  }
-
-#define YG_NODE_STYLE_EDGE_PROPERTY_IMPL(type, name, paramName, instanceName)  \
-  void YGNodeStyleSet##name(                                                   \
-      const YGNodeRef node, const YGEdge edge, const float paramName) {        \
-    YGValue value = {                                                          \
-        .value = paramName,                                                    \
-        .unit = YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint, \
-    };                                                                         \
-    if ((node->getStyle().instanceName[edge].value != value.value &&           \
-         value.unit != YGUnitUndefined) ||                                     \
-        node->getStyle().instanceName[edge].unit != value.unit) {              \
-      YGStyle style = node->getStyle();                                        \
-      style.instanceName[edge] = value;                                        \
-      node->setStyle(style);                                                   \
-      node->markDirtyAndPropogate();                                           \
+    YGValue value = node->getStyle().instanceName[edge];                       \
+    if (value.unit == YGUnitUndefined || value.unit == YGUnitAuto) {           \
+      value.value = YGUndefined;                                               \
     }                                                                          \
-  }                                                                            \
-                                                                               \
-  float YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge) {        \
-    return node->getStyle().instanceName[edge].value;                          \
+    return WIN_STRUCT_REF(value);                                              \
   }
 
 #define YG_NODE_LAYOUT_PROPERTY_IMPL(type, name, instanceName) \
@@ -873,7 +856,8 @@ void YGNodeStyleSetBorder(
 }
 
 float YGNodeStyleGetBorder(const YGNodeRef node, const YGEdge edge) {
-  if (node->getStyle().border[edge].unit == YGUnitUndefined) {
+  if (node->getStyle().border[edge].unit == YGUnitUndefined ||
+      node->getStyle().border[edge].unit == YGUnitAuto) {
     // TODO(T26792433): Rather than returning YGUndefined, change the api to
     // return YGFloatOptional.
     return YGUndefined;

From da2d410122fd2072497f55a9934325f38cfcbba7 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Thu, 15 Mar 2018 07:13:03 -0700
Subject: [PATCH 0033/1109] Fix getters and setters if min and max Dimension

Reviewed By: emilsjolander

Differential Revision: D7274807

fbshipit-source-id: 7c1a4c19e8d0552b089a410c3330392cb26a6a47
---
 ReactCommon/yoga/yoga/Yoga.cpp | 10 +++++++---
 1 file changed, 7 insertions(+), 3 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 5ccb6b1eff3d..e38ff26870c0 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -538,7 +538,7 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
     type, name, paramName, instanceName)                                       \
   void YGNodeStyleSet##name(const YGNodeRef node, const type paramName) {      \
     YGValue value = {                                                          \
-        .value = paramName,                                                    \
+        .value = YGFloatSanitize(paramName),                                   \
         .unit = YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint, \
     };                                                                         \
     if ((node->getStyle().instanceName.value != value.value &&                 \
@@ -554,7 +554,7 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
   void YGNodeStyleSet##name##Percent(                                          \
       const YGNodeRef node, const type paramName) {                            \
     YGValue value = {                                                          \
-        .value = paramName,                                                    \
+        .value = YGFloatSanitize(paramName),                                   \
         .unit =                                                                \
             YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPercent,   \
     };                                                                         \
@@ -621,7 +621,11 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
       float, name, paramName, instanceName)                                   \
                                                                               \
   type YGNodeStyleGet##name(const YGNodeRef node) {                           \
-    return node->getStyle().instanceName;                                     \
+    YGValue value = node->getStyle().instanceName;                            \
+    if (value.unit == YGUndefined || value.unit == YGUnitAuto) {              \
+      value.value = YGUndefined;                                              \
+    }                                                                         \
+    return value;                                                             \
   }
 
 #define YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(      \

From c989ea87281f9ee667090b119469754035dfcd7e Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Thu, 15 Mar 2018 09:21:04 -0700
Subject: [PATCH 0034/1109] Extract NativeExtensionsProvider definition

Reviewed By: danzimm

Differential Revision: D6964355

fbshipit-source-id: e20dfa99bd9d8784a5f31a313302104d6dc33652
---
 ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp | 2 +-
 ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h   | 3 ++-
 ReactCommon/cxxreact/JSCExecutor.cpp                      | 2 +-
 ReactCommon/cxxreact/JSCExecutor.h                        | 8 ++++----
 ReactCommon/cxxreact/JSExecutor.h                         | 2 ++
 5 files changed, 10 insertions(+), 7 deletions(-)

diff --git a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
index ed551a61a2b5..73d774e7d5d8 100644
--- a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
@@ -90,7 +90,7 @@ void injectJSCExecutorAndroidPlatform() {
 }
 
 std::unique_ptr<JSExecutorFactory> makeAndroidJSCExecutorFactory(
-    const folly::dynamic& jscConfig, std::function<folly::dynamic(const std::string&)> nativeExtensionsProvider) {
+    const folly::dynamic& jscConfig, NativeExtensionsProvider nativeExtensionsProvider) {
   detail::injectJSCExecutorAndroidPlatform();
   return folly::make_unique<JSCExecutorFactory>(std::move(jscConfig), std::move(nativeExtensionsProvider));
 }
diff --git a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
index e1e782145c91..5de2f99eefc7 100644
--- a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
+++ b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
@@ -3,6 +3,7 @@
 #pragma once
 
 #include <memory>
+#include <cxxreact/JSExecutor.h>
 
 namespace folly {
 
@@ -23,7 +24,7 @@ void injectJSCExecutorAndroidPlatform();
 }
 
 std::unique_ptr<JSExecutorFactory> makeAndroidJSCExecutorFactory(
-    const folly::dynamic& jscConfig, std::function<folly::dynamic(const std::string&)> nativeExtensionsProvider);
+    const folly::dynamic& jscConfig, NativeExtensionsProvider nativeExtensionsProvider);
 
 }
 }
diff --git a/ReactCommon/cxxreact/JSCExecutor.cpp b/ReactCommon/cxxreact/JSCExecutor.cpp
index 81e71eddbaa5..ddae9fdda4b6 100644
--- a/ReactCommon/cxxreact/JSCExecutor.cpp
+++ b/ReactCommon/cxxreact/JSCExecutor.cpp
@@ -121,7 +121,7 @@ namespace facebook {
     JSCExecutor::JSCExecutor(std::shared_ptr<ExecutorDelegate> delegate,
                              std::shared_ptr<MessageQueueThread> messageQueueThread,
                              const folly::dynamic& jscConfig,
-                             std::function<folly::dynamic(const std::string &)> nativeExtensionsProvider) throw(JSException) :
+                             NativeExtensionsProvider nativeExtensionsProvider) throw(JSException) :
     m_delegate(delegate),
     m_messageQueueThread(messageQueueThread),
     m_nativeModules(delegate ? delegate->getModuleRegistry() : nullptr),
diff --git a/ReactCommon/cxxreact/JSCExecutor.h b/ReactCommon/cxxreact/JSCExecutor.h
index 5acc967722e5..44b13aa94b2a 100644
--- a/ReactCommon/cxxreact/JSCExecutor.h
+++ b/ReactCommon/cxxreact/JSCExecutor.h
@@ -27,7 +27,7 @@ class RAMBundleRegistry;
 
 class RN_EXPORT JSCExecutorFactory : public JSExecutorFactory {
 public:
-  JSCExecutorFactory(const folly::dynamic& jscConfig, std::function<folly::dynamic(const std::string &)> provider) :
+  JSCExecutorFactory(const folly::dynamic& jscConfig, NativeExtensionsProvider provider) :
     m_jscConfig(jscConfig), m_nativeExtensionsProvider(provider) {}
   std::unique_ptr<JSExecutor> createJSExecutor(
     std::shared_ptr<ExecutorDelegate> delegate,
@@ -35,7 +35,7 @@ class RN_EXPORT JSCExecutorFactory : public JSExecutorFactory {
 private:
   std::string m_cacheDir;
   folly::dynamic m_jscConfig;
-  std::function<folly::dynamic(const std::string &)> m_nativeExtensionsProvider;
+  NativeExtensionsProvider m_nativeExtensionsProvider;
 };
 
 template<typename T>
@@ -60,7 +60,7 @@ class RN_EXPORT JSCExecutor : public JSExecutor, public PrivateDataBase {
   explicit JSCExecutor(std::shared_ptr<ExecutorDelegate> delegate,
                        std::shared_ptr<MessageQueueThread> messageQueueThread,
                        const folly::dynamic& jscConfig,
-                       std::function<folly::dynamic(const std::string &)> nativeExtensionsProvider) throw(JSException);
+                       NativeExtensionsProvider nativeExtensionsProvider) throw(JSException);
   ~JSCExecutor() override;
 
   virtual void loadApplicationScript(
@@ -106,7 +106,7 @@ class RN_EXPORT JSCExecutor : public JSExecutor, public PrivateDataBase {
   JSCNativeModules m_nativeModules;
   folly::dynamic m_jscConfig;
   std::once_flag m_bindFlag;
-  std::function<folly::dynamic(const std::string &)> m_nativeExtensionsProvider;
+  NativeExtensionsProvider m_nativeExtensionsProvider;
 
   folly::Optional<Object> m_invokeCallbackAndReturnFlushedQueueJS;
   folly::Optional<Object> m_callFunctionReturnFlushedQueueJS;
diff --git a/ReactCommon/cxxreact/JSExecutor.h b/ReactCommon/cxxreact/JSExecutor.h
index 91bc070c4937..85b4bfcb0364 100644
--- a/ReactCommon/cxxreact/JSExecutor.h
+++ b/ReactCommon/cxxreact/JSExecutor.h
@@ -32,6 +32,8 @@ class ExecutorDelegate {
     JSExecutor& executor, unsigned int moduleId, unsigned int methodId, folly::dynamic&& args) = 0;
 };
 
+using NativeExtensionsProvider = std::function<folly::dynamic(const std::string&)>;
+
 class JSExecutorFactory {
 public:
   virtual std::unique_ptr<JSExecutor> createJSExecutor(

From 8e85bf84e8139caebc79d2034313ff0f4c936bea Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Thu, 15 Mar 2018 09:21:08 -0700
Subject: [PATCH 0035/1109] Gatekeeper for Native Extensions

Reviewed By: danzimm, johnislarry

Differential Revision: D6965463

fbshipit-source-id: 28bcfbff980abfda3c63d7016ccf05beb1d178eb
---
 ReactCommon/cxxreact/JSCExecutor.cpp | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/cxxreact/JSCExecutor.cpp b/ReactCommon/cxxreact/JSCExecutor.cpp
index ddae9fdda4b6..a7d8c72cbf70 100644
--- a/ReactCommon/cxxreact/JSCExecutor.cpp
+++ b/ReactCommon/cxxreact/JSCExecutor.cpp
@@ -134,8 +134,10 @@ namespace facebook {
         installGlobalProxy(m_context, "nativeModuleProxy",
                            exceptionWrapMethod<&JSCExecutor::getNativeModule>());
       }
-      installGlobalProxy(m_context, "nativeExtensions",
-                         exceptionWrapMethod<&JSCExecutor::getNativeExtension>());
+      if (nativeExtensionsProvider) {
+        installGlobalProxy(m_context, "nativeExtensions",
+                           exceptionWrapMethod<&JSCExecutor::getNativeExtension>());
+      }
     }
 
     JSCExecutor::~JSCExecutor() {

From 139d554c48560c3273c10a8881543c2f44ec64d0 Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Thu, 15 Mar 2018 09:58:16 -0700
Subject: [PATCH 0036/1109] Replace js Dimensions with shadow view in
 InputAccessoryViewExample

Reviewed By: mmmulani

Differential Revision: D7196168

fbshipit-source-id: 031ed5ab24d1075f775ec71e5b78d32e03fe8f6f
---
 .../Text/TextInput/RCTInputAccessoryShadowView.h  |  7 +++++++
 .../Text/TextInput/RCTInputAccessoryShadowView.m  | 15 +++++++++++++++
 .../Text/TextInput/RCTInputAccessoryViewManager.m |  6 ++++++
 RNTester/js/InputAccessoryViewExample.js          |  4 +---
 4 files changed, 29 insertions(+), 3 deletions(-)
 create mode 100644 Libraries/Text/TextInput/RCTInputAccessoryShadowView.h
 create mode 100644 Libraries/Text/TextInput/RCTInputAccessoryShadowView.m

diff --git a/Libraries/Text/TextInput/RCTInputAccessoryShadowView.h b/Libraries/Text/TextInput/RCTInputAccessoryShadowView.h
new file mode 100644
index 000000000000..4731cea4d8e1
--- /dev/null
+++ b/Libraries/Text/TextInput/RCTInputAccessoryShadowView.h
@@ -0,0 +1,7 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#import <React/RCTShadowView.h>
+
+@interface RCTInputAccessoryShadowView : RCTShadowView
+
+@end
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryShadowView.m b/Libraries/Text/TextInput/RCTInputAccessoryShadowView.m
new file mode 100644
index 000000000000..b2664aaec8bd
--- /dev/null
+++ b/Libraries/Text/TextInput/RCTInputAccessoryShadowView.m
@@ -0,0 +1,15 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#import "RCTInputAccessoryShadowView.h"
+
+#import <React/RCTUtils.h>
+
+@implementation RCTInputAccessoryShadowView
+
+- (void)insertReactSubview:(RCTShadowView *)subview atIndex:(NSInteger)atIndex
+{
+  [super insertReactSubview:subview atIndex:atIndex];
+  subview.width = (YGValue) { RCTScreenSize().width, YGUnitPoint };
+}
+
+@end
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryViewManager.m b/Libraries/Text/TextInput/RCTInputAccessoryViewManager.m
index aeeff835e844..490aa841aa49 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryViewManager.m
+++ b/Libraries/Text/TextInput/RCTInputAccessoryViewManager.m
@@ -7,6 +7,7 @@
 
 #import "RCTInputAccessoryViewManager.h"
 
+#import "RCTInputAccessoryShadowView.h"
 #import "RCTInputAccessoryView.h"
 
 @implementation RCTInputAccessoryViewManager
@@ -23,6 +24,11 @@ - (UIView *)view
   return [[RCTInputAccessoryView alloc] initWithBridge:self.bridge];
 }
 
+- (RCTShadowView *)shadowView
+{
+  return [RCTInputAccessoryShadowView new];
+}
+
 RCT_REMAP_VIEW_PROPERTY(backgroundColor, inputAccessoryView.backgroundColor, UIColor)
 
 @end
diff --git a/RNTester/js/InputAccessoryViewExample.js b/RNTester/js/InputAccessoryViewExample.js
index 13b5885789b9..7ebcf5f0090a 100644
--- a/RNTester/js/InputAccessoryViewExample.js
+++ b/RNTester/js/InputAccessoryViewExample.js
@@ -13,7 +13,6 @@
 
 const Alert = require('Alert');
 const Button = require('Button');
-const Dimensions = require('Dimensions');
 const InputAccessoryView = require('InputAccessoryView');
 const React = require('React');
 const ScrollView = require('ScrollView');
@@ -36,9 +35,8 @@ class TextInputBar extends React.PureComponent<*, *> {
   state = {text: ''};
 
   render() {
-    const {width} = Dimensions.get('window');
     return (
-      <View style={[styles.textInputContainer, {width}]}>
+      <View style={styles.textInputContainer}>
         <TextInput
           style={styles.textInput}
           onChangeText={text => {

From ce92b8592b08e78e11d8e16f330c054528af1bf2 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Thu, 15 Mar 2018 12:29:00 -0700
Subject: [PATCH 0037/1109] Fixed a typo and added a test case

Reviewed By: emilsjolander

Differential Revision: D7289221

fbshipit-source-id: 48ee9ccfac4adee51d515a366b5a11790f7236fc
---
 ReactCommon/yoga/yoga/Yoga.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index e38ff26870c0..b21b23d2e183 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -778,7 +778,7 @@ void YGNodeStyleSetFlexShrink(const YGNodeRef node, const float flexShrink) {
   if (!YGFloatOptionalFloatEquals(node->getStyle().flexShrink, flexShrink)) {
     YGStyle style = node->getStyle();
     if (YGFloatIsUndefined(flexShrink)) {
-      style.flexGrow = {true, 0};
+      style.flexShrink = {true, 0};
     } else {
       style.flexShrink = {false, flexShrink};
     }

From 9102ff94e7b9527e2162357a5e1334f7fffe8bcd Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Thu, 15 Mar 2018 12:29:02 -0700
Subject: [PATCH 0038/1109] Moved YGFloatOptional from C struct to C++ struct

Reviewed By: emilsjolander

Differential Revision: D7288555

fbshipit-source-id: f61cc92c8fd0d48d2fc1f4d0e6fcef155f19ff8a
---
 React/React.xcodeproj/project.pbxproj     | 12 ++++++
 ReactCommon/yoga/yoga/Utils.cpp           |  2 +-
 ReactCommon/yoga/yoga/Utils.h             |  9 +++--
 ReactCommon/yoga/yoga/YGFloatOptional.cpp | 32 ++++++++++++++++
 ReactCommon/yoga/yoga/YGFloatOptional.h   | 26 +++++++++++++
 ReactCommon/yoga/yoga/YGNode.cpp          | 30 ++++++++-------
 ReactCommon/yoga/yoga/YGNodePrint.cpp     |  4 +-
 ReactCommon/yoga/yoga/YGStyle.cpp         | 32 ++++++++--------
 ReactCommon/yoga/yoga/YGStyle.h           |  1 +
 ReactCommon/yoga/yoga/Yoga.cpp            | 46 ++++++++++++-----------
 ReactCommon/yoga/yoga/Yoga.h              |  5 ---
 11 files changed, 135 insertions(+), 64 deletions(-)
 create mode 100644 ReactCommon/yoga/yoga/YGFloatOptional.cpp
 create mode 100644 ReactCommon/yoga/yoga/YGFloatOptional.h

diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index 1ec79122f44a..dbc8cef8aad0 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -978,6 +978,10 @@
 		53D1239F1FBF1EFB001B8A10 /* Yoga-internal.h in Headers */ = {isa = PBXBuildFile; fileRef = 53CBF1851FB4FE80002CBB31 /* Yoga-internal.h */; };
 		53D123A01FBF1EFF001B8A10 /* Yoga.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 53CBF1871FB4FE80002CBB31 /* Yoga.cpp */; };
 		53D123A11FBF1EFF001B8A10 /* Yoga.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 53CBF1871FB4FE80002CBB31 /* Yoga.cpp */; };
+		53DEF6EA205AE5A0006A3890 /* YGFloatOptional.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 53DEF6E6205AE59B006A3890 /* YGFloatOptional.cpp */; };
+		53DEF6EB205AE5A1006A3890 /* YGFloatOptional.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 53DEF6E6205AE59B006A3890 /* YGFloatOptional.cpp */; };
+		53DEF6EC205AE5A6006A3890 /* YGFloatOptional.h in Headers */ = {isa = PBXBuildFile; fileRef = 53DEF6E7205AE59C006A3890 /* YGFloatOptional.h */; };
+		53DEF6ED205AE5A7006A3890 /* YGFloatOptional.h in Headers */ = {isa = PBXBuildFile; fileRef = 53DEF6E7205AE59C006A3890 /* YGFloatOptional.h */; };
 		53EC85E21FDEC75F0051B2B5 /* YGNode.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 53EC85DF1FDEC75A0051B2B5 /* YGNode.cpp */; };
 		53EC85E31FDEC75F0051B2B5 /* YGNode.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 53EC85DF1FDEC75A0051B2B5 /* YGNode.cpp */; };
 		53EC85E41FDEC7630051B2B5 /* YGNode.h in Headers */ = {isa = PBXBuildFile; fileRef = 53EC85DE1FDEC75A0051B2B5 /* YGNode.h */; };
@@ -2169,6 +2173,8 @@
 		53CBF1861FB4FE80002CBB31 /* YGEnums.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = YGEnums.cpp; sourceTree = "<group>"; };
 		53CBF1871FB4FE80002CBB31 /* Yoga.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Yoga.cpp; sourceTree = "<group>"; };
 		53D123831FBF1D49001B8A10 /* libyoga.a */ = {isa = PBXFileReference; lastKnownFileType = archive.ar; name = libyoga.a; path = "../../../../../../../../../Library/Developer/Xcode/DerivedData/yoga-hdfifpwsinitsibujacpiefkjfdy/Build/Products/Debug/libyoga.a"; sourceTree = "<group>"; };
+		53DEF6E6205AE59B006A3890 /* YGFloatOptional.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = YGFloatOptional.cpp; sourceTree = "<group>"; };
+		53DEF6E7205AE59C006A3890 /* YGFloatOptional.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = YGFloatOptional.h; sourceTree = "<group>"; };
 		53EC85DE1FDEC75A0051B2B5 /* YGNode.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = YGNode.h; sourceTree = "<group>"; };
 		53EC85DF1FDEC75A0051B2B5 /* YGNode.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = YGNode.cpp; sourceTree = "<group>"; };
 		58114A121AAE854800E7D092 /* RCTPicker.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTPicker.h; sourceTree = "<group>"; };
@@ -2349,6 +2355,8 @@
 		130A77021DF767AF001F9587 /* yoga */ = {
 			isa = PBXGroup;
 			children = (
+				53DEF6E6205AE59B006A3890 /* YGFloatOptional.cpp */,
+				53DEF6E7205AE59C006A3890 /* YGFloatOptional.h */,
 				5343895E203905B6008E0CB3 /* YGLayout.cpp */,
 				5343895F203905B6008E0CB3 /* YGLayout.h */,
 				5352C5722038FF8D00A3B97E /* YGStyle.cpp */,
@@ -3299,6 +3307,7 @@
 				5376C5E71FC6DDC20083513D /* YGNodePrint.h in Headers */,
 				3DFE0D191DF8574D00459392 /* Yoga.h in Headers */,
 				53438965203905C0008E0CB3 /* YGLayout.h in Headers */,
+				53DEF6ED205AE5A7006A3890 /* YGFloatOptional.h in Headers */,
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};
@@ -3379,6 +3388,7 @@
 				5376C5E61FC6DDC10083513D /* YGNodePrint.h in Headers */,
 				133957891DF76D3500EC27BE /* YGMacros.h in Headers */,
 				53438964203905BF008E0CB3 /* YGLayout.h in Headers */,
+				53DEF6EC205AE5A6006A3890 /* YGFloatOptional.h in Headers */,
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};
@@ -4318,6 +4328,7 @@
 			isa = PBXSourcesBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
+				53DEF6EA205AE5A0006A3890 /* YGFloatOptional.cpp in Sources */,
 				53D123A01FBF1EFF001B8A10 /* Yoga.cpp in Sources */,
 				5352C5752038FF9500A3B97E /* YGStyle.cpp in Sources */,
 				53EC85E21FDEC75F0051B2B5 /* YGNode.cpp in Sources */,
@@ -4332,6 +4343,7 @@
 			isa = PBXSourcesBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
+				53DEF6EB205AE5A1006A3890 /* YGFloatOptional.cpp in Sources */,
 				53D123A11FBF1EFF001B8A10 /* Yoga.cpp in Sources */,
 				5352C5762038FF9700A3B97E /* YGStyle.cpp in Sources */,
 				53EC85E31FDEC75F0051B2B5 /* YGNode.cpp in Sources */,
diff --git a/ReactCommon/yoga/yoga/Utils.cpp b/ReactCommon/yoga/yoga/Utils.cpp
index 8c6e91cce6ee..aec7564fb66b 100644
--- a/ReactCommon/yoga/yoga/Utils.cpp
+++ b/ReactCommon/yoga/yoga/Utils.cpp
@@ -55,7 +55,7 @@ float YGFloatSanitize(const float& val) {
 }
 
 float YGUnwrapFloatOptional(const YGFloatOptional& op) {
-  return op.isUndefined ? YGUndefined : op.value;
+  return op.isUndefined() ? YGUndefined : op.getValue();
 }
 
 bool YGFloatOptionalFloatEquals(
diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index 311030e23f0c..7190fd7ff249 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -113,13 +113,14 @@ inline YGFloatOptional YGResolveValue(const YGValue value, const float parentSiz
   switch (value.unit) {
     case YGUnitUndefined:
     case YGUnitAuto:
-      return {true, 0};
+      return YGFloatOptional();
     case YGUnitPoint:
-      return {false, value.value};
+      return YGFloatOptional(value.value);
     case YGUnitPercent:
-      return {false, static_cast<float>(value.value * parentSize * 0.01)};
+      return YGFloatOptional(
+          static_cast<float>(value.value * parentSize * 0.01));
   }
-  return {true, 0};
+  return YGFloatOptional();
 }
 
 inline bool YGFlexDirectionIsColumn(const YGFlexDirection flexDirection) {
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.cpp b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
new file mode 100644
index 000000000000..af9a6fc42ad7
--- /dev/null
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
@@ -0,0 +1,32 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "YGFloatOptional.h"
+#include <cstdlib>
+#include <iostream>
+
+YGFloatOptional::YGFloatOptional(const float& value)
+    : value_(value), isUndefined_(false) {}
+YGFloatOptional::YGFloatOptional() : value_(0), isUndefined_(true) {}
+
+float YGFloatOptional::getValue() const {
+  if (isUndefined_) {
+    // Abort, accessing a value of an undefined float optional
+    std::cerr << "Tried to get value of an undefined YGFloatOptional\n";
+    std::exit(EXIT_FAILURE);
+  }
+  return value_;
+}
+
+void YGFloatOptional::setValue(const float& val) {
+  value_ = val;
+  isUndefined_ = false;
+}
+
+bool YGFloatOptional::isUndefined() const {
+  return isUndefined_;
+}
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.h b/ReactCommon/yoga/yoga/YGFloatOptional.h
new file mode 100644
index 000000000000..d82230be3ff7
--- /dev/null
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.h
@@ -0,0 +1,26 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+struct YGFloatOptional {
+ private:
+  float value_;
+  bool isUndefined_;
+
+ public:
+  YGFloatOptional(const float& value);
+  YGFloatOptional();
+
+  // Program will terminate if the value of an undefined is accessed. Please
+  // make sure to check if the optional is defined before calling this function.
+  // To check if float optional is defined, use `isUndefined()`.
+  float getValue() const;
+
+  // Sets the value of float optional, and thus isUndefined is assigned false.
+  void setValue(const float& val);
+
+  bool isUndefined() const;
+};
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index df61b14a8966..5a33c6e86e73 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -500,7 +500,7 @@ YGValue YGNode::resolveFlexBasisPtr() const {
   if (flexBasis.unit != YGUnitAuto && flexBasis.unit != YGUnitUndefined) {
     return flexBasis;
   }
-  if (!style_.flex.isUndefined && style_.flex.value > 0.0f) {
+  if (!style_.flex.isUndefined() && style_.flex.getValue() > 0.0f) {
     return config_->useWebDefaults ? YGValueAuto : YGValueZero;
   }
   return YGValueAuto;
@@ -592,11 +592,11 @@ float YGNode::resolveFlexGrow() {
   if (parent_ == nullptr) {
     return 0.0;
   }
-  if (!style_.flexGrow.isUndefined) {
-    return style_.flexGrow.value;
+  if (!style_.flexGrow.isUndefined()) {
+    return style_.flexGrow.getValue();
   }
-  if (!style_.flex.isUndefined && style_.flex.value > 0.0f) {
-    return style_.flex.value;
+  if (!style_.flex.isUndefined() && style_.flex.getValue() > 0.0f) {
+    return style_.flex.getValue();
   }
   return kDefaultFlexGrow;
 }
@@ -605,12 +605,12 @@ float YGNode::resolveFlexShrink() {
   if (parent_ == nullptr) {
     return 0.0;
   }
-  if (!style_.flexShrink.isUndefined) {
-    return style_.flexShrink.value;
+  if (!style_.flexShrink.isUndefined()) {
+    return style_.flexShrink.getValue();
   }
-  if (!config_->useWebDefaults && !style_.flex.isUndefined &&
-      style_.flex.value < 0.0f) {
-    return -style_.flex.value;
+  if (!config_->useWebDefaults && !style_.flex.isUndefined() &&
+      style_.flex.getValue() < 0.0f) {
+    return -style_.flex.getValue();
   }
   return config_->useWebDefaults ? kWebDefaultFlexShrink : kDefaultFlexShrink;
 }
@@ -653,8 +653,9 @@ float YGNode::getLeadingPadding(
     const float widthSize) {
   if (YGFlexDirectionIsRow(axis) &&
       style_.padding[YGEdgeStart].unit != YGUnitUndefined &&
-          !YGResolveValue(style_.padding[YGEdgeStart], widthSize).isUndefined &&
-      YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeStart], widthSize)) > 0.0f) {
+      !YGResolveValue(style_.padding[YGEdgeStart], widthSize).isUndefined() &&
+      YGUnwrapFloatOptional(
+          YGResolveValue(style_.padding[YGEdgeStart], widthSize)) > 0.0f) {
     return YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeStart], widthSize));
   }
 
@@ -669,8 +670,9 @@ float YGNode::getTrailingPadding(
     const float widthSize) {
   if (YGFlexDirectionIsRow(axis) &&
       style_.padding[YGEdgeEnd].unit != YGUnitUndefined &&
-      !YGResolveValue(style_.padding[YGEdgeEnd], widthSize).isUndefined &&
-      YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeEnd], widthSize)) >= 0.0f) {
+      !YGResolveValue(style_.padding[YGEdgeEnd], widthSize).isUndefined() &&
+      YGUnwrapFloatOptional(
+          YGResolveValue(style_.padding[YGEdgeEnd], widthSize)) >= 0.0f) {
     return YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeEnd], widthSize));
   }
 
diff --git a/ReactCommon/yoga/yoga/YGNodePrint.cpp b/ReactCommon/yoga/yoga/YGNodePrint.cpp
index ab0666d07eb5..ab3aa7c7b3be 100644
--- a/ReactCommon/yoga/yoga/YGNodePrint.cpp
+++ b/ReactCommon/yoga/yoga/YGNodePrint.cpp
@@ -43,8 +43,8 @@ static void appendFloatOptionalIfDefined(
     string* base,
     const string key,
     const YGFloatOptional num) {
-  if (!num.isUndefined) {
-    appendFormatedString(base, "%s: %g; ", key.c_str(), num.value);
+  if (!num.isUndefined()) {
+    appendFormatedString(base, "%s: %g; ", key.c_str(), num.getValue());
   }
 }
 
diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index 031443c8cbf5..437b682d6146 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -7,9 +7,6 @@
 
 #include "YGStyle.h"
 
-#define YGFloatOptionalUndefined \
-  { true, 0 }
-
 const YGValue kYGValueUndefined = {0, YGUnitUndefined};
 
 const YGValue kYGValueAuto = {YGUndefined, YGUnitAuto};
@@ -42,9 +39,9 @@ YGStyle::YGStyle()
       flexWrap(YGWrapNoWrap),
       overflow(YGOverflowVisible),
       display(YGDisplayFlex),
-      flex(YGFloatOptionalUndefined),
-      flexGrow(YGFloatOptionalUndefined),
-      flexShrink(YGFloatOptionalUndefined),
+      flex(YGFloatOptional()),
+      flexGrow(YGFloatOptional()),
+      flexShrink(YGFloatOptional()),
       flexBasis({0, YGUnitAuto}),
       margin(kYGDefaultEdgeValuesUnit),
       position(kYGDefaultEdgeValuesUnit),
@@ -73,24 +70,25 @@ bool YGStyle::operator==(const YGStyle& style) {
       YGValueArrayEqual(maxDimensions, style.maxDimensions);
 
   areNonFloatValuesEqual =
-      areNonFloatValuesEqual && flex.isUndefined == style.flex.isUndefined;
-  if (areNonFloatValuesEqual && !flex.isUndefined && !style.flex.isUndefined) {
+      areNonFloatValuesEqual && flex.isUndefined() == style.flex.isUndefined();
+  if (areNonFloatValuesEqual && !flex.isUndefined() &&
+      !style.flex.isUndefined()) {
     areNonFloatValuesEqual =
-        areNonFloatValuesEqual && flex.value == style.flex.value;
+        areNonFloatValuesEqual && flex.getValue() == style.flex.getValue();
   }
 
   areNonFloatValuesEqual = areNonFloatValuesEqual &&
-      flexGrow.isUndefined == style.flexGrow.isUndefined;
-  if (areNonFloatValuesEqual && !flexGrow.isUndefined) {
-    areNonFloatValuesEqual =
-        areNonFloatValuesEqual && flexGrow.value == style.flexGrow.value;
+      flexGrow.isUndefined() == style.flexGrow.isUndefined();
+  if (areNonFloatValuesEqual && !flexGrow.isUndefined()) {
+    areNonFloatValuesEqual = areNonFloatValuesEqual &&
+        flexGrow.getValue() == style.flexGrow.getValue();
   }
 
   areNonFloatValuesEqual = areNonFloatValuesEqual &&
-      flexShrink.isUndefined == style.flexShrink.isUndefined;
-  if (areNonFloatValuesEqual && !style.flexShrink.isUndefined) {
-    areNonFloatValuesEqual =
-        areNonFloatValuesEqual && flexShrink.value == style.flexShrink.value;
+      flexShrink.isUndefined() == style.flexShrink.isUndefined();
+  if (areNonFloatValuesEqual && !style.flexShrink.isUndefined()) {
+    areNonFloatValuesEqual = areNonFloatValuesEqual &&
+        flexShrink.getValue() == style.flexShrink.getValue();
   }
 
   if (!(YGFloatIsUndefined(aspectRatio) &&
diff --git a/ReactCommon/yoga/yoga/YGStyle.h b/ReactCommon/yoga/yoga/YGStyle.h
index 3abc4c084d4d..7a7f519a5f9b 100644
--- a/ReactCommon/yoga/yoga/YGStyle.h
+++ b/ReactCommon/yoga/yoga/YGStyle.h
@@ -6,6 +6,7 @@
  */
 
 #pragma once
+#include "YGFloatOptional.h"
 #include "Yoga-internal.h"
 #include "Yoga.h"
 
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index b21b23d2e183..570f7ab964e1 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -13,7 +13,6 @@
 #include "YGNode.h"
 #include "YGNodePrint.h"
 #include "Yoga-internal.h"
-
 #ifdef _MSC_VER
 #include <float.h>
 
@@ -511,16 +510,16 @@ void YGNodeCopyStyle(const YGNodeRef dstNode, const YGNodeRef srcNode) {
 }
 
 float YGNodeStyleGetFlexGrow(const YGNodeRef node) {
-  return node->getStyle().flexGrow.isUndefined
+  return node->getStyle().flexGrow.isUndefined()
       ? kDefaultFlexGrow
-      : node->getStyle().flexGrow.value;
+      : node->getStyle().flexGrow.getValue();
 }
 
 float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
-  return node->getStyle().flexShrink.isUndefined
+  return node->getStyle().flexShrink.isUndefined()
       ? (node->getConfig()->useWebDefaults ? kWebDefaultFlexShrink
                                            : kDefaultFlexShrink)
-      : node->getStyle().flexShrink.value;
+      : node->getStyle().flexShrink.getValue();
 }
 
 #define YG_NODE_STYLE_PROPERTY_SETTER_IMPL(                               \
@@ -744,9 +743,9 @@ void YGNodeStyleSetFlex(const YGNodeRef node, const float flex) {
   if (!YGFloatOptionalFloatEquals(node->getStyle().flex, flex)) {
     YGStyle style = node->getStyle();
     if (YGFloatIsUndefined(flex)) {
-      style.flex = {true, 0};
+      style.flex = YGFloatOptional();
     } else {
-      style.flex = {false, flex};
+      style.flex = YGFloatOptional(flex);
     }
     node->setStyle(style);
     node->markDirtyAndPropogate();
@@ -755,8 +754,8 @@ void YGNodeStyleSetFlex(const YGNodeRef node, const float flex) {
 
 // TODO(T26792433): Change the API to accept YGFloatOptional.
 float YGNodeStyleGetFlex(const YGNodeRef node) {
-  return node->getStyle().flex.isUndefined ? YGUndefined
-                                           : node->getStyle().flex.value;
+  return node->getStyle().flex.isUndefined() ? YGUndefined
+                                             : node->getStyle().flex.getValue();
 }
 
 // TODO(T26792433): Change the API to accept YGFloatOptional.
@@ -764,9 +763,9 @@ void YGNodeStyleSetFlexGrow(const YGNodeRef node, const float flexGrow) {
   if (!YGFloatOptionalFloatEquals(node->getStyle().flexGrow, flexGrow)) {
     YGStyle style = node->getStyle();
     if (YGFloatIsUndefined(flexGrow)) {
-      style.flexGrow = {true, 0};
+      style.flexGrow = YGFloatOptional();
     } else {
-      style.flexGrow = {false, flexGrow};
+      style.flexGrow = YGFloatOptional(flexGrow);
     }
     node->setStyle(style);
     node->markDirtyAndPropogate();
@@ -778,9 +777,9 @@ void YGNodeStyleSetFlexShrink(const YGNodeRef node, const float flexShrink) {
   if (!YGFloatOptionalFloatEquals(node->getStyle().flexShrink, flexShrink)) {
     YGStyle style = node->getStyle();
     if (YGFloatIsUndefined(flexShrink)) {
-      style.flexShrink = {true, 0};
+      style.flexShrink = YGFloatOptional();
     } else {
-      style.flexShrink = {false, flexShrink};
+      style.flexShrink = YGFloatOptional(flexShrink);
     }
     node->setStyle(style);
     node->markDirtyAndPropogate();
@@ -1669,13 +1668,15 @@ static float YGNodeCalculateAvailableInnerDim(
     // We want to make sure our available height does not violate min and max
     // constraints
     const YGFloatOptional minDimensionOptional = YGResolveValue(node->getStyle().minDimensions[dimension], parentDim);
-    const float minInnerDim = minDimensionOptional.isUndefined
+    const float minInnerDim = minDimensionOptional.isUndefined()
         ? 0.0f
-        : minDimensionOptional.value - paddingAndBorder;
+        : minDimensionOptional.getValue() - paddingAndBorder;
 
     const YGFloatOptional maxDimensionOptional = YGResolveValue(node->getStyle().maxDimensions[dimension], parentDim) ;
 
-    const float maxInnerDim = maxDimensionOptional.isUndefined ? FLT_MAX : maxDimensionOptional.value - paddingAndBorder;
+    const float maxInnerDim = maxDimensionOptional.isUndefined()
+        ? FLT_MAX
+        : maxDimensionOptional.getValue() - paddingAndBorder;
     availableInnerDim =
         YGFloatMax(YGFloatMin(availableInnerDim, maxInnerDim), minInnerDim);
   }
@@ -2207,7 +2208,8 @@ static void YGJustifyMainAxis(
   if (measureModeMainDim == YGMeasureModeAtMost &&
       collectedFlexItemsValues.remainingFreeSpace > 0) {
     if (style.minDimensions[dim[mainAxis]].unit != YGUnitUndefined &&
-        !YGResolveValue(style.minDimensions[dim[mainAxis]], mainAxisParentSize).isUndefined) {
+        !YGResolveValue(style.minDimensions[dim[mainAxis]], mainAxisParentSize)
+             .isUndefined()) {
       collectedFlexItemsValues.remainingFreeSpace = YGFloatMax(
           0,
           YGUnwrapFloatOptional(YGResolveValue(
@@ -3713,8 +3715,8 @@ void YGNodeCalculateLayout(
         node->getMarginForAxis(YGFlexDirectionRow, parentWidth);
     widthMeasureMode = YGMeasureModeExactly;
   } else if (!YGResolveValue(
-                 node->getStyle().maxDimensions[YGDimensionWidth],
-                 parentWidth).isUndefined) {
+                  node->getStyle().maxDimensions[YGDimensionWidth], parentWidth)
+                  .isUndefined()) {
     width = YGUnwrapFloatOptional(YGResolveValue(
         node->getStyle().maxDimensions[YGDimensionWidth], parentWidth));
     widthMeasureMode = YGMeasureModeAtMost;
@@ -3732,8 +3734,10 @@ void YGNodeCalculateLayout(
                  parentHeight)) +
         node->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
     heightMeasureMode = YGMeasureModeExactly;
-  } else if (!YGResolveValue(node->getStyle().maxDimensions[YGDimensionHeight],
-                 parentHeight).isUndefined) {
+  } else if (!YGResolveValue(
+                  node->getStyle().maxDimensions[YGDimensionHeight],
+                  parentHeight)
+                  .isUndefined()) {
     height = YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionHeight], parentHeight));
     heightMeasureMode = YGMeasureModeAtMost;
   } else {
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index 83eefa026893..2ec6a687ee74 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -42,11 +42,6 @@ typedef struct YGValue {
   YGUnit unit;
 } YGValue;
 
-struct YGFloatOptional {
-  bool isUndefined;
-  float value;
-};
-
 extern const YGValue YGValueUndefined;
 extern const YGValue YGValueAuto;
 

From f376fe3232fb23c7ffefe2cbc7a1b51c64632a08 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Thu, 15 Mar 2018 16:27:02 -0700
Subject: [PATCH 0039/1109] Remove @xplat cell syntax in open source

Differential Revision: D7292243

fbshipit-source-id: f1c162be8bc90669481f04de8aa71f3d9dbece36
---
 .../src/main/java/com/facebook/react/fabric/jsc/jni/BUCK        | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
index cbf088f2d277..4c4dd27047f9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
@@ -1,4 +1,4 @@
-load("@xplat//ReactNative:DEFS.bzl", "react_native_target", "react_native_xplat_target", "rn_xplat_cxx_library", "FBJNI_TARGET", "ANDROID")
+load("//ReactNative:DEFS.bzl", "react_native_target", "react_native_xplat_target", "rn_xplat_cxx_library", "FBJNI_TARGET", "ANDROID")
 
 rn_xplat_cxx_library(
     name = "jni",

From b02b1670d65118c333d3e0b83ddc99d2dc39dbed Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Thu, 15 Mar 2018 18:19:05 -0700
Subject: [PATCH 0040/1109] Bump metro@0.30.2

Reviewed By: BYK

Differential Revision: D7292431

fbshipit-source-id: 2d81e502e060ecd278977b838e0ef2db7e13b0e3
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index bc2e7cd11a03..3aab6dca4ba0 100644
--- a/package.json
+++ b/package.json
@@ -175,8 +175,8 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.30.1",
-    "metro-core": "^0.30.1",
+    "metro": "^0.30.2",
+    "metro-core": "^0.30.2",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From dbd47592a18ed09ee6e94c79bed16d63be625af6 Mon Sep 17 00:00:00 2001
From: Thibault Malbranche <thibault.malbranche@epitech.eu>
Date: Fri, 16 Mar 2018 11:11:40 -0700
Subject: [PATCH 0041/1109] Local cli/android/normalize project name
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

Scoped packages are starting to be the new thing, and gradle does not work properly with '/' in the project name, so this PR links them and replaces '/' by '_' . This only affects android.

I added tests in the 2 impacted functions + a test file for the normalizer function

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

-->
[CLI] [BUGFIX] [local-cli/link/link.js] - On android, Scoped packages will now get the '/' replaced with '_' to ensure gradle works nicely.  ⚠️ However if you previously linked scoped packages, they will get linked again. ⚠️
Closes https://github.com/facebook/react-native/pull/18275

Differential Revision: D7305227

Pulled By: hramos

fbshipit-source-id: 1c95563e884175529692948b29407a7733c44353
---
 .../__tests__/android/makeBuildPatch.spec.js  | 18 +++++++++++
 .../android/makeSettingsPatch.spec.js         | 30 +++++++++++++++++++
 .../android/normalizeProjectName.spec.js      | 26 ++++++++++++++++
 .../link/android/patches/makeBuildPatch.js    |  7 +++--
 .../link/android/patches/makeSettingsPatch.js |  8 +++--
 .../android/patches/normalizeProjectName.js   |  4 +++
 6 files changed, 89 insertions(+), 4 deletions(-)
 create mode 100644 local-cli/link/__tests__/android/normalizeProjectName.spec.js
 create mode 100644 local-cli/link/android/patches/normalizeProjectName.js

diff --git a/local-cli/link/__tests__/android/makeBuildPatch.spec.js b/local-cli/link/__tests__/android/makeBuildPatch.spec.js
index 0fd082da91f6..fdcdad0453b1 100644
--- a/local-cli/link/__tests__/android/makeBuildPatch.spec.js
+++ b/local-cli/link/__tests__/android/makeBuildPatch.spec.js
@@ -10,7 +10,11 @@
 'use strict';
 
 const makeBuildPatch = require('../../android/patches/makeBuildPatch');
+const normalizeProjectName = require('../../android/patches/normalizeProjectName');
+
 const name = 'test';
+const scopedName = '@scoped/test';
+const normalizedScopedName = normalizeProjectName('@scoped/test');
 
 describe('makeBuildPatch', () => {
   it('should build a patch function', () => {
@@ -29,3 +33,17 @@ describe('makeBuildPatch', () => {
     expect(installPattern.toString()).toBe(match);
   });
 });
+
+
+describe('makeBuildPatchWithScopedPackage', () => {
+  it('should make a correct patch', () => {
+    const {patch} = makeBuildPatch(scopedName);
+    expect(patch).toBe(`    compile project(':${normalizedScopedName}')\n`);
+  });
+
+  it('should make a correct install check pattern', () => {
+    const {installPattern} = makeBuildPatch(scopedName);
+    const match = `/\\s{4}(compile)(\\(|\\s)(project)\\(\\':${normalizedScopedName}\\'\\)(\\)|\\s)/`;
+    expect(installPattern.toString()).toBe(match);
+  });
+});
diff --git a/local-cli/link/__tests__/android/makeSettingsPatch.spec.js b/local-cli/link/__tests__/android/makeSettingsPatch.spec.js
index a8c7e3c2ba8d..63954af8155f 100644
--- a/local-cli/link/__tests__/android/makeSettingsPatch.spec.js
+++ b/local-cli/link/__tests__/android/makeSettingsPatch.spec.js
@@ -11,8 +11,11 @@
 
 const path = require('path');
 const makeSettingsPatch = require('../../android/patches/makeSettingsPatch');
+const normalizeProjectName = require('../../android/patches/normalizeProjectName');
 
 const name = 'test';
+const scopedName = '@scoped/test';
+const normalizedScopedName = normalizeProjectName('@scoped/test');
 const projectConfig = {
   sourceDir: '/home/project/android/app',
   settingsGradlePath: '/home/project/android/settings.gradle',
@@ -20,6 +23,9 @@ const projectConfig = {
 const dependencyConfig = {
   sourceDir: `/home/project/node_modules/${name}/android`,
 };
+const scopedDependencyConfig = {
+  sourceDir: `/home/project/node_modules/${scopedName}/android`,
+};
 
 describe('makeSettingsPatch', () => {
   it('should build a patch function', () => {
@@ -44,3 +50,27 @@ describe('makeSettingsPatch', () => {
       );
   });
 });
+
+describe('makeSettingsPatchWithScopedPackage', () => {
+  it('should build a patch function', () => {
+    expect(Object.prototype.toString(
+      makeSettingsPatch(scopedName, scopedDependencyConfig, projectConfig)
+    )).toBe('[object Object]');
+  });
+
+  it('should make a correct patch', () => {
+    const projectDir = path.relative(
+      path.dirname(projectConfig.settingsGradlePath),
+      scopedDependencyConfig.sourceDir
+    );
+
+    const {patch} = makeSettingsPatch(scopedName, scopedDependencyConfig, projectConfig);
+
+    expect(patch)
+      .toBe(
+        `include ':${normalizedScopedName}'\n` +
+        `project(':${normalizedScopedName}').projectDir = ` +
+        `new File(rootProject.projectDir, '${projectDir}')\n`
+      );
+  });
+});
diff --git a/local-cli/link/__tests__/android/normalizeProjectName.spec.js b/local-cli/link/__tests__/android/normalizeProjectName.spec.js
new file mode 100644
index 000000000000..e4e236aca42f
--- /dev/null
+++ b/local-cli/link/__tests__/android/normalizeProjectName.spec.js
@@ -0,0 +1,26 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * All rights reserved.
+ *
+ * @emails oncall+javascript_foundation
+ */
+
+ 'use strict';
+
+const normalizeProjectName = require('../../android/patches/normalizeProjectName');
+
+const name = 'test';
+const scopedName = '@scoped/test';
+
+ describe('normalizeProjectName', () => {
+  it('should replace slashes with underscores', () => {
+    expect(normalizeProjectName(name))
+      .toBe('test');
+    expect(normalizeProjectName(scopedName))
+      .toBe('@scoped_test');
+  });
+});
diff --git a/local-cli/link/android/patches/makeBuildPatch.js b/local-cli/link/android/patches/makeBuildPatch.js
index 67f7d8aac3f1..3c4969af22d8 100644
--- a/local-cli/link/android/patches/makeBuildPatch.js
+++ b/local-cli/link/android/patches/makeBuildPatch.js
@@ -5,14 +5,17 @@
  * LICENSE file in the root directory of this source tree.
  */
 
+const normalizeProjectName = require('./normalizeProjectName');
+
 module.exports = function makeBuildPatch(name) {
+  const normalizedProjectName = normalizeProjectName(name);
   const installPattern = new RegExp(
-    `\\s{4}(compile)(\\(|\\s)(project)\\(\\\':${name}\\\'\\)(\\)|\\s)`
+    `\\s{4}(compile)(\\(|\\s)(project)\\(\\\':${normalizedProjectName}\\\'\\)(\\)|\\s)`
   );
 
   return {
     installPattern,
     pattern: /[^ \t]dependencies {\n/,
-    patch: `    compile project(':${name}')\n`
+    patch: `    compile project(':${normalizedProjectName}')\n`
   };
 };
diff --git a/local-cli/link/android/patches/makeSettingsPatch.js b/local-cli/link/android/patches/makeSettingsPatch.js
index a8a6e148333f..a39de2be17dc 100644
--- a/local-cli/link/android/patches/makeSettingsPatch.js
+++ b/local-cli/link/android/patches/makeSettingsPatch.js
@@ -6,6 +6,8 @@
  */
 
 const path = require('path');
+const normalizeProjectName = require('./normalizeProjectName');
+
 const isWin = process.platform === 'win32';
 
 module.exports = function makeSettingsPatch(name, androidConfig, projectConfig) {
@@ -13,6 +15,8 @@ module.exports = function makeSettingsPatch(name, androidConfig, projectConfig)
     path.dirname(projectConfig.settingsGradlePath),
     androidConfig.sourceDir
   );
+  const normalizedProjectName = normalizeProjectName(name);
+
 
   /*
    * Fix for Windows
@@ -26,8 +30,8 @@ module.exports = function makeSettingsPatch(name, androidConfig, projectConfig)
 
   return {
     pattern: '\n',
-    patch: `include ':${name}'\n` +
-      `project(':${name}').projectDir = ` +
+    patch: `include ':${normalizedProjectName}'\n` +
+      `project(':${normalizedProjectName}').projectDir = ` +
       `new File(rootProject.projectDir, '${projectDir}')\n`,
   };
 };
diff --git a/local-cli/link/android/patches/normalizeProjectName.js b/local-cli/link/android/patches/normalizeProjectName.js
new file mode 100644
index 000000000000..fd52d1bb108b
--- /dev/null
+++ b/local-cli/link/android/patches/normalizeProjectName.js
@@ -0,0 +1,4 @@
+
+module.exports = function normalizeProjectName(name) {
+  return name.replace(/\//g, '_');
+};

From 076b1cea3563cae30e11d63cc100ceaed9082692 Mon Sep 17 00:00:00 2001
From: Tadeu Valentt <tadeu.valentt@gmail.com>
Date: Fri, 16 Mar 2018 16:35:37 -0700
Subject: [PATCH 0042/1109] Prevent show a hidden status bar when opening
 modals, fix #7474

Summary:
<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

Closes the old #7474, keeping the status bar hidden when displaying a modal
or dialog, this is accomplished by verifying if the activity status bar is hidden or not.

Added a test to [RNTester](https://github.com/facebook/react-native/tree/master/RNTester), so it can be tested from there:

1. Run [RNTester](https://github.com/facebook/react-native/tree/master/RNTester) project
2. Go to <StatusBar> tests
3. Set `hidden: true` in the *StatusBar hidden* samples
4. Set `modal visible: true` and see the result

Here are some gifs to help see the results:
![fail](https://user-images.githubusercontent.com/1649955/36345378-f443ad7e-1407-11e8-850d-d6317fb34da4.gif)
![success](https://user-images.githubusercontent.com/1649955/36345392-1c590b56-1408-11e8-9244-a2e828f579ab.gif)

none

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[ GENERAL  ]   [ BUGFIX      ]   [ [StatusBar] - Prevent show a hidden status bar when opening modals
 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
[ GENERAL  ]   [ BUGFIX      ]   [StatusBar] - Prevent show a hidden status bar when opening modals
Closes https://github.com/facebook/react-native/pull/18004

Differential Revision: D7307564

Pulled By: hramos

fbshipit-source-id: 47e481ead78204865811ddf2ef3d27da77ad8b8f
---
 RNTester/js/StatusBarExample.js               | 59 ++++++++++++++++++-
 .../react/views/modal/ReactModalHostView.java | 11 ++++
 2 files changed, 69 insertions(+), 1 deletion(-)

diff --git a/RNTester/js/StatusBarExample.js b/RNTester/js/StatusBarExample.js
index 0df43f42edb3..e5dae5c77c49 100644
--- a/RNTester/js/StatusBarExample.js
+++ b/RNTester/js/StatusBarExample.js
@@ -17,6 +17,7 @@ const {
   Text,
   TouchableHighlight,
   View,
+  Modal,
 } = ReactNative;
 
 exports.framework = 'React';
@@ -100,6 +101,7 @@ class StatusBarHiddenExample extends React.Component<{}, $FlowFixMeState> {
             </Text>
           </View>
         </TouchableHighlight>
+        <ModalExample />
       </View>
     );
   }
@@ -380,6 +382,48 @@ class StatusBarStaticAndroidExample extends React.Component<{}> {
   }
 }
 
+
+class ModalExample extends React.Component<{}, $FlowFixMeState> {
+  state = {
+    modalVisible: false,
+  };
+
+  _onChangeModalVisible = () => {
+    this.setState({modalVisible: !this.state.modalVisible});
+  };
+
+  render() {
+    return (
+      <View>
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={this._onChangeModalVisible}>
+          <View style={styles.button}>
+            <Text>modal visible: {this.state.hidden ? 'true' : 'false'}</Text>
+          </View>
+        </TouchableHighlight>
+        <Modal
+          visible={this.state.modalVisible}
+          transparent={true}
+          onRequestClose={this._onChangeModalVisible}>
+          <View style={[styles.container]}>
+            <View style={[styles.innerContainer]}>
+              <Text>This modal was presented!</Text>
+              <TouchableHighlight
+                onPress={this._onChangeModalVisible}
+                style={styles.modalButton}>
+                <View style={styles.button}>
+                  <Text>Close</Text>
+                </View>
+              </TouchableHighlight>
+            </View>
+          </View>
+        </Modal>
+      </View>
+    );
+  }
+}
+
 const examples = [{
   title: 'StatusBar hidden',
   render() {
@@ -436,6 +480,16 @@ const examples = [{
 exports.examples = examples;
 
 var styles = StyleSheet.create({
+  container: {
+    flex: 1,
+    justifyContent: 'center',
+    padding: 20,
+    backgroundColor: '#f5fcff'
+  },
+  innerContainer: {
+    borderRadius: 10,
+    alignItems: 'center',
+  },
   wrapper: {
     borderRadius: 5,
     marginBottom: 5,
@@ -449,5 +503,8 @@ var styles = StyleSheet.create({
     marginTop: 16,
     marginBottom: 8,
     fontWeight: 'bold',
-  }
+  },
+  modalButton: {
+    marginTop: 10,
+  },
 });
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
index 1d64cb83f8f0..00eac510ab8f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
@@ -276,6 +276,17 @@ private View getContentView() {
   private void updateProperties() {
     Assertions.assertNotNull(mDialog, "mDialog must exist when we call updateProperties");
 
+    Activity currentActivity = getCurrentActivity();
+    if (currentActivity != null) {
+      int activityWindowFlags = currentActivity.getWindow().getAttributes().flags;
+      if ((activityWindowFlags
+          & WindowManager.LayoutParams.FLAG_FULLSCREEN) != 0) {
+        mDialog.getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
+      } else {
+        mDialog.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
+      }
+    }
+
     if (mTransparent) {
       mDialog.getWindow().clearFlags(WindowManager.LayoutParams.FLAG_DIM_BEHIND);
     } else {

From 6f6084db69de372cbc6dcec259389e4b7dfd7fa5 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Fri, 16 Mar 2018 16:48:36 -0700
Subject: [PATCH 0043/1109] Explicitly set path to yarn

Summary:
Due to issues with Circle's Docker images ([link](https://twitter.com/circleci/status/974694807091073024)), jobs are failing with an error "yarn not found".

Test Plan
Run on Circle

Release Notes
[GENERAL][MINOR][.circleci] - Fix Circle issue
Closes https://github.com/facebook/react-native/pull/18419

Differential Revision: D7312052

Pulled By: hramos

fbshipit-source-id: 2768b9c69046a2f80518430024d3e7afbbd7de65
---
 .circleci/config.yml                   | 10 +++++++---
 scripts/circleci/analyze_code.sh       | 12 ++++++++++++
 scripts/circleci/exec_swallow_error.sh | 13 +++++++++++++
 3 files changed, 32 insertions(+), 3 deletions(-)
 create mode 100755 scripts/circleci/analyze_code.sh
 create mode 100755 scripts/circleci/exec_swallow_error.sh

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 100bc1276ffd..4006882af1b7 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -157,10 +157,11 @@ aliases:
   - &run-js-tests
     name: JavaScript Test Suite
     command: yarn test-ci
-    
+
+  # eslint sometimes runs into trouble generating the reports
   - &run-lint-checks
     name: Lint code
-    command: yarn lint --format junit -o ~/react-native/reports/junit/js-lint-results.xml
+    command: scripts/circleci/exec_swallow_error.sh yarn lint --format junit -o ~/react-native/reports/junit/js-lint-results.xml
     when: always
 
   - &run-flow-checks
@@ -251,6 +252,8 @@ js_defaults: &js_defaults
   <<: *defaults
   docker:
     - image: circleci/node:8
+  environment:
+    - PATH: "/opt/yarn/yarn-v1.5.1/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
 
 android_defaults: &android_defaults
   <<: *defaults
@@ -258,6 +261,7 @@ android_defaults: &android_defaults
     - image: circleci/android:api-26-alpha
   resource_class: "large"
   environment:
+    - PATH: "/opt/yarn/yarn-v1.5.1/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
     - TERM: "dumb"
     - ADB_INSTALL_TIMEOUT: 10
     - _JAVA_OPTIONS: "-XX:+UnlockExperimentalVMOptions -XX:+UseCGroupMemoryLimitForHeap"
@@ -539,7 +543,7 @@ jobs:
           command: |
             # GITHUB_TOKEN=eslint-bot public_repo access token
             if [ -n "$CIRCLE_PR_NUMBER" ]; then
-              cat <(echo eslint; yarn --silent lint --format=json; echo flow; yarn --silent flow check --json) | GITHUB_TOKEN="af6ef0d15709bc91d""06a6217a5a826a226fb57b7" CI_USER=$CIRCLE_PROJECT_USERNAME CI_REPO=$CIRCLE_PROJECT_REPONAME PULL_REQUEST_NUMBER=$CIRCLE_PR_NUMBER node bots/code-analysis-bot.js
+              GITHUB_TOKEN="af6ef0d15709bc91d""06a6217a5a826a226fb57b7" CI_USER=$CIRCLE_PROJECT_USERNAME CI_REPO=$CIRCLE_PROJECT_REPONAME PULL_REQUEST_NUMBER=$CIRCLE_PR_NUMBER scripts/circleci/analyze_code.sh
             else
               echo "Skipping code analysis."            
             fi
diff --git a/scripts/circleci/analyze_code.sh b/scripts/circleci/analyze_code.sh
new file mode 100755
index 000000000000..9569a4fa8e73
--- /dev/null
+++ b/scripts/circleci/analyze_code.sh
@@ -0,0 +1,12 @@
+#!/bin/bash
+
+cat <(echo eslint; yarn --silent lint --format=json; echo flow; yarn --silent flow check --json) | GITHUB_TOKEN=$GITHUB_TOKEN CI_USER=$CI_USER CI_REPO=$CI_REPO PULL_REQUEST_NUMBER=$PULL_REQUEST_NUMBER node bots/code-analysis-bot.js
+
+# check status
+STATUS=$?
+if [ $STATUS == 0 ]; then
+  echo "Code analyzed successfully"
+else
+  echo "Code analyzis failed, error status $STATUS"
+fi
+
diff --git a/scripts/circleci/exec_swallow_error.sh b/scripts/circleci/exec_swallow_error.sh
new file mode 100755
index 000000000000..297cf5b01219
--- /dev/null
+++ b/scripts/circleci/exec_swallow_error.sh
@@ -0,0 +1,13 @@
+#!/bin/bash
+
+# execute command
+$@
+
+# check status
+STATUS=$?
+if [ $STATUS == 0 ]; then
+  echo "Command '$@' completed successfully"
+else
+  echo "Command '$@' exited with error status $STATUS"
+fi
+

From 6426735e825a466d9e2e1c27c22dbfad6329d395 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Fri, 16 Mar 2018 16:48:45 -0700
Subject: [PATCH 0044/1109] Simplify templates

Summary:
Trivial PR.

[GENERAL][MINOR][.circleci/, bots/] - Simplify GitHub templates
Closes https://github.com/facebook/react-native/pull/18418

Differential Revision: D7311869

Pulled By: hramos

fbshipit-source-id: b87599c53938406d585d711492aacbdde2fcb02a
---
 .github/ISSUE_TEMPLATE.md         | 38 +++++++++++-----------
 .github/PULL_REQUEST_TEMPLATE.md  | 53 ++++++++++++++++---------------
 .github/no-response.yml           |  9 ------
 bots/NewIssueGreeting.md          |  9 ------
 bots/QuestionGreeting.md          |  5 ---
 bots/dangerfile.js                | 26 +--------------
 bots/pr-inactivity-bookmarklet.js |  1 -
 bots/question-bookmarklet.js      |  1 -
 breaking-changes.md               |  3 --
 9 files changed, 47 insertions(+), 98 deletions(-)
 delete mode 100644 .github/no-response.yml
 delete mode 100644 bots/NewIssueGreeting.md
 delete mode 100644 bots/QuestionGreeting.md
 delete mode 100644 bots/pr-inactivity-bookmarklet.js
 delete mode 100644 bots/question-bookmarklet.js
 delete mode 100644 breaking-changes.md

diff --git a/.github/ISSUE_TEMPLATE.md b/.github/ISSUE_TEMPLATE.md
index bbe1d31e0b8f..46d7bb4760de 100644
--- a/.github/ISSUE_TEMPLATE.md
+++ b/.github/ISSUE_TEMPLATE.md
@@ -1,29 +1,27 @@
 <!--
   We use GitHub Issues exclusively for tracking bugs in React Native.
-  Please follow this template when preparing your bug report.
+  Questions? Visit http://facebook.github.io/react-native/help.html
+  If this issue is about documentation or the website, please file it at:
+  https://github.com/facebook/react-native-website/issues/new
 -->
 
-(Describe your issue in detail.)
+- [ ] I have reviewed the [documentation](https://facebook.github.io/react-native)
+- [ ] I have searched [existing issues](https://github.com/facebook/react-native/issues)
+- [ ] I am using the [latest React Native version](https://github.com/facebook/react-native/releases)
 
-### Environment
+<!-- Describe your issue in detail. -->
 
-(Run `react-native info` in your terminal and paste its contents here.)
+## Environment
+<!-- Required. Run `react-native info` in your terminal and paste its contents here. -->
 
-### Expected Behavior
-
-(Write what you thought would happen.)
-
-### Actual Behavior
-
-(Write what happened. Include screenshots if needed.)
-
-### Steps to Reproduce
-
-(Link to Snack, or steps to reproduce.)
+## Steps to Reproduce
+<!-- 
+  Required. Let us know how to reproduce the issue. Include a code sample, share a project, 
+  or share an app that reproduces the issue using [Snack](https://snack.expo.io/).
+-->
 
-<!--
-  Please share a project that reproduces the issue. 
-  Ideally, create a new app using https://snack.expo.io/ and try to reproduce the issue in it.
+## Expected Behavior
+<!-- Write what you thought would happen. -->
 
-  This is a good guide to creating bug demos: https://stackoverflow.com/help/mcve
--->
+## Actual Behavior
+<!-- Write what happened. Include screenshots if needed. If this is a regression, let us know. -->
diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md
index d8a1469f3290..93f140001bd7 100644
--- a/.github/PULL_REQUEST_TEMPLATE.md
+++ b/.github/PULL_REQUEST_TEMPLATE.md
@@ -1,43 +1,46 @@
-<!--
 Thank you for sending the PR! We appreciate you spending the time to work on these changes. 
-
 Help us understand your motivation by explaining why you decided to make this change.
 
-You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html
-
-Happy contributing!
-
+<!-- 
+  Required: Write your motivation here.
+  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
 -->
 
-## Motivation
-
-(Write your motivation here.)
-
 ## Test Plan
 
-(Write your test plan here. If you changed any code, please provide us with clear instructions on how you verified your changes work. Bonus points for screenshots and videos!)
+<!-- 
+  Required: Write your test plan here. If you changed any code, please provide us with 
+  clear instructions on how you verified your changes work. Bonus points for screenshots and videos! 
+-->
 
 ## Related PRs
 
-(If this PR adds or changes functionality, please take some time to update the docs at https://github.com/facebook/react-native-website, and link to your PR here.)
+<!-- 
+  Does this PR require a documentation change? 
+  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
+-->
 
 ## Release Notes
-<!--
-Help reviewers and the release process by writing your own release notes
 
-**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**
+<!-- 
+  Required. 
+  Help reviewers and the release process by writing your own release notes. See below for an example.
+-->
 
-  CATEGORY
-[----------]        TYPE
-[ CLI      ]   [-------------]      LOCATION
-[ DOCS     ]   [ BREAKING    ]   [-------------]
-[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
-[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
-[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
-[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
-[----------]   [-------------]   [-------------]   |-----------|
+[CATEGORY] [TYPE] [LOCATION] - Message
 
-[CATEGORY] [TYPE] [LOCATION] - MESSAGE
+<!--
+  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**
+
+    CATEGORY
+  [----------]      TYPE
+  [ CLI      ] [-------------]    LOCATION
+  [ DOCS     ] [ BREAKING    ] [-------------]
+  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
+  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
+  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
+  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
+  [----------] [-------------] [-------------]   |-----------|
 
  EXAMPLES:
 
diff --git a/.github/no-response.yml b/.github/no-response.yml
deleted file mode 100644
index 24203633432e..000000000000
--- a/.github/no-response.yml
+++ /dev/null
@@ -1,9 +0,0 @@
-# Configuration for probot-no-response - https://github.com/probot/no-response
-
-# Number of days of inactivity before an Issue is closed for lack of response
-daysUntilClose: 14
-# Label requiring a response
-responseRequiredLabel: Needs more information
-# Comment to post when closing an Issue for lack of response. Set to `false` to disable
-closeComment: >
-  Closing this issue as more information is needed to debug this and we have not heard back from the author.
diff --git a/bots/NewIssueGreeting.md b/bots/NewIssueGreeting.md
deleted file mode 100644
index 1d3ccd997e95..000000000000
--- a/bots/NewIssueGreeting.md
+++ /dev/null
@@ -1,9 +0,0 @@
-Hey {author}, thanks for reporting this issue!
-
-React Native, as you've probably heard, is getting really popular and truth is we're getting a bit overwhelmed by the activity surrounding it. There are just too many issues for us to manage properly.
-
-- If you **don't know how to do something** or **something is not working as you expect but not sure it's a bug**, please ask on [StackOverflow](https://stackoverflow.com/questions/tagged/react-native) with the tag `react-native` or for more real time interactions, ask on [Discord](https://discord.gg/0ZcbPKXt5bZjGY5n) in the #react-native channel.
-
-- If this is a **feature request or a bug** that you would like to be fixed, please report it on [Canny](https://react-native.canny.io/feature-requests). It has a ranking feature that lets us focus on the most important issues the community is experiencing.
-
-- We welcome clear issues and PRs that are ready for in-depth discussion. Please provide **screenshots** where appropriate and always mention the **version** of React Native you're using. Thank you for your contributions!
diff --git a/bots/QuestionGreeting.md b/bots/QuestionGreeting.md
deleted file mode 100644
index a63b273b5c84..000000000000
--- a/bots/QuestionGreeting.md
+++ /dev/null
@@ -1,5 +0,0 @@
-*By analyzing the title and description for some common words it looks like this issue might be a question. I'm just a bot and might be wrong. In that case please cc mkonicek, he would like to know about it :)*
-
-Please consider using [Stack Overflow](https://stackoverflow.com/questions/tagged/react-native) for questions. It's the best system for Q&A and the best way to get questions answered.
-
-Many people from the community hang out on Stack Overflow and will be able to see your question and be more likely to answer because of the reputation system. If after reading this you think your question is better suited for Stack Overflow, please consider closing this issue.
diff --git a/bots/dangerfile.js b/bots/dangerfile.js
index 9c9218b34d36..b97ecaf8e19f 100644
--- a/bots/dangerfile.js
+++ b/bots/dangerfile.js
@@ -18,14 +18,6 @@ if (!danger.github.pr.body || danger.github.pr.body.length < 10) {
   fail(':grey_question: This pull request needs a description.');
 }
 
-// Warns if the PR title contains [WIP]
-const isWIP = includes(danger.github.pr.title, '[WIP]');
-if (isWIP) {
-  const title = ':construction_worker: Work In Progress';
-  const idea = 'This PR appears to be a work in progress, and may not be ready to be merged yet.';
-  warn(`${title} - <i>${idea}</i>`);
-}
-
 // Warns if there are changes to package.json, and tags the team.
 const packageChanged = includes(danger.git.modified_files, 'package.json');
 if (packageChanged) {
@@ -44,10 +36,9 @@ if (!includesTestPlan) {
 }
 
 // Regex looks for given categories, types, a file/framework/component, and a message - broken into 4 capture groups
-const releaseNotesRegex = /\[(ANDROID|CLI|DOCS|GENERAL|INTERNAL|IOS|TVOS|WINDOWS)\]\s*?\[(BREAKING|BUGFIX|ENHANCEMENT|FEATURE|MINOR)\]\s*?\[(.*)\]\s*?\-\s*?(.*)/ig;
+const releaseNotesRegex = /\[\s?(ANDROID|CLI|DOCS|GENERAL|INTERNAL|IOS|TVOS|WINDOWS)\s?\]\s*?\[\s?(BREAKING|BUGFIX|ENHANCEMENT|FEATURE|MINOR)\s?\]\s*?\[(.*)\]\s*?\-\s*?(.*)/ig;
 const includesReleaseNotes = danger.github.pr.body && danger.github.pr.body.toLowerCase().includes('release notes');
 const correctlyFormattedReleaseNotes = releaseNotesRegex.test(danger.github.pr.body);
-const releaseNotesCaptureGroups = releaseNotesRegex.exec(danger.github.pr.body);
 
 if (!includesReleaseNotes) {
   const title = ':clipboard: Release Notes';
@@ -57,21 +48,6 @@ if (!includesReleaseNotes) {
   const title = ':clipboard: Release Notes';
   const idea = 'This PR may have incorrectly formatted Release Notes.';
   warn(`${title} - <i>${idea}</i>`);
-} else if (releaseNotesCaptureGroups) {
-  const category = releaseNotesCaptureGroups[1].toLowerCase();
-
-  // Use Release Notes to Tag PRs appropriately
-  if (category === 'ios' || category === 'tvos') {
-    message('Suggested label: iOS');
-  }
-
-  if (category === 'android') {
-    message('Suggested label: Android');
-  }
-
-  if (category === 'cli') {
-    message('Suggested label: Tooling');
-  }
 }
 
 // Tags big PRs
diff --git a/bots/pr-inactivity-bookmarklet.js b/bots/pr-inactivity-bookmarklet.js
deleted file mode 100644
index f0c363922c36..000000000000
--- a/bots/pr-inactivity-bookmarklet.js
+++ /dev/null
@@ -1 +0,0 @@
-javascript:(function(){$('#new_comment_field')[0].value='Hey @' + $(".timeline-comment-header-text").first().find(".author").text() + '! Thanks for making the pull request, but we are closing it due to inactivity (' + Math.round(Math.abs((Date.now() - new Date($(".timeline-comment-header-text").last().find("time").attr("datetime")).getTime())/(24*60*60*1000))) + ' days with no activity). If you want to get your proposed changes merged, please rebase your branch with master and send a new pull request. :)';/*$('button.btn-primary:contains("Comment")').click()*/})()
diff --git a/bots/question-bookmarklet.js b/bots/question-bookmarklet.js
deleted file mode 100644
index 0e16164c2fc7..000000000000
--- a/bots/question-bookmarklet.js
+++ /dev/null
@@ -1 +0,0 @@
-javascript:(function(){$('#new_comment_field')[0].value='Hey @' + $(".timeline-comment-header-text").first().find(".author").text() + '! Thanks for reporting this!\n\nThere\'s an awesome place to ask question like this one: [StackOverflow](http://stackoverflow.com/questions/tagged/react-native). It\'s the best system for Q&A. Many people from the community hang out there and will be able to see your question, you can vote on answers and mark question as answered etc. This lets us keep a list of bug reports and feature requests on github and especially [Canny](https://react-native.canny.io/feature-requests) (again, with voting which is really nice).\n\nIf you think StackOverflow works for you please consider posting there instead and closing this issue.\n\nI\'m posting this here because github issues haven\'t been working very well for us and because StackOverflow is so much better. Thanks for reading! :)';$('button.btn-primary:contains("Comment")').click()})()
diff --git a/breaking-changes.md b/breaking-changes.md
deleted file mode 100644
index ccf4fef1780c..000000000000
--- a/breaking-changes.md
+++ /dev/null
@@ -1,3 +0,0 @@
-# Breaking Changes
-
-**Breaking changes are now tracked in [the Wiki](https://github.com/facebook/react-native/wiki/Breaking-Changes)**.

From 353c070be9e9a5528d2098db4df3f0dc02d758a9 Mon Sep 17 00:00:00 2001
From: miguelsm <miguelsantesmases@gmail.com>
Date: Fri, 16 Mar 2018 16:59:49 -0700
Subject: [PATCH 0045/1109] Add a way to dismiss PopupMenu elements

Summary:
In native Android apps, like the YouTube app, context menus are closed when the device orientation changes.

In React Native apps instead, when having a [PopupMenu](https://developer.android.com/reference/android/widget/PopupMenu.html) open and rotating the device, the PopupMenu is not dismissed and appears in a wrong position on the screen.

This PR exposes a `dismissPopupMenu` method to allow the application to dismiss any open PopupMenu:

```(javascript)
UIManager.dismissPopupMenu()
```
Closes https://github.com/facebook/react-native/pull/15636

Differential Revision: D6837663

Pulled By: hramos

fbshipit-source-id: 7b0f4f04341129ad45c703a50897e17d93651974
---
 .../uimanager/NativeViewHierarchyManager.java | 20 ++++++++++++-----
 .../react/uimanager/UIImplementation.java     |  4 ++++
 .../react/uimanager/UIManagerModule.java      |  5 +++++
 .../react/uimanager/UIViewOperationQueue.java | 11 ++++++++++
 .../views/toolbar/ReactToolbarManager.java    | 22 +++++++++++++++++++
 5 files changed, 57 insertions(+), 5 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
index 2b259c6806ff..a57205b861eb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
@@ -74,6 +74,7 @@ public class NativeViewHierarchyManager {
   private final LayoutAnimationController mLayoutAnimator = new LayoutAnimationController();
 
   private boolean mLayoutAnimationEnabled;
+  private PopupMenu mPopupMenu;
 
   public NativeViewHierarchyManager(ViewManagerRegistry viewManagers) {
     this(viewManagers, new RootViewManager());
@@ -731,18 +732,27 @@ public synchronized void showPopupMenu(int reactTag, ReadableArray items, Callba
       error.invoke("Can't display popup. Could not find view with tag " + reactTag);
       return;
     }
-    PopupMenu popupMenu = new PopupMenu(getReactContextForView(reactTag), anchor);
+    mPopupMenu = new PopupMenu(getReactContextForView(reactTag), anchor);
 
-    Menu menu = popupMenu.getMenu();
+    Menu menu = mPopupMenu.getMenu();
     for (int i = 0; i < items.size(); i++) {
       menu.add(Menu.NONE, Menu.NONE, i, items.getString(i));
     }
 
     PopupMenuCallbackHandler handler = new PopupMenuCallbackHandler(success);
-    popupMenu.setOnMenuItemClickListener(handler);
-    popupMenu.setOnDismissListener(handler);
+    mPopupMenu.setOnMenuItemClickListener(handler);
+    mPopupMenu.setOnDismissListener(handler);
 
-    popupMenu.show();
+    mPopupMenu.show();
+  }
+
+  /**
+   * Dismiss the last opened PopupMenu {@link PopupMenu}.
+   */
+  public void dismissPopupMenu() {
+    if (mPopupMenu != null) {
+      mPopupMenu.dismiss();
+    }
   }
 
   private static class PopupMenuCallbackHandler implements PopupMenu.OnMenuItemClickListener,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
index c312ff763b06..46353bc28fc3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
@@ -802,6 +802,10 @@ public void showPopupMenu(int reactTag, ReadableArray items, Callback error, Cal
     mOperationsQueue.enqueueShowPopupMenu(reactTag, items, error, success);
   }
 
+  public void dismissPopupMenu() {
+    mOperationsQueue.enqueueDismissPopupMenu();
+  }
+
   public void sendAccessibilityEvent(int tag, int eventType) {
     mOperationsQueue.enqueueSendAccessibilityEvent(tag, eventType);
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 282c92ca3814..57430f3d07e7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -600,6 +600,11 @@ public void showPopupMenu(int reactTag, ReadableArray items, Callback error, Cal
     mUIImplementation.showPopupMenu(reactTag, items, error, success);
   }
 
+  @ReactMethod
+  public void dismissPopupMenu() {
+    mUIImplementation.dismissPopupMenu();
+  }
+
   /**
    * LayoutAnimation API on Android is currently experimental. Therefore, it needs to be enabled
    * explicitly in order to avoid regression in existing application written for iOS using this API.
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
index 1f2135db8652..832b94ce2cdc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
@@ -285,6 +285,13 @@ public void execute() {
     }
   }
 
+  private final class DismissPopupMenuOperation implements UIOperation {
+    @Override
+    public void execute() {
+      mNativeViewHierarchyManager.dismissPopupMenu();
+    }
+  }
+
   /**
    * A spec for animation operations (add/remove)
    */
@@ -656,6 +663,10 @@ public void enqueueShowPopupMenu(
     mOperations.add(new ShowPopupMenuOperation(reactTag, items, error, success));
   }
 
+  public void enqueueDismissPopupMenu() {
+    mOperations.add(new DismissPopupMenuOperation());
+  }
+
   public void enqueueCreateView(
       ThemedReactContext themedContext,
       int viewReactTag,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
index be9377047a90..0de356f1b95e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
@@ -33,6 +33,7 @@
 public class ReactToolbarManager extends ViewGroupManager<ReactToolbar> {
 
   private static final String REACT_CLASS = "ToolbarAndroid";
+  private static final int COMMAND_DISMISS_POPUP_MENUS = 1;
 
   @Override
   public String getName() {
@@ -157,6 +158,27 @@ public boolean needsCustomLayoutForChildren() {
     return true;
   }
 
+  @Nullable
+  @Override
+  public Map<String, Integer> getCommandsMap() {
+    return MapBuilder.of("dismissPopupMenus", COMMAND_DISMISS_POPUP_MENUS);
+  }
+
+  @Override
+  public void receiveCommand(ReactToolbar view, int commandType, @Nullable ReadableArray args) {
+    switch (commandType) {
+      case COMMAND_DISMISS_POPUP_MENUS: {
+        view.dismissPopupMenus();
+        return;
+      }
+      default:
+        throw new IllegalArgumentException(String.format(
+          "Unsupported command %d received by %s.",
+          commandType,
+          getClass().getSimpleName()));
+    }
+  }
+
   private int[] getDefaultContentInsets(Context context) {
     Resources.Theme theme = context.getTheme();
     TypedArray toolbarStyle = null;

From c2fd54fcb287bb635f93d1de15bafecbeb282264 Mon Sep 17 00:00:00 2001
From: Jamie Lynch <fractalwrench@gmail.com>
Date: Fri, 16 Mar 2018 18:21:59 -0700
Subject: [PATCH 0046/1109] Enable obfuscation in ProGuard rules by default

Summary:
This PR enables obfuscation in ProGuard by default when creating a new project, and documents how developers can turn obfuscation off if they desire.

The ProGuard phase is currently disabled by default. If a developer wanted to enable ProGuard, the first thing they would see is the following line in their build.gradle file: `def enableProguardInReleaseBuilds = false`

It's really easy to assume that enabling this flag will setup code shrinking and obfuscation, as this is the default behaviour for a completely native Android Studio project, or when running ProGuard from the command line directly.

However, the generated ProGuard rules override the default behaviour. Without visually inspecting the rules file, searching for a mapping file, or analyzing the Dex file classes, this isn't immediately obvious, as the APK will be smaller, and gradle will show the Proguard task as completing.

Personally I find this confusing and really wasn't expecting for obfuscation to be disabled - most Android Error Reporting services allow deobfuscation of stacktraces via mapping files.

1. Create a new project using `react-native init MyProject`
2. Observe that `-dontobfuscate` is commented out

[ANDROID] [MINOR] [ProGuard] - Enables obfuscation by default in newly created projects
Closes https://github.com/facebook/react-native/pull/17754

Differential Revision: D7251680

Pulled By: hramos

fbshipit-source-id: cf9ca7753640643377a51daa4fa9065516197340
---
 local-cli/templates/HelloWorld/android/app/proguard-rules.pro | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/local-cli/templates/HelloWorld/android/app/proguard-rules.pro b/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
index 6e8516c8d6dd..d8ec99250e54 100644
--- a/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
+++ b/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
@@ -18,7 +18,7 @@
 
 # Disabling obfuscation is useful if you collect stack traces from production crashes
 # (unless you are using a system that supports de-obfuscate the stack traces).
--dontobfuscate
+# -dontobfuscate
 
 # React Native
 

From 6f588b31befe9828fa216fde2fc1e4563b430a7e Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Fri, 16 Mar 2018 18:42:04 -0700
Subject: [PATCH 0047/1109] Fix Android job

Summary:
Yarn is not used in the Android step, not directly

Test Plan
Circle

Release Notes

[GENERAL][MINOR][.circleci] - Fix Android CI job
Closes https://github.com/facebook/react-native/pull/18421

Differential Revision: D7314158

Pulled By: hramos

fbshipit-source-id: ad40346b6a1c1f63a1b952fd05cbe9398d9c59a1
---
 .circleci/config.yml | 1 -
 1 file changed, 1 deletion(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 4006882af1b7..675aeb4e0b07 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -261,7 +261,6 @@ android_defaults: &android_defaults
     - image: circleci/android:api-26-alpha
   resource_class: "large"
   environment:
-    - PATH: "/opt/yarn/yarn-v1.5.1/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
     - TERM: "dumb"
     - ADB_INSTALL_TIMEOUT: 10
     - _JAVA_OPTIONS: "-XX:+UnlockExperimentalVMOptions -XX:+UseCGroupMemoryLimitForHeap"

From 541485c7feff9fc081c0dcf89600687e8a34ca74 Mon Sep 17 00:00:00 2001
From: Hunkyo Jung <hunkyo.jung@gmail.com>
Date: Sat, 17 Mar 2018 20:09:00 -0700
Subject: [PATCH 0048/1109] Add inverted prop in SectionListExample

Summary:
This PR adds an option to pass`inverted` prop to SectionListExample in RNTester. FlatListExample already has this option but it's not available in SectionListExample.

Run RNTester app on device or simulator and select SectionListExample. Depending on switching `inverted` option, you can see either inverted list or not.

[GENERAL][ENHANCEMENT][RNTeater] - Add inverted prop to SectionListExample
Closes https://github.com/facebook/react-native/pull/18370

Differential Revision: D7317168

Pulled By: hramos

fbshipit-source-id: c6c212c705e686281f23954775cc3465cce3c8df
---
 RNTester/js/SectionListExample.js | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/RNTester/js/SectionListExample.js b/RNTester/js/SectionListExample.js
index d5d7e685c6c6..920be1768644 100644
--- a/RNTester/js/SectionListExample.js
+++ b/RNTester/js/SectionListExample.js
@@ -76,6 +76,7 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
     filterText: '',
     logViewable: false,
     virtualized: true,
+    inverted: false,
   };
 
   _scrollPos = new Animated.Value(0);
@@ -125,6 +126,7 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
             {renderSmallSwitchOption(this, 'virtualized')}
             {renderSmallSwitchOption(this, 'logViewable')}
             {renderSmallSwitchOption(this, 'debug')}
+            {renderSmallSwitchOption(this, 'inverted')}
             <Spindicator value={this._scrollPos} />
           </View>
           <View style={styles.scrollToRow}>
@@ -146,6 +148,7 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
             <CustomSeparatorComponent {...info} text="ITEM SEPARATOR" />
           }
           debug={this.state.debug}
+          inverted={this.state.inverted}
           enableVirtualization={this.state.virtualized}
           onRefresh={() => Alert.alert('onRefresh: nothing to refresh :P')}
           onScroll={this._scrollSinkY}
@@ -232,6 +235,8 @@ const styles = StyleSheet.create({
   },
   optionSection: {
     flexDirection: 'row',
+    flexWrap: 'wrap',
+    alignItems: 'center',
   },
   searchRow: {
     paddingHorizontal: 10,

From 1c534719115fc4e99da9a414cff8638a6059a948 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Sat, 17 Mar 2018 21:59:57 -0700
Subject: [PATCH 0049/1109] iOS OSS: fixed RNTester - missing
 RCTInputAccessoryShadowView.* in .xcodeproj

Reviewed By: yungsters

Differential Revision: D7317380

fbshipit-source-id: 0a40d62c70cd3c3a875e5a418f4b77fecb0417b1
---
 Libraries/Text/RCTText.xcodeproj/project.pbxproj       | 6 ++++++
 Libraries/Text/TextInput/RCTInputAccessoryShadowView.h | 7 ++++++-
 Libraries/Text/TextInput/RCTInputAccessoryShadowView.m | 7 ++++++-
 3 files changed, 18 insertions(+), 2 deletions(-)

diff --git a/Libraries/Text/RCTText.xcodeproj/project.pbxproj b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
index da27ece2a1b1..8fc301593f03 100644
--- a/Libraries/Text/RCTText.xcodeproj/project.pbxproj
+++ b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
@@ -103,6 +103,7 @@
 		5956B1A6200FF35C008D9D16 /* RCTUITextField.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B103200FEBA9008D9D16 /* RCTUITextField.m */; };
 		5956B1A7200FF35C008D9D16 /* RCTVirtualTextShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */; };
 		5956B1A8200FF35C008D9D16 /* RCTVirtualTextViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12B200FEBAA008D9D16 /* RCTVirtualTextViewManager.m */; };
+		5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */; };
 		8F2807C7202D2B6B005D65E6 /* RCTInputAccessoryViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */; };
 		8F2807C8202D2B6B005D65E6 /* RCTInputAccessoryView.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */; };
 		8F2807C9202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C5202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m */; };
@@ -232,6 +233,8 @@
 		5956B12D200FEBAA008D9D16 /* RCTVirtualTextViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTVirtualTextViewManager.h; sourceTree = "<group>"; };
 		5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTVirtualTextShadowView.m; sourceTree = "<group>"; };
 		5956B12F200FEBAA008D9D16 /* RCTConvert+Text.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "RCTConvert+Text.m"; sourceTree = "<group>"; };
+		5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryShadowView.m; sourceTree = "<group>"; };
+		5C245F38205E216A00D936E9 /* RCTInputAccessoryShadowView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryShadowView.h; sourceTree = "<group>"; };
 		8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryViewManager.m; sourceTree = "<group>"; };
 		8F2807C2202D2B6A005D65E6 /* RCTInputAccessoryViewContent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryViewContent.h; sourceTree = "<group>"; };
 		8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryView.m; sourceTree = "<group>"; };
@@ -283,6 +286,8 @@
 		5956B0FF200FEBA9008D9D16 /* TextInput */ = {
 			isa = PBXGroup;
 			children = (
+				5C245F38205E216A00D936E9 /* RCTInputAccessoryShadowView.h */,
+				5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */,
 				8F2807C4202D2B6A005D65E6 /* RCTInputAccessoryView.h */,
 				8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */,
 				8F2807C2202D2B6A005D65E6 /* RCTInputAccessoryViewContent.h */,
@@ -493,6 +498,7 @@
 				5956B142200FEBAA008D9D16 /* RCTTextViewManager.m in Sources */,
 				5956B135200FEBAA008D9D16 /* RCTBaseTextInputView.m in Sources */,
 				5956B144200FEBAA008D9D16 /* RCTVirtualTextViewManager.m in Sources */,
+				5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */,
 				5956B13B200FEBAA008D9D16 /* RCTMultilineTextInputViewManager.m in Sources */,
 				5956B134200FEBAA008D9D16 /* RCTSinglelineTextInputViewManager.m in Sources */,
 				5956B139200FEBAA008D9D16 /* RCTBaseTextInputViewManager.m in Sources */,
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryShadowView.h b/Libraries/Text/TextInput/RCTInputAccessoryShadowView.h
index 4731cea4d8e1..c63fdf48158a 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryShadowView.h
+++ b/Libraries/Text/TextInput/RCTInputAccessoryShadowView.h
@@ -1,4 +1,9 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
 
 #import <React/RCTShadowView.h>
 
diff --git a/Libraries/Text/TextInput/RCTInputAccessoryShadowView.m b/Libraries/Text/TextInput/RCTInputAccessoryShadowView.m
index b2664aaec8bd..6798744148e3 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryShadowView.m
+++ b/Libraries/Text/TextInput/RCTInputAccessoryShadowView.m
@@ -1,4 +1,9 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
 
 #import "RCTInputAccessoryShadowView.h"
 

From d16772a31ec8b4429996c0f6fb4871b5162ec6fd Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:08 -0700
Subject: [PATCH 0050/1109] Sealable: fixed semantic; atomic type for the flag
 variable

Summary:
* Fixed semantic: all kinds of derivative instances lose `sealed` flag (which is expected);
 * Using atomic<bool> for `sealed_` ivar.

Reviewed By: fkgozali

Differential Revision: D7230674

fbshipit-source-id: abe786610c20a45a0fabb9068120e24adeeeac7f
---
 .../fabric/core/primitives/Sealable.cpp       | 30 +++++++++++++++++++
 ReactCommon/fabric/core/primitives/Sealable.h | 25 ++++++++++++----
 2 files changed, 49 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/fabric/core/primitives/Sealable.cpp b/ReactCommon/fabric/core/primitives/Sealable.cpp
index fc4bb8c259ec..a93f640db531 100644
--- a/ReactCommon/fabric/core/primitives/Sealable.cpp
+++ b/ReactCommon/fabric/core/primitives/Sealable.cpp
@@ -12,6 +12,36 @@
 namespace facebook {
 namespace react {
 
+/*
+ * Note:
+ * We must explictly implement all *the rule of five* methods because:
+ *   1. Using `std::atomic` behind `sealed_` implicitly deletes default
+ *      constructors;
+ *   2. We have to establish behaviour where any new cloned or moved instances
+ *      of the object lose `sealed` flag.
+ *
+ * See more about the rule of three/five/zero:
+ * http://en.cppreference.com/w/cpp/language/rule_of_three
+ */
+
+Sealable::Sealable(): sealed_(false) {}
+
+Sealable::Sealable(const Sealable& other): sealed_(false) {};
+
+Sealable::Sealable(Sealable&& other) noexcept: sealed_(false) {};
+
+Sealable::~Sealable() noexcept {};
+
+Sealable& Sealable::operator= (const Sealable& other) {
+  ensureUnsealed();
+  return *this;
+}
+
+Sealable& Sealable::operator= (Sealable&& other) noexcept {
+  ensureUnsealed();
+  return *this;
+};
+
 void Sealable::seal() const {
   sealed_ = true;
 }
diff --git a/ReactCommon/fabric/core/primitives/Sealable.h b/ReactCommon/fabric/core/primitives/Sealable.h
index 1f8fa0f093a0..e0d168e44e08 100644
--- a/ReactCommon/fabric/core/primitives/Sealable.h
+++ b/ReactCommon/fabric/core/primitives/Sealable.h
@@ -7,21 +7,27 @@
 
 #pragma once
 
+#import <atomic>
+
 namespace facebook {
 namespace react {
 
 /*
- * Represents something which can be *sealed* (imperatively marked as immutable).
+ * Represents an object which can be *sealed* (imperatively marked as immutable).
+ *
+ * The `sealed` flag is tight to a particular instance of the class and resets
+ * to `false` for all newly created (by copy-constructor, assignment operator
+ * and so on) derivative objects.
  *
  * Why do we need this? In Fabric, some objects are semi-immutable
- * even if they explicitly marked as `const`. It means that in some special
- * cases those objects can be const-cast-away and then mutated. That comes from
+ * even if they are explicitly marked as `const`. It means that in some special
+ * cases those objects can be const-casted-away and then mutated. That comes from
  * the fact that we share some object's life-cycle responsibilities with React
  * and the immutability is guaranteed by some logic splitted between native and
- * JavaScript worlds (which makes impossible to fully use immutability
+ * JavaScript worlds (which makes it impossible to fully use immutability
  * enforcement at a language level).
  * To detect possible errors as early as possible we additionally mark objects
- * as *sealed* after some stage and then enforce this at run-time.
+ * as *sealed* after some stages and then enforce this at run-time.
  *
  * How to use:
  *   1. Inherit your class from `Sealable`.
@@ -31,6 +37,13 @@ namespace react {
  */
 class Sealable {
 public:
+  Sealable();
+  Sealable(const Sealable& other);
+  Sealable(Sealable&& other) noexcept;
+  ~Sealable() noexcept;
+  Sealable& operator=(const Sealable& other);
+  Sealable& operator=(Sealable&& other) noexcept;
+
   /*
    * Seals the object. This operation is irreversible;
    * the object cannot be "unsealed" after being sealing.
@@ -50,7 +63,7 @@ class Sealable {
   void ensureUnsealed() const;
 
 private:
-  mutable bool sealed_ {false};
+  mutable std::atomic<bool> sealed_ {false};
 };
 
 } // namespace react

From c6234558458fc3c8eb7bf742782189e8df8b8b90 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:10 -0700
Subject: [PATCH 0051/1109] Abstract classes for ShadowNode and Props

Summary: Foundation clases for Fabric designed to be "const-first".

Reviewed By: fkgozali

Differential Revision: D7230672

fbshipit-source-id: 433acd35a7958d5d577358b0a306923f970e573f
---
 ReactCommon/fabric/FabricUIManager.cpp        |  21 ++-
 ReactCommon/fabric/FabricUIManager.h          |  25 ++--
 ReactCommon/fabric/ShadowNode.cpp             |  20 ---
 ReactCommon/fabric/ShadowNode.h               |  27 ----
 ReactCommon/fabric/core/BUCK                  |   1 +
 .../fabric/core/primitives/ReactPrimitives.h  |  55 +++++++
 ReactCommon/fabric/core/shadownode/Props.cpp  |  29 ++++
 ReactCommon/fabric/core/shadownode/Props.h    |  38 +++++
 .../fabric/core/shadownode/ShadowNode.cpp     | 134 ++++++++++++++++++
 .../fabric/core/shadownode/ShadowNode.h       |  80 +++++++++++
 10 files changed, 358 insertions(+), 72 deletions(-)
 delete mode 100644 ReactCommon/fabric/ShadowNode.cpp
 delete mode 100644 ReactCommon/fabric/ShadowNode.h
 create mode 100644 ReactCommon/fabric/core/primitives/ReactPrimitives.h
 create mode 100644 ReactCommon/fabric/core/shadownode/Props.cpp
 create mode 100644 ReactCommon/fabric/core/shadownode/Props.h
 create mode 100644 ReactCommon/fabric/core/shadownode/ShadowNode.cpp
 create mode 100644 ReactCommon/fabric/core/shadownode/ShadowNode.h

diff --git a/ReactCommon/fabric/FabricUIManager.cpp b/ReactCommon/fabric/FabricUIManager.cpp
index 54262fc9edbf..9b6ec3216e61 100644
--- a/ReactCommon/fabric/FabricUIManager.cpp
+++ b/ReactCommon/fabric/FabricUIManager.cpp
@@ -8,7 +8,6 @@
 #include "FabricUIManager.h"
 
 #include "IFabricPlatformUIOperationManager.h"
-#include "ShadowNode.h"
 
 namespace facebook {
 namespace react {
@@ -16,38 +15,38 @@ namespace react {
 FabricUIManager::FabricUIManager(const std::shared_ptr<IFabricPlatformUIOperationManager> &platformUIOperationManager) :
   platformUIOperationManager_(platformUIOperationManager) {};
 
-ShadowNodeRef FabricUIManager::createNode(int reactTag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
+SharedShadowNode FabricUIManager::createNode(int reactTag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
   platformUIOperationManager_->performUIOperation();
-  return std::make_shared<ShadowNode>(reactTag, viewName, rootTag, props, instanceHandle);
+  return nullptr;
 }
 
-ShadowNodeRef FabricUIManager::cloneNode(const ShadowNodeRef &node) {
+SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &node) {
   return nullptr;
 }
 
-ShadowNodeRef FabricUIManager::cloneNodeWithNewChildren(const ShadowNodeRef &node) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &node) {
   return nullptr;
 }
 
-ShadowNodeRef FabricUIManager::cloneNodeWithNewProps(const ShadowNodeRef &node, folly::dynamic props) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props) {
   return nullptr;
 }
 
-ShadowNodeRef FabricUIManager::cloneNodeWithNewChildrenAndProps(const ShadowNodeRef &node, folly::dynamic newProps) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps) {
   return nullptr;
 }
 
-void FabricUIManager::appendChild(const ShadowNodeRef &parentNode, const ShadowNodeRef &childNode) {
+void FabricUIManager::appendChild(const SharedShadowNode &parentNode, const SharedShadowNode &childNode) {
 }
 
-ShadowNodeSetRef FabricUIManager::createChildSet(int rootTag) {
+SharedShadowNodeUnsharedList FabricUIManager::createChildSet(int rootTag) {
   return nullptr;
 }
 
-void FabricUIManager::appendChildToSet(const ShadowNodeSetRef &childSet, const ShadowNodeRef &childNode) {
+void FabricUIManager::appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode) {
 }
 
-void FabricUIManager::completeRoot(int rootTag, const ShadowNodeSetRef &childSet) {
+void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedList &childSet) {
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/FabricUIManager.h b/ReactCommon/fabric/FabricUIManager.h
index 06ee2a94f70e..4857a4291d75 100644
--- a/ReactCommon/fabric/FabricUIManager.h
+++ b/ReactCommon/fabric/FabricUIManager.h
@@ -11,29 +11,26 @@
 #include <folly/FBVector.h>
 #include <memory>
 
+#include <fabric/core/ShadowNode.h>
+
 namespace facebook {
 namespace react {
 
-class ShadowNode;
 class IFabricPlatformUIOperationManager;
 
-typedef std::shared_ptr<const ShadowNode> ShadowNodeRef;
-typedef folly::fbvector<const ShadowNodeRef> ShadowNodeSet;
-typedef std::shared_ptr<const ShadowNodeSet> ShadowNodeSetRef;
-
 class FabricUIManager {
 public:
   FabricUIManager(const std::shared_ptr<IFabricPlatformUIOperationManager> &platformUIOperationManager);
 
-  ShadowNodeRef createNode(int reactTag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle);
-  ShadowNodeRef cloneNode(const ShadowNodeRef &node);
-  ShadowNodeRef cloneNodeWithNewChildren(const ShadowNodeRef &node);
-  ShadowNodeRef cloneNodeWithNewProps(const ShadowNodeRef &node, folly::dynamic props);
-  ShadowNodeRef cloneNodeWithNewChildrenAndProps(const ShadowNodeRef &node, folly::dynamic newProps);
-  void appendChild(const ShadowNodeRef &parentNode, const ShadowNodeRef &childNode);
-  ShadowNodeSetRef createChildSet(int rootTag);
-  void appendChildToSet(const ShadowNodeSetRef &childSet, const ShadowNodeRef &childNode);
-  void completeRoot(int rootTag, const ShadowNodeSetRef &childSet);
+  SharedShadowNode createNode(int reactTag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle);
+  SharedShadowNode cloneNode(const SharedShadowNode &node);
+  SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node);
+  SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props);
+  SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps);
+  void appendChild(const SharedShadowNode &parentNode, const SharedShadowNode &childNode);
+  SharedShadowNodeUnsharedList createChildSet(int rootTag);
+  void appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode);
+  void completeRoot(int rootTag, const SharedShadowNodeUnsharedList &childSet);
 
 private:
   std::shared_ptr<IFabricPlatformUIOperationManager> platformUIOperationManager_;
diff --git a/ReactCommon/fabric/ShadowNode.cpp b/ReactCommon/fabric/ShadowNode.cpp
deleted file mode 100644
index 9f675572bc81..000000000000
--- a/ReactCommon/fabric/ShadowNode.cpp
+++ /dev/null
@@ -1,20 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#include "ShadowNode.h"
-
-namespace facebook {
-namespace react {
-
-ShadowNode::ShadowNode(int reactTag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) :
-  reactTag_(reactTag),
-  viewName_(viewName),
-  rootTag_(rootTag),
-  props_(props),
-  instanceHandle_(instanceHandle) {}
-
-}}
diff --git a/ReactCommon/fabric/ShadowNode.h b/ReactCommon/fabric/ShadowNode.h
deleted file mode 100644
index 257b7c19e940..000000000000
--- a/ReactCommon/fabric/ShadowNode.h
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <folly/dynamic.h>
-#include <memory>
-
-namespace facebook {
-namespace react {
-
-class ShadowNode {
-public:
-  int reactTag_;
-  std::string viewName_;
-  int rootTag_;
-  folly::dynamic props_;
-  void *instanceHandle_;
-
-  ShadowNode(int reactTag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle);
-};
-
-}}
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 4001090955b4..ec92dc42c2c2 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -23,6 +23,7 @@ rn_xplat_cxx_library(
     exported_headers = subdir_glob(
         [
             ("primitives", "*.h"),
+            ("shadownode", "*.h"),
         ],
         prefix = "fabric/core",
     ),
diff --git a/ReactCommon/fabric/core/primitives/ReactPrimitives.h b/ReactCommon/fabric/core/primitives/ReactPrimitives.h
new file mode 100644
index 000000000000..0b5004ab2ca0
--- /dev/null
+++ b/ReactCommon/fabric/core/primitives/ReactPrimitives.h
@@ -0,0 +1,55 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+#include <string>
+
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * `Tag` and `InstanceHandle` are used to address React Native components.
+ */
+using Tag = int32_t;
+using InstanceHandle = void *;
+
+/*
+ * `RawProps` represents untyped map with props comes from JavaScript side.
+ */
+// TODO(T26954420): Use iterator as underlying type for RawProps.
+using RawProps = std::map<std::string, folly::dynamic>;
+using SharedRawProps = std::shared_ptr<const RawProps>;
+
+/*
+ * Components event handlers.
+ * Something which usually called from JavaScript side.
+ */
+using BubblingEventHandler = void (*)(void);
+using SharedBubblingEventHandler = std::shared_ptr<BubblingEventHandler>;
+using DirectEventHandler = void (*)(void);
+using SharedDirectEventHandler = std::shared_ptr<DirectEventHandler>;
+
+/*
+ * Universal component handle which allows to refer to `ComponentDescriptor`s
+ * in maps efficiently.
+ * Practically, it's something that concrete ShadowNode and concrete
+ * ComponentDescriptor have in common.
+ */
+using ComponentHandle = size_t;
+
+/*
+ * String identifier for components used for addressing them from
+ * JavaScript side.
+ */
+using ComponentName = std::string;
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/Props.cpp b/ReactCommon/fabric/core/shadownode/Props.cpp
new file mode 100644
index 000000000000..fb527d62be95
--- /dev/null
+++ b/ReactCommon/fabric/core/shadownode/Props.cpp
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "Props.h"
+
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+void Props::apply(const RawProps &rawProps) {
+  ensureUnsealed();
+
+  for (auto const &pair : rawProps) {
+    auto const &name = pair.first;
+    auto const &value = pair.second;
+
+    if (name == "nativeID") {
+      nativeId_ = value.asString();
+    }
+  }
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/Props.h b/ReactCommon/fabric/core/shadownode/Props.h
new file mode 100644
index 000000000000..da9f4f3b6f14
--- /dev/null
+++ b/ReactCommon/fabric/core/shadownode/Props.h
@@ -0,0 +1,38 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <folly/dynamic.h>
+
+#include <fabric/core/Sealable.h>
+#include <fabric/core/ReactPrimitives.h>
+#include <fabric/debug/DebugStringConvertible.h>
+
+namespace facebook {
+namespace react {
+
+class Props;
+
+using SharedProps = std::shared_ptr<const Props>;
+
+/*
+ * Represents the most generic props object.
+ */
+class Props:
+  public virtual Sealable,
+  public virtual DebugStringConvertible {
+
+public:
+  virtual void apply(const RawProps &rawProps);
+
+private:
+  std::string nativeId_ {""};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
new file mode 100644
index 000000000000..1f2777429d18
--- /dev/null
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -0,0 +1,134 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ShadowNode.h"
+
+#include <fabric/debug/DebugStringConvertible.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+namespace facebook {
+namespace react {
+
+SharedShadowNodeSharedList ShadowNode::emptySharedShadowNodeSharedList() {
+  static const auto emptySharedShadowNodeSharedList = std::make_shared<SharedShadowNodeList>();
+  return emptySharedShadowNodeSharedList;
+}
+
+#pragma mark - Constructors
+
+ShadowNode::ShadowNode(
+  Tag tag,
+  InstanceHandle instanceHandle,
+  SharedProps props,
+  SharedShadowNodeSharedList children
+):
+  tag_(tag),
+  instanceHandle_(instanceHandle),
+  props_(props),
+  children_(children) {}
+
+ShadowNode::ShadowNode(
+  SharedShadowNode shadowNode,
+  SharedProps props,
+  SharedShadowNodeSharedList children
+):
+  tag_(shadowNode->tag_),
+  instanceHandle_(shadowNode->instanceHandle_),
+  props_(props ? props : shadowNode->props_),
+  children_(children ? children : shadowNode->children_) {}
+
+#pragma mark - Getters
+
+SharedShadowNodeSharedList ShadowNode::getChildren() const {
+  return children_;
+}
+
+SharedProps ShadowNode::getProps() const {
+  return props_;
+}
+
+Tag ShadowNode::getTag() const {
+  return tag_;
+}
+
+#pragma mark - Mutating Methods
+
+void ShadowNode::sealRecursive() const {
+  if (getSealed()) {
+    return;
+  }
+
+  seal();
+
+  props_->seal();
+
+  for (auto child : *children_) {
+    child->sealRecursive();
+  }
+}
+
+void ShadowNode::appendChild(const SharedShadowNode &child) {
+  ensureUnsealed();
+
+  // We cannot mutate `children_` in place here because it is a *shared*
+  // data structure which means other `ShadowNodes` might refer to its old value.
+  // So, we have to clone this and only then mutate.
+  auto nonConstChildrenCopy = SharedShadowNodeList(*children_);
+  nonConstChildrenCopy.push_back(child);
+  children_ = std::make_shared<const SharedShadowNodeList>(nonConstChildrenCopy);
+}
+
+void ShadowNode::replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild) {
+  ensureUnsealed();
+
+  // We cannot mutate `children_` in place here because it is a *shared*
+  // data structure which means other `ShadowNodes` might refer to its old value.
+  // So, we have to clone this and only then mutate.
+  auto nonConstChildrenCopy = SharedShadowNodeList(*children_);
+  std::replace(nonConstChildrenCopy.begin(), nonConstChildrenCopy.end(), oldChild, newChild);
+  children_ = std::make_shared<const SharedShadowNodeList>(nonConstChildrenCopy);
+}
+
+#pragma mark - DebugStringConvertible
+
+std::string ShadowNode::getDebugName() const {
+  return getComponentName();
+}
+
+std::string ShadowNode::getDebugValue() const {
+  return getSealed() ? "sealed" : "";
+}
+
+SharedDebugStringConvertibleList ShadowNode::getDebugChildren() const {
+  SharedDebugStringConvertibleList debugChildren = {};
+
+  for (auto child : *children_) {
+    auto debugChild = std::dynamic_pointer_cast<const DebugStringConvertible>(child);
+    if (debugChild) {
+      debugChildren.push_back(debugChild);
+    }
+  }
+
+  return debugChildren;
+}
+
+SharedDebugStringConvertibleList ShadowNode::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+
+  list.push_back(std::make_shared<DebugStringConvertibleItem>("tag", std::to_string(tag_)));
+
+  if (instanceHandle_) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("handle", std::to_string((size_t)instanceHandle_)));
+  }
+
+  SharedDebugStringConvertibleList propsList = props_->getDebugProps();
+  std::move(propsList.begin(), propsList.end(), std::back_inserter(list));
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
new file mode 100644
index 000000000000..f341d6f12e66
--- /dev/null
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -0,0 +1,80 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <string>
+#include <vector>
+
+#include <fabric/core/Props.h>
+#include <fabric/core/Sealable.h>
+#include <fabric/core/ReactPrimitives.h>
+#include <fabric/debug/DebugStringConvertible.h>
+
+namespace facebook {
+namespace react {
+
+class ShadowNode;
+
+using SharedShadowNode = std::shared_ptr<const ShadowNode>;
+using SharedShadowNodeList = std::vector<std::shared_ptr<const ShadowNode>>;
+using SharedShadowNodeSharedList = std::shared_ptr<const SharedShadowNodeList>;
+using SharedShadowNodeUnsharedList = std::shared_ptr<SharedShadowNodeList>;
+
+class ShadowNode:
+  public virtual Sealable,
+  public virtual DebugStringConvertible {
+public:
+  static SharedShadowNodeSharedList emptySharedShadowNodeSharedList();
+
+#pragma mark - Constructors
+
+  ShadowNode(
+    Tag tag,
+    InstanceHandle instanceHandle,
+    SharedProps props = SharedProps(),
+    SharedShadowNodeSharedList children = SharedShadowNodeSharedList()
+  );
+
+  ShadowNode(
+    SharedShadowNode shadowNode,
+    SharedProps props = nullptr,
+    SharedShadowNodeSharedList children = nullptr
+  );
+
+#pragma mark - Getters
+
+  virtual ComponentHandle getComponentHandle() const = 0;
+  virtual ComponentName getComponentName() const = 0;
+
+  SharedShadowNodeSharedList getChildren() const;
+  SharedProps getProps() const;
+  Tag getTag() const;
+
+#pragma mark - Mutating Methods
+
+  void sealRecursive() const;
+
+  void appendChild(const SharedShadowNode &child);
+  void replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild);
+
+#pragma mark - DebugStringConvertible
+
+  std::string getDebugName() const override;
+  std::string getDebugValue() const override;
+  SharedDebugStringConvertibleList getDebugChildren() const override;
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+protected:
+  Tag tag_;
+  InstanceHandle instanceHandle_;
+  SharedProps props_;
+  SharedShadowNodeSharedList children_;
+};
+
+} // namespace react
+} // namespace facebook

From 608d1fb5909a3c6574b47ecda77b7647ba5776a5 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:13 -0700
Subject: [PATCH 0052/1109] `fabric/graphics` module: all about graphics

Summary: `fabric/graphics` provides graphics primitives; the implementation should be platform-specific eventually.

Reviewed By: fkgozali

Differential Revision: D7230675

fbshipit-source-id: ff05d2673072fad5ee6f331f0155561969e1a8b6
---
 ReactCommon/fabric/core/BUCK                  |  1 +
 ReactCommon/fabric/graphics/BUCK              | 50 ++++++++++++++++
 ReactCommon/fabric/graphics/Color.cpp         | 39 ++++++++++++
 ReactCommon/fabric/graphics/Color.h           | 30 ++++++++++
 ReactCommon/fabric/graphics/Geometry.h        | 60 +++++++++++++++++++
 .../graphics/graphicValuesConversions.cpp     | 51 ++++++++++++++++
 .../graphics/graphicValuesConversions.h       | 20 +++++++
 7 files changed, 251 insertions(+)
 create mode 100644 ReactCommon/fabric/graphics/BUCK
 create mode 100644 ReactCommon/fabric/graphics/Color.cpp
 create mode 100644 ReactCommon/fabric/graphics/Color.h
 create mode 100644 ReactCommon/fabric/graphics/Geometry.h
 create mode 100644 ReactCommon/fabric/graphics/graphicValuesConversions.cpp
 create mode 100644 ReactCommon/fabric/graphics/graphicValuesConversions.h

diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index ec92dc42c2c2..977460fc5984 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -48,5 +48,6 @@ rn_xplat_cxx_library(
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
         react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/graphics:graphics"),
     ],
 )
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
new file mode 100644
index 000000000000..e1a020d730b4
--- /dev/null
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -0,0 +1,50 @@
+load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+
+rn_xplat_cxx_library(
+    name = "graphics",
+    srcs = glob(
+        [
+            "**/*.cpp",
+        ],
+    ),
+    headers = glob(
+        [
+            "**/*.h",
+        ],
+    ),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/graphics",
+    ),
+    compiler_flags = [
+        "-std=c++14",
+        "-Wall",
+        "-fexceptions",
+        "-frtti",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    force_static = True,
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+    ],
+)
diff --git a/ReactCommon/fabric/graphics/Color.cpp b/ReactCommon/fabric/graphics/Color.cpp
new file mode 100644
index 000000000000..ba6c897b4932
--- /dev/null
+++ b/ReactCommon/fabric/graphics/Color.cpp
@@ -0,0 +1,39 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "Color.h"
+#include <CoreGraphics/CoreGraphics.h>
+#include <CoreGraphics/CGColor.h>
+#include <cassert>
+
+namespace facebook {
+namespace react {
+
+SharedColor colorFromComponents(float red, float green, float blue, float alpha) {
+  const CGFloat components[] = {red, green, blue, alpha};
+  CGColorRef color = CGColorCreate(
+    CGColorSpaceCreateDeviceRGB(),
+    components
+  );
+
+  return SharedColor(color, CFRelease);
+}
+
+ColorComponents colorComponentsFromColor(SharedColor color) {
+  int numberOfComponents = CGColorGetNumberOfComponents(color.get());
+  assert(numberOfComponents == 4);
+  const CGFloat *components = CGColorGetComponents(color.get());
+  return ColorComponents {
+    (float)components[0],
+    (float)components[1],
+    (float)components[2],
+    (float)components[3]
+  };
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/Color.h b/ReactCommon/fabric/graphics/Color.h
new file mode 100644
index 000000000000..0a84e7b3a970
--- /dev/null
+++ b/ReactCommon/fabric/graphics/Color.h
@@ -0,0 +1,30 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <CoreGraphics/CoreGraphics.h>
+#include <memory>
+
+namespace facebook {
+namespace react {
+
+using Color = CGColor;
+using SharedColor = std::shared_ptr<Color>;
+
+struct ColorComponents {
+  float red {0};
+  float green {0};
+  float blue {0};
+  float alpha {0};
+};
+
+SharedColor colorFromComponents(float red, float green, float blue, float alpha);
+ColorComponents colorComponentsFromColor(SharedColor color);
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
new file mode 100644
index 000000000000..915cc3b76831
--- /dev/null
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -0,0 +1,60 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+namespace facebook {
+namespace react {
+
+/*
+ * Exact type of float numbers which ideally should match a type behing
+ * platform- and chip-architecture-specific float type (something like
+ * CGFloat on iOS).
+ */
+using Float = double;
+
+/*
+ * Point
+ */
+struct Point {
+  Float x {0};
+  Float y {0};
+
+  Point& operator += (const Point& rhs) {
+    x += rhs.x;
+    y += rhs.y;
+    return *this;
+  }
+
+  friend Point operator + (Point lhs, const Point& rhs) {
+    return lhs += rhs;
+  }
+};
+
+/*
+ * Size
+ */
+struct Size {
+  Float width {0};
+  Float height {0};
+};
+
+/*
+ * Rect: Point and Size
+ */
+struct Rect {
+  Point origin {0, 0};
+  Size size {0, 0};
+};
+
+/*
+ * EdgeInsets
+ */
+struct EdgeInsets {
+  Float top {0};
+  Float left {0};
+  Float bottom {0};
+  Float right {0};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp b/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
new file mode 100644
index 000000000000..cfd80a4a1149
--- /dev/null
+++ b/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
@@ -0,0 +1,51 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "graphicValuesConversions.h"
+
+namespace facebook {
+namespace react {
+
+SharedColor colorFromDynamic(folly::dynamic value) {
+  float red;
+  float green;
+  float blue;
+  float alpha;
+
+  if (value.isNumber()) {
+    auto argb = value.asInt();
+    float ratio = 256;
+    alpha = ((argb >> 24) & 0xFF) / ratio;
+    red = ((argb >> 16) & 0xFF) / ratio;
+    green = ((argb >> 8) & 0xFF) / ratio;
+    blue = (argb & 0xFF) / ratio;
+  } else if (value.isArray()) {
+    auto size = value.size();
+    assert(size == 3 || size == 4);
+    red = value[0].asDouble();
+    green = value[1].asDouble();
+    blue = value[2].asDouble();
+    alpha = size == 4 ? value[3].asDouble() : 1.0;
+  } else {
+    abort();
+  }
+
+  return colorFromComponents(red, green, blue, alpha);
+}
+
+std::string colorNameFromColor(SharedColor value) {
+  ColorComponents components = colorComponentsFromColor(value);
+  const float ratio = 256;
+  return "rgba(" +
+    folly::to<std::string>(round(components.red * ratio)) + ", " +
+    folly::to<std::string>(round(components.green * ratio)) + ", " +
+    folly::to<std::string>(round(components.blue * ratio)) + ", " +
+    folly::to<std::string>(round(components.alpha * ratio)) + ")";
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.h b/ReactCommon/fabric/graphics/graphicValuesConversions.h
new file mode 100644
index 000000000000..8ee9e2799d35
--- /dev/null
+++ b/ReactCommon/fabric/graphics/graphicValuesConversions.h
@@ -0,0 +1,20 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <folly/dynamic.h>
+#include <fabric/graphics/Color.h>
+
+namespace facebook {
+namespace react {
+
+SharedColor colorFromDynamic(folly::dynamic value);
+std::string colorNameFromColor(SharedColor value);
+
+} // namespace react
+} // namespace facebook

From 840638c441b78ed1e97bded5ba9a39c0410bcc80 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:16 -0700
Subject: [PATCH 0053/1109] Introducing `ComponentDescriptor`

Summary:
Abstract class and default template implementation.
`ComponentDescriptor`s define basic logic of managing (creation, cloning, applying props) ShadowNode of particular type.

Reviewed By: fkgozali

Differential Revision: D7230671

fbshipit-source-id: c32636f4db0716b55a1637f61c4f1872fc52cea7
---
 ReactCommon/fabric/core/BUCK                  |  1 +
 .../componentdescriptor/ComponentDescriptor.h | 71 +++++++++++++++++++
 .../ConcreteComponentDescriptor.h             | 66 +++++++++++++++++
 .../fabric/core/shadownode/ShadowNode.cpp     |  2 +
 .../fabric/core/shadownode/ShadowNode.h       |  2 +
 5 files changed, 142 insertions(+)
 create mode 100644 ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h

diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 977460fc5984..4e062a8bccb4 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -23,6 +23,7 @@ rn_xplat_cxx_library(
     exported_headers = subdir_glob(
         [
             ("primitives", "*.h"),
+            ("componentdescriptor", "*.h"),
             ("shadownode", "*.h"),
         ],
         prefix = "fabric/core",
diff --git a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
new file mode 100644
index 000000000000..975900c91cf5
--- /dev/null
+++ b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
@@ -0,0 +1,71 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ShadowNode.h>
+#include <fabric/core/Props.h>
+
+namespace facebook {
+namespace react {
+
+class ComponentDescriptor;
+
+using SharedComponentDescriptor = std::shared_ptr<ComponentDescriptor>;
+
+/*
+ * Abstract class defining an interface of `ComponentDescriptor`.
+ * `ComponentDescriptor` represents particular `ShadowNode` type and
+ * defines (customizes) basic operations with particular kind of
+ * `ShadowNode`s (such as creating, cloning, props and children managing).
+ */
+class ComponentDescriptor {
+public:
+
+  /*
+   * Returns `componentHandle` associated with particular kind of components.
+   * All `ShadowNode`s of this type must return same `componentHandle`.
+   */
+  virtual ComponentHandle getComponentHandle() const = 0;
+
+  /*
+   * Returns component's name.
+   * React uses a `name` to refer to particular kind of components in
+   * `create` requests.
+   */
+  virtual ComponentName getComponentName() const = 0;
+
+  /*
+   * Creates a new `ShadowNode` of a particular type.
+   */
+  virtual SharedShadowNode createShadowNode(
+    const Tag &tag,
+    const Tag &rootTag,
+    const InstanceHandle &instanceHandle,
+    const RawProps &rawProps
+  ) const = 0;
+
+  /*
+   * Clones a `ShadowNode` with optionally new `props` and/or `children`.
+   */
+  virtual SharedShadowNode cloneShadowNode(
+    const SharedShadowNode &shadowNode,
+    const SharedRawProps &rawProps = nullptr,
+    const SharedShadowNodeSharedList &children = nullptr
+  ) const = 0;
+
+  /*
+   * Appends (by mutating) a given `childShadowNode` to `parentShadowNode`.
+   */
+  virtual void appendChild(
+    const SharedShadowNode &parentShadowNode,
+    const SharedShadowNode &childShadowNode
+  ) const = 0;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
new file mode 100644
index 000000000000..0a521bd49994
--- /dev/null
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -0,0 +1,66 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ShadowNode.h>
+#include <fabric/core/Props.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Default template-based implementation of ComponentDescriptor.
+ * Use your `ShadowNode` type as a template argument and override any methods
+ * if necessary.
+ */
+template <typename ShadowNodeT>
+class ConcreteComponentDescriptor: public ComponentDescriptor {
+  static_assert(std::is_base_of<ShadowNode, ShadowNodeT>::value, "ShadowNodeT must be a descendant of ShadowNode");
+
+  using SharedShadowNodeT = std::shared_ptr<const ShadowNodeT>;
+  using SharedConcreteProps = typename ShadowNodeT::SharedConcreteProps;
+
+public:
+  ComponentHandle getComponentHandle() const override {
+    return typeid(ShadowNodeT).hash_code();
+  }
+
+  SharedShadowNode createShadowNode(
+    const Tag &tag,
+    const Tag &rootTag,
+    const InstanceHandle &instanceHandle,
+    const RawProps &rawProps
+  ) const override {
+    auto props = ShadowNodeT::Props(rawProps);
+    return std::make_shared<ShadowNodeT>(tag, rootTag, instanceHandle, props);
+  }
+
+  SharedShadowNode cloneShadowNode(
+    const SharedShadowNode &shadowNode,
+    const SharedRawProps &rawProps = nullptr,
+    const SharedShadowNodeSharedList &children = nullptr
+  ) const override {
+    const SharedConcreteProps props = rawProps ? ShadowNodeT::Props(*rawProps, shadowNode->getProps()) : nullptr;
+    return std::make_shared<ShadowNodeT>(std::static_pointer_cast<const ShadowNodeT>(shadowNode), props, children);
+  }
+
+  void appendChild(
+    const SharedShadowNode &parentShadowNode,
+    const SharedShadowNode &childShadowNode
+  ) const override {
+    auto concreteParentShadowNode = std::static_pointer_cast<const ShadowNodeT>(parentShadowNode);
+    auto concreteNonConstParentShadowNode = std::const_pointer_cast<ShadowNodeT>(concreteParentShadowNode);
+    concreteNonConstParentShadowNode->appendChild(childShadowNode);
+  }
+
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 1f2777429d18..d095a882186d 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -22,11 +22,13 @@ SharedShadowNodeSharedList ShadowNode::emptySharedShadowNodeSharedList() {
 
 ShadowNode::ShadowNode(
   Tag tag,
+  Tag rootTag,
   InstanceHandle instanceHandle,
   SharedProps props,
   SharedShadowNodeSharedList children
 ):
   tag_(tag),
+  rootTag_(rootTag),
   instanceHandle_(instanceHandle),
   props_(props),
   children_(children) {}
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index f341d6f12e66..0f2fab928056 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -35,6 +35,7 @@ class ShadowNode:
 
   ShadowNode(
     Tag tag,
+    Tag rootTag,
     InstanceHandle instanceHandle,
     SharedProps props = SharedProps(),
     SharedShadowNodeSharedList children = SharedShadowNodeSharedList()
@@ -71,6 +72,7 @@ class ShadowNode:
 
 protected:
   Tag tag_;
+  Tag rootTag_;
   InstanceHandle instanceHandle_;
   SharedProps props_;
   SharedShadowNodeSharedList children_;

From 811d5bfc73423e6ec2a980c58095c16272a1c5cb Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:20 -0700
Subject: [PATCH 0054/1109] Introducing LayoutableShadowNode

Summary: LayoutableShadowNode defines a unified interface (and set of primitives) essential for laying out shadow nodes.

Reviewed By: fkgozali

Differential Revision: D7230668

fbshipit-source-id: d8c1772d4c3bd1f87c41f7240a39aecebf3696ae
---
 ReactCommon/fabric/core/BUCK                  |   1 +
 .../fabric/core/layout/LayoutConstraints.h    |  26 ++++
 .../fabric/core/layout/LayoutContext.h        |  36 ++++++
 .../fabric/core/layout/LayoutMetrics.h        |  28 +++++
 .../fabric/core/layout/LayoutPrimitives.h     |  33 +++++
 .../core/layout/LayoutableShadowNode.cpp      |  97 +++++++++++++++
 .../fabric/core/layout/LayoutableShadowNode.h | 113 ++++++++++++++++++
 7 files changed, 334 insertions(+)
 create mode 100644 ReactCommon/fabric/core/layout/LayoutConstraints.h
 create mode 100644 ReactCommon/fabric/core/layout/LayoutContext.h
 create mode 100644 ReactCommon/fabric/core/layout/LayoutMetrics.h
 create mode 100644 ReactCommon/fabric/core/layout/LayoutPrimitives.h
 create mode 100644 ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
 create mode 100644 ReactCommon/fabric/core/layout/LayoutableShadowNode.h

diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 4e062a8bccb4..932e86410f1e 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -24,6 +24,7 @@ rn_xplat_cxx_library(
         [
             ("primitives", "*.h"),
             ("componentdescriptor", "*.h"),
+            ("layout", "*.h"),
             ("shadownode", "*.h"),
         ],
         prefix = "fabric/core",
diff --git a/ReactCommon/fabric/core/layout/LayoutConstraints.h b/ReactCommon/fabric/core/layout/LayoutConstraints.h
new file mode 100644
index 000000000000..432a8aad324d
--- /dev/null
+++ b/ReactCommon/fabric/core/layout/LayoutConstraints.h
@@ -0,0 +1,26 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/LayoutPrimitives.h>
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Unified layout constraints for measuring.
+ */
+struct LayoutConstraints {
+  Size minimumSize;
+  Size maximumSize;
+  LayoutDirection layoutDirection;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/layout/LayoutContext.h b/ReactCommon/fabric/core/layout/LayoutContext.h
new file mode 100644
index 000000000000..6f8d49ff4a18
--- /dev/null
+++ b/ReactCommon/fabric/core/layout/LayoutContext.h
@@ -0,0 +1,36 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <unordered_set>
+
+#include <fabric/core/LayoutableShadowNode.h>
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * LayoutContext: Additional contextual information useful for particular
+ * layout approaches.
+ */
+struct LayoutContext {
+  /*
+   * Compound absolute position of the node relative to the root node.
+   */
+  Point absolutePosition {0, 0};
+
+  /*
+   * Collection of shadow nodes which were chanded during the layout pass,
+   * and which associated views might need to be updated.
+   */
+  std::shared_ptr<std::unordered_set<SharedLayoutableShadowNode>> affectedShadowNodes {nullptr};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/layout/LayoutMetrics.h b/ReactCommon/fabric/core/layout/LayoutMetrics.h
new file mode 100644
index 000000000000..d34d7d9f9780
--- /dev/null
+++ b/ReactCommon/fabric/core/layout/LayoutMetrics.h
@@ -0,0 +1,28 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/LayoutPrimitives.h>
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Describes results of layout process for partucular shadow node.
+ */
+struct LayoutMetrics {
+  Rect frame;
+  EdgeInsets contentInsets {0};
+  EdgeInsets borderWidth {0};
+  DisplayType displayType {Flex};
+  LayoutDirection layoutDirection {Undefined};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/layout/LayoutPrimitives.h b/ReactCommon/fabric/core/layout/LayoutPrimitives.h
new file mode 100644
index 000000000000..0036e134e887
--- /dev/null
+++ b/ReactCommon/fabric/core/layout/LayoutPrimitives.h
@@ -0,0 +1,33 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+namespace facebook {
+namespace react {
+
+/*
+ * Defines visibility of the shadow node and partucular layout
+ * engine which should be used for laying out the node.
+ */
+enum DisplayType {
+  None,
+  Flex,
+  Inline,
+};
+
+/*
+ * User interface layout direction.
+ */
+enum LayoutDirection {
+  Undefined,
+  LeftToRight,
+  RightToLeft,
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
new file mode 100644
index 000000000000..3f0b50ae747a
--- /dev/null
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -0,0 +1,97 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "LayoutableShadowNode.h"
+
+#include <fabric/core/LayoutConstraints.h>
+#include <fabric/core/LayoutContext.h>
+#include <fabric/core/LayoutMetrics.h>
+
+namespace facebook {
+namespace react {
+
+LayoutMetrics LayoutableShadowNode::getLayoutMetrics() const {
+  return layoutMetrics_;
+}
+
+bool LayoutableShadowNode::setLayoutMetrics(LayoutMetrics layoutMetrics) {
+  layoutMetrics_ = layoutMetrics;
+  return true;
+}
+
+void LayoutableShadowNode::cleanLayout() {
+  isLayoutClean_ = true;
+}
+
+void LayoutableShadowNode::dirtyLayout() {
+  isLayoutClean_ = false;
+}
+
+bool LayoutableShadowNode::getIsLayoutClean() const {
+  return isLayoutClean_;
+}
+
+bool LayoutableShadowNode::getHasNewLayout() const {
+  return hasNewLayout_;
+};
+
+void LayoutableShadowNode::setHasNewLayout(bool hasNewLayout) {
+  hasNewLayout_ = hasNewLayout;
+}
+
+Size LayoutableShadowNode::measure(LayoutConstraints layoutConstraints) const {
+  return Size();
+}
+
+Float LayoutableShadowNode::firstBaseline(Size size) const {
+  return 0;
+}
+
+Float LayoutableShadowNode::lastBaseline(Size size) const {
+  return 0;
+}
+
+void LayoutableShadowNode::layout(LayoutContext layoutContext) {
+  ensureUnsealed();
+
+  layoutChildren(layoutContext);
+
+  for (auto child : getChildren()) {
+    if (!child->getHasNewLayout()) {
+      continue;
+    }
+
+    // The assumption:
+    // All `sealed` children were replaced with not-yet-sealed clones
+    // somewhere in `layoutChildren`.
+    auto nonConstChild = std::const_pointer_cast<LayoutableShadowNode>(child);
+
+    nonConstChild->setHasNewLayout(false);
+
+    const LayoutMetrics childLayoutMetrics = nonConstChild->getLayoutMetrics();
+    if (childLayoutMetrics.displayType == None) {
+      continue;
+    }
+
+    LayoutContext childLayoutContext = LayoutContext(layoutContext);
+    childLayoutContext.absolutePosition += childLayoutMetrics.frame.origin;
+
+    nonConstChild->layout(layoutContext);
+  }
+}
+
+void LayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
+  ensureUnsealed();
+  // Default implementation does nothing.
+}
+
+SharedLayoutableShadowNode LayoutableShadowNode::cloneAndReplaceChild(const SharedLayoutableShadowNode &child) {
+  return child;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
new file mode 100644
index 000000000000..e59df8bc9ab4
--- /dev/null
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
@@ -0,0 +1,113 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <array>
+#include <cmath>
+#include <vector>
+
+#include <fabric/core/LayoutMetrics.h>
+#include <fabric/core/Sealable.h>
+
+namespace facebook {
+namespace react {
+
+struct LayoutConstraints;
+struct LayoutContext;
+
+class LayoutableShadowNode;
+using SharedLayoutableShadowNode = std::shared_ptr<const LayoutableShadowNode>;
+using SharedLayoutableShadowNodeList = std::vector<const SharedLayoutableShadowNode>;
+using LayoutableShadowNodeIterator = std::iterator<std::input_iterator_tag, const SharedLayoutableShadowNode>;
+
+/*
+ * Describes all sufficient layout API (in approach-agnostic way)
+ * which makes a concurrent layout possible.
+ */
+class LayoutableShadowNode:
+  public virtual Sealable {
+
+public:
+
+  /*
+   * Measures the node (and node content, propbably recursivly) with
+   * given constrains and relying on possible layout.
+   * Default implementation returns zero size.
+   */
+  virtual Size measure(LayoutConstraints layoutConstraints) const;
+
+  /*
+   * Computes layout recusively.
+   * Additional environmental constraints might be provided via `layoutContext`
+   * argument.
+   * Default implementation basically calls `layoutChildren()` and then `layout()`
+   * (recursively), and provides some obvious performance optimization.
+   */
+  virtual void layout(LayoutContext layoutContext);
+
+  /*
+   * Returns layout metrics computed during previous layout pass.
+   */
+  virtual LayoutMetrics getLayoutMetrics() const;
+
+protected:
+
+  /*
+   * Clean or Dirty layout state:
+   * Indicates whether all nodes (and possibly their subtrees) along the path
+   * to the root node should be re-layouted.
+   */
+  virtual void cleanLayout();
+  virtual void dirtyLayout();
+  virtual bool getIsLayoutClean() const;
+
+  /*
+   * Indicates does the shadow node (or any descendand node of the node)
+   * get a new layout metrics during a previous layout pass.
+   */
+  virtual void setHasNewLayout(bool hasNewLayout);
+  virtual bool getHasNewLayout() const;
+
+  /*
+   * Applies layout for all children;
+   * does not call anything in recusive manner *by desing*.
+   */
+  virtual void layoutChildren(LayoutContext layoutContext);
+
+  /*
+   * Unifed methods to access text layout metrics.
+   */
+  virtual Float firstBaseline(Size size) const;
+  virtual Float lastBaseline(Size size) const;
+
+  /*
+   * Returns layoutable children to interate on.
+   */
+  virtual SharedLayoutableShadowNodeList getChildren() const = 0;
+
+  /*
+   * In case layout algorithm needs to mutate this (probably sealed) node,
+   * it has to clone and replace it in the hierarchy before to do so.
+   * Default implementation does nothing and returns `child`.
+   */
+  virtual SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child);
+
+  /*
+   * Sets layout metrics for the shadow node.
+   * Returns true if the metrics are different from previous ones.
+   */
+  virtual bool setLayoutMetrics(LayoutMetrics layoutMetrics);
+
+private:
+  LayoutMetrics layoutMetrics_ {};
+  bool hasNewLayout_ {false};
+  bool isLayoutClean_ {false};
+};
+
+} // namespace react
+} // namespace facebook

From 6b0960cbdbb3b6517e4b4f2d65f6c3bd2f5d6545 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:23 -0700
Subject: [PATCH 0055/1109] Introducing `ConcreteShadowNode`

Summary: ConcreteShadowNode defines a template which connects typed Props and typed ShadowNode.

Reviewed By: fkgozali

Differential Revision: D7230667

fbshipit-source-id: be28314d6846d69960e921da852f01232951f965
---
 .../core/shadownode/ConcreteShadowNode.h      | 86 +++++++++++++++++++
 1 file changed, 86 insertions(+)
 create mode 100644 ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h

diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
new file mode 100644
index 000000000000..c9f2741762c5
--- /dev/null
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -0,0 +1,86 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/Props.h>
+#include <fabric/core/ShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Base templace class for all `ShadowNode`s which connects exact `ShadowNode`
+ * type with exact `Props` type.
+ * `ConcreteShadowNode` is a default implementation of `ShadowNode` interface
+ * with many handy features.
+ */
+template <typename PropsT>
+class ConcreteShadowNode: public ShadowNode {
+  static_assert(std::is_base_of<Props, PropsT>::value, "PropsT must be a descendant of Props");
+
+public:
+  using ConcreteProps = PropsT;
+  using SharedConcreteProps = std::shared_ptr<const PropsT>;
+  using SharedConcreteShadowNode = std::shared_ptr<const ConcreteShadowNode>;
+
+  static const SharedConcreteProps Props(const RawProps &rawProps, const SharedProps &baseProps = nullptr) {
+    if (!baseProps) {
+      auto props = std::make_shared<PropsT>();
+      props->apply(rawProps);
+      return props;
+    }
+
+    auto concreteBaseProps = std::dynamic_pointer_cast<const PropsT>(baseProps);
+    auto props = std::make_shared<PropsT>(*concreteBaseProps);
+    props->apply(rawProps);
+    return props;
+  }
+
+  static const SharedConcreteProps defaultSharedProps() {
+    static const SharedConcreteProps defaultSharedProps = std::make_shared<PropsT>();
+    return defaultSharedProps;
+  }
+
+  ConcreteShadowNode(
+    const Tag &tag,
+    const Tag &rootTag,
+    const InstanceHandle &instanceHandle,
+    const SharedConcreteProps &props = ConcreteShadowNode::defaultSharedProps(),
+    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList()
+  ):
+    ShadowNode(
+      tag,
+      rootTag,
+      instanceHandle,
+      (SharedProps)props,
+      children
+    ) {};
+
+  ConcreteShadowNode(
+    const SharedConcreteShadowNode &shadowNode,
+    const SharedProps &props = nullptr,
+    const SharedShadowNodeSharedList &children = nullptr
+  ):
+    ShadowNode(
+      shadowNode,
+      (SharedProps)props,
+      children
+    ) {}
+
+  virtual ComponentHandle getComponentHandle() const {
+    return typeid(*this).hash_code();
+  }
+
+  const SharedConcreteProps &getProps() const {
+    return std::static_pointer_cast<const PropsT>(props_);
+  }
+
+};
+
+} // namespace react
+} // namespace facebook

From 965e60b05aee4782d0da85baaaabd3e387bb06ee Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:25 -0700
Subject: [PATCH 0056/1109] `fabric/view` module

Summary: Defines `<View>`: Yoga-powered, Accessible and styleable component.

Reviewed By: fkgozali

Differential Revision: D7230673

fbshipit-source-id: 08a1d8626c0b41260fafdca938d4fe9489b1b793
---
 ReactCommon/fabric/BUCK                       |   3 +-
 ReactCommon/fabric/core/BUCK                  |   2 +-
 ReactCommon/fabric/graphics/Geometry.h        |  12 +-
 ReactCommon/fabric/view/BUCK                  |  52 +++
 .../fabric/view/ViewComponentDescriptor.h     |  24 ++
 ReactCommon/fabric/view/ViewProps.cpp         |  75 +++++
 ReactCommon/fabric/view/ViewProps.h           |  48 +++
 ReactCommon/fabric/view/ViewShadowNode.cpp    | 104 ++++++
 ReactCommon/fabric/view/ViewShadowNode.h      |  63 ++++
 .../accessibility/AccessibilityPrimitives.h   |  38 +++
 .../view/accessibility/AccessibilityProps.cpp |  31 ++
 .../view/accessibility/AccessibilityProps.h   |  42 +++
 .../accessibility/AccessibleShadowNode.cpp    |  29 ++
 .../view/accessibility/AccessibleShadowNode.h |  41 +++
 .../accessibilityValuesConversions.cpp        |  23 ++
 .../accessibilityValuesConversions.h          |  20 ++
 .../view/yoga/YogaLayoutableShadowNode.cpp    | 228 +++++++++++++
 .../view/yoga/YogaLayoutableShadowNode.h      |  93 ++++++
 .../fabric/view/yoga/YogaStylableProps.cpp    | 148 +++++++++
 .../fabric/view/yoga/YogaStylableProps.h      |  39 +++
 .../view/yoga/yogaValuesConversions.cpp       | 303 ++++++++++++++++++
 .../fabric/view/yoga/yogaValuesConversions.h  |  57 ++++
 22 files changed, 1470 insertions(+), 5 deletions(-)
 create mode 100644 ReactCommon/fabric/view/BUCK
 create mode 100644 ReactCommon/fabric/view/ViewComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/view/ViewProps.cpp
 create mode 100644 ReactCommon/fabric/view/ViewProps.h
 create mode 100644 ReactCommon/fabric/view/ViewShadowNode.cpp
 create mode 100644 ReactCommon/fabric/view/ViewShadowNode.h
 create mode 100644 ReactCommon/fabric/view/accessibility/AccessibilityPrimitives.h
 create mode 100644 ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp
 create mode 100644 ReactCommon/fabric/view/accessibility/AccessibilityProps.h
 create mode 100644 ReactCommon/fabric/view/accessibility/AccessibleShadowNode.cpp
 create mode 100644 ReactCommon/fabric/view/accessibility/AccessibleShadowNode.h
 create mode 100644 ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.cpp
 create mode 100644 ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.h
 create mode 100644 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
 create mode 100644 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
 create mode 100644 ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
 create mode 100644 ReactCommon/fabric/view/yoga/YogaStylableProps.h
 create mode 100644 ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
 create mode 100644 ReactCommon/fabric/view/yoga/yogaValuesConversions.h

diff --git a/ReactCommon/fabric/BUCK b/ReactCommon/fabric/BUCK
index 6788c76801c9..162ae5ec4230 100644
--- a/ReactCommon/fabric/BUCK
+++ b/ReactCommon/fabric/BUCK
@@ -1,4 +1,4 @@
-load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
+load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
 
 APPLE_COMPILER_FLAGS = []
@@ -40,5 +40,6 @@ rn_xplat_cxx_library(
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
         react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/view:view"),
     ],
 )
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 932e86410f1e..f566a70f6ee7 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -1,4 +1,4 @@
-load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
+load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
 
 APPLE_COMPILER_FLAGS = []
diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index 915cc3b76831..dcaf88f43f54 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -2,15 +2,21 @@
 
 #pragma once
 
+#include <CoreGraphics/CGBase.h>
+
 namespace facebook {
 namespace react {
 
 /*
  * Exact type of float numbers which ideally should match a type behing
- * platform- and chip-architecture-specific float type (something like
- * CGFloat on iOS).
+ * platform- and chip-architecture-specific float type.
+ */
+using Float = CGFloat;
+
+/*
+ * Large positive number signifies that the `Float` values is `undefined`.
  */
-using Float = double;
+const Float kFloatUndefined = CGFLOAT_MAX;
 
 /*
  * Point
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
new file mode 100644
index 000000000000..3db0dd82bf72
--- /dev/null
+++ b/ReactCommon/fabric/view/BUCK
@@ -0,0 +1,52 @@
+load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "react_native_xplat_target")
+
+CXX_LIBRARY_COMPILER_FLAGS = [
+    "-std=c++14",
+    "-Wall",
+]
+
+rn_xplat_cxx_library(
+    name = "view",
+    srcs = glob(
+        [
+            "**/*.cpp",
+        ],
+    ),
+    headers = glob(
+        [
+            "**/*.h",
+        ],
+    ),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+            ("accessibility", "*.h"),
+            ("yoga", "*.h"),
+        ],
+        prefix = "fabric/view",
+    ),
+    compiler_flags = CXX_LIBRARY_COMPILER_FLAGS + [
+        "-fexceptions",
+        "-frtti",
+    ],
+    force_static = True,
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+    ],
+)
diff --git a/ReactCommon/fabric/view/ViewComponentDescriptor.h b/ReactCommon/fabric/view/ViewComponentDescriptor.h
new file mode 100644
index 000000000000..1db26dc3b5b7
--- /dev/null
+++ b/ReactCommon/fabric/view/ViewComponentDescriptor.h
@@ -0,0 +1,24 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ConcreteComponentDescriptor.h>
+#include <fabric/view/ViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class ViewComponentDescriptor: public ConcreteComponentDescriptor<ViewShadowNode> {
+public:
+  ComponentName getComponentName() const override {
+    return "View";
+  }
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
new file mode 100644
index 000000000000..e3f9f6fddc0d
--- /dev/null
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -0,0 +1,75 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ViewProps.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/graphics/graphicValuesConversions.h>
+
+namespace facebook {
+namespace react {
+
+void ViewProps::apply(const RawProps &rawProps) {
+  Props::apply(rawProps);
+  YogaStylableProps::apply(rawProps);
+
+  for (auto const &pair : rawProps) {
+    auto const &name = pair.first;
+    auto const &value = pair.second;
+
+    #pragma mark View Specific Properties
+
+    if (name == "zIndex") {
+      zIndex_ = value.asInt();
+      continue;
+    }
+
+    if (name == "opacity") {
+      opacity_ = value.asDouble();
+      continue;
+    }
+
+    if (name == "color") {
+      foregroundColor_ = colorFromDynamic(value);
+      continue;
+    }
+
+    if (name == "backgroundColor") {
+      backgroundColor_ = colorFromDynamic(value);
+      continue;
+    }
+  }
+}
+
+SharedDebugStringConvertibleList ViewProps::getDebugProps() const {
+  ViewProps defaultProps = {};
+
+  SharedDebugStringConvertibleList list = {};
+
+#define VIEW_PROPS_ADD_TO_SET(stringName, propertyName, accessor, convertor) \
+  if (propertyName != defaultProps.propertyName) { \
+    list.push_back(std::make_shared<DebugStringConvertibleItem>(#stringName, convertor(propertyName accessor))); \
+  }
+
+  VIEW_PROPS_ADD_TO_SET(zIndex, zIndex_, , std::to_string)
+  VIEW_PROPS_ADD_TO_SET(opacity, opacity_, , std::to_string)
+
+  VIEW_PROPS_ADD_TO_SET(backgroundColor, backgroundColor_, , colorNameFromColor)
+  VIEW_PROPS_ADD_TO_SET(foregroundColor, foregroundColor_, , colorNameFromColor)
+
+  // Accessibility Props
+  auto accessibilityPropsList = AccessibilityProps::getDebugProps();
+  std::move(accessibilityPropsList.begin(), accessibilityPropsList.end(), std::back_inserter(list));
+
+  // Yoga styles
+  list.push_back(std::make_shared<DebugStringConvertibleItem>("style", "", YogaStylableProps::getDebugProps()));
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
new file mode 100644
index 000000000000..89b20dec799f
--- /dev/null
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -0,0 +1,48 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/Props.h>
+#include <fabric/graphics/Geometry.h>
+#include <fabric/graphics/Color.h>
+#include <fabric/view/YogaStylableProps.h>
+#include <fabric/view/AccessibilityProps.h>
+
+namespace facebook {
+namespace react {
+
+class ViewProps;
+
+using SharedViewProps = std::shared_ptr<const ViewProps>;
+
+class ViewProps:
+  public Props,
+  public YogaStylableProps,
+  public AccessibilityProps {
+
+public:
+  void apply(const RawProps &rawProps) override;
+
+private:
+  int zIndex_ {0};
+  float opacity_ {1.0};
+
+  SharedColor foregroundColor_ {nullptr};
+  SharedColor backgroundColor_ {nullptr};
+
+  SharedColor shadowColor_ {nullptr};
+  Point shadowOffset_ {0, 0};
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+};
+
+} // namespace react
+} // namespace facebook
+
diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/view/ViewShadowNode.cpp
new file mode 100644
index 000000000000..7b07fec22775
--- /dev/null
+++ b/ReactCommon/fabric/view/ViewShadowNode.cpp
@@ -0,0 +1,104 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ViewShadowNode.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+namespace facebook {
+namespace react {
+
+#pragma mark - Constructors
+
+ViewShadowNode::ViewShadowNode(
+  const Tag &tag,
+  const Tag &rootTag,
+  const InstanceHandle &instanceHandle,
+  const SharedViewProps &props,
+  const SharedShadowNodeSharedList &children
+):
+  ConcreteShadowNode(
+    tag,
+    rootTag,
+    instanceHandle,
+    props,
+    children
+  ),
+  AccessibleShadowNode(
+    props
+  ),
+  YogaLayoutableShadowNode(
+    props,
+    children
+  ) {};
+
+ViewShadowNode::ViewShadowNode(
+  const SharedViewShadowNode &shadowNode,
+  const SharedViewProps &props,
+  const SharedShadowNodeSharedList &children
+):
+  ConcreteShadowNode(
+    shadowNode,
+    props,
+    children
+  ),
+  AccessibleShadowNode(
+    shadowNode,
+    props
+  ),
+  YogaLayoutableShadowNode(
+    shadowNode,
+    props,
+    children
+  ) {};
+
+ComponentName ViewShadowNode::getComponentName() const {
+  return ComponentName("View");
+}
+
+void ViewShadowNode::appendChild(const SharedShadowNode &child) {
+  ensureUnsealed();
+
+  ShadowNode::appendChild(child);
+
+  auto yogaLayoutableChild = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(child);
+  if (yogaLayoutableChild) {
+    YogaLayoutableShadowNode::appendChild(yogaLayoutableChild);
+  }
+}
+
+#pragma mark - YogaLayoutableShadowNode
+
+SharedLayoutableShadowNodeList ViewShadowNode::getChildren() const {
+  SharedLayoutableShadowNodeList sharedLayoutableShadowNodeList = {};
+  for (auto child : *children_) {
+    const SharedLayoutableShadowNode layoutableShadowNode = std::dynamic_pointer_cast<const LayoutableShadowNode>(child);
+    if (!layoutableShadowNode) {
+      continue;
+    }
+
+    sharedLayoutableShadowNodeList.push_back(layoutableShadowNode);
+  }
+
+  return sharedLayoutableShadowNodeList;
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList ViewShadowNode::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+
+  auto basePropsList = ShadowNode::getDebugProps();
+  std::move(basePropsList.begin(), basePropsList.end(), std::back_inserter(list));
+
+  list.push_back(std::make_shared<DebugStringConvertibleItem>("layout", "", YogaLayoutableShadowNode::getDebugProps()));
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/view/ViewShadowNode.h
new file mode 100644
index 000000000000..fffaaa20c98a
--- /dev/null
+++ b/ReactCommon/fabric/view/ViewShadowNode.h
@@ -0,0 +1,63 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ConcreteShadowNode.h>
+#include <fabric/core/LayoutableShadowNode.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/view/AccessibleShadowNode.h>
+#include <fabric/view/ViewProps.h>
+#include <fabric/view/YogaLayoutableShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class ViewShadowNode;
+
+using SharedViewShadowNode = std::shared_ptr<const ViewShadowNode>;
+
+class ViewShadowNode:
+  public ConcreteShadowNode<ViewProps>,
+  public AccessibleShadowNode,
+  public YogaLayoutableShadowNode {
+
+  static_assert(std::is_base_of<YogaStylableProps, ViewProps>::value, "ViewProps must be a descendant of YogaStylableProps");
+  static_assert(std::is_base_of<AccessibilityProps, ViewProps>::value, "ViewProps must be a descendant of AccessibilityProps");
+
+public:
+  ViewShadowNode(
+    const Tag &tag,
+    const Tag &rootTag,
+    const InstanceHandle &instanceHandle,
+    const SharedViewProps &props = ViewShadowNode::defaultSharedProps(),
+    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList()
+  );
+
+  ViewShadowNode(
+    const SharedViewShadowNode &shadowNode,
+    const SharedViewProps &props = nullptr,
+    const SharedShadowNodeSharedList &children = nullptr
+  );
+
+  ComponentName getComponentName() const override;
+
+  void appendChild(const SharedShadowNode &child);
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+private:
+
+#pragma mark - LayoutableShadowNode
+
+  SharedLayoutableShadowNodeList getChildren() const override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityPrimitives.h b/ReactCommon/fabric/view/accessibility/AccessibilityPrimitives.h
new file mode 100644
index 000000000000..60e73f1c485b
--- /dev/null
+++ b/ReactCommon/fabric/view/accessibility/AccessibilityPrimitives.h
@@ -0,0 +1,38 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+namespace facebook {
+namespace react {
+
+enum class AccessibilityTraits: uint32_t {
+  None = 0,
+  Button = (1 << 0),
+  Link = (1 << 1),
+  Image = (1 << 2),
+  Selected = (1 << 3),
+  PlaysSound = (1 << 4),
+  KeyboardKey = (1 << 5),
+  StaticText = (1 << 6),
+  SummaryElement = (1 << 7),
+  NotEnabled = (1 << 8),
+  UpdatesFrequently = (1 << 9),
+  SearchField = (1 << 10),
+  StartsMediaSession = (1 << 11),
+  Adjustable = (1 << 12),
+  DirectInteraction = (1 << 13),
+  CausesPageTurn = (1 << 14),
+  Header = (1 << 15),
+};
+
+constexpr enum AccessibilityTraits operator |(const enum AccessibilityTraits lhs, const enum AccessibilityTraits rhs) {
+  return (enum AccessibilityTraits)((uint32_t)lhs | (uint32_t)rhs);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp b/ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp
new file mode 100644
index 000000000000..373b4d9412c8
--- /dev/null
+++ b/ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp
@@ -0,0 +1,31 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "AccessibilityProps.h"
+
+#include "accessibilityValuesConversions.h"
+
+namespace facebook {
+namespace react {
+
+void AccessibilityProps::apply(const RawProps &rawProps) {
+  for (auto const &pair : rawProps) {
+    auto const &name = pair.first;
+    auto const &value = pair.second;
+
+#define ACCESSIBILITY_PROPERTY(stringName, variableName, accessor, convertor) \
+  if (name == #stringName) { \
+    variableName = convertor(value accessor); \
+    continue; \
+  }
+
+    ACCESSIBILITY_PROPERTY(accessibilityLabel, accessibilityLabel_, .asString(),)
+  }
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h b/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
new file mode 100644
index 000000000000..12d1dbaf0a77
--- /dev/null
+++ b/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
@@ -0,0 +1,42 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/Props.h>
+#include <fabric/core/ReactPrimitives.h>
+#include <fabric/debug/DebugStringConvertible.h>
+#include <fabric/view/AccessibilityPrimitives.h>
+
+namespace facebook {
+namespace react {
+
+class AccessibilityProps;
+
+typedef std::shared_ptr<const AccessibilityProps> SharedAccessibilityProps;
+
+class AccessibilityProps:
+  public virtual DebugStringConvertible
+{
+
+public:
+  void apply(const RawProps &rawProps);
+
+protected:
+  bool accessible_ {true};
+  std::string accessibilityActions_ {""};
+  std::string accessibilityLabel_ {""};
+  AccessibilityTraits accessibilityTraits_ {AccessibilityTraits::None};
+  bool accessibilityViewIsModal_ {false};
+  bool accessibilityElementsHidden_ {false};
+  SharedDirectEventHandler onAccessibilityAction_ {nullptr};
+  SharedDirectEventHandler onAccessibilityTap_ {nullptr};
+  SharedDirectEventHandler onMagicTap_ {nullptr};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.cpp b/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.cpp
new file mode 100644
index 000000000000..4941cd49e285
--- /dev/null
+++ b/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.cpp
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "AccessibleShadowNode.h"
+
+#include <memory>
+
+namespace facebook {
+namespace react {
+
+AccessibleShadowNode::AccessibleShadowNode(
+  const SharedAccessibilityProps &props
+) {
+  assert(props);
+}
+
+AccessibleShadowNode::AccessibleShadowNode(
+  const SharedAccessibleShadowNode &shadowNode,
+  const SharedAccessibilityProps &props
+) {
+  assert(shadowNode);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.h b/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.h
new file mode 100644
index 000000000000..1fa8316ba6d4
--- /dev/null
+++ b/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.h
@@ -0,0 +1,41 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ShadowNode.h>
+#include <fabric/view/AccessibilityProps.h>
+
+namespace facebook {
+namespace react {
+
+class AccessibleShadowNode;
+
+typedef std::shared_ptr<const AccessibleShadowNode> SharedAccessibleShadowNode;
+
+class AccessibleShadowNode {
+
+public:
+
+#pragma mark - Constructors
+
+  AccessibleShadowNode() = default;
+
+  AccessibleShadowNode(
+    const SharedAccessibilityProps &props
+  );
+
+  AccessibleShadowNode(
+    const SharedAccessibleShadowNode &shadowNode,
+    const SharedAccessibilityProps &props = nullptr
+  );
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.cpp b/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.cpp
new file mode 100644
index 000000000000..1e97d64e2650
--- /dev/null
+++ b/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.cpp
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "accessibilityValuesConversions.h"
+
+#include <folly/Conv.h>
+
+namespace facebook {
+namespace react {
+
+AccessibilityTraits accessibilityTraitsFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+
+  // FIXME: Not clear yet.
+  abort();
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.h b/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.h
new file mode 100644
index 000000000000..7240a7cd9aa6
--- /dev/null
+++ b/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.h
@@ -0,0 +1,20 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <folly/dynamic.h>
+
+#include <fabric/view/AccessibilityPrimitives.h>
+
+namespace facebook {
+namespace react {
+
+AccessibilityTraits accessibilityTraitsFromDynamic(const folly::dynamic &value);
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
new file mode 100644
index 000000000000..3684f75abc4b
--- /dev/null
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -0,0 +1,228 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "YogaLayoutableShadowNode.h"
+
+#include <algorithm>
+#include <memory>
+
+#include <yoga/Yoga.h>
+#include <fabric/core/LayoutContext.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+#include "yogaValuesConversions.h"
+
+namespace facebook {
+namespace react {
+
+SharedYogaConfig YogaLayoutableShadowNode::suitableYogaConfig() {
+  static SharedYogaConfig sharedYogaConfig;
+
+  if (!sharedYogaConfig) {
+    sharedYogaConfig = std::make_shared<YGConfig>(YGConfig({
+      .cloneNodeCallback = YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector
+    }));
+  }
+
+  return sharedYogaConfig;
+}
+
+YogaLayoutableShadowNode::YogaLayoutableShadowNode() {
+  auto yogaNode = std::make_shared<YGNode>();
+  yogaNode->markDirtyAndPropogate();
+  yogaNode->setConfig(suitableYogaConfig().get());
+  yogaNode->setContext(this);
+  yogaNode_ = yogaNode;
+}
+
+YogaLayoutableShadowNode::YogaLayoutableShadowNode(
+  const SharedYogaStylableProps &props,
+  const SharedShadowNodeSharedList &children
+) {
+  assert(props);
+  assert(children);
+
+  auto yogaNode = std::make_shared<YGNode>();
+  yogaNode->setConfig(suitableYogaConfig().get());
+  yogaNode->setStyle(props->getYogaStyle());
+  yogaNode->setContext(this);
+  yogaNode->markDirtyAndPropogate();
+  YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(*yogaNode, children);
+  yogaNode_ = yogaNode;
+}
+
+YogaLayoutableShadowNode::YogaLayoutableShadowNode(
+  const SharedYogaLayoutableShadowNode &shadowNode,
+  const SharedYogaStylableProps &props,
+  const SharedShadowNodeSharedList &children
+) {
+  auto yogaNode = std::make_shared<YGNode>(*shadowNode->yogaNode_);
+  yogaNode->setContext(this);
+  yogaNode->setParent(nullptr);
+
+  if (props) {
+    yogaNode->setStyle(props->getYogaStyle());
+  }
+
+  if (children) {
+    YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(*yogaNode, children);
+  }
+
+  yogaNode->markDirtyAndPropogate();
+
+  yogaNode_ = yogaNode;
+}
+
+void YogaLayoutableShadowNode::cleanLayout() {
+  yogaNode_->setDirty(false);
+}
+
+void YogaLayoutableShadowNode::dirtyLayout() {
+  yogaNode_->markDirtyAndPropogate();
+}
+
+bool YogaLayoutableShadowNode::getIsLayoutClean() const {
+  return !yogaNode_->isDirty();
+}
+
+bool YogaLayoutableShadowNode::getHasNewLayout() const {
+  return yogaNode_->getHasNewLayout();
+}
+
+void YogaLayoutableShadowNode::setHasNewLayout(bool hasNewLayout) {
+  yogaNode_->setHasNewLayout(hasNewLayout);
+}
+
+#pragma mark - Mutating Methods
+
+void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child) {
+  ensureUnsealed();
+
+  auto nonConstYogaNode = std::const_pointer_cast<YGNode>(yogaNode_);
+  auto nonConstChildYogaNode = std::const_pointer_cast<YGNode>(child->yogaNode_);
+  nonConstYogaNode->insertChild(nonConstChildYogaNode.get(), nonConstYogaNode->getChildrenCount());
+}
+
+void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
+  ensureUnsealed();
+
+  if (!getIsLayoutClean()) {
+    YGNode *yogaNode = const_cast<YGNode *>(yogaNode_.get());
+    YGNodeCalculateLayout(yogaNode, YGUndefined, YGUndefined, YGDirectionInherit);
+  }
+
+  LayoutableShadowNode::layout(layoutContext);
+}
+
+void YogaLayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
+  ensureUnsealed();
+
+  for (auto child : getChildren()) {
+    auto yogaLayoutableChild = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(child);
+    if (!yogaLayoutableChild) {
+      continue;
+    }
+
+    auto nonConstYogaLayoutableChild = std::const_pointer_cast<YogaLayoutableShadowNode>(yogaLayoutableChild);
+
+    LayoutMetrics childLayoutMetrics = layoutMetricsFromYogaNode(*nonConstYogaLayoutableChild->yogaNode_);
+    bool isAffected = nonConstYogaLayoutableChild->setLayoutMetrics(childLayoutMetrics);
+    if (isAffected) {
+      layoutContext.affectedShadowNodes->insert(child);
+    }
+  }
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList YogaLayoutableShadowNode::getDebugProps() const {
+  // TODO: Move to the base class and return `layoutMetrics` instead.
+
+  SharedDebugStringConvertibleList list = {};
+
+  if (getHasNewLayout()) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("hasNewLayout"));
+  }
+
+  YGLayout defaultYogaLayout = YGLayout();
+  YGLayout currentYogaLayout = std::const_pointer_cast<YGNode>(yogaNode_)->getLayout();
+
+#define YOGA_LAYOUT_PROPS_ADD_TO_SET(stringName, propertyName, accessor, convertor) \
+  { \
+    auto currentValueString = convertor(currentYogaLayout.propertyName accessor); \
+    auto defaultValueString = convertor(defaultYogaLayout.propertyName accessor); \
+    if (currentValueString != defaultValueString) { \
+      list.push_back(std::make_shared<DebugStringConvertibleItem>(#stringName, currentValueString)); \
+    } \
+  }
+
+  YOGA_LAYOUT_PROPS_ADD_TO_SET(position, position, , stringFromYogaPosition)
+  YOGA_LAYOUT_PROPS_ADD_TO_SET(dimensions, dimensions, , stringFromYogaDimensions)
+  YOGA_LAYOUT_PROPS_ADD_TO_SET(margin, margin, , stringFromYogaEdges)
+  YOGA_LAYOUT_PROPS_ADD_TO_SET(border, border, , stringFromYogaEdges)
+  YOGA_LAYOUT_PROPS_ADD_TO_SET(padding, padding, , stringFromYogaEdges)
+  YOGA_LAYOUT_PROPS_ADD_TO_SET(direction, direction, , stringFromYogaStyleDirection)
+
+  return list;
+}
+
+#pragma mark - Helpers
+
+#pragma mark - Yoga Connectors
+
+void YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *newYogaNode, YGNode *parentYogaNode, int childIndex) {
+  // We have only raw pointer to the parent shadow node, but that's enough for now.
+  YogaLayoutableShadowNode *parentShadowNodeRawPtr = (YogaLayoutableShadowNode *)parentYogaNode->getContext();
+  assert(parentShadowNodeRawPtr);
+
+  // Old child shadow node already exists but we have only raw pointer to it...
+  YogaLayoutableShadowNode *oldShadowNodeRawPtr = (YogaLayoutableShadowNode *)oldYogaNode->getContext();
+  assert(oldShadowNodeRawPtr);
+
+  // ... but we have to address this by `shared_ptr`. We cannot create a new `shared_ptr` for it because we will end up with two shared pointers to
+  // single object which will cause preluminary destroyng the object.
+  // Another approaches to consider:
+  //  * Create a new `shared_ptr` with empty deleter.
+  //  * Using `childIndex` to find exact node.
+  SharedLayoutableShadowNode oldShadowNode = nullptr;
+  for (auto child : parentShadowNodeRawPtr->getChildren()) {
+    if (child.get() == oldShadowNodeRawPtr) {
+      oldShadowNode = child;
+      break;
+    }
+  }
+
+  assert(oldShadowNode);
+
+  // The new one does not exist yet. So, we have to clone and replace this using `cloneAndReplaceChild`.
+  SharedYogaLayoutableShadowNode newShadowNode =
+    std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(parentShadowNodeRawPtr->cloneAndReplaceChild(oldShadowNode));
+  assert(newShadowNode);
+
+  // And finally, we have to replace underline yoga node with the new one provided by Yoga.
+  newShadowNode->yogaNode_ = std::shared_ptr<YGNode>(newYogaNode);
+}
+
+void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children) {
+  auto yogaNodeChildren = YGVector();
+
+  for (const SharedShadowNode &shadowNode : *children) {
+    const SharedYogaLayoutableShadowNode yogaLayoutableShadowNode = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(shadowNode);
+
+    if (!yogaLayoutableShadowNode) {
+      continue;
+    }
+
+    yogaNodeChildren.push_back((YGNode *)yogaLayoutableShadowNode->yogaNode_.get());
+  }
+
+  yogaNode.setChildren(yogaNodeChildren);
+  yogaNode.setDirty(true);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
new file mode 100644
index 000000000000..cba25fe87d2b
--- /dev/null
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -0,0 +1,93 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+#include <vector>
+
+#include <yoga/YGNode.h>
+
+#include <fabric/core/LayoutableShadowNode.h>
+#include <fabric/core/Sealable.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/debug/DebugStringConvertible.h>
+#include <fabric/view/YogaStylableProps.h>
+
+namespace facebook {
+namespace react {
+
+class YogaLayoutableShadowNode;
+
+// We accept that Yoga node is highly mutable thing and we don't try to enforce immutability,
+// so it does not have `const` qualifier (and we mark it as `mutable` in the class).
+using SharedYogaNode = std::shared_ptr<YGNode>;
+using SharedYogaConfig = std::shared_ptr<YGConfig>;
+
+using SharedYogaLayoutableShadowNode = std::shared_ptr<const YogaLayoutableShadowNode>;
+using SharedYogaLayoutableShadowNodeList = std::vector<const SharedYogaLayoutableShadowNode>;
+using SharedYogaLayoutableShadowNodeSharedList = std::shared_ptr<const SharedYogaLayoutableShadowNodeList>;
+
+class YogaLayoutableShadowNode:
+  public LayoutableShadowNode,
+  public virtual DebugStringConvertible,
+  public virtual Sealable {
+
+public:
+
+#pragma mark - Constructors
+  YogaLayoutableShadowNode();
+
+  YogaLayoutableShadowNode(
+    const SharedYogaStylableProps &props,
+    const SharedShadowNodeSharedList &children
+  );
+
+  YogaLayoutableShadowNode(
+    const SharedYogaLayoutableShadowNode &shadowNode,
+    const SharedYogaStylableProps &props = nullptr,
+    const SharedShadowNodeSharedList &children = nullptr
+  );
+
+#pragma mark - Mutating Methods
+
+  /*
+   * Appends `child`'s Yoga node to the own Yoga node.
+   * So, it complements `ShadowNode::appendChild(...)` functionality from Yoga
+   * perspective.
+   */
+  void appendChild(SharedYogaLayoutableShadowNode child);
+
+  void cleanLayout() override;
+  void dirtyLayout() override;
+  bool getIsLayoutClean() const override;
+
+  void setHasNewLayout(bool hasNewLayout) override;
+  bool getHasNewLayout() const override;
+
+  /*
+   * Computes layout using Yoga layout engine.
+   * See `LayoutableShadowNode` for more details.
+   */
+  void layout(LayoutContext layoutContext) override;
+  
+  void layoutChildren(LayoutContext layoutContext) override;
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+private:
+  mutable SharedYogaNode yogaNode_;
+
+  static SharedYogaConfig suitableYogaConfig();
+  static void setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children);
+  static void yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *newYogaNode, YGNode *parentYogaNode, int childIndex);
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
new file mode 100644
index 000000000000..24a2ca5682da
--- /dev/null
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
@@ -0,0 +1,148 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "YogaStylableProps.h"
+
+#include <yoga/Yoga.h>
+#include <yoga/YGNode.h>
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+#include "yogaValuesConversions.h"
+
+namespace facebook {
+namespace react {
+
+const YGStyle &YogaStylableProps::getYogaStyle() const {
+  return yogaStyle_;
+}
+
+void YogaStylableProps::apply(const RawProps &rawProps) {
+  for (auto const &pair : rawProps) {
+    auto const &name = pair.first;
+    auto const &value = pair.second;
+
+#define YOGA_STYLE_PROPERTY(stringName, yogaName, accessor, convertor) \
+  if (name == #stringName) { \
+    yogaStyle_.yogaName = convertor(value accessor); \
+    continue; \
+  }
+
+#define YOGA_STYLE_SIMPLE_FLOAT_PROPERTY(name) \
+  YOGA_STYLE_PROPERTY(name, name, .asDouble(), )
+
+#define YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(name) \
+  YOGA_STYLE_PROPERTY(name, name, .asDouble(), yogaOptionalFloatFromFabricFloat)
+
+#define YOGA_STYLE_SIMPLE_INTEGER_PROPERTY(name) \
+  YOGA_STYLE_PROPERTY(name, name, .asInt(), )
+
+// Dimension Properties
+#define YOGA_STYLE_DIMENSION_PROPERTY() \
+  YOGA_STYLE_PROPERTY(width, dimensions[YGDimensionWidth], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(height, dimensions[YGDimensionHeight], , yogaStyleValueFromDynamic)
+
+#define YOGA_STYLE_PREFIXED_DIMENSION_PROPERTY(prefix) \
+  YOGA_STYLE_PROPERTY(prefix##Width, prefix##Dimensions[YGDimensionWidth], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix##Height, prefix##Dimensions[YGDimensionHeight], , yogaStyleValueFromDynamic)
+
+// Edge Properties
+#define YOGA_STYLE_POSITION_EDGE_PROPERTY() \
+  YOGA_STYLE_PROPERTY(left, position[YGEdgeLeft], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(top, position[YGEdgeTop], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(right, position[YGEdgeRight], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(bottom, position[YGEdgeBottom], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(start, position[YGEdgeStart], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(end, position[YGEdgeEnd], , yogaStyleValueFromDynamic)
+
+#define YOGA_STYLE_PREFIXED_EDGE_PROPERTY(prefix) \
+  YOGA_STYLE_PROPERTY(prefix##Left, prefix[YGEdgeLeft], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix##Top, prefix[YGEdgeTop], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix##Right, prefix[YGEdgeRight], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix##Bottom, prefix[YGEdgeBottom], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix##Start, prefix[YGEdgeStart], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix##End, prefix[YGEdgeEnd], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix##Horizontal, prefix[YGEdgeHorizontal], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix##Vertical, prefix[YGEdgeVertical], , yogaStyleValueFromDynamic) \
+  YOGA_STYLE_PROPERTY(prefix, prefix[YGEdgeAll], , yogaStyleValueFromDynamic)
+
+    YOGA_STYLE_PROPERTY(direction, direction, , yogaStyleDirectionFromDynamic)
+    YOGA_STYLE_PROPERTY(flexDirection, flexDirection, , yogaStyleFlexDirectionFromDynamic)
+    YOGA_STYLE_PROPERTY(justifyContent, justifyContent, , yogaStyleJustifyFromDynamic)
+    YOGA_STYLE_PROPERTY(alignContent, alignContent, , yogaStyleAlignFromDynamic)
+    YOGA_STYLE_PROPERTY(alignItems, alignItems, , yogaStyleAlignFromDynamic)
+    YOGA_STYLE_PROPERTY(alignSelf, alignSelf, , yogaStyleAlignFromDynamic)
+    YOGA_STYLE_PROPERTY(positionType, positionType, , yogaStylePositionTypeFromDynamic)
+    YOGA_STYLE_PROPERTY(flexWrap, flexWrap, , yogaStyleWrapFromDynamic)
+    YOGA_STYLE_PROPERTY(overflow, overflow, , yogaStyleOverflowFromDynamic)
+    YOGA_STYLE_PROPERTY(display, display, , yogaStyleDisplayFromDynamic)
+
+    YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(flex)
+    YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(flexGrow)
+    YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(flexShrink)
+    YOGA_STYLE_PROPERTY(flexBasis, flexBasis, , yogaStyleValueFromDynamic)
+
+    YOGA_STYLE_DIMENSION_PROPERTY()
+    YOGA_STYLE_PREFIXED_DIMENSION_PROPERTY(min)
+    YOGA_STYLE_PREFIXED_DIMENSION_PROPERTY(max)
+
+    YOGA_STYLE_POSITION_EDGE_PROPERTY()
+    YOGA_STYLE_PREFIXED_EDGE_PROPERTY(margin)
+    YOGA_STYLE_PREFIXED_EDGE_PROPERTY(padding)
+    YOGA_STYLE_PREFIXED_EDGE_PROPERTY(border)
+
+    YOGA_STYLE_SIMPLE_FLOAT_PROPERTY(aspectRatio)
+  }
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList YogaStylableProps::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+
+  YGStyle defaultYogaStyle = YGStyle();
+  YGStyle currentYogaStyle = yogaStyle_;
+
+#define YOGA_STYLE_PROPS_ADD_TO_SET(stringName, propertyName, accessor, convertor) \
+  { \
+    auto currentValueString = convertor(currentYogaStyle.propertyName accessor); \
+    auto defaultValueString = convertor(defaultYogaStyle.propertyName accessor); \
+    if (currentValueString != defaultValueString) { \
+      list.push_back(std::make_shared<DebugStringConvertibleItem>(#stringName, currentValueString)); \
+    } \
+  }
+
+  YOGA_STYLE_PROPS_ADD_TO_SET(direction, direction, , stringFromYogaStyleDirection)
+
+  YOGA_STYLE_PROPS_ADD_TO_SET(flexDirection, flexDirection, , stringFromYogaStyleFlexDirection)
+  YOGA_STYLE_PROPS_ADD_TO_SET(justifyContent, justifyContent, , stringFromYogaStyleJustify)
+  YOGA_STYLE_PROPS_ADD_TO_SET(alignItems, alignItems, , stringFromYogaStyleAlign)
+  YOGA_STYLE_PROPS_ADD_TO_SET(alignSelf, alignSelf, , stringFromYogaStyleAlign)
+  YOGA_STYLE_PROPS_ADD_TO_SET(positionType, positionType, , stringFromYogaStylePositionType)
+  YOGA_STYLE_PROPS_ADD_TO_SET(flexWrap, flexWrap, , stringFromYogaStyleWrap)
+  YOGA_STYLE_PROPS_ADD_TO_SET(overflow, overflow, , stringFromYogaStyleOverflow)
+
+  YOGA_STYLE_PROPS_ADD_TO_SET(flex, flex, , stringFromYogaStyleOptionalFloat)
+  YOGA_STYLE_PROPS_ADD_TO_SET(flexGrow, flexGrow, , stringFromYogaStyleOptionalFloat)
+  YOGA_STYLE_PROPS_ADD_TO_SET(flexShrink, flexShrink, , stringFromYogaStyleOptionalFloat)
+  YOGA_STYLE_PROPS_ADD_TO_SET(flexBasis, flexBasis, , stringFromYogaStyleValue)
+  YOGA_STYLE_PROPS_ADD_TO_SET(margin, margin, , stringFromYogaStyleEdge)
+  YOGA_STYLE_PROPS_ADD_TO_SET(position, position, , stringFromYogaStyleEdge)
+  YOGA_STYLE_PROPS_ADD_TO_SET(padding, padding, , stringFromYogaStyleEdge)
+  YOGA_STYLE_PROPS_ADD_TO_SET(border, border, , stringFromYogaStyleEdge)
+
+  YOGA_STYLE_PROPS_ADD_TO_SET(size, dimensions, , stringFromYogaStyleDimensions)
+  YOGA_STYLE_PROPS_ADD_TO_SET(minSize, minDimensions, , stringFromYogaStyleDimensions)
+  YOGA_STYLE_PROPS_ADD_TO_SET(maxSize, maxDimensions, , stringFromYogaStyleDimensions)
+
+  YOGA_STYLE_PROPS_ADD_TO_SET(aspectRatio, aspectRatio, , folly::to<std::string>)
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.h b/ReactCommon/fabric/view/yoga/YogaStylableProps.h
new file mode 100644
index 000000000000..61d935a22f27
--- /dev/null
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.h
@@ -0,0 +1,39 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <yoga/YGStyle.h>
+
+#include <fabric/core/Props.h>
+#include <fabric/debug/DebugStringConvertible.h>
+
+namespace facebook {
+namespace react {
+
+class YogaStylableProps;
+
+typedef std::shared_ptr<const YogaStylableProps> SharedYogaStylableProps;
+
+class YogaStylableProps:
+  public virtual DebugStringConvertible
+{
+public:
+  const YGStyle &getYogaStyle() const;
+
+  void apply(const RawProps &rawProps);
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+protected:
+  YGStyle yogaStyle_ {};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
new file mode 100644
index 000000000000..e329b8437644
--- /dev/null
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
@@ -0,0 +1,303 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "yogaValuesConversions.h"
+
+#include <folly/Conv.h>
+
+#include <fabric/core/LayoutMetrics.h>
+
+namespace facebook {
+namespace react {
+
+Float fabricFloatFromYogaFloat(float value) {
+  return (Float)value;
+}
+
+float yogaFloatFromFabricFloat(Float value) {
+  return (float)value;
+}
+
+Float fabricFloatFromYogaOptionalFloat(YGFloatOptional value) {
+  if (value.isUndefined()) {
+    return kFloatUndefined;
+  }
+
+  return fabricFloatFromYogaFloat(value.getValue());
+}
+
+YGFloatOptional yogaOptionalFloatFromFabricFloat(Float value) {
+  if (value == kFloatUndefined) {
+    return YGFloatOptional();
+  }
+
+  return YGFloatOptional(yogaFloatFromFabricFloat(value));
+}
+
+LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode) {
+  LayoutMetrics layoutMetrics;
+
+  YGLayout layout = yogaNode.getLayout();
+
+  layoutMetrics.frame = Rect {
+    Point {fabricFloatFromYogaFloat(layout.position[0]), fabricFloatFromYogaFloat(layout.position[1])},
+    Size {fabricFloatFromYogaFloat(layout.dimensions[0]), fabricFloatFromYogaFloat(layout.dimensions[1])}
+  };
+
+  // FIXME: Add more.
+
+  return layoutMetrics;
+}
+
+YGDirection yogaStyleDirectionFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+
+  if (stringValue == "inherit") { return YGDirectionInherit; }
+  if (stringValue == "ltr") { return YGDirectionLTR; }
+  if (stringValue == "rtl") { return YGDirectionRTL; }
+
+  abort();
+}
+
+YGFlexDirection yogaStyleFlexDirectionFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+
+  if (stringValue == "column") { return YGFlexDirectionColumn; }
+  if (stringValue == "column-reverse") { return YGFlexDirectionColumnReverse; }
+  if (stringValue == "row") { return YGFlexDirectionRow; }
+  if (stringValue == "row-reverse") { return YGFlexDirectionRowReverse; }
+
+  abort();
+}
+
+YGJustify yogaStyleJustifyFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+
+  if (stringValue == "flex-start") { return YGJustifyFlexStart; }
+  if (stringValue == "center") { return YGJustifyCenter; }
+  if (stringValue == "flex-end") { return YGJustifyFlexEnd; }
+  if (stringValue == "space-between") { return YGJustifySpaceBetween; }
+  if (stringValue == "space-around") { return YGJustifySpaceAround; }
+  if (stringValue == "space-evenly") { return YGJustifySpaceEvenly; }
+
+  abort();
+}
+
+YGAlign yogaStyleAlignFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+
+  if (stringValue == "auto") { return YGAlignAuto; }
+  if (stringValue == "flex-start") { return YGAlignFlexStart; }
+  if (stringValue == "center") { return YGAlignCenter; }
+  if (stringValue == "flex-end") { return YGAlignFlexEnd; }
+  if (stringValue == "stretch") { return YGAlignStretch; }
+  if (stringValue == "baseline") { return YGAlignBaseline; }
+  if (stringValue == "between") { return YGAlignSpaceBetween; }
+  if (stringValue == "space-around") { return YGAlignSpaceAround; }
+
+  abort();
+}
+
+YGPositionType yogaStylePositionTypeFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+
+  if (stringValue == "relative") { return YGPositionTypeRelative; }
+  if (stringValue == "absolute") { return YGPositionTypeAbsolute; }
+
+  abort();
+}
+
+YGWrap yogaStyleWrapFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+
+  if (stringValue == "no-wrap") { return YGWrapNoWrap; }
+  if (stringValue == "wrap") { return YGWrapWrap; }
+  if (stringValue == "wrap-reverse") { return YGWrapWrapReverse; }
+
+  abort();
+}
+
+YGOverflow yogaStyleOverflowFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+
+  if (stringValue == "visible") { return YGOverflowVisible; }
+  if (stringValue == "hidden") { return YGOverflowHidden; }
+  if (stringValue == "scroll") { return YGOverflowScroll; }
+
+  abort();
+}
+
+YGDisplay yogaStyleDisplayFromDynamic(const folly::dynamic &value) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+
+  if (stringValue == "flex") { return YGDisplayFlex; }
+  if (stringValue == "none") { return YGDisplayNone; }
+
+  abort();
+}
+
+YGValue yogaStyleValueFromDynamic(const folly::dynamic &value) {
+  if (value.isNumber()) {
+    float x = value.asDouble();
+    return { x, YGUnitPoint };
+  } else if (value.isString()) {
+    const auto stringValue = value.asString();
+    if (stringValue == "auto") {
+      return { YGUndefined, YGUnitAuto };
+    } else {
+      if (stringValue.back() == '%') {
+        return { folly::to<float>(stringValue.substr(stringValue.length() - 1)), YGUnitPercent };
+      } else {
+        return { folly::to<float>(stringValue), YGUnitPoint };
+      }
+    }
+  }
+
+  return YGValueUndefined;
+}
+
+YGFloatOptional yogaStyleOptionalFloatFromDynamic(const folly::dynamic &value) {
+  if (value.isNumber()) {
+    return YGFloatOptional(value.asDouble());
+  } else if (value.isString()) {
+    const auto stringValue = value.asString();
+    if (stringValue == "auto") {
+      return YGFloatOptional();
+    }
+  }
+
+  abort();
+}
+
+std::string stringFromYogaDimensions(std::array<float, 2> dimensions) {
+  return "{" + folly::to<std::string>(dimensions[0]) + ", " + folly::to<std::string>(dimensions[1]) + "}";
+}
+
+std::string stringFromYogaPosition(std::array<float, 4> position) {
+  return "{" + folly::to<std::string>(position[0]) + ", " + folly::to<std::string>(position[1]) + "}";
+}
+
+std::string stringFromYogaEdges(std::array<float, 6> edges) {
+  return "{" +
+    folly::to<std::string>(edges[0]) + ", " +
+    folly::to<std::string>(edges[1]) + ", " +
+    folly::to<std::string>(edges[2]) + ", " +
+    folly::to<std::string>(edges[3]) + "}";
+}
+
+std::string stringFromYogaStyleDirection(YGDirection value) {
+  switch (value) {
+    case YGDirectionInherit: return "inherit";
+    case YGDirectionLTR: return "ltr";
+    case YGDirectionRTL: return "rtl";
+  }
+}
+
+std::string stringFromYogaStyleFlexDirection(YGFlexDirection value) {
+  switch (value) {
+    case YGFlexDirectionColumn: return "column";
+    case YGFlexDirectionColumnReverse: return "column-reverse";
+    case YGFlexDirectionRow: return "row";
+    case YGFlexDirectionRowReverse: return "row-reverse";
+  }
+}
+
+std::string stringFromYogaStyleJustify(YGJustify value) {
+  switch (value) {
+    case YGJustifyFlexStart: return "flex-start";
+    case YGJustifyCenter: return "center";
+    case YGJustifyFlexEnd: return "flex-end";
+    case YGJustifySpaceBetween: return "space-between";
+    case YGJustifySpaceAround: return "space-around";
+    case YGJustifySpaceEvenly: return "space-evenly";
+  }
+}
+
+std::string stringFromYogaStyleAlign(YGAlign value) {
+  switch (value) {
+    case YGAlignAuto: return "auto";
+    case YGAlignFlexStart: return "flex-start";
+    case YGAlignCenter: return "center";
+    case YGAlignFlexEnd: return "flex-end";
+    case YGAlignStretch: return "stretch";
+    case YGAlignBaseline: return "baseline";
+    case YGAlignSpaceBetween: return "space-between";
+    case YGAlignSpaceAround: return "space-around";
+  }
+}
+
+std::string stringFromYogaStylePositionType(YGPositionType value) {
+  switch (value) {
+    case YGPositionTypeRelative: return "relative";
+    case YGPositionTypeAbsolute: return "absolute";
+  }
+}
+
+std::string stringFromYogaStyleWrap(YGWrap value) {
+  switch (value) {
+    case YGWrapNoWrap: return "no-wrap";
+    case YGWrapWrap: return "wrap";
+    case YGWrapWrapReverse: return "wrap-reverse";
+  }
+}
+
+std::string stringFromYogaStyleOverflow(YGOverflow value) {
+  switch (value) {
+    case YGOverflowVisible: return "visible";
+    case YGOverflowScroll: return "scroll";
+    case YGOverflowHidden: return "hidden";
+  }
+}
+
+std::string stringFromYogaStyleDisplay(YGDisplay value) {
+  switch (value) {
+    case YGDisplayFlex: return "flex";
+    case YGDisplayNone: return "none";
+  }
+}
+
+std::string stringFromYogaStyleValue(YGValue value) {
+  switch (value.unit) {
+    case YGUnitUndefined: return "undefined";
+    case YGUnitPoint: return folly::to<std::string>(value.value);
+    case YGUnitPercent: return folly::to<std::string>(value.value) + "%";
+    case YGUnitAuto: return "auto";
+  }
+}
+
+std::string stringFromYogaStyleOptionalFloat(YGFloatOptional value) {
+  if (value.isUndefined()) {
+    return "undefined";
+  }
+
+  return folly::to<std::string>(fabricFloatFromYogaFloat(value.getValue()));
+}
+
+std::string stringFromYogaStyleDimensions(std::array<YGValue, 2> value) {
+  return "{" +
+    stringFromYogaStyleValue(value[0]) + ", " +
+    stringFromYogaStyleValue(value[1]) + "}";
+}
+
+std::string stringFromYogaStyleEdge(std::array<YGValue, YGEdgeCount> value) {
+  return "{" +
+    stringFromYogaStyleValue(value[0]) + ", " +
+    stringFromYogaStyleValue(value[1]) + ", " +
+    stringFromYogaStyleValue(value[2]) + ", " +
+    stringFromYogaStyleValue(value[3]) + "}";
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.h b/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
new file mode 100644
index 000000000000..6c5156598300
--- /dev/null
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
@@ -0,0 +1,57 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <folly/dynamic.h>
+#include <yoga/Yoga.h>
+#include <yoga/YGNode.h>
+
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+struct LayoutMetrics;
+
+Float fabricFloatFromYogaFloat(float value);
+float yogaFloatFromFabricFloat(Float value);
+
+Float fabricFloatFromYogaOptionalFloat(YGFloatOptional value);
+YGFloatOptional yogaOptionalFloatFromFabricFloat(Float value);
+
+LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode);
+
+YGDirection yogaStyleDirectionFromDynamic(const folly::dynamic &value);
+YGFlexDirection yogaStyleFlexDirectionFromDynamic(const folly::dynamic &value);
+YGJustify yogaStyleJustifyFromDynamic(const folly::dynamic &value);
+YGAlign yogaStyleAlignFromDynamic(const folly::dynamic &value);
+YGPositionType yogaStylePositionTypeFromDynamic(const folly::dynamic &value);
+YGWrap yogaStyleWrapFromDynamic(const folly::dynamic &value);
+YGOverflow yogaStyleOverflowFromDynamic(const folly::dynamic &value);
+YGDisplay yogaStyleDisplayFromDynamic(const folly::dynamic &value);
+YGValue yogaStyleValueFromDynamic(const folly::dynamic &value);
+YGFloatOptional yogaStyleOptionalFloatFromDynamic(const folly::dynamic &value);
+
+std::string stringFromYogaDimensions(std::array<float, 2> dimensions);
+std::string stringFromYogaPosition(std::array<float, 4> position);
+std::string stringFromYogaEdges(std::array<float, 6> edges);
+std::string stringFromYogaStyleDirection(YGDirection direction);
+std::string stringFromYogaStyleFlexDirection(YGFlexDirection value);
+std::string stringFromYogaStyleJustify(YGJustify value);
+std::string stringFromYogaStyleAlign(YGAlign value);
+std::string stringFromYogaStylePositionType(YGPositionType value);
+std::string stringFromYogaStyleWrap(YGWrap value);
+std::string stringFromYogaStyleOverflow(YGOverflow value);
+std::string stringFromYogaStyleDisplay(YGDisplay value);
+std::string stringFromYogaStyleValue(YGValue value);
+std::string stringFromYogaStyleOptionalFloat(YGFloatOptional value);
+std::string stringFromYogaStyleDimensions(std::array<YGValue, 2> value);
+std::string stringFromYogaStyleEdge(std::array<YGValue, YGEdgeCount> value);
+
+} // namespace react
+} // namespace facebook

From c2ad59a277e543ed291c13633dc8e76bd5db6db0 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:27 -0700
Subject: [PATCH 0057/1109] `fabric/uimanager` module

Summary: `fabric/uimanager` implements FabricUIModule.

Reviewed By: fkgozali

Differential Revision: D7230669

fbshipit-source-id: db6228021352598feac7854b5871d9d6c5c85119
---
 ReactCommon/fabric/BUCK                       |   1 +
 ReactCommon/fabric/FabricUIManager.cpp        |  53 ---------
 ReactCommon/fabric/uimanager/BUCK             |  52 +++++++++
 .../uimanager/ComponentDescriptorRegistry.cpp |  26 +++++
 .../uimanager/ComponentDescriptorRegistry.h   |  29 +++++
 .../fabric/uimanager/FabricUIManager.cpp      | 109 ++++++++++++++++++
 .../fabric/{ => uimanager}/FabricUIManager.h  |   9 +-
 .../IFabricPlatformUIOperationManager.h       |   0
 8 files changed, 224 insertions(+), 55 deletions(-)
 delete mode 100644 ReactCommon/fabric/FabricUIManager.cpp
 create mode 100644 ReactCommon/fabric/uimanager/BUCK
 create mode 100644 ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
 create mode 100644 ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
 create mode 100644 ReactCommon/fabric/uimanager/FabricUIManager.cpp
 rename ReactCommon/fabric/{ => uimanager}/FabricUIManager.h (88%)
 rename ReactCommon/fabric/{ => uimanager}/IFabricPlatformUIOperationManager.h (100%)

diff --git a/ReactCommon/fabric/BUCK b/ReactCommon/fabric/BUCK
index 162ae5ec4230..62a6c5ccab56 100644
--- a/ReactCommon/fabric/BUCK
+++ b/ReactCommon/fabric/BUCK
@@ -40,6 +40,7 @@ rn_xplat_cxx_library(
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
         react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/uimanager:uimanager"),
         react_native_xplat_target("fabric/view:view"),
     ],
 )
diff --git a/ReactCommon/fabric/FabricUIManager.cpp b/ReactCommon/fabric/FabricUIManager.cpp
deleted file mode 100644
index 9b6ec3216e61..000000000000
--- a/ReactCommon/fabric/FabricUIManager.cpp
+++ /dev/null
@@ -1,53 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#include "FabricUIManager.h"
-
-#include "IFabricPlatformUIOperationManager.h"
-
-namespace facebook {
-namespace react {
-
-FabricUIManager::FabricUIManager(const std::shared_ptr<IFabricPlatformUIOperationManager> &platformUIOperationManager) :
-  platformUIOperationManager_(platformUIOperationManager) {};
-
-SharedShadowNode FabricUIManager::createNode(int reactTag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
-  platformUIOperationManager_->performUIOperation();
-  return nullptr;
-}
-
-SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &node) {
-  return nullptr;
-}
-
-SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &node) {
-  return nullptr;
-}
-
-SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props) {
-  return nullptr;
-}
-
-SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps) {
-  return nullptr;
-}
-
-void FabricUIManager::appendChild(const SharedShadowNode &parentNode, const SharedShadowNode &childNode) {
-}
-
-SharedShadowNodeUnsharedList FabricUIManager::createChildSet(int rootTag) {
-  return nullptr;
-}
-
-void FabricUIManager::appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode) {
-}
-
-void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedList &childSet) {
-}
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
new file mode 100644
index 000000000000..8b3e3ad6b73c
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -0,0 +1,52 @@
+load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+
+rn_xplat_cxx_library(
+    name = "uimanager",
+    srcs = glob(
+        [
+            "**/*.cpp",
+        ],
+    ),
+    headers = glob(
+        [
+            "**/*.h",
+        ],
+    ),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/uimanager",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    force_static = True,
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/core:core"),
+    ],
+)
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
new file mode 100644
index 000000000000..d209f590ce55
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
@@ -0,0 +1,26 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include "ComponentDescriptorRegistry.h"
+
+namespace facebook {
+namespace react {
+
+void ComponentDescriptorRegistry::registerComponentDescriptor(SharedComponentDescriptor componentDescriptor) {
+  ComponentHandle componentHandle = componentDescriptor->getComponentHandle();
+  _registryByHandle[componentHandle] = componentDescriptor;
+
+  ComponentName componentName = componentDescriptor->getComponentName();
+  _registryByName[componentName] = componentDescriptor;
+}
+
+const SharedComponentDescriptor ComponentDescriptorRegistry::operator[](const SharedShadowNode &shadowNode) {
+  ComponentHandle componentHandle = shadowNode->getComponentHandle();
+  return _registryByHandle[componentHandle];
+}
+
+const SharedComponentDescriptor ComponentDescriptorRegistry::operator[](const ComponentName &componentName) {
+  return _registryByName[componentName];
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
new file mode 100644
index 000000000000..462ab9f7f0d8
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
@@ -0,0 +1,29 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ComponentDescriptor.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Registry of particular `ComponentDescriptor`s.
+ */
+class ComponentDescriptorRegistry {
+
+public:
+  void registerComponentDescriptor(SharedComponentDescriptor componentDescriptor);
+
+  const SharedComponentDescriptor operator[](const SharedShadowNode &shadowNode);
+  const SharedComponentDescriptor operator[](const ComponentName &componentName);
+
+private:
+  std::unordered_map<ComponentHandle, SharedComponentDescriptor> _registryByHandle;
+  std::unordered_map<ComponentName, SharedComponentDescriptor> _registryByName;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
new file mode 100644
index 000000000000..d35762482531
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -0,0 +1,109 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "FabricUIManager.h"
+
+#include <fabric/core/LayoutContext.h>
+#include <fabric/view/ViewComponentDescriptor.h>
+#include <fabric/view/ViewProps.h>
+#include <fabric/view/ViewShadowNode.h>
+
+#include "IFabricPlatformUIOperationManager.h"
+
+namespace facebook {
+namespace react {
+
+static const RawProps rawPropsFromDynamic(const folly::dynamic object) {
+  // TODO: Convert this to something smarter, probably returning `std::iterator`.
+  RawProps result;
+
+  if (object.isNull()) {
+    return result;
+  }
+
+  assert(object.isObject());
+
+  for (const auto &pair : object.items()) {
+    assert(pair.first.isString());
+    result[pair.first.asString()] = pair.second;
+  }
+
+  return result;
+}
+
+FabricUIManager::FabricUIManager(const std::shared_ptr<IFabricPlatformUIOperationManager> &platformUIOperationManager):
+  platformUIOperationManager_(platformUIOperationManager) {
+
+  SharedComponentDescriptor viewComponentDescriptor = std::make_shared<ViewComponentDescriptor>();
+  _registry.registerComponentDescriptor(viewComponentDescriptor);
+}
+
+SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
+  ComponentDescriptor &componentDescriptor = *_registry["View"];
+  RawProps rawProps = rawPropsFromDynamic(props);
+  SharedShadowNode shadowNode = componentDescriptor.createShadowNode(tag, rootTag, instanceHandle, rawProps);
+  return shadowNode;
+}
+
+SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode) {
+  ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
+  return componentDescriptor.cloneShadowNode(shadowNode);
+}
+
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode) {
+  // Assuming semantic: Cloning with same props but empty children.
+  ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
+  return componentDescriptor.cloneShadowNode(shadowNode, nullptr, {});
+}
+
+SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
+  // Assuming semantic: Cloning with same children and specified props.
+  ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
+  RawProps rawProps = rawPropsFromDynamic(props);
+  return componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), nullptr);
+}
+
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
+  // Assuming semantic: Cloning with empty children and specified props.
+  ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
+  RawProps rawProps = rawPropsFromDynamic(props);
+  return componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), {});
+}
+
+void FabricUIManager::appendChild(const SharedShadowNode &parentShadowNode, const SharedShadowNode &childShadowNode) {
+  ComponentDescriptor &componentDescriptor = *_registry[parentShadowNode];
+  componentDescriptor.appendChild(parentShadowNode, childShadowNode);
+}
+
+SharedShadowNodeUnsharedList FabricUIManager::createChildSet(int rootTag) {
+  return std::make_shared<SharedShadowNodeList>(SharedShadowNodeList({}));
+}
+
+void FabricUIManager::appendChildToSet(const SharedShadowNodeUnsharedList &shadowNodeList, const SharedShadowNode &shadowNode) {
+  shadowNodeList->push_back(shadowNode);
+}
+
+void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedList &children) {
+  ComponentDescriptor &componentDescriptor = *_registry["View"];
+  SharedShadowNode previousRootShadowNode = componentDescriptor.createShadowNode(rootTag, rootTag, nullptr, {});
+  auto childrenCopy = std::make_shared<const SharedShadowNodeList>(SharedShadowNodeList(*children));
+  SharedShadowNode rootShadowNode = componentDescriptor.cloneShadowNode(previousRootShadowNode, nullptr, childrenCopy);
+
+  SharedViewShadowNode viewShadowNode = std::dynamic_pointer_cast<const ViewShadowNode>(rootShadowNode);
+  LayoutContext layoutContext = LayoutContext();
+  layoutContext.affectedShadowNodes = std::make_shared<std::unordered_set<SharedLayoutableShadowNode>>();
+
+  auto nonConstViewShadowNode = std::const_pointer_cast<ViewShadowNode>(viewShadowNode);
+  nonConstViewShadowNode->layout(layoutContext);
+
+  rootShadowNode->sealRecursive();
+
+  printf("## layouted rootShadowNode: %s \n", nonConstViewShadowNode->getDebugDescription(0).c_str());
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
similarity index 88%
rename from ReactCommon/fabric/FabricUIManager.h
rename to ReactCommon/fabric/uimanager/FabricUIManager.h
index 4857a4291d75..1db615b37c3f 100644
--- a/ReactCommon/fabric/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -7,18 +7,22 @@
 
 #pragma once
 
-#include <folly/dynamic.h>
-#include <folly/FBVector.h>
 #include <memory>
 
+#include <folly/dynamic.h>
+
+#include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/ShadowNode.h>
+#include <fabric/uimanager/ComponentDescriptorRegistry.h>
 
 namespace facebook {
 namespace react {
 
 class IFabricPlatformUIOperationManager;
+class ComponentDescriptorRegistry;
 
 class FabricUIManager {
+
 public:
   FabricUIManager(const std::shared_ptr<IFabricPlatformUIOperationManager> &platformUIOperationManager);
 
@@ -33,6 +37,7 @@ class FabricUIManager {
   void completeRoot(int rootTag, const SharedShadowNodeUnsharedList &childSet);
 
 private:
+  ComponentDescriptorRegistry _registry;
   std::shared_ptr<IFabricPlatformUIOperationManager> platformUIOperationManager_;
 };
 
diff --git a/ReactCommon/fabric/IFabricPlatformUIOperationManager.h b/ReactCommon/fabric/uimanager/IFabricPlatformUIOperationManager.h
similarity index 100%
rename from ReactCommon/fabric/IFabricPlatformUIOperationManager.h
rename to ReactCommon/fabric/uimanager/IFabricPlatformUIOperationManager.h

From 4cda0df2e516a3680ea0fdbd8b503ce34a794a74 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:30 -0700
Subject: [PATCH 0058/1109] Switching to the new FabricUIManager and all new
 shadow tree infra

Reviewed By: fkgozali

Differential Revision: D7230670

fbshipit-source-id: bca7d2859b87931c0d15406782b7d689de1d8c36
---
 .../RCTFabricPlatformUIOperationManager.h     |  2 +-
 React/Fabric/RCTFabricUIManagerWrapper.mm     |  6 ++-
 ReactCommon/fabric/BUCK                       | 46 -------------------
 ReactCommon/fabric/uimanager/BUCK             |  3 +-
 .../fabric/uimanager/FabricUIManager.cpp      |  6 ++-
 5 files changed, 13 insertions(+), 50 deletions(-)
 delete mode 100644 ReactCommon/fabric/BUCK

diff --git a/React/Fabric/RCTFabricPlatformUIOperationManager.h b/React/Fabric/RCTFabricPlatformUIOperationManager.h
index 2043959760ea..fe6c89ea21b8 100644
--- a/React/Fabric/RCTFabricPlatformUIOperationManager.h
+++ b/React/Fabric/RCTFabricPlatformUIOperationManager.h
@@ -10,7 +10,7 @@
 
 #import <memory>
 
-#include <fabric/IFabricPlatformUIOperationManager.h>
+#include <fabric/uimanager/IFabricPlatformUIOperationManager.h>
 
 @class RCTFabricPlatformUIOperationManager;
 
diff --git a/React/Fabric/RCTFabricUIManagerWrapper.mm b/React/Fabric/RCTFabricUIManagerWrapper.mm
index 892669145d0a..811aa8d0ad81 100644
--- a/React/Fabric/RCTFabricUIManagerWrapper.mm
+++ b/React/Fabric/RCTFabricUIManagerWrapper.mm
@@ -7,7 +7,11 @@
 
 #import "RCTFabricUIManagerWrapper.h"
 
-#include <fabric/FabricUIManager.h>
+#include <fabric/uimanager/FabricUIManager.h>
+
+#include <folly/dynamic.h>
+#include <folly/json.h>
+
 
 #import "RCTFabricPlatformUIOperationManager.h"
 
diff --git a/ReactCommon/fabric/BUCK b/ReactCommon/fabric/BUCK
deleted file mode 100644
index 62a6c5ccab56..000000000000
--- a/ReactCommon/fabric/BUCK
+++ /dev/null
@@ -1,46 +0,0 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
-
-rn_xplat_cxx_library(
-    name = "fabric",
-    srcs = glob(["*.cpp"]),
-    header_namespace = "",
-    exported_headers = subdir_glob(
-        [
-            ("", "*.h"),
-        ],
-        prefix = "fabric",
-    ),
-    compiler_flags = [
-        "-fexceptions",
-        "-frtti",
-        "-std=c++14",
-        "-Wall",
-    ],
-    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
-    force_static = True,
-    preprocessor_flags = [
-        "-DLOG_TAG=\"ReactNative\"",
-        "-DWITH_FBSYSTRACE=1",
-    ],
-    visibility = [
-        "PUBLIC",
-    ],
-    deps = [
-        "xplat//fbsystrace:fbsystrace",
-        "xplat//folly:headers_only",
-        "xplat//folly:memory",
-        "xplat//folly:molly",
-        "xplat//third-party/glog:glog",
-        react_native_xplat_target("fabric/core:core"),
-        react_native_xplat_target("fabric/uimanager:uimanager"),
-        react_native_xplat_target("fabric/view:view"),
-    ],
-)
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 8b3e3ad6b73c..dc7939377d97 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -46,7 +46,8 @@ rn_xplat_cxx_library(
         "xplat//folly:memory",
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
-        react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/view:view"),
     ],
 )
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index d35762482531..14adad47c8ce 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -7,6 +7,8 @@
 
 #include "FabricUIManager.h"
 
+#include <glog/logging.h>
+
 #include <fabric/core/LayoutContext.h>
 #include <fabric/view/ViewComponentDescriptor.h>
 #include <fabric/view/ViewProps.h>
@@ -97,12 +99,14 @@ void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedLi
   LayoutContext layoutContext = LayoutContext();
   layoutContext.affectedShadowNodes = std::make_shared<std::unordered_set<SharedLayoutableShadowNode>>();
 
+  LOG(INFO) << "Shadow tree *before* layout: \n" << viewShadowNode->getDebugDescription() ;
+
   auto nonConstViewShadowNode = std::const_pointer_cast<ViewShadowNode>(viewShadowNode);
   nonConstViewShadowNode->layout(layoutContext);
 
   rootShadowNode->sealRecursive();
 
-  printf("## layouted rootShadowNode: %s \n", nonConstViewShadowNode->getDebugDescription(0).c_str());
+  LOG(INFO) << "Shadow tree *after* layout: \n" << nonConstViewShadowNode->getDebugDescription();
 }
 
 } // namespace react

From 378da73201eeabf92d9aca81ba5396967eb22537 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 18 Mar 2018 19:04:32 -0700
Subject: [PATCH 0059/1109] DebugStringConvertibleOptions: Formating

Summary:
DebugStringConvertibleOptions allows pretty-format debug strings.
https://pxl.cl/ch0m

Reviewed By: fkgozali

Differential Revision: D7312622

fbshipit-source-id: 0ed62520bbc521790bedf5a6d18c796b42f85658
---
 .../fabric/debug/DebugStringConvertible.cpp   | 29 +++++++++++++------
 .../fabric/debug/DebugStringConvertible.h     | 11 +++++--
 2 files changed, 28 insertions(+), 12 deletions(-)

diff --git a/ReactCommon/fabric/debug/DebugStringConvertible.cpp b/ReactCommon/fabric/debug/DebugStringConvertible.cpp
index 8186297643e9..f669c1bd5ad2 100644
--- a/ReactCommon/fabric/debug/DebugStringConvertible.cpp
+++ b/ReactCommon/fabric/debug/DebugStringConvertible.cpp
@@ -10,23 +10,31 @@
 namespace facebook {
 namespace react {
 
-std::string DebugStringConvertible::getDebugChildrenDescription(int level) const {
+std::string DebugStringConvertible::getDebugChildrenDescription(DebugStringConvertibleOptions options, int depth) const {
+  if (depth >= options.maximumDepth) {
+    return "";
+  }
+
   std::string childrenString = "";
 
   for (auto child : getDebugChildren()) {
-    childrenString += child->getDebugDescription(level + 1);
+    childrenString += child->getDebugDescription(options, depth + 1);
   }
 
   return childrenString;
 }
 
-std::string DebugStringConvertible::getDebugPropsDescription(int level) const {
+std::string DebugStringConvertible::getDebugPropsDescription(DebugStringConvertibleOptions options, int depth) const {
+  if (depth >= options.maximumDepth) {
+    return "";
+  }
+
   std::string propsString = "";
 
   for (auto prop : getDebugProps()) {
     auto name = prop->getDebugName();
     auto value = prop->getDebugValue();
-    auto children = prop->getDebugPropsDescription(level + 1);
+    auto children = prop->getDebugPropsDescription(options, depth + 1);
     auto valueAndChildren = value + (children.empty() ? "" : "(" + children + ")");
     propsString += " " + name + (valueAndChildren.empty() ? "" : "=" + valueAndChildren);
   }
@@ -39,16 +47,19 @@ std::string DebugStringConvertible::getDebugPropsDescription(int level) const {
   return propsString;
 }
 
-std::string DebugStringConvertible::getDebugDescription(int level) const {
+std::string DebugStringConvertible::getDebugDescription(DebugStringConvertibleOptions options, int depth) const {
   std::string nameString = getDebugName();
   std::string valueString = getDebugValue();
-  std::string childrenString = getDebugChildrenDescription(level);
-  std::string propsString = getDebugPropsDescription(level);
+  std::string childrenString = getDebugChildrenDescription(options, depth + 1);
+  std::string propsString = getDebugPropsDescription(options, depth /* The first-level props are considered as same-depth things. */);
+
+  std::string leading = options.format ? std::string(depth, '\t') : "";
+  std::string trailing = options.format ? "\n" : "";
 
-  return "<" + nameString +
+  return leading + "<" + nameString +
     (valueString.empty() ? "" : "=" + valueString) +
     (propsString.empty() ? "" : " " + propsString) +
-    (childrenString.empty() ? "/>" : ">" + childrenString + "</" + nameString + ">");
+    (childrenString.empty() ? "/>" + trailing : ">" + trailing + childrenString + leading + "</" + nameString + ">" + trailing);
 }
 
 std::string DebugStringConvertible::getDebugName() const {
diff --git a/ReactCommon/fabric/debug/DebugStringConvertible.h b/ReactCommon/fabric/debug/DebugStringConvertible.h
index b743a933243d..b47d0c0d435f 100644
--- a/ReactCommon/fabric/debug/DebugStringConvertible.h
+++ b/ReactCommon/fabric/debug/DebugStringConvertible.h
@@ -18,6 +18,11 @@ class DebugStringConvertible;
 using SharedDebugStringConvertible = std::shared_ptr<const DebugStringConvertible>;
 using SharedDebugStringConvertibleList = std::vector<const SharedDebugStringConvertible>;
 
+struct DebugStringConvertibleOptions {
+  bool format {true};
+  int maximumDepth {INT_MAX};
+};
+
 // Abstract class describes conformance to DebugStringConvertible concept
 // and implements basic recursive debug string assembly algorithm.
 // Use this as a base class for providing a debugging textual representation
@@ -47,12 +52,12 @@ class DebugStringConvertible {
   // Returns a string which represents the object in a human-readable way.
   // Default implementation returns a description of the subtree
   // rooted at this node, represented in XML-like format.
-  virtual std::string getDebugDescription(int level = 0) const;
+  virtual std::string getDebugDescription(DebugStringConvertibleOptions options = {}, int depth = 0) const;
 
   // Do same as `getDebugDescription` but return only *children* and
   // *properties* parts (which are used in `getDebugDescription`).
-  virtual std::string getDebugPropsDescription(int level = 0) const;
-  virtual std::string getDebugChildrenDescription(int level = 0) const;
+  virtual std::string getDebugPropsDescription(DebugStringConvertibleOptions options = {}, int depth = 0) const;
+  virtual std::string getDebugChildrenDescription(DebugStringConvertibleOptions options = {}, int depth = 0) const;
 };
 
 } // namespace react

From 263d04d756321b3250d9ae700101f52d9663a2f0 Mon Sep 17 00:00:00 2001
From: tuncaulubilge <tunca.ulubilge@gmail.com>
Date: Sun, 18 Mar 2018 20:04:45 -0700
Subject: [PATCH 0060/1109] Added nestedScrollEnabled prop to scroll view for
 android

Summary:
Nested scrolling in scrollViews, listViews and flatLists are enabled on iOS by default, but needs to be enabled manually on Android. This PR introduces a `nestedScrollEnabled` property to ScrollViews to support nested scrolling on Android 21 and above.

Enabling nested scroll will resolve issues with coordinator layout in android and required to support a collapsing toolbar.

Tested on the test app. We are also using this property in our app currently to support scrolling behaviour required by coordinator layouts.

[ANDROID] [ENHANCEMENT] [ScrollView] - Added a prop to enable nested scrolling
Closes https://github.com/facebook/react-native/pull/18299

Reviewed By: sahrens

Differential Revision: D7256604

Pulled By: mdvacca

fbshipit-source-id: fb8b7f1b5bed39837a2066db7f2a8798d52a3fd6
---
 Libraries/Components/ScrollView/ScrollView.js          |  6 ++++++
 .../views/scroll/ReactHorizontalScrollViewManager.java |  8 ++++++++
 .../react/views/scroll/ReactScrollViewManager.java     | 10 +++++++++-
 3 files changed, 23 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 5d0d007fe29f..29b9d57ca2a2 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -275,6 +275,12 @@ const ScrollView = createReactClass({
      * @platform ios
      */
     minimumZoomScale: PropTypes.number,
+     /**
+     * Enables nested scrolling for Android API level 21+.
+     * Nested scrolling is supported by default on iOS
+     * @platform android
+     */
+    nestedScrollEnabled: PropTypes.bool,
     /**
      * Called when the momentum scroll starts (scroll which occurs as the ScrollView glides to a stop).
      */
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
index f0d9a6011684..e6536a6e53eb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
@@ -8,7 +8,9 @@
 package com.facebook.react.views.scroll;
 
 import android.graphics.Color;
+import android.support.v4.view.ViewCompat;
 import android.util.DisplayMetrics;
+
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
@@ -21,6 +23,7 @@
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.annotations.ReactPropGroup;
 import com.facebook.yoga.YogaConstants;
+
 import javax.annotation.Nullable;
 
 /**
@@ -120,6 +123,11 @@ public void setOverScrollMode(ReactHorizontalScrollView view, String value) {
     view.setOverScrollMode(ReactScrollViewHelper.parseOverScrollMode(value));
   }
 
+  @ReactProp(name = "nestedScrollEnabled")
+  public void setNestedScrollEnabled(ReactHorizontalScrollView view, boolean value) {
+    ViewCompat.setNestedScrollingEnabled(view, value);
+  }
+
   @Override
   public void receiveCommand(
       ReactHorizontalScrollView scrollView,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.java
index ecab38a6d16e..df520b5e4669 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.java
@@ -9,6 +9,8 @@
 
 import android.annotation.TargetApi;
 import android.graphics.Color;
+import android.support.v4.view.ViewCompat;
+
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.module.annotations.ReactModule;
@@ -21,8 +23,9 @@
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.annotations.ReactPropGroup;
 import com.facebook.yoga.YogaConstants;
-import java.util.Map;
+
 import javax.annotation.Nullable;
+import java.util.Map;
 
 /**
  * View manager for {@link ReactScrollView} components.
@@ -121,6 +124,11 @@ public void setOverScrollMode(ReactScrollView view, String value) {
     view.setOverScrollMode(ReactScrollViewHelper.parseOverScrollMode(value));
   }
 
+  @ReactProp(name = "nestedScrollEnabled")
+  public void setNestedScrollEnabled(ReactScrollView view, boolean value) {
+    ViewCompat.setNestedScrollingEnabled(view, value);
+  }
+
   @Override
   public @Nullable Map<String, Integer> getCommandsMap() {
     return ReactScrollViewCommandHelper.getCommandsMap();

From f42b5892a16b71f4c7b09892f142b2b89c5388c8 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Sun, 18 Mar 2018 23:49:51 -0700
Subject: [PATCH 0061/1109] iOS C++: Add ICxxExceptionManager to access
 RCTExceptionsManager native module

Summary: It is sometimes useful to report soft/fatal errors from C++ (native) to the same RCTExceptionsManager that is already handling JS exceptions. `ICxxExceptionManager` is an approach to provide such access, which impl provided for ObjC++.

Reviewed By: shergin

Differential Revision: D7224944

fbshipit-source-id: 8c607226b67851d46f4c787f5b6e6c8cb6a1afea
---
 React/Base/RCTLog.h                           |  7 ++
 React/Base/RCTLog.mm                          | 65 ++++++++++---------
 React/CxxExceptions/RCTCxxExceptionManager.h  | 27 ++++++++
 React/CxxExceptions/RCTCxxExceptionManager.mm | 31 +++++++++
 React/Modules/RCTExceptionsManager.h          |  3 +
 ReactCommon/exceptions/BUCK                   | 40 ++++++++++++
 ReactCommon/exceptions/ExceptionManager.h     | 24 +++++++
 7 files changed, 168 insertions(+), 29 deletions(-)
 create mode 100644 React/CxxExceptions/RCTCxxExceptionManager.h
 create mode 100644 React/CxxExceptions/RCTCxxExceptionManager.mm
 create mode 100644 ReactCommon/exceptions/BUCK
 create mode 100644 ReactCommon/exceptions/ExceptionManager.h

diff --git a/React/Base/RCTLog.h b/React/Base/RCTLog.h
index 9f9317da410c..6ef09d620c55 100644
--- a/React/Base/RCTLog.h
+++ b/React/Base/RCTLog.h
@@ -120,6 +120,13 @@ RCT_EXTERN void RCTPerformBlockWithLogFunction(void (^block)(void), RCTLogFuncti
  */
 RCT_EXTERN void RCTPerformBlockWithLogPrefix(void (^block)(void), NSString *prefix);
 
+/**
+ * This method computes the current call stack, useful for error reporting.
+ */
+RCT_EXTERN NSArray<NSDictionary *> *RCTGetCallStack(const char *fileName, int lineNumber);
+
+#define RCT_CALLSTACK RCTGetCallStack(__FILE__, __LINE__)
+
 /**
  * Private logging function - ignore this.
  */
diff --git a/React/Base/RCTLog.mm b/React/Base/RCTLog.mm
index edb92fe01468..4e65fa0cc87b 100644
--- a/React/Base/RCTLog.mm
+++ b/React/Base/RCTLog.mm
@@ -197,6 +197,41 @@ void RCTPerformBlockWithLogPrefix(void (^block)(void), NSString *prefix)
   return _regex;
 }
 
+NSArray<NSDictionary *>* RCTGetCallStack(const char *fileName, int lineNumber)
+{
+  NSArray<NSString *> *stackSymbols = [NSThread callStackSymbols];
+  NSMutableArray<NSDictionary *> *stack =
+  [NSMutableArray arrayWithCapacity:(stackSymbols.count - 1)];
+  [stackSymbols enumerateObjectsUsingBlock:^(NSString *frameSymbols, NSUInteger idx, __unused BOOL *stop) {
+    if (idx == 0) {
+      // don't include the current frame
+      return;
+    }
+
+    NSRange range = NSMakeRange(0, frameSymbols.length);
+    NSTextCheckingResult *match = [nativeStackFrameRegex() firstMatchInString:frameSymbols options:0 range:range];
+    if (!match) {
+      return;
+    }
+
+    NSString *methodName = [frameSymbols substringWithRange:[match rangeAtIndex:1]];
+    char *demangledName = abi::__cxa_demangle([methodName UTF8String], NULL, NULL, NULL);
+    if (demangledName) {
+      methodName = @(demangledName);
+      free(demangledName);
+    }
+
+    if (idx == 1 && fileName) {
+      NSString *file = [@(fileName) componentsSeparatedByString:@"/"].lastObject;
+      [stack addObject:@{@"methodName": methodName, @"file": file, @"lineNumber": @(lineNumber)}];
+    } else {
+      [stack addObject:@{@"methodName": methodName}];
+    }
+  }];
+
+  return [stack copy];
+}
+
 void _RCTLogNativeInternal(RCTLogLevel level, const char *fileName, int lineNumber, NSString *format, ...)
 {
   RCTLogFunction logFunction = RCTGetLocalLogFunction();
@@ -217,35 +252,7 @@ void _RCTLogNativeInternal(RCTLogLevel level, const char *fileName, int lineNumb
 
     // Log to red box in debug mode.
     if (RCTSharedApplication() && level >= RCTLOG_REDBOX_LEVEL) {
-      NSArray<NSString *> *stackSymbols = [NSThread callStackSymbols];
-      NSMutableArray<NSDictionary *> *stack =
-        [NSMutableArray arrayWithCapacity:(stackSymbols.count - 1)];
-      [stackSymbols enumerateObjectsUsingBlock:^(NSString *frameSymbols, NSUInteger idx, __unused BOOL *stop) {
-        if (idx == 0) {
-          // don't include the current frame
-          return;
-        }
-
-        NSRange range = NSMakeRange(0, frameSymbols.length);
-        NSTextCheckingResult *match = [nativeStackFrameRegex() firstMatchInString:frameSymbols options:0 range:range];
-        if (!match) {
-          return;
-        }
-
-        NSString *methodName = [frameSymbols substringWithRange:[match rangeAtIndex:1]];
-        char *demangledName = abi::__cxa_demangle([methodName UTF8String], NULL, NULL, NULL);
-        if (demangledName) {
-          methodName = @(demangledName);
-          free(demangledName);
-        }
-
-        if (idx == 1 && fileName) {
-          NSString *file = [@(fileName) componentsSeparatedByString:@"/"].lastObject;
-          [stack addObject:@{@"methodName": methodName, @"file": file, @"lineNumber": @(lineNumber)}];
-        } else {
-          [stack addObject:@{@"methodName": methodName}];
-        }
-      }];
+      NSArray<NSDictionary *> *stack = RCT_CALLSTACK;
 
       dispatch_async(dispatch_get_main_queue(), ^{
         // red box is thread safe, but by deferring to main queue we avoid a startup
diff --git a/React/CxxExceptions/RCTCxxExceptionManager.h b/React/CxxExceptions/RCTCxxExceptionManager.h
new file mode 100644
index 000000000000..c8e3de44c40f
--- /dev/null
+++ b/React/CxxExceptions/RCTCxxExceptionManager.h
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <cxxreact/ExceptionManager.h>
+
+namespace facebook {
+namespace react {
+
+/**
+ * Connector class (from C++ to ObjC++) to allow FabricUIManager to invoke native UI operations/updates.
+ * UIKit-related impl doesn't live here, but this class gets passed to the FabricUIManager C++ impl directly.
+ */
+class RCTCxxExceptionManager : public ExceptionManager {
+public:
+
+  virtual void handleSoftException(const std::exception& e) const override;
+  virtual void handleFatalException(const std::exception& e) const override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/React/CxxExceptions/RCTCxxExceptionManager.mm b/React/CxxExceptions/RCTCxxExceptionManager.mm
new file mode 100644
index 000000000000..61e636378ddd
--- /dev/null
+++ b/React/CxxExceptions/RCTCxxExceptionManager.mm
@@ -0,0 +1,31 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTCxxExceptionManager.h"
+
+#import <Foundation/Foundation.h>
+
+#import <React/RCTBridge.h>
+#import <React/RCTBridge+Private.h>
+#import <React/RCTExceptionsManager.h>
+#import <React/RCTLog.h>
+
+namespace facebook {
+namespace react {
+
+void RCTCxxExceptionManager::handleSoftException(const std::exception& e) const {
+  RCTExceptionsManager *manager = [[RCTBridge currentBridge] moduleForClass:[RCTExceptionsManager class]];
+  [manager reportSoftException:[NSString stringWithUTF8String:e.what()] stack:RCT_CALLSTACK exceptionId:@0];
+}
+
+void RCTCxxExceptionManager::handleFatalException(const std::exception& e) const {
+  RCTExceptionsManager *manager = [[RCTBridge currentBridge] moduleForClass:[RCTExceptionsManager class]];
+  [manager reportFatalException:[NSString stringWithUTF8String:e.what()] stack:RCT_CALLSTACK exceptionId:@0];
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/React/Modules/RCTExceptionsManager.h b/React/Modules/RCTExceptionsManager.h
index 57e81fb9e490..950cdaeab296 100644
--- a/React/Modules/RCTExceptionsManager.h
+++ b/React/Modules/RCTExceptionsManager.h
@@ -23,6 +23,9 @@
 
 - (instancetype)initWithDelegate:(id<RCTExceptionsManagerDelegate>)delegate;
 
+- (void)reportSoftException:(NSString *)message stack:(NSArray<NSDictionary *> *)stack exceptionId:(nonnull NSNumber *)exceptionId;
+- (void)reportFatalException:(NSString *)message stack:(NSArray<NSDictionary *> *)stack exceptionId:(nonnull NSNumber *)exceptionId;
+
 @property (nonatomic, weak) id<RCTExceptionsManagerDelegate> delegate;
 
 @property (nonatomic, assign) NSUInteger maxReloadAttempts;
diff --git a/ReactCommon/exceptions/BUCK b/ReactCommon/exceptions/BUCK
new file mode 100644
index 000000000000..352bc036fdff
--- /dev/null
+++ b/ReactCommon/exceptions/BUCK
@@ -0,0 +1,40 @@
+load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+
+rn_xplat_cxx_library(
+    name = "exceptions",
+    srcs = glob(["*.cpp"]),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "cxxreact",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    force_static = True,
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    visibility = [
+        "PUBLIC",
+    ],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//third-party/glog:glog",
+    ],
+)
diff --git a/ReactCommon/exceptions/ExceptionManager.h b/ReactCommon/exceptions/ExceptionManager.h
new file mode 100644
index 000000000000..ba07912bfa59
--- /dev/null
+++ b/ReactCommon/exceptions/ExceptionManager.h
@@ -0,0 +1,24 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <exception>
+
+namespace facebook {
+namespace react {
+
+/**
+ * An abstract class for C++-based exception handling that differentiates
+ * soft exceptions from fatal exceptions.
+ */
+class ExceptionManager {
+public:
+  virtual void handleSoftException(const std::exception &e) const = 0;
+  virtual void handleFatalException(const std::exception &e) const = 0;
+};
+
+} // namespace react
+} // namespace facebook

From 53a0470b83416d3eb07931df00385de071f231a4 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Sun, 18 Mar 2018 23:49:52 -0700
Subject: [PATCH 0062/1109] iOS JSC: Use ICxxExceptionManager to report
 exception

Reviewed By: shergin

Differential Revision: D7224945

fbshipit-source-id: 8aadbc04c700d6e965be311085d95332571b00b0
---
 React/Fabric/RCTFabricUIManagerWrapper.h  |  2 ++
 React/Fabric/RCTFabricUIManagerWrapper.mm | 10 ++++++++--
 2 files changed, 10 insertions(+), 2 deletions(-)

diff --git a/React/Fabric/RCTFabricUIManagerWrapper.h b/React/Fabric/RCTFabricUIManagerWrapper.h
index d40ef78c359c..234668bb1b09 100644
--- a/React/Fabric/RCTFabricUIManagerWrapper.h
+++ b/React/Fabric/RCTFabricUIManagerWrapper.h
@@ -17,6 +17,7 @@ namespace facebook {
 namespace react {
 
 class FabricUIManager;
+class ExceptionManager;
 
 } // namespace react
 } // namespace facebook
@@ -29,6 +30,7 @@ using namespace facebook::react;
 @interface RCTFabricUIManagerWrapper : NSObject <RCTInvalidating>
 
 - (std::shared_ptr<FabricUIManager>)manager;
+- (std::shared_ptr<ExceptionManager>)exceptionManager;
 
 @end
 
diff --git a/React/Fabric/RCTFabricUIManagerWrapper.mm b/React/Fabric/RCTFabricUIManagerWrapper.mm
index 811aa8d0ad81..d3b6839eba06 100644
--- a/React/Fabric/RCTFabricUIManagerWrapper.mm
+++ b/React/Fabric/RCTFabricUIManagerWrapper.mm
@@ -7,18 +7,18 @@
 
 #import "RCTFabricUIManagerWrapper.h"
 
+#include <React/RCTCxxExceptionManager.h>
 #include <fabric/uimanager/FabricUIManager.h>
-
 #include <folly/dynamic.h>
 #include <folly/json.h>
 
-
 #import "RCTFabricPlatformUIOperationManager.h"
 
 // This file contains experimental placeholders, nothing is finalized.
 @implementation RCTFabricUIManagerWrapper
 {
   std::shared_ptr<FabricUIManager> _manager;
+  std::shared_ptr<ExceptionManager> _exceptionManager;
   std::shared_ptr<IFabricPlatformUIOperationManager> _platformUIOperationManager;
 }
 
@@ -26,6 +26,7 @@ - (instancetype)init
 {
   self = [super init];
   if (self) {
+    _exceptionManager = std::make_shared<RCTCxxExceptionManager>();
     _platformUIOperationManager = std::make_shared<RCTFabricPlatformUIOperationManagerConnector>();
     _manager = std::make_shared<FabricUIManager>(_platformUIOperationManager);
   }
@@ -37,6 +38,11 @@ - (instancetype)init
   return _manager;
 }
 
+- (std::shared_ptr<ExceptionManager>)exceptionManager
+{
+  return _exceptionManager;
+}
+
 - (void)invalidate
 {
 }

From def789cd7edcd904aac56750fd58db63dfae38d2 Mon Sep 17 00:00:00 2001
From: Cristiano Santos <cristianomnsantos@gmail.com>
Date: Mon, 19 Mar 2018 02:10:36 -0700
Subject: [PATCH 0063/1109] Wrong height when TextInput has an empty string

Summary:
<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

The caret/cursor did not appear when the TextInput was empty. Found that the cause was because the frame of the TextInput had an height of 0

Just fill and clear a TextInput and the caret/cursor will always appear there.

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[CATEGORY] [TYPE] [LOCATION] - MESSAGE

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
[IOS] [BUGFIX] [TextInput] - This was causing the cursor/caret to not appear since the size of the frame had an height of 0.
Closes https://github.com/facebook/react-native/pull/18355

Differential Revision: D7319723

Pulled By: shergin

fbshipit-source-id: b0249ab5493b6ac310d1898ff20c0bad78cf82c9
---
 Libraries/Text/TextInput/RCTBaseTextInputShadowView.m | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/Text/TextInput/RCTBaseTextInputShadowView.m b/Libraries/Text/TextInput/RCTBaseTextInputShadowView.m
index d1fdbcd3d250..f5a7ca172475 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputShadowView.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputShadowView.m
@@ -180,8 +180,8 @@ - (NSAttributedString *)measurableAttributedText
     // Placeholder also can represent the intrinsic size when it is visible.
     NSString *text = self.placeholder;
     if (!text.length) {
-      // Zero-width space
-      text = @"\u200B";
+      // Note: `zero-width space` is insufficient in some cases.
+      text = @"I";
     }
     attributedText = [[NSAttributedString alloc] initWithString:text attributes:self.textAttributes.effectiveTextAttributes];
   }

From c73242938c2b9d45f9da02b201a02f3b5993eaf5 Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Mon, 19 Mar 2018 09:30:35 -0700
Subject: [PATCH 0064/1109] Make access to SourceCode Native Extension lazy

Reviewed By: fromcelticpark

Differential Revision: D6987478

fbshipit-source-id: 6d600131239be34480bd1c5a0ca84b4fab360386
---
 Libraries/Image/resolveAssetSource.js | 26 +++++++++++++++++---------
 1 file changed, 17 insertions(+), 9 deletions(-)

diff --git a/Libraries/Image/resolveAssetSource.js b/Libraries/Image/resolveAssetSource.js
index 24fec6ef33c7..0d160a28077d 100644
--- a/Libraries/Image/resolveAssetSource.js
+++ b/Libraries/Image/resolveAssetSource.js
@@ -17,11 +17,26 @@ const AssetSourceResolver = require('AssetSourceResolver');
 import type { ResolvedAssetSource } from 'AssetSourceResolver';
 
 let _customSourceTransformer, _serverURL, _scriptURL;
+
 let _sourceCodeScriptURL: ?string;
+function getSourceCodeScriptURL(): ?string {
+  if (_sourceCodeScriptURL) {
+    return _sourceCodeScriptURL;
+  }
+
+  let sourceCode = global.nativeExtensions && global.nativeExtensions.SourceCode;
+  if (!sourceCode) {
+    const NativeModules = require('NativeModules');
+    sourceCode = NativeModules && NativeModules.SourceCode;
+  }
+  _sourceCodeScriptURL = sourceCode.scriptURL;
+  return _sourceCodeScriptURL;
+}
 
 function getDevServerURL(): ?string {
   if (_serverURL === undefined) {
-    const match = _sourceCodeScriptURL && _sourceCodeScriptURL.match(/^https?:\/\/.*?\//);
+    const sourceCodeScriptURL = getSourceCodeScriptURL();
+    const match = sourceCodeScriptURL && sourceCodeScriptURL.match(/^https?:\/\/.*?\//);
     if (match) {
       // jsBundle was loaded from network
       _serverURL = match[0];
@@ -51,7 +66,7 @@ function _coerceLocalScriptURL(scriptURL: ?string): ?string {
 
 function getScriptURL(): ?string {
   if (_scriptURL === undefined) {
-    _scriptURL = _coerceLocalScriptURL(_sourceCodeScriptURL);
+    _scriptURL = _coerceLocalScriptURL(getSourceCodeScriptURL());
   }
   return _scriptURL;
 }
@@ -87,13 +102,6 @@ function resolveAssetSource(source: any): ?ResolvedAssetSource {
   return resolver.defaultAsset();
 }
 
-let sourceCode = global.nativeExtensions && global.nativeExtensions.SourceCode;
-if (!sourceCode) {
-  const NativeModules = require('NativeModules');
-  sourceCode = NativeModules && NativeModules.SourceCode;
-}
-_sourceCodeScriptURL = sourceCode && sourceCode.scriptURL;
-
 module.exports = resolveAssetSource;
 module.exports.pickScale = AssetSourceResolver.pickScale;
 module.exports.setCustomSourceTransformer = setCustomSourceTransformer;

From 15bc6d1e0b6f14ed42100515fef7a26419e71b0e Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Mon, 19 Mar 2018 10:06:58 -0700
Subject: [PATCH 0065/1109] Added console warning to InputAccessoryView

Reviewed By: mmmulani

Differential Revision: D7305377

fbshipit-source-id: 4a9888b5592014956c3aa44baffb2ac3a0329b88
---
 Libraries/Components/TextInput/InputAccessoryView.js | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/Libraries/Components/TextInput/InputAccessoryView.js b/Libraries/Components/TextInput/InputAccessoryView.js
index cd12758435ff..73d83c03a22b 100644
--- a/Libraries/Components/TextInput/InputAccessoryView.js
+++ b/Libraries/Components/TextInput/InputAccessoryView.js
@@ -90,6 +90,8 @@ type Props = {
 
 class InputAccessoryView extends React.Component<Props> {
   render(): React.Node {
+    console.warn('<InputAccessoryView> is not supported on Android yet.');
+
     if (React.Children.count(this.props.children) === 0) {
       return null;
     }

From 12c208cbd483c13587b4977c48f582e61eaea50e Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Mon, 19 Mar 2018 10:34:57 -0700
Subject: [PATCH 0066/1109] Create a new instrumentation test that does not
 enforce rendering a single RN component

Reviewed By: mdvacca

Differential Revision: D7293466

fbshipit-source-id: 8ddaf9a52f4d6324e8b37f3c6fd4d3e0db6f3a12
---
 .../react/testing/ReactAppTestActivity.java   |  96 ++++++++------
 .../testing/ReactInstrumentationTest.java     | 124 ++++++++++++++++++
 2 files changed, 181 insertions(+), 39 deletions(-)
 create mode 100644 ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index 0a68ad1ed5df..341c87814942 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -176,8 +176,36 @@ public void loadApp(
     String bundleName,
     boolean useDevSupport,
     UIImplementationProvider uiImplementationProvider) {
+    loadBundle(spec, bundleName, useDevSupport, uiImplementationProvider);
+    renderComponent(appKey, initialProps);
+  }
 
+  public void renderComponent(String appKey, @Nullable Bundle initialProps) {
     final CountDownLatch currentLayoutEvent = mLayoutEvent = new CountDownLatch(1);
+    Assertions.assertNotNull(mReactRootView).getViewTreeObserver().addOnGlobalLayoutListener(
+        new ViewTreeObserver.OnGlobalLayoutListener() {
+          @Override
+          public void onGlobalLayout() {
+            currentLayoutEvent.countDown();
+          }
+        });
+    Assertions.assertNotNull(mReactRootView)
+        .startReactApplication(mReactInstanceManager, appKey, initialProps);
+  }
+
+  public void loadBundle(
+      ReactInstanceSpecForTest spec,
+      String bundleName,
+      boolean useDevSupport) {
+    loadBundle(spec, bundleName, useDevSupport, null);
+  }
+
+  public void loadBundle(
+      ReactInstanceSpecForTest spec,
+      String bundleName,
+      boolean useDevSupport,
+      UIImplementationProvider uiImplementationProvider) {
+
     mBridgeIdleSignaler = new ReactBridgeIdleSignaler();
 
     ReactInstanceManagerBuilder builder =
@@ -200,49 +228,39 @@ public void loadApp(
         .setBridgeIdleDebugListener(mBridgeIdleSignaler)
         .setInitialLifecycleState(mLifecycleState)
         .setJSIModulesProvider(
-          new JSIModulesProvider() {
-            @Override
-            public List<JSIModuleHolder> getJSIModules(
-              final ReactApplicationContext reactApplicationContext,
-              final JavaScriptContextHolder jsContext) {
-
-              List<JSIModuleHolder> modules = new ArrayList<>();
-              modules.add(
-                new JSIModuleHolder() {
-
-                  @Override
-                  public Class<? extends JSIModule> getJSIModuleClass() {
-                    return UIManager.class;
-                  }
-
-                  @Override
-                  public FabricUIManager getJSIModule() {
-                    List<ViewManager> viewManagers =
-                      getReactInstanceManager().getOrCreateViewManagers(reactApplicationContext);
-                    FabricUIManager fabricUIManager =
-                      new FabricUIManager(
-                        reactApplicationContext, new ViewManagerRegistry(viewManagers));
-                    new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
-                    return fabricUIManager;
-                  }
-                });
-
-              return modules;
-            }})
+            new JSIModulesProvider() {
+              @Override
+              public List<JSIModuleHolder> getJSIModules(
+                  final ReactApplicationContext reactApplicationContext,
+                  final JavaScriptContextHolder jsContext) {
+
+                List<JSIModuleHolder> modules = new ArrayList<>();
+                modules.add(
+                    new JSIModuleHolder() {
+
+                      @Override
+                      public Class<? extends JSIModule> getJSIModuleClass() {
+                        return UIManager.class;
+                      }
+
+                      @Override
+                      public FabricUIManager getJSIModule() {
+                        List<ViewManager> viewManagers =
+                            getReactInstanceManager().getOrCreateViewManagers(reactApplicationContext);
+                        FabricUIManager fabricUIManager =
+                            new FabricUIManager(
+                                reactApplicationContext, new ViewManagerRegistry(viewManagers));
+                        new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
+                        return fabricUIManager;
+                      }
+                    });
+
+                return modules;
+              }})
         .setUIImplementationProvider(uiImplementationProvider);
 
     mReactInstanceManager = builder.build();
     mReactInstanceManager.onHostResume(this, this);
-
-    Assertions.assertNotNull(mReactRootView).getViewTreeObserver().addOnGlobalLayoutListener(
-        new ViewTreeObserver.OnGlobalLayoutListener() {
-          @Override
-          public void onGlobalLayout() {
-            currentLayoutEvent.countDown();
-          }
-        });
-    Assertions.assertNotNull(mReactRootView)
-        .startReactApplication(mReactInstanceManager, appKey, initialProps);
   }
 
   private ReactInstanceManager getReactInstanceManager() {
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
new file mode 100644
index 000000000000..fe6c7c687aec
--- /dev/null
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
@@ -0,0 +1,124 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.testing;
+
+import android.content.Intent;
+import android.test.ActivityInstrumentationTestCase2;
+import android.view.View;
+import android.view.ViewGroup;
+import com.facebook.react.bridge.ReactContext;
+import com.facebook.react.testing.idledetection.IdleWaiter;
+
+/**
+ * Base class for instrumentation tests that runs React based application.
+ *
+ * This is similar to ReactAppInstrumentationTestCase except ReactInstrumentationTest allows
+ * optional rendering of components. A test case can render no components or render multiple
+ * components.
+ */
+public abstract class ReactInstrumentationTest extends
+    ActivityInstrumentationTestCase2<ReactAppTestActivity> implements IdleWaiter {
+
+  public ReactInstrumentationTest() {
+    super(ReactAppTestActivity.class);
+  }
+
+  @Override
+  protected void setUp() throws Exception {
+    super.setUp();
+
+    Intent intent = new Intent();
+    intent.putExtra(ReactAppTestActivity.EXTRA_IS_FABRIC_TEST, isFabricTest());
+    setActivityIntent(intent);
+    final ReactAppTestActivity activity = getActivity();
+    try {
+      runTestOnUiThread(new Runnable() {
+        @Override
+        public void run() {
+          activity.loadBundle(
+              createReactInstanceSpecForTest(),
+              getBundleName(),
+              getEnableDevSupport());
+        }
+      });
+    } catch (Throwable t) {
+      throw new Exception("Unable to load react bundle " + getBundleName(), t);
+    }
+  }
+
+  /**
+   * Renders this component within this test's activity
+   */
+  public void renderComponent(final String componentName) throws Exception {
+    final ReactAppTestActivity activity = getActivity();
+    try {
+      runTestOnUiThread(new Runnable() {
+        @Override
+        public void run() {
+          activity.renderComponent(componentName, null);
+        }
+      });
+    } catch (Throwable t) {
+      throw new Exception("Unable to render component " + componentName, t);
+    }
+    assertTrue("Layout never occurred!", activity.waitForLayout(5000));
+    waitForBridgeAndUIIdle();
+  }
+
+  @Override
+  protected void tearDown() throws Exception {
+    ReactAppTestActivity activity = getActivity();
+    super.tearDown();
+    activity.waitForDestroy(5000);
+  }
+
+  public ViewGroup getRootView() {
+    return (ViewGroup) getActivity().getRootView();
+  }
+
+  public <T extends View> T getViewByTestId(String testID) {
+    return (T) ReactTestHelper
+        .getViewWithReactTestId((ViewGroup) getRootView().getParent(), testID);
+  }
+
+  public SingleTouchGestureGenerator createGestureGenerator() {
+    return new SingleTouchGestureGenerator(getRootView(), this);
+  }
+
+  public void waitForBridgeAndUIIdle() {
+    getActivity().waitForBridgeAndUIIdle();
+  }
+
+  public void waitForBridgeAndUIIdle(long timeoutMs) {
+    getActivity().waitForBridgeAndUIIdle(timeoutMs);
+  }
+
+  protected boolean getEnableDevSupport() {
+    return false;
+  }
+
+  protected boolean isFabricTest() {
+    return false;
+  }
+
+  /**
+   * Override this method to provide extra native modules to be loaded before the app starts
+   */
+  protected ReactInstanceSpecForTest createReactInstanceSpecForTest() {
+    return new ReactInstanceSpecForTest();
+  }
+
+  /**
+   * Implement this method to provide the bundle for this test
+   */
+  protected abstract String getBundleName();
+
+  protected ReactContext getReactContext() {
+    return getActivity().getReactContext();
+  }
+}

From 9d45de60accda028d11b715a3407119353a81d2c Mon Sep 17 00:00:00 2001
From: Mehdi Mulani <mehdi@fb.com>
Date: Mon, 19 Mar 2018 10:51:01 -0700
Subject: [PATCH 0067/1109] Properly tear down the reachabilityRef in
 RCTNetInfo

Summary: The pull request that added this (#17397) simply forgot to remove the callback, which would cause crashes if the RCTNetInfo module was ever deallocated. While that usually doesn't happen in apps, it can if the user logs out and you need to wipe all the RCT modules (to remove user data, for instance).

Reviewed By: PeteTheHeat

Differential Revision: D7322999

fbshipit-source-id: e49ec7311b39920f7b7743a5854c0dda1dbccc73
---
 Libraries/Network/RCTNetInfo.m | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Libraries/Network/RCTNetInfo.m b/Libraries/Network/RCTNetInfo.m
index afc3d1db3333..9b51a5c1ab4f 100644
--- a/Libraries/Network/RCTNetInfo.m
+++ b/Libraries/Network/RCTNetInfo.m
@@ -164,6 +164,7 @@ - (BOOL)setReachabilityStatus:(SCNetworkReachabilityFlags)flags
                   reject:(__unused RCTPromiseRejectBlock)reject)
 {
   SCNetworkReachabilityRef reachability = [self getReachabilityRef];
+  SCNetworkReachabilityUnscheduleFromRunLoop(reachability, CFRunLoopGetMain(), kCFRunLoopCommonModes);
   CFRelease(reachability);
   resolve(@{@"connectionType": _connectionType ?: RCTConnectionTypeUnknown,
             @"effectiveConnectionType": _effectiveConnectionType ?: RCTEffectiveConnectionTypeUnknown,

From 41db09d573a458fb7a0787a87ba55aa0f47af2ea Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Mon, 19 Mar 2018 12:23:57 -0700
Subject: [PATCH 0068/1109] Remove @xplat cell syntax in open source, part 2

Differential Revision: D7325421

fbshipit-source-id: 95e3ee0a6c41292b1d2e1fc8b0691861ad69468f
---
 ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
index ac6ce3d53025..38ed913d7aa4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
@@ -1,4 +1,4 @@
-load("@xplat//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library", "IS_OSS_BUILD")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library", "IS_OSS_BUILD")
 
 rn_android_library(
     name = "jsc",

From ff70ecf868cf12fc66b45dc1496391d0a1e9011f Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Mon, 19 Mar 2018 14:09:32 -0700
Subject: [PATCH 0069/1109] Fixed <TextInput> bug with autocapitalization

Reviewed By: shergin

Differential Revision: D7304936

fbshipit-source-id: ef587db89b64e7111dfdeb049c3a1a334c15430b
---
 Libraries/Text/TextInput/RCTBaseTextInputView.m | 12 +++++++++++-
 1 file changed, 11 insertions(+), 1 deletion(-)

diff --git a/Libraries/Text/TextInput/RCTBaseTextInputView.m b/Libraries/Text/TextInput/RCTBaseTextInputView.m
index 65885a4882a6..64a3a865c6d7 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputView.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputView.m
@@ -102,7 +102,17 @@ - (void)setAttributedText:(NSAttributedString *)attributedText
 {
   NSInteger eventLag = _nativeEventCount - _mostRecentEventCount;
 
-  if (eventLag == 0 && ![attributedText isEqualToAttributedString:self.backedTextInputView.attributedText]) {
+  // Remove tag attribute to ensure correct attributed string comparison.
+  NSMutableAttributedString *const backedTextInputViewTextCopy = [self.backedTextInputView.attributedText mutableCopy];
+  NSMutableAttributedString *const attributedTextCopy = [attributedText mutableCopy];
+
+  [backedTextInputViewTextCopy removeAttribute:RCTTextAttributesTagAttributeName
+                                         range:NSMakeRange(0, backedTextInputViewTextCopy.length)];
+
+  [attributedTextCopy removeAttribute:RCTTextAttributesTagAttributeName
+                                range:NSMakeRange(0, attributedTextCopy.length)];
+
+  if (eventLag == 0 && ![attributedTextCopy isEqualToAttributedString:backedTextInputViewTextCopy]) {
     UITextRange *selection = self.backedTextInputView.selectedTextRange;
     NSInteger oldTextLength = self.backedTextInputView.attributedText.string.length;
 

From 12535ae69d25930b438299fec7cbe6e16007e307 Mon Sep 17 00:00:00 2001
From: Naris Siamwalla <naris@fb.com>
Date: Mon, 19 Mar 2018 14:23:24 -0700
Subject: [PATCH 0070/1109] Fix clang-6 strictness surrounding virtual
 destructors

Reviewed By: smeenai

Differential Revision: D7326765

fbshipit-source-id: 9df477dfa89812e05e79b5e6d510bcbbc793381c
---
 ReactCommon/exceptions/ExceptionManager.h                       | 2 ++
 .../fabric/core/componentdescriptor/ComponentDescriptor.h       | 2 ++
 ReactCommon/fabric/core/shadownode/Props.h                      | 2 ++
 ReactCommon/fabric/debug/DebugStringConvertible.h               | 2 ++
 4 files changed, 8 insertions(+)

diff --git a/ReactCommon/exceptions/ExceptionManager.h b/ReactCommon/exceptions/ExceptionManager.h
index ba07912bfa59..842975b3ba87 100644
--- a/ReactCommon/exceptions/ExceptionManager.h
+++ b/ReactCommon/exceptions/ExceptionManager.h
@@ -16,6 +16,8 @@ namespace react {
  */
 class ExceptionManager {
 public:
+  virtual ~ExceptionManager() = default;
+
   virtual void handleSoftException(const std::exception &e) const = 0;
   virtual void handleFatalException(const std::exception &e) const = 0;
 };
diff --git a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
index 975900c91cf5..7b7b7a5578d6 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
@@ -26,6 +26,8 @@ using SharedComponentDescriptor = std::shared_ptr<ComponentDescriptor>;
 class ComponentDescriptor {
 public:
 
+  virtual ~ComponentDescriptor() = default;
+
   /*
    * Returns `componentHandle` associated with particular kind of components.
    * All `ShadowNode`s of this type must return same `componentHandle`.
diff --git a/ReactCommon/fabric/core/shadownode/Props.h b/ReactCommon/fabric/core/shadownode/Props.h
index da9f4f3b6f14..8a6a73834879 100644
--- a/ReactCommon/fabric/core/shadownode/Props.h
+++ b/ReactCommon/fabric/core/shadownode/Props.h
@@ -28,6 +28,8 @@ class Props:
   public virtual DebugStringConvertible {
 
 public:
+  virtual ~Props() = default;
+
   virtual void apply(const RawProps &rawProps);
 
 private:
diff --git a/ReactCommon/fabric/debug/DebugStringConvertible.h b/ReactCommon/fabric/debug/DebugStringConvertible.h
index b47d0c0d435f..8ef96d8882fd 100644
--- a/ReactCommon/fabric/debug/DebugStringConvertible.h
+++ b/ReactCommon/fabric/debug/DebugStringConvertible.h
@@ -31,6 +31,8 @@ struct DebugStringConvertibleOptions {
 class DebugStringConvertible {
 
 public:
+  virtual ~DebugStringConvertible() = default;
+
   // Returns a name of the object.
   // Default implementation returns "Node".
   virtual std::string getDebugName() const;

From 75a735976d039c6d2db815d79e99731f086e306e Mon Sep 17 00:00:00 2001
From: Frederic Barthelemy <git@fbartho.com>
Date: Mon, 19 Mar 2018 15:10:14 -0700
Subject: [PATCH 0071/1109] RCTObjcExecutor: fix initializer-list
 initialization order build warning.

Summary:
Fixes: #18384

Previously line 42 had a warning of: `Field 'm_jsThread' will be initialized after field 'm_delegate'`

This appears to be because the private member fields are declared in a different order than the initializer-list was told to initialize things.

I chose to re-order the initializer list because that fixes the warning by matching the code structure to what the compiler was telling us it was going to do.

An alternate fix would be to change the order of the member variables declared in the `private:` section to match the coded order in the initializer list. This might be the right move if the initializer list had the correct intent, but this would be a breaking change from a behavior perspective, so I'd need somebody with more knowledge to suggest this is the right move.

A. Examine line to see the warning is gone.
B. Get a C++ guru to figure out the intent of this file and see if this actually exposed a bug that recommends we go with the alternate fix suggested above.

[IOS][MINOR][React/CxxBridge/] - Build warning fix

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[CATEGORY] [TYPE] [LOCATION] - MESSAGE

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18385

Differential Revision: D7328272

Pulled By: mhorowitz

fbshipit-source-id: 59d7ace6222c4609ac7d023f97e522e85e02a9db
---
 React/CxxBridge/RCTObjcExecutor.mm | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/CxxBridge/RCTObjcExecutor.mm b/React/CxxBridge/RCTObjcExecutor.mm
index 2f861ffc983e..6039ef24a50a 100644
--- a/React/CxxBridge/RCTObjcExecutor.mm
+++ b/React/CxxBridge/RCTObjcExecutor.mm
@@ -39,8 +39,8 @@
                   std::shared_ptr<ExecutorDelegate> delegate)
     : m_jse(jse)
     , m_errorBlock(errorBlock)
-    , m_jsThread(std::move(jsThread))
     , m_delegate(std::move(delegate))
+    , m_jsThread(std::move(jsThread))
   {
     m_jsCallback = ^(id json, NSError *error) {
       if (error) {

From aaaa946e6d4774b1ae3a758428e1254adf38e142 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 19 Mar 2018 16:51:29 -0700
Subject: [PATCH 0072/1109] Fabric: Equality operators for geometry types

Summary: We will need this soon.

Reviewed By: fkgozali

Differential Revision: D7330338

fbshipit-source-id: 30aeadc182893e86c6a039c74d245f9b56624151
---
 ReactCommon/fabric/graphics/Geometry.h | 44 ++++++++++++++++++++++++--
 1 file changed, 42 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index dcaf88f43f54..8471b1d1a7db 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -34,6 +34,16 @@ struct Point {
   friend Point operator + (Point lhs, const Point& rhs) {
     return lhs += rhs;
   }
+
+  bool operator ==(const Point& rhs) const {
+    return
+      std::tie(this->x, this->y) ==
+      std::tie(rhs.x, rhs.y);
+  }
+
+  bool operator !=(const Point& rhs) const {
+    return !(*this == rhs);
+  }
 };
 
 /*
@@ -42,6 +52,16 @@ struct Point {
 struct Size {
   Float width {0};
   Float height {0};
+
+  bool operator ==(const Size& rhs) const {
+    return
+      std::tie(this->width, this->height) ==
+      std::tie(rhs.width, rhs.height);
+  }
+
+  bool operator !=(const Size& rhs) const {
+    return !(*this == rhs);
+  }
 };
 
 /*
@@ -50,16 +70,36 @@ struct Size {
 struct Rect {
   Point origin {0, 0};
   Size size {0, 0};
+
+  bool operator ==(const Rect& rhs) const {
+    return
+      std::tie(this->origin, this->size) ==
+      std::tie(rhs.origin, rhs.size);
+  }
+
+  bool operator !=(const Rect& rhs) const {
+    return !(*this == rhs);
+  }
 };
 
 /*
  * EdgeInsets
  */
 struct EdgeInsets {
-  Float top {0};
   Float left {0};
-  Float bottom {0};
+  Float top {0};
   Float right {0};
+  Float bottom {0};
+
+  bool operator ==(const EdgeInsets& rhs) const {
+    return
+      std::tie(this->left, this->top, this->right, this->bottom) ==
+      std::tie(rhs.left, rhs.top, rhs.right, rhs.bottom);
+  }
+
+  bool operator !=(const EdgeInsets& rhs) const {
+    return !(*this == rhs);
+  }
 };
 
 } // namespace react

From a5a34565e070c40f7f98aad8a09fdba904a73906 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 19 Mar 2018 16:51:30 -0700
Subject: [PATCH 0073/1109] Fabric: Proper return value of
 `LayoutableShadowNode::setLayoutMetrics()`

Summary: `LayoutableShadowNode::setLayoutMetrics()` must return `false` is nothing was changes.

Reviewed By: fkgozali

Differential Revision: D7330334

fbshipit-source-id: 700d50b0047919fa2b919acfa72825f100cd496f
---
 ReactCommon/fabric/core/layout/LayoutMetrics.h         | 10 ++++++++++
 .../fabric/core/layout/LayoutableShadowNode.cpp        |  4 ++++
 2 files changed, 14 insertions(+)

diff --git a/ReactCommon/fabric/core/layout/LayoutMetrics.h b/ReactCommon/fabric/core/layout/LayoutMetrics.h
index d34d7d9f9780..4bc2641a91bd 100644
--- a/ReactCommon/fabric/core/layout/LayoutMetrics.h
+++ b/ReactCommon/fabric/core/layout/LayoutMetrics.h
@@ -22,6 +22,16 @@ struct LayoutMetrics {
   EdgeInsets borderWidth {0};
   DisplayType displayType {Flex};
   LayoutDirection layoutDirection {Undefined};
+
+  bool operator ==(const LayoutMetrics& rhs) const {
+    return
+      std::tie(this->frame, this->contentInsets, this->borderWidth, this->displayType, this->layoutDirection) ==
+      std::tie(rhs.frame, rhs.contentInsets, rhs.borderWidth, rhs.displayType, rhs.layoutDirection);
+  }
+
+  bool operator !=(const LayoutMetrics& rhs) const {
+    return !(*this == rhs);
+  }
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index 3f0b50ae747a..ea2de415cdfe 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -19,6 +19,10 @@ LayoutMetrics LayoutableShadowNode::getLayoutMetrics() const {
 }
 
 bool LayoutableShadowNode::setLayoutMetrics(LayoutMetrics layoutMetrics) {
+  if (layoutMetrics_ == layoutMetrics) {
+    return false;
+  }
+
   layoutMetrics_ = layoutMetrics;
   return true;
 }

From ff288b7416977d81ac442fd9fbf210b6f2b85e31 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 19 Mar 2018 16:51:32 -0700
Subject: [PATCH 0074/1109] Fabric: Complete implementation of
 `layoutMetricsFromYogaNode`

Summary: That was simply incomplete.

Reviewed By: fkgozali

Differential Revision: D7330336

fbshipit-source-id: c495c7f61d8e551fa963bfa6cc0408343eb8439b
---
 .../view/yoga/yogaValuesConversions.cpp       | 38 +++++++++++++++++--
 1 file changed, 35 insertions(+), 3 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
index e329b8437644..e780d2cecd6f 100644
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
@@ -15,10 +15,18 @@ namespace facebook {
 namespace react {
 
 Float fabricFloatFromYogaFloat(float value) {
+  if (value == YGUndefined) {
+    return Undefined;
+  }
+
   return (Float)value;
 }
 
 float yogaFloatFromFabricFloat(Float value) {
+  if (value == Undefined) {
+    return YGUndefined;
+  }
+
   return (float)value;
 }
 
@@ -44,11 +52,35 @@ LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode) {
   YGLayout layout = yogaNode.getLayout();
 
   layoutMetrics.frame = Rect {
-    Point {fabricFloatFromYogaFloat(layout.position[0]), fabricFloatFromYogaFloat(layout.position[1])},
-    Size {fabricFloatFromYogaFloat(layout.dimensions[0]), fabricFloatFromYogaFloat(layout.dimensions[1])}
+    Point {
+      fabricFloatFromYogaFloat(layout.position[YGEdgeLeft]),
+      fabricFloatFromYogaFloat(layout.position[YGEdgeTop])
+    },
+    Size {
+      fabricFloatFromYogaFloat(layout.dimensions[YGDimensionWidth]),
+      fabricFloatFromYogaFloat(layout.dimensions[YGDimensionHeight])
+    }
   };
 
-  // FIXME: Add more.
+  layoutMetrics.borderWidth = EdgeInsets {
+    fabricFloatFromYogaFloat(layout.border[YGEdgeLeft]),
+    fabricFloatFromYogaFloat(layout.border[YGEdgeTop]),
+    fabricFloatFromYogaFloat(layout.border[YGEdgeRight]),
+    fabricFloatFromYogaFloat(layout.border[YGEdgeBottom])
+  };
+
+  layoutMetrics.contentInsets = EdgeInsets {
+    fabricFloatFromYogaFloat(layout.border[YGEdgeLeft] + layout.padding[YGEdgeLeft]),
+    fabricFloatFromYogaFloat(layout.border[YGEdgeTop] + layout.padding[YGEdgeTop]),
+    fabricFloatFromYogaFloat(layout.border[YGEdgeRight] + layout.padding[YGEdgeRight]),
+    fabricFloatFromYogaFloat(layout.border[YGEdgeBottom] + layout.padding[YGEdgeBottom])
+  };
+
+  layoutMetrics.displayType =
+    yogaNode.getStyle().display == YGDisplayNone ? None : Flex;
+
+  layoutMetrics.layoutDirection =
+    layout.direction == YGDirectionRTL ? RightToLeft : LeftToRight;
 
   return layoutMetrics;
 }

From 39383d1189a23eb52e9ea6bdcbb11bba81cefb61 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 19 Mar 2018 16:51:35 -0700
Subject: [PATCH 0075/1109] Fabric: Improved YogaLayoutableShadowNode printing

Summary: `LTR` is actually a default value for `direction` here, because an `inherit` value makes no sense for YGLayout (because it's *computed* value by definition).

Reviewed By: fkgozali

Differential Revision: D7330335

fbshipit-source-id: b3c7736c104689f2296e150f0cf57d622483d537
---
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 1 +
 1 file changed, 1 insertion(+)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 3684f75abc4b..09301f35b50a 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -149,6 +149,7 @@ SharedDebugStringConvertibleList YogaLayoutableShadowNode::getDebugProps() const
   }
 
   YGLayout defaultYogaLayout = YGLayout();
+  defaultYogaLayout.direction = YGDirectionLTR;
   YGLayout currentYogaLayout = std::const_pointer_cast<YGNode>(yogaNode_)->getLayout();
 
 #define YOGA_LAYOUT_PROPS_ADD_TO_SET(stringName, propertyName, accessor, convertor) \

From b808bfdce2384837197f92ffa730a188c6411a98 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 19 Mar 2018 16:51:39 -0700
Subject: [PATCH 0076/1109] Fabric: Introducting `ShadowNode.sourceNode`, the
 node used in copy-constructor

Summary: We will need this later in the diffing alogrithm.

Reviewed By: fkgozali

Differential Revision: D7330337

fbshipit-source-id: 3da44a62e4d5f30deed28b18a5779544153244f3
---
 .../fabric/core/shadownode/ShadowNode.cpp     | 21 +++++++++++++++++--
 .../fabric/core/shadownode/ShadowNode.h       |  6 ++++--
 2 files changed, 23 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index d095a882186d..3f7aee7be56b 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -41,7 +41,8 @@ ShadowNode::ShadowNode(
   tag_(shadowNode->tag_),
   instanceHandle_(shadowNode->instanceHandle_),
   props_(props ? props : shadowNode->props_),
-  children_(children ? children : shadowNode->children_) {}
+  children_(children ? children : shadowNode->children_),
+  sourceNode_(shadowNode) {}
 
 #pragma mark - Getters
 
@@ -57,7 +58,9 @@ Tag ShadowNode::getTag() const {
   return tag_;
 }
 
-#pragma mark - Mutating Methods
+SharedShadowNode ShadowNode::getSourceNode() const {
+  return sourceNode_;
+}
 
 void ShadowNode::sealRecursive() const {
   if (getSealed()) {
@@ -73,6 +76,8 @@ void ShadowNode::sealRecursive() const {
   }
 }
 
+#pragma mark - Mutating Methods
+
 void ShadowNode::appendChild(const SharedShadowNode &child) {
   ensureUnsealed();
 
@@ -95,6 +100,11 @@ void ShadowNode::replaceChild(const SharedShadowNode &oldChild, const SharedShad
   children_ = std::make_shared<const SharedShadowNodeList>(nonConstChildrenCopy);
 }
 
+void ShadowNode::clearSourceNode() {
+  ensureUnsealed();
+  sourceNode_ = nullptr;
+}
+
 #pragma mark - DebugStringConvertible
 
 std::string ShadowNode::getDebugName() const {
@@ -127,6 +137,13 @@ SharedDebugStringConvertibleList ShadowNode::getDebugProps() const {
     list.push_back(std::make_shared<DebugStringConvertibleItem>("handle", std::to_string((size_t)instanceHandle_)));
   }
 
+  if (sourceNode_) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>(
+      "source",
+      sourceNode_->getDebugDescription({.maximumDepth = 1, .format = false})
+    ));
+  }
+
   SharedDebugStringConvertibleList propsList = props_->getDebugProps();
   std::move(propsList.begin(), propsList.end(), std::back_inserter(list));
   return list;
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 0f2fab928056..7fcb9d04cfa0 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -55,13 +55,14 @@ class ShadowNode:
   SharedShadowNodeSharedList getChildren() const;
   SharedProps getProps() const;
   Tag getTag() const;
+  SharedShadowNode getSourceNode() const;
+  void sealRecursive() const;
 
 #pragma mark - Mutating Methods
 
-  void sealRecursive() const;
-
   void appendChild(const SharedShadowNode &child);
   void replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild);
+  void clearSourceNode();
 
 #pragma mark - DebugStringConvertible
 
@@ -76,6 +77,7 @@ class ShadowNode:
   InstanceHandle instanceHandle_;
   SharedProps props_;
   SharedShadowNodeSharedList children_;
+  SharedShadowNode sourceNode_;
 };
 
 } // namespace react

From e2462e90166d29cd3cbfa95ad4bbeccc17b78426 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Mon, 19 Mar 2018 17:33:04 -0700
Subject: [PATCH 0077/1109] iOS: set the default measure size correctly for
 RCTSurfaceHostingView

Summary: The RCTRootView default needs to be translated during init of RCTSurfaceHostingView correctly.

Reviewed By: shergin

Differential Revision: D7327918

fbshipit-source-id: 67a2a42b554782b37a032cc0470d794554cc1e5a
---
 .../RCTSurfaceHostingProxyRootView.mm                 |  5 ++++-
 .../SurfaceHostingView/RCTSurfaceHostingView.h        |  6 ++++--
 .../SurfaceHostingView/RCTSurfaceHostingView.mm       | 11 ++++-------
 React/Fabric/Surface/RCTFabricSurfaceHostingView.mm   |  3 ++-
 4 files changed, 14 insertions(+), 11 deletions(-)

diff --git a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm
index 4fc100f6b6c1..076773a58b56 100644
--- a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm
+++ b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm
@@ -61,7 +61,10 @@ - (instancetype)initWithBridge:(RCTBridge *)bridge
     [bridge.performanceLogger markStartForTag:RCTPLTTI];
   }
 
-  if (self = [super initWithBridge:bridge moduleName:moduleName initialProperties:initialProperties]) {
+  // `RCTRootViewSizeFlexibilityNone` is the RCTRootView's default.
+  RCTSurfaceSizeMeasureMode sizeMeasureMode = convertToSurfaceSizeMeasureMode(RCTRootViewSizeFlexibilityNone);
+
+  if (self = [super initWithBridge:bridge moduleName:moduleName initialProperties:initialProperties sizeMeasureMode:sizeMeasureMode]) {
     self.backgroundColor = [UIColor whiteColor];
   }
 
diff --git a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.h b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.h
index 4434df84e005..25894ec00156 100644
--- a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.h
+++ b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.h
@@ -31,7 +31,8 @@ NS_ASSUME_NONNULL_BEGIN
  * Instanciates a view with given Surface object.
  * Note: The view retains the surface object.
  */
-- (instancetype)initWithSurface:(RCTSurface *)surface NS_DESIGNATED_INITIALIZER;
+- (instancetype)initWithSurface:(RCTSurface *)surface
+                sizeMeasureMode:(RCTSurfaceSizeMeasureMode)sizeMeasureMode NS_DESIGNATED_INITIALIZER;
 
 /**
  * Convenience initializer.
@@ -40,7 +41,8 @@ NS_ASSUME_NONNULL_BEGIN
  */
 - (instancetype)initWithBridge:(RCTBridge *)bridge
                     moduleName:(NSString *)moduleName
-             initialProperties:(NSDictionary *)initialProperties;
+             initialProperties:(NSDictionary *)initialProperties
+               sizeMeasureMode:(RCTSurfaceSizeMeasureMode)sizeMeasureMode;
 
 /**
  * Create an instance of RCTSurface to be hosted.
diff --git a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.mm b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.mm
index 3c3ab2bf7fa8..9eb41ff0b2d0 100644
--- a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.mm
+++ b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.mm
@@ -33,20 +33,17 @@ @implementation RCTSurfaceHostingView {
 - (instancetype)initWithBridge:(RCTBridge *)bridge
                     moduleName:(NSString *)moduleName
              initialProperties:(NSDictionary *)initialProperties
+               sizeMeasureMode:(RCTSurfaceSizeMeasureMode)sizeMeasureMode
 {
   RCTSurface *surface = [self createSurfaceWithBridge:bridge moduleName:moduleName initialProperties:initialProperties];
-  return [self initWithSurface:surface];
-
+  return [self initWithSurface:surface sizeMeasureMode:sizeMeasureMode];
 }
 
-- (instancetype)initWithSurface:(RCTSurface *)surface
+- (instancetype)initWithSurface:(RCTSurface *)surface sizeMeasureMode:(RCTSurfaceSizeMeasureMode)sizeMeasureMode
 {
   if (self = [super initWithFrame:CGRectZero]) {
     _surface = surface;
-
-    _sizeMeasureMode =
-      RCTSurfaceSizeMeasureModeWidthAtMost |
-      RCTSurfaceSizeMeasureModeHeightAtMost;
+    _sizeMeasureMode = sizeMeasureMode;
 
     _surface.delegate = self;
     _stage = surface.stage;
diff --git a/React/Fabric/Surface/RCTFabricSurfaceHostingView.mm b/React/Fabric/Surface/RCTFabricSurfaceHostingView.mm
index 395d40afb68e..eec159cceb92 100644
--- a/React/Fabric/Surface/RCTFabricSurfaceHostingView.mm
+++ b/React/Fabric/Surface/RCTFabricSurfaceHostingView.mm
@@ -14,11 +14,12 @@ @implementation RCTFabricSurfaceHostingView
 - (instancetype)initWithBridge:(RCTBridge *)bridge
                     moduleName:(NSString *)moduleName
              initialProperties:(NSDictionary *)initialProperties
+               sizeMeasureMode:(RCTSurfaceSizeMeasureMode)sizeMeasureMode
 {
   RCTFabricSurface *surface = [[RCTFabricSurface alloc] initWithBridge:bridge
                                                             moduleName:moduleName
                                                      initialProperties:initialProperties];
-  return [self initWithSurface:surface];
+  return [self initWithSurface:surface sizeMeasureMode:sizeMeasureMode];
 }
 
 @end

From 0930fef46d23d4b2894f3f05afb2c2807b2b354c Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 19 Mar 2018 18:21:34 -0700
Subject: [PATCH 0078/1109] Disable YogaNode cloning in Android

Reviewed By: achen1

Differential Revision: D7313239

fbshipit-source-id: ecf905a22e04a2115ab968fd29f7582301f0f3c9
---
 .../react/uimanager/ReactShadowNodeImpl.java  | 65 ++++++++++---------
 1 file changed, 36 insertions(+), 29 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 664dd09729af..dddaf466caa3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -111,35 +111,32 @@ public ReactShadowNodeImpl() {
     }
   }
 
-  public ReactShadowNodeImpl(ReactShadowNodeImpl original) {
-    try {
-      mReactTag = original.mReactTag;
-      mRootTag = original.mRootTag;
-      mViewClassName = original.mViewClassName;
-      mRootNode = original.mRootNode;
-      mThemedContext = original.mThemedContext;
-      mShouldNotifyOnLayout = original.mShouldNotifyOnLayout;
-      mNodeUpdated = original.mNodeUpdated;
-      mChildren = original.mChildren == null ? null : new ArrayList<>(original.mChildren);
-      mIsLayoutOnly = original.mIsLayoutOnly;
-      mTotalNativeChildren = original.mTotalNativeChildren;
-      mNativeParent = original.mNativeParent;
-      mNativeChildren = original.mNativeChildren == null ? null : new ArrayList<>(original.mNativeChildren);
-      mNativeParent = original.mNativeParent;
-      mScreenX = original.mScreenX;
-      mScreenY = original.mScreenY;
-      mScreenWidth = original.mScreenWidth;
-      mScreenHeight = original.mScreenHeight;
-      arraycopy(original.mPadding, 0, mPadding, 0, original.mPadding.length);
-      arraycopy(original.mPaddingIsPercent, 0, mPaddingIsPercent, 0, original.mPaddingIsPercent.length);
-      mYogaNode = original.mYogaNode.clone();
-      mYogaNode.setData(this);
-      mParent = null;
-      mNewProps = null;
-    } catch (CloneNotSupportedException e) {
-      // it should never happen
-      throw new IllegalArgumentException();
-    }
+  protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
+    mReactTag = original.mReactTag;
+    mRootTag = original.mRootTag;
+    mViewClassName = original.mViewClassName;
+    mRootNode = original.mRootNode;
+    mThemedContext = original.mThemedContext;
+    mShouldNotifyOnLayout = original.mShouldNotifyOnLayout;
+    mNodeUpdated = original.mNodeUpdated;
+    mIsLayoutOnly = original.mIsLayoutOnly;
+    mTotalNativeChildren = original.mTotalNativeChildren;
+    mNativeParent = original.mNativeParent;
+    mNativeParent = original.mNativeParent;
+    mScreenX = original.mScreenX;
+    mScreenY = original.mScreenY;
+    mScreenWidth = original.mScreenWidth;
+    mScreenHeight = original.mScreenHeight;
+    arraycopy(original.mPadding, 0, mPadding, 0, original.mPadding.length);
+    arraycopy(original.mPaddingIsPercent, 0, mPaddingIsPercent, 0, original.mPaddingIsPercent.length);
+    mNewProps = null;
+    mParent = null;
+    mYogaNode = original.mYogaNode;
+    // TODO: T26729293 clone YogaNode instead of reusing the same instance
+    //mYogaNode = original.mYogaNode.clone();
+    mNativeChildren = original.mNativeChildren == null ? null : new ArrayList<>(original.mNativeChildren);
+    mChildren = original.mChildren == null ? null : new ArrayList<>(original.mChildren);
+    mYogaNode.setData(this);
   }
 
   @Override
@@ -279,6 +276,16 @@ public void addChildAt(ReactShadowNodeImpl child, int i) {
                 + toString()
                 + "')");
       }
+      // TODO: T26729293 This is a temporary code that will be replaced as part of T26729293.
+      YogaNode parent = childYogaNode.getParent();
+      if (parent != null) {
+        for (int k = 0; k < parent.getChildCount(); k++) {
+          if (parent.getChildAt(k) == childYogaNode) {
+            parent.removeChildAt(k);
+            break;
+          }
+        }
+      }
       mYogaNode.addChildAt(childYogaNode, i);
     }
     markUpdated();

From b43afcdde964a4be48c45cbec24c0c8001031a84 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 19 Mar 2018 18:21:35 -0700
Subject: [PATCH 0079/1109] Change cloning mechanism for
 mutableCopyWithNewChildren method

Reviewed By: achen1

Differential Revision: D7239873

fbshipit-source-id: d931e753c3a0b26d439eb450d62af93a672641f4
---
 .../react/fabric/FabricUIManager.java         |  2 +-
 .../react/uimanager/LayoutShadowNode.java     |  4 +-
 .../react/uimanager/ReactShadowNode.java      |  7 +++
 .../react/uimanager/ReactShadowNodeImpl.java  | 46 +++++++++++++------
 .../react/views/art/ARTGroupShadowNode.java   |  2 +-
 .../react/views/art/ARTShapeShadowNode.java   |  2 +-
 .../react/views/art/ARTTextShadowNode.java    |  2 +-
 .../views/modal/ModalHostShadowNode.java      |  2 +-
 .../progressbar/ProgressBarShadowNode.java    |  2 +-
 .../views/slider/ReactSliderManager.java      |  2 +-
 .../views/switchview/ReactSwitchManager.java  |  2 +-
 .../views/text/ReactRawTextShadowNode.java    |  2 +-
 .../react/views/text/ReactTextShadowNode.java |  2 +-
 .../text/ReactVirtualTextShadowNode.java      |  2 +-
 ...coBasedReactTextInlineImageShadowNode.java |  2 +-
 .../textinput/ReactTextInputShadowNode.java   |  2 +-
 16 files changed, 53 insertions(+), 30 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 38eea630d4bb..f66b0ce56823 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -177,7 +177,7 @@ public ReactShadowNode cloneNodeWithNewChildrenAndProps(
   private void assertReactShadowNodeCopy(ReactShadowNode source, ReactShadowNode target) {
     Assertions.assertCondition(source.getClass().equals(target.getClass()),
       "Found " + target.getClass() + " class when expecting: " +   source.getClass() +
-        ". Check that " + source.getClass() + " implements the mutableCopy() method correctly.");
+        ". Check that " + source.getClass() + " implements the copy() method correctly.");
   }
 
   /**
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
index b941c21672a4..86c1a7832ba7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
@@ -74,11 +74,11 @@ public LayoutShadowNode() {
 
   protected LayoutShadowNode(LayoutShadowNode node) {
     super(node);
-    mTempYogaValue = new MutableYogaValue(node.mTempYogaValue);
+    mTempYogaValue = new MutableYogaValue();
   }
 
   @Override
-  public LayoutShadowNode mutableCopy() {
+  protected LayoutShadowNode copy() {
     return new LayoutShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
index ab8e2692533a..75ae4fb8ac0e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
@@ -18,6 +18,7 @@
 import com.facebook.yoga.YogaPositionType;
 import com.facebook.yoga.YogaValue;
 import com.facebook.yoga.YogaWrap;
+import java.util.List;
 import javax.annotation.Nullable;
 
 /**
@@ -358,4 +359,10 @@ public interface ReactShadowNode<T extends ReactShadowNode> {
   boolean isMeasureDefined();
 
   void dispose();
+
+  /**
+   * @return an immutable {@link List<ReactShadowNode>} containing the children of this
+   * {@link ReactShadowNode}.
+   */
+  List<ReactShadowNode> getChildrenList();
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index dddaf466caa3..7673c45236f3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -28,6 +28,8 @@
 import com.facebook.yoga.YogaWrap;
 import java.util.ArrayList;
 import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
 import javax.annotation.Nullable;
 
 /**
@@ -96,7 +98,7 @@ public void onNodeCloned(YogaNode oldYogaNode,
   private final Spacing mDefaultPadding = new Spacing(0);
   private final float[] mPadding = new float[Spacing.ALL + 1];
   private final boolean[] mPaddingIsPercent = new boolean[Spacing.ALL + 1];
-  private final YogaNode mYogaNode;
+  private YogaNode mYogaNode;
 
   private @Nullable ReactStylesDiffMap mNewProps;
 
@@ -120,8 +122,6 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     mShouldNotifyOnLayout = original.mShouldNotifyOnLayout;
     mNodeUpdated = original.mNodeUpdated;
     mIsLayoutOnly = original.mIsLayoutOnly;
-    mTotalNativeChildren = original.mTotalNativeChildren;
-    mNativeParent = original.mNativeParent;
     mNativeParent = original.mNativeParent;
     mScreenX = original.mScreenX;
     mScreenY = original.mScreenY;
@@ -131,24 +131,38 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     arraycopy(original.mPaddingIsPercent, 0, mPaddingIsPercent, 0, original.mPaddingIsPercent.length);
     mNewProps = null;
     mParent = null;
-    mYogaNode = original.mYogaNode;
-    // TODO: T26729293 clone YogaNode instead of reusing the same instance
-    //mYogaNode = original.mYogaNode.clone();
-    mNativeChildren = original.mNativeChildren == null ? null : new ArrayList<>(original.mNativeChildren);
-    mChildren = original.mChildren == null ? null : new ArrayList<>(original.mChildren);
-    mYogaNode.setData(this);
+  }
+
+  /**
+   * @return a copy of this object (no including copy of its children or the underlying yogaNode).
+   */
+  protected ReactShadowNodeImpl copy() {
+    return new ReactShadowNodeImpl(this);
   }
 
   @Override
   public ReactShadowNodeImpl mutableCopy() {
-    return new ReactShadowNodeImpl(this);
+    ReactShadowNodeImpl copy = copy();
+    copy.mYogaNode = mYogaNode;
+    // TODO: T26729293 clone YogaNode instead of reusing the same instance
+    //mYogaNode = original.mYogaNode.clone();
+    copy.mNativeChildren = mNativeChildren == null ? null : new ArrayList<>(mNativeChildren);
+    copy.mTotalNativeChildren = mTotalNativeChildren;
+    copy.mChildren = mChildren == null ? null : new ArrayList<>(mChildren);
+    copy.mYogaNode.setData(this);
+    return copy;
   }
 
   @Override
   public ReactShadowNodeImpl mutableCopyWithNewChildren() {
-    ReactShadowNodeImpl copy = mutableCopy();
+    ReactShadowNodeImpl copy = copy();
+    copy.mYogaNode = mYogaNode;
+    // TODO: T26729293 clone YogaNode instead of reusing the same instance
+    //mYogaNode = original.mYogaNode.cloneWithNewChildren();
     copy.mNativeChildren = null;
     copy.mChildren = null;
+    copy.mTotalNativeChildren = 0;
+    copy.mYogaNode.setData(this);
     return copy;
   }
 
@@ -253,10 +267,6 @@ public final boolean isDirty() {
 
   @Override
   public void addChildAt(ReactShadowNodeImpl child, int i) {
-    if (child.getParent() != null) {
-      throw new IllegalViewOperationException(
-        "Tried to add child that already has a parent! Remove it from its parent first.");
-    }
     if (mChildren == null) {
       mChildren = new ArrayList<>(4);
     }
@@ -1056,4 +1066,10 @@ public void dispose() {
       YogaNodePool.get().release(mYogaNode);
     }
   }
+
+  @Nullable
+  @Override
+  public List<ReactShadowNode> getChildrenList() {
+    return mChildren == null ? null : Collections.<ReactShadowNode>unmodifiableList(mChildren);
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTGroupShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTGroupShadowNode.java
index 35cf8169ca18..fdb9f53b3018 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTGroupShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTGroupShadowNode.java
@@ -43,7 +43,7 @@ public void setClipping(@Nullable ReadableArray clippingDims) {
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopy() {
+  protected ReactShadowNodeImpl copy() {
     return new ARTGroupShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTShapeShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTShapeShadowNode.java
index e60ad880397b..d4bc72e284f4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTShapeShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTShapeShadowNode.java
@@ -72,7 +72,7 @@ public ARTShapeShadowNode(ARTShapeShadowNode node) {
   }
 
   @Override
-  public ARTShapeShadowNode mutableCopy() {
+  protected ARTShapeShadowNode copy() {
     return new ARTShapeShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTTextShadowNode.java
index 4a52e7a28a06..accb79e4ef83 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTTextShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTTextShadowNode.java
@@ -49,7 +49,7 @@ public ARTTextShadowNode(ARTTextShadowNode node) {
   }
 
   @Override
-  public ARTShapeShadowNode mutableCopy() {
+  protected ARTShapeShadowNode copy() {
     return new ARTTextShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ModalHostShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ModalHostShadowNode.java
index 5e429ac67bb2..5b63f107dd6b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ModalHostShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ModalHostShadowNode.java
@@ -28,7 +28,7 @@ private ModalHostShadowNode(ModalHostShadowNode node) {
   }
 
   @Override
-  public ModalHostShadowNode mutableCopy() {
+  protected ModalHostShadowNode copy() {
     return new ModalHostShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
index 5e44b62135e2..367f4a90bd3d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
@@ -53,7 +53,7 @@ public ProgressBarShadowNode(ProgressBarShadowNode node) {
   }
 
   @Override
-  public ProgressBarShadowNode mutableCopy() {
+  protected ProgressBarShadowNode copy() {
     return new ProgressBarShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
index 9ab464ad0e19..a73aa6ec72f6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
@@ -64,7 +64,7 @@ private void initMeasureFunction() {
     }
 
     @Override
-    public ReactSliderShadowNode mutableCopy() {
+    protected ReactSliderShadowNode copy() {
       return new ReactSliderShadowNode(this);
     }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
index 62a3ad3f41fa..1c9bff1ce1b9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
@@ -56,7 +56,7 @@ private void initMeasureFunction() {
     }
 
     @Override
-    public ReactSwitchShadowNode mutableCopy() {
+    protected ReactSwitchShadowNode copy() {
       return new ReactSwitchShadowNode(this);
     }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactRawTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactRawTextShadowNode.java
index 87f6d53692c5..488abfe84c06 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactRawTextShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactRawTextShadowNode.java
@@ -30,7 +30,7 @@ private ReactRawTextShadowNode(ReactRawTextShadowNode node) {
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopy() {
+  protected ReactShadowNodeImpl copy() {
     return new ReactRawTextShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
index 72e044ee8b04..37b13700fc36 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
@@ -154,7 +154,7 @@ private void initMeasureFunction() {
   }
 
   @Override
-  public LayoutShadowNode mutableCopy() {
+  protected LayoutShadowNode copy() {
     return new ReactTextShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactVirtualTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactVirtualTextShadowNode.java
index 6506e9697abb..59ae82cc7102 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactVirtualTextShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactVirtualTextShadowNode.java
@@ -19,7 +19,7 @@ private ReactVirtualTextShadowNode(ReactVirtualTextShadowNode node) {
   }
 
   @Override
-  public ReactVirtualTextShadowNode mutableCopy() {
+  protected ReactVirtualTextShadowNode copy() {
     return new ReactVirtualTextShadowNode(this);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageShadowNode.java
index 56298de90205..c66f009714c8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageShadowNode.java
@@ -60,7 +60,7 @@ private FrescoBasedReactTextInlineImageShadowNode(FrescoBasedReactTextInlineImag
   }
 
   @Override
-  public FrescoBasedReactTextInlineImageShadowNode mutableCopy() {
+  protected FrescoBasedReactTextInlineImageShadowNode copy() {
     return new FrescoBasedReactTextInlineImageShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
index 375c02a62857..2fb427ee8057 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
@@ -61,7 +61,7 @@ private ReactTextInputShadowNode(ReactTextInputShadowNode node) {
   }
 
   @Override
-  public ReactTextInputShadowNode mutableCopy() {
+  protected ReactTextInputShadowNode copy() {
     return new ReactTextInputShadowNode(this);
   }
 

From 3f84a0a6f483aed1aeb93820550451c9f35eb726 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 19 Mar 2018 18:21:37 -0700
Subject: [PATCH 0080/1109] Extend ReactShadowNode in order to have a reference
 to the ReactShadowNode that was used to clone a node

Reviewed By: achen1

Differential Revision: D7289345

fbshipit-source-id: 34bfba8aca43299a3a8929a0e3eb85721f736dd0
---
 .../com/facebook/react/uimanager/ReactShadowNode.java |  8 ++++++++
 .../facebook/react/uimanager/ReactShadowNodeImpl.java | 11 +++++++++++
 2 files changed, 19 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
index 75ae4fb8ac0e..dbf64b1355b8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
@@ -365,4 +365,12 @@ public interface ReactShadowNode<T extends ReactShadowNode> {
    * {@link ReactShadowNode}.
    */
   List<ReactShadowNode> getChildrenList();
+
+  /**
+   * @return the {@link ReactShadowNode} that was used during the cloning mechanism to create
+   * this {@link ReactShadowNode} or null if this object was not created using a clone operation.
+   */
+  @Nullable ReactShadowNode getOriginalReactShadowNode();
+
+  void setOriginalReactShadowNode(@Nullable ReactShadowNode node);
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 7673c45236f3..d097842e4e13 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -99,6 +99,7 @@ public void onNodeCloned(YogaNode oldYogaNode,
   private final float[] mPadding = new float[Spacing.ALL + 1];
   private final boolean[] mPaddingIsPercent = new boolean[Spacing.ALL + 1];
   private YogaNode mYogaNode;
+  private ReactShadowNode mOriginalReactShadowNode = null;
 
   private @Nullable ReactStylesDiffMap mNewProps;
 
@@ -1072,4 +1073,14 @@ public void dispose() {
   public List<ReactShadowNode> getChildrenList() {
     return mChildren == null ? null : Collections.<ReactShadowNode>unmodifiableList(mChildren);
   }
+
+  @Override
+  public ReactShadowNode getOriginalReactShadowNode() {
+    return mOriginalReactShadowNode;
+  }
+
+  @Override
+  public void setOriginalReactShadowNode(ReactShadowNode node) {
+    mOriginalReactShadowNode = node;
+  }
 }

From 7d3de1016a37e28977840d71104b9f1348525419 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 19 Mar 2018 18:21:39 -0700
Subject: [PATCH 0081/1109] Implement Fabric Reconciler

Reviewed By: achen1

Differential Revision: D7240208

fbshipit-source-id: 236b76146c50fb7f357190b08f8a5bfcef7f6645
---
 .../com/facebook/react/common/ArrayUtils.java |   9 +
 .../main/java/com/facebook/react/fabric/BUCK  |   1 +
 .../react/fabric/FabricReconciler.java        | 108 +++++++++++
 .../react/fabric/FabricUIManager.java         | 180 +++++++++---------
 .../react/uimanager/ReactShadowNodeImpl.java  |   8 +
 5 files changed, 214 insertions(+), 92 deletions(-)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/common/ArrayUtils.java b/ReactAndroid/src/main/java/com/facebook/react/common/ArrayUtils.java
index 0036e9bac13a..41b62c19f255 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/common/ArrayUtils.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/common/ArrayUtils.java
@@ -1,6 +1,7 @@
 package com.facebook.react.common;
 
 import java.util.Arrays;
+import java.util.List;
 
 public class ArrayUtils {
 
@@ -8,4 +9,12 @@ public static float[] copyArray(float[] array) {
     return array == null ? null : Arrays.copyOf(array, array.length);
   }
 
+  public static int[] copyListToArray(List<Integer> list) {
+    int[] array = new int[list.size()];
+    for (int t = 0 ; t < list.size() ; t++) {
+      array[t] = list.get(t);
+    }
+    return array;
+  }
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
index a5c3d74099be..da59ddbf2bfc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
@@ -18,6 +18,7 @@ rn_android_library(
         react_native_target("java/com/facebook/react/uimanager:uimanager"),
         react_native_target("java/com/facebook/react/uimanager/annotations:annotations"),
         react_native_target("java/com/facebook/react/module/annotations:annotations"),
+        react_native_target("java/com/facebook/react/common:common"),
         react_native_target("java/com/facebook/react/modules/i18nmanager:i18nmanager"),
     ],
 )
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
new file mode 100644
index 000000000000..a4666759c990
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -0,0 +1,108 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.fabric;
+
+import com.facebook.react.common.ArrayUtils;
+import com.facebook.react.uimanager.ReactShadowNode;
+import com.facebook.react.uimanager.UIViewOperationQueue;
+import com.facebook.react.uimanager.ViewAtIndex;
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Set;
+import javax.annotation.Nullable;
+
+public class FabricReconciler {
+
+  private UIViewOperationQueue uiViewOperationQueue;
+
+  public FabricReconciler(UIViewOperationQueue uiViewOperationQueue) {
+    this.uiViewOperationQueue = uiViewOperationQueue;
+  }
+
+  public void manageChildren(ReactShadowNode previousRootShadowNode, ReactShadowNode newRootShadowNode) {
+    List<ReactShadowNode> prevList =
+      previousRootShadowNode == null ? null :  previousRootShadowNode.getChildrenList();
+    manageChildren(newRootShadowNode, prevList, newRootShadowNode.getChildrenList());
+  }
+
+  private void manageChildren(
+    ReactShadowNode parent,
+    @Nullable List<ReactShadowNode> prevList,
+    @Nullable List<ReactShadowNode> newList) {
+    prevList = prevList == null ? Collections.<ReactShadowNode>emptyList() : prevList;
+    newList = newList == null ? Collections.<ReactShadowNode>emptyList() : newList;
+
+    // Iterate through each child list and compare each previous and next child. Same nodes
+    // implies no change is needed. If the nodes are different but are referencing the same view,
+    // the view needs to be updated with new props and children. Otherwise, there has been
+    // a change in the children positions.
+    int sameReactTagIndex = 0;
+    for (; sameReactTagIndex < Math.min(prevList.size(), newList.size()); sameReactTagIndex++) {
+      ReactShadowNode prevNode = prevList.get(sameReactTagIndex);
+      ReactShadowNode newNode = newList.get(sameReactTagIndex);
+      if (prevNode == newNode) {
+        continue;
+      }
+      if (prevNode.getReactTag() != newNode.getReactTag()) {
+        break;
+      }
+
+      if (newNode.getNewProps() != null) {
+        uiViewOperationQueue.enqueueUpdateProperties(
+          newNode.getReactTag(), newNode.getViewClass(), newNode.getNewProps());
+      }
+
+      manageChildren(prevNode, prevNode.getChildrenList(), newNode.getChildrenList());
+      prevNode.setOriginalReactShadowNode(newNode);
+    }
+    int firstRemovedOrAddedViewIndex = sameReactTagIndex;
+
+    // Every ReactShadowNode on the newList that is on the right side of
+    // firstRemovedOrAddedViewIndex is defined as an added view.
+    // It is more efficient to reorder removing and adding all the views in the right order, instead
+    // of calculating the minimum amount of reorder operations.
+    Set<Integer> addedTags = new HashSet<>();
+    ViewAtIndex[] viewsToAdd = new ViewAtIndex[newList.size() - firstRemovedOrAddedViewIndex];
+    int viewsToAddIndex = 0;
+    for (int k = firstRemovedOrAddedViewIndex; k < newList.size(); k++) {
+      ReactShadowNode newNode = newList.get(k);
+      if (newNode.getNewProps() != null) {
+        uiViewOperationQueue.enqueueUpdateProperties(
+          newNode.getReactTag(), newNode.getViewClass(), newNode.getNewProps());
+      }
+      viewsToAdd[viewsToAddIndex++] = new ViewAtIndex(newNode.getReactTag(), k);
+      List previousChildrenList = newNode.getOriginalReactShadowNode() == null ? null : newNode.getOriginalReactShadowNode().getChildrenList();
+      manageChildren(newNode, previousChildrenList, newNode.getChildrenList());
+      newNode.setOriginalReactShadowNode(newNode);
+      addedTags.add(newNode.getReactTag());
+    }
+
+    // Every ReactShadowNode on the prevList that is on the right side of
+    // firstRemovedOrAddedViewIndex is defined as a removed view.
+    // It is more efficient to reorder removing and adding all the views in the right order, instead
+    // of calculating the minimum amount of reorder operations.
+    // If a View is not re-ordered, then the ReactTag is deleted (ReactShadowNode and native View
+    // are released from memory)
+    List<Integer> tagsToDelete = new LinkedList<>();
+    int[] indicesToRemove = new int[prevList.size() - firstRemovedOrAddedViewIndex];
+    int indicesToRemoveIndex = 0;
+    for (int j = firstRemovedOrAddedViewIndex; j < prevList.size(); j++) {
+      ReactShadowNode nodeToRemove = prevList.get(j);
+      indicesToRemove[indicesToRemoveIndex++] = j;
+      if (!addedTags.contains(nodeToRemove.getReactTag())) {
+        tagsToDelete.add(nodeToRemove.getReactTag());
+      }
+    }
+
+    uiViewOperationQueue.enqueueManageChildren(
+      parent.getReactTag(), indicesToRemove, viewsToAdd, ArrayUtils.copyListToArray(tagsToDelete));
+  }
+
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index f66b0ce56823..4820e8496d81 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -14,7 +14,6 @@
 import android.util.Log;
 import android.view.View;
 import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.JavaOnlyArray;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.ReadableNativeMap;
@@ -28,7 +27,6 @@
 import com.facebook.react.uimanager.ReactStylesDiffMap;
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.UIViewOperationQueue;
-import com.facebook.react.uimanager.ViewAtIndex;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
@@ -38,8 +36,8 @@
 import javax.annotation.Nullable;
 
 /**
- * This class is responsible to create, clone and update {@link ReactShadowNode} using the
- * Fabric API.
+ * This class is responsible to create, clone and update {@link ReactShadowNode} using the Fabric
+ * API.
  */
 @SuppressWarnings("unused") // used from JNI
 public class FabricUIManager implements UIManager {
@@ -49,23 +47,25 @@ public class FabricUIManager implements UIManager {
   private final ReactApplicationContext mReactApplicationContext;
   private final ViewManagerRegistry mViewManagerRegistry;
   private final UIViewOperationQueue mUIViewOperationQueue;
+  private volatile int mCurrentBatch = 0;
+  private ReactShadowNode mCurrentRootShadowNode;
+  private FabricReconciler mFabricReconciler;
 
-  public FabricUIManager(ReactApplicationContext reactContext,
-    ViewManagerRegistry viewManagerRegistry) {
+  public FabricUIManager(
+      ReactApplicationContext reactContext, ViewManagerRegistry viewManagerRegistry) {
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
     mReactApplicationContext = reactContext;
     mViewManagerRegistry = viewManagerRegistry;
-    mUIViewOperationQueue = new UIViewOperationQueue(reactContext, new NativeViewHierarchyManager(viewManagerRegistry), 0);
+    mUIViewOperationQueue =
+        new UIViewOperationQueue(
+            reactContext, new NativeViewHierarchyManager(viewManagerRegistry), 0);
+    mFabricReconciler = new FabricReconciler(mUIViewOperationQueue);
   }
 
-  /**
-   * Creates a new {@link ReactShadowNode}
-   */
+  /** Creates a new {@link ReactShadowNode} */
   @Nullable
-  public ReactShadowNode createNode(int reactTag,
-    String viewName,
-    int rootTag,
-    ReadableNativeMap props) {
+  public ReactShadowNode createNode(
+      int reactTag, String viewName, int rootTag, ReadableNativeMap props) {
     try {
       ViewManager viewManager = mViewManagerRegistry.get(viewName);
       ReactShadowNode node = viewManager.createShadowNodeInstance(mReactApplicationContext);
@@ -78,8 +78,8 @@ public ReactShadowNode createNode(int reactTag,
       ReactStylesDiffMap styles = updateProps(node, props);
 
       if (!node.isVirtual()) {
-        mUIViewOperationQueue
-          .enqueueCreateView(rootNode.getThemedContext(), reactTag, viewName, styles);
+        mUIViewOperationQueue.enqueueCreateView(
+            rootNode.getThemedContext(), reactTag, viewName, styles);
       }
       return node;
     } catch (Throwable t) {
@@ -103,8 +103,8 @@ private ReactStylesDiffMap updateProps(ReactShadowNode node, @Nullable ReadableN
 
   /**
    * @return a clone of the {@link ReactShadowNode} received by parameter. The cloned
-   * ReactShadowNode will contain a copy of all the internal data of the original node, including
-   * its children set (note that the children nodes will not be cloned).
+   *     ReactShadowNode will contain a copy of all the internal data of the original node,
+   *     including its children set (note that the children nodes will not be cloned).
    */
   @Nullable
   public ReactShadowNode cloneNode(ReactShadowNode node) {
@@ -120,8 +120,8 @@ public ReactShadowNode cloneNode(ReactShadowNode node) {
 
   /**
    * @return a clone of the {@link ReactShadowNode} received by parameter. The cloned
-   * ReactShadowNode will contain a copy of all the internal data of the original node, but
-   * its children set will be empty.
+   *     ReactShadowNode will contain a copy of all the internal data of the original node, but its
+   *     children set will be empty.
    */
   @Nullable
   public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node) {
@@ -137,15 +137,15 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node) {
 
   /**
    * @return a clone of the {@link ReactShadowNode} received by parameter. The cloned
-   * ReactShadowNode will contain a copy of all the internal data of the original node, but its
-   * props will be overridden with the {@link ReadableMap} received by parameter.
+   *     ReactShadowNode will contain a copy of all the internal data of the original node, but its
+   *     props will be overridden with the {@link ReadableMap} received by parameter.
    */
   @Nullable
   public ReactShadowNode cloneNodeWithNewProps(
-      ReactShadowNode node,
-      @Nullable ReadableNativeMap newProps) {
+      ReactShadowNode node, @Nullable ReadableNativeMap newProps) {
     try {
-      ReactShadowNode clone = node.mutableCopyWithNewProps(newProps == null ? null : new ReactStylesDiffMap(newProps));
+      ReactShadowNode clone =
+          node.mutableCopyWithNewProps(newProps == null ? null : new ReactStylesDiffMap(newProps));
       assertReactShadowNodeCopy(node, clone);
       return clone;
     } catch (Throwable t) {
@@ -156,16 +156,17 @@ public ReactShadowNode cloneNodeWithNewProps(
 
   /**
    * @return a clone of the {@link ReactShadowNode} received by parameter. The cloned
-   * ReactShadowNode will contain a copy of all the internal data of the original node, but its
-   * props will be overridden with the {@link ReadableMap} received by parameter and its children
-   * set will be empty.
+   *     ReactShadowNode will contain a copy of all the internal data of the original node, but its
+   *     props will be overridden with the {@link ReadableMap} received by parameter and its
+   *     children set will be empty.
    */
   @Nullable
   public ReactShadowNode cloneNodeWithNewChildrenAndProps(
-      ReactShadowNode node,
-      ReadableNativeMap newProps) {
+      ReactShadowNode node, ReadableNativeMap newProps) {
     try {
-      ReactShadowNode clone = node.mutableCopyWithNewChildrenAndProps(newProps == null ? null : new ReactStylesDiffMap(newProps));
+      ReactShadowNode clone =
+          node.mutableCopyWithNewChildrenAndProps(
+              newProps == null ? null : new ReactStylesDiffMap(newProps));
       assertReactShadowNodeCopy(node, clone);
       return clone;
     } catch (Throwable t) {
@@ -175,38 +176,33 @@ public ReactShadowNode cloneNodeWithNewChildrenAndProps(
   }
 
   private void assertReactShadowNodeCopy(ReactShadowNode source, ReactShadowNode target) {
-    Assertions.assertCondition(source.getClass().equals(target.getClass()),
-      "Found " + target.getClass() + " class when expecting: " +   source.getClass() +
-        ". Check that " + source.getClass() + " implements the copy() method correctly.");
+    Assertions.assertCondition(
+        source.getClass().equals(target.getClass()),
+        "Found "
+            + target.getClass()
+            + " class when expecting: "
+            + source.getClass()
+            + ". Check that "
+            + source.getClass()
+            + " implements the copy() method correctly.");
   }
 
   /**
-   * Appends the child {@link ReactShadowNode} to the children set of the parent
-   * {@link ReactShadowNode}.
+   * Appends the child {@link ReactShadowNode} to the children set of the parent {@link
+   * ReactShadowNode}.
    */
   @Nullable
   public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
     try {
-      int childIndex = parent.getChildCount();
-      parent.addChildAt(child, childIndex);
-      ViewAtIndex[] viewsToAdd =
-        new ViewAtIndex[]{new ViewAtIndex(child.getReactTag(), childIndex)};
-      if (!child.isVirtual()) {
-        mUIViewOperationQueue.enqueueManageChildren(
-          parent.getReactTag(),
-          null,
-          viewsToAdd,
-          null
-        );
-      }
+      parent.addChildAt(child, parent.getChildCount());
     } catch (Throwable t) {
       handleException(parent, t);
     }
   }
 
   /**
-   * @return an empty {@link List<ReactShadowNode>} that will be used to append the
-   * {@link ReactShadowNode} elements of the root. Typically this List will contain one element.
+   * @return an empty {@link List<ReactShadowNode>} that will be used to append the {@link
+   *     ReactShadowNode} elements of the root. Typically this List will contain one element.
    */
   public List<ReactShadowNode> createChildSet(int rootTag) {
     return new ArrayList<>(1);
@@ -219,22 +215,24 @@ public void appendChildToSet(List<ReactShadowNode> childList, ReactShadowNode ch
     childList.add(child);
   }
 
-  public void completeRoot(int rootTag, List<ReactShadowNode> childList) {
+  public synchronized void completeRoot(int rootTag, List<ReactShadowNode> childList) {
     try {
       ReactShadowNode rootNode = getRootNode(rootTag);
       Assertions.assertNotNull(
-        rootNode,
-        "Root view with tag " + rootTag + " must be added before completeRoot is called");
-      for (int i = 0; i < childList.size(); i++) {
-        ReactShadowNode child = childList.get(i);
-        appendChild(rootNode, child);
-      }
+          rootNode,
+          "Root view with tag " + rootTag + " must be added before completeRoot is called");
+
+
+      rootNode = calculateDiffingAndCreateNewRootNode(rootNode, childList);
 
       notifyOnBeforeLayoutRecursive(rootNode);
-      calculateRootLayout(rootNode);
+      rootNode.calculateLayout();
+
       applyUpdatesRecursive(rootNode, 0, 0);
-      mUIViewOperationQueue
-        .dispatchViewUpdates(1, System.currentTimeMillis(), System.currentTimeMillis());
+      mUIViewOperationQueue.dispatchViewUpdates(
+        mCurrentBatch++, System.currentTimeMillis(), System.currentTimeMillis());
+
+      mCurrentRootShadowNode = rootNode;
     } catch (Exception e) {
       handleException(getRootNode(rootTag), e);
     }
@@ -250,46 +248,45 @@ private void notifyOnBeforeLayoutRecursive(ReactShadowNode node) {
     node.onBeforeLayout();
   }
 
-  private void calculateRootLayout(ReactShadowNode cssRoot) {
-    cssRoot.calculateLayout();
-  }
+  private ReactShadowNode calculateDiffingAndCreateNewRootNode(
+    ReactShadowNode currentRootShadowNode, List<ReactShadowNode> newChildList) {
+    ReactShadowNode newRootShadowNode = currentRootShadowNode.mutableCopyWithNewChildren();
+    for (ReactShadowNode child : newChildList) {
+      appendChild(newRootShadowNode, child);
+    }
 
-  private void applyUpdatesRecursive(
-    ReactShadowNode cssNode,
-    float absoluteX,
-    float absoluteY) {
+    mFabricReconciler.manageChildren(mCurrentRootShadowNode, newRootShadowNode);
+    return newRootShadowNode;
+  }
 
-    if (!cssNode.hasUpdates()) {
+  private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float absoluteY) {
+    if (!node.hasUpdates()) {
       return;
     }
 
-    if (!cssNode.isVirtualAnchor()) {
-      for (int i = 0; i < cssNode.getChildCount(); i++) {
+    if (!node.isVirtualAnchor()) {
+      for (int i = 0; i < node.getChildCount(); i++) {
         applyUpdatesRecursive(
-          cssNode.getChildAt(i),
-          absoluteX + cssNode.getLayoutX(),
-          absoluteY + cssNode.getLayoutY());
+            node.getChildAt(i),
+            absoluteX + node.getLayoutX(),
+            absoluteY + node.getLayoutY());
       }
     }
 
-    int tag = cssNode.getReactTag();
+    int tag = node.getReactTag();
     if (mRootShadowNodeRegistry.getNode(tag) == null) {
-      boolean frameDidChange = cssNode.dispatchUpdates(
-        absoluteX,
-        absoluteY,
-        mUIViewOperationQueue,
-        null);
+      boolean frameDidChange =
+          node.dispatchUpdates(absoluteX, absoluteY, mUIViewOperationQueue, null);
     }
-    cssNode.markUpdateSeen();
+    node.markUpdateSeen();
   }
 
   @Override
   public <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(
-    final T rootView) {
+      final T rootView) {
     int rootTag = ReactRootViewTagGenerator.getNextRootViewTag();
-    ThemedReactContext themedRootContext = new ThemedReactContext(
-      mReactApplicationContext,
-      rootView.getContext());
+    ThemedReactContext themedRootContext =
+        new ThemedReactContext(mReactApplicationContext, rootView.getContext());
 
     ReactShadowNode rootShadowNode = createRootShadowNode(rootTag, themedRootContext);
 
@@ -321,18 +318,18 @@ private ReactShadowNode createRootShadowNode(int rootTag, ThemedReactContext the
    * parameters.
    */
   public void updateRootView(
-    ReactShadowNode rootCSSNode, int widthMeasureSpec, int heightMeasureSpec) {
+      ReactShadowNode node, int widthMeasureSpec, int heightMeasureSpec) {
     int widthMode = View.MeasureSpec.getMode(widthMeasureSpec);
     int widthSize = View.MeasureSpec.getSize(widthMeasureSpec);
     switch (widthMode) {
       case EXACTLY:
-        rootCSSNode.setStyleWidth(widthSize);
+        node.setStyleWidth(widthSize);
         break;
       case AT_MOST:
-        rootCSSNode.setStyleMaxWidth(widthSize);
+        node.setStyleMaxWidth(widthSize);
         break;
       case UNSPECIFIED:
-        rootCSSNode.setStyleWidthAuto();
+        node.setStyleWidthAuto();
         break;
     }
 
@@ -340,13 +337,13 @@ public void updateRootView(
     int heightSize = View.MeasureSpec.getSize(heightMeasureSpec);
     switch (heightMode) {
       case EXACTLY:
-        rootCSSNode.setStyleHeight(heightSize);
+        node.setStyleHeight(heightSize);
         break;
       case AT_MOST:
-        rootCSSNode.setStyleMaxHeight(heightSize);
+        node.setStyleMaxHeight(heightSize);
         break;
       case UNSPECIFIED:
-        rootCSSNode.setStyleHeightAuto();
+        node.setStyleHeightAuto();
         break;
     }
   }
@@ -362,5 +359,4 @@ private void handleException(ReactShadowNode node, Throwable t) {
       throw new RuntimeException(ex.getMessage(), t);
     }
   }
-
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index d097842e4e13..a43355e84fc8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -132,6 +132,7 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     arraycopy(original.mPaddingIsPercent, 0, mPaddingIsPercent, 0, original.mPaddingIsPercent.length);
     mNewProps = null;
     mParent = null;
+    mOriginalReactShadowNode = original;
   }
 
   /**
@@ -151,6 +152,13 @@ public ReactShadowNodeImpl mutableCopy() {
     copy.mTotalNativeChildren = mTotalNativeChildren;
     copy.mChildren = mChildren == null ? null : new ArrayList<>(mChildren);
     copy.mYogaNode.setData(this);
+    if (mChildren != null) {
+      for (ReactShadowNode child : mChildren) {
+        if (child.getOriginalReactShadowNode() == null) {
+          child.setOriginalReactShadowNode(child);
+        }
+      }
+    }
     return copy;
   }
 

From cc3d45d2e9cc701604d27714103cbee49171bcfa Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 19 Mar 2018 18:21:43 -0700
Subject: [PATCH 0082/1109] Add logging to debug Fabric diffing algorithm

Reviewed By: achen1

Differential Revision: D7319185

fbshipit-source-id: fe47c21db5e1415aebe806f0d74b1f65f667a397
---
 .../facebook/react/fabric/FabricReconciler.java  | 16 +++++++++++++++-
 .../facebook/react/fabric/FabricUIManager.java   | 13 ++++++++++++-
 .../facebook/react/uimanager/ViewAtIndex.java    |  5 +++++
 3 files changed, 32 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index a4666759c990..d60cfdaed796 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -7,10 +7,12 @@
 
 package com.facebook.react.fabric;
 
+import android.util.Log;
 import com.facebook.react.common.ArrayUtils;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.UIViewOperationQueue;
 import com.facebook.react.uimanager.ViewAtIndex;
+import java.util.Arrays;
 import java.util.Collections;
 import java.util.HashSet;
 import java.util.LinkedList;
@@ -20,6 +22,9 @@
 
 public class FabricReconciler {
 
+  private static final String TAG = FabricReconciler.class.getSimpleName();
+  private static final boolean DEBUG = true;
+
   private UIViewOperationQueue uiViewOperationQueue;
 
   public FabricReconciler(UIViewOperationQueue uiViewOperationQueue) {
@@ -101,8 +106,17 @@ private void manageChildren(
       }
     }
 
+    int[] tagsToDeleteArray = ArrayUtils.copyListToArray(tagsToDelete);
+    if (DEBUG) {
+      Log.d(
+        TAG,
+        "manageChildren.enqueueManageChildren parent: " + parent.getReactTag() +
+          "\n\tIndices2Remove: " + Arrays.toString(indicesToRemove) +
+          "\n\tViews2Add: " + Arrays.toString(viewsToAdd) +
+          "\n\tTags2Delete: " + Arrays.toString(tagsToDeleteArray));
+    }
     uiViewOperationQueue.enqueueManageChildren(
-      parent.getReactTag(), indicesToRemove, viewsToAdd, ArrayUtils.copyListToArray(tagsToDelete));
+      parent.getReactTag(), indicesToRemove, viewsToAdd, tagsToDeleteArray);
   }
 
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 4820e8496d81..8fd0dd706a76 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -42,7 +42,8 @@
 @SuppressWarnings("unused") // used from JNI
 public class FabricUIManager implements UIManager {
 
-  private static final String TAG = FabricUIManager.class.toString();
+  private static final String TAG = FabricUIManager.class.getSimpleName();
+  private static final boolean DEBUG = true;
   private final RootShadowNodeRegistry mRootShadowNodeRegistry = new RootShadowNodeRegistry();
   private final ReactApplicationContext mReactApplicationContext;
   private final ViewManagerRegistry mViewManagerRegistry;
@@ -225,9 +226,19 @@ public synchronized void completeRoot(int rootTag, List<ReactShadowNode> childLi
 
       rootNode = calculateDiffingAndCreateNewRootNode(rootNode, childList);
 
+      if (DEBUG) {
+        Log.d(TAG, "ReactShadowNodeHierarchy after diffing: " + rootNode.getHierarchyInfo());
+      }
+
       notifyOnBeforeLayoutRecursive(rootNode);
       rootNode.calculateLayout();
 
+      if (DEBUG) {
+        Log.d(
+          TAG,
+          "ReactShadowNodeHierarchy after calculate Layout: " + rootNode.getHierarchyInfo());
+      }
+
       applyUpdatesRecursive(rootNode, 0, 0);
       mUIViewOperationQueue.dispatchViewUpdates(
         mCurrentBatch++, System.currentTimeMillis(), System.currentTimeMillis());
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewAtIndex.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewAtIndex.java
index 6000e0554c85..ef2a914d3cf3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewAtIndex.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewAtIndex.java
@@ -28,4 +28,9 @@ public ViewAtIndex(int tag, int index) {
     mTag = tag;
     mIndex = index;
   }
+
+  @Override
+  public String toString() {
+    return "[" + mIndex + ", " + mTag + "]";
+  }
 }

From 5347ecfd296cdc882c7c198e6489f7482f27a073 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 19 Mar 2018 18:21:45 -0700
Subject: [PATCH 0083/1109] Fix removal of ReactShadowNode

Reviewed By: achen1

Differential Revision: D7323294

fbshipit-source-id: 411aa1bcd93cc4f9df78f64ceb0c0d8c127bc3b0
---
 .../main/java/com/facebook/react/fabric/FabricReconciler.java  | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index d60cfdaed796..4ea5d143bcdd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -103,6 +103,9 @@ private void manageChildren(
       indicesToRemove[indicesToRemoveIndex++] = j;
       if (!addedTags.contains(nodeToRemove.getReactTag())) {
         tagsToDelete.add(nodeToRemove.getReactTag());
+        // TODO: T26729293 since we are not cloning ReactShadowNode's we need to "manually" remove
+        // from the ReactShadowTree when one of the nodes is deleted in JS.
+        nodeToRemove.getParent().removeChildAt(j);
       }
     }
 

From 0d924dd629046b522f1a093bef8660219626f731 Mon Sep 17 00:00:00 2001
From: Sam Goldman <samgoldman@fb.com>
Date: Mon, 19 Mar 2018 18:24:11 -0700
Subject: [PATCH 0084/1109] Upgrade to Flow v0.68.0

Reviewed By: gabelevi

Differential Revision: D7310349

fbshipit-source-id: 70d29815dd7912704aec8a015c970be3fafeeba3
---
 .flowconfig                                       |  2 +-
 Libraries/Animated/src/nodes/AnimatedValue.js     |  3 +++
 .../SwipeableRow/SwipeableListView.js             |  6 ++++++
 Libraries/Lists/VirtualizedList.js                | 14 ++++++--------
 Libraries/ReactNative/YellowBox.js                |  9 +++++++++
 Libraries/ReactNative/renderApplication.js        |  3 +++
 Libraries/ReactNative/renderFabricSurface.js      |  3 +++
 Libraries/ReactNative/requireFabricComponent.js   |  3 +++
 Libraries/ReactNative/requireNativeComponent.js   |  3 +++
 Libraries/WebSocket/WebSocket.js                  |  3 +++
 RNTester/js/CameraRollView.js                     |  3 +++
 RNTester/js/RNTesterExampleList.js                |  9 +++++++++
 RNTester/js/RNTesterPage.js                       |  3 +++
 local-cli/server/runServer.js                     | 15 +++++++++++++++
 local-cli/templates/HelloWorld/_flowconfig        |  2 +-
 package.json                                      |  2 +-
 16 files changed, 72 insertions(+), 11 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index 361d475f2404..182bf0f089e6 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -52,4 +52,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.67.0
+^0.68.0
diff --git a/Libraries/Animated/src/nodes/AnimatedValue.js b/Libraries/Animated/src/nodes/AnimatedValue.js
index 862d25f8e53a..9d06c751cefb 100644
--- a/Libraries/Animated/src/nodes/AnimatedValue.js
+++ b/Libraries/Animated/src/nodes/AnimatedValue.js
@@ -51,6 +51,9 @@ let _uniqueId = 1;
 function _flush(rootNode: AnimatedValue): void {
   const animatedStyles = new Set();
   function findAnimatedStyles(node) {
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     if (typeof node.update === 'function') {
       animatedStyles.add(node);
     } else {
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableListView.js b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
index 569f3581d047..c6623be75b3b 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableListView.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
@@ -142,6 +142,9 @@ class SwipeableListView extends React.Component<Props, State> {
    * (from high 20s to almost consistently 60 fps)
    */
   _setListViewScrollable(value: boolean): void {
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     if (this._listViewRef && typeof this._listViewRef.setNativeProps === 'function') {
       this._listViewRef.setNativeProps({
         scrollEnabled: value,
@@ -151,6 +154,9 @@ class SwipeableListView extends React.Component<Props, State> {
 
   // Passing through ListView's getScrollResponder() function
   getScrollResponder(): ?Object {
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     if (this._listViewRef && typeof this._listViewRef.getScrollResponder === 'function') {
       return this._listViewRef.getScrollResponder();
     }
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 8ee3da2ea4f4..4c7a83b19d77 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -748,10 +748,6 @@ class VirtualizedList extends React.PureComponent<Props, State> {
           cellKey={this._getCellKey() + '-header'}
           key="$header">
           <View onLayout={this._onLayoutHeader} style={inversionStyle}>
-            {/*
-              Flow doesn't know this is a React.Element and not a React.Component
-              $FlowFixMe https://fburl.com/b9xmtm09
-            */}
             {element}
           </View>
         </VirtualizedCellWrapper>,
@@ -883,10 +879,6 @@ class VirtualizedList extends React.PureComponent<Props, State> {
           cellKey={this._getCellKey() + '-footer'}
           key="$footer">
           <View onLayout={this._onLayoutFooter} style={inversionStyle}>
-            {/*
-              Flow doesn't know this is a React.Element and not a React.Component
-              $FlowFixMe https://fburl.com/b9xmtm09
-            */}
             {element}
           </View>
         </VirtualizedCellWrapper>,
@@ -1122,6 +1114,9 @@ class VirtualizedList extends React.PureComponent<Props, State> {
     const itemCount = this.props.getItemCount(this.props.data);
     for (let ii = 0; ii < itemCount; ii++) {
       const frame = this._getFrameMetricsApprox(ii);
+      /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+       * error found when Flow v0.68 was deployed. To see the error delete this
+       * comment and run Flow. */
       if (frame.inLayout) {
         framesInLayout.push(frame);
       }
@@ -1646,6 +1641,9 @@ class CellRenderer extends React.Component<
       separators: this._separators,
     });
     const onLayout =
+      /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+       * error found when Flow v0.68 was deployed. To see the error delete this
+       * comment and run Flow. */
       getItemLayout && !parentProps.debug && !fillRateHelper.enabled()
         ? undefined
         : this.props.onLayout;
diff --git a/Libraries/ReactNative/YellowBox.js b/Libraries/ReactNative/YellowBox.js
index 8bd31d3cd8b7..26749987affb 100644
--- a/Libraries/ReactNative/YellowBox.js
+++ b/Libraries/ReactNative/YellowBox.js
@@ -105,6 +105,9 @@ function sprintf(format, ...args) {
 }
 
 function updateWarningMap(...args): void {
+  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
+   * found when Flow v0.68 was deployed. To see the error delete this comment
+   * and run Flow. */
   if (console.disableYellowBox) {
     return;
   }
@@ -178,6 +181,9 @@ function isWarningIgnored(warning: string): boolean {
 
   // DEPRECATED
   return (
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     Array.isArray(console.ignoredYellowBox) &&
     console.ignoredYellowBox.some(ignorePrefix =>
       warning.startsWith(String(ignorePrefix)),
@@ -379,6 +385,9 @@ class YellowBox extends React.Component<
   }
 
   render() {
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     if (console.disableYellowBox || this.state.warningMap.size === 0) {
       return null;
     }
diff --git a/Libraries/ReactNative/renderApplication.js b/Libraries/ReactNative/renderApplication.js
index e72853e8e459..896c88207eb0 100644
--- a/Libraries/ReactNative/renderApplication.js
+++ b/Libraries/ReactNative/renderApplication.js
@@ -38,6 +38,9 @@ function renderApplication<Props: Object>(
   // to be async also. To do this, wrap AppContainer with an async marker.
   // For more info see https://fb.me/is-component-async
   if (
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     RootComponent.prototype != null &&
     RootComponent.prototype.unstable_isAsyncReactComponent === true
   ) {
diff --git a/Libraries/ReactNative/renderFabricSurface.js b/Libraries/ReactNative/renderFabricSurface.js
index 841a079b1d06..0279f1759926 100644
--- a/Libraries/ReactNative/renderFabricSurface.js
+++ b/Libraries/ReactNative/renderFabricSurface.js
@@ -42,6 +42,9 @@ function renderFabricSurface<Props: Object>(
   // to be async also. To do this, wrap AppContainer with an async marker.
   // For more info see https://fb.me/is-component-async
   if (
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     RootComponent.prototype != null &&
     RootComponent.prototype.unstable_isAsyncReactComponent === true
   ) {
diff --git a/Libraries/ReactNative/requireFabricComponent.js b/Libraries/ReactNative/requireFabricComponent.js
index 1544c6fdff97..4b6010a0c264 100644
--- a/Libraries/ReactNative/requireFabricComponent.js
+++ b/Libraries/ReactNative/requireFabricComponent.js
@@ -121,6 +121,9 @@ function requireNativeComponent(
     // TODO (bvaughn) Revert this particular change any time after April 1
     if (componentInterface) {
       viewConfig.propTypes =
+        /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+         * error found when Flow v0.68 was deployed. To see the error delete
+         * this comment and run Flow. */
         typeof componentInterface.__propTypesSecretDontUseThesePlease ===
         'object'
           ? componentInterface.__propTypesSecretDontUseThesePlease
diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index 2a6c7c8ca71e..4a6fd4c1310c 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -119,6 +119,9 @@ function requireNativeComponent(
     // TODO (bvaughn) Revert this particular change any time after April 1
     if (componentInterface) {
       viewConfig.propTypes =
+        /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+         * error found when Flow v0.68 was deployed. To see the error delete
+         * this comment and run Flow. */
         typeof componentInterface.__propTypesSecretDontUseThesePlease ===
         'object'
           ? componentInterface.__propTypesSecretDontUseThesePlease
diff --git a/Libraries/WebSocket/WebSocket.js b/Libraries/WebSocket/WebSocket.js
index daa1ed77ca05..021e42507e5d 100644
--- a/Libraries/WebSocket/WebSocket.js
+++ b/Libraries/WebSocket/WebSocket.js
@@ -103,6 +103,9 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
     const {headers = {}, ...unrecognized} = options || {};
 
     // Preserve deprecated backwards compatibility for the 'origin' option
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     if (unrecognized && typeof unrecognized.origin === 'string') {
       console.warn('Specifying `origin` as a WebSocket connection option is deprecated. Include it under `headers` instead.');
       /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This
diff --git a/RNTester/js/CameraRollView.js b/RNTester/js/CameraRollView.js
index f69a4feed65f..c08aeb71e833 100644
--- a/RNTester/js/CameraRollView.js
+++ b/RNTester/js/CameraRollView.js
@@ -123,6 +123,9 @@ var CameraRollView = createReactClass({
     this.fetch();
   },
 
+  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
+   * found when Flow v0.68 was deployed. To see the error delete this comment
+   * and run Flow. */
   UNSAFE_componentWillReceiveProps: function(nextProps: {groupTypes?: string}) {
     if (this.props.groupTypes !== nextProps.groupTypes) {
       this.fetch(true);
diff --git a/RNTester/js/RNTesterExampleList.js b/RNTester/js/RNTesterExampleList.js
index 96e1ed9b474a..e043e2d5cba1 100644
--- a/RNTester/js/RNTesterExampleList.js
+++ b/RNTester/js/RNTesterExampleList.js
@@ -76,6 +76,9 @@ class RNTesterExampleList extends React.Component<Props, $FlowFixMeState> {
     const filterText = this.props.persister.state.filter;
     const filterRegex = new RegExp(String(filterText), 'i');
     const filter = (example) =>
+      /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+       * error found when Flow v0.68 was deployed. To see the error delete this
+       * comment and run Flow. */
       this.props.disableSearch ||
         filterRegex.test(example.module.title) &&
         (!Platform.isTVOS || example.supportsTVOS);
@@ -128,6 +131,9 @@ class RNTesterExampleList extends React.Component<Props, $FlowFixMeState> {
   );
 
   _renderTitleRow(): ?React.Element<any> {
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     if (!this.props.displayTitleRow) {
       return null;
     }
@@ -146,6 +152,9 @@ class RNTesterExampleList extends React.Component<Props, $FlowFixMeState> {
   }
 
   _renderTextInput(): ?React.Element<any> {
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     if (this.props.disableSearch) {
       return null;
     }
diff --git a/RNTester/js/RNTesterPage.js b/RNTester/js/RNTesterPage.js
index 5dfb3bda2039..96b016a00000 100644
--- a/RNTester/js/RNTesterPage.js
+++ b/RNTester/js/RNTesterPage.js
@@ -41,6 +41,9 @@ class RNTesterPage extends React.Component<{
       wrapperProps.keyboardShouldPersistTaps = 'handled';
       wrapperProps.keyboardDismissMode = 'interactive';
     }
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     var title = this.props.title ?
       <RNTesterTitle title={this.props.title} /> :
       null;
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 371f43a39af5..8b790eac4d1f 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -78,6 +78,9 @@ function runServer(
   var ms = null;
 
   const terminal = new Terminal(process.stdout);
+  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
+   * found when Flow v0.68 was deployed. To see the error delete this comment
+   * and run Flow. */
   const ReporterImpl = getReporterImpl(args.customLogReporterPath || null);
   const reporter = new ReporterImpl(terminal);
   const packagerServer = getPackagerServer(args, config, reporter);
@@ -105,10 +108,16 @@ function runServer(
 
   app.use(morgan('combined')).use(errorhandler());
 
+  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
+   * found when Flow v0.68 was deployed. To see the error delete this comment
+   * and run Flow. */
   if (args.https && (!args.key || !args.cert)) {
     throw new Error('Cannot use https without specifying key and cert options');
   }
 
+  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
+   * found when Flow v0.68 was deployed. To see the error delete this comment
+   * and run Flow. */
   const serverInstance = args.https
     ? https.createServer(
         {
@@ -157,11 +166,17 @@ function getReporterImpl(customLogReporterPath: ?string) {
 }
 
 function getPackagerServer(args, config, reporter) {
+  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
+   * found when Flow v0.68 was deployed. To see the error delete this comment
+   * and run Flow. */
   const transformModulePath = args.transformer
     ? path.resolve(args.transformer)
     : config.getTransformModulePath();
 
   const providesModuleNodeModules =
+    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.68 was deployed. To see the error delete this
+     * comment and run Flow. */
     args.providesModuleNodeModules || defaultProvidesModuleNodeModules;
 
   return Metro.createServer({
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 7d5e2d3362ba..3813ec4a1011 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -51,4 +51,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.67.0
+^0.68.0
diff --git a/package.json b/package.json
index 3aab6dca4ba0..e7a8250c4d16 100644
--- a/package.json
+++ b/package.json
@@ -215,7 +215,7 @@
     "eslint-plugin-jest": "21.8.0",
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
-    "flow-bin": "^0.67.1",
+    "flow-bin": "^0.68.0",
     "jest": "22.4.2",
     "jest-junit": "3.6.0",
     "prettier": "1.9.1",

From 785c8f7eb920e3df7d1c74875e199d03eda074a8 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 20 Mar 2018 00:58:05 -0700
Subject: [PATCH 0085/1109] Use native as the source of truth to decide if a
 test should use Fabric

Reviewed By: fkgozali

Differential Revision: D7304221

fbshipit-source-id: cdd7053e6ce6522474df261db5710e2d9c013be6
---
 Libraries/Components/View/TestFabricView.js   | 24 ++++++++++++
 .../testing/ReactInstrumentationTest.java     |  7 +++-
 .../testing/fabric/FabricTestModule.java      | 39 +++++++++++++++++++
 3 files changed, 69 insertions(+), 1 deletion(-)
 create mode 100644 Libraries/Components/View/TestFabricView.js
 create mode 100644 ReactAndroid/src/androidTest/java/com/facebook/react/testing/fabric/FabricTestModule.java

diff --git a/Libraries/Components/View/TestFabricView.js b/Libraries/Components/View/TestFabricView.js
new file mode 100644
index 000000000000..01e0e4897b2b
--- /dev/null
+++ b/Libraries/Components/View/TestFabricView.js
@@ -0,0 +1,24 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @providesModule TestFabricView
+ * @flow
+ * @format
+ */
+'use strict';
+
+/**
+ * This is a switch on the correct View to use for Fabric testing purposes
+ */
+let TestFabricView;
+const FabricTestModule = require('NativeModules').FabricTestModule;
+if (FabricTestModule && FabricTestModule.IS_FABRIC_ENABLED) {
+  TestFabricView = require('FabricView');
+} else {
+  TestFabricView = require('View');
+}
+
+module.exports = TestFabricView;
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
index fe6c7c687aec..849254353378 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
@@ -12,6 +12,7 @@
 import android.view.View;
 import android.view.ViewGroup;
 import com.facebook.react.bridge.ReactContext;
+import com.facebook.react.testing.fabric.FabricTestModule;
 import com.facebook.react.testing.idledetection.IdleWaiter;
 
 /**
@@ -110,7 +111,11 @@ protected boolean isFabricTest() {
    * Override this method to provide extra native modules to be loaded before the app starts
    */
   protected ReactInstanceSpecForTest createReactInstanceSpecForTest() {
-    return new ReactInstanceSpecForTest();
+    ReactInstanceSpecForTest instanceSpec = new ReactInstanceSpecForTest();
+    if (isFabricTest()) {
+      instanceSpec.addNativeModule(new FabricTestModule(isFabricTest()));
+    }
+    return instanceSpec;
   }
 
   /**
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/fabric/FabricTestModule.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/fabric/FabricTestModule.java
new file mode 100644
index 000000000000..0e4fe05b099a
--- /dev/null
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/fabric/FabricTestModule.java
@@ -0,0 +1,39 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.testing.fabric;
+
+import com.facebook.react.common.MapBuilder;
+import java.util.Map;
+import javax.annotation.Nullable;
+
+import com.facebook.react.bridge.BaseJavaModule;
+import com.facebook.react.bridge.ReactMethod;
+import com.facebook.react.bridge.ReadableArray;
+import com.facebook.react.bridge.ReadableMap;
+
+/**
+ * Module to indicate if a test is using Fabric
+ */
+public final class FabricTestModule extends BaseJavaModule {
+
+  private final boolean mIsFabricEnabled;
+
+  public FabricTestModule(boolean isFabricEnabled) {
+    mIsFabricEnabled = isFabricEnabled;
+  }
+
+  @Override
+  public String getName() {
+    return "FabricTestModule";
+  }
+
+  @Override
+  public Map<String, Object> getConstants() {
+    return MapBuilder.<String, Object>of("IS_FABRIC_ENABLED", mIsFabricEnabled);
+  }
+}

From c49afb174f76b74e390f531ee67d43997d76f71b Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 20 Mar 2018 00:58:10 -0700
Subject: [PATCH 0086/1109] Add debug logs to FabricUIManager

Reviewed By: mdvacca

Differential Revision: D7310879

fbshipit-source-id: 3c874fd4dbd75dd865f7d94e7e31f538ef67eb66
---
 .../react/fabric/FabricUIManager.java         | 28 +++++++++++++++++++
 .../react/uimanager/ReactShadowNodeImpl.java  |  2 +-
 2 files changed, 29 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 8fd0dd706a76..81a604350978 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -44,6 +44,7 @@ public class FabricUIManager implements UIManager {
 
   private static final String TAG = FabricUIManager.class.getSimpleName();
   private static final boolean DEBUG = true;
+
   private final RootShadowNodeRegistry mRootShadowNodeRegistry = new RootShadowNodeRegistry();
   private final ReactApplicationContext mReactApplicationContext;
   private final ViewManagerRegistry mViewManagerRegistry;
@@ -67,6 +68,12 @@ public FabricUIManager(
   @Nullable
   public ReactShadowNode createNode(
       int reactTag, String viewName, int rootTag, ReadableNativeMap props) {
+    if (DEBUG) {
+      Log.d(TAG, "createNode \n\ttag: " + reactTag +
+          "\n\tviewName: " + viewName +
+          "\n\trootTag: " + rootTag +
+          "\n\tprops: " + props);
+    }
     try {
       ViewManager viewManager = mViewManagerRegistry.get(viewName);
       ReactShadowNode node = viewManager.createShadowNodeInstance(mReactApplicationContext);
@@ -109,6 +116,9 @@ private ReactStylesDiffMap updateProps(ReactShadowNode node, @Nullable ReadableN
    */
   @Nullable
   public ReactShadowNode cloneNode(ReactShadowNode node) {
+    if (DEBUG) {
+      Log.d(TAG, "cloneNode \n\tnode: " + node);
+    }
     try {
       ReactShadowNode clone = node.mutableCopy();
       assertReactShadowNodeCopy(node, clone);
@@ -126,6 +136,9 @@ public ReactShadowNode cloneNode(ReactShadowNode node) {
    */
   @Nullable
   public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node) {
+    if (DEBUG) {
+      Log.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
+    }
     try {
       ReactShadowNode clone = node.mutableCopyWithNewChildren();
       assertReactShadowNodeCopy(node, clone);
@@ -144,6 +157,9 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node) {
   @Nullable
   public ReactShadowNode cloneNodeWithNewProps(
       ReactShadowNode node, @Nullable ReadableNativeMap newProps) {
+    if (DEBUG) {
+      Log.d(TAG, "cloneNodeWithNewProps \n\tnode: " + node + "\n\tprops: " + newProps);
+    }
     try {
       ReactShadowNode clone =
           node.mutableCopyWithNewProps(newProps == null ? null : new ReactStylesDiffMap(newProps));
@@ -164,6 +180,9 @@ public ReactShadowNode cloneNodeWithNewProps(
   @Nullable
   public ReactShadowNode cloneNodeWithNewChildrenAndProps(
       ReactShadowNode node, ReadableNativeMap newProps) {
+    if (DEBUG) {
+      Log.d(TAG, "cloneNodeWithNewChildrenAndProps \n\tnode: " + node + "\n\tnewProps: " + newProps);
+    }
     try {
       ReactShadowNode clone =
           node.mutableCopyWithNewChildrenAndProps(
@@ -194,6 +213,9 @@ private void assertReactShadowNodeCopy(ReactShadowNode source, ReactShadowNode t
    */
   @Nullable
   public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
+    if (DEBUG) {
+      Log.d(TAG, "appendChild \n\tparent: " + parent + "\n\tchild: " + child);
+    }
     try {
       parent.addChildAt(child, parent.getChildCount());
     } catch (Throwable t) {
@@ -206,6 +228,9 @@ public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
    *     ReactShadowNode} elements of the root. Typically this List will contain one element.
    */
   public List<ReactShadowNode> createChildSet(int rootTag) {
+    if (DEBUG) {
+      Log.d(TAG, "createChildSet rootTag: " + rootTag);
+    }
     return new ArrayList<>(1);
   }
 
@@ -217,6 +242,9 @@ public void appendChildToSet(List<ReactShadowNode> childList, ReactShadowNode ch
   }
 
   public synchronized void completeRoot(int rootTag, List<ReactShadowNode> childList) {
+    if (DEBUG) {
+      Log.d(TAG, "completeRoot rootTag: " + rootTag + ", childList: " + childList);
+    }
     try {
       ReactShadowNode rootNode = getRootNode(rootTag);
       Assertions.assertNotNull(
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index a43355e84fc8..8d906c4bc298 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -643,7 +643,7 @@ public boolean isDescendantOf(ReactShadowNodeImpl ancestorNode) {
 
   @Override
   public String toString() {
-    return mViewClassName;
+    return "[" + mViewClassName + " " + getReactTag() + "]";
   }
 
   /*

From f136ae136278c374e24989c693a5b3a0a101178c Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 20 Mar 2018 00:58:16 -0700
Subject: [PATCH 0087/1109] Add test for FabricText

Reviewed By: mdvacca

Differential Revision: D7326562

fbshipit-source-id: e1229f84496e9181475979d757066e3796a24a3f
---
 Libraries/Text/FabricText.js                  | 242 ++++++++++++++++++
 Libraries/Text/TestFabricText.js              |  24 ++
 .../com/facebook/react/common/ArrayUtils.java |   3 +-
 .../react/fabric/FabricReconciler.java        |  18 +-
 4 files changed, 279 insertions(+), 8 deletions(-)
 create mode 100644 Libraries/Text/FabricText.js
 create mode 100644 Libraries/Text/TestFabricText.js

diff --git a/Libraries/Text/FabricText.js b/Libraries/Text/FabricText.js
new file mode 100644
index 000000000000..1eedd8b181c8
--- /dev/null
+++ b/Libraries/Text/FabricText.js
@@ -0,0 +1,242 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @providesModule FabricText
+ * @flow
+ * @format
+ */
+'use strict';
+
+const React = require('React');
+const ReactNative = require('ReactNative');
+const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
+const TextPropTypes = require('TextPropTypes');
+const Touchable = require('Touchable');
+const UIManager = require('UIManager');
+
+const {createReactNativeComponentClass} = require('ReactFabricInternals');
+const mergeFast = require('mergeFast');
+const processColor = require('processColor');
+const {ViewContextTypes} = require('ViewContext');
+
+import type {PressEvent} from 'CoreEventTypes';
+import type {TextProps} from 'TextProps';
+import type {ViewChildContext} from 'ViewContext';
+
+type State = {
+  isHighlighted: boolean,
+};
+
+type RectOffset = {
+  top: number,
+  left: number,
+  right: number,
+  bottom: number,
+};
+
+const PRESS_RECT_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
+
+const viewConfig = {
+  validAttributes: mergeFast(ReactNativeViewAttributes.UIView, {
+    isHighlighted: true,
+    numberOfLines: true,
+    ellipsizeMode: true,
+    allowFontScaling: true,
+    disabled: true,
+    selectable: true,
+    selectionColor: true,
+    adjustsFontSizeToFit: true,
+    minimumFontScale: true,
+    textBreakStrategy: true,
+  }),
+  uiViewClassName: 'RCTText',
+};
+
+/**
+ * A React component for displaying text.
+ *
+ * See https://facebook.github.io/react-native/docs/text.html
+ */
+class Text extends ReactNative.NativeComponent<TextProps, State> {
+  static propTypes = TextPropTypes;
+  static childContextTypes = ViewContextTypes;
+  static contextTypes = ViewContextTypes;
+
+  static defaultProps = {
+    accessible: true,
+    allowFontScaling: true,
+    ellipsizeMode: 'tail',
+  };
+
+  state = mergeFast(Touchable.Mixin.touchableGetInitialState(), {
+    isHighlighted: false,
+  });
+
+  viewConfig = viewConfig;
+
+  getChildContext(): ViewChildContext {
+    return {
+      isInAParentText: true,
+    };
+  }
+
+  _handlers: ?Object;
+
+  _hasPressHandler(): boolean {
+    return !!this.props.onPress || !!this.props.onLongPress;
+  }
+  /**
+   * These are assigned lazily the first time the responder is set to make plain
+   * text nodes as cheap as possible.
+   */
+  touchableHandleActivePressIn: ?Function;
+  touchableHandleActivePressOut: ?Function;
+  touchableHandlePress: ?Function;
+  touchableHandleLongPress: ?Function;
+  touchableHandleResponderGrant: ?Function;
+  touchableHandleResponderMove: ?Function;
+  touchableHandleResponderRelease: ?Function;
+  touchableHandleResponderTerminate: ?Function;
+  touchableHandleResponderTerminationRequest: ?Function;
+  touchableGetPressRectOffset: ?Function;
+
+  render(): React.Element<any> {
+    let newProps = this.props;
+    if (this.props.onStartShouldSetResponder || this._hasPressHandler()) {
+      if (!this._handlers) {
+        this._handlers = {
+          onStartShouldSetResponder: (): boolean => {
+            const shouldSetFromProps =
+              this.props.onStartShouldSetResponder &&
+              this.props.onStartShouldSetResponder();
+            const setResponder = shouldSetFromProps || this._hasPressHandler();
+            if (setResponder && !this.touchableHandleActivePressIn) {
+              // Attach and bind all the other handlers only the first time a touch
+              // actually happens.
+              for (const key in Touchable.Mixin) {
+                if (typeof Touchable.Mixin[key] === 'function') {
+                  (this: any)[key] = Touchable.Mixin[key].bind(this);
+                }
+              }
+              this.touchableHandleActivePressIn = () => {
+                if (
+                  this.props.suppressHighlighting ||
+                  !this._hasPressHandler()
+                ) {
+                  return;
+                }
+                this.setState({
+                  isHighlighted: true,
+                });
+              };
+
+              this.touchableHandleActivePressOut = () => {
+                if (
+                  this.props.suppressHighlighting ||
+                  !this._hasPressHandler()
+                ) {
+                  return;
+                }
+                this.setState({
+                  isHighlighted: false,
+                });
+              };
+
+              this.touchableHandlePress = (e: PressEvent) => {
+                this.props.onPress && this.props.onPress(e);
+              };
+
+              this.touchableHandleLongPress = (e: PressEvent) => {
+                this.props.onLongPress && this.props.onLongPress(e);
+              };
+
+              this.touchableGetPressRectOffset = function(): RectOffset {
+                return this.props.pressRetentionOffset || PRESS_RECT_OFFSET;
+              };
+            }
+            return setResponder;
+          },
+          onResponderGrant: function(e: SyntheticEvent<>, dispatchID: string) {
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
+            this.touchableHandleResponderGrant(e, dispatchID);
+            this.props.onResponderGrant &&
+              this.props.onResponderGrant.apply(this, arguments);
+          }.bind(this),
+          onResponderMove: function(e: SyntheticEvent<>) {
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
+            this.touchableHandleResponderMove(e);
+            this.props.onResponderMove &&
+              this.props.onResponderMove.apply(this, arguments);
+          }.bind(this),
+          onResponderRelease: function(e: SyntheticEvent<>) {
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
+            this.touchableHandleResponderRelease(e);
+            this.props.onResponderRelease &&
+              this.props.onResponderRelease.apply(this, arguments);
+          }.bind(this),
+          onResponderTerminate: function(e: SyntheticEvent<>) {
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
+            this.touchableHandleResponderTerminate(e);
+            this.props.onResponderTerminate &&
+              this.props.onResponderTerminate.apply(this, arguments);
+          }.bind(this),
+          onResponderTerminationRequest: function(): boolean {
+            // Allow touchable or props.onResponderTerminationRequest to deny
+            // the request
+            // $FlowFixMe TouchableMixin handlers couldn't actually be null
+            var allowTermination = this.touchableHandleResponderTerminationRequest();
+            if (allowTermination && this.props.onResponderTerminationRequest) {
+              allowTermination = this.props.onResponderTerminationRequest.apply(
+                this,
+                arguments,
+              );
+            }
+            return allowTermination;
+          }.bind(this),
+        };
+      }
+      newProps = {
+        ...this.props,
+        ...this._handlers,
+        isHighlighted: this.state.isHighlighted,
+      };
+    }
+    if (newProps.selectionColor != null) {
+      newProps = {
+        ...newProps,
+        selectionColor: processColor(newProps.selectionColor),
+      };
+    }
+    if (Touchable.TOUCH_TARGET_DEBUG && newProps.onPress) {
+      newProps = {
+        ...newProps,
+        style: [this.props.style, {color: 'magenta'}],
+      };
+    }
+    if (this.context.isInAParentText) {
+      return <RCTVirtualText {...newProps} />;
+    } else {
+      return <RCTText {...newProps} />;
+    }
+  }
+}
+
+var RCTText = createReactNativeComponentClass(
+  viewConfig.uiViewClassName,
+  () => viewConfig,
+);
+var RCTVirtualText = RCTText;
+
+if (UIManager.RCTVirtualText) {
+  RCTVirtualText = createReactNativeComponentClass('RCTVirtualText', () => ({
+    validAttributes: mergeFast(ReactNativeViewAttributes.UIView, {
+      isHighlighted: true,
+    }),
+    uiViewClassName: 'RCTVirtualText',
+  }));
+}
+
+module.exports = Text;
diff --git a/Libraries/Text/TestFabricText.js b/Libraries/Text/TestFabricText.js
new file mode 100644
index 000000000000..cdedcc3177ca
--- /dev/null
+++ b/Libraries/Text/TestFabricText.js
@@ -0,0 +1,24 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @providesModule TestFabricText
+ * @flow
+ * @format
+ */
+'use strict';
+
+/**
+ * This is a switch on the correct Text to use for Fabric testing purposes
+ */
+let TestFabricText;
+const FabricTestModule = require('NativeModules').FabricTestModule;
+if (FabricTestModule && FabricTestModule.IS_FABRIC_ENABLED) {
+  TestFabricText = require('FabricText');
+} else {
+  TestFabricText = require('Text');
+}
+
+module.exports = TestFabricText;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/common/ArrayUtils.java b/ReactAndroid/src/main/java/com/facebook/react/common/ArrayUtils.java
index 41b62c19f255..5b2f32023c1c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/common/ArrayUtils.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/common/ArrayUtils.java
@@ -11,10 +11,9 @@ public static float[] copyArray(float[] array) {
 
   public static int[] copyListToArray(List<Integer> list) {
     int[] array = new int[list.size()];
-    for (int t = 0 ; t < list.size() ; t++) {
+    for (int t = 0; t < list.size(); t++) {
       array[t] = list.get(t);
     }
     return array;
   }
-
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index 4ea5d143bcdd..3d7571e496b9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -8,6 +8,7 @@
 package com.facebook.react.fabric;
 
 import android.util.Log;
+import android.util.SparseArray;
 import com.facebook.react.common.ArrayUtils;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.UIViewOperationQueue;
@@ -74,15 +75,15 @@ private void manageChildren(
     // It is more efficient to reorder removing and adding all the views in the right order, instead
     // of calculating the minimum amount of reorder operations.
     Set<Integer> addedTags = new HashSet<>();
-    ViewAtIndex[] viewsToAdd = new ViewAtIndex[newList.size() - firstRemovedOrAddedViewIndex];
-    int viewsToAddIndex = 0;
+    List<ViewAtIndex> viewsToAdd = new LinkedList<>();
     for (int k = firstRemovedOrAddedViewIndex; k < newList.size(); k++) {
       ReactShadowNode newNode = newList.get(k);
+      if (newNode.isVirtual()) continue;
       if (newNode.getNewProps() != null) {
         uiViewOperationQueue.enqueueUpdateProperties(
           newNode.getReactTag(), newNode.getViewClass(), newNode.getNewProps());
       }
-      viewsToAdd[viewsToAddIndex++] = new ViewAtIndex(newNode.getReactTag(), k);
+      viewsToAdd.add(new ViewAtIndex(newNode.getReactTag(), k));
       List previousChildrenList = newNode.getOriginalReactShadowNode() == null ? null : newNode.getOriginalReactShadowNode().getChildrenList();
       manageChildren(newNode, previousChildrenList, newNode.getChildrenList());
       newNode.setOriginalReactShadowNode(newNode);
@@ -100,6 +101,7 @@ private void manageChildren(
     int indicesToRemoveIndex = 0;
     for (int j = firstRemovedOrAddedViewIndex; j < prevList.size(); j++) {
       ReactShadowNode nodeToRemove = prevList.get(j);
+      if (nodeToRemove.isVirtual()) continue;
       indicesToRemove[indicesToRemoveIndex++] = j;
       if (!addedTags.contains(nodeToRemove.getReactTag())) {
         tagsToDelete.add(nodeToRemove.getReactTag());
@@ -110,16 +112,20 @@ private void manageChildren(
     }
 
     int[] tagsToDeleteArray = ArrayUtils.copyListToArray(tagsToDelete);
+    ViewAtIndex[] viewsToAddArray = viewsToAdd.toArray(new ViewAtIndex[viewsToAdd.size()]);
     if (DEBUG) {
       Log.d(
         TAG,
         "manageChildren.enqueueManageChildren parent: " + parent.getReactTag() +
           "\n\tIndices2Remove: " + Arrays.toString(indicesToRemove) +
-          "\n\tViews2Add: " + Arrays.toString(viewsToAdd) +
+          "\n\tViews2Add: " + Arrays.toString(viewsToAddArray) +
           "\n\tTags2Delete: " + Arrays.toString(tagsToDeleteArray));
     }
-    uiViewOperationQueue.enqueueManageChildren(
-      parent.getReactTag(), indicesToRemove, viewsToAdd, tagsToDeleteArray);
+    // TODO (t27180994): Mutate views synchronously on main thread
+    if (indicesToRemove.length > 0 || viewsToAddArray.length > 0 || tagsToDeleteArray.length > 0) {
+      uiViewOperationQueue.enqueueManageChildren(
+        parent.getReactTag(), indicesToRemove, viewsToAddArray, tagsToDeleteArray);
+    }
   }
 
 }

From af4282940436e81095804dc1729784d2413461aa Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 20 Mar 2018 00:58:18 -0700
Subject: [PATCH 0088/1109] Fix TextRenderingTestCase

Reviewed By: mdvacca

Differential Revision: D7330681

fbshipit-source-id: 5dd2a60382d01fb841f16851a9b2027e2b08e748
---
 .../com/facebook/react/testing/ReactInstrumentationTest.java | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
index 849254353378..7544395157c6 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
@@ -11,6 +11,7 @@
 import android.test.ActivityInstrumentationTestCase2;
 import android.view.View;
 import android.view.ViewGroup;
+import com.facebook.react.bridge.JavaScriptModule;
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.testing.fabric.FabricTestModule;
 import com.facebook.react.testing.idledetection.IdleWaiter;
@@ -107,6 +108,10 @@ protected boolean isFabricTest() {
     return false;
   }
 
+  protected <T extends JavaScriptModule> T getJSModule(Class<T> jsInterface) {
+    return getReactContext().getJSModule(jsInterface);
+  }
+
   /**
    * Override this method to provide extra native modules to be loaded before the app starts
    */

From aabd5d1458798e6ba3c7f8194f489c17b28903ca Mon Sep 17 00:00:00 2001
From: Charles Dick <cwdick@fb.com>
Date: Tue, 20 Mar 2018 04:12:06 -0700
Subject: [PATCH 0089/1109] Use map instead of array

Reviewed By: dcaspi

Differential Revision: D7327839

fbshipit-source-id: e48d2b9f34e337d14f9519eac16b6a15fa56deb5
---
 Libraries/BatchedBridge/MessageQueue.js | 11 ++++++-----
 1 file changed, 6 insertions(+), 5 deletions(-)

diff --git a/Libraries/BatchedBridge/MessageQueue.js b/Libraries/BatchedBridge/MessageQueue.js
index 428d38817398..98662c28cc6d 100644
--- a/Libraries/BatchedBridge/MessageQueue.js
+++ b/Libraries/BatchedBridge/MessageQueue.js
@@ -44,8 +44,8 @@ let JSTimers = null;
 class MessageQueue {
   _lazyCallableModules: {[key: string]: (void) => Object};
   _queue: [number[], number[], any[], number];
-  _successCallbacks: (?Function)[];
-  _failureCallbacks: (?Function)[];
+  _successCallbacks: {[key: number]: ?Function};
+  _failureCallbacks: {[key: number]: ?Function};
   _callID: number;
   _inCall: number;
   _lastFlush: number;
@@ -62,8 +62,8 @@ class MessageQueue {
   constructor(shouldUninstallGlobalErrorHandler: boolean = false) {
     this._lazyCallableModules = {};
     this._queue = [[], [], [], 0];
-    this._successCallbacks = [];
-    this._failureCallbacks = [];
+    this._successCallbacks = {};
+    this._failureCallbacks = {};
     this._callID = 0;
     this._lastFlush = 0;
     this._eventLoopStartTime = new Date().getTime();
@@ -394,7 +394,8 @@ class MessageQueue {
       return;
     }
 
-    this._successCallbacks[callID] = this._failureCallbacks[callID] = null;
+    delete this._successCallbacks[callID];
+    delete this._failureCallbacks[callID];
     callback(...args);
 
     if (__DEV__) {

From fa7c322af42e0debed0cdc0944faaf55f17e6f15 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Tue, 20 Mar 2018 04:49:12 -0700
Subject: [PATCH 0090/1109] Depend on local version of
 babel-plugin-react-transform

Reviewed By: jeanlauliac

Differential Revision: D7319513

fbshipit-source-id: 4945ec753087206cd01eca4ba9464672d5fb05ba
---
 babel-preset/configs/hmr.js | 7 +++----
 1 file changed, 3 insertions(+), 4 deletions(-)

diff --git a/babel-preset/configs/hmr.js b/babel-preset/configs/hmr.js
index 91cb9a356c65..cdf5a022c202 100644
--- a/babel-preset/configs/hmr.js
+++ b/babel-preset/configs/hmr.js
@@ -7,7 +7,6 @@
 'use strict';
 
 var path = require('path');
-var resolvePlugins = require('../lib/resolvePlugins');
 
 var hmrTransform = 'react-transform-hmr/lib/index.js';
 var transformPath = require.resolve(hmrTransform);
@@ -23,9 +22,9 @@ module.exports = function(options, filename) {
   }
 
   return {
-    plugins: resolvePlugins([
+    plugins: [
       [
-        'react-transform',
+        require('metro-babel7-plugin-react-transform').default,
         {
           transforms: [{
             transform: transform,
@@ -34,6 +33,6 @@ module.exports = function(options, filename) {
           }]
         },
       ]
-    ])
+    ]
   };
 };

From f6bcd73ed7cdc1f76a940e301a42d8b578f890c8 Mon Sep 17 00:00:00 2001
From: Jeff Hampton <jhampton@gmail.com>
Date: Tue, 20 Mar 2018 05:15:48 -0700
Subject: [PATCH 0091/1109] feat: Remove platform check in
 requireNativeComponent to support additional platforms

Summary:
Using platform checks can make it difficult to incorporate changes for other platforms (e.g. Windows).
 Using a check for the underlying function accomplishes the same goal without relying on an Android-specific check.  This change allows this JS file to be re-used instead of copied and modified.

[X] Run Jest tests
[X] Test in RNTester on simulators
[X] Test in Playground

No related PR's found :)

[GENERAL] [ENHANCEMENT] [Libraries/ReactNative/requireFabricComponent.js] - Simplified check against UIManager to support additional platforms, removing Android-specific check
Closes https://github.com/facebook/react-native/pull/18381

Differential Revision: D7336214

Pulled By: hramos

fbshipit-source-id: e936f1fdcf36556c528115ee3f79197883d7b7d4
---
 .../ReactNative/requireFabricComponent.js     | 31 +++++++++----------
 .../ReactNative/requireNativeComponent.js     | 31 +++++++++----------
 2 files changed, 30 insertions(+), 32 deletions(-)

diff --git a/Libraries/ReactNative/requireFabricComponent.js b/Libraries/ReactNative/requireFabricComponent.js
index 4b6010a0c264..4d9fca04cd58 100644
--- a/Libraries/ReactNative/requireFabricComponent.js
+++ b/Libraries/ReactNative/requireFabricComponent.js
@@ -53,22 +53,21 @@ function requireNativeComponent(
   extraConfig?: ?{nativeOnly?: Object},
 ): React$ComponentType<any> | string {
   function attachDefaultEventTypes(viewConfig: any) {
-    if (Platform.OS === 'android') {
-      // This is supported on Android platform only,
-      // as lazy view managers discovery is Android-specific.
-      if (UIManager.ViewManagerNames) {
-        // Lazy view managers enabled.
-        viewConfig = merge(viewConfig, UIManager.getDefaultEventTypes());
-      } else {
-        viewConfig.bubblingEventTypes = merge(
-          viewConfig.bubblingEventTypes,
-          UIManager.genericBubblingEventTypes,
-        );
-        viewConfig.directEventTypes = merge(
-          viewConfig.directEventTypes,
-          UIManager.genericDirectEventTypes,
-        );
-      }
+    // This is supported on UIManager platforms (ex: Android),
+    // as lazy view managers are not implemented for all platforms.
+    // See [UIManager] for details on constants and implementations.
+    if (UIManager.ViewManagerNames) {
+      // Lazy view managers enabled.
+      viewConfig = merge(viewConfig, UIManager.getDefaultEventTypes());
+    } else {
+      viewConfig.bubblingEventTypes = merge(
+        viewConfig.bubblingEventTypes,
+        UIManager.genericBubblingEventTypes,
+      );
+      viewConfig.directEventTypes = merge(
+        viewConfig.directEventTypes,
+        UIManager.genericDirectEventTypes,
+      );
     }
   }
 
diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index 4a6fd4c1310c..453be93f715b 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -51,22 +51,21 @@ function requireNativeComponent(
   extraConfig?: ?{nativeOnly?: Object},
 ): React$ComponentType<any> | string {
   function attachDefaultEventTypes(viewConfig: any) {
-    if (Platform.OS === 'android') {
-      // This is supported on Android platform only,
-      // as lazy view managers discovery is Android-specific.
-      if (UIManager.ViewManagerNames) {
-        // Lazy view managers enabled.
-        viewConfig = merge(viewConfig, UIManager.getDefaultEventTypes());
-      } else {
-        viewConfig.bubblingEventTypes = merge(
-          viewConfig.bubblingEventTypes,
-          UIManager.genericBubblingEventTypes,
-        );
-        viewConfig.directEventTypes = merge(
-          viewConfig.directEventTypes,
-          UIManager.genericDirectEventTypes,
-        );
-      }
+    // This is supported on UIManager platforms (ex: Android),
+    // as lazy view managers are not implemented for all platforms.
+    // See [UIManager] for details on constants and implementations.
+    if (UIManager.ViewManagerNames) {
+      // Lazy view managers enabled.
+      viewConfig = merge(viewConfig, UIManager.getDefaultEventTypes());
+    } else {
+      viewConfig.bubblingEventTypes = merge(
+        viewConfig.bubblingEventTypes,
+        UIManager.genericBubblingEventTypes,
+      );
+      viewConfig.directEventTypes = merge(
+        viewConfig.directEventTypes,
+        UIManager.genericDirectEventTypes,
+      );
     }
   }
 

From ad6938cda188f30e38d1aa9cbc30ca791ef2d45f Mon Sep 17 00:00:00 2001
From: Naor Matania <naorm1991@fb.com>
Date: Tue, 20 Mar 2018 06:32:57 -0700
Subject: [PATCH 0092/1109] Revert D7319513: Depend on local version of
 babel-plugin-react-transform

Differential Revision:
D7319513

Original commit changeset: 4945ec753087

fbshipit-source-id: 98de6a0fda19732c02ad780953497f9d9b451dea
---
 babel-preset/configs/hmr.js | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/babel-preset/configs/hmr.js b/babel-preset/configs/hmr.js
index cdf5a022c202..91cb9a356c65 100644
--- a/babel-preset/configs/hmr.js
+++ b/babel-preset/configs/hmr.js
@@ -7,6 +7,7 @@
 'use strict';
 
 var path = require('path');
+var resolvePlugins = require('../lib/resolvePlugins');
 
 var hmrTransform = 'react-transform-hmr/lib/index.js';
 var transformPath = require.resolve(hmrTransform);
@@ -22,9 +23,9 @@ module.exports = function(options, filename) {
   }
 
   return {
-    plugins: [
+    plugins: resolvePlugins([
       [
-        require('metro-babel7-plugin-react-transform').default,
+        'react-transform',
         {
           transforms: [{
             transform: transform,
@@ -33,6 +34,6 @@ module.exports = function(options, filename) {
           }]
         },
       ]
-    ]
+    ])
   };
 };

From 6f339b6fcb011340d99d7b384f35987dcf03bdd4 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 20 Mar 2018 06:53:37 -0700
Subject: [PATCH 0093/1109] Deprecate postProcessModules config param

Reviewed By: mjesun

Differential Revision: D7320671

fbshipit-source-id: 979108f0931f9ee0dd820025782137d4c726d19f
---
 local-cli/bundle/buildBundle.js | 1 -
 local-cli/server/runServer.js   | 1 -
 2 files changed, 2 deletions(-)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index 10d1ecc6b78b..f476a1396054 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -95,7 +95,6 @@ async function buildBundle(
     maxWorkers: args.maxWorkers,
     platforms: defaultPlatforms.concat(platforms),
     postMinifyProcess: config.postMinifyProcess,
-    postProcessModules: config.postProcessModules,
     postProcessBundleSourcemap: config.postProcessBundleSourcemap,
     projectRoots: config.getProjectRoots(),
     providesModuleNodeModules: providesModuleNodeModules,
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 8b790eac4d1f..b0daff3c5277 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -198,7 +198,6 @@ function getPackagerServer(args, config, reporter) {
     polyfillModuleNames: config.getPolyfillModuleNames(),
     postMinifyProcess: config.postMinifyProcess,
     postProcessBundleSourcemap: config.postProcessBundleSourcemap,
-    postProcessModules: config.postProcessModules,
     projectRoots: args.projectRoots,
     providesModuleNodeModules: providesModuleNodeModules,
     reporter,

From 15f0a7b76c7fc6ea86ca0f0e28e23ce492890431 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 20 Mar 2018 06:53:49 -0700
Subject: [PATCH 0094/1109] Add getRunModuleStatement config param to configure
 the require() statements

Reviewed By: cpojer

Differential Revision: D7334078

fbshipit-source-id: c19340567c634e3173ee707e92389eaaa4e724e9
---
 local-cli/bundle/buildBundle.js | 1 +
 local-cli/server/runServer.js   | 1 +
 2 files changed, 2 insertions(+)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index f476a1396054..51427aa8f3a3 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -89,6 +89,7 @@ async function buildBundle(
     extraNodeModules: config.extraNodeModules,
     getModulesRunBeforeMainModule: config.getModulesRunBeforeMainModule,
     getPolyfills: config.getPolyfills,
+    getRunModuleStatement: config.getRunModuleStatement,
     getTransformOptions: config.getTransformOptions,
     globalTransformCache: null,
     hasteImplModulePath: config.hasteImplModulePath,
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index b0daff3c5277..a9ba1557ddc7 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -190,6 +190,7 @@ function getPackagerServer(args, config, reporter) {
     dynamicDepsInPackages: config.dynamicDepsInPackages,
     getModulesRunBeforeMainModule: config.getModulesRunBeforeMainModule,
     getPolyfills: config.getPolyfills,
+    getRunModuleStatement: config.getRunModuleStatement,
     getTransformOptions: config.getTransformOptions,
     globalTransformCache: null,
     hasteImplModulePath: config.hasteImplModulePath,

From ddfcaf96bcea0d08f89afe7d340be4a5f23679ce Mon Sep 17 00:00:00 2001
From: Jonathan Kim <jjkim@fb.com>
Date: Tue, 20 Mar 2018 14:37:57 -0700
Subject: [PATCH 0095/1109] Drop fb{android|objc} prefixed keys for oss builds

Reviewed By: hramos

Differential Revision: D7329425

fbshipit-source-id: 8a2e5936991f99b0d5112a6940856e8ee1d32a55
---
 ReactNative/DEFS.bzl | 38 +++++++++++++++++++++-----------------
 1 file changed, 21 insertions(+), 17 deletions(-)

diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index 8842ed74f8cd..b84007444e5e 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -34,8 +34,12 @@ with allow_unsafe_import():
 
 
 # Building is not supported in OSS right now
-def rn_xplat_cxx_library(name, platforms = None, **kwargs):
-    cxx_library(name=name, **kwargs)
+def rn_xplat_cxx_library(name, **kwargs):
+    _ignore = kwargs
+    native.cxx_library(
+        name=name,
+        visibility=kwargs.get("visibility", [])
+    )
 
 
 # Example: react_native_target('java/com/facebook/react/common:common')
@@ -89,39 +93,39 @@ def rn_android_library(name, deps=[], plugins=[], *args, **kwargs):
 
         plugins = list(set(plugins + react_module_plugins))
 
-    android_library(name=name, deps=deps, plugins=plugins, *args, **kwargs)
+    native.android_library(name=name, deps=deps, plugins=plugins, *args, **kwargs)
 
 
 def rn_android_binary(*args, **kwargs):
-    android_binary(*args, **kwargs)
+    native.android_binary(*args, **kwargs)
 
 
 def rn_android_build_config(*args, **kwargs):
-    android_build_config(*args, **kwargs)
+    native.android_build_config(*args, **kwargs)
 
 
 def rn_android_resource(*args, **kwargs):
-    android_resource(*args, **kwargs)
+    native.android_resource(*args, **kwargs)
 
 
 def rn_android_prebuilt_aar(*args, **kwargs):
-    android_prebuilt_aar(*args, **kwargs)
+    native.android_prebuilt_aar(*args, **kwargs)
 
 
 def rn_java_library(*args, **kwargs):
-    java_library(*args, **kwargs)
+    native.java_library(*args, **kwargs)
 
 
 def rn_java_annotation_processor(*args, **kwargs):
-    java_annotation_processor(*args, **kwargs)
+    native.java_annotation_processor(*args, **kwargs)
 
 
 def rn_prebuilt_native_library(*args, **kwargs):
-    prebuilt_native_library(*args, **kwargs)
+    native.prebuilt_native_library(*args, **kwargs)
 
 
 def rn_prebuilt_jar(*args, **kwargs):
-    prebuilt_jar(*args, **kwargs)
+    native.prebuilt_jar(*args, **kwargs)
 
 
 def rn_robolectric_test(name, srcs, vm_args=None, *args, **kwargs):
@@ -166,10 +170,10 @@ def rn_robolectric_test(name, srcs, vm_args=None, *args, **kwargs):
     )
 
 
-original_cxx_library = cxx_library
-
-
 def cxx_library(allow_jni_merging=None, **kwargs):
-    kwargs.pop('fbandroid_deps', [])
-    kwargs.pop('fbobjc_deps', [])
-    original_cxx_library(**kwargs)
+    args = {
+        k: v
+        for k, v in kwargs.items()
+        if not (k.startswith("fbandroid_") or k.startswith("fbobjc_"))
+    }
+    native.cxx_library(**args)

From ea92f47d901e260983a3e28e209a764a0d8b567b Mon Sep 17 00:00:00 2001
From: Artem Egorov <v-aregor@microsoft.com>
Date: Tue, 20 Mar 2018 14:41:26 -0700
Subject: [PATCH 0096/1109] While linking plugin ask for params only once

Summary:
Resolve #18333

CLI should ask users for params only once and waiting for response while linking plugin

Ran the `link` commands for iOS and Android and confirmed that params requested only once.

[CLI][FEATURE][local-cli/link/link.js] - Requesting link params only once for all platforms
Closes https://github.com/facebook/react-native/pull/18349

Differential Revision: D7342181

Pulled By: hramos

fbshipit-source-id: a10f0f7f2170f067d78b30e5a5221634b77da577
---
 local-cli/link/link.js | 22 +++++++++++-----------
 1 file changed, 11 insertions(+), 11 deletions(-)

diff --git a/local-cli/link/link.js b/local-cli/link/link.js
index b77c135f9f47..66e9efbf563c 100644
--- a/local-cli/link/link.js
+++ b/local-cli/link/link.js
@@ -37,7 +37,9 @@ log.heading = 'rnpm-link';
 
 const dedupeAssets = (assets) => uniqBy(assets, asset => path.basename(asset));
 
-const linkDependency = (platforms, project, dependency) => {
+const linkDependency = async (platforms, project, dependency) => {
+  const params = await pollParams(dependency.config.params);
+
   Object.keys(platforms || {})
     .forEach(platform => {
       if (!project[platform] || !dependency.config[platform]) {
@@ -56,18 +58,16 @@ const linkDependency = (platforms, project, dependency) => {
         return null;
       }
 
-      return pollParams(dependency.config.params).then(params => {
-        log.info(`Linking ${dependency.name} ${platform} dependency`);
+      log.info(`Linking ${dependency.name} ${platform} dependency`);
 
-        linkConfig.register(
-          dependency.name,
-          dependency.config[platform],
-          params,
-          project[platform]
-        );
+      linkConfig.register(
+        dependency.name,
+        dependency.config[platform],
+        params,
+        project[platform]
+      );
 
-        log.info(`Platform '${platform}' module ${dependency.name} has been successfully linked`);
-      });
+      log.info(`Platform '${platform}' module ${dependency.name} has been successfully linked`);
     });
 };
 

From 38fe8c2a9e35df5017c9e5fdef1338fd0394b80c Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 20 Mar 2018 15:28:17 -0700
Subject: [PATCH 0097/1109] moved ReactFabricInternals outside of shims

Summary: Simply moving it out of shims to not confuse React project

Reviewed By: bvaughn

Differential Revision: D7341846

fbshipit-source-id: b1a0cdb0caca977de744699521f42556699993a7
---
 Libraries/{Renderer/shims => ReactNative}/ReactFabricInternals.js | 0
 1 file changed, 0 insertions(+), 0 deletions(-)
 rename Libraries/{Renderer/shims => ReactNative}/ReactFabricInternals.js (100%)

diff --git a/Libraries/Renderer/shims/ReactFabricInternals.js b/Libraries/ReactNative/ReactFabricInternals.js
similarity index 100%
rename from Libraries/Renderer/shims/ReactFabricInternals.js
rename to Libraries/ReactNative/ReactFabricInternals.js

From 3b36a6bf06dee69481a47534e41426a6288bf617 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 20 Mar 2018 17:03:06 -0700
Subject: [PATCH 0098/1109] React sync for revisions ced176e...9d484ed

Reviewed By: bvaughn

Differential Revision: D7338640

fbshipit-source-id: e2d75d2f1795fb3c37f193d15216951c707711d9
---
 Libraries/Renderer/REVISION                   |    2 +-
 Libraries/Renderer/ReactFabric-dev.js         | 3259 ++++++++--------
 Libraries/Renderer/ReactFabric-prod.js        |  671 ++--
 Libraries/Renderer/ReactNativeRenderer-dev.js | 3265 +++++++++--------
 .../Renderer/ReactNativeRenderer-prod.js      |  681 ++--
 Libraries/Renderer/shims/ReactFabric.js       |    5 +
 6 files changed, 4154 insertions(+), 3729 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index 321055318423..7e989de97203 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-ced176edb7605a25e916895fd060f3943c647fee
\ No newline at end of file
+9d484edc4b64160cb335a23a2cb21667fb2cdf4c
\ No newline at end of file
diff --git a/Libraries/Renderer/ReactFabric-dev.js b/Libraries/Renderer/ReactFabric-dev.js
index e485c5621823..22c77f2e072d 100644
--- a/Libraries/Renderer/ReactFabric-dev.js
+++ b/Libraries/Renderer/ReactFabric-dev.js
@@ -25,8 +25,8 @@ var deepDiffer = require("deepDiffer");
 var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
-var checkPropTypes = require("prop-types/checkPropTypes");
 var shallowEqual = require("fbjs/lib/shallowEqual");
+var checkPropTypes = require("prop-types/checkPropTypes");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
 var FabricUIManager = require("FabricUIManager");
 
@@ -4134,1645 +4134,1320 @@ function findCurrentHostFiberWithNoPortals(parent) {
   return null;
 }
 
-var valueStack = [];
+// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
+// Math.pow(2, 30) - 1
+// 0b111111111111111111111111111111
+var MAX_SIGNED_31_BIT_INT = 1073741823;
 
-var fiberStack = void 0;
+// TODO: Use an opaque type once ESLint et al support the syntax
 
-{
-  fiberStack = [];
-}
+var NoWork = 0;
+var Sync = 1;
+var Never = MAX_SIGNED_31_BIT_INT;
 
-var index = -1;
+var UNIT_SIZE = 10;
+var MAGIC_NUMBER_OFFSET = 2;
 
-function createCursor(defaultValue) {
-  return {
-    current: defaultValue
-  };
+// 1 unit of expiration time represents 10ms.
+function msToExpirationTime(ms) {
+  // Always add an offset so that we don't clash with the magic number for NoWork.
+  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
 }
 
-function pop(cursor, fiber) {
-  if (index < 0) {
-    {
-      warning(false, "Unexpected pop.");
-    }
-    return;
-  }
+function expirationTimeToMs(expirationTime) {
+  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
+}
 
-  {
-    if (fiber !== fiberStack[index]) {
-      warning(false, "Unexpected Fiber popped.");
-    }
-  }
+function ceiling(num, precision) {
+  return (((num / precision) | 0) + 1) * precision;
+}
+
+function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
+  return ceiling(
+    currentTime + expirationInMs / UNIT_SIZE,
+    bucketSizeMs / UNIT_SIZE
+  );
+}
 
-  cursor.current = valueStack[index];
+var NoContext = 0;
+var AsyncMode = 1;
+var StrictMode = 2;
 
-  valueStack[index] = null;
+var hasBadMapPolyfill = void 0;
 
-  {
-    fiberStack[index] = null;
+{
+  hasBadMapPolyfill = false;
+  try {
+    var nonExtensibleObject = Object.preventExtensions({});
+    var testMap = new Map([[nonExtensibleObject, null]]);
+    var testSet = new Set([nonExtensibleObject]);
+    // This is necessary for Rollup to not consider these unused.
+    // https://github.com/rollup/rollup/issues/1771
+    // TODO: we can remove these if Rollup fixes the bug.
+    testMap.set(0, 0);
+    testSet.add(0);
+  } catch (e) {
+    // TODO: Consider warning about bad polyfills
+    hasBadMapPolyfill = true;
   }
+}
+
+// A Fiber is work on a Component that needs to be done or was done. There can
+// be more than one per component.
+
+var debugCounter = void 0;
 
-  index--;
+{
+  debugCounter = 1;
 }
 
-function push(cursor, value, fiber) {
-  index++;
+function FiberNode(tag, pendingProps, key, mode) {
+  // Instance
+  this.tag = tag;
+  this.key = key;
+  this.type = null;
+  this.stateNode = null;
 
-  valueStack[index] = cursor.current;
+  // Fiber
+  this["return"] = null;
+  this.child = null;
+  this.sibling = null;
+  this.index = 0;
 
-  {
-    fiberStack[index] = fiber;
-  }
+  this.ref = null;
 
-  cursor.current = value;
-}
+  this.pendingProps = pendingProps;
+  this.memoizedProps = null;
+  this.updateQueue = null;
+  this.memoizedState = null;
 
-function reset() {
-  while (index > -1) {
-    valueStack[index] = null;
+  this.mode = mode;
 
-    {
-      fiberStack[index] = null;
-    }
+  // Effects
+  this.effectTag = NoEffect;
+  this.nextEffect = null;
 
-    index--;
+  this.firstEffect = null;
+  this.lastEffect = null;
+
+  this.expirationTime = NoWork;
+
+  this.alternate = null;
+
+  {
+    this._debugID = debugCounter++;
+    this._debugSource = null;
+    this._debugOwner = null;
+    this._debugIsCurrentlyTiming = false;
+    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
+      Object.preventExtensions(this);
+    }
   }
 }
 
-var describeComponentFrame = function(name, source, ownerName) {
-  return (
-    "\n    in " +
-    (name || "Unknown") +
-    (source
-      ? " (at " +
-        source.fileName.replace(/^.*[\\\/]/, "") +
-        ":" +
-        source.lineNumber +
-        ")"
-      : ownerName ? " (created by " + ownerName + ")" : "")
-  );
+// This is a constructor function, rather than a POJO constructor, still
+// please ensure we do the following:
+// 1) Nobody should add any instance methods on this. Instance methods can be
+//    more difficult to predict when they get optimized and they are almost
+//    never inlined properly in static compilers.
+// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
+//    always know when it is a fiber.
+// 3) We might want to experiment with using numeric keys since they are easier
+//    to optimize in a non-JIT environment.
+// 4) We can easily go from a constructor to a createFiber object literal if that
+//    is faster.
+// 5) It should be easy to port this to a C struct and keep a C implementation
+//    compatible.
+var createFiber = function(tag, pendingProps, key, mode) {
+  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
+  return new FiberNode(tag, pendingProps, key, mode);
 };
 
-function describeFiber(fiber) {
-  switch (fiber.tag) {
-    case IndeterminateComponent:
-    case FunctionalComponent:
-    case ClassComponent:
-    case HostComponent:
-      var owner = fiber._debugOwner;
-      var source = fiber._debugSource;
-      var name = getComponentName(fiber);
-      var ownerName = null;
-      if (owner) {
-        ownerName = getComponentName(owner);
-      }
-      return describeComponentFrame(name, source, ownerName);
-    default:
-      return "";
-  }
+function shouldConstruct(Component) {
+  return !!(Component.prototype && Component.prototype.isReactComponent);
 }
 
-// This function can only be called with a work-in-progress fiber and
-// only during begin or complete phase. Do not call it under any other
-// circumstances.
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  var node = workInProgress;
-  do {
-    info += describeFiber(node);
-    // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
-  } while (node);
-  return info;
-}
+// This is used to create an alternate fiber to do work on.
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  if (workInProgress === null) {
+    // We use a double buffering pooling technique because we know that we'll
+    // only ever need at most two versions of a tree. We pool the "other" unused
+    // node that we're free to reuse. This is lazily created to avoid allocating
+    // extra objects for things that are never updated. It also allow us to
+    // reclaim the extra memory if needed.
+    workInProgress = createFiber(
+      current.tag,
+      pendingProps,
+      current.key,
+      current.mode
+    );
+    workInProgress.type = current.type;
+    workInProgress.stateNode = current.stateNode;
 
-function getCurrentFiberOwnerName() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    var owner = fiber._debugOwner;
-    if (owner !== null && typeof owner !== "undefined") {
-      return getComponentName(owner);
+    {
+      // DEV-only fields
+      workInProgress._debugID = current._debugID;
+      workInProgress._debugSource = current._debugSource;
+      workInProgress._debugOwner = current._debugOwner;
     }
-  }
-  return null;
-}
 
-function getCurrentFiberStackAddendum() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    // Safe because if current fiber exists, we are reconciling,
-    // and it is guaranteed to be the work-in-progress version.
-    return getStackAddendumByWorkInProgressFiber(fiber);
+    workInProgress.alternate = current;
+    current.alternate = workInProgress;
+  } else {
+    workInProgress.pendingProps = pendingProps;
+
+    // We already have an alternate.
+    // Reset the effect tag.
+    workInProgress.effectTag = NoEffect;
+
+    // The effect list is no longer valid.
+    workInProgress.nextEffect = null;
+    workInProgress.firstEffect = null;
+    workInProgress.lastEffect = null;
   }
-  return null;
-}
 
-function resetCurrentFiber() {
-  ReactDebugCurrentFrame.getCurrentStack = null;
-  ReactDebugCurrentFiber.current = null;
-  ReactDebugCurrentFiber.phase = null;
-}
+  workInProgress.expirationTime = expirationTime;
 
-function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
-  ReactDebugCurrentFiber.current = fiber;
-  ReactDebugCurrentFiber.phase = null;
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+
+  // These will be overridden during the parent's reconciliation
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+
+  return workInProgress;
 }
 
-function setCurrentPhase(phase) {
-  ReactDebugCurrentFiber.phase = phase;
+function createHostRootFiber(isAsync) {
+  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
+  return createFiber(HostRoot, null, null, mode);
 }
 
-var ReactDebugCurrentFiber = {
-  current: null,
-  phase: null,
-  resetCurrentFiber: resetCurrentFiber,
-  setCurrentFiber: setCurrentFiber,
-  setCurrentPhase: setCurrentPhase,
-  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
-};
-
-var debugRenderPhaseSideEffects = false;
-var debugRenderPhaseSideEffectsForStrictMode = false;
-
-var enableUserTimingAPI = true;
-var enableGetDerivedStateFromCatch = false;
-var warnAboutDeprecatedLifecycles = false;
-var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
-
-// React Fabric uses persistent reconciler.
-var enableMutatingReconciler = false;
-var enableNoopReconciler = false;
-var enablePersistentReconciler = true;
-
-// Only used in www builds.
-
-// Prefix measurements so that it's possible to filter them.
-// Longer prefixes are hard to read in DevTools.
-var reactEmoji = "\u269B";
-var warningEmoji = "\u26D4";
-var supportsUserTiming =
-  typeof performance !== "undefined" &&
-  typeof performance.mark === "function" &&
-  typeof performance.clearMarks === "function" &&
-  typeof performance.measure === "function" &&
-  typeof performance.clearMeasures === "function";
-
-// Keep track of current fiber so that we know the path to unwind on pause.
-// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
-var currentFiber = null;
-// If we're in the middle of user code, which fiber and method is it?
-// Reusing `currentFiber` would be confusing for this because user code fiber
-// can change during commit phase too, but we don't need to unwind it (since
-// lifecycles in the commit phase don't resemble a tree).
-var currentPhase = null;
-var currentPhaseFiber = null;
-// Did lifecycle hook schedule an update? This is often a performance problem,
-// so we will keep track of it, and include it in the report.
-// Track commits caused by cascading updates.
-var isCommitting = false;
-var hasScheduledUpdateInCurrentCommit = false;
-var hasScheduledUpdateInCurrentPhase = false;
-var commitCountInCurrentWorkLoop = 0;
-var effectCountInCurrentCommit = 0;
-var isWaitingForCallback = false;
-// During commits, we only show a measurement once per method name
-// to avoid stretch the commit phase with measurement overhead.
-var labelsInCurrentCommit = new Set();
-
-var formatMarkName = function(markName) {
-  return reactEmoji + " " + markName;
-};
-
-var formatLabel = function(label, warning$$1) {
-  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
-  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
-  return "" + prefix + label + suffix;
-};
-
-var beginMark = function(markName) {
-  performance.mark(formatMarkName(markName));
-};
-
-var clearMark = function(markName) {
-  performance.clearMarks(formatMarkName(markName));
-};
-
-var endMark = function(label, markName, warning$$1) {
-  var formattedMarkName = formatMarkName(markName);
-  var formattedLabel = formatLabel(label, warning$$1);
-  try {
-    performance.measure(formattedLabel, formattedMarkName);
-  } catch (err) {}
-  // If previous mark was missing for some reason, this will throw.
-  // This could only happen if React crashed in an unexpected place earlier.
-  // Don't pile on with more errors.
-
-  // Clear marks immediately to avoid growing buffer.
-  performance.clearMarks(formattedMarkName);
-  performance.clearMeasures(formattedLabel);
-};
-
-var getFiberMarkName = function(label, debugID) {
-  return label + " (#" + debugID + ")";
-};
-
-var getFiberLabel = function(componentName, isMounted, phase) {
-  if (phase === null) {
-    // These are composite component total time measurements.
-    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
-  } else {
-    // Composite component methods.
-    return componentName + "." + phase;
-  }
-};
-
-var beginFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-
-  if (isCommitting && labelsInCurrentCommit.has(label)) {
-    // During the commit phase, we don't show duplicate labels because
-    // there is a fixed overhead for every measurement, and we don't
-    // want to stretch the commit phase beyond necessary.
-    return false;
-  }
-  labelsInCurrentCommit.add(label);
-
-  var markName = getFiberMarkName(label, debugID);
-  beginMark(markName);
-  return true;
-};
-
-var clearFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  clearMark(markName);
-};
-
-var endFiberMark = function(fiber, phase, warning$$1) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  endMark(label, markName, warning$$1);
-};
-
-var shouldIgnoreFiber = function(fiber) {
-  // Host components should be skipped in the timeline.
-  // We could check typeof fiber.type, but does this work with RN?
-  switch (fiber.tag) {
-    case HostRoot:
-    case HostComponent:
-    case HostText:
-    case HostPortal:
-    case CallComponent:
-    case ReturnComponent:
-    case Fragment:
-    case ContextProvider:
-    case ContextConsumer:
-      return true;
-    default:
-      return false;
-  }
-};
-
-var clearPendingPhaseMeasurement = function() {
-  if (currentPhase !== null && currentPhaseFiber !== null) {
-    clearFiberMark(currentPhaseFiber, currentPhase);
-  }
-  currentPhaseFiber = null;
-  currentPhase = null;
-  hasScheduledUpdateInCurrentPhase = false;
-};
-
-var pauseTimers = function() {
-  // Stops all currently active measurements so that they can be resumed
-  // if we continue in a later deferred loop from the same unit of work.
-  var fiber = currentFiber;
-  while (fiber) {
-    if (fiber._debugIsCurrentlyTiming) {
-      endFiberMark(fiber, null, null);
-    }
-    fiber = fiber["return"];
-  }
-};
-
-var resumeTimersRecursively = function(fiber) {
-  if (fiber["return"] !== null) {
-    resumeTimersRecursively(fiber["return"]);
-  }
-  if (fiber._debugIsCurrentlyTiming) {
-    beginFiberMark(fiber, null);
-  }
-};
-
-var resumeTimers = function() {
-  // Resumes all measurements that were active during the last deferred loop.
-  if (currentFiber !== null) {
-    resumeTimersRecursively(currentFiber);
-  }
-};
-
-function recordEffect() {
-  if (enableUserTimingAPI) {
-    effectCountInCurrentCommit++;
-  }
-}
-
-function recordScheduleUpdate() {
-  if (enableUserTimingAPI) {
-    if (isCommitting) {
-      hasScheduledUpdateInCurrentCommit = true;
-    }
-    if (
-      currentPhase !== null &&
-      currentPhase !== "componentWillMount" &&
-      currentPhase !== "componentWillReceiveProps"
-    ) {
-      hasScheduledUpdateInCurrentPhase = true;
-    }
-  }
-}
-
-function startRequestCallbackTimer() {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming && !isWaitingForCallback) {
-      isWaitingForCallback = true;
-      beginMark("(Waiting for async callback...)");
-    }
-  }
-}
-
-function stopRequestCallbackTimer(didExpire) {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming) {
-      isWaitingForCallback = false;
-      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
-      endMark(
-        "(Waiting for async callback...)",
-        "(Waiting for async callback...)",
-        warning$$1
-      );
-    }
-  }
-}
-
-function startWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, this is the fiber to unwind from.
-    currentFiber = fiber;
-    if (!beginFiberMark(fiber, null)) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = true;
-  }
-}
-
-function cancelWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // Remember we shouldn't complete measurement for this fiber.
-    // Otherwise flamechart will be deep even for small updates.
-    fiber._debugIsCurrentlyTiming = false;
-    clearFiberMark(fiber, null);
-  }
-}
-
-function stopWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    endFiberMark(fiber, null, null);
-  }
-}
-
-function stopFailedWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    var warning$$1 = "An error was thrown inside this error boundary";
-    endFiberMark(fiber, null, warning$$1);
-  }
-}
-
-function startPhaseTimer(fiber, phase) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    clearPendingPhaseMeasurement();
-    if (!beginFiberMark(fiber, phase)) {
-      return;
-    }
-    currentPhaseFiber = fiber;
-    currentPhase = phase;
-  }
-}
-
-function stopPhaseTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    if (currentPhase !== null && currentPhaseFiber !== null) {
-      var warning$$1 = hasScheduledUpdateInCurrentPhase
-        ? "Scheduled a cascading update"
-        : null;
-      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
-    }
-    currentPhase = null;
-    currentPhaseFiber = null;
-  }
-}
-
-function startWorkLoopTimer(nextUnitOfWork) {
-  if (enableUserTimingAPI) {
-    currentFiber = nextUnitOfWork;
-    if (!supportsUserTiming) {
-      return;
-    }
-    commitCountInCurrentWorkLoop = 0;
-    // This is top level call.
-    // Any other measurements are performed within.
-    beginMark("(React Tree Reconciliation)");
-    // Resume any measurements that were in progress during the last loop.
-    resumeTimers();
-  }
-}
-
-function stopWorkLoopTimer(interruptedBy) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var warning$$1 = null;
-    if (interruptedBy !== null) {
-      if (interruptedBy.tag === HostRoot) {
-        warning$$1 = "A top-level update interrupted the previous render";
-      } else {
-        var componentName = getComponentName(interruptedBy) || "Unknown";
-        warning$$1 =
-          "An update to " + componentName + " interrupted the previous render";
-      }
-    } else if (commitCountInCurrentWorkLoop > 1) {
-      warning$$1 = "There were cascading updates";
-    }
-    commitCountInCurrentWorkLoop = 0;
-    // Pause any measurements until the next loop.
-    pauseTimers();
-    endMark(
-      "(React Tree Reconciliation)",
-      "(React Tree Reconciliation)",
-      warning$$1
-    );
-  }
-}
-
-function startCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    isCommitting = true;
-    hasScheduledUpdateInCurrentCommit = false;
-    labelsInCurrentCommit.clear();
-    beginMark("(Committing Changes)");
-  }
-}
-
-function stopCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-
-    var warning$$1 = null;
-    if (hasScheduledUpdateInCurrentCommit) {
-      warning$$1 = "Lifecycle hook scheduled a cascading update";
-    } else if (commitCountInCurrentWorkLoop > 0) {
-      warning$$1 = "Caused by a cascading update in earlier commit";
-    }
-    hasScheduledUpdateInCurrentCommit = false;
-    commitCountInCurrentWorkLoop++;
-    isCommitting = false;
-    labelsInCurrentCommit.clear();
-
-    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
-  }
-}
-
-function startCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Host Effects)");
-  }
-}
-
-function stopCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Host Effects: " + count + " Total)",
-      "(Committing Host Effects)",
-      null
-    );
+function createFiberFromElement(element, mode, expirationTime) {
+  var owner = null;
+  {
+    owner = element._owner;
   }
-}
 
-function startCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Calling Lifecycle Methods)");
-  }
-}
+  var fiber = void 0;
+  var type = element.type;
+  var key = element.key;
+  var pendingProps = element.props;
 
-function stopCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
+  var fiberTag = void 0;
+  if (typeof type === "function") {
+    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
+  } else if (typeof type === "string") {
+    fiberTag = HostComponent;
+  } else {
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          pendingProps.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= AsyncMode | StrictMode;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= StrictMode;
+        break;
+      case REACT_CALL_TYPE:
+        fiberTag = CallComponent;
+        break;
+      case REACT_RETURN_TYPE:
+        fiberTag = ReturnComponent;
+        break;
+      default: {
+        if (typeof type === "object" && type !== null) {
+          switch (type.$$typeof) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = ContextProvider;
+              break;
+            case REACT_CONTEXT_TYPE:
+              // This is a consumer
+              fiberTag = ContextConsumer;
+              break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = ForwardRef;
+              break;
+            default:
+              if (typeof type.tag === "number") {
+                // Currently assumed to be a continuation and therefore is a
+                // fiber already.
+                // TODO: The yield system is currently broken for updates in
+                // some cases. The reified yield stores a fiber, but we don't
+                // know which fiber that is; the current or a workInProgress?
+                // When the continuation gets rendered here we don't know if we
+                // can reuse that fiber or if we need to clone it. There is
+                // probably a clever way to restructure this.
+                fiber = type;
+                fiber.pendingProps = pendingProps;
+                fiber.expirationTime = expirationTime;
+                return fiber;
+              } else {
+                throwOnInvalidElementType(type, owner);
+              }
+              break;
+          }
+        } else {
+          throwOnInvalidElementType(type, owner);
+        }
+      }
     }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Calling Lifecycle Methods: " + count + " Total)",
-      "(Calling Lifecycle Methods)",
-      null
-    );
   }
-}
-
-var warnedAboutMissingGetChildContext = void 0;
-
-{
-  warnedAboutMissingGetChildContext = {};
-}
 
-// A cursor to the current merged context object on the stack.
-var contextStackCursor = createCursor(emptyObject);
-// A cursor to a boolean indicating whether the context has changed.
-var didPerformWorkStackCursor = createCursor(false);
-// Keep track of the previous context object that was on the stack.
-// We use this to get access to the parent context after we have already
-// pushed the next context provider, and now need to merge their contexts.
-var previousContext = emptyObject;
+  fiber = createFiber(fiberTag, pendingProps, key, mode);
+  fiber.type = type;
+  fiber.expirationTime = expirationTime;
 
-function getUnmaskedContext(workInProgress) {
-  var hasOwnContext = isContextProvider(workInProgress);
-  if (hasOwnContext) {
-    // If the fiber is a context provider itself, when we read its context
-    // we have already pushed its own child context on the stack. A context
-    // provider should not "see" its own child context. Therefore we read the
-    // previous (parent) context instead for a context provider.
-    return previousContext;
+  {
+    fiber._debugSource = element._source;
+    fiber._debugOwner = element._owner;
   }
-  return contextStackCursor.current;
-}
 
-function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-  var instance = workInProgress.stateNode;
-  instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-  instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  return fiber;
 }
 
-function getMaskedContext(workInProgress, unmaskedContext) {
-  var type = workInProgress.type;
-  var contextTypes = type.contextTypes;
-  if (!contextTypes) {
-    return emptyObject;
-  }
-
-  // Avoid recreating masked context unless unmasked context has changed.
-  // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
-  // This may trigger infinite loops if componentWillReceiveProps calls setState.
-  var instance = workInProgress.stateNode;
-  if (
-    instance &&
-    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-  ) {
-    return instance.__reactInternalMemoizedMaskedChildContext;
-  }
-
-  var context = {};
-  for (var key in contextTypes) {
-    context[key] = unmaskedContext[key];
-  }
-
+function throwOnInvalidElementType(type, owner) {
+  var info = "";
   {
-    var name = getComponentName(workInProgress) || "Unknown";
-    checkPropTypes(
-      contextTypes,
-      context,
-      "context",
-      name,
-      ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-    );
-  }
-
-  // Cache unmasked context so we can avoid recreating masked context unless necessary.
-  // Context is created before the class component is instantiated so check for instance.
-  if (instance) {
-    cacheContext(workInProgress, unmaskedContext, context);
+    if (
+      type === undefined ||
+      (typeof type === "object" &&
+        type !== null &&
+        Object.keys(type).length === 0)
+    ) {
+      info +=
+        " You likely forgot to export your component from the file " +
+        "it's defined in, or you might have mixed up default and " +
+        "named imports.";
+    }
+    var ownerName = owner ? getComponentName(owner) : null;
+    if (ownerName) {
+      info += "\n\nCheck the render method of `" + ownerName + "`.";
+    }
   }
-
-  return context;
-}
-
-function hasContextChanged() {
-  return didPerformWorkStackCursor.current;
+  invariant(
+    false,
+    "Element type is invalid: expected a string (for built-in " +
+      "components) or a class/function (for composite components) " +
+      "but got: %s.%s",
+    type == null ? type : typeof type,
+    info
+  );
 }
 
-function isContextConsumer(fiber) {
-  return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  var fiber = createFiber(Fragment, elements, key, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
 }
 
-function isContextProvider(fiber) {
-  return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+function createFiberFromText(content, mode, expirationTime) {
+  var fiber = createFiber(HostText, content, null, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
 }
 
-function popContextProvider(fiber) {
-  if (!isContextProvider(fiber)) {
-    return;
-  }
-
-  pop(didPerformWorkStackCursor, fiber);
-  pop(contextStackCursor, fiber);
+function createFiberFromHostInstanceForDeletion() {
+  var fiber = createFiber(HostComponent, null, null, NoContext);
+  fiber.type = "DELETED";
+  return fiber;
 }
 
-function popTopLevelContextObject(fiber) {
-  pop(didPerformWorkStackCursor, fiber);
-  pop(contextStackCursor, fiber);
+function createFiberFromPortal(portal, mode, expirationTime) {
+  var pendingProps = portal.children !== null ? portal.children : [];
+  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null, // Used by persistent updates
+    implementation: portal.implementation
+  };
+  return fiber;
 }
 
-function pushTopLevelContextObject(fiber, context, didChange) {
-  invariant(
-    contextStackCursor.cursor == null,
-    "Unexpected context found on stack. " +
-      "This error is likely caused by a bug in React. Please file an issue."
-  );
+// TODO: This should be lifted into the renderer.
 
-  push(contextStackCursor, context, fiber);
-  push(didPerformWorkStackCursor, didChange, fiber);
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  // Cyclic construction. This cheats the type system right now because
+  // stateNode is any.
+  var uninitializedFiber = createHostRootFiber(isAsync);
+  var root = {
+    current: uninitializedFiber,
+    containerInfo: containerInfo,
+    pendingChildren: null,
+    pendingCommitExpirationTime: NoWork,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    remainingExpirationTime: NoWork,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  uninitializedFiber.stateNode = root;
+  return root;
 }
 
-function processChildContext(fiber, parentContext) {
-  var instance = fiber.stateNode;
-  var childContextTypes = fiber.type.childContextTypes;
-
-  // TODO (bvaughn) Replace this behavior with an invariant() in the future.
-  // It has only been added in Fiber to match the (unintentional) behavior in Stack.
-  if (typeof instance.getChildContext !== "function") {
-    {
-      var componentName = getComponentName(fiber) || "Unknown";
+var onCommitFiberRoot = null;
+var onCommitFiberUnmount = null;
+var hasLoggedError = false;
 
-      if (!warnedAboutMissingGetChildContext[componentName]) {
-        warnedAboutMissingGetChildContext[componentName] = true;
-        warning(
-          false,
-          "%s.childContextTypes is specified but there is no getChildContext() method " +
-            "on the instance. You can either define getChildContext() on %s or remove " +
-            "childContextTypes from it.",
-          componentName,
-          componentName
-        );
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {
+      if (true && !hasLoggedError) {
+        hasLoggedError = true;
+        warning(false, "React DevTools encountered an error: %s", err);
       }
     }
-    return parentContext;
-  }
+  };
+}
 
-  var childContext = void 0;
-  {
-    ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
-  }
-  startPhaseTimer(fiber, "getChildContext");
-  childContext = instance.getChildContext();
-  stopPhaseTimer();
-  {
-    ReactDebugCurrentFiber.setCurrentPhase(null);
+function injectInternals(internals) {
+  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
+    // No DevTools
+    return false;
   }
-  for (var contextKey in childContext) {
-    invariant(
-      contextKey in childContextTypes,
-      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-      getComponentName(fiber) || "Unknown",
-      contextKey
-    );
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled) {
+    // This isn't a real property on the hook, but it can be set to opt out
+    // of DevTools integration and associated warnings and logs.
+    // https://github.com/facebook/react/issues/3877
+    return true;
   }
-  {
-    var name = getComponentName(fiber) || "Unknown";
-    checkPropTypes(
-      childContextTypes,
-      childContext,
-      "child context",
-      name,
-      // In practice, there is one case in which we won't get a stack. It's when
-      // somebody calls unstable_renderSubtreeIntoContainer() and we process
-      // context from the parent component instance. The stack will be missing
-      // because it's outside of the reconciliation, and so the pointer has not
-      // been set. This is rare and doesn't matter. We'll also remove that API.
-      ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-    );
+  if (!hook.supportsFiber) {
+    {
+      warning(
+        false,
+        "The installed version of React DevTools is too old and will not work " +
+          "with the current version of React. Please update React DevTools. " +
+          "https://fb.me/react-devtools"
+      );
+    }
+    // DevTools exists, even though it doesn't support Fiber.
+    return true;
   }
-
-  return Object.assign({}, parentContext, childContext);
-}
-
-function pushContextProvider(workInProgress) {
-  if (!isContextProvider(workInProgress)) {
-    return false;
+  try {
+    var rendererID = hook.inject(internals);
+    // We have successfully injected, so now it is safe to set up hooks.
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {
+    // Catch all errors because it is unsafe to throw during initialization.
+    {
+      warning(false, "React DevTools encountered an error: %s.", err);
+    }
   }
-
-  var instance = workInProgress.stateNode;
-  // We push the context as early as possible to ensure stack integrity.
-  // If the instance does not exist yet, we will push null at first,
-  // and replace it on the stack later when invalidating the context.
-  var memoizedMergedChildContext =
-    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-    emptyObject;
-
-  // Remember the parent context so we can merge with it later.
-  // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
-  previousContext = contextStackCursor.current;
-  push(contextStackCursor, memoizedMergedChildContext, workInProgress);
-  push(
-    didPerformWorkStackCursor,
-    didPerformWorkStackCursor.current,
-    workInProgress
-  );
-
+  // DevTools exists
   return true;
 }
 
-function invalidateContextProvider(workInProgress, didChange) {
-  var instance = workInProgress.stateNode;
-  invariant(
-    instance,
-    "Expected to have an instance by this point. " +
-      "This error is likely caused by a bug in React. Please file an issue."
-  );
-
-  if (didChange) {
-    // Merge parent and own context.
-    // Skip this if we're not updating due to sCU.
-    // This avoids unnecessarily recomputing memoized values.
-    var mergedContext = processChildContext(workInProgress, previousContext);
-    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-
-    // Replace the old (or empty) context with the new one.
-    // It is important to unwind the context in the reverse order.
-    pop(didPerformWorkStackCursor, workInProgress);
-    pop(contextStackCursor, workInProgress);
-    // Now push the new context and mark that it has changed.
-    push(contextStackCursor, mergedContext, workInProgress);
-    push(didPerformWorkStackCursor, didChange, workInProgress);
-  } else {
-    pop(didPerformWorkStackCursor, workInProgress);
-    push(didPerformWorkStackCursor, didChange, workInProgress);
+function onCommitRoot(root) {
+  if (typeof onCommitFiberRoot === "function") {
+    onCommitFiberRoot(root);
   }
 }
 
-function resetContext() {
-  previousContext = emptyObject;
-  contextStackCursor.current = emptyObject;
-  didPerformWorkStackCursor.current = false;
-}
-
-function findCurrentUnmaskedContext(fiber) {
-  // Currently this is only used with renderSubtreeIntoContainer; not sure if it
-  // makes sense elsewhere
-  invariant(
-    isFiberMounted(fiber) && fiber.tag === ClassComponent,
-    "Expected subtree parent to be a mounted class component. " +
-      "This error is likely caused by a bug in React. Please file an issue."
-  );
-
-  var node = fiber;
-  while (node.tag !== HostRoot) {
-    if (isContextProvider(node)) {
-      return node.stateNode.__reactInternalMemoizedMergedChildContext;
-    }
-    var parent = node["return"];
-    invariant(
-      parent,
-      "Found unexpected detached subtree parent. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-    node = parent;
+function onCommitUnmount(fiber) {
+  if (typeof onCommitFiberUnmount === "function") {
+    onCommitFiberUnmount(fiber);
   }
-  return node.stateNode.context;
-}
-
-// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
-// Math.pow(2, 30) - 1
-// 0b111111111111111111111111111111
-var MAX_SIGNED_31_BIT_INT = 1073741823;
-
-// TODO: Use an opaque type once ESLint et al support the syntax
-
-var NoWork = 0;
-var Sync = 1;
-var Never = MAX_SIGNED_31_BIT_INT;
-
-var UNIT_SIZE = 10;
-var MAGIC_NUMBER_OFFSET = 2;
-
-// 1 unit of expiration time represents 10ms.
-function msToExpirationTime(ms) {
-  // Always add an offset so that we don't clash with the magic number for NoWork.
-  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
-}
-
-function expirationTimeToMs(expirationTime) {
-  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
-}
-
-function ceiling(num, precision) {
-  return (((num / precision) | 0) + 1) * precision;
 }
 
-function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
-  return ceiling(
-    currentTime + expirationInMs / UNIT_SIZE,
-    bucketSizeMs / UNIT_SIZE
+var describeComponentFrame = function(name, source, ownerName) {
+  return (
+    "\n    in " +
+    (name || "Unknown") +
+    (source
+      ? " (at " +
+        source.fileName.replace(/^.*[\\\/]/, "") +
+        ":" +
+        source.lineNumber +
+        ")"
+      : ownerName ? " (created by " + ownerName + ")" : "")
   );
-}
-
-var NoContext = 0;
-var AsyncMode = 1;
-var StrictMode = 2;
-
-var hasBadMapPolyfill = void 0;
+};
 
-{
-  hasBadMapPolyfill = false;
-  try {
-    var nonExtensibleObject = Object.preventExtensions({});
-    var testMap = new Map([[nonExtensibleObject, null]]);
-    var testSet = new Set([nonExtensibleObject]);
-    // This is necessary for Rollup to not consider these unused.
-    // https://github.com/rollup/rollup/issues/1771
-    // TODO: we can remove these if Rollup fixes the bug.
-    testMap.set(0, 0);
-    testSet.add(0);
-  } catch (e) {
-    // TODO: Consider warning about bad polyfills
-    hasBadMapPolyfill = true;
+function describeFiber(fiber) {
+  switch (fiber.tag) {
+    case IndeterminateComponent:
+    case FunctionalComponent:
+    case ClassComponent:
+    case HostComponent:
+      var owner = fiber._debugOwner;
+      var source = fiber._debugSource;
+      var name = getComponentName(fiber);
+      var ownerName = null;
+      if (owner) {
+        ownerName = getComponentName(owner);
+      }
+      return describeComponentFrame(name, source, ownerName);
+    default:
+      return "";
   }
 }
 
-// A Fiber is work on a Component that needs to be done or was done. There can
-// be more than one per component.
-
-var debugCounter = void 0;
-
-{
-  debugCounter = 1;
+// This function can only be called with a work-in-progress fiber and
+// only during begin or complete phase. Do not call it under any other
+// circumstances.
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  var node = workInProgress;
+  do {
+    info += describeFiber(node);
+    // Otherwise this return pointer might point to the wrong tree:
+    node = node["return"];
+  } while (node);
+  return info;
 }
 
-function FiberNode(tag, pendingProps, key, mode) {
-  // Instance
-  this.tag = tag;
-  this.key = key;
-  this.type = null;
-  this.stateNode = null;
-
-  // Fiber
-  this["return"] = null;
-  this.child = null;
-  this.sibling = null;
-  this.index = 0;
-
-  this.ref = null;
-
-  this.pendingProps = pendingProps;
-  this.memoizedProps = null;
-  this.updateQueue = null;
-  this.memoizedState = null;
-
-  this.mode = mode;
+/**
+ * Forked from fbjs/warning:
+ * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
+ *
+ * Only change is we use console.warn instead of console.error,
+ * and do nothing when 'console' is not supported.
+ * This really simplifies the code.
+ * ---
+ * Similar to invariant but only logs a warning if the condition is not met.
+ * This can be used to log issues in development environments in critical
+ * paths. Removing the logging code for production environments will keep the
+ * same logic and follow the same code paths.
+ */
 
-  // Effects
-  this.effectTag = NoEffect;
-  this.nextEffect = null;
+var lowPriorityWarning = function() {};
 
-  this.firstEffect = null;
-  this.lastEffect = null;
+{
+  var printWarning = function(format) {
+    for (
+      var _len = arguments.length,
+        args = Array(_len > 1 ? _len - 1 : 0),
+        _key = 1;
+      _key < _len;
+      _key++
+    ) {
+      args[_key - 1] = arguments[_key];
+    }
 
-  this.expirationTime = NoWork;
+    var argIndex = 0;
+    var message =
+      "Warning: " +
+      format.replace(/%s/g, function() {
+        return args[argIndex++];
+      });
+    if (typeof console !== "undefined") {
+      console.warn(message);
+    }
+    try {
+      // --- Welcome to debugging React ---
+      // This error was thrown as a convenience so that you can use this stack
+      // to find the callsite that caused this warning to fire.
+      throw new Error(message);
+    } catch (x) {}
+  };
 
-  this.alternate = null;
+  lowPriorityWarning = function(condition, format) {
+    if (format === undefined) {
+      throw new Error(
+        "`warning(condition, format, ...args)` requires a warning " +
+          "message argument"
+      );
+    }
+    if (!condition) {
+      for (
+        var _len2 = arguments.length,
+          args = Array(_len2 > 2 ? _len2 - 2 : 0),
+          _key2 = 2;
+        _key2 < _len2;
+        _key2++
+      ) {
+        args[_key2 - 2] = arguments[_key2];
+      }
 
-  {
-    this._debugID = debugCounter++;
-    this._debugSource = null;
-    this._debugOwner = null;
-    this._debugIsCurrentlyTiming = false;
-    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
-      Object.preventExtensions(this);
+      printWarning.apply(undefined, [format].concat(args));
     }
-  }
+  };
 }
 
-// This is a constructor function, rather than a POJO constructor, still
-// please ensure we do the following:
-// 1) Nobody should add any instance methods on this. Instance methods can be
-//    more difficult to predict when they get optimized and they are almost
-//    never inlined properly in static compilers.
-// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
-//    always know when it is a fiber.
-// 3) We might want to experiment with using numeric keys since they are easier
-//    to optimize in a non-JIT environment.
-// 4) We can easily go from a constructor to a createFiber object literal if that
-//    is faster.
-// 5) It should be easy to port this to a C struct and keep a C implementation
-//    compatible.
-var createFiber = function(tag, pendingProps, key, mode) {
-  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
-  return new FiberNode(tag, pendingProps, key, mode);
-};
+var lowPriorityWarning$1 = lowPriorityWarning;
 
-function shouldConstruct(Component) {
-  return !!(Component.prototype && Component.prototype.isReactComponent);
-}
+var ReactStrictModeWarnings = {
+  discardPendingWarnings: function() {},
+  flushPendingDeprecationWarnings: function() {},
+  flushPendingUnsafeLifecycleWarnings: function() {},
+  recordDeprecationWarnings: function(fiber, instance) {},
+  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
+};
 
-// This is used to create an alternate fiber to do work on.
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  if (workInProgress === null) {
-    // We use a double buffering pooling technique because we know that we'll
-    // only ever need at most two versions of a tree. We pool the "other" unused
-    // node that we're free to reuse. This is lazily created to avoid allocating
-    // extra objects for things that are never updated. It also allow us to
-    // reclaim the extra memory if needed.
-    workInProgress = createFiber(
-      current.tag,
-      pendingProps,
-      current.key,
-      current.mode
-    );
-    workInProgress.type = current.type;
-    workInProgress.stateNode = current.stateNode;
+{
+  var LIFECYCLE_SUGGESTIONS = {
+    UNSAFE_componentWillMount: "componentDidMount",
+    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
+    UNSAFE_componentWillUpdate: "componentDidUpdate"
+  };
 
-    {
-      // DEV-only fields
-      workInProgress._debugID = current._debugID;
-      workInProgress._debugSource = current._debugSource;
-      workInProgress._debugOwner = current._debugOwner;
-    }
+  var pendingComponentWillMountWarnings = [];
+  var pendingComponentWillReceivePropsWarnings = [];
+  var pendingComponentWillUpdateWarnings = [];
+  var pendingUnsafeLifecycleWarnings = new Map();
 
-    workInProgress.alternate = current;
-    current.alternate = workInProgress;
-  } else {
-    workInProgress.pendingProps = pendingProps;
+  // Tracks components we have already warned about.
+  var didWarnAboutDeprecatedLifecycles = new Set();
+  var didWarnAboutUnsafeLifecycles = new Set();
 
-    // We already have an alternate.
-    // Reset the effect tag.
-    workInProgress.effectTag = NoEffect;
+  ReactStrictModeWarnings.discardPendingWarnings = function() {
+    pendingComponentWillMountWarnings = [];
+    pendingComponentWillReceivePropsWarnings = [];
+    pendingComponentWillUpdateWarnings = [];
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
 
-    // The effect list is no longer valid.
-    workInProgress.nextEffect = null;
-    workInProgress.firstEffect = null;
-    workInProgress.lastEffect = null;
-  }
+  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
+    pendingUnsafeLifecycleWarnings.forEach(function(
+      lifecycleWarningsMap,
+      strictRoot
+    ) {
+      var lifecyclesWarningMesages = [];
 
-  workInProgress.expirationTime = expirationTime;
+      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
+        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
+        if (lifecycleWarnings.length > 0) {
+          var componentNames = new Set();
+          lifecycleWarnings.forEach(function(fiber) {
+            componentNames.add(getComponentName(fiber) || "Component");
+            didWarnAboutUnsafeLifecycles.add(fiber.type);
+          });
 
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
+          var formatted = lifecycle.replace("UNSAFE_", "");
+          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
+          var sortedComponentNames = Array.from(componentNames)
+            .sort()
+            .join(", ");
 
-  // These will be overridden during the parent's reconciliation
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
+          lifecyclesWarningMesages.push(
+            formatted +
+              ": Please update the following components to use " +
+              (suggestion + " instead: " + sortedComponentNames)
+          );
+        }
+      });
 
-  return workInProgress;
-}
+      if (lifecyclesWarningMesages.length > 0) {
+        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+          strictRoot
+        );
 
-function createHostRootFiber(isAsync) {
-  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
-  return createFiber(HostRoot, null, null, mode);
-}
+        warning(
+          false,
+          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
+            "\n\n%s" +
+            "\n\nLearn more about this warning here:" +
+            "\nhttps://fb.me/react-strict-mode-warnings",
+          strictRootComponentStack,
+          lifecyclesWarningMesages.join("\n\n")
+        );
+      }
+    });
 
-function createFiberFromElement(element, mode, expirationTime) {
-  var owner = null;
-  {
-    owner = element._owner;
-  }
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
 
-  var fiber = void 0;
-  var type = element.type;
-  var key = element.key;
-  var pendingProps = element.props;
+  var getStrictRoot = function(fiber) {
+    var maybeStrictRoot = null;
 
-  var fiberTag = void 0;
-  if (typeof type === "function") {
-    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
-  } else if (typeof type === "string") {
-    fiberTag = HostComponent;
-  } else {
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          pendingProps.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= AsyncMode | StrictMode;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= StrictMode;
-        break;
-      case REACT_CALL_TYPE:
-        fiberTag = CallComponent;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = ReturnComponent;
-        break;
-      default: {
-        if (typeof type === "object" && type !== null) {
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = ContextProvider;
-              break;
-            case REACT_CONTEXT_TYPE:
-              // This is a consumer
-              fiberTag = ContextConsumer;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = ForwardRef;
-              break;
-            default:
-              if (typeof type.tag === "number") {
-                // Currently assumed to be a continuation and therefore is a
-                // fiber already.
-                // TODO: The yield system is currently broken for updates in
-                // some cases. The reified yield stores a fiber, but we don't
-                // know which fiber that is; the current or a workInProgress?
-                // When the continuation gets rendered here we don't know if we
-                // can reuse that fiber or if we need to clone it. There is
-                // probably a clever way to restructure this.
-                fiber = type;
-                fiber.pendingProps = pendingProps;
-                fiber.expirationTime = expirationTime;
-                return fiber;
-              } else {
-                throwOnInvalidElementType(type, owner);
-              }
-              break;
-          }
-        } else {
-          throwOnInvalidElementType(type, owner);
-        }
+    while (fiber !== null) {
+      if (fiber.mode & StrictMode) {
+        maybeStrictRoot = fiber;
       }
+
+      fiber = fiber["return"];
     }
-  }
 
-  fiber = createFiber(fiberTag, pendingProps, key, mode);
-  fiber.type = type;
-  fiber.expirationTime = expirationTime;
+    return maybeStrictRoot;
+  };
+
+  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
+    if (pendingComponentWillMountWarnings.length > 0) {
+      var uniqueNames = new Set();
+      pendingComponentWillMountWarnings.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-  {
-    fiber._debugSource = element._source;
-    fiber._debugOwner = element._owner;
-  }
+      var sortedNames = Array.from(uniqueNames)
+        .sort()
+        .join(", ");
 
-  return fiber;
-}
+      lowPriorityWarning$1(
+        false,
+        "componentWillMount is deprecated and will be removed in the next major version. " +
+          "Use componentDidMount instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillMount." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        sortedNames
+      );
 
-function throwOnInvalidElementType(type, owner) {
-  var info = "";
-  {
-    if (
-      type === undefined ||
-      (typeof type === "object" &&
-        type !== null &&
-        Object.keys(type).length === 0)
-    ) {
-      info +=
-        " You likely forgot to export your component from the file " +
-        "it's defined in, or you might have mixed up default and " +
-        "named imports.";
+      pendingComponentWillMountWarnings = [];
     }
-    var ownerName = owner ? getComponentName(owner) : null;
-    if (ownerName) {
-      info += "\n\nCheck the render method of `" + ownerName + "`.";
+
+    if (pendingComponentWillReceivePropsWarnings.length > 0) {
+      var _uniqueNames = new Set();
+      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
+        _uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var _sortedNames = Array.from(_uniqueNames)
+        .sort()
+        .join(", ");
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
+          "Use static getDerivedStateFromProps instead." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames
+      );
+
+      pendingComponentWillReceivePropsWarnings = [];
     }
-  }
-  invariant(
-    false,
-    "Element type is invalid: expected a string (for built-in " +
-      "components) or a class/function (for composite components) " +
-      "but got: %s.%s",
-    type == null ? type : typeof type,
-    info
-  );
-}
 
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  var fiber = createFiber(Fragment, elements, key, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
+    if (pendingComponentWillUpdateWarnings.length > 0) {
+      var _uniqueNames2 = new Set();
+      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
+        _uniqueNames2.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-function createFiberFromText(content, mode, expirationTime) {
-  var fiber = createFiber(HostText, content, null, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
+      var _sortedNames2 = Array.from(_uniqueNames2)
+        .sort()
+        .join(", ");
 
-function createFiberFromHostInstanceForDeletion() {
-  var fiber = createFiber(HostComponent, null, null, NoContext);
-  fiber.type = "DELETED";
-  return fiber;
-}
+      lowPriorityWarning$1(
+        false,
+        "componentWillUpdate is deprecated and will be removed in the next major version. " +
+          "Use componentDidUpdate instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillUpdate." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames2
+      );
 
-function createFiberFromPortal(portal, mode, expirationTime) {
-  var pendingProps = portal.children !== null ? portal.children : [];
-  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null, // Used by persistent updates
-    implementation: portal.implementation
+      pendingComponentWillUpdateWarnings = [];
+    }
   };
-  return fiber;
-}
 
-// TODO: This should be lifted into the renderer.
+  ReactStrictModeWarnings.recordDeprecationWarnings = function(
+    fiber,
+    instance
+  ) {
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
+      return;
+    }
 
-function createFiberRoot(containerInfo, isAsync, hydrate) {
-  // Cyclic construction. This cheats the type system right now because
-  // stateNode is any.
-  var uninitializedFiber = createHostRootFiber(isAsync);
-  var root = {
-    current: uninitializedFiber,
-    containerInfo: containerInfo,
-    pendingChildren: null,
-    pendingCommitExpirationTime: NoWork,
-    finishedWork: null,
-    context: null,
-    pendingContext: null,
-    hydrate: hydrate,
-    remainingExpirationTime: NoWork,
-    firstBatch: null,
-    nextScheduledRoot: null
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillMountWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" &&
+      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillReceivePropsWarnings.push(fiber);
+    }
+    if (typeof instance.componentWillUpdate === "function") {
+      pendingComponentWillUpdateWarnings.push(fiber);
+    }
   };
-  uninitializedFiber.stateNode = root;
-  return root;
-}
 
-var onCommitFiberRoot = null;
-var onCommitFiberUnmount = null;
-var hasLoggedError = false;
+  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = getStrictRoot(fiber);
 
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {
-      if (true && !hasLoggedError) {
-        hasLoggedError = true;
-        warning(false, "React DevTools encountered an error: %s", err);
-      }
+    // Dedup strategy: Warn once per component.
+    // This is difficult to track any other way since component names
+    // are often vague and are likely to collide between 3rd party libraries.
+    // An expand property is probably okay to use here since it's DEV-only,
+    // and will only be set in the event of serious warnings.
+    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+      return;
     }
-  };
-}
 
-function injectInternals(internals) {
-  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
-    // No DevTools
-    return false;
-  }
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled) {
-    // This isn't a real property on the hook, but it can be set to opt out
-    // of DevTools integration and associated warnings and logs.
-    // https://github.com/facebook/react/issues/3877
-    return true;
-  }
-  if (!hook.supportsFiber) {
-    {
-      warning(
-        false,
-        "The installed version of React DevTools is too old and will not work " +
-          "with the current version of React. Please update React DevTools. " +
-          "https://fb.me/react-devtools"
-      );
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    // Note that it is sufficient to check for the presence of a
+    // single lifecycle, componentWillMount, with the polyfill flag.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning === true
+    ) {
+      return;
+    }
+
+    var warningsForRoot = void 0;
+    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
+      warningsForRoot = {
+        UNSAFE_componentWillMount: [],
+        UNSAFE_componentWillReceiveProps: [],
+        UNSAFE_componentWillUpdate: []
+      };
+
+      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
+    } else {
+      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
+    }
+
+    var unsafeLifecycles = [];
+    if (
+      typeof instance.componentWillMount === "function" ||
+      typeof instance.UNSAFE_componentWillMount === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillMount");
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" ||
+      typeof instance.UNSAFE_componentWillReceiveProps === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    }
+    if (
+      typeof instance.componentWillUpdate === "function" ||
+      typeof instance.UNSAFE_componentWillUpdate === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
     }
-    // DevTools exists, even though it doesn't support Fiber.
-    return true;
-  }
-  try {
-    var rendererID = hook.inject(internals);
-    // We have successfully injected, so now it is safe to set up hooks.
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {
-    // Catch all errors because it is unsafe to throw during initialization.
-    {
-      warning(false, "React DevTools encountered an error: %s.", err);
+
+    if (unsafeLifecycles.length > 0) {
+      unsafeLifecycles.forEach(function(lifecycle) {
+        warningsForRoot[lifecycle].push(fiber);
+      });
     }
-  }
-  // DevTools exists
-  return true;
+  };
 }
 
-function onCommitRoot(root) {
-  if (typeof onCommitFiberRoot === "function") {
-    onCommitFiberRoot(root);
+var debugRenderPhaseSideEffects = false;
+var debugRenderPhaseSideEffectsForStrictMode = false;
+
+var enableUserTimingAPI = true;
+var enableGetDerivedStateFromCatch = false;
+var warnAboutDeprecatedLifecycles = false;
+var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
+
+// React Fabric uses persistent reconciler.
+var enableMutatingReconciler = false;
+var enableNoopReconciler = false;
+var enablePersistentReconciler = true;
+
+// Only used in www builds.
+
+function getCurrentFiberOwnerName() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    var owner = fiber._debugOwner;
+    if (owner !== null && typeof owner !== "undefined") {
+      return getComponentName(owner);
+    }
   }
+  return null;
 }
 
-function onCommitUnmount(fiber) {
-  if (typeof onCommitFiberUnmount === "function") {
-    onCommitFiberUnmount(fiber);
+function getCurrentFiberStackAddendum() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    // Safe because if current fiber exists, we are reconciling,
+    // and it is guaranteed to be the work-in-progress version.
+    return getStackAddendumByWorkInProgressFiber(fiber);
   }
+  return null;
 }
 
-/**
- * Forked from fbjs/warning:
- * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
- *
- * Only change is we use console.warn instead of console.error,
- * and do nothing when 'console' is not supported.
- * This really simplifies the code.
- * ---
- * Similar to invariant but only logs a warning if the condition is not met.
- * This can be used to log issues in development environments in critical
- * paths. Removing the logging code for production environments will keep the
- * same logic and follow the same code paths.
- */
+function resetCurrentFiber() {
+  ReactDebugCurrentFrame.getCurrentStack = null;
+  ReactDebugCurrentFiber.current = null;
+  ReactDebugCurrentFiber.phase = null;
+}
 
-var lowPriorityWarning = function() {};
+function setCurrentFiber(fiber) {
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
+  ReactDebugCurrentFiber.current = fiber;
+  ReactDebugCurrentFiber.phase = null;
+}
 
-{
-  var printWarning = function(format) {
-    for (
-      var _len = arguments.length,
-        args = Array(_len > 1 ? _len - 1 : 0),
-        _key = 1;
-      _key < _len;
-      _key++
-    ) {
-      args[_key - 1] = arguments[_key];
-    }
+function setCurrentPhase(phase) {
+  ReactDebugCurrentFiber.phase = phase;
+}
 
-    var argIndex = 0;
-    var message =
-      "Warning: " +
-      format.replace(/%s/g, function() {
-        return args[argIndex++];
-      });
-    if (typeof console !== "undefined") {
-      console.warn(message);
-    }
-    try {
-      // --- Welcome to debugging React ---
-      // This error was thrown as a convenience so that you can use this stack
-      // to find the callsite that caused this warning to fire.
-      throw new Error(message);
-    } catch (x) {}
-  };
+var ReactDebugCurrentFiber = {
+  current: null,
+  phase: null,
+  resetCurrentFiber: resetCurrentFiber,
+  setCurrentFiber: setCurrentFiber,
+  setCurrentPhase: setCurrentPhase,
+  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
+};
 
-  lowPriorityWarning = function(condition, format) {
-    if (format === undefined) {
-      throw new Error(
-        "`warning(condition, format, ...args)` requires a warning " +
-          "message argument"
-      );
-    }
-    if (!condition) {
-      for (
-        var _len2 = arguments.length,
-          args = Array(_len2 > 2 ? _len2 - 2 : 0),
-          _key2 = 2;
-        _key2 < _len2;
-        _key2++
-      ) {
-        args[_key2 - 2] = arguments[_key2];
-      }
+// Prefix measurements so that it's possible to filter them.
+// Longer prefixes are hard to read in DevTools.
+var reactEmoji = "\u269B";
+var warningEmoji = "\u26D4";
+var supportsUserTiming =
+  typeof performance !== "undefined" &&
+  typeof performance.mark === "function" &&
+  typeof performance.clearMarks === "function" &&
+  typeof performance.measure === "function" &&
+  typeof performance.clearMeasures === "function";
 
-      printWarning.apply(undefined, [format].concat(args));
-    }
-  };
-}
+// Keep track of current fiber so that we know the path to unwind on pause.
+// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
+var currentFiber = null;
+// If we're in the middle of user code, which fiber and method is it?
+// Reusing `currentFiber` would be confusing for this because user code fiber
+// can change during commit phase too, but we don't need to unwind it (since
+// lifecycles in the commit phase don't resemble a tree).
+var currentPhase = null;
+var currentPhaseFiber = null;
+// Did lifecycle hook schedule an update? This is often a performance problem,
+// so we will keep track of it, and include it in the report.
+// Track commits caused by cascading updates.
+var isCommitting = false;
+var hasScheduledUpdateInCurrentCommit = false;
+var hasScheduledUpdateInCurrentPhase = false;
+var commitCountInCurrentWorkLoop = 0;
+var effectCountInCurrentCommit = 0;
+var isWaitingForCallback = false;
+// During commits, we only show a measurement once per method name
+// to avoid stretch the commit phase with measurement overhead.
+var labelsInCurrentCommit = new Set();
 
-var lowPriorityWarning$1 = lowPriorityWarning;
+var formatMarkName = function(markName) {
+  return reactEmoji + " " + markName;
+};
 
-var ReactStrictModeWarnings = {
-  discardPendingWarnings: function() {},
-  flushPendingDeprecationWarnings: function() {},
-  flushPendingUnsafeLifecycleWarnings: function() {},
-  recordDeprecationWarnings: function(fiber, instance) {},
-  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
+var formatLabel = function(label, warning$$1) {
+  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
+  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
+  return "" + prefix + label + suffix;
 };
 
-{
-  var LIFECYCLE_SUGGESTIONS = {
-    UNSAFE_componentWillMount: "componentDidMount",
-    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
-    UNSAFE_componentWillUpdate: "componentDidUpdate"
-  };
+var beginMark = function(markName) {
+  performance.mark(formatMarkName(markName));
+};
 
-  var pendingComponentWillMountWarnings = [];
-  var pendingComponentWillReceivePropsWarnings = [];
-  var pendingComponentWillUpdateWarnings = [];
-  var pendingUnsafeLifecycleWarnings = new Map();
+var clearMark = function(markName) {
+  performance.clearMarks(formatMarkName(markName));
+};
 
-  // Tracks components we have already warned about.
-  var didWarnAboutDeprecatedLifecycles = new Set();
-  var didWarnAboutUnsafeLifecycles = new Set();
+var endMark = function(label, markName, warning$$1) {
+  var formattedMarkName = formatMarkName(markName);
+  var formattedLabel = formatLabel(label, warning$$1);
+  try {
+    performance.measure(formattedLabel, formattedMarkName);
+  } catch (err) {}
+  // If previous mark was missing for some reason, this will throw.
+  // This could only happen if React crashed in an unexpected place earlier.
+  // Don't pile on with more errors.
 
-  ReactStrictModeWarnings.discardPendingWarnings = function() {
-    pendingComponentWillMountWarnings = [];
-    pendingComponentWillReceivePropsWarnings = [];
-    pendingComponentWillUpdateWarnings = [];
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+  // Clear marks immediately to avoid growing buffer.
+  performance.clearMarks(formattedMarkName);
+  performance.clearMeasures(formattedLabel);
+};
 
-  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
-    pendingUnsafeLifecycleWarnings.forEach(function(
-      lifecycleWarningsMap,
-      strictRoot
-    ) {
-      var lifecyclesWarningMesages = [];
+var getFiberMarkName = function(label, debugID) {
+  return label + " (#" + debugID + ")";
+};
 
-      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
-        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
-        if (lifecycleWarnings.length > 0) {
-          var componentNames = new Set();
-          lifecycleWarnings.forEach(function(fiber) {
-            componentNames.add(getComponentName(fiber) || "Component");
-            didWarnAboutUnsafeLifecycles.add(fiber.type);
-          });
+var getFiberLabel = function(componentName, isMounted, phase) {
+  if (phase === null) {
+    // These are composite component total time measurements.
+    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
+  } else {
+    // Composite component methods.
+    return componentName + "." + phase;
+  }
+};
 
-          var formatted = lifecycle.replace("UNSAFE_", "");
-          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = Array.from(componentNames)
-            .sort()
-            .join(", ");
+var beginFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
 
-          lifecyclesWarningMesages.push(
-            formatted +
-              ": Please update the following components to use " +
-              (suggestion + " instead: " + sortedComponentNames)
-          );
-        }
-      });
+  if (isCommitting && labelsInCurrentCommit.has(label)) {
+    // During the commit phase, we don't show duplicate labels because
+    // there is a fixed overhead for every measurement, and we don't
+    // want to stretch the commit phase beyond necessary.
+    return false;
+  }
+  labelsInCurrentCommit.add(label);
 
-      if (lifecyclesWarningMesages.length > 0) {
-        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
-          strictRoot
-        );
+  var markName = getFiberMarkName(label, debugID);
+  beginMark(markName);
+  return true;
+};
 
-        warning(
-          false,
-          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
-            "\n\n%s" +
-            "\n\nLearn more about this warning here:" +
-            "\nhttps://fb.me/react-strict-mode-warnings",
-          strictRootComponentStack,
-          lifecyclesWarningMesages.join("\n\n")
-        );
-      }
-    });
+var clearFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  clearMark(markName);
+};
 
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+var endFiberMark = function(fiber, phase, warning$$1) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  endMark(label, markName, warning$$1);
+};
 
-  var getStrictRoot = function(fiber) {
-    var maybeStrictRoot = null;
+var shouldIgnoreFiber = function(fiber) {
+  // Host components should be skipped in the timeline.
+  // We could check typeof fiber.type, but does this work with RN?
+  switch (fiber.tag) {
+    case HostRoot:
+    case HostComponent:
+    case HostText:
+    case HostPortal:
+    case CallComponent:
+    case ReturnComponent:
+    case Fragment:
+    case ContextProvider:
+    case ContextConsumer:
+      return true;
+    default:
+      return false;
+  }
+};
 
-    while (fiber !== null) {
-      if (fiber.mode & StrictMode) {
-        maybeStrictRoot = fiber;
-      }
+var clearPendingPhaseMeasurement = function() {
+  if (currentPhase !== null && currentPhaseFiber !== null) {
+    clearFiberMark(currentPhaseFiber, currentPhase);
+  }
+  currentPhaseFiber = null;
+  currentPhase = null;
+  hasScheduledUpdateInCurrentPhase = false;
+};
 
-      fiber = fiber["return"];
+var pauseTimers = function() {
+  // Stops all currently active measurements so that they can be resumed
+  // if we continue in a later deferred loop from the same unit of work.
+  var fiber = currentFiber;
+  while (fiber) {
+    if (fiber._debugIsCurrentlyTiming) {
+      endFiberMark(fiber, null, null);
     }
+    fiber = fiber["return"];
+  }
+};
 
-    return maybeStrictRoot;
-  };
-
-  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
-    if (pendingComponentWillMountWarnings.length > 0) {
-      var uniqueNames = new Set();
-      pendingComponentWillMountWarnings.forEach(function(fiber) {
-        uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+var resumeTimersRecursively = function(fiber) {
+  if (fiber["return"] !== null) {
+    resumeTimersRecursively(fiber["return"]);
+  }
+  if (fiber._debugIsCurrentlyTiming) {
+    beginFiberMark(fiber, null);
+  }
+};
 
-      var sortedNames = Array.from(uniqueNames)
-        .sort()
-        .join(", ");
+var resumeTimers = function() {
+  // Resumes all measurements that were active during the last deferred loop.
+  if (currentFiber !== null) {
+    resumeTimersRecursively(currentFiber);
+  }
+};
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillMount is deprecated and will be removed in the next major version. " +
-          "Use componentDidMount instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillMount." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        sortedNames
-      );
+function recordEffect() {
+  if (enableUserTimingAPI) {
+    effectCountInCurrentCommit++;
+  }
+}
 
-      pendingComponentWillMountWarnings = [];
+function recordScheduleUpdate() {
+  if (enableUserTimingAPI) {
+    if (isCommitting) {
+      hasScheduledUpdateInCurrentCommit = true;
     }
+    if (
+      currentPhase !== null &&
+      currentPhase !== "componentWillMount" &&
+      currentPhase !== "componentWillReceiveProps"
+    ) {
+      hasScheduledUpdateInCurrentPhase = true;
+    }
+  }
+}
 
-    if (pendingComponentWillReceivePropsWarnings.length > 0) {
-      var _uniqueNames = new Set();
-      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
-        _uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames = Array.from(_uniqueNames)
-        .sort()
-        .join(", ");
+function startRequestCallbackTimer() {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming && !isWaitingForCallback) {
+      isWaitingForCallback = true;
+      beginMark("(Waiting for async callback...)");
+    }
+  }
+}
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
-          "Use static getDerivedStateFromProps instead." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames
+function stopRequestCallbackTimer(didExpire) {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming) {
+      isWaitingForCallback = false;
+      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
+      endMark(
+        "(Waiting for async callback...)",
+        "(Waiting for async callback...)",
+        warning$$1
       );
-
-      pendingComponentWillReceivePropsWarnings = [];
     }
+  }
+}
 
-    if (pendingComponentWillUpdateWarnings.length > 0) {
-      var _uniqueNames2 = new Set();
-      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
-        _uniqueNames2.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames2 = Array.from(_uniqueNames2)
-        .sort()
-        .join(", ");
+function startWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, this is the fiber to unwind from.
+    currentFiber = fiber;
+    if (!beginFiberMark(fiber, null)) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = true;
+  }
+}
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillUpdate is deprecated and will be removed in the next major version. " +
-          "Use componentDidUpdate instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillUpdate." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames2
-      );
+function cancelWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // Remember we shouldn't complete measurement for this fiber.
+    // Otherwise flamechart will be deep even for small updates.
+    fiber._debugIsCurrentlyTiming = false;
+    clearFiberMark(fiber, null);
+  }
+}
 
-      pendingComponentWillUpdateWarnings = [];
+function stopWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber["return"];
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
     }
-  };
+    fiber._debugIsCurrentlyTiming = false;
+    endFiberMark(fiber, null, null);
+  }
+}
 
-  ReactStrictModeWarnings.recordDeprecationWarnings = function(
-    fiber,
-    instance
-  ) {
-    // Dedup strategy: Warn once per component.
-    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
+function stopFailedWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber["return"];
+    if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
+    fiber._debugIsCurrentlyTiming = false;
+    var warning$$1 = "An error was thrown inside this error boundary";
+    endFiberMark(fiber, null, warning$$1);
+  }
+}
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillMountWarnings.push(fiber);
+function startPhaseTimer(fiber, phase) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    if (
-      typeof instance.componentWillReceiveProps === "function" &&
-      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillReceivePropsWarnings.push(fiber);
+    clearPendingPhaseMeasurement();
+    if (!beginFiberMark(fiber, phase)) {
+      return;
     }
-    if (typeof instance.componentWillUpdate === "function") {
-      pendingComponentWillUpdateWarnings.push(fiber);
+    currentPhaseFiber = fiber;
+    currentPhase = phase;
+  }
+}
+
+function stopPhaseTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-  };
+    if (currentPhase !== null && currentPhaseFiber !== null) {
+      var warning$$1 = hasScheduledUpdateInCurrentPhase
+        ? "Scheduled a cascading update"
+        : null;
+      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
+    }
+    currentPhase = null;
+    currentPhaseFiber = null;
+  }
+}
 
-  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
-    fiber,
-    instance
-  ) {
-    var strictRoot = getStrictRoot(fiber);
+function startWorkLoopTimer(nextUnitOfWork) {
+  if (enableUserTimingAPI) {
+    currentFiber = nextUnitOfWork;
+    if (!supportsUserTiming) {
+      return;
+    }
+    commitCountInCurrentWorkLoop = 0;
+    // This is top level call.
+    // Any other measurements are performed within.
+    beginMark("(React Tree Reconciliation)");
+    // Resume any measurements that were in progress during the last loop.
+    resumeTimers();
+  }
+}
 
-    // Dedup strategy: Warn once per component.
-    // This is difficult to track any other way since component names
-    // are often vague and are likely to collide between 3rd party libraries.
-    // An expand property is probably okay to use here since it's DEV-only,
-    // and will only be set in the event of serious warnings.
-    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+function stopWorkLoopTimer(interruptedBy) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
       return;
     }
+    var warning$$1 = null;
+    if (interruptedBy !== null) {
+      if (interruptedBy.tag === HostRoot) {
+        warning$$1 = "A top-level update interrupted the previous render";
+      } else {
+        var componentName = getComponentName(interruptedBy) || "Unknown";
+        warning$$1 =
+          "An update to " + componentName + " interrupted the previous render";
+      }
+    } else if (commitCountInCurrentWorkLoop > 1) {
+      warning$$1 = "There were cascading updates";
+    }
+    commitCountInCurrentWorkLoop = 0;
+    // Pause any measurements until the next loop.
+    pauseTimers();
+    endMark(
+      "(React Tree Reconciliation)",
+      "(React Tree Reconciliation)",
+      warning$$1
+    );
+  }
+}
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    // Note that it is sufficient to check for the presence of a
-    // single lifecycle, componentWillMount, with the polyfill flag.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning === true
-    ) {
+function startCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
       return;
     }
+    isCommitting = true;
+    hasScheduledUpdateInCurrentCommit = false;
+    labelsInCurrentCommit.clear();
+    beginMark("(Committing Changes)");
+  }
+}
 
-    var warningsForRoot = void 0;
-    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
-      warningsForRoot = {
-        UNSAFE_componentWillMount: [],
-        UNSAFE_componentWillReceiveProps: [],
-        UNSAFE_componentWillUpdate: []
-      };
+function stopCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
 
-      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
-    } else {
-      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
+    var warning$$1 = null;
+    if (hasScheduledUpdateInCurrentCommit) {
+      warning$$1 = "Lifecycle hook scheduled a cascading update";
+    } else if (commitCountInCurrentWorkLoop > 0) {
+      warning$$1 = "Caused by a cascading update in earlier commit";
     }
+    hasScheduledUpdateInCurrentCommit = false;
+    commitCountInCurrentWorkLoop++;
+    isCommitting = false;
+    labelsInCurrentCommit.clear();
 
-    var unsafeLifecycles = [];
-    if (
-      typeof instance.componentWillMount === "function" ||
-      typeof instance.UNSAFE_componentWillMount === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillMount");
+    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
+  }
+}
+
+function startCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    if (
-      typeof instance.componentWillReceiveProps === "function" ||
-      typeof instance.UNSAFE_componentWillReceiveProps === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Host Effects)");
+  }
+}
+
+function stopCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    if (
-      typeof instance.componentWillUpdate === "function" ||
-      typeof instance.UNSAFE_componentWillUpdate === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Host Effects: " + count + " Total)",
+      "(Committing Host Effects)",
+      null
+    );
+  }
+}
+
+function startCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Calling Lifecycle Methods)");
+  }
+}
 
-    if (unsafeLifecycles.length > 0) {
-      unsafeLifecycles.forEach(function(lifecycle) {
-        warningsForRoot[lifecycle].push(fiber);
-      });
+function stopCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-  };
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Calling Lifecycle Methods: " + count + " Total)",
+      "(Calling Lifecycle Methods)",
+      null
+    );
+  }
 }
 
 var didWarnUpdateInsideUpdate = void 0;
@@ -6172,12 +5847,20 @@ function callGetDerivedStateFromCatch(ctor, capturedValues) {
 }
 
 var ReactFiberClassComponent = function(
+  legacyContext,
   scheduleWork,
   computeExpirationForFiber,
   memoizeProps,
   memoizeState
 ) {
+  var cacheContext = legacyContext.cacheContext,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    isContextConsumer = legacyContext.isContextConsumer,
+    hasContextChanged = legacyContext.hasContextChanged;
+
   // Class component state updater
+
   var updater = {
     isMounted: isMounted,
     enqueueSetState: function(instance, partialState, callback) {
@@ -8310,84 +7993,19 @@ function cloneChildFibers(current, workInProgress) {
     currentChild.pendingProps,
     currentChild.expirationTime
   );
-  workInProgress.child = newChild;
-
-  newChild["return"] = workInProgress;
-  while (currentChild.sibling !== null) {
-    currentChild = currentChild.sibling;
-    newChild = newChild.sibling = createWorkInProgress(
-      currentChild,
-      currentChild.pendingProps,
-      currentChild.expirationTime
-    );
-    newChild["return"] = workInProgress;
-  }
-  newChild.sibling = null;
-}
-
-var changedBitsStack = [];
-var currentValueStack = [];
-var stack = [];
-var index$1 = -1;
-
-var rendererSigil = void 0;
-{
-  // Use this to detect multiple renderers using the same context
-  rendererSigil = {};
-}
-
-function pushProvider(providerFiber) {
-  var context = providerFiber.type.context;
-  index$1 += 1;
-  changedBitsStack[index$1] = context._changedBits;
-  currentValueStack[index$1] = context._currentValue;
-  stack[index$1] = providerFiber;
-  context._currentValue = providerFiber.pendingProps.value;
-  context._changedBits = providerFiber.stateNode;
-
-  {
-    warning(
-      context._currentRenderer === null ||
-        context._currentRenderer === rendererSigil,
-      "Detected multiple renderers concurrently rendering the " +
-        "same context provider. This is currently unsupported."
-    );
-    context._currentRenderer = rendererSigil;
-  }
-}
-
-function popProvider(providerFiber) {
-  {
-    warning(
-      index$1 > -1 && providerFiber === stack[index$1],
-      "Unexpected pop."
-    );
-  }
-  var changedBits = changedBitsStack[index$1];
-  var currentValue = currentValueStack[index$1];
-  changedBitsStack[index$1] = null;
-  currentValueStack[index$1] = null;
-  stack[index$1] = null;
-  index$1 -= 1;
-  var context = providerFiber.type.context;
-  context._currentValue = currentValue;
-  context._changedBits = changedBits;
-}
+  workInProgress.child = newChild;
 
-function resetProviderStack() {
-  for (var i = index$1; i > -1; i--) {
-    var providerFiber = stack[i];
-    var context = providerFiber.type.context;
-    context._currentValue = context._defaultValue;
-    context._changedBits = 0;
-    changedBitsStack[i] = null;
-    currentValueStack[i] = null;
-    stack[i] = null;
-    {
-      context._currentRenderer = null;
-    }
+  newChild["return"] = workInProgress;
+  while (currentChild.sibling !== null) {
+    currentChild = currentChild.sibling;
+    newChild = newChild.sibling = createWorkInProgress(
+      currentChild,
+      currentChild.pendingProps,
+      currentChild.expirationTime
+    );
+    newChild["return"] = workInProgress;
   }
-  index$1 = -1;
+  newChild.sibling = null;
 }
 
 var didWarnAboutBadClass = void 0;
@@ -8403,6 +8021,8 @@ var didWarnAboutStatelessRefs = void 0;
 var ReactFiberBeginWork = function(
   config,
   hostContext,
+  legacyContext,
+  newContext,
   hydrationContext,
   scheduleWork,
   computeExpirationForFiber
@@ -8411,12 +8031,20 @@ var ReactFiberBeginWork = function(
     shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
   var pushHostContext = hostContext.pushHostContext,
     pushHostContainer = hostContext.pushHostContainer;
+  var pushProvider = newContext.pushProvider;
+  var getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    hasLegacyContextChanged = legacyContext.hasContextChanged,
+    pushLegacyContextProvider = legacyContext.pushContextProvider,
+    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
+    invalidateContextProvider = legacyContext.invalidateContextProvider;
   var enterHydrationState = hydrationContext.enterHydrationState,
     resetHydrationState = hydrationContext.resetHydrationState,
     tryToClaimNextHydratableInstance =
       hydrationContext.tryToClaimNextHydratableInstance;
 
   var _ReactFiberClassCompo = ReactFiberClassComponent(
+      legacyContext,
       scheduleWork,
       computeExpirationForFiber,
       memoizeProps,
@@ -8484,7 +8112,7 @@ var ReactFiberBeginWork = function(
 
   function updateFragment(current, workInProgress) {
     var nextChildren = workInProgress.pendingProps;
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (workInProgress.memoizedProps === nextChildren) {
@@ -8497,7 +8125,7 @@ var ReactFiberBeginWork = function(
 
   function updateMode(current, workInProgress) {
     var nextChildren = workInProgress.pendingProps.children;
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (
@@ -8526,7 +8154,7 @@ var ReactFiberBeginWork = function(
     var fn = workInProgress.type;
     var nextProps = workInProgress.pendingProps;
 
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else {
@@ -8559,7 +8187,7 @@ var ReactFiberBeginWork = function(
     // Push context providers early to prevent context stack mismatches.
     // During mounting we don't know the child context yet as the instance doesn't exist.
     // We will invalidate the child context in finishClassComponent() right after rendering.
-    var hasContext = pushContextProvider(workInProgress);
+    var hasContext = pushLegacyContextProvider(workInProgress);
     var shouldUpdate = void 0;
     if (current === null) {
       if (workInProgress.stateNode === null) {
@@ -8784,7 +8412,7 @@ var ReactFiberBeginWork = function(
     var nextProps = workInProgress.pendingProps;
     var prevProps = current !== null ? current.memoizedProps : null;
 
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (memoizedProps === nextProps) {
@@ -8919,7 +8547,7 @@ var ReactFiberBeginWork = function(
       // Push context providers early to prevent context stack mismatches.
       // During mounting we don't know the child context yet as the instance doesn't exist.
       // We will invalidate the child context in finishClassComponent() right after rendering.
-      var hasContext = pushContextProvider(workInProgress);
+      var hasContext = pushLegacyContextProvider(workInProgress);
       adoptClassInstance(workInProgress, value);
       mountClassInstance(workInProgress, renderExpirationTime);
       return finishClassComponent(
@@ -8992,7 +8620,7 @@ var ReactFiberBeginWork = function(
 
   function updateCallComponent(current, workInProgress, renderExpirationTime) {
     var nextProps = workInProgress.pendingProps;
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (workInProgress.memoizedProps === nextProps) {
@@ -9035,7 +8663,7 @@ var ReactFiberBeginWork = function(
   ) {
     pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
     var nextChildren = workInProgress.pendingProps;
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (workInProgress.memoizedProps === nextChildren) {
@@ -9069,6 +8697,10 @@ var ReactFiberBeginWork = function(
     renderExpirationTime
   ) {
     var fiber = workInProgress.child;
+    if (fiber !== null) {
+      // Set the return pointer of the child to the work-in-progress fiber.
+      fiber["return"] = workInProgress;
+    }
     while (fiber !== null) {
       var nextFiber = void 0;
       // Visit this fiber.
@@ -9161,7 +8793,7 @@ var ReactFiberBeginWork = function(
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
 
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (oldProps === newProps) {
@@ -9257,7 +8889,7 @@ var ReactFiberBeginWork = function(
     var newValue = context._currentValue;
     var changedBits = context._changedBits;
 
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (changedBits === 0 && oldProps === newProps) {
@@ -9354,7 +8986,7 @@ var ReactFiberBeginWork = function(
         pushHostRootContext(workInProgress);
         break;
       case ClassComponent:
-        pushContextProvider(workInProgress);
+        pushLegacyContextProvider(workInProgress);
         break;
       case HostPortal:
         pushHostContainer(
@@ -9467,7 +9099,13 @@ var ReactFiberBeginWork = function(
   };
 };
 
-var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
+var ReactFiberCompleteWork = function(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext
+) {
   var createInstance = config.createInstance,
     createTextInstance = config.createTextInstance,
     appendInitialChild = config.appendInitialChild,
@@ -9479,6 +9117,9 @@ var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
     popHostContext = hostContext.popHostContext,
     getHostContext = hostContext.getHostContext,
     popHostContainer = hostContext.popHostContainer;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
   var prepareToHydrateHostInstance =
       hydrationContext.prepareToHydrateHostInstance,
     prepareToHydrateHostTextInstance =
@@ -9794,7 +9435,7 @@ var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
         return null;
       case ClassComponent: {
         // We are leaving this subtree, so pop context if any.
-        popContextProvider(workInProgress);
+        popLegacyContextProvider(workInProgress);
 
         // If this component caught an error, schedule an error log effect.
         var instance = workInProgress.stateNode;
@@ -9813,7 +9454,7 @@ var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
       }
       case HostRoot: {
         popHostContainer(workInProgress);
-        popTopLevelContextObject(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
         var fiberRoot = workInProgress.stateNode;
         if (fiberRoot.pendingContext) {
           fiberRoot.context = fiberRoot.pendingContext;
@@ -10040,11 +9681,16 @@ function createCapturedValue(value, source) {
 
 var ReactFiberUnwindWork = function(
   hostContext,
+  legacyContext,
+  newContext,
   scheduleWork,
   isAlreadyFailedLegacyErrorBoundary
 ) {
   var popHostContainer = hostContext.popHostContainer,
     popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
 
   function throwException(returnFiber, sourceFiber, rawValue) {
     // The source fiber did not complete.
@@ -10100,7 +9746,7 @@ var ReactFiberUnwindWork = function(
   function unwindWork(workInProgress) {
     switch (workInProgress.tag) {
       case ClassComponent: {
-        popContextProvider(workInProgress);
+        popLegacyContextProvider(workInProgress);
         var effectTag = workInProgress.effectTag;
         if (effectTag & ShouldCapture) {
           workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
@@ -10110,7 +9756,7 @@ var ReactFiberUnwindWork = function(
       }
       case HostRoot: {
         popHostContainer(workInProgress);
-        popTopLevelContextObject(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
         var _effectTag = workInProgress.effectTag;
         if (_effectTag & ShouldCapture) {
           workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
@@ -10132,9 +9778,37 @@ var ReactFiberUnwindWork = function(
         return null;
     }
   }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      default:
+        break;
+    }
+  }
+
   return {
     throwException: throwException,
-    unwindWork: unwindWork
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork
   };
 };
 
@@ -10466,7 +10140,7 @@ var ReactFiberCommitWork = function(
             warning(
               false,
               "Unexpected ref object provided for %s. " +
-                "Use either a ref-setter function or Reacte.createRef().%s",
+                "Use either a ref-setter function or React.createRef().%s",
               getComponentName(finishedWork),
               getStackAddendumByWorkInProgressFiber(finishedWork)
             );
@@ -10972,9 +10646,12 @@ var ReactFiberCommitWork = function(
 
 var NO_CONTEXT = {};
 
-var ReactFiberHostContext = function(config) {
+var ReactFiberHostContext = function(config, stack) {
   var getChildHostContext = config.getChildHostContext,
     getRootHostContext = config.getRootHostContext;
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
 
   var contextStackCursor = createCursor(NO_CONTEXT);
   var contextFiberStackCursor = createCursor(NO_CONTEXT);
@@ -11045,19 +10722,13 @@ var ReactFiberHostContext = function(config) {
     pop(contextFiberStackCursor, fiber);
   }
 
-  function resetHostContainer() {
-    contextStackCursor.current = NO_CONTEXT;
-    rootInstanceStackCursor.current = NO_CONTEXT;
-  }
-
   return {
     getHostContext: getHostContext,
     getRootHostContainer: getRootHostContainer,
     popHostContainer: popHostContainer,
     popHostContext: popHostContext,
     pushHostContainer: pushHostContainer,
-    pushHostContext: pushHostContext,
-    resetHostContainer: resetHostContainer
+    pushHostContext: pushHostContext
   };
 };
 
@@ -11427,6 +11098,425 @@ var ReactFiberInstrumentation = {
 
 var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
 
+var warnedAboutMissingGetChildContext = void 0;
+
+{
+  warnedAboutMissingGetChildContext = {};
+}
+
+var ReactFiberLegacyContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  // A cursor to the current merged context object on the stack.
+
+  var contextStackCursor = createCursor(emptyObject);
+  // A cursor to a boolean indicating whether the context has changed.
+  var didPerformWorkStackCursor = createCursor(false);
+  // Keep track of the previous context object that was on the stack.
+  // We use this to get access to the parent context after we have already
+  // pushed the next context provider, and now need to merge their contexts.
+  var previousContext = emptyObject;
+
+  function getUnmaskedContext(workInProgress) {
+    var hasOwnContext = isContextProvider(workInProgress);
+    if (hasOwnContext) {
+      // If the fiber is a context provider itself, when we read its context
+      // we have already pushed its own child context on the stack. A context
+      // provider should not "see" its own child context. Therefore we read the
+      // previous (parent) context instead for a context provider.
+      return previousContext;
+    }
+    return contextStackCursor.current;
+  }
+
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    var instance = workInProgress.stateNode;
+    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
+
+  function getMaskedContext(workInProgress, unmaskedContext) {
+    var type = workInProgress.type;
+    var contextTypes = type.contextTypes;
+    if (!contextTypes) {
+      return emptyObject;
+    }
+
+    // Avoid recreating masked context unless unmasked context has changed.
+    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
+    // This may trigger infinite loops if componentWillReceiveProps calls setState.
+    var instance = workInProgress.stateNode;
+    if (
+      instance &&
+      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+    ) {
+      return instance.__reactInternalMemoizedMaskedChildContext;
+    }
+
+    var context = {};
+    for (var key in contextTypes) {
+      context[key] = unmaskedContext[key];
+    }
+
+    {
+      var name = getComponentName(workInProgress) || "Unknown";
+      checkPropTypes(
+        contextTypes,
+        context,
+        "context",
+        name,
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    // Context is created before the class component is instantiated so check for instance.
+    if (instance) {
+      cacheContext(workInProgress, unmaskedContext, context);
+    }
+
+    return context;
+  }
+
+  function hasContextChanged() {
+    return didPerformWorkStackCursor.current;
+  }
+
+  function isContextConsumer(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+  }
+
+  function isContextProvider(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+  }
+
+  function popContextProvider(fiber) {
+    if (!isContextProvider(fiber)) {
+      return;
+    }
+
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
+
+  function popTopLevelContextObject(fiber) {
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
+
+  function pushTopLevelContextObject(fiber, context, didChange) {
+    invariant(
+      contextStackCursor.cursor == null,
+      "Unexpected context found on stack. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    push(contextStackCursor, context, fiber);
+    push(didPerformWorkStackCursor, didChange, fiber);
+  }
+
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode;
+    var childContextTypes = fiber.type.childContextTypes;
+
+    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
+    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
+    if (typeof instance.getChildContext !== "function") {
+      {
+        var componentName = getComponentName(fiber) || "Unknown";
+
+        if (!warnedAboutMissingGetChildContext[componentName]) {
+          warnedAboutMissingGetChildContext[componentName] = true;
+          warning(
+            false,
+            "%s.childContextTypes is specified but there is no getChildContext() method " +
+              "on the instance. You can either define getChildContext() on %s or remove " +
+              "childContextTypes from it.",
+            componentName,
+            componentName
+          );
+        }
+      }
+      return parentContext;
+    }
+
+    var childContext = void 0;
+    {
+      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
+    }
+    startPhaseTimer(fiber, "getChildContext");
+    childContext = instance.getChildContext();
+    stopPhaseTimer();
+    {
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+    for (var contextKey in childContext) {
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    }
+    {
+      var name = getComponentName(fiber) || "Unknown";
+      checkPropTypes(
+        childContextTypes,
+        childContext,
+        "child context",
+        name,
+        // In practice, there is one case in which we won't get a stack. It's when
+        // somebody calls unstable_renderSubtreeIntoContainer() and we process
+        // context from the parent component instance. The stack will be missing
+        // because it's outside of the reconciliation, and so the pointer has not
+        // been set. This is rare and doesn't matter. We'll also remove that API.
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    return Object.assign({}, parentContext, childContext);
+  }
+
+  function pushContextProvider(workInProgress) {
+    if (!isContextProvider(workInProgress)) {
+      return false;
+    }
+
+    var instance = workInProgress.stateNode;
+    // We push the context as early as possible to ensure stack integrity.
+    // If the instance does not exist yet, we will push null at first,
+    // and replace it on the stack later when invalidating the context.
+    var memoizedMergedChildContext =
+      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+      emptyObject;
+
+    // Remember the parent context so we can merge with it later.
+    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
+    previousContext = contextStackCursor.current;
+    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
+    push(
+      didPerformWorkStackCursor,
+      didPerformWorkStackCursor.current,
+      workInProgress
+    );
+
+    return true;
+  }
+
+  function invalidateContextProvider(workInProgress, didChange) {
+    var instance = workInProgress.stateNode;
+    invariant(
+      instance,
+      "Expected to have an instance by this point. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    if (didChange) {
+      // Merge parent and own context.
+      // Skip this if we're not updating due to sCU.
+      // This avoids unnecessarily recomputing memoized values.
+      var mergedContext = processChildContext(workInProgress, previousContext);
+      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+
+      // Replace the old (or empty) context with the new one.
+      // It is important to unwind the context in the reverse order.
+      pop(didPerformWorkStackCursor, workInProgress);
+      pop(contextStackCursor, workInProgress);
+      // Now push the new context and mark that it has changed.
+      push(contextStackCursor, mergedContext, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    } else {
+      pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    }
+  }
+
+  function findCurrentUnmaskedContext(fiber) {
+    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
+    // makes sense elsewhere
+    invariant(
+      isFiberMounted(fiber) && fiber.tag === ClassComponent,
+      "Expected subtree parent to be a mounted class component. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    var node = fiber;
+    while (node.tag !== HostRoot) {
+      if (isContextProvider(node)) {
+        return node.stateNode.__reactInternalMemoizedMergedChildContext;
+      }
+      var parent = node["return"];
+      invariant(
+        parent,
+        "Found unexpected detached subtree parent. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
+      node = parent;
+    }
+    return node.stateNode.context;
+  }
+
+  return {
+    getUnmaskedContext: getUnmaskedContext,
+    cacheContext: cacheContext,
+    getMaskedContext: getMaskedContext,
+    hasContextChanged: hasContextChanged,
+    isContextConsumer: isContextConsumer,
+    isContextProvider: isContextProvider,
+    popContextProvider: popContextProvider,
+    popTopLevelContextObject: popTopLevelContextObject,
+    pushTopLevelContextObject: pushTopLevelContextObject,
+    processChildContext: processChildContext,
+    pushContextProvider: pushContextProvider,
+    invalidateContextProvider: invalidateContextProvider,
+    findCurrentUnmaskedContext: findCurrentUnmaskedContext
+  };
+};
+
+var ReactFiberNewContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  var providerCursor = createCursor(null);
+  var valueCursor = createCursor(null);
+  var changedBitsCursor = createCursor(0);
+
+  var rendererSigil = void 0;
+  {
+    // Use this to detect multiple renderers using the same context
+    rendererSigil = {};
+  }
+
+  function pushProvider(providerFiber) {
+    var context = providerFiber.type.context;
+
+    push(changedBitsCursor, context._changedBits, providerFiber);
+    push(valueCursor, context._currentValue, providerFiber);
+    push(providerCursor, providerFiber, providerFiber);
+
+    context._currentValue = providerFiber.pendingProps.value;
+    context._changedBits = providerFiber.stateNode;
+
+    {
+      warning(
+        context._currentRenderer === null ||
+          context._currentRenderer === rendererSigil,
+        "Detected multiple renderers concurrently rendering the " +
+          "same context provider. This is currently unsupported."
+      );
+      context._currentRenderer = rendererSigil;
+    }
+  }
+
+  function popProvider(providerFiber) {
+    var changedBits = changedBitsCursor.current;
+    var currentValue = valueCursor.current;
+
+    pop(providerCursor, providerFiber);
+    pop(valueCursor, providerFiber);
+    pop(changedBitsCursor, providerFiber);
+
+    var context = providerFiber.type.context;
+    context._currentValue = currentValue;
+    context._changedBits = changedBits;
+  }
+
+  return {
+    pushProvider: pushProvider,
+    popProvider: popProvider
+  };
+};
+
+var ReactFiberStack = function() {
+  var valueStack = [];
+
+  var fiberStack = void 0;
+
+  {
+    fiberStack = [];
+  }
+
+  var index = -1;
+
+  function createCursor(defaultValue) {
+    return {
+      current: defaultValue
+    };
+  }
+
+  function isEmpty() {
+    return index === -1;
+  }
+
+  function pop(cursor, fiber) {
+    if (index < 0) {
+      {
+        warning(false, "Unexpected pop.");
+      }
+      return;
+    }
+
+    {
+      if (fiber !== fiberStack[index]) {
+        warning(false, "Unexpected Fiber popped.");
+      }
+    }
+
+    cursor.current = valueStack[index];
+
+    valueStack[index] = null;
+
+    {
+      fiberStack[index] = null;
+    }
+
+    index--;
+  }
+
+  function push(cursor, value, fiber) {
+    index++;
+
+    valueStack[index] = cursor.current;
+
+    {
+      fiberStack[index] = fiber;
+    }
+
+    cursor.current = value;
+  }
+
+  function checkThatStackIsEmpty() {
+    {
+      if (index !== -1) {
+        warning(
+          false,
+          "Expected an empty stack. Something was not reset properly."
+        );
+      }
+    }
+  }
+
+  function resetStackAfterFatalErrorInDev() {
+    {
+      index = -1;
+      valueStack.length = 0;
+      fiberStack.length = 0;
+    }
+  }
+
+  return {
+    createCursor: createCursor,
+    isEmpty: isEmpty,
+    pop: pop,
+    push: push,
+    checkThatStackIsEmpty: checkThatStackIsEmpty,
+    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
+  };
+};
+
 var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
 var hasCaughtError = ReactErrorUtils.hasCaughtError;
 var clearCaughtError = ReactErrorUtils.clearCaughtError;
@@ -11487,16 +11577,23 @@ var warnAboutInvalidUpdates = void 0;
 }
 
 var ReactFiberScheduler = function(config) {
-  var hostContext = ReactFiberHostContext(config);
+  var stack = ReactFiberStack();
+  var hostContext = ReactFiberHostContext(config, stack);
+  var legacyContext = ReactFiberLegacyContext(stack);
+  var newContext = ReactFiberNewContext(stack);
   var popHostContext = hostContext.popHostContext,
     popHostContainer = hostContext.popHostContainer;
+  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popLegacyContextProvider = legacyContext.popContextProvider;
+  var popProvider = newContext.popProvider;
 
   var hydrationContext = ReactFiberHydrationContext(config);
-  var resetHostContainer = hostContext.resetHostContainer;
 
   var _ReactFiberBeginWork = ReactFiberBeginWork(
       config,
       hostContext,
+      legacyContext,
+      newContext,
       hydrationContext,
       scheduleWork,
       computeExpirationForFiber
@@ -11506,17 +11603,22 @@ var ReactFiberScheduler = function(config) {
   var _ReactFiberCompleteWo = ReactFiberCompleteWork(
       config,
       hostContext,
+      legacyContext,
+      newContext,
       hydrationContext
     ),
     completeWork = _ReactFiberCompleteWo.completeWork;
 
   var _ReactFiberUnwindWork = ReactFiberUnwindWork(
       hostContext,
+      legacyContext,
+      newContext,
       scheduleWork,
       isAlreadyFailedLegacyErrorBoundary
     ),
     throwException = _ReactFiberUnwindWork.throwException,
-    unwindWork = _ReactFiberUnwindWork.unwindWork;
+    unwindWork = _ReactFiberUnwindWork.unwindWork,
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
 
   var _ReactFiberCommitWork = ReactFiberCommitWork(
       config,
@@ -11585,13 +11687,13 @@ var ReactFiberScheduler = function(config) {
       switch (failedUnitOfWork.tag) {
         case HostRoot:
           popHostContainer(failedUnitOfWork);
-          popTopLevelContextObject(failedUnitOfWork);
+          popTopLevelLegacyContextObject(failedUnitOfWork);
           break;
         case HostComponent:
           popHostContext(failedUnitOfWork);
           break;
         case ClassComponent:
-          popContextProvider(failedUnitOfWork);
+          popLegacyContextProvider(failedUnitOfWork);
           break;
         case HostPortal:
           popHostContainer(failedUnitOfWork);
@@ -11611,18 +11713,18 @@ var ReactFiberScheduler = function(config) {
     };
   }
 
-  function resetContextStack() {
-    // Reset the stack
-    reset();
-    // Reset the cursors
-    resetContext();
-    resetHostContainer();
-
-    // TODO: Unify new context implementation with other stacks
-    resetProviderStack();
+  function resetStack() {
+    if (nextUnitOfWork !== null) {
+      var interruptedWork = nextUnitOfWork["return"];
+      while (interruptedWork !== null) {
+        unwindInterruptedWork(interruptedWork);
+        interruptedWork = interruptedWork["return"];
+      }
+    }
 
     {
       ReactStrictModeWarnings.discardPendingWarnings();
+      stack.checkThatStackIsEmpty();
     }
 
     nextRoot = null;
@@ -12146,7 +12248,7 @@ var ReactFiberScheduler = function(config) {
       nextUnitOfWork === null
     ) {
       // Reset the stack and start working from the root.
-      resetContextStack();
+      resetStack();
       nextRoot = root;
       nextRenderExpirationTime = expirationTime;
       nextUnitOfWork = createWorkInProgress(
@@ -12199,6 +12301,9 @@ var ReactFiberScheduler = function(config) {
     // Yield back to main thread.
     if (didFatal) {
       // There was a fatal error.
+      {
+        stack.resetStackAfterFatalErrorInDev();
+      }
       return null;
     } else if (nextUnitOfWork === null) {
       // We reached the root.
@@ -12399,7 +12504,7 @@ var ReactFiberScheduler = function(config) {
           ) {
             // This is an interruption. (Used for performance tracking.)
             interruptedBy = fiber;
-            resetContextStack();
+            resetStack();
           }
           if (nextRoot !== root || !isWorking) {
             requestWork(root, expirationTime);
@@ -12970,7 +13075,8 @@ var ReactFiberScheduler = function(config) {
     syncUpdates: syncUpdates,
     interactiveUpdates: interactiveUpdates,
     flushInteractiveUpdates: flushInteractiveUpdates,
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration
+    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+    legacyContext: legacyContext
   };
 };
 
@@ -12983,18 +13089,6 @@ var didWarnAboutNestedUpdates = void 0;
 // 0 is PROD, 1 is DEV.
 // Might add PROFILE later.
 
-function getContextForSubtree(parentComponent) {
-  if (!parentComponent) {
-    return emptyObject;
-  }
-
-  var fiber = get(parentComponent);
-  var parentContext = findCurrentUnmaskedContext(fiber);
-  return isContextProvider(fiber)
-    ? processChildContext(fiber, parentContext)
-    : parentContext;
-}
-
 var ReactFiberReconciler$1 = function(config) {
   var getPublicInstance = config.getPublicInstance;
 
@@ -13013,7 +13107,24 @@ var ReactFiberReconciler$1 = function(config) {
     deferredUpdates = _ReactFiberScheduler.deferredUpdates,
     syncUpdates = _ReactFiberScheduler.syncUpdates,
     interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
-    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates;
+    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
+    legacyContext = _ReactFiberScheduler.legacyContext;
+
+  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
+
+  function getContextForSubtree(parentComponent) {
+    if (!parentComponent) {
+      return emptyObject;
+    }
+
+    var fiber = get(parentComponent);
+    var parentContext = findCurrentUnmaskedContext(fiber);
+    return isContextProvider(fiber)
+      ? processChildContext(fiber, parentContext)
+      : parentContext;
+  }
 
   function scheduleRootUpdate(
     current,
diff --git a/Libraries/Renderer/ReactFabric-prod.js b/Libraries/Renderer/ReactFabric-prod.js
index 637481f04146..08f112c70d45 100644
--- a/Libraries/Renderer/ReactFabric-prod.js
+++ b/Libraries/Renderer/ReactFabric-prod.js
@@ -1633,136 +1633,6 @@ function findCurrentHostFiberWithNoPortals(parent) {
   }
   return null;
 }
-var valueStack = [],
-  index = -1;
-function pop(cursor) {
-  0 > index ||
-    ((cursor.current = valueStack[index]), (valueStack[index] = null), index--);
-}
-function push(cursor, value) {
-  index++;
-  valueStack[index] = cursor.current;
-  cursor.current = value;
-}
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  do {
-    a: switch (workInProgress.tag) {
-      case 0:
-      case 1:
-      case 2:
-      case 5:
-        var owner = workInProgress._debugOwner,
-          source = workInProgress._debugSource;
-        var JSCompiler_inline_result = getComponentName(workInProgress);
-        var ownerName = null;
-        owner && (ownerName = getComponentName(owner));
-        owner = source;
-        JSCompiler_inline_result =
-          "\n    in " +
-          (JSCompiler_inline_result || "Unknown") +
-          (owner
-            ? " (at " +
-              owner.fileName.replace(/^.*[\\\/]/, "") +
-              ":" +
-              owner.lineNumber +
-              ")"
-            : ownerName ? " (created by " + ownerName + ")" : "");
-        break a;
-      default:
-        JSCompiler_inline_result = "";
-    }
-    info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
-  } while (workInProgress);
-  return info;
-}
-new Set();
-var contextStackCursor = { current: emptyObject },
-  didPerformWorkStackCursor = { current: !1 },
-  previousContext = emptyObject;
-function getUnmaskedContext(workInProgress) {
-  return isContextProvider(workInProgress)
-    ? previousContext
-    : contextStackCursor.current;
-}
-function getMaskedContext(workInProgress, unmaskedContext) {
-  var contextTypes = workInProgress.type.contextTypes;
-  if (!contextTypes) return emptyObject;
-  var instance = workInProgress.stateNode;
-  if (
-    instance &&
-    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-  )
-    return instance.__reactInternalMemoizedMaskedChildContext;
-  var context = {},
-    key;
-  for (key in contextTypes) context[key] = unmaskedContext[key];
-  instance &&
-    ((workInProgress = workInProgress.stateNode),
-    (workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext),
-    (workInProgress.__reactInternalMemoizedMaskedChildContext = context));
-  return context;
-}
-function isContextProvider(fiber) {
-  return 2 === fiber.tag && null != fiber.type.childContextTypes;
-}
-function popContextProvider(fiber) {
-  isContextProvider(fiber) &&
-    (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
-}
-function pushTopLevelContextObject(fiber, context, didChange) {
-  invariant(
-    null == contextStackCursor.cursor,
-    "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
-  );
-  push(contextStackCursor, context, fiber);
-  push(didPerformWorkStackCursor, didChange, fiber);
-}
-function processChildContext(fiber, parentContext) {
-  var instance = fiber.stateNode,
-    childContextTypes = fiber.type.childContextTypes;
-  if ("function" !== typeof instance.getChildContext) return parentContext;
-  instance = instance.getChildContext();
-  for (var contextKey in instance)
-    invariant(
-      contextKey in childContextTypes,
-      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-      getComponentName(fiber) || "Unknown",
-      contextKey
-    );
-  return Object.assign({}, parentContext, instance);
-}
-function pushContextProvider(workInProgress) {
-  if (!isContextProvider(workInProgress)) return !1;
-  var instance = workInProgress.stateNode;
-  instance =
-    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-    emptyObject;
-  previousContext = contextStackCursor.current;
-  push(contextStackCursor, instance, workInProgress);
-  push(
-    didPerformWorkStackCursor,
-    didPerformWorkStackCursor.current,
-    workInProgress
-  );
-  return !0;
-}
-function invalidateContextProvider(workInProgress, didChange) {
-  var instance = workInProgress.stateNode;
-  invariant(
-    instance,
-    "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
-  );
-  if (didChange) {
-    var mergedContext = processChildContext(workInProgress, previousContext);
-    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-    pop(didPerformWorkStackCursor, workInProgress);
-    pop(contextStackCursor, workInProgress);
-    push(contextStackCursor, mergedContext, workInProgress);
-  } else pop(didPerformWorkStackCursor, workInProgress);
-  push(didPerformWorkStackCursor, didChange, workInProgress);
-}
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
   this.key = key;
@@ -1929,6 +1799,40 @@ function onCommitRoot(root) {
 function onCommitUnmount(fiber) {
   "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
 }
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
+    }
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress["return"];
+  } while (workInProgress);
+  return info;
+}
+new Set();
 function createUpdateQueue(baseState) {
   return {
     baseState: baseState,
@@ -2084,6 +1988,7 @@ function commitCallbacks(queue, context) {
     }
 }
 function ReactFiberClassComponent(
+  legacyContext,
   scheduleWork,
   computeExpirationForFiber,
   memoizeProps,
@@ -2140,62 +2045,66 @@ function ReactFiberClassComponent(
         workInProgress.memoizedState
       );
   }
-  var updater = {
-    isMounted: isMounted,
-    enqueueSetState: function(instance, partialState, callback) {
-      instance = instance._reactInternalFiber;
-      callback = void 0 === callback ? null : callback;
-      var expirationTime = computeExpirationForFiber(instance);
-      insertUpdateIntoFiber(instance, {
-        expirationTime: expirationTime,
-        partialState: partialState,
-        callback: callback,
-        isReplace: !1,
-        isForced: !1,
-        capturedValue: null,
-        next: null
-      });
-      scheduleWork(instance, expirationTime);
-    },
-    enqueueReplaceState: function(instance, state, callback) {
-      instance = instance._reactInternalFiber;
-      callback = void 0 === callback ? null : callback;
-      var expirationTime = computeExpirationForFiber(instance);
-      insertUpdateIntoFiber(instance, {
-        expirationTime: expirationTime,
-        partialState: state,
-        callback: callback,
-        isReplace: !0,
-        isForced: !1,
-        capturedValue: null,
-        next: null
-      });
-      scheduleWork(instance, expirationTime);
-    },
-    enqueueForceUpdate: function(instance, callback) {
-      instance = instance._reactInternalFiber;
-      callback = void 0 === callback ? null : callback;
-      var expirationTime = computeExpirationForFiber(instance);
-      insertUpdateIntoFiber(instance, {
-        expirationTime: expirationTime,
-        partialState: null,
-        callback: callback,
-        isReplace: !1,
-        isForced: !0,
-        capturedValue: null,
-        next: null
-      });
-      scheduleWork(instance, expirationTime);
-    }
-  };
+  var cacheContext = legacyContext.cacheContext,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    isContextConsumer = legacyContext.isContextConsumer,
+    hasContextChanged = legacyContext.hasContextChanged,
+    updater = {
+      isMounted: isMounted,
+      enqueueSetState: function(instance, partialState, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: partialState,
+          callback: callback,
+          isReplace: !1,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      },
+      enqueueReplaceState: function(instance, state, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: state,
+          callback: callback,
+          isReplace: !0,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      },
+      enqueueForceUpdate: function(instance, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: null,
+          callback: callback,
+          isReplace: !1,
+          isForced: !0,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      }
+    };
   return {
     adoptClassInstance: adoptClassInstance,
     callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: function(workInProgress, props) {
       var ctor = workInProgress.type,
         unmaskedContext = getUnmaskedContext(workInProgress),
-        needsContext =
-          2 === workInProgress.tag && null != workInProgress.type.contextTypes,
+        needsContext = isContextConsumer(workInProgress),
         context = needsContext
           ? getMaskedContext(workInProgress, unmaskedContext)
           : emptyObject;
@@ -2212,10 +2121,7 @@ function ReactFiberClassComponent(
           workInProgress.memoizedState,
           props
         ));
-      needsContext &&
-        ((workInProgress = workInProgress.stateNode),
-        (workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext),
-        (workInProgress.__reactInternalMemoizedMaskedChildContext = context));
+      needsContext && cacheContext(workInProgress, unmaskedContext, context);
       return ctor;
     },
     mountClassInstance: function(workInProgress, renderExpirationTime) {
@@ -2300,7 +2206,7 @@ function ReactFiberClassComponent(
         !(
           oldProps !== newProps ||
           oldState !== renderExpirationTime ||
-          didPerformWorkStackCursor.current ||
+          hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
         )
@@ -2389,7 +2295,7 @@ function ReactFiberClassComponent(
         !(
           oldProps !== newProps ||
           oldContext !== renderExpirationTime ||
-          didPerformWorkStackCursor.current ||
+          hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
         )
@@ -3112,34 +3018,12 @@ function ChildReconciler(shouldTrackSideEffects) {
   };
 }
 var reconcileChildFibers = ChildReconciler(!0),
-  mountChildFibers = ChildReconciler(!1),
-  changedBitsStack = [],
-  currentValueStack = [],
-  stack = [],
-  index$1 = -1;
-function pushProvider(providerFiber) {
-  var context = providerFiber.type.context;
-  index$1 += 1;
-  changedBitsStack[index$1] = context._changedBits;
-  currentValueStack[index$1] = context._currentValue;
-  stack[index$1] = providerFiber;
-  context._currentValue = providerFiber.pendingProps.value;
-  context._changedBits = providerFiber.stateNode;
-}
-function popProvider(providerFiber) {
-  var changedBits = changedBitsStack[index$1],
-    currentValue = currentValueStack[index$1];
-  changedBitsStack[index$1] = null;
-  currentValueStack[index$1] = null;
-  stack[index$1] = null;
-  --index$1;
-  providerFiber = providerFiber.type.context;
-  providerFiber._currentValue = currentValue;
-  providerFiber._changedBits = changedBits;
-}
+  mountChildFibers = ChildReconciler(!1);
 function ReactFiberBeginWork(
   config,
   hostContext,
+  legacyContext,
+  newContext,
   hydrationContext,
   scheduleWork,
   computeExpirationForFiber
@@ -3236,7 +3120,12 @@ function ReactFiberBeginWork(
     changedBits,
     renderExpirationTime
   ) {
-    for (var fiber = workInProgress.child; null !== fiber; ) {
+    var fiber = workInProgress.child;
+    for (
+      null !== fiber && (fiber["return"] = workInProgress);
+      null !== fiber;
+
+    ) {
       switch (fiber.tag) {
         case 12:
           var nextFiber = fiber.stateNode | 0;
@@ -3295,7 +3184,7 @@ function ReactFiberBeginWork(
     var context = workInProgress.type.context,
       newProps = workInProgress.pendingProps,
       oldProps = workInProgress.memoizedProps;
-    if (!didPerformWorkStackCursor.current && oldProps === newProps)
+    if (!hasLegacyContextChanged() && oldProps === newProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
@@ -3382,11 +3271,19 @@ function ReactFiberBeginWork(
     shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree,
     pushHostContext = hostContext.pushHostContext,
     pushHostContainer = hostContext.pushHostContainer,
+    pushProvider = newContext.pushProvider,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    hasLegacyContextChanged = legacyContext.hasContextChanged,
+    pushLegacyContextProvider = legacyContext.pushContextProvider,
+    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
+    invalidateContextProvider = legacyContext.invalidateContextProvider,
     enterHydrationState = hydrationContext.enterHydrationState,
     resetHydrationState = hydrationContext.resetHydrationState,
     tryToClaimNextHydratableInstance =
       hydrationContext.tryToClaimNextHydratableInstance;
   config = ReactFiberClassComponent(
+    legacyContext,
     scheduleWork,
     computeExpirationForFiber,
     function(workInProgress, nextProps) {
@@ -3413,7 +3310,7 @@ function ReactFiberBeginWork(
             pushHostRootContext(workInProgress);
             break;
           case 2:
-            pushContextProvider(workInProgress);
+            pushLegacyContextProvider(workInProgress);
             break;
           case 4:
             pushHostContainer(
@@ -3459,7 +3356,7 @@ function ReactFiberBeginWork(
                     workInProgress.memoizedState,
                     props
                   ))),
-              (props = pushContextProvider(workInProgress)),
+              (props = pushLegacyContextProvider(workInProgress)),
               adoptClassInstance(workInProgress, fn),
               mountClassInstance(workInProgress, renderExpirationTime),
               (current = finishClassComponent(
@@ -3479,7 +3376,7 @@ function ReactFiberBeginWork(
           return (
             (props = workInProgress.type),
             (renderExpirationTime = workInProgress.pendingProps),
-            didPerformWorkStackCursor.current ||
+            hasLegacyContextChanged() ||
             workInProgress.memoizedProps !== renderExpirationTime
               ? ((fn = getUnmaskedContext(workInProgress)),
                 (fn = getMaskedContext(workInProgress, fn)),
@@ -3495,7 +3392,7 @@ function ReactFiberBeginWork(
             current
           );
         case 2:
-          props = pushContextProvider(workInProgress);
+          props = pushLegacyContextProvider(workInProgress);
           null === current
             ? null === workInProgress.stateNode
               ? (constructClassInstance(
@@ -3577,7 +3474,7 @@ function ReactFiberBeginWork(
             updateQueue = workInProgress.memoizedProps;
             fn = workInProgress.pendingProps;
             unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!didPerformWorkStackCursor.current && updateQueue === fn) {
+            if (!hasLegacyContextChanged() && updateQueue === fn) {
               if (
                 (updateQueue =
                   workInProgress.mode & 1 &&
@@ -3619,7 +3516,7 @@ function ReactFiberBeginWork(
         case 7:
           return (
             (props = workInProgress.pendingProps),
-            didPerformWorkStackCursor.current ||
+            hasLegacyContextChanged() ||
               workInProgress.memoizedProps !== props ||
               (props = workInProgress.memoizedProps),
             (fn = props.children),
@@ -3649,8 +3546,7 @@ function ReactFiberBeginWork(
               workInProgress.stateNode.containerInfo
             ),
             (props = workInProgress.pendingProps),
-            didPerformWorkStackCursor.current ||
-            workInProgress.memoizedProps !== props
+            hasLegacyContextChanged() || workInProgress.memoizedProps !== props
               ? (null === current
                   ? (workInProgress.child = reconcileChildFibers(
                       workInProgress,
@@ -3681,7 +3577,7 @@ function ReactFiberBeginWork(
         case 10:
           return (
             (renderExpirationTime = workInProgress.pendingProps),
-            didPerformWorkStackCursor.current ||
+            hasLegacyContextChanged() ||
             workInProgress.memoizedProps !== renderExpirationTime
               ? (reconcileChildren(
                   current,
@@ -3699,7 +3595,7 @@ function ReactFiberBeginWork(
         case 11:
           return (
             (renderExpirationTime = workInProgress.pendingProps.children),
-            didPerformWorkStackCursor.current ||
+            hasLegacyContextChanged() ||
             (null !== renderExpirationTime &&
               workInProgress.memoizedProps !== renderExpirationTime)
               ? (reconcileChildren(
@@ -3729,7 +3625,7 @@ function ReactFiberBeginWork(
             props = fn._currentValue;
             var changedBits = fn._changedBits;
             if (
-              didPerformWorkStackCursor.current ||
+              hasLegacyContextChanged() ||
               0 !== changedBits ||
               updateQueue !== unmaskedContext
             ) {
@@ -3769,7 +3665,13 @@ function ReactFiberBeginWork(
     }
   };
 }
-function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
+function ReactFiberCompleteWork(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext
+) {
   function markUpdate(workInProgress) {
     workInProgress.effectTag |= 4;
   }
@@ -3802,6 +3704,9 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
     popHostContext = hostContext.popHostContext,
     getHostContext = hostContext.getHostContext,
     popHostContainer = hostContext.popHostContainer,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider,
     prepareToHydrateHostInstance =
       hydrationContext.prepareToHydrateHostInstance,
     prepareToHydrateHostTextInstance =
@@ -3901,7 +3806,7 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
           return null;
         case 2:
           return (
-            popContextProvider(workInProgress),
+            popLegacyContextProvider(workInProgress),
             (current = workInProgress.stateNode),
             (newProps = workInProgress.updateQueue),
             null !== newProps &&
@@ -3914,8 +3819,7 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
           );
         case 3:
           popHostContainer(workInProgress);
-          pop(didPerformWorkStackCursor, workInProgress);
-          pop(contextStackCursor, workInProgress);
+          popTopLevelLegacyContextObject(workInProgress);
           newProps = workInProgress.stateNode;
           newProps.pendingContext &&
             ((newProps.context = newProps.pendingContext),
@@ -4099,11 +4003,16 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
 }
 function ReactFiberUnwindWork(
   hostContext,
+  legacyContext,
+  newContext,
   scheduleWork,
   isAlreadyFailedLegacyErrorBoundary
 ) {
   var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
   return {
     throwException: function(returnFiber, sourceFiber, rawValue) {
       sourceFiber.effectTag |= 512;
@@ -4144,7 +4053,7 @@ function ReactFiberUnwindWork(
     unwindWork: function(workInProgress) {
       switch (workInProgress.tag) {
         case 2:
-          popContextProvider(workInProgress);
+          popLegacyContextProvider(workInProgress);
           var effectTag = workInProgress.effectTag;
           return effectTag & 1024
             ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
@@ -4153,8 +4062,7 @@ function ReactFiberUnwindWork(
         case 3:
           return (
             popHostContainer(workInProgress),
-            pop(didPerformWorkStackCursor, workInProgress),
-            pop(contextStackCursor, workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
             (effectTag = workInProgress.effectTag),
             effectTag & 1024
               ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
@@ -4170,6 +4078,25 @@ function ReactFiberUnwindWork(
         default:
           return null;
       }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
     }
   };
 }
@@ -4425,7 +4352,7 @@ function ReactFiberCommitWork(
   invariant(!1, "Mutating reconciler is disabled.");
 }
 var NO_CONTEXT = {};
-function ReactFiberHostContext(config) {
+function ReactFiberHostContext(config, stack) {
   function requiredContext(c) {
     invariant(
       c !== NO_CONTEXT,
@@ -4434,10 +4361,13 @@ function ReactFiberHostContext(config) {
     return c;
   }
   var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext,
-    contextStackCursor = { current: NO_CONTEXT },
-    contextFiberStackCursor = { current: NO_CONTEXT },
-    rootInstanceStackCursor = { current: NO_CONTEXT };
+    getRootHostContext = config.getRootHostContext;
+  config = stack.createCursor;
+  var push = stack.push,
+    pop = stack.pop,
+    contextStackCursor = config(NO_CONTEXT),
+    contextFiberStackCursor = config(NO_CONTEXT),
+    rootInstanceStackCursor = config(NO_CONTEXT);
   return {
     getHostContext: function() {
       return requiredContext(contextStackCursor.current);
@@ -4467,10 +4397,6 @@ function ReactFiberHostContext(config) {
       context !== rootInstance &&
         (push(contextFiberStackCursor, fiber, fiber),
         push(contextStackCursor, rootInstance, fiber));
-    },
-    resetHostContainer: function() {
-      contextStackCursor.current = NO_CONTEXT;
-      rootInstanceStackCursor.current = NO_CONTEXT;
     }
   };
 }
@@ -4630,22 +4556,198 @@ function ReactFiberHydrationContext(config) {
     }
   };
 }
-function ReactFiberScheduler(config) {
-  function resetContextStack() {
-    for (; -1 < index; ) (valueStack[index] = null), index--;
+function ReactFiberLegacyContext(stack) {
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    workInProgress = workInProgress.stateNode;
+    workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    workInProgress.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
+  function isContextProvider(fiber) {
+    return 2 === fiber.tag && null != fiber.type.childContextTypes;
+  }
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode,
+      childContextTypes = fiber.type.childContextTypes;
+    if ("function" !== typeof instance.getChildContext) return parentContext;
+    instance = instance.getChildContext();
+    for (var contextKey in instance)
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    return Object.assign({}, parentContext, instance);
+  }
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop,
+    contextStackCursor = createCursor(emptyObject),
+    didPerformWorkStackCursor = createCursor(!1),
     previousContext = emptyObject;
-    contextStackCursor.current = emptyObject;
-    didPerformWorkStackCursor.current = !1;
-    resetHostContainer();
-    for (var i = index$1; -1 < i; i--) {
-      var context = stack[i].type.context;
-      context._currentValue = context._defaultValue;
-      context._changedBits = 0;
-      changedBitsStack[i] = null;
-      currentValueStack[i] = null;
-      stack[i] = null;
+  return {
+    getUnmaskedContext: function(workInProgress) {
+      return isContextProvider(workInProgress)
+        ? previousContext
+        : contextStackCursor.current;
+    },
+    cacheContext: cacheContext,
+    getMaskedContext: function(workInProgress, unmaskedContext) {
+      var contextTypes = workInProgress.type.contextTypes;
+      if (!contextTypes) return emptyObject;
+      var instance = workInProgress.stateNode;
+      if (
+        instance &&
+        instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+      )
+        return instance.__reactInternalMemoizedMaskedChildContext;
+      var context = {},
+        key;
+      for (key in contextTypes) context[key] = unmaskedContext[key];
+      instance && cacheContext(workInProgress, unmaskedContext, context);
+      return context;
+    },
+    hasContextChanged: function() {
+      return didPerformWorkStackCursor.current;
+    },
+    isContextConsumer: function(fiber) {
+      return 2 === fiber.tag && null != fiber.type.contextTypes;
+    },
+    isContextProvider: isContextProvider,
+    popContextProvider: function(fiber) {
+      isContextProvider(fiber) &&
+        (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
+    },
+    popTopLevelContextObject: function(fiber) {
+      pop(didPerformWorkStackCursor, fiber);
+      pop(contextStackCursor, fiber);
+    },
+    pushTopLevelContextObject: function(fiber, context, didChange) {
+      invariant(
+        null == contextStackCursor.cursor,
+        "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
+      );
+      push(contextStackCursor, context, fiber);
+      push(didPerformWorkStackCursor, didChange, fiber);
+    },
+    processChildContext: processChildContext,
+    pushContextProvider: function(workInProgress) {
+      if (!isContextProvider(workInProgress)) return !1;
+      var instance = workInProgress.stateNode;
+      instance =
+        (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+        emptyObject;
+      previousContext = contextStackCursor.current;
+      push(contextStackCursor, instance, workInProgress);
+      push(
+        didPerformWorkStackCursor,
+        didPerformWorkStackCursor.current,
+        workInProgress
+      );
+      return !0;
+    },
+    invalidateContextProvider: function(workInProgress, didChange) {
+      var instance = workInProgress.stateNode;
+      invariant(
+        instance,
+        "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+      );
+      if (didChange) {
+        var mergedContext = processChildContext(
+          workInProgress,
+          previousContext
+        );
+        instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+        pop(didPerformWorkStackCursor, workInProgress);
+        pop(contextStackCursor, workInProgress);
+        push(contextStackCursor, mergedContext, workInProgress);
+      } else pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    },
+    findCurrentUnmaskedContext: function(fiber) {
+      for (
+        invariant(
+          2 === isFiberMountedImpl(fiber) && 2 === fiber.tag,
+          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
+        );
+        3 !== fiber.tag;
+
+      ) {
+        if (isContextProvider(fiber))
+          return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
+        fiber = fiber["return"];
+        invariant(
+          fiber,
+          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+      }
+      return fiber.stateNode.context;
+    }
+  };
+}
+function ReactFiberNewContext(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop,
+    providerCursor = createCursor(null),
+    valueCursor = createCursor(null),
+    changedBitsCursor = createCursor(0);
+  return {
+    pushProvider: function(providerFiber) {
+      var context = providerFiber.type.context;
+      push(changedBitsCursor, context._changedBits, providerFiber);
+      push(valueCursor, context._currentValue, providerFiber);
+      push(providerCursor, providerFiber, providerFiber);
+      context._currentValue = providerFiber.pendingProps.value;
+      context._changedBits = providerFiber.stateNode;
+    },
+    popProvider: function(providerFiber) {
+      var changedBits = changedBitsCursor.current,
+        currentValue = valueCursor.current;
+      pop(providerCursor, providerFiber);
+      pop(valueCursor, providerFiber);
+      pop(changedBitsCursor, providerFiber);
+      providerFiber = providerFiber.type.context;
+      providerFiber._currentValue = currentValue;
+      providerFiber._changedBits = changedBits;
     }
-    index$1 = -1;
+  };
+}
+function ReactFiberStack() {
+  var valueStack = [],
+    index = -1;
+  return {
+    createCursor: function(defaultValue) {
+      return { current: defaultValue };
+    },
+    isEmpty: function() {
+      return -1 === index;
+    },
+    pop: function(cursor) {
+      0 > index ||
+        ((cursor.current = valueStack[index]),
+        (valueStack[index] = null),
+        index--);
+    },
+    push: function(cursor, value) {
+      index++;
+      valueStack[index] = cursor.current;
+      cursor.current = value;
+    },
+    checkThatStackIsEmpty: function() {},
+    resetStackAfterFatalErrorInDev: function() {}
+  };
+}
+function ReactFiberScheduler(config) {
+  function resetStack() {
+    if (null !== nextUnitOfWork)
+      for (
+        var interruptedWork = nextUnitOfWork["return"];
+        null !== interruptedWork;
+
+      )
+        unwindInterruptedWork(interruptedWork),
+          (interruptedWork = interruptedWork["return"]);
     nextRoot = null;
     nextRenderExpirationTime = 0;
     nextUnitOfWork = null;
@@ -4751,7 +4853,7 @@ function ReactFiberScheduler(config) {
       root !== nextRoot ||
       null === nextUnitOfWork
     )
-      resetContextStack(),
+      resetStack(),
         (nextRoot = root),
         (nextRenderExpirationTime = expirationTime),
         (nextUnitOfWork = createWorkInProgress(
@@ -4881,7 +4983,7 @@ function ReactFiberScheduler(config) {
             !isWorking &&
               0 !== nextRenderExpirationTime &&
               expirationTime < nextRenderExpirationTime &&
-              resetContextStack();
+              resetStack();
             (nextRoot === root && isWorking) ||
               requestWork(root, expirationTime);
             nestedUpdateCount > NESTED_UPDATE_LIMIT &&
@@ -5225,25 +5327,37 @@ function ReactFiberScheduler(config) {
     nextFlushedRoot.remainingExpirationTime = 0;
     hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
   }
-  var hostContext = ReactFiberHostContext(config),
-    hydrationContext = ReactFiberHydrationContext(config),
-    resetHostContainer = hostContext.resetHostContainer,
+  var stack = ReactFiberStack(),
+    hostContext = ReactFiberHostContext(config, stack),
+    legacyContext = ReactFiberLegacyContext(stack);
+  stack = ReactFiberNewContext(stack);
+  var hydrationContext = ReactFiberHydrationContext(config),
     beginWork = ReactFiberBeginWork(
       config,
       hostContext,
+      legacyContext,
+      stack,
       hydrationContext,
       scheduleWork,
       computeExpirationForFiber
     ).beginWork,
-    completeWork = ReactFiberCompleteWork(config, hostContext, hydrationContext)
-      .completeWork;
+    completeWork = ReactFiberCompleteWork(
+      config,
+      hostContext,
+      legacyContext,
+      stack,
+      hydrationContext
+    ).completeWork;
   hostContext = ReactFiberUnwindWork(
     hostContext,
+    legacyContext,
+    stack,
     scheduleWork,
     isAlreadyFailedLegacyErrorBoundary
   );
   var throwException = hostContext.throwException,
-    unwindWork = hostContext.unwindWork;
+    unwindWork = hostContext.unwindWork,
+    unwindInterruptedWork = hostContext.unwindInterruptedWork;
   hostContext = ReactFiberCommitWork(
     config,
     onCommitPhaseError,
@@ -5402,7 +5516,8 @@ function ReactFiberScheduler(config) {
       result <= lastUniqueAsyncExpiration &&
         (result = lastUniqueAsyncExpiration + 1);
       return (lastUniqueAsyncExpiration = result);
-    }
+    },
+    legacyContext: legacyContext
   };
 }
 function ReactFiberReconciler$1(config) {
@@ -5417,27 +5532,7 @@ function ReactFiberReconciler$1(config) {
     currentTime = container.current;
     if (parentComponent) {
       parentComponent = parentComponent._reactInternalFiber;
-      var parentContext;
-      b: {
-        invariant(
-          2 === isFiberMountedImpl(parentComponent) &&
-            2 === parentComponent.tag,
-          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
-        );
-        for (parentContext = parentComponent; 3 !== parentContext.tag; ) {
-          if (isContextProvider(parentContext)) {
-            parentContext =
-              parentContext.stateNode.__reactInternalMemoizedMergedChildContext;
-            break b;
-          }
-          parentContext = parentContext["return"];
-          invariant(
-            parentContext,
-            "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
-          );
-        }
-        parentContext = parentContext.stateNode.context;
-      }
+      var parentContext = findCurrentUnmaskedContext(parentComponent);
       parentComponent = isContextProvider(parentComponent)
         ? processChildContext(parentComponent, parentContext)
         : parentContext;
@@ -5466,7 +5561,11 @@ function ReactFiberReconciler$1(config) {
   config = ReactFiberScheduler(config);
   var recalculateCurrentTime = config.recalculateCurrentTime,
     computeExpirationForFiber = config.computeExpirationForFiber,
-    scheduleWork = config.scheduleWork;
+    scheduleWork = config.scheduleWork,
+    legacyContext = config.legacyContext,
+    findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
   return {
     createContainer: function(containerInfo, isAsync, hydrate) {
       isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
diff --git a/Libraries/Renderer/ReactNativeRenderer-dev.js b/Libraries/Renderer/ReactNativeRenderer-dev.js
index d54c9f31c6cd..8ea8bcf85094 100644
--- a/Libraries/Renderer/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/ReactNativeRenderer-dev.js
@@ -26,9 +26,9 @@ var deepDiffer = require("deepDiffer");
 var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
-var checkPropTypes = require("prop-types/checkPropTypes");
 var shallowEqual = require("fbjs/lib/shallowEqual");
 var ExceptionsManager = require("ExceptionsManager");
+var checkPropTypes = require("prop-types/checkPropTypes");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
 
 var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
@@ -4389,1648 +4389,1323 @@ function findCurrentHostFiberWithNoPortals(parent) {
   return null;
 }
 
-var valueStack = [];
+// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
+// Math.pow(2, 30) - 1
+// 0b111111111111111111111111111111
+var MAX_SIGNED_31_BIT_INT = 1073741823;
 
-var fiberStack = void 0;
+// TODO: Use an opaque type once ESLint et al support the syntax
 
-{
-  fiberStack = [];
-}
+var NoWork = 0;
+var Sync = 1;
+var Never = MAX_SIGNED_31_BIT_INT;
 
-var index = -1;
+var UNIT_SIZE = 10;
+var MAGIC_NUMBER_OFFSET = 2;
 
-function createCursor(defaultValue) {
-  return {
-    current: defaultValue
-  };
+// 1 unit of expiration time represents 10ms.
+function msToExpirationTime(ms) {
+  // Always add an offset so that we don't clash with the magic number for NoWork.
+  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
 }
 
-function pop(cursor, fiber) {
-  if (index < 0) {
-    {
-      warning(false, "Unexpected pop.");
-    }
-    return;
-  }
+function expirationTimeToMs(expirationTime) {
+  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
+}
 
-  {
-    if (fiber !== fiberStack[index]) {
-      warning(false, "Unexpected Fiber popped.");
-    }
-  }
+function ceiling(num, precision) {
+  return (((num / precision) | 0) + 1) * precision;
+}
+
+function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
+  return ceiling(
+    currentTime + expirationInMs / UNIT_SIZE,
+    bucketSizeMs / UNIT_SIZE
+  );
+}
 
-  cursor.current = valueStack[index];
+var NoContext = 0;
+var AsyncMode = 1;
+var StrictMode = 2;
 
-  valueStack[index] = null;
+var hasBadMapPolyfill = void 0;
 
-  {
-    fiberStack[index] = null;
+{
+  hasBadMapPolyfill = false;
+  try {
+    var nonExtensibleObject = Object.preventExtensions({});
+    var testMap = new Map([[nonExtensibleObject, null]]);
+    var testSet = new Set([nonExtensibleObject]);
+    // This is necessary for Rollup to not consider these unused.
+    // https://github.com/rollup/rollup/issues/1771
+    // TODO: we can remove these if Rollup fixes the bug.
+    testMap.set(0, 0);
+    testSet.add(0);
+  } catch (e) {
+    // TODO: Consider warning about bad polyfills
+    hasBadMapPolyfill = true;
   }
+}
+
+// A Fiber is work on a Component that needs to be done or was done. There can
+// be more than one per component.
+
+var debugCounter = void 0;
 
-  index--;
+{
+  debugCounter = 1;
 }
 
-function push(cursor, value, fiber) {
-  index++;
+function FiberNode(tag, pendingProps, key, mode) {
+  // Instance
+  this.tag = tag;
+  this.key = key;
+  this.type = null;
+  this.stateNode = null;
 
-  valueStack[index] = cursor.current;
+  // Fiber
+  this["return"] = null;
+  this.child = null;
+  this.sibling = null;
+  this.index = 0;
 
-  {
-    fiberStack[index] = fiber;
-  }
+  this.ref = null;
 
-  cursor.current = value;
-}
+  this.pendingProps = pendingProps;
+  this.memoizedProps = null;
+  this.updateQueue = null;
+  this.memoizedState = null;
 
-function reset() {
-  while (index > -1) {
-    valueStack[index] = null;
+  this.mode = mode;
 
-    {
-      fiberStack[index] = null;
-    }
+  // Effects
+  this.effectTag = NoEffect;
+  this.nextEffect = null;
 
-    index--;
+  this.firstEffect = null;
+  this.lastEffect = null;
+
+  this.expirationTime = NoWork;
+
+  this.alternate = null;
+
+  {
+    this._debugID = debugCounter++;
+    this._debugSource = null;
+    this._debugOwner = null;
+    this._debugIsCurrentlyTiming = false;
+    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
+      Object.preventExtensions(this);
+    }
   }
 }
 
-var describeComponentFrame = function(name, source, ownerName) {
-  return (
-    "\n    in " +
-    (name || "Unknown") +
-    (source
-      ? " (at " +
-        source.fileName.replace(/^.*[\\\/]/, "") +
-        ":" +
-        source.lineNumber +
-        ")"
-      : ownerName ? " (created by " + ownerName + ")" : "")
-  );
+// This is a constructor function, rather than a POJO constructor, still
+// please ensure we do the following:
+// 1) Nobody should add any instance methods on this. Instance methods can be
+//    more difficult to predict when they get optimized and they are almost
+//    never inlined properly in static compilers.
+// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
+//    always know when it is a fiber.
+// 3) We might want to experiment with using numeric keys since they are easier
+//    to optimize in a non-JIT environment.
+// 4) We can easily go from a constructor to a createFiber object literal if that
+//    is faster.
+// 5) It should be easy to port this to a C struct and keep a C implementation
+//    compatible.
+var createFiber = function(tag, pendingProps, key, mode) {
+  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
+  return new FiberNode(tag, pendingProps, key, mode);
 };
 
-function describeFiber(fiber) {
-  switch (fiber.tag) {
-    case IndeterminateComponent:
-    case FunctionalComponent:
-    case ClassComponent:
-    case HostComponent:
-      var owner = fiber._debugOwner;
-      var source = fiber._debugSource;
-      var name = getComponentName(fiber);
-      var ownerName = null;
-      if (owner) {
-        ownerName = getComponentName(owner);
-      }
-      return describeComponentFrame(name, source, ownerName);
-    default:
-      return "";
-  }
+function shouldConstruct(Component) {
+  return !!(Component.prototype && Component.prototype.isReactComponent);
 }
 
-// This function can only be called with a work-in-progress fiber and
-// only during begin or complete phase. Do not call it under any other
-// circumstances.
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  var node = workInProgress;
-  do {
-    info += describeFiber(node);
-    // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
-  } while (node);
-  return info;
-}
+// This is used to create an alternate fiber to do work on.
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  if (workInProgress === null) {
+    // We use a double buffering pooling technique because we know that we'll
+    // only ever need at most two versions of a tree. We pool the "other" unused
+    // node that we're free to reuse. This is lazily created to avoid allocating
+    // extra objects for things that are never updated. It also allow us to
+    // reclaim the extra memory if needed.
+    workInProgress = createFiber(
+      current.tag,
+      pendingProps,
+      current.key,
+      current.mode
+    );
+    workInProgress.type = current.type;
+    workInProgress.stateNode = current.stateNode;
 
-function getCurrentFiberOwnerName() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    var owner = fiber._debugOwner;
-    if (owner !== null && typeof owner !== "undefined") {
-      return getComponentName(owner);
+    {
+      // DEV-only fields
+      workInProgress._debugID = current._debugID;
+      workInProgress._debugSource = current._debugSource;
+      workInProgress._debugOwner = current._debugOwner;
     }
-  }
-  return null;
-}
 
-function getCurrentFiberStackAddendum() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    // Safe because if current fiber exists, we are reconciling,
-    // and it is guaranteed to be the work-in-progress version.
-    return getStackAddendumByWorkInProgressFiber(fiber);
+    workInProgress.alternate = current;
+    current.alternate = workInProgress;
+  } else {
+    workInProgress.pendingProps = pendingProps;
+
+    // We already have an alternate.
+    // Reset the effect tag.
+    workInProgress.effectTag = NoEffect;
+
+    // The effect list is no longer valid.
+    workInProgress.nextEffect = null;
+    workInProgress.firstEffect = null;
+    workInProgress.lastEffect = null;
   }
-  return null;
-}
 
-function resetCurrentFiber() {
-  ReactDebugCurrentFrame.getCurrentStack = null;
-  ReactDebugCurrentFiber.current = null;
-  ReactDebugCurrentFiber.phase = null;
-}
+  workInProgress.expirationTime = expirationTime;
 
-function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
-  ReactDebugCurrentFiber.current = fiber;
-  ReactDebugCurrentFiber.phase = null;
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+
+  // These will be overridden during the parent's reconciliation
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+
+  return workInProgress;
 }
 
-function setCurrentPhase(phase) {
-  ReactDebugCurrentFiber.phase = phase;
+function createHostRootFiber(isAsync) {
+  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
+  return createFiber(HostRoot, null, null, mode);
 }
 
-var ReactDebugCurrentFiber = {
-  current: null,
-  phase: null,
-  resetCurrentFiber: resetCurrentFiber,
-  setCurrentFiber: setCurrentFiber,
-  setCurrentPhase: setCurrentPhase,
-  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
-};
-
-// Re-export dynamic flags from the fbsource version.
-var _require = require("ReactFeatureFlags");
-
-var enableGetDerivedStateFromCatch = _require.enableGetDerivedStateFromCatch;
-var debugRenderPhaseSideEffects = _require.debugRenderPhaseSideEffects;
-var debugRenderPhaseSideEffectsForStrictMode =
-  _require.debugRenderPhaseSideEffectsForStrictMode;
-var warnAboutDeprecatedLifecycles = _require.warnAboutDeprecatedLifecycles;
-var replayFailedUnitOfWorkWithInvokeGuardedCallback =
-  _require.replayFailedUnitOfWorkWithInvokeGuardedCallback;
-
-var enableUserTimingAPI = true;
-var enableMutatingReconciler = true;
-var enableNoopReconciler = false;
-var enablePersistentReconciler = false;
-
-// Only used in www builds.
-
-// Prefix measurements so that it's possible to filter them.
-// Longer prefixes are hard to read in DevTools.
-var reactEmoji = "\u269B";
-var warningEmoji = "\u26D4";
-var supportsUserTiming =
-  typeof performance !== "undefined" &&
-  typeof performance.mark === "function" &&
-  typeof performance.clearMarks === "function" &&
-  typeof performance.measure === "function" &&
-  typeof performance.clearMeasures === "function";
-
-// Keep track of current fiber so that we know the path to unwind on pause.
-// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
-var currentFiber = null;
-// If we're in the middle of user code, which fiber and method is it?
-// Reusing `currentFiber` would be confusing for this because user code fiber
-// can change during commit phase too, but we don't need to unwind it (since
-// lifecycles in the commit phase don't resemble a tree).
-var currentPhase = null;
-var currentPhaseFiber = null;
-// Did lifecycle hook schedule an update? This is often a performance problem,
-// so we will keep track of it, and include it in the report.
-// Track commits caused by cascading updates.
-var isCommitting = false;
-var hasScheduledUpdateInCurrentCommit = false;
-var hasScheduledUpdateInCurrentPhase = false;
-var commitCountInCurrentWorkLoop = 0;
-var effectCountInCurrentCommit = 0;
-var isWaitingForCallback = false;
-// During commits, we only show a measurement once per method name
-// to avoid stretch the commit phase with measurement overhead.
-var labelsInCurrentCommit = new Set();
-
-var formatMarkName = function(markName) {
-  return reactEmoji + " " + markName;
-};
-
-var formatLabel = function(label, warning$$1) {
-  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
-  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
-  return "" + prefix + label + suffix;
-};
-
-var beginMark = function(markName) {
-  performance.mark(formatMarkName(markName));
-};
-
-var clearMark = function(markName) {
-  performance.clearMarks(formatMarkName(markName));
-};
-
-var endMark = function(label, markName, warning$$1) {
-  var formattedMarkName = formatMarkName(markName);
-  var formattedLabel = formatLabel(label, warning$$1);
-  try {
-    performance.measure(formattedLabel, formattedMarkName);
-  } catch (err) {}
-  // If previous mark was missing for some reason, this will throw.
-  // This could only happen if React crashed in an unexpected place earlier.
-  // Don't pile on with more errors.
-
-  // Clear marks immediately to avoid growing buffer.
-  performance.clearMarks(formattedMarkName);
-  performance.clearMeasures(formattedLabel);
-};
-
-var getFiberMarkName = function(label, debugID) {
-  return label + " (#" + debugID + ")";
-};
-
-var getFiberLabel = function(componentName, isMounted, phase) {
-  if (phase === null) {
-    // These are composite component total time measurements.
-    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
-  } else {
-    // Composite component methods.
-    return componentName + "." + phase;
-  }
-};
-
-var beginFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-
-  if (isCommitting && labelsInCurrentCommit.has(label)) {
-    // During the commit phase, we don't show duplicate labels because
-    // there is a fixed overhead for every measurement, and we don't
-    // want to stretch the commit phase beyond necessary.
-    return false;
-  }
-  labelsInCurrentCommit.add(label);
-
-  var markName = getFiberMarkName(label, debugID);
-  beginMark(markName);
-  return true;
-};
-
-var clearFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  clearMark(markName);
-};
-
-var endFiberMark = function(fiber, phase, warning$$1) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  endMark(label, markName, warning$$1);
-};
-
-var shouldIgnoreFiber = function(fiber) {
-  // Host components should be skipped in the timeline.
-  // We could check typeof fiber.type, but does this work with RN?
-  switch (fiber.tag) {
-    case HostRoot:
-    case HostComponent:
-    case HostText:
-    case HostPortal:
-    case CallComponent:
-    case ReturnComponent:
-    case Fragment:
-    case ContextProvider:
-    case ContextConsumer:
-      return true;
-    default:
-      return false;
-  }
-};
-
-var clearPendingPhaseMeasurement = function() {
-  if (currentPhase !== null && currentPhaseFiber !== null) {
-    clearFiberMark(currentPhaseFiber, currentPhase);
-  }
-  currentPhaseFiber = null;
-  currentPhase = null;
-  hasScheduledUpdateInCurrentPhase = false;
-};
-
-var pauseTimers = function() {
-  // Stops all currently active measurements so that they can be resumed
-  // if we continue in a later deferred loop from the same unit of work.
-  var fiber = currentFiber;
-  while (fiber) {
-    if (fiber._debugIsCurrentlyTiming) {
-      endFiberMark(fiber, null, null);
-    }
-    fiber = fiber["return"];
-  }
-};
-
-var resumeTimersRecursively = function(fiber) {
-  if (fiber["return"] !== null) {
-    resumeTimersRecursively(fiber["return"]);
-  }
-  if (fiber._debugIsCurrentlyTiming) {
-    beginFiberMark(fiber, null);
-  }
-};
-
-var resumeTimers = function() {
-  // Resumes all measurements that were active during the last deferred loop.
-  if (currentFiber !== null) {
-    resumeTimersRecursively(currentFiber);
-  }
-};
-
-function recordEffect() {
-  if (enableUserTimingAPI) {
-    effectCountInCurrentCommit++;
-  }
-}
-
-function recordScheduleUpdate() {
-  if (enableUserTimingAPI) {
-    if (isCommitting) {
-      hasScheduledUpdateInCurrentCommit = true;
-    }
-    if (
-      currentPhase !== null &&
-      currentPhase !== "componentWillMount" &&
-      currentPhase !== "componentWillReceiveProps"
-    ) {
-      hasScheduledUpdateInCurrentPhase = true;
-    }
-  }
-}
-
-function startRequestCallbackTimer() {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming && !isWaitingForCallback) {
-      isWaitingForCallback = true;
-      beginMark("(Waiting for async callback...)");
-    }
-  }
-}
-
-function stopRequestCallbackTimer(didExpire) {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming) {
-      isWaitingForCallback = false;
-      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
-      endMark(
-        "(Waiting for async callback...)",
-        "(Waiting for async callback...)",
-        warning$$1
-      );
-    }
-  }
-}
-
-function startWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, this is the fiber to unwind from.
-    currentFiber = fiber;
-    if (!beginFiberMark(fiber, null)) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = true;
-  }
-}
-
-function cancelWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // Remember we shouldn't complete measurement for this fiber.
-    // Otherwise flamechart will be deep even for small updates.
-    fiber._debugIsCurrentlyTiming = false;
-    clearFiberMark(fiber, null);
-  }
-}
-
-function stopWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    endFiberMark(fiber, null, null);
-  }
-}
-
-function stopFailedWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    var warning$$1 = "An error was thrown inside this error boundary";
-    endFiberMark(fiber, null, warning$$1);
-  }
-}
-
-function startPhaseTimer(fiber, phase) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    clearPendingPhaseMeasurement();
-    if (!beginFiberMark(fiber, phase)) {
-      return;
-    }
-    currentPhaseFiber = fiber;
-    currentPhase = phase;
-  }
-}
-
-function stopPhaseTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    if (currentPhase !== null && currentPhaseFiber !== null) {
-      var warning$$1 = hasScheduledUpdateInCurrentPhase
-        ? "Scheduled a cascading update"
-        : null;
-      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
-    }
-    currentPhase = null;
-    currentPhaseFiber = null;
-  }
-}
-
-function startWorkLoopTimer(nextUnitOfWork) {
-  if (enableUserTimingAPI) {
-    currentFiber = nextUnitOfWork;
-    if (!supportsUserTiming) {
-      return;
-    }
-    commitCountInCurrentWorkLoop = 0;
-    // This is top level call.
-    // Any other measurements are performed within.
-    beginMark("(React Tree Reconciliation)");
-    // Resume any measurements that were in progress during the last loop.
-    resumeTimers();
-  }
-}
-
-function stopWorkLoopTimer(interruptedBy) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var warning$$1 = null;
-    if (interruptedBy !== null) {
-      if (interruptedBy.tag === HostRoot) {
-        warning$$1 = "A top-level update interrupted the previous render";
-      } else {
-        var componentName = getComponentName(interruptedBy) || "Unknown";
-        warning$$1 =
-          "An update to " + componentName + " interrupted the previous render";
-      }
-    } else if (commitCountInCurrentWorkLoop > 1) {
-      warning$$1 = "There were cascading updates";
-    }
-    commitCountInCurrentWorkLoop = 0;
-    // Pause any measurements until the next loop.
-    pauseTimers();
-    endMark(
-      "(React Tree Reconciliation)",
-      "(React Tree Reconciliation)",
-      warning$$1
-    );
-  }
-}
-
-function startCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    isCommitting = true;
-    hasScheduledUpdateInCurrentCommit = false;
-    labelsInCurrentCommit.clear();
-    beginMark("(Committing Changes)");
-  }
-}
-
-function stopCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-
-    var warning$$1 = null;
-    if (hasScheduledUpdateInCurrentCommit) {
-      warning$$1 = "Lifecycle hook scheduled a cascading update";
-    } else if (commitCountInCurrentWorkLoop > 0) {
-      warning$$1 = "Caused by a cascading update in earlier commit";
-    }
-    hasScheduledUpdateInCurrentCommit = false;
-    commitCountInCurrentWorkLoop++;
-    isCommitting = false;
-    labelsInCurrentCommit.clear();
-
-    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
-  }
-}
-
-function startCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Host Effects)");
-  }
-}
-
-function stopCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Host Effects: " + count + " Total)",
-      "(Committing Host Effects)",
-      null
-    );
+function createFiberFromElement(element, mode, expirationTime) {
+  var owner = null;
+  {
+    owner = element._owner;
   }
-}
 
-function startCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Calling Lifecycle Methods)");
-  }
-}
+  var fiber = void 0;
+  var type = element.type;
+  var key = element.key;
+  var pendingProps = element.props;
 
-function stopCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
+  var fiberTag = void 0;
+  if (typeof type === "function") {
+    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
+  } else if (typeof type === "string") {
+    fiberTag = HostComponent;
+  } else {
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          pendingProps.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= AsyncMode | StrictMode;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= StrictMode;
+        break;
+      case REACT_CALL_TYPE:
+        fiberTag = CallComponent;
+        break;
+      case REACT_RETURN_TYPE:
+        fiberTag = ReturnComponent;
+        break;
+      default: {
+        if (typeof type === "object" && type !== null) {
+          switch (type.$$typeof) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = ContextProvider;
+              break;
+            case REACT_CONTEXT_TYPE:
+              // This is a consumer
+              fiberTag = ContextConsumer;
+              break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = ForwardRef;
+              break;
+            default:
+              if (typeof type.tag === "number") {
+                // Currently assumed to be a continuation and therefore is a
+                // fiber already.
+                // TODO: The yield system is currently broken for updates in
+                // some cases. The reified yield stores a fiber, but we don't
+                // know which fiber that is; the current or a workInProgress?
+                // When the continuation gets rendered here we don't know if we
+                // can reuse that fiber or if we need to clone it. There is
+                // probably a clever way to restructure this.
+                fiber = type;
+                fiber.pendingProps = pendingProps;
+                fiber.expirationTime = expirationTime;
+                return fiber;
+              } else {
+                throwOnInvalidElementType(type, owner);
+              }
+              break;
+          }
+        } else {
+          throwOnInvalidElementType(type, owner);
+        }
+      }
     }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Calling Lifecycle Methods: " + count + " Total)",
-      "(Calling Lifecycle Methods)",
-      null
-    );
   }
-}
 
-var warnedAboutMissingGetChildContext = void 0;
-
-{
-  warnedAboutMissingGetChildContext = {};
-}
-
-// A cursor to the current merged context object on the stack.
-var contextStackCursor = createCursor(emptyObject);
-// A cursor to a boolean indicating whether the context has changed.
-var didPerformWorkStackCursor = createCursor(false);
-// Keep track of the previous context object that was on the stack.
-// We use this to get access to the parent context after we have already
-// pushed the next context provider, and now need to merge their contexts.
-var previousContext = emptyObject;
+  fiber = createFiber(fiberTag, pendingProps, key, mode);
+  fiber.type = type;
+  fiber.expirationTime = expirationTime;
 
-function getUnmaskedContext(workInProgress) {
-  var hasOwnContext = isContextProvider(workInProgress);
-  if (hasOwnContext) {
-    // If the fiber is a context provider itself, when we read its context
-    // we have already pushed its own child context on the stack. A context
-    // provider should not "see" its own child context. Therefore we read the
-    // previous (parent) context instead for a context provider.
-    return previousContext;
+  {
+    fiber._debugSource = element._source;
+    fiber._debugOwner = element._owner;
   }
-  return contextStackCursor.current;
-}
 
-function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-  var instance = workInProgress.stateNode;
-  instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-  instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  return fiber;
 }
 
-function getMaskedContext(workInProgress, unmaskedContext) {
-  var type = workInProgress.type;
-  var contextTypes = type.contextTypes;
-  if (!contextTypes) {
-    return emptyObject;
-  }
-
-  // Avoid recreating masked context unless unmasked context has changed.
-  // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
-  // This may trigger infinite loops if componentWillReceiveProps calls setState.
-  var instance = workInProgress.stateNode;
-  if (
-    instance &&
-    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-  ) {
-    return instance.__reactInternalMemoizedMaskedChildContext;
-  }
-
-  var context = {};
-  for (var key in contextTypes) {
-    context[key] = unmaskedContext[key];
-  }
-
+function throwOnInvalidElementType(type, owner) {
+  var info = "";
   {
-    var name = getComponentName(workInProgress) || "Unknown";
-    checkPropTypes(
-      contextTypes,
-      context,
-      "context",
-      name,
-      ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-    );
-  }
-
-  // Cache unmasked context so we can avoid recreating masked context unless necessary.
-  // Context is created before the class component is instantiated so check for instance.
-  if (instance) {
-    cacheContext(workInProgress, unmaskedContext, context);
+    if (
+      type === undefined ||
+      (typeof type === "object" &&
+        type !== null &&
+        Object.keys(type).length === 0)
+    ) {
+      info +=
+        " You likely forgot to export your component from the file " +
+        "it's defined in, or you might have mixed up default and " +
+        "named imports.";
+    }
+    var ownerName = owner ? getComponentName(owner) : null;
+    if (ownerName) {
+      info += "\n\nCheck the render method of `" + ownerName + "`.";
+    }
   }
-
-  return context;
-}
-
-function hasContextChanged() {
-  return didPerformWorkStackCursor.current;
+  invariant(
+    false,
+    "Element type is invalid: expected a string (for built-in " +
+      "components) or a class/function (for composite components) " +
+      "but got: %s.%s",
+    type == null ? type : typeof type,
+    info
+  );
 }
 
-function isContextConsumer(fiber) {
-  return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  var fiber = createFiber(Fragment, elements, key, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
 }
 
-function isContextProvider(fiber) {
-  return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+function createFiberFromText(content, mode, expirationTime) {
+  var fiber = createFiber(HostText, content, null, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
 }
 
-function popContextProvider(fiber) {
-  if (!isContextProvider(fiber)) {
-    return;
-  }
-
-  pop(didPerformWorkStackCursor, fiber);
-  pop(contextStackCursor, fiber);
+function createFiberFromHostInstanceForDeletion() {
+  var fiber = createFiber(HostComponent, null, null, NoContext);
+  fiber.type = "DELETED";
+  return fiber;
 }
 
-function popTopLevelContextObject(fiber) {
-  pop(didPerformWorkStackCursor, fiber);
-  pop(contextStackCursor, fiber);
+function createFiberFromPortal(portal, mode, expirationTime) {
+  var pendingProps = portal.children !== null ? portal.children : [];
+  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null, // Used by persistent updates
+    implementation: portal.implementation
+  };
+  return fiber;
 }
 
-function pushTopLevelContextObject(fiber, context, didChange) {
-  invariant(
-    contextStackCursor.cursor == null,
-    "Unexpected context found on stack. " +
-      "This error is likely caused by a bug in React. Please file an issue."
-  );
+// TODO: This should be lifted into the renderer.
 
-  push(contextStackCursor, context, fiber);
-  push(didPerformWorkStackCursor, didChange, fiber);
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  // Cyclic construction. This cheats the type system right now because
+  // stateNode is any.
+  var uninitializedFiber = createHostRootFiber(isAsync);
+  var root = {
+    current: uninitializedFiber,
+    containerInfo: containerInfo,
+    pendingChildren: null,
+    pendingCommitExpirationTime: NoWork,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    remainingExpirationTime: NoWork,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  uninitializedFiber.stateNode = root;
+  return root;
 }
 
-function processChildContext(fiber, parentContext) {
-  var instance = fiber.stateNode;
-  var childContextTypes = fiber.type.childContextTypes;
-
-  // TODO (bvaughn) Replace this behavior with an invariant() in the future.
-  // It has only been added in Fiber to match the (unintentional) behavior in Stack.
-  if (typeof instance.getChildContext !== "function") {
-    {
-      var componentName = getComponentName(fiber) || "Unknown";
+var onCommitFiberRoot = null;
+var onCommitFiberUnmount = null;
+var hasLoggedError = false;
 
-      if (!warnedAboutMissingGetChildContext[componentName]) {
-        warnedAboutMissingGetChildContext[componentName] = true;
-        warning(
-          false,
-          "%s.childContextTypes is specified but there is no getChildContext() method " +
-            "on the instance. You can either define getChildContext() on %s or remove " +
-            "childContextTypes from it.",
-          componentName,
-          componentName
-        );
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {
+      if (true && !hasLoggedError) {
+        hasLoggedError = true;
+        warning(false, "React DevTools encountered an error: %s", err);
       }
     }
-    return parentContext;
-  }
+  };
+}
 
-  var childContext = void 0;
-  {
-    ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
-  }
-  startPhaseTimer(fiber, "getChildContext");
-  childContext = instance.getChildContext();
-  stopPhaseTimer();
-  {
-    ReactDebugCurrentFiber.setCurrentPhase(null);
+function injectInternals(internals) {
+  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
+    // No DevTools
+    return false;
   }
-  for (var contextKey in childContext) {
-    invariant(
-      contextKey in childContextTypes,
-      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-      getComponentName(fiber) || "Unknown",
-      contextKey
-    );
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled) {
+    // This isn't a real property on the hook, but it can be set to opt out
+    // of DevTools integration and associated warnings and logs.
+    // https://github.com/facebook/react/issues/3877
+    return true;
   }
-  {
-    var name = getComponentName(fiber) || "Unknown";
-    checkPropTypes(
-      childContextTypes,
-      childContext,
-      "child context",
-      name,
-      // In practice, there is one case in which we won't get a stack. It's when
-      // somebody calls unstable_renderSubtreeIntoContainer() and we process
-      // context from the parent component instance. The stack will be missing
-      // because it's outside of the reconciliation, and so the pointer has not
-      // been set. This is rare and doesn't matter. We'll also remove that API.
-      ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-    );
+  if (!hook.supportsFiber) {
+    {
+      warning(
+        false,
+        "The installed version of React DevTools is too old and will not work " +
+          "with the current version of React. Please update React DevTools. " +
+          "https://fb.me/react-devtools"
+      );
+    }
+    // DevTools exists, even though it doesn't support Fiber.
+    return true;
   }
-
-  return Object.assign({}, parentContext, childContext);
-}
-
-function pushContextProvider(workInProgress) {
-  if (!isContextProvider(workInProgress)) {
-    return false;
+  try {
+    var rendererID = hook.inject(internals);
+    // We have successfully injected, so now it is safe to set up hooks.
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {
+    // Catch all errors because it is unsafe to throw during initialization.
+    {
+      warning(false, "React DevTools encountered an error: %s.", err);
+    }
   }
-
-  var instance = workInProgress.stateNode;
-  // We push the context as early as possible to ensure stack integrity.
-  // If the instance does not exist yet, we will push null at first,
-  // and replace it on the stack later when invalidating the context.
-  var memoizedMergedChildContext =
-    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-    emptyObject;
-
-  // Remember the parent context so we can merge with it later.
-  // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
-  previousContext = contextStackCursor.current;
-  push(contextStackCursor, memoizedMergedChildContext, workInProgress);
-  push(
-    didPerformWorkStackCursor,
-    didPerformWorkStackCursor.current,
-    workInProgress
-  );
-
+  // DevTools exists
   return true;
 }
 
-function invalidateContextProvider(workInProgress, didChange) {
-  var instance = workInProgress.stateNode;
-  invariant(
-    instance,
-    "Expected to have an instance by this point. " +
-      "This error is likely caused by a bug in React. Please file an issue."
-  );
-
-  if (didChange) {
-    // Merge parent and own context.
-    // Skip this if we're not updating due to sCU.
-    // This avoids unnecessarily recomputing memoized values.
-    var mergedContext = processChildContext(workInProgress, previousContext);
-    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-
-    // Replace the old (or empty) context with the new one.
-    // It is important to unwind the context in the reverse order.
-    pop(didPerformWorkStackCursor, workInProgress);
-    pop(contextStackCursor, workInProgress);
-    // Now push the new context and mark that it has changed.
-    push(contextStackCursor, mergedContext, workInProgress);
-    push(didPerformWorkStackCursor, didChange, workInProgress);
-  } else {
-    pop(didPerformWorkStackCursor, workInProgress);
-    push(didPerformWorkStackCursor, didChange, workInProgress);
+function onCommitRoot(root) {
+  if (typeof onCommitFiberRoot === "function") {
+    onCommitFiberRoot(root);
   }
 }
 
-function resetContext() {
-  previousContext = emptyObject;
-  contextStackCursor.current = emptyObject;
-  didPerformWorkStackCursor.current = false;
-}
-
-function findCurrentUnmaskedContext(fiber) {
-  // Currently this is only used with renderSubtreeIntoContainer; not sure if it
-  // makes sense elsewhere
-  invariant(
-    isFiberMounted(fiber) && fiber.tag === ClassComponent,
-    "Expected subtree parent to be a mounted class component. " +
-      "This error is likely caused by a bug in React. Please file an issue."
-  );
-
-  var node = fiber;
-  while (node.tag !== HostRoot) {
-    if (isContextProvider(node)) {
-      return node.stateNode.__reactInternalMemoizedMergedChildContext;
-    }
-    var parent = node["return"];
-    invariant(
-      parent,
-      "Found unexpected detached subtree parent. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-    node = parent;
+function onCommitUnmount(fiber) {
+  if (typeof onCommitFiberUnmount === "function") {
+    onCommitFiberUnmount(fiber);
   }
-  return node.stateNode.context;
-}
-
-// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
-// Math.pow(2, 30) - 1
-// 0b111111111111111111111111111111
-var MAX_SIGNED_31_BIT_INT = 1073741823;
-
-// TODO: Use an opaque type once ESLint et al support the syntax
-
-var NoWork = 0;
-var Sync = 1;
-var Never = MAX_SIGNED_31_BIT_INT;
-
-var UNIT_SIZE = 10;
-var MAGIC_NUMBER_OFFSET = 2;
-
-// 1 unit of expiration time represents 10ms.
-function msToExpirationTime(ms) {
-  // Always add an offset so that we don't clash with the magic number for NoWork.
-  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
-}
-
-function expirationTimeToMs(expirationTime) {
-  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
-}
-
-function ceiling(num, precision) {
-  return (((num / precision) | 0) + 1) * precision;
 }
 
-function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
-  return ceiling(
-    currentTime + expirationInMs / UNIT_SIZE,
-    bucketSizeMs / UNIT_SIZE
+var describeComponentFrame = function(name, source, ownerName) {
+  return (
+    "\n    in " +
+    (name || "Unknown") +
+    (source
+      ? " (at " +
+        source.fileName.replace(/^.*[\\\/]/, "") +
+        ":" +
+        source.lineNumber +
+        ")"
+      : ownerName ? " (created by " + ownerName + ")" : "")
   );
-}
-
-var NoContext = 0;
-var AsyncMode = 1;
-var StrictMode = 2;
-
-var hasBadMapPolyfill = void 0;
+};
 
-{
-  hasBadMapPolyfill = false;
-  try {
-    var nonExtensibleObject = Object.preventExtensions({});
-    var testMap = new Map([[nonExtensibleObject, null]]);
-    var testSet = new Set([nonExtensibleObject]);
-    // This is necessary for Rollup to not consider these unused.
-    // https://github.com/rollup/rollup/issues/1771
-    // TODO: we can remove these if Rollup fixes the bug.
-    testMap.set(0, 0);
-    testSet.add(0);
-  } catch (e) {
-    // TODO: Consider warning about bad polyfills
-    hasBadMapPolyfill = true;
+function describeFiber(fiber) {
+  switch (fiber.tag) {
+    case IndeterminateComponent:
+    case FunctionalComponent:
+    case ClassComponent:
+    case HostComponent:
+      var owner = fiber._debugOwner;
+      var source = fiber._debugSource;
+      var name = getComponentName(fiber);
+      var ownerName = null;
+      if (owner) {
+        ownerName = getComponentName(owner);
+      }
+      return describeComponentFrame(name, source, ownerName);
+    default:
+      return "";
   }
 }
 
-// A Fiber is work on a Component that needs to be done or was done. There can
-// be more than one per component.
-
-var debugCounter = void 0;
-
-{
-  debugCounter = 1;
+// This function can only be called with a work-in-progress fiber and
+// only during begin or complete phase. Do not call it under any other
+// circumstances.
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  var node = workInProgress;
+  do {
+    info += describeFiber(node);
+    // Otherwise this return pointer might point to the wrong tree:
+    node = node["return"];
+  } while (node);
+  return info;
 }
 
-function FiberNode(tag, pendingProps, key, mode) {
-  // Instance
-  this.tag = tag;
-  this.key = key;
-  this.type = null;
-  this.stateNode = null;
-
-  // Fiber
-  this["return"] = null;
-  this.child = null;
-  this.sibling = null;
-  this.index = 0;
-
-  this.ref = null;
-
-  this.pendingProps = pendingProps;
-  this.memoizedProps = null;
-  this.updateQueue = null;
-  this.memoizedState = null;
-
-  this.mode = mode;
+/**
+ * Forked from fbjs/warning:
+ * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
+ *
+ * Only change is we use console.warn instead of console.error,
+ * and do nothing when 'console' is not supported.
+ * This really simplifies the code.
+ * ---
+ * Similar to invariant but only logs a warning if the condition is not met.
+ * This can be used to log issues in development environments in critical
+ * paths. Removing the logging code for production environments will keep the
+ * same logic and follow the same code paths.
+ */
 
-  // Effects
-  this.effectTag = NoEffect;
-  this.nextEffect = null;
+var lowPriorityWarning = function() {};
 
-  this.firstEffect = null;
-  this.lastEffect = null;
+{
+  var printWarning = function(format) {
+    for (
+      var _len = arguments.length,
+        args = Array(_len > 1 ? _len - 1 : 0),
+        _key = 1;
+      _key < _len;
+      _key++
+    ) {
+      args[_key - 1] = arguments[_key];
+    }
 
-  this.expirationTime = NoWork;
+    var argIndex = 0;
+    var message =
+      "Warning: " +
+      format.replace(/%s/g, function() {
+        return args[argIndex++];
+      });
+    if (typeof console !== "undefined") {
+      console.warn(message);
+    }
+    try {
+      // --- Welcome to debugging React ---
+      // This error was thrown as a convenience so that you can use this stack
+      // to find the callsite that caused this warning to fire.
+      throw new Error(message);
+    } catch (x) {}
+  };
 
-  this.alternate = null;
+  lowPriorityWarning = function(condition, format) {
+    if (format === undefined) {
+      throw new Error(
+        "`warning(condition, format, ...args)` requires a warning " +
+          "message argument"
+      );
+    }
+    if (!condition) {
+      for (
+        var _len2 = arguments.length,
+          args = Array(_len2 > 2 ? _len2 - 2 : 0),
+          _key2 = 2;
+        _key2 < _len2;
+        _key2++
+      ) {
+        args[_key2 - 2] = arguments[_key2];
+      }
 
-  {
-    this._debugID = debugCounter++;
-    this._debugSource = null;
-    this._debugOwner = null;
-    this._debugIsCurrentlyTiming = false;
-    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
-      Object.preventExtensions(this);
+      printWarning.apply(undefined, [format].concat(args));
     }
-  }
+  };
 }
 
-// This is a constructor function, rather than a POJO constructor, still
-// please ensure we do the following:
-// 1) Nobody should add any instance methods on this. Instance methods can be
-//    more difficult to predict when they get optimized and they are almost
-//    never inlined properly in static compilers.
-// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
-//    always know when it is a fiber.
-// 3) We might want to experiment with using numeric keys since they are easier
-//    to optimize in a non-JIT environment.
-// 4) We can easily go from a constructor to a createFiber object literal if that
-//    is faster.
-// 5) It should be easy to port this to a C struct and keep a C implementation
-//    compatible.
-var createFiber = function(tag, pendingProps, key, mode) {
-  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
-  return new FiberNode(tag, pendingProps, key, mode);
-};
+var lowPriorityWarning$1 = lowPriorityWarning;
 
-function shouldConstruct(Component) {
-  return !!(Component.prototype && Component.prototype.isReactComponent);
-}
+var ReactStrictModeWarnings = {
+  discardPendingWarnings: function() {},
+  flushPendingDeprecationWarnings: function() {},
+  flushPendingUnsafeLifecycleWarnings: function() {},
+  recordDeprecationWarnings: function(fiber, instance) {},
+  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
+};
 
-// This is used to create an alternate fiber to do work on.
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  if (workInProgress === null) {
-    // We use a double buffering pooling technique because we know that we'll
-    // only ever need at most two versions of a tree. We pool the "other" unused
-    // node that we're free to reuse. This is lazily created to avoid allocating
-    // extra objects for things that are never updated. It also allow us to
-    // reclaim the extra memory if needed.
-    workInProgress = createFiber(
-      current.tag,
-      pendingProps,
-      current.key,
-      current.mode
-    );
-    workInProgress.type = current.type;
-    workInProgress.stateNode = current.stateNode;
+{
+  var LIFECYCLE_SUGGESTIONS = {
+    UNSAFE_componentWillMount: "componentDidMount",
+    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
+    UNSAFE_componentWillUpdate: "componentDidUpdate"
+  };
 
-    {
-      // DEV-only fields
-      workInProgress._debugID = current._debugID;
-      workInProgress._debugSource = current._debugSource;
-      workInProgress._debugOwner = current._debugOwner;
-    }
+  var pendingComponentWillMountWarnings = [];
+  var pendingComponentWillReceivePropsWarnings = [];
+  var pendingComponentWillUpdateWarnings = [];
+  var pendingUnsafeLifecycleWarnings = new Map();
 
-    workInProgress.alternate = current;
-    current.alternate = workInProgress;
-  } else {
-    workInProgress.pendingProps = pendingProps;
+  // Tracks components we have already warned about.
+  var didWarnAboutDeprecatedLifecycles = new Set();
+  var didWarnAboutUnsafeLifecycles = new Set();
 
-    // We already have an alternate.
-    // Reset the effect tag.
-    workInProgress.effectTag = NoEffect;
+  ReactStrictModeWarnings.discardPendingWarnings = function() {
+    pendingComponentWillMountWarnings = [];
+    pendingComponentWillReceivePropsWarnings = [];
+    pendingComponentWillUpdateWarnings = [];
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
 
-    // The effect list is no longer valid.
-    workInProgress.nextEffect = null;
-    workInProgress.firstEffect = null;
-    workInProgress.lastEffect = null;
-  }
+  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
+    pendingUnsafeLifecycleWarnings.forEach(function(
+      lifecycleWarningsMap,
+      strictRoot
+    ) {
+      var lifecyclesWarningMesages = [];
 
-  workInProgress.expirationTime = expirationTime;
+      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
+        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
+        if (lifecycleWarnings.length > 0) {
+          var componentNames = new Set();
+          lifecycleWarnings.forEach(function(fiber) {
+            componentNames.add(getComponentName(fiber) || "Component");
+            didWarnAboutUnsafeLifecycles.add(fiber.type);
+          });
 
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
+          var formatted = lifecycle.replace("UNSAFE_", "");
+          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
+          var sortedComponentNames = Array.from(componentNames)
+            .sort()
+            .join(", ");
 
-  // These will be overridden during the parent's reconciliation
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
+          lifecyclesWarningMesages.push(
+            formatted +
+              ": Please update the following components to use " +
+              (suggestion + " instead: " + sortedComponentNames)
+          );
+        }
+      });
 
-  return workInProgress;
-}
+      if (lifecyclesWarningMesages.length > 0) {
+        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+          strictRoot
+        );
 
-function createHostRootFiber(isAsync) {
-  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
-  return createFiber(HostRoot, null, null, mode);
-}
+        warning(
+          false,
+          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
+            "\n\n%s" +
+            "\n\nLearn more about this warning here:" +
+            "\nhttps://fb.me/react-strict-mode-warnings",
+          strictRootComponentStack,
+          lifecyclesWarningMesages.join("\n\n")
+        );
+      }
+    });
 
-function createFiberFromElement(element, mode, expirationTime) {
-  var owner = null;
-  {
-    owner = element._owner;
-  }
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
 
-  var fiber = void 0;
-  var type = element.type;
-  var key = element.key;
-  var pendingProps = element.props;
+  var getStrictRoot = function(fiber) {
+    var maybeStrictRoot = null;
 
-  var fiberTag = void 0;
-  if (typeof type === "function") {
-    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
-  } else if (typeof type === "string") {
-    fiberTag = HostComponent;
-  } else {
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          pendingProps.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= AsyncMode | StrictMode;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= StrictMode;
-        break;
-      case REACT_CALL_TYPE:
-        fiberTag = CallComponent;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = ReturnComponent;
-        break;
-      default: {
-        if (typeof type === "object" && type !== null) {
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = ContextProvider;
-              break;
-            case REACT_CONTEXT_TYPE:
-              // This is a consumer
-              fiberTag = ContextConsumer;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = ForwardRef;
-              break;
-            default:
-              if (typeof type.tag === "number") {
-                // Currently assumed to be a continuation and therefore is a
-                // fiber already.
-                // TODO: The yield system is currently broken for updates in
-                // some cases. The reified yield stores a fiber, but we don't
-                // know which fiber that is; the current or a workInProgress?
-                // When the continuation gets rendered here we don't know if we
-                // can reuse that fiber or if we need to clone it. There is
-                // probably a clever way to restructure this.
-                fiber = type;
-                fiber.pendingProps = pendingProps;
-                fiber.expirationTime = expirationTime;
-                return fiber;
-              } else {
-                throwOnInvalidElementType(type, owner);
-              }
-              break;
-          }
-        } else {
-          throwOnInvalidElementType(type, owner);
-        }
+    while (fiber !== null) {
+      if (fiber.mode & StrictMode) {
+        maybeStrictRoot = fiber;
       }
+
+      fiber = fiber["return"];
+    }
+
+    return maybeStrictRoot;
+  };
+
+  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
+    if (pendingComponentWillMountWarnings.length > 0) {
+      var uniqueNames = new Set();
+      pendingComponentWillMountWarnings.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var sortedNames = Array.from(uniqueNames)
+        .sort()
+        .join(", ");
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillMount is deprecated and will be removed in the next major version. " +
+          "Use componentDidMount instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillMount." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        sortedNames
+      );
+
+      pendingComponentWillMountWarnings = [];
     }
-  }
 
-  fiber = createFiber(fiberTag, pendingProps, key, mode);
-  fiber.type = type;
-  fiber.expirationTime = expirationTime;
+    if (pendingComponentWillReceivePropsWarnings.length > 0) {
+      var _uniqueNames = new Set();
+      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
+        _uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-  {
-    fiber._debugSource = element._source;
-    fiber._debugOwner = element._owner;
-  }
+      var _sortedNames = Array.from(_uniqueNames)
+        .sort()
+        .join(", ");
 
-  return fiber;
-}
+      lowPriorityWarning$1(
+        false,
+        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
+          "Use static getDerivedStateFromProps instead." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames
+      );
 
-function throwOnInvalidElementType(type, owner) {
-  var info = "";
-  {
-    if (
-      type === undefined ||
-      (typeof type === "object" &&
-        type !== null &&
-        Object.keys(type).length === 0)
-    ) {
-      info +=
-        " You likely forgot to export your component from the file " +
-        "it's defined in, or you might have mixed up default and " +
-        "named imports.";
-    }
-    var ownerName = owner ? getComponentName(owner) : null;
-    if (ownerName) {
-      info += "\n\nCheck the render method of `" + ownerName + "`.";
+      pendingComponentWillReceivePropsWarnings = [];
     }
-  }
-  invariant(
-    false,
-    "Element type is invalid: expected a string (for built-in " +
-      "components) or a class/function (for composite components) " +
-      "but got: %s.%s",
-    type == null ? type : typeof type,
-    info
-  );
-}
 
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  var fiber = createFiber(Fragment, elements, key, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
+    if (pendingComponentWillUpdateWarnings.length > 0) {
+      var _uniqueNames2 = new Set();
+      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
+        _uniqueNames2.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-function createFiberFromText(content, mode, expirationTime) {
-  var fiber = createFiber(HostText, content, null, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
+      var _sortedNames2 = Array.from(_uniqueNames2)
+        .sort()
+        .join(", ");
 
-function createFiberFromHostInstanceForDeletion() {
-  var fiber = createFiber(HostComponent, null, null, NoContext);
-  fiber.type = "DELETED";
-  return fiber;
-}
+      lowPriorityWarning$1(
+        false,
+        "componentWillUpdate is deprecated and will be removed in the next major version. " +
+          "Use componentDidUpdate instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillUpdate." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames2
+      );
 
-function createFiberFromPortal(portal, mode, expirationTime) {
-  var pendingProps = portal.children !== null ? portal.children : [];
-  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null, // Used by persistent updates
-    implementation: portal.implementation
+      pendingComponentWillUpdateWarnings = [];
+    }
   };
-  return fiber;
-}
 
-// TODO: This should be lifted into the renderer.
+  ReactStrictModeWarnings.recordDeprecationWarnings = function(
+    fiber,
+    instance
+  ) {
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
+      return;
+    }
 
-function createFiberRoot(containerInfo, isAsync, hydrate) {
-  // Cyclic construction. This cheats the type system right now because
-  // stateNode is any.
-  var uninitializedFiber = createHostRootFiber(isAsync);
-  var root = {
-    current: uninitializedFiber,
-    containerInfo: containerInfo,
-    pendingChildren: null,
-    pendingCommitExpirationTime: NoWork,
-    finishedWork: null,
-    context: null,
-    pendingContext: null,
-    hydrate: hydrate,
-    remainingExpirationTime: NoWork,
-    firstBatch: null,
-    nextScheduledRoot: null
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillMountWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" &&
+      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillReceivePropsWarnings.push(fiber);
+    }
+    if (typeof instance.componentWillUpdate === "function") {
+      pendingComponentWillUpdateWarnings.push(fiber);
+    }
   };
-  uninitializedFiber.stateNode = root;
-  return root;
-}
 
-var onCommitFiberRoot = null;
-var onCommitFiberUnmount = null;
-var hasLoggedError = false;
+  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = getStrictRoot(fiber);
 
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {
-      if (true && !hasLoggedError) {
-        hasLoggedError = true;
-        warning(false, "React DevTools encountered an error: %s", err);
-      }
+    // Dedup strategy: Warn once per component.
+    // This is difficult to track any other way since component names
+    // are often vague and are likely to collide between 3rd party libraries.
+    // An expand property is probably okay to use here since it's DEV-only,
+    // and will only be set in the event of serious warnings.
+    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+      return;
+    }
+
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    // Note that it is sufficient to check for the presence of a
+    // single lifecycle, componentWillMount, with the polyfill flag.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning === true
+    ) {
+      return;
+    }
+
+    var warningsForRoot = void 0;
+    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
+      warningsForRoot = {
+        UNSAFE_componentWillMount: [],
+        UNSAFE_componentWillReceiveProps: [],
+        UNSAFE_componentWillUpdate: []
+      };
+
+      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
+    } else {
+      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
+    }
+
+    var unsafeLifecycles = [];
+    if (
+      typeof instance.componentWillMount === "function" ||
+      typeof instance.UNSAFE_componentWillMount === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillMount");
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" ||
+      typeof instance.UNSAFE_componentWillReceiveProps === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    }
+    if (
+      typeof instance.componentWillUpdate === "function" ||
+      typeof instance.UNSAFE_componentWillUpdate === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
+    }
+
+    if (unsafeLifecycles.length > 0) {
+      unsafeLifecycles.forEach(function(lifecycle) {
+        warningsForRoot[lifecycle].push(fiber);
+      });
     }
   };
 }
 
-function injectInternals(internals) {
-  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
-    // No DevTools
-    return false;
-  }
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled) {
-    // This isn't a real property on the hook, but it can be set to opt out
-    // of DevTools integration and associated warnings and logs.
-    // https://github.com/facebook/react/issues/3877
-    return true;
-  }
-  if (!hook.supportsFiber) {
-    {
-      warning(
-        false,
-        "The installed version of React DevTools is too old and will not work " +
-          "with the current version of React. Please update React DevTools. " +
-          "https://fb.me/react-devtools"
-      );
+// Re-export dynamic flags from the fbsource version.
+var _require = require("ReactFeatureFlags");
+
+var enableGetDerivedStateFromCatch = _require.enableGetDerivedStateFromCatch;
+var debugRenderPhaseSideEffects = _require.debugRenderPhaseSideEffects;
+var debugRenderPhaseSideEffectsForStrictMode =
+  _require.debugRenderPhaseSideEffectsForStrictMode;
+var warnAboutDeprecatedLifecycles = _require.warnAboutDeprecatedLifecycles;
+var replayFailedUnitOfWorkWithInvokeGuardedCallback =
+  _require.replayFailedUnitOfWorkWithInvokeGuardedCallback;
+
+var enableUserTimingAPI = true;
+var enableMutatingReconciler = true;
+var enableNoopReconciler = false;
+var enablePersistentReconciler = false;
+
+// Only used in www builds.
+
+function getCurrentFiberOwnerName() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
     }
-    // DevTools exists, even though it doesn't support Fiber.
-    return true;
-  }
-  try {
-    var rendererID = hook.inject(internals);
-    // We have successfully injected, so now it is safe to set up hooks.
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {
-    // Catch all errors because it is unsafe to throw during initialization.
-    {
-      warning(false, "React DevTools encountered an error: %s.", err);
+    var owner = fiber._debugOwner;
+    if (owner !== null && typeof owner !== "undefined") {
+      return getComponentName(owner);
     }
   }
-  // DevTools exists
-  return true;
+  return null;
 }
 
-function onCommitRoot(root) {
-  if (typeof onCommitFiberRoot === "function") {
-    onCommitFiberRoot(root);
+function getCurrentFiberStackAddendum() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    // Safe because if current fiber exists, we are reconciling,
+    // and it is guaranteed to be the work-in-progress version.
+    return getStackAddendumByWorkInProgressFiber(fiber);
   }
+  return null;
 }
 
-function onCommitUnmount(fiber) {
-  if (typeof onCommitFiberUnmount === "function") {
-    onCommitFiberUnmount(fiber);
-  }
+function resetCurrentFiber() {
+  ReactDebugCurrentFrame.getCurrentStack = null;
+  ReactDebugCurrentFiber.current = null;
+  ReactDebugCurrentFiber.phase = null;
 }
 
-/**
- * Forked from fbjs/warning:
- * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
- *
- * Only change is we use console.warn instead of console.error,
- * and do nothing when 'console' is not supported.
- * This really simplifies the code.
- * ---
- * Similar to invariant but only logs a warning if the condition is not met.
- * This can be used to log issues in development environments in critical
- * paths. Removing the logging code for production environments will keep the
- * same logic and follow the same code paths.
- */
-
-var lowPriorityWarning = function() {};
+function setCurrentFiber(fiber) {
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
+  ReactDebugCurrentFiber.current = fiber;
+  ReactDebugCurrentFiber.phase = null;
+}
 
-{
-  var printWarning = function(format) {
-    for (
-      var _len = arguments.length,
-        args = Array(_len > 1 ? _len - 1 : 0),
-        _key = 1;
-      _key < _len;
-      _key++
-    ) {
-      args[_key - 1] = arguments[_key];
-    }
+function setCurrentPhase(phase) {
+  ReactDebugCurrentFiber.phase = phase;
+}
 
-    var argIndex = 0;
-    var message =
-      "Warning: " +
-      format.replace(/%s/g, function() {
-        return args[argIndex++];
-      });
-    if (typeof console !== "undefined") {
-      console.warn(message);
-    }
-    try {
-      // --- Welcome to debugging React ---
-      // This error was thrown as a convenience so that you can use this stack
-      // to find the callsite that caused this warning to fire.
-      throw new Error(message);
-    } catch (x) {}
-  };
+var ReactDebugCurrentFiber = {
+  current: null,
+  phase: null,
+  resetCurrentFiber: resetCurrentFiber,
+  setCurrentFiber: setCurrentFiber,
+  setCurrentPhase: setCurrentPhase,
+  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
+};
 
-  lowPriorityWarning = function(condition, format) {
-    if (format === undefined) {
-      throw new Error(
-        "`warning(condition, format, ...args)` requires a warning " +
-          "message argument"
-      );
-    }
-    if (!condition) {
-      for (
-        var _len2 = arguments.length,
-          args = Array(_len2 > 2 ? _len2 - 2 : 0),
-          _key2 = 2;
-        _key2 < _len2;
-        _key2++
-      ) {
-        args[_key2 - 2] = arguments[_key2];
-      }
+// Prefix measurements so that it's possible to filter them.
+// Longer prefixes are hard to read in DevTools.
+var reactEmoji = "\u269B";
+var warningEmoji = "\u26D4";
+var supportsUserTiming =
+  typeof performance !== "undefined" &&
+  typeof performance.mark === "function" &&
+  typeof performance.clearMarks === "function" &&
+  typeof performance.measure === "function" &&
+  typeof performance.clearMeasures === "function";
 
-      printWarning.apply(undefined, [format].concat(args));
-    }
-  };
-}
+// Keep track of current fiber so that we know the path to unwind on pause.
+// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
+var currentFiber = null;
+// If we're in the middle of user code, which fiber and method is it?
+// Reusing `currentFiber` would be confusing for this because user code fiber
+// can change during commit phase too, but we don't need to unwind it (since
+// lifecycles in the commit phase don't resemble a tree).
+var currentPhase = null;
+var currentPhaseFiber = null;
+// Did lifecycle hook schedule an update? This is often a performance problem,
+// so we will keep track of it, and include it in the report.
+// Track commits caused by cascading updates.
+var isCommitting = false;
+var hasScheduledUpdateInCurrentCommit = false;
+var hasScheduledUpdateInCurrentPhase = false;
+var commitCountInCurrentWorkLoop = 0;
+var effectCountInCurrentCommit = 0;
+var isWaitingForCallback = false;
+// During commits, we only show a measurement once per method name
+// to avoid stretch the commit phase with measurement overhead.
+var labelsInCurrentCommit = new Set();
 
-var lowPriorityWarning$1 = lowPriorityWarning;
+var formatMarkName = function(markName) {
+  return reactEmoji + " " + markName;
+};
 
-var ReactStrictModeWarnings = {
-  discardPendingWarnings: function() {},
-  flushPendingDeprecationWarnings: function() {},
-  flushPendingUnsafeLifecycleWarnings: function() {},
-  recordDeprecationWarnings: function(fiber, instance) {},
-  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
+var formatLabel = function(label, warning$$1) {
+  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
+  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
+  return "" + prefix + label + suffix;
 };
 
-{
-  var LIFECYCLE_SUGGESTIONS = {
-    UNSAFE_componentWillMount: "componentDidMount",
-    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
-    UNSAFE_componentWillUpdate: "componentDidUpdate"
-  };
+var beginMark = function(markName) {
+  performance.mark(formatMarkName(markName));
+};
 
-  var pendingComponentWillMountWarnings = [];
-  var pendingComponentWillReceivePropsWarnings = [];
-  var pendingComponentWillUpdateWarnings = [];
-  var pendingUnsafeLifecycleWarnings = new Map();
+var clearMark = function(markName) {
+  performance.clearMarks(formatMarkName(markName));
+};
 
-  // Tracks components we have already warned about.
-  var didWarnAboutDeprecatedLifecycles = new Set();
-  var didWarnAboutUnsafeLifecycles = new Set();
+var endMark = function(label, markName, warning$$1) {
+  var formattedMarkName = formatMarkName(markName);
+  var formattedLabel = formatLabel(label, warning$$1);
+  try {
+    performance.measure(formattedLabel, formattedMarkName);
+  } catch (err) {}
+  // If previous mark was missing for some reason, this will throw.
+  // This could only happen if React crashed in an unexpected place earlier.
+  // Don't pile on with more errors.
 
-  ReactStrictModeWarnings.discardPendingWarnings = function() {
-    pendingComponentWillMountWarnings = [];
-    pendingComponentWillReceivePropsWarnings = [];
-    pendingComponentWillUpdateWarnings = [];
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+  // Clear marks immediately to avoid growing buffer.
+  performance.clearMarks(formattedMarkName);
+  performance.clearMeasures(formattedLabel);
+};
 
-  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
-    pendingUnsafeLifecycleWarnings.forEach(function(
-      lifecycleWarningsMap,
-      strictRoot
-    ) {
-      var lifecyclesWarningMesages = [];
+var getFiberMarkName = function(label, debugID) {
+  return label + " (#" + debugID + ")";
+};
 
-      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
-        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
-        if (lifecycleWarnings.length > 0) {
-          var componentNames = new Set();
-          lifecycleWarnings.forEach(function(fiber) {
-            componentNames.add(getComponentName(fiber) || "Component");
-            didWarnAboutUnsafeLifecycles.add(fiber.type);
-          });
+var getFiberLabel = function(componentName, isMounted, phase) {
+  if (phase === null) {
+    // These are composite component total time measurements.
+    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
+  } else {
+    // Composite component methods.
+    return componentName + "." + phase;
+  }
+};
 
-          var formatted = lifecycle.replace("UNSAFE_", "");
-          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = Array.from(componentNames)
-            .sort()
-            .join(", ");
+var beginFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
 
-          lifecyclesWarningMesages.push(
-            formatted +
-              ": Please update the following components to use " +
-              (suggestion + " instead: " + sortedComponentNames)
-          );
-        }
-      });
+  if (isCommitting && labelsInCurrentCommit.has(label)) {
+    // During the commit phase, we don't show duplicate labels because
+    // there is a fixed overhead for every measurement, and we don't
+    // want to stretch the commit phase beyond necessary.
+    return false;
+  }
+  labelsInCurrentCommit.add(label);
 
-      if (lifecyclesWarningMesages.length > 0) {
-        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
-          strictRoot
-        );
+  var markName = getFiberMarkName(label, debugID);
+  beginMark(markName);
+  return true;
+};
 
-        warning(
-          false,
-          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
-            "\n\n%s" +
-            "\n\nLearn more about this warning here:" +
-            "\nhttps://fb.me/react-strict-mode-warnings",
-          strictRootComponentStack,
-          lifecyclesWarningMesages.join("\n\n")
-        );
-      }
-    });
+var clearFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  clearMark(markName);
+};
 
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+var endFiberMark = function(fiber, phase, warning$$1) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  endMark(label, markName, warning$$1);
+};
 
-  var getStrictRoot = function(fiber) {
-    var maybeStrictRoot = null;
+var shouldIgnoreFiber = function(fiber) {
+  // Host components should be skipped in the timeline.
+  // We could check typeof fiber.type, but does this work with RN?
+  switch (fiber.tag) {
+    case HostRoot:
+    case HostComponent:
+    case HostText:
+    case HostPortal:
+    case CallComponent:
+    case ReturnComponent:
+    case Fragment:
+    case ContextProvider:
+    case ContextConsumer:
+      return true;
+    default:
+      return false;
+  }
+};
 
-    while (fiber !== null) {
-      if (fiber.mode & StrictMode) {
-        maybeStrictRoot = fiber;
-      }
+var clearPendingPhaseMeasurement = function() {
+  if (currentPhase !== null && currentPhaseFiber !== null) {
+    clearFiberMark(currentPhaseFiber, currentPhase);
+  }
+  currentPhaseFiber = null;
+  currentPhase = null;
+  hasScheduledUpdateInCurrentPhase = false;
+};
 
-      fiber = fiber["return"];
+var pauseTimers = function() {
+  // Stops all currently active measurements so that they can be resumed
+  // if we continue in a later deferred loop from the same unit of work.
+  var fiber = currentFiber;
+  while (fiber) {
+    if (fiber._debugIsCurrentlyTiming) {
+      endFiberMark(fiber, null, null);
     }
+    fiber = fiber["return"];
+  }
+};
 
-    return maybeStrictRoot;
-  };
-
-  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
-    if (pendingComponentWillMountWarnings.length > 0) {
-      var uniqueNames = new Set();
-      pendingComponentWillMountWarnings.forEach(function(fiber) {
-        uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+var resumeTimersRecursively = function(fiber) {
+  if (fiber["return"] !== null) {
+    resumeTimersRecursively(fiber["return"]);
+  }
+  if (fiber._debugIsCurrentlyTiming) {
+    beginFiberMark(fiber, null);
+  }
+};
 
-      var sortedNames = Array.from(uniqueNames)
-        .sort()
-        .join(", ");
+var resumeTimers = function() {
+  // Resumes all measurements that were active during the last deferred loop.
+  if (currentFiber !== null) {
+    resumeTimersRecursively(currentFiber);
+  }
+};
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillMount is deprecated and will be removed in the next major version. " +
-          "Use componentDidMount instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillMount." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        sortedNames
-      );
+function recordEffect() {
+  if (enableUserTimingAPI) {
+    effectCountInCurrentCommit++;
+  }
+}
 
-      pendingComponentWillMountWarnings = [];
+function recordScheduleUpdate() {
+  if (enableUserTimingAPI) {
+    if (isCommitting) {
+      hasScheduledUpdateInCurrentCommit = true;
     }
+    if (
+      currentPhase !== null &&
+      currentPhase !== "componentWillMount" &&
+      currentPhase !== "componentWillReceiveProps"
+    ) {
+      hasScheduledUpdateInCurrentPhase = true;
+    }
+  }
+}
 
-    if (pendingComponentWillReceivePropsWarnings.length > 0) {
-      var _uniqueNames = new Set();
-      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
-        _uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames = Array.from(_uniqueNames)
-        .sort()
-        .join(", ");
+function startRequestCallbackTimer() {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming && !isWaitingForCallback) {
+      isWaitingForCallback = true;
+      beginMark("(Waiting for async callback...)");
+    }
+  }
+}
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
-          "Use static getDerivedStateFromProps instead." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames
+function stopRequestCallbackTimer(didExpire) {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming) {
+      isWaitingForCallback = false;
+      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
+      endMark(
+        "(Waiting for async callback...)",
+        "(Waiting for async callback...)",
+        warning$$1
       );
-
-      pendingComponentWillReceivePropsWarnings = [];
     }
+  }
+}
 
-    if (pendingComponentWillUpdateWarnings.length > 0) {
-      var _uniqueNames2 = new Set();
-      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
-        _uniqueNames2.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames2 = Array.from(_uniqueNames2)
-        .sort()
-        .join(", ");
+function startWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, this is the fiber to unwind from.
+    currentFiber = fiber;
+    if (!beginFiberMark(fiber, null)) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = true;
+  }
+}
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillUpdate is deprecated and will be removed in the next major version. " +
-          "Use componentDidUpdate instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillUpdate." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames2
-      );
+function cancelWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // Remember we shouldn't complete measurement for this fiber.
+    // Otherwise flamechart will be deep even for small updates.
+    fiber._debugIsCurrentlyTiming = false;
+    clearFiberMark(fiber, null);
+  }
+}
 
-      pendingComponentWillUpdateWarnings = [];
+function stopWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber["return"];
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
     }
-  };
+    fiber._debugIsCurrentlyTiming = false;
+    endFiberMark(fiber, null, null);
+  }
+}
 
-  ReactStrictModeWarnings.recordDeprecationWarnings = function(
-    fiber,
-    instance
-  ) {
-    // Dedup strategy: Warn once per component.
-    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
+function stopFailedWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber["return"];
+    if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
+    fiber._debugIsCurrentlyTiming = false;
+    var warning$$1 = "An error was thrown inside this error boundary";
+    endFiberMark(fiber, null, warning$$1);
+  }
+}
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillMountWarnings.push(fiber);
+function startPhaseTimer(fiber, phase) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    if (
-      typeof instance.componentWillReceiveProps === "function" &&
-      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillReceivePropsWarnings.push(fiber);
+    clearPendingPhaseMeasurement();
+    if (!beginFiberMark(fiber, phase)) {
+      return;
     }
-    if (typeof instance.componentWillUpdate === "function") {
-      pendingComponentWillUpdateWarnings.push(fiber);
+    currentPhaseFiber = fiber;
+    currentPhase = phase;
+  }
+}
+
+function stopPhaseTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-  };
+    if (currentPhase !== null && currentPhaseFiber !== null) {
+      var warning$$1 = hasScheduledUpdateInCurrentPhase
+        ? "Scheduled a cascading update"
+        : null;
+      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
+    }
+    currentPhase = null;
+    currentPhaseFiber = null;
+  }
+}
 
-  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
-    fiber,
-    instance
-  ) {
-    var strictRoot = getStrictRoot(fiber);
+function startWorkLoopTimer(nextUnitOfWork) {
+  if (enableUserTimingAPI) {
+    currentFiber = nextUnitOfWork;
+    if (!supportsUserTiming) {
+      return;
+    }
+    commitCountInCurrentWorkLoop = 0;
+    // This is top level call.
+    // Any other measurements are performed within.
+    beginMark("(React Tree Reconciliation)");
+    // Resume any measurements that were in progress during the last loop.
+    resumeTimers();
+  }
+}
 
-    // Dedup strategy: Warn once per component.
-    // This is difficult to track any other way since component names
-    // are often vague and are likely to collide between 3rd party libraries.
-    // An expand property is probably okay to use here since it's DEV-only,
-    // and will only be set in the event of serious warnings.
-    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+function stopWorkLoopTimer(interruptedBy) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
       return;
     }
+    var warning$$1 = null;
+    if (interruptedBy !== null) {
+      if (interruptedBy.tag === HostRoot) {
+        warning$$1 = "A top-level update interrupted the previous render";
+      } else {
+        var componentName = getComponentName(interruptedBy) || "Unknown";
+        warning$$1 =
+          "An update to " + componentName + " interrupted the previous render";
+      }
+    } else if (commitCountInCurrentWorkLoop > 1) {
+      warning$$1 = "There were cascading updates";
+    }
+    commitCountInCurrentWorkLoop = 0;
+    // Pause any measurements until the next loop.
+    pauseTimers();
+    endMark(
+      "(React Tree Reconciliation)",
+      "(React Tree Reconciliation)",
+      warning$$1
+    );
+  }
+}
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    // Note that it is sufficient to check for the presence of a
-    // single lifecycle, componentWillMount, with the polyfill flag.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning === true
-    ) {
+function startCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
       return;
     }
+    isCommitting = true;
+    hasScheduledUpdateInCurrentCommit = false;
+    labelsInCurrentCommit.clear();
+    beginMark("(Committing Changes)");
+  }
+}
 
-    var warningsForRoot = void 0;
-    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
-      warningsForRoot = {
-        UNSAFE_componentWillMount: [],
-        UNSAFE_componentWillReceiveProps: [],
-        UNSAFE_componentWillUpdate: []
-      };
+function stopCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
 
-      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
-    } else {
-      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
+    var warning$$1 = null;
+    if (hasScheduledUpdateInCurrentCommit) {
+      warning$$1 = "Lifecycle hook scheduled a cascading update";
+    } else if (commitCountInCurrentWorkLoop > 0) {
+      warning$$1 = "Caused by a cascading update in earlier commit";
     }
+    hasScheduledUpdateInCurrentCommit = false;
+    commitCountInCurrentWorkLoop++;
+    isCommitting = false;
+    labelsInCurrentCommit.clear();
 
-    var unsafeLifecycles = [];
-    if (
-      typeof instance.componentWillMount === "function" ||
-      typeof instance.UNSAFE_componentWillMount === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillMount");
+    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
+  }
+}
+
+function startCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    if (
-      typeof instance.componentWillReceiveProps === "function" ||
-      typeof instance.UNSAFE_componentWillReceiveProps === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Host Effects)");
+  }
+}
+
+function stopCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    if (
-      typeof instance.componentWillUpdate === "function" ||
-      typeof instance.UNSAFE_componentWillUpdate === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Host Effects: " + count + " Total)",
+      "(Committing Host Effects)",
+      null
+    );
+  }
+}
+
+function startCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Calling Lifecycle Methods)");
+  }
+}
 
-    if (unsafeLifecycles.length > 0) {
-      unsafeLifecycles.forEach(function(lifecycle) {
-        warningsForRoot[lifecycle].push(fiber);
-      });
+function stopCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-  };
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Calling Lifecycle Methods: " + count + " Total)",
+      "(Calling Lifecycle Methods)",
+      null
+    );
+  }
 }
 
 var didWarnUpdateInsideUpdate = void 0;
@@ -6430,12 +6105,20 @@ function callGetDerivedStateFromCatch(ctor, capturedValues) {
 }
 
 var ReactFiberClassComponent = function(
+  legacyContext,
   scheduleWork,
   computeExpirationForFiber,
   memoizeProps,
   memoizeState
 ) {
+  var cacheContext = legacyContext.cacheContext,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    isContextConsumer = legacyContext.isContextConsumer,
+    hasContextChanged = legacyContext.hasContextChanged;
+
   // Class component state updater
+
   var updater = {
     isMounted: isMounted,
     enqueueSetState: function(instance, partialState, callback) {
@@ -8568,84 +8251,19 @@ function cloneChildFibers(current, workInProgress) {
     currentChild.pendingProps,
     currentChild.expirationTime
   );
-  workInProgress.child = newChild;
-
-  newChild["return"] = workInProgress;
-  while (currentChild.sibling !== null) {
-    currentChild = currentChild.sibling;
-    newChild = newChild.sibling = createWorkInProgress(
-      currentChild,
-      currentChild.pendingProps,
-      currentChild.expirationTime
-    );
-    newChild["return"] = workInProgress;
-  }
-  newChild.sibling = null;
-}
-
-var changedBitsStack = [];
-var currentValueStack = [];
-var stack = [];
-var index$1 = -1;
-
-var rendererSigil = void 0;
-{
-  // Use this to detect multiple renderers using the same context
-  rendererSigil = {};
-}
-
-function pushProvider(providerFiber) {
-  var context = providerFiber.type.context;
-  index$1 += 1;
-  changedBitsStack[index$1] = context._changedBits;
-  currentValueStack[index$1] = context._currentValue;
-  stack[index$1] = providerFiber;
-  context._currentValue = providerFiber.pendingProps.value;
-  context._changedBits = providerFiber.stateNode;
-
-  {
-    warning(
-      context._currentRenderer === null ||
-        context._currentRenderer === rendererSigil,
-      "Detected multiple renderers concurrently rendering the " +
-        "same context provider. This is currently unsupported."
-    );
-    context._currentRenderer = rendererSigil;
-  }
-}
-
-function popProvider(providerFiber) {
-  {
-    warning(
-      index$1 > -1 && providerFiber === stack[index$1],
-      "Unexpected pop."
-    );
-  }
-  var changedBits = changedBitsStack[index$1];
-  var currentValue = currentValueStack[index$1];
-  changedBitsStack[index$1] = null;
-  currentValueStack[index$1] = null;
-  stack[index$1] = null;
-  index$1 -= 1;
-  var context = providerFiber.type.context;
-  context._currentValue = currentValue;
-  context._changedBits = changedBits;
-}
+  workInProgress.child = newChild;
 
-function resetProviderStack() {
-  for (var i = index$1; i > -1; i--) {
-    var providerFiber = stack[i];
-    var context = providerFiber.type.context;
-    context._currentValue = context._defaultValue;
-    context._changedBits = 0;
-    changedBitsStack[i] = null;
-    currentValueStack[i] = null;
-    stack[i] = null;
-    {
-      context._currentRenderer = null;
-    }
+  newChild["return"] = workInProgress;
+  while (currentChild.sibling !== null) {
+    currentChild = currentChild.sibling;
+    newChild = newChild.sibling = createWorkInProgress(
+      currentChild,
+      currentChild.pendingProps,
+      currentChild.expirationTime
+    );
+    newChild["return"] = workInProgress;
   }
-  index$1 = -1;
+  newChild.sibling = null;
 }
 
 var didWarnAboutBadClass = void 0;
@@ -8661,6 +8279,8 @@ var didWarnAboutStatelessRefs = void 0;
 var ReactFiberBeginWork = function(
   config,
   hostContext,
+  legacyContext,
+  newContext,
   hydrationContext,
   scheduleWork,
   computeExpirationForFiber
@@ -8669,12 +8289,20 @@ var ReactFiberBeginWork = function(
     shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
   var pushHostContext = hostContext.pushHostContext,
     pushHostContainer = hostContext.pushHostContainer;
+  var pushProvider = newContext.pushProvider;
+  var getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    hasLegacyContextChanged = legacyContext.hasContextChanged,
+    pushLegacyContextProvider = legacyContext.pushContextProvider,
+    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
+    invalidateContextProvider = legacyContext.invalidateContextProvider;
   var enterHydrationState = hydrationContext.enterHydrationState,
     resetHydrationState = hydrationContext.resetHydrationState,
     tryToClaimNextHydratableInstance =
       hydrationContext.tryToClaimNextHydratableInstance;
 
   var _ReactFiberClassCompo = ReactFiberClassComponent(
+      legacyContext,
       scheduleWork,
       computeExpirationForFiber,
       memoizeProps,
@@ -8742,7 +8370,7 @@ var ReactFiberBeginWork = function(
 
   function updateFragment(current, workInProgress) {
     var nextChildren = workInProgress.pendingProps;
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (workInProgress.memoizedProps === nextChildren) {
@@ -8755,7 +8383,7 @@ var ReactFiberBeginWork = function(
 
   function updateMode(current, workInProgress) {
     var nextChildren = workInProgress.pendingProps.children;
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (
@@ -8784,7 +8412,7 @@ var ReactFiberBeginWork = function(
     var fn = workInProgress.type;
     var nextProps = workInProgress.pendingProps;
 
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else {
@@ -8817,7 +8445,7 @@ var ReactFiberBeginWork = function(
     // Push context providers early to prevent context stack mismatches.
     // During mounting we don't know the child context yet as the instance doesn't exist.
     // We will invalidate the child context in finishClassComponent() right after rendering.
-    var hasContext = pushContextProvider(workInProgress);
+    var hasContext = pushLegacyContextProvider(workInProgress);
     var shouldUpdate = void 0;
     if (current === null) {
       if (workInProgress.stateNode === null) {
@@ -9042,7 +8670,7 @@ var ReactFiberBeginWork = function(
     var nextProps = workInProgress.pendingProps;
     var prevProps = current !== null ? current.memoizedProps : null;
 
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (memoizedProps === nextProps) {
@@ -9177,7 +8805,7 @@ var ReactFiberBeginWork = function(
       // Push context providers early to prevent context stack mismatches.
       // During mounting we don't know the child context yet as the instance doesn't exist.
       // We will invalidate the child context in finishClassComponent() right after rendering.
-      var hasContext = pushContextProvider(workInProgress);
+      var hasContext = pushLegacyContextProvider(workInProgress);
       adoptClassInstance(workInProgress, value);
       mountClassInstance(workInProgress, renderExpirationTime);
       return finishClassComponent(
@@ -9250,7 +8878,7 @@ var ReactFiberBeginWork = function(
 
   function updateCallComponent(current, workInProgress, renderExpirationTime) {
     var nextProps = workInProgress.pendingProps;
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (workInProgress.memoizedProps === nextProps) {
@@ -9293,7 +8921,7 @@ var ReactFiberBeginWork = function(
   ) {
     pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
     var nextChildren = workInProgress.pendingProps;
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (workInProgress.memoizedProps === nextChildren) {
@@ -9327,6 +8955,10 @@ var ReactFiberBeginWork = function(
     renderExpirationTime
   ) {
     var fiber = workInProgress.child;
+    if (fiber !== null) {
+      // Set the return pointer of the child to the work-in-progress fiber.
+      fiber["return"] = workInProgress;
+    }
     while (fiber !== null) {
       var nextFiber = void 0;
       // Visit this fiber.
@@ -9419,7 +9051,7 @@ var ReactFiberBeginWork = function(
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
 
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (oldProps === newProps) {
@@ -9515,7 +9147,7 @@ var ReactFiberBeginWork = function(
     var newValue = context._currentValue;
     var changedBits = context._changedBits;
 
-    if (hasContextChanged()) {
+    if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (changedBits === 0 && oldProps === newProps) {
@@ -9612,7 +9244,7 @@ var ReactFiberBeginWork = function(
         pushHostRootContext(workInProgress);
         break;
       case ClassComponent:
-        pushContextProvider(workInProgress);
+        pushLegacyContextProvider(workInProgress);
         break;
       case HostPortal:
         pushHostContainer(
@@ -9725,7 +9357,13 @@ var ReactFiberBeginWork = function(
   };
 };
 
-var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
+var ReactFiberCompleteWork = function(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext
+) {
   var createInstance = config.createInstance,
     createTextInstance = config.createTextInstance,
     appendInitialChild = config.appendInitialChild,
@@ -9737,6 +9375,9 @@ var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
     popHostContext = hostContext.popHostContext,
     getHostContext = hostContext.getHostContext,
     popHostContainer = hostContext.popHostContainer;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
   var prepareToHydrateHostInstance =
       hydrationContext.prepareToHydrateHostInstance,
     prepareToHydrateHostTextInstance =
@@ -10052,7 +9693,7 @@ var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
         return null;
       case ClassComponent: {
         // We are leaving this subtree, so pop context if any.
-        popContextProvider(workInProgress);
+        popLegacyContextProvider(workInProgress);
 
         // If this component caught an error, schedule an error log effect.
         var instance = workInProgress.stateNode;
@@ -10071,7 +9712,7 @@ var ReactFiberCompleteWork = function(config, hostContext, hydrationContext) {
       }
       case HostRoot: {
         popHostContainer(workInProgress);
-        popTopLevelContextObject(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
         var fiberRoot = workInProgress.stateNode;
         if (fiberRoot.pendingContext) {
           fiberRoot.context = fiberRoot.pendingContext;
@@ -10298,11 +9939,16 @@ function createCapturedValue(value, source) {
 
 var ReactFiberUnwindWork = function(
   hostContext,
+  legacyContext,
+  newContext,
   scheduleWork,
   isAlreadyFailedLegacyErrorBoundary
 ) {
   var popHostContainer = hostContext.popHostContainer,
     popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
 
   function throwException(returnFiber, sourceFiber, rawValue) {
     // The source fiber did not complete.
@@ -10358,7 +10004,7 @@ var ReactFiberUnwindWork = function(
   function unwindWork(workInProgress) {
     switch (workInProgress.tag) {
       case ClassComponent: {
-        popContextProvider(workInProgress);
+        popLegacyContextProvider(workInProgress);
         var effectTag = workInProgress.effectTag;
         if (effectTag & ShouldCapture) {
           workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
@@ -10368,7 +10014,7 @@ var ReactFiberUnwindWork = function(
       }
       case HostRoot: {
         popHostContainer(workInProgress);
-        popTopLevelContextObject(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
         var _effectTag = workInProgress.effectTag;
         if (_effectTag & ShouldCapture) {
           workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
@@ -10390,9 +10036,37 @@ var ReactFiberUnwindWork = function(
         return null;
     }
   }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      default:
+        break;
+    }
+  }
+
   return {
     throwException: throwException,
-    unwindWork: unwindWork
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork
   };
 };
 
@@ -10758,7 +10432,7 @@ var ReactFiberCommitWork = function(
             warning(
               false,
               "Unexpected ref object provided for %s. " +
-                "Use either a ref-setter function or Reacte.createRef().%s",
+                "Use either a ref-setter function or React.createRef().%s",
               getComponentName(finishedWork),
               getStackAddendumByWorkInProgressFiber(finishedWork)
             );
@@ -11264,9 +10938,12 @@ var ReactFiberCommitWork = function(
 
 var NO_CONTEXT = {};
 
-var ReactFiberHostContext = function(config) {
+var ReactFiberHostContext = function(config, stack) {
   var getChildHostContext = config.getChildHostContext,
     getRootHostContext = config.getRootHostContext;
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
 
   var contextStackCursor = createCursor(NO_CONTEXT);
   var contextFiberStackCursor = createCursor(NO_CONTEXT);
@@ -11337,19 +11014,13 @@ var ReactFiberHostContext = function(config) {
     pop(contextFiberStackCursor, fiber);
   }
 
-  function resetHostContainer() {
-    contextStackCursor.current = NO_CONTEXT;
-    rootInstanceStackCursor.current = NO_CONTEXT;
-  }
-
   return {
     getHostContext: getHostContext,
     getRootHostContainer: getRootHostContainer,
     popHostContainer: popHostContainer,
     popHostContext: popHostContext,
     pushHostContainer: pushHostContainer,
-    pushHostContext: pushHostContext,
-    resetHostContainer: resetHostContainer
+    pushHostContext: pushHostContext
   };
 };
 
@@ -11719,6 +11390,425 @@ var ReactFiberInstrumentation = {
 
 var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
 
+var warnedAboutMissingGetChildContext = void 0;
+
+{
+  warnedAboutMissingGetChildContext = {};
+}
+
+var ReactFiberLegacyContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  // A cursor to the current merged context object on the stack.
+
+  var contextStackCursor = createCursor(emptyObject);
+  // A cursor to a boolean indicating whether the context has changed.
+  var didPerformWorkStackCursor = createCursor(false);
+  // Keep track of the previous context object that was on the stack.
+  // We use this to get access to the parent context after we have already
+  // pushed the next context provider, and now need to merge their contexts.
+  var previousContext = emptyObject;
+
+  function getUnmaskedContext(workInProgress) {
+    var hasOwnContext = isContextProvider(workInProgress);
+    if (hasOwnContext) {
+      // If the fiber is a context provider itself, when we read its context
+      // we have already pushed its own child context on the stack. A context
+      // provider should not "see" its own child context. Therefore we read the
+      // previous (parent) context instead for a context provider.
+      return previousContext;
+    }
+    return contextStackCursor.current;
+  }
+
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    var instance = workInProgress.stateNode;
+    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
+
+  function getMaskedContext(workInProgress, unmaskedContext) {
+    var type = workInProgress.type;
+    var contextTypes = type.contextTypes;
+    if (!contextTypes) {
+      return emptyObject;
+    }
+
+    // Avoid recreating masked context unless unmasked context has changed.
+    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
+    // This may trigger infinite loops if componentWillReceiveProps calls setState.
+    var instance = workInProgress.stateNode;
+    if (
+      instance &&
+      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+    ) {
+      return instance.__reactInternalMemoizedMaskedChildContext;
+    }
+
+    var context = {};
+    for (var key in contextTypes) {
+      context[key] = unmaskedContext[key];
+    }
+
+    {
+      var name = getComponentName(workInProgress) || "Unknown";
+      checkPropTypes(
+        contextTypes,
+        context,
+        "context",
+        name,
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    // Context is created before the class component is instantiated so check for instance.
+    if (instance) {
+      cacheContext(workInProgress, unmaskedContext, context);
+    }
+
+    return context;
+  }
+
+  function hasContextChanged() {
+    return didPerformWorkStackCursor.current;
+  }
+
+  function isContextConsumer(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+  }
+
+  function isContextProvider(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+  }
+
+  function popContextProvider(fiber) {
+    if (!isContextProvider(fiber)) {
+      return;
+    }
+
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
+
+  function popTopLevelContextObject(fiber) {
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
+
+  function pushTopLevelContextObject(fiber, context, didChange) {
+    invariant(
+      contextStackCursor.cursor == null,
+      "Unexpected context found on stack. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    push(contextStackCursor, context, fiber);
+    push(didPerformWorkStackCursor, didChange, fiber);
+  }
+
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode;
+    var childContextTypes = fiber.type.childContextTypes;
+
+    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
+    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
+    if (typeof instance.getChildContext !== "function") {
+      {
+        var componentName = getComponentName(fiber) || "Unknown";
+
+        if (!warnedAboutMissingGetChildContext[componentName]) {
+          warnedAboutMissingGetChildContext[componentName] = true;
+          warning(
+            false,
+            "%s.childContextTypes is specified but there is no getChildContext() method " +
+              "on the instance. You can either define getChildContext() on %s or remove " +
+              "childContextTypes from it.",
+            componentName,
+            componentName
+          );
+        }
+      }
+      return parentContext;
+    }
+
+    var childContext = void 0;
+    {
+      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
+    }
+    startPhaseTimer(fiber, "getChildContext");
+    childContext = instance.getChildContext();
+    stopPhaseTimer();
+    {
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+    for (var contextKey in childContext) {
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    }
+    {
+      var name = getComponentName(fiber) || "Unknown";
+      checkPropTypes(
+        childContextTypes,
+        childContext,
+        "child context",
+        name,
+        // In practice, there is one case in which we won't get a stack. It's when
+        // somebody calls unstable_renderSubtreeIntoContainer() and we process
+        // context from the parent component instance. The stack will be missing
+        // because it's outside of the reconciliation, and so the pointer has not
+        // been set. This is rare and doesn't matter. We'll also remove that API.
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    return Object.assign({}, parentContext, childContext);
+  }
+
+  function pushContextProvider(workInProgress) {
+    if (!isContextProvider(workInProgress)) {
+      return false;
+    }
+
+    var instance = workInProgress.stateNode;
+    // We push the context as early as possible to ensure stack integrity.
+    // If the instance does not exist yet, we will push null at first,
+    // and replace it on the stack later when invalidating the context.
+    var memoizedMergedChildContext =
+      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+      emptyObject;
+
+    // Remember the parent context so we can merge with it later.
+    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
+    previousContext = contextStackCursor.current;
+    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
+    push(
+      didPerformWorkStackCursor,
+      didPerformWorkStackCursor.current,
+      workInProgress
+    );
+
+    return true;
+  }
+
+  function invalidateContextProvider(workInProgress, didChange) {
+    var instance = workInProgress.stateNode;
+    invariant(
+      instance,
+      "Expected to have an instance by this point. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    if (didChange) {
+      // Merge parent and own context.
+      // Skip this if we're not updating due to sCU.
+      // This avoids unnecessarily recomputing memoized values.
+      var mergedContext = processChildContext(workInProgress, previousContext);
+      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+
+      // Replace the old (or empty) context with the new one.
+      // It is important to unwind the context in the reverse order.
+      pop(didPerformWorkStackCursor, workInProgress);
+      pop(contextStackCursor, workInProgress);
+      // Now push the new context and mark that it has changed.
+      push(contextStackCursor, mergedContext, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    } else {
+      pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    }
+  }
+
+  function findCurrentUnmaskedContext(fiber) {
+    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
+    // makes sense elsewhere
+    invariant(
+      isFiberMounted(fiber) && fiber.tag === ClassComponent,
+      "Expected subtree parent to be a mounted class component. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    var node = fiber;
+    while (node.tag !== HostRoot) {
+      if (isContextProvider(node)) {
+        return node.stateNode.__reactInternalMemoizedMergedChildContext;
+      }
+      var parent = node["return"];
+      invariant(
+        parent,
+        "Found unexpected detached subtree parent. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
+      node = parent;
+    }
+    return node.stateNode.context;
+  }
+
+  return {
+    getUnmaskedContext: getUnmaskedContext,
+    cacheContext: cacheContext,
+    getMaskedContext: getMaskedContext,
+    hasContextChanged: hasContextChanged,
+    isContextConsumer: isContextConsumer,
+    isContextProvider: isContextProvider,
+    popContextProvider: popContextProvider,
+    popTopLevelContextObject: popTopLevelContextObject,
+    pushTopLevelContextObject: pushTopLevelContextObject,
+    processChildContext: processChildContext,
+    pushContextProvider: pushContextProvider,
+    invalidateContextProvider: invalidateContextProvider,
+    findCurrentUnmaskedContext: findCurrentUnmaskedContext
+  };
+};
+
+var ReactFiberNewContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  var providerCursor = createCursor(null);
+  var valueCursor = createCursor(null);
+  var changedBitsCursor = createCursor(0);
+
+  var rendererSigil = void 0;
+  {
+    // Use this to detect multiple renderers using the same context
+    rendererSigil = {};
+  }
+
+  function pushProvider(providerFiber) {
+    var context = providerFiber.type.context;
+
+    push(changedBitsCursor, context._changedBits, providerFiber);
+    push(valueCursor, context._currentValue, providerFiber);
+    push(providerCursor, providerFiber, providerFiber);
+
+    context._currentValue = providerFiber.pendingProps.value;
+    context._changedBits = providerFiber.stateNode;
+
+    {
+      warning(
+        context._currentRenderer === null ||
+          context._currentRenderer === rendererSigil,
+        "Detected multiple renderers concurrently rendering the " +
+          "same context provider. This is currently unsupported."
+      );
+      context._currentRenderer = rendererSigil;
+    }
+  }
+
+  function popProvider(providerFiber) {
+    var changedBits = changedBitsCursor.current;
+    var currentValue = valueCursor.current;
+
+    pop(providerCursor, providerFiber);
+    pop(valueCursor, providerFiber);
+    pop(changedBitsCursor, providerFiber);
+
+    var context = providerFiber.type.context;
+    context._currentValue = currentValue;
+    context._changedBits = changedBits;
+  }
+
+  return {
+    pushProvider: pushProvider,
+    popProvider: popProvider
+  };
+};
+
+var ReactFiberStack = function() {
+  var valueStack = [];
+
+  var fiberStack = void 0;
+
+  {
+    fiberStack = [];
+  }
+
+  var index = -1;
+
+  function createCursor(defaultValue) {
+    return {
+      current: defaultValue
+    };
+  }
+
+  function isEmpty() {
+    return index === -1;
+  }
+
+  function pop(cursor, fiber) {
+    if (index < 0) {
+      {
+        warning(false, "Unexpected pop.");
+      }
+      return;
+    }
+
+    {
+      if (fiber !== fiberStack[index]) {
+        warning(false, "Unexpected Fiber popped.");
+      }
+    }
+
+    cursor.current = valueStack[index];
+
+    valueStack[index] = null;
+
+    {
+      fiberStack[index] = null;
+    }
+
+    index--;
+  }
+
+  function push(cursor, value, fiber) {
+    index++;
+
+    valueStack[index] = cursor.current;
+
+    {
+      fiberStack[index] = fiber;
+    }
+
+    cursor.current = value;
+  }
+
+  function checkThatStackIsEmpty() {
+    {
+      if (index !== -1) {
+        warning(
+          false,
+          "Expected an empty stack. Something was not reset properly."
+        );
+      }
+    }
+  }
+
+  function resetStackAfterFatalErrorInDev() {
+    {
+      index = -1;
+      valueStack.length = 0;
+      fiberStack.length = 0;
+    }
+  }
+
+  return {
+    createCursor: createCursor,
+    isEmpty: isEmpty,
+    pop: pop,
+    push: push,
+    checkThatStackIsEmpty: checkThatStackIsEmpty,
+    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
+  };
+};
+
 var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
 var hasCaughtError = ReactErrorUtils.hasCaughtError;
 var clearCaughtError = ReactErrorUtils.clearCaughtError;
@@ -11779,16 +11869,23 @@ var warnAboutInvalidUpdates = void 0;
 }
 
 var ReactFiberScheduler = function(config) {
-  var hostContext = ReactFiberHostContext(config);
+  var stack = ReactFiberStack();
+  var hostContext = ReactFiberHostContext(config, stack);
+  var legacyContext = ReactFiberLegacyContext(stack);
+  var newContext = ReactFiberNewContext(stack);
   var popHostContext = hostContext.popHostContext,
     popHostContainer = hostContext.popHostContainer;
+  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popLegacyContextProvider = legacyContext.popContextProvider;
+  var popProvider = newContext.popProvider;
 
   var hydrationContext = ReactFiberHydrationContext(config);
-  var resetHostContainer = hostContext.resetHostContainer;
 
   var _ReactFiberBeginWork = ReactFiberBeginWork(
       config,
       hostContext,
+      legacyContext,
+      newContext,
       hydrationContext,
       scheduleWork,
       computeExpirationForFiber
@@ -11798,17 +11895,22 @@ var ReactFiberScheduler = function(config) {
   var _ReactFiberCompleteWo = ReactFiberCompleteWork(
       config,
       hostContext,
+      legacyContext,
+      newContext,
       hydrationContext
     ),
     completeWork = _ReactFiberCompleteWo.completeWork;
 
   var _ReactFiberUnwindWork = ReactFiberUnwindWork(
       hostContext,
+      legacyContext,
+      newContext,
       scheduleWork,
       isAlreadyFailedLegacyErrorBoundary
     ),
     throwException = _ReactFiberUnwindWork.throwException,
-    unwindWork = _ReactFiberUnwindWork.unwindWork;
+    unwindWork = _ReactFiberUnwindWork.unwindWork,
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
 
   var _ReactFiberCommitWork = ReactFiberCommitWork(
       config,
@@ -11877,13 +11979,13 @@ var ReactFiberScheduler = function(config) {
       switch (failedUnitOfWork.tag) {
         case HostRoot:
           popHostContainer(failedUnitOfWork);
-          popTopLevelContextObject(failedUnitOfWork);
+          popTopLevelLegacyContextObject(failedUnitOfWork);
           break;
         case HostComponent:
           popHostContext(failedUnitOfWork);
           break;
         case ClassComponent:
-          popContextProvider(failedUnitOfWork);
+          popLegacyContextProvider(failedUnitOfWork);
           break;
         case HostPortal:
           popHostContainer(failedUnitOfWork);
@@ -11903,18 +12005,18 @@ var ReactFiberScheduler = function(config) {
     };
   }
 
-  function resetContextStack() {
-    // Reset the stack
-    reset();
-    // Reset the cursors
-    resetContext();
-    resetHostContainer();
-
-    // TODO: Unify new context implementation with other stacks
-    resetProviderStack();
+  function resetStack() {
+    if (nextUnitOfWork !== null) {
+      var interruptedWork = nextUnitOfWork["return"];
+      while (interruptedWork !== null) {
+        unwindInterruptedWork(interruptedWork);
+        interruptedWork = interruptedWork["return"];
+      }
+    }
 
     {
       ReactStrictModeWarnings.discardPendingWarnings();
+      stack.checkThatStackIsEmpty();
     }
 
     nextRoot = null;
@@ -12438,7 +12540,7 @@ var ReactFiberScheduler = function(config) {
       nextUnitOfWork === null
     ) {
       // Reset the stack and start working from the root.
-      resetContextStack();
+      resetStack();
       nextRoot = root;
       nextRenderExpirationTime = expirationTime;
       nextUnitOfWork = createWorkInProgress(
@@ -12491,6 +12593,9 @@ var ReactFiberScheduler = function(config) {
     // Yield back to main thread.
     if (didFatal) {
       // There was a fatal error.
+      {
+        stack.resetStackAfterFatalErrorInDev();
+      }
       return null;
     } else if (nextUnitOfWork === null) {
       // We reached the root.
@@ -12691,7 +12796,7 @@ var ReactFiberScheduler = function(config) {
           ) {
             // This is an interruption. (Used for performance tracking.)
             interruptedBy = fiber;
-            resetContextStack();
+            resetStack();
           }
           if (nextRoot !== root || !isWorking) {
             requestWork(root, expirationTime);
@@ -13262,7 +13367,8 @@ var ReactFiberScheduler = function(config) {
     syncUpdates: syncUpdates,
     interactiveUpdates: interactiveUpdates,
     flushInteractiveUpdates: flushInteractiveUpdates,
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration
+    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+    legacyContext: legacyContext
   };
 };
 
@@ -13275,18 +13381,6 @@ var didWarnAboutNestedUpdates = void 0;
 // 0 is PROD, 1 is DEV.
 // Might add PROFILE later.
 
-function getContextForSubtree(parentComponent) {
-  if (!parentComponent) {
-    return emptyObject;
-  }
-
-  var fiber = get(parentComponent);
-  var parentContext = findCurrentUnmaskedContext(fiber);
-  return isContextProvider(fiber)
-    ? processChildContext(fiber, parentContext)
-    : parentContext;
-}
-
 var ReactFiberReconciler$1 = function(config) {
   var getPublicInstance = config.getPublicInstance;
 
@@ -13305,7 +13399,24 @@ var ReactFiberReconciler$1 = function(config) {
     deferredUpdates = _ReactFiberScheduler.deferredUpdates,
     syncUpdates = _ReactFiberScheduler.syncUpdates,
     interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
-    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates;
+    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
+    legacyContext = _ReactFiberScheduler.legacyContext;
+
+  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
+
+  function getContextForSubtree(parentComponent) {
+    if (!parentComponent) {
+      return emptyObject;
+    }
+
+    var fiber = get(parentComponent);
+    var parentContext = findCurrentUnmaskedContext(fiber);
+    return isContextProvider(fiber)
+      ? processChildContext(fiber, parentContext)
+      : parentContext;
+  }
 
   function scheduleRootUpdate(
     current,
diff --git a/Libraries/Renderer/ReactNativeRenderer-prod.js b/Libraries/Renderer/ReactNativeRenderer-prod.js
index 258608b7f31a..f11aa6c82da4 100644
--- a/Libraries/Renderer/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/ReactNativeRenderer-prod.js
@@ -1822,141 +1822,6 @@ function findCurrentHostFiberWithNoPortals(parent) {
   }
   return null;
 }
-var valueStack = [],
-  index = -1;
-function pop(cursor) {
-  0 > index ||
-    ((cursor.current = valueStack[index]), (valueStack[index] = null), index--);
-}
-function push(cursor, value) {
-  index++;
-  valueStack[index] = cursor.current;
-  cursor.current = value;
-}
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  do {
-    a: switch (workInProgress.tag) {
-      case 0:
-      case 1:
-      case 2:
-      case 5:
-        var owner = workInProgress._debugOwner,
-          source = workInProgress._debugSource;
-        var JSCompiler_inline_result = getComponentName(workInProgress);
-        var ownerName = null;
-        owner && (ownerName = getComponentName(owner));
-        owner = source;
-        JSCompiler_inline_result =
-          "\n    in " +
-          (JSCompiler_inline_result || "Unknown") +
-          (owner
-            ? " (at " +
-              owner.fileName.replace(/^.*[\\\/]/, "") +
-              ":" +
-              owner.lineNumber +
-              ")"
-            : ownerName ? " (created by " + ownerName + ")" : "");
-        break a;
-      default:
-        JSCompiler_inline_result = "";
-    }
-    info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
-  } while (workInProgress);
-  return info;
-}
-var _require = require("ReactFeatureFlags"),
-  enableGetDerivedStateFromCatch = _require.enableGetDerivedStateFromCatch,
-  debugRenderPhaseSideEffects = _require.debugRenderPhaseSideEffects,
-  debugRenderPhaseSideEffectsForStrictMode =
-    _require.debugRenderPhaseSideEffectsForStrictMode;
-new Set();
-var contextStackCursor = { current: emptyObject },
-  didPerformWorkStackCursor = { current: !1 },
-  previousContext = emptyObject;
-function getUnmaskedContext(workInProgress) {
-  return isContextProvider(workInProgress)
-    ? previousContext
-    : contextStackCursor.current;
-}
-function getMaskedContext(workInProgress, unmaskedContext) {
-  var contextTypes = workInProgress.type.contextTypes;
-  if (!contextTypes) return emptyObject;
-  var instance = workInProgress.stateNode;
-  if (
-    instance &&
-    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-  )
-    return instance.__reactInternalMemoizedMaskedChildContext;
-  var context = {},
-    key;
-  for (key in contextTypes) context[key] = unmaskedContext[key];
-  instance &&
-    ((workInProgress = workInProgress.stateNode),
-    (workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext),
-    (workInProgress.__reactInternalMemoizedMaskedChildContext = context));
-  return context;
-}
-function isContextProvider(fiber) {
-  return 2 === fiber.tag && null != fiber.type.childContextTypes;
-}
-function popContextProvider(fiber) {
-  isContextProvider(fiber) &&
-    (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
-}
-function pushTopLevelContextObject(fiber, context, didChange) {
-  invariant(
-    null == contextStackCursor.cursor,
-    "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
-  );
-  push(contextStackCursor, context, fiber);
-  push(didPerformWorkStackCursor, didChange, fiber);
-}
-function processChildContext(fiber, parentContext) {
-  var instance = fiber.stateNode,
-    childContextTypes = fiber.type.childContextTypes;
-  if ("function" !== typeof instance.getChildContext) return parentContext;
-  instance = instance.getChildContext();
-  for (var contextKey in instance)
-    invariant(
-      contextKey in childContextTypes,
-      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-      getComponentName(fiber) || "Unknown",
-      contextKey
-    );
-  return Object.assign({}, parentContext, instance);
-}
-function pushContextProvider(workInProgress) {
-  if (!isContextProvider(workInProgress)) return !1;
-  var instance = workInProgress.stateNode;
-  instance =
-    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-    emptyObject;
-  previousContext = contextStackCursor.current;
-  push(contextStackCursor, instance, workInProgress);
-  push(
-    didPerformWorkStackCursor,
-    didPerformWorkStackCursor.current,
-    workInProgress
-  );
-  return !0;
-}
-function invalidateContextProvider(workInProgress, didChange) {
-  var instance = workInProgress.stateNode;
-  invariant(
-    instance,
-    "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
-  );
-  if (didChange) {
-    var mergedContext = processChildContext(workInProgress, previousContext);
-    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-    pop(didPerformWorkStackCursor, workInProgress);
-    pop(contextStackCursor, workInProgress);
-    push(contextStackCursor, mergedContext, workInProgress);
-  } else pop(didPerformWorkStackCursor, workInProgress);
-  push(didPerformWorkStackCursor, didChange, workInProgress);
-}
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
   this.key = key;
@@ -2123,6 +1988,45 @@ function onCommitRoot(root) {
 function onCommitUnmount(fiber) {
   "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
 }
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
+    }
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress["return"];
+  } while (workInProgress);
+  return info;
+}
+var _require = require("ReactFeatureFlags"),
+  enableGetDerivedStateFromCatch = _require.enableGetDerivedStateFromCatch,
+  debugRenderPhaseSideEffects = _require.debugRenderPhaseSideEffects,
+  debugRenderPhaseSideEffectsForStrictMode =
+    _require.debugRenderPhaseSideEffectsForStrictMode;
+new Set();
 function createUpdateQueue(baseState) {
   return {
     baseState: baseState,
@@ -2294,6 +2198,7 @@ function callGetDerivedStateFromCatch(ctor, capturedValues) {
   return resultState;
 }
 function ReactFiberClassComponent(
+  legacyContext,
   scheduleWork,
   computeExpirationForFiber,
   memoizeProps,
@@ -2360,62 +2265,66 @@ function ReactFiberClassComponent(
         )
       );
   }
-  var updater = {
-    isMounted: isMounted,
-    enqueueSetState: function(instance, partialState, callback) {
-      instance = instance._reactInternalFiber;
-      callback = void 0 === callback ? null : callback;
-      var expirationTime = computeExpirationForFiber(instance);
-      insertUpdateIntoFiber(instance, {
-        expirationTime: expirationTime,
-        partialState: partialState,
-        callback: callback,
-        isReplace: !1,
-        isForced: !1,
-        capturedValue: null,
-        next: null
-      });
-      scheduleWork(instance, expirationTime);
-    },
-    enqueueReplaceState: function(instance, state, callback) {
-      instance = instance._reactInternalFiber;
-      callback = void 0 === callback ? null : callback;
-      var expirationTime = computeExpirationForFiber(instance);
-      insertUpdateIntoFiber(instance, {
-        expirationTime: expirationTime,
-        partialState: state,
-        callback: callback,
-        isReplace: !0,
-        isForced: !1,
-        capturedValue: null,
-        next: null
-      });
-      scheduleWork(instance, expirationTime);
-    },
-    enqueueForceUpdate: function(instance, callback) {
-      instance = instance._reactInternalFiber;
-      callback = void 0 === callback ? null : callback;
-      var expirationTime = computeExpirationForFiber(instance);
-      insertUpdateIntoFiber(instance, {
-        expirationTime: expirationTime,
-        partialState: null,
-        callback: callback,
-        isReplace: !1,
-        isForced: !0,
-        capturedValue: null,
-        next: null
-      });
-      scheduleWork(instance, expirationTime);
-    }
-  };
+  var cacheContext = legacyContext.cacheContext,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    isContextConsumer = legacyContext.isContextConsumer,
+    hasContextChanged = legacyContext.hasContextChanged,
+    updater = {
+      isMounted: isMounted,
+      enqueueSetState: function(instance, partialState, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: partialState,
+          callback: callback,
+          isReplace: !1,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      },
+      enqueueReplaceState: function(instance, state, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: state,
+          callback: callback,
+          isReplace: !0,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      },
+      enqueueForceUpdate: function(instance, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: null,
+          callback: callback,
+          isReplace: !1,
+          isForced: !0,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      }
+    };
   return {
     adoptClassInstance: adoptClassInstance,
     callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: function(workInProgress, props) {
       var ctor = workInProgress.type,
         unmaskedContext = getUnmaskedContext(workInProgress),
-        needsContext =
-          2 === workInProgress.tag && null != workInProgress.type.contextTypes,
+        needsContext = isContextConsumer(workInProgress),
         context = needsContext
           ? getMaskedContext(workInProgress, unmaskedContext)
           : emptyObject;
@@ -2436,10 +2345,7 @@ function ReactFiberClassComponent(
           workInProgress.memoizedState,
           props
         ));
-      needsContext &&
-        ((workInProgress = workInProgress.stateNode),
-        (workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext),
-        (workInProgress.__reactInternalMemoizedMaskedChildContext = context));
+      needsContext && cacheContext(workInProgress, unmaskedContext, context);
       return ctor;
     },
     mountClassInstance: function(workInProgress, renderExpirationTime) {
@@ -2539,7 +2445,7 @@ function ReactFiberClassComponent(
         !(
           oldProps !== newProps ||
           oldState !== renderExpirationTime ||
-          didPerformWorkStackCursor.current ||
+          hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
         )
@@ -2643,7 +2549,7 @@ function ReactFiberClassComponent(
         !(
           oldProps !== newProps ||
           oldContext !== renderExpirationTime ||
-          didPerformWorkStackCursor.current ||
+          hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
         )
@@ -3366,34 +3272,12 @@ function ChildReconciler(shouldTrackSideEffects) {
   };
 }
 var reconcileChildFibers = ChildReconciler(!0),
-  mountChildFibers = ChildReconciler(!1),
-  changedBitsStack = [],
-  currentValueStack = [],
-  stack = [],
-  index$1 = -1;
-function pushProvider(providerFiber) {
-  var context = providerFiber.type.context;
-  index$1 += 1;
-  changedBitsStack[index$1] = context._changedBits;
-  currentValueStack[index$1] = context._currentValue;
-  stack[index$1] = providerFiber;
-  context._currentValue = providerFiber.pendingProps.value;
-  context._changedBits = providerFiber.stateNode;
-}
-function popProvider(providerFiber) {
-  var changedBits = changedBitsStack[index$1],
-    currentValue = currentValueStack[index$1];
-  changedBitsStack[index$1] = null;
-  currentValueStack[index$1] = null;
-  stack[index$1] = null;
-  --index$1;
-  providerFiber = providerFiber.type.context;
-  providerFiber._currentValue = currentValue;
-  providerFiber._changedBits = changedBits;
-}
+  mountChildFibers = ChildReconciler(!1);
 function ReactFiberBeginWork(
   config,
   hostContext,
+  legacyContext,
+  newContext,
   hydrationContext,
   scheduleWork,
   computeExpirationForFiber
@@ -3499,7 +3383,12 @@ function ReactFiberBeginWork(
     changedBits,
     renderExpirationTime
   ) {
-    for (var fiber = workInProgress.child; null !== fiber; ) {
+    var fiber = workInProgress.child;
+    for (
+      null !== fiber && (fiber["return"] = workInProgress);
+      null !== fiber;
+
+    ) {
       switch (fiber.tag) {
         case 12:
           var nextFiber = fiber.stateNode | 0;
@@ -3558,7 +3447,7 @@ function ReactFiberBeginWork(
     var context = workInProgress.type.context,
       newProps = workInProgress.pendingProps,
       oldProps = workInProgress.memoizedProps;
-    if (!didPerformWorkStackCursor.current && oldProps === newProps)
+    if (!hasLegacyContextChanged() && oldProps === newProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
@@ -3645,11 +3534,19 @@ function ReactFiberBeginWork(
     shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree,
     pushHostContext = hostContext.pushHostContext,
     pushHostContainer = hostContext.pushHostContainer,
+    pushProvider = newContext.pushProvider,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    hasLegacyContextChanged = legacyContext.hasContextChanged,
+    pushLegacyContextProvider = legacyContext.pushContextProvider,
+    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
+    invalidateContextProvider = legacyContext.invalidateContextProvider,
     enterHydrationState = hydrationContext.enterHydrationState,
     resetHydrationState = hydrationContext.resetHydrationState,
     tryToClaimNextHydratableInstance =
       hydrationContext.tryToClaimNextHydratableInstance;
   config = ReactFiberClassComponent(
+    legacyContext,
     scheduleWork,
     computeExpirationForFiber,
     function(workInProgress, nextProps) {
@@ -3676,7 +3573,7 @@ function ReactFiberBeginWork(
             pushHostRootContext(workInProgress);
             break;
           case 2:
-            pushContextProvider(workInProgress);
+            pushLegacyContextProvider(workInProgress);
             break;
           case 4:
             pushHostContainer(
@@ -3722,7 +3619,7 @@ function ReactFiberBeginWork(
                     workInProgress.memoizedState,
                     props
                   ))),
-              (props = pushContextProvider(workInProgress)),
+              (props = pushLegacyContextProvider(workInProgress)),
               adoptClassInstance(workInProgress, fn),
               mountClassInstance(workInProgress, renderExpirationTime),
               (current = finishClassComponent(
@@ -3742,7 +3639,7 @@ function ReactFiberBeginWork(
           return (
             (props = workInProgress.type),
             (renderExpirationTime = workInProgress.pendingProps),
-            didPerformWorkStackCursor.current ||
+            hasLegacyContextChanged() ||
             workInProgress.memoizedProps !== renderExpirationTime
               ? ((fn = getUnmaskedContext(workInProgress)),
                 (fn = getMaskedContext(workInProgress, fn)),
@@ -3758,7 +3655,7 @@ function ReactFiberBeginWork(
             current
           );
         case 2:
-          props = pushContextProvider(workInProgress);
+          props = pushLegacyContextProvider(workInProgress);
           null === current
             ? null === workInProgress.stateNode
               ? (constructClassInstance(
@@ -3840,7 +3737,7 @@ function ReactFiberBeginWork(
             updateQueue = workInProgress.memoizedProps;
             fn = workInProgress.pendingProps;
             unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!didPerformWorkStackCursor.current && updateQueue === fn) {
+            if (!hasLegacyContextChanged() && updateQueue === fn) {
               if (
                 (updateQueue =
                   workInProgress.mode & 1 &&
@@ -3882,7 +3779,7 @@ function ReactFiberBeginWork(
         case 7:
           return (
             (props = workInProgress.pendingProps),
-            didPerformWorkStackCursor.current ||
+            hasLegacyContextChanged() ||
               workInProgress.memoizedProps !== props ||
               (props = workInProgress.memoizedProps),
             (fn = props.children),
@@ -3912,8 +3809,7 @@ function ReactFiberBeginWork(
               workInProgress.stateNode.containerInfo
             ),
             (props = workInProgress.pendingProps),
-            didPerformWorkStackCursor.current ||
-            workInProgress.memoizedProps !== props
+            hasLegacyContextChanged() || workInProgress.memoizedProps !== props
               ? (null === current
                   ? (workInProgress.child = reconcileChildFibers(
                       workInProgress,
@@ -3944,7 +3840,7 @@ function ReactFiberBeginWork(
         case 10:
           return (
             (renderExpirationTime = workInProgress.pendingProps),
-            didPerformWorkStackCursor.current ||
+            hasLegacyContextChanged() ||
             workInProgress.memoizedProps !== renderExpirationTime
               ? (reconcileChildren(
                   current,
@@ -3962,7 +3858,7 @@ function ReactFiberBeginWork(
         case 11:
           return (
             (renderExpirationTime = workInProgress.pendingProps.children),
-            didPerformWorkStackCursor.current ||
+            hasLegacyContextChanged() ||
             (null !== renderExpirationTime &&
               workInProgress.memoizedProps !== renderExpirationTime)
               ? (reconcileChildren(
@@ -3992,7 +3888,7 @@ function ReactFiberBeginWork(
             props = fn._currentValue;
             var changedBits = fn._changedBits;
             if (
-              didPerformWorkStackCursor.current ||
+              hasLegacyContextChanged() ||
               0 !== changedBits ||
               updateQueue !== unmaskedContext
             ) {
@@ -4032,7 +3928,13 @@ function ReactFiberBeginWork(
     }
   };
 }
-function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
+function ReactFiberCompleteWork(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext
+) {
   function markUpdate(workInProgress) {
     workInProgress.effectTag |= 4;
   }
@@ -4046,6 +3948,9 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
     popHostContext = hostContext.popHostContext,
     getHostContext = hostContext.getHostContext,
     popHostContainer = hostContext.popHostContainer,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider,
     prepareToHydrateHostInstance =
       hydrationContext.prepareToHydrateHostInstance,
     prepareToHydrateHostTextInstance =
@@ -4074,7 +3979,7 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
           return null;
         case 2:
           return (
-            popContextProvider(workInProgress),
+            popLegacyContextProvider(workInProgress),
             (current = workInProgress.stateNode),
             (newProps = workInProgress.updateQueue),
             null !== newProps &&
@@ -4087,8 +3992,7 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
           );
         case 3:
           popHostContainer(workInProgress);
-          pop(didPerformWorkStackCursor, workInProgress);
-          pop(contextStackCursor, workInProgress);
+          popTopLevelLegacyContextObject(workInProgress);
           newProps = workInProgress.stateNode;
           newProps.pendingContext &&
             ((newProps.context = newProps.pendingContext),
@@ -4304,11 +4208,16 @@ function ReactFiberCompleteWork(config, hostContext, hydrationContext) {
 }
 function ReactFiberUnwindWork(
   hostContext,
+  legacyContext,
+  newContext,
   scheduleWork,
   isAlreadyFailedLegacyErrorBoundary
 ) {
   var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
   return {
     throwException: function(returnFiber, sourceFiber, rawValue) {
       sourceFiber.effectTag |= 512;
@@ -4352,7 +4261,7 @@ function ReactFiberUnwindWork(
     unwindWork: function(workInProgress) {
       switch (workInProgress.tag) {
         case 2:
-          popContextProvider(workInProgress);
+          popLegacyContextProvider(workInProgress);
           var effectTag = workInProgress.effectTag;
           return effectTag & 1024
             ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
@@ -4361,8 +4270,7 @@ function ReactFiberUnwindWork(
         case 3:
           return (
             popHostContainer(workInProgress),
-            pop(didPerformWorkStackCursor, workInProgress),
-            pop(contextStackCursor, workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
             (effectTag = workInProgress.effectTag),
             effectTag & 1024
               ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
@@ -4378,6 +4286,25 @@ function ReactFiberUnwindWork(
         default:
           return null;
       }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
     }
   };
 }
@@ -4819,7 +4746,7 @@ function ReactFiberCommitWork(
   };
 }
 var NO_CONTEXT = {};
-function ReactFiberHostContext(config) {
+function ReactFiberHostContext(config, stack) {
   function requiredContext(c) {
     invariant(
       c !== NO_CONTEXT,
@@ -4828,10 +4755,13 @@ function ReactFiberHostContext(config) {
     return c;
   }
   var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext,
-    contextStackCursor = { current: NO_CONTEXT },
-    contextFiberStackCursor = { current: NO_CONTEXT },
-    rootInstanceStackCursor = { current: NO_CONTEXT };
+    getRootHostContext = config.getRootHostContext;
+  config = stack.createCursor;
+  var push = stack.push,
+    pop = stack.pop,
+    contextStackCursor = config(NO_CONTEXT),
+    contextFiberStackCursor = config(NO_CONTEXT),
+    rootInstanceStackCursor = config(NO_CONTEXT);
   return {
     getHostContext: function() {
       return requiredContext(contextStackCursor.current);
@@ -4861,10 +4791,6 @@ function ReactFiberHostContext(config) {
       context !== rootInstance &&
         (push(contextFiberStackCursor, fiber, fiber),
         push(contextStackCursor, rootInstance, fiber));
-    },
-    resetHostContainer: function() {
-      contextStackCursor.current = NO_CONTEXT;
-      rootInstanceStackCursor.current = NO_CONTEXT;
     }
   };
 }
@@ -5024,22 +4950,198 @@ function ReactFiberHydrationContext(config) {
     }
   };
 }
-function ReactFiberScheduler(config) {
-  function resetContextStack() {
-    for (; -1 < index; ) (valueStack[index] = null), index--;
+function ReactFiberLegacyContext(stack) {
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    workInProgress = workInProgress.stateNode;
+    workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    workInProgress.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
+  function isContextProvider(fiber) {
+    return 2 === fiber.tag && null != fiber.type.childContextTypes;
+  }
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode,
+      childContextTypes = fiber.type.childContextTypes;
+    if ("function" !== typeof instance.getChildContext) return parentContext;
+    instance = instance.getChildContext();
+    for (var contextKey in instance)
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    return Object.assign({}, parentContext, instance);
+  }
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop,
+    contextStackCursor = createCursor(emptyObject),
+    didPerformWorkStackCursor = createCursor(!1),
     previousContext = emptyObject;
-    contextStackCursor.current = emptyObject;
-    didPerformWorkStackCursor.current = !1;
-    resetHostContainer();
-    for (var i = index$1; -1 < i; i--) {
-      var context = stack[i].type.context;
-      context._currentValue = context._defaultValue;
-      context._changedBits = 0;
-      changedBitsStack[i] = null;
-      currentValueStack[i] = null;
-      stack[i] = null;
+  return {
+    getUnmaskedContext: function(workInProgress) {
+      return isContextProvider(workInProgress)
+        ? previousContext
+        : contextStackCursor.current;
+    },
+    cacheContext: cacheContext,
+    getMaskedContext: function(workInProgress, unmaskedContext) {
+      var contextTypes = workInProgress.type.contextTypes;
+      if (!contextTypes) return emptyObject;
+      var instance = workInProgress.stateNode;
+      if (
+        instance &&
+        instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+      )
+        return instance.__reactInternalMemoizedMaskedChildContext;
+      var context = {},
+        key;
+      for (key in contextTypes) context[key] = unmaskedContext[key];
+      instance && cacheContext(workInProgress, unmaskedContext, context);
+      return context;
+    },
+    hasContextChanged: function() {
+      return didPerformWorkStackCursor.current;
+    },
+    isContextConsumer: function(fiber) {
+      return 2 === fiber.tag && null != fiber.type.contextTypes;
+    },
+    isContextProvider: isContextProvider,
+    popContextProvider: function(fiber) {
+      isContextProvider(fiber) &&
+        (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
+    },
+    popTopLevelContextObject: function(fiber) {
+      pop(didPerformWorkStackCursor, fiber);
+      pop(contextStackCursor, fiber);
+    },
+    pushTopLevelContextObject: function(fiber, context, didChange) {
+      invariant(
+        null == contextStackCursor.cursor,
+        "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
+      );
+      push(contextStackCursor, context, fiber);
+      push(didPerformWorkStackCursor, didChange, fiber);
+    },
+    processChildContext: processChildContext,
+    pushContextProvider: function(workInProgress) {
+      if (!isContextProvider(workInProgress)) return !1;
+      var instance = workInProgress.stateNode;
+      instance =
+        (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+        emptyObject;
+      previousContext = contextStackCursor.current;
+      push(contextStackCursor, instance, workInProgress);
+      push(
+        didPerformWorkStackCursor,
+        didPerformWorkStackCursor.current,
+        workInProgress
+      );
+      return !0;
+    },
+    invalidateContextProvider: function(workInProgress, didChange) {
+      var instance = workInProgress.stateNode;
+      invariant(
+        instance,
+        "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+      );
+      if (didChange) {
+        var mergedContext = processChildContext(
+          workInProgress,
+          previousContext
+        );
+        instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+        pop(didPerformWorkStackCursor, workInProgress);
+        pop(contextStackCursor, workInProgress);
+        push(contextStackCursor, mergedContext, workInProgress);
+      } else pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    },
+    findCurrentUnmaskedContext: function(fiber) {
+      for (
+        invariant(
+          2 === isFiberMountedImpl(fiber) && 2 === fiber.tag,
+          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
+        );
+        3 !== fiber.tag;
+
+      ) {
+        if (isContextProvider(fiber))
+          return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
+        fiber = fiber["return"];
+        invariant(
+          fiber,
+          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+      }
+      return fiber.stateNode.context;
     }
-    index$1 = -1;
+  };
+}
+function ReactFiberNewContext(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop,
+    providerCursor = createCursor(null),
+    valueCursor = createCursor(null),
+    changedBitsCursor = createCursor(0);
+  return {
+    pushProvider: function(providerFiber) {
+      var context = providerFiber.type.context;
+      push(changedBitsCursor, context._changedBits, providerFiber);
+      push(valueCursor, context._currentValue, providerFiber);
+      push(providerCursor, providerFiber, providerFiber);
+      context._currentValue = providerFiber.pendingProps.value;
+      context._changedBits = providerFiber.stateNode;
+    },
+    popProvider: function(providerFiber) {
+      var changedBits = changedBitsCursor.current,
+        currentValue = valueCursor.current;
+      pop(providerCursor, providerFiber);
+      pop(valueCursor, providerFiber);
+      pop(changedBitsCursor, providerFiber);
+      providerFiber = providerFiber.type.context;
+      providerFiber._currentValue = currentValue;
+      providerFiber._changedBits = changedBits;
+    }
+  };
+}
+function ReactFiberStack() {
+  var valueStack = [],
+    index = -1;
+  return {
+    createCursor: function(defaultValue) {
+      return { current: defaultValue };
+    },
+    isEmpty: function() {
+      return -1 === index;
+    },
+    pop: function(cursor) {
+      0 > index ||
+        ((cursor.current = valueStack[index]),
+        (valueStack[index] = null),
+        index--);
+    },
+    push: function(cursor, value) {
+      index++;
+      valueStack[index] = cursor.current;
+      cursor.current = value;
+    },
+    checkThatStackIsEmpty: function() {},
+    resetStackAfterFatalErrorInDev: function() {}
+  };
+}
+function ReactFiberScheduler(config) {
+  function resetStack() {
+    if (null !== nextUnitOfWork)
+      for (
+        var interruptedWork = nextUnitOfWork["return"];
+        null !== interruptedWork;
+
+      )
+        unwindInterruptedWork(interruptedWork),
+          (interruptedWork = interruptedWork["return"]);
     nextRoot = null;
     nextRenderExpirationTime = 0;
     nextUnitOfWork = null;
@@ -5145,7 +5247,7 @@ function ReactFiberScheduler(config) {
       root !== nextRoot ||
       null === nextUnitOfWork
     )
-      resetContextStack(),
+      resetStack(),
         (nextRoot = root),
         (nextRenderExpirationTime = expirationTime),
         (nextUnitOfWork = createWorkInProgress(
@@ -5275,7 +5377,7 @@ function ReactFiberScheduler(config) {
             !isWorking &&
               0 !== nextRenderExpirationTime &&
               expirationTime < nextRenderExpirationTime &&
-              resetContextStack();
+              resetStack();
             (nextRoot === root && isWorking) ||
               requestWork(root, expirationTime);
             nestedUpdateCount > NESTED_UPDATE_LIMIT &&
@@ -5619,25 +5721,37 @@ function ReactFiberScheduler(config) {
     nextFlushedRoot.remainingExpirationTime = 0;
     hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
   }
-  var hostContext = ReactFiberHostContext(config),
-    hydrationContext = ReactFiberHydrationContext(config),
-    resetHostContainer = hostContext.resetHostContainer,
+  var stack = ReactFiberStack(),
+    hostContext = ReactFiberHostContext(config, stack),
+    legacyContext = ReactFiberLegacyContext(stack);
+  stack = ReactFiberNewContext(stack);
+  var hydrationContext = ReactFiberHydrationContext(config),
     beginWork = ReactFiberBeginWork(
       config,
       hostContext,
+      legacyContext,
+      stack,
       hydrationContext,
       scheduleWork,
       computeExpirationForFiber
     ).beginWork,
-    completeWork = ReactFiberCompleteWork(config, hostContext, hydrationContext)
-      .completeWork;
+    completeWork = ReactFiberCompleteWork(
+      config,
+      hostContext,
+      legacyContext,
+      stack,
+      hydrationContext
+    ).completeWork;
   hostContext = ReactFiberUnwindWork(
     hostContext,
+    legacyContext,
+    stack,
     scheduleWork,
     isAlreadyFailedLegacyErrorBoundary
   );
   var throwException = hostContext.throwException,
-    unwindWork = hostContext.unwindWork;
+    unwindWork = hostContext.unwindWork,
+    unwindInterruptedWork = hostContext.unwindInterruptedWork;
   hostContext = ReactFiberCommitWork(
     config,
     onCommitPhaseError,
@@ -5796,7 +5910,8 @@ function ReactFiberScheduler(config) {
       result <= lastUniqueAsyncExpiration &&
         (result = lastUniqueAsyncExpiration + 1);
       return (lastUniqueAsyncExpiration = result);
-    }
+    },
+    legacyContext: legacyContext
   };
 }
 function ReactFiberReconciler$1(config) {
@@ -5811,27 +5926,7 @@ function ReactFiberReconciler$1(config) {
     currentTime = container.current;
     if (parentComponent) {
       parentComponent = parentComponent._reactInternalFiber;
-      var parentContext;
-      b: {
-        invariant(
-          2 === isFiberMountedImpl(parentComponent) &&
-            2 === parentComponent.tag,
-          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
-        );
-        for (parentContext = parentComponent; 3 !== parentContext.tag; ) {
-          if (isContextProvider(parentContext)) {
-            parentContext =
-              parentContext.stateNode.__reactInternalMemoizedMergedChildContext;
-            break b;
-          }
-          parentContext = parentContext["return"];
-          invariant(
-            parentContext,
-            "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
-          );
-        }
-        parentContext = parentContext.stateNode.context;
-      }
+      var parentContext = findCurrentUnmaskedContext(parentComponent);
       parentComponent = isContextProvider(parentComponent)
         ? processChildContext(parentComponent, parentContext)
         : parentContext;
@@ -5860,7 +5955,11 @@ function ReactFiberReconciler$1(config) {
   config = ReactFiberScheduler(config);
   var recalculateCurrentTime = config.recalculateCurrentTime,
     computeExpirationForFiber = config.computeExpirationForFiber,
-    scheduleWork = config.scheduleWork;
+    scheduleWork = config.scheduleWork,
+    legacyContext = config.legacyContext,
+    findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
   return {
     createContainer: function(containerInfo, isAsync, hydrate) {
       isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
diff --git a/Libraries/Renderer/shims/ReactFabric.js b/Libraries/Renderer/shims/ReactFabric.js
index 4a396c224cd4..6ab336bf11f0 100644
--- a/Libraries/Renderer/shims/ReactFabric.js
+++ b/Libraries/Renderer/shims/ReactFabric.js
@@ -9,6 +9,8 @@
  */
 'use strict';
 
+const BatchedBridge = require('BatchedBridge');
+
 // TODO @sema: Adjust types
 import type {ReactNativeType} from 'ReactNativeTypes';
 
@@ -20,4 +22,7 @@ if (__DEV__) {
   ReactFabric = require('ReactFabric-prod');
 }
 
+BatchedBridge.registerCallableModule('ReactFabric', ReactFabric);
+
 module.exports = (ReactFabric: ReactNativeType);
+

From f68e04136c1af90a378e9f76607506edee63f906 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Tue, 20 Mar 2018 19:11:54 -0700
Subject: [PATCH 0099/1109] Move TypeForStyleKey from StyleSheetTypes to
 StyleSheet

Reviewed By: yungsters

Differential Revision: D7281362

fbshipit-source-id: 936d198e83dfbfc62449e82b5559a30bd57621c4
---
 Libraries/StyleSheet/StyleSheet.js      | 35 +++++++++++++++++++++++++
 Libraries/StyleSheet/StyleSheetTypes.js | 25 +++---------------
 Libraries/StyleSheet/flattenStyle.js    |  6 +++--
 3 files changed, 42 insertions(+), 24 deletions(-)

diff --git a/Libraries/StyleSheet/StyleSheet.js b/Libraries/StyleSheet/StyleSheet.js
index f2552f3e66d1..db35fc8424af 100644
--- a/Libraries/StyleSheet/StyleSheet.js
+++ b/Libraries/StyleSheet/StyleSheet.js
@@ -20,6 +20,7 @@ const flatten = require('flattenStyle');
 import type {
   ____StyleSheetInternalStyleIdentifier_Internal as StyleSheetInternalStyleIdentifier,
   ____Styles_Internal,
+  ____DangerouslyImpreciseStyle_Internal,
   ____DangerouslyImpreciseStyleProp_Internal,
   ____ViewStyleProp_Internal,
   ____TextStyleProp_Internal,
@@ -66,6 +67,40 @@ export type ImageStyleProp = ____ImageStyleProp_Internal;
  */
 export type DangerouslyImpreciseStyleProp = ____DangerouslyImpreciseStyleProp_Internal;
 
+/**
+ * Utility type for getting the values for specific style keys.
+ *
+ * The following is bad because position is more restrictive than 'string':
+ * ```
+ * type Props = {position: string};
+ * ```
+ *
+ * You should use the following instead:
+ *
+ * ```
+ * type Props = {position: TypeForStyleKey<'position'>};
+ * ```
+ *
+ * This will correctly give you the type 'absolute' | 'relative'
+ */
+export type TypeForStyleKey<
+  +key: $Keys<____DangerouslyImpreciseStyle_Internal>,
+> = $ElementType<____DangerouslyImpreciseStyle_Internal, key>;
+
+/**
+ * WARNING: You probably shouldn't be using this type. This type is an object
+ * with all possible style key's and their values. Note that this isn't
+ * a safe way to type a style prop for a component as results from
+ * StyleSheet.create return an internal identifier, not an object of styles.
+ *
+ * If you want to type the style prop of a function, consider using
+ * ViewStyleProp, TextStyleProp, or ImageStyleProp.
+ *
+ * This should only be used by very core utilities that operate on an object
+ * containing any possible style value.
+ */
+export type DangerouslyImpreciseStyle = ____DangerouslyImpreciseStyle_Internal;
+
 let hairlineWidth = PixelRatio.roundToNearestPixel(0.4);
 if (hairlineWidth === 0) {
   hairlineWidth = 1 / PixelRatio.get();
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index b9c3c59fd2d3..19b57c700c18 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -213,7 +213,7 @@ export type ImageStyle = $ReadOnly<{|
   overlayColor?: string,
 |}>;
 
-export type DangerouslyImpreciseStyle = {
+export type ____DangerouslyImpreciseStyle_Internal = {
   ...$Exact<TextStyle>,
   +resizeMode?: 'contain' | 'cover' | 'stretch' | 'center' | 'repeat',
   +tintColor?: ColorValue,
@@ -231,7 +231,7 @@ type GenericStyleProp<+T> =
   | $ReadOnlyArray<GenericStyleProp<T>>;
 
 export type ____DangerouslyImpreciseStyleProp_Internal = GenericStyleProp<
-  $Shape<DangerouslyImpreciseStyle>,
+  $Shape<____DangerouslyImpreciseStyle_Internal>,
 >;
 export type ____ViewStyleProp_Internal = GenericStyleProp<
   $ReadOnly<$Shape<ViewStyle>>,
@@ -244,24 +244,5 @@ export type ____ImageStyleProp_Internal = GenericStyleProp<
 >;
 
 export type ____Styles_Internal = {
-  +[key: string]: $Shape<DangerouslyImpreciseStyle>,
+  +[key: string]: $Shape<____DangerouslyImpreciseStyle_Internal>,
 };
-
-/*
-Utility type get non-nullable types for specific style keys.
-Useful when a component requires values for certain Style Keys.
-So Instead:
-```
-type Props = {position: string};
-```
-You should use:
-```
-type Props = {position: TypeForStyleKey<'position'>};
-```
-
-This will correctly give you the type 'absolute' | 'relative' instead of the
-weak type of just string;
-*/
-export type TypeForStyleKey<
-  +key: $Keys<DangerouslyImpreciseStyle>,
-> = $ElementType<DangerouslyImpreciseStyle, key>;
diff --git a/Libraries/StyleSheet/flattenStyle.js b/Libraries/StyleSheet/flattenStyle.js
index 37ac2d434a0f..3ef381d0b6a2 100644
--- a/Libraries/StyleSheet/flattenStyle.js
+++ b/Libraries/StyleSheet/flattenStyle.js
@@ -12,8 +12,10 @@
 
 var ReactNativePropRegistry;
 
-import type {DangerouslyImpreciseStyleProp} from 'StyleSheet';
-import type {DangerouslyImpreciseStyle} from 'StyleSheetTypes';
+import type {
+  DangerouslyImpreciseStyle,
+  DangerouslyImpreciseStyleProp,
+} from 'StyleSheet';
 
 function getStyle(style) {
   if (ReactNativePropRegistry === undefined) {

From a0388f4adc693bfc11279a5c9513ca3ee1348ed0 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Tue, 20 Mar 2018 19:11:56 -0700
Subject: [PATCH 0100/1109] Move ViewStyle, TextStyle, ImageStyle from
 StyleSheetTypes to StyleSheet

Reviewed By: yungsters

Differential Revision: D7282491

fbshipit-source-id: d6b54d0a2e1fe1816b6a856b1b0b1245a655320a
---
 Libraries/StyleSheet/StyleSheet.js      | 56 ++++++++++++++++++++++++-
 Libraries/StyleSheet/StyleSheetTypes.js | 18 ++++----
 2 files changed, 64 insertions(+), 10 deletions(-)

diff --git a/Libraries/StyleSheet/StyleSheet.js b/Libraries/StyleSheet/StyleSheet.js
index db35fc8424af..c2579f21a361 100644
--- a/Libraries/StyleSheet/StyleSheet.js
+++ b/Libraries/StyleSheet/StyleSheet.js
@@ -22,8 +22,11 @@ import type {
   ____Styles_Internal,
   ____DangerouslyImpreciseStyle_Internal,
   ____DangerouslyImpreciseStyleProp_Internal,
+  ____ViewStyle_Internal,
   ____ViewStyleProp_Internal,
+  ____TextStyle_Internal,
   ____TextStyleProp_Internal,
+  ____ImageStyle_Internal,
   ____ImageStyleProp_Internal,
   LayoutStyle,
 } from 'StyleSheetTypes';
@@ -87,9 +90,60 @@ export type TypeForStyleKey<
   +key: $Keys<____DangerouslyImpreciseStyle_Internal>,
 > = $ElementType<____DangerouslyImpreciseStyle_Internal, key>;
 
+/**
+ * This type is an object of the different possible style
+ * properties that can be specified for View.
+ *
+ * Note that this isn't a safe way to type a style prop for a component as
+ * results from StyleSheet.create return an internal identifier, not
+ * an object of styles.
+ *
+ * If you want to type the style prop of a function,
+ * consider using ViewStyleProp.
+ *
+ * A reasonable usage of this type is for helper functions that return an
+ * object of styles to pass to a View that can't be precomputed with
+ * StyleSheet.create.
+ */
+export type ViewStyle = ____ViewStyle_Internal;
+
+/**
+ * This type is an object of the different possible style
+ * properties that can be specified for Text.
+ *
+ * Note that this isn't a safe way to type a style prop for a component as
+ * results from StyleSheet.create return an internal identifier, not
+ * an object of styles.
+ *
+ * If you want to type the style prop of a function,
+ * consider using TextStyleProp.
+ *
+ * A reasonable usage of this type is for helper functions that return an
+ * object of styles to pass to a Text that can't be precomputed with
+ * StyleSheet.create.
+ */
+export type TextStyle = ____TextStyle_Internal;
+
+/**
+ * This type is an object of the different possible style
+ * properties that can be specified for Image.
+ *
+ * Note that this isn't a safe way to type a style prop for a component as
+ * results from StyleSheet.create return an internal identifier, not
+ * an object of styles.
+ *
+ * If you want to type the style prop of a function,
+ * consider using ImageStyleProp.
+ *
+ * A reasonable usage of this type is for helper functions that return an
+ * object of styles to pass to an Image that can't be precomputed with
+ * StyleSheet.create.
+ */
+export type ImageStyle = ____ImageStyle_Internal;
+
 /**
  * WARNING: You probably shouldn't be using this type. This type is an object
- * with all possible style key's and their values. Note that this isn't
+ * with all possible style keys and their values. Note that this isn't
  * a safe way to type a style prop for a component as results from
  * StyleSheet.create return an internal identifier, not an object of styles.
  *
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index 19b57c700c18..44688ef72087 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -126,7 +126,7 @@ export type ShadowStyle = $ReadOnly<{|
   shadowRadius?: number,
 |}>;
 
-export type ViewStyle = $ReadOnly<{|
+export type ____ViewStyle_Internal = $ReadOnly<{|
   ...$Exact<LayoutStyle>,
   ...$Exact<ShadowStyle>,
   ...$Exact<TransformStyle>,
@@ -160,8 +160,8 @@ export type ViewStyle = $ReadOnly<{|
   elevation?: number,
 |}>;
 
-export type TextStyle = $ReadOnly<{|
-  ...$Exact<ViewStyle>,
+export type ____TextStyle_Internal = $ReadOnly<{|
+  ...$Exact<____ViewStyle_Internal>,
   color?: ColorValue,
   fontFamily?: string,
   fontSize?: number,
@@ -206,15 +206,15 @@ export type TextStyle = $ReadOnly<{|
   writingDirection?: 'auto' | 'ltr' | 'rtl',
 |}>;
 
-export type ImageStyle = $ReadOnly<{|
-  ...$Exact<ViewStyle>,
+export type ____ImageStyle_Internal = $ReadOnly<{|
+  ...$Exact<____ViewStyle_Internal>,
   resizeMode?: 'contain' | 'cover' | 'stretch' | 'center' | 'repeat',
   tintColor?: ColorValue,
   overlayColor?: string,
 |}>;
 
 export type ____DangerouslyImpreciseStyle_Internal = {
-  ...$Exact<TextStyle>,
+  ...$Exact<____TextStyle_Internal>,
   +resizeMode?: 'contain' | 'cover' | 'stretch' | 'center' | 'repeat',
   +tintColor?: ColorValue,
   +overlayColor?: string,
@@ -234,13 +234,13 @@ export type ____DangerouslyImpreciseStyleProp_Internal = GenericStyleProp<
   $Shape<____DangerouslyImpreciseStyle_Internal>,
 >;
 export type ____ViewStyleProp_Internal = GenericStyleProp<
-  $ReadOnly<$Shape<ViewStyle>>,
+  $ReadOnly<$Shape<____ViewStyle_Internal>>,
 >;
 export type ____TextStyleProp_Internal = GenericStyleProp<
-  $ReadOnly<$Shape<TextStyle>>,
+  $ReadOnly<$Shape<____TextStyle_Internal>>,
 >;
 export type ____ImageStyleProp_Internal = GenericStyleProp<
-  $ReadOnly<$Shape<ImageStyle>>,
+  $ReadOnly<$Shape<____ImageStyle_Internal>>,
 >;
 
 export type ____Styles_Internal = {

From a3f1ca84afe4dca0c0255c68e84e0bcb8ad29c14 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 20 Mar 2018 19:19:17 -0700
Subject: [PATCH 0101/1109] Bump metro@0.31.0

Reviewed By: mjesun

Differential Revision: D7336904

fbshipit-source-id: 2132c77d07e52a91f09b6f905bee4806aaf7d23e
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index e7a8250c4d16..eb2c29584298 100644
--- a/package.json
+++ b/package.json
@@ -175,8 +175,8 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.30.2",
-    "metro-core": "^0.30.2",
+    "metro": "^0.31.0",
+    "metro-core": "^0.31.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 657c1a45bd007f8c837237ee2c2c2e27a5d8ac11 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 20 Mar 2018 19:20:33 -0700
Subject: [PATCH 0102/1109] Add more debug logs to FabricReconciler

Reviewed By: mdvacca

Differential Revision: D7338946

fbshipit-source-id: 839de31ca26a8e45d3bb3271d3ab5a4f53f639b0
---
 .../react/fabric/FabricReconciler.java        | 45 +++++++++++--------
 1 file changed, 27 insertions(+), 18 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index 3d7571e496b9..eba24f2754ef 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -59,12 +59,7 @@ private void manageChildren(
       if (prevNode.getReactTag() != newNode.getReactTag()) {
         break;
       }
-
-      if (newNode.getNewProps() != null) {
-        uiViewOperationQueue.enqueueUpdateProperties(
-          newNode.getReactTag(), newNode.getViewClass(), newNode.getNewProps());
-      }
-
+      enqueueUpdateProperties(newNode);
       manageChildren(prevNode, prevNode.getChildrenList(), newNode.getChildrenList());
       prevNode.setOriginalReactShadowNode(newNode);
     }
@@ -79,10 +74,7 @@ private void manageChildren(
     for (int k = firstRemovedOrAddedViewIndex; k < newList.size(); k++) {
       ReactShadowNode newNode = newList.get(k);
       if (newNode.isVirtual()) continue;
-      if (newNode.getNewProps() != null) {
-        uiViewOperationQueue.enqueueUpdateProperties(
-          newNode.getReactTag(), newNode.getViewClass(), newNode.getNewProps());
-      }
+      enqueueUpdateProperties(newNode);
       viewsToAdd.add(new ViewAtIndex(newNode.getReactTag(), k));
       List previousChildrenList = newNode.getOriginalReactShadowNode() == null ? null : newNode.getOriginalReactShadowNode().getChildrenList();
       manageChildren(newNode, previousChildrenList, newNode.getChildrenList());
@@ -113,19 +105,36 @@ private void manageChildren(
 
     int[] tagsToDeleteArray = ArrayUtils.copyListToArray(tagsToDelete);
     ViewAtIndex[] viewsToAddArray = viewsToAdd.toArray(new ViewAtIndex[viewsToAdd.size()]);
-    if (DEBUG) {
-      Log.d(
-        TAG,
-        "manageChildren.enqueueManageChildren parent: " + parent.getReactTag() +
-          "\n\tIndices2Remove: " + Arrays.toString(indicesToRemove) +
-          "\n\tViews2Add: " + Arrays.toString(viewsToAddArray) +
-          "\n\tTags2Delete: " + Arrays.toString(tagsToDeleteArray));
-    }
+
     // TODO (t27180994): Mutate views synchronously on main thread
     if (indicesToRemove.length > 0 || viewsToAddArray.length > 0 || tagsToDeleteArray.length > 0) {
+      if (DEBUG) {
+        Log.d(
+            TAG,
+            "manageChildren.enqueueManageChildren parent: " + parent.getReactTag() +
+                "\n\tIndices2Remove: " + Arrays.toString(indicesToRemove) +
+                "\n\tViews2Add: " + Arrays.toString(viewsToAddArray) +
+                "\n\tTags2Delete: " + Arrays.toString(tagsToDeleteArray));
+      }
       uiViewOperationQueue.enqueueManageChildren(
         parent.getReactTag(), indicesToRemove, viewsToAddArray, tagsToDeleteArray);
     }
   }
 
+  private void enqueueUpdateProperties(ReactShadowNode node) {
+    if (node.getNewProps() == null) {
+      return;
+    }
+    if (DEBUG) {
+      Log.d(
+          TAG,
+          "manageChildren.enqueueUpdateProperties " +
+              "\n\ttag: " + node.getReactTag() +
+              "\n\tviewClass: " + node.getViewClass() +
+              "\n\tnewProps: " + node.getNewProps());
+    }
+    uiViewOperationQueue.enqueueUpdateProperties(
+        node.getReactTag(), node.getViewClass(), node.getNewProps());
+  }
+
 }

From b961ac3effec2e97db011cdea3e866891aa1d13a Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Wed, 21 Mar 2018 09:27:25 -0700
Subject: [PATCH 0103/1109] Depend on local version of
 babel-plugin-react-transform

Reviewed By: arcanis

Differential Revision: D7337432

fbshipit-source-id: 3729359da0ccfd3161546ab3ea9331ad30fb6e8d
---
 babel-preset/configs/hmr.js | 7 +++----
 1 file changed, 3 insertions(+), 4 deletions(-)

diff --git a/babel-preset/configs/hmr.js b/babel-preset/configs/hmr.js
index 91cb9a356c65..cdf5a022c202 100644
--- a/babel-preset/configs/hmr.js
+++ b/babel-preset/configs/hmr.js
@@ -7,7 +7,6 @@
 'use strict';
 
 var path = require('path');
-var resolvePlugins = require('../lib/resolvePlugins');
 
 var hmrTransform = 'react-transform-hmr/lib/index.js';
 var transformPath = require.resolve(hmrTransform);
@@ -23,9 +22,9 @@ module.exports = function(options, filename) {
   }
 
   return {
-    plugins: resolvePlugins([
+    plugins: [
       [
-        'react-transform',
+        require('metro-babel7-plugin-react-transform').default,
         {
           transforms: [{
             transform: transform,
@@ -34,6 +33,6 @@ module.exports = function(options, filename) {
           }]
         },
       ]
-    ])
+    ]
   };
 };

From 0594a109d157843af9e95061e6f72ba847d5549c Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Wed, 21 Mar 2018 10:18:57 -0700
Subject: [PATCH 0104/1109] Removed unnecessary `intrinsicContentSize`
 implementation from `RCTSurfaceHostingProxyRootView`

Summary:
The base class already implements `intrinsicContentSize` (and it's a bit more complicated that that).
(Not sure if this change anything visible.)

Reviewed By: fkgozali

Differential Revision: D7343567

fbshipit-source-id: 86f86715b0dacc3c2230289a13926f0520540089
---
 .../SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm     | 5 -----
 1 file changed, 5 deletions(-)

diff --git a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm
index 076773a58b56..14466297473e 100644
--- a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm
+++ b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingProxyRootView.mm
@@ -130,11 +130,6 @@ - (void)setAppProperties:(NSDictionary *)appProperties
   [super.surface setProperties:appProperties];
 }
 
-- (CGSize)intrinsicContentSize
-{
-  return super.surface.intrinsicSize;
-}
-
 - (UIView *)loadingView
 {
   return super.activityIndicatorViewFactory ? super.activityIndicatorViewFactory() : nil;

From 909861ff058b7b6e458ac4f0786b11d9cf18f669 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Wed, 21 Mar 2018 10:18:59 -0700
Subject: [PATCH 0105/1109] Fixed race condition in RCTUIManager's mounting
 process

Summary:
See the comment in code.
This picture also illustrates the problem: https://cl.ly/250z0D1B0c17.
https://pxl.cl/ckBq

Reviewed By: fkgozali

Differential Revision: D7343566

fbshipit-source-id: e45a691add5e43434dea8708be4b76ff18e52131
---
 React/Modules/RCTUIManager.m | 23 +++++++++++++++++++++++
 1 file changed, 23 insertions(+)

diff --git a/React/Modules/RCTUIManager.m b/React/Modules/RCTUIManager.m
index 5dcce46588ba..4653e239ed3f 100644
--- a/React/Modules/RCTUIManager.m
+++ b/React/Modules/RCTUIManager.m
@@ -69,6 +69,9 @@ @implementation RCTUIManager
 
   // Keyed by viewName
   NSDictionary *_componentDataByName;
+
+  BOOL _isMountingInProgress;
+  BOOL _isRemountingNeeded;
 }
 
 @synthesize bridge = _bridge;
@@ -1046,6 +1049,19 @@ - (void)batchDidComplete
  */
 - (void)_layoutAndMount
 {
+  // Mounting is (usually, not always) an asynchronous process.
+  // So, we have to ensure that there is no any case of self-interleaving
+  // (when another mourning process is initiated before the previous
+  // one finishes) here.
+  if (_isMountingInProgress) {
+    // In a case when another mounting process hasn't completed yet,
+    // we have to run another pass right after it finishes.
+    _isRemountingNeeded = YES;
+    return;
+  }
+
+  _isMountingInProgress = YES;
+
   [self _dispatchPropsDidChangeEvents];
   [self _dispatchChildrenDidChangeEvents];
 
@@ -1063,6 +1079,13 @@ - (void)_layoutAndMount
 
   [self flushUIBlocksWithCompletion:^{
     [self->_observerCoordinator uiManagerDidPerformMounting:self];
+
+    self->_isMountingInProgress = NO;
+
+    if (self->_isRemountingNeeded) {
+      self->_isRemountingNeeded = NO;
+      [self _layoutAndMount];
+    }
   }];
 }
 

From c194c18126ab890657902e5fff0fec1d3b311633 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Wed, 21 Mar 2018 10:19:01 -0700
Subject: [PATCH 0106/1109] Fixed performance regression in `ShadowView`s
 layout process

Summary:
This fixes perf regression which was introduced by recent refactoring of the layout process.
That is how it used to be:
https://github.com/facebook/react-native/blob/114c258045ccca3a4433de206c7983b42d14c03b/React/Views/RCTShadowView.m#L160-L166
Note: We have to resert this flag in indication that we already applied those changes and we don't need to traverse this subtree until it is changed again.

Reviewed By: fkgozali

Differential Revision: D7343564

fbshipit-source-id: ba7e00bc5fe4992d777eed20ba0d959fd8f6c037
---
 React/Views/RCTShadowView.m | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/React/Views/RCTShadowView.m b/React/Views/RCTShadowView.m
index f29dbcbbd363..457117653900 100644
--- a/React/Views/RCTShadowView.m
+++ b/React/Views/RCTShadowView.m
@@ -284,6 +284,8 @@ - (void)layoutWithMinimumSize:(CGSize)minimumSize
     return;
   }
 
+  YGNodeSetHasNewLayout(yogaNode, false);
+
   RCTLayoutMetrics layoutMetrics = RCTLayoutMetricsFromYogaNode(yogaNode);
 
   layoutContext.absolutePosition.x += layoutMetrics.frame.origin.x;
@@ -321,6 +323,8 @@ - (void)layoutSubviewsWithContext:(RCTLayoutContext)layoutContext
       continue;
     }
 
+    YGNodeSetHasNewLayout(childYogaNode, false);
+
     RCTLayoutMetrics childLayoutMetrics = RCTLayoutMetricsFromYogaNode(childYogaNode);
 
     layoutContext.absolutePosition.x += childLayoutMetrics.frame.origin.x;

From d50cefb1f25045bf676b52bcb5cbd169ff4069d0 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 21 Mar 2018 14:02:30 -0700
Subject: [PATCH 0107/1109] Moving remaining Style types from StyleSheetTypes
 to StyleSheet

Reviewed By: yungsters

Differential Revision: D7282831

fbshipit-source-id: ced44d79ad30b7abdda77a25b72493899c2108e4
---
 Libraries/StyleSheet/StyleSheet.js      | 13 ++++++++++++-
 Libraries/StyleSheet/StyleSheetTypes.js | 12 ++++++------
 2 files changed, 18 insertions(+), 7 deletions(-)

diff --git a/Libraries/StyleSheet/StyleSheet.js b/Libraries/StyleSheet/StyleSheet.js
index c2579f21a361..ec20623d8a27 100644
--- a/Libraries/StyleSheet/StyleSheet.js
+++ b/Libraries/StyleSheet/StyleSheet.js
@@ -28,7 +28,9 @@ import type {
   ____TextStyleProp_Internal,
   ____ImageStyle_Internal,
   ____ImageStyleProp_Internal,
-  LayoutStyle,
+  ____LayoutStyle_Internal,
+  ____ShadowStyle_Internal,
+  ____TransformStyle_Internal,
 } from 'StyleSheetTypes';
 
 /**
@@ -155,6 +157,15 @@ export type ImageStyle = ____ImageStyle_Internal;
  */
 export type DangerouslyImpreciseStyle = ____DangerouslyImpreciseStyle_Internal;
 
+/**
+ * These types are simlilar to the style types above. They are objects of the
+ * possible style keys in that group. For example, ShadowStyle contains
+ * keys like `shadowColor` and `shadowRadius`.
+ */
+export type LayoutStyle = ____LayoutStyle_Internal;
+export type ShadowStyle = ____ShadowStyle_Internal;
+export type TransformStyle = ____TransformStyle_Internal;
+
 let hairlineWidth = PixelRatio.roundToNearestPixel(0.4);
 if (hairlineWidth === 0) {
   hairlineWidth = 1 / PixelRatio.get();
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index 44688ef72087..6ff412ce8a67 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -18,7 +18,7 @@ export opaque type ____StyleSheetInternalStyleIdentifier_Internal: number = numb
 export type ColorValue = null | string;
 export type DimensionValue = null | number | string | AnimatedNode;
 
-export type LayoutStyle = $ReadOnly<{|
+export type ____LayoutStyle_Internal = $ReadOnly<{|
   display?: 'none' | 'flex',
   width?: DimensionValue,
   height?: DimensionValue,
@@ -92,7 +92,7 @@ export type LayoutStyle = $ReadOnly<{|
   direction?: 'inherit' | 'ltr' | 'rtl',
 |}>;
 
-export type TransformStyle = $ReadOnly<{|
+export type ____TransformStyle_Internal = $ReadOnly<{|
   transform?: $ReadOnlyArray<
     | {|+perspective: number | AnimatedNode|}
     | {|+rotate: string|}
@@ -116,7 +116,7 @@ export type TransformStyle = $ReadOnly<{|
   >,
 |}>;
 
-export type ShadowStyle = $ReadOnly<{|
+export type ____ShadowStyle_Internal = $ReadOnly<{|
   shadowColor?: ColorValue,
   shadowOffset?: $ReadOnly<{|
     width?: number,
@@ -127,9 +127,9 @@ export type ShadowStyle = $ReadOnly<{|
 |}>;
 
 export type ____ViewStyle_Internal = $ReadOnly<{|
-  ...$Exact<LayoutStyle>,
-  ...$Exact<ShadowStyle>,
-  ...$Exact<TransformStyle>,
+  ...$Exact<____LayoutStyle_Internal>,
+  ...$Exact<____ShadowStyle_Internal>,
+  ...$Exact<____TransformStyle_Internal>,
   backfaceVisibility?: 'visible' | 'hidden',
   backgroundColor?: ColorValue,
   borderColor?: ColorValue,

From cf036dbc7af16a8453c115372694dc51e8086fcf Mon Sep 17 00:00:00 2001
From: Orta <orta.therox+github@gmail.com>
Date: Wed, 21 Mar 2018 14:12:08 -0700
Subject: [PATCH 0108/1109] Updates Yoga to handle being in a Xcode framework
 project
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
Updates the Yoga Podspec to work with Cocoa frameworks. Replicated a2's work over on Yoga https://github.com/facebook/yoga/pull/726

(Which should also get merged too please ❤️ )

Set it manually in my own project and tested 👍

Only https://github.com/facebook/yoga/pull/726

[IOS] [BUGFIX] [Yoga] - Fixes to yoga.podspec when integrating into an iOS app using Cocoa frameworks.
Closes https://github.com/facebook/react-native/pull/18492

Differential Revision: D7355907

Pulled By: hramos

fbshipit-source-id: 6986d2bc560a23bb7f0f20b80e88bb440079891a
---
 ReactCommon/yoga/yoga.podspec | 6 +++++-
 1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/yoga/yoga.podspec b/ReactCommon/yoga/yoga.podspec
index c38f4c09796c..69144f9bb01b 100644
--- a/ReactCommon/yoga/yoga.podspec
+++ b/ReactCommon/yoga/yoga.podspec
@@ -36,9 +36,13 @@ Pod::Spec.new do |spec|
   # Pinning to the same version as React.podspec.
   spec.platforms = { :ios => "8.0", :tvos => "9.2" }
 
-  # Set this environment variable when not using the `:path` option to install the pod.
+  # Set this environment variable when *not* using the `:path` option to install the pod.
   # E.g. when publishing this spec to a spec repo.
   source_files = 'yoga/**/*.{cpp,h}'
   source_files = File.join('ReactCommon/yoga', source_files) if ENV['INSTALL_YOGA_WITHOUT_PATH_OPTION']
   spec.source_files = source_files
+  
+  header_files = 'yoga/{Yoga,YGEnums,YGMacros}.h'
+  header_files = File.join('ReactCommon/yoga', header_files) if ENV['INSTALL_YOGA_WITHOUT_PATH_OPTION']
+  spec.public_header_files = header_files
 end

From c0d27de37eec7b6860387e35dae4dfc455d4b6e2 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 21 Mar 2018 14:21:37 -0700
Subject: [PATCH 0109/1109] Fix removal of virtual nodes in FabricReconciler

Reviewed By: mdvacca

Differential Revision: D7338949

fbshipit-source-id: 31263c138689f9b3f59deb26851132df04b8a823
---
 .../react/fabric/FabricReconciler.java        | 19 +++++++++----------
 .../facebook/react/uimanager/ViewAtIndex.java | 11 ++++++++++-
 2 files changed, 19 insertions(+), 11 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index eba24f2754ef..cc851c228fe2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -89,12 +89,11 @@ private void manageChildren(
     // If a View is not re-ordered, then the ReactTag is deleted (ReactShadowNode and native View
     // are released from memory)
     List<Integer> tagsToDelete = new LinkedList<>();
-    int[] indicesToRemove = new int[prevList.size() - firstRemovedOrAddedViewIndex];
-    int indicesToRemoveIndex = 0;
-    for (int j = firstRemovedOrAddedViewIndex; j < prevList.size(); j++) {
+    List<Integer> indicesToRemove = new LinkedList<>();
+    for (int j = prevList.size() - 1; j >= firstRemovedOrAddedViewIndex; j--) {
       ReactShadowNode nodeToRemove = prevList.get(j);
       if (nodeToRemove.isVirtual()) continue;
-      indicesToRemove[indicesToRemoveIndex++] = j;
+      indicesToRemove.add(0, j);
       if (!addedTags.contains(nodeToRemove.getReactTag())) {
         tagsToDelete.add(nodeToRemove.getReactTag());
         // TODO: T26729293 since we are not cloning ReactShadowNode's we need to "manually" remove
@@ -103,21 +102,21 @@ private void manageChildren(
       }
     }
 
-    int[] tagsToDeleteArray = ArrayUtils.copyListToArray(tagsToDelete);
-    ViewAtIndex[] viewsToAddArray = viewsToAdd.toArray(new ViewAtIndex[viewsToAdd.size()]);
-
     // TODO (t27180994): Mutate views synchronously on main thread
-    if (indicesToRemove.length > 0 || viewsToAddArray.length > 0 || tagsToDeleteArray.length > 0) {
+    if (!(indicesToRemove.isEmpty() && viewsToAdd.isEmpty() && tagsToDelete.isEmpty())) {
+      int[] indicesToRemoveArray = ArrayUtils.copyListToArray(indicesToRemove);
+      ViewAtIndex[] viewsToAddArray = viewsToAdd.toArray(new ViewAtIndex[viewsToAdd.size()]);
+      int[] tagsToDeleteArray = ArrayUtils.copyListToArray(tagsToDelete);
       if (DEBUG) {
         Log.d(
             TAG,
             "manageChildren.enqueueManageChildren parent: " + parent.getReactTag() +
-                "\n\tIndices2Remove: " + Arrays.toString(indicesToRemove) +
+                "\n\tIndices2Remove: " + Arrays.toString(indicesToRemoveArray) +
                 "\n\tViews2Add: " + Arrays.toString(viewsToAddArray) +
                 "\n\tTags2Delete: " + Arrays.toString(tagsToDeleteArray));
       }
       uiViewOperationQueue.enqueueManageChildren(
-        parent.getReactTag(), indicesToRemove, viewsToAddArray, tagsToDeleteArray);
+        parent.getReactTag(), indicesToRemoveArray, viewsToAddArray, tagsToDeleteArray);
     }
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewAtIndex.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewAtIndex.java
index ef2a914d3cf3..c242d7c310dd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewAtIndex.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewAtIndex.java
@@ -29,8 +29,17 @@ public ViewAtIndex(int tag, int index) {
     mIndex = index;
   }
 
+  @Override
+  public boolean equals(Object obj) {
+    if (obj == null || obj.getClass() != getClass()) {
+      return false;
+    }
+    ViewAtIndex other = (ViewAtIndex) obj;
+    return mIndex == other.mIndex && mTag == other.mTag;
+  }
+
   @Override
   public String toString() {
-    return "[" + mIndex + ", " + mTag + "]";
+    return "[" + mTag + ", " + mIndex + "]";
   }
 }

From 0b085a80bdd8ac68347de9cd7610e0991cb4a85a Mon Sep 17 00:00:00 2001
From: Jonathan Dann <jonathan@fb.com>
Date: Wed, 21 Mar 2018 16:05:09 -0700
Subject: [PATCH 0110/1109] Pass-by-reference in YGNode::setStyle()
 ::setChildren() ::setLayout()

Reviewed By: priteshrnandgaonkar

Differential Revision: D7291096

fbshipit-source-id: 7a4025831811d622050adbb5f86608855b94d68e
---
 ReactCommon/yoga/yoga/YGNode.cpp | 6 +++---
 ReactCommon/yoga/yoga/YGNode.h   | 6 +++---
 2 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 5a33c6e86e73..7a71058a7b81 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -225,11 +225,11 @@ void YGNode::setDirtiedFunc(YGDirtiedFunc dirtiedFunc) {
   dirtied_ = dirtiedFunc;
 }
 
-void YGNode::setStyle(YGStyle style) {
+void YGNode::setStyle(const YGStyle& style) {
   style_ = style;
 }
 
-void YGNode::setLayout(YGLayout layout) {
+void YGNode::setLayout(const YGLayout& layout) {
   layout_ = layout;
 }
 
@@ -241,7 +241,7 @@ void YGNode::setParent(YGNodeRef parent) {
   parent_ = parent;
 }
 
-void YGNode::setChildren(YGVector children) {
+void YGNode::setChildren(const YGVector& children) {
   children_ = children;
 }
 
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 27a1ed68fac1..081bc235c2e3 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -106,13 +106,13 @@ struct YGNode {
   void setMeasureFunc(YGMeasureFunc measureFunc);
   void setBaseLineFunc(YGBaselineFunc baseLineFunc);
   void setDirtiedFunc(YGDirtiedFunc dirtiedFunc);
-  void setStyle(YGStyle style);
+  void setStyle(const YGStyle& style);
   void setStyleFlexDirection(YGFlexDirection direction);
   void setStyleAlignContent(YGAlign alignContent);
-  void setLayout(YGLayout layout);
+  void setLayout(const YGLayout& layout);
   void setLineIndex(uint32_t lineIndex);
   void setParent(YGNodeRef parent);
-  void setChildren(YGVector children);
+  void setChildren(const YGVector& children);
   void setNextChild(YGNodeRef nextChild);
   void setConfig(YGConfigRef config);
   void setDirty(bool isDirty);

From ed0ba1bfc7ae4e213b1c4362f812da05f4e299ce Mon Sep 17 00:00:00 2001
From: Jonathan Dann <jonathan@fb.com>
Date: Wed, 21 Mar 2018 16:05:10 -0700
Subject: [PATCH 0111/1109] Pass some constructor argumetns by const-reference

Reviewed By: priteshrnandgaonkar

Differential Revision: D7291363

fbshipit-source-id: 22e606d0b3fa1133d7e0334c8cf9f5f1f32fe64b
---
 ReactCommon/yoga/yoga/YGNode.cpp | 4 ++--
 ReactCommon/yoga/yoga/YGNode.h   | 4 ++--
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 7a71058a7b81..37b630426b77 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -423,10 +423,10 @@ YGNode::YGNode(
     YGBaselineFunc baseline,
     YGDirtiedFunc dirtied,
     YGStyle style,
-    YGLayout layout,
+    const YGLayout& layout,
     uint32_t lineIndex,
     YGNodeRef parent,
-    YGVector children,
+    const YGVector& children,
     YGNodeRef nextChild,
     YGConfigRef config,
     bool isDirty,
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 081bc235c2e3..c9c5599c0909 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -47,10 +47,10 @@ struct YGNode {
       YGBaselineFunc baseline,
       YGDirtiedFunc dirtied,
       YGStyle style,
-      YGLayout layout,
+      const YGLayout& layout,
       uint32_t lineIndex,
       YGNodeRef parent,
-      YGVector children,
+      const YGVector& children,
       YGNodeRef nextChild,
       YGConfigRef config,
       bool isDirty,

From cb3103ce0916ce1e7863fc3baa98f173c1d480aa Mon Sep 17 00:00:00 2001
From: Jonathan Dann <jonathan@fb.com>
Date: Wed, 21 Mar 2018 16:05:12 -0700
Subject: [PATCH 0112/1109] Mark more member functions as const

Reviewed By: priteshrnandgaonkar

Differential Revision: D7291364

fbshipit-source-id: 2e7d96cfe0345692ffa411bb21a80eb7a859880b
---
 ReactCommon/yoga/yoga/YGNode.cpp | 26 +++++++++++++-------------
 ReactCommon/yoga/yoga/YGNode.h   | 26 +++++++++++++-------------
 2 files changed, 26 insertions(+), 26 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 37b630426b77..8fcb44c39dcb 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -87,7 +87,7 @@ std::array<YGValue, 2> YGNode::getResolvedDimensions() const {
 
 float YGNode::getLeadingPosition(
     const YGFlexDirection axis,
-    const float axisSize) {
+    const float axisSize) const {
   if (YGFlexDirectionIsRow(axis)) {
     const YGValue* leadingPosition =
         YGComputedEdgeValue(style_.position, YGEdgeStart, &YGValueUndefined);
@@ -106,7 +106,7 @@ float YGNode::getLeadingPosition(
 
 float YGNode::getTrailingPosition(
     const YGFlexDirection axis,
-    const float axisSize) {
+    const float axisSize) const {
   if (YGFlexDirectionIsRow(axis)) {
     const YGValue* trailingPosition =
         YGComputedEdgeValue(style_.position, YGEdgeEnd, &YGValueUndefined);
@@ -123,7 +123,7 @@ float YGNode::getTrailingPosition(
       : YGUnwrapFloatOptional(YGResolveValue(*trailingPosition, axisSize));
 }
 
-bool YGNode::isLeadingPositionDefined(const YGFlexDirection axis) {
+bool YGNode::isLeadingPositionDefined(const YGFlexDirection axis) const {
   return (YGFlexDirectionIsRow(axis) &&
           YGComputedEdgeValue(style_.position, YGEdgeStart, &YGValueUndefined)
                   ->unit != YGUnitUndefined) ||
@@ -131,7 +131,7 @@ bool YGNode::isLeadingPositionDefined(const YGFlexDirection axis) {
           ->unit != YGUnitUndefined;
 }
 
-bool YGNode::isTrailingPosDefined(const YGFlexDirection axis) {
+bool YGNode::isTrailingPosDefined(const YGFlexDirection axis) const {
   return (YGFlexDirectionIsRow(axis) &&
           YGComputedEdgeValue(style_.position, YGEdgeEnd, &YGValueUndefined)
                   ->unit != YGUnitUndefined) ||
@@ -141,7 +141,7 @@ bool YGNode::isTrailingPosDefined(const YGFlexDirection axis) {
 
 float YGNode::getLeadingMargin(
     const YGFlexDirection axis,
-    const float widthSize) {
+    const float widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.margin[YGEdgeStart].unit != YGUnitUndefined) {
     return YGResolveValueMargin(style_.margin[YGEdgeStart], widthSize);
@@ -154,7 +154,7 @@ float YGNode::getLeadingMargin(
 
 float YGNode::getTrailingMargin(
     const YGFlexDirection axis,
-    const float widthSize) {
+    const float widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.margin[YGEdgeEnd].unit != YGUnitUndefined) {
     return YGResolveValueMargin(style_.margin[YGEdgeEnd], widthSize);
@@ -167,7 +167,7 @@ float YGNode::getTrailingMargin(
 
 float YGNode::getMarginForAxis(
     const YGFlexDirection axis,
-    const float widthSize) {
+    const float widthSize) const {
   return getLeadingMargin(axis, widthSize) + getTrailingMargin(axis, widthSize);
 }
 
@@ -621,7 +621,7 @@ bool YGNode::isNodeFlexible() {
       (resolveFlexGrow() != 0 || resolveFlexShrink() != 0));
 }
 
-float YGNode::getLeadingBorder(const YGFlexDirection axis) {
+float YGNode::getLeadingBorder(const YGFlexDirection axis) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.border[YGEdgeStart].unit != YGUnitUndefined &&
       !YGFloatIsUndefined(style_.border[YGEdgeStart].value) &&
@@ -634,7 +634,7 @@ float YGNode::getLeadingBorder(const YGFlexDirection axis) {
   return YGFloatMax(computedEdgeValue, 0.0f);
 }
 
-float YGNode::getTrailingBorder(const YGFlexDirection flexDirection) {
+float YGNode::getTrailingBorder(const YGFlexDirection flexDirection) const {
   if (YGFlexDirectionIsRow(flexDirection) &&
       style_.border[YGEdgeEnd].unit != YGUnitUndefined &&
       !YGFloatIsUndefined(style_.border[YGEdgeEnd].value) &&
@@ -650,7 +650,7 @@ float YGNode::getTrailingBorder(const YGFlexDirection flexDirection) {
 
 float YGNode::getLeadingPadding(
     const YGFlexDirection axis,
-    const float widthSize) {
+    const float widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.padding[YGEdgeStart].unit != YGUnitUndefined &&
       !YGResolveValue(style_.padding[YGEdgeStart], widthSize).isUndefined() &&
@@ -667,7 +667,7 @@ float YGNode::getLeadingPadding(
 
 float YGNode::getTrailingPadding(
     const YGFlexDirection axis,
-    const float widthSize) {
+    const float widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.padding[YGEdgeEnd].unit != YGUnitUndefined &&
       !YGResolveValue(style_.padding[YGEdgeEnd], widthSize).isUndefined() &&
@@ -685,13 +685,13 @@ float YGNode::getTrailingPadding(
 
 float YGNode::getLeadingPaddingAndBorder(
     const YGFlexDirection axis,
-    const float widthSize) {
+    const float widthSize) const {
   return getLeadingPadding(axis, widthSize) + getLeadingBorder(axis);
 }
 
 float YGNode::getTrailingPaddingAndBorder(
     const YGFlexDirection axis,
-    const float widthSize) {
+    const float widthSize) const {
   return getTrailingPadding(axis, widthSize) + getTrailingBorder(axis);
 }
 
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index c9c5599c0909..0ed05d7e5521 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -80,23 +80,23 @@ struct YGNode {
   YGValue getResolvedDimension(int index);
 
   // Methods related to positions, margin, padding and border
-  float getLeadingPosition(const YGFlexDirection axis, const float axisSize);
-  bool isLeadingPositionDefined(const YGFlexDirection axis);
-  bool isTrailingPosDefined(const YGFlexDirection axis);
-  float getTrailingPosition(const YGFlexDirection axis, const float axisSize);
-  float getLeadingMargin(const YGFlexDirection axis, const float widthSize);
-  float getTrailingMargin(const YGFlexDirection axis, const float widthSize);
-  float getLeadingBorder(const YGFlexDirection flexDirection);
-  float getTrailingBorder(const YGFlexDirection flexDirection);
-  float getLeadingPadding(const YGFlexDirection axis, const float widthSize);
-  float getTrailingPadding(const YGFlexDirection axis, const float widthSize);
+  float getLeadingPosition(const YGFlexDirection axis, const float axisSize) const;
+  bool isLeadingPositionDefined(const YGFlexDirection axis) const;
+  bool isTrailingPosDefined(const YGFlexDirection axis) const;
+  float getTrailingPosition(const YGFlexDirection axis, const float axisSize) const;
+  float getLeadingMargin(const YGFlexDirection axis, const float widthSize) const;
+  float getTrailingMargin(const YGFlexDirection axis, const float widthSize) const;
+  float getLeadingBorder(const YGFlexDirection flexDirection) const;
+  float getTrailingBorder(const YGFlexDirection flexDirection) const;
+  float getLeadingPadding(const YGFlexDirection axis, const float widthSize) const;
+  float getTrailingPadding(const YGFlexDirection axis, const float widthSize) const;
   float getLeadingPaddingAndBorder(
       const YGFlexDirection axis,
-      const float widthSize);
+      const float widthSize) const;
   float getTrailingPaddingAndBorder(
       const YGFlexDirection axis,
-      const float widthSize);
-  float getMarginForAxis(const YGFlexDirection axis, const float widthSize);
+      const float widthSize) const;
+  float getMarginForAxis(const YGFlexDirection axis, const float widthSize) const;
   // Setters
 
   void setContext(void* context);

From f015900d30321bc24ba850118746eb7a68d5d8fd Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Wed, 21 Mar 2018 16:38:41 -0700
Subject: [PATCH 0113/1109] fixed debug string formatting for structure

Summary:
Fixed minor issue:
* use double spaces instead of a tab character for indentation
* depth should increase by 1, not 2

Reviewed By: shergin

Differential Revision: D7332803

fbshipit-source-id: 74fda2c7a4be4f509270d3074a7d71a3d4d32fe4
---
 ReactCommon/fabric/debug/DebugStringConvertible.cpp | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/ReactCommon/fabric/debug/DebugStringConvertible.cpp b/ReactCommon/fabric/debug/DebugStringConvertible.cpp
index f669c1bd5ad2..ce2c91611af9 100644
--- a/ReactCommon/fabric/debug/DebugStringConvertible.cpp
+++ b/ReactCommon/fabric/debug/DebugStringConvertible.cpp
@@ -50,10 +50,10 @@ std::string DebugStringConvertible::getDebugPropsDescription(DebugStringConverti
 std::string DebugStringConvertible::getDebugDescription(DebugStringConvertibleOptions options, int depth) const {
   std::string nameString = getDebugName();
   std::string valueString = getDebugValue();
-  std::string childrenString = getDebugChildrenDescription(options, depth + 1);
-  std::string propsString = getDebugPropsDescription(options, depth /* The first-level props are considered as same-depth things. */);
+  std::string childrenString = getDebugChildrenDescription(options, depth);
+  std::string propsString = getDebugPropsDescription(options, depth);
 
-  std::string leading = options.format ? std::string(depth, '\t') : "";
+  std::string leading = options.format ? std::string(depth * 2, ' ') : "";
   std::string trailing = options.format ? "\n" : "";
 
   return leading + "<" + nameString +

From 6ae38feb654576054839d7b5b5741069a4e14a2f Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Wed, 21 Mar 2018 16:38:43 -0700
Subject: [PATCH 0114/1109] Added sample iOS unit test setup for fabric/debug
 target

Summary: basic setup for unit testing Fabric impl

Reviewed By: hramos

Differential Revision: D7359239

fbshipit-source-id: ccaf36e775036f2fad4d8c882bce86bbbe06dd28
---
 ReactCommon/fabric/debug/BUCK                 | 33 ++++++--
 .../tests/DebugStringConvertibleTest.cpp      | 77 +++++++++++++++++++
 2 files changed, 105 insertions(+), 5 deletions(-)
 create mode 100644 ReactCommon/fabric/debug/tests/DebugStringConvertibleTest.cpp

diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index 5a021202ebb7..d17009730e11 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -5,18 +5,18 @@ APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
     load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "debug",
     srcs = glob(
         [
-            "**/*.cpp",
+            "*.cpp",
         ],
     ),
     headers = glob(
         [
-            "**/*.h",
+            "*.h",
         ],
     ),
     header_namespace = "",
@@ -27,10 +27,10 @@ rn_xplat_cxx_library(
         prefix = "fabric/debug",
     ),
     compiler_flags = [
-        "-std=c++14",
-        "-Wall",
         "-fexceptions",
         "-frtti",
+        "-std=c++14",
+        "-Wall",
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
@@ -39,8 +39,31 @@ rn_xplat_cxx_library(
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
+    tests = [
+        ":tests",
+    ],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//folly:headers_only",
     ],
 )
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+
+    cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":debug",
+        ],
+    )
diff --git a/ReactCommon/fabric/debug/tests/DebugStringConvertibleTest.cpp b/ReactCommon/fabric/debug/tests/DebugStringConvertibleTest.cpp
new file mode 100644
index 000000000000..272255b39eb7
--- /dev/null
+++ b/ReactCommon/fabric/debug/tests/DebugStringConvertibleTest.cpp
@@ -0,0 +1,77 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <gtest/gtest.h>
+
+using namespace facebook::react;
+
+TEST(DebugStringConvertibleTest, handleSimpleNode) {
+  SharedDebugStringConvertibleList empty;
+  auto item = std::make_shared<DebugStringConvertibleItem>("View", "hello", empty, empty);
+
+  ASSERT_STREQ(item->getDebugName().c_str(), "View");
+  ASSERT_STREQ(item->getDebugValue().c_str(), "hello");
+  ASSERT_STREQ(item->getDebugDescription().c_str(), "<View=hello/>\n");
+}
+
+TEST(DebugStringConvertibleTest, handleSimpleNodeWithProps) {
+  SharedDebugStringConvertibleList empty;
+  SharedDebugStringConvertibleList props = {
+    std::make_shared<DebugStringConvertibleItem>("x", "1", empty, empty)
+  };
+  auto item = std::make_shared<DebugStringConvertibleItem>("View", "hello", props, empty);
+
+  ASSERT_STREQ(item->getDebugName().c_str(), "View");
+  ASSERT_STREQ(item->getDebugValue().c_str(), "hello");
+  ASSERT_STREQ(item->getDebugDescription().c_str(), "<View=hello x=1/>\n");
+}
+
+TEST(DebugStringConvertibleTest, handleSimpleNodeWithChildren) {
+  SharedDebugStringConvertibleList empty;
+  SharedDebugStringConvertibleList children = {
+    std::make_shared<DebugStringConvertibleItem>("Child", "a", empty, empty)
+  };
+  auto item = std::make_shared<DebugStringConvertibleItem>("View", "hello", empty, children);
+
+  ASSERT_STREQ(item->getDebugName().c_str(), "View");
+  ASSERT_STREQ(item->getDebugValue().c_str(), "hello");
+  ASSERT_STREQ(item->getDebugDescription().c_str(), "<View=hello>\n  <Child=a/>\n</View>\n");
+}
+
+TEST(DebugStringConvertibleTest, handleNestedNode) {
+  SharedDebugStringConvertibleList empty;
+  SharedDebugStringConvertibleList props = {
+    std::make_shared<DebugStringConvertibleItem>("x", "1", empty, empty)
+  };
+  SharedDebugStringConvertibleList children = {
+    std::make_shared<DebugStringConvertibleItem>("Child", "a", props, empty)
+  };
+  auto item = std::make_shared<DebugStringConvertibleItem>("View", "hello", props, children);
+
+  ASSERT_STREQ(item->getDebugName().c_str(), "View");
+  ASSERT_STREQ(item->getDebugValue().c_str(), "hello");
+  ASSERT_STREQ(item->getDebugDescription().c_str(), "<View=hello x=1>\n  <Child=a x=1/>\n</View>\n");
+}
+
+TEST(DebugStringConvertibleTest, handleNodeWithComplexProps) {
+  SharedDebugStringConvertibleList empty;
+  SharedDebugStringConvertibleList subProps = {
+    std::make_shared<DebugStringConvertibleItem>("height", "100", empty, empty),
+    std::make_shared<DebugStringConvertibleItem>("width", "200", empty, empty)
+  };
+  SharedDebugStringConvertibleList props = {
+    std::make_shared<DebugStringConvertibleItem>("x", "1", subProps, empty)
+  };
+  auto item = std::make_shared<DebugStringConvertibleItem>("View", "hello", props, empty);
+
+  ASSERT_STREQ(item->getDebugName().c_str(), "View");
+  ASSERT_STREQ(item->getDebugValue().c_str(), "hello");
+  ASSERT_STREQ(item->getDebugDescription().c_str(), "<View=hello x=1(height=100 width=200)/>\n");
+}

From 96daf677b7eda7e4344da7e674d3d6c298875913 Mon Sep 17 00:00:00 2001
From: Jonathan Kim <jjkim@fb.com>
Date: Wed, 21 Mar 2018 17:40:46 -0700
Subject: [PATCH 0115/1109] Fix OSS Android test failure

Reviewed By: fkgozali, hramos

Differential Revision: D7358801

fbshipit-source-id: 6f7979489fd7f5c9f7d9e1d7461121b7ff9f3ab0
---
 ReactNative/DEFS.bzl | 10 ++++++++--
 1 file changed, 8 insertions(+), 2 deletions(-)

diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index b84007444e5e..135bacfbc93d 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -35,10 +35,16 @@ with allow_unsafe_import():
 
 # Building is not supported in OSS right now
 def rn_xplat_cxx_library(name, **kwargs):
-    _ignore = kwargs
+    new_kwargs = {
+        k: v
+        for k, v in kwargs.items()
+        if k.startswith("exported_")
+    }
+
     native.cxx_library(
         name=name,
-        visibility=kwargs.get("visibility", [])
+        visibility=kwargs.get("visibility", []),
+        **new_kwargs
     )
 
 

From 47910f0cadda30099bc6f5dfda03a69babd663a7 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 21 Mar 2018 17:43:11 -0700
Subject: [PATCH 0116/1109] Set measure function after YogaNode has been copied

Reviewed By: mdvacca

Differential Revision: D7338948

fbshipit-source-id: e805169e162a47d0c7c775a3decbe9013c27c0e4
---
 .../react/uimanager/ReactShadowNodeImpl.java     |  5 -----
 .../react/views/text/ReactTextShadowNode.java    | 16 +++++++++++++++-
 2 files changed, 15 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 8d906c4bc298..5f4ad868fe77 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -1024,11 +1024,6 @@ public void setBaselineFunction(YogaBaselineFunction baselineFunction) {
 
   @Override
   public void setMeasureFunction(YogaMeasureFunction measureFunction) {
-    if ((measureFunction == null ^ mYogaNode.isMeasureDefined()) && getChildCount() != 0) {
-      throw new RuntimeException(
-          "Since a node with a measure function does not add any native yoga children, it's "
-              + "not safe to transition to/from having a measure function unless a node has no children");
-    }
     mYogaNode.setMeasureFunction(measureFunction);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
index 37b13700fc36..1cec7c690bcb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
@@ -18,6 +18,7 @@
 import android.widget.TextView;
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.uimanager.LayoutShadowNode;
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.Spacing;
 import com.facebook.react.uimanager.UIViewOperationQueue;
 import com.facebook.yoga.YogaConstants;
@@ -144,7 +145,6 @@ public ReactTextShadowNode() {
   private ReactTextShadowNode(ReactTextShadowNode node) {
     super(node);
     this.mPreparedSpannableText = node.mPreparedSpannableText;
-    initMeasureFunction();
   }
 
   private void initMeasureFunction() {
@@ -158,6 +158,20 @@ protected LayoutShadowNode copy() {
     return new ReactTextShadowNode(this);
   }
 
+  @Override
+  public ReactShadowNodeImpl mutableCopy() {
+    ReactTextShadowNode copy = (ReactTextShadowNode) super.mutableCopy();
+    copy.initMeasureFunction();
+    return copy;
+  }
+
+  @Override
+  public ReactShadowNodeImpl mutableCopyWithNewChildren() {
+    ReactTextShadowNode copy = (ReactTextShadowNode) super.mutableCopyWithNewChildren();
+    copy.initMeasureFunction();
+    return copy;
+  }
+
   // Return text alignment according to LTR or RTL style
   private int getTextAlign() {
     int textAlign = mTextAlign;

From 8e065baad43a124a999d4f3c253b1081a3045a1a Mon Sep 17 00:00:00 2001
From: Andrew Jack <me@andrewjack.uk>
Date: Wed, 21 Mar 2018 18:07:47 -0700
Subject: [PATCH 0117/1109] Update fresco to v1.8.1

Summary:
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->
The current version of fresco in use is [v1.3.0](https://github.com/facebook/fresco/releases/tag/v1.3.0) from April 2017. There has been a lot of [improvements](https://github.com/facebook/fresco/releases) since then.

Fresco also depends on OkHttp 3.8.0 and soloader 0.3.0 so I have updated these too. Let me know if there's any reason either of these shouldn't be updated, however this will prevent Fresco from being updated.

The latest version of OkHttp is 3.10.0, but I have kept it as low as possible to allow developers to choose the version.

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->
Test with local build.
Check CI passes.

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [ENHANCEMENT] [Fresco/OkHttp/SoLoader] - Updates Fresco to 1.8.1, OkHttp to 3.8.0, & SoLoader to 0.3.0

cc foghina

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18496

Differential Revision: D7361161

Pulled By: foghina

fbshipit-source-id: 6d2c5afb94ce5ff8e621188c2ac60f1ca4b787a6
---
 ReactAndroid/build.gradle                     | 10 ++++----
 .../libraries/fresco/fresco-react-native/BUCK | 24 +++++++++----------
 .../soloader/java/com/facebook/soloader/BUCK  |  4 ++--
 .../src/main/third-party/java/okhttp/BUCK     |  8 +++----
 4 files changed, 23 insertions(+), 23 deletions(-)

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index fdea9de2db7e..48c38722a167 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -281,12 +281,12 @@ dependencies {
     compile 'javax.inject:javax.inject:1'
     compile 'com.android.support:appcompat-v7:23.0.1'
     compile 'com.facebook.fbui.textlayoutbuilder:textlayoutbuilder:1.0.0'
-    compile 'com.facebook.fresco:fresco:1.3.0'
-    compile 'com.facebook.fresco:imagepipeline-okhttp3:1.3.0'
-    compile 'com.facebook.soloader:soloader:0.1.0'
+    compile 'com.facebook.fresco:fresco:1.8.1'
+    compile 'com.facebook.fresco:imagepipeline-okhttp3:1.8.1'
+    compile 'com.facebook.soloader:soloader:0.3.0'
     compile 'com.google.code.findbugs:jsr305:3.0.0'
-    compile 'com.squareup.okhttp3:okhttp:3.6.0'
-    compile 'com.squareup.okhttp3:okhttp-urlconnection:3.6.0'
+    compile 'com.squareup.okhttp3:okhttp:3.8.0'
+    compile 'com.squareup.okhttp3:okhttp-urlconnection:3.8.0'
     compile 'com.squareup.okio:okio:1.13.0'
     compile 'org.webkit:android-jsc:r174650'
 
diff --git a/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK b/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
index 06dca9bcc73f..33ceb77095e7 100644
--- a/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
+++ b/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
@@ -8,8 +8,8 @@ rn_android_prebuilt_aar(
 
 remote_file(
     name = "fresco-binary-aar",
-    sha1 = "b6271dc58383b4ce119ecc05e2bcaedde0e74ad9",
-    url = "mvn:com.facebook.fresco:fresco:aar:1.3.0",
+    sha1 = "c6ed3f696ed47dca3b20d4ffbd0600c94b9119b2",
+    url = "mvn:com.facebook.fresco:fresco:aar:1.8.1",
 )
 
 android_prebuilt_aar(
@@ -20,8 +20,8 @@ android_prebuilt_aar(
 
 remote_file(
     name = "drawee-binary-aar",
-    sha1 = "c88fb84ed4ae8a4e0efe6fd3cad1a1d20c19ea69",
-    url = "mvn:com.facebook.fresco:drawee:aar:1.3.0",
+    sha1 = "6bc689901ddcac8f3df5ba4db1f8aabeb8e80107",
+    url = "mvn:com.facebook.fresco:drawee:aar:1.8.1",
 )
 
 rn_android_library(
@@ -42,8 +42,8 @@ rn_android_prebuilt_aar(
 
 remote_file(
     name = "imagepipeline-base-aar",
-    sha1 = "a43f1043fc684d2794438544f73f1968ec9cf21a",
-    url = "mvn:com.facebook.fresco:imagepipeline-base:aar:1.3.0",
+    sha1 = "42fd80c46a853850dfc0d71808b982fef401c841",
+    url = "mvn:com.facebook.fresco:imagepipeline-base:aar:1.8.1",
 )
 
 rn_android_prebuilt_aar(
@@ -54,8 +54,8 @@ rn_android_prebuilt_aar(
 
 remote_file(
     name = "imagepipeline-aar",
-    sha1 = "32c08122d47210d437f34eba5472e880b0f1e8b8",
-    url = "mvn:com.facebook.fresco:imagepipeline:aar:1.3.0",
+    sha1 = "06a2a4c3e1d9a7fb7d7f1ad14db63e2d32ef0b61",
+    url = "mvn:com.facebook.fresco:imagepipeline:aar:1.8.1",
 )
 
 rn_prebuilt_jar(
@@ -78,8 +78,8 @@ android_prebuilt_aar(
 
 remote_file(
     name = "fbcore-aar",
-    sha1 = "3b941157dd0c36fca9a19c22cae578f37deb97e5",
-    url = "mvn:com.facebook.fresco:fbcore:aar:1.3.0",
+    sha1 = "99b7a83946e16f037149e4cd3abfd6840a09445d",
+    url = "mvn:com.facebook.fresco:fbcore:aar:1.8.1",
 )
 
 android_prebuilt_aar(
@@ -90,6 +90,6 @@ android_prebuilt_aar(
 
 remote_file(
     name = "imagepipeline-okhttp3-binary-aar",
-    sha1 = "ac9b1a7c9906ed6be41c8df923a59f6952fce94c",
-    url = "mvn:com.facebook.fresco:imagepipeline-okhttp3:aar:1.3.0",
+    sha1 = "751f19412e1843b1c1e76eae46e388fb1deddbcc",
+    url = "mvn:com.facebook.fresco:imagepipeline-okhttp3:aar:1.8.1",
 )
diff --git a/ReactAndroid/src/main/libraries/soloader/java/com/facebook/soloader/BUCK b/ReactAndroid/src/main/libraries/soloader/java/com/facebook/soloader/BUCK
index c91ded296895..3008da960a23 100644
--- a/ReactAndroid/src/main/libraries/soloader/java/com/facebook/soloader/BUCK
+++ b/ReactAndroid/src/main/libraries/soloader/java/com/facebook/soloader/BUCK
@@ -6,6 +6,6 @@ android_prebuilt_aar(
 
 remote_file(
     name = "soloader-binary-aar",
-    sha1 = "918573465c94c6bc9bad48ef259f1e0cd6543c1b",
-    url = "mvn:com.facebook.soloader:soloader:aar:0.1.0",
+    sha1 = "5f4b28f3c401f3d9bb2d081af08f6ce784a02da5",
+    url = "mvn:com.facebook.soloader:soloader:aar:0.3.0",
 )
diff --git a/ReactAndroid/src/main/third-party/java/okhttp/BUCK b/ReactAndroid/src/main/third-party/java/okhttp/BUCK
index b02f1486168b..84be571ad87c 100644
--- a/ReactAndroid/src/main/third-party/java/okhttp/BUCK
+++ b/ReactAndroid/src/main/third-party/java/okhttp/BUCK
@@ -6,8 +6,8 @@ prebuilt_jar(
 
 remote_file(
     name = "okhttp3-binary-jar",
-    sha1 = "69edde9fc4b01c9fd51d25b83428837478c27254",
-    url = "mvn:com.squareup.okhttp3:okhttp:jar:3.6.0",
+    sha1 = "5a11f020cce2d11eb71ba916700600e18c4547e7",
+    url = "mvn:com.squareup.okhttp3:okhttp:jar:3.8.0",
 )
 
 prebuilt_jar(
@@ -18,6 +18,6 @@ prebuilt_jar(
 
 remote_file(
     name = "okhttp3-urlconnection-binary-jar",
-    sha1 = "3f9b16b774f2c36cfd86dd2053d0b3059531dacc",
-    url = "mvn:com.squareup.okhttp3:okhttp-urlconnection:jar:3.6.0",
+    sha1 = "265257b82f20bb0371a926cc8ceb5f7bb17c0df8",
+    url = "mvn:com.squareup.okhttp3:okhttp-urlconnection:jar:3.8.0",
 )

From ff1444e2151488b0cde612e5920bbbb300562331 Mon Sep 17 00:00:00 2001
From: Andrew Jack <me@andrewjack.uk>
Date: Thu, 22 Mar 2018 09:51:29 -0700
Subject: [PATCH 0118/1109] Add fresco proguard rules

Summary:
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->
Adds proguard rules, which I missed off from the #18496 PR.

I've added the proguard rules as suggested in http://frescolib.org/docs/shipping.html, with the duplicates & unused libraries removed.

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->
CI passes.
Build example project with proguard turned on.

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [BREAKING] [proguard] - Update Proguard config in template. If upgrading make sure you update your project's proguard file.

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->

cc foghina & hramos
Closes https://github.com/facebook/react-native/pull/18499

Differential Revision: D7366113

Pulled By: foghina

fbshipit-source-id: 20864c34976bc3930d9fdcc9428f40f7a8d7a9b8
---
 .../HelloWorld/android/app/proguard-rules.pro | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)

diff --git a/local-cli/templates/HelloWorld/android/app/proguard-rules.pro b/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
index d8ec99250e54..b30112461f0e 100644
--- a/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
+++ b/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
@@ -54,6 +54,25 @@
 # See libs/proxy/src/main/java/com/facebook/fbui/textlayoutbuilder/proxy for details.
 -dontwarn android.text.StaticLayout
 
+# Fresco
+# Keep our interfaces so they can be used by other ProGuard rules.
+# See http://sourceforge.net/p/proguard/bugs/466/
+-keep,allowobfuscation @interface com.facebook.soloader.DoNotOptimize
+
+# Do not strip any method/class that is annotated with @DoNotOptimize
+-keep @com.facebook.soloader.DoNotOptimize class *
+-keepclassmembers class * {
+    @com.facebook.soloader.DoNotOptimize *;
+}
+
+# Keep native methods
+-keepclassmembers class * {
+    native <methods>;
+}
+
+-dontwarn javax.annotation.**
+-dontwarn com.facebook.infer.**
+
 # okhttp
 
 -keepattributes Signature

From 10c95a25ccd55c0dc60484b30e4db75930bb31e9 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 22 Mar 2018 10:37:25 -0700
Subject: [PATCH 0119/1109] fixed contacts for the test target

Reviewed By: mdvacca

Differential Revision: D7366977

fbshipit-source-id: 93341f8964da71a7e23049fc5d2324a0da376746
---
 ReactCommon/fabric/debug/BUCK | 1 +
 1 file changed, 1 insertion(+)

diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index d17009730e11..6ce9e7f29e3d 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -54,6 +54,7 @@ if not IS_OSS_BUILD:
     cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
         compiler_flags = [
             "-fexceptions",
             "-frtti",

From 15fa2250fdd0865ce1d0c6ac13b817e7b2c7757a Mon Sep 17 00:00:00 2001
From: Eric Samelson <samelson.e@gmail.com>
Date: Thu, 22 Mar 2018 10:47:40 -0700
Subject: [PATCH 0120/1109] fix ReadableNativeMap.toHashMap() for nested maps
 and arrays

Summary:
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

Commit https://github.com/facebook/react-native/commit/7891805d22e3fdc821961ff0ccc5c450c3d625c8 broke the previous behavior of `ReadableNativeMap.toHashMap()` for nested maps and arrays. Previously, all nested `ReadableNativeMap`s and `ReadableNativeArray`s were recursively converted to `HashMap`s and `ArrayList`s, but this is lost when only `getLocalMap()` is returned.

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Call `ReadableNativeMap.toHashMap()` on a map with values of type `ReadableNativeMap` and `ReadableNativeArray`. Verify the returned hash map has these converted to `HashMap` and `ArrayList`, respectively.

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [BUGFIX] [ReadableNativeMap] - Fix toHashMap() for nested maps and arrays

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18455

Reviewed By: kathryngray

Differential Revision: D7347344

Pulled By: mdvacca

fbshipit-source-id: af2bca9dec6c0cb8a7da099b6757434fcc3ac785
---
 .../react/bridge/ReadableNativeMap.java       | 27 ++++++++++++++++++-
 1 file changed, 26 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReadableNativeMap.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReadableNativeMap.java
index 82f7f20a0229..0cb9c10ef1c6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReadableNativeMap.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReadableNativeMap.java
@@ -11,6 +11,7 @@
 import com.facebook.proguard.annotations.DoNotStrip;
 
 import java.util.HashMap;
+import java.util.Iterator;
 
 import com.facebook.infer.annotation.Assertions;
 import javax.annotation.Nullable;
@@ -248,7 +249,31 @@ public HashMap<String, Object> toHashMap() {
         }
       return hashMap;
     }
-    return getLocalMap();
+
+    // we can almost just return getLocalMap(), but we need to convert nested arrays and maps to the
+    // correct types first
+    HashMap<String, Object> hashMap = new HashMap<>(getLocalMap());
+    Iterator iterator = hashMap.keySet().iterator();
+
+    while (iterator.hasNext()) {
+      String key = (String) iterator.next();
+      switch (getType(key)) {
+        case Null:
+        case Boolean:
+        case Number:
+        case String:
+          break;
+        case Map:
+          hashMap.put(key, Assertions.assertNotNull(getMap(key)).toHashMap());
+          break;
+        case Array:
+          hashMap.put(key, Assertions.assertNotNull(getArray(key)).toArrayList());
+          break;
+        default:
+          throw new IllegalArgumentException("Could not convert object with key: " + key + ".");
+      }
+    }
+    return hashMap;
   }
 
   /**

From cf642c9b1d0856200936882d5e08cae171520c7a Mon Sep 17 00:00:00 2001
From: Shoaib Meenai <smeenai@fb.com>
Date: Thu, 22 Mar 2018 16:19:01 -0700
Subject: [PATCH 0121/1109] Mark global variable as extern "C"

Reviewed By: mnovakovic

Differential Revision: D7369214

fbshipit-source-id: 710d817b4bf74b5ca0621645dd5c005b778d7171
---
 React/Base/RCTRootView.h | 7 ++++++-
 1 file changed, 6 insertions(+), 1 deletion(-)

diff --git a/React/Base/RCTRootView.h b/React/Base/RCTRootView.h
index daab13efbe8c..35561f68a8e4 100644
--- a/React/Base/RCTRootView.h
+++ b/React/Base/RCTRootView.h
@@ -30,7 +30,12 @@ typedef NS_ENUM(NSInteger, RCTRootViewSizeFlexibility) {
  * after the application has loaded. This is used to hide the `loadingView`, and
  * is a good indicator that the application is ready to use.
  */
-extern NSString *const RCTContentDidAppearNotification;
+#if defined(__cplusplus)
+extern "C"
+#else
+extern
+#endif
+NSString *const RCTContentDidAppearNotification;
 
 /**
  * Native view used to host React-managed views within the app. Can be used just

From 0376baf4b365c345ca0a607a80aaf7f4c4deeaf2 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 22 Mar 2018 17:32:08 -0700
Subject: [PATCH 0122/1109] Revert D7343566: [RN] Fixed race condition in
 RCTUIManager's mounting process

Differential Revision:
D7343566

Original commit changeset: e45a691add5e

fbshipit-source-id: 08ec04538c07dc3cd630240da8bb42a932a23b6f
---
 React/Modules/RCTUIManager.m | 23 -----------------------
 1 file changed, 23 deletions(-)

diff --git a/React/Modules/RCTUIManager.m b/React/Modules/RCTUIManager.m
index 4653e239ed3f..5dcce46588ba 100644
--- a/React/Modules/RCTUIManager.m
+++ b/React/Modules/RCTUIManager.m
@@ -69,9 +69,6 @@ @implementation RCTUIManager
 
   // Keyed by viewName
   NSDictionary *_componentDataByName;
-
-  BOOL _isMountingInProgress;
-  BOOL _isRemountingNeeded;
 }
 
 @synthesize bridge = _bridge;
@@ -1049,19 +1046,6 @@ - (void)batchDidComplete
  */
 - (void)_layoutAndMount
 {
-  // Mounting is (usually, not always) an asynchronous process.
-  // So, we have to ensure that there is no any case of self-interleaving
-  // (when another mourning process is initiated before the previous
-  // one finishes) here.
-  if (_isMountingInProgress) {
-    // In a case when another mounting process hasn't completed yet,
-    // we have to run another pass right after it finishes.
-    _isRemountingNeeded = YES;
-    return;
-  }
-
-  _isMountingInProgress = YES;
-
   [self _dispatchPropsDidChangeEvents];
   [self _dispatchChildrenDidChangeEvents];
 
@@ -1079,13 +1063,6 @@ - (void)_layoutAndMount
 
   [self flushUIBlocksWithCompletion:^{
     [self->_observerCoordinator uiManagerDidPerformMounting:self];
-
-    self->_isMountingInProgress = NO;
-
-    if (self->_isRemountingNeeded) {
-      self->_isRemountingNeeded = NO;
-      [self _layoutAndMount];
-    }
   }];
 }
 

From 046d4cee8b468bcc67be7fb9cae9737908833296 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Thu, 22 Mar 2018 22:06:01 -0700
Subject: [PATCH 0123/1109] Assert root node isn't null in createView

Reviewed By: mdvacca

Differential Revision: D7374406

fbshipit-source-id: 534e58e7867a9fa8e395abd587e2c808c9c7843d
---
 .../main/java/com/facebook/react/uimanager/UIImplementation.java | 1 +
 1 file changed, 1 insertion(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
index 46353bc28fc3..f33ab605700f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
@@ -276,6 +276,7 @@ public Map<String, Long> getProfiledBatchPerfCounters() {
   public void createView(int tag, String className, int rootViewTag, ReadableMap props) {
     ReactShadowNode cssNode = createShadowNode(className);
     ReactShadowNode rootNode = mShadowNodeRegistry.getNode(rootViewTag);
+    Assertions.assertNotNull(rootNode, "Root node with tag " + rootViewTag + " doesn't exist");
     cssNode.setReactTag(tag);
     cssNode.setViewClassName(className);
     cssNode.setRootNode(rootNode);

From cbb7c7c193ff3ba183e3c2243ec16e196d290996 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Fri, 23 Mar 2018 09:03:45 -0700
Subject: [PATCH 0124/1109] Pass fabric flag from native to JS

Reviewed By: mdvacca

Differential Revision: D7373722

fbshipit-source-id: 3cd051f38677900693f3da797effa11f9161df37
---
 Libraries/Components/View/TestFabricView.js   | 24 ------------
 .../Components/View/requireFabricView.js      | 25 ++++++++++++
 Libraries/ReactNative/AppRegistry.js          |  5 +--
 Libraries/ReactNative/renderFabricSurface.js  |  2 +-
 Libraries/Text/TestFabricText.js              | 24 ------------
 .../testing/ReactInstrumentationTest.java     |  7 +---
 .../testing/fabric/FabricTestModule.java      | 39 -------------------
 .../com/facebook/react/ReactRootView.java     |  3 ++
 8 files changed, 31 insertions(+), 98 deletions(-)
 delete mode 100644 Libraries/Components/View/TestFabricView.js
 create mode 100644 Libraries/Components/View/requireFabricView.js
 delete mode 100644 Libraries/Text/TestFabricText.js
 delete mode 100644 ReactAndroid/src/androidTest/java/com/facebook/react/testing/fabric/FabricTestModule.java

diff --git a/Libraries/Components/View/TestFabricView.js b/Libraries/Components/View/TestFabricView.js
deleted file mode 100644
index 01e0e4897b2b..000000000000
--- a/Libraries/Components/View/TestFabricView.js
+++ /dev/null
@@ -1,24 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule TestFabricView
- * @flow
- * @format
- */
-'use strict';
-
-/**
- * This is a switch on the correct View to use for Fabric testing purposes
- */
-let TestFabricView;
-const FabricTestModule = require('NativeModules').FabricTestModule;
-if (FabricTestModule && FabricTestModule.IS_FABRIC_ENABLED) {
-  TestFabricView = require('FabricView');
-} else {
-  TestFabricView = require('View');
-}
-
-module.exports = TestFabricView;
diff --git a/Libraries/Components/View/requireFabricView.js b/Libraries/Components/View/requireFabricView.js
new file mode 100644
index 000000000000..55a7c40f4da0
--- /dev/null
+++ b/Libraries/Components/View/requireFabricView.js
@@ -0,0 +1,25 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @providesModule requireFabricView
+ * @flow
+ * @format
+ */
+'use strict';
+
+/**
+ * This is a switch on the correct view to use for Fabric
+ */
+module.exports = (name: string, fabric: boolean) => {
+  switch (name) {
+    case 'View':
+      return fabric ? require('FabricView') : require('View');
+    case 'Text':
+      return fabric ? require('FabricText') : require('Text');
+    default:
+      throw new Error(name + ' is not supported by Fabric yet');
+  }
+};
diff --git a/Libraries/ReactNative/AppRegistry.js b/Libraries/ReactNative/AppRegistry.js
index 21fdca68a43d..8ddfb64118d0 100644
--- a/Libraries/ReactNative/AppRegistry.js
+++ b/Libraries/ReactNative/AppRegistry.js
@@ -35,7 +35,6 @@ export type AppConfig = {
   component?: ComponentProvider,
   run?: Function,
   section?: boolean,
-  fabric?: boolean,
 };
 export type Runnable = {
   component?: ComponentProvider,
@@ -85,7 +84,6 @@ const AppRegistry = {
           appConfig.appKey,
           appConfig.component,
           appConfig.section,
-          appConfig.fabric,
         );
       }
     });
@@ -100,13 +98,12 @@ const AppRegistry = {
     appKey: string,
     componentProvider: ComponentProvider,
     section?: boolean,
-    fabric?: boolean,
   ): string {
     runnables[appKey] = {
       componentProvider,
       run: appParameters => {
         let renderFunc = renderApplication;
-        if (fabric) {
+        if (appParameters.fabric) {
           invariant(
             fabricRendererProvider != null,
             'A Fabric renderer provider must be set to render Fabric components',
diff --git a/Libraries/ReactNative/renderFabricSurface.js b/Libraries/ReactNative/renderFabricSurface.js
index 0279f1759926..46536a755ce5 100644
--- a/Libraries/ReactNative/renderFabricSurface.js
+++ b/Libraries/ReactNative/renderFabricSurface.js
@@ -34,7 +34,7 @@ function renderFabricSurface<Props: Object>(
       fabric={true}
       rootTag={rootTag}
       WrapperComponent={WrapperComponent}>
-      <RootComponent {...initialProps} rootTag={rootTag} />
+      <RootComponent {...initialProps} rootTag={rootTag} fabric={true} />
     </AppContainer>
   );
 
diff --git a/Libraries/Text/TestFabricText.js b/Libraries/Text/TestFabricText.js
deleted file mode 100644
index cdedcc3177ca..000000000000
--- a/Libraries/Text/TestFabricText.js
+++ /dev/null
@@ -1,24 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule TestFabricText
- * @flow
- * @format
- */
-'use strict';
-
-/**
- * This is a switch on the correct Text to use for Fabric testing purposes
- */
-let TestFabricText;
-const FabricTestModule = require('NativeModules').FabricTestModule;
-if (FabricTestModule && FabricTestModule.IS_FABRIC_ENABLED) {
-  TestFabricText = require('FabricText');
-} else {
-  TestFabricText = require('Text');
-}
-
-module.exports = TestFabricText;
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
index 7544395157c6..3f0a7e250bfa 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
@@ -13,7 +13,6 @@
 import android.view.ViewGroup;
 import com.facebook.react.bridge.JavaScriptModule;
 import com.facebook.react.bridge.ReactContext;
-import com.facebook.react.testing.fabric.FabricTestModule;
 import com.facebook.react.testing.idledetection.IdleWaiter;
 
 /**
@@ -116,11 +115,7 @@ protected <T extends JavaScriptModule> T getJSModule(Class<T> jsInterface) {
    * Override this method to provide extra native modules to be loaded before the app starts
    */
   protected ReactInstanceSpecForTest createReactInstanceSpecForTest() {
-    ReactInstanceSpecForTest instanceSpec = new ReactInstanceSpecForTest();
-    if (isFabricTest()) {
-      instanceSpec.addNativeModule(new FabricTestModule(isFabricTest()));
-    }
-    return instanceSpec;
+    return new ReactInstanceSpecForTest();
   }
 
   /**
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/fabric/FabricTestModule.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/fabric/FabricTestModule.java
deleted file mode 100644
index 0e4fe05b099a..000000000000
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/fabric/FabricTestModule.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.testing.fabric;
-
-import com.facebook.react.common.MapBuilder;
-import java.util.Map;
-import javax.annotation.Nullable;
-
-import com.facebook.react.bridge.BaseJavaModule;
-import com.facebook.react.bridge.ReactMethod;
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.bridge.ReadableMap;
-
-/**
- * Module to indicate if a test is using Fabric
- */
-public final class FabricTestModule extends BaseJavaModule {
-
-  private final boolean mIsFabricEnabled;
-
-  public FabricTestModule(boolean isFabricEnabled) {
-    mIsFabricEnabled = isFabricEnabled;
-  }
-
-  @Override
-  public String getName() {
-    return "FabricTestModule";
-  }
-
-  @Override
-  public Map<String, Object> getConstants() {
-    return MapBuilder.<String, Object>of("IS_FABRIC_ENABLED", mIsFabricEnabled);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 5d4a88bc5025..5b8e3c53947e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -490,6 +490,9 @@ private void defaultJSEntryPoint() {
         if (appProperties != null) {
           appParams.putMap("initialProps", Arguments.fromBundle(appProperties));
         }
+        if (isFabric()) {
+          appParams.putBoolean("fabric", true);
+        }
 
         mShouldLogContentAppeared = true;
 

From dd479a93772c3a52561fc32ee84b25ce822a30fa Mon Sep 17 00:00:00 2001
From: Danny Cochran <daniel@cochrans.org>
Date: Fri, 23 Mar 2018 14:45:59 -0700
Subject: [PATCH 0125/1109] Pass invertStickyHeaders to ScrollView

Summary:
invertStickyHeaders was being set to "this.props.inverted" -- it should just inherit from the props of VirtualizedList instead, per discussion in https://github.com/facebook/react-native/issues/18471

Fixes #18471

Pass "invertStickyHeaders: false" to a SectionList (or FlatList), and expect that your sticky headers stick to the bottom of the ScrollView, instead of the top.

none

[ANDROID] [BUGFIX] [SectionList] - invertStickyHeaders can now be set from SectionList or FlatList.
Closes https://github.com/facebook/react-native/pull/18524

Differential Revision: D7386163

Pulled By: hramos

fbshipit-source-id: 3b66dfca280e657303f69f98c5a8bc0df033f9f7
---
 Libraries/Lists/VirtualizedList.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 4c7a83b19d77..928050f7682f 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -893,7 +893,9 @@ class VirtualizedList extends React.PureComponent<Props, State> {
       onScrollEndDrag: this._onScrollEndDrag,
       onMomentumScrollEnd: this._onMomentumScrollEnd,
       scrollEventThrottle: this.props.scrollEventThrottle, // TODO: Android support
-      invertStickyHeaders: this.props.inverted,
+      invertStickyHeaders: this.props.invertStickyHeaders !== undefined
+        ? this.props.invertStickyHeaders
+        : this.props.inverted,	
       stickyHeaderIndices,
     };
     if (inversionStyle) {

From 8c0070c706c42cf21a0f55050a1bd718dad47298 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 23 Mar 2018 16:46:07 -0700
Subject: [PATCH 0126/1109] iOS: added fabric/core primitives tests

Summary: basic tests for fabric core primitives

Reviewed By: shergin

Differential Revision: D7373952

fbshipit-source-id: e2d9b3c15716c16b1aab698883817e670dcb7a57
---
 ReactCommon/fabric/core/BUCK                  | 34 +++++++++++++---
 .../fabric/core/tests/PrimitivesTest.cpp      | 40 +++++++++++++++++++
 2 files changed, 68 insertions(+), 6 deletions(-)
 create mode 100644 ReactCommon/fabric/core/tests/PrimitivesTest.cpp

diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index f566a70f6ee7..f394579fc09a 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -10,14 +10,12 @@ if not IS_OSS_BUILD:
 rn_xplat_cxx_library(
     name = "core",
     srcs = glob(
-        [
-            "**/*.cpp",
-        ],
+        ["**/*.cpp"],
+        excludes = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
-        [
-            "**/*.h",
-        ],
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
@@ -42,6 +40,9 @@ rn_xplat_cxx_library(
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
+    tests = [
+        ":tests",
+    ],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//fbsystrace:fbsystrace",
@@ -53,3 +54,24 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/graphics:graphics"),
     ],
 )
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+
+    cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":core",
+        ],
+    )
diff --git a/ReactCommon/fabric/core/tests/PrimitivesTest.cpp b/ReactCommon/fabric/core/tests/PrimitivesTest.cpp
new file mode 100644
index 000000000000..99ecae6bfc28
--- /dev/null
+++ b/ReactCommon/fabric/core/tests/PrimitivesTest.cpp
@@ -0,0 +1,40 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <exception>
+
+#include <fabric/core/Sealable.h>
+#include <gtest/gtest.h>
+
+using namespace facebook::react;
+
+TEST(SealableTest, sealObjectCorrectly) {
+  Sealable obj;
+  ASSERT_FALSE(obj.getSealed());
+
+  obj.seal();
+  ASSERT_TRUE(obj.getSealed());
+}
+
+TEST(SealableTest, handleAssignmentsCorrectly) {
+  Sealable obj;
+  Sealable other;
+  EXPECT_NO_THROW(obj = other);
+
+  // Assignment after getting sealed is not allowed.
+  obj.seal();
+  Sealable other2;
+  EXPECT_THROW(obj = other2, std::runtime_error);
+
+  // It doesn't matter if the other object is also sealed, it's still not allowed.
+  other2.seal();
+  EXPECT_THROW(obj = other2, std::runtime_error);
+
+  // Fresh creation off other Sealable is still unsealed.
+  Sealable other3(obj);
+  ASSERT_FALSE(other3.getSealed());
+}

From e254474d4cbaebdb38ef5fdb5e69ca45257ce6ef Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 23 Mar 2018 16:46:09 -0700
Subject: [PATCH 0127/1109] iOS: added fabric/core ShadowNode tests

Summary: basic tests for shadow nodes and props for fabric

Reviewed By: shergin

Differential Revision: D7377867

fbshipit-source-id: dc8e5bb369aeb32b4790fd8b56f333376bc1578c
---
 ReactCommon/fabric/core/shadownode/Props.cpp  |   4 +
 ReactCommon/fabric/core/shadownode/Props.h    |   2 +
 .../fabric/core/shadownode/ShadowNode.cpp     |   8 ++
 .../fabric/core/shadownode/ShadowNode.h       |   2 +
 .../fabric/core/tests/ShadowNodeTest.cpp      | 115 ++++++++++++++++++
 5 files changed, 131 insertions(+)
 create mode 100644 ReactCommon/fabric/core/tests/ShadowNodeTest.cpp

diff --git a/ReactCommon/fabric/core/shadownode/Props.cpp b/ReactCommon/fabric/core/shadownode/Props.cpp
index fb527d62be95..cd5655ee588a 100644
--- a/ReactCommon/fabric/core/shadownode/Props.cpp
+++ b/ReactCommon/fabric/core/shadownode/Props.cpp
@@ -25,5 +25,9 @@ void Props::apply(const RawProps &rawProps) {
   }
 }
 
+const std::string &Props::getNativeId() const {
+  return nativeId_;
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/Props.h b/ReactCommon/fabric/core/shadownode/Props.h
index 8a6a73834879..5760f3491678 100644
--- a/ReactCommon/fabric/core/shadownode/Props.h
+++ b/ReactCommon/fabric/core/shadownode/Props.h
@@ -32,6 +32,8 @@ class Props:
 
   virtual void apply(const RawProps &rawProps);
 
+  const std::string &getNativeId() const;
+
 private:
   std::string nativeId_ {""};
 };
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 3f7aee7be56b..0dfb51e1eba2 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -58,6 +58,14 @@ Tag ShadowNode::getTag() const {
   return tag_;
 }
 
+Tag ShadowNode::getRootTag() const {
+  return rootTag_;
+}
+
+InstanceHandle ShadowNode::getInstanceHandle() const {
+  return instanceHandle_;
+}
+
 SharedShadowNode ShadowNode::getSourceNode() const {
   return sourceNode_;
 }
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 7fcb9d04cfa0..1deb4d520790 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -55,6 +55,8 @@ class ShadowNode:
   SharedShadowNodeSharedList getChildren() const;
   SharedProps getProps() const;
   Tag getTag() const;
+  Tag getRootTag() const;
+  InstanceHandle getInstanceHandle() const;
   SharedShadowNode getSourceNode() const;
   void sealRecursive() const;
 
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
new file mode 100644
index 000000000000..75bc82e8039d
--- /dev/null
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -0,0 +1,115 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <fabric/core/ConcreteShadowNode.h>
+#include <fabric/core/ShadowNode.h>
+#include <gtest/gtest.h>
+
+using namespace facebook::react;
+
+class TestProps : public Props {
+public:
+  TestProps() {
+    RawProps raw;
+    raw["nativeID"] = "testNativeID";
+    apply(raw);
+  }
+};
+using SharedTestProps = std::shared_ptr<const TestProps>;
+
+class TestShadowNode;
+using SharedTestShadowNode = std::shared_ptr<const TestShadowNode>;
+class TestShadowNode : public ConcreteShadowNode<TestProps> {
+public:
+  using ConcreteShadowNode::ConcreteShadowNode;
+
+  ComponentName getComponentName() const override {
+    return ComponentName("Test");
+  }
+};
+
+TEST(ShadowNodeTest, handleProps) {
+  RawProps raw;
+  raw["nativeID"] = "abc";
+
+  auto props = std::make_shared<Props>();
+  props->apply(raw);
+
+  // Props are not sealed after applying raw props.
+  ASSERT_FALSE(props->getSealed());
+
+  ASSERT_STREQ(props->getNativeId().c_str(), "abc");
+}
+
+TEST(ShadowNodeTest, handleShadowNodeCreation) {
+  auto node = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+
+  ASSERT_FALSE(node->getSealed());
+  ASSERT_STREQ(node->getComponentName().c_str(), "Test");
+  ASSERT_EQ(node->getTag(), 9);
+  ASSERT_EQ(node->getRootTag(), 1);
+  ASSERT_EQ(node->getInstanceHandle(), (void *)NULL);
+  TestShadowNode *nodePtr = node.get();
+  ASSERT_EQ(node->getComponentHandle(), typeid(*nodePtr).hash_code());
+  ASSERT_EQ(node->getSourceNode(), nullptr);
+  ASSERT_EQ(node->getChildren()->size(), 0);
+
+  // TODO(#27369757): getProps() doesn't work
+  // ASSERT_STREQ(node->getProps()->getNativeId().c_str(), "testNativeID");
+
+  node->sealRecursive();
+  ASSERT_TRUE(node->getSealed());
+
+  // TODO(#27369757): verify Props are also sealed.
+  // ASSERT_TRUE(node->getProps()->getSealed());
+}
+
+TEST(ShadowNodeTest, handleShadowNodeSimpleCloning) {
+  auto node = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+  auto node2 = std::make_shared<TestShadowNode>(node);
+
+  ASSERT_STREQ(node->getComponentName().c_str(), "Test");
+  ASSERT_EQ(node->getTag(), 9);
+  ASSERT_EQ(node->getRootTag(), 1);
+  ASSERT_EQ(node->getInstanceHandle(), (void *)NULL);
+  ASSERT_EQ(node2->getSourceNode(), node);
+}
+
+TEST(ShadowNodeTest, handleShadowNodeMutation) {
+  auto node1 = std::make_shared<TestShadowNode>(1, 1, (void *)NULL);
+  auto node2 = std::make_shared<TestShadowNode>(2, 1, (void *)NULL);
+  auto node3 = std::make_shared<TestShadowNode>(3, 1, (void *)NULL);
+
+  node1->appendChild(node2);
+  node1->appendChild(node3);
+  SharedShadowNodeSharedList node1Children = node1->getChildren();
+  ASSERT_EQ(node1Children->size(), 2);
+  ASSERT_EQ(node1Children->at(0), node2);
+  ASSERT_EQ(node1Children->at(1), node3);
+
+  auto node4 = std::make_shared<TestShadowNode>(node2);
+  node1->replaceChild(node2, node4);
+  node1Children = node1->getChildren();
+  ASSERT_EQ(node1Children->size(), 2);
+  ASSERT_EQ(node1Children->at(0), node4);
+  ASSERT_EQ(node1Children->at(1), node3);
+
+  // Seal the entire tree.
+  node1->sealRecursive();
+  ASSERT_TRUE(node1->getSealed());
+  ASSERT_TRUE(node3->getSealed());
+  ASSERT_TRUE(node4->getSealed());
+
+  // No more mutation after sealing.
+  EXPECT_THROW(node4->clearSourceNode(), std::runtime_error);
+
+  auto node5 = std::make_shared<TestShadowNode>(node4);
+  node5->clearSourceNode();
+  ASSERT_EQ(node5->getSourceNode(), nullptr);
+}

From 408a5f264b4f67873e6763c3a718bafe40fd48b3 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 23 Mar 2018 16:46:10 -0700
Subject: [PATCH 0128/1109] iOS: added fabric/core ComponentDescriptor tests

Summary: Basic test for ComponentDescriptor mechanism.

Reviewed By: shergin

Differential Revision: D7388297

fbshipit-source-id: 3b0c625656e31df03d71a2e036388621a5e2e21d
---
 ReactCommon/fabric/core/BUCK                  |  1 +
 .../ConcreteComponentDescriptor.h             |  3 +-
 .../fabric/core/shadownode/ShadowNode.cpp     |  1 +
 .../core/tests/ComponentDescriptorTest.cpp    | 66 +++++++++++++++++++
 .../fabric/core/tests/ShadowNodeTest.cpp      | 23 +------
 ReactCommon/fabric/core/tests/TestComponent.h | 50 ++++++++++++++
 6 files changed, 122 insertions(+), 22 deletions(-)
 create mode 100644 ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
 create mode 100644 ReactCommon/fabric/core/tests/TestComponent.h

diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index f394579fc09a..d9ee58fae8b5 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -61,6 +61,7 @@ if not IS_OSS_BUILD:
     cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
         contacts = ["oncall+react_native@xmail.facebook.com"],
         compiler_flags = [
             "-fexceptions",
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 0a521bd49994..95de5e17534d 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -9,8 +9,9 @@
 
 #include <memory>
 
-#include <fabric/core/ShadowNode.h>
+#include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/Props.h>
+#include <fabric/core/ShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 0dfb51e1eba2..04fb5d30f86f 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -39,6 +39,7 @@ ShadowNode::ShadowNode(
   SharedShadowNodeSharedList children
 ):
   tag_(shadowNode->tag_),
+  rootTag_(shadowNode->rootTag_),
   instanceHandle_(shadowNode->instanceHandle_),
   props_(props ? props : shadowNode->props_),
   children_(children ? children : shadowNode->children_),
diff --git a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
new file mode 100644
index 000000000000..699642ce7f2d
--- /dev/null
+++ b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
@@ -0,0 +1,66 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <gtest/gtest.h>
+
+#include "TestComponent.h"
+
+using namespace facebook::react;
+
+TEST(ComponentDescriptorTest, createShadowNode) {
+  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>();
+
+  ASSERT_EQ(descriptor->getComponentHandle(), typeid(TestShadowNode).hash_code());
+  ASSERT_STREQ(descriptor->getComponentName().c_str(), "Test");
+
+  RawProps raw;
+  raw["nativeID"] = "abc";
+  SharedShadowNode node = descriptor->createShadowNode(9, 1, (void *)NULL, raw);
+
+  ASSERT_EQ(node->getComponentHandle(), typeid(TestShadowNode).hash_code());
+  ASSERT_STREQ(node->getComponentName().c_str(), "Test");
+  ASSERT_EQ(node->getTag(), 9);
+  ASSERT_EQ(node->getRootTag(), 1);
+
+  // TODO(#27369757): getProps() doesn't work
+  // ASSERT_STREQ(node->getProps()->getNativeId().c_str(), "testNativeID");
+}
+
+TEST(ComponentDescriptorTest, cloneShadowNode) {
+  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>();
+
+  RawProps raw;
+  raw["nativeID"] = "abc";
+  SharedShadowNode node = descriptor->createShadowNode(9, 1, (void *)NULL, raw);
+  SharedShadowNode cloned = descriptor->cloneShadowNode(node);
+
+  ASSERT_EQ(cloned->getComponentHandle(), typeid(TestShadowNode).hash_code());
+  ASSERT_STREQ(cloned->getComponentName().c_str(), "Test");
+  ASSERT_EQ(cloned->getTag(), 9);
+  ASSERT_EQ(cloned->getRootTag(), 1);
+
+  // TODO(#27369757): getProps() doesn't work
+  // ASSERT_STREQ(cloned->getProps()->getNativeId().c_str(), "testNativeID");
+}
+
+TEST(ComponentDescriptorTest, appendChild) {
+  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>();
+
+  RawProps raw;
+  raw["nativeID"] = "abc";
+  SharedShadowNode node1 = descriptor->createShadowNode(1, 1, (void *)NULL, raw);
+  SharedShadowNode node2 = descriptor->createShadowNode(2, 1, (void *)NULL, raw);
+  SharedShadowNode node3 = descriptor->createShadowNode(3, 1, (void *)NULL, raw);
+
+  descriptor->appendChild(node1, node2);
+  descriptor->appendChild(node1, node3);
+
+  SharedShadowNodeSharedList node1Children = node1->getChildren();
+  ASSERT_EQ(node1Children->size(), 2);
+  ASSERT_EQ(node1Children->at(0), node2);
+  ASSERT_EQ(node1Children->at(1), node3);
+}
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index 75bc82e8039d..418938a497e1 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -11,28 +11,9 @@
 #include <fabric/core/ShadowNode.h>
 #include <gtest/gtest.h>
 
-using namespace facebook::react;
+#include "TestComponent.h"
 
-class TestProps : public Props {
-public:
-  TestProps() {
-    RawProps raw;
-    raw["nativeID"] = "testNativeID";
-    apply(raw);
-  }
-};
-using SharedTestProps = std::shared_ptr<const TestProps>;
-
-class TestShadowNode;
-using SharedTestShadowNode = std::shared_ptr<const TestShadowNode>;
-class TestShadowNode : public ConcreteShadowNode<TestProps> {
-public:
-  using ConcreteShadowNode::ConcreteShadowNode;
-
-  ComponentName getComponentName() const override {
-    return ComponentName("Test");
-  }
-};
+using namespace facebook::react;
 
 TEST(ShadowNodeTest, handleProps) {
   RawProps raw;
diff --git a/ReactCommon/fabric/core/tests/TestComponent.h b/ReactCommon/fabric/core/tests/TestComponent.h
new file mode 100644
index 000000000000..18890daeb03d
--- /dev/null
+++ b/ReactCommon/fabric/core/tests/TestComponent.h
@@ -0,0 +1,50 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ConcreteComponentDescriptor.h>
+#include <fabric/core/ConcreteShadowNode.h>
+#include <fabric/core/ShadowNode.h>
+
+using namespace facebook::react;
+
+/**
+ * This defines a set of TestComponent classes: Props, ShadowNode, ComponentDescriptor.
+ * To be used for testing purpose.
+ */
+
+class TestProps : public Props {
+public:
+  TestProps() {
+    RawProps raw;
+    raw["nativeID"] = "testNativeID";
+    apply(raw);
+  }
+};
+using SharedTestProps = std::shared_ptr<const TestProps>;
+
+class TestShadowNode;
+using SharedTestShadowNode = std::shared_ptr<const TestShadowNode>;
+class TestShadowNode : public ConcreteShadowNode<TestProps> {
+public:
+  using ConcreteShadowNode::ConcreteShadowNode;
+
+  ComponentName getComponentName() const override {
+    return ComponentName("Test");
+  }
+};
+
+class TestComponentDescriptor: public ConcreteComponentDescriptor<TestShadowNode> {
+public:
+  // TODO (shergin): Why does this gets repeated here and the shadow node class?
+  ComponentName getComponentName() const override {
+    return "Test";
+  }
+};

From 1acef4597747cc3068ae25bd22c26d500a228f3b Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 23 Mar 2018 22:09:11 -0700
Subject: [PATCH 0129/1109] iOS: added placeholder test setup for fabric
 graphics/uimanager/view targets

Reviewed By: shergin

Differential Revision: D7390366

fbshipit-source-id: d49fcc335fc03d52402676341f1da24177c6084b
---
 ReactCommon/fabric/debug/BUCK                 | 11 ++--
 ReactCommon/fabric/graphics/BUCK              | 35 ++++++++++---
 .../fabric/graphics/tests/GraphicsTest.cpp    | 17 +++++++
 ReactCommon/fabric/uimanager/BUCK             | 35 ++++++++++---
 .../uimanager/tests/FabricUIManagerTest.cpp   | 17 +++++++
 ReactCommon/fabric/view/BUCK                  | 50 +++++++++++++++----
 ReactCommon/fabric/view/tests/ViewTest.cpp    | 17 +++++++
 7 files changed, 153 insertions(+), 29 deletions(-)
 create mode 100644 ReactCommon/fabric/graphics/tests/GraphicsTest.cpp
 create mode 100644 ReactCommon/fabric/uimanager/tests/FabricUIManagerTest.cpp
 create mode 100644 ReactCommon/fabric/view/tests/ViewTest.cpp

diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index 6ce9e7f29e3d..d22caf8f9556 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -10,14 +10,12 @@ if not IS_OSS_BUILD:
 rn_xplat_cxx_library(
     name = "debug",
     srcs = glob(
-        [
-            "*.cpp",
-        ],
+        ["**/*.cpp"],
+        excludes = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
-        [
-            "*.h",
-        ],
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
@@ -54,6 +52,7 @@ if not IS_OSS_BUILD:
     cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
         contacts = ["oncall+react_native@xmail.facebook.com"],
         compiler_flags = [
             "-fexceptions",
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index e1a020d730b4..967f33aafc9b 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -10,14 +10,12 @@ if not IS_OSS_BUILD:
 rn_xplat_cxx_library(
     name = "graphics",
     srcs = glob(
-        [
-            "**/*.cpp",
-        ],
+        ["**/*.cpp"],
+        excludes = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
-        [
-            "**/*.h",
-        ],
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
@@ -39,6 +37,9 @@ rn_xplat_cxx_library(
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
+    tests = [
+        ":tests",
+    ],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//fbsystrace:fbsystrace",
@@ -48,3 +49,25 @@ rn_xplat_cxx_library(
         "xplat//third-party/glog:glog",
     ],
 )
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+
+    cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":graphics",
+        ],
+    )
diff --git a/ReactCommon/fabric/graphics/tests/GraphicsTest.cpp b/ReactCommon/fabric/graphics/tests/GraphicsTest.cpp
new file mode 100644
index 000000000000..3b88ac8a423d
--- /dev/null
+++ b/ReactCommon/fabric/graphics/tests/GraphicsTest.cpp
@@ -0,0 +1,17 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <fabric/graphics/graphicValuesConversions.h>
+#include <gtest/gtest.h>
+
+using namespace facebook::react;
+
+TEST(GraphicsTest, testSomething) {
+  // TODO
+}
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index dc7939377d97..ca7700e5c44b 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -10,14 +10,12 @@ if not IS_OSS_BUILD:
 rn_xplat_cxx_library(
     name = "uimanager",
     srcs = glob(
-        [
-            "**/*.cpp",
-        ],
+        ["**/*.cpp"],
+        excludes = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
-        [
-            "**/*.h",
-        ],
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
@@ -39,6 +37,9 @@ rn_xplat_cxx_library(
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
+    tests = [
+        ":tests",
+    ],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//fbsystrace:fbsystrace",
@@ -51,3 +52,25 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/view:view"),
     ],
 )
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+
+    cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":uimanager",
+        ],
+    )
diff --git a/ReactCommon/fabric/uimanager/tests/FabricUIManagerTest.cpp b/ReactCommon/fabric/uimanager/tests/FabricUIManagerTest.cpp
new file mode 100644
index 000000000000..d22ed7f94631
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/tests/FabricUIManagerTest.cpp
@@ -0,0 +1,17 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <fabric/uimanager/FabricUIManager.h>
+#include <gtest/gtest.h>
+
+using namespace facebook::react;
+
+TEST(FabricUIManagerTest, testSomething) {
+  // TODO
+}
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 3db0dd82bf72..5716485f77e5 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -2,22 +2,21 @@ load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "
 load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
 load("//ReactNative:DEFS.bzl", "react_native_xplat_target")
 
-CXX_LIBRARY_COMPILER_FLAGS = [
-    "-std=c++14",
-    "-Wall",
-]
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
 
 rn_xplat_cxx_library(
     name = "view",
     srcs = glob(
-        [
-            "**/*.cpp",
-        ],
+        ["**/*.cpp"],
+        excludes = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
-        [
-            "**/*.h",
-        ],
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
@@ -28,15 +27,22 @@ rn_xplat_cxx_library(
         ],
         prefix = "fabric/view",
     ),
-    compiler_flags = CXX_LIBRARY_COMPILER_FLAGS + [
+    compiler_flags = [
         "-fexceptions",
         "-frtti",
+        "-std=c++14",
+        "-Wall",
     ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
     force_static = True,
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
+    tests = [
+        ":tests",
+    ],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//fbsystrace:fbsystrace",
@@ -50,3 +56,25 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/graphics:graphics"),
     ],
 )
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+
+    cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":view",
+        ],
+    )
diff --git a/ReactCommon/fabric/view/tests/ViewTest.cpp b/ReactCommon/fabric/view/tests/ViewTest.cpp
new file mode 100644
index 000000000000..6ea577d8fa52
--- /dev/null
+++ b/ReactCommon/fabric/view/tests/ViewTest.cpp
@@ -0,0 +1,17 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <fabric/view/ViewComponentDescriptor.h>
+#include <gtest/gtest.h>
+
+using namespace facebook::react;
+
+TEST(ViewTest, testSomething) {
+  // TODO
+}

From 228f5c83f9f2459b119ff388d0abd8e2f852c6c7 Mon Sep 17 00:00:00 2001
From: Jake <me@jh.gg>
Date: Sat, 24 Mar 2018 23:04:41 -0700
Subject: [PATCH 0130/1109] use correct delegate queue in RCTRSWebSocket

Summary:
This commit makes the websocket's delegate dispatch queue use `RCTWebSocketModule`'s method queue.

This fixes a bug where didReceiveMessage was called on the wrong queue, which is especially harmful if the websocket has a contentHandler expects to be running on the RCTWebSocketModule's method queue.

This also fixes the race condition where `_contentHandlers` and `_sockets` can be mutated from the main dispatch queue (the default in `RCTRSWebSocket`) and `RCTWebSocketModule`'s method queue.

Websockets still work, and hopefully crash less now.

- [iOS][BUGFIX][WebSocket] fix crashes caused by a race condition in websocket delegates.
Closes https://github.com/facebook/react-native/pull/18530

Differential Revision: D7394298

Pulled By: hramos

fbshipit-source-id: 230466ccb47ea532ced15cd7603256a19077b32b
---
 Libraries/WebSocket/RCTWebSocketModule.m | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Libraries/WebSocket/RCTWebSocketModule.m b/Libraries/WebSocket/RCTWebSocketModule.m
index 425ff9873643..bc79dcd16c30 100644
--- a/Libraries/WebSocket/RCTWebSocketModule.m
+++ b/Libraries/WebSocket/RCTWebSocketModule.m
@@ -82,6 +82,7 @@ - (void)invalidate
   }];
 
   RCTSRWebSocket *webSocket = [[RCTSRWebSocket alloc] initWithURLRequest:request protocols:protocols];
+  [webSocket setDelegateDispatchQueue:_methodQueue];
   webSocket.delegate = self;
   webSocket.reactTag = socketID;
   if (!_sockets) {

From 2cc75f7d4781a7ec7b5f4566964b988435859e5e Mon Sep 17 00:00:00 2001
From: Jonathan Dann <jonathan@fb.com>
Date: Sun, 25 Mar 2018 13:56:13 -0700
Subject: [PATCH 0131/1109] Add YGNodeSetChildren(), YGNodeTraversePreOrder()

Reviewed By: Woody17

Differential Revision: D7360203

fbshipit-source-id: 32df8e1213ead03bc0a026ec4bf453bc799bb9ce
---
 ReactCommon/yoga/yoga/Yoga.cpp | 61 ++++++++++++++++++++++++++++++++--
 ReactCommon/yoga/yoga/Yoga.h   | 13 ++++++++
 2 files changed, 72 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 570f7ab964e1..1600b1b05fa0 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -295,8 +295,8 @@ static YGNodeRef YGNodeDeepClone(YGNodeRef oldNode) {
 }
 
 void YGNodeFree(const YGNodeRef node) {
-  if (node->getParent()) {
-    node->getParent()->removeChild(node);
+  if (YGNodeRef parent = node->getParent()) {
+    parent->removeChild(node);
     node->setParent(nullptr);
   }
 
@@ -477,6 +477,48 @@ void YGNodeRemoveAllChildren(const YGNodeRef parent) {
   parent->markDirtyAndPropogate();
 }
 
+static void YGNodeSetChildrenInternal(YGNodeRef const parent, const std::vector<YGNodeRef> &children)
+{
+  if (!parent) {
+    return;
+  }
+  if (children.size() == 0) {
+    if (YGNodeGetChildCount(parent) > 0) {
+      for (YGNodeRef const child : parent->getChildren()) {
+        child->setLayout(YGLayout());
+        child->setParent(nullptr);
+      }
+      parent->setChildren(YGVector());
+      parent->markDirtyAndPropogate();
+    }
+  } else {
+    if (YGNodeGetChildCount(parent) > 0) {
+      for (YGNodeRef const oldChild : parent->getChildren()) {
+        // Our new children may have nodes in common with the old children. We don't reset these common nodes.
+        if (std::find(children.begin(), children.end(), oldChild) == children.end()) {
+          oldChild->setLayout(YGLayout());
+          oldChild->setParent(nullptr);
+        }
+      }
+    }
+    parent->setChildren(children);
+    for (YGNodeRef child : children) {
+      child->setParent(parent);
+    }
+    parent->markDirtyAndPropogate();
+  }
+}
+
+void YGNodeSetChildren(YGNodeRef const parent, const YGNodeRef c[], const uint32_t count) {
+  const YGVector children = {c, c + count};
+  YGNodeSetChildrenInternal(parent, children);
+}
+
+void YGNodeSetChildren(YGNodeRef const parent, const std::vector<YGNodeRef> &children)
+{
+  YGNodeSetChildrenInternal(parent, children);
+}
+
 YGNodeRef YGNodeGetChild(const YGNodeRef node, const uint32_t index) {
   if (index < node->getChildren().size()) {
     return node->getChild(index);
@@ -3925,3 +3967,18 @@ void *YGConfigGetContext(const YGConfigRef config) {
 void YGConfigSetNodeClonedFunc(const YGConfigRef config, const YGNodeClonedFunc callback) {
   config->cloneNodeCallback = callback;
 }
+
+static void YGTraverseChildrenPreOrder(const YGVector& children, const std::function<void(YGNodeRef node)>& f) {
+  for (YGNodeRef node : children) {
+    f(node);
+    YGTraverseChildrenPreOrder(node->getChildren(), f);
+  }
+}
+
+void YGTraversePreOrder(YGNodeRef const node, std::function<void(YGNodeRef node)>&& f) {
+  if (!node) {
+    return;
+  }
+  f(node);
+  YGTraverseChildrenPreOrder(node->getChildren(), f);
+}
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index 2ec6a687ee74..1a985fa56317 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -84,6 +84,7 @@ WIN_EXPORT void YGNodeRemoveAllChildren(const YGNodeRef node);
 WIN_EXPORT YGNodeRef YGNodeGetChild(const YGNodeRef node, const uint32_t index);
 WIN_EXPORT YGNodeRef YGNodeGetParent(const YGNodeRef node);
 WIN_EXPORT uint32_t YGNodeGetChildCount(const YGNodeRef node);
+WIN_EXPORT void YGNodeSetChildren(YGNodeRef const parent, const YGNodeRef children[], const uint32_t count);
 
 WIN_EXPORT void YGNodeCalculateLayout(const YGNodeRef node,
                                       const float availableWidth,
@@ -298,3 +299,15 @@ WIN_EXPORT float YGRoundValueToPixelGrid(
     const bool forceFloor);
 
 YG_EXTERN_C_END
+
+#ifdef __cplusplus
+
+#include <functional>
+#include <vector>
+
+// Calls f on each node in the tree including the given node argument.
+extern void YGTraversePreOrder(YGNodeRef const node, std::function<void(YGNodeRef node)>&& f);
+
+extern void YGNodeSetChildren(YGNodeRef const parent, const std::vector<YGNodeRef> &children);
+
+#endif

From 8b9b3f605ed9691728872e74dd555a0b1792c47a Mon Sep 17 00:00:00 2001
From: Gustavo Gard <gusgard@gmail.com>
Date: Sun, 25 Mar 2018 19:46:13 -0700
Subject: [PATCH 0132/1109] Correct AnimatedValueXY URL

Summary:
Correct URL
Closes https://github.com/facebook/react-native/pull/18556

Differential Revision: D7396357

Pulled By: mdvacca

fbshipit-source-id: f8ff6c9b037fe733cf3be8d1b889d1dcd9c94afb
---
 Libraries/Animated/src/AnimatedImplementation.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/Animated/src/AnimatedImplementation.js b/Libraries/Animated/src/AnimatedImplementation.js
index 69a96ba1d3e6..e13aef1e7235 100644
--- a/Libraries/Animated/src/AnimatedImplementation.js
+++ b/Libraries/Animated/src/AnimatedImplementation.js
@@ -521,7 +521,7 @@ module.exports = {
   /**
    * 2D value class for driving 2D animations, such as pan gestures.
    *
-   * See https://facebook.github.io/react-native/releases/next/docs/animatedvaluexy.html
+   * See https://facebook.github.io/react-native/docs/animatedvaluexy.html
    */
   ValueXY: AnimatedValueXY,
   /**

From 85e33aaf908996e99220bff4a2bdbbdf7c0d12b0 Mon Sep 17 00:00:00 2001
From: Tadeu Valentt <tadeu.valentt@gmail.com>
Date: Sun, 25 Mar 2018 20:39:22 -0700
Subject: [PATCH 0133/1109] Prevents android crash due to unsupported ellipsize
 mode

Summary:
Fixes #18474

This allows use clip as ellipsize mode for truncated text on android

Added a test to RNTester, so it can be tested from there:
1. Run RNTester project
2. Navigate to `<Text>` tests
3. Scroll down to "Ellipsize mode" examples
4. Check the default behavior being applied when the value is set to "clip"

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [BUGFIX] [Text] - Prevents android crash due to unsupported "clip" ellipsize mode

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18540

Differential Revision: D7396379

Pulled By: mdvacca

fbshipit-source-id: 6c4b223731143c5081b3d12a3c740d1e375bd586
---
 RNTester/js/TextExample.android.js                             | 3 +++
 .../facebook/react/views/text/ReactTextAnchorViewManager.java  | 2 ++
 2 files changed, 5 insertions(+)

diff --git a/RNTester/js/TextExample.android.js b/RNTester/js/TextExample.android.js
index 0b0bf195f68f..b912337827a2 100644
--- a/RNTester/js/TextExample.android.js
+++ b/RNTester/js/TextExample.android.js
@@ -453,6 +453,9 @@ class TextExample extends React.Component<{}> {
           <Text ellipsizeMode="head" numberOfLines={1}>
             This very long text should be truncated with dots in the beginning.
           </Text>
+          <Text ellipsizeMode="clip" numberOfLines={1}>
+            This very long text should be clipped and this will not be visible.
+          </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Include Font Padding">
           <View style={{flexDirection: 'row', justifyContent: 'space-around', marginBottom: 10}}>
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextAnchorViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextAnchorViewManager.java
index 71ba5eef4609..776bce7ccdc5 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextAnchorViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextAnchorViewManager.java
@@ -52,6 +52,8 @@ public void setEllipsizeMode(ReactTextView view, @Nullable String ellipsizeMode)
       view.setEllipsizeLocation(TextUtils.TruncateAt.START);
     } else if (ellipsizeMode.equals("middle")) {
       view.setEllipsizeLocation(TextUtils.TruncateAt.MIDDLE);
+    } else if (ellipsizeMode.equals("clip")) {
+      view.setEllipsizeLocation(null);
     } else {
       throw new JSApplicationIllegalArgumentException("Invalid ellipsizeMode: " + ellipsizeMode);
     }

From 226bff3ed0772ff3b9d69ea45fb57f3c0c930029 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Sun, 25 Mar 2018 20:56:27 -0700
Subject: [PATCH 0134/1109] Android: include error types in getCurrentPosition
 error

Summary:
Thank you for sending the PR! We appreciate you spending the time to work on these changes.
Help us understand your motivation by explaining why you decided to make this change.

Include geolocation error types in error, and provide feature parity with iOS.

If error occurs when you call getCurrentPosition, then error object includes PERMISSION_DENIED, POSITION_UNAVAILABLE, TIMEOUT keys with error codes. It should be used to compare with error.code value.

This is minor fix that provides feature parity with iOS.
Closes https://github.com/facebook/react-native/pull/18533

Differential Revision: D7396586

Pulled By: mdvacca

fbshipit-source-id: bd698b80a3d075456738a3d4e48b572ae819ee3d
---
 .../facebook/react/modules/location/PositionError.java    | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/location/PositionError.java b/ReactAndroid/src/main/java/com/facebook/react/modules/location/PositionError.java
index 82f7d0dc8015..f8dffa5850ae 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/location/PositionError.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/location/PositionError.java
@@ -35,9 +35,17 @@ public class PositionError {
   public static WritableMap buildError(int code, String message) {
     WritableMap error = Arguments.createMap();
     error.putInt("code", code);
+
     if (message != null) {
       error.putString("message", message);
     }
+    
+    /**
+    * Provide error types in error message. Feature parity with iOS
+    */
+    error.putInt("PERMISSION_DENIED", PERMISSION_DENIED);
+    error.putInt("POSITION_UNAVAILABLE", POSITION_UNAVAILABLE);
+    error.putInt("TIMEOUT", TIMEOUT);
     return error;
   }
 }

From ca20fcd47d55585e66f429e698afda49abdc339c Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Sun, 25 Mar 2018 22:00:11 -0700
Subject: [PATCH 0135/1109] Use afterEvaluate to make gradle bundle task work
 with configureondemand

Summary:
The js bundle task does not run when `org.gradle.configureondemand` is set to true. This uses `afterEvaluate` instead of `gradle.projectsEvaluated` which is executed properly.

Add `org.gradle.configureondemand=true`, run RNTester in release mode and make sure the bundle task is run.

[ANDROID] [BUGFIX] [LOCATION] - Fix release bundle task when org.gradle.configureondemand=true
Closes https://github.com/facebook/react-native/pull/18557

Differential Revision: D7396744

Pulled By: mdvacca

fbshipit-source-id: 9ea134cb49e8a087cec16f82b990cd19af76785a
---
 RNTester/android/app/gradle.properties | 2 ++
 react.gradle                           | 2 +-
 2 files changed, 3 insertions(+), 1 deletion(-)

diff --git a/RNTester/android/app/gradle.properties b/RNTester/android/app/gradle.properties
index 74027349d96f..04cbf4f74219 100644
--- a/RNTester/android/app/gradle.properties
+++ b/RNTester/android/app/gradle.properties
@@ -1,4 +1,6 @@
 android.useDeprecatedNdk=true
+org.gradle.parallel=true
+org.gradle.configureondemand=true
 MYAPP_RELEASE_STORE_FILE=my-release-key.keystore
 MYAPP_RELEASE_KEY_ALIAS=my-key-alias
 MYAPP_RELEASE_STORE_PASSWORD=*****
diff --git a/react.gradle b/react.gradle
index 64b2f02f8cbf..bdf392ad9a71 100644
--- a/react.gradle
+++ b/react.gradle
@@ -23,7 +23,7 @@ void runBefore(String dependentTaskName, Task task) {
     }
 }
 
-gradle.projectsEvaluated {
+afterEvaluate {
     // Grab all build types and product flavors
     def buildTypes = android.buildTypes.collect { type -> type.name }
     def productFlavors = android.productFlavors.collect { flavor -> flavor.name }

From 53782eafc96d9f0564e25c668c57a60321ccc2ec Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:26 -0700
Subject: [PATCH 0136/1109] Fabric: Source shadow node is now stored as a weak
 pointer

Summary:
We use shource nodes only in the diffing alogorithm. It implies that we have strong pointers to those nodes in trees we compare against.
Using weak_ptr's allows to avoid memory leaks.

Reviewed By: mdvacca

Differential Revision: D7376348

fbshipit-source-id: 34e5f58f18a00475f6bcdfbea3996b41c84dff62
---
 ReactCommon/fabric/core/shadownode/ShadowNode.cpp | 9 +++++----
 ReactCommon/fabric/core/shadownode/ShadowNode.h   | 3 ++-
 2 files changed, 7 insertions(+), 5 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 04fb5d30f86f..e1394cccca71 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -68,7 +68,7 @@ InstanceHandle ShadowNode::getInstanceHandle() const {
 }
 
 SharedShadowNode ShadowNode::getSourceNode() const {
-  return sourceNode_;
+  return sourceNode_.lock();
 }
 
 void ShadowNode::sealRecursive() const {
@@ -111,7 +111,7 @@ void ShadowNode::replaceChild(const SharedShadowNode &oldChild, const SharedShad
 
 void ShadowNode::clearSourceNode() {
   ensureUnsealed();
-  sourceNode_ = nullptr;
+  sourceNode_.reset();
 }
 
 #pragma mark - DebugStringConvertible
@@ -146,10 +146,11 @@ SharedDebugStringConvertibleList ShadowNode::getDebugProps() const {
     list.push_back(std::make_shared<DebugStringConvertibleItem>("handle", std::to_string((size_t)instanceHandle_)));
   }
 
-  if (sourceNode_) {
+  SharedShadowNode sourceNode = getSourceNode();
+  if (sourceNode) {
     list.push_back(std::make_shared<DebugStringConvertibleItem>(
       "source",
-      sourceNode_->getDebugDescription({.maximumDepth = 1, .format = false})
+      sourceNode->getDebugDescription({.maximumDepth = 1, .format = false})
     ));
   }
 
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 1deb4d520790..aa68556f9ce3 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -24,6 +24,7 @@ using SharedShadowNode = std::shared_ptr<const ShadowNode>;
 using SharedShadowNodeList = std::vector<std::shared_ptr<const ShadowNode>>;
 using SharedShadowNodeSharedList = std::shared_ptr<const SharedShadowNodeList>;
 using SharedShadowNodeUnsharedList = std::shared_ptr<SharedShadowNodeList>;
+using WeakShadowNode = std::weak_ptr<const ShadowNode>;
 
 class ShadowNode:
   public virtual Sealable,
@@ -79,7 +80,7 @@ class ShadowNode:
   InstanceHandle instanceHandle_;
   SharedProps props_;
   SharedShadowNodeSharedList children_;
-  SharedShadowNode sourceNode_;
+  WeakShadowNode sourceNode_;
 };
 
 } // namespace react

From 1bb6db36bef1c5018c06ada5763554b23312060f Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:28 -0700
Subject: [PATCH 0137/1109] Fabric: Removed unused copy constructor
 YogaLayoutableShadowNode()

Summary: Trivial. We don't use it, and it shouldn't be exist by desing.

Reviewed By: mdvacca

Differential Revision: D7376351

fbshipit-source-id: 22f03af2b3596c274a22bab1fab6d8af854a7374
---
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 7 -------
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h   | 1 -
 2 files changed, 8 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 09301f35b50a..f53d63f70eea 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -31,13 +31,6 @@ SharedYogaConfig YogaLayoutableShadowNode::suitableYogaConfig() {
   return sharedYogaConfig;
 }
 
-YogaLayoutableShadowNode::YogaLayoutableShadowNode() {
-  auto yogaNode = std::make_shared<YGNode>();
-  yogaNode->markDirtyAndPropogate();
-  yogaNode->setConfig(suitableYogaConfig().get());
-  yogaNode->setContext(this);
-  yogaNode_ = yogaNode;
-}
 
 YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   const SharedYogaStylableProps &props,
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index cba25fe87d2b..e07acc8598cf 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -40,7 +40,6 @@ class YogaLayoutableShadowNode:
 public:
 
 #pragma mark - Constructors
-  YogaLayoutableShadowNode();
 
   YogaLayoutableShadowNode(
     const SharedYogaStylableProps &props,

From 8f9212b83922e3adeb3dcdd20d239ebab7a1fcda Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:30 -0700
Subject: [PATCH 0138/1109] Fabric: Fixed lost YogaNode's context in
 YogaLayoutableShadowNode

Summary: We replace yogaNode with newly creaded (by Yoga) one. So, we have to set up context.

Reviewed By: mdvacca

Differential Revision: D7376345

fbshipit-source-id: 7926a10e3f057fc385e7731c354827aeb8245760
---
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index f53d63f70eea..376f092367c9 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -31,7 +31,6 @@ SharedYogaConfig YogaLayoutableShadowNode::suitableYogaConfig() {
   return sharedYogaConfig;
 }
 
-
 YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   const SharedYogaStylableProps &props,
   const SharedShadowNodeSharedList &children
@@ -198,6 +197,7 @@ void YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYogaNod
   assert(newShadowNode);
 
   // And finally, we have to replace underline yoga node with the new one provided by Yoga.
+  newYogaNode->setContext((void *)newShadowNode.get());
   newShadowNode->yogaNode_ = std::shared_ptr<YGNode>(newYogaNode);
 }
 

From ee0cc6bbe7b4597ebbb27b6975b6b77ae64da9a8 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:33 -0700
Subject: [PATCH 0139/1109] Fabric: Implementing cloneAndReplaceChild() for
 ViewShadowNode

Summary:
First, LayoutableShadowNode::cloneAndReplaceChild() is now pure virtual. The default implementation was useless and confusing.
Second, cloneAndReplaceChild() is now fully implemented for ViewShadowNode, so fancy Yoga Concurrent layout *should* work now.

Reviewed By: mdvacca

Differential Revision: D7376352

fbshipit-source-id: 1199a37e64535c8592a2a5480e60139f61d02006
---
 .../core/layout/LayoutableShadowNode.cpp      |  4 ---
 .../fabric/core/layout/LayoutableShadowNode.h |  3 +--
 ReactCommon/fabric/view/ViewShadowNode.cpp    | 27 +++++++++++++++++++
 ReactCommon/fabric/view/ViewShadowNode.h      |  1 +
 4 files changed, 29 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index ea2de415cdfe..8148f00dff00 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -93,9 +93,5 @@ void LayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
   // Default implementation does nothing.
 }
 
-SharedLayoutableShadowNode LayoutableShadowNode::cloneAndReplaceChild(const SharedLayoutableShadowNode &child) {
-  return child;
-}
-
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
index e59df8bc9ab4..e3176f1f3572 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
@@ -93,9 +93,8 @@ class LayoutableShadowNode:
   /*
    * In case layout algorithm needs to mutate this (probably sealed) node,
    * it has to clone and replace it in the hierarchy before to do so.
-   * Default implementation does nothing and returns `child`.
    */
-  virtual SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child);
+  virtual SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child) = 0;
 
   /*
    * Sets layout metrics for the shadow node.
diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/view/ViewShadowNode.cpp
index 7b07fec22775..8bb5f33fdb83 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.cpp
+++ b/ReactCommon/fabric/view/ViewShadowNode.cpp
@@ -7,6 +7,8 @@
 
 #include "ViewShadowNode.h"
 
+#include <algorithm>
+
 #include <fabric/debug/DebugStringConvertibleItem.h>
 
 namespace facebook {
@@ -87,6 +89,31 @@ SharedLayoutableShadowNodeList ViewShadowNode::getChildren() const {
   return sharedLayoutableShadowNodeList;
 }
 
+SharedLayoutableShadowNode ViewShadowNode::cloneAndReplaceChild(const SharedLayoutableShadowNode &child) {
+  ensureUnsealed();
+
+  // We cannot mutate `children_` in place here because it is a *shared*
+  // data structure which means other `ShadowNodes` might refer to its old value.
+  // So, we have to clone this and only then mutate.
+  auto nonConstChildrenCopy = SharedShadowNodeList(*children_);
+
+  auto viewShadowNodeChild = std::dynamic_pointer_cast<const ViewShadowNode>(child);
+  assert(viewShadowNodeChild);
+
+  auto viewShadowNodeChildClone = std::make_shared<const ViewShadowNode>(viewShadowNodeChild);
+
+  std::replace(
+    nonConstChildrenCopy.begin(),
+    nonConstChildrenCopy.end(),
+    std::static_pointer_cast<const ShadowNode>(viewShadowNodeChild),
+    std::static_pointer_cast<const ShadowNode>(viewShadowNodeChildClone)
+  );
+
+  children_ = std::make_shared<const SharedShadowNodeList>(nonConstChildrenCopy);
+
+  return std::static_pointer_cast<const LayoutableShadowNode>(viewShadowNodeChildClone);
+}
+
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList ViewShadowNode::getDebugProps() const {
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/view/ViewShadowNode.h
index fffaaa20c98a..4ac446556d77 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.h
+++ b/ReactCommon/fabric/view/ViewShadowNode.h
@@ -57,6 +57,7 @@ class ViewShadowNode:
 #pragma mark - LayoutableShadowNode
 
   SharedLayoutableShadowNodeList getChildren() const override;
+  SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child) override;
 };
 
 } // namespace react

From 5642514aa52e3b1afc2a59e9bf4bba604a9aaa16 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:36 -0700
Subject: [PATCH 0140/1109] Fabric: Detailed looging in FabricUIManager

Summary: Apparently, we need this.

Reviewed By: mdvacca

Differential Revision: D7376350

fbshipit-source-id: 11d8ad54c7439e6c19a739ae1ac31af90d37166a
---
 .../fabric/uimanager/FabricUIManager.cpp      | 26 ++++++++++++++++---
 1 file changed, 22 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 14adad47c8ce..997a5a91b9b7 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -45,51 +45,69 @@ FabricUIManager::FabricUIManager(const std::shared_ptr<IFabricPlatformUIOperatio
 }
 
 SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
+  LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
   ComponentDescriptor &componentDescriptor = *_registry["View"];
   RawProps rawProps = rawPropsFromDynamic(props);
   SharedShadowNode shadowNode = componentDescriptor.createShadowNode(tag, rootTag, instanceHandle, rawProps);
+  LOG(INFO) << "FabricUIManager::createNode() -> " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return shadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode) {
+  LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
-  return componentDescriptor.cloneShadowNode(shadowNode);
+  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode);
+  LOG(INFO) << "FabricUIManager::cloneNode() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  return clonnedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode) {
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   // Assuming semantic: Cloning with same props but empty children.
   ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
-  return componentDescriptor.cloneShadowNode(shadowNode, nullptr, {});
+  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, nullptr, {});
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  return clonnedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with same children and specified props.
   ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
-  return componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), nullptr);
+  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), nullptr);
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  return clonnedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with empty children and specified props.
   ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
-  return componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), {});
+  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), {});
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  return clonnedShadowNode;
 }
 
 void FabricUIManager::appendChild(const SharedShadowNode &parentShadowNode, const SharedShadowNode &childShadowNode) {
+  LOG(INFO) << "FabricUIManager::appendChild(parentShadowNode: " << parentShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", childShadowNode: " << childShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   ComponentDescriptor &componentDescriptor = *_registry[parentShadowNode];
   componentDescriptor.appendChild(parentShadowNode, childShadowNode);
 }
 
 SharedShadowNodeUnsharedList FabricUIManager::createChildSet(int rootTag) {
+  LOG(INFO) << "FabricUIManager::createChildSet(rootTag: " << rootTag << ")";
   return std::make_shared<SharedShadowNodeList>(SharedShadowNodeList({}));
 }
 
 void FabricUIManager::appendChildToSet(const SharedShadowNodeUnsharedList &shadowNodeList, const SharedShadowNode &shadowNode) {
+  LOG(INFO) << "FabricUIManager::appendChildToSet(shadowNodeList: " << shadowNodeList << ", shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   shadowNodeList->push_back(shadowNode);
 }
 
 void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedList &children) {
+  LOG(INFO) << "FabricUIManager::appendChildToSet(rootTag: " << rootTag << ", shadowNodeList: " << children << ")";
   ComponentDescriptor &componentDescriptor = *_registry["View"];
   SharedShadowNode previousRootShadowNode = componentDescriptor.createShadowNode(rootTag, rootTag, nullptr, {});
   auto childrenCopy = std::make_shared<const SharedShadowNodeList>(SharedShadowNodeList(*children));

From 53dfbcc81c6d8623c7e9d9febf67416c6cdd2cdf Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:38 -0700
Subject: [PATCH 0141/1109] Fabric: Fixed bug in node management in
 FabricUIManager

Summary: Suddenly, `{}` means `{nullptr}`, not `empty list`.

Reviewed By: mdvacca

Differential Revision: D7376347

fbshipit-source-id: 76f81eebe046ae592f0a42be7bcaa0587732c2a9
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 997a5a91b9b7..0da19722a252 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -65,7 +65,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   // Assuming semantic: Cloning with same props but empty children.
   ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
-  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, nullptr, {});
+  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, nullptr, ShadowNode::emptySharedShadowNodeSharedList());
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonnedShadowNode;
 }
@@ -85,7 +85,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
   // Assuming semantic: Cloning with empty children and specified props.
   ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
-  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), {});
+  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), ShadowNode::emptySharedShadowNodeSharedList());
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonnedShadowNode;
 }

From 6f17e3b328f61a8c75ceb07fc95231636db4ecc7 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:40 -0700
Subject: [PATCH 0142/1109] Fabric: Introducing `TreeMutationInstruction`

Summary: The Great Diffing algorithm is coming.

Reviewed By: fkgozali

Differential Revision: D7376528

fbshipit-source-id: bdfef69551980136cfd1717a11ae376d5eef126b
---
 .../uimanager/TreeMutationInstruction.cpp     | 150 ++++++++++++++++++
 .../uimanager/TreeMutationInstruction.h       | 109 +++++++++++++
 2 files changed, 259 insertions(+)
 create mode 100644 ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
 create mode 100644 ReactCommon/fabric/uimanager/TreeMutationInstruction.h

diff --git a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
new file mode 100644
index 000000000000..da60fb83cf01
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
@@ -0,0 +1,150 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "TreeMutationInstruction.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+namespace facebook {
+namespace react {
+
+const TreeMutationInstruction TreeMutationInstruction::Insert(
+  SharedShadowNode parentNode,
+  SharedShadowNode childNode,
+  int index
+) {
+  assert(parentNode);
+  assert(childNode);
+  assert(index != -1);
+
+  return TreeMutationInstruction(
+    Inserting,
+    parentNode,
+    nullptr,
+    childNode,
+    index
+  );
+}
+
+const TreeMutationInstruction TreeMutationInstruction::Delete(
+  SharedShadowNode parentNode,
+  SharedShadowNode childNode,
+  int index
+) {
+  assert(parentNode);
+  assert(childNode);
+  assert(index != -1);
+
+  return TreeMutationInstruction(
+    Deleting,
+    parentNode,
+    childNode,
+    nullptr,
+    index
+  );
+}
+
+const TreeMutationInstruction TreeMutationInstruction::Update(
+  SharedShadowNode parentNode,
+  SharedShadowNode oldChildNode,
+  SharedShadowNode newChildNode,
+  int index
+) {
+  assert(parentNode);
+  assert(oldChildNode);
+  assert(newChildNode);
+  assert(index != -1);
+
+  return TreeMutationInstruction(
+    Updating,
+    parentNode,
+    oldChildNode,
+    newChildNode,
+    index
+  );
+}
+
+TreeMutationInstruction::TreeMutationInstruction(
+  Type type,
+  SharedShadowNode parentNode,
+  SharedShadowNode oldChildNode,
+  SharedShadowNode newChildNode,
+  int index
+):
+  type_(type),
+  parentNode_(parentNode),
+  oldChildNode_(oldChildNode),
+  newChildNode_(newChildNode),
+  index_(index) {};
+
+#pragma mark - Getters
+
+TreeMutationInstruction::Type TreeMutationInstruction::getType() const {
+  return type_;
+}
+
+SharedShadowNode TreeMutationInstruction::getParentNode() const {
+  assert(parentNode_);
+  return parentNode_;
+}
+
+SharedShadowNode TreeMutationInstruction::getOldChildNode() const {
+  assert(oldChildNode_);
+  return oldChildNode_;
+}
+
+SharedShadowNode TreeMutationInstruction::getNewChildNode() const {
+  assert(newChildNode_);
+  return newChildNode_;
+}
+
+int TreeMutationInstruction::getIndex() const {
+  assert(index_ != -1);
+  return index_;
+}
+
+#pragma mark - DebugStringConvertible
+
+std::string TreeMutationInstruction::getDebugName() const {
+  switch (type_) {
+    case Inserting:
+      return "Insert";
+    case Deleting:
+      return "Delete";
+    case Updating:
+      return "Update";
+  }
+};
+
+SharedDebugStringConvertibleList TreeMutationInstruction::getDebugProps() const {
+  DebugStringConvertibleOptions options = {.maximumDepth = 1, .format = false};
+
+  switch (type_) {
+    case Inserting:
+      return SharedDebugStringConvertibleList {
+        std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
+        std::make_shared<DebugStringConvertibleItem>("childNode", newChildNode_->getDebugDescription(options)),
+        std::make_shared<DebugStringConvertibleItem>("index", std::to_string(index_))
+      };
+    case Deleting:
+      return SharedDebugStringConvertibleList {
+        std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
+        std::make_shared<DebugStringConvertibleItem>("childNode", oldChildNode_->getDebugDescription(options)),
+        std::make_shared<DebugStringConvertibleItem>("index", std::to_string(index_))
+      };
+    case Updating:
+      return SharedDebugStringConvertibleList {
+        std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
+        std::make_shared<DebugStringConvertibleItem>("oldChildNode", oldChildNode_->getDebugDescription(options)),
+        std::make_shared<DebugStringConvertibleItem>("newChildNode", newChildNode_->getDebugDescription(options)),
+        std::make_shared<DebugStringConvertibleItem>("index", std::to_string(index_))
+      };
+  }
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/TreeMutationInstruction.h b/ReactCommon/fabric/uimanager/TreeMutationInstruction.h
new file mode 100644
index 000000000000..f0e09c17d35b
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/TreeMutationInstruction.h
@@ -0,0 +1,109 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <vector>
+
+#include <fabric/core/ShadowNode.h>
+#include <fabric/debug/DebugStringConvertible.h>
+
+namespace facebook {
+namespace react {
+
+class TreeMutationInstruction;
+
+using TreeMutationInstructionList = std::vector<TreeMutationInstruction>;
+
+/*
+ * Describes single native views tree mutation instruction which may contain
+ * pointers to an old shadow node, a new shadow node, a parent shadow node and
+ * final index of inserted or updated node.
+ * The relationship between native view instances and shadow node instances is
+ * defined by `tag` value.
+ */
+class TreeMutationInstruction:
+  public DebugStringConvertible {
+public:
+
+#pragma mark - Designated Initializers
+
+  /*
+   * Creates and returns an *Insert* instruction with following semantic:
+   *   1. Create a native view for the shadow node if needed;
+   *   2. Unmount the native view from a previous superview if needed;
+   *   3. Mount the native view to the new superview.
+   */
+  static const TreeMutationInstruction Insert(
+    SharedShadowNode parentNode,
+    SharedShadowNode childNode,
+    int index
+  );
+
+  /*
+   * Creates and returns a *Delete* instruction with following semantic:
+   *   1. Unmount the native view from a previous superview if needed;
+   *   2. Destroy (or return to a recycle pool) the native view.
+   */
+  static const TreeMutationInstruction Delete(
+    SharedShadowNode parentNode,
+    SharedShadowNode childNode,
+    int index
+  );
+  
+  /*
+   * Creates and returns an *Update* instruction with following semantic:
+   *   1. Update the presentation of a native view based on the new shadow node;
+   *   2. The exact set of changes are not specified but might contain
+   *      new props and/or new layout (or might be empty).
+   */
+  static const TreeMutationInstruction Update(
+    SharedShadowNode parentNode,
+    SharedShadowNode oldChildNode,
+    SharedShadowNode newChildNode,
+    int index
+  );
+
+#pragma mark - Type
+
+  enum Type {
+    Inserting,
+    Deleting,
+    Updating
+  };
+
+#pragma mark - Getters
+
+  Type getType() const;
+  SharedShadowNode getParentNode() const;
+  SharedShadowNode getOldChildNode() const;
+  SharedShadowNode getNewChildNode() const;
+  int getIndex() const;
+
+#pragma mark - DebugStringConvertible
+
+  std::string getDebugName() const override;
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+private:
+  TreeMutationInstruction(
+    Type type,
+    SharedShadowNode parentNode,
+    SharedShadowNode oldChildNode,
+    SharedShadowNode newChildNode,
+    int index
+  );
+
+  Type type_ {Inserting};
+  SharedShadowNode parentNode_ {nullptr};
+  SharedShadowNode oldChildNode_ {nullptr};
+  SharedShadowNode newChildNode_ {nullptr};
+  int index_ {-1};
+};
+
+} // namespace react
+} // namespace facebook

From cb7a7f3b93cbee1621a190f4c5dedfb31ac35744 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:42 -0700
Subject: [PATCH 0143/1109] Fabric: Deleted virtual default destructor from
 Props

Summary: Trivial. We don't need this because we already have another virtual method.

Reviewed By: fkgozali

Differential Revision: D7388964

fbshipit-source-id: 5ea6eb33ece72796d8cde2cc4b12c1240447d22a
---
 ReactCommon/fabric/core/shadownode/Props.h | 2 --
 1 file changed, 2 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/Props.h b/ReactCommon/fabric/core/shadownode/Props.h
index 5760f3491678..d7ecea7426c6 100644
--- a/ReactCommon/fabric/core/shadownode/Props.h
+++ b/ReactCommon/fabric/core/shadownode/Props.h
@@ -28,8 +28,6 @@ class Props:
   public virtual DebugStringConvertible {
 
 public:
-  virtual ~Props() = default;
-
   virtual void apply(const RawProps &rawProps);
 
   const std::string &getNativeId() const;

From 99e9c6e798e21b83d4bf664ca12286c57d6b104d Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 25 Mar 2018 22:43:43 -0700
Subject: [PATCH 0144/1109] Fabric: Collecting and printing ShadowNode's
 revision/generation

Summary: It drastically simplifies reading logs.

Reviewed By: fkgozali

Differential Revision: D7388963

fbshipit-source-id: 7849c803f295719918c20ddf8c082e5a5780116f
---
 ReactCommon/fabric/core/shadownode/ShadowNode.cpp | 8 +++++---
 ReactCommon/fabric/core/shadownode/ShadowNode.h   | 1 +
 2 files changed, 6 insertions(+), 3 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index e1394cccca71..2313be859eef 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -31,7 +31,8 @@ ShadowNode::ShadowNode(
   rootTag_(rootTag),
   instanceHandle_(instanceHandle),
   props_(props),
-  children_(children) {}
+  children_(children),
+  revision_(1) {}
 
 ShadowNode::ShadowNode(
   SharedShadowNode shadowNode,
@@ -43,7 +44,8 @@ ShadowNode::ShadowNode(
   instanceHandle_(shadowNode->instanceHandle_),
   props_(props ? props : shadowNode->props_),
   children_(children ? children : shadowNode->children_),
-  sourceNode_(shadowNode) {}
+  sourceNode_(shadowNode),
+  revision_(shadowNode->revision_ + 1) {}
 
 #pragma mark - Getters
 
@@ -121,7 +123,7 @@ std::string ShadowNode::getDebugName() const {
 }
 
 std::string ShadowNode::getDebugValue() const {
-  return getSealed() ? "sealed" : "";
+  return "r" + std::to_string(revision_) + (getSealed() ? "/sealed" : "");
 }
 
 SharedDebugStringConvertibleList ShadowNode::getDebugChildren() const {
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index aa68556f9ce3..4045be8462e6 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -81,6 +81,7 @@ class ShadowNode:
   SharedProps props_;
   SharedShadowNodeSharedList children_;
   WeakShadowNode sourceNode_;
+  int revision_;
 };
 
 } // namespace react

From 2ff8b7024ec7b8db71dcc600adc87b7ce5a9d81c Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Mon, 26 Mar 2018 12:12:53 -0700
Subject: [PATCH 0145/1109] Replace android_library with fb_android_library.

Reviewed By: adamjernst

Differential Revision: D7393004

fbshipit-source-id: 99060333267dd6e81a41e9da52002e05152e7ccb
---
 ReactNative/DEFS.bzl | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index 135bacfbc93d..13402b1bc878 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -183,3 +183,7 @@ def cxx_library(allow_jni_merging=None, **kwargs):
         if not (k.startswith("fbandroid_") or k.startswith("fbobjc_"))
     }
     native.cxx_library(**args)
+
+
+def fb_android_library(**kwargs):
+    native.android_library(**kwargs)

From de1040fcff558a58e2a616efebaf55d9bf5332b0 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 27 Mar 2018 09:15:54 -0700
Subject: [PATCH 0146/1109] Cache apt dependencies in test_android

Summary: Closes https://github.com/facebook/react-native/pull/18576

Differential Revision: D7415216

Pulled By: hramos

fbshipit-source-id: 9b7199fe5fb91a26ba0881e426a85395b2923f26
---
 .circleci/config.yml                     | 46 ++++++++++++++++++++----
 scripts/circleci/apt-get-android-deps.sh | 25 +++++++++++++
 2 files changed, 65 insertions(+), 6 deletions(-)
 create mode 100755 scripts/circleci/apt-get-android-deps.sh

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 675aeb4e0b07..196d3d3e6edf 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -38,6 +38,31 @@ aliases:
       - /opt/android/sdk
     key: v1-android-sdkmanager-packages-{{ arch }}-{{ .Branch }}-api-26-alpha-{{ checksum "scripts/circle-ci-android-setup.sh" }}
 
+  - &restore-cache-gradle
+    keys:
+      - v1-gradle-{{ arch }}-{{ .Branch }}-{{ checksum "build.gradle" }}-{{ checksum "ReactAndroid/build.gradle" }}
+      # Fallback in case checksum fails
+      - v1-gradle-{{ arch }}-{{ .Branch }}-{{ checksum "build.gradle" }}-
+      - v1-gradle-{{ arch }}-{{ .Branch }}-
+      # Fallback in case this is a first-time run on a fork
+      - v1-gradle-{{ arch }}-master-
+  - &save-cache-gradle
+    paths:
+      - ~/.gradle
+    key: v1-gradle-{{ arch }}-{{ .Branch }}-{{ checksum "build.gradle" }}-{{ checksum "ReactAndroid/build.gradle" }}
+
+  - &restore-cache-apt
+    keys:
+      - v1-apt-{{ arch }}-{{ .Branch }}-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
+      # Fallback in case checksum fails
+      - v1-apt-{{ arch }}-{{ .Branch }}-
+      # Fallback in case this is a first-time run on a fork
+      - v1-apt-{{ arch }}-master-
+  - &save-cache-apt
+    paths:
+      - ~/vendor/apt
+    key: v1-apt-{{ arch }}-{{ .Branch }}-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
+
   - &restore-cache-ndk
     keys:
       - v2-android-ndk-{{ arch }}-r10e-32-64-{{ checksum "scripts/circle-ci-android-setup.sh" }}
@@ -97,7 +122,8 @@ aliases:
       yarn install --non-interactive --cache-folder ~/.cache/yarn
 
   - &install-yarn
-    |
+    name: Install Yarn
+    command: |
       curl -sS https://dl.yarnpkg.com/debian/pubkey.gpg | sudo apt-key add -
       echo "deb https://dl.yarnpkg.com/debian/ stable main" | sudo tee /etc/apt/sources.list.d/yarn.list
       sudo apt-get update && sudo apt-get install yarn
@@ -107,7 +133,8 @@ aliases:
       npm install --no-package-lock --no-spin --no-progress
 
   - &install-buck
-    |
+    name: Install BUCK
+    command: |
       if [[ ! -e ~/buck ]]; then
         git clone https://github.com/facebook/buck.git ~/buck --branch v2018.02.16.01 --depth=1
       fi
@@ -115,7 +142,8 @@ aliases:
       buck --version
 
   - &install-node
-    |
+    name: Install Node
+    command: |
       curl -sL https://deb.nodesource.com/setup_8.x | sudo -E bash -
       sudo apt-get install -y nodejs
 
@@ -141,9 +169,7 @@ aliases:
 
   - &install-android-build-dependencies
     name: Install Android Build Dependencies
-    command: |
-      sudo apt-get update -y
-      sudo apt-get install ant autoconf automake g++ gcc libqt5widgets5 lib32z1 lib32stdc++6  make maven python-dev python3-dev qml-module-qtquick-controls qtdeclarative5-dev file -y
+    command: ./scripts/circleci/apt-get-android-deps.sh
 
   - &validate-android-sdk
     name: Validate Android SDK Install
@@ -400,6 +426,7 @@ jobs:
       # Configure Android SDK and related dependencies
       - run: *configure-android-path
       - run: *install-android-build-dependencies
+
       - restore-cache: *restore-cache-android-packages
       - run: *install-android-packages
       - save-cache: *save-cache-android-packages
@@ -450,7 +477,10 @@ jobs:
 
       # Configure Android SDK and related dependencies
       - run: *configure-android-path
+      - restore-cache: *restore-cache-apt
       - run: *install-android-build-dependencies
+      - save-cache: *save-cache-apt
+
       - restore-cache: *restore-cache-android-packages
       - run: *install-android-packages
       - save-cache: *save-cache-android-packages
@@ -481,7 +511,11 @@ jobs:
       - run: buck fetch ReactAndroid/src/main/java/com/facebook/react/shell
       - run: buck fetch ReactAndroid/src/test/...
       - run: buck fetch ReactAndroid/src/androidTest/...
+
+      # Gradle
+      - restore-cache: *restore-cache-gradle
       - run: ./gradlew :ReactAndroid:downloadBoost :ReactAndroid:downloadDoubleConversion :ReactAndroid:downloadFolly :ReactAndroid:downloadGlog :ReactAndroid:downloadJSCHeaders
+      - save-cache: *save-cache-gradle
 
       # Build and compile
       - run: *build-android-app
diff --git a/scripts/circleci/apt-get-android-deps.sh b/scripts/circleci/apt-get-android-deps.sh
new file mode 100755
index 000000000000..6463de83d046
--- /dev/null
+++ b/scripts/circleci/apt-get-android-deps.sh
@@ -0,0 +1,25 @@
+#!/bin/bash
+
+set -e
+
+echo "Downloading package lists..."
+sudo apt-get update -y
+
+if ! [[ -d ~/vendor/apt ]]; then
+  mkdir -p ~/vendor/apt
+fi
+
+# First check for archives cache
+if ! [[ -d ~/vendor/apt/archives ]]; then
+  # It doesn't so download the packages
+  echo "Downloading build dependencies..."
+  sudo apt-get install --download-only ant autoconf automake g++ gcc libqt5widgets5 lib32z1 lib32stdc++6 make maven python-dev python3-dev qml-module-qtquick-controls qtdeclarative5-dev file -y
+  # Then move them to our cache directory
+  sudo cp -R /var/cache/apt ~/vendor/
+  # Making sure our user has ownership, in order to cache
+  sudo chown -R ${USER:=$(/usr/bin/id -run)}:$USER ~/vendor/apt
+fi
+
+# Install all packages in the cache
+echo "Installing build dependencies..."
+sudo dpkg -i ~/vendor/apt/archives/*.deb
\ No newline at end of file

From f5207ba9c764f33ef83fa897f6014d67193be0e2 Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Tue, 27 Mar 2018 10:34:09 -0700
Subject: [PATCH 0147/1109] Fix blob response parsing for empty body on iOS

Summary:
We currently handle empty body poorly in the iOS blob implementation, this happens because of an early return that cause the blob response to not be processed by the blob module, resulting in an empty string as the body instead of a blob object. We also need to make sure to create an empty blob object when data is nil (empty body) as per the XMLHttpRequest spec. The Android implementation was already handling this properly.

Fixes #18223

Send a HEAD request

```js
fetch('https://apipre.monkimun.com/whoami', {
  body: null,
  method: 'HEAD',
  headers: {
    Accept: 'application/json',
    'Content-Type': 'application/json',
  },
})
```

[IOS][BUGFIX][Blob] - Fix blob response parsing for empty body
Closes https://github.com/facebook/react-native/pull/18547

Differential Revision: D7415950

Pulled By: hramos

fbshipit-source-id: 56860532c6171255869f02a0960f55d155184a46
---
 Libraries/Blob/RCTBlobManager.mm   | 3 +++
 Libraries/Network/RCTNetworking.mm | 8 ++++----
 2 files changed, 7 insertions(+), 4 deletions(-)

diff --git a/Libraries/Blob/RCTBlobManager.mm b/Libraries/Blob/RCTBlobManager.mm
index 56235ee04b6d..7c0cbb8673f0 100755
--- a/Libraries/Blob/RCTBlobManager.mm
+++ b/Libraries/Blob/RCTBlobManager.mm
@@ -258,6 +258,9 @@ - (BOOL)canHandleNetworkingResponse:(NSString *)responseType
 
 - (id)handleNetworkingResponse:(NSURLResponse *)response data:(NSData *)data
 {
+  // An empty body will have nil for data, in this case we need to return
+  // an empty blob as per the XMLHttpRequest spec.
+  data = data ?: [NSData new];
   return @{
     @"blobId": [self store:data],
     @"offset": @0,
diff --git a/Libraries/Network/RCTNetworking.mm b/Libraries/Network/RCTNetworking.mm
index fe86d31e67e0..f8de23abf012 100644
--- a/Libraries/Network/RCTNetworking.mm
+++ b/Libraries/Network/RCTNetworking.mm
@@ -439,10 +439,6 @@ - (void)sendData:(NSData *)data
 {
   RCTAssertThread(_methodQueue, @"sendData: must be called on method queue");
 
-  if (data.length == 0) {
-    return;
-  }
-
   id responseData = nil;
   for (id<RCTNetworkingResponseHandler> handler in _responseHandlers) {
     if ([handler canHandleNetworkingResponse:responseType]) {
@@ -452,6 +448,10 @@ - (void)sendData:(NSData *)data
   }
 
   if (!responseData) {
+    if (data.length == 0) {
+      return;
+    }
+
     if ([responseType isEqualToString:@"text"]) {
       // No carry storage is required here because the entire data has been loaded.
       responseData = [RCTNetworking decodeTextData:data fromResponse:task.response withCarryData:nil];

From 0150a0c85b06c4159729bac5aedd1696b4776e99 Mon Sep 17 00:00:00 2001
From: Riley Dulin <dulinr@fb.com>
Date: Tue, 27 Mar 2018 10:43:27 -0700
Subject: [PATCH 0148/1109] Add nativeLoggingHook to JSIExecutor

Reviewed By: danzimm

Differential Revision: D7203114

fbshipit-source-id: 2f4640d19267dc4d75f6d6c8a7876c92abc22276
---
 ReactAndroid/src/main/jni/react/jni/BUCK      |  1 +
 .../src/main/jni/react/jni/JSLogging.cpp      | 24 +++++++++++++++----
 .../src/main/jni/react/jni/JSLogging.h        | 16 +++++++++++--
 3 files changed, 34 insertions(+), 7 deletions(-)

diff --git a/ReactAndroid/src/main/jni/react/jni/BUCK b/ReactAndroid/src/main/jni/react/jni/BUCK
index 7673ad3bdfd3..dc0f2a76d55c 100644
--- a/ReactAndroid/src/main/jni/react/jni/BUCK
+++ b/ReactAndroid/src/main/jni/react/jni/BUCK
@@ -8,6 +8,7 @@ EXPORTED_HEADERS = [
     "JavaModuleWrapper.h",
     "JavaScriptExecutorHolder.h",
     "JSLoader.h",
+    "JSLogging.h",
     "MethodInvoker.h",
     "ModuleRegistryBuilder.h",
     "NativeArray.h",
diff --git a/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp b/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
index 5fdc9a8b273d..e178542157e0 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
@@ -2,9 +2,8 @@
 
 #include "JSLogging.h"
 
-#include <android/log.h>
-#include <algorithm>
 #include <fb/log.h>
+#include <algorithm>
 
 #include <jschelpers/Value.h>
 
@@ -16,7 +15,8 @@ JSValueRef nativeLoggingHook(
     JSObjectRef function,
     JSObjectRef thisObject,
     size_t argumentCount,
-    const JSValueRef arguments[], JSValueRef *exception) {
+    const JSValueRef arguments[],
+    JSValueRef* exception) {
   android_LogPriority logLevel = ANDROID_LOG_DEBUG;
   if (argumentCount > 1) {
     int level = (int)Value(ctx, arguments[1]).asNumber();
@@ -28,9 +28,23 @@ JSValueRef nativeLoggingHook(
   }
   if (argumentCount > 0) {
     String message = Value(ctx, arguments[0]).toString();
-    FBLOG_PRI(logLevel, "ReactNativeJS", "%s", message.str().c_str());
+    reactAndroidLoggingHook(message.str(), logLevel);
   }
   return Value::makeUndefined(ctx);
 }
 
-}};
+void reactAndroidLoggingHook(
+    const std::string& message,
+    android_LogPriority logLevel) {
+  FBLOG_PRI(logLevel, "ReactNativeJS", "%s", message.c_str());
+}
+
+void reactAndroidLoggingHook(
+    const std::string& message,
+    unsigned int logLevel) {
+  reactAndroidLoggingHook(
+      message, static_cast<android_LogPriority>(logLevel + ANDROID_LOG_DEBUG));
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactAndroid/src/main/jni/react/jni/JSLogging.h b/ReactAndroid/src/main/jni/react/jni/JSLogging.h
index 2a38aaf3137c..5e4e99143a29 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSLogging.h
+++ b/ReactAndroid/src/main/jni/react/jni/JSLogging.h
@@ -2,6 +2,9 @@
 
 #pragma once
 
+#include <android/log.h>
+#include <string>
+
 #include <JavaScriptCore/JSContextRef.h>
 
 namespace facebook {
@@ -12,6 +15,15 @@ JSValueRef nativeLoggingHook(
     JSObjectRef function,
     JSObjectRef thisObject,
     size_t argumentCount,
-    const JSValueRef arguments[], JSValueRef *exception);
+    const JSValueRef arguments[],
+    JSValueRef* exception);
+
+void reactAndroidLoggingHook(
+    const std::string& message,
+    android_LogPriority logLevel);
+void reactAndroidLoggingHook(
+    const std::string& message,
+    unsigned int logLevel);
 
-}}
+} // namespace react
+} // namespace facebook

From 45abbf36d67fb50ddf5f74f8d7912a35bf7c1dad Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 27 Mar 2018 10:44:15 -0700
Subject: [PATCH 0149/1109] Support multiple Fabric ReactRootView running at
 the same time

Reviewed By: achen1

Differential Revision: D7409472

fbshipit-source-id: 9525e610f3bce49cae8d3c5e4427f99a48c32091
---
 .../react/fabric/FabricUIManager.java         | 23 +++++++++----------
 1 file changed, 11 insertions(+), 12 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 81a604350978..47359b44fa76 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -50,7 +50,6 @@ public class FabricUIManager implements UIManager {
   private final ViewManagerRegistry mViewManagerRegistry;
   private final UIViewOperationQueue mUIViewOperationQueue;
   private volatile int mCurrentBatch = 0;
-  private ReactShadowNode mCurrentRootShadowNode;
   private FabricReconciler mFabricReconciler;
 
   public FabricUIManager(
@@ -246,32 +245,32 @@ public synchronized void completeRoot(int rootTag, List<ReactShadowNode> childLi
       Log.d(TAG, "completeRoot rootTag: " + rootTag + ", childList: " + childList);
     }
     try {
-      ReactShadowNode rootNode = getRootNode(rootTag);
+      ReactShadowNode currentRootShadowNode = getRootNode(rootTag);
       Assertions.assertNotNull(
-          rootNode,
+          currentRootShadowNode,
           "Root view with tag " + rootTag + " must be added before completeRoot is called");
 
 
-      rootNode = calculateDiffingAndCreateNewRootNode(rootNode, childList);
+      currentRootShadowNode = calculateDiffingAndCreateNewRootNode(currentRootShadowNode, childList);
 
       if (DEBUG) {
-        Log.d(TAG, "ReactShadowNodeHierarchy after diffing: " + rootNode.getHierarchyInfo());
+        Log.d(TAG, "ReactShadowNodeHierarchy after diffing: " + currentRootShadowNode.getHierarchyInfo());
       }
 
-      notifyOnBeforeLayoutRecursive(rootNode);
-      rootNode.calculateLayout();
+      notifyOnBeforeLayoutRecursive(currentRootShadowNode);
+      currentRootShadowNode.calculateLayout();
 
       if (DEBUG) {
         Log.d(
           TAG,
-          "ReactShadowNodeHierarchy after calculate Layout: " + rootNode.getHierarchyInfo());
+          "ReactShadowNodeHierarchy after calculate Layout: " + currentRootShadowNode.getHierarchyInfo());
       }
 
-      applyUpdatesRecursive(rootNode, 0, 0);
+      applyUpdatesRecursive(currentRootShadowNode, 0, 0);
       mUIViewOperationQueue.dispatchViewUpdates(
         mCurrentBatch++, System.currentTimeMillis(), System.currentTimeMillis());
 
-      mCurrentRootShadowNode = rootNode;
+      mRootShadowNodeRegistry.addNode(currentRootShadowNode);
     } catch (Exception e) {
       handleException(getRootNode(rootTag), e);
     }
@@ -294,7 +293,7 @@ private ReactShadowNode calculateDiffingAndCreateNewRootNode(
       appendChild(newRootShadowNode, child);
     }
 
-    mFabricReconciler.manageChildren(mCurrentRootShadowNode, newRootShadowNode);
+    mFabricReconciler.manageChildren(currentRootShadowNode, newRootShadowNode);
     return newRootShadowNode;
   }
 
@@ -321,7 +320,7 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
   }
 
   @Override
-  public <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(
+  public synchronized <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(
       final T rootView) {
     int rootTag = ReactRootViewTagGenerator.getNextRootViewTag();
     ThemedReactContext themedRootContext =

From 56971bbb152babb0ee745d7abd55f5a5d35ae004 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Tue, 27 Mar 2018 11:49:02 -0700
Subject: [PATCH 0150/1109] RN: Fix rounded Image Background (Android)

Reviewed By: achen1

Differential Revision: D7384113

fbshipit-source-id: 348bdbc54a3e5923e012cb4cbc32da83145f04b4
---
 .../react/views/image/ReactImageView.java     | 134 ++++++++++--------
 1 file changed, 77 insertions(+), 57 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index 9396cac1c5c1..9ab9c8884e80 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -29,6 +29,8 @@
 import com.facebook.drawee.controller.ControllerListener;
 import com.facebook.drawee.controller.ForwardingControllerListener;
 import com.facebook.drawee.drawable.AutoRotateDrawable;
+import com.facebook.drawee.drawable.RoundedColorDrawable;
+
 import com.facebook.drawee.drawable.ScalingUtils;
 import com.facebook.drawee.generic.GenericDraweeHierarchy;
 import com.facebook.drawee.generic.GenericDraweeHierarchyBuilder;
@@ -91,25 +93,25 @@ private class RoundedCornerPostprocessor extends BasePostprocessor {
 
     void getRadii(Bitmap source, float[] computedCornerRadii, float[] mappedRadii) {
       mScaleType.getTransform(
-            sMatrix,
-            new Rect(0, 0, source.getWidth(), source.getHeight()),
-            source.getWidth(),
-            source.getHeight(),
-            0.0f,
-            0.0f);
-        sMatrix.invert(sInverse);
+        sMatrix,
+        new Rect(0, 0, source.getWidth(), source.getHeight()),
+        source.getWidth(),
+        source.getHeight(),
+        0.0f,
+        0.0f);
+      sMatrix.invert(sInverse);
 
-        mappedRadii[0] = sInverse.mapRadius(computedCornerRadii[0]);
-        mappedRadii[1] = mappedRadii[0];
+      mappedRadii[0] = sInverse.mapRadius(computedCornerRadii[0]);
+      mappedRadii[1] = mappedRadii[0];
 
-        mappedRadii[2] = sInverse.mapRadius(computedCornerRadii[1]);
-        mappedRadii[3] = mappedRadii[2];
+      mappedRadii[2] = sInverse.mapRadius(computedCornerRadii[1]);
+      mappedRadii[3] = mappedRadii[2];
 
-        mappedRadii[4] = sInverse.mapRadius(computedCornerRadii[2]);
-        mappedRadii[5] = mappedRadii[4];
+      mappedRadii[4] = sInverse.mapRadius(computedCornerRadii[2]);
+      mappedRadii[5] = mappedRadii[4];
 
-        mappedRadii[6] = sInverse.mapRadius(computedCornerRadii[3]);
-        mappedRadii[7] = mappedRadii[6];
+      mappedRadii[6] = sInverse.mapRadius(computedCornerRadii[3]);
+      mappedRadii[7] = mappedRadii[6];
     }
 
     @Override
@@ -118,9 +120,9 @@ public void process(Bitmap output, Bitmap source) {
 
       output.setHasAlpha(true);
       if (FloatUtil.floatsEqual(sComputedCornerRadii[0], 0f) &&
-          FloatUtil.floatsEqual(sComputedCornerRadii[1], 0f) &&
-          FloatUtil.floatsEqual(sComputedCornerRadii[2], 0f) &&
-          FloatUtil.floatsEqual(sComputedCornerRadii[3], 0f)) {
+        FloatUtil.floatsEqual(sComputedCornerRadii[1], 0f) &&
+        FloatUtil.floatsEqual(sComputedCornerRadii[2], 0f) &&
+        FloatUtil.floatsEqual(sComputedCornerRadii[3], 0f)) {
         super.process(output, source);
         return;
       }
@@ -136,9 +138,9 @@ public void process(Bitmap output, Bitmap source) {
       Path pathForBorderRadius = new Path();
 
       pathForBorderRadius.addRoundRect(
-          new RectF(0, 0, source.getWidth(), source.getHeight()),
-          radii,
-          Path.Direction.CW);
+        new RectF(0, 0, source.getWidth(), source.getHeight()),
+        radii,
+        Path.Direction.CW);
 
       canvas.drawPath(pathForBorderRadius, paint);
     }
@@ -183,6 +185,8 @@ public CloseableReference<Bitmap> process(Bitmap source, PlatformBitmapFactory b
   private @Nullable ImageSource mImageSource;
   private @Nullable ImageSource mCachedImageSource;
   private @Nullable Drawable mLoadingImageDrawable;
+  private @Nullable RoundedColorDrawable mBackgroundImageDrawable;
+  private int mBackgroundColor = 0x00000000;
   private int mBorderColor;
   private int mOverlayColor;
   private float mBorderWidth;
@@ -206,15 +210,15 @@ public CloseableReference<Bitmap> process(Bitmap source, PlatformBitmapFactory b
   // We can't specify rounding in XML, so have to do so here
   private static GenericDraweeHierarchy buildHierarchy(Context context) {
     return new GenericDraweeHierarchyBuilder(context.getResources())
-        .setRoundingParams(RoundingParams.fromCornersRadius(0))
-        .build();
+      .setRoundingParams(RoundingParams.fromCornersRadius(0))
+      .build();
   }
 
   public ReactImageView(
-      Context context,
-      AbstractDraweeControllerBuilder draweeControllerBuilder,
-      @Nullable GlobalImageLoadListener globalImageLoadListener,
-      @Nullable Object callerContext) {
+    Context context,
+    AbstractDraweeControllerBuilder draweeControllerBuilder,
+    @Nullable GlobalImageLoadListener globalImageLoadListener,
+    @Nullable Object callerContext) {
     super(context, buildHierarchy(context));
     mScaleType = ImageResizeMode.defaultValue();
     mDraweeControllerBuilder = draweeControllerBuilder;
@@ -230,20 +234,20 @@ public void setShouldNotifyLoadEvents(boolean shouldNotify) {
       mControllerListener = null;
     } else {
       final EventDispatcher mEventDispatcher = ((ReactContext) getContext()).
-          getNativeModule(UIManagerModule.class).getEventDispatcher();
+        getNativeModule(UIManagerModule.class).getEventDispatcher();
 
       mControllerListener = new BaseControllerListener<ImageInfo>() {
         @Override
         public void onSubmit(String id, Object callerContext) {
           mEventDispatcher.dispatchEvent(
-              new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_START));
+            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_START));
         }
 
         @Override
         public void onFinalImageSet(
-            String id,
-            @Nullable final ImageInfo imageInfo,
-            @Nullable Animatable animatable) {
+          String id,
+          @Nullable final ImageInfo imageInfo,
+          @Nullable Animatable animatable) {
           if (imageInfo != null) {
             mEventDispatcher.dispatchEvent(
               new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD,
@@ -276,6 +280,15 @@ public void setBlurRadius(float blurRadius) {
     mIsDirty = true;
   }
 
+  @Override
+  public void setBackgroundColor(int backgroundColor) {
+    if(mBackgroundColor != backgroundColor) {
+      mBackgroundColor = backgroundColor;
+      mBackgroundImageDrawable = new RoundedColorDrawable(backgroundColor);
+      mIsDirty = true;
+    }
+  }
+
   public void setBorderColor(int borderColor) {
     mBorderColor = borderColor;
     mIsDirty = true;
@@ -342,10 +355,10 @@ public void setSource(@Nullable ReadableArray sources) {
           ReadableMap source = sources.getMap(idx);
           String uri = source.getString("uri");
           ImageSource imageSource = new ImageSource(
-              getContext(),
-              uri,
-              source.getDouble("width"),
-              source.getDouble("height"));
+            getContext(),
+            uri,
+            source.getDouble("width"),
+            source.getDouble("height"));
           mSources.add(imageSource);
           if (Uri.EMPTY.equals(imageSource.getUri())) {
             warnImageSource(uri);
@@ -359,7 +372,7 @@ public void setSource(@Nullable ReadableArray sources) {
   public void setLoadingIndicatorSource(@Nullable String name) {
     Drawable drawable = ResourceDrawableIdHelper.getInstance().getResourceDrawable(getContext(), name);
     mLoadingImageDrawable =
-        drawable != null ? (Drawable) new AutoRotateDrawable(drawable, 1000) : null;
+      drawable != null ? (Drawable) new AutoRotateDrawable(drawable, 1000) : null;
     mIsDirty = true;
   }
 
@@ -420,31 +433,37 @@ public void maybeUpdateView() {
     }
 
     boolean usePostprocessorScaling =
-        mScaleType != ScalingUtils.ScaleType.CENTER_CROP &&
+      mScaleType != ScalingUtils.ScaleType.CENTER_CROP &&
         mScaleType != ScalingUtils.ScaleType.FOCUS_CROP;
 
     RoundingParams roundingParams = hierarchy.getRoundingParams();
 
+    cornerRadii(sComputedCornerRadii);
+
+    roundingParams.setCornersRadii(sComputedCornerRadii[0], sComputedCornerRadii[1], sComputedCornerRadii[2], sComputedCornerRadii[3]);
+
+    if (mBackgroundImageDrawable != null) {
+      mBackgroundImageDrawable.setBorder(mBorderColor, mBorderWidth);
+      mBackgroundImageDrawable.setRadii(roundingParams.getCornersRadii());
+      hierarchy.setBackgroundImage(mBackgroundImageDrawable);
+    }
+
     if (usePostprocessorScaling) {
       roundingParams.setCornersRadius(0);
-    } else {
-      cornerRadii(sComputedCornerRadii);
-
-      roundingParams.setCornersRadii(sComputedCornerRadii[0], sComputedCornerRadii[1], sComputedCornerRadii[2], sComputedCornerRadii[3]);
     }
 
     roundingParams.setBorder(mBorderColor, mBorderWidth);
     if (mOverlayColor != Color.TRANSPARENT) {
-        roundingParams.setOverlayColor(mOverlayColor);
+      roundingParams.setOverlayColor(mOverlayColor);
     } else {
-        // make sure the default rounding method is used.
-        roundingParams.setRoundingMethod(RoundingParams.RoundingMethod.BITMAP_ONLY);
+      // make sure the default rounding method is used.
+      roundingParams.setRoundingMethod(RoundingParams.RoundingMethod.BITMAP_ONLY);
     }
     hierarchy.setRoundingParams(roundingParams);
     hierarchy.setFadeDuration(
-        mFadeDurationMs >= 0
-            ? mFadeDurationMs
-            : mImageSource.isResource() ? 0 : REMOTE_IMAGE_FADE_DURATION_MS);
+      mFadeDurationMs >= 0
+        ? mFadeDurationMs
+        : mImageSource.isResource() ? 0 : REMOTE_IMAGE_FADE_DURATION_MS);
 
     List<Postprocessor> postprocessors = new LinkedList<>();
     if (usePostprocessorScaling) {
@@ -461,10 +480,10 @@ public void maybeUpdateView() {
     ResizeOptions resizeOptions = doResize ? new ResizeOptions(getWidth(), getHeight()) : null;
 
     ImageRequestBuilder imageRequestBuilder = ImageRequestBuilder.newBuilderWithSource(mImageSource.getUri())
-        .setPostprocessor(postprocessor)
-        .setResizeOptions(resizeOptions)
-        .setAutoRotateEnabled(true)
-        .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled);
+      .setPostprocessor(postprocessor)
+      .setResizeOptions(resizeOptions)
+      .setAutoRotateEnabled(true)
+      .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled);
 
     ImageRequest imageRequest = ReactNetworkImageRequest.fromBuilderWithHeaders(imageRequestBuilder, mHeaders);
 
@@ -476,10 +495,10 @@ public void maybeUpdateView() {
     mDraweeControllerBuilder.reset();
 
     mDraweeControllerBuilder
-        .setAutoPlayAnimations(true)
-        .setCallerContext(mCallerContext)
-        .setOldController(getController())
-        .setImageRequest(imageRequest);
+      .setAutoPlayAnimations(true)
+      .setCallerContext(mCallerContext)
+      .setOldController(getController())
+      .setImageRequest(imageRequest);
 
     if (mCachedImageSource != null) {
       ImageRequest cachedImageRequest =
@@ -566,7 +585,7 @@ private boolean shouldResize(ImageSource imageSource) {
     if (mResizeMethod == ImageResizeMethod.AUTO) {
       return
         UriUtil.isLocalContentUri(imageSource.getUri()) ||
-        UriUtil.isLocalFileUri(imageSource.getUri());
+          UriUtil.isLocalFileUri(imageSource.getUri());
     } else if (mResizeMethod == ImageResizeMethod.RESIZE) {
       return true;
     } else {
@@ -583,3 +602,4 @@ private void warnImageSource(String uri) {
     }
   }
 }
+

From 2ebd55f879c3d1d0aa608b84f36158c5bafac6ec Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Tue, 27 Mar 2018 12:27:32 -0700
Subject: [PATCH 0151/1109] Upgrade Jest to 23.0.0-alpha.4

Reviewed By: cpojer

Differential Revision: D7397960

fbshipit-source-id: 40984ff1ebfccdcba58f898abf8c52e2ed337221
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index eb2c29584298..c9793054ddc5 100644
--- a/package.json
+++ b/package.json
@@ -216,7 +216,7 @@
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
     "flow-bin": "^0.68.0",
-    "jest": "22.4.2",
+    "jest": "23.0.0-alpha.4",
     "jest-junit": "3.6.0",
     "prettier": "1.9.1",
     "react": "^16.3.0-alpha.2",

From 15b25d854a01642530c1e5f7a2016f6dba41a714 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Tue, 27 Mar 2018 14:31:42 -0700
Subject: [PATCH 0152/1109] Cache C++ downloads

Summary: Closes https://github.com/facebook/react-native/pull/18595

Differential Revision: D7419532

Pulled By: hramos

fbshipit-source-id: 0b64763f91efea8300c4cde4703e8496dbda8c49
---
 .circleci/config.yml                     | 71 +++++++++++++-----------
 scripts/circleci/gradle_download_deps.sh |  5 ++
 2 files changed, 44 insertions(+), 32 deletions(-)
 create mode 100755 scripts/circleci/gradle_download_deps.sh

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 196d3d3e6edf..bb9570bf3227 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -1,42 +1,33 @@
 aliases:
   # Cache Management
-  - &restore-yarn-cache
+  - &restore-cache-yarn
     keys:
-      - v1-yarn-{{ arch }}-{{ .Branch }}-{{ checksum "package.json" }}
-      # Fallback in case checksum fails
-      - v1-yarn-{{ arch }}-{{ .Branch }}-
-      # Fallback in case this is a first-time run on a fork
-      - v1-yarn-{{ arch }}-master-
-  - &save-yarn-cache
+      - v1-yarn-{{ arch }}-{{ checksum "package.json" }}
+      - v1-yarn-{{ arch }}-
+  - &save-cache-yarn
     paths:
       - node_modules
       - ~/.cache/yarn
-    key: v1-yarn-{{ arch }}-{{ .Branch }}-{{ checksum "package.json" }}
+    key: v1-yarn-{{ arch }}-{{ checksum "package.json" }}
 
   - &restore-cache-analysis
     keys:
-      - v1-analysis-dependencies-{{ arch }}-{{ .Branch }}-{{ checksum "package.json" }}{{ checksum "bots/package.json" }}
-      # Fallback in case checksum fails
-      - v1-analysis-dependencies-{{ arch }}-{{ .Branch }}-
-      # Fallback in case this is a first-time run on a fork
-      - v1-analysis-dependencies-{{ arch }}-master-
+      - v1-analysis-dependencies-{{ arch }}-{{ checksum "package.json" }}{{ checksum "bots/package.json" }}
+      - v1-analysis-dependencies-{{ arch }}-
   - &save-cache-analysis
     paths:
       - bots/node_modules
       - node_modules
-    key: v1-analysis-dependencies-{{ arch }}-{{ .Branch }}-{{ checksum "package.json" }}{{ checksum "bots/package.json" }}
+    key: v1-analysis-dependencies-{{ arch }}-{{ checksum "package.json" }}{{ checksum "bots/package.json" }}
 
   - &restore-cache-android-packages
     keys:
-      - v1-android-sdkmanager-packages-{{ arch }}-{{ .Branch }}-api-26-alpha-{{ checksum "scripts/circle-ci-android-setup.sh" }}
-      # Fallback in case checksum fails
-      - v1-android-sdkmanager-packages-{{ arch }}-{{ .Branch }}-api-26-alpha-
-      # Fallback in case this is a first-time run on a fork
-      - v1-android-sdkmanager-packages-{{ arch }}-master-api-26-alpha-
+      - v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-{{ checksum "scripts/circle-ci-android-setup.sh" }}
+      - v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-
   - &save-cache-android-packages
     paths:
       - /opt/android/sdk
-    key: v1-android-sdkmanager-packages-{{ arch }}-{{ .Branch }}-api-26-alpha-{{ checksum "scripts/circle-ci-android-setup.sh" }}
+    key: v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-{{ checksum "scripts/circle-ci-android-setup.sh" }}
 
   - &restore-cache-gradle
     keys:
@@ -66,7 +57,6 @@ aliases:
   - &restore-cache-ndk
     keys:
       - v2-android-ndk-{{ arch }}-r10e-32-64-{{ checksum "scripts/circle-ci-android-setup.sh" }}
-      # Fallback in case checksum fails
       - v2-android-ndk-{{ arch }}-r10e-32-64-
   - &save-cache-ndk
     paths:
@@ -89,6 +79,17 @@ aliases:
       - ~/watchman
     key: v1-watchman-{{ arch }}-v4.9.0
 
+  - &restore-cache-gradle-downloads
+    keys:
+      - v1-gradle-{{ arch }}-{{ checksum "ReactAndroid/build.gradle" }}-{{ checksum "scripts/circleci/gradle_download_deps.sh" }}
+      - v1-gradle-{{ arch }}-
+  - &save-cache-gradle-downloads
+    paths:
+      - ~/.gradle
+      - ReactAndroid/build/downloads
+      - ReactAndroid/build/third-party-ndk
+    key: v1-gradle-{{ arch }}-{{ checksum "ReactAndroid/build.gradle" }}-{{ checksum "scripts/circleci/gradle_download_deps.sh" }}
+
   # Branch Filtering
   - &filter-only-master-stable
     branches:
@@ -201,6 +202,10 @@ aliases:
       ./scripts/circleci/check_license.sh
       ./scripts/circleci/check_cache.sh
     when: always
+
+  - &gradle-download-deps
+    name: Download C++ Dependencies
+    command: ./scripts/circleci/gradle_download_deps.sh
     
   - &build-android-app
     name: Build Android App
@@ -309,9 +314,9 @@ jobs:
       - checkout
       - run: *setup-artifacts
 
-      - restore-cache: *restore-yarn-cache
+      - restore-cache: *restore-cache-yarn
       - run: *yarn
-      - save-cache: *save-yarn-cache
+      - save-cache: *save-cache-yarn
 
       # Basic checks against the checkout, cache...
       - run: *run-sanity-checks
@@ -357,9 +362,9 @@ jobs:
       - checkout
       - run: *setup-artifacts
 
-      - restore-cache: *restore-yarn-cache
+      - restore-cache: *restore-cache-yarn
       - run: *yarn
-      - save-cache: *save-yarn-cache
+      - save-cache: *save-cache-yarn
 
       - run: *run-js-tests
 
@@ -447,13 +452,16 @@ jobs:
       - run: buck fetch ReactAndroid/src/main/java/com/facebook/react/shell
       - run: buck fetch ReactAndroid/src/test/...
       - run: buck fetch ReactAndroid/src/androidTest/...
-      - run: ./gradlew :ReactAndroid:downloadBoost :ReactAndroid:downloadDoubleConversion :ReactAndroid:downloadFolly :ReactAndroid:downloadGlog :ReactAndroid:downloadJSCHeaders
+
+      - restore-cache: *restore-cache-gradle-downloads
+      - run: *gradle-download-deps
+      - save-cache: *save-cache-gradle-downloads
 
       - run: *install-node
       - run: *install-yarn
-      - restore-cache: *restore-yarn-cache
+      - restore-cache: *restore-cache-yarn
       - run: *yarn
-      - save-cache: *save-yarn-cache
+      - save-cache: *save-cache-yarn
       
       - run:
           name: Publish React Native Package
@@ -512,10 +520,9 @@ jobs:
       - run: buck fetch ReactAndroid/src/test/...
       - run: buck fetch ReactAndroid/src/androidTest/...
 
-      # Gradle
-      - restore-cache: *restore-cache-gradle
-      - run: ./gradlew :ReactAndroid:downloadBoost :ReactAndroid:downloadDoubleConversion :ReactAndroid:downloadFolly :ReactAndroid:downloadGlog :ReactAndroid:downloadJSCHeaders
-      - save-cache: *save-cache-gradle
+      - restore-cache: *restore-cache-gradle-downloads
+      - run: *gradle-download-deps
+      - save-cache: *save-cache-gradle-downloads
 
       # Build and compile
       - run: *build-android-app
diff --git a/scripts/circleci/gradle_download_deps.sh b/scripts/circleci/gradle_download_deps.sh
new file mode 100755
index 000000000000..1e093de55a0b
--- /dev/null
+++ b/scripts/circleci/gradle_download_deps.sh
@@ -0,0 +1,5 @@
+#!/bin/bash
+
+set -e
+
+./gradlew :ReactAndroid:downloadBoost :ReactAndroid:downloadDoubleConversion :ReactAndroid:downloadFolly :ReactAndroid:downloadGlog :ReactAndroid:downloadJSCHeaders
\ No newline at end of file

From e3941a18b184fe3b31051da1eccc21de14a5fc02 Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Tue, 27 Mar 2018 15:04:07 -0700
Subject: [PATCH 0153/1109] Native Animated - Support border radius

Summary:
Border radius already works properly with native animated but was not in the whitelisted props.

Tested in an app that animating border radius with native animated actually works.

[GENERAL] [ENHANCEMENT] [NativeAnimated] - Support border radius
Closes https://github.com/facebook/react-native/pull/18574

Differential Revision: D7415956

Pulled By: hramos

fbshipit-source-id: 6dd46bcdcb10c6a1956dd1f526212f33a4f44425
---
 Libraries/Animated/src/NativeAnimatedHelper.js | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/Libraries/Animated/src/NativeAnimatedHelper.js b/Libraries/Animated/src/NativeAnimatedHelper.js
index 5765dcfc63b8..68bf4563fa95 100644
--- a/Libraries/Animated/src/NativeAnimatedHelper.js
+++ b/Libraries/Animated/src/NativeAnimatedHelper.js
@@ -145,6 +145,15 @@ const API = {
 const STYLES_WHITELIST = {
   opacity: true,
   transform: true,
+  borderRadius: true,
+  borderBottomEndRadius: true,
+  borderBottomLeftRadius: true,
+  borderBottomRightRadius: true,
+  borderBottomStartRadius: true,
+  borderTopEndRadius: true,
+  borderTopLeftRadius: true,
+  borderTopRightRadius: true,
+  borderTopStartRadius: true,
   /* ios styles */
   shadowOpacity: true,
   shadowRadius: true,

From 979c01ed2d3ebfc338fafac1014d1ed5c8f1882b Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 27 Mar 2018 15:12:11 -0700
Subject: [PATCH 0154/1109] Build yoga in OSS

Differential Revision: D7417644

fbshipit-source-id: 2641c1abc1083db83cbb304f8dcc7b781e329041
---
 ReactCommon/yoga/BUCK | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/yoga/BUCK b/ReactCommon/yoga/BUCK
index aa6308d384f6..43ac54923360 100644
--- a/ReactCommon/yoga/BUCK
+++ b/ReactCommon/yoga/BUCK
@@ -1,6 +1,6 @@
-load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library")
+load("//ReactNative:DEFS.bzl", "cxx_library")
 
-rn_xplat_cxx_library(
+cxx_library(
     name = "yoga",
     srcs = glob(["yoga/*.cpp"]),
     header_namespace = "",

From f96d7ae6486eb245496c0fef07239ae0480e88b6 Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Tue, 27 Mar 2018 17:56:05 -0700
Subject: [PATCH 0155/1109] Bridged FBPullToRefresh to JS

Reviewed By: shergin

Differential Revision: D6875099

fbshipit-source-id: 00bbad7569ff047a77f198ad2bf4d77fccbaa2e9
---
 React/Views/ScrollView/RCTScrollView.m | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/React/Views/ScrollView/RCTScrollView.m b/React/Views/ScrollView/RCTScrollView.m
index f146ba0d2369..f2d4da1ecff5 100644
--- a/React/Views/ScrollView/RCTScrollView.m
+++ b/React/Views/ScrollView/RCTScrollView.m
@@ -443,6 +443,11 @@ - (void)insertReactSubview:(UIView *)view atIndex:(NSInteger)atIndex
 #if !TARGET_OS_TV
   if ([view isKindOfClass:[RCTRefreshControl class]]) {
     [_scrollView setRctRefreshControl:(RCTRefreshControl *)view];
+  }
+  else if ([view conformsToProtocol:@protocol(UIScrollViewDelegate)]) {
+    [self addScrollListener:(UIView<UIScrollViewDelegate> *)view];
+    [_scrollView addSubview:view];
+    [_scrollView sendSubviewToBack:view];
   } else
 #endif
   {
@@ -459,6 +464,9 @@ - (void)removeReactSubview:(UIView *)subview
 #if !TARGET_OS_TV
   if ([subview isKindOfClass:[RCTRefreshControl class]]) {
     [_scrollView setRctRefreshControl:nil];
+  } else if ([subview conformsToProtocol:@protocol(UIScrollViewDelegate)]) {
+    [self removeScrollListener:(UIView<UIScrollViewDelegate> *)subview];
+    [subview removeFromSuperview];
   } else
 #endif
   {

From fd4bc72512d548700759212b0d65926c98e7ba49 Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Tue, 27 Mar 2018 17:56:06 -0700
Subject: [PATCH 0156/1109] Add custom RefreshControl support to
 VirtualizedList

Reviewed By: TheSavior, mmmulani

Differential Revision: D7388137

fbshipit-source-id: 8a1448e5fc526b45773fe4a4f123a179d4a8bee9
---
 Libraries/Lists/VirtualizedList.js | 33 +++++++++++++++++++-----------
 1 file changed, 21 insertions(+), 12 deletions(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 928050f7682f..e03750e106ab 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -173,6 +173,12 @@ type OptionalProps = {
    * @platform android
    */
   progressViewOffset?: number,
+  /**
+   * A custom refresh control element. When set, it overrides the default
+   * <RefreshControl> component built internally. The onRefresh and refreshing
+   * props are also ignored. Only works for vertical VirtualizedList.
+   */
+  refreshControl?: ?React.Element<any>,
   /**
    * Set this true while waiting for new data from a refresh.
    */
@@ -893,9 +899,10 @@ class VirtualizedList extends React.PureComponent<Props, State> {
       onScrollEndDrag: this._onScrollEndDrag,
       onMomentumScrollEnd: this._onMomentumScrollEnd,
       scrollEventThrottle: this.props.scrollEventThrottle, // TODO: Android support
-      invertStickyHeaders: this.props.invertStickyHeaders !== undefined
-        ? this.props.invertStickyHeaders
-        : this.props.inverted,	
+      invertStickyHeaders:
+        this.props.invertStickyHeaders !== undefined
+          ? this.props.invertStickyHeaders
+          : this.props.inverted,
       stickyHeaderIndices,
     };
     if (inversionStyle) {
@@ -990,9 +997,10 @@ class VirtualizedList extends React.PureComponent<Props, State> {
   }
 
   _defaultRenderScrollComponent = props => {
+    const onRefresh = props.onRefresh;
     if (this._isNestedWithSameOrientation()) {
       return <View {...props} />;
-    } else if (props.onRefresh) {
+    } else if (onRefresh) {
       invariant(
         typeof props.refreshing === 'boolean',
         '`refreshing` prop must be set as a boolean in order to use `onRefresh`, but got `' +
@@ -1003,14 +1011,15 @@ class VirtualizedList extends React.PureComponent<Props, State> {
         <ScrollView
           {...props}
           refreshControl={
-            /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-             * comment suppresses an error when upgrading Flow's support for
-             * React. To see the error delete this comment and run Flow. */
-            <RefreshControl
-              refreshing={props.refreshing}
-              onRefresh={props.onRefresh}
-              progressViewOffset={props.progressViewOffset}
-            />
+            props.refreshControl == null ? (
+              <RefreshControl
+                refreshing={props.refreshing}
+                onRefresh={onRefresh}
+                progressViewOffset={props.progressViewOffset}
+              />
+            ) : (
+              props.refreshControl
+            )
           }
         />
       );

From 9c805062e780b323a08747568a1efda367cbec13 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 27 Mar 2018 18:27:13 -0700
Subject: [PATCH 0157/1109] Refactor RootShadowNodeRegistry to make it
 ThreadSafe

Reviewed By: achen1

Differential Revision: D7417965

fbshipit-source-id: 90fa007242d2f00a315a4db25d2b6a0949e4b0d3
---
 .../react/fabric/FabricUIManager.java         |  6 ++---
 .../react/fabric/RootShadowNodeRegistry.java  | 26 +++++++++++++------
 2 files changed, 21 insertions(+), 11 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 47359b44fa76..6959c275ff59 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -270,7 +270,7 @@ public synchronized void completeRoot(int rootTag, List<ReactShadowNode> childLi
       mUIViewOperationQueue.dispatchViewUpdates(
         mCurrentBatch++, System.currentTimeMillis(), System.currentTimeMillis());
 
-      mRootShadowNodeRegistry.addNode(currentRootShadowNode);
+      mRootShadowNodeRegistry.replaceNode(currentRootShadowNode);
     } catch (Exception e) {
       handleException(getRootNode(rootTag), e);
     }
@@ -320,7 +320,7 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
   }
 
   @Override
-  public synchronized <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(
+  public <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(
       final T rootView) {
     int rootTag = ReactRootViewTagGenerator.getNextRootViewTag();
     ThemedReactContext themedRootContext =
@@ -332,7 +332,7 @@ public synchronized <T extends SizeMonitoringFrameLayout & MeasureSpecProvider>
     int heightMeasureSpec = rootView.getHeightMeasureSpec();
     updateRootView(rootShadowNode, widthMeasureSpec, heightMeasureSpec);
 
-    mRootShadowNodeRegistry.addNode(rootShadowNode);
+    mRootShadowNodeRegistry.registerNode(rootShadowNode);
     mUIViewOperationQueue.addRootView(rootTag, rootView, themedRootContext);
     return rootTag;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/RootShadowNodeRegistry.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/RootShadowNodeRegistry.java
index 49884cfc1f24..1d66d4b500e6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/RootShadowNodeRegistry.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/RootShadowNodeRegistry.java
@@ -7,30 +7,40 @@
 
 package com.facebook.react.fabric;
 
-import android.util.SparseArray;
 import com.facebook.react.uimanager.ReactShadowNode;
+import java.util.concurrent.ConcurrentHashMap;
+import javax.annotation.concurrent.ThreadSafe;
 
 /**
  * Simple container class to keep track of {@link ReactShadowNode}s that represents the Root
- * Shadow Nodes of a {@link FabricUIManager}
+ * Shadow Nodes of a {@link FabricUIManager}.
  */
+@ThreadSafe
 public class RootShadowNodeRegistry {
 
-  private final SparseArray<ReactShadowNode> mTagsToRootNodes;
+  private final ConcurrentHashMap<Integer, ReactShadowNode> mTagsToRootNodes = new ConcurrentHashMap<>();
 
-  public RootShadowNodeRegistry() {
-    mTagsToRootNodes = new SparseArray<>();
+  /**
+   * Registers the {@link ReactShadowNode} received as a parameter as a RootShadowNode.
+   */
+  public synchronized void registerNode(ReactShadowNode node) {
+    mTagsToRootNodes.put(node.getReactTag(), node);
   }
 
-  public void addNode(ReactShadowNode node) {
-    mTagsToRootNodes.put(node.getReactTag(), node);
+  /**
+   * Register the {@link ReactShadowNode} received as a parameter as a RootShadowNode, replacing
+   * the previous RootShadowNode associated for the {@link ReactShadowNode#getReactTag()}
+   */
+  public void replaceNode(ReactShadowNode node) {
+    mTagsToRootNodes.replace(node.getReactTag(), node);
   }
 
-  public void removeNode(int tag) {
+  public void removeNode(Integer tag) {
     mTagsToRootNodes.remove(tag);
   }
 
   public ReactShadowNode getNode(int tag) {
     return mTagsToRootNodes.get(tag);
   }
+
 }

From bd134ce6af6f247ab72f5cdc5b36a6b44ad84811 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Wed, 28 Mar 2018 04:38:59 -0700
Subject: [PATCH 0158/1109] Increase timeouts to 15, 10

Reviewed By: javache

Differential Revision: D7415558

fbshipit-source-id: 76912d22b8e330845fcca3fa27aab6ed28256a94
---
 Libraries/WebSocket/RCTWebSocketExecutor.m | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/WebSocket/RCTWebSocketExecutor.m b/Libraries/WebSocket/RCTWebSocketExecutor.m
index 14f53a43c2da..2544772829a2 100644
--- a/Libraries/WebSocket/RCTWebSocketExecutor.m
+++ b/Libraries/WebSocket/RCTWebSocketExecutor.m
@@ -103,7 +103,7 @@ - (BOOL)connectToProxy
 {
   _socketOpenSemaphore = dispatch_semaphore_create(0);
   [_socket open];
-  long connected = dispatch_semaphore_wait(_socketOpenSemaphore, dispatch_time(DISPATCH_TIME_NOW, NSEC_PER_SEC * 10));
+  long connected = dispatch_semaphore_wait(_socketOpenSemaphore, dispatch_time(DISPATCH_TIME_NOW, NSEC_PER_SEC * 15));
   return connected == 0 && _socket.readyState == RCTSR_OPEN;
 }
 
@@ -115,7 +115,7 @@ - (BOOL)prepareJSRuntime
     initError = error;
     dispatch_semaphore_signal(s);
   }];
-  long runtimeIsReady = dispatch_semaphore_wait(s, dispatch_time(DISPATCH_TIME_NOW, NSEC_PER_SEC * 5));
+  long runtimeIsReady = dispatch_semaphore_wait(s, dispatch_time(DISPATCH_TIME_NOW, NSEC_PER_SEC * 10));
   if (initError) {
     RCTLogInfo(@"Websocket runtime setup failed: %@", initError);
   }

From 88ba7ebcc77e5ff0a38954d298b6478960d0702a Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Wed, 28 Mar 2018 10:10:57 -0700
Subject: [PATCH 0159/1109] Fix "function statements" in strict mode builds

Reviewed By: davidaurelio

Differential Revision: D7427473

fbshipit-source-id: 130d0653c100c4a12b2a01aa3489b780febf6d8e
---
 Libraries/polyfills/console.js | 180 ++++++++++++++++-----------------
 1 file changed, 90 insertions(+), 90 deletions(-)

diff --git a/Libraries/polyfills/console.js b/Libraries/polyfills/console.js
index 37a92b1a62fe..794a89c4f49f 100644
--- a/Libraries/polyfills/console.js
+++ b/Libraries/polyfills/console.js
@@ -401,108 +401,108 @@ INSPECTOR_LEVELS[LOG_LEVELS.error] = 'error';
 // strip method printing to originalConsole.
 const INSPECTOR_FRAMES_TO_SKIP = __DEV__ ? 2 : 1;
 
-if (global.nativeLoggingHook) {
-  function getNativeLogFunction(level) {
-    return function() {
-      let str;
-      if (arguments.length === 1 && typeof arguments[0] === 'string') {
-        str = arguments[0];
-      } else {
-        str = Array.prototype.map
-          .call(arguments, function(arg) {
-            return inspect(arg, {depth: 10});
-          })
-          .join(', ');
-      }
-
-      let logLevel = level;
-      if (str.slice(0, 9) === 'Warning: ' && logLevel >= LOG_LEVELS.error) {
-        // React warnings use console.error so that a stack trace is shown,
-        // but we don't (currently) want these to show a redbox
-        // (Note: Logic duplicated in ExceptionsManager.js.)
-        logLevel = LOG_LEVELS.warn;
-      }
-      if (global.__inspectorLog) {
-        global.__inspectorLog(
-          INSPECTOR_LEVELS[logLevel],
-          str,
-          [].slice.call(arguments),
-          INSPECTOR_FRAMES_TO_SKIP,
-        );
-      }
-      global.nativeLoggingHook(str, logLevel);
-    };
-  }
-
-  function repeat(element, n) {
-    return Array.apply(null, Array(n)).map(function() {
-      return element;
-    });
-  }
+function getNativeLogFunction(level) {
+  return function() {
+    let str;
+    if (arguments.length === 1 && typeof arguments[0] === 'string') {
+      str = arguments[0];
+    } else {
+      str = Array.prototype.map
+        .call(arguments, function(arg) {
+          return inspect(arg, {depth: 10});
+        })
+        .join(', ');
+    }
 
-  function consoleTablePolyfill(rows) {
-    // convert object -> array
-    if (!Array.isArray(rows)) {
-      var data = rows;
-      rows = [];
-      for (var key in data) {
-        if (data.hasOwnProperty(key)) {
-          var row = data[key];
-          row[OBJECT_COLUMN_NAME] = key;
-          rows.push(row);
-        }
-      }
+    let logLevel = level;
+    if (str.slice(0, 9) === 'Warning: ' && logLevel >= LOG_LEVELS.error) {
+      // React warnings use console.error so that a stack trace is shown,
+      // but we don't (currently) want these to show a redbox
+      // (Note: Logic duplicated in ExceptionsManager.js.)
+      logLevel = LOG_LEVELS.warn;
     }
-    if (rows.length === 0) {
-      global.nativeLoggingHook('', LOG_LEVELS.info);
-      return;
+    if (global.__inspectorLog) {
+      global.__inspectorLog(
+        INSPECTOR_LEVELS[logLevel],
+        str,
+        [].slice.call(arguments),
+        INSPECTOR_FRAMES_TO_SKIP,
+      );
     }
+    global.nativeLoggingHook(str, logLevel);
+  };
+}
 
-    var columns = Object.keys(rows[0]).sort();
-    var stringRows = [];
-    var columnWidths = [];
-
-    // Convert each cell to a string. Also
-    // figure out max cell width for each column
-    columns.forEach(function(k, i) {
-      columnWidths[i] = k.length;
-      for (var j = 0; j < rows.length; j++) {
-        var cellStr = (rows[j][k] || '?').toString();
-        stringRows[j] = stringRows[j] || [];
-        stringRows[j][i] = cellStr;
-        columnWidths[i] = Math.max(columnWidths[i], cellStr.length);
-      }
-    });
+function repeat(element, n) {
+  return Array.apply(null, Array(n)).map(function() {
+    return element;
+  });
+}
 
-    // Join all elements in the row into a single string with | separators
-    // (appends extra spaces to each cell to make separators  | aligned)
-    function joinRow(row, space) {
-      var cells = row.map(function(cell, i) {
-        var extraSpaces = repeat(' ', columnWidths[i] - cell.length).join('');
-        return cell + extraSpaces;
-      });
-      space = space || ' ';
-      return cells.join(space + '|' + space);
+function consoleTablePolyfill(rows) {
+  // convert object -> array
+  if (!Array.isArray(rows)) {
+    var data = rows;
+    rows = [];
+    for (var key in data) {
+      if (data.hasOwnProperty(key)) {
+        var row = data[key];
+        row[OBJECT_COLUMN_NAME] = key;
+        rows.push(row);
+      }
     }
+  }
+  if (rows.length === 0) {
+    global.nativeLoggingHook('', LOG_LEVELS.info);
+    return;
+  }
 
-    var separators = columnWidths.map(function(columnWidth) {
-      return repeat('-', columnWidth).join('');
+  var columns = Object.keys(rows[0]).sort();
+  var stringRows = [];
+  var columnWidths = [];
+
+  // Convert each cell to a string. Also
+  // figure out max cell width for each column
+  columns.forEach(function(k, i) {
+    columnWidths[i] = k.length;
+    for (var j = 0; j < rows.length; j++) {
+      var cellStr = (rows[j][k] || '?').toString();
+      stringRows[j] = stringRows[j] || [];
+      stringRows[j][i] = cellStr;
+      columnWidths[i] = Math.max(columnWidths[i], cellStr.length);
+    }
+  });
+
+  // Join all elements in the row into a single string with | separators
+  // (appends extra spaces to each cell to make separators  | aligned)
+  function joinRow(row, space) {
+    var cells = row.map(function(cell, i) {
+      var extraSpaces = repeat(' ', columnWidths[i] - cell.length).join('');
+      return cell + extraSpaces;
     });
-    var separatorRow = joinRow(separators, '-');
-    var header = joinRow(columns);
-    var table = [header, separatorRow];
+    space = space || ' ';
+    return cells.join(space + '|' + space);
+  }
 
-    for (var i = 0; i < rows.length; i++) {
-      table.push(joinRow(stringRows[i]));
-    }
+  var separators = columnWidths.map(function(columnWidth) {
+    return repeat('-', columnWidth).join('');
+  });
+  var separatorRow = joinRow(separators, '-');
+  var header = joinRow(columns);
+  var table = [header, separatorRow];
 
-    // Notice extra empty line at the beginning.
-    // Native logging hook adds "RCTLog >" at the front of every
-    // logged string, which would shift the header and screw up
-    // the table
-    global.nativeLoggingHook('\n' + table.join('\n'), LOG_LEVELS.info);
+  for (var i = 0; i < rows.length; i++) {
+    table.push(joinRow(stringRows[i]));
   }
 
+  // Notice extra empty line at the beginning.
+  // Native logging hook adds "RCTLog >" at the front of every
+  // logged string, which would shift the header and screw up
+  // the table
+  global.nativeLoggingHook('\n' + table.join('\n'), LOG_LEVELS.info);
+}
+
+if (global.nativeLoggingHook) {
   const originalConsole = global.console;
   global.console = {
     error: getNativeLogFunction(LOG_LEVELS.error),

From 7cbb222cd53b6cc49ec848827104ccf497f33de2 Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Wed, 28 Mar 2018 12:52:20 -0700
Subject: [PATCH 0160/1109] Remove class-loading experiment for View Managers.

Reviewed By: fkgozali

Differential Revision: D7418876

fbshipit-source-id: 52f8dce29a509233b9545a564c4f0d390fa81f13
---
 .../java/com/facebook/react/CompositeReactPackage.java | 10 ++++------
 .../java/com/facebook/react/ReactInstanceManager.java  |  7 ++-----
 .../facebook/react/ReactInstanceManagerBuilder.java    |  8 --------
 .../react/ViewManagerOnDemandReactPackage.java         |  9 ++-------
 4 files changed, 8 insertions(+), 26 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/CompositeReactPackage.java b/ReactAndroid/src/main/java/com/facebook/react/CompositeReactPackage.java
index ab82f0d96432..7aff02cfccfe 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/CompositeReactPackage.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/CompositeReactPackage.java
@@ -98,14 +98,13 @@ public List<ViewManager> createViewManagers(ReactApplicationContext reactContext
 
   /** {@inheritDoc} */
   @Override
-  public List<String> getViewManagerNames(
-      ReactApplicationContext reactContext, boolean loadClasses) {
+  public List<String> getViewManagerNames(ReactApplicationContext reactContext) {
     Set<String> uniqueNames = new HashSet<>();
     for (ReactPackage reactPackage : mChildReactPackages) {
       if (reactPackage instanceof ViewManagerOnDemandReactPackage) {
         List<String> names =
             ((ViewManagerOnDemandReactPackage) reactPackage)
-                .getViewManagerNames(reactContext, loadClasses);
+                .getViewManagerNames(reactContext);
         if (names != null) {
           uniqueNames.addAll(names);
         }
@@ -116,15 +115,14 @@ public List<String> getViewManagerNames(
 
   /** {@inheritDoc} */
   @Override
-  public @Nullable ViewManager createViewManager(
-      ReactApplicationContext reactContext, String viewManagerName, boolean loadClasses) {
+  public @Nullable ViewManager createViewManager(ReactApplicationContext reactContext, String viewManagerName) {
     ListIterator<ReactPackage> iterator = mChildReactPackages.listIterator(mChildReactPackages.size());
     while (iterator.hasPrevious()) {
       ReactPackage reactPackage = iterator.previous();
       if (reactPackage instanceof ViewManagerOnDemandReactPackage) {
         ViewManager viewManager =
             ((ViewManagerOnDemandReactPackage) reactPackage)
-                .createViewManager(reactContext, viewManagerName, loadClasses);
+                .createViewManager(reactContext, viewManagerName);
         if (viewManager != null) {
           return viewManager;
         }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 1d2731a71c85..d2dbda4dd6d9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -156,7 +156,6 @@ public interface ReactInstanceEventListener {
   private final MemoryPressureRouter mMemoryPressureRouter;
   private final @Nullable NativeModuleCallExceptionHandler mNativeModuleCallExceptionHandler;
   private final boolean mLazyNativeModulesEnabled;
-  private final boolean mDelayViewManagerClassLoadsEnabled;
   private final @Nullable JSIModulesProvider mJSIModulesProvider;
   private List<ViewManager> mViewManagers;
 
@@ -203,7 +202,6 @@ public static ReactInstanceManagerBuilder builder() {
     @Nullable RedBoxHandler redBoxHandler,
     boolean lazyNativeModulesEnabled,
     boolean lazyViewManagersEnabled,
-    boolean delayViewManagerClassLoadsEnabled,
     @Nullable DevBundleDownloadListener devBundleDownloadListener,
     int minNumShakes,
     int minTimeLeftInFrameForNonBatchedOperationMs,
@@ -235,7 +233,6 @@ public static ReactInstanceManagerBuilder builder() {
     mMemoryPressureRouter = new MemoryPressureRouter(applicationContext);
     mNativeModuleCallExceptionHandler = nativeModuleCallExceptionHandler;
     mLazyNativeModulesEnabled = lazyNativeModulesEnabled;
-    mDelayViewManagerClassLoadsEnabled = delayViewManagerClassLoadsEnabled;
     synchronized (mPackages) {
       PrinterHolder.getPrinter()
           .logMessage(ReactDebugOverlayTags.RN_CORE, "RNCore: Use Split Packages");
@@ -780,7 +777,7 @@ public List<ViewManager> getOrCreateViewManagers(
         if (reactPackage instanceof ViewManagerOnDemandReactPackage) {
           ViewManager viewManager =
               ((ViewManagerOnDemandReactPackage) reactPackage)
-                  .createViewManager(context, viewManagerName, !mDelayViewManagerClassLoadsEnabled);
+                  .createViewManager(context, viewManagerName);
           if (viewManager != null) {
             return viewManager;
           }
@@ -805,7 +802,7 @@ public List<ViewManager> getOrCreateViewManagers(
         if (reactPackage instanceof ViewManagerOnDemandReactPackage) {
           List<String> names =
               ((ViewManagerOnDemandReactPackage) reactPackage)
-                  .getViewManagerNames(context, !mDelayViewManagerClassLoadsEnabled);
+                  .getViewManagerNames(context);
           if (names != null) {
             uniqueNames.addAll(names);
           }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
index 75792d83db3b..a0f4438330e6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
@@ -44,7 +44,6 @@ public class ReactInstanceManagerBuilder {
   private @Nullable RedBoxHandler mRedBoxHandler;
   private boolean mLazyNativeModulesEnabled;
   private boolean mLazyViewManagersEnabled;
-  private boolean mDelayViewManagerClassLoadsEnabled;
   private @Nullable DevBundleDownloadListener mDevBundleDownloadListener;
   private @Nullable JavaScriptExecutorFactory mJavaScriptExecutorFactory;
   private int mMinNumShakes = 1;
@@ -209,12 +208,6 @@ public ReactInstanceManagerBuilder setLazyViewManagersEnabled(boolean lazyViewMa
     return this;
   }
 
-  public ReactInstanceManagerBuilder setDelayViewManagerClassLoadsEnabled(
-      boolean delayViewManagerClassLoadsEnabled) {
-    mDelayViewManagerClassLoadsEnabled = delayViewManagerClassLoadsEnabled;
-    return this;
-  }
-
   public ReactInstanceManagerBuilder setDevBundleDownloadListener(
     @Nullable DevBundleDownloadListener listener) {
     mDevBundleDownloadListener = listener;
@@ -285,7 +278,6 @@ public ReactInstanceManager build() {
         mRedBoxHandler,
         mLazyNativeModulesEnabled,
         mLazyViewManagersEnabled,
-        mDelayViewManagerClassLoadsEnabled,
         mDevBundleDownloadListener,
         mMinNumShakes,
         mMinTimeLeftInFrameForNonBatchedOperationMs,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ViewManagerOnDemandReactPackage.java b/ReactAndroid/src/main/java/com/facebook/react/ViewManagerOnDemandReactPackage.java
index 7f17809ffbb1..c28f91f60ee8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ViewManagerOnDemandReactPackage.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ViewManagerOnDemandReactPackage.java
@@ -16,17 +16,12 @@ public interface ViewManagerOnDemandReactPackage {
   /**
    * Provides a list of names of ViewManagers with which these modules can be accessed from JS.
    * Typically, this is ViewManager.getName().
-   *
-   * @param loadClasses defines if View Managers classes should be loaded or be avoided.
    */
-  @Nullable List<String> getViewManagerNames(ReactApplicationContext reactContext, boolean loadClasses);
+  @Nullable List<String> getViewManagerNames(ReactApplicationContext reactContext);
   /**
    * Creates and returns a ViewManager with a specific name {@param viewManagerName}. It's up to an
    * implementing package how to interpret the name.
-   *
-   * @param loadClasses defines if View Managers classes should be loaded or be avoided.
    */
   @Nullable
-  ViewManager createViewManager(
-      ReactApplicationContext reactContext, String viewManagerName, boolean loadClasses);
+  ViewManager createViewManager(ReactApplicationContext reactContext, String viewManagerName);
 }

From b531612b2c917e1f2bd6bb37bf854fe51e658b36 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Wed, 28 Mar 2018 12:53:08 -0700
Subject: [PATCH 0161/1109] Collect unit test results in test_android job

Summary:
Explicitly generate a XML file with unit test results, and convert this file to JUnit format for display in Circle.

Run in Circle: https://circleci.com/gh/hramos/react-native/1869

![screen shot 2018-03-28 at 12 07 15 pm](https://user-images.githubusercontent.com/165856/38050644-9712b6c6-3280-11e8-953c-a2eb722edf39.png)

[INTERNAL] [MINOR] [.circleci] - Collect, process, and display Android unit test results on Circle
Closes https://github.com/facebook/react-native/pull/18608

Differential Revision: D7433151

Pulled By: hramos

fbshipit-source-id: 7c18b552d7790b238b4c2a720fb316dff8fd7ec3
---
 .circleci/config.yml               | 38 ++++++++++++++++++------------
 scripts/circle-ci-android-setup.sh |  5 +---
 2 files changed, 24 insertions(+), 19 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index bb9570bf3227..7452d4bd43a7 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -56,20 +56,21 @@ aliases:
 
   - &restore-cache-ndk
     keys:
-      - v2-android-ndk-{{ arch }}-r10e-32-64-{{ checksum "scripts/circle-ci-android-setup.sh" }}
-      - v2-android-ndk-{{ arch }}-r10e-32-64-
+      - v3-android-ndk-{{ arch }}-r10e-{{ checksum "scripts/circle-ci-android-setup.sh" }}
+      - v3-android-ndk-{{ arch }}-r10e-
   - &save-cache-ndk
     paths:
       - /opt/ndk
-    key: v2-android-ndk-{{ arch }}-r10e-32-64-{{ checksum "scripts/circle-ci-android-setup.sh" }}
+    key: v3-android-ndk-{{ arch }}-r10e-{{ checksum "scripts/circle-ci-android-setup.sh" }}
 
   - &restore-cache-buck
     keys:
-      - v2-buck-{{ arch }}-v2018.02.16.01
+      - v3-buck-{{ arch }}-v2018.02.16.01
   - &save-cache-buck
     paths:
       - ~/buck
-    key: v2-buck-{{ arch }}-v2018.02.16.01
+      - ~/okbuck
+    key: v3-buck-{{ arch }}-v2018.02.16.01
 
   - &restore-cache-watchman
     keys:
@@ -141,6 +142,13 @@ aliases:
       fi
       cd ~/buck && ant
       buck --version
+      # Install related tooling
+      if [[ ! -e ~/okbuck ]]; then
+        git clone https://github.com/uber/okbuck.git ~/okbuck --depth=1
+      fi
+      mkdir -p ~/react-native/tooling/junit
+      cp -R ~/okbuck/tooling/junit/* ~/react-native/tooling/junit/.      
+
 
   - &install-node
     name: Install Node
@@ -237,7 +245,7 @@ aliases:
 
   - &run-android-unit-tests
     name: Run Unit Tests
-    command: buck test ReactAndroid/src/test/... --config build.threads=$BUILD_THREADS
+    command: buck test ReactAndroid/src/test/... --config build.threads=$BUILD_THREADS --xml ~/react-native/reports/buck/all-results-raw.xml
 
   - &run-android-instrumentation-tests
     name: Run Instrumentation Tests
@@ -250,15 +258,19 @@ aliases:
   - &collect-android-test-results
     name: Collect Test Results
     command: |
-      find . -type f -regex ".*/build/test-results/debug/.*xml" -exec cp {} ~/react-native/reports/junit/ \;
-      find . -type f -regex ".*/outputs/androidTest-results/connected/.*xml" -exec cp {} ~/react-native/reports/junit/ \;
-      find . -type f -regex ".*/buck-out/gen/ReactAndroid/src/test/.*/.*xml" -exec cp {} ~/react-native/reports/junit/ \;
+      find . -type f -regex ".*/build/test-results/debug/.*xml" -exec cp {} ~/react-native/reports/build/ \;
+      find . -type f -regex ".*/outputs/androidTest-results/connected/.*xml" -exec cp {} ~/react-native/reports/outputs/ \;
+      find . -type f -regex ".*/buck-out/gen/ReactAndroid/src/test/.*/.*xml" -exec cp {} ~/react-native/reports/buck/ \;
+      ./tooling/junit/buck_to_junit.sh ~/react-native/reports/buck/all-results-raw.xml ~/react-native/reports/junit/all-results-junit.xml
     when: always
 
   - &setup-artifacts
     name: Initial Setup
     command: | 
+      mkdir -p ~/react-native/reports/buck/
+      mkdir -p ~/react-native/reports/build/
       mkdir -p ~/react-native/reports/junit/
+      mkdir -p ~/react-native/reports/outputs/
   
   - &run-objc-ios-tests
     name: iOS Test Suite
@@ -289,7 +301,7 @@ js_defaults: &js_defaults
 android_defaults: &android_defaults
   <<: *defaults
   docker:
-    - image: circleci/android:api-26-alpha
+    - image: circleci/android:api-26-node8-alpha
   resource_class: "large"
   environment:
     - TERM: "dumb"
@@ -457,8 +469,6 @@ jobs:
       - run: *gradle-download-deps
       - save-cache: *save-cache-gradle-downloads
 
-      - run: *install-node
-      - run: *install-yarn
       - restore-cache: *restore-cache-yarn
       - run: *yarn
       - save-cache: *save-cache-yarn
@@ -529,7 +539,6 @@ jobs:
       - run: *compile-native-libs
 
       # Build JavaScript Bundle for instrumentation tests
-      - run: *install-node
       - run: *build-js-bundle
 
       # Wait for AVD to finish booting before running tests
@@ -539,12 +548,11 @@ jobs:
       - run: *run-android-unit-tests
       - run: *run-android-instrumentation-tests
       
-      # post (always runs)
+      # Collect Results
       - run: *collect-android-test-results
       - store_test_results:
           path: ~/react-native/reports/junit
 
-
   # Analyze pull request and raise any lint/flow issues.
   # Issues will be posted to the PR itself via GitHub bots.
   # This workflow should only fail if the bots fail to run.
diff --git a/scripts/circle-ci-android-setup.sh b/scripts/circle-ci-android-setup.sh
index c5a0a1f31b52..35421a598a03 100644
--- a/scripts/circle-ci-android-setup.sh
+++ b/scripts/circle-ci-android-setup.sh
@@ -41,14 +41,11 @@ function getAndroidNDK {
   if [ ! -e $DEPS ]; then
     cd $NDK_HOME
     echo "Downloading NDK..."
-    curl -o ndk.zip https://dl.google.com/android/repository/android-ndk-r10e-linux-x86.zip
-    curl -o ndk_64.zip https://dl.google.com/android/repository/android-ndk-r10e-linux-x86_64.zip
+    curl -o ndk.zip https://dl.google.com/android/repository/android-ndk-r10e-linux-x86_64.zip
     unzip -o -q ndk.zip
-    unzip -o -q ndk_64.zip
     echo "Installed Android NDK at $NDK_HOME"
     touch $DEPS
     rm ndk.zip
-    rm ndk_64.zip
   fi
 }
 

From e88f1286089aad05f8c3932c87913f30a64f1be6 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 28 Mar 2018 23:17:32 -0700
Subject: [PATCH 0162/1109] Refactor ReactShadowNode.SetRootNode() ->
 ReactShadowNode.setRootTag()

Reviewed By: achen1

Differential Revision: D7419566

fbshipit-source-id: 6be790972e88b879fe690acd4f23d0caa27964a4
---
 .../com/facebook/react/fabric/FabricUIManager.java    |  2 +-
 .../react/uimanager/NativeViewHierarchyOptimizer.java |  2 +-
 .../com/facebook/react/uimanager/ReactShadowNode.java |  4 ++--
 .../facebook/react/uimanager/ReactShadowNodeImpl.java | 11 +++++------
 .../facebook/react/uimanager/UIImplementation.java    |  4 ++--
 5 files changed, 11 insertions(+), 12 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 6959c275ff59..2cadd153c3f1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -77,7 +77,7 @@ public ReactShadowNode createNode(
       ViewManager viewManager = mViewManagerRegistry.get(viewName);
       ReactShadowNode node = viewManager.createShadowNodeInstance(mReactApplicationContext);
       ReactShadowNode rootNode = getRootNode(rootTag);
-      node.setRootNode(rootNode);
+      node.setRootTag(rootNode.getReactTag());
       node.setViewClassName(viewName);
       node.setReactTag(reactTag);
       node.setThemedContext(rootNode.getThemedContext());
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyOptimizer.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyOptimizer.java
index de23eeaa1cce..b6562779875f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyOptimizer.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyOptimizer.java
@@ -407,7 +407,7 @@ private void transitionLayoutOnlyViewToNativeView(
 
     // Create the view since it doesn't exist in the native hierarchy yet
     mUIViewOperationQueue.enqueueCreateView(
-        node.getRootNode().getThemedContext(),
+        node.getThemedContext(),
         node.getReactTag(),
         node.getViewClass(),
         props);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
index dbf64b1355b8..7790a49ddf61 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
@@ -139,9 +139,9 @@ public interface ReactShadowNode<T extends ReactShadowNode> {
 
   void setReactTag(int reactTag);
 
-  T getRootNode();
+  int getRootTag();
 
-  void setRootNode(T rootNode);
+  void setRootTag(int rootTag);
 
   void setViewClassName(String viewClassName);
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 5f4ad868fe77..e6b4a9012271 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -78,7 +78,6 @@ public void onNodeCloned(YogaNode oldYogaNode,
 
   private int mReactTag;
   private @Nullable String mViewClassName;
-  private @Nullable ReactShadowNodeImpl mRootNode;
   private int mRootTag;
   private @Nullable ThemedReactContext mThemedContext;
   private boolean mShouldNotifyOnLayout;
@@ -118,7 +117,6 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     mReactTag = original.mReactTag;
     mRootTag = original.mRootTag;
     mViewClassName = original.mViewClassName;
-    mRootNode = original.mRootNode;
     mThemedContext = original.mThemedContext;
     mShouldNotifyOnLayout = original.mShouldNotifyOnLayout;
     mNodeUpdated = original.mNodeUpdated;
@@ -493,13 +491,14 @@ public void setReactTag(int reactTag) {
   }
 
   @Override
-  public final ReactShadowNodeImpl getRootNode() {
-    return Assertions.assertNotNull(mRootNode);
+  public final int getRootTag() {
+    Assertions.assertCondition(mRootTag != 0);
+    return mRootTag;
   }
 
   @Override
-  public final void setRootNode(ReactShadowNodeImpl rootNode) {
-    mRootNode = rootNode;
+  public final void setRootTag(int rootTag) {
+    mRootTag = rootTag;
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
index f33ab605700f..186a4d4357c3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
@@ -279,7 +279,7 @@ public void createView(int tag, String className, int rootViewTag, ReadableMap p
     Assertions.assertNotNull(rootNode, "Root node with tag " + rootViewTag + " doesn't exist");
     cssNode.setReactTag(tag);
     cssNode.setViewClassName(className);
-    cssNode.setRootNode(rootNode);
+    cssNode.setRootTag(rootNode.getReactTag());
     cssNode.setThemedContext(rootNode.getThemedContext());
 
     mShadowNodeRegistry.addNode(cssNode);
@@ -1008,7 +1008,7 @@ public int resolveRootTagFromReactTag(int reactTag) {
     ReactShadowNode node = resolveShadowNode(reactTag);
     int rootTag = 0;
     if (node != null) {
-      rootTag = node.getRootNode().getReactTag();
+      rootTag = node.getRootTag();
     } else {
       FLog.w(
         ReactConstants.TAG,

From ff2260b0220faf124c43df9746e1394882fa4d71 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 29 Mar 2018 05:24:29 -0700
Subject: [PATCH 0163/1109] Add `JByteBuffer::rewind()`

Summary:
Adds a `rewind()` method to `JByteBuffer`, which maps to `java.nio.Buffer#rewind()`.
This is useful if a `ByteBuffer` is reused for calls between Java and C++.

Differential Revision: D7435171

fbshipit-source-id: 488131d6ad2d5abb1b86a5efabc2f39ba0ab16cd
---
 .../main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h  | 7 +++++++
 .../src/main/jni/first-party/fb/jni/ByteBuffer.cpp         | 5 +++++
 2 files changed, 12 insertions(+)

diff --git a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h
index 21d17a27ad8e..1e31d76cf8cc 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h
+++ b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h
@@ -15,6 +15,13 @@
 namespace facebook {
 namespace jni {
 
+class JBuffer : public JavaClass<JBuffer> {
+public:
+  static constexpr const char* kJavaDescriptor = "Ljava/nio/Buffer;";
+
+  void rewind() const;
+};
+
 // JNI's NIO support has some awkward preconditions and error reporting. This
 // class provides much more user-friendly access.
 class FBEXPORT JByteBuffer : public JavaClass<JByteBuffer> {
diff --git a/ReactAndroid/src/main/jni/first-party/fb/jni/ByteBuffer.cpp b/ReactAndroid/src/main/jni/first-party/fb/jni/ByteBuffer.cpp
index 5a5317f9f2b1..8060930275c5 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/jni/ByteBuffer.cpp
+++ b/ReactAndroid/src/main/jni/first-party/fb/jni/ByteBuffer.cpp
@@ -22,6 +22,11 @@ local_ref<JByteBuffer> createEmpty() {
 }
 }
 
+void JBuffer::rewind() const {
+  static auto meth = javaClassStatic()->getMethod<alias_ref<JBuffer>()>("rewind");
+  meth(self());
+}
+
 local_ref<JByteBuffer> JByteBuffer::wrapBytes(uint8_t* data, size_t size) {
   // env->NewDirectByteBuffer requires that size is positive. Android's
   // dalvik returns an invalid result and Android's art aborts if size == 0.

From f3ef227904acef4f0525839e84f407d6cf5d7a0c Mon Sep 17 00:00:00 2001
From: "glevi@fb.com" <glevi@fb.com>
Date: Thu, 29 Mar 2018 06:24:04 -0700
Subject: [PATCH 0164/1109] Upgrade to Flow v0.69.0

Reviewed By: panagosg7

Differential Revision: D7437630

fbshipit-source-id: db9627afed89049c07a121296fbd52e2bfbf39bf
---
 .flowconfig                                | 2 +-
 local-cli/bundle/buildBundle.js            | 1 -
 local-cli/server/runServer.js              | 1 -
 local-cli/server/server.js                 | 2 +-
 local-cli/templates/HelloWorld/_flowconfig | 2 +-
 package.json                               | 2 +-
 6 files changed, 4 insertions(+), 6 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index 182bf0f089e6..f67339eee784 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -52,4 +52,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.68.0
+^0.69.0
diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index 51427aa8f3a3..ebebc09c6ebf 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -13,7 +13,6 @@ const log = require('../util/log').out('bundle');
 /* $FlowFixMe(site=react_native_oss) */
 const Server = require('metro/src/Server');
 const {Terminal} = require('metro-core');
-/* $FlowFixMe(site=react_native_oss) */
 const TerminalReporter = require('metro/src/lib/TerminalReporter');
 /* $FlowFixMe(site=react_native_oss) */
 const TransformCaching = require('metro/src/lib/TransformCaching');
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index a9ba1557ddc7..768fbaf0d367 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -48,7 +48,6 @@ const TransformCaching = require('metro/src/lib/TransformCaching');
 
 const {ASSET_REGISTRY_PATH} = require('../core/Constants');
 
-/* $FlowFixMe(site=react_native_oss) */
 import type {ConfigT} from 'metro';
 /* $FlowFixMe(site=react_native_oss) */
 import type {Reporter} from 'metro/src/lib/reporting';
diff --git a/local-cli/server/server.js b/local-cli/server/server.js
index f188a3e82dd4..7711e8590afc 100644
--- a/local-cli/server/server.js
+++ b/local-cli/server/server.js
@@ -47,7 +47,7 @@ function server(argv: mixed, config: RNConfig, allArgs: Object) {
     });
   };
   const runServerArgs: RunServerArgs = args;
-  /* $FlowFixMe: ConfigT shouldn't be extendable. */
+  /* $FlowFixMe(site=react_native_fb) ConfigT shouldn't be extendable. */
   const configT: ConfigT = config;
   runServer(runServerArgs, configT, startedCallback, readyCallback);
 }
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 3813ec4a1011..159649f1348e 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -51,4 +51,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.68.0
+^0.69.0
diff --git a/package.json b/package.json
index c9793054ddc5..5c9215a2c228 100644
--- a/package.json
+++ b/package.json
@@ -215,7 +215,7 @@
     "eslint-plugin-jest": "21.8.0",
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
-    "flow-bin": "^0.68.0",
+    "flow-bin": "^0.69.0",
     "jest": "23.0.0-alpha.4",
     "jest-junit": "3.6.0",
     "prettier": "1.9.1",

From 24b5721fb4a7c7c3a5994649c4e8bf78e647fce9 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 29 Mar 2018 07:58:16 -0700
Subject: [PATCH 0165/1109] Fix `ByteBuffer.h`

Reviewed By: mjesun

Differential Revision: D7443482

fbshipit-source-id: aa765d54149fd81f785dbca7252342ed9b3c236d
---
 .../src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h   | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h
index 1e31d76cf8cc..2f160839f5b4 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h
+++ b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ByteBuffer.h
@@ -24,7 +24,7 @@ class JBuffer : public JavaClass<JBuffer> {
 
 // JNI's NIO support has some awkward preconditions and error reporting. This
 // class provides much more user-friendly access.
-class FBEXPORT JByteBuffer : public JavaClass<JByteBuffer> {
+class FBEXPORT JByteBuffer : public JavaClass<JByteBuffer, JBuffer> {
  public:
   static constexpr const char* kJavaDescriptor = "Ljava/nio/ByteBuffer;";
 

From 6be7b396ecd5f10a8c08cd5f6428eeccbf986a7d Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 29 Mar 2018 11:02:04 -0700
Subject: [PATCH 0166/1109] Update okio

Summary:
Update okio dependency from 1.13.0 to 1.14.0.

The interesting feature is `BufferedSource` extending `java.nio.ReadableByteChannel`, allowing to bridge with `java.nio` more easily and integrating with the latest fbjni additions.

Reviewed By: emilsjolander

Differential Revision: D7443269

fbshipit-source-id: e397d7a0436e3fc59ade1f4357f30190ca7bbe35
---
 ReactAndroid/build.gradle                        | 4 ++--
 ReactAndroid/src/main/third-party/java/okio/BUCK | 4 ++--
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 48c38722a167..25ba9d2c1b28 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -287,7 +287,7 @@ dependencies {
     compile 'com.google.code.findbugs:jsr305:3.0.0'
     compile 'com.squareup.okhttp3:okhttp:3.8.0'
     compile 'com.squareup.okhttp3:okhttp-urlconnection:3.8.0'
-    compile 'com.squareup.okio:okio:1.13.0'
+    compile 'com.squareup.okio:okio:1.14.0'
     compile 'org.webkit:android-jsc:r174650'
 
     testCompile "junit:junit:${JUNIT_VERSION}"
@@ -297,7 +297,7 @@ dependencies {
     testCompile "org.mockito:mockito-core:${MOCKITO_CORE_VERSION}"
     testCompile "org.easytesting:fest-assert-core:${FEST_ASSERT_CORE_VERSION}"
     testCompile "org.robolectric:robolectric:${ROBOLECTRIC_VERSION}"
-    
+
     androidTestCompile fileTree(dir: 'src/main/third-party/java/buck-android-support/', include: ['*.jar'])
     androidTestCompile 'com.android.support.test:runner:0.3'
     androidTestCompile "org.mockito:mockito-core:${MOCKITO_CORE_VERSION}"
diff --git a/ReactAndroid/src/main/third-party/java/okio/BUCK b/ReactAndroid/src/main/third-party/java/okio/BUCK
index 45955117a037..eef6fb6cc50b 100644
--- a/ReactAndroid/src/main/third-party/java/okio/BUCK
+++ b/ReactAndroid/src/main/third-party/java/okio/BUCK
@@ -6,6 +6,6 @@ prebuilt_jar(
 
 remote_file(
     name = "okio-binary-jar",
-    sha1 = "a9283170b7305c8d92d25aff02a6ab7e45d06cbe",
-    url = "mvn:com.squareup.okio:okio:jar:1.13.0",
+    sha1 = "102d7be47241d781ef95f1581d414b0943053130",
+    url = "mvn:com.squareup.okio:okio:jar:1.14.0",
 )

From 9bdc31069addb9df468d551357724d9a2fc5f9b2 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Thu, 29 Mar 2018 11:29:09 -0700
Subject: [PATCH 0167/1109] Update Android Docker images

Summary:
yarn docker-build-android-base
yarn docker-build-android

[INTERNAL] [MINOR] [ContainerShip] - Bump versions in Dockerfiles
Closes https://github.com/facebook/react-native/pull/18597

Differential Revision: D7433542

Pulled By: hramos

fbshipit-source-id: 5ec7496c84203a0ed20ef3875ac3d367914a0e80
---
 ContainerShip/Dockerfile.android      | 11 +++++++----
 ContainerShip/Dockerfile.android-base | 17 +++--------------
 package.json                          | 14 +++++++-------
 3 files changed, 17 insertions(+), 25 deletions(-)

diff --git a/ContainerShip/Dockerfile.android b/ContainerShip/Dockerfile.android
index adb361ab58f7..f7a207aea3e5 100644
--- a/ContainerShip/Dockerfile.android
+++ b/ContainerShip/Dockerfile.android
@@ -9,6 +9,7 @@ ADD .buckconfig /app/.buckconfig
 ADD .buckjavaargs /app/.buckjavaargs
 ADD ReactAndroid /app/ReactAndroid
 ADD ReactCommon /app/ReactCommon
+ADD ReactNative /app/ReactNative
 ADD keystores /app/keystores
 
 # set workdir
@@ -41,10 +42,12 @@ RUN ./gradlew :ReactAndroid:packageReactNdkLibsForBuck -Pjobs=1 -Pcom.android.bu
 ADD . /app
 WORKDIR /app
 
-# https://github.com/npm/npm/issues/13306
-RUN cd $(npm root -g)/npm && npm install fs-extra && sed -i -e s/graceful-fs/fs-extra/ -e s/fs.rename/fs.move/ ./lib/utils/rename.js
-
 # build node dependencies
-RUN npm install
+RUN curl -sS https://dl.yarnpkg.com/debian/pubkey.gpg | apt-key add -
+RUN echo "deb https://dl.yarnpkg.com/debian/ stable main" | tee /etc/apt/sources.list.d/yarn.list
+RUN apt-get install apt-transport-https
+RUN apt-get update
+RUN apt-get install yarn
+RUN yarn
 
 WORKDIR /app
diff --git a/ContainerShip/Dockerfile.android-base b/ContainerShip/Dockerfile.android-base
index 05caa480f3c8..93a1aafa8117 100644
--- a/ContainerShip/Dockerfile.android-base
+++ b/ContainerShip/Dockerfile.android-base
@@ -2,10 +2,10 @@ FROM library/ubuntu:16.04
 
 # set default build arguments
 ARG ANDROID_TOOLS_VERSION=25.2.5
-ARG BUCK_VERSION=v2017.11.16.01
+ARG BUCK_VERSION=v2018.02.16.01
 ARG NDK_VERSION=10e
-ARG NODE_VERSION=6.2.0
-ARG WATCHMAN_VERSION=4.7.0
+ARG NODE_VERSION=8.10.0
+ARG WATCHMAN_VERSION=4.9.0
 
 # set default environment variables
 ENV ADB_INSTALL_TIMEOUT=10
@@ -34,17 +34,6 @@ WORKDIR /opt/buck
 # build buck
 RUN ant
 
-# download watchman
-RUN git clone https://github.com/facebook/watchman.git /opt/watchman
-WORKDIR /opt/watchman
-RUN git checkout v$WATCHMAN_VERSION
-
-# build watchman
-RUN ./autogen.sh
-RUN ./configure
-RUN make
-RUN make install
-
 # Full reference at https://dl.google.com/android/repository/repository2-1.xml
 # download and unpack android
 RUN mkdir /opt/android
diff --git a/package.json b/package.json
index 5c9215a2c228..d15a462f15e1 100644
--- a/package.json
+++ b/package.json
@@ -127,16 +127,16 @@
     "lint": "eslint .",
     "prettier": "find . -name node_modules -prune -or -name '*.js' -print | xargs prettier --write",
     "start": "/usr/bin/env bash -c './scripts/packager.sh \"$@\" || true' --",
-    "test-android-setup": "docker pull hramos/android-base:latest",
-    "test-android-build-base": "docker build -t hramos/android-base -f ContainerShip/Dockerfile.android-base .",
-    "test-android-build": "docker build -t react/android -f ContainerShip/Dockerfile.android .",
+    "docker-setup-android": "docker pull hramos/android-base:latest",
+    "docker-build-android-base": "docker build -t hramos/android-base -f ContainerShip/Dockerfile.android-base .",
+    "docker-build-android": "docker build -t react/android -f ContainerShip/Dockerfile.android .",
     "test-android-run-instrumentation": "docker run --cap-add=SYS_ADMIN -it react/android bash ContainerShip/scripts/run-android-docker-instrumentation-tests.sh",
     "test-android-run-unit": "docker run --cap-add=SYS_ADMIN -it react/android bash ContainerShip/scripts/run-android-docker-unit-tests.sh",
     "test-android-run-e2e": "docker run --privileged -it react/android bash ContainerShip/scripts/run-ci-e2e-tests.sh --android --js",
-    "test-android-all": "npm run test-android-build && npm run test-android-run-unit && npm run test-android-run-instrumentation && npm run test-android-run-e2e",
-    "test-android-instrumentation": "npm run test-android-build && npm run test-android-run-instrumentation",
-    "test-android-unit": "npm run test-android-build && npm run test-android-run-unit",
-    "test-android-e2e": "npm run test-android-build && npm run test-android-run-e2e"
+    "test-android-all": "yarn run docker-build-android && yarn run test-android-run-unit && yarn run test-android-run-instrumentation && yarn run test-android-run-e2e",
+    "test-android-instrumentation": "yarn run docker-build-android && yarn run test-android-run-instrumentation",
+    "test-android-unit": "yarn run docker-build-android && yarn run test-android-run-unit",
+    "test-android-e2e": "yarn run docker-build-android && yarn run test-android-run-e2e"
   },
   "bin": {
     "react-native": "local-cli/wrong-react-native.js"

From ee0c69dfa66de2a5dd320a85c6d9294f38733352 Mon Sep 17 00:00:00 2001
From: Ram N <axe@fb.com>
Date: Thu, 29 Mar 2018 16:05:10 -0700
Subject: [PATCH 0168/1109] Keep nativeIDs immutable in ReactFindViewUtil

Reviewed By: mdvacca

Differential Revision: D7430144

fbshipit-source-id: c8e8242c1c3216258e4b8c27623160338e2578d8
---
 .../uimanager/util/ReactFindViewUtil.java      | 18 +++++-------------
 1 file changed, 5 insertions(+), 13 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/ReactFindViewUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/ReactFindViewUtil.java
index 1d0d41d82c83..cd3104ae3726 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/ReactFindViewUtil.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/ReactFindViewUtil.java
@@ -129,19 +129,11 @@ public static void notifyViewRendered(View view) {
       }
     }
 
-    Iterator<Map.Entry<OnMultipleViewsFoundListener, Set<String>>>
-        viewIterator = mOnMultipleViewsFoundListener.entrySet().iterator();
-    while (viewIterator.hasNext()) {
-      Map.Entry<OnMultipleViewsFoundListener, Set<String>> entry =
-          viewIterator.next();
-      Set<String> nativeIds = entry.getValue();
-      if (nativeIds.contains(nativeId)) {
-        entry.getKey().onViewFound(view, nativeId);
-        nativeIds.remove(nativeId); // remove it from list of NativeIds to search for.
-      }
-      if (nativeIds.isEmpty()) {
-        viewIterator.remove();
-      }
+    for (Map.Entry<OnMultipleViewsFoundListener, Set<String>> entry : mOnMultipleViewsFoundListener.entrySet()) {
+       Set<String> nativeIds = entry.getValue();
+       if (nativeIds != null && nativeIds.contains(nativeId)) {
+            entry.getKey().onViewFound(view, nativeId);
+       }
     }
   }
 

From 1020ac9481b5fedc2cc6aa31f757501f7ef556df Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 29 Mar 2018 20:59:47 -0700
Subject: [PATCH 0169/1109] OSS: add gradle wrapper helper to prepare offline
 gradle caches

Summary:
This is to help build offline module caches for gradle builds.

allow-large-files

Reviewed By: hramos

Differential Revision: D7441450

fbshipit-source-id: 37ceb070223f0de06720f5c104ecfce2ad6cedfd
---
 ReactAndroid/build.gradle | 13 ++++++++++++-
 1 file changed, 12 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 25ba9d2c1b28..fa1be07afa74 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -13,7 +13,8 @@ import org.apache.tools.ant.filters.ReplaceTokens
 // We then copy both the downloaded code and our custom makefiles and headers into third-party-ndk.
 // After that we build native code from src/main/jni with module path pointing at third-party-ndk.
 
-def downloadsDir = new File("$buildDir/downloads")
+def customDownloadsDir = System.getenv("REACT_NATIVE_DOWNLOADS_DIR")
+def downloadsDir = customDownloadsDir ? new File(customDownloadsDir) : new File("$buildDir/downloads")
 def thirdPartyNdkDir = new File("$buildDir/third-party-ndk")
 
 // You need to have following folders in this directory:
@@ -145,6 +146,16 @@ task prepareJSC(dependsOn: dependenciesPath ? [] : [downloadJSCHeaders]) << {
     }
 }
 
+task downloadNdkBuildDependencies {
+  if (!boostPath) {
+    dependsOn downloadBoost
+  }
+  dependsOn downloadDoubleConversion
+  dependsOn downloadFolly
+  dependsOn downloadGlog
+  dependsOn downloadJSCHeaders
+}
+
 def getNdkBuildName() {
     if (Os.isFamily(Os.FAMILY_WINDOWS)) {
         return "ndk-build.cmd"

From 550339c71b8d647cf63e6282a961caff9887f9d7 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 29 Mar 2018 22:48:44 -0700
Subject: [PATCH 0170/1109] Add `JReadableByteChannel`

Summary:
Adds `JReadableByteChannel`, which maps to `java.nio.ReadableByteChannel`.
This class is useful to stream data from Java to C++ memory (in conjunction with `JByteBuffer`).

Differential Revision: D7437312

fbshipit-source-id: 4979706148f0e20228f0f52341fb340497c24a8b
---
 .../src/main/jni/first-party/fb/Android.mk    |  1 +
 .../fb/include/fb/fbjni/ReadableByteChannel.h | 23 +++++++++++++++++++
 .../fb/jni/ReadableByteChannel.cpp            | 21 +++++++++++++++++
 3 files changed, 45 insertions(+)
 create mode 100644 ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ReadableByteChannel.h
 create mode 100644 ReactAndroid/src/main/jni/first-party/fb/jni/ReadableByteChannel.cpp

diff --git a/ReactAndroid/src/main/jni/first-party/fb/Android.mk b/ReactAndroid/src/main/jni/first-party/fb/Android.mk
index aaf198bce73f..4540eef1d602 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/Android.mk
+++ b/ReactAndroid/src/main/jni/first-party/fb/Android.mk
@@ -13,6 +13,7 @@ LOCAL_SRC_FILES:= \
        jni/jni_helpers.cpp \
        jni/LocalString.cpp \
        jni/OnLoad.cpp \
+       jni/ReadableByteChannel.cpp \
        jni/References.cpp \
        jni/WeakReference.cpp \
        log.cpp \
diff --git a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ReadableByteChannel.h b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ReadableByteChannel.h
new file mode 100644
index 000000000000..f895a3e6ff65
--- /dev/null
+++ b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/ReadableByteChannel.h
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2016-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fb/fbjni.h>
+#include <fb/fbjni/ByteBuffer.h>
+
+namespace facebook {
+namespace jni {
+
+class JReadableByteChannel : public JavaClass<JReadableByteChannel> {
+public:
+  static constexpr const char* kJavaDescriptor = "Ljava/nio/channels/ReadableByteChannel;";
+
+  int read(alias_ref<JByteBuffer> dest) const;
+};
+
+}}
diff --git a/ReactAndroid/src/main/jni/first-party/fb/jni/ReadableByteChannel.cpp b/ReactAndroid/src/main/jni/first-party/fb/jni/ReadableByteChannel.cpp
new file mode 100644
index 000000000000..9c67df3fa923
--- /dev/null
+++ b/ReactAndroid/src/main/jni/first-party/fb/jni/ReadableByteChannel.cpp
@@ -0,0 +1,21 @@
+/*
+ * Copyright (c) 2016-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fb/fbjni/ReadableByteChannel.h>
+
+namespace facebook {
+namespace jni {
+
+int JReadableByteChannel::read(alias_ref<JByteBuffer> dest) const {
+  if (!self()) {
+    throwNewJavaException("java/lang/NullPointerException", "java.lang.NullPointerException");
+  }
+  static auto method = javaClassStatic()->getMethod<jint(alias_ref<JByteBuffer>)>("read");
+  return method(self(), dest);
+}
+
+}}

From 1f27098a1aacea3d10a34738b3a5ff1ca9902743 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 30 Mar 2018 11:43:18 -0700
Subject: [PATCH 0171/1109] Fabric: Proper Yoga node dirting in
 YogaLayoutableShadowNode

Summary: Any change must be propagate upwards.

Reviewed By: mdvacca

Differential Revision: D7389058

fbshipit-source-id: 09c74640d0e9607d2e17bdd31d7ce69df8565f72
---
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 376f092367c9..d7974ae0fed3 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -215,7 +215,7 @@ void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNo
   }
 
   yogaNode.setChildren(yogaNodeChildren);
-  yogaNode.setDirty(true);
+  yogaNode.markDirtyAndPropogate();
 }
 
 } // namespace react

From 4906f8d28cdbaf1b432494b473a4c61c1e193881 Mon Sep 17 00:00:00 2001
From: Vladislav Pilgasov <avendiart@gmail.com>
Date: Fri, 30 Mar 2018 20:57:42 -0700
Subject: [PATCH 0172/1109] Add an implementation of Animated.subtract

Summary:
Fixes #18451

I've added another example to NativeAnimationsExample, which makes use of `Animated.substract()`, let me know if the example is not desired / doesn't add much value. Below two GIFs of the new method working on iOS and Android:

<img width="320" src="https://user-images.githubusercontent.com/1437605/38154748-165cc5f8-3474-11e8-8b31-504444271896.gif" />
<img width="320" src="https://user-images.githubusercontent.com/1437605/38154749-1679bff0-3474-11e8-80b1-b558d44e0494.gif" />

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

https://github.com/facebook/react-native-website/pull/276

[GENERAL] [ENHANCEMENT] [Animated] - Implemented Animated.subtract
Closes https://github.com/facebook/react-native/pull/18630

Differential Revision: D7462867

Pulled By: hramos

fbshipit-source-id: 4cb0b8af08bb0c841e44ea2099889b8c02a22a4a
---
 .../Animated/src/AnimatedImplementation.js    | 16 +++++
 .../src/__tests__/AnimatedNative-test.js      | 32 ++++++++++
 .../Animated/src/nodes/AnimatedSubtraction.js | 63 +++++++++++++++++++
 .../Nodes/RCTSubtractionAnimatedNode.h        | 13 ++++
 .../Nodes/RCTSubtractionAnimatedNode.m        | 27 ++++++++
 .../RCTAnimation.xcodeproj/project.pbxproj    |  6 ++
 .../RCTNativeAnimatedNodesManager.m           |  2 +
 RNTester/js/NativeAnimationsExample.js        | 42 +++++++++++++
 .../animated/NativeAnimatedNodesManager.java  |  2 +
 .../animated/SubtractionAnimatedNode.java     | 51 +++++++++++++++
 10 files changed, 254 insertions(+)
 create mode 100644 Libraries/Animated/src/nodes/AnimatedSubtraction.js
 create mode 100644 Libraries/NativeAnimation/Nodes/RCTSubtractionAnimatedNode.h
 create mode 100644 Libraries/NativeAnimation/Nodes/RCTSubtractionAnimatedNode.m
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/animated/SubtractionAnimatedNode.java

diff --git a/Libraries/Animated/src/AnimatedImplementation.js b/Libraries/Animated/src/AnimatedImplementation.js
index e13aef1e7235..9291a7956531 100644
--- a/Libraries/Animated/src/AnimatedImplementation.js
+++ b/Libraries/Animated/src/AnimatedImplementation.js
@@ -20,6 +20,7 @@ const AnimatedModulo = require('./nodes/AnimatedModulo');
 const AnimatedMultiplication = require('./nodes/AnimatedMultiplication');
 const AnimatedNode = require('./nodes/AnimatedNode');
 const AnimatedProps = require('./nodes/AnimatedProps');
+const AnimatedSubtraction = require('./nodes/AnimatedSubtraction');
 const AnimatedTracking = require('./nodes/AnimatedTracking');
 const AnimatedValue = require('./nodes/AnimatedValue');
 const AnimatedValueXY = require('./nodes/AnimatedValueXY');
@@ -54,6 +55,13 @@ const add = function(
   return new AnimatedAddition(a, b);
 };
 
+const subtract = function(
+  a: AnimatedNode | number,
+  b: AnimatedNode | number,
+): AnimatedSubtraction {
+  return new AnimatedSubtraction(a, b);
+};
+
 const divide = function(
   a: AnimatedNode | number,
   b: AnimatedNode | number,
@@ -568,6 +576,14 @@ module.exports = {
    */
   add,
 
+  /**
+   * Creates a new Animated value composed by subtracting the second Animated
+   * value from the first Animated value.
+   *
+   * See http://facebook.github.io/react-native/docs/animated.html#subtract
+   */
+  subtract,
+
   /**
    * Creates a new Animated value composed by dividing the first Animated value
    * by the second Animated value.
diff --git a/Libraries/Animated/src/__tests__/AnimatedNative-test.js b/Libraries/Animated/src/__tests__/AnimatedNative-test.js
index 1c6700e4dc06..f04d5afb1429 100644
--- a/Libraries/Animated/src/__tests__/AnimatedNative-test.js
+++ b/Libraries/Animated/src/__tests__/AnimatedNative-test.js
@@ -333,6 +333,38 @@ describe('Native Animated', () => {
         .toBeCalledWith(additionCall[1].input[1], {type: 'value', value: 2, offset: 0});
     });
 
+    it('sends a valid graph description for Animated.subtract nodes', () => {
+      const first = new Animated.Value(2);
+      const second = new Animated.Value(1);
+      first.__makeNative();
+      second.__makeNative();
+
+      createAndMountComponent(Animated.View, {
+        style: {
+          opacity: Animated.subtract(first, second),
+        },
+      });
+
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        expect.any(Number),
+        {type: 'subtraction', input: expect.any(Array)},
+      );
+      const subtractionCalls = nativeAnimatedModule.createAnimatedNode.mock.calls.filter(
+        (call) => call[1].type === 'subtraction'
+      );
+      expect(subtractionCalls.length).toBe(1);
+      const subtractionCall = subtractionCalls[0];
+      const subtractionNodeTag = subtractionCall[0];
+      const subtractionConnectionCalls = nativeAnimatedModule.connectAnimatedNodes.mock.calls.filter(
+        (call) => call[1] === subtractionNodeTag
+      );
+      expect(subtractionConnectionCalls.length).toBe(2);
+      expect(nativeAnimatedModule.createAnimatedNode)
+        .toBeCalledWith(subtractionCall[1].input[0], {type: 'value', value: 2, offset: 0});
+      expect(nativeAnimatedModule.createAnimatedNode)
+        .toBeCalledWith(subtractionCall[1].input[1], {type: 'value', value: 1, offset: 0});
+    });
+
     it('sends a valid graph description for Animated.multiply nodes', () => {
       const first = new Animated.Value(2);
       const second = new Animated.Value(1);
diff --git a/Libraries/Animated/src/nodes/AnimatedSubtraction.js b/Libraries/Animated/src/nodes/AnimatedSubtraction.js
new file mode 100644
index 000000000000..610fc226eb65
--- /dev/null
+++ b/Libraries/Animated/src/nodes/AnimatedSubtraction.js
@@ -0,0 +1,63 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @providesModule AnimatedSubtraction
+ * @flow
+ * @format
+ */
+'use strict';
+
+const AnimatedInterpolation = require('./AnimatedInterpolation');
+const AnimatedNode = require('./AnimatedNode');
+const AnimatedValue = require('./AnimatedValue');
+const AnimatedWithChildren = require('./AnimatedWithChildren');
+
+import type {InterpolationConfigType} from './AnimatedInterpolation';
+
+class AnimatedSubtraction extends AnimatedWithChildren {
+  _a: AnimatedNode;
+  _b: AnimatedNode;
+
+  constructor(a: AnimatedNode | number, b: AnimatedNode | number) {
+    super();
+    this._a = typeof a === 'number' ? new AnimatedValue(a) : a;
+    this._b = typeof b === 'number' ? new AnimatedValue(b) : b;
+  }
+
+  __makeNative() {
+    this._a.__makeNative();
+    this._b.__makeNative();
+    super.__makeNative();
+  }
+
+  __getValue(): number {
+    return this._a.__getValue() - this._b.__getValue();
+  }
+
+  interpolate(config: InterpolationConfigType): AnimatedInterpolation {
+    return new AnimatedInterpolation(this, config);
+  }
+
+  __attach(): void {
+    this._a.__addChild(this);
+    this._b.__addChild(this);
+  }
+
+  __detach(): void {
+    this._a.__removeChild(this);
+    this._b.__removeChild(this);
+    super.__detach();
+  }
+
+  __getNativeConfig(): any {
+    return {
+      type: 'subtraction',
+      input: [this._a.__getNativeTag(), this._b.__getNativeTag()],
+    };
+  }
+}
+
+module.exports = AnimatedSubtraction;
diff --git a/Libraries/NativeAnimation/Nodes/RCTSubtractionAnimatedNode.h b/Libraries/NativeAnimation/Nodes/RCTSubtractionAnimatedNode.h
new file mode 100644
index 000000000000..45524b69d025
--- /dev/null
+++ b/Libraries/NativeAnimation/Nodes/RCTSubtractionAnimatedNode.h
@@ -0,0 +1,13 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTValueAnimatedNode.h"
+
+@interface RCTSubtractionAnimatedNode : RCTValueAnimatedNode
+
+@end
+
diff --git a/Libraries/NativeAnimation/Nodes/RCTSubtractionAnimatedNode.m b/Libraries/NativeAnimation/Nodes/RCTSubtractionAnimatedNode.m
new file mode 100644
index 000000000000..91688c9aec51
--- /dev/null
+++ b/Libraries/NativeAnimation/Nodes/RCTSubtractionAnimatedNode.m
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTSubtractionAnimatedNode.h"
+
+@implementation RCTSubtractionAnimatedNode
+
+- (void)performUpdate
+{
+  [super performUpdate];
+  NSArray<NSNumber *> *inputNodes = self.config[@"input"];
+  if (inputNodes.count > 1) {
+    RCTValueAnimatedNode *parent1 = (RCTValueAnimatedNode *)[self.parentNodes objectForKey:inputNodes[0]];
+    RCTValueAnimatedNode *parent2 = (RCTValueAnimatedNode *)[self.parentNodes objectForKey:inputNodes[1]];
+    if ([parent1 isKindOfClass:[RCTValueAnimatedNode class]] &&
+        [parent2 isKindOfClass:[RCTValueAnimatedNode class]]) {
+      self.value = parent1.value - parent2.value;
+    }
+  }
+}
+
+@end
+
diff --git a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
index 0ba244627156..08a629eaecca 100644
--- a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
+++ b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
@@ -111,6 +111,7 @@
 		2D3B5EFE1D9B0B4800451313 /* RCTStyleAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E501E31D07A6C9005F35D8 /* RCTStyleAnimatedNode.m */; };
 		2D3B5EFF1D9B0B4800451313 /* RCTTransformAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E501E51D07A6C9005F35D8 /* RCTTransformAnimatedNode.m */; };
 		2D3B5F001D9B0B4800451313 /* RCTValueAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E501E71D07A6C9005F35D8 /* RCTValueAnimatedNode.m */; };
+		2EC00631206EA19300586E91 /* RCTSubtractionAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 2EC00630206EA19300586E91 /* RCTSubtractionAnimatedNode.m */; };
 		44DB7D942024F74200588FCD /* RCTTrackingAnimatedNode.h in Headers */ = {isa = PBXBuildFile; fileRef = 44DB7D932024F74200588FCD /* RCTTrackingAnimatedNode.h */; };
 		44DB7D952024F74200588FCD /* RCTTrackingAnimatedNode.h in Headers */ = {isa = PBXBuildFile; fileRef = 44DB7D932024F74200588FCD /* RCTTrackingAnimatedNode.h */; };
 		44DB7D972024F75100588FCD /* RCTTrackingAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 44DB7D962024F75100588FCD /* RCTTrackingAnimatedNode.m */; };
@@ -213,6 +214,8 @@
 		19F00F201DC8847500113FEE /* RCTEventAnimation.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; lineEnding = 0; path = RCTEventAnimation.h; sourceTree = "<group>"; xcLanguageSpecificationIdentifier = xcode.lang.objcpp; };
 		19F00F211DC8847500113FEE /* RCTEventAnimation.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTEventAnimation.m; sourceTree = "<group>"; };
 		2D2A28201D9B03D100D4039D /* libRCTAnimation.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libRCTAnimation.a; sourceTree = BUILT_PRODUCTS_DIR; };
+		2EC0062F206EA15F00586E91 /* RCTSubtractionAnimatedNode.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = RCTSubtractionAnimatedNode.h; sourceTree = "<group>"; };
+		2EC00630206EA19300586E91 /* RCTSubtractionAnimatedNode.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = RCTSubtractionAnimatedNode.m; sourceTree = "<group>"; };
 		44DB7D932024F74200588FCD /* RCTTrackingAnimatedNode.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = RCTTrackingAnimatedNode.h; sourceTree = "<group>"; };
 		44DB7D962024F75100588FCD /* RCTTrackingAnimatedNode.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = RCTTrackingAnimatedNode.m; sourceTree = "<group>"; };
 		5C9894931D999639008027DB /* RCTDivisionAnimatedNode.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; lineEnding = 0; path = RCTDivisionAnimatedNode.h; sourceTree = "<group>"; xcLanguageSpecificationIdentifier = xcode.lang.objcpp; };
@@ -246,6 +249,8 @@
 				193F64F31D776EC6004D1CAA /* RCTDiffClampAnimatedNode.m */,
 				13E501D61D07A6C9005F35D8 /* RCTAdditionAnimatedNode.h */,
 				13E501D71D07A6C9005F35D8 /* RCTAdditionAnimatedNode.m */,
+				2EC0062F206EA15F00586E91 /* RCTSubtractionAnimatedNode.h */,
+				2EC00630206EA19300586E91 /* RCTSubtractionAnimatedNode.m */,
 				13E501D81D07A6C9005F35D8 /* RCTAnimatedNode.h */,
 				13E501D91D07A6C9005F35D8 /* RCTAnimatedNode.m */,
 				13E501DC1D07A6C9005F35D8 /* RCTInterpolationAnimatedNode.h */,
@@ -483,6 +488,7 @@
 				5C9894951D999639008027DB /* RCTDivisionAnimatedNode.m in Sources */,
 				13E501EF1D07A6C9005F35D8 /* RCTTransformAnimatedNode.m in Sources */,
 				194804EE1E975D8E00623005 /* RCTDecayAnimation.m in Sources */,
+				2EC00631206EA19300586E91 /* RCTSubtractionAnimatedNode.m in Sources */,
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};
diff --git a/Libraries/NativeAnimation/RCTNativeAnimatedNodesManager.m b/Libraries/NativeAnimation/RCTNativeAnimatedNodesManager.m
index e05286decf9e..e649020d5f30 100644
--- a/Libraries/NativeAnimation/RCTNativeAnimatedNodesManager.m
+++ b/Libraries/NativeAnimation/RCTNativeAnimatedNodesManager.m
@@ -23,6 +23,7 @@
 #import "RCTPropsAnimatedNode.h"
 #import "RCTSpringAnimation.h"
 #import "RCTStyleAnimatedNode.h"
+#import "RCTSubtractionAnimatedNode.h"
 #import "RCTTransformAnimatedNode.h"
 #import "RCTValueAnimatedNode.h"
 #import "RCTTrackingAnimatedNode.h"
@@ -66,6 +67,7 @@ - (void)createAnimatedNode:(nonnull NSNumber *)tag
             @"division" : [RCTDivisionAnimatedNode class],
             @"multiplication" : [RCTMultiplicationAnimatedNode class],
             @"modulus" : [RCTModuloAnimatedNode class],
+            @"subtraction" : [RCTSubtractionAnimatedNode class],
             @"transform" : [RCTTransformAnimatedNode class],
             @"tracking" : [RCTTrackingAnimatedNode class]};
   });
diff --git a/RNTester/js/NativeAnimationsExample.js b/RNTester/js/NativeAnimationsExample.js
index 983b0c9d290f..5a6e5df55e84 100644
--- a/RNTester/js/NativeAnimationsExample.js
+++ b/RNTester/js/NativeAnimationsExample.js
@@ -429,6 +429,48 @@ exports.examples = [
       );
     },
   },
+  {
+    title: 'Multistage With Subtract',
+    render: function() {
+      return (
+        <Tester type="timing" config={{duration: 1000}}>
+          {anim => (
+            <Animated.View
+              style={[
+                styles.block,
+                {
+                  transform: [
+                    {
+                      translateX: anim.interpolate({
+                        inputRange: [0, 1],
+                        outputRange: [0, 200],
+                      }),
+                    },
+                    {
+                      translateY: anim.interpolate({
+                        inputRange: [0, 0.5, 1],
+                        outputRange: [0, 50, 0],
+                      }),
+                    },
+                  ],
+                  opacity: Animated.subtract(
+                    anim.interpolate({
+                      inputRange: [0, 1],
+                      outputRange: [1, 1],
+                    }),
+                    anim.interpolate({
+                      inputRange: [0, 0.5, 1],
+                      outputRange: [0, 0.5, 0],
+                    }),
+                  ),
+                },
+              ]}
+            />
+          )}
+        </Tester>
+      );
+    },
+  },
   {
     title: 'Scale interpolation with clamping',
     render: function() {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/animated/NativeAnimatedNodesManager.java b/ReactAndroid/src/main/java/com/facebook/react/animated/NativeAnimatedNodesManager.java
index 1fad4e52d3cd..07357fd7eea9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/animated/NativeAnimatedNodesManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/animated/NativeAnimatedNodesManager.java
@@ -93,6 +93,8 @@ public void createAnimatedNode(int tag, ReadableMap config) {
       node = new InterpolationAnimatedNode(config);
     } else if ("addition".equals(type)) {
       node = new AdditionAnimatedNode(config, this);
+    } else if ("subtraction".equals(type)) {
+      node = new SubtractionAnimatedNode(config, this);
     } else if ("division".equals(type)) {
       node = new DivisionAnimatedNode(config, this);
     } else if ("multiplication".equals(type)) {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/animated/SubtractionAnimatedNode.java b/ReactAndroid/src/main/java/com/facebook/react/animated/SubtractionAnimatedNode.java
new file mode 100644
index 000000000000..4a8ecd8ce736
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/animated/SubtractionAnimatedNode.java
@@ -0,0 +1,51 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.animated;
+
+import com.facebook.react.bridge.JSApplicationCausedNativeException;
+import com.facebook.react.bridge.ReadableArray;
+import com.facebook.react.bridge.ReadableMap;
+
+/**
+ * Animated node that plays a role of value aggregator. It takes two or more value nodes as an input
+ * and outputs a difference of values outputted by those nodes.
+ */
+/*package*/ class SubtractionAnimatedNode extends ValueAnimatedNode {
+
+  private final NativeAnimatedNodesManager mNativeAnimatedNodesManager;
+  private final int[] mInputNodes;
+
+  public SubtractionAnimatedNode(
+      ReadableMap config,
+      NativeAnimatedNodesManager nativeAnimatedNodesManager) {
+    mNativeAnimatedNodesManager = nativeAnimatedNodesManager;
+    ReadableArray inputNodes = config.getArray("input");
+    mInputNodes = new int[inputNodes.size()];
+    for (int i = 0; i < mInputNodes.length; i++) {
+      mInputNodes[i] = inputNodes.getInt(i);
+    }
+  }
+
+  @Override
+  public void update() {
+    for (int i = 0; i < mInputNodes.length; i++) {
+      AnimatedNode animatedNode = mNativeAnimatedNodesManager.getNodeById(mInputNodes[i]);
+      if (animatedNode != null && animatedNode instanceof ValueAnimatedNode) {
+        double value = ((ValueAnimatedNode) animatedNode).getValue();
+        if (i == 0) {
+          mValue = value;
+          continue;
+        }
+        mValue -= ((ValueAnimatedNode) animatedNode).getValue();
+      } else {
+        throw new JSApplicationCausedNativeException("Illegal node ID set as an input for " +
+          "Animated.subtract node");
+      }
+    }
+  }
+}

From d58ba8242b02b58ae2ac2c59fe3082d259c8c4db Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sat, 31 Mar 2018 23:20:52 -0700
Subject: [PATCH 0173/1109] Avoid app crashing when a StackOverflowError is
 thrown when rendering deep RN view hierarcy

Reviewed By: achen1

Differential Revision: D7400906

fbshipit-source-id: faaf701a88440f89390518f00e6a35f19e9203db
---
 .../com/facebook/react/views/view/ReactViewGroup.java     | 8 +++++++-
 1 file changed, 7 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index 3641d120dab3..1915b6eb48fb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -21,6 +21,7 @@
 import android.view.ViewGroup;
 import android.view.animation.Animation;
 import com.facebook.infer.annotation.Assertions;
+import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.common.annotations.VisibleForTesting;
 import com.facebook.react.modules.i18nmanager.I18nUtil;
 import com.facebook.react.touch.OnInterceptTouchEventListener;
@@ -668,7 +669,12 @@ protected void dispatchDraw(Canvas canvas) {
       if (rootView != null) {
         rootView.handleException(e);
       } else {
-        throw e;
+        if (getContext() instanceof  ReactContext) {
+          ReactContext reactContext = (ReactContext) getContext();
+          reactContext.handleException(new IllegalViewOperationException("StackOverflowException", this, e));
+        } else {
+          throw e;
+        }
       }
     }
   }

From aff5a75d8ee1e1ffe12406c1c0d741832455a6a3 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sun, 1 Apr 2018 18:27:04 -0700
Subject: [PATCH 0174/1109] Refactor cloning of YogaNode

Reviewed By: priteshrnandgaonkar

Differential Revision: D7339832

fbshipit-source-id: 2de6f47ae7601ac083d3b9fbe10ffaf6307ae760
---
 .../react/uimanager/ReactShadowNodeImpl.java  | 25 +++++----
 .../java/com/facebook/yoga/YogaConfig.java    | 15 +++---
 .../main/java/com/facebook/yoga/YogaNode.java | 14 +++++
 ...nction.java => YogaNodeCloneFunction.java} |  4 +-
 .../jni/first-party/yogajni/jni/YGJNI.cpp     | 54 +++++++++++--------
 .../view/yoga/YogaLayoutableShadowNode.cpp    |  2 +-
 ReactCommon/yoga/yoga/YGNode.cpp              | 13 +++--
 ReactCommon/yoga/yoga/Yoga-internal.h         |  2 +-
 ReactCommon/yoga/yoga/Yoga.cpp                | 16 +++---
 ReactCommon/yoga/yoga/Yoga.h                  |  7 ++-
 10 files changed, 94 insertions(+), 58 deletions(-)
 rename ReactAndroid/src/main/java/com/facebook/yoga/{YogaNodeClonedFunction.java => YogaNodeCloneFunction.java} (69%)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index e6b4a9012271..ebf8e6ae6393 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -10,6 +10,7 @@
 
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.uimanager.annotations.ReactPropertyHolder;
+import com.facebook.yoga.YogaNodeCloneFunction;
 import com.facebook.yoga.YogaAlign;
 import com.facebook.yoga.YogaBaselineFunction;
 import com.facebook.yoga.YogaConfig;
@@ -21,7 +22,6 @@
 import com.facebook.yoga.YogaJustify;
 import com.facebook.yoga.YogaMeasureFunction;
 import com.facebook.yoga.YogaNode;
-import com.facebook.yoga.YogaNodeClonedFunction;
 import com.facebook.yoga.YogaOverflow;
 import com.facebook.yoga.YogaPositionType;
 import com.facebook.yoga.YogaValue;
@@ -61,17 +61,19 @@ public class ReactShadowNodeImpl implements ReactShadowNode<ReactShadowNodeImpl>
   private static final YogaConfig sYogaConfig;
   static {
     sYogaConfig = ReactYogaConfigProvider.get();
-    sYogaConfig.setOnNodeCloned(new YogaNodeClonedFunction() {
+    sYogaConfig.setOnCloneNode(new YogaNodeCloneFunction() {
       @Override
-      public void onNodeCloned(YogaNode oldYogaNode,
-          YogaNode newYogaNode,
+      public YogaNode cloneNode(YogaNode oldYogaNode,
           YogaNode parent,
           int childIndex) {
-        ReactShadowNode parentReactShadowNode = (ReactShadowNode) parent.getData();
+        ReactShadowNodeImpl parentReactShadowNode = (ReactShadowNodeImpl) parent.getData();
         Assertions.assertNotNull(parentReactShadowNode);
-
-        ReactShadowNode newReactShadowNode = (ReactShadowNode) newYogaNode.getData();
+        ReactShadowNodeImpl newReactShadowNode = (ReactShadowNodeImpl) oldYogaNode.getData();
         Assertions.assertNotNull(newReactShadowNode);
+
+        ReactShadowNodeImpl newNode = newReactShadowNode.mutableCopy();
+        parentReactShadowNode.replaceChild(newNode, childIndex);
+        return newNode.mYogaNode;
       }
     });
   }
@@ -133,6 +135,11 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     mOriginalReactShadowNode = original;
   }
 
+  private void replaceChild(ReactShadowNodeImpl newNode, int childIndex) {
+    mChildren.remove(childIndex);
+    mChildren.add(childIndex, newNode);
+  }
+
   /**
    * @return a copy of this object (no including copy of its children or the underlying yogaNode).
    */
@@ -145,7 +152,7 @@ public ReactShadowNodeImpl mutableCopy() {
     ReactShadowNodeImpl copy = copy();
     copy.mYogaNode = mYogaNode;
     // TODO: T26729293 clone YogaNode instead of reusing the same instance
-    //mYogaNode = original.mYogaNode.clone();
+    //copy.mYogaNode = mYogaNode.clone();
     copy.mNativeChildren = mNativeChildren == null ? null : new ArrayList<>(mNativeChildren);
     copy.mTotalNativeChildren = mTotalNativeChildren;
     copy.mChildren = mChildren == null ? null : new ArrayList<>(mChildren);
@@ -165,7 +172,7 @@ public ReactShadowNodeImpl mutableCopyWithNewChildren() {
     ReactShadowNodeImpl copy = copy();
     copy.mYogaNode = mYogaNode;
     // TODO: T26729293 clone YogaNode instead of reusing the same instance
-    //mYogaNode = original.mYogaNode.cloneWithNewChildren();
+    //copy.mYogaNode = mYogaNode.clone();
     copy.mNativeChildren = null;
     copy.mChildren = null;
     copy.mTotalNativeChildren = 0;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
index 2d90eec9de9d..ebb64aaff5a8 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
@@ -25,7 +25,7 @@ public class YogaConfig {
 
   long mNativePointer;
   private YogaLogger mLogger;
-  private YogaNodeClonedFunction mNodeClonedFunction;
+  private YogaNodeCloneFunction mYogaNodeCloneFunction;
 
   private native long jni_YGConfigNew();
   public YogaConfig() {
@@ -97,16 +97,15 @@ public YogaLogger getLogger() {
     return mLogger;
   }
 
-  private native void jni_YGConfigSetHasNodeClonedFunc(long nativePointer, boolean hasClonedFunc);
+  private native void jni_YGConfigSetHasCloneNodeFunc(long nativePointer, boolean hasClonedFunc);
 
-  public void setOnNodeCloned(YogaNodeClonedFunction nodeClonedFunction) {
-    mNodeClonedFunction = nodeClonedFunction;
-    jni_YGConfigSetHasNodeClonedFunc(mNativePointer, nodeClonedFunction != null);
+  public void setOnCloneNode(YogaNodeCloneFunction cloneYogaNodeFunction) {
+    mYogaNodeCloneFunction = cloneYogaNodeFunction;
+    jni_YGConfigSetHasCloneNodeFunc(mNativePointer, cloneYogaNodeFunction != null);
   }
 
   @DoNotStrip
-  public final void onNodeCloned(
-      YogaNode oldNode, YogaNode newNode, YogaNode parent, int childIndex) {
-    mNodeClonedFunction.onNodeCloned(oldNode, newNode, parent, childIndex);
+  private final YogaNode cloneNode(YogaNode oldNode, YogaNode parent, int childIndex) {
+    return mYogaNodeCloneFunction.cloneNode(oldNode, parent, childIndex);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index 1c6e67a55eb9..577ee3fb05cd 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -697,4 +697,18 @@ public Object getData() {
   public void print() {
     jni_YGNodePrint(mNativePointer);
   }
+
+  /**
+   * This method replaces the child at childIndex position with the newNode received by parameter.
+   * This is different than calling removeChildAt and addChildAt because this method ONLY replaces
+   * the child in the mChildren datastructure. @DoNotStrip: called from JNI
+   *
+   * @return the nativePointer of the newNode {@linl YogaNode}
+   */
+  @DoNotStrip
+  private final long replaceChild(YogaNode newNode, int childIndex) {
+    mChildren.remove(childIndex);
+    mChildren.add(childIndex, newNode);
+    return newNode.mNativePointer;
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeClonedFunction.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeCloneFunction.java
similarity index 69%
rename from ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeClonedFunction.java
rename to ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeCloneFunction.java
index f469546495f8..0733776a7e37 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeClonedFunction.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeCloneFunction.java
@@ -10,8 +10,8 @@
 import com.facebook.proguard.annotations.DoNotStrip;
 
 @DoNotStrip
-public interface YogaNodeClonedFunction {
+public interface YogaNodeCloneFunction {
 
   @DoNotStrip
-  void onNodeCloned(YogaNode oldNode, YogaNode newNode, YogaNode parent, int childIndex);
+  YogaNode cloneNode(YogaNode oldNode, YogaNode parent, int childIndex);
 }
diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
index cc75df96a151..7f92ba8e06df 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
@@ -142,31 +142,49 @@ static float YGJNIBaselineFunc(YGNodeRef node, float width, float height) {
   }
 }
 
-static void YGJNIOnNodeClonedFunc(
+static inline YGNodeRef _jlong2YGNodeRef(jlong addr) {
+  return reinterpret_cast<YGNodeRef>(static_cast<intptr_t>(addr));
+}
+
+static inline YGConfigRef _jlong2YGConfigRef(jlong addr) {
+  return reinterpret_cast<YGConfigRef>(static_cast<intptr_t>(addr));
+}
+
+static YGNodeRef YGJNIOnNodeClonedFunc(
     YGNodeRef oldNode,
-    YGNodeRef newNode,
     YGNodeRef parent,
     int childIndex) {
   auto config = oldNode->getConfig();
   if (!config) {
-    return;
+    return nullptr;
   }
+
   static auto onNodeClonedFunc = findClassStatic("com/facebook/yoga/YogaConfig")
-                                     ->getMethod<void(
+                                     ->getMethod<alias_ref<JYogaNode>(
                                          local_ref<JYogaNode>,
                                          local_ref<JYogaNode>,
-                                         local_ref<JYogaNode>,
-                                         jint)>("onNodeCloned");
+                                         jint)>("cloneNode");
 
   auto context = reinterpret_cast<YGConfigContext*>(YGConfigGetContext(config));
   auto javaConfig = context->config;
 
-  onNodeClonedFunc(
+  auto newNode = onNodeClonedFunc(
       javaConfig->get(),
       YGNodeJobject(oldNode)->lockLocal(),
-      YGNodeJobject(newNode)->lockLocal(),
       YGNodeJobject(parent)->lockLocal(),
       childIndex);
+
+  static auto replaceChild = findClassStatic("com/facebook/yoga/YogaNode")
+                                     ->getMethod<jlong(
+                                         local_ref<JYogaNode>,
+                                         jint)>("replaceChild");
+
+  jlong newNodeNativePointer = replaceChild(
+      YGNodeJobject(parent)->lockLocal(),
+      newNode,
+      childIndex);
+
+  return _jlong2YGNodeRef(newNodeNativePointer);
 }
 
 static YGSize YGJNIMeasureFunc(
@@ -234,14 +252,6 @@ static int YGJNILogFunc(const YGConfigRef config,
   return result;
 }
 
-static inline YGNodeRef _jlong2YGNodeRef(jlong addr) {
-  return reinterpret_cast<YGNodeRef>(static_cast<intptr_t>(addr));
-}
-
-static inline YGConfigRef _jlong2YGConfigRef(jlong addr) {
-  return reinterpret_cast<YGConfigRef>(static_cast<intptr_t>(addr));
-}
-
 jlong jni_YGNodeNew(alias_ref<jobject> thiz) {
   const YGNodeRef node = YGNodeNew();
   node->setContext(new weak_ref<jobject>(make_weak(thiz)));
@@ -506,10 +516,10 @@ void jni_YGConfigSetUseLegacyStretchBehaviour(alias_ref<jobject>,
   YGConfigSetUseLegacyStretchBehaviour(config, useLegacyStretchBehaviour);
 }
 
-void jni_YGConfigSetHasNodeClonedFunc(
+void jni_YGConfigSetHasCloneNodeFunc(
     alias_ref<jobject> thiz,
     jlong nativePointer,
-    jboolean hasNodeClonedFunc) {
+    jboolean hasCloneNodeFunc) {
   const YGConfigRef config = _jlong2YGConfigRef(nativePointer);
   auto context = reinterpret_cast<YGConfigContext*>(YGConfigGetContext(config));
   if (context && context->config) {
@@ -517,15 +527,15 @@ void jni_YGConfigSetHasNodeClonedFunc(
     context->config = nullptr;
   }
 
-  if (hasNodeClonedFunc) {
+  if (hasCloneNodeFunc) {
     if (!context) {
       context = new YGConfigContext();
       YGConfigSetContext(config, context);
     }
     context->config = new global_ref<jobject>(make_global(thiz));
-    YGConfigSetNodeClonedFunc(config, YGJNIOnNodeClonedFunc);
+    YGConfigSetCloneNodeFunc(config, YGJNIOnNodeClonedFunc);
   } else {
-    YGConfigSetNodeClonedFunc(config, nullptr);
+    YGConfigSetCloneNodeFunc(config, nullptr);
   }
 }
 
@@ -652,7 +662,7 @@ jint JNI_OnLoad(JavaVM *vm, void *) {
             YGMakeNativeMethod(jni_YGConfigSetPointScaleFactor),
             YGMakeNativeMethod(jni_YGConfigSetUseLegacyStretchBehaviour),
             YGMakeNativeMethod(jni_YGConfigSetLogger),
-            YGMakeNativeMethod(jni_YGConfigSetHasNodeClonedFunc),
+            YGMakeNativeMethod(jni_YGConfigSetHasCloneNodeFunc),
             YGMakeNativeMethod(
                 jni_YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour),
         });
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index d7974ae0fed3..60586c9249e5 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -24,7 +24,7 @@ SharedYogaConfig YogaLayoutableShadowNode::suitableYogaConfig() {
 
   if (!sharedYogaConfig) {
     sharedYogaConfig = std::make_shared<YGConfig>(YGConfig({
-      .cloneNodeCallback = YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector
+      // .cloneNodeCallback = YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector
     }));
   }
 
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 8fcb44c39dcb..f15105f26fe9 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -558,15 +558,18 @@ void YGNode::cloneChildrenIfNeeded() {
     return;
   }
 
-  const YGNodeClonedFunc cloneNodeCallback = config_->cloneNodeCallback;
+  const YGCloneNodeFunc cloneNodeCallback = config_->cloneNodeCallback;
   for (uint32_t i = 0; i < childCount; ++i) {
     const YGNodeRef oldChild = children_[i];
-    const YGNodeRef newChild = YGNodeClone(oldChild);
-    replaceChild(newChild, i);
-    newChild->setParent(this);
+    YGNodeRef newChild = nullptr;
     if (cloneNodeCallback) {
-      cloneNodeCallback(oldChild, newChild, this, i);
+      newChild = cloneNodeCallback(oldChild, this, i);
+    }
+    if (newChild == nullptr) {
+      newChild = YGNodeClone(oldChild);
     }
+    replaceChild(newChild, i);
+    newChild->setParent(this);
   }
 }
 
diff --git a/ReactCommon/yoga/yoga/Yoga-internal.h b/ReactCommon/yoga/yoga/Yoga-internal.h
index 56078d6c3f06..d11f8c29d938 100644
--- a/ReactCommon/yoga/yoga/Yoga-internal.h
+++ b/ReactCommon/yoga/yoga/Yoga-internal.h
@@ -94,7 +94,7 @@ struct YGConfig {
   bool shouldDiffLayoutWithoutLegacyStretchBehaviour;
   float pointScaleFactor;
   YGLogger logger;
-  YGNodeClonedFunc cloneNodeCallback;
+  YGCloneNodeFunc cloneNodeCallback;
   void* context;
 };
 
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 1600b1b05fa0..b597727bc4ce 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -428,7 +428,7 @@ void YGNodeRemoveChild(const YGNodeRef parent, const YGNodeRef excludedChild) {
   // Otherwise we have to clone the node list except for the child we're trying to delete.
   // We don't want to simply clone all children, because then the host will need to free
   // the clone of the child that was just deleted.
-  const YGNodeClonedFunc cloneNodeCallback =
+  const YGCloneNodeFunc cloneNodeCallback =
       parent->getConfig()->cloneNodeCallback;
   uint32_t nextInsertIndex = 0;
   for (uint32_t i = 0; i < childCount; i++) {
@@ -440,12 +440,16 @@ void YGNodeRemoveChild(const YGNodeRef parent, const YGNodeRef excludedChild) {
       parent->markDirtyAndPropogate();
       continue;
     }
-    const YGNodeRef newChild = YGNodeClone(oldChild);
-    parent->replaceChild(newChild, nextInsertIndex);
-    newChild->setParent(parent);
+    YGNodeRef newChild = nullptr;
     if (cloneNodeCallback) {
-      cloneNodeCallback(oldChild, newChild, parent, nextInsertIndex);
+      newChild = cloneNodeCallback(oldChild, parent, nextInsertIndex);
+    }
+    if (newChild == nullptr) {
+      newChild = YGNodeClone(oldChild);
     }
+    parent->replaceChild(newChild, nextInsertIndex);
+    newChild->setParent(parent);
+
     nextInsertIndex++;
   }
   while (nextInsertIndex < childCount) {
@@ -3964,7 +3968,7 @@ void *YGConfigGetContext(const YGConfigRef config) {
   return config->context;
 }
 
-void YGConfigSetNodeClonedFunc(const YGConfigRef config, const YGNodeClonedFunc callback) {
+void YGConfigSetCloneNodeFunc(const YGConfigRef config, const YGCloneNodeFunc callback) {
   config->cloneNodeCallback = callback;
 }
 
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index 1a985fa56317..73e7c7fdb1a2 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -62,8 +62,7 @@ typedef int (*YGLogger)(const YGConfigRef config,
                         YGLogLevel level,
                         const char *format,
                         va_list args);
-typedef void (*YGNodeClonedFunc)(YGNodeRef oldNode,
-                                 YGNodeRef newNode,
+typedef YGNodeRef (*YGCloneNodeFunc)(YGNodeRef oldNode,
                                  YGNodeRef parent,
                                  int childIndex);
 
@@ -283,8 +282,8 @@ WIN_EXPORT bool YGConfigIsExperimentalFeatureEnabled(const YGConfigRef config,
 WIN_EXPORT void YGConfigSetUseWebDefaults(const YGConfigRef config, const bool enabled);
 WIN_EXPORT bool YGConfigGetUseWebDefaults(const YGConfigRef config);
 
-WIN_EXPORT void YGConfigSetNodeClonedFunc(const YGConfigRef config,
-                                          const YGNodeClonedFunc callback);
+WIN_EXPORT void YGConfigSetCloneNodeFunc(const YGConfigRef config,
+                                          const YGCloneNodeFunc callback);
 
 // Export only for C#
 WIN_EXPORT YGConfigRef YGConfigGetDefault(void);

From 29ff30c539469bf2928fe90bdc31d1c3b2c19356 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sun, 1 Apr 2018 18:27:06 -0700
Subject: [PATCH 0175/1109] Rename YogaNode.parent -> YogaNode.owner

Reviewed By: priteshrnandgaonkar

Differential Revision: D7352778

fbshipit-source-id: dcf1af5e72bfc3063b5c4bda197d7952a9194768
---
 .../react/uimanager/ReactShadowNodeImpl.java  |   2 +-
 .../main/java/com/facebook/yoga/YogaNode.java |  20 +-
 .../jni/first-party/yogajni/jni/YGJNI.cpp     |   6 +-
 .../view/yoga/YogaLayoutableShadowNode.cpp    |   2 +-
 ReactCommon/yoga/yoga/Utils.h                 |  10 +-
 ReactCommon/yoga/yoga/YGLayout.cpp            |   4 +-
 ReactCommon/yoga/yoga/YGLayout.h              |   2 +-
 ReactCommon/yoga/yoga/YGNode.cpp              |  54 +--
 ReactCommon/yoga/yoga/YGNode.h                |  19 +-
 ReactCommon/yoga/yoga/Yoga.cpp                | 458 +++++++++---------
 ReactCommon/yoga/yoga/Yoga.h                  |   4 +-
 11 files changed, 297 insertions(+), 284 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index ebf8e6ae6393..53a27c440b76 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -301,7 +301,7 @@ public void addChildAt(ReactShadowNodeImpl child, int i) {
                 + "')");
       }
       // TODO: T26729293 This is a temporary code that will be replaced as part of T26729293.
-      YogaNode parent = childYogaNode.getParent();
+      YogaNode parent = childYogaNode.getOwner();
       if (parent != null) {
         for (int k = 0; k < parent.getChildCount(); k++) {
           if (parent.getChildAt(k) == childYogaNode) {
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index 577ee3fb05cd..ae5165e63844 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -29,7 +29,7 @@ public class YogaNode implements Cloneable {
    */
   static native int jni_YGNodeGetInstanceCount();
 
-  private YogaNode mParent;
+  private YogaNode mOwner;
   private List<YogaNode> mChildren;
   private YogaMeasureFunction mMeasureFunction;
   private YogaBaselineFunction mBaselineFunction;
@@ -152,7 +152,7 @@ public YogaNode getChildAt(int i) {
 
   private native void jni_YGNodeInsertChild(long nativePointer, long childPointer, int index);
   public void addChildAt(YogaNode child, int i) {
-    if (child.mParent != null) {
+    if (child.mOwner != null) {
       throw new IllegalStateException("Child already has a parent, it must be removed first.");
     }
 
@@ -160,7 +160,7 @@ public void addChildAt(YogaNode child, int i) {
       mChildren = new ArrayList<>(4);
     }
     mChildren.add(i, child);
-    child.mParent = this;
+    child.mOwner = this;
     jni_YGNodeInsertChild(mNativePointer, child.mNativePointer, i);
   }
 
@@ -180,15 +180,23 @@ public YogaNode clone() throws CloneNotSupportedException {
   public YogaNode removeChildAt(int i) {
 
     final YogaNode child = mChildren.remove(i);
-    child.mParent = null;
+    child.mOwner = null;
     jni_YGNodeRemoveChild(mNativePointer, child.mNativePointer);
     return child;
   }
 
+  /**
+   * @returns the {@link YogaNode} that owns this {@link YogaNode}.
+   * The owner is used to identify the YogaTree that a {@link YogaNode} belongs
+   * to.
+   * This method will return the parent of the {@link YogaNode} when the
+   * {@link YogaNode} only belongs to one YogaTree or null when the
+   * {@link YogaNode} is shared between two or more YogaTrees.
+   */
   @Nullable
   public
-  YogaNode getParent() {
-    return mParent;
+  YogaNode getOwner() {
+    return mOwner;
   }
 
   public int indexOf(YogaNode child) {
diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
index 7f92ba8e06df..b303ce223a92 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
@@ -152,7 +152,7 @@ static inline YGConfigRef _jlong2YGConfigRef(jlong addr) {
 
 static YGNodeRef YGJNIOnNodeClonedFunc(
     YGNodeRef oldNode,
-    YGNodeRef parent,
+    YGNodeRef owner,
     int childIndex) {
   auto config = oldNode->getConfig();
   if (!config) {
@@ -171,7 +171,7 @@ static YGNodeRef YGJNIOnNodeClonedFunc(
   auto newNode = onNodeClonedFunc(
       javaConfig->get(),
       YGNodeJobject(oldNode)->lockLocal(),
-      YGNodeJobject(parent)->lockLocal(),
+      YGNodeJobject(owner)->lockLocal(),
       childIndex);
 
   static auto replaceChild = findClassStatic("com/facebook/yoga/YogaNode")
@@ -180,7 +180,7 @@ static YGNodeRef YGJNIOnNodeClonedFunc(
                                          jint)>("replaceChild");
 
   jlong newNodeNativePointer = replaceChild(
-      YGNodeJobject(parent)->lockLocal(),
+      YGNodeJobject(owner)->lockLocal(),
       newNode,
       childIndex);
 
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 60586c9249e5..6ad453100e8f 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -54,7 +54,7 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
 ) {
   auto yogaNode = std::make_shared<YGNode>(*shadowNode->yogaNode_);
   yogaNode->setContext(this);
-  yogaNode->setParent(nullptr);
+  yogaNode->setOwner(nullptr);
 
   if (props) {
     yogaNode->setStyle(props->getYogaStyle());
diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index 7190fd7ff249..34284d2c3513 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -45,7 +45,7 @@ struct YGCollectFlexItemsRowValues {
   float remainingFreeSpace;
   // The size of the mainDim for the row after considering size, padding, margin
   // and border of flex items. This is used to calculate maxLineDim after going
-  // through all the rows to decide on the main axis size of parent.
+  // through all the rows to decide on the main axis size of owner.
   float mainDim;
   // The size of the crossDim for the row after considering size, padding,
   // margin and border of flex items. Used for calculating containers crossSize.
@@ -109,7 +109,7 @@ inline bool YGFlexDirectionIsRow(const YGFlexDirection flexDirection) {
       flexDirection == YGFlexDirectionRowReverse;
 }
 
-inline YGFloatOptional YGResolveValue(const YGValue value, const float parentSize) {
+inline YGFloatOptional YGResolveValue(const YGValue value, const float ownerSize) {
   switch (value.unit) {
     case YGUnitUndefined:
     case YGUnitAuto:
@@ -118,7 +118,7 @@ inline YGFloatOptional YGResolveValue(const YGValue value, const float parentSiz
       return YGFloatOptional(value.value);
     case YGUnitPercent:
       return YGFloatOptional(
-          static_cast<float>(value.value * parentSize * 0.01));
+          static_cast<float>(value.value * ownerSize * 0.01));
   }
   return YGFloatOptional();
 }
@@ -144,6 +144,6 @@ inline YGFlexDirection YGResolveFlexDirection(
 
 static inline float YGResolveValueMargin(
     const YGValue value,
-    const float parentSize) {
-  return value.unit == YGUnitAuto ? 0 : YGUnwrapFloatOptional(YGResolveValue(value, parentSize));
+    const float ownerSize) {
+  return value.unit == YGUnitAuto ? 0 : YGUnwrapFloatOptional(YGResolveValue(value, ownerSize));
 }
diff --git a/ReactCommon/yoga/yoga/YGLayout.cpp b/ReactCommon/yoga/yoga/YGLayout.cpp
index 4d798476ab18..117638d7a15f 100644
--- a/ReactCommon/yoga/yoga/YGLayout.cpp
+++ b/ReactCommon/yoga/yoga/YGLayout.cpp
@@ -22,7 +22,7 @@ YGLayout::YGLayout()
       computedFlexBasis(YGUndefined),
       hadOverflow(false),
       generationCount(0),
-      lastParentDirection((YGDirection)-1),
+      lastOwnerDirection((YGDirection)-1),
       nextCachedMeasurementsIndex(0),
       cachedMeasurements(),
       measuredDimensions(kYGDefaultDimensionValues),
@@ -37,7 +37,7 @@ bool YGLayout::operator==(YGLayout layout) const {
       YGFloatArrayEqual(border, layout.border) &&
       YGFloatArrayEqual(padding, layout.padding) &&
       direction == layout.direction && hadOverflow == layout.hadOverflow &&
-      lastParentDirection == layout.lastParentDirection &&
+      lastOwnerDirection == layout.lastOwnerDirection &&
       nextCachedMeasurementsIndex == layout.nextCachedMeasurementsIndex &&
       cachedLayout == layout.cachedLayout;
 
diff --git a/ReactCommon/yoga/yoga/YGLayout.h b/ReactCommon/yoga/yoga/YGLayout.h
index cfe559f64bc1..81cc66317a5a 100644
--- a/ReactCommon/yoga/yoga/YGLayout.h
+++ b/ReactCommon/yoga/yoga/YGLayout.h
@@ -23,7 +23,7 @@ struct YGLayout {
   // Instead of recomputing the entire layout every single time, we
   // cache some information to break early when nothing changed
   uint32_t generationCount;
-  YGDirection lastParentDirection;
+  YGDirection lastOwnerDirection;
 
   uint32_t nextCachedMeasurementsIndex;
   std::array<YGCachedMeasurement, YG_MAX_CACHED_RESULT_COUNT>
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index f15105f26fe9..01be3a7c0328 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -49,8 +49,8 @@ uint32_t YGNode::getLineIndex() const {
   return lineIndex_;
 }
 
-YGNodeRef YGNode::getParent() const {
-  return parent_;
+YGNodeRef YGNode::getOwner() const {
+  return owner_;
 }
 
 YGVector YGNode::getChildren() const {
@@ -237,8 +237,8 @@ void YGNode::setLineIndex(uint32_t lineIndex) {
   lineIndex_ = lineIndex;
 }
 
-void YGNode::setParent(YGNodeRef parent) {
-  parent_ = parent;
+void YGNode::setOwner(YGNodeRef owner) {
+  owner_ = owner;
 }
 
 void YGNode::setChildren(const YGVector& children) {
@@ -305,8 +305,8 @@ void YGNode::setLayoutPadding(float padding, int index) {
   layout_.padding[index] = padding;
 }
 
-void YGNode::setLayoutLastParentDirection(YGDirection direction) {
-  layout_.lastParentDirection = direction;
+void YGNode::setLayoutLastOwnerDirection(YGDirection direction) {
+  layout_.lastOwnerDirection = direction;
 }
 
 void YGNode::setLayoutComputedFlexBasis(float computedFlexBasis) {
@@ -347,11 +347,11 @@ void YGNode::setPosition(
     const YGDirection direction,
     const float mainSize,
     const float crossSize,
-    const float parentWidth) {
+    const float ownerWidth) {
   /* Root nodes should be always layouted as LTR, so we don't return negative
    * values. */
   const YGDirection directionRespectingRoot =
-      parent_ != nullptr ? direction : YGDirectionLTR;
+      owner_ != nullptr ? direction : YGDirectionLTR;
   const YGFlexDirection mainAxis =
       YGResolveFlexDirection(style_.flexDirection, directionRespectingRoot);
   const YGFlexDirection crossAxis =
@@ -361,16 +361,16 @@ void YGNode::setPosition(
   const float relativePositionCross = relativePosition(crossAxis, crossSize);
 
   setLayoutPosition(
-      getLeadingMargin(mainAxis, parentWidth) + relativePositionMain,
+      getLeadingMargin(mainAxis, ownerWidth) + relativePositionMain,
       leading[mainAxis]);
   setLayoutPosition(
-      getTrailingMargin(mainAxis, parentWidth) + relativePositionMain,
+      getTrailingMargin(mainAxis, ownerWidth) + relativePositionMain,
       trailing[mainAxis]);
   setLayoutPosition(
-      getLeadingMargin(crossAxis, parentWidth) + relativePositionCross,
+      getLeadingMargin(crossAxis, ownerWidth) + relativePositionCross,
       leading[crossAxis]);
   setLayoutPosition(
-      getTrailingMargin(crossAxis, parentWidth) + relativePositionCross,
+      getTrailingMargin(crossAxis, ownerWidth) + relativePositionCross,
       trailing[crossAxis]);
 }
 
@@ -385,7 +385,7 @@ YGNode::YGNode()
       style_(YGStyle()),
       layout_(YGLayout()),
       lineIndex_(0),
-      parent_(nullptr),
+      owner_(nullptr),
       children_(YGVector()),
       nextChild_(nullptr),
       config_(nullptr),
@@ -403,7 +403,7 @@ YGNode::YGNode(const YGNode& node)
       style_(node.style_),
       layout_(node.layout_),
       lineIndex_(node.lineIndex_),
-      parent_(node.parent_),
+      owner_(node.owner_),
       children_(node.children_),
       nextChild_(node.nextChild_),
       config_(node.config_),
@@ -425,7 +425,7 @@ YGNode::YGNode(
     YGStyle style,
     const YGLayout& layout,
     uint32_t lineIndex,
-    YGNodeRef parent,
+    YGNodeRef owner,
     const YGVector& children,
     YGNodeRef nextChild,
     YGConfigRef config,
@@ -441,7 +441,7 @@ YGNode::YGNode(
       style_(style),
       layout_(layout),
       lineIndex_(lineIndex),
-      parent_(parent),
+      owner_(owner),
       children_(children),
       nextChild_(nextChild),
       config_(config),
@@ -467,7 +467,7 @@ YGNode& YGNode::operator=(const YGNode& node) {
   style_ = node.style_;
   layout_ = node.layout_;
   lineIndex_ = node.getLineIndex();
-  parent_ = node.getParent();
+  owner_ = node.getOwner();
   children_ = node.getChildren();
   nextChild_ = node.getNextChild();
   config_ = node.getConfig();
@@ -518,9 +518,9 @@ void YGNode::resolveDimension() {
   }
 }
 
-YGDirection YGNode::resolveDirection(const YGDirection parentDirection) {
+YGDirection YGNode::resolveDirection(const YGDirection ownerDirection) {
   if (style_.direction == YGDirectionInherit) {
-    return parentDirection > YGDirectionInherit ? parentDirection
+    return ownerDirection > YGDirectionInherit ? ownerDirection
                                                 : YGDirectionLTR;
   } else {
     return style_.direction;
@@ -550,10 +550,10 @@ void YGNode::cloneChildrenIfNeeded() {
   }
 
   const YGNodeRef firstChild = children_.front();
-  if (firstChild->getParent() == this) {
-    // If the first child has this node as its parent, we assume that it is
+  if (firstChild->getOwner() == this) {
+    // If the first child has this node as its owner, we assume that it is
     // already unique. We can do this because if we have it has a child, that
-    // means that its parent was at some point cloned which made that subtree
+    // means that its owner was at some point cloned which made that subtree
     // immutable. We also assume that all its sibling are cloned as well.
     return;
   }
@@ -569,7 +569,7 @@ void YGNode::cloneChildrenIfNeeded() {
       newChild = YGNodeClone(oldChild);
     }
     replaceChild(newChild, i);
-    newChild->setParent(this);
+    newChild->setOwner(this);
   }
 }
 
@@ -577,8 +577,8 @@ void YGNode::markDirtyAndPropogate() {
   if (!isDirty_) {
     setDirty(true);
     setLayoutComputedFlexBasis(YGUndefined);
-    if (parent_) {
-      parent_->markDirtyAndPropogate();
+    if (owner_) {
+      owner_->markDirtyAndPropogate();
     }
   }
 }
@@ -592,7 +592,7 @@ void YGNode::markDirtyAndPropogateDownwards() {
 
 float YGNode::resolveFlexGrow() {
   // Root nodes flexGrow should always be 0
-  if (parent_ == nullptr) {
+  if (owner_ == nullptr) {
     return 0.0;
   }
   if (!style_.flexGrow.isUndefined()) {
@@ -605,7 +605,7 @@ float YGNode::resolveFlexGrow() {
 }
 
 float YGNode::resolveFlexShrink() {
-  if (parent_ == nullptr) {
+  if (owner_ == nullptr) {
     return 0.0;
   }
   if (!style_.flexShrink.isUndefined()) {
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 0ed05d7e5521..02afb830e8b4 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -23,7 +23,7 @@ struct YGNode {
   YGStyle style_;
   YGLayout layout_;
   uint32_t lineIndex_;
-  YGNodeRef parent_;
+  YGNodeRef owner_;
   YGVector children_;
   YGNodeRef nextChild_;
   YGConfigRef config_;
@@ -49,7 +49,7 @@ struct YGNode {
       YGStyle style,
       const YGLayout& layout,
       uint32_t lineIndex,
-      YGNodeRef parent,
+      YGNodeRef owner,
       const YGVector& children,
       YGNodeRef nextChild,
       YGConfigRef config,
@@ -69,7 +69,12 @@ struct YGNode {
   // For Performance reasons passing as reference.
   YGLayout& getLayout();
   uint32_t getLineIndex() const;
-  YGNodeRef getParent() const;
+  // returns the YGNodeRef that owns this YGNode. An owner is used to identify
+  // the YogaTree that a YGNode belongs to.
+  // This method will return the parent of the YGNode when a YGNode only belongs
+  // to one YogaTree or nullptr when the YGNode is shared between two or more
+  // YogaTrees.
+  YGNodeRef getOwner() const;
   YGVector getChildren() const;
   uint32_t getChildrenCount() const;
   YGNodeRef getChild(uint32_t index) const;
@@ -111,12 +116,12 @@ struct YGNode {
   void setStyleAlignContent(YGAlign alignContent);
   void setLayout(const YGLayout& layout);
   void setLineIndex(uint32_t lineIndex);
-  void setParent(YGNodeRef parent);
+  void setOwner(YGNodeRef owner);
   void setChildren(const YGVector& children);
   void setNextChild(YGNodeRef nextChild);
   void setConfig(YGConfigRef config);
   void setDirty(bool isDirty);
-  void setLayoutLastParentDirection(YGDirection direction);
+  void setLayoutLastOwnerDirection(YGDirection direction);
   void setLayoutComputedFlexBasis(float computedFlexBasis);
   void setLayoutComputedFlexBasisGeneration(
       uint32_t computedFlexBasisGeneration);
@@ -132,7 +137,7 @@ struct YGNode {
       const YGDirection direction,
       const float mainSize,
       const float crossSize,
-      const float parentWidth);
+      const float ownerWidth);
   void setAndPropogateUseLegacyFlag(bool useLegacyFlag);
   void setLayoutDoesLegacyFlagAffectsLayout(bool doesLegacyFlagAffectsLayout);
   void setLayoutDidUseLegacyFlag(bool didUseLegacyFlag);
@@ -143,7 +148,7 @@ struct YGNode {
   YGValue marginTrailingValue(const YGFlexDirection axis) const;
   YGValue resolveFlexBasisPtr() const;
   void resolveDimension();
-  YGDirection resolveDirection(const YGDirection parentDirection);
+  YGDirection resolveDirection(const YGDirection ownerDirection);
   void clearChildren();
   /// Replaces the occurrences of oldChild with newChild
   void replaceChild(YGNodeRef oldChild, YGNodeRef newChild);
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index b597727bc4ce..2e5979a2dd0f 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -257,7 +257,7 @@ YGNodeRef YGNodeClone(YGNodeRef oldNode) {
       node != nullptr,
       "Could not allocate memory for node");
   gNodeInstanceCount++;
-  node->setParent(nullptr);
+  node->setOwner(nullptr);
   return node;
 }
 
@@ -278,7 +278,7 @@ static YGNodeRef YGNodeDeepClone(YGNodeRef oldNode) {
   YGNodeRef childNode = nullptr;
   for (auto& item : oldNode->getChildren()) {
     childNode = YGNodeDeepClone(item);
-    childNode->setParent(node);
+    childNode->setOwner(node);
     vec.push_back(childNode);
   }
   node->setChildren(vec);
@@ -295,15 +295,15 @@ static YGNodeRef YGNodeDeepClone(YGNodeRef oldNode) {
 }
 
 void YGNodeFree(const YGNodeRef node) {
-  if (YGNodeRef parent = node->getParent()) {
-    parent->removeChild(node);
-    node->setParent(nullptr);
+  if (YGNodeRef owner = node->getOwner()) {
+    owner->removeChild(node);
+    node->setOwner(nullptr);
   }
 
   const uint32_t childCount = YGNodeGetChildCount(node);
   for (uint32_t i = 0; i < childCount; i++) {
     const YGNodeRef child = YGNodeGetChild(node, i);
-    child->setParent(nullptr);
+    child->setOwner(nullptr);
   }
 
   node->clearChildren();
@@ -325,7 +325,7 @@ static void YGConfigFreeRecursive(const YGNodeRef root) {
 void YGNodeFreeRecursive(const YGNodeRef root) {
   while (YGNodeGetChildCount(root) > 0) {
     const YGNodeRef child = YGNodeGetChild(root, 0);
-    if (child->getParent() != root) {
+    if (child->getOwner() != root) {
       // Don't free shared nodes that we don't own.
       break;
     }
@@ -341,8 +341,8 @@ void YGNodeReset(const YGNodeRef node) {
                    "Cannot reset a node which still has children attached");
   YGAssertWithNode(
       node,
-      node->getParent() == nullptr,
-      "Cannot reset a node still attached to a parent");
+      node->getOwner() == nullptr,
+      "Cannot reset a node still attached to a owner");
 
   node->clearChildren();
 
@@ -391,8 +391,8 @@ void YGConfigCopy(const YGConfigRef dest, const YGConfigRef src) {
 void YGNodeInsertChild(const YGNodeRef node, const YGNodeRef child, const uint32_t index) {
   YGAssertWithNode(
       node,
-      child->getParent() == nullptr,
-      "Child already has a parent, it must be removed first.");
+      child->getOwner() == nullptr,
+      "Child already has a owner, it must be removed first.");
   YGAssertWithNode(
       node,
       node->getMeasure() == nullptr,
@@ -400,28 +400,28 @@ void YGNodeInsertChild(const YGNodeRef node, const YGNodeRef child, const uint32
 
   node->cloneChildrenIfNeeded();
   node->insertChild(child, index);
-  child->setParent(node);
+  child->setOwner(node);
   node->markDirtyAndPropogate();
 }
 
-void YGNodeRemoveChild(const YGNodeRef parent, const YGNodeRef excludedChild) {
+void YGNodeRemoveChild(const YGNodeRef owner, const YGNodeRef excludedChild) {
   // This algorithm is a forked variant from cloneChildrenIfNeeded in YGNode
   // that excludes a child.
-  const uint32_t childCount = YGNodeGetChildCount(parent);
+  const uint32_t childCount = YGNodeGetChildCount(owner);
 
   if (childCount == 0) {
     // This is an empty set. Nothing to remove.
     return;
   }
-  const YGNodeRef firstChild = YGNodeGetChild(parent, 0);
-  if (firstChild->getParent() == parent) {
-    // If the first child has this node as its parent, we assume that it is already unique.
+  const YGNodeRef firstChild = YGNodeGetChild(owner, 0);
+  if (firstChild->getOwner() == owner) {
+    // If the first child has this node as its owner, we assume that it is already unique.
     // We can now try to delete a child in this list.
-    if (parent->removeChild(excludedChild)) {
+    if (owner->removeChild(excludedChild)) {
       excludedChild->setLayout(
           YGNode().getLayout()); // layout is no longer valid
-      excludedChild->setParent(nullptr);
-      parent->markDirtyAndPropogate();
+      excludedChild->setOwner(nullptr);
+      owner->markDirtyAndPropogate();
     }
     return;
   }
@@ -429,98 +429,98 @@ void YGNodeRemoveChild(const YGNodeRef parent, const YGNodeRef excludedChild) {
   // We don't want to simply clone all children, because then the host will need to free
   // the clone of the child that was just deleted.
   const YGCloneNodeFunc cloneNodeCallback =
-      parent->getConfig()->cloneNodeCallback;
+      owner->getConfig()->cloneNodeCallback;
   uint32_t nextInsertIndex = 0;
   for (uint32_t i = 0; i < childCount; i++) {
-    const YGNodeRef oldChild = parent->getChild(i);
+    const YGNodeRef oldChild = owner->getChild(i);
     if (excludedChild == oldChild) {
-      // Ignore the deleted child. Don't reset its layout or parent since it is still valid
-      // in the other parent. However, since this parent has now changed, we need to mark it
+      // Ignore the deleted child. Don't reset its layout or owner since it is still valid
+      // in the other owner. However, since this owner has now changed, we need to mark it
       // as dirty.
-      parent->markDirtyAndPropogate();
+      owner->markDirtyAndPropogate();
       continue;
     }
     YGNodeRef newChild = nullptr;
     if (cloneNodeCallback) {
-      newChild = cloneNodeCallback(oldChild, parent, nextInsertIndex);
+      newChild = cloneNodeCallback(oldChild, owner, nextInsertIndex);
     }
     if (newChild == nullptr) {
       newChild = YGNodeClone(oldChild);
     }
-    parent->replaceChild(newChild, nextInsertIndex);
-    newChild->setParent(parent);
+    owner->replaceChild(newChild, nextInsertIndex);
+    newChild->setOwner(owner);
 
     nextInsertIndex++;
   }
   while (nextInsertIndex < childCount) {
-    parent->removeChild(nextInsertIndex);
+    owner->removeChild(nextInsertIndex);
     nextInsertIndex++;
   }
 }
 
-void YGNodeRemoveAllChildren(const YGNodeRef parent) {
-  const uint32_t childCount = YGNodeGetChildCount(parent);
+void YGNodeRemoveAllChildren(const YGNodeRef owner) {
+  const uint32_t childCount = YGNodeGetChildCount(owner);
   if (childCount == 0) {
     // This is an empty set already. Nothing to do.
     return;
   }
-  const YGNodeRef firstChild = YGNodeGetChild(parent, 0);
-  if (firstChild->getParent() == parent) {
-    // If the first child has this node as its parent, we assume that this child set is unique.
+  const YGNodeRef firstChild = YGNodeGetChild(owner, 0);
+  if (firstChild->getOwner() == owner) {
+    // If the first child has this node as its owner, we assume that this child set is unique.
     for (uint32_t i = 0; i < childCount; i++) {
-      const YGNodeRef oldChild = YGNodeGetChild(parent, i);
+      const YGNodeRef oldChild = YGNodeGetChild(owner, i);
       oldChild->setLayout(YGNode().getLayout()); // layout is no longer valid
-      oldChild->setParent(nullptr);
+      oldChild->setOwner(nullptr);
     }
-    parent->clearChildren();
-    parent->markDirtyAndPropogate();
+    owner->clearChildren();
+    owner->markDirtyAndPropogate();
     return;
   }
   // Otherwise, we are not the owner of the child set. We don't have to do anything to clear it.
-  parent->setChildren(YGVector());
-  parent->markDirtyAndPropogate();
+  owner->setChildren(YGVector());
+  owner->markDirtyAndPropogate();
 }
 
-static void YGNodeSetChildrenInternal(YGNodeRef const parent, const std::vector<YGNodeRef> &children)
+static void YGNodeSetChildrenInternal(YGNodeRef const owner, const std::vector<YGNodeRef> &children)
 {
-  if (!parent) {
+  if (!owner) {
     return;
   }
   if (children.size() == 0) {
-    if (YGNodeGetChildCount(parent) > 0) {
-      for (YGNodeRef const child : parent->getChildren()) {
+    if (YGNodeGetChildCount(owner) > 0) {
+      for (YGNodeRef const child : owner->getChildren()) {
         child->setLayout(YGLayout());
-        child->setParent(nullptr);
+        child->setOwner(nullptr);
       }
-      parent->setChildren(YGVector());
-      parent->markDirtyAndPropogate();
+      owner->setChildren(YGVector());
+      owner->markDirtyAndPropogate();
     }
   } else {
-    if (YGNodeGetChildCount(parent) > 0) {
-      for (YGNodeRef const oldChild : parent->getChildren()) {
+    if (YGNodeGetChildCount(owner) > 0) {
+      for (YGNodeRef const oldChild : owner->getChildren()) {
         // Our new children may have nodes in common with the old children. We don't reset these common nodes.
         if (std::find(children.begin(), children.end(), oldChild) == children.end()) {
           oldChild->setLayout(YGLayout());
-          oldChild->setParent(nullptr);
+          oldChild->setOwner(nullptr);
         }
       }
     }
-    parent->setChildren(children);
+    owner->setChildren(children);
     for (YGNodeRef child : children) {
-      child->setParent(parent);
+      child->setOwner(owner);
     }
-    parent->markDirtyAndPropogate();
+    owner->markDirtyAndPropogate();
   }
 }
 
-void YGNodeSetChildren(YGNodeRef const parent, const YGNodeRef c[], const uint32_t count) {
+void YGNodeSetChildren(YGNodeRef const owner, const YGNodeRef c[], const uint32_t count) {
   const YGVector children = {c, c + count};
-  YGNodeSetChildrenInternal(parent, children);
+  YGNodeSetChildrenInternal(owner, children);
 }
 
-void YGNodeSetChildren(YGNodeRef const parent, const std::vector<YGNodeRef> &children)
+void YGNodeSetChildren(YGNodeRef const owner, const std::vector<YGNodeRef> &children)
 {
-  YGNodeSetChildrenInternal(parent, children);
+  YGNodeSetChildrenInternal(owner, children);
 }
 
 YGNodeRef YGNodeGetChild(const YGNodeRef node, const uint32_t index) {
@@ -534,8 +534,8 @@ uint32_t YGNodeGetChildCount(const YGNodeRef node) {
   return static_cast<uint32_t>(node->getChildren().size());
 }
 
-YGNodeRef YGNodeGetParent(const YGNodeRef node) {
-  return node->getParent();
+YGNodeRef YGNodeGetOwner(const YGNodeRef node) {
+  return node->getOwner();
 }
 
 void YGNodeMarkDirty(const YGNodeRef node) {
@@ -947,11 +947,11 @@ uint32_t gCurrentGenerationCount = 0;
 bool YGLayoutNodeInternal(const YGNodeRef node,
                           const float availableWidth,
                           const float availableHeight,
-                          const YGDirection parentDirection,
+                          const YGDirection ownerDirection,
                           const YGMeasureMode widthMeasureMode,
                           const YGMeasureMode heightMeasureMode,
-                          const float parentWidth,
-                          const float parentHeight,
+                          const float ownerWidth,
+                          const float ownerHeight,
                           const bool performLayout,
                           const char *reason,
                           const YGConfigRef config);
@@ -1069,7 +1069,7 @@ static inline float YGNodeDimWithMargin(const YGNodeRef node,
 
 static inline bool YGNodeIsStyleDimDefined(const YGNodeRef node,
                                            const YGFlexDirection axis,
-                                           const float parentSize) {
+                                           const float ownerSize) {
   bool isUndefined =
       YGFloatIsUndefined(node->getResolvedDimension(dim[axis]).value);
   return !(
@@ -1080,7 +1080,7 @@ static inline bool YGNodeIsStyleDimDefined(const YGNodeRef node,
       (node->getResolvedDimension(dim[axis]).unit == YGUnitPercent &&
        !isUndefined &&
        (node->getResolvedDimension(dim[axis]).value < 0.0f ||
-        YGFloatIsUndefined(parentSize))));
+        YGFloatIsUndefined(ownerSize))));
 }
 
 static inline bool YGNodeIsLayoutDimDefined(const YGNodeRef node, const YGFlexDirection axis) {
@@ -1145,14 +1145,14 @@ static void YGNodeSetChildTrailingPosition(const YGNodeRef node,
 
 static void YGConstrainMaxSizeForMode(const YGNodeRef node,
                                       const enum YGFlexDirection axis,
-                                      const float parentAxisSize,
-                                      const float parentWidth,
+                                      const float ownerAxisSize,
+                                      const float ownerWidth,
                                       YGMeasureMode *mode,
                                       float *size) {
   const float maxSize =
       YGUnwrapFloatOptional(YGResolveValue(
-          node->getStyle().maxDimensions[dim[axis]], parentAxisSize)) +
-      node->getMarginForAxis(axis, parentWidth);
+          node->getStyle().maxDimensions[dim[axis]], ownerAxisSize)) +
+      node->getMarginForAxis(axis, ownerWidth);
   switch (*mode) {
     case YGMeasureModeExactly:
     case YGMeasureModeAtMost:
@@ -1172,8 +1172,8 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
                                            const float width,
                                            const YGMeasureMode widthMode,
                                            const float height,
-                                           const float parentWidth,
-                                           const float parentHeight,
+                                           const float ownerWidth,
+                                           const float ownerHeight,
                                            const YGMeasureMode heightMode,
                                            const YGDirection direction,
                                            const YGConfigRef config) {
@@ -1181,7 +1181,7 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
       YGResolveFlexDirection(node->getStyle().flexDirection, direction);
   const bool isMainAxisRow = YGFlexDirectionIsRow(mainAxis);
   const float mainAxisSize = isMainAxisRow ? width : height;
-  const float mainAxisParentSize = isMainAxisRow ? parentWidth : parentHeight;
+  const float mainAxisownerSize = isMainAxisRow ? ownerWidth : ownerHeight;
 
   float childWidth;
   float childHeight;
@@ -1189,10 +1189,10 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
   YGMeasureMode childHeightMeasureMode;
 
   const float resolvedFlexBasis =
-      YGUnwrapFloatOptional(YGResolveValue(child->resolveFlexBasisPtr(), mainAxisParentSize));
-  const bool isRowStyleDimDefined = YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, parentWidth);
+      YGUnwrapFloatOptional(YGResolveValue(child->resolveFlexBasisPtr(), mainAxisownerSize));
+  const bool isRowStyleDimDefined = YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, ownerWidth);
   const bool isColumnStyleDimDefined =
-      YGNodeIsStyleDimDefined(child, YGFlexDirectionColumn, parentHeight);
+      YGNodeIsStyleDimDefined(child, YGFlexDirectionColumn, ownerHeight);
 
   if (!YGFloatIsUndefined(resolvedFlexBasis) && !YGFloatIsUndefined(mainAxisSize)) {
     if (YGFloatIsUndefined(child->getLayout().computedFlexBasis) ||
@@ -1202,21 +1202,21 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
              gCurrentGenerationCount)) {
       child->setLayoutComputedFlexBasis(YGFloatMax(
           resolvedFlexBasis,
-          YGNodePaddingAndBorderForAxis(child, mainAxis, parentWidth)));
+          YGNodePaddingAndBorderForAxis(child, mainAxis, ownerWidth)));
     }
   } else if (isMainAxisRow && isRowStyleDimDefined) {
     // The width is definite, so use that as the flex basis.
     child->setLayoutComputedFlexBasis(YGFloatMax(
         YGUnwrapFloatOptional(YGResolveValue(
-            child->getResolvedDimension(YGDimensionWidth), parentWidth)),
-        YGNodePaddingAndBorderForAxis(child, YGFlexDirectionRow, parentWidth)));
+            child->getResolvedDimension(YGDimensionWidth), ownerWidth)),
+        YGNodePaddingAndBorderForAxis(child, YGFlexDirectionRow, ownerWidth)));
   } else if (!isMainAxisRow && isColumnStyleDimDefined) {
     // The height is definite, so use that as the flex basis.
     child->setLayoutComputedFlexBasis(YGFloatMax(
         YGUnwrapFloatOptional(YGResolveValue(
-            child->getResolvedDimension(YGDimensionHeight), parentHeight)),
+            child->getResolvedDimension(YGDimensionHeight), ownerHeight)),
         YGNodePaddingAndBorderForAxis(
-            child, YGFlexDirectionColumn, parentWidth)));
+            child, YGFlexDirectionColumn, ownerWidth)));
   } else {
     // Compute the flex basis and hypothetical main size (i.e. the clamped
     // flex basis).
@@ -1226,21 +1226,21 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
     childHeightMeasureMode = YGMeasureModeUndefined;
 
     const float marginRow =
-        child->getMarginForAxis(YGFlexDirectionRow, parentWidth);
+        child->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
     const float marginColumn =
-        child->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
+        child->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
 
     if (isRowStyleDimDefined) {
       childWidth =
           YGUnwrapFloatOptional(YGResolveValue(
-              child->getResolvedDimension(YGDimensionWidth), parentWidth)) +
+              child->getResolvedDimension(YGDimensionWidth), ownerWidth)) +
           marginRow;
       childWidthMeasureMode = YGMeasureModeExactly;
     }
     if (isColumnStyleDimDefined) {
       childHeight =
           YGUnwrapFloatOptional(YGResolveValue(
-              child->getResolvedDimension(YGDimensionHeight), parentHeight)) +
+              child->getResolvedDimension(YGDimensionHeight), ownerHeight)) +
           marginColumn;
       childHeightMeasureMode = YGMeasureModeExactly;
     }
@@ -1306,11 +1306,11 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
     }
 
     YGConstrainMaxSizeForMode(
-        child, YGFlexDirectionRow, parentWidth, parentWidth, &childWidthMeasureMode, &childWidth);
+        child, YGFlexDirectionRow, ownerWidth, ownerWidth, &childWidthMeasureMode, &childWidth);
     YGConstrainMaxSizeForMode(child,
                               YGFlexDirectionColumn,
-                              parentHeight,
-                              parentWidth,
+                              ownerHeight,
+                              ownerWidth,
                               &childHeightMeasureMode,
                               &childHeight);
 
@@ -1321,15 +1321,15 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
                          direction,
                          childWidthMeasureMode,
                          childHeightMeasureMode,
-                         parentWidth,
-                         parentHeight,
+                         ownerWidth,
+                         ownerHeight,
                          false,
                          "measure",
                          config);
 
     child->setLayoutComputedFlexBasis(YGFloatMax(
         child->getLayout().measuredDimensions[dim[mainAxis]],
-        YGNodePaddingAndBorderForAxis(child, mainAxis, parentWidth)));
+        YGNodePaddingAndBorderForAxis(child, mainAxis, ownerWidth)));
   }
   child->setLayoutComputedFlexBasisGeneration(gCurrentGenerationCount);
 }
@@ -1414,8 +1414,8 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
     childHeightMeasureMode =
         YGFloatIsUndefined(childHeight) ? YGMeasureModeUndefined : YGMeasureModeExactly;
 
-    // If the size of the parent is defined then try to constrain the absolute child to that size
-    // as well. This allows text within the absolute child to wrap to the size of its parent.
+    // If the size of the owner is defined then try to constrain the absolute child to that size
+    // as well. This allows text within the absolute child to wrap to the size of its owner.
     // This is the same behavior as many browsers implement.
     if (!isMainAxisRow && YGFloatIsUndefined(childWidth) &&
         widthMode != YGMeasureModeUndefined && !YGFloatIsUndefined(width) &&
@@ -1515,8 +1515,8 @@ static void YGNodeWithMeasureFuncSetMeasuredDimensions(const YGNodeRef node,
                                                        const float availableHeight,
                                                        const YGMeasureMode widthMeasureMode,
                                                        const YGMeasureMode heightMeasureMode,
-                                                       const float parentWidth,
-                                                       const float parentHeight) {
+                                                       const float ownerWidth,
+                                                       const float ownerHeight) {
   YGAssertWithNode(
       node,
       node->getMeasure() != nullptr,
@@ -1548,16 +1548,16 @@ static void YGNodeWithMeasureFuncSetMeasuredDimensions(const YGNodeRef node,
             node,
             YGFlexDirectionRow,
             availableWidth - marginAxisRow,
-            parentWidth,
-            parentWidth),
+            ownerWidth,
+            ownerWidth),
         YGDimensionWidth);
     node->setLayoutMeasuredDimension(
         YGNodeBoundAxis(
             node,
             YGFlexDirectionColumn,
             availableHeight - marginAxisColumn,
-            parentHeight,
-            parentWidth),
+            ownerHeight,
+            ownerWidth),
         YGDimensionHeight);
   } else {
     // Measure the text under the current constraints.
@@ -1572,8 +1572,8 @@ static void YGNodeWithMeasureFuncSetMeasuredDimensions(const YGNodeRef node,
              widthMeasureMode == YGMeasureModeAtMost)
                 ? measuredSize.width + paddingAndBorderAxisRow
                 : availableWidth - marginAxisRow,
-            parentWidth,
-            parentWidth),
+            ownerWidth,
+            ownerWidth),
         YGDimensionWidth);
 
     node->setLayoutMeasuredDimension(
@@ -1584,8 +1584,8 @@ static void YGNodeWithMeasureFuncSetMeasuredDimensions(const YGNodeRef node,
              heightMeasureMode == YGMeasureModeAtMost)
                 ? measuredSize.height + paddingAndBorderAxisColumn
                 : availableHeight - marginAxisColumn,
-            parentHeight,
-            parentWidth),
+            ownerHeight,
+            ownerWidth),
         YGDimensionHeight);
   }
 }
@@ -1597,16 +1597,16 @@ static void YGNodeEmptyContainerSetMeasuredDimensions(const YGNodeRef node,
                                                       const float availableHeight,
                                                       const YGMeasureMode widthMeasureMode,
                                                       const YGMeasureMode heightMeasureMode,
-                                                      const float parentWidth,
-                                                      const float parentHeight) {
+                                                      const float ownerWidth,
+                                                      const float ownerHeight) {
   const float paddingAndBorderAxisRow =
-      YGNodePaddingAndBorderForAxis(node, YGFlexDirectionRow, parentWidth);
+      YGNodePaddingAndBorderForAxis(node, YGFlexDirectionRow, ownerWidth);
   const float paddingAndBorderAxisColumn =
-      YGNodePaddingAndBorderForAxis(node, YGFlexDirectionColumn, parentWidth);
+      YGNodePaddingAndBorderForAxis(node, YGFlexDirectionColumn, ownerWidth);
   const float marginAxisRow =
-      node->getMarginForAxis(YGFlexDirectionRow, parentWidth);
+      node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
   const float marginAxisColumn =
-      node->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
+      node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
 
   node->setLayoutMeasuredDimension(
       YGNodeBoundAxis(
@@ -1616,8 +1616,8 @@ static void YGNodeEmptyContainerSetMeasuredDimensions(const YGNodeRef node,
            widthMeasureMode == YGMeasureModeAtMost)
               ? paddingAndBorderAxisRow
               : availableWidth - marginAxisRow,
-          parentWidth,
-          parentWidth),
+          ownerWidth,
+          ownerWidth),
       YGDimensionWidth);
 
   node->setLayoutMeasuredDimension(
@@ -1628,8 +1628,8 @@ static void YGNodeEmptyContainerSetMeasuredDimensions(const YGNodeRef node,
            heightMeasureMode == YGMeasureModeAtMost)
               ? paddingAndBorderAxisColumn
               : availableHeight - marginAxisColumn,
-          parentHeight,
-          parentWidth),
+          ownerHeight,
+          ownerWidth),
       YGDimensionHeight);
 }
 
@@ -1638,8 +1638,8 @@ static bool YGNodeFixedSizeSetMeasuredDimensions(const YGNodeRef node,
                                                  const float availableHeight,
                                                  const YGMeasureMode widthMeasureMode,
                                                  const YGMeasureMode heightMeasureMode,
-                                                 const float parentWidth,
-                                                 const float parentHeight) {
+                                                 const float ownerWidth,
+                                                 const float ownerHeight) {
   if ((!YGFloatIsUndefined(availableWidth) &&
        widthMeasureMode == YGMeasureModeAtMost && availableWidth <= 0.0f) ||
       (!YGFloatIsUndefined(availableHeight) &&
@@ -1647,9 +1647,9 @@ static bool YGNodeFixedSizeSetMeasuredDimensions(const YGNodeRef node,
       (widthMeasureMode == YGMeasureModeExactly &&
        heightMeasureMode == YGMeasureModeExactly)) {
     const float marginAxisColumn =
-        node->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
+        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
     const float marginAxisRow =
-        node->getMarginForAxis(YGFlexDirectionRow, parentWidth);
+        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
 
     node->setLayoutMeasuredDimension(
         YGNodeBoundAxis(
@@ -1660,8 +1660,8 @@ static bool YGNodeFixedSizeSetMeasuredDimensions(const YGNodeRef node,
                      availableWidth < 0.0f)
                 ? 0.0f
                 : availableWidth - marginAxisRow,
-            parentWidth,
-            parentWidth),
+            ownerWidth,
+            ownerWidth),
         YGDimensionWidth);
 
     node->setLayoutMeasuredDimension(
@@ -1673,8 +1673,8 @@ static bool YGNodeFixedSizeSetMeasuredDimensions(const YGNodeRef node,
                      availableHeight < 0.0f)
                 ? 0.0f
                 : availableHeight - marginAxisColumn,
-            parentHeight,
-            parentWidth),
+            ownerHeight,
+            ownerWidth),
         YGDimensionHeight);
     return true;
   }
@@ -1697,15 +1697,15 @@ static float YGNodeCalculateAvailableInnerDim(
     const YGNodeRef node,
     YGFlexDirection axis,
     float availableDim,
-    float parentDim) {
+    float ownerDim) {
   YGFlexDirection direction =
       YGFlexDirectionIsRow(axis) ? YGFlexDirectionRow : YGFlexDirectionColumn;
   YGDimension dimension =
       YGFlexDirectionIsRow(axis) ? YGDimensionWidth : YGDimensionHeight;
 
-  const float margin = node->getMarginForAxis(direction, parentDim);
+  const float margin = node->getMarginForAxis(direction, ownerDim);
   const float paddingAndBorder =
-      YGNodePaddingAndBorderForAxis(node, direction, parentDim);
+      YGNodePaddingAndBorderForAxis(node, direction, ownerDim);
 
   float availableInnerDim = availableDim - margin - paddingAndBorder;
   // Max dimension overrides predefined dimension value; Min dimension in turn
@@ -1713,12 +1713,12 @@ static float YGNodeCalculateAvailableInnerDim(
   if (!YGFloatIsUndefined(availableInnerDim)) {
     // We want to make sure our available height does not violate min and max
     // constraints
-    const YGFloatOptional minDimensionOptional = YGResolveValue(node->getStyle().minDimensions[dimension], parentDim);
+    const YGFloatOptional minDimensionOptional = YGResolveValue(node->getStyle().minDimensions[dimension], ownerDim);
     const float minInnerDim = minDimensionOptional.isUndefined()
         ? 0.0f
         : minDimensionOptional.getValue() - paddingAndBorder;
 
-    const YGFloatOptional maxDimensionOptional = YGResolveValue(node->getStyle().maxDimensions[dimension], parentDim) ;
+    const YGFloatOptional maxDimensionOptional = YGResolveValue(node->getStyle().maxDimensions[dimension], ownerDim) ;
 
     const float maxInnerDim = maxDimensionOptional.isUndefined()
         ? FLT_MAX
@@ -1773,7 +1773,7 @@ static void YGNodeComputeFlexBasisForChildren(
       continue;
     }
     if (performLayout) {
-      // Set the initial position (relative to the parent).
+      // Set the initial position (relative to the owner).
       const YGDirection childDirection = child->resolveDirection(direction);
       const float mainDim = YGFlexDirectionIsRow(mainAxis)
           ? availableInnerWidth
@@ -1816,8 +1816,8 @@ static void YGNodeComputeFlexBasisForChildren(
 // This function calculates YGCollectFlexItemsRowMeasurement
 static YGCollectFlexItemsRowValues YGCalculateCollectFlexItemsRowValues(
     const YGNodeRef& node,
-    const YGDirection parentDirection,
-    const float mainAxisParentSize,
+    const YGDirection ownerDirection,
+    const float mainAxisownerSize,
     const float availableInnerWidth,
     const float availableInnerMainDim,
     const uint32_t startOfLineIndex,
@@ -1827,7 +1827,7 @@ static YGCollectFlexItemsRowValues YGCalculateCollectFlexItemsRowValues(
 
   float sizeConsumedOnCurrentLineIncludingMinConstraint = 0;
   const YGFlexDirection mainAxis = YGResolveFlexDirection(
-      node->getStyle().flexDirection, node->resolveDirection(parentDirection));
+      node->getStyle().flexDirection, node->resolveDirection(ownerDirection));
   const bool isNodeFlexWrap = node->getStyle().flexWrap != YGWrapNoWrap;
 
   // Add items to the current line until it's full or we run out of items.
@@ -1846,7 +1846,7 @@ static YGCollectFlexItemsRowValues YGCalculateCollectFlexItemsRowValues(
             child,
             mainAxis,
             child->getLayout().computedFlexBasis,
-            mainAxisParentSize);
+            mainAxisownerSize);
 
     // If this is a multi-line flow and this item pushes us over the
     // available size, we've
@@ -1901,7 +1901,7 @@ static float YGDistributeFreeSpaceSecondPass(
     const YGNodeRef node,
     const YGFlexDirection mainAxis,
     const YGFlexDirection crossAxis,
-    const float mainAxisParentSize,
+    const float mainAxisownerSize,
     const float availableInnerMainDim,
     const float availableInnerCrossDim,
     const float availableInnerWidth,
@@ -1922,7 +1922,7 @@ static float YGDistributeFreeSpaceSecondPass(
         currentRelativeChild,
         mainAxis,
         currentRelativeChild->getLayout().computedFlexBasis,
-        mainAxisParentSize);
+        mainAxisownerSize);
     float updatedMainSize = childFlexBasis;
 
     if (!YGFloatIsUndefined(collectedFlexItemsValues.remainingFreeSpace) &&
@@ -2083,7 +2083,7 @@ static float YGDistributeFreeSpaceSecondPass(
 static void YGDistributeFreeSpaceFirstPass(
     YGCollectFlexItemsRowValues& collectedFlexItemsValues,
     const YGFlexDirection mainAxis,
-    const float mainAxisParentSize,
+    const float mainAxisownerSize,
     const float availableInnerMainDim,
     const float availableInnerWidth) {
   float flexShrinkScaledFactor = 0;
@@ -2097,7 +2097,7 @@ static void YGDistributeFreeSpaceFirstPass(
         currentRelativeChild,
         mainAxis,
         currentRelativeChild->getLayout().computedFlexBasis,
-        mainAxisParentSize);
+        mainAxisownerSize);
 
     if (collectedFlexItemsValues.remainingFreeSpace < 0) {
       flexShrinkScaledFactor =
@@ -2195,7 +2195,7 @@ static void YGResolveFlexibleLength(
     YGCollectFlexItemsRowValues& collectedFlexItemsValues,
     const YGFlexDirection mainAxis,
     const YGFlexDirection crossAxis,
-    const float mainAxisParentSize,
+    const float mainAxisownerSize,
     const float availableInnerMainDim,
     const float availableInnerCrossDim,
     const float availableInnerWidth,
@@ -2209,7 +2209,7 @@ static void YGResolveFlexibleLength(
   YGDistributeFreeSpaceFirstPass(
       collectedFlexItemsValues,
       mainAxis,
-      mainAxisParentSize,
+      mainAxisownerSize,
       availableInnerMainDim,
       availableInnerWidth);
 
@@ -2219,7 +2219,7 @@ static void YGResolveFlexibleLength(
       node,
       mainAxis,
       crossAxis,
-      mainAxisParentSize,
+      mainAxisownerSize,
       availableInnerMainDim,
       availableInnerCrossDim,
       availableInnerWidth,
@@ -2241,8 +2241,8 @@ static void YGJustifyMainAxis(
     const YGFlexDirection& crossAxis,
     const YGMeasureMode& measureModeMainDim,
     const YGMeasureMode& measureModeCrossDim,
-    const float& mainAxisParentSize,
-    const float& parentWidth,
+    const float& mainAxisownerSize,
+    const float& ownerWidth,
     const float& availableInnerMainDim,
     const float& availableInnerCrossDim,
     const float& availableInnerWidth,
@@ -2254,12 +2254,12 @@ static void YGJustifyMainAxis(
   if (measureModeMainDim == YGMeasureModeAtMost &&
       collectedFlexItemsValues.remainingFreeSpace > 0) {
     if (style.minDimensions[dim[mainAxis]].unit != YGUnitUndefined &&
-        !YGResolveValue(style.minDimensions[dim[mainAxis]], mainAxisParentSize)
+        !YGResolveValue(style.minDimensions[dim[mainAxis]], mainAxisownerSize)
              .isUndefined()) {
       collectedFlexItemsValues.remainingFreeSpace = YGFloatMax(
           0,
           YGUnwrapFloatOptional(YGResolveValue(
-              style.minDimensions[dim[mainAxis]], mainAxisParentSize)) -
+              style.minDimensions[dim[mainAxis]], mainAxisownerSize)) -
               (availableInnerMainDim -
                collectedFlexItemsValues.remainingFreeSpace));
     } else {
@@ -2324,7 +2324,7 @@ static void YGJustifyMainAxis(
   }
 
   const float leadingPaddingAndBorderMain =
-      node->getLeadingPaddingAndBorder(mainAxis, parentWidth);
+      node->getLeadingPaddingAndBorder(mainAxis, ownerWidth);
   collectedFlexItemsValues.mainDim =
       leadingPaddingAndBorderMain + leadingMainDim;
   collectedFlexItemsValues.crossDim = 0;
@@ -2405,7 +2405,7 @@ static void YGJustifyMainAxis(
     }
   }
   collectedFlexItemsValues.mainDim +=
-      node->getTrailingPaddingAndBorder(mainAxis, parentWidth);
+      node->getTrailingPaddingAndBorder(mainAxis, ownerWidth);
 }
 
 //
@@ -2451,7 +2451,7 @@ static void YGJustifyMainAxis(
 //      or YGUndefined if the size is not available; interpretation depends on
 //      layout
 //      flags
-//    - parentDirection: the inline (text) direction within the parent
+//    - ownerDirection: the inline (text) direction within the owner
 //    (left-to-right or
 //      right-to-left)
 //    - widthMeasureMode: indicates the sizing rules for the width (see below
@@ -2497,11 +2497,11 @@ static void YGJustifyMainAxis(
 static void YGNodelayoutImpl(const YGNodeRef node,
                              const float availableWidth,
                              const float availableHeight,
-                             const YGDirection parentDirection,
+                             const YGDirection ownerDirection,
                              const YGMeasureMode widthMeasureMode,
                              const YGMeasureMode heightMeasureMode,
-                             const float parentWidth,
-                             const float parentHeight,
+                             const float ownerWidth,
+                             const float ownerHeight,
                              const bool performLayout,
                              const YGConfigRef config) {
   YGAssertWithNode(node,
@@ -2516,7 +2516,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                    "YGMeasureModeUndefined");
 
   // Set the resolved resolution in the node's layout.
-  const YGDirection direction = node->resolveDirection(parentDirection);
+  const YGDirection direction = node->resolveDirection(ownerDirection);
   node->setLayoutDirection(direction);
 
   const YGFlexDirection flexRowDirection = YGResolveFlexDirection(YGFlexDirectionRow, direction);
@@ -2524,13 +2524,13 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       YGResolveFlexDirection(YGFlexDirectionColumn, direction);
 
   node->setLayoutMargin(
-      node->getLeadingMargin(flexRowDirection, parentWidth), YGEdgeStart);
+      node->getLeadingMargin(flexRowDirection, ownerWidth), YGEdgeStart);
   node->setLayoutMargin(
-      node->getTrailingMargin(flexRowDirection, parentWidth), YGEdgeEnd);
+      node->getTrailingMargin(flexRowDirection, ownerWidth), YGEdgeEnd);
   node->setLayoutMargin(
-      node->getLeadingMargin(flexColumnDirection, parentWidth), YGEdgeTop);
+      node->getLeadingMargin(flexColumnDirection, ownerWidth), YGEdgeTop);
   node->setLayoutMargin(
-      node->getTrailingMargin(flexColumnDirection, parentWidth), YGEdgeBottom);
+      node->getTrailingMargin(flexColumnDirection, ownerWidth), YGEdgeBottom);
 
   node->setLayoutBorder(node->getLeadingBorder(flexRowDirection), YGEdgeStart);
   node->setLayoutBorder(node->getTrailingBorder(flexRowDirection), YGEdgeEnd);
@@ -2539,13 +2539,13 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       node->getTrailingBorder(flexColumnDirection), YGEdgeBottom);
 
   node->setLayoutPadding(
-      node->getLeadingPadding(flexRowDirection, parentWidth), YGEdgeStart);
+      node->getLeadingPadding(flexRowDirection, ownerWidth), YGEdgeStart);
   node->setLayoutPadding(
-      node->getTrailingPadding(flexRowDirection, parentWidth), YGEdgeEnd);
+      node->getTrailingPadding(flexRowDirection, ownerWidth), YGEdgeEnd);
   node->setLayoutPadding(
-      node->getLeadingPadding(flexColumnDirection, parentWidth), YGEdgeTop);
+      node->getLeadingPadding(flexColumnDirection, ownerWidth), YGEdgeTop);
   node->setLayoutPadding(
-      node->getTrailingPadding(flexColumnDirection, parentWidth), YGEdgeBottom);
+      node->getTrailingPadding(flexColumnDirection, ownerWidth), YGEdgeBottom);
 
   if (node->getMeasure() != nullptr) {
     YGNodeWithMeasureFuncSetMeasuredDimensions(node,
@@ -2553,8 +2553,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                                                availableHeight,
                                                widthMeasureMode,
                                                heightMeasureMode,
-                                               parentWidth,
-                                               parentHeight);
+                                               ownerWidth,
+                                               ownerHeight);
     return;
   }
 
@@ -2565,8 +2565,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                                               availableHeight,
                                               widthMeasureMode,
                                               heightMeasureMode,
-                                              parentWidth,
-                                              parentHeight);
+                                              ownerWidth,
+                                              ownerHeight);
     return;
   }
 
@@ -2577,8 +2577,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                                                              availableHeight,
                                                              widthMeasureMode,
                                                              heightMeasureMode,
-                                                             parentWidth,
-                                                             parentHeight)) {
+                                                             ownerWidth,
+                                                             ownerHeight)) {
     return;
   }
 
@@ -2594,14 +2594,14 @@ static void YGNodelayoutImpl(const YGNodeRef node,
   const bool isMainAxisRow = YGFlexDirectionIsRow(mainAxis);
   const bool isNodeFlexWrap = node->getStyle().flexWrap != YGWrapNoWrap;
 
-  const float mainAxisParentSize = isMainAxisRow ? parentWidth : parentHeight;
-  const float crossAxisParentSize = isMainAxisRow ? parentHeight : parentWidth;
+  const float mainAxisownerSize = isMainAxisRow ? ownerWidth : ownerHeight;
+  const float crossAxisownerSize = isMainAxisRow ? ownerHeight : ownerWidth;
 
   const float leadingPaddingAndBorderCross =
-      node->getLeadingPaddingAndBorder(crossAxis, parentWidth);
-  const float paddingAndBorderAxisMain = YGNodePaddingAndBorderForAxis(node, mainAxis, parentWidth);
+      node->getLeadingPaddingAndBorder(crossAxis, ownerWidth);
+  const float paddingAndBorderAxisMain = YGNodePaddingAndBorderForAxis(node, mainAxis, ownerWidth);
   const float paddingAndBorderAxisCross =
-      YGNodePaddingAndBorderForAxis(node, crossAxis, parentWidth);
+      YGNodePaddingAndBorderForAxis(node, crossAxis, ownerWidth);
 
   YGMeasureMode measureModeMainDim = isMainAxisRow ? widthMeasureMode : heightMeasureMode;
   YGMeasureMode measureModeCrossDim = isMainAxisRow ? heightMeasureMode : widthMeasureMode;
@@ -2612,22 +2612,22 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       isMainAxisRow ? paddingAndBorderAxisCross : paddingAndBorderAxisMain;
 
   const float marginAxisRow =
-      node->getMarginForAxis(YGFlexDirectionRow, parentWidth);
+      node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
   const float marginAxisColumn =
-      node->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
+      node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
 
   const float minInnerWidth =
-      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionWidth], parentWidth)) -
+      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionWidth], ownerWidth)) -
       paddingAndBorderAxisRow;
   const float maxInnerWidth =
-      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionWidth], parentWidth)) -
+      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionWidth], ownerWidth)) -
       paddingAndBorderAxisRow;
   const float minInnerHeight =
-      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionHeight], parentHeight)) -
+      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionHeight], ownerHeight)) -
       paddingAndBorderAxisColumn;
   const float maxInnerHeight =
       YGUnwrapFloatOptional(YGResolveValue(
-          node->getStyle().maxDimensions[YGDimensionHeight], parentHeight)) -
+          node->getStyle().maxDimensions[YGDimensionHeight], ownerHeight)) -
       paddingAndBorderAxisColumn;
 
   const float minInnerMainDim = isMainAxisRow ? minInnerWidth : minInnerHeight;
@@ -2636,9 +2636,9 @@ static void YGNodelayoutImpl(const YGNodeRef node,
   // STEP 2: DETERMINE AVAILABLE SIZE IN MAIN AND CROSS DIRECTIONS
 
   float availableInnerWidth = YGNodeCalculateAvailableInnerDim(
-      node, YGFlexDirectionRow, availableWidth, parentWidth);
+      node, YGFlexDirectionRow, availableWidth, ownerWidth);
   float availableInnerHeight = YGNodeCalculateAvailableInnerDim(
-      node, YGFlexDirectionColumn, availableHeight, parentHeight);
+      node, YGFlexDirectionColumn, availableHeight, ownerHeight);
 
   float availableInnerMainDim =
       isMainAxisRow ? availableInnerWidth : availableInnerHeight;
@@ -2687,8 +2687,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
        lineCount++, startOfLineIndex = endOfLineIndex) {
     collectedFlexItemsValues = YGCalculateCollectFlexItemsRowValues(
         node,
-        parentDirection,
-        mainAxisParentSize,
+        ownerDirection,
+        mainAxisownerSize,
         availableInnerWidth,
         availableInnerMainDim,
         startOfLineIndex,
@@ -2756,7 +2756,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
           collectedFlexItemsValues,
           mainAxis,
           crossAxis,
-          mainAxisParentSize,
+          mainAxisownerSize,
           availableInnerMainDim,
           availableInnerCrossDim,
           availableInnerWidth,
@@ -2788,8 +2788,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
         crossAxis,
         measureModeMainDim,
         measureModeCrossDim,
-        mainAxisParentSize,
-        parentWidth,
+        mainAxisownerSize,
+        ownerWidth,
         availableInnerMainDim,
         availableInnerCrossDim,
         availableInnerWidth,
@@ -2804,8 +2804,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               node,
               crossAxis,
               collectedFlexItemsValues.crossDim + paddingAndBorderAxisCross,
-              crossAxisParentSize,
-              parentWidth) -
+              crossAxisownerSize,
+              ownerWidth) -
           paddingAndBorderAxisCross;
     }
 
@@ -2820,8 +2820,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
             node,
             crossAxis,
             collectedFlexItemsValues.crossDim + paddingAndBorderAxisCross,
-            crossAxisParentSize,
-            parentWidth) -
+            crossAxisownerSize,
+            ownerWidth) -
         paddingAndBorderAxisCross;
 
     // STEP 7: CROSS-AXIS ALIGNMENT
@@ -2856,7 +2856,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
         } else {
           float leadingCrossDim = leadingPaddingAndBorderCross;
 
-          // For a relative children, we're either using alignItems (parent) or
+          // For a relative children, we're either using alignItems (owner) or
           // alignSelf (child) in order to determine the position in the cross
           // axis
           const YGAlign alignItem = YGNodeAlignItem(node, child);
@@ -3083,7 +3083,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                     pos[crossAxis]);
 
                 // Remeasure child with the line height as it as been only measured with the
-                // parents height yet.
+                // owners height yet.
                 if (!YGNodeIsStyleDimDefined(child, crossAxis, availableInnerCrossDim)) {
                   const float childWidth = isMainAxisRow
                       ? (child->getLayout()
@@ -3150,8 +3150,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
           node,
           YGFlexDirectionRow,
           availableWidth - marginAxisRow,
-          parentWidth,
-          parentWidth),
+          ownerWidth,
+          ownerWidth),
       YGDimensionWidth);
 
   node->setLayoutMeasuredDimension(
@@ -3159,8 +3159,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
           node,
           YGFlexDirectionColumn,
           availableHeight - marginAxisColumn,
-          parentHeight,
-          parentWidth),
+          ownerHeight,
+          ownerWidth),
       YGDimensionHeight);
 
   // If the user didn't specify a width or height for the node, set the
@@ -3172,7 +3172,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
     // doesn't go below the padding and border amount.
     node->setLayoutMeasuredDimension(
         YGNodeBoundAxis(
-            node, mainAxis, maxLineMainDim, mainAxisParentSize, parentWidth),
+            node, mainAxis, maxLineMainDim, mainAxisownerSize, ownerWidth),
         dim[mainAxis]);
 
   } else if (
@@ -3183,7 +3183,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
             YGFloatMin(
                 availableInnerMainDim + paddingAndBorderAxisMain,
                 YGNodeBoundAxisWithinMinAndMax(
-                    node, mainAxis, maxLineMainDim, mainAxisParentSize)),
+                    node, mainAxis, maxLineMainDim, mainAxisownerSize)),
             paddingAndBorderAxisMain),
         dim[mainAxis]);
   }
@@ -3199,8 +3199,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
             node,
             crossAxis,
             totalLineCrossDim + paddingAndBorderAxisCross,
-            crossAxisParentSize,
-            parentWidth),
+            crossAxisownerSize,
+            ownerWidth),
         dim[crossAxis]);
 
   } else if (
@@ -3214,7 +3214,7 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                     node,
                     crossAxis,
                     totalLineCrossDim + paddingAndBorderAxisCross,
-                    crossAxisParentSize)),
+                    crossAxisownerSize)),
             paddingAndBorderAxisCross),
         dim[crossAxis]);
   }
@@ -3435,11 +3435,11 @@ bool YGNodeCanUseCachedMeasurement(const YGMeasureMode widthMode,
 bool YGLayoutNodeInternal(const YGNodeRef node,
                           const float availableWidth,
                           const float availableHeight,
-                          const YGDirection parentDirection,
+                          const YGDirection ownerDirection,
                           const YGMeasureMode widthMeasureMode,
                           const YGMeasureMode heightMeasureMode,
-                          const float parentWidth,
-                          const float parentHeight,
+                          const float ownerWidth,
+                          const float ownerHeight,
                           const bool performLayout,
                           const char *reason,
                           const YGConfigRef config) {
@@ -3449,7 +3449,7 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
 
   const bool needToVisitNode =
       (node->isDirty() && layout->generationCount != gCurrentGenerationCount) ||
-      layout->lastParentDirection != parentDirection;
+      layout->lastOwnerDirection != ownerDirection;
 
   if (needToVisitNode) {
     // Invalidate the cached results.
@@ -3476,9 +3476,9 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
   // all possible.
   if (node->getMeasure() != nullptr) {
     const float marginAxisRow =
-        node->getMarginForAxis(YGFlexDirectionRow, parentWidth);
+        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
     const float marginAxisColumn =
-        node->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
+        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
 
     // First, try to use the layout cache.
     if (YGNodeCanUseCachedMeasurement(widthMeasureMode,
@@ -3582,11 +3582,11 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
     YGNodelayoutImpl(node,
                      availableWidth,
                      availableHeight,
-                     parentDirection,
+                     ownerDirection,
                      widthMeasureMode,
                      heightMeasureMode,
-                     parentWidth,
-                     parentHeight,
+                     ownerWidth,
+                     ownerHeight,
                      performLayout,
                      config);
 
@@ -3612,7 +3612,7 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
           reason);
     }
 
-    layout->lastParentDirection = parentDirection;
+    layout->lastOwnerDirection = ownerDirection;
 
     if (cachedResults == nullptr) {
       if (layout->nextCachedMeasurementsIndex == YG_MAX_CACHED_RESULT_COUNT) {
@@ -3742,9 +3742,9 @@ static void YGRoundToPixelGrid(const YGNodeRef node,
 
 void YGNodeCalculateLayout(
     const YGNodeRef node,
-    const float parentWidth,
-    const float parentHeight,
-    const YGDirection parentDirection) {
+    const float ownerWidth,
+    const float ownerHeight,
+    const YGDirection ownerDirection) {
   // Increment the generation count. This will force the recursive routine to
   // visit
   // all dirty nodes at least once. Subsequent visits will be skipped if the
@@ -3754,40 +3754,40 @@ void YGNodeCalculateLayout(
   node->resolveDimension();
   float width = YGUndefined;
   YGMeasureMode widthMeasureMode = YGMeasureModeUndefined;
-  if (YGNodeIsStyleDimDefined(node, YGFlexDirectionRow, parentWidth)) {
+  if (YGNodeIsStyleDimDefined(node, YGFlexDirectionRow, ownerWidth)) {
     width =
         YGUnwrapFloatOptional(YGResolveValue(
-            node->getResolvedDimension(dim[YGFlexDirectionRow]), parentWidth)) +
-        node->getMarginForAxis(YGFlexDirectionRow, parentWidth);
+            node->getResolvedDimension(dim[YGFlexDirectionRow]), ownerWidth)) +
+        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
     widthMeasureMode = YGMeasureModeExactly;
   } else if (!YGResolveValue(
-                  node->getStyle().maxDimensions[YGDimensionWidth], parentWidth)
+                  node->getStyle().maxDimensions[YGDimensionWidth], ownerWidth)
                   .isUndefined()) {
     width = YGUnwrapFloatOptional(YGResolveValue(
-        node->getStyle().maxDimensions[YGDimensionWidth], parentWidth));
+        node->getStyle().maxDimensions[YGDimensionWidth], ownerWidth));
     widthMeasureMode = YGMeasureModeAtMost;
   } else {
-    width = parentWidth;
+    width = ownerWidth;
     widthMeasureMode = YGFloatIsUndefined(width) ? YGMeasureModeUndefined
                                                  : YGMeasureModeExactly;
   }
 
   float height = YGUndefined;
   YGMeasureMode heightMeasureMode = YGMeasureModeUndefined;
-  if (YGNodeIsStyleDimDefined(node, YGFlexDirectionColumn, parentHeight)) {
+  if (YGNodeIsStyleDimDefined(node, YGFlexDirectionColumn, ownerHeight)) {
     height = YGUnwrapFloatOptional(YGResolveValue(
                  node->getResolvedDimension(dim[YGFlexDirectionColumn]),
-                 parentHeight)) +
-        node->getMarginForAxis(YGFlexDirectionColumn, parentWidth);
+                 ownerHeight)) +
+        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
     heightMeasureMode = YGMeasureModeExactly;
   } else if (!YGResolveValue(
                   node->getStyle().maxDimensions[YGDimensionHeight],
-                  parentHeight)
+                  ownerHeight)
                   .isUndefined()) {
-    height = YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionHeight], parentHeight));
+    height = YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionHeight], ownerHeight));
     heightMeasureMode = YGMeasureModeAtMost;
   } else {
-    height = parentHeight;
+    height = ownerHeight;
     heightMeasureMode = YGFloatIsUndefined(height) ? YGMeasureModeUndefined
                                                    : YGMeasureModeExactly;
   }
@@ -3795,16 +3795,16 @@ void YGNodeCalculateLayout(
           node,
           width,
           height,
-          parentDirection,
+          ownerDirection,
           widthMeasureMode,
           heightMeasureMode,
-          parentWidth,
-          parentHeight,
+          ownerWidth,
+          ownerHeight,
           true,
           "initial",
           node->getConfig())) {
     node->setPosition(
-        node->getLayout().direction, parentWidth, parentHeight, parentWidth);
+        node->getLayout().direction, ownerWidth, ownerHeight, ownerWidth);
     YGRoundToPixelGrid(node, node->getConfig()->pointScaleFactor, 0.0f, 0.0f);
 
     if (gPrintTree) {
@@ -3836,19 +3836,19 @@ void YGNodeCalculateLayout(
             originalNode,
             width,
             height,
-            parentDirection,
+            ownerDirection,
             widthMeasureMode,
             heightMeasureMode,
-            parentWidth,
-            parentHeight,
+            ownerWidth,
+            ownerHeight,
             true,
             "initial",
             originalNode->getConfig())) {
       originalNode->setPosition(
           originalNode->getLayout().direction,
-          parentWidth,
-          parentHeight,
-          parentWidth);
+          ownerWidth,
+          ownerHeight,
+          ownerWidth);
       YGRoundToPixelGrid(
           originalNode,
           originalNode->getConfig()->pointScaleFactor,
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index 73e7c7fdb1a2..445c0b065d55 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -81,14 +81,14 @@ WIN_EXPORT void YGNodeInsertChild(const YGNodeRef node,
 WIN_EXPORT void YGNodeRemoveChild(const YGNodeRef node, const YGNodeRef child);
 WIN_EXPORT void YGNodeRemoveAllChildren(const YGNodeRef node);
 WIN_EXPORT YGNodeRef YGNodeGetChild(const YGNodeRef node, const uint32_t index);
-WIN_EXPORT YGNodeRef YGNodeGetParent(const YGNodeRef node);
+WIN_EXPORT YGNodeRef YGNodeGetOwner(const YGNodeRef node);
 WIN_EXPORT uint32_t YGNodeGetChildCount(const YGNodeRef node);
 WIN_EXPORT void YGNodeSetChildren(YGNodeRef const parent, const YGNodeRef children[], const uint32_t count);
 
 WIN_EXPORT void YGNodeCalculateLayout(const YGNodeRef node,
                                       const float availableWidth,
                                       const float availableHeight,
-                                      const YGDirection parentDirection);
+                                      const YGDirection ownerDirection);
 
 // Mark a node as dirty. Only valid for nodes with a custom measure function
 // set.

From 5be4ff026162e342a4457d1df9750216ce84ac3c Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sun, 1 Apr 2018 18:27:08 -0700
Subject: [PATCH 0176/1109] Extend Yoga to be able clone Yoga Node with new
 children

Reviewed By: emilsjolander

Differential Revision: D7245421

fbshipit-source-id: 72578c8261f29e4a12fc6c72a91f2f891cd58d48
---
 .../main/java/com/facebook/yoga/YogaNode.java | 66 ++++++++++++++++---
 .../jni/first-party/yogajni/jni/YGJNI.cpp     | 16 +++++
 ReactCommon/yoga/yoga/Yoga.cpp                | 19 ++++--
 ReactCommon/yoga/yoga/Yoga.h                  | 25 +++++--
 4 files changed, 108 insertions(+), 18 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index ae5165e63844..69bb3348b396 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -30,7 +30,7 @@ public class YogaNode implements Cloneable {
   static native int jni_YGNodeGetInstanceCount();
 
   private YogaNode mOwner;
-  private List<YogaNode> mChildren;
+  @Nullable private List<YogaNode> mChildren;
   private YogaMeasureFunction mMeasureFunction;
   private YogaBaselineFunction mBaselineFunction;
   private long mNativePointer;
@@ -147,6 +147,9 @@ public int getChildCount() {
   }
 
   public YogaNode getChildAt(int i) {
+    if (mChildren == null) {
+      throw new IllegalStateException("YogaNode does not have children");
+    }
     return mChildren.get(i);
   }
 
@@ -164,21 +167,62 @@ public void addChildAt(YogaNode child, int i) {
     jni_YGNodeInsertChild(mNativePointer, child.mNativePointer, i);
   }
 
+  private native void jni_YGNodeInsertSharedChild(long nativePointer, long childPointer, int index);
+
+  public void addSharedChildAt(YogaNode child, int i) {
+    if (mChildren == null) {
+      mChildren = new ArrayList<>(4);
+    }
+    mChildren.add(i, child);
+    child.mOwner = null;
+    jni_YGNodeInsertSharedChild(mNativePointer, child.mNativePointer, i);
+  }
+
   private native long jni_YGNodeClone(long nativePointer, Object newNode);
 
   @Override
-  public YogaNode clone() throws CloneNotSupportedException {
-    YogaNode clonedYogaNode = (YogaNode) super.clone();
-    long clonedNativePointer = jni_YGNodeClone(mNativePointer, clonedYogaNode);
-    clonedYogaNode.mNativePointer = clonedNativePointer;
-    clonedYogaNode.mChildren =
-        mChildren != null ? (List<YogaNode>) ((ArrayList) mChildren).clone() : null;
-    return clonedYogaNode;
+  public YogaNode clone() {
+    try {
+      YogaNode clonedYogaNode = (YogaNode) super.clone();
+      long clonedNativePointer = jni_YGNodeClone(mNativePointer, clonedYogaNode);
+      clonedYogaNode.mNativePointer = clonedNativePointer;
+      clonedYogaNode.mOwner = null;
+      clonedYogaNode.mChildren =
+          mChildren != null ? (List<YogaNode>) ((ArrayList) mChildren).clone() : null;
+      return clonedYogaNode;
+    } catch (CloneNotSupportedException ex) {
+      // This class implements Cloneable, this should not happen
+      throw new RuntimeException(ex);
+    }
+  }
+
+  public YogaNode cloneWithNewChildren() {
+    try {
+      YogaNode clonedYogaNode = (YogaNode) super.clone();
+      long clonedNativePointer = jni_YGNodeClone(mNativePointer, clonedYogaNode);
+      clonedYogaNode.mOwner = null;
+      clonedYogaNode.mNativePointer = clonedNativePointer;
+      clonedYogaNode.clearChildren();
+      return clonedYogaNode;
+    } catch (CloneNotSupportedException ex) {
+      // This class implements Cloneable, this should not happen
+      throw new RuntimeException(ex);
+    }
+  }
+
+  private native void jni_YGNodeClearChildren(long nativePointer);
+
+  private void clearChildren() {
+    mChildren = null;
+    jni_YGNodeClearChildren(mNativePointer);
   }
 
   private native void jni_YGNodeRemoveChild(long nativePointer, long childPointer);
   public YogaNode removeChildAt(int i) {
-
+    if (mChildren == null) {
+      throw new IllegalStateException(
+          "Trying to remove a child of a YogaNode that does not have children");
+    }
     final YogaNode child = mChildren.remove(i);
     child.mOwner = null;
     jni_YGNodeRemoveChild(mNativePointer, child.mNativePointer);
@@ -715,8 +759,12 @@ public void print() {
    */
   @DoNotStrip
   private final long replaceChild(YogaNode newNode, int childIndex) {
+    if (mChildren == null) {
+      throw new IllegalStateException("Cannot replace child. YogaNode does not have children");
+    }
     mChildren.remove(childIndex);
     mChildren.add(childIndex, newNode);
+    newNode.mOwner = this;
     return newNode.mNativePointer;
   }
 }
diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
index b303ce223a92..69cbb38115c4 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
@@ -284,6 +284,11 @@ void jni_YGNodeFree(alias_ref<jobject> thiz, jlong nativePointer) {
   YGNodeFree(node);
 }
 
+void jni_YGNodeClearChildren(alias_ref<jobject> thiz, jlong nativePointer) {
+  const YGNodeRef node = _jlong2YGNodeRef(nativePointer);
+  node->clearChildren();
+}
+
 void jni_YGNodeReset(alias_ref<jobject> thiz, jlong nativePointer) {
   const YGNodeRef node = _jlong2YGNodeRef(nativePointer);
   void* context = node->getContext();
@@ -303,6 +308,15 @@ void jni_YGNodeInsertChild(alias_ref<jobject>, jlong nativePointer, jlong childP
   YGNodeInsertChild(_jlong2YGNodeRef(nativePointer), _jlong2YGNodeRef(childPointer), index);
 }
 
+void jni_YGNodeInsertSharedChild(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jlong childPointer,
+    jint index) {
+  YGNodeInsertSharedChild(
+      _jlong2YGNodeRef(nativePointer), _jlong2YGNodeRef(childPointer), index);
+}
+
 void jni_YGNodeRemoveChild(alias_ref<jobject>, jlong nativePointer, jlong childPointer) {
   YGNodeRemoveChild(_jlong2YGNodeRef(nativePointer), _jlong2YGNodeRef(childPointer));
 }
@@ -577,7 +591,9 @@ jint JNI_OnLoad(JavaVM *vm, void *) {
             YGMakeNativeMethod(jni_YGNodeNewWithConfig),
             YGMakeNativeMethod(jni_YGNodeFree),
             YGMakeNativeMethod(jni_YGNodeReset),
+            YGMakeNativeMethod(jni_YGNodeClearChildren),
             YGMakeNativeMethod(jni_YGNodeInsertChild),
+            YGMakeNativeMethod(jni_YGNodeInsertSharedChild),
             YGMakeNativeMethod(jni_YGNodeRemoveChild),
             YGMakeNativeMethod(jni_YGNodeCalculateLayout),
             YGMakeNativeMethod(jni_YGNodeMarkDirty),
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 2e5979a2dd0f..7518e858603a 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -391,16 +391,27 @@ void YGConfigCopy(const YGConfigRef dest, const YGConfigRef src) {
 void YGNodeInsertChild(const YGNodeRef node, const YGNodeRef child, const uint32_t index) {
   YGAssertWithNode(
       node,
-      child->getOwner() == nullptr,
-      "Child already has a owner, it must be removed first.");
+      node->getMeasure() == nullptr,
+      "Cannot add child: Nodes with measure functions cannot have children.");
+
+  node->cloneChildrenIfNeeded();
+  node->insertChild(child, index);
+  YGNodeRef owner = child->getOwner() ? nullptr : node;
+  child->setOwner(owner);
+  node->markDirtyAndPropogate();
+}
+
+void YGNodeInsertSharedChild(
+    const YGNodeRef node,
+    const YGNodeRef child,
+    const uint32_t index) {
   YGAssertWithNode(
       node,
       node->getMeasure() == nullptr,
       "Cannot add child: Nodes with measure functions cannot have children.");
 
-  node->cloneChildrenIfNeeded();
   node->insertChild(child, index);
-  child->setOwner(node);
+  child->setOwner(nullptr);
   node->markDirtyAndPropogate();
 }
 
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index 445c0b065d55..25eb0eb6f5a8 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -62,9 +62,8 @@ typedef int (*YGLogger)(const YGConfigRef config,
                         YGLogLevel level,
                         const char *format,
                         va_list args);
-typedef YGNodeRef (*YGCloneNodeFunc)(YGNodeRef oldNode,
-                                 YGNodeRef parent,
-                                 int childIndex);
+typedef YGNodeRef (
+    *YGCloneNodeFunc)(YGNodeRef oldNode, YGNodeRef owner, int childIndex);
 
 // YGNode
 WIN_EXPORT YGNodeRef YGNodeNew(void);
@@ -78,12 +77,26 @@ WIN_EXPORT int32_t YGNodeGetInstanceCount(void);
 WIN_EXPORT void YGNodeInsertChild(const YGNodeRef node,
                                   const YGNodeRef child,
                                   const uint32_t index);
+
+// This function inserts the child YGNodeRef as a children of the node received
+// by parameter and set the Owner of the child object to null. This function is
+// expected to be called when using Yoga in persistent mode in order to share a
+// YGNodeRef object as a child of two different Yoga trees. The child YGNodeRef
+// is expected to be referenced from its original owner and from a clone of its
+// original owner.
+WIN_EXPORT void YGNodeInsertSharedChild(
+    const YGNodeRef node,
+    const YGNodeRef child,
+    const uint32_t index);
 WIN_EXPORT void YGNodeRemoveChild(const YGNodeRef node, const YGNodeRef child);
 WIN_EXPORT void YGNodeRemoveAllChildren(const YGNodeRef node);
 WIN_EXPORT YGNodeRef YGNodeGetChild(const YGNodeRef node, const uint32_t index);
 WIN_EXPORT YGNodeRef YGNodeGetOwner(const YGNodeRef node);
 WIN_EXPORT uint32_t YGNodeGetChildCount(const YGNodeRef node);
-WIN_EXPORT void YGNodeSetChildren(YGNodeRef const parent, const YGNodeRef children[], const uint32_t count);
+WIN_EXPORT void YGNodeSetChildren(
+    YGNodeRef const owner,
+    const YGNodeRef children[],
+    const uint32_t count);
 
 WIN_EXPORT void YGNodeCalculateLayout(const YGNodeRef node,
                                       const float availableWidth,
@@ -307,6 +320,8 @@ YG_EXTERN_C_END
 // Calls f on each node in the tree including the given node argument.
 extern void YGTraversePreOrder(YGNodeRef const node, std::function<void(YGNodeRef node)>&& f);
 
-extern void YGNodeSetChildren(YGNodeRef const parent, const std::vector<YGNodeRef> &children);
+extern void YGNodeSetChildren(
+    YGNodeRef const owner,
+    const std::vector<YGNodeRef>& children);
 
 #endif

From 8a99241f8134e7f58fe14557f0d70fcb6a96d226 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sun, 1 Apr 2018 18:27:11 -0700
Subject: [PATCH 0177/1109] Re-enable Yoga cloning in React Shadow Node

Reviewed By: achen1

Differential Revision: D7435365

fbshipit-source-id: 3e04b3252945112cf0c7206b0e6fb63535499eb9
---
 .../java/com/facebook/react/fabric/FabricReconciler.java  | 3 ---
 .../com/facebook/react/uimanager/ReactShadowNodeImpl.java | 8 ++------
 2 files changed, 2 insertions(+), 9 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index cc851c228fe2..3e8eca9cabeb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -96,9 +96,6 @@ private void manageChildren(
       indicesToRemove.add(0, j);
       if (!addedTags.contains(nodeToRemove.getReactTag())) {
         tagsToDelete.add(nodeToRemove.getReactTag());
-        // TODO: T26729293 since we are not cloning ReactShadowNode's we need to "manually" remove
-        // from the ReactShadowTree when one of the nodes is deleted in JS.
-        nodeToRemove.getParent().removeChildAt(j);
       }
     }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 53a27c440b76..c5727e664e4c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -150,9 +150,7 @@ protected ReactShadowNodeImpl copy() {
   @Override
   public ReactShadowNodeImpl mutableCopy() {
     ReactShadowNodeImpl copy = copy();
-    copy.mYogaNode = mYogaNode;
-    // TODO: T26729293 clone YogaNode instead of reusing the same instance
-    //copy.mYogaNode = mYogaNode.clone();
+    copy.mYogaNode = mYogaNode.clone();
     copy.mNativeChildren = mNativeChildren == null ? null : new ArrayList<>(mNativeChildren);
     copy.mTotalNativeChildren = mTotalNativeChildren;
     copy.mChildren = mChildren == null ? null : new ArrayList<>(mChildren);
@@ -170,9 +168,7 @@ public ReactShadowNodeImpl mutableCopy() {
   @Override
   public ReactShadowNodeImpl mutableCopyWithNewChildren() {
     ReactShadowNodeImpl copy = copy();
-    copy.mYogaNode = mYogaNode;
-    // TODO: T26729293 clone YogaNode instead of reusing the same instance
-    //copy.mYogaNode = mYogaNode.clone();
+    copy.mYogaNode = mYogaNode.cloneWithNewChildren();
     copy.mNativeChildren = null;
     copy.mChildren = null;
     copy.mTotalNativeChildren = 0;

From d4fb87b0b873f035872eca1eccf737d509838250 Mon Sep 17 00:00:00 2001
From: Christian Brevik <christian.brevik@gmail.com>
Date: Mon, 2 Apr 2018 02:31:16 -0700
Subject: [PATCH 0178/1109] Add iOS 10 textContentType for TextInput

Summary:
Setting `textContentType` will provide the keyboard and system with semantic meaning for inputs. Should enable password/username autofill in apps running on iOS 11+ as demonstrated here: https://developer.apple.com/videos/play/wwdc2017/206/

Also gives you the ability to disable autofill by setting `textContentType="none"`: https://stackoverflow.com/questions/48489479/react-native-disable-password-autofill-option-on-ios-keyboard

Adding `textContentType` equal to `username` or `password`  should give you an autofill-bar over the keyboard which will let you fill in values from the device Keychain:

![image](https://user-images.githubusercontent.com/4932625/37848513-b2170490-2ed4-11e8-85bf-895823d4f98a.png)

Setting the appropriate `textContentType` will fill in the correct value in the `TextInput`.
I have only been able to get this to work on device, and not simulator.

Usage:
```jsx
<TextInput
    value={this.state.username}
    onChangeText={this.setUserName}
    textContentType="username"
/>
```

```jsx
<TextInput
    value={this.state.password}
    onChangeText={this.setPassword}
    secureTextEntry={true}
    textContentType="password"
/>
```

To disable:
```jsx
<TextInput
    value={this.state.password}
    onChangeText={this.setPassword}
    secureTextEntry={true}
    textContentType="none"
/>
```

This will set `textContentType` to an empty string: https://stackoverflow.com/a/46474180/5703116

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

Docs PR coming up.

[IOS] [MINOR] [TextInput] - Added `textContentType` prop for iOS 10+. Will enable password autofill for iOS 11+.
Closes https://github.com/facebook/react-native/pull/18526

Differential Revision: D7469630

Pulled By: hramos

fbshipit-source-id: 852a9749be98d477ecd82154c0a65a7c084521c1
---
 Libraries/Components/TextInput/TextInput.js   | 33 +++++++++++++++++++
 .../Text/TextInput/RCTBaseTextInputView.m     | 11 +++++++
 .../TextInput/RCTBaseTextInputViewManager.m   |  1 +
 3 files changed, 45 insertions(+)

diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index 2c6c4f8ef19b..eb838174f151 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -605,6 +605,39 @@ const TextInput = createReactClass({
      * @platform ios
      */
     inputAccessoryViewID: PropTypes.string,
+    /**
+     * Give the keyboard and the system information about the
+     * expected semantic meaning for the content that users enter.
+     * @platform ios
+     */
+    textContentType: PropTypes.oneOf([
+      'none',
+      'URL',
+      'addressCity',
+      'addressCityAndState',
+      'addressState',
+      'countryName',
+      'creditCardNumber',
+      'emailAddress',
+      'familyName',
+      'fullStreetAddress',
+      'givenName',
+      'jobTitle',
+      'location',
+      'middleName',
+      'name',
+      'namePrefix',
+      'nameSuffix',
+      'nickname',
+      'organizationName',
+      'postalCode',
+      'streetAddressLine1',
+      'streetAddressLine2',
+      'sublocality',
+      'telephoneNumber',
+      'username',
+      'password',
+    ]),
   },
   getDefaultProps(): Object {
     return {
diff --git a/Libraries/Text/TextInput/RCTBaseTextInputView.m b/Libraries/Text/TextInput/RCTBaseTextInputView.m
index 64a3a865c6d7..cbfa24d1ab4f 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputView.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputView.m
@@ -167,6 +167,17 @@ - (void)setSelection:(RCTTextSelection *)selection
   }
 }
 
+- (void)setTextContentType:(NSString *)type
+{
+  #if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_10_0
+    if (@available(iOS 10.0, *)) {
+        // Setting textContentType to an empty string will disable any
+        // default behaviour, like the autofill bar for password inputs
+        self.backedTextInputView.textContentType = [type isEqualToString:@"none"] ? @"" : type;
+    }
+  #endif
+}
+
 #pragma mark - RCTBackedTextInputDelegate
 
 - (BOOL)textInputShouldBeginEditing
diff --git a/Libraries/Text/TextInput/RCTBaseTextInputViewManager.m b/Libraries/Text/TextInput/RCTBaseTextInputViewManager.m
index aaead20b0b9c..42266eacfb91 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputViewManager.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputViewManager.m
@@ -55,6 +55,7 @@ @implementation RCTBaseTextInputViewManager
 RCT_EXPORT_VIEW_PROPERTY(selectTextOnFocus, BOOL)
 RCT_EXPORT_VIEW_PROPERTY(selection, RCTTextSelection)
 RCT_EXPORT_VIEW_PROPERTY(inputAccessoryViewID, NSString)
+RCT_EXPORT_VIEW_PROPERTY(textContentType, NSString)
 
 RCT_EXPORT_VIEW_PROPERTY(onChange, RCTBubblingEventBlock)
 RCT_EXPORT_VIEW_PROPERTY(onSelectionChange, RCTDirectEventBlock)

From 201e74f9b7bc2814a4ecdba16fd425e999798532 Mon Sep 17 00:00:00 2001
From: Douglas Lowder <dlowder@salesforce.com>
Date: Mon, 2 Apr 2018 22:20:34 -0700
Subject: [PATCH 0179/1109] Fix tvOS build breakage in RCTAnimation Xcode
 project

Summary:
`RCTSubtractionAnimatedNode.m` was not added to the tvOS build of RCTAnimation... this PR fixes the issue.

tvOS CI should succeed after this change.

[TVOS] [BUGFIX] [RCTAnimation] Fix build breakage
Closes https://github.com/facebook/react-native/pull/18663

Differential Revision: D7483586

Pulled By: hramos

fbshipit-source-id: 521152d829b064b7002dc8651a0558373c5505f8
---
 .../NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj      | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
index 08a629eaecca..b55c034809b4 100644
--- a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
+++ b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
@@ -111,6 +111,7 @@
 		2D3B5EFE1D9B0B4800451313 /* RCTStyleAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E501E31D07A6C9005F35D8 /* RCTStyleAnimatedNode.m */; };
 		2D3B5EFF1D9B0B4800451313 /* RCTTransformAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E501E51D07A6C9005F35D8 /* RCTTransformAnimatedNode.m */; };
 		2D3B5F001D9B0B4800451313 /* RCTValueAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E501E71D07A6C9005F35D8 /* RCTValueAnimatedNode.m */; };
+		2D65C80020732E4700C62FDF /* RCTSubtractionAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 2EC00630206EA19300586E91 /* RCTSubtractionAnimatedNode.m */; };
 		2EC00631206EA19300586E91 /* RCTSubtractionAnimatedNode.m in Sources */ = {isa = PBXBuildFile; fileRef = 2EC00630206EA19300586E91 /* RCTSubtractionAnimatedNode.m */; };
 		44DB7D942024F74200588FCD /* RCTTrackingAnimatedNode.h in Headers */ = {isa = PBXBuildFile; fileRef = 44DB7D932024F74200588FCD /* RCTTrackingAnimatedNode.h */; };
 		44DB7D952024F74200588FCD /* RCTTrackingAnimatedNode.h in Headers */ = {isa = PBXBuildFile; fileRef = 44DB7D932024F74200588FCD /* RCTTrackingAnimatedNode.h */; };
@@ -462,6 +463,7 @@
 				944244D11DB962DC0032A02B /* RCTSpringAnimation.m in Sources */,
 				9476E8EC1DC9232D005D5CD1 /* RCTNativeAnimatedNodesManager.m in Sources */,
 				194804F21E977DDB00623005 /* RCTDecayAnimation.m in Sources */,
+				2D65C80020732E4700C62FDF /* RCTSubtractionAnimatedNode.m in Sources */,
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};

From 976712afa3e350f3e8d18287b8292f63d274702e Mon Sep 17 00:00:00 2001
From: Paco Estevez Garcia <festevezga@fb.com>
Date: Tue, 3 Apr 2018 05:59:07 -0700
Subject: [PATCH 0180/1109] Replace RN exception handling override with new
 version

Reviewed By: Hypuk

Differential Revision: D7385541

fbshipit-source-id: 287d3f4d681046f740ed0552e00a2249c3803a0b
---
 Libraries/BatchedBridge/BatchedBridge.js      | 15 +----
 Libraries/BatchedBridge/MessageQueue.js       | 54 ++++++++--------
 .../__tests__/MessageQueue-test.js            | 64 +++++--------------
 3 files changed, 43 insertions(+), 90 deletions(-)

diff --git a/Libraries/BatchedBridge/BatchedBridge.js b/Libraries/BatchedBridge/BatchedBridge.js
index bfc6862cb835..516c2ac1e223 100644
--- a/Libraries/BatchedBridge/BatchedBridge.js
+++ b/Libraries/BatchedBridge/BatchedBridge.js
@@ -11,20 +11,7 @@
 
 const MessageQueue = require('MessageQueue');
 
-// MessageQueue can install a global handler to catch all exceptions where JS users can register their own behavior
-// This handler makes all exceptions to be handled inside MessageQueue rather than by the VM at its origin
-// This makes stacktraces to be placed at MessageQueue rather than at where they were launched
-// The parameter __fbUninstallRNGlobalErrorHandler is passed to MessageQueue to prevent the handler from being installed
-//
-// __fbUninstallRNGlobalErrorHandler is conditionally set by the Inspector while the VM is paused for initialization
-// If the Inspector isn't present it defaults to undefined and the global error handler is installed
-// The Inspector can still call MessageQueue#uninstallGlobalErrorHandler to uninstalled on attach
-
-const BatchedBridge = new MessageQueue(
-  // $FlowFixMe
-  typeof __fbUninstallRNGlobalErrorHandler !== 'undefined' &&
-    __fbUninstallRNGlobalErrorHandler === true, // eslint-disable-line no-undef
-);
+const BatchedBridge = new MessageQueue();
 
 // Wire up the batched bridge on the global object so that we can call into it.
 // Ideally, this would be the inverse relationship. I.e. the native environment
diff --git a/Libraries/BatchedBridge/MessageQueue.js b/Libraries/BatchedBridge/MessageQueue.js
index 98662c28cc6d..ef689333917d 100644
--- a/Libraries/BatchedBridge/MessageQueue.js
+++ b/Libraries/BatchedBridge/MessageQueue.js
@@ -57,9 +57,7 @@ class MessageQueue {
 
   __spy: ?(data: SpyData) => void;
 
-  __guard: (() => void) => void;
-
-  constructor(shouldUninstallGlobalErrorHandler: boolean = false) {
+  constructor() {
     this._lazyCallableModules = {};
     this._queue = [[], [], [], 0];
     this._successCallbacks = {};
@@ -67,11 +65,6 @@ class MessageQueue {
     this._callID = 0;
     this._lastFlush = 0;
     this._eventLoopStartTime = new Date().getTime();
-    if (shouldUninstallGlobalErrorHandler) {
-      this.uninstallGlobalErrorHandler();
-    } else {
-      this.installGlobalErrorHandler();
-    }
 
     if (__DEV__) {
       this._debugInfo = {};
@@ -289,34 +282,39 @@ class MessageQueue {
     }
   }
 
-  uninstallGlobalErrorHandler() {
-    this.__guard = this.__guardUnsafe;
-  }
-
-  installGlobalErrorHandler() {
-    this.__guard = this.__guardSafe;
-  }
-
   /**
    * Private methods
    */
 
-  // Lets exceptions propagate to be handled by the VM at the origin
-  __guardUnsafe(fn: () => void) {
+  __guard(fn: () => void) {
     this._inCall++;
-    fn();
+    if (this.__shouldPauseOnThrow()) {
+      fn();
+    } else {
+      try {
+        fn();
+      } catch (error) {
+        ErrorUtils.reportFatalError(error);
+      }
+    }
     this._inCall--;
   }
 
-  __guardSafe(fn: () => void) {
-    this._inCall++;
-    try {
-      fn();
-    } catch (error) {
-      ErrorUtils.reportFatalError(error);
-    } finally {
-      this._inCall--;
-    }
+  // MessageQueue installs a global handler to catch all exceptions where JS users can register their own behavior
+  // This handler makes all exceptions to be propagated from inside MessageQueue rather than by the VM at their origin
+  // This makes stacktraces to be placed at MessageQueue rather than at where they were launched
+  // The parameter DebuggerInternal.shouldPauseOnThrow is used to check before catching all exceptions and
+  // can be configured by the VM or any Inspector
+  __shouldPauseOnThrow() {
+    return (
+      // $FlowFixMe
+      (typeof DebuggerInternal !== 'undefined' &&
+        DebuggerInternal.shouldPauseOnThrow === true) || // eslint-disable-line no-undef
+      // FIXME(festevezga) Remove once T24034309 is rolled out internally
+      // $FlowFixMe
+      (typeof __fbUninstallRNGlobalErrorHandler !== 'undefined' &&
+        __fbUninstallRNGlobalErrorHandler === true) // eslint-disable-line no-undef
+    );
   }
 
   __callImmediates() {
diff --git a/Libraries/BatchedBridge/__tests__/MessageQueue-test.js b/Libraries/BatchedBridge/__tests__/MessageQueue-test.js
index ecf60bcd0455..555a9e2053be 100644
--- a/Libraries/BatchedBridge/__tests__/MessageQueue-test.js
+++ b/Libraries/BatchedBridge/__tests__/MessageQueue-test.js
@@ -125,59 +125,27 @@ describe('MessageQueue', function() {
     expect(factory).toHaveBeenCalledTimes(1);
   });
 
-  it('should catch all exceptions if the global error handler is installed', () => {
-    const errorMessage = 'intentional error';
-    const errorModule = {
-      explode: function() {
-        throw new Error(errorMessage);
-      },
+  it('should check if the global error handler is not overriden by the DebuggerInternal object', () => {
+    const dummyModule = {
+      dummy: function() {},
     };
-    const name = 'errorModuleName';
-    const factory = jest.fn(() => errorModule);
-    queue.__guardSafe = jest.fn(() => {});
-    queue.__guardUnsafe = jest.fn(() => {});
-    queue.installGlobalErrorHandler();
-    queue.registerLazyCallableModule(name, factory);
-    queue.callFunctionReturnFlushedQueue(name, 'explode', []);
-    expect(queue.__guardUnsafe).toHaveBeenCalledTimes(0);
-    expect(queue.__guardSafe).toHaveBeenCalledTimes(2);
-  });
-
-  it('should propagate exceptions if the global error handler is uninstalled', () => {
-    queue.uninstallGlobalErrorHandler();
-    const errorMessage = 'intentional error';
-    const errorModule = {
-      explode: function() {
-        throw new Error(errorMessage);
-      },
-    };
-    const name = 'errorModuleName';
-    const factory = jest.fn(() => errorModule);
-    queue.__guardUnsafe = jest.fn(() => {});
-    queue.__guardSafe = jest.fn(() => {});
+    const name = 'emptyModuleName';
+    const factory = jest.fn(() => dummyModule);
+    queue.__shouldPauseOnThrow = jest.fn(() => false);
     queue.registerLazyCallableModule(name, factory);
-    queue.uninstallGlobalErrorHandler();
-    queue.callFunctionReturnFlushedQueue(name, 'explode');
-    expect(queue.__guardUnsafe).toHaveBeenCalledTimes(2);
-    expect(queue.__guardSafe).toHaveBeenCalledTimes(0);
+    queue.callFunctionReturnFlushedQueue(name, 'dummy', []);
+    expect(queue.__shouldPauseOnThrow).toHaveBeenCalledTimes(2);
   });
 
-  it('should catch all exceptions if the global error handler is re-installed', () => {
-    const errorMessage = 'intentional error';
-    const errorModule = {
-      explode: function() {
-        throw new Error(errorMessage);
-      },
+  it('should check if the global error handler is overriden by the DebuggerInternal object', () => {
+    const dummyModule = {
+      dummy: function() {},
     };
-    const name = 'errorModuleName';
-    const factory = jest.fn(() => errorModule);
-    queue.__guardUnsafe = jest.fn(() => {});
-    queue.__guardSafe = jest.fn(() => {});
+    const name = 'emptyModuleName';
+    const factory = jest.fn(() => dummyModule);
+    queue.__shouldPauseOnThrow = jest.fn(() => true);
     queue.registerLazyCallableModule(name, factory);
-    queue.uninstallGlobalErrorHandler();
-    queue.installGlobalErrorHandler();
-    queue.callFunctionReturnFlushedQueue(name, 'explode');
-    expect(queue.__guardUnsafe).toHaveBeenCalledTimes(0);
-    expect(queue.__guardSafe).toHaveBeenCalledTimes(2);
+    queue.callFunctionReturnFlushedQueue(name, 'dummy', []);
+    expect(queue.__shouldPauseOnThrow).toHaveBeenCalledTimes(2);
   });
 });

From e5a4d59244caaae64a08575b0f928033edcd661f Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Tue, 3 Apr 2018 14:56:27 -0700
Subject: [PATCH 0181/1109] Remove the usage of YGUndefined for kYGValueAuto
 and fix setter and getter of dimensions

Reviewed By: emilsjolander

Differential Revision: D7302453

fbshipit-source-id: e002a1ddd75bfc6fe142a7275e7913c064972e16
---
 ReactCommon/yoga/yoga/YGStyle.cpp |  4 ++--
 ReactCommon/yoga/yoga/Yoga.cpp    | 28 ++++++++++++++++------------
 2 files changed, 18 insertions(+), 14 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index 437b682d6146..66e4d04ccccf 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -9,7 +9,7 @@
 
 const YGValue kYGValueUndefined = {0, YGUnitUndefined};
 
-const YGValue kYGValueAuto = {YGUndefined, YGUnitAuto};
+const YGValue kYGValueAuto = {0, YGUnitAuto};
 
 const std::array<YGValue, YGEdgeCount> kYGDefaultEdgeValuesUnit = {
     {kYGValueUndefined,
@@ -42,7 +42,7 @@ YGStyle::YGStyle()
       flex(YGFloatOptional()),
       flexGrow(YGFloatOptional()),
       flexShrink(YGFloatOptional()),
-      flexBasis({0, YGUnitAuto}),
+      flexBasis(kYGValueAuto),
       margin(kYGDefaultEdgeValuesUnit),
       position(kYGDefaultEdgeValuesUnit),
       padding(kYGDefaultEdgeValuesUnit),
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 7518e858603a..b13b28e1cbbe 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -629,7 +629,7 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
     type, name, paramName, instanceName)                                       \
   void YGNodeStyleSet##name(const YGNodeRef node, const type paramName) {      \
     YGValue value = {                                                          \
-        .value = paramName,                                                    \
+        .value = YGFloatSanitize(paramName),                                   \
         .unit = YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint, \
     };                                                                         \
     if ((node->getStyle().instanceName.value != value.value &&                 \
@@ -644,10 +644,10 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
                                                                                \
   void YGNodeStyleSet##name##Percent(                                          \
       const YGNodeRef node, const type paramName) {                            \
-    if (node->getStyle().instanceName.value != paramName ||                    \
+    if (node->getStyle().instanceName.value != YGFloatSanitize(paramName) ||   \
         node->getStyle().instanceName.unit != YGUnitPercent) {                 \
       YGStyle style = node->getStyle();                                        \
-      style.instanceName.value = paramName;                                    \
+      style.instanceName.value = YGFloatSanitize(paramName);                   \
       style.instanceName.unit =                                                \
           YGFloatIsUndefined(paramName) ? YGUnitAuto : YGUnitPercent;          \
       node->setStyle(style);                                                   \
@@ -658,7 +658,7 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
   void YGNodeStyleSet##name##Auto(const YGNodeRef node) {                      \
     if (node->getStyle().instanceName.unit != YGUnitAuto) {                    \
       YGStyle style = node->getStyle();                                        \
-      style.instanceName.value = YGUndefined;                                  \
+      style.instanceName.value = 0;                                            \
       style.instanceName.unit = YGUnitAuto;                                    \
       node->setStyle(style);                                                   \
       node->markDirtyAndPropogate();                                           \
@@ -678,19 +678,23 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
                                                                               \
   type YGNodeStyleGet##name(const YGNodeRef node) {                           \
     YGValue value = node->getStyle().instanceName;                            \
-    if (value.unit == YGUndefined || value.unit == YGUnitAuto) {              \
+    if (value.unit == YGUnitUndefined || value.unit == YGUnitAuto) {          \
       value.value = YGUndefined;                                              \
     }                                                                         \
     return value;                                                             \
   }
 
-#define YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(      \
-    type, name, paramName, instanceName)            \
-  YG_NODE_STYLE_PROPERTY_SETTER_UNIT_AUTO_IMPL(     \
-      float, name, paramName, instanceName)         \
-                                                    \
-  type YGNodeStyleGet##name(const YGNodeRef node) { \
-    return node->getStyle().instanceName;           \
+#define YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(                       \
+    type, name, paramName, instanceName)                             \
+  YG_NODE_STYLE_PROPERTY_SETTER_UNIT_AUTO_IMPL(                      \
+      float, name, paramName, instanceName)                          \
+                                                                     \
+  type YGNodeStyleGet##name(const YGNodeRef node) {                  \
+    YGValue value = node->getStyle().instanceName;                   \
+    if (value.unit == YGUnitUndefined || value.unit == YGUnitAuto) { \
+      value.value = YGUndefined;                                     \
+    }                                                                \
+    return value;                                                    \
   }
 
 #define YG_NODE_STYLE_EDGE_PROPERTY_UNIT_AUTO_IMPL(type, name, instanceName) \

From bcd12f1e87634343efe238691a535eabfcc21260 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Tue, 3 Apr 2018 14:56:29 -0700
Subject: [PATCH 0182/1109] Change the type of aspect Ratio to YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7302651

fbshipit-source-id: 53e3b4c9627207a379f927b1f3485e36a9c70601
---
 .../fabric/view/yoga/YogaStylableProps.cpp    |  4 +-
 ReactCommon/yoga/yoga/YGStyle.cpp             |  9 ++-
 ReactCommon/yoga/yoga/YGStyle.h               |  2 +-
 ReactCommon/yoga/yoga/Yoga.cpp                | 62 ++++++++++++-------
 4 files changed, 47 insertions(+), 30 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
index 24a2ca5682da..c13e3462dfce 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
@@ -95,7 +95,7 @@ void YogaStylableProps::apply(const RawProps &rawProps) {
     YOGA_STYLE_PREFIXED_EDGE_PROPERTY(padding)
     YOGA_STYLE_PREFIXED_EDGE_PROPERTY(border)
 
-    YOGA_STYLE_SIMPLE_FLOAT_PROPERTY(aspectRatio)
+    YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(aspectRatio)
   }
 }
 
@@ -139,7 +139,7 @@ SharedDebugStringConvertibleList YogaStylableProps::getDebugProps() const {
   YOGA_STYLE_PROPS_ADD_TO_SET(minSize, minDimensions, , stringFromYogaStyleDimensions)
   YOGA_STYLE_PROPS_ADD_TO_SET(maxSize, maxDimensions, , stringFromYogaStyleDimensions)
 
-  YOGA_STYLE_PROPS_ADD_TO_SET(aspectRatio, aspectRatio, , folly::to<std::string>)
+  YOGA_STYLE_PROPS_ADD_TO_SET(aspectRatio, aspectRatio, , stringFromYogaStyleOptionalFloat)
 
   return list;
 }
diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index 66e4d04ccccf..7664dcf8e59c 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -50,7 +50,7 @@ YGStyle::YGStyle()
       dimensions(kYGDefaultDimensionValuesAutoUnit),
       minDimensions(kYGDefaultDimensionValuesUnit),
       maxDimensions(kYGDefaultDimensionValuesUnit),
-      aspectRatio(YGUndefined) {}
+      aspectRatio(YGFloatOptional()) {}
 
 // Yoga specific properties, not compatible with flexbox specification
 bool YGStyle::operator==(const YGStyle& style) {
@@ -91,10 +91,9 @@ bool YGStyle::operator==(const YGStyle& style) {
         flexShrink.getValue() == style.flexShrink.getValue();
   }
 
-  if (!(YGFloatIsUndefined(aspectRatio) &&
-        YGFloatIsUndefined(style.aspectRatio))) {
-    areNonFloatValuesEqual =
-        areNonFloatValuesEqual && aspectRatio == style.aspectRatio;
+  if (!(aspectRatio.isUndefined() && style.aspectRatio.isUndefined())) {
+    areNonFloatValuesEqual = areNonFloatValuesEqual &&
+        aspectRatio.getValue() == style.aspectRatio.getValue();
   }
 
   return areNonFloatValuesEqual;
diff --git a/ReactCommon/yoga/yoga/YGStyle.h b/ReactCommon/yoga/yoga/YGStyle.h
index 7a7f519a5f9b..f0f97bd8faf1 100644
--- a/ReactCommon/yoga/yoga/YGStyle.h
+++ b/ReactCommon/yoga/yoga/YGStyle.h
@@ -32,7 +32,7 @@ struct YGStyle {
   std::array<YGValue, 2> dimensions;
   std::array<YGValue, 2> minDimensions;
   std::array<YGValue, 2> maxDimensions;
-  float aspectRatio;
+  YGFloatOptional aspectRatio;
 
   YGStyle();
   // Yoga specific properties, not compatible with flexbox specification
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index b13b28e1cbbe..f00133e2fe89 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -930,16 +930,30 @@ float YGNodeStyleGetBorder(const YGNodeRef node, const YGEdge edge) {
   return node->getStyle().border[edge].value;
 }
 
+// Yoga specific properties, not compatible with flexbox specification
+
+// TODO(T26792433): Change the API to accept YGFloatOptional.
+float YGNodeStyleGetAspectRatio(const YGNodeRef node) {
+  const YGFloatOptional op = node->getStyle().aspectRatio;
+  return op.isUndefined() ? YGUndefined : op.getValue();
+}
+
+// TODO(T26792433): Change the API to accept YGFloatOptional.
+void YGNodeStyleSetAspectRatio(const YGNodeRef node, const float aspectRatio) {
+  if (!YGFloatOptionalFloatEquals(node->getStyle().aspectRatio, aspectRatio)) {
+    YGStyle style = node->getStyle();
+    style.aspectRatio = YGFloatOptional(aspectRatio);
+    node->setStyle(style);
+    node->markDirtyAndPropogate();
+  }
+}
+
 YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Width, width, dimensions[YGDimensionWidth]);
 YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Height, height, dimensions[YGDimensionHeight]);
 YG_NODE_STYLE_PROPERTY_UNIT_IMPL(YGValue, MinWidth, minWidth, minDimensions[YGDimensionWidth]);
 YG_NODE_STYLE_PROPERTY_UNIT_IMPL(YGValue, MinHeight, minHeight, minDimensions[YGDimensionHeight]);
 YG_NODE_STYLE_PROPERTY_UNIT_IMPL(YGValue, MaxWidth, maxWidth, maxDimensions[YGDimensionWidth]);
 YG_NODE_STYLE_PROPERTY_UNIT_IMPL(YGValue, MaxHeight, maxHeight, maxDimensions[YGDimensionHeight]);
-
-// Yoga specific properties, not compatible with flexbox specification
-YG_NODE_STYLE_PROPERTY_IMPL(float, AspectRatio, aspectRatio, aspectRatio);
-
 YG_NODE_LAYOUT_PROPERTY_IMPL(float, Left, position[YGEdgeLeft]);
 YG_NODE_LAYOUT_PROPERTY_IMPL(float, Top, position[YGEdgeTop]);
 YG_NODE_LAYOUT_PROPERTY_IMPL(float, Right, position[YGEdgeRight]);
@@ -1278,14 +1292,15 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
       }
     }
 
-    if (!YGFloatIsUndefined(child->getStyle().aspectRatio)) {
+    if (!child->getStyle().aspectRatio.isUndefined()) {
       if (!isMainAxisRow && childWidthMeasureMode == YGMeasureModeExactly) {
         childHeight = marginColumn +
-            (childWidth - marginRow) / child->getStyle().aspectRatio;
+            (childWidth - marginRow) / child->getStyle().aspectRatio.getValue();
         childHeightMeasureMode = YGMeasureModeExactly;
       } else if (isMainAxisRow && childHeightMeasureMode == YGMeasureModeExactly) {
         childWidth = marginRow +
-            (childHeight - marginColumn) * child->getStyle().aspectRatio;
+            (childHeight - marginColumn) *
+                child->getStyle().aspectRatio.getValue();
         childWidthMeasureMode = YGMeasureModeExactly;
       }
     }
@@ -1300,8 +1315,9 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
     if (!isMainAxisRow && !isRowStyleDimDefined && hasExactWidth && childWidthStretch) {
       childWidth = width;
       childWidthMeasureMode = YGMeasureModeExactly;
-      if (!YGFloatIsUndefined(child->getStyle().aspectRatio)) {
-        childHeight = (childWidth - marginRow) / child->getStyle().aspectRatio;
+      if (!child->getStyle().aspectRatio.isUndefined()) {
+        childHeight =
+            (childWidth - marginRow) / child->getStyle().aspectRatio.getValue();
         childHeightMeasureMode = YGMeasureModeExactly;
       }
     }
@@ -1313,9 +1329,9 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
       childHeight = height;
       childHeightMeasureMode = YGMeasureModeExactly;
 
-      if (!YGFloatIsUndefined(child->getStyle().aspectRatio)) {
-        childWidth =
-            (childHeight - marginColumn) * child->getStyle().aspectRatio;
+      if (!child->getStyle().aspectRatio.isUndefined()) {
+        childWidth = (childHeight - marginColumn) *
+            child->getStyle().aspectRatio.getValue();
         childWidthMeasureMode = YGMeasureModeExactly;
       }
     }
@@ -1411,13 +1427,14 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
   // Exactly one dimension needs to be defined for us to be able to do aspect ratio
   // calculation. One dimension being the anchor and the other being flexible.
   if (YGFloatIsUndefined(childWidth) ^ YGFloatIsUndefined(childHeight)) {
-    if (!YGFloatIsUndefined(child->getStyle().aspectRatio)) {
+    if (!child->getStyle().aspectRatio.isUndefined()) {
       if (YGFloatIsUndefined(childWidth)) {
         childWidth = marginRow +
-            (childHeight - marginColumn) * child->getStyle().aspectRatio;
+            (childHeight - marginColumn) *
+                child->getStyle().aspectRatio.getValue();
       } else if (YGFloatIsUndefined(childHeight)) {
         childHeight = marginColumn +
-            (childWidth - marginRow) / child->getStyle().aspectRatio;
+            (childWidth - marginRow) / child->getStyle().aspectRatio.getValue();
       }
     }
   }
@@ -1997,11 +2014,11 @@ static float YGDistributeFreeSpaceSecondPass(
     YGMeasureMode childCrossMeasureMode;
     YGMeasureMode childMainMeasureMode = YGMeasureModeExactly;
 
-    if (!YGFloatIsUndefined(currentRelativeChild->getStyle().aspectRatio)) {
+    if (!currentRelativeChild->getStyle().aspectRatio.isUndefined()) {
       childCrossSize = isMainAxisRow ? (childMainSize - marginMain) /
-              currentRelativeChild->getStyle().aspectRatio
+              currentRelativeChild->getStyle().aspectRatio.getValue()
                                      : (childMainSize - marginMain) *
-              currentRelativeChild->getStyle().aspectRatio;
+              currentRelativeChild->getStyle().aspectRatio.getValue();
       childCrossMeasureMode = YGMeasureModeExactly;
 
       childCrossSize += marginCross;
@@ -2889,11 +2906,12 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               float childMainSize =
                   child->getLayout().measuredDimensions[dim[mainAxis]];
               float childCrossSize =
-                  !YGFloatIsUndefined(child->getStyle().aspectRatio)
+                  !child->getStyle().aspectRatio.isUndefined()
                   ? ((child->getMarginForAxis(crossAxis, availableInnerWidth) +
-                      (isMainAxisRow
-                           ? childMainSize / child->getStyle().aspectRatio
-                           : childMainSize * child->getStyle().aspectRatio)))
+                      (isMainAxisRow ? childMainSize /
+                               child->getStyle().aspectRatio.getValue()
+                                     : childMainSize *
+                               child->getStyle().aspectRatio.getValue())))
                   : collectedFlexItemsValues.crossDim;
 
               childMainSize +=

From 63c073d994322a55a421a085dc9055deb16b9f27 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Tue, 3 Apr 2018 14:56:31 -0700
Subject: [PATCH 0183/1109] Move equaltiy function from utils to an operator on
 YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7303460

fbshipit-source-id: 41ec0076ace621ec1a5bdbab00b72eea57780fff
---
 ReactCommon/yoga/yoga/Utils.cpp           |  6 ------
 ReactCommon/yoga/yoga/Utils.h             |  6 ------
 ReactCommon/yoga/yoga/YGFloatOptional.cpp | 23 +++++++++++++++++++++++
 ReactCommon/yoga/yoga/YGFloatOptional.h   |  6 ++++++
 ReactCommon/yoga/yoga/Yoga.cpp            |  8 ++++----
 5 files changed, 33 insertions(+), 16 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.cpp b/ReactCommon/yoga/yoga/Utils.cpp
index aec7564fb66b..5c670c31db26 100644
--- a/ReactCommon/yoga/yoga/Utils.cpp
+++ b/ReactCommon/yoga/yoga/Utils.cpp
@@ -57,9 +57,3 @@ float YGFloatSanitize(const float& val) {
 float YGUnwrapFloatOptional(const YGFloatOptional& op) {
   return op.isUndefined() ? YGUndefined : op.getValue();
 }
-
-bool YGFloatOptionalFloatEquals(
-    const YGFloatOptional& optional,
-    const float& val) {
-  return YGUnwrapFloatOptional(optional) == val;
-}
diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index 34284d2c3513..328ccef71057 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -94,12 +94,6 @@ float YGFloatSanitize(const float& val);
 // TODO: Get rid off this function
 float YGUnwrapFloatOptional(const YGFloatOptional& op);
 
-// This function returns true if val and optional both are undefined or if val
-// and optional.val is true, otherwise its false.
-bool YGFloatOptionalFloatEquals(
-    const YGFloatOptional& optional,
-    const float& val);
-
 YGFlexDirection YGFlexDirectionCross(
     const YGFlexDirection flexDirection,
     const YGDirection direction);
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.cpp b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
index af9a6fc42ad7..380e7880cefd 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.cpp
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
@@ -8,6 +8,7 @@
 #include "YGFloatOptional.h"
 #include <cstdlib>
 #include <iostream>
+#include "Yoga.h"
 
 YGFloatOptional::YGFloatOptional(const float& value)
     : value_(value), isUndefined_(false) {}
@@ -30,3 +31,25 @@ void YGFloatOptional::setValue(const float& val) {
 bool YGFloatOptional::isUndefined() const {
   return isUndefined_;
 }
+
+bool YGFloatOptional::operator==(const YGFloatOptional& op) const {
+  if (isUndefined_ == op.isUndefined()) {
+    return isUndefined_ ? true : value_ == op.getValue();
+  }
+  return false;
+}
+
+bool YGFloatOptional::operator!=(const YGFloatOptional& op) const {
+  return !(*this == op);
+}
+
+bool YGFloatOptional::operator==(const float& val) const {
+  if (YGFloatIsUndefined(val) == isUndefined_) {
+    return isUndefined_ ? true : val == value_;
+  }
+  return false;
+}
+
+bool YGFloatOptional::operator!=(const float& val) const {
+  return !(*this == val);
+}
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.h b/ReactCommon/yoga/yoga/YGFloatOptional.h
index d82230be3ff7..1f633c3656d8 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.h
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.h
@@ -23,4 +23,10 @@ struct YGFloatOptional {
   void setValue(const float& val);
 
   bool isUndefined() const;
+
+  bool operator==(const YGFloatOptional& op) const;
+  bool operator!=(const YGFloatOptional& op) const;
+
+  bool operator==(const float& val) const;
+  bool operator!=(const float& val) const;
 };
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index f00133e2fe89..af5b2b410717 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -801,7 +801,7 @@ YG_NODE_STYLE_PROPERTY_IMPL(YGDisplay, Display, display, display);
 
 // TODO(T26792433): Change the API to accept YGFloatOptional.
 void YGNodeStyleSetFlex(const YGNodeRef node, const float flex) {
-  if (!YGFloatOptionalFloatEquals(node->getStyle().flex, flex)) {
+  if (node->getStyle().flex != flex) {
     YGStyle style = node->getStyle();
     if (YGFloatIsUndefined(flex)) {
       style.flex = YGFloatOptional();
@@ -821,7 +821,7 @@ float YGNodeStyleGetFlex(const YGNodeRef node) {
 
 // TODO(T26792433): Change the API to accept YGFloatOptional.
 void YGNodeStyleSetFlexGrow(const YGNodeRef node, const float flexGrow) {
-  if (!YGFloatOptionalFloatEquals(node->getStyle().flexGrow, flexGrow)) {
+  if (node->getStyle().flexGrow != flexGrow) {
     YGStyle style = node->getStyle();
     if (YGFloatIsUndefined(flexGrow)) {
       style.flexGrow = YGFloatOptional();
@@ -835,7 +835,7 @@ void YGNodeStyleSetFlexGrow(const YGNodeRef node, const float flexGrow) {
 
 // TODO(T26792433): Change the API to accept YGFloatOptional.
 void YGNodeStyleSetFlexShrink(const YGNodeRef node, const float flexShrink) {
-  if (!YGFloatOptionalFloatEquals(node->getStyle().flexShrink, flexShrink)) {
+  if (node->getStyle().flexShrink != flexShrink) {
     YGStyle style = node->getStyle();
     if (YGFloatIsUndefined(flexShrink)) {
       style.flexShrink = YGFloatOptional();
@@ -940,7 +940,7 @@ float YGNodeStyleGetAspectRatio(const YGNodeRef node) {
 
 // TODO(T26792433): Change the API to accept YGFloatOptional.
 void YGNodeStyleSetAspectRatio(const YGNodeRef node, const float aspectRatio) {
-  if (!YGFloatOptionalFloatEquals(node->getStyle().aspectRatio, aspectRatio)) {
+  if (node->getStyle().aspectRatio != aspectRatio) {
     YGStyle style = node->getStyle();
     style.aspectRatio = YGFloatOptional(aspectRatio);
     node->setStyle(style);

From f84f4fd04a96d0af2a4c4b9ba45a5a3543a64f9a Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Tue, 3 Apr 2018 14:56:34 -0700
Subject: [PATCH 0184/1109] Changed the return type of YGResolveValueMargin to
 YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7304090

fbshipit-source-id: cbec03a9367cf34976d083ad475d4da0b736e6d2
---
 ReactCommon/yoga/yoga/Utils.h    |  5 +++--
 ReactCommon/yoga/yoga/YGNode.cpp | 14 ++++++++------
 2 files changed, 11 insertions(+), 8 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index 328ccef71057..1de614ce8852 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -136,8 +136,9 @@ inline YGFlexDirection YGResolveFlexDirection(
   return flexDirection;
 }
 
-static inline float YGResolveValueMargin(
+static inline YGFloatOptional YGResolveValueMargin(
     const YGValue value,
     const float ownerSize) {
-  return value.unit == YGUnitAuto ? 0 : YGUnwrapFloatOptional(YGResolveValue(value, ownerSize));
+  return value.unit == YGUnitAuto ? YGFloatOptional(0)
+                                  : YGResolveValue(value, ownerSize);
 }
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 01be3a7c0328..87a92b394d36 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -144,12 +144,13 @@ float YGNode::getLeadingMargin(
     const float widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.margin[YGEdgeStart].unit != YGUnitUndefined) {
-    return YGResolveValueMargin(style_.margin[YGEdgeStart], widthSize);
+    return YGUnwrapFloatOptional(
+        YGResolveValueMargin(style_.margin[YGEdgeStart], widthSize));
   }
 
-  return YGResolveValueMargin(
+  return YGUnwrapFloatOptional(YGResolveValueMargin(
       *YGComputedEdgeValue(style_.margin, leading[axis], &YGValueZero),
-      widthSize);
+      widthSize));
 }
 
 float YGNode::getTrailingMargin(
@@ -157,12 +158,13 @@ float YGNode::getTrailingMargin(
     const float widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.margin[YGEdgeEnd].unit != YGUnitUndefined) {
-    return YGResolveValueMargin(style_.margin[YGEdgeEnd], widthSize);
+    return YGUnwrapFloatOptional(
+        YGResolveValueMargin(style_.margin[YGEdgeEnd], widthSize));
   }
 
-  return YGResolveValueMargin(
+  return YGUnwrapFloatOptional(YGResolveValueMargin(
       *YGComputedEdgeValue(style_.margin, trailing[axis], &YGValueZero),
-      widthSize);
+      widthSize));
 }
 
 float YGNode::getMarginForAxis(

From 746945824a426a6f16555df0f12f92d836d5cc18 Mon Sep 17 00:00:00 2001
From: Kyle Roach <kroach.work@gmail.com>
Date: Tue, 3 Apr 2018 16:13:58 -0700
Subject: [PATCH 0185/1109] fix(RCTImageLoader): Adds `requiresMainQueueSetup`
 to fix v0.52

Summary:
<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

In react-native v0.52 this warning shows:
```
"RCTImageLoader requires main queue setup
since it overrides `init` but doesn't implement `requiresMainQueueSetup`".
```
This removes the warning by implementing `requiresMainQueueSetup` on RCTImageLoader

* Create new react-native project
* Enable Remote JS Debugging
* Should see no warning regarding RCTImageLoader requiring main queue setup

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[CATEGORY] [TYPE] [LOCATION] - MESSAGE

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
[IOS] [BUGFIX] [Libraries/Image/RCTImageLoader.m] - Implements `requiresMainQueueSetup`
Closes https://github.com/facebook/react-native/pull/17679

Reviewed By: shergin

Differential Revision: D7159601

Pulled By: fkgozali

fbshipit-source-id: e17bae67f4005d2c9ddd0d3701506521f3cac152
---
 Libraries/Image/RCTImageLoader.m | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/Libraries/Image/RCTImageLoader.m b/Libraries/Image/RCTImageLoader.m
index bc50fb03a0ea..775e53e95f7a 100644
--- a/Libraries/Image/RCTImageLoader.m
+++ b/Libraries/Image/RCTImageLoader.m
@@ -58,6 +58,11 @@ - (instancetype)init
   return [self initWithRedirectDelegate:nil];
 }
 
++ (BOOL)requiresMainQueueSetup
+{
+    return NO;
+}
+
 - (instancetype)initWithRedirectDelegate:(id<RCTImageRedirectProtocol>)redirectDelegate
 {
     if (self = [super init]) {

From cdfc34609268327fd8842753b829143f42c8c72e Mon Sep 17 00:00:00 2001
From: Sunny Luo <sunnylqm@qq.com>
Date: Tue, 3 Apr 2018 19:22:38 -0700
Subject: [PATCH 0186/1109] Fix wrong root path in RNTester gradle config
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
Currrent(0.54-stable) root path in RNTester gradle config would cause a failure when trying to compile a release version for RNTester:
```
module.js:545
    throw err;
    ^

Error: Cannot find module ’TheParentDirectoryOfCurrentRepo/local-cli/cli.js'
    at Function.Module._resolveFilename (module.js:543:15)
    at Function.Module._load (module.js:470:25)
    at Function.Module.runMain (module.js:690:10)
    at startup (bootstrap_node.js:194:16)
    at bootstrap_node.js:666:3
:RNTester:android:app:bundleReleaseJsAndAssets FAILED
```

[ANDROID] [INTERNAL] [RNTester] - Fix wrong root path in RNTester gradle config
Closes https://github.com/facebook/react-native/pull/18553

Differential Revision: D7488301

Pulled By: mdvacca

fbshipit-source-id: b49a01820957eb77daeca9c0949f662b668f2bd1
---
 RNTester/android/app/build.gradle | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index 95d02acb788a..bc001b26aca5 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -60,7 +60,7 @@ import com.android.build.OutputFile
 project.ext.react = [
     bundleAssetName: "RNTesterApp.android.bundle",
     entryFile: file("../../js/RNTesterApp.android.js"),
-    root: "../../../../",
+    root: "../../../",
     inputExcludes: ["android/**", "./**"]
 ]
 

From d4add3fc1c3af80239e0f27663f359f2a1665d37 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Lukas=20W=C3=B6hrl?= <lukas@woehrl.net>
Date: Wed, 4 Apr 2018 06:42:36 -0700
Subject: [PATCH 0187/1109] Fix float type mismatch on endOfLineIndex and
 inside rounding

Summary:
This PR fixes a type mismatch on `endOfLineIndex` where it should be of type `uint32_t` while it is of type `float`

Additonally it fixes some `double` casting in the rounding methods.
Closes https://github.com/facebook/yoga/pull/745

Differential Revision: D7494519

Pulled By: emilsjolander

fbshipit-source-id: 30a86574ce163458a6888f61a902d0640c1874fb
---
 ReactCommon/yoga/yoga/Utils.h  | 2 +-
 ReactCommon/yoga/yoga/Yoga.cpp | 6 +++---
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index 1de614ce8852..ce45e348b548 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -40,7 +40,7 @@ struct YGCollectFlexItemsRowValues {
   float sizeConsumedOnCurrentLine;
   float totalFlexGrowFactors;
   float totalFlexShrinkScaledFactors;
-  float endOfLineIndex;
+  uint32_t endOfLineIndex;
   std::vector<YGNodeRef> relativeChildren;
   float remainingFreeSpace;
   // The size of the mainDim for the row after considering size, padding, margin
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index af5b2b410717..0dba65651357 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -3368,12 +3368,12 @@ float YGRoundValueToPixelGrid(const float value,
                               const bool forceCeil,
                               const bool forceFloor) {
   float scaledValue = value * pointScaleFactor;
-  float fractial = fmodf(scaledValue, 1.0);
+  float fractial = fmodf(scaledValue, 1.0f);
   if (YGFloatsEqual(fractial, 0)) {
     // First we check if the value is already rounded
     scaledValue = scaledValue - fractial;
-  } else if (YGFloatsEqual(fractial, 1.0)) {
-    scaledValue = scaledValue - fractial + 1.0;
+  } else if (YGFloatsEqual(fractial, 1.0f)) {
+    scaledValue = scaledValue - fractial + 1.0f;
   } else if (forceCeil) {
     // Next we check if we need to use forced rounding
     scaledValue = scaledValue - fractial + 1.0f;

From 2ace555972a1a09e919e914431e9399111d43671 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:23 -0700
Subject: [PATCH 0188/1109] Made the acccessors method to return const
 references

Reviewed By: emilsjolander

Differential Revision: D7321801

fbshipit-source-id: 9fc4da724bc2f58a0d95824ca3c0b5bf1690bccf
---
 ReactCommon/yoga/yoga/YGFloatOptional.cpp | 4 ++--
 ReactCommon/yoga/yoga/YGFloatOptional.h   | 4 ++--
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.cpp b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
index 380e7880cefd..1947e9f1755a 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.cpp
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
@@ -14,7 +14,7 @@ YGFloatOptional::YGFloatOptional(const float& value)
     : value_(value), isUndefined_(false) {}
 YGFloatOptional::YGFloatOptional() : value_(0), isUndefined_(true) {}
 
-float YGFloatOptional::getValue() const {
+const float& YGFloatOptional::getValue() const {
   if (isUndefined_) {
     // Abort, accessing a value of an undefined float optional
     std::cerr << "Tried to get value of an undefined YGFloatOptional\n";
@@ -28,7 +28,7 @@ void YGFloatOptional::setValue(const float& val) {
   isUndefined_ = false;
 }
 
-bool YGFloatOptional::isUndefined() const {
+const bool& YGFloatOptional::isUndefined() const {
   return isUndefined_;
 }
 
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.h b/ReactCommon/yoga/yoga/YGFloatOptional.h
index 1f633c3656d8..9894e40eb7d7 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.h
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.h
@@ -17,12 +17,12 @@ struct YGFloatOptional {
   // Program will terminate if the value of an undefined is accessed. Please
   // make sure to check if the optional is defined before calling this function.
   // To check if float optional is defined, use `isUndefined()`.
-  float getValue() const;
+  const float& getValue() const;
 
   // Sets the value of float optional, and thus isUndefined is assigned false.
   void setValue(const float& val);
 
-  bool isUndefined() const;
+  const bool& isUndefined() const;
 
   bool operator==(const YGFloatOptional& op) const;
   bool operator!=(const YGFloatOptional& op) const;

From dbb2c6b0fdc3c00fb4a2190c6aa6a1e3d708ff06 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:25 -0700
Subject: [PATCH 0189/1109] Remove the use of YGUnwrapOptional from
 YGConstrainedMaxSizeForMode

Reviewed By: emilsjolander

Differential Revision: D7322743

fbshipit-source-id: d825c60bcdc9ecdc0c784a215dc6b1b8a7a7860e
---
 ReactCommon/yoga/yoga/YGFloatOptional.cpp | 19 +++++++++++++++++--
 ReactCommon/yoga/yoga/YGFloatOptional.h   |  1 +
 ReactCommon/yoga/yoga/YGNode.cpp          |  1 +
 ReactCommon/yoga/yoga/Yoga.cpp            | 16 +++++++++-------
 4 files changed, 28 insertions(+), 9 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.cpp b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
index 1947e9f1755a..5982c307025a 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.cpp
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
@@ -10,8 +10,16 @@
 #include <iostream>
 #include "Yoga.h"
 
-YGFloatOptional::YGFloatOptional(const float& value)
-    : value_(value), isUndefined_(false) {}
+YGFloatOptional::YGFloatOptional(const float& value) {
+  if (YGFloatIsUndefined(value)) {
+    isUndefined_ = true;
+    value_ = 0;
+  } else {
+    value_ = value;
+    isUndefined_ = false;
+  }
+}
+
 YGFloatOptional::YGFloatOptional() : value_(0), isUndefined_(true) {}
 
 const float& YGFloatOptional::getValue() const {
@@ -53,3 +61,10 @@ bool YGFloatOptional::operator==(const float& val) const {
 bool YGFloatOptional::operator!=(const float& val) const {
   return !(*this == val);
 }
+
+YGFloatOptional YGFloatOptional::operator+(const YGFloatOptional& op) {
+  if (!isUndefined_ && !op.isUndefined_) {
+    return YGFloatOptional(value_ + op.value_);
+  }
+  return YGFloatOptional();
+}
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.h b/ReactCommon/yoga/yoga/YGFloatOptional.h
index 9894e40eb7d7..06ae8f15ade4 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.h
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.h
@@ -24,6 +24,7 @@ struct YGFloatOptional {
 
   const bool& isUndefined() const;
 
+  YGFloatOptional operator+(const YGFloatOptional& op);
   bool operator==(const YGFloatOptional& op) const;
   bool operator!=(const YGFloatOptional& op) const;
 
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 87a92b394d36..d10f19414d8e 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -167,6 +167,7 @@ float YGNode::getTrailingMargin(
       widthSize));
 }
 
+// TODO: Make its return type to YGFloatOptional
 float YGNode::getMarginForAxis(
     const YGFlexDirection axis,
     const float widthSize) const {
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 0dba65651357..e10136e7806f 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1178,19 +1178,21 @@ static void YGConstrainMaxSizeForMode(const YGNodeRef node,
                                       const float ownerWidth,
                                       YGMeasureMode *mode,
                                       float *size) {
-  const float maxSize =
-      YGUnwrapFloatOptional(YGResolveValue(
-          node->getStyle().maxDimensions[dim[axis]], ownerAxisSize)) +
-      node->getMarginForAxis(axis, ownerWidth);
+  const YGFloatOptional maxSize =
+      YGResolveValue(
+          node->getStyle().maxDimensions[dim[axis]], ownerAxisSize) +
+      YGFloatOptional(node->getMarginForAxis(axis, ownerWidth));
   switch (*mode) {
     case YGMeasureModeExactly:
     case YGMeasureModeAtMost:
-      *size = (YGFloatIsUndefined(maxSize) || *size < maxSize) ? *size : maxSize;
+      *size = (maxSize.isUndefined() || *size < maxSize.getValue())
+          ? *size
+          : maxSize.getValue();
       break;
     case YGMeasureModeUndefined:
-      if (!YGFloatIsUndefined(maxSize)) {
+      if (!maxSize.isUndefined()) {
         *mode = YGMeasureModeAtMost;
-        *size = maxSize;
+        *size = maxSize.getValue();
       }
       break;
   }

From 20e5193207fe0c060eedf9e685f347de245aa9c7 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:28 -0700
Subject: [PATCH 0190/1109] Make the return type of
 YGNodeBoundAxisWithinMinAndMax to YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7323382

fbshipit-source-id: 8e3eb4f3744b5f3f9e2b353f56184905f7557191
---
 ReactCommon/yoga/yoga/YGFloatOptional.cpp | 22 ++++++++
 ReactCommon/yoga/yoga/YGFloatOptional.h   |  4 ++
 ReactCommon/yoga/yoga/Yoga.cpp            | 64 +++++++++++------------
 3 files changed, 58 insertions(+), 32 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.cpp b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
index 5982c307025a..00bfc71e2df2 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.cpp
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
@@ -68,3 +68,25 @@ YGFloatOptional YGFloatOptional::operator+(const YGFloatOptional& op) {
   }
   return YGFloatOptional();
 }
+
+bool YGFloatOptional::operator>(const YGFloatOptional& op) const {
+  if (isUndefined_ || op.isUndefined_) {
+    return false;
+  }
+  return value_ > op.value_;
+}
+
+bool YGFloatOptional::operator<(const YGFloatOptional& op) const {
+  if (isUndefined_ || op.isUndefined_) {
+    return false;
+  }
+  return value_ < op.value_;
+}
+
+bool YGFloatOptional::operator>=(const YGFloatOptional& op) const {
+  return *this == op ? true : *this > op;
+}
+
+bool YGFloatOptional::operator<=(const YGFloatOptional& op) const {
+  return *this == op ? true : *this < op;
+}
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.h b/ReactCommon/yoga/yoga/YGFloatOptional.h
index 06ae8f15ade4..9ecad46f3fc5 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.h
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.h
@@ -25,6 +25,10 @@ struct YGFloatOptional {
   const bool& isUndefined() const;
 
   YGFloatOptional operator+(const YGFloatOptional& op);
+  bool operator>(const YGFloatOptional& op) const;
+  bool operator<(const YGFloatOptional& op) const;
+  bool operator>=(const YGFloatOptional& op) const;
+  bool operator<=(const YGFloatOptional& op) const;
   bool operator==(const YGFloatOptional& op) const;
   bool operator!=(const YGFloatOptional& op) const;
 
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index e10136e7806f..271eff3a27e0 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1117,36 +1117,35 @@ static inline bool YGNodeIsLayoutDimDefined(const YGNodeRef node, const YGFlexDi
   return !YGFloatIsUndefined(value) && value >= 0.0f;
 }
 
-static float YGNodeBoundAxisWithinMinAndMax(const YGNodeRef node,
-                                            const YGFlexDirection axis,
-                                            const float value,
-                                            const float axisSize) {
-  float min = YGUndefined;
-  float max = YGUndefined;
+static YGFloatOptional YGNodeBoundAxisWithinMinAndMax(
+    const YGNodeRef node,
+    const YGFlexDirection& axis,
+    const float& value,
+    const float& axisSize) {
+  YGFloatOptional min;
+  YGFloatOptional max;
 
   if (YGFlexDirectionIsColumn(axis)) {
-    min = YGUnwrapFloatOptional(YGResolveValue(
-        node->getStyle().minDimensions[YGDimensionHeight], axisSize));
-    max = YGUnwrapFloatOptional(YGResolveValue(
-        node->getStyle().maxDimensions[YGDimensionHeight], axisSize));
+    min = YGResolveValue(
+        node->getStyle().minDimensions[YGDimensionHeight], axisSize);
+    max = YGResolveValue(
+        node->getStyle().maxDimensions[YGDimensionHeight], axisSize);
   } else if (YGFlexDirectionIsRow(axis)) {
-    min = YGUnwrapFloatOptional(YGResolveValue(
-        node->getStyle().minDimensions[YGDimensionWidth], axisSize));
-    max = YGUnwrapFloatOptional(YGResolveValue(
-        node->getStyle().maxDimensions[YGDimensionWidth], axisSize));
+    min = YGResolveValue(
+        node->getStyle().minDimensions[YGDimensionWidth], axisSize);
+    max = YGResolveValue(
+        node->getStyle().maxDimensions[YGDimensionWidth], axisSize);
   }
 
-  float boundValue = value;
-
-  if (!YGFloatIsUndefined(max) && max >= 0.0f && boundValue > max) {
-    boundValue = max;
+  if (!max.isUndefined() && max.getValue() >= 0 && value > max.getValue()) {
+    return max;
   }
 
-  if (!YGFloatIsUndefined(min) && min >= 0.0f && boundValue < min) {
-    boundValue = min;
+  if (!min.isUndefined() && min.getValue() >= 0 && value < min.getValue()) {
+    return min;
   }
 
-  return boundValue;
+  return YGFloatOptional(value);
 }
 
 // Like YGNodeBoundAxisWithinMinAndMax but also ensures that the value doesn't go
@@ -1158,7 +1157,8 @@ static inline float YGNodeBoundAxis(const YGNodeRef node,
                                     const float axisSize,
                                     const float widthSize) {
   return YGFloatMax(
-      YGNodeBoundAxisWithinMinAndMax(node, axis, value, axisSize),
+      YGUnwrapFloatOptional(
+          YGNodeBoundAxisWithinMinAndMax(node, axis, value, axisSize)),
       YGNodePaddingAndBorderForAxis(node, axis, widthSize));
 }
 
@@ -1876,11 +1876,11 @@ static YGCollectFlexItemsRowValues YGCalculateCollectFlexItemsRowValues(
     const float childMarginMainAxis =
         child->getMarginForAxis(mainAxis, availableInnerWidth);
     const float flexBasisWithMinAndMaxConstraints =
-        YGNodeBoundAxisWithinMinAndMax(
+        YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
             child,
             mainAxis,
             child->getLayout().computedFlexBasis,
-            mainAxisownerSize);
+            mainAxisownerSize));
 
     // If this is a multi-line flow and this item pushes us over the
     // available size, we've
@@ -1952,11 +1952,11 @@ static float YGDistributeFreeSpaceSecondPass(
   const bool isNodeFlexWrap = node->getStyle().flexWrap != YGWrapNoWrap;
 
   for (auto currentRelativeChild : collectedFlexItemsValues.relativeChildren) {
-    childFlexBasis = YGNodeBoundAxisWithinMinAndMax(
+    childFlexBasis = YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
         currentRelativeChild,
         mainAxis,
         currentRelativeChild->getLayout().computedFlexBasis,
-        mainAxisownerSize);
+        mainAxisownerSize));
     float updatedMainSize = childFlexBasis;
 
     if (!YGFloatIsUndefined(collectedFlexItemsValues.remainingFreeSpace) &&
@@ -2127,11 +2127,11 @@ static void YGDistributeFreeSpaceFirstPass(
   float deltaFreeSpace = 0;
 
   for (auto currentRelativeChild : collectedFlexItemsValues.relativeChildren) {
-    float childFlexBasis = YGNodeBoundAxisWithinMinAndMax(
+    float childFlexBasis = YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
         currentRelativeChild,
         mainAxis,
         currentRelativeChild->getLayout().computedFlexBasis,
-        mainAxisownerSize);
+        mainAxisownerSize));
 
     if (collectedFlexItemsValues.remainingFreeSpace < 0) {
       flexShrinkScaledFactor =
@@ -3217,8 +3217,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
         YGFloatMax(
             YGFloatMin(
                 availableInnerMainDim + paddingAndBorderAxisMain,
-                YGNodeBoundAxisWithinMinAndMax(
-                    node, mainAxis, maxLineMainDim, mainAxisownerSize)),
+                YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
+                    node, mainAxis, maxLineMainDim, mainAxisownerSize))),
             paddingAndBorderAxisMain),
         dim[mainAxis]);
   }
@@ -3245,11 +3245,11 @@ static void YGNodelayoutImpl(const YGNodeRef node,
         YGFloatMax(
             YGFloatMin(
                 availableInnerCrossDim + paddingAndBorderAxisCross,
-                YGNodeBoundAxisWithinMinAndMax(
+                YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
                     node,
                     crossAxis,
                     totalLineCrossDim + paddingAndBorderAxisCross,
-                    crossAxisownerSize)),
+                    crossAxisownerSize))),
             paddingAndBorderAxisCross),
         dim[crossAxis]);
   }

From 51f5cd4810c1d33023177b9fbd7c1e61060388d4 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:30 -0700
Subject: [PATCH 0191/1109] Updated the implementation of leading padding

Reviewed By: emilsjolander

Differential Revision: D7336690

fbshipit-source-id: b2a2f010026f26fc2cc9fb35ad921da8f7017c9f
---
 ReactCommon/yoga/yoga/Utils.cpp  |  9 +++++++++
 ReactCommon/yoga/yoga/Utils.h    |  4 ++++
 ReactCommon/yoga/yoga/YGNode.cpp | 23 ++++++++++++-----------
 ReactCommon/yoga/yoga/YGNode.h   |  4 +++-
 ReactCommon/yoga/yoga/Yoga.cpp   |  8 ++++++--
 5 files changed, 34 insertions(+), 14 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.cpp b/ReactCommon/yoga/yoga/Utils.cpp
index 5c670c31db26..6fa8df823ba3 100644
--- a/ReactCommon/yoga/yoga/Utils.cpp
+++ b/ReactCommon/yoga/yoga/Utils.cpp
@@ -57,3 +57,12 @@ float YGFloatSanitize(const float& val) {
 float YGUnwrapFloatOptional(const YGFloatOptional& op) {
   return op.isUndefined() ? YGUndefined : op.getValue();
 }
+
+YGFloatOptional YGFloatOptionalMax(
+    const YGFloatOptional& op1,
+    const YGFloatOptional& op2) {
+  if (!op1.isUndefined() && !op2.isUndefined()) {
+    return op1.getValue() > op2.getValue() ? op1 : op2;
+  }
+  return op1.isUndefined() ? op2 : op1;
+}
diff --git a/ReactCommon/yoga/yoga/Utils.h b/ReactCommon/yoga/yoga/Utils.h
index ce45e348b548..6c95b1e7aaf7 100644
--- a/ReactCommon/yoga/yoga/Utils.h
+++ b/ReactCommon/yoga/yoga/Utils.h
@@ -65,6 +65,10 @@ bool YGFloatsEqual(const float a, const float b);
 // compiler flag.
 float YGFloatMax(const float a, const float b);
 
+YGFloatOptional YGFloatOptionalMax(
+    const YGFloatOptional& op1,
+    const YGFloatOptional& op2);
+
 // We need custom min function, since we want that, if one argument is
 // YGUndefined then the min funtion should return the other argument as the min
 // value. We wouldn't have needed a custom min function if YGUndefined was NAN
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index d10f19414d8e..913ec329ecbb 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -654,21 +654,21 @@ float YGNode::getTrailingBorder(const YGFlexDirection flexDirection) const {
   return YGFloatMax(computedEdgeValue, 0.0f);
 }
 
-float YGNode::getLeadingPadding(
-    const YGFlexDirection axis,
-    const float widthSize) const {
+YGFloatOptional YGNode::getLeadingPadding(
+    const YGFlexDirection& axis,
+    const float& widthSize) const {
+  const YGFloatOptional& paddingEdgeStart =
+      YGResolveValue(style_.padding[YGEdgeStart], widthSize);
   if (YGFlexDirectionIsRow(axis) &&
       style_.padding[YGEdgeStart].unit != YGUnitUndefined &&
-      !YGResolveValue(style_.padding[YGEdgeStart], widthSize).isUndefined() &&
-      YGUnwrapFloatOptional(
-          YGResolveValue(style_.padding[YGEdgeStart], widthSize)) > 0.0f) {
-    return YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeStart], widthSize));
+      !paddingEdgeStart.isUndefined() && paddingEdgeStart.getValue() > 0.0f) {
+    return paddingEdgeStart;
   }
 
-  float resolvedValue = YGUnwrapFloatOptional(YGResolveValue(
+  YGFloatOptional resolvedValue = YGResolveValue(
       *YGComputedEdgeValue(style_.padding, leading[axis], &YGValueZero),
-      widthSize));
-  return YGFloatMax(resolvedValue, 0.0f);
+      widthSize);
+  return YGFloatOptionalMax(resolvedValue, YGFloatOptional(0.0f));
 }
 
 float YGNode::getTrailingPadding(
@@ -692,7 +692,8 @@ float YGNode::getTrailingPadding(
 float YGNode::getLeadingPaddingAndBorder(
     const YGFlexDirection axis,
     const float widthSize) const {
-  return getLeadingPadding(axis, widthSize) + getLeadingBorder(axis);
+  return YGUnwrapFloatOptional(getLeadingPadding(axis, widthSize)) +
+      getLeadingBorder(axis);
 }
 
 float YGNode::getTrailingPaddingAndBorder(
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 02afb830e8b4..cdb6fae47c3a 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -93,7 +93,9 @@ struct YGNode {
   float getTrailingMargin(const YGFlexDirection axis, const float widthSize) const;
   float getLeadingBorder(const YGFlexDirection flexDirection) const;
   float getTrailingBorder(const YGFlexDirection flexDirection) const;
-  float getLeadingPadding(const YGFlexDirection axis, const float widthSize) const;
+  YGFloatOptional getLeadingPadding(
+      const YGFlexDirection& axis,
+      const float& widthSize) const;
   float getTrailingPadding(const YGFlexDirection axis, const float widthSize) const;
   float getLeadingPaddingAndBorder(
       const YGFlexDirection axis,
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 271eff3a27e0..12f8facb1ee8 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -2573,11 +2573,15 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       node->getTrailingBorder(flexColumnDirection), YGEdgeBottom);
 
   node->setLayoutPadding(
-      node->getLeadingPadding(flexRowDirection, ownerWidth), YGEdgeStart);
+      YGUnwrapFloatOptional(
+          node->getLeadingPadding(flexRowDirection, ownerWidth)),
+      YGEdgeStart);
   node->setLayoutPadding(
       node->getTrailingPadding(flexRowDirection, ownerWidth), YGEdgeEnd);
   node->setLayoutPadding(
-      node->getLeadingPadding(flexColumnDirection, ownerWidth), YGEdgeTop);
+      YGUnwrapFloatOptional(
+          node->getLeadingPadding(flexColumnDirection, ownerWidth)),
+      YGEdgeTop);
   node->setLayoutPadding(
       node->getTrailingPadding(flexColumnDirection, ownerWidth), YGEdgeBottom);
 

From ee0d621d2aa8c2cb2edb345c84b25e95fe404d57 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:34 -0700
Subject: [PATCH 0192/1109] Changed the return type of trailing padding to
 YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7339712

fbshipit-source-id: 483c5886838c14b17cb731c81abb9fc80f519956
---
 ReactCommon/yoga/yoga/YGNode.cpp | 20 ++++++++++----------
 ReactCommon/yoga/yoga/YGNode.h   |  4 +++-
 ReactCommon/yoga/yoga/Yoga.cpp   |  8 ++++++--
 3 files changed, 19 insertions(+), 13 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 913ec329ecbb..9f6c6a2a8711 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -671,22 +671,21 @@ YGFloatOptional YGNode::getLeadingPadding(
   return YGFloatOptionalMax(resolvedValue, YGFloatOptional(0.0f));
 }
 
-float YGNode::getTrailingPadding(
-    const YGFlexDirection axis,
-    const float widthSize) const {
+YGFloatOptional YGNode::getTrailingPadding(
+    const YGFlexDirection& axis,
+    const float& widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.padding[YGEdgeEnd].unit != YGUnitUndefined &&
       !YGResolveValue(style_.padding[YGEdgeEnd], widthSize).isUndefined() &&
-      YGUnwrapFloatOptional(
-          YGResolveValue(style_.padding[YGEdgeEnd], widthSize)) >= 0.0f) {
-    return YGUnwrapFloatOptional(YGResolveValue(style_.padding[YGEdgeEnd], widthSize));
+      YGResolveValue(style_.padding[YGEdgeEnd], widthSize).getValue() >= 0.0f) {
+    return YGResolveValue(style_.padding[YGEdgeEnd], widthSize);
   }
 
-  float resolvedValue = YGUnwrapFloatOptional(YGResolveValue(
+  YGFloatOptional resolvedValue = YGResolveValue(
       *YGComputedEdgeValue(style_.padding, trailing[axis], &YGValueZero),
-      widthSize));
+      widthSize);
 
-  return YGFloatMax(resolvedValue, 0.0f);
+  return YGFloatOptionalMax(resolvedValue, YGFloatOptional(0.0f));
 }
 
 float YGNode::getLeadingPaddingAndBorder(
@@ -699,7 +698,8 @@ float YGNode::getLeadingPaddingAndBorder(
 float YGNode::getTrailingPaddingAndBorder(
     const YGFlexDirection axis,
     const float widthSize) const {
-  return getTrailingPadding(axis, widthSize) + getTrailingBorder(axis);
+  return YGUnwrapFloatOptional(getTrailingPadding(axis, widthSize)) +
+      getTrailingBorder(axis);
 }
 
 bool YGNode::didUseLegacyFlag() {
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index cdb6fae47c3a..010b0dc7acb3 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -96,7 +96,9 @@ struct YGNode {
   YGFloatOptional getLeadingPadding(
       const YGFlexDirection& axis,
       const float& widthSize) const;
-  float getTrailingPadding(const YGFlexDirection axis, const float widthSize) const;
+  YGFloatOptional getTrailingPadding(
+      const YGFlexDirection& axis,
+      const float& widthSize) const;
   float getLeadingPaddingAndBorder(
       const YGFlexDirection axis,
       const float widthSize) const;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 12f8facb1ee8..8740c6667b20 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -2577,13 +2577,17 @@ static void YGNodelayoutImpl(const YGNodeRef node,
           node->getLeadingPadding(flexRowDirection, ownerWidth)),
       YGEdgeStart);
   node->setLayoutPadding(
-      node->getTrailingPadding(flexRowDirection, ownerWidth), YGEdgeEnd);
+      YGUnwrapFloatOptional(
+          node->getTrailingPadding(flexRowDirection, ownerWidth)),
+      YGEdgeEnd);
   node->setLayoutPadding(
       YGUnwrapFloatOptional(
           node->getLeadingPadding(flexColumnDirection, ownerWidth)),
       YGEdgeTop);
   node->setLayoutPadding(
-      node->getTrailingPadding(flexColumnDirection, ownerWidth), YGEdgeBottom);
+      YGUnwrapFloatOptional(
+          node->getTrailingPadding(flexColumnDirection, ownerWidth)),
+      YGEdgeBottom);
 
   if (node->getMeasure() != nullptr) {
     YGNodeWithMeasureFuncSetMeasuredDimensions(node,

From fe3a9d4013009fe499cf58313643172694a91040 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:37 -0700
Subject: [PATCH 0193/1109] Fixed types of getLeadingPaddingAndBorder and
 getTrailingPaddingAndBorder to YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7339998

fbshipit-source-id: aa24335c2db1cd895b9711214b72195add718c32
---
 ReactCommon/yoga/yoga/YGNode.cpp | 24 ++++++++++++------------
 ReactCommon/yoga/yoga/YGNode.h   | 16 ++++++++--------
 ReactCommon/yoga/yoga/Yoga.cpp   | 17 +++++++++--------
 3 files changed, 29 insertions(+), 28 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 9f6c6a2a8711..06a583951f97 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -627,7 +627,7 @@ bool YGNode::isNodeFlexible() {
       (resolveFlexGrow() != 0 || resolveFlexShrink() != 0));
 }
 
-float YGNode::getLeadingBorder(const YGFlexDirection axis) const {
+float YGNode::getLeadingBorder(const YGFlexDirection& axis) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.border[YGEdgeStart].unit != YGUnitUndefined &&
       !YGFloatIsUndefined(style_.border[YGEdgeStart].value) &&
@@ -640,7 +640,7 @@ float YGNode::getLeadingBorder(const YGFlexDirection axis) const {
   return YGFloatMax(computedEdgeValue, 0.0f);
 }
 
-float YGNode::getTrailingBorder(const YGFlexDirection flexDirection) const {
+float YGNode::getTrailingBorder(const YGFlexDirection& flexDirection) const {
   if (YGFlexDirectionIsRow(flexDirection) &&
       style_.border[YGEdgeEnd].unit != YGUnitUndefined &&
       !YGFloatIsUndefined(style_.border[YGEdgeEnd].value) &&
@@ -688,18 +688,18 @@ YGFloatOptional YGNode::getTrailingPadding(
   return YGFloatOptionalMax(resolvedValue, YGFloatOptional(0.0f));
 }
 
-float YGNode::getLeadingPaddingAndBorder(
-    const YGFlexDirection axis,
-    const float widthSize) const {
-  return YGUnwrapFloatOptional(getLeadingPadding(axis, widthSize)) +
-      getLeadingBorder(axis);
+YGFloatOptional YGNode::getLeadingPaddingAndBorder(
+    const YGFlexDirection& axis,
+    const float& widthSize) const {
+  return getLeadingPadding(axis, widthSize) +
+      YGFloatOptional(getLeadingBorder(axis));
 }
 
-float YGNode::getTrailingPaddingAndBorder(
-    const YGFlexDirection axis,
-    const float widthSize) const {
-  return YGUnwrapFloatOptional(getTrailingPadding(axis, widthSize)) +
-      getTrailingBorder(axis);
+YGFloatOptional YGNode::getTrailingPaddingAndBorder(
+    const YGFlexDirection& axis,
+    const float& widthSize) const {
+  return getTrailingPadding(axis, widthSize) +
+      YGFloatOptional(getTrailingBorder(axis));
 }
 
 bool YGNode::didUseLegacyFlag() {
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 010b0dc7acb3..d65b0b71dc53 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -91,20 +91,20 @@ struct YGNode {
   float getTrailingPosition(const YGFlexDirection axis, const float axisSize) const;
   float getLeadingMargin(const YGFlexDirection axis, const float widthSize) const;
   float getTrailingMargin(const YGFlexDirection axis, const float widthSize) const;
-  float getLeadingBorder(const YGFlexDirection flexDirection) const;
-  float getTrailingBorder(const YGFlexDirection flexDirection) const;
+  float getLeadingBorder(const YGFlexDirection& flexDirection) const;
+  float getTrailingBorder(const YGFlexDirection& flexDirection) const;
   YGFloatOptional getLeadingPadding(
       const YGFlexDirection& axis,
       const float& widthSize) const;
   YGFloatOptional getTrailingPadding(
       const YGFlexDirection& axis,
       const float& widthSize) const;
-  float getLeadingPaddingAndBorder(
-      const YGFlexDirection axis,
-      const float widthSize) const;
-  float getTrailingPaddingAndBorder(
-      const YGFlexDirection axis,
-      const float widthSize) const;
+  YGFloatOptional getLeadingPaddingAndBorder(
+      const YGFlexDirection& axis,
+      const float& widthSize) const;
+  YGFloatOptional getTrailingPaddingAndBorder(
+      const YGFlexDirection& axis,
+      const float& widthSize) const;
   float getMarginForAxis(const YGFlexDirection axis, const float widthSize) const;
   // Setters
 
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 8740c6667b20..19cb30df15ed 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1014,8 +1014,9 @@ static const std::array<YGDimension, 4> dim = {
 static inline float YGNodePaddingAndBorderForAxis(const YGNodeRef node,
                                                   const YGFlexDirection axis,
                                                   const float widthSize) {
-  return node->getLeadingPaddingAndBorder(axis, widthSize) +
-      node->getTrailingPaddingAndBorder(axis, widthSize);
+  return YGUnwrapFloatOptional(
+      node->getLeadingPaddingAndBorder(axis, widthSize) +
+      node->getTrailingPaddingAndBorder(axis, widthSize));
 }
 
 static inline YGAlign YGNodeAlignItem(const YGNodeRef node, const YGNodeRef child) {
@@ -2357,8 +2358,8 @@ static void YGJustifyMainAxis(
     }
   }
 
-  const float leadingPaddingAndBorderMain =
-      node->getLeadingPaddingAndBorder(mainAxis, ownerWidth);
+  const float leadingPaddingAndBorderMain = YGUnwrapFloatOptional(
+      node->getLeadingPaddingAndBorder(mainAxis, ownerWidth));
   collectedFlexItemsValues.mainDim =
       leadingPaddingAndBorderMain + leadingMainDim;
   collectedFlexItemsValues.crossDim = 0;
@@ -2438,8 +2439,8 @@ static void YGJustifyMainAxis(
       }
     }
   }
-  collectedFlexItemsValues.mainDim +=
-      node->getTrailingPaddingAndBorder(mainAxis, ownerWidth);
+  collectedFlexItemsValues.mainDim += YGUnwrapFloatOptional(
+      node->getTrailingPaddingAndBorder(mainAxis, ownerWidth));
 }
 
 //
@@ -2639,8 +2640,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
   const float mainAxisownerSize = isMainAxisRow ? ownerWidth : ownerHeight;
   const float crossAxisownerSize = isMainAxisRow ? ownerHeight : ownerWidth;
 
-  const float leadingPaddingAndBorderCross =
-      node->getLeadingPaddingAndBorder(crossAxis, ownerWidth);
+  const float leadingPaddingAndBorderCross = YGUnwrapFloatOptional(
+      node->getLeadingPaddingAndBorder(crossAxis, ownerWidth));
   const float paddingAndBorderAxisMain = YGNodePaddingAndBorderForAxis(node, mainAxis, ownerWidth);
   const float paddingAndBorderAxisCross =
       YGNodePaddingAndBorderForAxis(node, crossAxis, ownerWidth);

From 0186ccf0068579e6f7c5864c4cf41973d6d8dff1 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:39 -0700
Subject: [PATCH 0194/1109] Changed the type of computedFlexBasis to
 YGFloatOptional in YGLayout

Reviewed By: emilsjolander

Differential Revision: D7340413

fbshipit-source-id: 39247b2b582a682e602f49f58b4bbd2bf0c995af
---
 ReactCommon/yoga/yoga/YGFloatOptional.h |  6 ++-
 ReactCommon/yoga/yoga/YGLayout.cpp      |  9 ++--
 ReactCommon/yoga/yoga/YGLayout.h        |  3 +-
 ReactCommon/yoga/yoga/YGNode.cpp        |  5 ++-
 ReactCommon/yoga/yoga/YGNode.h          |  2 +-
 ReactCommon/yoga/yoga/Yoga.cpp          | 60 ++++++++++++++-----------
 6 files changed, 48 insertions(+), 37 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.h b/ReactCommon/yoga/yoga/YGFloatOptional.h
index 9ecad46f3fc5..21af2a806198 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.h
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.h
@@ -5,14 +5,16 @@
  * LICENSE file in the root directory of this source tree.
  */
 
+#pragma once
+
 struct YGFloatOptional {
  private:
   float value_;
   bool isUndefined_;
 
  public:
-  YGFloatOptional(const float& value);
-  YGFloatOptional();
+  explicit YGFloatOptional(const float& value);
+  explicit YGFloatOptional();
 
   // Program will terminate if the value of an undefined is accessed. Please
   // make sure to check if the optional is defined before calling this function.
diff --git a/ReactCommon/yoga/yoga/YGLayout.cpp b/ReactCommon/yoga/yoga/YGLayout.cpp
index 117638d7a15f..6e367bd50a9b 100644
--- a/ReactCommon/yoga/yoga/YGLayout.cpp
+++ b/ReactCommon/yoga/yoga/YGLayout.cpp
@@ -19,7 +19,7 @@ YGLayout::YGLayout()
       padding(),
       direction(YGDirectionInherit),
       computedFlexBasisGeneration(0),
-      computedFlexBasis(YGUndefined),
+      computedFlexBasis(YGFloatOptional()),
       hadOverflow(false),
       generationCount(0),
       lastOwnerDirection((YGDirection)-1),
@@ -39,16 +39,13 @@ bool YGLayout::operator==(YGLayout layout) const {
       direction == layout.direction && hadOverflow == layout.hadOverflow &&
       lastOwnerDirection == layout.lastOwnerDirection &&
       nextCachedMeasurementsIndex == layout.nextCachedMeasurementsIndex &&
-      cachedLayout == layout.cachedLayout;
+      cachedLayout == layout.cachedLayout &&
+      computedFlexBasis == layout.computedFlexBasis;
 
   for (uint32_t i = 0; i < YG_MAX_CACHED_RESULT_COUNT && isEqual; ++i) {
     isEqual = isEqual && cachedMeasurements[i] == layout.cachedMeasurements[i];
   }
 
-  if (!YGFloatIsUndefined(computedFlexBasis) ||
-      !YGFloatIsUndefined(layout.computedFlexBasis)) {
-    isEqual = isEqual && (computedFlexBasis == layout.computedFlexBasis);
-  }
   if (!YGFloatIsUndefined(measuredDimensions[0]) ||
       !YGFloatIsUndefined(layout.measuredDimensions[0])) {
     isEqual =
diff --git a/ReactCommon/yoga/yoga/YGLayout.h b/ReactCommon/yoga/yoga/YGLayout.h
index 81cc66317a5a..46ca130d29bf 100644
--- a/ReactCommon/yoga/yoga/YGLayout.h
+++ b/ReactCommon/yoga/yoga/YGLayout.h
@@ -6,6 +6,7 @@
  */
 
 #pragma once
+#include "YGFloatOptional.h"
 #include "Yoga-internal.h"
 
 struct YGLayout {
@@ -17,7 +18,7 @@ struct YGLayout {
   YGDirection direction;
 
   uint32_t computedFlexBasisGeneration;
-  float computedFlexBasis;
+  YGFloatOptional computedFlexBasis;
   bool hadOverflow;
 
   // Instead of recomputing the entire layout every single time, we
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 06a583951f97..eb840ef1dde9 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -312,7 +312,8 @@ void YGNode::setLayoutLastOwnerDirection(YGDirection direction) {
   layout_.lastOwnerDirection = direction;
 }
 
-void YGNode::setLayoutComputedFlexBasis(float computedFlexBasis) {
+void YGNode::setLayoutComputedFlexBasis(
+    const YGFloatOptional& computedFlexBasis) {
   layout_.computedFlexBasis = computedFlexBasis;
 }
 
@@ -579,7 +580,7 @@ void YGNode::cloneChildrenIfNeeded() {
 void YGNode::markDirtyAndPropogate() {
   if (!isDirty_) {
     setDirty(true);
-    setLayoutComputedFlexBasis(YGUndefined);
+    setLayoutComputedFlexBasis(YGFloatOptional());
     if (owner_) {
       owner_->markDirtyAndPropogate();
     }
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index d65b0b71dc53..fe24fa037f64 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -126,7 +126,7 @@ struct YGNode {
   void setConfig(YGConfigRef config);
   void setDirty(bool isDirty);
   void setLayoutLastOwnerDirection(YGDirection direction);
-  void setLayoutComputedFlexBasis(float computedFlexBasis);
+  void setLayoutComputedFlexBasis(const YGFloatOptional& computedFlexBasis);
   void setLayoutComputedFlexBasisGeneration(
       uint32_t computedFlexBasisGeneration);
   void setLayoutMeasuredDimension(float measuredDimension, int index);
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 19cb30df15ed..3b117243e709 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1220,35 +1220,41 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
   YGMeasureMode childWidthMeasureMode;
   YGMeasureMode childHeightMeasureMode;
 
-  const float resolvedFlexBasis =
-      YGUnwrapFloatOptional(YGResolveValue(child->resolveFlexBasisPtr(), mainAxisownerSize));
+  const YGFloatOptional resolvedFlexBasis =
+      YGResolveValue(child->resolveFlexBasisPtr(), mainAxisownerSize);
   const bool isRowStyleDimDefined = YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, ownerWidth);
   const bool isColumnStyleDimDefined =
       YGNodeIsStyleDimDefined(child, YGFlexDirectionColumn, ownerHeight);
 
-  if (!YGFloatIsUndefined(resolvedFlexBasis) && !YGFloatIsUndefined(mainAxisSize)) {
-    if (YGFloatIsUndefined(child->getLayout().computedFlexBasis) ||
+  if (!resolvedFlexBasis.isUndefined() && !YGFloatIsUndefined(mainAxisSize)) {
+    if (child->getLayout().computedFlexBasis.isUndefined() ||
         (YGConfigIsExperimentalFeatureEnabled(
              child->getConfig(), YGExperimentalFeatureWebFlexBasis) &&
          child->getLayout().computedFlexBasisGeneration !=
              gCurrentGenerationCount)) {
-      child->setLayoutComputedFlexBasis(YGFloatMax(
-          resolvedFlexBasis,
-          YGNodePaddingAndBorderForAxis(child, mainAxis, ownerWidth)));
+      const YGFloatOptional& paddingAndBorder = YGFloatOptional(
+          YGNodePaddingAndBorderForAxis(child, mainAxis, ownerWidth));
+      child->setLayoutComputedFlexBasis(
+          YGFloatOptionalMax(resolvedFlexBasis, paddingAndBorder));
     }
   } else if (isMainAxisRow && isRowStyleDimDefined) {
     // The width is definite, so use that as the flex basis.
-    child->setLayoutComputedFlexBasis(YGFloatMax(
-        YGUnwrapFloatOptional(YGResolveValue(
-            child->getResolvedDimension(YGDimensionWidth), ownerWidth)),
-        YGNodePaddingAndBorderForAxis(child, YGFlexDirectionRow, ownerWidth)));
+    const YGFloatOptional& paddingAndBorder = YGFloatOptional(
+        YGNodePaddingAndBorderForAxis(child, YGFlexDirectionRow, ownerWidth));
+
+    child->setLayoutComputedFlexBasis(YGFloatOptionalMax(
+        YGResolveValue(
+            child->getResolvedDimension(YGDimensionWidth), ownerWidth),
+        paddingAndBorder));
   } else if (!isMainAxisRow && isColumnStyleDimDefined) {
     // The height is definite, so use that as the flex basis.
-    child->setLayoutComputedFlexBasis(YGFloatMax(
-        YGUnwrapFloatOptional(YGResolveValue(
-            child->getResolvedDimension(YGDimensionHeight), ownerHeight)),
-        YGNodePaddingAndBorderForAxis(
-            child, YGFlexDirectionColumn, ownerWidth)));
+    const YGFloatOptional& paddingAndBorder =
+        YGFloatOptional(YGNodePaddingAndBorderForAxis(
+            child, YGFlexDirectionColumn, ownerWidth));
+    child->setLayoutComputedFlexBasis(YGFloatOptionalMax(
+        YGResolveValue(
+            child->getResolvedDimension(YGDimensionHeight), ownerHeight),
+        paddingAndBorder));
   } else {
     // Compute the flex basis and hypothetical main size (i.e. the clamped
     // flex basis).
@@ -1361,9 +1367,9 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
                          "measure",
                          config);
 
-    child->setLayoutComputedFlexBasis(YGFloatMax(
+    child->setLayoutComputedFlexBasis(YGFloatOptional(YGFloatMax(
         child->getLayout().measuredDimensions[dim[mainAxis]],
-        YGNodePaddingAndBorderForAxis(child, mainAxis, ownerWidth)));
+        YGNodePaddingAndBorderForAxis(child, mainAxis, ownerWidth))));
   }
   child->setLayoutComputedFlexBasisGeneration(gCurrentGenerationCount);
 }
@@ -1825,7 +1831,7 @@ static void YGNodeComputeFlexBasisForChildren(
     }
     if (child == singleFlexChild) {
       child->setLayoutComputedFlexBasisGeneration(gCurrentGenerationCount);
-      child->setLayoutComputedFlexBasis(0);
+      child->setLayoutComputedFlexBasis(YGFloatOptional(0));
     } else {
       YGNodeComputeFlexBasisForChild(
           node,
@@ -1840,7 +1846,8 @@ static void YGNodeComputeFlexBasisForChildren(
           config);
     }
 
-    totalOuterFlexBasis += child->getLayout().computedFlexBasis +
+    totalOuterFlexBasis +=
+        YGUnwrapFloatOptional(child->getLayout().computedFlexBasis) +
         child->getMarginForAxis(mainAxis, availableInnerWidth);
   }
 }
@@ -1880,7 +1887,7 @@ static YGCollectFlexItemsRowValues YGCalculateCollectFlexItemsRowValues(
         YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
             child,
             mainAxis,
-            child->getLayout().computedFlexBasis,
+            YGUnwrapFloatOptional(child->getLayout().computedFlexBasis),
             mainAxisownerSize));
 
     // If this is a multi-line flow and this item pushes us over the
@@ -1906,7 +1913,8 @@ static YGCollectFlexItemsRowValues YGCalculateCollectFlexItemsRowValues(
       // Unlike the grow factor, the shrink factor is scaled relative to the
       // child dimension.
       flexAlgoRowMeasurement.totalFlexShrinkScaledFactors +=
-          -child->resolveFlexShrink() * child->getLayout().computedFlexBasis;
+          -child->resolveFlexShrink() *
+          YGUnwrapFloatOptional(child->getLayout().computedFlexBasis);
     }
 
     flexAlgoRowMeasurement.relativeChildren.push_back(child);
@@ -1956,7 +1964,8 @@ static float YGDistributeFreeSpaceSecondPass(
     childFlexBasis = YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
         currentRelativeChild,
         mainAxis,
-        currentRelativeChild->getLayout().computedFlexBasis,
+        YGUnwrapFloatOptional(
+            currentRelativeChild->getLayout().computedFlexBasis),
         mainAxisownerSize));
     float updatedMainSize = childFlexBasis;
 
@@ -2131,7 +2140,8 @@ static void YGDistributeFreeSpaceFirstPass(
     float childFlexBasis = YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
         currentRelativeChild,
         mainAxis,
-        currentRelativeChild->getLayout().computedFlexBasis,
+        YGUnwrapFloatOptional(
+            currentRelativeChild->getLayout().computedFlexBasis),
         mainAxisownerSize));
 
     if (collectedFlexItemsValues.remainingFreeSpace < 0) {
@@ -2417,7 +2427,7 @@ static void YGJustifyMainAxis(
           // YGNodeDimWithMargin.
           collectedFlexItemsValues.mainDim += betweenMainDim +
               child->getMarginForAxis(mainAxis, availableInnerWidth) +
-              childLayout.computedFlexBasis;
+              YGUnwrapFloatOptional(childLayout.computedFlexBasis);
           collectedFlexItemsValues.crossDim = availableInnerCrossDim;
         } else {
           // The main dimension is the sum of all the elements dimension plus

From f3c2ab306c360d79c8d8784cacc78b650858aaf3 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:42 -0700
Subject: [PATCH 0195/1109] Changed the type of return value of
 getLeadingPosition to YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7344367

fbshipit-source-id: 0f5a667ca357b2ce056c86763aa3e9e4c54b82f0
---
 ReactCommon/yoga/yoga/YGNode.cpp | 17 +++++++++--------
 ReactCommon/yoga/yoga/YGNode.h   |  3 ++-
 ReactCommon/yoga/yoga/Yoga.cpp   | 16 ++++++++++------
 3 files changed, 21 insertions(+), 15 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index eb840ef1dde9..3d1729cda73e 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -85,14 +85,14 @@ std::array<YGValue, 2> YGNode::getResolvedDimensions() const {
   return resolvedDimensions_;
 }
 
-float YGNode::getLeadingPosition(
-    const YGFlexDirection axis,
-    const float axisSize) const {
+YGFloatOptional YGNode::getLeadingPosition(
+    const YGFlexDirection& axis,
+    const float& axisSize) const {
   if (YGFlexDirectionIsRow(axis)) {
     const YGValue* leadingPosition =
         YGComputedEdgeValue(style_.position, YGEdgeStart, &YGValueUndefined);
     if (leadingPosition->unit != YGUnitUndefined) {
-      return YGUnwrapFloatOptional(YGResolveValue(*leadingPosition, axisSize));
+      return YGResolveValue(*leadingPosition, axisSize);
     }
   }
 
@@ -100,8 +100,8 @@ float YGNode::getLeadingPosition(
       YGComputedEdgeValue(style_.position, leading[axis], &YGValueUndefined);
 
   return leadingPosition->unit == YGUnitUndefined
-      ? 0.0f
-      : YGUnwrapFloatOptional(YGResolveValue(*leadingPosition, axisSize));
+      ? YGFloatOptional(0)
+      : YGResolveValue(*leadingPosition, axisSize);
 }
 
 float YGNode::getTrailingPosition(
@@ -343,8 +343,9 @@ void YGNode::setLayoutDimension(float dimension, int index) {
 float YGNode::relativePosition(
     const YGFlexDirection axis,
     const float axisSize) {
-  return isLeadingPositionDefined(axis) ? getLeadingPosition(axis, axisSize)
-                                        : -getTrailingPosition(axis, axisSize);
+  return isLeadingPositionDefined(axis)
+      ? YGUnwrapFloatOptional(getLeadingPosition(axis, axisSize))
+      : -getTrailingPosition(axis, axisSize);
 }
 
 void YGNode::setPosition(
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index fe24fa037f64..8fb55d6def43 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -85,7 +85,8 @@ struct YGNode {
   YGValue getResolvedDimension(int index);
 
   // Methods related to positions, margin, padding and border
-  float getLeadingPosition(const YGFlexDirection axis, const float axisSize) const;
+  YGFloatOptional getLeadingPosition(const YGFlexDirection& axis,
+      const float& axisSize) const;
   bool isLeadingPositionDefined(const YGFlexDirection axis) const;
   bool isTrailingPosDefined(const YGFlexDirection axis) const;
   float getTrailingPosition(const YGFlexDirection axis, const float axisSize) const;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 3b117243e709..fbb37ee4d546 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1408,7 +1408,8 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
       childWidth = node->getLayout().measuredDimensions[YGDimensionWidth] -
           (node->getLeadingBorder(YGFlexDirectionRow) +
            node->getTrailingBorder(YGFlexDirectionRow)) -
-          (child->getLeadingPosition(YGFlexDirectionRow, width) +
+          (YGUnwrapFloatOptional(
+               child->getLeadingPosition(YGFlexDirectionRow, width)) +
            child->getTrailingPosition(YGFlexDirectionRow, width));
       childWidth = YGNodeBoundAxis(child, YGFlexDirectionRow, childWidth, width, width);
     }
@@ -1427,7 +1428,8 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
       childHeight = node->getLayout().measuredDimensions[YGDimensionHeight] -
           (node->getLeadingBorder(YGFlexDirectionColumn) +
            node->getTrailingBorder(YGFlexDirectionColumn)) -
-          (child->getLeadingPosition(YGFlexDirectionColumn, height) +
+          (YGUnwrapFloatOptional(
+               child->getLeadingPosition(YGFlexDirectionColumn, height)) +
            child->getTrailingPosition(YGFlexDirectionColumn, height));
       childHeight = YGNodeBoundAxis(child, YGFlexDirectionColumn, childHeight, height, width);
     }
@@ -2390,7 +2392,8 @@ static void YGJustifyMainAxis(
         // defined, we override the position to whatever the user said
         // (and margin/border).
         child->setLayoutPosition(
-            child->getLeadingPosition(mainAxis, availableInnerMainDim) +
+            YGUnwrapFloatOptional(
+                child->getLeadingPosition(mainAxis, availableInnerMainDim)) +
                 node->getLeadingBorder(mainAxis) +
                 child->getLeadingMargin(mainAxis, availableInnerWidth),
             pos[mainAxis]);
@@ -2893,7 +2896,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               child->isLeadingPositionDefined(crossAxis);
           if (isChildLeadingPosDefined) {
             child->setLayoutPosition(
-                child->getLeadingPosition(crossAxis, availableInnerCrossDim) +
+                YGUnwrapFloatOptional(child->getLeadingPosition(
+                    crossAxis, availableInnerCrossDim)) +
                     node->getLeadingBorder(crossAxis) +
                     child->getLeadingMargin(crossAxis, availableInnerWidth),
                 pos[crossAxis]);
@@ -3178,8 +3182,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               case YGAlignBaseline: {
                 child->setLayoutPosition(
                     currentLead + maxAscentForCurrentLine - YGBaseline(child) +
-                        child->getLeadingPosition(
-                            YGFlexDirectionColumn, availableInnerCrossDim),
+                        YGUnwrapFloatOptional(child->getLeadingPosition(
+                            YGFlexDirectionColumn, availableInnerCrossDim)),
                     YGEdgeTop);
 
                 break;

From de70bc74d598f534fd80588aa79c7861483d72f8 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:44 -0700
Subject: [PATCH 0196/1109] Change the type of getTrailingPosition to
 YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7344710

fbshipit-source-id: eb4c422b6e0f55d90b083221aa8ff1ab797d58a8
---
 ReactCommon/yoga/yoga/YGNode.cpp | 14 +++++++-------
 ReactCommon/yoga/yoga/YGNode.h   |  4 +++-
 ReactCommon/yoga/yoga/Yoga.cpp   | 23 ++++++++++++-----------
 3 files changed, 22 insertions(+), 19 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 3d1729cda73e..68d7b10400f5 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -104,14 +104,14 @@ YGFloatOptional YGNode::getLeadingPosition(
       : YGResolveValue(*leadingPosition, axisSize);
 }
 
-float YGNode::getTrailingPosition(
-    const YGFlexDirection axis,
-    const float axisSize) const {
+YGFloatOptional YGNode::getTrailingPosition(
+    const YGFlexDirection& axis,
+    const float& axisSize) const {
   if (YGFlexDirectionIsRow(axis)) {
     const YGValue* trailingPosition =
         YGComputedEdgeValue(style_.position, YGEdgeEnd, &YGValueUndefined);
     if (trailingPosition->unit != YGUnitUndefined) {
-      return YGUnwrapFloatOptional(YGResolveValue(*trailingPosition, axisSize));
+      return YGResolveValue(*trailingPosition, axisSize);
     }
   }
 
@@ -119,8 +119,8 @@ float YGNode::getTrailingPosition(
       YGComputedEdgeValue(style_.position, trailing[axis], &YGValueUndefined);
 
   return trailingPosition->unit == YGUnitUndefined
-      ? 0.0f
-      : YGUnwrapFloatOptional(YGResolveValue(*trailingPosition, axisSize));
+      ? YGFloatOptional(0)
+      : YGResolveValue(*trailingPosition, axisSize);
 }
 
 bool YGNode::isLeadingPositionDefined(const YGFlexDirection axis) const {
@@ -345,7 +345,7 @@ float YGNode::relativePosition(
     const float axisSize) {
   return isLeadingPositionDefined(axis)
       ? YGUnwrapFloatOptional(getLeadingPosition(axis, axisSize))
-      : -getTrailingPosition(axis, axisSize);
+      : -YGUnwrapFloatOptional(getTrailingPosition(axis, axisSize));
 }
 
 void YGNode::setPosition(
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 8fb55d6def43..87637991570f 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -89,7 +89,9 @@ struct YGNode {
       const float& axisSize) const;
   bool isLeadingPositionDefined(const YGFlexDirection axis) const;
   bool isTrailingPosDefined(const YGFlexDirection axis) const;
-  float getTrailingPosition(const YGFlexDirection axis, const float axisSize) const;
+  YGFloatOptional getTrailingPosition(
+      const YGFlexDirection& axis,
+      const float& axisSize) const;
   float getLeadingMargin(const YGFlexDirection axis, const float widthSize) const;
   float getTrailingMargin(const YGFlexDirection axis, const float widthSize) const;
   float getLeadingBorder(const YGFlexDirection& flexDirection) const;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index fbb37ee4d546..2805e7f6c896 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1408,9 +1408,9 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
       childWidth = node->getLayout().measuredDimensions[YGDimensionWidth] -
           (node->getLeadingBorder(YGFlexDirectionRow) +
            node->getTrailingBorder(YGFlexDirectionRow)) -
-          (YGUnwrapFloatOptional(
-               child->getLeadingPosition(YGFlexDirectionRow, width)) +
-           child->getTrailingPosition(YGFlexDirectionRow, width));
+          YGUnwrapFloatOptional(
+                       child->getLeadingPosition(YGFlexDirectionRow, width) +
+                       child->getTrailingPosition(YGFlexDirectionRow, width));
       childWidth = YGNodeBoundAxis(child, YGFlexDirectionRow, childWidth, width, width);
     }
   }
@@ -1425,12 +1425,13 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
     // offsets if they're defined.
     if (child->isLeadingPositionDefined(YGFlexDirectionColumn) &&
         child->isTrailingPosDefined(YGFlexDirectionColumn)) {
-      childHeight = node->getLayout().measuredDimensions[YGDimensionHeight] -
+      childHeight =
+          node->getLayout().measuredDimensions[YGDimensionHeight] -
           (node->getLeadingBorder(YGFlexDirectionColumn) +
            node->getTrailingBorder(YGFlexDirectionColumn)) -
-          (YGUnwrapFloatOptional(
-               child->getLeadingPosition(YGFlexDirectionColumn, height)) +
-           child->getTrailingPosition(YGFlexDirectionColumn, height));
+          YGUnwrapFloatOptional(
+              child->getLeadingPosition(YGFlexDirectionColumn, height) +
+              child->getTrailingPosition(YGFlexDirectionColumn, height));
       childHeight = YGNodeBoundAxis(child, YGFlexDirectionColumn, childHeight, height, width);
     }
   }
@@ -1503,8 +1504,8 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
             child->getLayout().measuredDimensions[dim[mainAxis]] -
             node->getTrailingBorder(mainAxis) -
             child->getTrailingMargin(mainAxis, width) -
-            child->getTrailingPosition(
-                mainAxis, isMainAxisRow ? width : height),
+            YGUnwrapFloatOptional(child->getTrailingPosition(
+                mainAxis, isMainAxisRow ? width : height)),
         leading[mainAxis]);
   } else if (
       !child->isLeadingPositionDefined(mainAxis) &&
@@ -1530,8 +1531,8 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
             child->getLayout().measuredDimensions[dim[crossAxis]] -
             node->getTrailingBorder(crossAxis) -
             child->getTrailingMargin(crossAxis, width) -
-            child->getTrailingPosition(
-                crossAxis, isMainAxisRow ? height : width),
+            YGUnwrapFloatOptional(child->getTrailingPosition(
+                crossAxis, isMainAxisRow ? height : width)),
         leading[crossAxis]);
 
   } else if (

From f0490d121737c8acc59e2ce181cf92915621f678 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:46 -0700
Subject: [PATCH 0197/1109] Refactored relativePosition private method to
 YGFloatOptional return type

Reviewed By: emilsjolander

Differential Revision: D7344939

fbshipit-source-id: 72443d38426a211d3e84be814e6a61baf4d26703
---
 ReactCommon/yoga/yoga/YGNode.cpp | 40 +++++++++++++++++++++-----------
 ReactCommon/yoga/yoga/YGNode.h   |  8 ++++---
 2 files changed, 31 insertions(+), 17 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 68d7b10400f5..7d29caf0431c 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -123,7 +123,7 @@ YGFloatOptional YGNode::getTrailingPosition(
       : YGResolveValue(*trailingPosition, axisSize);
 }
 
-bool YGNode::isLeadingPositionDefined(const YGFlexDirection axis) const {
+bool YGNode::isLeadingPositionDefined(const YGFlexDirection& axis) const {
   return (YGFlexDirectionIsRow(axis) &&
           YGComputedEdgeValue(style_.position, YGEdgeStart, &YGValueUndefined)
                   ->unit != YGUnitUndefined) ||
@@ -131,7 +131,7 @@ bool YGNode::isLeadingPositionDefined(const YGFlexDirection axis) const {
           ->unit != YGUnitUndefined;
 }
 
-bool YGNode::isTrailingPosDefined(const YGFlexDirection axis) const {
+bool YGNode::isTrailingPosDefined(const YGFlexDirection& axis) const {
   return (YGFlexDirectionIsRow(axis) &&
           YGComputedEdgeValue(style_.position, YGEdgeEnd, &YGValueUndefined)
                   ->unit != YGUnitUndefined) ||
@@ -340,12 +340,18 @@ void YGNode::setLayoutDimension(float dimension, int index) {
 
 // If both left and right are defined, then use left. Otherwise return
 // +left or -right depending on which is defined.
-float YGNode::relativePosition(
-    const YGFlexDirection axis,
-    const float axisSize) {
-  return isLeadingPositionDefined(axis)
-      ? YGUnwrapFloatOptional(getLeadingPosition(axis, axisSize))
-      : -YGUnwrapFloatOptional(getTrailingPosition(axis, axisSize));
+YGFloatOptional YGNode::relativePosition(
+    const YGFlexDirection& axis,
+    const float& axisSize) const {
+  if (isLeadingPositionDefined(axis)) {
+    return getLeadingPosition(axis, axisSize);
+  }
+
+  YGFloatOptional trailingPosition = getTrailingPosition(axis, axisSize);
+  if (!trailingPosition.isUndefined()) {
+    trailingPosition.setValue(-1 * trailingPosition.getValue());
+  }
+  return trailingPosition;
 }
 
 void YGNode::setPosition(
@@ -362,20 +368,26 @@ void YGNode::setPosition(
   const YGFlexDirection crossAxis =
       YGFlexDirectionCross(mainAxis, directionRespectingRoot);
 
-  const float relativePositionMain = relativePosition(mainAxis, mainSize);
-  const float relativePositionCross = relativePosition(crossAxis, crossSize);
+  const YGFloatOptional relativePositionMain =
+      relativePosition(mainAxis, mainSize);
+  const YGFloatOptional relativePositionCross =
+      relativePosition(crossAxis, crossSize);
 
   setLayoutPosition(
-      getLeadingMargin(mainAxis, ownerWidth) + relativePositionMain,
+      getLeadingMargin(mainAxis, ownerWidth) +
+          YGUnwrapFloatOptional(relativePositionMain),
       leading[mainAxis]);
   setLayoutPosition(
-      getTrailingMargin(mainAxis, ownerWidth) + relativePositionMain,
+      getTrailingMargin(mainAxis, ownerWidth) +
+          YGUnwrapFloatOptional(relativePositionMain),
       trailing[mainAxis]);
   setLayoutPosition(
-      getLeadingMargin(crossAxis, ownerWidth) + relativePositionCross,
+      getLeadingMargin(crossAxis, ownerWidth) +
+          YGUnwrapFloatOptional(relativePositionCross),
       leading[crossAxis]);
   setLayoutPosition(
-      getTrailingMargin(crossAxis, ownerWidth) + relativePositionCross,
+      getTrailingMargin(crossAxis, ownerWidth) +
+          YGUnwrapFloatOptional(relativePositionCross),
       trailing[crossAxis]);
 }
 
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 87637991570f..95fac7214b30 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -30,7 +30,9 @@ struct YGNode {
   bool isDirty_;
   std::array<YGValue, 2> resolvedDimensions_;
 
-  float relativePosition(const YGFlexDirection axis, const float axisSize);
+  YGFloatOptional relativePosition(
+      const YGFlexDirection& axis,
+      const float& axisSize) const;
 
  public:
   YGNode();
@@ -87,8 +89,8 @@ struct YGNode {
   // Methods related to positions, margin, padding and border
   YGFloatOptional getLeadingPosition(const YGFlexDirection& axis,
       const float& axisSize) const;
-  bool isLeadingPositionDefined(const YGFlexDirection axis) const;
-  bool isTrailingPosDefined(const YGFlexDirection axis) const;
+  bool isLeadingPositionDefined(const YGFlexDirection& axis) const;
+  bool isTrailingPosDefined(const YGFlexDirection& axis) const;
   YGFloatOptional getTrailingPosition(
       const YGFlexDirection& axis,
       const float& axisSize) const;

From 1024e98b9533bc0094ace2e324ed36876b19de9e Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:49 -0700
Subject: [PATCH 0198/1109] Changed the return type of getLeadingMargin to
 YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7349907

fbshipit-source-id: b20894fbc33fd5b29a28f3c9174d1b5f406774ab
---
 ReactCommon/yoga/yoga/YGNode.cpp | 24 ++++++++++++------------
 ReactCommon/yoga/yoga/YGNode.h   |  4 +++-
 ReactCommon/yoga/yoga/Yoga.cpp   | 29 +++++++++++++++++++----------
 3 files changed, 34 insertions(+), 23 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 7d29caf0431c..f388f91dd4e9 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -139,18 +139,17 @@ bool YGNode::isTrailingPosDefined(const YGFlexDirection& axis) const {
           ->unit != YGUnitUndefined;
 }
 
-float YGNode::getLeadingMargin(
-    const YGFlexDirection axis,
-    const float widthSize) const {
+YGFloatOptional YGNode::getLeadingMargin(
+    const YGFlexDirection& axis,
+    const float& widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.margin[YGEdgeStart].unit != YGUnitUndefined) {
-    return YGUnwrapFloatOptional(
-        YGResolveValueMargin(style_.margin[YGEdgeStart], widthSize));
+    return YGResolveValueMargin(style_.margin[YGEdgeStart], widthSize);
   }
 
-  return YGUnwrapFloatOptional(YGResolveValueMargin(
+  return YGResolveValueMargin(
       *YGComputedEdgeValue(style_.margin, leading[axis], &YGValueZero),
-      widthSize));
+      widthSize);
 }
 
 float YGNode::getTrailingMargin(
@@ -171,7 +170,8 @@ float YGNode::getTrailingMargin(
 float YGNode::getMarginForAxis(
     const YGFlexDirection axis,
     const float widthSize) const {
-  return getLeadingMargin(axis, widthSize) + getTrailingMargin(axis, widthSize);
+  return YGUnwrapFloatOptional(getLeadingMargin(axis, widthSize)) +
+      getTrailingMargin(axis, widthSize);
 }
 
 // Setters
@@ -374,16 +374,16 @@ void YGNode::setPosition(
       relativePosition(crossAxis, crossSize);
 
   setLayoutPosition(
-      getLeadingMargin(mainAxis, ownerWidth) +
-          YGUnwrapFloatOptional(relativePositionMain),
+      YGUnwrapFloatOptional(
+          getLeadingMargin(mainAxis, ownerWidth) + relativePositionMain),
       leading[mainAxis]);
   setLayoutPosition(
       getTrailingMargin(mainAxis, ownerWidth) +
           YGUnwrapFloatOptional(relativePositionMain),
       trailing[mainAxis]);
   setLayoutPosition(
-      getLeadingMargin(crossAxis, ownerWidth) +
-          YGUnwrapFloatOptional(relativePositionCross),
+      YGUnwrapFloatOptional(
+          getLeadingMargin(crossAxis, ownerWidth) + relativePositionCross),
       leading[crossAxis]);
   setLayoutPosition(
       getTrailingMargin(crossAxis, ownerWidth) +
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 95fac7214b30..7b2275ea2274 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -94,7 +94,9 @@ struct YGNode {
   YGFloatOptional getTrailingPosition(
       const YGFlexDirection& axis,
       const float& axisSize) const;
-  float getLeadingMargin(const YGFlexDirection axis, const float widthSize) const;
+  YGFloatOptional getLeadingMargin(
+      const YGFlexDirection& axis,
+      const float& widthSize) const;
   float getTrailingMargin(const YGFlexDirection axis, const float widthSize) const;
   float getLeadingBorder(const YGFlexDirection& flexDirection) const;
   float getTrailingBorder(const YGFlexDirection& flexDirection) const;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 2805e7f6c896..1bcb4a205298 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1093,7 +1093,7 @@ static inline float YGNodeDimWithMargin(const YGNodeRef node,
                                         const YGFlexDirection axis,
                                         const float widthSize) {
   return node->getLayout().measuredDimensions[dim[axis]] +
-      node->getLeadingMargin(axis, widthSize) +
+      YGUnwrapFloatOptional(node->getLeadingMargin(axis, widthSize)) +
       node->getTrailingMargin(axis, widthSize);
 }
 
@@ -2396,7 +2396,8 @@ static void YGJustifyMainAxis(
             YGUnwrapFloatOptional(
                 child->getLeadingPosition(mainAxis, availableInnerMainDim)) +
                 node->getLeadingBorder(mainAxis) +
-                child->getLeadingMargin(mainAxis, availableInnerWidth),
+                YGUnwrapFloatOptional(
+                    child->getLeadingMargin(mainAxis, availableInnerWidth)),
             pos[mainAxis]);
       }
     } else {
@@ -2573,11 +2574,15 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       YGResolveFlexDirection(YGFlexDirectionColumn, direction);
 
   node->setLayoutMargin(
-      node->getLeadingMargin(flexRowDirection, ownerWidth), YGEdgeStart);
+      YGUnwrapFloatOptional(
+          node->getLeadingMargin(flexRowDirection, ownerWidth)),
+      YGEdgeStart);
   node->setLayoutMargin(
       node->getTrailingMargin(flexRowDirection, ownerWidth), YGEdgeEnd);
   node->setLayoutMargin(
-      node->getLeadingMargin(flexColumnDirection, ownerWidth), YGEdgeTop);
+      YGUnwrapFloatOptional(
+          node->getLeadingMargin(flexColumnDirection, ownerWidth)),
+      YGEdgeTop);
   node->setLayoutMargin(
       node->getTrailingMargin(flexColumnDirection, ownerWidth), YGEdgeBottom);
 
@@ -2900,7 +2905,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                 YGUnwrapFloatOptional(child->getLeadingPosition(
                     crossAxis, availableInnerCrossDim)) +
                     node->getLeadingBorder(crossAxis) +
-                    child->getLeadingMargin(crossAxis, availableInnerWidth),
+                    YGUnwrapFloatOptional(child->getLeadingMargin(
+                        crossAxis, availableInnerWidth)),
                 pos[crossAxis]);
           }
           // If leading position is not defined or calculations result in Nan, default to border + margin
@@ -2908,7 +2914,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               YGFloatIsUndefined(child->getLayout().position[pos[crossAxis]])) {
             child->setLayoutPosition(
                 node->getLeadingBorder(crossAxis) +
-                    child->getLeadingMargin(crossAxis, availableInnerWidth),
+                    YGUnwrapFloatOptional(child->getLeadingMargin(
+                        crossAxis, availableInnerWidth)),
                 pos[crossAxis]);
           }
         } else {
@@ -3083,8 +3090,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
           }
           if (YGNodeAlignItem(node, child) == YGAlignBaseline) {
             const float ascent = YGBaseline(child) +
-                child->getLeadingMargin(
-                    YGFlexDirectionColumn, availableInnerWidth);
+                YGUnwrapFloatOptional(child->getLeadingMargin(
+                    YGFlexDirectionColumn, availableInnerWidth));
             const float descent =
                 child->getLayout().measuredDimensions[YGDimensionHeight] +
                 child->getMarginForAxis(
@@ -3113,7 +3120,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               case YGAlignFlexStart: {
                 child->setLayoutPosition(
                     currentLead +
-                        child->getLeadingMargin(crossAxis, availableInnerWidth),
+                        YGUnwrapFloatOptional(child->getLeadingMargin(
+                            crossAxis, availableInnerWidth)),
                     pos[crossAxis]);
                 break;
               }
@@ -3138,7 +3146,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               case YGAlignStretch: {
                 child->setLayoutPosition(
                     currentLead +
-                        child->getLeadingMargin(crossAxis, availableInnerWidth),
+                        YGUnwrapFloatOptional(child->getLeadingMargin(
+                            crossAxis, availableInnerWidth)),
                     pos[crossAxis]);
 
                 // Remeasure child with the line height as it as been only measured with the

From 3a65fa56c50cec118b5bd044edd760cd81b79d72 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:51 -0700
Subject: [PATCH 0199/1109] Change the return type of getTrailingMargin to
 YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7350221

fbshipit-source-id: 61a67364c1975ec6dd1883bc2cb4968b830c73df
---
 ReactCommon/yoga/yoga/YGNode.cpp | 25 ++++++++++++-------------
 ReactCommon/yoga/yoga/YGNode.h   |  4 +++-
 ReactCommon/yoga/yoga/Yoga.cpp   | 21 +++++++++++++--------
 3 files changed, 28 insertions(+), 22 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index f388f91dd4e9..b3115c18a9df 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -152,26 +152,25 @@ YGFloatOptional YGNode::getLeadingMargin(
       widthSize);
 }
 
-float YGNode::getTrailingMargin(
-    const YGFlexDirection axis,
-    const float widthSize) const {
+YGFloatOptional YGNode::getTrailingMargin(
+    const YGFlexDirection& axis,
+    const float& widthSize) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.margin[YGEdgeEnd].unit != YGUnitUndefined) {
-    return YGUnwrapFloatOptional(
-        YGResolveValueMargin(style_.margin[YGEdgeEnd], widthSize));
+    return YGResolveValueMargin(style_.margin[YGEdgeEnd], widthSize);
   }
 
-  return YGUnwrapFloatOptional(YGResolveValueMargin(
+  return YGResolveValueMargin(
       *YGComputedEdgeValue(style_.margin, trailing[axis], &YGValueZero),
-      widthSize));
+      widthSize);
 }
 
 // TODO: Make its return type to YGFloatOptional
 float YGNode::getMarginForAxis(
     const YGFlexDirection axis,
     const float widthSize) const {
-  return YGUnwrapFloatOptional(getLeadingMargin(axis, widthSize)) +
-      getTrailingMargin(axis, widthSize);
+  return YGUnwrapFloatOptional(
+      getLeadingMargin(axis, widthSize) + getTrailingMargin(axis, widthSize));
 }
 
 // Setters
@@ -378,16 +377,16 @@ void YGNode::setPosition(
           getLeadingMargin(mainAxis, ownerWidth) + relativePositionMain),
       leading[mainAxis]);
   setLayoutPosition(
-      getTrailingMargin(mainAxis, ownerWidth) +
-          YGUnwrapFloatOptional(relativePositionMain),
+      YGUnwrapFloatOptional(
+          getTrailingMargin(mainAxis, ownerWidth) + relativePositionMain),
       trailing[mainAxis]);
   setLayoutPosition(
       YGUnwrapFloatOptional(
           getLeadingMargin(crossAxis, ownerWidth) + relativePositionCross),
       leading[crossAxis]);
   setLayoutPosition(
-      getTrailingMargin(crossAxis, ownerWidth) +
-          YGUnwrapFloatOptional(relativePositionCross),
+      YGUnwrapFloatOptional(
+          getTrailingMargin(crossAxis, ownerWidth) + relativePositionCross),
       trailing[crossAxis]);
 }
 
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 7b2275ea2274..5c628a6f5827 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -97,7 +97,9 @@ struct YGNode {
   YGFloatOptional getLeadingMargin(
       const YGFlexDirection& axis,
       const float& widthSize) const;
-  float getTrailingMargin(const YGFlexDirection axis, const float widthSize) const;
+  YGFloatOptional getTrailingMargin(
+      const YGFlexDirection& axis,
+      const float& widthSize) const;
   float getLeadingBorder(const YGFlexDirection& flexDirection) const;
   float getTrailingBorder(const YGFlexDirection& flexDirection) const;
   YGFloatOptional getLeadingPadding(
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 1bcb4a205298..efb09e4439da 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1093,8 +1093,9 @@ static inline float YGNodeDimWithMargin(const YGNodeRef node,
                                         const YGFlexDirection axis,
                                         const float widthSize) {
   return node->getLayout().measuredDimensions[dim[axis]] +
-      YGUnwrapFloatOptional(node->getLeadingMargin(axis, widthSize)) +
-      node->getTrailingMargin(axis, widthSize);
+      YGUnwrapFloatOptional(
+             node->getLeadingMargin(axis, widthSize) +
+             node->getTrailingMargin(axis, widthSize));
 }
 
 static inline bool YGNodeIsStyleDimDefined(const YGNodeRef node,
@@ -1503,7 +1504,7 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
         node->getLayout().measuredDimensions[dim[mainAxis]] -
             child->getLayout().measuredDimensions[dim[mainAxis]] -
             node->getTrailingBorder(mainAxis) -
-            child->getTrailingMargin(mainAxis, width) -
+            YGUnwrapFloatOptional(child->getTrailingMargin(mainAxis, width)) -
             YGUnwrapFloatOptional(child->getTrailingPosition(
                 mainAxis, isMainAxisRow ? width : height)),
         leading[mainAxis]);
@@ -1530,7 +1531,7 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
         node->getLayout().measuredDimensions[dim[crossAxis]] -
             child->getLayout().measuredDimensions[dim[crossAxis]] -
             node->getTrailingBorder(crossAxis) -
-            child->getTrailingMargin(crossAxis, width) -
+            YGUnwrapFloatOptional(child->getTrailingMargin(crossAxis, width)) -
             YGUnwrapFloatOptional(child->getTrailingPosition(
                 crossAxis, isMainAxisRow ? height : width)),
         leading[crossAxis]);
@@ -2578,13 +2579,17 @@ static void YGNodelayoutImpl(const YGNodeRef node,
           node->getLeadingMargin(flexRowDirection, ownerWidth)),
       YGEdgeStart);
   node->setLayoutMargin(
-      node->getTrailingMargin(flexRowDirection, ownerWidth), YGEdgeEnd);
+      YGUnwrapFloatOptional(
+          node->getTrailingMargin(flexRowDirection, ownerWidth)),
+      YGEdgeEnd);
   node->setLayoutMargin(
       YGUnwrapFloatOptional(
           node->getLeadingMargin(flexColumnDirection, ownerWidth)),
       YGEdgeTop);
   node->setLayoutMargin(
-      node->getTrailingMargin(flexColumnDirection, ownerWidth), YGEdgeBottom);
+      YGUnwrapFloatOptional(
+          node->getTrailingMargin(flexColumnDirection, ownerWidth)),
+      YGEdgeBottom);
 
   node->setLayoutBorder(node->getLeadingBorder(flexRowDirection), YGEdgeStart);
   node->setLayoutBorder(node->getTrailingBorder(flexRowDirection), YGEdgeEnd);
@@ -3128,8 +3133,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               case YGAlignFlexEnd: {
                 child->setLayoutPosition(
                     currentLead + lineHeight -
-                        child->getTrailingMargin(
-                            crossAxis, availableInnerWidth) -
+                        YGUnwrapFloatOptional(child->getTrailingMargin(
+                            crossAxis, availableInnerWidth)) -
                         child->getLayout().measuredDimensions[dim[crossAxis]],
                     pos[crossAxis]);
                 break;

From 4841aed82cdea084428754aea6d86e45d6754d4f Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 07:55:54 -0700
Subject: [PATCH 0200/1109] Change the return type of getMarginForAxis to
 YGFloatOptional

Reviewed By: emilsjolander

Differential Revision: D7350337

fbshipit-source-id: dd1ee2fcd295ccd14f7d414ab0c24090b24e91e0
---
 ReactCommon/yoga/yoga/YGNode.cpp |  10 +--
 ReactCommon/yoga/yoga/YGNode.h   |   4 +-
 ReactCommon/yoga/yoga/Yoga.cpp   | 123 +++++++++++++++++--------------
 3 files changed, 73 insertions(+), 64 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index b3115c18a9df..64a47d356a37 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -165,12 +165,10 @@ YGFloatOptional YGNode::getTrailingMargin(
       widthSize);
 }
 
-// TODO: Make its return type to YGFloatOptional
-float YGNode::getMarginForAxis(
-    const YGFlexDirection axis,
-    const float widthSize) const {
-  return YGUnwrapFloatOptional(
-      getLeadingMargin(axis, widthSize) + getTrailingMargin(axis, widthSize));
+YGFloatOptional YGNode::getMarginForAxis(
+    const YGFlexDirection& axis,
+    const float& widthSize) const {
+  return getLeadingMargin(axis, widthSize) + getTrailingMargin(axis, widthSize);
 }
 
 // Setters
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 5c628a6f5827..5f7038f44fc7 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -114,7 +114,9 @@ struct YGNode {
   YGFloatOptional getTrailingPaddingAndBorder(
       const YGFlexDirection& axis,
       const float& widthSize) const;
-  float getMarginForAxis(const YGFlexDirection axis, const float widthSize) const;
+  YGFloatOptional getMarginForAxis(
+      const YGFlexDirection& axis,
+      const float& widthSize) const;
   // Setters
 
   void setContext(void* context);
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index efb09e4439da..11c0fddd7378 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1264,10 +1264,10 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
     childWidthMeasureMode = YGMeasureModeUndefined;
     childHeightMeasureMode = YGMeasureModeUndefined;
 
-    const float marginRow =
-        child->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
-    const float marginColumn =
-        child->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
+    const float& marginRow = YGUnwrapFloatOptional(
+        child->getMarginForAxis(YGFlexDirectionRow, ownerWidth));
+    const float& marginColumn = YGUnwrapFloatOptional(
+        child->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
 
     if (isRowStyleDimDefined) {
       childWidth =
@@ -1392,9 +1392,10 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
   YGMeasureMode childWidthMeasureMode = YGMeasureModeUndefined;
   YGMeasureMode childHeightMeasureMode = YGMeasureModeUndefined;
 
-  const float marginRow = child->getMarginForAxis(YGFlexDirectionRow, width);
-  const float marginColumn =
-      child->getMarginForAxis(YGFlexDirectionColumn, width);
+  const float& marginRow =
+      YGUnwrapFloatOptional(child->getMarginForAxis(YGFlexDirectionRow, width));
+  const float& marginColumn = YGUnwrapFloatOptional(
+      child->getMarginForAxis(YGFlexDirectionColumn, width));
 
   if (YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, width)) {
     childWidth =
@@ -1481,9 +1482,11 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
                          "abs-measure",
                          config);
     childWidth = child->getLayout().measuredDimensions[YGDimensionWidth] +
-        child->getMarginForAxis(YGFlexDirectionRow, width);
+        YGUnwrapFloatOptional(
+                     child->getMarginForAxis(YGFlexDirectionRow, width));
     childHeight = child->getLayout().measuredDimensions[YGDimensionHeight] +
-        child->getMarginForAxis(YGFlexDirectionColumn, width);
+        YGUnwrapFloatOptional(
+                      child->getMarginForAxis(YGFlexDirectionColumn, width));
   }
 
   YGLayoutNodeInternal(child,
@@ -1571,10 +1574,10 @@ static void YGNodeWithMeasureFuncSetMeasuredDimensions(const YGNodeRef node,
       YGNodePaddingAndBorderForAxis(node, YGFlexDirectionRow, availableWidth);
   const float paddingAndBorderAxisColumn =
       YGNodePaddingAndBorderForAxis(node, YGFlexDirectionColumn, availableWidth);
-  const float marginAxisRow =
-      node->getMarginForAxis(YGFlexDirectionRow, availableWidth);
-  const float marginAxisColumn =
-      node->getMarginForAxis(YGFlexDirectionColumn, availableWidth);
+  const float marginAxisRow = YGUnwrapFloatOptional(
+      node->getMarginForAxis(YGFlexDirectionRow, availableWidth));
+  const float marginAxisColumn = YGUnwrapFloatOptional(
+      node->getMarginForAxis(YGFlexDirectionColumn, availableWidth));
 
   // We want to make sure we don't call measure with negative size
   const float innerWidth = YGFloatIsUndefined(availableWidth)
@@ -1648,10 +1651,10 @@ static void YGNodeEmptyContainerSetMeasuredDimensions(const YGNodeRef node,
       YGNodePaddingAndBorderForAxis(node, YGFlexDirectionRow, ownerWidth);
   const float paddingAndBorderAxisColumn =
       YGNodePaddingAndBorderForAxis(node, YGFlexDirectionColumn, ownerWidth);
-  const float marginAxisRow =
-      node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
-  const float marginAxisColumn =
-      node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
+  const float marginAxisRow = YGUnwrapFloatOptional(
+      node->getMarginForAxis(YGFlexDirectionRow, ownerWidth));
+  const float marginAxisColumn = YGUnwrapFloatOptional(
+      node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
 
   node->setLayoutMeasuredDimension(
       YGNodeBoundAxis(
@@ -1691,10 +1694,10 @@ static bool YGNodeFixedSizeSetMeasuredDimensions(const YGNodeRef node,
        heightMeasureMode == YGMeasureModeAtMost && availableHeight <= 0.0f) ||
       (widthMeasureMode == YGMeasureModeExactly &&
        heightMeasureMode == YGMeasureModeExactly)) {
-    const float marginAxisColumn =
-        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
-    const float marginAxisRow =
-        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
+    const float& marginAxisColumn = YGUnwrapFloatOptional(
+        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
+    const float& marginAxisRow = YGUnwrapFloatOptional(
+        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth));
 
     node->setLayoutMeasuredDimension(
         YGNodeBoundAxis(
@@ -1748,7 +1751,8 @@ static float YGNodeCalculateAvailableInnerDim(
   YGDimension dimension =
       YGFlexDirectionIsRow(axis) ? YGDimensionWidth : YGDimensionHeight;
 
-  const float margin = node->getMarginForAxis(direction, ownerDim);
+  const float margin =
+      YGUnwrapFloatOptional(node->getMarginForAxis(direction, ownerDim));
   const float paddingAndBorder =
       YGNodePaddingAndBorderForAxis(node, direction, ownerDim);
 
@@ -1850,9 +1854,9 @@ static void YGNodeComputeFlexBasisForChildren(
           config);
     }
 
-    totalOuterFlexBasis +=
-        YGUnwrapFloatOptional(child->getLayout().computedFlexBasis) +
-        child->getMarginForAxis(mainAxis, availableInnerWidth);
+    totalOuterFlexBasis += YGUnwrapFloatOptional(
+        child->getLayout().computedFlexBasis +
+        child->getMarginForAxis(mainAxis, availableInnerWidth));
   }
 }
 
@@ -1885,8 +1889,8 @@ static YGCollectFlexItemsRowValues YGCalculateCollectFlexItemsRowValues(
       continue;
     }
     child->setLineIndex(lineCount);
-    const float childMarginMainAxis =
-        child->getMarginForAxis(mainAxis, availableInnerWidth);
+    const float childMarginMainAxis = YGUnwrapFloatOptional(
+        child->getMarginForAxis(mainAxis, availableInnerWidth));
     const float flexBasisWithMinAndMaxConstraints =
         YGUnwrapFloatOptional(YGNodeBoundAxisWithinMinAndMax(
             child,
@@ -2020,10 +2024,10 @@ static float YGDistributeFreeSpaceSecondPass(
 
     deltaFreeSpace += updatedMainSize - childFlexBasis;
 
-    const float marginMain =
-        currentRelativeChild->getMarginForAxis(mainAxis, availableInnerWidth);
-    const float marginCross =
-        currentRelativeChild->getMarginForAxis(crossAxis, availableInnerWidth);
+    const float marginMain = YGUnwrapFloatOptional(
+        currentRelativeChild->getMarginForAxis(mainAxis, availableInnerWidth));
+    const float marginCross = YGUnwrapFloatOptional(
+        currentRelativeChild->getMarginForAxis(crossAxis, availableInnerWidth));
 
     float childCrossSize;
     float childMainSize = updatedMainSize + marginMain;
@@ -2432,7 +2436,8 @@ static void YGJustifyMainAxis(
           // they weren't computed. This means we can't call
           // YGNodeDimWithMargin.
           collectedFlexItemsValues.mainDim += betweenMainDim +
-              child->getMarginForAxis(mainAxis, availableInnerWidth) +
+              YGUnwrapFloatOptional(child->getMarginForAxis(
+                  mainAxis, availableInnerWidth)) +
               YGUnwrapFloatOptional(childLayout.computedFlexBasis);
           collectedFlexItemsValues.crossDim = availableInnerCrossDim;
         } else {
@@ -2678,10 +2683,10 @@ static void YGNodelayoutImpl(const YGNodeRef node,
   const float paddingAndBorderAxisColumn =
       isMainAxisRow ? paddingAndBorderAxisCross : paddingAndBorderAxisMain;
 
-  const float marginAxisRow =
-      node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
-  const float marginAxisColumn =
-      node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
+  const float marginAxisRow = YGUnwrapFloatOptional(
+      node->getMarginForAxis(YGFlexDirectionRow, ownerWidth));
+  const float marginAxisColumn = YGUnwrapFloatOptional(
+      node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
 
   const float minInnerWidth =
       YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionWidth], ownerWidth)) -
@@ -2945,15 +2950,16 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                   child->getLayout().measuredDimensions[dim[mainAxis]];
               float childCrossSize =
                   !child->getStyle().aspectRatio.isUndefined()
-                  ? ((child->getMarginForAxis(crossAxis, availableInnerWidth) +
+                  ? ((YGUnwrapFloatOptional(child->getMarginForAxis(
+                          crossAxis, availableInnerWidth)) +
                       (isMainAxisRow ? childMainSize /
                                child->getStyle().aspectRatio.getValue()
                                      : childMainSize *
                                child->getStyle().aspectRatio.getValue())))
                   : collectedFlexItemsValues.crossDim;
 
-              childMainSize +=
-                  child->getMarginForAxis(mainAxis, availableInnerWidth);
+              childMainSize += YGUnwrapFloatOptional(
+                  child->getMarginForAxis(mainAxis, availableInnerWidth));
 
               YGMeasureMode childMainMeasureMode = YGMeasureModeExactly;
               YGMeasureMode childCrossMeasureMode = YGMeasureModeExactly;
@@ -3091,7 +3097,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
             lineHeight = YGFloatMax(
                 lineHeight,
                 child->getLayout().measuredDimensions[dim[crossAxis]] +
-                    child->getMarginForAxis(crossAxis, availableInnerWidth));
+                    YGUnwrapFloatOptional(child->getMarginForAxis(
+                        crossAxis, availableInnerWidth)));
           }
           if (YGNodeAlignItem(node, child) == YGAlignBaseline) {
             const float ascent = YGBaseline(child) +
@@ -3099,8 +3106,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                     YGFlexDirectionColumn, availableInnerWidth));
             const float descent =
                 child->getLayout().measuredDimensions[YGDimensionHeight] +
-                child->getMarginForAxis(
-                    YGFlexDirectionColumn, availableInnerWidth) -
+                YGUnwrapFloatOptional(child->getMarginForAxis(
+                    YGFlexDirectionColumn, availableInnerWidth)) -
                 ascent;
             maxAscentForCurrentLine =
                 YGFloatMax(maxAscentForCurrentLine, ascent);
@@ -3161,14 +3168,15 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                   const float childWidth = isMainAxisRow
                       ? (child->getLayout()
                              .measuredDimensions[YGDimensionWidth] +
-                         child->getMarginForAxis(mainAxis, availableInnerWidth))
+                         YGUnwrapFloatOptional(child->getMarginForAxis(
+                             mainAxis, availableInnerWidth)))
                       : lineHeight;
 
                   const float childHeight = !isMainAxisRow
                       ? (child->getLayout()
                              .measuredDimensions[YGDimensionHeight] +
-                         child->getMarginForAxis(
-                             crossAxis, availableInnerWidth))
+                         YGUnwrapFloatOptional(child->getMarginForAxis(
+                             crossAxis, availableInnerWidth)))
                       : lineHeight;
 
                   if (!(YGFloatsEqual(
@@ -3548,10 +3556,10 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
   // expensive to measure, so it's worth avoiding redundant measurements if at
   // all possible.
   if (node->getMeasure() != nullptr) {
-    const float marginAxisRow =
-        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
-    const float marginAxisColumn =
-        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
+    const float marginAxisRow = YGUnwrapFloatOptional(
+        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth));
+    const float marginAxisColumn = YGUnwrapFloatOptional(
+        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
 
     // First, try to use the layout cache.
     if (YGNodeCanUseCachedMeasurement(widthMeasureMode,
@@ -3828,10 +3836,10 @@ void YGNodeCalculateLayout(
   float width = YGUndefined;
   YGMeasureMode widthMeasureMode = YGMeasureModeUndefined;
   if (YGNodeIsStyleDimDefined(node, YGFlexDirectionRow, ownerWidth)) {
-    width =
-        YGUnwrapFloatOptional(YGResolveValue(
-            node->getResolvedDimension(dim[YGFlexDirectionRow]), ownerWidth)) +
-        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth);
+    width = YGUnwrapFloatOptional(
+        YGResolveValue(
+            node->getResolvedDimension(dim[YGFlexDirectionRow]), ownerWidth) +
+        node->getMarginForAxis(YGFlexDirectionRow, ownerWidth));
     widthMeasureMode = YGMeasureModeExactly;
   } else if (!YGResolveValue(
                   node->getStyle().maxDimensions[YGDimensionWidth], ownerWidth)
@@ -3848,10 +3856,11 @@ void YGNodeCalculateLayout(
   float height = YGUndefined;
   YGMeasureMode heightMeasureMode = YGMeasureModeUndefined;
   if (YGNodeIsStyleDimDefined(node, YGFlexDirectionColumn, ownerHeight)) {
-    height = YGUnwrapFloatOptional(YGResolveValue(
-                 node->getResolvedDimension(dim[YGFlexDirectionColumn]),
-                 ownerHeight)) +
-        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth);
+    height = YGUnwrapFloatOptional(
+        YGResolveValue(
+            node->getResolvedDimension(dim[YGFlexDirectionColumn]),
+            ownerHeight) +
+        node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
     heightMeasureMode = YGMeasureModeExactly;
   } else if (!YGResolveValue(
                   node->getStyle().maxDimensions[YGDimensionHeight],

From c041c9fd628a9a216a52f6ffce2bf4b98a66cb29 Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 4 Apr 2018 08:17:04 -0700
Subject: [PATCH 0201/1109] clean up experimental setup and keep using
 ffast-math flag

Reviewed By: emilsjolander

Differential Revision: D7414228

fbshipit-source-id: 320e1b1953f6af867b13e617af7872eb8999160e
---
 ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java  | 4 ----
 .../src/main/java/com/facebook/yoga/YogaConstants.java        | 2 --
 ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java    | 4 ----
 3 files changed, 10 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
index ebb64aaff5a8..12aa0d8e4a27 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
@@ -16,11 +16,7 @@ public class YogaConfig {
   public static int SPACING_TYPE = 1;
 
   static {
-    if (YogaConstants.shouldUseFastMath) {
-      SoLoader.loadLibrary("yogafastmath");
-    } else {
       SoLoader.loadLibrary("yoga");
-    }
   }
 
   long mNativePointer;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConstants.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConstants.java
index f235cfdeef6a..4e081ce49a0e 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConstants.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConstants.java
@@ -18,8 +18,6 @@ public class YogaConstants {
    */
   public static final float UNDEFINED = (float) (10E20);
 
-  public static boolean shouldUseFastMath = false;
-
   public static boolean isUndefined(float value) {
     // Value of a float in the case of it being not defined is 10.1E20. Earlier it used to be NAN,
     // the benefit of which
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index 69bb3348b396..59a14d242088 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -17,11 +17,7 @@
 public class YogaNode implements Cloneable {
 
   static {
-    if (YogaConstants.shouldUseFastMath) {
-      SoLoader.loadLibrary("yogafastmath");
-    } else {
       SoLoader.loadLibrary("yoga");
-    }
   }
 
   /**

From 24f574032aae903a5bffd0033d45dc9fb5907ea0 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Lukas=20W=C3=B6hrl?= <lukas@woehrl.net>
Date: Wed, 4 Apr 2018 09:24:34 -0700
Subject: [PATCH 0202/1109] Fix compilation on MSVC by moving YGConfig to C++

Summary:
This PR fixes the compilation on MSVC. I moved the `YGConfig` creation to a C++ constructor.

Addionally it removes the "dot" notation on `YGValue`, I didn't want to change that type to a C++ constructor, because I think this will break the ABI.
Closes https://github.com/facebook/yoga/pull/746

Differential Revision: D7498141

Pulled By: emilsjolander

fbshipit-source-id: 5f5308ff838dcd803065785ddc08b2404524acb9
---
 ReactCommon/yoga/yoga/YGConfig.cpp    |  19 ++
 ReactCommon/yoga/yoga/YGConfig.h      |  23 +++
 ReactCommon/yoga/yoga/YGNode.h        |   1 +
 ReactCommon/yoga/yoga/Yoga-internal.h |  10 -
 ReactCommon/yoga/yoga/Yoga.cpp        | 281 ++++++++++++--------------
 5 files changed, 173 insertions(+), 161 deletions(-)
 create mode 100644 ReactCommon/yoga/yoga/YGConfig.cpp
 create mode 100644 ReactCommon/yoga/yoga/YGConfig.h

diff --git a/ReactCommon/yoga/yoga/YGConfig.cpp b/ReactCommon/yoga/yoga/YGConfig.cpp
new file mode 100644
index 000000000000..5cee527852fc
--- /dev/null
+++ b/ReactCommon/yoga/yoga/YGConfig.cpp
@@ -0,0 +1,19 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "YGConfig.h"
+
+const std::array<bool, YGExperimentalFeatureCount>
+    kYGDefaultExperimentalFeatures = {{false}};
+
+YGConfig::YGConfig(YGLogger logger)
+    : experimentalFeatures(kYGDefaultExperimentalFeatures),
+      useWebDefaults(false),
+      useLegacyStretchBehaviour(false),
+      shouldDiffLayoutWithoutLegacyStretchBehaviour(false),
+      pointScaleFactor(1.0f), logger(logger), cloneNodeCallback(nullptr),
+      context(nullptr) {}
diff --git a/ReactCommon/yoga/yoga/YGConfig.h b/ReactCommon/yoga/yoga/YGConfig.h
new file mode 100644
index 000000000000..0f655d1be3e6
--- /dev/null
+++ b/ReactCommon/yoga/yoga/YGConfig.h
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+#include "Yoga-internal.h"
+#include "Yoga.h"
+
+struct YGConfig {
+  std::array<bool, YGExperimentalFeatureCount> experimentalFeatures;
+  bool useWebDefaults;
+  bool useLegacyStretchBehaviour;
+  bool shouldDiffLayoutWithoutLegacyStretchBehaviour;
+  float pointScaleFactor;
+  YGLogger logger;
+  YGCloneNodeFunc cloneNodeCallback;
+  void* context;
+
+  YGConfig(YGLogger logger);
+};
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 5f7038f44fc7..96541a575eeb 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -7,6 +7,7 @@
 
 #pragma once
 #include <stdio.h>
+#include "YGConfig.h"
 #include "YGLayout.h"
 #include "YGStyle.h"
 #include "Yoga-internal.h"
diff --git a/ReactCommon/yoga/yoga/Yoga-internal.h b/ReactCommon/yoga/yoga/Yoga-internal.h
index d11f8c29d938..be1d96325b95 100644
--- a/ReactCommon/yoga/yoga/Yoga-internal.h
+++ b/ReactCommon/yoga/yoga/Yoga-internal.h
@@ -87,16 +87,6 @@ struct YGCachedMeasurement {
 // layouts should not require more than 16 entries to fit within the cache.
 #define YG_MAX_CACHED_RESULT_COUNT 16
 
-struct YGConfig {
-  bool experimentalFeatures[YGExperimentalFeatureCount + 1];
-  bool useWebDefaults;
-  bool useLegacyStretchBehaviour;
-  bool shouldDiffLayoutWithoutLegacyStretchBehaviour;
-  float pointScaleFactor;
-  YGLogger logger;
-  YGCloneNodeFunc cloneNodeCallback;
-  void* context;
-};
 
 static const float kDefaultFlexGrow = 0.0f;
 static const float kDefaultFlexShrink = 0.0f;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 11c0fddd7378..ca0b834b08fb 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -41,25 +41,7 @@ static int YGDefaultLog(const YGConfigRef config,
                         va_list args);
 #endif
 
-static YGConfig gYGConfigDefaults = {
-    .experimentalFeatures =
-        {
-            [YGExperimentalFeatureWebFlexBasis] = false,
-        },
-    .useWebDefaults = false,
-    .useLegacyStretchBehaviour = false,
-    .shouldDiffLayoutWithoutLegacyStretchBehaviour = false,
-    .pointScaleFactor = 1.0f,
-#ifdef ANDROID
-    .logger = &YGAndroidLog,
-#else
-    .logger = &YGDefaultLog,
-#endif
-    .cloneNodeCallback = nullptr,
-    .context = nullptr,
-};
-
-const YGValue YGValueZero = {.value = 0, .unit = YGUnitPoint};
+const YGValue YGValueZero = {0, YGUnitPoint};
 const YGValue YGValueUndefined = {YGUndefined, YGUnitUndefined};
 const YGValue YGValueAuto = {YGUndefined, YGUnitAuto};
 
@@ -246,8 +228,13 @@ WIN_EXPORT YGNodeRef YGNodeNewWithConfig(const YGConfigRef config) {
   return node;
 }
 
+YGConfigRef YGConfigGetDefault() {
+  static YGConfigRef defaultConfig = YGConfigNew();
+  return defaultConfig;
+}
+
 YGNodeRef YGNodeNew(void) {
-  return YGNodeNewWithConfig(&gYGConfigDefaults);
+  return YGNodeNewWithConfig(YGConfigGetDefault());
 }
 
 YGNodeRef YGNodeClone(YGNodeRef oldNode) {
@@ -363,19 +350,13 @@ int32_t YGConfigGetInstanceCount(void) {
   return gConfigInstanceCount;
 }
 
-// Export only for C#
-YGConfigRef YGConfigGetDefault() {
-  return &gYGConfigDefaults;
-}
-
 YGConfigRef YGConfigNew(void) {
-  const YGConfigRef config = (const YGConfigRef)malloc(sizeof(YGConfig));
-  YGAssert(config != nullptr, "Could not allocate memory for config");
-  if (config == nullptr) {
-    abort();
-  }
+  #ifdef ANDROID
+  const YGConfigRef config = new YGConfig(YGAndroidLog);
+  #else
+  const YGConfigRef config = new YGConfig(YGDefaultLog);
+  #endif
   gConfigInstanceCount++;
-  memcpy(config, &gYGConfigDefaults, sizeof(YGConfig));
   return config;
 }
 
@@ -590,79 +571,78 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
     }                                                                     \
   }
 
-#define YG_NODE_STYLE_PROPERTY_SETTER_UNIT_IMPL(                               \
-    type, name, paramName, instanceName)                                       \
-  void YGNodeStyleSet##name(const YGNodeRef node, const type paramName) {      \
-    YGValue value = {                                                          \
-        .value = YGFloatSanitize(paramName),                                   \
-        .unit = YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint, \
-    };                                                                         \
-    if ((node->getStyle().instanceName.value != value.value &&                 \
-         value.unit != YGUnitUndefined) ||                                     \
-        node->getStyle().instanceName.unit != value.unit) {                    \
-      YGStyle style = node->getStyle();                                        \
-      style.instanceName = value;                                              \
-      node->setStyle(style);                                                   \
-      node->markDirtyAndPropogate();                                           \
-    }                                                                          \
-  }                                                                            \
-                                                                               \
-  void YGNodeStyleSet##name##Percent(                                          \
-      const YGNodeRef node, const type paramName) {                            \
-    YGValue value = {                                                          \
-        .value = YGFloatSanitize(paramName),                                   \
-        .unit =                                                                \
-            YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPercent,   \
-    };                                                                         \
-    if ((node->getStyle().instanceName.value != value.value &&                 \
-         value.unit != YGUnitUndefined) ||                                     \
-        node->getStyle().instanceName.unit != value.unit) {                    \
-      YGStyle style = node->getStyle();                                        \
-                                                                               \
-      style.instanceName = value;                                              \
-      node->setStyle(style);                                                   \
-      node->markDirtyAndPropogate();                                           \
-    }                                                                          \
-  }
-
-#define YG_NODE_STYLE_PROPERTY_SETTER_UNIT_AUTO_IMPL(                          \
-    type, name, paramName, instanceName)                                       \
-  void YGNodeStyleSet##name(const YGNodeRef node, const type paramName) {      \
-    YGValue value = {                                                          \
-        .value = YGFloatSanitize(paramName),                                   \
-        .unit = YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint, \
-    };                                                                         \
-    if ((node->getStyle().instanceName.value != value.value &&                 \
-         value.unit != YGUnitUndefined) ||                                     \
-        node->getStyle().instanceName.unit != value.unit) {                    \
-      YGStyle style = node->getStyle();                                        \
-      style.instanceName = value;                                              \
-      node->setStyle(style);                                                   \
-      node->markDirtyAndPropogate();                                           \
-    }                                                                          \
-  }                                                                            \
-                                                                               \
-  void YGNodeStyleSet##name##Percent(                                          \
-      const YGNodeRef node, const type paramName) {                            \
-    if (node->getStyle().instanceName.value != YGFloatSanitize(paramName) ||   \
-        node->getStyle().instanceName.unit != YGUnitPercent) {                 \
-      YGStyle style = node->getStyle();                                        \
-      style.instanceName.value = YGFloatSanitize(paramName);                   \
-      style.instanceName.unit =                                                \
-          YGFloatIsUndefined(paramName) ? YGUnitAuto : YGUnitPercent;          \
-      node->setStyle(style);                                                   \
-      node->markDirtyAndPropogate();                                           \
-    }                                                                          \
-  }                                                                            \
-                                                                               \
-  void YGNodeStyleSet##name##Auto(const YGNodeRef node) {                      \
-    if (node->getStyle().instanceName.unit != YGUnitAuto) {                    \
-      YGStyle style = node->getStyle();                                        \
-      style.instanceName.value = 0;                                            \
-      style.instanceName.unit = YGUnitAuto;                                    \
-      node->setStyle(style);                                                   \
-      node->markDirtyAndPropogate();                                           \
-    }                                                                          \
+#define YG_NODE_STYLE_PROPERTY_SETTER_UNIT_IMPL(                          \
+    type, name, paramName, instanceName)                                  \
+  void YGNodeStyleSet##name(const YGNodeRef node, const type paramName) { \
+    YGValue value = {                                                     \
+        YGFloatSanitize(paramName),                                       \
+        YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint,    \
+    };                                                                    \
+    if ((node->getStyle().instanceName.value != value.value &&            \
+         value.unit != YGUnitUndefined) ||                                \
+        node->getStyle().instanceName.unit != value.unit) {               \
+      YGStyle style = node->getStyle();                                   \
+      style.instanceName = value;                                         \
+      node->setStyle(style);                                              \
+      node->markDirtyAndPropogate();                                      \
+    }                                                                     \
+  }                                                                       \
+                                                                          \
+  void YGNodeStyleSet##name##Percent(                                     \
+      const YGNodeRef node, const type paramName) {                       \
+    YGValue value = {                                                     \
+        YGFloatSanitize(paramName),                                       \
+        YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPercent,  \
+    };                                                                    \
+    if ((node->getStyle().instanceName.value != value.value &&            \
+         value.unit != YGUnitUndefined) ||                                \
+        node->getStyle().instanceName.unit != value.unit) {               \
+      YGStyle style = node->getStyle();                                   \
+                                                                          \
+      style.instanceName = value;                                         \
+      node->setStyle(style);                                              \
+      node->markDirtyAndPropogate();                                      \
+    }                                                                     \
+  }
+
+#define YG_NODE_STYLE_PROPERTY_SETTER_UNIT_AUTO_IMPL(                        \
+    type, name, paramName, instanceName)                                     \
+  void YGNodeStyleSet##name(const YGNodeRef node, const type paramName) {    \
+    YGValue value = {                                                        \
+        YGFloatSanitize(paramName),                                          \
+        YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint,       \
+    };                                                                       \
+    if ((node->getStyle().instanceName.value != value.value &&               \
+         value.unit != YGUnitUndefined) ||                                   \
+        node->getStyle().instanceName.unit != value.unit) {                  \
+      YGStyle style = node->getStyle();                                      \
+      style.instanceName = value;                                            \
+      node->setStyle(style);                                                 \
+      node->markDirtyAndPropogate();                                         \
+    }                                                                        \
+  }                                                                          \
+                                                                             \
+  void YGNodeStyleSet##name##Percent(                                        \
+      const YGNodeRef node, const type paramName) {                          \
+    if (node->getStyle().instanceName.value != YGFloatSanitize(paramName) || \
+        node->getStyle().instanceName.unit != YGUnitPercent) {               \
+      YGStyle style = node->getStyle();                                      \
+      style.instanceName.value = YGFloatSanitize(paramName);                 \
+      style.instanceName.unit =                                              \
+          YGFloatIsUndefined(paramName) ? YGUnitAuto : YGUnitPercent;        \
+      node->setStyle(style);                                                 \
+      node->markDirtyAndPropogate();                                         \
+    }                                                                        \
+  }                                                                          \
+                                                                             \
+  void YGNodeStyleSet##name##Auto(const YGNodeRef node) {                    \
+    if (node->getStyle().instanceName.unit != YGUnitAuto) {                  \
+      YGStyle style = node->getStyle();                                      \
+      style.instanceName.value = 0;                                          \
+      style.instanceName.unit = YGUnitAuto;                                  \
+      node->setStyle(style);                                                 \
+      node->markDirtyAndPropogate();                                         \
+    }                                                                        \
   }
 
 #define YG_NODE_STYLE_PROPERTY_IMPL(type, name, paramName, instanceName)  \
@@ -708,48 +688,47 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
     }                                                                        \
   }
 
-#define YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(                                 \
-    type, name, paramName, instanceName)                                       \
-  void YGNodeStyleSet##name(                                                   \
-      const YGNodeRef node, const YGEdge edge, const float paramName) {        \
-    YGValue value = {                                                          \
-        .value = YGFloatSanitize(paramName),                                   \
-        .unit = YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint, \
-    };                                                                         \
-    if ((node->getStyle().instanceName[edge].value != value.value &&           \
-         value.unit != YGUnitUndefined) ||                                     \
-        node->getStyle().instanceName[edge].unit != value.unit) {              \
-      YGStyle style = node->getStyle();                                        \
-      style.instanceName[edge] = value;                                        \
-      node->setStyle(style);                                                   \
-      node->markDirtyAndPropogate();                                           \
-    }                                                                          \
-  }                                                                            \
-                                                                               \
-  void YGNodeStyleSet##name##Percent(                                          \
-      const YGNodeRef node, const YGEdge edge, const float paramName) {        \
-    YGValue value = {                                                          \
-        .value = YGFloatSanitize(paramName),                                   \
-        .unit =                                                                \
-            YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPercent,   \
-    };                                                                         \
-    if ((node->getStyle().instanceName[edge].value != value.value &&           \
-         value.unit != YGUnitUndefined) ||                                     \
-        node->getStyle().instanceName[edge].unit != value.unit) {              \
-      YGStyle style = node->getStyle();                                        \
-      style.instanceName[edge] = value;                                        \
-      node->setStyle(style);                                                   \
-      node->markDirtyAndPropogate();                                           \
-    }                                                                          \
-  }                                                                            \
-                                                                               \
-  WIN_STRUCT(type)                                                             \
-  YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge) {              \
-    YGValue value = node->getStyle().instanceName[edge];                       \
-    if (value.unit == YGUnitUndefined || value.unit == YGUnitAuto) {           \
-      value.value = YGUndefined;                                               \
-    }                                                                          \
-    return WIN_STRUCT_REF(value);                                              \
+#define YG_NODE_STYLE_EDGE_PROPERTY_UNIT_IMPL(                           \
+    type, name, paramName, instanceName)                                 \
+  void YGNodeStyleSet##name(                                             \
+      const YGNodeRef node, const YGEdge edge, const float paramName) {  \
+    YGValue value = {                                                    \
+        YGFloatSanitize(paramName),                                      \
+        YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPoint,   \
+    };                                                                   \
+    if ((node->getStyle().instanceName[edge].value != value.value &&     \
+         value.unit != YGUnitUndefined) ||                               \
+        node->getStyle().instanceName[edge].unit != value.unit) {        \
+      YGStyle style = node->getStyle();                                  \
+      style.instanceName[edge] = value;                                  \
+      node->setStyle(style);                                             \
+      node->markDirtyAndPropogate();                                     \
+    }                                                                    \
+  }                                                                      \
+                                                                         \
+  void YGNodeStyleSet##name##Percent(                                    \
+      const YGNodeRef node, const YGEdge edge, const float paramName) {  \
+    YGValue value = {                                                    \
+        YGFloatSanitize(paramName),                                      \
+        YGFloatIsUndefined(paramName) ? YGUnitUndefined : YGUnitPercent, \
+    };                                                                   \
+    if ((node->getStyle().instanceName[edge].value != value.value &&     \
+         value.unit != YGUnitUndefined) ||                               \
+        node->getStyle().instanceName[edge].unit != value.unit) {        \
+      YGStyle style = node->getStyle();                                  \
+      style.instanceName[edge] = value;                                  \
+      node->setStyle(style);                                             \
+      node->markDirtyAndPropogate();                                     \
+    }                                                                    \
+  }                                                                      \
+                                                                         \
+  WIN_STRUCT(type)                                                       \
+  YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge) {        \
+    YGValue value = node->getStyle().instanceName[edge];                 \
+    if (value.unit == YGUnitUndefined || value.unit == YGUnitAuto) {     \
+      value.value = YGUndefined;                                         \
+    }                                                                    \
+    return WIN_STRUCT_REF(value);                                        \
   }
 
 #define YG_NODE_LAYOUT_PROPERTY_IMPL(type, name, instanceName) \
@@ -858,8 +837,8 @@ YGValue YGNodeStyleGetFlexBasis(const YGNodeRef node) {
 
 void YGNodeStyleSetFlexBasis(const YGNodeRef node, const float flexBasis) {
   YGValue value = {
-      .value = YGFloatSanitize(flexBasis),
-      .unit = YGFloatIsUndefined(flexBasis) ? YGUnitUndefined : YGUnitPoint,
+      YGFloatSanitize(flexBasis),
+      YGFloatIsUndefined(flexBasis) ? YGUnitUndefined : YGUnitPoint,
   };
   if ((node->getStyle().flexBasis.value != value.value &&
        value.unit != YGUnitUndefined) ||
@@ -906,8 +885,8 @@ void YGNodeStyleSetBorder(
     const YGEdge edge,
     const float border) {
   YGValue value = {
-      .value = YGFloatSanitize(border),
-      .unit = YGFloatIsUndefined(border) ? YGUnitUndefined : YGUnitPoint,
+      YGFloatSanitize(border),
+      YGFloatIsUndefined(border) ? YGUnitUndefined : YGUnitPoint,
   };
   if ((node->getStyle().border[edge].value != value.value &&
        value.unit != YGUnitUndefined) ||
@@ -3977,7 +3956,7 @@ static void YGVLog(const YGConfigRef config,
                    YGLogLevel level,
                    const char *format,
                    va_list args) {
-  const YGConfigRef logConfig = config != nullptr ? config : &gYGConfigDefaults;
+  const YGConfigRef logConfig = config != nullptr ? config : YGConfigGetDefault();
   logConfig->logger(logConfig, node, level, format, args);
 
   if (level == YGLogLevelFatal) {

From 3cd2b4342653d0cc6edfc9e7d436d73bfb4f139f Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 4 Apr 2018 10:30:16 -0700
Subject: [PATCH 0203/1109] [yoga re-add assertion to check for owner reference
 before adding child.

Reviewed By: emilsjolander

Differential Revision: D7495417

fbshipit-source-id: b81174aeea3f2796d76ccdae4a8eddd0beace0aa
---
 ReactCommon/yoga/yoga/Yoga.cpp | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index ca0b834b08fb..a927ef556c47 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -370,6 +370,11 @@ void YGConfigCopy(const YGConfigRef dest, const YGConfigRef src) {
 }
 
 void YGNodeInsertChild(const YGNodeRef node, const YGNodeRef child, const uint32_t index) {
+  YGAssertWithNode(
+      node,
+      child->getOwner() == nullptr,
+      "Child already has a owner, it must be removed first.");
+
   YGAssertWithNode(
       node,
       node->getMeasure() == nullptr,

From 0b4f33c2d006190a2443a58d583f294a4183587e Mon Sep 17 00:00:00 2001
From: Dominik Wienand <dominikw@fb.com>
Date: Wed, 4 Apr 2018 12:02:55 -0700
Subject: [PATCH 0204/1109] Use .includes instead of .startsWith for checking
 ignored YellowBox warnings

Summary:
Some warnings don't have a good prefix that can be targeted using .startsWith, e.g. "Module $modulename requires main queue setup". It would be helpful to be able to select this warning using the much more specific middle part of the string ("requires main queue setup since it overrides `constantsToExport`) so I want to change this check from startsWith to includes to enable that.

Changing from .startsWith -> .includes should be completely backward compatible.

Reviewed By: TheSavior

Differential Revision: D7445309

fbshipit-source-id: 2c91dbe5ee3c3aa74be1bca091b20d294e64e853
---
 Libraries/ReactNative/YellowBox.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/ReactNative/YellowBox.js b/Libraries/ReactNative/YellowBox.js
index 26749987affb..8c3eb1f2cb71 100644
--- a/Libraries/ReactNative/YellowBox.js
+++ b/Libraries/ReactNative/YellowBox.js
@@ -172,7 +172,7 @@ function ensureSymbolicatedWarning(warning: string): void {
 
 function isWarningIgnored(warning: string): boolean {
   const isIgnored = IGNORED_WARNINGS.some((ignoredWarning: string) =>
-    warning.startsWith(ignoredWarning),
+    warning.includes(ignoredWarning),
   );
 
   if (isIgnored) {

From c787e0e25216d04a76ce2e3c0c88218ab9db3545 Mon Sep 17 00:00:00 2001
From: Gustav Ahlberg <gustav.ahlberg@gmail.com>
Date: Wed, 4 Apr 2018 13:20:35 -0700
Subject: [PATCH 0205/1109] exclude React/Fabric/ from core

Summary:
Thank you for sending the PR! We appreciate you spending the time to work on these changes.
Help us understand your motivation by explaining why you decided to make this change.

<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

React native does not build on iOS when using Podspec environment. I tried the solution proposed in https://github.com/facebook/react-native/issues/18683 and got it to build.

Fixes https://github.com/facebook/react-native/issues/18683

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[IOS] [BUGFIX] [React.podspec] - Exclude `React/Fabric/*` from Core subspec
<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18688

Differential Revision: D7505267

Pulled By: hramos

fbshipit-source-id: 8e7138ee966d08209a74193e418feaecceefb86a
---
 React.podspec | 1 +
 1 file changed, 1 insertion(+)

diff --git a/React.podspec b/React.podspec
index 9d222499f384..a9a4de5a523e 100644
--- a/React.podspec
+++ b/React.podspec
@@ -51,6 +51,7 @@ Pod::Spec.new do |s|
                               "React/Inspector/*",
                               "ReactCommon/yoga/*",
                               "React/Cxx*/*",
+                              "React/Fabric/*",
     ss.ios.exclude_files    = "React/**/RCTTV*.*"
     ss.tvos.exclude_files   = "React/Modules/RCTClipboard*",
                               "React/Views/RCTDatePicker*",

From e574b85db6cdd73457c10d21f9be68f8fa44927d Mon Sep 17 00:00:00 2001
From: Brian Vaughn <bvaughn@fb.com>
Date: Wed, 4 Apr 2018 15:11:21 -0700
Subject: [PATCH 0206/1109] React sync for revisions 9d484ed...1c2876d

Reviewed By: gaearon

Differential Revision: D7500761

fbshipit-source-id: 8dc1cda879942fc4990b23144a616039fdbe6dc0
---
 Libraries/Renderer/REVISION                   |    2 +-
 Libraries/Renderer/ReactFabric-dev.js         | 1186 ++++++++++++-----
 Libraries/Renderer/ReactFabric-prod.js        |  313 +++--
 Libraries/Renderer/ReactNativeRenderer-dev.js | 1185 +++++++++++-----
 .../Renderer/ReactNativeRenderer-prod.js      |  369 +++--
 Libraries/Renderer/shims/ReactFabric.js       |    1 -
 Libraries/Renderer/shims/ReactTypes.js        |    4 +-
 package.json                                  |    6 +-
 8 files changed, 2091 insertions(+), 975 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index 7e989de97203..fc81a7c7f28c 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-9d484edc4b64160cb335a23a2cb21667fb2cdf4c
\ No newline at end of file
+1c2876d5b558b8591feb335d8d7204bc46f7da8a
\ No newline at end of file
diff --git a/Libraries/Renderer/ReactFabric-dev.js b/Libraries/Renderer/ReactFabric-dev.js
index 22c77f2e072d..0b7a78516c11 100644
--- a/Libraries/Renderer/ReactFabric-dev.js
+++ b/Libraries/Renderer/ReactFabric-dev.js
@@ -509,11 +509,13 @@ var injection$1 = {
     getNodeFromInstance = Injected.getNodeFromInstance;
 
     {
-      warning(
-        getNodeFromInstance && getInstanceFromNode,
-        "EventPluginUtils.injection.injectComponentTree(...): Injected " +
-          "module is missing getNodeFromInstance or getInstanceFromNode."
-      );
+      !(getNodeFromInstance && getInstanceFromNode)
+        ? warning(
+            false,
+            "EventPluginUtils.injection.injectComponentTree(...): Injected " +
+              "module is missing getNodeFromInstance or getInstanceFromNode."
+          )
+        : void 0;
     }
   }
 };
@@ -549,10 +551,9 @@ var validateEventDispatches = void 0;
       ? dispatchInstances.length
       : dispatchInstances ? 1 : 0;
 
-    warning(
-      instancesIsArr === listenersIsArr && instancesLen === listenersLen,
-      "EventPluginUtils: Invalid `event`."
-    );
+    !(instancesIsArr === listenersIsArr && instancesLen === listenersLen)
+      ? warning(false, "EventPluginUtils: Invalid `event`.")
+      : void 0;
   };
 }
 
@@ -939,7 +940,7 @@ function listenerAtPhase(inst, event, propagationPhase) {
  */
 function accumulateDirectionalDispatches(inst, phase, event) {
   {
-    warning(inst, "Dispatching inst must not be null");
+    !inst ? warning(false, "Dispatching inst must not be null") : void 0;
   }
   var listener = listenerAtPhase(inst, event, phase);
   if (listener) {
@@ -1258,13 +1259,15 @@ SyntheticEvent.extend = function(Interface) {
               !target.constructor.Interface.hasOwnProperty(prop) &&
               shouldBeReleasedProperties.indexOf(prop) === -1
             ) {
-              warning(
-                didWarnForAddedNewProperty || target.isPersistent(),
-                "This synthetic event is reused for performance reasons. If you're " +
-                  "seeing this, you're adding a new property in the synthetic event object. " +
-                  "The property is never released. See " +
-                  "https://fb.me/react-event-pooling for more information."
-              );
+              !(didWarnForAddedNewProperty || target.isPersistent())
+                ? warning(
+                    false,
+                    "This synthetic event is reused for performance reasons. If you're " +
+                      "seeing this, you're adding a new property in the synthetic event object. " +
+                      "The property is never released. See " +
+                      "https://fb.me/react-event-pooling for more information."
+                  )
+                : void 0;
               didWarnForAddedNewProperty = true;
             }
             target[prop] = value;
@@ -1311,16 +1314,18 @@ function getPooledWarningPropertyDefinition(propName, getVal) {
 
   function warn(action, result) {
     var warningCondition = false;
-    warning(
-      warningCondition,
-      "This synthetic event is reused for performance reasons. If you're seeing this, " +
-        "you're %s `%s` on a released/nullified synthetic event. %s. " +
-        "If you must keep the original synthetic event around, use event.persist(). " +
-        "See https://fb.me/react-event-pooling for more information.",
-      action,
-      propName,
-      result
-    );
+    !warningCondition
+      ? warning(
+          false,
+          "This synthetic event is reused for performance reasons. If you're seeing this, " +
+            "you're %s `%s` on a released/nullified synthetic event. %s. " +
+            "If you must keep the original synthetic event around, use event.persist(). " +
+            "See https://fb.me/react-event-pooling for more information.",
+          action,
+          propName,
+          result
+        )
+      : void 0;
   }
 }
 
@@ -1438,13 +1443,15 @@ function getTouchIdentifier(_ref) {
 
   invariant(identifier != null, "Touch object is missing identifier.");
   {
-    warning(
-      identifier <= MAX_TOUCH_BANK,
-      "Touch identifier %s is greater than maximum supported %s which causes " +
-        "performance issues backfilling array locations for all of the indices.",
-      identifier,
-      MAX_TOUCH_BANK
-    );
+    !(identifier <= MAX_TOUCH_BANK)
+      ? warning(
+          false,
+          "Touch identifier %s is greater than maximum supported %s which causes " +
+            "performance issues backfilling array locations for all of the indices.",
+          identifier,
+          MAX_TOUCH_BANK
+        )
+      : void 0;
   }
   return identifier;
 }
@@ -1543,10 +1550,9 @@ var ResponderTouchHistoryStore = {
         }
         {
           var activeRecord = touchBank[touchHistory.indexOfSingleActiveTouch];
-          warning(
-            activeRecord != null && activeRecord.touchActive,
-            "Cannot find single active touch."
-          );
+          !(activeRecord != null && activeRecord.touchActive)
+            ? warning(false, "Cannot find single active touch.")
+            : void 0;
         }
       }
     }
@@ -2641,7 +2647,7 @@ var TouchHistoryMath = {
 
 // TODO: this is special because it gets imported during build.
 
-var ReactVersion = "16.3.0-alpha.2";
+var ReactVersion = "16.3.1";
 
 function _classCallCheck(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
@@ -3311,15 +3317,17 @@ function findNodeHandle(componentOrHandle) {
   {
     var owner = ReactCurrentOwner.current;
     if (owner !== null && owner.stateNode !== null) {
-      warning(
-        owner.stateNode._warnedAboutRefsInRender,
-        "%s is accessing findNodeHandle inside its render(). " +
-          "render() should be a pure function of props and state. It should " +
-          "never access something that requires stale data from the previous " +
-          "render, such as refs. Move this logic to componentDidMount and " +
-          "componentDidUpdate instead.",
-        getComponentName(owner) || "A component"
-      );
+      !owner.stateNode._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing findNodeHandle inside its render(). " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(owner) || "A component"
+          )
+        : void 0;
 
       owner.stateNode._warnedAboutRefsInRender = true;
     }
@@ -3777,7 +3785,8 @@ var frameDeadline = 0;
 var frameDeadlineObject = {
   timeRemaining: function() {
     return frameDeadline - now();
-  }
+  },
+  didTimeout: false
 };
 
 function setTimeoutCallback() {
@@ -3865,9 +3874,10 @@ var Callback = /*              */ 32;
 var DidCapture = /*            */ 64;
 var Ref = /*                   */ 128;
 var ErrLog = /*                */ 256;
+var Snapshot = /*              */ 2048;
 
 // Union of all host effects
-var HostEffectMask = /*        */ 511;
+var HostEffectMask = /*        */ 2559;
 
 var Incomplete = /*            */ 512;
 var ShouldCapture = /*         */ 1024;
@@ -3915,15 +3925,17 @@ function isMounted(component) {
     if (owner !== null && owner.tag === ClassComponent) {
       var ownerFiber = owner;
       var instance = ownerFiber.stateNode;
-      warning(
-        instance._warnedAboutRefsInRender,
-        "%s is accessing isMounted inside its render() function. " +
-          "render() should be a pure function of props and state. It should " +
-          "never access something that requires stale data from the previous " +
-          "render, such as refs. Move this logic to componentDidMount and " +
-          "componentDidUpdate instead.",
-        getComponentName(ownerFiber) || "A component"
-      );
+      !instance._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing isMounted inside its render() function. " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(ownerFiber) || "A component"
+          )
+        : void 0;
       instance._warnedAboutRefsInRender = true;
     }
   }
@@ -4476,6 +4488,47 @@ function createFiberFromPortal(portal, mode, expirationTime) {
   return fiber;
 }
 
+// Used for stashing WIP properties to replay failed work in DEV.
+function assignFiberPropertiesInDEV(target, source) {
+  if (target === null) {
+    // This Fiber's initial properties will always be overwritten.
+    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
+    target = createFiber(IndeterminateComponent, null, null, NoContext);
+  }
+
+  // This is intentionally written as a list of all properties.
+  // We tried to use Object.assign() instead but this is called in
+  // the hottest path, and Object.assign() was too slow:
+  // https://github.com/facebook/react/issues/12502
+  // This code is DEV-only so size is not a concern.
+
+  target.tag = source.tag;
+  target.key = source.key;
+  target.type = source.type;
+  target.stateNode = source.stateNode;
+  target["return"] = source["return"];
+  target.child = source.child;
+  target.sibling = source.sibling;
+  target.index = source.index;
+  target.ref = source.ref;
+  target.pendingProps = source.pendingProps;
+  target.memoizedProps = source.memoizedProps;
+  target.updateQueue = source.updateQueue;
+  target.memoizedState = source.memoizedState;
+  target.mode = source.mode;
+  target.effectTag = source.effectTag;
+  target.nextEffect = source.nextEffect;
+  target.firstEffect = source.firstEffect;
+  target.lastEffect = source.lastEffect;
+  target.expirationTime = source.expirationTime;
+  target.alternate = source.alternate;
+  target._debugID = source._debugID;
+  target._debugSource = source._debugSource;
+  target._debugOwner = source._debugOwner;
+  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
+  return target;
+}
+
 // TODO: This should be lifted into the renderer.
 
 function createFiberRoot(containerInfo, isAsync, hydrate) {
@@ -4881,7 +4934,10 @@ var ReactStrictModeWarnings = {
     ) {
       pendingComponentWillReceivePropsWarnings.push(fiber);
     }
-    if (typeof instance.componentWillUpdate === "function") {
+    if (
+      typeof instance.componentWillUpdate === "function" &&
+      instance.componentWillUpdate.__suppressDeprecationWarning !== true
+    ) {
       pendingComponentWillUpdateWarnings.push(fiber);
     }
   };
@@ -4954,7 +5010,6 @@ var ReactStrictModeWarnings = {
 
 var debugRenderPhaseSideEffects = false;
 var debugRenderPhaseSideEffectsForStrictMode = false;
-
 var enableUserTimingAPI = true;
 var enableGetDerivedStateFromCatch = false;
 var warnAboutDeprecatedLifecycles = false;
@@ -5223,13 +5278,15 @@ function startRequestCallbackTimer() {
   }
 }
 
-function stopRequestCallbackTimer(didExpire) {
+function stopRequestCallbackTimer(didExpire, expirationTime) {
   if (enableUserTimingAPI) {
     if (supportsUserTiming) {
       isWaitingForCallback = false;
       var warning$$1 = didExpire ? "React was blocked by main thread" : null;
       endMark(
-        "(Waiting for async callback...)",
+        "(Waiting for async callback... will force flush in " +
+          expirationTime +
+          " ms)",
         "(Waiting for async callback...)",
         warning$$1
       );
@@ -5339,7 +5396,7 @@ function startWorkLoopTimer(nextUnitOfWork) {
   }
 }
 
-function stopWorkLoopTimer(interruptedBy) {
+function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
   if (enableUserTimingAPI) {
     if (!supportsUserTiming) {
       return;
@@ -5357,13 +5414,12 @@ function stopWorkLoopTimer(interruptedBy) {
       warning$$1 = "There were cascading updates";
     }
     commitCountInCurrentWorkLoop = 0;
+    var label = didCompleteRoot
+      ? "(React Tree Reconciliation: Completed Root)"
+      : "(React Tree Reconciliation: Yielded)";
     // Pause any measurements until the next loop.
     pauseTimers();
-    endMark(
-      "(React Tree Reconciliation)",
-      "(React Tree Reconciliation)",
-      warning$$1
-    );
+    endMark(label, "(React Tree Reconciliation)", warning$$1);
   }
 }
 
@@ -5400,6 +5456,31 @@ function stopCommitTimer() {
   }
 }
 
+function startCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Snapshot Effects)");
+  }
+}
+
+function stopCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Snapshot Effects: " + count + " Total)",
+      "(Committing Snapshot Effects)",
+      null
+    );
+  }
+}
+
 function startCommitHostEffectsTimer() {
   if (enableUserTimingAPI) {
     if (!supportsUserTiming) {
@@ -5784,23 +5865,26 @@ var isArray = Array.isArray;
 var didWarnAboutStateAssignmentForComponent = void 0;
 var didWarnAboutUndefinedDerivedState = void 0;
 var didWarnAboutUninitializedState = void 0;
-var didWarnAboutWillReceivePropsAndDerivedState = void 0;
+var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
+var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
 var warnOnInvalidCallback = void 0;
 
 {
-  didWarnAboutStateAssignmentForComponent = {};
-  didWarnAboutUndefinedDerivedState = {};
-  didWarnAboutUninitializedState = {};
-  didWarnAboutWillReceivePropsAndDerivedState = {};
+  didWarnAboutStateAssignmentForComponent = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
+  didWarnAboutUninitializedState = new Set();
+  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
+  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
 
-  var didWarnOnInvalidCallback = {};
+  var didWarnOnInvalidCallback = new Set();
 
   warnOnInvalidCallback = function(callback, callerName) {
     if (callback === null || typeof callback === "function") {
       return;
     }
     var key = callerName + "_" + callback;
-    if (!didWarnOnInvalidCallback[key]) {
+    if (!didWarnOnInvalidCallback.has(key)) {
+      didWarnOnInvalidCallback.add(key);
       warning(
         false,
         "%s(...): Expected the last optional `callback` argument to be a " +
@@ -5808,7 +5892,6 @@ var warnOnInvalidCallback = void 0;
         callerName,
         callback
       );
-      didWarnOnInvalidCallback[key] = true;
     }
   };
 
@@ -5951,12 +6034,14 @@ var ReactFiberClassComponent = function(
       stopPhaseTimer();
 
       {
-        warning(
-          shouldUpdate !== undefined,
-          "%s.shouldComponentUpdate(): Returned undefined instead of a " +
-            "boolean value. Make sure to return true or false.",
-          getComponentName(workInProgress) || "Unknown"
-        );
+        !(shouldUpdate !== undefined)
+          ? warning(
+              false,
+              "%s.shouldComponentUpdate(): Returned undefined instead of a " +
+                "boolean value. Make sure to return true or false.",
+              getComponentName(workInProgress) || "Component"
+            )
+          : void 0;
       }
 
       return shouldUpdate;
@@ -5975,7 +6060,7 @@ var ReactFiberClassComponent = function(
     var instance = workInProgress.stateNode;
     var type = workInProgress.type;
     {
-      var name = getComponentName(workInProgress);
+      var name = getComponentName(workInProgress) || "Component";
       var renderPresent = instance.render;
 
       if (!renderPresent) {
@@ -6000,47 +6085,57 @@ var ReactFiberClassComponent = function(
         !instance.getInitialState ||
         instance.getInitialState.isReactClassApproved ||
         instance.state;
-      warning(
-        noGetInitialStateOnES6,
-        "getInitialState was defined on %s, a plain JavaScript class. " +
-          "This is only supported for classes created using React.createClass. " +
-          "Did you mean to define a state property instead?",
-        name
-      );
+      !noGetInitialStateOnES6
+        ? warning(
+            false,
+            "getInitialState was defined on %s, a plain JavaScript class. " +
+              "This is only supported for classes created using React.createClass. " +
+              "Did you mean to define a state property instead?",
+            name
+          )
+        : void 0;
       var noGetDefaultPropsOnES6 =
         !instance.getDefaultProps ||
         instance.getDefaultProps.isReactClassApproved;
-      warning(
-        noGetDefaultPropsOnES6,
-        "getDefaultProps was defined on %s, a plain JavaScript class. " +
-          "This is only supported for classes created using React.createClass. " +
-          "Use a static property to define defaultProps instead.",
-        name
-      );
+      !noGetDefaultPropsOnES6
+        ? warning(
+            false,
+            "getDefaultProps was defined on %s, a plain JavaScript class. " +
+              "This is only supported for classes created using React.createClass. " +
+              "Use a static property to define defaultProps instead.",
+            name
+          )
+        : void 0;
       var noInstancePropTypes = !instance.propTypes;
-      warning(
-        noInstancePropTypes,
-        "propTypes was defined as an instance property on %s. Use a static " +
-          "property to define propTypes instead.",
-        name
-      );
+      !noInstancePropTypes
+        ? warning(
+            false,
+            "propTypes was defined as an instance property on %s. Use a static " +
+              "property to define propTypes instead.",
+            name
+          )
+        : void 0;
       var noInstanceContextTypes = !instance.contextTypes;
-      warning(
-        noInstanceContextTypes,
-        "contextTypes was defined as an instance property on %s. Use a static " +
-          "property to define contextTypes instead.",
-        name
-      );
+      !noInstanceContextTypes
+        ? warning(
+            false,
+            "contextTypes was defined as an instance property on %s. Use a static " +
+              "property to define contextTypes instead.",
+            name
+          )
+        : void 0;
       var noComponentShouldUpdate =
         typeof instance.componentShouldUpdate !== "function";
-      warning(
-        noComponentShouldUpdate,
-        "%s has a method called " +
-          "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
-          "The name is phrased as a question because the function is " +
-          "expected to return a value.",
-        name
-      );
+      !noComponentShouldUpdate
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
+              "The name is phrased as a question because the function is " +
+              "expected to return a value.",
+            name
+          )
+        : void 0;
       if (
         type.prototype &&
         type.prototype.isPureReactComponent &&
@@ -6056,73 +6151,128 @@ var ReactFiberClassComponent = function(
       }
       var noComponentDidUnmount =
         typeof instance.componentDidUnmount !== "function";
-      warning(
-        noComponentDidUnmount,
-        "%s has a method called " +
-          "componentDidUnmount(). But there is no such lifecycle method. " +
-          "Did you mean componentWillUnmount()?",
-        name
-      );
+      !noComponentDidUnmount
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentDidUnmount(). But there is no such lifecycle method. " +
+              "Did you mean componentWillUnmount()?",
+            name
+          )
+        : void 0;
       var noComponentDidReceiveProps =
         typeof instance.componentDidReceiveProps !== "function";
-      warning(
-        noComponentDidReceiveProps,
-        "%s has a method called " +
-          "componentDidReceiveProps(). But there is no such lifecycle method. " +
-          "If you meant to update the state in response to changing props, " +
-          "use componentWillReceiveProps(). If you meant to fetch data or " +
-          "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
-        name
-      );
+      !noComponentDidReceiveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentDidReceiveProps(). But there is no such lifecycle method. " +
+              "If you meant to update the state in response to changing props, " +
+              "use componentWillReceiveProps(). If you meant to fetch data or " +
+              "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
+            name
+          )
+        : void 0;
       var noComponentWillRecieveProps =
         typeof instance.componentWillRecieveProps !== "function";
-      warning(
-        noComponentWillRecieveProps,
-        "%s has a method called " +
-          "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
-        name
-      );
+      !noComponentWillRecieveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
+            name
+          )
+        : void 0;
       var noUnsafeComponentWillRecieveProps =
         typeof instance.UNSAFE_componentWillRecieveProps !== "function";
-      warning(
-        noUnsafeComponentWillRecieveProps,
-        "%s has a method called " +
-          "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
-        name
-      );
+      !noUnsafeComponentWillRecieveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
+            name
+          )
+        : void 0;
       var hasMutatedProps = instance.props !== workInProgress.pendingProps;
-      warning(
-        instance.props === undefined || !hasMutatedProps,
-        "%s(...): When calling super() in `%s`, make sure to pass " +
-          "up the same props that your component's constructor was passed.",
-        name,
-        name
-      );
+      !(instance.props === undefined || !hasMutatedProps)
+        ? warning(
+            false,
+            "%s(...): When calling super() in `%s`, make sure to pass " +
+              "up the same props that your component's constructor was passed.",
+            name,
+            name
+          )
+        : void 0;
       var noInstanceDefaultProps = !instance.defaultProps;
-      warning(
-        noInstanceDefaultProps,
-        "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
-          " Instead, define defaultProps as a static property on %s.",
-        name,
-        name
-      );
-    }
+      !noInstanceDefaultProps
+        ? warning(
+            false,
+            "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
+              " Instead, define defaultProps as a static property on %s.",
+            name,
+            name
+          )
+        : void 0;
 
-    var state = instance.state;
-    if (state && (typeof state !== "object" || isArray(state))) {
-      warning(
-        false,
-        "%s.state: must be set to an object or null",
-        getComponentName(workInProgress)
-      );
-    }
-    if (typeof instance.getChildContext === "function") {
-      warning(
-        typeof type.childContextTypes === "object",
-        "%s.getChildContext(): childContextTypes must be defined in order to " +
-          "use getChildContext().",
-        getComponentName(workInProgress)
-      );
+      if (
+        typeof instance.getSnapshotBeforeUpdate === "function" &&
+        typeof instance.componentDidUpdate !== "function" &&
+        typeof instance.componentDidUpdate !== "function" &&
+        !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
+      ) {
+        didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
+        warning(
+          false,
+          "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
+            "This component defines getSnapshotBeforeUpdate() only.",
+          getComponentName(workInProgress)
+        );
+      }
+
+      var noInstanceGetDerivedStateFromProps =
+        typeof instance.getDerivedStateFromProps !== "function";
+      !noInstanceGetDerivedStateFromProps
+        ? warning(
+            false,
+            "%s: getDerivedStateFromProps() is defined as an instance method " +
+              "and will be ignored. Instead, declare it as a static method.",
+            name
+          )
+        : void 0;
+      var noInstanceGetDerivedStateFromCatch =
+        typeof instance.getDerivedStateFromCatch !== "function";
+      !noInstanceGetDerivedStateFromCatch
+        ? warning(
+            false,
+            "%s: getDerivedStateFromCatch() is defined as an instance method " +
+              "and will be ignored. Instead, declare it as a static method.",
+            name
+          )
+        : void 0;
+      var noStaticGetSnapshotBeforeUpdate =
+        typeof type.getSnapshotBeforeUpdate !== "function";
+      !noStaticGetSnapshotBeforeUpdate
+        ? warning(
+            false,
+            "%s: getSnapshotBeforeUpdate() is defined as a static method " +
+              "and will be ignored. Instead, declare it as an instance method.",
+            name
+          )
+        : void 0;
+      var _state = instance.state;
+      if (_state && (typeof _state !== "object" || isArray(_state))) {
+        warning(false, "%s.state: must be set to an object or null", name);
+      }
+      if (typeof instance.getChildContext === "function") {
+        !(typeof type.childContextTypes === "object")
+          ? warning(
+              false,
+              "%s.getChildContext(): childContextTypes must be defined in order to " +
+                "use getChildContext().",
+              name
+            )
+          : void 0;
+      }
     }
   }
 
@@ -6170,8 +6320,9 @@ var ReactFiberClassComponent = function(
         typeof ctor.getDerivedStateFromProps === "function" &&
         state === null
       ) {
-        var componentName = getComponentName(workInProgress) || "Unknown";
-        if (!didWarnAboutUninitializedState[componentName]) {
+        var componentName = getComponentName(workInProgress) || "Component";
+        if (!didWarnAboutUninitializedState.has(componentName)) {
+          didWarnAboutUninitializedState.add(componentName);
           warning(
             false,
             "%s: Did not properly initialize state during construction. " +
@@ -6179,7 +6330,75 @@ var ReactFiberClassComponent = function(
             componentName,
             instance.state === null ? "null" : "undefined"
           );
-          didWarnAboutUninitializedState[componentName] = true;
+        }
+      }
+
+      // If new component APIs are defined, "unsafe" lifecycles won't be called.
+      // Warn about these lifecycles if they are present.
+      // Don't warn about react-lifecycles-compat polyfilled methods though.
+      if (
+        typeof ctor.getDerivedStateFromProps === "function" ||
+        typeof instance.getSnapshotBeforeUpdate === "function"
+      ) {
+        var foundWillMountName = null;
+        var foundWillReceivePropsName = null;
+        var foundWillUpdateName = null;
+        if (
+          typeof instance.componentWillMount === "function" &&
+          instance.componentWillMount.__suppressDeprecationWarning !== true
+        ) {
+          foundWillMountName = "componentWillMount";
+        } else if (typeof instance.UNSAFE_componentWillMount === "function") {
+          foundWillMountName = "UNSAFE_componentWillMount";
+        }
+        if (
+          typeof instance.componentWillReceiveProps === "function" &&
+          instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+            true
+        ) {
+          foundWillReceivePropsName = "componentWillReceiveProps";
+        } else if (
+          typeof instance.UNSAFE_componentWillReceiveProps === "function"
+        ) {
+          foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
+        }
+        if (
+          typeof instance.componentWillUpdate === "function" &&
+          instance.componentWillUpdate.__suppressDeprecationWarning !== true
+        ) {
+          foundWillUpdateName = "componentWillUpdate";
+        } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+          foundWillUpdateName = "UNSAFE_componentWillUpdate";
+        }
+        if (
+          foundWillMountName !== null ||
+          foundWillReceivePropsName !== null ||
+          foundWillUpdateName !== null
+        ) {
+          var _componentName = getComponentName(workInProgress) || "Component";
+          var newApiName =
+            typeof ctor.getDerivedStateFromProps === "function"
+              ? "getDerivedStateFromProps()"
+              : "getSnapshotBeforeUpdate()";
+          if (
+            !didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)
+          ) {
+            didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
+            warning(
+              false,
+              "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
+                "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
+                "The above lifecycles should be removed. Learn more about this warning here:\n" +
+                "https://fb.me/react-async-component-lifecycle-hooks",
+              _componentName,
+              newApiName,
+              foundWillMountName !== null ? "\n  " + foundWillMountName : "",
+              foundWillReceivePropsName !== null
+                ? "\n  " + foundWillReceivePropsName
+                : "",
+              foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
+            );
+          }
         }
       }
     }
@@ -6189,7 +6408,8 @@ var ReactFiberClassComponent = function(
     var partialState = callGetDerivedStateFromProps(
       workInProgress,
       instance,
-      props
+      props,
+      state
     );
 
     if (partialState !== null && partialState !== undefined) {
@@ -6232,7 +6452,7 @@ var ReactFiberClassComponent = function(
           "%s.componentWillMount(): Assigning directly to this.state is " +
             "deprecated (except inside a component's " +
             "constructor). Use setState instead.",
-          getComponentName(workInProgress)
+          getComponentName(workInProgress) || "Component"
         );
       }
       updater.enqueueReplaceState(instance, instance.state, null);
@@ -6258,7 +6478,8 @@ var ReactFiberClassComponent = function(
     if (instance.state !== oldState) {
       {
         var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutStateAssignmentForComponent[componentName]) {
+        if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
+          didWarnAboutStateAssignmentForComponent.add(componentName);
           warning(
             false,
             "%s.componentWillReceiveProps(): Assigning directly to " +
@@ -6266,69 +6487,47 @@ var ReactFiberClassComponent = function(
               "constructor). Use setState instead.",
             componentName
           );
-          didWarnAboutStateAssignmentForComponent[componentName] = true;
         }
       }
       updater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
-  function callGetDerivedStateFromProps(workInProgress, instance, props) {
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
     var type = workInProgress.type;
 
     if (typeof type.getDerivedStateFromProps === "function") {
-      {
-        // Don't warn about react-lifecycles-compat polyfilled components
-        if (
-          (typeof instance.componentWillReceiveProps === "function" &&
-            instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-              true) ||
-          typeof instance.UNSAFE_componentWillReceiveProps === "function"
-        ) {
-          var componentName = getComponentName(workInProgress) || "Unknown";
-          if (!didWarnAboutWillReceivePropsAndDerivedState[componentName]) {
-            warning(
-              false,
-              "%s: Defines both componentWillReceiveProps() and static " +
-                "getDerivedStateFromProps() methods. We recommend using " +
-                "only getDerivedStateFromProps().",
-              componentName
-            );
-            didWarnAboutWillReceivePropsAndDerivedState[componentName] = true;
-          }
-        }
-      }
-
       if (
         debugRenderPhaseSideEffects ||
         (debugRenderPhaseSideEffectsForStrictMode &&
           workInProgress.mode & StrictMode)
       ) {
         // Invoke method an extra time to help detect side-effects.
-        type.getDerivedStateFromProps.call(
-          null,
-          props,
-          workInProgress.memoizedState
-        );
+        type.getDerivedStateFromProps.call(null, nextProps, prevState);
       }
 
       var partialState = type.getDerivedStateFromProps.call(
         null,
-        props,
-        workInProgress.memoizedState
+        nextProps,
+        prevState
       );
 
       {
         if (partialState === undefined) {
-          var _componentName = getComponentName(workInProgress) || "Unknown";
-          if (!didWarnAboutUndefinedDerivedState[_componentName]) {
+          var componentName = getComponentName(workInProgress) || "Component";
+          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+            didWarnAboutUndefinedDerivedState.add(componentName);
             warning(
               false,
               "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
                 "You have returned undefined.",
-              _componentName
+              componentName
             );
-            didWarnAboutUndefinedDerivedState[_componentName] = _componentName;
           }
         }
       }
@@ -6372,11 +6571,12 @@ var ReactFiberClassComponent = function(
     }
 
     // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
+      typeof ctor.getDerivedStateFromProps !== "function" &&
+      typeof instance.getSnapshotBeforeUpdate !== "function" &&
       (typeof instance.UNSAFE_componentWillMount === "function" ||
-        typeof instance.componentWillMount === "function") &&
-      typeof ctor.getDerivedStateFromProps !== "function"
+        typeof instance.componentWillMount === "function")
     ) {
       callComponentWillMount(workInProgress, instance);
       // If we had additional state updates during this life-cycle, let's
@@ -6409,16 +6609,20 @@ var ReactFiberClassComponent = function(
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var hasNewLifecycles =
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function";
+
     // Note: During these life-cycles, instance.props/instance.state are what
     // ever the previously attempted to render - not the "current". However,
     // during componentDidUpdate we pass the "current" props.
 
     // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
+      !hasNewLifecycles &&
       (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function") &&
-      typeof ctor.getDerivedStateFromProps !== "function"
+        typeof instance.componentWillReceiveProps === "function")
     ) {
       if (oldProps !== newProps || oldContext !== newContext) {
         callComponentWillReceiveProps(
@@ -6430,15 +6634,6 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
-        instance,
-        newProps
-      );
-    }
-
     // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
     // TODO: Previous state can be null.
@@ -6475,6 +6670,18 @@ var ReactFiberClassComponent = function(
       newState = oldState;
     }
 
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
+        workInProgress,
+        instance,
+        newProps,
+        newState
+      );
+    }
+
     if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
       // Render-phase updates (like this) should not be added to the update queue,
       // So that multiple render passes do not enqueue multiple updates.
@@ -6483,6 +6690,17 @@ var ReactFiberClassComponent = function(
         newState === null || newState === undefined
           ? derivedStateFromProps
           : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue = workInProgress.updateQueue;
+      if (_updateQueue !== null) {
+        _updateQueue.baseState = Object.assign(
+          {},
+          _updateQueue.baseState,
+          derivedStateFromProps
+        );
+      }
     }
     if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
       // Render-phase updates (like this) should not be added to the update queue,
@@ -6492,6 +6710,17 @@ var ReactFiberClassComponent = function(
         newState === null || newState === undefined
           ? derivedStateFromCatch
           : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue2 = workInProgress.updateQueue;
+      if (_updateQueue2 !== null) {
+        _updateQueue2.baseState = Object.assign(
+          {},
+          _updateQueue2.baseState,
+          derivedStateFromCatch
+        );
+      }
     }
 
     if (
@@ -6522,11 +6751,11 @@ var ReactFiberClassComponent = function(
 
     if (shouldUpdate) {
       // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+      // Unsafe lifecycles should not be invoked for components using the new APIs.
       if (
+        !hasNewLifecycles &&
         (typeof instance.UNSAFE_componentWillMount === "function" ||
-          typeof instance.componentWillMount === "function") &&
-        typeof ctor.getDerivedStateFromProps !== "function"
+          typeof instance.componentWillMount === "function")
       ) {
         startPhaseTimer(workInProgress, "componentWillMount");
         if (typeof instance.componentWillMount === "function") {
@@ -6574,16 +6803,20 @@ var ReactFiberClassComponent = function(
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var hasNewLifecycles =
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function";
+
     // Note: During these life-cycles, instance.props/instance.state are what
     // ever the previously attempted to render - not the "current". However,
     // during componentDidUpdate we pass the "current" props.
 
     // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
+      !hasNewLifecycles &&
       (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function") &&
-      typeof ctor.getDerivedStateFromProps !== "function"
+        typeof instance.componentWillReceiveProps === "function")
     ) {
       if (oldProps !== newProps || oldContext !== newContext) {
         callComponentWillReceiveProps(
@@ -6595,20 +6828,12 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
-        instance,
-        newProps
-      );
-    }
-
     // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
     // TODO: Previous state can be null.
     var newState = void 0;
     var derivedStateFromCatch = void 0;
+
     if (workInProgress.updateQueue !== null) {
       newState = processUpdateQueue(
         current,
@@ -6640,6 +6865,18 @@ var ReactFiberClassComponent = function(
       newState = oldState;
     }
 
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
+        workInProgress,
+        instance,
+        newProps,
+        newState
+      );
+    }
+
     if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
       // Render-phase updates (like this) should not be added to the update queue,
       // So that multiple render passes do not enqueue multiple updates.
@@ -6648,6 +6885,17 @@ var ReactFiberClassComponent = function(
         newState === null || newState === undefined
           ? derivedStateFromProps
           : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue3 = workInProgress.updateQueue;
+      if (_updateQueue3 !== null) {
+        _updateQueue3.baseState = Object.assign(
+          {},
+          _updateQueue3.baseState,
+          derivedStateFromProps
+        );
+      }
     }
     if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
       // Render-phase updates (like this) should not be added to the update queue,
@@ -6657,6 +6905,17 @@ var ReactFiberClassComponent = function(
         newState === null || newState === undefined
           ? derivedStateFromCatch
           : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue4 = workInProgress.updateQueue;
+      if (_updateQueue4 !== null) {
+        _updateQueue4.baseState = Object.assign(
+          {},
+          _updateQueue4.baseState,
+          derivedStateFromCatch
+        );
+      }
     }
 
     if (
@@ -6678,6 +6937,14 @@ var ReactFiberClassComponent = function(
           workInProgress.effectTag |= Update;
         }
       }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Snapshot;
+        }
+      }
       return false;
     }
 
@@ -6692,11 +6959,11 @@ var ReactFiberClassComponent = function(
 
     if (shouldUpdate) {
       // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+      // Unsafe lifecycles should not be invoked for components using the new APIs.
       if (
+        !hasNewLifecycles &&
         (typeof instance.UNSAFE_componentWillUpdate === "function" ||
-          typeof instance.componentWillUpdate === "function") &&
-        typeof ctor.getDerivedStateFromProps !== "function"
+          typeof instance.componentWillUpdate === "function")
       ) {
         startPhaseTimer(workInProgress, "componentWillUpdate");
         if (typeof instance.componentWillUpdate === "function") {
@@ -6710,6 +6977,9 @@ var ReactFiberClassComponent = function(
       if (typeof instance.componentDidUpdate === "function") {
         workInProgress.effectTag |= Update;
       }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        workInProgress.effectTag |= Snapshot;
+      }
     } else {
       // If an update was already in progress, we should schedule an Update
       // effect even though we're bailing out, so that cWU/cDU are called.
@@ -6721,6 +6991,14 @@ var ReactFiberClassComponent = function(
           workInProgress.effectTag |= Update;
         }
       }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Snapshot;
+        }
+      }
 
       // If shouldComponentUpdate returned false, we should still update the
       // memoized props/state to indicate that this work can be reused.
@@ -7560,13 +7838,15 @@ function ChildReconciler(shouldTrackSideEffects) {
       if (typeof newChildrenIterable.entries === "function") {
         var possibleMap = newChildrenIterable;
         if (possibleMap.entries === iteratorFn) {
-          warning(
-            didWarnAboutMaps,
-            "Using Maps as children is unsupported and will likely yield " +
-              "unexpected results. Convert it to a sequence/iterable of keyed " +
-              "ReactElements instead.%s",
-            getCurrentFiberStackAddendum$1()
-          );
+          !didWarnAboutMaps
+            ? warning(
+                false,
+                "Using Maps as children is unsupported and will likely yield " +
+                  "unexpected results. Convert it to a sequence/iterable of keyed " +
+                  "ReactElements instead.%s",
+                getCurrentFiberStackAddendum$1()
+              )
+            : void 0;
           didWarnAboutMaps = true;
         }
       }
@@ -8532,7 +8812,8 @@ var ReactFiberBeginWork = function(
         var partialState = callGetDerivedStateFromProps(
           workInProgress,
           value,
-          props
+          props,
+          workInProgress.memoizedState
         );
 
         if (partialState !== null && partialState !== undefined) {
@@ -8565,11 +8846,13 @@ var ReactFiberBeginWork = function(
         var _Component = workInProgress.type;
 
         if (_Component) {
-          warning(
-            !_Component.childContextTypes,
-            "%s(...): childContextTypes cannot be defined on a functional component.",
-            _Component.displayName || _Component.name || "Component"
-          );
+          !!_Component.childContextTypes
+            ? warning(
+                false,
+                "%s(...): childContextTypes cannot be defined on a functional component.",
+                _Component.displayName || _Component.name || "Component"
+              )
+            : void 0;
         }
         if (workInProgress.ref !== null) {
           var info = "";
@@ -8788,7 +9071,7 @@ var ReactFiberBeginWork = function(
     renderExpirationTime
   ) {
     var providerType = workInProgress.type;
-    var context = providerType.context;
+    var context = providerType._context;
 
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
@@ -8841,12 +9124,14 @@ var ReactFiberBeginWork = function(
               ? context._calculateChangedBits(oldValue, newValue)
               : MAX_SIGNED_31_BIT_INT;
           {
-            warning(
-              (changedBits & MAX_SIGNED_31_BIT_INT) === changedBits,
-              "calculateChangedBits: Expected the return value to be a " +
-                "31-bit integer. Instead received: %s",
-              changedBits
-            );
+            !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
+              ? warning(
+                  false,
+                  "calculateChangedBits: Expected the return value to be a " +
+                    "31-bit integer. Instead received: %s",
+                  changedBits
+                )
+              : void 0;
           }
           changedBits |= 0;
 
@@ -8914,21 +9199,23 @@ var ReactFiberBeginWork = function(
         changedBits,
         renderExpirationTime
       );
-    } else if (oldProps !== null && oldProps.children === newProps.children) {
-      // No change. Bailout early if children are the same.
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
+    // There is no bailout on `children` equality because we expect people
+    // to often pass a bound method as a child, but it may reference
+    // `this.state` or `this.props` (and thus needs to re-render on `setState`).
 
     var render = newProps.children;
 
     {
-      warning(
-        typeof render === "function",
-        "A context consumer was rendered with multiple children, or a child " +
-          "that isn't a function. A context consumer expects a single child " +
-          "that is a function. If you did pass a function, make sure there " +
-          "is no trailing or leading whitespace around it."
-      );
+      !(typeof render === "function")
+        ? warning(
+            false,
+            "A context consumer was rendered with multiple children, or a child " +
+              "that isn't a function. A context consumer expects a single child " +
+              "that is a function. If you did pass a function, make sure there " +
+              "is no trailing or leading whitespace around it."
+          )
+        : void 0;
     }
 
     var newChildren = render(newValue);
@@ -9883,6 +10170,11 @@ var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
 var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
 var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
 
+var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
+{
+  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
+}
+
 function logError(boundary, errorInfo) {
   var source = errorInfo.source;
   var stack = errorInfo.stack;
@@ -9892,21 +10184,19 @@ function logError(boundary, errorInfo) {
 
   var capturedError = {
     componentName: source !== null ? getComponentName(source) : null,
-    error: errorInfo.value,
-    errorBoundary: boundary,
     componentStack: stack !== null ? stack : "",
+    error: errorInfo.value,
+    errorBoundary: null,
     errorBoundaryName: null,
     errorBoundaryFound: false,
     willRetry: false
   };
 
-  if (boundary !== null) {
+  if (boundary !== null && boundary.tag === ClassComponent) {
+    capturedError.errorBoundary = boundary.stateNode;
     capturedError.errorBoundaryName = getComponentName(boundary);
-    capturedError.errorBoundaryFound = capturedError.willRetry =
-      boundary.tag === ClassComponent;
-  } else {
-    capturedError.errorBoundaryName = null;
-    capturedError.errorBoundaryFound = capturedError.willRetry = false;
+    capturedError.errorBoundaryFound = true;
+    capturedError.willRetry = true;
   }
 
   try {
@@ -9975,6 +10265,58 @@ var ReactFiberCommitWork = function(
     }
   }
 
+  function commitBeforeMutationLifeCycles(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        if (finishedWork.effectTag & Snapshot) {
+          if (current !== null) {
+            var prevProps = current.memoizedProps;
+            var prevState = current.memoizedState;
+            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
+            var _instance = finishedWork.stateNode;
+            _instance.props = finishedWork.memoizedProps;
+            _instance.state = finishedWork.memoizedState;
+            var snapshot = _instance.getSnapshotBeforeUpdate(
+              prevProps,
+              prevState
+            );
+            {
+              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
+              if (
+                snapshot === undefined &&
+                !didWarnSet.has(finishedWork.type)
+              ) {
+                didWarnSet.add(finishedWork.type);
+                warning(
+                  false,
+                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
+                    "must be returned. You have returned undefined.",
+                  getComponentName(finishedWork)
+                );
+              }
+            }
+            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+            stopPhaseTimer();
+          }
+        }
+        return;
+      }
+      case HostRoot:
+      case HostComponent:
+      case HostText:
+      case HostPortal:
+        // Nothing to do for these component types
+        return;
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
   function commitLifeCycles(
     finishedRoot,
     current,
@@ -9984,50 +10326,54 @@ var ReactFiberCommitWork = function(
   ) {
     switch (finishedWork.tag) {
       case ClassComponent: {
-        var _instance = finishedWork.stateNode;
+        var _instance2 = finishedWork.stateNode;
         if (finishedWork.effectTag & Update) {
           if (current === null) {
             startPhaseTimer(finishedWork, "componentDidMount");
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            _instance.componentDidMount();
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidMount();
             stopPhaseTimer();
           } else {
             var prevProps = current.memoizedProps;
             var prevState = current.memoizedState;
             startPhaseTimer(finishedWork, "componentDidUpdate");
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            _instance.componentDidUpdate(prevProps, prevState);
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidUpdate(
+              prevProps,
+              prevState,
+              _instance2.__reactInternalSnapshotBeforeUpdate
+            );
             stopPhaseTimer();
           }
         }
         var updateQueue = finishedWork.updateQueue;
         if (updateQueue !== null) {
-          commitCallbacks(updateQueue, _instance);
+          commitCallbacks(updateQueue, _instance2);
         }
         return;
       }
       case HostRoot: {
         var _updateQueue = finishedWork.updateQueue;
         if (_updateQueue !== null) {
-          var _instance2 = null;
+          var _instance3 = null;
           if (finishedWork.child !== null) {
             switch (finishedWork.child.tag) {
               case HostComponent:
-                _instance2 = getPublicInstance(finishedWork.child.stateNode);
+                _instance3 = getPublicInstance(finishedWork.child.stateNode);
                 break;
               case ClassComponent:
-                _instance2 = finishedWork.child.stateNode;
+                _instance3 = finishedWork.child.stateNode;
                 break;
             }
           }
-          commitCallbacks(_updateQueue, _instance2);
+          commitCallbacks(_updateQueue, _instance3);
         }
         return;
       }
       case HostComponent: {
-        var _instance3 = finishedWork.stateNode;
+        var _instance4 = finishedWork.stateNode;
 
         // Renderers may schedule work to be done after host components are mounted
         // (eg DOM renderer may schedule auto-focus for inputs and form controls).
@@ -10036,7 +10382,7 @@ var ReactFiberCommitWork = function(
         if (current === null && finishedWork.effectTag & Update) {
           var type = finishedWork.type;
           var props = finishedWork.memoizedProps;
-          commitMount(_instance3, type, props, finishedWork);
+          commitMount(_instance4, type, props, finishedWork);
         }
 
         return;
@@ -10064,7 +10410,7 @@ var ReactFiberCommitWork = function(
       case ClassComponent:
         {
           var ctor = finishedWork.type;
-          var _instance4 = finishedWork.stateNode;
+          var _instance5 = finishedWork.stateNode;
           var updateQueue = finishedWork.updateQueue;
           invariant(
             updateQueue !== null && updateQueue.capturedValues !== null,
@@ -10081,16 +10427,19 @@ var ReactFiberCommitWork = function(
             // This gets reset before we yield back to the browser.
             // TODO: Warn in strict mode if getDerivedStateFromCatch is
             // not defined.
-            markLegacyErrorBoundaryAsFailed(_instance4);
+            markLegacyErrorBoundaryAsFailed(_instance5);
           }
 
-          _instance4.props = finishedWork.memoizedProps;
-          _instance4.state = finishedWork.memoizedState;
+          _instance5.props = finishedWork.memoizedProps;
+          _instance5.state = finishedWork.memoizedState;
           for (var i = 0; i < capturedErrors.length; i++) {
             var errorInfo = capturedErrors[i];
             var _error = errorInfo.value;
+            var stack = errorInfo.stack;
             logError(finishedWork, errorInfo);
-            _instance4.componentDidCatch(_error);
+            _instance5.componentDidCatch(_error, {
+              componentStack: stack !== null ? stack : ""
+            });
           }
         }
         break;
@@ -10123,14 +10472,14 @@ var ReactFiberCommitWork = function(
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (ref !== null) {
-      var _instance5 = finishedWork.stateNode;
+      var _instance6 = finishedWork.stateNode;
       var instanceToUse = void 0;
       switch (finishedWork.tag) {
         case HostComponent:
-          instanceToUse = getPublicInstance(_instance5);
+          instanceToUse = getPublicInstance(_instance6);
           break;
         default:
-          instanceToUse = _instance5;
+          instanceToUse = _instance6;
       }
       if (typeof ref === "function") {
         ref(instanceToUse);
@@ -10174,9 +10523,9 @@ var ReactFiberCommitWork = function(
     switch (current.tag) {
       case ClassComponent: {
         safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if (typeof _instance6.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance6);
+        var _instance7 = current.stateNode;
+        if (typeof _instance7.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance7);
         }
         return;
       }
@@ -10313,6 +10662,7 @@ var ReactFiberCommitWork = function(
         },
 
         commitLifeCycles: commitLifeCycles,
+        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
         commitErrorLogging: commitErrorLogging,
         commitAttachRef: commitAttachRef,
         commitDetachRef: commitDetachRef
@@ -10571,8 +10921,8 @@ var ReactFiberCommitWork = function(
         return;
       }
       case HostComponent: {
-        var _instance7 = finishedWork.stateNode;
-        if (_instance7 != null) {
+        var _instance8 = finishedWork.stateNode;
+        if (_instance8 != null) {
           // Commit the work prepared earlier.
           var newProps = finishedWork.memoizedProps;
           // For hydration we reuse the update path but we treat the oldProps
@@ -10585,7 +10935,7 @@ var ReactFiberCommitWork = function(
           finishedWork.updateQueue = null;
           if (updatePayload !== null) {
             commitUpdate(
-              _instance7,
+              _instance8,
               updatePayload,
               type,
               oldProps,
@@ -10630,6 +10980,7 @@ var ReactFiberCommitWork = function(
 
   if (enableMutatingReconciler) {
     return {
+      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
       commitResetTextContent: commitResetTextContent,
       commitPlacement: commitPlacement,
       commitDeletion: commitDeletion,
@@ -10675,12 +11026,19 @@ var ReactFiberHostContext = function(config, stack) {
     // Push current root instance onto the stack;
     // This allows us to reset root when portals are popped.
     push(rootInstanceStackCursor, nextRootInstance, fiber);
-
-    var nextRootContext = getRootHostContext(nextRootInstance);
-
     // Track the context and the Fiber that provided it.
     // This enables us to pop only Fibers that provide unique contexts.
     push(contextFiberStackCursor, fiber, fiber);
+
+    // Finally, we need to push the host context to the stack.
+    // However, we can't just call getRootHostContext() and push it because
+    // we'd have a different number of entries on the stack depending on
+    // whether getRootHostContext() throws somewhere in renderer code or not.
+    // So we push an empty value first. This lets us safely unwind on errors.
+    push(contextStackCursor, NO_CONTEXT, fiber);
+    var nextRootContext = getRootHostContext(nextRootInstance);
+    // Now that we know this function doesn't throw, replace it.
+    pop(contextStackCursor, fiber);
     push(contextStackCursor, nextRootContext, fiber);
   }
 
@@ -11391,7 +11749,7 @@ var ReactFiberNewContext = function(stack) {
   }
 
   function pushProvider(providerFiber) {
-    var context = providerFiber.type.context;
+    var context = providerFiber.type._context;
 
     push(changedBitsCursor, context._changedBits, providerFiber);
     push(valueCursor, context._currentValue, providerFiber);
@@ -11401,12 +11759,16 @@ var ReactFiberNewContext = function(stack) {
     context._changedBits = providerFiber.stateNode;
 
     {
-      warning(
+      !(
         context._currentRenderer === null ||
-          context._currentRenderer === rendererSigil,
-        "Detected multiple renderers concurrently rendering the " +
-          "same context provider. This is currently unsupported."
-      );
+        context._currentRenderer === rendererSigil
+      )
+        ? warning(
+            false,
+            "Detected multiple renderers concurrently rendering the " +
+              "same context provider. This is currently unsupported."
+          )
+        : void 0;
       context._currentRenderer = rendererSigil;
     }
   }
@@ -11419,7 +11781,7 @@ var ReactFiberNewContext = function(stack) {
     pop(valueCursor, providerFiber);
     pop(changedBitsCursor, providerFiber);
 
-    var context = providerFiber.type.context;
+    var context = providerFiber.type._context;
     context._currentValue = currentValue;
     context._changedBits = changedBits;
   }
@@ -11532,17 +11894,19 @@ var warnAboutInvalidUpdates = void 0;
   var didWarnStateUpdateForUnmountedComponent = {};
 
   warnAboutUpdateOnUnmounted = function(fiber) {
+    // We show the whole stack but dedupe on the top component's name because
+    // the problematic code almost always lies inside that component.
     var componentName = getComponentName(fiber) || "ReactClass";
     if (didWarnStateUpdateForUnmountedComponent[componentName]) {
       return;
     }
     warning(
       false,
-      "Can only update a mounted or mounting " +
-        "component. This usually means you called setState, replaceState, " +
-        "or forceUpdate on an unmounted component. This is a no-op.\n\nPlease " +
-        "check the code for the %s component.",
-      componentName
+      "Can't call setState (or forceUpdate) on an unmounted component. This " +
+        "is a no-op, but it indicates a memory leak in your application. To " +
+        "fix, cancel all subscriptions and asynchronous tasks in the " +
+        "componentWillUnmount method.%s",
+      getStackAddendumByWorkInProgressFiber(fiber)
     );
     didWarnStateUpdateForUnmountedComponent[componentName] = true;
   };
@@ -11628,6 +11992,8 @@ var ReactFiberScheduler = function(config) {
       markLegacyErrorBoundaryAsFailed,
       recalculateCurrentTime
     ),
+    commitBeforeMutationLifeCycles =
+      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
     commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
     commitPlacement = _ReactFiberCommitWork.commitPlacement,
     commitDeletion = _ReactFiberCommitWork.commitDeletion,
@@ -11679,11 +12045,19 @@ var ReactFiberScheduler = function(config) {
 
   var stashedWorkInProgressProperties = void 0;
   var replayUnitOfWork = void 0;
+  var isReplayingFailedUnitOfWork = void 0;
+  var originalReplayError = void 0;
+  var rethrowOriginalError = void 0;
   if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
     stashedWorkInProgressProperties = null;
-    replayUnitOfWork = function(failedUnitOfWork, isAsync) {
-      // Retore the original state of the work-in-progress
-      Object.assign(failedUnitOfWork, stashedWorkInProgressProperties);
+    isReplayingFailedUnitOfWork = false;
+    originalReplayError = null;
+    replayUnitOfWork = function(failedUnitOfWork, error, isAsync) {
+      // Restore the original state of the work-in-progress
+      assignFiberPropertiesInDEV(
+        failedUnitOfWork,
+        stashedWorkInProgressProperties
+      );
       switch (failedUnitOfWork.tag) {
         case HostRoot:
           popHostContainer(failedUnitOfWork);
@@ -11703,14 +12077,22 @@ var ReactFiberScheduler = function(config) {
           break;
       }
       // Replay the begin phase.
+      isReplayingFailedUnitOfWork = true;
+      originalReplayError = error;
       invokeGuardedCallback$2(null, workLoop, null, isAsync);
+      isReplayingFailedUnitOfWork = false;
+      originalReplayError = null;
       if (hasCaughtError()) {
         clearCaughtError();
       } else {
-        // This should be unreachable because the render phase is
-        // idempotent
+        // If the begin phase did not fail the second time, set this pointer
+        // back to the original value.
+        nextUnitOfWork = failedUnitOfWork;
       }
     };
+    rethrowOriginalError = function() {
+      throw originalReplayError;
+    };
   }
 
   function resetStack() {
@@ -11742,6 +12124,7 @@ var ReactFiberScheduler = function(config) {
       recordEffect();
 
       var effectTag = nextEffect.effectTag;
+
       if (effectTag & ContentReset) {
         commitResetTextContent(nextEffect);
       }
@@ -11799,6 +12182,22 @@ var ReactFiberScheduler = function(config) {
     }
   }
 
+  function commitBeforeMutationLifecycles() {
+    while (nextEffect !== null) {
+      var effectTag = nextEffect.effectTag;
+
+      if (effectTag & Snapshot) {
+        recordEffect();
+        var current = nextEffect.alternate;
+        commitBeforeMutationLifeCycles(current, nextEffect);
+      }
+
+      // Don't cleanup effects yet;
+      // This will be done by commitAllLifeCycles()
+      nextEffect = nextEffect.nextEffect;
+    }
+  }
+
   function commitAllLifeCycles(
     finishedRoot,
     currentTime,
@@ -11906,16 +12305,14 @@ var ReactFiberScheduler = function(config) {
 
     prepareForCommit(root.containerInfo);
 
-    // Commit all the side-effects within a tree. We'll do this in two passes.
-    // The first pass performs all the host insertions, updates, deletions and
-    // ref unmounts.
+    // Invoke instances of getSnapshotBeforeUpdate before mutation.
     nextEffect = firstEffect;
-    startCommitHostEffectsTimer();
+    startCommitSnapshotEffectsTimer();
     while (nextEffect !== null) {
       var didError = false;
       var error = void 0;
       {
-        invokeGuardedCallback$2(null, commitAllHostEffects, null);
+        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
         if (hasCaughtError()) {
           didError = true;
           error = clearCaughtError();
@@ -11934,6 +12331,36 @@ var ReactFiberScheduler = function(config) {
         }
       }
     }
+    stopCommitSnapshotEffectsTimer();
+
+    // Commit all the side-effects within a tree. We'll do this in two passes.
+    // The first pass performs all the host insertions, updates, deletions and
+    // ref unmounts.
+    nextEffect = firstEffect;
+    startCommitHostEffectsTimer();
+    while (nextEffect !== null) {
+      var _didError = false;
+      var _error = void 0;
+      {
+        invokeGuardedCallback$2(null, commitAllHostEffects, null);
+        if (hasCaughtError()) {
+          _didError = true;
+          _error = clearCaughtError();
+        }
+      }
+      if (_didError) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, _error);
+        // Clean-up
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
     stopCommitHostEffectsTimer();
 
     resetAfterCommit(root.containerInfo);
@@ -11951,8 +12378,8 @@ var ReactFiberScheduler = function(config) {
     nextEffect = firstEffect;
     startCommitLifeCyclesTimer();
     while (nextEffect !== null) {
-      var _didError = false;
-      var _error = void 0;
+      var _didError2 = false;
+      var _error2 = void 0;
       {
         invokeGuardedCallback$2(
           null,
@@ -11963,17 +12390,17 @@ var ReactFiberScheduler = function(config) {
           committedExpirationTime
         );
         if (hasCaughtError()) {
-          _didError = true;
-          _error = clearCaughtError();
+          _didError2 = true;
+          _error2 = clearCaughtError();
         }
       }
-      if (_didError) {
+      if (_didError2) {
         invariant(
           nextEffect !== null,
           "Should have next effect. This error is likely caused by a bug " +
             "in React. Please file an issue."
         );
-        onCommitPhaseError(nextEffect, _error);
+        onCommitPhaseError(nextEffect, _error2);
         if (nextEffect !== null) {
           nextEffect = nextEffect.nextEffect;
         }
@@ -12197,12 +12624,21 @@ var ReactFiberScheduler = function(config) {
     }
 
     if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-      stashedWorkInProgressProperties = Object.assign({}, workInProgress);
+      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
+        stashedWorkInProgressProperties,
+        workInProgress
+      );
     }
     var next = beginWork(current, workInProgress, nextRenderExpirationTime);
-
     {
       ReactDebugCurrentFiber.resetCurrentFiber();
+      if (isReplayingFailedUnitOfWork) {
+        // Currently replaying a failed unit of work. This should be unreachable,
+        // because the render phase is meant to be idempotent, and it should
+        // have thrown again. Since it didn't, rethrow the original error, so
+        // React's internal stack is not misaligned.
+        rethrowOriginalError();
+      }
     }
     if (true && ReactFiberInstrumentation_1.debugTool) {
       ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
@@ -12276,13 +12712,18 @@ var ReactFiberScheduler = function(config) {
 
         if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
-          replayUnitOfWork(failedUnitOfWork, isAsync);
+          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
         }
 
         var sourceFiber = nextUnitOfWork;
         var returnFiber = sourceFiber["return"];
         if (returnFiber === null) {
-          // This is a fatal error.
+          // This is the root. The root could capture its own errors. However,
+          // we don't know if it errors before or after we pushed the host
+          // context. This information is needed to avoid a stack mismatch.
+          // Because we're not sure, treat this as a fatal error. We could track
+          // which phase it fails in, but doesn't seem worth it. At least
+          // for now.
           didFatal = true;
           onUncaughtError(thrownValue);
           break;
@@ -12294,12 +12735,13 @@ var ReactFiberScheduler = function(config) {
     } while (true);
 
     // We're done performing work. Time to clean up.
-    stopWorkLoopTimer(interruptedBy);
-    interruptedBy = null;
+    var didCompleteRoot = false;
     isWorking = false;
 
     // Yield back to main thread.
     if (didFatal) {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
       // There was a fatal error.
       {
         stack.resetStackAfterFatalErrorInDev();
@@ -12308,12 +12750,17 @@ var ReactFiberScheduler = function(config) {
     } else if (nextUnitOfWork === null) {
       // We reached the root.
       if (isRootReadyForCommit) {
+        didCompleteRoot = true;
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
         // The root successfully completed. It's ready for commit.
         root.pendingCommitExpirationTime = expirationTime;
         var finishedWork = root.current.alternate;
         return finishedWork;
       } else {
         // The root did not complete.
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
         invariant(
           false,
           "Expired work should have completed. This error is likely caused " +
@@ -12321,6 +12768,8 @@ var ReactFiberScheduler = function(config) {
         );
       }
     } else {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
       // There's more work to do, but we ran out of time. Yield back to
       // the renderer.
       return null;
@@ -12506,7 +12955,15 @@ var ReactFiberScheduler = function(config) {
             interruptedBy = fiber;
             resetStack();
           }
-          if (nextRoot !== root || !isWorking) {
+          if (
+            // If we're in the render phase, we don't need to schedule this root
+            // for an update, because we'll do it before we exit...
+            !isWorking ||
+            isCommitting ||
+            // ...unless this is a different root than the one we're rendering.
+            nextRoot !== root
+          ) {
+            // Add this root to the root schedule.
             requestWork(root, expirationTime);
           }
           if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
@@ -12766,7 +13223,8 @@ var ReactFiberScheduler = function(config) {
 
     if (enableUserTimingAPI && deadline !== null) {
       var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
-      stopRequestCallbackTimer(didExpire);
+      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
+      stopRequestCallbackTimer(didExpire, timeout);
     }
 
     if (isAsync) {
@@ -12826,7 +13284,11 @@ var ReactFiberScheduler = function(config) {
     // Perform work on root as if the given expiration time is the current time.
     // This has the effect of synchronously flushing all work up to and
     // including the given time.
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
     performWorkOnRoot(root, expirationTime, false);
+    // Flush any sync work that was scheduled by lifecycles
+    performSyncWork();
     finishRendering();
   }
 
@@ -13153,12 +13615,14 @@ var ReactFiberReconciler$1 = function(config) {
 
     callback = callback === undefined ? null : callback;
     {
-      warning(
-        callback === null || typeof callback === "function",
-        "render(...): Expected the last optional `callback` argument to be a " +
-          "function. Instead received: %s.",
-        callback
-      );
+      !(callback === null || typeof callback === "function")
+        ? warning(
+            false,
+            "render(...): Expected the last optional `callback` argument to be a " +
+              "function. Instead received: %s.",
+            callback
+          )
+        : void 0;
     }
 
     var update = {
diff --git a/Libraries/Renderer/ReactFabric-prod.js b/Libraries/Renderer/ReactFabric-prod.js
index 08f112c70d45..c12ebd601c84 100644
--- a/Libraries/Renderer/ReactFabric-prod.js
+++ b/Libraries/Renderer/ReactFabric-prod.js
@@ -1494,7 +1494,8 @@ var ReactNativeComponent = (function(_React$Component) {
   frameDeadlineObject = {
     timeRemaining: function() {
       return frameDeadline - now();
-    }
+    },
+    didTimeout: !1
   };
 function setTimeoutCallback() {
   frameDeadline = now() + 5;
@@ -2036,13 +2037,18 @@ function ReactFiberClassComponent(
     instance.state !== workInProgress &&
       updater.enqueueReplaceState(instance, instance.state, null);
   }
-  function callGetDerivedStateFromProps(workInProgress, instance, props) {
-    instance = workInProgress.type;
-    if ("function" === typeof instance.getDerivedStateFromProps)
-      return instance.getDerivedStateFromProps.call(
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    workInProgress = workInProgress.type;
+    if ("function" === typeof workInProgress.getDerivedStateFromProps)
+      return workInProgress.getDerivedStateFromProps.call(
         null,
-        props,
-        workInProgress.memoizedState
+        nextProps,
+        prevState
       );
   }
   var cacheContext = legacyContext.cacheContext,
@@ -2113,7 +2119,7 @@ function ReactFiberClassComponent(
         null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
       adoptClassInstance(workInProgress, ctor);
       workInProgress.memoizedState = state;
-      props = callGetDerivedStateFromProps(workInProgress, ctor, props);
+      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
       null !== props &&
         void 0 !== props &&
         (workInProgress.memoizedState = Object.assign(
@@ -2134,9 +2140,10 @@ function ReactFiberClassComponent(
       instance.state = workInProgress.memoizedState;
       instance.refs = emptyObject;
       instance.context = getMaskedContext(workInProgress, unmaskedContext);
-      ("function" !== typeof instance.UNSAFE_componentWillMount &&
-        "function" !== typeof instance.componentWillMount) ||
-        "function" === typeof ctor.getDerivedStateFromProps ||
+      "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate ||
+        ("function" !== typeof instance.UNSAFE_componentWillMount &&
+          "function" !== typeof instance.componentWillMount) ||
         ((ctor = instance.state),
         "function" === typeof instance.componentWillMount &&
           instance.componentWillMount(),
@@ -2167,9 +2174,11 @@ function ReactFiberClassComponent(
         oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-        "function" !== typeof instance.componentWillReceiveProps) ||
+      (ctor =
         "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate) ||
+        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
+          "function" !== typeof instance.componentWillReceiveProps) ||
         ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
           callComponentWillReceiveProps(
             workInProgress,
@@ -2177,14 +2186,7 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      oldContext = void 0;
-      oldProps !== newProps &&
-        (oldContext = callGetDerivedStateFromProps(
-          workInProgress,
-          instance,
-          newProps
-        ));
-      var oldState = workInProgress.memoizedState;
+      oldContext = workInProgress.memoizedState;
       renderExpirationTime =
         null !== workInProgress.updateQueue
           ? processUpdateQueue(
@@ -2195,17 +2197,32 @@ function ReactFiberClassComponent(
               newProps,
               renderExpirationTime
             )
-          : oldState;
-      null !== oldContext &&
-        void 0 !== oldContext &&
-        (renderExpirationTime =
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
+          workInProgress,
+          instance,
+          newProps,
+          renderExpirationTime
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
           null === renderExpirationTime || void 0 === renderExpirationTime
-            ? oldContext
-            : Object.assign({}, renderExpirationTime, oldContext));
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue = workInProgress.updateQueue;
+        null !== _updateQueue &&
+          (_updateQueue.baseState = Object.assign(
+            {},
+            _updateQueue.baseState,
+            derivedStateFromProps
+          ));
+      }
       if (
         !(
           oldProps !== newProps ||
-          oldState !== renderExpirationTime ||
+          oldContext !== renderExpirationTime ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2220,13 +2237,13 @@ function ReactFiberClassComponent(
         workInProgress,
         oldProps,
         newProps,
-        oldState,
+        oldContext,
         renderExpirationTime,
         newUnmaskedContext
       ))
-        ? (("function" !== typeof instance.UNSAFE_componentWillMount &&
-            "function" !== typeof instance.componentWillMount) ||
-            "function" === typeof ctor.getDerivedStateFromProps ||
+        ? (ctor ||
+            ("function" !== typeof instance.UNSAFE_componentWillMount &&
+              "function" !== typeof instance.componentWillMount) ||
             ("function" === typeof instance.componentWillMount &&
               instance.componentWillMount(),
             "function" === typeof instance.UNSAFE_componentWillMount &&
@@ -2256,9 +2273,11 @@ function ReactFiberClassComponent(
         oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-        "function" !== typeof instance.componentWillReceiveProps) ||
+      (ctor =
         "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate) ||
+        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
+          "function" !== typeof instance.componentWillReceiveProps) ||
         ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
           callComponentWillReceiveProps(
             workInProgress,
@@ -2266,13 +2285,6 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
-          workInProgress,
-          instance,
-          newProps
-        ));
       oldContext = workInProgress.memoizedState;
       renderExpirationTime =
         null !== workInProgress.updateQueue
@@ -2285,12 +2297,27 @@ function ReactFiberClassComponent(
               renderExpirationTime
             )
           : oldContext;
-      null !== derivedStateFromProps &&
-        void 0 !== derivedStateFromProps &&
-        (renderExpirationTime =
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
+          workInProgress,
+          instance,
+          newProps,
+          renderExpirationTime
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
           null === renderExpirationTime || void 0 === renderExpirationTime
             ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps));
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue3 = workInProgress.updateQueue;
+        null !== _updateQueue3 &&
+          (_updateQueue3.baseState = Object.assign(
+            {},
+            _updateQueue3.baseState,
+            derivedStateFromProps
+          ));
+      }
       if (
         !(
           oldProps !== newProps ||
@@ -2305,6 +2332,10 @@ function ReactFiberClassComponent(
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
             (workInProgress.effectTag |= 4),
+          "function" !== typeof instance.getSnapshotBeforeUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 2048),
           !1
         );
       (derivedStateFromProps = checkShouldComponentUpdate(
@@ -2315,9 +2346,9 @@ function ReactFiberClassComponent(
         renderExpirationTime,
         newUnmaskedContext
       ))
-        ? (("function" !== typeof instance.UNSAFE_componentWillUpdate &&
-            "function" !== typeof instance.componentWillUpdate) ||
-            "function" === typeof ctor.getDerivedStateFromProps ||
+        ? (ctor ||
+            ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
+              "function" !== typeof instance.componentWillUpdate) ||
             ("function" === typeof instance.componentWillUpdate &&
               instance.componentWillUpdate(
                 newProps,
@@ -2331,11 +2362,17 @@ function ReactFiberClassComponent(
                 newUnmaskedContext
               )),
           "function" === typeof instance.componentDidUpdate &&
-            (workInProgress.effectTag |= 4))
+            (workInProgress.effectTag |= 4),
+          "function" === typeof instance.getSnapshotBeforeUpdate &&
+            (workInProgress.effectTag |= 2048))
         : ("function" !== typeof instance.componentDidUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
             (workInProgress.effectTag |= 4),
+          "function" !== typeof instance.getSnapshotBeforeUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 2048),
           memoizeProps(workInProgress, newProps),
           memoizeState(workInProgress, renderExpirationTime));
       instance.props = newProps;
@@ -3181,7 +3218,7 @@ function ReactFiberBeginWork(
     workInProgress,
     renderExpirationTime
   ) {
-    var context = workInProgress.type.context,
+    var context = workInProgress.type._context,
       newProps = workInProgress.pendingProps,
       oldProps = workInProgress.memoizedProps;
     if (!hasLegacyContextChanged() && oldProps === newProps)
@@ -3347,7 +3384,8 @@ function ReactFiberBeginWork(
                 ((props = callGetDerivedStateFromProps(
                   workInProgress,
                   fn,
-                  props
+                  props,
+                  workInProgress.memoizedState
                 )),
                 null !== props &&
                   void 0 !== props &&
@@ -3618,43 +3656,33 @@ function ReactFiberBeginWork(
             renderExpirationTime
           );
         case 12:
-          a: {
-            fn = workInProgress.type;
-            unmaskedContext = workInProgress.pendingProps;
-            updateQueue = workInProgress.memoizedProps;
-            props = fn._currentValue;
-            var changedBits = fn._changedBits;
-            if (
-              hasLegacyContextChanged() ||
-              0 !== changedBits ||
-              updateQueue !== unmaskedContext
-            ) {
-              workInProgress.memoizedProps = unmaskedContext;
-              var observedBits = unmaskedContext.unstable_observedBits;
-              if (void 0 === observedBits || null === observedBits)
-                observedBits = 1073741823;
-              workInProgress.stateNode = observedBits;
-              if (0 !== (changedBits & observedBits))
-                propagateContextChange(
-                  workInProgress,
-                  fn,
-                  changedBits,
-                  renderExpirationTime
-                );
-              else if (
-                null !== updateQueue &&
-                updateQueue.children === unmaskedContext.children
-              ) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-              renderExpirationTime = unmaskedContext.children;
-              renderExpirationTime = renderExpirationTime(props);
-              reconcileChildren(current, workInProgress, renderExpirationTime);
-              current = workInProgress.child;
-            } else
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
+          fn = workInProgress.type;
+          unmaskedContext = workInProgress.pendingProps;
+          var oldProps = workInProgress.memoizedProps;
+          props = fn._currentValue;
+          updateQueue = fn._changedBits;
+          if (
+            hasLegacyContextChanged() ||
+            0 !== updateQueue ||
+            oldProps !== unmaskedContext
+          ) {
+            workInProgress.memoizedProps = unmaskedContext;
+            oldProps = unmaskedContext.unstable_observedBits;
+            if (void 0 === oldProps || null === oldProps) oldProps = 1073741823;
+            workInProgress.stateNode = oldProps;
+            0 !== (updateQueue & oldProps) &&
+              propagateContextChange(
+                workInProgress,
+                fn,
+                updateQueue,
+                renderExpirationTime
+              );
+            renderExpirationTime = unmaskedContext.children;
+            renderExpirationTime = renderExpirationTime(props);
+            reconcileChildren(current, workInProgress, renderExpirationTime);
+            current = workInProgress.child;
+          } else
+            current = bailoutOnAlreadyFinishedWork(current, workInProgress);
           return current;
         default:
           invariant(
@@ -4105,7 +4133,7 @@ function logError(boundary, errorInfo) {
   null === errorInfo.stack && getStackAddendumByWorkInProgressFiber(source);
   null !== source && getComponentName(source);
   errorInfo = errorInfo.value;
-  null !== boundary && getComponentName(boundary);
+  null !== boundary && 2 === boundary.tag && getComponentName(boundary);
   try {
     (errorInfo && errorInfo.suppressReactErrorLogging) ||
       console.error(errorInfo);
@@ -4131,6 +4159,31 @@ function ReactFiberCommitWork(
         }
       else ref.current = null;
   }
+  function commitBeforeMutationLifeCycles(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case 2:
+        if (finishedWork.effectTag & 2048 && null !== current) {
+          var prevProps = current.memoizedProps,
+            prevState = current.memoizedState;
+          current = finishedWork.stateNode;
+          current.props = finishedWork.memoizedProps;
+          current.state = finishedWork.memoizedState;
+          finishedWork = current.getSnapshotBeforeUpdate(prevProps, prevState);
+          current.__reactInternalSnapshotBeforeUpdate = finishedWork;
+        }
+        break;
+      case 3:
+      case 5:
+      case 6:
+      case 4:
+        break;
+      default:
+        invariant(
+          !1,
+          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
   function commitLifeCycles(finishedRoot, current, finishedWork) {
     switch (finishedWork.tag) {
       case 2:
@@ -4145,7 +4198,11 @@ function ReactFiberCommitWork(
             current = current.memoizedState;
             finishedRoot.props = finishedWork.memoizedProps;
             finishedRoot.state = finishedWork.memoizedState;
-            finishedRoot.componentDidUpdate(prevProps, current);
+            finishedRoot.componentDidUpdate(
+              prevProps,
+              current,
+              finishedRoot.__reactInternalSnapshotBeforeUpdate
+            );
           }
         finishedWork = finishedWork.updateQueue;
         null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
@@ -4205,9 +4262,12 @@ function ReactFiberCommitWork(
         onUncaughtError.state = finishedWork.memoizedState;
         for (ctor = 0; ctor < capturedErrors.length; ctor++) {
           updateQueue = capturedErrors[ctor];
-          var _error = updateQueue.value;
+          var _error = updateQueue.value,
+            stack = updateQueue.stack;
           logError(finishedWork, updateQueue);
-          onUncaughtError.componentDidCatch(_error);
+          onUncaughtError.componentDidCatch(_error, {
+            componentStack: null !== stack ? stack : ""
+          });
         }
         break;
       case 3:
@@ -4233,13 +4293,13 @@ function ReactFiberCommitWork(
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (null !== ref) {
-      var _instance5 = finishedWork.stateNode;
+      var _instance6 = finishedWork.stateNode;
       switch (finishedWork.tag) {
         case 5:
-          finishedWork = getPublicInstance(_instance5);
+          finishedWork = getPublicInstance(_instance6);
           break;
         default:
-          finishedWork = _instance5;
+          finishedWork = _instance6;
       }
       "function" === typeof ref
         ? ref(finishedWork)
@@ -4260,12 +4320,12 @@ function ReactFiberCommitWork(
       switch (current.tag) {
         case 2:
           safelyDetachRef(current);
-          var _instance6 = current.stateNode;
-          if ("function" === typeof _instance6.componentWillUnmount)
+          var _instance7 = current.stateNode;
+          if ("function" === typeof _instance7.componentWillUnmount)
             try {
-              (_instance6.props = current.memoizedProps),
-                (_instance6.state = current.memoizedState),
-                _instance6.componentWillUnmount();
+              (_instance7.props = current.memoizedProps),
+                (_instance7.state = current.memoizedState),
+                _instance7.componentWillUnmount();
             } catch (unmountError) {
               captureError(current, unmountError);
             }
@@ -4343,6 +4403,7 @@ function ReactFiberCommitWork(
         commitContainer(finishedWork);
       },
       commitLifeCycles: commitLifeCycles,
+      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
       commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
@@ -4386,8 +4447,10 @@ function ReactFiberHostContext(config, stack) {
     },
     pushHostContainer: function(fiber, nextRootInstance) {
       push(rootInstanceStackCursor, nextRootInstance, fiber);
-      nextRootInstance = getRootHostContext(nextRootInstance);
       push(contextFiberStackCursor, fiber, fiber);
+      push(contextStackCursor, NO_CONTEXT, fiber);
+      nextRootInstance = getRootHostContext(nextRootInstance);
+      pop(contextStackCursor, fiber);
       push(contextStackCursor, nextRootInstance, fiber);
     },
     pushHostContext: function(fiber) {
@@ -4694,7 +4757,7 @@ function ReactFiberNewContext(stack) {
     changedBitsCursor = createCursor(0);
   return {
     pushProvider: function(providerFiber) {
-      var context = providerFiber.type.context;
+      var context = providerFiber.type._context;
       push(changedBitsCursor, context._changedBits, providerFiber);
       push(valueCursor, context._currentValue, providerFiber);
       push(providerCursor, providerFiber, providerFiber);
@@ -4707,7 +4770,7 @@ function ReactFiberNewContext(stack) {
       pop(providerCursor, providerFiber);
       pop(valueCursor, providerFiber);
       pop(changedBitsCursor, providerFiber);
-      providerFiber = providerFiber.type.context;
+      providerFiber = providerFiber.type._context;
       providerFiber._currentValue = currentValue;
       providerFiber._changedBits = changedBits;
     }
@@ -4820,7 +4883,7 @@ function ReactFiberScheduler(config) {
         workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
         if (null !== workInProgress$jscomp$0)
           return (
-            (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
+            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
           );
         null !== returnFiber &&
           ((returnFiber.firstEffect = returnFiber.lastEffect = null),
@@ -4984,7 +5047,7 @@ function ReactFiberScheduler(config) {
               0 !== nextRenderExpirationTime &&
               expirationTime < nextRenderExpirationTime &&
               resetStack();
-            (nextRoot === root && isWorking) ||
+            (isWorking && !isCommitting && nextRoot === root) ||
               requestWork(root, expirationTime);
             nestedUpdateCount > NESTED_UPDATE_LIMIT &&
               invariant(
@@ -5048,7 +5111,7 @@ function ReactFiberScheduler(config) {
           (nextFlushedExpirationTime = 1),
           performWorkOnRoot(root, 1, !1))
         : 1 === expirationTime
-          ? performWork(1, !1, null)
+          ? performSyncWork()
           : scheduleCallbackWithExpiration(expirationTime));
   }
   function findHighestPriorityRoot() {
@@ -5108,6 +5171,9 @@ function ReactFiberScheduler(config) {
   function performAsyncWork(dl) {
     performWork(0, !0, dl);
   }
+  function performSyncWork() {
+    performWork(1, !1, null);
+  }
   function performWork(minExpirationTime, isAsync, dl) {
     deadline = dl;
     findHighestPriorityRoot();
@@ -5230,6 +5296,25 @@ function ReactFiberScheduler(config) {
     for (nextEffect = firstEffect; null !== nextEffect; ) {
       var didError = !1,
         error = void 0;
+      try {
+        for (; null !== nextEffect; )
+          nextEffect.effectTag & 2048 &&
+            commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
+            (nextEffect = nextEffect.nextEffect);
+      } catch (e) {
+        (didError = !0), (error = e);
+      }
+      didError &&
+        (invariant(
+          null !== nextEffect,
+          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        onCommitPhaseError(nextEffect, error),
+        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    }
+    for (nextEffect = firstEffect; null !== nextEffect; ) {
+      didError = !1;
+      error = void 0;
       try {
         for (; null !== nextEffect; ) {
           var effectTag = nextEffect.effectTag;
@@ -5370,7 +5455,9 @@ function ReactFiberScheduler(config) {
     },
     recalculateCurrentTime
   );
-  var commitResetTextContent = hostContext.commitResetTextContent,
+  var commitBeforeMutationLifeCycles =
+      hostContext.commitBeforeMutationLifeCycles,
+    commitResetTextContent = hostContext.commitResetTextContent,
     commitPlacement = hostContext.commitPlacement,
     commitDeletion = hostContext.commitDeletion,
     commitWork = hostContext.commitWork,
@@ -5425,7 +5512,10 @@ function ReactFiberScheduler(config) {
         !isRendering,
         "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
       );
+      nextFlushedRoot = root;
+      nextFlushedExpirationTime = expirationTime;
       performWorkOnRoot(root, expirationTime, !1);
+      performSyncWork();
       finishRendering();
     },
     batchedUpdates: function(fn, a) {
@@ -5436,7 +5526,7 @@ function ReactFiberScheduler(config) {
       } finally {
         (isBatchingUpdates = previousIsBatchingUpdates) ||
           isRendering ||
-          performWork(1, !1, null);
+          performSyncWork();
       }
     },
     unbatchedUpdates: function(fn, a) {
@@ -5460,8 +5550,7 @@ function ReactFiberScheduler(config) {
       try {
         return syncUpdates(fn, a);
       } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates),
-          performWork(1, !1, null);
+        (isBatchingUpdates = previousIsBatchingUpdates), performSyncWork();
       }
     },
     flushControlled: function(fn) {
@@ -5502,7 +5591,7 @@ function ReactFiberScheduler(config) {
         (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
           (isBatchingUpdates = previousIsBatchingUpdates) ||
             isRendering ||
-            performWork(1, !1, null);
+            performSyncWork();
       }
     },
     flushInteractiveUpdates: function() {
@@ -6003,7 +6092,7 @@ ReactFabricRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
-  version: "16.3.0-alpha.2",
+  version: "16.3.1",
   rendererPackageName: "react-native-renderer"
 });
 var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
diff --git a/Libraries/Renderer/ReactNativeRenderer-dev.js b/Libraries/Renderer/ReactNativeRenderer-dev.js
index 8ea8bcf85094..7fd62f11ca6a 100644
--- a/Libraries/Renderer/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/ReactNativeRenderer-dev.js
@@ -510,11 +510,13 @@ var injection$1 = {
     getNodeFromInstance = Injected.getNodeFromInstance;
 
     {
-      warning(
-        getNodeFromInstance && getInstanceFromNode,
-        "EventPluginUtils.injection.injectComponentTree(...): Injected " +
-          "module is missing getNodeFromInstance or getInstanceFromNode."
-      );
+      !(getNodeFromInstance && getInstanceFromNode)
+        ? warning(
+            false,
+            "EventPluginUtils.injection.injectComponentTree(...): Injected " +
+              "module is missing getNodeFromInstance or getInstanceFromNode."
+          )
+        : void 0;
     }
   }
 };
@@ -550,10 +552,9 @@ var validateEventDispatches = void 0;
       ? dispatchInstances.length
       : dispatchInstances ? 1 : 0;
 
-    warning(
-      instancesIsArr === listenersIsArr && instancesLen === listenersLen,
-      "EventPluginUtils: Invalid `event`."
-    );
+    !(instancesIsArr === listenersIsArr && instancesLen === listenersLen)
+      ? warning(false, "EventPluginUtils: Invalid `event`.")
+      : void 0;
   };
 }
 
@@ -1094,7 +1095,7 @@ function listenerAtPhase(inst, event, propagationPhase) {
  */
 function accumulateDirectionalDispatches(inst, phase, event) {
   {
-    warning(inst, "Dispatching inst must not be null");
+    !inst ? warning(false, "Dispatching inst must not be null") : void 0;
   }
   var listener = listenerAtPhase(inst, event, phase);
   if (listener) {
@@ -1413,13 +1414,15 @@ SyntheticEvent.extend = function(Interface) {
               !target.constructor.Interface.hasOwnProperty(prop) &&
               shouldBeReleasedProperties.indexOf(prop) === -1
             ) {
-              warning(
-                didWarnForAddedNewProperty || target.isPersistent(),
-                "This synthetic event is reused for performance reasons. If you're " +
-                  "seeing this, you're adding a new property in the synthetic event object. " +
-                  "The property is never released. See " +
-                  "https://fb.me/react-event-pooling for more information."
-              );
+              !(didWarnForAddedNewProperty || target.isPersistent())
+                ? warning(
+                    false,
+                    "This synthetic event is reused for performance reasons. If you're " +
+                      "seeing this, you're adding a new property in the synthetic event object. " +
+                      "The property is never released. See " +
+                      "https://fb.me/react-event-pooling for more information."
+                  )
+                : void 0;
               didWarnForAddedNewProperty = true;
             }
             target[prop] = value;
@@ -1466,16 +1469,18 @@ function getPooledWarningPropertyDefinition(propName, getVal) {
 
   function warn(action, result) {
     var warningCondition = false;
-    warning(
-      warningCondition,
-      "This synthetic event is reused for performance reasons. If you're seeing this, " +
-        "you're %s `%s` on a released/nullified synthetic event. %s. " +
-        "If you must keep the original synthetic event around, use event.persist(). " +
-        "See https://fb.me/react-event-pooling for more information.",
-      action,
-      propName,
-      result
-    );
+    !warningCondition
+      ? warning(
+          false,
+          "This synthetic event is reused for performance reasons. If you're seeing this, " +
+            "you're %s `%s` on a released/nullified synthetic event. %s. " +
+            "If you must keep the original synthetic event around, use event.persist(). " +
+            "See https://fb.me/react-event-pooling for more information.",
+          action,
+          propName,
+          result
+        )
+      : void 0;
   }
 }
 
@@ -1593,13 +1598,15 @@ function getTouchIdentifier(_ref) {
 
   invariant(identifier != null, "Touch object is missing identifier.");
   {
-    warning(
-      identifier <= MAX_TOUCH_BANK,
-      "Touch identifier %s is greater than maximum supported %s which causes " +
-        "performance issues backfilling array locations for all of the indices.",
-      identifier,
-      MAX_TOUCH_BANK
-    );
+    !(identifier <= MAX_TOUCH_BANK)
+      ? warning(
+          false,
+          "Touch identifier %s is greater than maximum supported %s which causes " +
+            "performance issues backfilling array locations for all of the indices.",
+          identifier,
+          MAX_TOUCH_BANK
+        )
+      : void 0;
   }
   return identifier;
 }
@@ -1698,10 +1705,9 @@ var ResponderTouchHistoryStore = {
         }
         {
           var activeRecord = touchBank[touchHistory.indexOfSingleActiveTouch];
-          warning(
-            activeRecord != null && activeRecord.touchActive,
-            "Cannot find single active touch."
-          );
+          !(activeRecord != null && activeRecord.touchActive)
+            ? warning(false, "Cannot find single active touch.")
+            : void 0;
         }
       }
     }
@@ -2987,7 +2993,7 @@ var TouchHistoryMath = {
 
 // TODO: this is special because it gets imported during build.
 
-var ReactVersion = "16.3.0-alpha.2";
+var ReactVersion = "16.3.1";
 
 function _classCallCheck(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
@@ -3657,15 +3663,17 @@ function findNodeHandle(componentOrHandle) {
   {
     var owner = ReactCurrentOwner.current;
     if (owner !== null && owner.stateNode !== null) {
-      warning(
-        owner.stateNode._warnedAboutRefsInRender,
-        "%s is accessing findNodeHandle inside its render(). " +
-          "render() should be a pure function of props and state. It should " +
-          "never access something that requires stale data from the previous " +
-          "render, such as refs. Move this logic to componentDidMount and " +
-          "componentDidUpdate instead.",
-        getComponentName(owner) || "A component"
-      );
+      !owner.stateNode._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing findNodeHandle inside its render(). " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(owner) || "A component"
+          )
+        : void 0;
 
       owner.stateNode._warnedAboutRefsInRender = true;
     }
@@ -4120,9 +4128,10 @@ var Callback = /*              */ 32;
 var DidCapture = /*            */ 64;
 var Ref = /*                   */ 128;
 var ErrLog = /*                */ 256;
+var Snapshot = /*              */ 2048;
 
 // Union of all host effects
-var HostEffectMask = /*        */ 511;
+var HostEffectMask = /*        */ 2559;
 
 var Incomplete = /*            */ 512;
 var ShouldCapture = /*         */ 1024;
@@ -4170,15 +4179,17 @@ function isMounted(component) {
     if (owner !== null && owner.tag === ClassComponent) {
       var ownerFiber = owner;
       var instance = ownerFiber.stateNode;
-      warning(
-        instance._warnedAboutRefsInRender,
-        "%s is accessing isMounted inside its render() function. " +
-          "render() should be a pure function of props and state. It should " +
-          "never access something that requires stale data from the previous " +
-          "render, such as refs. Move this logic to componentDidMount and " +
-          "componentDidUpdate instead.",
-        getComponentName(ownerFiber) || "A component"
-      );
+      !instance._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing isMounted inside its render() function. " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(ownerFiber) || "A component"
+          )
+        : void 0;
       instance._warnedAboutRefsInRender = true;
     }
   }
@@ -4731,6 +4742,47 @@ function createFiberFromPortal(portal, mode, expirationTime) {
   return fiber;
 }
 
+// Used for stashing WIP properties to replay failed work in DEV.
+function assignFiberPropertiesInDEV(target, source) {
+  if (target === null) {
+    // This Fiber's initial properties will always be overwritten.
+    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
+    target = createFiber(IndeterminateComponent, null, null, NoContext);
+  }
+
+  // This is intentionally written as a list of all properties.
+  // We tried to use Object.assign() instead but this is called in
+  // the hottest path, and Object.assign() was too slow:
+  // https://github.com/facebook/react/issues/12502
+  // This code is DEV-only so size is not a concern.
+
+  target.tag = source.tag;
+  target.key = source.key;
+  target.type = source.type;
+  target.stateNode = source.stateNode;
+  target["return"] = source["return"];
+  target.child = source.child;
+  target.sibling = source.sibling;
+  target.index = source.index;
+  target.ref = source.ref;
+  target.pendingProps = source.pendingProps;
+  target.memoizedProps = source.memoizedProps;
+  target.updateQueue = source.updateQueue;
+  target.memoizedState = source.memoizedState;
+  target.mode = source.mode;
+  target.effectTag = source.effectTag;
+  target.nextEffect = source.nextEffect;
+  target.firstEffect = source.firstEffect;
+  target.lastEffect = source.lastEffect;
+  target.expirationTime = source.expirationTime;
+  target.alternate = source.alternate;
+  target._debugID = source._debugID;
+  target._debugSource = source._debugSource;
+  target._debugOwner = source._debugOwner;
+  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
+  return target;
+}
+
 // TODO: This should be lifted into the renderer.
 
 function createFiberRoot(containerInfo, isAsync, hydrate) {
@@ -5136,7 +5188,10 @@ var ReactStrictModeWarnings = {
     ) {
       pendingComponentWillReceivePropsWarnings.push(fiber);
     }
-    if (typeof instance.componentWillUpdate === "function") {
+    if (
+      typeof instance.componentWillUpdate === "function" &&
+      instance.componentWillUpdate.__suppressDeprecationWarning !== true
+    ) {
       pendingComponentWillUpdateWarnings.push(fiber);
     }
   };
@@ -5481,13 +5536,15 @@ function startRequestCallbackTimer() {
   }
 }
 
-function stopRequestCallbackTimer(didExpire) {
+function stopRequestCallbackTimer(didExpire, expirationTime) {
   if (enableUserTimingAPI) {
     if (supportsUserTiming) {
       isWaitingForCallback = false;
       var warning$$1 = didExpire ? "React was blocked by main thread" : null;
       endMark(
-        "(Waiting for async callback...)",
+        "(Waiting for async callback... will force flush in " +
+          expirationTime +
+          " ms)",
         "(Waiting for async callback...)",
         warning$$1
       );
@@ -5597,7 +5654,7 @@ function startWorkLoopTimer(nextUnitOfWork) {
   }
 }
 
-function stopWorkLoopTimer(interruptedBy) {
+function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
   if (enableUserTimingAPI) {
     if (!supportsUserTiming) {
       return;
@@ -5615,13 +5672,12 @@ function stopWorkLoopTimer(interruptedBy) {
       warning$$1 = "There were cascading updates";
     }
     commitCountInCurrentWorkLoop = 0;
+    var label = didCompleteRoot
+      ? "(React Tree Reconciliation: Completed Root)"
+      : "(React Tree Reconciliation: Yielded)";
     // Pause any measurements until the next loop.
     pauseTimers();
-    endMark(
-      "(React Tree Reconciliation)",
-      "(React Tree Reconciliation)",
-      warning$$1
-    );
+    endMark(label, "(React Tree Reconciliation)", warning$$1);
   }
 }
 
@@ -5658,6 +5714,31 @@ function stopCommitTimer() {
   }
 }
 
+function startCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Snapshot Effects)");
+  }
+}
+
+function stopCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Snapshot Effects: " + count + " Total)",
+      "(Committing Snapshot Effects)",
+      null
+    );
+  }
+}
+
 function startCommitHostEffectsTimer() {
   if (enableUserTimingAPI) {
     if (!supportsUserTiming) {
@@ -6042,23 +6123,26 @@ var isArray = Array.isArray;
 var didWarnAboutStateAssignmentForComponent = void 0;
 var didWarnAboutUndefinedDerivedState = void 0;
 var didWarnAboutUninitializedState = void 0;
-var didWarnAboutWillReceivePropsAndDerivedState = void 0;
+var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
+var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
 var warnOnInvalidCallback = void 0;
 
 {
-  didWarnAboutStateAssignmentForComponent = {};
-  didWarnAboutUndefinedDerivedState = {};
-  didWarnAboutUninitializedState = {};
-  didWarnAboutWillReceivePropsAndDerivedState = {};
+  didWarnAboutStateAssignmentForComponent = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
+  didWarnAboutUninitializedState = new Set();
+  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
+  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
 
-  var didWarnOnInvalidCallback = {};
+  var didWarnOnInvalidCallback = new Set();
 
   warnOnInvalidCallback = function(callback, callerName) {
     if (callback === null || typeof callback === "function") {
       return;
     }
     var key = callerName + "_" + callback;
-    if (!didWarnOnInvalidCallback[key]) {
+    if (!didWarnOnInvalidCallback.has(key)) {
+      didWarnOnInvalidCallback.add(key);
       warning(
         false,
         "%s(...): Expected the last optional `callback` argument to be a " +
@@ -6066,7 +6150,6 @@ var warnOnInvalidCallback = void 0;
         callerName,
         callback
       );
-      didWarnOnInvalidCallback[key] = true;
     }
   };
 
@@ -6209,12 +6292,14 @@ var ReactFiberClassComponent = function(
       stopPhaseTimer();
 
       {
-        warning(
-          shouldUpdate !== undefined,
-          "%s.shouldComponentUpdate(): Returned undefined instead of a " +
-            "boolean value. Make sure to return true or false.",
-          getComponentName(workInProgress) || "Unknown"
-        );
+        !(shouldUpdate !== undefined)
+          ? warning(
+              false,
+              "%s.shouldComponentUpdate(): Returned undefined instead of a " +
+                "boolean value. Make sure to return true or false.",
+              getComponentName(workInProgress) || "Component"
+            )
+          : void 0;
       }
 
       return shouldUpdate;
@@ -6233,7 +6318,7 @@ var ReactFiberClassComponent = function(
     var instance = workInProgress.stateNode;
     var type = workInProgress.type;
     {
-      var name = getComponentName(workInProgress);
+      var name = getComponentName(workInProgress) || "Component";
       var renderPresent = instance.render;
 
       if (!renderPresent) {
@@ -6258,47 +6343,57 @@ var ReactFiberClassComponent = function(
         !instance.getInitialState ||
         instance.getInitialState.isReactClassApproved ||
         instance.state;
-      warning(
-        noGetInitialStateOnES6,
-        "getInitialState was defined on %s, a plain JavaScript class. " +
-          "This is only supported for classes created using React.createClass. " +
-          "Did you mean to define a state property instead?",
-        name
-      );
+      !noGetInitialStateOnES6
+        ? warning(
+            false,
+            "getInitialState was defined on %s, a plain JavaScript class. " +
+              "This is only supported for classes created using React.createClass. " +
+              "Did you mean to define a state property instead?",
+            name
+          )
+        : void 0;
       var noGetDefaultPropsOnES6 =
         !instance.getDefaultProps ||
         instance.getDefaultProps.isReactClassApproved;
-      warning(
-        noGetDefaultPropsOnES6,
-        "getDefaultProps was defined on %s, a plain JavaScript class. " +
-          "This is only supported for classes created using React.createClass. " +
-          "Use a static property to define defaultProps instead.",
-        name
-      );
+      !noGetDefaultPropsOnES6
+        ? warning(
+            false,
+            "getDefaultProps was defined on %s, a plain JavaScript class. " +
+              "This is only supported for classes created using React.createClass. " +
+              "Use a static property to define defaultProps instead.",
+            name
+          )
+        : void 0;
       var noInstancePropTypes = !instance.propTypes;
-      warning(
-        noInstancePropTypes,
-        "propTypes was defined as an instance property on %s. Use a static " +
-          "property to define propTypes instead.",
-        name
-      );
+      !noInstancePropTypes
+        ? warning(
+            false,
+            "propTypes was defined as an instance property on %s. Use a static " +
+              "property to define propTypes instead.",
+            name
+          )
+        : void 0;
       var noInstanceContextTypes = !instance.contextTypes;
-      warning(
-        noInstanceContextTypes,
-        "contextTypes was defined as an instance property on %s. Use a static " +
-          "property to define contextTypes instead.",
-        name
-      );
+      !noInstanceContextTypes
+        ? warning(
+            false,
+            "contextTypes was defined as an instance property on %s. Use a static " +
+              "property to define contextTypes instead.",
+            name
+          )
+        : void 0;
       var noComponentShouldUpdate =
         typeof instance.componentShouldUpdate !== "function";
-      warning(
-        noComponentShouldUpdate,
-        "%s has a method called " +
-          "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
-          "The name is phrased as a question because the function is " +
-          "expected to return a value.",
-        name
-      );
+      !noComponentShouldUpdate
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
+              "The name is phrased as a question because the function is " +
+              "expected to return a value.",
+            name
+          )
+        : void 0;
       if (
         type.prototype &&
         type.prototype.isPureReactComponent &&
@@ -6314,73 +6409,128 @@ var ReactFiberClassComponent = function(
       }
       var noComponentDidUnmount =
         typeof instance.componentDidUnmount !== "function";
-      warning(
-        noComponentDidUnmount,
-        "%s has a method called " +
-          "componentDidUnmount(). But there is no such lifecycle method. " +
-          "Did you mean componentWillUnmount()?",
-        name
-      );
+      !noComponentDidUnmount
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentDidUnmount(). But there is no such lifecycle method. " +
+              "Did you mean componentWillUnmount()?",
+            name
+          )
+        : void 0;
       var noComponentDidReceiveProps =
         typeof instance.componentDidReceiveProps !== "function";
-      warning(
-        noComponentDidReceiveProps,
-        "%s has a method called " +
-          "componentDidReceiveProps(). But there is no such lifecycle method. " +
-          "If you meant to update the state in response to changing props, " +
-          "use componentWillReceiveProps(). If you meant to fetch data or " +
-          "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
-        name
-      );
+      !noComponentDidReceiveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentDidReceiveProps(). But there is no such lifecycle method. " +
+              "If you meant to update the state in response to changing props, " +
+              "use componentWillReceiveProps(). If you meant to fetch data or " +
+              "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
+            name
+          )
+        : void 0;
       var noComponentWillRecieveProps =
         typeof instance.componentWillRecieveProps !== "function";
-      warning(
-        noComponentWillRecieveProps,
-        "%s has a method called " +
-          "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
-        name
-      );
+      !noComponentWillRecieveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
+            name
+          )
+        : void 0;
       var noUnsafeComponentWillRecieveProps =
         typeof instance.UNSAFE_componentWillRecieveProps !== "function";
-      warning(
-        noUnsafeComponentWillRecieveProps,
-        "%s has a method called " +
-          "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
-        name
-      );
+      !noUnsafeComponentWillRecieveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
+            name
+          )
+        : void 0;
       var hasMutatedProps = instance.props !== workInProgress.pendingProps;
-      warning(
-        instance.props === undefined || !hasMutatedProps,
-        "%s(...): When calling super() in `%s`, make sure to pass " +
-          "up the same props that your component's constructor was passed.",
-        name,
-        name
-      );
+      !(instance.props === undefined || !hasMutatedProps)
+        ? warning(
+            false,
+            "%s(...): When calling super() in `%s`, make sure to pass " +
+              "up the same props that your component's constructor was passed.",
+            name,
+            name
+          )
+        : void 0;
       var noInstanceDefaultProps = !instance.defaultProps;
-      warning(
-        noInstanceDefaultProps,
-        "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
-          " Instead, define defaultProps as a static property on %s.",
-        name,
-        name
-      );
-    }
+      !noInstanceDefaultProps
+        ? warning(
+            false,
+            "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
+              " Instead, define defaultProps as a static property on %s.",
+            name,
+            name
+          )
+        : void 0;
 
-    var state = instance.state;
-    if (state && (typeof state !== "object" || isArray(state))) {
-      warning(
-        false,
-        "%s.state: must be set to an object or null",
-        getComponentName(workInProgress)
-      );
-    }
-    if (typeof instance.getChildContext === "function") {
-      warning(
-        typeof type.childContextTypes === "object",
-        "%s.getChildContext(): childContextTypes must be defined in order to " +
-          "use getChildContext().",
-        getComponentName(workInProgress)
-      );
+      if (
+        typeof instance.getSnapshotBeforeUpdate === "function" &&
+        typeof instance.componentDidUpdate !== "function" &&
+        typeof instance.componentDidUpdate !== "function" &&
+        !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
+      ) {
+        didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
+        warning(
+          false,
+          "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
+            "This component defines getSnapshotBeforeUpdate() only.",
+          getComponentName(workInProgress)
+        );
+      }
+
+      var noInstanceGetDerivedStateFromProps =
+        typeof instance.getDerivedStateFromProps !== "function";
+      !noInstanceGetDerivedStateFromProps
+        ? warning(
+            false,
+            "%s: getDerivedStateFromProps() is defined as an instance method " +
+              "and will be ignored. Instead, declare it as a static method.",
+            name
+          )
+        : void 0;
+      var noInstanceGetDerivedStateFromCatch =
+        typeof instance.getDerivedStateFromCatch !== "function";
+      !noInstanceGetDerivedStateFromCatch
+        ? warning(
+            false,
+            "%s: getDerivedStateFromCatch() is defined as an instance method " +
+              "and will be ignored. Instead, declare it as a static method.",
+            name
+          )
+        : void 0;
+      var noStaticGetSnapshotBeforeUpdate =
+        typeof type.getSnapshotBeforeUpdate !== "function";
+      !noStaticGetSnapshotBeforeUpdate
+        ? warning(
+            false,
+            "%s: getSnapshotBeforeUpdate() is defined as a static method " +
+              "and will be ignored. Instead, declare it as an instance method.",
+            name
+          )
+        : void 0;
+      var _state = instance.state;
+      if (_state && (typeof _state !== "object" || isArray(_state))) {
+        warning(false, "%s.state: must be set to an object or null", name);
+      }
+      if (typeof instance.getChildContext === "function") {
+        !(typeof type.childContextTypes === "object")
+          ? warning(
+              false,
+              "%s.getChildContext(): childContextTypes must be defined in order to " +
+                "use getChildContext().",
+              name
+            )
+          : void 0;
+      }
     }
   }
 
@@ -6428,8 +6578,9 @@ var ReactFiberClassComponent = function(
         typeof ctor.getDerivedStateFromProps === "function" &&
         state === null
       ) {
-        var componentName = getComponentName(workInProgress) || "Unknown";
-        if (!didWarnAboutUninitializedState[componentName]) {
+        var componentName = getComponentName(workInProgress) || "Component";
+        if (!didWarnAboutUninitializedState.has(componentName)) {
+          didWarnAboutUninitializedState.add(componentName);
           warning(
             false,
             "%s: Did not properly initialize state during construction. " +
@@ -6437,7 +6588,75 @@ var ReactFiberClassComponent = function(
             componentName,
             instance.state === null ? "null" : "undefined"
           );
-          didWarnAboutUninitializedState[componentName] = true;
+        }
+      }
+
+      // If new component APIs are defined, "unsafe" lifecycles won't be called.
+      // Warn about these lifecycles if they are present.
+      // Don't warn about react-lifecycles-compat polyfilled methods though.
+      if (
+        typeof ctor.getDerivedStateFromProps === "function" ||
+        typeof instance.getSnapshotBeforeUpdate === "function"
+      ) {
+        var foundWillMountName = null;
+        var foundWillReceivePropsName = null;
+        var foundWillUpdateName = null;
+        if (
+          typeof instance.componentWillMount === "function" &&
+          instance.componentWillMount.__suppressDeprecationWarning !== true
+        ) {
+          foundWillMountName = "componentWillMount";
+        } else if (typeof instance.UNSAFE_componentWillMount === "function") {
+          foundWillMountName = "UNSAFE_componentWillMount";
+        }
+        if (
+          typeof instance.componentWillReceiveProps === "function" &&
+          instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+            true
+        ) {
+          foundWillReceivePropsName = "componentWillReceiveProps";
+        } else if (
+          typeof instance.UNSAFE_componentWillReceiveProps === "function"
+        ) {
+          foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
+        }
+        if (
+          typeof instance.componentWillUpdate === "function" &&
+          instance.componentWillUpdate.__suppressDeprecationWarning !== true
+        ) {
+          foundWillUpdateName = "componentWillUpdate";
+        } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+          foundWillUpdateName = "UNSAFE_componentWillUpdate";
+        }
+        if (
+          foundWillMountName !== null ||
+          foundWillReceivePropsName !== null ||
+          foundWillUpdateName !== null
+        ) {
+          var _componentName = getComponentName(workInProgress) || "Component";
+          var newApiName =
+            typeof ctor.getDerivedStateFromProps === "function"
+              ? "getDerivedStateFromProps()"
+              : "getSnapshotBeforeUpdate()";
+          if (
+            !didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)
+          ) {
+            didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
+            warning(
+              false,
+              "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
+                "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
+                "The above lifecycles should be removed. Learn more about this warning here:\n" +
+                "https://fb.me/react-async-component-lifecycle-hooks",
+              _componentName,
+              newApiName,
+              foundWillMountName !== null ? "\n  " + foundWillMountName : "",
+              foundWillReceivePropsName !== null
+                ? "\n  " + foundWillReceivePropsName
+                : "",
+              foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
+            );
+          }
         }
       }
     }
@@ -6447,7 +6666,8 @@ var ReactFiberClassComponent = function(
     var partialState = callGetDerivedStateFromProps(
       workInProgress,
       instance,
-      props
+      props,
+      state
     );
 
     if (partialState !== null && partialState !== undefined) {
@@ -6490,7 +6710,7 @@ var ReactFiberClassComponent = function(
           "%s.componentWillMount(): Assigning directly to this.state is " +
             "deprecated (except inside a component's " +
             "constructor). Use setState instead.",
-          getComponentName(workInProgress)
+          getComponentName(workInProgress) || "Component"
         );
       }
       updater.enqueueReplaceState(instance, instance.state, null);
@@ -6516,7 +6736,8 @@ var ReactFiberClassComponent = function(
     if (instance.state !== oldState) {
       {
         var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutStateAssignmentForComponent[componentName]) {
+        if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
+          didWarnAboutStateAssignmentForComponent.add(componentName);
           warning(
             false,
             "%s.componentWillReceiveProps(): Assigning directly to " +
@@ -6524,69 +6745,47 @@ var ReactFiberClassComponent = function(
               "constructor). Use setState instead.",
             componentName
           );
-          didWarnAboutStateAssignmentForComponent[componentName] = true;
         }
       }
       updater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
-  function callGetDerivedStateFromProps(workInProgress, instance, props) {
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
     var type = workInProgress.type;
 
     if (typeof type.getDerivedStateFromProps === "function") {
-      {
-        // Don't warn about react-lifecycles-compat polyfilled components
-        if (
-          (typeof instance.componentWillReceiveProps === "function" &&
-            instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-              true) ||
-          typeof instance.UNSAFE_componentWillReceiveProps === "function"
-        ) {
-          var componentName = getComponentName(workInProgress) || "Unknown";
-          if (!didWarnAboutWillReceivePropsAndDerivedState[componentName]) {
-            warning(
-              false,
-              "%s: Defines both componentWillReceiveProps() and static " +
-                "getDerivedStateFromProps() methods. We recommend using " +
-                "only getDerivedStateFromProps().",
-              componentName
-            );
-            didWarnAboutWillReceivePropsAndDerivedState[componentName] = true;
-          }
-        }
-      }
-
       if (
         debugRenderPhaseSideEffects ||
         (debugRenderPhaseSideEffectsForStrictMode &&
           workInProgress.mode & StrictMode)
       ) {
         // Invoke method an extra time to help detect side-effects.
-        type.getDerivedStateFromProps.call(
-          null,
-          props,
-          workInProgress.memoizedState
-        );
+        type.getDerivedStateFromProps.call(null, nextProps, prevState);
       }
 
       var partialState = type.getDerivedStateFromProps.call(
         null,
-        props,
-        workInProgress.memoizedState
+        nextProps,
+        prevState
       );
 
       {
         if (partialState === undefined) {
-          var _componentName = getComponentName(workInProgress) || "Unknown";
-          if (!didWarnAboutUndefinedDerivedState[_componentName]) {
+          var componentName = getComponentName(workInProgress) || "Component";
+          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+            didWarnAboutUndefinedDerivedState.add(componentName);
             warning(
               false,
               "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
                 "You have returned undefined.",
-              _componentName
+              componentName
             );
-            didWarnAboutUndefinedDerivedState[_componentName] = _componentName;
           }
         }
       }
@@ -6630,11 +6829,12 @@ var ReactFiberClassComponent = function(
     }
 
     // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
+      typeof ctor.getDerivedStateFromProps !== "function" &&
+      typeof instance.getSnapshotBeforeUpdate !== "function" &&
       (typeof instance.UNSAFE_componentWillMount === "function" ||
-        typeof instance.componentWillMount === "function") &&
-      typeof ctor.getDerivedStateFromProps !== "function"
+        typeof instance.componentWillMount === "function")
     ) {
       callComponentWillMount(workInProgress, instance);
       // If we had additional state updates during this life-cycle, let's
@@ -6667,16 +6867,20 @@ var ReactFiberClassComponent = function(
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var hasNewLifecycles =
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function";
+
     // Note: During these life-cycles, instance.props/instance.state are what
     // ever the previously attempted to render - not the "current". However,
     // during componentDidUpdate we pass the "current" props.
 
     // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
+      !hasNewLifecycles &&
       (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function") &&
-      typeof ctor.getDerivedStateFromProps !== "function"
+        typeof instance.componentWillReceiveProps === "function")
     ) {
       if (oldProps !== newProps || oldContext !== newContext) {
         callComponentWillReceiveProps(
@@ -6688,15 +6892,6 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
-        instance,
-        newProps
-      );
-    }
-
     // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
     // TODO: Previous state can be null.
@@ -6733,6 +6928,18 @@ var ReactFiberClassComponent = function(
       newState = oldState;
     }
 
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
+        workInProgress,
+        instance,
+        newProps,
+        newState
+      );
+    }
+
     if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
       // Render-phase updates (like this) should not be added to the update queue,
       // So that multiple render passes do not enqueue multiple updates.
@@ -6741,6 +6948,17 @@ var ReactFiberClassComponent = function(
         newState === null || newState === undefined
           ? derivedStateFromProps
           : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue = workInProgress.updateQueue;
+      if (_updateQueue !== null) {
+        _updateQueue.baseState = Object.assign(
+          {},
+          _updateQueue.baseState,
+          derivedStateFromProps
+        );
+      }
     }
     if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
       // Render-phase updates (like this) should not be added to the update queue,
@@ -6750,6 +6968,17 @@ var ReactFiberClassComponent = function(
         newState === null || newState === undefined
           ? derivedStateFromCatch
           : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue2 = workInProgress.updateQueue;
+      if (_updateQueue2 !== null) {
+        _updateQueue2.baseState = Object.assign(
+          {},
+          _updateQueue2.baseState,
+          derivedStateFromCatch
+        );
+      }
     }
 
     if (
@@ -6780,11 +7009,11 @@ var ReactFiberClassComponent = function(
 
     if (shouldUpdate) {
       // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+      // Unsafe lifecycles should not be invoked for components using the new APIs.
       if (
+        !hasNewLifecycles &&
         (typeof instance.UNSAFE_componentWillMount === "function" ||
-          typeof instance.componentWillMount === "function") &&
-        typeof ctor.getDerivedStateFromProps !== "function"
+          typeof instance.componentWillMount === "function")
       ) {
         startPhaseTimer(workInProgress, "componentWillMount");
         if (typeof instance.componentWillMount === "function") {
@@ -6832,16 +7061,20 @@ var ReactFiberClassComponent = function(
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var hasNewLifecycles =
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function";
+
     // Note: During these life-cycles, instance.props/instance.state are what
     // ever the previously attempted to render - not the "current". However,
     // during componentDidUpdate we pass the "current" props.
 
     // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
+      !hasNewLifecycles &&
       (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function") &&
-      typeof ctor.getDerivedStateFromProps !== "function"
+        typeof instance.componentWillReceiveProps === "function")
     ) {
       if (oldProps !== newProps || oldContext !== newContext) {
         callComponentWillReceiveProps(
@@ -6853,20 +7086,12 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
-        instance,
-        newProps
-      );
-    }
-
     // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
     // TODO: Previous state can be null.
     var newState = void 0;
     var derivedStateFromCatch = void 0;
+
     if (workInProgress.updateQueue !== null) {
       newState = processUpdateQueue(
         current,
@@ -6898,6 +7123,18 @@ var ReactFiberClassComponent = function(
       newState = oldState;
     }
 
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
+        workInProgress,
+        instance,
+        newProps,
+        newState
+      );
+    }
+
     if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
       // Render-phase updates (like this) should not be added to the update queue,
       // So that multiple render passes do not enqueue multiple updates.
@@ -6906,6 +7143,17 @@ var ReactFiberClassComponent = function(
         newState === null || newState === undefined
           ? derivedStateFromProps
           : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue3 = workInProgress.updateQueue;
+      if (_updateQueue3 !== null) {
+        _updateQueue3.baseState = Object.assign(
+          {},
+          _updateQueue3.baseState,
+          derivedStateFromProps
+        );
+      }
     }
     if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
       // Render-phase updates (like this) should not be added to the update queue,
@@ -6915,6 +7163,17 @@ var ReactFiberClassComponent = function(
         newState === null || newState === undefined
           ? derivedStateFromCatch
           : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue4 = workInProgress.updateQueue;
+      if (_updateQueue4 !== null) {
+        _updateQueue4.baseState = Object.assign(
+          {},
+          _updateQueue4.baseState,
+          derivedStateFromCatch
+        );
+      }
     }
 
     if (
@@ -6936,6 +7195,14 @@ var ReactFiberClassComponent = function(
           workInProgress.effectTag |= Update;
         }
       }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Snapshot;
+        }
+      }
       return false;
     }
 
@@ -6950,11 +7217,11 @@ var ReactFiberClassComponent = function(
 
     if (shouldUpdate) {
       // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for any component with the new gDSFP.
+      // Unsafe lifecycles should not be invoked for components using the new APIs.
       if (
+        !hasNewLifecycles &&
         (typeof instance.UNSAFE_componentWillUpdate === "function" ||
-          typeof instance.componentWillUpdate === "function") &&
-        typeof ctor.getDerivedStateFromProps !== "function"
+          typeof instance.componentWillUpdate === "function")
       ) {
         startPhaseTimer(workInProgress, "componentWillUpdate");
         if (typeof instance.componentWillUpdate === "function") {
@@ -6968,6 +7235,9 @@ var ReactFiberClassComponent = function(
       if (typeof instance.componentDidUpdate === "function") {
         workInProgress.effectTag |= Update;
       }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        workInProgress.effectTag |= Snapshot;
+      }
     } else {
       // If an update was already in progress, we should schedule an Update
       // effect even though we're bailing out, so that cWU/cDU are called.
@@ -6979,6 +7249,14 @@ var ReactFiberClassComponent = function(
           workInProgress.effectTag |= Update;
         }
       }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Snapshot;
+        }
+      }
 
       // If shouldComponentUpdate returned false, we should still update the
       // memoized props/state to indicate that this work can be reused.
@@ -7818,13 +8096,15 @@ function ChildReconciler(shouldTrackSideEffects) {
       if (typeof newChildrenIterable.entries === "function") {
         var possibleMap = newChildrenIterable;
         if (possibleMap.entries === iteratorFn) {
-          warning(
-            didWarnAboutMaps,
-            "Using Maps as children is unsupported and will likely yield " +
-              "unexpected results. Convert it to a sequence/iterable of keyed " +
-              "ReactElements instead.%s",
-            getCurrentFiberStackAddendum$1()
-          );
+          !didWarnAboutMaps
+            ? warning(
+                false,
+                "Using Maps as children is unsupported and will likely yield " +
+                  "unexpected results. Convert it to a sequence/iterable of keyed " +
+                  "ReactElements instead.%s",
+                getCurrentFiberStackAddendum$1()
+              )
+            : void 0;
           didWarnAboutMaps = true;
         }
       }
@@ -8790,7 +9070,8 @@ var ReactFiberBeginWork = function(
         var partialState = callGetDerivedStateFromProps(
           workInProgress,
           value,
-          props
+          props,
+          workInProgress.memoizedState
         );
 
         if (partialState !== null && partialState !== undefined) {
@@ -8823,11 +9104,13 @@ var ReactFiberBeginWork = function(
         var _Component = workInProgress.type;
 
         if (_Component) {
-          warning(
-            !_Component.childContextTypes,
-            "%s(...): childContextTypes cannot be defined on a functional component.",
-            _Component.displayName || _Component.name || "Component"
-          );
+          !!_Component.childContextTypes
+            ? warning(
+                false,
+                "%s(...): childContextTypes cannot be defined on a functional component.",
+                _Component.displayName || _Component.name || "Component"
+              )
+            : void 0;
         }
         if (workInProgress.ref !== null) {
           var info = "";
@@ -9046,7 +9329,7 @@ var ReactFiberBeginWork = function(
     renderExpirationTime
   ) {
     var providerType = workInProgress.type;
-    var context = providerType.context;
+    var context = providerType._context;
 
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
@@ -9099,12 +9382,14 @@ var ReactFiberBeginWork = function(
               ? context._calculateChangedBits(oldValue, newValue)
               : MAX_SIGNED_31_BIT_INT;
           {
-            warning(
-              (changedBits & MAX_SIGNED_31_BIT_INT) === changedBits,
-              "calculateChangedBits: Expected the return value to be a " +
-                "31-bit integer. Instead received: %s",
-              changedBits
-            );
+            !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
+              ? warning(
+                  false,
+                  "calculateChangedBits: Expected the return value to be a " +
+                    "31-bit integer. Instead received: %s",
+                  changedBits
+                )
+              : void 0;
           }
           changedBits |= 0;
 
@@ -9172,21 +9457,23 @@ var ReactFiberBeginWork = function(
         changedBits,
         renderExpirationTime
       );
-    } else if (oldProps !== null && oldProps.children === newProps.children) {
-      // No change. Bailout early if children are the same.
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
+    // There is no bailout on `children` equality because we expect people
+    // to often pass a bound method as a child, but it may reference
+    // `this.state` or `this.props` (and thus needs to re-render on `setState`).
 
     var render = newProps.children;
 
     {
-      warning(
-        typeof render === "function",
-        "A context consumer was rendered with multiple children, or a child " +
-          "that isn't a function. A context consumer expects a single child " +
-          "that is a function. If you did pass a function, make sure there " +
-          "is no trailing or leading whitespace around it."
-      );
+      !(typeof render === "function")
+        ? warning(
+            false,
+            "A context consumer was rendered with multiple children, or a child " +
+              "that isn't a function. A context consumer expects a single child " +
+              "that is a function. If you did pass a function, make sure there " +
+              "is no trailing or leading whitespace around it."
+          )
+        : void 0;
     }
 
     var newChildren = render(newValue);
@@ -10175,6 +10462,11 @@ var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
 var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
 var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
 
+var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
+{
+  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
+}
+
 function logError(boundary, errorInfo) {
   var source = errorInfo.source;
   var stack = errorInfo.stack;
@@ -10184,21 +10476,19 @@ function logError(boundary, errorInfo) {
 
   var capturedError = {
     componentName: source !== null ? getComponentName(source) : null,
-    error: errorInfo.value,
-    errorBoundary: boundary,
     componentStack: stack !== null ? stack : "",
+    error: errorInfo.value,
+    errorBoundary: null,
     errorBoundaryName: null,
     errorBoundaryFound: false,
     willRetry: false
   };
 
-  if (boundary !== null) {
+  if (boundary !== null && boundary.tag === ClassComponent) {
+    capturedError.errorBoundary = boundary.stateNode;
     capturedError.errorBoundaryName = getComponentName(boundary);
-    capturedError.errorBoundaryFound = capturedError.willRetry =
-      boundary.tag === ClassComponent;
-  } else {
-    capturedError.errorBoundaryName = null;
-    capturedError.errorBoundaryFound = capturedError.willRetry = false;
+    capturedError.errorBoundaryFound = true;
+    capturedError.willRetry = true;
   }
 
   try {
@@ -10267,6 +10557,58 @@ var ReactFiberCommitWork = function(
     }
   }
 
+  function commitBeforeMutationLifeCycles(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        if (finishedWork.effectTag & Snapshot) {
+          if (current !== null) {
+            var prevProps = current.memoizedProps;
+            var prevState = current.memoizedState;
+            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
+            var _instance = finishedWork.stateNode;
+            _instance.props = finishedWork.memoizedProps;
+            _instance.state = finishedWork.memoizedState;
+            var snapshot = _instance.getSnapshotBeforeUpdate(
+              prevProps,
+              prevState
+            );
+            {
+              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
+              if (
+                snapshot === undefined &&
+                !didWarnSet.has(finishedWork.type)
+              ) {
+                didWarnSet.add(finishedWork.type);
+                warning(
+                  false,
+                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
+                    "must be returned. You have returned undefined.",
+                  getComponentName(finishedWork)
+                );
+              }
+            }
+            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+            stopPhaseTimer();
+          }
+        }
+        return;
+      }
+      case HostRoot:
+      case HostComponent:
+      case HostText:
+      case HostPortal:
+        // Nothing to do for these component types
+        return;
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
   function commitLifeCycles(
     finishedRoot,
     current,
@@ -10276,50 +10618,54 @@ var ReactFiberCommitWork = function(
   ) {
     switch (finishedWork.tag) {
       case ClassComponent: {
-        var _instance = finishedWork.stateNode;
+        var _instance2 = finishedWork.stateNode;
         if (finishedWork.effectTag & Update) {
           if (current === null) {
             startPhaseTimer(finishedWork, "componentDidMount");
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            _instance.componentDidMount();
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidMount();
             stopPhaseTimer();
           } else {
             var prevProps = current.memoizedProps;
             var prevState = current.memoizedState;
             startPhaseTimer(finishedWork, "componentDidUpdate");
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            _instance.componentDidUpdate(prevProps, prevState);
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidUpdate(
+              prevProps,
+              prevState,
+              _instance2.__reactInternalSnapshotBeforeUpdate
+            );
             stopPhaseTimer();
           }
         }
         var updateQueue = finishedWork.updateQueue;
         if (updateQueue !== null) {
-          commitCallbacks(updateQueue, _instance);
+          commitCallbacks(updateQueue, _instance2);
         }
         return;
       }
       case HostRoot: {
         var _updateQueue = finishedWork.updateQueue;
         if (_updateQueue !== null) {
-          var _instance2 = null;
+          var _instance3 = null;
           if (finishedWork.child !== null) {
             switch (finishedWork.child.tag) {
               case HostComponent:
-                _instance2 = getPublicInstance(finishedWork.child.stateNode);
+                _instance3 = getPublicInstance(finishedWork.child.stateNode);
                 break;
               case ClassComponent:
-                _instance2 = finishedWork.child.stateNode;
+                _instance3 = finishedWork.child.stateNode;
                 break;
             }
           }
-          commitCallbacks(_updateQueue, _instance2);
+          commitCallbacks(_updateQueue, _instance3);
         }
         return;
       }
       case HostComponent: {
-        var _instance3 = finishedWork.stateNode;
+        var _instance4 = finishedWork.stateNode;
 
         // Renderers may schedule work to be done after host components are mounted
         // (eg DOM renderer may schedule auto-focus for inputs and form controls).
@@ -10328,7 +10674,7 @@ var ReactFiberCommitWork = function(
         if (current === null && finishedWork.effectTag & Update) {
           var type = finishedWork.type;
           var props = finishedWork.memoizedProps;
-          commitMount(_instance3, type, props, finishedWork);
+          commitMount(_instance4, type, props, finishedWork);
         }
 
         return;
@@ -10356,7 +10702,7 @@ var ReactFiberCommitWork = function(
       case ClassComponent:
         {
           var ctor = finishedWork.type;
-          var _instance4 = finishedWork.stateNode;
+          var _instance5 = finishedWork.stateNode;
           var updateQueue = finishedWork.updateQueue;
           invariant(
             updateQueue !== null && updateQueue.capturedValues !== null,
@@ -10373,16 +10719,19 @@ var ReactFiberCommitWork = function(
             // This gets reset before we yield back to the browser.
             // TODO: Warn in strict mode if getDerivedStateFromCatch is
             // not defined.
-            markLegacyErrorBoundaryAsFailed(_instance4);
+            markLegacyErrorBoundaryAsFailed(_instance5);
           }
 
-          _instance4.props = finishedWork.memoizedProps;
-          _instance4.state = finishedWork.memoizedState;
+          _instance5.props = finishedWork.memoizedProps;
+          _instance5.state = finishedWork.memoizedState;
           for (var i = 0; i < capturedErrors.length; i++) {
             var errorInfo = capturedErrors[i];
             var _error = errorInfo.value;
+            var stack = errorInfo.stack;
             logError(finishedWork, errorInfo);
-            _instance4.componentDidCatch(_error);
+            _instance5.componentDidCatch(_error, {
+              componentStack: stack !== null ? stack : ""
+            });
           }
         }
         break;
@@ -10415,14 +10764,14 @@ var ReactFiberCommitWork = function(
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (ref !== null) {
-      var _instance5 = finishedWork.stateNode;
+      var _instance6 = finishedWork.stateNode;
       var instanceToUse = void 0;
       switch (finishedWork.tag) {
         case HostComponent:
-          instanceToUse = getPublicInstance(_instance5);
+          instanceToUse = getPublicInstance(_instance6);
           break;
         default:
-          instanceToUse = _instance5;
+          instanceToUse = _instance6;
       }
       if (typeof ref === "function") {
         ref(instanceToUse);
@@ -10466,9 +10815,9 @@ var ReactFiberCommitWork = function(
     switch (current.tag) {
       case ClassComponent: {
         safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if (typeof _instance6.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance6);
+        var _instance7 = current.stateNode;
+        if (typeof _instance7.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance7);
         }
         return;
       }
@@ -10605,6 +10954,7 @@ var ReactFiberCommitWork = function(
         },
 
         commitLifeCycles: commitLifeCycles,
+        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
         commitErrorLogging: commitErrorLogging,
         commitAttachRef: commitAttachRef,
         commitDetachRef: commitDetachRef
@@ -10863,8 +11213,8 @@ var ReactFiberCommitWork = function(
         return;
       }
       case HostComponent: {
-        var _instance7 = finishedWork.stateNode;
-        if (_instance7 != null) {
+        var _instance8 = finishedWork.stateNode;
+        if (_instance8 != null) {
           // Commit the work prepared earlier.
           var newProps = finishedWork.memoizedProps;
           // For hydration we reuse the update path but we treat the oldProps
@@ -10877,7 +11227,7 @@ var ReactFiberCommitWork = function(
           finishedWork.updateQueue = null;
           if (updatePayload !== null) {
             commitUpdate(
-              _instance7,
+              _instance8,
               updatePayload,
               type,
               oldProps,
@@ -10922,6 +11272,7 @@ var ReactFiberCommitWork = function(
 
   if (enableMutatingReconciler) {
     return {
+      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
       commitResetTextContent: commitResetTextContent,
       commitPlacement: commitPlacement,
       commitDeletion: commitDeletion,
@@ -10967,12 +11318,19 @@ var ReactFiberHostContext = function(config, stack) {
     // Push current root instance onto the stack;
     // This allows us to reset root when portals are popped.
     push(rootInstanceStackCursor, nextRootInstance, fiber);
-
-    var nextRootContext = getRootHostContext(nextRootInstance);
-
     // Track the context and the Fiber that provided it.
     // This enables us to pop only Fibers that provide unique contexts.
     push(contextFiberStackCursor, fiber, fiber);
+
+    // Finally, we need to push the host context to the stack.
+    // However, we can't just call getRootHostContext() and push it because
+    // we'd have a different number of entries on the stack depending on
+    // whether getRootHostContext() throws somewhere in renderer code or not.
+    // So we push an empty value first. This lets us safely unwind on errors.
+    push(contextStackCursor, NO_CONTEXT, fiber);
+    var nextRootContext = getRootHostContext(nextRootInstance);
+    // Now that we know this function doesn't throw, replace it.
+    pop(contextStackCursor, fiber);
     push(contextStackCursor, nextRootContext, fiber);
   }
 
@@ -11683,7 +12041,7 @@ var ReactFiberNewContext = function(stack) {
   }
 
   function pushProvider(providerFiber) {
-    var context = providerFiber.type.context;
+    var context = providerFiber.type._context;
 
     push(changedBitsCursor, context._changedBits, providerFiber);
     push(valueCursor, context._currentValue, providerFiber);
@@ -11693,12 +12051,16 @@ var ReactFiberNewContext = function(stack) {
     context._changedBits = providerFiber.stateNode;
 
     {
-      warning(
+      !(
         context._currentRenderer === null ||
-          context._currentRenderer === rendererSigil,
-        "Detected multiple renderers concurrently rendering the " +
-          "same context provider. This is currently unsupported."
-      );
+        context._currentRenderer === rendererSigil
+      )
+        ? warning(
+            false,
+            "Detected multiple renderers concurrently rendering the " +
+              "same context provider. This is currently unsupported."
+          )
+        : void 0;
       context._currentRenderer = rendererSigil;
     }
   }
@@ -11711,7 +12073,7 @@ var ReactFiberNewContext = function(stack) {
     pop(valueCursor, providerFiber);
     pop(changedBitsCursor, providerFiber);
 
-    var context = providerFiber.type.context;
+    var context = providerFiber.type._context;
     context._currentValue = currentValue;
     context._changedBits = changedBits;
   }
@@ -11824,17 +12186,19 @@ var warnAboutInvalidUpdates = void 0;
   var didWarnStateUpdateForUnmountedComponent = {};
 
   warnAboutUpdateOnUnmounted = function(fiber) {
+    // We show the whole stack but dedupe on the top component's name because
+    // the problematic code almost always lies inside that component.
     var componentName = getComponentName(fiber) || "ReactClass";
     if (didWarnStateUpdateForUnmountedComponent[componentName]) {
       return;
     }
     warning(
       false,
-      "Can only update a mounted or mounting " +
-        "component. This usually means you called setState, replaceState, " +
-        "or forceUpdate on an unmounted component. This is a no-op.\n\nPlease " +
-        "check the code for the %s component.",
-      componentName
+      "Can't call setState (or forceUpdate) on an unmounted component. This " +
+        "is a no-op, but it indicates a memory leak in your application. To " +
+        "fix, cancel all subscriptions and asynchronous tasks in the " +
+        "componentWillUnmount method.%s",
+      getStackAddendumByWorkInProgressFiber(fiber)
     );
     didWarnStateUpdateForUnmountedComponent[componentName] = true;
   };
@@ -11920,6 +12284,8 @@ var ReactFiberScheduler = function(config) {
       markLegacyErrorBoundaryAsFailed,
       recalculateCurrentTime
     ),
+    commitBeforeMutationLifeCycles =
+      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
     commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
     commitPlacement = _ReactFiberCommitWork.commitPlacement,
     commitDeletion = _ReactFiberCommitWork.commitDeletion,
@@ -11971,11 +12337,19 @@ var ReactFiberScheduler = function(config) {
 
   var stashedWorkInProgressProperties = void 0;
   var replayUnitOfWork = void 0;
+  var isReplayingFailedUnitOfWork = void 0;
+  var originalReplayError = void 0;
+  var rethrowOriginalError = void 0;
   if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
     stashedWorkInProgressProperties = null;
-    replayUnitOfWork = function(failedUnitOfWork, isAsync) {
-      // Retore the original state of the work-in-progress
-      Object.assign(failedUnitOfWork, stashedWorkInProgressProperties);
+    isReplayingFailedUnitOfWork = false;
+    originalReplayError = null;
+    replayUnitOfWork = function(failedUnitOfWork, error, isAsync) {
+      // Restore the original state of the work-in-progress
+      assignFiberPropertiesInDEV(
+        failedUnitOfWork,
+        stashedWorkInProgressProperties
+      );
       switch (failedUnitOfWork.tag) {
         case HostRoot:
           popHostContainer(failedUnitOfWork);
@@ -11995,14 +12369,22 @@ var ReactFiberScheduler = function(config) {
           break;
       }
       // Replay the begin phase.
+      isReplayingFailedUnitOfWork = true;
+      originalReplayError = error;
       invokeGuardedCallback$2(null, workLoop, null, isAsync);
+      isReplayingFailedUnitOfWork = false;
+      originalReplayError = null;
       if (hasCaughtError()) {
         clearCaughtError();
       } else {
-        // This should be unreachable because the render phase is
-        // idempotent
+        // If the begin phase did not fail the second time, set this pointer
+        // back to the original value.
+        nextUnitOfWork = failedUnitOfWork;
       }
     };
+    rethrowOriginalError = function() {
+      throw originalReplayError;
+    };
   }
 
   function resetStack() {
@@ -12034,6 +12416,7 @@ var ReactFiberScheduler = function(config) {
       recordEffect();
 
       var effectTag = nextEffect.effectTag;
+
       if (effectTag & ContentReset) {
         commitResetTextContent(nextEffect);
       }
@@ -12091,6 +12474,22 @@ var ReactFiberScheduler = function(config) {
     }
   }
 
+  function commitBeforeMutationLifecycles() {
+    while (nextEffect !== null) {
+      var effectTag = nextEffect.effectTag;
+
+      if (effectTag & Snapshot) {
+        recordEffect();
+        var current = nextEffect.alternate;
+        commitBeforeMutationLifeCycles(current, nextEffect);
+      }
+
+      // Don't cleanup effects yet;
+      // This will be done by commitAllLifeCycles()
+      nextEffect = nextEffect.nextEffect;
+    }
+  }
+
   function commitAllLifeCycles(
     finishedRoot,
     currentTime,
@@ -12198,16 +12597,14 @@ var ReactFiberScheduler = function(config) {
 
     prepareForCommit(root.containerInfo);
 
-    // Commit all the side-effects within a tree. We'll do this in two passes.
-    // The first pass performs all the host insertions, updates, deletions and
-    // ref unmounts.
+    // Invoke instances of getSnapshotBeforeUpdate before mutation.
     nextEffect = firstEffect;
-    startCommitHostEffectsTimer();
+    startCommitSnapshotEffectsTimer();
     while (nextEffect !== null) {
       var didError = false;
       var error = void 0;
       {
-        invokeGuardedCallback$2(null, commitAllHostEffects, null);
+        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
         if (hasCaughtError()) {
           didError = true;
           error = clearCaughtError();
@@ -12226,6 +12623,36 @@ var ReactFiberScheduler = function(config) {
         }
       }
     }
+    stopCommitSnapshotEffectsTimer();
+
+    // Commit all the side-effects within a tree. We'll do this in two passes.
+    // The first pass performs all the host insertions, updates, deletions and
+    // ref unmounts.
+    nextEffect = firstEffect;
+    startCommitHostEffectsTimer();
+    while (nextEffect !== null) {
+      var _didError = false;
+      var _error = void 0;
+      {
+        invokeGuardedCallback$2(null, commitAllHostEffects, null);
+        if (hasCaughtError()) {
+          _didError = true;
+          _error = clearCaughtError();
+        }
+      }
+      if (_didError) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, _error);
+        // Clean-up
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
     stopCommitHostEffectsTimer();
 
     resetAfterCommit(root.containerInfo);
@@ -12243,8 +12670,8 @@ var ReactFiberScheduler = function(config) {
     nextEffect = firstEffect;
     startCommitLifeCyclesTimer();
     while (nextEffect !== null) {
-      var _didError = false;
-      var _error = void 0;
+      var _didError2 = false;
+      var _error2 = void 0;
       {
         invokeGuardedCallback$2(
           null,
@@ -12255,17 +12682,17 @@ var ReactFiberScheduler = function(config) {
           committedExpirationTime
         );
         if (hasCaughtError()) {
-          _didError = true;
-          _error = clearCaughtError();
+          _didError2 = true;
+          _error2 = clearCaughtError();
         }
       }
-      if (_didError) {
+      if (_didError2) {
         invariant(
           nextEffect !== null,
           "Should have next effect. This error is likely caused by a bug " +
             "in React. Please file an issue."
         );
-        onCommitPhaseError(nextEffect, _error);
+        onCommitPhaseError(nextEffect, _error2);
         if (nextEffect !== null) {
           nextEffect = nextEffect.nextEffect;
         }
@@ -12489,12 +12916,21 @@ var ReactFiberScheduler = function(config) {
     }
 
     if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-      stashedWorkInProgressProperties = Object.assign({}, workInProgress);
+      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
+        stashedWorkInProgressProperties,
+        workInProgress
+      );
     }
     var next = beginWork(current, workInProgress, nextRenderExpirationTime);
-
     {
       ReactDebugCurrentFiber.resetCurrentFiber();
+      if (isReplayingFailedUnitOfWork) {
+        // Currently replaying a failed unit of work. This should be unreachable,
+        // because the render phase is meant to be idempotent, and it should
+        // have thrown again. Since it didn't, rethrow the original error, so
+        // React's internal stack is not misaligned.
+        rethrowOriginalError();
+      }
     }
     if (true && ReactFiberInstrumentation_1.debugTool) {
       ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
@@ -12568,13 +13004,18 @@ var ReactFiberScheduler = function(config) {
 
         if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
-          replayUnitOfWork(failedUnitOfWork, isAsync);
+          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
         }
 
         var sourceFiber = nextUnitOfWork;
         var returnFiber = sourceFiber["return"];
         if (returnFiber === null) {
-          // This is a fatal error.
+          // This is the root. The root could capture its own errors. However,
+          // we don't know if it errors before or after we pushed the host
+          // context. This information is needed to avoid a stack mismatch.
+          // Because we're not sure, treat this as a fatal error. We could track
+          // which phase it fails in, but doesn't seem worth it. At least
+          // for now.
           didFatal = true;
           onUncaughtError(thrownValue);
           break;
@@ -12586,12 +13027,13 @@ var ReactFiberScheduler = function(config) {
     } while (true);
 
     // We're done performing work. Time to clean up.
-    stopWorkLoopTimer(interruptedBy);
-    interruptedBy = null;
+    var didCompleteRoot = false;
     isWorking = false;
 
     // Yield back to main thread.
     if (didFatal) {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
       // There was a fatal error.
       {
         stack.resetStackAfterFatalErrorInDev();
@@ -12600,12 +13042,17 @@ var ReactFiberScheduler = function(config) {
     } else if (nextUnitOfWork === null) {
       // We reached the root.
       if (isRootReadyForCommit) {
+        didCompleteRoot = true;
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
         // The root successfully completed. It's ready for commit.
         root.pendingCommitExpirationTime = expirationTime;
         var finishedWork = root.current.alternate;
         return finishedWork;
       } else {
         // The root did not complete.
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
         invariant(
           false,
           "Expired work should have completed. This error is likely caused " +
@@ -12613,6 +13060,8 @@ var ReactFiberScheduler = function(config) {
         );
       }
     } else {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
       // There's more work to do, but we ran out of time. Yield back to
       // the renderer.
       return null;
@@ -12798,7 +13247,15 @@ var ReactFiberScheduler = function(config) {
             interruptedBy = fiber;
             resetStack();
           }
-          if (nextRoot !== root || !isWorking) {
+          if (
+            // If we're in the render phase, we don't need to schedule this root
+            // for an update, because we'll do it before we exit...
+            !isWorking ||
+            isCommitting ||
+            // ...unless this is a different root than the one we're rendering.
+            nextRoot !== root
+          ) {
+            // Add this root to the root schedule.
             requestWork(root, expirationTime);
           }
           if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
@@ -13058,7 +13515,8 @@ var ReactFiberScheduler = function(config) {
 
     if (enableUserTimingAPI && deadline !== null) {
       var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
-      stopRequestCallbackTimer(didExpire);
+      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
+      stopRequestCallbackTimer(didExpire, timeout);
     }
 
     if (isAsync) {
@@ -13118,7 +13576,11 @@ var ReactFiberScheduler = function(config) {
     // Perform work on root as if the given expiration time is the current time.
     // This has the effect of synchronously flushing all work up to and
     // including the given time.
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
     performWorkOnRoot(root, expirationTime, false);
+    // Flush any sync work that was scheduled by lifecycles
+    performSyncWork();
     finishRendering();
   }
 
@@ -13445,12 +13907,14 @@ var ReactFiberReconciler$1 = function(config) {
 
     callback = callback === undefined ? null : callback;
     {
-      warning(
-        callback === null || typeof callback === "function",
-        "render(...): Expected the last optional `callback` argument to be a " +
-          "function. Instead received: %s.",
-        callback
-      );
+      !(callback === null || typeof callback === "function")
+        ? warning(
+            false,
+            "render(...): Expected the last optional `callback` argument to be a " +
+              "function. Instead received: %s.",
+            callback
+          )
+        : void 0;
     }
 
     var update = {
@@ -13772,7 +14236,8 @@ var frameDeadline = 0;
 var frameDeadlineObject = {
   timeRemaining: function() {
     return frameDeadline - now();
-  }
+  },
+  didTimeout: false
 };
 
 function setTimeoutCallback() {
diff --git a/Libraries/Renderer/ReactNativeRenderer-prod.js b/Libraries/Renderer/ReactNativeRenderer-prod.js
index f11aa6c82da4..055ddd7bb0c1 100644
--- a/Libraries/Renderer/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/ReactNativeRenderer-prod.js
@@ -2246,23 +2246,20 @@ function ReactFiberClassComponent(
     instance.state !== workInProgress &&
       updater.enqueueReplaceState(instance, instance.state, null);
   }
-  function callGetDerivedStateFromProps(workInProgress, instance, props) {
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
     instance = workInProgress.type;
     if ("function" === typeof instance.getDerivedStateFromProps)
       return (
         (debugRenderPhaseSideEffects ||
           (debugRenderPhaseSideEffectsForStrictMode &&
             workInProgress.mode & 2)) &&
-          instance.getDerivedStateFromProps.call(
-            null,
-            props,
-            workInProgress.memoizedState
-          ),
-        instance.getDerivedStateFromProps.call(
-          null,
-          props,
-          workInProgress.memoizedState
-        )
+          instance.getDerivedStateFromProps.call(null, nextProps, prevState),
+        instance.getDerivedStateFromProps.call(null, nextProps, prevState)
       );
   }
   var cacheContext = legacyContext.cacheContext,
@@ -2337,7 +2334,7 @@ function ReactFiberClassComponent(
         null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
       adoptClassInstance(workInProgress, ctor);
       workInProgress.memoizedState = state;
-      props = callGetDerivedStateFromProps(workInProgress, ctor, props);
+      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
       null !== props &&
         void 0 !== props &&
         (workInProgress.memoizedState = Object.assign(
@@ -2358,9 +2355,10 @@ function ReactFiberClassComponent(
       instance.state = workInProgress.memoizedState;
       instance.refs = emptyObject;
       instance.context = getMaskedContext(workInProgress, unmaskedContext);
-      ("function" !== typeof instance.UNSAFE_componentWillMount &&
-        "function" !== typeof instance.componentWillMount) ||
-        "function" === typeof ctor.getDerivedStateFromProps ||
+      "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate ||
+        ("function" !== typeof instance.UNSAFE_componentWillMount &&
+          "function" !== typeof instance.componentWillMount) ||
         ((ctor = instance.state),
         "function" === typeof instance.componentWillMount &&
           instance.componentWillMount(),
@@ -2391,9 +2389,12 @@ function ReactFiberClassComponent(
         oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-        "function" !== typeof instance.componentWillReceiveProps) ||
+      var hasNewLifecycles =
         "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate;
+      hasNewLifecycles ||
+        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
+          "function" !== typeof instance.componentWillReceiveProps) ||
         ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
           callComponentWillReceiveProps(
             workInProgress,
@@ -2401,15 +2402,8 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      oldContext = void 0;
-      oldProps !== newProps &&
-        (oldContext = callGetDerivedStateFromProps(
-          workInProgress,
-          instance,
-          newProps
-        ));
-      var oldState = workInProgress.memoizedState,
-        derivedStateFromCatch = void 0;
+      oldContext = workInProgress.memoizedState;
+      var derivedStateFromCatch = void 0;
       if (null !== workInProgress.updateQueue) {
         renderExpirationTime = processUpdateQueue(
           null,
@@ -2428,23 +2422,45 @@ function ReactFiberClassComponent(
             ctor,
             updateQueue.capturedValues
           ));
-      } else renderExpirationTime = oldState;
-      null !== oldContext &&
-        void 0 !== oldContext &&
-        (renderExpirationTime =
+      } else renderExpirationTime = oldContext;
+      ctor = void 0;
+      oldProps !== newProps &&
+        (ctor = callGetDerivedStateFromProps(
+          workInProgress,
+          instance,
+          newProps,
+          renderExpirationTime
+        ));
+      null !== ctor &&
+        void 0 !== ctor &&
+        ((renderExpirationTime =
           null === renderExpirationTime || void 0 === renderExpirationTime
-            ? oldContext
-            : Object.assign({}, renderExpirationTime, oldContext));
+            ? ctor
+            : Object.assign({}, renderExpirationTime, ctor)),
+        (updateQueue = workInProgress.updateQueue),
+        null !== updateQueue &&
+          (updateQueue.baseState = Object.assign(
+            {},
+            updateQueue.baseState,
+            ctor
+          )));
       null !== derivedStateFromCatch &&
         void 0 !== derivedStateFromCatch &&
-        (renderExpirationTime =
+        ((renderExpirationTime =
           null === renderExpirationTime || void 0 === renderExpirationTime
             ? derivedStateFromCatch
-            : Object.assign({}, renderExpirationTime, derivedStateFromCatch));
+            : Object.assign({}, renderExpirationTime, derivedStateFromCatch)),
+        (ctor = workInProgress.updateQueue),
+        null !== ctor &&
+          (ctor.baseState = Object.assign(
+            {},
+            ctor.baseState,
+            derivedStateFromCatch
+          )));
       if (
         !(
           oldProps !== newProps ||
-          oldState !== renderExpirationTime ||
+          oldContext !== renderExpirationTime ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2459,13 +2475,13 @@ function ReactFiberClassComponent(
         workInProgress,
         oldProps,
         newProps,
-        oldState,
+        oldContext,
         renderExpirationTime,
         newUnmaskedContext
       ))
-        ? (("function" !== typeof instance.UNSAFE_componentWillMount &&
-            "function" !== typeof instance.componentWillMount) ||
-            "function" === typeof ctor.getDerivedStateFromProps ||
+        ? (hasNewLifecycles ||
+            ("function" !== typeof instance.UNSAFE_componentWillMount &&
+              "function" !== typeof instance.componentWillMount) ||
             ("function" === typeof instance.componentWillMount &&
               instance.componentWillMount(),
             "function" === typeof instance.UNSAFE_componentWillMount &&
@@ -2495,9 +2511,12 @@ function ReactFiberClassComponent(
         oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-        "function" !== typeof instance.componentWillReceiveProps) ||
+      var hasNewLifecycles =
         "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate;
+      hasNewLifecycles ||
+        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
+          "function" !== typeof instance.componentWillReceiveProps) ||
         ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
           callComponentWillReceiveProps(
             workInProgress,
@@ -2505,13 +2524,6 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
-          workInProgress,
-          instance,
-          newProps
-        ));
       oldContext = workInProgress.memoizedState;
       var derivedStateFromCatch = void 0;
       if (null !== workInProgress.updateQueue) {
@@ -2533,18 +2545,40 @@ function ReactFiberClassComponent(
             updateQueue.capturedValues
           ));
       } else renderExpirationTime = oldContext;
-      null !== derivedStateFromProps &&
-        void 0 !== derivedStateFromProps &&
-        (renderExpirationTime =
+      ctor = void 0;
+      oldProps !== newProps &&
+        (ctor = callGetDerivedStateFromProps(
+          workInProgress,
+          instance,
+          newProps,
+          renderExpirationTime
+        ));
+      null !== ctor &&
+        void 0 !== ctor &&
+        ((renderExpirationTime =
           null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps));
+            ? ctor
+            : Object.assign({}, renderExpirationTime, ctor)),
+        (updateQueue = workInProgress.updateQueue),
+        null !== updateQueue &&
+          (updateQueue.baseState = Object.assign(
+            {},
+            updateQueue.baseState,
+            ctor
+          )));
       null !== derivedStateFromCatch &&
         void 0 !== derivedStateFromCatch &&
-        (renderExpirationTime =
+        ((renderExpirationTime =
           null === renderExpirationTime || void 0 === renderExpirationTime
             ? derivedStateFromCatch
-            : Object.assign({}, renderExpirationTime, derivedStateFromCatch));
+            : Object.assign({}, renderExpirationTime, derivedStateFromCatch)),
+        (ctor = workInProgress.updateQueue),
+        null !== ctor &&
+          (ctor.baseState = Object.assign(
+            {},
+            ctor.baseState,
+            derivedStateFromCatch
+          )));
       if (
         !(
           oldProps !== newProps ||
@@ -2559,9 +2593,13 @@ function ReactFiberClassComponent(
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
             (workInProgress.effectTag |= 4),
+          "function" !== typeof instance.getSnapshotBeforeUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 2048),
           !1
         );
-      (derivedStateFromProps = checkShouldComponentUpdate(
+      (derivedStateFromCatch = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
@@ -2569,9 +2607,9 @@ function ReactFiberClassComponent(
         renderExpirationTime,
         newUnmaskedContext
       ))
-        ? (("function" !== typeof instance.UNSAFE_componentWillUpdate &&
-            "function" !== typeof instance.componentWillUpdate) ||
-            "function" === typeof ctor.getDerivedStateFromProps ||
+        ? (hasNewLifecycles ||
+            ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
+              "function" !== typeof instance.componentWillUpdate) ||
             ("function" === typeof instance.componentWillUpdate &&
               instance.componentWillUpdate(
                 newProps,
@@ -2585,17 +2623,23 @@ function ReactFiberClassComponent(
                 newUnmaskedContext
               )),
           "function" === typeof instance.componentDidUpdate &&
-            (workInProgress.effectTag |= 4))
+            (workInProgress.effectTag |= 4),
+          "function" === typeof instance.getSnapshotBeforeUpdate &&
+            (workInProgress.effectTag |= 2048))
         : ("function" !== typeof instance.componentDidUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
             (workInProgress.effectTag |= 4),
+          "function" !== typeof instance.getSnapshotBeforeUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 2048),
           memoizeProps(workInProgress, newProps),
           memoizeState(workInProgress, renderExpirationTime));
       instance.props = newProps;
       instance.state = renderExpirationTime;
       instance.context = newUnmaskedContext;
-      return derivedStateFromProps;
+      return derivedStateFromCatch;
     }
   };
 }
@@ -3444,7 +3488,7 @@ function ReactFiberBeginWork(
     workInProgress,
     renderExpirationTime
   ) {
-    var context = workInProgress.type.context,
+    var context = workInProgress.type._context,
       newProps = workInProgress.pendingProps,
       oldProps = workInProgress.memoizedProps;
     if (!hasLegacyContextChanged() && oldProps === newProps)
@@ -3610,7 +3654,8 @@ function ReactFiberBeginWork(
                 ((props = callGetDerivedStateFromProps(
                   workInProgress,
                   fn,
-                  props
+                  props,
+                  workInProgress.memoizedState
                 )),
                 null !== props &&
                   void 0 !== props &&
@@ -3881,43 +3926,33 @@ function ReactFiberBeginWork(
             renderExpirationTime
           );
         case 12:
-          a: {
-            fn = workInProgress.type;
-            unmaskedContext = workInProgress.pendingProps;
-            updateQueue = workInProgress.memoizedProps;
-            props = fn._currentValue;
-            var changedBits = fn._changedBits;
-            if (
-              hasLegacyContextChanged() ||
-              0 !== changedBits ||
-              updateQueue !== unmaskedContext
-            ) {
-              workInProgress.memoizedProps = unmaskedContext;
-              var observedBits = unmaskedContext.unstable_observedBits;
-              if (void 0 === observedBits || null === observedBits)
-                observedBits = 1073741823;
-              workInProgress.stateNode = observedBits;
-              if (0 !== (changedBits & observedBits))
-                propagateContextChange(
-                  workInProgress,
-                  fn,
-                  changedBits,
-                  renderExpirationTime
-                );
-              else if (
-                null !== updateQueue &&
-                updateQueue.children === unmaskedContext.children
-              ) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-              renderExpirationTime = unmaskedContext.children;
-              renderExpirationTime = renderExpirationTime(props);
-              reconcileChildren(current, workInProgress, renderExpirationTime);
-              current = workInProgress.child;
-            } else
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
+          fn = workInProgress.type;
+          unmaskedContext = workInProgress.pendingProps;
+          var oldProps = workInProgress.memoizedProps;
+          props = fn._currentValue;
+          updateQueue = fn._changedBits;
+          if (
+            hasLegacyContextChanged() ||
+            0 !== updateQueue ||
+            oldProps !== unmaskedContext
+          ) {
+            workInProgress.memoizedProps = unmaskedContext;
+            oldProps = unmaskedContext.unstable_observedBits;
+            if (void 0 === oldProps || null === oldProps) oldProps = 1073741823;
+            workInProgress.stateNode = oldProps;
+            0 !== (updateQueue & oldProps) &&
+              propagateContextChange(
+                workInProgress,
+                fn,
+                updateQueue,
+                renderExpirationTime
+              );
+            renderExpirationTime = unmaskedContext.children;
+            renderExpirationTime = renderExpirationTime(props);
+            reconcileChildren(current, workInProgress, renderExpirationTime);
+            current = workInProgress.child;
+          } else
+            current = bailoutOnAlreadyFinishedWork(current, workInProgress);
           return current;
         default:
           invariant(
@@ -4313,9 +4348,9 @@ function logError(boundary, errorInfo) {
     stack = errorInfo.stack;
   null === stack && (stack = getStackAddendumByWorkInProgressFiber(source));
   null !== source && getComponentName(source);
+  source = null !== stack ? stack : "";
   errorInfo = errorInfo.value;
-  stack = null !== stack ? stack : "";
-  null !== boundary && getComponentName(boundary);
+  null !== boundary && 2 === boundary.tag && getComponentName(boundary);
   try {
     if (errorInfo instanceof Error) {
       var message = errorInfo.message,
@@ -4325,13 +4360,13 @@ function logError(boundary, errorInfo) {
         errorToHandle.message =
           (message ? name + ": " + message : name) +
           "\n\nThis error is located at:" +
-          stack;
+          source;
       } catch (e) {}
     } else
       errorToHandle =
         "string" === typeof errorInfo
-          ? Error(errorInfo + "\n\nThis error is located at:" + stack)
-          : Error("Unspecified error at:" + stack);
+          ? Error(errorInfo + "\n\nThis error is located at:" + source)
+          : Error("Unspecified error at:" + source);
     ExceptionsManager.handleException(errorToHandle, !1);
   } catch (e) {
     (e && e.suppressReactErrorLogging) || console.error(e);
@@ -4360,12 +4395,12 @@ function ReactFiberCommitWork(
     switch (current.tag) {
       case 2:
         safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if ("function" === typeof _instance6.componentWillUnmount)
+        var _instance7 = current.stateNode;
+        if ("function" === typeof _instance7.componentWillUnmount)
           try {
-            (_instance6.props = current.memoizedProps),
-              (_instance6.state = current.memoizedState),
-              _instance6.componentWillUnmount();
+            (_instance7.props = current.memoizedProps),
+              (_instance7.state = current.memoizedState),
+              _instance7.componentWillUnmount();
           } catch (unmountError) {
             captureError(current, unmountError);
           }
@@ -4475,6 +4510,34 @@ function ReactFiberCommitWork(
     removeChild = mutation.removeChild,
     removeChildFromContainer = mutation.removeChildFromContainer;
   return {
+    commitBeforeMutationLifeCycles: function(current, finishedWork) {
+      switch (finishedWork.tag) {
+        case 2:
+          if (finishedWork.effectTag & 2048 && null !== current) {
+            var prevProps = current.memoizedProps,
+              prevState = current.memoizedState;
+            current = finishedWork.stateNode;
+            current.props = finishedWork.memoizedProps;
+            current.state = finishedWork.memoizedState;
+            finishedWork = current.getSnapshotBeforeUpdate(
+              prevProps,
+              prevState
+            );
+            current.__reactInternalSnapshotBeforeUpdate = finishedWork;
+          }
+          break;
+        case 3:
+        case 5:
+        case 6:
+        case 4:
+          break;
+        default:
+          invariant(
+            !1,
+            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    },
     commitResetTextContent: function(current) {
       resetTextContent(current.stateNode);
     },
@@ -4580,8 +4643,8 @@ function ReactFiberCommitWork(
         case 2:
           break;
         case 5:
-          var _instance7 = finishedWork.stateNode;
-          if (null != _instance7) {
+          var _instance8 = finishedWork.stateNode;
+          if (null != _instance8) {
             var newProps = finishedWork.memoizedProps;
             current = null !== current ? current.memoizedProps : newProps;
             var type = finishedWork.type,
@@ -4589,7 +4652,7 @@ function ReactFiberCommitWork(
             finishedWork.updateQueue = null;
             null !== updatePayload &&
               commitUpdate(
-                _instance7,
+                _instance8,
                 updatePayload,
                 type,
                 current,
@@ -4603,11 +4666,11 @@ function ReactFiberCommitWork(
             null !== finishedWork.stateNode,
             "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
           );
-          _instance7 = finishedWork.memoizedProps;
+          _instance8 = finishedWork.memoizedProps;
           commitTextUpdate(
             finishedWork.stateNode,
-            null !== current ? current.memoizedProps : _instance7,
-            _instance7
+            null !== current ? current.memoizedProps : _instance8,
+            _instance8
           );
           break;
         case 3:
@@ -4633,7 +4696,11 @@ function ReactFiberCommitWork(
               current = current.memoizedState;
               finishedRoot.props = finishedWork.memoizedProps;
               finishedRoot.state = finishedWork.memoizedState;
-              finishedRoot.componentDidUpdate(prevProps, current);
+              finishedRoot.componentDidUpdate(
+                prevProps,
+                current,
+                finishedRoot.__reactInternalSnapshotBeforeUpdate
+              );
             }
           finishedWork = finishedWork.updateQueue;
           null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
@@ -4695,9 +4762,12 @@ function ReactFiberCommitWork(
           onUncaughtError.state = finishedWork.memoizedState;
           for (ctor = 0; ctor < capturedErrors.length; ctor++) {
             updateQueue = capturedErrors[ctor];
-            var _error = updateQueue.value;
+            var _error = updateQueue.value,
+              stack = updateQueue.stack;
             logError(finishedWork, updateQueue);
-            onUncaughtError.componentDidCatch(_error);
+            onUncaughtError.componentDidCatch(_error, {
+              componentStack: null !== stack ? stack : ""
+            });
           }
           break;
         case 3:
@@ -4723,13 +4793,13 @@ function ReactFiberCommitWork(
     commitAttachRef: function(finishedWork) {
       var ref = finishedWork.ref;
       if (null !== ref) {
-        var _instance5 = finishedWork.stateNode;
+        var _instance6 = finishedWork.stateNode;
         switch (finishedWork.tag) {
           case 5:
-            finishedWork = getPublicInstance(_instance5);
+            finishedWork = getPublicInstance(_instance6);
             break;
           default:
-            finishedWork = _instance5;
+            finishedWork = _instance6;
         }
         "function" === typeof ref
           ? ref(finishedWork)
@@ -4780,8 +4850,10 @@ function ReactFiberHostContext(config, stack) {
     },
     pushHostContainer: function(fiber, nextRootInstance) {
       push(rootInstanceStackCursor, nextRootInstance, fiber);
-      nextRootInstance = getRootHostContext(nextRootInstance);
       push(contextFiberStackCursor, fiber, fiber);
+      push(contextStackCursor, NO_CONTEXT, fiber);
+      nextRootInstance = getRootHostContext(nextRootInstance);
+      pop(contextStackCursor, fiber);
       push(contextStackCursor, nextRootInstance, fiber);
     },
     pushHostContext: function(fiber) {
@@ -5088,7 +5160,7 @@ function ReactFiberNewContext(stack) {
     changedBitsCursor = createCursor(0);
   return {
     pushProvider: function(providerFiber) {
-      var context = providerFiber.type.context;
+      var context = providerFiber.type._context;
       push(changedBitsCursor, context._changedBits, providerFiber);
       push(valueCursor, context._currentValue, providerFiber);
       push(providerCursor, providerFiber, providerFiber);
@@ -5101,7 +5173,7 @@ function ReactFiberNewContext(stack) {
       pop(providerCursor, providerFiber);
       pop(valueCursor, providerFiber);
       pop(changedBitsCursor, providerFiber);
-      providerFiber = providerFiber.type.context;
+      providerFiber = providerFiber.type._context;
       providerFiber._currentValue = currentValue;
       providerFiber._changedBits = changedBits;
     }
@@ -5214,7 +5286,7 @@ function ReactFiberScheduler(config) {
         workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
         if (null !== workInProgress$jscomp$0)
           return (
-            (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
+            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
           );
         null !== returnFiber &&
           ((returnFiber.firstEffect = returnFiber.lastEffect = null),
@@ -5378,7 +5450,7 @@ function ReactFiberScheduler(config) {
               0 !== nextRenderExpirationTime &&
               expirationTime < nextRenderExpirationTime &&
               resetStack();
-            (nextRoot === root && isWorking) ||
+            (isWorking && !isCommitting && nextRoot === root) ||
               requestWork(root, expirationTime);
             nestedUpdateCount > NESTED_UPDATE_LIMIT &&
               invariant(
@@ -5442,7 +5514,7 @@ function ReactFiberScheduler(config) {
           (nextFlushedExpirationTime = 1),
           performWorkOnRoot(root, 1, !1))
         : 1 === expirationTime
-          ? performWork(1, !1, null)
+          ? performSyncWork()
           : scheduleCallbackWithExpiration(expirationTime));
   }
   function findHighestPriorityRoot() {
@@ -5502,6 +5574,9 @@ function ReactFiberScheduler(config) {
   function performAsyncWork(dl) {
     performWork(0, !0, dl);
   }
+  function performSyncWork() {
+    performWork(1, !1, null);
+  }
   function performWork(minExpirationTime, isAsync, dl) {
     deadline = dl;
     findHighestPriorityRoot();
@@ -5624,6 +5699,25 @@ function ReactFiberScheduler(config) {
     for (nextEffect = firstEffect; null !== nextEffect; ) {
       var didError = !1,
         error = void 0;
+      try {
+        for (; null !== nextEffect; )
+          nextEffect.effectTag & 2048 &&
+            commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
+            (nextEffect = nextEffect.nextEffect);
+      } catch (e) {
+        (didError = !0), (error = e);
+      }
+      didError &&
+        (invariant(
+          null !== nextEffect,
+          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        onCommitPhaseError(nextEffect, error),
+        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    }
+    for (nextEffect = firstEffect; null !== nextEffect; ) {
+      didError = !1;
+      error = void 0;
       try {
         for (; null !== nextEffect; ) {
           var effectTag = nextEffect.effectTag;
@@ -5764,7 +5858,9 @@ function ReactFiberScheduler(config) {
     },
     recalculateCurrentTime
   );
-  var commitResetTextContent = hostContext.commitResetTextContent,
+  var commitBeforeMutationLifeCycles =
+      hostContext.commitBeforeMutationLifeCycles,
+    commitResetTextContent = hostContext.commitResetTextContent,
     commitPlacement = hostContext.commitPlacement,
     commitDeletion = hostContext.commitDeletion,
     commitWork = hostContext.commitWork,
@@ -5819,7 +5915,10 @@ function ReactFiberScheduler(config) {
         !isRendering,
         "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
       );
+      nextFlushedRoot = root;
+      nextFlushedExpirationTime = expirationTime;
       performWorkOnRoot(root, expirationTime, !1);
+      performSyncWork();
       finishRendering();
     },
     batchedUpdates: function(fn, a) {
@@ -5830,7 +5929,7 @@ function ReactFiberScheduler(config) {
       } finally {
         (isBatchingUpdates = previousIsBatchingUpdates) ||
           isRendering ||
-          performWork(1, !1, null);
+          performSyncWork();
       }
     },
     unbatchedUpdates: function(fn, a) {
@@ -5854,8 +5953,7 @@ function ReactFiberScheduler(config) {
       try {
         return syncUpdates(fn, a);
       } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates),
-          performWork(1, !1, null);
+        (isBatchingUpdates = previousIsBatchingUpdates), performSyncWork();
       }
     },
     flushControlled: function(fn) {
@@ -5896,7 +5994,7 @@ function ReactFiberScheduler(config) {
         (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
           (isBatchingUpdates = previousIsBatchingUpdates) ||
             isRendering ||
-            performWork(1, !1, null);
+            performSyncWork();
       }
     },
     flushInteractiveUpdates: function() {
@@ -6128,7 +6226,8 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
   frameDeadlineObject = {
     timeRemaining: function() {
       return frameDeadline - now();
-    }
+    },
+    didTimeout: !1
   };
 function setTimeoutCallback() {
   frameDeadline = now() + 5;
@@ -6462,7 +6561,7 @@ NativeRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
-  version: "16.3.0-alpha.2",
+  version: "16.3.1",
   rendererPackageName: "react-native-renderer"
 });
 var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
diff --git a/Libraries/Renderer/shims/ReactFabric.js b/Libraries/Renderer/shims/ReactFabric.js
index 6ab336bf11f0..4162ca62fef7 100644
--- a/Libraries/Renderer/shims/ReactFabric.js
+++ b/Libraries/Renderer/shims/ReactFabric.js
@@ -25,4 +25,3 @@ if (__DEV__) {
 BatchedBridge.registerCallableModule('ReactFabric', ReactFabric);
 
 module.exports = (ReactFabric: ReactNativeType);
-
diff --git a/Libraries/Renderer/shims/ReactTypes.js b/Libraries/Renderer/shims/ReactTypes.js
index f6a56ccc96ed..689ed18bf952 100644
--- a/Libraries/Renderer/shims/ReactTypes.js
+++ b/Libraries/Renderer/shims/ReactTypes.js
@@ -62,7 +62,7 @@ export type ReactProvider<T> = {
 
 export type ReactProviderType<T> = {
   $$typeof: Symbol | number,
-  context: ReactContext<T>,
+  _context: ReactContext<T>,
 };
 
 export type ReactConsumer<T> = {
@@ -72,7 +72,7 @@ export type ReactConsumer<T> = {
   ref: null,
   props: {
     children: (value: T) => ReactNodeList,
-    bits?: number,
+    unstable_observedBits?: number,
   },
 };
 
diff --git a/package.json b/package.json
index d15a462f15e1..4f4f55845110 100644
--- a/package.json
+++ b/package.json
@@ -142,7 +142,7 @@
     "react-native": "local-cli/wrong-react-native.js"
   },
   "peerDependencies": {
-    "react": "^16.3.0-alpha.2"
+    "react": "16.3.1"
   },
   "dependencies": {
     "absolute-path": "^0.0.0",
@@ -219,8 +219,8 @@
     "jest": "23.0.0-alpha.4",
     "jest-junit": "3.6.0",
     "prettier": "1.9.1",
-    "react": "^16.3.0-alpha.2",
-    "react-test-renderer": "^16.3.0-alpha.2",
+    "react": "16.3.1",
+    "react-test-renderer": "16.3.1",
     "shelljs": "^0.7.8",
     "sinon": "^2.2.0"
   }

From 490f22ae72ba43fa9364ce0f6c238744c07ac830 Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Wed, 4 Apr 2018 16:43:37 -0700
Subject: [PATCH 0207/1109] Fix bug with <InputAccessoryView> safe area
 conformance

Reviewed By: wwalser

Differential Revision: D7507732

fbshipit-source-id: 10bf8d58c65f1353a3e62a27fc74c2dfd73ac2c4
---
 Libraries/Text/TextInput/RCTInputAccessoryViewContent.m | 9 ++-------
 1 file changed, 2 insertions(+), 7 deletions(-)

diff --git a/Libraries/Text/TextInput/RCTInputAccessoryViewContent.m b/Libraries/Text/TextInput/RCTInputAccessoryViewContent.m
index 73ec648ad8e1..5a9f142c6108 100644
--- a/Libraries/Text/TextInput/RCTInputAccessoryViewContent.m
+++ b/Libraries/Text/TextInput/RCTInputAccessoryViewContent.m
@@ -27,18 +27,13 @@ - (void)didMoveToSuperview
 {
 
 #if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
-  // Avoid the home pill (in portrait mode) and notch (in landscape mode) on iPhoneX.
+  // Avoid the home pill (in portrait mode)
+  // TODO: Support rotation, anchor to left and right without breaking frame x coordinate (T27974328).
   if (@available(iOS 11.0, *)) {
     if (self.window) {
       [_safeAreaContainer.bottomAnchor
        constraintLessThanOrEqualToSystemSpacingBelowAnchor:self.window.safeAreaLayoutGuide.bottomAnchor
        multiplier:1.0f].active = YES;
-      [_safeAreaContainer.leftAnchor
-       constraintGreaterThanOrEqualToSystemSpacingAfterAnchor:self.window.safeAreaLayoutGuide.leftAnchor
-       multiplier:1.0f].active = YES;
-      [_safeAreaContainer.rightAnchor
-       constraintLessThanOrEqualToSystemSpacingAfterAnchor:self.window.safeAreaLayoutGuide.rightAnchor
-       multiplier:1.0f].active = YES;
     }
   }
 #endif

From 3ed076b65a79cf8438d99d2e031013d8859eec33 Mon Sep 17 00:00:00 2001
From: philvasseur <pvass153@gmail.com>
Date: Wed, 4 Apr 2018 20:33:11 -0700
Subject: [PATCH 0208/1109] added in snapAlignment for horizontal android
 scrollView

Summary:
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->
`snapToAlignment` is available on iOS but not android yet. This PR is to add support for `snapToAlignment` on android as `snapToInterval` was recently added to android and they are very useful together.

Make a `Flatlist` in android with `pagingEnabled`, `horizontal`, `snapToInterval` and `snapToAlignment` set and see how adjusting between the three values of `snapToAlignment` aligns just like it does in iOS.

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [MINOR] [ScrollView] - On Android, **ScrollView** now takes snapToAlignment like iOS

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18648

Differential Revision: D7473762

Pulled By: mdvacca

fbshipit-source-id: ad4778b83f9fd1352455b2ed28a5f37229d9d8c7
---
 .../scroll/ReactHorizontalScrollView.java     | 21 ++++++++++++++++++-
 .../ReactHorizontalScrollViewManager.java     |  5 +++++
 2 files changed, 25 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
index 90b9d1fc4d3a..fe4762ac4a2f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
@@ -52,6 +52,7 @@ public class ReactHorizontalScrollView extends HorizontalScrollView implements
   private @Nullable Drawable mEndBackground;
   private int mEndFillColor = Color.TRANSPARENT;
   private int mSnapInterval = 0;
+  private String mSnapAlignment = "start";
   private ReactViewBackgroundManager mReactBackgroundManager;
 
   public ReactHorizontalScrollView(Context context) {
@@ -96,6 +97,13 @@ public void setPagingEnabled(boolean pagingEnabled) {
 
   public void setSnapInterval(int snapInterval) {
     mSnapInterval = snapInterval;
+    if(snapInterval != 0) {
+      mPagingEnabled = true;
+    }
+  }
+
+  public void setSnapAlignment(String snapAlignment) {
+    mSnapAlignment = snapAlignment;
   }
 
   public void flashScrollIndicators() {
@@ -236,6 +244,17 @@ private int getSnapInterval() {
     return getWidth();
   }
 
+  private int getAlignmentOffset() {
+    int width = getWidth();
+    int snapInterval = getSnapInterval();
+    if (mSnapAlignment.equals("center")) {
+      return (width - snapInterval)/2;
+    } else if(mSnapAlignment.equals("end")) {
+      return (width - snapInterval);
+    }
+    return 0;
+  }
+
   public void setEndFillColor(int color) {
     if (color != mEndFillColor) {
       mEndFillColor = color;
@@ -349,7 +368,7 @@ private void smoothScrollToPage(int velocity) {
     if (predictedX > page * width + width / 2) {
       page = page + 1;
     }
-    smoothScrollTo(page * width, getScrollY());
+    smoothScrollTo(page * width - getAlignmentOffset(), getScrollY());
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
index e6536a6e53eb..d5fe728c3098 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
@@ -80,6 +80,11 @@ public void setSnapToInterval(ReactHorizontalScrollView view, float snapToInterv
     view.setSnapInterval((int) (snapToInterval * screenDisplayMetrics.density));
   }
 
+  @ReactProp(name = "snapToAlignment")
+  public void setSnapToAlignment(ReactHorizontalScrollView view, String snapToAlignment) {
+    view.setSnapAlignment(snapToAlignment);
+  }
+
   @ReactProp(name = ReactClippingViewGroupHelper.PROP_REMOVE_CLIPPED_SUBVIEWS)
   public void setRemoveClippedSubviews(ReactHorizontalScrollView view, boolean removeClippedSubviews) {
     view.setRemoveClippedSubviews(removeClippedSubviews);

From 4a814d1370329ac75a6fb0924c73c48b3d3754fb Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 5 Apr 2018 06:14:51 -0700
Subject: [PATCH 0209/1109] Change ES6 module syntax to module.exports

Reviewed By: rubennorte

Differential Revision: D7490562

fbshipit-source-id: 861681c24eab678d25af47bb25738651fe3e26b4
---
 Libraries/Components/View/ViewContext.js | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/View/ViewContext.js b/Libraries/Components/View/ViewContext.js
index 563d2b253b93..f9f98000409d 100644
--- a/Libraries/Components/View/ViewContext.js
+++ b/Libraries/Components/View/ViewContext.js
@@ -16,6 +16,8 @@ export type ViewChildContext = {|
   +isInAParentText: boolean,
 |};
 
-export const ViewContextTypes = {
-  isInAParentText: PropTypes.bool,
+module.exports = {
+  ViewContextTypes: {
+    isInAParentText: PropTypes.bool,
+  },
 };

From cea798c57b4a46d7819cfc417278c764b2486a45 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 5 Apr 2018 06:14:52 -0700
Subject: [PATCH 0210/1109] Downgrade ES6 import to ES5 compat module.exports

Reviewed By: rubennorte

Differential Revision: D7498658

fbshipit-source-id: 6825c3010ce13c56f05284448ad9961fe058d7ea
---
 Libraries/Network/fetch.js              | 2 +-
 Libraries/StyleSheet/StyleSheetTypes.js | 2 +-
 bots/dangerfile.js                      | 2 +-
 3 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/Libraries/Network/fetch.js b/Libraries/Network/fetch.js
index 5a0de646c912..1e1c934316d6 100644
--- a/Libraries/Network/fetch.js
+++ b/Libraries/Network/fetch.js
@@ -12,7 +12,7 @@
 
 'use strict';
 
-import whatwg from 'whatwg-fetch';
+const whatwg = require('whatwg-fetch');
 
 if (whatwg && whatwg.fetch) {
   module.exports = whatwg;
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index 6ff412ce8a67..1e359e8b515c 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -11,7 +11,7 @@
 
 'use strict';
 
-import AnimatedNode from 'AnimatedNode';
+const AnimatedNode = require('AnimatedNode');
 
 export opaque type ____StyleSheetInternalStyleIdentifier_Internal: number = number;
 
diff --git a/bots/dangerfile.js b/bots/dangerfile.js
index b97ecaf8e19f..3380e718fb34 100644
--- a/bots/dangerfile.js
+++ b/bots/dangerfile.js
@@ -11,7 +11,7 @@ const fs = require('fs');
 const includes = require('lodash.includes');
 const minimatch = require('minimatch');
 
-import { danger, fail, markdown, message, warn } from 'danger';
+const { danger, fail, markdown, message, warn } = require('danger');
 
 // Fails if the description is too short.
 if (!danger.github.pr.body || danger.github.pr.body.length < 10) {

From 439614891cb0ea5c0eeb6ef4d3bf1bbdec88d659 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 5 Apr 2018 06:14:54 -0700
Subject: [PATCH 0211/1109] Small refactor

Reviewed By: cpojer

Differential Revision: D7498659

fbshipit-source-id: 43ad85645e2366a385e08d68172e76e336fdfb1f
---
 Libraries/Components/ScrollView/ScrollView.js | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 29b9d57ca2a2..bc57f5cb400b 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -746,10 +746,9 @@ const ScrollView = createReactClass({
       this.props.horizontal && styles.contentContainerHorizontal,
       this.props.contentContainerStyle,
     ];
-    let style, childLayoutProps;
     if (__DEV__ && this.props.style) {
-      style = flattenStyle(this.props.style);
-      childLayoutProps = ['alignItems', 'justifyContent']
+      const style = flattenStyle(this.props.style);
+      const childLayoutProps = ['alignItems', 'justifyContent']
         .filter((prop) => style && style[prop] !== undefined);
       invariant(
         childLayoutProps.length === 0,

From 6be5d7827bd92b833319671c446bfabe34f9491d Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Ma=C3=ABl=20Nison?= <mael@fb.com>
Date: Thu, 5 Apr 2018 08:54:52 -0700
Subject: [PATCH 0212/1109] Adds an experimental hook for custom resolutions

Reviewed By: mjesun

Differential Revision: D7337022

fbshipit-source-id: fea1ee345e4d3b5713fed6cdc33869fbba6f21e2
---
 local-cli/bundle/buildBundle.js | 3 ++-
 local-cli/server/runServer.js   | 1 +
 2 files changed, 3 insertions(+), 1 deletion(-)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index ebebc09c6ebf..5b1f5be06534 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -98,8 +98,9 @@ async function buildBundle(
     postProcessBundleSourcemap: config.postProcessBundleSourcemap,
     projectRoots: config.getProjectRoots(),
     providesModuleNodeModules: providesModuleNodeModules,
-    resetCache: args.resetCache,
     reporter: new TerminalReporter(terminal),
+    resetCache: args.resetCache,
+    resolveRequest: config.resolveRequest,
     sourceExts: sourceExts.concat(defaultSourceExts),
     transformCache: TransformCaching.useTempDir(),
     transformModulePath: transformModulePath,
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 768fbaf0d367..1ccedf77765e 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -202,6 +202,7 @@ function getPackagerServer(args, config, reporter) {
     providesModuleNodeModules: providesModuleNodeModules,
     reporter,
     resetCache: args.resetCache,
+    resolveRequest: config.resolveRequest,
     sourceExts: args.sourceExts.concat(defaultSourceExts),
     transformModulePath: transformModulePath,
     transformCache: TransformCaching.useTempDir(),

From 52a3443e9805b2d56cbd288e10cab6e9d154cf90 Mon Sep 17 00:00:00 2001
From: Mehdi Mulani <mehdi@fb.com>
Date: Thu, 5 Apr 2018 14:32:43 -0700
Subject: [PATCH 0213/1109] Weakly capture the bridge in callback methods

Summary: Callback blocks are frequently held onto by modules, e.g. for animation the `RCTFrameAnimation` holds onto its callback method. This causes a bunch of retain cycles since the module will be strongly held onto by the bridge.

Reviewed By: Megra

Differential Revision: D7492136

fbshipit-source-id: 708e61ffe7bf0dcffaebc056ab861b9023ffc1df
---
 React/Base/RCTModuleMethod.mm | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/Base/RCTModuleMethod.mm b/React/Base/RCTModuleMethod.mm
index a8361482c4ed..1a1515779147 100644
--- a/React/Base/RCTModuleMethod.mm
+++ b/React/Base/RCTModuleMethod.mm
@@ -213,7 +213,7 @@ - (void)processMethodSignature
 #endif
 
 #define RCT_RETAINED_ARG_BLOCK(_logic) \
-[argumentBlocks addObject:^(__unused RCTBridge *bridge, NSUInteger index, id json) { \
+[argumentBlocks addObject:^(__unused __weak RCTBridge *bridge, NSUInteger index, id json) { \
   _logic                                                                             \
   [invocation setArgument:&value atIndex:(index) + 2];                               \
   if (value) {                                                                       \

From 7a29ad1d834a77cb66a3470f7598b1e6861adc70 Mon Sep 17 00:00:00 2001
From: Michael Lee <mzlee@fb.com>
Date: Thu, 5 Apr 2018 15:47:03 -0700
Subject: [PATCH 0214/1109] Specify platforms for the a few targets

Differential Revision: D7516968

fbshipit-source-id: db9d6df7c1b67dbdd998ea017229a976f78b2eb1
---
 ReactCommon/cxxreact/BUCK   | 1 +
 ReactCommon/jschelpers/BUCK | 2 ++
 2 files changed, 3 insertions(+)

diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 5f84b3fd5a24..6201e74cdf3b 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -141,6 +141,7 @@ rn_xplat_cxx_library(
     ],
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
     force_static = True,
+    platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
diff --git a/ReactCommon/jschelpers/BUCK b/ReactCommon/jschelpers/BUCK
index ac9ee706deb1..37dc1abb0df5 100644
--- a/ReactCommon/jschelpers/BUCK
+++ b/ReactCommon/jschelpers/BUCK
@@ -40,6 +40,7 @@ rn_xplat_cxx_library(
     fbandroid_deps = ANDROID_JSC_INTERNAL_DEPS,
     fbobjc_deps = APPLE_JSC_INTERNAL_DEPS,
     force_static = True,
+    platforms = (ANDROID, APPLE),
     visibility = [
         "PUBLIC",
     ],
@@ -64,6 +65,7 @@ rn_xplat_cxx_library(
     ],
     fbobjc_srcs = ["systemJSCWrapper.cpp"],
     force_static = True,
+    platforms = (ANDROID, APPLE),
     visibility = [
         "PUBLIC",
     ],

From 9b9b6c845e597e38a9801d34b6ffbe491cea7a20 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Thu, 5 Apr 2018 17:26:39 -0700
Subject: [PATCH 0215/1109] Inline and fix proguard rules

Summary:
The original proguard rules are put in the template, which is not very convenient and easy to get wrong. Because new rules get put, people also has two copy paste the rule. And there are also existing project import react native as a dependency. So the best way to  keep a android library project proguard rule is to manage the rule itself, using `consumerProguardFiles` like [dagger](https://github.com/JakeWharton/butterknife/blob/46baef6d96e93a1872efa17fdfc1d2af59b36f0c/butterknife/build.gradle#L9) and other android library project.

<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

Use RNTester to build the release flavor (now it has bugs https://github.com/facebook/react-native/issues/18460, I keep my change in local for now), after build success, run to check if crash.

In the process, I also fix https://github.com/facebook/react-native/issues/12994 and https://github.com/facebook/react-native/issues/6624 by adding the following to proguard rules
```proguard
-keep,includedescriptorclasses class com.facebook.react.bridge.** { *; }
```

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

[ANDROID] [ENHANCEMENT and BUGFIX] [Proguard rules] - inline and fix proguard rules .

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18461

Differential Revision: D7527533

Pulled By: hramos

fbshipit-source-id: 447dbc16983bcfb597187b40c1be3987a8c5a832
---
 ReactAndroid/build.gradle                     |  2 +
 ReactAndroid/proguard-rules.pro               | 90 +++++++++++++++++++
 .../HelloWorld/android/app/proguard-rules.pro | 72 ---------------
 3 files changed, 92 insertions(+), 72 deletions(-)
 create mode 100644 ReactAndroid/proguard-rules.pro

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index fa1be07afa74..15b5c02cdcab 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -251,6 +251,8 @@ android {
         versionCode 1
         versionName "1.0"
 
+        consumerProguardFiles 'proguard-rules.pro'
+
         ndk {
             moduleName "reactnativejni"
         }
diff --git a/ReactAndroid/proguard-rules.pro b/ReactAndroid/proguard-rules.pro
new file mode 100644
index 000000000000..6e9ff0ac7551
--- /dev/null
+++ b/ReactAndroid/proguard-rules.pro
@@ -0,0 +1,90 @@
+# Add project specific ProGuard rules here.
+# By default, the flags in this file are appended to flags specified
+# in /usr/local/Cellar/android-sdk/24.3.3/tools/proguard/proguard-android.txt
+# You can edit the include path and order by changing the proguardFiles
+# directive in build.gradle.
+#
+# For more details, see
+#   http://developer.android.com/guide/developing/tools/proguard.html
+
+# Add any project specific keep options here:
+
+# If your project uses WebView with JS, uncomment the following
+# and specify the fully qualified class name to the JavaScript interface
+# class:
+#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
+#   public *;
+#}
+
+# Disabling obfuscation is useful if you collect stack traces from production crashes
+# (unless you are using a system that supports de-obfuscate the stack traces).
+# -dontobfuscate
+
+# React Native
+
+# Keep our interfaces so they can be used by other ProGuard rules.
+# See http://sourceforge.net/p/proguard/bugs/466/
+-keep,allowobfuscation @interface com.facebook.proguard.annotations.DoNotStrip
+-keep,allowobfuscation @interface com.facebook.proguard.annotations.KeepGettersAndSetters
+-keep,allowobfuscation @interface com.facebook.common.internal.DoNotStrip
+
+# Do not strip any method/class that is annotated with @DoNotStrip
+-keep @com.facebook.proguard.annotations.DoNotStrip class *
+-keep @com.facebook.common.internal.DoNotStrip class *
+-keepclassmembers class * {
+    @com.facebook.proguard.annotations.DoNotStrip *;
+    @com.facebook.common.internal.DoNotStrip *;
+}
+
+-keepclassmembers @com.facebook.proguard.annotations.KeepGettersAndSetters class * {
+  void set*(***);
+  *** get*();
+}
+
+-keep class * extends com.facebook.react.bridge.JavaScriptModule { *; }
+-keep class * extends com.facebook.react.bridge.NativeModule { *; }
+-keepclassmembers,includedescriptorclasses class * { native <methods>; }
+-keepclassmembers class *  { @com.facebook.react.uimanager.UIProp <fields>; }
+-keepclassmembers class *  { @com.facebook.react.uimanager.annotations.ReactProp <methods>; }
+-keepclassmembers class *  { @com.facebook.react.uimanager.annotations.ReactPropGroup <methods>; }
+
+-dontwarn com.facebook.react.**
+-keep,includedescriptorclasses class com.facebook.react.bridge.** { *; }
+
+# TextLayoutBuilder uses a non-public Android constructor within StaticLayout.
+# See libs/proxy/src/main/java/com/facebook/fbui/textlayoutbuilder/proxy for details.
+-dontwarn android.text.StaticLayout
+
+# okhttp
+
+-keepattributes Signature
+-keepattributes *Annotation*
+-keep class okhttp3.** { *; }
+-keep interface okhttp3.** { *; }
+-dontwarn okhttp3.**
+
+# okio
+
+-keep class sun.misc.Unsafe { *; }
+-dontwarn java.nio.file.*
+-dontwarn org.codehaus.mojo.animal_sniffer.IgnoreJRERequirement
+-dontwarn okio.**
+
+# Fresco
+# Keep our interfaces so they can be used by other ProGuard rules.
+# See http://sourceforge.net/p/proguard/bugs/466/
+-keep,allowobfuscation @interface com.facebook.soloader.DoNotOptimize
+
+# Do not strip any method/class that is annotated with @DoNotOptimize
+-keep @com.facebook.soloader.DoNotOptimize class *
+-keepclassmembers class * {
+    @com.facebook.soloader.DoNotOptimize *;
+}
+
+# Keep native methods
+-keepclassmembers class * {
+    native <methods>;
+}
+
+-dontwarn javax.annotation.**
+-dontwarn com.facebook.infer.**
diff --git a/local-cli/templates/HelloWorld/android/app/proguard-rules.pro b/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
index b30112461f0e..a92fa177ee49 100644
--- a/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
+++ b/local-cli/templates/HelloWorld/android/app/proguard-rules.pro
@@ -15,75 +15,3 @@
 #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
 #   public *;
 #}
-
-# Disabling obfuscation is useful if you collect stack traces from production crashes
-# (unless you are using a system that supports de-obfuscate the stack traces).
-# -dontobfuscate
-
-# React Native
-
-# Keep our interfaces so they can be used by other ProGuard rules.
-# See http://sourceforge.net/p/proguard/bugs/466/
--keep,allowobfuscation @interface com.facebook.proguard.annotations.DoNotStrip
--keep,allowobfuscation @interface com.facebook.proguard.annotations.KeepGettersAndSetters
--keep,allowobfuscation @interface com.facebook.common.internal.DoNotStrip
-
-# Do not strip any method/class that is annotated with @DoNotStrip
--keep @com.facebook.proguard.annotations.DoNotStrip class *
--keep @com.facebook.common.internal.DoNotStrip class *
--keepclassmembers class * {
-    @com.facebook.proguard.annotations.DoNotStrip *;
-    @com.facebook.common.internal.DoNotStrip *;
-}
-
--keepclassmembers @com.facebook.proguard.annotations.KeepGettersAndSetters class * {
-  void set*(***);
-  *** get*();
-}
-
--keep class * extends com.facebook.react.bridge.JavaScriptModule { *; }
--keep class * extends com.facebook.react.bridge.NativeModule { *; }
--keepclassmembers,includedescriptorclasses class * { native <methods>; }
--keepclassmembers class *  { @com.facebook.react.uimanager.UIProp <fields>; }
--keepclassmembers class *  { @com.facebook.react.uimanager.annotations.ReactProp <methods>; }
--keepclassmembers class *  { @com.facebook.react.uimanager.annotations.ReactPropGroup <methods>; }
-
--dontwarn com.facebook.react.**
-
-# TextLayoutBuilder uses a non-public Android constructor within StaticLayout.
-# See libs/proxy/src/main/java/com/facebook/fbui/textlayoutbuilder/proxy for details.
--dontwarn android.text.StaticLayout
-
-# Fresco
-# Keep our interfaces so they can be used by other ProGuard rules.
-# See http://sourceforge.net/p/proguard/bugs/466/
--keep,allowobfuscation @interface com.facebook.soloader.DoNotOptimize
-
-# Do not strip any method/class that is annotated with @DoNotOptimize
--keep @com.facebook.soloader.DoNotOptimize class *
--keepclassmembers class * {
-    @com.facebook.soloader.DoNotOptimize *;
-}
-
-# Keep native methods
--keepclassmembers class * {
-    native <methods>;
-}
-
--dontwarn javax.annotation.**
--dontwarn com.facebook.infer.**
-
-# okhttp
-
--keepattributes Signature
--keepattributes *Annotation*
--keep class okhttp3.** { *; }
--keep interface okhttp3.** { *; }
--dontwarn okhttp3.**
-
-# okio
-
--keep class sun.misc.Unsafe { *; }
--dontwarn java.nio.file.*
--dontwarn org.codehaus.mojo.animal_sniffer.IgnoreJRERequirement
--dontwarn okio.**

From 445b0c7080dca699744f2aa7c69dde4f62b9c657 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Thu, 5 Apr 2018 17:33:08 -0700
Subject: [PATCH 0216/1109] React sync for revisions 1c2876d...7a3416f

Reviewed By: bvaughn

Differential Revision: D7526137

fbshipit-source-id: 9f9db8a6b56cb4ae581a7b8d28079ec38de2180f
---
 Libraries/Renderer/REVISION                   |   2 +-
 Libraries/Renderer/ReactFabric-dev.js         |  29 +-
 Libraries/Renderer/ReactFabric-prod.js        |  61 ++--
 Libraries/Renderer/ReactNativeRenderer-dev.js | 178 ++++-----
 .../Renderer/ReactNativeRenderer-prod.js      | 344 +++++++++---------
 5 files changed, 322 insertions(+), 292 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index fc81a7c7f28c..f505341495fa 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-1c2876d5b558b8591feb335d8d7204bc46f7da8a
\ No newline at end of file
+7a3416f27532ac25849dfbc505300d469b43bbcc
\ No newline at end of file
diff --git a/Libraries/Renderer/ReactFabric-dev.js b/Libraries/Renderer/ReactFabric-dev.js
index 0b7a78516c11..e51c0254b904 100644
--- a/Libraries/Renderer/ReactFabric-dev.js
+++ b/Libraries/Renderer/ReactFabric-dev.js
@@ -4765,6 +4765,14 @@ var ReactStrictModeWarnings = {
   var didWarnAboutDeprecatedLifecycles = new Set();
   var didWarnAboutUnsafeLifecycles = new Set();
 
+  var setToSortedString = function(set) {
+    var array = [];
+    set.forEach(function(value) {
+      array.push(value);
+    });
+    return array.sort().join(", ");
+  };
+
   ReactStrictModeWarnings.discardPendingWarnings = function() {
     pendingComponentWillMountWarnings = [];
     pendingComponentWillReceivePropsWarnings = [];
@@ -4790,9 +4798,7 @@ var ReactStrictModeWarnings = {
 
           var formatted = lifecycle.replace("UNSAFE_", "");
           var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = Array.from(componentNames)
-            .sort()
-            .join(", ");
+          var sortedComponentNames = setToSortedString(componentNames);
 
           lifecyclesWarningMesages.push(
             formatted +
@@ -4844,9 +4850,7 @@ var ReactStrictModeWarnings = {
         didWarnAboutDeprecatedLifecycles.add(fiber.type);
       });
 
-      var sortedNames = Array.from(uniqueNames)
-        .sort()
-        .join(", ");
+      var sortedNames = setToSortedString(uniqueNames);
 
       lowPriorityWarning$1(
         false,
@@ -4869,9 +4873,7 @@ var ReactStrictModeWarnings = {
         didWarnAboutDeprecatedLifecycles.add(fiber.type);
       });
 
-      var _sortedNames = Array.from(_uniqueNames)
-        .sort()
-        .join(", ");
+      var _sortedNames = setToSortedString(_uniqueNames);
 
       lowPriorityWarning$1(
         false,
@@ -4893,9 +4895,7 @@ var ReactStrictModeWarnings = {
         didWarnAboutDeprecatedLifecycles.add(fiber.type);
       });
 
-      var _sortedNames2 = Array.from(_uniqueNames2)
-        .sort()
-        .join(", ");
+      var _sortedNames2 = setToSortedString(_uniqueNames2);
 
       lowPriorityWarning$1(
         false,
@@ -6217,7 +6217,6 @@ var ReactFiberClassComponent = function(
       if (
         typeof instance.getSnapshotBeforeUpdate === "function" &&
         typeof instance.componentDidUpdate !== "function" &&
-        typeof instance.componentDidUpdate !== "function" &&
         !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
       ) {
         didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
@@ -9199,6 +9198,10 @@ var ReactFiberBeginWork = function(
         changedBits,
         renderExpirationTime
       );
+    } else if (oldProps === newProps) {
+      // Skip over a memoized parent with a bitmask bailout even
+      // if we began working on it because of a deeper matching child.
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
     // There is no bailout on `children` equality because we expect people
     // to often pass a bound method as a child, but it may reference
diff --git a/Libraries/Renderer/ReactFabric-prod.js b/Libraries/Renderer/ReactFabric-prod.js
index c12ebd601c84..c57d9bb9d0c9 100644
--- a/Libraries/Renderer/ReactFabric-prod.js
+++ b/Libraries/Renderer/ReactFabric-prod.js
@@ -3656,33 +3656,40 @@ function ReactFiberBeginWork(
             renderExpirationTime
           );
         case 12:
-          fn = workInProgress.type;
-          unmaskedContext = workInProgress.pendingProps;
-          var oldProps = workInProgress.memoizedProps;
-          props = fn._currentValue;
-          updateQueue = fn._changedBits;
-          if (
-            hasLegacyContextChanged() ||
-            0 !== updateQueue ||
-            oldProps !== unmaskedContext
-          ) {
-            workInProgress.memoizedProps = unmaskedContext;
-            oldProps = unmaskedContext.unstable_observedBits;
-            if (void 0 === oldProps || null === oldProps) oldProps = 1073741823;
-            workInProgress.stateNode = oldProps;
-            0 !== (updateQueue & oldProps) &&
-              propagateContextChange(
-                workInProgress,
-                fn,
-                updateQueue,
-                renderExpirationTime
-              );
-            renderExpirationTime = unmaskedContext.children;
-            renderExpirationTime = renderExpirationTime(props);
-            reconcileChildren(current, workInProgress, renderExpirationTime);
-            current = workInProgress.child;
-          } else
-            current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          a: {
+            fn = workInProgress.type;
+            unmaskedContext = workInProgress.pendingProps;
+            updateQueue = workInProgress.memoizedProps;
+            props = fn._currentValue;
+            var changedBits = fn._changedBits;
+            if (
+              hasLegacyContextChanged() ||
+              0 !== changedBits ||
+              updateQueue !== unmaskedContext
+            ) {
+              workInProgress.memoizedProps = unmaskedContext;
+              var observedBits = unmaskedContext.unstable_observedBits;
+              if (void 0 === observedBits || null === observedBits)
+                observedBits = 1073741823;
+              workInProgress.stateNode = observedBits;
+              if (0 !== (changedBits & observedBits))
+                propagateContextChange(
+                  workInProgress,
+                  fn,
+                  changedBits,
+                  renderExpirationTime
+                );
+              else if (updateQueue === unmaskedContext) {
+                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+                break a;
+              }
+              renderExpirationTime = unmaskedContext.children;
+              renderExpirationTime = renderExpirationTime(props);
+              reconcileChildren(current, workInProgress, renderExpirationTime);
+              current = workInProgress.child;
+            } else
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
           return current;
         default:
           invariant(
diff --git a/Libraries/Renderer/ReactNativeRenderer-dev.js b/Libraries/Renderer/ReactNativeRenderer-dev.js
index 7fd62f11ca6a..97bbfa4bef4d 100644
--- a/Libraries/Renderer/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/ReactNativeRenderer-dev.js
@@ -2995,6 +2995,75 @@ var TouchHistoryMath = {
 
 var ReactVersion = "16.3.1";
 
+var describeComponentFrame = function(name, source, ownerName) {
+  return (
+    "\n    in " +
+    (name || "Unknown") +
+    (source
+      ? " (at " +
+        source.fileName.replace(/^.*[\\\/]/, "") +
+        ":" +
+        source.lineNumber +
+        ")"
+      : ownerName ? " (created by " + ownerName + ")" : "")
+  );
+};
+
+function getComponentName(fiber) {
+  var type = fiber.type;
+
+  if (typeof type === "function") {
+    return type.displayName || type.name;
+  }
+  if (typeof type === "string") {
+    return type;
+  }
+  switch (type) {
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_RETURN_TYPE:
+      return "ReactReturn";
+  }
+  return null;
+}
+
+function describeFiber(fiber) {
+  switch (fiber.tag) {
+    case IndeterminateComponent:
+    case FunctionalComponent:
+    case ClassComponent:
+    case HostComponent:
+      var owner = fiber._debugOwner;
+      var source = fiber._debugSource;
+      var name = getComponentName(fiber);
+      var ownerName = null;
+      if (owner) {
+        ownerName = getComponentName(owner);
+      }
+      return describeComponentFrame(name, source, ownerName);
+    default:
+      return "";
+  }
+}
+
+// This function can only be called with a work-in-progress fiber and
+// only during begin or complete phase. Do not call it under any other
+// circumstances.
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  var node = workInProgress;
+  do {
+    info += describeFiber(node);
+    // Otherwise this return pointer might point to the wrong tree:
+    node = node["return"];
+  } while (node);
+  return info;
+}
+
 function _classCallCheck(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
     throw new TypeError("Cannot call a class as a function");
@@ -3589,28 +3658,6 @@ var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
 var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
 var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
 
-function getComponentName(fiber) {
-  var type = fiber.type;
-
-  if (typeof type === "function") {
-    return type.displayName || type.name;
-  }
-  if (typeof type === "string") {
-    return type;
-  }
-  switch (type) {
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
-  }
-  return null;
-}
-
 // TODO: Share this module between Fabric and React Native renderers
 // so that both can be used in the same tree.
 
@@ -4878,53 +4925,6 @@ function onCommitUnmount(fiber) {
   }
 }
 
-var describeComponentFrame = function(name, source, ownerName) {
-  return (
-    "\n    in " +
-    (name || "Unknown") +
-    (source
-      ? " (at " +
-        source.fileName.replace(/^.*[\\\/]/, "") +
-        ":" +
-        source.lineNumber +
-        ")"
-      : ownerName ? " (created by " + ownerName + ")" : "")
-  );
-};
-
-function describeFiber(fiber) {
-  switch (fiber.tag) {
-    case IndeterminateComponent:
-    case FunctionalComponent:
-    case ClassComponent:
-    case HostComponent:
-      var owner = fiber._debugOwner;
-      var source = fiber._debugSource;
-      var name = getComponentName(fiber);
-      var ownerName = null;
-      if (owner) {
-        ownerName = getComponentName(owner);
-      }
-      return describeComponentFrame(name, source, ownerName);
-    default:
-      return "";
-  }
-}
-
-// This function can only be called with a work-in-progress fiber and
-// only during begin or complete phase. Do not call it under any other
-// circumstances.
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  var node = workInProgress;
-  do {
-    info += describeFiber(node);
-    // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
-  } while (node);
-  return info;
-}
-
 /**
  * Forked from fbjs/warning:
  * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
@@ -5019,6 +5019,14 @@ var ReactStrictModeWarnings = {
   var didWarnAboutDeprecatedLifecycles = new Set();
   var didWarnAboutUnsafeLifecycles = new Set();
 
+  var setToSortedString = function(set) {
+    var array = [];
+    set.forEach(function(value) {
+      array.push(value);
+    });
+    return array.sort().join(", ");
+  };
+
   ReactStrictModeWarnings.discardPendingWarnings = function() {
     pendingComponentWillMountWarnings = [];
     pendingComponentWillReceivePropsWarnings = [];
@@ -5044,9 +5052,7 @@ var ReactStrictModeWarnings = {
 
           var formatted = lifecycle.replace("UNSAFE_", "");
           var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = Array.from(componentNames)
-            .sort()
-            .join(", ");
+          var sortedComponentNames = setToSortedString(componentNames);
 
           lifecyclesWarningMesages.push(
             formatted +
@@ -5098,9 +5104,7 @@ var ReactStrictModeWarnings = {
         didWarnAboutDeprecatedLifecycles.add(fiber.type);
       });
 
-      var sortedNames = Array.from(uniqueNames)
-        .sort()
-        .join(", ");
+      var sortedNames = setToSortedString(uniqueNames);
 
       lowPriorityWarning$1(
         false,
@@ -5123,9 +5127,7 @@ var ReactStrictModeWarnings = {
         didWarnAboutDeprecatedLifecycles.add(fiber.type);
       });
 
-      var _sortedNames = Array.from(_uniqueNames)
-        .sort()
-        .join(", ");
+      var _sortedNames = setToSortedString(_uniqueNames);
 
       lowPriorityWarning$1(
         false,
@@ -5147,9 +5149,7 @@ var ReactStrictModeWarnings = {
         didWarnAboutDeprecatedLifecycles.add(fiber.type);
       });
 
-      var _sortedNames2 = Array.from(_uniqueNames2)
-        .sort()
-        .join(", ");
+      var _sortedNames2 = setToSortedString(_uniqueNames2);
 
       lowPriorityWarning$1(
         false,
@@ -6475,7 +6475,6 @@ var ReactFiberClassComponent = function(
       if (
         typeof instance.getSnapshotBeforeUpdate === "function" &&
         typeof instance.componentDidUpdate !== "function" &&
-        typeof instance.componentDidUpdate !== "function" &&
         !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
       ) {
         didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
@@ -9457,6 +9456,10 @@ var ReactFiberBeginWork = function(
         changedBits,
         renderExpirationTime
       );
+    } else if (oldProps === newProps) {
+      // Skip over a memoized parent with a bitmask bailout even
+      // if we began working on it because of a deeper matching child.
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
     // There is no bailout on `children` equality because we expect people
     // to often pass a bound method as a child, but it may reference
@@ -14707,6 +14710,14 @@ injectFindHostInstance(NativeRenderer.findHostInstance);
 
 injection$2.injectRenderer(NativeRenderer);
 
+function computeComponentStackForErrorReporting(reactTag) {
+  var fiber = getInstanceFromTag(reactTag);
+  if (!fiber) {
+    return "";
+  }
+  return getStackAddendumByWorkInProgressFiber(fiber);
+}
+
 var roots = new Map();
 
 var ReactNativeRenderer = {
@@ -14762,7 +14773,8 @@ var ReactNativeRenderer = {
     ReactNativePropRegistry: ReactNativePropRegistry, // flattenStyle, Stylesheet
     TouchHistoryMath: TouchHistoryMath, // PanResponder
     createReactNativeComponentClass: createReactNativeComponentClass, // RCTText, RCTView, ReactNativeART
-    takeSnapshot: takeSnapshot
+    takeSnapshot: takeSnapshot, // react-native-implementation
+    computeComponentStackForErrorReporting: computeComponentStackForErrorReporting
   }
 };
 
diff --git a/Libraries/Renderer/ReactNativeRenderer-prod.js b/Libraries/Renderer/ReactNativeRenderer-prod.js
index 055ddd7bb0c1..bf2480f1c03d 100644
--- a/Libraries/Renderer/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/ReactNativeRenderer-prod.js
@@ -1198,107 +1198,152 @@ function createPortal(children, containerInfo, implementation) {
   };
 }
 var TouchHistoryMath = {
-    centroidDimension: function(
-      touchHistory,
-      touchesChangedAfter,
-      isXAxis,
-      ofCurrent
-    ) {
-      var touchBank = touchHistory.touchBank,
-        total = 0,
-        count = 0;
-      touchHistory =
-        1 === touchHistory.numberActiveTouches
-          ? touchHistory.touchBank[touchHistory.indexOfSingleActiveTouch]
-          : null;
-      if (null !== touchHistory)
-        touchHistory.touchActive &&
-          touchHistory.currentTimeStamp > touchesChangedAfter &&
+  centroidDimension: function(
+    touchHistory,
+    touchesChangedAfter,
+    isXAxis,
+    ofCurrent
+  ) {
+    var touchBank = touchHistory.touchBank,
+      total = 0,
+      count = 0;
+    touchHistory =
+      1 === touchHistory.numberActiveTouches
+        ? touchHistory.touchBank[touchHistory.indexOfSingleActiveTouch]
+        : null;
+    if (null !== touchHistory)
+      touchHistory.touchActive &&
+        touchHistory.currentTimeStamp > touchesChangedAfter &&
+        ((total +=
+          ofCurrent && isXAxis
+            ? touchHistory.currentPageX
+            : ofCurrent && !isXAxis
+              ? touchHistory.currentPageY
+              : !ofCurrent && isXAxis
+                ? touchHistory.previousPageX
+                : touchHistory.previousPageY),
+        (count = 1));
+    else
+      for (touchHistory = 0; touchHistory < touchBank.length; touchHistory++) {
+        var touchTrack = touchBank[touchHistory];
+        null !== touchTrack &&
+          void 0 !== touchTrack &&
+          touchTrack.touchActive &&
+          touchTrack.currentTimeStamp >= touchesChangedAfter &&
           ((total +=
             ofCurrent && isXAxis
-              ? touchHistory.currentPageX
+              ? touchTrack.currentPageX
               : ofCurrent && !isXAxis
-                ? touchHistory.currentPageY
+                ? touchTrack.currentPageY
                 : !ofCurrent && isXAxis
-                  ? touchHistory.previousPageX
-                  : touchHistory.previousPageY),
-          (count = 1));
-      else
-        for (
-          touchHistory = 0;
-          touchHistory < touchBank.length;
-          touchHistory++
-        ) {
-          var touchTrack = touchBank[touchHistory];
-          null !== touchTrack &&
-            void 0 !== touchTrack &&
-            touchTrack.touchActive &&
-            touchTrack.currentTimeStamp >= touchesChangedAfter &&
-            ((total +=
-              ofCurrent && isXAxis
-                ? touchTrack.currentPageX
-                : ofCurrent && !isXAxis
-                  ? touchTrack.currentPageY
-                  : !ofCurrent && isXAxis
-                    ? touchTrack.previousPageX
-                    : touchTrack.previousPageY),
-            count++);
-        }
-      return 0 < count ? total / count : TouchHistoryMath.noCentroid;
-    },
-    currentCentroidXOfTouchesChangedAfter: function(
+                  ? touchTrack.previousPageX
+                  : touchTrack.previousPageY),
+          count++);
+      }
+    return 0 < count ? total / count : TouchHistoryMath.noCentroid;
+  },
+  currentCentroidXOfTouchesChangedAfter: function(
+    touchHistory,
+    touchesChangedAfter
+  ) {
+    return TouchHistoryMath.centroidDimension(
       touchHistory,
-      touchesChangedAfter
-    ) {
-      return TouchHistoryMath.centroidDimension(
-        touchHistory,
-        touchesChangedAfter,
-        !0,
-        !0
-      );
-    },
-    currentCentroidYOfTouchesChangedAfter: function(
+      touchesChangedAfter,
+      !0,
+      !0
+    );
+  },
+  currentCentroidYOfTouchesChangedAfter: function(
+    touchHistory,
+    touchesChangedAfter
+  ) {
+    return TouchHistoryMath.centroidDimension(
       touchHistory,
-      touchesChangedAfter
-    ) {
-      return TouchHistoryMath.centroidDimension(
-        touchHistory,
-        touchesChangedAfter,
-        !1,
-        !0
-      );
-    },
-    previousCentroidXOfTouchesChangedAfter: function(
+      touchesChangedAfter,
+      !1,
+      !0
+    );
+  },
+  previousCentroidXOfTouchesChangedAfter: function(
+    touchHistory,
+    touchesChangedAfter
+  ) {
+    return TouchHistoryMath.centroidDimension(
       touchHistory,
-      touchesChangedAfter
-    ) {
-      return TouchHistoryMath.centroidDimension(
-        touchHistory,
-        touchesChangedAfter,
-        !0,
-        !1
-      );
-    },
-    previousCentroidYOfTouchesChangedAfter: function(
+      touchesChangedAfter,
+      !0,
+      !1
+    );
+  },
+  previousCentroidYOfTouchesChangedAfter: function(
+    touchHistory,
+    touchesChangedAfter
+  ) {
+    return TouchHistoryMath.centroidDimension(
       touchHistory,
-      touchesChangedAfter
-    ) {
-      return TouchHistoryMath.centroidDimension(
-        touchHistory,
-        touchesChangedAfter,
-        !1,
-        !1
-      );
-    },
-    currentCentroidX: function(touchHistory) {
-      return TouchHistoryMath.centroidDimension(touchHistory, 0, !0, !0);
-    },
-    currentCentroidY: function(touchHistory) {
-      return TouchHistoryMath.centroidDimension(touchHistory, 0, !1, !0);
-    },
-    noCentroid: -1
+      touchesChangedAfter,
+      !1,
+      !1
+    );
+  },
+  currentCentroidX: function(touchHistory) {
+    return TouchHistoryMath.centroidDimension(touchHistory, 0, !0, !0);
   },
-  objects = {},
+  currentCentroidY: function(touchHistory) {
+    return TouchHistoryMath.centroidDimension(touchHistory, 0, !1, !0);
+  },
+  noCentroid: -1
+};
+function getComponentName(fiber) {
+  fiber = fiber.type;
+  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
+  if ("string" === typeof fiber) return fiber;
+  switch (fiber) {
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_RETURN_TYPE:
+      return "ReactReturn";
+  }
+  return null;
+}
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
+    }
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress["return"];
+  } while (workInProgress);
+  return info;
+}
+var objects = {},
   uniqueID = 1,
   emptyObject$2 = {},
   ReactNativePropRegistry = (function() {
@@ -1561,22 +1606,6 @@ function mountSafeCallback(context, callback) {
 }
 var ReactCurrentOwner =
   React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
-function getComponentName(fiber) {
-  fiber = fiber.type;
-  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
-  if ("string" === typeof fiber) return fiber;
-  switch (fiber) {
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
-  }
-  return null;
-}
 function findHostInstance() {
   return null;
 }
@@ -1988,39 +2017,6 @@ function onCommitRoot(root) {
 function onCommitUnmount(fiber) {
   "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
 }
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  do {
-    a: switch (workInProgress.tag) {
-      case 0:
-      case 1:
-      case 2:
-      case 5:
-        var owner = workInProgress._debugOwner,
-          source = workInProgress._debugSource;
-        var JSCompiler_inline_result = getComponentName(workInProgress);
-        var ownerName = null;
-        owner && (ownerName = getComponentName(owner));
-        owner = source;
-        JSCompiler_inline_result =
-          "\n    in " +
-          (JSCompiler_inline_result || "Unknown") +
-          (owner
-            ? " (at " +
-              owner.fileName.replace(/^.*[\\\/]/, "") +
-              ":" +
-              owner.lineNumber +
-              ")"
-            : ownerName ? " (created by " + ownerName + ")" : "");
-        break a;
-      default:
-        JSCompiler_inline_result = "";
-    }
-    info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
-  } while (workInProgress);
-  return info;
-}
 var _require = require("ReactFeatureFlags"),
   enableGetDerivedStateFromCatch = _require.enableGetDerivedStateFromCatch,
   debugRenderPhaseSideEffects = _require.debugRenderPhaseSideEffects,
@@ -3926,33 +3922,40 @@ function ReactFiberBeginWork(
             renderExpirationTime
           );
         case 12:
-          fn = workInProgress.type;
-          unmaskedContext = workInProgress.pendingProps;
-          var oldProps = workInProgress.memoizedProps;
-          props = fn._currentValue;
-          updateQueue = fn._changedBits;
-          if (
-            hasLegacyContextChanged() ||
-            0 !== updateQueue ||
-            oldProps !== unmaskedContext
-          ) {
-            workInProgress.memoizedProps = unmaskedContext;
-            oldProps = unmaskedContext.unstable_observedBits;
-            if (void 0 === oldProps || null === oldProps) oldProps = 1073741823;
-            workInProgress.stateNode = oldProps;
-            0 !== (updateQueue & oldProps) &&
-              propagateContextChange(
-                workInProgress,
-                fn,
-                updateQueue,
-                renderExpirationTime
-              );
-            renderExpirationTime = unmaskedContext.children;
-            renderExpirationTime = renderExpirationTime(props);
-            reconcileChildren(current, workInProgress, renderExpirationTime);
-            current = workInProgress.child;
-          } else
-            current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          a: {
+            fn = workInProgress.type;
+            unmaskedContext = workInProgress.pendingProps;
+            updateQueue = workInProgress.memoizedProps;
+            props = fn._currentValue;
+            var changedBits = fn._changedBits;
+            if (
+              hasLegacyContextChanged() ||
+              0 !== changedBits ||
+              updateQueue !== unmaskedContext
+            ) {
+              workInProgress.memoizedProps = unmaskedContext;
+              var observedBits = unmaskedContext.unstable_observedBits;
+              if (void 0 === observedBits || null === observedBits)
+                observedBits = 1073741823;
+              workInProgress.stateNode = observedBits;
+              if (0 !== (changedBits & observedBits))
+                propagateContextChange(
+                  workInProgress,
+                  fn,
+                  changedBits,
+                  renderExpirationTime
+                );
+              else if (updateQueue === unmaskedContext) {
+                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+                break a;
+              }
+              renderExpirationTime = unmaskedContext.children;
+              renderExpirationTime = renderExpirationTime(props);
+              reconcileChildren(current, workInProgress, renderExpirationTime);
+              current = workInProgress.child;
+            } else
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
           return current;
         default:
           invariant(
@@ -6554,6 +6557,11 @@ var roots = new Map(),
           "window" !== view &&
           (view = findNumericNodeHandleFiber(view) || "window");
         return UIManager.__takeSnapshot(view, options);
+      },
+      computeComponentStackForErrorReporting: function(reactTag) {
+        return (reactTag = getInstanceFromTag(reactTag))
+          ? getStackAddendumByWorkInProgressFiber(reactTag)
+          : "";
       }
     }
   };

From 06085d38366373f3135074dc14e2c9871ca4fe29 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Thu, 5 Apr 2018 21:53:07 -0700
Subject: [PATCH 0217/1109] Move TouchHistoryMath from React Repo to React
 Native

Summary:
This hasn't been used by React core for a while. It's unclear why it was in the first place.

We can move it back next to the Panresponder.

https://github.com/facebook/react/pull/12557

Reviewed By: sophiebits

Differential Revision: D7529949

fbshipit-source-id: ef9892cfa8d2d6768da216b81befabe02795a245
---
 Libraries/Interaction/TouchHistoryMath.js    | 151 +++++++++++++++++++
 Libraries/Renderer/shims/TouchHistoryMath.js |  17 ---
 2 files changed, 151 insertions(+), 17 deletions(-)
 create mode 100644 Libraries/Interaction/TouchHistoryMath.js
 delete mode 100644 Libraries/Renderer/shims/TouchHistoryMath.js

diff --git a/Libraries/Interaction/TouchHistoryMath.js b/Libraries/Interaction/TouchHistoryMath.js
new file mode 100644
index 000000000000..be5aa707653c
--- /dev/null
+++ b/Libraries/Interaction/TouchHistoryMath.js
@@ -0,0 +1,151 @@
+/**
+ * Copyright (c) 2016-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+const TouchHistoryMath = {
+  /**
+   * This code is optimized and not intended to look beautiful. This allows
+   * computing of touch centroids that have moved after `touchesChangedAfter`
+   * timeStamp. You can compute the current centroid involving all touches
+   * moves after `touchesChangedAfter`, or you can compute the previous
+   * centroid of all touches that were moved after `touchesChangedAfter`.
+   *
+   * @param {TouchHistoryMath} touchHistory Standard Responder touch track
+   * data.
+   * @param {number} touchesChangedAfter timeStamp after which moved touches
+   * are considered "actively moving" - not just "active".
+   * @param {boolean} isXAxis Consider `x` dimension vs. `y` dimension.
+   * @param {boolean} ofCurrent Compute current centroid for actively moving
+   * touches vs. previous centroid of now actively moving touches.
+   * @return {number} value of centroid in specified dimension.
+   */
+  centroidDimension: function(
+    touchHistory,
+    touchesChangedAfter,
+    isXAxis,
+    ofCurrent,
+  ) {
+    const touchBank = touchHistory.touchBank;
+    let total = 0;
+    let count = 0;
+
+    const oneTouchData =
+      touchHistory.numberActiveTouches === 1
+        ? touchHistory.touchBank[touchHistory.indexOfSingleActiveTouch]
+        : null;
+
+    if (oneTouchData !== null) {
+      if (
+        oneTouchData.touchActive &&
+        oneTouchData.currentTimeStamp > touchesChangedAfter
+      ) {
+        total +=
+          ofCurrent && isXAxis
+            ? oneTouchData.currentPageX
+            : ofCurrent && !isXAxis
+              ? oneTouchData.currentPageY
+              : !ofCurrent && isXAxis
+                ? oneTouchData.previousPageX
+                : oneTouchData.previousPageY;
+        count = 1;
+      }
+    } else {
+      for (let i = 0; i < touchBank.length; i++) {
+        const touchTrack = touchBank[i];
+        if (
+          touchTrack !== null &&
+          touchTrack !== undefined &&
+          touchTrack.touchActive &&
+          touchTrack.currentTimeStamp >= touchesChangedAfter
+        ) {
+          let toAdd; // Yuck, program temporarily in invalid state.
+          if (ofCurrent && isXAxis) {
+            toAdd = touchTrack.currentPageX;
+          } else if (ofCurrent && !isXAxis) {
+            toAdd = touchTrack.currentPageY;
+          } else if (!ofCurrent && isXAxis) {
+            toAdd = touchTrack.previousPageX;
+          } else {
+            toAdd = touchTrack.previousPageY;
+          }
+          total += toAdd;
+          count++;
+        }
+      }
+    }
+    return count > 0 ? total / count : TouchHistoryMath.noCentroid;
+  },
+
+  currentCentroidXOfTouchesChangedAfter: function(
+    touchHistory,
+    touchesChangedAfter,
+  ) {
+    return TouchHistoryMath.centroidDimension(
+      touchHistory,
+      touchesChangedAfter,
+      true, // isXAxis
+      true, // ofCurrent
+    );
+  },
+
+  currentCentroidYOfTouchesChangedAfter: function(
+    touchHistory,
+    touchesChangedAfter,
+  ) {
+    return TouchHistoryMath.centroidDimension(
+      touchHistory,
+      touchesChangedAfter,
+      false, // isXAxis
+      true, // ofCurrent
+    );
+  },
+
+  previousCentroidXOfTouchesChangedAfter: function(
+    touchHistory,
+    touchesChangedAfter,
+  ) {
+    return TouchHistoryMath.centroidDimension(
+      touchHistory,
+      touchesChangedAfter,
+      true, // isXAxis
+      false, // ofCurrent
+    );
+  },
+
+  previousCentroidYOfTouchesChangedAfter: function(
+    touchHistory,
+    touchesChangedAfter,
+  ) {
+    return TouchHistoryMath.centroidDimension(
+      touchHistory,
+      touchesChangedAfter,
+      false, // isXAxis
+      false, // ofCurrent
+    );
+  },
+
+  currentCentroidX: function(touchHistory) {
+    return TouchHistoryMath.centroidDimension(
+      touchHistory,
+      0, // touchesChangedAfter
+      true, // isXAxis
+      true, // ofCurrent
+    );
+  },
+
+  currentCentroidY: function(touchHistory) {
+    return TouchHistoryMath.centroidDimension(
+      touchHistory,
+      0, // touchesChangedAfter
+      false, // isXAxis
+      true, // ofCurrent
+    );
+  },
+
+  noCentroid: -1,
+};
+
+module.exports = TouchHistoryMath;
diff --git a/Libraries/Renderer/shims/TouchHistoryMath.js b/Libraries/Renderer/shims/TouchHistoryMath.js
deleted file mode 100644
index 75edb24a7209..000000000000
--- a/Libraries/Renderer/shims/TouchHistoryMath.js
+++ /dev/null
@@ -1,17 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule TouchHistoryMath
- */
-
-'use strict';
-
-const {
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-} = require('ReactNative');
-
-module.exports =
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.TouchHistoryMath;

From 95f625e151c7abbb05efcd14404c8aa9583faa83 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 5 Apr 2018 22:01:35 -0700
Subject: [PATCH 0218/1109] Fixed RNTester (iOS) xcode project to include new
 Yoga files

Summary: Recent commit that added YGConfig.h broke this project because the files were not added to it.

Reviewed By: shergin

Differential Revision: D7530369

fbshipit-source-id: 77129288905d25b94ad7aad4be43e0052a784163
---
 React/React.xcodeproj/project.pbxproj | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index dbc8cef8aad0..e9d07dd8d9e8 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -1147,6 +1147,8 @@
 		59EDBCC61FDF4E55003573DE /* (null) in Copy Headers */ = {isa = PBXBuildFile; };
 		59EDBCC71FDF4E55003573DE /* RCTScrollView.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 59EDBCA31FDF4E0C003573DE /* RCTScrollView.h */; };
 		59EDBCC81FDF4E55003573DE /* RCTScrollViewManager.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 59EDBCA51FDF4E0C003573DE /* RCTScrollViewManager.h */; };
+		5CE2080220772F7D009A43B3 /* YGConfig.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 5CE2080020772F7C009A43B3 /* YGConfig.cpp */; };
+		5CE2080320772F7D009A43B3 /* YGConfig.h in Headers */ = {isa = PBXBuildFile; fileRef = 5CE2080120772F7C009A43B3 /* YGConfig.h */; };
 		657734841EE834C900A0E9EA /* RCTInspectorDevServerHelper.h in Headers */ = {isa = PBXBuildFile; fileRef = 657734821EE834C900A0E9EA /* RCTInspectorDevServerHelper.h */; };
 		657734851EE834C900A0E9EA /* RCTInspectorDevServerHelper.mm in Sources */ = {isa = PBXBuildFile; fileRef = 657734831EE834C900A0E9EA /* RCTInspectorDevServerHelper.mm */; };
 		657734861EE834D900A0E9EA /* RCTInspectorDevServerHelper.mm in Sources */ = {isa = PBXBuildFile; fileRef = 657734831EE834C900A0E9EA /* RCTInspectorDevServerHelper.mm */; };
@@ -2237,6 +2239,8 @@
 		59EDBCA41FDF4E0C003573DE /* RCTScrollView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTScrollView.m; sourceTree = "<group>"; };
 		59EDBCA51FDF4E0C003573DE /* RCTScrollViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTScrollViewManager.h; sourceTree = "<group>"; };
 		59EDBCA61FDF4E0C003573DE /* RCTScrollViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTScrollViewManager.m; sourceTree = "<group>"; };
+		5CE2080020772F7C009A43B3 /* YGConfig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = YGConfig.cpp; sourceTree = "<group>"; };
+		5CE2080120772F7C009A43B3 /* YGConfig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = YGConfig.h; sourceTree = "<group>"; };
 		657734821EE834C900A0E9EA /* RCTInspectorDevServerHelper.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInspectorDevServerHelper.h; sourceTree = "<group>"; };
 		657734831EE834C900A0E9EA /* RCTInspectorDevServerHelper.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = RCTInspectorDevServerHelper.mm; sourceTree = "<group>"; };
 		6577348A1EE8354A00A0E9EA /* RCTInspector.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = RCTInspector.h; path = Inspector/RCTInspector.h; sourceTree = "<group>"; };
@@ -2355,6 +2359,8 @@
 		130A77021DF767AF001F9587 /* yoga */ = {
 			isa = PBXGroup;
 			children = (
+				5CE2080020772F7C009A43B3 /* YGConfig.cpp */,
+				5CE2080120772F7C009A43B3 /* YGConfig.h */,
 				53DEF6E6205AE59B006A3890 /* YGFloatOptional.cpp */,
 				53DEF6E7205AE59C006A3890 /* YGFloatOptional.h */,
 				5343895E203905B6008E0CB3 /* YGLayout.cpp */,
@@ -3561,6 +3567,7 @@
 				59EDBCAD1FDF4E0C003573DE /* RCTScrollContentView.h in Headers */,
 				59EDBCA71FDF4E0C003573DE /* RCTScrollableProtocol.h in Headers */,
 				591F78DC202ADB22004A668C /* RCTLayout.h in Headers */,
+				5CE2080320772F7D009A43B3 /* YGConfig.h in Headers */,
 				3D80DA631DF820620028D040 /* RCTBorderDrawing.h in Headers */,
 				3D80DA641DF820620028D040 /* RCTBorderStyle.h in Headers */,
 				3D80DA651DF820620028D040 /* RCTComponent.h in Headers */,
@@ -4538,6 +4545,7 @@
 				13A1F71E1A75392D00D3D453 /* RCTKeyCommands.m in Sources */,
 				83CBBA531A601E3B00E9B192 /* RCTUtils.m in Sources */,
 				130443C61E401A8C00D93A67 /* RCTConvert+Transform.m in Sources */,
+				5CE2080220772F7D009A43B3 /* YGConfig.cpp in Sources */,
 				191E3EC11C29DC3800C180A6 /* RCTRefreshControl.m in Sources */,
 				3DCE532B1FEAB23100613583 /* RCTDatePickerManager.m in Sources */,
 				13C156051AB1A2840079392D /* RCTWebView.m in Sources */,

From c6610577fd6f6ad443f96669fb39a2197e33434e Mon Sep 17 00:00:00 2001
From: Angly Cat <angly.cat@gmail.com>
Date: Fri, 6 Apr 2018 09:49:56 -0700
Subject: [PATCH 0219/1109] Fix launching iOS simulator regression

Summary:
PR #17284 (accepted in 2ad34075f1d048bebb08ef30799ac0d081073150) introduced a couple of regressions.

~1. There's the code:~
```
.then((appName) => resolve(selectedSimulator.udid, appName));
/* ... */
.then((udid, appName) => {
```

~~This makes `appName` to be always `undefined` as per `resolve` accepts only 1 argument. This regression causes issues if an app name differs from a scheme name.~

~This PR fixes this by wrapping both values in an array.~

This was fixed in 589eae1432cc4bbc16221f841e27b038099fd128.

2. The code
```
child_process.execFileSync('xcrun', ['simctl', 'boot', selectedSimulator.udid]);
```
makes a simulator *boot*, but the simulator *doesn't launch*. That's a regression, which forces developers to launch simulators by other means (by running a number of elaborate console commands, by running Xcode, or by running a simulator manually).

This PR reverts that part of changes.

Create a blank project with a name that differs from scheme name. Try to `react-native run-ios` in it. See that a simulator is launched and installing succeeds. Without this changes simulator wouldn't launch, and installing step would fail because of app name mismatch.

[CLI][BUGFIX][local-cli/runIOS/runIOS.js] - Fix running on multiple simulators feature regressions
Closes https://github.com/facebook/react-native/pull/18711

Differential Revision: D7535150

Pulled By: hramos

fbshipit-source-id: 5c714231e9977c0c829b6f8c793497cd31cd46b5
---
 local-cli/runIOS/runIOS.js | 11 ++++-------
 1 file changed, 4 insertions(+), 7 deletions(-)

diff --git a/local-cli/runIOS/runIOS.js b/local-cli/runIOS/runIOS.js
index 8927be98d802..1cbcc4108db7 100644
--- a/local-cli/runIOS/runIOS.js
+++ b/local-cli/runIOS/runIOS.js
@@ -115,15 +115,12 @@ function runOnSimulator(xcodeProject, args, scheme) {
 
     if (!selectedSimulator.booted) {
       const simulatorFullName = formattedDeviceName(selectedSimulator);
-      console.log(`Booting ${simulatorFullName}...`);
+      console.log(`Launching ${simulatorFullName}...`);
       try {
-        child_process.execFileSync('xcrun', ['simctl', 'boot', selectedSimulator.udid]);
+        child_process.spawnSync('xcrun', ['instruments', '-w', selectedSimulator.udid]);
       } catch (e) {
-        throw new Error(
-`Could not boot ${args.simulator} simulator. Is there already a simulator running?
-Running multiple simulators is only supported from Xcode 9 and up.
-Try closing the simulator or run the command again without specifying a simulator.`
-        );
+        // instruments always fail with 255 because it expects more arguments,
+        // but we want it to only launch the simulator
       }
     }
 

From 159869d250c8d8a7a43c3cfcd114ad8bc674e23e Mon Sep 17 00:00:00 2001
From: Mike Grabowski <grabbou@gmail.com>
Date: Fri, 6 Apr 2018 10:36:56 -0700
Subject: [PATCH 0220/1109] Fix: "Metro listenting on port undefined"

Summary:
Regression introduced in https://github.com/facebook/react-native/commit/2ad34075f1d048bebb08ef30799ac0d081073150.

Fixes https://github.com/facebook/react-native/issues/18681
Closes https://github.com/facebook/react-native/pull/18722

Differential Revision: D7535684

Pulled By: hramos

fbshipit-source-id: 21bc79091148daba7b668965cd5becaa43117721
---
 local-cli/runIOS/runIOS.js | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/local-cli/runIOS/runIOS.js b/local-cli/runIOS/runIOS.js
index 1cbcc4108db7..ba6e844b5c2a 100644
--- a/local-cli/runIOS/runIOS.js
+++ b/local-cli/runIOS/runIOS.js
@@ -124,10 +124,10 @@ function runOnSimulator(xcodeProject, args, scheme) {
       }
     }
 
-    buildProject(xcodeProject, selectedSimulator.udid, scheme, args.configuration, args.packager, args.verbose)
-      .then((appName) => resolve(selectedSimulator.udid, appName));
+    buildProject(xcodeProject, selectedSimulator.udid, scheme, args.configuration, args.packager, args.verbose, args.port)
+      .then((appName) => resolve({ udid: selectedSimulator.udid, appName }));
   })
-  .then((udid, appName) => {
+  .then(({udid, appName}) => {
     if (!appName) {
       appName = scheme;
     }

From c2b9be08f8a20b080859e0d245e0cd1140522836 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Fri, 6 Apr 2018 12:31:02 -0700
Subject: [PATCH 0221/1109] Thread safe renderComponent

Reviewed By: mdvacca

Differential Revision: D7528307

fbshipit-source-id: 1f22898c17f10b883965b03d5c95bbb3c39209c4
---
 .../ReactAppInstrumentationTestCase.java      | 19 ++-----
 .../react/testing/ReactAppTestActivity.java   | 55 ++++++++++++++-----
 .../testing/ReactInstrumentationTest.java     | 30 ++--------
 3 files changed, 51 insertions(+), 53 deletions(-)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppInstrumentationTestCase.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppInstrumentationTestCase.java
index 863e249cbfe3..b01d0542af4b 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppInstrumentationTestCase.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppInstrumentationTestCase.java
@@ -37,21 +37,10 @@ protected void setUp() throws Exception {
     intent.putExtra(ReactAppTestActivity.EXTRA_IS_FABRIC_TEST, isFabricTest());
     setActivityIntent(intent);
     final ReactAppTestActivity activity = getActivity();
-    try {
-      runTestOnUiThread(new Runnable() {
-        @Override
-        public void run() {
-          activity.loadApp(
-              getReactApplicationKeyUnderTest(),
-              createReactInstanceSpecForTest(),
-              getEnableDevSupport());
-        }
-      });
-    } catch (Throwable t) {
-      throw new Exception("Unable to load react app", t);
-    }
-    waitForBridgeAndUIIdle();
-    assertTrue("Layout never occurred!", activity.waitForLayout(5000));
+    activity.loadApp(
+        getReactApplicationKeyUnderTest(),
+        createReactInstanceSpecForTest(),
+        getEnableDevSupport());
     waitForBridgeAndUIIdle();
   }
 
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index 341c87814942..de18fad93e27 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -11,6 +11,7 @@
 import android.graphics.Bitmap;
 import android.os.Bundle;
 import android.support.v4.app.FragmentActivity;
+import android.util.Log;
 import android.view.View;
 import android.view.ViewTreeObserver;
 import android.widget.FrameLayout;
@@ -180,17 +181,32 @@ public void loadApp(
     renderComponent(appKey, initialProps);
   }
 
-  public void renderComponent(String appKey, @Nullable Bundle initialProps) {
+  public void renderComponent(String appKey) {
+    renderComponent(appKey, null);
+  }
+
+  public void renderComponent(final String appKey, final @Nullable Bundle initialProps) {
     final CountDownLatch currentLayoutEvent = mLayoutEvent = new CountDownLatch(1);
-    Assertions.assertNotNull(mReactRootView).getViewTreeObserver().addOnGlobalLayoutListener(
-        new ViewTreeObserver.OnGlobalLayoutListener() {
-          @Override
-          public void onGlobalLayout() {
-            currentLayoutEvent.countDown();
-          }
-        });
-    Assertions.assertNotNull(mReactRootView)
-        .startReactApplication(mReactInstanceManager, appKey, initialProps);
+    runOnUiThread(new Runnable() {
+      @Override
+      public void run() {
+        Assertions.assertNotNull(mReactRootView).getViewTreeObserver().addOnGlobalLayoutListener(
+            new ViewTreeObserver.OnGlobalLayoutListener() {
+              @Override
+              public void onGlobalLayout() {
+                currentLayoutEvent.countDown();
+              }
+            });
+        Assertions.assertNotNull(mReactRootView)
+            .startReactApplication(mReactInstanceManager, appKey, initialProps);
+      }
+    });
+    try {
+      waitForBridgeAndUIIdle();
+      waitForLayout(5000);
+    } catch (InterruptedException e) {
+      throw new RuntimeException("Layout never occurred for component " + appKey, e);
+    }
   }
 
   public void loadBundle(
@@ -208,7 +224,7 @@ public void loadBundle(
 
     mBridgeIdleSignaler = new ReactBridgeIdleSignaler();
 
-    ReactInstanceManagerBuilder builder =
+    final ReactInstanceManagerBuilder builder =
         ReactTestHelper.getReactTestFactory()
             .getReactInstanceManagerBuilder()
             .setApplication(getApplication())
@@ -259,8 +275,21 @@ public FabricUIManager getJSIModule() {
               }})
         .setUIImplementationProvider(uiImplementationProvider);
 
-    mReactInstanceManager = builder.build();
-    mReactInstanceManager.onHostResume(this, this);
+    final CountDownLatch latch = new CountDownLatch(1);
+    runOnUiThread(new Runnable() {
+      @Override
+      public void run() {
+        mReactInstanceManager = builder.build();
+        mReactInstanceManager.onHostResume(ReactAppTestActivity.this, ReactAppTestActivity.this);
+        latch.countDown();
+      }
+    });
+    try {
+      latch.await(1000, TimeUnit.MILLISECONDS);
+    } catch (InterruptedException e) {
+      throw new RuntimeException(
+          "ReactInstanceManager never finished initializing " + bundleName, e);
+    }
   }
 
   private ReactInstanceManager getReactInstanceManager() {
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
index 3f0a7e250bfa..20dcc3ef516c 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
@@ -37,37 +37,17 @@ protected void setUp() throws Exception {
     intent.putExtra(ReactAppTestActivity.EXTRA_IS_FABRIC_TEST, isFabricTest());
     setActivityIntent(intent);
     final ReactAppTestActivity activity = getActivity();
-    try {
-      runTestOnUiThread(new Runnable() {
-        @Override
-        public void run() {
-          activity.loadBundle(
-              createReactInstanceSpecForTest(),
-              getBundleName(),
-              getEnableDevSupport());
-        }
-      });
-    } catch (Throwable t) {
-      throw new Exception("Unable to load react bundle " + getBundleName(), t);
-    }
+    activity.loadBundle(
+        createReactInstanceSpecForTest(),
+        getBundleName(),
+        getEnableDevSupport());
   }
 
   /**
    * Renders this component within this test's activity
    */
   public void renderComponent(final String componentName) throws Exception {
-    final ReactAppTestActivity activity = getActivity();
-    try {
-      runTestOnUiThread(new Runnable() {
-        @Override
-        public void run() {
-          activity.renderComponent(componentName, null);
-        }
-      });
-    } catch (Throwable t) {
-      throw new Exception("Unable to render component " + componentName, t);
-    }
-    assertTrue("Layout never occurred!", activity.waitForLayout(5000));
+    getActivity().renderComponent(componentName, null);
     waitForBridgeAndUIIdle();
   }
 

From 9736ddc061e9c4291df8a3185c7f9d6f73e435c7 Mon Sep 17 00:00:00 2001
From: Mike Grabowski <grabbou@gmail.com>
Date: Fri, 6 Apr 2018 14:10:12 -0700
Subject: [PATCH 0222/1109] Fix `run-ios` not turning on Simulator app

Summary:
Right now, `run-ios` will "boot" Simulator in the headless mode in the background, as long as the Simulator.app is not running. It is exactly what "detox" does - it executes your test suite in the background.

It seems to me that the author of this change was testing it with `Simulator.app` open.

In order to fix this behavior, we have to make sure it runs before we attempt booting.

This passed through the release process since we don't use `run-ios` there (it recommends turning on XCode and testing manually which is what I have done recently too).

Differential Revision: D7535693

Pulled By: hramos

fbshipit-source-id: 881db7740ace805ecefb98bfdb660e32aafd4664
---
 local-cli/runIOS/runIOS.js | 18 ++++++++++++++++++
 1 file changed, 18 insertions(+)

diff --git a/local-cli/runIOS/runIOS.js b/local-cli/runIOS/runIOS.js
index ba6e844b5c2a..de72569de6e4 100644
--- a/local-cli/runIOS/runIOS.js
+++ b/local-cli/runIOS/runIOS.js
@@ -112,6 +112,24 @@ function runOnSimulator(xcodeProject, args, scheme) {
     if (!selectedSimulator) {
       throw new Error(`Could not find ${args.simulator} simulator`);
     }
+    
+    /**
+		 * Booting simulator through `xcrun simctl boot` will boot it in the `headless` mode
+		 * (running in the background).
+		 *
+		 * In order for user to see the app and the simulator itself, we have to make sure
+		 * that the Simulator.app is running.
+		 *
+		 * We also pass it `-CurrentDeviceUDID` so that when we launch it for the first time,
+		 * it will not boot the "default" device, but the one we set. If the app is already running,
+		 * this flag has no effect.
+		 */
+		child_process.execFileSync('open', [
+			'/Applications/Xcode.app/Contents/Developer/Applications/Simulator.app',
+			'--args',
+			'-CurrentDeviceUDID',
+			selectedSimulator.udid
+		]);
 
     if (!selectedSimulator.booted) {
       const simulatorFullName = formattedDeviceName(selectedSimulator);

From e21bbee5862eaf08c8f198fa18a32350f5caabbc Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 6 Apr 2018 15:01:13 -0700
Subject: [PATCH 0223/1109] Mutate shared ReactShadowNode during
 Fabric.appendChild

Reviewed By: shergin

Differential Revision: D7495539

fbshipit-source-id: 2b2b06d3d4f02a00b01c7ed27d47b61787ea922f
---
 .../java/com/facebook/react/fabric/FabricUIManager.java     | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 2cadd153c3f1..52519e9d3129 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -216,6 +216,12 @@ public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
       Log.d(TAG, "appendChild \n\tparent: " + parent + "\n\tchild: " + child);
     }
     try {
+      // If the child to append is shared with another tree (child.getParent() != null),
+      // then we add a mutation of it. In the future this will be performed by FabricJS / Fiber.
+      //TODO: T27926878 avoid cloning shared child
+      if (child.getParent() != null) {
+        child = child.mutableCopy();
+      }
       parent.addChildAt(child, parent.getChildCount());
     } catch (Throwable t) {
       handleException(parent, t);

From 84ae1c9aecf38fdb1e02e0dea3ee7f9e73728e9f Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 6 Apr 2018 15:01:15 -0700
Subject: [PATCH 0224/1109] Move execution of Yoga.calculateLayout method
 before diffing algorithm

Reviewed By: shergin

Differential Revision: D7495581

fbshipit-source-id: 63d2f2a66c53727dea7981837d6d0f896bac35d3
---
 .../react/fabric/FabricUIManager.java         | 25 ++++++++++++-------
 1 file changed, 16 insertions(+), 9 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 52519e9d3129..0e7f8e7724a6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -256,20 +256,12 @@ public synchronized void completeRoot(int rootTag, List<ReactShadowNode> childLi
           currentRootShadowNode,
           "Root view with tag " + rootTag + " must be added before completeRoot is called");
 
-
       currentRootShadowNode = calculateDiffingAndCreateNewRootNode(currentRootShadowNode, childList);
 
-      if (DEBUG) {
-        Log.d(TAG, "ReactShadowNodeHierarchy after diffing: " + currentRootShadowNode.getHierarchyInfo());
-      }
-
-      notifyOnBeforeLayoutRecursive(currentRootShadowNode);
-      currentRootShadowNode.calculateLayout();
-
       if (DEBUG) {
         Log.d(
           TAG,
-          "ReactShadowNodeHierarchy after calculate Layout: " + currentRootShadowNode.getHierarchyInfo());
+          "ReactShadowNodeHierarchy after diffing: " + currentRootShadowNode.getHierarchyInfo());
       }
 
       applyUpdatesRecursive(currentRootShadowNode, 0, 0);
@@ -299,6 +291,21 @@ private ReactShadowNode calculateDiffingAndCreateNewRootNode(
       appendChild(newRootShadowNode, child);
     }
 
+    if (DEBUG) {
+      Log.d(
+        TAG,
+        "ReactShadowNodeHierarchy before calculateLayout: " + newRootShadowNode.getHierarchyInfo());
+    }
+
+    notifyOnBeforeLayoutRecursive(newRootShadowNode);
+    newRootShadowNode.calculateLayout();
+
+    if (DEBUG) {
+      Log.d(
+        TAG,
+        "ReactShadowNodeHierarchy after calculateLayout: " + newRootShadowNode.getHierarchyInfo());
+    }
+    
     mFabricReconciler.manageChildren(currentRootShadowNode, newRootShadowNode);
     return newRootShadowNode;
   }

From 9fd2b9a75fe3128de80230d5a1faf7d72e916cb0 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 6 Apr 2018 15:01:17 -0700
Subject: [PATCH 0225/1109] Add more logs into FabricUIManager and
 ReactShadowNodeImpl

Reviewed By: shergin, achen1

Differential Revision: D7495615

fbshipit-source-id: 4227b6648aaff8d9fe59bff1d4f75fd546baae6a
---
 .../react/fabric/FabricUIManager.java         |  2 +-
 .../react/uimanager/ReactShadowNodeImpl.java  | 28 +++++++++++++------
 2 files changed, 21 insertions(+), 9 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 0e7f8e7724a6..2eda32a0ee9f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -305,7 +305,7 @@ private ReactShadowNode calculateDiffingAndCreateNewRootNode(
         TAG,
         "ReactShadowNodeHierarchy after calculateLayout: " + newRootShadowNode.getHierarchyInfo());
     }
-    
+
     mFabricReconciler.manageChildren(currentRootShadowNode, newRootShadowNode);
     return newRootShadowNode;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index c5727e664e4c..1e92ab478581 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -8,6 +8,7 @@
 
 import static java.lang.System.arraycopy;
 
+import android.util.Log;
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.uimanager.annotations.ReactPropertyHolder;
 import com.facebook.yoga.YogaNodeCloneFunction;
@@ -58,6 +59,8 @@
 @ReactPropertyHolder
 public class ReactShadowNodeImpl implements ReactShadowNode<ReactShadowNodeImpl> {
 
+  private static final boolean DEBUG = true;
+  private static final String TAG = ReactShadowNodeImpl.class.getSimpleName();
   private static final YogaConfig sYogaConfig;
   static {
     sYogaConfig = ReactYogaConfigProvider.get();
@@ -68,10 +71,17 @@ public YogaNode cloneNode(YogaNode oldYogaNode,
           int childIndex) {
         ReactShadowNodeImpl parentReactShadowNode = (ReactShadowNodeImpl) parent.getData();
         Assertions.assertNotNull(parentReactShadowNode);
-        ReactShadowNodeImpl newReactShadowNode = (ReactShadowNodeImpl) oldYogaNode.getData();
-        Assertions.assertNotNull(newReactShadowNode);
+        ReactShadowNodeImpl oldReactShadowNode = (ReactShadowNodeImpl) oldYogaNode.getData();
+        Assertions.assertNotNull(oldReactShadowNode);
+
+        if (DEBUG) {
+          Log.d(
+            TAG,
+            "YogaNode started cloning: oldYogaNode: " + oldReactShadowNode + " - parent: "
+              + parentReactShadowNode + " index: " + childIndex);
+        }
 
-        ReactShadowNodeImpl newNode = newReactShadowNode.mutableCopy();
+        ReactShadowNodeImpl newNode = oldReactShadowNode.mutableCopy();
         parentReactShadowNode.replaceChild(newNode, childIndex);
         return newNode.mYogaNode;
       }
@@ -1044,17 +1054,19 @@ public String getHierarchyInfo() {
   private void getHierarchyInfoWithIndentation(StringBuilder result, int level) {
     // Spaces and tabs are dropped by IntelliJ logcat integration, so rely on __ instead.
     for (int i = 0; i < level; ++i) {
-      result.append("__");
+      result.append("  ");
     }
 
-    result.append(getClass().getSimpleName()).append(" ").append(getReactTag()).append(" ");
+    result.append("<").append(getClass().getSimpleName()).append(" tag=").append(getReactTag()).append(" hash=")
+      .append(hashCode());
     if (mYogaNode != null) {
-      result.append(getScreenX()).append(";").append(getScreenY()).append(";")
-        .append(getLayoutWidth()).append(";").append(getLayoutHeight());
+      result.append(" layout='x:").append(getScreenX())
+        .append(" y:").append(getScreenY()).append(" w:").append(getLayoutWidth()).append(" h:")
+        .append(getLayoutHeight()).append("'");
     } else {
       result.append("(virtual node)");
     }
-    result.append("\n");
+    result.append(">\n");
 
     if (getChildCount() == 0) {
       return;

From bf7601fde102114eda1144b48d2cfbc8dd7c95c1 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 6 Apr 2018 15:01:19 -0700
Subject: [PATCH 0226/1109] Avoid holding references to ReactShadowNode after a
 tree is commited

Reviewed By: achen1

Differential Revision: D7495721

fbshipit-source-id: 33d5bba5040729f891455a9c330234fe25130b02
---
 .../react/fabric/FabricUIManager.java         |  3 ++
 .../react/uimanager/ReactShadowNodeImpl.java  | 35 ++++++-------------
 2 files changed, 14 insertions(+), 24 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 2eda32a0ee9f..50e24738bf56 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -329,6 +329,9 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
       boolean frameDidChange =
           node.dispatchUpdates(absoluteX, absoluteY, mUIViewOperationQueue, null);
     }
+    // Set the reference to the OriginalReactShadowNode to NULL, as the tree is already committed
+    // and we do not need to hold references to the previous tree anymore
+    node.setOriginalReactShadowNode(null);
     node.markUpdateSeen();
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 1e92ab478581..7d08bd08ec65 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -131,13 +131,16 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     mViewClassName = original.mViewClassName;
     mThemedContext = original.mThemedContext;
     mShouldNotifyOnLayout = original.mShouldNotifyOnLayout;
-    mNodeUpdated = original.mNodeUpdated;
     mIsLayoutOnly = original.mIsLayoutOnly;
     mNativeParent = original.mNativeParent;
-    mScreenX = original.mScreenX;
-    mScreenY = original.mScreenY;
-    mScreenWidth = original.mScreenWidth;
-    mScreenHeight = original.mScreenHeight;
+    // Cloned nodes should be always updated.
+    mNodeUpdated = true;
+    // "cached" screen coordinates are not cloned because FabricJS not always clone the last
+    // ReactShadowNode that was rendered in the screen.
+    mScreenX = 0;
+    mScreenY = 0;
+    mScreenWidth = 0;
+    mScreenHeight = 0;
     arraycopy(original.mPadding, 0, mPadding, 0, original.mPadding.length);
     arraycopy(original.mPaddingIsPercent, 0, mPaddingIsPercent, 0, original.mPaddingIsPercent.length);
     mNewProps = null;
@@ -148,6 +151,7 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
   private void replaceChild(ReactShadowNodeImpl newNode, int childIndex) {
     mChildren.remove(childIndex);
     mChildren.add(childIndex, newNode);
+    newNode.mParent = this;
   }
 
   /**
@@ -164,14 +168,7 @@ public ReactShadowNodeImpl mutableCopy() {
     copy.mNativeChildren = mNativeChildren == null ? null : new ArrayList<>(mNativeChildren);
     copy.mTotalNativeChildren = mTotalNativeChildren;
     copy.mChildren = mChildren == null ? null : new ArrayList<>(mChildren);
-    copy.mYogaNode.setData(this);
-    if (mChildren != null) {
-      for (ReactShadowNode child : mChildren) {
-        if (child.getOriginalReactShadowNode() == null) {
-          child.setOriginalReactShadowNode(child);
-        }
-      }
-    }
+    copy.mYogaNode.setData(copy);
     return copy;
   }
 
@@ -182,7 +179,7 @@ public ReactShadowNodeImpl mutableCopyWithNewChildren() {
     copy.mNativeChildren = null;
     copy.mChildren = null;
     copy.mTotalNativeChildren = 0;
-    copy.mYogaNode.setData(this);
+    copy.mYogaNode.setData(copy);
     return copy;
   }
 
@@ -306,16 +303,6 @@ public void addChildAt(ReactShadowNodeImpl child, int i) {
                 + toString()
                 + "')");
       }
-      // TODO: T26729293 This is a temporary code that will be replaced as part of T26729293.
-      YogaNode parent = childYogaNode.getOwner();
-      if (parent != null) {
-        for (int k = 0; k < parent.getChildCount(); k++) {
-          if (parent.getChildAt(k) == childYogaNode) {
-            parent.removeChildAt(k);
-            break;
-          }
-        }
-      }
       mYogaNode.addChildAt(childYogaNode, i);
     }
     markUpdated();

From b0fa3228a77d89d6736da6fcae5dd32f74f3052c Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Fri, 6 Apr 2018 15:57:09 -0700
Subject: [PATCH 0227/1109] Implement Image.defaultSource property on Android

Summary:
This pull request implements Image.defaultSource property on Android, using Fresco (http://frescolib.org/docs/placeholder-failure-retry.html), which will show placeholder image (local asset) while loading remote image. Implementation code is almost same with loadingIndicatorSource, but without rotation.

This requires release or production to bundle local images in an APK file.

This provides feature parity with iOS.

Set Image.defaultSource on Android, and will show it while loading Image.source.

```JSX
<Image
  defaultSource={require('<path to image>')}
  source={{uri: '<url to remote image>'}}
  style={{ height: 300, width: 300 }}
/>
```

[ANDROID] [FEATURE] [IMAGE] - Image.defaultSource will show local image as placeholder while loading remote Image.source.
Closes https://github.com/facebook/react-native/pull/18588

Differential Revision: D7540489

Pulled By: himabindugadupudi

fbshipit-source-id: 908ceb659b3416e517bba64c76a31879d965ec09
---
 Libraries/Image/Image.android.js                  | 15 +++++++++++++++
 .../react/views/image/ReactImageManager.java      |  6 ++++++
 .../react/views/image/ReactImageView.java         | 10 ++++++++++
 3 files changed, 31 insertions(+)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index 4e218487c9b5..870b31cd8f92 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -74,6 +74,10 @@ var Image = createReactClass({
      * See https://facebook.github.io/react-native/docs/image.html#blurradius
      */
     blurRadius: PropTypes.number,
+    /**
+    * See https://facebook.github.io/react-native/docs/image.html#defaultsource
+    */
+    defaultSource: PropTypes.number,
     /**
      * See https://facebook.github.io/react-native/docs/image.html#loadingindicatorsource
      */
@@ -197,6 +201,7 @@ var Image = createReactClass({
 
   render: function() {
     const source = resolveAssetSource(this.props.source);
+    const defaultSource = resolveAssetSource(this.props.defaultSource);
     const loadingIndicatorSource = resolveAssetSource(
       this.props.loadingIndicatorSource,
     );
@@ -220,6 +225,12 @@ var Image = createReactClass({
       );
     }
 
+    if (this.props.defaultSource && this.props.loadingIndicatorSource) {
+      throw new Error(
+        'The <Image> component cannot have defaultSource and loadingIndicatorSource at the same time. Please use either defaultSource or loadingIndicatorSource.',
+      );
+    }
+
     if (source && (source.uri || Array.isArray(source))) {
       let style;
       let sources;
@@ -243,6 +254,9 @@ var Image = createReactClass({
         ),
         src: sources,
         headers: source.headers,
+        defaultSrc: defaultSource
+          ? defaultSource.uri
+          : null,
         loadingIndicatorSrc: loadingIndicatorSource
           ? loadingIndicatorSource.uri
           : null,
@@ -268,6 +282,7 @@ var cfg = {
   nativeOnly: {
     src: true,
     headers: true,
+    defaultSrc: true,
     loadingIndicatorSrc: true,
     shouldNotifyLoadEvents: true,
   },
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageManager.java
index 938524d30121..2565e2294ef1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageManager.java
@@ -88,6 +88,12 @@ public void setBlurRadius(ReactImageView view, float blurRadius) {
     view.setBlurRadius(blurRadius);
   }
 
+  // In JS this is Image.props.defaultSource
+  @ReactProp(name = "defaultSrc")
+  public void setDefaultSource(ReactImageView view, @Nullable String source) {
+    view.setDefaultSource(source);
+  }
+
   // In JS this is Image.props.loadingIndicatorSource.uri
   @ReactProp(name = "loadingIndicatorSrc")
   public void setLoadingIndicatorSource(ReactImageView view, @Nullable String source) {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index 9ab9c8884e80..cb294cbb93d7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -184,6 +184,7 @@ public CloseableReference<Bitmap> process(Bitmap source, PlatformBitmapFactory b
 
   private @Nullable ImageSource mImageSource;
   private @Nullable ImageSource mCachedImageSource;
+  private @Nullable Drawable mDefaultImageDrawable;
   private @Nullable Drawable mLoadingImageDrawable;
   private @Nullable RoundedColorDrawable mBackgroundImageDrawable;
   private int mBackgroundColor = 0x00000000;
@@ -369,6 +370,11 @@ public void setSource(@Nullable ReadableArray sources) {
     mIsDirty = true;
   }
 
+  public void setDefaultSource(@Nullable String name) {
+    mDefaultImageDrawable = ResourceDrawableIdHelper.getInstance().getResourceDrawable(getContext(), name);
+    mIsDirty = true;
+  }
+
   public void setLoadingIndicatorSource(@Nullable String name) {
     Drawable drawable = ResourceDrawableIdHelper.getInstance().getResourceDrawable(getContext(), name);
     mLoadingImageDrawable =
@@ -428,6 +434,10 @@ public void maybeUpdateView() {
     GenericDraweeHierarchy hierarchy = getHierarchy();
     hierarchy.setActualImageScaleType(mScaleType);
 
+    if (mDefaultImageDrawable != null) {
+      hierarchy.setPlaceholderImage(mDefaultImageDrawable, ScalingUtils.ScaleType.CENTER);
+    }
+
     if (mLoadingImageDrawable != null) {
       hierarchy.setPlaceholderImage(mLoadingImageDrawable, ScalingUtils.ScaleType.CENTER);
     }

From 667ca15893f4ef0538ed34dd93a2c04696e01240 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 6 Apr 2018 17:16:55 -0700
Subject: [PATCH 0228/1109] android: don't process touch events too early

Summary: There can be a race when loading JS from rootview for the first time vs touching rootview before JS is ready. This may cause redbox on the JS side.

Reviewed By: mdvacca

Differential Revision: D7531334

fbshipit-source-id: 36ffa1e5ff205f60b95e0a1d1016301ea76936aa
---
 .../com/facebook/react/ReactRootView.java     | 21 +++++++++++++++++--
 1 file changed, 19 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 5b8e3c53947e..c1d74a4aeddb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -84,7 +84,7 @@ public interface ReactRootViewEventListener {
   private int mRootViewTag;
   private boolean mIsAttachedToInstance;
   private boolean mShouldLogContentAppeared;
-  private final JSTouchDispatcher mJSTouchDispatcher = new JSTouchDispatcher(this);
+  private @Nullable JSTouchDispatcher mJSTouchDispatcher;
   private final ReactAndroidHWInputDeviceHelper mAndroidHWInputDeviceHelper = new ReactAndroidHWInputDeviceHelper(this);
   private boolean mWasMeasured = false;
   private int mWidthMeasureSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED);
@@ -183,6 +183,12 @@ public void onChildStartedNativeGesture(MotionEvent androidEvent) {
         "Unable to dispatch touch to JS as the catalyst instance has not been attached");
       return;
     }
+    if (mJSTouchDispatcher == null) {
+      FLog.w(
+        ReactConstants.TAG,
+        "Unable to dispatch touch to JS before the dispatcher is available");
+      return;
+    }
     ReactContext reactContext = mReactInstanceManager.getCurrentReactContext();
     EventDispatcher eventDispatcher = reactContext.getNativeModule(UIManagerModule.class)
       .getEventDispatcher();
@@ -264,6 +270,12 @@ private void dispatchJSTouchEvent(MotionEvent event) {
         "Unable to dispatch touch to JS as the catalyst instance has not been attached");
       return;
     }
+    if (mJSTouchDispatcher == null) {
+      FLog.w(
+        ReactConstants.TAG,
+        "Unable to dispatch touch to JS before the dispatcher is available");
+      return;
+    }
     ReactContext reactContext = mReactInstanceManager.getCurrentReactContext();
     EventDispatcher eventDispatcher = reactContext.getNativeModule(UIManagerModule.class)
       .getEventDispatcher();
@@ -414,6 +426,11 @@ public void unmountReactApplication() {
   }
 
   public void onAttachedToReactInstance() {
+    // Create the touch dispatcher here instead of having it always available, to make sure
+    // that all touch events are only passed to JS after React/JS side is ready to consume
+    // them. Otherwise, these events might break the states expected by JS.
+    // Note that this callback was invoked from within the UI thread.
+    mJSTouchDispatcher = new JSTouchDispatcher(this);
     if (mRootViewEventListener != null) {
       mRootViewEventListener.onAttachedToReactInstance(this);
     }
@@ -582,7 +599,7 @@ public boolean isFabric() {
   public ReactInstanceManager getReactInstanceManager() {
     return mReactInstanceManager;
   }
-  
+
   /* package */ void sendEvent(String eventName, @Nullable WritableMap params) {
     if (mReactInstanceManager != null) {
       mReactInstanceManager.getCurrentReactContext()

From 3372541a2a7ffc38311ba02f9183ba96edc6dfd8 Mon Sep 17 00:00:00 2001
From: Liamandrew <liam.e.andrew@gmail.com>
Date: Fri, 6 Apr 2018 17:39:54 -0700
Subject: [PATCH 0229/1109] Add ability for Animated views to be created with
 scale X or scale Y

Summary:
<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

*Accidentally closed previous PR*

Sometimes it can be useful to have an animated view be created with either scale X or scale Y in cases where scaleXY might not be as visually appealing.

Test Plan
Tested on both ios and android in the sample project:

https://github.com/Liamandrew/ScaleAnimationSample

![scaleanimation](https://user-images.githubusercontent.com/30114733/37023697-d0aa7372-217a-11e8-8d3b-2958c63ad83a.gif)
Closes https://github.com/facebook/react-native/pull/18220

Differential Revision: D7542334

Pulled By: hramos

fbshipit-source-id: 208472e5d8f5a04ca3c3a99adce77b035e331ef1
---
 Libraries/LayoutAnimation/LayoutAnimation.js  |  2 ++
 React/Modules/RCTUIManager.m                  | 14 +++++++++-
 .../layoutanimation/AnimatedPropertyType.java |  2 ++
 .../layoutanimation/BaseLayoutAnimation.java  | 26 +++++++++++++++++++
 4 files changed, 43 insertions(+), 1 deletion(-)

diff --git a/Libraries/LayoutAnimation/LayoutAnimation.js b/Libraries/LayoutAnimation/LayoutAnimation.js
index fe4a2cc2b843..f04feca9331a 100644
--- a/Libraries/LayoutAnimation/LayoutAnimation.js
+++ b/Libraries/LayoutAnimation/LayoutAnimation.js
@@ -32,6 +32,8 @@ const Types = keyMirror(TypesEnum);
 
 const PropertiesEnum = {
   opacity: true,
+  scaleX: true,
+  scaleY: true,
   scaleXY: true,
 };
 const Properties = keyMirror(PropertiesEnum);
diff --git a/React/Modules/RCTUIManager.m b/React/Modules/RCTUIManager.m
index 5dcce46588ba..49b0f774e3cd 100644
--- a/React/Modules/RCTUIManager.m
+++ b/React/Modules/RCTUIManager.m
@@ -595,6 +595,10 @@ - (RCTViewManagerUIBlock)uiBlockWithLayoutUpdateForRootView:(RCTRootShadowView *
         NSString *property = creatingLayoutAnimation.property;
         if ([property isEqualToString:@"scaleXY"]) {
           view.layer.transform = CATransform3DMakeScale(0, 0, 0);
+        } else if ([property isEqualToString:@"scaleX"]) {
+        view.layer.transform = CATransform3DMakeScale(0, 1, 0);
+        } else if ([property isEqualToString:@"scaleY"]) {
+        view.layer.transform = CATransform3DMakeScale(1, 0, 0);
         } else if ([property isEqualToString:@"opacity"]) {
           view.layer.opacity = 0.0;
         } else {
@@ -603,7 +607,11 @@ - (RCTViewManagerUIBlock)uiBlockWithLayoutUpdateForRootView:(RCTRootShadowView *
         }
 
         [creatingLayoutAnimation performAnimations:^{
-          if ([property isEqualToString:@"scaleXY"]) {
+          if (
+            [property isEqualToString:@"scaleX"] ||
+            [property isEqualToString:@"scaleY"] ||
+            [property isEqualToString:@"scaleXY"]
+          ) {
             view.layer.transform = finalTransform;
           } else if ([property isEqualToString:@"opacity"]) {
             view.layer.opacity = finalOpacity;
@@ -738,6 +746,10 @@ - (void)_removeChildren:(NSArray<UIView *> *)children
     [deletingLayoutAnimation performAnimations:^{
       if ([property isEqualToString:@"scaleXY"]) {
         removedChild.layer.transform = CATransform3DMakeScale(0.001, 0.001, 0.001);
+      } else if ([property isEqualToString:@"scaleX"]) {
+      removedChild.layer.transform = CATransform3DMakeScale(0.001, 1, 0.001);
+      } else if ([property isEqualToString:@"scaleY"]) {
+      removedChild.layer.transform = CATransform3DMakeScale(1, 0.001, 0.001);
       } else if ([property isEqualToString:@"opacity"]) {
         removedChild.layer.opacity = 0.0;
       } else {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AnimatedPropertyType.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AnimatedPropertyType.java
index 51a9d246c061..b979799747ca 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AnimatedPropertyType.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AnimatedPropertyType.java
@@ -8,6 +8,8 @@
  */
 /* package */ enum AnimatedPropertyType {
   OPACITY("opacity"),
+  SCALE_X("scaleX"),
+  SCALE_Y("scaleY"),
   SCALE_XY("scaleXY");
 
   private final String mName;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/BaseLayoutAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/BaseLayoutAnimation.java
index f4fa2ea5cd42..be06aedbc195 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/BaseLayoutAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/BaseLayoutAnimation.java
@@ -42,6 +42,32 @@ Animation createAnimationImpl(View view, int x, int y, int width, int height) {
               Animation.RELATIVE_TO_SELF,
               .5f);
         }
+        case SCALE_X: {
+          float fromValue = isReverse() ? 1.0f : 0.0f;
+          float toValue = isReverse() ? 0.0f : 1.0f;
+          return new ScaleAnimation(
+              fromValue,
+              toValue,
+              1f,
+              1f,
+              Animation.RELATIVE_TO_SELF,
+              .5f,
+              Animation.RELATIVE_TO_SELF,
+              0f);
+        }
+        case SCALE_Y: {
+          float fromValue = isReverse() ? 1.0f : 0.0f;
+          float toValue = isReverse() ? 0.0f : 1.0f;
+          return new ScaleAnimation(
+              1f,
+              1f,
+              fromValue,
+              toValue,
+              Animation.RELATIVE_TO_SELF,
+              0f,
+              Animation.RELATIVE_TO_SELF,
+              .5f);
+        }
         default:
           throw new IllegalViewOperationException(
               "Missing animation for property : " + mAnimatedProperty);

From 16bed9e6e50508c99e9666cb2fb5a06b0b534bf6 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sat, 7 Apr 2018 00:50:38 -0700
Subject: [PATCH 0230/1109] Support cloning of virtual ReactShadowNodes

Reviewed By: achen1

Differential Revision: D7542648

fbshipit-source-id: 58494db9f8525d4deabc6345f36941fa93a1d887
---
 .../react/uimanager/ReactShadowNodeImpl.java   | 18 ++++++++++++++----
 1 file changed, 14 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 7d08bd08ec65..018fa5ddace0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -164,22 +164,32 @@ protected ReactShadowNodeImpl copy() {
   @Override
   public ReactShadowNodeImpl mutableCopy() {
     ReactShadowNodeImpl copy = copy();
-    copy.mYogaNode = mYogaNode.clone();
+    if (mYogaNode != null) {
+      copy.mYogaNode = mYogaNode.clone();
+      copy.mYogaNode.setData(copy);
+    } else {
+      // Virtual ReactShadowNode do not have a YogaNode associated
+      copy.mYogaNode = null;
+    }
     copy.mNativeChildren = mNativeChildren == null ? null : new ArrayList<>(mNativeChildren);
     copy.mTotalNativeChildren = mTotalNativeChildren;
     copy.mChildren = mChildren == null ? null : new ArrayList<>(mChildren);
-    copy.mYogaNode.setData(copy);
     return copy;
   }
 
   @Override
   public ReactShadowNodeImpl mutableCopyWithNewChildren() {
     ReactShadowNodeImpl copy = copy();
-    copy.mYogaNode = mYogaNode.cloneWithNewChildren();
+    if (mYogaNode != null) {
+      copy.mYogaNode = mYogaNode.cloneWithNewChildren();
+      copy.mYogaNode.setData(copy);
+    } else {
+      // Virtual ReactShadowNode do not have a YogaNode associated
+      copy.mYogaNode = null;
+    }
     copy.mNativeChildren = null;
     copy.mChildren = null;
     copy.mTotalNativeChildren = 0;
-    copy.mYogaNode.setData(copy);
     return copy;
   }
 

From 554243eb567cc587ce50a3f2224bbf42b931c9b4 Mon Sep 17 00:00:00 2001
From: Sam Mueller <sjmueller@gmail.com>
Date: Sat, 7 Apr 2018 21:02:43 -0700
Subject: [PATCH 0231/1109] Fix TouchHistoryMath import

Summary:
The reference needed to be updated after the file was moved in this commit:
https://github.com/facebook/react-native/commit/06085d38366373f3135074dc14e2c9871ca4fe29

Otherwise, results in the packager failing with the following error:
> Unable to resolve module TouchHistoryMath from /node_modules/react-native/Libraries/Interaction/PanResponder.js: Module TouchHistoryMath does not exist in the Haste module map
Closes https://github.com/facebook/react-native/pull/18732

Differential Revision: D7547181

Pulled By: sebmarkbage

fbshipit-source-id: 78028c2f46faa2ce130a1a0c25fcaca47d2516a8
---
 Libraries/Interaction/PanResponder.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/Interaction/PanResponder.js b/Libraries/Interaction/PanResponder.js
index db7d85c87e27..d927fa5fc14d 100644
--- a/Libraries/Interaction/PanResponder.js
+++ b/Libraries/Interaction/PanResponder.js
@@ -10,7 +10,7 @@
 'use strict';
 
 const InteractionManager = require('./InteractionManager');
-const TouchHistoryMath = require('TouchHistoryMath');
+const TouchHistoryMath = require('./TouchHistoryMath');
 
 const currentCentroidXOfTouchesChangedAfter = TouchHistoryMath.currentCentroidXOfTouchesChangedAfter;
 const currentCentroidYOfTouchesChangedAfter = TouchHistoryMath.currentCentroidYOfTouchesChangedAfter;

From 9574f88701d2a23bbf2438d08d5af467e6a04ae8 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Sat, 7 Apr 2018 23:02:28 -0700
Subject: [PATCH 0232/1109] Move takeSnapshot from React repo to RN

Reviewed By: sophiebits

Differential Revision: D7547298

fbshipit-source-id: 6ab0c0a9e244a2f68d27307b84285b2c8fff1342
---
 Libraries/ReactNative/takeSnapshot.js    | 48 ++++++++++++++++++++++++
 Libraries/Renderer/shims/takeSnapshot.js | 17 ---------
 2 files changed, 48 insertions(+), 17 deletions(-)
 create mode 100644 Libraries/ReactNative/takeSnapshot.js
 delete mode 100644 Libraries/Renderer/shims/takeSnapshot.js

diff --git a/Libraries/ReactNative/takeSnapshot.js b/Libraries/ReactNative/takeSnapshot.js
new file mode 100644
index 000000000000..212e6338faca
--- /dev/null
+++ b/Libraries/ReactNative/takeSnapshot.js
@@ -0,0 +1,48 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @providesModule takeSnapshot
+ * @format
+ * @flow
+ */
+
+const ReactNative = require('ReactNative');
+const UIManager = require('UIManager');
+
+/**
+ * Capture an image of the screen, window or an individual view. The image
+ * will be stored in a temporary file that will only exist for as long as the
+ * app is running.
+ *
+ * The `view` argument can be the literal string `window` if you want to
+ * capture the entire window, or it can be a reference to a specific
+ * React Native component.
+ *
+ * The `options` argument may include:
+ * - width/height (number) - the width and height of the image to capture.
+ * - format (string) - either 'png' or 'jpeg'. Defaults to 'png'.
+ * - quality (number) - the quality when using jpeg. 0.0 - 1.0 (default).
+ *
+ * Returns a Promise.
+ * @platform ios
+ */
+module.exports = function takeSnapshot(
+  view?: 'window' | React$Element<any> | number,
+  options?: {
+    width?: number,
+    height?: number,
+    format?: 'png' | 'jpeg',
+    quality?: number,
+  },
+): Promise<any> {
+  if (typeof view !== 'number' && view !== 'window') {
+    view = ReactNative.findNodeHandle(view) || 'window';
+  }
+
+  // Call the hidden '__takeSnapshot' method; the main one throws an error to
+  // prevent accidental backwards-incompatible usage.
+  return UIManager.__takeSnapshot(view, options);
+};
diff --git a/Libraries/Renderer/shims/takeSnapshot.js b/Libraries/Renderer/shims/takeSnapshot.js
deleted file mode 100644
index 00abd891769c..000000000000
--- a/Libraries/Renderer/shims/takeSnapshot.js
+++ /dev/null
@@ -1,17 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule takeSnapshot
- */
-
-'use strict';
-
-const {
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-} = require('ReactNative');
-
-module.exports =
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.takeSnapshot;

From 9874004711f971648eb4f5d7e74b3a888eb8a521 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Sun, 8 Apr 2018 17:13:52 -0700
Subject: [PATCH 0233/1109] enhance RNTester android config

Summary:
* cliPath is not config right
* root config can be better config instead of a relative path which can easily go wrong if location changed
* DeveloperSupport should only be in debug mode.

* make https://github.com/facebook/react-native/pull/18732 change on local.
* config signingConfig
* execute `./gradlew :RNTester:android:app:assembleRelease`, and run app on device to check everything is fine.

none

[GENERAL][ENHANCEMENT][RNTester]
Closes https://github.com/facebook/react-native/pull/18746

Differential Revision: D7548846

Pulled By: hramos

fbshipit-source-id: 8943f84a6c99456477dff2deeaacc96f093b2e09
---
 RNTester/android/app/build.gradle                              | 3 ++-
 .../java/com/facebook/react/uiapp/RNTesterApplication.java     | 2 +-
 2 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index bc001b26aca5..5e5503b5eb7c 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -58,9 +58,10 @@ import com.android.build.OutputFile
  */
 
 project.ext.react = [
+    cliPath: "$rootDir/local-cli/cli.js",
     bundleAssetName: "RNTesterApp.android.bundle",
     entryFile: file("../../js/RNTesterApp.android.js"),
-    root: "../../../",
+    root: "$rootDir",
     inputExcludes: ["android/**", "./**"]
 ]
 
diff --git a/RNTester/android/app/src/main/java/com/facebook/react/uiapp/RNTesterApplication.java b/RNTester/android/app/src/main/java/com/facebook/react/uiapp/RNTesterApplication.java
index b8c61a384ac4..b5eb40277e89 100644
--- a/RNTester/android/app/src/main/java/com/facebook/react/uiapp/RNTesterApplication.java
+++ b/RNTester/android/app/src/main/java/com/facebook/react/uiapp/RNTesterApplication.java
@@ -34,7 +34,7 @@ public String getJSMainModuleName() {
 
     @Override
     public boolean getUseDeveloperSupport() {
-      return true;
+      return BuildConfig.DEBUG;
     }
 
     @Override

From 4b6e9d3dfd213689c5b319a4efee8d4f606d6f9d Mon Sep 17 00:00:00 2001
From: Eric Rozell <erozell@outlook.com>
Date: Sun, 8 Apr 2018 18:06:21 -0700
Subject: [PATCH 0234/1109] Revert "Remove Platform check from WebSocket
 module"

Summary:
This reverts commit b9be28915cf323eb36f1d7c77821cdf994954074.

Thank you for sending the PR! We appreciate you spending the time to work on these changes.
Help us understand your motivation by explaining why you decided to make this change.

<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

Fix #18696

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Run Jest tests.
Run WebSocket example from RNTester on Android.

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[CATEGORY] [TYPE] [LOCATION] - Message

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
[ANDROID][BUGFIX][WebSocketModule] - revert change that regresses WebSocketModule
Closes https://github.com/facebook/react-native/pull/18733

Differential Revision: D7548850

Pulled By: hramos

fbshipit-source-id: b8c79810c1cd6e5a30ec4118bd5ff8ad719f04b9
---
 Libraries/WebSocket/WebSocket.js | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/Libraries/WebSocket/WebSocket.js b/Libraries/WebSocket/WebSocket.js
index 021e42507e5d..1b401d236c28 100644
--- a/Libraries/WebSocket/WebSocket.js
+++ b/Libraries/WebSocket/WebSocket.js
@@ -14,6 +14,7 @@ const EventTarget = require('event-target-shim');
 const NativeEventEmitter = require('NativeEventEmitter');
 const BlobManager = require('BlobManager');
 const NativeModules = require('NativeModules');
+const Platform = require('Platform');
 const WebSocketEvent = require('WebSocketEvent');
 
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
@@ -205,7 +206,7 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
   }
 
   _close(code?: number, reason?: string): void {
-    if (WebSocketModule.close.length === 3) {
+    if (Platform.OS === 'android') {
       // See https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent
       const statusCode = typeof code === 'number' ? code : CLOSE_NORMAL;
       const closeReason = typeof reason === 'string' ? reason : '';

From bfcfe7961db0970e2575eafe2f3c9c668bd8940d Mon Sep 17 00:00:00 2001
From: Gabriele Mondada <gmondada@recolive.com>
Date: Sun, 8 Apr 2018 22:57:49 -0700
Subject: [PATCH 0235/1109] fix use of C++ syntax in an header file

Summary:
All public header files can be included from Obj-C and Swift, except RCTSurfaceSizeMeasureMode.h which contains C++ code.

Change is trivial and can be validated by review.

None.

[IOS][BUGFIX][{RCTSurfaceSizeMeasureMode.h}] - fix use of C++ syntax in an header file that could be included from Obj-C and Swift
Closes https://github.com/facebook/react-native/pull/18730

Differential Revision: D7550290

Pulled By: shergin

fbshipit-source-id: 3835e2c57697a067ff94afdaeaca06bce132ef66
---
 .../RCTSurfaceHostingView.mm                  |  8 ++++----
 .../RCTSurfaceSizeMeasureMode.h               |  4 ++--
 .../RCTSurfaceSizeMeasureMode.mm              | 20 +++++++++----------
 3 files changed, 16 insertions(+), 16 deletions(-)

diff --git a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.mm b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.mm
index 9eb41ff0b2d0..f8c3a5d69813 100644
--- a/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.mm
+++ b/React/Base/Surface/SurfaceHostingView/RCTSurfaceHostingView.mm
@@ -70,8 +70,8 @@ - (void)setFrame:(CGRect)frame
   RCTSurfaceMinimumSizeAndMaximumSizeFromSizeAndSizeMeasureMode(
     self.bounds.size,
     _sizeMeasureMode,
-    minimumSize,
-    maximumSize
+    &minimumSize,
+    &maximumSize
   );
 
   [_surface setMinimumSize:minimumSize
@@ -107,8 +107,8 @@ - (CGSize)sizeThatFits:(CGSize)size
   RCTSurfaceMinimumSizeAndMaximumSizeFromSizeAndSizeMeasureMode(
     size,
     _sizeMeasureMode,
-    minimumSize,
-    maximumSize
+    &minimumSize,
+    &maximumSize
   );
 
   return [_surface sizeThatFitsMinimumSize:minimumSize
diff --git a/React/Base/Surface/SurfaceHostingView/RCTSurfaceSizeMeasureMode.h b/React/Base/Surface/SurfaceHostingView/RCTSurfaceSizeMeasureMode.h
index d463d36d091a..ead7429b5574 100644
--- a/React/Base/Surface/SurfaceHostingView/RCTSurfaceSizeMeasureMode.h
+++ b/React/Base/Surface/SurfaceHostingView/RCTSurfaceSizeMeasureMode.h
@@ -28,6 +28,6 @@ typedef NS_OPTIONS(NSInteger, RCTSurfaceSizeMeasureMode) {
 RCT_EXTERN void RCTSurfaceMinimumSizeAndMaximumSizeFromSizeAndSizeMeasureMode(
   CGSize size,
   RCTSurfaceSizeMeasureMode sizeMeasureMode,
-  CGSize &minimumSize,
-  CGSize &maximumSize
+  CGSize *minimumSize,
+  CGSize *maximumSize
 );
diff --git a/React/Base/Surface/SurfaceHostingView/RCTSurfaceSizeMeasureMode.mm b/React/Base/Surface/SurfaceHostingView/RCTSurfaceSizeMeasureMode.mm
index 5d1689b1b369..946b027d8c0a 100644
--- a/React/Base/Surface/SurfaceHostingView/RCTSurfaceSizeMeasureMode.mm
+++ b/React/Base/Surface/SurfaceHostingView/RCTSurfaceSizeMeasureMode.mm
@@ -12,25 +12,25 @@
 void RCTSurfaceMinimumSizeAndMaximumSizeFromSizeAndSizeMeasureMode(
   CGSize size,
   RCTSurfaceSizeMeasureMode sizeMeasureMode,
-  CGSize &minimumSize,
-  CGSize &maximumSize
+  CGSize *minimumSize,
+  CGSize *maximumSize
 ) {
-  minimumSize = CGSizeZero;
-  maximumSize = CGSizeMake(CGFLOAT_MAX, CGFLOAT_MAX);
+  *minimumSize = CGSizeZero;
+  *maximumSize = CGSizeMake(CGFLOAT_MAX, CGFLOAT_MAX);
 
   if (sizeMeasureMode & RCTSurfaceSizeMeasureModeWidthExact) {
-    minimumSize.width = size.width;
-    maximumSize.width = size.width;
+    minimumSize->width = size.width;
+    maximumSize->width = size.width;
   }
   else if (sizeMeasureMode & RCTSurfaceSizeMeasureModeWidthAtMost) {
-    maximumSize.width = size.width;
+    maximumSize->width = size.width;
   }
 
   if (sizeMeasureMode & RCTSurfaceSizeMeasureModeHeightExact) {
-    minimumSize.height = size.height;
-    maximumSize.height = size.height;
+    minimumSize->height = size.height;
+    maximumSize->height = size.height;
   }
   else if (sizeMeasureMode & RCTSurfaceSizeMeasureModeHeightAtMost) {
-    maximumSize.height = size.height;
+    maximumSize->height = size.height;
   }
 }

From 43014eaf1992c0b6d8610ba52e1bfea31d00ffe6 Mon Sep 17 00:00:00 2001
From: Matt Oakes <hello@mattoakes.net>
Date: Mon, 9 Apr 2018 11:15:22 -0700
Subject: [PATCH 0236/1109] Fix #18279: Add 'addNetworkingHandler' to jest mock
 setup

Summary:
Fixes #18279 by adding the correct methods to the jest mocks setup file.

Test by no longer including the workarounds in [issue comments](https://github.com/facebook/react-native/issues/18279#issuecomment-374177940). A [comment from hramos](https://github.com/facebook/react-native/issues/18279#issuecomment-371914037) mentioned improving the test coverage as well, but I wasn't certain how to achieve that.

[GENERAL] [BUGFIX] [BlobManager] - Fixed the jest mocks to avoid breaking tests
Closes https://github.com/facebook/react-native/pull/18718

Differential Revision: D7542458

Pulled By: hramos

fbshipit-source-id: 77c9c7cae77971d62e878c4832b2e1d205131e8f
---
 jest/setup.js | 1 +
 1 file changed, 1 insertion(+)

diff --git a/jest/setup.js b/jest/setup.js
index 0d4553b3f756..52916060777e 100644
--- a/jest/setup.js
+++ b/jest/setup.js
@@ -297,6 +297,7 @@ const mockNativeModules = {
   BlobModule: {
     BLOB_URI_SCHEME: 'content',
     BLOB_URI_HOST: null,
+    addNetworkingHandler: jest.fn(),
     enableBlobSupport: jest.fn(),
     disableBlobSupport: jest.fn(),
     createFromParts: jest.fn(),

From 0934c1778f0e3c0b691e1a3ca2df1d486eb905dd Mon Sep 17 00:00:00 2001
From: Angly Cat <angly.cat@gmail.com>
Date: Mon, 9 Apr 2018 12:24:39 -0700
Subject: [PATCH 0237/1109] Fix installing step of `run-ios` command

Summary:
To date if you create a new `react-native@0.55.0` project and try to build/run it for iOS via CLI, e.g. by running:

```
$ react-native init test
$ cd test
$ react-native run-ios --no-packager
```

the build would succeed, but installing will fail afterwards:

```
** BUILD SUCCEEDED **

Installing Build/Products/Debug-iphonesimulator/test.app
An error was encountered processing the command (domain=NSPOSIXErrorDomain, code=2):
Failed to install the requested application
An application bundle was not found at the provided path.
Provide a valid path to the desired application bundle.
Print: Entry, ":CFBundleIdentifier", Does Not Exist

Command failed: /usr/libexec/PlistBuddy -c Print:CFBundleIdentifier Build/Products/Debug-iphonesimulator/test.app/Info.plist
Print: Entry, ":CFBundleIdentifier", Does Not Exist
```

This fail happens because `/usr/libexec/PlistBuddy` can't find `Info.plist` file at the provided path.

This is a regression introduced by changes from PR #17963 (accepted in https://github.com/facebook/react-native/commit/5447ca67076a110e2b0df03b014f53d1df4646ab). If you execute test plan from that PR, it would fail.

As per why:

By default, `run-ios` process's working directory is `$PROJECT_DIR/ios`.

According to [this line in `runIOS.js`](https://github.com/facebook/react-native/blob/3cd2b4342653d0cc6edfc9e7d436d73bfb4f139f/local-cli/runIOS/runIOS.js#L184), `xcodebuild` places all artifacts in `build` directory.

And the default Xcode paths for products is `Build/Products` (at least of Xcode 9.2 which I use, and Xcode 9.3 which I tested this with also).

So, the required `Info.plist` file is actually being created at `$PROJECT_DIR/ios/build/Build/Products/Debug-iphonesimulator/test.app/Info.plist` (with double `build`, the first from `derivedDataPath` key, the second from default products path). Relatively to `run-ios` process's working directory, the path of the file is `build/Build/Products/Debug-iphonesimulator/test.app/Info.plist`.

PR #17963 changed correct path to incorrect, thus introducing this regression.

If changes from that PR are reverted, CLI doesn't fail on install step.

I catch this error on both existing project and a freshly created test project. I can build/run an app from Xcode just fine, but running from CLI still would fail. The other workaround is to change path of products artifacts in Xcode, which is user settings and therefore can't be commited to a project's repo with VCS.

Run:

```
$ react-native init test
$ cd test
$ react-native run-ios --no-packager
```

Ensure that it doesn't fail on install step and produce output similar to this:

```
Installing build/Build/Products/Debug-iphonesimulator/test.app
Launching org.reactjs.native.example.test
```

[CLI][BUGFIX][local-cli/runIOS/runIOS.js] - Fix failing of `run-ios` command on install step
Closes https://github.com/facebook/react-native/pull/18700

Differential Revision: D7555096

Pulled By: hramos

fbshipit-source-id: d877b867e89256f4356f22781d78308affbb9d9c
---
 local-cli/runIOS/runIOS.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/local-cli/runIOS/runIOS.js b/local-cli/runIOS/runIOS.js
index de72569de6e4..61b6795d5ab5 100644
--- a/local-cli/runIOS/runIOS.js
+++ b/local-cli/runIOS/runIOS.js
@@ -24,7 +24,7 @@ const getBuildPath = function (configuration = 'Debug', appName, isDevice) {
     device = 'iphonesimulator';
   }
 
-  return `Build/Products/${configuration}-${device}/${appName}.app`;
+  return `build/Build/Products/${configuration}-${device}/${appName}.app`;
 };
 const xcprettyAvailable = function() {
   try {

From 722f88ca9058c5d902c416b826a7a7ab347326b8 Mon Sep 17 00:00:00 2001
From: Andrew Kriger <akriger@womackelectric.com>
Date: Mon, 9 Apr 2018 16:57:54 -0700
Subject: [PATCH 0238/1109] Adds Android click sound to Touchables

Summary:
Android apps play a touch sound on press, as long as you have "Touch sounds" enabled in the settings. As and Android user, when building my app using React Native, one of the first things I noticed was that there were not any touch sounds. This is missing from React Native and there have been multiple PRs to have this implemented, but no success.

This PR iterates over [#6825](https://github.com/facebook/react-native/pull/6825) and [#11136](https://github.com/facebook/react-native/pull/11136)

This PR keeps it simple by only implementing the enhancement for Android, as iOS apps typically do not use touch sounds, and follows the users' system settings for whether or not the sound is played.

I have manually tested this on multiple devices and emulators with zero problems

[ANDROID] [ENHANCEMENT] [UIManagerModule.java]- Adds Android click sound to touchables

[ANDROID] [ENHANCEMENT] [Touchable] - Adds Android click sound to touchables
Closes https://github.com/facebook/react-native/pull/17183

Differential Revision: D7560327

Pulled By: hramos

fbshipit-source-id: ce1094c437541bc677c7d64b0dba343dd9574422
---
 Libraries/Components/Touchable/Touchable.js            |  9 ++++++++-
 .../com/facebook/react/uimanager/UIManagerModule.java  | 10 ++++++++++
 2 files changed, 18 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/Touchable/Touchable.js b/Libraries/Components/Touchable/Touchable.js
index 00a82cd64ac6..f39457b82725 100644
--- a/Libraries/Components/Touchable/Touchable.js
+++ b/Libraries/Components/Touchable/Touchable.js
@@ -741,6 +741,9 @@ const TouchableMixin = {
           this._startHighlight(e);
           this._endHighlight(e);
         }
+        if (Platform.OS === 'android') {
+          this._playTouchSound();
+        }
         this.touchableHandlePress(e);
       }
     }
@@ -748,7 +751,11 @@ const TouchableMixin = {
     this.touchableDelayTimeout && clearTimeout(this.touchableDelayTimeout);
     this.touchableDelayTimeout = null;
   },
-
+  
+  _playTouchSound: function() {
+    UIManager.playTouchSound();
+  },
+  
   _startHighlight: function(e) {
     this._savePressInLocation(e);
     this.touchableHandleActivePressIn && this.touchableHandleActivePressIn(e);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 57430f3d07e7..3ef612874938 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -12,6 +12,8 @@
 
 import android.content.ComponentCallbacks2;
 import android.content.res.Configuration;
+import android.content.Context;
+import android.media.AudioManager;
 import com.facebook.common.logging.FLog;
 import com.facebook.debug.holder.PrinterHolder;
 import com.facebook.debug.tags.ReactDebugOverlayTags;
@@ -584,6 +586,14 @@ public void clearJSResponder() {
   public void dispatchViewManagerCommand(int reactTag, int commandId, ReadableArray commandArgs) {
     mUIImplementation.dispatchViewManagerCommand(reactTag, commandId, commandArgs);
   }
+  
+  @ReactMethod
+  public void playTouchSound() {
+    AudioManager audioManager = (AudioManager) getReactApplicationContext().getSystemService(Context.AUDIO_SERVICE);
+    if (audioManager != null) {
+      audioManager.playSoundEffect(AudioManager.FX_KEY_CLICK);
+    }
+  }
 
   /**
    * Show a PopupMenu.

From a8e3c7f5780516eb0297830632862484ad032c10 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Mon, 9 Apr 2018 18:39:48 -0700
Subject: [PATCH 0239/1109] Yolo Delete ReactNativePropRegistry

Summary:
Changed StyleSheet.create to be the identity function. We no longer hide it behind an opaque number. Better for types and perf since we don't use it.

I don't really know if we have/need any safer way of rolling this out than just landing it.

It can break if the object passed to StyleSheet.create is mutated afterwards but that isn't a practice anywhere I've seen.

Reviewed By: sophiebits

Differential Revision: D7530023

fbshipit-source-id: bc1afa879c5a5d9cd95cb13bc8ff3347b3622851
---
 .../Renderer/shims/ReactNativePropRegistry.js | 18 -----------
 Libraries/StyleSheet/StyleSheet.js            | 32 +++++++++----------
 Libraries/StyleSheet/StyleSheetTypes.js       |  4 ---
 .../StyleSheet/__tests__/flattenStyle-test.js |  2 +-
 Libraries/StyleSheet/flattenStyle.js          | 19 ++---------
 jest/setup.js                                 |  6 +---
 6 files changed, 20 insertions(+), 61 deletions(-)
 delete mode 100644 Libraries/Renderer/shims/ReactNativePropRegistry.js

diff --git a/Libraries/Renderer/shims/ReactNativePropRegistry.js b/Libraries/Renderer/shims/ReactNativePropRegistry.js
deleted file mode 100644
index 1ffd01057d51..000000000000
--- a/Libraries/Renderer/shims/ReactNativePropRegistry.js
+++ /dev/null
@@ -1,18 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule ReactNativePropRegistry
- * @flow
- */
-
-'use strict';
-
-const {
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-} = require('ReactNative');
-
-module.exports =
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactNativePropRegistry;
diff --git a/Libraries/StyleSheet/StyleSheet.js b/Libraries/StyleSheet/StyleSheet.js
index ec20623d8a27..ff9a88a088aa 100644
--- a/Libraries/StyleSheet/StyleSheet.js
+++ b/Libraries/StyleSheet/StyleSheet.js
@@ -11,14 +11,12 @@
 'use strict';
 
 const PixelRatio = require('PixelRatio');
-const ReactNativePropRegistry = require('ReactNativePropRegistry');
 const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
 const StyleSheetValidation = require('StyleSheetValidation');
 
 const flatten = require('flattenStyle');
 
 import type {
-  ____StyleSheetInternalStyleIdentifier_Internal as StyleSheetInternalStyleIdentifier,
   ____Styles_Internal,
   ____DangerouslyImpreciseStyle_Internal,
   ____DangerouslyImpreciseStyleProp_Internal,
@@ -171,16 +169,16 @@ if (hairlineWidth === 0) {
   hairlineWidth = 1 / PixelRatio.get();
 }
 
-const absoluteFillObject: LayoutStyle = {
+const absoluteFill: LayoutStyle = {
   position: 'absolute',
   left: 0,
   right: 0,
   top: 0,
   bottom: 0,
 };
-const absoluteFill: StyleSheetInternalStyleIdentifier = ReactNativePropRegistry.register(
-  absoluteFillObject,
-); // This also freezes it
+if (__DEV__) {
+  Object.freeze(absoluteFill);
+}
 
 /**
  * A StyleSheet is an abstraction similar to CSS StyleSheets
@@ -253,7 +251,7 @@ module.exports = {
    * so `absoluteFill` can be used for convenience and to reduce duplication of these repeated
    * styles.
    */
-  absoluteFill,
+  absoluteFill: (absoluteFill: any), // TODO: This should be updated after we fix downstream Flow sites.
 
   /**
    * Sometimes you may want `absoluteFill` but with a couple tweaks - `absoluteFillObject` can be
@@ -267,7 +265,7 @@ module.exports = {
    *     },
    *   });
    */
-  absoluteFillObject,
+  absoluteFillObject: absoluteFill,
 
   /**
    * Combines two styles such that `style2` will override any styles in `style1`.
@@ -361,14 +359,16 @@ module.exports = {
   /**
    * Creates a StyleSheet style reference from the given object.
    */
-  create<+S: ____Styles_Internal>(
-    obj: S,
-  ): $ObjMap<S, (Object) => StyleSheetInternalStyleIdentifier> {
-    const result = {};
-    for (const key in obj) {
-      StyleSheetValidation.validateStyle(key, obj);
-      result[key] = obj[key] && ReactNativePropRegistry.register(obj[key]);
+  create<+S: ____Styles_Internal>(obj: S): $ObjMap<S, (Object) => any> {
+    // TODO: This should return S as the return type. But first,
+    // we need to codemod all the callsites that are typing this
+    // return value as a number (even though it was opaque).
+    if (__DEV__) {
+      for (const key in obj) {
+        StyleSheetValidation.validateStyle(key, obj);
+        Object.freeze(obj[key]);
+      }
     }
-    return result;
+    return obj;
   },
 };
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index 1e359e8b515c..cd80f8b8d6e0 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -13,8 +13,6 @@
 
 const AnimatedNode = require('AnimatedNode');
 
-export opaque type ____StyleSheetInternalStyleIdentifier_Internal: number = number;
-
 export type ColorValue = null | string;
 export type DimensionValue = null | number | string | AnimatedNode;
 
@@ -224,8 +222,6 @@ type GenericStyleProp<+T> =
   | null
   | void
   | T
-  | ____StyleSheetInternalStyleIdentifier_Internal
-  | number
   | false
   | ''
   | $ReadOnlyArray<GenericStyleProp<T>>;
diff --git a/Libraries/StyleSheet/__tests__/flattenStyle-test.js b/Libraries/StyleSheet/__tests__/flattenStyle-test.js
index 2f0fdcc0fb0a..76ce2822d900 100644
--- a/Libraries/StyleSheet/__tests__/flattenStyle-test.js
+++ b/Libraries/StyleSheet/__tests__/flattenStyle-test.js
@@ -150,7 +150,7 @@ describe('flattenStyle', () => {
   it('should ignore invalid class names', () => {
     var invalid = flattenStyle(1234, null);
 
-    expect(invalid).toEqual({});
+    expect(invalid).toEqual(undefined);
     // Invalid class name 1234 skipping ...
   });
 });
diff --git a/Libraries/StyleSheet/flattenStyle.js b/Libraries/StyleSheet/flattenStyle.js
index 3ef381d0b6a2..176f5492a7e7 100644
--- a/Libraries/StyleSheet/flattenStyle.js
+++ b/Libraries/StyleSheet/flattenStyle.js
@@ -10,35 +10,20 @@
  */
 'use strict';
 
-var ReactNativePropRegistry;
-
 import type {
   DangerouslyImpreciseStyle,
   DangerouslyImpreciseStyleProp,
 } from 'StyleSheet';
 
-function getStyle(style) {
-  if (ReactNativePropRegistry === undefined) {
-    ReactNativePropRegistry = require('ReactNativePropRegistry');
-  }
-  if (typeof style === 'number') {
-    return ReactNativePropRegistry.getByID(style);
-  }
-  return style;
-}
-
 function flattenStyle(
   style: ?DangerouslyImpreciseStyleProp,
 ): ?DangerouslyImpreciseStyle {
-  if (style == null) {
+  if (style === null || typeof style !== 'object') {
     return undefined;
   }
 
   if (!Array.isArray(style)) {
-    /* $FlowFixMe(>=0.63.0 site=react_native_fb) This comment suppresses an
-     * error found when Flow v0.63 was deployed. To see the error delete this
-     * comment and run Flow. */
-    return getStyle(style);
+    return style;
   }
 
   var result = {};
diff --git a/jest/setup.js b/jest/setup.js
index 52916060777e..25fed46877e9 100644
--- a/jest/setup.js
+++ b/jest/setup.js
@@ -324,11 +324,7 @@ Object.keys(mockNativeModules).forEach(module => {
 });
 
 jest
-  .doMock('NativeModules', () => mockNativeModules)
-  .doMock('ReactNativePropRegistry', () => ({
-    register: id => id,
-    getByID: () => mockEmptyObject,
-  }));
+  .doMock('NativeModules', () => mockNativeModules);
 
 jest.doMock('requireNativeComponent', () => {
   const React = require('react');

From b4c71361d953bb743205b72c0e5f5844983b3ed2 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Tue, 10 Apr 2018 09:09:57 -0700
Subject: [PATCH 0240/1109] Don't freeze null

Reviewed By: acdlite

Differential Revision: D7567032

fbshipit-source-id: ea9c826d572371748c6e9b5defbb92b427d83bee
---
 Libraries/StyleSheet/StyleSheet.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/Libraries/StyleSheet/StyleSheet.js b/Libraries/StyleSheet/StyleSheet.js
index ff9a88a088aa..5aab99d15762 100644
--- a/Libraries/StyleSheet/StyleSheet.js
+++ b/Libraries/StyleSheet/StyleSheet.js
@@ -366,7 +366,9 @@ module.exports = {
     if (__DEV__) {
       for (const key in obj) {
         StyleSheetValidation.validateStyle(key, obj);
-        Object.freeze(obj[key]);
+        if (obj[key]) {
+          Object.freeze(obj[key]);
+        }
       }
     }
     return obj;

From 2f1421dec7cd3a35779caceac108e872033c7d72 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Bj=C3=B8rn-Erik=20Andreasen?= <betezett@gmail.com>
Date: Tue, 10 Apr 2018 10:33:25 -0700
Subject: [PATCH 0241/1109] Fix for scrollview android

Summary:
Trying this again with a fresh pullrequest as the old one kept having issued due to rebasing.

Fixes #16635
the issue is a little serious if you use a scrollview which contains textinput, you will never get a chance to input something since keyboard will always be dismissed because of on-drag event if your scroll-view use the property: keyboardDismissMode ='on-drag'

verify the issue #16635 and tested this fix worked

[ANDROID] [BUGFIX] [ScrollView] - Check that isTouching is also set when dismissing keyboard with on-drag android.
Closes https://github.com/facebook/react-native/pull/18785

Differential Revision: D7569815

Pulled By: hramos

fbshipit-source-id: 2a07369297ce9ce5a7714e513ccb480ee7011a4d
---
 Libraries/Components/ScrollView/ScrollView.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index bc57f5cb400b..2d9d031027ca 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -681,7 +681,7 @@ const ScrollView = createReactClass({
       }
     }
     if (Platform.OS === 'android') {
-      if (this.props.keyboardDismissMode === 'on-drag') {
+      if (this.props.keyboardDismissMode === 'on-drag' && this.state.isTouching) {
         dismissKeyboard();
       }
     }

From 4ebb57b0bae83dadf07a5fe9ce528796b1bb35b5 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:28 -0700
Subject: [PATCH 0242/1109] Fabric: `ShadowNode.revision_` field is now private

Summary: It prevents accidental access to the variable.

Reviewed By: fkgozali

Differential Revision: D7467789

fbshipit-source-id: fa026734f58f0039e9b6d401751e022a9ae2431d
---
 ReactCommon/fabric/core/shadownode/ShadowNode.h | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 4045be8462e6..2efadda40b2d 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -81,7 +81,15 @@ class ShadowNode:
   SharedProps props_;
   SharedShadowNodeSharedList children_;
   WeakShadowNode sourceNode_;
-  int revision_;
+
+private:
+
+  /*
+   * A number of the generation of the ShadowNode instance;
+   * is used and useful for debug-printing purposes *only*.
+   * Do not access this value in any circumstances.
+   */
+  const int revision_;
 };
 
 } // namespace react

From 1f969d34404175c04eb5a579b6bb886c8493c170 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:30 -0700
Subject: [PATCH 0243/1109] Fabric: Equality operators for ShadowNode

Summary: Test for equality will be used in ShadowNode Tree Diffing algorithm.

Reviewed By: fkgozali

Differential Revision: D7467802

fbshipit-source-id: 5383add9fc7d7e4a772ca16e70a54f7e0c36823a
---
 ReactCommon/fabric/core/shadownode/ShadowNode.cpp | 15 +++++++++++++++
 ReactCommon/fabric/core/shadownode/ShadowNode.h   | 12 ++++++++++++
 2 files changed, 27 insertions(+)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 2313be859eef..c2da0db17ee5 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -116,6 +116,21 @@ void ShadowNode::clearSourceNode() {
   sourceNode_.reset();
 }
 
+#pragma mark - Equality
+
+bool ShadowNode::operator==(const ShadowNode& rhs) const {
+  // Note: Child nodes are not considered as part of instance's value
+  // and/or identity.
+  return
+    tag_ == rhs.tag_ &&
+    rootTag_ == rhs.rootTag_ &&
+    props_ == rhs.props_;
+}
+
+bool ShadowNode::operator!=(const ShadowNode& rhs) const {
+  return !(*this == rhs);
+}
+
 #pragma mark - DebugStringConvertible
 
 std::string ShadowNode::getDebugName() const {
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 2efadda40b2d..f03acb107ee5 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -67,6 +67,18 @@ class ShadowNode:
   void replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild);
   void clearSourceNode();
 
+#pragma mark - Equality
+
+  /*
+   * Equality operators.
+   * Use this to compare `ShadowNode`s values for equality (and non-equality).
+   * Same values indicates that nodes must not produce mutation instructions
+   * during tree diffing process.
+   * Child nodes are not considered as part of the value.
+   */
+  virtual bool operator==(const ShadowNode& rhs) const;
+  virtual bool operator!=(const ShadowNode& rhs) const;
+
 #pragma mark - DebugStringConvertible
 
   std::string getDebugName() const override;

From c83aeaaf821c3905c273c826eebe8d032ea01800 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:33 -0700
Subject: [PATCH 0244/1109] Fabric: Forgotten compiler directive and include

Summary: Trivial. Those nits prevent cause compilation errors in some configurations.

Reviewed By: fkgozali

Differential Revision: D7467794

fbshipit-source-id: cbda285748374fd941a0b1ca6718d702ca2d6d82
---
 ReactCommon/exceptions/ExceptionManager.h | 2 ++
 ReactCommon/fabric/graphics/Geometry.h    | 2 ++
 2 files changed, 4 insertions(+)

diff --git a/ReactCommon/exceptions/ExceptionManager.h b/ReactCommon/exceptions/ExceptionManager.h
index 842975b3ba87..278179c67dec 100644
--- a/ReactCommon/exceptions/ExceptionManager.h
+++ b/ReactCommon/exceptions/ExceptionManager.h
@@ -5,6 +5,8 @@
  * LICENSE file in the root directory of this source tree.
  */
 
+#pragma once
+
 #include <exception>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index 8471b1d1a7db..6c2b0f041fae 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -2,6 +2,8 @@
 
 #pragma once
 
+#include <tuple>
+
 #include <CoreGraphics/CGBase.h>
 
 namespace facebook {

From 7e84cadc9c933fce19d2f9cc580f76b1e0d54089 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:35 -0700
Subject: [PATCH 0245/1109] Fabric: Refined conception and usage of Sealable

Summary: Slightly new approach: Some non-const methods might not always mutate objects, so sometimes we should call `ensureUnsealed()` only inside conditional branches where we actually mutate an instance.

Reviewed By: fkgozali

Differential Revision: D7467793

fbshipit-source-id: 1b9f229cf6816e54e0df36699a571fdb612d3c3c
---
 ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp | 7 ++++---
 ReactCommon/fabric/core/primitives/Sealable.h           | 8 ++++++--
 2 files changed, 10 insertions(+), 5 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index 8148f00dff00..0e2652efc887 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -23,6 +23,8 @@ bool LayoutableShadowNode::setLayoutMetrics(LayoutMetrics layoutMetrics) {
     return false;
   }
 
+  ensureUnsealed();
+
   layoutMetrics_ = layoutMetrics;
   return true;
 }
@@ -60,8 +62,6 @@ Float LayoutableShadowNode::lastBaseline(Size size) const {
 }
 
 void LayoutableShadowNode::layout(LayoutContext layoutContext) {
-  ensureUnsealed();
-
   layoutChildren(layoutContext);
 
   for (auto child : getChildren()) {
@@ -69,6 +69,8 @@ void LayoutableShadowNode::layout(LayoutContext layoutContext) {
       continue;
     }
 
+    ensureUnsealed();
+
     // The assumption:
     // All `sealed` children were replaced with not-yet-sealed clones
     // somewhere in `layoutChildren`.
@@ -89,7 +91,6 @@ void LayoutableShadowNode::layout(LayoutContext layoutContext) {
 }
 
 void LayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
-  ensureUnsealed();
   // Default implementation does nothing.
 }
 
diff --git a/ReactCommon/fabric/core/primitives/Sealable.h b/ReactCommon/fabric/core/primitives/Sealable.h
index e0d168e44e08..7f07819a1ff7 100644
--- a/ReactCommon/fabric/core/primitives/Sealable.h
+++ b/ReactCommon/fabric/core/primitives/Sealable.h
@@ -31,7 +31,12 @@ namespace react {
  *
  * How to use:
  *   1. Inherit your class from `Sealable`.
- *   2. Call `ensureUnsealed()` from all non-const methods.
+ *   2. Call `ensureUnsealed()` in all cases where the object might be mutated:
+ *      a. At the beginning of all *always* mutating `non-const` methods;
+ *      b. Right before the place where actual mutation happens in all *possible*
+ *         mutating `non-const` methods;
+ *      c. Right after performing `const_cast`. (Optionally. This is not strictly
+ *         necessary but might help detect problems earlier.)
  *   3. Call `seal()` at some point from which any modifications
  *      must be prevented.
  */
@@ -55,7 +60,6 @@ class Sealable {
    */
   bool getSealed() const;
 
-protected:
   /*
    * Throws an exception if the object is sealed.
    * Call this from all non-`const` methods.

From dc1a9680de59b68f6efc5d553bf5a8b8382c2c1d Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:40 -0700
Subject: [PATCH 0246/1109] Fabric: Refined TreeMutationInstruction class

Summary: Two additional types of instructions were added and now all of them have explicitly clear semantic.

Reviewed By: fkgozali

Differential Revision: D7467798

fbshipit-source-id: 83c0e774d56975be504aa3fe892035f5f724f809
---
 .../uimanager/TreeMutationInstruction.cpp     | 66 +++++++++++++++----
 .../uimanager/TreeMutationInstruction.h       | 43 +++++++-----
 2 files changed, 79 insertions(+), 30 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
index da60fb83cf01..42882ee6cfc6 100644
--- a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
+++ b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
@@ -12,6 +12,34 @@
 namespace facebook {
 namespace react {
 
+const TreeMutationInstruction TreeMutationInstruction::Create(
+  SharedShadowNode node
+) {
+  assert(node);
+
+  return TreeMutationInstruction(
+    Creation,
+    nullptr,
+    nullptr,
+    node,
+    -1
+  );
+}
+
+const TreeMutationInstruction TreeMutationInstruction::Delete(
+  SharedShadowNode node
+) {
+  assert(node);
+
+  return TreeMutationInstruction(
+    Deletion,
+    nullptr,
+    node,
+    nullptr,
+    -1
+  );
+}
+
 const TreeMutationInstruction TreeMutationInstruction::Insert(
   SharedShadowNode parentNode,
   SharedShadowNode childNode,
@@ -22,7 +50,7 @@ const TreeMutationInstruction TreeMutationInstruction::Insert(
   assert(index != -1);
 
   return TreeMutationInstruction(
-    Inserting,
+    Insertion,
     parentNode,
     nullptr,
     childNode,
@@ -30,7 +58,7 @@ const TreeMutationInstruction TreeMutationInstruction::Insert(
   );
 }
 
-const TreeMutationInstruction TreeMutationInstruction::Delete(
+const TreeMutationInstruction TreeMutationInstruction::Remove(
   SharedShadowNode parentNode,
   SharedShadowNode childNode,
   int index
@@ -40,7 +68,7 @@ const TreeMutationInstruction TreeMutationInstruction::Delete(
   assert(index != -1);
 
   return TreeMutationInstruction(
-    Deleting,
+    Removal,
     parentNode,
     childNode,
     nullptr,
@@ -48,7 +76,7 @@ const TreeMutationInstruction TreeMutationInstruction::Delete(
   );
 }
 
-const TreeMutationInstruction TreeMutationInstruction::Update(
+const TreeMutationInstruction TreeMutationInstruction::Replace(
   SharedShadowNode parentNode,
   SharedShadowNode oldChildNode,
   SharedShadowNode newChildNode,
@@ -60,7 +88,7 @@ const TreeMutationInstruction TreeMutationInstruction::Update(
   assert(index != -1);
 
   return TreeMutationInstruction(
-    Updating,
+    Replacement,
     parentNode,
     oldChildNode,
     newChildNode,
@@ -111,12 +139,16 @@ int TreeMutationInstruction::getIndex() const {
 
 std::string TreeMutationInstruction::getDebugName() const {
   switch (type_) {
-    case Inserting:
-      return "Insert";
-    case Deleting:
+    case Creation:
+      return "Create";
+    case Deletion:
       return "Delete";
-    case Updating:
-      return "Update";
+    case Insertion:
+      return "Insert";
+    case Removal:
+      return "Remove";
+    case Replacement:
+      return "Replace";
   }
 };
 
@@ -124,19 +156,27 @@ SharedDebugStringConvertibleList TreeMutationInstruction::getDebugProps() const
   DebugStringConvertibleOptions options = {.maximumDepth = 1, .format = false};
 
   switch (type_) {
-    case Inserting:
+    case Creation:
+      return SharedDebugStringConvertibleList {
+        std::make_shared<DebugStringConvertibleItem>("node", newChildNode_->getDebugDescription(options)),
+      };
+    case Deletion:
+      return SharedDebugStringConvertibleList {
+        std::make_shared<DebugStringConvertibleItem>("node", oldChildNode_->getDebugDescription(options)),
+      };
+    case Insertion:
       return SharedDebugStringConvertibleList {
         std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("childNode", newChildNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("index", std::to_string(index_))
       };
-    case Deleting:
+    case Removal:
       return SharedDebugStringConvertibleList {
         std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("childNode", oldChildNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("index", std::to_string(index_))
       };
-    case Updating:
+    case Replacement:
       return SharedDebugStringConvertibleList {
         std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("oldChildNode", oldChildNode_->getDebugDescription(options)),
diff --git a/ReactCommon/fabric/uimanager/TreeMutationInstruction.h b/ReactCommon/fabric/uimanager/TreeMutationInstruction.h
index f0e09c17d35b..920cd27f87cb 100644
--- a/ReactCommon/fabric/uimanager/TreeMutationInstruction.h
+++ b/ReactCommon/fabric/uimanager/TreeMutationInstruction.h
@@ -25,6 +25,7 @@ using TreeMutationInstructionList = std::vector<TreeMutationInstruction>;
  * final index of inserted or updated node.
  * The relationship between native view instances and shadow node instances is
  * defined by `tag` value.
+ * Use static methods to instantiate mutation instructions of different types.
  */
 class TreeMutationInstruction:
   public DebugStringConvertible {
@@ -33,10 +34,21 @@ class TreeMutationInstruction:
 #pragma mark - Designated Initializers
 
   /*
-   * Creates and returns an *Insert* instruction with following semantic:
-   *   1. Create a native view for the shadow node if needed;
-   *   2. Unmount the native view from a previous superview if needed;
-   *   3. Mount the native view to the new superview.
+   * Creates and returns an *Creation* instruction.
+   */
+  static const TreeMutationInstruction Create(
+    SharedShadowNode node
+  );
+
+  /*
+   * Creates and returns an *Deletion* instruction.
+   */
+  static const TreeMutationInstruction Delete(
+    SharedShadowNode node
+  );
+
+  /*
+   * Creates and returns an *Insertion* instruction.
    */
   static const TreeMutationInstruction Insert(
     SharedShadowNode parentNode,
@@ -45,23 +57,18 @@ class TreeMutationInstruction:
   );
 
   /*
-   * Creates and returns a *Delete* instruction with following semantic:
-   *   1. Unmount the native view from a previous superview if needed;
-   *   2. Destroy (or return to a recycle pool) the native view.
+   * Creates and returns a *Removal* instruction.
    */
-  static const TreeMutationInstruction Delete(
+  static const TreeMutationInstruction Remove(
     SharedShadowNode parentNode,
     SharedShadowNode childNode,
     int index
   );
   
   /*
-   * Creates and returns an *Update* instruction with following semantic:
-   *   1. Update the presentation of a native view based on the new shadow node;
-   *   2. The exact set of changes are not specified but might contain
-   *      new props and/or new layout (or might be empty).
+   * Creates and returns an *Replacement* instruction.
    */
-  static const TreeMutationInstruction Update(
+  static const TreeMutationInstruction Replace(
     SharedShadowNode parentNode,
     SharedShadowNode oldChildNode,
     SharedShadowNode newChildNode,
@@ -71,9 +78,11 @@ class TreeMutationInstruction:
 #pragma mark - Type
 
   enum Type {
-    Inserting,
-    Deleting,
-    Updating
+    Creation,
+    Deletion,
+    Insertion,
+    Removal,
+    Replacement
   };
 
 #pragma mark - Getters
@@ -98,7 +107,7 @@ class TreeMutationInstruction:
     int index
   );
 
-  Type type_ {Inserting};
+  Type type_ {Creation};
   SharedShadowNode parentNode_ {nullptr};
   SharedShadowNode oldChildNode_ {nullptr};
   SharedShadowNode newChildNode_ {nullptr};

From a38f32a5a6880a5429d1c57dd530b8ad9f0dc79e Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:43 -0700
Subject: [PATCH 0247/1109] Fabric: Couple of ViewProps fields were exposed as
 getters

Summary: We have to have getters for all props/fields.

Reviewed By: mdvacca

Differential Revision: D7467792

fbshipit-source-id: 1492aad2d3398e6c14e0e354047730cf91201175
---
 ReactCommon/fabric/view/ViewProps.cpp | 12 ++++++++++++
 ReactCommon/fabric/view/ViewProps.h   |  5 +++++
 2 files changed, 17 insertions(+)

diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index e3f9f6fddc0d..725c2014bc27 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -45,6 +45,18 @@ void ViewProps::apply(const RawProps &rawProps) {
   }
 }
 
+#pragma mark - Getters
+
+SharedColor ViewProps::getForegroundColor() const {
+  return foregroundColor_;
+}
+
+SharedColor ViewProps::getBackgroundColor() const {
+  return backgroundColor_;
+}
+
+#pragma mark - DebugStringConvertible
+
 SharedDebugStringConvertibleList ViewProps::getDebugProps() const {
   ViewProps defaultProps = {};
 
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
index 89b20dec799f..365d469f746b 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -28,6 +28,11 @@ class ViewProps:
 public:
   void apply(const RawProps &rawProps) override;
 
+#pragma mark - Getters
+
+  SharedColor getForegroundColor() const;
+  SharedColor getBackgroundColor() const;
+
 private:
   int zIndex_ {0};
   float opacity_ {1.0};

From fec0a51e85811d20c84480946d953d6410bb5393 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:46 -0700
Subject: [PATCH 0248/1109] Fabric: Simplified
 `ViewShadowNode::cloneAndReplaceChild`

Summary: Using methods of the base class instead of custom implementation.

Reviewed By: fkgozali

Differential Revision: D7467795

fbshipit-source-id: 4d168b72880f6900bf8b747e1d655c10140e0c79
---
 ReactCommon/fabric/view/ViewShadowNode.cpp | 16 ++--------------
 1 file changed, 2 insertions(+), 14 deletions(-)

diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/view/ViewShadowNode.cpp
index 8bb5f33fdb83..2418279903e3 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.cpp
+++ b/ReactCommon/fabric/view/ViewShadowNode.cpp
@@ -92,26 +92,14 @@ SharedLayoutableShadowNodeList ViewShadowNode::getChildren() const {
 SharedLayoutableShadowNode ViewShadowNode::cloneAndReplaceChild(const SharedLayoutableShadowNode &child) {
   ensureUnsealed();
 
-  // We cannot mutate `children_` in place here because it is a *shared*
-  // data structure which means other `ShadowNodes` might refer to its old value.
-  // So, we have to clone this and only then mutate.
-  auto nonConstChildrenCopy = SharedShadowNodeList(*children_);
-
   auto viewShadowNodeChild = std::dynamic_pointer_cast<const ViewShadowNode>(child);
   assert(viewShadowNodeChild);
-
   auto viewShadowNodeChildClone = std::make_shared<const ViewShadowNode>(viewShadowNodeChild);
+  ShadowNode::replaceChild(viewShadowNodeChild, viewShadowNodeChildClone);
+  return std::static_pointer_cast<const LayoutableShadowNode>(viewShadowNodeChildClone);
 
-  std::replace(
-    nonConstChildrenCopy.begin(),
-    nonConstChildrenCopy.end(),
-    std::static_pointer_cast<const ShadowNode>(viewShadowNodeChild),
-    std::static_pointer_cast<const ShadowNode>(viewShadowNodeChildClone)
-  );
 
-  children_ = std::make_shared<const SharedShadowNodeList>(nonConstChildrenCopy);
 
-  return std::static_pointer_cast<const LayoutableShadowNode>(viewShadowNodeChildClone);
 }
 
 #pragma mark - DebugStringConvertible

From 1a4b6f0b3dbe2bef1ddee0e81fb1fff784737420 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:48 -0700
Subject: [PATCH 0249/1109] Fabric: Overriden equality operator for
 ViewShadowNode

Summary:
Computed `layoutMetrics` are also considered as part of ViewShadowNode's value.
In the future we probably have to add something like `localData` and `imperativeCommands`.
We need all this for diffing algorithm and mointing phase.

Reviewed By: mdvacca

Differential Revision: D7467800

fbshipit-source-id: 8a0dcf1fd2f97dc501d6969cb0b0f6a2c6a648b4
---
 ReactCommon/fabric/view/ViewShadowNode.cpp | 8 ++++++++
 ReactCommon/fabric/view/ViewShadowNode.h   | 4 ++++
 2 files changed, 12 insertions(+)

diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/view/ViewShadowNode.cpp
index 2418279903e3..b8f610c10d5f 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.cpp
+++ b/ReactCommon/fabric/view/ViewShadowNode.cpp
@@ -97,9 +97,17 @@ SharedLayoutableShadowNode ViewShadowNode::cloneAndReplaceChild(const SharedLayo
   auto viewShadowNodeChildClone = std::make_shared<const ViewShadowNode>(viewShadowNodeChild);
   ShadowNode::replaceChild(viewShadowNodeChild, viewShadowNodeChildClone);
   return std::static_pointer_cast<const LayoutableShadowNode>(viewShadowNodeChildClone);
+}
 
+#pragma mark - Equality
 
+bool ViewShadowNode::operator==(const ShadowNode& rhs) const {
+  if (!ShadowNode::operator==(rhs)) {
+    return false;
+  }
 
+  auto &&other = static_cast<const ViewShadowNode&>(rhs);
+  return getLayoutMetrics() == other.getLayoutMetrics();
 }
 
 #pragma mark - DebugStringConvertible
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/view/ViewShadowNode.h
index 4ac446556d77..b80a138fd444 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.h
+++ b/ReactCommon/fabric/view/ViewShadowNode.h
@@ -48,6 +48,10 @@ class ViewShadowNode:
 
   void appendChild(const SharedShadowNode &child);
 
+#pragma mark - Equality
+
+  bool operator==(const ShadowNode& rhs) const override;
+
 #pragma mark - DebugStringConvertible
 
   SharedDebugStringConvertibleList getDebugProps() const override;

From 5dca3e7c7411ca370e0d9911fdef9f3a88dc14b4 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:51 -0700
Subject: [PATCH 0250/1109] Fabric: New approach of mutating ShadowNode's
 children collection

Summary: Previously we recreate a vector with pointers to child nodes every single time we modify the collection. That was okay but recently I realized that the we can  simply make a copy of the vector one time during object construction and then mutate it freely.

Reviewed By: mdvacca

Differential Revision: D7467796

fbshipit-source-id: 660f1706a19ae5f07c34c509f411ce9d67b93b35
---
 .../fabric/core/shadownode/ShadowNode.cpp     | 20 ++++++-------------
 1 file changed, 6 insertions(+), 14 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index c2da0db17ee5..f15964b0b5d9 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -31,7 +31,7 @@ ShadowNode::ShadowNode(
   rootTag_(rootTag),
   instanceHandle_(instanceHandle),
   props_(props),
-  children_(children),
+  children_(std::make_shared<SharedShadowNodeList>(*children)),
   revision_(1) {}
 
 ShadowNode::ShadowNode(
@@ -43,7 +43,7 @@ ShadowNode::ShadowNode(
   rootTag_(shadowNode->rootTag_),
   instanceHandle_(shadowNode->instanceHandle_),
   props_(props ? props : shadowNode->props_),
-  children_(children ? children : shadowNode->children_),
+  children_(std::make_shared<SharedShadowNodeList>(*(children ? children : shadowNode->children_))),
   sourceNode_(shadowNode),
   revision_(shadowNode->revision_ + 1) {}
 
@@ -92,23 +92,15 @@ void ShadowNode::sealRecursive() const {
 void ShadowNode::appendChild(const SharedShadowNode &child) {
   ensureUnsealed();
 
-  // We cannot mutate `children_` in place here because it is a *shared*
-  // data structure which means other `ShadowNodes` might refer to its old value.
-  // So, we have to clone this and only then mutate.
-  auto nonConstChildrenCopy = SharedShadowNodeList(*children_);
-  nonConstChildrenCopy.push_back(child);
-  children_ = std::make_shared<const SharedShadowNodeList>(nonConstChildrenCopy);
+  auto nonConstChildren = std::const_pointer_cast<SharedShadowNodeList>(children_);
+  nonConstChildren->push_back(child);
 }
 
 void ShadowNode::replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild) {
   ensureUnsealed();
 
-  // We cannot mutate `children_` in place here because it is a *shared*
-  // data structure which means other `ShadowNodes` might refer to its old value.
-  // So, we have to clone this and only then mutate.
-  auto nonConstChildrenCopy = SharedShadowNodeList(*children_);
-  std::replace(nonConstChildrenCopy.begin(), nonConstChildrenCopy.end(), oldChild, newChild);
-  children_ = std::make_shared<const SharedShadowNodeList>(nonConstChildrenCopy);
+  auto nonConstChildren = std::const_pointer_cast<SharedShadowNodeList>(children_);
+  std::replace(nonConstChildren->begin(), nonConstChildren->end(), oldChild, newChild);
 }
 
 void ShadowNode::clearSourceNode() {

From ef6b916e48204158f649035d08d2183fafeab00b Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:53 -0700
Subject: [PATCH 0251/1109] Fabric: New approach to manage Yoga's parent/owner
 references

Summary:
The modern Concurent Yoga's concept is:
We have to set parent/owner reference as part of `appendChild` process only if the current reference to parent/owner is `null`.
The motivation:
 * Null-parent indicates that this node was not attached to anything yet;
 * So, in this case there is no any concurrent memory access because we always create and (first time) attach the node on same thread;
 * Simmetrical parent-child relationship indicates that we don't need to (re)clone assosiated ShadowNode (nor Yoga node).

Reviewed By: mdvacca

Differential Revision: D7467791

fbshipit-source-id: 9a7f517380fde3bb00272de18fd5dc13edb52071
---
 .../fabric/view/yoga/YogaLayoutableShadowNode.cpp  | 14 +++++++++++++-
 1 file changed, 13 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 6ad453100e8f..9aadda4d83ca 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -97,6 +97,11 @@ void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child)
   auto nonConstYogaNode = std::const_pointer_cast<YGNode>(yogaNode_);
   auto nonConstChildYogaNode = std::const_pointer_cast<YGNode>(child->yogaNode_);
   nonConstYogaNode->insertChild(nonConstChildYogaNode.get(), nonConstYogaNode->getChildrenCount());
+
+  if (nonConstChildYogaNode->getParent() == nullptr) {
+    child->ensureUnsealed();
+    nonConstChildYogaNode->setParent(nonConstYogaNode.get());
+  }
 }
 
 void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
@@ -211,7 +216,14 @@ void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNo
       continue;
     }
 
-    yogaNodeChildren.push_back((YGNode *)yogaLayoutableShadowNode->yogaNode_.get());
+    YGNode *yogaNodeChild = (YGNode *)yogaLayoutableShadowNode->yogaNode_.get();
+
+    yogaNodeChildren.push_back(yogaNodeChild);
+
+    if (yogaNodeChild->getParent() == nullptr) {
+      yogaLayoutableShadowNode->ensureUnsealed();
+      yogaNodeChild->setParent(&yogaNode);
+    }
   }
 
   yogaNode.setChildren(yogaNodeChildren);

From 0332d475ccfbbe4ec7649e1b80c02a142294a025 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:56 -0700
Subject: [PATCH 0252/1109] Fabric: Refined Yoga's `isDirty` flag management in
 YogaLayoutableShadowNode

Summary:
Motivation:
 * We never should call `markDirtyAndPropogate()` during tree construction/mutation because it might affect trees in different thread/dimentions;
 * In Fabric we basically always have to dirty nodes ourselves manually duting tree construction;
 * In Fabric we don't have "scoped/limited" tree mutations which require recursive dirtying; any mutation is creation of the new tree instance;
 * Default value of the `isDirty` flag is "false", so we have to change this right after creation of Yoga node (and after cloning).

Reviewed By: mdvacca

Differential Revision: D7467797

fbshipit-source-id: 2c9144271dceea6ba2b95173209b99b5d86fbd87
---
 .../fabric/view/yoga/YogaLayoutableShadowNode.cpp | 15 +++++++--------
 1 file changed, 7 insertions(+), 8 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 9aadda4d83ca..71e5ac89b345 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -42,7 +42,7 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   yogaNode->setConfig(suitableYogaConfig().get());
   yogaNode->setStyle(props->getYogaStyle());
   yogaNode->setContext(this);
-  yogaNode->markDirtyAndPropogate();
+  yogaNode->setDirty(true);
   YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(*yogaNode, children);
   yogaNode_ = yogaNode;
 }
@@ -53,8 +53,10 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   const SharedShadowNodeSharedList &children
 ) {
   auto yogaNode = std::make_shared<YGNode>(*shadowNode->yogaNode_);
+  yogaNode->setConfig(suitableYogaConfig().get());
   yogaNode->setContext(this);
   yogaNode->setOwner(nullptr);
+  yogaNode->setDirty(true);
 
   if (props) {
     yogaNode->setStyle(props->getYogaStyle());
@@ -64,8 +66,6 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
     YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(*yogaNode, children);
   }
 
-  yogaNode->markDirtyAndPropogate();
-
   yogaNode_ = yogaNode;
 }
 
@@ -98,9 +98,9 @@ void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child)
   auto nonConstChildYogaNode = std::const_pointer_cast<YGNode>(child->yogaNode_);
   nonConstYogaNode->insertChild(nonConstChildYogaNode.get(), nonConstYogaNode->getChildrenCount());
 
-  if (nonConstChildYogaNode->getParent() == nullptr) {
+  if (nonConstChildYogaNode->getOwner() == nullptr) {
     child->ensureUnsealed();
-    nonConstChildYogaNode->setParent(nonConstYogaNode.get());
+    nonConstChildYogaNode->setOwner(nonConstYogaNode.get());
   }
 }
 
@@ -220,14 +220,13 @@ void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNo
 
     yogaNodeChildren.push_back(yogaNodeChild);
 
-    if (yogaNodeChild->getParent() == nullptr) {
+    if (yogaNodeChild->getOwner() == nullptr) {
       yogaLayoutableShadowNode->ensureUnsealed();
-      yogaNodeChild->setParent(&yogaNode);
+      yogaNodeChild->setOwner(&yogaNode);
     }
   }
 
   yogaNode.setChildren(yogaNodeChildren);
-  yogaNode.markDirtyAndPropogate();
 }
 
 } // namespace react

From b2af59a0f0ff51c292b0f15be5a970f5073092c9 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:45:59 -0700
Subject: [PATCH 0253/1109] Fabric: Diffing Algorithm (computing shadow node
 tree mutation instructions)

Summary:
The first and quite naive implementation of The Diffing algorithm.
The exact set of instructions, their semantic, order, amount, and excessiveness are still unclear.
The concept should be verified by comprehensive testing with working native views rendering layer.

Reviewed By: mdvacca

Differential Revision: D7467790

fbshipit-source-id: 08f2f646e058cac8a4b73bf7b148e2748633348d
---
 .../fabric/uimanager/Differentiator.cpp       | 159 ++++++++++++++++++
 ReactCommon/fabric/uimanager/Differentiator.h |  24 +++
 2 files changed, 183 insertions(+)
 create mode 100644 ReactCommon/fabric/uimanager/Differentiator.cpp
 create mode 100644 ReactCommon/fabric/uimanager/Differentiator.h

diff --git a/ReactCommon/fabric/uimanager/Differentiator.cpp b/ReactCommon/fabric/uimanager/Differentiator.cpp
new file mode 100644
index 000000000000..20ff6add69df
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/Differentiator.cpp
@@ -0,0 +1,159 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include "Differentiator.h"
+
+namespace facebook {
+namespace react {
+
+void calculateMutationInstructions(
+  TreeMutationInstructionList &instructions,
+  SharedShadowNode parentNode,
+  SharedShadowNodeSharedList oldChildNodes,
+  SharedShadowNodeSharedList newChildNodes
+) {
+  // The current version of the algorithm is otimized for simplicity,
+  // not for performance of optimal result.
+
+  // TODO(shergin): Consider to use Minimal Edit Distance algorithm to produce
+  // optimal set of instructions and improve mounting performance.
+  // https://en.wikipedia.org/wiki/Edit_distance
+  // https://www.geeksforgeeks.org/dynamic-programming-set-5-edit-distance/
+
+  if (oldChildNodes == newChildNodes) {
+    return;
+  }
+
+  if (oldChildNodes->size() == 0 && newChildNodes->size() == 0) {
+    return;
+  }
+
+  std::unordered_set<Tag> insertedTags = {};
+  int index = 0;
+
+  TreeMutationInstructionList createInstructions = {};
+  TreeMutationInstructionList deleteInstructions = {};
+  TreeMutationInstructionList insertInstructions = {};
+  TreeMutationInstructionList removeInstructions = {};
+  TreeMutationInstructionList replaceInstructions = {};
+  TreeMutationInstructionList downwardInstructions = {};
+
+  // Stage 1: Collectings Updates
+
+  for (index = 0; index < oldChildNodes->size() && index < newChildNodes->size(); index++) {
+    SharedShadowNode oldChildNode = oldChildNodes->at(index);
+    SharedShadowNode newChildNode = newChildNodes->at(index);
+
+    if (oldChildNode->getTag() != newChildNode->getTag()) {
+      // Totally different nodes, updating is impossible.
+      break;
+    }
+
+    if (*oldChildNode != *newChildNode) {
+      replaceInstructions.push_back(
+        TreeMutationInstruction::Replace(
+          parentNode,
+          oldChildNode,
+          newChildNode,
+          index
+        )
+      );
+    }
+
+    calculateMutationInstructions(
+      downwardInstructions,
+      oldChildNode,
+      oldChildNode->getChildren(),
+      newChildNode->getChildren()
+    );
+  }
+
+  int lastIndexAfterFirstStage = index;
+
+  // Stage 2: Collectings Insertions
+  for (; index < newChildNodes->size(); index++) {
+    SharedShadowNode newChildNode = newChildNodes->at(index);
+
+    insertInstructions.push_back(
+      TreeMutationInstruction::Insert(
+        parentNode,
+        newChildNodes->at(index),
+        index
+      )
+    );
+
+    insertedTags.insert(newChildNode->getTag());
+
+    SharedShadowNode newChildSourceNode = newChildNode->getSourceNode();
+    SharedShadowNodeSharedList newChildSourceChildNodes =
+      newChildSourceNode ? newChildSourceNode->getChildren() : ShadowNode::emptySharedShadowNodeSharedList();
+
+    calculateMutationInstructions(
+      downwardInstructions,
+      newChildNode,
+      newChildSourceChildNodes,
+      newChildNode->getChildren()
+    );
+  }
+
+  // Stage 3: Collectings Deletions and Removals
+  for (index = lastIndexAfterFirstStage; index < oldChildNodes->size(); index++) {
+    SharedShadowNode oldChildNode = oldChildNodes->at(index);
+
+    auto numberOfRemovedTags = insertedTags.erase(oldChildNode->getTag());
+    assert(numberOfRemovedTags == 0 || numberOfRemovedTags == 1);
+
+    if (numberOfRemovedTags != 0) {
+      // The old node *was* (re)inserted,
+      // so we have to generate `remove` instruction.
+      removeInstructions.push_back(
+        TreeMutationInstruction::Remove(
+          parentNode,
+          oldChildNode,
+          index
+        )
+      );
+    } else {
+      // The old node was *not* (re)inserted,
+      // so we have to generate `delete` instruction and apply the algorithm
+      // recursively.
+      deleteInstructions.push_back(
+        TreeMutationInstruction::Delete(
+          oldChildNode
+        )
+      );
+
+      calculateMutationInstructions(
+        downwardInstructions,
+        oldChildNode,
+        oldChildNode->getChildren(),
+        ShadowNode::emptySharedShadowNodeSharedList()
+      );
+    }
+  }
+
+  // Stage 4: Collectings Creations
+  for (index = lastIndexAfterFirstStage; index < newChildNodes->size(); index++) {
+    SharedShadowNode newChildNode = newChildNodes->at(index);
+    if (insertedTags.find(newChildNode->getTag()) == insertedTags.end()) {
+      // The new node was (re)inserted, so there is no need to create it.
+      continue;
+    }
+
+    createInstructions.push_back(
+      TreeMutationInstruction::Create(
+        newChildNode
+      )
+    );
+  }
+
+  // All instructions in an optimal order:
+  instructions.insert(instructions.end(), replaceInstructions.begin(), replaceInstructions.end());
+  instructions.insert(instructions.end(), removeInstructions.begin(), removeInstructions.end());
+  instructions.insert(instructions.end(), deleteInstructions.begin(), deleteInstructions.end());
+  instructions.insert(instructions.end(), createInstructions.begin(), createInstructions.end());
+  instructions.insert(instructions.end(), insertInstructions.begin(), insertInstructions.end());
+  instructions.insert(instructions.end(), downwardInstructions.begin(), downwardInstructions.end());
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/Differentiator.h b/ReactCommon/fabric/uimanager/Differentiator.h
new file mode 100644
index 000000000000..7eb9fa332ff6
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/Differentiator.h
@@ -0,0 +1,24 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <fabric/core/ShadowNode.h>
+#include <fabric/uimanager/TreeMutationInstruction.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Calculates set of mutation instuctions which describe how the old
+ * ShadowNode tree can be transformed to the new ShadowNode tree.
+ * The set of instuctions might be and might not be optimal.
+ */
+void calculateMutationInstructions(
+  TreeMutationInstructionList &instructions,
+  SharedShadowNode parentNode,
+  SharedShadowNodeSharedList oldChildNodes,
+  SharedShadowNodeSharedList newChildNodes
+);
+
+} // namespace react
+} // namespace facebook

From 5463fc260b8d703f9da34e6be5f83d1079e4302a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:46:01 -0700
Subject: [PATCH 0254/1109] Fabric: ComponentDescriptorRegistry::operator[]
 marked as const

Summary:
Quite trivial.
Note that std::unordered_map's `operator[]` is not `const`, so we have to use `at` instead.

Reviewed By: mdvacca

Differential Revision: D7467799

fbshipit-source-id: df38b21dccee4b347f7c070600af0d52f38d6570
---
 .../fabric/uimanager/ComponentDescriptorRegistry.cpp      | 8 ++++----
 .../fabric/uimanager/ComponentDescriptorRegistry.h        | 8 ++++++--
 2 files changed, 10 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
index d209f590ce55..298e6c999c52 100644
--- a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
@@ -13,13 +13,13 @@ void ComponentDescriptorRegistry::registerComponentDescriptor(SharedComponentDes
   _registryByName[componentName] = componentDescriptor;
 }
 
-const SharedComponentDescriptor ComponentDescriptorRegistry::operator[](const SharedShadowNode &shadowNode) {
+const SharedComponentDescriptor ComponentDescriptorRegistry::operator[](const SharedShadowNode &shadowNode) const {
   ComponentHandle componentHandle = shadowNode->getComponentHandle();
-  return _registryByHandle[componentHandle];
+  return _registryByHandle.at(componentHandle);
 }
 
-const SharedComponentDescriptor ComponentDescriptorRegistry::operator[](const ComponentName &componentName) {
-  return _registryByName[componentName];
+const SharedComponentDescriptor ComponentDescriptorRegistry::operator[](const ComponentName &componentName) const {
+  return _registryByName.at(componentName);
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
index 462ab9f7f0d8..57d03d5242cc 100644
--- a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
@@ -9,6 +9,10 @@
 namespace facebook {
 namespace react {
 
+class ComponentDescriptorRegistry;
+
+using SharedComponentDescriptorRegistry = std::shared_ptr<const ComponentDescriptorRegistry>;
+
 /*
  * Registry of particular `ComponentDescriptor`s.
  */
@@ -17,8 +21,8 @@ class ComponentDescriptorRegistry {
 public:
   void registerComponentDescriptor(SharedComponentDescriptor componentDescriptor);
 
-  const SharedComponentDescriptor operator[](const SharedShadowNode &shadowNode);
-  const SharedComponentDescriptor operator[](const ComponentName &componentName);
+  const SharedComponentDescriptor operator[](const SharedShadowNode &shadowNode) const;
+  const SharedComponentDescriptor operator[](const ComponentName &componentName) const;
 
 private:
   std::unordered_map<ComponentHandle, SharedComponentDescriptor> _registryByHandle;

From db7f98b78993a28100ca15134c0f8f8138e9efcf Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:46:04 -0700
Subject: [PATCH 0255/1109] Fabric: Introducing ShadowNode::shallowSourceNode()

Summary:
The method replaces the current source node with its source node.
It's useful when we have to clone some node but don't want to change a source node pointer.

Reviewed By: fkgozali

Differential Revision: D7503384

fbshipit-source-id: 81ec64079c7e99cb9abdda2af10d85281a94e1b1
---
 ReactCommon/fabric/core/shadownode/ShadowNode.cpp | 4 ++++
 ReactCommon/fabric/core/shadownode/ShadowNode.h   | 8 ++++++++
 2 files changed, 12 insertions(+)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index f15964b0b5d9..8f54601d0431 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -108,6 +108,10 @@ void ShadowNode::clearSourceNode() {
   sourceNode_.reset();
 }
 
+void ShadowNode::shallowSourceNode() {
+  sourceNode_ = sourceNode_.lock()->getSourceNode();
+}
+
 #pragma mark - Equality
 
 bool ShadowNode::operator==(const ShadowNode& rhs) const {
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index f03acb107ee5..cd0264c2242f 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -67,6 +67,14 @@ class ShadowNode:
   void replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild);
   void clearSourceNode();
 
+  /*
+   * Replaces the current source node with its source node.
+   * This method might be used for illuminating side-effects caused by the last
+   * cloning operation which are not desirable from the diffing algorithm
+   * perspective.
+   */
+  void shallowSourceNode();
+
 #pragma mark - Equality
 
   /*

From c4bd7cef69ccdccaee848435ef068bb95c4ca7ba Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:46:07 -0700
Subject: [PATCH 0256/1109] Fabric: Fixed issue in the diffing algorithm

Summary:
Previously we generated `removed` *or* `delete` instruction, but sometimes we have to generate both.
So, basically we did it wrong. :(

Reviewed By: mdvacca

Differential Revision: D7503386

fbshipit-source-id: 8ee476abd29f088f31dc776f6e6a68d5293fbb35
---
 .../fabric/uimanager/Differentiator.cpp       | 25 +++++++++----------
 1 file changed, 12 insertions(+), 13 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/Differentiator.cpp b/ReactCommon/fabric/uimanager/Differentiator.cpp
index 20ff6add69df..87f929904503 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.cpp
+++ b/ReactCommon/fabric/uimanager/Differentiator.cpp
@@ -38,7 +38,6 @@ void calculateMutationInstructions(
   TreeMutationInstructionList downwardInstructions = {};
 
   // Stage 1: Collectings Updates
-
   for (index = 0; index < oldChildNodes->size() && index < newChildNodes->size(); index++) {
     SharedShadowNode oldChildNode = oldChildNodes->at(index);
     SharedShadowNode newChildNode = newChildNodes->at(index);
@@ -76,7 +75,7 @@ void calculateMutationInstructions(
     insertInstructions.push_back(
       TreeMutationInstruction::Insert(
         parentNode,
-        newChildNodes->at(index),
+        newChildNode,
         index
       )
     );
@@ -99,20 +98,20 @@ void calculateMutationInstructions(
   for (index = lastIndexAfterFirstStage; index < oldChildNodes->size(); index++) {
     SharedShadowNode oldChildNode = oldChildNodes->at(index);
 
+    // Even if the old node was (re)inserted, we have to generate `remove`
+    // instruction.
+    removeInstructions.push_back(
+      TreeMutationInstruction::Remove(
+        parentNode,
+        oldChildNode,
+        index
+      )
+    );
+
     auto numberOfRemovedTags = insertedTags.erase(oldChildNode->getTag());
     assert(numberOfRemovedTags == 0 || numberOfRemovedTags == 1);
 
-    if (numberOfRemovedTags != 0) {
-      // The old node *was* (re)inserted,
-      // so we have to generate `remove` instruction.
-      removeInstructions.push_back(
-        TreeMutationInstruction::Remove(
-          parentNode,
-          oldChildNode,
-          index
-        )
-      );
-    } else {
+    if (numberOfRemovedTags == 0) {
       // The old node was *not* (re)inserted,
       // so we have to generate `delete` instruction and apply the algorithm
       // recursively.

From 53837c4a4f9e689eb2f435564afede5f3466b84e Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:46:09 -0700
Subject: [PATCH 0257/1109] Fabric: Refined usage of `ensureunSealed` in
 `YogaLayoutableShadowNode::layout()`

Summary: We have to call `ensureunSealed()` only if the node was changed.

Reviewed By: mdvacca

Differential Revision: D7503388

fbshipit-source-id: a3d07d50fa983ef93c14fa771711fa783fdf4c12
---
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 5 +----
 1 file changed, 1 insertion(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 71e5ac89b345..e2aa05f843a1 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -105,9 +105,8 @@ void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child)
 }
 
 void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
-  ensureUnsealed();
-
   if (!getIsLayoutClean()) {
+    ensureUnsealed();
     YGNode *yogaNode = const_cast<YGNode *>(yogaNode_.get());
     YGNodeCalculateLayout(yogaNode, YGUndefined, YGUndefined, YGDirectionInherit);
   }
@@ -116,8 +115,6 @@ void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
 }
 
 void YogaLayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
-  ensureUnsealed();
-
   for (auto child : getChildren()) {
     auto yogaLayoutableChild = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(child);
     if (!yogaLayoutableChild) {

From 47c0ab91a5af2606b185272eedf8888a26d01126 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:46:12 -0700
Subject: [PATCH 0258/1109] Fabric: Using `shallowSourceNode()` inside
 `ViewShadowNode::cloneAndReplaceChild()`

Summary:
We have to call shallowSourceNode() in all cases of cloning which were not caused by UIManager instructions,
otherwise the diffing alogorith might produce incorrect mutation instructions.

Reviewed By: mdvacca

Differential Revision: D7503383

fbshipit-source-id: b33e5c39b7ba8cbd0f925fd29b3af379441a40a4
---
 .../fabric/core/shadownode/ShadowNode.cpp     |  6 ++++-
 .../fabric/core/shadownode/ShadowNode.h       |  8 +++++++
 .../fabric/core/tests/ShadowNodeTest.cpp      | 24 +++++++++++++++++++
 ReactCommon/fabric/view/ViewShadowNode.cpp    | 16 ++++++++++++-
 4 files changed, 52 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 8f54601d0431..3c9fa034bdbe 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -109,7 +109,11 @@ void ShadowNode::clearSourceNode() {
 }
 
 void ShadowNode::shallowSourceNode() {
-  sourceNode_ = sourceNode_.lock()->getSourceNode();
+  ensureUnsealed();
+
+  auto sourceNode = sourceNode_.lock();
+  assert(sourceNode);
+  sourceNode_ = sourceNode->getSourceNode();
 }
 
 #pragma mark - Equality
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index cd0264c2242f..48e840fd6798 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -58,7 +58,15 @@ class ShadowNode:
   Tag getTag() const;
   Tag getRootTag() const;
   InstanceHandle getInstanceHandle() const;
+
+  /*
+   * Returns the node which was used as a prototype in clone constructor.
+   * The node is held as a weak reference so that the method may return
+   * `nullptr` in cases where the node was constructed using the explicit
+   * constructor or the node was already deallocated.
+   */
   SharedShadowNode getSourceNode() const;
+
   void sealRecursive() const;
 
 #pragma mark - Mutating Methods
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index 418938a497e1..c14fda2003dd 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -94,3 +94,27 @@ TEST(ShadowNodeTest, handleShadowNodeMutation) {
   node5->clearSourceNode();
   ASSERT_EQ(node5->getSourceNode(), nullptr);
 }
+
+TEST(ShadowNodeTest, handleSourceNode) {
+  auto nodeFirstGeneration = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+  auto nodeSecondGeneration = std::make_shared<TestShadowNode>(nodeFirstGeneration);
+  auto nodeThirdGeneration = std::make_shared<TestShadowNode>(nodeSecondGeneration);
+  auto nodeForthGeneration = std::make_shared<TestShadowNode>(nodeThirdGeneration);
+
+  // Ensure established shource nodes structure.
+  ASSERT_EQ(nodeForthGeneration->getSourceNode(), nodeThirdGeneration);
+  ASSERT_EQ(nodeThirdGeneration->getSourceNode(), nodeSecondGeneration);
+  ASSERT_EQ(nodeSecondGeneration->getSourceNode(), nodeFirstGeneration);
+
+  // Shallow source node for the forth generation node.
+  nodeForthGeneration->shallowSourceNode();
+  ASSERT_EQ(nodeForthGeneration->getSourceNode(), nodeSecondGeneration);
+
+  // Shallow it one more time.
+  nodeForthGeneration->shallowSourceNode();
+  ASSERT_EQ(nodeForthGeneration->getSourceNode(), nodeFirstGeneration);
+
+  // Ensure that 3th and 2nd were not affected.
+  ASSERT_EQ(nodeThirdGeneration->getSourceNode(), nodeSecondGeneration);
+  ASSERT_EQ(nodeSecondGeneration->getSourceNode(), nodeFirstGeneration);
+}
diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/view/ViewShadowNode.cpp
index b8f610c10d5f..a51f151b92ff 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.cpp
+++ b/ReactCommon/fabric/view/ViewShadowNode.cpp
@@ -94,7 +94,21 @@ SharedLayoutableShadowNode ViewShadowNode::cloneAndReplaceChild(const SharedLayo
 
   auto viewShadowNodeChild = std::dynamic_pointer_cast<const ViewShadowNode>(child);
   assert(viewShadowNodeChild);
-  auto viewShadowNodeChildClone = std::make_shared<const ViewShadowNode>(viewShadowNodeChild);
+  auto viewShadowNodeChildClone = std::make_shared<ViewShadowNode>(viewShadowNodeChild);
+
+  // This is overloading of `SharedLayoutableShadowNode::cloneAndReplaceChild`,
+  // the method is used to clone some node as a preparation for future mutation
+  // caused by relayout.
+  // Because those changes are not requested by UIManager, they add a layer
+  // of node generation (between the committed stage and new proposed stage).
+  // That additional layer confuses the Diffing algorithm which uses
+  // `sourceNode` for referencing the previous (aka committed) stage
+  // of the tree to produce mutation instructions.
+  // In other words, if we don't compensate this change here,
+  // the Diffing algorithm will compare wrong trees
+  // ("new-but-not-laid-out-yet vs. new" instead of "committed vs. new").
+  viewShadowNodeChildClone->shallowSourceNode();
+
   ShadowNode::replaceChild(viewShadowNodeChild, viewShadowNodeChildClone);
   return std::static_pointer_cast<const LayoutableShadowNode>(viewShadowNodeChildClone);
 }

From 534abeca040e1d43514cfa8d8197adb20b30862c Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:46:15 -0700
Subject: [PATCH 0259/1109] Fabric: Introducing UIManagerDelegate

Summary: UIManager uses UIManagerDelegate to communicate about shadow tree changes to another parts of the system.

Reviewed By: fkgozali

Differential Revision: D7503484

fbshipit-source-id: 0afe0f0d6cad31fe2ee9d61235d02b379cfe8217
---
 React/Fabric/RCTFabricUIManagerWrapper.mm     |  9 +-
 .../fabric/uimanager/FabricUIManager.cpp      | 96 ++++++++++---------
 .../fabric/uimanager/FabricUIManager.h        | 31 +++---
 .../fabric/uimanager/UIManagerDelegate.h      | 37 +++++++
 4 files changed, 117 insertions(+), 56 deletions(-)
 create mode 100644 ReactCommon/fabric/uimanager/UIManagerDelegate.h

diff --git a/React/Fabric/RCTFabricUIManagerWrapper.mm b/React/Fabric/RCTFabricUIManagerWrapper.mm
index d3b6839eba06..dff3f263f12d 100644
--- a/React/Fabric/RCTFabricUIManagerWrapper.mm
+++ b/React/Fabric/RCTFabricUIManagerWrapper.mm
@@ -8,7 +8,9 @@
 #import "RCTFabricUIManagerWrapper.h"
 
 #include <React/RCTCxxExceptionManager.h>
+#include <fabric/uimanager/ComponentDescriptorRegistry.h>
 #include <fabric/uimanager/FabricUIManager.h>
+#include <fabric/view/ViewComponentDescriptor.h>
 #include <folly/dynamic.h>
 #include <folly/json.h>
 
@@ -28,7 +30,12 @@ - (instancetype)init
   if (self) {
     _exceptionManager = std::make_shared<RCTCxxExceptionManager>();
     _platformUIOperationManager = std::make_shared<RCTFabricPlatformUIOperationManagerConnector>();
-    _manager = std::make_shared<FabricUIManager>(_platformUIOperationManager);
+
+    auto componentDescriptorRegistry = std::make_shared<ComponentDescriptorRegistry>();
+    SharedComponentDescriptor viewComponentDescriptor = std::make_shared<ViewComponentDescriptor>();
+    componentDescriptorRegistry->registerComponentDescriptor(viewComponentDescriptor);
+
+    _manager = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
   }
   return self;
 }
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 0da19722a252..e2f3233980d5 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -9,13 +9,14 @@
 
 #include <glog/logging.h>
 
+#include <fabric/core/componentDescriptor.h>
 #include <fabric/core/LayoutContext.h>
-#include <fabric/view/ViewComponentDescriptor.h>
+#include <fabric/debug/DebugStringConvertible.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/view/ViewcomponentDescriptor.h>
 #include <fabric/view/ViewProps.h>
 #include <fabric/view/ViewShadowNode.h>
 
-#include "IFabricPlatformUIOperationManager.h"
-
 namespace facebook {
 namespace react {
 
@@ -37,63 +38,83 @@ static const RawProps rawPropsFromDynamic(const folly::dynamic object) {
   return result;
 }
 
-FabricUIManager::FabricUIManager(const std::shared_ptr<IFabricPlatformUIOperationManager> &platformUIOperationManager):
-  platformUIOperationManager_(platformUIOperationManager) {
+FabricUIManager::FabricUIManager(SharedComponentDescriptorRegistry componentDescriptorRegistry) {
+  componentDescriptorRegistry_ = componentDescriptorRegistry;
+}
+
+void FabricUIManager::setDelegate(UIManagerDelegate *delegate) {
+  delegate_ = delegate;
+}
 
-  SharedComponentDescriptor viewComponentDescriptor = std::make_shared<ViewComponentDescriptor>();
-  _registry.registerComponentDescriptor(viewComponentDescriptor);
+UIManagerDelegate *FabricUIManager::getDelegate() {
+  return delegate_;
 }
 
 SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
   LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
-  ComponentDescriptor &componentDescriptor = *_registry["View"];
+  const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)["View"];
   RawProps rawProps = rawPropsFromDynamic(props);
-  SharedShadowNode shadowNode = componentDescriptor.createShadowNode(tag, rootTag, instanceHandle, rawProps);
+  SharedShadowNode shadowNode = componentDescriptor->createShadowNode(tag, rootTag, instanceHandle, rawProps);
   LOG(INFO) << "FabricUIManager::createNode() -> " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+
+  if (delegate_) {
+    delegate_->uiManagerDidCreateShadowNode(shadowNode);
+  }
+
   return shadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode) {
   LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
-  ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
-  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode);
-  LOG(INFO) << "FabricUIManager::cloneNode() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
-  return clonnedShadowNode;
+  const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
+  SharedShadowNode clonedShadowNode = componentDescriptor->cloneShadowNode(shadowNode);
+  LOG(INFO) << "FabricUIManager::cloneNode() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  return clonedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode) {
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   // Assuming semantic: Cloning with same props but empty children.
-  ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
-  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, nullptr, ShadowNode::emptySharedShadowNodeSharedList());
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
-  return clonnedShadowNode;
+  const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
+  SharedShadowNode clonedShadowNode = componentDescriptor->cloneShadowNode(shadowNode, nullptr, ShadowNode::emptySharedShadowNodeSharedList());
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  return clonedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with same children and specified props.
-  ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
+  const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
-  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), nullptr);
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
-  return clonnedShadowNode;
+  SharedShadowNode clonedShadowNode = componentDescriptor->cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), nullptr);
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  return clonedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with empty children and specified props.
-  ComponentDescriptor &componentDescriptor = *_registry[shadowNode];
+  const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
-  SharedShadowNode clonnedShadowNode = componentDescriptor.cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), ShadowNode::emptySharedShadowNodeSharedList());
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps() -> " << clonnedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
-  return clonnedShadowNode;
+  SharedShadowNode clonedShadowNode = componentDescriptor->cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), ShadowNode::emptySharedShadowNodeSharedList());
+  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  return clonedShadowNode;
 }
 
 void FabricUIManager::appendChild(const SharedShadowNode &parentShadowNode, const SharedShadowNode &childShadowNode) {
   LOG(INFO) << "FabricUIManager::appendChild(parentShadowNode: " << parentShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", childShadowNode: " << childShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
-  ComponentDescriptor &componentDescriptor = *_registry[parentShadowNode];
-  componentDescriptor.appendChild(parentShadowNode, childShadowNode);
+  const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[parentShadowNode];
+
+  // TODO: Remove this after we move this to JS side.
+  if (childShadowNode->getSealed()) {
+    auto clonedChildShadowNode = componentDescriptor->cloneShadowNode(childShadowNode);
+    auto nonConstClonedChildShadowNode = std::const_pointer_cast<ShadowNode>(clonedChildShadowNode);
+    nonConstClonedChildShadowNode->shallowSourceNode();
+    componentDescriptor->appendChild(parentShadowNode, clonedChildShadowNode);
+    return;
+  }
+
+  componentDescriptor->appendChild(parentShadowNode, childShadowNode);
 }
 
 SharedShadowNodeUnsharedList FabricUIManager::createChildSet(int rootTag) {
@@ -107,24 +128,11 @@ void FabricUIManager::appendChildToSet(const SharedShadowNodeUnsharedList &shado
 }
 
 void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedList &children) {
-  LOG(INFO) << "FabricUIManager::appendChildToSet(rootTag: " << rootTag << ", shadowNodeList: " << children << ")";
-  ComponentDescriptor &componentDescriptor = *_registry["View"];
-  SharedShadowNode previousRootShadowNode = componentDescriptor.createShadowNode(rootTag, rootTag, nullptr, {});
-  auto childrenCopy = std::make_shared<const SharedShadowNodeList>(SharedShadowNodeList(*children));
-  SharedShadowNode rootShadowNode = componentDescriptor.cloneShadowNode(previousRootShadowNode, nullptr, childrenCopy);
-
-  SharedViewShadowNode viewShadowNode = std::dynamic_pointer_cast<const ViewShadowNode>(rootShadowNode);
-  LayoutContext layoutContext = LayoutContext();
-  layoutContext.affectedShadowNodes = std::make_shared<std::unordered_set<SharedLayoutableShadowNode>>();
-
-  LOG(INFO) << "Shadow tree *before* layout: \n" << viewShadowNode->getDebugDescription() ;
+  LOG(INFO) << "FabricUIManager::completeRoot(rootTag: " << rootTag << ", shadowNodeList: " << children << ")";
 
-  auto nonConstViewShadowNode = std::const_pointer_cast<ViewShadowNode>(viewShadowNode);
-  nonConstViewShadowNode->layout(layoutContext);
-
-  rootShadowNode->sealRecursive();
-
-  LOG(INFO) << "Shadow tree *after* layout: \n" << nonConstViewShadowNode->getDebugDescription();
+  if (delegate_) {
+    delegate_->uiManagerDidFinishTransaction(rootTag, children);
+  }
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index 1db615b37c3f..c2b3dea9bfee 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -11,34 +11,43 @@
 
 #include <folly/dynamic.h>
 
-#include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/ShadowNode.h>
 #include <fabric/uimanager/ComponentDescriptorRegistry.h>
+#include <fabric/uimanager/UIManagerDelegate.h>
 
 namespace facebook {
 namespace react {
 
-class IFabricPlatformUIOperationManager;
-class ComponentDescriptorRegistry;
-
 class FabricUIManager {
-
 public:
-  FabricUIManager(const std::shared_ptr<IFabricPlatformUIOperationManager> &platformUIOperationManager);
 
-  SharedShadowNode createNode(int reactTag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle);
+#pragma mark - Native-facing Interface
+
+  FabricUIManager(SharedComponentDescriptorRegistry componentDescriptorRegistry);
+
+  /*
+   * Sets and gets the UIManager's delegate.
+   * The delegate is stored as a raw pointer, so the owner must null
+   * the pointer before being destroyed.
+   */
+  void setDelegate(UIManagerDelegate *delegate);
+  UIManagerDelegate *getDelegate();
+
+#pragma mark - JavaScript/React-facing Interface
+
+  SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, void *instanceHandle);
   SharedShadowNode cloneNode(const SharedShadowNode &node);
   SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node);
   SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props);
   SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps);
   void appendChild(const SharedShadowNode &parentNode, const SharedShadowNode &childNode);
-  SharedShadowNodeUnsharedList createChildSet(int rootTag);
+  SharedShadowNodeUnsharedList createChildSet(Tag rootTag);
   void appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode);
-  void completeRoot(int rootTag, const SharedShadowNodeUnsharedList &childSet);
+  void completeRoot(Tag rootTag, const SharedShadowNodeUnsharedList &childSet);
 
 private:
-  ComponentDescriptorRegistry _registry;
-  std::shared_ptr<IFabricPlatformUIOperationManager> platformUIOperationManager_;
+  SharedComponentDescriptorRegistry componentDescriptorRegistry_;
+  UIManagerDelegate *delegate_;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/UIManagerDelegate.h b/ReactCommon/fabric/uimanager/UIManagerDelegate.h
new file mode 100644
index 000000000000..e94af1f44034
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/UIManagerDelegate.h
@@ -0,0 +1,37 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ShadowNode.h>
+#include <fabric/core/ReactPrimitives.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Abstract class for UIManager's delegate.
+ */
+class UIManagerDelegate {
+public:
+
+  /*
+   * Called right after the new/updated Shadow Node tree is constructed.
+   * The tree is not layed out and not sealed at this time.
+   */
+  virtual void uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNodeUnsharedList &rootChildNodes) = 0;
+
+  /*
+   * Called each time when UIManager constructs a new Shadow Node. Receiver
+   * maight use this to preluminary optimistically allocate a new native view
+   * instances.
+   */
+  virtual void uiManagerDidCreateShadowNode(const SharedShadowNode &shadowNode) = 0;
+};
+
+} // namespace react
+} // namespace facebook

From f6f7d0484c7e561cd6583844f75ba6004acbe744 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:46:17 -0700
Subject: [PATCH 0260/1109] Fixed typo in RCTShadowView

Summary: Trivial.

Reviewed By: PeteTheHeat

Differential Revision: D7503382

fbshipit-source-id: 0c553553bcde5c2f32bace0fa047aee6a106619b
---
 React/Views/RCTShadowView.m | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/React/Views/RCTShadowView.m b/React/Views/RCTShadowView.m
index 457117653900..84ad1c908c3e 100644
--- a/React/Views/RCTShadowView.m
+++ b/React/Views/RCTShadowView.m
@@ -340,10 +340,10 @@ - (void)layoutSubviewsWithContext:(RCTLayoutContext)layoutContext
 
 - (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize maximumSize:(CGSize)maximumSize
 {
-  YGNodeRef clonnedYogaNode = YGNodeClone(self.yogaNode);
+  YGNodeRef clonedYogaNode = YGNodeClone(self.yogaNode);
   YGNodeRef constraintYogaNode = YGNodeNewWithConfig([[self class] yogaConfig]);
 
-  YGNodeInsertChild(constraintYogaNode, clonnedYogaNode, 0);
+  YGNodeInsertChild(constraintYogaNode, clonedYogaNode, 0);
 
   YGNodeStyleSetMinWidth(constraintYogaNode, RCTYogaFloatFromCoreGraphicsFloat(minimumSize.width));
   YGNodeStyleSetMinHeight(constraintYogaNode, RCTYogaFloatFromCoreGraphicsFloat(minimumSize.height));
@@ -362,9 +362,9 @@ - (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize maximumSize:(CGSize)maximu
     RCTCoreGraphicsFloatFromYogaFloat(YGNodeLayoutGetHeight(constraintYogaNode)),
   };
 
-  YGNodeRemoveChild(constraintYogaNode, clonnedYogaNode);
+  YGNodeRemoveChild(constraintYogaNode, clonedYogaNode);
   YGNodeFree(constraintYogaNode);
-  YGNodeFree(clonnedYogaNode);
+  YGNodeFree(clonedYogaNode);
 
   return measuredSize;
 }

From ba45895a3f7b54cf2b0bf93daaf6b362726e14df Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 12:46:20 -0700
Subject: [PATCH 0261/1109] Fabric: Introducing Scheduler

Summary: Scheduler coordinates Shadow Tree updates and event flows (not yet).

Reviewed By: mdvacca

Differential Revision: D7503387

fbshipit-source-id: 4cb8bc574c25a0fd2ace6319c26c644a1e4757a9
---
 ReactCommon/fabric/uimanager/Scheduler.cpp    | 108 ++++++++++++++++++
 ReactCommon/fabric/uimanager/Scheduler.h      |  74 ++++++++++++
 .../fabric/uimanager/SchedulerDelegate.h      |  33 ++++++
 3 files changed, 215 insertions(+)
 create mode 100644 ReactCommon/fabric/uimanager/Scheduler.cpp
 create mode 100644 ReactCommon/fabric/uimanager/Scheduler.h
 create mode 100644 ReactCommon/fabric/uimanager/SchedulerDelegate.h

diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
new file mode 100644
index 000000000000..b2571ebf6168
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -0,0 +1,108 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include "Scheduler.h"
+
+#include <fabric/core/LayoutContext.h>
+#include <fabric/uimanager/ComponentDescriptorRegistry.h>
+#include <fabric/uimanager/FabricUIManager.h>
+#include <fabric/view/ViewComponentDescriptor.h>
+#include <fabric/view/ViewProps.h>
+#include <fabric/view/ViewShadowNode.h>
+
+#include "Differentiator.h"
+
+namespace facebook {
+namespace react {
+
+Scheduler::Scheduler() {
+  auto componentDescriptorRegistry = std::make_shared<ComponentDescriptorRegistry>();
+  SharedComponentDescriptor viewComponentDescriptor = std::make_shared<ViewComponentDescriptor>();
+  componentDescriptorRegistry->registerComponentDescriptor(viewComponentDescriptor);
+
+  uiManager_ = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
+  uiManager_->setDelegate(this);
+}
+
+Scheduler::~Scheduler() {
+  uiManager_->setDelegate(nullptr);
+}
+
+void Scheduler::registerRootTag(Tag rootTag) {
+  auto rootShadowNode = std::make_shared<RootShadowNode>(rootTag, rootTag, nullptr);
+  rootNodeRegistry_.insert({rootTag, rootShadowNode});
+}
+
+void Scheduler::unregisterRootTag(Tag rootTag) {
+  rootNodeRegistry_.erase(rootTag);
+}
+
+#pragma mark - Delegate
+
+void Scheduler::setDelegate(SchedulerDelegate *delegate) {
+  delegate_ = delegate;
+}
+
+SchedulerDelegate *Scheduler::getDelegate() {
+  return delegate_;
+}
+
+#pragma mark - UIManagerDelegate
+  
+void Scheduler::uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNodeUnsharedList &rootChildNodes) {
+  SharedRootShadowNode oldRootShadowNode = rootNodeRegistry_[rootTag];
+  assert(oldRootShadowNode);
+
+  SharedRootShadowNode newRootShadowNode =
+    std::make_shared<RootShadowNode>(oldRootShadowNode, nullptr, SharedShadowNodeSharedList(rootChildNodes));
+
+  auto nonConstOldRootShadowNode = std::const_pointer_cast<RootShadowNode>(oldRootShadowNode);
+  auto nonConstNewRootShadowNode = std::const_pointer_cast<RootShadowNode>(newRootShadowNode);
+
+  LayoutContext layoutContext = LayoutContext();
+  layoutContext.affectedShadowNodes = std::make_shared<std::unordered_set<SharedLayoutableShadowNode>>();
+
+  LOG(INFO) << "Old Shadow Tree: \n" << oldRootShadowNode->getDebugDescription();
+  LOG(INFO) << "New Shadow Tree *before* layout: \n" << newRootShadowNode->getDebugDescription();
+
+  nonConstNewRootShadowNode->layout(layoutContext);
+
+  nonConstNewRootShadowNode->sealRecursive();
+
+  LOG(INFO) << "New Shadow Tree *after* layout: \n" << nonConstNewRootShadowNode->getDebugDescription();
+
+  TreeMutationInstructionList instructions = TreeMutationInstructionList();
+
+  calculateMutationInstructions(
+    instructions,
+    oldRootShadowNode,
+    oldRootShadowNode->ShadowNode::getChildren(),
+    newRootShadowNode->ShadowNode::getChildren()
+  );
+
+  LOG(INFO) << "TreeMutationInstructionList:";
+
+  for (auto instruction : instructions) {
+    LOG(INFO) << "Instruction: " << instruction.getDebugDescription();
+  }
+
+  rootNodeRegistry_[rootTag] = newRootShadowNode;
+
+  if (delegate_) {
+    delegate_->schedulerDidComputeMutationInstructions(rootTag, instructions);
+  }
+}
+
+void Scheduler::uiManagerDidCreateShadowNode(const SharedShadowNode &shadowNode) {
+  if (delegate_) {
+    delegate_->schedulerDidRequestPreliminaryViewAllocation(shadowNode->getComponentName());
+  }
+}
+
+#pragma mark - Deprecated
+
+std::shared_ptr<FabricUIManager> Scheduler::getUIManager_DO_NOT_USE() {
+  return uiManager_;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
new file mode 100644
index 000000000000..4f4ff203b54a
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -0,0 +1,74 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ComponentDescriptor.h>
+#include <fabric/core/LayoutConstraints.h>
+#include <fabric/uimanager/SchedulerDelegate.h>
+#include <fabric/uimanager/UIManagerDelegate.h>
+#include <fabric/view/ViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * We expect having a dedicated subclass for root shadow node.
+ */
+using SharedRootShadowNode = SharedViewShadowNode;
+using RootShadowNode = ViewShadowNode;
+
+class FabricUIManager;
+
+/*
+ * Scheduler coordinates Shadow Tree updates and event flows.
+ */
+class Scheduler:
+  public UIManagerDelegate {
+
+public:
+  Scheduler();
+  ~Scheduler();
+
+#pragma mark - Root Nodes Managerment
+
+  void registerRootTag(Tag rootTag);
+  void unregisterRootTag(Tag rootTag);
+
+  void setLayoutConstraints(Tag rootTag, LayoutConstraints layoutConstraints);
+
+#pragma mark - Delegate
+
+  /*
+   * Sets and gets the Scheduler's delegate.
+   * The delegate is stored as a raw pointer, so the owner must null
+   * the pointer before being destroyed.
+   */
+  void setDelegate(SchedulerDelegate *delegate);
+  SchedulerDelegate *getDelegate();
+
+#pragma mark - UIManagerDelegate
+
+  void uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNodeUnsharedList &rootChildNodes) override;
+  void uiManagerDidCreateShadowNode(const SharedShadowNode &shadowNode) override;
+
+#pragma mark - Deprecated
+
+  /*
+   * UIManager instance must be temporarily exposed for registration purposes.
+   */
+  std::shared_ptr<FabricUIManager> getUIManager_DO_NOT_USE();
+
+private:
+  SchedulerDelegate *delegate_;
+  std::shared_ptr<FabricUIManager> uiManager_;
+
+  /*
+   * All commited `RootShadowNode` instances to differentiate against.
+   */
+  std::unordered_map<Tag, SharedRootShadowNode> rootNodeRegistry_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/SchedulerDelegate.h b/ReactCommon/fabric/uimanager/SchedulerDelegate.h
new file mode 100644
index 000000000000..2fe3da02ace1
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/SchedulerDelegate.h
@@ -0,0 +1,33 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ReactPrimitives.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/uimanager/TreeMutationInstruction.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Abstract class for Scheduler's delegate.
+ */
+class SchedulerDelegate {
+public:
+  /*
+   * Called right after Scheduler computed (and laid out) a new updated version
+   * of the tree and calculated a set of mutation instructions which are
+   * suffisient to construct a new one.
+   */
+  virtual void schedulerDidComputeMutationInstructions(Tag rootTag, const TreeMutationInstructionList &instructions) = 0;
+
+  /*
+   * Called right after a new ShadowNode was created.
+   */
+  virtual void schedulerDidRequestPreliminaryViewAllocation(ComponentName componentName) = 0;
+};
+
+} // namespace react
+} // namespace facebook

From 906dde06b3f25b4e87adcbc8ed64f72bc930ac6a Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Tue, 10 Apr 2018 15:19:57 -0700
Subject: [PATCH 0262/1109] React sync for revisions 7a3416f...725c054

Reviewed By: bvaughn

Differential Revision: D7565731

fbshipit-source-id: 91d76a11b7c91dab2fb3295418d1372ca9c1b572
---
 Libraries/Components/View/FabricView.js       |  102 +-
 Libraries/ReactNative/ReactFabricInternals.js |    8 +-
 .../ReactNative/requireFabricComponent.js     |   10 +-
 .../ReactNative/requireNativeComponent.js     |    6 -
 Libraries/Renderer/REVISION                   |    2 +-
 Libraries/Renderer/ReactFabric-dev.js         | 1438 ++++++-----------
 Libraries/Renderer/ReactFabric-prod.js        |  671 +++-----
 Libraries/Renderer/ReactNativeRenderer-dev.js | 1334 ++++++---------
 .../Renderer/ReactNativeRenderer-prod.js      |  600 +++----
 .../shims/ReactNativeBridgeEventPlugin.js     |   17 -
 Libraries/Renderer/shims/ReactNativeTypes.js  |   23 +-
 .../shims/ReactNativeViewConfigRegistry.js    |  106 ++
 .../shims/createReactNativeComponentClass.js  |   24 +-
 Libraries/Text/FabricText.js                  |  231 +--
 14 files changed, 1494 insertions(+), 3078 deletions(-)
 delete mode 100644 Libraries/Renderer/shims/ReactNativeBridgeEventPlugin.js
 create mode 100644 Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js

diff --git a/Libraries/Components/View/FabricView.js b/Libraries/Components/View/FabricView.js
index 4d686f7beb29..d56189052877 100644
--- a/Libraries/Components/View/FabricView.js
+++ b/Libraries/Components/View/FabricView.js
@@ -10,104 +10,4 @@
  */
 'use strict';
 
-/**
- * This is a temporary fork of View.js for Fabric purpose.
- * Do not use outside of Fabric tree.
- */
-
-const Platform = require('Platform');
-const React = require('React');
-const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
-const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
-const ViewPropTypes = require('ViewPropTypes');
-const {NativeMethodsMixin} = require('ReactFabricInternals');
-const {ViewContextTypes} = require('ViewContext');
-
-const createReactClass = require('create-react-class');
-const invariant = require('fbjs/lib/invariant');
-const requireFabricComponent = require('requireFabricComponent');
-
-import type {ViewProps} from 'ViewPropTypes';
-import type {ViewChildContext} from 'ViewContext';
-
-export type Props = ViewProps;
-
-/**
- * The most fundamental component for building a UI.
- *
- * See http://facebook.github.io/react-native/docs/view.html
- */
-const View = createReactClass({
-  displayName: 'View',
-  // TODO: We should probably expose the mixins, viewConfig, and statics publicly. For example,
-  // one of the props is of type AccessibilityComponentType. That is defined as a const[] above,
-  // but it is not rendered by the docs, since `statics` below is not rendered. So its Possible
-  // values had to be hardcoded.
-  mixins: [NativeMethodsMixin],
-
-  // `propTypes` should not be accessed directly on View since this wrapper only
-  // exists for DEV mode. However it's important for them to be declared.
-  // If the object passed to `createClass` specifies `propTypes`, Flow will
-  // create a static type from it.
-  propTypes: ViewPropTypes,
-
-  /**
-   * `NativeMethodsMixin` will look for this when invoking `setNativeProps`. We
-   * make `this` look like an actual native component class.
-   */
-  viewConfig: {
-    uiViewClassName: 'RCTView',
-    validAttributes: ReactNativeViewAttributes.RCTView,
-  },
-
-  childContextTypes: ViewContextTypes,
-
-  getChildContext(): ViewChildContext {
-    return {
-      isInAParentText: false,
-    };
-  },
-
-  render() {
-    invariant(
-      !(this.context.isInAParentText && Platform.OS === 'android'),
-      'Nesting of <View> within <Text> is not supported on Android.',
-    );
-
-    // WARNING: This method will not be used in production mode as in that mode we
-    // replace wrapper component View with generated native wrapper RCTView. Avoid
-    // adding functionality this component that you'd want to be available in both
-    // dev and prod modes.
-    return <RCTView {...this.props} />;
-  },
-});
-
-const RCTView = requireFabricComponent('RCTView', View, {
-  nativeOnly: {
-    nativeBackgroundAndroid: true,
-    nativeForegroundAndroid: true,
-  },
-  fabric: true,
-});
-
-if (__DEV__) {
-  const UIManager = require('UIManager');
-  const viewConfig =
-    (UIManager.viewConfigs && UIManager.viewConfigs.RCTView) || {};
-  for (const prop in viewConfig.nativeProps) {
-    const viewAny: any = View; // Appease flow
-    if (!viewAny.propTypes[prop] && !ReactNativeStyleAttributes[prop]) {
-      throw new Error(
-        'View is missing propType for native prop `' + prop + '`',
-      );
-    }
-  }
-}
-
-let ViewToExport = RCTView;
-if (__DEV__) {
-  ViewToExport = View;
-}
-
-// No one should depend on the DEV-mode createClass View wrapper.
-module.exports = ((ViewToExport: any): typeof RCTView);
+module.exports = require('View');
diff --git a/Libraries/ReactNative/ReactFabricInternals.js b/Libraries/ReactNative/ReactFabricInternals.js
index d360803412a1..72f37a41232d 100644
--- a/Libraries/ReactNative/ReactFabricInternals.js
+++ b/Libraries/ReactNative/ReactFabricInternals.js
@@ -14,19 +14,15 @@
 const {
   __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
 } = require('ReactFabric');
+const createReactNativeComponentClass = require('createReactNativeComponentClass');
 
 import type {NativeMethodsMixinType} from 'ReactNativeTypes';
 
-const {
-  NativeMethodsMixin,
-  ReactNativeBridgeEventPlugin,
-  createReactNativeComponentClass,
-} = __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+const {NativeMethodsMixin} = __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
 
 module.exports = {
   NativeMethodsMixin: ((NativeMethodsMixin: any): $Exact<
     NativeMethodsMixinType,
   >),
-  ReactNativeBridgeEventPlugin,
   createReactNativeComponentClass,
 };
diff --git a/Libraries/ReactNative/requireFabricComponent.js b/Libraries/ReactNative/requireFabricComponent.js
index 4d9fca04cd58..dfd02bfeb612 100644
--- a/Libraries/ReactNative/requireFabricComponent.js
+++ b/Libraries/ReactNative/requireFabricComponent.js
@@ -11,10 +11,7 @@
 'use strict';
 
 const Platform = require('Platform');
-const {
-  ReactNativeBridgeEventPlugin,
-  createReactNativeComponentClass,
-} = require('ReactFabricInternals');
+const {createReactNativeComponentClass} = require('ReactFabricInternals');
 const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
 const UIManager = require('UIManager');
 
@@ -200,11 +197,6 @@ function requireNativeComponent(
       hasAttachedDefaultEventTypes = true;
     }
 
-    // Register this view's event types with the ReactNative renderer.
-    // This enables view managers to be initialized lazily, improving perf,
-    // While also enabling 3rd party components to define custom event types.
-    ReactNativeBridgeEventPlugin.processEventTypes(viewConfig);
-
     return viewConfig;
   }
 
diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index 453be93f715b..77141b1c049a 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -11,7 +11,6 @@
 'use strict';
 
 const Platform = require('Platform');
-const ReactNativeBridgeEventPlugin = require('ReactNativeBridgeEventPlugin');
 const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
 const UIManager = require('UIManager');
 
@@ -198,11 +197,6 @@ function requireNativeComponent(
       hasAttachedDefaultEventTypes = true;
     }
 
-    // Register this view's event types with the ReactNative renderer.
-    // This enables view managers to be initialized lazily, improving perf,
-    // While also enabling 3rd party components to define custom event types.
-    ReactNativeBridgeEventPlugin.processEventTypes(viewConfig);
-
     return viewConfig;
   }
 
diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index f505341495fa..4d4db61db4a5 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-7a3416f27532ac25849dfbc505300d469b43bbcc
\ No newline at end of file
+52afbe0ebb6fca0fe480e77c6fa8482870ddb2c9
\ No newline at end of file
diff --git a/Libraries/Renderer/ReactFabric-dev.js b/Libraries/Renderer/ReactFabric-dev.js
index e51c0254b904..e933ab8f0bb4 100644
--- a/Libraries/Renderer/ReactFabric-dev.js
+++ b/Libraries/Renderer/ReactFabric-dev.js
@@ -19,6 +19,7 @@ require("InitializeCore");
 var invariant = require("fbjs/lib/invariant");
 var warning = require("fbjs/lib/warning");
 var emptyFunction = require("fbjs/lib/emptyFunction");
+var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
 var UIManager = require("UIManager");
 var TextInputState = require("TextInputState");
 var deepDiffer = require("deepDiffer");
@@ -1294,7 +1295,7 @@ function getPooledWarningPropertyDefinition(propName, getVal) {
   return {
     configurable: true,
     set: set,
-    get: get
+    get: get$$1
   };
 
   function set(val) {
@@ -1303,7 +1304,7 @@ function getPooledWarningPropertyDefinition(propName, getVal) {
     return val;
   }
 
-  function get() {
+  function get$$1() {
     var action = isFunction ? "accessing the method" : "accessing the property";
     var result = isFunction
       ? "This is a no-op function"
@@ -1620,7 +1621,7 @@ var changeResponder = function(nextResponderInst, blockHostResponder) {
   }
 };
 
-var eventTypes = {
+var eventTypes$1 = {
   /**
    * On a `touchStart`/`mouseDown`, is it desired that this element become the
    * responder?
@@ -1885,12 +1886,12 @@ function setResponderAndExtractTransfer(
   nativeEventTarget
 ) {
   var shouldSetEventType = isStartish(topLevelType)
-    ? eventTypes.startShouldSetResponder
+    ? eventTypes$1.startShouldSetResponder
     : isMoveish(topLevelType)
-      ? eventTypes.moveShouldSetResponder
+      ? eventTypes$1.moveShouldSetResponder
       : topLevelType === "topSelectionChange"
-        ? eventTypes.selectionChangeShouldSetResponder
-        : eventTypes.scrollShouldSetResponder;
+        ? eventTypes$1.selectionChangeShouldSetResponder
+        : eventTypes$1.scrollShouldSetResponder;
 
   // TODO: stop one short of the current responder.
   var bubbleShouldSetFrom = !responderInst
@@ -1924,7 +1925,7 @@ function setResponderAndExtractTransfer(
   }
   var extracted = void 0;
   var grantEvent = ResponderSyntheticEvent.getPooled(
-    eventTypes.responderGrant,
+    eventTypes$1.responderGrant,
     wantsResponderInst,
     nativeEvent,
     nativeEventTarget
@@ -1935,7 +1936,7 @@ function setResponderAndExtractTransfer(
   var blockHostResponder = executeDirectDispatch(grantEvent) === true;
   if (responderInst) {
     var terminationRequestEvent = ResponderSyntheticEvent.getPooled(
-      eventTypes.responderTerminationRequest,
+      eventTypes$1.responderTerminationRequest,
       responderInst,
       nativeEvent,
       nativeEventTarget
@@ -1952,7 +1953,7 @@ function setResponderAndExtractTransfer(
 
     if (shouldSwitch) {
       var terminateEvent = ResponderSyntheticEvent.getPooled(
-        eventTypes.responderTerminate,
+        eventTypes$1.responderTerminate,
         responderInst,
         nativeEvent,
         nativeEventTarget
@@ -1963,7 +1964,7 @@ function setResponderAndExtractTransfer(
       changeResponder(wantsResponderInst, blockHostResponder);
     } else {
       var rejectEvent = ResponderSyntheticEvent.getPooled(
-        eventTypes.responderReject,
+        eventTypes$1.responderReject,
         wantsResponderInst,
         nativeEvent,
         nativeEventTarget
@@ -2032,7 +2033,7 @@ var ResponderEventPlugin = {
     return responderInst;
   },
 
-  eventTypes: eventTypes,
+  eventTypes: eventTypes$1,
 
   /**
    * We must be resilient to `targetInst` being `null` on `touchMove` or
@@ -2082,10 +2083,10 @@ var ResponderEventPlugin = {
     var isResponderTouchMove = responderInst && isMoveish(topLevelType);
     var isResponderTouchEnd = responderInst && isEndish(topLevelType);
     var incrementalTouch = isResponderTouchStart
-      ? eventTypes.responderStart
+      ? eventTypes$1.responderStart
       : isResponderTouchMove
-        ? eventTypes.responderMove
-        : isResponderTouchEnd ? eventTypes.responderEnd : null;
+        ? eventTypes$1.responderMove
+        : isResponderTouchEnd ? eventTypes$1.responderEnd : null;
 
     if (incrementalTouch) {
       var gesture = ResponderSyntheticEvent.getPooled(
@@ -2107,8 +2108,8 @@ var ResponderEventPlugin = {
       isEndish(topLevelType) &&
       noResponderTouches(nativeEvent);
     var finalTouch = isResponderTerminate
-      ? eventTypes.responderTerminate
-      : isResponderRelease ? eventTypes.responderRelease : null;
+      ? eventTypes$1.responderTerminate
+      : isResponderRelease ? eventTypes$1.responderRelease : null;
     if (finalTouch) {
       var finalEvent = ResponderSyntheticEvent.getPooled(
         finalTouch,
@@ -2160,11 +2161,14 @@ var ResponderEventPlugin = {
   }
 };
 
-var customBubblingEventTypes = {};
-var customDirectEventTypes = {};
+var customBubblingEventTypes$1 =
+  ReactNativeViewConfigRegistry.customBubblingEventTypes;
+var customDirectEventTypes$1 =
+  ReactNativeViewConfigRegistry.customDirectEventTypes;
+var eventTypes$2 = ReactNativeViewConfigRegistry.eventTypes;
 
 var ReactNativeBridgeEventPlugin = {
-  eventTypes: {},
+  eventTypes: eventTypes$2,
 
   /**
    * @see {EventPluginHub.extractEvents}
@@ -2179,8 +2183,8 @@ var ReactNativeBridgeEventPlugin = {
       // Probably a node belonging to another renderer's tree.
       return null;
     }
-    var bubbleDispatchConfig = customBubblingEventTypes[topLevelType];
-    var directDispatchConfig = customDirectEventTypes[topLevelType];
+    var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType];
+    var directDispatchConfig = customDirectEventTypes$1[topLevelType];
     invariant(
       bubbleDispatchConfig || directDispatchConfig,
       'Unsupported top level event type "%s" dispatched',
@@ -2200,45 +2204,6 @@ var ReactNativeBridgeEventPlugin = {
       return null;
     }
     return event;
-  },
-
-  processEventTypes: function(viewConfig) {
-    var bubblingEventTypes = viewConfig.bubblingEventTypes,
-      directEventTypes = viewConfig.directEventTypes;
-
-    {
-      if (bubblingEventTypes != null && directEventTypes != null) {
-        for (var topLevelType in directEventTypes) {
-          invariant(
-            bubblingEventTypes[topLevelType] == null,
-            "Event cannot be both direct and bubbling: %s",
-            topLevelType
-          );
-        }
-      }
-    }
-
-    if (bubblingEventTypes != null) {
-      for (var _topLevelType in bubblingEventTypes) {
-        if (customBubblingEventTypes[_topLevelType] == null) {
-          ReactNativeBridgeEventPlugin.eventTypes[
-            _topLevelType
-          ] = customBubblingEventTypes[_topLevelType] =
-            bubblingEventTypes[_topLevelType];
-        }
-      }
-    }
-
-    if (directEventTypes != null) {
-      for (var _topLevelType2 in directEventTypes) {
-        if (customDirectEventTypes[_topLevelType2] == null) {
-          ReactNativeBridgeEventPlugin.eventTypes[
-            _topLevelType2
-          ] = customDirectEventTypes[_topLevelType2] =
-            directEventTypes[_topLevelType2];
-        }
-      }
-    }
   }
 };
 
@@ -2402,56 +2367,6 @@ function createPortal(
   };
 }
 
-// Use to restore controlled state after a change event has fired.
-
-var fiberHostComponent = null;
-
-var restoreTarget = null;
-var restoreQueue = null;
-
-function restoreStateOfTarget(target) {
-  // We perform this translation at the end of the event loop so that we
-  // always receive the correct fiber here
-  var internalInstance = getInstanceFromNode(target);
-  if (!internalInstance) {
-    // Unmounted
-    return;
-  }
-  invariant(
-    fiberHostComponent &&
-      typeof fiberHostComponent.restoreControlledState === "function",
-    "Fiber needs to be injected to handle a fiber target for controlled " +
-      "events. This error is likely caused by a bug in React. Please file an issue."
-  );
-  var props = getFiberCurrentPropsFromNode(internalInstance.stateNode);
-  fiberHostComponent.restoreControlledState(
-    internalInstance.stateNode,
-    internalInstance.type,
-    props
-  );
-}
-
-function needsStateRestore() {
-  return restoreTarget !== null || restoreQueue !== null;
-}
-
-function restoreStateIfNeeded() {
-  if (!restoreTarget) {
-    return;
-  }
-  var target = restoreTarget;
-  var queuedTargets = restoreQueue;
-  restoreTarget = null;
-  restoreQueue = null;
-
-  restoreStateOfTarget(target);
-  if (queuedTargets) {
-    for (var i = 0; i < queuedTargets.length; i++) {
-      restoreStateOfTarget(queuedTargets[i]);
-    }
-  }
-}
-
 // Used as a way to call batchedUpdates when we don't have a reference to
 // the renderer. Such as when we're dispatching events or if third party
 // libraries need to call batchedUpdates. Eventually, this API will go away when
@@ -2467,33 +2382,6 @@ var _interactiveUpdates = function(fn, a, b) {
 };
 var _flushInteractiveUpdates = function() {};
 
-var isBatching = false;
-function batchedUpdates(fn, bookkeeping) {
-  if (isBatching) {
-    // If we are currently inside another batch, we need to wait until it
-    // fully completes before restoring state.
-    return fn(bookkeeping);
-  }
-  isBatching = true;
-  try {
-    return _batchedUpdates(fn, bookkeeping);
-  } finally {
-    // Here we wait until all updates have propagated, which is important
-    // when using controlled components within layers:
-    // https://github.com/facebook/react/issues/1698
-    // Then we restore state of any controlled component.
-    isBatching = false;
-    var controlledComponentsHavePendingUpdates = needsStateRestore();
-    if (controlledComponentsHavePendingUpdates) {
-      // If a controlled event was fired, we may need to restore the state of
-      // the DOM node back to the controlled value. This is necessary when React
-      // bails out of the update without touching the DOM.
-      _flushInteractiveUpdates();
-      restoreStateIfNeeded();
-    }
-  }
-}
-
 var injection$2 = {
   injectRenderer: function(renderer) {
     _batchedUpdates = renderer.batchedUpdates;
@@ -2502,195 +2390,10 @@ var injection$2 = {
   }
 };
 
-var TouchHistoryMath = {
-  /**
-   * This code is optimized and not intended to look beautiful. This allows
-   * computing of touch centroids that have moved after `touchesChangedAfter`
-   * timeStamp. You can compute the current centroid involving all touches
-   * moves after `touchesChangedAfter`, or you can compute the previous
-   * centroid of all touches that were moved after `touchesChangedAfter`.
-   *
-   * @param {TouchHistoryMath} touchHistory Standard Responder touch track
-   * data.
-   * @param {number} touchesChangedAfter timeStamp after which moved touches
-   * are considered "actively moving" - not just "active".
-   * @param {boolean} isXAxis Consider `x` dimension vs. `y` dimension.
-   * @param {boolean} ofCurrent Compute current centroid for actively moving
-   * touches vs. previous centroid of now actively moving touches.
-   * @return {number} value of centroid in specified dimension.
-   */
-  centroidDimension: function(
-    touchHistory,
-    touchesChangedAfter,
-    isXAxis,
-    ofCurrent
-  ) {
-    var touchBank = touchHistory.touchBank;
-    var total = 0;
-    var count = 0;
-
-    var oneTouchData =
-      touchHistory.numberActiveTouches === 1
-        ? touchHistory.touchBank[touchHistory.indexOfSingleActiveTouch]
-        : null;
-
-    if (oneTouchData !== null) {
-      if (
-        oneTouchData.touchActive &&
-        oneTouchData.currentTimeStamp > touchesChangedAfter
-      ) {
-        total +=
-          ofCurrent && isXAxis
-            ? oneTouchData.currentPageX
-            : ofCurrent && !isXAxis
-              ? oneTouchData.currentPageY
-              : !ofCurrent && isXAxis
-                ? oneTouchData.previousPageX
-                : oneTouchData.previousPageY;
-        count = 1;
-      }
-    } else {
-      for (var i = 0; i < touchBank.length; i++) {
-        var touchTrack = touchBank[i];
-        if (
-          touchTrack !== null &&
-          touchTrack !== undefined &&
-          touchTrack.touchActive &&
-          touchTrack.currentTimeStamp >= touchesChangedAfter
-        ) {
-          var toAdd = void 0; // Yuck, program temporarily in invalid state.
-          if (ofCurrent && isXAxis) {
-            toAdd = touchTrack.currentPageX;
-          } else if (ofCurrent && !isXAxis) {
-            toAdd = touchTrack.currentPageY;
-          } else if (!ofCurrent && isXAxis) {
-            toAdd = touchTrack.previousPageX;
-          } else {
-            toAdd = touchTrack.previousPageY;
-          }
-          total += toAdd;
-          count++;
-        }
-      }
-    }
-    return count > 0 ? total / count : TouchHistoryMath.noCentroid;
-  },
-
-  currentCentroidXOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      true, // isXAxis
-      true
-    );
-  },
-
-  currentCentroidYOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      false, // isXAxis
-      true
-    );
-  },
-
-  previousCentroidXOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      true, // isXAxis
-      false
-    );
-  },
-
-  previousCentroidYOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      false, // isXAxis
-      false
-    );
-  },
-
-  currentCentroidX: function(touchHistory) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      0, // touchesChangedAfter
-      true, // isXAxis
-      true
-    );
-  },
-
-  currentCentroidY: function(touchHistory) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      0, // touchesChangedAfter
-      false, // isXAxis
-      true
-    );
-  },
-
-  noCentroid: -1
-};
-
 // TODO: this is special because it gets imported during build.
 
 var ReactVersion = "16.3.1";
 
-function _classCallCheck(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
-  }
-}
-
-var objects = {};
-var uniqueID = 1;
-var emptyObject$2 = {};
-
-var ReactNativePropRegistry = (function() {
-  function ReactNativePropRegistry() {
-    _classCallCheck(this, ReactNativePropRegistry);
-  }
-
-  ReactNativePropRegistry.register = function register(object) {
-    var id = ++uniqueID;
-    {
-      Object.freeze(object);
-    }
-    objects[id] = object;
-    return id;
-  };
-
-  ReactNativePropRegistry.getByID = function getByID(id) {
-    if (!id) {
-      // Used in the style={[condition && id]} pattern,
-      // we want it to be a no-op when the value is false or null
-      return emptyObject$2;
-    }
-
-    var object = objects[id];
-    if (!object) {
-      console.warn("Invalid style with id `" + id + "`. Skipping ...");
-      return emptyObject$2;
-    }
-    return object;
-  };
-
-  return ReactNativePropRegistry;
-})();
-
 // Modules provided by RN:
 var emptyObject$1 = {};
 
@@ -2717,13 +2420,6 @@ function defaultDiffer(prevProp, nextProp) {
   }
 }
 
-function resolveObject(idOrObject) {
-  if (typeof idOrObject === "number") {
-    return ReactNativePropRegistry.getByID(idOrObject);
-  }
-  return idOrObject;
-}
-
 function restoreDeletedValuesInNestedArray(
   updatePayload,
   node,
@@ -2739,7 +2435,7 @@ function restoreDeletedValuesInNestedArray(
       );
     }
   } else if (node && removedKeyCount > 0) {
-    var obj = resolveObject(node);
+    var obj = node;
     for (var propKey in removedKeys) {
       if (!removedKeys[propKey]) {
         continue;
@@ -2843,12 +2539,7 @@ function diffNestedProperty(
 
   if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
     // Both are leaves, we can diff the leaves.
-    return diffProperties(
-      updatePayload,
-      resolveObject(prevProp),
-      resolveObject(nextProp),
-      validAttributes
-    );
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
   }
 
   if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
@@ -2867,14 +2558,14 @@ function diffNestedProperty(
       // $FlowFixMe - We know that this is always an object when the input is.
       flattenStyle(prevProp),
       // $FlowFixMe - We know that this isn't an array because of above flow.
-      resolveObject(nextProp),
+      nextProp,
       validAttributes
     );
   }
 
   return diffProperties(
     updatePayload,
-    resolveObject(prevProp),
+    prevProp,
     // $FlowFixMe - We know that this is always an object when the input is.
     flattenStyle(nextProp),
     validAttributes
@@ -2893,11 +2584,7 @@ function addNestedProperty(updatePayload, nextProp, validAttributes) {
 
   if (!Array.isArray(nextProp)) {
     // Add each property of the leaf.
-    return addProperties(
-      updatePayload,
-      resolveObject(nextProp),
-      validAttributes
-    );
+    return addProperties(updatePayload, nextProp, validAttributes);
   }
 
   for (var i = 0; i < nextProp.length; i++) {
@@ -2923,11 +2610,7 @@ function clearNestedProperty(updatePayload, prevProp, validAttributes) {
 
   if (!Array.isArray(prevProp)) {
     // Add each property of the leaf.
-    return clearProperties(
-      updatePayload,
-      resolveObject(prevProp),
-      validAttributes
-    );
+    return clearProperties(updatePayload, prevProp, validAttributes);
   }
 
   for (var i = 0; i < prevProp.length; i++) {
@@ -3214,361 +2897,195 @@ function warnForStyleProps(props, validAttributes) {
   }
 }
 
-/**
- * `ReactInstanceMap` maintains a mapping from a public facing stateful
- * instance (key) and the internal representation (value). This allows public
- * methods to accept the user facing instance as an argument and map them back
- * to internal methods.
- *
- * Note that this module is currently shared and assumed to be stateless.
- * If this becomes an actual Map, that will break.
- */
-
-/**
- * This API should be called `delete` but we'd have to make sure to always
- * transform these to strings for IE support. When this transform is fully
- * supported we can rename it.
- */
-
-function get(key) {
-  return key._reactInternalFiber;
-}
-
-function set(key, value) {
-  key._reactInternalFiber = value;
-}
-
-var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
-
-var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
-var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
-
-function getComponentName(fiber) {
-  var type = fiber.type;
-
-  if (typeof type === "function") {
-    return type.displayName || type.name;
-  }
-  if (typeof type === "string") {
-    return type;
-  }
-  switch (type) {
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
-  }
-  return null;
-}
-
-// TODO: Share this module between Fabric and React Native renderers
-// so that both can be used in the same tree.
-
-var findHostInstance = function(fiber) {
-  return null;
-};
-
-var findHostInstanceFabric = function(fiber) {
-  return null;
-};
-
-function injectFindHostInstanceFabric(impl) {
-  findHostInstanceFabric = impl;
-}
-
-/**
- * ReactNative vs ReactWeb
- * -----------------------
- * React treats some pieces of data opaquely. This means that the information
- * is first class (it can be passed around), but cannot be inspected. This
- * allows us to build infrastructure that reasons about resources, without
- * making assumptions about the nature of those resources, and this allows that
- * infra to be shared across multiple platforms, where the resources are very
- * different. General infra (such as `ReactMultiChild`) reasons opaquely about
- * the data, but platform specific code (such as `ReactNativeBaseComponent`) can
- * make assumptions about the data.
- *
- *
- * `rootNodeID`, uniquely identifies a position in the generated native view
- * tree. Many layers of composite components (created with `React.createClass`)
- * can all share the same `rootNodeID`.
- *
- * `nodeHandle`: A sufficiently unambiguous way to refer to a lower level
- * resource (dom node, native view etc). The `rootNodeID` is sufficient for web
- * `nodeHandle`s, because the position in a tree is always enough to uniquely
- * identify a DOM node (we never have nodes in some bank outside of the
- * document). The same would be true for `ReactNative`, but we must maintain a
- * mapping that we can send efficiently serializable
- * strings across native boundaries.
- *
- * Opaque name      TodaysWebReact   FutureWebWorkerReact   ReactNative
- * ----------------------------------------------------------------------------
- * nodeHandle       N/A              rootNodeID             tag
- */
-
-// TODO (bvaughn) Rename the findNodeHandle module to something more descriptive
-// eg findInternalHostInstance. This will reduce the likelihood of someone
-// accidentally deep-requiring this version.
-function findNodeHandle(componentOrHandle) {
-  {
-    var owner = ReactCurrentOwner.current;
-    if (owner !== null && owner.stateNode !== null) {
-      !owner.stateNode._warnedAboutRefsInRender
-        ? warning(
-            false,
-            "%s is accessing findNodeHandle inside its render(). " +
-              "render() should be a pure function of props and state. It should " +
-              "never access something that requires stale data from the previous " +
-              "render, such as refs. Move this logic to componentDidMount and " +
-              "componentDidUpdate instead.",
-            getComponentName(owner) || "A component"
-          )
-        : void 0;
-
-      owner.stateNode._warnedAboutRefsInRender = true;
-    }
-  }
-  if (componentOrHandle == null) {
-    return null;
-  }
-  if (typeof componentOrHandle === "number") {
-    // Already a node handle
-    return componentOrHandle;
-  }
-
-  var component = componentOrHandle;
-
-  // TODO (balpert): Wrap iOS native components in a composite wrapper, then
-  // ReactInstanceMap.get here will always succeed for mounted components
-  var internalInstance = get(component);
-  if (internalInstance) {
-    return (
-      findHostInstance(internalInstance) ||
-      findHostInstanceFabric(internalInstance)
-    );
-  } else {
-    if (component) {
-      return component;
-    } else {
-      invariant(
-        // Native
-        (typeof component === "object" && "_nativeTag" in component) ||
-          // Composite
-          (component.render != null && typeof component.render === "function"),
-        "findNodeHandle(...): Argument is not a component " +
-          "(type: %s, keys: %s)",
-        typeof component,
-        Object.keys(component)
-      );
-      invariant(
-        false,
-        "findNodeHandle(...): Unable to find node handle for unmounted " +
-          "component."
-      );
-    }
-  }
-}
-
-/**
- * External users of findNodeHandle() expect the host tag number return type.
- * The injected findNodeHandle() strategy returns the instance wrapper though.
- * See NativeMethodsMixin#setNativeProps for more info on why this is done.
- */
-function findNumericNodeHandleFiber(componentOrHandle) {
-  var instance = findNodeHandle(componentOrHandle);
-  if (instance == null || typeof instance === "number") {
-    return instance;
-  }
-  return instance._nativeTag;
-}
-
 // Modules provided by RN:
-/**
- * `NativeMethodsMixin` provides methods to access the underlying native
- * component directly. This can be useful in cases when you want to focus
- * a view or measure its on-screen dimensions, for example.
- *
- * The methods described here are available on most of the default components
- * provided by React Native. Note, however, that they are *not* available on
- * composite components that aren't directly backed by a native view. This will
- * generally include most components that you define in your own app. For more
- * information, see [Direct
- * Manipulation](docs/direct-manipulation.html).
- *
- * Note the Flow $Exact<> syntax is required to support mixins.
- * React createClass mixins can only be used with exact types.
- */
-var NativeMethodsMixin = {
+var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
   /**
-   * Determines the location on screen, width, and height of the given view and
-   * returns the values via an async callback. If successful, the callback will
-   * be called with the following arguments:
+   * `NativeMethodsMixin` provides methods to access the underlying native
+   * component directly. This can be useful in cases when you want to focus
+   * a view or measure its on-screen dimensions, for example.
    *
-   *  - x
-   *  - y
-   *  - width
-   *  - height
-   *  - pageX
-   *  - pageY
+   * The methods described here are available on most of the default components
+   * provided by React Native. Note, however, that they are *not* available on
+   * composite components that aren't directly backed by a native view. This will
+   * generally include most components that you define in your own app. For more
+   * information, see [Direct
+   * Manipulation](docs/direct-manipulation.html).
    *
-   * Note that these measurements are not available until after the rendering
-   * has been completed in native. If you need the measurements as soon as
-   * possible, consider using the [`onLayout`
-   * prop](docs/view.html#onlayout) instead.
+   * Note the Flow $Exact<> syntax is required to support mixins.
+   * React createClass mixins can only be used with exact types.
    */
-  measure: function(callback) {
-    UIManager.measure(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  },
+  var NativeMethodsMixin = {
+    /**
+     * Determines the location on screen, width, and height of the given view and
+     * returns the values via an async callback. If successful, the callback will
+     * be called with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native. If you need the measurements as soon as
+     * possible, consider using the [`onLayout`
+     * prop](docs/view.html#onlayout) instead.
+     */
+    measure: function(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
 
-  /**
-   * Determines the location of the given view in the window and returns the
-   * values via an async callback. If the React root view is embedded in
-   * another native view, this will give you the absolute coordinates. If
-   * successful, the callback will be called with the following
-   * arguments:
-   *
-   *  - x
-   *  - y
-   *  - width
-   *  - height
-   *
-   * Note that these measurements are not available until after the rendering
-   * has been completed in native.
-   */
-  measureInWindow: function(callback) {
-    UIManager.measureInWindow(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  },
+    /**
+     * Determines the location of the given view in the window and returns the
+     * values via an async callback. If the React root view is embedded in
+     * another native view, this will give you the absolute coordinates. If
+     * successful, the callback will be called with the following
+     * arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native.
+     */
+    measureInWindow: function(callback) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
 
-  /**
-   * Like [`measure()`](#measure), but measures the view relative an ancestor,
-   * specified as `relativeToNativeNode`. This means that the returned x, y
-   * are relative to the origin x, y of the ancestor view.
-   *
-   * As always, to obtain a native node handle for a component, you can use
-   * `findNumericNodeHandle(component)`.
-   */
-  measureLayout: function(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      findNumericNodeHandleFiber(this),
+    /**
+     * Like [`measure()`](#measure), but measures the view relative an ancestor,
+     * specified as `relativeToNativeNode`. This means that the returned x, y
+     * are relative to the origin x, y of the ancestor view.
+     *
+     * As always, to obtain a native node handle for a component, you can use
+     * `findNodeHandle(component)`.
+     */
+    measureLayout: function(
       relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  },
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    },
 
-  /**
-   * This function sends props straight to native. They will not participate in
-   * future diff process - this means that if you do not include them in the
-   * next render, they will remain active (see [Direct
-   * Manipulation](docs/direct-manipulation.html)).
-   */
-  setNativeProps: function(nativeProps) {
-    // Class components don't have viewConfig -> validateAttributes.
-    // Nor does it make sense to set native props on a non-native component.
-    // Instead, find the nearest host component and set props on it.
-    // Use findNodeHandle() rather than findNumericNodeHandle() because
-    // We want the instance/wrapper (not the native tag).
-    var maybeInstance = void 0;
-
-    // Fiber errors if findNodeHandle is called for an umounted component.
-    // Tests using ReactTestRenderer will trigger this case indirectly.
-    // Mimicking stack behavior, we should silently ignore this case.
-    // TODO Fix ReactTestRenderer so we can remove this try/catch.
-    try {
-      maybeInstance = findNodeHandle(this);
-    } catch (error) {}
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
+    setNativeProps: function(nativeProps) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
+
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
 
-    // If there is no host component beneath this we should fail silently.
-    // This is not an error; it could mean a class component rendered null.
-    if (maybeInstance == null) {
-      return;
-    }
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
 
-    var viewConfig = maybeInstance.viewConfig;
+      var viewConfig = maybeInstance.viewConfig;
 
-    {
-      warnForStyleProps(nativeProps, viewConfig.validAttributes);
-    }
+      {
+        warnForStyleProps(nativeProps, viewConfig.validAttributes);
+      }
 
-    var updatePayload = create(nativeProps, viewConfig.validAttributes);
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
 
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        maybeInstance._nativeTag,
-        viewConfig.uiViewClassName,
-        updatePayload
-      );
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    },
+
+    /**
+     * Requests focus for the given input or view. The exact behavior triggered
+     * will depend on the platform and type of view.
+     */
+    focus: function() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    },
+
+    /**
+     * Removes focus from an input or view. This is the opposite of `focus()`.
+     */
+    blur: function() {
+      TextInputState.blurTextInput(findNodeHandle(this));
     }
-  },
+  };
 
-  /**
-   * Requests focus for the given input or view. The exact behavior triggered
-   * will depend on the platform and type of view.
-   */
-  focus: function() {
-    TextInputState.focusTextInput(findNumericNodeHandleFiber(this));
-  },
+  {
+    // hide this from Flow since we can't define these properties outside of
+    // true without actually implementing them (setting them to undefined
+    // isn't allowed by ReactClass)
+    var NativeMethodsMixin_DEV = NativeMethodsMixin;
+    invariant(
+      !NativeMethodsMixin_DEV.componentWillMount &&
+        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
+      "Do not override existing functions."
+    );
+    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
+    // Once these lifecycles have been remove from the reconciler.
+    NativeMethodsMixin_DEV.componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
+      throwOnStylesProp(this, newProps);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
+      newProps
+    ) {
+      throwOnStylesProp(this, newProps);
+    };
 
-  /**
-   * Removes focus from an input or view. This is the opposite of `focus()`.
-   */
-  blur: function() {
-    TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
+    // React may warn about cWM/cWRP/cWU methods being deprecated.
+    // Add a flag to suppress these warnings for this special case.
+    // TODO (bvaughn) Remove this flag once the above methods have been removed.
+    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
+    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
   }
-};
-
-{
-  // hide this from Flow since we can't define these properties outside of
-  // true without actually implementing them (setting them to undefined
-  // isn't allowed by ReactClass)
-  var NativeMethodsMixin_DEV = NativeMethodsMixin;
-  invariant(
-    !NativeMethodsMixin_DEV.componentWillMount &&
-      !NativeMethodsMixin_DEV.componentWillReceiveProps &&
-      !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
-      !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
-    "Do not override existing functions."
-  );
-  // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
-  // Once these lifecycles have been remove from the reconciler.
-  NativeMethodsMixin_DEV.componentWillMount = function() {
-    throwOnStylesProp(this, this.props);
-  };
-  NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
-    throwOnStylesProp(this, newProps);
-  };
-  NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
-    throwOnStylesProp(this, this.props);
-  };
-  NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(newProps) {
-    throwOnStylesProp(this, newProps);
-  };
 
-  // React may warn about cWM/cWRP/cWU methods being deprecated.
-  // Add a flag to suppress these warnings for this special case.
-  // TODO (bvaughn) Remove this flag once the above methods have been removed.
-  NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
-  NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
-}
+  return NativeMethodsMixin;
+};
 
-function _classCallCheck$1(instance, Constructor) {
+function _classCallCheck(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
     throw new TypeError("Cannot call a class as a function");
   }
@@ -3607,166 +3124,171 @@ function _inherits(subClass, superClass) {
 }
 
 // Modules provided by RN:
-/**
- * Superclass that provides methods to access the underlying native component.
- * This can be useful when you want to focus a view or measure its dimensions.
- *
- * Methods implemented by this class are available on most default components
- * provided by React Native. However, they are *not* available on composite
- * components that are not directly backed by a native view. For more
- * information, see [Direct Manipulation](docs/direct-manipulation.html).
- *
- * @abstract
- */
-
-var ReactNativeComponent = (function(_React$Component) {
-  _inherits(ReactNativeComponent, _React$Component);
+var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
+  /**
+   * Superclass that provides methods to access the underlying native component.
+   * This can be useful when you want to focus a view or measure its dimensions.
+   *
+   * Methods implemented by this class are available on most default components
+   * provided by React Native. However, they are *not* available on composite
+   * components that are not directly backed by a native view. For more
+   * information, see [Direct Manipulation](docs/direct-manipulation.html).
+   *
+   * @abstract
+   */
+  var ReactNativeComponent = (function(_React$Component) {
+    _inherits(ReactNativeComponent, _React$Component);
 
-  function ReactNativeComponent() {
-    _classCallCheck$1(this, ReactNativeComponent);
+    function ReactNativeComponent() {
+      _classCallCheck(this, ReactNativeComponent);
 
-    return _possibleConstructorReturn(
-      this,
-      _React$Component.apply(this, arguments)
-    );
-  }
+      return _possibleConstructorReturn(
+        this,
+        _React$Component.apply(this, arguments)
+      );
+    }
 
-  /**
-   * Removes focus. This is the opposite of `focus()`.
-   */
+    /**
+     * Removes focus. This is the opposite of `focus()`.
+     */
 
-  /**
-   * Due to bugs in Flow's handling of React.createClass, some fields already
-   * declared in the base class need to be redeclared below.
-   */
-  ReactNativeComponent.prototype.blur = function blur() {
-    TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
-  };
+    /**
+     * Due to bugs in Flow's handling of React.createClass, some fields already
+     * declared in the base class need to be redeclared below.
+     */
+    ReactNativeComponent.prototype.blur = function blur() {
+      TextInputState.blurTextInput(findNodeHandle(this));
+    };
 
-  /**
-   * Requests focus. The exact behavior depends on the platform and view.
-   */
+    /**
+     * Requests focus. The exact behavior depends on the platform and view.
+     */
 
-  ReactNativeComponent.prototype.focus = function focus() {
-    TextInputState.focusTextInput(findNumericNodeHandleFiber(this));
-  };
+    ReactNativeComponent.prototype.focus = function focus() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    };
 
-  /**
-   * Measures the on-screen location and dimensions. If successful, the callback
-   * will be called asynchronously with the following arguments:
-   *
-   *  - x
-   *  - y
-   *  - width
-   *  - height
-   *  - pageX
-   *  - pageY
-   *
-   * These values are not available until after natives rendering completes. If
-   * you need the measurements as soon as possible, consider using the
-   * [`onLayout` prop](docs/view.html#onlayout) instead.
-   */
+    /**
+     * Measures the on-screen location and dimensions. If successful, the callback
+     * will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * These values are not available until after natives rendering completes. If
+     * you need the measurements as soon as possible, consider using the
+     * [`onLayout` prop](docs/view.html#onlayout) instead.
+     */
 
-  ReactNativeComponent.prototype.measure = function measure(callback) {
-    UIManager.measure(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  };
+    ReactNativeComponent.prototype.measure = function measure(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
 
-  /**
-   * Measures the on-screen location and dimensions. Even if the React Native
-   * root view is embedded within another native view, this method will give you
-   * the absolute coordinates measured from the window. If successful, the
-   * callback will be called asynchronously with the following arguments:
-   *
-   *  - x
-   *  - y
-   *  - width
-   *  - height
-   *
-   * These values are not available until after natives rendering completes.
-   */
+    /**
+     * Measures the on-screen location and dimensions. Even if the React Native
+     * root view is embedded within another native view, this method will give you
+     * the absolute coordinates measured from the window. If successful, the
+     * callback will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * These values are not available until after natives rendering completes.
+     */
 
-  ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
-    callback
-  ) {
-    UIManager.measureInWindow(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  };
+    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
 
-  /**
-   * Similar to [`measure()`](#measure), but the resulting location will be
-   * relative to the supplied ancestor's location.
-   *
-   * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
-   */
+    /**
+     * Similar to [`measure()`](#measure), but the resulting location will be
+     * relative to the supplied ancestor's location.
+     *
+     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
+     */
 
-  ReactNativeComponent.prototype.measureLayout = function measureLayout(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      findNumericNodeHandleFiber(this),
+    ReactNativeComponent.prototype.measureLayout = function measureLayout(
       relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  };
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
 
-  /**
-   * This function sends props straight to native. They will not participate in
-   * future diff process - this means that if you do not include them in the
-   * next render, they will remain active (see [Direct
-   * Manipulation](docs/direct-manipulation.html)).
-   */
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
 
-  ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
-    nativeProps
-  ) {
-    // Class components don't have viewConfig -> validateAttributes.
-    // Nor does it make sense to set native props on a non-native component.
-    // Instead, find the nearest host component and set props on it.
-    // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
-    // We want the instance/wrapper (not the native tag).
-    var maybeInstance = void 0;
-
-    // Fiber errors if findNodeHandle is called for an umounted component.
-    // Tests using ReactTestRenderer will trigger this case indirectly.
-    // Mimicking stack behavior, we should silently ignore this case.
-    // TODO Fix ReactTestRenderer so we can remove this try/catch.
-    try {
-      maybeInstance = findNodeHandle(this);
-    } catch (error) {}
+    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
+      nativeProps
+    ) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
+
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
 
-    // If there is no host component beneath this we should fail silently.
-    // This is not an error; it could mean a class component rendered null.
-    if (maybeInstance == null) {
-      return;
-    }
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
 
-    var viewConfig =
-      maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+      var viewConfig =
+        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
 
-    var updatePayload = create(nativeProps, viewConfig.validAttributes);
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
 
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        maybeInstance._nativeTag,
-        viewConfig.uiViewClassName,
-        updatePayload
-      );
-    }
-  };
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    };
+
+    return ReactNativeComponent;
+  })(React.Component);
+
+  // eslint-disable-next-line no-unused-expressions
 
   return ReactNativeComponent;
-})(React.Component);
+};
 
 var hasNativePerformanceNow =
   typeof performance === "object" && typeof performance.now === "function";
@@ -3817,47 +3339,55 @@ function cancelDeferredCallback(callbackID) {
   clearTimeout(callbackID);
 }
 
-var viewConfigCallbacks = new Map();
-var viewConfigs = new Map();
-
 /**
- * Registers a native view/component by name.
- * A callback is provided to load the view config from UIManager.
- * The callback is deferred until the view is actually rendered.
- * This is done to avoid causing Prepack deopts.
+ * `ReactInstanceMap` maintains a mapping from a public facing stateful
+ * instance (key) and the internal representation (value). This allows public
+ * methods to accept the user facing instance as an argument and map them back
+ * to internal methods.
+ *
+ * Note that this module is currently shared and assumed to be stateless.
+ * If this becomes an actual Map, that will break.
  */
-function register(name, callback) {
-  invariant(
-    !viewConfigCallbacks.has(name),
-    "Tried to register two views with the same name %s",
-    name
-  );
-  viewConfigCallbacks.set(name, callback);
-  return name;
-}
 
 /**
- * Retrieves a config for the specified view.
- * If this is the first time the view has been used,
- * This configuration will be lazy-loaded from UIManager.
+ * This API should be called `delete` but we'd have to make sure to always
+ * transform these to strings for IE support. When this transform is fully
+ * supported we can rename it.
  */
-function get$1(name) {
-  var viewConfig = void 0;
-  if (!viewConfigs.has(name)) {
-    var callback = viewConfigCallbacks.get(name);
-    invariant(
-      typeof callback === "function",
-      "View config not found for name %s",
-      name
-    );
-    viewConfigCallbacks.set(name, null);
-    viewConfig = callback();
-    viewConfigs.set(name, viewConfig);
-  } else {
-    viewConfig = viewConfigs.get(name);
+
+function get$1(key) {
+  return key._reactInternalFiber;
+}
+
+function set(key, value) {
+  key._reactInternalFiber = value;
+}
+
+var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+
+var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
+var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
+
+function getComponentName(fiber) {
+  var type = fiber.type;
+
+  if (typeof type === "function") {
+    return type.displayName || type.name;
+  }
+  if (typeof type === "string") {
+    return type;
   }
-  invariant(viewConfig, "View config not found for name %s", name);
-  return viewConfig;
+  switch (type) {
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_RETURN_TYPE:
+      return "ReactReturn";
+  }
+  return null;
 }
 
 // Don't change these two values. They're used by React Dev Tools.
@@ -3940,7 +3470,7 @@ function isMounted(component) {
     }
   }
 
-  var fiber = get(component);
+  var fiber = get$1(component);
   if (!fiber) {
     return false;
   }
@@ -5947,7 +5477,7 @@ var ReactFiberClassComponent = function(
   var updater = {
     isMounted: isMounted,
     enqueueSetState: function(instance, partialState, callback) {
-      var fiber = get(instance);
+      var fiber = get$1(instance);
       callback = callback === undefined ? null : callback;
       {
         warnOnInvalidCallback(callback, "setState");
@@ -5966,7 +5496,7 @@ var ReactFiberClassComponent = function(
       scheduleWork(fiber, expirationTime);
     },
     enqueueReplaceState: function(instance, state, callback) {
-      var fiber = get(instance);
+      var fiber = get$1(instance);
       callback = callback === undefined ? null : callback;
       {
         warnOnInvalidCallback(callback, "replaceState");
@@ -5985,7 +5515,7 @@ var ReactFiberClassComponent = function(
       scheduleWork(fiber, expirationTime);
     },
     enqueueForceUpdate: function(instance, callback) {
-      var fiber = get(instance);
+      var fiber = get$1(instance);
       callback = callback === undefined ? null : callback;
       {
         warnOnInvalidCallback(callback, "forceUpdate");
@@ -9418,7 +8948,7 @@ var ReactFiberCompleteWork = function(
 
   function markUpdate(workInProgress) {
     // Tag the fiber with an update effect. This turns a Placement into
-    // an UpdateAndPlacement.
+    // a PlacementAndUpdate.
     workInProgress.effectTag |= Update;
   }
 
@@ -13584,7 +13114,7 @@ var ReactFiberReconciler$1 = function(config) {
       return emptyObject;
     }
 
-    var fiber = get(parentComponent);
+    var fiber = get$1(parentComponent);
     var parentContext = findCurrentUnmaskedContext(fiber);
     return isContextProvider(fiber)
       ? processChildContext(fiber, parentContext)
@@ -13682,7 +13212,19 @@ var ReactFiberReconciler$1 = function(config) {
     );
   }
 
-  function findHostInstance(fiber) {
+  function findHostInstance(component) {
+    var fiber = get$1(component);
+    if (fiber === undefined) {
+      if (typeof component.render === "function") {
+        invariant(false, "Unable to find node on an unmounted component.");
+      } else {
+        invariant(
+          false,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        );
+      }
+    }
     var hostFiber = findCurrentHostFiber(fiber);
     if (hostFiber === null) {
       return null;
@@ -13775,7 +13317,11 @@ var ReactFiberReconciler$1 = function(config) {
       return injectInternals(
         Object.assign({}, devToolsConfig, {
           findHostInstanceByFiber: function(fiber) {
-            return findHostInstance(fiber);
+            var hostFiber = findCurrentHostFiber(fiber);
+            if (hostFiber === null) {
+              return null;
+            }
+            return hostFiber.stateNode;
           },
           findFiberByHostInstance: function(instance) {
             if (!findFiberByHostInstance) {
@@ -13805,62 +13351,26 @@ var reactReconciler = ReactFiberReconciler$3["default"]
   ? ReactFiberReconciler$3["default"]
   : ReactFiberReconciler$3;
 
-/**
- * Keeps track of allocating and associating native "tags" which are numeric,
- * unique view IDs. All the native tags are negative numbers, to avoid
- * collisions, but in the JS we keep track of them as positive integers to store
- * them effectively in Arrays. So we must refer to them as "inverses" of the
- * native tags (that are * normally negative).
- *
- * It *must* be the case that every `rootNodeID` always maps to the exact same
- * `tag` forever. The easiest way to accomplish this is to never delete
- * anything from this table.
- * Why: Because `dangerouslyReplaceNodeWithMarkupByID` relies on being able to
- * unmount a component with a `rootNodeID`, then mount a new one in its place,
- */
-var INITIAL_TAG_COUNT = 1;
-var ReactNativeTagHandles = {
-  tagsStartAt: INITIAL_TAG_COUNT,
-  tagCount: INITIAL_TAG_COUNT,
-
-  allocateTag: function() {
-    // Skip over root IDs as those are reserved for native
-    while (this.reactTagIsNativeTopRootID(ReactNativeTagHandles.tagCount)) {
-      ReactNativeTagHandles.tagCount++;
-    }
-    var tag = ReactNativeTagHandles.tagCount;
-    ReactNativeTagHandles.tagCount++;
-    return tag;
-  },
-
-  assertRootTag: function(tag) {
-    invariant(
-      this.reactTagIsNativeTopRootID(tag),
-      "Expect a native root tag, instead got %s",
-      tag
-    );
-  },
-
-  reactTagIsNativeTopRootID: function(reactTag) {
-    // We reserve all tags that are 1 mod 10 for native root views
-    return reactTag % 10 === 1;
-  }
-};
-
-function _classCallCheck$2(instance, Constructor) {
+function _classCallCheck$1(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
     throw new TypeError("Cannot call a class as a function");
   }
 }
 
 // Modules provided by RN:
+// Counter for uniquely identifying views.
+// % 10 === 1 means it is a rootTag.
+// % 2 === 0 means it is a Fabric tag.
+// This means that they never overlap.
+var nextReactTag = 2;
+
 /**
  * This is used for refs on host components.
  */
 
 var ReactFabricHostComponent = (function() {
   function ReactFabricHostComponent(tag, viewConfig, props) {
-    _classCallCheck$2(this, ReactFabricHostComponent);
+    _classCallCheck$1(this, ReactFabricHostComponent);
 
     this._nativeTag = tag;
     this.viewConfig = viewConfig;
@@ -13936,8 +13446,10 @@ var ReactFabricRenderer = reactReconciler({
     hostContext,
     internalInstanceHandle
   ) {
-    var tag = ReactNativeTagHandles.allocateTag();
-    var viewConfig = get$1(type);
+    var tag = nextReactTag;
+    nextReactTag += 2;
+
+    var viewConfig = ReactNativeViewConfigRegistry.get(type);
 
     {
       for (var key in viewConfig.validAttributes) {
@@ -13970,7 +13482,8 @@ var ReactFabricRenderer = reactReconciler({
     hostContext,
     internalInstanceHandle
   ) {
-    var tag = ReactNativeTagHandles.allocateTag();
+    var tag = nextReactTag;
+    nextReactTag += 2;
 
     var node = FabricUIManager.createNode(
       tag, // reactTag
@@ -14190,56 +13703,59 @@ var getInspectorDataForViewTag = void 0;
   };
 }
 
-/**
- * Creates a renderable ReactNative host component.
- * Use this method for view configs that are loaded from UIManager.
- * Use createReactNativeComponentClass() for view configs defined within JavaScript.
- *
- * @param {string} config iOS View configuration.
- * @private
- */
-var createReactNativeComponentClass = function(name, callback) {
-  return register(name, callback);
-};
+var findHostInstance = ReactFabricRenderer.findHostInstance;
 
-// Module provided by RN:
-/**
- * Capture an image of the screen, window or an individual view. The image
- * will be stored in a temporary file that will only exist for as long as the
- * app is running.
- *
- * The `view` argument can be the literal string `window` if you want to
- * capture the entire window, or it can be a reference to a specific
- * React Native component.
- *
- * The `options` argument may include:
- * - width/height (number) - the width and height of the image to capture.
- * - format (string) - either 'png' or 'jpeg'. Defaults to 'png'.
- * - quality (number) - the quality when using jpeg. 0.0 - 1.0 (default).
- *
- * Returns a Promise.
- * @platform ios
- */
-function takeSnapshot(view, options) {
-  if (typeof view !== "number" && view !== "window") {
-    view = findNumericNodeHandleFiber(view) || "window";
-  }
+function findNodeHandle(componentOrHandle) {
+  {
+    var owner = ReactCurrentOwner.current;
+    if (owner !== null && owner.stateNode !== null) {
+      !owner.stateNode._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing findNodeHandle inside its render(). " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(owner) || "A component"
+          )
+        : void 0;
 
-  // Call the hidden '__takeSnapshot' method; the main one throws an error to
-  // prevent accidental backwards-incompatible usage.
-  return UIManager.__takeSnapshot(view, options);
+      owner.stateNode._warnedAboutRefsInRender = true;
+    }
+  }
+  if (componentOrHandle == null) {
+    return null;
+  }
+  if (typeof componentOrHandle === "number") {
+    // Already a node handle
+    return componentOrHandle;
+  }
+  if (componentOrHandle._nativeTag) {
+    return componentOrHandle._nativeTag;
+  }
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag) {
+    return componentOrHandle.canonical._nativeTag;
+  }
+  var hostInstance = findHostInstance(componentOrHandle);
+  if (hostInstance == null) {
+    return hostInstance;
+  }
+  if (hostInstance.canonical) {
+    // Fabric
+    return hostInstance.canonical._nativeTag;
+  }
+  return hostInstance._nativeTag;
 }
 
-injectFindHostInstanceFabric(ReactFabricRenderer.findHostInstance);
-
 injection$2.injectRenderer(ReactFabricRenderer);
 
 var roots = new Map();
 
 var ReactFabric = {
-  NativeComponent: ReactNativeComponent,
+  NativeComponent: ReactNativeComponent(findNodeHandle, findHostInstance),
 
-  findNodeHandle: findNumericNodeHandleFiber,
+  findNodeHandle: findNodeHandle,
 
   render: function(element, containerTag, callback) {
     var root = roots.get(containerTag);
@@ -14263,9 +13779,6 @@ var ReactFabric = {
       });
     }
   },
-  unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
-    ReactFabric.unmountComponentAtNode(containerTag);
-  },
   createPortal: function(children, containerTag) {
     var key =
       arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : null;
@@ -14273,20 +13786,11 @@ var ReactFabric = {
     return createPortal(children, containerTag, null, key);
   },
 
-  unstable_batchedUpdates: batchedUpdates,
-
-  flushSync: ReactFabricRenderer.flushSync,
-
   __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
     // Used as a mixin in many createClass-based components
-    NativeMethodsMixin: NativeMethodsMixin,
+    NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
     // Used by react-native-github/Libraries/ components
-    ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin, // requireNativeComponent
-    ReactNativeComponentTree: ReactNativeComponentTree, // ScrollResponder
-    ReactNativePropRegistry: ReactNativePropRegistry, // flattenStyle, Stylesheet
-    TouchHistoryMath: TouchHistoryMath, // PanResponder
-    createReactNativeComponentClass: createReactNativeComponentClass, // RCTText, RCTView, ReactNativeART
-    takeSnapshot: takeSnapshot
+    ReactNativeComponentTree: ReactNativeComponentTree
   }
 };
 
diff --git a/Libraries/Renderer/ReactFabric-prod.js b/Libraries/Renderer/ReactFabric-prod.js
index c57d9bb9d0c9..d264fcf01637 100644
--- a/Libraries/Renderer/ReactFabric-prod.js
+++ b/Libraries/Renderer/ReactFabric-prod.js
@@ -13,6 +13,7 @@
 require("InitializeCore");
 var invariant = require("fbjs/lib/invariant"),
   emptyFunction = require("fbjs/lib/emptyFunction"),
+  ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
   UIManager = require("UIManager"),
   TextInputState = require("TextInputState"),
   deepDiffer = require("deepDiffer"),
@@ -528,7 +529,7 @@ function changeResponder(nextResponderInst, blockHostResponder) {
       blockHostResponder
     );
 }
-var eventTypes = {
+var eventTypes$1 = {
     startShouldSetResponder: {
       phasedRegistrationNames: {
         bubbled: "onStartShouldSetResponder",
@@ -568,7 +569,7 @@ var eventTypes = {
     _getResponder: function() {
       return responderInst;
     },
-    eventTypes: eventTypes,
+    eventTypes: eventTypes$1,
     extractEvents: function(
       topLevelType,
       targetInst,
@@ -594,12 +595,12 @@ var eventTypes = {
           isMoveish(topLevelType))
       ) {
         var JSCompiler_temp = isStartish(topLevelType)
-          ? eventTypes.startShouldSetResponder
+          ? eventTypes$1.startShouldSetResponder
           : isMoveish(topLevelType)
-            ? eventTypes.moveShouldSetResponder
+            ? eventTypes$1.moveShouldSetResponder
             : "topSelectionChange" === topLevelType
-              ? eventTypes.selectionChangeShouldSetResponder
-              : eventTypes.scrollShouldSetResponder;
+              ? eventTypes$1.selectionChangeShouldSetResponder
+              : eventTypes$1.scrollShouldSetResponder;
         if (responderInst)
           b: {
             var JSCompiler_temp$jscomp$0 = responderInst;
@@ -685,7 +686,7 @@ var eventTypes = {
         JSCompiler_temp && JSCompiler_temp !== responderInst
           ? ((JSCompiler_temp$jscomp$0 = void 0),
             (targetInst = ResponderSyntheticEvent.getPooled(
-              eventTypes.responderGrant,
+              eventTypes$1.responderGrant,
               JSCompiler_temp,
               nativeEvent,
               nativeEventTarget
@@ -695,7 +696,7 @@ var eventTypes = {
             (depthA = !0 === executeDirectDispatch(targetInst)),
             responderInst
               ? ((tempA = ResponderSyntheticEvent.getPooled(
-                  eventTypes.responderTerminationRequest,
+                  eventTypes$1.responderTerminationRequest,
                   responderInst,
                   nativeEvent,
                   nativeEventTarget
@@ -707,7 +708,7 @@ var eventTypes = {
                 tempA.isPersistent() || tempA.constructor.release(tempA),
                 tempB
                   ? ((tempA = ResponderSyntheticEvent.getPooled(
-                      eventTypes.responderTerminate,
+                      eventTypes$1.responderTerminate,
                       responderInst,
                       nativeEvent,
                       nativeEventTarget
@@ -721,7 +722,7 @@ var eventTypes = {
                     )),
                     changeResponder(JSCompiler_temp, depthA))
                   : ((JSCompiler_temp = ResponderSyntheticEvent.getPooled(
-                      eventTypes.responderReject,
+                      eventTypes$1.responderReject,
                       JSCompiler_temp,
                       nativeEvent,
                       nativeEventTarget
@@ -749,10 +750,10 @@ var eventTypes = {
       depthA = responderInst && isEndish(topLevelType);
       if (
         (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
-          ? eventTypes.responderStart
+          ? eventTypes$1.responderStart
           : targetInst
-            ? eventTypes.responderMove
-            : depthA ? eventTypes.responderEnd : null)
+            ? eventTypes$1.responderMove
+            : depthA ? eventTypes$1.responderEnd : null)
       )
         (JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
           JSCompiler_temp$jscomp$0,
@@ -803,8 +804,8 @@ var eventTypes = {
         }
       if (
         (topLevelType = JSCompiler_temp$jscomp$0
-          ? eventTypes.responderTerminate
-          : topLevelType ? eventTypes.responderRelease : null)
+          ? eventTypes$1.responderTerminate
+          : topLevelType ? eventTypes$1.responderRelease : null)
       )
         (nativeEvent = ResponderSyntheticEvent.getPooled(
           topLevelType,
@@ -836,10 +837,12 @@ var eventTypes = {
       }
     }
   },
-  customBubblingEventTypes = {},
-  customDirectEventTypes = {},
+  customBubblingEventTypes$1 =
+    ReactNativeViewConfigRegistry.customBubblingEventTypes,
+  customDirectEventTypes$1 =
+    ReactNativeViewConfigRegistry.customDirectEventTypes,
   ReactNativeBridgeEventPlugin = {
-    eventTypes: {},
+    eventTypes: ReactNativeViewConfigRegistry.eventTypes,
     extractEvents: function(
       topLevelType,
       targetInst,
@@ -847,8 +850,8 @@ var eventTypes = {
       nativeEventTarget
     ) {
       if (null == targetInst) return null;
-      var bubbleDispatchConfig = customBubblingEventTypes[topLevelType],
-        directDispatchConfig = customDirectEventTypes[topLevelType];
+      var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType],
+        directDispatchConfig = customDirectEventTypes$1[topLevelType];
       invariant(
         bubbleDispatchConfig || directDispatchConfig,
         'Unsupported top level event type "%s" dispatched',
@@ -866,24 +869,6 @@ var eventTypes = {
         forEachAccumulated(topLevelType, accumulateDirectDispatchesSingle);
       else return null;
       return topLevelType;
-    },
-    processEventTypes: function(viewConfig) {
-      var bubblingEventTypes = viewConfig.bubblingEventTypes;
-      viewConfig = viewConfig.directEventTypes;
-      if (null != bubblingEventTypes)
-        for (var _topLevelType in bubblingEventTypes)
-          null == customBubblingEventTypes[_topLevelType] &&
-            (ReactNativeBridgeEventPlugin.eventTypes[
-              _topLevelType
-            ] = customBubblingEventTypes[_topLevelType] =
-              bubblingEventTypes[_topLevelType]);
-      if (null != viewConfig)
-        for (var _topLevelType2 in viewConfig)
-          null == customDirectEventTypes[_topLevelType2] &&
-            (ReactNativeBridgeEventPlugin.eventTypes[
-              _topLevelType2
-            ] = customDirectEventTypes[_topLevelType2] =
-              viewConfig[_topLevelType2]);
     }
   },
   instanceCache = {},
@@ -968,155 +953,9 @@ function createPortal(children, containerInfo, implementation) {
     implementation: implementation
   };
 }
-var restoreTarget = null,
-  restoreQueue = null;
-function restoreStateOfTarget(target) {
-  if ((target = getInstanceFromNode(target))) {
-    invariant(
-      null,
-      "Fiber needs to be injected to handle a fiber target for controlled events. This error is likely caused by a bug in React. Please file an issue."
-    );
-    var props = getFiberCurrentPropsFromNode(target.stateNode);
-    null.restoreControlledState(target.stateNode, target.type, props);
-  }
-}
-function _batchedUpdates(fn, bookkeeping) {
-  return fn(bookkeeping);
-}
-function _flushInteractiveUpdates() {}
-var isBatching = !1,
-  TouchHistoryMath = {
-    centroidDimension: function(
-      touchHistory,
-      touchesChangedAfter,
-      isXAxis,
-      ofCurrent
-    ) {
-      var touchBank = touchHistory.touchBank,
-        total = 0,
-        count = 0;
-      touchHistory =
-        1 === touchHistory.numberActiveTouches
-          ? touchHistory.touchBank[touchHistory.indexOfSingleActiveTouch]
-          : null;
-      if (null !== touchHistory)
-        touchHistory.touchActive &&
-          touchHistory.currentTimeStamp > touchesChangedAfter &&
-          ((total +=
-            ofCurrent && isXAxis
-              ? touchHistory.currentPageX
-              : ofCurrent && !isXAxis
-                ? touchHistory.currentPageY
-                : !ofCurrent && isXAxis
-                  ? touchHistory.previousPageX
-                  : touchHistory.previousPageY),
-          (count = 1));
-      else
-        for (
-          touchHistory = 0;
-          touchHistory < touchBank.length;
-          touchHistory++
-        ) {
-          var touchTrack = touchBank[touchHistory];
-          null !== touchTrack &&
-            void 0 !== touchTrack &&
-            touchTrack.touchActive &&
-            touchTrack.currentTimeStamp >= touchesChangedAfter &&
-            ((total +=
-              ofCurrent && isXAxis
-                ? touchTrack.currentPageX
-                : ofCurrent && !isXAxis
-                  ? touchTrack.currentPageY
-                  : !ofCurrent && isXAxis
-                    ? touchTrack.previousPageX
-                    : touchTrack.previousPageY),
-            count++);
-        }
-      return 0 < count ? total / count : TouchHistoryMath.noCentroid;
-    },
-    currentCentroidXOfTouchesChangedAfter: function(
-      touchHistory,
-      touchesChangedAfter
-    ) {
-      return TouchHistoryMath.centroidDimension(
-        touchHistory,
-        touchesChangedAfter,
-        !0,
-        !0
-      );
-    },
-    currentCentroidYOfTouchesChangedAfter: function(
-      touchHistory,
-      touchesChangedAfter
-    ) {
-      return TouchHistoryMath.centroidDimension(
-        touchHistory,
-        touchesChangedAfter,
-        !1,
-        !0
-      );
-    },
-    previousCentroidXOfTouchesChangedAfter: function(
-      touchHistory,
-      touchesChangedAfter
-    ) {
-      return TouchHistoryMath.centroidDimension(
-        touchHistory,
-        touchesChangedAfter,
-        !0,
-        !1
-      );
-    },
-    previousCentroidYOfTouchesChangedAfter: function(
-      touchHistory,
-      touchesChangedAfter
-    ) {
-      return TouchHistoryMath.centroidDimension(
-        touchHistory,
-        touchesChangedAfter,
-        !1,
-        !1
-      );
-    },
-    currentCentroidX: function(touchHistory) {
-      return TouchHistoryMath.centroidDimension(touchHistory, 0, !0, !0);
-    },
-    currentCentroidY: function(touchHistory) {
-      return TouchHistoryMath.centroidDimension(touchHistory, 0, !1, !0);
-    },
-    noCentroid: -1
-  },
-  objects = {},
-  uniqueID = 1,
-  emptyObject$2 = {},
-  ReactNativePropRegistry = (function() {
-    function ReactNativePropRegistry() {
-      if (!(this instanceof ReactNativePropRegistry))
-        throw new TypeError("Cannot call a class as a function");
-    }
-    ReactNativePropRegistry.register = function(object) {
-      var id = ++uniqueID;
-      objects[id] = object;
-      return id;
-    };
-    ReactNativePropRegistry.getByID = function(id) {
-      if (!id) return emptyObject$2;
-      var object = objects[id];
-      return object
-        ? object
-        : (console.warn("Invalid style with id `" + id + "`. Skipping ..."),
-          emptyObject$2);
-    };
-    return ReactNativePropRegistry;
-  })(),
-  emptyObject$1 = {},
+var emptyObject$1 = {},
   removedKeys = null,
   removedKeyCount = 0;
-function resolveObject(idOrObject) {
-  return "number" === typeof idOrObject
-    ? ReactNativePropRegistry.getByID(idOrObject)
-    : idOrObject;
-}
 function restoreDeletedValuesInNestedArray(
   updatePayload,
   node,
@@ -1130,7 +969,7 @@ function restoreDeletedValuesInNestedArray(
         validAttributes
       );
   else if (node && 0 < removedKeyCount)
-    for (i in ((node = resolveObject(node)), removedKeys))
+    for (i in removedKeys)
       if (removedKeys[i]) {
         var _nextProp = node[i];
         if (void 0 !== _nextProp) {
@@ -1169,12 +1008,7 @@ function diffNestedProperty(
         ? clearNestedProperty(updatePayload, prevProp, validAttributes)
         : updatePayload;
   if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
-    return diffProperties(
-      updatePayload,
-      resolveObject(prevProp),
-      resolveObject(nextProp),
-      validAttributes
-    );
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
   if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
     var minLength =
         prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
@@ -1204,12 +1038,12 @@ function diffNestedProperty(
     ? diffProperties(
         updatePayload,
         flattenStyle(prevProp),
-        resolveObject(nextProp),
+        nextProp,
         validAttributes
       )
     : diffProperties(
         updatePayload,
-        resolveObject(prevProp),
+        prevProp,
         flattenStyle(nextProp),
         validAttributes
       );
@@ -1217,9 +1051,11 @@ function diffNestedProperty(
 function addNestedProperty(updatePayload, nextProp, validAttributes) {
   if (!nextProp) return updatePayload;
   if (!Array.isArray(nextProp))
-    return (
-      (nextProp = resolveObject(nextProp)),
-      diffProperties(updatePayload, emptyObject$1, nextProp, validAttributes)
+    return diffProperties(
+      updatePayload,
+      emptyObject$1,
+      nextProp,
+      validAttributes
     );
   for (var i = 0; i < nextProp.length; i++)
     updatePayload = addNestedProperty(
@@ -1232,9 +1068,11 @@ function addNestedProperty(updatePayload, nextProp, validAttributes) {
 function clearNestedProperty(updatePayload, prevProp, validAttributes) {
   if (!prevProp) return updatePayload;
   if (!Array.isArray(prevProp))
-    return (
-      (prevProp = resolveObject(prevProp)),
-      diffProperties(updatePayload, prevProp, emptyObject$1, validAttributes)
+    return diffProperties(
+      updatePayload,
+      prevProp,
+      emptyObject$1,
+      validAttributes
     );
   for (var i = 0; i < prevProp.length; i++)
     updatePayload = clearNestedProperty(
@@ -1347,53 +1185,6 @@ function mountSafeCallback(context, callback) {
     }
   };
 }
-var ReactCurrentOwner =
-  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
-function getComponentName(fiber) {
-  fiber = fiber.type;
-  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
-  if ("string" === typeof fiber) return fiber;
-  switch (fiber) {
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
-  }
-  return null;
-}
-function findHostInstanceFabric() {
-  return null;
-}
-function findNodeHandle(componentOrHandle) {
-  if (null == componentOrHandle) return null;
-  if ("number" === typeof componentOrHandle) return componentOrHandle;
-  var internalInstance = componentOrHandle._reactInternalFiber;
-  if (internalInstance) return findHostInstanceFabric(internalInstance);
-  if (componentOrHandle) return componentOrHandle;
-  invariant(
-    ("object" === typeof componentOrHandle &&
-      "_nativeTag" in componentOrHandle) ||
-      (null != componentOrHandle.render &&
-        "function" === typeof componentOrHandle.render),
-    "findNodeHandle(...): Argument is not a component (type: %s, keys: %s)",
-    typeof componentOrHandle,
-    Object.keys(componentOrHandle)
-  );
-  invariant(
-    !1,
-    "findNodeHandle(...): Unable to find node handle for unmounted component."
-  );
-}
-function findNumericNodeHandleFiber(componentOrHandle) {
-  componentOrHandle = findNodeHandle(componentOrHandle);
-  return null == componentOrHandle || "number" === typeof componentOrHandle
-    ? componentOrHandle
-    : componentOrHandle._nativeTag;
-}
 function _inherits(subClass, superClass) {
   if ("function" !== typeof superClass && null !== superClass)
     throw new TypeError(
@@ -1413,75 +1204,7 @@ function _inherits(subClass, superClass) {
       ? Object.setPrototypeOf(subClass, superClass)
       : (subClass.__proto__ = superClass));
 }
-var ReactNativeComponent = (function(_React$Component) {
-    function ReactNativeComponent() {
-      if (!(this instanceof ReactNativeComponent))
-        throw new TypeError("Cannot call a class as a function");
-      var call = _React$Component.apply(this, arguments);
-      if (!this)
-        throw new ReferenceError(
-          "this hasn't been initialised - super() hasn't been called"
-        );
-      return !call || ("object" !== typeof call && "function" !== typeof call)
-        ? this
-        : call;
-    }
-    _inherits(ReactNativeComponent, _React$Component);
-    ReactNativeComponent.prototype.blur = function() {
-      TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
-    };
-    ReactNativeComponent.prototype.focus = function() {
-      TextInputState.focusTextInput(findNumericNodeHandleFiber(this));
-    };
-    ReactNativeComponent.prototype.measure = function(callback) {
-      UIManager.measure(
-        findNumericNodeHandleFiber(this),
-        mountSafeCallback(this, callback)
-      );
-    };
-    ReactNativeComponent.prototype.measureInWindow = function(callback) {
-      UIManager.measureInWindow(
-        findNumericNodeHandleFiber(this),
-        mountSafeCallback(this, callback)
-      );
-    };
-    ReactNativeComponent.prototype.measureLayout = function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail
-    ) {
-      UIManager.measureLayout(
-        findNumericNodeHandleFiber(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    };
-    ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
-      var maybeInstance = void 0;
-      try {
-        maybeInstance = findNodeHandle(this);
-      } catch (error) {}
-      if (null != maybeInstance) {
-        var viewConfig =
-          maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
-        nativeProps = diffProperties(
-          null,
-          emptyObject$1,
-          nativeProps,
-          viewConfig.validAttributes
-        );
-        null != nativeProps &&
-          UIManager.updateView(
-            maybeInstance._nativeTag,
-            viewConfig.uiViewClassName,
-            nativeProps
-          );
-      }
-    };
-    return ReactNativeComponent;
-  })(React.Component),
-  now =
+var now =
     "object" === typeof performance && "function" === typeof performance.now
       ? function() {
           return performance.now();
@@ -1503,8 +1226,24 @@ function setTimeoutCallback() {
   scheduledCallback = null;
   null !== callback && callback(frameDeadlineObject);
 }
-var viewConfigCallbacks = new Map(),
-  viewConfigs = new Map();
+var ReactCurrentOwner =
+  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
+function getComponentName(fiber) {
+  fiber = fiber.type;
+  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
+  if ("string" === typeof fiber) return fiber;
+  switch (fiber) {
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_RETURN_TYPE:
+      return "ReactReturn";
+  }
+  return null;
+}
 function isFiberMountedImpl(fiber) {
   var node = fiber;
   if (fiber.alternate) for (; node["return"]; ) node = node["return"];
@@ -5649,10 +5388,6 @@ function ReactFiberReconciler$1(config) {
     scheduleWork(currentTime, expirationTime);
     return expirationTime;
   }
-  function findHostInstance(fiber) {
-    fiber = findCurrentHostFiber(fiber);
-    return null === fiber ? null : fiber.stateNode;
-  }
   var getPublicInstance = config.getPublicInstance;
   config = ReactFiberScheduler(config);
   var recalculateCurrentTime = config.recalculateCurrentTime,
@@ -5731,7 +5466,19 @@ function ReactFiberReconciler$1(config) {
           return container.child.stateNode;
       }
     },
-    findHostInstance: findHostInstance,
+    findHostInstance: function(component) {
+      var fiber = component._reactInternalFiber;
+      void 0 === fiber &&
+        ("function" === typeof component.render
+          ? invariant(!1, "Unable to find node on an unmounted component.")
+          : invariant(
+              !1,
+              "Argument appears to not be a ReactComponent. Keys: %s",
+              Object.keys(component)
+            ));
+      component = findCurrentHostFiber(fiber);
+      return null === component ? null : component.stateNode;
+    },
     findHostInstanceWithNoPortals: function(fiber) {
       fiber = findCurrentHostFiberWithNoPortals(fiber);
       return null === fiber ? null : fiber.stateNode;
@@ -5741,7 +5488,8 @@ function ReactFiberReconciler$1(config) {
       return injectInternals(
         Object.assign({}, devToolsConfig, {
           findHostInstanceByFiber: function(fiber) {
-            return findHostInstance(fiber);
+            fiber = findCurrentHostFiber(fiber);
+            return null === fiber ? null : fiber.stateNode;
           },
           findFiberByHostInstance: function(instance) {
             return findFiberByHostInstance
@@ -5760,27 +5508,7 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
   reactReconciler = ReactFiberReconciler$3["default"]
     ? ReactFiberReconciler$3["default"]
     : ReactFiberReconciler$3,
-  ReactNativeTagHandles = {
-    tagsStartAt: 1,
-    tagCount: 1,
-    allocateTag: function() {
-      for (; this.reactTagIsNativeTopRootID(ReactNativeTagHandles.tagCount); )
-        ReactNativeTagHandles.tagCount++;
-      var tag = ReactNativeTagHandles.tagCount;
-      ReactNativeTagHandles.tagCount++;
-      return tag;
-    },
-    assertRootTag: function(tag) {
-      invariant(
-        this.reactTagIsNativeTopRootID(tag),
-        "Expect a native root tag, instead got %s",
-        tag
-      );
-    },
-    reactTagIsNativeTopRootID: function(reactTag) {
-      return 1 === reactTag % 10;
-    }
-  },
+  nextReactTag = 2,
   ReactFabricHostComponent = (function() {
     function ReactFabricHostComponent(tag, viewConfig, props) {
       if (!(this instanceof ReactFabricHostComponent))
@@ -5843,21 +5571,10 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
       hostContext,
       internalInstanceHandle
     ) {
-      hostContext = ReactNativeTagHandles.allocateTag();
-      if (viewConfigs.has(type)) var viewConfig = viewConfigs.get(type);
-      else
-        (viewConfig = viewConfigCallbacks.get(type)),
-          invariant(
-            "function" === typeof viewConfig,
-            "View config not found for name %s",
-            type
-          ),
-          viewConfigCallbacks.set(type, null),
-          (viewConfig = viewConfig()),
-          viewConfigs.set(type, viewConfig);
-      invariant(viewConfig, "View config not found for name %s", type);
-      type = viewConfig;
-      viewConfig = diffProperties(
+      hostContext = nextReactTag;
+      nextReactTag += 2;
+      type = ReactNativeViewConfigRegistry.get(type);
+      var updatePayload = diffProperties(
         null,
         emptyObject$1,
         props,
@@ -5867,7 +5584,7 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
         hostContext,
         type.uiViewClassName,
         rootContainerInstance,
-        viewConfig,
+        updatePayload,
         internalInstanceHandle
       );
       props = new ReactFabricHostComponent(hostContext, type, props);
@@ -5879,7 +5596,8 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
       hostContext,
       internalInstanceHandle
     ) {
-      hostContext = ReactNativeTagHandles.allocateTag();
+      hostContext = nextReactTag;
+      nextReactTag += 2;
       return {
         node: FabricUIManager.createNode(
           hostContext,
@@ -5968,91 +5686,76 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
 getInspectorDataForViewTag = function() {
   invariant(!1, "getInspectorDataForViewTag() is not available in production");
 };
-findHostInstanceFabric = ReactFabricRenderer.findHostInstance;
-_batchedUpdates = ReactFabricRenderer.batchedUpdates;
-_flushInteractiveUpdates = ReactFabricRenderer.flushInteractiveUpdates;
+var findHostInstance = ReactFabricRenderer.findHostInstance;
+function findNodeHandle(componentOrHandle) {
+  if (null == componentOrHandle) return null;
+  if ("number" === typeof componentOrHandle) return componentOrHandle;
+  if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
+    return componentOrHandle.canonical._nativeTag;
+  componentOrHandle = findHostInstance(componentOrHandle);
+  return null == componentOrHandle
+    ? componentOrHandle
+    : componentOrHandle.canonical
+      ? componentOrHandle.canonical._nativeTag
+      : componentOrHandle._nativeTag;
+}
 var roots = new Map(),
   ReactFabric = {
-    NativeComponent: ReactNativeComponent,
-    findNodeHandle: findNumericNodeHandleFiber,
-    render: function(element, containerTag, callback) {
-      var root = roots.get(containerTag);
-      root ||
-        ((root = ReactFabricRenderer.createContainer(containerTag, !1, !1)),
-        roots.set(containerTag, root));
-      ReactFabricRenderer.updateContainer(element, root, null, callback);
-      return ReactFabricRenderer.getPublicRootInstance(root);
-    },
-    unmountComponentAtNode: function(containerTag) {
-      var root = roots.get(containerTag);
-      root &&
-        ReactFabricRenderer.updateContainer(null, root, null, function() {
-          roots["delete"](containerTag);
-        });
-    },
-    unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
-      ReactFabric.unmountComponentAtNode(containerTag);
-    },
-    createPortal: function(children, containerTag) {
-      return createPortal(
-        children,
-        containerTag,
-        null,
-        2 < arguments.length && void 0 !== arguments[2] ? arguments[2] : null
-      );
-    },
-    unstable_batchedUpdates: function(fn, bookkeeping) {
-      if (isBatching) return fn(bookkeeping);
-      isBatching = !0;
-      try {
-        return _batchedUpdates(fn, bookkeeping);
-      } finally {
-        if (
-          ((isBatching = !1), null !== restoreTarget || null !== restoreQueue)
-        )
-          if (
-            (_flushInteractiveUpdates(),
-            restoreTarget &&
-              ((bookkeeping = restoreTarget),
-              (fn = restoreQueue),
-              (restoreQueue = restoreTarget = null),
-              restoreStateOfTarget(bookkeeping),
-              fn))
-          )
-            for (bookkeeping = 0; bookkeeping < fn.length; bookkeeping++)
-              restoreStateOfTarget(fn[bookkeeping]);
-      }
-    },
-    flushSync: ReactFabricRenderer.flushSync,
-    __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
-      NativeMethodsMixin: {
-        measure: function(callback) {
+    NativeComponent: (function(findNodeHandle, findHostInstance) {
+      return (function(_React$Component) {
+        function ReactNativeComponent() {
+          if (!(this instanceof ReactNativeComponent))
+            throw new TypeError("Cannot call a class as a function");
+          var call = _React$Component.apply(this, arguments);
+          if (!this)
+            throw new ReferenceError(
+              "this hasn't been initialised - super() hasn't been called"
+            );
+          return !call ||
+            ("object" !== typeof call && "function" !== typeof call)
+            ? this
+            : call;
+        }
+        _inherits(ReactNativeComponent, _React$Component);
+        ReactNativeComponent.prototype.blur = function() {
+          TextInputState.blurTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.focus = function() {
+          TextInputState.focusTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.measure = function(callback) {
           UIManager.measure(
-            findNumericNodeHandleFiber(this),
+            findNodeHandle(this),
             mountSafeCallback(this, callback)
           );
-        },
-        measureInWindow: function(callback) {
+        };
+        ReactNativeComponent.prototype.measureInWindow = function(callback) {
           UIManager.measureInWindow(
-            findNumericNodeHandleFiber(this),
+            findNodeHandle(this),
             mountSafeCallback(this, callback)
           );
-        },
-        measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
+        };
+        ReactNativeComponent.prototype.measureLayout = function(
+          relativeToNativeNode,
+          onSuccess,
+          onFail
+        ) {
           UIManager.measureLayout(
-            findNumericNodeHandleFiber(this),
+            findNodeHandle(this),
             relativeToNativeNode,
             mountSafeCallback(this, onFail),
             mountSafeCallback(this, onSuccess)
           );
-        },
-        setNativeProps: function(nativeProps) {
+        };
+        ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
           var maybeInstance = void 0;
           try {
-            maybeInstance = findNodeHandle(this);
+            maybeInstance = findHostInstance(this);
           } catch (error) {}
           if (null != maybeInstance) {
-            var viewConfig = maybeInstance.viewConfig;
+            var viewConfig =
+              maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
             nativeProps = diffProperties(
               null,
               emptyObject$1,
@@ -6066,33 +5769,87 @@ var roots = new Map(),
                 nativeProps
               );
           }
-        },
-        focus: function() {
-          TextInputState.focusTextInput(findNumericNodeHandleFiber(this));
-        },
-        blur: function() {
-          TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
-        }
-      },
-      ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin,
-      ReactNativeComponentTree: ReactNativeComponentTree,
-      ReactNativePropRegistry: ReactNativePropRegistry,
-      TouchHistoryMath: TouchHistoryMath,
-      createReactNativeComponentClass: function(name, callback) {
-        invariant(
-          !viewConfigCallbacks.has(name),
-          "Tried to register two views with the same name %s",
-          name
-        );
-        viewConfigCallbacks.set(name, callback);
-        return name;
-      },
-      takeSnapshot: function(view, options) {
-        "number" !== typeof view &&
-          "window" !== view &&
-          (view = findNumericNodeHandleFiber(view) || "window");
-        return UIManager.__takeSnapshot(view, options);
-      }
+        };
+        return ReactNativeComponent;
+      })(React.Component);
+    })(findNodeHandle, findHostInstance),
+    findNodeHandle: findNodeHandle,
+    render: function(element, containerTag, callback) {
+      var root = roots.get(containerTag);
+      root ||
+        ((root = ReactFabricRenderer.createContainer(containerTag, !1, !1)),
+        roots.set(containerTag, root));
+      ReactFabricRenderer.updateContainer(element, root, null, callback);
+      return ReactFabricRenderer.getPublicRootInstance(root);
+    },
+    unmountComponentAtNode: function(containerTag) {
+      var root = roots.get(containerTag);
+      root &&
+        ReactFabricRenderer.updateContainer(null, root, null, function() {
+          roots["delete"](containerTag);
+        });
+    },
+    createPortal: function(children, containerTag) {
+      return createPortal(
+        children,
+        containerTag,
+        null,
+        2 < arguments.length && void 0 !== arguments[2] ? arguments[2] : null
+      );
+    },
+    __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
+      NativeMethodsMixin: (function(findNodeHandle, findHostInstance) {
+        return {
+          measure: function(callback) {
+            UIManager.measure(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureInWindow: function(callback) {
+            UIManager.measureInWindow(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
+            UIManager.measureLayout(
+              findNodeHandle(this),
+              relativeToNativeNode,
+              mountSafeCallback(this, onFail),
+              mountSafeCallback(this, onSuccess)
+            );
+          },
+          setNativeProps: function(nativeProps) {
+            var maybeInstance = void 0;
+            try {
+              maybeInstance = findHostInstance(this);
+            } catch (error) {}
+            if (null != maybeInstance) {
+              var viewConfig = maybeInstance.viewConfig;
+              nativeProps = diffProperties(
+                null,
+                emptyObject$1,
+                nativeProps,
+                viewConfig.validAttributes
+              );
+              null != nativeProps &&
+                UIManager.updateView(
+                  maybeInstance._nativeTag,
+                  viewConfig.uiViewClassName,
+                  nativeProps
+                );
+            }
+          },
+          focus: function() {
+            TextInputState.focusTextInput(findNodeHandle(this));
+          },
+          blur: function() {
+            TextInputState.blurTextInput(findNodeHandle(this));
+          }
+        };
+      })(findNodeHandle, findHostInstance),
+      ReactNativeComponentTree: ReactNativeComponentTree
     }
   };
 ReactFabricRenderer.injectIntoDevTools({
diff --git a/Libraries/Renderer/ReactNativeRenderer-dev.js b/Libraries/Renderer/ReactNativeRenderer-dev.js
index 97bbfa4bef4d..51e4aa2b0adc 100644
--- a/Libraries/Renderer/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/ReactNativeRenderer-dev.js
@@ -19,6 +19,7 @@ require("InitializeCore");
 var invariant = require("fbjs/lib/invariant");
 var warning = require("fbjs/lib/warning");
 var emptyFunction = require("fbjs/lib/emptyFunction");
+var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
 var UIManager = require("UIManager");
 var RCTEventEmitter = require("RCTEventEmitter");
 var TextInputState = require("TextInputState");
@@ -1449,7 +1450,7 @@ function getPooledWarningPropertyDefinition(propName, getVal) {
   return {
     configurable: true,
     set: set,
-    get: get
+    get: get$$1
   };
 
   function set(val) {
@@ -1458,7 +1459,7 @@ function getPooledWarningPropertyDefinition(propName, getVal) {
     return val;
   }
 
-  function get() {
+  function get$$1() {
     var action = isFunction ? "accessing the method" : "accessing the property";
     var result = isFunction
       ? "This is a no-op function"
@@ -1775,7 +1776,7 @@ var changeResponder = function(nextResponderInst, blockHostResponder) {
   }
 };
 
-var eventTypes = {
+var eventTypes$1 = {
   /**
    * On a `touchStart`/`mouseDown`, is it desired that this element become the
    * responder?
@@ -2040,12 +2041,12 @@ function setResponderAndExtractTransfer(
   nativeEventTarget
 ) {
   var shouldSetEventType = isStartish(topLevelType)
-    ? eventTypes.startShouldSetResponder
+    ? eventTypes$1.startShouldSetResponder
     : isMoveish(topLevelType)
-      ? eventTypes.moveShouldSetResponder
+      ? eventTypes$1.moveShouldSetResponder
       : topLevelType === "topSelectionChange"
-        ? eventTypes.selectionChangeShouldSetResponder
-        : eventTypes.scrollShouldSetResponder;
+        ? eventTypes$1.selectionChangeShouldSetResponder
+        : eventTypes$1.scrollShouldSetResponder;
 
   // TODO: stop one short of the current responder.
   var bubbleShouldSetFrom = !responderInst
@@ -2079,7 +2080,7 @@ function setResponderAndExtractTransfer(
   }
   var extracted = void 0;
   var grantEvent = ResponderSyntheticEvent.getPooled(
-    eventTypes.responderGrant,
+    eventTypes$1.responderGrant,
     wantsResponderInst,
     nativeEvent,
     nativeEventTarget
@@ -2090,7 +2091,7 @@ function setResponderAndExtractTransfer(
   var blockHostResponder = executeDirectDispatch(grantEvent) === true;
   if (responderInst) {
     var terminationRequestEvent = ResponderSyntheticEvent.getPooled(
-      eventTypes.responderTerminationRequest,
+      eventTypes$1.responderTerminationRequest,
       responderInst,
       nativeEvent,
       nativeEventTarget
@@ -2107,7 +2108,7 @@ function setResponderAndExtractTransfer(
 
     if (shouldSwitch) {
       var terminateEvent = ResponderSyntheticEvent.getPooled(
-        eventTypes.responderTerminate,
+        eventTypes$1.responderTerminate,
         responderInst,
         nativeEvent,
         nativeEventTarget
@@ -2118,7 +2119,7 @@ function setResponderAndExtractTransfer(
       changeResponder(wantsResponderInst, blockHostResponder);
     } else {
       var rejectEvent = ResponderSyntheticEvent.getPooled(
-        eventTypes.responderReject,
+        eventTypes$1.responderReject,
         wantsResponderInst,
         nativeEvent,
         nativeEventTarget
@@ -2187,7 +2188,7 @@ var ResponderEventPlugin = {
     return responderInst;
   },
 
-  eventTypes: eventTypes,
+  eventTypes: eventTypes$1,
 
   /**
    * We must be resilient to `targetInst` being `null` on `touchMove` or
@@ -2237,10 +2238,10 @@ var ResponderEventPlugin = {
     var isResponderTouchMove = responderInst && isMoveish(topLevelType);
     var isResponderTouchEnd = responderInst && isEndish(topLevelType);
     var incrementalTouch = isResponderTouchStart
-      ? eventTypes.responderStart
+      ? eventTypes$1.responderStart
       : isResponderTouchMove
-        ? eventTypes.responderMove
-        : isResponderTouchEnd ? eventTypes.responderEnd : null;
+        ? eventTypes$1.responderMove
+        : isResponderTouchEnd ? eventTypes$1.responderEnd : null;
 
     if (incrementalTouch) {
       var gesture = ResponderSyntheticEvent.getPooled(
@@ -2262,8 +2263,8 @@ var ResponderEventPlugin = {
       isEndish(topLevelType) &&
       noResponderTouches(nativeEvent);
     var finalTouch = isResponderTerminate
-      ? eventTypes.responderTerminate
-      : isResponderRelease ? eventTypes.responderRelease : null;
+      ? eventTypes$1.responderTerminate
+      : isResponderRelease ? eventTypes$1.responderRelease : null;
     if (finalTouch) {
       var finalEvent = ResponderSyntheticEvent.getPooled(
         finalTouch,
@@ -2315,11 +2316,14 @@ var ResponderEventPlugin = {
   }
 };
 
-var customBubblingEventTypes = {};
-var customDirectEventTypes = {};
+var customBubblingEventTypes$1 =
+  ReactNativeViewConfigRegistry.customBubblingEventTypes;
+var customDirectEventTypes$1 =
+  ReactNativeViewConfigRegistry.customDirectEventTypes;
+var eventTypes$2 = ReactNativeViewConfigRegistry.eventTypes;
 
 var ReactNativeBridgeEventPlugin = {
-  eventTypes: {},
+  eventTypes: eventTypes$2,
 
   /**
    * @see {EventPluginHub.extractEvents}
@@ -2334,8 +2338,8 @@ var ReactNativeBridgeEventPlugin = {
       // Probably a node belonging to another renderer's tree.
       return null;
     }
-    var bubbleDispatchConfig = customBubblingEventTypes[topLevelType];
-    var directDispatchConfig = customDirectEventTypes[topLevelType];
+    var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType];
+    var directDispatchConfig = customDirectEventTypes$1[topLevelType];
     invariant(
       bubbleDispatchConfig || directDispatchConfig,
       'Unsupported top level event type "%s" dispatched',
@@ -2355,45 +2359,6 @@ var ReactNativeBridgeEventPlugin = {
       return null;
     }
     return event;
-  },
-
-  processEventTypes: function(viewConfig) {
-    var bubblingEventTypes = viewConfig.bubblingEventTypes,
-      directEventTypes = viewConfig.directEventTypes;
-
-    {
-      if (bubblingEventTypes != null && directEventTypes != null) {
-        for (var topLevelType in directEventTypes) {
-          invariant(
-            bubblingEventTypes[topLevelType] == null,
-            "Event cannot be both direct and bubbling: %s",
-            topLevelType
-          );
-        }
-      }
-    }
-
-    if (bubblingEventTypes != null) {
-      for (var _topLevelType in bubblingEventTypes) {
-        if (customBubblingEventTypes[_topLevelType] == null) {
-          ReactNativeBridgeEventPlugin.eventTypes[
-            _topLevelType
-          ] = customBubblingEventTypes[_topLevelType] =
-            bubblingEventTypes[_topLevelType];
-        }
-      }
-    }
-
-    if (directEventTypes != null) {
-      for (var _topLevelType2 in directEventTypes) {
-        if (customDirectEventTypes[_topLevelType2] == null) {
-          ReactNativeBridgeEventPlugin.eventTypes[
-            _topLevelType2
-          ] = customDirectEventTypes[_topLevelType2] =
-            directEventTypes[_topLevelType2];
-        }
-      }
-    }
   }
 };
 
@@ -2588,48 +2553,6 @@ var injection$2 = {
   }
 };
 
-/**
- * Keeps track of allocating and associating native "tags" which are numeric,
- * unique view IDs. All the native tags are negative numbers, to avoid
- * collisions, but in the JS we keep track of them as positive integers to store
- * them effectively in Arrays. So we must refer to them as "inverses" of the
- * native tags (that are * normally negative).
- *
- * It *must* be the case that every `rootNodeID` always maps to the exact same
- * `tag` forever. The easiest way to accomplish this is to never delete
- * anything from this table.
- * Why: Because `dangerouslyReplaceNodeWithMarkupByID` relies on being able to
- * unmount a component with a `rootNodeID`, then mount a new one in its place,
- */
-var INITIAL_TAG_COUNT = 1;
-var ReactNativeTagHandles = {
-  tagsStartAt: INITIAL_TAG_COUNT,
-  tagCount: INITIAL_TAG_COUNT,
-
-  allocateTag: function() {
-    // Skip over root IDs as those are reserved for native
-    while (this.reactTagIsNativeTopRootID(ReactNativeTagHandles.tagCount)) {
-      ReactNativeTagHandles.tagCount++;
-    }
-    var tag = ReactNativeTagHandles.tagCount;
-    ReactNativeTagHandles.tagCount++;
-    return tag;
-  },
-
-  assertRootTag: function(tag) {
-    invariant(
-      this.reactTagIsNativeTopRootID(tag),
-      "Expect a native root tag, instead got %s",
-      tag
-    );
-  },
-
-  reactTagIsNativeTopRootID: function(reactTag) {
-    // We reserve all tags that are 1 mod 10 for native root views
-    return reactTag % 10 === 1;
-  }
-};
-
 /**
  * Version of `ReactBrowserEventEmitter` that works on the receiving side of a
  * serialized worker boundary.
@@ -2762,7 +2685,7 @@ function receiveTouches(eventTopLevelType, touches, changedIndices) {
     var rootNodeID = null;
     var target = nativeEvent.target;
     if (target !== null && target !== undefined) {
-      if (target < ReactNativeTagHandles.tagsStartAt) {
+      if (target < 1) {
         {
           warning(
             false,
@@ -2848,149 +2771,6 @@ function createPortal(
   };
 }
 
-var TouchHistoryMath = {
-  /**
-   * This code is optimized and not intended to look beautiful. This allows
-   * computing of touch centroids that have moved after `touchesChangedAfter`
-   * timeStamp. You can compute the current centroid involving all touches
-   * moves after `touchesChangedAfter`, or you can compute the previous
-   * centroid of all touches that were moved after `touchesChangedAfter`.
-   *
-   * @param {TouchHistoryMath} touchHistory Standard Responder touch track
-   * data.
-   * @param {number} touchesChangedAfter timeStamp after which moved touches
-   * are considered "actively moving" - not just "active".
-   * @param {boolean} isXAxis Consider `x` dimension vs. `y` dimension.
-   * @param {boolean} ofCurrent Compute current centroid for actively moving
-   * touches vs. previous centroid of now actively moving touches.
-   * @return {number} value of centroid in specified dimension.
-   */
-  centroidDimension: function(
-    touchHistory,
-    touchesChangedAfter,
-    isXAxis,
-    ofCurrent
-  ) {
-    var touchBank = touchHistory.touchBank;
-    var total = 0;
-    var count = 0;
-
-    var oneTouchData =
-      touchHistory.numberActiveTouches === 1
-        ? touchHistory.touchBank[touchHistory.indexOfSingleActiveTouch]
-        : null;
-
-    if (oneTouchData !== null) {
-      if (
-        oneTouchData.touchActive &&
-        oneTouchData.currentTimeStamp > touchesChangedAfter
-      ) {
-        total +=
-          ofCurrent && isXAxis
-            ? oneTouchData.currentPageX
-            : ofCurrent && !isXAxis
-              ? oneTouchData.currentPageY
-              : !ofCurrent && isXAxis
-                ? oneTouchData.previousPageX
-                : oneTouchData.previousPageY;
-        count = 1;
-      }
-    } else {
-      for (var i = 0; i < touchBank.length; i++) {
-        var touchTrack = touchBank[i];
-        if (
-          touchTrack !== null &&
-          touchTrack !== undefined &&
-          touchTrack.touchActive &&
-          touchTrack.currentTimeStamp >= touchesChangedAfter
-        ) {
-          var toAdd = void 0; // Yuck, program temporarily in invalid state.
-          if (ofCurrent && isXAxis) {
-            toAdd = touchTrack.currentPageX;
-          } else if (ofCurrent && !isXAxis) {
-            toAdd = touchTrack.currentPageY;
-          } else if (!ofCurrent && isXAxis) {
-            toAdd = touchTrack.previousPageX;
-          } else {
-            toAdd = touchTrack.previousPageY;
-          }
-          total += toAdd;
-          count++;
-        }
-      }
-    }
-    return count > 0 ? total / count : TouchHistoryMath.noCentroid;
-  },
-
-  currentCentroidXOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      true, // isXAxis
-      true
-    );
-  },
-
-  currentCentroidYOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      false, // isXAxis
-      true
-    );
-  },
-
-  previousCentroidXOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      true, // isXAxis
-      false
-    );
-  },
-
-  previousCentroidYOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      false, // isXAxis
-      false
-    );
-  },
-
-  currentCentroidX: function(touchHistory) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      0, // touchesChangedAfter
-      true, // isXAxis
-      true
-    );
-  },
-
-  currentCentroidY: function(touchHistory) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      0, // touchesChangedAfter
-      false, // isXAxis
-      true
-    );
-  },
-
-  noCentroid: -1
-};
-
 // TODO: this is special because it gets imported during build.
 
 var ReactVersion = "16.3.1";
@@ -3064,48 +2844,6 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
   return info;
 }
 
-function _classCallCheck(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
-  }
-}
-
-var objects = {};
-var uniqueID = 1;
-var emptyObject$2 = {};
-
-var ReactNativePropRegistry = (function() {
-  function ReactNativePropRegistry() {
-    _classCallCheck(this, ReactNativePropRegistry);
-  }
-
-  ReactNativePropRegistry.register = function register(object) {
-    var id = ++uniqueID;
-    {
-      Object.freeze(object);
-    }
-    objects[id] = object;
-    return id;
-  };
-
-  ReactNativePropRegistry.getByID = function getByID(id) {
-    if (!id) {
-      // Used in the style={[condition && id]} pattern,
-      // we want it to be a no-op when the value is false or null
-      return emptyObject$2;
-    }
-
-    var object = objects[id];
-    if (!object) {
-      console.warn("Invalid style with id `" + id + "`. Skipping ...");
-      return emptyObject$2;
-    }
-    return object;
-  };
-
-  return ReactNativePropRegistry;
-})();
-
 // Modules provided by RN:
 var emptyObject$1 = {};
 
@@ -3132,13 +2870,6 @@ function defaultDiffer(prevProp, nextProp) {
   }
 }
 
-function resolveObject(idOrObject) {
-  if (typeof idOrObject === "number") {
-    return ReactNativePropRegistry.getByID(idOrObject);
-  }
-  return idOrObject;
-}
-
 function restoreDeletedValuesInNestedArray(
   updatePayload,
   node,
@@ -3154,7 +2885,7 @@ function restoreDeletedValuesInNestedArray(
       );
     }
   } else if (node && removedKeyCount > 0) {
-    var obj = resolveObject(node);
+    var obj = node;
     for (var propKey in removedKeys) {
       if (!removedKeys[propKey]) {
         continue;
@@ -3258,12 +2989,7 @@ function diffNestedProperty(
 
   if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
     // Both are leaves, we can diff the leaves.
-    return diffProperties(
-      updatePayload,
-      resolveObject(prevProp),
-      resolveObject(nextProp),
-      validAttributes
-    );
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
   }
 
   if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
@@ -3282,14 +3008,14 @@ function diffNestedProperty(
       // $FlowFixMe - We know that this is always an object when the input is.
       flattenStyle(prevProp),
       // $FlowFixMe - We know that this isn't an array because of above flow.
-      resolveObject(nextProp),
+      nextProp,
       validAttributes
     );
   }
 
   return diffProperties(
     updatePayload,
-    resolveObject(prevProp),
+    prevProp,
     // $FlowFixMe - We know that this is always an object when the input is.
     flattenStyle(nextProp),
     validAttributes
@@ -3308,11 +3034,7 @@ function addNestedProperty(updatePayload, nextProp, validAttributes) {
 
   if (!Array.isArray(nextProp)) {
     // Add each property of the leaf.
-    return addProperties(
-      updatePayload,
-      resolveObject(nextProp),
-      validAttributes
-    );
+    return addProperties(updatePayload, nextProp, validAttributes);
   }
 
   for (var i = 0; i < nextProp.length; i++) {
@@ -3338,11 +3060,7 @@ function clearNestedProperty(updatePayload, prevProp, validAttributes) {
 
   if (!Array.isArray(prevProp)) {
     // Add each property of the leaf.
-    return clearProperties(
-      updatePayload,
-      resolveObject(prevProp),
-      validAttributes
-    );
+    return clearProperties(updatePayload, prevProp, validAttributes);
   }
 
   for (var i = 0; i < prevProp.length; i++) {
@@ -3629,339 +3347,195 @@ function warnForStyleProps(props, validAttributes) {
   }
 }
 
-/**
- * `ReactInstanceMap` maintains a mapping from a public facing stateful
- * instance (key) and the internal representation (value). This allows public
- * methods to accept the user facing instance as an argument and map them back
- * to internal methods.
- *
- * Note that this module is currently shared and assumed to be stateless.
- * If this becomes an actual Map, that will break.
- */
-
-/**
- * This API should be called `delete` but we'd have to make sure to always
- * transform these to strings for IE support. When this transform is fully
- * supported we can rename it.
- */
-
-function get(key) {
-  return key._reactInternalFiber;
-}
-
-function set(key, value) {
-  key._reactInternalFiber = value;
-}
-
-var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
-
-var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
-var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
-
-// TODO: Share this module between Fabric and React Native renderers
-// so that both can be used in the same tree.
-
-var findHostInstance = function(fiber) {
-  return null;
-};
-
-var findHostInstanceFabric = function(fiber) {
-  return null;
-};
-
-function injectFindHostInstance(impl) {
-  findHostInstance = impl;
-}
-
-/**
- * ReactNative vs ReactWeb
- * -----------------------
- * React treats some pieces of data opaquely. This means that the information
- * is first class (it can be passed around), but cannot be inspected. This
- * allows us to build infrastructure that reasons about resources, without
- * making assumptions about the nature of those resources, and this allows that
- * infra to be shared across multiple platforms, where the resources are very
- * different. General infra (such as `ReactMultiChild`) reasons opaquely about
- * the data, but platform specific code (such as `ReactNativeBaseComponent`) can
- * make assumptions about the data.
- *
- *
- * `rootNodeID`, uniquely identifies a position in the generated native view
- * tree. Many layers of composite components (created with `React.createClass`)
- * can all share the same `rootNodeID`.
- *
- * `nodeHandle`: A sufficiently unambiguous way to refer to a lower level
- * resource (dom node, native view etc). The `rootNodeID` is sufficient for web
- * `nodeHandle`s, because the position in a tree is always enough to uniquely
- * identify a DOM node (we never have nodes in some bank outside of the
- * document). The same would be true for `ReactNative`, but we must maintain a
- * mapping that we can send efficiently serializable
- * strings across native boundaries.
- *
- * Opaque name      TodaysWebReact   FutureWebWorkerReact   ReactNative
- * ----------------------------------------------------------------------------
- * nodeHandle       N/A              rootNodeID             tag
- */
-
-// TODO (bvaughn) Rename the findNodeHandle module to something more descriptive
-// eg findInternalHostInstance. This will reduce the likelihood of someone
-// accidentally deep-requiring this version.
-function findNodeHandle(componentOrHandle) {
-  {
-    var owner = ReactCurrentOwner.current;
-    if (owner !== null && owner.stateNode !== null) {
-      !owner.stateNode._warnedAboutRefsInRender
-        ? warning(
-            false,
-            "%s is accessing findNodeHandle inside its render(). " +
-              "render() should be a pure function of props and state. It should " +
-              "never access something that requires stale data from the previous " +
-              "render, such as refs. Move this logic to componentDidMount and " +
-              "componentDidUpdate instead.",
-            getComponentName(owner) || "A component"
-          )
-        : void 0;
-
-      owner.stateNode._warnedAboutRefsInRender = true;
-    }
-  }
-  if (componentOrHandle == null) {
-    return null;
-  }
-  if (typeof componentOrHandle === "number") {
-    // Already a node handle
-    return componentOrHandle;
-  }
-
-  var component = componentOrHandle;
-
-  // TODO (balpert): Wrap iOS native components in a composite wrapper, then
-  // ReactInstanceMap.get here will always succeed for mounted components
-  var internalInstance = get(component);
-  if (internalInstance) {
-    return (
-      findHostInstance(internalInstance) ||
-      findHostInstanceFabric(internalInstance)
-    );
-  } else {
-    if (component) {
-      return component;
-    } else {
-      invariant(
-        // Native
-        (typeof component === "object" && "_nativeTag" in component) ||
-          // Composite
-          (component.render != null && typeof component.render === "function"),
-        "findNodeHandle(...): Argument is not a component " +
-          "(type: %s, keys: %s)",
-        typeof component,
-        Object.keys(component)
-      );
-      invariant(
-        false,
-        "findNodeHandle(...): Unable to find node handle for unmounted " +
-          "component."
-      );
-    }
-  }
-}
-
-/**
- * External users of findNodeHandle() expect the host tag number return type.
- * The injected findNodeHandle() strategy returns the instance wrapper though.
- * See NativeMethodsMixin#setNativeProps for more info on why this is done.
- */
-function findNumericNodeHandleFiber(componentOrHandle) {
-  var instance = findNodeHandle(componentOrHandle);
-  if (instance == null || typeof instance === "number") {
-    return instance;
-  }
-  return instance._nativeTag;
-}
-
 // Modules provided by RN:
-/**
- * `NativeMethodsMixin` provides methods to access the underlying native
- * component directly. This can be useful in cases when you want to focus
- * a view or measure its on-screen dimensions, for example.
- *
- * The methods described here are available on most of the default components
- * provided by React Native. Note, however, that they are *not* available on
- * composite components that aren't directly backed by a native view. This will
- * generally include most components that you define in your own app. For more
- * information, see [Direct
- * Manipulation](docs/direct-manipulation.html).
- *
- * Note the Flow $Exact<> syntax is required to support mixins.
- * React createClass mixins can only be used with exact types.
- */
-var NativeMethodsMixin = {
+var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
   /**
-   * Determines the location on screen, width, and height of the given view and
-   * returns the values via an async callback. If successful, the callback will
-   * be called with the following arguments:
+   * `NativeMethodsMixin` provides methods to access the underlying native
+   * component directly. This can be useful in cases when you want to focus
+   * a view or measure its on-screen dimensions, for example.
    *
-   *  - x
-   *  - y
-   *  - width
-   *  - height
-   *  - pageX
-   *  - pageY
+   * The methods described here are available on most of the default components
+   * provided by React Native. Note, however, that they are *not* available on
+   * composite components that aren't directly backed by a native view. This will
+   * generally include most components that you define in your own app. For more
+   * information, see [Direct
+   * Manipulation](docs/direct-manipulation.html).
    *
-   * Note that these measurements are not available until after the rendering
-   * has been completed in native. If you need the measurements as soon as
-   * possible, consider using the [`onLayout`
-   * prop](docs/view.html#onlayout) instead.
+   * Note the Flow $Exact<> syntax is required to support mixins.
+   * React createClass mixins can only be used with exact types.
    */
-  measure: function(callback) {
-    UIManager.measure(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  },
+  var NativeMethodsMixin = {
+    /**
+     * Determines the location on screen, width, and height of the given view and
+     * returns the values via an async callback. If successful, the callback will
+     * be called with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native. If you need the measurements as soon as
+     * possible, consider using the [`onLayout`
+     * prop](docs/view.html#onlayout) instead.
+     */
+    measure: function(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
 
-  /**
-   * Determines the location of the given view in the window and returns the
-   * values via an async callback. If the React root view is embedded in
-   * another native view, this will give you the absolute coordinates. If
-   * successful, the callback will be called with the following
-   * arguments:
-   *
-   *  - x
-   *  - y
-   *  - width
-   *  - height
-   *
-   * Note that these measurements are not available until after the rendering
-   * has been completed in native.
-   */
-  measureInWindow: function(callback) {
-    UIManager.measureInWindow(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  },
+    /**
+     * Determines the location of the given view in the window and returns the
+     * values via an async callback. If the React root view is embedded in
+     * another native view, this will give you the absolute coordinates. If
+     * successful, the callback will be called with the following
+     * arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native.
+     */
+    measureInWindow: function(callback) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
 
-  /**
-   * Like [`measure()`](#measure), but measures the view relative an ancestor,
-   * specified as `relativeToNativeNode`. This means that the returned x, y
-   * are relative to the origin x, y of the ancestor view.
-   *
-   * As always, to obtain a native node handle for a component, you can use
-   * `findNumericNodeHandle(component)`.
-   */
-  measureLayout: function(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      findNumericNodeHandleFiber(this),
+    /**
+     * Like [`measure()`](#measure), but measures the view relative an ancestor,
+     * specified as `relativeToNativeNode`. This means that the returned x, y
+     * are relative to the origin x, y of the ancestor view.
+     *
+     * As always, to obtain a native node handle for a component, you can use
+     * `findNodeHandle(component)`.
+     */
+    measureLayout: function(
       relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  },
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    },
 
-  /**
-   * This function sends props straight to native. They will not participate in
-   * future diff process - this means that if you do not include them in the
-   * next render, they will remain active (see [Direct
-   * Manipulation](docs/direct-manipulation.html)).
-   */
-  setNativeProps: function(nativeProps) {
-    // Class components don't have viewConfig -> validateAttributes.
-    // Nor does it make sense to set native props on a non-native component.
-    // Instead, find the nearest host component and set props on it.
-    // Use findNodeHandle() rather than findNumericNodeHandle() because
-    // We want the instance/wrapper (not the native tag).
-    var maybeInstance = void 0;
-
-    // Fiber errors if findNodeHandle is called for an umounted component.
-    // Tests using ReactTestRenderer will trigger this case indirectly.
-    // Mimicking stack behavior, we should silently ignore this case.
-    // TODO Fix ReactTestRenderer so we can remove this try/catch.
-    try {
-      maybeInstance = findNodeHandle(this);
-    } catch (error) {}
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
+    setNativeProps: function(nativeProps) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
+
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
 
-    // If there is no host component beneath this we should fail silently.
-    // This is not an error; it could mean a class component rendered null.
-    if (maybeInstance == null) {
-      return;
-    }
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
 
-    var viewConfig = maybeInstance.viewConfig;
+      var viewConfig = maybeInstance.viewConfig;
 
-    {
-      warnForStyleProps(nativeProps, viewConfig.validAttributes);
-    }
+      {
+        warnForStyleProps(nativeProps, viewConfig.validAttributes);
+      }
 
-    var updatePayload = create(nativeProps, viewConfig.validAttributes);
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
 
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        maybeInstance._nativeTag,
-        viewConfig.uiViewClassName,
-        updatePayload
-      );
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    },
+
+    /**
+     * Requests focus for the given input or view. The exact behavior triggered
+     * will depend on the platform and type of view.
+     */
+    focus: function() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    },
+
+    /**
+     * Removes focus from an input or view. This is the opposite of `focus()`.
+     */
+    blur: function() {
+      TextInputState.blurTextInput(findNodeHandle(this));
     }
-  },
+  };
 
-  /**
-   * Requests focus for the given input or view. The exact behavior triggered
-   * will depend on the platform and type of view.
-   */
-  focus: function() {
-    TextInputState.focusTextInput(findNumericNodeHandleFiber(this));
-  },
+  {
+    // hide this from Flow since we can't define these properties outside of
+    // true without actually implementing them (setting them to undefined
+    // isn't allowed by ReactClass)
+    var NativeMethodsMixin_DEV = NativeMethodsMixin;
+    invariant(
+      !NativeMethodsMixin_DEV.componentWillMount &&
+        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
+      "Do not override existing functions."
+    );
+    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
+    // Once these lifecycles have been remove from the reconciler.
+    NativeMethodsMixin_DEV.componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
+      throwOnStylesProp(this, newProps);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
+      newProps
+    ) {
+      throwOnStylesProp(this, newProps);
+    };
 
-  /**
-   * Removes focus from an input or view. This is the opposite of `focus()`.
-   */
-  blur: function() {
-    TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
+    // React may warn about cWM/cWRP/cWU methods being deprecated.
+    // Add a flag to suppress these warnings for this special case.
+    // TODO (bvaughn) Remove this flag once the above methods have been removed.
+    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
+    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
   }
-};
-
-{
-  // hide this from Flow since we can't define these properties outside of
-  // true without actually implementing them (setting them to undefined
-  // isn't allowed by ReactClass)
-  var NativeMethodsMixin_DEV = NativeMethodsMixin;
-  invariant(
-    !NativeMethodsMixin_DEV.componentWillMount &&
-      !NativeMethodsMixin_DEV.componentWillReceiveProps &&
-      !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
-      !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
-    "Do not override existing functions."
-  );
-  // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
-  // Once these lifecycles have been remove from the reconciler.
-  NativeMethodsMixin_DEV.componentWillMount = function() {
-    throwOnStylesProp(this, this.props);
-  };
-  NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
-    throwOnStylesProp(this, newProps);
-  };
-  NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
-    throwOnStylesProp(this, this.props);
-  };
-  NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(newProps) {
-    throwOnStylesProp(this, newProps);
-  };
 
-  // React may warn about cWM/cWRP/cWU methods being deprecated.
-  // Add a flag to suppress these warnings for this special case.
-  // TODO (bvaughn) Remove this flag once the above methods have been removed.
-  NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
-  NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
-}
+  return NativeMethodsMixin;
+};
 
-function _classCallCheck$1(instance, Constructor) {
+function _classCallCheck(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
     throw new TypeError("Cannot call a class as a function");
   }
@@ -4000,166 +3574,200 @@ function _inherits(subClass, superClass) {
 }
 
 // Modules provided by RN:
-/**
- * Superclass that provides methods to access the underlying native component.
- * This can be useful when you want to focus a view or measure its dimensions.
- *
- * Methods implemented by this class are available on most default components
- * provided by React Native. However, they are *not* available on composite
- * components that are not directly backed by a native view. For more
- * information, see [Direct Manipulation](docs/direct-manipulation.html).
- *
- * @abstract
- */
-
-var ReactNativeComponent = (function(_React$Component) {
-  _inherits(ReactNativeComponent, _React$Component);
+var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
+  /**
+   * Superclass that provides methods to access the underlying native component.
+   * This can be useful when you want to focus a view or measure its dimensions.
+   *
+   * Methods implemented by this class are available on most default components
+   * provided by React Native. However, they are *not* available on composite
+   * components that are not directly backed by a native view. For more
+   * information, see [Direct Manipulation](docs/direct-manipulation.html).
+   *
+   * @abstract
+   */
+  var ReactNativeComponent = (function(_React$Component) {
+    _inherits(ReactNativeComponent, _React$Component);
 
-  function ReactNativeComponent() {
-    _classCallCheck$1(this, ReactNativeComponent);
+    function ReactNativeComponent() {
+      _classCallCheck(this, ReactNativeComponent);
 
-    return _possibleConstructorReturn(
-      this,
-      _React$Component.apply(this, arguments)
-    );
-  }
+      return _possibleConstructorReturn(
+        this,
+        _React$Component.apply(this, arguments)
+      );
+    }
 
-  /**
-   * Removes focus. This is the opposite of `focus()`.
-   */
+    /**
+     * Removes focus. This is the opposite of `focus()`.
+     */
 
-  /**
-   * Due to bugs in Flow's handling of React.createClass, some fields already
-   * declared in the base class need to be redeclared below.
-   */
-  ReactNativeComponent.prototype.blur = function blur() {
-    TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
-  };
+    /**
+     * Due to bugs in Flow's handling of React.createClass, some fields already
+     * declared in the base class need to be redeclared below.
+     */
+    ReactNativeComponent.prototype.blur = function blur() {
+      TextInputState.blurTextInput(findNodeHandle(this));
+    };
 
-  /**
-   * Requests focus. The exact behavior depends on the platform and view.
-   */
+    /**
+     * Requests focus. The exact behavior depends on the platform and view.
+     */
 
-  ReactNativeComponent.prototype.focus = function focus() {
-    TextInputState.focusTextInput(findNumericNodeHandleFiber(this));
-  };
+    ReactNativeComponent.prototype.focus = function focus() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    };
 
-  /**
-   * Measures the on-screen location and dimensions. If successful, the callback
-   * will be called asynchronously with the following arguments:
-   *
-   *  - x
-   *  - y
-   *  - width
-   *  - height
-   *  - pageX
-   *  - pageY
-   *
-   * These values are not available until after natives rendering completes. If
-   * you need the measurements as soon as possible, consider using the
-   * [`onLayout` prop](docs/view.html#onlayout) instead.
-   */
+    /**
+     * Measures the on-screen location and dimensions. If successful, the callback
+     * will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * These values are not available until after natives rendering completes. If
+     * you need the measurements as soon as possible, consider using the
+     * [`onLayout` prop](docs/view.html#onlayout) instead.
+     */
 
-  ReactNativeComponent.prototype.measure = function measure(callback) {
-    UIManager.measure(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  };
+    ReactNativeComponent.prototype.measure = function measure(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
 
-  /**
-   * Measures the on-screen location and dimensions. Even if the React Native
-   * root view is embedded within another native view, this method will give you
-   * the absolute coordinates measured from the window. If successful, the
-   * callback will be called asynchronously with the following arguments:
-   *
-   *  - x
-   *  - y
-   *  - width
-   *  - height
-   *
-   * These values are not available until after natives rendering completes.
-   */
+    /**
+     * Measures the on-screen location and dimensions. Even if the React Native
+     * root view is embedded within another native view, this method will give you
+     * the absolute coordinates measured from the window. If successful, the
+     * callback will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * These values are not available until after natives rendering completes.
+     */
 
-  ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
-    callback
-  ) {
-    UIManager.measureInWindow(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  };
+    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
 
-  /**
-   * Similar to [`measure()`](#measure), but the resulting location will be
-   * relative to the supplied ancestor's location.
-   *
-   * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
-   */
+    /**
+     * Similar to [`measure()`](#measure), but the resulting location will be
+     * relative to the supplied ancestor's location.
+     *
+     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
+     */
 
-  ReactNativeComponent.prototype.measureLayout = function measureLayout(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      findNumericNodeHandleFiber(this),
+    ReactNativeComponent.prototype.measureLayout = function measureLayout(
       relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  };
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
 
-  /**
-   * This function sends props straight to native. They will not participate in
-   * future diff process - this means that if you do not include them in the
-   * next render, they will remain active (see [Direct
-   * Manipulation](docs/direct-manipulation.html)).
-   */
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
 
-  ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
-    nativeProps
-  ) {
-    // Class components don't have viewConfig -> validateAttributes.
-    // Nor does it make sense to set native props on a non-native component.
-    // Instead, find the nearest host component and set props on it.
-    // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
-    // We want the instance/wrapper (not the native tag).
-    var maybeInstance = void 0;
-
-    // Fiber errors if findNodeHandle is called for an umounted component.
-    // Tests using ReactTestRenderer will trigger this case indirectly.
-    // Mimicking stack behavior, we should silently ignore this case.
-    // TODO Fix ReactTestRenderer so we can remove this try/catch.
-    try {
-      maybeInstance = findNodeHandle(this);
-    } catch (error) {}
+    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
+      nativeProps
+    ) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
+
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
 
-    // If there is no host component beneath this we should fail silently.
-    // This is not an error; it could mean a class component rendered null.
-    if (maybeInstance == null) {
-      return;
-    }
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
 
-    var viewConfig =
-      maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+      var viewConfig =
+        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
 
-    var updatePayload = create(nativeProps, viewConfig.validAttributes);
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
 
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        maybeInstance._nativeTag,
-        viewConfig.uiViewClassName,
-        updatePayload
-      );
-    }
-  };
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    };
+
+    return ReactNativeComponent;
+  })(React.Component);
+
+  // eslint-disable-next-line no-unused-expressions
 
   return ReactNativeComponent;
-})(React.Component);
+};
+
+/**
+ * `ReactInstanceMap` maintains a mapping from a public facing stateful
+ * instance (key) and the internal representation (value). This allows public
+ * methods to accept the user facing instance as an argument and map them back
+ * to internal methods.
+ *
+ * Note that this module is currently shared and assumed to be stateless.
+ * If this becomes an actual Map, that will break.
+ */
+
+/**
+ * This API should be called `delete` but we'd have to make sure to always
+ * transform these to strings for IE support. When this transform is fully
+ * supported we can rename it.
+ */
+
+function get$1(key) {
+  return key._reactInternalFiber;
+}
+
+function set(key, value) {
+  key._reactInternalFiber = value;
+}
+
+var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+
+var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
+var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
 
 // Don't change these two values. They're used by React Dev Tools.
 var NoEffect = /*              */ 0;
@@ -4241,7 +3849,7 @@ function isMounted(component) {
     }
   }
 
-  var fiber = get(component);
+  var fiber = get$1(component);
   if (!fiber) {
     return false;
   }
@@ -6205,7 +5813,7 @@ var ReactFiberClassComponent = function(
   var updater = {
     isMounted: isMounted,
     enqueueSetState: function(instance, partialState, callback) {
-      var fiber = get(instance);
+      var fiber = get$1(instance);
       callback = callback === undefined ? null : callback;
       {
         warnOnInvalidCallback(callback, "setState");
@@ -6224,7 +5832,7 @@ var ReactFiberClassComponent = function(
       scheduleWork(fiber, expirationTime);
     },
     enqueueReplaceState: function(instance, state, callback) {
-      var fiber = get(instance);
+      var fiber = get$1(instance);
       callback = callback === undefined ? null : callback;
       {
         warnOnInvalidCallback(callback, "replaceState");
@@ -6243,7 +5851,7 @@ var ReactFiberClassComponent = function(
       scheduleWork(fiber, expirationTime);
     },
     enqueueForceUpdate: function(instance, callback) {
-      var fiber = get(instance);
+      var fiber = get$1(instance);
       callback = callback === undefined ? null : callback;
       {
         warnOnInvalidCallback(callback, "forceUpdate");
@@ -9676,7 +9284,7 @@ var ReactFiberCompleteWork = function(
 
   function markUpdate(workInProgress) {
     // Tag the fiber with an update effect. This turns a Placement into
-    // an UpdateAndPlacement.
+    // a PlacementAndUpdate.
     workInProgress.effectTag |= Update;
   }
 
@@ -13876,7 +13484,7 @@ var ReactFiberReconciler$1 = function(config) {
       return emptyObject;
     }
 
-    var fiber = get(parentComponent);
+    var fiber = get$1(parentComponent);
     var parentContext = findCurrentUnmaskedContext(fiber);
     return isContextProvider(fiber)
       ? processChildContext(fiber, parentContext)
@@ -13974,7 +13582,19 @@ var ReactFiberReconciler$1 = function(config) {
     );
   }
 
-  function findHostInstance(fiber) {
+  function findHostInstance(component) {
+    var fiber = get$1(component);
+    if (fiber === undefined) {
+      if (typeof component.render === "function") {
+        invariant(false, "Unable to find node on an unmounted component.");
+      } else {
+        invariant(
+          false,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        );
+      }
+    }
     var hostFiber = findCurrentHostFiber(fiber);
     if (hostFiber === null) {
       return null;
@@ -14067,7 +13687,11 @@ var ReactFiberReconciler$1 = function(config) {
       return injectInternals(
         Object.assign({}, devToolsConfig, {
           findHostInstanceByFiber: function(fiber) {
-            return findHostInstance(fiber);
+            var hostFiber = findCurrentHostFiber(fiber);
+            if (hostFiber === null) {
+              return null;
+            }
+            return hostFiber.stateNode;
           },
           findFiberByHostInstance: function(instance) {
             if (!findFiberByHostInstance) {
@@ -14097,50 +13721,7 @@ var reactReconciler = ReactFiberReconciler$3["default"]
   ? ReactFiberReconciler$3["default"]
   : ReactFiberReconciler$3;
 
-var viewConfigCallbacks = new Map();
-var viewConfigs = new Map();
-
-/**
- * Registers a native view/component by name.
- * A callback is provided to load the view config from UIManager.
- * The callback is deferred until the view is actually rendered.
- * This is done to avoid causing Prepack deopts.
- */
-function register(name, callback) {
-  invariant(
-    !viewConfigCallbacks.has(name),
-    "Tried to register two views with the same name %s",
-    name
-  );
-  viewConfigCallbacks.set(name, callback);
-  return name;
-}
-
-/**
- * Retrieves a config for the specified view.
- * If this is the first time the view has been used,
- * This configuration will be lazy-loaded from UIManager.
- */
-function get$1(name) {
-  var viewConfig = void 0;
-  if (!viewConfigs.has(name)) {
-    var callback = viewConfigCallbacks.get(name);
-    invariant(
-      typeof callback === "function",
-      "View config not found for name %s",
-      name
-    );
-    viewConfigCallbacks.set(name, null);
-    viewConfig = callback();
-    viewConfigs.set(name, viewConfig);
-  } else {
-    viewConfig = viewConfigs.get(name);
-  }
-  invariant(viewConfig, "View config not found for name %s", name);
-  return viewConfig;
-}
-
-function _classCallCheck$2(instance, Constructor) {
+function _classCallCheck$1(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
     throw new TypeError("Cannot call a class as a function");
   }
@@ -14157,7 +13738,7 @@ function _classCallCheck$2(instance, Constructor) {
 
 var ReactNativeFiberHostComponent = (function() {
   function ReactNativeFiberHostComponent(tag, viewConfig) {
-    _classCallCheck$2(this, ReactNativeFiberHostComponent);
+    _classCallCheck$1(this, ReactNativeFiberHostComponent);
 
     this._nativeTag = tag;
     this._children = [];
@@ -14272,6 +13853,19 @@ function cancelDeferredCallback(callbackID) {
 }
 
 // Modules provided by RN:
+// Counter for uniquely identifying views.
+// % 10 === 1 means it is a rootTag.
+// % 2 === 0 means it is a Fabric tag.
+var nextReactTag = 3;
+function allocateTag() {
+  var tag = nextReactTag;
+  if (tag % 10 === 1) {
+    tag += 2;
+  }
+  nextReactTag = tag + 2;
+  return tag;
+}
+
 function recursivelyUncacheFiberNode(node) {
   if (typeof node === "number") {
     // Leaf node (eg text)
@@ -14294,8 +13888,8 @@ var NativeRenderer = reactReconciler({
     hostContext,
     internalInstanceHandle
   ) {
-    var tag = ReactNativeTagHandles.allocateTag();
-    var viewConfig = get$1(type);
+    var tag = allocateTag();
+    var viewConfig = ReactNativeViewConfigRegistry.get(type);
 
     {
       for (var key in viewConfig.validAttributes) {
@@ -14329,7 +13923,7 @@ var NativeRenderer = reactReconciler({
     hostContext,
     internalInstanceHandle
   ) {
-    var tag = ReactNativeTagHandles.allocateTag();
+    var tag = allocateTag();
 
     UIManager.createView(
       tag, // reactTag
@@ -14665,48 +14259,51 @@ var getInspectorDataForViewTag = void 0;
   };
 }
 
-/**
- * Creates a renderable ReactNative host component.
- * Use this method for view configs that are loaded from UIManager.
- * Use createReactNativeComponentClass() for view configs defined within JavaScript.
- *
- * @param {string} config iOS View configuration.
- * @private
- */
-var createReactNativeComponentClass = function(name, callback) {
-  return register(name, callback);
-};
-
 // Module provided by RN:
-/**
- * Capture an image of the screen, window or an individual view. The image
- * will be stored in a temporary file that will only exist for as long as the
- * app is running.
- *
- * The `view` argument can be the literal string `window` if you want to
- * capture the entire window, or it can be a reference to a specific
- * React Native component.
- *
- * The `options` argument may include:
- * - width/height (number) - the width and height of the image to capture.
- * - format (string) - either 'png' or 'jpeg'. Defaults to 'png'.
- * - quality (number) - the quality when using jpeg. 0.0 - 1.0 (default).
- *
- * Returns a Promise.
- * @platform ios
- */
-function takeSnapshot(view, options) {
-  if (typeof view !== "number" && view !== "window") {
-    view = findNumericNodeHandleFiber(view) || "window";
-  }
+var findHostInstance = NativeRenderer.findHostInstance;
 
-  // Call the hidden '__takeSnapshot' method; the main one throws an error to
-  // prevent accidental backwards-incompatible usage.
-  return UIManager.__takeSnapshot(view, options);
-}
+function findNodeHandle(componentOrHandle) {
+  {
+    var owner = ReactCurrentOwner.current;
+    if (owner !== null && owner.stateNode !== null) {
+      !owner.stateNode._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing findNodeHandle inside its render(). " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(owner) || "A component"
+          )
+        : void 0;
 
-// Module provided by RN:
-injectFindHostInstance(NativeRenderer.findHostInstance);
+      owner.stateNode._warnedAboutRefsInRender = true;
+    }
+  }
+  if (componentOrHandle == null) {
+    return null;
+  }
+  if (typeof componentOrHandle === "number") {
+    // Already a node handle
+    return componentOrHandle;
+  }
+  if (componentOrHandle._nativeTag) {
+    return componentOrHandle._nativeTag;
+  }
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag) {
+    return componentOrHandle.canonical._nativeTag;
+  }
+  var hostInstance = findHostInstance(componentOrHandle);
+  if (hostInstance == null) {
+    return hostInstance;
+  }
+  if (hostInstance.canonical) {
+    // Fabric
+    return hostInstance.canonical._nativeTag;
+  }
+  return hostInstance._nativeTag;
+}
 
 injection$2.injectRenderer(NativeRenderer);
 
@@ -14721,9 +14318,9 @@ function computeComponentStackForErrorReporting(reactTag) {
 var roots = new Map();
 
 var ReactNativeRenderer = {
-  NativeComponent: ReactNativeComponent,
+  NativeComponent: ReactNativeComponent(findNodeHandle, findHostInstance),
 
-  findNodeHandle: findNumericNodeHandleFiber,
+  findNodeHandle: findNodeHandle,
 
   render: function(element, containerTag, callback) {
     var root = roots.get(containerTag);
@@ -14762,18 +14359,11 @@ var ReactNativeRenderer = {
 
   unstable_batchedUpdates: batchedUpdates,
 
-  flushSync: NativeRenderer.flushSync,
-
   __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
     // Used as a mixin in many createClass-based components
-    NativeMethodsMixin: NativeMethodsMixin,
+    NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
     // Used by react-native-github/Libraries/ components
-    ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin, // requireNativeComponent
     ReactNativeComponentTree: ReactNativeComponentTree, // ScrollResponder
-    ReactNativePropRegistry: ReactNativePropRegistry, // flattenStyle, Stylesheet
-    TouchHistoryMath: TouchHistoryMath, // PanResponder
-    createReactNativeComponentClass: createReactNativeComponentClass, // RCTText, RCTView, ReactNativeART
-    takeSnapshot: takeSnapshot, // react-native-implementation
     computeComponentStackForErrorReporting: computeComponentStackForErrorReporting
   }
 };
diff --git a/Libraries/Renderer/ReactNativeRenderer-prod.js b/Libraries/Renderer/ReactNativeRenderer-prod.js
index bf2480f1c03d..10e7f6b5fc96 100644
--- a/Libraries/Renderer/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/ReactNativeRenderer-prod.js
@@ -13,6 +13,7 @@
 require("InitializeCore");
 var invariant = require("fbjs/lib/invariant"),
   emptyFunction = require("fbjs/lib/emptyFunction"),
+  ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
   UIManager = require("UIManager"),
   RCTEventEmitter = require("RCTEventEmitter"),
   TextInputState = require("TextInputState"),
@@ -624,7 +625,7 @@ function changeResponder(nextResponderInst, blockHostResponder) {
       blockHostResponder
     );
 }
-var eventTypes = {
+var eventTypes$1 = {
     startShouldSetResponder: {
       phasedRegistrationNames: {
         bubbled: "onStartShouldSetResponder",
@@ -664,7 +665,7 @@ var eventTypes = {
     _getResponder: function() {
       return responderInst;
     },
-    eventTypes: eventTypes,
+    eventTypes: eventTypes$1,
     extractEvents: function(
       topLevelType,
       targetInst,
@@ -690,12 +691,12 @@ var eventTypes = {
           isMoveish(topLevelType))
       ) {
         var JSCompiler_temp = isStartish(topLevelType)
-          ? eventTypes.startShouldSetResponder
+          ? eventTypes$1.startShouldSetResponder
           : isMoveish(topLevelType)
-            ? eventTypes.moveShouldSetResponder
+            ? eventTypes$1.moveShouldSetResponder
             : "topSelectionChange" === topLevelType
-              ? eventTypes.selectionChangeShouldSetResponder
-              : eventTypes.scrollShouldSetResponder;
+              ? eventTypes$1.selectionChangeShouldSetResponder
+              : eventTypes$1.scrollShouldSetResponder;
         if (responderInst)
           b: {
             var JSCompiler_temp$jscomp$0 = responderInst;
@@ -781,7 +782,7 @@ var eventTypes = {
         JSCompiler_temp && JSCompiler_temp !== responderInst
           ? ((JSCompiler_temp$jscomp$0 = void 0),
             (targetInst = ResponderSyntheticEvent.getPooled(
-              eventTypes.responderGrant,
+              eventTypes$1.responderGrant,
               JSCompiler_temp,
               nativeEvent,
               nativeEventTarget
@@ -791,7 +792,7 @@ var eventTypes = {
             (depthA = !0 === executeDirectDispatch(targetInst)),
             responderInst
               ? ((tempA = ResponderSyntheticEvent.getPooled(
-                  eventTypes.responderTerminationRequest,
+                  eventTypes$1.responderTerminationRequest,
                   responderInst,
                   nativeEvent,
                   nativeEventTarget
@@ -803,7 +804,7 @@ var eventTypes = {
                 tempA.isPersistent() || tempA.constructor.release(tempA),
                 tempB
                   ? ((tempA = ResponderSyntheticEvent.getPooled(
-                      eventTypes.responderTerminate,
+                      eventTypes$1.responderTerminate,
                       responderInst,
                       nativeEvent,
                       nativeEventTarget
@@ -817,7 +818,7 @@ var eventTypes = {
                     )),
                     changeResponder(JSCompiler_temp, depthA))
                   : ((JSCompiler_temp = ResponderSyntheticEvent.getPooled(
-                      eventTypes.responderReject,
+                      eventTypes$1.responderReject,
                       JSCompiler_temp,
                       nativeEvent,
                       nativeEventTarget
@@ -845,10 +846,10 @@ var eventTypes = {
       depthA = responderInst && isEndish(topLevelType);
       if (
         (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
-          ? eventTypes.responderStart
+          ? eventTypes$1.responderStart
           : targetInst
-            ? eventTypes.responderMove
-            : depthA ? eventTypes.responderEnd : null)
+            ? eventTypes$1.responderMove
+            : depthA ? eventTypes$1.responderEnd : null)
       )
         (JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
           JSCompiler_temp$jscomp$0,
@@ -899,8 +900,8 @@ var eventTypes = {
         }
       if (
         (topLevelType = JSCompiler_temp$jscomp$0
-          ? eventTypes.responderTerminate
-          : topLevelType ? eventTypes.responderRelease : null)
+          ? eventTypes$1.responderTerminate
+          : topLevelType ? eventTypes$1.responderRelease : null)
       )
         (nativeEvent = ResponderSyntheticEvent.getPooled(
           topLevelType,
@@ -932,10 +933,12 @@ var eventTypes = {
       }
     }
   },
-  customBubblingEventTypes = {},
-  customDirectEventTypes = {},
+  customBubblingEventTypes$1 =
+    ReactNativeViewConfigRegistry.customBubblingEventTypes,
+  customDirectEventTypes$1 =
+    ReactNativeViewConfigRegistry.customDirectEventTypes,
   ReactNativeBridgeEventPlugin = {
-    eventTypes: {},
+    eventTypes: ReactNativeViewConfigRegistry.eventTypes,
     extractEvents: function(
       topLevelType,
       targetInst,
@@ -943,8 +946,8 @@ var eventTypes = {
       nativeEventTarget
     ) {
       if (null == targetInst) return null;
-      var bubbleDispatchConfig = customBubblingEventTypes[topLevelType],
-        directDispatchConfig = customDirectEventTypes[topLevelType];
+      var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType],
+        directDispatchConfig = customDirectEventTypes$1[topLevelType];
       invariant(
         bubbleDispatchConfig || directDispatchConfig,
         'Unsupported top level event type "%s" dispatched',
@@ -962,24 +965,6 @@ var eventTypes = {
         forEachAccumulated(topLevelType, accumulateDirectDispatchesSingle);
       else return null;
       return topLevelType;
-    },
-    processEventTypes: function(viewConfig) {
-      var bubblingEventTypes = viewConfig.bubblingEventTypes;
-      viewConfig = viewConfig.directEventTypes;
-      if (null != bubblingEventTypes)
-        for (var _topLevelType in bubblingEventTypes)
-          null == customBubblingEventTypes[_topLevelType] &&
-            (ReactNativeBridgeEventPlugin.eventTypes[
-              _topLevelType
-            ] = customBubblingEventTypes[_topLevelType] =
-              bubblingEventTypes[_topLevelType]);
-      if (null != viewConfig)
-        for (var _topLevelType2 in viewConfig)
-          null == customDirectEventTypes[_topLevelType2] &&
-            (ReactNativeBridgeEventPlugin.eventTypes[
-              _topLevelType2
-            ] = customDirectEventTypes[_topLevelType2] =
-              viewConfig[_topLevelType2]);
     }
   },
   instanceCache = {},
@@ -1067,28 +1052,7 @@ function batchedUpdates(fn, bookkeeping) {
           restoreStateOfTarget(fn[bookkeeping]);
   }
 }
-var ReactNativeTagHandles = {
-    tagsStartAt: 1,
-    tagCount: 1,
-    allocateTag: function() {
-      for (; this.reactTagIsNativeTopRootID(ReactNativeTagHandles.tagCount); )
-        ReactNativeTagHandles.tagCount++;
-      var tag = ReactNativeTagHandles.tagCount;
-      ReactNativeTagHandles.tagCount++;
-      return tag;
-    },
-    assertRootTag: function(tag) {
-      invariant(
-        this.reactTagIsNativeTopRootID(tag),
-        "Expect a native root tag, instead got %s",
-        tag
-      );
-    },
-    reactTagIsNativeTopRootID: function(reactTag) {
-      return 1 === reactTag % 10;
-    }
-  },
-  EMPTY_NATIVE_EVENT = {};
+var EMPTY_NATIVE_EVENT = {};
 function _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam) {
   var nativeEvent = nativeEventParam || EMPTY_NATIVE_EVENT,
     inst = getInstanceFromTag(rootNodeID);
@@ -1153,10 +1117,7 @@ var ReactNativeEventEmitter = Object.freeze({
       i.touches = touches;
       index = null;
       var target = i.target;
-      null === target ||
-        void 0 === target ||
-        target < ReactNativeTagHandles.tagsStartAt ||
-        (index = target);
+      null === target || void 0 === target || 1 > target || (index = target);
       _receiveRootNodeIDEvent(index, eventTopLevelType, i);
     }
   }
@@ -1197,103 +1158,6 @@ function createPortal(children, containerInfo, implementation) {
     implementation: implementation
   };
 }
-var TouchHistoryMath = {
-  centroidDimension: function(
-    touchHistory,
-    touchesChangedAfter,
-    isXAxis,
-    ofCurrent
-  ) {
-    var touchBank = touchHistory.touchBank,
-      total = 0,
-      count = 0;
-    touchHistory =
-      1 === touchHistory.numberActiveTouches
-        ? touchHistory.touchBank[touchHistory.indexOfSingleActiveTouch]
-        : null;
-    if (null !== touchHistory)
-      touchHistory.touchActive &&
-        touchHistory.currentTimeStamp > touchesChangedAfter &&
-        ((total +=
-          ofCurrent && isXAxis
-            ? touchHistory.currentPageX
-            : ofCurrent && !isXAxis
-              ? touchHistory.currentPageY
-              : !ofCurrent && isXAxis
-                ? touchHistory.previousPageX
-                : touchHistory.previousPageY),
-        (count = 1));
-    else
-      for (touchHistory = 0; touchHistory < touchBank.length; touchHistory++) {
-        var touchTrack = touchBank[touchHistory];
-        null !== touchTrack &&
-          void 0 !== touchTrack &&
-          touchTrack.touchActive &&
-          touchTrack.currentTimeStamp >= touchesChangedAfter &&
-          ((total +=
-            ofCurrent && isXAxis
-              ? touchTrack.currentPageX
-              : ofCurrent && !isXAxis
-                ? touchTrack.currentPageY
-                : !ofCurrent && isXAxis
-                  ? touchTrack.previousPageX
-                  : touchTrack.previousPageY),
-          count++);
-      }
-    return 0 < count ? total / count : TouchHistoryMath.noCentroid;
-  },
-  currentCentroidXOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      !0,
-      !0
-    );
-  },
-  currentCentroidYOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      !1,
-      !0
-    );
-  },
-  previousCentroidXOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      !0,
-      !1
-    );
-  },
-  previousCentroidYOfTouchesChangedAfter: function(
-    touchHistory,
-    touchesChangedAfter
-  ) {
-    return TouchHistoryMath.centroidDimension(
-      touchHistory,
-      touchesChangedAfter,
-      !1,
-      !1
-    );
-  },
-  currentCentroidX: function(touchHistory) {
-    return TouchHistoryMath.centroidDimension(touchHistory, 0, !0, !0);
-  },
-  currentCentroidY: function(touchHistory) {
-    return TouchHistoryMath.centroidDimension(touchHistory, 0, !1, !0);
-  },
-  noCentroid: -1
-};
 function getComponentName(fiber) {
   fiber = fiber.type;
   if ("function" === typeof fiber) return fiber.displayName || fiber.name;
@@ -1343,37 +1207,9 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
   } while (workInProgress);
   return info;
 }
-var objects = {},
-  uniqueID = 1,
-  emptyObject$2 = {},
-  ReactNativePropRegistry = (function() {
-    function ReactNativePropRegistry() {
-      if (!(this instanceof ReactNativePropRegistry))
-        throw new TypeError("Cannot call a class as a function");
-    }
-    ReactNativePropRegistry.register = function(object) {
-      var id = ++uniqueID;
-      objects[id] = object;
-      return id;
-    };
-    ReactNativePropRegistry.getByID = function(id) {
-      if (!id) return emptyObject$2;
-      var object = objects[id];
-      return object
-        ? object
-        : (console.warn("Invalid style with id `" + id + "`. Skipping ..."),
-          emptyObject$2);
-    };
-    return ReactNativePropRegistry;
-  })(),
-  emptyObject$1 = {},
+var emptyObject$1 = {},
   removedKeys = null,
   removedKeyCount = 0;
-function resolveObject(idOrObject) {
-  return "number" === typeof idOrObject
-    ? ReactNativePropRegistry.getByID(idOrObject)
-    : idOrObject;
-}
 function restoreDeletedValuesInNestedArray(
   updatePayload,
   node,
@@ -1387,7 +1223,7 @@ function restoreDeletedValuesInNestedArray(
         validAttributes
       );
   else if (node && 0 < removedKeyCount)
-    for (i in ((node = resolveObject(node)), removedKeys))
+    for (i in removedKeys)
       if (removedKeys[i]) {
         var _nextProp = node[i];
         if (void 0 !== _nextProp) {
@@ -1426,12 +1262,7 @@ function diffNestedProperty(
         ? clearNestedProperty(updatePayload, prevProp, validAttributes)
         : updatePayload;
   if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
-    return diffProperties(
-      updatePayload,
-      resolveObject(prevProp),
-      resolveObject(nextProp),
-      validAttributes
-    );
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
   if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
     var minLength =
         prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
@@ -1461,12 +1292,12 @@ function diffNestedProperty(
     ? diffProperties(
         updatePayload,
         flattenStyle(prevProp),
-        resolveObject(nextProp),
+        nextProp,
         validAttributes
       )
     : diffProperties(
         updatePayload,
-        resolveObject(prevProp),
+        prevProp,
         flattenStyle(nextProp),
         validAttributes
       );
@@ -1474,9 +1305,11 @@ function diffNestedProperty(
 function addNestedProperty(updatePayload, nextProp, validAttributes) {
   if (!nextProp) return updatePayload;
   if (!Array.isArray(nextProp))
-    return (
-      (nextProp = resolveObject(nextProp)),
-      diffProperties(updatePayload, emptyObject$1, nextProp, validAttributes)
+    return diffProperties(
+      updatePayload,
+      emptyObject$1,
+      nextProp,
+      validAttributes
     );
   for (var i = 0; i < nextProp.length; i++)
     updatePayload = addNestedProperty(
@@ -1489,9 +1322,11 @@ function addNestedProperty(updatePayload, nextProp, validAttributes) {
 function clearNestedProperty(updatePayload, prevProp, validAttributes) {
   if (!prevProp) return updatePayload;
   if (!Array.isArray(prevProp))
-    return (
-      (prevProp = resolveObject(prevProp)),
-      diffProperties(updatePayload, prevProp, emptyObject$1, validAttributes)
+    return diffProperties(
+      updatePayload,
+      prevProp,
+      emptyObject$1,
+      validAttributes
     );
   for (var i = 0; i < prevProp.length; i++)
     updatePayload = clearNestedProperty(
@@ -1604,37 +1439,6 @@ function mountSafeCallback(context, callback) {
     }
   };
 }
-var ReactCurrentOwner =
-  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
-function findHostInstance() {
-  return null;
-}
-function findNodeHandle(componentOrHandle) {
-  if (null == componentOrHandle) return null;
-  if ("number" === typeof componentOrHandle) return componentOrHandle;
-  var internalInstance = componentOrHandle._reactInternalFiber;
-  if (internalInstance) return findHostInstance(internalInstance) || null;
-  if (componentOrHandle) return componentOrHandle;
-  invariant(
-    ("object" === typeof componentOrHandle &&
-      "_nativeTag" in componentOrHandle) ||
-      (null != componentOrHandle.render &&
-        "function" === typeof componentOrHandle.render),
-    "findNodeHandle(...): Argument is not a component (type: %s, keys: %s)",
-    typeof componentOrHandle,
-    Object.keys(componentOrHandle)
-  );
-  invariant(
-    !1,
-    "findNodeHandle(...): Unable to find node handle for unmounted component."
-  );
-}
-function findNumericNodeHandleFiber(componentOrHandle) {
-  componentOrHandle = findNodeHandle(componentOrHandle);
-  return null == componentOrHandle || "number" === typeof componentOrHandle
-    ? componentOrHandle
-    : componentOrHandle._nativeTag;
-}
 function _inherits(subClass, superClass) {
   if ("function" !== typeof superClass && null !== superClass)
     throw new TypeError(
@@ -1654,74 +1458,8 @@ function _inherits(subClass, superClass) {
       ? Object.setPrototypeOf(subClass, superClass)
       : (subClass.__proto__ = superClass));
 }
-var ReactNativeComponent = (function(_React$Component) {
-  function ReactNativeComponent() {
-    if (!(this instanceof ReactNativeComponent))
-      throw new TypeError("Cannot call a class as a function");
-    var call = _React$Component.apply(this, arguments);
-    if (!this)
-      throw new ReferenceError(
-        "this hasn't been initialised - super() hasn't been called"
-      );
-    return !call || ("object" !== typeof call && "function" !== typeof call)
-      ? this
-      : call;
-  }
-  _inherits(ReactNativeComponent, _React$Component);
-  ReactNativeComponent.prototype.blur = function() {
-    TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
-  };
-  ReactNativeComponent.prototype.focus = function() {
-    TextInputState.focusTextInput(findNumericNodeHandleFiber(this));
-  };
-  ReactNativeComponent.prototype.measure = function(callback) {
-    UIManager.measure(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  };
-  ReactNativeComponent.prototype.measureInWindow = function(callback) {
-    UIManager.measureInWindow(
-      findNumericNodeHandleFiber(this),
-      mountSafeCallback(this, callback)
-    );
-  };
-  ReactNativeComponent.prototype.measureLayout = function(
-    relativeToNativeNode,
-    onSuccess,
-    onFail
-  ) {
-    UIManager.measureLayout(
-      findNumericNodeHandleFiber(this),
-      relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  };
-  ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
-    var maybeInstance = void 0;
-    try {
-      maybeInstance = findNodeHandle(this);
-    } catch (error) {}
-    if (null != maybeInstance) {
-      var viewConfig =
-        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
-      nativeProps = diffProperties(
-        null,
-        emptyObject$1,
-        nativeProps,
-        viewConfig.validAttributes
-      );
-      null != nativeProps &&
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          nativeProps
-        );
-    }
-  };
-  return ReactNativeComponent;
-})(React.Component);
+var ReactCurrentOwner =
+  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
 function isFiberMountedImpl(fiber) {
   var node = fiber;
   if (fiber.alternate) for (; node["return"]; ) node = node["return"];
@@ -6048,10 +5786,6 @@ function ReactFiberReconciler$1(config) {
     scheduleWork(currentTime, expirationTime);
     return expirationTime;
   }
-  function findHostInstance(fiber) {
-    fiber = findCurrentHostFiber(fiber);
-    return null === fiber ? null : fiber.stateNode;
-  }
   var getPublicInstance = config.getPublicInstance;
   config = ReactFiberScheduler(config);
   var recalculateCurrentTime = config.recalculateCurrentTime,
@@ -6130,7 +5864,19 @@ function ReactFiberReconciler$1(config) {
           return container.child.stateNode;
       }
     },
-    findHostInstance: findHostInstance,
+    findHostInstance: function(component) {
+      var fiber = component._reactInternalFiber;
+      void 0 === fiber &&
+        ("function" === typeof component.render
+          ? invariant(!1, "Unable to find node on an unmounted component.")
+          : invariant(
+              !1,
+              "Argument appears to not be a ReactComponent. Keys: %s",
+              Object.keys(component)
+            ));
+      component = findCurrentHostFiber(fiber);
+      return null === component ? null : component.stateNode;
+    },
     findHostInstanceWithNoPortals: function(fiber) {
       fiber = findCurrentHostFiberWithNoPortals(fiber);
       return null === fiber ? null : fiber.stateNode;
@@ -6140,7 +5886,8 @@ function ReactFiberReconciler$1(config) {
       return injectInternals(
         Object.assign({}, devToolsConfig, {
           findHostInstanceByFiber: function(fiber) {
-            return findHostInstance(fiber);
+            fiber = findCurrentHostFiber(fiber);
+            return null === fiber ? null : fiber.stateNode;
           },
           findFiberByHostInstance: function(instance) {
             return findFiberByHostInstance
@@ -6159,8 +5906,6 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
   reactReconciler = ReactFiberReconciler$3["default"]
     ? ReactFiberReconciler$3["default"]
     : ReactFiberReconciler$3,
-  viewConfigCallbacks = new Map(),
-  viewConfigs = new Map(),
   ReactNativeFiberHostComponent = (function() {
     function ReactNativeFiberHostComponent(tag, viewConfig) {
       if (!(this instanceof ReactNativeFiberHostComponent))
@@ -6238,6 +5983,13 @@ function setTimeoutCallback() {
   scheduledCallback = null;
   null !== callback && callback(frameDeadlineObject);
 }
+var nextReactTag = 3;
+function allocateTag() {
+  var tag = nextReactTag;
+  1 === tag % 10 && (tag += 2);
+  nextReactTag = tag + 2;
+  return tag;
+}
 function recursivelyUncacheFiberNode(node) {
   "number" === typeof node
     ? uncacheFiberNode(node)
@@ -6255,21 +6007,9 @@ var NativeRenderer = reactReconciler({
       hostContext,
       internalInstanceHandle
     ) {
-      hostContext = ReactNativeTagHandles.allocateTag();
-      if (viewConfigs.has(type)) var viewConfig = viewConfigs.get(type);
-      else
-        (viewConfig = viewConfigCallbacks.get(type)),
-          invariant(
-            "function" === typeof viewConfig,
-            "View config not found for name %s",
-            type
-          ),
-          viewConfigCallbacks.set(type, null),
-          (viewConfig = viewConfig()),
-          viewConfigs.set(type, viewConfig);
-      invariant(viewConfig, "View config not found for name %s", type);
-      type = viewConfig;
-      viewConfig = diffProperties(
+      hostContext = allocateTag();
+      type = ReactNativeViewConfigRegistry.get(type);
+      var updatePayload = diffProperties(
         null,
         emptyObject$1,
         props,
@@ -6279,7 +6019,7 @@ var NativeRenderer = reactReconciler({
         hostContext,
         type.uiViewClassName,
         rootContainerInstance,
-        viewConfig
+        updatePayload
       );
       rootContainerInstance = new ReactNativeFiberHostComponent(
         hostContext,
@@ -6295,7 +6035,7 @@ var NativeRenderer = reactReconciler({
       hostContext,
       internalInstanceHandle
     ) {
-      hostContext = ReactNativeTagHandles.allocateTag();
+      hostContext = allocateTag();
       UIManager.createView(hostContext, "RCTRawText", rootContainerInstance, {
         text: text
       });
@@ -6453,13 +6193,96 @@ var NativeRenderer = reactReconciler({
 getInspectorDataForViewTag = function() {
   invariant(!1, "getInspectorDataForViewTag() is not available in production");
 };
-findHostInstance = NativeRenderer.findHostInstance;
+var findHostInstance = NativeRenderer.findHostInstance;
+function findNodeHandle(componentOrHandle) {
+  if (null == componentOrHandle) return null;
+  if ("number" === typeof componentOrHandle) return componentOrHandle;
+  if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
+    return componentOrHandle.canonical._nativeTag;
+  componentOrHandle = findHostInstance(componentOrHandle);
+  return null == componentOrHandle
+    ? componentOrHandle
+    : componentOrHandle.canonical
+      ? componentOrHandle.canonical._nativeTag
+      : componentOrHandle._nativeTag;
+}
 _batchedUpdates = NativeRenderer.batchedUpdates;
 _flushInteractiveUpdates = NativeRenderer.flushInteractiveUpdates;
 var roots = new Map(),
   ReactNativeRenderer = {
-    NativeComponent: ReactNativeComponent,
-    findNodeHandle: findNumericNodeHandleFiber,
+    NativeComponent: (function(findNodeHandle, findHostInstance) {
+      return (function(_React$Component) {
+        function ReactNativeComponent() {
+          if (!(this instanceof ReactNativeComponent))
+            throw new TypeError("Cannot call a class as a function");
+          var call = _React$Component.apply(this, arguments);
+          if (!this)
+            throw new ReferenceError(
+              "this hasn't been initialised - super() hasn't been called"
+            );
+          return !call ||
+            ("object" !== typeof call && "function" !== typeof call)
+            ? this
+            : call;
+        }
+        _inherits(ReactNativeComponent, _React$Component);
+        ReactNativeComponent.prototype.blur = function() {
+          TextInputState.blurTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.focus = function() {
+          TextInputState.focusTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.measure = function(callback) {
+          UIManager.measure(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureInWindow = function(callback) {
+          UIManager.measureInWindow(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureLayout = function(
+          relativeToNativeNode,
+          onSuccess,
+          onFail
+        ) {
+          UIManager.measureLayout(
+            findNodeHandle(this),
+            relativeToNativeNode,
+            mountSafeCallback(this, onFail),
+            mountSafeCallback(this, onSuccess)
+          );
+        };
+        ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
+          var maybeInstance = void 0;
+          try {
+            maybeInstance = findHostInstance(this);
+          } catch (error) {}
+          if (null != maybeInstance) {
+            var viewConfig =
+              maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+            nativeProps = diffProperties(
+              null,
+              emptyObject$1,
+              nativeProps,
+              viewConfig.validAttributes
+            );
+            null != nativeProps &&
+              UIManager.updateView(
+                maybeInstance._nativeTag,
+                viewConfig.uiViewClassName,
+                nativeProps
+              );
+          }
+        };
+        return ReactNativeComponent;
+      })(React.Component);
+    })(findNodeHandle, findHostInstance),
+    findNodeHandle: findNodeHandle,
     render: function(element, containerTag, callback) {
       var root = roots.get(containerTag);
       root ||
@@ -6488,76 +6311,59 @@ var roots = new Map(),
       );
     },
     unstable_batchedUpdates: batchedUpdates,
-    flushSync: NativeRenderer.flushSync,
     __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
-      NativeMethodsMixin: {
-        measure: function(callback) {
-          UIManager.measure(
-            findNumericNodeHandleFiber(this),
-            mountSafeCallback(this, callback)
-          );
-        },
-        measureInWindow: function(callback) {
-          UIManager.measureInWindow(
-            findNumericNodeHandleFiber(this),
-            mountSafeCallback(this, callback)
-          );
-        },
-        measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
-          UIManager.measureLayout(
-            findNumericNodeHandleFiber(this),
-            relativeToNativeNode,
-            mountSafeCallback(this, onFail),
-            mountSafeCallback(this, onSuccess)
-          );
-        },
-        setNativeProps: function(nativeProps) {
-          var maybeInstance = void 0;
-          try {
-            maybeInstance = findNodeHandle(this);
-          } catch (error) {}
-          if (null != maybeInstance) {
-            var viewConfig = maybeInstance.viewConfig;
-            nativeProps = diffProperties(
-              null,
-              emptyObject$1,
-              nativeProps,
-              viewConfig.validAttributes
+      NativeMethodsMixin: (function(findNodeHandle, findHostInstance) {
+        return {
+          measure: function(callback) {
+            UIManager.measure(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
             );
-            null != nativeProps &&
-              UIManager.updateView(
-                maybeInstance._nativeTag,
-                viewConfig.uiViewClassName,
-                nativeProps
+          },
+          measureInWindow: function(callback) {
+            UIManager.measureInWindow(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
+            UIManager.measureLayout(
+              findNodeHandle(this),
+              relativeToNativeNode,
+              mountSafeCallback(this, onFail),
+              mountSafeCallback(this, onSuccess)
+            );
+          },
+          setNativeProps: function(nativeProps) {
+            var maybeInstance = void 0;
+            try {
+              maybeInstance = findHostInstance(this);
+            } catch (error) {}
+            if (null != maybeInstance) {
+              var viewConfig = maybeInstance.viewConfig;
+              nativeProps = diffProperties(
+                null,
+                emptyObject$1,
+                nativeProps,
+                viewConfig.validAttributes
               );
+              null != nativeProps &&
+                UIManager.updateView(
+                  maybeInstance._nativeTag,
+                  viewConfig.uiViewClassName,
+                  nativeProps
+                );
+            }
+          },
+          focus: function() {
+            TextInputState.focusTextInput(findNodeHandle(this));
+          },
+          blur: function() {
+            TextInputState.blurTextInput(findNodeHandle(this));
           }
-        },
-        focus: function() {
-          TextInputState.focusTextInput(findNumericNodeHandleFiber(this));
-        },
-        blur: function() {
-          TextInputState.blurTextInput(findNumericNodeHandleFiber(this));
-        }
-      },
-      ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin,
+        };
+      })(findNodeHandle, findHostInstance),
       ReactNativeComponentTree: ReactNativeComponentTree,
-      ReactNativePropRegistry: ReactNativePropRegistry,
-      TouchHistoryMath: TouchHistoryMath,
-      createReactNativeComponentClass: function(name, callback) {
-        invariant(
-          !viewConfigCallbacks.has(name),
-          "Tried to register two views with the same name %s",
-          name
-        );
-        viewConfigCallbacks.set(name, callback);
-        return name;
-      },
-      takeSnapshot: function(view, options) {
-        "number" !== typeof view &&
-          "window" !== view &&
-          (view = findNumericNodeHandleFiber(view) || "window");
-        return UIManager.__takeSnapshot(view, options);
-      },
       computeComponentStackForErrorReporting: function(reactTag) {
         return (reactTag = getInstanceFromTag(reactTag))
           ? getStackAddendumByWorkInProgressFiber(reactTag)
diff --git a/Libraries/Renderer/shims/ReactNativeBridgeEventPlugin.js b/Libraries/Renderer/shims/ReactNativeBridgeEventPlugin.js
deleted file mode 100644
index 3170faedbad7..000000000000
--- a/Libraries/Renderer/shims/ReactNativeBridgeEventPlugin.js
+++ /dev/null
@@ -1,17 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule ReactNativeBridgeEventPlugin
- */
-
-'use strict';
-
-const {
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-} = require('ReactNative');
-
-module.exports =
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactNativeBridgeEventPlugin;
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index f20bb30faa79..fdee974ae88a 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -69,19 +69,9 @@ export type NativeMethodsMixinType = {
   setNativeProps(nativeProps: Object): void,
 };
 
-type ReactNativeBridgeEventPlugin = {
-  processEventTypes(viewConfig: ReactNativeBaseComponentViewConfig): void,
-};
-
 type SecretInternalsType = {
   NativeMethodsMixin: NativeMethodsMixinType,
-  createReactNativeComponentClass(
-    name: string,
-    callback: ViewConfigGetter,
-  ): any,
-  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin,
   ReactNativeComponentTree: any,
-  ReactNativePropRegistry: any,
   // TODO (bvaughn) Decide which additional types to expose here?
   // And how much information to fill in for the above types.
 };
@@ -104,3 +94,16 @@ export type ReactNativeType = {
 
   __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: SecretInternalsType,
 };
+
+export type ReactFabricType = {
+  NativeComponent: any,
+  findNodeHandle(componentOrHandle: any): ?number,
+  render(
+    element: React$Element<any>,
+    containerTag: any,
+    callback: ?Function,
+  ): any,
+  unmountComponentAtNode(containerTag: number): any,
+
+  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: SecretInternalsType,
+};
diff --git a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
new file mode 100644
index 000000000000..ffb0fa213f3b
--- /dev/null
+++ b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
@@ -0,0 +1,106 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @providesModule ReactNativeViewConfigRegistry
+ * @flow
+ */
+'use strict';
+
+import type {
+  ReactNativeBaseComponentViewConfig,
+  ViewConfigGetter,
+} from './ReactNativeTypes';
+
+const invariant = require('fbjs/lib/invariant');
+
+// Event configs
+const customBubblingEventTypes = {};
+const customDirectEventTypes = {};
+const eventTypes = {};
+
+exports.customBubblingEventTypes = customBubblingEventTypes;
+exports.customDirectEventTypes = customDirectEventTypes;
+exports.eventTypes = eventTypes;
+
+const viewConfigCallbacks = new Map();
+const viewConfigs = new Map();
+
+function processEventTypes(
+  viewConfig: ReactNativeBaseComponentViewConfig,
+): void {
+  const {bubblingEventTypes, directEventTypes} = viewConfig;
+
+  if (__DEV__) {
+    if (bubblingEventTypes != null && directEventTypes != null) {
+      for (const topLevelType in directEventTypes) {
+        invariant(
+          bubblingEventTypes[topLevelType] == null,
+          'Event cannot be both direct and bubbling: %s',
+          topLevelType,
+        );
+      }
+    }
+  }
+
+  if (bubblingEventTypes != null) {
+    for (const topLevelType in bubblingEventTypes) {
+      if (customBubblingEventTypes[topLevelType] == null) {
+        eventTypes[topLevelType] = customBubblingEventTypes[topLevelType] =
+          bubblingEventTypes[topLevelType];
+      }
+    }
+  }
+
+  if (directEventTypes != null) {
+    for (const topLevelType in directEventTypes) {
+      if (customDirectEventTypes[topLevelType] == null) {
+        eventTypes[topLevelType] = customDirectEventTypes[topLevelType] =
+          directEventTypes[topLevelType];
+      }
+    }
+  }
+}
+
+/**
+ * Registers a native view/component by name.
+ * A callback is provided to load the view config from UIManager.
+ * The callback is deferred until the view is actually rendered.
+ * This is done to avoid causing Prepack deopts.
+ */
+exports.register = function(name: string, callback: ViewConfigGetter): string {
+  invariant(
+    !viewConfigCallbacks.has(name),
+    'Tried to register two views with the same name %s',
+    name,
+  );
+  viewConfigCallbacks.set(name, callback);
+  return name;
+};
+
+/**
+ * Retrieves a config for the specified view.
+ * If this is the first time the view has been used,
+ * This configuration will be lazy-loaded from UIManager.
+ */
+exports.get = function(name: string): ReactNativeBaseComponentViewConfig {
+  let viewConfig;
+  if (!viewConfigs.has(name)) {
+    const callback = viewConfigCallbacks.get(name);
+    invariant(
+      typeof callback === 'function',
+      'View config not found for name %s',
+      name,
+    );
+    viewConfigCallbacks.set(name, null);
+    viewConfig = callback();
+    processEventTypes(viewConfig);
+    viewConfigs.set(name, viewConfig);
+  } else {
+    viewConfig = viewConfigs.get(name);
+  }
+  invariant(viewConfig, 'View config not found for name %s', name);
+  return viewConfig;
+};
diff --git a/Libraries/Renderer/shims/createReactNativeComponentClass.js b/Libraries/Renderer/shims/createReactNativeComponentClass.js
index d5d2b8c59009..1a050e8b3cf0 100644
--- a/Libraries/Renderer/shims/createReactNativeComponentClass.js
+++ b/Libraries/Renderer/shims/createReactNativeComponentClass.js
@@ -10,9 +10,23 @@
 
 'use strict';
 
-const {
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-} = require('ReactNative');
+import type {ViewConfigGetter} from './ReactNativeTypes';
 
-module.exports =
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.createReactNativeComponentClass;
+const {register} = require('ReactNativeViewConfigRegistry');
+
+/**
+ * Creates a renderable ReactNative host component.
+ * Use this method for view configs that are loaded from UIManager.
+ * Use createReactNativeComponentClass() for view configs defined within JavaScript.
+ *
+ * @param {string} config iOS View configuration.
+ * @private
+ */
+const createReactNativeComponentClass = function(
+  name: string,
+  callback: ViewConfigGetter,
+): string {
+  return register(name, callback);
+};
+
+module.exports = createReactNativeComponentClass;
diff --git a/Libraries/Text/FabricText.js b/Libraries/Text/FabricText.js
index 1eedd8b181c8..2b6748749b7e 100644
--- a/Libraries/Text/FabricText.js
+++ b/Libraries/Text/FabricText.js
@@ -10,233 +10,4 @@
  */
 'use strict';
 
-const React = require('React');
-const ReactNative = require('ReactNative');
-const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
-const TextPropTypes = require('TextPropTypes');
-const Touchable = require('Touchable');
-const UIManager = require('UIManager');
-
-const {createReactNativeComponentClass} = require('ReactFabricInternals');
-const mergeFast = require('mergeFast');
-const processColor = require('processColor');
-const {ViewContextTypes} = require('ViewContext');
-
-import type {PressEvent} from 'CoreEventTypes';
-import type {TextProps} from 'TextProps';
-import type {ViewChildContext} from 'ViewContext';
-
-type State = {
-  isHighlighted: boolean,
-};
-
-type RectOffset = {
-  top: number,
-  left: number,
-  right: number,
-  bottom: number,
-};
-
-const PRESS_RECT_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
-
-const viewConfig = {
-  validAttributes: mergeFast(ReactNativeViewAttributes.UIView, {
-    isHighlighted: true,
-    numberOfLines: true,
-    ellipsizeMode: true,
-    allowFontScaling: true,
-    disabled: true,
-    selectable: true,
-    selectionColor: true,
-    adjustsFontSizeToFit: true,
-    minimumFontScale: true,
-    textBreakStrategy: true,
-  }),
-  uiViewClassName: 'RCTText',
-};
-
-/**
- * A React component for displaying text.
- *
- * See https://facebook.github.io/react-native/docs/text.html
- */
-class Text extends ReactNative.NativeComponent<TextProps, State> {
-  static propTypes = TextPropTypes;
-  static childContextTypes = ViewContextTypes;
-  static contextTypes = ViewContextTypes;
-
-  static defaultProps = {
-    accessible: true,
-    allowFontScaling: true,
-    ellipsizeMode: 'tail',
-  };
-
-  state = mergeFast(Touchable.Mixin.touchableGetInitialState(), {
-    isHighlighted: false,
-  });
-
-  viewConfig = viewConfig;
-
-  getChildContext(): ViewChildContext {
-    return {
-      isInAParentText: true,
-    };
-  }
-
-  _handlers: ?Object;
-
-  _hasPressHandler(): boolean {
-    return !!this.props.onPress || !!this.props.onLongPress;
-  }
-  /**
-   * These are assigned lazily the first time the responder is set to make plain
-   * text nodes as cheap as possible.
-   */
-  touchableHandleActivePressIn: ?Function;
-  touchableHandleActivePressOut: ?Function;
-  touchableHandlePress: ?Function;
-  touchableHandleLongPress: ?Function;
-  touchableHandleResponderGrant: ?Function;
-  touchableHandleResponderMove: ?Function;
-  touchableHandleResponderRelease: ?Function;
-  touchableHandleResponderTerminate: ?Function;
-  touchableHandleResponderTerminationRequest: ?Function;
-  touchableGetPressRectOffset: ?Function;
-
-  render(): React.Element<any> {
-    let newProps = this.props;
-    if (this.props.onStartShouldSetResponder || this._hasPressHandler()) {
-      if (!this._handlers) {
-        this._handlers = {
-          onStartShouldSetResponder: (): boolean => {
-            const shouldSetFromProps =
-              this.props.onStartShouldSetResponder &&
-              this.props.onStartShouldSetResponder();
-            const setResponder = shouldSetFromProps || this._hasPressHandler();
-            if (setResponder && !this.touchableHandleActivePressIn) {
-              // Attach and bind all the other handlers only the first time a touch
-              // actually happens.
-              for (const key in Touchable.Mixin) {
-                if (typeof Touchable.Mixin[key] === 'function') {
-                  (this: any)[key] = Touchable.Mixin[key].bind(this);
-                }
-              }
-              this.touchableHandleActivePressIn = () => {
-                if (
-                  this.props.suppressHighlighting ||
-                  !this._hasPressHandler()
-                ) {
-                  return;
-                }
-                this.setState({
-                  isHighlighted: true,
-                });
-              };
-
-              this.touchableHandleActivePressOut = () => {
-                if (
-                  this.props.suppressHighlighting ||
-                  !this._hasPressHandler()
-                ) {
-                  return;
-                }
-                this.setState({
-                  isHighlighted: false,
-                });
-              };
-
-              this.touchableHandlePress = (e: PressEvent) => {
-                this.props.onPress && this.props.onPress(e);
-              };
-
-              this.touchableHandleLongPress = (e: PressEvent) => {
-                this.props.onLongPress && this.props.onLongPress(e);
-              };
-
-              this.touchableGetPressRectOffset = function(): RectOffset {
-                return this.props.pressRetentionOffset || PRESS_RECT_OFFSET;
-              };
-            }
-            return setResponder;
-          },
-          onResponderGrant: function(e: SyntheticEvent<>, dispatchID: string) {
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            this.touchableHandleResponderGrant(e, dispatchID);
-            this.props.onResponderGrant &&
-              this.props.onResponderGrant.apply(this, arguments);
-          }.bind(this),
-          onResponderMove: function(e: SyntheticEvent<>) {
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            this.touchableHandleResponderMove(e);
-            this.props.onResponderMove &&
-              this.props.onResponderMove.apply(this, arguments);
-          }.bind(this),
-          onResponderRelease: function(e: SyntheticEvent<>) {
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            this.touchableHandleResponderRelease(e);
-            this.props.onResponderRelease &&
-              this.props.onResponderRelease.apply(this, arguments);
-          }.bind(this),
-          onResponderTerminate: function(e: SyntheticEvent<>) {
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            this.touchableHandleResponderTerminate(e);
-            this.props.onResponderTerminate &&
-              this.props.onResponderTerminate.apply(this, arguments);
-          }.bind(this),
-          onResponderTerminationRequest: function(): boolean {
-            // Allow touchable or props.onResponderTerminationRequest to deny
-            // the request
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            var allowTermination = this.touchableHandleResponderTerminationRequest();
-            if (allowTermination && this.props.onResponderTerminationRequest) {
-              allowTermination = this.props.onResponderTerminationRequest.apply(
-                this,
-                arguments,
-              );
-            }
-            return allowTermination;
-          }.bind(this),
-        };
-      }
-      newProps = {
-        ...this.props,
-        ...this._handlers,
-        isHighlighted: this.state.isHighlighted,
-      };
-    }
-    if (newProps.selectionColor != null) {
-      newProps = {
-        ...newProps,
-        selectionColor: processColor(newProps.selectionColor),
-      };
-    }
-    if (Touchable.TOUCH_TARGET_DEBUG && newProps.onPress) {
-      newProps = {
-        ...newProps,
-        style: [this.props.style, {color: 'magenta'}],
-      };
-    }
-    if (this.context.isInAParentText) {
-      return <RCTVirtualText {...newProps} />;
-    } else {
-      return <RCTText {...newProps} />;
-    }
-  }
-}
-
-var RCTText = createReactNativeComponentClass(
-  viewConfig.uiViewClassName,
-  () => viewConfig,
-);
-var RCTVirtualText = RCTText;
-
-if (UIManager.RCTVirtualText) {
-  RCTVirtualText = createReactNativeComponentClass('RCTVirtualText', () => ({
-    validAttributes: mergeFast(ReactNativeViewAttributes.UIView, {
-      isHighlighted: true,
-    }),
-    uiViewClassName: 'RCTVirtualText',
-  }));
-}
-
-module.exports = Text;
+module.exports = require('Text');

From 87539c34dbe1ba359d4f42caf612380a930498ff Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:36:43 -0700
Subject: [PATCH 0263/1109] Fabric: RCTComponentViewProtocol

Summary: RCTComponentViewProtocol is a protocol for all UIView instances which are managed by React/MountingManager.

Reviewed By: mdvacca

Differential Revision: D7507520

fbshipit-source-id: dcbed8c5d0cc97f72942508aeccb445833ade271
---
 .../Mounting/RCTComponentViewProtocol.h       | 64 +++++++++++++++++++
 React/Fabric/RCTPrimitives.h                  | 10 +++
 2 files changed, 74 insertions(+)
 create mode 100644 React/Fabric/Mounting/RCTComponentViewProtocol.h
 create mode 100644 React/Fabric/RCTPrimitives.h

diff --git a/React/Fabric/Mounting/RCTComponentViewProtocol.h b/React/Fabric/Mounting/RCTComponentViewProtocol.h
new file mode 100644
index 000000000000..d23ac72adfef
--- /dev/null
+++ b/React/Fabric/Mounting/RCTComponentViewProtocol.h
@@ -0,0 +1,64 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <fabric/core/Props.h>
+#import <fabric/core/LayoutMetrics.h>
+#import <React/RCTPrimitives.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Represents a `UIView` instance managed by React.
+ * All methods are non-@optional.
+ * `UIView+ComponentViewProtocol` category provides default implementation
+ * for all of them.
+ */
+@protocol RCTComponentViewProtocol <NSObject>
+
+/*
+ * Called for mounting (attaching) a child component view inside `self`
+ * component view.
+ * Receiver must add `childComponentView` as a subview.
+ */
+- (void)mountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
+                          index:(NSInteger)index;
+
+/*
+ * Called for unmounting (detaching) a child component view from `self`
+ * component view.
+ * Receiver must remove `childComponentView` as a subview.
+ */
+- (void)unmountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
+                            index:(NSInteger)index;
+
+/*
+ * Called for updating component's props.
+ * Receiver must update native view props accordingly changed props.
+ */
+- (void)updateProps:(facebook::react::SharedProps)props
+           oldProps:(facebook::react::SharedProps)oldProps;
+
+/*
+ * Called for updating component's layout metrics.
+ * Receiver must update `UIView` layout-related fields (such as `frame`,
+ * `bounds`, `layer.zPosition`, and so on) accordingly.
+ */
+- (void)updateLayoutMetrics:(facebook::react::LayoutMetrics)layoutMetrics
+           oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics;
+
+/*
+ * Called right after the component view is moved to a recycle pool.
+ * Receiver must reset any local state and release associated
+ * non-reusable resources.
+ */
+- (void)prepareForRecycle;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/RCTPrimitives.h b/React/Fabric/RCTPrimitives.h
new file mode 100644
index 000000000000..7712dabc9f1e
--- /dev/null
+++ b/React/Fabric/RCTPrimitives.h
@@ -0,0 +1,10 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <Foundation/Foundation.h>
+
+typedef NSInteger ReactTag;

From dfb8fd26e64b66ca9731f7f37b6d5082d6df4035 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:36:45 -0700
Subject: [PATCH 0264/1109] Fabric: Default implementation of
 RCTComponentViewProtocol

Summary:
All methods of RCTComponentViewProtocol are non-optional,
but this default implementation removes necessity to implement all of them manually.

Reviewed By: mdvacca

Differential Revision: D7507522

fbshipit-source-id: e4dff97e8bf64e79d2f1ffca94f0549bd4b5e2fa
---
 .../Mounting/UIView+ComponentViewProtocol.h   | 35 ++++++++++++
 .../Mounting/UIView+ComponentViewProtocol.mm  | 57 +++++++++++++++++++
 2 files changed, 92 insertions(+)
 create mode 100644 React/Fabric/Mounting/UIView+ComponentViewProtocol.h
 create mode 100644 React/Fabric/Mounting/UIView+ComponentViewProtocol.mm

diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.h b/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
new file mode 100644
index 000000000000..b38b41ba5cfb
--- /dev/null
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
@@ -0,0 +1,35 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTComponentViewProtocol.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Default implementation of RCTComponentViewProtocol.
+ */
+@interface UIView (ComponentViewProtocol)
+
+- (void)mountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
+                          index:(NSInteger)index;
+
+- (void)unmountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
+                            index:(NSInteger)index;
+
+- (void)updateProps:(facebook::react::SharedProps)props
+           oldProps:(facebook::react::SharedProps)oldProps;
+
+- (void)updateLayoutMetrics:(facebook::react::LayoutMetrics)layoutMetrics
+           oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics;
+
+- (void)prepareForRecycle;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
new file mode 100644
index 000000000000..93b5784e3d92
--- /dev/null
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
@@ -0,0 +1,57 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "UIView+ComponentViewProtocol.h"
+
+#import <React/RCTAssert.h>
+
+@implementation UIView (ComponentViewProtocol)
+
+- (void)mountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
+                          index:(NSInteger)index
+{
+  [self insertSubview:childComponentView atIndex:index];
+}
+
+- (void)unmountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
+                            index:(NSInteger)index
+{
+  RCTAssert(childComponentView.superview == self, @"Attempt to unmount improperly mounted component view.");
+  [childComponentView removeFromSuperview];
+}
+
+- (void)updateProps:(facebook::react::SharedProps)props
+           oldProps:(facebook::react::SharedProps)oldProps
+{
+  // Default implementation does nothing.
+}
+
+- (void)updateLayoutMetrics:(facebook::react::LayoutMetrics)layoutMetrics
+           oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics
+{
+  if (layoutMetrics.frame != oldLayoutMetrics.frame) {
+    self.frame = {
+      .origin = {
+        .x = layoutMetrics.frame.origin.x,
+        .y = layoutMetrics.frame.origin.y
+      },
+      .size = {
+        .width = layoutMetrics.frame.size.width,
+        .height = layoutMetrics.frame.size.height
+      }
+    };
+  }
+
+  // TODO: Apply another layout metrics here.
+}
+
+- (void)prepareForRecycle
+{
+  // Default implementation does nothing.
+}
+
+@end

From 11833714d9a98b3963e28f025b4fafb03497b0d1 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:36:47 -0700
Subject: [PATCH 0265/1109] Fabric: RCTMountItemProtocol and five base mount
 items

Summary:
MountItem is a small granular light-weight instruction describing a change in the component view tree.
All instruction are supposed to be small and standard. All additional logic must be implemented in component view subclasses.
No more opaque and untyped objcblocks.
All that allows mounting manager to control and optimize an execution of those items (eventually).

Besides that five we probably will need `perform imperative instruction` (for execution something like `scrollTo`) and `update local data` (for updating local state of something like text input).

Reviewed By: mdvacca

Differential Revision: D7507518

fbshipit-source-id: 745b93125231a02cbc152cfa6c6baf423d100f81
---
 .../Mounting/MountItems/RCTCreateMountItem.h  | 27 ++++++++++++
 .../Mounting/MountItems/RCTCreateMountItem.mm | 33 +++++++++++++++
 .../Mounting/MountItems/RCTDeleteMountItem.h  | 25 +++++++++++
 .../Mounting/MountItems/RCTDeleteMountItem.mm | 34 +++++++++++++++
 .../Mounting/MountItems/RCTInsertMountItem.h  | 28 +++++++++++++
 .../Mounting/MountItems/RCTInsertMountItem.mm | 40 ++++++++++++++++++
 .../MountItems/RCTMountItemProtocol.h         | 23 +++++++++++
 .../Mounting/MountItems/RCTRemoveMountItem.h  | 26 ++++++++++++
 .../Mounting/MountItems/RCTRemoveMountItem.mm | 40 ++++++++++++++++++
 .../RCTUpdateLayoutMetricsMountItem.h         | 27 ++++++++++++
 .../RCTUpdateLayoutMetricsMountItem.mm        | 41 +++++++++++++++++++
 .../MountItems/RCTUpdatePropsMountItem.h      | 27 ++++++++++++
 .../MountItems/RCTUpdatePropsMountItem.mm     | 39 ++++++++++++++++++
 13 files changed, 410 insertions(+)
 create mode 100644 React/Fabric/Mounting/MountItems/RCTCreateMountItem.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTCreateMountItem.mm
 create mode 100644 React/Fabric/Mounting/MountItems/RCTDeleteMountItem.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm
 create mode 100644 React/Fabric/Mounting/MountItems/RCTInsertMountItem.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm
 create mode 100644 React/Fabric/Mounting/MountItems/RCTMountItemProtocol.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTRemoveMountItem.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm
 create mode 100644 React/Fabric/Mounting/MountItems/RCTUpdateLayoutMetricsMountItem.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTUpdateLayoutMetricsMountItem.mm
 create mode 100644 React/Fabric/Mounting/MountItems/RCTUpdatePropsMountItem.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTUpdatePropsMountItem.mm

diff --git a/React/Fabric/Mounting/MountItems/RCTCreateMountItem.h b/React/Fabric/Mounting/MountItems/RCTCreateMountItem.h
new file mode 100644
index 000000000000..6376094894d2
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTCreateMountItem.h
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTMountItemProtocol.h>
+#import <React/RCTPrimitives.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTComponentViewRegistry;
+
+/**
+ * Creates a ready-to-mount component view.
+ */
+@interface RCTCreateMountItem : NSObject <RCTMountItemProtocol>
+
+- (instancetype)initWithComponentName:(NSString *)componentName
+                                  tag:(ReactTag)tag;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTCreateMountItem.mm b/React/Fabric/Mounting/MountItems/RCTCreateMountItem.mm
new file mode 100644
index 000000000000..df04396b4760
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTCreateMountItem.mm
@@ -0,0 +1,33 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTCreateMountItem.h"
+
+#import "RCTComponentViewRegistry.h"
+
+@implementation RCTCreateMountItem {
+  NSString *_componentName;
+  ReactTag _tag;
+}
+
+- (instancetype)initWithComponentName:(NSString *)componentName
+                                  tag:(ReactTag)tag
+{
+  if (self = [super init]) {
+    _componentName = componentName;
+    _tag = tag;
+  }
+
+  return self;
+}
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
+{
+  [registry dequeueComponentViewWithName:_componentName tag:_tag];
+}
+
+@end
diff --git a/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.h b/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.h
new file mode 100644
index 000000000000..a4c6077b56f3
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.h
@@ -0,0 +1,25 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTMountItemProtocol.h>
+#import <React/RCTPrimitives.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Deletes (returns to recycle pool) a component view.
+ */
+@interface RCTDeleteMountItem : NSObject <RCTMountItemProtocol>
+
+- (instancetype)initWithComponentName:(NSString *)componentName
+                                  tag:(ReactTag)tag;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm b/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm
new file mode 100644
index 000000000000..99909f450cc2
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm
@@ -0,0 +1,34 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTDeleteMountItem.h"
+
+#import "RCTComponentViewRegistry.h"
+
+@implementation RCTDeleteMountItem {
+  NSString *_componentName;
+  ReactTag _tag;
+}
+
+- (instancetype)initWithComponentName:(NSString *)componentName
+                                  tag:(ReactTag)tag
+{
+  if (self = [super init]) {
+    _componentName = componentName;
+    _tag = tag;
+  }
+
+  return self;
+}
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
+{
+  UIView<RCTComponentViewProtocol> *componentView = [registry componentViewByTag:_tag];
+  [registry enqueueComponentViewWithName:_componentName tag:_tag componentView:componentView];
+}
+
+@end
diff --git a/React/Fabric/Mounting/MountItems/RCTInsertMountItem.h b/React/Fabric/Mounting/MountItems/RCTInsertMountItem.h
new file mode 100644
index 000000000000..e3d4ac29d7aa
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTInsertMountItem.h
@@ -0,0 +1,28 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTMountItemProtocol.h>
+#import <React/RCTPrimitives.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTComponentViewRegistry;
+
+/**
+ * Inserts a component view into another component view.
+ */
+@interface RCTInsertMountItem : NSObject <RCTMountItemProtocol>
+
+- (instancetype)initWithChildTag:(ReactTag)childTag
+                       parentTag:(ReactTag)parentTag
+                           index:(NSInteger)index;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm b/React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm
new file mode 100644
index 000000000000..f714cb0a70db
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm
@@ -0,0 +1,40 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTInsertMountItem.h"
+
+#import "RCTComponentViewRegistry.h"
+
+@implementation RCTInsertMountItem {
+  ReactTag _childTag;
+  ReactTag _parentTag;
+  NSInteger _index;
+}
+
+- (instancetype)initWithChildTag:(ReactTag)childTag
+                       parentTag:(ReactTag)parentTag
+                           index:(NSInteger)index
+{
+  if (self = [super init]) {
+    _childTag = childTag;
+    _parentTag = parentTag;
+    _index = index;
+  }
+
+  return self;
+}
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
+{
+  UIView<RCTComponentViewProtocol> *childComponentView = [registry componentViewByTag:_childTag];
+  UIView<RCTComponentViewProtocol> *parentComponentView = [registry componentViewByTag:_parentTag];
+
+  [parentComponentView mountChildComponentView:childComponentView
+                                         index:_index];
+}
+
+@end
diff --git a/React/Fabric/Mounting/MountItems/RCTMountItemProtocol.h b/React/Fabric/Mounting/MountItems/RCTMountItemProtocol.h
new file mode 100644
index 000000000000..f46c397498b4
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTMountItemProtocol.h
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTComponentViewRegistry;
+
+/**
+ * Granular representation of any change in a user interface.
+ */
+@protocol RCTMountItemProtocol <NSObject>
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.h b/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.h
new file mode 100644
index 000000000000..0fe9555a613e
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.h
@@ -0,0 +1,26 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTMountItemProtocol.h>
+#import <React/RCTPrimitives.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Removes a component view from another component view.
+ */
+@interface RCTRemoveMountItem : NSObject <RCTMountItemProtocol>
+
+- (instancetype)initWithChildTag:(ReactTag)childTag
+                       parentTag:(ReactTag)parentTag
+                           index:(NSInteger)index;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm b/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm
new file mode 100644
index 000000000000..d46b936dd044
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm
@@ -0,0 +1,40 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTRemoveMountItem.h"
+
+#import "RCTComponentViewRegistry.h"
+
+@implementation RCTRemoveMountItem {
+  ReactTag _childTag;
+  ReactTag _parentTag;
+  NSInteger _index;
+}
+
+- (instancetype)initWithChildTag:(ReactTag)childTag
+                       parentTag:(ReactTag)parentTag
+                           index:(NSInteger)index
+{
+  if (self = [super init]) {
+    _childTag = childTag;
+    _parentTag = parentTag;
+    _index = index;
+  }
+
+  return self;
+}
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
+{
+  UIView<RCTComponentViewProtocol> *childComponentView = [registry componentViewByTag:_childTag];
+  UIView<RCTComponentViewProtocol> *parentComponentView = [registry componentViewByTag:_parentTag];
+
+  [parentComponentView unmountChildComponentView:childComponentView
+                                           index:_index];
+}
+
+@end
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateLayoutMetricsMountItem.h b/React/Fabric/Mounting/MountItems/RCTUpdateLayoutMetricsMountItem.h
new file mode 100644
index 000000000000..378c179d3c46
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateLayoutMetricsMountItem.h
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTMountItemProtocol.h>
+#import <React/RCTPrimitives.h>
+#import <fabric/core/LayoutMetrics.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Updates layout metrics of a component view.
+ */
+@interface RCTUpdateLayoutMetricsMountItem : NSObject <RCTMountItemProtocol>
+
+- (instancetype)initWithTag:(ReactTag)tag
+           oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics
+           newLayoutMetrics:(facebook::react::LayoutMetrics)newLayoutMetrics;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateLayoutMetricsMountItem.mm b/React/Fabric/Mounting/MountItems/RCTUpdateLayoutMetricsMountItem.mm
new file mode 100644
index 000000000000..c61a043626a6
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateLayoutMetricsMountItem.mm
@@ -0,0 +1,41 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTUpdateLayoutMetricsMountItem.h"
+
+#import "RCTComponentViewRegistry.h"
+
+using namespace facebook::react;
+
+@implementation RCTUpdateLayoutMetricsMountItem {
+  ReactTag _tag;
+  LayoutMetrics _oldLayoutMetrics;
+  LayoutMetrics _newLayoutMetrics;
+}
+
+- (instancetype)initWithTag:(ReactTag)tag
+           oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics
+           newLayoutMetrics:(facebook::react::LayoutMetrics)newLayoutMetrics
+{
+  if (self = [super init]) {
+    _tag = tag;
+    _oldLayoutMetrics = oldLayoutMetrics;
+    _newLayoutMetrics = newLayoutMetrics;
+  }
+
+  return self;
+}
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
+{
+  UIView<RCTComponentViewProtocol> *componentView = [registry componentViewByTag:_tag];
+
+  [componentView updateLayoutMetrics:_newLayoutMetrics
+                    oldLayoutMetrics:_oldLayoutMetrics];
+}
+
+@end
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdatePropsMountItem.h b/React/Fabric/Mounting/MountItems/RCTUpdatePropsMountItem.h
new file mode 100644
index 000000000000..efdfed64ddbf
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTUpdatePropsMountItem.h
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTMountItemProtocol.h>
+#import <React/RCTPrimitives.h>
+#import <fabric/core/Props.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Updates props of a component view.
+ */
+@interface RCTUpdatePropsMountItem : NSObject <RCTMountItemProtocol>
+
+- (instancetype)initWithTag:(ReactTag)tag
+                   oldProps:(facebook::react::SharedProps)oldProps
+                   newProps:(facebook::react::SharedProps)newProps;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdatePropsMountItem.mm b/React/Fabric/Mounting/MountItems/RCTUpdatePropsMountItem.mm
new file mode 100644
index 000000000000..694b72e4046a
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTUpdatePropsMountItem.mm
@@ -0,0 +1,39 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTUpdatePropsMountItem.h"
+
+#import "RCTComponentViewRegistry.h"
+
+using namespace facebook::react;
+
+@implementation RCTUpdatePropsMountItem {
+  ReactTag _tag;
+  SharedProps _oldProps;
+  SharedProps _newProps;
+}
+
+- (instancetype)initWithTag:(ReactTag)tag
+                   oldProps:(SharedProps)oldProps
+                   newProps:(SharedProps)newProps
+{
+  if (self = [super init]) {
+    _tag = tag;
+    _oldProps = oldProps;
+    _newProps = newProps;
+  }
+
+  return self;
+}
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
+{
+  UIView<RCTComponentViewProtocol> *componentView = [registry componentViewByTag:_tag];
+  [componentView updateProps:_newProps oldProps:_oldProps];
+}
+
+@end

From 6c406ffe3873db931022d6674a12f4d294fcf5e0 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:36:50 -0700
Subject: [PATCH 0266/1109] Fabric: RCTComponentViewRegistry

Summary:
A registry for components. The registry allows to refer to component view instance by react tag.
It also has recycle-pool-like interface (and eventually the pool will be implemented).

Reviewed By: mdvacca

Differential Revision: D7507519

fbshipit-source-id: ed74203fb4d0694490b0dc23aae0aa067b3fc55b
---
 .../Mounting/RCTComponentViewRegistry.h       | 48 +++++++++++++++
 .../Mounting/RCTComponentViewRegistry.mm      | 59 +++++++++++++++++++
 2 files changed, 107 insertions(+)
 create mode 100644 React/Fabric/Mounting/RCTComponentViewRegistry.h
 create mode 100644 React/Fabric/Mounting/RCTComponentViewRegistry.mm

diff --git a/React/Fabric/Mounting/RCTComponentViewRegistry.h b/React/Fabric/Mounting/RCTComponentViewRegistry.h
new file mode 100644
index 000000000000..1e747b124da1
--- /dev/null
+++ b/React/Fabric/Mounting/RCTComponentViewRegistry.h
@@ -0,0 +1,48 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTComponentViewProtocol.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Registry of native component views.
+ * Provides basic functionality for allocation, recycling, and querying (by tag) native view instances.
+ */
+@interface RCTComponentViewRegistry : NSObject
+
+/**
+ * Returns a native view instance from the recycle pool (or create)
+ * for given `componentName` and with given `tag`.
+ * #RefuseSingleUse
+ */
+- (UIView<RCTComponentViewProtocol> *)dequeueComponentViewWithName:(NSString *)componentName
+                                                               tag:(ReactTag)tag;
+
+/**
+ * Puts a given native component view to the recycle pool.
+ * #RefuseSingleUse
+ */
+- (void)enqueueComponentViewWithName:(NSString *)componentName
+                                 tag:(ReactTag)tag
+                       componentView:(UIView<RCTComponentViewProtocol> *)componentView;
+
+/**
+ * Returns a native component view by given `tag`.
+ */
+- (UIView<RCTComponentViewProtocol> *)componentViewByTag:(ReactTag)tag;
+
+/**
+ * Returns `tag` assosiated with given `componentView`.
+ */
+- (ReactTag)tagByComponentView:(UIView<RCTComponentViewProtocol> *)componentView;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/RCTComponentViewRegistry.mm b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
new file mode 100644
index 000000000000..c9d8224007e4
--- /dev/null
+++ b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
@@ -0,0 +1,59 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTComponentViewRegistry.h"
+
+#import <Foundation/NSMapTable.h>
+#import <React/RCTAssert.h>
+
+@implementation RCTComponentViewRegistry {
+  NSMapTable<id, UIView<RCTComponentViewProtocol> *> *_registry;
+}
+
+- (instancetype)init
+{
+  if (self = [super init]) {
+    _registry = [NSMapTable mapTableWithKeyOptions:NSPointerFunctionsIntegerPersonality | NSPointerFunctionsOpaqueMemory
+                                      valueOptions:NSPointerFunctionsObjectPersonality];
+  }
+
+  return self;
+}
+
+- (UIView<RCTComponentViewProtocol> *)dequeueComponentViewWithName:(NSString *)componentName
+                                                               tag:(ReactTag)tag
+{
+  RCTAssertMainQueue();
+  // This is temporary approach.
+  NSString *className = [NSString stringWithFormat:@"RCT%@ComponentView", componentName];
+  UIView<RCTComponentViewProtocol> *componentView = [[NSClassFromString(className) alloc] init];
+  componentView.tag = tag;
+  [_registry setObject:componentView forKey:(__bridge id)(void *)tag];
+  return componentView;
+}
+
+- (void)enqueueComponentViewWithName:(NSString *)componentName
+                                 tag:(ReactTag)tag
+                       componentView:(UIView<RCTComponentViewProtocol> *)componentView
+{
+  RCTAssertMainQueue();
+  [_registry removeObjectForKey:(__bridge id)(void *)tag];
+}
+
+- (UIView<RCTComponentViewProtocol> *)componentViewByTag:(ReactTag)tag
+{
+  RCTAssertMainQueue();
+  return [_registry objectForKey:(__bridge id)(void *)tag];
+}
+
+- (ReactTag)tagByComponentView:(UIView<RCTComponentViewProtocol> *)componentView
+{
+  RCTAssertMainQueue();
+  return componentView.tag;
+}
+
+@end

From 3093df675490c9b40801350a994e9479dc445350 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:36:54 -0700
Subject: [PATCH 0267/1109] Fabric: RCTMountingManager and
 RCTMountingManagerDelegate

Summary: RCTMountingManager manages mounting process transforming mutation instructions into mount items and executing them.

Reviewed By: mdvacca

Differential Revision: D7507521

fbshipit-source-id: 6e5acdbf0b7f8bedc7e1de141dc9086f35a376c9
---
 React/Fabric/Mounting/RCTMountingManager.h    |  35 ++++
 React/Fabric/Mounting/RCTMountingManager.mm   | 152 ++++++++++++++++++
 .../Mounting/RCTMountingManagerDelegate.h     |  37 +++++
 3 files changed, 224 insertions(+)
 create mode 100644 React/Fabric/Mounting/RCTMountingManager.h
 create mode 100644 React/Fabric/Mounting/RCTMountingManager.mm
 create mode 100644 React/Fabric/Mounting/RCTMountingManagerDelegate.h

diff --git a/React/Fabric/Mounting/RCTMountingManager.h b/React/Fabric/Mounting/RCTMountingManager.h
new file mode 100644
index 000000000000..bf66ac7f5757
--- /dev/null
+++ b/React/Fabric/Mounting/RCTMountingManager.h
@@ -0,0 +1,35 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <fabric/uimanager/TreeMutationInstruction.h>
+#import <React/RCTPrimitives.h>
+#import <React/RCTMountingManagerDelegate.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTComponentViewRegistry;
+
+/**
+ * Manages mounting process.
+ */
+@interface RCTMountingManager : NSObject
+
+@property (nonatomic, weak) id <RCTMountingManagerDelegate> delegate;
+@property (nonatomic, strong) RCTComponentViewRegistry *componentViewRegistry;
+
+/**
+ * Transfroms mutation insturctions to mount items and execute them.
+ * The order of mutation tnstructions matters.
+ */
+- (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions
+                                                rootTag:(ReactTag)rootTag;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/RCTMountingManager.mm b/React/Fabric/Mounting/RCTMountingManager.mm
new file mode 100644
index 000000000000..5f16ac2513dc
--- /dev/null
+++ b/React/Fabric/Mounting/RCTMountingManager.mm
@@ -0,0 +1,152 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTMountingManager.h"
+
+#import <fabric/core/LayoutableShadowNode.h>
+#import <React/RCTAssert.h>
+#import <React/RCTUtils.h>
+
+#import "RCTComponentViewProtocol.h"
+#import "RCTComponentViewRegistry.h"
+#import "RCTMountItemProtocol.h"
+
+#import "RCTCreateMountItem.h"
+#import "RCTDeleteMountItem.h"
+#import "RCTInsertMountItem.h"
+#import "RCTRemoveMountItem.h"
+#import "RCTUpdatePropsMountItem.h"
+#import "RCTUpdateLayoutMetricsMountItem.h"
+
+using namespace facebook::react;
+
+@implementation RCTMountingManager
+
+- (instancetype)init
+{
+  if (self = [super init]) {
+    _componentViewRegistry = [[RCTComponentViewRegistry alloc] init];
+  }
+
+  return self;
+}
+
+- (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions
+                                                rootTag:(ReactTag)rootTag
+{
+  NSMutableArray<RCTMountItemProtocol> *mountItems =
+    [[NSMutableArray<RCTMountItemProtocol> alloc] initWithCapacity:instructions.size() * 2 /* ~ the worst case */];
+
+  for (auto instruction : instructions) {
+    switch (instruction.getType()) {
+      case TreeMutationInstruction::Creation: {
+        NSString *componentName = [NSString stringWithCString:instruction.getNewChildNode()->getComponentName().c_str()
+                                                     encoding:NSASCIIStringEncoding];
+        RCTCreateMountItem *mountItem =
+          [[RCTCreateMountItem alloc] initWithComponentName:componentName
+                                                        tag:instruction.getNewChildNode()->getTag()];
+        [mountItems addObject:mountItem];
+        break;
+      }
+      case TreeMutationInstruction::Deletion: {
+        NSString *componentName = [NSString stringWithCString:instruction.getOldChildNode()->getComponentName().c_str()
+                                                     encoding:NSASCIIStringEncoding];
+        RCTDeleteMountItem *mountItem =
+          [[RCTDeleteMountItem alloc] initWithComponentName:componentName
+                                                        tag:instruction.getOldChildNode()->getTag()];
+        [mountItems addObject:mountItem];
+        break;
+      }
+
+      case TreeMutationInstruction::Insertion: {
+        RCTInsertMountItem *mountItem =
+          [[RCTInsertMountItem alloc] initWithChildTag:instruction.getNewChildNode()->getTag()
+                                             parentTag:instruction.getParentNode()->getTag()
+                                                 index:instruction.getIndex()];
+        [mountItems addObject:mountItem];
+
+        // Props
+        [mountItems addObject:[[RCTUpdatePropsMountItem alloc] initWithTag:instruction.getNewChildNode()->getTag()
+                                                                  oldProps:nullptr
+                                                                  newProps:instruction.getNewChildNode()->getProps()]];
+
+        // Layout
+        SharedLayoutableShadowNode layoutableNewShadowNode =
+          std::dynamic_pointer_cast<const LayoutableShadowNode>(instruction.getNewChildNode());
+
+        if (layoutableNewShadowNode) {
+          [mountItems addObject:[[RCTUpdateLayoutMetricsMountItem alloc] initWithTag:instruction.getNewChildNode()->getTag()
+                                                                    oldLayoutMetrics:{}
+                                                                    newLayoutMetrics:layoutableNewShadowNode->getLayoutMetrics()]];
+        }
+        break;
+      }
+
+      case TreeMutationInstruction::Removal: {
+        RCTRemoveMountItem *mountItem =
+          [[RCTRemoveMountItem alloc] initWithChildTag:instruction.getOldChildNode()->getTag()
+                                             parentTag:instruction.getParentNode()->getTag()
+                                                 index:instruction.getIndex()];
+        [mountItems addObject:mountItem];
+        break;
+      }
+
+      case TreeMutationInstruction::Replacement: {
+        SharedShadowNode oldShadowNode = instruction.getOldChildNode();
+        SharedShadowNode newShadowNode = instruction.getNewChildNode();
+
+        // Props
+        if (oldShadowNode->getProps() != newShadowNode->getProps()) {
+          RCTUpdatePropsMountItem *mountItem =
+            [[RCTUpdatePropsMountItem alloc] initWithTag:instruction.getOldChildNode()->getTag()
+                                                oldProps:instruction.getOldChildNode()->getProps()
+                                                newProps:instruction.getNewChildNode()->getProps()];
+          [mountItems addObject:mountItem];
+        }
+
+        // Layout
+        SharedLayoutableShadowNode layoutableOldShadowNode =
+          std::dynamic_pointer_cast<const LayoutableShadowNode>(oldShadowNode);
+
+        if (layoutableOldShadowNode) {
+          SharedLayoutableShadowNode layoutableNewShadowNode =
+            std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode);
+
+          if (layoutableOldShadowNode->getLayoutMetrics() != layoutableNewShadowNode->getLayoutMetrics()) {
+            RCTUpdateLayoutMetricsMountItem *mountItem =
+              [[RCTUpdateLayoutMetricsMountItem alloc] initWithTag:instruction.getOldChildNode()->getTag()
+                                                  oldLayoutMetrics:layoutableOldShadowNode->getLayoutMetrics()
+                                                  newLayoutMetrics:layoutableNewShadowNode->getLayoutMetrics()];
+            [mountItems addObject:mountItem];
+          }
+        }
+
+        break;
+      }
+    }
+  }
+
+  RCTExecuteOnMainQueue(^{
+    [self _performMountItems:mountItems rootTag:rootTag];
+  });
+}
+
+- (void)_performMountItems:(NSArray<RCTMountItemProtocol> *)mountItems
+                   rootTag:(ReactTag)rootTag
+{
+  RCTAssertMainQueue();
+
+  [self.delegate mountingManager:self willMountComponentsWithRootTag:rootTag];
+
+  for (id<RCTMountItemProtocol> mountItem in mountItems) {
+    [mountItem executeWithRegistry:_componentViewRegistry];
+  }
+
+  [self.delegate mountingManager:self didMountComponentsWithRootTag:rootTag];
+}
+
+@end
diff --git a/React/Fabric/Mounting/RCTMountingManagerDelegate.h b/React/Fabric/Mounting/RCTMountingManagerDelegate.h
new file mode 100644
index 000000000000..90ef6cecfa6a
--- /dev/null
+++ b/React/Fabric/Mounting/RCTMountingManagerDelegate.h
@@ -0,0 +1,37 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTPrimitives.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTMountingManager;
+
+/**
+ * MountingManager's delegate.
+ */
+@protocol RCTMountingManagerDelegate <NSObject>
+
+/*
+ * Called right *before* execution of mount items which affect a Surface with
+ * given `rootTag`.
+ * Always called on the main queue.
+ */
+- (void)mountingManager:(RCTMountingManager *)mountingManager willMountComponentsWithRootTag:(ReactTag)MountingManager;
+
+/*
+ * Called right *after* execution of mount items which affect a Surface with
+ * given `rootTag`.
+ * Always called on the main queue.
+ */
+- (void)mountingManager:(RCTMountingManager *)mountingManager didMountComponentsWithRootTag:(ReactTag)rootTag;
+
+@end
+
+NS_ASSUME_NONNULL_END

From 05f41931e22fd6fe849876646802c07f4cbd1b69 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:36:56 -0700
Subject: [PATCH 0268/1109] Fabric: Fixed
 YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector

Summary:
YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector recently was disabled because of change in Yoga (D7339832).
This diff brings is back.

Reviewed By: mdvacca

Differential Revision: D7526417

fbshipit-source-id: 5369d641bf1e118132cf742d2d243bf426c0ffdb
---
 .../fabric/view/yoga/YogaLayoutableShadowNode.cpp     | 11 ++++-------
 .../fabric/view/yoga/YogaLayoutableShadowNode.h       |  2 +-
 2 files changed, 5 insertions(+), 8 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index e2aa05f843a1..62c803b2f0c1 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -23,9 +23,8 @@ SharedYogaConfig YogaLayoutableShadowNode::suitableYogaConfig() {
   static SharedYogaConfig sharedYogaConfig;
 
   if (!sharedYogaConfig) {
-    sharedYogaConfig = std::make_shared<YGConfig>(YGConfig({
-      // .cloneNodeCallback = YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector
-    }));
+    sharedYogaConfig = std::shared_ptr<YGConfig>(YGConfigNew());
+    sharedYogaConfig->cloneNodeCallback = YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector;
   }
 
   return sharedYogaConfig;
@@ -169,7 +168,7 @@ SharedDebugStringConvertibleList YogaLayoutableShadowNode::getDebugProps() const
 
 #pragma mark - Yoga Connectors
 
-void YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *newYogaNode, YGNode *parentYogaNode, int childIndex) {
+YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex) {
   // We have only raw pointer to the parent shadow node, but that's enough for now.
   YogaLayoutableShadowNode *parentShadowNodeRawPtr = (YogaLayoutableShadowNode *)parentYogaNode->getContext();
   assert(parentShadowNodeRawPtr);
@@ -198,9 +197,7 @@ void YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYogaNod
     std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(parentShadowNodeRawPtr->cloneAndReplaceChild(oldShadowNode));
   assert(newShadowNode);
 
-  // And finally, we have to replace underline yoga node with the new one provided by Yoga.
-  newYogaNode->setContext((void *)newShadowNode.get());
-  newShadowNode->yogaNode_ = std::shared_ptr<YGNode>(newYogaNode);
+  return newShadowNode->yogaNode_.get();
 }
 
 void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children) {
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index e07acc8598cf..15f25cdf4043 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -85,7 +85,7 @@ class YogaLayoutableShadowNode:
 
   static SharedYogaConfig suitableYogaConfig();
   static void setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children);
-  static void yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *newYogaNode, YGNode *parentYogaNode, int childIndex);
+  static YGNode *yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex);
 };
 
 } // namespace react

From 00f44248b3c35c78ed4c0b67fbd8d91da8a86b41 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:36:59 -0700
Subject: [PATCH 0269/1109] Fabric: RCTFabricSurface as separate class

Summary: RCTFabricSurface was reimplemented as separate class which does not rely on (old) RCTUIManager and delegate some functionality (which must be coordinated between Surface instances and Scheduler) to RCTSurfacePresenter.

Reviewed By: mdvacca

Differential Revision: D7526404

fbshipit-source-id: e8c38261bc489fd6066ba29a829cd8f623c26217
---
 React/Fabric/Surface/RCTFabricSurface.h       | 119 +++++++-
 React/Fabric/Surface/RCTFabricSurface.mm      | 256 +++++++++++++++++-
 .../RCTFabricSurfaceHostingProxyRootView.mm   |   2 +-
 .../Surface/RCTFabricSurfaceHostingView.mm    |   6 +-
 4 files changed, 369 insertions(+), 14 deletions(-)

diff --git a/React/Fabric/Surface/RCTFabricSurface.h b/React/Fabric/Surface/RCTFabricSurface.h
index 1672a9a86ac6..498fe1807c89 100644
--- a/React/Fabric/Surface/RCTFabricSurface.h
+++ b/React/Fabric/Surface/RCTFabricSurface.h
@@ -5,12 +5,123 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#import <React/RCTSurface.h>
+#import <React/RCTSurfaceStage.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTBridge;
+@class RCTSurfaceView;
+@class RCTSurfacePresenter;
+@protocol RCTSurfaceDelegate;
+
+/**
+ * (This is Fabric-compatible RCTSurface implementation.)
+ *
+ * RCTSurface instance represents React Native-powered piece of a user interface
+ * which can be a full-screen app, separate modal view controller,
+ * or even small widget.
+ * It is called "Surface".
+ *
+ * The RCTSurface instance is completely thread-safe by design;
+ * it can be created on any thread, and any its method can be called from
+ * any thread (if the opposite is not mentioned explicitly).
+ *
+ * The primary goals of the RCTSurface are:
+ *  * ability to measure and layout the surface in a thread-safe
+ *    and synchronous manner;
+ *  * ability to create a UIView instance on demand (later);
+ *  * ability to communicate the current stage of the surface granularly.
+ */
+@interface RCTFabricSurface : NSObject
+
+@property (atomic, readonly) RCTSurfaceStage stage;
+@property (atomic, readonly) RCTBridge *bridge;
+@property (atomic, readonly) NSString *moduleName;
+@property (atomic, readonly) NSNumber *rootViewTag;
+
+@property (atomic, readwrite, weak, nullable) id<RCTSurfaceDelegate> delegate;
+
+@property (atomic, copy, readwrite) NSDictionary *properties;
+
+- (instancetype)initWithBridge:(RCTBridge *)bridge
+                    moduleName:(NSString *)moduleName
+             initialProperties:(NSDictionary *)initialProperties;
+
+- (instancetype)initWithSurfacePresenter:(RCTSurfacePresenter *)surfacePresenter
+                              moduleName:(NSString *)moduleName
+                       initialProperties:(NSDictionary *)initialProperties;
+
+#pragma mark - Dealing with UIView representation, the Main thread only access
 
 /**
- * Fabric-compatible RCTSurface implementation.
- * It may not continue extending from RCTSurface in the future.
+ * Creates (if needed) and returns `UIView` instance which represents the Surface.
+ * The Surface will cache and *retain* this object.
+ * Returning the UIView instance does not mean that the Surface is ready
+ * to execute and layout. It can be just a handler which Surface will use later
+ * to mount the actual views.
+ * RCTSurface does not control (or influence in any way) the size or origin
+ * of this view. Some superview (or another owner) must use other methods
+ * of this class to setup proper layout and interop interactions with UIKit
+ * or another UI framework.
+ * This method must be called only from the main queue.
  */
-@interface RCTFabricSurface : RCTSurface
+- (RCTSurfaceView *)view;
+
+#pragma mark - Layout: Setting the size constrains
+
+/**
+ * Sets `minimumSize` and `maximumSize` layout constraints for the Surface.
+ */
+- (void)setMinimumSize:(CGSize)minimumSize
+           maximumSize:(CGSize)maximumSize;
+
+/**
+ * Previously set `minimumSize` layout constraint.
+ * Defaults to `{0, 0}`.
+ */
+@property (atomic, assign, readonly) CGSize minimumSize;
+
+/**
+ * Previously set `maximumSize` layout constraint.
+ * Defaults to `{CGFLOAT_MAX, CGFLOAT_MAX}`.
+ */
+@property (atomic, assign, readonly) CGSize maximumSize;
+
+/**
+ * Simple shortcut to `-[RCTSurface setMinimumSize:size maximumSize:size]`.
+ */
+- (void)setSize:(CGSize)size;
+
+#pragma mark - Layout: Measuring
+
+/**
+ * Measures the Surface with given constraints.
+ * This method does not cause any side effects on the surface object.
+ */
+- (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize
+                      maximumSize:(CGSize)maximumSize;
+
+/**
+ * Return the current size of the root view based on (but not clamp by) current
+ * size constraints.
+ */
+@property (atomic, assign, readonly) CGSize intrinsicSize;
+
+#pragma mark - Synchronous waiting
+
+/**
+ * Synchronously blocks the current thread up to given `timeout` until
+ * the Surface reaches `stage`.
+ * NOT SUPPORTED IN FABRIC YET.
+ */
+- (BOOL)synchronouslyWaitForStage:(RCTSurfaceStage)stage timeout:(NSTimeInterval)timeout;
 
 @end
+
+@interface RCTFabricSurface (Internal)
+
+- (void)_setStage:(RCTSurfaceStage)stage;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Surface/RCTFabricSurface.mm b/React/Fabric/Surface/RCTFabricSurface.mm
index bcdaac13129e..babdc28c7c3d 100644
--- a/React/Fabric/Surface/RCTFabricSurface.mm
+++ b/React/Fabric/Surface/RCTFabricSurface.mm
@@ -7,16 +7,260 @@
 
 #import "RCTFabricSurface.h"
 
+#import <React/RCTSurfaceView+Internal.h>
+
+#import <mutex>
+#import <stdatomic.h>
+
+#import <React/RCTAssert.h>
 #import <React/RCTBridge.h>
+#import <React/RCTSurfaceDelegate.h>
+#import <React/RCTSurfaceRootView.h>
+#import <React/RCTSurfaceView.h>
+#import <React/RCTTouchHandler.h>
+#import <React/RCTUIManagerUtils.h>
+#import <React/RCTUtils.h>
+
+#import "RCTSurfacePresenter.h"
+#import "RCTMountingManager.h"
+
+@implementation RCTFabricSurface {
+  // Immutable
+  RCTSurfacePresenter *_surfacePresenter;
+  NSString *_moduleName;
+  ReactTag _rootTag;
+
+  // Protected by the `_mutex`
+  std::mutex _mutex;
+  RCTSurfaceStage _stage;
+  NSDictionary *_properties;
+  CGSize _minimumSize;
+  CGSize _maximumSize;
+  CGSize _intrinsicSize;
+
+  // The Main thread only
+  RCTSurfaceView *_Nullable _view;
+  RCTTouchHandler *_Nullable _touchHandler;
+}
+
+- (instancetype)initWithBridge:(RCTBridge *)bridge
+                    moduleName:(NSString *)moduleName
+             initialProperties:(NSDictionary *)initialProperties
+{
+  RCTAssert(bridge.valid, @"Valid bridge is required to instanciate `RCTSurface`.");
+
+  self = [self initWithSurfacePresenter:bridge.surfacePresenter
+                             moduleName:moduleName
+                      initialProperties:initialProperties];
+
+  return self;
+}
+
+- (instancetype)initWithSurfacePresenter:(RCTSurfacePresenter *)surfacePresenter
+                              moduleName:(NSString *)moduleName
+                       initialProperties:(NSDictionary *)initialProperties
+{
+
+  if (self = [super init]) {
+    _surfacePresenter = surfacePresenter;
+    _moduleName = moduleName;
+    _properties = [initialProperties copy];
+    _rootTag = [RCTAllocateRootViewTag() integerValue];
+
+    _minimumSize = CGSizeZero;
+    _maximumSize = CGSizeMake(CGFLOAT_MAX, CGFLOAT_MAX);
+
+    _stage = RCTSurfaceStageSurfaceDidInitialize;
+
+    [self _run];
+  }
+
+  return self;
+}
+
+- (void)dealloc
+{
+  [self _stop];
+}
+
+#pragma mark - Immutable Properties (no need to enforce synchonization)
+
+- (NSString *)moduleName
+{
+  return _moduleName;
+}
+
+- (NSNumber *)rootViewTag
+{
+  return @(_rootTag);
+}
+
+#pragma mark - Main-Threaded Routines
+
+- (RCTSurfaceView *)view
+{
+  RCTAssertMainQueue();
+
+  if (!_view) {
+    _view = [[RCTSurfaceView alloc] initWithSurface:(RCTSurface *)self];
+  }
+
+  return _view;
+}
+
+#pragma mark - Stage management
+
+- (RCTSurfaceStage)stage
+{
+  std::lock_guard<std::mutex> lock(_mutex);
+  return _stage;
+}
+
+- (void)_setStage:(RCTSurfaceStage)stage
+{
+  RCTSurfaceStage updatedStage;
+  {
+    std::lock_guard<std::mutex> lock(_mutex);
+
+    if (_stage & stage) {
+      return;
+    }
+
+    updatedStage = (RCTSurfaceStage)(_stage | stage);
+    _stage = updatedStage;
+  }
+
+  [self _propagateStageChange:updatedStage];
+}
+
+- (void)_propagateStageChange:(RCTSurfaceStage)stage
+{
+  // Updating the `view`
+  RCTExecuteOnMainQueue(^{
+    self->_view.stage = stage;
+  });
+
+  // Notifying the `delegate`
+  id<RCTSurfaceDelegate> delegate = self.delegate;
+  if ([delegate respondsToSelector:@selector(surface:didChangeStage:)]) {
+    [delegate surface:(RCTSurface *)self didChangeStage:stage];
+  }
+}
+
+#pragma mark - Properties Management
+
+- (NSDictionary *)properties
+{
+  std::lock_guard<std::mutex> lock(_mutex);
+  return _properties;
+}
+
+- (void)setProperties:(NSDictionary *)properties
+{
+  {
+    std::lock_guard<std::mutex> lock(_mutex);
+
+    if ([properties isEqualToDictionary:_properties]) {
+      return;
+    }
+
+    _properties = [properties copy];
+  }
+
+  [self _run];
+}
+
+#pragma mark - Running
+
+- (void)_run
+{
+  [_surfacePresenter registerSurface:self];
+  [self _setStage:RCTSurfaceStageSurfaceDidRun];
+}
+
+- (void)_stop
+{
+  [_surfacePresenter unregisterSurface:self];
+  [self _setStage:RCTSurfaceStageSurfaceDidStop];
+}
+
+#pragma mark - Layout
+
+- (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize
+                      maximumSize:(CGSize)maximumSize
+{
+  // TODO: Not supported yet.
+  return CGSizeZero;
+}
+
+#pragma mark - Size Constraints
+
+- (void)setSize:(CGSize)size
+{
+  [self setMinimumSize:size maximumSize:size];
+}
+
+- (void)setMinimumSize:(CGSize)minimumSize
+           maximumSize:(CGSize)maximumSize
+{
+  {
+    std::lock_guard<std::mutex> lock(_mutex);
+    if (CGSizeEqualToSize(minimumSize, _minimumSize) &&
+        CGSizeEqualToSize(maximumSize, _maximumSize)) {
+      return;
+    }
+
+    _maximumSize = maximumSize;
+    _minimumSize = minimumSize;
+  }
+
+  // TODO: Not supported yet.
+}
+
+- (CGSize)minimumSize
+{
+  std::lock_guard<std::mutex> lock(_mutex);
+  return _minimumSize;
+}
+
+- (CGSize)maximumSize
+{
+  std::lock_guard<std::mutex> lock(_mutex);
+  return _maximumSize;
+}
+
+#pragma mark - intrinsicSize
+
+- (void)setIntrinsicSize:(CGSize)intrinsicSize
+{
+  {
+    std::lock_guard<std::mutex> lock(_mutex);
+    if (CGSizeEqualToSize(intrinsicSize, _intrinsicSize)) {
+      return;
+    }
+
+    _intrinsicSize = intrinsicSize;
+  }
+
+  // Notifying `delegate`
+  id<RCTSurfaceDelegate> delegate = self.delegate;
+  if ([delegate respondsToSelector:@selector(surface:didChangeIntrinsicSize:)]) {
+    [delegate surface:(RCTSurface *)(id)self didChangeIntrinsicSize:intrinsicSize];
+  }
+}
+
+- (CGSize)intrinsicSize
+{
+  std::lock_guard<std::mutex> lock(_mutex);
+  return _intrinsicSize;
+}
 
-@implementation RCTFabricSurface
+#pragma mark - Synchronous Waiting
 
-- (void)unmountReactComponentWithBridge:(RCTBridge *)bridge rootViewTag:(NSNumber *)rootViewTag
+- (BOOL)synchronouslyWaitForStage:(RCTSurfaceStage)stage timeout:(NSTimeInterval)timeout
 {
-  [bridge enqueueJSCall:@"ReactFabric"
-                 method:@"unmountComponentAtNodeAndRemoveContainer"
-                   args:@[rootViewTag]
-             completion:NULL];
+  // TODO: Not supported yet.
+  return NO;
 }
 
 @end
diff --git a/React/Fabric/Surface/RCTFabricSurfaceHostingProxyRootView.mm b/React/Fabric/Surface/RCTFabricSurfaceHostingProxyRootView.mm
index 159a63c865e4..e2210daf8cd2 100644
--- a/React/Fabric/Surface/RCTFabricSurfaceHostingProxyRootView.mm
+++ b/React/Fabric/Surface/RCTFabricSurfaceHostingProxyRootView.mm
@@ -13,7 +13,7 @@ @implementation RCTFabricSurfaceHostingProxyRootView
 
 - (RCTSurface *)createSurfaceWithBridge:(RCTBridge *)bridge moduleName:(NSString *)moduleName initialProperties:(NSDictionary *)initialProperties
 {
-  return [[RCTFabricSurface alloc] initWithBridge:bridge moduleName:moduleName initialProperties:initialProperties];
+  return (RCTSurface *)[[RCTFabricSurface alloc] initWithBridge:bridge moduleName:moduleName initialProperties:initialProperties];
 }
 
 @end
diff --git a/React/Fabric/Surface/RCTFabricSurfaceHostingView.mm b/React/Fabric/Surface/RCTFabricSurfaceHostingView.mm
index eec159cceb92..0157c974b3fd 100644
--- a/React/Fabric/Surface/RCTFabricSurfaceHostingView.mm
+++ b/React/Fabric/Surface/RCTFabricSurfaceHostingView.mm
@@ -16,9 +16,9 @@ - (instancetype)initWithBridge:(RCTBridge *)bridge
              initialProperties:(NSDictionary *)initialProperties
                sizeMeasureMode:(RCTSurfaceSizeMeasureMode)sizeMeasureMode
 {
-  RCTFabricSurface *surface = [[RCTFabricSurface alloc] initWithBridge:bridge
-                                                            moduleName:moduleName
-                                                     initialProperties:initialProperties];
+  RCTSurface *surface = (RCTSurface *)[[RCTFabricSurface alloc] initWithBridge:bridge
+                                                                    moduleName:moduleName
+                                                             initialProperties:initialProperties];
   return [self initWithSurface:surface sizeMeasureMode:sizeMeasureMode];
 }
 

From 515d49ed1c144c5827107dda3a2210a4d343cd1d Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:01 -0700
Subject: [PATCH 0270/1109] Fabric: Introducing RCTScheduler

Summary:
RCTScheduler represent facebook::react::Scheduler as a Obejctive-C object.
It supposed to be single, unified, bidirectional interop layer between C++ and Obejctive-C worlds.

Reviewed By: mdvacca

Differential Revision: D7526405

fbshipit-source-id: a206755f64f2904981b356a40e7659922b24d7bb
---
 React/Fabric/RCTScheduler.h  | 49 ++++++++++++++++++++++++
 React/Fabric/RCTScheduler.mm | 73 ++++++++++++++++++++++++++++++++++++
 2 files changed, 122 insertions(+)
 create mode 100644 React/Fabric/RCTScheduler.h
 create mode 100644 React/Fabric/RCTScheduler.mm

diff --git a/React/Fabric/RCTScheduler.h b/React/Fabric/RCTScheduler.h
new file mode 100644
index 000000000000..1f1e367060f5
--- /dev/null
+++ b/React/Fabric/RCTScheduler.h
@@ -0,0 +1,49 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+#import <memory>
+
+#import <React/RCTPrimitives.h>
+#import <fabric/uimanager/FabricUIManager.h>
+#import <fabric/uimanager/TreeMutationInstruction.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTMountingManager;
+
+/**
+ * Exacly same semantic as `facebook::react::SchedulerDelegate`.
+ */
+@protocol RCTSchedulerDelegate
+
+- (void)schedulerDidComputeMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions rootTag:(ReactTag)rootTag;
+
+- (void)schedulerDidRequestPreliminaryViewAllocationWithComponentName:(NSString *)componentName;
+
+@end
+
+/**
+ * `facebook::react::Scheduler` as an Objective-C class.
+ */
+@interface RCTScheduler : NSObject
+
+@property (atomic, weak, nullable) id<RCTSchedulerDelegate> delegate;
+
+- (void)registerRootTag:(ReactTag)tag;
+
+- (void)unregisterRootTag:(ReactTag)tag;
+
+@end
+
+@interface RCTScheduler (Deprecated)
+
+- (std::shared_ptr<facebook::react::FabricUIManager>)uiManager_DO_NOT_USE;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/RCTScheduler.mm b/React/Fabric/RCTScheduler.mm
new file mode 100644
index 000000000000..0fe06175ee4d
--- /dev/null
+++ b/React/Fabric/RCTScheduler.mm
@@ -0,0 +1,73 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTScheduler.h"
+
+#import <fabric/uimanager/Scheduler.h>
+#import <fabric/uimanager/SchedulerDelegate.h>
+
+using namespace facebook::react;
+
+class SchedulerDelegateProxy: public SchedulerDelegate {
+public:
+  SchedulerDelegateProxy(void *scheduler): scheduler_(scheduler) {}
+
+  void schedulerDidComputeMutationInstructions(Tag rootTag, const TreeMutationInstructionList &instructions) override {
+    RCTScheduler *scheduler = (__bridge RCTScheduler *)scheduler_;
+    [scheduler.delegate schedulerDidComputeMutationInstructions:instructions rootTag:rootTag];
+  }
+
+  void schedulerDidRequestPreliminaryViewAllocation(ComponentName componentName) override {
+    RCTScheduler *scheduler = (__bridge RCTScheduler *)scheduler_;
+    [scheduler.delegate schedulerDidRequestPreliminaryViewAllocationWithComponentName:[NSString stringWithCString:componentName.c_str() encoding:NSASCIIStringEncoding]];
+  }
+
+private:
+  void *scheduler_;
+};
+
+@implementation RCTScheduler {
+  std::shared_ptr<Scheduler> _scheduler;
+  std::shared_ptr<SchedulerDelegateProxy> _delegateProxy;
+}
+
+- (instancetype)init
+{
+  if (self = [super init]) {
+    _delegateProxy = std::make_shared<SchedulerDelegateProxy>((__bridge void *)self);
+    _scheduler = std::make_shared<Scheduler>();
+    _scheduler->setDelegate(_delegateProxy.get());
+  }
+
+  return self;
+}
+
+- (void)dealloc
+{
+  _scheduler->setDelegate(nullptr);
+}
+
+- (void)registerRootTag:(ReactTag)tag
+{
+  _scheduler->registerRootTag(tag);
+}
+
+- (void)unregisterRootTag:(ReactTag)tag
+{
+  _scheduler->unregisterRootTag(tag);
+}
+
+@end
+
+@implementation RCTScheduler (Deprecated)
+
+- (std::shared_ptr<FabricUIManager>)uiManager_DO_NOT_USE
+{
+  return _scheduler->getUIManager_DO_NOT_USE();
+}
+
+@end

From ab5859b44b2ad3998625d42088943362167ae276 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:04 -0700
Subject: [PATCH 0271/1109] Fabric: Introducing RCTSurfaceRegistry

Summary: Simple incapsulation of thread-safe weak set of Surface instances.

Reviewed By: mdvacca

Differential Revision: D7526409

fbshipit-source-id: 8dd789fd6148af3dacf74aac2125b022d11a0fdb
---
 React/Fabric/RCTSurfaceRegistry.h  | 43 ++++++++++++++++++++++++
 React/Fabric/RCTSurfaceRegistry.mm | 52 ++++++++++++++++++++++++++++++
 2 files changed, 95 insertions(+)
 create mode 100644 React/Fabric/RCTSurfaceRegistry.h
 create mode 100644 React/Fabric/RCTSurfaceRegistry.mm

diff --git a/React/Fabric/RCTSurfaceRegistry.h b/React/Fabric/RCTSurfaceRegistry.h
new file mode 100644
index 000000000000..013d70f48955
--- /dev/null
+++ b/React/Fabric/RCTSurfaceRegistry.h
@@ -0,0 +1,43 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTPrimitives.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTFabricSurface;
+
+/**
+ * Registry of Surfaces.
+ * Incapsulates storing Surface objects and quering them by root tag.
+ * All methods of the registry are thread-safe.
+ * The registry stores Surface objects as weak refereces.
+ */
+@interface RCTSurfaceRegistry : NSObject
+
+/**
+ * Adds Surface object into the registry.
+ * The registry does not retain Surface references.
+ */
+- (void)registerSurface:(RCTFabricSurface *)surface;
+
+/**
+ * Removes Surface object from the registry.
+ */
+- (void)unregisterSurface:(RCTFabricSurface *)surface;
+
+/**
+ * Returns stored Surface object by given root tag.
+ * If the registry does not have such Surface registred, returns `nil`.
+ */
+- (nullable RCTFabricSurface *)surfaceForRootTag:(ReactTag)rootTag;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/RCTSurfaceRegistry.mm b/React/Fabric/RCTSurfaceRegistry.mm
new file mode 100644
index 000000000000..d2aa3bde42d5
--- /dev/null
+++ b/React/Fabric/RCTSurfaceRegistry.mm
@@ -0,0 +1,52 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTSurfaceRegistry.h"
+
+#import <mutex>
+
+#import <React/RCTFabricSurface.h>
+
+@implementation RCTSurfaceRegistry {
+  std::mutex _mutex;
+  NSMapTable<id, RCTFabricSurface *> *_registry;
+}
+
+- (instancetype)init
+{
+  if (self = [super init]) {
+    _registry = [NSMapTable mapTableWithKeyOptions:NSPointerFunctionsIntegerPersonality | NSPointerFunctionsOpaqueMemory
+                                      valueOptions:NSPointerFunctionsObjectPersonality];
+  }
+
+  return self;
+}
+
+- (void)registerSurface:(RCTFabricSurface *)surface
+{
+  std::lock_guard<std::mutex> lock(_mutex);
+
+  ReactTag rootTag = surface.rootViewTag.integerValue;
+  [_registry setObject:surface forKey:(__bridge id)(void *)rootTag];
+}
+
+- (void)unregisterSurface:(RCTFabricSurface *)surface
+{
+  std::lock_guard<std::mutex> lock(_mutex);
+
+  ReactTag rootTag = surface.rootViewTag.integerValue;
+  [_registry removeObjectForKey:(__bridge id)(void *)rootTag];
+}
+
+- (RCTFabricSurface *)surfaceForRootTag:(ReactTag)rootTag
+{
+  std::lock_guard<std::mutex> lock(_mutex);
+
+  return [_registry objectForKey:(__bridge id)(void *)rootTag];
+}
+
+@end

From cf036ee2fafac646662bcb7913e8b99ba90e0a4e Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:06 -0700
Subject: [PATCH 0272/1109] Fabric: Introducing RCTSurfacePresenter

Summary:
RCTSurfacePresenter coordinates presenting of React Native Surfaces and represents application-facing interface of running React Native core.
SurfacePresenter incapsulates a bridge object inside and discourages direct access to it.

Reviewed By: mdvacca

Differential Revision: D7526413

fbshipit-source-id: 9b6c513ec63a84d8b6c0951458cbd6b47f49669b
---
 React/Fabric/RCTSurfacePresenter.h  |  60 +++++++++++
 React/Fabric/RCTSurfacePresenter.mm | 154 ++++++++++++++++++++++++++++
 2 files changed, 214 insertions(+)
 create mode 100644 React/Fabric/RCTSurfacePresenter.h
 create mode 100644 React/Fabric/RCTSurfacePresenter.mm

diff --git a/React/Fabric/RCTSurfacePresenter.h b/React/Fabric/RCTSurfacePresenter.h
new file mode 100644
index 000000000000..d99133d59a91
--- /dev/null
+++ b/React/Fabric/RCTSurfacePresenter.h
@@ -0,0 +1,60 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+#import <memory>
+
+#import <React/RCTBridge.h>
+#import <React/RCTCxxExceptionManager.h>
+#import <fabric/uimanager/FabricUIManager.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTFabricSurface;
+@class RCTMountingManager;
+
+/**
+ * Coordinates presenting of React Native Surfaces and represents application
+ * facing interface of running React Native core.
+ * SurfacePresenter incapsulates a bridge object inside and discourage direct
+ * access to it.
+ */
+@interface RCTSurfacePresenter : NSObject
+
+- (instancetype)initWithBridge:(RCTBridge *)bridge;
+
+@end
+
+@interface RCTSurfacePresenter (Internal)
+
+/**
+ * Surface uses those methods to register itself in the Presenter.
+ * Registering initiates running, rendering and mounting processes.
+ */
+- (void)registerSurface:(RCTFabricSurface *)surface;
+- (void)unregisterSurface:(RCTFabricSurface *)surface;
+
+@end
+
+@interface RCTSurfacePresenter (Deprecated)
+
+/**
+ * We need to expose `exceptionManager` and `uiManager` for registration
+ * purposes. Eventually, we will move this down to C++ side.
+ */
+- (std::shared_ptr<facebook::react::ExceptionManager>)exceptionManager_DO_NOT_USE;
+- (std::shared_ptr<facebook::react::FabricUIManager>)uiManager_DO_NOT_USE;
+
+@end
+
+@interface RCTBridge (RCTSurfacePresenter)
+
+- (RCTSurfacePresenter *)surfacePresenter;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
new file mode 100644
index 000000000000..8e88548c8d78
--- /dev/null
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -0,0 +1,154 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTSurfacePresenter.h"
+
+#import <React/RCTAssert.h>
+#import <React/RCTCxxExceptionManager.h>
+#import <React/RCTScheduler.h>
+#import <React/RCTMountingManager.h>
+#import <React/RCTFabricSurface.h>
+#import <React/RCTBridge+Private.h>
+#import <React/RCTMountingManagerDelegate.h>
+#import <React/RCTSurfaceRegistry.h>
+#import <React/RCTComponentViewRegistry.h>
+#import <React/RCTSurfaceView.h>
+#import <React/RCTSurfaceView+Internal.h>
+
+using namespace facebook::react;
+
+@interface RCTSurfacePresenter () <RCTSchedulerDelegate, RCTMountingManagerDelegate>
+@end
+
+@implementation RCTSurfacePresenter {
+  std::shared_ptr<ExceptionManager> _exceptionManager;
+  RCTScheduler *_scheduler;
+  RCTMountingManager *_mountingManager;
+  RCTBridge *_bridge;
+  RCTBridge *_batchedBridge;
+  RCTSurfaceRegistry *_surfaceRegistry;
+}
+
+- (instancetype)initWithBridge:(RCTBridge *)bridge
+{
+  if (self = [super init]) {
+    _bridge = bridge;
+    _batchedBridge = [_bridge batchedBridge] ?: _bridge;
+
+    _exceptionManager = std::make_shared<RCTCxxExceptionManager>();
+
+    _scheduler = [[RCTScheduler alloc] init];
+    _scheduler.delegate = self;
+
+    _surfaceRegistry = [[RCTSurfaceRegistry alloc] init];
+    _mountingManager = [[RCTMountingManager alloc] init];
+    _mountingManager.delegate = self;
+  }
+
+  return self;
+}
+
+- (std::shared_ptr<ExceptionManager>)exceptionManager
+{
+  return _exceptionManager;
+}
+
+- (void)schedulerDidComputeMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions rootTag:(ReactTag)rootTag
+{
+  [_mountingManager mutateComponentViewTreeWithMutationInstructions:instructions
+                                                            rootTag:rootTag];
+}
+
+- (void)schedulerDidRequestPreliminaryViewAllocationWithComponentName:(NSString *)componentName
+{
+  // TODO: To be implemeted.
+}
+
+#pragma mark - Internal Surface-dedicated Interface
+
+- (void)registerSurface:(RCTFabricSurface *)surface
+{
+  [_surfaceRegistry registerSurface:surface];
+  [_scheduler registerRootTag:surface.rootViewTag.integerValue];
+  [self runSurface:surface];
+
+  // FIXME: Mutation instruction MUST produce instruction for root node.
+  [_mountingManager.componentViewRegistry dequeueComponentViewWithName:@"Root" tag:surface.rootViewTag.integerValue];
+}
+
+- (void)unregisterSurface:(RCTFabricSurface *)surface
+{
+  [self stopSurface:surface];
+  [_scheduler unregisterRootTag:surface.rootViewTag.integerValue];
+  [_surfaceRegistry unregisterSurface:surface];
+}
+
+- (void)runSurface:(RCTFabricSurface *)surface
+{
+  NSDictionary *applicationParameters = @{
+    @"rootTag": surface.rootViewTag,
+    @"initialProps": surface.properties,
+  };
+
+  [_batchedBridge enqueueJSCall:@"AppRegistry" method:@"runApplication" args:@[surface.moduleName, applicationParameters] completion:NULL];
+}
+
+- (void)stopSurface:(RCTFabricSurface *)surface
+{
+  [_batchedBridge enqueueJSCall:@"AppRegistry" method:@"unmountApplicationComponentAtRootTag" args:@[surface.rootViewTag] completion:NULL];
+}
+
+#pragma mark - RCTMountingManagerDelegate
+
+- (void)mountingManager:(RCTMountingManager *)mountingManager willMountComponentsWithRootTag:(ReactTag)rootTag
+{
+  RCTIsMainQueue();
+  // TODO: Propagate state change to Surface.
+}
+
+- (void)mountingManager:(RCTMountingManager *)mountingManager didMountComponentsWithRootTag:(ReactTag)rootTag
+{
+  RCTIsMainQueue();
+  RCTFabricSurface *surface = [_surfaceRegistry surfaceForRootTag:rootTag];
+
+  // FIXME: Implement proper state propagation mechanism.
+  [surface _setStage:RCTSurfaceStageSurfaceDidInitialRendering];
+  [surface _setStage:RCTSurfaceStageSurfaceDidInitialLayout];
+  [surface _setStage:RCTSurfaceStageSurfaceDidInitialMounting];
+
+  UIView *rootComponentView = [_mountingManager.componentViewRegistry componentViewByTag:rootTag];
+
+  // FIXME: Remove this.
+  rootComponentView.frame = CGRectMake(0, 0, 400, 400);
+
+  surface.view.rootView = (RCTSurfaceRootView *)rootComponentView;
+}
+
+@end
+
+@implementation RCTSurfacePresenter (Deprecated)
+
+- (std::shared_ptr<FabricUIManager>)uiManager_DO_NOT_USE
+{
+  return _scheduler.uiManager_DO_NOT_USE;
+}
+
+- (std::shared_ptr<facebook::react::ExceptionManager>)exceptionManager_DO_NOT_USE
+{
+  return _exceptionManager;
+}
+
+@end
+
+@implementation RCTBridge (RCTSurfacePresenter)
+
+- (RCTSurfacePresenter *)surfacePresenter
+{
+  return [self jsBoundExtraModuleForClass:[RCTSurfacePresenter class]];
+}
+
+@end

From db92b16e04c2f9e807572a7fbd9fbbb26a4eeddb Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:09 -0700
Subject: [PATCH 0273/1109] Fabric: Proper invocation of `ensureunsealed` in
 `LayoutableShadowNode::layout`

Summary: Quite obvious. We have to check `sealable` flag of the child (not a parent) before mutating it.

Reviewed By: mdvacca

Differential Revision: D7526407

fbshipit-source-id: ce8e0d6446ff7eb23baee9c92f246d5e198fe377
---
 ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index 0e2652efc887..df967d57c151 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -69,7 +69,7 @@ void LayoutableShadowNode::layout(LayoutContext layoutContext) {
       continue;
     }
 
-    ensureUnsealed();
+    child->ensureUnsealed();
 
     // The assumption:
     // All `sealed` children were replaced with not-yet-sealed clones

From 568529e1ecdc12726a152ba627c552612f85a2d9 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:11 -0700
Subject: [PATCH 0274/1109] Fabric: Introducting RCTViewComponentView

Summary:
Implementation of the native view component of <View>.
Root View also must have dedicated class even if its empty now.

Reviewed By: mdvacca

Differential Revision: D7526406

fbshipit-source-id: 9e14c9f679396c2cdb2d64c99086bb19df37c25c
---
 React/Fabric/Mounting/RCTRootComponentView.h  | 21 ++++++++++++
 React/Fabric/Mounting/RCTRootComponentView.mm | 12 +++++++
 React/Fabric/Mounting/RCTViewComponentView.h  | 22 +++++++++++++
 React/Fabric/Mounting/RCTViewComponentView.mm | 33 +++++++++++++++++++
 4 files changed, 88 insertions(+)
 create mode 100644 React/Fabric/Mounting/RCTRootComponentView.h
 create mode 100644 React/Fabric/Mounting/RCTRootComponentView.mm
 create mode 100644 React/Fabric/Mounting/RCTViewComponentView.h
 create mode 100644 React/Fabric/Mounting/RCTViewComponentView.mm

diff --git a/React/Fabric/Mounting/RCTRootComponentView.h b/React/Fabric/Mounting/RCTRootComponentView.h
new file mode 100644
index 000000000000..687d4f73a72b
--- /dev/null
+++ b/React/Fabric/Mounting/RCTRootComponentView.h
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTViewComponentView.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * UIView class for root <View> component.
+ */
+@interface RCTRootComponentView : RCTViewComponentView
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/RCTRootComponentView.mm b/React/Fabric/Mounting/RCTRootComponentView.mm
new file mode 100644
index 000000000000..703c03e5ddfe
--- /dev/null
+++ b/React/Fabric/Mounting/RCTRootComponentView.mm
@@ -0,0 +1,12 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTRootComponentView.h"
+
+@implementation RCTRootComponentView
+
+@end
diff --git a/React/Fabric/Mounting/RCTViewComponentView.h b/React/Fabric/Mounting/RCTViewComponentView.h
new file mode 100644
index 000000000000..046030a8faa3
--- /dev/null
+++ b/React/Fabric/Mounting/RCTViewComponentView.h
@@ -0,0 +1,22 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTComponentViewProtocol.h>
+#import <React/UIView+ComponentViewProtocol.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * UIView class for <View> component.
+ */
+@interface RCTViewComponentView : UIView <RCTComponentViewProtocol>
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/RCTViewComponentView.mm b/React/Fabric/Mounting/RCTViewComponentView.mm
new file mode 100644
index 000000000000..24a985949012
--- /dev/null
+++ b/React/Fabric/Mounting/RCTViewComponentView.mm
@@ -0,0 +1,33 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTViewComponentView.h"
+
+#import <fabric/view/ViewProps.h>
+
+using namespace facebook::react;
+
+@implementation RCTViewComponentView
+
+- (void)updateProps:(facebook::react::SharedProps)props
+           oldProps:(facebook::react::SharedProps)oldProps
+{
+  if (!oldProps) {
+    oldProps = std::make_shared<ViewProps>();
+  }
+
+  auto oldViewProps = *std::dynamic_pointer_cast<const ViewProps>(oldProps);
+  auto newViewProps = *std::dynamic_pointer_cast<const ViewProps>(props);
+
+  if (oldViewProps.getBackgroundColor() != newViewProps.getBackgroundColor()) {
+    self.backgroundColor = [UIColor colorWithCGColor:newViewProps.getBackgroundColor().get()];
+  }
+
+  // TODO: Implement all sutable non-layout <View> props.
+}
+
+@end

From dd49f9e0bc10cf3bc4cc86015823c4a7a6e297ae Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:16 -0700
Subject: [PATCH 0275/1109] Fabric: Fixed incorrect usage of `Undefined`
 (instead of `kFloatUndefined`) in `yogaValuesConversions`

Summary: `Undefined` is actually equal `0` (becasuse it is `LayoutDirection::Undefined`), whereas `kFloatUndefined` is a magic huge number.

Reviewed By: fkgozali

Differential Revision: D7554550

fbshipit-source-id: 3ea37f0b8b6a59b4b0e00d205b75cd7252247d03
---
 ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
index e780d2cecd6f..05137f5e92b4 100644
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
@@ -16,14 +16,14 @@ namespace react {
 
 Float fabricFloatFromYogaFloat(float value) {
   if (value == YGUndefined) {
-    return Undefined;
+    return kFloatUndefined;
   }
 
   return (Float)value;
 }
 
 float yogaFloatFromFabricFloat(Float value) {
-  if (value == Undefined) {
+  if (value == kFloatUndefined) {
     return YGUndefined;
   }
 

From 711abeda7968311ab95bb0f4404ad53bfc008093 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:19 -0700
Subject: [PATCH 0276/1109] Fabric: Using `enum class` for some graphics types

Summary:
`enum class` types do not provide default conversion to integers and reguire use typename before value names.
This must prevent bugs like the previous one where we used `Undefined` as a number value.

Reviewed By: fkgozali

Differential Revision: D7554548

fbshipit-source-id: b19379aae48c9aebe03043e08cf3acc712da3cb8
---
 ReactCommon/fabric/core/layout/LayoutMetrics.h          | 4 ++--
 ReactCommon/fabric/core/layout/LayoutPrimitives.h       | 4 ++--
 ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp | 2 +-
 ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp  | 4 ++--
 4 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutMetrics.h b/ReactCommon/fabric/core/layout/LayoutMetrics.h
index 4bc2641a91bd..22cff2d7cc1e 100644
--- a/ReactCommon/fabric/core/layout/LayoutMetrics.h
+++ b/ReactCommon/fabric/core/layout/LayoutMetrics.h
@@ -20,8 +20,8 @@ struct LayoutMetrics {
   Rect frame;
   EdgeInsets contentInsets {0};
   EdgeInsets borderWidth {0};
-  DisplayType displayType {Flex};
-  LayoutDirection layoutDirection {Undefined};
+  DisplayType displayType {DisplayType::Flex};
+  LayoutDirection layoutDirection {LayoutDirection::Undefined};
 
   bool operator ==(const LayoutMetrics& rhs) const {
     return
diff --git a/ReactCommon/fabric/core/layout/LayoutPrimitives.h b/ReactCommon/fabric/core/layout/LayoutPrimitives.h
index 0036e134e887..0d699aac3c6b 100644
--- a/ReactCommon/fabric/core/layout/LayoutPrimitives.h
+++ b/ReactCommon/fabric/core/layout/LayoutPrimitives.h
@@ -14,7 +14,7 @@ namespace react {
  * Defines visibility of the shadow node and partucular layout
  * engine which should be used for laying out the node.
  */
-enum DisplayType {
+enum class DisplayType {
   None,
   Flex,
   Inline,
@@ -23,7 +23,7 @@ enum DisplayType {
 /*
  * User interface layout direction.
  */
-enum LayoutDirection {
+enum class LayoutDirection {
   Undefined,
   LeftToRight,
   RightToLeft,
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index df967d57c151..b6f9923fd071 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -79,7 +79,7 @@ void LayoutableShadowNode::layout(LayoutContext layoutContext) {
     nonConstChild->setHasNewLayout(false);
 
     const LayoutMetrics childLayoutMetrics = nonConstChild->getLayoutMetrics();
-    if (childLayoutMetrics.displayType == None) {
+    if (childLayoutMetrics.displayType == DisplayType::None) {
       continue;
     }
 
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
index 05137f5e92b4..f13744de7577 100644
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
@@ -77,10 +77,10 @@ LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode) {
   };
 
   layoutMetrics.displayType =
-    yogaNode.getStyle().display == YGDisplayNone ? None : Flex;
+    yogaNode.getStyle().display == YGDisplayNone ? DisplayType::None : DisplayType::Flex;
 
   layoutMetrics.layoutDirection =
-    layout.direction == YGDirectionRTL ? RightToLeft : LeftToRight;
+    layout.direction == YGDirectionRTL ? LayoutDirection::RightToLeft : LayoutDirection::LeftToRight;
 
   return layoutMetrics;
 }

From b13d5beb11ee633509896c1d432be23f7da76117 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:22 -0700
Subject: [PATCH 0277/1109] Fabric: `LayoutableShadowNodeList::getChildren`
 renamed to `getLayoutableChildNodes`

Summary:
The previous name conflicts with the method with same (but with different semantic) name in `ShadowNode` class.
That was bad idea to use same name especially because the different semantic.

Reviewed By: fkgozali

Differential Revision: D7554549

fbshipit-source-id: 0bccbaacd0812f8a26592b2008f15ddb5bc34ebc
---
 ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp   | 2 +-
 ReactCommon/fabric/core/layout/LayoutableShadowNode.h     | 2 +-
 ReactCommon/fabric/view/ViewShadowNode.cpp                | 2 +-
 ReactCommon/fabric/view/ViewShadowNode.h                  | 2 +-
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 4 ++--
 5 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index b6f9923fd071..3e2b4a0e8f7b 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -64,7 +64,7 @@ Float LayoutableShadowNode::lastBaseline(Size size) const {
 void LayoutableShadowNode::layout(LayoutContext layoutContext) {
   layoutChildren(layoutContext);
 
-  for (auto child : getChildren()) {
+  for (auto child : getLayoutableChildNodes()) {
     if (!child->getHasNewLayout()) {
       continue;
     }
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
index e3176f1f3572..d1c9ce1d6a3e 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
@@ -88,7 +88,7 @@ class LayoutableShadowNode:
   /*
    * Returns layoutable children to interate on.
    */
-  virtual SharedLayoutableShadowNodeList getChildren() const = 0;
+  virtual SharedLayoutableShadowNodeList getLayoutableChildNodes() const = 0;
 
   /*
    * In case layout algorithm needs to mutate this (probably sealed) node,
diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/view/ViewShadowNode.cpp
index a51f151b92ff..111d220ec12d 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.cpp
+++ b/ReactCommon/fabric/view/ViewShadowNode.cpp
@@ -75,7 +75,7 @@ void ViewShadowNode::appendChild(const SharedShadowNode &child) {
 
 #pragma mark - YogaLayoutableShadowNode
 
-SharedLayoutableShadowNodeList ViewShadowNode::getChildren() const {
+SharedLayoutableShadowNodeList ViewShadowNode::getLayoutableChildNodes() const {
   SharedLayoutableShadowNodeList sharedLayoutableShadowNodeList = {};
   for (auto child : *children_) {
     const SharedLayoutableShadowNode layoutableShadowNode = std::dynamic_pointer_cast<const LayoutableShadowNode>(child);
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/view/ViewShadowNode.h
index b80a138fd444..230aad5694fe 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.h
+++ b/ReactCommon/fabric/view/ViewShadowNode.h
@@ -60,7 +60,7 @@ class ViewShadowNode:
 
 #pragma mark - LayoutableShadowNode
 
-  SharedLayoutableShadowNodeList getChildren() const override;
+  SharedLayoutableShadowNodeList getLayoutableChildNodes() const override;
   SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child) override;
 };
 
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 62c803b2f0c1..2851fa4d985b 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -114,7 +114,7 @@ void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
 }
 
 void YogaLayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
-  for (auto child : getChildren()) {
+  for (auto child : getLayoutableChildNodes()) {
     auto yogaLayoutableChild = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(child);
     if (!yogaLayoutableChild) {
       continue;
@@ -183,7 +183,7 @@ YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYoga
   //  * Create a new `shared_ptr` with empty deleter.
   //  * Using `childIndex` to find exact node.
   SharedLayoutableShadowNode oldShadowNode = nullptr;
-  for (auto child : parentShadowNodeRawPtr->getChildren()) {
+  for (auto child : parentShadowNodeRawPtr->getLayoutableChildNodes()) {
     if (child.get() == oldShadowNodeRawPtr) {
       oldShadowNode = child;
       break;

From 6924d44b201b9f91e6c8672f053d9a5ad9352358 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 10 Apr 2018 16:37:24 -0700
Subject: [PATCH 0278/1109] Fabric: Fixed ConcreteShadowNode::getProps()

Summary:
Apparently, there is no point to return a reference from this method because the struct (std::shared_ptr) is allocated on stack.
The test is also updated.

allow-large-files

Reviewed By: fkgozali

Differential Revision: D7557749

fbshipit-source-id: aa74146322c6d340256752586f05fc672024038e
---
 ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h | 2 +-
 ReactCommon/fabric/core/tests/ShadowNodeTest.cpp        | 7 ++-----
 2 files changed, 3 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index c9f2741762c5..278d448708c8 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -76,7 +76,7 @@ class ConcreteShadowNode: public ShadowNode {
     return typeid(*this).hash_code();
   }
 
-  const SharedConcreteProps &getProps() const {
+  const SharedConcreteProps getProps() const {
     return std::static_pointer_cast<const PropsT>(props_);
   }
 
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index c14fda2003dd..168cf4886985 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -41,14 +41,11 @@ TEST(ShadowNodeTest, handleShadowNodeCreation) {
   ASSERT_EQ(node->getSourceNode(), nullptr);
   ASSERT_EQ(node->getChildren()->size(), 0);
 
-  // TODO(#27369757): getProps() doesn't work
-  // ASSERT_STREQ(node->getProps()->getNativeId().c_str(), "testNativeID");
+  ASSERT_STREQ(node->getProps()->getNativeId().c_str(), "testNativeID");
 
   node->sealRecursive();
   ASSERT_TRUE(node->getSealed());
-
-  // TODO(#27369757): verify Props are also sealed.
-  // ASSERT_TRUE(node->getProps()->getSealed());
+  ASSERT_TRUE(node->getProps()->getSealed());
 }
 
 TEST(ShadowNodeTest, handleShadowNodeSimpleCloning) {

From edd22bf49de6954ea0f57c009f563ae25d22db28 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Tue, 10 Apr 2018 19:23:07 -0700
Subject: [PATCH 0279/1109] Log bridge description for e2e reloads

Reviewed By: mhorowitz

Differential Revision: D7577953

fbshipit-source-id: 96871c664cb7ec84570bc76f2edb36ff8c8c6aeb
---
 React/Base/RCTBridge.h          | 6 ++++++
 React/Base/RCTBridge.m          | 1 +
 React/CxxBridge/RCTCxxBridge.mm | 6 +++++-
 3 files changed, 12 insertions(+), 1 deletion(-)

diff --git a/React/Base/RCTBridge.h b/React/Base/RCTBridge.h
index 2a7eabe5ce84..5222a15b5ca7 100644
--- a/React/Base/RCTBridge.h
+++ b/React/Base/RCTBridge.h
@@ -72,6 +72,12 @@ RCT_EXTERN NSString *const RCTBridgeDidDownloadScriptNotification;
  */
 RCT_EXTERN NSString *const RCTBridgeDidDownloadScriptNotificationSourceKey;
 
+/**
+ * Key for the bridge description (NSString_ in the
+ * RCTBridgeDidDownloadScriptNotification userInfo dictionary.
+ */
+RCT_EXTERN NSString *const RCTBridgeDidDownloadScriptNotificationBridgeDescriptionKey;
+
 /**
  * This block can be used to instantiate modules that require additional
  * init parameters, or additional configuration prior to being used.
diff --git a/React/Base/RCTBridge.m b/React/Base/RCTBridge.m
index 76f2d17a203f..4f85966d9712 100644
--- a/React/Base/RCTBridge.m
+++ b/React/Base/RCTBridge.m
@@ -31,6 +31,7 @@
 NSString *const RCTBridgeWillDownloadScriptNotification = @"RCTBridgeWillDownloadScriptNotification";
 NSString *const RCTBridgeDidDownloadScriptNotification = @"RCTBridgeDidDownloadScriptNotification";
 NSString *const RCTBridgeDidDownloadScriptNotificationSourceKey = @"source";
+NSString *const RCTBridgeDidDownloadScriptNotificationBridgeDescriptionKey = @"bridgeDescription";
 
 static NSMutableArray<Class> *RCTModuleClasses;
 NSArray<Class> *RCTGetModuleClasses(void)
diff --git a/React/CxxBridge/RCTCxxBridge.mm b/React/CxxBridge/RCTCxxBridge.mm
index 7411dcdcc613..cd82c3ccd85a 100644
--- a/React/CxxBridge/RCTCxxBridge.mm
+++ b/React/CxxBridge/RCTCxxBridge.mm
@@ -400,7 +400,11 @@ - (void)loadSource:(RCTSourceLoadBlock)_onSourceLoad onProgress:(RCTSourceLoadPr
     [performanceLogger markStopForTag:RCTPLScriptDownload];
     [performanceLogger setValue:source.length forTag:RCTPLBundleSize];
 
-    NSDictionary *userInfo = source ? @{ RCTBridgeDidDownloadScriptNotificationSourceKey: source } : nil;
+    NSDictionary *userInfo = @{
+      RCTBridgeDidDownloadScriptNotificationSourceKey: source ?: [NSNull null],
+      RCTBridgeDidDownloadScriptNotificationBridgeDescriptionKey: self->_bridgeDescription ?: [NSNull null],
+    };
+
     [center postNotificationName:RCTBridgeDidDownloadScriptNotification object:self->_parentBridge userInfo:userInfo];
 
     _onSourceLoad(error, source);

From 80fc415cf179ffe26d020bc8d6e4451352da94fd Mon Sep 17 00:00:00 2001
From: Manuel Alabor <manuel@alabor.me>
Date: Tue, 10 Apr 2018 19:47:21 -0700
Subject: [PATCH 0280/1109] Expose InputAccessoryView Module

Summary:
The latest release of react-native (0.55.2) does not expose the new `InputAccessoryView` component; It can't be accessed at all. This change fixes this problem.

* Problem: Snack showing the problem: https://snack.expo.io/B1fDQRYif
* Proof: `RNTester` still works with adapted imports

No related PRs.

[IOS] [BUGFIX] [InputAccessoryView] - Expose `InputAccessoryView` so it can be imported
Closes https://github.com/facebook/react-native/pull/18780

Differential Revision: D7581729

Pulled By: hramos

fbshipit-source-id: d61ab1f167360e829e32b93fb5414d2f7e57e115
---
 .../react-native-implementation.js            |  1 +
 RNTester/js/InputAccessoryViewExample.js      | 19 +++++++++++--------
 2 files changed, 12 insertions(+), 8 deletions(-)

diff --git a/Libraries/react-native/react-native-implementation.js b/Libraries/react-native/react-native-implementation.js
index 200409bcbc04..e3b19adc459c 100644
--- a/Libraries/react-native/react-native-implementation.js
+++ b/Libraries/react-native/react-native-implementation.js
@@ -26,6 +26,7 @@ const ReactNative = {
   get ImageBackground() { return require('ImageBackground'); },
   get ImageEditor() { return require('ImageEditor'); },
   get ImageStore() { return require('ImageStore'); },
+  get InputAccessoryView() { return require('InputAccessoryView') },
   get KeyboardAvoidingView() { return require('KeyboardAvoidingView'); },
   get ListView() { return require('ListView'); },
   get MaskedViewIOS() { return require('MaskedViewIOS'); },
diff --git a/RNTester/js/InputAccessoryViewExample.js b/RNTester/js/InputAccessoryViewExample.js
index 7ebcf5f0090a..9287fb7e1e68 100644
--- a/RNTester/js/InputAccessoryViewExample.js
+++ b/RNTester/js/InputAccessoryViewExample.js
@@ -11,15 +11,18 @@
 
 'use strict';
 
-const Alert = require('Alert');
-const Button = require('Button');
-const InputAccessoryView = require('InputAccessoryView');
 const React = require('React');
-const ScrollView = require('ScrollView');
-const StyleSheet = require('StyleSheet');
-const Text = require('Text');
-const TextInput = require('TextInput');
-const View = require('View');
+const ReactNative = require('react-native');
+const {
+  Alert,
+  Button,
+  InputAccessoryView,
+  ScrollView,
+  StyleSheet,
+  Text,
+  TextInput,
+  View,
+} = ReactNative;
 
 class Message extends React.PureComponent<*> {
   render() {

From ebd12fa09fca8c9cee4a48e3f1652986d51fcdb3 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Tue, 10 Apr 2018 20:58:22 -0700
Subject: [PATCH 0281/1109] BREAKING CHANGE: UPGRADE REACT NATIVE TO BABEL 7!

Summary:
BREAKING CHANGE
This change upgrades the React Native build pipeline from Babel 6 to Babel 7

If you use a `.babelrc` then you'll need to update it to Babel 7 (note that some plugins are no longer relevant, some plugins are automatically upgraded, and some will need some manual love).

Note that you may also need to upgrade your dev env, tests etc, to make sure they work with Babel 7.

Reviewed By: cpojer

Differential Revision: D7097279

fbshipit-source-id: 9fb204cae733174a1c155669b7c17ddb70f7aecc
---
 Libraries/polyfills/babelHelpers.js | 220 ++++++++++++++++++----------
 babel-preset/configs/main.js        |  78 +++++-----
 jest/preprocessor.js                |  47 +++++-
 3 files changed, 233 insertions(+), 112 deletions(-)

diff --git a/Libraries/polyfills/babelHelpers.js b/Libraries/polyfills/babelHelpers.js
index dfe819464f09..7d251ea34748 100644
--- a/Libraries/polyfills/babelHelpers.js
+++ b/Libraries/polyfills/babelHelpers.js
@@ -12,19 +12,15 @@
 /* eslint-disable quotes, curly, no-proto, no-undef-init, dot-notation */
 
 // Created by running:
-// require('babel-core').buildExternalHelpers('_extends classCallCheck createClass createRawReactElement defineProperty get inherits  interopRequireDefault interopRequireWildcard objectWithoutProperties possibleConstructorReturn slicedToArray taggedTemplateLiteral toArray toConsumableArray '.split(' '))
-// then replacing the `global` reference in the last line to also use `this`.
+// require('fs').writeFileSync('babelExternalHelpers.js', require('@babel/core').buildExternalHelpers('_extends classCallCheck createClass createRawReactElement defineProperty get inherits  interopRequireDefault interopRequireWildcard objectWithoutProperties possibleConstructorReturn slicedToArray taggedTemplateLiteral toArray toConsumableArray wrapNativeSuper assertThisInitialized taggedTemplateLiteralLoose'.split(' ')))// then replacing the `global` reference in the last line to also use `this`.
 //
-// actually, that's a lie, because babel6 omits _extends and createRawReactElement
+// Actually, that's a lie, because babel omits _extends and
+// createRawReactElement. the file is also cleaned up a bit.
+// You may need to clear wrapNativeSuper while the bug hasn't been fixed yet.
+// Do try to keep diffs to a minimum.
 
 var babelHelpers = global.babelHelpers = {};
 
-babelHelpers.typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) {
-  return typeof obj;
-} : function (obj) {
-  return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
-};
-
 babelHelpers.createRawReactElement = (function () {
   var REACT_ELEMENT_TYPE = typeof Symbol === "function" && Symbol.for && Symbol.for("react.element") || 0xeac7;
   return function createRawReactElement(type, key, props) {
@@ -45,32 +41,20 @@ babelHelpers.classCallCheck = function (instance, Constructor) {
   }
 };
 
-babelHelpers.createClass = (function () {
-  function defineProperties(target, props) {
-    for (var i = 0; i < props.length; i++) {
-      var descriptor = props[i];
-      descriptor.enumerable = descriptor.enumerable || false;
-      descriptor.configurable = true;
-      if ("value" in descriptor) descriptor.writable = true;
-      Object.defineProperty(target, descriptor.key, descriptor);
-    }
+function _defineProperties(target, props) {
+  for (var i = 0; i < props.length; i++) {
+    var descriptor = props[i];
+    descriptor.enumerable = descriptor.enumerable || false;
+    descriptor.configurable = true;
+    if ("value" in descriptor) descriptor.writable = true;
+    Object.defineProperty(target, descriptor.key, descriptor);
   }
+}
 
-  return function (Constructor, protoProps, staticProps) {
-    if (protoProps) defineProperties(Constructor.prototype, protoProps);
-    if (staticProps) defineProperties(Constructor, staticProps);
-    return Constructor;
-  };
-})();
-
-babelHelpers.defineEnumerableProperties = function(obj, descs) {
-  for (var key in descs) {
-    var desc = descs[key];
-    desc.configurable = (desc.enumerable = true);
-    if ('value' in desc) desc.writable = true;
-    Object.defineProperty(obj, key, desc);
-  }
-  return obj;
+babelHelpers.createClass = function(Constructor, protoProps, staticProps) {
+  if (protoProps) _defineProperties(Constructor.prototype, protoProps);
+  if (staticProps) _defineProperties(Constructor, staticProps);
+  return Constructor;
 };
 
 babelHelpers.defineProperty = function (obj, key, value) {
@@ -129,9 +113,8 @@ babelHelpers.get = function get(object, property, receiver) {
 
 babelHelpers.inherits = function (subClass, superClass) {
   if (typeof superClass !== "function" && superClass !== null) {
-    throw new TypeError("Super expression must either be null or a function, not " + typeof superClass);
+    throw new TypeError("Super expression must either be null or a function");
   }
-
   subClass.prototype = Object.create(superClass && superClass.prototype, {
     constructor: {
       value: subClass,
@@ -143,6 +126,54 @@ babelHelpers.inherits = function (subClass, superClass) {
   if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass;
 };
 
+var _gPO = Object.getPrototypeOf || function _gPO(o) { return o.__proto__ };
+var _sPO = Object.setPrototypeOf || function _sPO(o, p) { o.__proto__ = p; return o };
+var _construct =
+// TODO: prepack does not like this line (and we can use the fallback just fine)
+// (typeof Reflect === "object" && Reflect.construct) ||
+  function _construct(Parent, args, Class) {
+    var Constructor, a = [null];
+    a.push.apply(a, args);
+    Constructor = Parent.bind.apply(Parent, a);
+    return _sPO(new Constructor, Class.prototype);
+  };
+var _cache = typeof Map === "function" && new Map();
+babelHelpers.wrapNativeSuper = function(Class) {
+  // FB:
+  // Note: while extending native classes is pretty meh we do have cases, for
+  // example; Error. There is also a false positive, for example; Blob.
+
+  if (typeof Class !== "function") {
+    throw new TypeError("Super expression must either be null or a function");
+  }
+  if (typeof _cache !== "undefined") {
+    if (_cache.has(Class)) return _cache.get(Class);
+    _cache.set(Class, Wrapper);
+  }
+  function Wrapper() {
+    // this is a temporary fix for a babel bug (it's invoking the wrong func
+    // when you do `super()`)
+    return _construct(Class, arguments, _gPO(this).constructor);
+  }
+  Wrapper.prototype = Object.create(Class.prototype, {
+    constructor: {
+      value: Wrapper,
+      enumerable: false,
+      writeable: true,
+      configurable: true,
+    }
+  });
+  return _sPO(
+    Wrapper,
+    _sPO(
+      function Super() {
+        return _construct(Class, arguments, _gPO(this).constructor);
+      },
+      Class
+    )
+  );
+};
+
 babelHelpers.interopRequireDefault = function (obj) {
   return obj && obj.__esModule ? obj : {
     default: obj
@@ -157,7 +188,15 @@ babelHelpers.interopRequireWildcard = function (obj) {
 
     if (obj != null) {
       for (var key in obj) {
-        if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key];
+        if (Object.prototype.hasOwnProperty.call(obj, key)) {
+          var desc = Object.defineProperty && Object.getOwnPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : {};
+
+          if (desc.get || desc.set) {
+            Object.defineProperty(newObj, key, desc);
+          } else {
+            newObj[key] = obj[key];
+          }
+        }
       }
     }
 
@@ -166,63 +205,79 @@ babelHelpers.interopRequireWildcard = function (obj) {
   }
 };
 
-babelHelpers.objectWithoutProperties = function (obj, keys) {
+babelHelpers.objectWithoutProperties = function(source, excluded) {
+  if (source == null) return {};
   var target = {};
+  var sourceKeys = Object.keys(source);
+  var key, i;
+
+  for (i = 0; i < sourceKeys.length; i++) {
+    key = sourceKeys[i];
+    if (excluded.indexOf(key) >= 0) continue;
+    target[key] = source[key];
+  }
+
+  if (Object.getOwnPropertySymbols) {
+    var sourceSymbolKeys = Object.getOwnPropertySymbols(source);
 
-  for (var i in obj) {
-    if (keys.indexOf(i) >= 0) continue;
-    if (!Object.prototype.hasOwnProperty.call(obj, i)) continue;
-    target[i] = obj[i];
+    for (i = 0; i < sourceSymbolKeys.length; i++) {
+      key = sourceSymbolKeys[i];
+      if (excluded.indexOf(key) >= 0) continue;
+      if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue;
+      target[key] = source[key];
+    }
   }
 
   return target;
 };
 
 babelHelpers.possibleConstructorReturn = function (self, call) {
-  if (!self) {
+  if (call && (typeof call === "object" || typeof call === "function")) {
+    return call;
+  }
+
+  if (self === void 0) {
     throw new ReferenceError("this hasn't been initialised - super() hasn't been called");
   }
 
-  return call && (typeof call === "object" || typeof call === "function") ? call : self;
+  return self;
 };
 
-babelHelpers.slicedToArray = (function () {
-  function sliceIterator(arr, i) {
-    var _arr = [];
-    var _n = true;
-    var _d = false;
-    var _e = undefined;
+function _sliceIterator(arr, i) {
+  var _arr = [];
+  var _n = true;
+  var _d = false;
+  var _e = undefined;
 
-    try {
-      for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
-        _arr.push(_s.value);
+  try {
+    for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
+      _arr.push(_s.value);
 
-        if (i && _arr.length === i) break;
-      }
-    } catch (err) {
-      _d = true;
-      _e = err;
+      if (i && _arr.length === i) break;
+    }
+  } catch (err) {
+    _d = true;
+    _e = err;
+  } finally {
+    try {
+      if (!_n && _i["return"] != null) _i["return"]();
     } finally {
-      try {
-        if (!_n && _i["return"]) _i["return"]();
-      } finally {
-        if (_d) throw _e;
-      }
+      if (_d) throw _e;
     }
-
-    return _arr;
   }
 
-  return function (arr, i) {
-    if (Array.isArray(arr)) {
-      return arr;
-    } else if (Symbol.iterator in Object(arr)) {
-      return sliceIterator(arr, i);
-    } else {
-      throw new TypeError("Invalid attempt to destructure non-iterable instance");
-    }
-  };
-})();
+  return _arr;
+}
+
+babelHelpers.slicedToArray = function(arr, i) {
+  if (Array.isArray(arr)) {
+    return arr;
+  } else if (Symbol.iterator in Object(arr)) {
+    return _sliceIterator(arr, i);
+  } else {
+    throw new TypeError("Invalid attempt to destructure non-iterable instance");
+  }
+};
 
 babelHelpers.taggedTemplateLiteral = function (strings, raw) {
   return Object.freeze(Object.defineProperties(strings, {
@@ -238,10 +293,25 @@ babelHelpers.toArray = function (arr) {
 
 babelHelpers.toConsumableArray = function (arr) {
   if (Array.isArray(arr)) {
-    for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i];
+    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) arr2[i] = arr[i];
 
     return arr2;
   } else {
     return Array.from(arr);
   }
 };
+
+babelHelpers.assertThisInitialized = function(self) {
+  if (self === void 0) {
+    throw new ReferenceError(
+      "this hasn't been initialised - super() hasn't been called",
+    );
+  }
+
+  return self;
+};
+
+babelHelpers.taggedTemplateLiteralLoose = function(strings, raw) {
+  strings.raw = raw;
+  return strings;
+};
diff --git a/babel-preset/configs/main.js b/babel-preset/configs/main.js
index 96405f002f95..d17db86969f7 100644
--- a/babel-preset/configs/main.js
+++ b/babel-preset/configs/main.js
@@ -8,37 +8,55 @@
 'use strict';
 
 const defaultPlugins = [
-  [require('babel-plugin-syntax-class-properties')],
-  [require('babel-plugin-syntax-trailing-function-commas')],
-  [require('babel-plugin-transform-class-properties')],
-  [require('babel-plugin-transform-es2015-block-scoping')],
-  [require('babel-plugin-transform-es2015-computed-properties')],
-  [require('babel-plugin-transform-es2015-destructuring')],
-  [require('babel-plugin-transform-es2015-function-name')],
-  [require('babel-plugin-transform-es2015-literals')],
-  [require('babel-plugin-transform-es2015-parameters')],
-  [require('babel-plugin-transform-es2015-shorthand-properties')],
-  [require('babel-plugin-transform-flow-strip-types')],
-  [require('babel-plugin-transform-react-jsx')],
-  [require('babel-plugin-transform-regenerator')],
+  [require('@babel/plugin-transform-block-scoping')],
+  // the flow strip types plugin must go BEFORE class properties!
+  // there'll be a test case that fails if you don't.
+  [require('@babel/plugin-transform-flow-strip-types')],
   [
-    require('babel-plugin-transform-es2015-modules-commonjs'),
-    {strict: false, allowTopLevelThis: true},
+    require('@babel/plugin-proposal-class-properties'),
+    // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
+    // (Makes the properties enumerable)
+    {loose: true},
+  ],
+  [require('@babel/plugin-transform-computed-properties')],
+  [require('@babel/plugin-transform-destructuring')],
+  [require('@babel/plugin-transform-function-name')],
+  [require('@babel/plugin-transform-literals')],
+  [require('@babel/plugin-transform-parameters')],
+  [require('@babel/plugin-transform-shorthand-properties')],
+  [require('@babel/plugin-transform-react-jsx')],
+  [require('@babel/plugin-transform-regenerator')],
+  [require('@babel/plugin-transform-sticky-regex')],
+  [require('@babel/plugin-transform-unicode-regex')],
+  [
+    require('@babel/plugin-transform-modules-commonjs'),
+    {
+      strict: false,
+      strictMode : false, // prevent "use strict" injections
+      allowTopLevelThis: true, // dont rewrite global `this` -> `undefined`
+    },
   ],
 ];
 
-const checkES2015Constants = [require('babel-plugin-check-es2015-constants')];
-const es2015ArrowFunctions = [require('babel-plugin-transform-es2015-arrow-functions')];
-const es2015Classes = [require('babel-plugin-transform-es2015-classes')];
-const es2015ForOf = [require('babel-plugin-transform-es2015-for-of'), {loose: true}];
-const es2015Spread = [require('babel-plugin-transform-es2015-spread')];
-const es2015TemplateLiterals = [require('babel-plugin-transform-es2015-template-literals')];
-const asyncFunctions = [require('babel-plugin-syntax-async-functions')];
-const exponentiationOperator = [require('babel-plugin-transform-exponentiation-operator')];
-const objectAssign = [require('babel-plugin-transform-object-assign')];
-const objectRestSpread = [require('babel-plugin-transform-object-rest-spread')];
-const reactDisplayName = [require('babel-plugin-transform-react-display-name')];
-const reactJsxSource = [require('babel-plugin-transform-react-jsx-source')];
+const es2015ArrowFunctions = [
+  require('@babel/plugin-transform-arrow-functions'),
+];
+const es2015Classes = [require('@babel/plugin-transform-classes')];
+const es2015ForOf = [require('@babel/plugin-transform-for-of'), {loose: true}];
+const es2015Spread = [require('@babel/plugin-transform-spread')];
+const es2015TemplateLiterals = [
+  require('@babel/plugin-transform-template-literals'),
+  {loose: true}, // dont 'a'.concat('b'), just use 'a'+'b'
+];
+const exponentiationOperator = [
+  require('@babel/plugin-transform-exponentiation-operator'),
+];
+const objectAssign = [require('@babel/plugin-transform-object-assign')];
+const objectRestSpread = [require('@babel/plugin-proposal-object-rest-spread')];
+const reactDisplayName = [
+  require('@babel/plugin-transform-react-display-name'),
+];
+const reactJsxSource = [require('@babel/plugin-transform-react-jsx-source')];
 const symbolMember = [require('../transforms/transform-symbol-member')];
 
 const getPreset = (src, options) => {
@@ -49,18 +67,12 @@ const getPreset = (src, options) => {
 
   const extraPlugins = [];
 
-  if (isNull || src.indexOf('async') !== -1 || src.indexOf('await') !== -1) {
-    extraPlugins.push(asyncFunctions);
-  }
   if (hasClass) {
     extraPlugins.push(es2015Classes);
   }
   if (isNull || src.indexOf('=>') !== -1) {
     extraPlugins.push(es2015ArrowFunctions);
   }
-  if (isNull || src.indexOf('const') !== -1) {
-    extraPlugins.push(checkES2015Constants);
-  }
   if (isNull || hasClass || src.indexOf('...') !== -1) {
     extraPlugins.push(es2015Spread);
     extraPlugins.push(objectRestSpread);
diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index e6a897f8e02a..a7c52411f190 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -11,7 +11,7 @@
 
 'use strict';
 
-const babel = require('babel-core');
+const {transformSync: babelTransformSync} = require('@babel/core');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
@@ -20,7 +20,7 @@ const babelRegisterOnly = require('metro/src/babelRegisterOnly');
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
 const createCacheKeyFunction = require('fbjs-scripts/jest/createCacheKeyFunction');
-const generate = require('babel-generator').default;
+const generate = require('@babel/generator').default;
 
 const nodeFiles = RegExp([
   '/local-cli/',
@@ -35,7 +35,7 @@ const transformer = require('metro/src/transformer.js');
 module.exports = {
   process(src/*: string*/, file/*: string*/) {
     if (nodeFiles.test(file)) { // node specific transforms only
-      return babel.transform(
+      return babelTransformSync(
         src,
         Object.assign({filename: file}, nodeOptions)
       ).code;
@@ -54,6 +54,45 @@ module.exports = {
         retainLines: true,
       },
       src,
+      plugins: [
+        [require('@babel/plugin-transform-block-scoping')],
+        // the flow strip types plugin must go BEFORE class properties!
+        // there'll be a test case that fails if you don't.
+        [require('@babel/plugin-transform-flow-strip-types')],
+        [
+          require('@babel/plugin-proposal-class-properties'),
+          // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
+          // (Makes the properties enumerable)
+          {loose: true},
+        ],
+        [require('@babel/plugin-transform-computed-properties')],
+        [require('@babel/plugin-transform-destructuring')],
+        [require('@babel/plugin-transform-function-name')],
+        [require('@babel/plugin-transform-literals')],
+        [require('@babel/plugin-transform-parameters')],
+        [require('@babel/plugin-transform-shorthand-properties')],
+        [require('@babel/plugin-transform-react-jsx')],
+        [require('@babel/plugin-transform-regenerator')],
+        [require('@babel/plugin-transform-sticky-regex')],
+        [require('@babel/plugin-transform-unicode-regex')],
+        [
+          require('@babel/plugin-transform-modules-commonjs'),
+          {strict: false, allowTopLevelThis: true},
+        ],
+        [require('@babel/plugin-transform-classes')],
+        [require('@babel/plugin-transform-arrow-functions')],
+        [require('@babel/plugin-transform-spread')],
+        [require('@babel/plugin-proposal-object-rest-spread')],
+        [
+          require('@babel/plugin-transform-template-literals'),
+          {loose: true}, // dont 'a'.concat('b'), just use 'a'+'b'
+        ],
+        [require('@babel/plugin-transform-exponentiation-operator')],
+        [require('@babel/plugin-transform-object-assign')],
+        [require('@babel/plugin-transform-for-of'), {loose: true}],
+        [require('@babel/plugin-transform-react-display-name')],
+        [require('@babel/plugin-transform-react-jsx-source')],
+      ],
     });
 
     return generate(ast, {
@@ -70,6 +109,6 @@ module.exports = {
   getCacheKey: createCacheKeyFunction([
     __filename,
     require.resolve('metro/src/transformer.js'),
-    require.resolve('babel-core/package.json'),
+    require.resolve('@babel/core/package.json'),
   ]),
 };

From c9a6b8560f0e6ef3e995d99c89ebca412a505521 Mon Sep 17 00:00:00 2001
From: Matt Mahoney <mmahoney@fb.com>
Date: Wed, 11 Apr 2018 08:12:44 -0700
Subject: [PATCH 0282/1109] Revert D7097279: BREAKING CHANGE: UPGRADE REACT
 NATIVE TO BABEL 7!

Differential Revision:
D7097279

Original commit changeset: 9fb204cae733

fbshipit-source-id: bbbb20b5dbed5dc01ae5557686a07d987b9a6cc6
---
 Libraries/polyfills/babelHelpers.js | 220 ++++++++++------------------
 babel-preset/configs/main.js        |  78 +++++-----
 jest/preprocessor.js                |  47 +-----
 3 files changed, 112 insertions(+), 233 deletions(-)

diff --git a/Libraries/polyfills/babelHelpers.js b/Libraries/polyfills/babelHelpers.js
index 7d251ea34748..dfe819464f09 100644
--- a/Libraries/polyfills/babelHelpers.js
+++ b/Libraries/polyfills/babelHelpers.js
@@ -12,15 +12,19 @@
 /* eslint-disable quotes, curly, no-proto, no-undef-init, dot-notation */
 
 // Created by running:
-// require('fs').writeFileSync('babelExternalHelpers.js', require('@babel/core').buildExternalHelpers('_extends classCallCheck createClass createRawReactElement defineProperty get inherits  interopRequireDefault interopRequireWildcard objectWithoutProperties possibleConstructorReturn slicedToArray taggedTemplateLiteral toArray toConsumableArray wrapNativeSuper assertThisInitialized taggedTemplateLiteralLoose'.split(' ')))// then replacing the `global` reference in the last line to also use `this`.
+// require('babel-core').buildExternalHelpers('_extends classCallCheck createClass createRawReactElement defineProperty get inherits  interopRequireDefault interopRequireWildcard objectWithoutProperties possibleConstructorReturn slicedToArray taggedTemplateLiteral toArray toConsumableArray '.split(' '))
+// then replacing the `global` reference in the last line to also use `this`.
 //
-// Actually, that's a lie, because babel omits _extends and
-// createRawReactElement. the file is also cleaned up a bit.
-// You may need to clear wrapNativeSuper while the bug hasn't been fixed yet.
-// Do try to keep diffs to a minimum.
+// actually, that's a lie, because babel6 omits _extends and createRawReactElement
 
 var babelHelpers = global.babelHelpers = {};
 
+babelHelpers.typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) {
+  return typeof obj;
+} : function (obj) {
+  return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
+};
+
 babelHelpers.createRawReactElement = (function () {
   var REACT_ELEMENT_TYPE = typeof Symbol === "function" && Symbol.for && Symbol.for("react.element") || 0xeac7;
   return function createRawReactElement(type, key, props) {
@@ -41,20 +45,32 @@ babelHelpers.classCallCheck = function (instance, Constructor) {
   }
 };
 
-function _defineProperties(target, props) {
-  for (var i = 0; i < props.length; i++) {
-    var descriptor = props[i];
-    descriptor.enumerable = descriptor.enumerable || false;
-    descriptor.configurable = true;
-    if ("value" in descriptor) descriptor.writable = true;
-    Object.defineProperty(target, descriptor.key, descriptor);
+babelHelpers.createClass = (function () {
+  function defineProperties(target, props) {
+    for (var i = 0; i < props.length; i++) {
+      var descriptor = props[i];
+      descriptor.enumerable = descriptor.enumerable || false;
+      descriptor.configurable = true;
+      if ("value" in descriptor) descriptor.writable = true;
+      Object.defineProperty(target, descriptor.key, descriptor);
+    }
   }
-}
 
-babelHelpers.createClass = function(Constructor, protoProps, staticProps) {
-  if (protoProps) _defineProperties(Constructor.prototype, protoProps);
-  if (staticProps) _defineProperties(Constructor, staticProps);
-  return Constructor;
+  return function (Constructor, protoProps, staticProps) {
+    if (protoProps) defineProperties(Constructor.prototype, protoProps);
+    if (staticProps) defineProperties(Constructor, staticProps);
+    return Constructor;
+  };
+})();
+
+babelHelpers.defineEnumerableProperties = function(obj, descs) {
+  for (var key in descs) {
+    var desc = descs[key];
+    desc.configurable = (desc.enumerable = true);
+    if ('value' in desc) desc.writable = true;
+    Object.defineProperty(obj, key, desc);
+  }
+  return obj;
 };
 
 babelHelpers.defineProperty = function (obj, key, value) {
@@ -113,8 +129,9 @@ babelHelpers.get = function get(object, property, receiver) {
 
 babelHelpers.inherits = function (subClass, superClass) {
   if (typeof superClass !== "function" && superClass !== null) {
-    throw new TypeError("Super expression must either be null or a function");
+    throw new TypeError("Super expression must either be null or a function, not " + typeof superClass);
   }
+
   subClass.prototype = Object.create(superClass && superClass.prototype, {
     constructor: {
       value: subClass,
@@ -126,54 +143,6 @@ babelHelpers.inherits = function (subClass, superClass) {
   if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass;
 };
 
-var _gPO = Object.getPrototypeOf || function _gPO(o) { return o.__proto__ };
-var _sPO = Object.setPrototypeOf || function _sPO(o, p) { o.__proto__ = p; return o };
-var _construct =
-// TODO: prepack does not like this line (and we can use the fallback just fine)
-// (typeof Reflect === "object" && Reflect.construct) ||
-  function _construct(Parent, args, Class) {
-    var Constructor, a = [null];
-    a.push.apply(a, args);
-    Constructor = Parent.bind.apply(Parent, a);
-    return _sPO(new Constructor, Class.prototype);
-  };
-var _cache = typeof Map === "function" && new Map();
-babelHelpers.wrapNativeSuper = function(Class) {
-  // FB:
-  // Note: while extending native classes is pretty meh we do have cases, for
-  // example; Error. There is also a false positive, for example; Blob.
-
-  if (typeof Class !== "function") {
-    throw new TypeError("Super expression must either be null or a function");
-  }
-  if (typeof _cache !== "undefined") {
-    if (_cache.has(Class)) return _cache.get(Class);
-    _cache.set(Class, Wrapper);
-  }
-  function Wrapper() {
-    // this is a temporary fix for a babel bug (it's invoking the wrong func
-    // when you do `super()`)
-    return _construct(Class, arguments, _gPO(this).constructor);
-  }
-  Wrapper.prototype = Object.create(Class.prototype, {
-    constructor: {
-      value: Wrapper,
-      enumerable: false,
-      writeable: true,
-      configurable: true,
-    }
-  });
-  return _sPO(
-    Wrapper,
-    _sPO(
-      function Super() {
-        return _construct(Class, arguments, _gPO(this).constructor);
-      },
-      Class
-    )
-  );
-};
-
 babelHelpers.interopRequireDefault = function (obj) {
   return obj && obj.__esModule ? obj : {
     default: obj
@@ -188,15 +157,7 @@ babelHelpers.interopRequireWildcard = function (obj) {
 
     if (obj != null) {
       for (var key in obj) {
-        if (Object.prototype.hasOwnProperty.call(obj, key)) {
-          var desc = Object.defineProperty && Object.getOwnPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : {};
-
-          if (desc.get || desc.set) {
-            Object.defineProperty(newObj, key, desc);
-          } else {
-            newObj[key] = obj[key];
-          }
-        }
+        if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key];
       }
     }
 
@@ -205,79 +166,63 @@ babelHelpers.interopRequireWildcard = function (obj) {
   }
 };
 
-babelHelpers.objectWithoutProperties = function(source, excluded) {
-  if (source == null) return {};
+babelHelpers.objectWithoutProperties = function (obj, keys) {
   var target = {};
-  var sourceKeys = Object.keys(source);
-  var key, i;
-
-  for (i = 0; i < sourceKeys.length; i++) {
-    key = sourceKeys[i];
-    if (excluded.indexOf(key) >= 0) continue;
-    target[key] = source[key];
-  }
-
-  if (Object.getOwnPropertySymbols) {
-    var sourceSymbolKeys = Object.getOwnPropertySymbols(source);
 
-    for (i = 0; i < sourceSymbolKeys.length; i++) {
-      key = sourceSymbolKeys[i];
-      if (excluded.indexOf(key) >= 0) continue;
-      if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue;
-      target[key] = source[key];
-    }
+  for (var i in obj) {
+    if (keys.indexOf(i) >= 0) continue;
+    if (!Object.prototype.hasOwnProperty.call(obj, i)) continue;
+    target[i] = obj[i];
   }
 
   return target;
 };
 
 babelHelpers.possibleConstructorReturn = function (self, call) {
-  if (call && (typeof call === "object" || typeof call === "function")) {
-    return call;
-  }
-
-  if (self === void 0) {
+  if (!self) {
     throw new ReferenceError("this hasn't been initialised - super() hasn't been called");
   }
 
-  return self;
+  return call && (typeof call === "object" || typeof call === "function") ? call : self;
 };
 
-function _sliceIterator(arr, i) {
-  var _arr = [];
-  var _n = true;
-  var _d = false;
-  var _e = undefined;
-
-  try {
-    for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
-      _arr.push(_s.value);
+babelHelpers.slicedToArray = (function () {
+  function sliceIterator(arr, i) {
+    var _arr = [];
+    var _n = true;
+    var _d = false;
+    var _e = undefined;
 
-      if (i && _arr.length === i) break;
-    }
-  } catch (err) {
-    _d = true;
-    _e = err;
-  } finally {
     try {
-      if (!_n && _i["return"] != null) _i["return"]();
+      for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
+        _arr.push(_s.value);
+
+        if (i && _arr.length === i) break;
+      }
+    } catch (err) {
+      _d = true;
+      _e = err;
     } finally {
-      if (_d) throw _e;
+      try {
+        if (!_n && _i["return"]) _i["return"]();
+      } finally {
+        if (_d) throw _e;
+      }
     }
-  }
-
-  return _arr;
-}
 
-babelHelpers.slicedToArray = function(arr, i) {
-  if (Array.isArray(arr)) {
-    return arr;
-  } else if (Symbol.iterator in Object(arr)) {
-    return _sliceIterator(arr, i);
-  } else {
-    throw new TypeError("Invalid attempt to destructure non-iterable instance");
+    return _arr;
   }
-};
+
+  return function (arr, i) {
+    if (Array.isArray(arr)) {
+      return arr;
+    } else if (Symbol.iterator in Object(arr)) {
+      return sliceIterator(arr, i);
+    } else {
+      throw new TypeError("Invalid attempt to destructure non-iterable instance");
+    }
+  };
+})();
 
 babelHelpers.taggedTemplateLiteral = function (strings, raw) {
   return Object.freeze(Object.defineProperties(strings, {
@@ -293,25 +238,10 @@ babelHelpers.toArray = function (arr) {
 
 babelHelpers.toConsumableArray = function (arr) {
   if (Array.isArray(arr)) {
-    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) arr2[i] = arr[i];
+    for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i];
 
     return arr2;
   } else {
     return Array.from(arr);
   }
 };
-
-babelHelpers.assertThisInitialized = function(self) {
-  if (self === void 0) {
-    throw new ReferenceError(
-      "this hasn't been initialised - super() hasn't been called",
-    );
-  }
-
-  return self;
-};
-
-babelHelpers.taggedTemplateLiteralLoose = function(strings, raw) {
-  strings.raw = raw;
-  return strings;
-};
diff --git a/babel-preset/configs/main.js b/babel-preset/configs/main.js
index d17db86969f7..96405f002f95 100644
--- a/babel-preset/configs/main.js
+++ b/babel-preset/configs/main.js
@@ -8,55 +8,37 @@
 'use strict';
 
 const defaultPlugins = [
-  [require('@babel/plugin-transform-block-scoping')],
-  // the flow strip types plugin must go BEFORE class properties!
-  // there'll be a test case that fails if you don't.
-  [require('@babel/plugin-transform-flow-strip-types')],
+  [require('babel-plugin-syntax-class-properties')],
+  [require('babel-plugin-syntax-trailing-function-commas')],
+  [require('babel-plugin-transform-class-properties')],
+  [require('babel-plugin-transform-es2015-block-scoping')],
+  [require('babel-plugin-transform-es2015-computed-properties')],
+  [require('babel-plugin-transform-es2015-destructuring')],
+  [require('babel-plugin-transform-es2015-function-name')],
+  [require('babel-plugin-transform-es2015-literals')],
+  [require('babel-plugin-transform-es2015-parameters')],
+  [require('babel-plugin-transform-es2015-shorthand-properties')],
+  [require('babel-plugin-transform-flow-strip-types')],
+  [require('babel-plugin-transform-react-jsx')],
+  [require('babel-plugin-transform-regenerator')],
   [
-    require('@babel/plugin-proposal-class-properties'),
-    // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
-    // (Makes the properties enumerable)
-    {loose: true},
-  ],
-  [require('@babel/plugin-transform-computed-properties')],
-  [require('@babel/plugin-transform-destructuring')],
-  [require('@babel/plugin-transform-function-name')],
-  [require('@babel/plugin-transform-literals')],
-  [require('@babel/plugin-transform-parameters')],
-  [require('@babel/plugin-transform-shorthand-properties')],
-  [require('@babel/plugin-transform-react-jsx')],
-  [require('@babel/plugin-transform-regenerator')],
-  [require('@babel/plugin-transform-sticky-regex')],
-  [require('@babel/plugin-transform-unicode-regex')],
-  [
-    require('@babel/plugin-transform-modules-commonjs'),
-    {
-      strict: false,
-      strictMode : false, // prevent "use strict" injections
-      allowTopLevelThis: true, // dont rewrite global `this` -> `undefined`
-    },
+    require('babel-plugin-transform-es2015-modules-commonjs'),
+    {strict: false, allowTopLevelThis: true},
   ],
 ];
 
-const es2015ArrowFunctions = [
-  require('@babel/plugin-transform-arrow-functions'),
-];
-const es2015Classes = [require('@babel/plugin-transform-classes')];
-const es2015ForOf = [require('@babel/plugin-transform-for-of'), {loose: true}];
-const es2015Spread = [require('@babel/plugin-transform-spread')];
-const es2015TemplateLiterals = [
-  require('@babel/plugin-transform-template-literals'),
-  {loose: true}, // dont 'a'.concat('b'), just use 'a'+'b'
-];
-const exponentiationOperator = [
-  require('@babel/plugin-transform-exponentiation-operator'),
-];
-const objectAssign = [require('@babel/plugin-transform-object-assign')];
-const objectRestSpread = [require('@babel/plugin-proposal-object-rest-spread')];
-const reactDisplayName = [
-  require('@babel/plugin-transform-react-display-name'),
-];
-const reactJsxSource = [require('@babel/plugin-transform-react-jsx-source')];
+const checkES2015Constants = [require('babel-plugin-check-es2015-constants')];
+const es2015ArrowFunctions = [require('babel-plugin-transform-es2015-arrow-functions')];
+const es2015Classes = [require('babel-plugin-transform-es2015-classes')];
+const es2015ForOf = [require('babel-plugin-transform-es2015-for-of'), {loose: true}];
+const es2015Spread = [require('babel-plugin-transform-es2015-spread')];
+const es2015TemplateLiterals = [require('babel-plugin-transform-es2015-template-literals')];
+const asyncFunctions = [require('babel-plugin-syntax-async-functions')];
+const exponentiationOperator = [require('babel-plugin-transform-exponentiation-operator')];
+const objectAssign = [require('babel-plugin-transform-object-assign')];
+const objectRestSpread = [require('babel-plugin-transform-object-rest-spread')];
+const reactDisplayName = [require('babel-plugin-transform-react-display-name')];
+const reactJsxSource = [require('babel-plugin-transform-react-jsx-source')];
 const symbolMember = [require('../transforms/transform-symbol-member')];
 
 const getPreset = (src, options) => {
@@ -67,12 +49,18 @@ const getPreset = (src, options) => {
 
   const extraPlugins = [];
 
+  if (isNull || src.indexOf('async') !== -1 || src.indexOf('await') !== -1) {
+    extraPlugins.push(asyncFunctions);
+  }
   if (hasClass) {
     extraPlugins.push(es2015Classes);
   }
   if (isNull || src.indexOf('=>') !== -1) {
     extraPlugins.push(es2015ArrowFunctions);
   }
+  if (isNull || src.indexOf('const') !== -1) {
+    extraPlugins.push(checkES2015Constants);
+  }
   if (isNull || hasClass || src.indexOf('...') !== -1) {
     extraPlugins.push(es2015Spread);
     extraPlugins.push(objectRestSpread);
diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index a7c52411f190..e6a897f8e02a 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -11,7 +11,7 @@
 
 'use strict';
 
-const {transformSync: babelTransformSync} = require('@babel/core');
+const babel = require('babel-core');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
@@ -20,7 +20,7 @@ const babelRegisterOnly = require('metro/src/babelRegisterOnly');
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
 const createCacheKeyFunction = require('fbjs-scripts/jest/createCacheKeyFunction');
-const generate = require('@babel/generator').default;
+const generate = require('babel-generator').default;
 
 const nodeFiles = RegExp([
   '/local-cli/',
@@ -35,7 +35,7 @@ const transformer = require('metro/src/transformer.js');
 module.exports = {
   process(src/*: string*/, file/*: string*/) {
     if (nodeFiles.test(file)) { // node specific transforms only
-      return babelTransformSync(
+      return babel.transform(
         src,
         Object.assign({filename: file}, nodeOptions)
       ).code;
@@ -54,45 +54,6 @@ module.exports = {
         retainLines: true,
       },
       src,
-      plugins: [
-        [require('@babel/plugin-transform-block-scoping')],
-        // the flow strip types plugin must go BEFORE class properties!
-        // there'll be a test case that fails if you don't.
-        [require('@babel/plugin-transform-flow-strip-types')],
-        [
-          require('@babel/plugin-proposal-class-properties'),
-          // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
-          // (Makes the properties enumerable)
-          {loose: true},
-        ],
-        [require('@babel/plugin-transform-computed-properties')],
-        [require('@babel/plugin-transform-destructuring')],
-        [require('@babel/plugin-transform-function-name')],
-        [require('@babel/plugin-transform-literals')],
-        [require('@babel/plugin-transform-parameters')],
-        [require('@babel/plugin-transform-shorthand-properties')],
-        [require('@babel/plugin-transform-react-jsx')],
-        [require('@babel/plugin-transform-regenerator')],
-        [require('@babel/plugin-transform-sticky-regex')],
-        [require('@babel/plugin-transform-unicode-regex')],
-        [
-          require('@babel/plugin-transform-modules-commonjs'),
-          {strict: false, allowTopLevelThis: true},
-        ],
-        [require('@babel/plugin-transform-classes')],
-        [require('@babel/plugin-transform-arrow-functions')],
-        [require('@babel/plugin-transform-spread')],
-        [require('@babel/plugin-proposal-object-rest-spread')],
-        [
-          require('@babel/plugin-transform-template-literals'),
-          {loose: true}, // dont 'a'.concat('b'), just use 'a'+'b'
-        ],
-        [require('@babel/plugin-transform-exponentiation-operator')],
-        [require('@babel/plugin-transform-object-assign')],
-        [require('@babel/plugin-transform-for-of'), {loose: true}],
-        [require('@babel/plugin-transform-react-display-name')],
-        [require('@babel/plugin-transform-react-jsx-source')],
-      ],
     });
 
     return generate(ast, {
@@ -109,6 +70,6 @@ module.exports = {
   getCacheKey: createCacheKeyFunction([
     __filename,
     require.resolve('metro/src/transformer.js'),
-    require.resolve('@babel/core/package.json'),
+    require.resolve('babel-core/package.json'),
   ]),
 };

From fcecc1502af772c3523531b0acd5ce5845bde006 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 11 Apr 2018 08:46:10 -0700
Subject: [PATCH 0283/1109] Revert D7473762: [react-native][PR] added in
 snapAlignment for horizontal android scrollView

Differential Revision:
D7473762

Original commit changeset: ad4778b83f9f

fbshipit-source-id: 90f002ad60d26abd801a7a9d37e71254b063faef
---
 .../scroll/ReactHorizontalScrollView.java     | 21 +------------------
 .../ReactHorizontalScrollViewManager.java     |  5 -----
 2 files changed, 1 insertion(+), 25 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
index fe4762ac4a2f..90b9d1fc4d3a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
@@ -52,7 +52,6 @@ public class ReactHorizontalScrollView extends HorizontalScrollView implements
   private @Nullable Drawable mEndBackground;
   private int mEndFillColor = Color.TRANSPARENT;
   private int mSnapInterval = 0;
-  private String mSnapAlignment = "start";
   private ReactViewBackgroundManager mReactBackgroundManager;
 
   public ReactHorizontalScrollView(Context context) {
@@ -97,13 +96,6 @@ public void setPagingEnabled(boolean pagingEnabled) {
 
   public void setSnapInterval(int snapInterval) {
     mSnapInterval = snapInterval;
-    if(snapInterval != 0) {
-      mPagingEnabled = true;
-    }
-  }
-
-  public void setSnapAlignment(String snapAlignment) {
-    mSnapAlignment = snapAlignment;
   }
 
   public void flashScrollIndicators() {
@@ -244,17 +236,6 @@ private int getSnapInterval() {
     return getWidth();
   }
 
-  private int getAlignmentOffset() {
-    int width = getWidth();
-    int snapInterval = getSnapInterval();
-    if (mSnapAlignment.equals("center")) {
-      return (width - snapInterval)/2;
-    } else if(mSnapAlignment.equals("end")) {
-      return (width - snapInterval);
-    }
-    return 0;
-  }
-
   public void setEndFillColor(int color) {
     if (color != mEndFillColor) {
       mEndFillColor = color;
@@ -368,7 +349,7 @@ private void smoothScrollToPage(int velocity) {
     if (predictedX > page * width + width / 2) {
       page = page + 1;
     }
-    smoothScrollTo(page * width - getAlignmentOffset(), getScrollY());
+    smoothScrollTo(page * width, getScrollY());
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
index d5fe728c3098..e6536a6e53eb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollViewManager.java
@@ -80,11 +80,6 @@ public void setSnapToInterval(ReactHorizontalScrollView view, float snapToInterv
     view.setSnapInterval((int) (snapToInterval * screenDisplayMetrics.density));
   }
 
-  @ReactProp(name = "snapToAlignment")
-  public void setSnapToAlignment(ReactHorizontalScrollView view, String snapToAlignment) {
-    view.setSnapAlignment(snapToAlignment);
-  }
-
   @ReactProp(name = ReactClippingViewGroupHelper.PROP_REMOVE_CLIPPED_SUBVIEWS)
   public void setRemoveClippedSubviews(ReactHorizontalScrollView view, boolean removeClippedSubviews) {
     view.setRemoveClippedSubviews(removeClippedSubviews);

From 3277bed1f861e81e9066be19fabd050ffb5a6016 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Wed, 11 Apr 2018 10:38:48 -0700
Subject: [PATCH 0284/1109] Bump metro@0.32.0

Reviewed By: mjesun

Differential Revision: D7586296

fbshipit-source-id: 72407851366c5c2de15d4b3c7fe6311281d697bf
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index 4f4f55845110..df681175da83 100644
--- a/package.json
+++ b/package.json
@@ -175,8 +175,8 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.31.0",
-    "metro-core": "^0.31.0",
+    "metro": "^0.32.0",
+    "metro-core": "^0.32.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From f8d6b97140cffe8d18b2558f94570c8d1b410d5c Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Wed, 11 Apr 2018 16:29:36 -0700
Subject: [PATCH 0285/1109] BREAKING CHANGE: UPGRADE REACT NATIVE TO BABEL 7!

Summary:
BREAKING CHANGE
This change upgrades the React Native build pipeline from Babel 6 to Babel 7

If you use a `.babelrc` then you'll need to update it to Babel 7 (note that some plugins are no longer relevant, some plugins are automatically upgraded, and some will need some manual love).

Note that you may also need to upgrade your dev env, tests etc, to make sure they work with Babel 7.

Reviewed By: mjesun

Differential Revision: D7591303

fbshipit-source-id: 29cef21f6466633a9c366d1f3c0d3cf874c714db
---
 Libraries/polyfills/babelHelpers.js | 220 ++++++++++++++++++----------
 babel-preset/configs/main.js        |  78 +++++-----
 jest/preprocessor.js                |  47 +++++-
 3 files changed, 233 insertions(+), 112 deletions(-)

diff --git a/Libraries/polyfills/babelHelpers.js b/Libraries/polyfills/babelHelpers.js
index dfe819464f09..7d251ea34748 100644
--- a/Libraries/polyfills/babelHelpers.js
+++ b/Libraries/polyfills/babelHelpers.js
@@ -12,19 +12,15 @@
 /* eslint-disable quotes, curly, no-proto, no-undef-init, dot-notation */
 
 // Created by running:
-// require('babel-core').buildExternalHelpers('_extends classCallCheck createClass createRawReactElement defineProperty get inherits  interopRequireDefault interopRequireWildcard objectWithoutProperties possibleConstructorReturn slicedToArray taggedTemplateLiteral toArray toConsumableArray '.split(' '))
-// then replacing the `global` reference in the last line to also use `this`.
+// require('fs').writeFileSync('babelExternalHelpers.js', require('@babel/core').buildExternalHelpers('_extends classCallCheck createClass createRawReactElement defineProperty get inherits  interopRequireDefault interopRequireWildcard objectWithoutProperties possibleConstructorReturn slicedToArray taggedTemplateLiteral toArray toConsumableArray wrapNativeSuper assertThisInitialized taggedTemplateLiteralLoose'.split(' ')))// then replacing the `global` reference in the last line to also use `this`.
 //
-// actually, that's a lie, because babel6 omits _extends and createRawReactElement
+// Actually, that's a lie, because babel omits _extends and
+// createRawReactElement. the file is also cleaned up a bit.
+// You may need to clear wrapNativeSuper while the bug hasn't been fixed yet.
+// Do try to keep diffs to a minimum.
 
 var babelHelpers = global.babelHelpers = {};
 
-babelHelpers.typeof = typeof Symbol === "function" && typeof Symbol.iterator === "symbol" ? function (obj) {
-  return typeof obj;
-} : function (obj) {
-  return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
-};
-
 babelHelpers.createRawReactElement = (function () {
   var REACT_ELEMENT_TYPE = typeof Symbol === "function" && Symbol.for && Symbol.for("react.element") || 0xeac7;
   return function createRawReactElement(type, key, props) {
@@ -45,32 +41,20 @@ babelHelpers.classCallCheck = function (instance, Constructor) {
   }
 };
 
-babelHelpers.createClass = (function () {
-  function defineProperties(target, props) {
-    for (var i = 0; i < props.length; i++) {
-      var descriptor = props[i];
-      descriptor.enumerable = descriptor.enumerable || false;
-      descriptor.configurable = true;
-      if ("value" in descriptor) descriptor.writable = true;
-      Object.defineProperty(target, descriptor.key, descriptor);
-    }
+function _defineProperties(target, props) {
+  for (var i = 0; i < props.length; i++) {
+    var descriptor = props[i];
+    descriptor.enumerable = descriptor.enumerable || false;
+    descriptor.configurable = true;
+    if ("value" in descriptor) descriptor.writable = true;
+    Object.defineProperty(target, descriptor.key, descriptor);
   }
+}
 
-  return function (Constructor, protoProps, staticProps) {
-    if (protoProps) defineProperties(Constructor.prototype, protoProps);
-    if (staticProps) defineProperties(Constructor, staticProps);
-    return Constructor;
-  };
-})();
-
-babelHelpers.defineEnumerableProperties = function(obj, descs) {
-  for (var key in descs) {
-    var desc = descs[key];
-    desc.configurable = (desc.enumerable = true);
-    if ('value' in desc) desc.writable = true;
-    Object.defineProperty(obj, key, desc);
-  }
-  return obj;
+babelHelpers.createClass = function(Constructor, protoProps, staticProps) {
+  if (protoProps) _defineProperties(Constructor.prototype, protoProps);
+  if (staticProps) _defineProperties(Constructor, staticProps);
+  return Constructor;
 };
 
 babelHelpers.defineProperty = function (obj, key, value) {
@@ -129,9 +113,8 @@ babelHelpers.get = function get(object, property, receiver) {
 
 babelHelpers.inherits = function (subClass, superClass) {
   if (typeof superClass !== "function" && superClass !== null) {
-    throw new TypeError("Super expression must either be null or a function, not " + typeof superClass);
+    throw new TypeError("Super expression must either be null or a function");
   }
-
   subClass.prototype = Object.create(superClass && superClass.prototype, {
     constructor: {
       value: subClass,
@@ -143,6 +126,54 @@ babelHelpers.inherits = function (subClass, superClass) {
   if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass;
 };
 
+var _gPO = Object.getPrototypeOf || function _gPO(o) { return o.__proto__ };
+var _sPO = Object.setPrototypeOf || function _sPO(o, p) { o.__proto__ = p; return o };
+var _construct =
+// TODO: prepack does not like this line (and we can use the fallback just fine)
+// (typeof Reflect === "object" && Reflect.construct) ||
+  function _construct(Parent, args, Class) {
+    var Constructor, a = [null];
+    a.push.apply(a, args);
+    Constructor = Parent.bind.apply(Parent, a);
+    return _sPO(new Constructor, Class.prototype);
+  };
+var _cache = typeof Map === "function" && new Map();
+babelHelpers.wrapNativeSuper = function(Class) {
+  // FB:
+  // Note: while extending native classes is pretty meh we do have cases, for
+  // example; Error. There is also a false positive, for example; Blob.
+
+  if (typeof Class !== "function") {
+    throw new TypeError("Super expression must either be null or a function");
+  }
+  if (typeof _cache !== "undefined") {
+    if (_cache.has(Class)) return _cache.get(Class);
+    _cache.set(Class, Wrapper);
+  }
+  function Wrapper() {
+    // this is a temporary fix for a babel bug (it's invoking the wrong func
+    // when you do `super()`)
+    return _construct(Class, arguments, _gPO(this).constructor);
+  }
+  Wrapper.prototype = Object.create(Class.prototype, {
+    constructor: {
+      value: Wrapper,
+      enumerable: false,
+      writeable: true,
+      configurable: true,
+    }
+  });
+  return _sPO(
+    Wrapper,
+    _sPO(
+      function Super() {
+        return _construct(Class, arguments, _gPO(this).constructor);
+      },
+      Class
+    )
+  );
+};
+
 babelHelpers.interopRequireDefault = function (obj) {
   return obj && obj.__esModule ? obj : {
     default: obj
@@ -157,7 +188,15 @@ babelHelpers.interopRequireWildcard = function (obj) {
 
     if (obj != null) {
       for (var key in obj) {
-        if (Object.prototype.hasOwnProperty.call(obj, key)) newObj[key] = obj[key];
+        if (Object.prototype.hasOwnProperty.call(obj, key)) {
+          var desc = Object.defineProperty && Object.getOwnPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : {};
+
+          if (desc.get || desc.set) {
+            Object.defineProperty(newObj, key, desc);
+          } else {
+            newObj[key] = obj[key];
+          }
+        }
       }
     }
 
@@ -166,63 +205,79 @@ babelHelpers.interopRequireWildcard = function (obj) {
   }
 };
 
-babelHelpers.objectWithoutProperties = function (obj, keys) {
+babelHelpers.objectWithoutProperties = function(source, excluded) {
+  if (source == null) return {};
   var target = {};
+  var sourceKeys = Object.keys(source);
+  var key, i;
+
+  for (i = 0; i < sourceKeys.length; i++) {
+    key = sourceKeys[i];
+    if (excluded.indexOf(key) >= 0) continue;
+    target[key] = source[key];
+  }
+
+  if (Object.getOwnPropertySymbols) {
+    var sourceSymbolKeys = Object.getOwnPropertySymbols(source);
 
-  for (var i in obj) {
-    if (keys.indexOf(i) >= 0) continue;
-    if (!Object.prototype.hasOwnProperty.call(obj, i)) continue;
-    target[i] = obj[i];
+    for (i = 0; i < sourceSymbolKeys.length; i++) {
+      key = sourceSymbolKeys[i];
+      if (excluded.indexOf(key) >= 0) continue;
+      if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue;
+      target[key] = source[key];
+    }
   }
 
   return target;
 };
 
 babelHelpers.possibleConstructorReturn = function (self, call) {
-  if (!self) {
+  if (call && (typeof call === "object" || typeof call === "function")) {
+    return call;
+  }
+
+  if (self === void 0) {
     throw new ReferenceError("this hasn't been initialised - super() hasn't been called");
   }
 
-  return call && (typeof call === "object" || typeof call === "function") ? call : self;
+  return self;
 };
 
-babelHelpers.slicedToArray = (function () {
-  function sliceIterator(arr, i) {
-    var _arr = [];
-    var _n = true;
-    var _d = false;
-    var _e = undefined;
+function _sliceIterator(arr, i) {
+  var _arr = [];
+  var _n = true;
+  var _d = false;
+  var _e = undefined;
 
-    try {
-      for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
-        _arr.push(_s.value);
+  try {
+    for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
+      _arr.push(_s.value);
 
-        if (i && _arr.length === i) break;
-      }
-    } catch (err) {
-      _d = true;
-      _e = err;
+      if (i && _arr.length === i) break;
+    }
+  } catch (err) {
+    _d = true;
+    _e = err;
+  } finally {
+    try {
+      if (!_n && _i["return"] != null) _i["return"]();
     } finally {
-      try {
-        if (!_n && _i["return"]) _i["return"]();
-      } finally {
-        if (_d) throw _e;
-      }
+      if (_d) throw _e;
     }
-
-    return _arr;
   }
 
-  return function (arr, i) {
-    if (Array.isArray(arr)) {
-      return arr;
-    } else if (Symbol.iterator in Object(arr)) {
-      return sliceIterator(arr, i);
-    } else {
-      throw new TypeError("Invalid attempt to destructure non-iterable instance");
-    }
-  };
-})();
+  return _arr;
+}
+
+babelHelpers.slicedToArray = function(arr, i) {
+  if (Array.isArray(arr)) {
+    return arr;
+  } else if (Symbol.iterator in Object(arr)) {
+    return _sliceIterator(arr, i);
+  } else {
+    throw new TypeError("Invalid attempt to destructure non-iterable instance");
+  }
+};
 
 babelHelpers.taggedTemplateLiteral = function (strings, raw) {
   return Object.freeze(Object.defineProperties(strings, {
@@ -238,10 +293,25 @@ babelHelpers.toArray = function (arr) {
 
 babelHelpers.toConsumableArray = function (arr) {
   if (Array.isArray(arr)) {
-    for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i];
+    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) arr2[i] = arr[i];
 
     return arr2;
   } else {
     return Array.from(arr);
   }
 };
+
+babelHelpers.assertThisInitialized = function(self) {
+  if (self === void 0) {
+    throw new ReferenceError(
+      "this hasn't been initialised - super() hasn't been called",
+    );
+  }
+
+  return self;
+};
+
+babelHelpers.taggedTemplateLiteralLoose = function(strings, raw) {
+  strings.raw = raw;
+  return strings;
+};
diff --git a/babel-preset/configs/main.js b/babel-preset/configs/main.js
index 96405f002f95..d17db86969f7 100644
--- a/babel-preset/configs/main.js
+++ b/babel-preset/configs/main.js
@@ -8,37 +8,55 @@
 'use strict';
 
 const defaultPlugins = [
-  [require('babel-plugin-syntax-class-properties')],
-  [require('babel-plugin-syntax-trailing-function-commas')],
-  [require('babel-plugin-transform-class-properties')],
-  [require('babel-plugin-transform-es2015-block-scoping')],
-  [require('babel-plugin-transform-es2015-computed-properties')],
-  [require('babel-plugin-transform-es2015-destructuring')],
-  [require('babel-plugin-transform-es2015-function-name')],
-  [require('babel-plugin-transform-es2015-literals')],
-  [require('babel-plugin-transform-es2015-parameters')],
-  [require('babel-plugin-transform-es2015-shorthand-properties')],
-  [require('babel-plugin-transform-flow-strip-types')],
-  [require('babel-plugin-transform-react-jsx')],
-  [require('babel-plugin-transform-regenerator')],
+  [require('@babel/plugin-transform-block-scoping')],
+  // the flow strip types plugin must go BEFORE class properties!
+  // there'll be a test case that fails if you don't.
+  [require('@babel/plugin-transform-flow-strip-types')],
   [
-    require('babel-plugin-transform-es2015-modules-commonjs'),
-    {strict: false, allowTopLevelThis: true},
+    require('@babel/plugin-proposal-class-properties'),
+    // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
+    // (Makes the properties enumerable)
+    {loose: true},
+  ],
+  [require('@babel/plugin-transform-computed-properties')],
+  [require('@babel/plugin-transform-destructuring')],
+  [require('@babel/plugin-transform-function-name')],
+  [require('@babel/plugin-transform-literals')],
+  [require('@babel/plugin-transform-parameters')],
+  [require('@babel/plugin-transform-shorthand-properties')],
+  [require('@babel/plugin-transform-react-jsx')],
+  [require('@babel/plugin-transform-regenerator')],
+  [require('@babel/plugin-transform-sticky-regex')],
+  [require('@babel/plugin-transform-unicode-regex')],
+  [
+    require('@babel/plugin-transform-modules-commonjs'),
+    {
+      strict: false,
+      strictMode : false, // prevent "use strict" injections
+      allowTopLevelThis: true, // dont rewrite global `this` -> `undefined`
+    },
   ],
 ];
 
-const checkES2015Constants = [require('babel-plugin-check-es2015-constants')];
-const es2015ArrowFunctions = [require('babel-plugin-transform-es2015-arrow-functions')];
-const es2015Classes = [require('babel-plugin-transform-es2015-classes')];
-const es2015ForOf = [require('babel-plugin-transform-es2015-for-of'), {loose: true}];
-const es2015Spread = [require('babel-plugin-transform-es2015-spread')];
-const es2015TemplateLiterals = [require('babel-plugin-transform-es2015-template-literals')];
-const asyncFunctions = [require('babel-plugin-syntax-async-functions')];
-const exponentiationOperator = [require('babel-plugin-transform-exponentiation-operator')];
-const objectAssign = [require('babel-plugin-transform-object-assign')];
-const objectRestSpread = [require('babel-plugin-transform-object-rest-spread')];
-const reactDisplayName = [require('babel-plugin-transform-react-display-name')];
-const reactJsxSource = [require('babel-plugin-transform-react-jsx-source')];
+const es2015ArrowFunctions = [
+  require('@babel/plugin-transform-arrow-functions'),
+];
+const es2015Classes = [require('@babel/plugin-transform-classes')];
+const es2015ForOf = [require('@babel/plugin-transform-for-of'), {loose: true}];
+const es2015Spread = [require('@babel/plugin-transform-spread')];
+const es2015TemplateLiterals = [
+  require('@babel/plugin-transform-template-literals'),
+  {loose: true}, // dont 'a'.concat('b'), just use 'a'+'b'
+];
+const exponentiationOperator = [
+  require('@babel/plugin-transform-exponentiation-operator'),
+];
+const objectAssign = [require('@babel/plugin-transform-object-assign')];
+const objectRestSpread = [require('@babel/plugin-proposal-object-rest-spread')];
+const reactDisplayName = [
+  require('@babel/plugin-transform-react-display-name'),
+];
+const reactJsxSource = [require('@babel/plugin-transform-react-jsx-source')];
 const symbolMember = [require('../transforms/transform-symbol-member')];
 
 const getPreset = (src, options) => {
@@ -49,18 +67,12 @@ const getPreset = (src, options) => {
 
   const extraPlugins = [];
 
-  if (isNull || src.indexOf('async') !== -1 || src.indexOf('await') !== -1) {
-    extraPlugins.push(asyncFunctions);
-  }
   if (hasClass) {
     extraPlugins.push(es2015Classes);
   }
   if (isNull || src.indexOf('=>') !== -1) {
     extraPlugins.push(es2015ArrowFunctions);
   }
-  if (isNull || src.indexOf('const') !== -1) {
-    extraPlugins.push(checkES2015Constants);
-  }
   if (isNull || hasClass || src.indexOf('...') !== -1) {
     extraPlugins.push(es2015Spread);
     extraPlugins.push(objectRestSpread);
diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index e6a897f8e02a..a7c52411f190 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -11,7 +11,7 @@
 
 'use strict';
 
-const babel = require('babel-core');
+const {transformSync: babelTransformSync} = require('@babel/core');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
@@ -20,7 +20,7 @@ const babelRegisterOnly = require('metro/src/babelRegisterOnly');
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
 const createCacheKeyFunction = require('fbjs-scripts/jest/createCacheKeyFunction');
-const generate = require('babel-generator').default;
+const generate = require('@babel/generator').default;
 
 const nodeFiles = RegExp([
   '/local-cli/',
@@ -35,7 +35,7 @@ const transformer = require('metro/src/transformer.js');
 module.exports = {
   process(src/*: string*/, file/*: string*/) {
     if (nodeFiles.test(file)) { // node specific transforms only
-      return babel.transform(
+      return babelTransformSync(
         src,
         Object.assign({filename: file}, nodeOptions)
       ).code;
@@ -54,6 +54,45 @@ module.exports = {
         retainLines: true,
       },
       src,
+      plugins: [
+        [require('@babel/plugin-transform-block-scoping')],
+        // the flow strip types plugin must go BEFORE class properties!
+        // there'll be a test case that fails if you don't.
+        [require('@babel/plugin-transform-flow-strip-types')],
+        [
+          require('@babel/plugin-proposal-class-properties'),
+          // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
+          // (Makes the properties enumerable)
+          {loose: true},
+        ],
+        [require('@babel/plugin-transform-computed-properties')],
+        [require('@babel/plugin-transform-destructuring')],
+        [require('@babel/plugin-transform-function-name')],
+        [require('@babel/plugin-transform-literals')],
+        [require('@babel/plugin-transform-parameters')],
+        [require('@babel/plugin-transform-shorthand-properties')],
+        [require('@babel/plugin-transform-react-jsx')],
+        [require('@babel/plugin-transform-regenerator')],
+        [require('@babel/plugin-transform-sticky-regex')],
+        [require('@babel/plugin-transform-unicode-regex')],
+        [
+          require('@babel/plugin-transform-modules-commonjs'),
+          {strict: false, allowTopLevelThis: true},
+        ],
+        [require('@babel/plugin-transform-classes')],
+        [require('@babel/plugin-transform-arrow-functions')],
+        [require('@babel/plugin-transform-spread')],
+        [require('@babel/plugin-proposal-object-rest-spread')],
+        [
+          require('@babel/plugin-transform-template-literals'),
+          {loose: true}, // dont 'a'.concat('b'), just use 'a'+'b'
+        ],
+        [require('@babel/plugin-transform-exponentiation-operator')],
+        [require('@babel/plugin-transform-object-assign')],
+        [require('@babel/plugin-transform-for-of'), {loose: true}],
+        [require('@babel/plugin-transform-react-display-name')],
+        [require('@babel/plugin-transform-react-jsx-source')],
+      ],
     });
 
     return generate(ast, {
@@ -70,6 +109,6 @@ module.exports = {
   getCacheKey: createCacheKeyFunction([
     __filename,
     require.resolve('metro/src/transformer.js'),
-    require.resolve('babel-core/package.json'),
+    require.resolve('@babel/core/package.json'),
   ]),
 };

From 5001b9f39eb9c81ba9dc38ed00972954c7d325e4 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Wed, 11 Apr 2018 18:05:54 -0700
Subject: [PATCH 0286/1109] Unfork Fabric

Reviewed By: achen1, mdvacca

Differential Revision: D7582130

fbshipit-source-id: f198c63ed2fcd8619610b4b2f28276e7ffca9217
---
 Libraries/Components/View/FabricView.js       |  13 -
 .../Components/View/requireFabricView.js      |  25 --
 Libraries/ReactNative/renderFabricSurface.js  |   2 +-
 .../ReactNative/requireFabricComponent.js     | 234 ------------------
 Libraries/Text/FabricText.js                  |  13 -
 5 files changed, 1 insertion(+), 286 deletions(-)
 delete mode 100644 Libraries/Components/View/FabricView.js
 delete mode 100644 Libraries/Components/View/requireFabricView.js
 delete mode 100644 Libraries/ReactNative/requireFabricComponent.js
 delete mode 100644 Libraries/Text/FabricText.js

diff --git a/Libraries/Components/View/FabricView.js b/Libraries/Components/View/FabricView.js
deleted file mode 100644
index d56189052877..000000000000
--- a/Libraries/Components/View/FabricView.js
+++ /dev/null
@@ -1,13 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule FabricView
- * @flow
- * @format
- */
-'use strict';
-
-module.exports = require('View');
diff --git a/Libraries/Components/View/requireFabricView.js b/Libraries/Components/View/requireFabricView.js
deleted file mode 100644
index 55a7c40f4da0..000000000000
--- a/Libraries/Components/View/requireFabricView.js
+++ /dev/null
@@ -1,25 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule requireFabricView
- * @flow
- * @format
- */
-'use strict';
-
-/**
- * This is a switch on the correct view to use for Fabric
- */
-module.exports = (name: string, fabric: boolean) => {
-  switch (name) {
-    case 'View':
-      return fabric ? require('FabricView') : require('View');
-    case 'Text':
-      return fabric ? require('FabricText') : require('Text');
-    default:
-      throw new Error(name + ' is not supported by Fabric yet');
-  }
-};
diff --git a/Libraries/ReactNative/renderFabricSurface.js b/Libraries/ReactNative/renderFabricSurface.js
index 46536a755ce5..0279f1759926 100644
--- a/Libraries/ReactNative/renderFabricSurface.js
+++ b/Libraries/ReactNative/renderFabricSurface.js
@@ -34,7 +34,7 @@ function renderFabricSurface<Props: Object>(
       fabric={true}
       rootTag={rootTag}
       WrapperComponent={WrapperComponent}>
-      <RootComponent {...initialProps} rootTag={rootTag} fabric={true} />
+      <RootComponent {...initialProps} rootTag={rootTag} />
     </AppContainer>
   );
 
diff --git a/Libraries/ReactNative/requireFabricComponent.js b/Libraries/ReactNative/requireFabricComponent.js
deleted file mode 100644
index dfd02bfeb612..000000000000
--- a/Libraries/ReactNative/requireFabricComponent.js
+++ /dev/null
@@ -1,234 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule requireFabricComponent
- * @flow
- * @format
- */
-'use strict';
-
-const Platform = require('Platform');
-const {createReactNativeComponentClass} = require('ReactFabricInternals');
-const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
-const UIManager = require('UIManager');
-
-const insetsDiffer = require('insetsDiffer');
-const matricesDiffer = require('matricesDiffer');
-const pointsDiffer = require('pointsDiffer');
-const processColor = require('processColor');
-const resolveAssetSource = require('resolveAssetSource');
-const sizesDiffer = require('sizesDiffer');
-const verifyPropTypes = require('verifyPropTypes');
-const invariant = require('fbjs/lib/invariant');
-const warning = require('fbjs/lib/warning');
-
-/**
- * Used to create React components that directly wrap native component
- * implementations.  Config information is extracted from data exported from the
- * UIManager module.  You should also wrap the native component in a
- * hand-written component with full propTypes definitions and other
- * documentation - pass the hand-written component in as `componentInterface` to
- * verify all the native props are documented via `propTypes`.
- *
- * If some native props shouldn't be exposed in the wrapper interface, you can
- * pass null for `componentInterface` and call `verifyPropTypes` directly
- * with `nativePropsToIgnore`;
- *
- * Common types are lined up with the appropriate prop differs with
- * `TypeToDifferMap`.  Non-scalar types not in the map default to `deepDiffer`.
- */
-import type {ComponentInterface} from 'verifyPropTypes';
-
-let hasAttachedDefaultEventTypes: boolean = false;
-
-function requireNativeComponent(
-  viewName: string,
-  componentInterface?: ?ComponentInterface,
-  extraConfig?: ?{nativeOnly?: Object},
-): React$ComponentType<any> | string {
-  function attachDefaultEventTypes(viewConfig: any) {
-    // This is supported on UIManager platforms (ex: Android),
-    // as lazy view managers are not implemented for all platforms.
-    // See [UIManager] for details on constants and implementations.
-    if (UIManager.ViewManagerNames) {
-      // Lazy view managers enabled.
-      viewConfig = merge(viewConfig, UIManager.getDefaultEventTypes());
-    } else {
-      viewConfig.bubblingEventTypes = merge(
-        viewConfig.bubblingEventTypes,
-        UIManager.genericBubblingEventTypes,
-      );
-      viewConfig.directEventTypes = merge(
-        viewConfig.directEventTypes,
-        UIManager.genericDirectEventTypes,
-      );
-    }
-  }
-
-  function merge(destination: ?Object, source: ?Object): ?Object {
-    if (!source) {
-      return destination;
-    }
-    if (!destination) {
-      return source;
-    }
-
-    for (const key in source) {
-      if (!source.hasOwnProperty(key)) {
-        continue;
-      }
-
-      var sourceValue = source[key];
-      if (destination.hasOwnProperty(key)) {
-        const destinationValue = destination[key];
-        if (
-          typeof sourceValue === 'object' &&
-          typeof destinationValue === 'object'
-        ) {
-          sourceValue = merge(destinationValue, sourceValue);
-        }
-      }
-      destination[key] = sourceValue;
-    }
-    return destination;
-  }
-
-  // Don't load the ViewConfig from UIManager until it's needed for rendering.
-  // Lazy-loading this can help avoid Prepack deopts.
-  function getViewConfig() {
-    const viewConfig = UIManager[viewName];
-
-    invariant(
-      viewConfig != null && !viewConfig.NativeProps != null,
-      'Native component for "%s" does not exist',
-      viewName,
-    );
-
-    viewConfig.uiViewClassName = viewName;
-    viewConfig.validAttributes = {};
-
-    // ReactNative `View.propTypes` have been deprecated in favor of
-    // `ViewPropTypes`. In their place a temporary getter has been added with a
-    // deprecated warning message. Avoid triggering that warning here by using
-    // temporary workaround, __propTypesSecretDontUseThesePlease.
-    // TODO (bvaughn) Revert this particular change any time after April 1
-    if (componentInterface) {
-      viewConfig.propTypes =
-        /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
-         * error found when Flow v0.68 was deployed. To see the error delete
-         * this comment and run Flow. */
-        typeof componentInterface.__propTypesSecretDontUseThesePlease ===
-        'object'
-          ? componentInterface.__propTypesSecretDontUseThesePlease
-          : componentInterface.propTypes;
-    } else {
-      viewConfig.propTypes = null;
-    }
-
-    let baseModuleName = viewConfig.baseModuleName;
-    let bubblingEventTypes = viewConfig.bubblingEventTypes;
-    let directEventTypes = viewConfig.directEventTypes;
-    let nativeProps = viewConfig.NativeProps;
-    while (baseModuleName) {
-      const baseModule = UIManager[baseModuleName];
-      if (!baseModule) {
-        warning(false, 'Base module "%s" does not exist', baseModuleName);
-        baseModuleName = null;
-      } else {
-        bubblingEventTypes = {
-          ...baseModule.bubblingEventTypes,
-          ...bubblingEventTypes,
-        };
-        directEventTypes = {
-          ...baseModule.directEventTypes,
-          ...directEventTypes,
-        };
-        nativeProps = {
-          ...baseModule.NativeProps,
-          ...nativeProps,
-        };
-        baseModuleName = baseModule.baseModuleName;
-      }
-    }
-
-    viewConfig.bubblingEventTypes = bubblingEventTypes;
-    viewConfig.directEventTypes = directEventTypes;
-
-    for (const key in nativeProps) {
-      let useAttribute = false;
-      const attribute = {};
-
-      const differ = TypeToDifferMap[nativeProps[key]];
-      if (differ) {
-        attribute.diff = differ;
-        useAttribute = true;
-      }
-
-      const processor = TypeToProcessorMap[nativeProps[key]];
-      if (processor) {
-        attribute.process = processor;
-        useAttribute = true;
-      }
-
-      viewConfig.validAttributes[key] = useAttribute ? attribute : true;
-    }
-
-    // Unfortunately, the current set up puts the style properties on the top
-    // level props object. We also need to add the nested form for API
-    // compatibility. This allows these props on both the top level and the
-    // nested style level. TODO: Move these to nested declarations on the
-    // native side.
-    viewConfig.validAttributes.style = ReactNativeStyleAttributes;
-
-    if (__DEV__) {
-      componentInterface &&
-        verifyPropTypes(
-          componentInterface,
-          viewConfig,
-          extraConfig && extraConfig.nativeOnly,
-        );
-    }
-
-    if (!hasAttachedDefaultEventTypes) {
-      attachDefaultEventTypes(viewConfig);
-      hasAttachedDefaultEventTypes = true;
-    }
-
-    return viewConfig;
-  }
-
-  return createReactNativeComponentClass(viewName, getViewConfig);
-}
-
-const TypeToDifferMap = {
-  // iOS Types
-  CATransform3D: matricesDiffer,
-  CGPoint: pointsDiffer,
-  CGSize: sizesDiffer,
-  UIEdgeInsets: insetsDiffer,
-  // Android Types
-  // (not yet implemented)
-};
-
-function processColorArray(colors: ?Array<any>): ?Array<?number> {
-  return colors && colors.map(processColor);
-}
-
-const TypeToProcessorMap = {
-  // iOS Types
-  CGColor: processColor,
-  CGColorArray: processColorArray,
-  UIColor: processColor,
-  UIColorArray: processColorArray,
-  CGImage: resolveAssetSource,
-  UIImage: resolveAssetSource,
-  RCTImageSource: resolveAssetSource,
-  // Android Types
-  Color: processColor,
-  ColorArray: processColorArray,
-};
-
-module.exports = requireNativeComponent;
diff --git a/Libraries/Text/FabricText.js b/Libraries/Text/FabricText.js
deleted file mode 100644
index 2b6748749b7e..000000000000
--- a/Libraries/Text/FabricText.js
+++ /dev/null
@@ -1,13 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule FabricText
- * @flow
- * @format
- */
-'use strict';
-
-module.exports = require('Text');

From 88139eb6e18ec268b1ba1e4f373992be33b5aae7 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Thu, 12 Apr 2018 09:50:55 -0700
Subject: [PATCH 0287/1109] rename unmountComponentAtNodeAndRemoveContainer ->
 unmountComponentAtNode

Reviewed By: achen1

Differential Revision: D7597730

fbshipit-source-id: d72a138b3fc82b09ab7b871089356d38c8405631
---
 .../src/main/java/com/facebook/react/ReactInstanceManager.java  | 2 +-
 .../java/com/facebook/react/modules/fabric/ReactFabric.java     | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index d2dbda4dd6d9..250f2091af72 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -1033,7 +1033,7 @@ private void detachViewFromInstance(
     UiThreadUtil.assertOnUiThread();
     if (rootView.isFabric()) {
       catalystInstance.getJSModule(ReactFabric.class)
-        .unmountComponentAtNodeAndRemoveContainer(rootView.getId());
+        .unmountComponentAtNode(rootView.getId());
     } else {
       catalystInstance.getJSModule(AppRegistry.class)
         .unmountApplicationComponentAtRootTag(rootView.getId());
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/fabric/ReactFabric.java b/ReactAndroid/src/main/java/com/facebook/react/modules/fabric/ReactFabric.java
index 888e9bafda3e..fd0896bdd6fd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/fabric/ReactFabric.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/fabric/ReactFabric.java
@@ -13,6 +13,6 @@ public interface ReactFabric extends JavaScriptModule {
    * JS method used to unmount Fabric surfaces.
    * @param rootTag {@link int} react tag of Root {@link com.facebook.react.uimanager.ReactShadowNode}
    */
-  void unmountComponentAtNodeAndRemoveContainer(int rootTag);
+  void unmountComponentAtNode(int rootTag);
 
 }

From 4fbd244b9a6b62e0efe1b4b5a7ec3de468f020f6 Mon Sep 17 00:00:00 2001
From: Aaron Brager <getaaron@gmail.com>
Date: Thu, 12 Apr 2018 11:40:33 -0700
Subject: [PATCH 0288/1109] Suggest git apply --reject for failed upgrades

Summary:
The upgrade script uses `git apply --3way`:

https://github.com/facebook/react-native/blob/4906f8d28cdbaf1b432494b473a4c61c1e193881/react-native-git-upgrade/cliEntry.js#L368-L369

If you've already upgraded something that React Native upgraded, this will silently fail. For example if you have already upgraded Gradle to the version available in the new version of React Native, the 3-way patch will fail. In this case, the upgraded version is installed into `node_modules` but `package.json` is not updated. More context, discussion, and information is in https://github.com/facebook/react-native/issues/12112#issuecomment-292619346.

Until a more robust solution is implemented, this PR proposes to mitigate the effects of the problem by informing the user of the possible issue and instructing them of a workaround.

In an affected project, I ran `react-native-git-upgrade` after applying my patch.

As expected, I now receive the following output:

![image](https://user-images.githubusercontent.com/789577/38165770-6209ac68-34de-11e8-9d96-7c782e9ef7ce.png)

After running the suggested command, `git status` now shows me the two rejections:

![image](https://user-images.githubusercontent.com/789577/38165796-d10ca7c8-34de-11e8-9037-8427513e3a84.png)

And I can now [manually apply](https://stackoverflow.com/a/28569128/1445366) these changes.

[CLI] [ENHANCEMENT] [react-native-git-upgrade/cliEntry.js] - Provide instructions for upgrading React Native when 3-way merges don't apply
Closes https://github.com/facebook/react-native/pull/18636

Differential Revision: D7603073

Pulled By: hramos

fbshipit-source-id: 32d387e1ee67d8b182d248c585cd33ba94808357
---
 react-native-git-upgrade/cliEntry.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/react-native-git-upgrade/cliEntry.js b/react-native-git-upgrade/cliEntry.js
index a9cbfa5641f3..49f9d53b4807 100644
--- a/react-native-git-upgrade/cliEntry.js
+++ b/react-native-git-upgrade/cliEntry.js
@@ -376,7 +376,9 @@ async function run(requestedVersion, cliArgs) {
     } catch (err) {
       log.warn(
         'The upgrade process succeeded but there might be conflicts to be resolved. ' +
-        'See above for the list of files that have merge conflicts.');
+        'See above for the list of files that have merge conflicts. ' +
+        'If you don’t see the expected changes, try running:\n' +
+        `git apply --reject ${patchPath}`);
     } finally {
       log.info('Upgrade done');
       if (cliArgs.verbose) {

From f6e2f13f4b8c92e96c6fd72b910341240a7d84a3 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Leo=20Nikkil=C3=A4?= <hello@lnikki.la>
Date: Thu, 12 Apr 2018 13:44:45 -0700
Subject: [PATCH 0289/1109] Handle layout updates during LayoutAnimation
 animations on Android
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
On Android, LayoutAnimation directly updates the layout since a generic
scaling animation is more difficult to implement. This causes a problem
if the layout is updated during an animation, as the previous layout is
stored with the animation and is not updated. As a result the view gets
the old layout instead once the animation completes.

This commit fixes this issue by storing the layout handling animations
while those animations are active, and updating the animations on the
fly if one of the views receives a new layout. The resulting behaviour
mirrors what iOS currently does.

This bug has real world consequences, for example if a LayoutAnimation
happens right after a VirtualizedList has mounted, it’s possible that
some list rows are mounted while the animation is active, making the
list content view bigger. If the content view is being animated, the
new size will not take effect and it becomes impossible to scroll to
the end of the list.

I wrote a minimal test case to verify the bug, which I’ve also added to
RNTester. You can find the standalone app here:

<https://gist.github.com/lnikkila/18096c15b2fb99b232795ef59f8fb0cd>

The app creates a 100x300 view that gets animated to 200x300 using
LayoutAnimation. In the middle of that animation, the view’s dimensions
are updated to 300x300.

The expected result (which is currently exhibited by iOS) is that the
view’s dimensions after the animation would be 300x300. On Android the
view keeps the 200x300 dimensions since the animation overrides the
layout update.

The test app could probably be turned into an integration test by
measuring the view through UIManager after the animation, however I
don’t have time to do that right now...

Here are some GIFs to compare, click to expand:

<details>
  <summary><b>Current master (iOS vs Android)</b></summary>
  <p></p>
  <img src="https://user-images.githubusercontent.com/1291143/38191325-f1aeb3d4-3670-11e8-8aca-14e7b24e2946.gif" height="400" /><img src="https://user-images.githubusercontent.com/1291143/38191337-f643fd8c-3670-11e8-9aac-531a32cc0a67.gif" height="400" />
</details><p></p>

<details>
  <summary><b>With this patch (iOS vs Android, fixed)</b></summary>
  <p></p>
  <img src="https://user-images.githubusercontent.com/1291143/38191325-f1aeb3d4-3670-11e8-8aca-14e7b24e2946.gif" height="400" /><img src="https://user-images.githubusercontent.com/1291143/38191355-07f6e972-3671-11e8-8ad2-130d06d0d64d.gif" height="400" />
</details><p></p>

No documentation changes needed.

[ANDROID] [BUGFIX] [LayoutAnimation] - View layout is updated correctly during an ongoing LayoutAnimation, mirroring iOS behaviour.
Closes https://github.com/facebook/react-native/pull/18651

Differential Revision: D7604698

Pulled By: hramos

fbshipit-source-id: 4d114682fd540419b7447e999910e05726f42b39
---
 RNTester/js/LayoutAnimationExample.js         | 56 +++++++++++++++++++
 .../layoutanimation/HandlesLayout.java        | 10 ----
 .../LayoutAnimationController.java            | 36 +++++++++++-
 .../LayoutHandlingAnimation.java              | 20 +++++++
 .../PositionAndSizeAnimation.java             | 36 +++++++-----
 5 files changed, 133 insertions(+), 25 deletions(-)
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/HandlesLayout.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutHandlingAnimation.java

diff --git a/RNTester/js/LayoutAnimationExample.js b/RNTester/js/LayoutAnimationExample.js
index 92134409879a..d815712bba4f 100644
--- a/RNTester/js/LayoutAnimationExample.js
+++ b/RNTester/js/LayoutAnimationExample.js
@@ -102,6 +102,57 @@ class CrossFadeExample extends React.Component<{}, $FlowFixMeState> {
   }
 }
 
+class LayoutUpdateExample extends React.Component<{}, $FlowFixMeState> {
+  state = {
+    width: 200,
+    height: 100,
+  };
+
+  timeout = null;
+
+  componentWillUnmount() {
+    this._clearTimeout();
+  }
+
+  _clearTimeout = () => {
+    if (this.timeout !== null) {
+      clearTimeout(this.timeout);
+      this.timeout = null;
+    }
+  }
+
+  _onPressToggle = () => {
+    this._clearTimeout();
+    this.setState({width: 150});
+
+    LayoutAnimation.configureNext({
+      duration: 1000,
+      update: {
+        type: LayoutAnimation.Types.linear,
+      },
+    });
+
+    this.timeout = setTimeout(() => this.setState({width: 100}), 500);
+  };
+
+  render() {
+    const {width, height} = this.state;
+
+    return (
+      <View style={styles.container}>
+        <TouchableOpacity onPress={this._onPressToggle}>
+          <View style={styles.button}>
+            <Text>Make box square</Text>
+          </View>
+        </TouchableOpacity>
+        <View style={[styles.view, {width, height}]}>
+          <Text>{width}x{height}</Text>
+        </View>
+      </View>
+    );
+  }
+}
+
 const styles = StyleSheet.create({
   container: {
     flex: 1,
@@ -156,4 +207,9 @@ exports.examples = [{
   render(): React.Element<any> {
     return <CrossFadeExample />;
   },
+}, {
+  title: 'Layout update during animation',
+  render(): React.Element<any> {
+    return <LayoutUpdateExample />;
+  },
 }];
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/HandlesLayout.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/HandlesLayout.java
deleted file mode 100644
index 9f3c907e97d0..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/HandlesLayout.java
+++ /dev/null
@@ -1,10 +0,0 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
-package com.facebook.react.uimanager.layoutanimation;
-
-/**
- * Marker interface to indicate a given animation type takes care of updating the view layout.
- */
-/* package */ interface HandleLayout {
-
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationController.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationController.java
index d5a08e6b264a..7c88514f9003 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationController.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationController.java
@@ -5,6 +5,7 @@
 import javax.annotation.Nullable;
 import javax.annotation.concurrent.NotThreadSafe;
 
+import android.util.SparseArray;
 import android.view.View;
 import android.view.ViewGroup;
 import android.view.animation.Animation;
@@ -27,6 +28,7 @@ public class LayoutAnimationController {
   private final AbstractLayoutAnimation mLayoutCreateAnimation = new LayoutCreateAnimation();
   private final AbstractLayoutAnimation mLayoutUpdateAnimation = new LayoutUpdateAnimation();
   private final AbstractLayoutAnimation mLayoutDeleteAnimation = new LayoutDeleteAnimation();
+  private final SparseArray<LayoutHandlingAnimation> mLayoutHandlers = new SparseArray<>(0);
   private boolean mShouldAnimateLayout;
 
   public void initializeFromConfig(final @Nullable ReadableMap config) {
@@ -68,7 +70,10 @@ public void reset() {
   public boolean shouldAnimateLayout(View viewToAnimate) {
     // if view parent is null, skip animation: view have been clipped, we don't want animation to
     // resume when view is re-attached to parent, which is the standard android animation behavior.
-    return mShouldAnimateLayout && viewToAnimate.getParent() != null;
+    // If there's a layout handling animation going on, it should be animated nonetheless since the
+    // ongoing animation needs to be updated.
+    return (mShouldAnimateLayout && viewToAnimate.getParent() != null)
+      || mLayoutHandlers.get(viewToAnimate.getId()) != null;
   }
 
   /**
@@ -85,6 +90,16 @@ public boolean shouldAnimateLayout(View viewToAnimate) {
   public void applyLayoutUpdate(View view, int x, int y, int width, int height) {
     UiThreadUtil.assertOnUiThread();
 
+    final int reactTag = view.getId();
+    LayoutHandlingAnimation existingAnimation = mLayoutHandlers.get(reactTag);
+
+    // Update an ongoing animation if possible, otherwise the layout update would be ignored as
+    // the existing animation would still animate to the old layout.
+    if (existingAnimation != null) {
+      existingAnimation.onLayoutUpdate(x, y, width, height);
+      return;
+    }
+
     // Determine which animation to use : if view is initially invisible, use create animation,
     // otherwise use update animation. This approach is easier than maintaining a list of tags
     // for recently created views.
@@ -93,9 +108,26 @@ public void applyLayoutUpdate(View view, int x, int y, int width, int height) {
         mLayoutUpdateAnimation;
 
     Animation animation = layoutAnimation.createAnimation(view, x, y, width, height);
-    if (animation == null || !(animation instanceof HandleLayout)) {
+
+    if (animation instanceof LayoutHandlingAnimation) {
+      animation.setAnimationListener(new Animation.AnimationListener() {
+        @Override
+        public void onAnimationStart(Animation animation) {
+          mLayoutHandlers.put(reactTag, (LayoutHandlingAnimation) animation);
+        }
+
+        @Override
+        public void onAnimationEnd(Animation animation) {
+          mLayoutHandlers.remove(reactTag);
+        }
+
+        @Override
+        public void onAnimationRepeat(Animation animation) {}
+      });
+    } else {
       view.layout(x, y, x + width, y + height);
     }
+
     if (animation != null) {
       view.startAnimation(animation);
     }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutHandlingAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutHandlingAnimation.java
new file mode 100644
index 000000000000..69234e27029a
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutHandlingAnimation.java
@@ -0,0 +1,20 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+package com.facebook.react.uimanager.layoutanimation;
+
+/**
+ * Interface for an animation type that takes care of updating the view layout.
+ */
+/* package */ interface LayoutHandlingAnimation {
+    /**
+     * Notifies the animation of a layout update in case one occurs during the animation. This
+     * avoids animating the view to the old layout since it's no longer correct; instead the
+     * animation should update and do whatever it can so that the final layout is correct.
+     *
+     * @param x the new X position for the view
+     * @param y the new Y position for the view
+     * @param width the new width value for the view
+     * @param height the new height value for the view
+     */
+    void onLayoutUpdate(int x, int y, int width, int height);
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/PositionAndSizeAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/PositionAndSizeAnimation.java
index 1cb3e83ac6f8..9bce9f781627 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/PositionAndSizeAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/PositionAndSizeAnimation.java
@@ -12,24 +12,15 @@
  * layout passes occurring on every frame.
  * What we might want to try to do instead is use a combined ScaleAnimation and TranslateAnimation.
  */
-/* package */ class PositionAndSizeAnimation extends Animation implements HandleLayout {
+/* package */ class PositionAndSizeAnimation extends Animation implements LayoutHandlingAnimation {
 
   private final View mView;
-  private final float mStartX, mStartY, mDeltaX, mDeltaY;
-  private final int mStartWidth, mStartHeight, mDeltaWidth, mDeltaHeight;
+  private float mStartX, mStartY, mDeltaX, mDeltaY;
+  private int mStartWidth, mStartHeight, mDeltaWidth, mDeltaHeight;
 
   public PositionAndSizeAnimation(View view, int x, int y, int width, int height) {
     mView = view;
-
-    mStartX = view.getX() - view.getTranslationX();
-    mStartY = view.getY() - view.getTranslationY();
-    mStartWidth = view.getWidth();
-    mStartHeight = view.getHeight();
-
-    mDeltaX = x - mStartX;
-    mDeltaY = y - mStartY;
-    mDeltaWidth = width - mStartWidth;
-    mDeltaHeight = height - mStartHeight;
+    calculateAnimation(x, y, width, height);
   }
 
   @Override
@@ -45,8 +36,27 @@ protected void applyTransformation(float interpolatedTime, Transformation t) {
         Math.round(newY + newHeight));
   }
 
+  @Override
+  public void onLayoutUpdate(int x, int y, int width, int height) {
+    // Layout changed during the animation, we should update our values so that the final layout
+    // is correct.
+    calculateAnimation(x, y, width, height);
+  }
+
   @Override
   public boolean willChangeBounds() {
     return true;
   }
+
+  private void calculateAnimation(int x, int y, int width, int height) {
+    mStartX = mView.getX() - mView.getTranslationX();
+    mStartY = mView.getY() - mView.getTranslationY();
+    mStartWidth = mView.getWidth();
+    mStartHeight = mView.getHeight();
+
+    mDeltaX = x - mStartX;
+    mDeltaY = y - mStartY;
+    mDeltaWidth = width - mStartWidth;
+    mDeltaHeight = height - mStartHeight;
+  }
 }

From 3e92073afc16b79a97ca050a969bb973da87a129 Mon Sep 17 00:00:00 2001
From: Jakub Grzmiel <jakubgr@fb.com>
Date: Thu, 12 Apr 2018 14:19:28 -0700
Subject: [PATCH 0290/1109] Handle processColor in routes

Reviewed By: shergin

Differential Revision: D6646858

fbshipit-source-id: c709464699482ef0c0b77434560612b99716074f
---
 Libraries/{StyleSheet => Color}/normalizeColor.js | 0
 Libraries/Color/package.json                      | 5 +++++
 2 files changed, 5 insertions(+)
 rename Libraries/{StyleSheet => Color}/normalizeColor.js (100%)
 create mode 100644 Libraries/Color/package.json

diff --git a/Libraries/StyleSheet/normalizeColor.js b/Libraries/Color/normalizeColor.js
similarity index 100%
rename from Libraries/StyleSheet/normalizeColor.js
rename to Libraries/Color/normalizeColor.js
diff --git a/Libraries/Color/package.json b/Libraries/Color/package.json
new file mode 100644
index 000000000000..1781e2e3d60b
--- /dev/null
+++ b/Libraries/Color/package.json
@@ -0,0 +1,5 @@
+{
+  "name": "Color",
+  "private": true,
+  "version": "0.0.0"
+}

From e636eb60d7c8cff3a73183e02d9d457d32a6ec53 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 12 Apr 2018 15:54:36 -0700
Subject: [PATCH 0291/1109] iOS OSS: added CocoaPods setup to RNTester and fix
 up the podspecs

Summary:
This adds a way to test out CocoaPods build to RNTester, but as a separate project/workspace.
This also fixes the podspecs due to Fabric stuffs.

Note that this setup is meant to be run manually, not by CI (yet)

Reviewed By: mmmulani

Differential Revision: D7603823

fbshipit-source-id: 2219aa4c77f40ec07097a5c9ed4052529226618b
---
 RNTester/.gitignore                           |   2 +
 RNTester/Podfile                              |  36 +
 RNTester/README.md                            |   8 +
 .../RNTesterPods.xcodeproj/project.pbxproj    | 729 ++++++++++++++++++
 React.podspec                                 |   9 +-
 5 files changed, 783 insertions(+), 1 deletion(-)
 create mode 100644 RNTester/.gitignore
 create mode 100644 RNTester/Podfile
 create mode 100644 RNTester/RNTesterPods.xcodeproj/project.pbxproj

diff --git a/RNTester/.gitignore b/RNTester/.gitignore
new file mode 100644
index 000000000000..003be3341c3e
--- /dev/null
+++ b/RNTester/.gitignore
@@ -0,0 +1,2 @@
+Podfile.lock
+Pods/
diff --git a/RNTester/Podfile b/RNTester/Podfile
new file mode 100644
index 000000000000..1bcd939928b8
--- /dev/null
+++ b/RNTester/Podfile
@@ -0,0 +1,36 @@
+platform :ios, '8.0'
+
+target 'RNTester' do
+  # Uncomment for Swift
+  # use_frameworks!
+
+  project 'RNTesterPods.xcodeproj'
+
+  pod 'React', :path => '../', :subspecs => [
+    'ART',
+    'Core',
+    'CxxBridge',
+    'DevSupport',
+    'RCTActionSheet',
+    'RCTAnimation',
+    'RCTBlob',
+    'RCTCameraRoll',
+    'RCTGeolocation',
+    'RCTImage',
+    'RCTLinkingIOS',
+    'RCTNetwork',
+    'RCTPushNotification',
+    'RCTSettings',
+    'RCTText',
+    'RCTVibration',
+    'RCTWebSocket',
+  ]
+
+  pod 'yoga', :path => '../ReactCommon/yoga'
+
+  # Third party deps podspec link
+  pod 'DoubleConversion', :podspec => '../third-party-podspecs/DoubleConversion.podspec'
+  pod 'glog', :podspec => '../third-party-podspecs/glog.podspec'
+  pod 'Folly', :podspec => '../third-party-podspecs/Folly.podspec'
+
+end
diff --git a/RNTester/README.md b/RNTester/README.md
index 2b5642852f2e..b612a321532f 100644
--- a/RNTester/README.md
+++ b/RNTester/README.md
@@ -19,6 +19,14 @@ Mac OS and Xcode are required.
 
 See [Running on device](https://facebook.github.io/react-native/docs/running-on-device.html) if you want to use a physical device.
 
+### Running on iOS with CocoaPods
+
+Similar to above, you can build the app via Xcode with help of CocoaPods.
+
+- Install [CocoaPods](http://facebook.github.io/react-native/docs/integration-with-existing-apps.html#3-install-cocoapods)
+- Run `cd RNTester; pod install`
+- Open the generated `RNTesterPods.xcworkspace` (this is not checked in). Do not open `RNTesterPods.xcodeproj` directly.
+
 ### Running on Android
 
 You'll need to have all the [prerequisites](https://github.com/facebook/react-native/tree/master/ReactAndroid#prerequisites) (SDK, NDK) for Building React Native installed.
diff --git a/RNTester/RNTesterPods.xcodeproj/project.pbxproj b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
new file mode 100644
index 000000000000..054c9cc2e7e5
--- /dev/null
+++ b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
@@ -0,0 +1,729 @@
+// !$*UTF8*$!
+{
+	archiveVersion = 1;
+	classes = {
+	};
+	objectVersion = 46;
+	objects = {
+
+/* Begin PBXBuildFile section */
+		13B07FBC1A68108700A75B9A /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 13B07FB01A68108700A75B9A /* AppDelegate.m */; };
+		13B07FBD1A68108700A75B9A /* LaunchScreen.xib in Resources */ = {isa = PBXBuildFile; fileRef = 13B07FB11A68108700A75B9A /* LaunchScreen.xib */; };
+		13B07FC11A68108700A75B9A /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = 13B07FB71A68108700A75B9A /* main.m */; };
+		272E6B3F1BEA849E001FCF37 /* UpdatePropertiesExampleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 272E6B3C1BEA849E001FCF37 /* UpdatePropertiesExampleView.m */; };
+		27F441EC1BEBE5030039B79C /* FlexibleSizeExampleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 27F441E81BEBE5030039B79C /* FlexibleSizeExampleView.m */; };
+		2DD323DC1DA2DDBF000FE1B8 /* FlexibleSizeExampleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 27F441E81BEBE5030039B79C /* FlexibleSizeExampleView.m */; };
+		2DD323DD1DA2DDBF000FE1B8 /* UpdatePropertiesExampleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 272E6B3C1BEA849E001FCF37 /* UpdatePropertiesExampleView.m */; };
+		2DD323DE1DA2DDBF000FE1B8 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 13B07FB01A68108700A75B9A /* AppDelegate.m */; };
+		2DD323E01DA2DDBF000FE1B8 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = 13B07FB71A68108700A75B9A /* main.m */; };
+		2DD323E11DA2DDBF000FE1B8 /* legacy_image@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = 3D2AFAF41D646CF80089D1A3 /* legacy_image@2x.png */; };
+		2DD323E21DA2DDBF000FE1B8 /* Info.plist in Resources */ = {isa = PBXBuildFile; fileRef = 13B07FB61A68108700A75B9A /* Info.plist */; };
+		2DDEF0101F84BF7B00DBDF73 /* Images.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2DDEF00F1F84BF7B00DBDF73 /* Images.xcassets */; };
+		3D13F8481D6F6AF900E69E0E /* ImageInBundle.png in Resources */ = {isa = PBXBuildFile; fileRef = 3D13F8441D6F6AF200E69E0E /* ImageInBundle.png */; };
+		3D13F84A1D6F6AFD00E69E0E /* OtherImages.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 3D13F8451D6F6AF200E69E0E /* OtherImages.xcassets */; };
+		3D2AFAF51D646CF80089D1A3 /* legacy_image@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = 3D2AFAF41D646CF80089D1A3 /* legacy_image@2x.png */; };
+		3D56F9F11D6F6E9B00F53A06 /* RNTesterBundle.bundle in Resources */ = {isa = PBXBuildFile; fileRef = 3D13F83E1D6F6AE000E69E0E /* RNTesterBundle.bundle */; };
+		EC31D453B972BC46FE559C89 /* libPods-RNTester.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 6C062A1C08AD9375355BE47F /* libPods-RNTester.a */; };
+/* End PBXBuildFile section */
+
+/* Begin PBXContainerItemProxy section */
+		143BC59B1B21E3E100462512 /* PBXContainerItemProxy */ = {
+			isa = PBXContainerItemProxy;
+			containerPortal = 83CBB9F71A601CBA00E9B192 /* Project object */;
+			proxyType = 1;
+			remoteGlobalIDString = 13B07F861A680F5B00A75B9A;
+			remoteInfo = RNTester;
+		};
+		3D13F84B1D6F6B5F00E69E0E /* PBXContainerItemProxy */ = {
+			isa = PBXContainerItemProxy;
+			containerPortal = 83CBB9F71A601CBA00E9B192 /* Project object */;
+			proxyType = 1;
+			remoteGlobalIDString = 3D13F83D1D6F6AE000E69E0E;
+			remoteInfo = RNTesterBundle;
+		};
+/* End PBXContainerItemProxy section */
+
+/* Begin PBXFileReference section */
+		13B07F961A680F5B00A75B9A /* RNTester.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = RNTester.app; sourceTree = BUILT_PRODUCTS_DIR; };
+		13B07FAF1A68108700A75B9A /* AppDelegate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = AppDelegate.h; path = RNTester/AppDelegate.h; sourceTree = "<group>"; };
+		13B07FB01A68108700A75B9A /* AppDelegate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = AppDelegate.m; path = RNTester/AppDelegate.m; sourceTree = "<group>"; };
+		13B07FB21A68108700A75B9A /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/LaunchScreen.xib; sourceTree = "<group>"; };
+		13B07FB61A68108700A75B9A /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; name = Info.plist; path = RNTester/Info.plist; sourceTree = "<group>"; };
+		13B07FB71A68108700A75B9A /* main.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = main.m; path = RNTester/main.m; sourceTree = "<group>"; };
+		272E6B3B1BEA849E001FCF37 /* UpdatePropertiesExampleView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = UpdatePropertiesExampleView.h; path = RNTester/NativeExampleViews/UpdatePropertiesExampleView.h; sourceTree = "<group>"; };
+		272E6B3C1BEA849E001FCF37 /* UpdatePropertiesExampleView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = UpdatePropertiesExampleView.m; path = RNTester/NativeExampleViews/UpdatePropertiesExampleView.m; sourceTree = "<group>"; };
+		27F441E81BEBE5030039B79C /* FlexibleSizeExampleView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = FlexibleSizeExampleView.m; path = RNTester/NativeExampleViews/FlexibleSizeExampleView.m; sourceTree = "<group>"; };
+		27F441EA1BEBE5030039B79C /* FlexibleSizeExampleView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = FlexibleSizeExampleView.h; path = RNTester/NativeExampleViews/FlexibleSizeExampleView.h; sourceTree = "<group>"; };
+		2DDEF00F1F84BF7B00DBDF73 /* Images.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; name = Images.xcassets; path = RNTester/Images.xcassets; sourceTree = "<group>"; };
+		3D13F83E1D6F6AE000E69E0E /* RNTesterBundle.bundle */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = RNTesterBundle.bundle; sourceTree = BUILT_PRODUCTS_DIR; };
+		3D13F8401D6F6AE000E69E0E /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; name = Info.plist; path = ../Info.plist; sourceTree = "<group>"; };
+		3D13F8441D6F6AF200E69E0E /* ImageInBundle.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = ImageInBundle.png; sourceTree = "<group>"; };
+		3D13F8451D6F6AF200E69E0E /* OtherImages.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = OtherImages.xcassets; sourceTree = "<group>"; };
+		3D2AFAF41D646CF80089D1A3 /* legacy_image@2x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "legacy_image@2x.png"; path = "RNTester/legacy_image@2x.png"; sourceTree = "<group>"; };
+		5BEC8567F3741044B6A5EFC5 /* Pods-RNTester.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-RNTester.release.xcconfig"; path = "Pods/Target Support Files/Pods-RNTester/Pods-RNTester.release.xcconfig"; sourceTree = "<group>"; };
+		6C062A1C08AD9375355BE47F /* libPods-RNTester.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = "libPods-RNTester.a"; sourceTree = BUILT_PRODUCTS_DIR; };
+		98233960D1D6A1977D1C7EAF /* Pods-RNTester.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-RNTester.debug.xcconfig"; path = "Pods/Target Support Files/Pods-RNTester/Pods-RNTester.debug.xcconfig"; sourceTree = "<group>"; };
+/* End PBXFileReference section */
+
+/* Begin PBXFrameworksBuildPhase section */
+		004D289B1AAF61C70097A701 /* Frameworks */ = {
+			isa = PBXFrameworksBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		13B07F8C1A680F5B00A75B9A /* Frameworks */ = {
+			isa = PBXFrameworksBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				EC31D453B972BC46FE559C89 /* libPods-RNTester.a in Frameworks */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		143BC5921B21E3E100462512 /* Frameworks */ = {
+			isa = PBXFrameworksBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2D4624D91DA2EA6900C74D09 /* Frameworks */ = {
+			isa = PBXFrameworksBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2DD3238D1DA2DD8A000FE1B8 /* Frameworks */ = {
+			isa = PBXFrameworksBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2DD323A21DA2DD8B000FE1B8 /* Frameworks */ = {
+			isa = PBXFrameworksBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		3D13F83B1D6F6AE000E69E0E /* Frameworks */ = {
+			isa = PBXFrameworksBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+/* End PBXFrameworksBuildPhase section */
+
+/* Begin PBXGroup section */
+		1323F18D1C04ABAC0091BED0 /* Supporting Files */ = {
+			isa = PBXGroup;
+			children = (
+				3D2AFAF41D646CF80089D1A3 /* legacy_image@2x.png */,
+				13B07FB61A68108700A75B9A /* Info.plist */,
+			);
+			name = "Supporting Files";
+			sourceTree = "<group>";
+		};
+		13B07FAE1A68108700A75B9A /* RNTester */ = {
+			isa = PBXGroup;
+			children = (
+				2DDEF00F1F84BF7B00DBDF73 /* Images.xcassets */,
+				272E6B3A1BEA846C001FCF37 /* NativeExampleViews */,
+				13B07FAF1A68108700A75B9A /* AppDelegate.h */,
+				13B07FB01A68108700A75B9A /* AppDelegate.m */,
+				13B07FB11A68108700A75B9A /* LaunchScreen.xib */,
+				13B07FB71A68108700A75B9A /* main.m */,
+				1323F18D1C04ABAC0091BED0 /* Supporting Files */,
+			);
+			name = RNTester;
+			sourceTree = "<group>";
+		};
+		272E6B3A1BEA846C001FCF37 /* NativeExampleViews */ = {
+			isa = PBXGroup;
+			children = (
+				27F441E81BEBE5030039B79C /* FlexibleSizeExampleView.m */,
+				27F441EA1BEBE5030039B79C /* FlexibleSizeExampleView.h */,
+				272E6B3B1BEA849E001FCF37 /* UpdatePropertiesExampleView.h */,
+				272E6B3C1BEA849E001FCF37 /* UpdatePropertiesExampleView.m */,
+			);
+			name = NativeExampleViews;
+			sourceTree = "<group>";
+		};
+		2DE7E7D81FB2A4F3009E225D /* Frameworks */ = {
+			isa = PBXGroup;
+			children = (
+				6C062A1C08AD9375355BE47F /* libPods-RNTester.a */,
+			);
+			name = Frameworks;
+			sourceTree = "<group>";
+		};
+		3D13F83F1D6F6AE000E69E0E /* RNTesterBundle */ = {
+			isa = PBXGroup;
+			children = (
+				3D13F8401D6F6AE000E69E0E /* Info.plist */,
+				3D13F8441D6F6AF200E69E0E /* ImageInBundle.png */,
+				3D13F8451D6F6AF200E69E0E /* OtherImages.xcassets */,
+			);
+			name = RNTesterBundle;
+			path = RNTester/RNTesterBundle;
+			sourceTree = "<group>";
+		};
+		571A4A20844C3BA40A3D302B /* Pods */ = {
+			isa = PBXGroup;
+			children = (
+				98233960D1D6A1977D1C7EAF /* Pods-RNTester.debug.xcconfig */,
+				5BEC8567F3741044B6A5EFC5 /* Pods-RNTester.release.xcconfig */,
+			);
+			name = Pods;
+			sourceTree = "<group>";
+		};
+		83CBB9F61A601CBA00E9B192 = {
+			isa = PBXGroup;
+			children = (
+				13B07FAE1A68108700A75B9A /* RNTester */,
+				3D13F83F1D6F6AE000E69E0E /* RNTesterBundle */,
+				83CBBA001A601CBA00E9B192 /* Products */,
+				2DE7E7D81FB2A4F3009E225D /* Frameworks */,
+				571A4A20844C3BA40A3D302B /* Pods */,
+			);
+			indentWidth = 2;
+			sourceTree = "<group>";
+			tabWidth = 2;
+			usesTabs = 0;
+		};
+		83CBBA001A601CBA00E9B192 /* Products */ = {
+			isa = PBXGroup;
+			children = (
+				13B07F961A680F5B00A75B9A /* RNTester.app */,
+				3D13F83E1D6F6AE000E69E0E /* RNTesterBundle.bundle */,
+			);
+			name = Products;
+			sourceTree = "<group>";
+		};
+/* End PBXGroup section */
+
+/* Begin PBXNativeTarget section */
+		13B07F861A680F5B00A75B9A /* RNTester */ = {
+			isa = PBXNativeTarget;
+			buildConfigurationList = 13B07F931A680F5B00A75B9A /* Build configuration list for PBXNativeTarget "RNTester" */;
+			buildPhases = (
+				F9CB97B0D9633939D43E75E0 /* [CP] Check Pods Manifest.lock */,
+				13B07F871A680F5B00A75B9A /* Sources */,
+				13B07F8C1A680F5B00A75B9A /* Frameworks */,
+				13B07F8E1A680F5B00A75B9A /* Resources */,
+				68CD48B71D2BCB2C007E06A9 /* Build JS Bundle */,
+				5CF0FD27207FC6EC00C13D65 /* Start Metro */,
+			);
+			buildRules = (
+			);
+			dependencies = (
+				3D13F84C1D6F6B5F00E69E0E /* PBXTargetDependency */,
+			);
+			name = RNTester;
+			productName = "Hello World";
+			productReference = 13B07F961A680F5B00A75B9A /* RNTester.app */;
+			productType = "com.apple.product-type.application";
+		};
+		3D13F83D1D6F6AE000E69E0E /* RNTesterBundle */ = {
+			isa = PBXNativeTarget;
+			buildConfigurationList = 3D13F8411D6F6AE000E69E0E /* Build configuration list for PBXNativeTarget "RNTesterBundle" */;
+			buildPhases = (
+				3D13F83A1D6F6AE000E69E0E /* Sources */,
+				3D13F83B1D6F6AE000E69E0E /* Frameworks */,
+				3D13F83C1D6F6AE000E69E0E /* Resources */,
+			);
+			buildRules = (
+			);
+			dependencies = (
+			);
+			name = RNTesterBundle;
+			productName = RNTesterBundle;
+			productReference = 3D13F83E1D6F6AE000E69E0E /* RNTesterBundle.bundle */;
+			productType = "com.apple.product-type.bundle";
+		};
+/* End PBXNativeTarget section */
+
+/* Begin PBXProject section */
+		83CBB9F71A601CBA00E9B192 /* Project object */ = {
+			isa = PBXProject;
+			attributes = {
+				LastUpgradeCheck = 0820;
+				ORGANIZATIONNAME = Facebook;
+				TargetAttributes = {
+					004D289D1AAF61C70097A701 = {
+						CreatedOnToolsVersion = 6.1.1;
+					};
+					13B07F861A680F5B00A75B9A = {
+						DevelopmentTeam = V9WTTPBFK9;
+					};
+					143BC5941B21E3E100462512 = {
+						CreatedOnToolsVersion = 6.3.2;
+						TestTargetID = 13B07F861A680F5B00A75B9A;
+					};
+					2DD3238F1DA2DD8A000FE1B8 = {
+						CreatedOnToolsVersion = 8.0;
+						ProvisioningStyle = Automatic;
+					};
+					2DD323A41DA2DD8B000FE1B8 = {
+						CreatedOnToolsVersion = 8.0;
+						ProvisioningStyle = Automatic;
+						TestTargetID = 2DD3238F1DA2DD8A000FE1B8;
+					};
+					3D13F83D1D6F6AE000E69E0E = {
+						CreatedOnToolsVersion = 7.3.1;
+					};
+				};
+			};
+			buildConfigurationList = 83CBB9FA1A601CBA00E9B192 /* Build configuration list for PBXProject "RNTesterPods" */;
+			compatibilityVersion = "Xcode 3.2";
+			developmentRegion = English;
+			hasScannedForEncodings = 0;
+			knownRegions = (
+				en,
+				Base,
+			);
+			mainGroup = 83CBB9F61A601CBA00E9B192;
+			productRefGroup = 83CBBA001A601CBA00E9B192 /* Products */;
+			projectDirPath = "";
+			projectRoot = "";
+			targets = (
+				13B07F861A680F5B00A75B9A /* RNTester */,
+				3D13F83D1D6F6AE000E69E0E /* RNTesterBundle */,
+			);
+		};
+/* End PBXProject section */
+
+/* Begin PBXResourcesBuildPhase section */
+		004D289C1AAF61C70097A701 /* Resources */ = {
+			isa = PBXResourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		13B07F8E1A680F5B00A75B9A /* Resources */ = {
+			isa = PBXResourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				3D56F9F11D6F6E9B00F53A06 /* RNTesterBundle.bundle in Resources */,
+				2DDEF0101F84BF7B00DBDF73 /* Images.xcassets in Resources */,
+				3D2AFAF51D646CF80089D1A3 /* legacy_image@2x.png in Resources */,
+				13B07FBD1A68108700A75B9A /* LaunchScreen.xib in Resources */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		143BC5931B21E3E100462512 /* Resources */ = {
+			isa = PBXResourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2D4624DB1DA2EA6900C74D09 /* Resources */ = {
+			isa = PBXResourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2DD3238E1DA2DD8A000FE1B8 /* Resources */ = {
+			isa = PBXResourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				2DD323E11DA2DDBF000FE1B8 /* legacy_image@2x.png in Resources */,
+				2DD323E21DA2DDBF000FE1B8 /* Info.plist in Resources */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2DD323A31DA2DD8B000FE1B8 /* Resources */ = {
+			isa = PBXResourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		3D13F83C1D6F6AE000E69E0E /* Resources */ = {
+			isa = PBXResourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				3D13F8481D6F6AF900E69E0E /* ImageInBundle.png in Resources */,
+				3D13F84A1D6F6AFD00E69E0E /* OtherImages.xcassets in Resources */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+/* End PBXResourcesBuildPhase section */
+
+/* Begin PBXShellScriptBuildPhase section */
+		2DD323EB1DA2DEC1000FE1B8 /* ShellScript */ = {
+			isa = PBXShellScriptBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			inputPaths = (
+			);
+			outputPaths = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+			shellPath = /bin/sh;
+			shellScript = "export NODE_BINARY=node\n$SRCROOT/../scripts/react-native-xcode.sh RNTester/js/RNTesterApp.ios.js";
+		};
+		5CF0FD27207FC6EC00C13D65 /* Start Metro */ = {
+			isa = PBXShellScriptBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			inputPaths = (
+			);
+			name = "Start Metro";
+			outputPaths = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+			shellPath = /bin/sh;
+			shellScript = "export RCT_METRO_PORT=\"${RCT_METRO_PORT:=8081}\"\necho \"export RCT_METRO_PORT=${RCT_METRO_PORT}\" > \"${SRCROOT}/../scripts/.packager.env\"\nif [ -z \"${RCT_NO_LAUNCH_PACKAGER+xxx}\" ] ; then\n  if nc -w 5 -z localhost ${RCT_METRO_PORT} ; then\n    if ! curl -s \"http://localhost:${RCT_METRO_PORT}/status\" | grep -q \"packager-status:running\" ; then\n      echo \"Port ${RCT_METRO_PORT} already in use, packager is either not running or not running correctly\"\n      exit 2\n    fi\n  else\n    open \"$SRCROOT/../scripts/launchPackager.command\" || echo \"Can't start packager automatically\"\n  fi\nfi";
+			showEnvVarsInLog = 0;
+		};
+		68CD48B71D2BCB2C007E06A9 /* Build JS Bundle */ = {
+			isa = PBXShellScriptBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			inputPaths = (
+			);
+			name = "Build JS Bundle";
+			outputPaths = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+			shellPath = /bin/sh;
+			shellScript = "export NODE_BINARY=node\n$SRCROOT/../scripts/react-native-xcode.sh RNTester/js/RNTesterApp.ios.js";
+		};
+		F9CB97B0D9633939D43E75E0 /* [CP] Check Pods Manifest.lock */ = {
+			isa = PBXShellScriptBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			inputPaths = (
+				"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
+				"${PODS_ROOT}/Manifest.lock",
+			);
+			name = "[CP] Check Pods Manifest.lock";
+			outputPaths = (
+				"$(DERIVED_FILE_DIR)/Pods-RNTester-checkManifestLockResult.txt",
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+			shellPath = /bin/sh;
+			shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n    # print error to STDERR\n    echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n    exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
+			showEnvVarsInLog = 0;
+		};
+/* End PBXShellScriptBuildPhase section */
+
+/* Begin PBXSourcesBuildPhase section */
+		004D289A1AAF61C70097A701 /* Sources */ = {
+			isa = PBXSourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		13B07F871A680F5B00A75B9A /* Sources */ = {
+			isa = PBXSourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				272E6B3F1BEA849E001FCF37 /* UpdatePropertiesExampleView.m in Sources */,
+				13B07FBC1A68108700A75B9A /* AppDelegate.m in Sources */,
+				27F441EC1BEBE5030039B79C /* FlexibleSizeExampleView.m in Sources */,
+				13B07FC11A68108700A75B9A /* main.m in Sources */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		143BC5911B21E3E100462512 /* Sources */ = {
+			isa = PBXSourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2D4624C41DA2EA6900C74D09 /* Sources */ = {
+			isa = PBXSourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2DD3238C1DA2DD8A000FE1B8 /* Sources */ = {
+			isa = PBXSourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				2DD323DC1DA2DDBF000FE1B8 /* FlexibleSizeExampleView.m in Sources */,
+				2DD323DD1DA2DDBF000FE1B8 /* UpdatePropertiesExampleView.m in Sources */,
+				2DD323E01DA2DDBF000FE1B8 /* main.m in Sources */,
+				2DD323DE1DA2DDBF000FE1B8 /* AppDelegate.m in Sources */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		2DD323A11DA2DD8B000FE1B8 /* Sources */ = {
+			isa = PBXSourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		3D13F83A1D6F6AE000E69E0E /* Sources */ = {
+			isa = PBXSourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+/* End PBXSourcesBuildPhase section */
+
+/* Begin PBXTargetDependency section */
+		143BC59C1B21E3E100462512 /* PBXTargetDependency */ = {
+			isa = PBXTargetDependency;
+			target = 13B07F861A680F5B00A75B9A /* RNTester */;
+			targetProxy = 143BC59B1B21E3E100462512 /* PBXContainerItemProxy */;
+		};
+		3D13F84C1D6F6B5F00E69E0E /* PBXTargetDependency */ = {
+			isa = PBXTargetDependency;
+			target = 3D13F83D1D6F6AE000E69E0E /* RNTesterBundle */;
+			targetProxy = 3D13F84B1D6F6B5F00E69E0E /* PBXContainerItemProxy */;
+		};
+/* End PBXTargetDependency section */
+
+/* Begin PBXVariantGroup section */
+		13B07FB11A68108700A75B9A /* LaunchScreen.xib */ = {
+			isa = PBXVariantGroup;
+			children = (
+				13B07FB21A68108700A75B9A /* Base */,
+			);
+			name = LaunchScreen.xib;
+			path = RNTester;
+			sourceTree = "<group>";
+		};
+/* End PBXVariantGroup section */
+
+/* Begin XCBuildConfiguration section */
+		13B07F941A680F5B00A75B9A /* Debug */ = {
+			isa = XCBuildConfiguration;
+			baseConfigurationReference = 98233960D1D6A1977D1C7EAF /* Pods-RNTester.debug.xcconfig */;
+			buildSettings = {
+				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
+				DEVELOPMENT_TEAM = V9WTTPBFK9;
+				INFOPLIST_FILE = "$(SRCROOT)/RNTester/Info.plist";
+				IPHONEOS_DEPLOYMENT_TARGET = 9.3;
+				LIBRARY_SEARCH_PATHS = "$(inherited)";
+				PRODUCT_BUNDLE_IDENTIFIER = com.facebook.react.uiapp;
+				PRODUCT_NAME = RNTester;
+				TARGETED_DEVICE_FAMILY = "1,2";
+			};
+			name = Debug;
+		};
+		13B07F951A680F5B00A75B9A /* Release */ = {
+			isa = XCBuildConfiguration;
+			baseConfigurationReference = 5BEC8567F3741044B6A5EFC5 /* Pods-RNTester.release.xcconfig */;
+			buildSettings = {
+				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
+				DEVELOPMENT_TEAM = V9WTTPBFK9;
+				INFOPLIST_FILE = "$(SRCROOT)/RNTester/Info.plist";
+				IPHONEOS_DEPLOYMENT_TARGET = 9.3;
+				LIBRARY_SEARCH_PATHS = "$(inherited)";
+				PRODUCT_BUNDLE_IDENTIFIER = com.facebook.react.uiapp;
+				PRODUCT_NAME = RNTester;
+				TARGETED_DEVICE_FAMILY = "1,2";
+			};
+			name = Release;
+		};
+		3D13F8421D6F6AE000E69E0E /* Debug */ = {
+			isa = XCBuildConfiguration;
+			buildSettings = {
+				CLANG_ANALYZER_NONNULL = YES;
+				COMBINE_HIDPI_IMAGES = YES;
+				GCC_NO_COMMON_BLOCKS = YES;
+				INFOPLIST_FILE = RNTester/RNTesterBundle/Info.plist;
+				PRODUCT_BUNDLE_IDENTIFIER = com.facebook.RNTesterBundle;
+				PRODUCT_NAME = "$(TARGET_NAME)";
+				SDKROOT = iphoneos;
+				WRAPPER_EXTENSION = bundle;
+			};
+			name = Debug;
+		};
+		3D13F8431D6F6AE000E69E0E /* Release */ = {
+			isa = XCBuildConfiguration;
+			buildSettings = {
+				CLANG_ANALYZER_NONNULL = YES;
+				COMBINE_HIDPI_IMAGES = YES;
+				GCC_NO_COMMON_BLOCKS = YES;
+				INFOPLIST_FILE = RNTester/RNTesterBundle/Info.plist;
+				PRODUCT_BUNDLE_IDENTIFIER = com.facebook.RNTesterBundle;
+				PRODUCT_NAME = "$(TARGET_NAME)";
+				SDKROOT = iphoneos;
+				WRAPPER_EXTENSION = bundle;
+			};
+			name = Release;
+		};
+		83CBBA201A601CBA00E9B192 /* Debug */ = {
+			isa = XCBuildConfiguration;
+			buildSettings = {
+				ALWAYS_SEARCH_USER_PATHS = NO;
+				CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
+				CLANG_CXX_LIBRARY = "libc++";
+				CLANG_ENABLE_MODULES = YES;
+				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
+				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
+				CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
+				CLANG_WARN_EMPTY_BODY = YES;
+				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
+				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
+				CLANG_WARN_UNREACHABLE_CODE = YES;
+				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+				COPY_PHASE_STRIP = NO;
+				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
+				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
+				GCC_OPTIMIZATION_LEVEL = 0;
+				GCC_PREPROCESSOR_DEFINITIONS = (
+					"DEBUG=1",
+					"$(inherited)",
+				);
+				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
+				GCC_TREAT_INCOMPATIBLE_POINTER_TYPE_WARNINGS_AS_ERRORS = YES;
+				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
+				GCC_WARN_ABOUT_MISSING_NEWLINE = YES;
+				GCC_WARN_ABOUT_MISSING_PROTOTYPES = YES;
+				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
+				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
+				GCC_WARN_MULTIPLE_DEFINITION_TYPES_FOR_SELECTOR = YES;
+				GCC_WARN_SHADOW = YES;
+				GCC_WARN_STRICT_SELECTOR_MATCH = YES;
+				GCC_WARN_UNDECLARED_SELECTOR = YES;
+				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
+				GCC_WARN_UNKNOWN_PRAGMAS = YES;
+				GCC_WARN_UNUSED_FUNCTION = YES;
+				GCC_WARN_UNUSED_LABEL = YES;
+				GCC_WARN_UNUSED_VARIABLE = YES;
+				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				MTL_ENABLE_DEBUG_INFO = YES;
+				ONLY_ACTIVE_ARCH = YES;
+				OTHER_LDFLAGS = (
+					"-ObjC",
+					"-lc++",
+				);
+				SDKROOT = iphoneos;
+				WARNING_CFLAGS = (
+					"-Wextra",
+					"-Wall",
+					"-Wno-semicolon-before-method-body",
+				);
+			};
+			name = Debug;
+		};
+		83CBBA211A601CBA00E9B192 /* Release */ = {
+			isa = XCBuildConfiguration;
+			buildSettings = {
+				ALWAYS_SEARCH_USER_PATHS = NO;
+				CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
+				CLANG_CXX_LIBRARY = "libc++";
+				CLANG_ENABLE_MODULES = YES;
+				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
+				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
+				CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
+				CLANG_WARN_EMPTY_BODY = YES;
+				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
+				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
+				CLANG_WARN_UNREACHABLE_CODE = YES;
+				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
+				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
+				COPY_PHASE_STRIP = YES;
+				ENABLE_NS_ASSERTIONS = NO;
+				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
+				GCC_TREAT_INCOMPATIBLE_POINTER_TYPE_WARNINGS_AS_ERRORS = YES;
+				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
+				GCC_WARN_ABOUT_MISSING_NEWLINE = YES;
+				GCC_WARN_ABOUT_MISSING_PROTOTYPES = YES;
+				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
+				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
+				GCC_WARN_MULTIPLE_DEFINITION_TYPES_FOR_SELECTOR = YES;
+				GCC_WARN_SHADOW = YES;
+				GCC_WARN_STRICT_SELECTOR_MATCH = YES;
+				GCC_WARN_UNDECLARED_SELECTOR = YES;
+				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
+				GCC_WARN_UNKNOWN_PRAGMAS = YES;
+				GCC_WARN_UNUSED_FUNCTION = YES;
+				GCC_WARN_UNUSED_LABEL = YES;
+				GCC_WARN_UNUSED_VARIABLE = YES;
+				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				MTL_ENABLE_DEBUG_INFO = NO;
+				OTHER_LDFLAGS = (
+					"-ObjC",
+					"-lc++",
+				);
+				SDKROOT = iphoneos;
+				VALIDATE_PRODUCT = YES;
+				WARNING_CFLAGS = (
+					"-Wextra",
+					"-Wall",
+					"-Wno-semicolon-before-method-body",
+				);
+			};
+			name = Release;
+		};
+/* End XCBuildConfiguration section */
+
+/* Begin XCConfigurationList section */
+		13B07F931A680F5B00A75B9A /* Build configuration list for PBXNativeTarget "RNTester" */ = {
+			isa = XCConfigurationList;
+			buildConfigurations = (
+				13B07F941A680F5B00A75B9A /* Debug */,
+				13B07F951A680F5B00A75B9A /* Release */,
+			);
+			defaultConfigurationIsVisible = 0;
+			defaultConfigurationName = Release;
+		};
+		3D13F8411D6F6AE000E69E0E /* Build configuration list for PBXNativeTarget "RNTesterBundle" */ = {
+			isa = XCConfigurationList;
+			buildConfigurations = (
+				3D13F8421D6F6AE000E69E0E /* Debug */,
+				3D13F8431D6F6AE000E69E0E /* Release */,
+			);
+			defaultConfigurationIsVisible = 0;
+			defaultConfigurationName = Release;
+		};
+		83CBB9FA1A601CBA00E9B192 /* Build configuration list for PBXProject "RNTesterPods" */ = {
+			isa = XCConfigurationList;
+			buildConfigurations = (
+				83CBBA201A601CBA00E9B192 /* Debug */,
+				83CBBA211A601CBA00E9B192 /* Release */,
+			);
+			defaultConfigurationIsVisible = 0;
+			defaultConfigurationName = Release;
+		};
+/* End XCConfigurationList section */
+	};
+	rootObject = 83CBB9F71A601CBA00E9B192 /* Project object */;
+}
diff --git a/React.podspec b/React.podspec
index a9a4de5a523e..2aaae1826403 100644
--- a/React.podspec
+++ b/React.podspec
@@ -51,7 +51,7 @@ Pod::Spec.new do |s|
                               "React/Inspector/*",
                               "ReactCommon/yoga/*",
                               "React/Cxx*/*",
-                              "React/Fabric/*",
+                              "React/Fabric/**/*",
     ss.ios.exclude_files    = "React/**/RCTTV*.*"
     ss.tvos.exclude_files   = "React/Modules/RCTClipboard*",
                               "React/Views/RCTDatePicker*",
@@ -73,6 +73,13 @@ Pod::Spec.new do |s|
     ss.compiler_flags       = folly_compiler_flags
     ss.private_header_files = "React/Cxx*/*.h"
     ss.source_files         = "React/Cxx*/*.{h,m,mm}"
+    ss.exclude_files        = "React/CxxExceptions/**/*"
+  end
+
+  s.subspec "CxxExceptions" do |ss|
+    ss.dependency             "React/CxxBridge"
+    ss.private_header_files = "React/CxxExceptions/*.h"
+    ss.source_files         = "React/CxxExceptions/*.{h,m,mm}"
   end
 
   s.subspec "DevSupport" do |ss|

From 7500b3ec839ada6d8e1f7a88d30743dfb0ad7e70 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Fri, 13 Apr 2018 12:19:57 -0700
Subject: [PATCH 0292/1109] Fix anti aliasing rounded background

Reviewed By: shergin, achen1

Differential Revision: D7569885

fbshipit-source-id: 4bfb00485211417b475f14a92fd7b2e52a4b2ff6
---
 .../view/ReactViewBackgroundDrawable.java     | 197 ++++++++++--------
 1 file changed, 108 insertions(+), 89 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
index 9e374b4c502e..e9fa14494a38 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
@@ -343,113 +343,132 @@ private void drawRoundedBackgroundWithBorders(Canvas canvas) {
         || borderWidth.bottom > 0
         || borderWidth.left > 0
         || borderWidth.right > 0) {
-      mPaint.setStyle(Paint.Style.FILL);
 
-      // Draw border
-      canvas.clipPath(mOuterClipPathForBorderRadius, Region.Op.INTERSECT);
-      canvas.clipPath(mInnerClipPathForBorderRadius, Region.Op.DIFFERENCE);
+      //If it's a full and even border draw inner rect path with stroke
+      final float fullBorderWidth = getFullBorderWidth();
+      if (borderWidth.top == fullBorderWidth &&
+        borderWidth.bottom == fullBorderWidth &&
+        borderWidth.left == fullBorderWidth &&
+        borderWidth.right == fullBorderWidth) {
+        if (fullBorderWidth > 0) {
+          int borderColor = getBorderColor(Spacing.ALL);
+          mPaint.setColor(ColorUtil.multiplyColorAlpha(borderColor, mAlpha));
+          mPaint.setStyle(Paint.Style.STROKE);
+          mPaint.setStrokeWidth(fullBorderWidth);
+          canvas.drawPath(mInnerClipPathForBorderRadius, mPaint);
+        }
+      }
+      //In the case of uneven border widths/colors draw quadrilateral in each direction
+      else {
+        mPaint.setStyle(Paint.Style.FILL);
 
-      int colorLeft = getBorderColor(Spacing.LEFT);
-      int colorTop = getBorderColor(Spacing.TOP);
-      int colorRight = getBorderColor(Spacing.RIGHT);
-      int colorBottom = getBorderColor(Spacing.BOTTOM);
+        // Draw border
+        canvas.clipPath(mOuterClipPathForBorderRadius, Region.Op.INTERSECT);
+        canvas.clipPath(mInnerClipPathForBorderRadius, Region.Op.DIFFERENCE);
 
-      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
-        final boolean isRTL = getResolvedLayoutDirection() == View.LAYOUT_DIRECTION_RTL;
-        int colorStart = getBorderColor(Spacing.START);
-        int colorEnd = getBorderColor(Spacing.END);
-
-        if (I18nUtil.getInstance().doLeftAndRightSwapInRTL(mContext)) {
-          if (!isBorderColorDefined(Spacing.START)) {
-            colorStart = colorLeft;
-          }
+        int colorLeft = getBorderColor(Spacing.LEFT);
+        int colorTop = getBorderColor(Spacing.TOP);
+        int colorRight = getBorderColor(Spacing.RIGHT);
+        int colorBottom = getBorderColor(Spacing.BOTTOM);
 
-          if (!isBorderColorDefined(Spacing.END)) {
-            colorEnd = colorRight;
-          }
+        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
+          final boolean isRTL = getResolvedLayoutDirection() == View.LAYOUT_DIRECTION_RTL;
+          int colorStart = getBorderColor(Spacing.START);
+          int colorEnd = getBorderColor(Spacing.END);
 
-          final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
-          final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
+          if (I18nUtil.getInstance().doLeftAndRightSwapInRTL(mContext)) {
+            if (!isBorderColorDefined(Spacing.START)) {
+              colorStart = colorLeft;
+            }
 
-          colorLeft = directionAwareColorLeft;
-          colorRight = directionAwareColorRight;
-        } else {
-          final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
-          final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
+            if (!isBorderColorDefined(Spacing.END)) {
+              colorEnd = colorRight;
+            }
 
-          final boolean isColorStartDefined = isBorderColorDefined(Spacing.START);
-          final boolean isColorEndDefined = isBorderColorDefined(Spacing.END);
-          final boolean isDirectionAwareColorLeftDefined = isRTL ? isColorEndDefined : isColorStartDefined;
-          final boolean isDirectionAwareColorRightDefined = isRTL ? isColorStartDefined : isColorEndDefined;
+            final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
+            final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
 
-          if (isDirectionAwareColorLeftDefined) {
             colorLeft = directionAwareColorLeft;
-          }
-
-          if (isDirectionAwareColorRightDefined) {
             colorRight = directionAwareColorRight;
+          } else {
+            final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
+            final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
+
+            final boolean isColorStartDefined = isBorderColorDefined(Spacing.START);
+            final boolean isColorEndDefined = isBorderColorDefined(Spacing.END);
+            final boolean isDirectionAwareColorLeftDefined =
+              isRTL ? isColorEndDefined : isColorStartDefined;
+            final boolean isDirectionAwareColorRightDefined =
+              isRTL ? isColorStartDefined : isColorEndDefined;
+
+            if (isDirectionAwareColorLeftDefined) {
+              colorLeft = directionAwareColorLeft;
+            }
+
+            if (isDirectionAwareColorRightDefined) {
+              colorRight = directionAwareColorRight;
+            }
           }
         }
-      }
 
-      final float left = mOuterClipTempRectForBorderRadius.left;
-      final float right = mOuterClipTempRectForBorderRadius.right;
-      final float top = mOuterClipTempRectForBorderRadius.top;
-      final float bottom = mOuterClipTempRectForBorderRadius.bottom;
-
-      if (borderWidth.left > 0) {
-        final float x1 = left;
-        final float y1 = top;
-        final float x2 = mInnerTopLeftCorner.x;
-        final float y2 = mInnerTopLeftCorner.y;
-        final float x3 = mInnerBottomLeftCorner.x;
-        final float y3 = mInnerBottomLeftCorner.y;
-        final float x4 = left;
-        final float y4 = bottom;
-
-        drawQuadrilateral(canvas, colorLeft, x1, y1, x2, y2, x3, y3, x4, y4);
-      }
+        final float left = mOuterClipTempRectForBorderRadius.left;
+        final float right = mOuterClipTempRectForBorderRadius.right;
+        final float top = mOuterClipTempRectForBorderRadius.top;
+        final float bottom = mOuterClipTempRectForBorderRadius.bottom;
 
-      if (borderWidth.top > 0) {
-        final float x1 = left;
-        final float y1 = top;
-        final float x2 = mInnerTopLeftCorner.x;
-        final float y2 = mInnerTopLeftCorner.y;
-        final float x3 = mInnerTopRightCorner.x;
-        final float y3 = mInnerTopRightCorner.y;
-        final float x4 = right;
-        final float y4 = top;
-
-        drawQuadrilateral(canvas, colorTop, x1, y1, x2, y2, x3, y3, x4, y4);
-      }
+        if (borderWidth.left > 0) {
+          final float x1 = left;
+          final float y1 = top;
+          final float x2 = mInnerTopLeftCorner.x;
+          final float y2 = mInnerTopLeftCorner.y;
+          final float x3 = mInnerBottomLeftCorner.x;
+          final float y3 = mInnerBottomLeftCorner.y;
+          final float x4 = left;
+          final float y4 = bottom;
 
-      if (borderWidth.right > 0) {
-        final float x1 = right;
-        final float y1 = top;
-        final float x2 = mInnerTopRightCorner.x;
-        final float y2 = mInnerTopRightCorner.y;
-        final float x3 = mInnerBottomRightCorner.x;
-        final float y3 = mInnerBottomRightCorner.y;
-        final float x4 = right;
-        final float y4 = bottom;
-
-        drawQuadrilateral(canvas, colorRight, x1, y1, x2, y2, x3, y3, x4, y4);
-      }
+          drawQuadrilateral(canvas, colorLeft, x1, y1, x2, y2, x3, y3, x4, y4);
+        }
+
+        if (borderWidth.top > 0) {
+          final float x1 = left;
+          final float y1 = top;
+          final float x2 = mInnerTopLeftCorner.x;
+          final float y2 = mInnerTopLeftCorner.y;
+          final float x3 = mInnerTopRightCorner.x;
+          final float y3 = mInnerTopRightCorner.y;
+          final float x4 = right;
+          final float y4 = top;
+
+          drawQuadrilateral(canvas, colorTop, x1, y1, x2, y2, x3, y3, x4, y4);
+        }
+
+        if (borderWidth.right > 0) {
+          final float x1 = right;
+          final float y1 = top;
+          final float x2 = mInnerTopRightCorner.x;
+          final float y2 = mInnerTopRightCorner.y;
+          final float x3 = mInnerBottomRightCorner.x;
+          final float y3 = mInnerBottomRightCorner.y;
+          final float x4 = right;
+          final float y4 = bottom;
 
-      if (borderWidth.bottom > 0) {
-        final float x1 = left;
-        final float y1 = bottom;
-        final float x2 = mInnerBottomLeftCorner.x;
-        final float y2 = mInnerBottomLeftCorner.y;
-        final float x3 = mInnerBottomRightCorner.x;
-        final float y3 = mInnerBottomRightCorner.y;
-        final float x4 = right;
-        final float y4 = bottom;
-
-        drawQuadrilateral(canvas, colorBottom, x1, y1, x2, y2, x3, y3, x4, y4);
+          drawQuadrilateral(canvas, colorRight, x1, y1, x2, y2, x3, y3, x4, y4);
+        }
+
+        if (borderWidth.bottom > 0) {
+          final float x1 = left;
+          final float y1 = bottom;
+          final float x2 = mInnerBottomLeftCorner.x;
+          final float y2 = mInnerBottomLeftCorner.y;
+          final float x3 = mInnerBottomRightCorner.x;
+          final float y3 = mInnerBottomRightCorner.y;
+          final float x4 = right;
+          final float y4 = bottom;
+
+          drawQuadrilateral(canvas, colorBottom, x1, y1, x2, y2, x3, y3, x4, y4);
+        }
       }
     }
-
     canvas.restore();
   }
 

From af661e4a6f6583b4c2b372a22d71f41470760d93 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Fri, 13 Apr 2018 14:10:43 -0700
Subject: [PATCH 0293/1109] Add metro to paths to be babel-transformed

Reviewed By: fkgozali

Differential Revision: D7620341

fbshipit-source-id: fc801c938628f5b6b118b8250d5c63268e19359e
---
 setupBabel.js | 34 +++++++++++++++++++---------------
 1 file changed, 19 insertions(+), 15 deletions(-)

diff --git a/setupBabel.js b/setupBabel.js
index 15e0f19a458b..0b21ffe31f5c 100644
--- a/setupBabel.js
+++ b/setupBabel.js
@@ -11,7 +11,7 @@ const babelRegisterOnly = require('metro/src/babelRegisterOnly');
 const escapeRegExp = require('lodash/escapeRegExp');
 const path = require('path');
 
-const BABEL_ENABLED_PATHS = ['local-cli'];
+const BABEL_ENABLED_PATHS = ['local-cli', 'metro'];
 
 /**
  * We use absolute paths for matching only the top-level folders reliably. For
@@ -21,20 +21,24 @@ const BABEL_ENABLED_PATHS = ['local-cli'];
 function buildRegExps(basePath, dirPaths) {
   return dirPaths.map(
     folderPath =>
-      // Babel `only` option works with forward slashes in the RegExp so replace
-      // backslashes for Windows.
-      folderPath instanceof RegExp
-        ? new RegExp(
-            `^${escapeRegExp(
-              path.resolve(basePath, '.').replace(/\\/g, '/')
-            )}/${folderPath.source}`,
-            folderPath.flags
-          )
-        : new RegExp(
-            `^${escapeRegExp(
-              path.resolve(basePath, folderPath).replace(/\\/g, '/')
-            )}`
-          )
+      folderPath === 'metro'
+        // metro uses flow (for example) which needs to be stripped out w/babel.
+        // it'll resolve to .../metro/packages/metro/src/index.js we want root
+        ? path.resolve(require.resolve('metro'), '..', '..', '..', '..')
+        // Babel `only` option works with forward slashes in the RegExp so replace
+        // backslashes for Windows.
+        : folderPath instanceof RegExp
+          ? new RegExp(
+              `^${escapeRegExp(
+                path.resolve(basePath, '.').replace(/\\/g, '/')
+              )}/${folderPath.source}`,
+              folderPath.flags
+            )
+          : new RegExp(
+              `^${escapeRegExp(
+                path.resolve(basePath, folderPath).replace(/\\/g, '/')
+              )}`
+            )
   );
 }
 

From e8e2a6e4102c1ba0ee3d068769e47fa61c160524 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Fri, 13 Apr 2018 17:13:07 -0700
Subject: [PATCH 0294/1109] Add tint color to inline icons

Reviewed By: achen1

Differential Revision: D7625378

fbshipit-source-id: a60cf79f32f2d4091dbddebd65af4880ebb8c2c7
---
 .../FrescoBasedReactTextInlineImageShadowNode.java     | 10 +++++++++-
 .../FrescoBasedReactTextInlineImageSpan.java           |  9 +++++++++
 2 files changed, 18 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageShadowNode.java
index c66f009714c8..301174772eac 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageShadowNode.java
@@ -41,6 +41,7 @@ public class FrescoBasedReactTextInlineImageShadowNode extends ReactTextInlineIm
   private final @Nullable Object mCallerContext;
   private float mWidth = YogaConstants.UNDEFINED;
   private float mHeight = YogaConstants.UNDEFINED;
+  private int mTintColor = 0;
 
   public FrescoBasedReactTextInlineImageShadowNode(
     AbstractDraweeControllerBuilder draweeControllerBuilder,
@@ -54,6 +55,7 @@ private FrescoBasedReactTextInlineImageShadowNode(FrescoBasedReactTextInlineImag
     mHeaders = node.mHeaders; // mHeaders is immutable
     mWidth = node.mWidth;
     mHeight = node.mHeight;
+    mTintColor = node.mTintColor;
     mDraweeControllerBuilder = node.mDraweeControllerBuilder;
     mCallerContext = node.mCallerContext;
     mUri = node.mUri;
@@ -94,6 +96,11 @@ public void setHeaders(ReadableMap headers) {
     mHeaders = headers;
   }
 
+  @ReactProp(name = "tintColor")
+  public void setTintColor(int tintColor) {
+    mTintColor = tintColor;
+  }
+
   /**
    * Besides width/height, all other layout props on inline images are ignored
    */
@@ -116,7 +123,7 @@ public void setHeight(Dynamic height) {
           "Inline images must not have percentage based height");
     }
   }
-
+  
   public @Nullable Uri getUri() {
     return mUri;
   }
@@ -155,6 +162,7 @@ public TextInlineImageSpan buildInlineImageSpan() {
       resources,
       height,
       width,
+      mTintColor,
       getUri(),
       getHeaders(),
       getDraweeControllerBuilder(),
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
index da53a968703f..d769d50fce99 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
@@ -7,6 +7,8 @@
 
 package com.facebook.react.views.text.frescosupport;
 
+import android.graphics.Color;
+import android.graphics.PorterDuff;
 import javax.annotation.Nullable;
 
 import android.content.res.Resources;
@@ -46,6 +48,7 @@ public class FrescoBasedReactTextInlineImageSpan extends TextInlineImageSpan {
   private final @Nullable Object mCallerContext;
 
   private int mHeight;
+  private int mTintColor;
   private Uri mUri;
   private int mWidth;
   private ReadableMap mHeaders;
@@ -56,6 +59,7 @@ public FrescoBasedReactTextInlineImageSpan(
       Resources resources,
       int height,
       int width,
+      int tintColor,
       @Nullable Uri uri,
       ReadableMap headers,
       AbstractDraweeControllerBuilder draweeControllerBuilder,
@@ -68,6 +72,7 @@ public FrescoBasedReactTextInlineImageSpan(
     mCallerContext = callerContext;
 
     mHeight = height;
+    mTintColor = tintColor;
     mWidth = width;
     mUri = (uri != null) ? uri : Uri.EMPTY;
     mHeaders = headers;
@@ -143,7 +148,11 @@ public void draw(
 
       mDrawable = mDraweeHolder.getTopLevelDrawable();
       mDrawable.setBounds(0, 0, mWidth, mHeight);
+      if(mTintColor != 0) {
+        mDrawable.setColorFilter(mTintColor, PorterDuff.Mode.SRC_IN);
+      }
       mDrawable.setCallback(mTextView);
+
     }
 
     // NOTE: This drawing code is copied from DynamicDrawableSpan

From cc57b7b1d36f7827ee545a38dd6a51cbfe0e1dae Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 13 Apr 2018 17:19:01 -0700
Subject: [PATCH 0295/1109] iOS OSS: check in the Podfile.lock

Summary: Should have been checked in previously. No setup change here.

Reviewed By: shergin

Differential Revision: D7626040

fbshipit-source-id: e7a1a9de70a40a22e39eb3777d1b62c8d7b66381
---
 RNTester/.gitignore   |   1 -
 RNTester/Podfile.lock | 112 ++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 112 insertions(+), 1 deletion(-)
 create mode 100644 RNTester/Podfile.lock

diff --git a/RNTester/.gitignore b/RNTester/.gitignore
index 003be3341c3e..389a2b20c85b 100644
--- a/RNTester/.gitignore
+++ b/RNTester/.gitignore
@@ -1,2 +1 @@
-Podfile.lock
 Pods/
diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
new file mode 100644
index 000000000000..64196db77f10
--- /dev/null
+++ b/RNTester/Podfile.lock
@@ -0,0 +1,112 @@
+PODS:
+  - boost-for-react-native (1.63.0)
+  - DoubleConversion (1.1.5)
+  - Folly (2016.09.26.00):
+    - boost-for-react-native
+    - DoubleConversion
+    - glog
+  - glog (0.3.4)
+  - React/ART (1000.0.0):
+    - React/Core
+  - React/Core (1000.0.0):
+    - yoga (= 1000.0.0.React)
+  - React/CxxBridge (1000.0.0):
+    - Folly (= 2016.09.26.00)
+    - React/Core
+    - React/cxxreact
+  - React/cxxreact (1000.0.0):
+    - boost-for-react-native (= 1.63.0)
+    - Folly (= 2016.09.26.00)
+    - React/jschelpers
+    - React/jsinspector
+  - React/DevSupport (1000.0.0):
+    - React/Core
+    - React/RCTWebSocket
+  - React/fishhook (1000.0.0)
+  - React/jschelpers (1000.0.0):
+    - Folly (= 2016.09.26.00)
+    - React/PrivateDatabase
+  - React/jsinspector (1000.0.0)
+  - React/PrivateDatabase (1000.0.0)
+  - React/RCTActionSheet (1000.0.0):
+    - React/Core
+  - React/RCTAnimation (1000.0.0):
+    - React/Core
+  - React/RCTBlob (1000.0.0):
+    - React/Core
+  - React/RCTCameraRoll (1000.0.0):
+    - React/Core
+    - React/RCTImage
+  - React/RCTGeolocation (1000.0.0):
+    - React/Core
+  - React/RCTImage (1000.0.0):
+    - React/Core
+    - React/RCTNetwork
+  - React/RCTLinkingIOS (1000.0.0):
+    - React/Core
+  - React/RCTNetwork (1000.0.0):
+    - React/Core
+  - React/RCTPushNotification (1000.0.0):
+    - React/Core
+  - React/RCTSettings (1000.0.0):
+    - React/Core
+  - React/RCTText (1000.0.0):
+    - React/Core
+  - React/RCTVibration (1000.0.0):
+    - React/Core
+  - React/RCTWebSocket (1000.0.0):
+    - React/Core
+    - React/fishhook
+    - React/RCTBlob
+  - yoga (1000.0.0.React)
+
+DEPENDENCIES:
+  - DoubleConversion (from `../third-party-podspecs/DoubleConversion.podspec`)
+  - Folly (from `../third-party-podspecs/Folly.podspec`)
+  - glog (from `../third-party-podspecs/glog.podspec`)
+  - React/ART (from `../`)
+  - React/Core (from `../`)
+  - React/CxxBridge (from `../`)
+  - React/DevSupport (from `../`)
+  - React/RCTActionSheet (from `../`)
+  - React/RCTAnimation (from `../`)
+  - React/RCTBlob (from `../`)
+  - React/RCTCameraRoll (from `../`)
+  - React/RCTGeolocation (from `../`)
+  - React/RCTImage (from `../`)
+  - React/RCTLinkingIOS (from `../`)
+  - React/RCTNetwork (from `../`)
+  - React/RCTPushNotification (from `../`)
+  - React/RCTSettings (from `../`)
+  - React/RCTText (from `../`)
+  - React/RCTVibration (from `../`)
+  - React/RCTWebSocket (from `../`)
+  - yoga (from `../ReactCommon/yoga`)
+
+SPEC REPOS:
+  https://github.com/CocoaPods/Specs.git:
+    - boost-for-react-native
+
+EXTERNAL SOURCES:
+  DoubleConversion:
+    :podspec: "../third-party-podspecs/DoubleConversion.podspec"
+  Folly:
+    :podspec: "../third-party-podspecs/Folly.podspec"
+  glog:
+    :podspec: "../third-party-podspecs/glog.podspec"
+  React:
+    :path: "../"
+  yoga:
+    :path: "../ReactCommon/yoga"
+
+SPEC CHECKSUMS:
+  boost-for-react-native: 39c7adb57c4e60d6c5479dd8623128eb5b3f0f2c
+  DoubleConversion: e22e0762848812a87afd67ffda3998d9ef29170c
+  Folly: 211775e49d8da0ca658aebc8eab89d642935755c
+  glog: 1de0bb937dccdc981596d3b5825ebfb765017ded
+  React: b5ea2f2f4800bbae06eaa2f11e5709fd1958f7bf
+  yoga: bdd268c5812f00bdb52cc2b58f129797e97935eb
+
+PODFILE CHECKSUM: 2db1aae50ba1389ea02bbb867efcf85182b0336a
+
+COCOAPODS: 1.5.0

From f569b45f4cdd72cca7e8c4eefcb59485ffe6022f Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 13 Apr 2018 17:19:02 -0700
Subject: [PATCH 0296/1109] OSS: upgrade Folly 2016.09.26 => 2016.10.31

Summary:
There was a fix around folly::dynamic constructor that will be needed for Fabric work. This was done in https://github.com/facebook/folly/commit/94e964976c1b65e79b0f7bdd960cfec260399a52#diff-7d1cb97d222ba0c863ea8a8e43b2ee2b and luckily the release 1 month after the Folly version we used in RN already had the fix, so that we don't need to upgrade to the latest folly yet (minimizing breakages).

Tested by:
* running RNTester xcode project (ios)
* running RNTesterPods workspace via cocoapods
* building android via gradle

Reviewed By: shergin

Differential Revision: D7626037

fbshipit-source-id: cb36ba5b91ba131d4e450300bd620db657cfa1e8
---
 RNTester/Podfile.lock                 | 12 ++++----
 React.podspec                         |  7 +++--
 React/React.xcodeproj/project.pbxproj | 40 +++++++++++++--------------
 React/third-party.xcconfig            |  2 +-
 ReactAndroid/build.gradle             |  8 +++---
 scripts/ios-install-third-party.sh    |  2 +-
 third-party-podspecs/Folly.podspec    |  2 +-
 7 files changed, 37 insertions(+), 36 deletions(-)

diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index 64196db77f10..5f5a3acb769e 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -1,7 +1,7 @@
 PODS:
   - boost-for-react-native (1.63.0)
   - DoubleConversion (1.1.5)
-  - Folly (2016.09.26.00):
+  - Folly (2016.10.31.00):
     - boost-for-react-native
     - DoubleConversion
     - glog
@@ -11,12 +11,12 @@ PODS:
   - React/Core (1000.0.0):
     - yoga (= 1000.0.0.React)
   - React/CxxBridge (1000.0.0):
-    - Folly (= 2016.09.26.00)
+    - Folly (= 2016.10.31.00)
     - React/Core
     - React/cxxreact
   - React/cxxreact (1000.0.0):
     - boost-for-react-native (= 1.63.0)
-    - Folly (= 2016.09.26.00)
+    - Folly (= 2016.10.31.00)
     - React/jschelpers
     - React/jsinspector
   - React/DevSupport (1000.0.0):
@@ -24,7 +24,7 @@ PODS:
     - React/RCTWebSocket
   - React/fishhook (1000.0.0)
   - React/jschelpers (1000.0.0):
-    - Folly (= 2016.09.26.00)
+    - Folly (= 2016.10.31.00)
     - React/PrivateDatabase
   - React/jsinspector (1000.0.0)
   - React/PrivateDatabase (1000.0.0)
@@ -102,9 +102,9 @@ EXTERNAL SOURCES:
 SPEC CHECKSUMS:
   boost-for-react-native: 39c7adb57c4e60d6c5479dd8623128eb5b3f0f2c
   DoubleConversion: e22e0762848812a87afd67ffda3998d9ef29170c
-  Folly: 211775e49d8da0ca658aebc8eab89d642935755c
+  Folly: 9a8eea4725a0b6ba3256ebf206c21e352c23abf8
   glog: 1de0bb937dccdc981596d3b5825ebfb765017ded
-  React: b5ea2f2f4800bbae06eaa2f11e5709fd1958f7bf
+  React: 4e8050da47914f710f7bf48d1aca39fd9afafe39
   yoga: bdd268c5812f00bdb52cc2b58f129797e97935eb
 
 PODFILE CHECKSUM: 2db1aae50ba1389ea02bbb867efcf85182b0336a
diff --git a/React.podspec b/React.podspec
index 2aaae1826403..ac3df357ad1c 100644
--- a/React.podspec
+++ b/React.podspec
@@ -13,6 +13,7 @@ else
 end
 
 folly_compiler_flags = '-DFOLLY_NO_CONFIG -DFOLLY_MOBILE=1 -DFOLLY_USE_LIBCPP=1'
+folly_version = '2016.10.31.00'
 
 Pod::Spec.new do |s|
   s.name                    = "React"
@@ -67,7 +68,7 @@ Pod::Spec.new do |s|
   end
 
   s.subspec "CxxBridge" do |ss|
-    ss.dependency             "Folly", "2016.09.26.00"
+    ss.dependency             "Folly", folly_version
     ss.dependency             "React/Core"
     ss.dependency             "React/cxxreact"
     ss.compiler_flags       = folly_compiler_flags
@@ -95,7 +96,7 @@ Pod::Spec.new do |s|
   end
 
   s.subspec "jschelpers" do |ss|
-    ss.dependency             "Folly", "2016.09.26.00"
+    ss.dependency             "Folly", folly_version
     ss.dependency             "React/PrivateDatabase"
     ss.compiler_flags       = folly_compiler_flags
     ss.source_files         = "ReactCommon/jschelpers/*.{cpp,h}"
@@ -120,7 +121,7 @@ Pod::Spec.new do |s|
     ss.dependency             "React/jschelpers"
     ss.dependency             "React/jsinspector"
     ss.dependency             "boost-for-react-native", "1.63.0"
-    ss.dependency             "Folly", "2016.09.26.00"
+    ss.dependency             "Folly", folly_version
     ss.compiler_flags       = folly_compiler_flags
     ss.source_files         = "ReactCommon/cxxreact/*.{cpp,h}"
     ss.exclude_files        = "ReactCommon/cxxreact/SampleCxxModule.*"
diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index e9d07dd8d9e8..5232e06f72a0 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -1946,21 +1946,21 @@
 		139D7F141E25DEC900323FB7 /* raw_logging.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = raw_logging.h; sourceTree = "<group>"; };
 		139D7F161E25DEC900323FB7 /* stl_logging.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = stl_logging.h; sourceTree = "<group>"; };
 		139D7F181E25DEC900323FB7 /* vlog_is_on.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = vlog_is_on.h; sourceTree = "<group>"; };
-		139D849C1E273B5600323FB7 /* AtomicIntrusiveLinkedList.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = AtomicIntrusiveLinkedList.h; path = "folly-2016.09.26.00/folly/AtomicIntrusiveLinkedList.h"; sourceTree = "<group>"; };
-		139D849D1E273B5600323FB7 /* Bits.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Bits.cpp; path = "folly-2016.09.26.00/folly/Bits.cpp"; sourceTree = "<group>"; };
-		139D849E1E273B5600323FB7 /* Bits.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Bits.h; path = "folly-2016.09.26.00/folly/Bits.h"; sourceTree = "<group>"; };
-		139D849F1E273B5600323FB7 /* Conv.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Conv.cpp; path = "folly-2016.09.26.00/folly/Conv.cpp"; sourceTree = "<group>"; };
-		139D84A01E273B5600323FB7 /* Conv.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Conv.h; path = "folly-2016.09.26.00/folly/Conv.h"; sourceTree = "<group>"; };
-		139D84A11E273B5600323FB7 /* dynamic-inl.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = "dynamic-inl.h"; path = "folly-2016.09.26.00/folly/dynamic-inl.h"; sourceTree = "<group>"; };
-		139D84A21E273B5600323FB7 /* dynamic.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = dynamic.cpp; path = "folly-2016.09.26.00/folly/dynamic.cpp"; sourceTree = "<group>"; };
-		139D84A31E273B5600323FB7 /* dynamic.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = dynamic.h; path = "folly-2016.09.26.00/folly/dynamic.h"; sourceTree = "<group>"; };
-		139D84A41E273B5600323FB7 /* Exception.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Exception.h; path = "folly-2016.09.26.00/folly/Exception.h"; sourceTree = "<group>"; };
-		139D84A71E273B5600323FB7 /* json.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = json.cpp; path = "folly-2016.09.26.00/folly/json.cpp"; sourceTree = "<group>"; };
-		139D84A81E273B5600323FB7 /* json.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = json.h; path = "folly-2016.09.26.00/folly/json.h"; sourceTree = "<group>"; };
-		139D84A91E273B5600323FB7 /* Memory.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Memory.h; path = "folly-2016.09.26.00/folly/Memory.h"; sourceTree = "<group>"; };
-		139D84AA1E273B5600323FB7 /* MoveWrapper.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = MoveWrapper.h; path = "folly-2016.09.26.00/folly/MoveWrapper.h"; sourceTree = "<group>"; };
-		139D84AB1E273B5600323FB7 /* Optional.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Optional.h; path = "folly-2016.09.26.00/folly/Optional.h"; sourceTree = "<group>"; };
-		139D84AC1E273B5600323FB7 /* ScopeGuard.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ScopeGuard.h; path = "folly-2016.09.26.00/folly/ScopeGuard.h"; sourceTree = "<group>"; };
+		139D849C1E273B5600323FB7 /* AtomicIntrusiveLinkedList.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = AtomicIntrusiveLinkedList.h; path = "folly-2016.10.31.00/folly/AtomicIntrusiveLinkedList.h"; sourceTree = "<group>"; };
+		139D849D1E273B5600323FB7 /* Bits.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Bits.cpp; path = "folly-2016.10.31.00/folly/Bits.cpp"; sourceTree = "<group>"; };
+		139D849E1E273B5600323FB7 /* Bits.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Bits.h; path = "folly-2016.10.31.00/folly/Bits.h"; sourceTree = "<group>"; };
+		139D849F1E273B5600323FB7 /* Conv.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Conv.cpp; path = "folly-2016.10.31.00/folly/Conv.cpp"; sourceTree = "<group>"; };
+		139D84A01E273B5600323FB7 /* Conv.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Conv.h; path = "folly-2016.10.31.00/folly/Conv.h"; sourceTree = "<group>"; };
+		139D84A11E273B5600323FB7 /* dynamic-inl.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = "dynamic-inl.h"; path = "folly-2016.10.31.00/folly/dynamic-inl.h"; sourceTree = "<group>"; };
+		139D84A21E273B5600323FB7 /* dynamic.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = dynamic.cpp; path = "folly-2016.10.31.00/folly/dynamic.cpp"; sourceTree = "<group>"; };
+		139D84A31E273B5600323FB7 /* dynamic.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = dynamic.h; path = "folly-2016.10.31.00/folly/dynamic.h"; sourceTree = "<group>"; };
+		139D84A41E273B5600323FB7 /* Exception.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Exception.h; path = "folly-2016.10.31.00/folly/Exception.h"; sourceTree = "<group>"; };
+		139D84A71E273B5600323FB7 /* json.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = json.cpp; path = "folly-2016.10.31.00/folly/json.cpp"; sourceTree = "<group>"; };
+		139D84A81E273B5600323FB7 /* json.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = json.h; path = "folly-2016.10.31.00/folly/json.h"; sourceTree = "<group>"; };
+		139D84A91E273B5600323FB7 /* Memory.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Memory.h; path = "folly-2016.10.31.00/folly/Memory.h"; sourceTree = "<group>"; };
+		139D84AA1E273B5600323FB7 /* MoveWrapper.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = MoveWrapper.h; path = "folly-2016.10.31.00/folly/MoveWrapper.h"; sourceTree = "<group>"; };
+		139D84AB1E273B5600323FB7 /* Optional.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Optional.h; path = "folly-2016.10.31.00/folly/Optional.h"; sourceTree = "<group>"; };
+		139D84AC1E273B5600323FB7 /* ScopeGuard.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ScopeGuard.h; path = "folly-2016.10.31.00/folly/ScopeGuard.h"; sourceTree = "<group>"; };
 		13A0C2851B74F71200B29F6F /* RCTDevLoadingView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; lineEnding = 0; path = RCTDevLoadingView.h; sourceTree = "<group>"; xcLanguageSpecificationIdentifier = xcode.lang.objcpp; };
 		13A0C2861B74F71200B29F6F /* RCTDevLoadingView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTDevLoadingView.m; sourceTree = "<group>"; };
 		13A0C2871B74F71200B29F6F /* RCTDevMenu.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; lineEnding = 0; path = RCTDevMenu.h; sourceTree = "<group>"; xcLanguageSpecificationIdentifier = xcode.lang.objcpp; };
@@ -2024,11 +2024,11 @@
 		13E067541A70F44B002CDEE1 /* UIView+React.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "UIView+React.m"; sourceTree = "<group>"; };
 		13F17A831B8493E5007D4C75 /* RCTRedBox.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTRedBox.h; sourceTree = "<group>"; };
 		13F17A841B8493E5007D4C75 /* RCTRedBox.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTRedBox.m; sourceTree = "<group>"; };
-		13F887521E2971C500C3C7A1 /* Demangle.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Demangle.cpp; path = "folly-2016.09.26.00/folly/Demangle.cpp"; sourceTree = "<group>"; };
-		13F887531E2971C500C3C7A1 /* StringBase.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = StringBase.cpp; path = "folly-2016.09.26.00/folly/StringBase.cpp"; sourceTree = "<group>"; };
-		13F887541E2971C500C3C7A1 /* Unicode.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Unicode.cpp; path = "folly-2016.09.26.00/folly/Unicode.cpp"; sourceTree = "<group>"; };
-		13F8879C1E29740700C3C7A1 /* BitsFunctexcept.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = BitsFunctexcept.cpp; path = "folly-2016.09.26.00/folly/portability/BitsFunctexcept.cpp"; sourceTree = "<group>"; };
-		13F887A01E2977D800C3C7A1 /* MallocImpl.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = MallocImpl.cpp; path = "folly-2016.09.26.00/folly/detail/MallocImpl.cpp"; sourceTree = "<group>"; };
+		13F887521E2971C500C3C7A1 /* Demangle.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Demangle.cpp; path = "folly-2016.10.31.00/folly/Demangle.cpp"; sourceTree = "<group>"; };
+		13F887531E2971C500C3C7A1 /* StringBase.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = StringBase.cpp; path = "folly-2016.10.31.00/folly/StringBase.cpp"; sourceTree = "<group>"; };
+		13F887541E2971C500C3C7A1 /* Unicode.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Unicode.cpp; path = "folly-2016.10.31.00/folly/Unicode.cpp"; sourceTree = "<group>"; };
+		13F8879C1E29740700C3C7A1 /* BitsFunctexcept.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = BitsFunctexcept.cpp; path = "folly-2016.10.31.00/folly/portability/BitsFunctexcept.cpp"; sourceTree = "<group>"; };
+		13F887A01E2977D800C3C7A1 /* MallocImpl.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = MallocImpl.cpp; path = "folly-2016.10.31.00/folly/detail/MallocImpl.cpp"; sourceTree = "<group>"; };
 		14200DA81AC179B3008EE6BA /* RCTJavaScriptLoader.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTJavaScriptLoader.h; sourceTree = "<group>"; };
 		142014171B32094000CC17BA /* RCTPerformanceLogger.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTPerformanceLogger.m; sourceTree = "<group>"; };
 		142014181B32094000CC17BA /* RCTPerformanceLogger.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTPerformanceLogger.h; sourceTree = "<group>"; };
diff --git a/React/third-party.xcconfig b/React/third-party.xcconfig
index 37a4baa2979b..24bf1727b384 100644
--- a/React/third-party.xcconfig
+++ b/React/third-party.xcconfig
@@ -6,5 +6,5 @@
 //  Copyright © 2017 Facebook. All rights reserved.
 //
 
-HEADER_SEARCH_PATHS = $(SRCROOT)/../third-party/boost_1_63_0 $(SRCROOT)/../third-party/folly-2016.09.26.00 $(SRCROOT)/../third-party/glog-0.3.4/src
+HEADER_SEARCH_PATHS = $(SRCROOT)/../third-party/boost_1_63_0 $(SRCROOT)/../third-party/folly-2016.10.31.00 $(SRCROOT)/../third-party/glog-0.3.4/src
 OTHER_CFLAGS = -DFOLLY_NO_CONFIG -DFOLLY_MOBILE=1 -DFOLLY_USE_LIBCPP=1
diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 15b5c02cdcab..eecfe6929779 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -70,17 +70,17 @@ task prepareDoubleConversion(dependsOn: dependenciesPath ? [] : [downloadDoubleC
 }
 
 task downloadFolly(dependsOn: createNativeDepsDirectories, type: Download) {
-    src 'https://github.com/facebook/folly/archive/v2016.09.26.00.tar.gz'
+    src 'https://github.com/facebook/folly/archive/v2016.10.31.00.tar.gz'
     onlyIfNewer true
     overwrite false
-    dest new File(downloadsDir, 'folly-2016.09.26.00.tar.gz');
+    dest new File(downloadsDir, 'folly-2016.10.31.00.tar.gz');
 }
 
 task prepareFolly(dependsOn: dependenciesPath ? [] : [downloadFolly], type: Copy) {
     from dependenciesPath ?: tarTree(downloadFolly.dest)
     from 'src/main/jni/third-party/folly/Android.mk'
-    include 'folly-2016.09.26.00/folly/**/*', 'Android.mk'
-    eachFile {fname -> fname.path = (fname.path - "folly-2016.09.26.00/")}
+    include 'folly-2016.10.31.00/folly/**/*', 'Android.mk'
+    eachFile {fname -> fname.path = (fname.path - "folly-2016.10.31.00/")}
     includeEmptyDirs = false
     into "$thirdPartyNdkDir/folly"
 }
diff --git a/scripts/ios-install-third-party.sh b/scripts/ios-install-third-party.sh
index 0d698ea3de1f..f10b23b32a6f 100755
--- a/scripts/ios-install-third-party.sh
+++ b/scripts/ios-install-third-party.sh
@@ -64,4 +64,4 @@ SCRIPTDIR=$(dirname "$0")
 fetch_and_unpack glog-0.3.4.tar.gz https://github.com/google/glog/archive/v0.3.4.tar.gz 69f91cd5a1de35ead0bc4103ea87294b0206a456 "\"$SCRIPTDIR/ios-configure-glog.sh\""
 fetch_and_unpack double-conversion-1.1.5.tar.gz https://github.com/google/double-conversion/archive/v1.1.5.tar.gz 96a8aba1b4ce7d4a7a3c123be26c379c2fed1def
 fetch_and_unpack boost_1_63_0.tar.gz https://github.com/react-native-community/boost-for-react-native/releases/download/v1.63.0-0/boost_1_63_0.tar.gz c3f57e1d22a995e608983effbb752b54b6eab741
-fetch_and_unpack folly-2016.09.26.00.tar.gz https://github.com/facebook/folly/archive/v2016.09.26.00.tar.gz f3b928b5039235bad6cece638c597c6684d1e4e6
+fetch_and_unpack folly-2016.10.31.00.tar.gz https://github.com/facebook/folly/archive/v2016.10.31.00.tar.gz fb8cdf8962d8c9d0c20a150b6ec3b75d1fa50696
diff --git a/third-party-podspecs/Folly.podspec b/third-party-podspecs/Folly.podspec
index b04c089e7183..c72b88fba93a 100644
--- a/third-party-podspecs/Folly.podspec
+++ b/third-party-podspecs/Folly.podspec
@@ -1,6 +1,6 @@
 Pod::Spec.new do |spec|
   spec.name = 'Folly'
-  spec.version = '2016.09.26.00'
+  spec.version = '2016.10.31.00'
   spec.license = { :type => 'Apache License, Version 2.0' }
   spec.homepage = 'https://github.com/facebook/folly'
   spec.summary = 'An open-source C++ library developed and used at Facebook.'

From 2299d4cd7cc8540c0f31873acb2f652ea1bba90c Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 13 Apr 2018 17:19:04 -0700
Subject: [PATCH 0297/1109] iOS OSS: updated Podfile to have fabric related
 targets

Summary: Initial attempt to make fabric stuffs built properly with CocoaPods + RNTesterPods project. This simply includes fabric libs to the build, it doesn't change any behavior or enable fabric runtime.

Reviewed By: shergin

Differential Revision: D7626038

fbshipit-source-id: 4a80e0066cffa4478bb442fa8aefeaee6ff56ddd
---
 RNTester/Podfile                              |  1 +
 RNTester/Podfile.lock                         | 31 +++++++-
 React.podspec                                 | 72 ++++++++++++++++++-
 .../fabric/uimanager/FabricUIManager.cpp      |  2 +-
 4 files changed, 101 insertions(+), 5 deletions(-)

diff --git a/RNTester/Podfile b/RNTester/Podfile
index 1bcd939928b8..155cec5aa04e 100644
--- a/RNTester/Podfile
+++ b/RNTester/Podfile
@@ -15,6 +15,7 @@ target 'RNTester' do
     'RCTAnimation',
     'RCTBlob',
     'RCTCameraRoll',
+    'RCTFabric',
     'RCTGeolocation',
     'RCTImage',
     'RCTLinkingIOS',
diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index 5f5a3acb769e..57ad2bcedbe7 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -14,6 +14,9 @@ PODS:
     - Folly (= 2016.10.31.00)
     - React/Core
     - React/cxxreact
+  - React/CxxExceptions (1000.0.0):
+    - React/CxxBridge
+    - React/exceptions
   - React/cxxreact (1000.0.0):
     - boost-for-react-native (= 1.63.0)
     - Folly (= 2016.10.31.00)
@@ -22,6 +25,24 @@ PODS:
   - React/DevSupport (1000.0.0):
     - React/Core
     - React/RCTWebSocket
+  - React/exceptions (1000.0.0)
+  - React/fabric (1000.0.0):
+    - React/fabric/core (= 1000.0.0)
+    - React/fabric/debug (= 1000.0.0)
+    - React/fabric/graphics (= 1000.0.0)
+    - React/fabric/uimanager (= 1000.0.0)
+    - React/fabric/view (= 1000.0.0)
+  - React/fabric/core (1000.0.0):
+    - Folly (= 2016.10.31.00)
+  - React/fabric/debug (1000.0.0):
+    - Folly (= 2016.10.31.00)
+  - React/fabric/graphics (1000.0.0):
+    - Folly (= 2016.10.31.00)
+  - React/fabric/uimanager (1000.0.0):
+    - Folly (= 2016.10.31.00)
+  - React/fabric/view (1000.0.0):
+    - Folly (= 2016.10.31.00)
+    - yoga
   - React/fishhook (1000.0.0)
   - React/jschelpers (1000.0.0):
     - Folly (= 2016.10.31.00)
@@ -37,6 +58,11 @@ PODS:
   - React/RCTCameraRoll (1000.0.0):
     - React/Core
     - React/RCTImage
+  - React/RCTFabric (1000.0.0):
+    - Folly (= 2016.10.31.00)
+    - React/Core
+    - React/CxxExceptions
+    - React/fabric
   - React/RCTGeolocation (1000.0.0):
     - React/Core
   - React/RCTImage (1000.0.0):
@@ -72,6 +98,7 @@ DEPENDENCIES:
   - React/RCTAnimation (from `../`)
   - React/RCTBlob (from `../`)
   - React/RCTCameraRoll (from `../`)
+  - React/RCTFabric (from `../`)
   - React/RCTGeolocation (from `../`)
   - React/RCTImage (from `../`)
   - React/RCTLinkingIOS (from `../`)
@@ -104,9 +131,9 @@ SPEC CHECKSUMS:
   DoubleConversion: e22e0762848812a87afd67ffda3998d9ef29170c
   Folly: 9a8eea4725a0b6ba3256ebf206c21e352c23abf8
   glog: 1de0bb937dccdc981596d3b5825ebfb765017ded
-  React: 4e8050da47914f710f7bf48d1aca39fd9afafe39
+  React: e3382e39c51a5e5889248e97c6b9b1b3ca443a08
   yoga: bdd268c5812f00bdb52cc2b58f129797e97935eb
 
-PODFILE CHECKSUM: 2db1aae50ba1389ea02bbb867efcf85182b0336a
+PODFILE CHECKSUM: 1a96172007b66aa74825c234f17139dd9c3d3cd7
 
 COCOAPODS: 1.5.0
diff --git a/React.podspec b/React.podspec
index ac3df357ad1c..027016aa07cb 100644
--- a/React.podspec
+++ b/React.podspec
@@ -52,7 +52,7 @@ Pod::Spec.new do |s|
                               "React/Inspector/*",
                               "ReactCommon/yoga/*",
                               "React/Cxx*/*",
-                              "React/Fabric/**/*",
+                              "React/Fabric/**/*"
     ss.ios.exclude_files    = "React/**/RCTTV*.*"
     ss.tvos.exclude_files   = "React/Modules/RCTClipboard*",
                               "React/Views/RCTDatePicker*",
@@ -79,7 +79,7 @@ Pod::Spec.new do |s|
 
   s.subspec "CxxExceptions" do |ss|
     ss.dependency             "React/CxxBridge"
-    ss.private_header_files = "React/CxxExceptions/*.h"
+    ss.dependency             "React/exceptions"
     ss.source_files         = "React/CxxExceptions/*.{h,m,mm}"
   end
 
@@ -90,6 +90,19 @@ Pod::Spec.new do |s|
                               "React/Inspector/*"
   end
 
+  s.subspec "RCTFabric" do |ss|
+    ss.dependency             "Folly", folly_version
+    ss.dependency             "React/Core"
+    ss.dependency             "React/CxxExceptions"
+    ss.dependency             "React/fabric"
+    ss.compiler_flags       = folly_compiler_flags
+    ss.source_files         = "React/Fabric/**/*.{c,h,m,mm,S,cpp}"
+    ss.exclude_files        = "**/tests/*"
+    ss.header_dir           = "React"
+    ss.framework            = "JavaScriptCore"
+    ss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\"" }
+  end
+
   s.subspec "tvOS" do |ss|
     ss.dependency             "React/Core"
     ss.source_files         = "React/**/RCTTV*.{h, m}"
@@ -129,6 +142,61 @@ Pod::Spec.new do |s|
     ss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/boost-for-react-native\" \"$(PODS_ROOT)/DoubleConversion\" \"$(PODS_ROOT)/Folly\"" }
   end
 
+  s.subspec "exceptions" do |ss|
+    ss.source_files         = "ReactCommon/exceptions/*.{cpp,h}"
+    ss.header_dir           = "cxxreact"
+    ss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\"" }
+  end
+
+  s.subspec "fabric" do |ss|
+    ss.subspec "core" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/core/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/core"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
+    ss.subspec "debug" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/debug/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/debug"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
+    ss.subspec "graphics" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/graphics/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/graphics"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
+    ss.subspec "uimanager" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/uimanager/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/uimanager"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
+    ss.subspec "view" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.dependency             "yoga"
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/view/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/view"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
+  end
+
   s.subspec "ART" do |ss|
     ss.dependency             "React/Core"
     ss.source_files         = "Libraries/ART/**/*.{h,m}"
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index e2f3233980d5..5ba9138d9baa 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -13,7 +13,7 @@
 #include <fabric/core/LayoutContext.h>
 #include <fabric/debug/DebugStringConvertible.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/view/ViewcomponentDescriptor.h>
+#include <fabric/view/ViewComponentDescriptor.h>
 #include <fabric/view/ViewProps.h>
 #include <fabric/view/ViewShadowNode.h>
 

From 7e58e2cbf6910a6b34e932e6494b2fb8ed6bf466 Mon Sep 17 00:00:00 2001
From: Patrice Vignola <vignola.patrice@gmail.com>
Date: Fri, 13 Apr 2018 19:59:06 -0700
Subject: [PATCH 0298/1109] Remove duplicate prop definition

Summary:
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

- This is most likely a merge issue?
- hasTVPreferredFocus was duplicated in the Flow types definition for the Button component, but the PropTypes are fine

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Removing a duplicated prop can't really throw a Flow error. Anyway, I removed the duplicated prop and successfully ran `$ yarn flow`

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

None

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[GENERAL] [ENHANCEMENT] [Button] - Remove duplicate prop definition

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18845

Differential Revision: D7627621

Pulled By: mdvacca

fbshipit-source-id: 924522641a334212f5e2c1310d81da1e321f19b1
---
 Libraries/Components/Button.js | 1 -
 1 file changed, 1 deletion(-)

diff --git a/Libraries/Components/Button.js b/Libraries/Components/Button.js
index 4370f3571c10..51ca2aa636c3 100644
--- a/Libraries/Components/Button.js
+++ b/Libraries/Components/Button.js
@@ -57,7 +57,6 @@ class Button extends React.Component<{
   accessibilityLabel?: ?string,
   disabled?: ?boolean,
   testID?: ?string,
-  hasTVPreferredFocus?: ?boolean,
 }> {
   static propTypes = {
     /**

From a42b2988ae3cf995b8ffe37609e40a7a8b983c06 Mon Sep 17 00:00:00 2001
From: Jakub Grzmiel <jakubgr@fb.com>
Date: Sat, 14 Apr 2018 13:04:28 -0700
Subject: [PATCH 0299/1109] Clean up BUCK files for missing dependencies and
 tests

Differential Revision: D7618360

fbshipit-source-id: 421834892519998ad088a138b3fc3d96afe34d79
---
 ReactAndroid/src/main/jni/first-party/fb/jni/java/BUCK | 4 ++--
 ReactCommon/cxxreact/BUCK                              | 1 +
 ReactCommon/fabric/core/BUCK                           | 8 +++++---
 ReactCommon/fabric/debug/BUCK                          | 8 +++++---
 ReactCommon/fabric/graphics/BUCK                       | 8 +++++---
 ReactCommon/fabric/uimanager/BUCK                      | 8 +++++---
 ReactCommon/fabric/view/BUCK                           | 8 +++++---
 7 files changed, 28 insertions(+), 17 deletions(-)

diff --git a/ReactAndroid/src/main/jni/first-party/fb/jni/java/BUCK b/ReactAndroid/src/main/jni/first-party/fb/jni/java/BUCK
index afec30c511f9..8b2cb7b5941a 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/jni/java/BUCK
+++ b/ReactAndroid/src/main/jni/first-party/fb/jni/java/BUCK
@@ -1,6 +1,6 @@
-load("//ReactNative:DEFS.bzl", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_java_library")
 
-java_library(
+rn_java_library(
     name = "java",
     srcs = glob(["**/*.java"]),
     visibility = ["PUBLIC"],
diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 6201e74cdf3b..43a5ce58276e 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -141,6 +141,7 @@ rn_xplat_cxx_library(
     ],
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
     force_static = True,
+    macosx_tests_override = [],
     platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index d9ee58fae8b5..913078944214 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -35,14 +35,16 @@ rn_xplat_cxx_library(
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_tests = [
+        ":tests",
+    ],
     force_static = True,
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
-    tests = [
-        ":tests",
-    ],
+    macosx_tests_override = [],
+    tests = [],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//fbsystrace:fbsystrace",
diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index d22caf8f9556..abc85f94c325 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -32,14 +32,16 @@ rn_xplat_cxx_library(
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_tests = [
+        ":tests",
+    ],
     force_static = True,
+    macosx_tests_override = [],
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
-    tests = [
-        ":tests",
-    ],
+    tests = [],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//folly:headers_only",
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index 967f33aafc9b..82a91faa4f45 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -32,14 +32,16 @@ rn_xplat_cxx_library(
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_tests = [
+        ":tests",
+    ],
     force_static = True,
+    macosx_tests_override = [],
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
-    tests = [
-        ":tests",
-    ],
+    tests = [],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//fbsystrace:fbsystrace",
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index ca7700e5c44b..9d1c076a9052 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -32,14 +32,16 @@ rn_xplat_cxx_library(
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_tests = [
+        ":tests",
+    ],
     force_static = True,
+    macosx_tests_override = [],
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
-    tests = [
-        ":tests",
-    ],
+    tests = [],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//fbsystrace:fbsystrace",
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 5716485f77e5..5202ded14a0f 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -35,14 +35,16 @@ rn_xplat_cxx_library(
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_tests = [
+        ":tests",
+    ],
     force_static = True,
+    macosx_tests_override = [],
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
-    tests = [
-        ":tests",
-    ],
+    tests = [],
     visibility = ["PUBLIC"],
     deps = [
         "xplat//fbsystrace:fbsystrace",

From c866ef243e0f475affed9518510ccdf9a951b19d Mon Sep 17 00:00:00 2001
From: Jakub Grzmiel <jakubgr@fb.com>
Date: Sat, 14 Apr 2018 15:27:04 -0700
Subject: [PATCH 0300/1109] Clean up BUCK files for missing dependencies and
 tests

Differential Revision: D7625433

fbshipit-source-id: 332b7ff7eaed82cb52f459921f1ae67b702a1636
---
 ReactCommon/fabric/uimanager/BUCK | 1 +
 ReactCommon/fabric/view/BUCK      | 1 +
 2 files changed, 2 insertions(+)

diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 9d1c076a9052..218b8ea92ebf 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -37,6 +37,7 @@ rn_xplat_cxx_library(
     ],
     force_static = True,
     macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 5202ded14a0f..8bdb1b175a39 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -40,6 +40,7 @@ rn_xplat_cxx_library(
     ],
     force_static = True,
     macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",

From 2fd7fda05d5dfd63af529838bf3511dca19877fc Mon Sep 17 00:00:00 2001
From: Jonathan Kim <jjkim@fb.com>
Date: Sat, 14 Apr 2018 18:37:38 -0700
Subject: [PATCH 0301/1109] Delete fb_xplat_cxx.bzl

Reviewed By: mzlee, ttsugriy

Differential Revision: D7625836

fbshipit-source-id: 3169d43f028b895e1075268495de66816c778b35
---
 ReactCommon/cxxreact/tests/BUCK | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/cxxreact/tests/BUCK b/ReactCommon/cxxreact/tests/BUCK
index 010e7c8e50d0..1d7657cc01ec 100644
--- a/ReactCommon/cxxreact/tests/BUCK
+++ b/ReactCommon/cxxreact/tests/BUCK
@@ -11,7 +11,7 @@ TEST_SRCS = [
 ]
 
 if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx.bzl", "cxx_test")
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "cxx_test")
     load("@xplat//configurations/buck/android:jni_instrumentation_test", "jni_instrumentation_test_lib")
     load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
     jni_instrumentation_test_lib(

From 3fd2e2da4fd5881e469cfda1f2e261e880fb1cab Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 16 Apr 2018 07:43:22 -0700
Subject: [PATCH 0302/1109] Fabric/Text/Prep: Refined ComponentDescriptor
 interface

Summary:
The new interface of ComponentDescriptor makes ShadowNode creation/cloning process a bit more explicit:
Now customers (UIManager) must prepare Props object explicitly before creation or cloning.
Besides general clarity, we need this to prepare for a new virtual `ShadowNode::clone()` method which will serve "virtual constructor" role,
redirecting execution to concrete ComponentDescriptor instance.

Actually, the whole purpose of concrete ComponentDescriptor instance is serve "virtual constructor" role (and all this code should be "templated").

Reviewed By: mdvacca

Differential Revision: D7591714

fbshipit-source-id: 8793b3ef70ed7ae113efb36ad1eee20573360dc8
---
 .../componentdescriptor/ComponentDescriptor.h | 15 ++++++-
 .../ConcreteComponentDescriptor.h             | 18 +++++---
 .../core/tests/ComponentDescriptorTest.cpp    | 13 +++---
 .../fabric/uimanager/FabricUIManager.cpp      | 42 ++++++++++++++++---
 4 files changed, 70 insertions(+), 18 deletions(-)

diff --git a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
index 7b7b7a5578d6..1b92620d9fdc 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
@@ -48,7 +48,7 @@ class ComponentDescriptor {
     const Tag &tag,
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
-    const RawProps &rawProps
+    const SharedProps &props
   ) const = 0;
 
   /*
@@ -56,7 +56,7 @@ class ComponentDescriptor {
    */
   virtual SharedShadowNode cloneShadowNode(
     const SharedShadowNode &shadowNode,
-    const SharedRawProps &rawProps = nullptr,
+    const SharedProps &props = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ) const = 0;
 
@@ -67,6 +67,17 @@ class ComponentDescriptor {
     const SharedShadowNode &parentShadowNode,
     const SharedShadowNode &childShadowNode
   ) const = 0;
+
+  /*
+   * Creates a new `Props` of a particular type with all values copied from
+   * `props` and `rawProps` applied on top of this.
+   * If `props` is `nullptr`, a default `Props` object (with default values)
+   * will be used.
+   */
+  virtual SharedProps cloneProps(
+    const SharedProps &props,
+    const RawProps &rawProps
+  ) const = 0;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 95de5e17534d..8739d849a4a1 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -26,6 +26,7 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   static_assert(std::is_base_of<ShadowNode, ShadowNodeT>::value, "ShadowNodeT must be a descendant of ShadowNode");
 
   using SharedShadowNodeT = std::shared_ptr<const ShadowNodeT>;
+  using ConcreteProps = typename ShadowNodeT::ConcreteProps;
   using SharedConcreteProps = typename ShadowNodeT::SharedConcreteProps;
 
 public:
@@ -37,19 +38,17 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     const Tag &tag,
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
-    const RawProps &rawProps
+    const SharedProps &props
   ) const override {
-    auto props = ShadowNodeT::Props(rawProps);
-    return std::make_shared<ShadowNodeT>(tag, rootTag, instanceHandle, props);
+    return std::make_shared<ShadowNodeT>(tag, rootTag, instanceHandle, std::static_pointer_cast<const ConcreteProps>(props));
   }
 
   SharedShadowNode cloneShadowNode(
     const SharedShadowNode &shadowNode,
-    const SharedRawProps &rawProps = nullptr,
+    const SharedProps &props = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ) const override {
-    const SharedConcreteProps props = rawProps ? ShadowNodeT::Props(*rawProps, shadowNode->getProps()) : nullptr;
-    return std::make_shared<ShadowNodeT>(std::static_pointer_cast<const ShadowNodeT>(shadowNode), props, children);
+    return std::make_shared<ShadowNodeT>(std::static_pointer_cast<const ShadowNodeT>(shadowNode), std::static_pointer_cast<const ConcreteProps>(props), children);
   }
 
   void appendChild(
@@ -61,6 +60,13 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     concreteNonConstParentShadowNode->appendChild(childShadowNode);
   }
 
+  virtual SharedProps cloneProps(
+    const SharedProps &props,
+    const RawProps &rawProps
+  ) const override {
+    return ShadowNodeT::Props(rawProps, props);
+  };
+
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
index 699642ce7f2d..5c2a0bc9d296 100644
--- a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
+++ b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
@@ -19,7 +19,8 @@ TEST(ComponentDescriptorTest, createShadowNode) {
 
   RawProps raw;
   raw["nativeID"] = "abc";
-  SharedShadowNode node = descriptor->createShadowNode(9, 1, (void *)NULL, raw);
+  SharedProps props = descriptor->cloneProps(nullptr, raw);
+  SharedShadowNode node = descriptor->createShadowNode(9, 1, (void *)NULL, props);
 
   ASSERT_EQ(node->getComponentHandle(), typeid(TestShadowNode).hash_code());
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
@@ -35,7 +36,8 @@ TEST(ComponentDescriptorTest, cloneShadowNode) {
 
   RawProps raw;
   raw["nativeID"] = "abc";
-  SharedShadowNode node = descriptor->createShadowNode(9, 1, (void *)NULL, raw);
+  SharedProps props = descriptor->cloneProps(nullptr, raw);
+  SharedShadowNode node = descriptor->createShadowNode(9, 1, (void *)NULL, props);
   SharedShadowNode cloned = descriptor->cloneShadowNode(node);
 
   ASSERT_EQ(cloned->getComponentHandle(), typeid(TestShadowNode).hash_code());
@@ -52,9 +54,10 @@ TEST(ComponentDescriptorTest, appendChild) {
 
   RawProps raw;
   raw["nativeID"] = "abc";
-  SharedShadowNode node1 = descriptor->createShadowNode(1, 1, (void *)NULL, raw);
-  SharedShadowNode node2 = descriptor->createShadowNode(2, 1, (void *)NULL, raw);
-  SharedShadowNode node3 = descriptor->createShadowNode(3, 1, (void *)NULL, raw);
+  SharedProps props = descriptor->cloneProps(nullptr, raw);
+  SharedShadowNode node1 = descriptor->createShadowNode(1, 1, (void *)NULL, props);
+  SharedShadowNode node2 = descriptor->createShadowNode(2, 1, (void *)NULL, props);
+  SharedShadowNode node3 = descriptor->createShadowNode(3, 1, (void *)NULL, props);
 
   descriptor->appendChild(node1, node2);
   descriptor->appendChild(node1, node3);
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 5ba9138d9baa..202073283121 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -54,7 +54,15 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
   LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)["View"];
   RawProps rawProps = rawPropsFromDynamic(props);
-  SharedShadowNode shadowNode = componentDescriptor->createShadowNode(tag, rootTag, instanceHandle, rawProps);
+
+  SharedShadowNode shadowNode =
+    componentDescriptor->createShadowNode(
+      tag,
+      rootTag,
+      instanceHandle,
+      componentDescriptor->cloneProps(nullptr, rawProps)
+    );
+
   LOG(INFO) << "FabricUIManager::createNode() -> " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
 
   if (delegate_) {
@@ -67,7 +75,10 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
 SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode) {
   LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
-  SharedShadowNode clonedShadowNode = componentDescriptor->cloneShadowNode(shadowNode);
+
+  SharedShadowNode clonedShadowNode =
+    componentDescriptor->cloneShadowNode(shadowNode);
+
   LOG(INFO) << "FabricUIManager::cloneNode() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }
@@ -76,7 +87,14 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   // Assuming semantic: Cloning with same props but empty children.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
-  SharedShadowNode clonedShadowNode = componentDescriptor->cloneShadowNode(shadowNode, nullptr, ShadowNode::emptySharedShadowNodeSharedList());
+
+  SharedShadowNode clonedShadowNode =
+    componentDescriptor->cloneShadowNode(
+      shadowNode,
+      nullptr,
+      ShadowNode::emptySharedShadowNodeSharedList()
+    );
+
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }
@@ -86,7 +104,14 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
   // Assuming semantic: Cloning with same children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
-  SharedShadowNode clonedShadowNode = componentDescriptor->cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), nullptr);
+
+  SharedShadowNode clonedShadowNode =
+    componentDescriptor->cloneShadowNode(
+      shadowNode,
+      componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
+      nullptr
+    );
+
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }
@@ -96,7 +121,14 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
   // Assuming semantic: Cloning with empty children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
-  SharedShadowNode clonedShadowNode = componentDescriptor->cloneShadowNode(shadowNode, std::make_shared<const RawProps>(rawProps), ShadowNode::emptySharedShadowNodeSharedList());
+
+  SharedShadowNode clonedShadowNode =
+    componentDescriptor->cloneShadowNode(
+      shadowNode,
+      componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
+      ShadowNode::emptySharedShadowNodeSharedList()
+    );
+
   LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }

From c399d697166301a823c7f7250b37ba5112e7bcc7 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 16 Apr 2018 07:43:23 -0700
Subject: [PATCH 0303/1109] Fabric: More restrictive types (const &) for
 ShadowNode constuctors' arguments

Summary: Should be more performant theoretically.

Reviewed By: mdvacca

Differential Revision: D7591713

fbshipit-source-id: 74141053f2b91cb621cc0d573f89f3454512c585
---
 .../fabric/core/shadownode/ShadowNode.cpp        | 16 ++++++++--------
 ReactCommon/fabric/core/shadownode/ShadowNode.h  | 16 ++++++++--------
 2 files changed, 16 insertions(+), 16 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 3c9fa034bdbe..e7c6b68f22ef 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -21,11 +21,11 @@ SharedShadowNodeSharedList ShadowNode::emptySharedShadowNodeSharedList() {
 #pragma mark - Constructors
 
 ShadowNode::ShadowNode(
-  Tag tag,
-  Tag rootTag,
-  InstanceHandle instanceHandle,
-  SharedProps props,
-  SharedShadowNodeSharedList children
+  const Tag &tag,
+  const Tag &rootTag,
+  const InstanceHandle &instanceHandle,
+  const SharedProps &props,
+  const SharedShadowNodeSharedList &children
 ):
   tag_(tag),
   rootTag_(rootTag),
@@ -35,9 +35,9 @@ ShadowNode::ShadowNode(
   revision_(1) {}
 
 ShadowNode::ShadowNode(
-  SharedShadowNode shadowNode,
-  SharedProps props,
-  SharedShadowNodeSharedList children
+  const SharedShadowNode &shadowNode,
+  const SharedProps &props,
+  const SharedShadowNodeSharedList &children
 ):
   tag_(shadowNode->tag_),
   rootTag_(shadowNode->rootTag_),
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 48e840fd6798..a5b8a2ff9da6 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -35,17 +35,17 @@ class ShadowNode:
 #pragma mark - Constructors
 
   ShadowNode(
-    Tag tag,
-    Tag rootTag,
-    InstanceHandle instanceHandle,
-    SharedProps props = SharedProps(),
-    SharedShadowNodeSharedList children = SharedShadowNodeSharedList()
+    const Tag &tag,
+    const Tag &rootTag,
+    const InstanceHandle &instanceHandle,
+    const SharedProps &props = SharedProps(),
+    const SharedShadowNodeSharedList &children = SharedShadowNodeSharedList()
   );
 
   ShadowNode(
-    SharedShadowNode shadowNode,
-    SharedProps props = nullptr,
-    SharedShadowNodeSharedList children = nullptr
+    const SharedShadowNode &shadowNode,
+    const SharedProps &props = nullptr,
+    const SharedShadowNodeSharedList &children = nullptr
   );
 
 #pragma mark - Getters

From 82bd4337c9b3c58fc8c2cad5f32a0b8908a3bc07 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 16 Apr 2018 07:43:25 -0700
Subject: [PATCH 0304/1109] Fabric: Fixed ComponentDescriptorTest

Summary: Trivial.

Reviewed By: mdvacca

Differential Revision: D7591712

fbshipit-source-id: fbcaaa30004f096749a6bcd47dcc56c060d7524a
---
 ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp | 8 ++------
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
index 5c2a0bc9d296..460a3124bc3e 100644
--- a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
+++ b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
@@ -26,9 +26,7 @@ TEST(ComponentDescriptorTest, createShadowNode) {
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
   ASSERT_EQ(node->getTag(), 9);
   ASSERT_EQ(node->getRootTag(), 1);
-
-  // TODO(#27369757): getProps() doesn't work
-  // ASSERT_STREQ(node->getProps()->getNativeId().c_str(), "testNativeID");
+  ASSERT_STREQ(node->getProps()->getNativeId().c_str(), "abc");
 }
 
 TEST(ComponentDescriptorTest, cloneShadowNode) {
@@ -44,9 +42,7 @@ TEST(ComponentDescriptorTest, cloneShadowNode) {
   ASSERT_STREQ(cloned->getComponentName().c_str(), "Test");
   ASSERT_EQ(cloned->getTag(), 9);
   ASSERT_EQ(cloned->getRootTag(), 1);
-
-  // TODO(#27369757): getProps() doesn't work
-  // ASSERT_STREQ(cloned->getProps()->getNativeId().c_str(), "testNativeID");
+  ASSERT_STREQ(cloned->getProps()->getNativeId().c_str(), "abc");
 }
 
 TEST(ComponentDescriptorTest, appendChild) {

From 8621d4b79731e13a0c6e397abd93c193c6219000 Mon Sep 17 00:00:00 2001
From: TomSwift <nicholashodapp@ip-10-10-2-134.us-west-2.compute.internal>
Date: Mon, 16 Apr 2018 08:59:26 -0700
Subject: [PATCH 0305/1109] iOS textTransform style support

Summary:
Issue [#2088](https://github.com/facebook/react-native/issues/2088).

The basic desire is to have a declarative mechanism to transform text content to uppercase or lowercase or titlecase ("capitalized").

My test plan involves having added a test-case to the RNTester app within the `<Text>` component area.   I then manually verified that the rendered content met my expectation.

Here is the markup that exercises my enhancement:

```
<View>
  <Text style={{ textTransform: 'uppercase'}}>
    This text should be uppercased.
  </Text>
  <Text style={{ textTransform: 'lowercase'}}>
    This TEXT SHOULD be lowercased.
  </Text>
  <Text style={{ textTransform: 'capitalize'}}>
    This text should be CAPITALIZED.
  </Text>
  <Text style={{ textTransform: 'capitalize'}}>
    Mixed:{' '}
    <Text style={{ textTransform: 'uppercase'}}>
      uppercase{' '}
    </Text>
    <Text style={{ textTransform: 'lowercase'}}>
      LoWeRcAsE{' '}
    </Text>
    <Text style={{ textTransform: 'capitalize'}}>
      capitalize each word
    </Text>
  </Text>
</View>
```

And here is a screenshot of the result:

![screen shot 2018-03-14 at 3 01 02 pm](https://user-images.githubusercontent.com/575821/37433772-7abe7fa0-279a-11e8-9ec9-fb3aa1952dad.png)

[Website Documentation PR](https://github.com/facebook/react-native-website/pull/254)
https://github.com/facebook/react-native-website/pull/254

[IOS] [ENHANCEMENT] [Text] - added textTransform style property enabling declarative casing transformations
Closes https://github.com/facebook/react-native/pull/18387

Differential Revision: D7583315

Pulled By: shergin

fbshipit-source-id: a5d22aea2aa4f494b7b25a055abe64799ccbaa79
---
 Libraries/StyleSheet/StyleSheetTypes.js       |  1 +
 .../Text/BaseText/RCTBaseTextShadowView.m     |  2 +-
 .../Text/BaseText/RCTBaseTextViewManager.m    |  1 +
 Libraries/Text/RCTConvert+Text.h              |  2 ++
 Libraries/Text/RCTConvert+Text.m              |  7 ++++
 .../Text/RCTText.xcodeproj/project.pbxproj    |  6 ++++
 Libraries/Text/RCTTextAttributes.h            |  7 ++++
 Libraries/Text/RCTTextAttributes.m            | 20 ++++++++++-
 Libraries/Text/RCTTextTransform.h             | 16 +++++++++
 Libraries/Text/TextStylePropTypes.js          |  6 ++++
 RNTester/js/TextExample.ios.js                | 36 +++++++++++++++++++
 11 files changed, 102 insertions(+), 2 deletions(-)
 create mode 100644 Libraries/Text/RCTTextTransform.h

diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index cd80f8b8d6e0..ffec5b54bc79 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -201,6 +201,7 @@ export type ____TextStyle_Internal = $ReadOnly<{|
     | 'underline line-through',
   textDecorationStyle?: 'solid' | 'double' | 'dotted' | 'dashed',
   textDecorationColor?: ColorValue,
+  textTransform?: 'none' | 'capitalize' | 'uppercase' | 'lowercase',
   writingDirection?: 'auto' | 'ltr' | 'rtl',
 |}>;
 
diff --git a/Libraries/Text/BaseText/RCTBaseTextShadowView.m b/Libraries/Text/BaseText/RCTBaseTextShadowView.m
index 85162926eb19..49ce7690dfc9 100644
--- a/Libraries/Text/BaseText/RCTBaseTextShadowView.m
+++ b/Libraries/Text/BaseText/RCTBaseTextShadowView.m
@@ -63,7 +63,7 @@ - (NSAttributedString *)attributedTextWithBaseTextAttributes:(nullable RCTTextAt
       NSString *text = rawTextShadowView.text;
       if (text) {
         NSAttributedString *rawTextAttributedString =
-          [[NSAttributedString alloc] initWithString:rawTextShadowView.text
+          [[NSAttributedString alloc] initWithString:[textAttributes applyTextAttributesToText:text]
                                           attributes:textAttributes.effectiveTextAttributes];
         [attributedText appendAttributedString:rawTextAttributedString];
       }
diff --git a/Libraries/Text/BaseText/RCTBaseTextViewManager.m b/Libraries/Text/BaseText/RCTBaseTextViewManager.m
index a5d0b2c63097..2cf43ebf38cf 100644
--- a/Libraries/Text/BaseText/RCTBaseTextViewManager.m
+++ b/Libraries/Text/BaseText/RCTBaseTextViewManager.m
@@ -51,5 +51,6 @@ - (RCTShadowView *)shadowView
 RCT_REMAP_SHADOW_PROPERTY(textShadowColor, textAttributes.textShadowColor, UIColor)
 // Special
 RCT_REMAP_SHADOW_PROPERTY(isHighlighted, textAttributes.isHighlighted, BOOL)
+RCT_REMAP_SHADOW_PROPERTY(textTransform, textAttributes.textTransform, RCTTextTransform)
 
 @end
diff --git a/Libraries/Text/RCTConvert+Text.h b/Libraries/Text/RCTConvert+Text.h
index 4cead0948ab7..81a3c7ccfaff 100644
--- a/Libraries/Text/RCTConvert+Text.h
+++ b/Libraries/Text/RCTConvert+Text.h
@@ -6,6 +6,7 @@
  */
 
 #import <React/RCTConvert.h>
+#import <RCTText/RCTTextTransform.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
@@ -13,6 +14,7 @@ NS_ASSUME_NONNULL_BEGIN
 
 + (UITextAutocorrectionType)UITextAutocorrectionType:(nullable id)json;
 + (UITextSpellCheckingType)UITextSpellCheckingType:(nullable id)json;
++ (RCTTextTransform)RCTTextTransform:(nullable id)json;
 
 @end
 
diff --git a/Libraries/Text/RCTConvert+Text.m b/Libraries/Text/RCTConvert+Text.m
index d4d1b167c879..aaf7c1383c1c 100644
--- a/Libraries/Text/RCTConvert+Text.m
+++ b/Libraries/Text/RCTConvert+Text.m
@@ -25,4 +25,11 @@ + (UITextSpellCheckingType)UITextSpellCheckingType:(id)json
     UITextSpellCheckingTypeNo;
 }
 
+RCT_ENUM_CONVERTER(RCTTextTransform, (@{
+  @"none": @(RCTTextTransformNone),
+  @"capitalize": @(RCTTextTransformCapitalize),
+  @"uppercase": @(RCTTextTransformUppercase),
+  @"lowercase": @(RCTTextTransformLowercase),
+}), RCTTextTransformUndefined, integerValue)
+
 @end
diff --git a/Libraries/Text/RCTText.xcodeproj/project.pbxproj b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
index 8fc301593f03..9765d035fedd 100644
--- a/Libraries/Text/RCTText.xcodeproj/project.pbxproj
+++ b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
@@ -104,6 +104,8 @@
 		5956B1A7200FF35C008D9D16 /* RCTVirtualTextShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */; };
 		5956B1A8200FF35C008D9D16 /* RCTVirtualTextViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12B200FEBAA008D9D16 /* RCTVirtualTextViewManager.m */; };
 		5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */; };
+		5970936920845EFC00D163A7 /* RCTTextTransform.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5970936820845DDE00D163A7 /* RCTTextTransform.h */; };
+		5970936A20845F0600D163A7 /* RCTTextTransform.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5970936820845DDE00D163A7 /* RCTTextTransform.h */; };
 		8F2807C7202D2B6B005D65E6 /* RCTInputAccessoryViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */; };
 		8F2807C8202D2B6B005D65E6 /* RCTInputAccessoryView.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */; };
 		8F2807C9202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C5202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m */; };
@@ -116,6 +118,7 @@
 			dstPath = include/RCTText;
 			dstSubfolderSpec = 16;
 			files = (
+				5970936920845EFC00D163A7 /* RCTTextTransform.h in Copy Headers */,
 				5956B160200FF324008D9D16 /* RCTBaseTextShadowView.h in Copy Headers */,
 				5956B161200FF324008D9D16 /* RCTBaseTextViewManager.h in Copy Headers */,
 				5956B162200FF324008D9D16 /* RCTRawTextShadowView.h in Copy Headers */,
@@ -151,6 +154,7 @@
 			dstPath = include/RCTText;
 			dstSubfolderSpec = 16;
 			files = (
+				5970936A20845F0600D163A7 /* RCTTextTransform.h in Copy Headers */,
 				5956B179200FF338008D9D16 /* RCTBaseTextShadowView.h in Copy Headers */,
 				5956B17A200FF338008D9D16 /* RCTBaseTextViewManager.h in Copy Headers */,
 				5956B17B200FF338008D9D16 /* RCTRawTextShadowView.h in Copy Headers */,
@@ -235,6 +239,7 @@
 		5956B12F200FEBAA008D9D16 /* RCTConvert+Text.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "RCTConvert+Text.m"; sourceTree = "<group>"; };
 		5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryShadowView.m; sourceTree = "<group>"; };
 		5C245F38205E216A00D936E9 /* RCTInputAccessoryShadowView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryShadowView.h; sourceTree = "<group>"; };
+		5970936820845DDE00D163A7 /* RCTTextTransform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTTextTransform.h; sourceTree = "<group>"; };
 		8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryViewManager.m; sourceTree = "<group>"; };
 		8F2807C2202D2B6A005D65E6 /* RCTInputAccessoryViewContent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryViewContent.h; sourceTree = "<group>"; };
 		8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryView.m; sourceTree = "<group>"; };
@@ -254,6 +259,7 @@
 				5956B12F200FEBAA008D9D16 /* RCTConvert+Text.m */,
 				5956B11A200FEBA9008D9D16 /* RCTTextAttributes.h */,
 				5956B120200FEBA9008D9D16 /* RCTTextAttributes.m */,
+				5970936820845DDE00D163A7 /* RCTTextTransform.h */,
 				5956B121200FEBAA008D9D16 /* Text */,
 				5956B0FF200FEBA9008D9D16 /* TextInput */,
 				5956B12A200FEBAA008D9D16 /* VirtualText */,
diff --git a/Libraries/Text/RCTTextAttributes.h b/Libraries/Text/RCTTextAttributes.h
index df9171c85d0a..802211909a42 100644
--- a/Libraries/Text/RCTTextAttributes.h
+++ b/Libraries/Text/RCTTextAttributes.h
@@ -8,6 +8,7 @@
 #import <UIKit/UIKit.h>
 
 #import <React/RCTTextDecorationLineType.h>
+#import <RCTText/RCTTextTransform.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
@@ -50,6 +51,7 @@ extern NSString *const RCTTextAttributesTagAttributeName;
 @property (nonatomic, assign) BOOL isHighlighted;
 @property (nonatomic, strong, nullable) NSNumber *tag;
 @property (nonatomic, assign) UIUserInterfaceLayoutDirection layoutDirection;
+@property (nonatomic, assign) RCTTextTransform textTransform;
 
 #pragma mark - Inheritance
 
@@ -78,6 +80,11 @@ extern NSString *const RCTTextAttributesTagAttributeName;
 - (UIColor *)effectiveForegroundColor;
 - (UIColor *)effectiveBackgroundColor;
 
+/**
+ * Text transformed per 'none', 'uppercase', 'lowercase', 'capitalize'
+ */
+- (NSString *)applyTextAttributesToText:(NSString *)text;
+
 @end
 
 NS_ASSUME_NONNULL_END
diff --git a/Libraries/Text/RCTTextAttributes.m b/Libraries/Text/RCTTextAttributes.m
index d74e0ab7611b..4309138d00fe 100644
--- a/Libraries/Text/RCTTextAttributes.m
+++ b/Libraries/Text/RCTTextAttributes.m
@@ -28,6 +28,7 @@ - (instancetype)init
     _baseWritingDirection = NSWritingDirectionNatural;
     _textShadowRadius = NAN;
     _opacity = NAN;
+    _textTransform = RCTTextTransformUndefined;
   }
 
   return self;
@@ -73,6 +74,7 @@ - (void)applyTextAttributes:(RCTTextAttributes *)textAttributes
   _isHighlighted = textAttributes->_isHighlighted || _isHighlighted;  // *
   _tag = textAttributes->_tag ?: _tag;
   _layoutDirection = textAttributes->_layoutDirection != UIUserInterfaceLayoutDirectionLeftToRight ? textAttributes->_layoutDirection : _layoutDirection;
+  _textTransform = textAttributes->_textTransform != RCTTextTransformUndefined ? textAttributes->_textTransform : _textTransform;
 }
 
 - (NSDictionary<NSAttributedStringKey, id> *)effectiveTextAttributes
@@ -214,6 +216,21 @@ - (UIColor *)effectiveBackgroundColor
   return effectiveBackgroundColor ?: [UIColor clearColor];
 }
 
+- (NSString *)applyTextAttributesToText:(NSString *)text
+{
+  switch (_textTransform) {
+    case RCTTextTransformUndefined:
+    case RCTTextTransformNone:
+      return text;
+    case RCTTextTransformLowercase:
+      return [text lowercaseString];
+    case RCTTextTransformUppercase:
+      return [text uppercaseString];
+    case RCTTextTransformCapitalize:
+      return [text capitalizedString];
+  }
+}
+
 - (RCTTextAttributes *)copyWithZone:(NSZone *)zone
 {
   RCTTextAttributes *textAttributes = [RCTTextAttributes new];
@@ -263,7 +280,8 @@ - (BOOL)isEqual:(RCTTextAttributes *)textAttributes
     // Special
     RCTTextAttributesCompareOthers(_isHighlighted) &&
     RCTTextAttributesCompareObjects(_tag) &&
-    RCTTextAttributesCompareOthers(_layoutDirection);
+    RCTTextAttributesCompareOthers(_layoutDirection) &&
+    RCTTextAttributesCompareOthers(_textTransform);
 }
 
 @end
diff --git a/Libraries/Text/RCTTextTransform.h b/Libraries/Text/RCTTextTransform.h
new file mode 100644
index 000000000000..eddebd0f0c20
--- /dev/null
+++ b/Libraries/Text/RCTTextTransform.h
@@ -0,0 +1,16 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <Foundation/Foundation.h>
+
+typedef NS_ENUM(NSInteger, RCTTextTransform) {
+  RCTTextTransformUndefined = 0,
+  RCTTextTransformNone,
+  RCTTextTransformCapitalize,
+  RCTTextTransformUppercase,
+  RCTTextTransformLowercase,
+};
diff --git a/Libraries/Text/TextStylePropTypes.js b/Libraries/Text/TextStylePropTypes.js
index c5e67ca99e17..872497ecf2ee 100644
--- a/Libraries/Text/TextStylePropTypes.js
+++ b/Libraries/Text/TextStylePropTypes.js
@@ -84,6 +84,12 @@ const TextStylePropTypes = {
    * @platform ios
    */
   textDecorationColor: ColorPropType,
+  /**
+   * @platform ios
+   */
+  textTransform: ReactPropTypes.oneOf(
+    ['none' /*default*/, 'capitalize', 'uppercase', 'lowercase']
+  ),
   /**
    * @platform ios
    */
diff --git a/RNTester/js/TextExample.ios.js b/RNTester/js/TextExample.ios.js
index e5510390d0a3..939774aa06a0 100644
--- a/RNTester/js/TextExample.ios.js
+++ b/RNTester/js/TextExample.ios.js
@@ -860,6 +860,42 @@ exports.examples = [
     title: 'Text `alignItems: \'baseline\'` style',
     render: function() {
       return <TextBaseLineLayoutExample />;
+    }
+  },
+  {
+    title: 'Transform',
+    render: function() {
+      return (
+        <View>
+          <Text style={{ textTransform: 'uppercase'}}>
+            This text should be uppercased.
+          </Text>
+          <Text style={{ textTransform: 'lowercase'}}>
+            This TEXT SHOULD be lowercased.
+          </Text>
+          <Text style={{ textTransform: 'capitalize'}}>
+            This text should be CAPITALIZED.
+          </Text>
+          <Text style={{ textTransform: 'capitalize'}}>
+            Mixed:{' '}
+            <Text style={{ textTransform: 'uppercase'}}>
+              uppercase{' '}
+            </Text>
+            <Text style={{ textTransform: 'lowercase'}}>
+              LoWeRcAsE{' '}
+            </Text>
+            <Text style={{ textTransform: 'capitalize'}}>
+              capitalize each word
+            </Text>
+          </Text>
+          <Text>Should be "ABC":
+            <Text style={{ textTransform: 'uppercase' }}>a<Text>b</Text>c</Text>
+          </Text>
+          <Text>Should be "AbC":
+            <Text style={{ textTransform: 'uppercase' }}>a<Text style={{ textTransform: 'none' }}>b</Text>c</Text>
+          </Text>
+        </View>
+      );
     },
   },
 ];

From 8102e35271ab68e0525a9c60d86a855bbeef9c1a Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Mon, 16 Apr 2018 12:16:11 -0700
Subject: [PATCH 0306/1109] Fix originalNode memory leak

Reviewed By: mdvacca

Differential Revision: D7608359

fbshipit-source-id: 7cf69f987d4c92202ea5794b76345cb1c685f881
---
 .../main/java/com/facebook/react/fabric/FabricReconciler.java | 4 ++--
 .../main/java/com/facebook/react/fabric/FabricUIManager.java  | 4 +++-
 .../com/facebook/react/uimanager/ReactShadowNodeImpl.java     | 2 +-
 3 files changed, 6 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index 3e8eca9cabeb..ddd3a386fc38 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -61,7 +61,7 @@ private void manageChildren(
       }
       enqueueUpdateProperties(newNode);
       manageChildren(prevNode, prevNode.getChildrenList(), newNode.getChildrenList());
-      prevNode.setOriginalReactShadowNode(newNode);
+      newNode.setOriginalReactShadowNode(null);
     }
     int firstRemovedOrAddedViewIndex = sameReactTagIndex;
 
@@ -78,7 +78,7 @@ private void manageChildren(
       viewsToAdd.add(new ViewAtIndex(newNode.getReactTag(), k));
       List previousChildrenList = newNode.getOriginalReactShadowNode() == null ? null : newNode.getOriginalReactShadowNode().getChildrenList();
       manageChildren(newNode, previousChildrenList, newNode.getChildrenList());
-      newNode.setOriginalReactShadowNode(newNode);
+      newNode.setOriginalReactShadowNode(null);
       addedTags.add(newNode.getReactTag());
     }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 50e24738bf56..191d463ab725 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -18,6 +18,7 @@
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.ReadableNativeMap;
 import com.facebook.react.bridge.UIManager;
+import com.facebook.react.common.annotations.VisibleForTesting;
 import com.facebook.react.modules.i18nmanager.I18nUtil;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
 import com.facebook.react.uimanager.NativeViewHierarchyManager;
@@ -95,7 +96,8 @@ public ReactShadowNode createNode(
     }
   }
 
-  private ReactShadowNode getRootNode(int rootTag) {
+  @VisibleForTesting
+  ReactShadowNode getRootNode(int rootTag) {
     return mRootShadowNodeRegistry.getNode(rootTag);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 018fa5ddace0..d0eb127f6e29 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -11,7 +11,6 @@
 import android.util.Log;
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.uimanager.annotations.ReactPropertyHolder;
-import com.facebook.yoga.YogaNodeCloneFunction;
 import com.facebook.yoga.YogaAlign;
 import com.facebook.yoga.YogaBaselineFunction;
 import com.facebook.yoga.YogaConfig;
@@ -23,6 +22,7 @@
 import com.facebook.yoga.YogaJustify;
 import com.facebook.yoga.YogaMeasureFunction;
 import com.facebook.yoga.YogaNode;
+import com.facebook.yoga.YogaNodeCloneFunction;
 import com.facebook.yoga.YogaOverflow;
 import com.facebook.yoga.YogaPositionType;
 import com.facebook.yoga.YogaValue;

From a275eac56e21b8f3631bcd03ace86c07a3b0c0ba Mon Sep 17 00:00:00 2001
From: Sophie Alpert <sophiebits@fb.com>
Date: Mon, 16 Apr 2018 13:03:50 -0700
Subject: [PATCH 0307/1109] Clean up some grossness in ScrollResponder

Summary: Still gross but less gross.

Reviewed By: sebmarkbage

Differential Revision: D7107180

fbshipit-source-id: 31f1639a8f44e4ab247c338001a4a5c9b4b83cdf
---
 Libraries/Components/ScrollResponder.js       | 28 ++++++------
 Libraries/Components/TextInput/TextInput.js   | 44 +++++++++++--------
 .../Components/TextInput/TextInputState.js    | 16 ++++++-
 3 files changed, 54 insertions(+), 34 deletions(-)

diff --git a/Libraries/Components/ScrollResponder.js b/Libraries/Components/ScrollResponder.js
index 9d60c462ef1d..6c926b9d40e1 100644
--- a/Libraries/Components/ScrollResponder.js
+++ b/Libraries/Components/ScrollResponder.js
@@ -23,7 +23,6 @@ const performanceNow = require('fbjs/lib/performanceNow');
 const warning = require('fbjs/lib/warning');
 
 const { ScrollViewManager } = require('NativeModules');
-const { getInstanceFromNode } = require('ReactNativeComponentTree');
 
 /**
  * Mixin that can be integrated in order to handle scrolling that plays well
@@ -114,15 +113,6 @@ type State = {
 };
 type Event = Object;
 
-function isTagInstanceOfTextInput(tag) {
-  const instance = getInstanceFromNode(tag);
-  return instance && instance.viewConfig && (
-    instance.viewConfig.uiViewClassName === 'AndroidTextInput' ||
-    instance.viewConfig.uiViewClassName === 'RCTMultilineTextInputView' ||
-    instance.viewConfig.uiViewClassName === 'RCTSinglelineTextInputView'
-  );
-}
-
 const ScrollResponderMixin = {
   mixins: [Subscribable.Mixin],
   scrollResponderMixinGetInitialState: function(): State {
@@ -196,17 +186,27 @@ const ScrollResponderMixin = {
    * Invoke this from an `onStartShouldSetResponderCapture` event.
    */
   scrollResponderHandleStartShouldSetResponderCapture: function(e: Event): boolean {
-    // First see if we want to eat taps while the keyboard is up
+    // The scroll view should receive taps instead of its descendants if:
+    // * it is already animating/decelerating
+    if (this.scrollResponderIsAnimating()) {
+      return true;
+    }
+
+    // * the keyboard is up, keyboardShouldPersistTaps is 'never' (the default),
+    // and a new touch starts with a non-textinput target (in which case the
+    // first tap should be sent to the scroll view and dismiss the keyboard,
+    // then the second tap goes to the actual interior view)
     const currentlyFocusedTextInput = TextInputState.currentlyFocusedField();
     const {keyboardShouldPersistTaps} = this.props;
     const keyboardNeverPersistTaps = !keyboardShouldPersistTaps ||
                                     keyboardShouldPersistTaps === 'never';
     if (keyboardNeverPersistTaps &&
-      currentlyFocusedTextInput != null &&
-      !isTagInstanceOfTextInput(e.target)) {
+      currentlyFocusedTextInput != null
+      /* && !TextInputState.isTextInput(e.target) */) {
       return true;
     }
-    return this.scrollResponderIsAnimating();
+
+    return false;
   },
 
   /**
diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index eb838174f151..fd67b8ec55fc 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -192,10 +192,6 @@ const DataDetectorTypes = [
 
 const TextInput = createReactClass({
   displayName: 'TextInput',
-  statics: {
-    /* TODO(brentvatne) docs are needed for this */
-    State: TextInputState,
-  },
 
   propTypes: {
     ...ViewPropTypes,
@@ -667,24 +663,30 @@ const TextInput = createReactClass({
 
   componentDidMount: function() {
     this._lastNativeText = this.props.value;
-    if (!this.context.focusEmitter) {
+    const tag = ReactNative.findNodeHandle(this._inputRef);
+    if (tag != null) {
+      // tag is null only in unit tests
+      TextInputState.registerInput(tag);
+    }
+
+    if (this.context.focusEmitter) {
+      this._focusSubscription = this.context.focusEmitter.addListener(
+        'focus',
+        el => {
+          if (this === el) {
+            this.requestAnimationFrame(this.focus);
+          } else if (this.isFocused()) {
+            this.blur();
+          }
+        },
+      );
+      if (this.props.autoFocus) {
+        this.context.onFocusRequested(this);
+      }
+    } else {
       if (this.props.autoFocus) {
         this.requestAnimationFrame(this.focus);
       }
-      return;
-    }
-    this._focusSubscription = this.context.focusEmitter.addListener(
-      'focus',
-      el => {
-        if (this === el) {
-          this.requestAnimationFrame(this.focus);
-        } else if (this.isFocused()) {
-          this.blur();
-        }
-      },
-    );
-    if (this.props.autoFocus) {
-      this.context.onFocusRequested(this);
     }
   },
 
@@ -693,6 +695,10 @@ const TextInput = createReactClass({
     if (this.isFocused()) {
       this.blur();
     }
+    const tag = ReactNative.findNodeHandle(this._inputRef);
+    if (tag != null) {
+      TextInputState.unregisterInput(tag);
+    }
   },
 
   getChildContext(): ViewChildContext {
diff --git a/Libraries/Components/TextInput/TextInputState.js b/Libraries/Components/TextInput/TextInputState.js
index afcca82bf320..cb41eef0c529 100644
--- a/Libraries/Components/TextInput/TextInputState.js
+++ b/Libraries/Components/TextInput/TextInputState.js
@@ -16,6 +16,8 @@
 const Platform = require('Platform');
 const UIManager = require('UIManager');
 
+const inputs = new Set();
+
 const TextInputState = {
    /**
    * Internal state
@@ -68,7 +70,19 @@ const TextInputState = {
         );
       }
     }
-  }
+  },
+
+  registerInput: function(textFieldID: number) {
+    inputs.add(textFieldID);
+  },
+
+  unregisterInput: function(textFieldID: number) {
+    inputs.delete(textFieldID);
+  },
+
+  isTextInput: function(textFieldID: number) {
+    return inputs.has(textFieldID);
+  },
 };
 
 module.exports = TextInputState;

From 311a7a8e82719d61d1e95c262d8535ddb6d214aa Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Mon, 16 Apr 2018 13:19:33 -0700
Subject: [PATCH 0308/1109] Use the provided NativeModuleCallExceptionHandler
 if provided

Summary:
Before, any calls to ReactContext would either use the default DevSupportManager's exception handler in debug mode OR throw exceptions immediately in non debug mode. In order to intercept these kinds of native exceptions, we should reuse the NativeModuleCallExceptionHandler provided by the ReactInstanceManager. For those who don't specify a NativeModuleCallExceptionHandler, the resulting behavior remains the same. For those who do specify a NativeModuleCallExceptionHandler,
the main difference is that it will now be responsible for handling exceptions for ReactContext.handleException

Reviewed By: mdvacca

Differential Revision: D7641772

fbshipit-source-id: 8f175df687723fcbb8a7620f90d8a08c94798738
---
 .../java/com/facebook/react/ReactInstanceManager.java  | 10 ++++------
 1 file changed, 4 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 250f2091af72..26ee98a9a034 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -1070,15 +1070,13 @@ private ReactApplicationContext createReactContext(
     ReactMarker.logMarker(CREATE_REACT_CONTEXT_START);
     final ReactApplicationContext reactContext = new ReactApplicationContext(mApplicationContext);
 
-    if (mUseDeveloperSupport) {
-      reactContext.setNativeModuleCallExceptionHandler(mDevSupportManager);
-    }
+    NativeModuleCallExceptionHandler exceptionHandler = mNativeModuleCallExceptionHandler != null
+        ? mNativeModuleCallExceptionHandler
+        : mDevSupportManager;
+    reactContext.setNativeModuleCallExceptionHandler(exceptionHandler);
 
     NativeModuleRegistry nativeModuleRegistry = processPackages(reactContext, mPackages, false);
 
-    NativeModuleCallExceptionHandler exceptionHandler = mNativeModuleCallExceptionHandler != null
-      ? mNativeModuleCallExceptionHandler
-      : mDevSupportManager;
     CatalystInstanceImpl.Builder catalystInstanceBuilder = new CatalystInstanceImpl.Builder()
       .setReactQueueConfigurationSpec(ReactQueueConfigurationSpec.createDefault())
       .setJSExecutor(jsExecutor)

From 660a578aebc9acb1c976cc7ed8ac9cf67ec657d4 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 16 Apr 2018 13:58:29 -0700
Subject: [PATCH 0309/1109] Fix cloning for ReactTextInputShadowNode

Reviewed By: shergin

Differential Revision: D7628252

fbshipit-source-id: 034f2d619f716600dde21a5dd43538c261be773b
---
 .../textinput/ReactTextInputShadowNode.java   | 26 ++++++++++++++++---
 1 file changed, 22 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
index 2fb427ee8057..1336314cdae3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
@@ -15,6 +15,7 @@
 import com.facebook.react.bridge.JSApplicationIllegalArgumentException;
 import com.facebook.react.common.annotations.VisibleForTesting;
 import com.facebook.react.uimanager.LayoutShadowNode;
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.Spacing;
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.UIViewOperationQueue;
@@ -53,16 +54,33 @@ private ReactTextInputShadowNode(ReactTextInputShadowNode node) {
     mMostRecentEventCount = node.mMostRecentEventCount;
     mText = node.mText;
     mLocalData = node.mLocalData;
-    setMeasureFunction(this);
+  }
+
+  @Override
+  protected ReactTextInputShadowNode copy() {
+    return new ReactTextInputShadowNode(this);
+  }
+
+  @Override
+  public ReactTextInputShadowNode mutableCopy() {
+    ReactTextInputShadowNode node = (ReactTextInputShadowNode) super.mutableCopy();
+    node.setMeasureFunction(this);
     ThemedReactContext themedContext = getThemedContext();
     if (themedContext != null) {
-      setThemedContext(themedContext);
+      node.setThemedContext(themedContext);
     }
+    return node;
   }
 
   @Override
-  protected ReactTextInputShadowNode copy() {
-    return new ReactTextInputShadowNode(this);
+  public ReactTextInputShadowNode mutableCopyWithNewChildren() {
+    ReactTextInputShadowNode node = (ReactTextInputShadowNode) super.mutableCopyWithNewChildren();
+    node.setMeasureFunction(this);
+    ThemedReactContext themedContext = getThemedContext();
+    if (themedContext != null) {
+      node.setThemedContext(themedContext);
+    }
+    return node;
   }
 
   @Override

From d8fcdb9bd7a308ed70caeac1b53da0a05abe452f Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Leo=20Nikkil=C3=A4?= <hello@lnikki.la>
Date: Mon, 16 Apr 2018 14:00:30 -0700
Subject: [PATCH 0310/1109] Fix view indices with Android LayoutAnimation
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
Fixes issue #11828 that causes layout animations for removed views to
remove some adjacent views as well. This happens because the animated
views are still present in the ViewGroup, which throws off subsequent
operations that rely on view indices having updated.

This issue was addressed in #11962, which was closed in favour of a more
reliable solution that addresses the issue globally since it’s difficult
to account for animated views everywhere. janicduplessis [recommended][0]
handling the issue through ViewManager.

Since API 11, Android provides `ViewGroup#startViewTransition(View)`
that can be used to keep child views visible even if they have been
removed from the group. ViewGroup keeps an array of these views, which
is only used for drawing. Methods such as `ViewGroup#getChildCount()`
and `ViewGroup#getChildAt(int)` will ignore them.

I believe relying on these framework methods within ViewManager is the
most reliable way to solve this issue because it also works if callers
ignore ViewManager and reach into the native view indices and counts
directly.

[0]: https://github.com/facebook/react-native/pull/11962#pullrequestreview-21862640

I wrote a minimal test app that you can find here:

<https://gist.github.com/lnikkila/87f3825442a5773f17ead433a810d53f>

The expected result is that the red and green squares disappear, a blue
one appears, and the black one stays in place. iOS has this behaviour,
but Android removes the black square as well.

We can see the bug with some breakpoint logging.

Without LayoutAnimation:

```
    NativeViewHierarchyOptimizer: Removing node from parent with tag 2 at index 0
    NativeViewHierarchyOptimizer: Removing node from parent with tag 4 at index 1
    NativeViewHierarchyManager: Removing indices [0] with tags [2]
    RootViewManager: Removing child view at index 0 with tag 2
    NativeViewHierarchyManager: Removing indices [1] with tags [4]
    RootViewManager: Removing child view at index 1 with tag 4
```

With LayoutAnimation tag 3 gets removed when it shouldn’t be:

```
    NativeViewHierarchyOptimizer: Removing node from parent with tag 2 at index 0
    NativeViewHierarchyOptimizer: Removing node from parent with tag 4 at index 1
    NativeViewHierarchyManager: Removing indices [0] with tags [2]
    NativeViewHierarchyManager: Removing indices [1] with tags [4]
->  RootViewManager: Removing child view at index 1 with tag 3
    RootViewManager: Removing child view at index 2 with tag 4

    (Animation listener kicks in here)

    RootViewManager: Removing child view at index 1 with tag 2
```

Here are some GIFs to compare, click to expand:

<details>
  <summary><b>Current master (iOS vs Android)</b></summary>
  <p></p>
  <img src="https://user-images.githubusercontent.com/1291143/38695083-fbc29cd4-3e93-11e8-9150-9b8ea75b87aa.gif" height="400" /><img src="https://user-images.githubusercontent.com/1291143/38695108-06eb73a6-3e94-11e8-867a-b95d7f926ccd.gif" height="400" />
</details><p></p>

<details>
  <summary><b>With this patch (iOS vs Android, fixed)</b></summary>
  <p></p>
  <img src="https://user-images.githubusercontent.com/1291143/38695083-fbc29cd4-3e93-11e8-9150-9b8ea75b87aa.gif" height="400" /><img src="https://user-images.githubusercontent.com/1291143/38695137-1090f782-3e94-11e8-94c8-ce33a5d7ebdb.gif" height="400" />
</details><p></p>

Previously addressed in #11962, which wasn’t merged.

Tangentially related to my other LayoutAnimation PR #18651.

No documentation changes needed.

[ANDROID] [BUGFIX] [LayoutAnimation] - Removal LayoutAnimations no longer remove adjacent views as well in certain cases.
Closes https://github.com/facebook/react-native/pull/18830

Reviewed By: achen1

Differential Revision: D7612904

Pulled By: mdvacca

fbshipit-source-id: a04cf47ab80e0e813fa043125b1f907e212b1ad4
---
 .../react/uimanager/NativeViewHierarchyManager.java | 13 ++++++++-----
 .../facebook/react/uimanager/ViewGroupManager.java  |  8 ++++++++
 2 files changed, 16 insertions(+), 5 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
index a57205b861eb..2b72a0a33330 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
@@ -373,12 +373,13 @@ public synchronized void manageChildren(
         if (mLayoutAnimationEnabled &&
             mLayoutAnimator.shouldAnimateLayout(viewToRemove) &&
             arrayContains(tagsToDelete, viewToRemove.getId())) {
-          // The view will be removed and dropped by the 'delete' layout animation
-          // instead, so do nothing
-        } else {
-          viewManager.removeViewAt(viewToManage, indexToRemove);
+          // Display the view in the parent after removal for the duration of the layout animation,
+          // but pretend that it doesn't exist when calling other ViewGroup methods.
+          viewManager.startViewTransition(viewToManage, viewToRemove);
         }
 
+        viewManager.removeViewAt(viewToManage, indexToRemove);
+
         lastIndexToRemove = indexToRemove;
       }
     }
@@ -423,7 +424,9 @@ public synchronized void manageChildren(
           mLayoutAnimator.deleteView(viewToDestroy, new LayoutAnimationListener() {
             @Override
             public void onAnimationEnd() {
-              viewManager.removeView(viewToManage, viewToDestroy);
+              // Already removed from the ViewGroup, we can just end the transition here to
+              // release the child.
+              viewManager.endViewTransition(viewToManage, viewToDestroy);
               dropView(viewToDestroy);
             }
           });
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewGroupManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewGroupManager.java
index 017fb5764e72..c4d5eed429dd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewGroupManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewGroupManager.java
@@ -93,6 +93,14 @@ public void removeAllViews(T parent) {
     }
   }
 
+  public void startViewTransition(T parent, View view) {
+    parent.startViewTransition(view);
+  }
+
+  public void endViewTransition(T parent, View view) {
+    parent.endViewTransition(view);
+  }
+
   /**
    * Returns whether this View type needs to handle laying out its own children instead of
    * deferring to the standard css-layout algorithm.

From eff98b6c252476067518bb5525eb4338fdc21823 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Mon, 16 Apr 2018 16:07:36 -0700
Subject: [PATCH 0311/1109] Better error message for invalid native module

Reviewed By: mdvacca

Differential Revision: D7641828

fbshipit-source-id: b1500029da49b60b6a69bc61ecc7f72629f65dcb
---
 .../java/com/facebook/react/bridge/NativeModuleRegistry.java   | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/NativeModuleRegistry.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/NativeModuleRegistry.java
index d30b7a5a3788..66c73e6af168 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/NativeModuleRegistry.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/NativeModuleRegistry.java
@@ -141,7 +141,8 @@ public <T extends NativeModule> boolean hasModule(Class<T> moduleInterface) {
   }
 
   public <T extends NativeModule> T getModule(Class<T> moduleInterface) {
-    return (T) Assertions.assertNotNull(mModules.get(moduleInterface)).getModule();
+    return (T) Assertions.assertNotNull(
+        mModules.get(moduleInterface), moduleInterface.getSimpleName()).getModule();
   }
 
   public List<NativeModule> getAllModules() {

From 7f7020a1dbcbbf843252b470c74cf5c135935683 Mon Sep 17 00:00:00 2001
From: Jonathan Kim <jjkim@fb.com>
Date: Tue, 17 Apr 2018 01:19:19 -0700
Subject: [PATCH 0312/1109] Fix up wrapped macros

Reviewed By: mzlee

Differential Revision: D7645524

fbshipit-source-id: e62101dac95fd7458a2519588105ce43607a9769
---
 ReactNative/DEFS.bzl | 4 ----
 1 file changed, 4 deletions(-)

diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index 13402b1bc878..135bacfbc93d 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -183,7 +183,3 @@ def cxx_library(allow_jni_merging=None, **kwargs):
         if not (k.startswith("fbandroid_") or k.startswith("fbobjc_"))
     }
     native.cxx_library(**args)
-
-
-def fb_android_library(**kwargs):
-    native.android_library(**kwargs)

From d31dfd6db09a5347768466906892d8c61550f233 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Tue, 17 Apr 2018 05:02:02 -0700
Subject: [PATCH 0313/1109] Remove babel packages from package.json

Reviewed By: fkgozali

Differential Revision: D7635547

fbshipit-source-id: d0fd9f7c2adde9ff56699dc5c4bc691f94b15772
---
 package.json | 9 ---------
 1 file changed, 9 deletions(-)

diff --git a/package.json b/package.json
index df681175da83..01c8d57da21e 100644
--- a/package.json
+++ b/package.json
@@ -147,15 +147,6 @@
   "dependencies": {
     "absolute-path": "^0.0.0",
     "art": "^0.10.0",
-    "babel-core": "^6.24.1",
-    "babel-plugin-syntax-trailing-function-commas": "^6.20.0",
-    "babel-plugin-transform-async-to-generator": "6.16.0",
-    "babel-plugin-transform-class-properties": "^6.18.0",
-    "babel-plugin-transform-exponentiation-operator": "^6.5.0",
-    "babel-plugin-transform-flow-strip-types": "^6.21.0",
-    "babel-plugin-transform-object-rest-spread": "^6.20.2",
-    "babel-register": "^6.24.1",
-    "babel-runtime": "^6.23.0",
     "base64-js": "^1.1.2",
     "chalk": "^1.1.1",
     "commander": "^2.9.0",

From 6de4ff36b0c5065e9fec9dac6998984552a7418e Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Tue, 17 Apr 2018 05:11:58 -0700
Subject: [PATCH 0314/1109] Fix babel-preset-react-native, bump it to babel 7

Reviewed By: yungsters

Differential Revision: D7635490

fbshipit-source-id: 9f32f4389178904c68e0a03fee0485372ec10900
---
 babel-preset/lib/resolvePlugins.js |  2 +-
 babel-preset/package.json          | 58 ++++++++++++++----------------
 babel-preset/plugins.js            | 54 ++++++++++++++--------------
 3 files changed, 54 insertions(+), 60 deletions(-)

diff --git a/babel-preset/lib/resolvePlugins.js b/babel-preset/lib/resolvePlugins.js
index ebbe5ddacfc5..0291c94e70f8 100644
--- a/babel-preset/lib/resolvePlugins.js
+++ b/babel-preset/lib/resolvePlugins.js
@@ -21,7 +21,7 @@ function resolvePlugins(plugins, prefix) {
 /**
  * Manually resolve a single Babel plugin.
  */
-function resolvePlugin(plugin, prefix = 'babel-plugin-') {
+function resolvePlugin(plugin, prefix = '@babel/plugin-') {
   // Normalise plugin to an array.
   if (!Array.isArray(plugin)) {
     plugin = [plugin];
diff --git a/babel-preset/package.json b/babel-preset/package.json
index 3181ee146f24..066af5f61b15 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -15,37 +15,31 @@
   },
   "homepage": "https://github.com/facebook/react-native/tree/master/babel-preset/README.md",
   "dependencies": {
-    "babel-plugin-check-es2015-constants": "^6.5.0",
-    "babel-plugin-react-transform": "^3.0.0",
-    "babel-plugin-syntax-async-functions": "^6.5.0",
-    "babel-plugin-syntax-class-properties": "^6.5.0",
-    "babel-plugin-syntax-dynamic-import": "^6.18.0",
-    "babel-plugin-syntax-flow": "^6.5.0",
-    "babel-plugin-syntax-jsx": "^6.5.0",
-    "babel-plugin-syntax-trailing-function-commas": "^6.5.0",
-    "babel-plugin-transform-class-properties": "^6.5.0",
-    "babel-plugin-transform-es2015-arrow-functions": "^6.5.0",
-    "babel-plugin-transform-es2015-block-scoping": "^6.5.0",
-    "babel-plugin-transform-es2015-classes": "^6.5.0",
-    "babel-plugin-transform-es2015-computed-properties": "^6.5.0",
-    "babel-plugin-transform-es2015-destructuring": "^6.5.0",
-    "babel-plugin-transform-es2015-for-of": "^6.5.0",
-    "babel-plugin-transform-es2015-function-name": "^6.5.0",
-    "babel-plugin-transform-es2015-literals": "^6.5.0",
-    "babel-plugin-transform-es2015-modules-commonjs": "^6.5.0",
-    "babel-plugin-transform-es2015-parameters": "^6.5.0",
-    "babel-plugin-transform-es2015-shorthand-properties": "^6.5.0",
-    "babel-plugin-transform-es2015-spread": "^6.5.0",
-    "babel-plugin-transform-es2015-template-literals": "^6.5.0",
-    "babel-plugin-transform-exponentiation-operator": "^6.5.0",
-    "babel-plugin-transform-flow-strip-types": "^6.5.0",
-    "babel-plugin-transform-object-assign": "^6.5.0",
-    "babel-plugin-transform-object-rest-spread": "^6.5.0",
-    "babel-plugin-transform-react-display-name": "^6.5.0",
-    "babel-plugin-transform-react-jsx": "^6.5.0",
-    "babel-plugin-transform-react-jsx-source": "^6.5.0",
-    "babel-plugin-transform-regenerator": "^6.5.0",
-    "babel-template": "^6.24.1",
-    "react-transform-hmr": "^1.0.4"
+    "@babel/plugin-proposal-class-properties": "^7.0.0-beta",
+    "@babel/plugin-proposal-object-rest-spread": "^7.0.0-beta",
+    "@babel/plugin-transform-arrow-functions": "^7.0.0-beta",
+    "@babel/plugin-transform-block-scoping": "^7.0.0-beta",
+    "@babel/plugin-transform-classes": "^7.0.0-beta",
+    "@babel/plugin-transform-computed-properties": "^7.0.0-beta",
+    "@babel/plugin-transform-destructuring": "^7.0.0-beta",
+    "@babel/plugin-transform-exponentiation-operator": "^7.0.0-beta",
+    "@babel/plugin-transform-flow-strip-types": "^7.0.0-beta",
+    "@babel/plugin-transform-for-of": "^7.0.0-beta",
+    "@babel/plugin-transform-function-name": "^7.0.0-beta",
+    "@babel/plugin-transform-literals": "^7.0.0-beta",
+    "@babel/plugin-transform-modules-commonjs": "^7.0.0-beta",
+    "@babel/plugin-transform-object-assign": "^7.0.0-beta",
+    "@babel/plugin-transform-parameters": "^7.0.0-beta",
+    "@babel/plugin-transform-shorthand-properties": "^7.0.0-beta",
+    "@babel/plugin-transform-react-display-name": "^7.0.0-beta",
+    "@babel/plugin-transform-react-jsx": "^7.0.0-beta",
+    "@babel/plugin-transform-react-jsx-source": "^7.0.0-beta",
+    "@babel/plugin-transform-regenerator": "^7.0.0-beta",
+    "@babel/plugin-transform-spread": "^7.0.0-beta",
+    "@babel/plugin-transform-sticky-regex": "^7.0.0-beta",
+    "@babel/plugin-transform-unicode-regex": "^7.0.0-beta",
+    "@babel/plugin-transform-template-literals": "^7.0.0-beta",
+    "@babel/template": "^7.0.0-beta",
+    "metro-babel7-plugin-react-transform": "0.32.0"
   }
 }
diff --git a/babel-preset/plugins.js b/babel-preset/plugins.js
index d572a11b042e..b53d23bbe4fc 100644
--- a/babel-preset/plugins.js
+++ b/babel-preset/plugins.js
@@ -3,35 +3,35 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ * @format
  */
 'use strict';
 
 module.exports = {
-  'babel-plugin-react-transform': require('babel-plugin-react-transform'),
-  'babel-plugin-syntax-async-functions': require('babel-plugin-syntax-async-functions'),
-  'babel-plugin-syntax-class-properties': require('babel-plugin-syntax-class-properties'),
-  'babel-plugin-syntax-dynamic-import': require('babel-plugin-syntax-dynamic-import'),
-  'babel-plugin-syntax-trailing-function-commas': require('babel-plugin-syntax-trailing-function-commas'),
-  'babel-plugin-transform-class-properties': require('babel-plugin-transform-class-properties'),
-  'babel-plugin-transform-es2015-function-name': require('babel-plugin-transform-es2015-function-name'),
-  'babel-plugin-transform-es2015-arrow-functions': require('babel-plugin-transform-es2015-arrow-functions'),
-  'babel-plugin-transform-es2015-block-scoping': require('babel-plugin-transform-es2015-block-scoping'),
-  'babel-plugin-transform-es2015-classes': require('babel-plugin-transform-es2015-classes'),
-  'babel-plugin-transform-es2015-computed-properties': require('babel-plugin-transform-es2015-computed-properties'),
-  'babel-plugin-check-es2015-constants': require('babel-plugin-check-es2015-constants'),
-  'babel-plugin-transform-es2015-destructuring': require('babel-plugin-transform-es2015-destructuring'),
-  'babel-plugin-transform-es2015-modules-commonjs': require('babel-plugin-transform-es2015-modules-commonjs'),
-  'babel-plugin-transform-es2015-parameters': require('babel-plugin-transform-es2015-parameters'),
-  'babel-plugin-transform-es2015-shorthand-properties': require('babel-plugin-transform-es2015-shorthand-properties'),
-  'babel-plugin-transform-es2015-spread': require('babel-plugin-transform-es2015-spread'),
-  'babel-plugin-transform-es2015-template-literals': require('babel-plugin-transform-es2015-template-literals'),
-  'babel-plugin-transform-es2015-literals' : require('babel-plugin-transform-es2015-literals'),
-  'babel-plugin-transform-flow-strip-types': require('babel-plugin-transform-flow-strip-types'),
-  'babel-plugin-transform-object-assign': require('babel-plugin-transform-object-assign'),
-  'babel-plugin-transform-object-rest-spread': require('babel-plugin-transform-object-rest-spread'),
-  'babel-plugin-transform-react-display-name': require('babel-plugin-transform-react-display-name'),
-  'babel-plugin-transform-react-jsx-source': require('babel-plugin-transform-react-jsx-source'),
-  'babel-plugin-transform-react-jsx': require('babel-plugin-transform-react-jsx'),
-  'babel-plugin-transform-regenerator': require('babel-plugin-transform-regenerator'),
-  'babel-plugin-transform-es2015-for-of': require('babel-plugin-transform-es2015-for-of'),
+  '@babel/plugin-proposal-class-properties': require('@babel/plugin-proposal-class-properties'),
+  '@babel/plugin-proposal-object-rest-spread': require('@babel/plugin-proposal-object-rest-spread'),
+  '@babel/plugin-transform-arrow-functions': require('@babel/plugin-transform-arrow-functions'),
+  '@babel/plugin-transform-block-scoping': require('@babel/plugin-transform-block-scoping'),
+  '@babel/plugin-transform-classes': require('@babel/plugin-transform-classes'),
+  '@babel/plugin-transform-computed-properties': require('@babel/plugin-transform-computed-properties'),
+  '@babel/plugin-transform-destructuring': require('@babel/plugin-transform-destructuring'),
+  '@babel/plugin-transform-exponentiation-operator': require('@babel/plugin-transform-exponentiation-operator'),
+  '@babel/plugin-transform-flow-strip-types': require('@babel/plugin-transform-flow-strip-types'),
+  '@babel/plugin-transform-for-of': require('@babel/plugin-transform-for-of'),
+  '@babel/plugin-transform-function-name': require('@babel/plugin-transform-function-name'),
+  '@babel/plugin-transform-literals': require('@babel/plugin-transform-literals'),
+  '@babel/plugin-transform-modules-commonjs': require('@babel/plugin-transform-modules-commonjs'),
+  '@babel/plugin-transform-object-assign': require('@babel/plugin-transform-object-assign'),
+  '@babel/plugin-transform-parameters': require('@babel/plugin-transform-parameters'),
+  '@babel/plugin-transform-shorthand-properties': require('@babel/plugin-transform-shorthand-properties'),
+  '@babel/plugin-transform-react-display-name': require('@babel/plugin-transform-react-display-name'),
+  '@babel/plugin-transform-react-jsx': require('@babel/plugin-transform-react-jsx'),
+  '@babel/plugin-transform-react-jsx-source': require('@babel/plugin-transform-react-jsx-source'),
+  '@babel/plugin-transform-regenerator': require('@babel/plugin-transform-regenerator'),
+  '@babel/plugin-transform-spread': require('@babel/plugin-transform-spread'),
+  '@babel/plugin-transform-sticky-regex': require('@babel/plugin-transform-sticky-regex'),
+  '@babel/plugin-transform-unicode-regex': require('@babel/plugin-transform-unicode-regex'),
+  '@babel/plugin-transform-template-literals': require('@babel/plugin-transform-template-literals'),
 };

From d2a1461d26df4c1b29362c0f6900fbf639d243d8 Mon Sep 17 00:00:00 2001
From: Avik Chaudhuri <avik@fb.com>
Date: Tue, 17 Apr 2018 05:37:02 -0700
Subject: [PATCH 0315/1109] @allow-large-files clean up xplat/js for flow
 0.70.0

Reviewed By: fishythefish

Differential Revision: D7643236

fbshipit-source-id: 1d9a95f1e249ce3fdc552a4ca92a6c63b267dae4
---
 .flowconfig                                           |  2 +-
 Libraries/Animated/src/nodes/AnimatedInterpolation.js |  3 +++
 Libraries/Components/Switch/Switch.js                 |  9 +++++++++
 Libraries/Lists/VirtualizedList.js                    |  3 +++
 RNTester/js/PointerEventsExample.js                   |  3 +++
 RNTester/js/ScrollViewExample.js                      | 10 ++++++++--
 local-cli/templates/HelloWorld/_flowconfig            |  2 +-
 local-cli/util/Config.js                              |  3 +++
 package.json                                          |  2 +-
 9 files changed, 32 insertions(+), 5 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index f67339eee784..386c9389a498 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -52,4 +52,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.69.0
+^0.70.0
diff --git a/Libraries/Animated/src/nodes/AnimatedInterpolation.js b/Libraries/Animated/src/nodes/AnimatedInterpolation.js
index eb4cc5d6995d..bc7b1365879d 100644
--- a/Libraries/Animated/src/nodes/AnimatedInterpolation.js
+++ b/Libraries/Animated/src/nodes/AnimatedInterpolation.js
@@ -350,6 +350,9 @@ class AnimatedInterpolation extends AnimatedWithChildren {
   __transformDataType(range: Array<any>) {
     // Change the string array type to number array
     // So we can reuse the same logic in iOS and Android platform
+    /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.70 was deployed. To see the error delete this
+     * comment and run Flow. */
     return range.map(function(value) {
       if (typeof value !== 'string') {
         return value;
diff --git a/Libraries/Components/Switch/Switch.js b/Libraries/Components/Switch/Switch.js
index e88272dacfa1..f259229c3538 100644
--- a/Libraries/Components/Switch/Switch.js
+++ b/Libraries/Components/Switch/Switch.js
@@ -102,9 +102,18 @@ const Switch = createReactClass({
     props.onStartShouldSetResponder = () => true;
     props.onResponderTerminationRequest = () => false;
     if (Platform.OS === 'android') {
+      /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
+       * error found when Flow v0.70 was deployed. To see the error delete
+       * this comment and run Flow. */
       props.enabled = !this.props.disabled;
+      /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
+       * error found when Flow v0.70 was deployed. To see the error delete
+       * this comment and run Flow. */
       props.on = this.props.value;
       props.style = this.props.style;
+      /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
+       * error found when Flow v0.70 was deployed. To see the error delete
+       * this comment and run Flow. */
       props.trackTintColor = this.props.value ? this.props.onTintColor : this.props.tintColor;
     } else if (Platform.OS === 'ios') {
       props.style = [styles.rctSwitchIOS, this.props.style];
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index e03750e106ab..2b1b83ff41bb 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -906,6 +906,9 @@ class VirtualizedList extends React.PureComponent<Props, State> {
       stickyHeaderIndices,
     };
     if (inversionStyle) {
+      /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
+       * error found when Flow v0.70 was deployed. To see the error delete
+       * this comment and run Flow. */
       scrollProps.style = [inversionStyle, this.props.style];
     }
 
diff --git a/RNTester/js/PointerEventsExample.js b/RNTester/js/PointerEventsExample.js
index ac838c4eb8e3..ac15811c96dd 100644
--- a/RNTester/js/PointerEventsExample.js
+++ b/RNTester/js/PointerEventsExample.js
@@ -251,4 +251,7 @@ exports.framework = 'React';
 exports.title = 'Pointer Events';
 exports.description = 'Demonstrates the use of the pointerEvents prop of a ' +
   'View to control how touches should be handled.';
+/* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an error
+ * found when Flow v0.70 was deployed. To see the error delete this comment
+ * and run Flow. */
 exports.examples = exampleClasses.map(infoToExample);
diff --git a/RNTester/js/ScrollViewExample.js b/RNTester/js/ScrollViewExample.js
index f5b5c8aab8fd..66bedc93552c 100644
--- a/RNTester/js/ScrollViewExample.js
+++ b/RNTester/js/ScrollViewExample.js
@@ -118,8 +118,14 @@ exports.examples = [
 
       return (
         <View>
-          {renderScrollView('LTR layout', {direction: 'ltr'})}
-          {renderScrollView('RTL layout', {direction: 'rtl'})}
+          {/* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment
+             * suppresses an error found when Flow v0.70 was deployed. To see
+             * the error delete this comment and run Flow. */
+          renderScrollView('LTR layout', {direction: 'ltr'})}
+          {/* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment
+             * suppresses an error found when Flow v0.70 was deployed. To see
+             * the error delete this comment and run Flow. */
+          renderScrollView('RTL layout', {direction: 'rtl'})}
         </View>
       );
     },
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 159649f1348e..4f75b3cb1405 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -51,4 +51,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.69.0
+^0.70.0
diff --git a/local-cli/util/Config.js b/local-cli/util/Config.js
index 9fc4487fe83e..5cd7b0f5fc22 100644
--- a/local-cli/util/Config.js
+++ b/local-cli/util/Config.js
@@ -42,6 +42,9 @@ function getProjectPath() {
 
 const resolveSymlinksForRoots = roots =>
   roots.reduce(
+    /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
+     * error found when Flow v0.70 was deployed. To see the error delete this
+     * comment and run Flow. */
     (arr, rootPath) => arr.concat(findSymlinkedModules(rootPath, roots)),
     [...roots],
   );
diff --git a/package.json b/package.json
index 01c8d57da21e..3509869f9b45 100644
--- a/package.json
+++ b/package.json
@@ -206,7 +206,7 @@
     "eslint-plugin-jest": "21.8.0",
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
-    "flow-bin": "^0.69.0",
+    "flow-bin": "^0.70.0",
     "jest": "23.0.0-alpha.4",
     "jest-junit": "3.6.0",
     "prettier": "1.9.1",

From b5f90ed497069481c4cbb3a52eaeb87567abd272 Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Tue, 17 Apr 2018 07:53:19 -0700
Subject: [PATCH 0316/1109] Update ModuleRegistry if there're new modules
 registered

Reviewed By: fkgozali

Differential Revision: D7638394

fbshipit-source-id: c1690da7977f0335bc661df5f19dc9f473150d41
---
 React/CxxBridge/RCTCxxBridge.mm | 14 +++++++++-----
 1 file changed, 9 insertions(+), 5 deletions(-)

diff --git a/React/CxxBridge/RCTCxxBridge.mm b/React/CxxBridge/RCTCxxBridge.mm
index cd82c3ccd85a..2517e2949192 100644
--- a/React/CxxBridge/RCTCxxBridge.mm
+++ b/React/CxxBridge/RCTCxxBridge.mm
@@ -305,7 +305,7 @@ - (void)start
 
   [self registerExtraModules];
   // Initialize all native modules that cannot be loaded lazily
-  [self _initModules:RCTGetModuleClasses() withDispatchGroup:prepareBridge lazilyDiscovered:NO];
+  (void)[self _initializeModules:RCTGetModuleClasses() withDispatchGroup:prepareBridge lazilyDiscovered:NO];
 
   [_performanceLogger markStopForTag:RCTPLNativeModuleInit];
 
@@ -635,9 +635,9 @@ - (void)installExtraJSBinding
   }
 }
 
-- (void)_initModules:(NSArray<id<RCTBridgeModule>> *)modules
-   withDispatchGroup:(dispatch_group_t)dispatchGroup
-    lazilyDiscovered:(BOOL)lazilyDiscovered
+- (NSArray<RCTModuleData *> *)_initializeModules:(NSArray<id<RCTBridgeModule>> *)modules
+                               withDispatchGroup:(dispatch_group_t)dispatchGroup
+                                lazilyDiscovered:(BOOL)lazilyDiscovered
 {
   RCTAssert(!(RCTIsMainQueue() && lazilyDiscovered), @"Lazy discovery can only happen off the Main Queue");
 
@@ -688,11 +688,15 @@ - (void)_initModules:(NSArray<id<RCTBridgeModule>> *)modules
     RCTProfileHookModules(self);
   }
 #endif
+  return moduleDataById;
 }
 
 - (void)registerAdditionalModuleClasses:(NSArray<Class> *)modules
 {
-  [self _initModules:modules withDispatchGroup:NULL lazilyDiscovered:YES];
+  NSArray<RCTModuleData *> *newModules = [self _initializeModules:modules withDispatchGroup:NULL lazilyDiscovered:YES];
+  if (_reactInstance) {
+    _reactInstance->getModuleRegistry().registerModules(createNativeModules(newModules, self, _reactInstance));
+  }
 }
 
 - (void)_prepareModulesWithDispatchGroup:(dispatch_group_t)dispatchGroup

From 1433d15557f11ab9ad42cdee9088e07d40f18be3 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Tue, 17 Apr 2018 09:32:30 -0700
Subject: [PATCH 0317/1109] Avoid top-level read_config invocations.

Reviewed By: danzimm

Differential Revision: D7651745

fbshipit-source-id: 5cbc82b3c9da3ab514278d438f97f98e19946dc7
---
 ReactCommon/cxxreact/BUCK         | 6 +++---
 ReactCommon/exceptions/BUCK       | 4 ++--
 ReactCommon/fabric/core/BUCK      | 6 +++---
 ReactCommon/fabric/debug/BUCK     | 4 ++--
 ReactCommon/fabric/graphics/BUCK  | 4 ++--
 ReactCommon/fabric/uimanager/BUCK | 4 ++--
 ReactCommon/fabric/view/BUCK      | 4 ++--
 7 files changed, 16 insertions(+), 16 deletions(-)

diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 43a5ce58276e..8bf767e82897 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -1,5 +1,5 @@
 load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "ANDROID_INSPECTOR_FLAGS", "APPLE_INSPECTOR_FLAGS", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "react_native_xplat_target")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_android_inspector_flags", "get_apple_inspector_flags", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "react_native_xplat_target")
 
 CXX_LIBRARY_COMPILER_FLAGS = [
     "-std=c++14",
@@ -129,7 +129,7 @@ rn_xplat_cxx_library(
         "-frtti",
     ],
     fbandroid_deps = ANDROID_JSC_DEPS,
-    fbandroid_preprocessor_flags = ANDROID_INSPECTOR_FLAGS + [
+    fbandroid_preprocessor_flags = get_android_inspector_flags() + [
         "-DWITH_JSC_EXTRA_TRACING=1",
         "-DWITH_JSC_MEMORY_PRESSURE=1",
         "-DWITH_FB_MEMORY_PROFILING=1",
@@ -139,7 +139,7 @@ rn_xplat_cxx_library(
     fbobjc_frameworks = [
         "$SDKROOT/System/Library/Frameworks/JavaScriptCore.framework",
     ],
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     force_static = True,
     macosx_tests_override = [],
     platforms = (ANDROID, APPLE),
diff --git a/ReactCommon/exceptions/BUCK b/ReactCommon/exceptions/BUCK
index 352bc036fdff..6f1ef1bb933b 100644
--- a/ReactCommon/exceptions/BUCK
+++ b/ReactCommon/exceptions/BUCK
@@ -1,5 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -24,7 +24,7 @@ rn_xplat_cxx_library(
         "-Wall",
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     force_static = True,
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 913078944214..23a9f30cfc0c 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -1,5 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -34,16 +34,16 @@ rn_xplat_cxx_library(
         "-Wall",
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     fbobjc_tests = [
         ":tests",
     ],
     force_static = True,
+    macosx_tests_override = [],
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
-    macosx_tests_override = [],
     tests = [],
     visibility = ["PUBLIC"],
     deps = [
diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index abc85f94c325..88f7bc47828c 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -1,5 +1,5 @@
 load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -31,7 +31,7 @@ rn_xplat_cxx_library(
         "-Wall",
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     fbobjc_tests = [
         ":tests",
     ],
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index 82a91faa4f45..7cdb8c59b90f 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -1,5 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -31,7 +31,7 @@ rn_xplat_cxx_library(
         "-frtti",
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     fbobjc_tests = [
         ":tests",
     ],
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 218b8ea92ebf..209502316d2b 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -1,5 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -31,7 +31,7 @@ rn_xplat_cxx_library(
         "-Wall",
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     fbobjc_tests = [
         ":tests",
     ],
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 8bdb1b175a39..d6ef5a048cfb 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -1,5 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "APPLE_INSPECTOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags")
 load("//ReactNative:DEFS.bzl", "react_native_xplat_target")
 
 APPLE_COMPILER_FLAGS = []
@@ -34,7 +34,7 @@ rn_xplat_cxx_library(
         "-Wall",
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + APPLE_INSPECTOR_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     fbobjc_tests = [
         ":tests",
     ],

From e4f88c66e300505d3c86329dacd84d84e8109837 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 17 Apr 2018 10:13:52 -0700
Subject: [PATCH 0318/1109] Revert D7569885: Fix anti aliasing rounded
 background

Differential Revision:
D7569885

Original commit changeset: 4bfb00485211

fbshipit-source-id: 2fc76ca8615d5562ebe8c7527e9a54058b8d82dc
---
 .../view/ReactViewBackgroundDrawable.java     | 197 ++++++++----------
 1 file changed, 89 insertions(+), 108 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
index e9fa14494a38..9e374b4c502e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
@@ -343,132 +343,113 @@ private void drawRoundedBackgroundWithBorders(Canvas canvas) {
         || borderWidth.bottom > 0
         || borderWidth.left > 0
         || borderWidth.right > 0) {
+      mPaint.setStyle(Paint.Style.FILL);
 
-      //If it's a full and even border draw inner rect path with stroke
-      final float fullBorderWidth = getFullBorderWidth();
-      if (borderWidth.top == fullBorderWidth &&
-        borderWidth.bottom == fullBorderWidth &&
-        borderWidth.left == fullBorderWidth &&
-        borderWidth.right == fullBorderWidth) {
-        if (fullBorderWidth > 0) {
-          int borderColor = getBorderColor(Spacing.ALL);
-          mPaint.setColor(ColorUtil.multiplyColorAlpha(borderColor, mAlpha));
-          mPaint.setStyle(Paint.Style.STROKE);
-          mPaint.setStrokeWidth(fullBorderWidth);
-          canvas.drawPath(mInnerClipPathForBorderRadius, mPaint);
-        }
-      }
-      //In the case of uneven border widths/colors draw quadrilateral in each direction
-      else {
-        mPaint.setStyle(Paint.Style.FILL);
-
-        // Draw border
-        canvas.clipPath(mOuterClipPathForBorderRadius, Region.Op.INTERSECT);
-        canvas.clipPath(mInnerClipPathForBorderRadius, Region.Op.DIFFERENCE);
-
-        int colorLeft = getBorderColor(Spacing.LEFT);
-        int colorTop = getBorderColor(Spacing.TOP);
-        int colorRight = getBorderColor(Spacing.RIGHT);
-        int colorBottom = getBorderColor(Spacing.BOTTOM);
-
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
-          final boolean isRTL = getResolvedLayoutDirection() == View.LAYOUT_DIRECTION_RTL;
-          int colorStart = getBorderColor(Spacing.START);
-          int colorEnd = getBorderColor(Spacing.END);
+      // Draw border
+      canvas.clipPath(mOuterClipPathForBorderRadius, Region.Op.INTERSECT);
+      canvas.clipPath(mInnerClipPathForBorderRadius, Region.Op.DIFFERENCE);
 
-          if (I18nUtil.getInstance().doLeftAndRightSwapInRTL(mContext)) {
-            if (!isBorderColorDefined(Spacing.START)) {
-              colorStart = colorLeft;
-            }
+      int colorLeft = getBorderColor(Spacing.LEFT);
+      int colorTop = getBorderColor(Spacing.TOP);
+      int colorRight = getBorderColor(Spacing.RIGHT);
+      int colorBottom = getBorderColor(Spacing.BOTTOM);
 
-            if (!isBorderColorDefined(Spacing.END)) {
-              colorEnd = colorRight;
-            }
+      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
+        final boolean isRTL = getResolvedLayoutDirection() == View.LAYOUT_DIRECTION_RTL;
+        int colorStart = getBorderColor(Spacing.START);
+        int colorEnd = getBorderColor(Spacing.END);
 
-            final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
-            final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
+        if (I18nUtil.getInstance().doLeftAndRightSwapInRTL(mContext)) {
+          if (!isBorderColorDefined(Spacing.START)) {
+            colorStart = colorLeft;
+          }
 
-            colorLeft = directionAwareColorLeft;
-            colorRight = directionAwareColorRight;
-          } else {
-            final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
-            final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
-
-            final boolean isColorStartDefined = isBorderColorDefined(Spacing.START);
-            final boolean isColorEndDefined = isBorderColorDefined(Spacing.END);
-            final boolean isDirectionAwareColorLeftDefined =
-              isRTL ? isColorEndDefined : isColorStartDefined;
-            final boolean isDirectionAwareColorRightDefined =
-              isRTL ? isColorStartDefined : isColorEndDefined;
-
-            if (isDirectionAwareColorLeftDefined) {
-              colorLeft = directionAwareColorLeft;
-            }
-
-            if (isDirectionAwareColorRightDefined) {
-              colorRight = directionAwareColorRight;
-            }
+          if (!isBorderColorDefined(Spacing.END)) {
+            colorEnd = colorRight;
           }
-        }
 
-        final float left = mOuterClipTempRectForBorderRadius.left;
-        final float right = mOuterClipTempRectForBorderRadius.right;
-        final float top = mOuterClipTempRectForBorderRadius.top;
-        final float bottom = mOuterClipTempRectForBorderRadius.bottom;
+          final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
+          final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
 
-        if (borderWidth.left > 0) {
-          final float x1 = left;
-          final float y1 = top;
-          final float x2 = mInnerTopLeftCorner.x;
-          final float y2 = mInnerTopLeftCorner.y;
-          final float x3 = mInnerBottomLeftCorner.x;
-          final float y3 = mInnerBottomLeftCorner.y;
-          final float x4 = left;
-          final float y4 = bottom;
+          colorLeft = directionAwareColorLeft;
+          colorRight = directionAwareColorRight;
+        } else {
+          final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
+          final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
 
-          drawQuadrilateral(canvas, colorLeft, x1, y1, x2, y2, x3, y3, x4, y4);
-        }
+          final boolean isColorStartDefined = isBorderColorDefined(Spacing.START);
+          final boolean isColorEndDefined = isBorderColorDefined(Spacing.END);
+          final boolean isDirectionAwareColorLeftDefined = isRTL ? isColorEndDefined : isColorStartDefined;
+          final boolean isDirectionAwareColorRightDefined = isRTL ? isColorStartDefined : isColorEndDefined;
 
-        if (borderWidth.top > 0) {
-          final float x1 = left;
-          final float y1 = top;
-          final float x2 = mInnerTopLeftCorner.x;
-          final float y2 = mInnerTopLeftCorner.y;
-          final float x3 = mInnerTopRightCorner.x;
-          final float y3 = mInnerTopRightCorner.y;
-          final float x4 = right;
-          final float y4 = top;
+          if (isDirectionAwareColorLeftDefined) {
+            colorLeft = directionAwareColorLeft;
+          }
 
-          drawQuadrilateral(canvas, colorTop, x1, y1, x2, y2, x3, y3, x4, y4);
+          if (isDirectionAwareColorRightDefined) {
+            colorRight = directionAwareColorRight;
+          }
         }
+      }
 
-        if (borderWidth.right > 0) {
-          final float x1 = right;
-          final float y1 = top;
-          final float x2 = mInnerTopRightCorner.x;
-          final float y2 = mInnerTopRightCorner.y;
-          final float x3 = mInnerBottomRightCorner.x;
-          final float y3 = mInnerBottomRightCorner.y;
-          final float x4 = right;
-          final float y4 = bottom;
+      final float left = mOuterClipTempRectForBorderRadius.left;
+      final float right = mOuterClipTempRectForBorderRadius.right;
+      final float top = mOuterClipTempRectForBorderRadius.top;
+      final float bottom = mOuterClipTempRectForBorderRadius.bottom;
+
+      if (borderWidth.left > 0) {
+        final float x1 = left;
+        final float y1 = top;
+        final float x2 = mInnerTopLeftCorner.x;
+        final float y2 = mInnerTopLeftCorner.y;
+        final float x3 = mInnerBottomLeftCorner.x;
+        final float y3 = mInnerBottomLeftCorner.y;
+        final float x4 = left;
+        final float y4 = bottom;
+
+        drawQuadrilateral(canvas, colorLeft, x1, y1, x2, y2, x3, y3, x4, y4);
+      }
 
-          drawQuadrilateral(canvas, colorRight, x1, y1, x2, y2, x3, y3, x4, y4);
-        }
+      if (borderWidth.top > 0) {
+        final float x1 = left;
+        final float y1 = top;
+        final float x2 = mInnerTopLeftCorner.x;
+        final float y2 = mInnerTopLeftCorner.y;
+        final float x3 = mInnerTopRightCorner.x;
+        final float y3 = mInnerTopRightCorner.y;
+        final float x4 = right;
+        final float y4 = top;
+
+        drawQuadrilateral(canvas, colorTop, x1, y1, x2, y2, x3, y3, x4, y4);
+      }
 
-        if (borderWidth.bottom > 0) {
-          final float x1 = left;
-          final float y1 = bottom;
-          final float x2 = mInnerBottomLeftCorner.x;
-          final float y2 = mInnerBottomLeftCorner.y;
-          final float x3 = mInnerBottomRightCorner.x;
-          final float y3 = mInnerBottomRightCorner.y;
-          final float x4 = right;
-          final float y4 = bottom;
+      if (borderWidth.right > 0) {
+        final float x1 = right;
+        final float y1 = top;
+        final float x2 = mInnerTopRightCorner.x;
+        final float y2 = mInnerTopRightCorner.y;
+        final float x3 = mInnerBottomRightCorner.x;
+        final float y3 = mInnerBottomRightCorner.y;
+        final float x4 = right;
+        final float y4 = bottom;
+
+        drawQuadrilateral(canvas, colorRight, x1, y1, x2, y2, x3, y3, x4, y4);
+      }
 
-          drawQuadrilateral(canvas, colorBottom, x1, y1, x2, y2, x3, y3, x4, y4);
-        }
+      if (borderWidth.bottom > 0) {
+        final float x1 = left;
+        final float y1 = bottom;
+        final float x2 = mInnerBottomLeftCorner.x;
+        final float y2 = mInnerBottomLeftCorner.y;
+        final float x3 = mInnerBottomRightCorner.x;
+        final float y3 = mInnerBottomRightCorner.y;
+        final float x4 = right;
+        final float y4 = bottom;
+
+        drawQuadrilateral(canvas, colorBottom, x1, y1, x2, y2, x3, y3, x4, y4);
       }
     }
+
     canvas.restore();
   }
 

From c9094e952bb806cd4f0cdb8179f92e595738010d Mon Sep 17 00:00:00 2001
From: Jean Lauliac <jeanlauliac@fb.com>
Date: Tue, 17 Apr 2018 11:54:47 -0700
Subject: [PATCH 0319/1109] cxxreact/RAMBundleRegistry: prepend segment ID

Reviewed By: fromcelticpark

Differential Revision: D7594348

fbshipit-source-id: 0b433de8722f8a952fd056139a350dc481f0af38
---
 ReactCommon/cxxreact/RAMBundleRegistry.cpp | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/cxxreact/RAMBundleRegistry.cpp b/ReactCommon/cxxreact/RAMBundleRegistry.cpp
index 635875b3b79c..127e06e01e85 100644
--- a/ReactCommon/cxxreact/RAMBundleRegistry.cpp
+++ b/ReactCommon/cxxreact/RAMBundleRegistry.cpp
@@ -3,6 +3,7 @@
 #include "RAMBundleRegistry.h"
 
 #include <folly/Memory.h>
+#include <folly/String.h>
 
 #include <libgen.h>
 
@@ -42,7 +43,14 @@ JSModulesUnbundle::Module RAMBundleRegistry::getModule(uint32_t bundleId, uint32
     m_bundles.emplace(bundleId, m_factory(bundlePath->second));
   }
 
-  return getBundle(bundleId)->getModule(moduleId);
+  auto module = getBundle(bundleId)->getModule(moduleId);
+  if (bundleId == MAIN_BUNDLE_ID) {
+    return module;
+  }
+  return {
+    folly::to<std::string>("seg-", bundleId, '_', std::move(module.name)),
+    std::move(module.code),
+  };
 }
 
 JSModulesUnbundle *RAMBundleRegistry::getBundle(uint32_t bundleId) const {

From 281ed9f4ce488e708de339e8543898ce30d4ce5a Mon Sep 17 00:00:00 2001
From: Jean Lauliac <jeanlauliac@fb.com>
Date: Tue, 17 Apr 2018 11:54:49 -0700
Subject: [PATCH 0320/1109] cxxreact/RAMBundleRegistry: nit fixes

Reviewed By: mhorowitz

Differential Revision: D7587411

fbshipit-source-id: 516753247af585914381308248de9652f18a6cf5
---
 ReactCommon/cxxreact/RAMBundleRegistry.cpp | 39 ++++++++++++++--------
 ReactCommon/cxxreact/RAMBundleRegistry.h   | 25 ++++++++------
 2 files changed, 41 insertions(+), 23 deletions(-)

diff --git a/ReactCommon/cxxreact/RAMBundleRegistry.cpp b/ReactCommon/cxxreact/RAMBundleRegistry.cpp
index 127e06e01e85..cc61ea254540 100644
--- a/ReactCommon/cxxreact/RAMBundleRegistry.cpp
+++ b/ReactCommon/cxxreact/RAMBundleRegistry.cpp
@@ -12,33 +12,46 @@ namespace react {
 
 constexpr uint32_t RAMBundleRegistry::MAIN_BUNDLE_ID;
 
-std::unique_ptr<RAMBundleRegistry> RAMBundleRegistry::singleBundleRegistry(std::unique_ptr<JSModulesUnbundle> mainBundle) {
-  RAMBundleRegistry *registry = new RAMBundleRegistry(std::move(mainBundle));
-  return std::unique_ptr<RAMBundleRegistry>(registry);
+std::unique_ptr<RAMBundleRegistry> RAMBundleRegistry::singleBundleRegistry(
+    std::unique_ptr<JSModulesUnbundle> mainBundle) {
+  return folly::make_unique<RAMBundleRegistry>(std::move(mainBundle));
 }
 
-std::unique_ptr<RAMBundleRegistry> RAMBundleRegistry::multipleBundlesRegistry(std::unique_ptr<JSModulesUnbundle> mainBundle, std::function<std::unique_ptr<JSModulesUnbundle>(std::string)> factory) {
-  RAMBundleRegistry *registry = new RAMBundleRegistry(std::move(mainBundle), std::move(factory));
-  return std::unique_ptr<RAMBundleRegistry>(registry);
+std::unique_ptr<RAMBundleRegistry> RAMBundleRegistry::multipleBundlesRegistry(
+    std::unique_ptr<JSModulesUnbundle> mainBundle,
+    std::function<std::unique_ptr<JSModulesUnbundle>(std::string)> factory) {
+  return folly::make_unique<RAMBundleRegistry>(
+      std::move(mainBundle), std::move(factory));
 }
 
-RAMBundleRegistry::RAMBundleRegistry(std::unique_ptr<JSModulesUnbundle> mainBundle, std::function<std::unique_ptr<JSModulesUnbundle>(std::string)> factory): m_factory(factory) {
+RAMBundleRegistry::RAMBundleRegistry(
+    std::unique_ptr<JSModulesUnbundle> mainBundle,
+    std::function<std::unique_ptr<JSModulesUnbundle>(std::string)> factory):
+      m_factory(std::move(factory)) {
   m_bundles.emplace(MAIN_BUNDLE_ID, std::move(mainBundle));
 }
 
-void RAMBundleRegistry::registerBundle(uint32_t bundleId, std::string bundlePath) {
-  m_bundlePaths.emplace(bundleId, bundlePath);
+void RAMBundleRegistry::registerBundle(
+    uint32_t bundleId, std::string bundlePath) {
+  m_bundlePaths.emplace(bundleId, std::move(bundlePath));
 }
 
-JSModulesUnbundle::Module RAMBundleRegistry::getModule(uint32_t bundleId, uint32_t moduleId) {
+JSModulesUnbundle::Module RAMBundleRegistry::getModule(
+    uint32_t bundleId, uint32_t moduleId) {
   if (m_bundles.find(bundleId) == m_bundles.end()) {
     if (!m_factory) {
-      throw std::runtime_error("You need to register factory function in order to support multiple RAM bundles.");
+      throw std::runtime_error(
+        "You need to register factory function in order to "
+        "support multiple RAM bundles."
+      );
     }
 
     auto bundlePath = m_bundlePaths.find(bundleId);
     if (bundlePath == m_bundlePaths.end()) {
-      throw std::runtime_error("In order to fetch RAM bundle from the registry, its file path needs to be registered first.");
+      throw std::runtime_error(
+        "In order to fetch RAM bundle from the registry, its file "
+        "path needs to be registered first."
+      );
     }
     m_bundles.emplace(bundleId, m_factory(bundlePath->second));
   }
@@ -53,7 +66,7 @@ JSModulesUnbundle::Module RAMBundleRegistry::getModule(uint32_t bundleId, uint32
   };
 }
 
-JSModulesUnbundle *RAMBundleRegistry::getBundle(uint32_t bundleId) const {
+JSModulesUnbundle* RAMBundleRegistry::getBundle(uint32_t bundleId) const {
   return m_bundles.at(bundleId).get();
 }
 
diff --git a/ReactCommon/cxxreact/RAMBundleRegistry.h b/ReactCommon/cxxreact/RAMBundleRegistry.h
index 2d628f22c35d..9fb546066bed 100644
--- a/ReactCommon/cxxreact/RAMBundleRegistry.h
+++ b/ReactCommon/cxxreact/RAMBundleRegistry.h
@@ -20,26 +20,31 @@ namespace react {
 
 class RN_EXPORT RAMBundleRegistry : noncopyable {
 public:
-  using unique_ram_bundle = std::unique_ptr<JSModulesUnbundle>;
-  using bundle_path = std::string;
   constexpr static uint32_t MAIN_BUNDLE_ID = 0;
 
-  static std::unique_ptr<RAMBundleRegistry> singleBundleRegistry(unique_ram_bundle mainBundle);
-  static std::unique_ptr<RAMBundleRegistry> multipleBundlesRegistry(unique_ram_bundle mainBundle, std::function<unique_ram_bundle(bundle_path)> factory);
+  static std::unique_ptr<RAMBundleRegistry> singleBundleRegistry(
+      std::unique_ptr<JSModulesUnbundle> mainBundle);
+  static std::unique_ptr<RAMBundleRegistry> multipleBundlesRegistry(
+      std::unique_ptr<JSModulesUnbundle> mainBundle,
+      std::function<std::unique_ptr<JSModulesUnbundle>(std::string)> factory);
+
+  explicit RAMBundleRegistry(
+      std::unique_ptr<JSModulesUnbundle> mainBundle,
+      std::function<
+        std::unique_ptr<JSModulesUnbundle>(std::string)> factory = nullptr);
 
   RAMBundleRegistry(RAMBundleRegistry&&) = default;
   RAMBundleRegistry& operator=(RAMBundleRegistry&&) = default;
 
-  void registerBundle(uint32_t bundleId, bundle_path bundlePath);
+  void registerBundle(uint32_t bundleId, std::string bundlePath);
   JSModulesUnbundle::Module getModule(uint32_t bundleId, uint32_t moduleId);
   virtual ~RAMBundleRegistry() {};
 private:
-  explicit RAMBundleRegistry(unique_ram_bundle mainBundle, std::function<unique_ram_bundle(bundle_path)> factory = {});
-  JSModulesUnbundle *getBundle(uint32_t bundleId) const;
+  JSModulesUnbundle* getBundle(uint32_t bundleId) const;
 
-  std::function<unique_ram_bundle(bundle_path)> m_factory;
-  std::unordered_map<uint32_t, bundle_path> m_bundlePaths;
-  std::unordered_map<uint32_t, unique_ram_bundle> m_bundles;
+  std::function<std::unique_ptr<JSModulesUnbundle>(std::string)> m_factory;
+  std::unordered_map<uint32_t, std::string> m_bundlePaths;
+  std::unordered_map<uint32_t, std::unique_ptr<JSModulesUnbundle>> m_bundles;
 };
 
 }  // namespace react

From 7c5d581d7848206603cf9d80a841afb49759ec1a Mon Sep 17 00:00:00 2001
From: shockdesign <rajesh@shockdesign.com.au>
Date: Tue, 17 Apr 2018 13:21:09 -0700
Subject: [PATCH 0321/1109] Switch equality check in BlobModule.java

Summary:
Switch the equality check to avoid crash on the first item. The check can be on a null object and return the correct result.

Fixes #18709

Just a simple switch on equals, to make sure we're not bombing out by having a null scheme.

No related PRs and does not require a document change.

[ANDROID][BUGFIX][BlobModule] Switch equality check in BlobModule.java
Closes https://github.com/facebook/react-native/pull/18893

Differential Revision: D7658036

Pulled By: hramos

fbshipit-source-id: db61b98dae178dbbb645070f7b0d73ab43d30541
---
 .../main/java/com/facebook/react/modules/blob/BlobModule.java   | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BlobModule.java b/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BlobModule.java
index 0c2adc91d43f..ee62d2cd2784 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BlobModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BlobModule.java
@@ -79,7 +79,7 @@ public void onMessage(ByteString bytes, WritableMap params) {
       @Override
       public boolean supports(Uri uri, String responseType) {
         String scheme = uri.getScheme();
-        boolean isRemote = scheme.equals("http") || scheme.equals("https");
+        boolean isRemote = "http".equals(scheme) || "https".equals(scheme);
 
         return (!isRemote && responseType.equals("blob"));
       }

From 4469952c9a493dbb865aa7c29055502b44ff570e Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Tue, 17 Apr 2018 13:27:46 -0700
Subject: [PATCH 0322/1109] Pass drawable width and height in pixels for inline
 image

Reviewed By: achen1

Differential Revision: D7655775

fbshipit-source-id: 32887eb5a686ccc45f50fb334248aad6889f704a
---
 .../frescosupport/FrescoBasedReactTextInlineImageSpan.java | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
index d769d50fce99..39cd24c6fd3c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
@@ -9,6 +9,7 @@
 
 import android.graphics.Color;
 import android.graphics.PorterDuff;
+import com.facebook.react.uimanager.PixelUtil;
 import javax.annotation.Nullable;
 
 import android.content.res.Resources;
@@ -70,12 +71,12 @@ public FrescoBasedReactTextInlineImageSpan(
     );
     mDraweeControllerBuilder = draweeControllerBuilder;
     mCallerContext = callerContext;
-
-    mHeight = height;
     mTintColor = tintColor;
-    mWidth = width;
     mUri = (uri != null) ? uri : Uri.EMPTY;
     mHeaders = headers;
+    mWidth = (int)(PixelUtil.toPixelFromDIP(width));
+    mHeight = (int)(PixelUtil.toPixelFromDIP(height));
+
   }
 
   /**

From c10c6dbf7c808b4f69007f297afea7d6f3522612 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 17 Apr 2018 13:54:42 -0700
Subject: [PATCH 0323/1109] Move Fabric tests to OSS

Reviewed By: mdvacca

Differential Revision: D7654802

fbshipit-source-id: a30c8cf062636243066a1fc73da0711442a29c76
---
 .../test/java/com/facebook/react/fabric/BUCK  |  41 ++
 .../react/fabric/FabricReconcilerTest.java    | 224 ++++++++++
 .../react/fabric/FabricUIManagerTest.java     | 387 ++++++++++++++++++
 3 files changed, 652 insertions(+)
 create mode 100644 ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
 create mode 100644 ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
 create mode 100644 ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java

diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
new file mode 100644
index 000000000000..21917d67f81f
--- /dev/null
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
@@ -0,0 +1,41 @@
+load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target")
+
+rn_robolectric_test(
+    name = "fabric",
+    srcs = glob(["**/*.java"]),
+    contacts = ["oncall+fbandroid_sheriff@xmail.facebook.com"],
+    resources = glob([
+        "**/*.txt",
+        "**/*.json",
+    ]),
+    visibility = [
+        "PUBLIC",
+    ],
+    deps = [
+        "xplat//yoga/java:java",
+        react_native_dep("java/com/facebook/common/executors:executors"),
+        react_native_dep("java/com/facebook/testing/robolectric/v3:v3"),
+        react_native_dep("third-party/java/assertj:assertj-core"),
+        react_native_dep("third-party/java/fest:fest"),
+        react_native_dep("third-party/java/fest:fest_android"),
+        react_native_dep("third-party/java/guava:guava"),
+        react_native_dep("third-party/java/jackson:jackson"),
+        react_native_dep("third-party/java/jsr-305:jsr-305"),
+        react_native_dep("third-party/java/jsr-330:jsr-330"),
+        react_native_dep("third-party/java/junit:junit"),
+        react_native_dep("third-party/java/mockito:mockito"),
+        react_native_dep("third-party/java/robolectric3/robolectric:robolectric"),
+        react_native_dep("libraries/fbcore/src/test/java/com/facebook/powermock:powermock"),
+        react_native_dep("libraries/soloader/java/com/facebook/soloader:soloader"),
+        react_native_dep("third-party/android/support/v4:lib-support-v4"),
+        react_native_target("java/com/facebook/react:react"),
+        react_native_target("java/com/facebook/react/bridge:bridge"),
+        react_native_target("java/com/facebook/react/common:common"),
+        react_native_target("java/com/facebook/react/fabric:fabric"),
+        react_native_target("java/com/facebook/react/modules/core:core"),
+        react_native_target("java/com/facebook/react/uimanager:uimanager"),
+        react_native_target("java/com/facebook/react/views/text:text"),
+        react_native_target("java/com/facebook/react/views/view:view"),
+        react_native_tests_target("java/com/facebook/react/bridge:testhelpers"),
+    ],
+)
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
new file mode 100644
index 000000000000..23272c23427c
--- /dev/null
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
@@ -0,0 +1,224 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+package com.facebook.react.fabric;
+
+import static org.fest.assertions.api.Assertions.assertThat;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+import static org.powermock.api.mockito.PowerMockito.mockStatic;
+
+import com.facebook.react.bridge.ReactApplicationContext;
+import com.facebook.react.common.ClearableSynchronizedPool;
+import com.facebook.react.fabric.FabricReconciler;
+import com.facebook.react.modules.core.ReactChoreographer;
+import com.facebook.react.uimanager.NativeViewHierarchyManager;
+import com.facebook.react.uimanager.ReactShadowNode;
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
+import com.facebook.react.uimanager.ReactYogaConfigProvider;
+import com.facebook.react.uimanager.UIViewOperationQueue;
+import com.facebook.react.uimanager.ViewAtIndex;
+import com.facebook.react.uimanager.YogaNodePool;
+import com.facebook.testing.robolectric.v3.WithTestDefaultsRunner;
+import com.facebook.yoga.YogaConfig;
+import com.facebook.yoga.YogaNode;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.invocation.InvocationOnMock;
+import org.mockito.stubbing.Answer;
+import org.powermock.api.mockito.PowerMockito;
+import org.powermock.core.classloader.annotations.PowerMockIgnore;
+import org.powermock.core.classloader.annotations.PrepareForTest;
+import org.robolectric.RuntimeEnvironment;
+
+/** Tests {@link FabricReconciler} */
+@PrepareForTest({
+  ReactChoreographer.class,
+  ReactYogaConfigProvider.class,
+  YogaNodePool.class,
+})
+@RunWith(WithTestDefaultsRunner.class)
+@PowerMockIgnore({"org.mockito.*", "org.robolectric.*", "android.*"})
+public class FabricReconcilerTest {
+
+  private FabricReconciler mFabricReconciler;
+  private MockUIViewOperationQueue mMockUIViewOperationQueue;
+
+  @Before
+  public void setUp() {
+    ReactApplicationContext reactContext =
+        new ReactApplicationContext(RuntimeEnvironment.application);
+    mMockUIViewOperationQueue = new MockUIViewOperationQueue(reactContext);
+    mFabricReconciler = new FabricReconciler(mMockUIViewOperationQueue);
+
+    setupHacks();
+  }
+
+  @Test
+  public void testSimpleHierarchy() {
+    ReactShadowNode parent = createNode(0);
+    ReactShadowNode child1 = createNode(1);
+    ReactShadowNode child2 = createNode(2);
+    addChildren(parent, child1, child2);
+
+    ReactShadowNode parentCloned = createNode(0);
+    ReactShadowNode child3 = createNode(3);
+    addChildren(parentCloned, child3, child2);
+
+    mFabricReconciler.manageChildren(parent, parentCloned);
+
+    List<ManageChildrenOperation> expectedOperations = new ArrayList<>();
+    expectedOperations.add(
+        new ManageChildrenOperation(
+            0,
+            new int[] {0, 1},
+            new ViewAtIndex[] {new ViewAtIndex(3, 0), new ViewAtIndex(2, 1)},
+            new int[] {1}));
+    assertThat(mMockUIViewOperationQueue.getOperations()).isEqualTo(expectedOperations);
+  }
+
+  @Test
+  public void testVirtualNodes() {
+    ReactShadowNode parent = createNode(0);
+    ReactShadowNode child1 = createVirtualNode(1);
+    ReactShadowNode child2 = createVirtualNode(2);
+    ReactShadowNode child3 = createVirtualNode(3);
+    addChildren(parent, child1, child2, child3);
+
+    ReactShadowNode parentCloned = createNode(0);
+    ReactShadowNode child4 = createVirtualNode(4);
+    addChildren(parentCloned, child1, child4, child3);
+
+    mFabricReconciler.manageChildren(parent, parentCloned);
+
+    List<ManageChildrenOperation> expectedOperations = new ArrayList<>();
+    assertThat(mMockUIViewOperationQueue.getOperations()).isEqualTo(expectedOperations);
+  }
+
+  private static ReactShadowNode createNode(int tag) {
+    return createNode(tag, false);
+  }
+
+  private static ReactShadowNode createVirtualNode(int tag) {
+    return createNode(tag, true);
+  }
+
+  private static ReactShadowNode createNode(int tag, boolean virtual) {
+    ReactShadowNode node;
+    if (virtual) {
+      node = new VirtualReactShadowNode();
+    } else {
+      node = new ReactShadowNodeImpl();
+    }
+    node.setReactTag(tag);
+    return node;
+  }
+
+  private static class VirtualReactShadowNode extends ReactShadowNodeImpl {
+
+    @Override
+    public boolean isVirtual() {
+      return true;
+    }
+  }
+
+  private static void addChildren(ReactShadowNode parent, ReactShadowNode... children) {
+    for (ReactShadowNode child : children) {
+      parent.addChildAt(child, parent.getChildCount());
+    }
+  }
+
+  private static class ManageChildrenOperation {
+    private int mTag;
+    private int[] mIndicesToRemove;
+    private ViewAtIndex[] mViewsToAdd;
+    private int[] mTagsToRemove;
+
+    private ManageChildrenOperation(
+        int tag, int[] indicesToRemove, ViewAtIndex[] viewsToAdd, int[] tagsToRemove) {
+      mTag = tag;
+      mIndicesToRemove = indicesToRemove;
+      mViewsToAdd = viewsToAdd;
+      mTagsToRemove = tagsToRemove;
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+      if (obj == null || obj.getClass() != getClass()) {
+        return false;
+      }
+      ManageChildrenOperation op = (ManageChildrenOperation) obj;
+      return mTag == op.mTag
+          && Arrays.equals(mIndicesToRemove, op.mIndicesToRemove)
+          && Arrays.equals(mViewsToAdd, op.mViewsToAdd)
+          && Arrays.equals(mTagsToRemove, op.mTagsToRemove);
+    }
+
+    @Override
+    public int hashCode() {
+      return Arrays.deepHashCode(new Object[] {mTag, mIndicesToRemove, mViewsToAdd, mTagsToRemove});
+    }
+
+    @Override
+    public String toString() {
+      return "ManageChildrenOperation \n\tindicesToRemove: "
+          + Arrays.toString(mIndicesToRemove)
+          + "\n\tviewsToAdd: "
+          + Arrays.toString(mViewsToAdd)
+          + "\n\ttagsToRemove: "
+          + Arrays.toString(mTagsToRemove);
+    }
+  }
+
+  private static class MockUIViewOperationQueue extends UIViewOperationQueue {
+
+    private List<ManageChildrenOperation> mOperations;
+
+    private MockUIViewOperationQueue(ReactApplicationContext context) {
+      super(context, mock(NativeViewHierarchyManager.class), 0);
+      mOperations = new ArrayList<>();
+    }
+
+    @Override
+    public void enqueueManageChildren(
+        int reactTag, int[] indicesToRemove, ViewAtIndex[] viewsToAdd, int[] tagsToDelete) {
+      mOperations.add(
+          new ManageChildrenOperation(reactTag, indicesToRemove, viewsToAdd, tagsToDelete));
+    }
+
+    public List<ManageChildrenOperation> getOperations() {
+      return Collections.unmodifiableList(mOperations);
+    }
+  }
+
+  /** Hacks to get tests to start working end to end */
+  private void setupHacks() {
+    // Hack around Yoga by mocking it out until the UnsatisfiedLinkErrors are fixed t14964130
+    mockStatic(YogaNodePool.class, ReactYogaConfigProvider.class);
+    PowerMockito.when(YogaNodePool.get())
+        .thenAnswer(
+            new Answer<Object>() {
+              @Override
+              public Object answer(InvocationOnMock invocation) throws Exception {
+                ClearableSynchronizedPool<YogaNode> yogaPool =
+                    mock(ClearableSynchronizedPool.class);
+                YogaNode yogaNode = mock(YogaNode.class);
+                when(yogaNode.clone()).thenReturn(mock(YogaNode.class));
+                when(yogaNode.isMeasureDefined()).thenReturn(true);
+                when(yogaPool.acquire()).thenReturn(yogaNode);
+                return yogaPool;
+              }
+            });
+    PowerMockito.when(ReactYogaConfigProvider.get())
+        .thenAnswer(
+            new Answer<Object>() {
+              @Override
+              public Object answer(InvocationOnMock invocation) {
+                return mock(YogaConfig.class);
+              }
+            });
+  }
+}
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
new file mode 100644
index 000000000000..d1aebcd7e263
--- /dev/null
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -0,0 +1,387 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+package com.facebook.react.fabric;
+
+import static org.fest.assertions.api.Assertions.assertThat;
+import static org.mockito.Matchers.any;
+import static org.mockito.Mockito.doAnswer;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
+import com.facebook.react.ReactRootView;
+import com.facebook.react.bridge.CatalystInstance;
+import com.facebook.react.bridge.ReactApplicationContext;
+import com.facebook.react.bridge.ReactTestHelper;
+import com.facebook.react.bridge.ReadableNativeMap;
+import com.facebook.react.common.ClearableSynchronizedPool;
+import com.facebook.react.fabric.FabricUIManager;
+import com.facebook.react.uimanager.ReactShadowNode;
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
+import com.facebook.react.uimanager.ReactYogaConfigProvider;
+import com.facebook.react.uimanager.Spacing;
+import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.ViewManager;
+import com.facebook.react.uimanager.ViewManagerRegistry;
+import com.facebook.react.uimanager.YogaNodePool;
+import com.facebook.react.views.text.ReactRawTextManager;
+import com.facebook.react.views.text.ReactRawTextShadowNode;
+import com.facebook.react.views.text.ReactTextViewManager;
+import com.facebook.react.views.view.ReactViewManager;
+import com.facebook.testing.robolectric.v3.WithTestDefaultsRunner;
+import com.facebook.yoga.YogaConfig;
+import com.facebook.yoga.YogaMeasureFunction;
+import com.facebook.yoga.YogaNode;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.LinkedList;
+import java.util.List;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.invocation.InvocationOnMock;
+import org.mockito.stubbing.Answer;
+import org.powermock.api.mockito.PowerMockito;
+import org.powermock.core.classloader.annotations.PrepareForTest;
+import org.robolectric.RuntimeEnvironment;
+
+/** Tests {@link FabricUIManager} */
+@PrepareForTest({YogaNodePool.class, ReactYogaConfigProvider.class})
+@RunWith(WithTestDefaultsRunner.class)
+public class FabricUIManagerTest {
+
+  private FabricUIManager mFabricUIManager;
+  private ThemedReactContext mThemedReactContext;
+  private int mNextReactTag;
+  private MockYogaNodePool mMockYogaNodePool;
+
+  private YogaMeasureFunction mLastYogaMeasureFunction;
+
+  @Before
+  public void setUp() throws Exception {
+    mNextReactTag = 2;
+    mThemedReactContext = mock(ThemedReactContext.class);
+    CatalystInstance catalystInstance = ReactTestHelper.createMockCatalystInstance();
+    ReactApplicationContext reactContext =
+        new ReactApplicationContext(RuntimeEnvironment.application);
+    reactContext.initializeWithInstance(catalystInstance);
+    List<ViewManager> viewManagers =
+        Arrays.<ViewManager>asList(
+            new ReactViewManager(), new ReactTextViewManager(), new ReactRawTextManager());
+    ViewManagerRegistry viewManagerRegistry = new ViewManagerRegistry(viewManagers);
+
+    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry);
+
+    // Hack around Yoga until the UnsatisfiedLinkErrors are fixed t14964130
+    PowerMockito.mockStatic(YogaNodePool.class, ReactYogaConfigProvider.class);
+    mMockYogaNodePool = new MockYogaNodePool();
+    PowerMockito.when(YogaNodePool.get()).thenReturn(mMockYogaNodePool);
+    PowerMockito.when(ReactYogaConfigProvider.get())
+        .thenAnswer(
+            new Answer<Object>() {
+              @Override
+              public Object answer(InvocationOnMock invocation) {
+                return mock(YogaConfig.class);
+              }
+            });
+  }
+
+  @Test
+  public void testCreateNode() {
+    ReactRootView rootView =
+        new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
+    int rootTag = mFabricUIManager.addRootView(rootView);
+    int reactTag = mNextReactTag++;
+    String viewClass = ReactViewManager.REACT_CLASS;
+    ReactShadowNode node = mFabricUIManager.createNode(reactTag, viewClass, rootTag, null);
+
+    assertThat(reactTag).isEqualTo(node.getReactTag());
+    assertThat(viewClass).isEqualTo(node.getViewClass());
+    assertThat(rootTag).isEqualTo(rootTag);
+  }
+
+  @Test
+  public void testCreateMultpleRootViews() {
+    createAndRenderRootView();
+    createAndRenderRootView();
+  }
+
+  private int createAndRenderRootView() {
+    ReactRootView rootView =
+        new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
+    int rootTag = mFabricUIManager.addRootView(rootView);
+    int reactTag = mNextReactTag++;
+    String viewClass = ReactViewManager.REACT_CLASS;
+    ReactShadowNode node = mFabricUIManager.createNode(reactTag, viewClass, rootTag, null);
+
+    List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(rootTag);
+    mFabricUIManager.appendChildToSet(childSet, node);
+    mFabricUIManager.completeRoot(rootTag, childSet);
+
+    return rootTag;
+  }
+
+  @Test
+  public void testCloneNode() {
+    ReactShadowNode node = createViewNode();
+    ReactShadowNode child = createViewNode();
+    node.addChildAt(child, 0);
+
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node);
+
+    assertThat(clonedNode).isNotSameAs(node);
+    assertThat(clonedNode.getOriginalReactShadowNode()).isSameAs(node);
+    assertSameFields(clonedNode, node);
+    assertSameChildren(clonedNode, node);
+    assertThat(clonedNode.getChildAt(0)).isEqualTo(child);
+  }
+
+  @Test
+  public void testCloneVirtualNode() {
+    ReactRawTextShadowNode node = new ReactRawTextShadowNode();
+    node.setText("test");
+    assertThat(node.isVirtual()).isTrue();
+
+    ReactRawTextShadowNode clonedNode = (ReactRawTextShadowNode) node.mutableCopy();
+
+    assertThat(clonedNode.getText()).isEqualTo("test");
+    assertThat(clonedNode).isNotEqualTo(node);
+  }
+
+  @Test
+  public void testCloneNodeWithNewChildren() {
+    ReactShadowNode node = createViewNode();
+    ReactShadowNode child = createViewNode();
+    node.addChildAt(child, 0);
+
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node);
+
+    assertThat(clonedNode.getChildCount()).isZero();
+    assertSameFields(clonedNode, node);
+  }
+
+  @Test
+  public void testCloneNodeWithNewProps() {
+    ReactShadowNode node = createViewNode();
+    ReadableNativeMap props = null; // TODO(ayc): Figure out how to create a Native map from tests.
+
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props);
+  }
+
+  @Test
+  public void testCloneNodeWithNewChildrenAndProps() {
+    ReactShadowNode node = createViewNode();
+    ReadableNativeMap props = null;
+
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props);
+
+    assertThat(clonedNode.getChildCount()).isZero();
+  }
+
+  @Test
+  public void testAppendChild() {
+    ReactShadowNode node = createViewNode();
+    ReactShadowNode child = createViewNode();
+
+    mFabricUIManager.appendChild(node, child);
+
+    assertThat(node.getChildCount()).isEqualTo(1);
+    assertThat(node.getChildAt(0)).isEqualTo(child);
+  }
+
+  @Test
+  public void testCreateChildSet() {
+    List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(0);
+
+    assertThat(childSet).isEmpty();
+  }
+
+  @Test
+  public void testAppendChildToSet() {
+    ReactShadowNode node = createViewNode();
+    List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(0);
+
+    mFabricUIManager.appendChildToSet(childSet, node);
+
+    assertThat(childSet).hasSize(1);
+    assertThat(childSet).contains(node);
+  }
+
+  @Test(expected = AssertionError.class)
+  public void testCompleteRootBeforeAddRoot() {
+    mFabricUIManager.completeRoot(0, new ArrayList<ReactShadowNode>());
+  }
+
+  @Test
+  public void testCompleteRoot() {
+    ReactRootView rootView =
+        new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
+    int rootTag = mFabricUIManager.addRootView(rootView);
+    List<ReactShadowNode> children = mFabricUIManager.createChildSet(rootTag);
+
+    mFabricUIManager.completeRoot(rootTag, children);
+  }
+
+  /**
+   * Tests that cloned text nodes will reassign their yoga nodes' measure functions.
+   *
+   * <p>TODO(T26729515): Currently this tests the wrong implementation. It assumes that yoga nodes
+   * are reused across clones and simply checks the most recently assigned measure functions of the
+   * shared yoga node. When yoga node cloning is implemented, this needs to be changed to mock each
+   * cloned shadow nodes' yoga nodes and make the same assertions on each of their measure
+   * functions.
+   */
+  @Test
+  public void testTextMutableClone() {
+    ReactRootView rootView =
+        new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
+    int rootTag = mFabricUIManager.addRootView(rootView);
+
+    final YogaNode yogaNode = mock(YogaNode.class);
+
+    doAnswer(
+            new Answer() {
+              @Override
+              public Object answer(InvocationOnMock invocation) {
+                when(yogaNode.isMeasureDefined()).thenReturn(true);
+                when(yogaNode.clone()).thenReturn(yogaNode);
+                when(yogaNode.cloneWithNewChildren()).thenReturn(yogaNode);
+                mLastYogaMeasureFunction = (YogaMeasureFunction) invocation.getArguments()[0];
+                return null;
+              }
+            })
+        .when(yogaNode)
+        .setMeasureFunction(any(YogaMeasureFunction.class));
+
+    mMockYogaNodePool.add(yogaNode);
+
+    ReactShadowNode text =
+        mFabricUIManager.createNode(0, ReactTextViewManager.REACT_CLASS, rootTag, null);
+    YogaMeasureFunction textMeasureFunction = mLastYogaMeasureFunction;
+    assertThat(text.isMeasureDefined()).isTrue();
+
+    ReactShadowNode textCopy = text.mutableCopy();
+    YogaMeasureFunction textCopyMeasureFunction = mLastYogaMeasureFunction;
+    assertThat(textCopy.isMeasureDefined()).isTrue();
+    assertThat(textCopyMeasureFunction).isNotSameAs(textMeasureFunction);
+
+    ReactShadowNode textCopyWithNewChildren = text.mutableCopyWithNewChildren();
+    YogaMeasureFunction textCopyWithNewChildrenMeasureFunction = mLastYogaMeasureFunction;
+    assertThat(textCopyWithNewChildren.isMeasureDefined()).isTrue();
+    assertThat(textCopyWithNewChildrenMeasureFunction).isNotSameAs(textMeasureFunction);
+    assertThat(textCopyWithNewChildrenMeasureFunction).isNotSameAs(textCopyMeasureFunction);
+  }
+
+  /**
+   * Verifies that the reconciliation phase will always set the originalNode field of every node in
+   * the tree to null once completeRoot has finished to prevent memory leaks.
+   */
+  @Test
+  public void testRemoveOriginalNodeReferences() {
+    ReactRootView rootView =
+        new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
+    int rootTag = mFabricUIManager.addRootView(rootView);
+    String viewClass = ReactViewManager.REACT_CLASS;
+
+    ReactShadowNode aa = mFabricUIManager.createNode(2, viewClass, rootTag, null);
+    ReactShadowNode a = mFabricUIManager.createNode(3, viewClass, rootTag, null);
+    mFabricUIManager.appendChild(a, aa);
+    ReactShadowNode bb = mFabricUIManager.createNode(4, viewClass, rootTag, null);
+    ReactShadowNode b = mFabricUIManager.createNode(5, viewClass, rootTag, null);
+    mFabricUIManager.appendChild(b, bb);
+    ReactShadowNode container = mFabricUIManager.createNode(6, viewClass, rootTag, null);
+    mFabricUIManager.appendChild(container, a);
+    mFabricUIManager.appendChild(container, b);
+    List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(rootTag);
+    mFabricUIManager.appendChildToSet(childSet, container);
+    mFabricUIManager.completeRoot(rootTag, childSet);
+
+    ReactShadowNode aaClone = mFabricUIManager.cloneNodeWithNewProps(aa, null);
+    ReactShadowNode aClone = mFabricUIManager.cloneNodeWithNewChildren(a);
+    mFabricUIManager.appendChild(aClone, aaClone);
+    ReactShadowNode containerClone = mFabricUIManager.cloneNodeWithNewChildren(container);
+    mFabricUIManager.appendChild(containerClone, b);
+    mFabricUIManager.appendChild(containerClone, aClone);
+    List<ReactShadowNode> childSet2 = mFabricUIManager.createChildSet(rootTag);
+    mFabricUIManager.appendChildToSet(childSet2, containerClone);
+    mFabricUIManager.completeRoot(rootTag, childSet2);
+
+    ReactShadowNode[] nodes =
+        new ReactShadowNode[] {aa, a, bb, b, container, aaClone, aClone, containerClone};
+
+    for (ReactShadowNode node : nodes) {
+      assertThat(node.getOriginalReactShadowNode()).isNull();
+    }
+  }
+
+  private void assertSameChildren(ReactShadowNode node1, ReactShadowNode node2) {
+    assertThat(node1.getChildCount()).isEqualTo(node2.getChildCount());
+    for (int i = 0; i < node1.getChildCount(); i++) {
+      assertThat(node1.getChildAt(i)).isEqualTo(node2.getChildAt(i));
+    }
+  }
+
+  private void assertSameFields(ReactShadowNode node1, ReactShadowNode node2) {
+    assertThat(node1.getReactTag()).isEqualTo(node2.getReactTag());
+    assertThat(node1.getViewClass()).isEqualTo(node2.getViewClass());
+    assertThat(node2.getParent()).isNull();
+    assertThat(node1.getThemedContext()).isEqualTo(node2.getThemedContext());
+    assertThat(node1.isVirtual()).isEqualTo(node2.isVirtual());
+    assertThat(node1.getLayoutDirection()).isEqualTo(node2.getLayoutDirection());
+    assertThat(node1.getLayoutHeight()).isEqualTo(node2.getLayoutHeight());
+    assertThat(node1.getLayoutWidth()).isEqualTo(node2.getLayoutWidth());
+    assertThat(node1.getLayoutX()).isEqualTo(node2.getLayoutX());
+    assertThat(node1.getLayoutY()).isEqualTo(node2.getLayoutY());
+    for (int spacingType = Spacing.LEFT; spacingType <= Spacing.ALL; spacingType++) {
+      assertThat(node1.getPadding(spacingType)).isEqualTo(node2.getPadding(spacingType));
+      assertThat(node1.getStylePadding(spacingType)).isEqualTo(node2.getStylePadding(spacingType));
+    }
+    assertThat(node1.getStyleWidth()).isEqualTo(node2.getStyleWidth());
+    assertThat(node1.getStyleHeight()).isEqualTo(node2.getStyleHeight());
+  }
+
+  private ReactShadowNode createViewNode() {
+    ReactShadowNode node = new ReactShadowNodeImpl();
+    node.setViewClassName(ReactViewManager.REACT_CLASS);
+    node.setThemedContext(mThemedReactContext);
+    return node;
+  }
+
+  private static class MockYogaNodePool extends ClearableSynchronizedPool<YogaNode> {
+
+    private List<YogaNode> mMockYogaNodes;
+
+    public MockYogaNodePool() {
+      super(1024);
+      mMockYogaNodes = new LinkedList<>();
+    }
+
+    public void add(YogaNode... nodes) {
+      Collections.addAll(mMockYogaNodes, nodes);
+    }
+
+    @Override
+    public synchronized YogaNode acquire() {
+      if (!mMockYogaNodes.isEmpty()) {
+        return mMockYogaNodes.remove(0);
+      }
+      return createMockYogaNode();
+    }
+
+    private static YogaNode createMockYogaNode() {
+      final YogaNode yogaNode = mock(YogaNode.class);
+      when(yogaNode.clone()).thenReturn(yogaNode);
+      when(yogaNode.cloneWithNewChildren()).thenReturn(yogaNode);
+      doAnswer(
+              new Answer() {
+                @Override
+                public Object answer(InvocationOnMock invocation) {
+                  when(yogaNode.isMeasureDefined()).thenReturn(true);
+                  return null;
+                }
+              })
+          .when(yogaNode)
+          .setMeasureFunction(any(YogaMeasureFunction.class));
+      return yogaNode;
+    }
+  }
+}

From c4ab03a18e75e6ed55444b5d86f3ceee435b9a78 Mon Sep 17 00:00:00 2001
From: Luciano Lima <beavess@gmail.com>
Date: Tue, 17 Apr 2018 16:12:03 -0700
Subject: [PATCH 0324/1109] Add devDependencies support for templates

Summary:
Add devDependencies support to React Native templates.
Template can have a devDependencies.json file with devDependencies inside.
Using separate files to dependencies and devDependencies, it maintains compatibility with the current version.

Allows React Native templates to have devDependencies, which can help applications to have better organization, quality and testability. It's possible start a new app with some dependencies for dev support like prettier, reactotron, eslint packages and others.

Add a devDependencies.json file with at least one dependency (like prettier)

[CLI] [FEATURE] [local-cli/generator/templates.js] - Add support to devDependencies for react native templates
Closes https://github.com/facebook/react-native/pull/18164

Differential Revision: D7660744

Pulled By: hramos

fbshipit-source-id: 6fbb13832d2d1bd0c06bada0842c890dd99cf331
---
 local-cli/generator/templates.js | 34 ++++++++++++++++++++++++++++++++
 1 file changed, 34 insertions(+)

diff --git a/local-cli/generator/templates.js b/local-cli/generator/templates.js
index 98e2897a5d02..99e63ec2e99c 100644
--- a/local-cli/generator/templates.js
+++ b/local-cli/generator/templates.js
@@ -99,6 +99,7 @@ function createFromBuiltInTemplate(templateName, destPath, newProjectName, yarnV
     newProjectName,
   );
   installTemplateDependencies(templatePath, yarnVersion);
+  installTemplateDevDependencies(templatePath, yarnVersion);
 }
 
 /**
@@ -143,6 +144,7 @@ function createFromRemoteTemplate(template, destPath, newProjectName, yarnVersio
       }
     );
     installTemplateDependencies(templatePath, yarnVersion);
+    installTemplateDevDependencies(templatePath, yarnVersion);
   } finally {
     // Clean up the temp files
     try {
@@ -196,6 +198,38 @@ function installTemplateDependencies(templatePath, yarnVersion) {
   execSync('react-native link', {stdio: 'inherit'});
 }
 
+function installTemplateDevDependencies(templatePath, yarnVersion) {
+  // devDependencies.json is a special file that lists additional develop dependencies
+  // that are required by this template
+  const devDependenciesJsonPath = path.resolve(
+    templatePath, 'devDependencies.json'
+  );
+  console.log('Adding develop dependencies for the project...');
+  if (!fs.existsSync(devDependenciesJsonPath)) {
+    console.log('No additional develop dependencies.');
+    return;
+  }
+
+  let dependencies;
+  try {
+    dependencies = JSON.parse(fs.readFileSync(devDependenciesJsonPath));
+  } catch (err) {
+    throw new Error(
+      'Could not parse the template\'s devDependencies.json: ' + err.message
+    );
+  }
+  for (let depName in dependencies) {
+    const depVersion = dependencies[depName];
+    const depToInstall = depName + '@' + depVersion;
+    console.log('Adding ' + depToInstall + '...');
+    if (yarnVersion) {
+      execSync(`yarn add ${depToInstall} -D`, {stdio: 'inherit'});
+    } else {
+      execSync(`npm install ${depToInstall} --save-dev --save-exact`, {stdio: 'inherit'});
+    }
+  }
+}
+
 module.exports = {
   listTemplatesAndExit,
   createProjectFromTemplate,

From ff9b3c6517d6427b8ca0cec2660555152be3d028 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 17 Apr 2018 17:17:12 -0700
Subject: [PATCH 0325/1109] Display JS component stack in native view
 exceptions

Reviewed By: mdvacca

Differential Revision: D7578033

fbshipit-source-id: 4dc393cddf8487db58cc3a9fefbff220983ba9da
---
 Libraries/Renderer/shims/ReactNativeTypes.js  |  1 +
 Libraries/Utilities/JSDevSupportModule.js     | 27 ++++---
 .../com/facebook/react/DebugCorePackage.java  |  9 ---
 .../com/facebook/react/ReactRootView.java     | 13 ++--
 .../devsupport/DevSupportManagerImpl.java     | 71 -------------------
 .../react/devsupport/JSDevSupport.java        | 59 ++++++++++-----
 .../react/devsupport/ViewHierarchyUtil.java   | 37 ++++++++++
 7 files changed, 102 insertions(+), 115 deletions(-)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/devsupport/ViewHierarchyUtil.java

diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index fdee974ae88a..1f7f5d0015a2 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -72,6 +72,7 @@ export type NativeMethodsMixinType = {
 type SecretInternalsType = {
   NativeMethodsMixin: NativeMethodsMixinType,
   ReactNativeComponentTree: any,
+  computeComponentStackForErrorReporting(tag: number): string,
   // TODO (bvaughn) Decide which additional types to expose here?
   // And how much information to fill in for the above types.
 };
diff --git a/Libraries/Utilities/JSDevSupportModule.js b/Libraries/Utilities/JSDevSupportModule.js
index a33e91e88618..dc45030bf3b5 100644
--- a/Libraries/Utilities/JSDevSupportModule.js
+++ b/Libraries/Utilities/JSDevSupportModule.js
@@ -9,16 +9,25 @@
  */
 'use strict';
 
-var JSDevSupportModule = {
-  getJSHierarchy: function (tag: string) {
-    const hook = window.__REACT_DEVTOOLS_GLOBAL_HOOK__;
-    const renderers = hook._renderers;
-    const keys = Object.keys(renderers);
-    const renderer = renderers[keys[0]];
+const JSDevSupport = require('NativeModules').JSDevSupport;
+const ReactNative = require('ReactNative');
 
-    var result = renderer.getInspectorDataForViewTag(tag);
-    var path = result.hierarchy.map( (item) => item.name).join(' -> ');
-    require('NativeModules').JSDevSupport.setResult(path, null);
+const JSDevSupportModule = {
+  getJSHierarchy: function (tag: number) {
+    try {
+      const {computeComponentStackForErrorReporting} =
+          ReactNative.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+      const componentStack = computeComponentStackForErrorReporting(tag);
+      if (!componentStack) {
+        JSDevSupport.onFailure(
+          JSDevSupport.ERROR_CODE_VIEW_NOT_FOUND,
+          'Component stack doesn\'t exist for tag ' + tag);
+      } else {
+        JSDevSupport.onSuccess(componentStack);
+      }
+    } catch (e) {
+      JSDevSupport.onFailure(JSDevSupport.ERROR_CODE_EXCEPTION, e.message);
+    }
   },
 };
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/DebugCorePackage.java b/ReactAndroid/src/main/java/com/facebook/react/DebugCorePackage.java
index 290082e545ba..1de05ef8977a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/DebugCorePackage.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/DebugCorePackage.java
@@ -48,15 +48,6 @@ public NativeModule get() {
                 return new JSCHeapCapture(reactContext);
               }
             }));
-    moduleSpecList.add(
-      ModuleSpec.nativeModuleSpec(
-        JSDevSupport.class,
-        new Provider<NativeModule>() {
-          @Override
-          public NativeModule get() {
-            return new JSDevSupport(reactContext);
-          }
-        }));
     moduleSpecList.add(
         ModuleSpec.nativeModuleSpec(
             JSCSamplingProfiler.class,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index c1d74a4aeddb..baa2a6e30d96 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -42,11 +42,11 @@
 import com.facebook.react.uimanager.DisplayMetricsHolder;
 import com.facebook.react.uimanager.IllegalViewOperationException;
 import com.facebook.react.uimanager.JSTouchDispatcher;
-import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.RootView;
-import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 import com.facebook.react.uimanager.UIManagerModule;
+import com.facebook.react.uimanager.common.MeasureSpecProvider;
+import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.systrace.Systrace;
 import javax.annotation.Nullable;
@@ -572,18 +572,13 @@ public void setRootViewTag(int rootViewTag) {
   }
 
   @Override
-  public void handleException(Throwable t) {
+  public void handleException(final Throwable t) {
     if (mReactInstanceManager == null
       || mReactInstanceManager.getCurrentReactContext() == null) {
         throw new RuntimeException(t);
     }
 
-    // Adding special exception management for StackOverflowError for logging purposes.
-    // This will be removed in the future.
-    Exception e = (t instanceof StackOverflowError) ?
-      new IllegalViewOperationException("StackOverflowException", this, t) :
-      t instanceof Exception ? (Exception) t : new RuntimeException(t);
-
+    Exception e = new IllegalViewOperationException(t.getMessage(), this, t);
     mReactInstanceManager.getCurrentReactContext().handleException(e);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
index c04211a98b09..ea25bf86c42a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
@@ -22,10 +22,7 @@
 import android.net.Uri;
 import android.os.AsyncTask;
 import android.util.Pair;
-import android.view.View;
-import android.view.ViewGroup;
 import android.widget.Toast;
-
 import com.facebook.common.logging.FLog;
 import com.facebook.debug.holder.PrinterHolder;
 import com.facebook.debug.tags.ReactDebugOverlayTags;
@@ -45,7 +42,6 @@
 import com.facebook.react.common.ShakeDetector;
 import com.facebook.react.common.futures.SimpleSettableFuture;
 import com.facebook.react.devsupport.DevServerHelper.PackagerCommandListener;
-import com.facebook.react.devsupport.InspectorPackagerConnection;
 import com.facebook.react.devsupport.interfaces.DevBundleDownloadListener;
 import com.facebook.react.devsupport.interfaces.DevOptionHandler;
 import com.facebook.react.devsupport.interfaces.DevSupportManager;
@@ -55,24 +51,18 @@
 import com.facebook.react.modules.debug.interfaces.DeveloperSettings;
 import com.facebook.react.packagerconnection.RequestHandler;
 import com.facebook.react.packagerconnection.Responder;
-
-import com.facebook.react.uimanager.IllegalViewOperationException;
 import java.io.File;
 import java.io.IOException;
 import java.net.MalformedURLException;
 import java.net.URL;
 import java.util.ArrayList;
 import java.util.LinkedHashMap;
-import java.util.LinkedList;
 import java.util.List;
 import java.util.Locale;
-import java.util.Queue;
 import java.util.concurrent.ExecutionException;
 import java.util.concurrent.TimeUnit;
 import java.util.concurrent.TimeoutException;
-
 import javax.annotation.Nullable;
-
 import okhttp3.MediaType;
 import okhttp3.OkHttpClient;
 import okhttp3.Request;
@@ -274,7 +264,6 @@ public void onReceive(Context context, Intent intent) {
             new DevLoadingViewController(applicationContext, reactInstanceManagerHelper);
 
     mExceptionLoggers.add(new JSExceptionLogger());
-    mExceptionLoggers.add(new StackOverflowExceptionLogger());
   }
 
   @Override
@@ -322,66 +311,6 @@ public void log(Exception e) {
     }
   }
 
-  private class StackOverflowExceptionLogger implements ExceptionLogger {
-
-    @Override
-    public void log(Exception e) {
-      if (e instanceof IllegalViewOperationException
-        && e.getCause() instanceof StackOverflowError) {
-        IllegalViewOperationException ivoe = (IllegalViewOperationException) e;
-        View view = ivoe.getView();
-        if (view != null)
-          logDeepestJSHierarchy(view);
-      }
-    }
-
-    private void logDeepestJSHierarchy(View view) {
-      if (mCurrentContext == null || view == null) return;
-
-      final Pair<View, Integer> deepestPairView = getDeepestNativeView(view);
-
-      View deepestView = deepestPairView.first;
-      Integer tagId = deepestView.getId();
-      final int depth = deepestPairView.second;
-      JSDevSupport JSDevSupport = mCurrentContext.getNativeModule(JSDevSupport.class);
-      JSDevSupport.getJSHierarchy(tagId.toString(), new JSDevSupport.DevSupportCallback() {
-        @Override
-        public void onSuccess(String hierarchy) {
-          FLog.e(ReactConstants.TAG,
-            "StackOverflowError when rendering JS Hierarchy (depth of native hierarchy = " +
-              depth +  "): \n" + hierarchy);
-        }
-
-        @Override
-        public void onFailure(Exception ex) {
-          FLog.e(ReactConstants.TAG, ex,
-            "Error retrieving JS Hierarchy (depth of native hierarchy = " + depth + ").");
-        }
-      });
-    }
-
-    private Pair<View, Integer> getDeepestNativeView(View root) {
-      Queue<Pair<View, Integer>> queue = new LinkedList<>();
-      Pair<View, Integer> maxPair = new Pair<>(root, 1);
-
-      queue.add(maxPair);
-      while (!queue.isEmpty()) {
-        Pair<View, Integer> current = queue.poll();
-        if (current.second > maxPair.second) {
-          maxPair = current;
-        }
-        if (current.first instanceof ViewGroup) {
-          ViewGroup viewGroup = (ViewGroup) current.first;
-          Integer depth = current.second + 1;
-          for (int i = 0 ; i < viewGroup.getChildCount() ; i++) {
-            queue.add(new Pair<>(viewGroup.getChildAt(i), depth));
-          }
-        }
-      }
-      return maxPair;
-    }
-  }
-
   @Override
   public void showNewJavaError(String message, Throwable e) {
     FLog.e(ReactConstants.TAG, "Exception in native call", e);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/JSDevSupport.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/JSDevSupport.java
index b5596d7f365a..4e306ba1035d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/JSDevSupport.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/JSDevSupport.java
@@ -2,23 +2,31 @@
 
 package com.facebook.react.devsupport;
 
+import android.util.Pair;
+import android.view.View;
 import com.facebook.react.bridge.JavaScriptModule;
 import com.facebook.react.bridge.ReactApplicationContext;
+import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.bridge.ReactContextBaseJavaModule;
 import com.facebook.react.bridge.ReactMethod;
 import com.facebook.react.module.annotations.ReactModule;
+import java.util.HashMap;
+import java.util.Map;
 import javax.annotation.Nullable;
 
-@ReactModule(name = "JSDevSupport", needsEagerInit = true)
+@ReactModule(name = JSDevSupport.MODULE_NAME)
 public class JSDevSupport extends ReactContextBaseJavaModule {
 
   static final String MODULE_NAME = "JSDevSupport";
 
+  public static final int ERROR_CODE_EXCEPTION = 0;
+  public static final int ERROR_CODE_VIEW_NOT_FOUND = 1;
+
   @Nullable
   private volatile DevSupportCallback mCurrentCallback = null;
 
   public interface JSDevSupportModule extends JavaScriptModule {
-    void getJSHierarchy(String reactTag);
+    void getJSHierarchy(int reactTag);
   }
 
   public JSDevSupport(ReactApplicationContext reactContext) {
@@ -29,19 +37,25 @@ public interface DevSupportCallback {
 
     void onSuccess(String data);
 
-    void onFailure(Exception error);
+    void onFailure(int errorCode, Exception error);
   }
 
-  public synchronized void getJSHierarchy(String reactTag, DevSupportCallback callback) {
-    if (mCurrentCallback != null) {
-      callback.onFailure(new RuntimeException("JS Hierarchy download already in progress."));
-      return;
-    }
+  /**
+   * Notifies the callback with either the JS hierarchy of the deepest leaf from the given root view
+   * or with an error.
+   */
+  public synchronized void computeDeepestJSHierarchy(View root, DevSupportCallback callback) {
+    final Pair<View, Integer> deepestPairView = ViewHierarchyUtil.getDeepestLeaf(root);
+    View deepestView = deepestPairView.first;
+    Integer tagId = deepestView.getId();
+    getJSHierarchy(tagId, callback);
+  }
 
+  public synchronized void getJSHierarchy(int reactTag, DevSupportCallback callback) {
     JSDevSupportModule
         jsDevSupportModule = getReactApplicationContext().getJSModule(JSDevSupportModule.class);
     if (jsDevSupportModule == null) {
-      callback.onFailure(new JSCHeapCapture.CaptureException(MODULE_NAME +
+      callback.onFailure(ERROR_CODE_EXCEPTION, new JSCHeapCapture.CaptureException(MODULE_NAME +
         " module not registered."));
       return;
     }
@@ -51,20 +65,31 @@ public synchronized void getJSHierarchy(String reactTag, DevSupportCallback call
 
   @SuppressWarnings("unused")
   @ReactMethod
-  public synchronized void setResult(String data, String error) {
+  public synchronized void onSuccess(String data) {
+    if (mCurrentCallback != null) {
+      mCurrentCallback.onSuccess(data);
+    }
+  }
+
+  @SuppressWarnings("unused")
+  @ReactMethod
+  public synchronized void onFailure(int errorCode, String error) {
     if (mCurrentCallback != null) {
-      if (error == null) {
-        mCurrentCallback.onSuccess(data);
-      } else {
-        mCurrentCallback.onFailure(new RuntimeException(error));
-      }
+      mCurrentCallback.onFailure(errorCode, new RuntimeException(error));
     }
-    mCurrentCallback = null;
+  }
+
+  @Override
+  public Map<String, Object> getConstants() {
+    HashMap<String, Object> constants = new HashMap<>();
+    constants.put("ERROR_CODE_EXCEPTION", ERROR_CODE_EXCEPTION);
+    constants.put("ERROR_CODE_VIEW_NOT_FOUND", ERROR_CODE_VIEW_NOT_FOUND);
+    return constants;
   }
 
   @Override
   public String getName() {
-    return "JSDevSupport";
+    return MODULE_NAME;
   }
 
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/ViewHierarchyUtil.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/ViewHierarchyUtil.java
new file mode 100644
index 000000000000..1aee0099e5f3
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/ViewHierarchyUtil.java
@@ -0,0 +1,37 @@
+package com.facebook.react.devsupport;
+
+import android.util.Pair;
+import android.view.View;
+import android.view.ViewGroup;
+import java.util.LinkedList;
+import java.util.Queue;
+
+/**
+ * Helper for computing information about the view hierarchy
+ */
+public class ViewHierarchyUtil {
+
+  /**
+   * Returns the view instance and depth of the deepest leaf view from the given root view.
+   */
+  public static Pair<View, Integer> getDeepestLeaf(View root) {
+    Queue<Pair<View, Integer>> queue = new LinkedList<>();
+    Pair<View, Integer> maxPair = new Pair<>(root, 1);
+
+    queue.add(maxPair);
+    while (!queue.isEmpty()) {
+      Pair<View, Integer> current = queue.poll();
+      if (current.second > maxPair.second) {
+        maxPair = current;
+      }
+      if (current.first instanceof ViewGroup) {
+        ViewGroup viewGroup = (ViewGroup) current.first;
+        Integer depth = current.second + 1;
+        for (int i = 0 ; i < viewGroup.getChildCount() ; i++) {
+          queue.add(new Pair<>(viewGroup.getChildAt(i), depth));
+        }
+      }
+    }
+    return maxPair;
+  }
+}

From 864cc00a6107fd8144f1c4ecaf5b35260d00cf7d Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Tue, 17 Apr 2018 18:11:28 -0700
Subject: [PATCH 0326/1109] Use real YogaNodes in FabricUIManagerTest

Reviewed By: mdvacca

Differential Revision: D7663769

fbshipit-source-id: 78cdde975037c4e8d97d4bd21ddd7927cc105dd0
---
 .../react/fabric/FabricUIManagerTest.java     | 103 ++----------------
 1 file changed, 8 insertions(+), 95 deletions(-)

diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index d1aebcd7e263..540ce011c708 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -16,20 +16,15 @@
 import com.facebook.react.fabric.FabricUIManager;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import com.facebook.react.uimanager.ReactYogaConfigProvider;
 import com.facebook.react.uimanager.Spacing;
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
-import com.facebook.react.uimanager.YogaNodePool;
 import com.facebook.react.views.text.ReactRawTextManager;
 import com.facebook.react.views.text.ReactRawTextShadowNode;
 import com.facebook.react.views.text.ReactTextViewManager;
 import com.facebook.react.views.view.ReactViewManager;
 import com.facebook.testing.robolectric.v3.WithTestDefaultsRunner;
-import com.facebook.yoga.YogaConfig;
-import com.facebook.yoga.YogaMeasureFunction;
-import com.facebook.yoga.YogaNode;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
@@ -45,16 +40,12 @@
 import org.robolectric.RuntimeEnvironment;
 
 /** Tests {@link FabricUIManager} */
-@PrepareForTest({YogaNodePool.class, ReactYogaConfigProvider.class})
 @RunWith(WithTestDefaultsRunner.class)
 public class FabricUIManagerTest {
 
   private FabricUIManager mFabricUIManager;
   private ThemedReactContext mThemedReactContext;
   private int mNextReactTag;
-  private MockYogaNodePool mMockYogaNodePool;
-
-  private YogaMeasureFunction mLastYogaMeasureFunction;
 
   @Before
   public void setUp() throws Exception {
@@ -70,19 +61,6 @@ public void setUp() throws Exception {
     ViewManagerRegistry viewManagerRegistry = new ViewManagerRegistry(viewManagers);
 
     mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry);
-
-    // Hack around Yoga until the UnsatisfiedLinkErrors are fixed t14964130
-    PowerMockito.mockStatic(YogaNodePool.class, ReactYogaConfigProvider.class);
-    mMockYogaNodePool = new MockYogaNodePool();
-    PowerMockito.when(YogaNodePool.get()).thenReturn(mMockYogaNodePool);
-    PowerMockito.when(ReactYogaConfigProvider.get())
-        .thenAnswer(
-            new Answer<Object>() {
-              @Override
-              public Object answer(InvocationOnMock invocation) {
-                return mock(YogaConfig.class);
-              }
-            });
   }
 
   @Test
@@ -222,13 +200,7 @@ public void testCompleteRoot() {
   }
 
   /**
-   * Tests that cloned text nodes will reassign their yoga nodes' measure functions.
-   *
-   * <p>TODO(T26729515): Currently this tests the wrong implementation. It assumes that yoga nodes
-   * are reused across clones and simply checks the most recently assigned measure functions of the
-   * shared yoga node. When yoga node cloning is implemented, this needs to be changed to mock each
-   * cloned shadow nodes' yoga nodes and make the same assertions on each of their measure
-   * functions.
+   * Tests that cloned text nodes will not share measure functions
    */
   @Test
   public void testTextMutableClone() {
@@ -236,39 +208,20 @@ public void testTextMutableClone() {
         new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
     int rootTag = mFabricUIManager.addRootView(rootView);
 
-    final YogaNode yogaNode = mock(YogaNode.class);
-
-    doAnswer(
-            new Answer() {
-              @Override
-              public Object answer(InvocationOnMock invocation) {
-                when(yogaNode.isMeasureDefined()).thenReturn(true);
-                when(yogaNode.clone()).thenReturn(yogaNode);
-                when(yogaNode.cloneWithNewChildren()).thenReturn(yogaNode);
-                mLastYogaMeasureFunction = (YogaMeasureFunction) invocation.getArguments()[0];
-                return null;
-              }
-            })
-        .when(yogaNode)
-        .setMeasureFunction(any(YogaMeasureFunction.class));
-
-    mMockYogaNodePool.add(yogaNode);
-
     ReactShadowNode text =
         mFabricUIManager.createNode(0, ReactTextViewManager.REACT_CLASS, rootTag, null);
-    YogaMeasureFunction textMeasureFunction = mLastYogaMeasureFunction;
     assertThat(text.isMeasureDefined()).isTrue();
 
     ReactShadowNode textCopy = text.mutableCopy();
-    YogaMeasureFunction textCopyMeasureFunction = mLastYogaMeasureFunction;
     assertThat(textCopy.isMeasureDefined()).isTrue();
-    assertThat(textCopyMeasureFunction).isNotSameAs(textMeasureFunction);
 
-    ReactShadowNode textCopyWithNewChildren = text.mutableCopyWithNewChildren();
-    YogaMeasureFunction textCopyWithNewChildrenMeasureFunction = mLastYogaMeasureFunction;
-    assertThat(textCopyWithNewChildren.isMeasureDefined()).isTrue();
-    assertThat(textCopyWithNewChildrenMeasureFunction).isNotSameAs(textMeasureFunction);
-    assertThat(textCopyWithNewChildrenMeasureFunction).isNotSameAs(textCopyMeasureFunction);
+    textCopy.setStyleWidth(200);
+    text.onBeforeLayout();
+    text.calculateLayout();
+    textCopy.onBeforeLayout();
+    textCopy.calculateLayout();
+
+    assertThat(text.getLayoutWidth()).isNotEqualTo(textCopy.getLayoutWidth());
   }
 
   /**
@@ -332,7 +285,6 @@ private void assertSameFields(ReactShadowNode node1, ReactShadowNode node2) {
     assertThat(node1.getLayoutX()).isEqualTo(node2.getLayoutX());
     assertThat(node1.getLayoutY()).isEqualTo(node2.getLayoutY());
     for (int spacingType = Spacing.LEFT; spacingType <= Spacing.ALL; spacingType++) {
-      assertThat(node1.getPadding(spacingType)).isEqualTo(node2.getPadding(spacingType));
       assertThat(node1.getStylePadding(spacingType)).isEqualTo(node2.getStylePadding(spacingType));
     }
     assertThat(node1.getStyleWidth()).isEqualTo(node2.getStyleWidth());
@@ -345,43 +297,4 @@ private ReactShadowNode createViewNode() {
     node.setThemedContext(mThemedReactContext);
     return node;
   }
-
-  private static class MockYogaNodePool extends ClearableSynchronizedPool<YogaNode> {
-
-    private List<YogaNode> mMockYogaNodes;
-
-    public MockYogaNodePool() {
-      super(1024);
-      mMockYogaNodes = new LinkedList<>();
-    }
-
-    public void add(YogaNode... nodes) {
-      Collections.addAll(mMockYogaNodes, nodes);
-    }
-
-    @Override
-    public synchronized YogaNode acquire() {
-      if (!mMockYogaNodes.isEmpty()) {
-        return mMockYogaNodes.remove(0);
-      }
-      return createMockYogaNode();
-    }
-
-    private static YogaNode createMockYogaNode() {
-      final YogaNode yogaNode = mock(YogaNode.class);
-      when(yogaNode.clone()).thenReturn(yogaNode);
-      when(yogaNode.cloneWithNewChildren()).thenReturn(yogaNode);
-      doAnswer(
-              new Answer() {
-                @Override
-                public Object answer(InvocationOnMock invocation) {
-                  when(yogaNode.isMeasureDefined()).thenReturn(true);
-                  return null;
-                }
-              })
-          .when(yogaNode)
-          .setMeasureFunction(any(YogaMeasureFunction.class));
-      return yogaNode;
-    }
-  }
 }

From aa6239301ab2eae2aefb44b024e18e5d5ee9be99 Mon Sep 17 00:00:00 2001
From: Pascal Hartig <realpassy@fb.com>
Date: Wed, 18 Apr 2018 04:29:45 -0700
Subject: [PATCH 0327/1109] Add getParent() method for easier migration

Reviewed By: emilsjolander

Differential Revision: D7654526

fbshipit-source-id: efe44807caa97f495c5e5691dedcf281760fa23e
---
 ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index 59a14d242088..fdb5b4be5017 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -239,6 +239,13 @@ YogaNode getOwner() {
     return mOwner;
   }
 
+  /** @deprecated Use #getOwner() instead. This will be removed in the next version. */
+  @Deprecated
+  @Nullable
+  YogaNode getParent() {
+    return getOwner();
+  }
+
   public int indexOf(YogaNode child) {
     return mChildren == null ? -1 : mChildren.indexOf(child);
   }

From 850fd869422d50a990f9ce64a37495cbd851fc47 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Wed, 18 Apr 2018 12:09:11 -0700
Subject: [PATCH 0328/1109] Bump metro@0.33.0

Reviewed By: davidaurelio

Differential Revision: D7661486

fbshipit-source-id: 5186a853eaff139948622e93d851deb9577567dc
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index 3509869f9b45..066c873aa89f 100644
--- a/package.json
+++ b/package.json
@@ -166,8 +166,8 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.32.0",
-    "metro-core": "^0.32.0",
+    "metro": "^0.33.0",
+    "metro-core": "^0.33.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From af2095842535c05613240215052fbcdd2f34ce64 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 18 Apr 2018 14:55:52 -0700
Subject: [PATCH 0329/1109] Use real YogaNodes in FabricReconcilerTest

Reviewed By: mdvacca

Differential Revision: D7664493

fbshipit-source-id: 74b088a91ea4f691cc15b5ea15dd585fe46e2035
---
 .../react/fabric/FabricReconcilerTest.java    | 80 +++++++------------
 1 file changed, 28 insertions(+), 52 deletions(-)

diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
index 23272c23427c..26def0ca1c2c 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
@@ -4,22 +4,21 @@
 import static org.fest.assertions.api.Assertions.assertThat;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.when;
-import static org.powermock.api.mockito.PowerMockito.mockStatic;
 
+import com.facebook.react.bridge.CatalystInstance;
 import com.facebook.react.bridge.ReactApplicationContext;
-import com.facebook.react.common.ClearableSynchronizedPool;
+import com.facebook.react.bridge.ReactTestHelper;
 import com.facebook.react.fabric.FabricReconciler;
-import com.facebook.react.modules.core.ReactChoreographer;
+import com.facebook.react.fabric.FabricUIManager;
 import com.facebook.react.uimanager.NativeViewHierarchyManager;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import com.facebook.react.uimanager.ReactYogaConfigProvider;
 import com.facebook.react.uimanager.UIViewOperationQueue;
 import com.facebook.react.uimanager.ViewAtIndex;
-import com.facebook.react.uimanager.YogaNodePool;
+import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.ViewManager;
+import com.facebook.react.uimanager.ViewManagerRegistry;
 import com.facebook.testing.robolectric.v3.WithTestDefaultsRunner;
-import com.facebook.yoga.YogaConfig;
-import com.facebook.yoga.YogaNode;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
@@ -27,34 +26,27 @@
 import org.junit.Before;
 import org.junit.Test;
 import org.junit.runner.RunWith;
-import org.mockito.invocation.InvocationOnMock;
-import org.mockito.stubbing.Answer;
-import org.powermock.api.mockito.PowerMockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
 import org.robolectric.RuntimeEnvironment;
 
 /** Tests {@link FabricReconciler} */
-@PrepareForTest({
-  ReactChoreographer.class,
-  ReactYogaConfigProvider.class,
-  YogaNodePool.class,
-})
 @RunWith(WithTestDefaultsRunner.class)
-@PowerMockIgnore({"org.mockito.*", "org.robolectric.*", "android.*"})
 public class FabricReconcilerTest {
 
   private FabricReconciler mFabricReconciler;
+  private FabricUIManager mFabricUIManager;
   private MockUIViewOperationQueue mMockUIViewOperationQueue;
 
   @Before
   public void setUp() {
+    CatalystInstance catalystInstance = ReactTestHelper.createMockCatalystInstance();
     ReactApplicationContext reactContext =
         new ReactApplicationContext(RuntimeEnvironment.application);
+    reactContext.initializeWithInstance(catalystInstance);
+    List<ViewManager> viewManagers = new ArrayList<>();
+    ViewManagerRegistry viewManagerRegistry = new ViewManagerRegistry(viewManagers);
+    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry);
     mMockUIViewOperationQueue = new MockUIViewOperationQueue(reactContext);
     mFabricReconciler = new FabricReconciler(mMockUIViewOperationQueue);
-
-    setupHacks();
   }
 
   @Test
@@ -98,6 +90,12 @@ public void testVirtualNodes() {
     assertThat(mMockUIViewOperationQueue.getOperations()).isEqualTo(expectedOperations);
   }
 
+  private void addChildren(ReactShadowNode parent, ReactShadowNode... children) {
+    for (ReactShadowNode child : children) {
+      mFabricUIManager.appendChild(parent, child);
+    }
+  }
+
   private static ReactShadowNode createNode(int tag) {
     return createNode(tag, false);
   }
@@ -114,20 +112,26 @@ private static ReactShadowNode createNode(int tag, boolean virtual) {
       node = new ReactShadowNodeImpl();
     }
     node.setReactTag(tag);
+    node.setThemedContext(mock(ThemedReactContext.class));
     return node;
   }
 
   private static class VirtualReactShadowNode extends ReactShadowNodeImpl {
 
+    VirtualReactShadowNode() {}
+
+    VirtualReactShadowNode(VirtualReactShadowNode original) {
+      super(original);
+    }
+
     @Override
     public boolean isVirtual() {
       return true;
     }
-  }
 
-  private static void addChildren(ReactShadowNode parent, ReactShadowNode... children) {
-    for (ReactShadowNode child : children) {
-      parent.addChildAt(child, parent.getChildCount());
+    @Override
+    public ReactShadowNodeImpl copy() {
+      return new VirtualReactShadowNode(this);
     }
   }
 
@@ -193,32 +197,4 @@ public List<ManageChildrenOperation> getOperations() {
       return Collections.unmodifiableList(mOperations);
     }
   }
-
-  /** Hacks to get tests to start working end to end */
-  private void setupHacks() {
-    // Hack around Yoga by mocking it out until the UnsatisfiedLinkErrors are fixed t14964130
-    mockStatic(YogaNodePool.class, ReactYogaConfigProvider.class);
-    PowerMockito.when(YogaNodePool.get())
-        .thenAnswer(
-            new Answer<Object>() {
-              @Override
-              public Object answer(InvocationOnMock invocation) throws Exception {
-                ClearableSynchronizedPool<YogaNode> yogaPool =
-                    mock(ClearableSynchronizedPool.class);
-                YogaNode yogaNode = mock(YogaNode.class);
-                when(yogaNode.clone()).thenReturn(mock(YogaNode.class));
-                when(yogaNode.isMeasureDefined()).thenReturn(true);
-                when(yogaPool.acquire()).thenReturn(yogaNode);
-                return yogaPool;
-              }
-            });
-    PowerMockito.when(ReactYogaConfigProvider.get())
-        .thenAnswer(
-            new Answer<Object>() {
-              @Override
-              public Object answer(InvocationOnMock invocation) {
-                return mock(YogaConfig.class);
-              }
-            });
-  }
 }

From 2ad0a92d388db6ba9a1e699640a3394092dbb521 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 18 Apr 2018 14:55:54 -0700
Subject: [PATCH 0330/1109] Fix OSS Fabric test build

Reviewed By: fkgozali

Differential Revision: D7676633

fbshipit-source-id: a7db945395af10d06dddc1fde4bd035aee14b702
---
 ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK     | 2 --
 .../java/com/facebook/react/fabric/FabricReconcilerTest.java  | 4 ++--
 .../java/com/facebook/react/fabric/FabricUIManagerTest.java   | 4 ++--
 3 files changed, 4 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
index 21917d67f81f..55eb26ebc3e6 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
@@ -13,8 +13,6 @@ rn_robolectric_test(
     ],
     deps = [
         "xplat//yoga/java:java",
-        react_native_dep("java/com/facebook/common/executors:executors"),
-        react_native_dep("java/com/facebook/testing/robolectric/v3:v3"),
         react_native_dep("third-party/java/assertj:assertj-core"),
         react_native_dep("third-party/java/fest:fest"),
         react_native_dep("third-party/java/fest:fest_android"),
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
index 26def0ca1c2c..36dfa8267a7e 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
@@ -18,7 +18,6 @@
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
-import com.facebook.testing.robolectric.v3.WithTestDefaultsRunner;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
@@ -26,10 +25,11 @@
 import org.junit.Before;
 import org.junit.Test;
 import org.junit.runner.RunWith;
+import org.robolectric.RobolectricTestRunner;
 import org.robolectric.RuntimeEnvironment;
 
 /** Tests {@link FabricReconciler} */
-@RunWith(WithTestDefaultsRunner.class)
+@RunWith(RobolectricTestRunner.class)
 public class FabricReconcilerTest {
 
   private FabricReconciler mFabricReconciler;
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 540ce011c708..40c8b2e78d55 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -24,7 +24,6 @@
 import com.facebook.react.views.text.ReactRawTextShadowNode;
 import com.facebook.react.views.text.ReactTextViewManager;
 import com.facebook.react.views.view.ReactViewManager;
-import com.facebook.testing.robolectric.v3.WithTestDefaultsRunner;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collections;
@@ -37,10 +36,11 @@
 import org.mockito.stubbing.Answer;
 import org.powermock.api.mockito.PowerMockito;
 import org.powermock.core.classloader.annotations.PrepareForTest;
+import org.robolectric.RobolectricTestRunner;
 import org.robolectric.RuntimeEnvironment;
 
 /** Tests {@link FabricUIManager} */
-@RunWith(WithTestDefaultsRunner.class)
+@RunWith(RobolectricTestRunner.class)
 public class FabricUIManagerTest {
 
   private FabricUIManager mFabricUIManager;

From 908e8850b9335d229fd51e60168dd6c161f7a026 Mon Sep 17 00:00:00 2001
From: Brian Vaughn <bvaughn@fb.com>
Date: Wed, 18 Apr 2018 14:59:57 -0700
Subject: [PATCH 0331/1109] Forked RN renderers for FB and OSS
 (52afbe0...0887c7d)

Reviewed By: fkgozali

Differential Revision: D7658727

fbshipit-source-id: 2fdd30694b169d180b40bc1059ecc297b07cd18d
---
 Libraries/Renderer/REVISION                   |     2 +-
 .../Renderer/{ => fb}/ReactFabric-dev.js      |    28 +-
 .../Renderer/{ => fb}/ReactFabric-prod.js     |    23 +-
 .../{shims => fb}/ReactFeatureFlags.js        |     0
 .../{ => fb}/ReactNativeRenderer-dev.js       |    28 +-
 .../{ => fb}/ReactNativeRenderer-prod.js      |    23 +-
 Libraries/Renderer/oss/ReactFabric-dev.js     | 13863 +++++++++++++++
 Libraries/Renderer/oss/ReactFabric-prod.js    |  5876 +++++++
 .../Renderer/oss/ReactNativeRenderer-dev.js   | 14432 ++++++++++++++++
 .../Renderer/oss/ReactNativeRenderer-prod.js  |  6311 +++++++
 Libraries/Renderer/shims/ReactNativeTypes.js  |     7 +-
 package.json                                  |     6 +-
 12 files changed, 40572 insertions(+), 27 deletions(-)
 rename Libraries/Renderer/{ => fb}/ReactFabric-dev.js (99%)
 rename Libraries/Renderer/{ => fb}/ReactFabric-prod.js (99%)
 rename Libraries/Renderer/{shims => fb}/ReactFeatureFlags.js (100%)
 rename Libraries/Renderer/{ => fb}/ReactNativeRenderer-dev.js (99%)
 rename Libraries/Renderer/{ => fb}/ReactNativeRenderer-prod.js (99%)
 create mode 100644 Libraries/Renderer/oss/ReactFabric-dev.js
 create mode 100644 Libraries/Renderer/oss/ReactFabric-prod.js
 create mode 100644 Libraries/Renderer/oss/ReactNativeRenderer-dev.js
 create mode 100644 Libraries/Renderer/oss/ReactNativeRenderer-prod.js

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index 4d4db61db4a5..ba0ce2996c48 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-52afbe0ebb6fca0fe480e77c6fa8482870ddb2c9
\ No newline at end of file
+0887c7d56cb9b83f36dcb490b4245d7bc33bda1f
\ No newline at end of file
diff --git a/Libraries/Renderer/ReactFabric-dev.js b/Libraries/Renderer/fb/ReactFabric-dev.js
similarity index 99%
rename from Libraries/Renderer/ReactFabric-dev.js
rename to Libraries/Renderer/fb/ReactFabric-dev.js
index e933ab8f0bb4..0424315c8ed6 100644
--- a/Libraries/Renderer/ReactFabric-dev.js
+++ b/Libraries/Renderer/fb/ReactFabric-dev.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactFabric-dev
  * @preventMunge
  */
 
@@ -2392,7 +2391,7 @@ var injection$2 = {
 
 // TODO: this is special because it gets imported during build.
 
-var ReactVersion = "16.3.1";
+var ReactVersion = "16.3.2";
 
 // Modules provided by RN:
 var emptyObject$1 = {};
@@ -3387,6 +3386,15 @@ function getComponentName(fiber) {
     case REACT_RETURN_TYPE:
       return "ReactReturn";
   }
+  if (typeof type === "object" && type !== null) {
+    switch (type.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        var functionName = type.render.displayName || type.render.name || "";
+        return functionName !== ""
+          ? "ForwardRef(" + functionName + ")"
+          : "ForwardRef";
+    }
+  }
   return null;
 }
 
@@ -4735,6 +4743,7 @@ var shouldIgnoreFiber = function(fiber) {
     case Fragment:
     case ContextProvider:
     case ContextConsumer:
+    case Mode:
       return true;
     default:
       return false;
@@ -12377,8 +12386,19 @@ var ReactFiberScheduler = function(config) {
   }
 
   function computeInteractiveExpiration(currentTime) {
-    // Should complete within ~500ms. 600ms max.
-    var expirationMs = 500;
+    var expirationMs = void 0;
+    // We intentionally set a higher expiration time for interactive updates in
+    // dev than in production.
+    // If the main thread is being blocked so long that you hit the expiration,
+    // it's a problem that could be solved with better scheduling.
+    // People will be more likely to notice this and fix it with the long
+    // expiration time in development.
+    // In production we opt for better UX at the risk of masking scheduling
+    // problems, by expiring fast.
+    {
+      // Should complete within ~500ms. 600ms max.
+      expirationMs = 500;
+    }
     var bucketSizeMs = 100;
     return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
   }
diff --git a/Libraries/Renderer/ReactFabric-prod.js b/Libraries/Renderer/fb/ReactFabric-prod.js
similarity index 99%
rename from Libraries/Renderer/ReactFabric-prod.js
rename to Libraries/Renderer/fb/ReactFabric-prod.js
index d264fcf01637..19ca0dde9e33 100644
--- a/Libraries/Renderer/ReactFabric-prod.js
+++ b/Libraries/Renderer/fb/ReactFabric-prod.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactFabric-prod
  * @preventMunge
  */
 
@@ -1242,6 +1241,14 @@ function getComponentName(fiber) {
     case REACT_RETURN_TYPE:
       return "ReactReturn";
   }
+  if ("object" === typeof fiber && null !== fiber)
+    switch (fiber.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        return (
+          (fiber = fiber.render.displayName || fiber.render.name || ""),
+          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
+        );
+    }
   return null;
 }
 function isFiberMountedImpl(fiber) {
@@ -2753,15 +2760,17 @@ function ChildReconciler(shouldTrackSideEffects) {
               currentFirstChild,
               newChild,
               expirationTime
-            )))
+            )),
+            (currentFirstChild["return"] = returnFiber),
+            (returnFiber = currentFirstChild))
           : (deleteRemainingChildren(returnFiber, currentFirstChild),
             (currentFirstChild = createFiberFromText(
               newChild,
               returnFiber.mode,
               expirationTime
-            ))),
-        (currentFirstChild["return"] = returnFiber),
-        (returnFiber = currentFirstChild),
+            )),
+            (currentFirstChild["return"] = returnFiber),
+            (returnFiber = currentFirstChild)),
         placeSingleChild(returnFiber)
       );
     if (isArray$1(newChild))
@@ -4768,7 +4777,7 @@ function ReactFiberScheduler(config) {
           ? isCommitting ? 1 : nextRenderExpirationTime
           : fiber.mode & 1
             ? isBatchingInteractiveUpdates
-              ? 10 * ((((recalculateCurrentTime() + 50) / 10) | 0) + 1)
+              ? 10 * ((((recalculateCurrentTime() + 15) / 10) | 0) + 1)
               : 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1)
             : 1;
     isBatchingInteractiveUpdates &&
@@ -5856,7 +5865,7 @@ ReactFabricRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
-  version: "16.3.1",
+  version: "16.3.2",
   rendererPackageName: "react-native-renderer"
 });
 var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
diff --git a/Libraries/Renderer/shims/ReactFeatureFlags.js b/Libraries/Renderer/fb/ReactFeatureFlags.js
similarity index 100%
rename from Libraries/Renderer/shims/ReactFeatureFlags.js
rename to Libraries/Renderer/fb/ReactFeatureFlags.js
diff --git a/Libraries/Renderer/ReactNativeRenderer-dev.js b/Libraries/Renderer/fb/ReactNativeRenderer-dev.js
similarity index 99%
rename from Libraries/Renderer/ReactNativeRenderer-dev.js
rename to Libraries/Renderer/fb/ReactNativeRenderer-dev.js
index 51e4aa2b0adc..bcdfa4c607aa 100644
--- a/Libraries/Renderer/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/fb/ReactNativeRenderer-dev.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactNativeRenderer-dev
  * @preventMunge
  */
 
@@ -2773,7 +2772,7 @@ function createPortal(
 
 // TODO: this is special because it gets imported during build.
 
-var ReactVersion = "16.3.1";
+var ReactVersion = "16.3.2";
 
 var describeComponentFrame = function(name, source, ownerName) {
   return (
@@ -2808,6 +2807,15 @@ function getComponentName(fiber) {
     case REACT_RETURN_TYPE:
       return "ReactReturn";
   }
+  if (typeof type === "object" && type !== null) {
+    switch (type.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        var functionName = type.render.displayName || type.render.name || "";
+        return functionName !== ""
+          ? "ForwardRef(" + functionName + ")"
+          : "ForwardRef";
+    }
+  }
   return null;
 }
 
@@ -5071,6 +5079,7 @@ var shouldIgnoreFiber = function(fiber) {
     case Fragment:
     case ContextProvider:
     case ContextConsumer:
+    case Mode:
       return true;
     default:
       return false;
@@ -12747,8 +12756,19 @@ var ReactFiberScheduler = function(config) {
   }
 
   function computeInteractiveExpiration(currentTime) {
-    // Should complete within ~500ms. 600ms max.
-    var expirationMs = 500;
+    var expirationMs = void 0;
+    // We intentionally set a higher expiration time for interactive updates in
+    // dev than in production.
+    // If the main thread is being blocked so long that you hit the expiration,
+    // it's a problem that could be solved with better scheduling.
+    // People will be more likely to notice this and fix it with the long
+    // expiration time in development.
+    // In production we opt for better UX at the risk of masking scheduling
+    // problems, by expiring fast.
+    {
+      // Should complete within ~500ms. 600ms max.
+      expirationMs = 500;
+    }
     var bucketSizeMs = 100;
     return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
   }
diff --git a/Libraries/Renderer/ReactNativeRenderer-prod.js b/Libraries/Renderer/fb/ReactNativeRenderer-prod.js
similarity index 99%
rename from Libraries/Renderer/ReactNativeRenderer-prod.js
rename to Libraries/Renderer/fb/ReactNativeRenderer-prod.js
index 10e7f6b5fc96..08b70c789b54 100644
--- a/Libraries/Renderer/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/fb/ReactNativeRenderer-prod.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactNativeRenderer-prod
  * @preventMunge
  */
 
@@ -1172,6 +1171,14 @@ function getComponentName(fiber) {
     case REACT_RETURN_TYPE:
       return "ReactReturn";
   }
+  if ("object" === typeof fiber && null !== fiber)
+    switch (fiber.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        return (
+          (fiber = fiber.render.displayName || fiber.render.name || ""),
+          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
+        );
+    }
   return null;
 }
 function getStackAddendumByWorkInProgressFiber(workInProgress) {
@@ -3009,15 +3016,17 @@ function ChildReconciler(shouldTrackSideEffects) {
               currentFirstChild,
               newChild,
               expirationTime
-            )))
+            )),
+            (currentFirstChild["return"] = returnFiber),
+            (returnFiber = currentFirstChild))
           : (deleteRemainingChildren(returnFiber, currentFirstChild),
             (currentFirstChild = createFiberFromText(
               newChild,
               returnFiber.mode,
               expirationTime
-            ))),
-        (currentFirstChild["return"] = returnFiber),
-        (returnFiber = currentFirstChild),
+            )),
+            (currentFirstChild["return"] = returnFiber),
+            (returnFiber = currentFirstChild)),
         placeSingleChild(returnFiber)
       );
     if (isArray$1(newChild))
@@ -5166,7 +5175,7 @@ function ReactFiberScheduler(config) {
           ? isCommitting ? 1 : nextRenderExpirationTime
           : fiber.mode & 1
             ? isBatchingInteractiveUpdates
-              ? 10 * ((((recalculateCurrentTime() + 50) / 10) | 0) + 1)
+              ? 10 * ((((recalculateCurrentTime() + 15) / 10) | 0) + 1)
               : 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1)
             : 1;
     isBatchingInteractiveUpdates &&
@@ -6375,7 +6384,7 @@ NativeRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
-  version: "16.3.1",
+  version: "16.3.2",
   rendererPackageName: "react-native-renderer"
 });
 var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
diff --git a/Libraries/Renderer/oss/ReactFabric-dev.js b/Libraries/Renderer/oss/ReactFabric-dev.js
new file mode 100644
index 000000000000..a24f4f6a50dd
--- /dev/null
+++ b/Libraries/Renderer/oss/ReactFabric-dev.js
@@ -0,0 +1,13863 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @noflow
+ * @providesModule ReactFabric-dev
+ * @preventMunge
+ */
+
+'use strict';
+
+if (__DEV__) {
+  (function() {
+"use strict";
+
+require("InitializeCore");
+var invariant = require("fbjs/lib/invariant");
+var warning = require("fbjs/lib/warning");
+var emptyFunction = require("fbjs/lib/emptyFunction");
+var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
+var UIManager = require("UIManager");
+var TextInputState = require("TextInputState");
+var deepDiffer = require("deepDiffer");
+var flattenStyle = require("flattenStyle");
+var React = require("react");
+var emptyObject = require("fbjs/lib/emptyObject");
+var shallowEqual = require("fbjs/lib/shallowEqual");
+var checkPropTypes = require("prop-types/checkPropTypes");
+var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
+var FabricUIManager = require("FabricUIManager");
+
+var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
+  this._hasCaughtError = false;
+  this._caughtError = null;
+  var funcArgs = Array.prototype.slice.call(arguments, 3);
+  try {
+    func.apply(context, funcArgs);
+  } catch (error) {
+    this._caughtError = error;
+    this._hasCaughtError = true;
+  }
+};
+
+{
+  // In DEV mode, we swap out invokeGuardedCallback for a special version
+  // that plays more nicely with the browser's DevTools. The idea is to preserve
+  // "Pause on exceptions" behavior. Because React wraps all user-provided
+  // functions in invokeGuardedCallback, and the production version of
+  // invokeGuardedCallback uses a try-catch, all user exceptions are treated
+  // like caught exceptions, and the DevTools won't pause unless the developer
+  // takes the extra step of enabling pause on caught exceptions. This is
+  // untintuitive, though, because even though React has caught the error, from
+  // the developer's perspective, the error is uncaught.
+  //
+  // To preserve the expected "Pause on exceptions" behavior, we don't use a
+  // try-catch in DEV. Instead, we synchronously dispatch a fake event to a fake
+  // DOM node, and call the user-provided callback from inside an event handler
+  // for that fake event. If the callback throws, the error is "captured" using
+  // a global event handler. But because the error happens in a different
+  // event loop context, it does not interrupt the normal program flow.
+  // Effectively, this gives us try-catch behavior without actually using
+  // try-catch. Neat!
+
+  // Check that the browser supports the APIs we need to implement our special
+  // DEV version of invokeGuardedCallback
+  if (
+    typeof window !== "undefined" &&
+    typeof window.dispatchEvent === "function" &&
+    typeof document !== "undefined" &&
+    typeof document.createEvent === "function"
+  ) {
+    var fakeNode = document.createElement("react");
+
+    var invokeGuardedCallbackDev = function(
+      name,
+      func,
+      context,
+      a,
+      b,
+      c,
+      d,
+      e,
+      f
+    ) {
+      // If document doesn't exist we know for sure we will crash in this method
+      // when we call document.createEvent(). However this can cause confusing
+      // errors: https://github.com/facebookincubator/create-react-app/issues/3482
+      // So we preemptively throw with a better message instead.
+      invariant(
+        typeof document !== "undefined",
+        "The `document` global was defined when React was initialized, but is not " +
+          "defined anymore. This can happen in a test environment if a component " +
+          "schedules an update from an asynchronous callback, but the test has already " +
+          "finished running. To solve this, you can either unmount the component at " +
+          "the end of your test (and ensure that any asynchronous operations get " +
+          "canceled in `componentWillUnmount`), or you can change the test itself " +
+          "to be asynchronous."
+      );
+      var evt = document.createEvent("Event");
+
+      // Keeps track of whether the user-provided callback threw an error. We
+      // set this to true at the beginning, then set it to false right after
+      // calling the function. If the function errors, `didError` will never be
+      // set to false. This strategy works even if the browser is flaky and
+      // fails to call our global error handler, because it doesn't rely on
+      // the error event at all.
+      var didError = true;
+
+      // Create an event handler for our fake event. We will synchronously
+      // dispatch our fake event using `dispatchEvent`. Inside the handler, we
+      // call the user-provided callback.
+      var funcArgs = Array.prototype.slice.call(arguments, 3);
+      function callCallback() {
+        // We immediately remove the callback from event listeners so that
+        // nested `invokeGuardedCallback` calls do not clash. Otherwise, a
+        // nested call would trigger the fake event handlers of any call higher
+        // in the stack.
+        fakeNode.removeEventListener(evtType, callCallback, false);
+        func.apply(context, funcArgs);
+        didError = false;
+      }
+
+      // Create a global error event handler. We use this to capture the value
+      // that was thrown. It's possible that this error handler will fire more
+      // than once; for example, if non-React code also calls `dispatchEvent`
+      // and a handler for that event throws. We should be resilient to most of
+      // those cases. Even if our error event handler fires more than once, the
+      // last error event is always used. If the callback actually does error,
+      // we know that the last error event is the correct one, because it's not
+      // possible for anything else to have happened in between our callback
+      // erroring and the code that follows the `dispatchEvent` call below. If
+      // the callback doesn't error, but the error event was fired, we know to
+      // ignore it because `didError` will be false, as described above.
+      var error = void 0;
+      // Use this to track whether the error event is ever called.
+      var didSetError = false;
+      var isCrossOriginError = false;
+
+      function onError(event) {
+        error = event.error;
+        didSetError = true;
+        if (error === null && event.colno === 0 && event.lineno === 0) {
+          isCrossOriginError = true;
+        }
+      }
+
+      // Create a fake event type.
+      var evtType = "react-" + (name ? name : "invokeguardedcallback");
+
+      // Attach our event handlers
+      window.addEventListener("error", onError);
+      fakeNode.addEventListener(evtType, callCallback, false);
+
+      // Synchronously dispatch our fake event. If the user-provided function
+      // errors, it will trigger our global error handler.
+      evt.initEvent(evtType, false, false);
+      fakeNode.dispatchEvent(evt);
+
+      if (didError) {
+        if (!didSetError) {
+          // The callback errored, but the error event never fired.
+          error = new Error(
+            "An error was thrown inside one of your components, but React " +
+              "doesn't know what it was. This is likely due to browser " +
+              'flakiness. React does its best to preserve the "Pause on ' +
+              'exceptions" behavior of the DevTools, which requires some ' +
+              "DEV-mode only tricks. It's possible that these don't work in " +
+              "your browser. Try triggering the error in production mode, " +
+              "or switching to a modern browser. If you suspect that this is " +
+              "actually an issue with React, please file an issue."
+          );
+        } else if (isCrossOriginError) {
+          error = new Error(
+            "A cross-origin error was thrown. React doesn't have access to " +
+              "the actual error object in development. " +
+              "See https://fb.me/react-crossorigin-error for more information."
+          );
+        }
+        this._hasCaughtError = true;
+        this._caughtError = error;
+      } else {
+        this._hasCaughtError = false;
+        this._caughtError = null;
+      }
+
+      // Remove our event listeners
+      window.removeEventListener("error", onError);
+    };
+
+    invokeGuardedCallback = invokeGuardedCallbackDev;
+  }
+}
+
+var invokeGuardedCallback$1 = invokeGuardedCallback;
+
+var ReactErrorUtils = {
+  // Used by Fiber to simulate a try-catch.
+  _caughtError: null,
+  _hasCaughtError: false,
+
+  // Used by event system to capture/rethrow the first error.
+  _rethrowError: null,
+  _hasRethrowError: false,
+
+  /**
+   * Call a function while guarding against errors that happens within it.
+   * Returns an error if it throws, otherwise null.
+   *
+   * In production, this is implemented using a try-catch. The reason we don't
+   * use a try-catch directly is so that we can swap out a different
+   * implementation in DEV mode.
+   *
+   * @param {String} name of the guard to use for logging or debugging
+   * @param {Function} func The function to invoke
+   * @param {*} context The context to use when calling the function
+   * @param {...*} args Arguments for function
+   */
+  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
+    invokeGuardedCallback$1.apply(ReactErrorUtils, arguments);
+  },
+
+  /**
+   * Same as invokeGuardedCallback, but instead of returning an error, it stores
+   * it in a global so it can be rethrown by `rethrowCaughtError` later.
+   * TODO: See if _caughtError and _rethrowError can be unified.
+   *
+   * @param {String} name of the guard to use for logging or debugging
+   * @param {Function} func The function to invoke
+   * @param {*} context The context to use when calling the function
+   * @param {...*} args Arguments for function
+   */
+  invokeGuardedCallbackAndCatchFirstError: function(
+    name,
+    func,
+    context,
+    a,
+    b,
+    c,
+    d,
+    e,
+    f
+  ) {
+    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
+    if (ReactErrorUtils.hasCaughtError()) {
+      var error = ReactErrorUtils.clearCaughtError();
+      if (!ReactErrorUtils._hasRethrowError) {
+        ReactErrorUtils._hasRethrowError = true;
+        ReactErrorUtils._rethrowError = error;
+      }
+    }
+  },
+
+  /**
+   * During execution of guarded functions we will capture the first error which
+   * we will rethrow to be handled by the top level error handler.
+   */
+  rethrowCaughtError: function() {
+    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
+  },
+
+  hasCaughtError: function() {
+    return ReactErrorUtils._hasCaughtError;
+  },
+
+  clearCaughtError: function() {
+    if (ReactErrorUtils._hasCaughtError) {
+      var error = ReactErrorUtils._caughtError;
+      ReactErrorUtils._caughtError = null;
+      ReactErrorUtils._hasCaughtError = false;
+      return error;
+    } else {
+      invariant(
+        false,
+        "clearCaughtError was called but no error was captured. This error " +
+          "is likely caused by a bug in React. Please file an issue."
+      );
+    }
+  }
+};
+
+var rethrowCaughtError = function() {
+  if (ReactErrorUtils._hasRethrowError) {
+    var error = ReactErrorUtils._rethrowError;
+    ReactErrorUtils._rethrowError = null;
+    ReactErrorUtils._hasRethrowError = false;
+    throw error;
+  }
+};
+
+/**
+ * Injectable ordering of event plugins.
+ */
+var eventPluginOrder = null;
+
+/**
+ * Injectable mapping from names to event plugin modules.
+ */
+var namesToPlugins = {};
+
+/**
+ * Recomputes the plugin list using the injected plugins and plugin ordering.
+ *
+ * @private
+ */
+function recomputePluginOrdering() {
+  if (!eventPluginOrder) {
+    // Wait until an `eventPluginOrder` is injected.
+    return;
+  }
+  for (var pluginName in namesToPlugins) {
+    var pluginModule = namesToPlugins[pluginName];
+    var pluginIndex = eventPluginOrder.indexOf(pluginName);
+    invariant(
+      pluginIndex > -1,
+      "EventPluginRegistry: Cannot inject event plugins that do not exist in " +
+        "the plugin ordering, `%s`.",
+      pluginName
+    );
+    if (plugins[pluginIndex]) {
+      continue;
+    }
+    invariant(
+      pluginModule.extractEvents,
+      "EventPluginRegistry: Event plugins must implement an `extractEvents` " +
+        "method, but `%s` does not.",
+      pluginName
+    );
+    plugins[pluginIndex] = pluginModule;
+    var publishedEvents = pluginModule.eventTypes;
+    for (var eventName in publishedEvents) {
+      invariant(
+        publishEventForPlugin(
+          publishedEvents[eventName],
+          pluginModule,
+          eventName
+        ),
+        "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
+        eventName,
+        pluginName
+      );
+    }
+  }
+}
+
+/**
+ * Publishes an event so that it can be dispatched by the supplied plugin.
+ *
+ * @param {object} dispatchConfig Dispatch configuration for the event.
+ * @param {object} PluginModule Plugin publishing the event.
+ * @return {boolean} True if the event was successfully published.
+ * @private
+ */
+function publishEventForPlugin(dispatchConfig, pluginModule, eventName) {
+  invariant(
+    !eventNameDispatchConfigs.hasOwnProperty(eventName),
+    "EventPluginHub: More than one plugin attempted to publish the same " +
+      "event name, `%s`.",
+    eventName
+  );
+  eventNameDispatchConfigs[eventName] = dispatchConfig;
+
+  var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
+  if (phasedRegistrationNames) {
+    for (var phaseName in phasedRegistrationNames) {
+      if (phasedRegistrationNames.hasOwnProperty(phaseName)) {
+        var phasedRegistrationName = phasedRegistrationNames[phaseName];
+        publishRegistrationName(
+          phasedRegistrationName,
+          pluginModule,
+          eventName
+        );
+      }
+    }
+    return true;
+  } else if (dispatchConfig.registrationName) {
+    publishRegistrationName(
+      dispatchConfig.registrationName,
+      pluginModule,
+      eventName
+    );
+    return true;
+  }
+  return false;
+}
+
+/**
+ * Publishes a registration name that is used to identify dispatched events.
+ *
+ * @param {string} registrationName Registration name to add.
+ * @param {object} PluginModule Plugin publishing the event.
+ * @private
+ */
+function publishRegistrationName(registrationName, pluginModule, eventName) {
+  invariant(
+    !registrationNameModules[registrationName],
+    "EventPluginHub: More than one plugin attempted to publish the same " +
+      "registration name, `%s`.",
+    registrationName
+  );
+  registrationNameModules[registrationName] = pluginModule;
+  registrationNameDependencies[registrationName] =
+    pluginModule.eventTypes[eventName].dependencies;
+
+  {
+    var lowerCasedName = registrationName.toLowerCase();
+  }
+}
+
+/**
+ * Registers plugins so that they can extract and dispatch events.
+ *
+ * @see {EventPluginHub}
+ */
+
+/**
+ * Ordered list of injected plugins.
+ */
+var plugins = [];
+
+/**
+ * Mapping from event name to dispatch config
+ */
+var eventNameDispatchConfigs = {};
+
+/**
+ * Mapping from registration name to plugin module
+ */
+var registrationNameModules = {};
+
+/**
+ * Mapping from registration name to event name
+ */
+var registrationNameDependencies = {};
+
+/**
+ * Mapping from lowercase registration names to the properly cased version,
+ * used to warn in the case of missing event handlers. Available
+ * only in true.
+ * @type {Object}
+ */
+
+// Trust the developer to only use possibleRegistrationNames in true
+
+/**
+ * Injects an ordering of plugins (by plugin name). This allows the ordering
+ * to be decoupled from injection of the actual plugins so that ordering is
+ * always deterministic regardless of packaging, on-the-fly injection, etc.
+ *
+ * @param {array} InjectedEventPluginOrder
+ * @internal
+ * @see {EventPluginHub.injection.injectEventPluginOrder}
+ */
+function injectEventPluginOrder(injectedEventPluginOrder) {
+  invariant(
+    !eventPluginOrder,
+    "EventPluginRegistry: Cannot inject event plugin ordering more than " +
+      "once. You are likely trying to load more than one copy of React."
+  );
+  // Clone the ordering so it cannot be dynamically mutated.
+  eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
+  recomputePluginOrdering();
+}
+
+/**
+ * Injects plugins to be used by `EventPluginHub`. The plugin names must be
+ * in the ordering injected by `injectEventPluginOrder`.
+ *
+ * Plugins can be injected as part of page initialization or on-the-fly.
+ *
+ * @param {object} injectedNamesToPlugins Map from names to plugin modules.
+ * @internal
+ * @see {EventPluginHub.injection.injectEventPluginsByName}
+ */
+function injectEventPluginsByName(injectedNamesToPlugins) {
+  var isOrderingDirty = false;
+  for (var pluginName in injectedNamesToPlugins) {
+    if (!injectedNamesToPlugins.hasOwnProperty(pluginName)) {
+      continue;
+    }
+    var pluginModule = injectedNamesToPlugins[pluginName];
+    if (
+      !namesToPlugins.hasOwnProperty(pluginName) ||
+      namesToPlugins[pluginName] !== pluginModule
+    ) {
+      invariant(
+        !namesToPlugins[pluginName],
+        "EventPluginRegistry: Cannot inject two different event plugins " +
+          "using the same name, `%s`.",
+        pluginName
+      );
+      namesToPlugins[pluginName] = pluginModule;
+      isOrderingDirty = true;
+    }
+  }
+  if (isOrderingDirty) {
+    recomputePluginOrdering();
+  }
+}
+
+var getFiberCurrentPropsFromNode = null;
+var getInstanceFromNode = null;
+var getNodeFromInstance = null;
+
+var injection$1 = {
+  injectComponentTree: function(Injected) {
+    getFiberCurrentPropsFromNode = Injected.getFiberCurrentPropsFromNode;
+    getInstanceFromNode = Injected.getInstanceFromNode;
+    getNodeFromInstance = Injected.getNodeFromInstance;
+
+    {
+      !(getNodeFromInstance && getInstanceFromNode)
+        ? warning(
+            false,
+            "EventPluginUtils.injection.injectComponentTree(...): Injected " +
+              "module is missing getNodeFromInstance or getInstanceFromNode."
+          )
+        : void 0;
+    }
+  }
+};
+
+function isEndish(topLevelType) {
+  return (
+    topLevelType === "topMouseUp" ||
+    topLevelType === "topTouchEnd" ||
+    topLevelType === "topTouchCancel"
+  );
+}
+
+function isMoveish(topLevelType) {
+  return topLevelType === "topMouseMove" || topLevelType === "topTouchMove";
+}
+function isStartish(topLevelType) {
+  return topLevelType === "topMouseDown" || topLevelType === "topTouchStart";
+}
+
+var validateEventDispatches = void 0;
+{
+  validateEventDispatches = function(event) {
+    var dispatchListeners = event._dispatchListeners;
+    var dispatchInstances = event._dispatchInstances;
+
+    var listenersIsArr = Array.isArray(dispatchListeners);
+    var listenersLen = listenersIsArr
+      ? dispatchListeners.length
+      : dispatchListeners ? 1 : 0;
+
+    var instancesIsArr = Array.isArray(dispatchInstances);
+    var instancesLen = instancesIsArr
+      ? dispatchInstances.length
+      : dispatchInstances ? 1 : 0;
+
+    !(instancesIsArr === listenersIsArr && instancesLen === listenersLen)
+      ? warning(false, "EventPluginUtils: Invalid `event`.")
+      : void 0;
+  };
+}
+
+/**
+ * Standard/simple iteration through an event's collected dispatches.
+ */
+
+/**
+ * Standard/simple iteration through an event's collected dispatches, but stops
+ * at the first dispatch execution returning true, and returns that id.
+ *
+ * @return {?string} id of the first dispatch execution who's listener returns
+ * true, or null if no listener returned true.
+ */
+function executeDispatchesInOrderStopAtTrueImpl(event) {
+  var dispatchListeners = event._dispatchListeners;
+  var dispatchInstances = event._dispatchInstances;
+  {
+    validateEventDispatches(event);
+  }
+  if (Array.isArray(dispatchListeners)) {
+    for (var i = 0; i < dispatchListeners.length; i++) {
+      if (event.isPropagationStopped()) {
+        break;
+      }
+      // Listeners and Instances are two parallel arrays that are always in sync.
+      if (dispatchListeners[i](event, dispatchInstances[i])) {
+        return dispatchInstances[i];
+      }
+    }
+  } else if (dispatchListeners) {
+    if (dispatchListeners(event, dispatchInstances)) {
+      return dispatchInstances;
+    }
+  }
+  return null;
+}
+
+/**
+ * @see executeDispatchesInOrderStopAtTrueImpl
+ */
+function executeDispatchesInOrderStopAtTrue(event) {
+  var ret = executeDispatchesInOrderStopAtTrueImpl(event);
+  event._dispatchInstances = null;
+  event._dispatchListeners = null;
+  return ret;
+}
+
+/**
+ * Execution of a "direct" dispatch - there must be at most one dispatch
+ * accumulated on the event or it is considered an error. It doesn't really make
+ * sense for an event with multiple dispatches (bubbled) to keep track of the
+ * return values at each dispatch execution, but it does tend to make sense when
+ * dealing with "direct" dispatches.
+ *
+ * @return {*} The return value of executing the single dispatch.
+ */
+function executeDirectDispatch(event) {
+  {
+    validateEventDispatches(event);
+  }
+  var dispatchListener = event._dispatchListeners;
+  var dispatchInstance = event._dispatchInstances;
+  invariant(
+    !Array.isArray(dispatchListener),
+    "executeDirectDispatch(...): Invalid `event`."
+  );
+  event.currentTarget = dispatchListener
+    ? getNodeFromInstance(dispatchInstance)
+    : null;
+  var res = dispatchListener ? dispatchListener(event) : null;
+  event.currentTarget = null;
+  event._dispatchListeners = null;
+  event._dispatchInstances = null;
+  return res;
+}
+
+/**
+ * @param {SyntheticEvent} event
+ * @return {boolean} True iff number of dispatches accumulated is greater than 0.
+ */
+function hasDispatches(event) {
+  return !!event._dispatchListeners;
+}
+
+/**
+ * Accumulates items that must not be null or undefined into the first one. This
+ * is used to conserve memory by avoiding array allocations, and thus sacrifices
+ * API cleanness. Since `current` can be null before being passed in and not
+ * null after this function, make sure to assign it back to `current`:
+ *
+ * `a = accumulateInto(a, b);`
+ *
+ * This API should be sparingly used. Try `accumulate` for something cleaner.
+ *
+ * @return {*|array<*>} An accumulation of items.
+ */
+
+function accumulateInto(current, next) {
+  invariant(
+    next != null,
+    "accumulateInto(...): Accumulated items must not be null or undefined."
+  );
+
+  if (current == null) {
+    return next;
+  }
+
+  // Both are not empty. Warning: Never call x.concat(y) when you are not
+  // certain that x is an Array (x could be a string with concat method).
+  if (Array.isArray(current)) {
+    if (Array.isArray(next)) {
+      current.push.apply(current, next);
+      return current;
+    }
+    current.push(next);
+    return current;
+  }
+
+  if (Array.isArray(next)) {
+    // A bit too dangerous to mutate `next`.
+    return [current].concat(next);
+  }
+
+  return [current, next];
+}
+
+/**
+ * @param {array} arr an "accumulation" of items which is either an Array or
+ * a single item. Useful when paired with the `accumulate` module. This is a
+ * simple utility that allows us to reason about a collection of items, but
+ * handling the case when there is exactly one item (and we do not need to
+ * allocate an array).
+ * @param {function} cb Callback invoked with each element or a collection.
+ * @param {?} [scope] Scope used as `this` in a callback.
+ */
+function forEachAccumulated(arr, cb, scope) {
+  if (Array.isArray(arr)) {
+    arr.forEach(cb, scope);
+  } else if (arr) {
+    cb.call(scope, arr);
+  }
+}
+
+function isInteractive(tag) {
+  return (
+    tag === "button" ||
+    tag === "input" ||
+    tag === "select" ||
+    tag === "textarea"
+  );
+}
+
+function shouldPreventMouseEvent(name, type, props) {
+  switch (name) {
+    case "onClick":
+    case "onClickCapture":
+    case "onDoubleClick":
+    case "onDoubleClickCapture":
+    case "onMouseDown":
+    case "onMouseDownCapture":
+    case "onMouseMove":
+    case "onMouseMoveCapture":
+    case "onMouseUp":
+    case "onMouseUpCapture":
+      return !!(props.disabled && isInteractive(type));
+    default:
+      return false;
+  }
+}
+
+/**
+ * This is a unified interface for event plugins to be installed and configured.
+ *
+ * Event plugins can implement the following properties:
+ *
+ *   `extractEvents` {function(string, DOMEventTarget, string, object): *}
+ *     Required. When a top-level event is fired, this method is expected to
+ *     extract synthetic events that will in turn be queued and dispatched.
+ *
+ *   `eventTypes` {object}
+ *     Optional, plugins that fire events must publish a mapping of registration
+ *     names that are used to register listeners. Values of this mapping must
+ *     be objects that contain `registrationName` or `phasedRegistrationNames`.
+ *
+ *   `executeDispatch` {function(object, function, string)}
+ *     Optional, allows plugins to override how an event gets dispatched. By
+ *     default, the listener is simply invoked.
+ *
+ * Each plugin that is injected into `EventsPluginHub` is immediately operable.
+ *
+ * @public
+ */
+
+/**
+ * Methods for injecting dependencies.
+ */
+var injection = {
+  /**
+   * @param {array} InjectedEventPluginOrder
+   * @public
+   */
+  injectEventPluginOrder: injectEventPluginOrder,
+
+  /**
+   * @param {object} injectedNamesToPlugins Map from names to plugin modules.
+   */
+  injectEventPluginsByName: injectEventPluginsByName
+};
+
+/**
+ * @param {object} inst The instance, which is the source of events.
+ * @param {string} registrationName Name of listener (e.g. `onClick`).
+ * @return {?function} The stored callback.
+ */
+function getListener(inst, registrationName) {
+  var listener = void 0;
+
+  // TODO: shouldPreventMouseEvent is DOM-specific and definitely should not
+  // live here; needs to be moved to a better place soon
+  var stateNode = inst.stateNode;
+  if (!stateNode) {
+    // Work in progress (ex: onload events in incremental mode).
+    return null;
+  }
+  var props = getFiberCurrentPropsFromNode(stateNode);
+  if (!props) {
+    // Work in progress.
+    return null;
+  }
+  listener = props[registrationName];
+  if (shouldPreventMouseEvent(registrationName, inst.type, props)) {
+    return null;
+  }
+  invariant(
+    !listener || typeof listener === "function",
+    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
+    registrationName,
+    typeof listener
+  );
+  return listener;
+}
+
+var IndeterminateComponent = 0; // Before we know whether it is functional or class
+var FunctionalComponent = 1;
+var ClassComponent = 2;
+var HostRoot = 3; // Root of a host tree. Could be nested inside another node.
+var HostPortal = 4; // A subtree. Could be an entry point to a different renderer.
+var HostComponent = 5;
+var HostText = 6;
+var CallComponent = 7;
+var CallHandlerPhase = 8;
+var ReturnComponent = 9;
+var Fragment = 10;
+var Mode = 11;
+var ContextConsumer = 12;
+var ContextProvider = 13;
+var ForwardRef = 14;
+
+function getParent(inst) {
+  do {
+    inst = inst["return"];
+    // TODO: If this is a HostRoot we might want to bail out.
+    // That is depending on if we want nested subtrees (layers) to bubble
+    // events to their parent. We could also go through parentNode on the
+    // host node but that wouldn't work for React Native and doesn't let us
+    // do the portal feature.
+  } while (inst && inst.tag !== HostComponent);
+  if (inst) {
+    return inst;
+  }
+  return null;
+}
+
+/**
+ * Return the lowest common ancestor of A and B, or null if they are in
+ * different trees.
+ */
+function getLowestCommonAncestor(instA, instB) {
+  var depthA = 0;
+  for (var tempA = instA; tempA; tempA = getParent(tempA)) {
+    depthA++;
+  }
+  var depthB = 0;
+  for (var tempB = instB; tempB; tempB = getParent(tempB)) {
+    depthB++;
+  }
+
+  // If A is deeper, crawl up.
+  while (depthA - depthB > 0) {
+    instA = getParent(instA);
+    depthA--;
+  }
+
+  // If B is deeper, crawl up.
+  while (depthB - depthA > 0) {
+    instB = getParent(instB);
+    depthB--;
+  }
+
+  // Walk in lockstep until we find a match.
+  var depth = depthA;
+  while (depth--) {
+    if (instA === instB || instA === instB.alternate) {
+      return instA;
+    }
+    instA = getParent(instA);
+    instB = getParent(instB);
+  }
+  return null;
+}
+
+/**
+ * Return if A is an ancestor of B.
+ */
+function isAncestor(instA, instB) {
+  while (instB) {
+    if (instA === instB || instA === instB.alternate) {
+      return true;
+    }
+    instB = getParent(instB);
+  }
+  return false;
+}
+
+/**
+ * Return the parent instance of the passed-in instance.
+ */
+function getParentInstance(inst) {
+  return getParent(inst);
+}
+
+/**
+ * Simulates the traversal of a two-phase, capture/bubble event dispatch.
+ */
+function traverseTwoPhase(inst, fn, arg) {
+  var path = [];
+  while (inst) {
+    path.push(inst);
+    inst = getParent(inst);
+  }
+  var i = void 0;
+  for (i = path.length; i-- > 0; ) {
+    fn(path[i], "captured", arg);
+  }
+  for (i = 0; i < path.length; i++) {
+    fn(path[i], "bubbled", arg);
+  }
+}
+
+/**
+ * Traverses the ID hierarchy and invokes the supplied `cb` on any IDs that
+ * should would receive a `mouseEnter` or `mouseLeave` event.
+ *
+ * Does not invoke the callback on the nearest common ancestor because nothing
+ * "entered" or "left" that element.
+ */
+
+/**
+ * Some event types have a notion of different registration names for different
+ * "phases" of propagation. This finds listeners by a given phase.
+ */
+function listenerAtPhase(inst, event, propagationPhase) {
+  var registrationName =
+    event.dispatchConfig.phasedRegistrationNames[propagationPhase];
+  return getListener(inst, registrationName);
+}
+
+/**
+ * A small set of propagation patterns, each of which will accept a small amount
+ * of information, and generate a set of "dispatch ready event objects" - which
+ * are sets of events that have already been annotated with a set of dispatched
+ * listener functions/ids. The API is designed this way to discourage these
+ * propagation strategies from actually executing the dispatches, since we
+ * always want to collect the entire set of dispatches before executing even a
+ * single one.
+ */
+
+/**
+ * Tags a `SyntheticEvent` with dispatched listeners. Creating this function
+ * here, allows us to not have to bind or create functions for each event.
+ * Mutating the event's members allows us to not have to create a wrapping
+ * "dispatch" object that pairs the event with the listener.
+ */
+function accumulateDirectionalDispatches(inst, phase, event) {
+  {
+    !inst ? warning(false, "Dispatching inst must not be null") : void 0;
+  }
+  var listener = listenerAtPhase(inst, event, phase);
+  if (listener) {
+    event._dispatchListeners = accumulateInto(
+      event._dispatchListeners,
+      listener
+    );
+    event._dispatchInstances = accumulateInto(event._dispatchInstances, inst);
+  }
+}
+
+/**
+ * Collect dispatches (must be entirely collected before dispatching - see unit
+ * tests). Lazily allocate the array to conserve memory.  We must loop through
+ * each event and perform the traversal for each one. We cannot perform a
+ * single traversal for the entire collection of events because each event may
+ * have a different target.
+ */
+function accumulateTwoPhaseDispatchesSingle(event) {
+  if (event && event.dispatchConfig.phasedRegistrationNames) {
+    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
+  }
+}
+
+/**
+ * Same as `accumulateTwoPhaseDispatchesSingle`, but skips over the targetID.
+ */
+function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
+  if (event && event.dispatchConfig.phasedRegistrationNames) {
+    var targetInst = event._targetInst;
+    var parentInst = targetInst ? getParentInstance(targetInst) : null;
+    traverseTwoPhase(parentInst, accumulateDirectionalDispatches, event);
+  }
+}
+
+/**
+ * Accumulates without regard to direction, does not look for phased
+ * registration names. Same as `accumulateDirectDispatchesSingle` but without
+ * requiring that the `dispatchMarker` be the same as the dispatched ID.
+ */
+function accumulateDispatches(inst, ignoredDirection, event) {
+  if (inst && event && event.dispatchConfig.registrationName) {
+    var registrationName = event.dispatchConfig.registrationName;
+    var listener = getListener(inst, registrationName);
+    if (listener) {
+      event._dispatchListeners = accumulateInto(
+        event._dispatchListeners,
+        listener
+      );
+      event._dispatchInstances = accumulateInto(event._dispatchInstances, inst);
+    }
+  }
+}
+
+/**
+ * Accumulates dispatches on an `SyntheticEvent`, but only for the
+ * `dispatchMarker`.
+ * @param {SyntheticEvent} event
+ */
+function accumulateDirectDispatchesSingle(event) {
+  if (event && event.dispatchConfig.registrationName) {
+    accumulateDispatches(event._targetInst, null, event);
+  }
+}
+
+function accumulateTwoPhaseDispatches(events) {
+  forEachAccumulated(events, accumulateTwoPhaseDispatchesSingle);
+}
+
+function accumulateTwoPhaseDispatchesSkipTarget(events) {
+  forEachAccumulated(events, accumulateTwoPhaseDispatchesSingleSkipTarget);
+}
+
+function accumulateDirectDispatches(events) {
+  forEachAccumulated(events, accumulateDirectDispatchesSingle);
+}
+
+/* eslint valid-typeof: 0 */
+
+var didWarnForAddedNewProperty = false;
+var EVENT_POOL_SIZE = 10;
+
+var shouldBeReleasedProperties = [
+  "dispatchConfig",
+  "_targetInst",
+  "nativeEvent",
+  "isDefaultPrevented",
+  "isPropagationStopped",
+  "_dispatchListeners",
+  "_dispatchInstances"
+];
+
+/**
+ * @interface Event
+ * @see http://www.w3.org/TR/DOM-Level-3-Events/
+ */
+var EventInterface = {
+  type: null,
+  target: null,
+  // currentTarget is set when dispatching; no use in copying it here
+  currentTarget: emptyFunction.thatReturnsNull,
+  eventPhase: null,
+  bubbles: null,
+  cancelable: null,
+  timeStamp: function(event) {
+    return event.timeStamp || Date.now();
+  },
+  defaultPrevented: null,
+  isTrusted: null
+};
+
+/**
+ * Synthetic events are dispatched by event plugins, typically in response to a
+ * top-level event delegation handler.
+ *
+ * These systems should generally use pooling to reduce the frequency of garbage
+ * collection. The system should check `isPersistent` to determine whether the
+ * event should be released into the pool after being dispatched. Users that
+ * need a persisted event should invoke `persist`.
+ *
+ * Synthetic events (and subclasses) implement the DOM Level 3 Events API by
+ * normalizing browser quirks. Subclasses do not necessarily have to implement a
+ * DOM interface; custom application-specific events can also subclass this.
+ *
+ * @param {object} dispatchConfig Configuration used to dispatch this event.
+ * @param {*} targetInst Marker identifying the event target.
+ * @param {object} nativeEvent Native browser event.
+ * @param {DOMEventTarget} nativeEventTarget Target node.
+ */
+function SyntheticEvent(
+  dispatchConfig,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  {
+    // these have a getter/setter for warnings
+    delete this.nativeEvent;
+    delete this.preventDefault;
+    delete this.stopPropagation;
+  }
+
+  this.dispatchConfig = dispatchConfig;
+  this._targetInst = targetInst;
+  this.nativeEvent = nativeEvent;
+
+  var Interface = this.constructor.Interface;
+  for (var propName in Interface) {
+    if (!Interface.hasOwnProperty(propName)) {
+      continue;
+    }
+    {
+      delete this[propName]; // this has a getter/setter for warnings
+    }
+    var normalize = Interface[propName];
+    if (normalize) {
+      this[propName] = normalize(nativeEvent);
+    } else {
+      if (propName === "target") {
+        this.target = nativeEventTarget;
+      } else {
+        this[propName] = nativeEvent[propName];
+      }
+    }
+  }
+
+  var defaultPrevented =
+    nativeEvent.defaultPrevented != null
+      ? nativeEvent.defaultPrevented
+      : nativeEvent.returnValue === false;
+  if (defaultPrevented) {
+    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
+  } else {
+    this.isDefaultPrevented = emptyFunction.thatReturnsFalse;
+  }
+  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
+  return this;
+}
+
+Object.assign(SyntheticEvent.prototype, {
+  preventDefault: function() {
+    this.defaultPrevented = true;
+    var event = this.nativeEvent;
+    if (!event) {
+      return;
+    }
+
+    if (event.preventDefault) {
+      event.preventDefault();
+    } else if (typeof event.returnValue !== "unknown") {
+      event.returnValue = false;
+    }
+    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
+  },
+
+  stopPropagation: function() {
+    var event = this.nativeEvent;
+    if (!event) {
+      return;
+    }
+
+    if (event.stopPropagation) {
+      event.stopPropagation();
+    } else if (typeof event.cancelBubble !== "unknown") {
+      // The ChangeEventPlugin registers a "propertychange" event for
+      // IE. This event does not support bubbling or cancelling, and
+      // any references to cancelBubble throw "Member not found".  A
+      // typeof check of "unknown" circumvents this issue (and is also
+      // IE specific).
+      event.cancelBubble = true;
+    }
+
+    this.isPropagationStopped = emptyFunction.thatReturnsTrue;
+  },
+
+  /**
+   * We release all dispatched `SyntheticEvent`s after each event loop, adding
+   * them back into the pool. This allows a way to hold onto a reference that
+   * won't be added back into the pool.
+   */
+  persist: function() {
+    this.isPersistent = emptyFunction.thatReturnsTrue;
+  },
+
+  /**
+   * Checks if this event should be released back into the pool.
+   *
+   * @return {boolean} True if this should not be released, false otherwise.
+   */
+  isPersistent: emptyFunction.thatReturnsFalse,
+
+  /**
+   * `PooledClass` looks for `destructor` on each instance it releases.
+   */
+  destructor: function() {
+    var Interface = this.constructor.Interface;
+    for (var propName in Interface) {
+      {
+        Object.defineProperty(
+          this,
+          propName,
+          getPooledWarningPropertyDefinition(propName, Interface[propName])
+        );
+      }
+    }
+    for (var i = 0; i < shouldBeReleasedProperties.length; i++) {
+      this[shouldBeReleasedProperties[i]] = null;
+    }
+    {
+      Object.defineProperty(
+        this,
+        "nativeEvent",
+        getPooledWarningPropertyDefinition("nativeEvent", null)
+      );
+      Object.defineProperty(
+        this,
+        "preventDefault",
+        getPooledWarningPropertyDefinition("preventDefault", emptyFunction)
+      );
+      Object.defineProperty(
+        this,
+        "stopPropagation",
+        getPooledWarningPropertyDefinition("stopPropagation", emptyFunction)
+      );
+    }
+  }
+});
+
+SyntheticEvent.Interface = EventInterface;
+
+/**
+ * Helper to reduce boilerplate when creating subclasses.
+ */
+SyntheticEvent.extend = function(Interface) {
+  var Super = this;
+
+  var E = function() {};
+  E.prototype = Super.prototype;
+  var prototype = new E();
+
+  function Class() {
+    return Super.apply(this, arguments);
+  }
+  Object.assign(prototype, Class.prototype);
+  Class.prototype = prototype;
+  Class.prototype.constructor = Class;
+
+  Class.Interface = Object.assign({}, Super.Interface, Interface);
+  Class.extend = Super.extend;
+  addEventPoolingTo(Class);
+
+  return Class;
+};
+
+/** Proxying after everything set on SyntheticEvent
+ * to resolve Proxy issue on some WebKit browsers
+ * in which some Event properties are set to undefined (GH#10010)
+ */
+{
+  var isProxySupported =
+    typeof Proxy === "function" &&
+    // https://github.com/facebook/react/issues/12011
+    !Object.isSealed(new Proxy({}, {}));
+
+  if (isProxySupported) {
+    /*eslint-disable no-func-assign */
+    SyntheticEvent = new Proxy(SyntheticEvent, {
+      construct: function(target, args) {
+        return this.apply(target, Object.create(target.prototype), args);
+      },
+      apply: function(constructor, that, args) {
+        return new Proxy(constructor.apply(that, args), {
+          set: function(target, prop, value) {
+            if (
+              prop !== "isPersistent" &&
+              !target.constructor.Interface.hasOwnProperty(prop) &&
+              shouldBeReleasedProperties.indexOf(prop) === -1
+            ) {
+              !(didWarnForAddedNewProperty || target.isPersistent())
+                ? warning(
+                    false,
+                    "This synthetic event is reused for performance reasons. If you're " +
+                      "seeing this, you're adding a new property in the synthetic event object. " +
+                      "The property is never released. See " +
+                      "https://fb.me/react-event-pooling for more information."
+                  )
+                : void 0;
+              didWarnForAddedNewProperty = true;
+            }
+            target[prop] = value;
+            return true;
+          }
+        });
+      }
+    });
+    /*eslint-enable no-func-assign */
+  }
+}
+
+addEventPoolingTo(SyntheticEvent);
+
+/**
+ * Helper to nullify syntheticEvent instance properties when destructing
+ *
+ * @param {String} propName
+ * @param {?object} getVal
+ * @return {object} defineProperty object
+ */
+function getPooledWarningPropertyDefinition(propName, getVal) {
+  var isFunction = typeof getVal === "function";
+  return {
+    configurable: true,
+    set: set,
+    get: get$$1
+  };
+
+  function set(val) {
+    var action = isFunction ? "setting the method" : "setting the property";
+    warn(action, "This is effectively a no-op");
+    return val;
+  }
+
+  function get$$1() {
+    var action = isFunction ? "accessing the method" : "accessing the property";
+    var result = isFunction
+      ? "This is a no-op function"
+      : "This is set to null";
+    warn(action, result);
+    return getVal;
+  }
+
+  function warn(action, result) {
+    var warningCondition = false;
+    !warningCondition
+      ? warning(
+          false,
+          "This synthetic event is reused for performance reasons. If you're seeing this, " +
+            "you're %s `%s` on a released/nullified synthetic event. %s. " +
+            "If you must keep the original synthetic event around, use event.persist(). " +
+            "See https://fb.me/react-event-pooling for more information.",
+          action,
+          propName,
+          result
+        )
+      : void 0;
+  }
+}
+
+function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
+  var EventConstructor = this;
+  if (EventConstructor.eventPool.length) {
+    var instance = EventConstructor.eventPool.pop();
+    EventConstructor.call(
+      instance,
+      dispatchConfig,
+      targetInst,
+      nativeEvent,
+      nativeInst
+    );
+    return instance;
+  }
+  return new EventConstructor(
+    dispatchConfig,
+    targetInst,
+    nativeEvent,
+    nativeInst
+  );
+}
+
+function releasePooledEvent(event) {
+  var EventConstructor = this;
+  invariant(
+    event instanceof EventConstructor,
+    "Trying to release an event instance  into a pool of a different type."
+  );
+  event.destructor();
+  if (EventConstructor.eventPool.length < EVENT_POOL_SIZE) {
+    EventConstructor.eventPool.push(event);
+  }
+}
+
+function addEventPoolingTo(EventConstructor) {
+  EventConstructor.eventPool = [];
+  EventConstructor.getPooled = getPooledEvent;
+  EventConstructor.release = releasePooledEvent;
+}
+
+var SyntheticEvent$1 = SyntheticEvent;
+
+/**
+ * `touchHistory` isn't actually on the native event, but putting it in the
+ * interface will ensure that it is cleaned up when pooled/destroyed. The
+ * `ResponderEventPlugin` will populate it appropriately.
+ */
+var ResponderSyntheticEvent = SyntheticEvent$1.extend({
+  touchHistory: function(nativeEvent) {
+    return null; // Actually doesn't even look at the native event.
+  }
+});
+
+/**
+ * Tracks the position and time of each active touch by `touch.identifier`. We
+ * should typically only see IDs in the range of 1-20 because IDs get recycled
+ * when touches end and start again.
+ */
+
+var MAX_TOUCH_BANK = 20;
+var touchBank = [];
+var touchHistory = {
+  touchBank: touchBank,
+  numberActiveTouches: 0,
+  // If there is only one active touch, we remember its location. This prevents
+  // us having to loop through all of the touches all the time in the most
+  // common case.
+  indexOfSingleActiveTouch: -1,
+  mostRecentTimeStamp: 0
+};
+
+function timestampForTouch(touch) {
+  // The legacy internal implementation provides "timeStamp", which has been
+  // renamed to "timestamp". Let both work for now while we iron it out
+  // TODO (evv): rename timeStamp to timestamp in internal code
+  return touch.timeStamp || touch.timestamp;
+}
+
+/**
+ * TODO: Instead of making gestures recompute filtered velocity, we could
+ * include a built in velocity computation that can be reused globally.
+ */
+function createTouchRecord(touch) {
+  return {
+    touchActive: true,
+    startPageX: touch.pageX,
+    startPageY: touch.pageY,
+    startTimeStamp: timestampForTouch(touch),
+    currentPageX: touch.pageX,
+    currentPageY: touch.pageY,
+    currentTimeStamp: timestampForTouch(touch),
+    previousPageX: touch.pageX,
+    previousPageY: touch.pageY,
+    previousTimeStamp: timestampForTouch(touch)
+  };
+}
+
+function resetTouchRecord(touchRecord, touch) {
+  touchRecord.touchActive = true;
+  touchRecord.startPageX = touch.pageX;
+  touchRecord.startPageY = touch.pageY;
+  touchRecord.startTimeStamp = timestampForTouch(touch);
+  touchRecord.currentPageX = touch.pageX;
+  touchRecord.currentPageY = touch.pageY;
+  touchRecord.currentTimeStamp = timestampForTouch(touch);
+  touchRecord.previousPageX = touch.pageX;
+  touchRecord.previousPageY = touch.pageY;
+  touchRecord.previousTimeStamp = timestampForTouch(touch);
+}
+
+function getTouchIdentifier(_ref) {
+  var identifier = _ref.identifier;
+
+  invariant(identifier != null, "Touch object is missing identifier.");
+  {
+    !(identifier <= MAX_TOUCH_BANK)
+      ? warning(
+          false,
+          "Touch identifier %s is greater than maximum supported %s which causes " +
+            "performance issues backfilling array locations for all of the indices.",
+          identifier,
+          MAX_TOUCH_BANK
+        )
+      : void 0;
+  }
+  return identifier;
+}
+
+function recordTouchStart(touch) {
+  var identifier = getTouchIdentifier(touch);
+  var touchRecord = touchBank[identifier];
+  if (touchRecord) {
+    resetTouchRecord(touchRecord, touch);
+  } else {
+    touchBank[identifier] = createTouchRecord(touch);
+  }
+  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+}
+
+function recordTouchMove(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  if (touchRecord) {
+    touchRecord.touchActive = true;
+    touchRecord.previousPageX = touchRecord.currentPageX;
+    touchRecord.previousPageY = touchRecord.currentPageY;
+    touchRecord.previousTimeStamp = touchRecord.currentTimeStamp;
+    touchRecord.currentPageX = touch.pageX;
+    touchRecord.currentPageY = touch.pageY;
+    touchRecord.currentTimeStamp = timestampForTouch(touch);
+    touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+  } else {
+    console.error(
+      "Cannot record touch move without a touch start.\n" + "Touch Move: %s\n",
+      "Touch Bank: %s",
+      printTouch(touch),
+      printTouchBank()
+    );
+  }
+}
+
+function recordTouchEnd(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  if (touchRecord) {
+    touchRecord.touchActive = false;
+    touchRecord.previousPageX = touchRecord.currentPageX;
+    touchRecord.previousPageY = touchRecord.currentPageY;
+    touchRecord.previousTimeStamp = touchRecord.currentTimeStamp;
+    touchRecord.currentPageX = touch.pageX;
+    touchRecord.currentPageY = touch.pageY;
+    touchRecord.currentTimeStamp = timestampForTouch(touch);
+    touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+  } else {
+    console.error(
+      "Cannot record touch end without a touch start.\n" + "Touch End: %s\n",
+      "Touch Bank: %s",
+      printTouch(touch),
+      printTouchBank()
+    );
+  }
+}
+
+function printTouch(touch) {
+  return JSON.stringify({
+    identifier: touch.identifier,
+    pageX: touch.pageX,
+    pageY: touch.pageY,
+    timestamp: timestampForTouch(touch)
+  });
+}
+
+function printTouchBank() {
+  var printed = JSON.stringify(touchBank.slice(0, MAX_TOUCH_BANK));
+  if (touchBank.length > MAX_TOUCH_BANK) {
+    printed += " (original size: " + touchBank.length + ")";
+  }
+  return printed;
+}
+
+var ResponderTouchHistoryStore = {
+  recordTouchTrack: function(topLevelType, nativeEvent) {
+    if (isMoveish(topLevelType)) {
+      nativeEvent.changedTouches.forEach(recordTouchMove);
+    } else if (isStartish(topLevelType)) {
+      nativeEvent.changedTouches.forEach(recordTouchStart);
+      touchHistory.numberActiveTouches = nativeEvent.touches.length;
+      if (touchHistory.numberActiveTouches === 1) {
+        touchHistory.indexOfSingleActiveTouch =
+          nativeEvent.touches[0].identifier;
+      }
+    } else if (isEndish(topLevelType)) {
+      nativeEvent.changedTouches.forEach(recordTouchEnd);
+      touchHistory.numberActiveTouches = nativeEvent.touches.length;
+      if (touchHistory.numberActiveTouches === 1) {
+        for (var i = 0; i < touchBank.length; i++) {
+          var touchTrackToCheck = touchBank[i];
+          if (touchTrackToCheck != null && touchTrackToCheck.touchActive) {
+            touchHistory.indexOfSingleActiveTouch = i;
+            break;
+          }
+        }
+        {
+          var activeRecord = touchBank[touchHistory.indexOfSingleActiveTouch];
+          !(activeRecord != null && activeRecord.touchActive)
+            ? warning(false, "Cannot find single active touch.")
+            : void 0;
+        }
+      }
+    }
+  },
+
+  touchHistory: touchHistory
+};
+
+/**
+ * Accumulates items that must not be null or undefined.
+ *
+ * This is used to conserve memory by avoiding array allocations.
+ *
+ * @return {*|array<*>} An accumulation of items.
+ */
+function accumulate(current, next) {
+  invariant(
+    next != null,
+    "accumulate(...): Accumulated items must be not be null or undefined."
+  );
+
+  if (current == null) {
+    return next;
+  }
+
+  // Both are not empty. Warning: Never call x.concat(y) when you are not
+  // certain that x is an Array (x could be a string with concat method).
+  if (Array.isArray(current)) {
+    return current.concat(next);
+  }
+
+  if (Array.isArray(next)) {
+    return [current].concat(next);
+  }
+
+  return [current, next];
+}
+
+/**
+ * Instance of element that should respond to touch/move types of interactions,
+ * as indicated explicitly by relevant callbacks.
+ */
+var responderInst = null;
+
+/**
+ * Count of current touches. A textInput should become responder iff the
+ * selection changes while there is a touch on the screen.
+ */
+var trackedTouchCount = 0;
+
+/**
+ * Last reported number of active touches.
+ */
+var previousActiveTouches = 0;
+
+var changeResponder = function(nextResponderInst, blockHostResponder) {
+  var oldResponderInst = responderInst;
+  responderInst = nextResponderInst;
+  if (ResponderEventPlugin.GlobalResponderHandler !== null) {
+    ResponderEventPlugin.GlobalResponderHandler.onChange(
+      oldResponderInst,
+      nextResponderInst,
+      blockHostResponder
+    );
+  }
+};
+
+var eventTypes$1 = {
+  /**
+   * On a `touchStart`/`mouseDown`, is it desired that this element become the
+   * responder?
+   */
+  startShouldSetResponder: {
+    phasedRegistrationNames: {
+      bubbled: "onStartShouldSetResponder",
+      captured: "onStartShouldSetResponderCapture"
+    }
+  },
+
+  /**
+   * On a `scroll`, is it desired that this element become the responder? This
+   * is usually not needed, but should be used to retroactively infer that a
+   * `touchStart` had occurred during momentum scroll. During a momentum scroll,
+   * a touch start will be immediately followed by a scroll event if the view is
+   * currently scrolling.
+   *
+   * TODO: This shouldn't bubble.
+   */
+  scrollShouldSetResponder: {
+    phasedRegistrationNames: {
+      bubbled: "onScrollShouldSetResponder",
+      captured: "onScrollShouldSetResponderCapture"
+    }
+  },
+
+  /**
+   * On text selection change, should this element become the responder? This
+   * is needed for text inputs or other views with native selection, so the
+   * JS view can claim the responder.
+   *
+   * TODO: This shouldn't bubble.
+   */
+  selectionChangeShouldSetResponder: {
+    phasedRegistrationNames: {
+      bubbled: "onSelectionChangeShouldSetResponder",
+      captured: "onSelectionChangeShouldSetResponderCapture"
+    }
+  },
+
+  /**
+   * On a `touchMove`/`mouseMove`, is it desired that this element become the
+   * responder?
+   */
+  moveShouldSetResponder: {
+    phasedRegistrationNames: {
+      bubbled: "onMoveShouldSetResponder",
+      captured: "onMoveShouldSetResponderCapture"
+    }
+  },
+
+  /**
+   * Direct responder events dispatched directly to responder. Do not bubble.
+   */
+  responderStart: { registrationName: "onResponderStart" },
+  responderMove: { registrationName: "onResponderMove" },
+  responderEnd: { registrationName: "onResponderEnd" },
+  responderRelease: { registrationName: "onResponderRelease" },
+  responderTerminationRequest: {
+    registrationName: "onResponderTerminationRequest"
+  },
+  responderGrant: { registrationName: "onResponderGrant" },
+  responderReject: { registrationName: "onResponderReject" },
+  responderTerminate: { registrationName: "onResponderTerminate" }
+};
+
+/**
+ *
+ * Responder System:
+ * ----------------
+ *
+ * - A global, solitary "interaction lock" on a view.
+ * - If a node becomes the responder, it should convey visual feedback
+ *   immediately to indicate so, either by highlighting or moving accordingly.
+ * - To be the responder means, that touches are exclusively important to that
+ *   responder view, and no other view.
+ * - While touches are still occurring, the responder lock can be transferred to
+ *   a new view, but only to increasingly "higher" views (meaning ancestors of
+ *   the current responder).
+ *
+ * Responder being granted:
+ * ------------------------
+ *
+ * - Touch starts, moves, and scrolls can cause an ID to become the responder.
+ * - We capture/bubble `startShouldSetResponder`/`moveShouldSetResponder` to
+ *   the "appropriate place".
+ * - If nothing is currently the responder, the "appropriate place" is the
+ *   initiating event's `targetID`.
+ * - If something *is* already the responder, the "appropriate place" is the
+ *   first common ancestor of the event target and the current `responderInst`.
+ * - Some negotiation happens: See the timing diagram below.
+ * - Scrolled views automatically become responder. The reasoning is that a
+ *   platform scroll view that isn't built on top of the responder system has
+ *   began scrolling, and the active responder must now be notified that the
+ *   interaction is no longer locked to it - the system has taken over.
+ *
+ * - Responder being released:
+ *   As soon as no more touches that *started* inside of descendants of the
+ *   *current* responderInst, an `onResponderRelease` event is dispatched to the
+ *   current responder, and the responder lock is released.
+ *
+ * TODO:
+ * - on "end", a callback hook for `onResponderEndShouldRemainResponder` that
+ *   determines if the responder lock should remain.
+ * - If a view shouldn't "remain" the responder, any active touches should by
+ *   default be considered "dead" and do not influence future negotiations or
+ *   bubble paths. It should be as if those touches do not exist.
+ * -- For multitouch: Usually a translate-z will choose to "remain" responder
+ *  after one out of many touches ended. For translate-y, usually the view
+ *  doesn't wish to "remain" responder after one of many touches end.
+ * - Consider building this on top of a `stopPropagation` model similar to
+ *   `W3C` events.
+ * - Ensure that `onResponderTerminate` is called on touch cancels, whether or
+ *   not `onResponderTerminationRequest` returns `true` or `false`.
+ *
+ */
+
+/*                                             Negotiation Performed
+                                             +-----------------------+
+                                            /                         \
+Process low level events to    +     Current Responder      +   wantsResponderID
+determine who to perform negot-|   (if any exists at all)   |
+iation/transition              | Otherwise just pass through|
+-------------------------------+----------------------------+------------------+
+Bubble to find first ID        |                            |
+to return true:wantsResponderID|                            |
+                               |                            |
+     +-------------+           |                            |
+     | onTouchStart|           |                            |
+     +------+------+     none  |                            |
+            |            return|                            |
++-----------v-------------+true| +------------------------+ |
+|onStartShouldSetResponder|----->|onResponderStart (cur)  |<-----------+
++-----------+-------------+    | +------------------------+ |          |
+            |                  |                            | +--------+-------+
+            | returned true for|       false:REJECT +-------->|onResponderReject
+            | wantsResponderID |                    |       | +----------------+
+            | (now attempt     | +------------------+-----+ |
+            |  handoff)        | |   onResponder          | |
+            +------------------->|      TerminationRequest| |
+                               | +------------------+-----+ |
+                               |                    |       | +----------------+
+                               |         true:GRANT +-------->|onResponderGrant|
+                               |                            | +--------+-------+
+                               | +------------------------+ |          |
+                               | |   onResponderTerminate |<-----------+
+                               | +------------------+-----+ |
+                               |                    |       | +----------------+
+                               |                    +-------->|onResponderStart|
+                               |                            | +----------------+
+Bubble to find first ID        |                            |
+to return true:wantsResponderID|                            |
+                               |                            |
+     +-------------+           |                            |
+     | onTouchMove |           |                            |
+     +------+------+     none  |                            |
+            |            return|                            |
++-----------v-------------+true| +------------------------+ |
+|onMoveShouldSetResponder |----->|onResponderMove (cur)   |<-----------+
++-----------+-------------+    | +------------------------+ |          |
+            |                  |                            | +--------+-------+
+            | returned true for|       false:REJECT +-------->|onResponderRejec|
+            | wantsResponderID |                    |       | +----------------+
+            | (now attempt     | +------------------+-----+ |
+            |  handoff)        | |   onResponder          | |
+            +------------------->|      TerminationRequest| |
+                               | +------------------+-----+ |
+                               |                    |       | +----------------+
+                               |         true:GRANT +-------->|onResponderGrant|
+                               |                            | +--------+-------+
+                               | +------------------------+ |          |
+                               | |   onResponderTerminate |<-----------+
+                               | +------------------+-----+ |
+                               |                    |       | +----------------+
+                               |                    +-------->|onResponderMove |
+                               |                            | +----------------+
+                               |                            |
+                               |                            |
+      Some active touch started|                            |
+      inside current responder | +------------------------+ |
+      +------------------------->|      onResponderEnd    | |
+      |                        | +------------------------+ |
+  +---+---------+              |                            |
+  | onTouchEnd  |              |                            |
+  +---+---------+              |                            |
+      |                        | +------------------------+ |
+      +------------------------->|     onResponderEnd     | |
+      No active touches started| +-----------+------------+ |
+      inside current responder |             |              |
+                               |             v              |
+                               | +------------------------+ |
+                               | |    onResponderRelease  | |
+                               | +------------------------+ |
+                               |                            |
+                               +                            + */
+
+/**
+ * A note about event ordering in the `EventPluginHub`.
+ *
+ * Suppose plugins are injected in the following order:
+ *
+ * `[R, S, C]`
+ *
+ * To help illustrate the example, assume `S` is `SimpleEventPlugin` (for
+ * `onClick` etc) and `R` is `ResponderEventPlugin`.
+ *
+ * "Deferred-Dispatched Events":
+ *
+ * - The current event plugin system will traverse the list of injected plugins,
+ *   in order, and extract events by collecting the plugin's return value of
+ *   `extractEvents()`.
+ * - These events that are returned from `extractEvents` are "deferred
+ *   dispatched events".
+ * - When returned from `extractEvents`, deferred-dispatched events contain an
+ *   "accumulation" of deferred dispatches.
+ * - These deferred dispatches are accumulated/collected before they are
+ *   returned, but processed at a later time by the `EventPluginHub` (hence the
+ *   name deferred).
+ *
+ * In the process of returning their deferred-dispatched events, event plugins
+ * themselves can dispatch events on-demand without returning them from
+ * `extractEvents`. Plugins might want to do this, so that they can use event
+ * dispatching as a tool that helps them decide which events should be extracted
+ * in the first place.
+ *
+ * "On-Demand-Dispatched Events":
+ *
+ * - On-demand-dispatched events are not returned from `extractEvents`.
+ * - On-demand-dispatched events are dispatched during the process of returning
+ *   the deferred-dispatched events.
+ * - They should not have side effects.
+ * - They should be avoided, and/or eventually be replaced with another
+ *   abstraction that allows event plugins to perform multiple "rounds" of event
+ *   extraction.
+ *
+ * Therefore, the sequence of event dispatches becomes:
+ *
+ * - `R`s on-demand events (if any)   (dispatched by `R` on-demand)
+ * - `S`s on-demand events (if any)   (dispatched by `S` on-demand)
+ * - `C`s on-demand events (if any)   (dispatched by `C` on-demand)
+ * - `R`s extracted events (if any)   (dispatched by `EventPluginHub`)
+ * - `S`s extracted events (if any)   (dispatched by `EventPluginHub`)
+ * - `C`s extracted events (if any)   (dispatched by `EventPluginHub`)
+ *
+ * In the case of `ResponderEventPlugin`: If the `startShouldSetResponder`
+ * on-demand dispatch returns `true` (and some other details are satisfied) the
+ * `onResponderGrant` deferred dispatched event is returned from
+ * `extractEvents`. The sequence of dispatch executions in this case
+ * will appear as follows:
+ *
+ * - `startShouldSetResponder` (`ResponderEventPlugin` dispatches on-demand)
+ * - `touchStartCapture`       (`EventPluginHub` dispatches as usual)
+ * - `touchStart`              (`EventPluginHub` dispatches as usual)
+ * - `responderGrant/Reject`   (`EventPluginHub` dispatches as usual)
+ */
+
+function setResponderAndExtractTransfer(
+  topLevelType,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  var shouldSetEventType = isStartish(topLevelType)
+    ? eventTypes$1.startShouldSetResponder
+    : isMoveish(topLevelType)
+      ? eventTypes$1.moveShouldSetResponder
+      : topLevelType === "topSelectionChange"
+        ? eventTypes$1.selectionChangeShouldSetResponder
+        : eventTypes$1.scrollShouldSetResponder;
+
+  // TODO: stop one short of the current responder.
+  var bubbleShouldSetFrom = !responderInst
+    ? targetInst
+    : getLowestCommonAncestor(responderInst, targetInst);
+
+  // When capturing/bubbling the "shouldSet" event, we want to skip the target
+  // (deepest ID) if it happens to be the current responder. The reasoning:
+  // It's strange to get an `onMoveShouldSetResponder` when you're *already*
+  // the responder.
+  var skipOverBubbleShouldSetFrom = bubbleShouldSetFrom === responderInst;
+  var shouldSetEvent = ResponderSyntheticEvent.getPooled(
+    shouldSetEventType,
+    bubbleShouldSetFrom,
+    nativeEvent,
+    nativeEventTarget
+  );
+  shouldSetEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+  if (skipOverBubbleShouldSetFrom) {
+    accumulateTwoPhaseDispatchesSkipTarget(shouldSetEvent);
+  } else {
+    accumulateTwoPhaseDispatches(shouldSetEvent);
+  }
+  var wantsResponderInst = executeDispatchesInOrderStopAtTrue(shouldSetEvent);
+  if (!shouldSetEvent.isPersistent()) {
+    shouldSetEvent.constructor.release(shouldSetEvent);
+  }
+
+  if (!wantsResponderInst || wantsResponderInst === responderInst) {
+    return null;
+  }
+  var extracted = void 0;
+  var grantEvent = ResponderSyntheticEvent.getPooled(
+    eventTypes$1.responderGrant,
+    wantsResponderInst,
+    nativeEvent,
+    nativeEventTarget
+  );
+  grantEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+
+  accumulateDirectDispatches(grantEvent);
+  var blockHostResponder = executeDirectDispatch(grantEvent) === true;
+  if (responderInst) {
+    var terminationRequestEvent = ResponderSyntheticEvent.getPooled(
+      eventTypes$1.responderTerminationRequest,
+      responderInst,
+      nativeEvent,
+      nativeEventTarget
+    );
+    terminationRequestEvent.touchHistory =
+      ResponderTouchHistoryStore.touchHistory;
+    accumulateDirectDispatches(terminationRequestEvent);
+    var shouldSwitch =
+      !hasDispatches(terminationRequestEvent) ||
+      executeDirectDispatch(terminationRequestEvent);
+    if (!terminationRequestEvent.isPersistent()) {
+      terminationRequestEvent.constructor.release(terminationRequestEvent);
+    }
+
+    if (shouldSwitch) {
+      var terminateEvent = ResponderSyntheticEvent.getPooled(
+        eventTypes$1.responderTerminate,
+        responderInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      terminateEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+      accumulateDirectDispatches(terminateEvent);
+      extracted = accumulate(extracted, [grantEvent, terminateEvent]);
+      changeResponder(wantsResponderInst, blockHostResponder);
+    } else {
+      var rejectEvent = ResponderSyntheticEvent.getPooled(
+        eventTypes$1.responderReject,
+        wantsResponderInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      rejectEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+      accumulateDirectDispatches(rejectEvent);
+      extracted = accumulate(extracted, rejectEvent);
+    }
+  } else {
+    extracted = accumulate(extracted, grantEvent);
+    changeResponder(wantsResponderInst, blockHostResponder);
+  }
+  return extracted;
+}
+
+/**
+ * A transfer is a negotiation between a currently set responder and the next
+ * element to claim responder status. Any start event could trigger a transfer
+ * of responderInst. Any move event could trigger a transfer.
+ *
+ * @param {string} topLevelType Record from `BrowserEventConstants`.
+ * @return {boolean} True if a transfer of responder could possibly occur.
+ */
+function canTriggerTransfer(topLevelType, topLevelInst, nativeEvent) {
+  return (
+    topLevelInst &&
+    // responderIgnoreScroll: We are trying to migrate away from specifically
+    // tracking native scroll events here and responderIgnoreScroll indicates we
+    // will send topTouchCancel to handle canceling touch events instead
+    ((topLevelType === "topScroll" && !nativeEvent.responderIgnoreScroll) ||
+      (trackedTouchCount > 0 && topLevelType === "topSelectionChange") ||
+      isStartish(topLevelType) ||
+      isMoveish(topLevelType))
+  );
+}
+
+/**
+ * Returns whether or not this touch end event makes it such that there are no
+ * longer any touches that started inside of the current `responderInst`.
+ *
+ * @param {NativeEvent} nativeEvent Native touch end event.
+ * @return {boolean} Whether or not this touch end event ends the responder.
+ */
+function noResponderTouches(nativeEvent) {
+  var touches = nativeEvent.touches;
+  if (!touches || touches.length === 0) {
+    return true;
+  }
+  for (var i = 0; i < touches.length; i++) {
+    var activeTouch = touches[i];
+    var target = activeTouch.target;
+    if (target !== null && target !== undefined && target !== 0) {
+      // Is the original touch location inside of the current responder?
+      var targetInst = getInstanceFromNode(target);
+      if (isAncestor(responderInst, targetInst)) {
+        return false;
+      }
+    }
+  }
+  return true;
+}
+
+var ResponderEventPlugin = {
+  /* For unit testing only */
+  _getResponder: function() {
+    return responderInst;
+  },
+
+  eventTypes: eventTypes$1,
+
+  /**
+   * We must be resilient to `targetInst` being `null` on `touchMove` or
+   * `touchEnd`. On certain platforms, this means that a native scroll has
+   * assumed control and the original touch targets are destroyed.
+   */
+  extractEvents: function(
+    topLevelType,
+    targetInst,
+    nativeEvent,
+    nativeEventTarget
+  ) {
+    if (isStartish(topLevelType)) {
+      trackedTouchCount += 1;
+    } else if (isEndish(topLevelType)) {
+      if (trackedTouchCount >= 0) {
+        trackedTouchCount -= 1;
+      } else {
+        console.error(
+          "Ended a touch event which was not counted in `trackedTouchCount`."
+        );
+        return null;
+      }
+    }
+
+    ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
+
+    var extracted = canTriggerTransfer(topLevelType, targetInst, nativeEvent)
+      ? setResponderAndExtractTransfer(
+          topLevelType,
+          targetInst,
+          nativeEvent,
+          nativeEventTarget
+        )
+      : null;
+    // Responder may or may not have transferred on a new touch start/move.
+    // Regardless, whoever is the responder after any potential transfer, we
+    // direct all touch start/move/ends to them in the form of
+    // `onResponderMove/Start/End`. These will be called for *every* additional
+    // finger that move/start/end, dispatched directly to whoever is the
+    // current responder at that moment, until the responder is "released".
+    //
+    // These multiple individual change touch events are are always bookended
+    // by `onResponderGrant`, and one of
+    // (`onResponderRelease/onResponderTerminate`).
+    var isResponderTouchStart = responderInst && isStartish(topLevelType);
+    var isResponderTouchMove = responderInst && isMoveish(topLevelType);
+    var isResponderTouchEnd = responderInst && isEndish(topLevelType);
+    var incrementalTouch = isResponderTouchStart
+      ? eventTypes$1.responderStart
+      : isResponderTouchMove
+        ? eventTypes$1.responderMove
+        : isResponderTouchEnd ? eventTypes$1.responderEnd : null;
+
+    if (incrementalTouch) {
+      var gesture = ResponderSyntheticEvent.getPooled(
+        incrementalTouch,
+        responderInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      gesture.touchHistory = ResponderTouchHistoryStore.touchHistory;
+      accumulateDirectDispatches(gesture);
+      extracted = accumulate(extracted, gesture);
+    }
+
+    var isResponderTerminate =
+      responderInst && topLevelType === "topTouchCancel";
+    var isResponderRelease =
+      responderInst &&
+      !isResponderTerminate &&
+      isEndish(topLevelType) &&
+      noResponderTouches(nativeEvent);
+    var finalTouch = isResponderTerminate
+      ? eventTypes$1.responderTerminate
+      : isResponderRelease ? eventTypes$1.responderRelease : null;
+    if (finalTouch) {
+      var finalEvent = ResponderSyntheticEvent.getPooled(
+        finalTouch,
+        responderInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      finalEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+      accumulateDirectDispatches(finalEvent);
+      extracted = accumulate(extracted, finalEvent);
+      changeResponder(null);
+    }
+
+    var numberActiveTouches =
+      ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
+    if (
+      ResponderEventPlugin.GlobalInteractionHandler &&
+      numberActiveTouches !== previousActiveTouches
+    ) {
+      ResponderEventPlugin.GlobalInteractionHandler.onChange(
+        numberActiveTouches
+      );
+    }
+    previousActiveTouches = numberActiveTouches;
+
+    return extracted;
+  },
+
+  GlobalResponderHandler: null,
+  GlobalInteractionHandler: null,
+
+  injection: {
+    /**
+     * @param {{onChange: (ReactID, ReactID) => void} GlobalResponderHandler
+     * Object that handles any change in responder. Use this to inject
+     * integration with an existing touch handling system etc.
+     */
+    injectGlobalResponderHandler: function(GlobalResponderHandler) {
+      ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
+    },
+
+    /**
+     * @param {{onChange: (numberActiveTouches) => void} GlobalInteractionHandler
+     * Object that handles any change in the number of active touches.
+     */
+    injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
+      ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
+    }
+  }
+};
+
+var customBubblingEventTypes$1 =
+  ReactNativeViewConfigRegistry.customBubblingEventTypes;
+var customDirectEventTypes$1 =
+  ReactNativeViewConfigRegistry.customDirectEventTypes;
+var eventTypes$2 = ReactNativeViewConfigRegistry.eventTypes;
+
+var ReactNativeBridgeEventPlugin = {
+  eventTypes: eventTypes$2,
+
+  /**
+   * @see {EventPluginHub.extractEvents}
+   */
+  extractEvents: function(
+    topLevelType,
+    targetInst,
+    nativeEvent,
+    nativeEventTarget
+  ) {
+    if (targetInst == null) {
+      // Probably a node belonging to another renderer's tree.
+      return null;
+    }
+    var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType];
+    var directDispatchConfig = customDirectEventTypes$1[topLevelType];
+    invariant(
+      bubbleDispatchConfig || directDispatchConfig,
+      'Unsupported top level event type "%s" dispatched',
+      topLevelType
+    );
+    var event = SyntheticEvent$1.getPooled(
+      bubbleDispatchConfig || directDispatchConfig,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    );
+    if (bubbleDispatchConfig) {
+      accumulateTwoPhaseDispatches(event);
+    } else if (directDispatchConfig) {
+      accumulateDirectDispatches(event);
+    } else {
+      return null;
+    }
+    return event;
+  }
+};
+
+var instanceCache = {};
+var instanceProps = {};
+
+function precacheFiberNode(hostInst, tag) {
+  instanceCache[tag] = hostInst;
+}
+
+function uncacheFiberNode(tag) {
+  delete instanceCache[tag];
+  delete instanceProps[tag];
+}
+
+function getInstanceFromTag(tag) {
+  if (typeof tag === "number") {
+    return instanceCache[tag] || null;
+  } else {
+    // Fabric will invoke event emitters on a direct fiber reference
+    return tag;
+  }
+}
+
+function getTagFromInstance(inst) {
+  var tag = inst.stateNode._nativeTag;
+  if (tag === undefined) {
+    tag = inst.stateNode.canonical._nativeTag;
+  }
+  invariant(tag, "All native instances should have a tag.");
+  return tag;
+}
+
+function getFiberCurrentPropsFromNode$1(stateNode) {
+  return instanceProps[stateNode._nativeTag] || null;
+}
+
+function updateFiberProps(tag, props) {
+  instanceProps[tag] = props;
+}
+
+var ReactNativeComponentTree = Object.freeze({
+  precacheFiberNode: precacheFiberNode,
+  uncacheFiberNode: uncacheFiberNode,
+  getClosestInstanceFromNode: getInstanceFromTag,
+  getInstanceFromNode: getInstanceFromTag,
+  getNodeFromInstance: getTagFromInstance,
+  getFiberCurrentPropsFromNode: getFiberCurrentPropsFromNode$1,
+  updateFiberProps: updateFiberProps
+});
+
+var ReactNativeEventPluginOrder = [
+  "ResponderEventPlugin",
+  "ReactNativeBridgeEventPlugin"
+];
+
+// Module provided by RN:
+var ReactNativeGlobalResponderHandler = {
+  onChange: function(from, to, blockNativeResponder) {
+    if (to !== null) {
+      var tag = to.stateNode._nativeTag;
+      UIManager.setJSResponder(tag, blockNativeResponder);
+    } else {
+      UIManager.clearJSResponder();
+    }
+  }
+};
+
+/**
+ * Make sure essential globals are available and are patched correctly. Please don't remove this
+ * line. Bundles created by react-packager `require` it before executing any application code. This
+ * ensures it exists in the dependency graph and can be `require`d.
+ * TODO: require this in packager, not in React #10932517
+ */
+// Module provided by RN:
+/**
+ * Inject module for resolving DOM hierarchy and plugin ordering.
+ */
+injection.injectEventPluginOrder(ReactNativeEventPluginOrder);
+injection$1.injectComponentTree(ReactNativeComponentTree);
+
+ResponderEventPlugin.injection.injectGlobalResponderHandler(
+  ReactNativeGlobalResponderHandler
+);
+
+/**
+ * Some important event plugins included by default (without having to require
+ * them).
+ */
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
+
+// TODO: The event emitter registration is interfering with the existing
+// ReactNative renderer. So disable it for Fabric for now.
+
+// import * as ReactNativeEventEmitter from './ReactNativeEventEmitter';
+
+// Module provided by RN:
+// import RCTEventEmitter from 'RCTEventEmitter';
+
+/**
+ * Register the event emitter with the native bridge
+ */
+// RCTEventEmitter.register(ReactNativeEventEmitter);
+
+// The Symbol used to tag the ReactElement-like types. If there is no native Symbol
+// nor polyfill, then a plain number is used for performance.
+var hasSymbol = typeof Symbol === "function" && Symbol["for"];
+
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
+var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
+var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
+var REACT_STRICT_MODE_TYPE = hasSymbol
+  ? Symbol["for"]("react.strict_mode")
+  : 0xeacc;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
+var REACT_ASYNC_MODE_TYPE = hasSymbol
+  ? Symbol["for"]("react.async_mode")
+  : 0xeacf;
+var REACT_FORWARD_REF_TYPE = hasSymbol
+  ? Symbol["for"]("react.forward_ref")
+  : 0xead0;
+
+var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
+var FAUX_ITERATOR_SYMBOL = "@@iterator";
+
+function getIteratorFn(maybeIterable) {
+  if (maybeIterable === null || typeof maybeIterable === "undefined") {
+    return null;
+  }
+  var maybeIterator =
+    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
+    maybeIterable[FAUX_ITERATOR_SYMBOL];
+  if (typeof maybeIterator === "function") {
+    return maybeIterator;
+  }
+  return null;
+}
+
+function createPortal(
+  children,
+  containerInfo,
+  // TODO: figure out the API for cross-renderer implementation.
+  implementation
+) {
+  var key =
+    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
+
+  return {
+    // This tag allow us to uniquely identify this as a React Portal
+    $$typeof: REACT_PORTAL_TYPE,
+    key: key == null ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+
+// Used as a way to call batchedUpdates when we don't have a reference to
+// the renderer. Such as when we're dispatching events or if third party
+// libraries need to call batchedUpdates. Eventually, this API will go away when
+// everything is batched by default. We'll then have a similar API to opt-out of
+// scheduled work and instead do synchronous work.
+
+// Defaults
+var _batchedUpdates = function(fn, bookkeeping) {
+  return fn(bookkeeping);
+};
+var _interactiveUpdates = function(fn, a, b) {
+  return fn(a, b);
+};
+var _flushInteractiveUpdates = function() {};
+
+var injection$2 = {
+  injectRenderer: function(renderer) {
+    _batchedUpdates = renderer.batchedUpdates;
+    _interactiveUpdates = renderer.interactiveUpdates;
+    _flushInteractiveUpdates = renderer.flushInteractiveUpdates;
+  }
+};
+
+// TODO: this is special because it gets imported during build.
+
+var ReactVersion = "16.3.2";
+
+// Modules provided by RN:
+var emptyObject$1 = {};
+
+/**
+ * Create a payload that contains all the updates between two sets of props.
+ *
+ * These helpers are all encapsulated into a single module, because they use
+ * mutation as a performance optimization which leads to subtle shared
+ * dependencies between the code paths. To avoid this mutable state leaking
+ * across modules, I've kept them isolated to this module.
+ */
+
+// Tracks removed keys
+var removedKeys = null;
+var removedKeyCount = 0;
+
+function defaultDiffer(prevProp, nextProp) {
+  if (typeof nextProp !== "object" || nextProp === null) {
+    // Scalars have already been checked for equality
+    return true;
+  } else {
+    // For objects and arrays, the default diffing algorithm is a deep compare
+    return deepDiffer(prevProp, nextProp);
+  }
+}
+
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node)) {
+    var i = node.length;
+    while (i-- && removedKeyCount > 0) {
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+    }
+  } else if (node && removedKeyCount > 0) {
+    var obj = node;
+    for (var propKey in removedKeys) {
+      if (!removedKeys[propKey]) {
+        continue;
+      }
+      var _nextProp = obj[propKey];
+      if (_nextProp === undefined) {
+        continue;
+      }
+
+      var attributeConfig = validAttributes[propKey];
+      if (!attributeConfig) {
+        continue; // not a valid native prop
+      }
+
+      if (typeof _nextProp === "function") {
+        _nextProp = true;
+      }
+      if (typeof _nextProp === "undefined") {
+        _nextProp = null;
+      }
+
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = _nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(_nextProp)
+            : _nextProp;
+        updatePayload[propKey] = nextValue;
+      }
+      removedKeys[propKey] = false;
+      removedKeyCount--;
+    }
+  }
+}
+
+function diffNestedArrayProperty(
+  updatePayload,
+  prevArray,
+  nextArray,
+  validAttributes
+) {
+  var minLength =
+    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
+  var i = void 0;
+  for (i = 0; i < minLength; i++) {
+    // Diff any items in the array in the forward direction. Repeated keys
+    // will be overwritten by later values.
+    updatePayload = diffNestedProperty(
+      updatePayload,
+      prevArray[i],
+      nextArray[i],
+      validAttributes
+    );
+  }
+  for (; i < prevArray.length; i++) {
+    // Clear out all remaining properties.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevArray[i],
+      validAttributes
+    );
+  }
+  for (; i < nextArray.length; i++) {
+    // Add all remaining properties.
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextArray[i],
+      validAttributes
+    );
+  }
+  return updatePayload;
+}
+
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) {
+    // If no properties have been added, then we can bail out quickly on object
+    // equality.
+    return updatePayload;
+  }
+
+  if (!prevProp || !nextProp) {
+    if (nextProp) {
+      return addNestedProperty(updatePayload, nextProp, validAttributes);
+    }
+    if (prevProp) {
+      return clearNestedProperty(updatePayload, prevProp, validAttributes);
+    }
+    return updatePayload;
+  }
+
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
+    // Both are leaves, we can diff the leaves.
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  }
+
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    // Both are arrays, we can diff the arrays.
+    return diffNestedArrayProperty(
+      updatePayload,
+      prevProp,
+      nextProp,
+      validAttributes
+    );
+  }
+
+  if (Array.isArray(prevProp)) {
+    return diffProperties(
+      updatePayload,
+      // $FlowFixMe - We know that this is always an object when the input is.
+      flattenStyle(prevProp),
+      // $FlowFixMe - We know that this isn't an array because of above flow.
+      nextProp,
+      validAttributes
+    );
+  }
+
+  return diffProperties(
+    updatePayload,
+    prevProp,
+    // $FlowFixMe - We know that this is always an object when the input is.
+    flattenStyle(nextProp),
+    validAttributes
+  );
+}
+
+/**
+ * addNestedProperty takes a single set of props and valid attribute
+ * attribute configurations. It processes each prop and adds it to the
+ * updatePayload.
+ */
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) {
+    return updatePayload;
+  }
+
+  if (!Array.isArray(nextProp)) {
+    // Add each property of the leaf.
+    return addProperties(updatePayload, nextProp, validAttributes);
+  }
+
+  for (var i = 0; i < nextProp.length; i++) {
+    // Add all the properties of the array.
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  }
+
+  return updatePayload;
+}
+
+/**
+ * clearNestedProperty takes a single set of props and valid attributes. It
+ * adds a null sentinel to the updatePayload, for each prop key.
+ */
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) {
+    return updatePayload;
+  }
+
+  if (!Array.isArray(prevProp)) {
+    // Add each property of the leaf.
+    return clearProperties(updatePayload, prevProp, validAttributes);
+  }
+
+  for (var i = 0; i < prevProp.length; i++) {
+    // Add all the properties of the array.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  }
+  return updatePayload;
+}
+
+/**
+ * diffProperties takes two sets of props and a set of valid attributes
+ * and write to updatePayload the values that changed or were deleted.
+ * If no updatePayload is provided, a new one is created and returned if
+ * anything changed.
+ */
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig = void 0;
+  var nextProp = void 0;
+  var prevProp = void 0;
+
+  for (var propKey in nextProps) {
+    attributeConfig = validAttributes[propKey];
+    if (!attributeConfig) {
+      continue; // not a valid native prop
+    }
+
+    prevProp = prevProps[propKey];
+    nextProp = nextProps[propKey];
+
+    // functions are converted to booleans as markers that the associated
+    // events should be sent from native.
+    if (typeof nextProp === "function") {
+      nextProp = true;
+      // If nextProp is not a function, then don't bother changing prevProp
+      // since nextProp will win and go into the updatePayload regardless.
+      if (typeof prevProp === "function") {
+        prevProp = true;
+      }
+    }
+
+    // An explicit value of undefined is treated as a null because it overrides
+    // any other preceding value.
+    if (typeof nextProp === "undefined") {
+      nextProp = null;
+      if (typeof prevProp === "undefined") {
+        prevProp = null;
+      }
+    }
+
+    if (removedKeys) {
+      removedKeys[propKey] = false;
+    }
+
+    if (updatePayload && updatePayload[propKey] !== undefined) {
+      // Something else already triggered an update to this key because another
+      // value diffed. Since we're now later in the nested arrays our value is
+      // more important so we need to calculate it and override the existing
+      // value. It doesn't matter if nothing changed, we'll set it anyway.
+
+      // Pattern match on: attributeConfig
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(nextProp)
+            : nextProp;
+        updatePayload[propKey] = nextValue;
+      }
+      continue;
+    }
+
+    if (prevProp === nextProp) {
+      continue; // nothing changed
+    }
+
+    // Pattern match on: attributeConfig
+    if (typeof attributeConfig !== "object") {
+      // case: !Object is the default case
+      if (defaultDiffer(prevProp, nextProp)) {
+        // a normal leaf has changed
+        (updatePayload || (updatePayload = {}))[propKey] = nextProp;
+      }
+    } else if (
+      typeof attributeConfig.diff === "function" ||
+      typeof attributeConfig.process === "function"
+    ) {
+      // case: CustomAttributeConfiguration
+      var shouldUpdate =
+        prevProp === undefined ||
+        (typeof attributeConfig.diff === "function"
+          ? attributeConfig.diff(prevProp, nextProp)
+          : defaultDiffer(prevProp, nextProp));
+      if (shouldUpdate) {
+        var _nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(nextProp)
+            : nextProp;
+        (updatePayload || (updatePayload = {}))[propKey] = _nextValue;
+      }
+    } else {
+      // default: fallthrough case when nested properties are defined
+      removedKeys = null;
+      removedKeyCount = 0;
+      // We think that attributeConfig is not CustomAttributeConfiguration at
+      // this point so we assume it must be AttributeConfiguration.
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp,
+        nextProp,
+        attributeConfig
+      );
+      if (removedKeyCount > 0 && updatePayload) {
+        restoreDeletedValuesInNestedArray(
+          updatePayload,
+          nextProp,
+          attributeConfig
+        );
+        removedKeys = null;
+      }
+    }
+  }
+
+  // Also iterate through all the previous props to catch any that have been
+  // removed and make sure native gets the signal so it can reset them to the
+  // default.
+  for (var _propKey in prevProps) {
+    if (nextProps[_propKey] !== undefined) {
+      continue; // we've already covered this key in the previous pass
+    }
+    attributeConfig = validAttributes[_propKey];
+    if (!attributeConfig) {
+      continue; // not a valid native prop
+    }
+
+    if (updatePayload && updatePayload[_propKey] !== undefined) {
+      // This was already updated to a diff result earlier.
+      continue;
+    }
+
+    prevProp = prevProps[_propKey];
+    if (prevProp === undefined) {
+      continue; // was already empty anyway
+    }
+    // Pattern match on: attributeConfig
+    if (
+      typeof attributeConfig !== "object" ||
+      typeof attributeConfig.diff === "function" ||
+      typeof attributeConfig.process === "function"
+    ) {
+      // case: CustomAttributeConfiguration | !Object
+      // Flag the leaf property for removal by sending a sentinel.
+      (updatePayload || (updatePayload = {}))[_propKey] = null;
+      if (!removedKeys) {
+        removedKeys = {};
+      }
+      if (!removedKeys[_propKey]) {
+        removedKeys[_propKey] = true;
+        removedKeyCount++;
+      }
+    } else {
+      // default:
+      // This is a nested attribute configuration where all the properties
+      // were removed so we need to go through and clear out all of them.
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp,
+        attributeConfig
+      );
+    }
+  }
+  return updatePayload;
+}
+
+/**
+ * addProperties adds all the valid props to the payload after being processed.
+ */
+function addProperties(updatePayload, props, validAttributes) {
+  // TODO: Fast path
+  return diffProperties(updatePayload, emptyObject$1, props, validAttributes);
+}
+
+/**
+ * clearProperties clears all the previous props by adding a null sentinel
+ * to the payload for each valid key.
+ */
+function clearProperties(updatePayload, prevProps, validAttributes) {
+  // TODO: Fast path
+  return diffProperties(
+    updatePayload,
+    prevProps,
+    emptyObject$1,
+    validAttributes
+  );
+}
+
+function create(props, validAttributes) {
+  return addProperties(
+    null, // updatePayload
+    props,
+    validAttributes
+  );
+}
+
+function diff(prevProps, nextProps, validAttributes) {
+  return diffProperties(
+    null, // updatePayload
+    prevProps,
+    nextProps,
+    validAttributes
+  );
+}
+
+/**
+ * In the future, we should cleanup callbacks by cancelling them instead of
+ * using this.
+ */
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (!callback) {
+      return undefined;
+    }
+    if (typeof context.__isMounted === "boolean") {
+      // TODO(gaearon): this is gross and should be removed.
+      // It is currently necessary because View uses createClass,
+      // and so any measure() calls on View (which are done by React
+      // DevTools) trigger the isMounted() deprecation warning.
+      if (!context.__isMounted) {
+        return undefined;
+      }
+      // The else branch is important so that we don't
+      // trigger the deprecation warning by calling isMounted.
+    } else if (typeof context.isMounted === "function") {
+      if (!context.isMounted()) {
+        return undefined;
+      }
+    }
+    return callback.apply(context, arguments);
+  };
+}
+
+function throwOnStylesProp(component, props) {
+  if (props.styles !== undefined) {
+    var owner = component._owner || null;
+    var name = component.constructor.displayName;
+    var msg =
+      "`styles` is not a supported property of `" +
+      name +
+      "`, did " +
+      "you mean `style` (singular)?";
+    if (owner && owner.constructor && owner.constructor.displayName) {
+      msg +=
+        "\n\nCheck the `" +
+        owner.constructor.displayName +
+        "` parent " +
+        " component.";
+    }
+    throw new Error(msg);
+  }
+}
+
+function warnForStyleProps(props, validAttributes) {
+  for (var key in validAttributes.style) {
+    if (!(validAttributes[key] || props[key] === undefined)) {
+      console.error(
+        "You are setting the style `{ " +
+          key +
+          ": ... }` as a prop. You " +
+          "should nest it in a style object. " +
+          "E.g. `{ style: { " +
+          key +
+          ": ... } }`"
+      );
+    }
+  }
+}
+
+// Modules provided by RN:
+var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
+  /**
+   * `NativeMethodsMixin` provides methods to access the underlying native
+   * component directly. This can be useful in cases when you want to focus
+   * a view or measure its on-screen dimensions, for example.
+   *
+   * The methods described here are available on most of the default components
+   * provided by React Native. Note, however, that they are *not* available on
+   * composite components that aren't directly backed by a native view. This will
+   * generally include most components that you define in your own app. For more
+   * information, see [Direct
+   * Manipulation](docs/direct-manipulation.html).
+   *
+   * Note the Flow $Exact<> syntax is required to support mixins.
+   * React createClass mixins can only be used with exact types.
+   */
+  var NativeMethodsMixin = {
+    /**
+     * Determines the location on screen, width, and height of the given view and
+     * returns the values via an async callback. If successful, the callback will
+     * be called with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native. If you need the measurements as soon as
+     * possible, consider using the [`onLayout`
+     * prop](docs/view.html#onlayout) instead.
+     */
+    measure: function(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
+
+    /**
+     * Determines the location of the given view in the window and returns the
+     * values via an async callback. If the React root view is embedded in
+     * another native view, this will give you the absolute coordinates. If
+     * successful, the callback will be called with the following
+     * arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native.
+     */
+    measureInWindow: function(callback) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
+
+    /**
+     * Like [`measure()`](#measure), but measures the view relative an ancestor,
+     * specified as `relativeToNativeNode`. This means that the returned x, y
+     * are relative to the origin x, y of the ancestor view.
+     *
+     * As always, to obtain a native node handle for a component, you can use
+     * `findNodeHandle(component)`.
+     */
+    measureLayout: function(
+      relativeToNativeNode,
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    },
+
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
+    setNativeProps: function(nativeProps) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
+
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
+
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
+
+      var viewConfig = maybeInstance.viewConfig;
+
+      {
+        warnForStyleProps(nativeProps, viewConfig.validAttributes);
+      }
+
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
+
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    },
+
+    /**
+     * Requests focus for the given input or view. The exact behavior triggered
+     * will depend on the platform and type of view.
+     */
+    focus: function() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    },
+
+    /**
+     * Removes focus from an input or view. This is the opposite of `focus()`.
+     */
+    blur: function() {
+      TextInputState.blurTextInput(findNodeHandle(this));
+    }
+  };
+
+  {
+    // hide this from Flow since we can't define these properties outside of
+    // true without actually implementing them (setting them to undefined
+    // isn't allowed by ReactClass)
+    var NativeMethodsMixin_DEV = NativeMethodsMixin;
+    invariant(
+      !NativeMethodsMixin_DEV.componentWillMount &&
+        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
+      "Do not override existing functions."
+    );
+    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
+    // Once these lifecycles have been remove from the reconciler.
+    NativeMethodsMixin_DEV.componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
+      throwOnStylesProp(this, newProps);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
+      newProps
+    ) {
+      throwOnStylesProp(this, newProps);
+    };
+
+    // React may warn about cWM/cWRP/cWU methods being deprecated.
+    // Add a flag to suppress these warnings for this special case.
+    // TODO (bvaughn) Remove this flag once the above methods have been removed.
+    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
+    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
+  }
+
+  return NativeMethodsMixin;
+};
+
+function _classCallCheck(instance, Constructor) {
+  if (!(instance instanceof Constructor)) {
+    throw new TypeError("Cannot call a class as a function");
+  }
+}
+
+function _possibleConstructorReturn(self, call) {
+  if (!self) {
+    throw new ReferenceError(
+      "this hasn't been initialised - super() hasn't been called"
+    );
+  }
+  return call && (typeof call === "object" || typeof call === "function")
+    ? call
+    : self;
+}
+
+function _inherits(subClass, superClass) {
+  if (typeof superClass !== "function" && superClass !== null) {
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
+  }
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: false,
+      writable: true,
+      configurable: true
+    }
+  });
+  if (superClass)
+    Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass);
+}
+
+// Modules provided by RN:
+var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
+  /**
+   * Superclass that provides methods to access the underlying native component.
+   * This can be useful when you want to focus a view or measure its dimensions.
+   *
+   * Methods implemented by this class are available on most default components
+   * provided by React Native. However, they are *not* available on composite
+   * components that are not directly backed by a native view. For more
+   * information, see [Direct Manipulation](docs/direct-manipulation.html).
+   *
+   * @abstract
+   */
+  var ReactNativeComponent = (function(_React$Component) {
+    _inherits(ReactNativeComponent, _React$Component);
+
+    function ReactNativeComponent() {
+      _classCallCheck(this, ReactNativeComponent);
+
+      return _possibleConstructorReturn(
+        this,
+        _React$Component.apply(this, arguments)
+      );
+    }
+
+    /**
+     * Removes focus. This is the opposite of `focus()`.
+     */
+
+    /**
+     * Due to bugs in Flow's handling of React.createClass, some fields already
+     * declared in the base class need to be redeclared below.
+     */
+    ReactNativeComponent.prototype.blur = function blur() {
+      TextInputState.blurTextInput(findNodeHandle(this));
+    };
+
+    /**
+     * Requests focus. The exact behavior depends on the platform and view.
+     */
+
+    ReactNativeComponent.prototype.focus = function focus() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    };
+
+    /**
+     * Measures the on-screen location and dimensions. If successful, the callback
+     * will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * These values are not available until after natives rendering completes. If
+     * you need the measurements as soon as possible, consider using the
+     * [`onLayout` prop](docs/view.html#onlayout) instead.
+     */
+
+    ReactNativeComponent.prototype.measure = function measure(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
+
+    /**
+     * Measures the on-screen location and dimensions. Even if the React Native
+     * root view is embedded within another native view, this method will give you
+     * the absolute coordinates measured from the window. If successful, the
+     * callback will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * These values are not available until after natives rendering completes.
+     */
+
+    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
+
+    /**
+     * Similar to [`measure()`](#measure), but the resulting location will be
+     * relative to the supplied ancestor's location.
+     *
+     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
+     */
+
+    ReactNativeComponent.prototype.measureLayout = function measureLayout(
+      relativeToNativeNode,
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
+
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
+
+    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
+      nativeProps
+    ) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
+
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
+
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
+
+      var viewConfig =
+        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
+
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    };
+
+    return ReactNativeComponent;
+  })(React.Component);
+
+  // eslint-disable-next-line no-unused-expressions
+
+  return ReactNativeComponent;
+};
+
+var hasNativePerformanceNow =
+  typeof performance === "object" && typeof performance.now === "function";
+
+var now = hasNativePerformanceNow
+  ? function() {
+      return performance.now();
+    }
+  : function() {
+      return Date.now();
+    };
+
+var scheduledCallback = null;
+var frameDeadline = 0;
+
+var frameDeadlineObject = {
+  timeRemaining: function() {
+    return frameDeadline - now();
+  },
+  didTimeout: false
+};
+
+function setTimeoutCallback() {
+  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
+  // React API probably changing to boolean rather than time remaining.
+  // Longer-term plan is to rewrite this using shared memory,
+  // And just return the value of the bit as the boolean.
+  frameDeadline = now() + 5;
+
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  if (callback !== null) {
+    callback(frameDeadlineObject);
+  }
+}
+
+// RN has a poor polyfill for requestIdleCallback so we aren't using it.
+// This implementation is only intended for short-term use anyway.
+// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
+function scheduleDeferredCallback(callback) {
+  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
+  scheduledCallback = callback;
+  return setTimeout(setTimeoutCallback, 1);
+}
+
+function cancelDeferredCallback(callbackID) {
+  scheduledCallback = null;
+  clearTimeout(callbackID);
+}
+
+/**
+ * `ReactInstanceMap` maintains a mapping from a public facing stateful
+ * instance (key) and the internal representation (value). This allows public
+ * methods to accept the user facing instance as an argument and map them back
+ * to internal methods.
+ *
+ * Note that this module is currently shared and assumed to be stateless.
+ * If this becomes an actual Map, that will break.
+ */
+
+/**
+ * This API should be called `delete` but we'd have to make sure to always
+ * transform these to strings for IE support. When this transform is fully
+ * supported we can rename it.
+ */
+
+function get$1(key) {
+  return key._reactInternalFiber;
+}
+
+function set(key, value) {
+  key._reactInternalFiber = value;
+}
+
+var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+
+var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
+var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
+
+function getComponentName(fiber) {
+  var type = fiber.type;
+
+  if (typeof type === "function") {
+    return type.displayName || type.name;
+  }
+  if (typeof type === "string") {
+    return type;
+  }
+  switch (type) {
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_RETURN_TYPE:
+      return "ReactReturn";
+  }
+  if (typeof type === "object" && type !== null) {
+    switch (type.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        var functionName = type.render.displayName || type.render.name || "";
+        return functionName !== ""
+          ? "ForwardRef(" + functionName + ")"
+          : "ForwardRef";
+    }
+  }
+  return null;
+}
+
+// Don't change these two values. They're used by React Dev Tools.
+var NoEffect = /*              */ 0;
+var PerformedWork = /*         */ 1;
+
+// You can change the rest (and add more).
+var Placement = /*             */ 2;
+var Update = /*                */ 4;
+var PlacementAndUpdate = /*    */ 6;
+var Deletion = /*              */ 8;
+var ContentReset = /*          */ 16;
+var Callback = /*              */ 32;
+var DidCapture = /*            */ 64;
+var Ref = /*                   */ 128;
+var ErrLog = /*                */ 256;
+var Snapshot = /*              */ 2048;
+
+// Union of all host effects
+var HostEffectMask = /*        */ 2559;
+
+var Incomplete = /*            */ 512;
+var ShouldCapture = /*         */ 1024;
+
+var MOUNTING = 1;
+var MOUNTED = 2;
+var UNMOUNTED = 3;
+
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (!fiber.alternate) {
+    // If there is no alternate, this might be a new tree that isn't inserted
+    // yet. If it is, then it will have a pending insertion effect on it.
+    if ((node.effectTag & Placement) !== NoEffect) {
+      return MOUNTING;
+    }
+    while (node["return"]) {
+      node = node["return"];
+      if ((node.effectTag & Placement) !== NoEffect) {
+        return MOUNTING;
+      }
+    }
+  } else {
+    while (node["return"]) {
+      node = node["return"];
+    }
+  }
+  if (node.tag === HostRoot) {
+    // TODO: Check if this was a nested HostRoot when used with
+    // renderContainerIntoSubtree.
+    return MOUNTED;
+  }
+  // If we didn't hit the root, that means that we're in an disconnected tree
+  // that has been unmounted.
+  return UNMOUNTED;
+}
+
+function isFiberMounted(fiber) {
+  return isFiberMountedImpl(fiber) === MOUNTED;
+}
+
+function isMounted(component) {
+  {
+    var owner = ReactCurrentOwner.current;
+    if (owner !== null && owner.tag === ClassComponent) {
+      var ownerFiber = owner;
+      var instance = ownerFiber.stateNode;
+      !instance._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing isMounted inside its render() function. " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(ownerFiber) || "A component"
+          )
+        : void 0;
+      instance._warnedAboutRefsInRender = true;
+    }
+  }
+
+  var fiber = get$1(component);
+  if (!fiber) {
+    return false;
+  }
+  return isFiberMountedImpl(fiber) === MOUNTED;
+}
+
+function assertIsMounted(fiber) {
+  invariant(
+    isFiberMountedImpl(fiber) === MOUNTED,
+    "Unable to find node on an unmounted component."
+  );
+}
+
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate) {
+    // If there is no alternate, then we only need to check if it is mounted.
+    var state = isFiberMountedImpl(fiber);
+    invariant(
+      state !== UNMOUNTED,
+      "Unable to find node on an unmounted component."
+    );
+    if (state === MOUNTING) {
+      return null;
+    }
+    return fiber;
+  }
+  // If we have two possible branches, we'll walk backwards up to the root
+  // to see what path the root points to. On the way we may hit one of the
+  // special cases and we'll deal with them.
+  var a = fiber;
+  var b = alternate;
+  while (true) {
+    var parentA = a["return"];
+    var parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) {
+      // We're at the root.
+      break;
+    }
+
+    // If both copies of the parent fiber point to the same child, we can
+    // assume that the child is current. This happens when we bailout on low
+    // priority: the bailed out fiber's child reuses the current child.
+    if (parentA.child === parentB.child) {
+      var child = parentA.child;
+      while (child) {
+        if (child === a) {
+          // We've determined that A is the current branch.
+          assertIsMounted(parentA);
+          return fiber;
+        }
+        if (child === b) {
+          // We've determined that B is the current branch.
+          assertIsMounted(parentA);
+          return alternate;
+        }
+        child = child.sibling;
+      }
+      // We should never have an alternate for any mounting node. So the only
+      // way this could possibly happen is if this was unmounted, if at all.
+      invariant(false, "Unable to find node on an unmounted component.");
+    }
+
+    if (a["return"] !== b["return"]) {
+      // The return pointer of A and the return pointer of B point to different
+      // fibers. We assume that return pointers never criss-cross, so A must
+      // belong to the child set of A.return, and B must belong to the child
+      // set of B.return.
+      a = parentA;
+      b = parentB;
+    } else {
+      // The return pointers point to the same fiber. We'll have to use the
+      // default, slow path: scan the child sets of each parent alternate to see
+      // which child belongs to which set.
+      //
+      // Search parent A's child set
+      var didFindChild = false;
+      var _child = parentA.child;
+      while (_child) {
+        if (_child === a) {
+          didFindChild = true;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          didFindChild = true;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!didFindChild) {
+        // Search parent B's child set
+        _child = parentB.child;
+        while (_child) {
+          if (_child === a) {
+            didFindChild = true;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            didFindChild = true;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          didFindChild,
+          "Child was not found in either parent set. This indicates a bug " +
+            "in React related to the return pointer. Please file an issue."
+        );
+      }
+    }
+
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+  // If the root is not a host container, we're in a disconnected tree. I.e.
+  // unmounted.
+  invariant(
+    a.tag === HostRoot,
+    "Unable to find node on an unmounted component."
+  );
+  if (a.stateNode.current === a) {
+    // We've determined that A is the current branch.
+    return fiber;
+  }
+  // Otherwise B has to be current branch.
+  return alternate;
+}
+
+function findCurrentHostFiber(parent) {
+  var currentParent = findCurrentFiberUsingSlowPath(parent);
+  if (!currentParent) {
+    return null;
+  }
+
+  // Next we'll drill down this component to find the first HostComponent/Text.
+  var node = currentParent;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      return node;
+    } else if (node.child) {
+      node.child["return"] = node;
+      node = node.child;
+      continue;
+    }
+    if (node === currentParent) {
+      return null;
+    }
+    while (!node.sibling) {
+      if (!node["return"] || node["return"] === currentParent) {
+        return null;
+      }
+      node = node["return"];
+    }
+    node.sibling["return"] = node["return"];
+    node = node.sibling;
+  }
+  // Flow needs the return null here, but ESLint complains about it.
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
+
+function findCurrentHostFiberWithNoPortals(parent) {
+  var currentParent = findCurrentFiberUsingSlowPath(parent);
+  if (!currentParent) {
+    return null;
+  }
+
+  // Next we'll drill down this component to find the first HostComponent/Text.
+  var node = currentParent;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      return node;
+    } else if (node.child && node.tag !== HostPortal) {
+      node.child["return"] = node;
+      node = node.child;
+      continue;
+    }
+    if (node === currentParent) {
+      return null;
+    }
+    while (!node.sibling) {
+      if (!node["return"] || node["return"] === currentParent) {
+        return null;
+      }
+      node = node["return"];
+    }
+    node.sibling["return"] = node["return"];
+    node = node.sibling;
+  }
+  // Flow needs the return null here, but ESLint complains about it.
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
+
+// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
+// Math.pow(2, 30) - 1
+// 0b111111111111111111111111111111
+var MAX_SIGNED_31_BIT_INT = 1073741823;
+
+// TODO: Use an opaque type once ESLint et al support the syntax
+
+var NoWork = 0;
+var Sync = 1;
+var Never = MAX_SIGNED_31_BIT_INT;
+
+var UNIT_SIZE = 10;
+var MAGIC_NUMBER_OFFSET = 2;
+
+// 1 unit of expiration time represents 10ms.
+function msToExpirationTime(ms) {
+  // Always add an offset so that we don't clash with the magic number for NoWork.
+  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
+}
+
+function expirationTimeToMs(expirationTime) {
+  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
+}
+
+function ceiling(num, precision) {
+  return (((num / precision) | 0) + 1) * precision;
+}
+
+function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
+  return ceiling(
+    currentTime + expirationInMs / UNIT_SIZE,
+    bucketSizeMs / UNIT_SIZE
+  );
+}
+
+var NoContext = 0;
+var AsyncMode = 1;
+var StrictMode = 2;
+
+var hasBadMapPolyfill = void 0;
+
+{
+  hasBadMapPolyfill = false;
+  try {
+    var nonExtensibleObject = Object.preventExtensions({});
+    var testMap = new Map([[nonExtensibleObject, null]]);
+    var testSet = new Set([nonExtensibleObject]);
+    // This is necessary for Rollup to not consider these unused.
+    // https://github.com/rollup/rollup/issues/1771
+    // TODO: we can remove these if Rollup fixes the bug.
+    testMap.set(0, 0);
+    testSet.add(0);
+  } catch (e) {
+    // TODO: Consider warning about bad polyfills
+    hasBadMapPolyfill = true;
+  }
+}
+
+// A Fiber is work on a Component that needs to be done or was done. There can
+// be more than one per component.
+
+var debugCounter = void 0;
+
+{
+  debugCounter = 1;
+}
+
+function FiberNode(tag, pendingProps, key, mode) {
+  // Instance
+  this.tag = tag;
+  this.key = key;
+  this.type = null;
+  this.stateNode = null;
+
+  // Fiber
+  this["return"] = null;
+  this.child = null;
+  this.sibling = null;
+  this.index = 0;
+
+  this.ref = null;
+
+  this.pendingProps = pendingProps;
+  this.memoizedProps = null;
+  this.updateQueue = null;
+  this.memoizedState = null;
+
+  this.mode = mode;
+
+  // Effects
+  this.effectTag = NoEffect;
+  this.nextEffect = null;
+
+  this.firstEffect = null;
+  this.lastEffect = null;
+
+  this.expirationTime = NoWork;
+
+  this.alternate = null;
+
+  {
+    this._debugID = debugCounter++;
+    this._debugSource = null;
+    this._debugOwner = null;
+    this._debugIsCurrentlyTiming = false;
+    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
+      Object.preventExtensions(this);
+    }
+  }
+}
+
+// This is a constructor function, rather than a POJO constructor, still
+// please ensure we do the following:
+// 1) Nobody should add any instance methods on this. Instance methods can be
+//    more difficult to predict when they get optimized and they are almost
+//    never inlined properly in static compilers.
+// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
+//    always know when it is a fiber.
+// 3) We might want to experiment with using numeric keys since they are easier
+//    to optimize in a non-JIT environment.
+// 4) We can easily go from a constructor to a createFiber object literal if that
+//    is faster.
+// 5) It should be easy to port this to a C struct and keep a C implementation
+//    compatible.
+var createFiber = function(tag, pendingProps, key, mode) {
+  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
+  return new FiberNode(tag, pendingProps, key, mode);
+};
+
+function shouldConstruct(Component) {
+  return !!(Component.prototype && Component.prototype.isReactComponent);
+}
+
+// This is used to create an alternate fiber to do work on.
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  if (workInProgress === null) {
+    // We use a double buffering pooling technique because we know that we'll
+    // only ever need at most two versions of a tree. We pool the "other" unused
+    // node that we're free to reuse. This is lazily created to avoid allocating
+    // extra objects for things that are never updated. It also allow us to
+    // reclaim the extra memory if needed.
+    workInProgress = createFiber(
+      current.tag,
+      pendingProps,
+      current.key,
+      current.mode
+    );
+    workInProgress.type = current.type;
+    workInProgress.stateNode = current.stateNode;
+
+    {
+      // DEV-only fields
+      workInProgress._debugID = current._debugID;
+      workInProgress._debugSource = current._debugSource;
+      workInProgress._debugOwner = current._debugOwner;
+    }
+
+    workInProgress.alternate = current;
+    current.alternate = workInProgress;
+  } else {
+    workInProgress.pendingProps = pendingProps;
+
+    // We already have an alternate.
+    // Reset the effect tag.
+    workInProgress.effectTag = NoEffect;
+
+    // The effect list is no longer valid.
+    workInProgress.nextEffect = null;
+    workInProgress.firstEffect = null;
+    workInProgress.lastEffect = null;
+  }
+
+  workInProgress.expirationTime = expirationTime;
+
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+
+  // These will be overridden during the parent's reconciliation
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+
+  return workInProgress;
+}
+
+function createHostRootFiber(isAsync) {
+  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
+  return createFiber(HostRoot, null, null, mode);
+}
+
+function createFiberFromElement(element, mode, expirationTime) {
+  var owner = null;
+  {
+    owner = element._owner;
+  }
+
+  var fiber = void 0;
+  var type = element.type;
+  var key = element.key;
+  var pendingProps = element.props;
+
+  var fiberTag = void 0;
+  if (typeof type === "function") {
+    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
+  } else if (typeof type === "string") {
+    fiberTag = HostComponent;
+  } else {
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          pendingProps.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= AsyncMode | StrictMode;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= StrictMode;
+        break;
+      case REACT_CALL_TYPE:
+        fiberTag = CallComponent;
+        break;
+      case REACT_RETURN_TYPE:
+        fiberTag = ReturnComponent;
+        break;
+      default: {
+        if (typeof type === "object" && type !== null) {
+          switch (type.$$typeof) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = ContextProvider;
+              break;
+            case REACT_CONTEXT_TYPE:
+              // This is a consumer
+              fiberTag = ContextConsumer;
+              break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = ForwardRef;
+              break;
+            default:
+              if (typeof type.tag === "number") {
+                // Currently assumed to be a continuation and therefore is a
+                // fiber already.
+                // TODO: The yield system is currently broken for updates in
+                // some cases. The reified yield stores a fiber, but we don't
+                // know which fiber that is; the current or a workInProgress?
+                // When the continuation gets rendered here we don't know if we
+                // can reuse that fiber or if we need to clone it. There is
+                // probably a clever way to restructure this.
+                fiber = type;
+                fiber.pendingProps = pendingProps;
+                fiber.expirationTime = expirationTime;
+                return fiber;
+              } else {
+                throwOnInvalidElementType(type, owner);
+              }
+              break;
+          }
+        } else {
+          throwOnInvalidElementType(type, owner);
+        }
+      }
+    }
+  }
+
+  fiber = createFiber(fiberTag, pendingProps, key, mode);
+  fiber.type = type;
+  fiber.expirationTime = expirationTime;
+
+  {
+    fiber._debugSource = element._source;
+    fiber._debugOwner = element._owner;
+  }
+
+  return fiber;
+}
+
+function throwOnInvalidElementType(type, owner) {
+  var info = "";
+  {
+    if (
+      type === undefined ||
+      (typeof type === "object" &&
+        type !== null &&
+        Object.keys(type).length === 0)
+    ) {
+      info +=
+        " You likely forgot to export your component from the file " +
+        "it's defined in, or you might have mixed up default and " +
+        "named imports.";
+    }
+    var ownerName = owner ? getComponentName(owner) : null;
+    if (ownerName) {
+      info += "\n\nCheck the render method of `" + ownerName + "`.";
+    }
+  }
+  invariant(
+    false,
+    "Element type is invalid: expected a string (for built-in " +
+      "components) or a class/function (for composite components) " +
+      "but got: %s.%s",
+    type == null ? type : typeof type,
+    info
+  );
+}
+
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  var fiber = createFiber(Fragment, elements, key, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
+}
+
+function createFiberFromText(content, mode, expirationTime) {
+  var fiber = createFiber(HostText, content, null, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
+}
+
+function createFiberFromHostInstanceForDeletion() {
+  var fiber = createFiber(HostComponent, null, null, NoContext);
+  fiber.type = "DELETED";
+  return fiber;
+}
+
+function createFiberFromPortal(portal, mode, expirationTime) {
+  var pendingProps = portal.children !== null ? portal.children : [];
+  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null, // Used by persistent updates
+    implementation: portal.implementation
+  };
+  return fiber;
+}
+
+// Used for stashing WIP properties to replay failed work in DEV.
+function assignFiberPropertiesInDEV(target, source) {
+  if (target === null) {
+    // This Fiber's initial properties will always be overwritten.
+    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
+    target = createFiber(IndeterminateComponent, null, null, NoContext);
+  }
+
+  // This is intentionally written as a list of all properties.
+  // We tried to use Object.assign() instead but this is called in
+  // the hottest path, and Object.assign() was too slow:
+  // https://github.com/facebook/react/issues/12502
+  // This code is DEV-only so size is not a concern.
+
+  target.tag = source.tag;
+  target.key = source.key;
+  target.type = source.type;
+  target.stateNode = source.stateNode;
+  target["return"] = source["return"];
+  target.child = source.child;
+  target.sibling = source.sibling;
+  target.index = source.index;
+  target.ref = source.ref;
+  target.pendingProps = source.pendingProps;
+  target.memoizedProps = source.memoizedProps;
+  target.updateQueue = source.updateQueue;
+  target.memoizedState = source.memoizedState;
+  target.mode = source.mode;
+  target.effectTag = source.effectTag;
+  target.nextEffect = source.nextEffect;
+  target.firstEffect = source.firstEffect;
+  target.lastEffect = source.lastEffect;
+  target.expirationTime = source.expirationTime;
+  target.alternate = source.alternate;
+  target._debugID = source._debugID;
+  target._debugSource = source._debugSource;
+  target._debugOwner = source._debugOwner;
+  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
+  return target;
+}
+
+// TODO: This should be lifted into the renderer.
+
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  // Cyclic construction. This cheats the type system right now because
+  // stateNode is any.
+  var uninitializedFiber = createHostRootFiber(isAsync);
+  var root = {
+    current: uninitializedFiber,
+    containerInfo: containerInfo,
+    pendingChildren: null,
+    pendingCommitExpirationTime: NoWork,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    remainingExpirationTime: NoWork,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  uninitializedFiber.stateNode = root;
+  return root;
+}
+
+var onCommitFiberRoot = null;
+var onCommitFiberUnmount = null;
+var hasLoggedError = false;
+
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {
+      if (true && !hasLoggedError) {
+        hasLoggedError = true;
+        warning(false, "React DevTools encountered an error: %s", err);
+      }
+    }
+  };
+}
+
+function injectInternals(internals) {
+  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
+    // No DevTools
+    return false;
+  }
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled) {
+    // This isn't a real property on the hook, but it can be set to opt out
+    // of DevTools integration and associated warnings and logs.
+    // https://github.com/facebook/react/issues/3877
+    return true;
+  }
+  if (!hook.supportsFiber) {
+    {
+      warning(
+        false,
+        "The installed version of React DevTools is too old and will not work " +
+          "with the current version of React. Please update React DevTools. " +
+          "https://fb.me/react-devtools"
+      );
+    }
+    // DevTools exists, even though it doesn't support Fiber.
+    return true;
+  }
+  try {
+    var rendererID = hook.inject(internals);
+    // We have successfully injected, so now it is safe to set up hooks.
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {
+    // Catch all errors because it is unsafe to throw during initialization.
+    {
+      warning(false, "React DevTools encountered an error: %s.", err);
+    }
+  }
+  // DevTools exists
+  return true;
+}
+
+function onCommitRoot(root) {
+  if (typeof onCommitFiberRoot === "function") {
+    onCommitFiberRoot(root);
+  }
+}
+
+function onCommitUnmount(fiber) {
+  if (typeof onCommitFiberUnmount === "function") {
+    onCommitFiberUnmount(fiber);
+  }
+}
+
+var describeComponentFrame = function(name, source, ownerName) {
+  return (
+    "\n    in " +
+    (name || "Unknown") +
+    (source
+      ? " (at " +
+        source.fileName.replace(/^.*[\\\/]/, "") +
+        ":" +
+        source.lineNumber +
+        ")"
+      : ownerName ? " (created by " + ownerName + ")" : "")
+  );
+};
+
+function describeFiber(fiber) {
+  switch (fiber.tag) {
+    case IndeterminateComponent:
+    case FunctionalComponent:
+    case ClassComponent:
+    case HostComponent:
+      var owner = fiber._debugOwner;
+      var source = fiber._debugSource;
+      var name = getComponentName(fiber);
+      var ownerName = null;
+      if (owner) {
+        ownerName = getComponentName(owner);
+      }
+      return describeComponentFrame(name, source, ownerName);
+    default:
+      return "";
+  }
+}
+
+// This function can only be called with a work-in-progress fiber and
+// only during begin or complete phase. Do not call it under any other
+// circumstances.
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  var node = workInProgress;
+  do {
+    info += describeFiber(node);
+    // Otherwise this return pointer might point to the wrong tree:
+    node = node["return"];
+  } while (node);
+  return info;
+}
+
+/**
+ * Forked from fbjs/warning:
+ * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
+ *
+ * Only change is we use console.warn instead of console.error,
+ * and do nothing when 'console' is not supported.
+ * This really simplifies the code.
+ * ---
+ * Similar to invariant but only logs a warning if the condition is not met.
+ * This can be used to log issues in development environments in critical
+ * paths. Removing the logging code for production environments will keep the
+ * same logic and follow the same code paths.
+ */
+
+var lowPriorityWarning = function() {};
+
+{
+  var printWarning = function(format) {
+    for (
+      var _len = arguments.length,
+        args = Array(_len > 1 ? _len - 1 : 0),
+        _key = 1;
+      _key < _len;
+      _key++
+    ) {
+      args[_key - 1] = arguments[_key];
+    }
+
+    var argIndex = 0;
+    var message =
+      "Warning: " +
+      format.replace(/%s/g, function() {
+        return args[argIndex++];
+      });
+    if (typeof console !== "undefined") {
+      console.warn(message);
+    }
+    try {
+      // --- Welcome to debugging React ---
+      // This error was thrown as a convenience so that you can use this stack
+      // to find the callsite that caused this warning to fire.
+      throw new Error(message);
+    } catch (x) {}
+  };
+
+  lowPriorityWarning = function(condition, format) {
+    if (format === undefined) {
+      throw new Error(
+        "`warning(condition, format, ...args)` requires a warning " +
+          "message argument"
+      );
+    }
+    if (!condition) {
+      for (
+        var _len2 = arguments.length,
+          args = Array(_len2 > 2 ? _len2 - 2 : 0),
+          _key2 = 2;
+        _key2 < _len2;
+        _key2++
+      ) {
+        args[_key2 - 2] = arguments[_key2];
+      }
+
+      printWarning.apply(undefined, [format].concat(args));
+    }
+  };
+}
+
+var lowPriorityWarning$1 = lowPriorityWarning;
+
+var ReactStrictModeWarnings = {
+  discardPendingWarnings: function() {},
+  flushPendingDeprecationWarnings: function() {},
+  flushPendingUnsafeLifecycleWarnings: function() {},
+  recordDeprecationWarnings: function(fiber, instance) {},
+  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
+};
+
+{
+  var LIFECYCLE_SUGGESTIONS = {
+    UNSAFE_componentWillMount: "componentDidMount",
+    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
+    UNSAFE_componentWillUpdate: "componentDidUpdate"
+  };
+
+  var pendingComponentWillMountWarnings = [];
+  var pendingComponentWillReceivePropsWarnings = [];
+  var pendingComponentWillUpdateWarnings = [];
+  var pendingUnsafeLifecycleWarnings = new Map();
+
+  // Tracks components we have already warned about.
+  var didWarnAboutDeprecatedLifecycles = new Set();
+  var didWarnAboutUnsafeLifecycles = new Set();
+
+  var setToSortedString = function(set) {
+    var array = [];
+    set.forEach(function(value) {
+      array.push(value);
+    });
+    return array.sort().join(", ");
+  };
+
+  ReactStrictModeWarnings.discardPendingWarnings = function() {
+    pendingComponentWillMountWarnings = [];
+    pendingComponentWillReceivePropsWarnings = [];
+    pendingComponentWillUpdateWarnings = [];
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
+
+  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
+    pendingUnsafeLifecycleWarnings.forEach(function(
+      lifecycleWarningsMap,
+      strictRoot
+    ) {
+      var lifecyclesWarningMesages = [];
+
+      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
+        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
+        if (lifecycleWarnings.length > 0) {
+          var componentNames = new Set();
+          lifecycleWarnings.forEach(function(fiber) {
+            componentNames.add(getComponentName(fiber) || "Component");
+            didWarnAboutUnsafeLifecycles.add(fiber.type);
+          });
+
+          var formatted = lifecycle.replace("UNSAFE_", "");
+          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
+          var sortedComponentNames = setToSortedString(componentNames);
+
+          lifecyclesWarningMesages.push(
+            formatted +
+              ": Please update the following components to use " +
+              (suggestion + " instead: " + sortedComponentNames)
+          );
+        }
+      });
+
+      if (lifecyclesWarningMesages.length > 0) {
+        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+          strictRoot
+        );
+
+        warning(
+          false,
+          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
+            "\n\n%s" +
+            "\n\nLearn more about this warning here:" +
+            "\nhttps://fb.me/react-strict-mode-warnings",
+          strictRootComponentStack,
+          lifecyclesWarningMesages.join("\n\n")
+        );
+      }
+    });
+
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
+
+  var getStrictRoot = function(fiber) {
+    var maybeStrictRoot = null;
+
+    while (fiber !== null) {
+      if (fiber.mode & StrictMode) {
+        maybeStrictRoot = fiber;
+      }
+
+      fiber = fiber["return"];
+    }
+
+    return maybeStrictRoot;
+  };
+
+  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
+    if (pendingComponentWillMountWarnings.length > 0) {
+      var uniqueNames = new Set();
+      pendingComponentWillMountWarnings.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var sortedNames = setToSortedString(uniqueNames);
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillMount is deprecated and will be removed in the next major version. " +
+          "Use componentDidMount instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillMount." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        sortedNames
+      );
+
+      pendingComponentWillMountWarnings = [];
+    }
+
+    if (pendingComponentWillReceivePropsWarnings.length > 0) {
+      var _uniqueNames = new Set();
+      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
+        _uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var _sortedNames = setToSortedString(_uniqueNames);
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
+          "Use static getDerivedStateFromProps instead." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames
+      );
+
+      pendingComponentWillReceivePropsWarnings = [];
+    }
+
+    if (pendingComponentWillUpdateWarnings.length > 0) {
+      var _uniqueNames2 = new Set();
+      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
+        _uniqueNames2.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var _sortedNames2 = setToSortedString(_uniqueNames2);
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillUpdate is deprecated and will be removed in the next major version. " +
+          "Use componentDidUpdate instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillUpdate." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames2
+      );
+
+      pendingComponentWillUpdateWarnings = [];
+    }
+  };
+
+  ReactStrictModeWarnings.recordDeprecationWarnings = function(
+    fiber,
+    instance
+  ) {
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
+      return;
+    }
+
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillMountWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" &&
+      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillReceivePropsWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillUpdate === "function" &&
+      instance.componentWillUpdate.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillUpdateWarnings.push(fiber);
+    }
+  };
+
+  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = getStrictRoot(fiber);
+
+    // Dedup strategy: Warn once per component.
+    // This is difficult to track any other way since component names
+    // are often vague and are likely to collide between 3rd party libraries.
+    // An expand property is probably okay to use here since it's DEV-only,
+    // and will only be set in the event of serious warnings.
+    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+      return;
+    }
+
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    // Note that it is sufficient to check for the presence of a
+    // single lifecycle, componentWillMount, with the polyfill flag.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning === true
+    ) {
+      return;
+    }
+
+    var warningsForRoot = void 0;
+    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
+      warningsForRoot = {
+        UNSAFE_componentWillMount: [],
+        UNSAFE_componentWillReceiveProps: [],
+        UNSAFE_componentWillUpdate: []
+      };
+
+      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
+    } else {
+      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
+    }
+
+    var unsafeLifecycles = [];
+    if (
+      typeof instance.componentWillMount === "function" ||
+      typeof instance.UNSAFE_componentWillMount === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillMount");
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" ||
+      typeof instance.UNSAFE_componentWillReceiveProps === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    }
+    if (
+      typeof instance.componentWillUpdate === "function" ||
+      typeof instance.UNSAFE_componentWillUpdate === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
+    }
+
+    if (unsafeLifecycles.length > 0) {
+      unsafeLifecycles.forEach(function(lifecycle) {
+        warningsForRoot[lifecycle].push(fiber);
+      });
+    }
+  };
+}
+
+var debugRenderPhaseSideEffects = false;
+var debugRenderPhaseSideEffectsForStrictMode = false;
+var enableUserTimingAPI = true;
+var enableGetDerivedStateFromCatch = false;
+var warnAboutDeprecatedLifecycles = false;
+var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
+
+// React Fabric uses persistent reconciler.
+var enableMutatingReconciler = false;
+var enableNoopReconciler = false;
+var enablePersistentReconciler = true;
+
+// Only used in www builds.
+
+function getCurrentFiberOwnerName() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    var owner = fiber._debugOwner;
+    if (owner !== null && typeof owner !== "undefined") {
+      return getComponentName(owner);
+    }
+  }
+  return null;
+}
+
+function getCurrentFiberStackAddendum() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    // Safe because if current fiber exists, we are reconciling,
+    // and it is guaranteed to be the work-in-progress version.
+    return getStackAddendumByWorkInProgressFiber(fiber);
+  }
+  return null;
+}
+
+function resetCurrentFiber() {
+  ReactDebugCurrentFrame.getCurrentStack = null;
+  ReactDebugCurrentFiber.current = null;
+  ReactDebugCurrentFiber.phase = null;
+}
+
+function setCurrentFiber(fiber) {
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
+  ReactDebugCurrentFiber.current = fiber;
+  ReactDebugCurrentFiber.phase = null;
+}
+
+function setCurrentPhase(phase) {
+  ReactDebugCurrentFiber.phase = phase;
+}
+
+var ReactDebugCurrentFiber = {
+  current: null,
+  phase: null,
+  resetCurrentFiber: resetCurrentFiber,
+  setCurrentFiber: setCurrentFiber,
+  setCurrentPhase: setCurrentPhase,
+  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
+};
+
+// Prefix measurements so that it's possible to filter them.
+// Longer prefixes are hard to read in DevTools.
+var reactEmoji = "\u269B";
+var warningEmoji = "\u26D4";
+var supportsUserTiming =
+  typeof performance !== "undefined" &&
+  typeof performance.mark === "function" &&
+  typeof performance.clearMarks === "function" &&
+  typeof performance.measure === "function" &&
+  typeof performance.clearMeasures === "function";
+
+// Keep track of current fiber so that we know the path to unwind on pause.
+// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
+var currentFiber = null;
+// If we're in the middle of user code, which fiber and method is it?
+// Reusing `currentFiber` would be confusing for this because user code fiber
+// can change during commit phase too, but we don't need to unwind it (since
+// lifecycles in the commit phase don't resemble a tree).
+var currentPhase = null;
+var currentPhaseFiber = null;
+// Did lifecycle hook schedule an update? This is often a performance problem,
+// so we will keep track of it, and include it in the report.
+// Track commits caused by cascading updates.
+var isCommitting = false;
+var hasScheduledUpdateInCurrentCommit = false;
+var hasScheduledUpdateInCurrentPhase = false;
+var commitCountInCurrentWorkLoop = 0;
+var effectCountInCurrentCommit = 0;
+var isWaitingForCallback = false;
+// During commits, we only show a measurement once per method name
+// to avoid stretch the commit phase with measurement overhead.
+var labelsInCurrentCommit = new Set();
+
+var formatMarkName = function(markName) {
+  return reactEmoji + " " + markName;
+};
+
+var formatLabel = function(label, warning$$1) {
+  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
+  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
+  return "" + prefix + label + suffix;
+};
+
+var beginMark = function(markName) {
+  performance.mark(formatMarkName(markName));
+};
+
+var clearMark = function(markName) {
+  performance.clearMarks(formatMarkName(markName));
+};
+
+var endMark = function(label, markName, warning$$1) {
+  var formattedMarkName = formatMarkName(markName);
+  var formattedLabel = formatLabel(label, warning$$1);
+  try {
+    performance.measure(formattedLabel, formattedMarkName);
+  } catch (err) {}
+  // If previous mark was missing for some reason, this will throw.
+  // This could only happen if React crashed in an unexpected place earlier.
+  // Don't pile on with more errors.
+
+  // Clear marks immediately to avoid growing buffer.
+  performance.clearMarks(formattedMarkName);
+  performance.clearMeasures(formattedLabel);
+};
+
+var getFiberMarkName = function(label, debugID) {
+  return label + " (#" + debugID + ")";
+};
+
+var getFiberLabel = function(componentName, isMounted, phase) {
+  if (phase === null) {
+    // These are composite component total time measurements.
+    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
+  } else {
+    // Composite component methods.
+    return componentName + "." + phase;
+  }
+};
+
+var beginFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+
+  if (isCommitting && labelsInCurrentCommit.has(label)) {
+    // During the commit phase, we don't show duplicate labels because
+    // there is a fixed overhead for every measurement, and we don't
+    // want to stretch the commit phase beyond necessary.
+    return false;
+  }
+  labelsInCurrentCommit.add(label);
+
+  var markName = getFiberMarkName(label, debugID);
+  beginMark(markName);
+  return true;
+};
+
+var clearFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  clearMark(markName);
+};
+
+var endFiberMark = function(fiber, phase, warning$$1) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  endMark(label, markName, warning$$1);
+};
+
+var shouldIgnoreFiber = function(fiber) {
+  // Host components should be skipped in the timeline.
+  // We could check typeof fiber.type, but does this work with RN?
+  switch (fiber.tag) {
+    case HostRoot:
+    case HostComponent:
+    case HostText:
+    case HostPortal:
+    case CallComponent:
+    case ReturnComponent:
+    case Fragment:
+    case ContextProvider:
+    case ContextConsumer:
+    case Mode:
+      return true;
+    default:
+      return false;
+  }
+};
+
+var clearPendingPhaseMeasurement = function() {
+  if (currentPhase !== null && currentPhaseFiber !== null) {
+    clearFiberMark(currentPhaseFiber, currentPhase);
+  }
+  currentPhaseFiber = null;
+  currentPhase = null;
+  hasScheduledUpdateInCurrentPhase = false;
+};
+
+var pauseTimers = function() {
+  // Stops all currently active measurements so that they can be resumed
+  // if we continue in a later deferred loop from the same unit of work.
+  var fiber = currentFiber;
+  while (fiber) {
+    if (fiber._debugIsCurrentlyTiming) {
+      endFiberMark(fiber, null, null);
+    }
+    fiber = fiber["return"];
+  }
+};
+
+var resumeTimersRecursively = function(fiber) {
+  if (fiber["return"] !== null) {
+    resumeTimersRecursively(fiber["return"]);
+  }
+  if (fiber._debugIsCurrentlyTiming) {
+    beginFiberMark(fiber, null);
+  }
+};
+
+var resumeTimers = function() {
+  // Resumes all measurements that were active during the last deferred loop.
+  if (currentFiber !== null) {
+    resumeTimersRecursively(currentFiber);
+  }
+};
+
+function recordEffect() {
+  if (enableUserTimingAPI) {
+    effectCountInCurrentCommit++;
+  }
+}
+
+function recordScheduleUpdate() {
+  if (enableUserTimingAPI) {
+    if (isCommitting) {
+      hasScheduledUpdateInCurrentCommit = true;
+    }
+    if (
+      currentPhase !== null &&
+      currentPhase !== "componentWillMount" &&
+      currentPhase !== "componentWillReceiveProps"
+    ) {
+      hasScheduledUpdateInCurrentPhase = true;
+    }
+  }
+}
+
+function startRequestCallbackTimer() {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming && !isWaitingForCallback) {
+      isWaitingForCallback = true;
+      beginMark("(Waiting for async callback...)");
+    }
+  }
+}
+
+function stopRequestCallbackTimer(didExpire, expirationTime) {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming) {
+      isWaitingForCallback = false;
+      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
+      endMark(
+        "(Waiting for async callback... will force flush in " +
+          expirationTime +
+          " ms)",
+        "(Waiting for async callback...)",
+        warning$$1
+      );
+    }
+  }
+}
+
+function startWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, this is the fiber to unwind from.
+    currentFiber = fiber;
+    if (!beginFiberMark(fiber, null)) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = true;
+  }
+}
+
+function cancelWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // Remember we shouldn't complete measurement for this fiber.
+    // Otherwise flamechart will be deep even for small updates.
+    fiber._debugIsCurrentlyTiming = false;
+    clearFiberMark(fiber, null);
+  }
+}
+
+function stopWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber["return"];
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = false;
+    endFiberMark(fiber, null, null);
+  }
+}
+
+function stopFailedWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber["return"];
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = false;
+    var warning$$1 = "An error was thrown inside this error boundary";
+    endFiberMark(fiber, null, warning$$1);
+  }
+}
+
+function startPhaseTimer(fiber, phase) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    clearPendingPhaseMeasurement();
+    if (!beginFiberMark(fiber, phase)) {
+      return;
+    }
+    currentPhaseFiber = fiber;
+    currentPhase = phase;
+  }
+}
+
+function stopPhaseTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    if (currentPhase !== null && currentPhaseFiber !== null) {
+      var warning$$1 = hasScheduledUpdateInCurrentPhase
+        ? "Scheduled a cascading update"
+        : null;
+      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
+    }
+    currentPhase = null;
+    currentPhaseFiber = null;
+  }
+}
+
+function startWorkLoopTimer(nextUnitOfWork) {
+  if (enableUserTimingAPI) {
+    currentFiber = nextUnitOfWork;
+    if (!supportsUserTiming) {
+      return;
+    }
+    commitCountInCurrentWorkLoop = 0;
+    // This is top level call.
+    // Any other measurements are performed within.
+    beginMark("(React Tree Reconciliation)");
+    // Resume any measurements that were in progress during the last loop.
+    resumeTimers();
+  }
+}
+
+function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var warning$$1 = null;
+    if (interruptedBy !== null) {
+      if (interruptedBy.tag === HostRoot) {
+        warning$$1 = "A top-level update interrupted the previous render";
+      } else {
+        var componentName = getComponentName(interruptedBy) || "Unknown";
+        warning$$1 =
+          "An update to " + componentName + " interrupted the previous render";
+      }
+    } else if (commitCountInCurrentWorkLoop > 1) {
+      warning$$1 = "There were cascading updates";
+    }
+    commitCountInCurrentWorkLoop = 0;
+    var label = didCompleteRoot
+      ? "(React Tree Reconciliation: Completed Root)"
+      : "(React Tree Reconciliation: Yielded)";
+    // Pause any measurements until the next loop.
+    pauseTimers();
+    endMark(label, "(React Tree Reconciliation)", warning$$1);
+  }
+}
+
+function startCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    isCommitting = true;
+    hasScheduledUpdateInCurrentCommit = false;
+    labelsInCurrentCommit.clear();
+    beginMark("(Committing Changes)");
+  }
+}
+
+function stopCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+
+    var warning$$1 = null;
+    if (hasScheduledUpdateInCurrentCommit) {
+      warning$$1 = "Lifecycle hook scheduled a cascading update";
+    } else if (commitCountInCurrentWorkLoop > 0) {
+      warning$$1 = "Caused by a cascading update in earlier commit";
+    }
+    hasScheduledUpdateInCurrentCommit = false;
+    commitCountInCurrentWorkLoop++;
+    isCommitting = false;
+    labelsInCurrentCommit.clear();
+
+    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
+  }
+}
+
+function startCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Snapshot Effects)");
+  }
+}
+
+function stopCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Snapshot Effects: " + count + " Total)",
+      "(Committing Snapshot Effects)",
+      null
+    );
+  }
+}
+
+function startCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Host Effects)");
+  }
+}
+
+function stopCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Host Effects: " + count + " Total)",
+      "(Committing Host Effects)",
+      null
+    );
+  }
+}
+
+function startCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Calling Lifecycle Methods)");
+  }
+}
+
+function stopCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Calling Lifecycle Methods: " + count + " Total)",
+      "(Calling Lifecycle Methods)",
+      null
+    );
+  }
+}
+
+var didWarnUpdateInsideUpdate = void 0;
+
+{
+  didWarnUpdateInsideUpdate = false;
+}
+
+// Callbacks are not validated until invocation
+
+// Singly linked-list of updates. When an update is scheduled, it is added to
+// the queue of the current fiber and the work-in-progress fiber. The two queues
+// are separate but they share a persistent structure.
+//
+// During reconciliation, updates are removed from the work-in-progress fiber,
+// but they remain on the current fiber. That ensures that if a work-in-progress
+// is aborted, the aborted updates are recovered by cloning from current.
+//
+// The work-in-progress queue is always a subset of the current queue.
+//
+// When the tree is committed, the work-in-progress becomes the current.
+
+function createUpdateQueue(baseState) {
+  var queue = {
+    baseState: baseState,
+    expirationTime: NoWork,
+    first: null,
+    last: null,
+    callbackList: null,
+    hasForceUpdate: false,
+    isInitialized: false,
+    capturedValues: null
+  };
+  {
+    queue.isProcessing = false;
+  }
+  return queue;
+}
+
+function insertUpdateIntoQueue(queue, update) {
+  // Append the update to the end of the list.
+  if (queue.last === null) {
+    // Queue is empty
+    queue.first = queue.last = update;
+  } else {
+    queue.last.next = update;
+    queue.last = update;
+  }
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > update.expirationTime
+  ) {
+    queue.expirationTime = update.expirationTime;
+  }
+}
+
+var q1 = void 0;
+var q2 = void 0;
+function ensureUpdateQueues(fiber) {
+  q1 = q2 = null;
+  // We'll have at least one and at most two distinct update queues.
+  var alternateFiber = fiber.alternate;
+  var queue1 = fiber.updateQueue;
+  if (queue1 === null) {
+    // TODO: We don't know what the base state will be until we begin work.
+    // It depends on which fiber is the next current. Initialize with an empty
+    // base state, then set to the memoizedState when rendering. Not super
+    // happy with this approach.
+    queue1 = fiber.updateQueue = createUpdateQueue(null);
+  }
+
+  var queue2 = void 0;
+  if (alternateFiber !== null) {
+    queue2 = alternateFiber.updateQueue;
+    if (queue2 === null) {
+      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
+    }
+  } else {
+    queue2 = null;
+  }
+  queue2 = queue2 !== queue1 ? queue2 : null;
+
+  // Use module variables instead of returning a tuple
+  q1 = queue1;
+  q2 = queue2;
+}
+
+function insertUpdateIntoFiber(fiber, update) {
+  ensureUpdateQueues(fiber);
+  var queue1 = q1;
+  var queue2 = q2;
+
+  // Warn if an update is scheduled from inside an updater function.
+  {
+    if (
+      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
+      !didWarnUpdateInsideUpdate
+    ) {
+      warning(
+        false,
+        "An update (setState, replaceState, or forceUpdate) was scheduled " +
+          "from inside an update function. Update functions should be pure, " +
+          "with zero side-effects. Consider using componentDidUpdate or a " +
+          "callback."
+      );
+      didWarnUpdateInsideUpdate = true;
+    }
+  }
+
+  // If there's only one queue, add the update to that queue and exit.
+  if (queue2 === null) {
+    insertUpdateIntoQueue(queue1, update);
+    return;
+  }
+
+  // If either queue is empty, we need to add to both queues.
+  if (queue1.last === null || queue2.last === null) {
+    insertUpdateIntoQueue(queue1, update);
+    insertUpdateIntoQueue(queue2, update);
+    return;
+  }
+
+  // If both lists are not empty, the last update is the same for both lists
+  // because of structural sharing. So, we should only append to one of
+  // the lists.
+  insertUpdateIntoQueue(queue1, update);
+  // But we still need to update the `last` pointer of queue2.
+  queue2.last = update;
+}
+
+function getUpdateExpirationTime(fiber) {
+  switch (fiber.tag) {
+    case HostRoot:
+    case ClassComponent:
+      var updateQueue = fiber.updateQueue;
+      if (updateQueue === null) {
+        return NoWork;
+      }
+      return updateQueue.expirationTime;
+    default:
+      return NoWork;
+  }
+}
+
+function getStateFromUpdate(update, instance, prevState, props) {
+  var partialState = update.partialState;
+  if (typeof partialState === "function") {
+    return partialState.call(instance, prevState, props);
+  } else {
+    return partialState;
+  }
+}
+
+function processUpdateQueue(
+  current,
+  workInProgress,
+  queue,
+  instance,
+  props,
+  renderExpirationTime
+) {
+  if (current !== null && current.updateQueue === queue) {
+    // We need to create a work-in-progress queue, by cloning the current queue.
+    var currentQueue = queue;
+    queue = workInProgress.updateQueue = {
+      baseState: currentQueue.baseState,
+      expirationTime: currentQueue.expirationTime,
+      first: currentQueue.first,
+      last: currentQueue.last,
+      isInitialized: currentQueue.isInitialized,
+      capturedValues: currentQueue.capturedValues,
+      // These fields are no longer valid because they were already committed.
+      // Reset them.
+      callbackList: null,
+      hasForceUpdate: false
+    };
+  }
+
+  {
+    // Set this flag so we can warn if setState is called inside the update
+    // function of another setState.
+    queue.isProcessing = true;
+  }
+
+  // Reset the remaining expiration time. If we skip over any updates, we'll
+  // increase this accordingly.
+  queue.expirationTime = NoWork;
+
+  // TODO: We don't know what the base state will be until we begin work.
+  // It depends on which fiber is the next current. Initialize with an empty
+  // base state, then set to the memoizedState when rendering. Not super
+  // happy with this approach.
+  var state = void 0;
+  if (queue.isInitialized) {
+    state = queue.baseState;
+  } else {
+    state = queue.baseState = workInProgress.memoizedState;
+    queue.isInitialized = true;
+  }
+  var dontMutatePrevState = true;
+  var update = queue.first;
+  var didSkip = false;
+  while (update !== null) {
+    var updateExpirationTime = update.expirationTime;
+    if (updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      var remainingExpirationTime = queue.expirationTime;
+      if (
+        remainingExpirationTime === NoWork ||
+        remainingExpirationTime > updateExpirationTime
+      ) {
+        // Update the remaining expiration time.
+        queue.expirationTime = updateExpirationTime;
+      }
+      if (!didSkip) {
+        didSkip = true;
+        queue.baseState = state;
+      }
+      // Continue to the next update.
+      update = update.next;
+      continue;
+    }
+
+    // This update does have sufficient priority.
+
+    // If no previous updates were skipped, drop this update from the queue by
+    // advancing the head of the list.
+    if (!didSkip) {
+      queue.first = update.next;
+      if (queue.first === null) {
+        queue.last = null;
+      }
+    }
+
+    // Invoke setState callback an extra time to help detect side-effects.
+    // Ignore the return value in this case.
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      getStateFromUpdate(update, instance, state, props);
+    }
+
+    // Process the update
+    var _partialState = void 0;
+    if (update.isReplace) {
+      state = getStateFromUpdate(update, instance, state, props);
+      dontMutatePrevState = true;
+    } else {
+      _partialState = getStateFromUpdate(update, instance, state, props);
+      if (_partialState) {
+        if (dontMutatePrevState) {
+          // $FlowFixMe: Idk how to type this properly.
+          state = Object.assign({}, state, _partialState);
+        } else {
+          state = Object.assign(state, _partialState);
+        }
+        dontMutatePrevState = false;
+      }
+    }
+    if (update.isForced) {
+      queue.hasForceUpdate = true;
+    }
+    if (update.callback !== null) {
+      // Append to list of callbacks.
+      var _callbackList = queue.callbackList;
+      if (_callbackList === null) {
+        _callbackList = queue.callbackList = [];
+      }
+      _callbackList.push(update);
+    }
+    if (update.capturedValue !== null) {
+      var _capturedValues = queue.capturedValues;
+      if (_capturedValues === null) {
+        queue.capturedValues = [update.capturedValue];
+      } else {
+        _capturedValues.push(update.capturedValue);
+      }
+    }
+    update = update.next;
+  }
+
+  if (queue.callbackList !== null) {
+    workInProgress.effectTag |= Callback;
+  } else if (
+    queue.first === null &&
+    !queue.hasForceUpdate &&
+    queue.capturedValues === null
+  ) {
+    // The queue is empty. We can reset it.
+    workInProgress.updateQueue = null;
+  }
+
+  if (!didSkip) {
+    didSkip = true;
+    queue.baseState = state;
+  }
+
+  {
+    // No longer processing.
+    queue.isProcessing = false;
+  }
+
+  return state;
+}
+
+function commitCallbacks(queue, context) {
+  var callbackList = queue.callbackList;
+  if (callbackList === null) {
+    return;
+  }
+  // Set the list to null to make sure they don't get called more than once.
+  queue.callbackList = null;
+  for (var i = 0; i < callbackList.length; i++) {
+    var update = callbackList[i];
+    var _callback = update.callback;
+    // This update might be processed again. Clear the callback so it's only
+    // called once.
+    update.callback = null;
+    invariant(
+      typeof _callback === "function",
+      "Invalid argument passed as callback. Expected a function. Instead " +
+        "received: %s",
+      _callback
+    );
+    _callback.call(context);
+  }
+}
+
+var fakeInternalInstance = {};
+var isArray = Array.isArray;
+
+var didWarnAboutStateAssignmentForComponent = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
+var didWarnAboutUninitializedState = void 0;
+var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
+var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
+var warnOnInvalidCallback = void 0;
+
+{
+  didWarnAboutStateAssignmentForComponent = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
+  didWarnAboutUninitializedState = new Set();
+  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
+  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
+
+  var didWarnOnInvalidCallback = new Set();
+
+  warnOnInvalidCallback = function(callback, callerName) {
+    if (callback === null || typeof callback === "function") {
+      return;
+    }
+    var key = callerName + "_" + callback;
+    if (!didWarnOnInvalidCallback.has(key)) {
+      didWarnOnInvalidCallback.add(key);
+      warning(
+        false,
+        "%s(...): Expected the last optional `callback` argument to be a " +
+          "function. Instead received: %s.",
+        callerName,
+        callback
+      );
+    }
+  };
+
+  // This is so gross but it's at least non-critical and can be removed if
+  // it causes problems. This is meant to give a nicer error message for
+  // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
+  // ...)) which otherwise throws a "_processChildContext is not a function"
+  // exception.
+  Object.defineProperty(fakeInternalInstance, "_processChildContext", {
+    enumerable: false,
+    value: function() {
+      invariant(
+        false,
+        "_processChildContext is not available in React 16+. This likely " +
+          "means you have multiple copies of React and are attempting to nest " +
+          "a React 15 tree inside a React 16 tree using " +
+          "unstable_renderSubtreeIntoContainer, which isn't supported. Try " +
+          "to make sure you have only one copy of React (and ideally, switch " +
+          "to ReactDOM.createPortal)."
+      );
+    }
+  });
+  Object.freeze(fakeInternalInstance);
+}
+function callGetDerivedStateFromCatch(ctor, capturedValues) {
+  var resultState = {};
+  for (var i = 0; i < capturedValues.length; i++) {
+    var capturedValue = capturedValues[i];
+    var error = capturedValue.value;
+    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
+    if (partialState !== null && partialState !== undefined) {
+      Object.assign(resultState, partialState);
+    }
+  }
+  return resultState;
+}
+
+var ReactFiberClassComponent = function(
+  legacyContext,
+  scheduleWork,
+  computeExpirationForFiber,
+  memoizeProps,
+  memoizeState
+) {
+  var cacheContext = legacyContext.cacheContext,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    isContextConsumer = legacyContext.isContextConsumer,
+    hasContextChanged = legacyContext.hasContextChanged;
+
+  // Class component state updater
+
+  var updater = {
+    isMounted: isMounted,
+    enqueueSetState: function(instance, partialState, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "setState");
+      }
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: partialState,
+        callback: callback,
+        isReplace: false,
+        isForced: false,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
+      scheduleWork(fiber, expirationTime);
+    },
+    enqueueReplaceState: function(instance, state, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "replaceState");
+      }
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: state,
+        callback: callback,
+        isReplace: true,
+        isForced: false,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
+      scheduleWork(fiber, expirationTime);
+    },
+    enqueueForceUpdate: function(instance, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "forceUpdate");
+      }
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: null,
+        callback: callback,
+        isReplace: false,
+        isForced: true,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
+      scheduleWork(fiber, expirationTime);
+    }
+  };
+
+  function checkShouldComponentUpdate(
+    workInProgress,
+    oldProps,
+    newProps,
+    oldState,
+    newState,
+    newContext
+  ) {
+    if (
+      oldProps === null ||
+      (workInProgress.updateQueue !== null &&
+        workInProgress.updateQueue.hasForceUpdate)
+    ) {
+      // If the workInProgress already has an Update effect, return true
+      return true;
+    }
+
+    var instance = workInProgress.stateNode;
+    var ctor = workInProgress.type;
+    if (typeof instance.shouldComponentUpdate === "function") {
+      startPhaseTimer(workInProgress, "shouldComponentUpdate");
+      var shouldUpdate = instance.shouldComponentUpdate(
+        newProps,
+        newState,
+        newContext
+      );
+      stopPhaseTimer();
+
+      {
+        !(shouldUpdate !== undefined)
+          ? warning(
+              false,
+              "%s.shouldComponentUpdate(): Returned undefined instead of a " +
+                "boolean value. Make sure to return true or false.",
+              getComponentName(workInProgress) || "Component"
+            )
+          : void 0;
+      }
+
+      return shouldUpdate;
+    }
+
+    if (ctor.prototype && ctor.prototype.isPureReactComponent) {
+      return (
+        !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+      );
+    }
+
+    return true;
+  }
+
+  function checkClassInstance(workInProgress) {
+    var instance = workInProgress.stateNode;
+    var type = workInProgress.type;
+    {
+      var name = getComponentName(workInProgress) || "Component";
+      var renderPresent = instance.render;
+
+      if (!renderPresent) {
+        if (type.prototype && typeof type.prototype.render === "function") {
+          warning(
+            false,
+            "%s(...): No `render` method found on the returned component " +
+              "instance: did you accidentally return an object from the constructor?",
+            name
+          );
+        } else {
+          warning(
+            false,
+            "%s(...): No `render` method found on the returned component " +
+              "instance: you may have forgotten to define `render`.",
+            name
+          );
+        }
+      }
+
+      var noGetInitialStateOnES6 =
+        !instance.getInitialState ||
+        instance.getInitialState.isReactClassApproved ||
+        instance.state;
+      !noGetInitialStateOnES6
+        ? warning(
+            false,
+            "getInitialState was defined on %s, a plain JavaScript class. " +
+              "This is only supported for classes created using React.createClass. " +
+              "Did you mean to define a state property instead?",
+            name
+          )
+        : void 0;
+      var noGetDefaultPropsOnES6 =
+        !instance.getDefaultProps ||
+        instance.getDefaultProps.isReactClassApproved;
+      !noGetDefaultPropsOnES6
+        ? warning(
+            false,
+            "getDefaultProps was defined on %s, a plain JavaScript class. " +
+              "This is only supported for classes created using React.createClass. " +
+              "Use a static property to define defaultProps instead.",
+            name
+          )
+        : void 0;
+      var noInstancePropTypes = !instance.propTypes;
+      !noInstancePropTypes
+        ? warning(
+            false,
+            "propTypes was defined as an instance property on %s. Use a static " +
+              "property to define propTypes instead.",
+            name
+          )
+        : void 0;
+      var noInstanceContextTypes = !instance.contextTypes;
+      !noInstanceContextTypes
+        ? warning(
+            false,
+            "contextTypes was defined as an instance property on %s. Use a static " +
+              "property to define contextTypes instead.",
+            name
+          )
+        : void 0;
+      var noComponentShouldUpdate =
+        typeof instance.componentShouldUpdate !== "function";
+      !noComponentShouldUpdate
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
+              "The name is phrased as a question because the function is " +
+              "expected to return a value.",
+            name
+          )
+        : void 0;
+      if (
+        type.prototype &&
+        type.prototype.isPureReactComponent &&
+        typeof instance.shouldComponentUpdate !== "undefined"
+      ) {
+        warning(
+          false,
+          "%s has a method called shouldComponentUpdate(). " +
+            "shouldComponentUpdate should not be used when extending React.PureComponent. " +
+            "Please extend React.Component if shouldComponentUpdate is used.",
+          getComponentName(workInProgress) || "A pure component"
+        );
+      }
+      var noComponentDidUnmount =
+        typeof instance.componentDidUnmount !== "function";
+      !noComponentDidUnmount
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentDidUnmount(). But there is no such lifecycle method. " +
+              "Did you mean componentWillUnmount()?",
+            name
+          )
+        : void 0;
+      var noComponentDidReceiveProps =
+        typeof instance.componentDidReceiveProps !== "function";
+      !noComponentDidReceiveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentDidReceiveProps(). But there is no such lifecycle method. " +
+              "If you meant to update the state in response to changing props, " +
+              "use componentWillReceiveProps(). If you meant to fetch data or " +
+              "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
+            name
+          )
+        : void 0;
+      var noComponentWillRecieveProps =
+        typeof instance.componentWillRecieveProps !== "function";
+      !noComponentWillRecieveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
+            name
+          )
+        : void 0;
+      var noUnsafeComponentWillRecieveProps =
+        typeof instance.UNSAFE_componentWillRecieveProps !== "function";
+      !noUnsafeComponentWillRecieveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
+            name
+          )
+        : void 0;
+      var hasMutatedProps = instance.props !== workInProgress.pendingProps;
+      !(instance.props === undefined || !hasMutatedProps)
+        ? warning(
+            false,
+            "%s(...): When calling super() in `%s`, make sure to pass " +
+              "up the same props that your component's constructor was passed.",
+            name,
+            name
+          )
+        : void 0;
+      var noInstanceDefaultProps = !instance.defaultProps;
+      !noInstanceDefaultProps
+        ? warning(
+            false,
+            "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
+              " Instead, define defaultProps as a static property on %s.",
+            name,
+            name
+          )
+        : void 0;
+
+      if (
+        typeof instance.getSnapshotBeforeUpdate === "function" &&
+        typeof instance.componentDidUpdate !== "function" &&
+        !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
+      ) {
+        didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
+        warning(
+          false,
+          "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
+            "This component defines getSnapshotBeforeUpdate() only.",
+          getComponentName(workInProgress)
+        );
+      }
+
+      var noInstanceGetDerivedStateFromProps =
+        typeof instance.getDerivedStateFromProps !== "function";
+      !noInstanceGetDerivedStateFromProps
+        ? warning(
+            false,
+            "%s: getDerivedStateFromProps() is defined as an instance method " +
+              "and will be ignored. Instead, declare it as a static method.",
+            name
+          )
+        : void 0;
+      var noInstanceGetDerivedStateFromCatch =
+        typeof instance.getDerivedStateFromCatch !== "function";
+      !noInstanceGetDerivedStateFromCatch
+        ? warning(
+            false,
+            "%s: getDerivedStateFromCatch() is defined as an instance method " +
+              "and will be ignored. Instead, declare it as a static method.",
+            name
+          )
+        : void 0;
+      var noStaticGetSnapshotBeforeUpdate =
+        typeof type.getSnapshotBeforeUpdate !== "function";
+      !noStaticGetSnapshotBeforeUpdate
+        ? warning(
+            false,
+            "%s: getSnapshotBeforeUpdate() is defined as a static method " +
+              "and will be ignored. Instead, declare it as an instance method.",
+            name
+          )
+        : void 0;
+      var _state = instance.state;
+      if (_state && (typeof _state !== "object" || isArray(_state))) {
+        warning(false, "%s.state: must be set to an object or null", name);
+      }
+      if (typeof instance.getChildContext === "function") {
+        !(typeof type.childContextTypes === "object")
+          ? warning(
+              false,
+              "%s.getChildContext(): childContextTypes must be defined in order to " +
+                "use getChildContext().",
+              name
+            )
+          : void 0;
+      }
+    }
+  }
+
+  function resetInputPointers(workInProgress, instance) {
+    instance.props = workInProgress.memoizedProps;
+    instance.state = workInProgress.memoizedState;
+  }
+
+  function adoptClassInstance(workInProgress, instance) {
+    instance.updater = updater;
+    workInProgress.stateNode = instance;
+    // The instance needs access to the fiber so that it can schedule updates
+    set(instance, workInProgress);
+    {
+      instance._reactInternalInstance = fakeInternalInstance;
+    }
+  }
+
+  function constructClassInstance(workInProgress, props) {
+    var ctor = workInProgress.type;
+    var unmaskedContext = getUnmaskedContext(workInProgress);
+    var needsContext = isContextConsumer(workInProgress);
+    var context = needsContext
+      ? getMaskedContext(workInProgress, unmaskedContext)
+      : emptyObject;
+
+    // Instantiate twice to help detect side-effects.
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      new ctor(props, context); // eslint-disable-line no-new
+    }
+
+    var instance = new ctor(props, context);
+    var state =
+      instance.state !== null && instance.state !== undefined
+        ? instance.state
+        : null;
+    adoptClassInstance(workInProgress, instance);
+
+    {
+      if (
+        typeof ctor.getDerivedStateFromProps === "function" &&
+        state === null
+      ) {
+        var componentName = getComponentName(workInProgress) || "Component";
+        if (!didWarnAboutUninitializedState.has(componentName)) {
+          didWarnAboutUninitializedState.add(componentName);
+          warning(
+            false,
+            "%s: Did not properly initialize state during construction. " +
+              "Expected state to be an object, but it was %s.",
+            componentName,
+            instance.state === null ? "null" : "undefined"
+          );
+        }
+      }
+
+      // If new component APIs are defined, "unsafe" lifecycles won't be called.
+      // Warn about these lifecycles if they are present.
+      // Don't warn about react-lifecycles-compat polyfilled methods though.
+      if (
+        typeof ctor.getDerivedStateFromProps === "function" ||
+        typeof instance.getSnapshotBeforeUpdate === "function"
+      ) {
+        var foundWillMountName = null;
+        var foundWillReceivePropsName = null;
+        var foundWillUpdateName = null;
+        if (
+          typeof instance.componentWillMount === "function" &&
+          instance.componentWillMount.__suppressDeprecationWarning !== true
+        ) {
+          foundWillMountName = "componentWillMount";
+        } else if (typeof instance.UNSAFE_componentWillMount === "function") {
+          foundWillMountName = "UNSAFE_componentWillMount";
+        }
+        if (
+          typeof instance.componentWillReceiveProps === "function" &&
+          instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+            true
+        ) {
+          foundWillReceivePropsName = "componentWillReceiveProps";
+        } else if (
+          typeof instance.UNSAFE_componentWillReceiveProps === "function"
+        ) {
+          foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
+        }
+        if (
+          typeof instance.componentWillUpdate === "function" &&
+          instance.componentWillUpdate.__suppressDeprecationWarning !== true
+        ) {
+          foundWillUpdateName = "componentWillUpdate";
+        } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+          foundWillUpdateName = "UNSAFE_componentWillUpdate";
+        }
+        if (
+          foundWillMountName !== null ||
+          foundWillReceivePropsName !== null ||
+          foundWillUpdateName !== null
+        ) {
+          var _componentName = getComponentName(workInProgress) || "Component";
+          var newApiName =
+            typeof ctor.getDerivedStateFromProps === "function"
+              ? "getDerivedStateFromProps()"
+              : "getSnapshotBeforeUpdate()";
+          if (
+            !didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)
+          ) {
+            didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
+            warning(
+              false,
+              "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
+                "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
+                "The above lifecycles should be removed. Learn more about this warning here:\n" +
+                "https://fb.me/react-async-component-lifecycle-hooks",
+              _componentName,
+              newApiName,
+              foundWillMountName !== null ? "\n  " + foundWillMountName : "",
+              foundWillReceivePropsName !== null
+                ? "\n  " + foundWillReceivePropsName
+                : "",
+              foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
+            );
+          }
+        }
+      }
+    }
+
+    workInProgress.memoizedState = state;
+
+    var partialState = callGetDerivedStateFromProps(
+      workInProgress,
+      instance,
+      props,
+      state
+    );
+
+    if (partialState !== null && partialState !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      workInProgress.memoizedState = Object.assign(
+        {},
+        workInProgress.memoizedState,
+        partialState
+      );
+    }
+
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    // ReactFiberContext usually updates this cache but can't for newly-created instances.
+    if (needsContext) {
+      cacheContext(workInProgress, unmaskedContext, context);
+    }
+
+    return instance;
+  }
+
+  function callComponentWillMount(workInProgress, instance) {
+    startPhaseTimer(workInProgress, "componentWillMount");
+    var oldState = instance.state;
+
+    if (typeof instance.componentWillMount === "function") {
+      instance.componentWillMount();
+    }
+    if (typeof instance.UNSAFE_componentWillMount === "function") {
+      instance.UNSAFE_componentWillMount();
+    }
+
+    stopPhaseTimer();
+
+    if (oldState !== instance.state) {
+      {
+        warning(
+          false,
+          "%s.componentWillMount(): Assigning directly to this.state is " +
+            "deprecated (except inside a component's " +
+            "constructor). Use setState instead.",
+          getComponentName(workInProgress) || "Component"
+        );
+      }
+      updater.enqueueReplaceState(instance, instance.state, null);
+    }
+  }
+
+  function callComponentWillReceiveProps(
+    workInProgress,
+    instance,
+    newProps,
+    newContext
+  ) {
+    var oldState = instance.state;
+    startPhaseTimer(workInProgress, "componentWillReceiveProps");
+    if (typeof instance.componentWillReceiveProps === "function") {
+      instance.componentWillReceiveProps(newProps, newContext);
+    }
+    if (typeof instance.UNSAFE_componentWillReceiveProps === "function") {
+      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+    }
+    stopPhaseTimer();
+
+    if (instance.state !== oldState) {
+      {
+        var componentName = getComponentName(workInProgress) || "Component";
+        if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
+          didWarnAboutStateAssignmentForComponent.add(componentName);
+          warning(
+            false,
+            "%s.componentWillReceiveProps(): Assigning directly to " +
+              "this.state is deprecated (except inside a component's " +
+              "constructor). Use setState instead.",
+            componentName
+          );
+        }
+      }
+      updater.enqueueReplaceState(instance, instance.state, null);
+    }
+  }
+
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    var type = workInProgress.type;
+
+    if (typeof type.getDerivedStateFromProps === "function") {
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        // Invoke method an extra time to help detect side-effects.
+        type.getDerivedStateFromProps.call(null, nextProps, prevState);
+      }
+
+      var partialState = type.getDerivedStateFromProps.call(
+        null,
+        nextProps,
+        prevState
+      );
+
+      {
+        if (partialState === undefined) {
+          var componentName = getComponentName(workInProgress) || "Component";
+          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+            didWarnAboutUndefinedDerivedState.add(componentName);
+            warning(
+              false,
+              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+                "You have returned undefined.",
+              componentName
+            );
+          }
+        }
+      }
+
+      return partialState;
+    }
+  }
+
+  // Invokes the mount life-cycles on a previously never rendered instance.
+  function mountClassInstance(workInProgress, renderExpirationTime) {
+    var ctor = workInProgress.type;
+    var current = workInProgress.alternate;
+
+    {
+      checkClassInstance(workInProgress);
+    }
+
+    var instance = workInProgress.stateNode;
+    var props = workInProgress.pendingProps;
+    var unmaskedContext = getUnmaskedContext(workInProgress);
+
+    instance.props = props;
+    instance.state = workInProgress.memoizedState;
+    instance.refs = emptyObject;
+    instance.context = getMaskedContext(workInProgress, unmaskedContext);
+
+    {
+      if (workInProgress.mode & StrictMode) {
+        ReactStrictModeWarnings.recordUnsafeLifecycleWarnings(
+          workInProgress,
+          instance
+        );
+      }
+
+      if (warnAboutDeprecatedLifecycles) {
+        ReactStrictModeWarnings.recordDeprecationWarnings(
+          workInProgress,
+          instance
+        );
+      }
+    }
+
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      typeof ctor.getDerivedStateFromProps !== "function" &&
+      typeof instance.getSnapshotBeforeUpdate !== "function" &&
+      (typeof instance.UNSAFE_componentWillMount === "function" ||
+        typeof instance.componentWillMount === "function")
+    ) {
+      callComponentWillMount(workInProgress, instance);
+      // If we had additional state updates during this life-cycle, let's
+      // process them now.
+      var updateQueue = workInProgress.updateQueue;
+      if (updateQueue !== null) {
+        instance.state = processUpdateQueue(
+          current,
+          workInProgress,
+          updateQueue,
+          instance,
+          props,
+          renderExpirationTime
+        );
+      }
+    }
+    if (typeof instance.componentDidMount === "function") {
+      workInProgress.effectTag |= Update;
+    }
+  }
+
+  function resumeMountClassInstance(workInProgress, renderExpirationTime) {
+    var ctor = workInProgress.type;
+    var instance = workInProgress.stateNode;
+    resetInputPointers(workInProgress, instance);
+
+    var oldProps = workInProgress.memoizedProps;
+    var newProps = workInProgress.pendingProps;
+    var oldContext = instance.context;
+    var newUnmaskedContext = getUnmaskedContext(workInProgress);
+    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+
+    var hasNewLifecycles =
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function";
+
+    // Note: During these life-cycles, instance.props/instance.state are what
+    // ever the previously attempted to render - not the "current". However,
+    // during componentDidUpdate we pass the "current" props.
+
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      !hasNewLifecycles &&
+      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
+        typeof instance.componentWillReceiveProps === "function")
+    ) {
+      if (oldProps !== newProps || oldContext !== newContext) {
+        callComponentWillReceiveProps(
+          workInProgress,
+          instance,
+          newProps,
+          newContext
+        );
+      }
+    }
+
+    // Compute the next state using the memoized state and the update queue.
+    var oldState = workInProgress.memoizedState;
+    // TODO: Previous state can be null.
+    var newState = void 0;
+    var derivedStateFromCatch = void 0;
+    if (workInProgress.updateQueue !== null) {
+      newState = processUpdateQueue(
+        null,
+        workInProgress,
+        workInProgress.updateQueue,
+        instance,
+        newProps,
+        renderExpirationTime
+      );
+
+      var updateQueue = workInProgress.updateQueue;
+      if (
+        updateQueue !== null &&
+        updateQueue.capturedValues !== null &&
+        enableGetDerivedStateFromCatch &&
+        typeof ctor.getDerivedStateFromCatch === "function"
+      ) {
+        var capturedValues = updateQueue.capturedValues;
+        // Don't remove these from the update queue yet. We need them in
+        // finishClassComponent. Do the reset there.
+        // TODO: This is awkward. Refactor class components.
+        // updateQueue.capturedValues = null;
+        derivedStateFromCatch = callGetDerivedStateFromCatch(
+          ctor,
+          capturedValues
+        );
+      }
+    } else {
+      newState = oldState;
+    }
+
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
+        workInProgress,
+        instance,
+        newProps,
+        newState
+      );
+    }
+
+    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromProps
+          : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue = workInProgress.updateQueue;
+      if (_updateQueue !== null) {
+        _updateQueue.baseState = Object.assign(
+          {},
+          _updateQueue.baseState,
+          derivedStateFromProps
+        );
+      }
+    }
+    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromCatch
+          : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue2 = workInProgress.updateQueue;
+      if (_updateQueue2 !== null) {
+        _updateQueue2.baseState = Object.assign(
+          {},
+          _updateQueue2.baseState,
+          derivedStateFromCatch
+        );
+      }
+    }
+
+    if (
+      oldProps === newProps &&
+      oldState === newState &&
+      !hasContextChanged() &&
+      !(
+        workInProgress.updateQueue !== null &&
+        workInProgress.updateQueue.hasForceUpdate
+      )
+    ) {
+      // If an update was already in progress, we should schedule an Update
+      // effect even though we're bailing out, so that cWU/cDU are called.
+      if (typeof instance.componentDidMount === "function") {
+        workInProgress.effectTag |= Update;
+      }
+      return false;
+    }
+
+    var shouldUpdate = checkShouldComponentUpdate(
+      workInProgress,
+      oldProps,
+      newProps,
+      oldState,
+      newState,
+      newContext
+    );
+
+    if (shouldUpdate) {
+      // In order to support react-lifecycles-compat polyfilled components,
+      // Unsafe lifecycles should not be invoked for components using the new APIs.
+      if (
+        !hasNewLifecycles &&
+        (typeof instance.UNSAFE_componentWillMount === "function" ||
+          typeof instance.componentWillMount === "function")
+      ) {
+        startPhaseTimer(workInProgress, "componentWillMount");
+        if (typeof instance.componentWillMount === "function") {
+          instance.componentWillMount();
+        }
+        if (typeof instance.UNSAFE_componentWillMount === "function") {
+          instance.UNSAFE_componentWillMount();
+        }
+        stopPhaseTimer();
+      }
+      if (typeof instance.componentDidMount === "function") {
+        workInProgress.effectTag |= Update;
+      }
+    } else {
+      // If an update was already in progress, we should schedule an Update
+      // effect even though we're bailing out, so that cWU/cDU are called.
+      if (typeof instance.componentDidMount === "function") {
+        workInProgress.effectTag |= Update;
+      }
+
+      // If shouldComponentUpdate returned false, we should still update the
+      // memoized props/state to indicate that this work can be reused.
+      memoizeProps(workInProgress, newProps);
+      memoizeState(workInProgress, newState);
+    }
+
+    // Update the existing instance's state, props, and context pointers even
+    // if shouldComponentUpdate returns false.
+    instance.props = newProps;
+    instance.state = newState;
+    instance.context = newContext;
+
+    return shouldUpdate;
+  }
+
+  // Invokes the update life-cycles and returns false if it shouldn't rerender.
+  function updateClassInstance(current, workInProgress, renderExpirationTime) {
+    var ctor = workInProgress.type;
+    var instance = workInProgress.stateNode;
+    resetInputPointers(workInProgress, instance);
+
+    var oldProps = workInProgress.memoizedProps;
+    var newProps = workInProgress.pendingProps;
+    var oldContext = instance.context;
+    var newUnmaskedContext = getUnmaskedContext(workInProgress);
+    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+
+    var hasNewLifecycles =
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function";
+
+    // Note: During these life-cycles, instance.props/instance.state are what
+    // ever the previously attempted to render - not the "current". However,
+    // during componentDidUpdate we pass the "current" props.
+
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      !hasNewLifecycles &&
+      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
+        typeof instance.componentWillReceiveProps === "function")
+    ) {
+      if (oldProps !== newProps || oldContext !== newContext) {
+        callComponentWillReceiveProps(
+          workInProgress,
+          instance,
+          newProps,
+          newContext
+        );
+      }
+    }
+
+    // Compute the next state using the memoized state and the update queue.
+    var oldState = workInProgress.memoizedState;
+    // TODO: Previous state can be null.
+    var newState = void 0;
+    var derivedStateFromCatch = void 0;
+
+    if (workInProgress.updateQueue !== null) {
+      newState = processUpdateQueue(
+        current,
+        workInProgress,
+        workInProgress.updateQueue,
+        instance,
+        newProps,
+        renderExpirationTime
+      );
+
+      var updateQueue = workInProgress.updateQueue;
+      if (
+        updateQueue !== null &&
+        updateQueue.capturedValues !== null &&
+        enableGetDerivedStateFromCatch &&
+        typeof ctor.getDerivedStateFromCatch === "function"
+      ) {
+        var capturedValues = updateQueue.capturedValues;
+        // Don't remove these from the update queue yet. We need them in
+        // finishClassComponent. Do the reset there.
+        // TODO: This is awkward. Refactor class components.
+        // updateQueue.capturedValues = null;
+        derivedStateFromCatch = callGetDerivedStateFromCatch(
+          ctor,
+          capturedValues
+        );
+      }
+    } else {
+      newState = oldState;
+    }
+
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
+        workInProgress,
+        instance,
+        newProps,
+        newState
+      );
+    }
+
+    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromProps
+          : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue3 = workInProgress.updateQueue;
+      if (_updateQueue3 !== null) {
+        _updateQueue3.baseState = Object.assign(
+          {},
+          _updateQueue3.baseState,
+          derivedStateFromProps
+        );
+      }
+    }
+    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromCatch
+          : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue4 = workInProgress.updateQueue;
+      if (_updateQueue4 !== null) {
+        _updateQueue4.baseState = Object.assign(
+          {},
+          _updateQueue4.baseState,
+          derivedStateFromCatch
+        );
+      }
+    }
+
+    if (
+      oldProps === newProps &&
+      oldState === newState &&
+      !hasContextChanged() &&
+      !(
+        workInProgress.updateQueue !== null &&
+        workInProgress.updateQueue.hasForceUpdate
+      )
+    ) {
+      // If an update was already in progress, we should schedule an Update
+      // effect even though we're bailing out, so that cWU/cDU are called.
+      if (typeof instance.componentDidUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Update;
+        }
+      }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Snapshot;
+        }
+      }
+      return false;
+    }
+
+    var shouldUpdate = checkShouldComponentUpdate(
+      workInProgress,
+      oldProps,
+      newProps,
+      oldState,
+      newState,
+      newContext
+    );
+
+    if (shouldUpdate) {
+      // In order to support react-lifecycles-compat polyfilled components,
+      // Unsafe lifecycles should not be invoked for components using the new APIs.
+      if (
+        !hasNewLifecycles &&
+        (typeof instance.UNSAFE_componentWillUpdate === "function" ||
+          typeof instance.componentWillUpdate === "function")
+      ) {
+        startPhaseTimer(workInProgress, "componentWillUpdate");
+        if (typeof instance.componentWillUpdate === "function") {
+          instance.componentWillUpdate(newProps, newState, newContext);
+        }
+        if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+          instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
+        }
+        stopPhaseTimer();
+      }
+      if (typeof instance.componentDidUpdate === "function") {
+        workInProgress.effectTag |= Update;
+      }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        workInProgress.effectTag |= Snapshot;
+      }
+    } else {
+      // If an update was already in progress, we should schedule an Update
+      // effect even though we're bailing out, so that cWU/cDU are called.
+      if (typeof instance.componentDidUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Update;
+        }
+      }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Snapshot;
+        }
+      }
+
+      // If shouldComponentUpdate returned false, we should still update the
+      // memoized props/state to indicate that this work can be reused.
+      memoizeProps(workInProgress, newProps);
+      memoizeState(workInProgress, newState);
+    }
+
+    // Update the existing instance's state, props, and context pointers even
+    // if shouldComponentUpdate returns false.
+    instance.props = newProps;
+    instance.state = newState;
+    instance.context = newContext;
+
+    return shouldUpdate;
+  }
+
+  return {
+    adoptClassInstance: adoptClassInstance,
+    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
+    constructClassInstance: constructClassInstance,
+    mountClassInstance: mountClassInstance,
+    resumeMountClassInstance: resumeMountClassInstance,
+    updateClassInstance: updateClassInstance
+  };
+};
+
+var getCurrentFiberStackAddendum$1 =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+
+var didWarnAboutMaps = void 0;
+var didWarnAboutStringRefInStrictMode = void 0;
+var ownerHasKeyUseWarning = void 0;
+var ownerHasFunctionTypeWarning = void 0;
+var warnForMissingKey = function(child) {};
+
+{
+  didWarnAboutMaps = false;
+  didWarnAboutStringRefInStrictMode = {};
+
+  /**
+   * Warn if there's no key explicitly set on dynamic arrays of children or
+   * object keys are not valid. This allows us to keep track of children between
+   * updates.
+   */
+  ownerHasKeyUseWarning = {};
+  ownerHasFunctionTypeWarning = {};
+
+  warnForMissingKey = function(child) {
+    if (child === null || typeof child !== "object") {
+      return;
+    }
+    if (!child._store || child._store.validated || child.key != null) {
+      return;
+    }
+    invariant(
+      typeof child._store === "object",
+      "React Component in warnForMissingKey should have a _store. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+    child._store.validated = true;
+
+    var currentComponentErrorInfo =
+      "Each child in an array or iterator should have a unique " +
+      '"key" prop. See https://fb.me/react-warning-keys for ' +
+      "more information." +
+      (getCurrentFiberStackAddendum$1() || "");
+    if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
+      return;
+    }
+    ownerHasKeyUseWarning[currentComponentErrorInfo] = true;
+
+    warning(
+      false,
+      "Each child in an array or iterator should have a unique " +
+        '"key" prop. See https://fb.me/react-warning-keys for ' +
+        "more information.%s",
+      getCurrentFiberStackAddendum$1()
+    );
+  };
+}
+
+var isArray$1 = Array.isArray;
+
+function coerceRef(returnFiber, current, element) {
+  var mixedRef = element.ref;
+  if (
+    mixedRef !== null &&
+    typeof mixedRef !== "function" &&
+    typeof mixedRef !== "object"
+  ) {
+    {
+      if (returnFiber.mode & StrictMode) {
+        var componentName = getComponentName(returnFiber) || "Component";
+        if (!didWarnAboutStringRefInStrictMode[componentName]) {
+          warning(
+            false,
+            'A string ref, "%s", has been found within a strict mode tree. ' +
+              "String refs are a source of potential bugs and should be avoided. " +
+              "We recommend using createRef() instead." +
+              "\n%s" +
+              "\n\nLearn more about using refs safely here:" +
+              "\nhttps://fb.me/react-strict-mode-string-ref",
+            mixedRef,
+            getStackAddendumByWorkInProgressFiber(returnFiber)
+          );
+          didWarnAboutStringRefInStrictMode[componentName] = true;
+        }
+      }
+    }
+
+    if (element._owner) {
+      var owner = element._owner;
+      var inst = void 0;
+      if (owner) {
+        var ownerFiber = owner;
+        invariant(
+          ownerFiber.tag === ClassComponent,
+          "Stateless function components cannot have refs."
+        );
+        inst = ownerFiber.stateNode;
+      }
+      invariant(
+        inst,
+        "Missing owner for string ref %s. This error is likely caused by a " +
+          "bug in React. Please file an issue.",
+        mixedRef
+      );
+      var stringRef = "" + mixedRef;
+      // Check if previous string ref matches new string ref
+      if (
+        current !== null &&
+        current.ref !== null &&
+        current.ref._stringRef === stringRef
+      ) {
+        return current.ref;
+      }
+      var ref = function(value) {
+        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
+        if (value === null) {
+          delete refs[stringRef];
+        } else {
+          refs[stringRef] = value;
+        }
+      };
+      ref._stringRef = stringRef;
+      return ref;
+    } else {
+      invariant(
+        typeof mixedRef === "string",
+        "Expected ref to be a function or a string."
+      );
+      invariant(
+        element._owner,
+        "Element ref was specified as a string (%s) but no owner was set. This could happen for one of" +
+          " the following reasons:\n" +
+          "1. You may be adding a ref to a functional component\n" +
+          "2. You may be adding a ref to a component that was not created inside a component's render method\n" +
+          "3. You have multiple copies of React loaded\n" +
+          "See https://fb.me/react-refs-must-have-owner for more information.",
+        mixedRef
+      );
+    }
+  }
+  return mixedRef;
+}
+
+function throwOnInvalidObjectType(returnFiber, newChild) {
+  if (returnFiber.type !== "textarea") {
+    var addendum = "";
+    {
+      addendum =
+        " If you meant to render a collection of children, use an array " +
+        "instead." +
+        (getCurrentFiberStackAddendum$1() || "");
+    }
+    invariant(
+      false,
+      "Objects are not valid as a React child (found: %s).%s",
+      Object.prototype.toString.call(newChild) === "[object Object]"
+        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
+        : newChild,
+      addendum
+    );
+  }
+}
+
+function warnOnFunctionType() {
+  var currentComponentErrorInfo =
+    "Functions are not valid as a React child. This may happen if " +
+    "you return a Component instead of <Component /> from render. " +
+    "Or maybe you meant to call this function rather than return it." +
+    (getCurrentFiberStackAddendum$1() || "");
+
+  if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
+    return;
+  }
+  ownerHasFunctionTypeWarning[currentComponentErrorInfo] = true;
+
+  warning(
+    false,
+    "Functions are not valid as a React child. This may happen if " +
+      "you return a Component instead of <Component /> from render. " +
+      "Or maybe you meant to call this function rather than return it.%s",
+    getCurrentFiberStackAddendum$1() || ""
+  );
+}
+
+// This wrapper function exists because I expect to clone the code in each path
+// to be able to optimize each path individually by branching early. This needs
+// a compiler or we can do it manually. Helpers that don't need this branching
+// live outside of this function.
+function ChildReconciler(shouldTrackSideEffects) {
+  function deleteChild(returnFiber, childToDelete) {
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return;
+    }
+    // Deletions are added in reversed order so we add it to the front.
+    // At this point, the return fiber's effect list is empty except for
+    // deletions, so we can just append the deletion to the list. The remaining
+    // effects aren't added until the complete phase. Once we implement
+    // resuming, this may not be true.
+    var last = returnFiber.lastEffect;
+    if (last !== null) {
+      last.nextEffect = childToDelete;
+      returnFiber.lastEffect = childToDelete;
+    } else {
+      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+    }
+    childToDelete.nextEffect = null;
+    childToDelete.effectTag = Deletion;
+  }
+
+  function deleteRemainingChildren(returnFiber, currentFirstChild) {
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return null;
+    }
+
+    // TODO: For the shouldClone case, this could be micro-optimized a bit by
+    // assuming that after the first child we've already added everything.
+    var childToDelete = currentFirstChild;
+    while (childToDelete !== null) {
+      deleteChild(returnFiber, childToDelete);
+      childToDelete = childToDelete.sibling;
+    }
+    return null;
+  }
+
+  function mapRemainingChildren(returnFiber, currentFirstChild) {
+    // Add the remaining children to a temporary map so that we can find them by
+    // keys quickly. Implicit (null) keys get added to this set with their index
+    var existingChildren = new Map();
+
+    var existingChild = currentFirstChild;
+    while (existingChild !== null) {
+      if (existingChild.key !== null) {
+        existingChildren.set(existingChild.key, existingChild);
+      } else {
+        existingChildren.set(existingChild.index, existingChild);
+      }
+      existingChild = existingChild.sibling;
+    }
+    return existingChildren;
+  }
+
+  function useFiber(fiber, pendingProps, expirationTime) {
+    // We currently set sibling to null and index to 0 here because it is easy
+    // to forget to do before returning it. E.g. for the single child case.
+    var clone = createWorkInProgress(fiber, pendingProps, expirationTime);
+    clone.index = 0;
+    clone.sibling = null;
+    return clone;
+  }
+
+  function placeChild(newFiber, lastPlacedIndex, newIndex) {
+    newFiber.index = newIndex;
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return lastPlacedIndex;
+    }
+    var current = newFiber.alternate;
+    if (current !== null) {
+      var oldIndex = current.index;
+      if (oldIndex < lastPlacedIndex) {
+        // This is a move.
+        newFiber.effectTag = Placement;
+        return lastPlacedIndex;
+      } else {
+        // This item can stay in place.
+        return oldIndex;
+      }
+    } else {
+      // This is an insertion.
+      newFiber.effectTag = Placement;
+      return lastPlacedIndex;
+    }
+  }
+
+  function placeSingleChild(newFiber) {
+    // This is simpler for the single child case. We only need to do a
+    // placement for inserting new children.
+    if (shouldTrackSideEffects && newFiber.alternate === null) {
+      newFiber.effectTag = Placement;
+    }
+    return newFiber;
+  }
+
+  function updateTextNode(returnFiber, current, textContent, expirationTime) {
+    if (current === null || current.tag !== HostText) {
+      // Insert
+      var created = createFiberFromText(
+        textContent,
+        returnFiber.mode,
+        expirationTime
+      );
+      created["return"] = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, textContent, expirationTime);
+      existing["return"] = returnFiber;
+      return existing;
+    }
+  }
+
+  function updateElement(returnFiber, current, element, expirationTime) {
+    if (current !== null && current.type === element.type) {
+      // Move based on index
+      var existing = useFiber(current, element.props, expirationTime);
+      existing.ref = coerceRef(returnFiber, current, element);
+      existing["return"] = returnFiber;
+      {
+        existing._debugSource = element._source;
+        existing._debugOwner = element._owner;
+      }
+      return existing;
+    } else {
+      // Insert
+      var created = createFiberFromElement(
+        element,
+        returnFiber.mode,
+        expirationTime
+      );
+      created.ref = coerceRef(returnFiber, current, element);
+      created["return"] = returnFiber;
+      return created;
+    }
+  }
+
+  function updatePortal(returnFiber, current, portal, expirationTime) {
+    if (
+      current === null ||
+      current.tag !== HostPortal ||
+      current.stateNode.containerInfo !== portal.containerInfo ||
+      current.stateNode.implementation !== portal.implementation
+    ) {
+      // Insert
+      var created = createFiberFromPortal(
+        portal,
+        returnFiber.mode,
+        expirationTime
+      );
+      created["return"] = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, portal.children || [], expirationTime);
+      existing["return"] = returnFiber;
+      return existing;
+    }
+  }
+
+  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
+    if (current === null || current.tag !== Fragment) {
+      // Insert
+      var created = createFiberFromFragment(
+        fragment,
+        returnFiber.mode,
+        expirationTime,
+        key
+      );
+      created["return"] = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, fragment, expirationTime);
+      existing["return"] = returnFiber;
+      return existing;
+    }
+  }
+
+  function createChild(returnFiber, newChild, expirationTime) {
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys. If the previous node is implicitly keyed
+      // we can continue to replace it without aborting even if it is not a text
+      // node.
+      var created = createFiberFromText(
+        "" + newChild,
+        returnFiber.mode,
+        expirationTime
+      );
+      created["return"] = returnFiber;
+      return created;
+    }
+
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          var _created = createFiberFromElement(
+            newChild,
+            returnFiber.mode,
+            expirationTime
+          );
+          _created.ref = coerceRef(returnFiber, null, newChild);
+          _created["return"] = returnFiber;
+          return _created;
+        }
+        case REACT_PORTAL_TYPE: {
+          var _created2 = createFiberFromPortal(
+            newChild,
+            returnFiber.mode,
+            expirationTime
+          );
+          _created2["return"] = returnFiber;
+          return _created2;
+        }
+      }
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        var _created3 = createFiberFromFragment(
+          newChild,
+          returnFiber.mode,
+          expirationTime,
+          null
+        );
+        _created3["return"] = returnFiber;
+        return _created3;
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+
+    return null;
+  }
+
+  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
+    // Update the fiber if the keys match, otherwise return null.
+
+    var key = oldFiber !== null ? oldFiber.key : null;
+
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys. If the previous node is implicitly keyed
+      // we can continue to replace it without aborting even if it is not a text
+      // node.
+      if (key !== null) {
+        return null;
+      }
+      return updateTextNode(
+        returnFiber,
+        oldFiber,
+        "" + newChild,
+        expirationTime
+      );
+    }
+
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          if (newChild.key === key) {
+            if (newChild.type === REACT_FRAGMENT_TYPE) {
+              return updateFragment(
+                returnFiber,
+                oldFiber,
+                newChild.props.children,
+                expirationTime,
+                key
+              );
+            }
+            return updateElement(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime
+            );
+          } else {
+            return null;
+          }
+        }
+        case REACT_PORTAL_TYPE: {
+          if (newChild.key === key) {
+            return updatePortal(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime
+            );
+          } else {
+            return null;
+          }
+        }
+      }
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        if (key !== null) {
+          return null;
+        }
+
+        return updateFragment(
+          returnFiber,
+          oldFiber,
+          newChild,
+          expirationTime,
+          null
+        );
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+
+    return null;
+  }
+
+  function updateFromMap(
+    existingChildren,
+    returnFiber,
+    newIdx,
+    newChild,
+    expirationTime
+  ) {
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys, so we neither have to check the old nor
+      // new node for the key. If both are text nodes, they match.
+      var matchedFiber = existingChildren.get(newIdx) || null;
+      return updateTextNode(
+        returnFiber,
+        matchedFiber,
+        "" + newChild,
+        expirationTime
+      );
+    }
+
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          var _matchedFiber =
+            existingChildren.get(
+              newChild.key === null ? newIdx : newChild.key
+            ) || null;
+          if (newChild.type === REACT_FRAGMENT_TYPE) {
+            return updateFragment(
+              returnFiber,
+              _matchedFiber,
+              newChild.props.children,
+              expirationTime,
+              newChild.key
+            );
+          }
+          return updateElement(
+            returnFiber,
+            _matchedFiber,
+            newChild,
+            expirationTime
+          );
+        }
+        case REACT_PORTAL_TYPE: {
+          var _matchedFiber2 =
+            existingChildren.get(
+              newChild.key === null ? newIdx : newChild.key
+            ) || null;
+          return updatePortal(
+            returnFiber,
+            _matchedFiber2,
+            newChild,
+            expirationTime
+          );
+        }
+      }
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        var _matchedFiber3 = existingChildren.get(newIdx) || null;
+        return updateFragment(
+          returnFiber,
+          _matchedFiber3,
+          newChild,
+          expirationTime,
+          null
+        );
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+
+    return null;
+  }
+
+  /**
+   * Warns if there is a duplicate or missing key
+   */
+  function warnOnInvalidKey(child, knownKeys) {
+    {
+      if (typeof child !== "object" || child === null) {
+        return knownKeys;
+      }
+      switch (child.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+        case REACT_PORTAL_TYPE:
+          warnForMissingKey(child);
+          var key = child.key;
+          if (typeof key !== "string") {
+            break;
+          }
+          if (knownKeys === null) {
+            knownKeys = new Set();
+            knownKeys.add(key);
+            break;
+          }
+          if (!knownKeys.has(key)) {
+            knownKeys.add(key);
+            break;
+          }
+          warning(
+            false,
+            "Encountered two children with the same key, `%s`. " +
+              "Keys should be unique so that components maintain their identity " +
+              "across updates. Non-unique keys may cause children to be " +
+              "duplicated and/or omitted — the behavior is unsupported and " +
+              "could change in a future version.%s",
+            key,
+            getCurrentFiberStackAddendum$1()
+          );
+          break;
+        default:
+          break;
+      }
+    }
+    return knownKeys;
+  }
+
+  function reconcileChildrenArray(
+    returnFiber,
+    currentFirstChild,
+    newChildren,
+    expirationTime
+  ) {
+    // This algorithm can't optimize by searching from boths ends since we
+    // don't have backpointers on fibers. I'm trying to see how far we can get
+    // with that model. If it ends up not being worth the tradeoffs, we can
+    // add it later.
+
+    // Even with a two ended optimization, we'd want to optimize for the case
+    // where there are few changes and brute force the comparison instead of
+    // going for the Map. It'd like to explore hitting that path first in
+    // forward-only mode and only go for the Map once we notice that we need
+    // lots of look ahead. This doesn't handle reversal as well as two ended
+    // search but that's unusual. Besides, for the two ended optimization to
+    // work on Iterables, we'd need to copy the whole set.
+
+    // In this first iteration, we'll just live with hitting the bad case
+    // (adding everything to a Map) in for every insert/move.
+
+    // If you change this code, also update reconcileChildrenIterator() which
+    // uses the same algorithm.
+
+    {
+      // First, validate keys.
+      var knownKeys = null;
+      for (var i = 0; i < newChildren.length; i++) {
+        var child = newChildren[i];
+        knownKeys = warnOnInvalidKey(child, knownKeys);
+      }
+    }
+
+    var resultingFirstChild = null;
+    var previousNewFiber = null;
+
+    var oldFiber = currentFirstChild;
+    var lastPlacedIndex = 0;
+    var newIdx = 0;
+    var nextOldFiber = null;
+    for (; oldFiber !== null && newIdx < newChildren.length; newIdx++) {
+      if (oldFiber.index > newIdx) {
+        nextOldFiber = oldFiber;
+        oldFiber = null;
+      } else {
+        nextOldFiber = oldFiber.sibling;
+      }
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (newFiber === null) {
+        // TODO: This breaks on empty slots like null children. That's
+        // unfortunate because it triggers the slow path all the time. We need
+        // a better way to communicate whether this was a miss or null,
+        // boolean, undefined, etc.
+        if (oldFiber === null) {
+          oldFiber = nextOldFiber;
+        }
+        break;
+      }
+      if (shouldTrackSideEffects) {
+        if (oldFiber && newFiber.alternate === null) {
+          // We matched the slot, but we didn't reuse the existing fiber, so we
+          // need to delete the existing child.
+          deleteChild(returnFiber, oldFiber);
+        }
+      }
+      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
+      if (previousNewFiber === null) {
+        // TODO: Move out of the loop. This only happens for the first run.
+        resultingFirstChild = newFiber;
+      } else {
+        // TODO: Defer siblings if we're not at the right index for this slot.
+        // I.e. if we had null values before, then we want to defer this
+        // for each null value. However, we also don't want to call updateSlot
+        // with the previous one.
+        previousNewFiber.sibling = newFiber;
+      }
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+
+    if (newIdx === newChildren.length) {
+      // We've reached the end of the new children. We can delete the rest.
+      deleteRemainingChildren(returnFiber, oldFiber);
+      return resultingFirstChild;
+    }
+
+    if (oldFiber === null) {
+      // If we don't have any more existing children we can choose a fast path
+      // since the rest will all be insertions.
+      for (; newIdx < newChildren.length; newIdx++) {
+        var _newFiber = createChild(
+          returnFiber,
+          newChildren[newIdx],
+          expirationTime
+        );
+        if (!_newFiber) {
+          continue;
+        }
+        lastPlacedIndex = placeChild(_newFiber, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          // TODO: Move out of the loop. This only happens for the first run.
+          resultingFirstChild = _newFiber;
+        } else {
+          previousNewFiber.sibling = _newFiber;
+        }
+        previousNewFiber = _newFiber;
+      }
+      return resultingFirstChild;
+    }
+
+    // Add all children to a key map for quick lookups.
+    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
+
+    // Keep scanning and use the map to restore deleted items as moves.
+    for (; newIdx < newChildren.length; newIdx++) {
+      var _newFiber2 = updateFromMap(
+        existingChildren,
+        returnFiber,
+        newIdx,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (_newFiber2) {
+        if (shouldTrackSideEffects) {
+          if (_newFiber2.alternate !== null) {
+            // The new fiber is a work in progress, but if there exists a
+            // current, that means that we reused the fiber. We need to delete
+            // it from the child list so that we don't add it to the deletion
+            // list.
+            existingChildren["delete"](
+              _newFiber2.key === null ? newIdx : _newFiber2.key
+            );
+          }
+        }
+        lastPlacedIndex = placeChild(_newFiber2, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          resultingFirstChild = _newFiber2;
+        } else {
+          previousNewFiber.sibling = _newFiber2;
+        }
+        previousNewFiber = _newFiber2;
+      }
+    }
+
+    if (shouldTrackSideEffects) {
+      // Any existing children that weren't consumed above were deleted. We need
+      // to add them to the deletion list.
+      existingChildren.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    }
+
+    return resultingFirstChild;
+  }
+
+  function reconcileChildrenIterator(
+    returnFiber,
+    currentFirstChild,
+    newChildrenIterable,
+    expirationTime
+  ) {
+    // This is the same implementation as reconcileChildrenArray(),
+    // but using the iterator instead.
+
+    var iteratorFn = getIteratorFn(newChildrenIterable);
+    invariant(
+      typeof iteratorFn === "function",
+      "An object is not an iterable. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+
+    {
+      // Warn about using Maps as children
+      if (typeof newChildrenIterable.entries === "function") {
+        var possibleMap = newChildrenIterable;
+        if (possibleMap.entries === iteratorFn) {
+          !didWarnAboutMaps
+            ? warning(
+                false,
+                "Using Maps as children is unsupported and will likely yield " +
+                  "unexpected results. Convert it to a sequence/iterable of keyed " +
+                  "ReactElements instead.%s",
+                getCurrentFiberStackAddendum$1()
+              )
+            : void 0;
+          didWarnAboutMaps = true;
+        }
+      }
+
+      // First, validate keys.
+      // We'll get a different iterator later for the main pass.
+      var _newChildren = iteratorFn.call(newChildrenIterable);
+      if (_newChildren) {
+        var knownKeys = null;
+        var _step = _newChildren.next();
+        for (; !_step.done; _step = _newChildren.next()) {
+          var child = _step.value;
+          knownKeys = warnOnInvalidKey(child, knownKeys);
+        }
+      }
+    }
+
+    var newChildren = iteratorFn.call(newChildrenIterable);
+    invariant(newChildren != null, "An iterable object provided no iterator.");
+
+    var resultingFirstChild = null;
+    var previousNewFiber = null;
+
+    var oldFiber = currentFirstChild;
+    var lastPlacedIndex = 0;
+    var newIdx = 0;
+    var nextOldFiber = null;
+
+    var step = newChildren.next();
+    for (
+      ;
+      oldFiber !== null && !step.done;
+      newIdx++, step = newChildren.next()
+    ) {
+      if (oldFiber.index > newIdx) {
+        nextOldFiber = oldFiber;
+        oldFiber = null;
+      } else {
+        nextOldFiber = oldFiber.sibling;
+      }
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        step.value,
+        expirationTime
+      );
+      if (newFiber === null) {
+        // TODO: This breaks on empty slots like null children. That's
+        // unfortunate because it triggers the slow path all the time. We need
+        // a better way to communicate whether this was a miss or null,
+        // boolean, undefined, etc.
+        if (!oldFiber) {
+          oldFiber = nextOldFiber;
+        }
+        break;
+      }
+      if (shouldTrackSideEffects) {
+        if (oldFiber && newFiber.alternate === null) {
+          // We matched the slot, but we didn't reuse the existing fiber, so we
+          // need to delete the existing child.
+          deleteChild(returnFiber, oldFiber);
+        }
+      }
+      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
+      if (previousNewFiber === null) {
+        // TODO: Move out of the loop. This only happens for the first run.
+        resultingFirstChild = newFiber;
+      } else {
+        // TODO: Defer siblings if we're not at the right index for this slot.
+        // I.e. if we had null values before, then we want to defer this
+        // for each null value. However, we also don't want to call updateSlot
+        // with the previous one.
+        previousNewFiber.sibling = newFiber;
+      }
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+
+    if (step.done) {
+      // We've reached the end of the new children. We can delete the rest.
+      deleteRemainingChildren(returnFiber, oldFiber);
+      return resultingFirstChild;
+    }
+
+    if (oldFiber === null) {
+      // If we don't have any more existing children we can choose a fast path
+      // since the rest will all be insertions.
+      for (; !step.done; newIdx++, step = newChildren.next()) {
+        var _newFiber3 = createChild(returnFiber, step.value, expirationTime);
+        if (_newFiber3 === null) {
+          continue;
+        }
+        lastPlacedIndex = placeChild(_newFiber3, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          // TODO: Move out of the loop. This only happens for the first run.
+          resultingFirstChild = _newFiber3;
+        } else {
+          previousNewFiber.sibling = _newFiber3;
+        }
+        previousNewFiber = _newFiber3;
+      }
+      return resultingFirstChild;
+    }
+
+    // Add all children to a key map for quick lookups.
+    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
+
+    // Keep scanning and use the map to restore deleted items as moves.
+    for (; !step.done; newIdx++, step = newChildren.next()) {
+      var _newFiber4 = updateFromMap(
+        existingChildren,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      );
+      if (_newFiber4 !== null) {
+        if (shouldTrackSideEffects) {
+          if (_newFiber4.alternate !== null) {
+            // The new fiber is a work in progress, but if there exists a
+            // current, that means that we reused the fiber. We need to delete
+            // it from the child list so that we don't add it to the deletion
+            // list.
+            existingChildren["delete"](
+              _newFiber4.key === null ? newIdx : _newFiber4.key
+            );
+          }
+        }
+        lastPlacedIndex = placeChild(_newFiber4, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          resultingFirstChild = _newFiber4;
+        } else {
+          previousNewFiber.sibling = _newFiber4;
+        }
+        previousNewFiber = _newFiber4;
+      }
+    }
+
+    if (shouldTrackSideEffects) {
+      // Any existing children that weren't consumed above were deleted. We need
+      // to add them to the deletion list.
+      existingChildren.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    }
+
+    return resultingFirstChild;
+  }
+
+  function reconcileSingleTextNode(
+    returnFiber,
+    currentFirstChild,
+    textContent,
+    expirationTime
+  ) {
+    // There's no need to check for keys on text nodes since we don't have a
+    // way to define them.
+    if (currentFirstChild !== null && currentFirstChild.tag === HostText) {
+      // We already have an existing node so let's just update it and delete
+      // the rest.
+      deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
+      var existing = useFiber(currentFirstChild, textContent, expirationTime);
+      existing["return"] = returnFiber;
+      return existing;
+    }
+    // The existing first child is not a text node so we need to create one
+    // and delete the existing ones.
+    deleteRemainingChildren(returnFiber, currentFirstChild);
+    var created = createFiberFromText(
+      textContent,
+      returnFiber.mode,
+      expirationTime
+    );
+    created["return"] = returnFiber;
+    return created;
+  }
+
+  function reconcileSingleElement(
+    returnFiber,
+    currentFirstChild,
+    element,
+    expirationTime
+  ) {
+    var key = element.key;
+    var child = currentFirstChild;
+    while (child !== null) {
+      // TODO: If key === null and child.key === null, then this only applies to
+      // the first item in the list.
+      if (child.key === key) {
+        if (
+          child.tag === Fragment
+            ? element.type === REACT_FRAGMENT_TYPE
+            : child.type === element.type
+        ) {
+          deleteRemainingChildren(returnFiber, child.sibling);
+          var existing = useFiber(
+            child,
+            element.type === REACT_FRAGMENT_TYPE
+              ? element.props.children
+              : element.props,
+            expirationTime
+          );
+          existing.ref = coerceRef(returnFiber, child, element);
+          existing["return"] = returnFiber;
+          {
+            existing._debugSource = element._source;
+            existing._debugOwner = element._owner;
+          }
+          return existing;
+        } else {
+          deleteRemainingChildren(returnFiber, child);
+          break;
+        }
+      } else {
+        deleteChild(returnFiber, child);
+      }
+      child = child.sibling;
+    }
+
+    if (element.type === REACT_FRAGMENT_TYPE) {
+      var created = createFiberFromFragment(
+        element.props.children,
+        returnFiber.mode,
+        expirationTime,
+        element.key
+      );
+      created["return"] = returnFiber;
+      return created;
+    } else {
+      var _created4 = createFiberFromElement(
+        element,
+        returnFiber.mode,
+        expirationTime
+      );
+      _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
+      _created4["return"] = returnFiber;
+      return _created4;
+    }
+  }
+
+  function reconcileSinglePortal(
+    returnFiber,
+    currentFirstChild,
+    portal,
+    expirationTime
+  ) {
+    var key = portal.key;
+    var child = currentFirstChild;
+    while (child !== null) {
+      // TODO: If key === null and child.key === null, then this only applies to
+      // the first item in the list.
+      if (child.key === key) {
+        if (
+          child.tag === HostPortal &&
+          child.stateNode.containerInfo === portal.containerInfo &&
+          child.stateNode.implementation === portal.implementation
+        ) {
+          deleteRemainingChildren(returnFiber, child.sibling);
+          var existing = useFiber(child, portal.children || [], expirationTime);
+          existing["return"] = returnFiber;
+          return existing;
+        } else {
+          deleteRemainingChildren(returnFiber, child);
+          break;
+        }
+      } else {
+        deleteChild(returnFiber, child);
+      }
+      child = child.sibling;
+    }
+
+    var created = createFiberFromPortal(
+      portal,
+      returnFiber.mode,
+      expirationTime
+    );
+    created["return"] = returnFiber;
+    return created;
+  }
+
+  // This API will tag the children with the side-effect of the reconciliation
+  // itself. They will be added to the side-effect list as we pass through the
+  // children and the parent.
+  function reconcileChildFibers(
+    returnFiber,
+    currentFirstChild,
+    newChild,
+    expirationTime
+  ) {
+    // This function is not recursive.
+    // If the top level item is an array, we treat it as a set of children,
+    // not as a fragment. Nested arrays on the other hand will be treated as
+    // fragment nodes. Recursion happens at the normal flow.
+
+    // Handle top level unkeyed fragments as if they were arrays.
+    // This leads to an ambiguity between <>{[...]}</> and <>...</>.
+    // We treat the ambiguous cases above the same.
+    if (
+      typeof newChild === "object" &&
+      newChild !== null &&
+      newChild.type === REACT_FRAGMENT_TYPE &&
+      newChild.key === null
+    ) {
+      newChild = newChild.props.children;
+    }
+
+    // Handle object types
+    var isObject = typeof newChild === "object" && newChild !== null;
+
+    if (isObject) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return placeSingleChild(
+            reconcileSingleElement(
+              returnFiber,
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )
+          );
+        case REACT_PORTAL_TYPE:
+          return placeSingleChild(
+            reconcileSinglePortal(
+              returnFiber,
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )
+          );
+      }
+    }
+
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      return placeSingleChild(
+        reconcileSingleTextNode(
+          returnFiber,
+          currentFirstChild,
+          "" + newChild,
+          expirationTime
+        )
+      );
+    }
+
+    if (isArray$1(newChild)) {
+      return reconcileChildrenArray(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    }
+
+    if (getIteratorFn(newChild)) {
+      return reconcileChildrenIterator(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    }
+
+    if (isObject) {
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+    if (typeof newChild === "undefined") {
+      // If the new child is undefined, and the return fiber is a composite
+      // component, throw an error. If Fiber return types are disabled,
+      // we already threw above.
+      switch (returnFiber.tag) {
+        case ClassComponent: {
+          {
+            var instance = returnFiber.stateNode;
+            if (instance.render._isMockFunction) {
+              // We allow auto-mocks to proceed as if they're returning null.
+              break;
+            }
+          }
+        }
+        // Intentionally fall through to the next case, which handles both
+        // functions and classes
+        // eslint-disable-next-lined no-fallthrough
+        case FunctionalComponent: {
+          var Component = returnFiber.type;
+          invariant(
+            false,
+            "%s(...): Nothing was returned from render. This usually means a " +
+              "return statement is missing. Or, to render nothing, " +
+              "return null.",
+            Component.displayName || Component.name || "Component"
+          );
+        }
+      }
+    }
+
+    // Remaining cases are all treated as empty.
+    return deleteRemainingChildren(returnFiber, currentFirstChild);
+  }
+
+  return reconcileChildFibers;
+}
+
+var reconcileChildFibers = ChildReconciler(true);
+var mountChildFibers = ChildReconciler(false);
+
+function cloneChildFibers(current, workInProgress) {
+  invariant(
+    current === null || workInProgress.child === current.child,
+    "Resuming work not yet implemented."
+  );
+
+  if (workInProgress.child === null) {
+    return;
+  }
+
+  var currentChild = workInProgress.child;
+  var newChild = createWorkInProgress(
+    currentChild,
+    currentChild.pendingProps,
+    currentChild.expirationTime
+  );
+  workInProgress.child = newChild;
+
+  newChild["return"] = workInProgress;
+  while (currentChild.sibling !== null) {
+    currentChild = currentChild.sibling;
+    newChild = newChild.sibling = createWorkInProgress(
+      currentChild,
+      currentChild.pendingProps,
+      currentChild.expirationTime
+    );
+    newChild["return"] = workInProgress;
+  }
+  newChild.sibling = null;
+}
+
+var didWarnAboutBadClass = void 0;
+var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
+var didWarnAboutStatelessRefs = void 0;
+
+{
+  didWarnAboutBadClass = {};
+  didWarnAboutGetDerivedStateOnFunctionalComponent = {};
+  didWarnAboutStatelessRefs = {};
+}
+
+var ReactFiberBeginWork = function(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext,
+  scheduleWork,
+  computeExpirationForFiber
+) {
+  var shouldSetTextContent = config.shouldSetTextContent,
+    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
+  var pushHostContext = hostContext.pushHostContext,
+    pushHostContainer = hostContext.pushHostContainer;
+  var pushProvider = newContext.pushProvider;
+  var getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    hasLegacyContextChanged = legacyContext.hasContextChanged,
+    pushLegacyContextProvider = legacyContext.pushContextProvider,
+    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
+    invalidateContextProvider = legacyContext.invalidateContextProvider;
+  var enterHydrationState = hydrationContext.enterHydrationState,
+    resetHydrationState = hydrationContext.resetHydrationState,
+    tryToClaimNextHydratableInstance =
+      hydrationContext.tryToClaimNextHydratableInstance;
+
+  var _ReactFiberClassCompo = ReactFiberClassComponent(
+      legacyContext,
+      scheduleWork,
+      computeExpirationForFiber,
+      memoizeProps,
+      memoizeState
+    ),
+    adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
+    callGetDerivedStateFromProps =
+      _ReactFiberClassCompo.callGetDerivedStateFromProps,
+    constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
+    mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
+    resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
+    updateClassInstance = _ReactFiberClassCompo.updateClassInstance;
+
+  // TODO: Remove this and use reconcileChildrenAtExpirationTime directly.
+
+  function reconcileChildren(current, workInProgress, nextChildren) {
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      nextChildren,
+      workInProgress.expirationTime
+    );
+  }
+
+  function reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    renderExpirationTime
+  ) {
+    if (current === null) {
+      // If this is a fresh new component that hasn't been rendered yet, we
+      // won't update its child set by applying minimal side-effects. Instead,
+      // we will add them all to the child before it gets rendered. That means
+      // we can optimize this reconciliation pass by not tracking side-effects.
+      workInProgress.child = mountChildFibers(
+        workInProgress,
+        null,
+        nextChildren,
+        renderExpirationTime
+      );
+    } else {
+      // If the current child is the same as the work in progress, it means that
+      // we haven't yet started any work on these children. Therefore, we use
+      // the clone algorithm to create a copy of all the current children.
+
+      // If we had any progressed work already, that is invalid at this point so
+      // let's throw it out.
+      workInProgress.child = reconcileChildFibers(
+        workInProgress,
+        current.child,
+        nextChildren,
+        renderExpirationTime
+      );
+    }
+  }
+
+  function updateForwardRef(current, workInProgress) {
+    var render = workInProgress.type.render;
+    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+    return workInProgress.child;
+  }
+
+  function updateFragment(current, workInProgress) {
+    var nextChildren = workInProgress.pendingProps;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextChildren) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+    return workInProgress.child;
+  }
+
+  function updateMode(current, workInProgress) {
+    var nextChildren = workInProgress.pendingProps.children;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (
+      nextChildren === null ||
+      workInProgress.memoizedProps === nextChildren
+    ) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+    return workInProgress.child;
+  }
+
+  function markRef(current, workInProgress) {
+    var ref = workInProgress.ref;
+    if (
+      (current === null && ref !== null) ||
+      (current !== null && current.ref !== ref)
+    ) {
+      // Schedule a Ref effect
+      workInProgress.effectTag |= Ref;
+    }
+  }
+
+  function updateFunctionalComponent(current, workInProgress) {
+    var fn = workInProgress.type;
+    var nextProps = workInProgress.pendingProps;
+
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else {
+      if (workInProgress.memoizedProps === nextProps) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+      // TODO: consider bringing fn.shouldComponentUpdate() back.
+      // It used to be here.
+    }
+
+    var unmaskedContext = getUnmaskedContext(workInProgress);
+    var context = getMaskedContext(workInProgress, unmaskedContext);
+
+    var nextChildren = void 0;
+
+    {
+      ReactCurrentOwner.current = workInProgress;
+      ReactDebugCurrentFiber.setCurrentPhase("render");
+      nextChildren = fn(nextProps, context);
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
+    return workInProgress.child;
+  }
+
+  function updateClassComponent(current, workInProgress, renderExpirationTime) {
+    // Push context providers early to prevent context stack mismatches.
+    // During mounting we don't know the child context yet as the instance doesn't exist.
+    // We will invalidate the child context in finishClassComponent() right after rendering.
+    var hasContext = pushLegacyContextProvider(workInProgress);
+    var shouldUpdate = void 0;
+    if (current === null) {
+      if (workInProgress.stateNode === null) {
+        // In the initial pass we might need to construct the instance.
+        constructClassInstance(workInProgress, workInProgress.pendingProps);
+        mountClassInstance(workInProgress, renderExpirationTime);
+
+        shouldUpdate = true;
+      } else {
+        // In a resume, we'll already have an instance we can reuse.
+        shouldUpdate = resumeMountClassInstance(
+          workInProgress,
+          renderExpirationTime
+        );
+      }
+    } else {
+      shouldUpdate = updateClassInstance(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    }
+
+    // We processed the update queue inside updateClassInstance. It may have
+    // included some errors that were dispatched during the commit phase.
+    // TODO: Refactor class components so this is less awkward.
+    var didCaptureError = false;
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null && updateQueue.capturedValues !== null) {
+      shouldUpdate = true;
+      didCaptureError = true;
+    }
+    return finishClassComponent(
+      current,
+      workInProgress,
+      shouldUpdate,
+      hasContext,
+      didCaptureError,
+      renderExpirationTime
+    );
+  }
+
+  function finishClassComponent(
+    current,
+    workInProgress,
+    shouldUpdate,
+    hasContext,
+    didCaptureError,
+    renderExpirationTime
+  ) {
+    // Refs should update even if shouldComponentUpdate returns false
+    markRef(current, workInProgress);
+
+    if (!shouldUpdate && !didCaptureError) {
+      // Context providers should defer to sCU for rendering
+      if (hasContext) {
+        invalidateContextProvider(workInProgress, false);
+      }
+
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    var ctor = workInProgress.type;
+    var instance = workInProgress.stateNode;
+
+    // Rerender
+    ReactCurrentOwner.current = workInProgress;
+    var nextChildren = void 0;
+    if (
+      didCaptureError &&
+      (!enableGetDerivedStateFromCatch ||
+        typeof ctor.getDerivedStateFromCatch !== "function")
+    ) {
+      // If we captured an error, but getDerivedStateFrom catch is not defined,
+      // unmount all the children. componentDidCatch will schedule an update to
+      // re-render a fallback. This is temporary until we migrate everyone to
+      // the new API.
+      // TODO: Warn in a future release.
+      nextChildren = null;
+    } else {
+      {
+        ReactDebugCurrentFiber.setCurrentPhase("render");
+        nextChildren = instance.render();
+        if (
+          debugRenderPhaseSideEffects ||
+          (debugRenderPhaseSideEffectsForStrictMode &&
+            workInProgress.mode & StrictMode)
+        ) {
+          instance.render();
+        }
+        ReactDebugCurrentFiber.setCurrentPhase(null);
+      }
+    }
+
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
+    if (didCaptureError) {
+      // If we're recovering from an error, reconcile twice: first to delete
+      // all the existing children.
+      reconcileChildrenAtExpirationTime(
+        current,
+        workInProgress,
+        null,
+        renderExpirationTime
+      );
+      workInProgress.child = null;
+      // Now we can continue reconciling like normal. This has the effect of
+      // remounting all children regardless of whether their their
+      // identity matches.
+    }
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      nextChildren,
+      renderExpirationTime
+    );
+    // Memoize props and state using the values we just used to render.
+    // TODO: Restructure so we never read values from the instance.
+    memoizeState(workInProgress, instance.state);
+    memoizeProps(workInProgress, instance.props);
+
+    // The context might have changed so we need to recalculate it.
+    if (hasContext) {
+      invalidateContextProvider(workInProgress, true);
+    }
+
+    return workInProgress.child;
+  }
+
+  function pushHostRootContext(workInProgress) {
+    var root = workInProgress.stateNode;
+    if (root.pendingContext) {
+      pushTopLevelContextObject(
+        workInProgress,
+        root.pendingContext,
+        root.pendingContext !== root.context
+      );
+    } else if (root.context) {
+      // Should always be set
+      pushTopLevelContextObject(workInProgress, root.context, false);
+    }
+    pushHostContainer(workInProgress, root.containerInfo);
+  }
+
+  function updateHostRoot(current, workInProgress, renderExpirationTime) {
+    pushHostRootContext(workInProgress);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      var prevState = workInProgress.memoizedState;
+      var state = processUpdateQueue(
+        current,
+        workInProgress,
+        updateQueue,
+        null,
+        null,
+        renderExpirationTime
+      );
+      memoizeState(workInProgress, state);
+      updateQueue = workInProgress.updateQueue;
+
+      var element = void 0;
+      if (updateQueue !== null && updateQueue.capturedValues !== null) {
+        // There's an uncaught error. Unmount the whole root.
+        element = null;
+      } else if (prevState === state) {
+        // If the state is the same as before, that's a bailout because we had
+        // no work that expires at this time.
+        resetHydrationState();
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      } else {
+        element = state.element;
+      }
+      var root = workInProgress.stateNode;
+      if (
+        (current === null || current.child === null) &&
+        root.hydrate &&
+        enterHydrationState(workInProgress)
+      ) {
+        // If we don't have any current children this might be the first pass.
+        // We always try to hydrate. If this isn't a hydration pass there won't
+        // be any children to hydrate which is effectively the same thing as
+        // not hydrating.
+
+        // This is a bit of a hack. We track the host root as a placement to
+        // know that we're currently in a mounting state. That way isMounted
+        // works as expected. We must reset this before committing.
+        // TODO: Delete this when we delete isMounted and findDOMNode.
+        workInProgress.effectTag |= Placement;
+
+        // Ensure that children mount into this root without tracking
+        // side-effects. This ensures that we don't store Placement effects on
+        // nodes that will be hydrated.
+        workInProgress.child = mountChildFibers(
+          workInProgress,
+          null,
+          element,
+          renderExpirationTime
+        );
+      } else {
+        // Otherwise reset hydration state in case we aborted and resumed another
+        // root.
+        resetHydrationState();
+        reconcileChildren(current, workInProgress, element);
+      }
+      memoizeState(workInProgress, state);
+      return workInProgress.child;
+    }
+    resetHydrationState();
+    // If there is no update queue, that's a bailout because the root has no props.
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  }
+
+  function updateHostComponent(current, workInProgress, renderExpirationTime) {
+    pushHostContext(workInProgress);
+
+    if (current === null) {
+      tryToClaimNextHydratableInstance(workInProgress);
+    }
+
+    var type = workInProgress.type;
+    var memoizedProps = workInProgress.memoizedProps;
+    var nextProps = workInProgress.pendingProps;
+    var prevProps = current !== null ? current.memoizedProps : null;
+
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (memoizedProps === nextProps) {
+      var isHidden =
+        workInProgress.mode & AsyncMode &&
+        shouldDeprioritizeSubtree(type, nextProps);
+      if (isHidden) {
+        // Before bailing out, make sure we've deprioritized a hidden component.
+        workInProgress.expirationTime = Never;
+      }
+      if (!isHidden || renderExpirationTime !== Never) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+      // If we're rendering a hidden node at hidden priority, don't bailout. The
+      // parent is complete, but the children may not be.
+    }
+
+    var nextChildren = nextProps.children;
+    var isDirectTextChild = shouldSetTextContent(type, nextProps);
+
+    if (isDirectTextChild) {
+      // We special case a direct text child of a host node. This is a common
+      // case. We won't handle it as a reified child. We will instead handle
+      // this in the host environment that also have access to this prop. That
+      // avoids allocating another HostText fiber and traversing it.
+      nextChildren = null;
+    } else if (prevProps && shouldSetTextContent(type, prevProps)) {
+      // If we're switching from a direct text child to a normal child, or to
+      // empty, we need to schedule the text content to be reset.
+      workInProgress.effectTag |= ContentReset;
+    }
+
+    markRef(current, workInProgress);
+
+    // Check the host config to see if the children are offscreen/hidden.
+    if (
+      renderExpirationTime !== Never &&
+      workInProgress.mode & AsyncMode &&
+      shouldDeprioritizeSubtree(type, nextProps)
+    ) {
+      // Down-prioritize the children.
+      workInProgress.expirationTime = Never;
+      // Bailout and come back to this fiber later.
+      workInProgress.memoizedProps = nextProps;
+      return null;
+    }
+
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
+    return workInProgress.child;
+  }
+
+  function updateHostText(current, workInProgress) {
+    if (current === null) {
+      tryToClaimNextHydratableInstance(workInProgress);
+    }
+    var nextProps = workInProgress.pendingProps;
+    memoizeProps(workInProgress, nextProps);
+    // Nothing to do here. This is terminal. We'll do the completion step
+    // immediately after.
+    return null;
+  }
+
+  function mountIndeterminateComponent(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    invariant(
+      current === null,
+      "An indeterminate component should never have mounted. This error is " +
+        "likely caused by a bug in React. Please file an issue."
+    );
+    var fn = workInProgress.type;
+    var props = workInProgress.pendingProps;
+    var unmaskedContext = getUnmaskedContext(workInProgress);
+    var context = getMaskedContext(workInProgress, unmaskedContext);
+
+    var value = void 0;
+
+    {
+      if (fn.prototype && typeof fn.prototype.render === "function") {
+        var componentName = getComponentName(workInProgress) || "Unknown";
+
+        if (!didWarnAboutBadClass[componentName]) {
+          warning(
+            false,
+            "The <%s /> component appears to have a render method, but doesn't extend React.Component. " +
+              "This is likely to cause errors. Change %s to extend React.Component instead.",
+            componentName,
+            componentName
+          );
+          didWarnAboutBadClass[componentName] = true;
+        }
+      }
+      ReactCurrentOwner.current = workInProgress;
+      value = fn(props, context);
+    }
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
+
+    if (
+      typeof value === "object" &&
+      value !== null &&
+      typeof value.render === "function" &&
+      value.$$typeof === undefined
+    ) {
+      var Component = workInProgress.type;
+
+      // Proceed under the assumption that this is a class instance
+      workInProgress.tag = ClassComponent;
+
+      workInProgress.memoizedState =
+        value.state !== null && value.state !== undefined ? value.state : null;
+
+      if (typeof Component.getDerivedStateFromProps === "function") {
+        var partialState = callGetDerivedStateFromProps(
+          workInProgress,
+          value,
+          props,
+          workInProgress.memoizedState
+        );
+
+        if (partialState !== null && partialState !== undefined) {
+          workInProgress.memoizedState = Object.assign(
+            {},
+            workInProgress.memoizedState,
+            partialState
+          );
+        }
+      }
+
+      // Push context providers early to prevent context stack mismatches.
+      // During mounting we don't know the child context yet as the instance doesn't exist.
+      // We will invalidate the child context in finishClassComponent() right after rendering.
+      var hasContext = pushLegacyContextProvider(workInProgress);
+      adoptClassInstance(workInProgress, value);
+      mountClassInstance(workInProgress, renderExpirationTime);
+      return finishClassComponent(
+        current,
+        workInProgress,
+        true,
+        hasContext,
+        false,
+        renderExpirationTime
+      );
+    } else {
+      // Proceed under the assumption that this is a functional component
+      workInProgress.tag = FunctionalComponent;
+      {
+        var _Component = workInProgress.type;
+
+        if (_Component) {
+          !!_Component.childContextTypes
+            ? warning(
+                false,
+                "%s(...): childContextTypes cannot be defined on a functional component.",
+                _Component.displayName || _Component.name || "Component"
+              )
+            : void 0;
+        }
+        if (workInProgress.ref !== null) {
+          var info = "";
+          var ownerName = ReactDebugCurrentFiber.getCurrentFiberOwnerName();
+          if (ownerName) {
+            info += "\n\nCheck the render method of `" + ownerName + "`.";
+          }
+
+          var warningKey = ownerName || workInProgress._debugID || "";
+          var debugSource = workInProgress._debugSource;
+          if (debugSource) {
+            warningKey = debugSource.fileName + ":" + debugSource.lineNumber;
+          }
+          if (!didWarnAboutStatelessRefs[warningKey]) {
+            didWarnAboutStatelessRefs[warningKey] = true;
+            warning(
+              false,
+              "Stateless function components cannot be given refs. " +
+                "Attempts to access this ref will fail.%s%s",
+              info,
+              ReactDebugCurrentFiber.getCurrentFiberStackAddendum()
+            );
+          }
+        }
+
+        if (typeof fn.getDerivedStateFromProps === "function") {
+          var _componentName = getComponentName(workInProgress) || "Unknown";
+
+          if (
+            !didWarnAboutGetDerivedStateOnFunctionalComponent[_componentName]
+          ) {
+            warning(
+              false,
+              "%s: Stateless functional components do not support getDerivedStateFromProps.",
+              _componentName
+            );
+            didWarnAboutGetDerivedStateOnFunctionalComponent[
+              _componentName
+            ] = true;
+          }
+        }
+      }
+      reconcileChildren(current, workInProgress, value);
+      memoizeProps(workInProgress, props);
+      return workInProgress.child;
+    }
+  }
+
+  function updateCallComponent(current, workInProgress, renderExpirationTime) {
+    var nextProps = workInProgress.pendingProps;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextProps) {
+      nextProps = workInProgress.memoizedProps;
+      // TODO: When bailing out, we might need to return the stateNode instead
+      // of the child. To check it for work.
+      // return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    var nextChildren = nextProps.children;
+
+    // The following is a fork of reconcileChildrenAtExpirationTime but using
+    // stateNode to store the child.
+    if (current === null) {
+      workInProgress.stateNode = mountChildFibers(
+        workInProgress,
+        workInProgress.stateNode,
+        nextChildren,
+        renderExpirationTime
+      );
+    } else {
+      workInProgress.stateNode = reconcileChildFibers(
+        workInProgress,
+        current.stateNode,
+        nextChildren,
+        renderExpirationTime
+      );
+    }
+
+    memoizeProps(workInProgress, nextProps);
+    // This doesn't take arbitrary time so we could synchronously just begin
+    // eagerly do the work of workInProgress.child as an optimization.
+    return workInProgress.stateNode;
+  }
+
+  function updatePortalComponent(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
+    var nextChildren = workInProgress.pendingProps;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextChildren) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    if (current === null) {
+      // Portals are special because we don't append the children during mount
+      // but at commit. Therefore we need to track insertions which the normal
+      // flow doesn't do during mount. This doesn't happen at the root because
+      // the root always starts with a "current" with a null child.
+      // TODO: Consider unifying this with how the root works.
+      workInProgress.child = reconcileChildFibers(
+        workInProgress,
+        null,
+        nextChildren,
+        renderExpirationTime
+      );
+      memoizeProps(workInProgress, nextChildren);
+    } else {
+      reconcileChildren(current, workInProgress, nextChildren);
+      memoizeProps(workInProgress, nextChildren);
+    }
+    return workInProgress.child;
+  }
+
+  function propagateContextChange(
+    workInProgress,
+    context,
+    changedBits,
+    renderExpirationTime
+  ) {
+    var fiber = workInProgress.child;
+    if (fiber !== null) {
+      // Set the return pointer of the child to the work-in-progress fiber.
+      fiber["return"] = workInProgress;
+    }
+    while (fiber !== null) {
+      var nextFiber = void 0;
+      // Visit this fiber.
+      switch (fiber.tag) {
+        case ContextConsumer:
+          // Check if the context matches.
+          var observedBits = fiber.stateNode | 0;
+          if (fiber.type === context && (observedBits & changedBits) !== 0) {
+            // Update the expiration time of all the ancestors, including
+            // the alternates.
+            var node = fiber;
+            while (node !== null) {
+              var alternate = node.alternate;
+              if (
+                node.expirationTime === NoWork ||
+                node.expirationTime > renderExpirationTime
+              ) {
+                node.expirationTime = renderExpirationTime;
+                if (
+                  alternate !== null &&
+                  (alternate.expirationTime === NoWork ||
+                    alternate.expirationTime > renderExpirationTime)
+                ) {
+                  alternate.expirationTime = renderExpirationTime;
+                }
+              } else if (
+                alternate !== null &&
+                (alternate.expirationTime === NoWork ||
+                  alternate.expirationTime > renderExpirationTime)
+              ) {
+                alternate.expirationTime = renderExpirationTime;
+              } else {
+                // Neither alternate was updated, which means the rest of the
+                // ancestor path already has sufficient priority.
+                break;
+              }
+              node = node["return"];
+            }
+            // Don't scan deeper than a matching consumer. When we render the
+            // consumer, we'll continue scanning from that point. This way the
+            // scanning work is time-sliced.
+            nextFiber = null;
+          } else {
+            // Traverse down.
+            nextFiber = fiber.child;
+          }
+          break;
+        case ContextProvider:
+          // Don't scan deeper if this is a matching provider
+          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+          break;
+        default:
+          // Traverse down.
+          nextFiber = fiber.child;
+          break;
+      }
+      if (nextFiber !== null) {
+        // Set the return pointer of the child to the work-in-progress fiber.
+        nextFiber["return"] = fiber;
+      } else {
+        // No child. Traverse to next sibling.
+        nextFiber = fiber;
+        while (nextFiber !== null) {
+          if (nextFiber === workInProgress) {
+            // We're back to the root of this subtree. Exit.
+            nextFiber = null;
+            break;
+          }
+          var sibling = nextFiber.sibling;
+          if (sibling !== null) {
+            nextFiber = sibling;
+            break;
+          }
+          // No more siblings. Traverse up.
+          nextFiber = nextFiber["return"];
+        }
+      }
+      fiber = nextFiber;
+    }
+  }
+
+  function updateContextProvider(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var providerType = workInProgress.type;
+    var context = providerType._context;
+
+    var newProps = workInProgress.pendingProps;
+    var oldProps = workInProgress.memoizedProps;
+
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (oldProps === newProps) {
+      workInProgress.stateNode = 0;
+      pushProvider(workInProgress);
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    var newValue = newProps.value;
+    workInProgress.memoizedProps = newProps;
+
+    var changedBits = void 0;
+    if (oldProps === null) {
+      // Initial render
+      changedBits = MAX_SIGNED_31_BIT_INT;
+    } else {
+      if (oldProps.value === newProps.value) {
+        // No change. Bailout early if children are the same.
+        if (oldProps.children === newProps.children) {
+          workInProgress.stateNode = 0;
+          pushProvider(workInProgress);
+          return bailoutOnAlreadyFinishedWork(current, workInProgress);
+        }
+        changedBits = 0;
+      } else {
+        var oldValue = oldProps.value;
+        // Use Object.is to compare the new context value to the old value.
+        // Inlined Object.is polyfill.
+        // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+        if (
+          (oldValue === newValue &&
+            (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
+          (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
+        ) {
+          // No change. Bailout early if children are the same.
+          if (oldProps.children === newProps.children) {
+            workInProgress.stateNode = 0;
+            pushProvider(workInProgress);
+            return bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+          changedBits = 0;
+        } else {
+          changedBits =
+            typeof context._calculateChangedBits === "function"
+              ? context._calculateChangedBits(oldValue, newValue)
+              : MAX_SIGNED_31_BIT_INT;
+          {
+            !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
+              ? warning(
+                  false,
+                  "calculateChangedBits: Expected the return value to be a " +
+                    "31-bit integer. Instead received: %s",
+                  changedBits
+                )
+              : void 0;
+          }
+          changedBits |= 0;
+
+          if (changedBits === 0) {
+            // No change. Bailout early if children are the same.
+            if (oldProps.children === newProps.children) {
+              workInProgress.stateNode = 0;
+              pushProvider(workInProgress);
+              return bailoutOnAlreadyFinishedWork(current, workInProgress);
+            }
+          } else {
+            propagateContextChange(
+              workInProgress,
+              context,
+              changedBits,
+              renderExpirationTime
+            );
+          }
+        }
+      }
+    }
+
+    workInProgress.stateNode = changedBits;
+    pushProvider(workInProgress);
+
+    var newChildren = newProps.children;
+    reconcileChildren(current, workInProgress, newChildren);
+    return workInProgress.child;
+  }
+
+  function updateContextConsumer(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var context = workInProgress.type;
+    var newProps = workInProgress.pendingProps;
+    var oldProps = workInProgress.memoizedProps;
+
+    var newValue = context._currentValue;
+    var changedBits = context._changedBits;
+
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (changedBits === 0 && oldProps === newProps) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    workInProgress.memoizedProps = newProps;
+
+    var observedBits = newProps.unstable_observedBits;
+    if (observedBits === undefined || observedBits === null) {
+      // Subscribe to all changes by default
+      observedBits = MAX_SIGNED_31_BIT_INT;
+    }
+    // Store the observedBits on the fiber's stateNode for quick access.
+    workInProgress.stateNode = observedBits;
+
+    if ((changedBits & observedBits) !== 0) {
+      // Context change propagation stops at matching consumers, for time-
+      // slicing. Continue the propagation here.
+      propagateContextChange(
+        workInProgress,
+        context,
+        changedBits,
+        renderExpirationTime
+      );
+    } else if (oldProps === newProps) {
+      // Skip over a memoized parent with a bitmask bailout even
+      // if we began working on it because of a deeper matching child.
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    // There is no bailout on `children` equality because we expect people
+    // to often pass a bound method as a child, but it may reference
+    // `this.state` or `this.props` (and thus needs to re-render on `setState`).
+
+    var render = newProps.children;
+
+    {
+      !(typeof render === "function")
+        ? warning(
+            false,
+            "A context consumer was rendered with multiple children, or a child " +
+              "that isn't a function. A context consumer expects a single child " +
+              "that is a function. If you did pass a function, make sure there " +
+              "is no trailing or leading whitespace around it."
+          )
+        : void 0;
+    }
+
+    var newChildren = render(newValue);
+    reconcileChildren(current, workInProgress, newChildren);
+    return workInProgress.child;
+  }
+
+  /*
+  function reuseChildrenEffects(returnFiber : Fiber, firstChild : Fiber) {
+    let child = firstChild;
+    do {
+      // Ensure that the first and last effect of the parent corresponds
+      // to the children's first and last effect.
+      if (!returnFiber.firstEffect) {
+        returnFiber.firstEffect = child.firstEffect;
+      }
+      if (child.lastEffect) {
+        if (returnFiber.lastEffect) {
+          returnFiber.lastEffect.nextEffect = child.firstEffect;
+        }
+        returnFiber.lastEffect = child.lastEffect;
+      }
+    } while (child = child.sibling);
+  }
+  */
+
+  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+    cancelWorkTimer(workInProgress);
+
+    // TODO: We should ideally be able to bail out early if the children have no
+    // more work to do. However, since we don't have a separation of this
+    // Fiber's priority and its children yet - we don't know without doing lots
+    // of the same work we do anyway. Once we have that separation we can just
+    // bail out here if the children has no more work at this priority level.
+    // if (workInProgress.priorityOfChildren <= priorityLevel) {
+    //   // If there are side-effects in these children that have not yet been
+    //   // committed we need to ensure that they get properly transferred up.
+    //   if (current && current.child !== workInProgress.child) {
+    //     reuseChildrenEffects(workInProgress, child);
+    //   }
+    //   return null;
+    // }
+
+    cloneChildFibers(current, workInProgress);
+    return workInProgress.child;
+  }
+
+  function bailoutOnLowPriority(current, workInProgress) {
+    cancelWorkTimer(workInProgress);
+
+    // TODO: Handle HostComponent tags here as well and call pushHostContext()?
+    // See PR 8590 discussion for context
+    switch (workInProgress.tag) {
+      case HostRoot:
+        pushHostRootContext(workInProgress);
+        break;
+      case ClassComponent:
+        pushLegacyContextProvider(workInProgress);
+        break;
+      case HostPortal:
+        pushHostContainer(
+          workInProgress,
+          workInProgress.stateNode.containerInfo
+        );
+        break;
+      case ContextProvider:
+        pushProvider(workInProgress);
+        break;
+    }
+    // TODO: What if this is currently in progress?
+    // How can that happen? How is this not being cloned?
+    return null;
+  }
+
+  // TODO: Delete memoizeProps/State and move to reconcile/bailout instead
+  function memoizeProps(workInProgress, nextProps) {
+    workInProgress.memoizedProps = nextProps;
+  }
+
+  function memoizeState(workInProgress, nextState) {
+    workInProgress.memoizedState = nextState;
+    // Don't reset the updateQueue, in case there are pending updates. Resetting
+    // is handled by processUpdateQueue.
+  }
+
+  function beginWork(current, workInProgress, renderExpirationTime) {
+    if (
+      workInProgress.expirationTime === NoWork ||
+      workInProgress.expirationTime > renderExpirationTime
+    ) {
+      return bailoutOnLowPriority(current, workInProgress);
+    }
+
+    switch (workInProgress.tag) {
+      case IndeterminateComponent:
+        return mountIndeterminateComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case FunctionalComponent:
+        return updateFunctionalComponent(current, workInProgress);
+      case ClassComponent:
+        return updateClassComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case HostRoot:
+        return updateHostRoot(current, workInProgress, renderExpirationTime);
+      case HostComponent:
+        return updateHostComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case HostText:
+        return updateHostText(current, workInProgress);
+      case CallHandlerPhase:
+        // This is a restart. Reset the tag to the initial phase.
+        workInProgress.tag = CallComponent;
+      // Intentionally fall through since this is now the same.
+      case CallComponent:
+        return updateCallComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case ReturnComponent:
+        // A return component is just a placeholder, we can just run through the
+        // next one immediately.
+        return null;
+      case HostPortal:
+        return updatePortalComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case ForwardRef:
+        return updateForwardRef(current, workInProgress);
+      case Fragment:
+        return updateFragment(current, workInProgress);
+      case Mode:
+        return updateMode(current, workInProgress);
+      case ContextProvider:
+        return updateContextProvider(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case ContextConsumer:
+        return updateContextConsumer(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      default:
+        invariant(
+          false,
+          "Unknown unit of work tag. This error is likely caused by a bug in " +
+            "React. Please file an issue."
+        );
+    }
+  }
+
+  return {
+    beginWork: beginWork
+  };
+};
+
+var ReactFiberCompleteWork = function(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext
+) {
+  var createInstance = config.createInstance,
+    createTextInstance = config.createTextInstance,
+    appendInitialChild = config.appendInitialChild,
+    finalizeInitialChildren = config.finalizeInitialChildren,
+    prepareUpdate = config.prepareUpdate,
+    mutation = config.mutation,
+    persistence = config.persistence;
+  var getRootHostContainer = hostContext.getRootHostContainer,
+    popHostContext = hostContext.popHostContext,
+    getHostContext = hostContext.getHostContext,
+    popHostContainer = hostContext.popHostContainer;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+  var prepareToHydrateHostInstance =
+      hydrationContext.prepareToHydrateHostInstance,
+    prepareToHydrateHostTextInstance =
+      hydrationContext.prepareToHydrateHostTextInstance,
+    popHydrationState = hydrationContext.popHydrationState;
+
+  function markUpdate(workInProgress) {
+    // Tag the fiber with an update effect. This turns a Placement into
+    // a PlacementAndUpdate.
+    workInProgress.effectTag |= Update;
+  }
+
+  function markRef(workInProgress) {
+    workInProgress.effectTag |= Ref;
+  }
+
+  function appendAllReturns(returns, workInProgress) {
+    var node = workInProgress.stateNode;
+    if (node) {
+      node["return"] = workInProgress;
+    }
+    while (node !== null) {
+      if (
+        node.tag === HostComponent ||
+        node.tag === HostText ||
+        node.tag === HostPortal
+      ) {
+        invariant(false, "A call cannot have host component children.");
+      } else if (node.tag === ReturnComponent) {
+        returns.push(node.pendingProps.value);
+      } else if (node.child !== null) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === workInProgress) {
+          return;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  function moveCallToHandlerPhase(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var props = workInProgress.memoizedProps;
+    invariant(
+      props,
+      "Should be resolved by now. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+
+    // First step of the call has completed. Now we need to do the second.
+    // TODO: It would be nice to have a multi stage call represented by a
+    // single component, or at least tail call optimize nested ones. Currently
+    // that requires additional fields that we don't want to add to the fiber.
+    // So this requires nested handlers.
+    // Note: This doesn't mutate the alternate node. I don't think it needs to
+    // since this stage is reset for every pass.
+    workInProgress.tag = CallHandlerPhase;
+
+    // Build up the returns.
+    // TODO: Compare this to a generator or opaque helpers like Children.
+    var returns = [];
+    appendAllReturns(returns, workInProgress);
+    var fn = props.handler;
+    var childProps = props.props;
+    var nextChildren = fn(childProps, returns);
+
+    var currentFirstChild = current !== null ? current.child : null;
+    workInProgress.child = reconcileChildFibers(
+      workInProgress,
+      currentFirstChild,
+      nextChildren,
+      renderExpirationTime
+    );
+    return workInProgress.child;
+  }
+
+  function appendAllChildren(parent, workInProgress) {
+    // We only have the top Fiber that was created but we need recurse down its
+    // children to find all the terminal nodes.
+    var node = workInProgress.child;
+    while (node !== null) {
+      if (node.tag === HostComponent || node.tag === HostText) {
+        appendInitialChild(parent, node.stateNode);
+      } else if (node.tag === HostPortal) {
+        // If we have a portal child, then we don't want to traverse
+        // down its children. Instead, we'll get insertions from each child in
+        // the portal directly.
+      } else if (node.child !== null) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      if (node === workInProgress) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === workInProgress) {
+          return;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  var updateHostContainer = void 0;
+  var updateHostComponent = void 0;
+  var updateHostText = void 0;
+  if (mutation) {
+    if (enableMutatingReconciler) {
+      // Mutation mode
+      updateHostContainer = function(workInProgress) {
+        // Noop
+      };
+      updateHostComponent = function(
+        current,
+        workInProgress,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        rootContainerInstance,
+        currentHostContext
+      ) {
+        // TODO: Type this specific to this type of component.
+        workInProgress.updateQueue = updatePayload;
+        // If the update payload indicates that there is a change or if there
+        // is a new ref we mark this as an update. All the work is done in commitWork.
+        if (updatePayload) {
+          markUpdate(workInProgress);
+        }
+      };
+      updateHostText = function(current, workInProgress, oldText, newText) {
+        // If the text differs, mark it as an update. All the work in done in commitWork.
+        if (oldText !== newText) {
+          markUpdate(workInProgress);
+        }
+      };
+    } else {
+      invariant(false, "Mutating reconciler is disabled.");
+    }
+  } else if (persistence) {
+    if (enablePersistentReconciler) {
+      // Persistent host tree mode
+      var cloneInstance = persistence.cloneInstance,
+        createContainerChildSet = persistence.createContainerChildSet,
+        appendChildToContainerChildSet =
+          persistence.appendChildToContainerChildSet,
+        finalizeContainerChildren = persistence.finalizeContainerChildren;
+
+      // An unfortunate fork of appendAllChildren because we have two different parent types.
+
+      var appendAllChildrenToContainer = function(
+        containerChildSet,
+        workInProgress
+      ) {
+        // We only have the top Fiber that was created but we need recurse down its
+        // children to find all the terminal nodes.
+        var node = workInProgress.child;
+        while (node !== null) {
+          if (node.tag === HostComponent || node.tag === HostText) {
+            appendChildToContainerChildSet(containerChildSet, node.stateNode);
+          } else if (node.tag === HostPortal) {
+            // If we have a portal child, then we don't want to traverse
+            // down its children. Instead, we'll get insertions from each child in
+            // the portal directly.
+          } else if (node.child !== null) {
+            node.child["return"] = node;
+            node = node.child;
+            continue;
+          }
+          if (node === workInProgress) {
+            return;
+          }
+          while (node.sibling === null) {
+            if (node["return"] === null || node["return"] === workInProgress) {
+              return;
+            }
+            node = node["return"];
+          }
+          node.sibling["return"] = node["return"];
+          node = node.sibling;
+        }
+      };
+      updateHostContainer = function(workInProgress) {
+        var portalOrRoot = workInProgress.stateNode;
+        var childrenUnchanged = workInProgress.firstEffect === null;
+        if (childrenUnchanged) {
+          // No changes, just reuse the existing instance.
+        } else {
+          var container = portalOrRoot.containerInfo;
+          var newChildSet = createContainerChildSet(container);
+          // If children might have changed, we have to add them all to the set.
+          appendAllChildrenToContainer(newChildSet, workInProgress);
+          portalOrRoot.pendingChildren = newChildSet;
+          // Schedule an update on the container to swap out the container.
+          markUpdate(workInProgress);
+          finalizeContainerChildren(container, newChildSet);
+        }
+      };
+      updateHostComponent = function(
+        current,
+        workInProgress,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        rootContainerInstance,
+        currentHostContext
+      ) {
+        // If there are no effects associated with this node, then none of our children had any updates.
+        // This guarantees that we can reuse all of them.
+        var childrenUnchanged = workInProgress.firstEffect === null;
+        var currentInstance = current.stateNode;
+        if (childrenUnchanged && updatePayload === null) {
+          // No changes, just reuse the existing instance.
+          // Note that this might release a previous clone.
+          workInProgress.stateNode = currentInstance;
+        } else {
+          var recyclableInstance = workInProgress.stateNode;
+          var newInstance = cloneInstance(
+            currentInstance,
+            updatePayload,
+            type,
+            oldProps,
+            newProps,
+            workInProgress,
+            childrenUnchanged,
+            recyclableInstance
+          );
+          if (
+            finalizeInitialChildren(
+              newInstance,
+              type,
+              newProps,
+              rootContainerInstance,
+              currentHostContext
+            )
+          ) {
+            markUpdate(workInProgress);
+          }
+          workInProgress.stateNode = newInstance;
+          if (childrenUnchanged) {
+            // If there are no other effects in this tree, we need to flag this node as having one.
+            // Even though we're not going to use it for anything.
+            // Otherwise parents won't know that there are new children to propagate upwards.
+            markUpdate(workInProgress);
+          } else {
+            // If children might have changed, we have to add them all to the set.
+            appendAllChildren(newInstance, workInProgress);
+          }
+        }
+      };
+      updateHostText = function(current, workInProgress, oldText, newText) {
+        if (oldText !== newText) {
+          // If the text content differs, we'll create a new text instance for it.
+          var rootContainerInstance = getRootHostContainer();
+          var currentHostContext = getHostContext();
+          workInProgress.stateNode = createTextInstance(
+            newText,
+            rootContainerInstance,
+            currentHostContext,
+            workInProgress
+          );
+          // We'll have to mark it as having an effect, even though we won't use the effect for anything.
+          // This lets the parents know that at least one of their children has changed.
+          markUpdate(workInProgress);
+        }
+      };
+    } else {
+      invariant(false, "Persistent reconciler is disabled.");
+    }
+  } else {
+    if (enableNoopReconciler) {
+      // No host operations
+      updateHostContainer = function(workInProgress) {
+        // Noop
+      };
+      updateHostComponent = function(
+        current,
+        workInProgress,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        rootContainerInstance,
+        currentHostContext
+      ) {
+        // Noop
+      };
+      updateHostText = function(current, workInProgress, oldText, newText) {
+        // Noop
+      };
+    } else {
+      invariant(false, "Noop reconciler is disabled.");
+    }
+  }
+
+  function completeWork(current, workInProgress, renderExpirationTime) {
+    var newProps = workInProgress.pendingProps;
+    switch (workInProgress.tag) {
+      case FunctionalComponent:
+        return null;
+      case ClassComponent: {
+        // We are leaving this subtree, so pop context if any.
+        popLegacyContextProvider(workInProgress);
+
+        // If this component caught an error, schedule an error log effect.
+        var instance = workInProgress.stateNode;
+        var updateQueue = workInProgress.updateQueue;
+        if (updateQueue !== null && updateQueue.capturedValues !== null) {
+          workInProgress.effectTag &= ~DidCapture;
+          if (typeof instance.componentDidCatch === "function") {
+            workInProgress.effectTag |= ErrLog;
+          } else {
+            // Normally we clear this in the commit phase, but since we did not
+            // schedule an effect, we need to reset it here.
+            updateQueue.capturedValues = null;
+          }
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var fiberRoot = workInProgress.stateNode;
+        if (fiberRoot.pendingContext) {
+          fiberRoot.context = fiberRoot.pendingContext;
+          fiberRoot.pendingContext = null;
+        }
+        if (current === null || current.child === null) {
+          // If we hydrated, pop so that we can delete any remaining children
+          // that weren't hydrated.
+          popHydrationState(workInProgress);
+          // This resets the hacky state to fix isMounted before committing.
+          // TODO: Delete this when we delete isMounted and findDOMNode.
+          workInProgress.effectTag &= ~Placement;
+        }
+        updateHostContainer(workInProgress);
+
+        var _updateQueue = workInProgress.updateQueue;
+        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
+          workInProgress.effectTag |= ErrLog;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        var rootContainerInstance = getRootHostContainer();
+        var type = workInProgress.type;
+        if (current !== null && workInProgress.stateNode != null) {
+          // If we have an alternate, that means this is an update and we need to
+          // schedule a side-effect to do the updates.
+          var oldProps = current.memoizedProps;
+          // If we get updated because one of our children updated, we don't
+          // have newProps so we'll have to reuse them.
+          // TODO: Split the update API as separate for the props vs. children.
+          // Even better would be if children weren't special cased at all tho.
+          var _instance = workInProgress.stateNode;
+          var currentHostContext = getHostContext();
+          // TODO: Experiencing an error where oldProps is null. Suggests a host
+          // component is hitting the resume path. Figure out why. Possibly
+          // related to `hidden`.
+          var updatePayload = prepareUpdate(
+            _instance,
+            type,
+            oldProps,
+            newProps,
+            rootContainerInstance,
+            currentHostContext
+          );
+
+          updateHostComponent(
+            current,
+            workInProgress,
+            updatePayload,
+            type,
+            oldProps,
+            newProps,
+            rootContainerInstance,
+            currentHostContext
+          );
+
+          if (current.ref !== workInProgress.ref) {
+            markRef(workInProgress);
+          }
+        } else {
+          if (!newProps) {
+            invariant(
+              workInProgress.stateNode !== null,
+              "We must have new props for new mounts. This error is likely " +
+                "caused by a bug in React. Please file an issue."
+            );
+            // This can happen when we abort work.
+            return null;
+          }
+
+          var _currentHostContext = getHostContext();
+          // TODO: Move createInstance to beginWork and keep it on a context
+          // "stack" as the parent. Then append children as we go in beginWork
+          // or completeWork depending on we want to add then top->down or
+          // bottom->up. Top->down is faster in IE11.
+          var wasHydrated = popHydrationState(workInProgress);
+          if (wasHydrated) {
+            // TODO: Move this and createInstance step into the beginPhase
+            // to consolidate.
+            if (
+              prepareToHydrateHostInstance(
+                workInProgress,
+                rootContainerInstance,
+                _currentHostContext
+              )
+            ) {
+              // If changes to the hydrated node needs to be applied at the
+              // commit-phase we mark this as such.
+              markUpdate(workInProgress);
+            }
+          } else {
+            var _instance2 = createInstance(
+              type,
+              newProps,
+              rootContainerInstance,
+              _currentHostContext,
+              workInProgress
+            );
+
+            appendAllChildren(_instance2, workInProgress);
+
+            // Certain renderers require commit-time effects for initial mount.
+            // (eg DOM renderer supports auto-focus for certain elements).
+            // Make sure such renderers get scheduled for later work.
+            if (
+              finalizeInitialChildren(
+                _instance2,
+                type,
+                newProps,
+                rootContainerInstance,
+                _currentHostContext
+              )
+            ) {
+              markUpdate(workInProgress);
+            }
+            workInProgress.stateNode = _instance2;
+          }
+
+          if (workInProgress.ref !== null) {
+            // If there is a ref on a host node we need to schedule a callback
+            markRef(workInProgress);
+          }
+        }
+        return null;
+      }
+      case HostText: {
+        var newText = newProps;
+        if (current && workInProgress.stateNode != null) {
+          var oldText = current.memoizedProps;
+          // If we have an alternate, that means this is an update and we need
+          // to schedule a side-effect to do the updates.
+          updateHostText(current, workInProgress, oldText, newText);
+        } else {
+          if (typeof newText !== "string") {
+            invariant(
+              workInProgress.stateNode !== null,
+              "We must have new props for new mounts. This error is likely " +
+                "caused by a bug in React. Please file an issue."
+            );
+            // This can happen when we abort work.
+            return null;
+          }
+          var _rootContainerInstance = getRootHostContainer();
+          var _currentHostContext2 = getHostContext();
+          var _wasHydrated = popHydrationState(workInProgress);
+          if (_wasHydrated) {
+            if (prepareToHydrateHostTextInstance(workInProgress)) {
+              markUpdate(workInProgress);
+            }
+          } else {
+            workInProgress.stateNode = createTextInstance(
+              newText,
+              _rootContainerInstance,
+              _currentHostContext2,
+              workInProgress
+            );
+          }
+        }
+        return null;
+      }
+      case CallComponent:
+        return moveCallToHandlerPhase(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case CallHandlerPhase:
+        // Reset the tag to now be a first phase call.
+        workInProgress.tag = CallComponent;
+        return null;
+      case ReturnComponent:
+        // Does nothing.
+        return null;
+      case ForwardRef:
+        return null;
+      case Fragment:
+        return null;
+      case Mode:
+        return null;
+      case HostPortal:
+        popHostContainer(workInProgress);
+        updateHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        // Pop provider fiber
+        popProvider(workInProgress);
+        return null;
+      case ContextConsumer:
+        return null;
+      // Error cases
+      case IndeterminateComponent:
+        invariant(
+          false,
+          "An indeterminate component should have become determinate before " +
+            "completing. This error is likely caused by a bug in React. Please " +
+            "file an issue."
+        );
+      // eslint-disable-next-line no-fallthrough
+      default:
+        invariant(
+          false,
+          "Unknown unit of work tag. This error is likely caused by a bug in " +
+            "React. Please file an issue."
+        );
+    }
+  }
+
+  return {
+    completeWork: completeWork
+  };
+};
+
+function createCapturedValue(value, source) {
+  // If the value is an error, call this function immediately after it is thrown
+  // so the stack is accurate.
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
+
+var ReactFiberUnwindWork = function(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  isAlreadyFailedLegacyErrorBoundary
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+
+  function throwException(returnFiber, sourceFiber, rawValue) {
+    // The source fiber did not complete.
+    sourceFiber.effectTag |= Incomplete;
+    // Its effect list is no longer valid.
+    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+
+    var value = createCapturedValue(rawValue, sourceFiber);
+
+    var workInProgress = returnFiber;
+    do {
+      switch (workInProgress.tag) {
+        case HostRoot: {
+          // Uncaught error
+          var errorInfo = value;
+          ensureUpdateQueues(workInProgress);
+          var updateQueue = workInProgress.updateQueue;
+          updateQueue.capturedValues = [errorInfo];
+          workInProgress.effectTag |= ShouldCapture;
+          return;
+        }
+        case ClassComponent:
+          // Capture and retry
+          var ctor = workInProgress.type;
+          var _instance = workInProgress.stateNode;
+          if (
+            (workInProgress.effectTag & DidCapture) === NoEffect &&
+            ((typeof ctor.getDerivedStateFromCatch === "function" &&
+              enableGetDerivedStateFromCatch) ||
+              (_instance !== null &&
+                typeof _instance.componentDidCatch === "function" &&
+                !isAlreadyFailedLegacyErrorBoundary(_instance)))
+          ) {
+            ensureUpdateQueues(workInProgress);
+            var _updateQueue = workInProgress.updateQueue;
+            var capturedValues = _updateQueue.capturedValues;
+            if (capturedValues === null) {
+              _updateQueue.capturedValues = [value];
+            } else {
+              capturedValues.push(value);
+            }
+            workInProgress.effectTag |= ShouldCapture;
+            return;
+          }
+          break;
+        default:
+          break;
+      }
+      workInProgress = workInProgress["return"];
+    } while (workInProgress !== null);
+  }
+
+  function unwindWork(workInProgress) {
+    switch (workInProgress.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(workInProgress);
+        var effectTag = workInProgress.effectTag;
+        if (effectTag & ShouldCapture) {
+          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var _effectTag = workInProgress.effectTag;
+        if (_effectTag & ShouldCapture) {
+          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        return null;
+      }
+      case HostPortal:
+        popHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        popProvider(workInProgress);
+        return null;
+      default:
+        return null;
+    }
+  }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      default:
+        break;
+    }
+  }
+
+  return {
+    throwException: throwException,
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork
+  };
+};
+
+// This module is forked in different environments.
+// By default, return `true` to log errors to the console.
+// Forks can return `false` if this isn't desirable.
+function showErrorDialog(capturedError) {
+  return true;
+}
+
+function logCapturedError(capturedError) {
+  var logError = showErrorDialog(capturedError);
+
+  // Allow injected showErrorDialog() to prevent default console.error logging.
+  // This enables renderers like ReactNative to better manage redbox behavior.
+  if (logError === false) {
+    return;
+  }
+
+  var error = capturedError.error;
+  var suppressLogging = error && error.suppressReactErrorLogging;
+  if (suppressLogging) {
+    return;
+  }
+
+  {
+    var componentName = capturedError.componentName,
+      componentStack = capturedError.componentStack,
+      errorBoundaryName = capturedError.errorBoundaryName,
+      errorBoundaryFound = capturedError.errorBoundaryFound,
+      willRetry = capturedError.willRetry;
+
+    var componentNameMessage = componentName
+      ? "The above error occurred in the <" + componentName + "> component:"
+      : "The above error occurred in one of your React components:";
+
+    var errorBoundaryMessage = void 0;
+    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
+    if (errorBoundaryFound && errorBoundaryName) {
+      if (willRetry) {
+        errorBoundaryMessage =
+          "React will try to recreate this component tree from scratch " +
+          ("using the error boundary you provided, " + errorBoundaryName + ".");
+      } else {
+        errorBoundaryMessage =
+          "This error was initially handled by the error boundary " +
+          errorBoundaryName +
+          ".\n" +
+          "Recreating the tree from scratch failed so React will unmount the tree.";
+      }
+    } else {
+      errorBoundaryMessage =
+        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
+        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
+    }
+    var combinedMessage =
+      "" +
+      componentNameMessage +
+      componentStack +
+      "\n\n" +
+      ("" + errorBoundaryMessage);
+
+    // In development, we provide our own message with just the component stack.
+    // We don't include the original error message and JS stack because the browser
+    // has already printed it. Even if the application swallows the error, it is still
+    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
+    console.error(combinedMessage);
+  }
+}
+
+var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
+var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
+
+var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
+{
+  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
+}
+
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source;
+  var stack = errorInfo.stack;
+  if (stack === null) {
+    stack = getStackAddendumByWorkInProgressFiber(source);
+  }
+
+  var capturedError = {
+    componentName: source !== null ? getComponentName(source) : null,
+    componentStack: stack !== null ? stack : "",
+    error: errorInfo.value,
+    errorBoundary: null,
+    errorBoundaryName: null,
+    errorBoundaryFound: false,
+    willRetry: false
+  };
+
+  if (boundary !== null && boundary.tag === ClassComponent) {
+    capturedError.errorBoundary = boundary.stateNode;
+    capturedError.errorBoundaryName = getComponentName(boundary);
+    capturedError.errorBoundaryFound = true;
+    capturedError.willRetry = true;
+  }
+
+  try {
+    logCapturedError(capturedError);
+  } catch (e) {
+    // Prevent cycle if logCapturedError() throws.
+    // A cycle may still occur if logCapturedError renders a component that throws.
+    var suppressLogging = e && e.suppressReactErrorLogging;
+    if (!suppressLogging) {
+      console.error(e);
+    }
+  }
+}
+
+var ReactFiberCommitWork = function(
+  config,
+  captureError,
+  scheduleWork,
+  computeExpirationForFiber,
+  markLegacyErrorBoundaryAsFailed,
+  recalculateCurrentTime
+) {
+  var getPublicInstance = config.getPublicInstance,
+    mutation = config.mutation,
+    persistence = config.persistence;
+
+  var callComponentWillUnmountWithTimer = function(current, instance) {
+    startPhaseTimer(current, "componentWillUnmount");
+    instance.props = current.memoizedProps;
+    instance.state = current.memoizedState;
+    instance.componentWillUnmount();
+    stopPhaseTimer();
+  };
+
+  // Capture errors so they don't interrupt unmounting.
+  function safelyCallComponentWillUnmount(current, instance) {
+    {
+      invokeGuardedCallback$3(
+        null,
+        callComponentWillUnmountWithTimer,
+        null,
+        current,
+        instance
+      );
+      if (hasCaughtError$1()) {
+        var unmountError = clearCaughtError$1();
+        captureError(current, unmountError);
+      }
+    }
+  }
+
+  function safelyDetachRef(current) {
+    var ref = current.ref;
+    if (ref !== null) {
+      if (typeof ref === "function") {
+        {
+          invokeGuardedCallback$3(null, ref, null, null);
+          if (hasCaughtError$1()) {
+            var refError = clearCaughtError$1();
+            captureError(current, refError);
+          }
+        }
+      } else {
+        ref.current = null;
+      }
+    }
+  }
+
+  function commitBeforeMutationLifeCycles(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        if (finishedWork.effectTag & Snapshot) {
+          if (current !== null) {
+            var prevProps = current.memoizedProps;
+            var prevState = current.memoizedState;
+            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
+            var _instance = finishedWork.stateNode;
+            _instance.props = finishedWork.memoizedProps;
+            _instance.state = finishedWork.memoizedState;
+            var snapshot = _instance.getSnapshotBeforeUpdate(
+              prevProps,
+              prevState
+            );
+            {
+              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
+              if (
+                snapshot === undefined &&
+                !didWarnSet.has(finishedWork.type)
+              ) {
+                didWarnSet.add(finishedWork.type);
+                warning(
+                  false,
+                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
+                    "must be returned. You have returned undefined.",
+                  getComponentName(finishedWork)
+                );
+              }
+            }
+            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+            stopPhaseTimer();
+          }
+        }
+        return;
+      }
+      case HostRoot:
+      case HostComponent:
+      case HostText:
+      case HostPortal:
+        // Nothing to do for these component types
+        return;
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
+  function commitLifeCycles(
+    finishedRoot,
+    current,
+    finishedWork,
+    currentTime,
+    committedExpirationTime
+  ) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        var _instance2 = finishedWork.stateNode;
+        if (finishedWork.effectTag & Update) {
+          if (current === null) {
+            startPhaseTimer(finishedWork, "componentDidMount");
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidMount();
+            stopPhaseTimer();
+          } else {
+            var prevProps = current.memoizedProps;
+            var prevState = current.memoizedState;
+            startPhaseTimer(finishedWork, "componentDidUpdate");
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidUpdate(
+              prevProps,
+              prevState,
+              _instance2.__reactInternalSnapshotBeforeUpdate
+            );
+            stopPhaseTimer();
+          }
+        }
+        var updateQueue = finishedWork.updateQueue;
+        if (updateQueue !== null) {
+          commitCallbacks(updateQueue, _instance2);
+        }
+        return;
+      }
+      case HostRoot: {
+        var _updateQueue = finishedWork.updateQueue;
+        if (_updateQueue !== null) {
+          var _instance3 = null;
+          if (finishedWork.child !== null) {
+            switch (finishedWork.child.tag) {
+              case HostComponent:
+                _instance3 = getPublicInstance(finishedWork.child.stateNode);
+                break;
+              case ClassComponent:
+                _instance3 = finishedWork.child.stateNode;
+                break;
+            }
+          }
+          commitCallbacks(_updateQueue, _instance3);
+        }
+        return;
+      }
+      case HostComponent: {
+        var _instance4 = finishedWork.stateNode;
+
+        // Renderers may schedule work to be done after host components are mounted
+        // (eg DOM renderer may schedule auto-focus for inputs and form controls).
+        // These effects should only be committed when components are first mounted,
+        // aka when there is no current/alternate.
+        if (current === null && finishedWork.effectTag & Update) {
+          var type = finishedWork.type;
+          var props = finishedWork.memoizedProps;
+          commitMount(_instance4, type, props, finishedWork);
+        }
+
+        return;
+      }
+      case HostText: {
+        // We have no life-cycles associated with text.
+        return;
+      }
+      case HostPortal: {
+        // We have no life-cycles associated with portals.
+        return;
+      }
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
+  function commitErrorLogging(finishedWork, onUncaughtError) {
+    switch (finishedWork.tag) {
+      case ClassComponent:
+        {
+          var ctor = finishedWork.type;
+          var _instance5 = finishedWork.stateNode;
+          var updateQueue = finishedWork.updateQueue;
+          invariant(
+            updateQueue !== null && updateQueue.capturedValues !== null,
+            "An error logging effect should not have been scheduled if no errors " +
+              "were captured. This error is likely caused by a bug in React. " +
+              "Please file an issue."
+          );
+          var capturedErrors = updateQueue.capturedValues;
+          updateQueue.capturedValues = null;
+
+          if (typeof ctor.getDerivedStateFromCatch !== "function") {
+            // To preserve the preexisting retry behavior of error boundaries,
+            // we keep track of which ones already failed during this batch.
+            // This gets reset before we yield back to the browser.
+            // TODO: Warn in strict mode if getDerivedStateFromCatch is
+            // not defined.
+            markLegacyErrorBoundaryAsFailed(_instance5);
+          }
+
+          _instance5.props = finishedWork.memoizedProps;
+          _instance5.state = finishedWork.memoizedState;
+          for (var i = 0; i < capturedErrors.length; i++) {
+            var errorInfo = capturedErrors[i];
+            var _error = errorInfo.value;
+            var stack = errorInfo.stack;
+            logError(finishedWork, errorInfo);
+            _instance5.componentDidCatch(_error, {
+              componentStack: stack !== null ? stack : ""
+            });
+          }
+        }
+        break;
+      case HostRoot: {
+        var _updateQueue2 = finishedWork.updateQueue;
+        invariant(
+          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
+          "An error logging effect should not have been scheduled if no errors " +
+            "were captured. This error is likely caused by a bug in React. " +
+            "Please file an issue."
+        );
+        var _capturedErrors = _updateQueue2.capturedValues;
+        _updateQueue2.capturedValues = null;
+        for (var _i = 0; _i < _capturedErrors.length; _i++) {
+          var _errorInfo = _capturedErrors[_i];
+          logError(finishedWork, _errorInfo);
+          onUncaughtError(_errorInfo.value);
+        }
+        break;
+      }
+      default:
+        invariant(
+          false,
+          "This unit of work tag cannot capture errors.  This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
+
+  function commitAttachRef(finishedWork) {
+    var ref = finishedWork.ref;
+    if (ref !== null) {
+      var _instance6 = finishedWork.stateNode;
+      var instanceToUse = void 0;
+      switch (finishedWork.tag) {
+        case HostComponent:
+          instanceToUse = getPublicInstance(_instance6);
+          break;
+        default:
+          instanceToUse = _instance6;
+      }
+      if (typeof ref === "function") {
+        ref(instanceToUse);
+      } else {
+        {
+          if (!ref.hasOwnProperty("current")) {
+            warning(
+              false,
+              "Unexpected ref object provided for %s. " +
+                "Use either a ref-setter function or React.createRef().%s",
+              getComponentName(finishedWork),
+              getStackAddendumByWorkInProgressFiber(finishedWork)
+            );
+          }
+        }
+
+        ref.current = instanceToUse;
+      }
+    }
+  }
+
+  function commitDetachRef(current) {
+    var currentRef = current.ref;
+    if (currentRef !== null) {
+      if (typeof currentRef === "function") {
+        currentRef(null);
+      } else {
+        currentRef.current = null;
+      }
+    }
+  }
+
+  // User-originating errors (lifecycles and refs) should not interrupt
+  // deletion, so don't let them throw. Host-originating errors should
+  // interrupt deletion, so it's okay
+  function commitUnmount(current) {
+    if (typeof onCommitUnmount === "function") {
+      onCommitUnmount(current);
+    }
+
+    switch (current.tag) {
+      case ClassComponent: {
+        safelyDetachRef(current);
+        var _instance7 = current.stateNode;
+        if (typeof _instance7.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance7);
+        }
+        return;
+      }
+      case HostComponent: {
+        safelyDetachRef(current);
+        return;
+      }
+      case CallComponent: {
+        commitNestedUnmounts(current.stateNode);
+        return;
+      }
+      case HostPortal: {
+        // TODO: this is recursive.
+        // We are also not using this parent because
+        // the portal will get pushed immediately.
+        if (enableMutatingReconciler && mutation) {
+          unmountHostComponents(current);
+        } else if (enablePersistentReconciler && persistence) {
+          emptyPortalContainer(current);
+        }
+        return;
+      }
+    }
+  }
+
+  function commitNestedUnmounts(root) {
+    // While we're inside a removed host node we don't want to call
+    // removeChild on the inner nodes because they're removed by the top
+    // call anyway. We also want to call componentWillUnmount on all
+    // composites before this host node is removed from the tree. Therefore
+    var node = root;
+    while (true) {
+      commitUnmount(node);
+      // Visit children because they may contain more composite or host nodes.
+      // Skip portals because commitUnmount() currently visits them recursively.
+      if (
+        node.child !== null &&
+        // If we use mutation we drill down into portals using commitUnmount above.
+        // If we don't use mutation we drill down into portals here instead.
+        (!mutation || node.tag !== HostPortal)
+      ) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      if (node === root) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === root) {
+          return;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  function detachFiber(current) {
+    // Cut off the return pointers to disconnect it from the tree. Ideally, we
+    // should clear the child pointer of the parent alternate to let this
+    // get GC:ed but we don't know which for sure which parent is the current
+    // one so we'll settle for GC:ing the subtree of this child. This child
+    // itself will be GC:ed when the parent updates the next time.
+    current["return"] = null;
+    current.child = null;
+    if (current.alternate) {
+      current.alternate.child = null;
+      current.alternate["return"] = null;
+    }
+  }
+
+  var emptyPortalContainer = void 0;
+
+  if (!mutation) {
+    var commitContainer = void 0;
+    if (persistence) {
+      var replaceContainerChildren = persistence.replaceContainerChildren,
+        createContainerChildSet = persistence.createContainerChildSet;
+
+      emptyPortalContainer = function(current) {
+        var portal = current.stateNode;
+        var containerInfo = portal.containerInfo;
+
+        var emptyChildSet = createContainerChildSet(containerInfo);
+        replaceContainerChildren(containerInfo, emptyChildSet);
+      };
+      commitContainer = function(finishedWork) {
+        switch (finishedWork.tag) {
+          case ClassComponent: {
+            return;
+          }
+          case HostComponent: {
+            return;
+          }
+          case HostText: {
+            return;
+          }
+          case HostRoot:
+          case HostPortal: {
+            var portalOrRoot = finishedWork.stateNode;
+            var containerInfo = portalOrRoot.containerInfo,
+              _pendingChildren = portalOrRoot.pendingChildren;
+
+            replaceContainerChildren(containerInfo, _pendingChildren);
+            return;
+          }
+          default: {
+            invariant(
+              false,
+              "This unit of work tag should not have side-effects. This error is " +
+                "likely caused by a bug in React. Please file an issue."
+            );
+          }
+        }
+      };
+    } else {
+      commitContainer = function(finishedWork) {
+        // Noop
+      };
+    }
+    if (enablePersistentReconciler || enableNoopReconciler) {
+      return {
+        commitResetTextContent: function(finishedWork) {},
+        commitPlacement: function(finishedWork) {},
+        commitDeletion: function(current) {
+          // Detach refs and call componentWillUnmount() on the whole subtree.
+          commitNestedUnmounts(current);
+          detachFiber(current);
+        },
+        commitWork: function(current, finishedWork) {
+          commitContainer(finishedWork);
+        },
+
+        commitLifeCycles: commitLifeCycles,
+        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+        commitErrorLogging: commitErrorLogging,
+        commitAttachRef: commitAttachRef,
+        commitDetachRef: commitDetachRef
+      };
+    } else if (persistence) {
+      invariant(false, "Persistent reconciler is disabled.");
+    } else {
+      invariant(false, "Noop reconciler is disabled.");
+    }
+  }
+  var commitMount = mutation.commitMount,
+    commitUpdate = mutation.commitUpdate,
+    resetTextContent = mutation.resetTextContent,
+    commitTextUpdate = mutation.commitTextUpdate,
+    appendChild = mutation.appendChild,
+    appendChildToContainer = mutation.appendChildToContainer,
+    insertBefore = mutation.insertBefore,
+    insertInContainerBefore = mutation.insertInContainerBefore,
+    removeChild = mutation.removeChild,
+    removeChildFromContainer = mutation.removeChildFromContainer;
+
+  function getHostParentFiber(fiber) {
+    var parent = fiber["return"];
+    while (parent !== null) {
+      if (isHostParent(parent)) {
+        return parent;
+      }
+      parent = parent["return"];
+    }
+    invariant(
+      false,
+      "Expected to find a host parent. This error is likely caused by a bug " +
+        "in React. Please file an issue."
+    );
+  }
+
+  function isHostParent(fiber) {
+    return (
+      fiber.tag === HostComponent ||
+      fiber.tag === HostRoot ||
+      fiber.tag === HostPortal
+    );
+  }
+
+  function getHostSibling(fiber) {
+    // We're going to search forward into the tree until we find a sibling host
+    // node. Unfortunately, if multiple insertions are done in a row we have to
+    // search past them. This leads to exponential search for the next sibling.
+    var node = fiber;
+    siblings: while (true) {
+      // If we didn't find anything, let's try the next sibling.
+      while (node.sibling === null) {
+        if (node["return"] === null || isHostParent(node["return"])) {
+          // If we pop out of the root or hit the parent the fiber we are the
+          // last sibling.
+          return null;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+      while (node.tag !== HostComponent && node.tag !== HostText) {
+        // If it is not host node and, we might have a host node inside it.
+        // Try to search down until we find one.
+        if (node.effectTag & Placement) {
+          // If we don't have a child, try the siblings instead.
+          continue siblings;
+        }
+        // If we don't have a child, try the siblings instead.
+        // We also skip portals because they are not part of this host tree.
+        if (node.child === null || node.tag === HostPortal) {
+          continue siblings;
+        } else {
+          node.child["return"] = node;
+          node = node.child;
+        }
+      }
+      // Check if this host node is stable or about to be placed.
+      if (!(node.effectTag & Placement)) {
+        // Found it!
+        return node.stateNode;
+      }
+    }
+  }
+
+  function commitPlacement(finishedWork) {
+    // Recursively insert all host nodes into the parent.
+    var parentFiber = getHostParentFiber(finishedWork);
+    var parent = void 0;
+    var isContainer = void 0;
+    switch (parentFiber.tag) {
+      case HostComponent:
+        parent = parentFiber.stateNode;
+        isContainer = false;
+        break;
+      case HostRoot:
+        parent = parentFiber.stateNode.containerInfo;
+        isContainer = true;
+        break;
+      case HostPortal:
+        parent = parentFiber.stateNode.containerInfo;
+        isContainer = true;
+        break;
+      default:
+        invariant(
+          false,
+          "Invalid host parent fiber. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+    }
+    if (parentFiber.effectTag & ContentReset) {
+      // Reset the text content of the parent before doing any insertions
+      resetTextContent(parent);
+      // Clear ContentReset from the effect tag
+      parentFiber.effectTag &= ~ContentReset;
+    }
+
+    var before = getHostSibling(finishedWork);
+    // We only have the top Fiber that was inserted but we need recurse down its
+    // children to find all the terminal nodes.
+    var node = finishedWork;
+    while (true) {
+      if (node.tag === HostComponent || node.tag === HostText) {
+        if (before) {
+          if (isContainer) {
+            insertInContainerBefore(parent, node.stateNode, before);
+          } else {
+            insertBefore(parent, node.stateNode, before);
+          }
+        } else {
+          if (isContainer) {
+            appendChildToContainer(parent, node.stateNode);
+          } else {
+            appendChild(parent, node.stateNode);
+          }
+        }
+      } else if (node.tag === HostPortal) {
+        // If the insertion itself is a portal, then we don't want to traverse
+        // down its children. Instead, we'll get insertions from each child in
+        // the portal directly.
+      } else if (node.child !== null) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      if (node === finishedWork) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === finishedWork) {
+          return;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  function unmountHostComponents(current) {
+    // We only have the top Fiber that was inserted but we need recurse down its
+    var node = current;
+
+    // Each iteration, currentParent is populated with node's host parent if not
+    // currentParentIsValid.
+    var currentParentIsValid = false;
+    var currentParent = void 0;
+    var currentParentIsContainer = void 0;
+
+    while (true) {
+      if (!currentParentIsValid) {
+        var parent = node["return"];
+        findParent: while (true) {
+          invariant(
+            parent !== null,
+            "Expected to find a host parent. This error is likely caused by " +
+              "a bug in React. Please file an issue."
+          );
+          switch (parent.tag) {
+            case HostComponent:
+              currentParent = parent.stateNode;
+              currentParentIsContainer = false;
+              break findParent;
+            case HostRoot:
+              currentParent = parent.stateNode.containerInfo;
+              currentParentIsContainer = true;
+              break findParent;
+            case HostPortal:
+              currentParent = parent.stateNode.containerInfo;
+              currentParentIsContainer = true;
+              break findParent;
+          }
+          parent = parent["return"];
+        }
+        currentParentIsValid = true;
+      }
+
+      if (node.tag === HostComponent || node.tag === HostText) {
+        commitNestedUnmounts(node);
+        // After all the children have unmounted, it is now safe to remove the
+        // node from the tree.
+        if (currentParentIsContainer) {
+          removeChildFromContainer(currentParent, node.stateNode);
+        } else {
+          removeChild(currentParent, node.stateNode);
+        }
+        // Don't visit children because we already visited them.
+      } else if (node.tag === HostPortal) {
+        // When we go into a portal, it becomes the parent to remove from.
+        // We will reassign it back when we pop the portal on the way up.
+        currentParent = node.stateNode.containerInfo;
+        // Visit children because portals might contain host components.
+        if (node.child !== null) {
+          node.child["return"] = node;
+          node = node.child;
+          continue;
+        }
+      } else {
+        commitUnmount(node);
+        // Visit children because we may find more host components below.
+        if (node.child !== null) {
+          node.child["return"] = node;
+          node = node.child;
+          continue;
+        }
+      }
+      if (node === current) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === current) {
+          return;
+        }
+        node = node["return"];
+        if (node.tag === HostPortal) {
+          // When we go out of the portal, we need to restore the parent.
+          // Since we don't keep a stack of them, we will search for it.
+          currentParentIsValid = false;
+        }
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  function commitDeletion(current) {
+    // Recursively delete all host nodes from the parent.
+    // Detach refs and call componentWillUnmount() on the whole subtree.
+    unmountHostComponents(current);
+    detachFiber(current);
+  }
+
+  function commitWork(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        return;
+      }
+      case HostComponent: {
+        var _instance8 = finishedWork.stateNode;
+        if (_instance8 != null) {
+          // Commit the work prepared earlier.
+          var newProps = finishedWork.memoizedProps;
+          // For hydration we reuse the update path but we treat the oldProps
+          // as the newProps. The updatePayload will contain the real change in
+          // this case.
+          var oldProps = current !== null ? current.memoizedProps : newProps;
+          var type = finishedWork.type;
+          // TODO: Type the updateQueue to be specific to host components.
+          var updatePayload = finishedWork.updateQueue;
+          finishedWork.updateQueue = null;
+          if (updatePayload !== null) {
+            commitUpdate(
+              _instance8,
+              updatePayload,
+              type,
+              oldProps,
+              newProps,
+              finishedWork
+            );
+          }
+        }
+        return;
+      }
+      case HostText: {
+        invariant(
+          finishedWork.stateNode !== null,
+          "This should have a text node initialized. This error is likely " +
+            "caused by a bug in React. Please file an issue."
+        );
+        var textInstance = finishedWork.stateNode;
+        var newText = finishedWork.memoizedProps;
+        // For hydration we reuse the update path but we treat the oldProps
+        // as the newProps. The updatePayload will contain the real change in
+        // this case.
+        var oldText = current !== null ? current.memoizedProps : newText;
+        commitTextUpdate(textInstance, oldText, newText);
+        return;
+      }
+      case HostRoot: {
+        return;
+      }
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
+  function commitResetTextContent(current) {
+    resetTextContent(current.stateNode);
+  }
+
+  if (enableMutatingReconciler) {
+    return {
+      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+      commitResetTextContent: commitResetTextContent,
+      commitPlacement: commitPlacement,
+      commitDeletion: commitDeletion,
+      commitWork: commitWork,
+      commitLifeCycles: commitLifeCycles,
+      commitErrorLogging: commitErrorLogging,
+      commitAttachRef: commitAttachRef,
+      commitDetachRef: commitDetachRef
+    };
+  } else {
+    invariant(false, "Mutating reconciler is disabled.");
+  }
+};
+
+var NO_CONTEXT = {};
+
+var ReactFiberHostContext = function(config, stack) {
+  var getChildHostContext = config.getChildHostContext,
+    getRootHostContext = config.getRootHostContext;
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  var contextStackCursor = createCursor(NO_CONTEXT);
+  var contextFiberStackCursor = createCursor(NO_CONTEXT);
+  var rootInstanceStackCursor = createCursor(NO_CONTEXT);
+
+  function requiredContext(c) {
+    invariant(
+      c !== NO_CONTEXT,
+      "Expected host context to exist. This error is likely caused by a bug " +
+        "in React. Please file an issue."
+    );
+    return c;
+  }
+
+  function getRootHostContainer() {
+    var rootInstance = requiredContext(rootInstanceStackCursor.current);
+    return rootInstance;
+  }
+
+  function pushHostContainer(fiber, nextRootInstance) {
+    // Push current root instance onto the stack;
+    // This allows us to reset root when portals are popped.
+    push(rootInstanceStackCursor, nextRootInstance, fiber);
+    // Track the context and the Fiber that provided it.
+    // This enables us to pop only Fibers that provide unique contexts.
+    push(contextFiberStackCursor, fiber, fiber);
+
+    // Finally, we need to push the host context to the stack.
+    // However, we can't just call getRootHostContext() and push it because
+    // we'd have a different number of entries on the stack depending on
+    // whether getRootHostContext() throws somewhere in renderer code or not.
+    // So we push an empty value first. This lets us safely unwind on errors.
+    push(contextStackCursor, NO_CONTEXT, fiber);
+    var nextRootContext = getRootHostContext(nextRootInstance);
+    // Now that we know this function doesn't throw, replace it.
+    pop(contextStackCursor, fiber);
+    push(contextStackCursor, nextRootContext, fiber);
+  }
+
+  function popHostContainer(fiber) {
+    pop(contextStackCursor, fiber);
+    pop(contextFiberStackCursor, fiber);
+    pop(rootInstanceStackCursor, fiber);
+  }
+
+  function getHostContext() {
+    var context = requiredContext(contextStackCursor.current);
+    return context;
+  }
+
+  function pushHostContext(fiber) {
+    var rootInstance = requiredContext(rootInstanceStackCursor.current);
+    var context = requiredContext(contextStackCursor.current);
+    var nextContext = getChildHostContext(context, fiber.type, rootInstance);
+
+    // Don't push this Fiber's context unless it's unique.
+    if (context === nextContext) {
+      return;
+    }
+
+    // Track the context and the Fiber that provided it.
+    // This enables us to pop only Fibers that provide unique contexts.
+    push(contextFiberStackCursor, fiber, fiber);
+    push(contextStackCursor, nextContext, fiber);
+  }
+
+  function popHostContext(fiber) {
+    // Do not pop unless this Fiber provided the current context.
+    // pushHostContext() only pushes Fibers that provide unique contexts.
+    if (contextFiberStackCursor.current !== fiber) {
+      return;
+    }
+
+    pop(contextStackCursor, fiber);
+    pop(contextFiberStackCursor, fiber);
+  }
+
+  return {
+    getHostContext: getHostContext,
+    getRootHostContainer: getRootHostContainer,
+    popHostContainer: popHostContainer,
+    popHostContext: popHostContext,
+    pushHostContainer: pushHostContainer,
+    pushHostContext: pushHostContext
+  };
+};
+
+var ReactFiberHydrationContext = function(config) {
+  var shouldSetTextContent = config.shouldSetTextContent,
+    hydration = config.hydration;
+
+  // If this doesn't have hydration mode.
+
+  if (!hydration) {
+    return {
+      enterHydrationState: function() {
+        return false;
+      },
+      resetHydrationState: function() {},
+      tryToClaimNextHydratableInstance: function() {},
+      prepareToHydrateHostInstance: function() {
+        invariant(
+          false,
+          "Expected prepareToHydrateHostInstance() to never be called. " +
+            "This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      prepareToHydrateHostTextInstance: function() {
+        invariant(
+          false,
+          "Expected prepareToHydrateHostTextInstance() to never be called. " +
+            "This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      popHydrationState: function(fiber) {
+        return false;
+      }
+    };
+  }
+
+  var canHydrateInstance = hydration.canHydrateInstance,
+    canHydrateTextInstance = hydration.canHydrateTextInstance,
+    getNextHydratableSibling = hydration.getNextHydratableSibling,
+    getFirstHydratableChild = hydration.getFirstHydratableChild,
+    hydrateInstance = hydration.hydrateInstance,
+    hydrateTextInstance = hydration.hydrateTextInstance,
+    didNotMatchHydratedContainerTextInstance =
+      hydration.didNotMatchHydratedContainerTextInstance,
+    didNotMatchHydratedTextInstance = hydration.didNotMatchHydratedTextInstance,
+    didNotHydrateContainerInstance = hydration.didNotHydrateContainerInstance,
+    didNotHydrateInstance = hydration.didNotHydrateInstance,
+    didNotFindHydratableContainerInstance =
+      hydration.didNotFindHydratableContainerInstance,
+    didNotFindHydratableContainerTextInstance =
+      hydration.didNotFindHydratableContainerTextInstance,
+    didNotFindHydratableInstance = hydration.didNotFindHydratableInstance,
+    didNotFindHydratableTextInstance =
+      hydration.didNotFindHydratableTextInstance;
+
+  // The deepest Fiber on the stack involved in a hydration context.
+  // This may have been an insertion or a hydration.
+
+  var hydrationParentFiber = null;
+  var nextHydratableInstance = null;
+  var isHydrating = false;
+
+  function enterHydrationState(fiber) {
+    var parentInstance = fiber.stateNode.containerInfo;
+    nextHydratableInstance = getFirstHydratableChild(parentInstance);
+    hydrationParentFiber = fiber;
+    isHydrating = true;
+    return true;
+  }
+
+  function deleteHydratableInstance(returnFiber, instance) {
+    {
+      switch (returnFiber.tag) {
+        case HostRoot:
+          didNotHydrateContainerInstance(
+            returnFiber.stateNode.containerInfo,
+            instance
+          );
+          break;
+        case HostComponent:
+          didNotHydrateInstance(
+            returnFiber.type,
+            returnFiber.memoizedProps,
+            returnFiber.stateNode,
+            instance
+          );
+          break;
+      }
+    }
+
+    var childToDelete = createFiberFromHostInstanceForDeletion();
+    childToDelete.stateNode = instance;
+    childToDelete["return"] = returnFiber;
+    childToDelete.effectTag = Deletion;
+
+    // This might seem like it belongs on progressedFirstDeletion. However,
+    // these children are not part of the reconciliation list of children.
+    // Even if we abort and rereconcile the children, that will try to hydrate
+    // again and the nodes are still in the host tree so these will be
+    // recreated.
+    if (returnFiber.lastEffect !== null) {
+      returnFiber.lastEffect.nextEffect = childToDelete;
+      returnFiber.lastEffect = childToDelete;
+    } else {
+      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+    }
+  }
+
+  function insertNonHydratedInstance(returnFiber, fiber) {
+    fiber.effectTag |= Placement;
+    {
+      switch (returnFiber.tag) {
+        case HostRoot: {
+          var parentContainer = returnFiber.stateNode.containerInfo;
+          switch (fiber.tag) {
+            case HostComponent:
+              var type = fiber.type;
+              var props = fiber.pendingProps;
+              didNotFindHydratableContainerInstance(
+                parentContainer,
+                type,
+                props
+              );
+              break;
+            case HostText:
+              var text = fiber.pendingProps;
+              didNotFindHydratableContainerTextInstance(parentContainer, text);
+              break;
+          }
+          break;
+        }
+        case HostComponent: {
+          var parentType = returnFiber.type;
+          var parentProps = returnFiber.memoizedProps;
+          var parentInstance = returnFiber.stateNode;
+          switch (fiber.tag) {
+            case HostComponent:
+              var _type = fiber.type;
+              var _props = fiber.pendingProps;
+              didNotFindHydratableInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                _type,
+                _props
+              );
+              break;
+            case HostText:
+              var _text = fiber.pendingProps;
+              didNotFindHydratableTextInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                _text
+              );
+              break;
+          }
+          break;
+        }
+        default:
+          return;
+      }
+    }
+  }
+
+  function tryHydrate(fiber, nextInstance) {
+    switch (fiber.tag) {
+      case HostComponent: {
+        var type = fiber.type;
+        var props = fiber.pendingProps;
+        var instance = canHydrateInstance(nextInstance, type, props);
+        if (instance !== null) {
+          fiber.stateNode = instance;
+          return true;
+        }
+        return false;
+      }
+      case HostText: {
+        var text = fiber.pendingProps;
+        var textInstance = canHydrateTextInstance(nextInstance, text);
+        if (textInstance !== null) {
+          fiber.stateNode = textInstance;
+          return true;
+        }
+        return false;
+      }
+      default:
+        return false;
+    }
+  }
+
+  function tryToClaimNextHydratableInstance(fiber) {
+    if (!isHydrating) {
+      return;
+    }
+    var nextInstance = nextHydratableInstance;
+    if (!nextInstance) {
+      // Nothing to hydrate. Make it an insertion.
+      insertNonHydratedInstance(hydrationParentFiber, fiber);
+      isHydrating = false;
+      hydrationParentFiber = fiber;
+      return;
+    }
+    if (!tryHydrate(fiber, nextInstance)) {
+      // If we can't hydrate this instance let's try the next one.
+      // We use this as a heuristic. It's based on intuition and not data so it
+      // might be flawed or unnecessary.
+      nextInstance = getNextHydratableSibling(nextInstance);
+      if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
+        // Nothing to hydrate. Make it an insertion.
+        insertNonHydratedInstance(hydrationParentFiber, fiber);
+        isHydrating = false;
+        hydrationParentFiber = fiber;
+        return;
+      }
+      // We matched the next one, we'll now assume that the first one was
+      // superfluous and we'll delete it. Since we can't eagerly delete it
+      // we'll have to schedule a deletion. To do that, this node needs a dummy
+      // fiber associated with it.
+      deleteHydratableInstance(hydrationParentFiber, nextHydratableInstance);
+    }
+    hydrationParentFiber = fiber;
+    nextHydratableInstance = getFirstHydratableChild(nextInstance);
+  }
+
+  function prepareToHydrateHostInstance(
+    fiber,
+    rootContainerInstance,
+    hostContext
+  ) {
+    var instance = fiber.stateNode;
+    var updatePayload = hydrateInstance(
+      instance,
+      fiber.type,
+      fiber.memoizedProps,
+      rootContainerInstance,
+      hostContext,
+      fiber
+    );
+    // TODO: Type this specific to this type of component.
+    fiber.updateQueue = updatePayload;
+    // If the update payload indicates that there is a change or if there
+    // is a new ref we mark this as an update.
+    if (updatePayload !== null) {
+      return true;
+    }
+    return false;
+  }
+
+  function prepareToHydrateHostTextInstance(fiber) {
+    var textInstance = fiber.stateNode;
+    var textContent = fiber.memoizedProps;
+    var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
+    {
+      if (shouldUpdate) {
+        // We assume that prepareToHydrateHostTextInstance is called in a context where the
+        // hydration parent is the parent host component of this host text.
+        var returnFiber = hydrationParentFiber;
+        if (returnFiber !== null) {
+          switch (returnFiber.tag) {
+            case HostRoot: {
+              var parentContainer = returnFiber.stateNode.containerInfo;
+              didNotMatchHydratedContainerTextInstance(
+                parentContainer,
+                textInstance,
+                textContent
+              );
+              break;
+            }
+            case HostComponent: {
+              var parentType = returnFiber.type;
+              var parentProps = returnFiber.memoizedProps;
+              var parentInstance = returnFiber.stateNode;
+              didNotMatchHydratedTextInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                textInstance,
+                textContent
+              );
+              break;
+            }
+          }
+        }
+      }
+    }
+    return shouldUpdate;
+  }
+
+  function popToNextHostParent(fiber) {
+    var parent = fiber["return"];
+    while (
+      parent !== null &&
+      parent.tag !== HostComponent &&
+      parent.tag !== HostRoot
+    ) {
+      parent = parent["return"];
+    }
+    hydrationParentFiber = parent;
+  }
+
+  function popHydrationState(fiber) {
+    if (fiber !== hydrationParentFiber) {
+      // We're deeper than the current hydration context, inside an inserted
+      // tree.
+      return false;
+    }
+    if (!isHydrating) {
+      // If we're not currently hydrating but we're in a hydration context, then
+      // we were an insertion and now need to pop up reenter hydration of our
+      // siblings.
+      popToNextHostParent(fiber);
+      isHydrating = true;
+      return false;
+    }
+
+    var type = fiber.type;
+
+    // If we have any remaining hydratable nodes, we need to delete them now.
+    // We only do this deeper than head and body since they tend to have random
+    // other nodes in them. We also ignore components with pure text content in
+    // side of them.
+    // TODO: Better heuristic.
+    if (
+      fiber.tag !== HostComponent ||
+      (type !== "head" &&
+        type !== "body" &&
+        !shouldSetTextContent(type, fiber.memoizedProps))
+    ) {
+      var nextInstance = nextHydratableInstance;
+      while (nextInstance) {
+        deleteHydratableInstance(fiber, nextInstance);
+        nextInstance = getNextHydratableSibling(nextInstance);
+      }
+    }
+
+    popToNextHostParent(fiber);
+    nextHydratableInstance = hydrationParentFiber
+      ? getNextHydratableSibling(fiber.stateNode)
+      : null;
+    return true;
+  }
+
+  function resetHydrationState() {
+    hydrationParentFiber = null;
+    nextHydratableInstance = null;
+    isHydrating = false;
+  }
+
+  return {
+    enterHydrationState: enterHydrationState,
+    resetHydrationState: resetHydrationState,
+    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
+    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
+    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
+    popHydrationState: popHydrationState
+  };
+};
+
+// This lets us hook into Fiber to debug what it's doing.
+// See https://github.com/facebook/react/pull/8033.
+// This is not part of the public API, not even for React DevTools.
+// You may only inject a debugTool if you work on React Fiber itself.
+var ReactFiberInstrumentation = {
+  debugTool: null
+};
+
+var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
+
+var warnedAboutMissingGetChildContext = void 0;
+
+{
+  warnedAboutMissingGetChildContext = {};
+}
+
+var ReactFiberLegacyContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  // A cursor to the current merged context object on the stack.
+
+  var contextStackCursor = createCursor(emptyObject);
+  // A cursor to a boolean indicating whether the context has changed.
+  var didPerformWorkStackCursor = createCursor(false);
+  // Keep track of the previous context object that was on the stack.
+  // We use this to get access to the parent context after we have already
+  // pushed the next context provider, and now need to merge their contexts.
+  var previousContext = emptyObject;
+
+  function getUnmaskedContext(workInProgress) {
+    var hasOwnContext = isContextProvider(workInProgress);
+    if (hasOwnContext) {
+      // If the fiber is a context provider itself, when we read its context
+      // we have already pushed its own child context on the stack. A context
+      // provider should not "see" its own child context. Therefore we read the
+      // previous (parent) context instead for a context provider.
+      return previousContext;
+    }
+    return contextStackCursor.current;
+  }
+
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    var instance = workInProgress.stateNode;
+    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
+
+  function getMaskedContext(workInProgress, unmaskedContext) {
+    var type = workInProgress.type;
+    var contextTypes = type.contextTypes;
+    if (!contextTypes) {
+      return emptyObject;
+    }
+
+    // Avoid recreating masked context unless unmasked context has changed.
+    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
+    // This may trigger infinite loops if componentWillReceiveProps calls setState.
+    var instance = workInProgress.stateNode;
+    if (
+      instance &&
+      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+    ) {
+      return instance.__reactInternalMemoizedMaskedChildContext;
+    }
+
+    var context = {};
+    for (var key in contextTypes) {
+      context[key] = unmaskedContext[key];
+    }
+
+    {
+      var name = getComponentName(workInProgress) || "Unknown";
+      checkPropTypes(
+        contextTypes,
+        context,
+        "context",
+        name,
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    // Context is created before the class component is instantiated so check for instance.
+    if (instance) {
+      cacheContext(workInProgress, unmaskedContext, context);
+    }
+
+    return context;
+  }
+
+  function hasContextChanged() {
+    return didPerformWorkStackCursor.current;
+  }
+
+  function isContextConsumer(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+  }
+
+  function isContextProvider(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+  }
+
+  function popContextProvider(fiber) {
+    if (!isContextProvider(fiber)) {
+      return;
+    }
+
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
+
+  function popTopLevelContextObject(fiber) {
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
+
+  function pushTopLevelContextObject(fiber, context, didChange) {
+    invariant(
+      contextStackCursor.cursor == null,
+      "Unexpected context found on stack. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    push(contextStackCursor, context, fiber);
+    push(didPerformWorkStackCursor, didChange, fiber);
+  }
+
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode;
+    var childContextTypes = fiber.type.childContextTypes;
+
+    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
+    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
+    if (typeof instance.getChildContext !== "function") {
+      {
+        var componentName = getComponentName(fiber) || "Unknown";
+
+        if (!warnedAboutMissingGetChildContext[componentName]) {
+          warnedAboutMissingGetChildContext[componentName] = true;
+          warning(
+            false,
+            "%s.childContextTypes is specified but there is no getChildContext() method " +
+              "on the instance. You can either define getChildContext() on %s or remove " +
+              "childContextTypes from it.",
+            componentName,
+            componentName
+          );
+        }
+      }
+      return parentContext;
+    }
+
+    var childContext = void 0;
+    {
+      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
+    }
+    startPhaseTimer(fiber, "getChildContext");
+    childContext = instance.getChildContext();
+    stopPhaseTimer();
+    {
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+    for (var contextKey in childContext) {
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    }
+    {
+      var name = getComponentName(fiber) || "Unknown";
+      checkPropTypes(
+        childContextTypes,
+        childContext,
+        "child context",
+        name,
+        // In practice, there is one case in which we won't get a stack. It's when
+        // somebody calls unstable_renderSubtreeIntoContainer() and we process
+        // context from the parent component instance. The stack will be missing
+        // because it's outside of the reconciliation, and so the pointer has not
+        // been set. This is rare and doesn't matter. We'll also remove that API.
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    return Object.assign({}, parentContext, childContext);
+  }
+
+  function pushContextProvider(workInProgress) {
+    if (!isContextProvider(workInProgress)) {
+      return false;
+    }
+
+    var instance = workInProgress.stateNode;
+    // We push the context as early as possible to ensure stack integrity.
+    // If the instance does not exist yet, we will push null at first,
+    // and replace it on the stack later when invalidating the context.
+    var memoizedMergedChildContext =
+      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+      emptyObject;
+
+    // Remember the parent context so we can merge with it later.
+    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
+    previousContext = contextStackCursor.current;
+    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
+    push(
+      didPerformWorkStackCursor,
+      didPerformWorkStackCursor.current,
+      workInProgress
+    );
+
+    return true;
+  }
+
+  function invalidateContextProvider(workInProgress, didChange) {
+    var instance = workInProgress.stateNode;
+    invariant(
+      instance,
+      "Expected to have an instance by this point. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    if (didChange) {
+      // Merge parent and own context.
+      // Skip this if we're not updating due to sCU.
+      // This avoids unnecessarily recomputing memoized values.
+      var mergedContext = processChildContext(workInProgress, previousContext);
+      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+
+      // Replace the old (or empty) context with the new one.
+      // It is important to unwind the context in the reverse order.
+      pop(didPerformWorkStackCursor, workInProgress);
+      pop(contextStackCursor, workInProgress);
+      // Now push the new context and mark that it has changed.
+      push(contextStackCursor, mergedContext, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    } else {
+      pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    }
+  }
+
+  function findCurrentUnmaskedContext(fiber) {
+    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
+    // makes sense elsewhere
+    invariant(
+      isFiberMounted(fiber) && fiber.tag === ClassComponent,
+      "Expected subtree parent to be a mounted class component. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    var node = fiber;
+    while (node.tag !== HostRoot) {
+      if (isContextProvider(node)) {
+        return node.stateNode.__reactInternalMemoizedMergedChildContext;
+      }
+      var parent = node["return"];
+      invariant(
+        parent,
+        "Found unexpected detached subtree parent. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
+      node = parent;
+    }
+    return node.stateNode.context;
+  }
+
+  return {
+    getUnmaskedContext: getUnmaskedContext,
+    cacheContext: cacheContext,
+    getMaskedContext: getMaskedContext,
+    hasContextChanged: hasContextChanged,
+    isContextConsumer: isContextConsumer,
+    isContextProvider: isContextProvider,
+    popContextProvider: popContextProvider,
+    popTopLevelContextObject: popTopLevelContextObject,
+    pushTopLevelContextObject: pushTopLevelContextObject,
+    processChildContext: processChildContext,
+    pushContextProvider: pushContextProvider,
+    invalidateContextProvider: invalidateContextProvider,
+    findCurrentUnmaskedContext: findCurrentUnmaskedContext
+  };
+};
+
+var ReactFiberNewContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  var providerCursor = createCursor(null);
+  var valueCursor = createCursor(null);
+  var changedBitsCursor = createCursor(0);
+
+  var rendererSigil = void 0;
+  {
+    // Use this to detect multiple renderers using the same context
+    rendererSigil = {};
+  }
+
+  function pushProvider(providerFiber) {
+    var context = providerFiber.type._context;
+
+    push(changedBitsCursor, context._changedBits, providerFiber);
+    push(valueCursor, context._currentValue, providerFiber);
+    push(providerCursor, providerFiber, providerFiber);
+
+    context._currentValue = providerFiber.pendingProps.value;
+    context._changedBits = providerFiber.stateNode;
+
+    {
+      !(
+        context._currentRenderer === null ||
+        context._currentRenderer === rendererSigil
+      )
+        ? warning(
+            false,
+            "Detected multiple renderers concurrently rendering the " +
+              "same context provider. This is currently unsupported."
+          )
+        : void 0;
+      context._currentRenderer = rendererSigil;
+    }
+  }
+
+  function popProvider(providerFiber) {
+    var changedBits = changedBitsCursor.current;
+    var currentValue = valueCursor.current;
+
+    pop(providerCursor, providerFiber);
+    pop(valueCursor, providerFiber);
+    pop(changedBitsCursor, providerFiber);
+
+    var context = providerFiber.type._context;
+    context._currentValue = currentValue;
+    context._changedBits = changedBits;
+  }
+
+  return {
+    pushProvider: pushProvider,
+    popProvider: popProvider
+  };
+};
+
+var ReactFiberStack = function() {
+  var valueStack = [];
+
+  var fiberStack = void 0;
+
+  {
+    fiberStack = [];
+  }
+
+  var index = -1;
+
+  function createCursor(defaultValue) {
+    return {
+      current: defaultValue
+    };
+  }
+
+  function isEmpty() {
+    return index === -1;
+  }
+
+  function pop(cursor, fiber) {
+    if (index < 0) {
+      {
+        warning(false, "Unexpected pop.");
+      }
+      return;
+    }
+
+    {
+      if (fiber !== fiberStack[index]) {
+        warning(false, "Unexpected Fiber popped.");
+      }
+    }
+
+    cursor.current = valueStack[index];
+
+    valueStack[index] = null;
+
+    {
+      fiberStack[index] = null;
+    }
+
+    index--;
+  }
+
+  function push(cursor, value, fiber) {
+    index++;
+
+    valueStack[index] = cursor.current;
+
+    {
+      fiberStack[index] = fiber;
+    }
+
+    cursor.current = value;
+  }
+
+  function checkThatStackIsEmpty() {
+    {
+      if (index !== -1) {
+        warning(
+          false,
+          "Expected an empty stack. Something was not reset properly."
+        );
+      }
+    }
+  }
+
+  function resetStackAfterFatalErrorInDev() {
+    {
+      index = -1;
+      valueStack.length = 0;
+      fiberStack.length = 0;
+    }
+  }
+
+  return {
+    createCursor: createCursor,
+    isEmpty: isEmpty,
+    pop: pop,
+    push: push,
+    checkThatStackIsEmpty: checkThatStackIsEmpty,
+    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
+  };
+};
+
+var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError = ReactErrorUtils.hasCaughtError;
+var clearCaughtError = ReactErrorUtils.clearCaughtError;
+
+var didWarnAboutStateTransition = void 0;
+var didWarnSetStateChildContext = void 0;
+var warnAboutUpdateOnUnmounted = void 0;
+var warnAboutInvalidUpdates = void 0;
+
+{
+  didWarnAboutStateTransition = false;
+  didWarnSetStateChildContext = false;
+  var didWarnStateUpdateForUnmountedComponent = {};
+
+  warnAboutUpdateOnUnmounted = function(fiber) {
+    // We show the whole stack but dedupe on the top component's name because
+    // the problematic code almost always lies inside that component.
+    var componentName = getComponentName(fiber) || "ReactClass";
+    if (didWarnStateUpdateForUnmountedComponent[componentName]) {
+      return;
+    }
+    warning(
+      false,
+      "Can't call setState (or forceUpdate) on an unmounted component. This " +
+        "is a no-op, but it indicates a memory leak in your application. To " +
+        "fix, cancel all subscriptions and asynchronous tasks in the " +
+        "componentWillUnmount method.%s",
+      getStackAddendumByWorkInProgressFiber(fiber)
+    );
+    didWarnStateUpdateForUnmountedComponent[componentName] = true;
+  };
+
+  warnAboutInvalidUpdates = function(instance) {
+    switch (ReactDebugCurrentFiber.phase) {
+      case "getChildContext":
+        if (didWarnSetStateChildContext) {
+          return;
+        }
+        warning(
+          false,
+          "setState(...): Cannot call setState() inside getChildContext()"
+        );
+        didWarnSetStateChildContext = true;
+        break;
+      case "render":
+        if (didWarnAboutStateTransition) {
+          return;
+        }
+        warning(
+          false,
+          "Cannot update during an existing state transition (such as within " +
+            "`render` or another component's constructor). Render methods should " +
+            "be a pure function of props and state; constructor side-effects are " +
+            "an anti-pattern, but can be moved to `componentWillMount`."
+        );
+        didWarnAboutStateTransition = true;
+        break;
+    }
+  };
+}
+
+var ReactFiberScheduler = function(config) {
+  var stack = ReactFiberStack();
+  var hostContext = ReactFiberHostContext(config, stack);
+  var legacyContext = ReactFiberLegacyContext(stack);
+  var newContext = ReactFiberNewContext(stack);
+  var popHostContext = hostContext.popHostContext,
+    popHostContainer = hostContext.popHostContainer;
+  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popLegacyContextProvider = legacyContext.popContextProvider;
+  var popProvider = newContext.popProvider;
+
+  var hydrationContext = ReactFiberHydrationContext(config);
+
+  var _ReactFiberBeginWork = ReactFiberBeginWork(
+      config,
+      hostContext,
+      legacyContext,
+      newContext,
+      hydrationContext,
+      scheduleWork,
+      computeExpirationForFiber
+    ),
+    beginWork = _ReactFiberBeginWork.beginWork;
+
+  var _ReactFiberCompleteWo = ReactFiberCompleteWork(
+      config,
+      hostContext,
+      legacyContext,
+      newContext,
+      hydrationContext
+    ),
+    completeWork = _ReactFiberCompleteWo.completeWork;
+
+  var _ReactFiberUnwindWork = ReactFiberUnwindWork(
+      hostContext,
+      legacyContext,
+      newContext,
+      scheduleWork,
+      isAlreadyFailedLegacyErrorBoundary
+    ),
+    throwException = _ReactFiberUnwindWork.throwException,
+    unwindWork = _ReactFiberUnwindWork.unwindWork,
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
+
+  var _ReactFiberCommitWork = ReactFiberCommitWork(
+      config,
+      onCommitPhaseError,
+      scheduleWork,
+      computeExpirationForFiber,
+      markLegacyErrorBoundaryAsFailed,
+      recalculateCurrentTime
+    ),
+    commitBeforeMutationLifeCycles =
+      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
+    commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
+    commitPlacement = _ReactFiberCommitWork.commitPlacement,
+    commitDeletion = _ReactFiberCommitWork.commitDeletion,
+    commitWork = _ReactFiberCommitWork.commitWork,
+    commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
+    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
+    commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
+    commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
+
+  var now = config.now,
+    scheduleDeferredCallback = config.scheduleDeferredCallback,
+    cancelDeferredCallback = config.cancelDeferredCallback,
+    prepareForCommit = config.prepareForCommit,
+    resetAfterCommit = config.resetAfterCommit;
+
+  // Represents the current time in ms.
+
+  var originalStartTimeMs = now();
+  var mostRecentCurrentTime = msToExpirationTime(0);
+  var mostRecentCurrentTimeMs = originalStartTimeMs;
+
+  // Used to ensure computeUniqueAsyncExpiration is monotonically increases.
+  var lastUniqueAsyncExpiration = 0;
+
+  // Represents the expiration time that incoming updates should use. (If this
+  // is NoWork, use the default strategy: async updates in async mode, sync
+  // updates in sync mode.)
+  var expirationContext = NoWork;
+
+  var isWorking = false;
+
+  // The next work in progress fiber that we're currently working on.
+  var nextUnitOfWork = null;
+  var nextRoot = null;
+  // The time at which we're currently rendering work.
+  var nextRenderExpirationTime = NoWork;
+
+  // The next fiber with an effect that we're currently committing.
+  var nextEffect = null;
+
+  var isCommitting = false;
+
+  var isRootReadyForCommit = false;
+
+  var legacyErrorBoundariesThatAlreadyFailed = null;
+
+  // Used for performance tracking.
+  var interruptedBy = null;
+
+  var stashedWorkInProgressProperties = void 0;
+  var replayUnitOfWork = void 0;
+  var isReplayingFailedUnitOfWork = void 0;
+  var originalReplayError = void 0;
+  var rethrowOriginalError = void 0;
+  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+    stashedWorkInProgressProperties = null;
+    isReplayingFailedUnitOfWork = false;
+    originalReplayError = null;
+    replayUnitOfWork = function(failedUnitOfWork, error, isAsync) {
+      // Restore the original state of the work-in-progress
+      assignFiberPropertiesInDEV(
+        failedUnitOfWork,
+        stashedWorkInProgressProperties
+      );
+      switch (failedUnitOfWork.tag) {
+        case HostRoot:
+          popHostContainer(failedUnitOfWork);
+          popTopLevelLegacyContextObject(failedUnitOfWork);
+          break;
+        case HostComponent:
+          popHostContext(failedUnitOfWork);
+          break;
+        case ClassComponent:
+          popLegacyContextProvider(failedUnitOfWork);
+          break;
+        case HostPortal:
+          popHostContainer(failedUnitOfWork);
+          break;
+        case ContextProvider:
+          popProvider(failedUnitOfWork);
+          break;
+      }
+      // Replay the begin phase.
+      isReplayingFailedUnitOfWork = true;
+      originalReplayError = error;
+      invokeGuardedCallback$2(null, workLoop, null, isAsync);
+      isReplayingFailedUnitOfWork = false;
+      originalReplayError = null;
+      if (hasCaughtError()) {
+        clearCaughtError();
+      } else {
+        // If the begin phase did not fail the second time, set this pointer
+        // back to the original value.
+        nextUnitOfWork = failedUnitOfWork;
+      }
+    };
+    rethrowOriginalError = function() {
+      throw originalReplayError;
+    };
+  }
+
+  function resetStack() {
+    if (nextUnitOfWork !== null) {
+      var interruptedWork = nextUnitOfWork["return"];
+      while (interruptedWork !== null) {
+        unwindInterruptedWork(interruptedWork);
+        interruptedWork = interruptedWork["return"];
+      }
+    }
+
+    {
+      ReactStrictModeWarnings.discardPendingWarnings();
+      stack.checkThatStackIsEmpty();
+    }
+
+    nextRoot = null;
+    nextRenderExpirationTime = NoWork;
+    nextUnitOfWork = null;
+
+    isRootReadyForCommit = false;
+  }
+
+  function commitAllHostEffects() {
+    while (nextEffect !== null) {
+      {
+        ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
+      }
+      recordEffect();
+
+      var effectTag = nextEffect.effectTag;
+
+      if (effectTag & ContentReset) {
+        commitResetTextContent(nextEffect);
+      }
+
+      if (effectTag & Ref) {
+        var current = nextEffect.alternate;
+        if (current !== null) {
+          commitDetachRef(current);
+        }
+      }
+
+      // The following switch statement is only concerned about placement,
+      // updates, and deletions. To avoid needing to add a case for every
+      // possible bitmap value, we remove the secondary effects from the
+      // effect tag and switch on that value.
+      var primaryEffectTag = effectTag & (Placement | Update | Deletion);
+      switch (primaryEffectTag) {
+        case Placement: {
+          commitPlacement(nextEffect);
+          // Clear the "placement" from effect tag so that we know that this is inserted, before
+          // any life-cycles like componentDidMount gets called.
+          // TODO: findDOMNode doesn't rely on this any more but isMounted
+          // does and isMounted is deprecated anyway so we should be able
+          // to kill this.
+          nextEffect.effectTag &= ~Placement;
+          break;
+        }
+        case PlacementAndUpdate: {
+          // Placement
+          commitPlacement(nextEffect);
+          // Clear the "placement" from effect tag so that we know that this is inserted, before
+          // any life-cycles like componentDidMount gets called.
+          nextEffect.effectTag &= ~Placement;
+
+          // Update
+          var _current = nextEffect.alternate;
+          commitWork(_current, nextEffect);
+          break;
+        }
+        case Update: {
+          var _current2 = nextEffect.alternate;
+          commitWork(_current2, nextEffect);
+          break;
+        }
+        case Deletion: {
+          commitDeletion(nextEffect);
+          break;
+        }
+      }
+      nextEffect = nextEffect.nextEffect;
+    }
+
+    {
+      ReactDebugCurrentFiber.resetCurrentFiber();
+    }
+  }
+
+  function commitBeforeMutationLifecycles() {
+    while (nextEffect !== null) {
+      var effectTag = nextEffect.effectTag;
+
+      if (effectTag & Snapshot) {
+        recordEffect();
+        var current = nextEffect.alternate;
+        commitBeforeMutationLifeCycles(current, nextEffect);
+      }
+
+      // Don't cleanup effects yet;
+      // This will be done by commitAllLifeCycles()
+      nextEffect = nextEffect.nextEffect;
+    }
+  }
+
+  function commitAllLifeCycles(
+    finishedRoot,
+    currentTime,
+    committedExpirationTime
+  ) {
+    {
+      ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
+
+      if (warnAboutDeprecatedLifecycles) {
+        ReactStrictModeWarnings.flushPendingDeprecationWarnings();
+      }
+    }
+    while (nextEffect !== null) {
+      var effectTag = nextEffect.effectTag;
+
+      if (effectTag & (Update | Callback)) {
+        recordEffect();
+        var current = nextEffect.alternate;
+        commitLifeCycles(
+          finishedRoot,
+          current,
+          nextEffect,
+          currentTime,
+          committedExpirationTime
+        );
+      }
+
+      if (effectTag & ErrLog) {
+        commitErrorLogging(nextEffect, onUncaughtError);
+      }
+
+      if (effectTag & Ref) {
+        recordEffect();
+        commitAttachRef(nextEffect);
+      }
+
+      var next = nextEffect.nextEffect;
+      // Ensure that we clean these up so that we don't accidentally keep them.
+      // I'm not actually sure this matters because we can't reset firstEffect
+      // and lastEffect since they're on every node, not just the effectful
+      // ones. So we have to clean everything as we reuse nodes anyway.
+      nextEffect.nextEffect = null;
+      // Ensure that we reset the effectTag here so that we can rely on effect
+      // tags to reason about the current life-cycle.
+      nextEffect = next;
+    }
+  }
+
+  function isAlreadyFailedLegacyErrorBoundary(instance) {
+    return (
+      legacyErrorBoundariesThatAlreadyFailed !== null &&
+      legacyErrorBoundariesThatAlreadyFailed.has(instance)
+    );
+  }
+
+  function markLegacyErrorBoundaryAsFailed(instance) {
+    if (legacyErrorBoundariesThatAlreadyFailed === null) {
+      legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
+    } else {
+      legacyErrorBoundariesThatAlreadyFailed.add(instance);
+    }
+  }
+
+  function commitRoot(finishedWork) {
+    isWorking = true;
+    isCommitting = true;
+    startCommitTimer();
+
+    var root = finishedWork.stateNode;
+    invariant(
+      root.current !== finishedWork,
+      "Cannot commit the same tree as before. This is probably a bug " +
+        "related to the return field. This error is likely caused by a bug " +
+        "in React. Please file an issue."
+    );
+    var committedExpirationTime = root.pendingCommitExpirationTime;
+    invariant(
+      committedExpirationTime !== NoWork,
+      "Cannot commit an incomplete root. This error is likely caused by a " +
+        "bug in React. Please file an issue."
+    );
+    root.pendingCommitExpirationTime = NoWork;
+
+    var currentTime = recalculateCurrentTime();
+
+    // Reset this to null before calling lifecycles
+    ReactCurrentOwner.current = null;
+
+    var firstEffect = void 0;
+    if (finishedWork.effectTag > PerformedWork) {
+      // A fiber's effect list consists only of its children, not itself. So if
+      // the root has an effect, we need to add it to the end of the list. The
+      // resulting list is the set that would belong to the root's parent, if
+      // it had one; that is, all the effects in the tree including the root.
+      if (finishedWork.lastEffect !== null) {
+        finishedWork.lastEffect.nextEffect = finishedWork;
+        firstEffect = finishedWork.firstEffect;
+      } else {
+        firstEffect = finishedWork;
+      }
+    } else {
+      // There is no effect on the root.
+      firstEffect = finishedWork.firstEffect;
+    }
+
+    prepareForCommit(root.containerInfo);
+
+    // Invoke instances of getSnapshotBeforeUpdate before mutation.
+    nextEffect = firstEffect;
+    startCommitSnapshotEffectsTimer();
+    while (nextEffect !== null) {
+      var didError = false;
+      var error = void 0;
+      {
+        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
+        if (hasCaughtError()) {
+          didError = true;
+          error = clearCaughtError();
+        }
+      }
+      if (didError) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, error);
+        // Clean-up
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
+    stopCommitSnapshotEffectsTimer();
+
+    // Commit all the side-effects within a tree. We'll do this in two passes.
+    // The first pass performs all the host insertions, updates, deletions and
+    // ref unmounts.
+    nextEffect = firstEffect;
+    startCommitHostEffectsTimer();
+    while (nextEffect !== null) {
+      var _didError = false;
+      var _error = void 0;
+      {
+        invokeGuardedCallback$2(null, commitAllHostEffects, null);
+        if (hasCaughtError()) {
+          _didError = true;
+          _error = clearCaughtError();
+        }
+      }
+      if (_didError) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, _error);
+        // Clean-up
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
+    stopCommitHostEffectsTimer();
+
+    resetAfterCommit(root.containerInfo);
+
+    // The work-in-progress tree is now the current tree. This must come after
+    // the first pass of the commit phase, so that the previous tree is still
+    // current during componentWillUnmount, but before the second pass, so that
+    // the finished work is current during componentDidMount/Update.
+    root.current = finishedWork;
+
+    // In the second pass we'll perform all life-cycles and ref callbacks.
+    // Life-cycles happen as a separate pass so that all placements, updates,
+    // and deletions in the entire tree have already been invoked.
+    // This pass also triggers any renderer-specific initial effects.
+    nextEffect = firstEffect;
+    startCommitLifeCyclesTimer();
+    while (nextEffect !== null) {
+      var _didError2 = false;
+      var _error2 = void 0;
+      {
+        invokeGuardedCallback$2(
+          null,
+          commitAllLifeCycles,
+          null,
+          root,
+          currentTime,
+          committedExpirationTime
+        );
+        if (hasCaughtError()) {
+          _didError2 = true;
+          _error2 = clearCaughtError();
+        }
+      }
+      if (_didError2) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, _error2);
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
+
+    isCommitting = false;
+    isWorking = false;
+    stopCommitLifeCyclesTimer();
+    stopCommitTimer();
+    if (typeof onCommitRoot === "function") {
+      onCommitRoot(finishedWork.stateNode);
+    }
+    if (true && ReactFiberInstrumentation_1.debugTool) {
+      ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
+    }
+
+    var remainingTime = root.current.expirationTime;
+    if (remainingTime === NoWork) {
+      // If there's no remaining work, we can clear the set of already failed
+      // error boundaries.
+      legacyErrorBoundariesThatAlreadyFailed = null;
+    }
+    return remainingTime;
+  }
+
+  function resetExpirationTime(workInProgress, renderTime) {
+    if (renderTime !== Never && workInProgress.expirationTime === Never) {
+      // The children of this component are hidden. Don't bubble their
+      // expiration times.
+      return;
+    }
+
+    // Check for pending updates.
+    var newExpirationTime = getUpdateExpirationTime(workInProgress);
+
+    // TODO: Calls need to visit stateNode
+
+    // Bubble up the earliest expiration time.
+    var child = workInProgress.child;
+    while (child !== null) {
+      if (
+        child.expirationTime !== NoWork &&
+        (newExpirationTime === NoWork ||
+          newExpirationTime > child.expirationTime)
+      ) {
+        newExpirationTime = child.expirationTime;
+      }
+      child = child.sibling;
+    }
+    workInProgress.expirationTime = newExpirationTime;
+  }
+
+  function completeUnitOfWork(workInProgress) {
+    // Attempt to complete the current unit of work, then move to the
+    // next sibling. If there are no more siblings, return to the
+    // parent fiber.
+    while (true) {
+      // The current, flushed, state of this fiber is the alternate.
+      // Ideally nothing should rely on this, but relying on it here
+      // means that we don't need an additional field on the work in
+      // progress.
+      var current = workInProgress.alternate;
+      {
+        ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+      }
+
+      var returnFiber = workInProgress["return"];
+      var siblingFiber = workInProgress.sibling;
+
+      if ((workInProgress.effectTag & Incomplete) === NoEffect) {
+        // This fiber completed.
+        var next = completeWork(
+          current,
+          workInProgress,
+          nextRenderExpirationTime
+        );
+        stopWorkTimer(workInProgress);
+        resetExpirationTime(workInProgress, nextRenderExpirationTime);
+        {
+          ReactDebugCurrentFiber.resetCurrentFiber();
+        }
+
+        if (next !== null) {
+          stopWorkTimer(workInProgress);
+          if (true && ReactFiberInstrumentation_1.debugTool) {
+            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
+              workInProgress
+            );
+          }
+          // If completing this work spawned new work, do that next. We'll come
+          // back here again.
+          return next;
+        }
+
+        if (
+          returnFiber !== null &&
+          // Do not append effects to parents if a sibling failed to complete
+          (returnFiber.effectTag & Incomplete) === NoEffect
+        ) {
+          // Append all the effects of the subtree and this fiber onto the effect
+          // list of the parent. The completion order of the children affects the
+          // side-effect order.
+          if (returnFiber.firstEffect === null) {
+            returnFiber.firstEffect = workInProgress.firstEffect;
+          }
+          if (workInProgress.lastEffect !== null) {
+            if (returnFiber.lastEffect !== null) {
+              returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
+            }
+            returnFiber.lastEffect = workInProgress.lastEffect;
+          }
+
+          // If this fiber had side-effects, we append it AFTER the children's
+          // side-effects. We can perform certain side-effects earlier if
+          // needed, by doing multiple passes over the effect list. We don't want
+          // to schedule our own side-effect on our own list because if end up
+          // reusing children we'll schedule this effect onto itself since we're
+          // at the end.
+          var effectTag = workInProgress.effectTag;
+          // Skip both NoWork and PerformedWork tags when creating the effect list.
+          // PerformedWork effect is read by React DevTools but shouldn't be committed.
+          if (effectTag > PerformedWork) {
+            if (returnFiber.lastEffect !== null) {
+              returnFiber.lastEffect.nextEffect = workInProgress;
+            } else {
+              returnFiber.firstEffect = workInProgress;
+            }
+            returnFiber.lastEffect = workInProgress;
+          }
+        }
+
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+        }
+
+        if (siblingFiber !== null) {
+          // If there is more work to do in this returnFiber, do that next.
+          return siblingFiber;
+        } else if (returnFiber !== null) {
+          // If there's no more work in this returnFiber. Complete the returnFiber.
+          workInProgress = returnFiber;
+          continue;
+        } else {
+          // We've reached the root.
+          isRootReadyForCommit = true;
+          return null;
+        }
+      } else {
+        // This fiber did not complete because something threw. Pop values off
+        // the stack without entering the complete phase. If this is a boundary,
+        // capture values if possible.
+        var _next = unwindWork(workInProgress);
+        // Because this fiber did not complete, don't reset its expiration time.
+        if (workInProgress.effectTag & DidCapture) {
+          // Restarting an error boundary
+          stopFailedWorkTimer(workInProgress);
+        } else {
+          stopWorkTimer(workInProgress);
+        }
+
+        {
+          ReactDebugCurrentFiber.resetCurrentFiber();
+        }
+
+        if (_next !== null) {
+          stopWorkTimer(workInProgress);
+          if (true && ReactFiberInstrumentation_1.debugTool) {
+            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
+              workInProgress
+            );
+          }
+          // If completing this work spawned new work, do that next. We'll come
+          // back here again.
+          // Since we're restarting, remove anything that is not a host effect
+          // from the effect tag.
+          _next.effectTag &= HostEffectMask;
+          return _next;
+        }
+
+        if (returnFiber !== null) {
+          // Mark the parent fiber as incomplete and clear its effect list.
+          returnFiber.firstEffect = returnFiber.lastEffect = null;
+          returnFiber.effectTag |= Incomplete;
+        }
+
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+        }
+
+        if (siblingFiber !== null) {
+          // If there is more work to do in this returnFiber, do that next.
+          return siblingFiber;
+        } else if (returnFiber !== null) {
+          // If there's no more work in this returnFiber. Complete the returnFiber.
+          workInProgress = returnFiber;
+          continue;
+        } else {
+          return null;
+        }
+      }
+    }
+
+    // Without this explicit null return Flow complains of invalid return type
+    // TODO Remove the above while(true) loop
+    // eslint-disable-next-line no-unreachable
+    return null;
+  }
+
+  function performUnitOfWork(workInProgress) {
+    // The current, flushed, state of this fiber is the alternate.
+    // Ideally nothing should rely on this, but relying on it here
+    // means that we don't need an additional field on the work in
+    // progress.
+    var current = workInProgress.alternate;
+
+    // See if beginning this work spawns more work.
+    startWorkTimer(workInProgress);
+    {
+      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+    }
+
+    if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
+        stashedWorkInProgressProperties,
+        workInProgress
+      );
+    }
+    var next = beginWork(current, workInProgress, nextRenderExpirationTime);
+    {
+      ReactDebugCurrentFiber.resetCurrentFiber();
+      if (isReplayingFailedUnitOfWork) {
+        // Currently replaying a failed unit of work. This should be unreachable,
+        // because the render phase is meant to be idempotent, and it should
+        // have thrown again. Since it didn't, rethrow the original error, so
+        // React's internal stack is not misaligned.
+        rethrowOriginalError();
+      }
+    }
+    if (true && ReactFiberInstrumentation_1.debugTool) {
+      ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
+    }
+
+    if (next === null) {
+      // If this doesn't spawn new work, complete the current work.
+      next = completeUnitOfWork(workInProgress);
+    }
+
+    ReactCurrentOwner.current = null;
+
+    return next;
+  }
+
+  function workLoop(isAsync) {
+    if (!isAsync) {
+      // Flush all expired work.
+      while (nextUnitOfWork !== null) {
+        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      }
+    } else {
+      // Flush asynchronous work until the deadline runs out of time.
+      while (nextUnitOfWork !== null && !shouldYield()) {
+        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      }
+    }
+  }
+
+  function renderRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isWorking,
+      "renderRoot was called recursively. This error is likely caused " +
+        "by a bug in React. Please file an issue."
+    );
+    isWorking = true;
+
+    // Check if we're starting from a fresh stack, or if we're resuming from
+    // previously yielded work.
+    if (
+      expirationTime !== nextRenderExpirationTime ||
+      root !== nextRoot ||
+      nextUnitOfWork === null
+    ) {
+      // Reset the stack and start working from the root.
+      resetStack();
+      nextRoot = root;
+      nextRenderExpirationTime = expirationTime;
+      nextUnitOfWork = createWorkInProgress(
+        nextRoot.current,
+        null,
+        nextRenderExpirationTime
+      );
+      root.pendingCommitExpirationTime = NoWork;
+    }
+
+    var didFatal = false;
+
+    startWorkLoopTimer(nextUnitOfWork);
+
+    do {
+      try {
+        workLoop(isAsync);
+      } catch (thrownValue) {
+        if (nextUnitOfWork === null) {
+          // This is a fatal error.
+          didFatal = true;
+          onUncaughtError(thrownValue);
+          break;
+        }
+
+        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+          var failedUnitOfWork = nextUnitOfWork;
+          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
+        }
+
+        var sourceFiber = nextUnitOfWork;
+        var returnFiber = sourceFiber["return"];
+        if (returnFiber === null) {
+          // This is the root. The root could capture its own errors. However,
+          // we don't know if it errors before or after we pushed the host
+          // context. This information is needed to avoid a stack mismatch.
+          // Because we're not sure, treat this as a fatal error. We could track
+          // which phase it fails in, but doesn't seem worth it. At least
+          // for now.
+          didFatal = true;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        throwException(returnFiber, sourceFiber, thrownValue);
+        nextUnitOfWork = completeUnitOfWork(sourceFiber);
+      }
+      break;
+    } while (true);
+
+    // We're done performing work. Time to clean up.
+    var didCompleteRoot = false;
+    isWorking = false;
+
+    // Yield back to main thread.
+    if (didFatal) {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
+      // There was a fatal error.
+      {
+        stack.resetStackAfterFatalErrorInDev();
+      }
+      return null;
+    } else if (nextUnitOfWork === null) {
+      // We reached the root.
+      if (isRootReadyForCommit) {
+        didCompleteRoot = true;
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
+        // The root successfully completed. It's ready for commit.
+        root.pendingCommitExpirationTime = expirationTime;
+        var finishedWork = root.current.alternate;
+        return finishedWork;
+      } else {
+        // The root did not complete.
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
+        invariant(
+          false,
+          "Expired work should have completed. This error is likely caused " +
+            "by a bug in React. Please file an issue."
+        );
+      }
+    } else {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
+      // There's more work to do, but we ran out of time. Yield back to
+      // the renderer.
+      return null;
+    }
+  }
+
+  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
+    // TODO: We only support dispatching errors.
+    var capturedValue = createCapturedValue(value, sourceFiber);
+    var update = {
+      expirationTime: expirationTime,
+      partialState: null,
+      callback: null,
+      isReplace: false,
+      isForced: false,
+      capturedValue: capturedValue,
+      next: null
+    };
+    insertUpdateIntoFiber(boundaryFiber, update);
+    scheduleWork(boundaryFiber, expirationTime);
+  }
+
+  function dispatch(sourceFiber, value, expirationTime) {
+    invariant(
+      !isWorking || isCommitting,
+      "dispatch: Cannot dispatch during the render phase."
+    );
+
+    // TODO: Handle arrays
+
+    var fiber = sourceFiber["return"];
+    while (fiber !== null) {
+      switch (fiber.tag) {
+        case ClassComponent:
+          var ctor = fiber.type;
+          var instance = fiber.stateNode;
+          if (
+            typeof ctor.getDerivedStateFromCatch === "function" ||
+            (typeof instance.componentDidCatch === "function" &&
+              !isAlreadyFailedLegacyErrorBoundary(instance))
+          ) {
+            scheduleCapture(sourceFiber, fiber, value, expirationTime);
+            return;
+          }
+          break;
+        // TODO: Handle async boundaries
+        case HostRoot:
+          scheduleCapture(sourceFiber, fiber, value, expirationTime);
+          return;
+      }
+      fiber = fiber["return"];
+    }
+
+    if (sourceFiber.tag === HostRoot) {
+      // Error was thrown at the root. There is no parent, so the root
+      // itself should capture it.
+      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
+    }
+  }
+
+  function onCommitPhaseError(fiber, error) {
+    return dispatch(fiber, error, Sync);
+  }
+
+  function computeAsyncExpiration(currentTime) {
+    // Given the current clock time, returns an expiration time. We use rounding
+    // to batch like updates together.
+    // Should complete within ~1000ms. 1200ms max.
+    var expirationMs = 5000;
+    var bucketSizeMs = 250;
+    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+  }
+
+  function computeInteractiveExpiration(currentTime) {
+    var expirationMs = void 0;
+    // We intentionally set a higher expiration time for interactive updates in
+    // dev than in production.
+    // If the main thread is being blocked so long that you hit the expiration,
+    // it's a problem that could be solved with better scheduling.
+    // People will be more likely to notice this and fix it with the long
+    // expiration time in development.
+    // In production we opt for better UX at the risk of masking scheduling
+    // problems, by expiring fast.
+    {
+      // Should complete within ~500ms. 600ms max.
+      expirationMs = 500;
+    }
+    var bucketSizeMs = 100;
+    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+  }
+
+  // Creates a unique async expiration time.
+  function computeUniqueAsyncExpiration() {
+    var currentTime = recalculateCurrentTime();
+    var result = computeAsyncExpiration(currentTime);
+    if (result <= lastUniqueAsyncExpiration) {
+      // Since we assume the current time monotonically increases, we only hit
+      // this branch when computeUniqueAsyncExpiration is fired multiple times
+      // within a 200ms window (or whatever the async bucket size is).
+      result = lastUniqueAsyncExpiration + 1;
+    }
+    lastUniqueAsyncExpiration = result;
+    return lastUniqueAsyncExpiration;
+  }
+
+  function computeExpirationForFiber(fiber) {
+    var expirationTime = void 0;
+    if (expirationContext !== NoWork) {
+      // An explicit expiration context was set;
+      expirationTime = expirationContext;
+    } else if (isWorking) {
+      if (isCommitting) {
+        // Updates that occur during the commit phase should have sync priority
+        // by default.
+        expirationTime = Sync;
+      } else {
+        // Updates during the render phase should expire at the same time as
+        // the work that is being rendered.
+        expirationTime = nextRenderExpirationTime;
+      }
+    } else {
+      // No explicit expiration context was set, and we're not currently
+      // performing work. Calculate a new expiration time.
+      if (fiber.mode & AsyncMode) {
+        if (isBatchingInteractiveUpdates) {
+          // This is an interactive update
+          var currentTime = recalculateCurrentTime();
+          expirationTime = computeInteractiveExpiration(currentTime);
+        } else {
+          // This is an async update
+          var _currentTime = recalculateCurrentTime();
+          expirationTime = computeAsyncExpiration(_currentTime);
+        }
+      } else {
+        // This is a sync update
+        expirationTime = Sync;
+      }
+    }
+    if (isBatchingInteractiveUpdates) {
+      // This is an interactive update. Keep track of the lowest pending
+      // interactive expiration time. This allows us to synchronously flush
+      // all interactive updates when needed.
+      if (
+        lowestPendingInteractiveExpirationTime === NoWork ||
+        expirationTime > lowestPendingInteractiveExpirationTime
+      ) {
+        lowestPendingInteractiveExpirationTime = expirationTime;
+      }
+    }
+    return expirationTime;
+  }
+
+  function scheduleWork(fiber, expirationTime) {
+    return scheduleWorkImpl(fiber, expirationTime, false);
+  }
+
+  function scheduleWorkImpl(fiber, expirationTime, isErrorRecovery) {
+    recordScheduleUpdate();
+
+    {
+      if (!isErrorRecovery && fiber.tag === ClassComponent) {
+        var instance = fiber.stateNode;
+        warnAboutInvalidUpdates(instance);
+      }
+    }
+
+    var node = fiber;
+    while (node !== null) {
+      // Walk the parent path to the root and update each node's
+      // expiration time.
+      if (
+        node.expirationTime === NoWork ||
+        node.expirationTime > expirationTime
+      ) {
+        node.expirationTime = expirationTime;
+      }
+      if (node.alternate !== null) {
+        if (
+          node.alternate.expirationTime === NoWork ||
+          node.alternate.expirationTime > expirationTime
+        ) {
+          node.alternate.expirationTime = expirationTime;
+        }
+      }
+      if (node["return"] === null) {
+        if (node.tag === HostRoot) {
+          var root = node.stateNode;
+          if (
+            !isWorking &&
+            nextRenderExpirationTime !== NoWork &&
+            expirationTime < nextRenderExpirationTime
+          ) {
+            // This is an interruption. (Used for performance tracking.)
+            interruptedBy = fiber;
+            resetStack();
+          }
+          if (
+            // If we're in the render phase, we don't need to schedule this root
+            // for an update, because we'll do it before we exit...
+            !isWorking ||
+            isCommitting ||
+            // ...unless this is a different root than the one we're rendering.
+            nextRoot !== root
+          ) {
+            // Add this root to the root schedule.
+            requestWork(root, expirationTime);
+          }
+          if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
+            invariant(
+              false,
+              "Maximum update depth exceeded. This can happen when a " +
+                "component repeatedly calls setState inside " +
+                "componentWillUpdate or componentDidUpdate. React limits " +
+                "the number of nested updates to prevent infinite loops."
+            );
+          }
+        } else {
+          {
+            if (!isErrorRecovery && fiber.tag === ClassComponent) {
+              warnAboutUpdateOnUnmounted(fiber);
+            }
+          }
+          return;
+        }
+      }
+      node = node["return"];
+    }
+  }
+
+  function recalculateCurrentTime() {
+    // Subtract initial time so it fits inside 32bits
+    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
+    mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
+    return mostRecentCurrentTime;
+  }
+
+  function deferredUpdates(fn) {
+    var previousExpirationContext = expirationContext;
+    var currentTime = recalculateCurrentTime();
+    expirationContext = computeAsyncExpiration(currentTime);
+    try {
+      return fn();
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  }
+  function syncUpdates(fn, a, b, c, d) {
+    var previousExpirationContext = expirationContext;
+    expirationContext = Sync;
+    try {
+      return fn(a, b, c, d);
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  }
+
+  // TODO: Everything below this is written as if it has been lifted to the
+  // renderers. I'll do this in a follow-up.
+
+  // Linked-list of roots
+  var firstScheduledRoot = null;
+  var lastScheduledRoot = null;
+
+  var callbackExpirationTime = NoWork;
+  var callbackID = -1;
+  var isRendering = false;
+  var nextFlushedRoot = null;
+  var nextFlushedExpirationTime = NoWork;
+  var lowestPendingInteractiveExpirationTime = NoWork;
+  var deadlineDidExpire = false;
+  var hasUnhandledError = false;
+  var unhandledError = null;
+  var deadline = null;
+
+  var isBatchingUpdates = false;
+  var isUnbatchingUpdates = false;
+  var isBatchingInteractiveUpdates = false;
+
+  var completedBatches = null;
+
+  // Use these to prevent an infinite loop of nested updates
+  var NESTED_UPDATE_LIMIT = 1000;
+  var nestedUpdateCount = 0;
+
+  var timeHeuristicForUnitOfWork = 1;
+
+  function scheduleCallbackWithExpiration(expirationTime) {
+    if (callbackExpirationTime !== NoWork) {
+      // A callback is already scheduled. Check its expiration time (timeout).
+      if (expirationTime > callbackExpirationTime) {
+        // Existing callback has sufficient timeout. Exit.
+        return;
+      } else {
+        // Existing callback has insufficient timeout. Cancel and schedule a
+        // new one.
+        cancelDeferredCallback(callbackID);
+      }
+      // The request callback timer is already running. Don't start a new one.
+    } else {
+      startRequestCallbackTimer();
+    }
+
+    // Compute a timeout for the given expiration time.
+    var currentMs = now() - originalStartTimeMs;
+    var expirationMs = expirationTimeToMs(expirationTime);
+    var timeout = expirationMs - currentMs;
+
+    callbackExpirationTime = expirationTime;
+    callbackID = scheduleDeferredCallback(performAsyncWork, {
+      timeout: timeout
+    });
+  }
+
+  // requestWork is called by the scheduler whenever a root receives an update.
+  // It's up to the renderer to call renderRoot at some point in the future.
+  function requestWork(root, expirationTime) {
+    addRootToSchedule(root, expirationTime);
+
+    if (isRendering) {
+      // Prevent reentrancy. Remaining work will be scheduled at the end of
+      // the currently rendering batch.
+      return;
+    }
+
+    if (isBatchingUpdates) {
+      // Flush work at the end of the batch.
+      if (isUnbatchingUpdates) {
+        // ...unless we're inside unbatchedUpdates, in which case we should
+        // flush it now.
+        nextFlushedRoot = root;
+        nextFlushedExpirationTime = Sync;
+        performWorkOnRoot(root, Sync, false);
+      }
+      return;
+    }
+
+    // TODO: Get rid of Sync and use current time?
+    if (expirationTime === Sync) {
+      performSyncWork();
+    } else {
+      scheduleCallbackWithExpiration(expirationTime);
+    }
+  }
+
+  function addRootToSchedule(root, expirationTime) {
+    // Add the root to the schedule.
+    // Check if this root is already part of the schedule.
+    if (root.nextScheduledRoot === null) {
+      // This root is not already scheduled. Add it.
+      root.remainingExpirationTime = expirationTime;
+      if (lastScheduledRoot === null) {
+        firstScheduledRoot = lastScheduledRoot = root;
+        root.nextScheduledRoot = root;
+      } else {
+        lastScheduledRoot.nextScheduledRoot = root;
+        lastScheduledRoot = root;
+        lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+      }
+    } else {
+      // This root is already scheduled, but its priority may have increased.
+      var remainingExpirationTime = root.remainingExpirationTime;
+      if (
+        remainingExpirationTime === NoWork ||
+        expirationTime < remainingExpirationTime
+      ) {
+        // Update the priority.
+        root.remainingExpirationTime = expirationTime;
+      }
+    }
+  }
+
+  function findHighestPriorityRoot() {
+    var highestPriorityWork = NoWork;
+    var highestPriorityRoot = null;
+    if (lastScheduledRoot !== null) {
+      var previousScheduledRoot = lastScheduledRoot;
+      var root = firstScheduledRoot;
+      while (root !== null) {
+        var remainingExpirationTime = root.remainingExpirationTime;
+        if (remainingExpirationTime === NoWork) {
+          // This root no longer has work. Remove it from the scheduler.
+
+          // TODO: This check is redudant, but Flow is confused by the branch
+          // below where we set lastScheduledRoot to null, even though we break
+          // from the loop right after.
+          invariant(
+            previousScheduledRoot !== null && lastScheduledRoot !== null,
+            "Should have a previous and last root. This error is likely " +
+              "caused by a bug in React. Please file an issue."
+          );
+          if (root === root.nextScheduledRoot) {
+            // This is the only root in the list.
+            root.nextScheduledRoot = null;
+            firstScheduledRoot = lastScheduledRoot = null;
+            break;
+          } else if (root === firstScheduledRoot) {
+            // This is the first root in the list.
+            var next = root.nextScheduledRoot;
+            firstScheduledRoot = next;
+            lastScheduledRoot.nextScheduledRoot = next;
+            root.nextScheduledRoot = null;
+          } else if (root === lastScheduledRoot) {
+            // This is the last root in the list.
+            lastScheduledRoot = previousScheduledRoot;
+            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+            root.nextScheduledRoot = null;
+            break;
+          } else {
+            previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
+            root.nextScheduledRoot = null;
+          }
+          root = previousScheduledRoot.nextScheduledRoot;
+        } else {
+          if (
+            highestPriorityWork === NoWork ||
+            remainingExpirationTime < highestPriorityWork
+          ) {
+            // Update the priority, if it's higher
+            highestPriorityWork = remainingExpirationTime;
+            highestPriorityRoot = root;
+          }
+          if (root === lastScheduledRoot) {
+            break;
+          }
+          previousScheduledRoot = root;
+          root = root.nextScheduledRoot;
+        }
+      }
+    }
+
+    // If the next root is the same as the previous root, this is a nested
+    // update. To prevent an infinite loop, increment the nested update count.
+    var previousFlushedRoot = nextFlushedRoot;
+    if (
+      previousFlushedRoot !== null &&
+      previousFlushedRoot === highestPriorityRoot &&
+      highestPriorityWork === Sync
+    ) {
+      nestedUpdateCount++;
+    } else {
+      // Reset whenever we switch roots.
+      nestedUpdateCount = 0;
+    }
+    nextFlushedRoot = highestPriorityRoot;
+    nextFlushedExpirationTime = highestPriorityWork;
+  }
+
+  function performAsyncWork(dl) {
+    performWork(NoWork, true, dl);
+  }
+
+  function performSyncWork() {
+    performWork(Sync, false, null);
+  }
+
+  function performWork(minExpirationTime, isAsync, dl) {
+    deadline = dl;
+
+    // Keep working on roots until there's no more work, or until the we reach
+    // the deadline.
+    findHighestPriorityRoot();
+
+    if (enableUserTimingAPI && deadline !== null) {
+      var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
+      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
+      stopRequestCallbackTimer(didExpire, timeout);
+    }
+
+    if (isAsync) {
+      while (
+        nextFlushedRoot !== null &&
+        nextFlushedExpirationTime !== NoWork &&
+        (minExpirationTime === NoWork ||
+          minExpirationTime >= nextFlushedExpirationTime) &&
+        (!deadlineDidExpire ||
+          recalculateCurrentTime() >= nextFlushedExpirationTime)
+      ) {
+        performWorkOnRoot(
+          nextFlushedRoot,
+          nextFlushedExpirationTime,
+          !deadlineDidExpire
+        );
+        findHighestPriorityRoot();
+      }
+    } else {
+      while (
+        nextFlushedRoot !== null &&
+        nextFlushedExpirationTime !== NoWork &&
+        (minExpirationTime === NoWork ||
+          minExpirationTime >= nextFlushedExpirationTime)
+      ) {
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
+        findHighestPriorityRoot();
+      }
+    }
+
+    // We're done flushing work. Either we ran out of time in this callback,
+    // or there's no more work left with sufficient priority.
+
+    // If we're inside a callback, set this to false since we just completed it.
+    if (deadline !== null) {
+      callbackExpirationTime = NoWork;
+      callbackID = -1;
+    }
+    // If there's work left over, schedule a new callback.
+    if (nextFlushedExpirationTime !== NoWork) {
+      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
+    }
+
+    // Clean-up.
+    deadline = null;
+    deadlineDidExpire = false;
+
+    finishRendering();
+  }
+
+  function flushRoot(root, expirationTime) {
+    invariant(
+      !isRendering,
+      "work.commit(): Cannot commit while already rendering. This likely " +
+        "means you attempted to commit from inside a lifecycle method."
+    );
+    // Perform work on root as if the given expiration time is the current time.
+    // This has the effect of synchronously flushing all work up to and
+    // including the given time.
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
+    performWorkOnRoot(root, expirationTime, false);
+    // Flush any sync work that was scheduled by lifecycles
+    performSyncWork();
+    finishRendering();
+  }
+
+  function finishRendering() {
+    nestedUpdateCount = 0;
+
+    if (completedBatches !== null) {
+      var batches = completedBatches;
+      completedBatches = null;
+      for (var i = 0; i < batches.length; i++) {
+        var batch = batches[i];
+        try {
+          batch._onComplete();
+        } catch (error) {
+          if (!hasUnhandledError) {
+            hasUnhandledError = true;
+            unhandledError = error;
+          }
+        }
+      }
+    }
+
+    if (hasUnhandledError) {
+      var error = unhandledError;
+      unhandledError = null;
+      hasUnhandledError = false;
+      throw error;
+    }
+  }
+
+  function performWorkOnRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isRendering,
+      "performWorkOnRoot was called recursively. This error is likely caused " +
+        "by a bug in React. Please file an issue."
+    );
+
+    isRendering = true;
+
+    // Check if this is async work or sync/expired work.
+    if (!isAsync) {
+      // Flush sync work.
+      var finishedWork = root.finishedWork;
+      if (finishedWork !== null) {
+        // This root is already complete. We can commit it.
+        completeRoot(root, finishedWork, expirationTime);
+      } else {
+        root.finishedWork = null;
+        finishedWork = renderRoot(root, expirationTime, false);
+        if (finishedWork !== null) {
+          // We've completed the root. Commit it.
+          completeRoot(root, finishedWork, expirationTime);
+        }
+      }
+    } else {
+      // Flush async work.
+      var _finishedWork = root.finishedWork;
+      if (_finishedWork !== null) {
+        // This root is already complete. We can commit it.
+        completeRoot(root, _finishedWork, expirationTime);
+      } else {
+        root.finishedWork = null;
+        _finishedWork = renderRoot(root, expirationTime, true);
+        if (_finishedWork !== null) {
+          // We've completed the root. Check the deadline one more time
+          // before committing.
+          if (!shouldYield()) {
+            // Still time left. Commit the root.
+            completeRoot(root, _finishedWork, expirationTime);
+          } else {
+            // There's no time left. Mark this root as complete. We'll come
+            // back and commit it later.
+            root.finishedWork = _finishedWork;
+          }
+        }
+      }
+    }
+
+    isRendering = false;
+  }
+
+  function completeRoot(root, finishedWork, expirationTime) {
+    // Check if there's a batch that matches this expiration time.
+    var firstBatch = root.firstBatch;
+    if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
+      if (completedBatches === null) {
+        completedBatches = [firstBatch];
+      } else {
+        completedBatches.push(firstBatch);
+      }
+      if (firstBatch._defer) {
+        // This root is blocked from committing by a batch. Unschedule it until
+        // we receive another update.
+        root.finishedWork = finishedWork;
+        root.remainingExpirationTime = NoWork;
+        return;
+      }
+    }
+
+    // Commit the root.
+    root.finishedWork = null;
+    root.remainingExpirationTime = commitRoot(finishedWork);
+  }
+
+  // When working on async work, the reconciler asks the renderer if it should
+  // yield execution. For DOM, we implement this with requestIdleCallback.
+  function shouldYield() {
+    if (deadline === null) {
+      return false;
+    }
+    if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
+      // Disregard deadline.didTimeout. Only expired work should be flushed
+      // during a timeout. This path is only hit for non-expired work.
+      return false;
+    }
+    deadlineDidExpire = true;
+    return true;
+  }
+
+  function onUncaughtError(error) {
+    invariant(
+      nextFlushedRoot !== null,
+      "Should be working on a root. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+    // Unschedule this root so we don't work on it again until there's
+    // another update.
+    nextFlushedRoot.remainingExpirationTime = NoWork;
+    if (!hasUnhandledError) {
+      hasUnhandledError = true;
+      unhandledError = error;
+    }
+  }
+
+  // TODO: Batching should be implemented at the renderer level, not inside
+  // the reconciler.
+  function batchedUpdates(fn, a) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      return fn(a);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performSyncWork();
+      }
+    }
+  }
+
+  // TODO: Batching should be implemented at the renderer level, not inside
+  // the reconciler.
+  function unbatchedUpdates(fn, a) {
+    if (isBatchingUpdates && !isUnbatchingUpdates) {
+      isUnbatchingUpdates = true;
+      try {
+        return fn(a);
+      } finally {
+        isUnbatchingUpdates = false;
+      }
+    }
+    return fn(a);
+  }
+
+  // TODO: Batching should be implemented at the renderer level, not within
+  // the reconciler.
+  function flushSync(fn, a) {
+    invariant(
+      !isRendering,
+      "flushSync was called from inside a lifecycle method. It cannot be " +
+        "called when React is already rendering."
+    );
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      return syncUpdates(fn, a);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      performSyncWork();
+    }
+  }
+
+  function interactiveUpdates(fn, a, b) {
+    if (isBatchingInteractiveUpdates) {
+      return fn(a, b);
+    }
+    // If there are any pending interactive updates, synchronously flush them.
+    // This needs to happen before we read any handlers, because the effect of
+    // the previous event may influence which handlers are called during
+    // this event.
+    if (
+      !isBatchingUpdates &&
+      !isRendering &&
+      lowestPendingInteractiveExpirationTime !== NoWork
+    ) {
+      // Synchronously flush pending interactive updates.
+      performWork(lowestPendingInteractiveExpirationTime, false, null);
+      lowestPendingInteractiveExpirationTime = NoWork;
+    }
+    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingInteractiveUpdates = true;
+    isBatchingUpdates = true;
+    try {
+      return fn(a, b);
+    } finally {
+      isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performSyncWork();
+      }
+    }
+  }
+
+  function flushInteractiveUpdates() {
+    if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
+      // Synchronously flush pending interactive updates.
+      performWork(lowestPendingInteractiveExpirationTime, false, null);
+      lowestPendingInteractiveExpirationTime = NoWork;
+    }
+  }
+
+  function flushControlled(fn) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      syncUpdates(fn);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performWork(Sync, false, null);
+      }
+    }
+  }
+
+  return {
+    recalculateCurrentTime: recalculateCurrentTime,
+    computeExpirationForFiber: computeExpirationForFiber,
+    scheduleWork: scheduleWork,
+    requestWork: requestWork,
+    flushRoot: flushRoot,
+    batchedUpdates: batchedUpdates,
+    unbatchedUpdates: unbatchedUpdates,
+    flushSync: flushSync,
+    flushControlled: flushControlled,
+    deferredUpdates: deferredUpdates,
+    syncUpdates: syncUpdates,
+    interactiveUpdates: interactiveUpdates,
+    flushInteractiveUpdates: flushInteractiveUpdates,
+    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+    legacyContext: legacyContext
+  };
+};
+
+var didWarnAboutNestedUpdates = void 0;
+
+{
+  didWarnAboutNestedUpdates = false;
+}
+
+// 0 is PROD, 1 is DEV.
+// Might add PROFILE later.
+
+var ReactFiberReconciler$1 = function(config) {
+  var getPublicInstance = config.getPublicInstance;
+
+  var _ReactFiberScheduler = ReactFiberScheduler(config),
+    computeUniqueAsyncExpiration =
+      _ReactFiberScheduler.computeUniqueAsyncExpiration,
+    recalculateCurrentTime = _ReactFiberScheduler.recalculateCurrentTime,
+    computeExpirationForFiber = _ReactFiberScheduler.computeExpirationForFiber,
+    scheduleWork = _ReactFiberScheduler.scheduleWork,
+    requestWork = _ReactFiberScheduler.requestWork,
+    flushRoot = _ReactFiberScheduler.flushRoot,
+    batchedUpdates = _ReactFiberScheduler.batchedUpdates,
+    unbatchedUpdates = _ReactFiberScheduler.unbatchedUpdates,
+    flushSync = _ReactFiberScheduler.flushSync,
+    flushControlled = _ReactFiberScheduler.flushControlled,
+    deferredUpdates = _ReactFiberScheduler.deferredUpdates,
+    syncUpdates = _ReactFiberScheduler.syncUpdates,
+    interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
+    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
+    legacyContext = _ReactFiberScheduler.legacyContext;
+
+  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
+
+  function getContextForSubtree(parentComponent) {
+    if (!parentComponent) {
+      return emptyObject;
+    }
+
+    var fiber = get$1(parentComponent);
+    var parentContext = findCurrentUnmaskedContext(fiber);
+    return isContextProvider(fiber)
+      ? processChildContext(fiber, parentContext)
+      : parentContext;
+  }
+
+  function scheduleRootUpdate(
+    current,
+    element,
+    currentTime,
+    expirationTime,
+    callback
+  ) {
+    {
+      if (
+        ReactDebugCurrentFiber.phase === "render" &&
+        ReactDebugCurrentFiber.current !== null &&
+        !didWarnAboutNestedUpdates
+      ) {
+        didWarnAboutNestedUpdates = true;
+        warning(
+          false,
+          "Render methods should be a pure function of props and state; " +
+            "triggering nested component updates from render is not allowed. " +
+            "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
+            "Check the render method of %s.",
+          getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
+        );
+      }
+    }
+
+    callback = callback === undefined ? null : callback;
+    {
+      !(callback === null || typeof callback === "function")
+        ? warning(
+            false,
+            "render(...): Expected the last optional `callback` argument to be a " +
+              "function. Instead received: %s.",
+            callback
+          )
+        : void 0;
+    }
+
+    var update = {
+      expirationTime: expirationTime,
+      partialState: { element: element },
+      callback: callback,
+      isReplace: false,
+      isForced: false,
+      capturedValue: null,
+      next: null
+    };
+    insertUpdateIntoFiber(current, update);
+    scheduleWork(current, expirationTime);
+
+    return expirationTime;
+  }
+
+  function updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    currentTime,
+    expirationTime,
+    callback
+  ) {
+    // TODO: If this is a nested container, this won't be the root.
+    var current = container.current;
+
+    {
+      if (ReactFiberInstrumentation_1.debugTool) {
+        if (current.alternate === null) {
+          ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
+        } else if (element === null) {
+          ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
+        } else {
+          ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
+        }
+      }
+    }
+
+    var context = getContextForSubtree(parentComponent);
+    if (container.context === null) {
+      container.context = context;
+    } else {
+      container.pendingContext = context;
+    }
+
+    return scheduleRootUpdate(
+      current,
+      element,
+      currentTime,
+      expirationTime,
+      callback
+    );
+  }
+
+  function findHostInstance(component) {
+    var fiber = get$1(component);
+    if (fiber === undefined) {
+      if (typeof component.render === "function") {
+        invariant(false, "Unable to find node on an unmounted component.");
+      } else {
+        invariant(
+          false,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        );
+      }
+    }
+    var hostFiber = findCurrentHostFiber(fiber);
+    if (hostFiber === null) {
+      return null;
+    }
+    return hostFiber.stateNode;
+  }
+
+  return {
+    createContainer: function(containerInfo, isAsync, hydrate) {
+      return createFiberRoot(containerInfo, isAsync, hydrate);
+    },
+    updateContainer: function(element, container, parentComponent, callback) {
+      var current = container.current;
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(current);
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        currentTime,
+        expirationTime,
+        callback
+      );
+    },
+    updateContainerAtExpirationTime: function(
+      element,
+      container,
+      parentComponent,
+      expirationTime,
+      callback
+    ) {
+      var currentTime = recalculateCurrentTime();
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        currentTime,
+        expirationTime,
+        callback
+      );
+    },
+
+    flushRoot: flushRoot,
+
+    requestWork: requestWork,
+
+    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+
+    batchedUpdates: batchedUpdates,
+
+    unbatchedUpdates: unbatchedUpdates,
+
+    deferredUpdates: deferredUpdates,
+
+    syncUpdates: syncUpdates,
+
+    interactiveUpdates: interactiveUpdates,
+
+    flushInteractiveUpdates: flushInteractiveUpdates,
+
+    flushControlled: flushControlled,
+
+    flushSync: flushSync,
+
+    getPublicRootInstance: function(container) {
+      var containerFiber = container.current;
+      if (!containerFiber.child) {
+        return null;
+      }
+      switch (containerFiber.child.tag) {
+        case HostComponent:
+          return getPublicInstance(containerFiber.child.stateNode);
+        default:
+          return containerFiber.child.stateNode;
+      }
+    },
+
+    findHostInstance: findHostInstance,
+
+    findHostInstanceWithNoPortals: function(fiber) {
+      var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
+      if (hostFiber === null) {
+        return null;
+      }
+      return hostFiber.stateNode;
+    },
+    injectIntoDevTools: function(devToolsConfig) {
+      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+
+      return injectInternals(
+        Object.assign({}, devToolsConfig, {
+          findHostInstanceByFiber: function(fiber) {
+            var hostFiber = findCurrentHostFiber(fiber);
+            if (hostFiber === null) {
+              return null;
+            }
+            return hostFiber.stateNode;
+          },
+          findFiberByHostInstance: function(instance) {
+            if (!findFiberByHostInstance) {
+              // Might not be implemented by the renderer.
+              return null;
+            }
+            return findFiberByHostInstance(instance);
+          }
+        })
+      );
+    }
+  };
+};
+
+var ReactFiberReconciler$2 = Object.freeze({
+  default: ReactFiberReconciler$1
+});
+
+var ReactFiberReconciler$3 =
+  (ReactFiberReconciler$2 && ReactFiberReconciler$1) || ReactFiberReconciler$2;
+
+// TODO: bundle Flow types with the package.
+
+// TODO: decide on the top-level export form.
+// This is hacky but makes it work with both Rollup and Jest.
+var reactReconciler = ReactFiberReconciler$3["default"]
+  ? ReactFiberReconciler$3["default"]
+  : ReactFiberReconciler$3;
+
+function _classCallCheck$1(instance, Constructor) {
+  if (!(instance instanceof Constructor)) {
+    throw new TypeError("Cannot call a class as a function");
+  }
+}
+
+// Modules provided by RN:
+// Counter for uniquely identifying views.
+// % 10 === 1 means it is a rootTag.
+// % 2 === 0 means it is a Fabric tag.
+// This means that they never overlap.
+var nextReactTag = 2;
+
+/**
+ * This is used for refs on host components.
+ */
+
+var ReactFabricHostComponent = (function() {
+  function ReactFabricHostComponent(tag, viewConfig, props) {
+    _classCallCheck$1(this, ReactFabricHostComponent);
+
+    this._nativeTag = tag;
+    this.viewConfig = viewConfig;
+    this.currentProps = props;
+  }
+
+  ReactFabricHostComponent.prototype.blur = function blur() {
+    TextInputState.blurTextInput(this._nativeTag);
+  };
+
+  ReactFabricHostComponent.prototype.focus = function focus() {
+    TextInputState.focusTextInput(this._nativeTag);
+  };
+
+  ReactFabricHostComponent.prototype.measure = function measure(callback) {
+    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+  };
+
+  ReactFabricHostComponent.prototype.measureInWindow = function measureInWindow(
+    callback
+  ) {
+    UIManager.measureInWindow(
+      this._nativeTag,
+      mountSafeCallback(this, callback)
+    );
+  };
+
+  ReactFabricHostComponent.prototype.measureLayout = function measureLayout(
+    relativeToNativeNode,
+    onSuccess,
+    onFail /* currently unused */
+  ) {
+    UIManager.measureLayout(
+      this._nativeTag,
+      relativeToNativeNode,
+      mountSafeCallback(this, onFail),
+      mountSafeCallback(this, onSuccess)
+    );
+  };
+
+  ReactFabricHostComponent.prototype.setNativeProps = function setNativeProps(
+    nativeProps
+  ) {
+    {
+      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
+    }
+
+    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
+
+    // Avoid the overhead of bridge calls if there's no update.
+    // This is an expensive no-op for Android, and causes an unnecessary
+    // view invalidation for certain components (eg RCTTextInput) on iOS.
+    if (updatePayload != null) {
+      UIManager.updateView(
+        this._nativeTag,
+        this.viewConfig.uiViewClassName,
+        updatePayload
+      );
+    }
+  };
+
+  return ReactFabricHostComponent;
+})();
+
+var ReactFabricRenderer = reactReconciler({
+  appendInitialChild: function(parentInstance, child) {
+    FabricUIManager.appendChild(parentInstance.node, child.node);
+  },
+  createInstance: function(
+    type,
+    props,
+    rootContainerInstance,
+    hostContext,
+    internalInstanceHandle
+  ) {
+    var tag = nextReactTag;
+    nextReactTag += 2;
+
+    var viewConfig = ReactNativeViewConfigRegistry.get(type);
+
+    {
+      for (var key in viewConfig.validAttributes) {
+        if (props.hasOwnProperty(key)) {
+          deepFreezeAndThrowOnMutationInDev(props[key]);
+        }
+      }
+    }
+
+    var updatePayload = create(props, viewConfig.validAttributes);
+
+    var node = FabricUIManager.createNode(
+      tag, // reactTag
+      viewConfig.uiViewClassName, // viewName
+      rootContainerInstance, // rootTag
+      updatePayload, // props
+      internalInstanceHandle
+    );
+
+    var component = new ReactFabricHostComponent(tag, viewConfig, props);
+
+    return {
+      node: node,
+      canonical: component
+    };
+  },
+  createTextInstance: function(
+    text,
+    rootContainerInstance,
+    hostContext,
+    internalInstanceHandle
+  ) {
+    var tag = nextReactTag;
+    nextReactTag += 2;
+
+    var node = FabricUIManager.createNode(
+      tag, // reactTag
+      "RCTRawText", // viewName
+      rootContainerInstance, // rootTag
+      { text: text }, // props
+      internalInstanceHandle
+    );
+
+    return {
+      node: node
+    };
+  },
+  finalizeInitialChildren: function(
+    parentInstance,
+    type,
+    props,
+    rootContainerInstance
+  ) {
+    return false;
+  },
+  getRootHostContext: function() {
+    return emptyObject;
+  },
+  getChildHostContext: function() {
+    return emptyObject;
+  },
+  getPublicInstance: function(instance) {
+    return instance.canonical;
+  },
+
+  now: now,
+
+  prepareForCommit: function() {
+    // Noop
+  },
+  prepareUpdate: function(
+    instance,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    hostContext
+  ) {
+    var viewConfig = instance.canonical.viewConfig;
+    var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
+    // TODO: If the event handlers have changed, we need to update the current props
+    // in the commit phase but there is no host config hook to do it yet.
+    return updatePayload;
+  },
+  resetAfterCommit: function() {
+    // Noop
+  },
+
+  scheduleDeferredCallback: scheduleDeferredCallback,
+  cancelDeferredCallback: cancelDeferredCallback,
+
+  shouldDeprioritizeSubtree: function(type, props) {
+    return false;
+  },
+  shouldSetTextContent: function(type, props) {
+    // TODO (bvaughn) Revisit this decision.
+    // Always returning false simplifies the createInstance() implementation,
+    // But creates an additional child Fiber for raw text children.
+    // No additional native views are created though.
+    // It's not clear to me which is better so I'm deferring for now.
+    // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
+    return false;
+  },
+
+  persistence: {
+    cloneInstance: function(
+      instance,
+      updatePayload,
+      type,
+      oldProps,
+      newProps,
+      internalInstanceHandle,
+      keepChildren,
+      recyclableInstance
+    ) {
+      var node = instance.node;
+      var clone = void 0;
+      if (keepChildren) {
+        if (updatePayload !== null) {
+          clone = FabricUIManager.cloneNodeWithNewProps(node, updatePayload);
+        } else {
+          clone = FabricUIManager.cloneNode(node);
+        }
+      } else {
+        if (updatePayload !== null) {
+          clone = FabricUIManager.cloneNodeWithNewChildrenAndProps(
+            node,
+            updatePayload
+          );
+        } else {
+          clone = FabricUIManager.cloneNodeWithNewChildren(node);
+        }
+      }
+      return {
+        node: clone,
+        canonical: instance.canonical
+      };
+    },
+    createContainerChildSet: function(container) {
+      return FabricUIManager.createChildSet(container);
+    },
+    appendChildToContainerChildSet: function(childSet, child) {
+      FabricUIManager.appendChildToSet(childSet, child.node);
+    },
+    finalizeContainerChildren: function(container, newChildren) {
+      FabricUIManager.completeRoot(container, newChildren);
+    },
+    replaceContainerChildren: function(container, newChildren) {}
+  }
+});
+
+// Module provided by RN:
+var getInspectorDataForViewTag = void 0;
+
+{
+  var traverseOwnerTreeUp = function(hierarchy, instance) {
+    if (instance) {
+      hierarchy.unshift(instance);
+      traverseOwnerTreeUp(hierarchy, instance._debugOwner);
+    }
+  };
+
+  var getOwnerHierarchy = function(instance) {
+    var hierarchy = [];
+    traverseOwnerTreeUp(hierarchy, instance);
+    return hierarchy;
+  };
+
+  var lastNonHostInstance = function(hierarchy) {
+    for (var i = hierarchy.length - 1; i > 1; i--) {
+      var instance = hierarchy[i];
+
+      if (instance.tag !== HostComponent) {
+        return instance;
+      }
+    }
+    return hierarchy[0];
+  };
+
+  var getHostProps = function(fiber) {
+    var host = findCurrentHostFiber(fiber);
+    if (host) {
+      return host.memoizedProps || emptyObject;
+    }
+    return emptyObject;
+  };
+
+  var getHostNode = function(fiber, findNodeHandle) {
+    var hostNode = void 0;
+    // look for children first for the hostNode
+    // as composite fibers do not have a hostNode
+    while (fiber) {
+      if (fiber.stateNode !== null && fiber.tag === HostComponent) {
+        hostNode = findNodeHandle(fiber.stateNode);
+      }
+      if (hostNode) {
+        return hostNode;
+      }
+      fiber = fiber.child;
+    }
+    return null;
+  };
+
+  var createHierarchy = function(fiberHierarchy) {
+    return fiberHierarchy.map(function(fiber) {
+      return {
+        name: getComponentName(fiber),
+        getInspectorData: function(findNodeHandle) {
+          return {
+            measure: function(callback) {
+              return UIManager.measure(
+                getHostNode(fiber, findNodeHandle),
+                callback
+              );
+            },
+            props: getHostProps(fiber),
+            source: fiber._debugSource
+          };
+        }
+      };
+    });
+  };
+
+  getInspectorDataForViewTag = function(viewTag) {
+    var closestInstance = getInstanceFromTag(viewTag);
+
+    // Handle case where user clicks outside of ReactNative
+    if (!closestInstance) {
+      return {
+        hierarchy: [],
+        props: emptyObject,
+        selection: null,
+        source: null
+      };
+    }
+
+    var fiber = findCurrentFiberUsingSlowPath(closestInstance);
+    var fiberHierarchy = getOwnerHierarchy(fiber);
+    var instance = lastNonHostInstance(fiberHierarchy);
+    var hierarchy = createHierarchy(fiberHierarchy);
+    var props = getHostProps(instance);
+    var source = instance._debugSource;
+    var selection = fiberHierarchy.indexOf(instance);
+
+    return {
+      hierarchy: hierarchy,
+      props: props,
+      selection: selection,
+      source: source
+    };
+  };
+}
+
+var findHostInstance = ReactFabricRenderer.findHostInstance;
+
+function findNodeHandle(componentOrHandle) {
+  {
+    var owner = ReactCurrentOwner.current;
+    if (owner !== null && owner.stateNode !== null) {
+      !owner.stateNode._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing findNodeHandle inside its render(). " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(owner) || "A component"
+          )
+        : void 0;
+
+      owner.stateNode._warnedAboutRefsInRender = true;
+    }
+  }
+  if (componentOrHandle == null) {
+    return null;
+  }
+  if (typeof componentOrHandle === "number") {
+    // Already a node handle
+    return componentOrHandle;
+  }
+  if (componentOrHandle._nativeTag) {
+    return componentOrHandle._nativeTag;
+  }
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag) {
+    return componentOrHandle.canonical._nativeTag;
+  }
+  var hostInstance = findHostInstance(componentOrHandle);
+  if (hostInstance == null) {
+    return hostInstance;
+  }
+  if (hostInstance.canonical) {
+    // Fabric
+    return hostInstance.canonical._nativeTag;
+  }
+  return hostInstance._nativeTag;
+}
+
+injection$2.injectRenderer(ReactFabricRenderer);
+
+var roots = new Map();
+
+var ReactFabric = {
+  NativeComponent: ReactNativeComponent(findNodeHandle, findHostInstance),
+
+  findNodeHandle: findNodeHandle,
+
+  render: function(element, containerTag, callback) {
+    var root = roots.get(containerTag);
+
+    if (!root) {
+      // TODO (bvaughn): If we decide to keep the wrapper component,
+      // We could create a wrapper for containerTag as well to reduce special casing.
+      root = ReactFabricRenderer.createContainer(containerTag, false, false);
+      roots.set(containerTag, root);
+    }
+    ReactFabricRenderer.updateContainer(element, root, null, callback);
+
+    return ReactFabricRenderer.getPublicRootInstance(root);
+  },
+  unmountComponentAtNode: function(containerTag) {
+    var root = roots.get(containerTag);
+    if (root) {
+      // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
+      ReactFabricRenderer.updateContainer(null, root, null, function() {
+        roots["delete"](containerTag);
+      });
+    }
+  },
+  createPortal: function(children, containerTag) {
+    var key =
+      arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : null;
+
+    return createPortal(children, containerTag, null, key);
+  },
+
+  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
+    // Used as a mixin in many createClass-based components
+    NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
+    // Used by react-native-github/Libraries/ components
+    ReactNativeComponentTree: ReactNativeComponentTree
+  }
+};
+
+{
+  // $FlowFixMe
+  Object.assign(
+    ReactFabric.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
+    {
+      // TODO: none of these work since Fiber. Remove these dependencies.
+      // Used by RCTRenderingPerf, Systrace:
+      ReactDebugTool: {
+        addHook: function() {},
+        removeHook: function() {}
+      },
+      // Used by ReactPerfStallHandler, RCTRenderingPerf:
+      ReactPerf: {
+        start: function() {},
+        stop: function() {},
+        printInclusive: function() {},
+        printWasted: function() {}
+      }
+    }
+  );
+}
+
+ReactFabricRenderer.injectIntoDevTools({
+  findFiberByHostInstance: getInstanceFromTag,
+  getInspectorDataForViewTag: getInspectorDataForViewTag,
+  bundleType: 1,
+  version: ReactVersion,
+  rendererPackageName: "react-native-renderer"
+});
+
+var ReactFabric$2 = Object.freeze({
+  default: ReactFabric
+});
+
+var ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
+
+// TODO: decide on the top-level export form.
+// This is hacky but makes it work with both Rollup and Jest.
+var fabric = ReactFabric$3["default"]
+  ? ReactFabric$3["default"]
+  : ReactFabric$3;
+
+module.exports = fabric;
+
+  })();
+}
diff --git a/Libraries/Renderer/oss/ReactFabric-prod.js b/Libraries/Renderer/oss/ReactFabric-prod.js
new file mode 100644
index 000000000000..48099a5351cb
--- /dev/null
+++ b/Libraries/Renderer/oss/ReactFabric-prod.js
@@ -0,0 +1,5876 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @noflow
+ * @providesModule ReactFabric-prod
+ * @preventMunge
+ */
+
+"use strict";
+require("InitializeCore");
+var invariant = require("fbjs/lib/invariant"),
+  emptyFunction = require("fbjs/lib/emptyFunction"),
+  ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
+  UIManager = require("UIManager"),
+  TextInputState = require("TextInputState"),
+  deepDiffer = require("deepDiffer"),
+  flattenStyle = require("flattenStyle"),
+  React = require("react"),
+  emptyObject = require("fbjs/lib/emptyObject"),
+  shallowEqual = require("fbjs/lib/shallowEqual"),
+  FabricUIManager = require("FabricUIManager"),
+  eventPluginOrder = null,
+  namesToPlugins = {};
+function recomputePluginOrdering() {
+  if (eventPluginOrder)
+    for (var pluginName in namesToPlugins) {
+      var pluginModule = namesToPlugins[pluginName],
+        pluginIndex = eventPluginOrder.indexOf(pluginName);
+      invariant(
+        -1 < pluginIndex,
+        "EventPluginRegistry: Cannot inject event plugins that do not exist in the plugin ordering, `%s`.",
+        pluginName
+      );
+      if (!plugins[pluginIndex]) {
+        invariant(
+          pluginModule.extractEvents,
+          "EventPluginRegistry: Event plugins must implement an `extractEvents` method, but `%s` does not.",
+          pluginName
+        );
+        plugins[pluginIndex] = pluginModule;
+        pluginIndex = pluginModule.eventTypes;
+        for (var eventName in pluginIndex) {
+          var JSCompiler_inline_result = void 0;
+          var dispatchConfig = pluginIndex[eventName],
+            pluginModule$jscomp$0 = pluginModule,
+            eventName$jscomp$0 = eventName;
+          invariant(
+            !eventNameDispatchConfigs.hasOwnProperty(eventName$jscomp$0),
+            "EventPluginHub: More than one plugin attempted to publish the same event name, `%s`.",
+            eventName$jscomp$0
+          );
+          eventNameDispatchConfigs[eventName$jscomp$0] = dispatchConfig;
+          var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
+          if (phasedRegistrationNames) {
+            for (JSCompiler_inline_result in phasedRegistrationNames)
+              phasedRegistrationNames.hasOwnProperty(
+                JSCompiler_inline_result
+              ) &&
+                publishRegistrationName(
+                  phasedRegistrationNames[JSCompiler_inline_result],
+                  pluginModule$jscomp$0,
+                  eventName$jscomp$0
+                );
+            JSCompiler_inline_result = !0;
+          } else
+            dispatchConfig.registrationName
+              ? (publishRegistrationName(
+                  dispatchConfig.registrationName,
+                  pluginModule$jscomp$0,
+                  eventName$jscomp$0
+                ),
+                (JSCompiler_inline_result = !0))
+              : (JSCompiler_inline_result = !1);
+          invariant(
+            JSCompiler_inline_result,
+            "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
+            eventName,
+            pluginName
+          );
+        }
+      }
+    }
+}
+function publishRegistrationName(registrationName, pluginModule) {
+  invariant(
+    !registrationNameModules[registrationName],
+    "EventPluginHub: More than one plugin attempted to publish the same registration name, `%s`.",
+    registrationName
+  );
+  registrationNameModules[registrationName] = pluginModule;
+}
+var plugins = [],
+  eventNameDispatchConfigs = {},
+  registrationNameModules = {},
+  getFiberCurrentPropsFromNode = null,
+  getInstanceFromNode = null,
+  getNodeFromInstance = null;
+function isEndish(topLevelType) {
+  return (
+    "topMouseUp" === topLevelType ||
+    "topTouchEnd" === topLevelType ||
+    "topTouchCancel" === topLevelType
+  );
+}
+function isMoveish(topLevelType) {
+  return "topMouseMove" === topLevelType || "topTouchMove" === topLevelType;
+}
+function isStartish(topLevelType) {
+  return "topMouseDown" === topLevelType || "topTouchStart" === topLevelType;
+}
+function executeDirectDispatch(event) {
+  var dispatchListener = event._dispatchListeners,
+    dispatchInstance = event._dispatchInstances;
+  invariant(
+    !Array.isArray(dispatchListener),
+    "executeDirectDispatch(...): Invalid `event`."
+  );
+  event.currentTarget = dispatchListener
+    ? getNodeFromInstance(dispatchInstance)
+    : null;
+  dispatchListener = dispatchListener ? dispatchListener(event) : null;
+  event.currentTarget = null;
+  event._dispatchListeners = null;
+  event._dispatchInstances = null;
+  return dispatchListener;
+}
+function accumulateInto(current, next) {
+  invariant(
+    null != next,
+    "accumulateInto(...): Accumulated items must not be null or undefined."
+  );
+  if (null == current) return next;
+  if (Array.isArray(current)) {
+    if (Array.isArray(next)) return current.push.apply(current, next), current;
+    current.push(next);
+    return current;
+  }
+  return Array.isArray(next) ? [current].concat(next) : [current, next];
+}
+function forEachAccumulated(arr, cb, scope) {
+  Array.isArray(arr) ? arr.forEach(cb, scope) : arr && cb.call(scope, arr);
+}
+var injection = {
+  injectEventPluginOrder: function(injectedEventPluginOrder) {
+    invariant(
+      !eventPluginOrder,
+      "EventPluginRegistry: Cannot inject event plugin ordering more than once. You are likely trying to load more than one copy of React."
+    );
+    eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
+    recomputePluginOrdering();
+  },
+  injectEventPluginsByName: function(injectedNamesToPlugins) {
+    var isOrderingDirty = !1,
+      pluginName;
+    for (pluginName in injectedNamesToPlugins)
+      if (injectedNamesToPlugins.hasOwnProperty(pluginName)) {
+        var pluginModule = injectedNamesToPlugins[pluginName];
+        (namesToPlugins.hasOwnProperty(pluginName) &&
+          namesToPlugins[pluginName] === pluginModule) ||
+          (invariant(
+            !namesToPlugins[pluginName],
+            "EventPluginRegistry: Cannot inject two different event plugins using the same name, `%s`.",
+            pluginName
+          ),
+          (namesToPlugins[pluginName] = pluginModule),
+          (isOrderingDirty = !0));
+      }
+    isOrderingDirty && recomputePluginOrdering();
+  }
+};
+function getListener(inst, registrationName) {
+  var listener = inst.stateNode;
+  if (!listener) return null;
+  var props = getFiberCurrentPropsFromNode(listener);
+  if (!props) return null;
+  listener = props[registrationName];
+  a: switch (registrationName) {
+    case "onClick":
+    case "onClickCapture":
+    case "onDoubleClick":
+    case "onDoubleClickCapture":
+    case "onMouseDown":
+    case "onMouseDownCapture":
+    case "onMouseMove":
+    case "onMouseMoveCapture":
+    case "onMouseUp":
+    case "onMouseUpCapture":
+      (props = !props.disabled) ||
+        ((inst = inst.type),
+        (props = !(
+          "button" === inst ||
+          "input" === inst ||
+          "select" === inst ||
+          "textarea" === inst
+        )));
+      inst = !props;
+      break a;
+    default:
+      inst = !1;
+  }
+  if (inst) return null;
+  invariant(
+    !listener || "function" === typeof listener,
+    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
+    registrationName,
+    typeof listener
+  );
+  return listener;
+}
+function getParent(inst) {
+  do inst = inst["return"];
+  while (inst && 5 !== inst.tag);
+  return inst ? inst : null;
+}
+function traverseTwoPhase(inst, fn, arg) {
+  for (var path = []; inst; ) path.push(inst), (inst = getParent(inst));
+  for (inst = path.length; 0 < inst--; ) fn(path[inst], "captured", arg);
+  for (inst = 0; inst < path.length; inst++) fn(path[inst], "bubbled", arg);
+}
+function accumulateDirectionalDispatches(inst, phase, event) {
+  if (
+    (phase = getListener(
+      inst,
+      event.dispatchConfig.phasedRegistrationNames[phase]
+    ))
+  )
+    (event._dispatchListeners = accumulateInto(
+      event._dispatchListeners,
+      phase
+    )),
+      (event._dispatchInstances = accumulateInto(
+        event._dispatchInstances,
+        inst
+      ));
+}
+function accumulateTwoPhaseDispatchesSingle(event) {
+  event &&
+    event.dispatchConfig.phasedRegistrationNames &&
+    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
+}
+function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
+  if (event && event.dispatchConfig.phasedRegistrationNames) {
+    var targetInst = event._targetInst;
+    targetInst = targetInst ? getParent(targetInst) : null;
+    traverseTwoPhase(targetInst, accumulateDirectionalDispatches, event);
+  }
+}
+function accumulateDirectDispatchesSingle(event) {
+  if (event && event.dispatchConfig.registrationName) {
+    var inst = event._targetInst;
+    if (inst && event && event.dispatchConfig.registrationName) {
+      var listener = getListener(inst, event.dispatchConfig.registrationName);
+      listener &&
+        ((event._dispatchListeners = accumulateInto(
+          event._dispatchListeners,
+          listener
+        )),
+        (event._dispatchInstances = accumulateInto(
+          event._dispatchInstances,
+          inst
+        )));
+    }
+  }
+}
+var shouldBeReleasedProperties = "dispatchConfig _targetInst nativeEvent isDefaultPrevented isPropagationStopped _dispatchListeners _dispatchInstances".split(
+    " "
+  ),
+  EventInterface = {
+    type: null,
+    target: null,
+    currentTarget: emptyFunction.thatReturnsNull,
+    eventPhase: null,
+    bubbles: null,
+    cancelable: null,
+    timeStamp: function(event) {
+      return event.timeStamp || Date.now();
+    },
+    defaultPrevented: null,
+    isTrusted: null
+  };
+function SyntheticEvent(
+  dispatchConfig,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  this.dispatchConfig = dispatchConfig;
+  this._targetInst = targetInst;
+  this.nativeEvent = nativeEvent;
+  dispatchConfig = this.constructor.Interface;
+  for (var propName in dispatchConfig)
+    dispatchConfig.hasOwnProperty(propName) &&
+      ((targetInst = dispatchConfig[propName])
+        ? (this[propName] = targetInst(nativeEvent))
+        : "target" === propName
+          ? (this.target = nativeEventTarget)
+          : (this[propName] = nativeEvent[propName]));
+  this.isDefaultPrevented = (null != nativeEvent.defaultPrevented
+  ? nativeEvent.defaultPrevented
+  : !1 === nativeEvent.returnValue)
+    ? emptyFunction.thatReturnsTrue
+    : emptyFunction.thatReturnsFalse;
+  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
+  return this;
+}
+Object.assign(SyntheticEvent.prototype, {
+  preventDefault: function() {
+    this.defaultPrevented = !0;
+    var event = this.nativeEvent;
+    event &&
+      (event.preventDefault
+        ? event.preventDefault()
+        : "unknown" !== typeof event.returnValue && (event.returnValue = !1),
+      (this.isDefaultPrevented = emptyFunction.thatReturnsTrue));
+  },
+  stopPropagation: function() {
+    var event = this.nativeEvent;
+    event &&
+      (event.stopPropagation
+        ? event.stopPropagation()
+        : "unknown" !== typeof event.cancelBubble && (event.cancelBubble = !0),
+      (this.isPropagationStopped = emptyFunction.thatReturnsTrue));
+  },
+  persist: function() {
+    this.isPersistent = emptyFunction.thatReturnsTrue;
+  },
+  isPersistent: emptyFunction.thatReturnsFalse,
+  destructor: function() {
+    var Interface = this.constructor.Interface,
+      propName;
+    for (propName in Interface) this[propName] = null;
+    for (
+      Interface = 0;
+      Interface < shouldBeReleasedProperties.length;
+      Interface++
+    )
+      this[shouldBeReleasedProperties[Interface]] = null;
+  }
+});
+SyntheticEvent.Interface = EventInterface;
+SyntheticEvent.extend = function(Interface) {
+  function E() {}
+  function Class() {
+    return Super.apply(this, arguments);
+  }
+  var Super = this;
+  E.prototype = Super.prototype;
+  var prototype = new E();
+  Object.assign(prototype, Class.prototype);
+  Class.prototype = prototype;
+  Class.prototype.constructor = Class;
+  Class.Interface = Object.assign({}, Super.Interface, Interface);
+  Class.extend = Super.extend;
+  addEventPoolingTo(Class);
+  return Class;
+};
+addEventPoolingTo(SyntheticEvent);
+function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
+  if (this.eventPool.length) {
+    var instance = this.eventPool.pop();
+    this.call(instance, dispatchConfig, targetInst, nativeEvent, nativeInst);
+    return instance;
+  }
+  return new this(dispatchConfig, targetInst, nativeEvent, nativeInst);
+}
+function releasePooledEvent(event) {
+  invariant(
+    event instanceof this,
+    "Trying to release an event instance  into a pool of a different type."
+  );
+  event.destructor();
+  10 > this.eventPool.length && this.eventPool.push(event);
+}
+function addEventPoolingTo(EventConstructor) {
+  EventConstructor.eventPool = [];
+  EventConstructor.getPooled = getPooledEvent;
+  EventConstructor.release = releasePooledEvent;
+}
+var ResponderSyntheticEvent = SyntheticEvent.extend({
+    touchHistory: function() {
+      return null;
+    }
+  }),
+  touchBank = [],
+  touchHistory = {
+    touchBank: touchBank,
+    numberActiveTouches: 0,
+    indexOfSingleActiveTouch: -1,
+    mostRecentTimeStamp: 0
+  };
+function timestampForTouch(touch) {
+  return touch.timeStamp || touch.timestamp;
+}
+function getTouchIdentifier(_ref) {
+  _ref = _ref.identifier;
+  invariant(null != _ref, "Touch object is missing identifier.");
+  return _ref;
+}
+function recordTouchStart(touch) {
+  var identifier = getTouchIdentifier(touch),
+    touchRecord = touchBank[identifier];
+  touchRecord
+    ? ((touchRecord.touchActive = !0),
+      (touchRecord.startPageX = touch.pageX),
+      (touchRecord.startPageY = touch.pageY),
+      (touchRecord.startTimeStamp = timestampForTouch(touch)),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchRecord.previousPageX = touch.pageX),
+      (touchRecord.previousPageY = touch.pageY),
+      (touchRecord.previousTimeStamp = timestampForTouch(touch)))
+    : ((touchRecord = {
+        touchActive: !0,
+        startPageX: touch.pageX,
+        startPageY: touch.pageY,
+        startTimeStamp: timestampForTouch(touch),
+        currentPageX: touch.pageX,
+        currentPageY: touch.pageY,
+        currentTimeStamp: timestampForTouch(touch),
+        previousPageX: touch.pageX,
+        previousPageY: touch.pageY,
+        previousTimeStamp: timestampForTouch(touch)
+      }),
+      (touchBank[identifier] = touchRecord));
+  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+}
+function recordTouchMove(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  touchRecord
+    ? ((touchRecord.touchActive = !0),
+      (touchRecord.previousPageX = touchRecord.currentPageX),
+      (touchRecord.previousPageY = touchRecord.currentPageY),
+      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
+    : console.error(
+        "Cannot record touch move without a touch start.\nTouch Move: %s\n",
+        "Touch Bank: %s",
+        printTouch(touch),
+        printTouchBank()
+      );
+}
+function recordTouchEnd(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  touchRecord
+    ? ((touchRecord.touchActive = !1),
+      (touchRecord.previousPageX = touchRecord.currentPageX),
+      (touchRecord.previousPageY = touchRecord.currentPageY),
+      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
+    : console.error(
+        "Cannot record touch end without a touch start.\nTouch End: %s\n",
+        "Touch Bank: %s",
+        printTouch(touch),
+        printTouchBank()
+      );
+}
+function printTouch(touch) {
+  return JSON.stringify({
+    identifier: touch.identifier,
+    pageX: touch.pageX,
+    pageY: touch.pageY,
+    timestamp: timestampForTouch(touch)
+  });
+}
+function printTouchBank() {
+  var printed = JSON.stringify(touchBank.slice(0, 20));
+  20 < touchBank.length &&
+    (printed += " (original size: " + touchBank.length + ")");
+  return printed;
+}
+var ResponderTouchHistoryStore = {
+  recordTouchTrack: function(topLevelType, nativeEvent) {
+    if (isMoveish(topLevelType))
+      nativeEvent.changedTouches.forEach(recordTouchMove);
+    else if (isStartish(topLevelType))
+      nativeEvent.changedTouches.forEach(recordTouchStart),
+        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+        1 === touchHistory.numberActiveTouches &&
+          (touchHistory.indexOfSingleActiveTouch =
+            nativeEvent.touches[0].identifier);
+    else if (
+      isEndish(topLevelType) &&
+      (nativeEvent.changedTouches.forEach(recordTouchEnd),
+      (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+      1 === touchHistory.numberActiveTouches)
+    )
+      for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
+        if (
+          ((nativeEvent = touchBank[topLevelType]),
+          null != nativeEvent && nativeEvent.touchActive)
+        ) {
+          touchHistory.indexOfSingleActiveTouch = topLevelType;
+          break;
+        }
+  },
+  touchHistory: touchHistory
+};
+function accumulate(current, next) {
+  invariant(
+    null != next,
+    "accumulate(...): Accumulated items must be not be null or undefined."
+  );
+  return null == current
+    ? next
+    : Array.isArray(current)
+      ? current.concat(next)
+      : Array.isArray(next) ? [current].concat(next) : [current, next];
+}
+var responderInst = null,
+  trackedTouchCount = 0,
+  previousActiveTouches = 0;
+function changeResponder(nextResponderInst, blockHostResponder) {
+  var oldResponderInst = responderInst;
+  responderInst = nextResponderInst;
+  if (null !== ResponderEventPlugin.GlobalResponderHandler)
+    ResponderEventPlugin.GlobalResponderHandler.onChange(
+      oldResponderInst,
+      nextResponderInst,
+      blockHostResponder
+    );
+}
+var eventTypes$1 = {
+    startShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onStartShouldSetResponder",
+        captured: "onStartShouldSetResponderCapture"
+      }
+    },
+    scrollShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onScrollShouldSetResponder",
+        captured: "onScrollShouldSetResponderCapture"
+      }
+    },
+    selectionChangeShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onSelectionChangeShouldSetResponder",
+        captured: "onSelectionChangeShouldSetResponderCapture"
+      }
+    },
+    moveShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onMoveShouldSetResponder",
+        captured: "onMoveShouldSetResponderCapture"
+      }
+    },
+    responderStart: { registrationName: "onResponderStart" },
+    responderMove: { registrationName: "onResponderMove" },
+    responderEnd: { registrationName: "onResponderEnd" },
+    responderRelease: { registrationName: "onResponderRelease" },
+    responderTerminationRequest: {
+      registrationName: "onResponderTerminationRequest"
+    },
+    responderGrant: { registrationName: "onResponderGrant" },
+    responderReject: { registrationName: "onResponderReject" },
+    responderTerminate: { registrationName: "onResponderTerminate" }
+  },
+  ResponderEventPlugin = {
+    _getResponder: function() {
+      return responderInst;
+    },
+    eventTypes: eventTypes$1,
+    extractEvents: function(
+      topLevelType,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    ) {
+      if (isStartish(topLevelType)) trackedTouchCount += 1;
+      else if (isEndish(topLevelType))
+        if (0 <= trackedTouchCount) --trackedTouchCount;
+        else
+          return (
+            console.error(
+              "Ended a touch event which was not counted in `trackedTouchCount`."
+            ),
+            null
+          );
+      ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
+      if (
+        targetInst &&
+        (("topScroll" === topLevelType && !nativeEvent.responderIgnoreScroll) ||
+          (0 < trackedTouchCount && "topSelectionChange" === topLevelType) ||
+          isStartish(topLevelType) ||
+          isMoveish(topLevelType))
+      ) {
+        var JSCompiler_temp = isStartish(topLevelType)
+          ? eventTypes$1.startShouldSetResponder
+          : isMoveish(topLevelType)
+            ? eventTypes$1.moveShouldSetResponder
+            : "topSelectionChange" === topLevelType
+              ? eventTypes$1.selectionChangeShouldSetResponder
+              : eventTypes$1.scrollShouldSetResponder;
+        if (responderInst)
+          b: {
+            var JSCompiler_temp$jscomp$0 = responderInst;
+            for (
+              var depthA = 0, tempA = JSCompiler_temp$jscomp$0;
+              tempA;
+              tempA = getParent(tempA)
+            )
+              depthA++;
+            tempA = 0;
+            for (var tempB = targetInst; tempB; tempB = getParent(tempB))
+              tempA++;
+            for (; 0 < depthA - tempA; )
+              (JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0)),
+                depthA--;
+            for (; 0 < tempA - depthA; )
+              (targetInst = getParent(targetInst)), tempA--;
+            for (; depthA--; ) {
+              if (
+                JSCompiler_temp$jscomp$0 === targetInst ||
+                JSCompiler_temp$jscomp$0 === targetInst.alternate
+              )
+                break b;
+              JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0);
+              targetInst = getParent(targetInst);
+            }
+            JSCompiler_temp$jscomp$0 = null;
+          }
+        else JSCompiler_temp$jscomp$0 = targetInst;
+        targetInst = JSCompiler_temp$jscomp$0 === responderInst;
+        JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
+          JSCompiler_temp,
+          JSCompiler_temp$jscomp$0,
+          nativeEvent,
+          nativeEventTarget
+        );
+        JSCompiler_temp$jscomp$0.touchHistory =
+          ResponderTouchHistoryStore.touchHistory;
+        targetInst
+          ? forEachAccumulated(
+              JSCompiler_temp$jscomp$0,
+              accumulateTwoPhaseDispatchesSingleSkipTarget
+            )
+          : forEachAccumulated(
+              JSCompiler_temp$jscomp$0,
+              accumulateTwoPhaseDispatchesSingle
+            );
+        b: {
+          JSCompiler_temp = JSCompiler_temp$jscomp$0._dispatchListeners;
+          targetInst = JSCompiler_temp$jscomp$0._dispatchInstances;
+          if (Array.isArray(JSCompiler_temp))
+            for (
+              depthA = 0;
+              depthA < JSCompiler_temp.length &&
+              !JSCompiler_temp$jscomp$0.isPropagationStopped();
+              depthA++
+            ) {
+              if (
+                JSCompiler_temp[depthA](
+                  JSCompiler_temp$jscomp$0,
+                  targetInst[depthA]
+                )
+              ) {
+                JSCompiler_temp = targetInst[depthA];
+                break b;
+              }
+            }
+          else if (
+            JSCompiler_temp &&
+            JSCompiler_temp(JSCompiler_temp$jscomp$0, targetInst)
+          ) {
+            JSCompiler_temp = targetInst;
+            break b;
+          }
+          JSCompiler_temp = null;
+        }
+        JSCompiler_temp$jscomp$0._dispatchInstances = null;
+        JSCompiler_temp$jscomp$0._dispatchListeners = null;
+        JSCompiler_temp$jscomp$0.isPersistent() ||
+          JSCompiler_temp$jscomp$0.constructor.release(
+            JSCompiler_temp$jscomp$0
+          );
+        JSCompiler_temp && JSCompiler_temp !== responderInst
+          ? ((JSCompiler_temp$jscomp$0 = void 0),
+            (targetInst = ResponderSyntheticEvent.getPooled(
+              eventTypes$1.responderGrant,
+              JSCompiler_temp,
+              nativeEvent,
+              nativeEventTarget
+            )),
+            (targetInst.touchHistory = ResponderTouchHistoryStore.touchHistory),
+            forEachAccumulated(targetInst, accumulateDirectDispatchesSingle),
+            (depthA = !0 === executeDirectDispatch(targetInst)),
+            responderInst
+              ? ((tempA = ResponderSyntheticEvent.getPooled(
+                  eventTypes$1.responderTerminationRequest,
+                  responderInst,
+                  nativeEvent,
+                  nativeEventTarget
+                )),
+                (tempA.touchHistory = ResponderTouchHistoryStore.touchHistory),
+                forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
+                (tempB =
+                  !tempA._dispatchListeners || executeDirectDispatch(tempA)),
+                tempA.isPersistent() || tempA.constructor.release(tempA),
+                tempB
+                  ? ((tempA = ResponderSyntheticEvent.getPooled(
+                      eventTypes$1.responderTerminate,
+                      responderInst,
+                      nativeEvent,
+                      nativeEventTarget
+                    )),
+                    (tempA.touchHistory =
+                      ResponderTouchHistoryStore.touchHistory),
+                    forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
+                    (JSCompiler_temp$jscomp$0 = accumulate(
+                      JSCompiler_temp$jscomp$0,
+                      [targetInst, tempA]
+                    )),
+                    changeResponder(JSCompiler_temp, depthA))
+                  : ((JSCompiler_temp = ResponderSyntheticEvent.getPooled(
+                      eventTypes$1.responderReject,
+                      JSCompiler_temp,
+                      nativeEvent,
+                      nativeEventTarget
+                    )),
+                    (JSCompiler_temp.touchHistory =
+                      ResponderTouchHistoryStore.touchHistory),
+                    forEachAccumulated(
+                      JSCompiler_temp,
+                      accumulateDirectDispatchesSingle
+                    ),
+                    (JSCompiler_temp$jscomp$0 = accumulate(
+                      JSCompiler_temp$jscomp$0,
+                      JSCompiler_temp
+                    ))))
+              : ((JSCompiler_temp$jscomp$0 = accumulate(
+                  JSCompiler_temp$jscomp$0,
+                  targetInst
+                )),
+                changeResponder(JSCompiler_temp, depthA)),
+            (JSCompiler_temp = JSCompiler_temp$jscomp$0))
+          : (JSCompiler_temp = null);
+      } else JSCompiler_temp = null;
+      JSCompiler_temp$jscomp$0 = responderInst && isStartish(topLevelType);
+      targetInst = responderInst && isMoveish(topLevelType);
+      depthA = responderInst && isEndish(topLevelType);
+      if (
+        (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
+          ? eventTypes$1.responderStart
+          : targetInst
+            ? eventTypes$1.responderMove
+            : depthA ? eventTypes$1.responderEnd : null)
+      )
+        (JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
+          JSCompiler_temp$jscomp$0,
+          responderInst,
+          nativeEvent,
+          nativeEventTarget
+        )),
+          (JSCompiler_temp$jscomp$0.touchHistory =
+            ResponderTouchHistoryStore.touchHistory),
+          forEachAccumulated(
+            JSCompiler_temp$jscomp$0,
+            accumulateDirectDispatchesSingle
+          ),
+          (JSCompiler_temp = accumulate(
+            JSCompiler_temp,
+            JSCompiler_temp$jscomp$0
+          ));
+      JSCompiler_temp$jscomp$0 =
+        responderInst && "topTouchCancel" === topLevelType;
+      if (
+        (topLevelType =
+          responderInst && !JSCompiler_temp$jscomp$0 && isEndish(topLevelType))
+      )
+        a: {
+          if ((topLevelType = nativeEvent.touches) && 0 !== topLevelType.length)
+            for (targetInst = 0; targetInst < topLevelType.length; targetInst++)
+              if (
+                ((depthA = topLevelType[targetInst].target),
+                null !== depthA && void 0 !== depthA && 0 !== depthA)
+              ) {
+                tempA = getInstanceFromNode(depthA);
+                b: {
+                  for (depthA = responderInst; tempA; ) {
+                    if (depthA === tempA || depthA === tempA.alternate) {
+                      depthA = !0;
+                      break b;
+                    }
+                    tempA = getParent(tempA);
+                  }
+                  depthA = !1;
+                }
+                if (depthA) {
+                  topLevelType = !1;
+                  break a;
+                }
+              }
+          topLevelType = !0;
+        }
+      if (
+        (topLevelType = JSCompiler_temp$jscomp$0
+          ? eventTypes$1.responderTerminate
+          : topLevelType ? eventTypes$1.responderRelease : null)
+      )
+        (nativeEvent = ResponderSyntheticEvent.getPooled(
+          topLevelType,
+          responderInst,
+          nativeEvent,
+          nativeEventTarget
+        )),
+          (nativeEvent.touchHistory = ResponderTouchHistoryStore.touchHistory),
+          forEachAccumulated(nativeEvent, accumulateDirectDispatchesSingle),
+          (JSCompiler_temp = accumulate(JSCompiler_temp, nativeEvent)),
+          changeResponder(null);
+      nativeEvent = ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
+      if (
+        ResponderEventPlugin.GlobalInteractionHandler &&
+        nativeEvent !== previousActiveTouches
+      )
+        ResponderEventPlugin.GlobalInteractionHandler.onChange(nativeEvent);
+      previousActiveTouches = nativeEvent;
+      return JSCompiler_temp;
+    },
+    GlobalResponderHandler: null,
+    GlobalInteractionHandler: null,
+    injection: {
+      injectGlobalResponderHandler: function(GlobalResponderHandler) {
+        ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
+      },
+      injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
+        ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
+      }
+    }
+  },
+  customBubblingEventTypes$1 =
+    ReactNativeViewConfigRegistry.customBubblingEventTypes,
+  customDirectEventTypes$1 =
+    ReactNativeViewConfigRegistry.customDirectEventTypes,
+  ReactNativeBridgeEventPlugin = {
+    eventTypes: ReactNativeViewConfigRegistry.eventTypes,
+    extractEvents: function(
+      topLevelType,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    ) {
+      if (null == targetInst) return null;
+      var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType],
+        directDispatchConfig = customDirectEventTypes$1[topLevelType];
+      invariant(
+        bubbleDispatchConfig || directDispatchConfig,
+        'Unsupported top level event type "%s" dispatched',
+        topLevelType
+      );
+      topLevelType = SyntheticEvent.getPooled(
+        bubbleDispatchConfig || directDispatchConfig,
+        targetInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      if (bubbleDispatchConfig)
+        forEachAccumulated(topLevelType, accumulateTwoPhaseDispatchesSingle);
+      else if (directDispatchConfig)
+        forEachAccumulated(topLevelType, accumulateDirectDispatchesSingle);
+      else return null;
+      return topLevelType;
+    }
+  },
+  instanceCache = {},
+  instanceProps = {};
+function getInstanceFromTag(tag) {
+  return "number" === typeof tag ? instanceCache[tag] || null : tag;
+}
+var ReactNativeComponentTree = Object.freeze({
+  precacheFiberNode: function(hostInst, tag) {
+    instanceCache[tag] = hostInst;
+  },
+  uncacheFiberNode: function(tag) {
+    delete instanceCache[tag];
+    delete instanceProps[tag];
+  },
+  getClosestInstanceFromNode: getInstanceFromTag,
+  getInstanceFromNode: getInstanceFromTag,
+  getNodeFromInstance: function(inst) {
+    var tag = inst.stateNode._nativeTag;
+    void 0 === tag && (tag = inst.stateNode.canonical._nativeTag);
+    invariant(tag, "All native instances should have a tag.");
+    return tag;
+  },
+  getFiberCurrentPropsFromNode: function(stateNode) {
+    return instanceProps[stateNode._nativeTag] || null;
+  },
+  updateFiberProps: function(tag, props) {
+    instanceProps[tag] = props;
+  }
+});
+injection.injectEventPluginOrder([
+  "ResponderEventPlugin",
+  "ReactNativeBridgeEventPlugin"
+]);
+getFiberCurrentPropsFromNode =
+  ReactNativeComponentTree.getFiberCurrentPropsFromNode;
+getInstanceFromNode = ReactNativeComponentTree.getInstanceFromNode;
+getNodeFromInstance = ReactNativeComponentTree.getNodeFromInstance;
+ResponderEventPlugin.injection.injectGlobalResponderHandler({
+  onChange: function(from, to, blockNativeResponder) {
+    null !== to
+      ? UIManager.setJSResponder(to.stateNode._nativeTag, blockNativeResponder)
+      : UIManager.clearJSResponder();
+  }
+});
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
+var hasSymbol = "function" === typeof Symbol && Symbol["for"],
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
+  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
+  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol
+    ? Symbol["for"]("react.strict_mode")
+    : 60108,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol
+    ? Symbol["for"]("react.forward_ref")
+    : 60112,
+  MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
+function getIteratorFn(maybeIterable) {
+  if (null === maybeIterable || "undefined" === typeof maybeIterable)
+    return null;
+  maybeIterable =
+    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
+    maybeIterable["@@iterator"];
+  return "function" === typeof maybeIterable ? maybeIterable : null;
+}
+function createPortal(children, containerInfo, implementation) {
+  var key =
+    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
+  return {
+    $$typeof: REACT_PORTAL_TYPE,
+    key: null == key ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+var emptyObject$1 = {},
+  removedKeys = null,
+  removedKeyCount = 0;
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node))
+    for (var i = node.length; i-- && 0 < removedKeyCount; )
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+  else if (node && 0 < removedKeyCount)
+    for (i in removedKeys)
+      if (removedKeys[i]) {
+        var _nextProp = node[i];
+        if (void 0 !== _nextProp) {
+          var attributeConfig = validAttributes[i];
+          if (attributeConfig) {
+            "function" === typeof _nextProp && (_nextProp = !0);
+            "undefined" === typeof _nextProp && (_nextProp = null);
+            if ("object" !== typeof attributeConfig)
+              updatePayload[i] = _nextProp;
+            else if (
+              "function" === typeof attributeConfig.diff ||
+              "function" === typeof attributeConfig.process
+            )
+              (_nextProp =
+                "function" === typeof attributeConfig.process
+                  ? attributeConfig.process(_nextProp)
+                  : _nextProp),
+                (updatePayload[i] = _nextProp);
+            removedKeys[i] = !1;
+            removedKeyCount--;
+          }
+        }
+      }
+}
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) return updatePayload;
+  if (!prevProp || !nextProp)
+    return nextProp
+      ? addNestedProperty(updatePayload, nextProp, validAttributes)
+      : prevProp
+        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
+        : updatePayload;
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    var minLength =
+        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
+      i;
+    for (i = 0; i < minLength; i++)
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp[i],
+        nextProp[i],
+        validAttributes
+      );
+    for (; i < prevProp.length; i++)
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp[i],
+        validAttributes
+      );
+    for (; i < nextProp.length; i++)
+      updatePayload = addNestedProperty(
+        updatePayload,
+        nextProp[i],
+        validAttributes
+      );
+    return updatePayload;
+  }
+  return Array.isArray(prevProp)
+    ? diffProperties(
+        updatePayload,
+        flattenStyle(prevProp),
+        nextProp,
+        validAttributes
+      )
+    : diffProperties(
+        updatePayload,
+        prevProp,
+        flattenStyle(nextProp),
+        validAttributes
+      );
+}
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) return updatePayload;
+  if (!Array.isArray(nextProp))
+    return diffProperties(
+      updatePayload,
+      emptyObject$1,
+      nextProp,
+      validAttributes
+    );
+  for (var i = 0; i < nextProp.length; i++)
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) return updatePayload;
+  if (!Array.isArray(prevProp))
+    return diffProperties(
+      updatePayload,
+      prevProp,
+      emptyObject$1,
+      validAttributes
+    );
+  for (var i = 0; i < prevProp.length; i++)
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig, propKey;
+  for (propKey in nextProps)
+    if ((attributeConfig = validAttributes[propKey])) {
+      var prevProp = prevProps[propKey];
+      var nextProp = nextProps[propKey];
+      "function" === typeof nextProp &&
+        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
+      "undefined" === typeof nextProp &&
+        ((nextProp = null),
+        "undefined" === typeof prevProp && (prevProp = null));
+      removedKeys && (removedKeys[propKey] = !1);
+      if (updatePayload && void 0 !== updatePayload[propKey])
+        if ("object" !== typeof attributeConfig)
+          updatePayload[propKey] = nextProp;
+        else {
+          if (
+            "function" === typeof attributeConfig.diff ||
+            "function" === typeof attributeConfig.process
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              (updatePayload[propKey] = attributeConfig);
+        }
+      else if (prevProp !== nextProp)
+        if ("object" !== typeof attributeConfig)
+          ("object" !== typeof nextProp ||
+            null === nextProp ||
+            deepDiffer(prevProp, nextProp)) &&
+            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
+        else if (
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+        ) {
+          if (
+            void 0 === prevProp ||
+            ("function" === typeof attributeConfig.diff
+              ? attributeConfig.diff(prevProp, nextProp)
+              : "object" !== typeof nextProp ||
+                null === nextProp ||
+                deepDiffer(prevProp, nextProp))
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              ((updatePayload || (updatePayload = {}))[
+                propKey
+              ] = attributeConfig);
+        } else
+          (removedKeys = null),
+            (removedKeyCount = 0),
+            (updatePayload = diffNestedProperty(
+              updatePayload,
+              prevProp,
+              nextProp,
+              attributeConfig
+            )),
+            0 < removedKeyCount &&
+              updatePayload &&
+              (restoreDeletedValuesInNestedArray(
+                updatePayload,
+                nextProp,
+                attributeConfig
+              ),
+              (removedKeys = null));
+    }
+  for (var _propKey in prevProps)
+    void 0 === nextProps[_propKey] &&
+      (!(attributeConfig = validAttributes[_propKey]) ||
+        (updatePayload && void 0 !== updatePayload[_propKey]) ||
+        ((prevProp = prevProps[_propKey]),
+        void 0 !== prevProp &&
+          ("object" !== typeof attributeConfig ||
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
+              removedKeys || (removedKeys = {}),
+              removedKeys[_propKey] ||
+                ((removedKeys[_propKey] = !0), removedKeyCount++))
+            : (updatePayload = clearNestedProperty(
+                updatePayload,
+                prevProp,
+                attributeConfig
+              )))));
+  return updatePayload;
+}
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (callback) {
+      if ("boolean" === typeof context.__isMounted) {
+        if (!context.__isMounted) return;
+      } else if (
+        "function" === typeof context.isMounted &&
+        !context.isMounted()
+      )
+        return;
+      return callback.apply(context, arguments);
+    }
+  };
+}
+function _inherits(subClass, superClass) {
+  if ("function" !== typeof superClass && null !== superClass)
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: !1,
+      writable: !0,
+      configurable: !0
+    }
+  });
+  superClass &&
+    (Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass));
+}
+var now =
+    "object" === typeof performance && "function" === typeof performance.now
+      ? function() {
+          return performance.now();
+        }
+      : function() {
+          return Date.now();
+        },
+  scheduledCallback = null,
+  frameDeadline = 0,
+  frameDeadlineObject = {
+    timeRemaining: function() {
+      return frameDeadline - now();
+    },
+    didTimeout: !1
+  };
+function setTimeoutCallback() {
+  frameDeadline = now() + 5;
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  null !== callback && callback(frameDeadlineObject);
+}
+var ReactCurrentOwner =
+  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
+function getComponentName(fiber) {
+  fiber = fiber.type;
+  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
+  if ("string" === typeof fiber) return fiber;
+  switch (fiber) {
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_RETURN_TYPE:
+      return "ReactReturn";
+  }
+  if ("object" === typeof fiber && null !== fiber)
+    switch (fiber.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        return (
+          (fiber = fiber.render.displayName || fiber.render.name || ""),
+          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
+        );
+    }
+  return null;
+}
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
+  else {
+    if (0 !== (node.effectTag & 2)) return 1;
+    for (; node["return"]; )
+      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
+  }
+  return 3 === node.tag ? 2 : 3;
+}
+function isMounted(component) {
+  return (component = component._reactInternalFiber)
+    ? 2 === isFiberMountedImpl(component)
+    : !1;
+}
+function assertIsMounted(fiber) {
+  invariant(
+    2 === isFiberMountedImpl(fiber),
+    "Unable to find node on an unmounted component."
+  );
+}
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate)
+    return (
+      (alternate = isFiberMountedImpl(fiber)),
+      invariant(
+        3 !== alternate,
+        "Unable to find node on an unmounted component."
+      ),
+      1 === alternate ? null : fiber
+    );
+  for (var a = fiber, b = alternate; ; ) {
+    var parentA = a["return"],
+      parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) break;
+    if (parentA.child === parentB.child) {
+      for (var child = parentA.child; child; ) {
+        if (child === a) return assertIsMounted(parentA), fiber;
+        if (child === b) return assertIsMounted(parentA), alternate;
+        child = child.sibling;
+      }
+      invariant(!1, "Unable to find node on an unmounted component.");
+    }
+    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
+    else {
+      child = !1;
+      for (var _child = parentA.child; _child; ) {
+        if (_child === a) {
+          child = !0;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          child = !0;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!child) {
+        for (_child = parentB.child; _child; ) {
+          if (_child === a) {
+            child = !0;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            child = !0;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          child,
+          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
+        );
+      }
+    }
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
+  return a.stateNode.current === a ? fiber : alternate;
+}
+function findCurrentHostFiber(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child) (node.child["return"] = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node["return"] || node["return"] === parent) return null;
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+  return null;
+}
+function findCurrentHostFiberWithNoPortals(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child && 4 !== node.tag)
+      (node.child["return"] = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node["return"] || node["return"] === parent) return null;
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+  return null;
+}
+function FiberNode(tag, pendingProps, key, mode) {
+  this.tag = tag;
+  this.key = key;
+  this.stateNode = this.type = null;
+  this.sibling = this.child = this["return"] = null;
+  this.index = 0;
+  this.ref = null;
+  this.pendingProps = pendingProps;
+  this.memoizedState = this.updateQueue = this.memoizedProps = null;
+  this.mode = mode;
+  this.effectTag = 0;
+  this.lastEffect = this.firstEffect = this.nextEffect = null;
+  this.expirationTime = 0;
+  this.alternate = null;
+}
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  null === workInProgress
+    ? ((workInProgress = new FiberNode(
+        current.tag,
+        pendingProps,
+        current.key,
+        current.mode
+      )),
+      (workInProgress.type = current.type),
+      (workInProgress.stateNode = current.stateNode),
+      (workInProgress.alternate = current),
+      (current.alternate = workInProgress))
+    : ((workInProgress.pendingProps = pendingProps),
+      (workInProgress.effectTag = 0),
+      (workInProgress.nextEffect = null),
+      (workInProgress.firstEffect = null),
+      (workInProgress.lastEffect = null));
+  workInProgress.expirationTime = expirationTime;
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+  return workInProgress;
+}
+function createFiberFromElement(element, mode, expirationTime) {
+  var type = element.type,
+    key = element.key;
+  element = element.props;
+  var fiberTag = void 0;
+  if ("function" === typeof type)
+    fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
+  else if ("string" === typeof type) fiberTag = 5;
+  else
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          element.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 3;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 2;
+        break;
+      case REACT_CALL_TYPE:
+        fiberTag = 7;
+        break;
+      case REACT_RETURN_TYPE:
+        fiberTag = 9;
+        break;
+      default:
+        if ("object" === typeof type && null !== type)
+          switch (type.$$typeof) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = 13;
+              break;
+            case REACT_CONTEXT_TYPE:
+              fiberTag = 12;
+              break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = 14;
+              break;
+            default:
+              if ("number" === typeof type.tag)
+                return (
+                  (mode = type),
+                  (mode.pendingProps = element),
+                  (mode.expirationTime = expirationTime),
+                  mode
+                );
+              throwOnInvalidElementType(type, null);
+          }
+        else throwOnInvalidElementType(type, null);
+    }
+  mode = new FiberNode(fiberTag, element, key, mode);
+  mode.type = type;
+  mode.expirationTime = expirationTime;
+  return mode;
+}
+function throwOnInvalidElementType(type) {
+  invariant(
+    !1,
+    "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
+    null == type ? type : typeof type,
+    ""
+  );
+}
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  elements = new FiberNode(10, elements, key, mode);
+  elements.expirationTime = expirationTime;
+  return elements;
+}
+function createFiberFromText(content, mode, expirationTime) {
+  content = new FiberNode(6, content, null, mode);
+  content.expirationTime = expirationTime;
+  return content;
+}
+function createFiberFromPortal(portal, mode, expirationTime) {
+  mode = new FiberNode(
+    4,
+    null !== portal.children ? portal.children : [],
+    portal.key,
+    mode
+  );
+  mode.expirationTime = expirationTime;
+  mode.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null,
+    implementation: portal.implementation
+  };
+  return mode;
+}
+var onCommitFiberRoot = null,
+  onCommitFiberUnmount = null;
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {}
+  };
+}
+function injectInternals(internals) {
+  if ("undefined" === typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) return !1;
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled || !hook.supportsFiber) return !0;
+  try {
+    var rendererID = hook.inject(internals);
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {}
+  return !0;
+}
+function onCommitRoot(root) {
+  "function" === typeof onCommitFiberRoot && onCommitFiberRoot(root);
+}
+function onCommitUnmount(fiber) {
+  "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
+}
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
+    }
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress["return"];
+  } while (workInProgress);
+  return info;
+}
+new Set();
+function createUpdateQueue(baseState) {
+  return {
+    baseState: baseState,
+    expirationTime: 0,
+    first: null,
+    last: null,
+    callbackList: null,
+    hasForceUpdate: !1,
+    isInitialized: !1,
+    capturedValues: null
+  };
+}
+function insertUpdateIntoQueue(queue, update) {
+  null === queue.last
+    ? (queue.first = queue.last = update)
+    : ((queue.last.next = update), (queue.last = update));
+  if (
+    0 === queue.expirationTime ||
+    queue.expirationTime > update.expirationTime
+  )
+    queue.expirationTime = update.expirationTime;
+}
+var q1 = void 0,
+  q2 = void 0;
+function ensureUpdateQueues(fiber) {
+  q1 = q2 = null;
+  var alternateFiber = fiber.alternate,
+    queue1 = fiber.updateQueue;
+  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
+  null !== alternateFiber
+    ? ((fiber = alternateFiber.updateQueue),
+      null === fiber &&
+        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
+    : (fiber = null);
+  q1 = queue1;
+  q2 = fiber !== queue1 ? fiber : null;
+}
+function insertUpdateIntoFiber(fiber, update) {
+  ensureUpdateQueues(fiber);
+  fiber = q1;
+  var queue2 = q2;
+  null === queue2
+    ? insertUpdateIntoQueue(fiber, update)
+    : null === fiber.last || null === queue2.last
+      ? (insertUpdateIntoQueue(fiber, update),
+        insertUpdateIntoQueue(queue2, update))
+      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
+}
+function getStateFromUpdate(update, instance, prevState, props) {
+  update = update.partialState;
+  return "function" === typeof update
+    ? update.call(instance, prevState, props)
+    : update;
+}
+function processUpdateQueue(
+  current,
+  workInProgress,
+  queue,
+  instance,
+  props,
+  renderExpirationTime
+) {
+  null !== current &&
+    current.updateQueue === queue &&
+    (queue = workInProgress.updateQueue = {
+      baseState: queue.baseState,
+      expirationTime: queue.expirationTime,
+      first: queue.first,
+      last: queue.last,
+      isInitialized: queue.isInitialized,
+      capturedValues: queue.capturedValues,
+      callbackList: null,
+      hasForceUpdate: !1
+    });
+  queue.expirationTime = 0;
+  queue.isInitialized
+    ? (current = queue.baseState)
+    : ((current = queue.baseState = workInProgress.memoizedState),
+      (queue.isInitialized = !0));
+  for (
+    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
+    null !== update;
+
+  ) {
+    var updateExpirationTime = update.expirationTime;
+    if (updateExpirationTime > renderExpirationTime) {
+      var remainingExpirationTime = queue.expirationTime;
+      if (
+        0 === remainingExpirationTime ||
+        remainingExpirationTime > updateExpirationTime
+      )
+        queue.expirationTime = updateExpirationTime;
+      didSkip || ((didSkip = !0), (queue.baseState = current));
+    } else {
+      didSkip ||
+        ((queue.first = update.next),
+        null === queue.first && (queue.last = null));
+      if (update.isReplace)
+        (current = getStateFromUpdate(update, instance, current, props)),
+          (dontMutatePrevState = !0);
+      else if (
+        (updateExpirationTime = getStateFromUpdate(
+          update,
+          instance,
+          current,
+          props
+        ))
+      )
+        (current = dontMutatePrevState
+          ? Object.assign({}, current, updateExpirationTime)
+          : Object.assign(current, updateExpirationTime)),
+          (dontMutatePrevState = !1);
+      update.isForced && (queue.hasForceUpdate = !0);
+      null !== update.callback &&
+        ((updateExpirationTime = queue.callbackList),
+        null === updateExpirationTime &&
+          (updateExpirationTime = queue.callbackList = []),
+        updateExpirationTime.push(update));
+      null !== update.capturedValue &&
+        ((updateExpirationTime = queue.capturedValues),
+        null === updateExpirationTime
+          ? (queue.capturedValues = [update.capturedValue])
+          : updateExpirationTime.push(update.capturedValue));
+    }
+    update = update.next;
+  }
+  null !== queue.callbackList
+    ? (workInProgress.effectTag |= 32)
+    : null !== queue.first ||
+      queue.hasForceUpdate ||
+      null !== queue.capturedValues ||
+      (workInProgress.updateQueue = null);
+  didSkip || (queue.baseState = current);
+  return current;
+}
+function commitCallbacks(queue, context) {
+  var callbackList = queue.callbackList;
+  if (null !== callbackList)
+    for (
+      queue.callbackList = null, queue = 0;
+      queue < callbackList.length;
+      queue++
+    ) {
+      var update = callbackList[queue],
+        _callback = update.callback;
+      update.callback = null;
+      invariant(
+        "function" === typeof _callback,
+        "Invalid argument passed as callback. Expected a function. Instead received: %s",
+        _callback
+      );
+      _callback.call(context);
+    }
+}
+function ReactFiberClassComponent(
+  legacyContext,
+  scheduleWork,
+  computeExpirationForFiber,
+  memoizeProps,
+  memoizeState
+) {
+  function checkShouldComponentUpdate(
+    workInProgress,
+    oldProps,
+    newProps,
+    oldState,
+    newState,
+    newContext
+  ) {
+    if (
+      null === oldProps ||
+      (null !== workInProgress.updateQueue &&
+        workInProgress.updateQueue.hasForceUpdate)
+    )
+      return !0;
+    var instance = workInProgress.stateNode;
+    workInProgress = workInProgress.type;
+    return "function" === typeof instance.shouldComponentUpdate
+      ? instance.shouldComponentUpdate(newProps, newState, newContext)
+      : workInProgress.prototype &&
+        workInProgress.prototype.isPureReactComponent
+        ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+        : !0;
+  }
+  function adoptClassInstance(workInProgress, instance) {
+    instance.updater = updater;
+    workInProgress.stateNode = instance;
+    instance._reactInternalFiber = workInProgress;
+  }
+  function callComponentWillReceiveProps(
+    workInProgress,
+    instance,
+    newProps,
+    newContext
+  ) {
+    workInProgress = instance.state;
+    "function" === typeof instance.componentWillReceiveProps &&
+      instance.componentWillReceiveProps(newProps, newContext);
+    "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
+      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+    instance.state !== workInProgress &&
+      updater.enqueueReplaceState(instance, instance.state, null);
+  }
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    workInProgress = workInProgress.type;
+    if ("function" === typeof workInProgress.getDerivedStateFromProps)
+      return workInProgress.getDerivedStateFromProps.call(
+        null,
+        nextProps,
+        prevState
+      );
+  }
+  var cacheContext = legacyContext.cacheContext,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    isContextConsumer = legacyContext.isContextConsumer,
+    hasContextChanged = legacyContext.hasContextChanged,
+    updater = {
+      isMounted: isMounted,
+      enqueueSetState: function(instance, partialState, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: partialState,
+          callback: callback,
+          isReplace: !1,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      },
+      enqueueReplaceState: function(instance, state, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: state,
+          callback: callback,
+          isReplace: !0,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      },
+      enqueueForceUpdate: function(instance, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: null,
+          callback: callback,
+          isReplace: !1,
+          isForced: !0,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      }
+    };
+  return {
+    adoptClassInstance: adoptClassInstance,
+    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
+    constructClassInstance: function(workInProgress, props) {
+      var ctor = workInProgress.type,
+        unmaskedContext = getUnmaskedContext(workInProgress),
+        needsContext = isContextConsumer(workInProgress),
+        context = needsContext
+          ? getMaskedContext(workInProgress, unmaskedContext)
+          : emptyObject;
+      ctor = new ctor(props, context);
+      var state =
+        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
+      adoptClassInstance(workInProgress, ctor);
+      workInProgress.memoizedState = state;
+      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
+      null !== props &&
+        void 0 !== props &&
+        (workInProgress.memoizedState = Object.assign(
+          {},
+          workInProgress.memoizedState,
+          props
+        ));
+      needsContext && cacheContext(workInProgress, unmaskedContext, context);
+      return ctor;
+    },
+    mountClassInstance: function(workInProgress, renderExpirationTime) {
+      var ctor = workInProgress.type,
+        current = workInProgress.alternate,
+        instance = workInProgress.stateNode,
+        props = workInProgress.pendingProps,
+        unmaskedContext = getUnmaskedContext(workInProgress);
+      instance.props = props;
+      instance.state = workInProgress.memoizedState;
+      instance.refs = emptyObject;
+      instance.context = getMaskedContext(workInProgress, unmaskedContext);
+      "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate ||
+        ("function" !== typeof instance.UNSAFE_componentWillMount &&
+          "function" !== typeof instance.componentWillMount) ||
+        ((ctor = instance.state),
+        "function" === typeof instance.componentWillMount &&
+          instance.componentWillMount(),
+        "function" === typeof instance.UNSAFE_componentWillMount &&
+          instance.UNSAFE_componentWillMount(),
+        ctor !== instance.state &&
+          updater.enqueueReplaceState(instance, instance.state, null),
+        (ctor = workInProgress.updateQueue),
+        null !== ctor &&
+          (instance.state = processUpdateQueue(
+            current,
+            workInProgress,
+            ctor,
+            instance,
+            props,
+            renderExpirationTime
+          )));
+      "function" === typeof instance.componentDidMount &&
+        (workInProgress.effectTag |= 4);
+    },
+    resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
+      var ctor = workInProgress.type,
+        instance = workInProgress.stateNode;
+      instance.props = workInProgress.memoizedProps;
+      instance.state = workInProgress.memoizedState;
+      var oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps,
+        oldContext = instance.context,
+        newUnmaskedContext = getUnmaskedContext(workInProgress);
+      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      (ctor =
+        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate) ||
+        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
+          "function" !== typeof instance.componentWillReceiveProps) ||
+        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
+          callComponentWillReceiveProps(
+            workInProgress,
+            instance,
+            newProps,
+            newUnmaskedContext
+          ));
+      oldContext = workInProgress.memoizedState;
+      renderExpirationTime =
+        null !== workInProgress.updateQueue
+          ? processUpdateQueue(
+              null,
+              workInProgress,
+              workInProgress.updateQueue,
+              instance,
+              newProps,
+              renderExpirationTime
+            )
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
+          workInProgress,
+          instance,
+          newProps,
+          renderExpirationTime
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
+          null === renderExpirationTime || void 0 === renderExpirationTime
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue = workInProgress.updateQueue;
+        null !== _updateQueue &&
+          (_updateQueue.baseState = Object.assign(
+            {},
+            _updateQueue.baseState,
+            derivedStateFromProps
+          ));
+      }
+      if (
+        !(
+          oldProps !== newProps ||
+          oldContext !== renderExpirationTime ||
+          hasContextChanged() ||
+          (null !== workInProgress.updateQueue &&
+            workInProgress.updateQueue.hasForceUpdate)
+        )
+      )
+        return (
+          "function" === typeof instance.componentDidMount &&
+            (workInProgress.effectTag |= 4),
+          !1
+        );
+      (oldProps = checkShouldComponentUpdate(
+        workInProgress,
+        oldProps,
+        newProps,
+        oldContext,
+        renderExpirationTime,
+        newUnmaskedContext
+      ))
+        ? (ctor ||
+            ("function" !== typeof instance.UNSAFE_componentWillMount &&
+              "function" !== typeof instance.componentWillMount) ||
+            ("function" === typeof instance.componentWillMount &&
+              instance.componentWillMount(),
+            "function" === typeof instance.UNSAFE_componentWillMount &&
+              instance.UNSAFE_componentWillMount()),
+          "function" === typeof instance.componentDidMount &&
+            (workInProgress.effectTag |= 4))
+        : ("function" === typeof instance.componentDidMount &&
+            (workInProgress.effectTag |= 4),
+          memoizeProps(workInProgress, newProps),
+          memoizeState(workInProgress, renderExpirationTime));
+      instance.props = newProps;
+      instance.state = renderExpirationTime;
+      instance.context = newUnmaskedContext;
+      return oldProps;
+    },
+    updateClassInstance: function(
+      current,
+      workInProgress,
+      renderExpirationTime
+    ) {
+      var ctor = workInProgress.type,
+        instance = workInProgress.stateNode;
+      instance.props = workInProgress.memoizedProps;
+      instance.state = workInProgress.memoizedState;
+      var oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps,
+        oldContext = instance.context,
+        newUnmaskedContext = getUnmaskedContext(workInProgress);
+      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      (ctor =
+        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate) ||
+        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
+          "function" !== typeof instance.componentWillReceiveProps) ||
+        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
+          callComponentWillReceiveProps(
+            workInProgress,
+            instance,
+            newProps,
+            newUnmaskedContext
+          ));
+      oldContext = workInProgress.memoizedState;
+      renderExpirationTime =
+        null !== workInProgress.updateQueue
+          ? processUpdateQueue(
+              current,
+              workInProgress,
+              workInProgress.updateQueue,
+              instance,
+              newProps,
+              renderExpirationTime
+            )
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
+          workInProgress,
+          instance,
+          newProps,
+          renderExpirationTime
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
+          null === renderExpirationTime || void 0 === renderExpirationTime
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue3 = workInProgress.updateQueue;
+        null !== _updateQueue3 &&
+          (_updateQueue3.baseState = Object.assign(
+            {},
+            _updateQueue3.baseState,
+            derivedStateFromProps
+          ));
+      }
+      if (
+        !(
+          oldProps !== newProps ||
+          oldContext !== renderExpirationTime ||
+          hasContextChanged() ||
+          (null !== workInProgress.updateQueue &&
+            workInProgress.updateQueue.hasForceUpdate)
+        )
+      )
+        return (
+          "function" !== typeof instance.componentDidUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 4),
+          "function" !== typeof instance.getSnapshotBeforeUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 2048),
+          !1
+        );
+      (derivedStateFromProps = checkShouldComponentUpdate(
+        workInProgress,
+        oldProps,
+        newProps,
+        oldContext,
+        renderExpirationTime,
+        newUnmaskedContext
+      ))
+        ? (ctor ||
+            ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
+              "function" !== typeof instance.componentWillUpdate) ||
+            ("function" === typeof instance.componentWillUpdate &&
+              instance.componentWillUpdate(
+                newProps,
+                renderExpirationTime,
+                newUnmaskedContext
+              ),
+            "function" === typeof instance.UNSAFE_componentWillUpdate &&
+              instance.UNSAFE_componentWillUpdate(
+                newProps,
+                renderExpirationTime,
+                newUnmaskedContext
+              )),
+          "function" === typeof instance.componentDidUpdate &&
+            (workInProgress.effectTag |= 4),
+          "function" === typeof instance.getSnapshotBeforeUpdate &&
+            (workInProgress.effectTag |= 2048))
+        : ("function" !== typeof instance.componentDidUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 4),
+          "function" !== typeof instance.getSnapshotBeforeUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 2048),
+          memoizeProps(workInProgress, newProps),
+          memoizeState(workInProgress, renderExpirationTime));
+      instance.props = newProps;
+      instance.state = renderExpirationTime;
+      instance.context = newUnmaskedContext;
+      return derivedStateFromProps;
+    }
+  };
+}
+var isArray$1 = Array.isArray;
+function coerceRef(returnFiber, current, element) {
+  returnFiber = element.ref;
+  if (
+    null !== returnFiber &&
+    "function" !== typeof returnFiber &&
+    "object" !== typeof returnFiber
+  ) {
+    if (element._owner) {
+      element = element._owner;
+      var inst = void 0;
+      element &&
+        (invariant(
+          2 === element.tag,
+          "Stateless function components cannot have refs."
+        ),
+        (inst = element.stateNode));
+      invariant(
+        inst,
+        "Missing owner for string ref %s. This error is likely caused by a bug in React. Please file an issue.",
+        returnFiber
+      );
+      var stringRef = "" + returnFiber;
+      if (
+        null !== current &&
+        null !== current.ref &&
+        current.ref._stringRef === stringRef
+      )
+        return current.ref;
+      current = function(value) {
+        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
+        null === value ? delete refs[stringRef] : (refs[stringRef] = value);
+      };
+      current._stringRef = stringRef;
+      return current;
+    }
+    invariant(
+      "string" === typeof returnFiber,
+      "Expected ref to be a function or a string."
+    );
+    invariant(
+      element._owner,
+      "Element ref was specified as a string (%s) but no owner was set. This could happen for one of the following reasons:\n1. You may be adding a ref to a functional component\n2. You may be adding a ref to a component that was not created inside a component's render method\n3. You have multiple copies of React loaded\nSee https://fb.me/react-refs-must-have-owner for more information.",
+      returnFiber
+    );
+  }
+  return returnFiber;
+}
+function throwOnInvalidObjectType(returnFiber, newChild) {
+  "textarea" !== returnFiber.type &&
+    invariant(
+      !1,
+      "Objects are not valid as a React child (found: %s).%s",
+      "[object Object]" === Object.prototype.toString.call(newChild)
+        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
+        : newChild,
+      ""
+    );
+}
+function ChildReconciler(shouldTrackSideEffects) {
+  function deleteChild(returnFiber, childToDelete) {
+    if (shouldTrackSideEffects) {
+      var last = returnFiber.lastEffect;
+      null !== last
+        ? ((last.nextEffect = childToDelete),
+          (returnFiber.lastEffect = childToDelete))
+        : (returnFiber.firstEffect = returnFiber.lastEffect = childToDelete);
+      childToDelete.nextEffect = null;
+      childToDelete.effectTag = 8;
+    }
+  }
+  function deleteRemainingChildren(returnFiber, currentFirstChild) {
+    if (!shouldTrackSideEffects) return null;
+    for (; null !== currentFirstChild; )
+      deleteChild(returnFiber, currentFirstChild),
+        (currentFirstChild = currentFirstChild.sibling);
+    return null;
+  }
+  function mapRemainingChildren(returnFiber, currentFirstChild) {
+    for (returnFiber = new Map(); null !== currentFirstChild; )
+      null !== currentFirstChild.key
+        ? returnFiber.set(currentFirstChild.key, currentFirstChild)
+        : returnFiber.set(currentFirstChild.index, currentFirstChild),
+        (currentFirstChild = currentFirstChild.sibling);
+    return returnFiber;
+  }
+  function useFiber(fiber, pendingProps, expirationTime) {
+    fiber = createWorkInProgress(fiber, pendingProps, expirationTime);
+    fiber.index = 0;
+    fiber.sibling = null;
+    return fiber;
+  }
+  function placeChild(newFiber, lastPlacedIndex, newIndex) {
+    newFiber.index = newIndex;
+    if (!shouldTrackSideEffects) return lastPlacedIndex;
+    newIndex = newFiber.alternate;
+    if (null !== newIndex)
+      return (
+        (newIndex = newIndex.index),
+        newIndex < lastPlacedIndex
+          ? ((newFiber.effectTag = 2), lastPlacedIndex)
+          : newIndex
+      );
+    newFiber.effectTag = 2;
+    return lastPlacedIndex;
+  }
+  function placeSingleChild(newFiber) {
+    shouldTrackSideEffects &&
+      null === newFiber.alternate &&
+      (newFiber.effectTag = 2);
+    return newFiber;
+  }
+  function updateTextNode(returnFiber, current, textContent, expirationTime) {
+    if (null === current || 6 !== current.tag)
+      return (
+        (current = createFiberFromText(
+          textContent,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (current["return"] = returnFiber),
+        current
+      );
+    current = useFiber(current, textContent, expirationTime);
+    current["return"] = returnFiber;
+    return current;
+  }
+  function updateElement(returnFiber, current, element, expirationTime) {
+    if (null !== current && current.type === element.type)
+      return (
+        (expirationTime = useFiber(current, element.props, expirationTime)),
+        (expirationTime.ref = coerceRef(returnFiber, current, element)),
+        (expirationTime["return"] = returnFiber),
+        expirationTime
+      );
+    expirationTime = createFiberFromElement(
+      element,
+      returnFiber.mode,
+      expirationTime
+    );
+    expirationTime.ref = coerceRef(returnFiber, current, element);
+    expirationTime["return"] = returnFiber;
+    return expirationTime;
+  }
+  function updatePortal(returnFiber, current, portal, expirationTime) {
+    if (
+      null === current ||
+      4 !== current.tag ||
+      current.stateNode.containerInfo !== portal.containerInfo ||
+      current.stateNode.implementation !== portal.implementation
+    )
+      return (
+        (current = createFiberFromPortal(
+          portal,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (current["return"] = returnFiber),
+        current
+      );
+    current = useFiber(current, portal.children || [], expirationTime);
+    current["return"] = returnFiber;
+    return current;
+  }
+  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
+    if (null === current || 10 !== current.tag)
+      return (
+        (current = createFiberFromFragment(
+          fragment,
+          returnFiber.mode,
+          expirationTime,
+          key
+        )),
+        (current["return"] = returnFiber),
+        current
+      );
+    current = useFiber(current, fragment, expirationTime);
+    current["return"] = returnFiber;
+    return current;
+  }
+  function createChild(returnFiber, newChild, expirationTime) {
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (newChild = createFiberFromText(
+          "" + newChild,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (newChild["return"] = returnFiber),
+        newChild
+      );
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return (
+            (expirationTime = createFiberFromElement(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
+            (expirationTime["return"] = returnFiber),
+            expirationTime
+          );
+        case REACT_PORTAL_TYPE:
+          return (
+            (newChild = createFiberFromPortal(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (newChild["return"] = returnFiber),
+            newChild
+          );
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return (
+          (newChild = createFiberFromFragment(
+            newChild,
+            returnFiber.mode,
+            expirationTime,
+            null
+          )),
+          (newChild["return"] = returnFiber),
+          newChild
+        );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
+    var key = null !== oldFiber ? oldFiber.key : null;
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return null !== key
+        ? null
+        : updateTextNode(returnFiber, oldFiber, "" + newChild, expirationTime);
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return newChild.key === key
+            ? newChild.type === REACT_FRAGMENT_TYPE
+              ? updateFragment(
+                  returnFiber,
+                  oldFiber,
+                  newChild.props.children,
+                  expirationTime,
+                  key
+                )
+              : updateElement(returnFiber, oldFiber, newChild, expirationTime)
+            : null;
+        case REACT_PORTAL_TYPE:
+          return newChild.key === key
+            ? updatePortal(returnFiber, oldFiber, newChild, expirationTime)
+            : null;
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return null !== key
+          ? null
+          : updateFragment(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime,
+              null
+            );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function updateFromMap(
+    existingChildren,
+    returnFiber,
+    newIdx,
+    newChild,
+    expirationTime
+  ) {
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (existingChildren = existingChildren.get(newIdx) || null),
+        updateTextNode(
+          returnFiber,
+          existingChildren,
+          "" + newChild,
+          expirationTime
+        )
+      );
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return (
+            (existingChildren =
+              existingChildren.get(
+                null === newChild.key ? newIdx : newChild.key
+              ) || null),
+            newChild.type === REACT_FRAGMENT_TYPE
+              ? updateFragment(
+                  returnFiber,
+                  existingChildren,
+                  newChild.props.children,
+                  expirationTime,
+                  newChild.key
+                )
+              : updateElement(
+                  returnFiber,
+                  existingChildren,
+                  newChild,
+                  expirationTime
+                )
+          );
+        case REACT_PORTAL_TYPE:
+          return (
+            (existingChildren =
+              existingChildren.get(
+                null === newChild.key ? newIdx : newChild.key
+              ) || null),
+            updatePortal(
+              returnFiber,
+              existingChildren,
+              newChild,
+              expirationTime
+            )
+          );
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return (
+          (existingChildren = existingChildren.get(newIdx) || null),
+          updateFragment(
+            returnFiber,
+            existingChildren,
+            newChild,
+            expirationTime,
+            null
+          )
+        );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function reconcileChildrenArray(
+    returnFiber,
+    currentFirstChild,
+    newChildren,
+    expirationTime
+  ) {
+    for (
+      var resultingFirstChild = null,
+        previousNewFiber = null,
+        oldFiber = currentFirstChild,
+        newIdx = (currentFirstChild = 0),
+        nextOldFiber = null;
+      null !== oldFiber && newIdx < newChildren.length;
+      newIdx++
+    ) {
+      oldFiber.index > newIdx
+        ? ((nextOldFiber = oldFiber), (oldFiber = null))
+        : (nextOldFiber = oldFiber.sibling);
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (null === newFiber) {
+        null === oldFiber && (oldFiber = nextOldFiber);
+        break;
+      }
+      shouldTrackSideEffects &&
+        oldFiber &&
+        null === newFiber.alternate &&
+        deleteChild(returnFiber, oldFiber);
+      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
+      null === previousNewFiber
+        ? (resultingFirstChild = newFiber)
+        : (previousNewFiber.sibling = newFiber);
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+    if (newIdx === newChildren.length)
+      return (
+        deleteRemainingChildren(returnFiber, oldFiber), resultingFirstChild
+      );
+    if (null === oldFiber) {
+      for (; newIdx < newChildren.length; newIdx++)
+        if (
+          (oldFiber = createChild(
+            returnFiber,
+            newChildren[newIdx],
+            expirationTime
+          ))
+        )
+          (currentFirstChild = placeChild(oldFiber, currentFirstChild, newIdx)),
+            null === previousNewFiber
+              ? (resultingFirstChild = oldFiber)
+              : (previousNewFiber.sibling = oldFiber),
+            (previousNewFiber = oldFiber);
+      return resultingFirstChild;
+    }
+    for (
+      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
+      newIdx < newChildren.length;
+      newIdx++
+    )
+      if (
+        (nextOldFiber = updateFromMap(
+          oldFiber,
+          returnFiber,
+          newIdx,
+          newChildren[newIdx],
+          expirationTime
+        ))
+      ) {
+        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
+          oldFiber["delete"](
+            null === nextOldFiber.key ? newIdx : nextOldFiber.key
+          );
+        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
+        null === previousNewFiber
+          ? (resultingFirstChild = nextOldFiber)
+          : (previousNewFiber.sibling = nextOldFiber);
+        previousNewFiber = nextOldFiber;
+      }
+    shouldTrackSideEffects &&
+      oldFiber.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    return resultingFirstChild;
+  }
+  function reconcileChildrenIterator(
+    returnFiber,
+    currentFirstChild,
+    newChildrenIterable,
+    expirationTime
+  ) {
+    var iteratorFn = getIteratorFn(newChildrenIterable);
+    invariant(
+      "function" === typeof iteratorFn,
+      "An object is not an iterable. This error is likely caused by a bug in React. Please file an issue."
+    );
+    newChildrenIterable = iteratorFn.call(newChildrenIterable);
+    invariant(
+      null != newChildrenIterable,
+      "An iterable object provided no iterator."
+    );
+    for (
+      var previousNewFiber = (iteratorFn = null),
+        oldFiber = currentFirstChild,
+        newIdx = (currentFirstChild = 0),
+        nextOldFiber = null,
+        step = newChildrenIterable.next();
+      null !== oldFiber && !step.done;
+      newIdx++, step = newChildrenIterable.next()
+    ) {
+      oldFiber.index > newIdx
+        ? ((nextOldFiber = oldFiber), (oldFiber = null))
+        : (nextOldFiber = oldFiber.sibling);
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        step.value,
+        expirationTime
+      );
+      if (null === newFiber) {
+        oldFiber || (oldFiber = nextOldFiber);
+        break;
+      }
+      shouldTrackSideEffects &&
+        oldFiber &&
+        null === newFiber.alternate &&
+        deleteChild(returnFiber, oldFiber);
+      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
+      null === previousNewFiber
+        ? (iteratorFn = newFiber)
+        : (previousNewFiber.sibling = newFiber);
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+    if (step.done)
+      return deleteRemainingChildren(returnFiber, oldFiber), iteratorFn;
+    if (null === oldFiber) {
+      for (; !step.done; newIdx++, step = newChildrenIterable.next())
+        (step = createChild(returnFiber, step.value, expirationTime)),
+          null !== step &&
+            ((currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+            null === previousNewFiber
+              ? (iteratorFn = step)
+              : (previousNewFiber.sibling = step),
+            (previousNewFiber = step));
+      return iteratorFn;
+    }
+    for (
+      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
+      !step.done;
+      newIdx++, step = newChildrenIterable.next()
+    )
+      if (
+        ((step = updateFromMap(
+          oldFiber,
+          returnFiber,
+          newIdx,
+          step.value,
+          expirationTime
+        )),
+        null !== step)
+      ) {
+        if (shouldTrackSideEffects && null !== step.alternate)
+          oldFiber["delete"](null === step.key ? newIdx : step.key);
+        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
+        null === previousNewFiber
+          ? (iteratorFn = step)
+          : (previousNewFiber.sibling = step);
+        previousNewFiber = step;
+      }
+    shouldTrackSideEffects &&
+      oldFiber.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    return iteratorFn;
+  }
+  return function(returnFiber, currentFirstChild, newChild, expirationTime) {
+    "object" === typeof newChild &&
+      null !== newChild &&
+      newChild.type === REACT_FRAGMENT_TYPE &&
+      null === newChild.key &&
+      (newChild = newChild.props.children);
+    var isObject = "object" === typeof newChild && null !== newChild;
+    if (isObject)
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          a: {
+            var key = newChild.key;
+            for (isObject = currentFirstChild; null !== isObject; ) {
+              if (isObject.key === key)
+                if (
+                  10 === isObject.tag
+                    ? newChild.type === REACT_FRAGMENT_TYPE
+                    : isObject.type === newChild.type
+                ) {
+                  deleteRemainingChildren(returnFiber, isObject.sibling);
+                  currentFirstChild = useFiber(
+                    isObject,
+                    newChild.type === REACT_FRAGMENT_TYPE
+                      ? newChild.props.children
+                      : newChild.props,
+                    expirationTime
+                  );
+                  currentFirstChild.ref = coerceRef(
+                    returnFiber,
+                    isObject,
+                    newChild
+                  );
+                  currentFirstChild["return"] = returnFiber;
+                  returnFiber = currentFirstChild;
+                  break a;
+                } else {
+                  deleteRemainingChildren(returnFiber, isObject);
+                  break;
+                }
+              else deleteChild(returnFiber, isObject);
+              isObject = isObject.sibling;
+            }
+            newChild.type === REACT_FRAGMENT_TYPE
+              ? ((currentFirstChild = createFiberFromFragment(
+                  newChild.props.children,
+                  returnFiber.mode,
+                  expirationTime,
+                  newChild.key
+                )),
+                (currentFirstChild["return"] = returnFiber),
+                (returnFiber = currentFirstChild))
+              : ((expirationTime = createFiberFromElement(
+                  newChild,
+                  returnFiber.mode,
+                  expirationTime
+                )),
+                (expirationTime.ref = coerceRef(
+                  returnFiber,
+                  currentFirstChild,
+                  newChild
+                )),
+                (expirationTime["return"] = returnFiber),
+                (returnFiber = expirationTime));
+          }
+          return placeSingleChild(returnFiber);
+        case REACT_PORTAL_TYPE:
+          a: {
+            for (isObject = newChild.key; null !== currentFirstChild; ) {
+              if (currentFirstChild.key === isObject)
+                if (
+                  4 === currentFirstChild.tag &&
+                  currentFirstChild.stateNode.containerInfo ===
+                    newChild.containerInfo &&
+                  currentFirstChild.stateNode.implementation ===
+                    newChild.implementation
+                ) {
+                  deleteRemainingChildren(
+                    returnFiber,
+                    currentFirstChild.sibling
+                  );
+                  currentFirstChild = useFiber(
+                    currentFirstChild,
+                    newChild.children || [],
+                    expirationTime
+                  );
+                  currentFirstChild["return"] = returnFiber;
+                  returnFiber = currentFirstChild;
+                  break a;
+                } else {
+                  deleteRemainingChildren(returnFiber, currentFirstChild);
+                  break;
+                }
+              else deleteChild(returnFiber, currentFirstChild);
+              currentFirstChild = currentFirstChild.sibling;
+            }
+            currentFirstChild = createFiberFromPortal(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            );
+            currentFirstChild["return"] = returnFiber;
+            returnFiber = currentFirstChild;
+          }
+          return placeSingleChild(returnFiber);
+      }
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (newChild = "" + newChild),
+        null !== currentFirstChild && 6 === currentFirstChild.tag
+          ? (deleteRemainingChildren(returnFiber, currentFirstChild.sibling),
+            (currentFirstChild = useFiber(
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )),
+            (currentFirstChild["return"] = returnFiber),
+            (returnFiber = currentFirstChild))
+          : (deleteRemainingChildren(returnFiber, currentFirstChild),
+            (currentFirstChild = createFiberFromText(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (currentFirstChild["return"] = returnFiber),
+            (returnFiber = currentFirstChild)),
+        placeSingleChild(returnFiber)
+      );
+    if (isArray$1(newChild))
+      return reconcileChildrenArray(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    if (getIteratorFn(newChild))
+      return reconcileChildrenIterator(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    isObject && throwOnInvalidObjectType(returnFiber, newChild);
+    if ("undefined" === typeof newChild)
+      switch (returnFiber.tag) {
+        case 2:
+        case 1:
+          (expirationTime = returnFiber.type),
+            invariant(
+              !1,
+              "%s(...): Nothing was returned from render. This usually means a return statement is missing. Or, to render nothing, return null.",
+              expirationTime.displayName || expirationTime.name || "Component"
+            );
+      }
+    return deleteRemainingChildren(returnFiber, currentFirstChild);
+  };
+}
+var reconcileChildFibers = ChildReconciler(!0),
+  mountChildFibers = ChildReconciler(!1);
+function ReactFiberBeginWork(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext,
+  scheduleWork,
+  computeExpirationForFiber
+) {
+  function reconcileChildren(current, workInProgress, nextChildren) {
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      nextChildren,
+      workInProgress.expirationTime
+    );
+  }
+  function reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    renderExpirationTime
+  ) {
+    workInProgress.child =
+      null === current
+        ? mountChildFibers(
+            workInProgress,
+            null,
+            nextChildren,
+            renderExpirationTime
+          )
+        : reconcileChildFibers(
+            workInProgress,
+            current.child,
+            nextChildren,
+            renderExpirationTime
+          );
+  }
+  function markRef(current, workInProgress) {
+    var ref = workInProgress.ref;
+    if (
+      (null === current && null !== ref) ||
+      (null !== current && current.ref !== ref)
+    )
+      workInProgress.effectTag |= 128;
+  }
+  function finishClassComponent(
+    current,
+    workInProgress,
+    shouldUpdate,
+    hasContext,
+    didCaptureError,
+    renderExpirationTime
+  ) {
+    markRef(current, workInProgress);
+    if (!shouldUpdate && !didCaptureError)
+      return (
+        hasContext && invalidateContextProvider(workInProgress, !1),
+        bailoutOnAlreadyFinishedWork(current, workInProgress)
+      );
+    shouldUpdate = workInProgress.stateNode;
+    ReactCurrentOwner.current = workInProgress;
+    var nextChildren = didCaptureError ? null : shouldUpdate.render();
+    workInProgress.effectTag |= 1;
+    didCaptureError &&
+      (reconcileChildrenAtExpirationTime(
+        current,
+        workInProgress,
+        null,
+        renderExpirationTime
+      ),
+      (workInProgress.child = null));
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      nextChildren,
+      renderExpirationTime
+    );
+    workInProgress.memoizedState = shouldUpdate.state;
+    workInProgress.memoizedProps = shouldUpdate.props;
+    hasContext && invalidateContextProvider(workInProgress, !0);
+    return workInProgress.child;
+  }
+  function pushHostRootContext(workInProgress) {
+    var root = workInProgress.stateNode;
+    root.pendingContext
+      ? pushTopLevelContextObject(
+          workInProgress,
+          root.pendingContext,
+          root.pendingContext !== root.context
+        )
+      : root.context &&
+        pushTopLevelContextObject(workInProgress, root.context, !1);
+    pushHostContainer(workInProgress, root.containerInfo);
+  }
+  function propagateContextChange(
+    workInProgress,
+    context,
+    changedBits,
+    renderExpirationTime
+  ) {
+    var fiber = workInProgress.child;
+    for (
+      null !== fiber && (fiber["return"] = workInProgress);
+      null !== fiber;
+
+    ) {
+      switch (fiber.tag) {
+        case 12:
+          var nextFiber = fiber.stateNode | 0;
+          if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
+            for (nextFiber = fiber; null !== nextFiber; ) {
+              var alternate = nextFiber.alternate;
+              if (
+                0 === nextFiber.expirationTime ||
+                nextFiber.expirationTime > renderExpirationTime
+              )
+                (nextFiber.expirationTime = renderExpirationTime),
+                  null !== alternate &&
+                    (0 === alternate.expirationTime ||
+                      alternate.expirationTime > renderExpirationTime) &&
+                    (alternate.expirationTime = renderExpirationTime);
+              else if (
+                null !== alternate &&
+                (0 === alternate.expirationTime ||
+                  alternate.expirationTime > renderExpirationTime)
+              )
+                alternate.expirationTime = renderExpirationTime;
+              else break;
+              nextFiber = nextFiber["return"];
+            }
+            nextFiber = null;
+          } else nextFiber = fiber.child;
+          break;
+        case 13:
+          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+          break;
+        default:
+          nextFiber = fiber.child;
+      }
+      if (null !== nextFiber) nextFiber["return"] = fiber;
+      else
+        for (nextFiber = fiber; null !== nextFiber; ) {
+          if (nextFiber === workInProgress) {
+            nextFiber = null;
+            break;
+          }
+          fiber = nextFiber.sibling;
+          if (null !== fiber) {
+            nextFiber = fiber;
+            break;
+          }
+          nextFiber = nextFiber["return"];
+        }
+      fiber = nextFiber;
+    }
+  }
+  function updateContextProvider(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var context = workInProgress.type._context,
+      newProps = workInProgress.pendingProps,
+      oldProps = workInProgress.memoizedProps;
+    if (!hasLegacyContextChanged() && oldProps === newProps)
+      return (
+        (workInProgress.stateNode = 0),
+        pushProvider(workInProgress),
+        bailoutOnAlreadyFinishedWork(current, workInProgress)
+      );
+    var newValue = newProps.value;
+    workInProgress.memoizedProps = newProps;
+    if (null === oldProps) newValue = 1073741823;
+    else if (oldProps.value === newProps.value) {
+      if (oldProps.children === newProps.children)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+      newValue = 0;
+    } else {
+      var oldValue = oldProps.value;
+      if (
+        (oldValue === newValue &&
+          (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
+        (oldValue !== oldValue && newValue !== newValue)
+      ) {
+        if (oldProps.children === newProps.children)
+          return (
+            (workInProgress.stateNode = 0),
+            pushProvider(workInProgress),
+            bailoutOnAlreadyFinishedWork(current, workInProgress)
+          );
+        newValue = 0;
+      } else if (
+        ((newValue =
+          "function" === typeof context._calculateChangedBits
+            ? context._calculateChangedBits(oldValue, newValue)
+            : 1073741823),
+        (newValue |= 0),
+        0 === newValue)
+      ) {
+        if (oldProps.children === newProps.children)
+          return (
+            (workInProgress.stateNode = 0),
+            pushProvider(workInProgress),
+            bailoutOnAlreadyFinishedWork(current, workInProgress)
+          );
+      } else
+        propagateContextChange(
+          workInProgress,
+          context,
+          newValue,
+          renderExpirationTime
+        );
+    }
+    workInProgress.stateNode = newValue;
+    pushProvider(workInProgress);
+    reconcileChildren(current, workInProgress, newProps.children);
+    return workInProgress.child;
+  }
+  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+    invariant(
+      null === current || workInProgress.child === current.child,
+      "Resuming work not yet implemented."
+    );
+    if (null !== workInProgress.child) {
+      current = workInProgress.child;
+      var newChild = createWorkInProgress(
+        current,
+        current.pendingProps,
+        current.expirationTime
+      );
+      workInProgress.child = newChild;
+      for (newChild["return"] = workInProgress; null !== current.sibling; )
+        (current = current.sibling),
+          (newChild = newChild.sibling = createWorkInProgress(
+            current,
+            current.pendingProps,
+            current.expirationTime
+          )),
+          (newChild["return"] = workInProgress);
+      newChild.sibling = null;
+    }
+    return workInProgress.child;
+  }
+  var shouldSetTextContent = config.shouldSetTextContent,
+    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree,
+    pushHostContext = hostContext.pushHostContext,
+    pushHostContainer = hostContext.pushHostContainer,
+    pushProvider = newContext.pushProvider,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    hasLegacyContextChanged = legacyContext.hasContextChanged,
+    pushLegacyContextProvider = legacyContext.pushContextProvider,
+    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
+    invalidateContextProvider = legacyContext.invalidateContextProvider,
+    enterHydrationState = hydrationContext.enterHydrationState,
+    resetHydrationState = hydrationContext.resetHydrationState,
+    tryToClaimNextHydratableInstance =
+      hydrationContext.tryToClaimNextHydratableInstance;
+  config = ReactFiberClassComponent(
+    legacyContext,
+    scheduleWork,
+    computeExpirationForFiber,
+    function(workInProgress, nextProps) {
+      workInProgress.memoizedProps = nextProps;
+    },
+    function(workInProgress, nextState) {
+      workInProgress.memoizedState = nextState;
+    }
+  );
+  var adoptClassInstance = config.adoptClassInstance,
+    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
+    constructClassInstance = config.constructClassInstance,
+    mountClassInstance = config.mountClassInstance,
+    resumeMountClassInstance = config.resumeMountClassInstance,
+    updateClassInstance = config.updateClassInstance;
+  return {
+    beginWork: function(current, workInProgress, renderExpirationTime) {
+      if (
+        0 === workInProgress.expirationTime ||
+        workInProgress.expirationTime > renderExpirationTime
+      ) {
+        switch (workInProgress.tag) {
+          case 3:
+            pushHostRootContext(workInProgress);
+            break;
+          case 2:
+            pushLegacyContextProvider(workInProgress);
+            break;
+          case 4:
+            pushHostContainer(
+              workInProgress,
+              workInProgress.stateNode.containerInfo
+            );
+            break;
+          case 13:
+            pushProvider(workInProgress);
+        }
+        return null;
+      }
+      switch (workInProgress.tag) {
+        case 0:
+          invariant(
+            null === current,
+            "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
+          );
+          var fn = workInProgress.type,
+            props = workInProgress.pendingProps,
+            unmaskedContext = getUnmaskedContext(workInProgress);
+          unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
+          fn = fn(props, unmaskedContext);
+          workInProgress.effectTag |= 1;
+          "object" === typeof fn &&
+          null !== fn &&
+          "function" === typeof fn.render &&
+          void 0 === fn.$$typeof
+            ? ((unmaskedContext = workInProgress.type),
+              (workInProgress.tag = 2),
+              (workInProgress.memoizedState =
+                null !== fn.state && void 0 !== fn.state ? fn.state : null),
+              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
+                ((props = callGetDerivedStateFromProps(
+                  workInProgress,
+                  fn,
+                  props,
+                  workInProgress.memoizedState
+                )),
+                null !== props &&
+                  void 0 !== props &&
+                  (workInProgress.memoizedState = Object.assign(
+                    {},
+                    workInProgress.memoizedState,
+                    props
+                  ))),
+              (props = pushLegacyContextProvider(workInProgress)),
+              adoptClassInstance(workInProgress, fn),
+              mountClassInstance(workInProgress, renderExpirationTime),
+              (current = finishClassComponent(
+                current,
+                workInProgress,
+                !0,
+                props,
+                !1,
+                renderExpirationTime
+              )))
+            : ((workInProgress.tag = 1),
+              reconcileChildren(current, workInProgress, fn),
+              (workInProgress.memoizedProps = props),
+              (current = workInProgress.child));
+          return current;
+        case 1:
+          return (
+            (props = workInProgress.type),
+            (renderExpirationTime = workInProgress.pendingProps),
+            hasLegacyContextChanged() ||
+            workInProgress.memoizedProps !== renderExpirationTime
+              ? ((fn = getUnmaskedContext(workInProgress)),
+                (fn = getMaskedContext(workInProgress, fn)),
+                (props = props(renderExpirationTime, fn)),
+                (workInProgress.effectTag |= 1),
+                reconcileChildren(current, workInProgress, props),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
+        case 2:
+          props = pushLegacyContextProvider(workInProgress);
+          null === current
+            ? null === workInProgress.stateNode
+              ? (constructClassInstance(
+                  workInProgress,
+                  workInProgress.pendingProps
+                ),
+                mountClassInstance(workInProgress, renderExpirationTime),
+                (fn = !0))
+              : (fn = resumeMountClassInstance(
+                  workInProgress,
+                  renderExpirationTime
+                ))
+            : (fn = updateClassInstance(
+                current,
+                workInProgress,
+                renderExpirationTime
+              ));
+          unmaskedContext = !1;
+          var updateQueue = workInProgress.updateQueue;
+          null !== updateQueue &&
+            null !== updateQueue.capturedValues &&
+            (unmaskedContext = fn = !0);
+          return finishClassComponent(
+            current,
+            workInProgress,
+            fn,
+            props,
+            unmaskedContext,
+            renderExpirationTime
+          );
+        case 3:
+          a: if (
+            (pushHostRootContext(workInProgress),
+            (fn = workInProgress.updateQueue),
+            null !== fn)
+          ) {
+            unmaskedContext = workInProgress.memoizedState;
+            props = processUpdateQueue(
+              current,
+              workInProgress,
+              fn,
+              null,
+              null,
+              renderExpirationTime
+            );
+            workInProgress.memoizedState = props;
+            fn = workInProgress.updateQueue;
+            if (null !== fn && null !== fn.capturedValues) fn = null;
+            else if (unmaskedContext === props) {
+              resetHydrationState();
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+              break a;
+            } else fn = props.element;
+            unmaskedContext = workInProgress.stateNode;
+            (null === current || null === current.child) &&
+            unmaskedContext.hydrate &&
+            enterHydrationState(workInProgress)
+              ? ((workInProgress.effectTag |= 2),
+                (workInProgress.child = mountChildFibers(
+                  workInProgress,
+                  null,
+                  fn,
+                  renderExpirationTime
+                )))
+              : (resetHydrationState(),
+                reconcileChildren(current, workInProgress, fn));
+            workInProgress.memoizedState = props;
+            current = workInProgress.child;
+          } else
+            resetHydrationState(),
+              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
+          return current;
+        case 5:
+          a: {
+            pushHostContext(workInProgress);
+            null === current &&
+              tryToClaimNextHydratableInstance(workInProgress);
+            props = workInProgress.type;
+            updateQueue = workInProgress.memoizedProps;
+            fn = workInProgress.pendingProps;
+            unmaskedContext = null !== current ? current.memoizedProps : null;
+            if (!hasLegacyContextChanged() && updateQueue === fn) {
+              if (
+                (updateQueue =
+                  workInProgress.mode & 1 &&
+                  shouldDeprioritizeSubtree(props, fn))
+              )
+                workInProgress.expirationTime = 1073741823;
+              if (!updateQueue || 1073741823 !== renderExpirationTime) {
+                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+                break a;
+              }
+            }
+            updateQueue = fn.children;
+            shouldSetTextContent(props, fn)
+              ? (updateQueue = null)
+              : unmaskedContext &&
+                shouldSetTextContent(props, unmaskedContext) &&
+                (workInProgress.effectTag |= 16);
+            markRef(current, workInProgress);
+            1073741823 !== renderExpirationTime &&
+            workInProgress.mode & 1 &&
+            shouldDeprioritizeSubtree(props, fn)
+              ? ((workInProgress.expirationTime = 1073741823),
+                (workInProgress.memoizedProps = fn),
+                (current = null))
+              : (reconcileChildren(current, workInProgress, updateQueue),
+                (workInProgress.memoizedProps = fn),
+                (current = workInProgress.child));
+          }
+          return current;
+        case 6:
+          return (
+            null === current &&
+              tryToClaimNextHydratableInstance(workInProgress),
+            (workInProgress.memoizedProps = workInProgress.pendingProps),
+            null
+          );
+        case 8:
+          workInProgress.tag = 7;
+        case 7:
+          return (
+            (props = workInProgress.pendingProps),
+            hasLegacyContextChanged() ||
+              workInProgress.memoizedProps !== props ||
+              (props = workInProgress.memoizedProps),
+            (fn = props.children),
+            (workInProgress.stateNode =
+              null === current
+                ? mountChildFibers(
+                    workInProgress,
+                    workInProgress.stateNode,
+                    fn,
+                    renderExpirationTime
+                  )
+                : reconcileChildFibers(
+                    workInProgress,
+                    current.stateNode,
+                    fn,
+                    renderExpirationTime
+                  )),
+            (workInProgress.memoizedProps = props),
+            workInProgress.stateNode
+          );
+        case 9:
+          return null;
+        case 4:
+          return (
+            pushHostContainer(
+              workInProgress,
+              workInProgress.stateNode.containerInfo
+            ),
+            (props = workInProgress.pendingProps),
+            hasLegacyContextChanged() || workInProgress.memoizedProps !== props
+              ? (null === current
+                  ? (workInProgress.child = reconcileChildFibers(
+                      workInProgress,
+                      null,
+                      props,
+                      renderExpirationTime
+                    ))
+                  : reconcileChildren(current, workInProgress, props),
+                (workInProgress.memoizedProps = props),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
+        case 14:
+          return (
+            (renderExpirationTime = workInProgress.type.render),
+            (renderExpirationTime = renderExpirationTime(
+              workInProgress.pendingProps,
+              workInProgress.ref
+            )),
+            reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            workInProgress.child
+          );
+        case 10:
+          return (
+            (renderExpirationTime = workInProgress.pendingProps),
+            hasLegacyContextChanged() ||
+            workInProgress.memoizedProps !== renderExpirationTime
+              ? (reconcileChildren(
+                  current,
+                  workInProgress,
+                  renderExpirationTime
+                ),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
+        case 11:
+          return (
+            (renderExpirationTime = workInProgress.pendingProps.children),
+            hasLegacyContextChanged() ||
+            (null !== renderExpirationTime &&
+              workInProgress.memoizedProps !== renderExpirationTime)
+              ? (reconcileChildren(
+                  current,
+                  workInProgress,
+                  renderExpirationTime
+                ),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
+        case 13:
+          return updateContextProvider(
+            current,
+            workInProgress,
+            renderExpirationTime
+          );
+        case 12:
+          a: {
+            fn = workInProgress.type;
+            unmaskedContext = workInProgress.pendingProps;
+            updateQueue = workInProgress.memoizedProps;
+            props = fn._currentValue;
+            var changedBits = fn._changedBits;
+            if (
+              hasLegacyContextChanged() ||
+              0 !== changedBits ||
+              updateQueue !== unmaskedContext
+            ) {
+              workInProgress.memoizedProps = unmaskedContext;
+              var observedBits = unmaskedContext.unstable_observedBits;
+              if (void 0 === observedBits || null === observedBits)
+                observedBits = 1073741823;
+              workInProgress.stateNode = observedBits;
+              if (0 !== (changedBits & observedBits))
+                propagateContextChange(
+                  workInProgress,
+                  fn,
+                  changedBits,
+                  renderExpirationTime
+                );
+              else if (updateQueue === unmaskedContext) {
+                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+                break a;
+              }
+              renderExpirationTime = unmaskedContext.children;
+              renderExpirationTime = renderExpirationTime(props);
+              reconcileChildren(current, workInProgress, renderExpirationTime);
+              current = workInProgress.child;
+            } else
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+          return current;
+        default:
+          invariant(
+            !1,
+            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    }
+  };
+}
+function ReactFiberCompleteWork(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext
+) {
+  function markUpdate(workInProgress) {
+    workInProgress.effectTag |= 4;
+  }
+  function appendAllChildren(parent, workInProgress) {
+    for (var node = workInProgress.child; null !== node; ) {
+      if (5 === node.tag || 6 === node.tag)
+        appendInitialChild(parent, node.stateNode);
+      else if (4 !== node.tag && null !== node.child) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      if (node === workInProgress) break;
+      for (; null === node.sibling; ) {
+        if (null === node["return"] || node["return"] === workInProgress)
+          return;
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+  var createInstance = config.createInstance,
+    createTextInstance = config.createTextInstance,
+    appendInitialChild = config.appendInitialChild,
+    finalizeInitialChildren = config.finalizeInitialChildren,
+    prepareUpdate = config.prepareUpdate,
+    persistence = config.persistence,
+    getRootHostContainer = hostContext.getRootHostContainer,
+    popHostContext = hostContext.popHostContext,
+    getHostContext = hostContext.getHostContext,
+    popHostContainer = hostContext.popHostContainer,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider,
+    prepareToHydrateHostInstance =
+      hydrationContext.prepareToHydrateHostInstance,
+    prepareToHydrateHostTextInstance =
+      hydrationContext.prepareToHydrateHostTextInstance,
+    popHydrationState = hydrationContext.popHydrationState,
+    updateHostContainer = void 0,
+    updateHostComponent = void 0,
+    updateHostText = void 0;
+  if (config.mutation) invariant(!1, "Mutating reconciler is disabled.");
+  else if (persistence) {
+    var cloneInstance = persistence.cloneInstance,
+      createContainerChildSet = persistence.createContainerChildSet,
+      appendChildToContainerChildSet =
+        persistence.appendChildToContainerChildSet,
+      finalizeContainerChildren = persistence.finalizeContainerChildren;
+    updateHostContainer = function(workInProgress) {
+      var portalOrRoot = workInProgress.stateNode;
+      if (null !== workInProgress.firstEffect) {
+        var container = portalOrRoot.containerInfo,
+          newChildSet = createContainerChildSet(container);
+        a: for (var node = workInProgress.child; null !== node; ) {
+          if (5 === node.tag || 6 === node.tag)
+            appendChildToContainerChildSet(newChildSet, node.stateNode);
+          else if (4 !== node.tag && null !== node.child) {
+            node.child["return"] = node;
+            node = node.child;
+            continue;
+          }
+          if (node === workInProgress) break a;
+          for (; null === node.sibling; ) {
+            if (null === node["return"] || node["return"] === workInProgress)
+              break a;
+            node = node["return"];
+          }
+          node.sibling["return"] = node["return"];
+          node = node.sibling;
+        }
+        portalOrRoot.pendingChildren = newChildSet;
+        markUpdate(workInProgress);
+        finalizeContainerChildren(container, newChildSet);
+      }
+    };
+    updateHostComponent = function(
+      current,
+      workInProgress,
+      updatePayload,
+      type,
+      oldProps,
+      newProps,
+      rootContainerInstance,
+      currentHostContext
+    ) {
+      var childrenUnchanged = null === workInProgress.firstEffect;
+      current = current.stateNode;
+      childrenUnchanged && null === updatePayload
+        ? (workInProgress.stateNode = current)
+        : ((updatePayload = cloneInstance(
+            current,
+            updatePayload,
+            type,
+            oldProps,
+            newProps,
+            workInProgress,
+            childrenUnchanged,
+            workInProgress.stateNode
+          )),
+          finalizeInitialChildren(
+            updatePayload,
+            type,
+            newProps,
+            rootContainerInstance,
+            currentHostContext
+          ) && markUpdate(workInProgress),
+          (workInProgress.stateNode = updatePayload),
+          childrenUnchanged
+            ? markUpdate(workInProgress)
+            : appendAllChildren(updatePayload, workInProgress));
+    };
+    updateHostText = function(current, workInProgress, oldText, newText) {
+      oldText !== newText &&
+        ((current = getRootHostContainer()),
+        (oldText = getHostContext()),
+        (workInProgress.stateNode = createTextInstance(
+          newText,
+          current,
+          oldText,
+          workInProgress
+        )),
+        markUpdate(workInProgress));
+    };
+  } else invariant(!1, "Noop reconciler is disabled.");
+  return {
+    completeWork: function(current, workInProgress, renderExpirationTime) {
+      var newProps = workInProgress.pendingProps;
+      switch (workInProgress.tag) {
+        case 1:
+          return null;
+        case 2:
+          return (
+            popLegacyContextProvider(workInProgress),
+            (current = workInProgress.stateNode),
+            (newProps = workInProgress.updateQueue),
+            null !== newProps &&
+              null !== newProps.capturedValues &&
+              ((workInProgress.effectTag &= -65),
+              "function" === typeof current.componentDidCatch
+                ? (workInProgress.effectTag |= 256)
+                : (newProps.capturedValues = null)),
+            null
+          );
+        case 3:
+          popHostContainer(workInProgress);
+          popTopLevelLegacyContextObject(workInProgress);
+          newProps = workInProgress.stateNode;
+          newProps.pendingContext &&
+            ((newProps.context = newProps.pendingContext),
+            (newProps.pendingContext = null));
+          if (null === current || null === current.child)
+            popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
+          updateHostContainer(workInProgress);
+          current = workInProgress.updateQueue;
+          null !== current &&
+            null !== current.capturedValues &&
+            (workInProgress.effectTag |= 256);
+          return null;
+        case 5:
+          popHostContext(workInProgress);
+          renderExpirationTime = getRootHostContainer();
+          var type = workInProgress.type;
+          if (null !== current && null != workInProgress.stateNode) {
+            var oldProps = current.memoizedProps,
+              _instance = workInProgress.stateNode,
+              currentHostContext = getHostContext();
+            _instance = prepareUpdate(
+              _instance,
+              type,
+              oldProps,
+              newProps,
+              renderExpirationTime,
+              currentHostContext
+            );
+            updateHostComponent(
+              current,
+              workInProgress,
+              _instance,
+              type,
+              oldProps,
+              newProps,
+              renderExpirationTime,
+              currentHostContext
+            );
+            current.ref !== workInProgress.ref &&
+              (workInProgress.effectTag |= 128);
+          } else {
+            if (!newProps)
+              return (
+                invariant(
+                  null !== workInProgress.stateNode,
+                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+                ),
+                null
+              );
+            current = getHostContext();
+            popHydrationState(workInProgress)
+              ? prepareToHydrateHostInstance(
+                  workInProgress,
+                  renderExpirationTime,
+                  current
+                ) && markUpdate(workInProgress)
+              : ((oldProps = createInstance(
+                  type,
+                  newProps,
+                  renderExpirationTime,
+                  current,
+                  workInProgress
+                )),
+                appendAllChildren(oldProps, workInProgress),
+                finalizeInitialChildren(
+                  oldProps,
+                  type,
+                  newProps,
+                  renderExpirationTime,
+                  current
+                ) && markUpdate(workInProgress),
+                (workInProgress.stateNode = oldProps));
+            null !== workInProgress.ref && (workInProgress.effectTag |= 128);
+          }
+          return null;
+        case 6:
+          if (current && null != workInProgress.stateNode)
+            updateHostText(
+              current,
+              workInProgress,
+              current.memoizedProps,
+              newProps
+            );
+          else {
+            if ("string" !== typeof newProps)
+              return (
+                invariant(
+                  null !== workInProgress.stateNode,
+                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+                ),
+                null
+              );
+            current = getRootHostContainer();
+            renderExpirationTime = getHostContext();
+            popHydrationState(workInProgress)
+              ? prepareToHydrateHostTextInstance(workInProgress) &&
+                markUpdate(workInProgress)
+              : (workInProgress.stateNode = createTextInstance(
+                  newProps,
+                  current,
+                  renderExpirationTime,
+                  workInProgress
+                ));
+          }
+          return null;
+        case 7:
+          newProps = workInProgress.memoizedProps;
+          invariant(
+            newProps,
+            "Should be resolved by now. This error is likely caused by a bug in React. Please file an issue."
+          );
+          workInProgress.tag = 8;
+          type = [];
+          a: for (
+            (oldProps = workInProgress.stateNode) &&
+            (oldProps["return"] = workInProgress);
+            null !== oldProps;
+
+          ) {
+            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
+              invariant(!1, "A call cannot have host component children.");
+            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
+            else if (null !== oldProps.child) {
+              oldProps.child["return"] = oldProps;
+              oldProps = oldProps.child;
+              continue;
+            }
+            for (; null === oldProps.sibling; ) {
+              if (
+                null === oldProps["return"] ||
+                oldProps["return"] === workInProgress
+              )
+                break a;
+              oldProps = oldProps["return"];
+            }
+            oldProps.sibling["return"] = oldProps["return"];
+            oldProps = oldProps.sibling;
+          }
+          oldProps = newProps.handler;
+          newProps = oldProps(newProps.props, type);
+          workInProgress.child = reconcileChildFibers(
+            workInProgress,
+            null !== current ? current.child : null,
+            newProps,
+            renderExpirationTime
+          );
+          return workInProgress.child;
+        case 8:
+          return (workInProgress.tag = 7), null;
+        case 9:
+          return null;
+        case 14:
+          return null;
+        case 10:
+          return null;
+        case 11:
+          return null;
+        case 4:
+          return (
+            popHostContainer(workInProgress),
+            updateHostContainer(workInProgress),
+            null
+          );
+        case 13:
+          return popProvider(workInProgress), null;
+        case 12:
+          return null;
+        case 0:
+          invariant(
+            !1,
+            "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
+          );
+        default:
+          invariant(
+            !1,
+            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    }
+  };
+}
+function ReactFiberUnwindWork(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  isAlreadyFailedLegacyErrorBoundary
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
+  return {
+    throwException: function(returnFiber, sourceFiber, rawValue) {
+      sourceFiber.effectTag |= 512;
+      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+      sourceFiber = {
+        value: rawValue,
+        source: sourceFiber,
+        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
+      };
+      do {
+        switch (returnFiber.tag) {
+          case 3:
+            ensureUpdateQueues(returnFiber);
+            returnFiber.updateQueue.capturedValues = [sourceFiber];
+            returnFiber.effectTag |= 1024;
+            return;
+          case 2:
+            if (
+              ((rawValue = returnFiber.stateNode),
+              0 === (returnFiber.effectTag & 64) &&
+                null !== rawValue &&
+                "function" === typeof rawValue.componentDidCatch &&
+                !isAlreadyFailedLegacyErrorBoundary(rawValue))
+            ) {
+              ensureUpdateQueues(returnFiber);
+              rawValue = returnFiber.updateQueue;
+              var capturedValues = rawValue.capturedValues;
+              null === capturedValues
+                ? (rawValue.capturedValues = [sourceFiber])
+                : capturedValues.push(sourceFiber);
+              returnFiber.effectTag |= 1024;
+              return;
+            }
+        }
+        returnFiber = returnFiber["return"];
+      } while (null !== returnFiber);
+    },
+    unwindWork: function(workInProgress) {
+      switch (workInProgress.tag) {
+        case 2:
+          popLegacyContextProvider(workInProgress);
+          var effectTag = workInProgress.effectTag;
+          return effectTag & 1024
+            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+              workInProgress)
+            : null;
+        case 3:
+          return (
+            popHostContainer(workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 5:
+          return popHostContext(workInProgress), null;
+        case 4:
+          return popHostContainer(workInProgress), null;
+        case 13:
+          return popProvider(workInProgress), null;
+        default:
+          return null;
+      }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
+    }
+  };
+}
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source;
+  null === errorInfo.stack && getStackAddendumByWorkInProgressFiber(source);
+  null !== source && getComponentName(source);
+  errorInfo = errorInfo.value;
+  null !== boundary && 2 === boundary.tag && getComponentName(boundary);
+  try {
+    (errorInfo && errorInfo.suppressReactErrorLogging) ||
+      console.error(errorInfo);
+  } catch (e) {
+    (e && e.suppressReactErrorLogging) || console.error(e);
+  }
+}
+function ReactFiberCommitWork(
+  config,
+  captureError,
+  scheduleWork,
+  computeExpirationForFiber,
+  markLegacyErrorBoundaryAsFailed
+) {
+  function safelyDetachRef(current) {
+    var ref = current.ref;
+    if (null !== ref)
+      if ("function" === typeof ref)
+        try {
+          ref(null);
+        } catch (refError) {
+          captureError(current, refError);
+        }
+      else ref.current = null;
+  }
+  function commitBeforeMutationLifeCycles(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case 2:
+        if (finishedWork.effectTag & 2048 && null !== current) {
+          var prevProps = current.memoizedProps,
+            prevState = current.memoizedState;
+          current = finishedWork.stateNode;
+          current.props = finishedWork.memoizedProps;
+          current.state = finishedWork.memoizedState;
+          finishedWork = current.getSnapshotBeforeUpdate(prevProps, prevState);
+          current.__reactInternalSnapshotBeforeUpdate = finishedWork;
+        }
+        break;
+      case 3:
+      case 5:
+      case 6:
+      case 4:
+        break;
+      default:
+        invariant(
+          !1,
+          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
+  function commitLifeCycles(finishedRoot, current, finishedWork) {
+    switch (finishedWork.tag) {
+      case 2:
+        finishedRoot = finishedWork.stateNode;
+        if (finishedWork.effectTag & 4)
+          if (null === current)
+            (finishedRoot.props = finishedWork.memoizedProps),
+              (finishedRoot.state = finishedWork.memoizedState),
+              finishedRoot.componentDidMount();
+          else {
+            var prevProps = current.memoizedProps;
+            current = current.memoizedState;
+            finishedRoot.props = finishedWork.memoizedProps;
+            finishedRoot.state = finishedWork.memoizedState;
+            finishedRoot.componentDidUpdate(
+              prevProps,
+              current,
+              finishedRoot.__reactInternalSnapshotBeforeUpdate
+            );
+          }
+        finishedWork = finishedWork.updateQueue;
+        null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
+        break;
+      case 3:
+        current = finishedWork.updateQueue;
+        if (null !== current) {
+          finishedRoot = null;
+          if (null !== finishedWork.child)
+            switch (finishedWork.child.tag) {
+              case 5:
+                finishedRoot = getPublicInstance(finishedWork.child.stateNode);
+                break;
+              case 2:
+                finishedRoot = finishedWork.child.stateNode;
+            }
+          commitCallbacks(current, finishedRoot);
+        }
+        break;
+      case 5:
+        finishedRoot = finishedWork.stateNode;
+        null === current &&
+          finishedWork.effectTag & 4 &&
+          commitMount(
+            finishedRoot,
+            finishedWork.type,
+            finishedWork.memoizedProps,
+            finishedWork
+          );
+        break;
+      case 6:
+        break;
+      case 4:
+        break;
+      default:
+        invariant(
+          !1,
+          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
+  function commitErrorLogging(finishedWork, onUncaughtError) {
+    switch (finishedWork.tag) {
+      case 2:
+        var ctor = finishedWork.type;
+        onUncaughtError = finishedWork.stateNode;
+        var updateQueue = finishedWork.updateQueue;
+        invariant(
+          null !== updateQueue && null !== updateQueue.capturedValues,
+          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
+        );
+        var capturedErrors = updateQueue.capturedValues;
+        updateQueue.capturedValues = null;
+        "function" !== typeof ctor.getDerivedStateFromCatch &&
+          markLegacyErrorBoundaryAsFailed(onUncaughtError);
+        onUncaughtError.props = finishedWork.memoizedProps;
+        onUncaughtError.state = finishedWork.memoizedState;
+        for (ctor = 0; ctor < capturedErrors.length; ctor++) {
+          updateQueue = capturedErrors[ctor];
+          var _error = updateQueue.value,
+            stack = updateQueue.stack;
+          logError(finishedWork, updateQueue);
+          onUncaughtError.componentDidCatch(_error, {
+            componentStack: null !== stack ? stack : ""
+          });
+        }
+        break;
+      case 3:
+        ctor = finishedWork.updateQueue;
+        invariant(
+          null !== ctor && null !== ctor.capturedValues,
+          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
+        );
+        capturedErrors = ctor.capturedValues;
+        ctor.capturedValues = null;
+        for (ctor = 0; ctor < capturedErrors.length; ctor++)
+          (updateQueue = capturedErrors[ctor]),
+            logError(finishedWork, updateQueue),
+            onUncaughtError(updateQueue.value);
+        break;
+      default:
+        invariant(
+          !1,
+          "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
+  function commitAttachRef(finishedWork) {
+    var ref = finishedWork.ref;
+    if (null !== ref) {
+      var _instance6 = finishedWork.stateNode;
+      switch (finishedWork.tag) {
+        case 5:
+          finishedWork = getPublicInstance(_instance6);
+          break;
+        default:
+          finishedWork = _instance6;
+      }
+      "function" === typeof ref
+        ? ref(finishedWork)
+        : (ref.current = finishedWork);
+    }
+  }
+  function commitDetachRef(current) {
+    current = current.ref;
+    null !== current &&
+      ("function" === typeof current
+        ? current(null)
+        : (current.current = null));
+  }
+  function commitNestedUnmounts(root) {
+    for (var node = root; ; ) {
+      var current = node;
+      "function" === typeof onCommitUnmount && onCommitUnmount(current);
+      switch (current.tag) {
+        case 2:
+          safelyDetachRef(current);
+          var _instance7 = current.stateNode;
+          if ("function" === typeof _instance7.componentWillUnmount)
+            try {
+              (_instance7.props = current.memoizedProps),
+                (_instance7.state = current.memoizedState),
+                _instance7.componentWillUnmount();
+            } catch (unmountError) {
+              captureError(current, unmountError);
+            }
+          break;
+        case 5:
+          safelyDetachRef(current);
+          break;
+        case 7:
+          commitNestedUnmounts(current.stateNode);
+          break;
+        case 4:
+          persistence && emptyPortalContainer(current);
+      }
+      if (null === node.child || (mutation && 4 === node.tag)) {
+        if (node === root) break;
+        for (; null === node.sibling; ) {
+          if (null === node["return"] || node["return"] === root) return;
+          node = node["return"];
+        }
+        node.sibling["return"] = node["return"];
+        node = node.sibling;
+      } else (node.child["return"] = node), (node = node.child);
+    }
+  }
+  var getPublicInstance = config.getPublicInstance,
+    mutation = config.mutation,
+    persistence = config.persistence,
+    emptyPortalContainer = void 0;
+  if (!mutation) {
+    var commitContainer = void 0;
+    if (persistence) {
+      var replaceContainerChildren = persistence.replaceContainerChildren,
+        createContainerChildSet = persistence.createContainerChildSet;
+      emptyPortalContainer = function(current) {
+        current = current.stateNode.containerInfo;
+        var emptyChildSet = createContainerChildSet(current);
+        replaceContainerChildren(current, emptyChildSet);
+      };
+      commitContainer = function(finishedWork) {
+        switch (finishedWork.tag) {
+          case 2:
+            break;
+          case 5:
+            break;
+          case 6:
+            break;
+          case 3:
+          case 4:
+            finishedWork = finishedWork.stateNode;
+            replaceContainerChildren(
+              finishedWork.containerInfo,
+              finishedWork.pendingChildren
+            );
+            break;
+          default:
+            invariant(
+              !1,
+              "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+            );
+        }
+      };
+    } else commitContainer = function() {};
+    return {
+      commitResetTextContent: function() {},
+      commitPlacement: function() {},
+      commitDeletion: function(current) {
+        commitNestedUnmounts(current);
+        current["return"] = null;
+        current.child = null;
+        current.alternate &&
+          ((current.alternate.child = null),
+          (current.alternate["return"] = null));
+      },
+      commitWork: function(current, finishedWork) {
+        commitContainer(finishedWork);
+      },
+      commitLifeCycles: commitLifeCycles,
+      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+      commitErrorLogging: commitErrorLogging,
+      commitAttachRef: commitAttachRef,
+      commitDetachRef: commitDetachRef
+    };
+  }
+  var commitMount = mutation.commitMount;
+  invariant(!1, "Mutating reconciler is disabled.");
+}
+var NO_CONTEXT = {};
+function ReactFiberHostContext(config, stack) {
+  function requiredContext(c) {
+    invariant(
+      c !== NO_CONTEXT,
+      "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
+    );
+    return c;
+  }
+  var getChildHostContext = config.getChildHostContext,
+    getRootHostContext = config.getRootHostContext;
+  config = stack.createCursor;
+  var push = stack.push,
+    pop = stack.pop,
+    contextStackCursor = config(NO_CONTEXT),
+    contextFiberStackCursor = config(NO_CONTEXT),
+    rootInstanceStackCursor = config(NO_CONTEXT);
+  return {
+    getHostContext: function() {
+      return requiredContext(contextStackCursor.current);
+    },
+    getRootHostContainer: function() {
+      return requiredContext(rootInstanceStackCursor.current);
+    },
+    popHostContainer: function(fiber) {
+      pop(contextStackCursor, fiber);
+      pop(contextFiberStackCursor, fiber);
+      pop(rootInstanceStackCursor, fiber);
+    },
+    popHostContext: function(fiber) {
+      contextFiberStackCursor.current === fiber &&
+        (pop(contextStackCursor, fiber), pop(contextFiberStackCursor, fiber));
+    },
+    pushHostContainer: function(fiber, nextRootInstance) {
+      push(rootInstanceStackCursor, nextRootInstance, fiber);
+      push(contextFiberStackCursor, fiber, fiber);
+      push(contextStackCursor, NO_CONTEXT, fiber);
+      nextRootInstance = getRootHostContext(nextRootInstance);
+      pop(contextStackCursor, fiber);
+      push(contextStackCursor, nextRootInstance, fiber);
+    },
+    pushHostContext: function(fiber) {
+      var rootInstance = requiredContext(rootInstanceStackCursor.current),
+        context = requiredContext(contextStackCursor.current);
+      rootInstance = getChildHostContext(context, fiber.type, rootInstance);
+      context !== rootInstance &&
+        (push(contextFiberStackCursor, fiber, fiber),
+        push(contextStackCursor, rootInstance, fiber));
+    }
+  };
+}
+function ReactFiberHydrationContext(config) {
+  function deleteHydratableInstance(returnFiber, instance) {
+    var fiber = new FiberNode(5, null, null, 0);
+    fiber.type = "DELETED";
+    fiber.stateNode = instance;
+    fiber["return"] = returnFiber;
+    fiber.effectTag = 8;
+    null !== returnFiber.lastEffect
+      ? ((returnFiber.lastEffect.nextEffect = fiber),
+        (returnFiber.lastEffect = fiber))
+      : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
+  }
+  function tryHydrate(fiber, nextInstance) {
+    switch (fiber.tag) {
+      case 5:
+        return (
+          (nextInstance = canHydrateInstance(
+            nextInstance,
+            fiber.type,
+            fiber.pendingProps
+          )),
+          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+        );
+      case 6:
+        return (
+          (nextInstance = canHydrateTextInstance(
+            nextInstance,
+            fiber.pendingProps
+          )),
+          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+        );
+      default:
+        return !1;
+    }
+  }
+  function popToNextHostParent(fiber) {
+    for (
+      fiber = fiber["return"];
+      null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
+
+    )
+      fiber = fiber["return"];
+    hydrationParentFiber = fiber;
+  }
+  var shouldSetTextContent = config.shouldSetTextContent;
+  config = config.hydration;
+  if (!config)
+    return {
+      enterHydrationState: function() {
+        return !1;
+      },
+      resetHydrationState: function() {},
+      tryToClaimNextHydratableInstance: function() {},
+      prepareToHydrateHostInstance: function() {
+        invariant(
+          !1,
+          "Expected prepareToHydrateHostInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      prepareToHydrateHostTextInstance: function() {
+        invariant(
+          !1,
+          "Expected prepareToHydrateHostTextInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      popHydrationState: function() {
+        return !1;
+      }
+    };
+  var canHydrateInstance = config.canHydrateInstance,
+    canHydrateTextInstance = config.canHydrateTextInstance,
+    getNextHydratableSibling = config.getNextHydratableSibling,
+    getFirstHydratableChild = config.getFirstHydratableChild,
+    hydrateInstance = config.hydrateInstance,
+    hydrateTextInstance = config.hydrateTextInstance,
+    hydrationParentFiber = null,
+    nextHydratableInstance = null,
+    isHydrating = !1;
+  return {
+    enterHydrationState: function(fiber) {
+      nextHydratableInstance = getFirstHydratableChild(
+        fiber.stateNode.containerInfo
+      );
+      hydrationParentFiber = fiber;
+      return (isHydrating = !0);
+    },
+    resetHydrationState: function() {
+      nextHydratableInstance = hydrationParentFiber = null;
+      isHydrating = !1;
+    },
+    tryToClaimNextHydratableInstance: function(fiber) {
+      if (isHydrating) {
+        var nextInstance = nextHydratableInstance;
+        if (nextInstance) {
+          if (!tryHydrate(fiber, nextInstance)) {
+            nextInstance = getNextHydratableSibling(nextInstance);
+            if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
+              fiber.effectTag |= 2;
+              isHydrating = !1;
+              hydrationParentFiber = fiber;
+              return;
+            }
+            deleteHydratableInstance(
+              hydrationParentFiber,
+              nextHydratableInstance
+            );
+          }
+          hydrationParentFiber = fiber;
+          nextHydratableInstance = getFirstHydratableChild(nextInstance);
+        } else
+          (fiber.effectTag |= 2),
+            (isHydrating = !1),
+            (hydrationParentFiber = fiber);
+      }
+    },
+    prepareToHydrateHostInstance: function(
+      fiber,
+      rootContainerInstance,
+      hostContext
+    ) {
+      rootContainerInstance = hydrateInstance(
+        fiber.stateNode,
+        fiber.type,
+        fiber.memoizedProps,
+        rootContainerInstance,
+        hostContext,
+        fiber
+      );
+      fiber.updateQueue = rootContainerInstance;
+      return null !== rootContainerInstance ? !0 : !1;
+    },
+    prepareToHydrateHostTextInstance: function(fiber) {
+      return hydrateTextInstance(fiber.stateNode, fiber.memoizedProps, fiber);
+    },
+    popHydrationState: function(fiber) {
+      if (fiber !== hydrationParentFiber) return !1;
+      if (!isHydrating)
+        return popToNextHostParent(fiber), (isHydrating = !0), !1;
+      var type = fiber.type;
+      if (
+        5 !== fiber.tag ||
+        ("head" !== type &&
+          "body" !== type &&
+          !shouldSetTextContent(type, fiber.memoizedProps))
+      )
+        for (type = nextHydratableInstance; type; )
+          deleteHydratableInstance(fiber, type),
+            (type = getNextHydratableSibling(type));
+      popToNextHostParent(fiber);
+      nextHydratableInstance = hydrationParentFiber
+        ? getNextHydratableSibling(fiber.stateNode)
+        : null;
+      return !0;
+    }
+  };
+}
+function ReactFiberLegacyContext(stack) {
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    workInProgress = workInProgress.stateNode;
+    workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    workInProgress.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
+  function isContextProvider(fiber) {
+    return 2 === fiber.tag && null != fiber.type.childContextTypes;
+  }
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode,
+      childContextTypes = fiber.type.childContextTypes;
+    if ("function" !== typeof instance.getChildContext) return parentContext;
+    instance = instance.getChildContext();
+    for (var contextKey in instance)
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    return Object.assign({}, parentContext, instance);
+  }
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop,
+    contextStackCursor = createCursor(emptyObject),
+    didPerformWorkStackCursor = createCursor(!1),
+    previousContext = emptyObject;
+  return {
+    getUnmaskedContext: function(workInProgress) {
+      return isContextProvider(workInProgress)
+        ? previousContext
+        : contextStackCursor.current;
+    },
+    cacheContext: cacheContext,
+    getMaskedContext: function(workInProgress, unmaskedContext) {
+      var contextTypes = workInProgress.type.contextTypes;
+      if (!contextTypes) return emptyObject;
+      var instance = workInProgress.stateNode;
+      if (
+        instance &&
+        instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+      )
+        return instance.__reactInternalMemoizedMaskedChildContext;
+      var context = {},
+        key;
+      for (key in contextTypes) context[key] = unmaskedContext[key];
+      instance && cacheContext(workInProgress, unmaskedContext, context);
+      return context;
+    },
+    hasContextChanged: function() {
+      return didPerformWorkStackCursor.current;
+    },
+    isContextConsumer: function(fiber) {
+      return 2 === fiber.tag && null != fiber.type.contextTypes;
+    },
+    isContextProvider: isContextProvider,
+    popContextProvider: function(fiber) {
+      isContextProvider(fiber) &&
+        (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
+    },
+    popTopLevelContextObject: function(fiber) {
+      pop(didPerformWorkStackCursor, fiber);
+      pop(contextStackCursor, fiber);
+    },
+    pushTopLevelContextObject: function(fiber, context, didChange) {
+      invariant(
+        null == contextStackCursor.cursor,
+        "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
+      );
+      push(contextStackCursor, context, fiber);
+      push(didPerformWorkStackCursor, didChange, fiber);
+    },
+    processChildContext: processChildContext,
+    pushContextProvider: function(workInProgress) {
+      if (!isContextProvider(workInProgress)) return !1;
+      var instance = workInProgress.stateNode;
+      instance =
+        (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+        emptyObject;
+      previousContext = contextStackCursor.current;
+      push(contextStackCursor, instance, workInProgress);
+      push(
+        didPerformWorkStackCursor,
+        didPerformWorkStackCursor.current,
+        workInProgress
+      );
+      return !0;
+    },
+    invalidateContextProvider: function(workInProgress, didChange) {
+      var instance = workInProgress.stateNode;
+      invariant(
+        instance,
+        "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+      );
+      if (didChange) {
+        var mergedContext = processChildContext(
+          workInProgress,
+          previousContext
+        );
+        instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+        pop(didPerformWorkStackCursor, workInProgress);
+        pop(contextStackCursor, workInProgress);
+        push(contextStackCursor, mergedContext, workInProgress);
+      } else pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    },
+    findCurrentUnmaskedContext: function(fiber) {
+      for (
+        invariant(
+          2 === isFiberMountedImpl(fiber) && 2 === fiber.tag,
+          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
+        );
+        3 !== fiber.tag;
+
+      ) {
+        if (isContextProvider(fiber))
+          return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
+        fiber = fiber["return"];
+        invariant(
+          fiber,
+          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+      }
+      return fiber.stateNode.context;
+    }
+  };
+}
+function ReactFiberNewContext(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop,
+    providerCursor = createCursor(null),
+    valueCursor = createCursor(null),
+    changedBitsCursor = createCursor(0);
+  return {
+    pushProvider: function(providerFiber) {
+      var context = providerFiber.type._context;
+      push(changedBitsCursor, context._changedBits, providerFiber);
+      push(valueCursor, context._currentValue, providerFiber);
+      push(providerCursor, providerFiber, providerFiber);
+      context._currentValue = providerFiber.pendingProps.value;
+      context._changedBits = providerFiber.stateNode;
+    },
+    popProvider: function(providerFiber) {
+      var changedBits = changedBitsCursor.current,
+        currentValue = valueCursor.current;
+      pop(providerCursor, providerFiber);
+      pop(valueCursor, providerFiber);
+      pop(changedBitsCursor, providerFiber);
+      providerFiber = providerFiber.type._context;
+      providerFiber._currentValue = currentValue;
+      providerFiber._changedBits = changedBits;
+    }
+  };
+}
+function ReactFiberStack() {
+  var valueStack = [],
+    index = -1;
+  return {
+    createCursor: function(defaultValue) {
+      return { current: defaultValue };
+    },
+    isEmpty: function() {
+      return -1 === index;
+    },
+    pop: function(cursor) {
+      0 > index ||
+        ((cursor.current = valueStack[index]),
+        (valueStack[index] = null),
+        index--);
+    },
+    push: function(cursor, value) {
+      index++;
+      valueStack[index] = cursor.current;
+      cursor.current = value;
+    },
+    checkThatStackIsEmpty: function() {},
+    resetStackAfterFatalErrorInDev: function() {}
+  };
+}
+function ReactFiberScheduler(config) {
+  function resetStack() {
+    if (null !== nextUnitOfWork)
+      for (
+        var interruptedWork = nextUnitOfWork["return"];
+        null !== interruptedWork;
+
+      )
+        unwindInterruptedWork(interruptedWork),
+          (interruptedWork = interruptedWork["return"]);
+    nextRoot = null;
+    nextRenderExpirationTime = 0;
+    nextUnitOfWork = null;
+    isRootReadyForCommit = !1;
+  }
+  function isAlreadyFailedLegacyErrorBoundary(instance) {
+    return (
+      null !== legacyErrorBoundariesThatAlreadyFailed &&
+      legacyErrorBoundariesThatAlreadyFailed.has(instance)
+    );
+  }
+  function completeUnitOfWork(workInProgress$jscomp$0) {
+    for (;;) {
+      var current = workInProgress$jscomp$0.alternate,
+        returnFiber = workInProgress$jscomp$0["return"],
+        siblingFiber = workInProgress$jscomp$0.sibling;
+      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
+        current = completeWork(
+          current,
+          workInProgress$jscomp$0,
+          nextRenderExpirationTime
+        );
+        var workInProgress = workInProgress$jscomp$0;
+        if (
+          1073741823 === nextRenderExpirationTime ||
+          1073741823 !== workInProgress.expirationTime
+        ) {
+          b: switch (workInProgress.tag) {
+            case 3:
+            case 2:
+              var newExpirationTime = workInProgress.updateQueue;
+              newExpirationTime =
+                null === newExpirationTime
+                  ? 0
+                  : newExpirationTime.expirationTime;
+              break b;
+            default:
+              newExpirationTime = 0;
+          }
+          for (var child = workInProgress.child; null !== child; )
+            0 !== child.expirationTime &&
+              (0 === newExpirationTime ||
+                newExpirationTime > child.expirationTime) &&
+              (newExpirationTime = child.expirationTime),
+              (child = child.sibling);
+          workInProgress.expirationTime = newExpirationTime;
+        }
+        if (null !== current) return current;
+        null !== returnFiber &&
+          0 === (returnFiber.effectTag & 512) &&
+          (null === returnFiber.firstEffect &&
+            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
+          null !== workInProgress$jscomp$0.lastEffect &&
+            (null !== returnFiber.lastEffect &&
+              (returnFiber.lastEffect.nextEffect =
+                workInProgress$jscomp$0.firstEffect),
+            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
+          1 < workInProgress$jscomp$0.effectTag &&
+            (null !== returnFiber.lastEffect
+              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
+              : (returnFiber.firstEffect = workInProgress$jscomp$0),
+            (returnFiber.lastEffect = workInProgress$jscomp$0)));
+        if (null !== siblingFiber) return siblingFiber;
+        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+        else {
+          isRootReadyForCommit = !0;
+          break;
+        }
+      } else {
+        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
+        if (null !== workInProgress$jscomp$0)
+          return (
+            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
+          );
+        null !== returnFiber &&
+          ((returnFiber.firstEffect = returnFiber.lastEffect = null),
+          (returnFiber.effectTag |= 512));
+        if (null !== siblingFiber) return siblingFiber;
+        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+        else break;
+      }
+    }
+    return null;
+  }
+  function performUnitOfWork(workInProgress) {
+    var next = beginWork(
+      workInProgress.alternate,
+      workInProgress,
+      nextRenderExpirationTime
+    );
+    null === next && (next = completeUnitOfWork(workInProgress));
+    ReactCurrentOwner.current = null;
+    return next;
+  }
+  function renderRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isWorking,
+      "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+    );
+    isWorking = !0;
+    if (
+      expirationTime !== nextRenderExpirationTime ||
+      root !== nextRoot ||
+      null === nextUnitOfWork
+    )
+      resetStack(),
+        (nextRoot = root),
+        (nextRenderExpirationTime = expirationTime),
+        (nextUnitOfWork = createWorkInProgress(
+          nextRoot.current,
+          null,
+          nextRenderExpirationTime
+        )),
+        (root.pendingCommitExpirationTime = 0);
+    var didFatal = !1;
+    do {
+      try {
+        if (isAsync)
+          for (; null !== nextUnitOfWork && !shouldYield(); )
+            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+        else
+          for (; null !== nextUnitOfWork; )
+            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      } catch (thrownValue) {
+        if (null === nextUnitOfWork) {
+          didFatal = !0;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        isAsync = nextUnitOfWork;
+        var returnFiber = isAsync["return"];
+        if (null === returnFiber) {
+          didFatal = !0;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        throwException(returnFiber, isAsync, thrownValue);
+        nextUnitOfWork = completeUnitOfWork(isAsync);
+      }
+      break;
+    } while (1);
+    isWorking = !1;
+    if (didFatal || null !== nextUnitOfWork) return null;
+    if (isRootReadyForCommit)
+      return (
+        (root.pendingCommitExpirationTime = expirationTime),
+        root.current.alternate
+      );
+    invariant(
+      !1,
+      "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
+    sourceFiber = {
+      value: value,
+      source: sourceFiber,
+      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
+    };
+    insertUpdateIntoFiber(boundaryFiber, {
+      expirationTime: expirationTime,
+      partialState: null,
+      callback: null,
+      isReplace: !1,
+      isForced: !1,
+      capturedValue: sourceFiber,
+      next: null
+    });
+    scheduleWork(boundaryFiber, expirationTime);
+  }
+  function onCommitPhaseError(fiber$jscomp$0, error) {
+    a: {
+      invariant(
+        !isWorking || isCommitting,
+        "dispatch: Cannot dispatch during the render phase."
+      );
+      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
+        switch (fiber.tag) {
+          case 2:
+            var instance = fiber.stateNode;
+            if (
+              "function" === typeof fiber.type.getDerivedStateFromCatch ||
+              ("function" === typeof instance.componentDidCatch &&
+                !isAlreadyFailedLegacyErrorBoundary(instance))
+            ) {
+              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
+              fiber$jscomp$0 = void 0;
+              break a;
+            }
+            break;
+          case 3:
+            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
+            fiber$jscomp$0 = void 0;
+            break a;
+        }
+        fiber = fiber["return"];
+      }
+      3 === fiber$jscomp$0.tag &&
+        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
+      fiber$jscomp$0 = void 0;
+    }
+    return fiber$jscomp$0;
+  }
+  function computeExpirationForFiber(fiber) {
+    fiber =
+      0 !== expirationContext
+        ? expirationContext
+        : isWorking
+          ? isCommitting ? 1 : nextRenderExpirationTime
+          : fiber.mode & 1
+            ? isBatchingInteractiveUpdates
+              ? 10 * ((((recalculateCurrentTime() + 15) / 10) | 0) + 1)
+              : 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1)
+            : 1;
+    isBatchingInteractiveUpdates &&
+      (0 === lowestPendingInteractiveExpirationTime ||
+        fiber > lowestPendingInteractiveExpirationTime) &&
+      (lowestPendingInteractiveExpirationTime = fiber);
+    return fiber;
+  }
+  function scheduleWork(fiber, expirationTime) {
+    a: {
+      for (; null !== fiber; ) {
+        if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
+          fiber.expirationTime = expirationTime;
+        null !== fiber.alternate &&
+          (0 === fiber.alternate.expirationTime ||
+            fiber.alternate.expirationTime > expirationTime) &&
+          (fiber.alternate.expirationTime = expirationTime);
+        if (null === fiber["return"])
+          if (3 === fiber.tag) {
+            var root = fiber.stateNode;
+            !isWorking &&
+              0 !== nextRenderExpirationTime &&
+              expirationTime < nextRenderExpirationTime &&
+              resetStack();
+            (isWorking && !isCommitting && nextRoot === root) ||
+              requestWork(root, expirationTime);
+            nestedUpdateCount > NESTED_UPDATE_LIMIT &&
+              invariant(
+                !1,
+                "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
+              );
+          } else {
+            expirationTime = void 0;
+            break a;
+          }
+        fiber = fiber["return"];
+      }
+      expirationTime = void 0;
+    }
+    return expirationTime;
+  }
+  function recalculateCurrentTime() {
+    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
+    return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
+  }
+  function syncUpdates(fn, a, b, c, d) {
+    var previousExpirationContext = expirationContext;
+    expirationContext = 1;
+    try {
+      return fn(a, b, c, d);
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  }
+  function scheduleCallbackWithExpiration(expirationTime) {
+    if (0 !== callbackExpirationTime) {
+      if (expirationTime > callbackExpirationTime) return;
+      cancelDeferredCallback(callbackID);
+    }
+    var currentMs = now() - originalStartTimeMs;
+    callbackExpirationTime = expirationTime;
+    callbackID = scheduleDeferredCallback(performAsyncWork, {
+      timeout: 10 * (expirationTime - 2) - currentMs
+    });
+  }
+  function requestWork(root, expirationTime) {
+    if (null === root.nextScheduledRoot)
+      (root.remainingExpirationTime = expirationTime),
+        null === lastScheduledRoot
+          ? ((firstScheduledRoot = lastScheduledRoot = root),
+            (root.nextScheduledRoot = root))
+          : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
+            (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
+    else {
+      var remainingExpirationTime = root.remainingExpirationTime;
+      if (
+        0 === remainingExpirationTime ||
+        expirationTime < remainingExpirationTime
+      )
+        root.remainingExpirationTime = expirationTime;
+    }
+    isRendering ||
+      (isBatchingUpdates
+        ? isUnbatchingUpdates &&
+          ((nextFlushedRoot = root),
+          (nextFlushedExpirationTime = 1),
+          performWorkOnRoot(root, 1, !1))
+        : 1 === expirationTime
+          ? performSyncWork()
+          : scheduleCallbackWithExpiration(expirationTime));
+  }
+  function findHighestPriorityRoot() {
+    var highestPriorityWork = 0,
+      highestPriorityRoot = null;
+    if (null !== lastScheduledRoot)
+      for (
+        var previousScheduledRoot = lastScheduledRoot,
+          root = firstScheduledRoot;
+        null !== root;
+
+      ) {
+        var remainingExpirationTime = root.remainingExpirationTime;
+        if (0 === remainingExpirationTime) {
+          invariant(
+            null !== previousScheduledRoot && null !== lastScheduledRoot,
+            "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
+          );
+          if (root === root.nextScheduledRoot) {
+            firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
+            break;
+          } else if (root === firstScheduledRoot)
+            (firstScheduledRoot = remainingExpirationTime =
+              root.nextScheduledRoot),
+              (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
+              (root.nextScheduledRoot = null);
+          else if (root === lastScheduledRoot) {
+            lastScheduledRoot = previousScheduledRoot;
+            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+            root.nextScheduledRoot = null;
+            break;
+          } else
+            (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
+              (root.nextScheduledRoot = null);
+          root = previousScheduledRoot.nextScheduledRoot;
+        } else {
+          if (
+            0 === highestPriorityWork ||
+            remainingExpirationTime < highestPriorityWork
+          )
+            (highestPriorityWork = remainingExpirationTime),
+              (highestPriorityRoot = root);
+          if (root === lastScheduledRoot) break;
+          previousScheduledRoot = root;
+          root = root.nextScheduledRoot;
+        }
+      }
+    previousScheduledRoot = nextFlushedRoot;
+    null !== previousScheduledRoot &&
+    previousScheduledRoot === highestPriorityRoot &&
+    1 === highestPriorityWork
+      ? nestedUpdateCount++
+      : (nestedUpdateCount = 0);
+    nextFlushedRoot = highestPriorityRoot;
+    nextFlushedExpirationTime = highestPriorityWork;
+  }
+  function performAsyncWork(dl) {
+    performWork(0, !0, dl);
+  }
+  function performSyncWork() {
+    performWork(1, !1, null);
+  }
+  function performWork(minExpirationTime, isAsync, dl) {
+    deadline = dl;
+    findHighestPriorityRoot();
+    if (isAsync)
+      for (
+        ;
+        null !== nextFlushedRoot &&
+        0 !== nextFlushedExpirationTime &&
+        (0 === minExpirationTime ||
+          minExpirationTime >= nextFlushedExpirationTime) &&
+        (!deadlineDidExpire ||
+          recalculateCurrentTime() >= nextFlushedExpirationTime);
+
+      )
+        performWorkOnRoot(
+          nextFlushedRoot,
+          nextFlushedExpirationTime,
+          !deadlineDidExpire
+        ),
+          findHighestPriorityRoot();
+    else
+      for (
+        ;
+        null !== nextFlushedRoot &&
+        0 !== nextFlushedExpirationTime &&
+        (0 === minExpirationTime ||
+          minExpirationTime >= nextFlushedExpirationTime);
+
+      )
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
+          findHighestPriorityRoot();
+    null !== deadline && ((callbackExpirationTime = 0), (callbackID = -1));
+    0 !== nextFlushedExpirationTime &&
+      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
+    deadline = null;
+    deadlineDidExpire = !1;
+    finishRendering();
+  }
+  function finishRendering() {
+    nestedUpdateCount = 0;
+    if (null !== completedBatches) {
+      var batches = completedBatches;
+      completedBatches = null;
+      for (var i = 0; i < batches.length; i++) {
+        var batch = batches[i];
+        try {
+          batch._onComplete();
+        } catch (error) {
+          hasUnhandledError ||
+            ((hasUnhandledError = !0), (unhandledError = error));
+        }
+      }
+    }
+    if (hasUnhandledError)
+      throw ((batches = unhandledError),
+      (unhandledError = null),
+      (hasUnhandledError = !1),
+      batches);
+  }
+  function performWorkOnRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isRendering,
+      "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+    );
+    isRendering = !0;
+    isAsync
+      ? ((isAsync = root.finishedWork),
+        null !== isAsync
+          ? completeRoot(root, isAsync, expirationTime)
+          : ((root.finishedWork = null),
+            (isAsync = renderRoot(root, expirationTime, !0)),
+            null !== isAsync &&
+              (shouldYield()
+                ? (root.finishedWork = isAsync)
+                : completeRoot(root, isAsync, expirationTime))))
+      : ((isAsync = root.finishedWork),
+        null !== isAsync
+          ? completeRoot(root, isAsync, expirationTime)
+          : ((root.finishedWork = null),
+            (isAsync = renderRoot(root, expirationTime, !1)),
+            null !== isAsync && completeRoot(root, isAsync, expirationTime)));
+    isRendering = !1;
+  }
+  function completeRoot(root, finishedWork, expirationTime) {
+    var firstBatch = root.firstBatch;
+    if (
+      null !== firstBatch &&
+      firstBatch._expirationTime <= expirationTime &&
+      (null === completedBatches
+        ? (completedBatches = [firstBatch])
+        : completedBatches.push(firstBatch),
+      firstBatch._defer)
+    ) {
+      root.finishedWork = finishedWork;
+      root.remainingExpirationTime = 0;
+      return;
+    }
+    root.finishedWork = null;
+    isCommitting = isWorking = !0;
+    expirationTime = finishedWork.stateNode;
+    invariant(
+      expirationTime.current !== finishedWork,
+      "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
+    );
+    firstBatch = expirationTime.pendingCommitExpirationTime;
+    invariant(
+      0 !== firstBatch,
+      "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
+    );
+    expirationTime.pendingCommitExpirationTime = 0;
+    var currentTime = recalculateCurrentTime();
+    ReactCurrentOwner.current = null;
+    if (1 < finishedWork.effectTag)
+      if (null !== finishedWork.lastEffect) {
+        finishedWork.lastEffect.nextEffect = finishedWork;
+        var firstEffect = finishedWork.firstEffect;
+      } else firstEffect = finishedWork;
+    else firstEffect = finishedWork.firstEffect;
+    prepareForCommit(expirationTime.containerInfo);
+    for (nextEffect = firstEffect; null !== nextEffect; ) {
+      var didError = !1,
+        error = void 0;
+      try {
+        for (; null !== nextEffect; )
+          nextEffect.effectTag & 2048 &&
+            commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
+            (nextEffect = nextEffect.nextEffect);
+      } catch (e) {
+        (didError = !0), (error = e);
+      }
+      didError &&
+        (invariant(
+          null !== nextEffect,
+          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        onCommitPhaseError(nextEffect, error),
+        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    }
+    for (nextEffect = firstEffect; null !== nextEffect; ) {
+      didError = !1;
+      error = void 0;
+      try {
+        for (; null !== nextEffect; ) {
+          var effectTag = nextEffect.effectTag;
+          effectTag & 16 && commitResetTextContent(nextEffect);
+          if (effectTag & 128) {
+            var current = nextEffect.alternate;
+            null !== current && commitDetachRef(current);
+          }
+          switch (effectTag & 14) {
+            case 2:
+              commitPlacement(nextEffect);
+              nextEffect.effectTag &= -3;
+              break;
+            case 6:
+              commitPlacement(nextEffect);
+              nextEffect.effectTag &= -3;
+              commitWork(nextEffect.alternate, nextEffect);
+              break;
+            case 4:
+              commitWork(nextEffect.alternate, nextEffect);
+              break;
+            case 8:
+              commitDeletion(nextEffect);
+          }
+          nextEffect = nextEffect.nextEffect;
+        }
+      } catch (e) {
+        (didError = !0), (error = e);
+      }
+      didError &&
+        (invariant(
+          null !== nextEffect,
+          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        onCommitPhaseError(nextEffect, error),
+        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    }
+    resetAfterCommit(expirationTime.containerInfo);
+    expirationTime.current = finishedWork;
+    for (nextEffect = firstEffect; null !== nextEffect; ) {
+      effectTag = !1;
+      current = void 0;
+      try {
+        for (
+          firstEffect = expirationTime,
+            didError = currentTime,
+            error = firstBatch;
+          null !== nextEffect;
+
+        ) {
+          var effectTag$jscomp$0 = nextEffect.effectTag;
+          effectTag$jscomp$0 & 36 &&
+            commitLifeCycles(
+              firstEffect,
+              nextEffect.alternate,
+              nextEffect,
+              didError,
+              error
+            );
+          effectTag$jscomp$0 & 256 &&
+            commitErrorLogging(nextEffect, onUncaughtError);
+          effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
+          var next = nextEffect.nextEffect;
+          nextEffect.nextEffect = null;
+          nextEffect = next;
+        }
+      } catch (e) {
+        (effectTag = !0), (current = e);
+      }
+      effectTag &&
+        (invariant(
+          null !== nextEffect,
+          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        onCommitPhaseError(nextEffect, current),
+        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    }
+    isWorking = isCommitting = !1;
+    "function" === typeof onCommitRoot && onCommitRoot(finishedWork.stateNode);
+    finishedWork = expirationTime.current.expirationTime;
+    0 === finishedWork && (legacyErrorBoundariesThatAlreadyFailed = null);
+    root.remainingExpirationTime = finishedWork;
+  }
+  function shouldYield() {
+    return null === deadline ||
+      deadline.timeRemaining() > timeHeuristicForUnitOfWork
+      ? !1
+      : (deadlineDidExpire = !0);
+  }
+  function onUncaughtError(error) {
+    invariant(
+      null !== nextFlushedRoot,
+      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
+    );
+    nextFlushedRoot.remainingExpirationTime = 0;
+    hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
+  }
+  var stack = ReactFiberStack(),
+    hostContext = ReactFiberHostContext(config, stack),
+    legacyContext = ReactFiberLegacyContext(stack);
+  stack = ReactFiberNewContext(stack);
+  var hydrationContext = ReactFiberHydrationContext(config),
+    beginWork = ReactFiberBeginWork(
+      config,
+      hostContext,
+      legacyContext,
+      stack,
+      hydrationContext,
+      scheduleWork,
+      computeExpirationForFiber
+    ).beginWork,
+    completeWork = ReactFiberCompleteWork(
+      config,
+      hostContext,
+      legacyContext,
+      stack,
+      hydrationContext
+    ).completeWork;
+  hostContext = ReactFiberUnwindWork(
+    hostContext,
+    legacyContext,
+    stack,
+    scheduleWork,
+    isAlreadyFailedLegacyErrorBoundary
+  );
+  var throwException = hostContext.throwException,
+    unwindWork = hostContext.unwindWork,
+    unwindInterruptedWork = hostContext.unwindInterruptedWork;
+  hostContext = ReactFiberCommitWork(
+    config,
+    onCommitPhaseError,
+    scheduleWork,
+    computeExpirationForFiber,
+    function(instance) {
+      null === legacyErrorBoundariesThatAlreadyFailed
+        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
+        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+    },
+    recalculateCurrentTime
+  );
+  var commitBeforeMutationLifeCycles =
+      hostContext.commitBeforeMutationLifeCycles,
+    commitResetTextContent = hostContext.commitResetTextContent,
+    commitPlacement = hostContext.commitPlacement,
+    commitDeletion = hostContext.commitDeletion,
+    commitWork = hostContext.commitWork,
+    commitLifeCycles = hostContext.commitLifeCycles,
+    commitErrorLogging = hostContext.commitErrorLogging,
+    commitAttachRef = hostContext.commitAttachRef,
+    commitDetachRef = hostContext.commitDetachRef,
+    now = config.now,
+    scheduleDeferredCallback = config.scheduleDeferredCallback,
+    cancelDeferredCallback = config.cancelDeferredCallback,
+    prepareForCommit = config.prepareForCommit,
+    resetAfterCommit = config.resetAfterCommit,
+    originalStartTimeMs = now(),
+    mostRecentCurrentTime = 2,
+    mostRecentCurrentTimeMs = originalStartTimeMs,
+    lastUniqueAsyncExpiration = 0,
+    expirationContext = 0,
+    isWorking = !1,
+    nextUnitOfWork = null,
+    nextRoot = null,
+    nextRenderExpirationTime = 0,
+    nextEffect = null,
+    isCommitting = !1,
+    isRootReadyForCommit = !1,
+    legacyErrorBoundariesThatAlreadyFailed = null,
+    firstScheduledRoot = null,
+    lastScheduledRoot = null,
+    callbackExpirationTime = 0,
+    callbackID = -1,
+    isRendering = !1,
+    nextFlushedRoot = null,
+    nextFlushedExpirationTime = 0,
+    lowestPendingInteractiveExpirationTime = 0,
+    deadlineDidExpire = !1,
+    hasUnhandledError = !1,
+    unhandledError = null,
+    deadline = null,
+    isBatchingUpdates = !1,
+    isUnbatchingUpdates = !1,
+    isBatchingInteractiveUpdates = !1,
+    completedBatches = null,
+    NESTED_UPDATE_LIMIT = 1e3,
+    nestedUpdateCount = 0,
+    timeHeuristicForUnitOfWork = 1;
+  return {
+    recalculateCurrentTime: recalculateCurrentTime,
+    computeExpirationForFiber: computeExpirationForFiber,
+    scheduleWork: scheduleWork,
+    requestWork: requestWork,
+    flushRoot: function(root, expirationTime) {
+      invariant(
+        !isRendering,
+        "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
+      );
+      nextFlushedRoot = root;
+      nextFlushedExpirationTime = expirationTime;
+      performWorkOnRoot(root, expirationTime, !1);
+      performSyncWork();
+      finishRendering();
+    },
+    batchedUpdates: function(fn, a) {
+      var previousIsBatchingUpdates = isBatchingUpdates;
+      isBatchingUpdates = !0;
+      try {
+        return fn(a);
+      } finally {
+        (isBatchingUpdates = previousIsBatchingUpdates) ||
+          isRendering ||
+          performSyncWork();
+      }
+    },
+    unbatchedUpdates: function(fn, a) {
+      if (isBatchingUpdates && !isUnbatchingUpdates) {
+        isUnbatchingUpdates = !0;
+        try {
+          return fn(a);
+        } finally {
+          isUnbatchingUpdates = !1;
+        }
+      }
+      return fn(a);
+    },
+    flushSync: function(fn, a) {
+      invariant(
+        !isRendering,
+        "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
+      );
+      var previousIsBatchingUpdates = isBatchingUpdates;
+      isBatchingUpdates = !0;
+      try {
+        return syncUpdates(fn, a);
+      } finally {
+        (isBatchingUpdates = previousIsBatchingUpdates), performSyncWork();
+      }
+    },
+    flushControlled: function(fn) {
+      var previousIsBatchingUpdates = isBatchingUpdates;
+      isBatchingUpdates = !0;
+      try {
+        syncUpdates(fn);
+      } finally {
+        (isBatchingUpdates = previousIsBatchingUpdates) ||
+          isRendering ||
+          performWork(1, !1, null);
+      }
+    },
+    deferredUpdates: function(fn) {
+      var previousExpirationContext = expirationContext;
+      expirationContext =
+        25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
+      try {
+        return fn();
+      } finally {
+        expirationContext = previousExpirationContext;
+      }
+    },
+    syncUpdates: syncUpdates,
+    interactiveUpdates: function(fn, a, b) {
+      if (isBatchingInteractiveUpdates) return fn(a, b);
+      isBatchingUpdates ||
+        isRendering ||
+        0 === lowestPendingInteractiveExpirationTime ||
+        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
+        (lowestPendingInteractiveExpirationTime = 0));
+      var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
+        previousIsBatchingUpdates = isBatchingUpdates;
+      isBatchingUpdates = isBatchingInteractiveUpdates = !0;
+      try {
+        return fn(a, b);
+      } finally {
+        (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
+          (isBatchingUpdates = previousIsBatchingUpdates) ||
+            isRendering ||
+            performSyncWork();
+      }
+    },
+    flushInteractiveUpdates: function() {
+      isRendering ||
+        0 === lowestPendingInteractiveExpirationTime ||
+        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
+        (lowestPendingInteractiveExpirationTime = 0));
+    },
+    computeUniqueAsyncExpiration: function() {
+      var result = 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
+      result <= lastUniqueAsyncExpiration &&
+        (result = lastUniqueAsyncExpiration + 1);
+      return (lastUniqueAsyncExpiration = result);
+    },
+    legacyContext: legacyContext
+  };
+}
+function ReactFiberReconciler$1(config) {
+  function updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    currentTime,
+    expirationTime,
+    callback
+  ) {
+    currentTime = container.current;
+    if (parentComponent) {
+      parentComponent = parentComponent._reactInternalFiber;
+      var parentContext = findCurrentUnmaskedContext(parentComponent);
+      parentComponent = isContextProvider(parentComponent)
+        ? processChildContext(parentComponent, parentContext)
+        : parentContext;
+    } else parentComponent = emptyObject;
+    null === container.context
+      ? (container.context = parentComponent)
+      : (container.pendingContext = parentComponent);
+    container = callback;
+    insertUpdateIntoFiber(currentTime, {
+      expirationTime: expirationTime,
+      partialState: { element: element },
+      callback: void 0 === container ? null : container,
+      isReplace: !1,
+      isForced: !1,
+      capturedValue: null,
+      next: null
+    });
+    scheduleWork(currentTime, expirationTime);
+    return expirationTime;
+  }
+  var getPublicInstance = config.getPublicInstance;
+  config = ReactFiberScheduler(config);
+  var recalculateCurrentTime = config.recalculateCurrentTime,
+    computeExpirationForFiber = config.computeExpirationForFiber,
+    scheduleWork = config.scheduleWork,
+    legacyContext = config.legacyContext,
+    findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
+  return {
+    createContainer: function(containerInfo, isAsync, hydrate) {
+      isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
+      containerInfo = {
+        current: isAsync,
+        containerInfo: containerInfo,
+        pendingChildren: null,
+        pendingCommitExpirationTime: 0,
+        finishedWork: null,
+        context: null,
+        pendingContext: null,
+        hydrate: hydrate,
+        remainingExpirationTime: 0,
+        firstBatch: null,
+        nextScheduledRoot: null
+      };
+      return (isAsync.stateNode = containerInfo);
+    },
+    updateContainer: function(element, container, parentComponent, callback) {
+      var current = container.current,
+        currentTime = recalculateCurrentTime();
+      current = computeExpirationForFiber(current);
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        currentTime,
+        current,
+        callback
+      );
+    },
+    updateContainerAtExpirationTime: function(
+      element,
+      container,
+      parentComponent,
+      expirationTime,
+      callback
+    ) {
+      var currentTime = recalculateCurrentTime();
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        currentTime,
+        expirationTime,
+        callback
+      );
+    },
+    flushRoot: config.flushRoot,
+    requestWork: config.requestWork,
+    computeUniqueAsyncExpiration: config.computeUniqueAsyncExpiration,
+    batchedUpdates: config.batchedUpdates,
+    unbatchedUpdates: config.unbatchedUpdates,
+    deferredUpdates: config.deferredUpdates,
+    syncUpdates: config.syncUpdates,
+    interactiveUpdates: config.interactiveUpdates,
+    flushInteractiveUpdates: config.flushInteractiveUpdates,
+    flushControlled: config.flushControlled,
+    flushSync: config.flushSync,
+    getPublicRootInstance: function(container) {
+      container = container.current;
+      if (!container.child) return null;
+      switch (container.child.tag) {
+        case 5:
+          return getPublicInstance(container.child.stateNode);
+        default:
+          return container.child.stateNode;
+      }
+    },
+    findHostInstance: function(component) {
+      var fiber = component._reactInternalFiber;
+      void 0 === fiber &&
+        ("function" === typeof component.render
+          ? invariant(!1, "Unable to find node on an unmounted component.")
+          : invariant(
+              !1,
+              "Argument appears to not be a ReactComponent. Keys: %s",
+              Object.keys(component)
+            ));
+      component = findCurrentHostFiber(fiber);
+      return null === component ? null : component.stateNode;
+    },
+    findHostInstanceWithNoPortals: function(fiber) {
+      fiber = findCurrentHostFiberWithNoPortals(fiber);
+      return null === fiber ? null : fiber.stateNode;
+    },
+    injectIntoDevTools: function(devToolsConfig) {
+      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+      return injectInternals(
+        Object.assign({}, devToolsConfig, {
+          findHostInstanceByFiber: function(fiber) {
+            fiber = findCurrentHostFiber(fiber);
+            return null === fiber ? null : fiber.stateNode;
+          },
+          findFiberByHostInstance: function(instance) {
+            return findFiberByHostInstance
+              ? findFiberByHostInstance(instance)
+              : null;
+          }
+        })
+      );
+    }
+  };
+}
+var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
+  ReactFiberReconciler$3 =
+    (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
+    ReactFiberReconciler$2,
+  reactReconciler = ReactFiberReconciler$3["default"]
+    ? ReactFiberReconciler$3["default"]
+    : ReactFiberReconciler$3,
+  nextReactTag = 2,
+  ReactFabricHostComponent = (function() {
+    function ReactFabricHostComponent(tag, viewConfig, props) {
+      if (!(this instanceof ReactFabricHostComponent))
+        throw new TypeError("Cannot call a class as a function");
+      this._nativeTag = tag;
+      this.viewConfig = viewConfig;
+      this.currentProps = props;
+    }
+    ReactFabricHostComponent.prototype.blur = function() {
+      TextInputState.blurTextInput(this._nativeTag);
+    };
+    ReactFabricHostComponent.prototype.focus = function() {
+      TextInputState.focusTextInput(this._nativeTag);
+    };
+    ReactFabricHostComponent.prototype.measure = function(callback) {
+      UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+    };
+    ReactFabricHostComponent.prototype.measureInWindow = function(callback) {
+      UIManager.measureInWindow(
+        this._nativeTag,
+        mountSafeCallback(this, callback)
+      );
+    };
+    ReactFabricHostComponent.prototype.measureLayout = function(
+      relativeToNativeNode,
+      onSuccess,
+      onFail
+    ) {
+      UIManager.measureLayout(
+        this._nativeTag,
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
+    ReactFabricHostComponent.prototype.setNativeProps = function(nativeProps) {
+      nativeProps = diffProperties(
+        null,
+        emptyObject$1,
+        nativeProps,
+        this.viewConfig.validAttributes
+      );
+      null != nativeProps &&
+        UIManager.updateView(
+          this._nativeTag,
+          this.viewConfig.uiViewClassName,
+          nativeProps
+        );
+    };
+    return ReactFabricHostComponent;
+  })(),
+  ReactFabricRenderer = reactReconciler({
+    appendInitialChild: function(parentInstance, child) {
+      FabricUIManager.appendChild(parentInstance.node, child.node);
+    },
+    createInstance: function(
+      type,
+      props,
+      rootContainerInstance,
+      hostContext,
+      internalInstanceHandle
+    ) {
+      hostContext = nextReactTag;
+      nextReactTag += 2;
+      type = ReactNativeViewConfigRegistry.get(type);
+      var updatePayload = diffProperties(
+        null,
+        emptyObject$1,
+        props,
+        type.validAttributes
+      );
+      rootContainerInstance = FabricUIManager.createNode(
+        hostContext,
+        type.uiViewClassName,
+        rootContainerInstance,
+        updatePayload,
+        internalInstanceHandle
+      );
+      props = new ReactFabricHostComponent(hostContext, type, props);
+      return { node: rootContainerInstance, canonical: props };
+    },
+    createTextInstance: function(
+      text,
+      rootContainerInstance,
+      hostContext,
+      internalInstanceHandle
+    ) {
+      hostContext = nextReactTag;
+      nextReactTag += 2;
+      return {
+        node: FabricUIManager.createNode(
+          hostContext,
+          "RCTRawText",
+          rootContainerInstance,
+          { text: text },
+          internalInstanceHandle
+        )
+      };
+    },
+    finalizeInitialChildren: function() {
+      return !1;
+    },
+    getRootHostContext: function() {
+      return emptyObject;
+    },
+    getChildHostContext: function() {
+      return emptyObject;
+    },
+    getPublicInstance: function(instance) {
+      return instance.canonical;
+    },
+    now: now,
+    prepareForCommit: function() {},
+    prepareUpdate: function(instance, type, oldProps, newProps) {
+      return diffProperties(
+        null,
+        oldProps,
+        newProps,
+        instance.canonical.viewConfig.validAttributes
+      );
+    },
+    resetAfterCommit: function() {},
+    scheduleDeferredCallback: function(callback) {
+      scheduledCallback = callback;
+      return setTimeout(setTimeoutCallback, 1);
+    },
+    cancelDeferredCallback: function(callbackID) {
+      scheduledCallback = null;
+      clearTimeout(callbackID);
+    },
+    shouldDeprioritizeSubtree: function() {
+      return !1;
+    },
+    shouldSetTextContent: function() {
+      return !1;
+    },
+    persistence: {
+      cloneInstance: function(
+        instance,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        internalInstanceHandle,
+        keepChildren
+      ) {
+        type = instance.node;
+        return {
+          node: keepChildren
+            ? null !== updatePayload
+              ? FabricUIManager.cloneNodeWithNewProps(type, updatePayload)
+              : FabricUIManager.cloneNode(type)
+            : null !== updatePayload
+              ? FabricUIManager.cloneNodeWithNewChildrenAndProps(
+                  type,
+                  updatePayload
+                )
+              : FabricUIManager.cloneNodeWithNewChildren(type),
+          canonical: instance.canonical
+        };
+      },
+      createContainerChildSet: function(container) {
+        return FabricUIManager.createChildSet(container);
+      },
+      appendChildToContainerChildSet: function(childSet, child) {
+        FabricUIManager.appendChildToSet(childSet, child.node);
+      },
+      finalizeContainerChildren: function(container, newChildren) {
+        FabricUIManager.completeRoot(container, newChildren);
+      },
+      replaceContainerChildren: function() {}
+    }
+  }),
+  getInspectorDataForViewTag = void 0;
+getInspectorDataForViewTag = function() {
+  invariant(!1, "getInspectorDataForViewTag() is not available in production");
+};
+var findHostInstance = ReactFabricRenderer.findHostInstance;
+function findNodeHandle(componentOrHandle) {
+  if (null == componentOrHandle) return null;
+  if ("number" === typeof componentOrHandle) return componentOrHandle;
+  if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
+    return componentOrHandle.canonical._nativeTag;
+  componentOrHandle = findHostInstance(componentOrHandle);
+  return null == componentOrHandle
+    ? componentOrHandle
+    : componentOrHandle.canonical
+      ? componentOrHandle.canonical._nativeTag
+      : componentOrHandle._nativeTag;
+}
+var roots = new Map(),
+  ReactFabric = {
+    NativeComponent: (function(findNodeHandle, findHostInstance) {
+      return (function(_React$Component) {
+        function ReactNativeComponent() {
+          if (!(this instanceof ReactNativeComponent))
+            throw new TypeError("Cannot call a class as a function");
+          var call = _React$Component.apply(this, arguments);
+          if (!this)
+            throw new ReferenceError(
+              "this hasn't been initialised - super() hasn't been called"
+            );
+          return !call ||
+            ("object" !== typeof call && "function" !== typeof call)
+            ? this
+            : call;
+        }
+        _inherits(ReactNativeComponent, _React$Component);
+        ReactNativeComponent.prototype.blur = function() {
+          TextInputState.blurTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.focus = function() {
+          TextInputState.focusTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.measure = function(callback) {
+          UIManager.measure(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureInWindow = function(callback) {
+          UIManager.measureInWindow(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureLayout = function(
+          relativeToNativeNode,
+          onSuccess,
+          onFail
+        ) {
+          UIManager.measureLayout(
+            findNodeHandle(this),
+            relativeToNativeNode,
+            mountSafeCallback(this, onFail),
+            mountSafeCallback(this, onSuccess)
+          );
+        };
+        ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
+          var maybeInstance = void 0;
+          try {
+            maybeInstance = findHostInstance(this);
+          } catch (error) {}
+          if (null != maybeInstance) {
+            var viewConfig =
+              maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+            nativeProps = diffProperties(
+              null,
+              emptyObject$1,
+              nativeProps,
+              viewConfig.validAttributes
+            );
+            null != nativeProps &&
+              UIManager.updateView(
+                maybeInstance._nativeTag,
+                viewConfig.uiViewClassName,
+                nativeProps
+              );
+          }
+        };
+        return ReactNativeComponent;
+      })(React.Component);
+    })(findNodeHandle, findHostInstance),
+    findNodeHandle: findNodeHandle,
+    render: function(element, containerTag, callback) {
+      var root = roots.get(containerTag);
+      root ||
+        ((root = ReactFabricRenderer.createContainer(containerTag, !1, !1)),
+        roots.set(containerTag, root));
+      ReactFabricRenderer.updateContainer(element, root, null, callback);
+      return ReactFabricRenderer.getPublicRootInstance(root);
+    },
+    unmountComponentAtNode: function(containerTag) {
+      var root = roots.get(containerTag);
+      root &&
+        ReactFabricRenderer.updateContainer(null, root, null, function() {
+          roots["delete"](containerTag);
+        });
+    },
+    createPortal: function(children, containerTag) {
+      return createPortal(
+        children,
+        containerTag,
+        null,
+        2 < arguments.length && void 0 !== arguments[2] ? arguments[2] : null
+      );
+    },
+    __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
+      NativeMethodsMixin: (function(findNodeHandle, findHostInstance) {
+        return {
+          measure: function(callback) {
+            UIManager.measure(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureInWindow: function(callback) {
+            UIManager.measureInWindow(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
+            UIManager.measureLayout(
+              findNodeHandle(this),
+              relativeToNativeNode,
+              mountSafeCallback(this, onFail),
+              mountSafeCallback(this, onSuccess)
+            );
+          },
+          setNativeProps: function(nativeProps) {
+            var maybeInstance = void 0;
+            try {
+              maybeInstance = findHostInstance(this);
+            } catch (error) {}
+            if (null != maybeInstance) {
+              var viewConfig = maybeInstance.viewConfig;
+              nativeProps = diffProperties(
+                null,
+                emptyObject$1,
+                nativeProps,
+                viewConfig.validAttributes
+              );
+              null != nativeProps &&
+                UIManager.updateView(
+                  maybeInstance._nativeTag,
+                  viewConfig.uiViewClassName,
+                  nativeProps
+                );
+            }
+          },
+          focus: function() {
+            TextInputState.focusTextInput(findNodeHandle(this));
+          },
+          blur: function() {
+            TextInputState.blurTextInput(findNodeHandle(this));
+          }
+        };
+      })(findNodeHandle, findHostInstance),
+      ReactNativeComponentTree: ReactNativeComponentTree
+    }
+  };
+ReactFabricRenderer.injectIntoDevTools({
+  findFiberByHostInstance: getInstanceFromTag,
+  getInspectorDataForViewTag: getInspectorDataForViewTag,
+  bundleType: 0,
+  version: "16.3.2",
+  rendererPackageName: "react-native-renderer"
+});
+var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
+  ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
+module.exports = ReactFabric$3["default"]
+  ? ReactFabric$3["default"]
+  : ReactFabric$3;
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
new file mode 100644
index 000000000000..9e14a0c266e9
--- /dev/null
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
@@ -0,0 +1,14432 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @noflow
+ * @providesModule ReactNativeRenderer-dev
+ * @preventMunge
+ */
+
+'use strict';
+
+if (__DEV__) {
+  (function() {
+"use strict";
+
+require("InitializeCore");
+var invariant = require("fbjs/lib/invariant");
+var warning = require("fbjs/lib/warning");
+var emptyFunction = require("fbjs/lib/emptyFunction");
+var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
+var UIManager = require("UIManager");
+var RCTEventEmitter = require("RCTEventEmitter");
+var TextInputState = require("TextInputState");
+var deepDiffer = require("deepDiffer");
+var flattenStyle = require("flattenStyle");
+var React = require("react");
+var emptyObject = require("fbjs/lib/emptyObject");
+var shallowEqual = require("fbjs/lib/shallowEqual");
+var ExceptionsManager = require("ExceptionsManager");
+var checkPropTypes = require("prop-types/checkPropTypes");
+var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
+
+var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
+  this._hasCaughtError = false;
+  this._caughtError = null;
+  var funcArgs = Array.prototype.slice.call(arguments, 3);
+  try {
+    func.apply(context, funcArgs);
+  } catch (error) {
+    this._caughtError = error;
+    this._hasCaughtError = true;
+  }
+};
+
+{
+  // In DEV mode, we swap out invokeGuardedCallback for a special version
+  // that plays more nicely with the browser's DevTools. The idea is to preserve
+  // "Pause on exceptions" behavior. Because React wraps all user-provided
+  // functions in invokeGuardedCallback, and the production version of
+  // invokeGuardedCallback uses a try-catch, all user exceptions are treated
+  // like caught exceptions, and the DevTools won't pause unless the developer
+  // takes the extra step of enabling pause on caught exceptions. This is
+  // untintuitive, though, because even though React has caught the error, from
+  // the developer's perspective, the error is uncaught.
+  //
+  // To preserve the expected "Pause on exceptions" behavior, we don't use a
+  // try-catch in DEV. Instead, we synchronously dispatch a fake event to a fake
+  // DOM node, and call the user-provided callback from inside an event handler
+  // for that fake event. If the callback throws, the error is "captured" using
+  // a global event handler. But because the error happens in a different
+  // event loop context, it does not interrupt the normal program flow.
+  // Effectively, this gives us try-catch behavior without actually using
+  // try-catch. Neat!
+
+  // Check that the browser supports the APIs we need to implement our special
+  // DEV version of invokeGuardedCallback
+  if (
+    typeof window !== "undefined" &&
+    typeof window.dispatchEvent === "function" &&
+    typeof document !== "undefined" &&
+    typeof document.createEvent === "function"
+  ) {
+    var fakeNode = document.createElement("react");
+
+    var invokeGuardedCallbackDev = function(
+      name,
+      func,
+      context,
+      a,
+      b,
+      c,
+      d,
+      e,
+      f
+    ) {
+      // If document doesn't exist we know for sure we will crash in this method
+      // when we call document.createEvent(). However this can cause confusing
+      // errors: https://github.com/facebookincubator/create-react-app/issues/3482
+      // So we preemptively throw with a better message instead.
+      invariant(
+        typeof document !== "undefined",
+        "The `document` global was defined when React was initialized, but is not " +
+          "defined anymore. This can happen in a test environment if a component " +
+          "schedules an update from an asynchronous callback, but the test has already " +
+          "finished running. To solve this, you can either unmount the component at " +
+          "the end of your test (and ensure that any asynchronous operations get " +
+          "canceled in `componentWillUnmount`), or you can change the test itself " +
+          "to be asynchronous."
+      );
+      var evt = document.createEvent("Event");
+
+      // Keeps track of whether the user-provided callback threw an error. We
+      // set this to true at the beginning, then set it to false right after
+      // calling the function. If the function errors, `didError` will never be
+      // set to false. This strategy works even if the browser is flaky and
+      // fails to call our global error handler, because it doesn't rely on
+      // the error event at all.
+      var didError = true;
+
+      // Create an event handler for our fake event. We will synchronously
+      // dispatch our fake event using `dispatchEvent`. Inside the handler, we
+      // call the user-provided callback.
+      var funcArgs = Array.prototype.slice.call(arguments, 3);
+      function callCallback() {
+        // We immediately remove the callback from event listeners so that
+        // nested `invokeGuardedCallback` calls do not clash. Otherwise, a
+        // nested call would trigger the fake event handlers of any call higher
+        // in the stack.
+        fakeNode.removeEventListener(evtType, callCallback, false);
+        func.apply(context, funcArgs);
+        didError = false;
+      }
+
+      // Create a global error event handler. We use this to capture the value
+      // that was thrown. It's possible that this error handler will fire more
+      // than once; for example, if non-React code also calls `dispatchEvent`
+      // and a handler for that event throws. We should be resilient to most of
+      // those cases. Even if our error event handler fires more than once, the
+      // last error event is always used. If the callback actually does error,
+      // we know that the last error event is the correct one, because it's not
+      // possible for anything else to have happened in between our callback
+      // erroring and the code that follows the `dispatchEvent` call below. If
+      // the callback doesn't error, but the error event was fired, we know to
+      // ignore it because `didError` will be false, as described above.
+      var error = void 0;
+      // Use this to track whether the error event is ever called.
+      var didSetError = false;
+      var isCrossOriginError = false;
+
+      function onError(event) {
+        error = event.error;
+        didSetError = true;
+        if (error === null && event.colno === 0 && event.lineno === 0) {
+          isCrossOriginError = true;
+        }
+      }
+
+      // Create a fake event type.
+      var evtType = "react-" + (name ? name : "invokeguardedcallback");
+
+      // Attach our event handlers
+      window.addEventListener("error", onError);
+      fakeNode.addEventListener(evtType, callCallback, false);
+
+      // Synchronously dispatch our fake event. If the user-provided function
+      // errors, it will trigger our global error handler.
+      evt.initEvent(evtType, false, false);
+      fakeNode.dispatchEvent(evt);
+
+      if (didError) {
+        if (!didSetError) {
+          // The callback errored, but the error event never fired.
+          error = new Error(
+            "An error was thrown inside one of your components, but React " +
+              "doesn't know what it was. This is likely due to browser " +
+              'flakiness. React does its best to preserve the "Pause on ' +
+              'exceptions" behavior of the DevTools, which requires some ' +
+              "DEV-mode only tricks. It's possible that these don't work in " +
+              "your browser. Try triggering the error in production mode, " +
+              "or switching to a modern browser. If you suspect that this is " +
+              "actually an issue with React, please file an issue."
+          );
+        } else if (isCrossOriginError) {
+          error = new Error(
+            "A cross-origin error was thrown. React doesn't have access to " +
+              "the actual error object in development. " +
+              "See https://fb.me/react-crossorigin-error for more information."
+          );
+        }
+        this._hasCaughtError = true;
+        this._caughtError = error;
+      } else {
+        this._hasCaughtError = false;
+        this._caughtError = null;
+      }
+
+      // Remove our event listeners
+      window.removeEventListener("error", onError);
+    };
+
+    invokeGuardedCallback = invokeGuardedCallbackDev;
+  }
+}
+
+var invokeGuardedCallback$1 = invokeGuardedCallback;
+
+var ReactErrorUtils = {
+  // Used by Fiber to simulate a try-catch.
+  _caughtError: null,
+  _hasCaughtError: false,
+
+  // Used by event system to capture/rethrow the first error.
+  _rethrowError: null,
+  _hasRethrowError: false,
+
+  /**
+   * Call a function while guarding against errors that happens within it.
+   * Returns an error if it throws, otherwise null.
+   *
+   * In production, this is implemented using a try-catch. The reason we don't
+   * use a try-catch directly is so that we can swap out a different
+   * implementation in DEV mode.
+   *
+   * @param {String} name of the guard to use for logging or debugging
+   * @param {Function} func The function to invoke
+   * @param {*} context The context to use when calling the function
+   * @param {...*} args Arguments for function
+   */
+  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
+    invokeGuardedCallback$1.apply(ReactErrorUtils, arguments);
+  },
+
+  /**
+   * Same as invokeGuardedCallback, but instead of returning an error, it stores
+   * it in a global so it can be rethrown by `rethrowCaughtError` later.
+   * TODO: See if _caughtError and _rethrowError can be unified.
+   *
+   * @param {String} name of the guard to use for logging or debugging
+   * @param {Function} func The function to invoke
+   * @param {*} context The context to use when calling the function
+   * @param {...*} args Arguments for function
+   */
+  invokeGuardedCallbackAndCatchFirstError: function(
+    name,
+    func,
+    context,
+    a,
+    b,
+    c,
+    d,
+    e,
+    f
+  ) {
+    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
+    if (ReactErrorUtils.hasCaughtError()) {
+      var error = ReactErrorUtils.clearCaughtError();
+      if (!ReactErrorUtils._hasRethrowError) {
+        ReactErrorUtils._hasRethrowError = true;
+        ReactErrorUtils._rethrowError = error;
+      }
+    }
+  },
+
+  /**
+   * During execution of guarded functions we will capture the first error which
+   * we will rethrow to be handled by the top level error handler.
+   */
+  rethrowCaughtError: function() {
+    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
+  },
+
+  hasCaughtError: function() {
+    return ReactErrorUtils._hasCaughtError;
+  },
+
+  clearCaughtError: function() {
+    if (ReactErrorUtils._hasCaughtError) {
+      var error = ReactErrorUtils._caughtError;
+      ReactErrorUtils._caughtError = null;
+      ReactErrorUtils._hasCaughtError = false;
+      return error;
+    } else {
+      invariant(
+        false,
+        "clearCaughtError was called but no error was captured. This error " +
+          "is likely caused by a bug in React. Please file an issue."
+      );
+    }
+  }
+};
+
+var rethrowCaughtError = function() {
+  if (ReactErrorUtils._hasRethrowError) {
+    var error = ReactErrorUtils._rethrowError;
+    ReactErrorUtils._rethrowError = null;
+    ReactErrorUtils._hasRethrowError = false;
+    throw error;
+  }
+};
+
+/**
+ * Injectable ordering of event plugins.
+ */
+var eventPluginOrder = null;
+
+/**
+ * Injectable mapping from names to event plugin modules.
+ */
+var namesToPlugins = {};
+
+/**
+ * Recomputes the plugin list using the injected plugins and plugin ordering.
+ *
+ * @private
+ */
+function recomputePluginOrdering() {
+  if (!eventPluginOrder) {
+    // Wait until an `eventPluginOrder` is injected.
+    return;
+  }
+  for (var pluginName in namesToPlugins) {
+    var pluginModule = namesToPlugins[pluginName];
+    var pluginIndex = eventPluginOrder.indexOf(pluginName);
+    invariant(
+      pluginIndex > -1,
+      "EventPluginRegistry: Cannot inject event plugins that do not exist in " +
+        "the plugin ordering, `%s`.",
+      pluginName
+    );
+    if (plugins[pluginIndex]) {
+      continue;
+    }
+    invariant(
+      pluginModule.extractEvents,
+      "EventPluginRegistry: Event plugins must implement an `extractEvents` " +
+        "method, but `%s` does not.",
+      pluginName
+    );
+    plugins[pluginIndex] = pluginModule;
+    var publishedEvents = pluginModule.eventTypes;
+    for (var eventName in publishedEvents) {
+      invariant(
+        publishEventForPlugin(
+          publishedEvents[eventName],
+          pluginModule,
+          eventName
+        ),
+        "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
+        eventName,
+        pluginName
+      );
+    }
+  }
+}
+
+/**
+ * Publishes an event so that it can be dispatched by the supplied plugin.
+ *
+ * @param {object} dispatchConfig Dispatch configuration for the event.
+ * @param {object} PluginModule Plugin publishing the event.
+ * @return {boolean} True if the event was successfully published.
+ * @private
+ */
+function publishEventForPlugin(dispatchConfig, pluginModule, eventName) {
+  invariant(
+    !eventNameDispatchConfigs.hasOwnProperty(eventName),
+    "EventPluginHub: More than one plugin attempted to publish the same " +
+      "event name, `%s`.",
+    eventName
+  );
+  eventNameDispatchConfigs[eventName] = dispatchConfig;
+
+  var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
+  if (phasedRegistrationNames) {
+    for (var phaseName in phasedRegistrationNames) {
+      if (phasedRegistrationNames.hasOwnProperty(phaseName)) {
+        var phasedRegistrationName = phasedRegistrationNames[phaseName];
+        publishRegistrationName(
+          phasedRegistrationName,
+          pluginModule,
+          eventName
+        );
+      }
+    }
+    return true;
+  } else if (dispatchConfig.registrationName) {
+    publishRegistrationName(
+      dispatchConfig.registrationName,
+      pluginModule,
+      eventName
+    );
+    return true;
+  }
+  return false;
+}
+
+/**
+ * Publishes a registration name that is used to identify dispatched events.
+ *
+ * @param {string} registrationName Registration name to add.
+ * @param {object} PluginModule Plugin publishing the event.
+ * @private
+ */
+function publishRegistrationName(registrationName, pluginModule, eventName) {
+  invariant(
+    !registrationNameModules[registrationName],
+    "EventPluginHub: More than one plugin attempted to publish the same " +
+      "registration name, `%s`.",
+    registrationName
+  );
+  registrationNameModules[registrationName] = pluginModule;
+  registrationNameDependencies[registrationName] =
+    pluginModule.eventTypes[eventName].dependencies;
+
+  {
+    var lowerCasedName = registrationName.toLowerCase();
+  }
+}
+
+/**
+ * Registers plugins so that they can extract and dispatch events.
+ *
+ * @see {EventPluginHub}
+ */
+
+/**
+ * Ordered list of injected plugins.
+ */
+var plugins = [];
+
+/**
+ * Mapping from event name to dispatch config
+ */
+var eventNameDispatchConfigs = {};
+
+/**
+ * Mapping from registration name to plugin module
+ */
+var registrationNameModules = {};
+
+/**
+ * Mapping from registration name to event name
+ */
+var registrationNameDependencies = {};
+
+/**
+ * Mapping from lowercase registration names to the properly cased version,
+ * used to warn in the case of missing event handlers. Available
+ * only in true.
+ * @type {Object}
+ */
+
+// Trust the developer to only use possibleRegistrationNames in true
+
+/**
+ * Injects an ordering of plugins (by plugin name). This allows the ordering
+ * to be decoupled from injection of the actual plugins so that ordering is
+ * always deterministic regardless of packaging, on-the-fly injection, etc.
+ *
+ * @param {array} InjectedEventPluginOrder
+ * @internal
+ * @see {EventPluginHub.injection.injectEventPluginOrder}
+ */
+function injectEventPluginOrder(injectedEventPluginOrder) {
+  invariant(
+    !eventPluginOrder,
+    "EventPluginRegistry: Cannot inject event plugin ordering more than " +
+      "once. You are likely trying to load more than one copy of React."
+  );
+  // Clone the ordering so it cannot be dynamically mutated.
+  eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
+  recomputePluginOrdering();
+}
+
+/**
+ * Injects plugins to be used by `EventPluginHub`. The plugin names must be
+ * in the ordering injected by `injectEventPluginOrder`.
+ *
+ * Plugins can be injected as part of page initialization or on-the-fly.
+ *
+ * @param {object} injectedNamesToPlugins Map from names to plugin modules.
+ * @internal
+ * @see {EventPluginHub.injection.injectEventPluginsByName}
+ */
+function injectEventPluginsByName(injectedNamesToPlugins) {
+  var isOrderingDirty = false;
+  for (var pluginName in injectedNamesToPlugins) {
+    if (!injectedNamesToPlugins.hasOwnProperty(pluginName)) {
+      continue;
+    }
+    var pluginModule = injectedNamesToPlugins[pluginName];
+    if (
+      !namesToPlugins.hasOwnProperty(pluginName) ||
+      namesToPlugins[pluginName] !== pluginModule
+    ) {
+      invariant(
+        !namesToPlugins[pluginName],
+        "EventPluginRegistry: Cannot inject two different event plugins " +
+          "using the same name, `%s`.",
+        pluginName
+      );
+      namesToPlugins[pluginName] = pluginModule;
+      isOrderingDirty = true;
+    }
+  }
+  if (isOrderingDirty) {
+    recomputePluginOrdering();
+  }
+}
+
+var getFiberCurrentPropsFromNode = null;
+var getInstanceFromNode = null;
+var getNodeFromInstance = null;
+
+var injection$1 = {
+  injectComponentTree: function(Injected) {
+    getFiberCurrentPropsFromNode = Injected.getFiberCurrentPropsFromNode;
+    getInstanceFromNode = Injected.getInstanceFromNode;
+    getNodeFromInstance = Injected.getNodeFromInstance;
+
+    {
+      !(getNodeFromInstance && getInstanceFromNode)
+        ? warning(
+            false,
+            "EventPluginUtils.injection.injectComponentTree(...): Injected " +
+              "module is missing getNodeFromInstance or getInstanceFromNode."
+          )
+        : void 0;
+    }
+  }
+};
+
+function isEndish(topLevelType) {
+  return (
+    topLevelType === "topMouseUp" ||
+    topLevelType === "topTouchEnd" ||
+    topLevelType === "topTouchCancel"
+  );
+}
+
+function isMoveish(topLevelType) {
+  return topLevelType === "topMouseMove" || topLevelType === "topTouchMove";
+}
+function isStartish(topLevelType) {
+  return topLevelType === "topMouseDown" || topLevelType === "topTouchStart";
+}
+
+var validateEventDispatches = void 0;
+{
+  validateEventDispatches = function(event) {
+    var dispatchListeners = event._dispatchListeners;
+    var dispatchInstances = event._dispatchInstances;
+
+    var listenersIsArr = Array.isArray(dispatchListeners);
+    var listenersLen = listenersIsArr
+      ? dispatchListeners.length
+      : dispatchListeners ? 1 : 0;
+
+    var instancesIsArr = Array.isArray(dispatchInstances);
+    var instancesLen = instancesIsArr
+      ? dispatchInstances.length
+      : dispatchInstances ? 1 : 0;
+
+    !(instancesIsArr === listenersIsArr && instancesLen === listenersLen)
+      ? warning(false, "EventPluginUtils: Invalid `event`.")
+      : void 0;
+  };
+}
+
+/**
+ * Dispatch the event to the listener.
+ * @param {SyntheticEvent} event SyntheticEvent to handle
+ * @param {boolean} simulated If the event is simulated (changes exn behavior)
+ * @param {function} listener Application-level callback
+ * @param {*} inst Internal component instance
+ */
+function executeDispatch(event, simulated, listener, inst) {
+  var type = event.type || "unknown-event";
+  event.currentTarget = getNodeFromInstance(inst);
+  ReactErrorUtils.invokeGuardedCallbackAndCatchFirstError(
+    type,
+    listener,
+    undefined,
+    event
+  );
+  event.currentTarget = null;
+}
+
+/**
+ * Standard/simple iteration through an event's collected dispatches.
+ */
+function executeDispatchesInOrder(event, simulated) {
+  var dispatchListeners = event._dispatchListeners;
+  var dispatchInstances = event._dispatchInstances;
+  {
+    validateEventDispatches(event);
+  }
+  if (Array.isArray(dispatchListeners)) {
+    for (var i = 0; i < dispatchListeners.length; i++) {
+      if (event.isPropagationStopped()) {
+        break;
+      }
+      // Listeners and Instances are two parallel arrays that are always in sync.
+      executeDispatch(
+        event,
+        simulated,
+        dispatchListeners[i],
+        dispatchInstances[i]
+      );
+    }
+  } else if (dispatchListeners) {
+    executeDispatch(event, simulated, dispatchListeners, dispatchInstances);
+  }
+  event._dispatchListeners = null;
+  event._dispatchInstances = null;
+}
+
+/**
+ * Standard/simple iteration through an event's collected dispatches, but stops
+ * at the first dispatch execution returning true, and returns that id.
+ *
+ * @return {?string} id of the first dispatch execution who's listener returns
+ * true, or null if no listener returned true.
+ */
+function executeDispatchesInOrderStopAtTrueImpl(event) {
+  var dispatchListeners = event._dispatchListeners;
+  var dispatchInstances = event._dispatchInstances;
+  {
+    validateEventDispatches(event);
+  }
+  if (Array.isArray(dispatchListeners)) {
+    for (var i = 0; i < dispatchListeners.length; i++) {
+      if (event.isPropagationStopped()) {
+        break;
+      }
+      // Listeners and Instances are two parallel arrays that are always in sync.
+      if (dispatchListeners[i](event, dispatchInstances[i])) {
+        return dispatchInstances[i];
+      }
+    }
+  } else if (dispatchListeners) {
+    if (dispatchListeners(event, dispatchInstances)) {
+      return dispatchInstances;
+    }
+  }
+  return null;
+}
+
+/**
+ * @see executeDispatchesInOrderStopAtTrueImpl
+ */
+function executeDispatchesInOrderStopAtTrue(event) {
+  var ret = executeDispatchesInOrderStopAtTrueImpl(event);
+  event._dispatchInstances = null;
+  event._dispatchListeners = null;
+  return ret;
+}
+
+/**
+ * Execution of a "direct" dispatch - there must be at most one dispatch
+ * accumulated on the event or it is considered an error. It doesn't really make
+ * sense for an event with multiple dispatches (bubbled) to keep track of the
+ * return values at each dispatch execution, but it does tend to make sense when
+ * dealing with "direct" dispatches.
+ *
+ * @return {*} The return value of executing the single dispatch.
+ */
+function executeDirectDispatch(event) {
+  {
+    validateEventDispatches(event);
+  }
+  var dispatchListener = event._dispatchListeners;
+  var dispatchInstance = event._dispatchInstances;
+  invariant(
+    !Array.isArray(dispatchListener),
+    "executeDirectDispatch(...): Invalid `event`."
+  );
+  event.currentTarget = dispatchListener
+    ? getNodeFromInstance(dispatchInstance)
+    : null;
+  var res = dispatchListener ? dispatchListener(event) : null;
+  event.currentTarget = null;
+  event._dispatchListeners = null;
+  event._dispatchInstances = null;
+  return res;
+}
+
+/**
+ * @param {SyntheticEvent} event
+ * @return {boolean} True iff number of dispatches accumulated is greater than 0.
+ */
+function hasDispatches(event) {
+  return !!event._dispatchListeners;
+}
+
+/**
+ * Accumulates items that must not be null or undefined into the first one. This
+ * is used to conserve memory by avoiding array allocations, and thus sacrifices
+ * API cleanness. Since `current` can be null before being passed in and not
+ * null after this function, make sure to assign it back to `current`:
+ *
+ * `a = accumulateInto(a, b);`
+ *
+ * This API should be sparingly used. Try `accumulate` for something cleaner.
+ *
+ * @return {*|array<*>} An accumulation of items.
+ */
+
+function accumulateInto(current, next) {
+  invariant(
+    next != null,
+    "accumulateInto(...): Accumulated items must not be null or undefined."
+  );
+
+  if (current == null) {
+    return next;
+  }
+
+  // Both are not empty. Warning: Never call x.concat(y) when you are not
+  // certain that x is an Array (x could be a string with concat method).
+  if (Array.isArray(current)) {
+    if (Array.isArray(next)) {
+      current.push.apply(current, next);
+      return current;
+    }
+    current.push(next);
+    return current;
+  }
+
+  if (Array.isArray(next)) {
+    // A bit too dangerous to mutate `next`.
+    return [current].concat(next);
+  }
+
+  return [current, next];
+}
+
+/**
+ * @param {array} arr an "accumulation" of items which is either an Array or
+ * a single item. Useful when paired with the `accumulate` module. This is a
+ * simple utility that allows us to reason about a collection of items, but
+ * handling the case when there is exactly one item (and we do not need to
+ * allocate an array).
+ * @param {function} cb Callback invoked with each element or a collection.
+ * @param {?} [scope] Scope used as `this` in a callback.
+ */
+function forEachAccumulated(arr, cb, scope) {
+  if (Array.isArray(arr)) {
+    arr.forEach(cb, scope);
+  } else if (arr) {
+    cb.call(scope, arr);
+  }
+}
+
+/**
+ * Internal queue of events that have accumulated their dispatches and are
+ * waiting to have their dispatches executed.
+ */
+var eventQueue = null;
+
+/**
+ * Dispatches an event and releases it back into the pool, unless persistent.
+ *
+ * @param {?object} event Synthetic event to be dispatched.
+ * @param {boolean} simulated If the event is simulated (changes exn behavior)
+ * @private
+ */
+var executeDispatchesAndRelease = function(event, simulated) {
+  if (event) {
+    executeDispatchesInOrder(event, simulated);
+
+    if (!event.isPersistent()) {
+      event.constructor.release(event);
+    }
+  }
+};
+var executeDispatchesAndReleaseSimulated = function(e) {
+  return executeDispatchesAndRelease(e, true);
+};
+var executeDispatchesAndReleaseTopLevel = function(e) {
+  return executeDispatchesAndRelease(e, false);
+};
+
+function isInteractive(tag) {
+  return (
+    tag === "button" ||
+    tag === "input" ||
+    tag === "select" ||
+    tag === "textarea"
+  );
+}
+
+function shouldPreventMouseEvent(name, type, props) {
+  switch (name) {
+    case "onClick":
+    case "onClickCapture":
+    case "onDoubleClick":
+    case "onDoubleClickCapture":
+    case "onMouseDown":
+    case "onMouseDownCapture":
+    case "onMouseMove":
+    case "onMouseMoveCapture":
+    case "onMouseUp":
+    case "onMouseUpCapture":
+      return !!(props.disabled && isInteractive(type));
+    default:
+      return false;
+  }
+}
+
+/**
+ * This is a unified interface for event plugins to be installed and configured.
+ *
+ * Event plugins can implement the following properties:
+ *
+ *   `extractEvents` {function(string, DOMEventTarget, string, object): *}
+ *     Required. When a top-level event is fired, this method is expected to
+ *     extract synthetic events that will in turn be queued and dispatched.
+ *
+ *   `eventTypes` {object}
+ *     Optional, plugins that fire events must publish a mapping of registration
+ *     names that are used to register listeners. Values of this mapping must
+ *     be objects that contain `registrationName` or `phasedRegistrationNames`.
+ *
+ *   `executeDispatch` {function(object, function, string)}
+ *     Optional, allows plugins to override how an event gets dispatched. By
+ *     default, the listener is simply invoked.
+ *
+ * Each plugin that is injected into `EventsPluginHub` is immediately operable.
+ *
+ * @public
+ */
+
+/**
+ * Methods for injecting dependencies.
+ */
+var injection = {
+  /**
+   * @param {array} InjectedEventPluginOrder
+   * @public
+   */
+  injectEventPluginOrder: injectEventPluginOrder,
+
+  /**
+   * @param {object} injectedNamesToPlugins Map from names to plugin modules.
+   */
+  injectEventPluginsByName: injectEventPluginsByName
+};
+
+/**
+ * @param {object} inst The instance, which is the source of events.
+ * @param {string} registrationName Name of listener (e.g. `onClick`).
+ * @return {?function} The stored callback.
+ */
+function getListener(inst, registrationName) {
+  var listener = void 0;
+
+  // TODO: shouldPreventMouseEvent is DOM-specific and definitely should not
+  // live here; needs to be moved to a better place soon
+  var stateNode = inst.stateNode;
+  if (!stateNode) {
+    // Work in progress (ex: onload events in incremental mode).
+    return null;
+  }
+  var props = getFiberCurrentPropsFromNode(stateNode);
+  if (!props) {
+    // Work in progress.
+    return null;
+  }
+  listener = props[registrationName];
+  if (shouldPreventMouseEvent(registrationName, inst.type, props)) {
+    return null;
+  }
+  invariant(
+    !listener || typeof listener === "function",
+    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
+    registrationName,
+    typeof listener
+  );
+  return listener;
+}
+
+/**
+ * Allows registered plugins an opportunity to extract events from top-level
+ * native browser events.
+ *
+ * @return {*} An accumulation of synthetic events.
+ * @internal
+ */
+function extractEvents(
+  topLevelType,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  var events = null;
+  for (var i = 0; i < plugins.length; i++) {
+    // Not every plugin in the ordering may be loaded at runtime.
+    var possiblePlugin = plugins[i];
+    if (possiblePlugin) {
+      var extractedEvents = possiblePlugin.extractEvents(
+        topLevelType,
+        targetInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      if (extractedEvents) {
+        events = accumulateInto(events, extractedEvents);
+      }
+    }
+  }
+  return events;
+}
+
+function runEventsInBatch(events, simulated) {
+  if (events !== null) {
+    eventQueue = accumulateInto(eventQueue, events);
+  }
+
+  // Set `eventQueue` to null before processing it so that we can tell if more
+  // events get enqueued while processing.
+  var processingEventQueue = eventQueue;
+  eventQueue = null;
+
+  if (!processingEventQueue) {
+    return;
+  }
+
+  if (simulated) {
+    forEachAccumulated(
+      processingEventQueue,
+      executeDispatchesAndReleaseSimulated
+    );
+  } else {
+    forEachAccumulated(
+      processingEventQueue,
+      executeDispatchesAndReleaseTopLevel
+    );
+  }
+  invariant(
+    !eventQueue,
+    "processEventQueue(): Additional events were enqueued while processing " +
+      "an event queue. Support for this has not yet been implemented."
+  );
+  // This would be a good time to rethrow if any of the event handlers threw.
+  ReactErrorUtils.rethrowCaughtError();
+}
+
+function runExtractedEventsInBatch(
+  topLevelType,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  var events = extractEvents(
+    topLevelType,
+    targetInst,
+    nativeEvent,
+    nativeEventTarget
+  );
+  runEventsInBatch(events, false);
+}
+
+var IndeterminateComponent = 0; // Before we know whether it is functional or class
+var FunctionalComponent = 1;
+var ClassComponent = 2;
+var HostRoot = 3; // Root of a host tree. Could be nested inside another node.
+var HostPortal = 4; // A subtree. Could be an entry point to a different renderer.
+var HostComponent = 5;
+var HostText = 6;
+var CallComponent = 7;
+var CallHandlerPhase = 8;
+var ReturnComponent = 9;
+var Fragment = 10;
+var Mode = 11;
+var ContextConsumer = 12;
+var ContextProvider = 13;
+var ForwardRef = 14;
+
+function getParent(inst) {
+  do {
+    inst = inst["return"];
+    // TODO: If this is a HostRoot we might want to bail out.
+    // That is depending on if we want nested subtrees (layers) to bubble
+    // events to their parent. We could also go through parentNode on the
+    // host node but that wouldn't work for React Native and doesn't let us
+    // do the portal feature.
+  } while (inst && inst.tag !== HostComponent);
+  if (inst) {
+    return inst;
+  }
+  return null;
+}
+
+/**
+ * Return the lowest common ancestor of A and B, or null if they are in
+ * different trees.
+ */
+function getLowestCommonAncestor(instA, instB) {
+  var depthA = 0;
+  for (var tempA = instA; tempA; tempA = getParent(tempA)) {
+    depthA++;
+  }
+  var depthB = 0;
+  for (var tempB = instB; tempB; tempB = getParent(tempB)) {
+    depthB++;
+  }
+
+  // If A is deeper, crawl up.
+  while (depthA - depthB > 0) {
+    instA = getParent(instA);
+    depthA--;
+  }
+
+  // If B is deeper, crawl up.
+  while (depthB - depthA > 0) {
+    instB = getParent(instB);
+    depthB--;
+  }
+
+  // Walk in lockstep until we find a match.
+  var depth = depthA;
+  while (depth--) {
+    if (instA === instB || instA === instB.alternate) {
+      return instA;
+    }
+    instA = getParent(instA);
+    instB = getParent(instB);
+  }
+  return null;
+}
+
+/**
+ * Return if A is an ancestor of B.
+ */
+function isAncestor(instA, instB) {
+  while (instB) {
+    if (instA === instB || instA === instB.alternate) {
+      return true;
+    }
+    instB = getParent(instB);
+  }
+  return false;
+}
+
+/**
+ * Return the parent instance of the passed-in instance.
+ */
+function getParentInstance(inst) {
+  return getParent(inst);
+}
+
+/**
+ * Simulates the traversal of a two-phase, capture/bubble event dispatch.
+ */
+function traverseTwoPhase(inst, fn, arg) {
+  var path = [];
+  while (inst) {
+    path.push(inst);
+    inst = getParent(inst);
+  }
+  var i = void 0;
+  for (i = path.length; i-- > 0; ) {
+    fn(path[i], "captured", arg);
+  }
+  for (i = 0; i < path.length; i++) {
+    fn(path[i], "bubbled", arg);
+  }
+}
+
+/**
+ * Traverses the ID hierarchy and invokes the supplied `cb` on any IDs that
+ * should would receive a `mouseEnter` or `mouseLeave` event.
+ *
+ * Does not invoke the callback on the nearest common ancestor because nothing
+ * "entered" or "left" that element.
+ */
+
+/**
+ * Some event types have a notion of different registration names for different
+ * "phases" of propagation. This finds listeners by a given phase.
+ */
+function listenerAtPhase(inst, event, propagationPhase) {
+  var registrationName =
+    event.dispatchConfig.phasedRegistrationNames[propagationPhase];
+  return getListener(inst, registrationName);
+}
+
+/**
+ * A small set of propagation patterns, each of which will accept a small amount
+ * of information, and generate a set of "dispatch ready event objects" - which
+ * are sets of events that have already been annotated with a set of dispatched
+ * listener functions/ids. The API is designed this way to discourage these
+ * propagation strategies from actually executing the dispatches, since we
+ * always want to collect the entire set of dispatches before executing even a
+ * single one.
+ */
+
+/**
+ * Tags a `SyntheticEvent` with dispatched listeners. Creating this function
+ * here, allows us to not have to bind or create functions for each event.
+ * Mutating the event's members allows us to not have to create a wrapping
+ * "dispatch" object that pairs the event with the listener.
+ */
+function accumulateDirectionalDispatches(inst, phase, event) {
+  {
+    !inst ? warning(false, "Dispatching inst must not be null") : void 0;
+  }
+  var listener = listenerAtPhase(inst, event, phase);
+  if (listener) {
+    event._dispatchListeners = accumulateInto(
+      event._dispatchListeners,
+      listener
+    );
+    event._dispatchInstances = accumulateInto(event._dispatchInstances, inst);
+  }
+}
+
+/**
+ * Collect dispatches (must be entirely collected before dispatching - see unit
+ * tests). Lazily allocate the array to conserve memory.  We must loop through
+ * each event and perform the traversal for each one. We cannot perform a
+ * single traversal for the entire collection of events because each event may
+ * have a different target.
+ */
+function accumulateTwoPhaseDispatchesSingle(event) {
+  if (event && event.dispatchConfig.phasedRegistrationNames) {
+    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
+  }
+}
+
+/**
+ * Same as `accumulateTwoPhaseDispatchesSingle`, but skips over the targetID.
+ */
+function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
+  if (event && event.dispatchConfig.phasedRegistrationNames) {
+    var targetInst = event._targetInst;
+    var parentInst = targetInst ? getParentInstance(targetInst) : null;
+    traverseTwoPhase(parentInst, accumulateDirectionalDispatches, event);
+  }
+}
+
+/**
+ * Accumulates without regard to direction, does not look for phased
+ * registration names. Same as `accumulateDirectDispatchesSingle` but without
+ * requiring that the `dispatchMarker` be the same as the dispatched ID.
+ */
+function accumulateDispatches(inst, ignoredDirection, event) {
+  if (inst && event && event.dispatchConfig.registrationName) {
+    var registrationName = event.dispatchConfig.registrationName;
+    var listener = getListener(inst, registrationName);
+    if (listener) {
+      event._dispatchListeners = accumulateInto(
+        event._dispatchListeners,
+        listener
+      );
+      event._dispatchInstances = accumulateInto(event._dispatchInstances, inst);
+    }
+  }
+}
+
+/**
+ * Accumulates dispatches on an `SyntheticEvent`, but only for the
+ * `dispatchMarker`.
+ * @param {SyntheticEvent} event
+ */
+function accumulateDirectDispatchesSingle(event) {
+  if (event && event.dispatchConfig.registrationName) {
+    accumulateDispatches(event._targetInst, null, event);
+  }
+}
+
+function accumulateTwoPhaseDispatches(events) {
+  forEachAccumulated(events, accumulateTwoPhaseDispatchesSingle);
+}
+
+function accumulateTwoPhaseDispatchesSkipTarget(events) {
+  forEachAccumulated(events, accumulateTwoPhaseDispatchesSingleSkipTarget);
+}
+
+function accumulateDirectDispatches(events) {
+  forEachAccumulated(events, accumulateDirectDispatchesSingle);
+}
+
+/* eslint valid-typeof: 0 */
+
+var didWarnForAddedNewProperty = false;
+var EVENT_POOL_SIZE = 10;
+
+var shouldBeReleasedProperties = [
+  "dispatchConfig",
+  "_targetInst",
+  "nativeEvent",
+  "isDefaultPrevented",
+  "isPropagationStopped",
+  "_dispatchListeners",
+  "_dispatchInstances"
+];
+
+/**
+ * @interface Event
+ * @see http://www.w3.org/TR/DOM-Level-3-Events/
+ */
+var EventInterface = {
+  type: null,
+  target: null,
+  // currentTarget is set when dispatching; no use in copying it here
+  currentTarget: emptyFunction.thatReturnsNull,
+  eventPhase: null,
+  bubbles: null,
+  cancelable: null,
+  timeStamp: function(event) {
+    return event.timeStamp || Date.now();
+  },
+  defaultPrevented: null,
+  isTrusted: null
+};
+
+/**
+ * Synthetic events are dispatched by event plugins, typically in response to a
+ * top-level event delegation handler.
+ *
+ * These systems should generally use pooling to reduce the frequency of garbage
+ * collection. The system should check `isPersistent` to determine whether the
+ * event should be released into the pool after being dispatched. Users that
+ * need a persisted event should invoke `persist`.
+ *
+ * Synthetic events (and subclasses) implement the DOM Level 3 Events API by
+ * normalizing browser quirks. Subclasses do not necessarily have to implement a
+ * DOM interface; custom application-specific events can also subclass this.
+ *
+ * @param {object} dispatchConfig Configuration used to dispatch this event.
+ * @param {*} targetInst Marker identifying the event target.
+ * @param {object} nativeEvent Native browser event.
+ * @param {DOMEventTarget} nativeEventTarget Target node.
+ */
+function SyntheticEvent(
+  dispatchConfig,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  {
+    // these have a getter/setter for warnings
+    delete this.nativeEvent;
+    delete this.preventDefault;
+    delete this.stopPropagation;
+  }
+
+  this.dispatchConfig = dispatchConfig;
+  this._targetInst = targetInst;
+  this.nativeEvent = nativeEvent;
+
+  var Interface = this.constructor.Interface;
+  for (var propName in Interface) {
+    if (!Interface.hasOwnProperty(propName)) {
+      continue;
+    }
+    {
+      delete this[propName]; // this has a getter/setter for warnings
+    }
+    var normalize = Interface[propName];
+    if (normalize) {
+      this[propName] = normalize(nativeEvent);
+    } else {
+      if (propName === "target") {
+        this.target = nativeEventTarget;
+      } else {
+        this[propName] = nativeEvent[propName];
+      }
+    }
+  }
+
+  var defaultPrevented =
+    nativeEvent.defaultPrevented != null
+      ? nativeEvent.defaultPrevented
+      : nativeEvent.returnValue === false;
+  if (defaultPrevented) {
+    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
+  } else {
+    this.isDefaultPrevented = emptyFunction.thatReturnsFalse;
+  }
+  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
+  return this;
+}
+
+Object.assign(SyntheticEvent.prototype, {
+  preventDefault: function() {
+    this.defaultPrevented = true;
+    var event = this.nativeEvent;
+    if (!event) {
+      return;
+    }
+
+    if (event.preventDefault) {
+      event.preventDefault();
+    } else if (typeof event.returnValue !== "unknown") {
+      event.returnValue = false;
+    }
+    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
+  },
+
+  stopPropagation: function() {
+    var event = this.nativeEvent;
+    if (!event) {
+      return;
+    }
+
+    if (event.stopPropagation) {
+      event.stopPropagation();
+    } else if (typeof event.cancelBubble !== "unknown") {
+      // The ChangeEventPlugin registers a "propertychange" event for
+      // IE. This event does not support bubbling or cancelling, and
+      // any references to cancelBubble throw "Member not found".  A
+      // typeof check of "unknown" circumvents this issue (and is also
+      // IE specific).
+      event.cancelBubble = true;
+    }
+
+    this.isPropagationStopped = emptyFunction.thatReturnsTrue;
+  },
+
+  /**
+   * We release all dispatched `SyntheticEvent`s after each event loop, adding
+   * them back into the pool. This allows a way to hold onto a reference that
+   * won't be added back into the pool.
+   */
+  persist: function() {
+    this.isPersistent = emptyFunction.thatReturnsTrue;
+  },
+
+  /**
+   * Checks if this event should be released back into the pool.
+   *
+   * @return {boolean} True if this should not be released, false otherwise.
+   */
+  isPersistent: emptyFunction.thatReturnsFalse,
+
+  /**
+   * `PooledClass` looks for `destructor` on each instance it releases.
+   */
+  destructor: function() {
+    var Interface = this.constructor.Interface;
+    for (var propName in Interface) {
+      {
+        Object.defineProperty(
+          this,
+          propName,
+          getPooledWarningPropertyDefinition(propName, Interface[propName])
+        );
+      }
+    }
+    for (var i = 0; i < shouldBeReleasedProperties.length; i++) {
+      this[shouldBeReleasedProperties[i]] = null;
+    }
+    {
+      Object.defineProperty(
+        this,
+        "nativeEvent",
+        getPooledWarningPropertyDefinition("nativeEvent", null)
+      );
+      Object.defineProperty(
+        this,
+        "preventDefault",
+        getPooledWarningPropertyDefinition("preventDefault", emptyFunction)
+      );
+      Object.defineProperty(
+        this,
+        "stopPropagation",
+        getPooledWarningPropertyDefinition("stopPropagation", emptyFunction)
+      );
+    }
+  }
+});
+
+SyntheticEvent.Interface = EventInterface;
+
+/**
+ * Helper to reduce boilerplate when creating subclasses.
+ */
+SyntheticEvent.extend = function(Interface) {
+  var Super = this;
+
+  var E = function() {};
+  E.prototype = Super.prototype;
+  var prototype = new E();
+
+  function Class() {
+    return Super.apply(this, arguments);
+  }
+  Object.assign(prototype, Class.prototype);
+  Class.prototype = prototype;
+  Class.prototype.constructor = Class;
+
+  Class.Interface = Object.assign({}, Super.Interface, Interface);
+  Class.extend = Super.extend;
+  addEventPoolingTo(Class);
+
+  return Class;
+};
+
+/** Proxying after everything set on SyntheticEvent
+ * to resolve Proxy issue on some WebKit browsers
+ * in which some Event properties are set to undefined (GH#10010)
+ */
+{
+  var isProxySupported =
+    typeof Proxy === "function" &&
+    // https://github.com/facebook/react/issues/12011
+    !Object.isSealed(new Proxy({}, {}));
+
+  if (isProxySupported) {
+    /*eslint-disable no-func-assign */
+    SyntheticEvent = new Proxy(SyntheticEvent, {
+      construct: function(target, args) {
+        return this.apply(target, Object.create(target.prototype), args);
+      },
+      apply: function(constructor, that, args) {
+        return new Proxy(constructor.apply(that, args), {
+          set: function(target, prop, value) {
+            if (
+              prop !== "isPersistent" &&
+              !target.constructor.Interface.hasOwnProperty(prop) &&
+              shouldBeReleasedProperties.indexOf(prop) === -1
+            ) {
+              !(didWarnForAddedNewProperty || target.isPersistent())
+                ? warning(
+                    false,
+                    "This synthetic event is reused for performance reasons. If you're " +
+                      "seeing this, you're adding a new property in the synthetic event object. " +
+                      "The property is never released. See " +
+                      "https://fb.me/react-event-pooling for more information."
+                  )
+                : void 0;
+              didWarnForAddedNewProperty = true;
+            }
+            target[prop] = value;
+            return true;
+          }
+        });
+      }
+    });
+    /*eslint-enable no-func-assign */
+  }
+}
+
+addEventPoolingTo(SyntheticEvent);
+
+/**
+ * Helper to nullify syntheticEvent instance properties when destructing
+ *
+ * @param {String} propName
+ * @param {?object} getVal
+ * @return {object} defineProperty object
+ */
+function getPooledWarningPropertyDefinition(propName, getVal) {
+  var isFunction = typeof getVal === "function";
+  return {
+    configurable: true,
+    set: set,
+    get: get$$1
+  };
+
+  function set(val) {
+    var action = isFunction ? "setting the method" : "setting the property";
+    warn(action, "This is effectively a no-op");
+    return val;
+  }
+
+  function get$$1() {
+    var action = isFunction ? "accessing the method" : "accessing the property";
+    var result = isFunction
+      ? "This is a no-op function"
+      : "This is set to null";
+    warn(action, result);
+    return getVal;
+  }
+
+  function warn(action, result) {
+    var warningCondition = false;
+    !warningCondition
+      ? warning(
+          false,
+          "This synthetic event is reused for performance reasons. If you're seeing this, " +
+            "you're %s `%s` on a released/nullified synthetic event. %s. " +
+            "If you must keep the original synthetic event around, use event.persist(). " +
+            "See https://fb.me/react-event-pooling for more information.",
+          action,
+          propName,
+          result
+        )
+      : void 0;
+  }
+}
+
+function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
+  var EventConstructor = this;
+  if (EventConstructor.eventPool.length) {
+    var instance = EventConstructor.eventPool.pop();
+    EventConstructor.call(
+      instance,
+      dispatchConfig,
+      targetInst,
+      nativeEvent,
+      nativeInst
+    );
+    return instance;
+  }
+  return new EventConstructor(
+    dispatchConfig,
+    targetInst,
+    nativeEvent,
+    nativeInst
+  );
+}
+
+function releasePooledEvent(event) {
+  var EventConstructor = this;
+  invariant(
+    event instanceof EventConstructor,
+    "Trying to release an event instance  into a pool of a different type."
+  );
+  event.destructor();
+  if (EventConstructor.eventPool.length < EVENT_POOL_SIZE) {
+    EventConstructor.eventPool.push(event);
+  }
+}
+
+function addEventPoolingTo(EventConstructor) {
+  EventConstructor.eventPool = [];
+  EventConstructor.getPooled = getPooledEvent;
+  EventConstructor.release = releasePooledEvent;
+}
+
+var SyntheticEvent$1 = SyntheticEvent;
+
+/**
+ * `touchHistory` isn't actually on the native event, but putting it in the
+ * interface will ensure that it is cleaned up when pooled/destroyed. The
+ * `ResponderEventPlugin` will populate it appropriately.
+ */
+var ResponderSyntheticEvent = SyntheticEvent$1.extend({
+  touchHistory: function(nativeEvent) {
+    return null; // Actually doesn't even look at the native event.
+  }
+});
+
+/**
+ * Tracks the position and time of each active touch by `touch.identifier`. We
+ * should typically only see IDs in the range of 1-20 because IDs get recycled
+ * when touches end and start again.
+ */
+
+var MAX_TOUCH_BANK = 20;
+var touchBank = [];
+var touchHistory = {
+  touchBank: touchBank,
+  numberActiveTouches: 0,
+  // If there is only one active touch, we remember its location. This prevents
+  // us having to loop through all of the touches all the time in the most
+  // common case.
+  indexOfSingleActiveTouch: -1,
+  mostRecentTimeStamp: 0
+};
+
+function timestampForTouch(touch) {
+  // The legacy internal implementation provides "timeStamp", which has been
+  // renamed to "timestamp". Let both work for now while we iron it out
+  // TODO (evv): rename timeStamp to timestamp in internal code
+  return touch.timeStamp || touch.timestamp;
+}
+
+/**
+ * TODO: Instead of making gestures recompute filtered velocity, we could
+ * include a built in velocity computation that can be reused globally.
+ */
+function createTouchRecord(touch) {
+  return {
+    touchActive: true,
+    startPageX: touch.pageX,
+    startPageY: touch.pageY,
+    startTimeStamp: timestampForTouch(touch),
+    currentPageX: touch.pageX,
+    currentPageY: touch.pageY,
+    currentTimeStamp: timestampForTouch(touch),
+    previousPageX: touch.pageX,
+    previousPageY: touch.pageY,
+    previousTimeStamp: timestampForTouch(touch)
+  };
+}
+
+function resetTouchRecord(touchRecord, touch) {
+  touchRecord.touchActive = true;
+  touchRecord.startPageX = touch.pageX;
+  touchRecord.startPageY = touch.pageY;
+  touchRecord.startTimeStamp = timestampForTouch(touch);
+  touchRecord.currentPageX = touch.pageX;
+  touchRecord.currentPageY = touch.pageY;
+  touchRecord.currentTimeStamp = timestampForTouch(touch);
+  touchRecord.previousPageX = touch.pageX;
+  touchRecord.previousPageY = touch.pageY;
+  touchRecord.previousTimeStamp = timestampForTouch(touch);
+}
+
+function getTouchIdentifier(_ref) {
+  var identifier = _ref.identifier;
+
+  invariant(identifier != null, "Touch object is missing identifier.");
+  {
+    !(identifier <= MAX_TOUCH_BANK)
+      ? warning(
+          false,
+          "Touch identifier %s is greater than maximum supported %s which causes " +
+            "performance issues backfilling array locations for all of the indices.",
+          identifier,
+          MAX_TOUCH_BANK
+        )
+      : void 0;
+  }
+  return identifier;
+}
+
+function recordTouchStart(touch) {
+  var identifier = getTouchIdentifier(touch);
+  var touchRecord = touchBank[identifier];
+  if (touchRecord) {
+    resetTouchRecord(touchRecord, touch);
+  } else {
+    touchBank[identifier] = createTouchRecord(touch);
+  }
+  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+}
+
+function recordTouchMove(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  if (touchRecord) {
+    touchRecord.touchActive = true;
+    touchRecord.previousPageX = touchRecord.currentPageX;
+    touchRecord.previousPageY = touchRecord.currentPageY;
+    touchRecord.previousTimeStamp = touchRecord.currentTimeStamp;
+    touchRecord.currentPageX = touch.pageX;
+    touchRecord.currentPageY = touch.pageY;
+    touchRecord.currentTimeStamp = timestampForTouch(touch);
+    touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+  } else {
+    console.error(
+      "Cannot record touch move without a touch start.\n" + "Touch Move: %s\n",
+      "Touch Bank: %s",
+      printTouch(touch),
+      printTouchBank()
+    );
+  }
+}
+
+function recordTouchEnd(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  if (touchRecord) {
+    touchRecord.touchActive = false;
+    touchRecord.previousPageX = touchRecord.currentPageX;
+    touchRecord.previousPageY = touchRecord.currentPageY;
+    touchRecord.previousTimeStamp = touchRecord.currentTimeStamp;
+    touchRecord.currentPageX = touch.pageX;
+    touchRecord.currentPageY = touch.pageY;
+    touchRecord.currentTimeStamp = timestampForTouch(touch);
+    touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+  } else {
+    console.error(
+      "Cannot record touch end without a touch start.\n" + "Touch End: %s\n",
+      "Touch Bank: %s",
+      printTouch(touch),
+      printTouchBank()
+    );
+  }
+}
+
+function printTouch(touch) {
+  return JSON.stringify({
+    identifier: touch.identifier,
+    pageX: touch.pageX,
+    pageY: touch.pageY,
+    timestamp: timestampForTouch(touch)
+  });
+}
+
+function printTouchBank() {
+  var printed = JSON.stringify(touchBank.slice(0, MAX_TOUCH_BANK));
+  if (touchBank.length > MAX_TOUCH_BANK) {
+    printed += " (original size: " + touchBank.length + ")";
+  }
+  return printed;
+}
+
+var ResponderTouchHistoryStore = {
+  recordTouchTrack: function(topLevelType, nativeEvent) {
+    if (isMoveish(topLevelType)) {
+      nativeEvent.changedTouches.forEach(recordTouchMove);
+    } else if (isStartish(topLevelType)) {
+      nativeEvent.changedTouches.forEach(recordTouchStart);
+      touchHistory.numberActiveTouches = nativeEvent.touches.length;
+      if (touchHistory.numberActiveTouches === 1) {
+        touchHistory.indexOfSingleActiveTouch =
+          nativeEvent.touches[0].identifier;
+      }
+    } else if (isEndish(topLevelType)) {
+      nativeEvent.changedTouches.forEach(recordTouchEnd);
+      touchHistory.numberActiveTouches = nativeEvent.touches.length;
+      if (touchHistory.numberActiveTouches === 1) {
+        for (var i = 0; i < touchBank.length; i++) {
+          var touchTrackToCheck = touchBank[i];
+          if (touchTrackToCheck != null && touchTrackToCheck.touchActive) {
+            touchHistory.indexOfSingleActiveTouch = i;
+            break;
+          }
+        }
+        {
+          var activeRecord = touchBank[touchHistory.indexOfSingleActiveTouch];
+          !(activeRecord != null && activeRecord.touchActive)
+            ? warning(false, "Cannot find single active touch.")
+            : void 0;
+        }
+      }
+    }
+  },
+
+  touchHistory: touchHistory
+};
+
+/**
+ * Accumulates items that must not be null or undefined.
+ *
+ * This is used to conserve memory by avoiding array allocations.
+ *
+ * @return {*|array<*>} An accumulation of items.
+ */
+function accumulate(current, next) {
+  invariant(
+    next != null,
+    "accumulate(...): Accumulated items must be not be null or undefined."
+  );
+
+  if (current == null) {
+    return next;
+  }
+
+  // Both are not empty. Warning: Never call x.concat(y) when you are not
+  // certain that x is an Array (x could be a string with concat method).
+  if (Array.isArray(current)) {
+    return current.concat(next);
+  }
+
+  if (Array.isArray(next)) {
+    return [current].concat(next);
+  }
+
+  return [current, next];
+}
+
+/**
+ * Instance of element that should respond to touch/move types of interactions,
+ * as indicated explicitly by relevant callbacks.
+ */
+var responderInst = null;
+
+/**
+ * Count of current touches. A textInput should become responder iff the
+ * selection changes while there is a touch on the screen.
+ */
+var trackedTouchCount = 0;
+
+/**
+ * Last reported number of active touches.
+ */
+var previousActiveTouches = 0;
+
+var changeResponder = function(nextResponderInst, blockHostResponder) {
+  var oldResponderInst = responderInst;
+  responderInst = nextResponderInst;
+  if (ResponderEventPlugin.GlobalResponderHandler !== null) {
+    ResponderEventPlugin.GlobalResponderHandler.onChange(
+      oldResponderInst,
+      nextResponderInst,
+      blockHostResponder
+    );
+  }
+};
+
+var eventTypes$1 = {
+  /**
+   * On a `touchStart`/`mouseDown`, is it desired that this element become the
+   * responder?
+   */
+  startShouldSetResponder: {
+    phasedRegistrationNames: {
+      bubbled: "onStartShouldSetResponder",
+      captured: "onStartShouldSetResponderCapture"
+    }
+  },
+
+  /**
+   * On a `scroll`, is it desired that this element become the responder? This
+   * is usually not needed, but should be used to retroactively infer that a
+   * `touchStart` had occurred during momentum scroll. During a momentum scroll,
+   * a touch start will be immediately followed by a scroll event if the view is
+   * currently scrolling.
+   *
+   * TODO: This shouldn't bubble.
+   */
+  scrollShouldSetResponder: {
+    phasedRegistrationNames: {
+      bubbled: "onScrollShouldSetResponder",
+      captured: "onScrollShouldSetResponderCapture"
+    }
+  },
+
+  /**
+   * On text selection change, should this element become the responder? This
+   * is needed for text inputs or other views with native selection, so the
+   * JS view can claim the responder.
+   *
+   * TODO: This shouldn't bubble.
+   */
+  selectionChangeShouldSetResponder: {
+    phasedRegistrationNames: {
+      bubbled: "onSelectionChangeShouldSetResponder",
+      captured: "onSelectionChangeShouldSetResponderCapture"
+    }
+  },
+
+  /**
+   * On a `touchMove`/`mouseMove`, is it desired that this element become the
+   * responder?
+   */
+  moveShouldSetResponder: {
+    phasedRegistrationNames: {
+      bubbled: "onMoveShouldSetResponder",
+      captured: "onMoveShouldSetResponderCapture"
+    }
+  },
+
+  /**
+   * Direct responder events dispatched directly to responder. Do not bubble.
+   */
+  responderStart: { registrationName: "onResponderStart" },
+  responderMove: { registrationName: "onResponderMove" },
+  responderEnd: { registrationName: "onResponderEnd" },
+  responderRelease: { registrationName: "onResponderRelease" },
+  responderTerminationRequest: {
+    registrationName: "onResponderTerminationRequest"
+  },
+  responderGrant: { registrationName: "onResponderGrant" },
+  responderReject: { registrationName: "onResponderReject" },
+  responderTerminate: { registrationName: "onResponderTerminate" }
+};
+
+/**
+ *
+ * Responder System:
+ * ----------------
+ *
+ * - A global, solitary "interaction lock" on a view.
+ * - If a node becomes the responder, it should convey visual feedback
+ *   immediately to indicate so, either by highlighting or moving accordingly.
+ * - To be the responder means, that touches are exclusively important to that
+ *   responder view, and no other view.
+ * - While touches are still occurring, the responder lock can be transferred to
+ *   a new view, but only to increasingly "higher" views (meaning ancestors of
+ *   the current responder).
+ *
+ * Responder being granted:
+ * ------------------------
+ *
+ * - Touch starts, moves, and scrolls can cause an ID to become the responder.
+ * - We capture/bubble `startShouldSetResponder`/`moveShouldSetResponder` to
+ *   the "appropriate place".
+ * - If nothing is currently the responder, the "appropriate place" is the
+ *   initiating event's `targetID`.
+ * - If something *is* already the responder, the "appropriate place" is the
+ *   first common ancestor of the event target and the current `responderInst`.
+ * - Some negotiation happens: See the timing diagram below.
+ * - Scrolled views automatically become responder. The reasoning is that a
+ *   platform scroll view that isn't built on top of the responder system has
+ *   began scrolling, and the active responder must now be notified that the
+ *   interaction is no longer locked to it - the system has taken over.
+ *
+ * - Responder being released:
+ *   As soon as no more touches that *started* inside of descendants of the
+ *   *current* responderInst, an `onResponderRelease` event is dispatched to the
+ *   current responder, and the responder lock is released.
+ *
+ * TODO:
+ * - on "end", a callback hook for `onResponderEndShouldRemainResponder` that
+ *   determines if the responder lock should remain.
+ * - If a view shouldn't "remain" the responder, any active touches should by
+ *   default be considered "dead" and do not influence future negotiations or
+ *   bubble paths. It should be as if those touches do not exist.
+ * -- For multitouch: Usually a translate-z will choose to "remain" responder
+ *  after one out of many touches ended. For translate-y, usually the view
+ *  doesn't wish to "remain" responder after one of many touches end.
+ * - Consider building this on top of a `stopPropagation` model similar to
+ *   `W3C` events.
+ * - Ensure that `onResponderTerminate` is called on touch cancels, whether or
+ *   not `onResponderTerminationRequest` returns `true` or `false`.
+ *
+ */
+
+/*                                             Negotiation Performed
+                                             +-----------------------+
+                                            /                         \
+Process low level events to    +     Current Responder      +   wantsResponderID
+determine who to perform negot-|   (if any exists at all)   |
+iation/transition              | Otherwise just pass through|
+-------------------------------+----------------------------+------------------+
+Bubble to find first ID        |                            |
+to return true:wantsResponderID|                            |
+                               |                            |
+     +-------------+           |                            |
+     | onTouchStart|           |                            |
+     +------+------+     none  |                            |
+            |            return|                            |
++-----------v-------------+true| +------------------------+ |
+|onStartShouldSetResponder|----->|onResponderStart (cur)  |<-----------+
++-----------+-------------+    | +------------------------+ |          |
+            |                  |                            | +--------+-------+
+            | returned true for|       false:REJECT +-------->|onResponderReject
+            | wantsResponderID |                    |       | +----------------+
+            | (now attempt     | +------------------+-----+ |
+            |  handoff)        | |   onResponder          | |
+            +------------------->|      TerminationRequest| |
+                               | +------------------+-----+ |
+                               |                    |       | +----------------+
+                               |         true:GRANT +-------->|onResponderGrant|
+                               |                            | +--------+-------+
+                               | +------------------------+ |          |
+                               | |   onResponderTerminate |<-----------+
+                               | +------------------+-----+ |
+                               |                    |       | +----------------+
+                               |                    +-------->|onResponderStart|
+                               |                            | +----------------+
+Bubble to find first ID        |                            |
+to return true:wantsResponderID|                            |
+                               |                            |
+     +-------------+           |                            |
+     | onTouchMove |           |                            |
+     +------+------+     none  |                            |
+            |            return|                            |
++-----------v-------------+true| +------------------------+ |
+|onMoveShouldSetResponder |----->|onResponderMove (cur)   |<-----------+
++-----------+-------------+    | +------------------------+ |          |
+            |                  |                            | +--------+-------+
+            | returned true for|       false:REJECT +-------->|onResponderRejec|
+            | wantsResponderID |                    |       | +----------------+
+            | (now attempt     | +------------------+-----+ |
+            |  handoff)        | |   onResponder          | |
+            +------------------->|      TerminationRequest| |
+                               | +------------------+-----+ |
+                               |                    |       | +----------------+
+                               |         true:GRANT +-------->|onResponderGrant|
+                               |                            | +--------+-------+
+                               | +------------------------+ |          |
+                               | |   onResponderTerminate |<-----------+
+                               | +------------------+-----+ |
+                               |                    |       | +----------------+
+                               |                    +-------->|onResponderMove |
+                               |                            | +----------------+
+                               |                            |
+                               |                            |
+      Some active touch started|                            |
+      inside current responder | +------------------------+ |
+      +------------------------->|      onResponderEnd    | |
+      |                        | +------------------------+ |
+  +---+---------+              |                            |
+  | onTouchEnd  |              |                            |
+  +---+---------+              |                            |
+      |                        | +------------------------+ |
+      +------------------------->|     onResponderEnd     | |
+      No active touches started| +-----------+------------+ |
+      inside current responder |             |              |
+                               |             v              |
+                               | +------------------------+ |
+                               | |    onResponderRelease  | |
+                               | +------------------------+ |
+                               |                            |
+                               +                            + */
+
+/**
+ * A note about event ordering in the `EventPluginHub`.
+ *
+ * Suppose plugins are injected in the following order:
+ *
+ * `[R, S, C]`
+ *
+ * To help illustrate the example, assume `S` is `SimpleEventPlugin` (for
+ * `onClick` etc) and `R` is `ResponderEventPlugin`.
+ *
+ * "Deferred-Dispatched Events":
+ *
+ * - The current event plugin system will traverse the list of injected plugins,
+ *   in order, and extract events by collecting the plugin's return value of
+ *   `extractEvents()`.
+ * - These events that are returned from `extractEvents` are "deferred
+ *   dispatched events".
+ * - When returned from `extractEvents`, deferred-dispatched events contain an
+ *   "accumulation" of deferred dispatches.
+ * - These deferred dispatches are accumulated/collected before they are
+ *   returned, but processed at a later time by the `EventPluginHub` (hence the
+ *   name deferred).
+ *
+ * In the process of returning their deferred-dispatched events, event plugins
+ * themselves can dispatch events on-demand without returning them from
+ * `extractEvents`. Plugins might want to do this, so that they can use event
+ * dispatching as a tool that helps them decide which events should be extracted
+ * in the first place.
+ *
+ * "On-Demand-Dispatched Events":
+ *
+ * - On-demand-dispatched events are not returned from `extractEvents`.
+ * - On-demand-dispatched events are dispatched during the process of returning
+ *   the deferred-dispatched events.
+ * - They should not have side effects.
+ * - They should be avoided, and/or eventually be replaced with another
+ *   abstraction that allows event plugins to perform multiple "rounds" of event
+ *   extraction.
+ *
+ * Therefore, the sequence of event dispatches becomes:
+ *
+ * - `R`s on-demand events (if any)   (dispatched by `R` on-demand)
+ * - `S`s on-demand events (if any)   (dispatched by `S` on-demand)
+ * - `C`s on-demand events (if any)   (dispatched by `C` on-demand)
+ * - `R`s extracted events (if any)   (dispatched by `EventPluginHub`)
+ * - `S`s extracted events (if any)   (dispatched by `EventPluginHub`)
+ * - `C`s extracted events (if any)   (dispatched by `EventPluginHub`)
+ *
+ * In the case of `ResponderEventPlugin`: If the `startShouldSetResponder`
+ * on-demand dispatch returns `true` (and some other details are satisfied) the
+ * `onResponderGrant` deferred dispatched event is returned from
+ * `extractEvents`. The sequence of dispatch executions in this case
+ * will appear as follows:
+ *
+ * - `startShouldSetResponder` (`ResponderEventPlugin` dispatches on-demand)
+ * - `touchStartCapture`       (`EventPluginHub` dispatches as usual)
+ * - `touchStart`              (`EventPluginHub` dispatches as usual)
+ * - `responderGrant/Reject`   (`EventPluginHub` dispatches as usual)
+ */
+
+function setResponderAndExtractTransfer(
+  topLevelType,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  var shouldSetEventType = isStartish(topLevelType)
+    ? eventTypes$1.startShouldSetResponder
+    : isMoveish(topLevelType)
+      ? eventTypes$1.moveShouldSetResponder
+      : topLevelType === "topSelectionChange"
+        ? eventTypes$1.selectionChangeShouldSetResponder
+        : eventTypes$1.scrollShouldSetResponder;
+
+  // TODO: stop one short of the current responder.
+  var bubbleShouldSetFrom = !responderInst
+    ? targetInst
+    : getLowestCommonAncestor(responderInst, targetInst);
+
+  // When capturing/bubbling the "shouldSet" event, we want to skip the target
+  // (deepest ID) if it happens to be the current responder. The reasoning:
+  // It's strange to get an `onMoveShouldSetResponder` when you're *already*
+  // the responder.
+  var skipOverBubbleShouldSetFrom = bubbleShouldSetFrom === responderInst;
+  var shouldSetEvent = ResponderSyntheticEvent.getPooled(
+    shouldSetEventType,
+    bubbleShouldSetFrom,
+    nativeEvent,
+    nativeEventTarget
+  );
+  shouldSetEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+  if (skipOverBubbleShouldSetFrom) {
+    accumulateTwoPhaseDispatchesSkipTarget(shouldSetEvent);
+  } else {
+    accumulateTwoPhaseDispatches(shouldSetEvent);
+  }
+  var wantsResponderInst = executeDispatchesInOrderStopAtTrue(shouldSetEvent);
+  if (!shouldSetEvent.isPersistent()) {
+    shouldSetEvent.constructor.release(shouldSetEvent);
+  }
+
+  if (!wantsResponderInst || wantsResponderInst === responderInst) {
+    return null;
+  }
+  var extracted = void 0;
+  var grantEvent = ResponderSyntheticEvent.getPooled(
+    eventTypes$1.responderGrant,
+    wantsResponderInst,
+    nativeEvent,
+    nativeEventTarget
+  );
+  grantEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+
+  accumulateDirectDispatches(grantEvent);
+  var blockHostResponder = executeDirectDispatch(grantEvent) === true;
+  if (responderInst) {
+    var terminationRequestEvent = ResponderSyntheticEvent.getPooled(
+      eventTypes$1.responderTerminationRequest,
+      responderInst,
+      nativeEvent,
+      nativeEventTarget
+    );
+    terminationRequestEvent.touchHistory =
+      ResponderTouchHistoryStore.touchHistory;
+    accumulateDirectDispatches(terminationRequestEvent);
+    var shouldSwitch =
+      !hasDispatches(terminationRequestEvent) ||
+      executeDirectDispatch(terminationRequestEvent);
+    if (!terminationRequestEvent.isPersistent()) {
+      terminationRequestEvent.constructor.release(terminationRequestEvent);
+    }
+
+    if (shouldSwitch) {
+      var terminateEvent = ResponderSyntheticEvent.getPooled(
+        eventTypes$1.responderTerminate,
+        responderInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      terminateEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+      accumulateDirectDispatches(terminateEvent);
+      extracted = accumulate(extracted, [grantEvent, terminateEvent]);
+      changeResponder(wantsResponderInst, blockHostResponder);
+    } else {
+      var rejectEvent = ResponderSyntheticEvent.getPooled(
+        eventTypes$1.responderReject,
+        wantsResponderInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      rejectEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+      accumulateDirectDispatches(rejectEvent);
+      extracted = accumulate(extracted, rejectEvent);
+    }
+  } else {
+    extracted = accumulate(extracted, grantEvent);
+    changeResponder(wantsResponderInst, blockHostResponder);
+  }
+  return extracted;
+}
+
+/**
+ * A transfer is a negotiation between a currently set responder and the next
+ * element to claim responder status. Any start event could trigger a transfer
+ * of responderInst. Any move event could trigger a transfer.
+ *
+ * @param {string} topLevelType Record from `BrowserEventConstants`.
+ * @return {boolean} True if a transfer of responder could possibly occur.
+ */
+function canTriggerTransfer(topLevelType, topLevelInst, nativeEvent) {
+  return (
+    topLevelInst &&
+    // responderIgnoreScroll: We are trying to migrate away from specifically
+    // tracking native scroll events here and responderIgnoreScroll indicates we
+    // will send topTouchCancel to handle canceling touch events instead
+    ((topLevelType === "topScroll" && !nativeEvent.responderIgnoreScroll) ||
+      (trackedTouchCount > 0 && topLevelType === "topSelectionChange") ||
+      isStartish(topLevelType) ||
+      isMoveish(topLevelType))
+  );
+}
+
+/**
+ * Returns whether or not this touch end event makes it such that there are no
+ * longer any touches that started inside of the current `responderInst`.
+ *
+ * @param {NativeEvent} nativeEvent Native touch end event.
+ * @return {boolean} Whether or not this touch end event ends the responder.
+ */
+function noResponderTouches(nativeEvent) {
+  var touches = nativeEvent.touches;
+  if (!touches || touches.length === 0) {
+    return true;
+  }
+  for (var i = 0; i < touches.length; i++) {
+    var activeTouch = touches[i];
+    var target = activeTouch.target;
+    if (target !== null && target !== undefined && target !== 0) {
+      // Is the original touch location inside of the current responder?
+      var targetInst = getInstanceFromNode(target);
+      if (isAncestor(responderInst, targetInst)) {
+        return false;
+      }
+    }
+  }
+  return true;
+}
+
+var ResponderEventPlugin = {
+  /* For unit testing only */
+  _getResponder: function() {
+    return responderInst;
+  },
+
+  eventTypes: eventTypes$1,
+
+  /**
+   * We must be resilient to `targetInst` being `null` on `touchMove` or
+   * `touchEnd`. On certain platforms, this means that a native scroll has
+   * assumed control and the original touch targets are destroyed.
+   */
+  extractEvents: function(
+    topLevelType,
+    targetInst,
+    nativeEvent,
+    nativeEventTarget
+  ) {
+    if (isStartish(topLevelType)) {
+      trackedTouchCount += 1;
+    } else if (isEndish(topLevelType)) {
+      if (trackedTouchCount >= 0) {
+        trackedTouchCount -= 1;
+      } else {
+        console.error(
+          "Ended a touch event which was not counted in `trackedTouchCount`."
+        );
+        return null;
+      }
+    }
+
+    ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
+
+    var extracted = canTriggerTransfer(topLevelType, targetInst, nativeEvent)
+      ? setResponderAndExtractTransfer(
+          topLevelType,
+          targetInst,
+          nativeEvent,
+          nativeEventTarget
+        )
+      : null;
+    // Responder may or may not have transferred on a new touch start/move.
+    // Regardless, whoever is the responder after any potential transfer, we
+    // direct all touch start/move/ends to them in the form of
+    // `onResponderMove/Start/End`. These will be called for *every* additional
+    // finger that move/start/end, dispatched directly to whoever is the
+    // current responder at that moment, until the responder is "released".
+    //
+    // These multiple individual change touch events are are always bookended
+    // by `onResponderGrant`, and one of
+    // (`onResponderRelease/onResponderTerminate`).
+    var isResponderTouchStart = responderInst && isStartish(topLevelType);
+    var isResponderTouchMove = responderInst && isMoveish(topLevelType);
+    var isResponderTouchEnd = responderInst && isEndish(topLevelType);
+    var incrementalTouch = isResponderTouchStart
+      ? eventTypes$1.responderStart
+      : isResponderTouchMove
+        ? eventTypes$1.responderMove
+        : isResponderTouchEnd ? eventTypes$1.responderEnd : null;
+
+    if (incrementalTouch) {
+      var gesture = ResponderSyntheticEvent.getPooled(
+        incrementalTouch,
+        responderInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      gesture.touchHistory = ResponderTouchHistoryStore.touchHistory;
+      accumulateDirectDispatches(gesture);
+      extracted = accumulate(extracted, gesture);
+    }
+
+    var isResponderTerminate =
+      responderInst && topLevelType === "topTouchCancel";
+    var isResponderRelease =
+      responderInst &&
+      !isResponderTerminate &&
+      isEndish(topLevelType) &&
+      noResponderTouches(nativeEvent);
+    var finalTouch = isResponderTerminate
+      ? eventTypes$1.responderTerminate
+      : isResponderRelease ? eventTypes$1.responderRelease : null;
+    if (finalTouch) {
+      var finalEvent = ResponderSyntheticEvent.getPooled(
+        finalTouch,
+        responderInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      finalEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
+      accumulateDirectDispatches(finalEvent);
+      extracted = accumulate(extracted, finalEvent);
+      changeResponder(null);
+    }
+
+    var numberActiveTouches =
+      ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
+    if (
+      ResponderEventPlugin.GlobalInteractionHandler &&
+      numberActiveTouches !== previousActiveTouches
+    ) {
+      ResponderEventPlugin.GlobalInteractionHandler.onChange(
+        numberActiveTouches
+      );
+    }
+    previousActiveTouches = numberActiveTouches;
+
+    return extracted;
+  },
+
+  GlobalResponderHandler: null,
+  GlobalInteractionHandler: null,
+
+  injection: {
+    /**
+     * @param {{onChange: (ReactID, ReactID) => void} GlobalResponderHandler
+     * Object that handles any change in responder. Use this to inject
+     * integration with an existing touch handling system etc.
+     */
+    injectGlobalResponderHandler: function(GlobalResponderHandler) {
+      ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
+    },
+
+    /**
+     * @param {{onChange: (numberActiveTouches) => void} GlobalInteractionHandler
+     * Object that handles any change in the number of active touches.
+     */
+    injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
+      ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
+    }
+  }
+};
+
+var customBubblingEventTypes$1 =
+  ReactNativeViewConfigRegistry.customBubblingEventTypes;
+var customDirectEventTypes$1 =
+  ReactNativeViewConfigRegistry.customDirectEventTypes;
+var eventTypes$2 = ReactNativeViewConfigRegistry.eventTypes;
+
+var ReactNativeBridgeEventPlugin = {
+  eventTypes: eventTypes$2,
+
+  /**
+   * @see {EventPluginHub.extractEvents}
+   */
+  extractEvents: function(
+    topLevelType,
+    targetInst,
+    nativeEvent,
+    nativeEventTarget
+  ) {
+    if (targetInst == null) {
+      // Probably a node belonging to another renderer's tree.
+      return null;
+    }
+    var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType];
+    var directDispatchConfig = customDirectEventTypes$1[topLevelType];
+    invariant(
+      bubbleDispatchConfig || directDispatchConfig,
+      'Unsupported top level event type "%s" dispatched',
+      topLevelType
+    );
+    var event = SyntheticEvent$1.getPooled(
+      bubbleDispatchConfig || directDispatchConfig,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    );
+    if (bubbleDispatchConfig) {
+      accumulateTwoPhaseDispatches(event);
+    } else if (directDispatchConfig) {
+      accumulateDirectDispatches(event);
+    } else {
+      return null;
+    }
+    return event;
+  }
+};
+
+var instanceCache = {};
+var instanceProps = {};
+
+function precacheFiberNode(hostInst, tag) {
+  instanceCache[tag] = hostInst;
+}
+
+function uncacheFiberNode(tag) {
+  delete instanceCache[tag];
+  delete instanceProps[tag];
+}
+
+function getInstanceFromTag(tag) {
+  if (typeof tag === "number") {
+    return instanceCache[tag] || null;
+  } else {
+    // Fabric will invoke event emitters on a direct fiber reference
+    return tag;
+  }
+}
+
+function getTagFromInstance(inst) {
+  var tag = inst.stateNode._nativeTag;
+  if (tag === undefined) {
+    tag = inst.stateNode.canonical._nativeTag;
+  }
+  invariant(tag, "All native instances should have a tag.");
+  return tag;
+}
+
+function getFiberCurrentPropsFromNode$1(stateNode) {
+  return instanceProps[stateNode._nativeTag] || null;
+}
+
+function updateFiberProps(tag, props) {
+  instanceProps[tag] = props;
+}
+
+var ReactNativeComponentTree = Object.freeze({
+  precacheFiberNode: precacheFiberNode,
+  uncacheFiberNode: uncacheFiberNode,
+  getClosestInstanceFromNode: getInstanceFromTag,
+  getInstanceFromNode: getInstanceFromTag,
+  getNodeFromInstance: getTagFromInstance,
+  getFiberCurrentPropsFromNode: getFiberCurrentPropsFromNode$1,
+  updateFiberProps: updateFiberProps
+});
+
+var ReactNativeEventPluginOrder = [
+  "ResponderEventPlugin",
+  "ReactNativeBridgeEventPlugin"
+];
+
+// Module provided by RN:
+var ReactNativeGlobalResponderHandler = {
+  onChange: function(from, to, blockNativeResponder) {
+    if (to !== null) {
+      var tag = to.stateNode._nativeTag;
+      UIManager.setJSResponder(tag, blockNativeResponder);
+    } else {
+      UIManager.clearJSResponder();
+    }
+  }
+};
+
+/**
+ * Make sure essential globals are available and are patched correctly. Please don't remove this
+ * line. Bundles created by react-packager `require` it before executing any application code. This
+ * ensures it exists in the dependency graph and can be `require`d.
+ * TODO: require this in packager, not in React #10932517
+ */
+// Module provided by RN:
+/**
+ * Inject module for resolving DOM hierarchy and plugin ordering.
+ */
+injection.injectEventPluginOrder(ReactNativeEventPluginOrder);
+injection$1.injectComponentTree(ReactNativeComponentTree);
+
+ResponderEventPlugin.injection.injectGlobalResponderHandler(
+  ReactNativeGlobalResponderHandler
+);
+
+/**
+ * Some important event plugins included by default (without having to require
+ * them).
+ */
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
+
+// Use to restore controlled state after a change event has fired.
+
+var fiberHostComponent = null;
+
+var restoreTarget = null;
+var restoreQueue = null;
+
+function restoreStateOfTarget(target) {
+  // We perform this translation at the end of the event loop so that we
+  // always receive the correct fiber here
+  var internalInstance = getInstanceFromNode(target);
+  if (!internalInstance) {
+    // Unmounted
+    return;
+  }
+  invariant(
+    fiberHostComponent &&
+      typeof fiberHostComponent.restoreControlledState === "function",
+    "Fiber needs to be injected to handle a fiber target for controlled " +
+      "events. This error is likely caused by a bug in React. Please file an issue."
+  );
+  var props = getFiberCurrentPropsFromNode(internalInstance.stateNode);
+  fiberHostComponent.restoreControlledState(
+    internalInstance.stateNode,
+    internalInstance.type,
+    props
+  );
+}
+
+function needsStateRestore() {
+  return restoreTarget !== null || restoreQueue !== null;
+}
+
+function restoreStateIfNeeded() {
+  if (!restoreTarget) {
+    return;
+  }
+  var target = restoreTarget;
+  var queuedTargets = restoreQueue;
+  restoreTarget = null;
+  restoreQueue = null;
+
+  restoreStateOfTarget(target);
+  if (queuedTargets) {
+    for (var i = 0; i < queuedTargets.length; i++) {
+      restoreStateOfTarget(queuedTargets[i]);
+    }
+  }
+}
+
+// Used as a way to call batchedUpdates when we don't have a reference to
+// the renderer. Such as when we're dispatching events or if third party
+// libraries need to call batchedUpdates. Eventually, this API will go away when
+// everything is batched by default. We'll then have a similar API to opt-out of
+// scheduled work and instead do synchronous work.
+
+// Defaults
+var _batchedUpdates = function(fn, bookkeeping) {
+  return fn(bookkeeping);
+};
+var _interactiveUpdates = function(fn, a, b) {
+  return fn(a, b);
+};
+var _flushInteractiveUpdates = function() {};
+
+var isBatching = false;
+function batchedUpdates(fn, bookkeeping) {
+  if (isBatching) {
+    // If we are currently inside another batch, we need to wait until it
+    // fully completes before restoring state.
+    return fn(bookkeeping);
+  }
+  isBatching = true;
+  try {
+    return _batchedUpdates(fn, bookkeeping);
+  } finally {
+    // Here we wait until all updates have propagated, which is important
+    // when using controlled components within layers:
+    // https://github.com/facebook/react/issues/1698
+    // Then we restore state of any controlled component.
+    isBatching = false;
+    var controlledComponentsHavePendingUpdates = needsStateRestore();
+    if (controlledComponentsHavePendingUpdates) {
+      // If a controlled event was fired, we may need to restore the state of
+      // the DOM node back to the controlled value. This is necessary when React
+      // bails out of the update without touching the DOM.
+      _flushInteractiveUpdates();
+      restoreStateIfNeeded();
+    }
+  }
+}
+
+var injection$2 = {
+  injectRenderer: function(renderer) {
+    _batchedUpdates = renderer.batchedUpdates;
+    _interactiveUpdates = renderer.interactiveUpdates;
+    _flushInteractiveUpdates = renderer.flushInteractiveUpdates;
+  }
+};
+
+/**
+ * Version of `ReactBrowserEventEmitter` that works on the receiving side of a
+ * serialized worker boundary.
+ */
+
+// Shared default empty native event - conserve memory.
+var EMPTY_NATIVE_EVENT = {};
+
+/**
+ * Selects a subsequence of `Touch`es, without destroying `touches`.
+ *
+ * @param {Array<Touch>} touches Deserialized touch objects.
+ * @param {Array<number>} indices Indices by which to pull subsequence.
+ * @return {Array<Touch>} Subsequence of touch objects.
+ */
+var touchSubsequence = function(touches, indices) {
+  var ret = [];
+  for (var i = 0; i < indices.length; i++) {
+    ret.push(touches[indices[i]]);
+  }
+  return ret;
+};
+
+/**
+ * TODO: Pool all of this.
+ *
+ * Destroys `touches` by removing touch objects at indices `indices`. This is
+ * to maintain compatibility with W3C touch "end" events, where the active
+ * touches don't include the set that has just been "ended".
+ *
+ * @param {Array<Touch>} touches Deserialized touch objects.
+ * @param {Array<number>} indices Indices to remove from `touches`.
+ * @return {Array<Touch>} Subsequence of removed touch objects.
+ */
+var removeTouchesAtIndices = function(touches, indices) {
+  var rippedOut = [];
+  // use an unsafe downcast to alias to nullable elements,
+  // so we can delete and then compact.
+  var temp = touches;
+  for (var i = 0; i < indices.length; i++) {
+    var index = indices[i];
+    rippedOut.push(touches[index]);
+    temp[index] = null;
+  }
+  var fillAt = 0;
+  for (var j = 0; j < temp.length; j++) {
+    var cur = temp[j];
+    if (cur !== null) {
+      temp[fillAt++] = cur;
+    }
+  }
+  temp.length = fillAt;
+  return rippedOut;
+};
+
+/**
+ * Internal version of `receiveEvent` in terms of normalized (non-tag)
+ * `rootNodeID`.
+ *
+ * @see receiveEvent.
+ *
+ * @param {rootNodeID} rootNodeID React root node ID that event occurred on.
+ * @param {TopLevelType} topLevelType Top level type of event.
+ * @param {?object} nativeEventParam Object passed from native.
+ */
+function _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam) {
+  var nativeEvent = nativeEventParam || EMPTY_NATIVE_EVENT;
+  var inst = getInstanceFromTag(rootNodeID);
+  batchedUpdates(function() {
+    runExtractedEventsInBatch(
+      topLevelType,
+      inst,
+      nativeEvent,
+      nativeEvent.target
+    );
+  });
+  // React Native doesn't use ReactControlledComponent but if it did, here's
+  // where it would do it.
+}
+
+/**
+ * Publicly exposed method on module for native objc to invoke when a top
+ * level event is extracted.
+ * @param {rootNodeID} rootNodeID React root node ID that event occurred on.
+ * @param {TopLevelType} topLevelType Top level type of event.
+ * @param {object} nativeEventParam Object passed from native.
+ */
+function receiveEvent(rootNodeID, topLevelType, nativeEventParam) {
+  _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam);
+}
+
+/**
+ * Simple multi-wrapper around `receiveEvent` that is intended to receive an
+ * efficient representation of `Touch` objects, and other information that
+ * can be used to construct W3C compliant `Event` and `Touch` lists.
+ *
+ * This may create dispatch behavior that differs than web touch handling. We
+ * loop through each of the changed touches and receive it as a single event.
+ * So two `touchStart`/`touchMove`s that occur simultaneously are received as
+ * two separate touch event dispatches - when they arguably should be one.
+ *
+ * This implementation reuses the `Touch` objects themselves as the `Event`s
+ * since we dispatch an event for each touch (though that might not be spec
+ * compliant). The main purpose of reusing them is to save allocations.
+ *
+ * TODO: Dispatch multiple changed touches in one event. The bubble path
+ * could be the first common ancestor of all the `changedTouches`.
+ *
+ * One difference between this behavior and W3C spec: cancelled touches will
+ * not appear in `.touches`, or in any future `.touches`, though they may
+ * still be "actively touching the surface".
+ *
+ * Web desktop polyfills only need to construct a fake touch event with
+ * identifier 0, also abandoning traditional click handlers.
+ */
+function receiveTouches(eventTopLevelType, touches, changedIndices) {
+  var changedTouches =
+    eventTopLevelType === "topTouchEnd" ||
+    eventTopLevelType === "topTouchCancel"
+      ? removeTouchesAtIndices(touches, changedIndices)
+      : touchSubsequence(touches, changedIndices);
+
+  for (var jj = 0; jj < changedTouches.length; jj++) {
+    var touch = changedTouches[jj];
+    // Touch objects can fulfill the role of `DOM` `Event` objects if we set
+    // the `changedTouches`/`touches`. This saves allocations.
+    touch.changedTouches = changedTouches;
+    touch.touches = touches;
+    var nativeEvent = touch;
+    var rootNodeID = null;
+    var target = nativeEvent.target;
+    if (target !== null && target !== undefined) {
+      if (target < 1) {
+        {
+          warning(
+            false,
+            "A view is reporting that a touch occurred on tag zero."
+          );
+        }
+      } else {
+        rootNodeID = target;
+      }
+    }
+    // $FlowFixMe Shouldn't we *not* call it if rootNodeID is null?
+    _receiveRootNodeIDEvent(rootNodeID, eventTopLevelType, nativeEvent);
+  }
+}
+
+var ReactNativeEventEmitter = Object.freeze({
+  getListener: getListener,
+  registrationNames: registrationNameModules,
+  _receiveRootNodeIDEvent: _receiveRootNodeIDEvent,
+  receiveEvent: receiveEvent,
+  receiveTouches: receiveTouches
+});
+
+// Module provided by RN:
+/**
+ * Register the event emitter with the native bridge
+ */
+RCTEventEmitter.register(ReactNativeEventEmitter);
+
+// The Symbol used to tag the ReactElement-like types. If there is no native Symbol
+// nor polyfill, then a plain number is used for performance.
+var hasSymbol = typeof Symbol === "function" && Symbol["for"];
+
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
+var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
+var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
+var REACT_STRICT_MODE_TYPE = hasSymbol
+  ? Symbol["for"]("react.strict_mode")
+  : 0xeacc;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
+var REACT_ASYNC_MODE_TYPE = hasSymbol
+  ? Symbol["for"]("react.async_mode")
+  : 0xeacf;
+var REACT_FORWARD_REF_TYPE = hasSymbol
+  ? Symbol["for"]("react.forward_ref")
+  : 0xead0;
+
+var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
+var FAUX_ITERATOR_SYMBOL = "@@iterator";
+
+function getIteratorFn(maybeIterable) {
+  if (maybeIterable === null || typeof maybeIterable === "undefined") {
+    return null;
+  }
+  var maybeIterator =
+    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
+    maybeIterable[FAUX_ITERATOR_SYMBOL];
+  if (typeof maybeIterator === "function") {
+    return maybeIterator;
+  }
+  return null;
+}
+
+function createPortal(
+  children,
+  containerInfo,
+  // TODO: figure out the API for cross-renderer implementation.
+  implementation
+) {
+  var key =
+    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
+
+  return {
+    // This tag allow us to uniquely identify this as a React Portal
+    $$typeof: REACT_PORTAL_TYPE,
+    key: key == null ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+
+// TODO: this is special because it gets imported during build.
+
+var ReactVersion = "16.3.2";
+
+var describeComponentFrame = function(name, source, ownerName) {
+  return (
+    "\n    in " +
+    (name || "Unknown") +
+    (source
+      ? " (at " +
+        source.fileName.replace(/^.*[\\\/]/, "") +
+        ":" +
+        source.lineNumber +
+        ")"
+      : ownerName ? " (created by " + ownerName + ")" : "")
+  );
+};
+
+function getComponentName(fiber) {
+  var type = fiber.type;
+
+  if (typeof type === "function") {
+    return type.displayName || type.name;
+  }
+  if (typeof type === "string") {
+    return type;
+  }
+  switch (type) {
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_RETURN_TYPE:
+      return "ReactReturn";
+  }
+  if (typeof type === "object" && type !== null) {
+    switch (type.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        var functionName = type.render.displayName || type.render.name || "";
+        return functionName !== ""
+          ? "ForwardRef(" + functionName + ")"
+          : "ForwardRef";
+    }
+  }
+  return null;
+}
+
+function describeFiber(fiber) {
+  switch (fiber.tag) {
+    case IndeterminateComponent:
+    case FunctionalComponent:
+    case ClassComponent:
+    case HostComponent:
+      var owner = fiber._debugOwner;
+      var source = fiber._debugSource;
+      var name = getComponentName(fiber);
+      var ownerName = null;
+      if (owner) {
+        ownerName = getComponentName(owner);
+      }
+      return describeComponentFrame(name, source, ownerName);
+    default:
+      return "";
+  }
+}
+
+// This function can only be called with a work-in-progress fiber and
+// only during begin or complete phase. Do not call it under any other
+// circumstances.
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  var node = workInProgress;
+  do {
+    info += describeFiber(node);
+    // Otherwise this return pointer might point to the wrong tree:
+    node = node["return"];
+  } while (node);
+  return info;
+}
+
+// Modules provided by RN:
+var emptyObject$1 = {};
+
+/**
+ * Create a payload that contains all the updates between two sets of props.
+ *
+ * These helpers are all encapsulated into a single module, because they use
+ * mutation as a performance optimization which leads to subtle shared
+ * dependencies between the code paths. To avoid this mutable state leaking
+ * across modules, I've kept them isolated to this module.
+ */
+
+// Tracks removed keys
+var removedKeys = null;
+var removedKeyCount = 0;
+
+function defaultDiffer(prevProp, nextProp) {
+  if (typeof nextProp !== "object" || nextProp === null) {
+    // Scalars have already been checked for equality
+    return true;
+  } else {
+    // For objects and arrays, the default diffing algorithm is a deep compare
+    return deepDiffer(prevProp, nextProp);
+  }
+}
+
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node)) {
+    var i = node.length;
+    while (i-- && removedKeyCount > 0) {
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+    }
+  } else if (node && removedKeyCount > 0) {
+    var obj = node;
+    for (var propKey in removedKeys) {
+      if (!removedKeys[propKey]) {
+        continue;
+      }
+      var _nextProp = obj[propKey];
+      if (_nextProp === undefined) {
+        continue;
+      }
+
+      var attributeConfig = validAttributes[propKey];
+      if (!attributeConfig) {
+        continue; // not a valid native prop
+      }
+
+      if (typeof _nextProp === "function") {
+        _nextProp = true;
+      }
+      if (typeof _nextProp === "undefined") {
+        _nextProp = null;
+      }
+
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = _nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(_nextProp)
+            : _nextProp;
+        updatePayload[propKey] = nextValue;
+      }
+      removedKeys[propKey] = false;
+      removedKeyCount--;
+    }
+  }
+}
+
+function diffNestedArrayProperty(
+  updatePayload,
+  prevArray,
+  nextArray,
+  validAttributes
+) {
+  var minLength =
+    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
+  var i = void 0;
+  for (i = 0; i < minLength; i++) {
+    // Diff any items in the array in the forward direction. Repeated keys
+    // will be overwritten by later values.
+    updatePayload = diffNestedProperty(
+      updatePayload,
+      prevArray[i],
+      nextArray[i],
+      validAttributes
+    );
+  }
+  for (; i < prevArray.length; i++) {
+    // Clear out all remaining properties.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevArray[i],
+      validAttributes
+    );
+  }
+  for (; i < nextArray.length; i++) {
+    // Add all remaining properties.
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextArray[i],
+      validAttributes
+    );
+  }
+  return updatePayload;
+}
+
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) {
+    // If no properties have been added, then we can bail out quickly on object
+    // equality.
+    return updatePayload;
+  }
+
+  if (!prevProp || !nextProp) {
+    if (nextProp) {
+      return addNestedProperty(updatePayload, nextProp, validAttributes);
+    }
+    if (prevProp) {
+      return clearNestedProperty(updatePayload, prevProp, validAttributes);
+    }
+    return updatePayload;
+  }
+
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
+    // Both are leaves, we can diff the leaves.
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  }
+
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    // Both are arrays, we can diff the arrays.
+    return diffNestedArrayProperty(
+      updatePayload,
+      prevProp,
+      nextProp,
+      validAttributes
+    );
+  }
+
+  if (Array.isArray(prevProp)) {
+    return diffProperties(
+      updatePayload,
+      // $FlowFixMe - We know that this is always an object when the input is.
+      flattenStyle(prevProp),
+      // $FlowFixMe - We know that this isn't an array because of above flow.
+      nextProp,
+      validAttributes
+    );
+  }
+
+  return diffProperties(
+    updatePayload,
+    prevProp,
+    // $FlowFixMe - We know that this is always an object when the input is.
+    flattenStyle(nextProp),
+    validAttributes
+  );
+}
+
+/**
+ * addNestedProperty takes a single set of props and valid attribute
+ * attribute configurations. It processes each prop and adds it to the
+ * updatePayload.
+ */
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) {
+    return updatePayload;
+  }
+
+  if (!Array.isArray(nextProp)) {
+    // Add each property of the leaf.
+    return addProperties(updatePayload, nextProp, validAttributes);
+  }
+
+  for (var i = 0; i < nextProp.length; i++) {
+    // Add all the properties of the array.
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  }
+
+  return updatePayload;
+}
+
+/**
+ * clearNestedProperty takes a single set of props and valid attributes. It
+ * adds a null sentinel to the updatePayload, for each prop key.
+ */
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) {
+    return updatePayload;
+  }
+
+  if (!Array.isArray(prevProp)) {
+    // Add each property of the leaf.
+    return clearProperties(updatePayload, prevProp, validAttributes);
+  }
+
+  for (var i = 0; i < prevProp.length; i++) {
+    // Add all the properties of the array.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  }
+  return updatePayload;
+}
+
+/**
+ * diffProperties takes two sets of props and a set of valid attributes
+ * and write to updatePayload the values that changed or were deleted.
+ * If no updatePayload is provided, a new one is created and returned if
+ * anything changed.
+ */
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig = void 0;
+  var nextProp = void 0;
+  var prevProp = void 0;
+
+  for (var propKey in nextProps) {
+    attributeConfig = validAttributes[propKey];
+    if (!attributeConfig) {
+      continue; // not a valid native prop
+    }
+
+    prevProp = prevProps[propKey];
+    nextProp = nextProps[propKey];
+
+    // functions are converted to booleans as markers that the associated
+    // events should be sent from native.
+    if (typeof nextProp === "function") {
+      nextProp = true;
+      // If nextProp is not a function, then don't bother changing prevProp
+      // since nextProp will win and go into the updatePayload regardless.
+      if (typeof prevProp === "function") {
+        prevProp = true;
+      }
+    }
+
+    // An explicit value of undefined is treated as a null because it overrides
+    // any other preceding value.
+    if (typeof nextProp === "undefined") {
+      nextProp = null;
+      if (typeof prevProp === "undefined") {
+        prevProp = null;
+      }
+    }
+
+    if (removedKeys) {
+      removedKeys[propKey] = false;
+    }
+
+    if (updatePayload && updatePayload[propKey] !== undefined) {
+      // Something else already triggered an update to this key because another
+      // value diffed. Since we're now later in the nested arrays our value is
+      // more important so we need to calculate it and override the existing
+      // value. It doesn't matter if nothing changed, we'll set it anyway.
+
+      // Pattern match on: attributeConfig
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(nextProp)
+            : nextProp;
+        updatePayload[propKey] = nextValue;
+      }
+      continue;
+    }
+
+    if (prevProp === nextProp) {
+      continue; // nothing changed
+    }
+
+    // Pattern match on: attributeConfig
+    if (typeof attributeConfig !== "object") {
+      // case: !Object is the default case
+      if (defaultDiffer(prevProp, nextProp)) {
+        // a normal leaf has changed
+        (updatePayload || (updatePayload = {}))[propKey] = nextProp;
+      }
+    } else if (
+      typeof attributeConfig.diff === "function" ||
+      typeof attributeConfig.process === "function"
+    ) {
+      // case: CustomAttributeConfiguration
+      var shouldUpdate =
+        prevProp === undefined ||
+        (typeof attributeConfig.diff === "function"
+          ? attributeConfig.diff(prevProp, nextProp)
+          : defaultDiffer(prevProp, nextProp));
+      if (shouldUpdate) {
+        var _nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(nextProp)
+            : nextProp;
+        (updatePayload || (updatePayload = {}))[propKey] = _nextValue;
+      }
+    } else {
+      // default: fallthrough case when nested properties are defined
+      removedKeys = null;
+      removedKeyCount = 0;
+      // We think that attributeConfig is not CustomAttributeConfiguration at
+      // this point so we assume it must be AttributeConfiguration.
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp,
+        nextProp,
+        attributeConfig
+      );
+      if (removedKeyCount > 0 && updatePayload) {
+        restoreDeletedValuesInNestedArray(
+          updatePayload,
+          nextProp,
+          attributeConfig
+        );
+        removedKeys = null;
+      }
+    }
+  }
+
+  // Also iterate through all the previous props to catch any that have been
+  // removed and make sure native gets the signal so it can reset them to the
+  // default.
+  for (var _propKey in prevProps) {
+    if (nextProps[_propKey] !== undefined) {
+      continue; // we've already covered this key in the previous pass
+    }
+    attributeConfig = validAttributes[_propKey];
+    if (!attributeConfig) {
+      continue; // not a valid native prop
+    }
+
+    if (updatePayload && updatePayload[_propKey] !== undefined) {
+      // This was already updated to a diff result earlier.
+      continue;
+    }
+
+    prevProp = prevProps[_propKey];
+    if (prevProp === undefined) {
+      continue; // was already empty anyway
+    }
+    // Pattern match on: attributeConfig
+    if (
+      typeof attributeConfig !== "object" ||
+      typeof attributeConfig.diff === "function" ||
+      typeof attributeConfig.process === "function"
+    ) {
+      // case: CustomAttributeConfiguration | !Object
+      // Flag the leaf property for removal by sending a sentinel.
+      (updatePayload || (updatePayload = {}))[_propKey] = null;
+      if (!removedKeys) {
+        removedKeys = {};
+      }
+      if (!removedKeys[_propKey]) {
+        removedKeys[_propKey] = true;
+        removedKeyCount++;
+      }
+    } else {
+      // default:
+      // This is a nested attribute configuration where all the properties
+      // were removed so we need to go through and clear out all of them.
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp,
+        attributeConfig
+      );
+    }
+  }
+  return updatePayload;
+}
+
+/**
+ * addProperties adds all the valid props to the payload after being processed.
+ */
+function addProperties(updatePayload, props, validAttributes) {
+  // TODO: Fast path
+  return diffProperties(updatePayload, emptyObject$1, props, validAttributes);
+}
+
+/**
+ * clearProperties clears all the previous props by adding a null sentinel
+ * to the payload for each valid key.
+ */
+function clearProperties(updatePayload, prevProps, validAttributes) {
+  // TODO: Fast path
+  return diffProperties(
+    updatePayload,
+    prevProps,
+    emptyObject$1,
+    validAttributes
+  );
+}
+
+function create(props, validAttributes) {
+  return addProperties(
+    null, // updatePayload
+    props,
+    validAttributes
+  );
+}
+
+function diff(prevProps, nextProps, validAttributes) {
+  return diffProperties(
+    null, // updatePayload
+    prevProps,
+    nextProps,
+    validAttributes
+  );
+}
+
+/**
+ * In the future, we should cleanup callbacks by cancelling them instead of
+ * using this.
+ */
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (!callback) {
+      return undefined;
+    }
+    if (typeof context.__isMounted === "boolean") {
+      // TODO(gaearon): this is gross and should be removed.
+      // It is currently necessary because View uses createClass,
+      // and so any measure() calls on View (which are done by React
+      // DevTools) trigger the isMounted() deprecation warning.
+      if (!context.__isMounted) {
+        return undefined;
+      }
+      // The else branch is important so that we don't
+      // trigger the deprecation warning by calling isMounted.
+    } else if (typeof context.isMounted === "function") {
+      if (!context.isMounted()) {
+        return undefined;
+      }
+    }
+    return callback.apply(context, arguments);
+  };
+}
+
+function throwOnStylesProp(component, props) {
+  if (props.styles !== undefined) {
+    var owner = component._owner || null;
+    var name = component.constructor.displayName;
+    var msg =
+      "`styles` is not a supported property of `" +
+      name +
+      "`, did " +
+      "you mean `style` (singular)?";
+    if (owner && owner.constructor && owner.constructor.displayName) {
+      msg +=
+        "\n\nCheck the `" +
+        owner.constructor.displayName +
+        "` parent " +
+        " component.";
+    }
+    throw new Error(msg);
+  }
+}
+
+function warnForStyleProps(props, validAttributes) {
+  for (var key in validAttributes.style) {
+    if (!(validAttributes[key] || props[key] === undefined)) {
+      console.error(
+        "You are setting the style `{ " +
+          key +
+          ": ... }` as a prop. You " +
+          "should nest it in a style object. " +
+          "E.g. `{ style: { " +
+          key +
+          ": ... } }`"
+      );
+    }
+  }
+}
+
+// Modules provided by RN:
+var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
+  /**
+   * `NativeMethodsMixin` provides methods to access the underlying native
+   * component directly. This can be useful in cases when you want to focus
+   * a view or measure its on-screen dimensions, for example.
+   *
+   * The methods described here are available on most of the default components
+   * provided by React Native. Note, however, that they are *not* available on
+   * composite components that aren't directly backed by a native view. This will
+   * generally include most components that you define in your own app. For more
+   * information, see [Direct
+   * Manipulation](docs/direct-manipulation.html).
+   *
+   * Note the Flow $Exact<> syntax is required to support mixins.
+   * React createClass mixins can only be used with exact types.
+   */
+  var NativeMethodsMixin = {
+    /**
+     * Determines the location on screen, width, and height of the given view and
+     * returns the values via an async callback. If successful, the callback will
+     * be called with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native. If you need the measurements as soon as
+     * possible, consider using the [`onLayout`
+     * prop](docs/view.html#onlayout) instead.
+     */
+    measure: function(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
+
+    /**
+     * Determines the location of the given view in the window and returns the
+     * values via an async callback. If the React root view is embedded in
+     * another native view, this will give you the absolute coordinates. If
+     * successful, the callback will be called with the following
+     * arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native.
+     */
+    measureInWindow: function(callback) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
+
+    /**
+     * Like [`measure()`](#measure), but measures the view relative an ancestor,
+     * specified as `relativeToNativeNode`. This means that the returned x, y
+     * are relative to the origin x, y of the ancestor view.
+     *
+     * As always, to obtain a native node handle for a component, you can use
+     * `findNodeHandle(component)`.
+     */
+    measureLayout: function(
+      relativeToNativeNode,
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    },
+
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
+    setNativeProps: function(nativeProps) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
+
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
+
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
+
+      var viewConfig = maybeInstance.viewConfig;
+
+      {
+        warnForStyleProps(nativeProps, viewConfig.validAttributes);
+      }
+
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
+
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    },
+
+    /**
+     * Requests focus for the given input or view. The exact behavior triggered
+     * will depend on the platform and type of view.
+     */
+    focus: function() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    },
+
+    /**
+     * Removes focus from an input or view. This is the opposite of `focus()`.
+     */
+    blur: function() {
+      TextInputState.blurTextInput(findNodeHandle(this));
+    }
+  };
+
+  {
+    // hide this from Flow since we can't define these properties outside of
+    // true without actually implementing them (setting them to undefined
+    // isn't allowed by ReactClass)
+    var NativeMethodsMixin_DEV = NativeMethodsMixin;
+    invariant(
+      !NativeMethodsMixin_DEV.componentWillMount &&
+        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
+      "Do not override existing functions."
+    );
+    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
+    // Once these lifecycles have been remove from the reconciler.
+    NativeMethodsMixin_DEV.componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
+      throwOnStylesProp(this, newProps);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
+      newProps
+    ) {
+      throwOnStylesProp(this, newProps);
+    };
+
+    // React may warn about cWM/cWRP/cWU methods being deprecated.
+    // Add a flag to suppress these warnings for this special case.
+    // TODO (bvaughn) Remove this flag once the above methods have been removed.
+    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
+    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
+  }
+
+  return NativeMethodsMixin;
+};
+
+function _classCallCheck(instance, Constructor) {
+  if (!(instance instanceof Constructor)) {
+    throw new TypeError("Cannot call a class as a function");
+  }
+}
+
+function _possibleConstructorReturn(self, call) {
+  if (!self) {
+    throw new ReferenceError(
+      "this hasn't been initialised - super() hasn't been called"
+    );
+  }
+  return call && (typeof call === "object" || typeof call === "function")
+    ? call
+    : self;
+}
+
+function _inherits(subClass, superClass) {
+  if (typeof superClass !== "function" && superClass !== null) {
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
+  }
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: false,
+      writable: true,
+      configurable: true
+    }
+  });
+  if (superClass)
+    Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass);
+}
+
+// Modules provided by RN:
+var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
+  /**
+   * Superclass that provides methods to access the underlying native component.
+   * This can be useful when you want to focus a view or measure its dimensions.
+   *
+   * Methods implemented by this class are available on most default components
+   * provided by React Native. However, they are *not* available on composite
+   * components that are not directly backed by a native view. For more
+   * information, see [Direct Manipulation](docs/direct-manipulation.html).
+   *
+   * @abstract
+   */
+  var ReactNativeComponent = (function(_React$Component) {
+    _inherits(ReactNativeComponent, _React$Component);
+
+    function ReactNativeComponent() {
+      _classCallCheck(this, ReactNativeComponent);
+
+      return _possibleConstructorReturn(
+        this,
+        _React$Component.apply(this, arguments)
+      );
+    }
+
+    /**
+     * Removes focus. This is the opposite of `focus()`.
+     */
+
+    /**
+     * Due to bugs in Flow's handling of React.createClass, some fields already
+     * declared in the base class need to be redeclared below.
+     */
+    ReactNativeComponent.prototype.blur = function blur() {
+      TextInputState.blurTextInput(findNodeHandle(this));
+    };
+
+    /**
+     * Requests focus. The exact behavior depends on the platform and view.
+     */
+
+    ReactNativeComponent.prototype.focus = function focus() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    };
+
+    /**
+     * Measures the on-screen location and dimensions. If successful, the callback
+     * will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * These values are not available until after natives rendering completes. If
+     * you need the measurements as soon as possible, consider using the
+     * [`onLayout` prop](docs/view.html#onlayout) instead.
+     */
+
+    ReactNativeComponent.prototype.measure = function measure(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
+
+    /**
+     * Measures the on-screen location and dimensions. Even if the React Native
+     * root view is embedded within another native view, this method will give you
+     * the absolute coordinates measured from the window. If successful, the
+     * callback will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * These values are not available until after natives rendering completes.
+     */
+
+    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
+
+    /**
+     * Similar to [`measure()`](#measure), but the resulting location will be
+     * relative to the supplied ancestor's location.
+     *
+     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
+     */
+
+    ReactNativeComponent.prototype.measureLayout = function measureLayout(
+      relativeToNativeNode,
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
+
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
+
+    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
+      nativeProps
+    ) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
+
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
+
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
+
+      var viewConfig =
+        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
+
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    };
+
+    return ReactNativeComponent;
+  })(React.Component);
+
+  // eslint-disable-next-line no-unused-expressions
+
+  return ReactNativeComponent;
+};
+
+/**
+ * `ReactInstanceMap` maintains a mapping from a public facing stateful
+ * instance (key) and the internal representation (value). This allows public
+ * methods to accept the user facing instance as an argument and map them back
+ * to internal methods.
+ *
+ * Note that this module is currently shared and assumed to be stateless.
+ * If this becomes an actual Map, that will break.
+ */
+
+/**
+ * This API should be called `delete` but we'd have to make sure to always
+ * transform these to strings for IE support. When this transform is fully
+ * supported we can rename it.
+ */
+
+function get$1(key) {
+  return key._reactInternalFiber;
+}
+
+function set(key, value) {
+  key._reactInternalFiber = value;
+}
+
+var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+
+var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
+var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
+
+// Don't change these two values. They're used by React Dev Tools.
+var NoEffect = /*              */ 0;
+var PerformedWork = /*         */ 1;
+
+// You can change the rest (and add more).
+var Placement = /*             */ 2;
+var Update = /*                */ 4;
+var PlacementAndUpdate = /*    */ 6;
+var Deletion = /*              */ 8;
+var ContentReset = /*          */ 16;
+var Callback = /*              */ 32;
+var DidCapture = /*            */ 64;
+var Ref = /*                   */ 128;
+var ErrLog = /*                */ 256;
+var Snapshot = /*              */ 2048;
+
+// Union of all host effects
+var HostEffectMask = /*        */ 2559;
+
+var Incomplete = /*            */ 512;
+var ShouldCapture = /*         */ 1024;
+
+var MOUNTING = 1;
+var MOUNTED = 2;
+var UNMOUNTED = 3;
+
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (!fiber.alternate) {
+    // If there is no alternate, this might be a new tree that isn't inserted
+    // yet. If it is, then it will have a pending insertion effect on it.
+    if ((node.effectTag & Placement) !== NoEffect) {
+      return MOUNTING;
+    }
+    while (node["return"]) {
+      node = node["return"];
+      if ((node.effectTag & Placement) !== NoEffect) {
+        return MOUNTING;
+      }
+    }
+  } else {
+    while (node["return"]) {
+      node = node["return"];
+    }
+  }
+  if (node.tag === HostRoot) {
+    // TODO: Check if this was a nested HostRoot when used with
+    // renderContainerIntoSubtree.
+    return MOUNTED;
+  }
+  // If we didn't hit the root, that means that we're in an disconnected tree
+  // that has been unmounted.
+  return UNMOUNTED;
+}
+
+function isFiberMounted(fiber) {
+  return isFiberMountedImpl(fiber) === MOUNTED;
+}
+
+function isMounted(component) {
+  {
+    var owner = ReactCurrentOwner.current;
+    if (owner !== null && owner.tag === ClassComponent) {
+      var ownerFiber = owner;
+      var instance = ownerFiber.stateNode;
+      !instance._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing isMounted inside its render() function. " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(ownerFiber) || "A component"
+          )
+        : void 0;
+      instance._warnedAboutRefsInRender = true;
+    }
+  }
+
+  var fiber = get$1(component);
+  if (!fiber) {
+    return false;
+  }
+  return isFiberMountedImpl(fiber) === MOUNTED;
+}
+
+function assertIsMounted(fiber) {
+  invariant(
+    isFiberMountedImpl(fiber) === MOUNTED,
+    "Unable to find node on an unmounted component."
+  );
+}
+
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate) {
+    // If there is no alternate, then we only need to check if it is mounted.
+    var state = isFiberMountedImpl(fiber);
+    invariant(
+      state !== UNMOUNTED,
+      "Unable to find node on an unmounted component."
+    );
+    if (state === MOUNTING) {
+      return null;
+    }
+    return fiber;
+  }
+  // If we have two possible branches, we'll walk backwards up to the root
+  // to see what path the root points to. On the way we may hit one of the
+  // special cases and we'll deal with them.
+  var a = fiber;
+  var b = alternate;
+  while (true) {
+    var parentA = a["return"];
+    var parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) {
+      // We're at the root.
+      break;
+    }
+
+    // If both copies of the parent fiber point to the same child, we can
+    // assume that the child is current. This happens when we bailout on low
+    // priority: the bailed out fiber's child reuses the current child.
+    if (parentA.child === parentB.child) {
+      var child = parentA.child;
+      while (child) {
+        if (child === a) {
+          // We've determined that A is the current branch.
+          assertIsMounted(parentA);
+          return fiber;
+        }
+        if (child === b) {
+          // We've determined that B is the current branch.
+          assertIsMounted(parentA);
+          return alternate;
+        }
+        child = child.sibling;
+      }
+      // We should never have an alternate for any mounting node. So the only
+      // way this could possibly happen is if this was unmounted, if at all.
+      invariant(false, "Unable to find node on an unmounted component.");
+    }
+
+    if (a["return"] !== b["return"]) {
+      // The return pointer of A and the return pointer of B point to different
+      // fibers. We assume that return pointers never criss-cross, so A must
+      // belong to the child set of A.return, and B must belong to the child
+      // set of B.return.
+      a = parentA;
+      b = parentB;
+    } else {
+      // The return pointers point to the same fiber. We'll have to use the
+      // default, slow path: scan the child sets of each parent alternate to see
+      // which child belongs to which set.
+      //
+      // Search parent A's child set
+      var didFindChild = false;
+      var _child = parentA.child;
+      while (_child) {
+        if (_child === a) {
+          didFindChild = true;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          didFindChild = true;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!didFindChild) {
+        // Search parent B's child set
+        _child = parentB.child;
+        while (_child) {
+          if (_child === a) {
+            didFindChild = true;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            didFindChild = true;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          didFindChild,
+          "Child was not found in either parent set. This indicates a bug " +
+            "in React related to the return pointer. Please file an issue."
+        );
+      }
+    }
+
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+  // If the root is not a host container, we're in a disconnected tree. I.e.
+  // unmounted.
+  invariant(
+    a.tag === HostRoot,
+    "Unable to find node on an unmounted component."
+  );
+  if (a.stateNode.current === a) {
+    // We've determined that A is the current branch.
+    return fiber;
+  }
+  // Otherwise B has to be current branch.
+  return alternate;
+}
+
+function findCurrentHostFiber(parent) {
+  var currentParent = findCurrentFiberUsingSlowPath(parent);
+  if (!currentParent) {
+    return null;
+  }
+
+  // Next we'll drill down this component to find the first HostComponent/Text.
+  var node = currentParent;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      return node;
+    } else if (node.child) {
+      node.child["return"] = node;
+      node = node.child;
+      continue;
+    }
+    if (node === currentParent) {
+      return null;
+    }
+    while (!node.sibling) {
+      if (!node["return"] || node["return"] === currentParent) {
+        return null;
+      }
+      node = node["return"];
+    }
+    node.sibling["return"] = node["return"];
+    node = node.sibling;
+  }
+  // Flow needs the return null here, but ESLint complains about it.
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
+
+function findCurrentHostFiberWithNoPortals(parent) {
+  var currentParent = findCurrentFiberUsingSlowPath(parent);
+  if (!currentParent) {
+    return null;
+  }
+
+  // Next we'll drill down this component to find the first HostComponent/Text.
+  var node = currentParent;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      return node;
+    } else if (node.child && node.tag !== HostPortal) {
+      node.child["return"] = node;
+      node = node.child;
+      continue;
+    }
+    if (node === currentParent) {
+      return null;
+    }
+    while (!node.sibling) {
+      if (!node["return"] || node["return"] === currentParent) {
+        return null;
+      }
+      node = node["return"];
+    }
+    node.sibling["return"] = node["return"];
+    node = node.sibling;
+  }
+  // Flow needs the return null here, but ESLint complains about it.
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
+
+// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
+// Math.pow(2, 30) - 1
+// 0b111111111111111111111111111111
+var MAX_SIGNED_31_BIT_INT = 1073741823;
+
+// TODO: Use an opaque type once ESLint et al support the syntax
+
+var NoWork = 0;
+var Sync = 1;
+var Never = MAX_SIGNED_31_BIT_INT;
+
+var UNIT_SIZE = 10;
+var MAGIC_NUMBER_OFFSET = 2;
+
+// 1 unit of expiration time represents 10ms.
+function msToExpirationTime(ms) {
+  // Always add an offset so that we don't clash with the magic number for NoWork.
+  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
+}
+
+function expirationTimeToMs(expirationTime) {
+  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
+}
+
+function ceiling(num, precision) {
+  return (((num / precision) | 0) + 1) * precision;
+}
+
+function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
+  return ceiling(
+    currentTime + expirationInMs / UNIT_SIZE,
+    bucketSizeMs / UNIT_SIZE
+  );
+}
+
+var NoContext = 0;
+var AsyncMode = 1;
+var StrictMode = 2;
+
+var hasBadMapPolyfill = void 0;
+
+{
+  hasBadMapPolyfill = false;
+  try {
+    var nonExtensibleObject = Object.preventExtensions({});
+    var testMap = new Map([[nonExtensibleObject, null]]);
+    var testSet = new Set([nonExtensibleObject]);
+    // This is necessary for Rollup to not consider these unused.
+    // https://github.com/rollup/rollup/issues/1771
+    // TODO: we can remove these if Rollup fixes the bug.
+    testMap.set(0, 0);
+    testSet.add(0);
+  } catch (e) {
+    // TODO: Consider warning about bad polyfills
+    hasBadMapPolyfill = true;
+  }
+}
+
+// A Fiber is work on a Component that needs to be done or was done. There can
+// be more than one per component.
+
+var debugCounter = void 0;
+
+{
+  debugCounter = 1;
+}
+
+function FiberNode(tag, pendingProps, key, mode) {
+  // Instance
+  this.tag = tag;
+  this.key = key;
+  this.type = null;
+  this.stateNode = null;
+
+  // Fiber
+  this["return"] = null;
+  this.child = null;
+  this.sibling = null;
+  this.index = 0;
+
+  this.ref = null;
+
+  this.pendingProps = pendingProps;
+  this.memoizedProps = null;
+  this.updateQueue = null;
+  this.memoizedState = null;
+
+  this.mode = mode;
+
+  // Effects
+  this.effectTag = NoEffect;
+  this.nextEffect = null;
+
+  this.firstEffect = null;
+  this.lastEffect = null;
+
+  this.expirationTime = NoWork;
+
+  this.alternate = null;
+
+  {
+    this._debugID = debugCounter++;
+    this._debugSource = null;
+    this._debugOwner = null;
+    this._debugIsCurrentlyTiming = false;
+    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
+      Object.preventExtensions(this);
+    }
+  }
+}
+
+// This is a constructor function, rather than a POJO constructor, still
+// please ensure we do the following:
+// 1) Nobody should add any instance methods on this. Instance methods can be
+//    more difficult to predict when they get optimized and they are almost
+//    never inlined properly in static compilers.
+// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
+//    always know when it is a fiber.
+// 3) We might want to experiment with using numeric keys since they are easier
+//    to optimize in a non-JIT environment.
+// 4) We can easily go from a constructor to a createFiber object literal if that
+//    is faster.
+// 5) It should be easy to port this to a C struct and keep a C implementation
+//    compatible.
+var createFiber = function(tag, pendingProps, key, mode) {
+  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
+  return new FiberNode(tag, pendingProps, key, mode);
+};
+
+function shouldConstruct(Component) {
+  return !!(Component.prototype && Component.prototype.isReactComponent);
+}
+
+// This is used to create an alternate fiber to do work on.
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  if (workInProgress === null) {
+    // We use a double buffering pooling technique because we know that we'll
+    // only ever need at most two versions of a tree. We pool the "other" unused
+    // node that we're free to reuse. This is lazily created to avoid allocating
+    // extra objects for things that are never updated. It also allow us to
+    // reclaim the extra memory if needed.
+    workInProgress = createFiber(
+      current.tag,
+      pendingProps,
+      current.key,
+      current.mode
+    );
+    workInProgress.type = current.type;
+    workInProgress.stateNode = current.stateNode;
+
+    {
+      // DEV-only fields
+      workInProgress._debugID = current._debugID;
+      workInProgress._debugSource = current._debugSource;
+      workInProgress._debugOwner = current._debugOwner;
+    }
+
+    workInProgress.alternate = current;
+    current.alternate = workInProgress;
+  } else {
+    workInProgress.pendingProps = pendingProps;
+
+    // We already have an alternate.
+    // Reset the effect tag.
+    workInProgress.effectTag = NoEffect;
+
+    // The effect list is no longer valid.
+    workInProgress.nextEffect = null;
+    workInProgress.firstEffect = null;
+    workInProgress.lastEffect = null;
+  }
+
+  workInProgress.expirationTime = expirationTime;
+
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+
+  // These will be overridden during the parent's reconciliation
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+
+  return workInProgress;
+}
+
+function createHostRootFiber(isAsync) {
+  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
+  return createFiber(HostRoot, null, null, mode);
+}
+
+function createFiberFromElement(element, mode, expirationTime) {
+  var owner = null;
+  {
+    owner = element._owner;
+  }
+
+  var fiber = void 0;
+  var type = element.type;
+  var key = element.key;
+  var pendingProps = element.props;
+
+  var fiberTag = void 0;
+  if (typeof type === "function") {
+    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
+  } else if (typeof type === "string") {
+    fiberTag = HostComponent;
+  } else {
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          pendingProps.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= AsyncMode | StrictMode;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= StrictMode;
+        break;
+      case REACT_CALL_TYPE:
+        fiberTag = CallComponent;
+        break;
+      case REACT_RETURN_TYPE:
+        fiberTag = ReturnComponent;
+        break;
+      default: {
+        if (typeof type === "object" && type !== null) {
+          switch (type.$$typeof) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = ContextProvider;
+              break;
+            case REACT_CONTEXT_TYPE:
+              // This is a consumer
+              fiberTag = ContextConsumer;
+              break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = ForwardRef;
+              break;
+            default:
+              if (typeof type.tag === "number") {
+                // Currently assumed to be a continuation and therefore is a
+                // fiber already.
+                // TODO: The yield system is currently broken for updates in
+                // some cases. The reified yield stores a fiber, but we don't
+                // know which fiber that is; the current or a workInProgress?
+                // When the continuation gets rendered here we don't know if we
+                // can reuse that fiber or if we need to clone it. There is
+                // probably a clever way to restructure this.
+                fiber = type;
+                fiber.pendingProps = pendingProps;
+                fiber.expirationTime = expirationTime;
+                return fiber;
+              } else {
+                throwOnInvalidElementType(type, owner);
+              }
+              break;
+          }
+        } else {
+          throwOnInvalidElementType(type, owner);
+        }
+      }
+    }
+  }
+
+  fiber = createFiber(fiberTag, pendingProps, key, mode);
+  fiber.type = type;
+  fiber.expirationTime = expirationTime;
+
+  {
+    fiber._debugSource = element._source;
+    fiber._debugOwner = element._owner;
+  }
+
+  return fiber;
+}
+
+function throwOnInvalidElementType(type, owner) {
+  var info = "";
+  {
+    if (
+      type === undefined ||
+      (typeof type === "object" &&
+        type !== null &&
+        Object.keys(type).length === 0)
+    ) {
+      info +=
+        " You likely forgot to export your component from the file " +
+        "it's defined in, or you might have mixed up default and " +
+        "named imports.";
+    }
+    var ownerName = owner ? getComponentName(owner) : null;
+    if (ownerName) {
+      info += "\n\nCheck the render method of `" + ownerName + "`.";
+    }
+  }
+  invariant(
+    false,
+    "Element type is invalid: expected a string (for built-in " +
+      "components) or a class/function (for composite components) " +
+      "but got: %s.%s",
+    type == null ? type : typeof type,
+    info
+  );
+}
+
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  var fiber = createFiber(Fragment, elements, key, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
+}
+
+function createFiberFromText(content, mode, expirationTime) {
+  var fiber = createFiber(HostText, content, null, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
+}
+
+function createFiberFromHostInstanceForDeletion() {
+  var fiber = createFiber(HostComponent, null, null, NoContext);
+  fiber.type = "DELETED";
+  return fiber;
+}
+
+function createFiberFromPortal(portal, mode, expirationTime) {
+  var pendingProps = portal.children !== null ? portal.children : [];
+  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null, // Used by persistent updates
+    implementation: portal.implementation
+  };
+  return fiber;
+}
+
+// Used for stashing WIP properties to replay failed work in DEV.
+function assignFiberPropertiesInDEV(target, source) {
+  if (target === null) {
+    // This Fiber's initial properties will always be overwritten.
+    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
+    target = createFiber(IndeterminateComponent, null, null, NoContext);
+  }
+
+  // This is intentionally written as a list of all properties.
+  // We tried to use Object.assign() instead but this is called in
+  // the hottest path, and Object.assign() was too slow:
+  // https://github.com/facebook/react/issues/12502
+  // This code is DEV-only so size is not a concern.
+
+  target.tag = source.tag;
+  target.key = source.key;
+  target.type = source.type;
+  target.stateNode = source.stateNode;
+  target["return"] = source["return"];
+  target.child = source.child;
+  target.sibling = source.sibling;
+  target.index = source.index;
+  target.ref = source.ref;
+  target.pendingProps = source.pendingProps;
+  target.memoizedProps = source.memoizedProps;
+  target.updateQueue = source.updateQueue;
+  target.memoizedState = source.memoizedState;
+  target.mode = source.mode;
+  target.effectTag = source.effectTag;
+  target.nextEffect = source.nextEffect;
+  target.firstEffect = source.firstEffect;
+  target.lastEffect = source.lastEffect;
+  target.expirationTime = source.expirationTime;
+  target.alternate = source.alternate;
+  target._debugID = source._debugID;
+  target._debugSource = source._debugSource;
+  target._debugOwner = source._debugOwner;
+  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
+  return target;
+}
+
+// TODO: This should be lifted into the renderer.
+
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  // Cyclic construction. This cheats the type system right now because
+  // stateNode is any.
+  var uninitializedFiber = createHostRootFiber(isAsync);
+  var root = {
+    current: uninitializedFiber,
+    containerInfo: containerInfo,
+    pendingChildren: null,
+    pendingCommitExpirationTime: NoWork,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    remainingExpirationTime: NoWork,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  uninitializedFiber.stateNode = root;
+  return root;
+}
+
+var onCommitFiberRoot = null;
+var onCommitFiberUnmount = null;
+var hasLoggedError = false;
+
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {
+      if (true && !hasLoggedError) {
+        hasLoggedError = true;
+        warning(false, "React DevTools encountered an error: %s", err);
+      }
+    }
+  };
+}
+
+function injectInternals(internals) {
+  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
+    // No DevTools
+    return false;
+  }
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled) {
+    // This isn't a real property on the hook, but it can be set to opt out
+    // of DevTools integration and associated warnings and logs.
+    // https://github.com/facebook/react/issues/3877
+    return true;
+  }
+  if (!hook.supportsFiber) {
+    {
+      warning(
+        false,
+        "The installed version of React DevTools is too old and will not work " +
+          "with the current version of React. Please update React DevTools. " +
+          "https://fb.me/react-devtools"
+      );
+    }
+    // DevTools exists, even though it doesn't support Fiber.
+    return true;
+  }
+  try {
+    var rendererID = hook.inject(internals);
+    // We have successfully injected, so now it is safe to set up hooks.
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {
+    // Catch all errors because it is unsafe to throw during initialization.
+    {
+      warning(false, "React DevTools encountered an error: %s.", err);
+    }
+  }
+  // DevTools exists
+  return true;
+}
+
+function onCommitRoot(root) {
+  if (typeof onCommitFiberRoot === "function") {
+    onCommitFiberRoot(root);
+  }
+}
+
+function onCommitUnmount(fiber) {
+  if (typeof onCommitFiberUnmount === "function") {
+    onCommitFiberUnmount(fiber);
+  }
+}
+
+/**
+ * Forked from fbjs/warning:
+ * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
+ *
+ * Only change is we use console.warn instead of console.error,
+ * and do nothing when 'console' is not supported.
+ * This really simplifies the code.
+ * ---
+ * Similar to invariant but only logs a warning if the condition is not met.
+ * This can be used to log issues in development environments in critical
+ * paths. Removing the logging code for production environments will keep the
+ * same logic and follow the same code paths.
+ */
+
+var lowPriorityWarning = function() {};
+
+{
+  var printWarning = function(format) {
+    for (
+      var _len = arguments.length,
+        args = Array(_len > 1 ? _len - 1 : 0),
+        _key = 1;
+      _key < _len;
+      _key++
+    ) {
+      args[_key - 1] = arguments[_key];
+    }
+
+    var argIndex = 0;
+    var message =
+      "Warning: " +
+      format.replace(/%s/g, function() {
+        return args[argIndex++];
+      });
+    if (typeof console !== "undefined") {
+      console.warn(message);
+    }
+    try {
+      // --- Welcome to debugging React ---
+      // This error was thrown as a convenience so that you can use this stack
+      // to find the callsite that caused this warning to fire.
+      throw new Error(message);
+    } catch (x) {}
+  };
+
+  lowPriorityWarning = function(condition, format) {
+    if (format === undefined) {
+      throw new Error(
+        "`warning(condition, format, ...args)` requires a warning " +
+          "message argument"
+      );
+    }
+    if (!condition) {
+      for (
+        var _len2 = arguments.length,
+          args = Array(_len2 > 2 ? _len2 - 2 : 0),
+          _key2 = 2;
+        _key2 < _len2;
+        _key2++
+      ) {
+        args[_key2 - 2] = arguments[_key2];
+      }
+
+      printWarning.apply(undefined, [format].concat(args));
+    }
+  };
+}
+
+var lowPriorityWarning$1 = lowPriorityWarning;
+
+var ReactStrictModeWarnings = {
+  discardPendingWarnings: function() {},
+  flushPendingDeprecationWarnings: function() {},
+  flushPendingUnsafeLifecycleWarnings: function() {},
+  recordDeprecationWarnings: function(fiber, instance) {},
+  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
+};
+
+{
+  var LIFECYCLE_SUGGESTIONS = {
+    UNSAFE_componentWillMount: "componentDidMount",
+    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
+    UNSAFE_componentWillUpdate: "componentDidUpdate"
+  };
+
+  var pendingComponentWillMountWarnings = [];
+  var pendingComponentWillReceivePropsWarnings = [];
+  var pendingComponentWillUpdateWarnings = [];
+  var pendingUnsafeLifecycleWarnings = new Map();
+
+  // Tracks components we have already warned about.
+  var didWarnAboutDeprecatedLifecycles = new Set();
+  var didWarnAboutUnsafeLifecycles = new Set();
+
+  var setToSortedString = function(set) {
+    var array = [];
+    set.forEach(function(value) {
+      array.push(value);
+    });
+    return array.sort().join(", ");
+  };
+
+  ReactStrictModeWarnings.discardPendingWarnings = function() {
+    pendingComponentWillMountWarnings = [];
+    pendingComponentWillReceivePropsWarnings = [];
+    pendingComponentWillUpdateWarnings = [];
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
+
+  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
+    pendingUnsafeLifecycleWarnings.forEach(function(
+      lifecycleWarningsMap,
+      strictRoot
+    ) {
+      var lifecyclesWarningMesages = [];
+
+      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
+        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
+        if (lifecycleWarnings.length > 0) {
+          var componentNames = new Set();
+          lifecycleWarnings.forEach(function(fiber) {
+            componentNames.add(getComponentName(fiber) || "Component");
+            didWarnAboutUnsafeLifecycles.add(fiber.type);
+          });
+
+          var formatted = lifecycle.replace("UNSAFE_", "");
+          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
+          var sortedComponentNames = setToSortedString(componentNames);
+
+          lifecyclesWarningMesages.push(
+            formatted +
+              ": Please update the following components to use " +
+              (suggestion + " instead: " + sortedComponentNames)
+          );
+        }
+      });
+
+      if (lifecyclesWarningMesages.length > 0) {
+        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+          strictRoot
+        );
+
+        warning(
+          false,
+          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
+            "\n\n%s" +
+            "\n\nLearn more about this warning here:" +
+            "\nhttps://fb.me/react-strict-mode-warnings",
+          strictRootComponentStack,
+          lifecyclesWarningMesages.join("\n\n")
+        );
+      }
+    });
+
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
+
+  var getStrictRoot = function(fiber) {
+    var maybeStrictRoot = null;
+
+    while (fiber !== null) {
+      if (fiber.mode & StrictMode) {
+        maybeStrictRoot = fiber;
+      }
+
+      fiber = fiber["return"];
+    }
+
+    return maybeStrictRoot;
+  };
+
+  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
+    if (pendingComponentWillMountWarnings.length > 0) {
+      var uniqueNames = new Set();
+      pendingComponentWillMountWarnings.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var sortedNames = setToSortedString(uniqueNames);
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillMount is deprecated and will be removed in the next major version. " +
+          "Use componentDidMount instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillMount." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        sortedNames
+      );
+
+      pendingComponentWillMountWarnings = [];
+    }
+
+    if (pendingComponentWillReceivePropsWarnings.length > 0) {
+      var _uniqueNames = new Set();
+      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
+        _uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var _sortedNames = setToSortedString(_uniqueNames);
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
+          "Use static getDerivedStateFromProps instead." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames
+      );
+
+      pendingComponentWillReceivePropsWarnings = [];
+    }
+
+    if (pendingComponentWillUpdateWarnings.length > 0) {
+      var _uniqueNames2 = new Set();
+      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
+        _uniqueNames2.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var _sortedNames2 = setToSortedString(_uniqueNames2);
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillUpdate is deprecated and will be removed in the next major version. " +
+          "Use componentDidUpdate instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillUpdate." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames2
+      );
+
+      pendingComponentWillUpdateWarnings = [];
+    }
+  };
+
+  ReactStrictModeWarnings.recordDeprecationWarnings = function(
+    fiber,
+    instance
+  ) {
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
+      return;
+    }
+
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillMountWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" &&
+      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillReceivePropsWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillUpdate === "function" &&
+      instance.componentWillUpdate.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillUpdateWarnings.push(fiber);
+    }
+  };
+
+  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = getStrictRoot(fiber);
+
+    // Dedup strategy: Warn once per component.
+    // This is difficult to track any other way since component names
+    // are often vague and are likely to collide between 3rd party libraries.
+    // An expand property is probably okay to use here since it's DEV-only,
+    // and will only be set in the event of serious warnings.
+    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+      return;
+    }
+
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    // Note that it is sufficient to check for the presence of a
+    // single lifecycle, componentWillMount, with the polyfill flag.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning === true
+    ) {
+      return;
+    }
+
+    var warningsForRoot = void 0;
+    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
+      warningsForRoot = {
+        UNSAFE_componentWillMount: [],
+        UNSAFE_componentWillReceiveProps: [],
+        UNSAFE_componentWillUpdate: []
+      };
+
+      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
+    } else {
+      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
+    }
+
+    var unsafeLifecycles = [];
+    if (
+      typeof instance.componentWillMount === "function" ||
+      typeof instance.UNSAFE_componentWillMount === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillMount");
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" ||
+      typeof instance.UNSAFE_componentWillReceiveProps === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    }
+    if (
+      typeof instance.componentWillUpdate === "function" ||
+      typeof instance.UNSAFE_componentWillUpdate === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
+    }
+
+    if (unsafeLifecycles.length > 0) {
+      unsafeLifecycles.forEach(function(lifecycle) {
+        warningsForRoot[lifecycle].push(fiber);
+      });
+    }
+  };
+}
+
+var debugRenderPhaseSideEffects = false;
+var debugRenderPhaseSideEffectsForStrictMode = false;
+var enableGetDerivedStateFromCatch = false;
+var enableMutatingReconciler = true;
+var enableNoopReconciler = false;
+var enablePersistentReconciler = false;
+var enableUserTimingAPI = true;
+var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
+var warnAboutDeprecatedLifecycles = false;
+
+// Only used in www builds.
+
+function getCurrentFiberOwnerName() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    var owner = fiber._debugOwner;
+    if (owner !== null && typeof owner !== "undefined") {
+      return getComponentName(owner);
+    }
+  }
+  return null;
+}
+
+function getCurrentFiberStackAddendum() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    // Safe because if current fiber exists, we are reconciling,
+    // and it is guaranteed to be the work-in-progress version.
+    return getStackAddendumByWorkInProgressFiber(fiber);
+  }
+  return null;
+}
+
+function resetCurrentFiber() {
+  ReactDebugCurrentFrame.getCurrentStack = null;
+  ReactDebugCurrentFiber.current = null;
+  ReactDebugCurrentFiber.phase = null;
+}
+
+function setCurrentFiber(fiber) {
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
+  ReactDebugCurrentFiber.current = fiber;
+  ReactDebugCurrentFiber.phase = null;
+}
+
+function setCurrentPhase(phase) {
+  ReactDebugCurrentFiber.phase = phase;
+}
+
+var ReactDebugCurrentFiber = {
+  current: null,
+  phase: null,
+  resetCurrentFiber: resetCurrentFiber,
+  setCurrentFiber: setCurrentFiber,
+  setCurrentPhase: setCurrentPhase,
+  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
+};
+
+// Prefix measurements so that it's possible to filter them.
+// Longer prefixes are hard to read in DevTools.
+var reactEmoji = "\u269B";
+var warningEmoji = "\u26D4";
+var supportsUserTiming =
+  typeof performance !== "undefined" &&
+  typeof performance.mark === "function" &&
+  typeof performance.clearMarks === "function" &&
+  typeof performance.measure === "function" &&
+  typeof performance.clearMeasures === "function";
+
+// Keep track of current fiber so that we know the path to unwind on pause.
+// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
+var currentFiber = null;
+// If we're in the middle of user code, which fiber and method is it?
+// Reusing `currentFiber` would be confusing for this because user code fiber
+// can change during commit phase too, but we don't need to unwind it (since
+// lifecycles in the commit phase don't resemble a tree).
+var currentPhase = null;
+var currentPhaseFiber = null;
+// Did lifecycle hook schedule an update? This is often a performance problem,
+// so we will keep track of it, and include it in the report.
+// Track commits caused by cascading updates.
+var isCommitting = false;
+var hasScheduledUpdateInCurrentCommit = false;
+var hasScheduledUpdateInCurrentPhase = false;
+var commitCountInCurrentWorkLoop = 0;
+var effectCountInCurrentCommit = 0;
+var isWaitingForCallback = false;
+// During commits, we only show a measurement once per method name
+// to avoid stretch the commit phase with measurement overhead.
+var labelsInCurrentCommit = new Set();
+
+var formatMarkName = function(markName) {
+  return reactEmoji + " " + markName;
+};
+
+var formatLabel = function(label, warning$$1) {
+  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
+  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
+  return "" + prefix + label + suffix;
+};
+
+var beginMark = function(markName) {
+  performance.mark(formatMarkName(markName));
+};
+
+var clearMark = function(markName) {
+  performance.clearMarks(formatMarkName(markName));
+};
+
+var endMark = function(label, markName, warning$$1) {
+  var formattedMarkName = formatMarkName(markName);
+  var formattedLabel = formatLabel(label, warning$$1);
+  try {
+    performance.measure(formattedLabel, formattedMarkName);
+  } catch (err) {}
+  // If previous mark was missing for some reason, this will throw.
+  // This could only happen if React crashed in an unexpected place earlier.
+  // Don't pile on with more errors.
+
+  // Clear marks immediately to avoid growing buffer.
+  performance.clearMarks(formattedMarkName);
+  performance.clearMeasures(formattedLabel);
+};
+
+var getFiberMarkName = function(label, debugID) {
+  return label + " (#" + debugID + ")";
+};
+
+var getFiberLabel = function(componentName, isMounted, phase) {
+  if (phase === null) {
+    // These are composite component total time measurements.
+    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
+  } else {
+    // Composite component methods.
+    return componentName + "." + phase;
+  }
+};
+
+var beginFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+
+  if (isCommitting && labelsInCurrentCommit.has(label)) {
+    // During the commit phase, we don't show duplicate labels because
+    // there is a fixed overhead for every measurement, and we don't
+    // want to stretch the commit phase beyond necessary.
+    return false;
+  }
+  labelsInCurrentCommit.add(label);
+
+  var markName = getFiberMarkName(label, debugID);
+  beginMark(markName);
+  return true;
+};
+
+var clearFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  clearMark(markName);
+};
+
+var endFiberMark = function(fiber, phase, warning$$1) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  endMark(label, markName, warning$$1);
+};
+
+var shouldIgnoreFiber = function(fiber) {
+  // Host components should be skipped in the timeline.
+  // We could check typeof fiber.type, but does this work with RN?
+  switch (fiber.tag) {
+    case HostRoot:
+    case HostComponent:
+    case HostText:
+    case HostPortal:
+    case CallComponent:
+    case ReturnComponent:
+    case Fragment:
+    case ContextProvider:
+    case ContextConsumer:
+    case Mode:
+      return true;
+    default:
+      return false;
+  }
+};
+
+var clearPendingPhaseMeasurement = function() {
+  if (currentPhase !== null && currentPhaseFiber !== null) {
+    clearFiberMark(currentPhaseFiber, currentPhase);
+  }
+  currentPhaseFiber = null;
+  currentPhase = null;
+  hasScheduledUpdateInCurrentPhase = false;
+};
+
+var pauseTimers = function() {
+  // Stops all currently active measurements so that they can be resumed
+  // if we continue in a later deferred loop from the same unit of work.
+  var fiber = currentFiber;
+  while (fiber) {
+    if (fiber._debugIsCurrentlyTiming) {
+      endFiberMark(fiber, null, null);
+    }
+    fiber = fiber["return"];
+  }
+};
+
+var resumeTimersRecursively = function(fiber) {
+  if (fiber["return"] !== null) {
+    resumeTimersRecursively(fiber["return"]);
+  }
+  if (fiber._debugIsCurrentlyTiming) {
+    beginFiberMark(fiber, null);
+  }
+};
+
+var resumeTimers = function() {
+  // Resumes all measurements that were active during the last deferred loop.
+  if (currentFiber !== null) {
+    resumeTimersRecursively(currentFiber);
+  }
+};
+
+function recordEffect() {
+  if (enableUserTimingAPI) {
+    effectCountInCurrentCommit++;
+  }
+}
+
+function recordScheduleUpdate() {
+  if (enableUserTimingAPI) {
+    if (isCommitting) {
+      hasScheduledUpdateInCurrentCommit = true;
+    }
+    if (
+      currentPhase !== null &&
+      currentPhase !== "componentWillMount" &&
+      currentPhase !== "componentWillReceiveProps"
+    ) {
+      hasScheduledUpdateInCurrentPhase = true;
+    }
+  }
+}
+
+function startRequestCallbackTimer() {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming && !isWaitingForCallback) {
+      isWaitingForCallback = true;
+      beginMark("(Waiting for async callback...)");
+    }
+  }
+}
+
+function stopRequestCallbackTimer(didExpire, expirationTime) {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming) {
+      isWaitingForCallback = false;
+      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
+      endMark(
+        "(Waiting for async callback... will force flush in " +
+          expirationTime +
+          " ms)",
+        "(Waiting for async callback...)",
+        warning$$1
+      );
+    }
+  }
+}
+
+function startWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, this is the fiber to unwind from.
+    currentFiber = fiber;
+    if (!beginFiberMark(fiber, null)) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = true;
+  }
+}
+
+function cancelWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // Remember we shouldn't complete measurement for this fiber.
+    // Otherwise flamechart will be deep even for small updates.
+    fiber._debugIsCurrentlyTiming = false;
+    clearFiberMark(fiber, null);
+  }
+}
+
+function stopWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber["return"];
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = false;
+    endFiberMark(fiber, null, null);
+  }
+}
+
+function stopFailedWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber["return"];
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = false;
+    var warning$$1 = "An error was thrown inside this error boundary";
+    endFiberMark(fiber, null, warning$$1);
+  }
+}
+
+function startPhaseTimer(fiber, phase) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    clearPendingPhaseMeasurement();
+    if (!beginFiberMark(fiber, phase)) {
+      return;
+    }
+    currentPhaseFiber = fiber;
+    currentPhase = phase;
+  }
+}
+
+function stopPhaseTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    if (currentPhase !== null && currentPhaseFiber !== null) {
+      var warning$$1 = hasScheduledUpdateInCurrentPhase
+        ? "Scheduled a cascading update"
+        : null;
+      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
+    }
+    currentPhase = null;
+    currentPhaseFiber = null;
+  }
+}
+
+function startWorkLoopTimer(nextUnitOfWork) {
+  if (enableUserTimingAPI) {
+    currentFiber = nextUnitOfWork;
+    if (!supportsUserTiming) {
+      return;
+    }
+    commitCountInCurrentWorkLoop = 0;
+    // This is top level call.
+    // Any other measurements are performed within.
+    beginMark("(React Tree Reconciliation)");
+    // Resume any measurements that were in progress during the last loop.
+    resumeTimers();
+  }
+}
+
+function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var warning$$1 = null;
+    if (interruptedBy !== null) {
+      if (interruptedBy.tag === HostRoot) {
+        warning$$1 = "A top-level update interrupted the previous render";
+      } else {
+        var componentName = getComponentName(interruptedBy) || "Unknown";
+        warning$$1 =
+          "An update to " + componentName + " interrupted the previous render";
+      }
+    } else if (commitCountInCurrentWorkLoop > 1) {
+      warning$$1 = "There were cascading updates";
+    }
+    commitCountInCurrentWorkLoop = 0;
+    var label = didCompleteRoot
+      ? "(React Tree Reconciliation: Completed Root)"
+      : "(React Tree Reconciliation: Yielded)";
+    // Pause any measurements until the next loop.
+    pauseTimers();
+    endMark(label, "(React Tree Reconciliation)", warning$$1);
+  }
+}
+
+function startCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    isCommitting = true;
+    hasScheduledUpdateInCurrentCommit = false;
+    labelsInCurrentCommit.clear();
+    beginMark("(Committing Changes)");
+  }
+}
+
+function stopCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+
+    var warning$$1 = null;
+    if (hasScheduledUpdateInCurrentCommit) {
+      warning$$1 = "Lifecycle hook scheduled a cascading update";
+    } else if (commitCountInCurrentWorkLoop > 0) {
+      warning$$1 = "Caused by a cascading update in earlier commit";
+    }
+    hasScheduledUpdateInCurrentCommit = false;
+    commitCountInCurrentWorkLoop++;
+    isCommitting = false;
+    labelsInCurrentCommit.clear();
+
+    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
+  }
+}
+
+function startCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Snapshot Effects)");
+  }
+}
+
+function stopCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Snapshot Effects: " + count + " Total)",
+      "(Committing Snapshot Effects)",
+      null
+    );
+  }
+}
+
+function startCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Host Effects)");
+  }
+}
+
+function stopCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Host Effects: " + count + " Total)",
+      "(Committing Host Effects)",
+      null
+    );
+  }
+}
+
+function startCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Calling Lifecycle Methods)");
+  }
+}
+
+function stopCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Calling Lifecycle Methods: " + count + " Total)",
+      "(Calling Lifecycle Methods)",
+      null
+    );
+  }
+}
+
+var didWarnUpdateInsideUpdate = void 0;
+
+{
+  didWarnUpdateInsideUpdate = false;
+}
+
+// Callbacks are not validated until invocation
+
+// Singly linked-list of updates. When an update is scheduled, it is added to
+// the queue of the current fiber and the work-in-progress fiber. The two queues
+// are separate but they share a persistent structure.
+//
+// During reconciliation, updates are removed from the work-in-progress fiber,
+// but they remain on the current fiber. That ensures that if a work-in-progress
+// is aborted, the aborted updates are recovered by cloning from current.
+//
+// The work-in-progress queue is always a subset of the current queue.
+//
+// When the tree is committed, the work-in-progress becomes the current.
+
+function createUpdateQueue(baseState) {
+  var queue = {
+    baseState: baseState,
+    expirationTime: NoWork,
+    first: null,
+    last: null,
+    callbackList: null,
+    hasForceUpdate: false,
+    isInitialized: false,
+    capturedValues: null
+  };
+  {
+    queue.isProcessing = false;
+  }
+  return queue;
+}
+
+function insertUpdateIntoQueue(queue, update) {
+  // Append the update to the end of the list.
+  if (queue.last === null) {
+    // Queue is empty
+    queue.first = queue.last = update;
+  } else {
+    queue.last.next = update;
+    queue.last = update;
+  }
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > update.expirationTime
+  ) {
+    queue.expirationTime = update.expirationTime;
+  }
+}
+
+var q1 = void 0;
+var q2 = void 0;
+function ensureUpdateQueues(fiber) {
+  q1 = q2 = null;
+  // We'll have at least one and at most two distinct update queues.
+  var alternateFiber = fiber.alternate;
+  var queue1 = fiber.updateQueue;
+  if (queue1 === null) {
+    // TODO: We don't know what the base state will be until we begin work.
+    // It depends on which fiber is the next current. Initialize with an empty
+    // base state, then set to the memoizedState when rendering. Not super
+    // happy with this approach.
+    queue1 = fiber.updateQueue = createUpdateQueue(null);
+  }
+
+  var queue2 = void 0;
+  if (alternateFiber !== null) {
+    queue2 = alternateFiber.updateQueue;
+    if (queue2 === null) {
+      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
+    }
+  } else {
+    queue2 = null;
+  }
+  queue2 = queue2 !== queue1 ? queue2 : null;
+
+  // Use module variables instead of returning a tuple
+  q1 = queue1;
+  q2 = queue2;
+}
+
+function insertUpdateIntoFiber(fiber, update) {
+  ensureUpdateQueues(fiber);
+  var queue1 = q1;
+  var queue2 = q2;
+
+  // Warn if an update is scheduled from inside an updater function.
+  {
+    if (
+      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
+      !didWarnUpdateInsideUpdate
+    ) {
+      warning(
+        false,
+        "An update (setState, replaceState, or forceUpdate) was scheduled " +
+          "from inside an update function. Update functions should be pure, " +
+          "with zero side-effects. Consider using componentDidUpdate or a " +
+          "callback."
+      );
+      didWarnUpdateInsideUpdate = true;
+    }
+  }
+
+  // If there's only one queue, add the update to that queue and exit.
+  if (queue2 === null) {
+    insertUpdateIntoQueue(queue1, update);
+    return;
+  }
+
+  // If either queue is empty, we need to add to both queues.
+  if (queue1.last === null || queue2.last === null) {
+    insertUpdateIntoQueue(queue1, update);
+    insertUpdateIntoQueue(queue2, update);
+    return;
+  }
+
+  // If both lists are not empty, the last update is the same for both lists
+  // because of structural sharing. So, we should only append to one of
+  // the lists.
+  insertUpdateIntoQueue(queue1, update);
+  // But we still need to update the `last` pointer of queue2.
+  queue2.last = update;
+}
+
+function getUpdateExpirationTime(fiber) {
+  switch (fiber.tag) {
+    case HostRoot:
+    case ClassComponent:
+      var updateQueue = fiber.updateQueue;
+      if (updateQueue === null) {
+        return NoWork;
+      }
+      return updateQueue.expirationTime;
+    default:
+      return NoWork;
+  }
+}
+
+function getStateFromUpdate(update, instance, prevState, props) {
+  var partialState = update.partialState;
+  if (typeof partialState === "function") {
+    return partialState.call(instance, prevState, props);
+  } else {
+    return partialState;
+  }
+}
+
+function processUpdateQueue(
+  current,
+  workInProgress,
+  queue,
+  instance,
+  props,
+  renderExpirationTime
+) {
+  if (current !== null && current.updateQueue === queue) {
+    // We need to create a work-in-progress queue, by cloning the current queue.
+    var currentQueue = queue;
+    queue = workInProgress.updateQueue = {
+      baseState: currentQueue.baseState,
+      expirationTime: currentQueue.expirationTime,
+      first: currentQueue.first,
+      last: currentQueue.last,
+      isInitialized: currentQueue.isInitialized,
+      capturedValues: currentQueue.capturedValues,
+      // These fields are no longer valid because they were already committed.
+      // Reset them.
+      callbackList: null,
+      hasForceUpdate: false
+    };
+  }
+
+  {
+    // Set this flag so we can warn if setState is called inside the update
+    // function of another setState.
+    queue.isProcessing = true;
+  }
+
+  // Reset the remaining expiration time. If we skip over any updates, we'll
+  // increase this accordingly.
+  queue.expirationTime = NoWork;
+
+  // TODO: We don't know what the base state will be until we begin work.
+  // It depends on which fiber is the next current. Initialize with an empty
+  // base state, then set to the memoizedState when rendering. Not super
+  // happy with this approach.
+  var state = void 0;
+  if (queue.isInitialized) {
+    state = queue.baseState;
+  } else {
+    state = queue.baseState = workInProgress.memoizedState;
+    queue.isInitialized = true;
+  }
+  var dontMutatePrevState = true;
+  var update = queue.first;
+  var didSkip = false;
+  while (update !== null) {
+    var updateExpirationTime = update.expirationTime;
+    if (updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      var remainingExpirationTime = queue.expirationTime;
+      if (
+        remainingExpirationTime === NoWork ||
+        remainingExpirationTime > updateExpirationTime
+      ) {
+        // Update the remaining expiration time.
+        queue.expirationTime = updateExpirationTime;
+      }
+      if (!didSkip) {
+        didSkip = true;
+        queue.baseState = state;
+      }
+      // Continue to the next update.
+      update = update.next;
+      continue;
+    }
+
+    // This update does have sufficient priority.
+
+    // If no previous updates were skipped, drop this update from the queue by
+    // advancing the head of the list.
+    if (!didSkip) {
+      queue.first = update.next;
+      if (queue.first === null) {
+        queue.last = null;
+      }
+    }
+
+    // Invoke setState callback an extra time to help detect side-effects.
+    // Ignore the return value in this case.
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      getStateFromUpdate(update, instance, state, props);
+    }
+
+    // Process the update
+    var _partialState = void 0;
+    if (update.isReplace) {
+      state = getStateFromUpdate(update, instance, state, props);
+      dontMutatePrevState = true;
+    } else {
+      _partialState = getStateFromUpdate(update, instance, state, props);
+      if (_partialState) {
+        if (dontMutatePrevState) {
+          // $FlowFixMe: Idk how to type this properly.
+          state = Object.assign({}, state, _partialState);
+        } else {
+          state = Object.assign(state, _partialState);
+        }
+        dontMutatePrevState = false;
+      }
+    }
+    if (update.isForced) {
+      queue.hasForceUpdate = true;
+    }
+    if (update.callback !== null) {
+      // Append to list of callbacks.
+      var _callbackList = queue.callbackList;
+      if (_callbackList === null) {
+        _callbackList = queue.callbackList = [];
+      }
+      _callbackList.push(update);
+    }
+    if (update.capturedValue !== null) {
+      var _capturedValues = queue.capturedValues;
+      if (_capturedValues === null) {
+        queue.capturedValues = [update.capturedValue];
+      } else {
+        _capturedValues.push(update.capturedValue);
+      }
+    }
+    update = update.next;
+  }
+
+  if (queue.callbackList !== null) {
+    workInProgress.effectTag |= Callback;
+  } else if (
+    queue.first === null &&
+    !queue.hasForceUpdate &&
+    queue.capturedValues === null
+  ) {
+    // The queue is empty. We can reset it.
+    workInProgress.updateQueue = null;
+  }
+
+  if (!didSkip) {
+    didSkip = true;
+    queue.baseState = state;
+  }
+
+  {
+    // No longer processing.
+    queue.isProcessing = false;
+  }
+
+  return state;
+}
+
+function commitCallbacks(queue, context) {
+  var callbackList = queue.callbackList;
+  if (callbackList === null) {
+    return;
+  }
+  // Set the list to null to make sure they don't get called more than once.
+  queue.callbackList = null;
+  for (var i = 0; i < callbackList.length; i++) {
+    var update = callbackList[i];
+    var _callback = update.callback;
+    // This update might be processed again. Clear the callback so it's only
+    // called once.
+    update.callback = null;
+    invariant(
+      typeof _callback === "function",
+      "Invalid argument passed as callback. Expected a function. Instead " +
+        "received: %s",
+      _callback
+    );
+    _callback.call(context);
+  }
+}
+
+var fakeInternalInstance = {};
+var isArray = Array.isArray;
+
+var didWarnAboutStateAssignmentForComponent = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
+var didWarnAboutUninitializedState = void 0;
+var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
+var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
+var warnOnInvalidCallback = void 0;
+
+{
+  didWarnAboutStateAssignmentForComponent = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
+  didWarnAboutUninitializedState = new Set();
+  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
+  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
+
+  var didWarnOnInvalidCallback = new Set();
+
+  warnOnInvalidCallback = function(callback, callerName) {
+    if (callback === null || typeof callback === "function") {
+      return;
+    }
+    var key = callerName + "_" + callback;
+    if (!didWarnOnInvalidCallback.has(key)) {
+      didWarnOnInvalidCallback.add(key);
+      warning(
+        false,
+        "%s(...): Expected the last optional `callback` argument to be a " +
+          "function. Instead received: %s.",
+        callerName,
+        callback
+      );
+    }
+  };
+
+  // This is so gross but it's at least non-critical and can be removed if
+  // it causes problems. This is meant to give a nicer error message for
+  // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
+  // ...)) which otherwise throws a "_processChildContext is not a function"
+  // exception.
+  Object.defineProperty(fakeInternalInstance, "_processChildContext", {
+    enumerable: false,
+    value: function() {
+      invariant(
+        false,
+        "_processChildContext is not available in React 16+. This likely " +
+          "means you have multiple copies of React and are attempting to nest " +
+          "a React 15 tree inside a React 16 tree using " +
+          "unstable_renderSubtreeIntoContainer, which isn't supported. Try " +
+          "to make sure you have only one copy of React (and ideally, switch " +
+          "to ReactDOM.createPortal)."
+      );
+    }
+  });
+  Object.freeze(fakeInternalInstance);
+}
+function callGetDerivedStateFromCatch(ctor, capturedValues) {
+  var resultState = {};
+  for (var i = 0; i < capturedValues.length; i++) {
+    var capturedValue = capturedValues[i];
+    var error = capturedValue.value;
+    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
+    if (partialState !== null && partialState !== undefined) {
+      Object.assign(resultState, partialState);
+    }
+  }
+  return resultState;
+}
+
+var ReactFiberClassComponent = function(
+  legacyContext,
+  scheduleWork,
+  computeExpirationForFiber,
+  memoizeProps,
+  memoizeState
+) {
+  var cacheContext = legacyContext.cacheContext,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    isContextConsumer = legacyContext.isContextConsumer,
+    hasContextChanged = legacyContext.hasContextChanged;
+
+  // Class component state updater
+
+  var updater = {
+    isMounted: isMounted,
+    enqueueSetState: function(instance, partialState, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "setState");
+      }
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: partialState,
+        callback: callback,
+        isReplace: false,
+        isForced: false,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
+      scheduleWork(fiber, expirationTime);
+    },
+    enqueueReplaceState: function(instance, state, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "replaceState");
+      }
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: state,
+        callback: callback,
+        isReplace: true,
+        isForced: false,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
+      scheduleWork(fiber, expirationTime);
+    },
+    enqueueForceUpdate: function(instance, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "forceUpdate");
+      }
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: null,
+        callback: callback,
+        isReplace: false,
+        isForced: true,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
+      scheduleWork(fiber, expirationTime);
+    }
+  };
+
+  function checkShouldComponentUpdate(
+    workInProgress,
+    oldProps,
+    newProps,
+    oldState,
+    newState,
+    newContext
+  ) {
+    if (
+      oldProps === null ||
+      (workInProgress.updateQueue !== null &&
+        workInProgress.updateQueue.hasForceUpdate)
+    ) {
+      // If the workInProgress already has an Update effect, return true
+      return true;
+    }
+
+    var instance = workInProgress.stateNode;
+    var ctor = workInProgress.type;
+    if (typeof instance.shouldComponentUpdate === "function") {
+      startPhaseTimer(workInProgress, "shouldComponentUpdate");
+      var shouldUpdate = instance.shouldComponentUpdate(
+        newProps,
+        newState,
+        newContext
+      );
+      stopPhaseTimer();
+
+      {
+        !(shouldUpdate !== undefined)
+          ? warning(
+              false,
+              "%s.shouldComponentUpdate(): Returned undefined instead of a " +
+                "boolean value. Make sure to return true or false.",
+              getComponentName(workInProgress) || "Component"
+            )
+          : void 0;
+      }
+
+      return shouldUpdate;
+    }
+
+    if (ctor.prototype && ctor.prototype.isPureReactComponent) {
+      return (
+        !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+      );
+    }
+
+    return true;
+  }
+
+  function checkClassInstance(workInProgress) {
+    var instance = workInProgress.stateNode;
+    var type = workInProgress.type;
+    {
+      var name = getComponentName(workInProgress) || "Component";
+      var renderPresent = instance.render;
+
+      if (!renderPresent) {
+        if (type.prototype && typeof type.prototype.render === "function") {
+          warning(
+            false,
+            "%s(...): No `render` method found on the returned component " +
+              "instance: did you accidentally return an object from the constructor?",
+            name
+          );
+        } else {
+          warning(
+            false,
+            "%s(...): No `render` method found on the returned component " +
+              "instance: you may have forgotten to define `render`.",
+            name
+          );
+        }
+      }
+
+      var noGetInitialStateOnES6 =
+        !instance.getInitialState ||
+        instance.getInitialState.isReactClassApproved ||
+        instance.state;
+      !noGetInitialStateOnES6
+        ? warning(
+            false,
+            "getInitialState was defined on %s, a plain JavaScript class. " +
+              "This is only supported for classes created using React.createClass. " +
+              "Did you mean to define a state property instead?",
+            name
+          )
+        : void 0;
+      var noGetDefaultPropsOnES6 =
+        !instance.getDefaultProps ||
+        instance.getDefaultProps.isReactClassApproved;
+      !noGetDefaultPropsOnES6
+        ? warning(
+            false,
+            "getDefaultProps was defined on %s, a plain JavaScript class. " +
+              "This is only supported for classes created using React.createClass. " +
+              "Use a static property to define defaultProps instead.",
+            name
+          )
+        : void 0;
+      var noInstancePropTypes = !instance.propTypes;
+      !noInstancePropTypes
+        ? warning(
+            false,
+            "propTypes was defined as an instance property on %s. Use a static " +
+              "property to define propTypes instead.",
+            name
+          )
+        : void 0;
+      var noInstanceContextTypes = !instance.contextTypes;
+      !noInstanceContextTypes
+        ? warning(
+            false,
+            "contextTypes was defined as an instance property on %s. Use a static " +
+              "property to define contextTypes instead.",
+            name
+          )
+        : void 0;
+      var noComponentShouldUpdate =
+        typeof instance.componentShouldUpdate !== "function";
+      !noComponentShouldUpdate
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
+              "The name is phrased as a question because the function is " +
+              "expected to return a value.",
+            name
+          )
+        : void 0;
+      if (
+        type.prototype &&
+        type.prototype.isPureReactComponent &&
+        typeof instance.shouldComponentUpdate !== "undefined"
+      ) {
+        warning(
+          false,
+          "%s has a method called shouldComponentUpdate(). " +
+            "shouldComponentUpdate should not be used when extending React.PureComponent. " +
+            "Please extend React.Component if shouldComponentUpdate is used.",
+          getComponentName(workInProgress) || "A pure component"
+        );
+      }
+      var noComponentDidUnmount =
+        typeof instance.componentDidUnmount !== "function";
+      !noComponentDidUnmount
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentDidUnmount(). But there is no such lifecycle method. " +
+              "Did you mean componentWillUnmount()?",
+            name
+          )
+        : void 0;
+      var noComponentDidReceiveProps =
+        typeof instance.componentDidReceiveProps !== "function";
+      !noComponentDidReceiveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentDidReceiveProps(). But there is no such lifecycle method. " +
+              "If you meant to update the state in response to changing props, " +
+              "use componentWillReceiveProps(). If you meant to fetch data or " +
+              "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
+            name
+          )
+        : void 0;
+      var noComponentWillRecieveProps =
+        typeof instance.componentWillRecieveProps !== "function";
+      !noComponentWillRecieveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
+            name
+          )
+        : void 0;
+      var noUnsafeComponentWillRecieveProps =
+        typeof instance.UNSAFE_componentWillRecieveProps !== "function";
+      !noUnsafeComponentWillRecieveProps
+        ? warning(
+            false,
+            "%s has a method called " +
+              "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
+            name
+          )
+        : void 0;
+      var hasMutatedProps = instance.props !== workInProgress.pendingProps;
+      !(instance.props === undefined || !hasMutatedProps)
+        ? warning(
+            false,
+            "%s(...): When calling super() in `%s`, make sure to pass " +
+              "up the same props that your component's constructor was passed.",
+            name,
+            name
+          )
+        : void 0;
+      var noInstanceDefaultProps = !instance.defaultProps;
+      !noInstanceDefaultProps
+        ? warning(
+            false,
+            "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
+              " Instead, define defaultProps as a static property on %s.",
+            name,
+            name
+          )
+        : void 0;
+
+      if (
+        typeof instance.getSnapshotBeforeUpdate === "function" &&
+        typeof instance.componentDidUpdate !== "function" &&
+        !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
+      ) {
+        didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
+        warning(
+          false,
+          "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
+            "This component defines getSnapshotBeforeUpdate() only.",
+          getComponentName(workInProgress)
+        );
+      }
+
+      var noInstanceGetDerivedStateFromProps =
+        typeof instance.getDerivedStateFromProps !== "function";
+      !noInstanceGetDerivedStateFromProps
+        ? warning(
+            false,
+            "%s: getDerivedStateFromProps() is defined as an instance method " +
+              "and will be ignored. Instead, declare it as a static method.",
+            name
+          )
+        : void 0;
+      var noInstanceGetDerivedStateFromCatch =
+        typeof instance.getDerivedStateFromCatch !== "function";
+      !noInstanceGetDerivedStateFromCatch
+        ? warning(
+            false,
+            "%s: getDerivedStateFromCatch() is defined as an instance method " +
+              "and will be ignored. Instead, declare it as a static method.",
+            name
+          )
+        : void 0;
+      var noStaticGetSnapshotBeforeUpdate =
+        typeof type.getSnapshotBeforeUpdate !== "function";
+      !noStaticGetSnapshotBeforeUpdate
+        ? warning(
+            false,
+            "%s: getSnapshotBeforeUpdate() is defined as a static method " +
+              "and will be ignored. Instead, declare it as an instance method.",
+            name
+          )
+        : void 0;
+      var _state = instance.state;
+      if (_state && (typeof _state !== "object" || isArray(_state))) {
+        warning(false, "%s.state: must be set to an object or null", name);
+      }
+      if (typeof instance.getChildContext === "function") {
+        !(typeof type.childContextTypes === "object")
+          ? warning(
+              false,
+              "%s.getChildContext(): childContextTypes must be defined in order to " +
+                "use getChildContext().",
+              name
+            )
+          : void 0;
+      }
+    }
+  }
+
+  function resetInputPointers(workInProgress, instance) {
+    instance.props = workInProgress.memoizedProps;
+    instance.state = workInProgress.memoizedState;
+  }
+
+  function adoptClassInstance(workInProgress, instance) {
+    instance.updater = updater;
+    workInProgress.stateNode = instance;
+    // The instance needs access to the fiber so that it can schedule updates
+    set(instance, workInProgress);
+    {
+      instance._reactInternalInstance = fakeInternalInstance;
+    }
+  }
+
+  function constructClassInstance(workInProgress, props) {
+    var ctor = workInProgress.type;
+    var unmaskedContext = getUnmaskedContext(workInProgress);
+    var needsContext = isContextConsumer(workInProgress);
+    var context = needsContext
+      ? getMaskedContext(workInProgress, unmaskedContext)
+      : emptyObject;
+
+    // Instantiate twice to help detect side-effects.
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      new ctor(props, context); // eslint-disable-line no-new
+    }
+
+    var instance = new ctor(props, context);
+    var state =
+      instance.state !== null && instance.state !== undefined
+        ? instance.state
+        : null;
+    adoptClassInstance(workInProgress, instance);
+
+    {
+      if (
+        typeof ctor.getDerivedStateFromProps === "function" &&
+        state === null
+      ) {
+        var componentName = getComponentName(workInProgress) || "Component";
+        if (!didWarnAboutUninitializedState.has(componentName)) {
+          didWarnAboutUninitializedState.add(componentName);
+          warning(
+            false,
+            "%s: Did not properly initialize state during construction. " +
+              "Expected state to be an object, but it was %s.",
+            componentName,
+            instance.state === null ? "null" : "undefined"
+          );
+        }
+      }
+
+      // If new component APIs are defined, "unsafe" lifecycles won't be called.
+      // Warn about these lifecycles if they are present.
+      // Don't warn about react-lifecycles-compat polyfilled methods though.
+      if (
+        typeof ctor.getDerivedStateFromProps === "function" ||
+        typeof instance.getSnapshotBeforeUpdate === "function"
+      ) {
+        var foundWillMountName = null;
+        var foundWillReceivePropsName = null;
+        var foundWillUpdateName = null;
+        if (
+          typeof instance.componentWillMount === "function" &&
+          instance.componentWillMount.__suppressDeprecationWarning !== true
+        ) {
+          foundWillMountName = "componentWillMount";
+        } else if (typeof instance.UNSAFE_componentWillMount === "function") {
+          foundWillMountName = "UNSAFE_componentWillMount";
+        }
+        if (
+          typeof instance.componentWillReceiveProps === "function" &&
+          instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+            true
+        ) {
+          foundWillReceivePropsName = "componentWillReceiveProps";
+        } else if (
+          typeof instance.UNSAFE_componentWillReceiveProps === "function"
+        ) {
+          foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
+        }
+        if (
+          typeof instance.componentWillUpdate === "function" &&
+          instance.componentWillUpdate.__suppressDeprecationWarning !== true
+        ) {
+          foundWillUpdateName = "componentWillUpdate";
+        } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+          foundWillUpdateName = "UNSAFE_componentWillUpdate";
+        }
+        if (
+          foundWillMountName !== null ||
+          foundWillReceivePropsName !== null ||
+          foundWillUpdateName !== null
+        ) {
+          var _componentName = getComponentName(workInProgress) || "Component";
+          var newApiName =
+            typeof ctor.getDerivedStateFromProps === "function"
+              ? "getDerivedStateFromProps()"
+              : "getSnapshotBeforeUpdate()";
+          if (
+            !didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)
+          ) {
+            didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
+            warning(
+              false,
+              "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
+                "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
+                "The above lifecycles should be removed. Learn more about this warning here:\n" +
+                "https://fb.me/react-async-component-lifecycle-hooks",
+              _componentName,
+              newApiName,
+              foundWillMountName !== null ? "\n  " + foundWillMountName : "",
+              foundWillReceivePropsName !== null
+                ? "\n  " + foundWillReceivePropsName
+                : "",
+              foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
+            );
+          }
+        }
+      }
+    }
+
+    workInProgress.memoizedState = state;
+
+    var partialState = callGetDerivedStateFromProps(
+      workInProgress,
+      instance,
+      props,
+      state
+    );
+
+    if (partialState !== null && partialState !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      workInProgress.memoizedState = Object.assign(
+        {},
+        workInProgress.memoizedState,
+        partialState
+      );
+    }
+
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    // ReactFiberContext usually updates this cache but can't for newly-created instances.
+    if (needsContext) {
+      cacheContext(workInProgress, unmaskedContext, context);
+    }
+
+    return instance;
+  }
+
+  function callComponentWillMount(workInProgress, instance) {
+    startPhaseTimer(workInProgress, "componentWillMount");
+    var oldState = instance.state;
+
+    if (typeof instance.componentWillMount === "function") {
+      instance.componentWillMount();
+    }
+    if (typeof instance.UNSAFE_componentWillMount === "function") {
+      instance.UNSAFE_componentWillMount();
+    }
+
+    stopPhaseTimer();
+
+    if (oldState !== instance.state) {
+      {
+        warning(
+          false,
+          "%s.componentWillMount(): Assigning directly to this.state is " +
+            "deprecated (except inside a component's " +
+            "constructor). Use setState instead.",
+          getComponentName(workInProgress) || "Component"
+        );
+      }
+      updater.enqueueReplaceState(instance, instance.state, null);
+    }
+  }
+
+  function callComponentWillReceiveProps(
+    workInProgress,
+    instance,
+    newProps,
+    newContext
+  ) {
+    var oldState = instance.state;
+    startPhaseTimer(workInProgress, "componentWillReceiveProps");
+    if (typeof instance.componentWillReceiveProps === "function") {
+      instance.componentWillReceiveProps(newProps, newContext);
+    }
+    if (typeof instance.UNSAFE_componentWillReceiveProps === "function") {
+      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+    }
+    stopPhaseTimer();
+
+    if (instance.state !== oldState) {
+      {
+        var componentName = getComponentName(workInProgress) || "Component";
+        if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
+          didWarnAboutStateAssignmentForComponent.add(componentName);
+          warning(
+            false,
+            "%s.componentWillReceiveProps(): Assigning directly to " +
+              "this.state is deprecated (except inside a component's " +
+              "constructor). Use setState instead.",
+            componentName
+          );
+        }
+      }
+      updater.enqueueReplaceState(instance, instance.state, null);
+    }
+  }
+
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    var type = workInProgress.type;
+
+    if (typeof type.getDerivedStateFromProps === "function") {
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        // Invoke method an extra time to help detect side-effects.
+        type.getDerivedStateFromProps.call(null, nextProps, prevState);
+      }
+
+      var partialState = type.getDerivedStateFromProps.call(
+        null,
+        nextProps,
+        prevState
+      );
+
+      {
+        if (partialState === undefined) {
+          var componentName = getComponentName(workInProgress) || "Component";
+          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+            didWarnAboutUndefinedDerivedState.add(componentName);
+            warning(
+              false,
+              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+                "You have returned undefined.",
+              componentName
+            );
+          }
+        }
+      }
+
+      return partialState;
+    }
+  }
+
+  // Invokes the mount life-cycles on a previously never rendered instance.
+  function mountClassInstance(workInProgress, renderExpirationTime) {
+    var ctor = workInProgress.type;
+    var current = workInProgress.alternate;
+
+    {
+      checkClassInstance(workInProgress);
+    }
+
+    var instance = workInProgress.stateNode;
+    var props = workInProgress.pendingProps;
+    var unmaskedContext = getUnmaskedContext(workInProgress);
+
+    instance.props = props;
+    instance.state = workInProgress.memoizedState;
+    instance.refs = emptyObject;
+    instance.context = getMaskedContext(workInProgress, unmaskedContext);
+
+    {
+      if (workInProgress.mode & StrictMode) {
+        ReactStrictModeWarnings.recordUnsafeLifecycleWarnings(
+          workInProgress,
+          instance
+        );
+      }
+
+      if (warnAboutDeprecatedLifecycles) {
+        ReactStrictModeWarnings.recordDeprecationWarnings(
+          workInProgress,
+          instance
+        );
+      }
+    }
+
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      typeof ctor.getDerivedStateFromProps !== "function" &&
+      typeof instance.getSnapshotBeforeUpdate !== "function" &&
+      (typeof instance.UNSAFE_componentWillMount === "function" ||
+        typeof instance.componentWillMount === "function")
+    ) {
+      callComponentWillMount(workInProgress, instance);
+      // If we had additional state updates during this life-cycle, let's
+      // process them now.
+      var updateQueue = workInProgress.updateQueue;
+      if (updateQueue !== null) {
+        instance.state = processUpdateQueue(
+          current,
+          workInProgress,
+          updateQueue,
+          instance,
+          props,
+          renderExpirationTime
+        );
+      }
+    }
+    if (typeof instance.componentDidMount === "function") {
+      workInProgress.effectTag |= Update;
+    }
+  }
+
+  function resumeMountClassInstance(workInProgress, renderExpirationTime) {
+    var ctor = workInProgress.type;
+    var instance = workInProgress.stateNode;
+    resetInputPointers(workInProgress, instance);
+
+    var oldProps = workInProgress.memoizedProps;
+    var newProps = workInProgress.pendingProps;
+    var oldContext = instance.context;
+    var newUnmaskedContext = getUnmaskedContext(workInProgress);
+    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+
+    var hasNewLifecycles =
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function";
+
+    // Note: During these life-cycles, instance.props/instance.state are what
+    // ever the previously attempted to render - not the "current". However,
+    // during componentDidUpdate we pass the "current" props.
+
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      !hasNewLifecycles &&
+      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
+        typeof instance.componentWillReceiveProps === "function")
+    ) {
+      if (oldProps !== newProps || oldContext !== newContext) {
+        callComponentWillReceiveProps(
+          workInProgress,
+          instance,
+          newProps,
+          newContext
+        );
+      }
+    }
+
+    // Compute the next state using the memoized state and the update queue.
+    var oldState = workInProgress.memoizedState;
+    // TODO: Previous state can be null.
+    var newState = void 0;
+    var derivedStateFromCatch = void 0;
+    if (workInProgress.updateQueue !== null) {
+      newState = processUpdateQueue(
+        null,
+        workInProgress,
+        workInProgress.updateQueue,
+        instance,
+        newProps,
+        renderExpirationTime
+      );
+
+      var updateQueue = workInProgress.updateQueue;
+      if (
+        updateQueue !== null &&
+        updateQueue.capturedValues !== null &&
+        enableGetDerivedStateFromCatch &&
+        typeof ctor.getDerivedStateFromCatch === "function"
+      ) {
+        var capturedValues = updateQueue.capturedValues;
+        // Don't remove these from the update queue yet. We need them in
+        // finishClassComponent. Do the reset there.
+        // TODO: This is awkward. Refactor class components.
+        // updateQueue.capturedValues = null;
+        derivedStateFromCatch = callGetDerivedStateFromCatch(
+          ctor,
+          capturedValues
+        );
+      }
+    } else {
+      newState = oldState;
+    }
+
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
+        workInProgress,
+        instance,
+        newProps,
+        newState
+      );
+    }
+
+    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromProps
+          : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue = workInProgress.updateQueue;
+      if (_updateQueue !== null) {
+        _updateQueue.baseState = Object.assign(
+          {},
+          _updateQueue.baseState,
+          derivedStateFromProps
+        );
+      }
+    }
+    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromCatch
+          : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue2 = workInProgress.updateQueue;
+      if (_updateQueue2 !== null) {
+        _updateQueue2.baseState = Object.assign(
+          {},
+          _updateQueue2.baseState,
+          derivedStateFromCatch
+        );
+      }
+    }
+
+    if (
+      oldProps === newProps &&
+      oldState === newState &&
+      !hasContextChanged() &&
+      !(
+        workInProgress.updateQueue !== null &&
+        workInProgress.updateQueue.hasForceUpdate
+      )
+    ) {
+      // If an update was already in progress, we should schedule an Update
+      // effect even though we're bailing out, so that cWU/cDU are called.
+      if (typeof instance.componentDidMount === "function") {
+        workInProgress.effectTag |= Update;
+      }
+      return false;
+    }
+
+    var shouldUpdate = checkShouldComponentUpdate(
+      workInProgress,
+      oldProps,
+      newProps,
+      oldState,
+      newState,
+      newContext
+    );
+
+    if (shouldUpdate) {
+      // In order to support react-lifecycles-compat polyfilled components,
+      // Unsafe lifecycles should not be invoked for components using the new APIs.
+      if (
+        !hasNewLifecycles &&
+        (typeof instance.UNSAFE_componentWillMount === "function" ||
+          typeof instance.componentWillMount === "function")
+      ) {
+        startPhaseTimer(workInProgress, "componentWillMount");
+        if (typeof instance.componentWillMount === "function") {
+          instance.componentWillMount();
+        }
+        if (typeof instance.UNSAFE_componentWillMount === "function") {
+          instance.UNSAFE_componentWillMount();
+        }
+        stopPhaseTimer();
+      }
+      if (typeof instance.componentDidMount === "function") {
+        workInProgress.effectTag |= Update;
+      }
+    } else {
+      // If an update was already in progress, we should schedule an Update
+      // effect even though we're bailing out, so that cWU/cDU are called.
+      if (typeof instance.componentDidMount === "function") {
+        workInProgress.effectTag |= Update;
+      }
+
+      // If shouldComponentUpdate returned false, we should still update the
+      // memoized props/state to indicate that this work can be reused.
+      memoizeProps(workInProgress, newProps);
+      memoizeState(workInProgress, newState);
+    }
+
+    // Update the existing instance's state, props, and context pointers even
+    // if shouldComponentUpdate returns false.
+    instance.props = newProps;
+    instance.state = newState;
+    instance.context = newContext;
+
+    return shouldUpdate;
+  }
+
+  // Invokes the update life-cycles and returns false if it shouldn't rerender.
+  function updateClassInstance(current, workInProgress, renderExpirationTime) {
+    var ctor = workInProgress.type;
+    var instance = workInProgress.stateNode;
+    resetInputPointers(workInProgress, instance);
+
+    var oldProps = workInProgress.memoizedProps;
+    var newProps = workInProgress.pendingProps;
+    var oldContext = instance.context;
+    var newUnmaskedContext = getUnmaskedContext(workInProgress);
+    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+
+    var hasNewLifecycles =
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function";
+
+    // Note: During these life-cycles, instance.props/instance.state are what
+    // ever the previously attempted to render - not the "current". However,
+    // during componentDidUpdate we pass the "current" props.
+
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      !hasNewLifecycles &&
+      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
+        typeof instance.componentWillReceiveProps === "function")
+    ) {
+      if (oldProps !== newProps || oldContext !== newContext) {
+        callComponentWillReceiveProps(
+          workInProgress,
+          instance,
+          newProps,
+          newContext
+        );
+      }
+    }
+
+    // Compute the next state using the memoized state and the update queue.
+    var oldState = workInProgress.memoizedState;
+    // TODO: Previous state can be null.
+    var newState = void 0;
+    var derivedStateFromCatch = void 0;
+
+    if (workInProgress.updateQueue !== null) {
+      newState = processUpdateQueue(
+        current,
+        workInProgress,
+        workInProgress.updateQueue,
+        instance,
+        newProps,
+        renderExpirationTime
+      );
+
+      var updateQueue = workInProgress.updateQueue;
+      if (
+        updateQueue !== null &&
+        updateQueue.capturedValues !== null &&
+        enableGetDerivedStateFromCatch &&
+        typeof ctor.getDerivedStateFromCatch === "function"
+      ) {
+        var capturedValues = updateQueue.capturedValues;
+        // Don't remove these from the update queue yet. We need them in
+        // finishClassComponent. Do the reset there.
+        // TODO: This is awkward. Refactor class components.
+        // updateQueue.capturedValues = null;
+        derivedStateFromCatch = callGetDerivedStateFromCatch(
+          ctor,
+          capturedValues
+        );
+      }
+    } else {
+      newState = oldState;
+    }
+
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
+        workInProgress,
+        instance,
+        newProps,
+        newState
+      );
+    }
+
+    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromProps
+          : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue3 = workInProgress.updateQueue;
+      if (_updateQueue3 !== null) {
+        _updateQueue3.baseState = Object.assign(
+          {},
+          _updateQueue3.baseState,
+          derivedStateFromProps
+        );
+      }
+    }
+    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromCatch
+          : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue4 = workInProgress.updateQueue;
+      if (_updateQueue4 !== null) {
+        _updateQueue4.baseState = Object.assign(
+          {},
+          _updateQueue4.baseState,
+          derivedStateFromCatch
+        );
+      }
+    }
+
+    if (
+      oldProps === newProps &&
+      oldState === newState &&
+      !hasContextChanged() &&
+      !(
+        workInProgress.updateQueue !== null &&
+        workInProgress.updateQueue.hasForceUpdate
+      )
+    ) {
+      // If an update was already in progress, we should schedule an Update
+      // effect even though we're bailing out, so that cWU/cDU are called.
+      if (typeof instance.componentDidUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Update;
+        }
+      }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Snapshot;
+        }
+      }
+      return false;
+    }
+
+    var shouldUpdate = checkShouldComponentUpdate(
+      workInProgress,
+      oldProps,
+      newProps,
+      oldState,
+      newState,
+      newContext
+    );
+
+    if (shouldUpdate) {
+      // In order to support react-lifecycles-compat polyfilled components,
+      // Unsafe lifecycles should not be invoked for components using the new APIs.
+      if (
+        !hasNewLifecycles &&
+        (typeof instance.UNSAFE_componentWillUpdate === "function" ||
+          typeof instance.componentWillUpdate === "function")
+      ) {
+        startPhaseTimer(workInProgress, "componentWillUpdate");
+        if (typeof instance.componentWillUpdate === "function") {
+          instance.componentWillUpdate(newProps, newState, newContext);
+        }
+        if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+          instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
+        }
+        stopPhaseTimer();
+      }
+      if (typeof instance.componentDidUpdate === "function") {
+        workInProgress.effectTag |= Update;
+      }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        workInProgress.effectTag |= Snapshot;
+      }
+    } else {
+      // If an update was already in progress, we should schedule an Update
+      // effect even though we're bailing out, so that cWU/cDU are called.
+      if (typeof instance.componentDidUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Update;
+        }
+      }
+      if (typeof instance.getSnapshotBeforeUpdate === "function") {
+        if (
+          oldProps !== current.memoizedProps ||
+          oldState !== current.memoizedState
+        ) {
+          workInProgress.effectTag |= Snapshot;
+        }
+      }
+
+      // If shouldComponentUpdate returned false, we should still update the
+      // memoized props/state to indicate that this work can be reused.
+      memoizeProps(workInProgress, newProps);
+      memoizeState(workInProgress, newState);
+    }
+
+    // Update the existing instance's state, props, and context pointers even
+    // if shouldComponentUpdate returns false.
+    instance.props = newProps;
+    instance.state = newState;
+    instance.context = newContext;
+
+    return shouldUpdate;
+  }
+
+  return {
+    adoptClassInstance: adoptClassInstance,
+    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
+    constructClassInstance: constructClassInstance,
+    mountClassInstance: mountClassInstance,
+    resumeMountClassInstance: resumeMountClassInstance,
+    updateClassInstance: updateClassInstance
+  };
+};
+
+var getCurrentFiberStackAddendum$1 =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+
+var didWarnAboutMaps = void 0;
+var didWarnAboutStringRefInStrictMode = void 0;
+var ownerHasKeyUseWarning = void 0;
+var ownerHasFunctionTypeWarning = void 0;
+var warnForMissingKey = function(child) {};
+
+{
+  didWarnAboutMaps = false;
+  didWarnAboutStringRefInStrictMode = {};
+
+  /**
+   * Warn if there's no key explicitly set on dynamic arrays of children or
+   * object keys are not valid. This allows us to keep track of children between
+   * updates.
+   */
+  ownerHasKeyUseWarning = {};
+  ownerHasFunctionTypeWarning = {};
+
+  warnForMissingKey = function(child) {
+    if (child === null || typeof child !== "object") {
+      return;
+    }
+    if (!child._store || child._store.validated || child.key != null) {
+      return;
+    }
+    invariant(
+      typeof child._store === "object",
+      "React Component in warnForMissingKey should have a _store. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+    child._store.validated = true;
+
+    var currentComponentErrorInfo =
+      "Each child in an array or iterator should have a unique " +
+      '"key" prop. See https://fb.me/react-warning-keys for ' +
+      "more information." +
+      (getCurrentFiberStackAddendum$1() || "");
+    if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
+      return;
+    }
+    ownerHasKeyUseWarning[currentComponentErrorInfo] = true;
+
+    warning(
+      false,
+      "Each child in an array or iterator should have a unique " +
+        '"key" prop. See https://fb.me/react-warning-keys for ' +
+        "more information.%s",
+      getCurrentFiberStackAddendum$1()
+    );
+  };
+}
+
+var isArray$1 = Array.isArray;
+
+function coerceRef(returnFiber, current, element) {
+  var mixedRef = element.ref;
+  if (
+    mixedRef !== null &&
+    typeof mixedRef !== "function" &&
+    typeof mixedRef !== "object"
+  ) {
+    {
+      if (returnFiber.mode & StrictMode) {
+        var componentName = getComponentName(returnFiber) || "Component";
+        if (!didWarnAboutStringRefInStrictMode[componentName]) {
+          warning(
+            false,
+            'A string ref, "%s", has been found within a strict mode tree. ' +
+              "String refs are a source of potential bugs and should be avoided. " +
+              "We recommend using createRef() instead." +
+              "\n%s" +
+              "\n\nLearn more about using refs safely here:" +
+              "\nhttps://fb.me/react-strict-mode-string-ref",
+            mixedRef,
+            getStackAddendumByWorkInProgressFiber(returnFiber)
+          );
+          didWarnAboutStringRefInStrictMode[componentName] = true;
+        }
+      }
+    }
+
+    if (element._owner) {
+      var owner = element._owner;
+      var inst = void 0;
+      if (owner) {
+        var ownerFiber = owner;
+        invariant(
+          ownerFiber.tag === ClassComponent,
+          "Stateless function components cannot have refs."
+        );
+        inst = ownerFiber.stateNode;
+      }
+      invariant(
+        inst,
+        "Missing owner for string ref %s. This error is likely caused by a " +
+          "bug in React. Please file an issue.",
+        mixedRef
+      );
+      var stringRef = "" + mixedRef;
+      // Check if previous string ref matches new string ref
+      if (
+        current !== null &&
+        current.ref !== null &&
+        current.ref._stringRef === stringRef
+      ) {
+        return current.ref;
+      }
+      var ref = function(value) {
+        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
+        if (value === null) {
+          delete refs[stringRef];
+        } else {
+          refs[stringRef] = value;
+        }
+      };
+      ref._stringRef = stringRef;
+      return ref;
+    } else {
+      invariant(
+        typeof mixedRef === "string",
+        "Expected ref to be a function or a string."
+      );
+      invariant(
+        element._owner,
+        "Element ref was specified as a string (%s) but no owner was set. This could happen for one of" +
+          " the following reasons:\n" +
+          "1. You may be adding a ref to a functional component\n" +
+          "2. You may be adding a ref to a component that was not created inside a component's render method\n" +
+          "3. You have multiple copies of React loaded\n" +
+          "See https://fb.me/react-refs-must-have-owner for more information.",
+        mixedRef
+      );
+    }
+  }
+  return mixedRef;
+}
+
+function throwOnInvalidObjectType(returnFiber, newChild) {
+  if (returnFiber.type !== "textarea") {
+    var addendum = "";
+    {
+      addendum =
+        " If you meant to render a collection of children, use an array " +
+        "instead." +
+        (getCurrentFiberStackAddendum$1() || "");
+    }
+    invariant(
+      false,
+      "Objects are not valid as a React child (found: %s).%s",
+      Object.prototype.toString.call(newChild) === "[object Object]"
+        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
+        : newChild,
+      addendum
+    );
+  }
+}
+
+function warnOnFunctionType() {
+  var currentComponentErrorInfo =
+    "Functions are not valid as a React child. This may happen if " +
+    "you return a Component instead of <Component /> from render. " +
+    "Or maybe you meant to call this function rather than return it." +
+    (getCurrentFiberStackAddendum$1() || "");
+
+  if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
+    return;
+  }
+  ownerHasFunctionTypeWarning[currentComponentErrorInfo] = true;
+
+  warning(
+    false,
+    "Functions are not valid as a React child. This may happen if " +
+      "you return a Component instead of <Component /> from render. " +
+      "Or maybe you meant to call this function rather than return it.%s",
+    getCurrentFiberStackAddendum$1() || ""
+  );
+}
+
+// This wrapper function exists because I expect to clone the code in each path
+// to be able to optimize each path individually by branching early. This needs
+// a compiler or we can do it manually. Helpers that don't need this branching
+// live outside of this function.
+function ChildReconciler(shouldTrackSideEffects) {
+  function deleteChild(returnFiber, childToDelete) {
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return;
+    }
+    // Deletions are added in reversed order so we add it to the front.
+    // At this point, the return fiber's effect list is empty except for
+    // deletions, so we can just append the deletion to the list. The remaining
+    // effects aren't added until the complete phase. Once we implement
+    // resuming, this may not be true.
+    var last = returnFiber.lastEffect;
+    if (last !== null) {
+      last.nextEffect = childToDelete;
+      returnFiber.lastEffect = childToDelete;
+    } else {
+      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+    }
+    childToDelete.nextEffect = null;
+    childToDelete.effectTag = Deletion;
+  }
+
+  function deleteRemainingChildren(returnFiber, currentFirstChild) {
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return null;
+    }
+
+    // TODO: For the shouldClone case, this could be micro-optimized a bit by
+    // assuming that after the first child we've already added everything.
+    var childToDelete = currentFirstChild;
+    while (childToDelete !== null) {
+      deleteChild(returnFiber, childToDelete);
+      childToDelete = childToDelete.sibling;
+    }
+    return null;
+  }
+
+  function mapRemainingChildren(returnFiber, currentFirstChild) {
+    // Add the remaining children to a temporary map so that we can find them by
+    // keys quickly. Implicit (null) keys get added to this set with their index
+    var existingChildren = new Map();
+
+    var existingChild = currentFirstChild;
+    while (existingChild !== null) {
+      if (existingChild.key !== null) {
+        existingChildren.set(existingChild.key, existingChild);
+      } else {
+        existingChildren.set(existingChild.index, existingChild);
+      }
+      existingChild = existingChild.sibling;
+    }
+    return existingChildren;
+  }
+
+  function useFiber(fiber, pendingProps, expirationTime) {
+    // We currently set sibling to null and index to 0 here because it is easy
+    // to forget to do before returning it. E.g. for the single child case.
+    var clone = createWorkInProgress(fiber, pendingProps, expirationTime);
+    clone.index = 0;
+    clone.sibling = null;
+    return clone;
+  }
+
+  function placeChild(newFiber, lastPlacedIndex, newIndex) {
+    newFiber.index = newIndex;
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return lastPlacedIndex;
+    }
+    var current = newFiber.alternate;
+    if (current !== null) {
+      var oldIndex = current.index;
+      if (oldIndex < lastPlacedIndex) {
+        // This is a move.
+        newFiber.effectTag = Placement;
+        return lastPlacedIndex;
+      } else {
+        // This item can stay in place.
+        return oldIndex;
+      }
+    } else {
+      // This is an insertion.
+      newFiber.effectTag = Placement;
+      return lastPlacedIndex;
+    }
+  }
+
+  function placeSingleChild(newFiber) {
+    // This is simpler for the single child case. We only need to do a
+    // placement for inserting new children.
+    if (shouldTrackSideEffects && newFiber.alternate === null) {
+      newFiber.effectTag = Placement;
+    }
+    return newFiber;
+  }
+
+  function updateTextNode(returnFiber, current, textContent, expirationTime) {
+    if (current === null || current.tag !== HostText) {
+      // Insert
+      var created = createFiberFromText(
+        textContent,
+        returnFiber.mode,
+        expirationTime
+      );
+      created["return"] = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, textContent, expirationTime);
+      existing["return"] = returnFiber;
+      return existing;
+    }
+  }
+
+  function updateElement(returnFiber, current, element, expirationTime) {
+    if (current !== null && current.type === element.type) {
+      // Move based on index
+      var existing = useFiber(current, element.props, expirationTime);
+      existing.ref = coerceRef(returnFiber, current, element);
+      existing["return"] = returnFiber;
+      {
+        existing._debugSource = element._source;
+        existing._debugOwner = element._owner;
+      }
+      return existing;
+    } else {
+      // Insert
+      var created = createFiberFromElement(
+        element,
+        returnFiber.mode,
+        expirationTime
+      );
+      created.ref = coerceRef(returnFiber, current, element);
+      created["return"] = returnFiber;
+      return created;
+    }
+  }
+
+  function updatePortal(returnFiber, current, portal, expirationTime) {
+    if (
+      current === null ||
+      current.tag !== HostPortal ||
+      current.stateNode.containerInfo !== portal.containerInfo ||
+      current.stateNode.implementation !== portal.implementation
+    ) {
+      // Insert
+      var created = createFiberFromPortal(
+        portal,
+        returnFiber.mode,
+        expirationTime
+      );
+      created["return"] = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, portal.children || [], expirationTime);
+      existing["return"] = returnFiber;
+      return existing;
+    }
+  }
+
+  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
+    if (current === null || current.tag !== Fragment) {
+      // Insert
+      var created = createFiberFromFragment(
+        fragment,
+        returnFiber.mode,
+        expirationTime,
+        key
+      );
+      created["return"] = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, fragment, expirationTime);
+      existing["return"] = returnFiber;
+      return existing;
+    }
+  }
+
+  function createChild(returnFiber, newChild, expirationTime) {
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys. If the previous node is implicitly keyed
+      // we can continue to replace it without aborting even if it is not a text
+      // node.
+      var created = createFiberFromText(
+        "" + newChild,
+        returnFiber.mode,
+        expirationTime
+      );
+      created["return"] = returnFiber;
+      return created;
+    }
+
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          var _created = createFiberFromElement(
+            newChild,
+            returnFiber.mode,
+            expirationTime
+          );
+          _created.ref = coerceRef(returnFiber, null, newChild);
+          _created["return"] = returnFiber;
+          return _created;
+        }
+        case REACT_PORTAL_TYPE: {
+          var _created2 = createFiberFromPortal(
+            newChild,
+            returnFiber.mode,
+            expirationTime
+          );
+          _created2["return"] = returnFiber;
+          return _created2;
+        }
+      }
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        var _created3 = createFiberFromFragment(
+          newChild,
+          returnFiber.mode,
+          expirationTime,
+          null
+        );
+        _created3["return"] = returnFiber;
+        return _created3;
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+
+    return null;
+  }
+
+  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
+    // Update the fiber if the keys match, otherwise return null.
+
+    var key = oldFiber !== null ? oldFiber.key : null;
+
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys. If the previous node is implicitly keyed
+      // we can continue to replace it without aborting even if it is not a text
+      // node.
+      if (key !== null) {
+        return null;
+      }
+      return updateTextNode(
+        returnFiber,
+        oldFiber,
+        "" + newChild,
+        expirationTime
+      );
+    }
+
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          if (newChild.key === key) {
+            if (newChild.type === REACT_FRAGMENT_TYPE) {
+              return updateFragment(
+                returnFiber,
+                oldFiber,
+                newChild.props.children,
+                expirationTime,
+                key
+              );
+            }
+            return updateElement(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime
+            );
+          } else {
+            return null;
+          }
+        }
+        case REACT_PORTAL_TYPE: {
+          if (newChild.key === key) {
+            return updatePortal(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime
+            );
+          } else {
+            return null;
+          }
+        }
+      }
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        if (key !== null) {
+          return null;
+        }
+
+        return updateFragment(
+          returnFiber,
+          oldFiber,
+          newChild,
+          expirationTime,
+          null
+        );
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+
+    return null;
+  }
+
+  function updateFromMap(
+    existingChildren,
+    returnFiber,
+    newIdx,
+    newChild,
+    expirationTime
+  ) {
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys, so we neither have to check the old nor
+      // new node for the key. If both are text nodes, they match.
+      var matchedFiber = existingChildren.get(newIdx) || null;
+      return updateTextNode(
+        returnFiber,
+        matchedFiber,
+        "" + newChild,
+        expirationTime
+      );
+    }
+
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          var _matchedFiber =
+            existingChildren.get(
+              newChild.key === null ? newIdx : newChild.key
+            ) || null;
+          if (newChild.type === REACT_FRAGMENT_TYPE) {
+            return updateFragment(
+              returnFiber,
+              _matchedFiber,
+              newChild.props.children,
+              expirationTime,
+              newChild.key
+            );
+          }
+          return updateElement(
+            returnFiber,
+            _matchedFiber,
+            newChild,
+            expirationTime
+          );
+        }
+        case REACT_PORTAL_TYPE: {
+          var _matchedFiber2 =
+            existingChildren.get(
+              newChild.key === null ? newIdx : newChild.key
+            ) || null;
+          return updatePortal(
+            returnFiber,
+            _matchedFiber2,
+            newChild,
+            expirationTime
+          );
+        }
+      }
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        var _matchedFiber3 = existingChildren.get(newIdx) || null;
+        return updateFragment(
+          returnFiber,
+          _matchedFiber3,
+          newChild,
+          expirationTime,
+          null
+        );
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+
+    return null;
+  }
+
+  /**
+   * Warns if there is a duplicate or missing key
+   */
+  function warnOnInvalidKey(child, knownKeys) {
+    {
+      if (typeof child !== "object" || child === null) {
+        return knownKeys;
+      }
+      switch (child.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+        case REACT_PORTAL_TYPE:
+          warnForMissingKey(child);
+          var key = child.key;
+          if (typeof key !== "string") {
+            break;
+          }
+          if (knownKeys === null) {
+            knownKeys = new Set();
+            knownKeys.add(key);
+            break;
+          }
+          if (!knownKeys.has(key)) {
+            knownKeys.add(key);
+            break;
+          }
+          warning(
+            false,
+            "Encountered two children with the same key, `%s`. " +
+              "Keys should be unique so that components maintain their identity " +
+              "across updates. Non-unique keys may cause children to be " +
+              "duplicated and/or omitted — the behavior is unsupported and " +
+              "could change in a future version.%s",
+            key,
+            getCurrentFiberStackAddendum$1()
+          );
+          break;
+        default:
+          break;
+      }
+    }
+    return knownKeys;
+  }
+
+  function reconcileChildrenArray(
+    returnFiber,
+    currentFirstChild,
+    newChildren,
+    expirationTime
+  ) {
+    // This algorithm can't optimize by searching from boths ends since we
+    // don't have backpointers on fibers. I'm trying to see how far we can get
+    // with that model. If it ends up not being worth the tradeoffs, we can
+    // add it later.
+
+    // Even with a two ended optimization, we'd want to optimize for the case
+    // where there are few changes and brute force the comparison instead of
+    // going for the Map. It'd like to explore hitting that path first in
+    // forward-only mode and only go for the Map once we notice that we need
+    // lots of look ahead. This doesn't handle reversal as well as two ended
+    // search but that's unusual. Besides, for the two ended optimization to
+    // work on Iterables, we'd need to copy the whole set.
+
+    // In this first iteration, we'll just live with hitting the bad case
+    // (adding everything to a Map) in for every insert/move.
+
+    // If you change this code, also update reconcileChildrenIterator() which
+    // uses the same algorithm.
+
+    {
+      // First, validate keys.
+      var knownKeys = null;
+      for (var i = 0; i < newChildren.length; i++) {
+        var child = newChildren[i];
+        knownKeys = warnOnInvalidKey(child, knownKeys);
+      }
+    }
+
+    var resultingFirstChild = null;
+    var previousNewFiber = null;
+
+    var oldFiber = currentFirstChild;
+    var lastPlacedIndex = 0;
+    var newIdx = 0;
+    var nextOldFiber = null;
+    for (; oldFiber !== null && newIdx < newChildren.length; newIdx++) {
+      if (oldFiber.index > newIdx) {
+        nextOldFiber = oldFiber;
+        oldFiber = null;
+      } else {
+        nextOldFiber = oldFiber.sibling;
+      }
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (newFiber === null) {
+        // TODO: This breaks on empty slots like null children. That's
+        // unfortunate because it triggers the slow path all the time. We need
+        // a better way to communicate whether this was a miss or null,
+        // boolean, undefined, etc.
+        if (oldFiber === null) {
+          oldFiber = nextOldFiber;
+        }
+        break;
+      }
+      if (shouldTrackSideEffects) {
+        if (oldFiber && newFiber.alternate === null) {
+          // We matched the slot, but we didn't reuse the existing fiber, so we
+          // need to delete the existing child.
+          deleteChild(returnFiber, oldFiber);
+        }
+      }
+      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
+      if (previousNewFiber === null) {
+        // TODO: Move out of the loop. This only happens for the first run.
+        resultingFirstChild = newFiber;
+      } else {
+        // TODO: Defer siblings if we're not at the right index for this slot.
+        // I.e. if we had null values before, then we want to defer this
+        // for each null value. However, we also don't want to call updateSlot
+        // with the previous one.
+        previousNewFiber.sibling = newFiber;
+      }
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+
+    if (newIdx === newChildren.length) {
+      // We've reached the end of the new children. We can delete the rest.
+      deleteRemainingChildren(returnFiber, oldFiber);
+      return resultingFirstChild;
+    }
+
+    if (oldFiber === null) {
+      // If we don't have any more existing children we can choose a fast path
+      // since the rest will all be insertions.
+      for (; newIdx < newChildren.length; newIdx++) {
+        var _newFiber = createChild(
+          returnFiber,
+          newChildren[newIdx],
+          expirationTime
+        );
+        if (!_newFiber) {
+          continue;
+        }
+        lastPlacedIndex = placeChild(_newFiber, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          // TODO: Move out of the loop. This only happens for the first run.
+          resultingFirstChild = _newFiber;
+        } else {
+          previousNewFiber.sibling = _newFiber;
+        }
+        previousNewFiber = _newFiber;
+      }
+      return resultingFirstChild;
+    }
+
+    // Add all children to a key map for quick lookups.
+    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
+
+    // Keep scanning and use the map to restore deleted items as moves.
+    for (; newIdx < newChildren.length; newIdx++) {
+      var _newFiber2 = updateFromMap(
+        existingChildren,
+        returnFiber,
+        newIdx,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (_newFiber2) {
+        if (shouldTrackSideEffects) {
+          if (_newFiber2.alternate !== null) {
+            // The new fiber is a work in progress, but if there exists a
+            // current, that means that we reused the fiber. We need to delete
+            // it from the child list so that we don't add it to the deletion
+            // list.
+            existingChildren["delete"](
+              _newFiber2.key === null ? newIdx : _newFiber2.key
+            );
+          }
+        }
+        lastPlacedIndex = placeChild(_newFiber2, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          resultingFirstChild = _newFiber2;
+        } else {
+          previousNewFiber.sibling = _newFiber2;
+        }
+        previousNewFiber = _newFiber2;
+      }
+    }
+
+    if (shouldTrackSideEffects) {
+      // Any existing children that weren't consumed above were deleted. We need
+      // to add them to the deletion list.
+      existingChildren.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    }
+
+    return resultingFirstChild;
+  }
+
+  function reconcileChildrenIterator(
+    returnFiber,
+    currentFirstChild,
+    newChildrenIterable,
+    expirationTime
+  ) {
+    // This is the same implementation as reconcileChildrenArray(),
+    // but using the iterator instead.
+
+    var iteratorFn = getIteratorFn(newChildrenIterable);
+    invariant(
+      typeof iteratorFn === "function",
+      "An object is not an iterable. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+
+    {
+      // Warn about using Maps as children
+      if (typeof newChildrenIterable.entries === "function") {
+        var possibleMap = newChildrenIterable;
+        if (possibleMap.entries === iteratorFn) {
+          !didWarnAboutMaps
+            ? warning(
+                false,
+                "Using Maps as children is unsupported and will likely yield " +
+                  "unexpected results. Convert it to a sequence/iterable of keyed " +
+                  "ReactElements instead.%s",
+                getCurrentFiberStackAddendum$1()
+              )
+            : void 0;
+          didWarnAboutMaps = true;
+        }
+      }
+
+      // First, validate keys.
+      // We'll get a different iterator later for the main pass.
+      var _newChildren = iteratorFn.call(newChildrenIterable);
+      if (_newChildren) {
+        var knownKeys = null;
+        var _step = _newChildren.next();
+        for (; !_step.done; _step = _newChildren.next()) {
+          var child = _step.value;
+          knownKeys = warnOnInvalidKey(child, knownKeys);
+        }
+      }
+    }
+
+    var newChildren = iteratorFn.call(newChildrenIterable);
+    invariant(newChildren != null, "An iterable object provided no iterator.");
+
+    var resultingFirstChild = null;
+    var previousNewFiber = null;
+
+    var oldFiber = currentFirstChild;
+    var lastPlacedIndex = 0;
+    var newIdx = 0;
+    var nextOldFiber = null;
+
+    var step = newChildren.next();
+    for (
+      ;
+      oldFiber !== null && !step.done;
+      newIdx++, step = newChildren.next()
+    ) {
+      if (oldFiber.index > newIdx) {
+        nextOldFiber = oldFiber;
+        oldFiber = null;
+      } else {
+        nextOldFiber = oldFiber.sibling;
+      }
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        step.value,
+        expirationTime
+      );
+      if (newFiber === null) {
+        // TODO: This breaks on empty slots like null children. That's
+        // unfortunate because it triggers the slow path all the time. We need
+        // a better way to communicate whether this was a miss or null,
+        // boolean, undefined, etc.
+        if (!oldFiber) {
+          oldFiber = nextOldFiber;
+        }
+        break;
+      }
+      if (shouldTrackSideEffects) {
+        if (oldFiber && newFiber.alternate === null) {
+          // We matched the slot, but we didn't reuse the existing fiber, so we
+          // need to delete the existing child.
+          deleteChild(returnFiber, oldFiber);
+        }
+      }
+      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
+      if (previousNewFiber === null) {
+        // TODO: Move out of the loop. This only happens for the first run.
+        resultingFirstChild = newFiber;
+      } else {
+        // TODO: Defer siblings if we're not at the right index for this slot.
+        // I.e. if we had null values before, then we want to defer this
+        // for each null value. However, we also don't want to call updateSlot
+        // with the previous one.
+        previousNewFiber.sibling = newFiber;
+      }
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+
+    if (step.done) {
+      // We've reached the end of the new children. We can delete the rest.
+      deleteRemainingChildren(returnFiber, oldFiber);
+      return resultingFirstChild;
+    }
+
+    if (oldFiber === null) {
+      // If we don't have any more existing children we can choose a fast path
+      // since the rest will all be insertions.
+      for (; !step.done; newIdx++, step = newChildren.next()) {
+        var _newFiber3 = createChild(returnFiber, step.value, expirationTime);
+        if (_newFiber3 === null) {
+          continue;
+        }
+        lastPlacedIndex = placeChild(_newFiber3, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          // TODO: Move out of the loop. This only happens for the first run.
+          resultingFirstChild = _newFiber3;
+        } else {
+          previousNewFiber.sibling = _newFiber3;
+        }
+        previousNewFiber = _newFiber3;
+      }
+      return resultingFirstChild;
+    }
+
+    // Add all children to a key map for quick lookups.
+    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
+
+    // Keep scanning and use the map to restore deleted items as moves.
+    for (; !step.done; newIdx++, step = newChildren.next()) {
+      var _newFiber4 = updateFromMap(
+        existingChildren,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      );
+      if (_newFiber4 !== null) {
+        if (shouldTrackSideEffects) {
+          if (_newFiber4.alternate !== null) {
+            // The new fiber is a work in progress, but if there exists a
+            // current, that means that we reused the fiber. We need to delete
+            // it from the child list so that we don't add it to the deletion
+            // list.
+            existingChildren["delete"](
+              _newFiber4.key === null ? newIdx : _newFiber4.key
+            );
+          }
+        }
+        lastPlacedIndex = placeChild(_newFiber4, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          resultingFirstChild = _newFiber4;
+        } else {
+          previousNewFiber.sibling = _newFiber4;
+        }
+        previousNewFiber = _newFiber4;
+      }
+    }
+
+    if (shouldTrackSideEffects) {
+      // Any existing children that weren't consumed above were deleted. We need
+      // to add them to the deletion list.
+      existingChildren.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    }
+
+    return resultingFirstChild;
+  }
+
+  function reconcileSingleTextNode(
+    returnFiber,
+    currentFirstChild,
+    textContent,
+    expirationTime
+  ) {
+    // There's no need to check for keys on text nodes since we don't have a
+    // way to define them.
+    if (currentFirstChild !== null && currentFirstChild.tag === HostText) {
+      // We already have an existing node so let's just update it and delete
+      // the rest.
+      deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
+      var existing = useFiber(currentFirstChild, textContent, expirationTime);
+      existing["return"] = returnFiber;
+      return existing;
+    }
+    // The existing first child is not a text node so we need to create one
+    // and delete the existing ones.
+    deleteRemainingChildren(returnFiber, currentFirstChild);
+    var created = createFiberFromText(
+      textContent,
+      returnFiber.mode,
+      expirationTime
+    );
+    created["return"] = returnFiber;
+    return created;
+  }
+
+  function reconcileSingleElement(
+    returnFiber,
+    currentFirstChild,
+    element,
+    expirationTime
+  ) {
+    var key = element.key;
+    var child = currentFirstChild;
+    while (child !== null) {
+      // TODO: If key === null and child.key === null, then this only applies to
+      // the first item in the list.
+      if (child.key === key) {
+        if (
+          child.tag === Fragment
+            ? element.type === REACT_FRAGMENT_TYPE
+            : child.type === element.type
+        ) {
+          deleteRemainingChildren(returnFiber, child.sibling);
+          var existing = useFiber(
+            child,
+            element.type === REACT_FRAGMENT_TYPE
+              ? element.props.children
+              : element.props,
+            expirationTime
+          );
+          existing.ref = coerceRef(returnFiber, child, element);
+          existing["return"] = returnFiber;
+          {
+            existing._debugSource = element._source;
+            existing._debugOwner = element._owner;
+          }
+          return existing;
+        } else {
+          deleteRemainingChildren(returnFiber, child);
+          break;
+        }
+      } else {
+        deleteChild(returnFiber, child);
+      }
+      child = child.sibling;
+    }
+
+    if (element.type === REACT_FRAGMENT_TYPE) {
+      var created = createFiberFromFragment(
+        element.props.children,
+        returnFiber.mode,
+        expirationTime,
+        element.key
+      );
+      created["return"] = returnFiber;
+      return created;
+    } else {
+      var _created4 = createFiberFromElement(
+        element,
+        returnFiber.mode,
+        expirationTime
+      );
+      _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
+      _created4["return"] = returnFiber;
+      return _created4;
+    }
+  }
+
+  function reconcileSinglePortal(
+    returnFiber,
+    currentFirstChild,
+    portal,
+    expirationTime
+  ) {
+    var key = portal.key;
+    var child = currentFirstChild;
+    while (child !== null) {
+      // TODO: If key === null and child.key === null, then this only applies to
+      // the first item in the list.
+      if (child.key === key) {
+        if (
+          child.tag === HostPortal &&
+          child.stateNode.containerInfo === portal.containerInfo &&
+          child.stateNode.implementation === portal.implementation
+        ) {
+          deleteRemainingChildren(returnFiber, child.sibling);
+          var existing = useFiber(child, portal.children || [], expirationTime);
+          existing["return"] = returnFiber;
+          return existing;
+        } else {
+          deleteRemainingChildren(returnFiber, child);
+          break;
+        }
+      } else {
+        deleteChild(returnFiber, child);
+      }
+      child = child.sibling;
+    }
+
+    var created = createFiberFromPortal(
+      portal,
+      returnFiber.mode,
+      expirationTime
+    );
+    created["return"] = returnFiber;
+    return created;
+  }
+
+  // This API will tag the children with the side-effect of the reconciliation
+  // itself. They will be added to the side-effect list as we pass through the
+  // children and the parent.
+  function reconcileChildFibers(
+    returnFiber,
+    currentFirstChild,
+    newChild,
+    expirationTime
+  ) {
+    // This function is not recursive.
+    // If the top level item is an array, we treat it as a set of children,
+    // not as a fragment. Nested arrays on the other hand will be treated as
+    // fragment nodes. Recursion happens at the normal flow.
+
+    // Handle top level unkeyed fragments as if they were arrays.
+    // This leads to an ambiguity between <>{[...]}</> and <>...</>.
+    // We treat the ambiguous cases above the same.
+    if (
+      typeof newChild === "object" &&
+      newChild !== null &&
+      newChild.type === REACT_FRAGMENT_TYPE &&
+      newChild.key === null
+    ) {
+      newChild = newChild.props.children;
+    }
+
+    // Handle object types
+    var isObject = typeof newChild === "object" && newChild !== null;
+
+    if (isObject) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return placeSingleChild(
+            reconcileSingleElement(
+              returnFiber,
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )
+          );
+        case REACT_PORTAL_TYPE:
+          return placeSingleChild(
+            reconcileSinglePortal(
+              returnFiber,
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )
+          );
+      }
+    }
+
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      return placeSingleChild(
+        reconcileSingleTextNode(
+          returnFiber,
+          currentFirstChild,
+          "" + newChild,
+          expirationTime
+        )
+      );
+    }
+
+    if (isArray$1(newChild)) {
+      return reconcileChildrenArray(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    }
+
+    if (getIteratorFn(newChild)) {
+      return reconcileChildrenIterator(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    }
+
+    if (isObject) {
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+    if (typeof newChild === "undefined") {
+      // If the new child is undefined, and the return fiber is a composite
+      // component, throw an error. If Fiber return types are disabled,
+      // we already threw above.
+      switch (returnFiber.tag) {
+        case ClassComponent: {
+          {
+            var instance = returnFiber.stateNode;
+            if (instance.render._isMockFunction) {
+              // We allow auto-mocks to proceed as if they're returning null.
+              break;
+            }
+          }
+        }
+        // Intentionally fall through to the next case, which handles both
+        // functions and classes
+        // eslint-disable-next-lined no-fallthrough
+        case FunctionalComponent: {
+          var Component = returnFiber.type;
+          invariant(
+            false,
+            "%s(...): Nothing was returned from render. This usually means a " +
+              "return statement is missing. Or, to render nothing, " +
+              "return null.",
+            Component.displayName || Component.name || "Component"
+          );
+        }
+      }
+    }
+
+    // Remaining cases are all treated as empty.
+    return deleteRemainingChildren(returnFiber, currentFirstChild);
+  }
+
+  return reconcileChildFibers;
+}
+
+var reconcileChildFibers = ChildReconciler(true);
+var mountChildFibers = ChildReconciler(false);
+
+function cloneChildFibers(current, workInProgress) {
+  invariant(
+    current === null || workInProgress.child === current.child,
+    "Resuming work not yet implemented."
+  );
+
+  if (workInProgress.child === null) {
+    return;
+  }
+
+  var currentChild = workInProgress.child;
+  var newChild = createWorkInProgress(
+    currentChild,
+    currentChild.pendingProps,
+    currentChild.expirationTime
+  );
+  workInProgress.child = newChild;
+
+  newChild["return"] = workInProgress;
+  while (currentChild.sibling !== null) {
+    currentChild = currentChild.sibling;
+    newChild = newChild.sibling = createWorkInProgress(
+      currentChild,
+      currentChild.pendingProps,
+      currentChild.expirationTime
+    );
+    newChild["return"] = workInProgress;
+  }
+  newChild.sibling = null;
+}
+
+var didWarnAboutBadClass = void 0;
+var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
+var didWarnAboutStatelessRefs = void 0;
+
+{
+  didWarnAboutBadClass = {};
+  didWarnAboutGetDerivedStateOnFunctionalComponent = {};
+  didWarnAboutStatelessRefs = {};
+}
+
+var ReactFiberBeginWork = function(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext,
+  scheduleWork,
+  computeExpirationForFiber
+) {
+  var shouldSetTextContent = config.shouldSetTextContent,
+    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
+  var pushHostContext = hostContext.pushHostContext,
+    pushHostContainer = hostContext.pushHostContainer;
+  var pushProvider = newContext.pushProvider;
+  var getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    hasLegacyContextChanged = legacyContext.hasContextChanged,
+    pushLegacyContextProvider = legacyContext.pushContextProvider,
+    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
+    invalidateContextProvider = legacyContext.invalidateContextProvider;
+  var enterHydrationState = hydrationContext.enterHydrationState,
+    resetHydrationState = hydrationContext.resetHydrationState,
+    tryToClaimNextHydratableInstance =
+      hydrationContext.tryToClaimNextHydratableInstance;
+
+  var _ReactFiberClassCompo = ReactFiberClassComponent(
+      legacyContext,
+      scheduleWork,
+      computeExpirationForFiber,
+      memoizeProps,
+      memoizeState
+    ),
+    adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
+    callGetDerivedStateFromProps =
+      _ReactFiberClassCompo.callGetDerivedStateFromProps,
+    constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
+    mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
+    resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
+    updateClassInstance = _ReactFiberClassCompo.updateClassInstance;
+
+  // TODO: Remove this and use reconcileChildrenAtExpirationTime directly.
+
+  function reconcileChildren(current, workInProgress, nextChildren) {
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      nextChildren,
+      workInProgress.expirationTime
+    );
+  }
+
+  function reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    renderExpirationTime
+  ) {
+    if (current === null) {
+      // If this is a fresh new component that hasn't been rendered yet, we
+      // won't update its child set by applying minimal side-effects. Instead,
+      // we will add them all to the child before it gets rendered. That means
+      // we can optimize this reconciliation pass by not tracking side-effects.
+      workInProgress.child = mountChildFibers(
+        workInProgress,
+        null,
+        nextChildren,
+        renderExpirationTime
+      );
+    } else {
+      // If the current child is the same as the work in progress, it means that
+      // we haven't yet started any work on these children. Therefore, we use
+      // the clone algorithm to create a copy of all the current children.
+
+      // If we had any progressed work already, that is invalid at this point so
+      // let's throw it out.
+      workInProgress.child = reconcileChildFibers(
+        workInProgress,
+        current.child,
+        nextChildren,
+        renderExpirationTime
+      );
+    }
+  }
+
+  function updateForwardRef(current, workInProgress) {
+    var render = workInProgress.type.render;
+    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+    return workInProgress.child;
+  }
+
+  function updateFragment(current, workInProgress) {
+    var nextChildren = workInProgress.pendingProps;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextChildren) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+    return workInProgress.child;
+  }
+
+  function updateMode(current, workInProgress) {
+    var nextChildren = workInProgress.pendingProps.children;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (
+      nextChildren === null ||
+      workInProgress.memoizedProps === nextChildren
+    ) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+    return workInProgress.child;
+  }
+
+  function markRef(current, workInProgress) {
+    var ref = workInProgress.ref;
+    if (
+      (current === null && ref !== null) ||
+      (current !== null && current.ref !== ref)
+    ) {
+      // Schedule a Ref effect
+      workInProgress.effectTag |= Ref;
+    }
+  }
+
+  function updateFunctionalComponent(current, workInProgress) {
+    var fn = workInProgress.type;
+    var nextProps = workInProgress.pendingProps;
+
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else {
+      if (workInProgress.memoizedProps === nextProps) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+      // TODO: consider bringing fn.shouldComponentUpdate() back.
+      // It used to be here.
+    }
+
+    var unmaskedContext = getUnmaskedContext(workInProgress);
+    var context = getMaskedContext(workInProgress, unmaskedContext);
+
+    var nextChildren = void 0;
+
+    {
+      ReactCurrentOwner.current = workInProgress;
+      ReactDebugCurrentFiber.setCurrentPhase("render");
+      nextChildren = fn(nextProps, context);
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
+    return workInProgress.child;
+  }
+
+  function updateClassComponent(current, workInProgress, renderExpirationTime) {
+    // Push context providers early to prevent context stack mismatches.
+    // During mounting we don't know the child context yet as the instance doesn't exist.
+    // We will invalidate the child context in finishClassComponent() right after rendering.
+    var hasContext = pushLegacyContextProvider(workInProgress);
+    var shouldUpdate = void 0;
+    if (current === null) {
+      if (workInProgress.stateNode === null) {
+        // In the initial pass we might need to construct the instance.
+        constructClassInstance(workInProgress, workInProgress.pendingProps);
+        mountClassInstance(workInProgress, renderExpirationTime);
+
+        shouldUpdate = true;
+      } else {
+        // In a resume, we'll already have an instance we can reuse.
+        shouldUpdate = resumeMountClassInstance(
+          workInProgress,
+          renderExpirationTime
+        );
+      }
+    } else {
+      shouldUpdate = updateClassInstance(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    }
+
+    // We processed the update queue inside updateClassInstance. It may have
+    // included some errors that were dispatched during the commit phase.
+    // TODO: Refactor class components so this is less awkward.
+    var didCaptureError = false;
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null && updateQueue.capturedValues !== null) {
+      shouldUpdate = true;
+      didCaptureError = true;
+    }
+    return finishClassComponent(
+      current,
+      workInProgress,
+      shouldUpdate,
+      hasContext,
+      didCaptureError,
+      renderExpirationTime
+    );
+  }
+
+  function finishClassComponent(
+    current,
+    workInProgress,
+    shouldUpdate,
+    hasContext,
+    didCaptureError,
+    renderExpirationTime
+  ) {
+    // Refs should update even if shouldComponentUpdate returns false
+    markRef(current, workInProgress);
+
+    if (!shouldUpdate && !didCaptureError) {
+      // Context providers should defer to sCU for rendering
+      if (hasContext) {
+        invalidateContextProvider(workInProgress, false);
+      }
+
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    var ctor = workInProgress.type;
+    var instance = workInProgress.stateNode;
+
+    // Rerender
+    ReactCurrentOwner.current = workInProgress;
+    var nextChildren = void 0;
+    if (
+      didCaptureError &&
+      (!enableGetDerivedStateFromCatch ||
+        typeof ctor.getDerivedStateFromCatch !== "function")
+    ) {
+      // If we captured an error, but getDerivedStateFrom catch is not defined,
+      // unmount all the children. componentDidCatch will schedule an update to
+      // re-render a fallback. This is temporary until we migrate everyone to
+      // the new API.
+      // TODO: Warn in a future release.
+      nextChildren = null;
+    } else {
+      {
+        ReactDebugCurrentFiber.setCurrentPhase("render");
+        nextChildren = instance.render();
+        if (
+          debugRenderPhaseSideEffects ||
+          (debugRenderPhaseSideEffectsForStrictMode &&
+            workInProgress.mode & StrictMode)
+        ) {
+          instance.render();
+        }
+        ReactDebugCurrentFiber.setCurrentPhase(null);
+      }
+    }
+
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
+    if (didCaptureError) {
+      // If we're recovering from an error, reconcile twice: first to delete
+      // all the existing children.
+      reconcileChildrenAtExpirationTime(
+        current,
+        workInProgress,
+        null,
+        renderExpirationTime
+      );
+      workInProgress.child = null;
+      // Now we can continue reconciling like normal. This has the effect of
+      // remounting all children regardless of whether their their
+      // identity matches.
+    }
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      nextChildren,
+      renderExpirationTime
+    );
+    // Memoize props and state using the values we just used to render.
+    // TODO: Restructure so we never read values from the instance.
+    memoizeState(workInProgress, instance.state);
+    memoizeProps(workInProgress, instance.props);
+
+    // The context might have changed so we need to recalculate it.
+    if (hasContext) {
+      invalidateContextProvider(workInProgress, true);
+    }
+
+    return workInProgress.child;
+  }
+
+  function pushHostRootContext(workInProgress) {
+    var root = workInProgress.stateNode;
+    if (root.pendingContext) {
+      pushTopLevelContextObject(
+        workInProgress,
+        root.pendingContext,
+        root.pendingContext !== root.context
+      );
+    } else if (root.context) {
+      // Should always be set
+      pushTopLevelContextObject(workInProgress, root.context, false);
+    }
+    pushHostContainer(workInProgress, root.containerInfo);
+  }
+
+  function updateHostRoot(current, workInProgress, renderExpirationTime) {
+    pushHostRootContext(workInProgress);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      var prevState = workInProgress.memoizedState;
+      var state = processUpdateQueue(
+        current,
+        workInProgress,
+        updateQueue,
+        null,
+        null,
+        renderExpirationTime
+      );
+      memoizeState(workInProgress, state);
+      updateQueue = workInProgress.updateQueue;
+
+      var element = void 0;
+      if (updateQueue !== null && updateQueue.capturedValues !== null) {
+        // There's an uncaught error. Unmount the whole root.
+        element = null;
+      } else if (prevState === state) {
+        // If the state is the same as before, that's a bailout because we had
+        // no work that expires at this time.
+        resetHydrationState();
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      } else {
+        element = state.element;
+      }
+      var root = workInProgress.stateNode;
+      if (
+        (current === null || current.child === null) &&
+        root.hydrate &&
+        enterHydrationState(workInProgress)
+      ) {
+        // If we don't have any current children this might be the first pass.
+        // We always try to hydrate. If this isn't a hydration pass there won't
+        // be any children to hydrate which is effectively the same thing as
+        // not hydrating.
+
+        // This is a bit of a hack. We track the host root as a placement to
+        // know that we're currently in a mounting state. That way isMounted
+        // works as expected. We must reset this before committing.
+        // TODO: Delete this when we delete isMounted and findDOMNode.
+        workInProgress.effectTag |= Placement;
+
+        // Ensure that children mount into this root without tracking
+        // side-effects. This ensures that we don't store Placement effects on
+        // nodes that will be hydrated.
+        workInProgress.child = mountChildFibers(
+          workInProgress,
+          null,
+          element,
+          renderExpirationTime
+        );
+      } else {
+        // Otherwise reset hydration state in case we aborted and resumed another
+        // root.
+        resetHydrationState();
+        reconcileChildren(current, workInProgress, element);
+      }
+      memoizeState(workInProgress, state);
+      return workInProgress.child;
+    }
+    resetHydrationState();
+    // If there is no update queue, that's a bailout because the root has no props.
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  }
+
+  function updateHostComponent(current, workInProgress, renderExpirationTime) {
+    pushHostContext(workInProgress);
+
+    if (current === null) {
+      tryToClaimNextHydratableInstance(workInProgress);
+    }
+
+    var type = workInProgress.type;
+    var memoizedProps = workInProgress.memoizedProps;
+    var nextProps = workInProgress.pendingProps;
+    var prevProps = current !== null ? current.memoizedProps : null;
+
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (memoizedProps === nextProps) {
+      var isHidden =
+        workInProgress.mode & AsyncMode &&
+        shouldDeprioritizeSubtree(type, nextProps);
+      if (isHidden) {
+        // Before bailing out, make sure we've deprioritized a hidden component.
+        workInProgress.expirationTime = Never;
+      }
+      if (!isHidden || renderExpirationTime !== Never) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+      // If we're rendering a hidden node at hidden priority, don't bailout. The
+      // parent is complete, but the children may not be.
+    }
+
+    var nextChildren = nextProps.children;
+    var isDirectTextChild = shouldSetTextContent(type, nextProps);
+
+    if (isDirectTextChild) {
+      // We special case a direct text child of a host node. This is a common
+      // case. We won't handle it as a reified child. We will instead handle
+      // this in the host environment that also have access to this prop. That
+      // avoids allocating another HostText fiber and traversing it.
+      nextChildren = null;
+    } else if (prevProps && shouldSetTextContent(type, prevProps)) {
+      // If we're switching from a direct text child to a normal child, or to
+      // empty, we need to schedule the text content to be reset.
+      workInProgress.effectTag |= ContentReset;
+    }
+
+    markRef(current, workInProgress);
+
+    // Check the host config to see if the children are offscreen/hidden.
+    if (
+      renderExpirationTime !== Never &&
+      workInProgress.mode & AsyncMode &&
+      shouldDeprioritizeSubtree(type, nextProps)
+    ) {
+      // Down-prioritize the children.
+      workInProgress.expirationTime = Never;
+      // Bailout and come back to this fiber later.
+      workInProgress.memoizedProps = nextProps;
+      return null;
+    }
+
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
+    return workInProgress.child;
+  }
+
+  function updateHostText(current, workInProgress) {
+    if (current === null) {
+      tryToClaimNextHydratableInstance(workInProgress);
+    }
+    var nextProps = workInProgress.pendingProps;
+    memoizeProps(workInProgress, nextProps);
+    // Nothing to do here. This is terminal. We'll do the completion step
+    // immediately after.
+    return null;
+  }
+
+  function mountIndeterminateComponent(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    invariant(
+      current === null,
+      "An indeterminate component should never have mounted. This error is " +
+        "likely caused by a bug in React. Please file an issue."
+    );
+    var fn = workInProgress.type;
+    var props = workInProgress.pendingProps;
+    var unmaskedContext = getUnmaskedContext(workInProgress);
+    var context = getMaskedContext(workInProgress, unmaskedContext);
+
+    var value = void 0;
+
+    {
+      if (fn.prototype && typeof fn.prototype.render === "function") {
+        var componentName = getComponentName(workInProgress) || "Unknown";
+
+        if (!didWarnAboutBadClass[componentName]) {
+          warning(
+            false,
+            "The <%s /> component appears to have a render method, but doesn't extend React.Component. " +
+              "This is likely to cause errors. Change %s to extend React.Component instead.",
+            componentName,
+            componentName
+          );
+          didWarnAboutBadClass[componentName] = true;
+        }
+      }
+      ReactCurrentOwner.current = workInProgress;
+      value = fn(props, context);
+    }
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
+
+    if (
+      typeof value === "object" &&
+      value !== null &&
+      typeof value.render === "function" &&
+      value.$$typeof === undefined
+    ) {
+      var Component = workInProgress.type;
+
+      // Proceed under the assumption that this is a class instance
+      workInProgress.tag = ClassComponent;
+
+      workInProgress.memoizedState =
+        value.state !== null && value.state !== undefined ? value.state : null;
+
+      if (typeof Component.getDerivedStateFromProps === "function") {
+        var partialState = callGetDerivedStateFromProps(
+          workInProgress,
+          value,
+          props,
+          workInProgress.memoizedState
+        );
+
+        if (partialState !== null && partialState !== undefined) {
+          workInProgress.memoizedState = Object.assign(
+            {},
+            workInProgress.memoizedState,
+            partialState
+          );
+        }
+      }
+
+      // Push context providers early to prevent context stack mismatches.
+      // During mounting we don't know the child context yet as the instance doesn't exist.
+      // We will invalidate the child context in finishClassComponent() right after rendering.
+      var hasContext = pushLegacyContextProvider(workInProgress);
+      adoptClassInstance(workInProgress, value);
+      mountClassInstance(workInProgress, renderExpirationTime);
+      return finishClassComponent(
+        current,
+        workInProgress,
+        true,
+        hasContext,
+        false,
+        renderExpirationTime
+      );
+    } else {
+      // Proceed under the assumption that this is a functional component
+      workInProgress.tag = FunctionalComponent;
+      {
+        var _Component = workInProgress.type;
+
+        if (_Component) {
+          !!_Component.childContextTypes
+            ? warning(
+                false,
+                "%s(...): childContextTypes cannot be defined on a functional component.",
+                _Component.displayName || _Component.name || "Component"
+              )
+            : void 0;
+        }
+        if (workInProgress.ref !== null) {
+          var info = "";
+          var ownerName = ReactDebugCurrentFiber.getCurrentFiberOwnerName();
+          if (ownerName) {
+            info += "\n\nCheck the render method of `" + ownerName + "`.";
+          }
+
+          var warningKey = ownerName || workInProgress._debugID || "";
+          var debugSource = workInProgress._debugSource;
+          if (debugSource) {
+            warningKey = debugSource.fileName + ":" + debugSource.lineNumber;
+          }
+          if (!didWarnAboutStatelessRefs[warningKey]) {
+            didWarnAboutStatelessRefs[warningKey] = true;
+            warning(
+              false,
+              "Stateless function components cannot be given refs. " +
+                "Attempts to access this ref will fail.%s%s",
+              info,
+              ReactDebugCurrentFiber.getCurrentFiberStackAddendum()
+            );
+          }
+        }
+
+        if (typeof fn.getDerivedStateFromProps === "function") {
+          var _componentName = getComponentName(workInProgress) || "Unknown";
+
+          if (
+            !didWarnAboutGetDerivedStateOnFunctionalComponent[_componentName]
+          ) {
+            warning(
+              false,
+              "%s: Stateless functional components do not support getDerivedStateFromProps.",
+              _componentName
+            );
+            didWarnAboutGetDerivedStateOnFunctionalComponent[
+              _componentName
+            ] = true;
+          }
+        }
+      }
+      reconcileChildren(current, workInProgress, value);
+      memoizeProps(workInProgress, props);
+      return workInProgress.child;
+    }
+  }
+
+  function updateCallComponent(current, workInProgress, renderExpirationTime) {
+    var nextProps = workInProgress.pendingProps;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextProps) {
+      nextProps = workInProgress.memoizedProps;
+      // TODO: When bailing out, we might need to return the stateNode instead
+      // of the child. To check it for work.
+      // return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    var nextChildren = nextProps.children;
+
+    // The following is a fork of reconcileChildrenAtExpirationTime but using
+    // stateNode to store the child.
+    if (current === null) {
+      workInProgress.stateNode = mountChildFibers(
+        workInProgress,
+        workInProgress.stateNode,
+        nextChildren,
+        renderExpirationTime
+      );
+    } else {
+      workInProgress.stateNode = reconcileChildFibers(
+        workInProgress,
+        current.stateNode,
+        nextChildren,
+        renderExpirationTime
+      );
+    }
+
+    memoizeProps(workInProgress, nextProps);
+    // This doesn't take arbitrary time so we could synchronously just begin
+    // eagerly do the work of workInProgress.child as an optimization.
+    return workInProgress.stateNode;
+  }
+
+  function updatePortalComponent(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
+    var nextChildren = workInProgress.pendingProps;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextChildren) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    if (current === null) {
+      // Portals are special because we don't append the children during mount
+      // but at commit. Therefore we need to track insertions which the normal
+      // flow doesn't do during mount. This doesn't happen at the root because
+      // the root always starts with a "current" with a null child.
+      // TODO: Consider unifying this with how the root works.
+      workInProgress.child = reconcileChildFibers(
+        workInProgress,
+        null,
+        nextChildren,
+        renderExpirationTime
+      );
+      memoizeProps(workInProgress, nextChildren);
+    } else {
+      reconcileChildren(current, workInProgress, nextChildren);
+      memoizeProps(workInProgress, nextChildren);
+    }
+    return workInProgress.child;
+  }
+
+  function propagateContextChange(
+    workInProgress,
+    context,
+    changedBits,
+    renderExpirationTime
+  ) {
+    var fiber = workInProgress.child;
+    if (fiber !== null) {
+      // Set the return pointer of the child to the work-in-progress fiber.
+      fiber["return"] = workInProgress;
+    }
+    while (fiber !== null) {
+      var nextFiber = void 0;
+      // Visit this fiber.
+      switch (fiber.tag) {
+        case ContextConsumer:
+          // Check if the context matches.
+          var observedBits = fiber.stateNode | 0;
+          if (fiber.type === context && (observedBits & changedBits) !== 0) {
+            // Update the expiration time of all the ancestors, including
+            // the alternates.
+            var node = fiber;
+            while (node !== null) {
+              var alternate = node.alternate;
+              if (
+                node.expirationTime === NoWork ||
+                node.expirationTime > renderExpirationTime
+              ) {
+                node.expirationTime = renderExpirationTime;
+                if (
+                  alternate !== null &&
+                  (alternate.expirationTime === NoWork ||
+                    alternate.expirationTime > renderExpirationTime)
+                ) {
+                  alternate.expirationTime = renderExpirationTime;
+                }
+              } else if (
+                alternate !== null &&
+                (alternate.expirationTime === NoWork ||
+                  alternate.expirationTime > renderExpirationTime)
+              ) {
+                alternate.expirationTime = renderExpirationTime;
+              } else {
+                // Neither alternate was updated, which means the rest of the
+                // ancestor path already has sufficient priority.
+                break;
+              }
+              node = node["return"];
+            }
+            // Don't scan deeper than a matching consumer. When we render the
+            // consumer, we'll continue scanning from that point. This way the
+            // scanning work is time-sliced.
+            nextFiber = null;
+          } else {
+            // Traverse down.
+            nextFiber = fiber.child;
+          }
+          break;
+        case ContextProvider:
+          // Don't scan deeper if this is a matching provider
+          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+          break;
+        default:
+          // Traverse down.
+          nextFiber = fiber.child;
+          break;
+      }
+      if (nextFiber !== null) {
+        // Set the return pointer of the child to the work-in-progress fiber.
+        nextFiber["return"] = fiber;
+      } else {
+        // No child. Traverse to next sibling.
+        nextFiber = fiber;
+        while (nextFiber !== null) {
+          if (nextFiber === workInProgress) {
+            // We're back to the root of this subtree. Exit.
+            nextFiber = null;
+            break;
+          }
+          var sibling = nextFiber.sibling;
+          if (sibling !== null) {
+            nextFiber = sibling;
+            break;
+          }
+          // No more siblings. Traverse up.
+          nextFiber = nextFiber["return"];
+        }
+      }
+      fiber = nextFiber;
+    }
+  }
+
+  function updateContextProvider(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var providerType = workInProgress.type;
+    var context = providerType._context;
+
+    var newProps = workInProgress.pendingProps;
+    var oldProps = workInProgress.memoizedProps;
+
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (oldProps === newProps) {
+      workInProgress.stateNode = 0;
+      pushProvider(workInProgress);
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    var newValue = newProps.value;
+    workInProgress.memoizedProps = newProps;
+
+    var changedBits = void 0;
+    if (oldProps === null) {
+      // Initial render
+      changedBits = MAX_SIGNED_31_BIT_INT;
+    } else {
+      if (oldProps.value === newProps.value) {
+        // No change. Bailout early if children are the same.
+        if (oldProps.children === newProps.children) {
+          workInProgress.stateNode = 0;
+          pushProvider(workInProgress);
+          return bailoutOnAlreadyFinishedWork(current, workInProgress);
+        }
+        changedBits = 0;
+      } else {
+        var oldValue = oldProps.value;
+        // Use Object.is to compare the new context value to the old value.
+        // Inlined Object.is polyfill.
+        // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+        if (
+          (oldValue === newValue &&
+            (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
+          (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
+        ) {
+          // No change. Bailout early if children are the same.
+          if (oldProps.children === newProps.children) {
+            workInProgress.stateNode = 0;
+            pushProvider(workInProgress);
+            return bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+          changedBits = 0;
+        } else {
+          changedBits =
+            typeof context._calculateChangedBits === "function"
+              ? context._calculateChangedBits(oldValue, newValue)
+              : MAX_SIGNED_31_BIT_INT;
+          {
+            !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
+              ? warning(
+                  false,
+                  "calculateChangedBits: Expected the return value to be a " +
+                    "31-bit integer. Instead received: %s",
+                  changedBits
+                )
+              : void 0;
+          }
+          changedBits |= 0;
+
+          if (changedBits === 0) {
+            // No change. Bailout early if children are the same.
+            if (oldProps.children === newProps.children) {
+              workInProgress.stateNode = 0;
+              pushProvider(workInProgress);
+              return bailoutOnAlreadyFinishedWork(current, workInProgress);
+            }
+          } else {
+            propagateContextChange(
+              workInProgress,
+              context,
+              changedBits,
+              renderExpirationTime
+            );
+          }
+        }
+      }
+    }
+
+    workInProgress.stateNode = changedBits;
+    pushProvider(workInProgress);
+
+    var newChildren = newProps.children;
+    reconcileChildren(current, workInProgress, newChildren);
+    return workInProgress.child;
+  }
+
+  function updateContextConsumer(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var context = workInProgress.type;
+    var newProps = workInProgress.pendingProps;
+    var oldProps = workInProgress.memoizedProps;
+
+    var newValue = context._currentValue;
+    var changedBits = context._changedBits;
+
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (changedBits === 0 && oldProps === newProps) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    workInProgress.memoizedProps = newProps;
+
+    var observedBits = newProps.unstable_observedBits;
+    if (observedBits === undefined || observedBits === null) {
+      // Subscribe to all changes by default
+      observedBits = MAX_SIGNED_31_BIT_INT;
+    }
+    // Store the observedBits on the fiber's stateNode for quick access.
+    workInProgress.stateNode = observedBits;
+
+    if ((changedBits & observedBits) !== 0) {
+      // Context change propagation stops at matching consumers, for time-
+      // slicing. Continue the propagation here.
+      propagateContextChange(
+        workInProgress,
+        context,
+        changedBits,
+        renderExpirationTime
+      );
+    } else if (oldProps === newProps) {
+      // Skip over a memoized parent with a bitmask bailout even
+      // if we began working on it because of a deeper matching child.
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    // There is no bailout on `children` equality because we expect people
+    // to often pass a bound method as a child, but it may reference
+    // `this.state` or `this.props` (and thus needs to re-render on `setState`).
+
+    var render = newProps.children;
+
+    {
+      !(typeof render === "function")
+        ? warning(
+            false,
+            "A context consumer was rendered with multiple children, or a child " +
+              "that isn't a function. A context consumer expects a single child " +
+              "that is a function. If you did pass a function, make sure there " +
+              "is no trailing or leading whitespace around it."
+          )
+        : void 0;
+    }
+
+    var newChildren = render(newValue);
+    reconcileChildren(current, workInProgress, newChildren);
+    return workInProgress.child;
+  }
+
+  /*
+  function reuseChildrenEffects(returnFiber : Fiber, firstChild : Fiber) {
+    let child = firstChild;
+    do {
+      // Ensure that the first and last effect of the parent corresponds
+      // to the children's first and last effect.
+      if (!returnFiber.firstEffect) {
+        returnFiber.firstEffect = child.firstEffect;
+      }
+      if (child.lastEffect) {
+        if (returnFiber.lastEffect) {
+          returnFiber.lastEffect.nextEffect = child.firstEffect;
+        }
+        returnFiber.lastEffect = child.lastEffect;
+      }
+    } while (child = child.sibling);
+  }
+  */
+
+  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+    cancelWorkTimer(workInProgress);
+
+    // TODO: We should ideally be able to bail out early if the children have no
+    // more work to do. However, since we don't have a separation of this
+    // Fiber's priority and its children yet - we don't know without doing lots
+    // of the same work we do anyway. Once we have that separation we can just
+    // bail out here if the children has no more work at this priority level.
+    // if (workInProgress.priorityOfChildren <= priorityLevel) {
+    //   // If there are side-effects in these children that have not yet been
+    //   // committed we need to ensure that they get properly transferred up.
+    //   if (current && current.child !== workInProgress.child) {
+    //     reuseChildrenEffects(workInProgress, child);
+    //   }
+    //   return null;
+    // }
+
+    cloneChildFibers(current, workInProgress);
+    return workInProgress.child;
+  }
+
+  function bailoutOnLowPriority(current, workInProgress) {
+    cancelWorkTimer(workInProgress);
+
+    // TODO: Handle HostComponent tags here as well and call pushHostContext()?
+    // See PR 8590 discussion for context
+    switch (workInProgress.tag) {
+      case HostRoot:
+        pushHostRootContext(workInProgress);
+        break;
+      case ClassComponent:
+        pushLegacyContextProvider(workInProgress);
+        break;
+      case HostPortal:
+        pushHostContainer(
+          workInProgress,
+          workInProgress.stateNode.containerInfo
+        );
+        break;
+      case ContextProvider:
+        pushProvider(workInProgress);
+        break;
+    }
+    // TODO: What if this is currently in progress?
+    // How can that happen? How is this not being cloned?
+    return null;
+  }
+
+  // TODO: Delete memoizeProps/State and move to reconcile/bailout instead
+  function memoizeProps(workInProgress, nextProps) {
+    workInProgress.memoizedProps = nextProps;
+  }
+
+  function memoizeState(workInProgress, nextState) {
+    workInProgress.memoizedState = nextState;
+    // Don't reset the updateQueue, in case there are pending updates. Resetting
+    // is handled by processUpdateQueue.
+  }
+
+  function beginWork(current, workInProgress, renderExpirationTime) {
+    if (
+      workInProgress.expirationTime === NoWork ||
+      workInProgress.expirationTime > renderExpirationTime
+    ) {
+      return bailoutOnLowPriority(current, workInProgress);
+    }
+
+    switch (workInProgress.tag) {
+      case IndeterminateComponent:
+        return mountIndeterminateComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case FunctionalComponent:
+        return updateFunctionalComponent(current, workInProgress);
+      case ClassComponent:
+        return updateClassComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case HostRoot:
+        return updateHostRoot(current, workInProgress, renderExpirationTime);
+      case HostComponent:
+        return updateHostComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case HostText:
+        return updateHostText(current, workInProgress);
+      case CallHandlerPhase:
+        // This is a restart. Reset the tag to the initial phase.
+        workInProgress.tag = CallComponent;
+      // Intentionally fall through since this is now the same.
+      case CallComponent:
+        return updateCallComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case ReturnComponent:
+        // A return component is just a placeholder, we can just run through the
+        // next one immediately.
+        return null;
+      case HostPortal:
+        return updatePortalComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case ForwardRef:
+        return updateForwardRef(current, workInProgress);
+      case Fragment:
+        return updateFragment(current, workInProgress);
+      case Mode:
+        return updateMode(current, workInProgress);
+      case ContextProvider:
+        return updateContextProvider(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case ContextConsumer:
+        return updateContextConsumer(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      default:
+        invariant(
+          false,
+          "Unknown unit of work tag. This error is likely caused by a bug in " +
+            "React. Please file an issue."
+        );
+    }
+  }
+
+  return {
+    beginWork: beginWork
+  };
+};
+
+var ReactFiberCompleteWork = function(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext
+) {
+  var createInstance = config.createInstance,
+    createTextInstance = config.createTextInstance,
+    appendInitialChild = config.appendInitialChild,
+    finalizeInitialChildren = config.finalizeInitialChildren,
+    prepareUpdate = config.prepareUpdate,
+    mutation = config.mutation,
+    persistence = config.persistence;
+  var getRootHostContainer = hostContext.getRootHostContainer,
+    popHostContext = hostContext.popHostContext,
+    getHostContext = hostContext.getHostContext,
+    popHostContainer = hostContext.popHostContainer;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+  var prepareToHydrateHostInstance =
+      hydrationContext.prepareToHydrateHostInstance,
+    prepareToHydrateHostTextInstance =
+      hydrationContext.prepareToHydrateHostTextInstance,
+    popHydrationState = hydrationContext.popHydrationState;
+
+  function markUpdate(workInProgress) {
+    // Tag the fiber with an update effect. This turns a Placement into
+    // a PlacementAndUpdate.
+    workInProgress.effectTag |= Update;
+  }
+
+  function markRef(workInProgress) {
+    workInProgress.effectTag |= Ref;
+  }
+
+  function appendAllReturns(returns, workInProgress) {
+    var node = workInProgress.stateNode;
+    if (node) {
+      node["return"] = workInProgress;
+    }
+    while (node !== null) {
+      if (
+        node.tag === HostComponent ||
+        node.tag === HostText ||
+        node.tag === HostPortal
+      ) {
+        invariant(false, "A call cannot have host component children.");
+      } else if (node.tag === ReturnComponent) {
+        returns.push(node.pendingProps.value);
+      } else if (node.child !== null) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === workInProgress) {
+          return;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  function moveCallToHandlerPhase(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var props = workInProgress.memoizedProps;
+    invariant(
+      props,
+      "Should be resolved by now. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+
+    // First step of the call has completed. Now we need to do the second.
+    // TODO: It would be nice to have a multi stage call represented by a
+    // single component, or at least tail call optimize nested ones. Currently
+    // that requires additional fields that we don't want to add to the fiber.
+    // So this requires nested handlers.
+    // Note: This doesn't mutate the alternate node. I don't think it needs to
+    // since this stage is reset for every pass.
+    workInProgress.tag = CallHandlerPhase;
+
+    // Build up the returns.
+    // TODO: Compare this to a generator or opaque helpers like Children.
+    var returns = [];
+    appendAllReturns(returns, workInProgress);
+    var fn = props.handler;
+    var childProps = props.props;
+    var nextChildren = fn(childProps, returns);
+
+    var currentFirstChild = current !== null ? current.child : null;
+    workInProgress.child = reconcileChildFibers(
+      workInProgress,
+      currentFirstChild,
+      nextChildren,
+      renderExpirationTime
+    );
+    return workInProgress.child;
+  }
+
+  function appendAllChildren(parent, workInProgress) {
+    // We only have the top Fiber that was created but we need recurse down its
+    // children to find all the terminal nodes.
+    var node = workInProgress.child;
+    while (node !== null) {
+      if (node.tag === HostComponent || node.tag === HostText) {
+        appendInitialChild(parent, node.stateNode);
+      } else if (node.tag === HostPortal) {
+        // If we have a portal child, then we don't want to traverse
+        // down its children. Instead, we'll get insertions from each child in
+        // the portal directly.
+      } else if (node.child !== null) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      if (node === workInProgress) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === workInProgress) {
+          return;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  var updateHostContainer = void 0;
+  var updateHostComponent = void 0;
+  var updateHostText = void 0;
+  if (mutation) {
+    if (enableMutatingReconciler) {
+      // Mutation mode
+      updateHostContainer = function(workInProgress) {
+        // Noop
+      };
+      updateHostComponent = function(
+        current,
+        workInProgress,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        rootContainerInstance,
+        currentHostContext
+      ) {
+        // TODO: Type this specific to this type of component.
+        workInProgress.updateQueue = updatePayload;
+        // If the update payload indicates that there is a change or if there
+        // is a new ref we mark this as an update. All the work is done in commitWork.
+        if (updatePayload) {
+          markUpdate(workInProgress);
+        }
+      };
+      updateHostText = function(current, workInProgress, oldText, newText) {
+        // If the text differs, mark it as an update. All the work in done in commitWork.
+        if (oldText !== newText) {
+          markUpdate(workInProgress);
+        }
+      };
+    } else {
+      invariant(false, "Mutating reconciler is disabled.");
+    }
+  } else if (persistence) {
+    if (enablePersistentReconciler) {
+      // Persistent host tree mode
+      var cloneInstance = persistence.cloneInstance,
+        createContainerChildSet = persistence.createContainerChildSet,
+        appendChildToContainerChildSet =
+          persistence.appendChildToContainerChildSet,
+        finalizeContainerChildren = persistence.finalizeContainerChildren;
+
+      // An unfortunate fork of appendAllChildren because we have two different parent types.
+
+      var appendAllChildrenToContainer = function(
+        containerChildSet,
+        workInProgress
+      ) {
+        // We only have the top Fiber that was created but we need recurse down its
+        // children to find all the terminal nodes.
+        var node = workInProgress.child;
+        while (node !== null) {
+          if (node.tag === HostComponent || node.tag === HostText) {
+            appendChildToContainerChildSet(containerChildSet, node.stateNode);
+          } else if (node.tag === HostPortal) {
+            // If we have a portal child, then we don't want to traverse
+            // down its children. Instead, we'll get insertions from each child in
+            // the portal directly.
+          } else if (node.child !== null) {
+            node.child["return"] = node;
+            node = node.child;
+            continue;
+          }
+          if (node === workInProgress) {
+            return;
+          }
+          while (node.sibling === null) {
+            if (node["return"] === null || node["return"] === workInProgress) {
+              return;
+            }
+            node = node["return"];
+          }
+          node.sibling["return"] = node["return"];
+          node = node.sibling;
+        }
+      };
+      updateHostContainer = function(workInProgress) {
+        var portalOrRoot = workInProgress.stateNode;
+        var childrenUnchanged = workInProgress.firstEffect === null;
+        if (childrenUnchanged) {
+          // No changes, just reuse the existing instance.
+        } else {
+          var container = portalOrRoot.containerInfo;
+          var newChildSet = createContainerChildSet(container);
+          // If children might have changed, we have to add them all to the set.
+          appendAllChildrenToContainer(newChildSet, workInProgress);
+          portalOrRoot.pendingChildren = newChildSet;
+          // Schedule an update on the container to swap out the container.
+          markUpdate(workInProgress);
+          finalizeContainerChildren(container, newChildSet);
+        }
+      };
+      updateHostComponent = function(
+        current,
+        workInProgress,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        rootContainerInstance,
+        currentHostContext
+      ) {
+        // If there are no effects associated with this node, then none of our children had any updates.
+        // This guarantees that we can reuse all of them.
+        var childrenUnchanged = workInProgress.firstEffect === null;
+        var currentInstance = current.stateNode;
+        if (childrenUnchanged && updatePayload === null) {
+          // No changes, just reuse the existing instance.
+          // Note that this might release a previous clone.
+          workInProgress.stateNode = currentInstance;
+        } else {
+          var recyclableInstance = workInProgress.stateNode;
+          var newInstance = cloneInstance(
+            currentInstance,
+            updatePayload,
+            type,
+            oldProps,
+            newProps,
+            workInProgress,
+            childrenUnchanged,
+            recyclableInstance
+          );
+          if (
+            finalizeInitialChildren(
+              newInstance,
+              type,
+              newProps,
+              rootContainerInstance,
+              currentHostContext
+            )
+          ) {
+            markUpdate(workInProgress);
+          }
+          workInProgress.stateNode = newInstance;
+          if (childrenUnchanged) {
+            // If there are no other effects in this tree, we need to flag this node as having one.
+            // Even though we're not going to use it for anything.
+            // Otherwise parents won't know that there are new children to propagate upwards.
+            markUpdate(workInProgress);
+          } else {
+            // If children might have changed, we have to add them all to the set.
+            appendAllChildren(newInstance, workInProgress);
+          }
+        }
+      };
+      updateHostText = function(current, workInProgress, oldText, newText) {
+        if (oldText !== newText) {
+          // If the text content differs, we'll create a new text instance for it.
+          var rootContainerInstance = getRootHostContainer();
+          var currentHostContext = getHostContext();
+          workInProgress.stateNode = createTextInstance(
+            newText,
+            rootContainerInstance,
+            currentHostContext,
+            workInProgress
+          );
+          // We'll have to mark it as having an effect, even though we won't use the effect for anything.
+          // This lets the parents know that at least one of their children has changed.
+          markUpdate(workInProgress);
+        }
+      };
+    } else {
+      invariant(false, "Persistent reconciler is disabled.");
+    }
+  } else {
+    if (enableNoopReconciler) {
+      // No host operations
+      updateHostContainer = function(workInProgress) {
+        // Noop
+      };
+      updateHostComponent = function(
+        current,
+        workInProgress,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        rootContainerInstance,
+        currentHostContext
+      ) {
+        // Noop
+      };
+      updateHostText = function(current, workInProgress, oldText, newText) {
+        // Noop
+      };
+    } else {
+      invariant(false, "Noop reconciler is disabled.");
+    }
+  }
+
+  function completeWork(current, workInProgress, renderExpirationTime) {
+    var newProps = workInProgress.pendingProps;
+    switch (workInProgress.tag) {
+      case FunctionalComponent:
+        return null;
+      case ClassComponent: {
+        // We are leaving this subtree, so pop context if any.
+        popLegacyContextProvider(workInProgress);
+
+        // If this component caught an error, schedule an error log effect.
+        var instance = workInProgress.stateNode;
+        var updateQueue = workInProgress.updateQueue;
+        if (updateQueue !== null && updateQueue.capturedValues !== null) {
+          workInProgress.effectTag &= ~DidCapture;
+          if (typeof instance.componentDidCatch === "function") {
+            workInProgress.effectTag |= ErrLog;
+          } else {
+            // Normally we clear this in the commit phase, but since we did not
+            // schedule an effect, we need to reset it here.
+            updateQueue.capturedValues = null;
+          }
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var fiberRoot = workInProgress.stateNode;
+        if (fiberRoot.pendingContext) {
+          fiberRoot.context = fiberRoot.pendingContext;
+          fiberRoot.pendingContext = null;
+        }
+        if (current === null || current.child === null) {
+          // If we hydrated, pop so that we can delete any remaining children
+          // that weren't hydrated.
+          popHydrationState(workInProgress);
+          // This resets the hacky state to fix isMounted before committing.
+          // TODO: Delete this when we delete isMounted and findDOMNode.
+          workInProgress.effectTag &= ~Placement;
+        }
+        updateHostContainer(workInProgress);
+
+        var _updateQueue = workInProgress.updateQueue;
+        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
+          workInProgress.effectTag |= ErrLog;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        var rootContainerInstance = getRootHostContainer();
+        var type = workInProgress.type;
+        if (current !== null && workInProgress.stateNode != null) {
+          // If we have an alternate, that means this is an update and we need to
+          // schedule a side-effect to do the updates.
+          var oldProps = current.memoizedProps;
+          // If we get updated because one of our children updated, we don't
+          // have newProps so we'll have to reuse them.
+          // TODO: Split the update API as separate for the props vs. children.
+          // Even better would be if children weren't special cased at all tho.
+          var _instance = workInProgress.stateNode;
+          var currentHostContext = getHostContext();
+          // TODO: Experiencing an error where oldProps is null. Suggests a host
+          // component is hitting the resume path. Figure out why. Possibly
+          // related to `hidden`.
+          var updatePayload = prepareUpdate(
+            _instance,
+            type,
+            oldProps,
+            newProps,
+            rootContainerInstance,
+            currentHostContext
+          );
+
+          updateHostComponent(
+            current,
+            workInProgress,
+            updatePayload,
+            type,
+            oldProps,
+            newProps,
+            rootContainerInstance,
+            currentHostContext
+          );
+
+          if (current.ref !== workInProgress.ref) {
+            markRef(workInProgress);
+          }
+        } else {
+          if (!newProps) {
+            invariant(
+              workInProgress.stateNode !== null,
+              "We must have new props for new mounts. This error is likely " +
+                "caused by a bug in React. Please file an issue."
+            );
+            // This can happen when we abort work.
+            return null;
+          }
+
+          var _currentHostContext = getHostContext();
+          // TODO: Move createInstance to beginWork and keep it on a context
+          // "stack" as the parent. Then append children as we go in beginWork
+          // or completeWork depending on we want to add then top->down or
+          // bottom->up. Top->down is faster in IE11.
+          var wasHydrated = popHydrationState(workInProgress);
+          if (wasHydrated) {
+            // TODO: Move this and createInstance step into the beginPhase
+            // to consolidate.
+            if (
+              prepareToHydrateHostInstance(
+                workInProgress,
+                rootContainerInstance,
+                _currentHostContext
+              )
+            ) {
+              // If changes to the hydrated node needs to be applied at the
+              // commit-phase we mark this as such.
+              markUpdate(workInProgress);
+            }
+          } else {
+            var _instance2 = createInstance(
+              type,
+              newProps,
+              rootContainerInstance,
+              _currentHostContext,
+              workInProgress
+            );
+
+            appendAllChildren(_instance2, workInProgress);
+
+            // Certain renderers require commit-time effects for initial mount.
+            // (eg DOM renderer supports auto-focus for certain elements).
+            // Make sure such renderers get scheduled for later work.
+            if (
+              finalizeInitialChildren(
+                _instance2,
+                type,
+                newProps,
+                rootContainerInstance,
+                _currentHostContext
+              )
+            ) {
+              markUpdate(workInProgress);
+            }
+            workInProgress.stateNode = _instance2;
+          }
+
+          if (workInProgress.ref !== null) {
+            // If there is a ref on a host node we need to schedule a callback
+            markRef(workInProgress);
+          }
+        }
+        return null;
+      }
+      case HostText: {
+        var newText = newProps;
+        if (current && workInProgress.stateNode != null) {
+          var oldText = current.memoizedProps;
+          // If we have an alternate, that means this is an update and we need
+          // to schedule a side-effect to do the updates.
+          updateHostText(current, workInProgress, oldText, newText);
+        } else {
+          if (typeof newText !== "string") {
+            invariant(
+              workInProgress.stateNode !== null,
+              "We must have new props for new mounts. This error is likely " +
+                "caused by a bug in React. Please file an issue."
+            );
+            // This can happen when we abort work.
+            return null;
+          }
+          var _rootContainerInstance = getRootHostContainer();
+          var _currentHostContext2 = getHostContext();
+          var _wasHydrated = popHydrationState(workInProgress);
+          if (_wasHydrated) {
+            if (prepareToHydrateHostTextInstance(workInProgress)) {
+              markUpdate(workInProgress);
+            }
+          } else {
+            workInProgress.stateNode = createTextInstance(
+              newText,
+              _rootContainerInstance,
+              _currentHostContext2,
+              workInProgress
+            );
+          }
+        }
+        return null;
+      }
+      case CallComponent:
+        return moveCallToHandlerPhase(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
+      case CallHandlerPhase:
+        // Reset the tag to now be a first phase call.
+        workInProgress.tag = CallComponent;
+        return null;
+      case ReturnComponent:
+        // Does nothing.
+        return null;
+      case ForwardRef:
+        return null;
+      case Fragment:
+        return null;
+      case Mode:
+        return null;
+      case HostPortal:
+        popHostContainer(workInProgress);
+        updateHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        // Pop provider fiber
+        popProvider(workInProgress);
+        return null;
+      case ContextConsumer:
+        return null;
+      // Error cases
+      case IndeterminateComponent:
+        invariant(
+          false,
+          "An indeterminate component should have become determinate before " +
+            "completing. This error is likely caused by a bug in React. Please " +
+            "file an issue."
+        );
+      // eslint-disable-next-line no-fallthrough
+      default:
+        invariant(
+          false,
+          "Unknown unit of work tag. This error is likely caused by a bug in " +
+            "React. Please file an issue."
+        );
+    }
+  }
+
+  return {
+    completeWork: completeWork
+  };
+};
+
+function createCapturedValue(value, source) {
+  // If the value is an error, call this function immediately after it is thrown
+  // so the stack is accurate.
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
+
+var ReactFiberUnwindWork = function(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  isAlreadyFailedLegacyErrorBoundary
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+
+  function throwException(returnFiber, sourceFiber, rawValue) {
+    // The source fiber did not complete.
+    sourceFiber.effectTag |= Incomplete;
+    // Its effect list is no longer valid.
+    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+
+    var value = createCapturedValue(rawValue, sourceFiber);
+
+    var workInProgress = returnFiber;
+    do {
+      switch (workInProgress.tag) {
+        case HostRoot: {
+          // Uncaught error
+          var errorInfo = value;
+          ensureUpdateQueues(workInProgress);
+          var updateQueue = workInProgress.updateQueue;
+          updateQueue.capturedValues = [errorInfo];
+          workInProgress.effectTag |= ShouldCapture;
+          return;
+        }
+        case ClassComponent:
+          // Capture and retry
+          var ctor = workInProgress.type;
+          var _instance = workInProgress.stateNode;
+          if (
+            (workInProgress.effectTag & DidCapture) === NoEffect &&
+            ((typeof ctor.getDerivedStateFromCatch === "function" &&
+              enableGetDerivedStateFromCatch) ||
+              (_instance !== null &&
+                typeof _instance.componentDidCatch === "function" &&
+                !isAlreadyFailedLegacyErrorBoundary(_instance)))
+          ) {
+            ensureUpdateQueues(workInProgress);
+            var _updateQueue = workInProgress.updateQueue;
+            var capturedValues = _updateQueue.capturedValues;
+            if (capturedValues === null) {
+              _updateQueue.capturedValues = [value];
+            } else {
+              capturedValues.push(value);
+            }
+            workInProgress.effectTag |= ShouldCapture;
+            return;
+          }
+          break;
+        default:
+          break;
+      }
+      workInProgress = workInProgress["return"];
+    } while (workInProgress !== null);
+  }
+
+  function unwindWork(workInProgress) {
+    switch (workInProgress.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(workInProgress);
+        var effectTag = workInProgress.effectTag;
+        if (effectTag & ShouldCapture) {
+          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var _effectTag = workInProgress.effectTag;
+        if (_effectTag & ShouldCapture) {
+          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        return null;
+      }
+      case HostPortal:
+        popHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        popProvider(workInProgress);
+        return null;
+      default:
+        return null;
+    }
+  }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      default:
+        break;
+    }
+  }
+
+  return {
+    throwException: throwException,
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork
+  };
+};
+
+// Module provided by RN:
+/**
+ * Intercept lifecycle errors and ensure they are shown with the correct stack
+ * trace within the native redbox component.
+ */
+function showErrorDialog(capturedError) {
+  var componentStack = capturedError.componentStack,
+    error = capturedError.error;
+
+  var errorToHandle = void 0;
+
+  // Typically Errors are thrown but eg strings or null can be thrown as well.
+  if (error instanceof Error) {
+    var message = error.message,
+      name = error.name;
+
+    var summary = message ? name + ": " + message : name;
+
+    errorToHandle = error;
+
+    try {
+      errorToHandle.message =
+        summary + "\n\nThis error is located at:" + componentStack;
+    } catch (e) {}
+  } else if (typeof error === "string") {
+    errorToHandle = new Error(
+      error + "\n\nThis error is located at:" + componentStack
+    );
+  } else {
+    errorToHandle = new Error("Unspecified error at:" + componentStack);
+  }
+
+  ExceptionsManager.handleException(errorToHandle, false);
+
+  // Return false here to prevent ReactFiberErrorLogger default behavior of
+  // logging error details to console.error. Calls to console.error are
+  // automatically routed to the native redbox controller, which we've already
+  // done above by calling ExceptionsManager.
+  return false;
+}
+
+function logCapturedError(capturedError) {
+  var logError = showErrorDialog(capturedError);
+
+  // Allow injected showErrorDialog() to prevent default console.error logging.
+  // This enables renderers like ReactNative to better manage redbox behavior.
+  if (logError === false) {
+    return;
+  }
+
+  var error = capturedError.error;
+  var suppressLogging = error && error.suppressReactErrorLogging;
+  if (suppressLogging) {
+    return;
+  }
+
+  {
+    var componentName = capturedError.componentName,
+      componentStack = capturedError.componentStack,
+      errorBoundaryName = capturedError.errorBoundaryName,
+      errorBoundaryFound = capturedError.errorBoundaryFound,
+      willRetry = capturedError.willRetry;
+
+    var componentNameMessage = componentName
+      ? "The above error occurred in the <" + componentName + "> component:"
+      : "The above error occurred in one of your React components:";
+
+    var errorBoundaryMessage = void 0;
+    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
+    if (errorBoundaryFound && errorBoundaryName) {
+      if (willRetry) {
+        errorBoundaryMessage =
+          "React will try to recreate this component tree from scratch " +
+          ("using the error boundary you provided, " + errorBoundaryName + ".");
+      } else {
+        errorBoundaryMessage =
+          "This error was initially handled by the error boundary " +
+          errorBoundaryName +
+          ".\n" +
+          "Recreating the tree from scratch failed so React will unmount the tree.";
+      }
+    } else {
+      errorBoundaryMessage =
+        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
+        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
+    }
+    var combinedMessage =
+      "" +
+      componentNameMessage +
+      componentStack +
+      "\n\n" +
+      ("" + errorBoundaryMessage);
+
+    // In development, we provide our own message with just the component stack.
+    // We don't include the original error message and JS stack because the browser
+    // has already printed it. Even if the application swallows the error, it is still
+    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
+    console.error(combinedMessage);
+  }
+}
+
+var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
+var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
+
+var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
+{
+  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
+}
+
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source;
+  var stack = errorInfo.stack;
+  if (stack === null) {
+    stack = getStackAddendumByWorkInProgressFiber(source);
+  }
+
+  var capturedError = {
+    componentName: source !== null ? getComponentName(source) : null,
+    componentStack: stack !== null ? stack : "",
+    error: errorInfo.value,
+    errorBoundary: null,
+    errorBoundaryName: null,
+    errorBoundaryFound: false,
+    willRetry: false
+  };
+
+  if (boundary !== null && boundary.tag === ClassComponent) {
+    capturedError.errorBoundary = boundary.stateNode;
+    capturedError.errorBoundaryName = getComponentName(boundary);
+    capturedError.errorBoundaryFound = true;
+    capturedError.willRetry = true;
+  }
+
+  try {
+    logCapturedError(capturedError);
+  } catch (e) {
+    // Prevent cycle if logCapturedError() throws.
+    // A cycle may still occur if logCapturedError renders a component that throws.
+    var suppressLogging = e && e.suppressReactErrorLogging;
+    if (!suppressLogging) {
+      console.error(e);
+    }
+  }
+}
+
+var ReactFiberCommitWork = function(
+  config,
+  captureError,
+  scheduleWork,
+  computeExpirationForFiber,
+  markLegacyErrorBoundaryAsFailed,
+  recalculateCurrentTime
+) {
+  var getPublicInstance = config.getPublicInstance,
+    mutation = config.mutation,
+    persistence = config.persistence;
+
+  var callComponentWillUnmountWithTimer = function(current, instance) {
+    startPhaseTimer(current, "componentWillUnmount");
+    instance.props = current.memoizedProps;
+    instance.state = current.memoizedState;
+    instance.componentWillUnmount();
+    stopPhaseTimer();
+  };
+
+  // Capture errors so they don't interrupt unmounting.
+  function safelyCallComponentWillUnmount(current, instance) {
+    {
+      invokeGuardedCallback$3(
+        null,
+        callComponentWillUnmountWithTimer,
+        null,
+        current,
+        instance
+      );
+      if (hasCaughtError$1()) {
+        var unmountError = clearCaughtError$1();
+        captureError(current, unmountError);
+      }
+    }
+  }
+
+  function safelyDetachRef(current) {
+    var ref = current.ref;
+    if (ref !== null) {
+      if (typeof ref === "function") {
+        {
+          invokeGuardedCallback$3(null, ref, null, null);
+          if (hasCaughtError$1()) {
+            var refError = clearCaughtError$1();
+            captureError(current, refError);
+          }
+        }
+      } else {
+        ref.current = null;
+      }
+    }
+  }
+
+  function commitBeforeMutationLifeCycles(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        if (finishedWork.effectTag & Snapshot) {
+          if (current !== null) {
+            var prevProps = current.memoizedProps;
+            var prevState = current.memoizedState;
+            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
+            var _instance = finishedWork.stateNode;
+            _instance.props = finishedWork.memoizedProps;
+            _instance.state = finishedWork.memoizedState;
+            var snapshot = _instance.getSnapshotBeforeUpdate(
+              prevProps,
+              prevState
+            );
+            {
+              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
+              if (
+                snapshot === undefined &&
+                !didWarnSet.has(finishedWork.type)
+              ) {
+                didWarnSet.add(finishedWork.type);
+                warning(
+                  false,
+                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
+                    "must be returned. You have returned undefined.",
+                  getComponentName(finishedWork)
+                );
+              }
+            }
+            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+            stopPhaseTimer();
+          }
+        }
+        return;
+      }
+      case HostRoot:
+      case HostComponent:
+      case HostText:
+      case HostPortal:
+        // Nothing to do for these component types
+        return;
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
+  function commitLifeCycles(
+    finishedRoot,
+    current,
+    finishedWork,
+    currentTime,
+    committedExpirationTime
+  ) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        var _instance2 = finishedWork.stateNode;
+        if (finishedWork.effectTag & Update) {
+          if (current === null) {
+            startPhaseTimer(finishedWork, "componentDidMount");
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidMount();
+            stopPhaseTimer();
+          } else {
+            var prevProps = current.memoizedProps;
+            var prevState = current.memoizedState;
+            startPhaseTimer(finishedWork, "componentDidUpdate");
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidUpdate(
+              prevProps,
+              prevState,
+              _instance2.__reactInternalSnapshotBeforeUpdate
+            );
+            stopPhaseTimer();
+          }
+        }
+        var updateQueue = finishedWork.updateQueue;
+        if (updateQueue !== null) {
+          commitCallbacks(updateQueue, _instance2);
+        }
+        return;
+      }
+      case HostRoot: {
+        var _updateQueue = finishedWork.updateQueue;
+        if (_updateQueue !== null) {
+          var _instance3 = null;
+          if (finishedWork.child !== null) {
+            switch (finishedWork.child.tag) {
+              case HostComponent:
+                _instance3 = getPublicInstance(finishedWork.child.stateNode);
+                break;
+              case ClassComponent:
+                _instance3 = finishedWork.child.stateNode;
+                break;
+            }
+          }
+          commitCallbacks(_updateQueue, _instance3);
+        }
+        return;
+      }
+      case HostComponent: {
+        var _instance4 = finishedWork.stateNode;
+
+        // Renderers may schedule work to be done after host components are mounted
+        // (eg DOM renderer may schedule auto-focus for inputs and form controls).
+        // These effects should only be committed when components are first mounted,
+        // aka when there is no current/alternate.
+        if (current === null && finishedWork.effectTag & Update) {
+          var type = finishedWork.type;
+          var props = finishedWork.memoizedProps;
+          commitMount(_instance4, type, props, finishedWork);
+        }
+
+        return;
+      }
+      case HostText: {
+        // We have no life-cycles associated with text.
+        return;
+      }
+      case HostPortal: {
+        // We have no life-cycles associated with portals.
+        return;
+      }
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
+  function commitErrorLogging(finishedWork, onUncaughtError) {
+    switch (finishedWork.tag) {
+      case ClassComponent:
+        {
+          var ctor = finishedWork.type;
+          var _instance5 = finishedWork.stateNode;
+          var updateQueue = finishedWork.updateQueue;
+          invariant(
+            updateQueue !== null && updateQueue.capturedValues !== null,
+            "An error logging effect should not have been scheduled if no errors " +
+              "were captured. This error is likely caused by a bug in React. " +
+              "Please file an issue."
+          );
+          var capturedErrors = updateQueue.capturedValues;
+          updateQueue.capturedValues = null;
+
+          if (typeof ctor.getDerivedStateFromCatch !== "function") {
+            // To preserve the preexisting retry behavior of error boundaries,
+            // we keep track of which ones already failed during this batch.
+            // This gets reset before we yield back to the browser.
+            // TODO: Warn in strict mode if getDerivedStateFromCatch is
+            // not defined.
+            markLegacyErrorBoundaryAsFailed(_instance5);
+          }
+
+          _instance5.props = finishedWork.memoizedProps;
+          _instance5.state = finishedWork.memoizedState;
+          for (var i = 0; i < capturedErrors.length; i++) {
+            var errorInfo = capturedErrors[i];
+            var _error = errorInfo.value;
+            var stack = errorInfo.stack;
+            logError(finishedWork, errorInfo);
+            _instance5.componentDidCatch(_error, {
+              componentStack: stack !== null ? stack : ""
+            });
+          }
+        }
+        break;
+      case HostRoot: {
+        var _updateQueue2 = finishedWork.updateQueue;
+        invariant(
+          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
+          "An error logging effect should not have been scheduled if no errors " +
+            "were captured. This error is likely caused by a bug in React. " +
+            "Please file an issue."
+        );
+        var _capturedErrors = _updateQueue2.capturedValues;
+        _updateQueue2.capturedValues = null;
+        for (var _i = 0; _i < _capturedErrors.length; _i++) {
+          var _errorInfo = _capturedErrors[_i];
+          logError(finishedWork, _errorInfo);
+          onUncaughtError(_errorInfo.value);
+        }
+        break;
+      }
+      default:
+        invariant(
+          false,
+          "This unit of work tag cannot capture errors.  This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
+
+  function commitAttachRef(finishedWork) {
+    var ref = finishedWork.ref;
+    if (ref !== null) {
+      var _instance6 = finishedWork.stateNode;
+      var instanceToUse = void 0;
+      switch (finishedWork.tag) {
+        case HostComponent:
+          instanceToUse = getPublicInstance(_instance6);
+          break;
+        default:
+          instanceToUse = _instance6;
+      }
+      if (typeof ref === "function") {
+        ref(instanceToUse);
+      } else {
+        {
+          if (!ref.hasOwnProperty("current")) {
+            warning(
+              false,
+              "Unexpected ref object provided for %s. " +
+                "Use either a ref-setter function or React.createRef().%s",
+              getComponentName(finishedWork),
+              getStackAddendumByWorkInProgressFiber(finishedWork)
+            );
+          }
+        }
+
+        ref.current = instanceToUse;
+      }
+    }
+  }
+
+  function commitDetachRef(current) {
+    var currentRef = current.ref;
+    if (currentRef !== null) {
+      if (typeof currentRef === "function") {
+        currentRef(null);
+      } else {
+        currentRef.current = null;
+      }
+    }
+  }
+
+  // User-originating errors (lifecycles and refs) should not interrupt
+  // deletion, so don't let them throw. Host-originating errors should
+  // interrupt deletion, so it's okay
+  function commitUnmount(current) {
+    if (typeof onCommitUnmount === "function") {
+      onCommitUnmount(current);
+    }
+
+    switch (current.tag) {
+      case ClassComponent: {
+        safelyDetachRef(current);
+        var _instance7 = current.stateNode;
+        if (typeof _instance7.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance7);
+        }
+        return;
+      }
+      case HostComponent: {
+        safelyDetachRef(current);
+        return;
+      }
+      case CallComponent: {
+        commitNestedUnmounts(current.stateNode);
+        return;
+      }
+      case HostPortal: {
+        // TODO: this is recursive.
+        // We are also not using this parent because
+        // the portal will get pushed immediately.
+        if (enableMutatingReconciler && mutation) {
+          unmountHostComponents(current);
+        } else if (enablePersistentReconciler && persistence) {
+          emptyPortalContainer(current);
+        }
+        return;
+      }
+    }
+  }
+
+  function commitNestedUnmounts(root) {
+    // While we're inside a removed host node we don't want to call
+    // removeChild on the inner nodes because they're removed by the top
+    // call anyway. We also want to call componentWillUnmount on all
+    // composites before this host node is removed from the tree. Therefore
+    var node = root;
+    while (true) {
+      commitUnmount(node);
+      // Visit children because they may contain more composite or host nodes.
+      // Skip portals because commitUnmount() currently visits them recursively.
+      if (
+        node.child !== null &&
+        // If we use mutation we drill down into portals using commitUnmount above.
+        // If we don't use mutation we drill down into portals here instead.
+        (!mutation || node.tag !== HostPortal)
+      ) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      if (node === root) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === root) {
+          return;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  function detachFiber(current) {
+    // Cut off the return pointers to disconnect it from the tree. Ideally, we
+    // should clear the child pointer of the parent alternate to let this
+    // get GC:ed but we don't know which for sure which parent is the current
+    // one so we'll settle for GC:ing the subtree of this child. This child
+    // itself will be GC:ed when the parent updates the next time.
+    current["return"] = null;
+    current.child = null;
+    if (current.alternate) {
+      current.alternate.child = null;
+      current.alternate["return"] = null;
+    }
+  }
+
+  var emptyPortalContainer = void 0;
+
+  if (!mutation) {
+    var commitContainer = void 0;
+    if (persistence) {
+      var replaceContainerChildren = persistence.replaceContainerChildren,
+        createContainerChildSet = persistence.createContainerChildSet;
+
+      emptyPortalContainer = function(current) {
+        var portal = current.stateNode;
+        var containerInfo = portal.containerInfo;
+
+        var emptyChildSet = createContainerChildSet(containerInfo);
+        replaceContainerChildren(containerInfo, emptyChildSet);
+      };
+      commitContainer = function(finishedWork) {
+        switch (finishedWork.tag) {
+          case ClassComponent: {
+            return;
+          }
+          case HostComponent: {
+            return;
+          }
+          case HostText: {
+            return;
+          }
+          case HostRoot:
+          case HostPortal: {
+            var portalOrRoot = finishedWork.stateNode;
+            var containerInfo = portalOrRoot.containerInfo,
+              _pendingChildren = portalOrRoot.pendingChildren;
+
+            replaceContainerChildren(containerInfo, _pendingChildren);
+            return;
+          }
+          default: {
+            invariant(
+              false,
+              "This unit of work tag should not have side-effects. This error is " +
+                "likely caused by a bug in React. Please file an issue."
+            );
+          }
+        }
+      };
+    } else {
+      commitContainer = function(finishedWork) {
+        // Noop
+      };
+    }
+    if (enablePersistentReconciler || enableNoopReconciler) {
+      return {
+        commitResetTextContent: function(finishedWork) {},
+        commitPlacement: function(finishedWork) {},
+        commitDeletion: function(current) {
+          // Detach refs and call componentWillUnmount() on the whole subtree.
+          commitNestedUnmounts(current);
+          detachFiber(current);
+        },
+        commitWork: function(current, finishedWork) {
+          commitContainer(finishedWork);
+        },
+
+        commitLifeCycles: commitLifeCycles,
+        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+        commitErrorLogging: commitErrorLogging,
+        commitAttachRef: commitAttachRef,
+        commitDetachRef: commitDetachRef
+      };
+    } else if (persistence) {
+      invariant(false, "Persistent reconciler is disabled.");
+    } else {
+      invariant(false, "Noop reconciler is disabled.");
+    }
+  }
+  var commitMount = mutation.commitMount,
+    commitUpdate = mutation.commitUpdate,
+    resetTextContent = mutation.resetTextContent,
+    commitTextUpdate = mutation.commitTextUpdate,
+    appendChild = mutation.appendChild,
+    appendChildToContainer = mutation.appendChildToContainer,
+    insertBefore = mutation.insertBefore,
+    insertInContainerBefore = mutation.insertInContainerBefore,
+    removeChild = mutation.removeChild,
+    removeChildFromContainer = mutation.removeChildFromContainer;
+
+  function getHostParentFiber(fiber) {
+    var parent = fiber["return"];
+    while (parent !== null) {
+      if (isHostParent(parent)) {
+        return parent;
+      }
+      parent = parent["return"];
+    }
+    invariant(
+      false,
+      "Expected to find a host parent. This error is likely caused by a bug " +
+        "in React. Please file an issue."
+    );
+  }
+
+  function isHostParent(fiber) {
+    return (
+      fiber.tag === HostComponent ||
+      fiber.tag === HostRoot ||
+      fiber.tag === HostPortal
+    );
+  }
+
+  function getHostSibling(fiber) {
+    // We're going to search forward into the tree until we find a sibling host
+    // node. Unfortunately, if multiple insertions are done in a row we have to
+    // search past them. This leads to exponential search for the next sibling.
+    var node = fiber;
+    siblings: while (true) {
+      // If we didn't find anything, let's try the next sibling.
+      while (node.sibling === null) {
+        if (node["return"] === null || isHostParent(node["return"])) {
+          // If we pop out of the root or hit the parent the fiber we are the
+          // last sibling.
+          return null;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+      while (node.tag !== HostComponent && node.tag !== HostText) {
+        // If it is not host node and, we might have a host node inside it.
+        // Try to search down until we find one.
+        if (node.effectTag & Placement) {
+          // If we don't have a child, try the siblings instead.
+          continue siblings;
+        }
+        // If we don't have a child, try the siblings instead.
+        // We also skip portals because they are not part of this host tree.
+        if (node.child === null || node.tag === HostPortal) {
+          continue siblings;
+        } else {
+          node.child["return"] = node;
+          node = node.child;
+        }
+      }
+      // Check if this host node is stable or about to be placed.
+      if (!(node.effectTag & Placement)) {
+        // Found it!
+        return node.stateNode;
+      }
+    }
+  }
+
+  function commitPlacement(finishedWork) {
+    // Recursively insert all host nodes into the parent.
+    var parentFiber = getHostParentFiber(finishedWork);
+    var parent = void 0;
+    var isContainer = void 0;
+    switch (parentFiber.tag) {
+      case HostComponent:
+        parent = parentFiber.stateNode;
+        isContainer = false;
+        break;
+      case HostRoot:
+        parent = parentFiber.stateNode.containerInfo;
+        isContainer = true;
+        break;
+      case HostPortal:
+        parent = parentFiber.stateNode.containerInfo;
+        isContainer = true;
+        break;
+      default:
+        invariant(
+          false,
+          "Invalid host parent fiber. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+    }
+    if (parentFiber.effectTag & ContentReset) {
+      // Reset the text content of the parent before doing any insertions
+      resetTextContent(parent);
+      // Clear ContentReset from the effect tag
+      parentFiber.effectTag &= ~ContentReset;
+    }
+
+    var before = getHostSibling(finishedWork);
+    // We only have the top Fiber that was inserted but we need recurse down its
+    // children to find all the terminal nodes.
+    var node = finishedWork;
+    while (true) {
+      if (node.tag === HostComponent || node.tag === HostText) {
+        if (before) {
+          if (isContainer) {
+            insertInContainerBefore(parent, node.stateNode, before);
+          } else {
+            insertBefore(parent, node.stateNode, before);
+          }
+        } else {
+          if (isContainer) {
+            appendChildToContainer(parent, node.stateNode);
+          } else {
+            appendChild(parent, node.stateNode);
+          }
+        }
+      } else if (node.tag === HostPortal) {
+        // If the insertion itself is a portal, then we don't want to traverse
+        // down its children. Instead, we'll get insertions from each child in
+        // the portal directly.
+      } else if (node.child !== null) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      if (node === finishedWork) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === finishedWork) {
+          return;
+        }
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  function unmountHostComponents(current) {
+    // We only have the top Fiber that was inserted but we need recurse down its
+    var node = current;
+
+    // Each iteration, currentParent is populated with node's host parent if not
+    // currentParentIsValid.
+    var currentParentIsValid = false;
+    var currentParent = void 0;
+    var currentParentIsContainer = void 0;
+
+    while (true) {
+      if (!currentParentIsValid) {
+        var parent = node["return"];
+        findParent: while (true) {
+          invariant(
+            parent !== null,
+            "Expected to find a host parent. This error is likely caused by " +
+              "a bug in React. Please file an issue."
+          );
+          switch (parent.tag) {
+            case HostComponent:
+              currentParent = parent.stateNode;
+              currentParentIsContainer = false;
+              break findParent;
+            case HostRoot:
+              currentParent = parent.stateNode.containerInfo;
+              currentParentIsContainer = true;
+              break findParent;
+            case HostPortal:
+              currentParent = parent.stateNode.containerInfo;
+              currentParentIsContainer = true;
+              break findParent;
+          }
+          parent = parent["return"];
+        }
+        currentParentIsValid = true;
+      }
+
+      if (node.tag === HostComponent || node.tag === HostText) {
+        commitNestedUnmounts(node);
+        // After all the children have unmounted, it is now safe to remove the
+        // node from the tree.
+        if (currentParentIsContainer) {
+          removeChildFromContainer(currentParent, node.stateNode);
+        } else {
+          removeChild(currentParent, node.stateNode);
+        }
+        // Don't visit children because we already visited them.
+      } else if (node.tag === HostPortal) {
+        // When we go into a portal, it becomes the parent to remove from.
+        // We will reassign it back when we pop the portal on the way up.
+        currentParent = node.stateNode.containerInfo;
+        // Visit children because portals might contain host components.
+        if (node.child !== null) {
+          node.child["return"] = node;
+          node = node.child;
+          continue;
+        }
+      } else {
+        commitUnmount(node);
+        // Visit children because we may find more host components below.
+        if (node.child !== null) {
+          node.child["return"] = node;
+          node = node.child;
+          continue;
+        }
+      }
+      if (node === current) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node["return"] === null || node["return"] === current) {
+          return;
+        }
+        node = node["return"];
+        if (node.tag === HostPortal) {
+          // When we go out of the portal, we need to restore the parent.
+          // Since we don't keep a stack of them, we will search for it.
+          currentParentIsValid = false;
+        }
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+
+  function commitDeletion(current) {
+    // Recursively delete all host nodes from the parent.
+    // Detach refs and call componentWillUnmount() on the whole subtree.
+    unmountHostComponents(current);
+    detachFiber(current);
+  }
+
+  function commitWork(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        return;
+      }
+      case HostComponent: {
+        var _instance8 = finishedWork.stateNode;
+        if (_instance8 != null) {
+          // Commit the work prepared earlier.
+          var newProps = finishedWork.memoizedProps;
+          // For hydration we reuse the update path but we treat the oldProps
+          // as the newProps. The updatePayload will contain the real change in
+          // this case.
+          var oldProps = current !== null ? current.memoizedProps : newProps;
+          var type = finishedWork.type;
+          // TODO: Type the updateQueue to be specific to host components.
+          var updatePayload = finishedWork.updateQueue;
+          finishedWork.updateQueue = null;
+          if (updatePayload !== null) {
+            commitUpdate(
+              _instance8,
+              updatePayload,
+              type,
+              oldProps,
+              newProps,
+              finishedWork
+            );
+          }
+        }
+        return;
+      }
+      case HostText: {
+        invariant(
+          finishedWork.stateNode !== null,
+          "This should have a text node initialized. This error is likely " +
+            "caused by a bug in React. Please file an issue."
+        );
+        var textInstance = finishedWork.stateNode;
+        var newText = finishedWork.memoizedProps;
+        // For hydration we reuse the update path but we treat the oldProps
+        // as the newProps. The updatePayload will contain the real change in
+        // this case.
+        var oldText = current !== null ? current.memoizedProps : newText;
+        commitTextUpdate(textInstance, oldText, newText);
+        return;
+      }
+      case HostRoot: {
+        return;
+      }
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
+  function commitResetTextContent(current) {
+    resetTextContent(current.stateNode);
+  }
+
+  if (enableMutatingReconciler) {
+    return {
+      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+      commitResetTextContent: commitResetTextContent,
+      commitPlacement: commitPlacement,
+      commitDeletion: commitDeletion,
+      commitWork: commitWork,
+      commitLifeCycles: commitLifeCycles,
+      commitErrorLogging: commitErrorLogging,
+      commitAttachRef: commitAttachRef,
+      commitDetachRef: commitDetachRef
+    };
+  } else {
+    invariant(false, "Mutating reconciler is disabled.");
+  }
+};
+
+var NO_CONTEXT = {};
+
+var ReactFiberHostContext = function(config, stack) {
+  var getChildHostContext = config.getChildHostContext,
+    getRootHostContext = config.getRootHostContext;
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  var contextStackCursor = createCursor(NO_CONTEXT);
+  var contextFiberStackCursor = createCursor(NO_CONTEXT);
+  var rootInstanceStackCursor = createCursor(NO_CONTEXT);
+
+  function requiredContext(c) {
+    invariant(
+      c !== NO_CONTEXT,
+      "Expected host context to exist. This error is likely caused by a bug " +
+        "in React. Please file an issue."
+    );
+    return c;
+  }
+
+  function getRootHostContainer() {
+    var rootInstance = requiredContext(rootInstanceStackCursor.current);
+    return rootInstance;
+  }
+
+  function pushHostContainer(fiber, nextRootInstance) {
+    // Push current root instance onto the stack;
+    // This allows us to reset root when portals are popped.
+    push(rootInstanceStackCursor, nextRootInstance, fiber);
+    // Track the context and the Fiber that provided it.
+    // This enables us to pop only Fibers that provide unique contexts.
+    push(contextFiberStackCursor, fiber, fiber);
+
+    // Finally, we need to push the host context to the stack.
+    // However, we can't just call getRootHostContext() and push it because
+    // we'd have a different number of entries on the stack depending on
+    // whether getRootHostContext() throws somewhere in renderer code or not.
+    // So we push an empty value first. This lets us safely unwind on errors.
+    push(contextStackCursor, NO_CONTEXT, fiber);
+    var nextRootContext = getRootHostContext(nextRootInstance);
+    // Now that we know this function doesn't throw, replace it.
+    pop(contextStackCursor, fiber);
+    push(contextStackCursor, nextRootContext, fiber);
+  }
+
+  function popHostContainer(fiber) {
+    pop(contextStackCursor, fiber);
+    pop(contextFiberStackCursor, fiber);
+    pop(rootInstanceStackCursor, fiber);
+  }
+
+  function getHostContext() {
+    var context = requiredContext(contextStackCursor.current);
+    return context;
+  }
+
+  function pushHostContext(fiber) {
+    var rootInstance = requiredContext(rootInstanceStackCursor.current);
+    var context = requiredContext(contextStackCursor.current);
+    var nextContext = getChildHostContext(context, fiber.type, rootInstance);
+
+    // Don't push this Fiber's context unless it's unique.
+    if (context === nextContext) {
+      return;
+    }
+
+    // Track the context and the Fiber that provided it.
+    // This enables us to pop only Fibers that provide unique contexts.
+    push(contextFiberStackCursor, fiber, fiber);
+    push(contextStackCursor, nextContext, fiber);
+  }
+
+  function popHostContext(fiber) {
+    // Do not pop unless this Fiber provided the current context.
+    // pushHostContext() only pushes Fibers that provide unique contexts.
+    if (contextFiberStackCursor.current !== fiber) {
+      return;
+    }
+
+    pop(contextStackCursor, fiber);
+    pop(contextFiberStackCursor, fiber);
+  }
+
+  return {
+    getHostContext: getHostContext,
+    getRootHostContainer: getRootHostContainer,
+    popHostContainer: popHostContainer,
+    popHostContext: popHostContext,
+    pushHostContainer: pushHostContainer,
+    pushHostContext: pushHostContext
+  };
+};
+
+var ReactFiberHydrationContext = function(config) {
+  var shouldSetTextContent = config.shouldSetTextContent,
+    hydration = config.hydration;
+
+  // If this doesn't have hydration mode.
+
+  if (!hydration) {
+    return {
+      enterHydrationState: function() {
+        return false;
+      },
+      resetHydrationState: function() {},
+      tryToClaimNextHydratableInstance: function() {},
+      prepareToHydrateHostInstance: function() {
+        invariant(
+          false,
+          "Expected prepareToHydrateHostInstance() to never be called. " +
+            "This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      prepareToHydrateHostTextInstance: function() {
+        invariant(
+          false,
+          "Expected prepareToHydrateHostTextInstance() to never be called. " +
+            "This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      popHydrationState: function(fiber) {
+        return false;
+      }
+    };
+  }
+
+  var canHydrateInstance = hydration.canHydrateInstance,
+    canHydrateTextInstance = hydration.canHydrateTextInstance,
+    getNextHydratableSibling = hydration.getNextHydratableSibling,
+    getFirstHydratableChild = hydration.getFirstHydratableChild,
+    hydrateInstance = hydration.hydrateInstance,
+    hydrateTextInstance = hydration.hydrateTextInstance,
+    didNotMatchHydratedContainerTextInstance =
+      hydration.didNotMatchHydratedContainerTextInstance,
+    didNotMatchHydratedTextInstance = hydration.didNotMatchHydratedTextInstance,
+    didNotHydrateContainerInstance = hydration.didNotHydrateContainerInstance,
+    didNotHydrateInstance = hydration.didNotHydrateInstance,
+    didNotFindHydratableContainerInstance =
+      hydration.didNotFindHydratableContainerInstance,
+    didNotFindHydratableContainerTextInstance =
+      hydration.didNotFindHydratableContainerTextInstance,
+    didNotFindHydratableInstance = hydration.didNotFindHydratableInstance,
+    didNotFindHydratableTextInstance =
+      hydration.didNotFindHydratableTextInstance;
+
+  // The deepest Fiber on the stack involved in a hydration context.
+  // This may have been an insertion or a hydration.
+
+  var hydrationParentFiber = null;
+  var nextHydratableInstance = null;
+  var isHydrating = false;
+
+  function enterHydrationState(fiber) {
+    var parentInstance = fiber.stateNode.containerInfo;
+    nextHydratableInstance = getFirstHydratableChild(parentInstance);
+    hydrationParentFiber = fiber;
+    isHydrating = true;
+    return true;
+  }
+
+  function deleteHydratableInstance(returnFiber, instance) {
+    {
+      switch (returnFiber.tag) {
+        case HostRoot:
+          didNotHydrateContainerInstance(
+            returnFiber.stateNode.containerInfo,
+            instance
+          );
+          break;
+        case HostComponent:
+          didNotHydrateInstance(
+            returnFiber.type,
+            returnFiber.memoizedProps,
+            returnFiber.stateNode,
+            instance
+          );
+          break;
+      }
+    }
+
+    var childToDelete = createFiberFromHostInstanceForDeletion();
+    childToDelete.stateNode = instance;
+    childToDelete["return"] = returnFiber;
+    childToDelete.effectTag = Deletion;
+
+    // This might seem like it belongs on progressedFirstDeletion. However,
+    // these children are not part of the reconciliation list of children.
+    // Even if we abort and rereconcile the children, that will try to hydrate
+    // again and the nodes are still in the host tree so these will be
+    // recreated.
+    if (returnFiber.lastEffect !== null) {
+      returnFiber.lastEffect.nextEffect = childToDelete;
+      returnFiber.lastEffect = childToDelete;
+    } else {
+      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+    }
+  }
+
+  function insertNonHydratedInstance(returnFiber, fiber) {
+    fiber.effectTag |= Placement;
+    {
+      switch (returnFiber.tag) {
+        case HostRoot: {
+          var parentContainer = returnFiber.stateNode.containerInfo;
+          switch (fiber.tag) {
+            case HostComponent:
+              var type = fiber.type;
+              var props = fiber.pendingProps;
+              didNotFindHydratableContainerInstance(
+                parentContainer,
+                type,
+                props
+              );
+              break;
+            case HostText:
+              var text = fiber.pendingProps;
+              didNotFindHydratableContainerTextInstance(parentContainer, text);
+              break;
+          }
+          break;
+        }
+        case HostComponent: {
+          var parentType = returnFiber.type;
+          var parentProps = returnFiber.memoizedProps;
+          var parentInstance = returnFiber.stateNode;
+          switch (fiber.tag) {
+            case HostComponent:
+              var _type = fiber.type;
+              var _props = fiber.pendingProps;
+              didNotFindHydratableInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                _type,
+                _props
+              );
+              break;
+            case HostText:
+              var _text = fiber.pendingProps;
+              didNotFindHydratableTextInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                _text
+              );
+              break;
+          }
+          break;
+        }
+        default:
+          return;
+      }
+    }
+  }
+
+  function tryHydrate(fiber, nextInstance) {
+    switch (fiber.tag) {
+      case HostComponent: {
+        var type = fiber.type;
+        var props = fiber.pendingProps;
+        var instance = canHydrateInstance(nextInstance, type, props);
+        if (instance !== null) {
+          fiber.stateNode = instance;
+          return true;
+        }
+        return false;
+      }
+      case HostText: {
+        var text = fiber.pendingProps;
+        var textInstance = canHydrateTextInstance(nextInstance, text);
+        if (textInstance !== null) {
+          fiber.stateNode = textInstance;
+          return true;
+        }
+        return false;
+      }
+      default:
+        return false;
+    }
+  }
+
+  function tryToClaimNextHydratableInstance(fiber) {
+    if (!isHydrating) {
+      return;
+    }
+    var nextInstance = nextHydratableInstance;
+    if (!nextInstance) {
+      // Nothing to hydrate. Make it an insertion.
+      insertNonHydratedInstance(hydrationParentFiber, fiber);
+      isHydrating = false;
+      hydrationParentFiber = fiber;
+      return;
+    }
+    if (!tryHydrate(fiber, nextInstance)) {
+      // If we can't hydrate this instance let's try the next one.
+      // We use this as a heuristic. It's based on intuition and not data so it
+      // might be flawed or unnecessary.
+      nextInstance = getNextHydratableSibling(nextInstance);
+      if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
+        // Nothing to hydrate. Make it an insertion.
+        insertNonHydratedInstance(hydrationParentFiber, fiber);
+        isHydrating = false;
+        hydrationParentFiber = fiber;
+        return;
+      }
+      // We matched the next one, we'll now assume that the first one was
+      // superfluous and we'll delete it. Since we can't eagerly delete it
+      // we'll have to schedule a deletion. To do that, this node needs a dummy
+      // fiber associated with it.
+      deleteHydratableInstance(hydrationParentFiber, nextHydratableInstance);
+    }
+    hydrationParentFiber = fiber;
+    nextHydratableInstance = getFirstHydratableChild(nextInstance);
+  }
+
+  function prepareToHydrateHostInstance(
+    fiber,
+    rootContainerInstance,
+    hostContext
+  ) {
+    var instance = fiber.stateNode;
+    var updatePayload = hydrateInstance(
+      instance,
+      fiber.type,
+      fiber.memoizedProps,
+      rootContainerInstance,
+      hostContext,
+      fiber
+    );
+    // TODO: Type this specific to this type of component.
+    fiber.updateQueue = updatePayload;
+    // If the update payload indicates that there is a change or if there
+    // is a new ref we mark this as an update.
+    if (updatePayload !== null) {
+      return true;
+    }
+    return false;
+  }
+
+  function prepareToHydrateHostTextInstance(fiber) {
+    var textInstance = fiber.stateNode;
+    var textContent = fiber.memoizedProps;
+    var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
+    {
+      if (shouldUpdate) {
+        // We assume that prepareToHydrateHostTextInstance is called in a context where the
+        // hydration parent is the parent host component of this host text.
+        var returnFiber = hydrationParentFiber;
+        if (returnFiber !== null) {
+          switch (returnFiber.tag) {
+            case HostRoot: {
+              var parentContainer = returnFiber.stateNode.containerInfo;
+              didNotMatchHydratedContainerTextInstance(
+                parentContainer,
+                textInstance,
+                textContent
+              );
+              break;
+            }
+            case HostComponent: {
+              var parentType = returnFiber.type;
+              var parentProps = returnFiber.memoizedProps;
+              var parentInstance = returnFiber.stateNode;
+              didNotMatchHydratedTextInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                textInstance,
+                textContent
+              );
+              break;
+            }
+          }
+        }
+      }
+    }
+    return shouldUpdate;
+  }
+
+  function popToNextHostParent(fiber) {
+    var parent = fiber["return"];
+    while (
+      parent !== null &&
+      parent.tag !== HostComponent &&
+      parent.tag !== HostRoot
+    ) {
+      parent = parent["return"];
+    }
+    hydrationParentFiber = parent;
+  }
+
+  function popHydrationState(fiber) {
+    if (fiber !== hydrationParentFiber) {
+      // We're deeper than the current hydration context, inside an inserted
+      // tree.
+      return false;
+    }
+    if (!isHydrating) {
+      // If we're not currently hydrating but we're in a hydration context, then
+      // we were an insertion and now need to pop up reenter hydration of our
+      // siblings.
+      popToNextHostParent(fiber);
+      isHydrating = true;
+      return false;
+    }
+
+    var type = fiber.type;
+
+    // If we have any remaining hydratable nodes, we need to delete them now.
+    // We only do this deeper than head and body since they tend to have random
+    // other nodes in them. We also ignore components with pure text content in
+    // side of them.
+    // TODO: Better heuristic.
+    if (
+      fiber.tag !== HostComponent ||
+      (type !== "head" &&
+        type !== "body" &&
+        !shouldSetTextContent(type, fiber.memoizedProps))
+    ) {
+      var nextInstance = nextHydratableInstance;
+      while (nextInstance) {
+        deleteHydratableInstance(fiber, nextInstance);
+        nextInstance = getNextHydratableSibling(nextInstance);
+      }
+    }
+
+    popToNextHostParent(fiber);
+    nextHydratableInstance = hydrationParentFiber
+      ? getNextHydratableSibling(fiber.stateNode)
+      : null;
+    return true;
+  }
+
+  function resetHydrationState() {
+    hydrationParentFiber = null;
+    nextHydratableInstance = null;
+    isHydrating = false;
+  }
+
+  return {
+    enterHydrationState: enterHydrationState,
+    resetHydrationState: resetHydrationState,
+    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
+    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
+    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
+    popHydrationState: popHydrationState
+  };
+};
+
+// This lets us hook into Fiber to debug what it's doing.
+// See https://github.com/facebook/react/pull/8033.
+// This is not part of the public API, not even for React DevTools.
+// You may only inject a debugTool if you work on React Fiber itself.
+var ReactFiberInstrumentation = {
+  debugTool: null
+};
+
+var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
+
+var warnedAboutMissingGetChildContext = void 0;
+
+{
+  warnedAboutMissingGetChildContext = {};
+}
+
+var ReactFiberLegacyContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  // A cursor to the current merged context object on the stack.
+
+  var contextStackCursor = createCursor(emptyObject);
+  // A cursor to a boolean indicating whether the context has changed.
+  var didPerformWorkStackCursor = createCursor(false);
+  // Keep track of the previous context object that was on the stack.
+  // We use this to get access to the parent context after we have already
+  // pushed the next context provider, and now need to merge their contexts.
+  var previousContext = emptyObject;
+
+  function getUnmaskedContext(workInProgress) {
+    var hasOwnContext = isContextProvider(workInProgress);
+    if (hasOwnContext) {
+      // If the fiber is a context provider itself, when we read its context
+      // we have already pushed its own child context on the stack. A context
+      // provider should not "see" its own child context. Therefore we read the
+      // previous (parent) context instead for a context provider.
+      return previousContext;
+    }
+    return contextStackCursor.current;
+  }
+
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    var instance = workInProgress.stateNode;
+    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
+
+  function getMaskedContext(workInProgress, unmaskedContext) {
+    var type = workInProgress.type;
+    var contextTypes = type.contextTypes;
+    if (!contextTypes) {
+      return emptyObject;
+    }
+
+    // Avoid recreating masked context unless unmasked context has changed.
+    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
+    // This may trigger infinite loops if componentWillReceiveProps calls setState.
+    var instance = workInProgress.stateNode;
+    if (
+      instance &&
+      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+    ) {
+      return instance.__reactInternalMemoizedMaskedChildContext;
+    }
+
+    var context = {};
+    for (var key in contextTypes) {
+      context[key] = unmaskedContext[key];
+    }
+
+    {
+      var name = getComponentName(workInProgress) || "Unknown";
+      checkPropTypes(
+        contextTypes,
+        context,
+        "context",
+        name,
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    // Context is created before the class component is instantiated so check for instance.
+    if (instance) {
+      cacheContext(workInProgress, unmaskedContext, context);
+    }
+
+    return context;
+  }
+
+  function hasContextChanged() {
+    return didPerformWorkStackCursor.current;
+  }
+
+  function isContextConsumer(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+  }
+
+  function isContextProvider(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+  }
+
+  function popContextProvider(fiber) {
+    if (!isContextProvider(fiber)) {
+      return;
+    }
+
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
+
+  function popTopLevelContextObject(fiber) {
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
+
+  function pushTopLevelContextObject(fiber, context, didChange) {
+    invariant(
+      contextStackCursor.cursor == null,
+      "Unexpected context found on stack. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    push(contextStackCursor, context, fiber);
+    push(didPerformWorkStackCursor, didChange, fiber);
+  }
+
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode;
+    var childContextTypes = fiber.type.childContextTypes;
+
+    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
+    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
+    if (typeof instance.getChildContext !== "function") {
+      {
+        var componentName = getComponentName(fiber) || "Unknown";
+
+        if (!warnedAboutMissingGetChildContext[componentName]) {
+          warnedAboutMissingGetChildContext[componentName] = true;
+          warning(
+            false,
+            "%s.childContextTypes is specified but there is no getChildContext() method " +
+              "on the instance. You can either define getChildContext() on %s or remove " +
+              "childContextTypes from it.",
+            componentName,
+            componentName
+          );
+        }
+      }
+      return parentContext;
+    }
+
+    var childContext = void 0;
+    {
+      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
+    }
+    startPhaseTimer(fiber, "getChildContext");
+    childContext = instance.getChildContext();
+    stopPhaseTimer();
+    {
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+    for (var contextKey in childContext) {
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    }
+    {
+      var name = getComponentName(fiber) || "Unknown";
+      checkPropTypes(
+        childContextTypes,
+        childContext,
+        "child context",
+        name,
+        // In practice, there is one case in which we won't get a stack. It's when
+        // somebody calls unstable_renderSubtreeIntoContainer() and we process
+        // context from the parent component instance. The stack will be missing
+        // because it's outside of the reconciliation, and so the pointer has not
+        // been set. This is rare and doesn't matter. We'll also remove that API.
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    return Object.assign({}, parentContext, childContext);
+  }
+
+  function pushContextProvider(workInProgress) {
+    if (!isContextProvider(workInProgress)) {
+      return false;
+    }
+
+    var instance = workInProgress.stateNode;
+    // We push the context as early as possible to ensure stack integrity.
+    // If the instance does not exist yet, we will push null at first,
+    // and replace it on the stack later when invalidating the context.
+    var memoizedMergedChildContext =
+      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+      emptyObject;
+
+    // Remember the parent context so we can merge with it later.
+    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
+    previousContext = contextStackCursor.current;
+    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
+    push(
+      didPerformWorkStackCursor,
+      didPerformWorkStackCursor.current,
+      workInProgress
+    );
+
+    return true;
+  }
+
+  function invalidateContextProvider(workInProgress, didChange) {
+    var instance = workInProgress.stateNode;
+    invariant(
+      instance,
+      "Expected to have an instance by this point. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    if (didChange) {
+      // Merge parent and own context.
+      // Skip this if we're not updating due to sCU.
+      // This avoids unnecessarily recomputing memoized values.
+      var mergedContext = processChildContext(workInProgress, previousContext);
+      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+
+      // Replace the old (or empty) context with the new one.
+      // It is important to unwind the context in the reverse order.
+      pop(didPerformWorkStackCursor, workInProgress);
+      pop(contextStackCursor, workInProgress);
+      // Now push the new context and mark that it has changed.
+      push(contextStackCursor, mergedContext, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    } else {
+      pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    }
+  }
+
+  function findCurrentUnmaskedContext(fiber) {
+    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
+    // makes sense elsewhere
+    invariant(
+      isFiberMounted(fiber) && fiber.tag === ClassComponent,
+      "Expected subtree parent to be a mounted class component. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    var node = fiber;
+    while (node.tag !== HostRoot) {
+      if (isContextProvider(node)) {
+        return node.stateNode.__reactInternalMemoizedMergedChildContext;
+      }
+      var parent = node["return"];
+      invariant(
+        parent,
+        "Found unexpected detached subtree parent. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
+      node = parent;
+    }
+    return node.stateNode.context;
+  }
+
+  return {
+    getUnmaskedContext: getUnmaskedContext,
+    cacheContext: cacheContext,
+    getMaskedContext: getMaskedContext,
+    hasContextChanged: hasContextChanged,
+    isContextConsumer: isContextConsumer,
+    isContextProvider: isContextProvider,
+    popContextProvider: popContextProvider,
+    popTopLevelContextObject: popTopLevelContextObject,
+    pushTopLevelContextObject: pushTopLevelContextObject,
+    processChildContext: processChildContext,
+    pushContextProvider: pushContextProvider,
+    invalidateContextProvider: invalidateContextProvider,
+    findCurrentUnmaskedContext: findCurrentUnmaskedContext
+  };
+};
+
+var ReactFiberNewContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  var providerCursor = createCursor(null);
+  var valueCursor = createCursor(null);
+  var changedBitsCursor = createCursor(0);
+
+  var rendererSigil = void 0;
+  {
+    // Use this to detect multiple renderers using the same context
+    rendererSigil = {};
+  }
+
+  function pushProvider(providerFiber) {
+    var context = providerFiber.type._context;
+
+    push(changedBitsCursor, context._changedBits, providerFiber);
+    push(valueCursor, context._currentValue, providerFiber);
+    push(providerCursor, providerFiber, providerFiber);
+
+    context._currentValue = providerFiber.pendingProps.value;
+    context._changedBits = providerFiber.stateNode;
+
+    {
+      !(
+        context._currentRenderer === null ||
+        context._currentRenderer === rendererSigil
+      )
+        ? warning(
+            false,
+            "Detected multiple renderers concurrently rendering the " +
+              "same context provider. This is currently unsupported."
+          )
+        : void 0;
+      context._currentRenderer = rendererSigil;
+    }
+  }
+
+  function popProvider(providerFiber) {
+    var changedBits = changedBitsCursor.current;
+    var currentValue = valueCursor.current;
+
+    pop(providerCursor, providerFiber);
+    pop(valueCursor, providerFiber);
+    pop(changedBitsCursor, providerFiber);
+
+    var context = providerFiber.type._context;
+    context._currentValue = currentValue;
+    context._changedBits = changedBits;
+  }
+
+  return {
+    pushProvider: pushProvider,
+    popProvider: popProvider
+  };
+};
+
+var ReactFiberStack = function() {
+  var valueStack = [];
+
+  var fiberStack = void 0;
+
+  {
+    fiberStack = [];
+  }
+
+  var index = -1;
+
+  function createCursor(defaultValue) {
+    return {
+      current: defaultValue
+    };
+  }
+
+  function isEmpty() {
+    return index === -1;
+  }
+
+  function pop(cursor, fiber) {
+    if (index < 0) {
+      {
+        warning(false, "Unexpected pop.");
+      }
+      return;
+    }
+
+    {
+      if (fiber !== fiberStack[index]) {
+        warning(false, "Unexpected Fiber popped.");
+      }
+    }
+
+    cursor.current = valueStack[index];
+
+    valueStack[index] = null;
+
+    {
+      fiberStack[index] = null;
+    }
+
+    index--;
+  }
+
+  function push(cursor, value, fiber) {
+    index++;
+
+    valueStack[index] = cursor.current;
+
+    {
+      fiberStack[index] = fiber;
+    }
+
+    cursor.current = value;
+  }
+
+  function checkThatStackIsEmpty() {
+    {
+      if (index !== -1) {
+        warning(
+          false,
+          "Expected an empty stack. Something was not reset properly."
+        );
+      }
+    }
+  }
+
+  function resetStackAfterFatalErrorInDev() {
+    {
+      index = -1;
+      valueStack.length = 0;
+      fiberStack.length = 0;
+    }
+  }
+
+  return {
+    createCursor: createCursor,
+    isEmpty: isEmpty,
+    pop: pop,
+    push: push,
+    checkThatStackIsEmpty: checkThatStackIsEmpty,
+    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
+  };
+};
+
+var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError = ReactErrorUtils.hasCaughtError;
+var clearCaughtError = ReactErrorUtils.clearCaughtError;
+
+var didWarnAboutStateTransition = void 0;
+var didWarnSetStateChildContext = void 0;
+var warnAboutUpdateOnUnmounted = void 0;
+var warnAboutInvalidUpdates = void 0;
+
+{
+  didWarnAboutStateTransition = false;
+  didWarnSetStateChildContext = false;
+  var didWarnStateUpdateForUnmountedComponent = {};
+
+  warnAboutUpdateOnUnmounted = function(fiber) {
+    // We show the whole stack but dedupe on the top component's name because
+    // the problematic code almost always lies inside that component.
+    var componentName = getComponentName(fiber) || "ReactClass";
+    if (didWarnStateUpdateForUnmountedComponent[componentName]) {
+      return;
+    }
+    warning(
+      false,
+      "Can't call setState (or forceUpdate) on an unmounted component. This " +
+        "is a no-op, but it indicates a memory leak in your application. To " +
+        "fix, cancel all subscriptions and asynchronous tasks in the " +
+        "componentWillUnmount method.%s",
+      getStackAddendumByWorkInProgressFiber(fiber)
+    );
+    didWarnStateUpdateForUnmountedComponent[componentName] = true;
+  };
+
+  warnAboutInvalidUpdates = function(instance) {
+    switch (ReactDebugCurrentFiber.phase) {
+      case "getChildContext":
+        if (didWarnSetStateChildContext) {
+          return;
+        }
+        warning(
+          false,
+          "setState(...): Cannot call setState() inside getChildContext()"
+        );
+        didWarnSetStateChildContext = true;
+        break;
+      case "render":
+        if (didWarnAboutStateTransition) {
+          return;
+        }
+        warning(
+          false,
+          "Cannot update during an existing state transition (such as within " +
+            "`render` or another component's constructor). Render methods should " +
+            "be a pure function of props and state; constructor side-effects are " +
+            "an anti-pattern, but can be moved to `componentWillMount`."
+        );
+        didWarnAboutStateTransition = true;
+        break;
+    }
+  };
+}
+
+var ReactFiberScheduler = function(config) {
+  var stack = ReactFiberStack();
+  var hostContext = ReactFiberHostContext(config, stack);
+  var legacyContext = ReactFiberLegacyContext(stack);
+  var newContext = ReactFiberNewContext(stack);
+  var popHostContext = hostContext.popHostContext,
+    popHostContainer = hostContext.popHostContainer;
+  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popLegacyContextProvider = legacyContext.popContextProvider;
+  var popProvider = newContext.popProvider;
+
+  var hydrationContext = ReactFiberHydrationContext(config);
+
+  var _ReactFiberBeginWork = ReactFiberBeginWork(
+      config,
+      hostContext,
+      legacyContext,
+      newContext,
+      hydrationContext,
+      scheduleWork,
+      computeExpirationForFiber
+    ),
+    beginWork = _ReactFiberBeginWork.beginWork;
+
+  var _ReactFiberCompleteWo = ReactFiberCompleteWork(
+      config,
+      hostContext,
+      legacyContext,
+      newContext,
+      hydrationContext
+    ),
+    completeWork = _ReactFiberCompleteWo.completeWork;
+
+  var _ReactFiberUnwindWork = ReactFiberUnwindWork(
+      hostContext,
+      legacyContext,
+      newContext,
+      scheduleWork,
+      isAlreadyFailedLegacyErrorBoundary
+    ),
+    throwException = _ReactFiberUnwindWork.throwException,
+    unwindWork = _ReactFiberUnwindWork.unwindWork,
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
+
+  var _ReactFiberCommitWork = ReactFiberCommitWork(
+      config,
+      onCommitPhaseError,
+      scheduleWork,
+      computeExpirationForFiber,
+      markLegacyErrorBoundaryAsFailed,
+      recalculateCurrentTime
+    ),
+    commitBeforeMutationLifeCycles =
+      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
+    commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
+    commitPlacement = _ReactFiberCommitWork.commitPlacement,
+    commitDeletion = _ReactFiberCommitWork.commitDeletion,
+    commitWork = _ReactFiberCommitWork.commitWork,
+    commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
+    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
+    commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
+    commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
+
+  var now = config.now,
+    scheduleDeferredCallback = config.scheduleDeferredCallback,
+    cancelDeferredCallback = config.cancelDeferredCallback,
+    prepareForCommit = config.prepareForCommit,
+    resetAfterCommit = config.resetAfterCommit;
+
+  // Represents the current time in ms.
+
+  var originalStartTimeMs = now();
+  var mostRecentCurrentTime = msToExpirationTime(0);
+  var mostRecentCurrentTimeMs = originalStartTimeMs;
+
+  // Used to ensure computeUniqueAsyncExpiration is monotonically increases.
+  var lastUniqueAsyncExpiration = 0;
+
+  // Represents the expiration time that incoming updates should use. (If this
+  // is NoWork, use the default strategy: async updates in async mode, sync
+  // updates in sync mode.)
+  var expirationContext = NoWork;
+
+  var isWorking = false;
+
+  // The next work in progress fiber that we're currently working on.
+  var nextUnitOfWork = null;
+  var nextRoot = null;
+  // The time at which we're currently rendering work.
+  var nextRenderExpirationTime = NoWork;
+
+  // The next fiber with an effect that we're currently committing.
+  var nextEffect = null;
+
+  var isCommitting = false;
+
+  var isRootReadyForCommit = false;
+
+  var legacyErrorBoundariesThatAlreadyFailed = null;
+
+  // Used for performance tracking.
+  var interruptedBy = null;
+
+  var stashedWorkInProgressProperties = void 0;
+  var replayUnitOfWork = void 0;
+  var isReplayingFailedUnitOfWork = void 0;
+  var originalReplayError = void 0;
+  var rethrowOriginalError = void 0;
+  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+    stashedWorkInProgressProperties = null;
+    isReplayingFailedUnitOfWork = false;
+    originalReplayError = null;
+    replayUnitOfWork = function(failedUnitOfWork, error, isAsync) {
+      // Restore the original state of the work-in-progress
+      assignFiberPropertiesInDEV(
+        failedUnitOfWork,
+        stashedWorkInProgressProperties
+      );
+      switch (failedUnitOfWork.tag) {
+        case HostRoot:
+          popHostContainer(failedUnitOfWork);
+          popTopLevelLegacyContextObject(failedUnitOfWork);
+          break;
+        case HostComponent:
+          popHostContext(failedUnitOfWork);
+          break;
+        case ClassComponent:
+          popLegacyContextProvider(failedUnitOfWork);
+          break;
+        case HostPortal:
+          popHostContainer(failedUnitOfWork);
+          break;
+        case ContextProvider:
+          popProvider(failedUnitOfWork);
+          break;
+      }
+      // Replay the begin phase.
+      isReplayingFailedUnitOfWork = true;
+      originalReplayError = error;
+      invokeGuardedCallback$2(null, workLoop, null, isAsync);
+      isReplayingFailedUnitOfWork = false;
+      originalReplayError = null;
+      if (hasCaughtError()) {
+        clearCaughtError();
+      } else {
+        // If the begin phase did not fail the second time, set this pointer
+        // back to the original value.
+        nextUnitOfWork = failedUnitOfWork;
+      }
+    };
+    rethrowOriginalError = function() {
+      throw originalReplayError;
+    };
+  }
+
+  function resetStack() {
+    if (nextUnitOfWork !== null) {
+      var interruptedWork = nextUnitOfWork["return"];
+      while (interruptedWork !== null) {
+        unwindInterruptedWork(interruptedWork);
+        interruptedWork = interruptedWork["return"];
+      }
+    }
+
+    {
+      ReactStrictModeWarnings.discardPendingWarnings();
+      stack.checkThatStackIsEmpty();
+    }
+
+    nextRoot = null;
+    nextRenderExpirationTime = NoWork;
+    nextUnitOfWork = null;
+
+    isRootReadyForCommit = false;
+  }
+
+  function commitAllHostEffects() {
+    while (nextEffect !== null) {
+      {
+        ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
+      }
+      recordEffect();
+
+      var effectTag = nextEffect.effectTag;
+
+      if (effectTag & ContentReset) {
+        commitResetTextContent(nextEffect);
+      }
+
+      if (effectTag & Ref) {
+        var current = nextEffect.alternate;
+        if (current !== null) {
+          commitDetachRef(current);
+        }
+      }
+
+      // The following switch statement is only concerned about placement,
+      // updates, and deletions. To avoid needing to add a case for every
+      // possible bitmap value, we remove the secondary effects from the
+      // effect tag and switch on that value.
+      var primaryEffectTag = effectTag & (Placement | Update | Deletion);
+      switch (primaryEffectTag) {
+        case Placement: {
+          commitPlacement(nextEffect);
+          // Clear the "placement" from effect tag so that we know that this is inserted, before
+          // any life-cycles like componentDidMount gets called.
+          // TODO: findDOMNode doesn't rely on this any more but isMounted
+          // does and isMounted is deprecated anyway so we should be able
+          // to kill this.
+          nextEffect.effectTag &= ~Placement;
+          break;
+        }
+        case PlacementAndUpdate: {
+          // Placement
+          commitPlacement(nextEffect);
+          // Clear the "placement" from effect tag so that we know that this is inserted, before
+          // any life-cycles like componentDidMount gets called.
+          nextEffect.effectTag &= ~Placement;
+
+          // Update
+          var _current = nextEffect.alternate;
+          commitWork(_current, nextEffect);
+          break;
+        }
+        case Update: {
+          var _current2 = nextEffect.alternate;
+          commitWork(_current2, nextEffect);
+          break;
+        }
+        case Deletion: {
+          commitDeletion(nextEffect);
+          break;
+        }
+      }
+      nextEffect = nextEffect.nextEffect;
+    }
+
+    {
+      ReactDebugCurrentFiber.resetCurrentFiber();
+    }
+  }
+
+  function commitBeforeMutationLifecycles() {
+    while (nextEffect !== null) {
+      var effectTag = nextEffect.effectTag;
+
+      if (effectTag & Snapshot) {
+        recordEffect();
+        var current = nextEffect.alternate;
+        commitBeforeMutationLifeCycles(current, nextEffect);
+      }
+
+      // Don't cleanup effects yet;
+      // This will be done by commitAllLifeCycles()
+      nextEffect = nextEffect.nextEffect;
+    }
+  }
+
+  function commitAllLifeCycles(
+    finishedRoot,
+    currentTime,
+    committedExpirationTime
+  ) {
+    {
+      ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
+
+      if (warnAboutDeprecatedLifecycles) {
+        ReactStrictModeWarnings.flushPendingDeprecationWarnings();
+      }
+    }
+    while (nextEffect !== null) {
+      var effectTag = nextEffect.effectTag;
+
+      if (effectTag & (Update | Callback)) {
+        recordEffect();
+        var current = nextEffect.alternate;
+        commitLifeCycles(
+          finishedRoot,
+          current,
+          nextEffect,
+          currentTime,
+          committedExpirationTime
+        );
+      }
+
+      if (effectTag & ErrLog) {
+        commitErrorLogging(nextEffect, onUncaughtError);
+      }
+
+      if (effectTag & Ref) {
+        recordEffect();
+        commitAttachRef(nextEffect);
+      }
+
+      var next = nextEffect.nextEffect;
+      // Ensure that we clean these up so that we don't accidentally keep them.
+      // I'm not actually sure this matters because we can't reset firstEffect
+      // and lastEffect since they're on every node, not just the effectful
+      // ones. So we have to clean everything as we reuse nodes anyway.
+      nextEffect.nextEffect = null;
+      // Ensure that we reset the effectTag here so that we can rely on effect
+      // tags to reason about the current life-cycle.
+      nextEffect = next;
+    }
+  }
+
+  function isAlreadyFailedLegacyErrorBoundary(instance) {
+    return (
+      legacyErrorBoundariesThatAlreadyFailed !== null &&
+      legacyErrorBoundariesThatAlreadyFailed.has(instance)
+    );
+  }
+
+  function markLegacyErrorBoundaryAsFailed(instance) {
+    if (legacyErrorBoundariesThatAlreadyFailed === null) {
+      legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
+    } else {
+      legacyErrorBoundariesThatAlreadyFailed.add(instance);
+    }
+  }
+
+  function commitRoot(finishedWork) {
+    isWorking = true;
+    isCommitting = true;
+    startCommitTimer();
+
+    var root = finishedWork.stateNode;
+    invariant(
+      root.current !== finishedWork,
+      "Cannot commit the same tree as before. This is probably a bug " +
+        "related to the return field. This error is likely caused by a bug " +
+        "in React. Please file an issue."
+    );
+    var committedExpirationTime = root.pendingCommitExpirationTime;
+    invariant(
+      committedExpirationTime !== NoWork,
+      "Cannot commit an incomplete root. This error is likely caused by a " +
+        "bug in React. Please file an issue."
+    );
+    root.pendingCommitExpirationTime = NoWork;
+
+    var currentTime = recalculateCurrentTime();
+
+    // Reset this to null before calling lifecycles
+    ReactCurrentOwner.current = null;
+
+    var firstEffect = void 0;
+    if (finishedWork.effectTag > PerformedWork) {
+      // A fiber's effect list consists only of its children, not itself. So if
+      // the root has an effect, we need to add it to the end of the list. The
+      // resulting list is the set that would belong to the root's parent, if
+      // it had one; that is, all the effects in the tree including the root.
+      if (finishedWork.lastEffect !== null) {
+        finishedWork.lastEffect.nextEffect = finishedWork;
+        firstEffect = finishedWork.firstEffect;
+      } else {
+        firstEffect = finishedWork;
+      }
+    } else {
+      // There is no effect on the root.
+      firstEffect = finishedWork.firstEffect;
+    }
+
+    prepareForCommit(root.containerInfo);
+
+    // Invoke instances of getSnapshotBeforeUpdate before mutation.
+    nextEffect = firstEffect;
+    startCommitSnapshotEffectsTimer();
+    while (nextEffect !== null) {
+      var didError = false;
+      var error = void 0;
+      {
+        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
+        if (hasCaughtError()) {
+          didError = true;
+          error = clearCaughtError();
+        }
+      }
+      if (didError) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, error);
+        // Clean-up
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
+    stopCommitSnapshotEffectsTimer();
+
+    // Commit all the side-effects within a tree. We'll do this in two passes.
+    // The first pass performs all the host insertions, updates, deletions and
+    // ref unmounts.
+    nextEffect = firstEffect;
+    startCommitHostEffectsTimer();
+    while (nextEffect !== null) {
+      var _didError = false;
+      var _error = void 0;
+      {
+        invokeGuardedCallback$2(null, commitAllHostEffects, null);
+        if (hasCaughtError()) {
+          _didError = true;
+          _error = clearCaughtError();
+        }
+      }
+      if (_didError) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, _error);
+        // Clean-up
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
+    stopCommitHostEffectsTimer();
+
+    resetAfterCommit(root.containerInfo);
+
+    // The work-in-progress tree is now the current tree. This must come after
+    // the first pass of the commit phase, so that the previous tree is still
+    // current during componentWillUnmount, but before the second pass, so that
+    // the finished work is current during componentDidMount/Update.
+    root.current = finishedWork;
+
+    // In the second pass we'll perform all life-cycles and ref callbacks.
+    // Life-cycles happen as a separate pass so that all placements, updates,
+    // and deletions in the entire tree have already been invoked.
+    // This pass also triggers any renderer-specific initial effects.
+    nextEffect = firstEffect;
+    startCommitLifeCyclesTimer();
+    while (nextEffect !== null) {
+      var _didError2 = false;
+      var _error2 = void 0;
+      {
+        invokeGuardedCallback$2(
+          null,
+          commitAllLifeCycles,
+          null,
+          root,
+          currentTime,
+          committedExpirationTime
+        );
+        if (hasCaughtError()) {
+          _didError2 = true;
+          _error2 = clearCaughtError();
+        }
+      }
+      if (_didError2) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, _error2);
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
+
+    isCommitting = false;
+    isWorking = false;
+    stopCommitLifeCyclesTimer();
+    stopCommitTimer();
+    if (typeof onCommitRoot === "function") {
+      onCommitRoot(finishedWork.stateNode);
+    }
+    if (true && ReactFiberInstrumentation_1.debugTool) {
+      ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
+    }
+
+    var remainingTime = root.current.expirationTime;
+    if (remainingTime === NoWork) {
+      // If there's no remaining work, we can clear the set of already failed
+      // error boundaries.
+      legacyErrorBoundariesThatAlreadyFailed = null;
+    }
+    return remainingTime;
+  }
+
+  function resetExpirationTime(workInProgress, renderTime) {
+    if (renderTime !== Never && workInProgress.expirationTime === Never) {
+      // The children of this component are hidden. Don't bubble their
+      // expiration times.
+      return;
+    }
+
+    // Check for pending updates.
+    var newExpirationTime = getUpdateExpirationTime(workInProgress);
+
+    // TODO: Calls need to visit stateNode
+
+    // Bubble up the earliest expiration time.
+    var child = workInProgress.child;
+    while (child !== null) {
+      if (
+        child.expirationTime !== NoWork &&
+        (newExpirationTime === NoWork ||
+          newExpirationTime > child.expirationTime)
+      ) {
+        newExpirationTime = child.expirationTime;
+      }
+      child = child.sibling;
+    }
+    workInProgress.expirationTime = newExpirationTime;
+  }
+
+  function completeUnitOfWork(workInProgress) {
+    // Attempt to complete the current unit of work, then move to the
+    // next sibling. If there are no more siblings, return to the
+    // parent fiber.
+    while (true) {
+      // The current, flushed, state of this fiber is the alternate.
+      // Ideally nothing should rely on this, but relying on it here
+      // means that we don't need an additional field on the work in
+      // progress.
+      var current = workInProgress.alternate;
+      {
+        ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+      }
+
+      var returnFiber = workInProgress["return"];
+      var siblingFiber = workInProgress.sibling;
+
+      if ((workInProgress.effectTag & Incomplete) === NoEffect) {
+        // This fiber completed.
+        var next = completeWork(
+          current,
+          workInProgress,
+          nextRenderExpirationTime
+        );
+        stopWorkTimer(workInProgress);
+        resetExpirationTime(workInProgress, nextRenderExpirationTime);
+        {
+          ReactDebugCurrentFiber.resetCurrentFiber();
+        }
+
+        if (next !== null) {
+          stopWorkTimer(workInProgress);
+          if (true && ReactFiberInstrumentation_1.debugTool) {
+            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
+              workInProgress
+            );
+          }
+          // If completing this work spawned new work, do that next. We'll come
+          // back here again.
+          return next;
+        }
+
+        if (
+          returnFiber !== null &&
+          // Do not append effects to parents if a sibling failed to complete
+          (returnFiber.effectTag & Incomplete) === NoEffect
+        ) {
+          // Append all the effects of the subtree and this fiber onto the effect
+          // list of the parent. The completion order of the children affects the
+          // side-effect order.
+          if (returnFiber.firstEffect === null) {
+            returnFiber.firstEffect = workInProgress.firstEffect;
+          }
+          if (workInProgress.lastEffect !== null) {
+            if (returnFiber.lastEffect !== null) {
+              returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
+            }
+            returnFiber.lastEffect = workInProgress.lastEffect;
+          }
+
+          // If this fiber had side-effects, we append it AFTER the children's
+          // side-effects. We can perform certain side-effects earlier if
+          // needed, by doing multiple passes over the effect list. We don't want
+          // to schedule our own side-effect on our own list because if end up
+          // reusing children we'll schedule this effect onto itself since we're
+          // at the end.
+          var effectTag = workInProgress.effectTag;
+          // Skip both NoWork and PerformedWork tags when creating the effect list.
+          // PerformedWork effect is read by React DevTools but shouldn't be committed.
+          if (effectTag > PerformedWork) {
+            if (returnFiber.lastEffect !== null) {
+              returnFiber.lastEffect.nextEffect = workInProgress;
+            } else {
+              returnFiber.firstEffect = workInProgress;
+            }
+            returnFiber.lastEffect = workInProgress;
+          }
+        }
+
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+        }
+
+        if (siblingFiber !== null) {
+          // If there is more work to do in this returnFiber, do that next.
+          return siblingFiber;
+        } else if (returnFiber !== null) {
+          // If there's no more work in this returnFiber. Complete the returnFiber.
+          workInProgress = returnFiber;
+          continue;
+        } else {
+          // We've reached the root.
+          isRootReadyForCommit = true;
+          return null;
+        }
+      } else {
+        // This fiber did not complete because something threw. Pop values off
+        // the stack without entering the complete phase. If this is a boundary,
+        // capture values if possible.
+        var _next = unwindWork(workInProgress);
+        // Because this fiber did not complete, don't reset its expiration time.
+        if (workInProgress.effectTag & DidCapture) {
+          // Restarting an error boundary
+          stopFailedWorkTimer(workInProgress);
+        } else {
+          stopWorkTimer(workInProgress);
+        }
+
+        {
+          ReactDebugCurrentFiber.resetCurrentFiber();
+        }
+
+        if (_next !== null) {
+          stopWorkTimer(workInProgress);
+          if (true && ReactFiberInstrumentation_1.debugTool) {
+            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
+              workInProgress
+            );
+          }
+          // If completing this work spawned new work, do that next. We'll come
+          // back here again.
+          // Since we're restarting, remove anything that is not a host effect
+          // from the effect tag.
+          _next.effectTag &= HostEffectMask;
+          return _next;
+        }
+
+        if (returnFiber !== null) {
+          // Mark the parent fiber as incomplete and clear its effect list.
+          returnFiber.firstEffect = returnFiber.lastEffect = null;
+          returnFiber.effectTag |= Incomplete;
+        }
+
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+        }
+
+        if (siblingFiber !== null) {
+          // If there is more work to do in this returnFiber, do that next.
+          return siblingFiber;
+        } else if (returnFiber !== null) {
+          // If there's no more work in this returnFiber. Complete the returnFiber.
+          workInProgress = returnFiber;
+          continue;
+        } else {
+          return null;
+        }
+      }
+    }
+
+    // Without this explicit null return Flow complains of invalid return type
+    // TODO Remove the above while(true) loop
+    // eslint-disable-next-line no-unreachable
+    return null;
+  }
+
+  function performUnitOfWork(workInProgress) {
+    // The current, flushed, state of this fiber is the alternate.
+    // Ideally nothing should rely on this, but relying on it here
+    // means that we don't need an additional field on the work in
+    // progress.
+    var current = workInProgress.alternate;
+
+    // See if beginning this work spawns more work.
+    startWorkTimer(workInProgress);
+    {
+      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+    }
+
+    if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
+        stashedWorkInProgressProperties,
+        workInProgress
+      );
+    }
+    var next = beginWork(current, workInProgress, nextRenderExpirationTime);
+    {
+      ReactDebugCurrentFiber.resetCurrentFiber();
+      if (isReplayingFailedUnitOfWork) {
+        // Currently replaying a failed unit of work. This should be unreachable,
+        // because the render phase is meant to be idempotent, and it should
+        // have thrown again. Since it didn't, rethrow the original error, so
+        // React's internal stack is not misaligned.
+        rethrowOriginalError();
+      }
+    }
+    if (true && ReactFiberInstrumentation_1.debugTool) {
+      ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
+    }
+
+    if (next === null) {
+      // If this doesn't spawn new work, complete the current work.
+      next = completeUnitOfWork(workInProgress);
+    }
+
+    ReactCurrentOwner.current = null;
+
+    return next;
+  }
+
+  function workLoop(isAsync) {
+    if (!isAsync) {
+      // Flush all expired work.
+      while (nextUnitOfWork !== null) {
+        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      }
+    } else {
+      // Flush asynchronous work until the deadline runs out of time.
+      while (nextUnitOfWork !== null && !shouldYield()) {
+        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      }
+    }
+  }
+
+  function renderRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isWorking,
+      "renderRoot was called recursively. This error is likely caused " +
+        "by a bug in React. Please file an issue."
+    );
+    isWorking = true;
+
+    // Check if we're starting from a fresh stack, or if we're resuming from
+    // previously yielded work.
+    if (
+      expirationTime !== nextRenderExpirationTime ||
+      root !== nextRoot ||
+      nextUnitOfWork === null
+    ) {
+      // Reset the stack and start working from the root.
+      resetStack();
+      nextRoot = root;
+      nextRenderExpirationTime = expirationTime;
+      nextUnitOfWork = createWorkInProgress(
+        nextRoot.current,
+        null,
+        nextRenderExpirationTime
+      );
+      root.pendingCommitExpirationTime = NoWork;
+    }
+
+    var didFatal = false;
+
+    startWorkLoopTimer(nextUnitOfWork);
+
+    do {
+      try {
+        workLoop(isAsync);
+      } catch (thrownValue) {
+        if (nextUnitOfWork === null) {
+          // This is a fatal error.
+          didFatal = true;
+          onUncaughtError(thrownValue);
+          break;
+        }
+
+        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+          var failedUnitOfWork = nextUnitOfWork;
+          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
+        }
+
+        var sourceFiber = nextUnitOfWork;
+        var returnFiber = sourceFiber["return"];
+        if (returnFiber === null) {
+          // This is the root. The root could capture its own errors. However,
+          // we don't know if it errors before or after we pushed the host
+          // context. This information is needed to avoid a stack mismatch.
+          // Because we're not sure, treat this as a fatal error. We could track
+          // which phase it fails in, but doesn't seem worth it. At least
+          // for now.
+          didFatal = true;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        throwException(returnFiber, sourceFiber, thrownValue);
+        nextUnitOfWork = completeUnitOfWork(sourceFiber);
+      }
+      break;
+    } while (true);
+
+    // We're done performing work. Time to clean up.
+    var didCompleteRoot = false;
+    isWorking = false;
+
+    // Yield back to main thread.
+    if (didFatal) {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
+      // There was a fatal error.
+      {
+        stack.resetStackAfterFatalErrorInDev();
+      }
+      return null;
+    } else if (nextUnitOfWork === null) {
+      // We reached the root.
+      if (isRootReadyForCommit) {
+        didCompleteRoot = true;
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
+        // The root successfully completed. It's ready for commit.
+        root.pendingCommitExpirationTime = expirationTime;
+        var finishedWork = root.current.alternate;
+        return finishedWork;
+      } else {
+        // The root did not complete.
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
+        invariant(
+          false,
+          "Expired work should have completed. This error is likely caused " +
+            "by a bug in React. Please file an issue."
+        );
+      }
+    } else {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
+      // There's more work to do, but we ran out of time. Yield back to
+      // the renderer.
+      return null;
+    }
+  }
+
+  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
+    // TODO: We only support dispatching errors.
+    var capturedValue = createCapturedValue(value, sourceFiber);
+    var update = {
+      expirationTime: expirationTime,
+      partialState: null,
+      callback: null,
+      isReplace: false,
+      isForced: false,
+      capturedValue: capturedValue,
+      next: null
+    };
+    insertUpdateIntoFiber(boundaryFiber, update);
+    scheduleWork(boundaryFiber, expirationTime);
+  }
+
+  function dispatch(sourceFiber, value, expirationTime) {
+    invariant(
+      !isWorking || isCommitting,
+      "dispatch: Cannot dispatch during the render phase."
+    );
+
+    // TODO: Handle arrays
+
+    var fiber = sourceFiber["return"];
+    while (fiber !== null) {
+      switch (fiber.tag) {
+        case ClassComponent:
+          var ctor = fiber.type;
+          var instance = fiber.stateNode;
+          if (
+            typeof ctor.getDerivedStateFromCatch === "function" ||
+            (typeof instance.componentDidCatch === "function" &&
+              !isAlreadyFailedLegacyErrorBoundary(instance))
+          ) {
+            scheduleCapture(sourceFiber, fiber, value, expirationTime);
+            return;
+          }
+          break;
+        // TODO: Handle async boundaries
+        case HostRoot:
+          scheduleCapture(sourceFiber, fiber, value, expirationTime);
+          return;
+      }
+      fiber = fiber["return"];
+    }
+
+    if (sourceFiber.tag === HostRoot) {
+      // Error was thrown at the root. There is no parent, so the root
+      // itself should capture it.
+      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
+    }
+  }
+
+  function onCommitPhaseError(fiber, error) {
+    return dispatch(fiber, error, Sync);
+  }
+
+  function computeAsyncExpiration(currentTime) {
+    // Given the current clock time, returns an expiration time. We use rounding
+    // to batch like updates together.
+    // Should complete within ~1000ms. 1200ms max.
+    var expirationMs = 5000;
+    var bucketSizeMs = 250;
+    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+  }
+
+  function computeInteractiveExpiration(currentTime) {
+    var expirationMs = void 0;
+    // We intentionally set a higher expiration time for interactive updates in
+    // dev than in production.
+    // If the main thread is being blocked so long that you hit the expiration,
+    // it's a problem that could be solved with better scheduling.
+    // People will be more likely to notice this and fix it with the long
+    // expiration time in development.
+    // In production we opt for better UX at the risk of masking scheduling
+    // problems, by expiring fast.
+    {
+      // Should complete within ~500ms. 600ms max.
+      expirationMs = 500;
+    }
+    var bucketSizeMs = 100;
+    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+  }
+
+  // Creates a unique async expiration time.
+  function computeUniqueAsyncExpiration() {
+    var currentTime = recalculateCurrentTime();
+    var result = computeAsyncExpiration(currentTime);
+    if (result <= lastUniqueAsyncExpiration) {
+      // Since we assume the current time monotonically increases, we only hit
+      // this branch when computeUniqueAsyncExpiration is fired multiple times
+      // within a 200ms window (or whatever the async bucket size is).
+      result = lastUniqueAsyncExpiration + 1;
+    }
+    lastUniqueAsyncExpiration = result;
+    return lastUniqueAsyncExpiration;
+  }
+
+  function computeExpirationForFiber(fiber) {
+    var expirationTime = void 0;
+    if (expirationContext !== NoWork) {
+      // An explicit expiration context was set;
+      expirationTime = expirationContext;
+    } else if (isWorking) {
+      if (isCommitting) {
+        // Updates that occur during the commit phase should have sync priority
+        // by default.
+        expirationTime = Sync;
+      } else {
+        // Updates during the render phase should expire at the same time as
+        // the work that is being rendered.
+        expirationTime = nextRenderExpirationTime;
+      }
+    } else {
+      // No explicit expiration context was set, and we're not currently
+      // performing work. Calculate a new expiration time.
+      if (fiber.mode & AsyncMode) {
+        if (isBatchingInteractiveUpdates) {
+          // This is an interactive update
+          var currentTime = recalculateCurrentTime();
+          expirationTime = computeInteractiveExpiration(currentTime);
+        } else {
+          // This is an async update
+          var _currentTime = recalculateCurrentTime();
+          expirationTime = computeAsyncExpiration(_currentTime);
+        }
+      } else {
+        // This is a sync update
+        expirationTime = Sync;
+      }
+    }
+    if (isBatchingInteractiveUpdates) {
+      // This is an interactive update. Keep track of the lowest pending
+      // interactive expiration time. This allows us to synchronously flush
+      // all interactive updates when needed.
+      if (
+        lowestPendingInteractiveExpirationTime === NoWork ||
+        expirationTime > lowestPendingInteractiveExpirationTime
+      ) {
+        lowestPendingInteractiveExpirationTime = expirationTime;
+      }
+    }
+    return expirationTime;
+  }
+
+  function scheduleWork(fiber, expirationTime) {
+    return scheduleWorkImpl(fiber, expirationTime, false);
+  }
+
+  function scheduleWorkImpl(fiber, expirationTime, isErrorRecovery) {
+    recordScheduleUpdate();
+
+    {
+      if (!isErrorRecovery && fiber.tag === ClassComponent) {
+        var instance = fiber.stateNode;
+        warnAboutInvalidUpdates(instance);
+      }
+    }
+
+    var node = fiber;
+    while (node !== null) {
+      // Walk the parent path to the root and update each node's
+      // expiration time.
+      if (
+        node.expirationTime === NoWork ||
+        node.expirationTime > expirationTime
+      ) {
+        node.expirationTime = expirationTime;
+      }
+      if (node.alternate !== null) {
+        if (
+          node.alternate.expirationTime === NoWork ||
+          node.alternate.expirationTime > expirationTime
+        ) {
+          node.alternate.expirationTime = expirationTime;
+        }
+      }
+      if (node["return"] === null) {
+        if (node.tag === HostRoot) {
+          var root = node.stateNode;
+          if (
+            !isWorking &&
+            nextRenderExpirationTime !== NoWork &&
+            expirationTime < nextRenderExpirationTime
+          ) {
+            // This is an interruption. (Used for performance tracking.)
+            interruptedBy = fiber;
+            resetStack();
+          }
+          if (
+            // If we're in the render phase, we don't need to schedule this root
+            // for an update, because we'll do it before we exit...
+            !isWorking ||
+            isCommitting ||
+            // ...unless this is a different root than the one we're rendering.
+            nextRoot !== root
+          ) {
+            // Add this root to the root schedule.
+            requestWork(root, expirationTime);
+          }
+          if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
+            invariant(
+              false,
+              "Maximum update depth exceeded. This can happen when a " +
+                "component repeatedly calls setState inside " +
+                "componentWillUpdate or componentDidUpdate. React limits " +
+                "the number of nested updates to prevent infinite loops."
+            );
+          }
+        } else {
+          {
+            if (!isErrorRecovery && fiber.tag === ClassComponent) {
+              warnAboutUpdateOnUnmounted(fiber);
+            }
+          }
+          return;
+        }
+      }
+      node = node["return"];
+    }
+  }
+
+  function recalculateCurrentTime() {
+    // Subtract initial time so it fits inside 32bits
+    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
+    mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
+    return mostRecentCurrentTime;
+  }
+
+  function deferredUpdates(fn) {
+    var previousExpirationContext = expirationContext;
+    var currentTime = recalculateCurrentTime();
+    expirationContext = computeAsyncExpiration(currentTime);
+    try {
+      return fn();
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  }
+  function syncUpdates(fn, a, b, c, d) {
+    var previousExpirationContext = expirationContext;
+    expirationContext = Sync;
+    try {
+      return fn(a, b, c, d);
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  }
+
+  // TODO: Everything below this is written as if it has been lifted to the
+  // renderers. I'll do this in a follow-up.
+
+  // Linked-list of roots
+  var firstScheduledRoot = null;
+  var lastScheduledRoot = null;
+
+  var callbackExpirationTime = NoWork;
+  var callbackID = -1;
+  var isRendering = false;
+  var nextFlushedRoot = null;
+  var nextFlushedExpirationTime = NoWork;
+  var lowestPendingInteractiveExpirationTime = NoWork;
+  var deadlineDidExpire = false;
+  var hasUnhandledError = false;
+  var unhandledError = null;
+  var deadline = null;
+
+  var isBatchingUpdates = false;
+  var isUnbatchingUpdates = false;
+  var isBatchingInteractiveUpdates = false;
+
+  var completedBatches = null;
+
+  // Use these to prevent an infinite loop of nested updates
+  var NESTED_UPDATE_LIMIT = 1000;
+  var nestedUpdateCount = 0;
+
+  var timeHeuristicForUnitOfWork = 1;
+
+  function scheduleCallbackWithExpiration(expirationTime) {
+    if (callbackExpirationTime !== NoWork) {
+      // A callback is already scheduled. Check its expiration time (timeout).
+      if (expirationTime > callbackExpirationTime) {
+        // Existing callback has sufficient timeout. Exit.
+        return;
+      } else {
+        // Existing callback has insufficient timeout. Cancel and schedule a
+        // new one.
+        cancelDeferredCallback(callbackID);
+      }
+      // The request callback timer is already running. Don't start a new one.
+    } else {
+      startRequestCallbackTimer();
+    }
+
+    // Compute a timeout for the given expiration time.
+    var currentMs = now() - originalStartTimeMs;
+    var expirationMs = expirationTimeToMs(expirationTime);
+    var timeout = expirationMs - currentMs;
+
+    callbackExpirationTime = expirationTime;
+    callbackID = scheduleDeferredCallback(performAsyncWork, {
+      timeout: timeout
+    });
+  }
+
+  // requestWork is called by the scheduler whenever a root receives an update.
+  // It's up to the renderer to call renderRoot at some point in the future.
+  function requestWork(root, expirationTime) {
+    addRootToSchedule(root, expirationTime);
+
+    if (isRendering) {
+      // Prevent reentrancy. Remaining work will be scheduled at the end of
+      // the currently rendering batch.
+      return;
+    }
+
+    if (isBatchingUpdates) {
+      // Flush work at the end of the batch.
+      if (isUnbatchingUpdates) {
+        // ...unless we're inside unbatchedUpdates, in which case we should
+        // flush it now.
+        nextFlushedRoot = root;
+        nextFlushedExpirationTime = Sync;
+        performWorkOnRoot(root, Sync, false);
+      }
+      return;
+    }
+
+    // TODO: Get rid of Sync and use current time?
+    if (expirationTime === Sync) {
+      performSyncWork();
+    } else {
+      scheduleCallbackWithExpiration(expirationTime);
+    }
+  }
+
+  function addRootToSchedule(root, expirationTime) {
+    // Add the root to the schedule.
+    // Check if this root is already part of the schedule.
+    if (root.nextScheduledRoot === null) {
+      // This root is not already scheduled. Add it.
+      root.remainingExpirationTime = expirationTime;
+      if (lastScheduledRoot === null) {
+        firstScheduledRoot = lastScheduledRoot = root;
+        root.nextScheduledRoot = root;
+      } else {
+        lastScheduledRoot.nextScheduledRoot = root;
+        lastScheduledRoot = root;
+        lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+      }
+    } else {
+      // This root is already scheduled, but its priority may have increased.
+      var remainingExpirationTime = root.remainingExpirationTime;
+      if (
+        remainingExpirationTime === NoWork ||
+        expirationTime < remainingExpirationTime
+      ) {
+        // Update the priority.
+        root.remainingExpirationTime = expirationTime;
+      }
+    }
+  }
+
+  function findHighestPriorityRoot() {
+    var highestPriorityWork = NoWork;
+    var highestPriorityRoot = null;
+    if (lastScheduledRoot !== null) {
+      var previousScheduledRoot = lastScheduledRoot;
+      var root = firstScheduledRoot;
+      while (root !== null) {
+        var remainingExpirationTime = root.remainingExpirationTime;
+        if (remainingExpirationTime === NoWork) {
+          // This root no longer has work. Remove it from the scheduler.
+
+          // TODO: This check is redudant, but Flow is confused by the branch
+          // below where we set lastScheduledRoot to null, even though we break
+          // from the loop right after.
+          invariant(
+            previousScheduledRoot !== null && lastScheduledRoot !== null,
+            "Should have a previous and last root. This error is likely " +
+              "caused by a bug in React. Please file an issue."
+          );
+          if (root === root.nextScheduledRoot) {
+            // This is the only root in the list.
+            root.nextScheduledRoot = null;
+            firstScheduledRoot = lastScheduledRoot = null;
+            break;
+          } else if (root === firstScheduledRoot) {
+            // This is the first root in the list.
+            var next = root.nextScheduledRoot;
+            firstScheduledRoot = next;
+            lastScheduledRoot.nextScheduledRoot = next;
+            root.nextScheduledRoot = null;
+          } else if (root === lastScheduledRoot) {
+            // This is the last root in the list.
+            lastScheduledRoot = previousScheduledRoot;
+            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+            root.nextScheduledRoot = null;
+            break;
+          } else {
+            previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
+            root.nextScheduledRoot = null;
+          }
+          root = previousScheduledRoot.nextScheduledRoot;
+        } else {
+          if (
+            highestPriorityWork === NoWork ||
+            remainingExpirationTime < highestPriorityWork
+          ) {
+            // Update the priority, if it's higher
+            highestPriorityWork = remainingExpirationTime;
+            highestPriorityRoot = root;
+          }
+          if (root === lastScheduledRoot) {
+            break;
+          }
+          previousScheduledRoot = root;
+          root = root.nextScheduledRoot;
+        }
+      }
+    }
+
+    // If the next root is the same as the previous root, this is a nested
+    // update. To prevent an infinite loop, increment the nested update count.
+    var previousFlushedRoot = nextFlushedRoot;
+    if (
+      previousFlushedRoot !== null &&
+      previousFlushedRoot === highestPriorityRoot &&
+      highestPriorityWork === Sync
+    ) {
+      nestedUpdateCount++;
+    } else {
+      // Reset whenever we switch roots.
+      nestedUpdateCount = 0;
+    }
+    nextFlushedRoot = highestPriorityRoot;
+    nextFlushedExpirationTime = highestPriorityWork;
+  }
+
+  function performAsyncWork(dl) {
+    performWork(NoWork, true, dl);
+  }
+
+  function performSyncWork() {
+    performWork(Sync, false, null);
+  }
+
+  function performWork(minExpirationTime, isAsync, dl) {
+    deadline = dl;
+
+    // Keep working on roots until there's no more work, or until the we reach
+    // the deadline.
+    findHighestPriorityRoot();
+
+    if (enableUserTimingAPI && deadline !== null) {
+      var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
+      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
+      stopRequestCallbackTimer(didExpire, timeout);
+    }
+
+    if (isAsync) {
+      while (
+        nextFlushedRoot !== null &&
+        nextFlushedExpirationTime !== NoWork &&
+        (minExpirationTime === NoWork ||
+          minExpirationTime >= nextFlushedExpirationTime) &&
+        (!deadlineDidExpire ||
+          recalculateCurrentTime() >= nextFlushedExpirationTime)
+      ) {
+        performWorkOnRoot(
+          nextFlushedRoot,
+          nextFlushedExpirationTime,
+          !deadlineDidExpire
+        );
+        findHighestPriorityRoot();
+      }
+    } else {
+      while (
+        nextFlushedRoot !== null &&
+        nextFlushedExpirationTime !== NoWork &&
+        (minExpirationTime === NoWork ||
+          minExpirationTime >= nextFlushedExpirationTime)
+      ) {
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
+        findHighestPriorityRoot();
+      }
+    }
+
+    // We're done flushing work. Either we ran out of time in this callback,
+    // or there's no more work left with sufficient priority.
+
+    // If we're inside a callback, set this to false since we just completed it.
+    if (deadline !== null) {
+      callbackExpirationTime = NoWork;
+      callbackID = -1;
+    }
+    // If there's work left over, schedule a new callback.
+    if (nextFlushedExpirationTime !== NoWork) {
+      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
+    }
+
+    // Clean-up.
+    deadline = null;
+    deadlineDidExpire = false;
+
+    finishRendering();
+  }
+
+  function flushRoot(root, expirationTime) {
+    invariant(
+      !isRendering,
+      "work.commit(): Cannot commit while already rendering. This likely " +
+        "means you attempted to commit from inside a lifecycle method."
+    );
+    // Perform work on root as if the given expiration time is the current time.
+    // This has the effect of synchronously flushing all work up to and
+    // including the given time.
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
+    performWorkOnRoot(root, expirationTime, false);
+    // Flush any sync work that was scheduled by lifecycles
+    performSyncWork();
+    finishRendering();
+  }
+
+  function finishRendering() {
+    nestedUpdateCount = 0;
+
+    if (completedBatches !== null) {
+      var batches = completedBatches;
+      completedBatches = null;
+      for (var i = 0; i < batches.length; i++) {
+        var batch = batches[i];
+        try {
+          batch._onComplete();
+        } catch (error) {
+          if (!hasUnhandledError) {
+            hasUnhandledError = true;
+            unhandledError = error;
+          }
+        }
+      }
+    }
+
+    if (hasUnhandledError) {
+      var error = unhandledError;
+      unhandledError = null;
+      hasUnhandledError = false;
+      throw error;
+    }
+  }
+
+  function performWorkOnRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isRendering,
+      "performWorkOnRoot was called recursively. This error is likely caused " +
+        "by a bug in React. Please file an issue."
+    );
+
+    isRendering = true;
+
+    // Check if this is async work or sync/expired work.
+    if (!isAsync) {
+      // Flush sync work.
+      var finishedWork = root.finishedWork;
+      if (finishedWork !== null) {
+        // This root is already complete. We can commit it.
+        completeRoot(root, finishedWork, expirationTime);
+      } else {
+        root.finishedWork = null;
+        finishedWork = renderRoot(root, expirationTime, false);
+        if (finishedWork !== null) {
+          // We've completed the root. Commit it.
+          completeRoot(root, finishedWork, expirationTime);
+        }
+      }
+    } else {
+      // Flush async work.
+      var _finishedWork = root.finishedWork;
+      if (_finishedWork !== null) {
+        // This root is already complete. We can commit it.
+        completeRoot(root, _finishedWork, expirationTime);
+      } else {
+        root.finishedWork = null;
+        _finishedWork = renderRoot(root, expirationTime, true);
+        if (_finishedWork !== null) {
+          // We've completed the root. Check the deadline one more time
+          // before committing.
+          if (!shouldYield()) {
+            // Still time left. Commit the root.
+            completeRoot(root, _finishedWork, expirationTime);
+          } else {
+            // There's no time left. Mark this root as complete. We'll come
+            // back and commit it later.
+            root.finishedWork = _finishedWork;
+          }
+        }
+      }
+    }
+
+    isRendering = false;
+  }
+
+  function completeRoot(root, finishedWork, expirationTime) {
+    // Check if there's a batch that matches this expiration time.
+    var firstBatch = root.firstBatch;
+    if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
+      if (completedBatches === null) {
+        completedBatches = [firstBatch];
+      } else {
+        completedBatches.push(firstBatch);
+      }
+      if (firstBatch._defer) {
+        // This root is blocked from committing by a batch. Unschedule it until
+        // we receive another update.
+        root.finishedWork = finishedWork;
+        root.remainingExpirationTime = NoWork;
+        return;
+      }
+    }
+
+    // Commit the root.
+    root.finishedWork = null;
+    root.remainingExpirationTime = commitRoot(finishedWork);
+  }
+
+  // When working on async work, the reconciler asks the renderer if it should
+  // yield execution. For DOM, we implement this with requestIdleCallback.
+  function shouldYield() {
+    if (deadline === null) {
+      return false;
+    }
+    if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
+      // Disregard deadline.didTimeout. Only expired work should be flushed
+      // during a timeout. This path is only hit for non-expired work.
+      return false;
+    }
+    deadlineDidExpire = true;
+    return true;
+  }
+
+  function onUncaughtError(error) {
+    invariant(
+      nextFlushedRoot !== null,
+      "Should be working on a root. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+    // Unschedule this root so we don't work on it again until there's
+    // another update.
+    nextFlushedRoot.remainingExpirationTime = NoWork;
+    if (!hasUnhandledError) {
+      hasUnhandledError = true;
+      unhandledError = error;
+    }
+  }
+
+  // TODO: Batching should be implemented at the renderer level, not inside
+  // the reconciler.
+  function batchedUpdates(fn, a) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      return fn(a);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performSyncWork();
+      }
+    }
+  }
+
+  // TODO: Batching should be implemented at the renderer level, not inside
+  // the reconciler.
+  function unbatchedUpdates(fn, a) {
+    if (isBatchingUpdates && !isUnbatchingUpdates) {
+      isUnbatchingUpdates = true;
+      try {
+        return fn(a);
+      } finally {
+        isUnbatchingUpdates = false;
+      }
+    }
+    return fn(a);
+  }
+
+  // TODO: Batching should be implemented at the renderer level, not within
+  // the reconciler.
+  function flushSync(fn, a) {
+    invariant(
+      !isRendering,
+      "flushSync was called from inside a lifecycle method. It cannot be " +
+        "called when React is already rendering."
+    );
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      return syncUpdates(fn, a);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      performSyncWork();
+    }
+  }
+
+  function interactiveUpdates(fn, a, b) {
+    if (isBatchingInteractiveUpdates) {
+      return fn(a, b);
+    }
+    // If there are any pending interactive updates, synchronously flush them.
+    // This needs to happen before we read any handlers, because the effect of
+    // the previous event may influence which handlers are called during
+    // this event.
+    if (
+      !isBatchingUpdates &&
+      !isRendering &&
+      lowestPendingInteractiveExpirationTime !== NoWork
+    ) {
+      // Synchronously flush pending interactive updates.
+      performWork(lowestPendingInteractiveExpirationTime, false, null);
+      lowestPendingInteractiveExpirationTime = NoWork;
+    }
+    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingInteractiveUpdates = true;
+    isBatchingUpdates = true;
+    try {
+      return fn(a, b);
+    } finally {
+      isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performSyncWork();
+      }
+    }
+  }
+
+  function flushInteractiveUpdates() {
+    if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
+      // Synchronously flush pending interactive updates.
+      performWork(lowestPendingInteractiveExpirationTime, false, null);
+      lowestPendingInteractiveExpirationTime = NoWork;
+    }
+  }
+
+  function flushControlled(fn) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      syncUpdates(fn);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performWork(Sync, false, null);
+      }
+    }
+  }
+
+  return {
+    recalculateCurrentTime: recalculateCurrentTime,
+    computeExpirationForFiber: computeExpirationForFiber,
+    scheduleWork: scheduleWork,
+    requestWork: requestWork,
+    flushRoot: flushRoot,
+    batchedUpdates: batchedUpdates,
+    unbatchedUpdates: unbatchedUpdates,
+    flushSync: flushSync,
+    flushControlled: flushControlled,
+    deferredUpdates: deferredUpdates,
+    syncUpdates: syncUpdates,
+    interactiveUpdates: interactiveUpdates,
+    flushInteractiveUpdates: flushInteractiveUpdates,
+    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+    legacyContext: legacyContext
+  };
+};
+
+var didWarnAboutNestedUpdates = void 0;
+
+{
+  didWarnAboutNestedUpdates = false;
+}
+
+// 0 is PROD, 1 is DEV.
+// Might add PROFILE later.
+
+var ReactFiberReconciler$1 = function(config) {
+  var getPublicInstance = config.getPublicInstance;
+
+  var _ReactFiberScheduler = ReactFiberScheduler(config),
+    computeUniqueAsyncExpiration =
+      _ReactFiberScheduler.computeUniqueAsyncExpiration,
+    recalculateCurrentTime = _ReactFiberScheduler.recalculateCurrentTime,
+    computeExpirationForFiber = _ReactFiberScheduler.computeExpirationForFiber,
+    scheduleWork = _ReactFiberScheduler.scheduleWork,
+    requestWork = _ReactFiberScheduler.requestWork,
+    flushRoot = _ReactFiberScheduler.flushRoot,
+    batchedUpdates = _ReactFiberScheduler.batchedUpdates,
+    unbatchedUpdates = _ReactFiberScheduler.unbatchedUpdates,
+    flushSync = _ReactFiberScheduler.flushSync,
+    flushControlled = _ReactFiberScheduler.flushControlled,
+    deferredUpdates = _ReactFiberScheduler.deferredUpdates,
+    syncUpdates = _ReactFiberScheduler.syncUpdates,
+    interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
+    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
+    legacyContext = _ReactFiberScheduler.legacyContext;
+
+  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
+
+  function getContextForSubtree(parentComponent) {
+    if (!parentComponent) {
+      return emptyObject;
+    }
+
+    var fiber = get$1(parentComponent);
+    var parentContext = findCurrentUnmaskedContext(fiber);
+    return isContextProvider(fiber)
+      ? processChildContext(fiber, parentContext)
+      : parentContext;
+  }
+
+  function scheduleRootUpdate(
+    current,
+    element,
+    currentTime,
+    expirationTime,
+    callback
+  ) {
+    {
+      if (
+        ReactDebugCurrentFiber.phase === "render" &&
+        ReactDebugCurrentFiber.current !== null &&
+        !didWarnAboutNestedUpdates
+      ) {
+        didWarnAboutNestedUpdates = true;
+        warning(
+          false,
+          "Render methods should be a pure function of props and state; " +
+            "triggering nested component updates from render is not allowed. " +
+            "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
+            "Check the render method of %s.",
+          getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
+        );
+      }
+    }
+
+    callback = callback === undefined ? null : callback;
+    {
+      !(callback === null || typeof callback === "function")
+        ? warning(
+            false,
+            "render(...): Expected the last optional `callback` argument to be a " +
+              "function. Instead received: %s.",
+            callback
+          )
+        : void 0;
+    }
+
+    var update = {
+      expirationTime: expirationTime,
+      partialState: { element: element },
+      callback: callback,
+      isReplace: false,
+      isForced: false,
+      capturedValue: null,
+      next: null
+    };
+    insertUpdateIntoFiber(current, update);
+    scheduleWork(current, expirationTime);
+
+    return expirationTime;
+  }
+
+  function updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    currentTime,
+    expirationTime,
+    callback
+  ) {
+    // TODO: If this is a nested container, this won't be the root.
+    var current = container.current;
+
+    {
+      if (ReactFiberInstrumentation_1.debugTool) {
+        if (current.alternate === null) {
+          ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
+        } else if (element === null) {
+          ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
+        } else {
+          ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
+        }
+      }
+    }
+
+    var context = getContextForSubtree(parentComponent);
+    if (container.context === null) {
+      container.context = context;
+    } else {
+      container.pendingContext = context;
+    }
+
+    return scheduleRootUpdate(
+      current,
+      element,
+      currentTime,
+      expirationTime,
+      callback
+    );
+  }
+
+  function findHostInstance(component) {
+    var fiber = get$1(component);
+    if (fiber === undefined) {
+      if (typeof component.render === "function") {
+        invariant(false, "Unable to find node on an unmounted component.");
+      } else {
+        invariant(
+          false,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        );
+      }
+    }
+    var hostFiber = findCurrentHostFiber(fiber);
+    if (hostFiber === null) {
+      return null;
+    }
+    return hostFiber.stateNode;
+  }
+
+  return {
+    createContainer: function(containerInfo, isAsync, hydrate) {
+      return createFiberRoot(containerInfo, isAsync, hydrate);
+    },
+    updateContainer: function(element, container, parentComponent, callback) {
+      var current = container.current;
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(current);
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        currentTime,
+        expirationTime,
+        callback
+      );
+    },
+    updateContainerAtExpirationTime: function(
+      element,
+      container,
+      parentComponent,
+      expirationTime,
+      callback
+    ) {
+      var currentTime = recalculateCurrentTime();
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        currentTime,
+        expirationTime,
+        callback
+      );
+    },
+
+    flushRoot: flushRoot,
+
+    requestWork: requestWork,
+
+    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+
+    batchedUpdates: batchedUpdates,
+
+    unbatchedUpdates: unbatchedUpdates,
+
+    deferredUpdates: deferredUpdates,
+
+    syncUpdates: syncUpdates,
+
+    interactiveUpdates: interactiveUpdates,
+
+    flushInteractiveUpdates: flushInteractiveUpdates,
+
+    flushControlled: flushControlled,
+
+    flushSync: flushSync,
+
+    getPublicRootInstance: function(container) {
+      var containerFiber = container.current;
+      if (!containerFiber.child) {
+        return null;
+      }
+      switch (containerFiber.child.tag) {
+        case HostComponent:
+          return getPublicInstance(containerFiber.child.stateNode);
+        default:
+          return containerFiber.child.stateNode;
+      }
+    },
+
+    findHostInstance: findHostInstance,
+
+    findHostInstanceWithNoPortals: function(fiber) {
+      var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
+      if (hostFiber === null) {
+        return null;
+      }
+      return hostFiber.stateNode;
+    },
+    injectIntoDevTools: function(devToolsConfig) {
+      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+
+      return injectInternals(
+        Object.assign({}, devToolsConfig, {
+          findHostInstanceByFiber: function(fiber) {
+            var hostFiber = findCurrentHostFiber(fiber);
+            if (hostFiber === null) {
+              return null;
+            }
+            return hostFiber.stateNode;
+          },
+          findFiberByHostInstance: function(instance) {
+            if (!findFiberByHostInstance) {
+              // Might not be implemented by the renderer.
+              return null;
+            }
+            return findFiberByHostInstance(instance);
+          }
+        })
+      );
+    }
+  };
+};
+
+var ReactFiberReconciler$2 = Object.freeze({
+  default: ReactFiberReconciler$1
+});
+
+var ReactFiberReconciler$3 =
+  (ReactFiberReconciler$2 && ReactFiberReconciler$1) || ReactFiberReconciler$2;
+
+// TODO: bundle Flow types with the package.
+
+// TODO: decide on the top-level export form.
+// This is hacky but makes it work with both Rollup and Jest.
+var reactReconciler = ReactFiberReconciler$3["default"]
+  ? ReactFiberReconciler$3["default"]
+  : ReactFiberReconciler$3;
+
+function _classCallCheck$1(instance, Constructor) {
+  if (!(instance instanceof Constructor)) {
+    throw new TypeError("Cannot call a class as a function");
+  }
+}
+
+// Modules provided by RN:
+/**
+ * This component defines the same methods as NativeMethodsMixin but without the
+ * findNodeHandle wrapper. This wrapper is unnecessary for HostComponent views
+ * and would also result in a circular require.js dependency (since
+ * ReactNativeFiber depends on this component and NativeMethodsMixin depends on
+ * ReactNativeFiber).
+ */
+
+var ReactNativeFiberHostComponent = (function() {
+  function ReactNativeFiberHostComponent(tag, viewConfig) {
+    _classCallCheck$1(this, ReactNativeFiberHostComponent);
+
+    this._nativeTag = tag;
+    this._children = [];
+    this.viewConfig = viewConfig;
+  }
+
+  ReactNativeFiberHostComponent.prototype.blur = function blur() {
+    TextInputState.blurTextInput(this._nativeTag);
+  };
+
+  ReactNativeFiberHostComponent.prototype.focus = function focus() {
+    TextInputState.focusTextInput(this._nativeTag);
+  };
+
+  ReactNativeFiberHostComponent.prototype.measure = function measure(callback) {
+    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+  };
+
+  ReactNativeFiberHostComponent.prototype.measureInWindow = function measureInWindow(
+    callback
+  ) {
+    UIManager.measureInWindow(
+      this._nativeTag,
+      mountSafeCallback(this, callback)
+    );
+  };
+
+  ReactNativeFiberHostComponent.prototype.measureLayout = function measureLayout(
+    relativeToNativeNode,
+    onSuccess,
+    onFail /* currently unused */
+  ) {
+    UIManager.measureLayout(
+      this._nativeTag,
+      relativeToNativeNode,
+      mountSafeCallback(this, onFail),
+      mountSafeCallback(this, onSuccess)
+    );
+  };
+
+  ReactNativeFiberHostComponent.prototype.setNativeProps = function setNativeProps(
+    nativeProps
+  ) {
+    {
+      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
+    }
+
+    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
+
+    // Avoid the overhead of bridge calls if there's no update.
+    // This is an expensive no-op for Android, and causes an unnecessary
+    // view invalidation for certain components (eg RCTTextInput) on iOS.
+    if (updatePayload != null) {
+      UIManager.updateView(
+        this._nativeTag,
+        this.viewConfig.uiViewClassName,
+        updatePayload
+      );
+    }
+  };
+
+  return ReactNativeFiberHostComponent;
+})();
+
+var hasNativePerformanceNow =
+  typeof performance === "object" && typeof performance.now === "function";
+
+var now = hasNativePerformanceNow
+  ? function() {
+      return performance.now();
+    }
+  : function() {
+      return Date.now();
+    };
+
+var scheduledCallback = null;
+var frameDeadline = 0;
+
+var frameDeadlineObject = {
+  timeRemaining: function() {
+    return frameDeadline - now();
+  },
+  didTimeout: false
+};
+
+function setTimeoutCallback() {
+  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
+  // React API probably changing to boolean rather than time remaining.
+  // Longer-term plan is to rewrite this using shared memory,
+  // And just return the value of the bit as the boolean.
+  frameDeadline = now() + 5;
+
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  if (callback !== null) {
+    callback(frameDeadlineObject);
+  }
+}
+
+// RN has a poor polyfill for requestIdleCallback so we aren't using it.
+// This implementation is only intended for short-term use anyway.
+// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
+function scheduleDeferredCallback(callback) {
+  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
+  scheduledCallback = callback;
+  return setTimeout(setTimeoutCallback, 1);
+}
+
+function cancelDeferredCallback(callbackID) {
+  scheduledCallback = null;
+  clearTimeout(callbackID);
+}
+
+// Modules provided by RN:
+// Counter for uniquely identifying views.
+// % 10 === 1 means it is a rootTag.
+// % 2 === 0 means it is a Fabric tag.
+var nextReactTag = 3;
+function allocateTag() {
+  var tag = nextReactTag;
+  if (tag % 10 === 1) {
+    tag += 2;
+  }
+  nextReactTag = tag + 2;
+  return tag;
+}
+
+function recursivelyUncacheFiberNode(node) {
+  if (typeof node === "number") {
+    // Leaf node (eg text)
+    uncacheFiberNode(node);
+  } else {
+    uncacheFiberNode(node._nativeTag);
+
+    node._children.forEach(recursivelyUncacheFiberNode);
+  }
+}
+
+var NativeRenderer = reactReconciler({
+  appendInitialChild: function(parentInstance, child) {
+    parentInstance._children.push(child);
+  },
+  createInstance: function(
+    type,
+    props,
+    rootContainerInstance,
+    hostContext,
+    internalInstanceHandle
+  ) {
+    var tag = allocateTag();
+    var viewConfig = ReactNativeViewConfigRegistry.get(type);
+
+    {
+      for (var key in viewConfig.validAttributes) {
+        if (props.hasOwnProperty(key)) {
+          deepFreezeAndThrowOnMutationInDev(props[key]);
+        }
+      }
+    }
+
+    var updatePayload = create(props, viewConfig.validAttributes);
+
+    UIManager.createView(
+      tag, // reactTag
+      viewConfig.uiViewClassName, // viewName
+      rootContainerInstance, // rootTag
+      updatePayload
+    );
+
+    var component = new ReactNativeFiberHostComponent(tag, viewConfig);
+
+    precacheFiberNode(internalInstanceHandle, tag);
+    updateFiberProps(tag, props);
+
+    // Not sure how to avoid this cast. Flow is okay if the component is defined
+    // in the same file but if it's external it can't see the types.
+    return component;
+  },
+  createTextInstance: function(
+    text,
+    rootContainerInstance,
+    hostContext,
+    internalInstanceHandle
+  ) {
+    var tag = allocateTag();
+
+    UIManager.createView(
+      tag, // reactTag
+      "RCTRawText", // viewName
+      rootContainerInstance, // rootTag
+      { text: text }
+    );
+
+    precacheFiberNode(internalInstanceHandle, tag);
+
+    return tag;
+  },
+  finalizeInitialChildren: function(
+    parentInstance,
+    type,
+    props,
+    rootContainerInstance
+  ) {
+    // Don't send a no-op message over the bridge.
+    if (parentInstance._children.length === 0) {
+      return false;
+    }
+
+    // Map from child objects to native tags.
+    // Either way we need to pass a copy of the Array to prevent it from being frozen.
+    var nativeTags = parentInstance._children.map(function(child) {
+      return typeof child === "number"
+        ? child // Leaf node (eg text)
+        : child._nativeTag;
+    });
+
+    UIManager.setChildren(
+      parentInstance._nativeTag, // containerTag
+      nativeTags
+    );
+
+    return false;
+  },
+  getRootHostContext: function() {
+    return emptyObject;
+  },
+  getChildHostContext: function() {
+    return emptyObject;
+  },
+  getPublicInstance: function(instance) {
+    return instance;
+  },
+
+  now: now,
+
+  prepareForCommit: function() {
+    // Noop
+  },
+  prepareUpdate: function(
+    instance,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    hostContext
+  ) {
+    return emptyObject;
+  },
+  resetAfterCommit: function() {
+    // Noop
+  },
+
+  scheduleDeferredCallback: scheduleDeferredCallback,
+  cancelDeferredCallback: cancelDeferredCallback,
+
+  shouldDeprioritizeSubtree: function(type, props) {
+    return false;
+  },
+  shouldSetTextContent: function(type, props) {
+    // TODO (bvaughn) Revisit this decision.
+    // Always returning false simplifies the createInstance() implementation,
+    // But creates an additional child Fiber for raw text children.
+    // No additional native views are created though.
+    // It's not clear to me which is better so I'm deferring for now.
+    // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
+    return false;
+  },
+
+  mutation: {
+    appendChild: function(parentInstance, child) {
+      var childTag = typeof child === "number" ? child : child._nativeTag;
+      var children = parentInstance._children;
+      var index = children.indexOf(child);
+
+      if (index >= 0) {
+        children.splice(index, 1);
+        children.push(child);
+
+        UIManager.manageChildren(
+          parentInstance._nativeTag, // containerTag
+          [index], // moveFromIndices
+          [children.length - 1], // moveToIndices
+          [], // addChildReactTags
+          [], // addAtIndices
+          []
+        );
+      } else {
+        children.push(child);
+
+        UIManager.manageChildren(
+          parentInstance._nativeTag, // containerTag
+          [], // moveFromIndices
+          [], // moveToIndices
+          [childTag], // addChildReactTags
+          [children.length - 1], // addAtIndices
+          []
+        );
+      }
+    },
+    appendChildToContainer: function(parentInstance, child) {
+      var childTag = typeof child === "number" ? child : child._nativeTag;
+      UIManager.setChildren(
+        parentInstance, // containerTag
+        [childTag]
+      );
+    },
+    commitTextUpdate: function(textInstance, oldText, newText) {
+      UIManager.updateView(
+        textInstance, // reactTag
+        "RCTRawText", // viewName
+        { text: newText }
+      );
+    },
+    commitMount: function(instance, type, newProps, internalInstanceHandle) {
+      // Noop
+    },
+    commitUpdate: function(
+      instance,
+      updatePayloadTODO,
+      type,
+      oldProps,
+      newProps,
+      internalInstanceHandle
+    ) {
+      var viewConfig = instance.viewConfig;
+
+      updateFiberProps(instance._nativeTag, newProps);
+
+      var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
+
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          instance._nativeTag, // reactTag
+          viewConfig.uiViewClassName, // viewName
+          updatePayload
+        );
+      }
+    },
+    insertBefore: function(parentInstance, child, beforeChild) {
+      var children = parentInstance._children;
+      var index = children.indexOf(child);
+
+      // Move existing child or add new child?
+      if (index >= 0) {
+        children.splice(index, 1);
+        var beforeChildIndex = children.indexOf(beforeChild);
+        children.splice(beforeChildIndex, 0, child);
+
+        UIManager.manageChildren(
+          parentInstance._nativeTag, // containerID
+          [index], // moveFromIndices
+          [beforeChildIndex], // moveToIndices
+          [], // addChildReactTags
+          [], // addAtIndices
+          []
+        );
+      } else {
+        var _beforeChildIndex = children.indexOf(beforeChild);
+        children.splice(_beforeChildIndex, 0, child);
+
+        var childTag = typeof child === "number" ? child : child._nativeTag;
+
+        UIManager.manageChildren(
+          parentInstance._nativeTag, // containerID
+          [], // moveFromIndices
+          [], // moveToIndices
+          [childTag], // addChildReactTags
+          [_beforeChildIndex], // addAtIndices
+          []
+        );
+      }
+    },
+    insertInContainerBefore: function(parentInstance, child, beforeChild) {
+      // TODO (bvaughn): Remove this check when...
+      // We create a wrapper object for the container in ReactNative render()
+      // Or we refactor to remove wrapper objects entirely.
+      // For more info on pros/cons see PR #8560 description.
+      invariant(
+        typeof parentInstance !== "number",
+        "Container does not support insertBefore operation"
+      );
+    },
+    removeChild: function(parentInstance, child) {
+      recursivelyUncacheFiberNode(child);
+      var children = parentInstance._children;
+      var index = children.indexOf(child);
+
+      children.splice(index, 1);
+
+      UIManager.manageChildren(
+        parentInstance._nativeTag, // containerID
+        [], // moveFromIndices
+        [], // moveToIndices
+        [], // addChildReactTags
+        [], // addAtIndices
+        [index]
+      );
+    },
+    removeChildFromContainer: function(parentInstance, child) {
+      recursivelyUncacheFiberNode(child);
+      UIManager.manageChildren(
+        parentInstance, // containerID
+        [], // moveFromIndices
+        [], // moveToIndices
+        [], // addChildReactTags
+        [], // addAtIndices
+        [0]
+      );
+    },
+    resetTextContent: function(instance) {
+      // Noop
+    }
+  }
+});
+
+// Module provided by RN:
+var getInspectorDataForViewTag = void 0;
+
+{
+  var traverseOwnerTreeUp = function(hierarchy, instance) {
+    if (instance) {
+      hierarchy.unshift(instance);
+      traverseOwnerTreeUp(hierarchy, instance._debugOwner);
+    }
+  };
+
+  var getOwnerHierarchy = function(instance) {
+    var hierarchy = [];
+    traverseOwnerTreeUp(hierarchy, instance);
+    return hierarchy;
+  };
+
+  var lastNonHostInstance = function(hierarchy) {
+    for (var i = hierarchy.length - 1; i > 1; i--) {
+      var instance = hierarchy[i];
+
+      if (instance.tag !== HostComponent) {
+        return instance;
+      }
+    }
+    return hierarchy[0];
+  };
+
+  var getHostProps = function(fiber) {
+    var host = findCurrentHostFiber(fiber);
+    if (host) {
+      return host.memoizedProps || emptyObject;
+    }
+    return emptyObject;
+  };
+
+  var getHostNode = function(fiber, findNodeHandle) {
+    var hostNode = void 0;
+    // look for children first for the hostNode
+    // as composite fibers do not have a hostNode
+    while (fiber) {
+      if (fiber.stateNode !== null && fiber.tag === HostComponent) {
+        hostNode = findNodeHandle(fiber.stateNode);
+      }
+      if (hostNode) {
+        return hostNode;
+      }
+      fiber = fiber.child;
+    }
+    return null;
+  };
+
+  var createHierarchy = function(fiberHierarchy) {
+    return fiberHierarchy.map(function(fiber) {
+      return {
+        name: getComponentName(fiber),
+        getInspectorData: function(findNodeHandle) {
+          return {
+            measure: function(callback) {
+              return UIManager.measure(
+                getHostNode(fiber, findNodeHandle),
+                callback
+              );
+            },
+            props: getHostProps(fiber),
+            source: fiber._debugSource
+          };
+        }
+      };
+    });
+  };
+
+  getInspectorDataForViewTag = function(viewTag) {
+    var closestInstance = getInstanceFromTag(viewTag);
+
+    // Handle case where user clicks outside of ReactNative
+    if (!closestInstance) {
+      return {
+        hierarchy: [],
+        props: emptyObject,
+        selection: null,
+        source: null
+      };
+    }
+
+    var fiber = findCurrentFiberUsingSlowPath(closestInstance);
+    var fiberHierarchy = getOwnerHierarchy(fiber);
+    var instance = lastNonHostInstance(fiberHierarchy);
+    var hierarchy = createHierarchy(fiberHierarchy);
+    var props = getHostProps(instance);
+    var source = instance._debugSource;
+    var selection = fiberHierarchy.indexOf(instance);
+
+    return {
+      hierarchy: hierarchy,
+      props: props,
+      selection: selection,
+      source: source
+    };
+  };
+}
+
+// Module provided by RN:
+var findHostInstance = NativeRenderer.findHostInstance;
+
+function findNodeHandle(componentOrHandle) {
+  {
+    var owner = ReactCurrentOwner.current;
+    if (owner !== null && owner.stateNode !== null) {
+      !owner.stateNode._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing findNodeHandle inside its render(). " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(owner) || "A component"
+          )
+        : void 0;
+
+      owner.stateNode._warnedAboutRefsInRender = true;
+    }
+  }
+  if (componentOrHandle == null) {
+    return null;
+  }
+  if (typeof componentOrHandle === "number") {
+    // Already a node handle
+    return componentOrHandle;
+  }
+  if (componentOrHandle._nativeTag) {
+    return componentOrHandle._nativeTag;
+  }
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag) {
+    return componentOrHandle.canonical._nativeTag;
+  }
+  var hostInstance = findHostInstance(componentOrHandle);
+  if (hostInstance == null) {
+    return hostInstance;
+  }
+  if (hostInstance.canonical) {
+    // Fabric
+    return hostInstance.canonical._nativeTag;
+  }
+  return hostInstance._nativeTag;
+}
+
+injection$2.injectRenderer(NativeRenderer);
+
+function computeComponentStackForErrorReporting(reactTag) {
+  var fiber = getInstanceFromTag(reactTag);
+  if (!fiber) {
+    return "";
+  }
+  return getStackAddendumByWorkInProgressFiber(fiber);
+}
+
+var roots = new Map();
+
+var ReactNativeRenderer = {
+  NativeComponent: ReactNativeComponent(findNodeHandle, findHostInstance),
+
+  findNodeHandle: findNodeHandle,
+
+  render: function(element, containerTag, callback) {
+    var root = roots.get(containerTag);
+
+    if (!root) {
+      // TODO (bvaughn): If we decide to keep the wrapper component,
+      // We could create a wrapper for containerTag as well to reduce special casing.
+      root = NativeRenderer.createContainer(containerTag, false, false);
+      roots.set(containerTag, root);
+    }
+    NativeRenderer.updateContainer(element, root, null, callback);
+
+    return NativeRenderer.getPublicRootInstance(root);
+  },
+  unmountComponentAtNode: function(containerTag) {
+    var root = roots.get(containerTag);
+    if (root) {
+      // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
+      NativeRenderer.updateContainer(null, root, null, function() {
+        roots["delete"](containerTag);
+      });
+    }
+  },
+  unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
+    ReactNativeRenderer.unmountComponentAtNode(containerTag);
+
+    // Call back into native to remove all of the subviews from this container
+    UIManager.removeRootView(containerTag);
+  },
+  createPortal: function(children, containerTag) {
+    var key =
+      arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : null;
+
+    return createPortal(children, containerTag, null, key);
+  },
+
+  unstable_batchedUpdates: batchedUpdates,
+
+  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
+    // Used as a mixin in many createClass-based components
+    NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
+    // Used by react-native-github/Libraries/ components
+    ReactNativeComponentTree: ReactNativeComponentTree, // ScrollResponder
+    computeComponentStackForErrorReporting: computeComponentStackForErrorReporting
+  }
+};
+
+{
+  // $FlowFixMe
+  Object.assign(
+    ReactNativeRenderer.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
+    {
+      // TODO: none of these work since Fiber. Remove these dependencies.
+      // Used by RCTRenderingPerf, Systrace:
+      ReactDebugTool: {
+        addHook: function() {},
+        removeHook: function() {}
+      },
+      // Used by ReactPerfStallHandler, RCTRenderingPerf:
+      ReactPerf: {
+        start: function() {},
+        stop: function() {},
+        printInclusive: function() {},
+        printWasted: function() {}
+      }
+    }
+  );
+}
+
+NativeRenderer.injectIntoDevTools({
+  findFiberByHostInstance: getInstanceFromTag,
+  getInspectorDataForViewTag: getInspectorDataForViewTag,
+  bundleType: 1,
+  version: ReactVersion,
+  rendererPackageName: "react-native-renderer"
+});
+
+var ReactNativeRenderer$2 = Object.freeze({
+  default: ReactNativeRenderer
+});
+
+var ReactNativeRenderer$3 =
+  (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
+
+// TODO: decide on the top-level export form.
+// This is hacky but makes it work with both Rollup and Jest.
+var reactNativeRenderer = ReactNativeRenderer$3["default"]
+  ? ReactNativeRenderer$3["default"]
+  : ReactNativeRenderer$3;
+
+module.exports = reactNativeRenderer;
+
+  })();
+}
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
new file mode 100644
index 000000000000..32b4729f3c96
--- /dev/null
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
@@ -0,0 +1,6311 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @noflow
+ * @providesModule ReactNativeRenderer-prod
+ * @preventMunge
+ */
+
+"use strict";
+require("InitializeCore");
+var invariant = require("fbjs/lib/invariant"),
+  emptyFunction = require("fbjs/lib/emptyFunction"),
+  ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
+  UIManager = require("UIManager"),
+  RCTEventEmitter = require("RCTEventEmitter"),
+  TextInputState = require("TextInputState"),
+  deepDiffer = require("deepDiffer"),
+  flattenStyle = require("flattenStyle"),
+  React = require("react"),
+  emptyObject = require("fbjs/lib/emptyObject"),
+  shallowEqual = require("fbjs/lib/shallowEqual"),
+  ExceptionsManager = require("ExceptionsManager");
+function invokeGuardedCallback(name, func, context, a, b, c, d, e, f) {
+  this._hasCaughtError = !1;
+  this._caughtError = null;
+  var funcArgs = Array.prototype.slice.call(arguments, 3);
+  try {
+    func.apply(context, funcArgs);
+  } catch (error) {
+    (this._caughtError = error), (this._hasCaughtError = !0);
+  }
+}
+var ReactErrorUtils = {
+  _caughtError: null,
+  _hasCaughtError: !1,
+  _rethrowError: null,
+  _hasRethrowError: !1,
+  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
+    invokeGuardedCallback.apply(ReactErrorUtils, arguments);
+  },
+  invokeGuardedCallbackAndCatchFirstError: function(
+    name,
+    func,
+    context,
+    a,
+    b,
+    c,
+    d,
+    e,
+    f
+  ) {
+    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
+    if (ReactErrorUtils.hasCaughtError()) {
+      var error = ReactErrorUtils.clearCaughtError();
+      ReactErrorUtils._hasRethrowError ||
+        ((ReactErrorUtils._hasRethrowError = !0),
+        (ReactErrorUtils._rethrowError = error));
+    }
+  },
+  rethrowCaughtError: function() {
+    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
+  },
+  hasCaughtError: function() {
+    return ReactErrorUtils._hasCaughtError;
+  },
+  clearCaughtError: function() {
+    if (ReactErrorUtils._hasCaughtError) {
+      var error = ReactErrorUtils._caughtError;
+      ReactErrorUtils._caughtError = null;
+      ReactErrorUtils._hasCaughtError = !1;
+      return error;
+    }
+    invariant(
+      !1,
+      "clearCaughtError was called but no error was captured. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+};
+function rethrowCaughtError() {
+  if (ReactErrorUtils._hasRethrowError) {
+    var error = ReactErrorUtils._rethrowError;
+    ReactErrorUtils._rethrowError = null;
+    ReactErrorUtils._hasRethrowError = !1;
+    throw error;
+  }
+}
+var eventPluginOrder = null,
+  namesToPlugins = {};
+function recomputePluginOrdering() {
+  if (eventPluginOrder)
+    for (var pluginName in namesToPlugins) {
+      var pluginModule = namesToPlugins[pluginName],
+        pluginIndex = eventPluginOrder.indexOf(pluginName);
+      invariant(
+        -1 < pluginIndex,
+        "EventPluginRegistry: Cannot inject event plugins that do not exist in the plugin ordering, `%s`.",
+        pluginName
+      );
+      if (!plugins[pluginIndex]) {
+        invariant(
+          pluginModule.extractEvents,
+          "EventPluginRegistry: Event plugins must implement an `extractEvents` method, but `%s` does not.",
+          pluginName
+        );
+        plugins[pluginIndex] = pluginModule;
+        pluginIndex = pluginModule.eventTypes;
+        for (var eventName in pluginIndex) {
+          var JSCompiler_inline_result = void 0;
+          var dispatchConfig = pluginIndex[eventName],
+            pluginModule$jscomp$0 = pluginModule,
+            eventName$jscomp$0 = eventName;
+          invariant(
+            !eventNameDispatchConfigs.hasOwnProperty(eventName$jscomp$0),
+            "EventPluginHub: More than one plugin attempted to publish the same event name, `%s`.",
+            eventName$jscomp$0
+          );
+          eventNameDispatchConfigs[eventName$jscomp$0] = dispatchConfig;
+          var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
+          if (phasedRegistrationNames) {
+            for (JSCompiler_inline_result in phasedRegistrationNames)
+              phasedRegistrationNames.hasOwnProperty(
+                JSCompiler_inline_result
+              ) &&
+                publishRegistrationName(
+                  phasedRegistrationNames[JSCompiler_inline_result],
+                  pluginModule$jscomp$0,
+                  eventName$jscomp$0
+                );
+            JSCompiler_inline_result = !0;
+          } else
+            dispatchConfig.registrationName
+              ? (publishRegistrationName(
+                  dispatchConfig.registrationName,
+                  pluginModule$jscomp$0,
+                  eventName$jscomp$0
+                ),
+                (JSCompiler_inline_result = !0))
+              : (JSCompiler_inline_result = !1);
+          invariant(
+            JSCompiler_inline_result,
+            "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
+            eventName,
+            pluginName
+          );
+        }
+      }
+    }
+}
+function publishRegistrationName(registrationName, pluginModule) {
+  invariant(
+    !registrationNameModules[registrationName],
+    "EventPluginHub: More than one plugin attempted to publish the same registration name, `%s`.",
+    registrationName
+  );
+  registrationNameModules[registrationName] = pluginModule;
+}
+var plugins = [],
+  eventNameDispatchConfigs = {},
+  registrationNameModules = {},
+  getFiberCurrentPropsFromNode = null,
+  getInstanceFromNode = null,
+  getNodeFromInstance = null;
+function isEndish(topLevelType) {
+  return (
+    "topMouseUp" === topLevelType ||
+    "topTouchEnd" === topLevelType ||
+    "topTouchCancel" === topLevelType
+  );
+}
+function isMoveish(topLevelType) {
+  return "topMouseMove" === topLevelType || "topTouchMove" === topLevelType;
+}
+function isStartish(topLevelType) {
+  return "topMouseDown" === topLevelType || "topTouchStart" === topLevelType;
+}
+function executeDispatch(event, simulated, listener, inst) {
+  simulated = event.type || "unknown-event";
+  event.currentTarget = getNodeFromInstance(inst);
+  ReactErrorUtils.invokeGuardedCallbackAndCatchFirstError(
+    simulated,
+    listener,
+    void 0,
+    event
+  );
+  event.currentTarget = null;
+}
+function executeDirectDispatch(event) {
+  var dispatchListener = event._dispatchListeners,
+    dispatchInstance = event._dispatchInstances;
+  invariant(
+    !Array.isArray(dispatchListener),
+    "executeDirectDispatch(...): Invalid `event`."
+  );
+  event.currentTarget = dispatchListener
+    ? getNodeFromInstance(dispatchInstance)
+    : null;
+  dispatchListener = dispatchListener ? dispatchListener(event) : null;
+  event.currentTarget = null;
+  event._dispatchListeners = null;
+  event._dispatchInstances = null;
+  return dispatchListener;
+}
+function accumulateInto(current, next) {
+  invariant(
+    null != next,
+    "accumulateInto(...): Accumulated items must not be null or undefined."
+  );
+  if (null == current) return next;
+  if (Array.isArray(current)) {
+    if (Array.isArray(next)) return current.push.apply(current, next), current;
+    current.push(next);
+    return current;
+  }
+  return Array.isArray(next) ? [current].concat(next) : [current, next];
+}
+function forEachAccumulated(arr, cb, scope) {
+  Array.isArray(arr) ? arr.forEach(cb, scope) : arr && cb.call(scope, arr);
+}
+var eventQueue = null;
+function executeDispatchesAndReleaseTopLevel(e) {
+  if (e) {
+    var dispatchListeners = e._dispatchListeners,
+      dispatchInstances = e._dispatchInstances;
+    if (Array.isArray(dispatchListeners))
+      for (
+        var i = 0;
+        i < dispatchListeners.length && !e.isPropagationStopped();
+        i++
+      )
+        executeDispatch(e, !1, dispatchListeners[i], dispatchInstances[i]);
+    else
+      dispatchListeners &&
+        executeDispatch(e, !1, dispatchListeners, dispatchInstances);
+    e._dispatchListeners = null;
+    e._dispatchInstances = null;
+    e.isPersistent() || e.constructor.release(e);
+  }
+}
+var injection = {
+  injectEventPluginOrder: function(injectedEventPluginOrder) {
+    invariant(
+      !eventPluginOrder,
+      "EventPluginRegistry: Cannot inject event plugin ordering more than once. You are likely trying to load more than one copy of React."
+    );
+    eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
+    recomputePluginOrdering();
+  },
+  injectEventPluginsByName: function(injectedNamesToPlugins) {
+    var isOrderingDirty = !1,
+      pluginName;
+    for (pluginName in injectedNamesToPlugins)
+      if (injectedNamesToPlugins.hasOwnProperty(pluginName)) {
+        var pluginModule = injectedNamesToPlugins[pluginName];
+        (namesToPlugins.hasOwnProperty(pluginName) &&
+          namesToPlugins[pluginName] === pluginModule) ||
+          (invariant(
+            !namesToPlugins[pluginName],
+            "EventPluginRegistry: Cannot inject two different event plugins using the same name, `%s`.",
+            pluginName
+          ),
+          (namesToPlugins[pluginName] = pluginModule),
+          (isOrderingDirty = !0));
+      }
+    isOrderingDirty && recomputePluginOrdering();
+  }
+};
+function getListener(inst, registrationName) {
+  var listener = inst.stateNode;
+  if (!listener) return null;
+  var props = getFiberCurrentPropsFromNode(listener);
+  if (!props) return null;
+  listener = props[registrationName];
+  a: switch (registrationName) {
+    case "onClick":
+    case "onClickCapture":
+    case "onDoubleClick":
+    case "onDoubleClickCapture":
+    case "onMouseDown":
+    case "onMouseDownCapture":
+    case "onMouseMove":
+    case "onMouseMoveCapture":
+    case "onMouseUp":
+    case "onMouseUpCapture":
+      (props = !props.disabled) ||
+        ((inst = inst.type),
+        (props = !(
+          "button" === inst ||
+          "input" === inst ||
+          "select" === inst ||
+          "textarea" === inst
+        )));
+      inst = !props;
+      break a;
+    default:
+      inst = !1;
+  }
+  if (inst) return null;
+  invariant(
+    !listener || "function" === typeof listener,
+    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
+    registrationName,
+    typeof listener
+  );
+  return listener;
+}
+function getParent(inst) {
+  do inst = inst["return"];
+  while (inst && 5 !== inst.tag);
+  return inst ? inst : null;
+}
+function traverseTwoPhase(inst, fn, arg) {
+  for (var path = []; inst; ) path.push(inst), (inst = getParent(inst));
+  for (inst = path.length; 0 < inst--; ) fn(path[inst], "captured", arg);
+  for (inst = 0; inst < path.length; inst++) fn(path[inst], "bubbled", arg);
+}
+function accumulateDirectionalDispatches(inst, phase, event) {
+  if (
+    (phase = getListener(
+      inst,
+      event.dispatchConfig.phasedRegistrationNames[phase]
+    ))
+  )
+    (event._dispatchListeners = accumulateInto(
+      event._dispatchListeners,
+      phase
+    )),
+      (event._dispatchInstances = accumulateInto(
+        event._dispatchInstances,
+        inst
+      ));
+}
+function accumulateTwoPhaseDispatchesSingle(event) {
+  event &&
+    event.dispatchConfig.phasedRegistrationNames &&
+    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
+}
+function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
+  if (event && event.dispatchConfig.phasedRegistrationNames) {
+    var targetInst = event._targetInst;
+    targetInst = targetInst ? getParent(targetInst) : null;
+    traverseTwoPhase(targetInst, accumulateDirectionalDispatches, event);
+  }
+}
+function accumulateDirectDispatchesSingle(event) {
+  if (event && event.dispatchConfig.registrationName) {
+    var inst = event._targetInst;
+    if (inst && event && event.dispatchConfig.registrationName) {
+      var listener = getListener(inst, event.dispatchConfig.registrationName);
+      listener &&
+        ((event._dispatchListeners = accumulateInto(
+          event._dispatchListeners,
+          listener
+        )),
+        (event._dispatchInstances = accumulateInto(
+          event._dispatchInstances,
+          inst
+        )));
+    }
+  }
+}
+var shouldBeReleasedProperties = "dispatchConfig _targetInst nativeEvent isDefaultPrevented isPropagationStopped _dispatchListeners _dispatchInstances".split(
+    " "
+  ),
+  EventInterface = {
+    type: null,
+    target: null,
+    currentTarget: emptyFunction.thatReturnsNull,
+    eventPhase: null,
+    bubbles: null,
+    cancelable: null,
+    timeStamp: function(event) {
+      return event.timeStamp || Date.now();
+    },
+    defaultPrevented: null,
+    isTrusted: null
+  };
+function SyntheticEvent(
+  dispatchConfig,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  this.dispatchConfig = dispatchConfig;
+  this._targetInst = targetInst;
+  this.nativeEvent = nativeEvent;
+  dispatchConfig = this.constructor.Interface;
+  for (var propName in dispatchConfig)
+    dispatchConfig.hasOwnProperty(propName) &&
+      ((targetInst = dispatchConfig[propName])
+        ? (this[propName] = targetInst(nativeEvent))
+        : "target" === propName
+          ? (this.target = nativeEventTarget)
+          : (this[propName] = nativeEvent[propName]));
+  this.isDefaultPrevented = (null != nativeEvent.defaultPrevented
+  ? nativeEvent.defaultPrevented
+  : !1 === nativeEvent.returnValue)
+    ? emptyFunction.thatReturnsTrue
+    : emptyFunction.thatReturnsFalse;
+  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
+  return this;
+}
+Object.assign(SyntheticEvent.prototype, {
+  preventDefault: function() {
+    this.defaultPrevented = !0;
+    var event = this.nativeEvent;
+    event &&
+      (event.preventDefault
+        ? event.preventDefault()
+        : "unknown" !== typeof event.returnValue && (event.returnValue = !1),
+      (this.isDefaultPrevented = emptyFunction.thatReturnsTrue));
+  },
+  stopPropagation: function() {
+    var event = this.nativeEvent;
+    event &&
+      (event.stopPropagation
+        ? event.stopPropagation()
+        : "unknown" !== typeof event.cancelBubble && (event.cancelBubble = !0),
+      (this.isPropagationStopped = emptyFunction.thatReturnsTrue));
+  },
+  persist: function() {
+    this.isPersistent = emptyFunction.thatReturnsTrue;
+  },
+  isPersistent: emptyFunction.thatReturnsFalse,
+  destructor: function() {
+    var Interface = this.constructor.Interface,
+      propName;
+    for (propName in Interface) this[propName] = null;
+    for (
+      Interface = 0;
+      Interface < shouldBeReleasedProperties.length;
+      Interface++
+    )
+      this[shouldBeReleasedProperties[Interface]] = null;
+  }
+});
+SyntheticEvent.Interface = EventInterface;
+SyntheticEvent.extend = function(Interface) {
+  function E() {}
+  function Class() {
+    return Super.apply(this, arguments);
+  }
+  var Super = this;
+  E.prototype = Super.prototype;
+  var prototype = new E();
+  Object.assign(prototype, Class.prototype);
+  Class.prototype = prototype;
+  Class.prototype.constructor = Class;
+  Class.Interface = Object.assign({}, Super.Interface, Interface);
+  Class.extend = Super.extend;
+  addEventPoolingTo(Class);
+  return Class;
+};
+addEventPoolingTo(SyntheticEvent);
+function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
+  if (this.eventPool.length) {
+    var instance = this.eventPool.pop();
+    this.call(instance, dispatchConfig, targetInst, nativeEvent, nativeInst);
+    return instance;
+  }
+  return new this(dispatchConfig, targetInst, nativeEvent, nativeInst);
+}
+function releasePooledEvent(event) {
+  invariant(
+    event instanceof this,
+    "Trying to release an event instance  into a pool of a different type."
+  );
+  event.destructor();
+  10 > this.eventPool.length && this.eventPool.push(event);
+}
+function addEventPoolingTo(EventConstructor) {
+  EventConstructor.eventPool = [];
+  EventConstructor.getPooled = getPooledEvent;
+  EventConstructor.release = releasePooledEvent;
+}
+var ResponderSyntheticEvent = SyntheticEvent.extend({
+    touchHistory: function() {
+      return null;
+    }
+  }),
+  touchBank = [],
+  touchHistory = {
+    touchBank: touchBank,
+    numberActiveTouches: 0,
+    indexOfSingleActiveTouch: -1,
+    mostRecentTimeStamp: 0
+  };
+function timestampForTouch(touch) {
+  return touch.timeStamp || touch.timestamp;
+}
+function getTouchIdentifier(_ref) {
+  _ref = _ref.identifier;
+  invariant(null != _ref, "Touch object is missing identifier.");
+  return _ref;
+}
+function recordTouchStart(touch) {
+  var identifier = getTouchIdentifier(touch),
+    touchRecord = touchBank[identifier];
+  touchRecord
+    ? ((touchRecord.touchActive = !0),
+      (touchRecord.startPageX = touch.pageX),
+      (touchRecord.startPageY = touch.pageY),
+      (touchRecord.startTimeStamp = timestampForTouch(touch)),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchRecord.previousPageX = touch.pageX),
+      (touchRecord.previousPageY = touch.pageY),
+      (touchRecord.previousTimeStamp = timestampForTouch(touch)))
+    : ((touchRecord = {
+        touchActive: !0,
+        startPageX: touch.pageX,
+        startPageY: touch.pageY,
+        startTimeStamp: timestampForTouch(touch),
+        currentPageX: touch.pageX,
+        currentPageY: touch.pageY,
+        currentTimeStamp: timestampForTouch(touch),
+        previousPageX: touch.pageX,
+        previousPageY: touch.pageY,
+        previousTimeStamp: timestampForTouch(touch)
+      }),
+      (touchBank[identifier] = touchRecord));
+  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+}
+function recordTouchMove(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  touchRecord
+    ? ((touchRecord.touchActive = !0),
+      (touchRecord.previousPageX = touchRecord.currentPageX),
+      (touchRecord.previousPageY = touchRecord.currentPageY),
+      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
+    : console.error(
+        "Cannot record touch move without a touch start.\nTouch Move: %s\n",
+        "Touch Bank: %s",
+        printTouch(touch),
+        printTouchBank()
+      );
+}
+function recordTouchEnd(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  touchRecord
+    ? ((touchRecord.touchActive = !1),
+      (touchRecord.previousPageX = touchRecord.currentPageX),
+      (touchRecord.previousPageY = touchRecord.currentPageY),
+      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
+    : console.error(
+        "Cannot record touch end without a touch start.\nTouch End: %s\n",
+        "Touch Bank: %s",
+        printTouch(touch),
+        printTouchBank()
+      );
+}
+function printTouch(touch) {
+  return JSON.stringify({
+    identifier: touch.identifier,
+    pageX: touch.pageX,
+    pageY: touch.pageY,
+    timestamp: timestampForTouch(touch)
+  });
+}
+function printTouchBank() {
+  var printed = JSON.stringify(touchBank.slice(0, 20));
+  20 < touchBank.length &&
+    (printed += " (original size: " + touchBank.length + ")");
+  return printed;
+}
+var ResponderTouchHistoryStore = {
+  recordTouchTrack: function(topLevelType, nativeEvent) {
+    if (isMoveish(topLevelType))
+      nativeEvent.changedTouches.forEach(recordTouchMove);
+    else if (isStartish(topLevelType))
+      nativeEvent.changedTouches.forEach(recordTouchStart),
+        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+        1 === touchHistory.numberActiveTouches &&
+          (touchHistory.indexOfSingleActiveTouch =
+            nativeEvent.touches[0].identifier);
+    else if (
+      isEndish(topLevelType) &&
+      (nativeEvent.changedTouches.forEach(recordTouchEnd),
+      (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+      1 === touchHistory.numberActiveTouches)
+    )
+      for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
+        if (
+          ((nativeEvent = touchBank[topLevelType]),
+          null != nativeEvent && nativeEvent.touchActive)
+        ) {
+          touchHistory.indexOfSingleActiveTouch = topLevelType;
+          break;
+        }
+  },
+  touchHistory: touchHistory
+};
+function accumulate(current, next) {
+  invariant(
+    null != next,
+    "accumulate(...): Accumulated items must be not be null or undefined."
+  );
+  return null == current
+    ? next
+    : Array.isArray(current)
+      ? current.concat(next)
+      : Array.isArray(next) ? [current].concat(next) : [current, next];
+}
+var responderInst = null,
+  trackedTouchCount = 0,
+  previousActiveTouches = 0;
+function changeResponder(nextResponderInst, blockHostResponder) {
+  var oldResponderInst = responderInst;
+  responderInst = nextResponderInst;
+  if (null !== ResponderEventPlugin.GlobalResponderHandler)
+    ResponderEventPlugin.GlobalResponderHandler.onChange(
+      oldResponderInst,
+      nextResponderInst,
+      blockHostResponder
+    );
+}
+var eventTypes$1 = {
+    startShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onStartShouldSetResponder",
+        captured: "onStartShouldSetResponderCapture"
+      }
+    },
+    scrollShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onScrollShouldSetResponder",
+        captured: "onScrollShouldSetResponderCapture"
+      }
+    },
+    selectionChangeShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onSelectionChangeShouldSetResponder",
+        captured: "onSelectionChangeShouldSetResponderCapture"
+      }
+    },
+    moveShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onMoveShouldSetResponder",
+        captured: "onMoveShouldSetResponderCapture"
+      }
+    },
+    responderStart: { registrationName: "onResponderStart" },
+    responderMove: { registrationName: "onResponderMove" },
+    responderEnd: { registrationName: "onResponderEnd" },
+    responderRelease: { registrationName: "onResponderRelease" },
+    responderTerminationRequest: {
+      registrationName: "onResponderTerminationRequest"
+    },
+    responderGrant: { registrationName: "onResponderGrant" },
+    responderReject: { registrationName: "onResponderReject" },
+    responderTerminate: { registrationName: "onResponderTerminate" }
+  },
+  ResponderEventPlugin = {
+    _getResponder: function() {
+      return responderInst;
+    },
+    eventTypes: eventTypes$1,
+    extractEvents: function(
+      topLevelType,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    ) {
+      if (isStartish(topLevelType)) trackedTouchCount += 1;
+      else if (isEndish(topLevelType))
+        if (0 <= trackedTouchCount) --trackedTouchCount;
+        else
+          return (
+            console.error(
+              "Ended a touch event which was not counted in `trackedTouchCount`."
+            ),
+            null
+          );
+      ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
+      if (
+        targetInst &&
+        (("topScroll" === topLevelType && !nativeEvent.responderIgnoreScroll) ||
+          (0 < trackedTouchCount && "topSelectionChange" === topLevelType) ||
+          isStartish(topLevelType) ||
+          isMoveish(topLevelType))
+      ) {
+        var JSCompiler_temp = isStartish(topLevelType)
+          ? eventTypes$1.startShouldSetResponder
+          : isMoveish(topLevelType)
+            ? eventTypes$1.moveShouldSetResponder
+            : "topSelectionChange" === topLevelType
+              ? eventTypes$1.selectionChangeShouldSetResponder
+              : eventTypes$1.scrollShouldSetResponder;
+        if (responderInst)
+          b: {
+            var JSCompiler_temp$jscomp$0 = responderInst;
+            for (
+              var depthA = 0, tempA = JSCompiler_temp$jscomp$0;
+              tempA;
+              tempA = getParent(tempA)
+            )
+              depthA++;
+            tempA = 0;
+            for (var tempB = targetInst; tempB; tempB = getParent(tempB))
+              tempA++;
+            for (; 0 < depthA - tempA; )
+              (JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0)),
+                depthA--;
+            for (; 0 < tempA - depthA; )
+              (targetInst = getParent(targetInst)), tempA--;
+            for (; depthA--; ) {
+              if (
+                JSCompiler_temp$jscomp$0 === targetInst ||
+                JSCompiler_temp$jscomp$0 === targetInst.alternate
+              )
+                break b;
+              JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0);
+              targetInst = getParent(targetInst);
+            }
+            JSCompiler_temp$jscomp$0 = null;
+          }
+        else JSCompiler_temp$jscomp$0 = targetInst;
+        targetInst = JSCompiler_temp$jscomp$0 === responderInst;
+        JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
+          JSCompiler_temp,
+          JSCompiler_temp$jscomp$0,
+          nativeEvent,
+          nativeEventTarget
+        );
+        JSCompiler_temp$jscomp$0.touchHistory =
+          ResponderTouchHistoryStore.touchHistory;
+        targetInst
+          ? forEachAccumulated(
+              JSCompiler_temp$jscomp$0,
+              accumulateTwoPhaseDispatchesSingleSkipTarget
+            )
+          : forEachAccumulated(
+              JSCompiler_temp$jscomp$0,
+              accumulateTwoPhaseDispatchesSingle
+            );
+        b: {
+          JSCompiler_temp = JSCompiler_temp$jscomp$0._dispatchListeners;
+          targetInst = JSCompiler_temp$jscomp$0._dispatchInstances;
+          if (Array.isArray(JSCompiler_temp))
+            for (
+              depthA = 0;
+              depthA < JSCompiler_temp.length &&
+              !JSCompiler_temp$jscomp$0.isPropagationStopped();
+              depthA++
+            ) {
+              if (
+                JSCompiler_temp[depthA](
+                  JSCompiler_temp$jscomp$0,
+                  targetInst[depthA]
+                )
+              ) {
+                JSCompiler_temp = targetInst[depthA];
+                break b;
+              }
+            }
+          else if (
+            JSCompiler_temp &&
+            JSCompiler_temp(JSCompiler_temp$jscomp$0, targetInst)
+          ) {
+            JSCompiler_temp = targetInst;
+            break b;
+          }
+          JSCompiler_temp = null;
+        }
+        JSCompiler_temp$jscomp$0._dispatchInstances = null;
+        JSCompiler_temp$jscomp$0._dispatchListeners = null;
+        JSCompiler_temp$jscomp$0.isPersistent() ||
+          JSCompiler_temp$jscomp$0.constructor.release(
+            JSCompiler_temp$jscomp$0
+          );
+        JSCompiler_temp && JSCompiler_temp !== responderInst
+          ? ((JSCompiler_temp$jscomp$0 = void 0),
+            (targetInst = ResponderSyntheticEvent.getPooled(
+              eventTypes$1.responderGrant,
+              JSCompiler_temp,
+              nativeEvent,
+              nativeEventTarget
+            )),
+            (targetInst.touchHistory = ResponderTouchHistoryStore.touchHistory),
+            forEachAccumulated(targetInst, accumulateDirectDispatchesSingle),
+            (depthA = !0 === executeDirectDispatch(targetInst)),
+            responderInst
+              ? ((tempA = ResponderSyntheticEvent.getPooled(
+                  eventTypes$1.responderTerminationRequest,
+                  responderInst,
+                  nativeEvent,
+                  nativeEventTarget
+                )),
+                (tempA.touchHistory = ResponderTouchHistoryStore.touchHistory),
+                forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
+                (tempB =
+                  !tempA._dispatchListeners || executeDirectDispatch(tempA)),
+                tempA.isPersistent() || tempA.constructor.release(tempA),
+                tempB
+                  ? ((tempA = ResponderSyntheticEvent.getPooled(
+                      eventTypes$1.responderTerminate,
+                      responderInst,
+                      nativeEvent,
+                      nativeEventTarget
+                    )),
+                    (tempA.touchHistory =
+                      ResponderTouchHistoryStore.touchHistory),
+                    forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
+                    (JSCompiler_temp$jscomp$0 = accumulate(
+                      JSCompiler_temp$jscomp$0,
+                      [targetInst, tempA]
+                    )),
+                    changeResponder(JSCompiler_temp, depthA))
+                  : ((JSCompiler_temp = ResponderSyntheticEvent.getPooled(
+                      eventTypes$1.responderReject,
+                      JSCompiler_temp,
+                      nativeEvent,
+                      nativeEventTarget
+                    )),
+                    (JSCompiler_temp.touchHistory =
+                      ResponderTouchHistoryStore.touchHistory),
+                    forEachAccumulated(
+                      JSCompiler_temp,
+                      accumulateDirectDispatchesSingle
+                    ),
+                    (JSCompiler_temp$jscomp$0 = accumulate(
+                      JSCompiler_temp$jscomp$0,
+                      JSCompiler_temp
+                    ))))
+              : ((JSCompiler_temp$jscomp$0 = accumulate(
+                  JSCompiler_temp$jscomp$0,
+                  targetInst
+                )),
+                changeResponder(JSCompiler_temp, depthA)),
+            (JSCompiler_temp = JSCompiler_temp$jscomp$0))
+          : (JSCompiler_temp = null);
+      } else JSCompiler_temp = null;
+      JSCompiler_temp$jscomp$0 = responderInst && isStartish(topLevelType);
+      targetInst = responderInst && isMoveish(topLevelType);
+      depthA = responderInst && isEndish(topLevelType);
+      if (
+        (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
+          ? eventTypes$1.responderStart
+          : targetInst
+            ? eventTypes$1.responderMove
+            : depthA ? eventTypes$1.responderEnd : null)
+      )
+        (JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
+          JSCompiler_temp$jscomp$0,
+          responderInst,
+          nativeEvent,
+          nativeEventTarget
+        )),
+          (JSCompiler_temp$jscomp$0.touchHistory =
+            ResponderTouchHistoryStore.touchHistory),
+          forEachAccumulated(
+            JSCompiler_temp$jscomp$0,
+            accumulateDirectDispatchesSingle
+          ),
+          (JSCompiler_temp = accumulate(
+            JSCompiler_temp,
+            JSCompiler_temp$jscomp$0
+          ));
+      JSCompiler_temp$jscomp$0 =
+        responderInst && "topTouchCancel" === topLevelType;
+      if (
+        (topLevelType =
+          responderInst && !JSCompiler_temp$jscomp$0 && isEndish(topLevelType))
+      )
+        a: {
+          if ((topLevelType = nativeEvent.touches) && 0 !== topLevelType.length)
+            for (targetInst = 0; targetInst < topLevelType.length; targetInst++)
+              if (
+                ((depthA = topLevelType[targetInst].target),
+                null !== depthA && void 0 !== depthA && 0 !== depthA)
+              ) {
+                tempA = getInstanceFromNode(depthA);
+                b: {
+                  for (depthA = responderInst; tempA; ) {
+                    if (depthA === tempA || depthA === tempA.alternate) {
+                      depthA = !0;
+                      break b;
+                    }
+                    tempA = getParent(tempA);
+                  }
+                  depthA = !1;
+                }
+                if (depthA) {
+                  topLevelType = !1;
+                  break a;
+                }
+              }
+          topLevelType = !0;
+        }
+      if (
+        (topLevelType = JSCompiler_temp$jscomp$0
+          ? eventTypes$1.responderTerminate
+          : topLevelType ? eventTypes$1.responderRelease : null)
+      )
+        (nativeEvent = ResponderSyntheticEvent.getPooled(
+          topLevelType,
+          responderInst,
+          nativeEvent,
+          nativeEventTarget
+        )),
+          (nativeEvent.touchHistory = ResponderTouchHistoryStore.touchHistory),
+          forEachAccumulated(nativeEvent, accumulateDirectDispatchesSingle),
+          (JSCompiler_temp = accumulate(JSCompiler_temp, nativeEvent)),
+          changeResponder(null);
+      nativeEvent = ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
+      if (
+        ResponderEventPlugin.GlobalInteractionHandler &&
+        nativeEvent !== previousActiveTouches
+      )
+        ResponderEventPlugin.GlobalInteractionHandler.onChange(nativeEvent);
+      previousActiveTouches = nativeEvent;
+      return JSCompiler_temp;
+    },
+    GlobalResponderHandler: null,
+    GlobalInteractionHandler: null,
+    injection: {
+      injectGlobalResponderHandler: function(GlobalResponderHandler) {
+        ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
+      },
+      injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
+        ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
+      }
+    }
+  },
+  customBubblingEventTypes$1 =
+    ReactNativeViewConfigRegistry.customBubblingEventTypes,
+  customDirectEventTypes$1 =
+    ReactNativeViewConfigRegistry.customDirectEventTypes,
+  ReactNativeBridgeEventPlugin = {
+    eventTypes: ReactNativeViewConfigRegistry.eventTypes,
+    extractEvents: function(
+      topLevelType,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    ) {
+      if (null == targetInst) return null;
+      var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType],
+        directDispatchConfig = customDirectEventTypes$1[topLevelType];
+      invariant(
+        bubbleDispatchConfig || directDispatchConfig,
+        'Unsupported top level event type "%s" dispatched',
+        topLevelType
+      );
+      topLevelType = SyntheticEvent.getPooled(
+        bubbleDispatchConfig || directDispatchConfig,
+        targetInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      if (bubbleDispatchConfig)
+        forEachAccumulated(topLevelType, accumulateTwoPhaseDispatchesSingle);
+      else if (directDispatchConfig)
+        forEachAccumulated(topLevelType, accumulateDirectDispatchesSingle);
+      else return null;
+      return topLevelType;
+    }
+  },
+  instanceCache = {},
+  instanceProps = {};
+function uncacheFiberNode(tag) {
+  delete instanceCache[tag];
+  delete instanceProps[tag];
+}
+function getInstanceFromTag(tag) {
+  return "number" === typeof tag ? instanceCache[tag] || null : tag;
+}
+var ReactNativeComponentTree = Object.freeze({
+  precacheFiberNode: function(hostInst, tag) {
+    instanceCache[tag] = hostInst;
+  },
+  uncacheFiberNode: uncacheFiberNode,
+  getClosestInstanceFromNode: getInstanceFromTag,
+  getInstanceFromNode: getInstanceFromTag,
+  getNodeFromInstance: function(inst) {
+    var tag = inst.stateNode._nativeTag;
+    void 0 === tag && (tag = inst.stateNode.canonical._nativeTag);
+    invariant(tag, "All native instances should have a tag.");
+    return tag;
+  },
+  getFiberCurrentPropsFromNode: function(stateNode) {
+    return instanceProps[stateNode._nativeTag] || null;
+  },
+  updateFiberProps: function(tag, props) {
+    instanceProps[tag] = props;
+  }
+});
+injection.injectEventPluginOrder([
+  "ResponderEventPlugin",
+  "ReactNativeBridgeEventPlugin"
+]);
+getFiberCurrentPropsFromNode =
+  ReactNativeComponentTree.getFiberCurrentPropsFromNode;
+getInstanceFromNode = ReactNativeComponentTree.getInstanceFromNode;
+getNodeFromInstance = ReactNativeComponentTree.getNodeFromInstance;
+ResponderEventPlugin.injection.injectGlobalResponderHandler({
+  onChange: function(from, to, blockNativeResponder) {
+    null !== to
+      ? UIManager.setJSResponder(to.stateNode._nativeTag, blockNativeResponder)
+      : UIManager.clearJSResponder();
+  }
+});
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
+var restoreTarget = null,
+  restoreQueue = null;
+function restoreStateOfTarget(target) {
+  if ((target = getInstanceFromNode(target))) {
+    invariant(
+      null,
+      "Fiber needs to be injected to handle a fiber target for controlled events. This error is likely caused by a bug in React. Please file an issue."
+    );
+    var props = getFiberCurrentPropsFromNode(target.stateNode);
+    null.restoreControlledState(target.stateNode, target.type, props);
+  }
+}
+function _batchedUpdates(fn, bookkeeping) {
+  return fn(bookkeeping);
+}
+function _flushInteractiveUpdates() {}
+var isBatching = !1;
+function batchedUpdates(fn, bookkeeping) {
+  if (isBatching) return fn(bookkeeping);
+  isBatching = !0;
+  try {
+    return _batchedUpdates(fn, bookkeeping);
+  } finally {
+    if (((isBatching = !1), null !== restoreTarget || null !== restoreQueue))
+      if (
+        (_flushInteractiveUpdates(),
+        restoreTarget &&
+          ((bookkeeping = restoreTarget),
+          (fn = restoreQueue),
+          (restoreQueue = restoreTarget = null),
+          restoreStateOfTarget(bookkeeping),
+          fn))
+      )
+        for (bookkeeping = 0; bookkeeping < fn.length; bookkeeping++)
+          restoreStateOfTarget(fn[bookkeeping]);
+  }
+}
+var EMPTY_NATIVE_EVENT = {};
+function _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam) {
+  var nativeEvent = nativeEventParam || EMPTY_NATIVE_EVENT,
+    inst = getInstanceFromTag(rootNodeID);
+  batchedUpdates(function() {
+    var events = nativeEvent.target;
+    for (var events$jscomp$0 = null, i = 0; i < plugins.length; i++) {
+      var possiblePlugin = plugins[i];
+      possiblePlugin &&
+        (possiblePlugin = possiblePlugin.extractEvents(
+          topLevelType,
+          inst,
+          nativeEvent,
+          events
+        )) &&
+        (events$jscomp$0 = accumulateInto(events$jscomp$0, possiblePlugin));
+    }
+    events = events$jscomp$0;
+    null !== events && (eventQueue = accumulateInto(eventQueue, events));
+    events = eventQueue;
+    eventQueue = null;
+    events &&
+      (forEachAccumulated(events, executeDispatchesAndReleaseTopLevel),
+      invariant(
+        !eventQueue,
+        "processEventQueue(): Additional events were enqueued while processing an event queue. Support for this has not yet been implemented."
+      ),
+      ReactErrorUtils.rethrowCaughtError());
+  });
+}
+var ReactNativeEventEmitter = Object.freeze({
+  getListener: getListener,
+  registrationNames: registrationNameModules,
+  _receiveRootNodeIDEvent: _receiveRootNodeIDEvent,
+  receiveEvent: function(rootNodeID, topLevelType, nativeEventParam) {
+    _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam);
+  },
+  receiveTouches: function(eventTopLevelType, touches, changedIndices) {
+    if (
+      "topTouchEnd" === eventTopLevelType ||
+      "topTouchCancel" === eventTopLevelType
+    ) {
+      var JSCompiler_temp = [];
+      for (var i = 0; i < changedIndices.length; i++) {
+        var index = changedIndices[i];
+        JSCompiler_temp.push(touches[index]);
+        touches[index] = null;
+      }
+      for (i = changedIndices = 0; i < touches.length; i++)
+        (index = touches[i]),
+          null !== index && (touches[changedIndices++] = index);
+      touches.length = changedIndices;
+    } else
+      for (JSCompiler_temp = [], i = 0; i < changedIndices.length; i++)
+        JSCompiler_temp.push(touches[changedIndices[i]]);
+    for (
+      changedIndices = 0;
+      changedIndices < JSCompiler_temp.length;
+      changedIndices++
+    ) {
+      i = JSCompiler_temp[changedIndices];
+      i.changedTouches = JSCompiler_temp;
+      i.touches = touches;
+      index = null;
+      var target = i.target;
+      null === target || void 0 === target || 1 > target || (index = target);
+      _receiveRootNodeIDEvent(index, eventTopLevelType, i);
+    }
+  }
+});
+RCTEventEmitter.register(ReactNativeEventEmitter);
+var hasSymbol = "function" === typeof Symbol && Symbol["for"],
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
+  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
+  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol
+    ? Symbol["for"]("react.strict_mode")
+    : 60108,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol
+    ? Symbol["for"]("react.forward_ref")
+    : 60112,
+  MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
+function getIteratorFn(maybeIterable) {
+  if (null === maybeIterable || "undefined" === typeof maybeIterable)
+    return null;
+  maybeIterable =
+    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
+    maybeIterable["@@iterator"];
+  return "function" === typeof maybeIterable ? maybeIterable : null;
+}
+function createPortal(children, containerInfo, implementation) {
+  var key =
+    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
+  return {
+    $$typeof: REACT_PORTAL_TYPE,
+    key: null == key ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+function getComponentName(fiber) {
+  fiber = fiber.type;
+  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
+  if ("string" === typeof fiber) return fiber;
+  switch (fiber) {
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_RETURN_TYPE:
+      return "ReactReturn";
+  }
+  if ("object" === typeof fiber && null !== fiber)
+    switch (fiber.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        return (
+          (fiber = fiber.render.displayName || fiber.render.name || ""),
+          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
+        );
+    }
+  return null;
+}
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
+    }
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress["return"];
+  } while (workInProgress);
+  return info;
+}
+var emptyObject$1 = {},
+  removedKeys = null,
+  removedKeyCount = 0;
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node))
+    for (var i = node.length; i-- && 0 < removedKeyCount; )
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+  else if (node && 0 < removedKeyCount)
+    for (i in removedKeys)
+      if (removedKeys[i]) {
+        var _nextProp = node[i];
+        if (void 0 !== _nextProp) {
+          var attributeConfig = validAttributes[i];
+          if (attributeConfig) {
+            "function" === typeof _nextProp && (_nextProp = !0);
+            "undefined" === typeof _nextProp && (_nextProp = null);
+            if ("object" !== typeof attributeConfig)
+              updatePayload[i] = _nextProp;
+            else if (
+              "function" === typeof attributeConfig.diff ||
+              "function" === typeof attributeConfig.process
+            )
+              (_nextProp =
+                "function" === typeof attributeConfig.process
+                  ? attributeConfig.process(_nextProp)
+                  : _nextProp),
+                (updatePayload[i] = _nextProp);
+            removedKeys[i] = !1;
+            removedKeyCount--;
+          }
+        }
+      }
+}
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) return updatePayload;
+  if (!prevProp || !nextProp)
+    return nextProp
+      ? addNestedProperty(updatePayload, nextProp, validAttributes)
+      : prevProp
+        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
+        : updatePayload;
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    var minLength =
+        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
+      i;
+    for (i = 0; i < minLength; i++)
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp[i],
+        nextProp[i],
+        validAttributes
+      );
+    for (; i < prevProp.length; i++)
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp[i],
+        validAttributes
+      );
+    for (; i < nextProp.length; i++)
+      updatePayload = addNestedProperty(
+        updatePayload,
+        nextProp[i],
+        validAttributes
+      );
+    return updatePayload;
+  }
+  return Array.isArray(prevProp)
+    ? diffProperties(
+        updatePayload,
+        flattenStyle(prevProp),
+        nextProp,
+        validAttributes
+      )
+    : diffProperties(
+        updatePayload,
+        prevProp,
+        flattenStyle(nextProp),
+        validAttributes
+      );
+}
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) return updatePayload;
+  if (!Array.isArray(nextProp))
+    return diffProperties(
+      updatePayload,
+      emptyObject$1,
+      nextProp,
+      validAttributes
+    );
+  for (var i = 0; i < nextProp.length; i++)
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) return updatePayload;
+  if (!Array.isArray(prevProp))
+    return diffProperties(
+      updatePayload,
+      prevProp,
+      emptyObject$1,
+      validAttributes
+    );
+  for (var i = 0; i < prevProp.length; i++)
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig, propKey;
+  for (propKey in nextProps)
+    if ((attributeConfig = validAttributes[propKey])) {
+      var prevProp = prevProps[propKey];
+      var nextProp = nextProps[propKey];
+      "function" === typeof nextProp &&
+        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
+      "undefined" === typeof nextProp &&
+        ((nextProp = null),
+        "undefined" === typeof prevProp && (prevProp = null));
+      removedKeys && (removedKeys[propKey] = !1);
+      if (updatePayload && void 0 !== updatePayload[propKey])
+        if ("object" !== typeof attributeConfig)
+          updatePayload[propKey] = nextProp;
+        else {
+          if (
+            "function" === typeof attributeConfig.diff ||
+            "function" === typeof attributeConfig.process
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              (updatePayload[propKey] = attributeConfig);
+        }
+      else if (prevProp !== nextProp)
+        if ("object" !== typeof attributeConfig)
+          ("object" !== typeof nextProp ||
+            null === nextProp ||
+            deepDiffer(prevProp, nextProp)) &&
+            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
+        else if (
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+        ) {
+          if (
+            void 0 === prevProp ||
+            ("function" === typeof attributeConfig.diff
+              ? attributeConfig.diff(prevProp, nextProp)
+              : "object" !== typeof nextProp ||
+                null === nextProp ||
+                deepDiffer(prevProp, nextProp))
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              ((updatePayload || (updatePayload = {}))[
+                propKey
+              ] = attributeConfig);
+        } else
+          (removedKeys = null),
+            (removedKeyCount = 0),
+            (updatePayload = diffNestedProperty(
+              updatePayload,
+              prevProp,
+              nextProp,
+              attributeConfig
+            )),
+            0 < removedKeyCount &&
+              updatePayload &&
+              (restoreDeletedValuesInNestedArray(
+                updatePayload,
+                nextProp,
+                attributeConfig
+              ),
+              (removedKeys = null));
+    }
+  for (var _propKey in prevProps)
+    void 0 === nextProps[_propKey] &&
+      (!(attributeConfig = validAttributes[_propKey]) ||
+        (updatePayload && void 0 !== updatePayload[_propKey]) ||
+        ((prevProp = prevProps[_propKey]),
+        void 0 !== prevProp &&
+          ("object" !== typeof attributeConfig ||
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
+              removedKeys || (removedKeys = {}),
+              removedKeys[_propKey] ||
+                ((removedKeys[_propKey] = !0), removedKeyCount++))
+            : (updatePayload = clearNestedProperty(
+                updatePayload,
+                prevProp,
+                attributeConfig
+              )))));
+  return updatePayload;
+}
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (callback) {
+      if ("boolean" === typeof context.__isMounted) {
+        if (!context.__isMounted) return;
+      } else if (
+        "function" === typeof context.isMounted &&
+        !context.isMounted()
+      )
+        return;
+      return callback.apply(context, arguments);
+    }
+  };
+}
+function _inherits(subClass, superClass) {
+  if ("function" !== typeof superClass && null !== superClass)
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: !1,
+      writable: !0,
+      configurable: !0
+    }
+  });
+  superClass &&
+    (Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass));
+}
+var ReactCurrentOwner =
+  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
+  else {
+    if (0 !== (node.effectTag & 2)) return 1;
+    for (; node["return"]; )
+      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
+  }
+  return 3 === node.tag ? 2 : 3;
+}
+function isMounted(component) {
+  return (component = component._reactInternalFiber)
+    ? 2 === isFiberMountedImpl(component)
+    : !1;
+}
+function assertIsMounted(fiber) {
+  invariant(
+    2 === isFiberMountedImpl(fiber),
+    "Unable to find node on an unmounted component."
+  );
+}
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate)
+    return (
+      (alternate = isFiberMountedImpl(fiber)),
+      invariant(
+        3 !== alternate,
+        "Unable to find node on an unmounted component."
+      ),
+      1 === alternate ? null : fiber
+    );
+  for (var a = fiber, b = alternate; ; ) {
+    var parentA = a["return"],
+      parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) break;
+    if (parentA.child === parentB.child) {
+      for (var child = parentA.child; child; ) {
+        if (child === a) return assertIsMounted(parentA), fiber;
+        if (child === b) return assertIsMounted(parentA), alternate;
+        child = child.sibling;
+      }
+      invariant(!1, "Unable to find node on an unmounted component.");
+    }
+    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
+    else {
+      child = !1;
+      for (var _child = parentA.child; _child; ) {
+        if (_child === a) {
+          child = !0;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          child = !0;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!child) {
+        for (_child = parentB.child; _child; ) {
+          if (_child === a) {
+            child = !0;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            child = !0;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          child,
+          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
+        );
+      }
+    }
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
+  return a.stateNode.current === a ? fiber : alternate;
+}
+function findCurrentHostFiber(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child) (node.child["return"] = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node["return"] || node["return"] === parent) return null;
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+  return null;
+}
+function findCurrentHostFiberWithNoPortals(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child && 4 !== node.tag)
+      (node.child["return"] = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node["return"] || node["return"] === parent) return null;
+        node = node["return"];
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+  return null;
+}
+function FiberNode(tag, pendingProps, key, mode) {
+  this.tag = tag;
+  this.key = key;
+  this.stateNode = this.type = null;
+  this.sibling = this.child = this["return"] = null;
+  this.index = 0;
+  this.ref = null;
+  this.pendingProps = pendingProps;
+  this.memoizedState = this.updateQueue = this.memoizedProps = null;
+  this.mode = mode;
+  this.effectTag = 0;
+  this.lastEffect = this.firstEffect = this.nextEffect = null;
+  this.expirationTime = 0;
+  this.alternate = null;
+}
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  null === workInProgress
+    ? ((workInProgress = new FiberNode(
+        current.tag,
+        pendingProps,
+        current.key,
+        current.mode
+      )),
+      (workInProgress.type = current.type),
+      (workInProgress.stateNode = current.stateNode),
+      (workInProgress.alternate = current),
+      (current.alternate = workInProgress))
+    : ((workInProgress.pendingProps = pendingProps),
+      (workInProgress.effectTag = 0),
+      (workInProgress.nextEffect = null),
+      (workInProgress.firstEffect = null),
+      (workInProgress.lastEffect = null));
+  workInProgress.expirationTime = expirationTime;
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+  return workInProgress;
+}
+function createFiberFromElement(element, mode, expirationTime) {
+  var type = element.type,
+    key = element.key;
+  element = element.props;
+  var fiberTag = void 0;
+  if ("function" === typeof type)
+    fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
+  else if ("string" === typeof type) fiberTag = 5;
+  else
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          element.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 3;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 2;
+        break;
+      case REACT_CALL_TYPE:
+        fiberTag = 7;
+        break;
+      case REACT_RETURN_TYPE:
+        fiberTag = 9;
+        break;
+      default:
+        if ("object" === typeof type && null !== type)
+          switch (type.$$typeof) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = 13;
+              break;
+            case REACT_CONTEXT_TYPE:
+              fiberTag = 12;
+              break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = 14;
+              break;
+            default:
+              if ("number" === typeof type.tag)
+                return (
+                  (mode = type),
+                  (mode.pendingProps = element),
+                  (mode.expirationTime = expirationTime),
+                  mode
+                );
+              throwOnInvalidElementType(type, null);
+          }
+        else throwOnInvalidElementType(type, null);
+    }
+  mode = new FiberNode(fiberTag, element, key, mode);
+  mode.type = type;
+  mode.expirationTime = expirationTime;
+  return mode;
+}
+function throwOnInvalidElementType(type) {
+  invariant(
+    !1,
+    "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
+    null == type ? type : typeof type,
+    ""
+  );
+}
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  elements = new FiberNode(10, elements, key, mode);
+  elements.expirationTime = expirationTime;
+  return elements;
+}
+function createFiberFromText(content, mode, expirationTime) {
+  content = new FiberNode(6, content, null, mode);
+  content.expirationTime = expirationTime;
+  return content;
+}
+function createFiberFromPortal(portal, mode, expirationTime) {
+  mode = new FiberNode(
+    4,
+    null !== portal.children ? portal.children : [],
+    portal.key,
+    mode
+  );
+  mode.expirationTime = expirationTime;
+  mode.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null,
+    implementation: portal.implementation
+  };
+  return mode;
+}
+var onCommitFiberRoot = null,
+  onCommitFiberUnmount = null;
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {}
+  };
+}
+function injectInternals(internals) {
+  if ("undefined" === typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) return !1;
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled || !hook.supportsFiber) return !0;
+  try {
+    var rendererID = hook.inject(internals);
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {}
+  return !0;
+}
+function onCommitRoot(root) {
+  "function" === typeof onCommitFiberRoot && onCommitFiberRoot(root);
+}
+function onCommitUnmount(fiber) {
+  "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
+}
+new Set();
+function createUpdateQueue(baseState) {
+  return {
+    baseState: baseState,
+    expirationTime: 0,
+    first: null,
+    last: null,
+    callbackList: null,
+    hasForceUpdate: !1,
+    isInitialized: !1,
+    capturedValues: null
+  };
+}
+function insertUpdateIntoQueue(queue, update) {
+  null === queue.last
+    ? (queue.first = queue.last = update)
+    : ((queue.last.next = update), (queue.last = update));
+  if (
+    0 === queue.expirationTime ||
+    queue.expirationTime > update.expirationTime
+  )
+    queue.expirationTime = update.expirationTime;
+}
+var q1 = void 0,
+  q2 = void 0;
+function ensureUpdateQueues(fiber) {
+  q1 = q2 = null;
+  var alternateFiber = fiber.alternate,
+    queue1 = fiber.updateQueue;
+  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
+  null !== alternateFiber
+    ? ((fiber = alternateFiber.updateQueue),
+      null === fiber &&
+        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
+    : (fiber = null);
+  q1 = queue1;
+  q2 = fiber !== queue1 ? fiber : null;
+}
+function insertUpdateIntoFiber(fiber, update) {
+  ensureUpdateQueues(fiber);
+  fiber = q1;
+  var queue2 = q2;
+  null === queue2
+    ? insertUpdateIntoQueue(fiber, update)
+    : null === fiber.last || null === queue2.last
+      ? (insertUpdateIntoQueue(fiber, update),
+        insertUpdateIntoQueue(queue2, update))
+      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
+}
+function getStateFromUpdate(update, instance, prevState, props) {
+  update = update.partialState;
+  return "function" === typeof update
+    ? update.call(instance, prevState, props)
+    : update;
+}
+function processUpdateQueue(
+  current,
+  workInProgress,
+  queue,
+  instance,
+  props,
+  renderExpirationTime
+) {
+  null !== current &&
+    current.updateQueue === queue &&
+    (queue = workInProgress.updateQueue = {
+      baseState: queue.baseState,
+      expirationTime: queue.expirationTime,
+      first: queue.first,
+      last: queue.last,
+      isInitialized: queue.isInitialized,
+      capturedValues: queue.capturedValues,
+      callbackList: null,
+      hasForceUpdate: !1
+    });
+  queue.expirationTime = 0;
+  queue.isInitialized
+    ? (current = queue.baseState)
+    : ((current = queue.baseState = workInProgress.memoizedState),
+      (queue.isInitialized = !0));
+  for (
+    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
+    null !== update;
+
+  ) {
+    var updateExpirationTime = update.expirationTime;
+    if (updateExpirationTime > renderExpirationTime) {
+      var remainingExpirationTime = queue.expirationTime;
+      if (
+        0 === remainingExpirationTime ||
+        remainingExpirationTime > updateExpirationTime
+      )
+        queue.expirationTime = updateExpirationTime;
+      didSkip || ((didSkip = !0), (queue.baseState = current));
+    } else {
+      didSkip ||
+        ((queue.first = update.next),
+        null === queue.first && (queue.last = null));
+      if (update.isReplace)
+        (current = getStateFromUpdate(update, instance, current, props)),
+          (dontMutatePrevState = !0);
+      else if (
+        (updateExpirationTime = getStateFromUpdate(
+          update,
+          instance,
+          current,
+          props
+        ))
+      )
+        (current = dontMutatePrevState
+          ? Object.assign({}, current, updateExpirationTime)
+          : Object.assign(current, updateExpirationTime)),
+          (dontMutatePrevState = !1);
+      update.isForced && (queue.hasForceUpdate = !0);
+      null !== update.callback &&
+        ((updateExpirationTime = queue.callbackList),
+        null === updateExpirationTime &&
+          (updateExpirationTime = queue.callbackList = []),
+        updateExpirationTime.push(update));
+      null !== update.capturedValue &&
+        ((updateExpirationTime = queue.capturedValues),
+        null === updateExpirationTime
+          ? (queue.capturedValues = [update.capturedValue])
+          : updateExpirationTime.push(update.capturedValue));
+    }
+    update = update.next;
+  }
+  null !== queue.callbackList
+    ? (workInProgress.effectTag |= 32)
+    : null !== queue.first ||
+      queue.hasForceUpdate ||
+      null !== queue.capturedValues ||
+      (workInProgress.updateQueue = null);
+  didSkip || (queue.baseState = current);
+  return current;
+}
+function commitCallbacks(queue, context) {
+  var callbackList = queue.callbackList;
+  if (null !== callbackList)
+    for (
+      queue.callbackList = null, queue = 0;
+      queue < callbackList.length;
+      queue++
+    ) {
+      var update = callbackList[queue],
+        _callback = update.callback;
+      update.callback = null;
+      invariant(
+        "function" === typeof _callback,
+        "Invalid argument passed as callback. Expected a function. Instead received: %s",
+        _callback
+      );
+      _callback.call(context);
+    }
+}
+function ReactFiberClassComponent(
+  legacyContext,
+  scheduleWork,
+  computeExpirationForFiber,
+  memoizeProps,
+  memoizeState
+) {
+  function checkShouldComponentUpdate(
+    workInProgress,
+    oldProps,
+    newProps,
+    oldState,
+    newState,
+    newContext
+  ) {
+    if (
+      null === oldProps ||
+      (null !== workInProgress.updateQueue &&
+        workInProgress.updateQueue.hasForceUpdate)
+    )
+      return !0;
+    var instance = workInProgress.stateNode;
+    workInProgress = workInProgress.type;
+    return "function" === typeof instance.shouldComponentUpdate
+      ? instance.shouldComponentUpdate(newProps, newState, newContext)
+      : workInProgress.prototype &&
+        workInProgress.prototype.isPureReactComponent
+        ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+        : !0;
+  }
+  function adoptClassInstance(workInProgress, instance) {
+    instance.updater = updater;
+    workInProgress.stateNode = instance;
+    instance._reactInternalFiber = workInProgress;
+  }
+  function callComponentWillReceiveProps(
+    workInProgress,
+    instance,
+    newProps,
+    newContext
+  ) {
+    workInProgress = instance.state;
+    "function" === typeof instance.componentWillReceiveProps &&
+      instance.componentWillReceiveProps(newProps, newContext);
+    "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
+      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+    instance.state !== workInProgress &&
+      updater.enqueueReplaceState(instance, instance.state, null);
+  }
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    workInProgress = workInProgress.type;
+    if ("function" === typeof workInProgress.getDerivedStateFromProps)
+      return workInProgress.getDerivedStateFromProps.call(
+        null,
+        nextProps,
+        prevState
+      );
+  }
+  var cacheContext = legacyContext.cacheContext,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    isContextConsumer = legacyContext.isContextConsumer,
+    hasContextChanged = legacyContext.hasContextChanged,
+    updater = {
+      isMounted: isMounted,
+      enqueueSetState: function(instance, partialState, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: partialState,
+          callback: callback,
+          isReplace: !1,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      },
+      enqueueReplaceState: function(instance, state, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: state,
+          callback: callback,
+          isReplace: !0,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      },
+      enqueueForceUpdate: function(instance, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: null,
+          callback: callback,
+          isReplace: !1,
+          isForced: !0,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
+      }
+    };
+  return {
+    adoptClassInstance: adoptClassInstance,
+    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
+    constructClassInstance: function(workInProgress, props) {
+      var ctor = workInProgress.type,
+        unmaskedContext = getUnmaskedContext(workInProgress),
+        needsContext = isContextConsumer(workInProgress),
+        context = needsContext
+          ? getMaskedContext(workInProgress, unmaskedContext)
+          : emptyObject;
+      ctor = new ctor(props, context);
+      var state =
+        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
+      adoptClassInstance(workInProgress, ctor);
+      workInProgress.memoizedState = state;
+      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
+      null !== props &&
+        void 0 !== props &&
+        (workInProgress.memoizedState = Object.assign(
+          {},
+          workInProgress.memoizedState,
+          props
+        ));
+      needsContext && cacheContext(workInProgress, unmaskedContext, context);
+      return ctor;
+    },
+    mountClassInstance: function(workInProgress, renderExpirationTime) {
+      var ctor = workInProgress.type,
+        current = workInProgress.alternate,
+        instance = workInProgress.stateNode,
+        props = workInProgress.pendingProps,
+        unmaskedContext = getUnmaskedContext(workInProgress);
+      instance.props = props;
+      instance.state = workInProgress.memoizedState;
+      instance.refs = emptyObject;
+      instance.context = getMaskedContext(workInProgress, unmaskedContext);
+      "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate ||
+        ("function" !== typeof instance.UNSAFE_componentWillMount &&
+          "function" !== typeof instance.componentWillMount) ||
+        ((ctor = instance.state),
+        "function" === typeof instance.componentWillMount &&
+          instance.componentWillMount(),
+        "function" === typeof instance.UNSAFE_componentWillMount &&
+          instance.UNSAFE_componentWillMount(),
+        ctor !== instance.state &&
+          updater.enqueueReplaceState(instance, instance.state, null),
+        (ctor = workInProgress.updateQueue),
+        null !== ctor &&
+          (instance.state = processUpdateQueue(
+            current,
+            workInProgress,
+            ctor,
+            instance,
+            props,
+            renderExpirationTime
+          )));
+      "function" === typeof instance.componentDidMount &&
+        (workInProgress.effectTag |= 4);
+    },
+    resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
+      var ctor = workInProgress.type,
+        instance = workInProgress.stateNode;
+      instance.props = workInProgress.memoizedProps;
+      instance.state = workInProgress.memoizedState;
+      var oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps,
+        oldContext = instance.context,
+        newUnmaskedContext = getUnmaskedContext(workInProgress);
+      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      (ctor =
+        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate) ||
+        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
+          "function" !== typeof instance.componentWillReceiveProps) ||
+        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
+          callComponentWillReceiveProps(
+            workInProgress,
+            instance,
+            newProps,
+            newUnmaskedContext
+          ));
+      oldContext = workInProgress.memoizedState;
+      renderExpirationTime =
+        null !== workInProgress.updateQueue
+          ? processUpdateQueue(
+              null,
+              workInProgress,
+              workInProgress.updateQueue,
+              instance,
+              newProps,
+              renderExpirationTime
+            )
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
+          workInProgress,
+          instance,
+          newProps,
+          renderExpirationTime
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
+          null === renderExpirationTime || void 0 === renderExpirationTime
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue = workInProgress.updateQueue;
+        null !== _updateQueue &&
+          (_updateQueue.baseState = Object.assign(
+            {},
+            _updateQueue.baseState,
+            derivedStateFromProps
+          ));
+      }
+      if (
+        !(
+          oldProps !== newProps ||
+          oldContext !== renderExpirationTime ||
+          hasContextChanged() ||
+          (null !== workInProgress.updateQueue &&
+            workInProgress.updateQueue.hasForceUpdate)
+        )
+      )
+        return (
+          "function" === typeof instance.componentDidMount &&
+            (workInProgress.effectTag |= 4),
+          !1
+        );
+      (oldProps = checkShouldComponentUpdate(
+        workInProgress,
+        oldProps,
+        newProps,
+        oldContext,
+        renderExpirationTime,
+        newUnmaskedContext
+      ))
+        ? (ctor ||
+            ("function" !== typeof instance.UNSAFE_componentWillMount &&
+              "function" !== typeof instance.componentWillMount) ||
+            ("function" === typeof instance.componentWillMount &&
+              instance.componentWillMount(),
+            "function" === typeof instance.UNSAFE_componentWillMount &&
+              instance.UNSAFE_componentWillMount()),
+          "function" === typeof instance.componentDidMount &&
+            (workInProgress.effectTag |= 4))
+        : ("function" === typeof instance.componentDidMount &&
+            (workInProgress.effectTag |= 4),
+          memoizeProps(workInProgress, newProps),
+          memoizeState(workInProgress, renderExpirationTime));
+      instance.props = newProps;
+      instance.state = renderExpirationTime;
+      instance.context = newUnmaskedContext;
+      return oldProps;
+    },
+    updateClassInstance: function(
+      current,
+      workInProgress,
+      renderExpirationTime
+    ) {
+      var ctor = workInProgress.type,
+        instance = workInProgress.stateNode;
+      instance.props = workInProgress.memoizedProps;
+      instance.state = workInProgress.memoizedState;
+      var oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps,
+        oldContext = instance.context,
+        newUnmaskedContext = getUnmaskedContext(workInProgress);
+      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      (ctor =
+        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof instance.getSnapshotBeforeUpdate) ||
+        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
+          "function" !== typeof instance.componentWillReceiveProps) ||
+        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
+          callComponentWillReceiveProps(
+            workInProgress,
+            instance,
+            newProps,
+            newUnmaskedContext
+          ));
+      oldContext = workInProgress.memoizedState;
+      renderExpirationTime =
+        null !== workInProgress.updateQueue
+          ? processUpdateQueue(
+              current,
+              workInProgress,
+              workInProgress.updateQueue,
+              instance,
+              newProps,
+              renderExpirationTime
+            )
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
+          workInProgress,
+          instance,
+          newProps,
+          renderExpirationTime
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
+          null === renderExpirationTime || void 0 === renderExpirationTime
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue3 = workInProgress.updateQueue;
+        null !== _updateQueue3 &&
+          (_updateQueue3.baseState = Object.assign(
+            {},
+            _updateQueue3.baseState,
+            derivedStateFromProps
+          ));
+      }
+      if (
+        !(
+          oldProps !== newProps ||
+          oldContext !== renderExpirationTime ||
+          hasContextChanged() ||
+          (null !== workInProgress.updateQueue &&
+            workInProgress.updateQueue.hasForceUpdate)
+        )
+      )
+        return (
+          "function" !== typeof instance.componentDidUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 4),
+          "function" !== typeof instance.getSnapshotBeforeUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 2048),
+          !1
+        );
+      (derivedStateFromProps = checkShouldComponentUpdate(
+        workInProgress,
+        oldProps,
+        newProps,
+        oldContext,
+        renderExpirationTime,
+        newUnmaskedContext
+      ))
+        ? (ctor ||
+            ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
+              "function" !== typeof instance.componentWillUpdate) ||
+            ("function" === typeof instance.componentWillUpdate &&
+              instance.componentWillUpdate(
+                newProps,
+                renderExpirationTime,
+                newUnmaskedContext
+              ),
+            "function" === typeof instance.UNSAFE_componentWillUpdate &&
+              instance.UNSAFE_componentWillUpdate(
+                newProps,
+                renderExpirationTime,
+                newUnmaskedContext
+              )),
+          "function" === typeof instance.componentDidUpdate &&
+            (workInProgress.effectTag |= 4),
+          "function" === typeof instance.getSnapshotBeforeUpdate &&
+            (workInProgress.effectTag |= 2048))
+        : ("function" !== typeof instance.componentDidUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 4),
+          "function" !== typeof instance.getSnapshotBeforeUpdate ||
+            (oldProps === current.memoizedProps &&
+              oldContext === current.memoizedState) ||
+            (workInProgress.effectTag |= 2048),
+          memoizeProps(workInProgress, newProps),
+          memoizeState(workInProgress, renderExpirationTime));
+      instance.props = newProps;
+      instance.state = renderExpirationTime;
+      instance.context = newUnmaskedContext;
+      return derivedStateFromProps;
+    }
+  };
+}
+var isArray$1 = Array.isArray;
+function coerceRef(returnFiber, current, element) {
+  returnFiber = element.ref;
+  if (
+    null !== returnFiber &&
+    "function" !== typeof returnFiber &&
+    "object" !== typeof returnFiber
+  ) {
+    if (element._owner) {
+      element = element._owner;
+      var inst = void 0;
+      element &&
+        (invariant(
+          2 === element.tag,
+          "Stateless function components cannot have refs."
+        ),
+        (inst = element.stateNode));
+      invariant(
+        inst,
+        "Missing owner for string ref %s. This error is likely caused by a bug in React. Please file an issue.",
+        returnFiber
+      );
+      var stringRef = "" + returnFiber;
+      if (
+        null !== current &&
+        null !== current.ref &&
+        current.ref._stringRef === stringRef
+      )
+        return current.ref;
+      current = function(value) {
+        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
+        null === value ? delete refs[stringRef] : (refs[stringRef] = value);
+      };
+      current._stringRef = stringRef;
+      return current;
+    }
+    invariant(
+      "string" === typeof returnFiber,
+      "Expected ref to be a function or a string."
+    );
+    invariant(
+      element._owner,
+      "Element ref was specified as a string (%s) but no owner was set. This could happen for one of the following reasons:\n1. You may be adding a ref to a functional component\n2. You may be adding a ref to a component that was not created inside a component's render method\n3. You have multiple copies of React loaded\nSee https://fb.me/react-refs-must-have-owner for more information.",
+      returnFiber
+    );
+  }
+  return returnFiber;
+}
+function throwOnInvalidObjectType(returnFiber, newChild) {
+  "textarea" !== returnFiber.type &&
+    invariant(
+      !1,
+      "Objects are not valid as a React child (found: %s).%s",
+      "[object Object]" === Object.prototype.toString.call(newChild)
+        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
+        : newChild,
+      ""
+    );
+}
+function ChildReconciler(shouldTrackSideEffects) {
+  function deleteChild(returnFiber, childToDelete) {
+    if (shouldTrackSideEffects) {
+      var last = returnFiber.lastEffect;
+      null !== last
+        ? ((last.nextEffect = childToDelete),
+          (returnFiber.lastEffect = childToDelete))
+        : (returnFiber.firstEffect = returnFiber.lastEffect = childToDelete);
+      childToDelete.nextEffect = null;
+      childToDelete.effectTag = 8;
+    }
+  }
+  function deleteRemainingChildren(returnFiber, currentFirstChild) {
+    if (!shouldTrackSideEffects) return null;
+    for (; null !== currentFirstChild; )
+      deleteChild(returnFiber, currentFirstChild),
+        (currentFirstChild = currentFirstChild.sibling);
+    return null;
+  }
+  function mapRemainingChildren(returnFiber, currentFirstChild) {
+    for (returnFiber = new Map(); null !== currentFirstChild; )
+      null !== currentFirstChild.key
+        ? returnFiber.set(currentFirstChild.key, currentFirstChild)
+        : returnFiber.set(currentFirstChild.index, currentFirstChild),
+        (currentFirstChild = currentFirstChild.sibling);
+    return returnFiber;
+  }
+  function useFiber(fiber, pendingProps, expirationTime) {
+    fiber = createWorkInProgress(fiber, pendingProps, expirationTime);
+    fiber.index = 0;
+    fiber.sibling = null;
+    return fiber;
+  }
+  function placeChild(newFiber, lastPlacedIndex, newIndex) {
+    newFiber.index = newIndex;
+    if (!shouldTrackSideEffects) return lastPlacedIndex;
+    newIndex = newFiber.alternate;
+    if (null !== newIndex)
+      return (
+        (newIndex = newIndex.index),
+        newIndex < lastPlacedIndex
+          ? ((newFiber.effectTag = 2), lastPlacedIndex)
+          : newIndex
+      );
+    newFiber.effectTag = 2;
+    return lastPlacedIndex;
+  }
+  function placeSingleChild(newFiber) {
+    shouldTrackSideEffects &&
+      null === newFiber.alternate &&
+      (newFiber.effectTag = 2);
+    return newFiber;
+  }
+  function updateTextNode(returnFiber, current, textContent, expirationTime) {
+    if (null === current || 6 !== current.tag)
+      return (
+        (current = createFiberFromText(
+          textContent,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (current["return"] = returnFiber),
+        current
+      );
+    current = useFiber(current, textContent, expirationTime);
+    current["return"] = returnFiber;
+    return current;
+  }
+  function updateElement(returnFiber, current, element, expirationTime) {
+    if (null !== current && current.type === element.type)
+      return (
+        (expirationTime = useFiber(current, element.props, expirationTime)),
+        (expirationTime.ref = coerceRef(returnFiber, current, element)),
+        (expirationTime["return"] = returnFiber),
+        expirationTime
+      );
+    expirationTime = createFiberFromElement(
+      element,
+      returnFiber.mode,
+      expirationTime
+    );
+    expirationTime.ref = coerceRef(returnFiber, current, element);
+    expirationTime["return"] = returnFiber;
+    return expirationTime;
+  }
+  function updatePortal(returnFiber, current, portal, expirationTime) {
+    if (
+      null === current ||
+      4 !== current.tag ||
+      current.stateNode.containerInfo !== portal.containerInfo ||
+      current.stateNode.implementation !== portal.implementation
+    )
+      return (
+        (current = createFiberFromPortal(
+          portal,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (current["return"] = returnFiber),
+        current
+      );
+    current = useFiber(current, portal.children || [], expirationTime);
+    current["return"] = returnFiber;
+    return current;
+  }
+  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
+    if (null === current || 10 !== current.tag)
+      return (
+        (current = createFiberFromFragment(
+          fragment,
+          returnFiber.mode,
+          expirationTime,
+          key
+        )),
+        (current["return"] = returnFiber),
+        current
+      );
+    current = useFiber(current, fragment, expirationTime);
+    current["return"] = returnFiber;
+    return current;
+  }
+  function createChild(returnFiber, newChild, expirationTime) {
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (newChild = createFiberFromText(
+          "" + newChild,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (newChild["return"] = returnFiber),
+        newChild
+      );
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return (
+            (expirationTime = createFiberFromElement(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
+            (expirationTime["return"] = returnFiber),
+            expirationTime
+          );
+        case REACT_PORTAL_TYPE:
+          return (
+            (newChild = createFiberFromPortal(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (newChild["return"] = returnFiber),
+            newChild
+          );
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return (
+          (newChild = createFiberFromFragment(
+            newChild,
+            returnFiber.mode,
+            expirationTime,
+            null
+          )),
+          (newChild["return"] = returnFiber),
+          newChild
+        );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
+    var key = null !== oldFiber ? oldFiber.key : null;
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return null !== key
+        ? null
+        : updateTextNode(returnFiber, oldFiber, "" + newChild, expirationTime);
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return newChild.key === key
+            ? newChild.type === REACT_FRAGMENT_TYPE
+              ? updateFragment(
+                  returnFiber,
+                  oldFiber,
+                  newChild.props.children,
+                  expirationTime,
+                  key
+                )
+              : updateElement(returnFiber, oldFiber, newChild, expirationTime)
+            : null;
+        case REACT_PORTAL_TYPE:
+          return newChild.key === key
+            ? updatePortal(returnFiber, oldFiber, newChild, expirationTime)
+            : null;
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return null !== key
+          ? null
+          : updateFragment(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime,
+              null
+            );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function updateFromMap(
+    existingChildren,
+    returnFiber,
+    newIdx,
+    newChild,
+    expirationTime
+  ) {
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (existingChildren = existingChildren.get(newIdx) || null),
+        updateTextNode(
+          returnFiber,
+          existingChildren,
+          "" + newChild,
+          expirationTime
+        )
+      );
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return (
+            (existingChildren =
+              existingChildren.get(
+                null === newChild.key ? newIdx : newChild.key
+              ) || null),
+            newChild.type === REACT_FRAGMENT_TYPE
+              ? updateFragment(
+                  returnFiber,
+                  existingChildren,
+                  newChild.props.children,
+                  expirationTime,
+                  newChild.key
+                )
+              : updateElement(
+                  returnFiber,
+                  existingChildren,
+                  newChild,
+                  expirationTime
+                )
+          );
+        case REACT_PORTAL_TYPE:
+          return (
+            (existingChildren =
+              existingChildren.get(
+                null === newChild.key ? newIdx : newChild.key
+              ) || null),
+            updatePortal(
+              returnFiber,
+              existingChildren,
+              newChild,
+              expirationTime
+            )
+          );
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return (
+          (existingChildren = existingChildren.get(newIdx) || null),
+          updateFragment(
+            returnFiber,
+            existingChildren,
+            newChild,
+            expirationTime,
+            null
+          )
+        );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function reconcileChildrenArray(
+    returnFiber,
+    currentFirstChild,
+    newChildren,
+    expirationTime
+  ) {
+    for (
+      var resultingFirstChild = null,
+        previousNewFiber = null,
+        oldFiber = currentFirstChild,
+        newIdx = (currentFirstChild = 0),
+        nextOldFiber = null;
+      null !== oldFiber && newIdx < newChildren.length;
+      newIdx++
+    ) {
+      oldFiber.index > newIdx
+        ? ((nextOldFiber = oldFiber), (oldFiber = null))
+        : (nextOldFiber = oldFiber.sibling);
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (null === newFiber) {
+        null === oldFiber && (oldFiber = nextOldFiber);
+        break;
+      }
+      shouldTrackSideEffects &&
+        oldFiber &&
+        null === newFiber.alternate &&
+        deleteChild(returnFiber, oldFiber);
+      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
+      null === previousNewFiber
+        ? (resultingFirstChild = newFiber)
+        : (previousNewFiber.sibling = newFiber);
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+    if (newIdx === newChildren.length)
+      return (
+        deleteRemainingChildren(returnFiber, oldFiber), resultingFirstChild
+      );
+    if (null === oldFiber) {
+      for (; newIdx < newChildren.length; newIdx++)
+        if (
+          (oldFiber = createChild(
+            returnFiber,
+            newChildren[newIdx],
+            expirationTime
+          ))
+        )
+          (currentFirstChild = placeChild(oldFiber, currentFirstChild, newIdx)),
+            null === previousNewFiber
+              ? (resultingFirstChild = oldFiber)
+              : (previousNewFiber.sibling = oldFiber),
+            (previousNewFiber = oldFiber);
+      return resultingFirstChild;
+    }
+    for (
+      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
+      newIdx < newChildren.length;
+      newIdx++
+    )
+      if (
+        (nextOldFiber = updateFromMap(
+          oldFiber,
+          returnFiber,
+          newIdx,
+          newChildren[newIdx],
+          expirationTime
+        ))
+      ) {
+        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
+          oldFiber["delete"](
+            null === nextOldFiber.key ? newIdx : nextOldFiber.key
+          );
+        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
+        null === previousNewFiber
+          ? (resultingFirstChild = nextOldFiber)
+          : (previousNewFiber.sibling = nextOldFiber);
+        previousNewFiber = nextOldFiber;
+      }
+    shouldTrackSideEffects &&
+      oldFiber.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    return resultingFirstChild;
+  }
+  function reconcileChildrenIterator(
+    returnFiber,
+    currentFirstChild,
+    newChildrenIterable,
+    expirationTime
+  ) {
+    var iteratorFn = getIteratorFn(newChildrenIterable);
+    invariant(
+      "function" === typeof iteratorFn,
+      "An object is not an iterable. This error is likely caused by a bug in React. Please file an issue."
+    );
+    newChildrenIterable = iteratorFn.call(newChildrenIterable);
+    invariant(
+      null != newChildrenIterable,
+      "An iterable object provided no iterator."
+    );
+    for (
+      var previousNewFiber = (iteratorFn = null),
+        oldFiber = currentFirstChild,
+        newIdx = (currentFirstChild = 0),
+        nextOldFiber = null,
+        step = newChildrenIterable.next();
+      null !== oldFiber && !step.done;
+      newIdx++, step = newChildrenIterable.next()
+    ) {
+      oldFiber.index > newIdx
+        ? ((nextOldFiber = oldFiber), (oldFiber = null))
+        : (nextOldFiber = oldFiber.sibling);
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        step.value,
+        expirationTime
+      );
+      if (null === newFiber) {
+        oldFiber || (oldFiber = nextOldFiber);
+        break;
+      }
+      shouldTrackSideEffects &&
+        oldFiber &&
+        null === newFiber.alternate &&
+        deleteChild(returnFiber, oldFiber);
+      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
+      null === previousNewFiber
+        ? (iteratorFn = newFiber)
+        : (previousNewFiber.sibling = newFiber);
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+    if (step.done)
+      return deleteRemainingChildren(returnFiber, oldFiber), iteratorFn;
+    if (null === oldFiber) {
+      for (; !step.done; newIdx++, step = newChildrenIterable.next())
+        (step = createChild(returnFiber, step.value, expirationTime)),
+          null !== step &&
+            ((currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+            null === previousNewFiber
+              ? (iteratorFn = step)
+              : (previousNewFiber.sibling = step),
+            (previousNewFiber = step));
+      return iteratorFn;
+    }
+    for (
+      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
+      !step.done;
+      newIdx++, step = newChildrenIterable.next()
+    )
+      if (
+        ((step = updateFromMap(
+          oldFiber,
+          returnFiber,
+          newIdx,
+          step.value,
+          expirationTime
+        )),
+        null !== step)
+      ) {
+        if (shouldTrackSideEffects && null !== step.alternate)
+          oldFiber["delete"](null === step.key ? newIdx : step.key);
+        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
+        null === previousNewFiber
+          ? (iteratorFn = step)
+          : (previousNewFiber.sibling = step);
+        previousNewFiber = step;
+      }
+    shouldTrackSideEffects &&
+      oldFiber.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    return iteratorFn;
+  }
+  return function(returnFiber, currentFirstChild, newChild, expirationTime) {
+    "object" === typeof newChild &&
+      null !== newChild &&
+      newChild.type === REACT_FRAGMENT_TYPE &&
+      null === newChild.key &&
+      (newChild = newChild.props.children);
+    var isObject = "object" === typeof newChild && null !== newChild;
+    if (isObject)
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          a: {
+            var key = newChild.key;
+            for (isObject = currentFirstChild; null !== isObject; ) {
+              if (isObject.key === key)
+                if (
+                  10 === isObject.tag
+                    ? newChild.type === REACT_FRAGMENT_TYPE
+                    : isObject.type === newChild.type
+                ) {
+                  deleteRemainingChildren(returnFiber, isObject.sibling);
+                  currentFirstChild = useFiber(
+                    isObject,
+                    newChild.type === REACT_FRAGMENT_TYPE
+                      ? newChild.props.children
+                      : newChild.props,
+                    expirationTime
+                  );
+                  currentFirstChild.ref = coerceRef(
+                    returnFiber,
+                    isObject,
+                    newChild
+                  );
+                  currentFirstChild["return"] = returnFiber;
+                  returnFiber = currentFirstChild;
+                  break a;
+                } else {
+                  deleteRemainingChildren(returnFiber, isObject);
+                  break;
+                }
+              else deleteChild(returnFiber, isObject);
+              isObject = isObject.sibling;
+            }
+            newChild.type === REACT_FRAGMENT_TYPE
+              ? ((currentFirstChild = createFiberFromFragment(
+                  newChild.props.children,
+                  returnFiber.mode,
+                  expirationTime,
+                  newChild.key
+                )),
+                (currentFirstChild["return"] = returnFiber),
+                (returnFiber = currentFirstChild))
+              : ((expirationTime = createFiberFromElement(
+                  newChild,
+                  returnFiber.mode,
+                  expirationTime
+                )),
+                (expirationTime.ref = coerceRef(
+                  returnFiber,
+                  currentFirstChild,
+                  newChild
+                )),
+                (expirationTime["return"] = returnFiber),
+                (returnFiber = expirationTime));
+          }
+          return placeSingleChild(returnFiber);
+        case REACT_PORTAL_TYPE:
+          a: {
+            for (isObject = newChild.key; null !== currentFirstChild; ) {
+              if (currentFirstChild.key === isObject)
+                if (
+                  4 === currentFirstChild.tag &&
+                  currentFirstChild.stateNode.containerInfo ===
+                    newChild.containerInfo &&
+                  currentFirstChild.stateNode.implementation ===
+                    newChild.implementation
+                ) {
+                  deleteRemainingChildren(
+                    returnFiber,
+                    currentFirstChild.sibling
+                  );
+                  currentFirstChild = useFiber(
+                    currentFirstChild,
+                    newChild.children || [],
+                    expirationTime
+                  );
+                  currentFirstChild["return"] = returnFiber;
+                  returnFiber = currentFirstChild;
+                  break a;
+                } else {
+                  deleteRemainingChildren(returnFiber, currentFirstChild);
+                  break;
+                }
+              else deleteChild(returnFiber, currentFirstChild);
+              currentFirstChild = currentFirstChild.sibling;
+            }
+            currentFirstChild = createFiberFromPortal(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            );
+            currentFirstChild["return"] = returnFiber;
+            returnFiber = currentFirstChild;
+          }
+          return placeSingleChild(returnFiber);
+      }
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (newChild = "" + newChild),
+        null !== currentFirstChild && 6 === currentFirstChild.tag
+          ? (deleteRemainingChildren(returnFiber, currentFirstChild.sibling),
+            (currentFirstChild = useFiber(
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )),
+            (currentFirstChild["return"] = returnFiber),
+            (returnFiber = currentFirstChild))
+          : (deleteRemainingChildren(returnFiber, currentFirstChild),
+            (currentFirstChild = createFiberFromText(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (currentFirstChild["return"] = returnFiber),
+            (returnFiber = currentFirstChild)),
+        placeSingleChild(returnFiber)
+      );
+    if (isArray$1(newChild))
+      return reconcileChildrenArray(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    if (getIteratorFn(newChild))
+      return reconcileChildrenIterator(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    isObject && throwOnInvalidObjectType(returnFiber, newChild);
+    if ("undefined" === typeof newChild)
+      switch (returnFiber.tag) {
+        case 2:
+        case 1:
+          (expirationTime = returnFiber.type),
+            invariant(
+              !1,
+              "%s(...): Nothing was returned from render. This usually means a return statement is missing. Or, to render nothing, return null.",
+              expirationTime.displayName || expirationTime.name || "Component"
+            );
+      }
+    return deleteRemainingChildren(returnFiber, currentFirstChild);
+  };
+}
+var reconcileChildFibers = ChildReconciler(!0),
+  mountChildFibers = ChildReconciler(!1);
+function ReactFiberBeginWork(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext,
+  scheduleWork,
+  computeExpirationForFiber
+) {
+  function reconcileChildren(current, workInProgress, nextChildren) {
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      nextChildren,
+      workInProgress.expirationTime
+    );
+  }
+  function reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    renderExpirationTime
+  ) {
+    workInProgress.child =
+      null === current
+        ? mountChildFibers(
+            workInProgress,
+            null,
+            nextChildren,
+            renderExpirationTime
+          )
+        : reconcileChildFibers(
+            workInProgress,
+            current.child,
+            nextChildren,
+            renderExpirationTime
+          );
+  }
+  function markRef(current, workInProgress) {
+    var ref = workInProgress.ref;
+    if (
+      (null === current && null !== ref) ||
+      (null !== current && current.ref !== ref)
+    )
+      workInProgress.effectTag |= 128;
+  }
+  function finishClassComponent(
+    current,
+    workInProgress,
+    shouldUpdate,
+    hasContext,
+    didCaptureError,
+    renderExpirationTime
+  ) {
+    markRef(current, workInProgress);
+    if (!shouldUpdate && !didCaptureError)
+      return (
+        hasContext && invalidateContextProvider(workInProgress, !1),
+        bailoutOnAlreadyFinishedWork(current, workInProgress)
+      );
+    shouldUpdate = workInProgress.stateNode;
+    ReactCurrentOwner.current = workInProgress;
+    var nextChildren = didCaptureError ? null : shouldUpdate.render();
+    workInProgress.effectTag |= 1;
+    didCaptureError &&
+      (reconcileChildrenAtExpirationTime(
+        current,
+        workInProgress,
+        null,
+        renderExpirationTime
+      ),
+      (workInProgress.child = null));
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      nextChildren,
+      renderExpirationTime
+    );
+    workInProgress.memoizedState = shouldUpdate.state;
+    workInProgress.memoizedProps = shouldUpdate.props;
+    hasContext && invalidateContextProvider(workInProgress, !0);
+    return workInProgress.child;
+  }
+  function pushHostRootContext(workInProgress) {
+    var root = workInProgress.stateNode;
+    root.pendingContext
+      ? pushTopLevelContextObject(
+          workInProgress,
+          root.pendingContext,
+          root.pendingContext !== root.context
+        )
+      : root.context &&
+        pushTopLevelContextObject(workInProgress, root.context, !1);
+    pushHostContainer(workInProgress, root.containerInfo);
+  }
+  function propagateContextChange(
+    workInProgress,
+    context,
+    changedBits,
+    renderExpirationTime
+  ) {
+    var fiber = workInProgress.child;
+    for (
+      null !== fiber && (fiber["return"] = workInProgress);
+      null !== fiber;
+
+    ) {
+      switch (fiber.tag) {
+        case 12:
+          var nextFiber = fiber.stateNode | 0;
+          if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
+            for (nextFiber = fiber; null !== nextFiber; ) {
+              var alternate = nextFiber.alternate;
+              if (
+                0 === nextFiber.expirationTime ||
+                nextFiber.expirationTime > renderExpirationTime
+              )
+                (nextFiber.expirationTime = renderExpirationTime),
+                  null !== alternate &&
+                    (0 === alternate.expirationTime ||
+                      alternate.expirationTime > renderExpirationTime) &&
+                    (alternate.expirationTime = renderExpirationTime);
+              else if (
+                null !== alternate &&
+                (0 === alternate.expirationTime ||
+                  alternate.expirationTime > renderExpirationTime)
+              )
+                alternate.expirationTime = renderExpirationTime;
+              else break;
+              nextFiber = nextFiber["return"];
+            }
+            nextFiber = null;
+          } else nextFiber = fiber.child;
+          break;
+        case 13:
+          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+          break;
+        default:
+          nextFiber = fiber.child;
+      }
+      if (null !== nextFiber) nextFiber["return"] = fiber;
+      else
+        for (nextFiber = fiber; null !== nextFiber; ) {
+          if (nextFiber === workInProgress) {
+            nextFiber = null;
+            break;
+          }
+          fiber = nextFiber.sibling;
+          if (null !== fiber) {
+            nextFiber = fiber;
+            break;
+          }
+          nextFiber = nextFiber["return"];
+        }
+      fiber = nextFiber;
+    }
+  }
+  function updateContextProvider(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    var context = workInProgress.type._context,
+      newProps = workInProgress.pendingProps,
+      oldProps = workInProgress.memoizedProps;
+    if (!hasLegacyContextChanged() && oldProps === newProps)
+      return (
+        (workInProgress.stateNode = 0),
+        pushProvider(workInProgress),
+        bailoutOnAlreadyFinishedWork(current, workInProgress)
+      );
+    var newValue = newProps.value;
+    workInProgress.memoizedProps = newProps;
+    if (null === oldProps) newValue = 1073741823;
+    else if (oldProps.value === newProps.value) {
+      if (oldProps.children === newProps.children)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+      newValue = 0;
+    } else {
+      var oldValue = oldProps.value;
+      if (
+        (oldValue === newValue &&
+          (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
+        (oldValue !== oldValue && newValue !== newValue)
+      ) {
+        if (oldProps.children === newProps.children)
+          return (
+            (workInProgress.stateNode = 0),
+            pushProvider(workInProgress),
+            bailoutOnAlreadyFinishedWork(current, workInProgress)
+          );
+        newValue = 0;
+      } else if (
+        ((newValue =
+          "function" === typeof context._calculateChangedBits
+            ? context._calculateChangedBits(oldValue, newValue)
+            : 1073741823),
+        (newValue |= 0),
+        0 === newValue)
+      ) {
+        if (oldProps.children === newProps.children)
+          return (
+            (workInProgress.stateNode = 0),
+            pushProvider(workInProgress),
+            bailoutOnAlreadyFinishedWork(current, workInProgress)
+          );
+      } else
+        propagateContextChange(
+          workInProgress,
+          context,
+          newValue,
+          renderExpirationTime
+        );
+    }
+    workInProgress.stateNode = newValue;
+    pushProvider(workInProgress);
+    reconcileChildren(current, workInProgress, newProps.children);
+    return workInProgress.child;
+  }
+  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+    invariant(
+      null === current || workInProgress.child === current.child,
+      "Resuming work not yet implemented."
+    );
+    if (null !== workInProgress.child) {
+      current = workInProgress.child;
+      var newChild = createWorkInProgress(
+        current,
+        current.pendingProps,
+        current.expirationTime
+      );
+      workInProgress.child = newChild;
+      for (newChild["return"] = workInProgress; null !== current.sibling; )
+        (current = current.sibling),
+          (newChild = newChild.sibling = createWorkInProgress(
+            current,
+            current.pendingProps,
+            current.expirationTime
+          )),
+          (newChild["return"] = workInProgress);
+      newChild.sibling = null;
+    }
+    return workInProgress.child;
+  }
+  var shouldSetTextContent = config.shouldSetTextContent,
+    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree,
+    pushHostContext = hostContext.pushHostContext,
+    pushHostContainer = hostContext.pushHostContainer,
+    pushProvider = newContext.pushProvider,
+    getMaskedContext = legacyContext.getMaskedContext,
+    getUnmaskedContext = legacyContext.getUnmaskedContext,
+    hasLegacyContextChanged = legacyContext.hasContextChanged,
+    pushLegacyContextProvider = legacyContext.pushContextProvider,
+    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
+    invalidateContextProvider = legacyContext.invalidateContextProvider,
+    enterHydrationState = hydrationContext.enterHydrationState,
+    resetHydrationState = hydrationContext.resetHydrationState,
+    tryToClaimNextHydratableInstance =
+      hydrationContext.tryToClaimNextHydratableInstance;
+  config = ReactFiberClassComponent(
+    legacyContext,
+    scheduleWork,
+    computeExpirationForFiber,
+    function(workInProgress, nextProps) {
+      workInProgress.memoizedProps = nextProps;
+    },
+    function(workInProgress, nextState) {
+      workInProgress.memoizedState = nextState;
+    }
+  );
+  var adoptClassInstance = config.adoptClassInstance,
+    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
+    constructClassInstance = config.constructClassInstance,
+    mountClassInstance = config.mountClassInstance,
+    resumeMountClassInstance = config.resumeMountClassInstance,
+    updateClassInstance = config.updateClassInstance;
+  return {
+    beginWork: function(current, workInProgress, renderExpirationTime) {
+      if (
+        0 === workInProgress.expirationTime ||
+        workInProgress.expirationTime > renderExpirationTime
+      ) {
+        switch (workInProgress.tag) {
+          case 3:
+            pushHostRootContext(workInProgress);
+            break;
+          case 2:
+            pushLegacyContextProvider(workInProgress);
+            break;
+          case 4:
+            pushHostContainer(
+              workInProgress,
+              workInProgress.stateNode.containerInfo
+            );
+            break;
+          case 13:
+            pushProvider(workInProgress);
+        }
+        return null;
+      }
+      switch (workInProgress.tag) {
+        case 0:
+          invariant(
+            null === current,
+            "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
+          );
+          var fn = workInProgress.type,
+            props = workInProgress.pendingProps,
+            unmaskedContext = getUnmaskedContext(workInProgress);
+          unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
+          fn = fn(props, unmaskedContext);
+          workInProgress.effectTag |= 1;
+          "object" === typeof fn &&
+          null !== fn &&
+          "function" === typeof fn.render &&
+          void 0 === fn.$$typeof
+            ? ((unmaskedContext = workInProgress.type),
+              (workInProgress.tag = 2),
+              (workInProgress.memoizedState =
+                null !== fn.state && void 0 !== fn.state ? fn.state : null),
+              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
+                ((props = callGetDerivedStateFromProps(
+                  workInProgress,
+                  fn,
+                  props,
+                  workInProgress.memoizedState
+                )),
+                null !== props &&
+                  void 0 !== props &&
+                  (workInProgress.memoizedState = Object.assign(
+                    {},
+                    workInProgress.memoizedState,
+                    props
+                  ))),
+              (props = pushLegacyContextProvider(workInProgress)),
+              adoptClassInstance(workInProgress, fn),
+              mountClassInstance(workInProgress, renderExpirationTime),
+              (current = finishClassComponent(
+                current,
+                workInProgress,
+                !0,
+                props,
+                !1,
+                renderExpirationTime
+              )))
+            : ((workInProgress.tag = 1),
+              reconcileChildren(current, workInProgress, fn),
+              (workInProgress.memoizedProps = props),
+              (current = workInProgress.child));
+          return current;
+        case 1:
+          return (
+            (props = workInProgress.type),
+            (renderExpirationTime = workInProgress.pendingProps),
+            hasLegacyContextChanged() ||
+            workInProgress.memoizedProps !== renderExpirationTime
+              ? ((fn = getUnmaskedContext(workInProgress)),
+                (fn = getMaskedContext(workInProgress, fn)),
+                (props = props(renderExpirationTime, fn)),
+                (workInProgress.effectTag |= 1),
+                reconcileChildren(current, workInProgress, props),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
+        case 2:
+          props = pushLegacyContextProvider(workInProgress);
+          null === current
+            ? null === workInProgress.stateNode
+              ? (constructClassInstance(
+                  workInProgress,
+                  workInProgress.pendingProps
+                ),
+                mountClassInstance(workInProgress, renderExpirationTime),
+                (fn = !0))
+              : (fn = resumeMountClassInstance(
+                  workInProgress,
+                  renderExpirationTime
+                ))
+            : (fn = updateClassInstance(
+                current,
+                workInProgress,
+                renderExpirationTime
+              ));
+          unmaskedContext = !1;
+          var updateQueue = workInProgress.updateQueue;
+          null !== updateQueue &&
+            null !== updateQueue.capturedValues &&
+            (unmaskedContext = fn = !0);
+          return finishClassComponent(
+            current,
+            workInProgress,
+            fn,
+            props,
+            unmaskedContext,
+            renderExpirationTime
+          );
+        case 3:
+          a: if (
+            (pushHostRootContext(workInProgress),
+            (fn = workInProgress.updateQueue),
+            null !== fn)
+          ) {
+            unmaskedContext = workInProgress.memoizedState;
+            props = processUpdateQueue(
+              current,
+              workInProgress,
+              fn,
+              null,
+              null,
+              renderExpirationTime
+            );
+            workInProgress.memoizedState = props;
+            fn = workInProgress.updateQueue;
+            if (null !== fn && null !== fn.capturedValues) fn = null;
+            else if (unmaskedContext === props) {
+              resetHydrationState();
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+              break a;
+            } else fn = props.element;
+            unmaskedContext = workInProgress.stateNode;
+            (null === current || null === current.child) &&
+            unmaskedContext.hydrate &&
+            enterHydrationState(workInProgress)
+              ? ((workInProgress.effectTag |= 2),
+                (workInProgress.child = mountChildFibers(
+                  workInProgress,
+                  null,
+                  fn,
+                  renderExpirationTime
+                )))
+              : (resetHydrationState(),
+                reconcileChildren(current, workInProgress, fn));
+            workInProgress.memoizedState = props;
+            current = workInProgress.child;
+          } else
+            resetHydrationState(),
+              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
+          return current;
+        case 5:
+          a: {
+            pushHostContext(workInProgress);
+            null === current &&
+              tryToClaimNextHydratableInstance(workInProgress);
+            props = workInProgress.type;
+            updateQueue = workInProgress.memoizedProps;
+            fn = workInProgress.pendingProps;
+            unmaskedContext = null !== current ? current.memoizedProps : null;
+            if (!hasLegacyContextChanged() && updateQueue === fn) {
+              if (
+                (updateQueue =
+                  workInProgress.mode & 1 &&
+                  shouldDeprioritizeSubtree(props, fn))
+              )
+                workInProgress.expirationTime = 1073741823;
+              if (!updateQueue || 1073741823 !== renderExpirationTime) {
+                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+                break a;
+              }
+            }
+            updateQueue = fn.children;
+            shouldSetTextContent(props, fn)
+              ? (updateQueue = null)
+              : unmaskedContext &&
+                shouldSetTextContent(props, unmaskedContext) &&
+                (workInProgress.effectTag |= 16);
+            markRef(current, workInProgress);
+            1073741823 !== renderExpirationTime &&
+            workInProgress.mode & 1 &&
+            shouldDeprioritizeSubtree(props, fn)
+              ? ((workInProgress.expirationTime = 1073741823),
+                (workInProgress.memoizedProps = fn),
+                (current = null))
+              : (reconcileChildren(current, workInProgress, updateQueue),
+                (workInProgress.memoizedProps = fn),
+                (current = workInProgress.child));
+          }
+          return current;
+        case 6:
+          return (
+            null === current &&
+              tryToClaimNextHydratableInstance(workInProgress),
+            (workInProgress.memoizedProps = workInProgress.pendingProps),
+            null
+          );
+        case 8:
+          workInProgress.tag = 7;
+        case 7:
+          return (
+            (props = workInProgress.pendingProps),
+            hasLegacyContextChanged() ||
+              workInProgress.memoizedProps !== props ||
+              (props = workInProgress.memoizedProps),
+            (fn = props.children),
+            (workInProgress.stateNode =
+              null === current
+                ? mountChildFibers(
+                    workInProgress,
+                    workInProgress.stateNode,
+                    fn,
+                    renderExpirationTime
+                  )
+                : reconcileChildFibers(
+                    workInProgress,
+                    current.stateNode,
+                    fn,
+                    renderExpirationTime
+                  )),
+            (workInProgress.memoizedProps = props),
+            workInProgress.stateNode
+          );
+        case 9:
+          return null;
+        case 4:
+          return (
+            pushHostContainer(
+              workInProgress,
+              workInProgress.stateNode.containerInfo
+            ),
+            (props = workInProgress.pendingProps),
+            hasLegacyContextChanged() || workInProgress.memoizedProps !== props
+              ? (null === current
+                  ? (workInProgress.child = reconcileChildFibers(
+                      workInProgress,
+                      null,
+                      props,
+                      renderExpirationTime
+                    ))
+                  : reconcileChildren(current, workInProgress, props),
+                (workInProgress.memoizedProps = props),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
+        case 14:
+          return (
+            (renderExpirationTime = workInProgress.type.render),
+            (renderExpirationTime = renderExpirationTime(
+              workInProgress.pendingProps,
+              workInProgress.ref
+            )),
+            reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            workInProgress.child
+          );
+        case 10:
+          return (
+            (renderExpirationTime = workInProgress.pendingProps),
+            hasLegacyContextChanged() ||
+            workInProgress.memoizedProps !== renderExpirationTime
+              ? (reconcileChildren(
+                  current,
+                  workInProgress,
+                  renderExpirationTime
+                ),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
+        case 11:
+          return (
+            (renderExpirationTime = workInProgress.pendingProps.children),
+            hasLegacyContextChanged() ||
+            (null !== renderExpirationTime &&
+              workInProgress.memoizedProps !== renderExpirationTime)
+              ? (reconcileChildren(
+                  current,
+                  workInProgress,
+                  renderExpirationTime
+                ),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
+        case 13:
+          return updateContextProvider(
+            current,
+            workInProgress,
+            renderExpirationTime
+          );
+        case 12:
+          a: {
+            fn = workInProgress.type;
+            unmaskedContext = workInProgress.pendingProps;
+            updateQueue = workInProgress.memoizedProps;
+            props = fn._currentValue;
+            var changedBits = fn._changedBits;
+            if (
+              hasLegacyContextChanged() ||
+              0 !== changedBits ||
+              updateQueue !== unmaskedContext
+            ) {
+              workInProgress.memoizedProps = unmaskedContext;
+              var observedBits = unmaskedContext.unstable_observedBits;
+              if (void 0 === observedBits || null === observedBits)
+                observedBits = 1073741823;
+              workInProgress.stateNode = observedBits;
+              if (0 !== (changedBits & observedBits))
+                propagateContextChange(
+                  workInProgress,
+                  fn,
+                  changedBits,
+                  renderExpirationTime
+                );
+              else if (updateQueue === unmaskedContext) {
+                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+                break a;
+              }
+              renderExpirationTime = unmaskedContext.children;
+              renderExpirationTime = renderExpirationTime(props);
+              reconcileChildren(current, workInProgress, renderExpirationTime);
+              current = workInProgress.child;
+            } else
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+          return current;
+        default:
+          invariant(
+            !1,
+            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    }
+  };
+}
+function ReactFiberCompleteWork(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  hydrationContext
+) {
+  function markUpdate(workInProgress) {
+    workInProgress.effectTag |= 4;
+  }
+  var createInstance = config.createInstance,
+    createTextInstance = config.createTextInstance,
+    appendInitialChild = config.appendInitialChild,
+    finalizeInitialChildren = config.finalizeInitialChildren,
+    prepareUpdate = config.prepareUpdate,
+    persistence = config.persistence,
+    getRootHostContainer = hostContext.getRootHostContainer,
+    popHostContext = hostContext.popHostContext,
+    getHostContext = hostContext.getHostContext,
+    popHostContainer = hostContext.popHostContainer,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider,
+    prepareToHydrateHostInstance =
+      hydrationContext.prepareToHydrateHostInstance,
+    prepareToHydrateHostTextInstance =
+      hydrationContext.prepareToHydrateHostTextInstance,
+    popHydrationState = hydrationContext.popHydrationState,
+    updateHostContainer = void 0,
+    updateHostComponent = void 0,
+    updateHostText = void 0;
+  config.mutation
+    ? ((updateHostContainer = function() {}),
+      (updateHostComponent = function(current, workInProgress, updatePayload) {
+        (workInProgress.updateQueue = updatePayload) &&
+          markUpdate(workInProgress);
+      }),
+      (updateHostText = function(current, workInProgress, oldText, newText) {
+        oldText !== newText && markUpdate(workInProgress);
+      }))
+    : persistence
+      ? invariant(!1, "Persistent reconciler is disabled.")
+      : invariant(!1, "Noop reconciler is disabled.");
+  return {
+    completeWork: function(current, workInProgress, renderExpirationTime) {
+      var newProps = workInProgress.pendingProps;
+      switch (workInProgress.tag) {
+        case 1:
+          return null;
+        case 2:
+          return (
+            popLegacyContextProvider(workInProgress),
+            (current = workInProgress.stateNode),
+            (newProps = workInProgress.updateQueue),
+            null !== newProps &&
+              null !== newProps.capturedValues &&
+              ((workInProgress.effectTag &= -65),
+              "function" === typeof current.componentDidCatch
+                ? (workInProgress.effectTag |= 256)
+                : (newProps.capturedValues = null)),
+            null
+          );
+        case 3:
+          popHostContainer(workInProgress);
+          popTopLevelLegacyContextObject(workInProgress);
+          newProps = workInProgress.stateNode;
+          newProps.pendingContext &&
+            ((newProps.context = newProps.pendingContext),
+            (newProps.pendingContext = null));
+          if (null === current || null === current.child)
+            popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
+          updateHostContainer(workInProgress);
+          current = workInProgress.updateQueue;
+          null !== current &&
+            null !== current.capturedValues &&
+            (workInProgress.effectTag |= 256);
+          return null;
+        case 5:
+          popHostContext(workInProgress);
+          renderExpirationTime = getRootHostContainer();
+          var type = workInProgress.type;
+          if (null !== current && null != workInProgress.stateNode) {
+            var oldProps = current.memoizedProps,
+              _instance = workInProgress.stateNode,
+              currentHostContext = getHostContext();
+            _instance = prepareUpdate(
+              _instance,
+              type,
+              oldProps,
+              newProps,
+              renderExpirationTime,
+              currentHostContext
+            );
+            updateHostComponent(
+              current,
+              workInProgress,
+              _instance,
+              type,
+              oldProps,
+              newProps,
+              renderExpirationTime,
+              currentHostContext
+            );
+            current.ref !== workInProgress.ref &&
+              (workInProgress.effectTag |= 128);
+          } else {
+            if (!newProps)
+              return (
+                invariant(
+                  null !== workInProgress.stateNode,
+                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+                ),
+                null
+              );
+            current = getHostContext();
+            if (popHydrationState(workInProgress))
+              prepareToHydrateHostInstance(
+                workInProgress,
+                renderExpirationTime,
+                current
+              ) && markUpdate(workInProgress);
+            else {
+              oldProps = createInstance(
+                type,
+                newProps,
+                renderExpirationTime,
+                current,
+                workInProgress
+              );
+              a: for (
+                currentHostContext = workInProgress.child;
+                null !== currentHostContext;
+
+              ) {
+                if (
+                  5 === currentHostContext.tag ||
+                  6 === currentHostContext.tag
+                )
+                  appendInitialChild(oldProps, currentHostContext.stateNode);
+                else if (
+                  4 !== currentHostContext.tag &&
+                  null !== currentHostContext.child
+                ) {
+                  currentHostContext.child["return"] = currentHostContext;
+                  currentHostContext = currentHostContext.child;
+                  continue;
+                }
+                if (currentHostContext === workInProgress) break;
+                for (; null === currentHostContext.sibling; ) {
+                  if (
+                    null === currentHostContext["return"] ||
+                    currentHostContext["return"] === workInProgress
+                  )
+                    break a;
+                  currentHostContext = currentHostContext["return"];
+                }
+                currentHostContext.sibling["return"] =
+                  currentHostContext["return"];
+                currentHostContext = currentHostContext.sibling;
+              }
+              finalizeInitialChildren(
+                oldProps,
+                type,
+                newProps,
+                renderExpirationTime,
+                current
+              ) && markUpdate(workInProgress);
+              workInProgress.stateNode = oldProps;
+            }
+            null !== workInProgress.ref && (workInProgress.effectTag |= 128);
+          }
+          return null;
+        case 6:
+          if (current && null != workInProgress.stateNode)
+            updateHostText(
+              current,
+              workInProgress,
+              current.memoizedProps,
+              newProps
+            );
+          else {
+            if ("string" !== typeof newProps)
+              return (
+                invariant(
+                  null !== workInProgress.stateNode,
+                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+                ),
+                null
+              );
+            current = getRootHostContainer();
+            renderExpirationTime = getHostContext();
+            popHydrationState(workInProgress)
+              ? prepareToHydrateHostTextInstance(workInProgress) &&
+                markUpdate(workInProgress)
+              : (workInProgress.stateNode = createTextInstance(
+                  newProps,
+                  current,
+                  renderExpirationTime,
+                  workInProgress
+                ));
+          }
+          return null;
+        case 7:
+          newProps = workInProgress.memoizedProps;
+          invariant(
+            newProps,
+            "Should be resolved by now. This error is likely caused by a bug in React. Please file an issue."
+          );
+          workInProgress.tag = 8;
+          type = [];
+          a: for (
+            (oldProps = workInProgress.stateNode) &&
+            (oldProps["return"] = workInProgress);
+            null !== oldProps;
+
+          ) {
+            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
+              invariant(!1, "A call cannot have host component children.");
+            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
+            else if (null !== oldProps.child) {
+              oldProps.child["return"] = oldProps;
+              oldProps = oldProps.child;
+              continue;
+            }
+            for (; null === oldProps.sibling; ) {
+              if (
+                null === oldProps["return"] ||
+                oldProps["return"] === workInProgress
+              )
+                break a;
+              oldProps = oldProps["return"];
+            }
+            oldProps.sibling["return"] = oldProps["return"];
+            oldProps = oldProps.sibling;
+          }
+          oldProps = newProps.handler;
+          newProps = oldProps(newProps.props, type);
+          workInProgress.child = reconcileChildFibers(
+            workInProgress,
+            null !== current ? current.child : null,
+            newProps,
+            renderExpirationTime
+          );
+          return workInProgress.child;
+        case 8:
+          return (workInProgress.tag = 7), null;
+        case 9:
+          return null;
+        case 14:
+          return null;
+        case 10:
+          return null;
+        case 11:
+          return null;
+        case 4:
+          return (
+            popHostContainer(workInProgress),
+            updateHostContainer(workInProgress),
+            null
+          );
+        case 13:
+          return popProvider(workInProgress), null;
+        case 12:
+          return null;
+        case 0:
+          invariant(
+            !1,
+            "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
+          );
+        default:
+          invariant(
+            !1,
+            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    }
+  };
+}
+function ReactFiberUnwindWork(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  isAlreadyFailedLegacyErrorBoundary
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
+  return {
+    throwException: function(returnFiber, sourceFiber, rawValue) {
+      sourceFiber.effectTag |= 512;
+      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+      sourceFiber = {
+        value: rawValue,
+        source: sourceFiber,
+        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
+      };
+      do {
+        switch (returnFiber.tag) {
+          case 3:
+            ensureUpdateQueues(returnFiber);
+            returnFiber.updateQueue.capturedValues = [sourceFiber];
+            returnFiber.effectTag |= 1024;
+            return;
+          case 2:
+            if (
+              ((rawValue = returnFiber.stateNode),
+              0 === (returnFiber.effectTag & 64) &&
+                null !== rawValue &&
+                "function" === typeof rawValue.componentDidCatch &&
+                !isAlreadyFailedLegacyErrorBoundary(rawValue))
+            ) {
+              ensureUpdateQueues(returnFiber);
+              rawValue = returnFiber.updateQueue;
+              var capturedValues = rawValue.capturedValues;
+              null === capturedValues
+                ? (rawValue.capturedValues = [sourceFiber])
+                : capturedValues.push(sourceFiber);
+              returnFiber.effectTag |= 1024;
+              return;
+            }
+        }
+        returnFiber = returnFiber["return"];
+      } while (null !== returnFiber);
+    },
+    unwindWork: function(workInProgress) {
+      switch (workInProgress.tag) {
+        case 2:
+          popLegacyContextProvider(workInProgress);
+          var effectTag = workInProgress.effectTag;
+          return effectTag & 1024
+            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+              workInProgress)
+            : null;
+        case 3:
+          return (
+            popHostContainer(workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 5:
+          return popHostContext(workInProgress), null;
+        case 4:
+          return popHostContainer(workInProgress), null;
+        case 13:
+          return popProvider(workInProgress), null;
+        default:
+          return null;
+      }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
+    }
+  };
+}
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source,
+    stack = errorInfo.stack;
+  null === stack && (stack = getStackAddendumByWorkInProgressFiber(source));
+  null !== source && getComponentName(source);
+  source = null !== stack ? stack : "";
+  errorInfo = errorInfo.value;
+  null !== boundary && 2 === boundary.tag && getComponentName(boundary);
+  try {
+    if (errorInfo instanceof Error) {
+      var message = errorInfo.message,
+        name = errorInfo.name;
+      var errorToHandle = errorInfo;
+      try {
+        errorToHandle.message =
+          (message ? name + ": " + message : name) +
+          "\n\nThis error is located at:" +
+          source;
+      } catch (e) {}
+    } else
+      errorToHandle =
+        "string" === typeof errorInfo
+          ? Error(errorInfo + "\n\nThis error is located at:" + source)
+          : Error("Unspecified error at:" + source);
+    ExceptionsManager.handleException(errorToHandle, !1);
+  } catch (e) {
+    (e && e.suppressReactErrorLogging) || console.error(e);
+  }
+}
+function ReactFiberCommitWork(
+  config,
+  captureError,
+  scheduleWork,
+  computeExpirationForFiber,
+  markLegacyErrorBoundaryAsFailed
+) {
+  function safelyDetachRef(current) {
+    var ref = current.ref;
+    if (null !== ref)
+      if ("function" === typeof ref)
+        try {
+          ref(null);
+        } catch (refError) {
+          captureError(current, refError);
+        }
+      else ref.current = null;
+  }
+  function commitUnmount(current) {
+    "function" === typeof onCommitUnmount && onCommitUnmount(current);
+    switch (current.tag) {
+      case 2:
+        safelyDetachRef(current);
+        var _instance7 = current.stateNode;
+        if ("function" === typeof _instance7.componentWillUnmount)
+          try {
+            (_instance7.props = current.memoizedProps),
+              (_instance7.state = current.memoizedState),
+              _instance7.componentWillUnmount();
+          } catch (unmountError) {
+            captureError(current, unmountError);
+          }
+        break;
+      case 5:
+        safelyDetachRef(current);
+        break;
+      case 7:
+        commitNestedUnmounts(current.stateNode);
+        break;
+      case 4:
+        mutation && unmountHostComponents(current);
+    }
+  }
+  function commitNestedUnmounts(root) {
+    for (var node = root; ; )
+      if (
+        (commitUnmount(node),
+        null === node.child || (mutation && 4 === node.tag))
+      ) {
+        if (node === root) break;
+        for (; null === node.sibling; ) {
+          if (null === node["return"] || node["return"] === root) return;
+          node = node["return"];
+        }
+        node.sibling["return"] = node["return"];
+        node = node.sibling;
+      } else (node.child["return"] = node), (node = node.child);
+  }
+  function isHostParent(fiber) {
+    return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
+  }
+  function unmountHostComponents(current) {
+    for (
+      var node = current,
+        currentParentIsValid = !1,
+        currentParent = void 0,
+        currentParentIsContainer = void 0;
+      ;
+
+    ) {
+      if (!currentParentIsValid) {
+        currentParentIsValid = node["return"];
+        a: for (;;) {
+          invariant(
+            null !== currentParentIsValid,
+            "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
+          );
+          switch (currentParentIsValid.tag) {
+            case 5:
+              currentParent = currentParentIsValid.stateNode;
+              currentParentIsContainer = !1;
+              break a;
+            case 3:
+              currentParent = currentParentIsValid.stateNode.containerInfo;
+              currentParentIsContainer = !0;
+              break a;
+            case 4:
+              currentParent = currentParentIsValid.stateNode.containerInfo;
+              currentParentIsContainer = !0;
+              break a;
+          }
+          currentParentIsValid = currentParentIsValid["return"];
+        }
+        currentParentIsValid = !0;
+      }
+      if (5 === node.tag || 6 === node.tag)
+        commitNestedUnmounts(node),
+          currentParentIsContainer
+            ? removeChildFromContainer(currentParent, node.stateNode)
+            : removeChild(currentParent, node.stateNode);
+      else if (
+        (4 === node.tag
+          ? (currentParent = node.stateNode.containerInfo)
+          : commitUnmount(node),
+        null !== node.child)
+      ) {
+        node.child["return"] = node;
+        node = node.child;
+        continue;
+      }
+      if (node === current) break;
+      for (; null === node.sibling; ) {
+        if (null === node["return"] || node["return"] === current) return;
+        node = node["return"];
+        4 === node.tag && (currentParentIsValid = !1);
+      }
+      node.sibling["return"] = node["return"];
+      node = node.sibling;
+    }
+  }
+  var getPublicInstance = config.getPublicInstance,
+    mutation = config.mutation;
+  config = config.persistence;
+  mutation ||
+    (config
+      ? invariant(!1, "Persistent reconciler is disabled.")
+      : invariant(!1, "Noop reconciler is disabled."));
+  var commitMount = mutation.commitMount,
+    commitUpdate = mutation.commitUpdate,
+    resetTextContent = mutation.resetTextContent,
+    commitTextUpdate = mutation.commitTextUpdate,
+    appendChild = mutation.appendChild,
+    appendChildToContainer = mutation.appendChildToContainer,
+    insertBefore = mutation.insertBefore,
+    insertInContainerBefore = mutation.insertInContainerBefore,
+    removeChild = mutation.removeChild,
+    removeChildFromContainer = mutation.removeChildFromContainer;
+  return {
+    commitBeforeMutationLifeCycles: function(current, finishedWork) {
+      switch (finishedWork.tag) {
+        case 2:
+          if (finishedWork.effectTag & 2048 && null !== current) {
+            var prevProps = current.memoizedProps,
+              prevState = current.memoizedState;
+            current = finishedWork.stateNode;
+            current.props = finishedWork.memoizedProps;
+            current.state = finishedWork.memoizedState;
+            finishedWork = current.getSnapshotBeforeUpdate(
+              prevProps,
+              prevState
+            );
+            current.__reactInternalSnapshotBeforeUpdate = finishedWork;
+          }
+          break;
+        case 3:
+        case 5:
+        case 6:
+        case 4:
+          break;
+        default:
+          invariant(
+            !1,
+            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    },
+    commitResetTextContent: function(current) {
+      resetTextContent(current.stateNode);
+    },
+    commitPlacement: function(finishedWork) {
+      a: {
+        for (var parent = finishedWork["return"]; null !== parent; ) {
+          if (isHostParent(parent)) {
+            var parentFiber = parent;
+            break a;
+          }
+          parent = parent["return"];
+        }
+        invariant(
+          !1,
+          "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+        parentFiber = void 0;
+      }
+      var isContainer = (parent = void 0);
+      switch (parentFiber.tag) {
+        case 5:
+          parent = parentFiber.stateNode;
+          isContainer = !1;
+          break;
+        case 3:
+          parent = parentFiber.stateNode.containerInfo;
+          isContainer = !0;
+          break;
+        case 4:
+          parent = parentFiber.stateNode.containerInfo;
+          isContainer = !0;
+          break;
+        default:
+          invariant(
+            !1,
+            "Invalid host parent fiber. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+      parentFiber.effectTag & 16 &&
+        (resetTextContent(parent), (parentFiber.effectTag &= -17));
+      a: b: for (parentFiber = finishedWork; ; ) {
+        for (; null === parentFiber.sibling; ) {
+          if (
+            null === parentFiber["return"] ||
+            isHostParent(parentFiber["return"])
+          ) {
+            parentFiber = null;
+            break a;
+          }
+          parentFiber = parentFiber["return"];
+        }
+        parentFiber.sibling["return"] = parentFiber["return"];
+        for (
+          parentFiber = parentFiber.sibling;
+          5 !== parentFiber.tag && 6 !== parentFiber.tag;
+
+        ) {
+          if (parentFiber.effectTag & 2) continue b;
+          if (null === parentFiber.child || 4 === parentFiber.tag) continue b;
+          else
+            (parentFiber.child["return"] = parentFiber),
+              (parentFiber = parentFiber.child);
+        }
+        if (!(parentFiber.effectTag & 2)) {
+          parentFiber = parentFiber.stateNode;
+          break a;
+        }
+      }
+      for (var node = finishedWork; ; ) {
+        if (5 === node.tag || 6 === node.tag)
+          parentFiber
+            ? isContainer
+              ? insertInContainerBefore(parent, node.stateNode, parentFiber)
+              : insertBefore(parent, node.stateNode, parentFiber)
+            : isContainer
+              ? appendChildToContainer(parent, node.stateNode)
+              : appendChild(parent, node.stateNode);
+        else if (4 !== node.tag && null !== node.child) {
+          node.child["return"] = node;
+          node = node.child;
+          continue;
+        }
+        if (node === finishedWork) break;
+        for (; null === node.sibling; ) {
+          if (null === node["return"] || node["return"] === finishedWork)
+            return;
+          node = node["return"];
+        }
+        node.sibling["return"] = node["return"];
+        node = node.sibling;
+      }
+    },
+    commitDeletion: function(current) {
+      unmountHostComponents(current);
+      current["return"] = null;
+      current.child = null;
+      current.alternate &&
+        ((current.alternate.child = null),
+        (current.alternate["return"] = null));
+    },
+    commitWork: function(current, finishedWork) {
+      switch (finishedWork.tag) {
+        case 2:
+          break;
+        case 5:
+          var _instance8 = finishedWork.stateNode;
+          if (null != _instance8) {
+            var newProps = finishedWork.memoizedProps;
+            current = null !== current ? current.memoizedProps : newProps;
+            var type = finishedWork.type,
+              updatePayload = finishedWork.updateQueue;
+            finishedWork.updateQueue = null;
+            null !== updatePayload &&
+              commitUpdate(
+                _instance8,
+                updatePayload,
+                type,
+                current,
+                newProps,
+                finishedWork
+              );
+          }
+          break;
+        case 6:
+          invariant(
+            null !== finishedWork.stateNode,
+            "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
+          );
+          _instance8 = finishedWork.memoizedProps;
+          commitTextUpdate(
+            finishedWork.stateNode,
+            null !== current ? current.memoizedProps : _instance8,
+            _instance8
+          );
+          break;
+        case 3:
+          break;
+        default:
+          invariant(
+            !1,
+            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    },
+    commitLifeCycles: function(finishedRoot, current, finishedWork) {
+      switch (finishedWork.tag) {
+        case 2:
+          finishedRoot = finishedWork.stateNode;
+          if (finishedWork.effectTag & 4)
+            if (null === current)
+              (finishedRoot.props = finishedWork.memoizedProps),
+                (finishedRoot.state = finishedWork.memoizedState),
+                finishedRoot.componentDidMount();
+            else {
+              var prevProps = current.memoizedProps;
+              current = current.memoizedState;
+              finishedRoot.props = finishedWork.memoizedProps;
+              finishedRoot.state = finishedWork.memoizedState;
+              finishedRoot.componentDidUpdate(
+                prevProps,
+                current,
+                finishedRoot.__reactInternalSnapshotBeforeUpdate
+              );
+            }
+          finishedWork = finishedWork.updateQueue;
+          null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
+          break;
+        case 3:
+          current = finishedWork.updateQueue;
+          if (null !== current) {
+            finishedRoot = null;
+            if (null !== finishedWork.child)
+              switch (finishedWork.child.tag) {
+                case 5:
+                  finishedRoot = getPublicInstance(
+                    finishedWork.child.stateNode
+                  );
+                  break;
+                case 2:
+                  finishedRoot = finishedWork.child.stateNode;
+              }
+            commitCallbacks(current, finishedRoot);
+          }
+          break;
+        case 5:
+          finishedRoot = finishedWork.stateNode;
+          null === current &&
+            finishedWork.effectTag & 4 &&
+            commitMount(
+              finishedRoot,
+              finishedWork.type,
+              finishedWork.memoizedProps,
+              finishedWork
+            );
+          break;
+        case 6:
+          break;
+        case 4:
+          break;
+        default:
+          invariant(
+            !1,
+            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    },
+    commitErrorLogging: function(finishedWork, onUncaughtError) {
+      switch (finishedWork.tag) {
+        case 2:
+          var ctor = finishedWork.type;
+          onUncaughtError = finishedWork.stateNode;
+          var updateQueue = finishedWork.updateQueue;
+          invariant(
+            null !== updateQueue && null !== updateQueue.capturedValues,
+            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
+          );
+          var capturedErrors = updateQueue.capturedValues;
+          updateQueue.capturedValues = null;
+          "function" !== typeof ctor.getDerivedStateFromCatch &&
+            markLegacyErrorBoundaryAsFailed(onUncaughtError);
+          onUncaughtError.props = finishedWork.memoizedProps;
+          onUncaughtError.state = finishedWork.memoizedState;
+          for (ctor = 0; ctor < capturedErrors.length; ctor++) {
+            updateQueue = capturedErrors[ctor];
+            var _error = updateQueue.value,
+              stack = updateQueue.stack;
+            logError(finishedWork, updateQueue);
+            onUncaughtError.componentDidCatch(_error, {
+              componentStack: null !== stack ? stack : ""
+            });
+          }
+          break;
+        case 3:
+          ctor = finishedWork.updateQueue;
+          invariant(
+            null !== ctor && null !== ctor.capturedValues,
+            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
+          );
+          capturedErrors = ctor.capturedValues;
+          ctor.capturedValues = null;
+          for (ctor = 0; ctor < capturedErrors.length; ctor++)
+            (updateQueue = capturedErrors[ctor]),
+              logError(finishedWork, updateQueue),
+              onUncaughtError(updateQueue.value);
+          break;
+        default:
+          invariant(
+            !1,
+            "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    },
+    commitAttachRef: function(finishedWork) {
+      var ref = finishedWork.ref;
+      if (null !== ref) {
+        var _instance6 = finishedWork.stateNode;
+        switch (finishedWork.tag) {
+          case 5:
+            finishedWork = getPublicInstance(_instance6);
+            break;
+          default:
+            finishedWork = _instance6;
+        }
+        "function" === typeof ref
+          ? ref(finishedWork)
+          : (ref.current = finishedWork);
+      }
+    },
+    commitDetachRef: function(current) {
+      current = current.ref;
+      null !== current &&
+        ("function" === typeof current
+          ? current(null)
+          : (current.current = null));
+    }
+  };
+}
+var NO_CONTEXT = {};
+function ReactFiberHostContext(config, stack) {
+  function requiredContext(c) {
+    invariant(
+      c !== NO_CONTEXT,
+      "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
+    );
+    return c;
+  }
+  var getChildHostContext = config.getChildHostContext,
+    getRootHostContext = config.getRootHostContext;
+  config = stack.createCursor;
+  var push = stack.push,
+    pop = stack.pop,
+    contextStackCursor = config(NO_CONTEXT),
+    contextFiberStackCursor = config(NO_CONTEXT),
+    rootInstanceStackCursor = config(NO_CONTEXT);
+  return {
+    getHostContext: function() {
+      return requiredContext(contextStackCursor.current);
+    },
+    getRootHostContainer: function() {
+      return requiredContext(rootInstanceStackCursor.current);
+    },
+    popHostContainer: function(fiber) {
+      pop(contextStackCursor, fiber);
+      pop(contextFiberStackCursor, fiber);
+      pop(rootInstanceStackCursor, fiber);
+    },
+    popHostContext: function(fiber) {
+      contextFiberStackCursor.current === fiber &&
+        (pop(contextStackCursor, fiber), pop(contextFiberStackCursor, fiber));
+    },
+    pushHostContainer: function(fiber, nextRootInstance) {
+      push(rootInstanceStackCursor, nextRootInstance, fiber);
+      push(contextFiberStackCursor, fiber, fiber);
+      push(contextStackCursor, NO_CONTEXT, fiber);
+      nextRootInstance = getRootHostContext(nextRootInstance);
+      pop(contextStackCursor, fiber);
+      push(contextStackCursor, nextRootInstance, fiber);
+    },
+    pushHostContext: function(fiber) {
+      var rootInstance = requiredContext(rootInstanceStackCursor.current),
+        context = requiredContext(contextStackCursor.current);
+      rootInstance = getChildHostContext(context, fiber.type, rootInstance);
+      context !== rootInstance &&
+        (push(contextFiberStackCursor, fiber, fiber),
+        push(contextStackCursor, rootInstance, fiber));
+    }
+  };
+}
+function ReactFiberHydrationContext(config) {
+  function deleteHydratableInstance(returnFiber, instance) {
+    var fiber = new FiberNode(5, null, null, 0);
+    fiber.type = "DELETED";
+    fiber.stateNode = instance;
+    fiber["return"] = returnFiber;
+    fiber.effectTag = 8;
+    null !== returnFiber.lastEffect
+      ? ((returnFiber.lastEffect.nextEffect = fiber),
+        (returnFiber.lastEffect = fiber))
+      : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
+  }
+  function tryHydrate(fiber, nextInstance) {
+    switch (fiber.tag) {
+      case 5:
+        return (
+          (nextInstance = canHydrateInstance(
+            nextInstance,
+            fiber.type,
+            fiber.pendingProps
+          )),
+          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+        );
+      case 6:
+        return (
+          (nextInstance = canHydrateTextInstance(
+            nextInstance,
+            fiber.pendingProps
+          )),
+          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+        );
+      default:
+        return !1;
+    }
+  }
+  function popToNextHostParent(fiber) {
+    for (
+      fiber = fiber["return"];
+      null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
+
+    )
+      fiber = fiber["return"];
+    hydrationParentFiber = fiber;
+  }
+  var shouldSetTextContent = config.shouldSetTextContent;
+  config = config.hydration;
+  if (!config)
+    return {
+      enterHydrationState: function() {
+        return !1;
+      },
+      resetHydrationState: function() {},
+      tryToClaimNextHydratableInstance: function() {},
+      prepareToHydrateHostInstance: function() {
+        invariant(
+          !1,
+          "Expected prepareToHydrateHostInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      prepareToHydrateHostTextInstance: function() {
+        invariant(
+          !1,
+          "Expected prepareToHydrateHostTextInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      popHydrationState: function() {
+        return !1;
+      }
+    };
+  var canHydrateInstance = config.canHydrateInstance,
+    canHydrateTextInstance = config.canHydrateTextInstance,
+    getNextHydratableSibling = config.getNextHydratableSibling,
+    getFirstHydratableChild = config.getFirstHydratableChild,
+    hydrateInstance = config.hydrateInstance,
+    hydrateTextInstance = config.hydrateTextInstance,
+    hydrationParentFiber = null,
+    nextHydratableInstance = null,
+    isHydrating = !1;
+  return {
+    enterHydrationState: function(fiber) {
+      nextHydratableInstance = getFirstHydratableChild(
+        fiber.stateNode.containerInfo
+      );
+      hydrationParentFiber = fiber;
+      return (isHydrating = !0);
+    },
+    resetHydrationState: function() {
+      nextHydratableInstance = hydrationParentFiber = null;
+      isHydrating = !1;
+    },
+    tryToClaimNextHydratableInstance: function(fiber) {
+      if (isHydrating) {
+        var nextInstance = nextHydratableInstance;
+        if (nextInstance) {
+          if (!tryHydrate(fiber, nextInstance)) {
+            nextInstance = getNextHydratableSibling(nextInstance);
+            if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
+              fiber.effectTag |= 2;
+              isHydrating = !1;
+              hydrationParentFiber = fiber;
+              return;
+            }
+            deleteHydratableInstance(
+              hydrationParentFiber,
+              nextHydratableInstance
+            );
+          }
+          hydrationParentFiber = fiber;
+          nextHydratableInstance = getFirstHydratableChild(nextInstance);
+        } else
+          (fiber.effectTag |= 2),
+            (isHydrating = !1),
+            (hydrationParentFiber = fiber);
+      }
+    },
+    prepareToHydrateHostInstance: function(
+      fiber,
+      rootContainerInstance,
+      hostContext
+    ) {
+      rootContainerInstance = hydrateInstance(
+        fiber.stateNode,
+        fiber.type,
+        fiber.memoizedProps,
+        rootContainerInstance,
+        hostContext,
+        fiber
+      );
+      fiber.updateQueue = rootContainerInstance;
+      return null !== rootContainerInstance ? !0 : !1;
+    },
+    prepareToHydrateHostTextInstance: function(fiber) {
+      return hydrateTextInstance(fiber.stateNode, fiber.memoizedProps, fiber);
+    },
+    popHydrationState: function(fiber) {
+      if (fiber !== hydrationParentFiber) return !1;
+      if (!isHydrating)
+        return popToNextHostParent(fiber), (isHydrating = !0), !1;
+      var type = fiber.type;
+      if (
+        5 !== fiber.tag ||
+        ("head" !== type &&
+          "body" !== type &&
+          !shouldSetTextContent(type, fiber.memoizedProps))
+      )
+        for (type = nextHydratableInstance; type; )
+          deleteHydratableInstance(fiber, type),
+            (type = getNextHydratableSibling(type));
+      popToNextHostParent(fiber);
+      nextHydratableInstance = hydrationParentFiber
+        ? getNextHydratableSibling(fiber.stateNode)
+        : null;
+      return !0;
+    }
+  };
+}
+function ReactFiberLegacyContext(stack) {
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    workInProgress = workInProgress.stateNode;
+    workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    workInProgress.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
+  function isContextProvider(fiber) {
+    return 2 === fiber.tag && null != fiber.type.childContextTypes;
+  }
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode,
+      childContextTypes = fiber.type.childContextTypes;
+    if ("function" !== typeof instance.getChildContext) return parentContext;
+    instance = instance.getChildContext();
+    for (var contextKey in instance)
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    return Object.assign({}, parentContext, instance);
+  }
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop,
+    contextStackCursor = createCursor(emptyObject),
+    didPerformWorkStackCursor = createCursor(!1),
+    previousContext = emptyObject;
+  return {
+    getUnmaskedContext: function(workInProgress) {
+      return isContextProvider(workInProgress)
+        ? previousContext
+        : contextStackCursor.current;
+    },
+    cacheContext: cacheContext,
+    getMaskedContext: function(workInProgress, unmaskedContext) {
+      var contextTypes = workInProgress.type.contextTypes;
+      if (!contextTypes) return emptyObject;
+      var instance = workInProgress.stateNode;
+      if (
+        instance &&
+        instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+      )
+        return instance.__reactInternalMemoizedMaskedChildContext;
+      var context = {},
+        key;
+      for (key in contextTypes) context[key] = unmaskedContext[key];
+      instance && cacheContext(workInProgress, unmaskedContext, context);
+      return context;
+    },
+    hasContextChanged: function() {
+      return didPerformWorkStackCursor.current;
+    },
+    isContextConsumer: function(fiber) {
+      return 2 === fiber.tag && null != fiber.type.contextTypes;
+    },
+    isContextProvider: isContextProvider,
+    popContextProvider: function(fiber) {
+      isContextProvider(fiber) &&
+        (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
+    },
+    popTopLevelContextObject: function(fiber) {
+      pop(didPerformWorkStackCursor, fiber);
+      pop(contextStackCursor, fiber);
+    },
+    pushTopLevelContextObject: function(fiber, context, didChange) {
+      invariant(
+        null == contextStackCursor.cursor,
+        "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
+      );
+      push(contextStackCursor, context, fiber);
+      push(didPerformWorkStackCursor, didChange, fiber);
+    },
+    processChildContext: processChildContext,
+    pushContextProvider: function(workInProgress) {
+      if (!isContextProvider(workInProgress)) return !1;
+      var instance = workInProgress.stateNode;
+      instance =
+        (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+        emptyObject;
+      previousContext = contextStackCursor.current;
+      push(contextStackCursor, instance, workInProgress);
+      push(
+        didPerformWorkStackCursor,
+        didPerformWorkStackCursor.current,
+        workInProgress
+      );
+      return !0;
+    },
+    invalidateContextProvider: function(workInProgress, didChange) {
+      var instance = workInProgress.stateNode;
+      invariant(
+        instance,
+        "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+      );
+      if (didChange) {
+        var mergedContext = processChildContext(
+          workInProgress,
+          previousContext
+        );
+        instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+        pop(didPerformWorkStackCursor, workInProgress);
+        pop(contextStackCursor, workInProgress);
+        push(contextStackCursor, mergedContext, workInProgress);
+      } else pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    },
+    findCurrentUnmaskedContext: function(fiber) {
+      for (
+        invariant(
+          2 === isFiberMountedImpl(fiber) && 2 === fiber.tag,
+          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
+        );
+        3 !== fiber.tag;
+
+      ) {
+        if (isContextProvider(fiber))
+          return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
+        fiber = fiber["return"];
+        invariant(
+          fiber,
+          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+      }
+      return fiber.stateNode.context;
+    }
+  };
+}
+function ReactFiberNewContext(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop,
+    providerCursor = createCursor(null),
+    valueCursor = createCursor(null),
+    changedBitsCursor = createCursor(0);
+  return {
+    pushProvider: function(providerFiber) {
+      var context = providerFiber.type._context;
+      push(changedBitsCursor, context._changedBits, providerFiber);
+      push(valueCursor, context._currentValue, providerFiber);
+      push(providerCursor, providerFiber, providerFiber);
+      context._currentValue = providerFiber.pendingProps.value;
+      context._changedBits = providerFiber.stateNode;
+    },
+    popProvider: function(providerFiber) {
+      var changedBits = changedBitsCursor.current,
+        currentValue = valueCursor.current;
+      pop(providerCursor, providerFiber);
+      pop(valueCursor, providerFiber);
+      pop(changedBitsCursor, providerFiber);
+      providerFiber = providerFiber.type._context;
+      providerFiber._currentValue = currentValue;
+      providerFiber._changedBits = changedBits;
+    }
+  };
+}
+function ReactFiberStack() {
+  var valueStack = [],
+    index = -1;
+  return {
+    createCursor: function(defaultValue) {
+      return { current: defaultValue };
+    },
+    isEmpty: function() {
+      return -1 === index;
+    },
+    pop: function(cursor) {
+      0 > index ||
+        ((cursor.current = valueStack[index]),
+        (valueStack[index] = null),
+        index--);
+    },
+    push: function(cursor, value) {
+      index++;
+      valueStack[index] = cursor.current;
+      cursor.current = value;
+    },
+    checkThatStackIsEmpty: function() {},
+    resetStackAfterFatalErrorInDev: function() {}
+  };
+}
+function ReactFiberScheduler(config) {
+  function resetStack() {
+    if (null !== nextUnitOfWork)
+      for (
+        var interruptedWork = nextUnitOfWork["return"];
+        null !== interruptedWork;
+
+      )
+        unwindInterruptedWork(interruptedWork),
+          (interruptedWork = interruptedWork["return"]);
+    nextRoot = null;
+    nextRenderExpirationTime = 0;
+    nextUnitOfWork = null;
+    isRootReadyForCommit = !1;
+  }
+  function isAlreadyFailedLegacyErrorBoundary(instance) {
+    return (
+      null !== legacyErrorBoundariesThatAlreadyFailed &&
+      legacyErrorBoundariesThatAlreadyFailed.has(instance)
+    );
+  }
+  function completeUnitOfWork(workInProgress$jscomp$0) {
+    for (;;) {
+      var current = workInProgress$jscomp$0.alternate,
+        returnFiber = workInProgress$jscomp$0["return"],
+        siblingFiber = workInProgress$jscomp$0.sibling;
+      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
+        current = completeWork(
+          current,
+          workInProgress$jscomp$0,
+          nextRenderExpirationTime
+        );
+        var workInProgress = workInProgress$jscomp$0;
+        if (
+          1073741823 === nextRenderExpirationTime ||
+          1073741823 !== workInProgress.expirationTime
+        ) {
+          b: switch (workInProgress.tag) {
+            case 3:
+            case 2:
+              var newExpirationTime = workInProgress.updateQueue;
+              newExpirationTime =
+                null === newExpirationTime
+                  ? 0
+                  : newExpirationTime.expirationTime;
+              break b;
+            default:
+              newExpirationTime = 0;
+          }
+          for (var child = workInProgress.child; null !== child; )
+            0 !== child.expirationTime &&
+              (0 === newExpirationTime ||
+                newExpirationTime > child.expirationTime) &&
+              (newExpirationTime = child.expirationTime),
+              (child = child.sibling);
+          workInProgress.expirationTime = newExpirationTime;
+        }
+        if (null !== current) return current;
+        null !== returnFiber &&
+          0 === (returnFiber.effectTag & 512) &&
+          (null === returnFiber.firstEffect &&
+            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
+          null !== workInProgress$jscomp$0.lastEffect &&
+            (null !== returnFiber.lastEffect &&
+              (returnFiber.lastEffect.nextEffect =
+                workInProgress$jscomp$0.firstEffect),
+            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
+          1 < workInProgress$jscomp$0.effectTag &&
+            (null !== returnFiber.lastEffect
+              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
+              : (returnFiber.firstEffect = workInProgress$jscomp$0),
+            (returnFiber.lastEffect = workInProgress$jscomp$0)));
+        if (null !== siblingFiber) return siblingFiber;
+        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+        else {
+          isRootReadyForCommit = !0;
+          break;
+        }
+      } else {
+        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
+        if (null !== workInProgress$jscomp$0)
+          return (
+            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
+          );
+        null !== returnFiber &&
+          ((returnFiber.firstEffect = returnFiber.lastEffect = null),
+          (returnFiber.effectTag |= 512));
+        if (null !== siblingFiber) return siblingFiber;
+        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+        else break;
+      }
+    }
+    return null;
+  }
+  function performUnitOfWork(workInProgress) {
+    var next = beginWork(
+      workInProgress.alternate,
+      workInProgress,
+      nextRenderExpirationTime
+    );
+    null === next && (next = completeUnitOfWork(workInProgress));
+    ReactCurrentOwner.current = null;
+    return next;
+  }
+  function renderRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isWorking,
+      "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+    );
+    isWorking = !0;
+    if (
+      expirationTime !== nextRenderExpirationTime ||
+      root !== nextRoot ||
+      null === nextUnitOfWork
+    )
+      resetStack(),
+        (nextRoot = root),
+        (nextRenderExpirationTime = expirationTime),
+        (nextUnitOfWork = createWorkInProgress(
+          nextRoot.current,
+          null,
+          nextRenderExpirationTime
+        )),
+        (root.pendingCommitExpirationTime = 0);
+    var didFatal = !1;
+    do {
+      try {
+        if (isAsync)
+          for (; null !== nextUnitOfWork && !shouldYield(); )
+            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+        else
+          for (; null !== nextUnitOfWork; )
+            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      } catch (thrownValue) {
+        if (null === nextUnitOfWork) {
+          didFatal = !0;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        isAsync = nextUnitOfWork;
+        var returnFiber = isAsync["return"];
+        if (null === returnFiber) {
+          didFatal = !0;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        throwException(returnFiber, isAsync, thrownValue);
+        nextUnitOfWork = completeUnitOfWork(isAsync);
+      }
+      break;
+    } while (1);
+    isWorking = !1;
+    if (didFatal || null !== nextUnitOfWork) return null;
+    if (isRootReadyForCommit)
+      return (
+        (root.pendingCommitExpirationTime = expirationTime),
+        root.current.alternate
+      );
+    invariant(
+      !1,
+      "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
+    sourceFiber = {
+      value: value,
+      source: sourceFiber,
+      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
+    };
+    insertUpdateIntoFiber(boundaryFiber, {
+      expirationTime: expirationTime,
+      partialState: null,
+      callback: null,
+      isReplace: !1,
+      isForced: !1,
+      capturedValue: sourceFiber,
+      next: null
+    });
+    scheduleWork(boundaryFiber, expirationTime);
+  }
+  function onCommitPhaseError(fiber$jscomp$0, error) {
+    a: {
+      invariant(
+        !isWorking || isCommitting,
+        "dispatch: Cannot dispatch during the render phase."
+      );
+      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
+        switch (fiber.tag) {
+          case 2:
+            var instance = fiber.stateNode;
+            if (
+              "function" === typeof fiber.type.getDerivedStateFromCatch ||
+              ("function" === typeof instance.componentDidCatch &&
+                !isAlreadyFailedLegacyErrorBoundary(instance))
+            ) {
+              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
+              fiber$jscomp$0 = void 0;
+              break a;
+            }
+            break;
+          case 3:
+            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
+            fiber$jscomp$0 = void 0;
+            break a;
+        }
+        fiber = fiber["return"];
+      }
+      3 === fiber$jscomp$0.tag &&
+        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
+      fiber$jscomp$0 = void 0;
+    }
+    return fiber$jscomp$0;
+  }
+  function computeExpirationForFiber(fiber) {
+    fiber =
+      0 !== expirationContext
+        ? expirationContext
+        : isWorking
+          ? isCommitting ? 1 : nextRenderExpirationTime
+          : fiber.mode & 1
+            ? isBatchingInteractiveUpdates
+              ? 10 * ((((recalculateCurrentTime() + 15) / 10) | 0) + 1)
+              : 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1)
+            : 1;
+    isBatchingInteractiveUpdates &&
+      (0 === lowestPendingInteractiveExpirationTime ||
+        fiber > lowestPendingInteractiveExpirationTime) &&
+      (lowestPendingInteractiveExpirationTime = fiber);
+    return fiber;
+  }
+  function scheduleWork(fiber, expirationTime) {
+    a: {
+      for (; null !== fiber; ) {
+        if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
+          fiber.expirationTime = expirationTime;
+        null !== fiber.alternate &&
+          (0 === fiber.alternate.expirationTime ||
+            fiber.alternate.expirationTime > expirationTime) &&
+          (fiber.alternate.expirationTime = expirationTime);
+        if (null === fiber["return"])
+          if (3 === fiber.tag) {
+            var root = fiber.stateNode;
+            !isWorking &&
+              0 !== nextRenderExpirationTime &&
+              expirationTime < nextRenderExpirationTime &&
+              resetStack();
+            (isWorking && !isCommitting && nextRoot === root) ||
+              requestWork(root, expirationTime);
+            nestedUpdateCount > NESTED_UPDATE_LIMIT &&
+              invariant(
+                !1,
+                "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
+              );
+          } else {
+            expirationTime = void 0;
+            break a;
+          }
+        fiber = fiber["return"];
+      }
+      expirationTime = void 0;
+    }
+    return expirationTime;
+  }
+  function recalculateCurrentTime() {
+    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
+    return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
+  }
+  function syncUpdates(fn, a, b, c, d) {
+    var previousExpirationContext = expirationContext;
+    expirationContext = 1;
+    try {
+      return fn(a, b, c, d);
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  }
+  function scheduleCallbackWithExpiration(expirationTime) {
+    if (0 !== callbackExpirationTime) {
+      if (expirationTime > callbackExpirationTime) return;
+      cancelDeferredCallback(callbackID);
+    }
+    var currentMs = now() - originalStartTimeMs;
+    callbackExpirationTime = expirationTime;
+    callbackID = scheduleDeferredCallback(performAsyncWork, {
+      timeout: 10 * (expirationTime - 2) - currentMs
+    });
+  }
+  function requestWork(root, expirationTime) {
+    if (null === root.nextScheduledRoot)
+      (root.remainingExpirationTime = expirationTime),
+        null === lastScheduledRoot
+          ? ((firstScheduledRoot = lastScheduledRoot = root),
+            (root.nextScheduledRoot = root))
+          : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
+            (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
+    else {
+      var remainingExpirationTime = root.remainingExpirationTime;
+      if (
+        0 === remainingExpirationTime ||
+        expirationTime < remainingExpirationTime
+      )
+        root.remainingExpirationTime = expirationTime;
+    }
+    isRendering ||
+      (isBatchingUpdates
+        ? isUnbatchingUpdates &&
+          ((nextFlushedRoot = root),
+          (nextFlushedExpirationTime = 1),
+          performWorkOnRoot(root, 1, !1))
+        : 1 === expirationTime
+          ? performSyncWork()
+          : scheduleCallbackWithExpiration(expirationTime));
+  }
+  function findHighestPriorityRoot() {
+    var highestPriorityWork = 0,
+      highestPriorityRoot = null;
+    if (null !== lastScheduledRoot)
+      for (
+        var previousScheduledRoot = lastScheduledRoot,
+          root = firstScheduledRoot;
+        null !== root;
+
+      ) {
+        var remainingExpirationTime = root.remainingExpirationTime;
+        if (0 === remainingExpirationTime) {
+          invariant(
+            null !== previousScheduledRoot && null !== lastScheduledRoot,
+            "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
+          );
+          if (root === root.nextScheduledRoot) {
+            firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
+            break;
+          } else if (root === firstScheduledRoot)
+            (firstScheduledRoot = remainingExpirationTime =
+              root.nextScheduledRoot),
+              (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
+              (root.nextScheduledRoot = null);
+          else if (root === lastScheduledRoot) {
+            lastScheduledRoot = previousScheduledRoot;
+            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+            root.nextScheduledRoot = null;
+            break;
+          } else
+            (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
+              (root.nextScheduledRoot = null);
+          root = previousScheduledRoot.nextScheduledRoot;
+        } else {
+          if (
+            0 === highestPriorityWork ||
+            remainingExpirationTime < highestPriorityWork
+          )
+            (highestPriorityWork = remainingExpirationTime),
+              (highestPriorityRoot = root);
+          if (root === lastScheduledRoot) break;
+          previousScheduledRoot = root;
+          root = root.nextScheduledRoot;
+        }
+      }
+    previousScheduledRoot = nextFlushedRoot;
+    null !== previousScheduledRoot &&
+    previousScheduledRoot === highestPriorityRoot &&
+    1 === highestPriorityWork
+      ? nestedUpdateCount++
+      : (nestedUpdateCount = 0);
+    nextFlushedRoot = highestPriorityRoot;
+    nextFlushedExpirationTime = highestPriorityWork;
+  }
+  function performAsyncWork(dl) {
+    performWork(0, !0, dl);
+  }
+  function performSyncWork() {
+    performWork(1, !1, null);
+  }
+  function performWork(minExpirationTime, isAsync, dl) {
+    deadline = dl;
+    findHighestPriorityRoot();
+    if (isAsync)
+      for (
+        ;
+        null !== nextFlushedRoot &&
+        0 !== nextFlushedExpirationTime &&
+        (0 === minExpirationTime ||
+          minExpirationTime >= nextFlushedExpirationTime) &&
+        (!deadlineDidExpire ||
+          recalculateCurrentTime() >= nextFlushedExpirationTime);
+
+      )
+        performWorkOnRoot(
+          nextFlushedRoot,
+          nextFlushedExpirationTime,
+          !deadlineDidExpire
+        ),
+          findHighestPriorityRoot();
+    else
+      for (
+        ;
+        null !== nextFlushedRoot &&
+        0 !== nextFlushedExpirationTime &&
+        (0 === minExpirationTime ||
+          minExpirationTime >= nextFlushedExpirationTime);
+
+      )
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
+          findHighestPriorityRoot();
+    null !== deadline && ((callbackExpirationTime = 0), (callbackID = -1));
+    0 !== nextFlushedExpirationTime &&
+      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
+    deadline = null;
+    deadlineDidExpire = !1;
+    finishRendering();
+  }
+  function finishRendering() {
+    nestedUpdateCount = 0;
+    if (null !== completedBatches) {
+      var batches = completedBatches;
+      completedBatches = null;
+      for (var i = 0; i < batches.length; i++) {
+        var batch = batches[i];
+        try {
+          batch._onComplete();
+        } catch (error) {
+          hasUnhandledError ||
+            ((hasUnhandledError = !0), (unhandledError = error));
+        }
+      }
+    }
+    if (hasUnhandledError)
+      throw ((batches = unhandledError),
+      (unhandledError = null),
+      (hasUnhandledError = !1),
+      batches);
+  }
+  function performWorkOnRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isRendering,
+      "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+    );
+    isRendering = !0;
+    isAsync
+      ? ((isAsync = root.finishedWork),
+        null !== isAsync
+          ? completeRoot(root, isAsync, expirationTime)
+          : ((root.finishedWork = null),
+            (isAsync = renderRoot(root, expirationTime, !0)),
+            null !== isAsync &&
+              (shouldYield()
+                ? (root.finishedWork = isAsync)
+                : completeRoot(root, isAsync, expirationTime))))
+      : ((isAsync = root.finishedWork),
+        null !== isAsync
+          ? completeRoot(root, isAsync, expirationTime)
+          : ((root.finishedWork = null),
+            (isAsync = renderRoot(root, expirationTime, !1)),
+            null !== isAsync && completeRoot(root, isAsync, expirationTime)));
+    isRendering = !1;
+  }
+  function completeRoot(root, finishedWork, expirationTime) {
+    var firstBatch = root.firstBatch;
+    if (
+      null !== firstBatch &&
+      firstBatch._expirationTime <= expirationTime &&
+      (null === completedBatches
+        ? (completedBatches = [firstBatch])
+        : completedBatches.push(firstBatch),
+      firstBatch._defer)
+    ) {
+      root.finishedWork = finishedWork;
+      root.remainingExpirationTime = 0;
+      return;
+    }
+    root.finishedWork = null;
+    isCommitting = isWorking = !0;
+    expirationTime = finishedWork.stateNode;
+    invariant(
+      expirationTime.current !== finishedWork,
+      "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
+    );
+    firstBatch = expirationTime.pendingCommitExpirationTime;
+    invariant(
+      0 !== firstBatch,
+      "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
+    );
+    expirationTime.pendingCommitExpirationTime = 0;
+    var currentTime = recalculateCurrentTime();
+    ReactCurrentOwner.current = null;
+    if (1 < finishedWork.effectTag)
+      if (null !== finishedWork.lastEffect) {
+        finishedWork.lastEffect.nextEffect = finishedWork;
+        var firstEffect = finishedWork.firstEffect;
+      } else firstEffect = finishedWork;
+    else firstEffect = finishedWork.firstEffect;
+    prepareForCommit(expirationTime.containerInfo);
+    for (nextEffect = firstEffect; null !== nextEffect; ) {
+      var didError = !1,
+        error = void 0;
+      try {
+        for (; null !== nextEffect; )
+          nextEffect.effectTag & 2048 &&
+            commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
+            (nextEffect = nextEffect.nextEffect);
+      } catch (e) {
+        (didError = !0), (error = e);
+      }
+      didError &&
+        (invariant(
+          null !== nextEffect,
+          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        onCommitPhaseError(nextEffect, error),
+        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    }
+    for (nextEffect = firstEffect; null !== nextEffect; ) {
+      didError = !1;
+      error = void 0;
+      try {
+        for (; null !== nextEffect; ) {
+          var effectTag = nextEffect.effectTag;
+          effectTag & 16 && commitResetTextContent(nextEffect);
+          if (effectTag & 128) {
+            var current = nextEffect.alternate;
+            null !== current && commitDetachRef(current);
+          }
+          switch (effectTag & 14) {
+            case 2:
+              commitPlacement(nextEffect);
+              nextEffect.effectTag &= -3;
+              break;
+            case 6:
+              commitPlacement(nextEffect);
+              nextEffect.effectTag &= -3;
+              commitWork(nextEffect.alternate, nextEffect);
+              break;
+            case 4:
+              commitWork(nextEffect.alternate, nextEffect);
+              break;
+            case 8:
+              commitDeletion(nextEffect);
+          }
+          nextEffect = nextEffect.nextEffect;
+        }
+      } catch (e) {
+        (didError = !0), (error = e);
+      }
+      didError &&
+        (invariant(
+          null !== nextEffect,
+          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        onCommitPhaseError(nextEffect, error),
+        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    }
+    resetAfterCommit(expirationTime.containerInfo);
+    expirationTime.current = finishedWork;
+    for (nextEffect = firstEffect; null !== nextEffect; ) {
+      effectTag = !1;
+      current = void 0;
+      try {
+        for (
+          firstEffect = expirationTime,
+            didError = currentTime,
+            error = firstBatch;
+          null !== nextEffect;
+
+        ) {
+          var effectTag$jscomp$0 = nextEffect.effectTag;
+          effectTag$jscomp$0 & 36 &&
+            commitLifeCycles(
+              firstEffect,
+              nextEffect.alternate,
+              nextEffect,
+              didError,
+              error
+            );
+          effectTag$jscomp$0 & 256 &&
+            commitErrorLogging(nextEffect, onUncaughtError);
+          effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
+          var next = nextEffect.nextEffect;
+          nextEffect.nextEffect = null;
+          nextEffect = next;
+        }
+      } catch (e) {
+        (effectTag = !0), (current = e);
+      }
+      effectTag &&
+        (invariant(
+          null !== nextEffect,
+          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        onCommitPhaseError(nextEffect, current),
+        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    }
+    isWorking = isCommitting = !1;
+    "function" === typeof onCommitRoot && onCommitRoot(finishedWork.stateNode);
+    finishedWork = expirationTime.current.expirationTime;
+    0 === finishedWork && (legacyErrorBoundariesThatAlreadyFailed = null);
+    root.remainingExpirationTime = finishedWork;
+  }
+  function shouldYield() {
+    return null === deadline ||
+      deadline.timeRemaining() > timeHeuristicForUnitOfWork
+      ? !1
+      : (deadlineDidExpire = !0);
+  }
+  function onUncaughtError(error) {
+    invariant(
+      null !== nextFlushedRoot,
+      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
+    );
+    nextFlushedRoot.remainingExpirationTime = 0;
+    hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
+  }
+  var stack = ReactFiberStack(),
+    hostContext = ReactFiberHostContext(config, stack),
+    legacyContext = ReactFiberLegacyContext(stack);
+  stack = ReactFiberNewContext(stack);
+  var hydrationContext = ReactFiberHydrationContext(config),
+    beginWork = ReactFiberBeginWork(
+      config,
+      hostContext,
+      legacyContext,
+      stack,
+      hydrationContext,
+      scheduleWork,
+      computeExpirationForFiber
+    ).beginWork,
+    completeWork = ReactFiberCompleteWork(
+      config,
+      hostContext,
+      legacyContext,
+      stack,
+      hydrationContext
+    ).completeWork;
+  hostContext = ReactFiberUnwindWork(
+    hostContext,
+    legacyContext,
+    stack,
+    scheduleWork,
+    isAlreadyFailedLegacyErrorBoundary
+  );
+  var throwException = hostContext.throwException,
+    unwindWork = hostContext.unwindWork,
+    unwindInterruptedWork = hostContext.unwindInterruptedWork;
+  hostContext = ReactFiberCommitWork(
+    config,
+    onCommitPhaseError,
+    scheduleWork,
+    computeExpirationForFiber,
+    function(instance) {
+      null === legacyErrorBoundariesThatAlreadyFailed
+        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
+        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+    },
+    recalculateCurrentTime
+  );
+  var commitBeforeMutationLifeCycles =
+      hostContext.commitBeforeMutationLifeCycles,
+    commitResetTextContent = hostContext.commitResetTextContent,
+    commitPlacement = hostContext.commitPlacement,
+    commitDeletion = hostContext.commitDeletion,
+    commitWork = hostContext.commitWork,
+    commitLifeCycles = hostContext.commitLifeCycles,
+    commitErrorLogging = hostContext.commitErrorLogging,
+    commitAttachRef = hostContext.commitAttachRef,
+    commitDetachRef = hostContext.commitDetachRef,
+    now = config.now,
+    scheduleDeferredCallback = config.scheduleDeferredCallback,
+    cancelDeferredCallback = config.cancelDeferredCallback,
+    prepareForCommit = config.prepareForCommit,
+    resetAfterCommit = config.resetAfterCommit,
+    originalStartTimeMs = now(),
+    mostRecentCurrentTime = 2,
+    mostRecentCurrentTimeMs = originalStartTimeMs,
+    lastUniqueAsyncExpiration = 0,
+    expirationContext = 0,
+    isWorking = !1,
+    nextUnitOfWork = null,
+    nextRoot = null,
+    nextRenderExpirationTime = 0,
+    nextEffect = null,
+    isCommitting = !1,
+    isRootReadyForCommit = !1,
+    legacyErrorBoundariesThatAlreadyFailed = null,
+    firstScheduledRoot = null,
+    lastScheduledRoot = null,
+    callbackExpirationTime = 0,
+    callbackID = -1,
+    isRendering = !1,
+    nextFlushedRoot = null,
+    nextFlushedExpirationTime = 0,
+    lowestPendingInteractiveExpirationTime = 0,
+    deadlineDidExpire = !1,
+    hasUnhandledError = !1,
+    unhandledError = null,
+    deadline = null,
+    isBatchingUpdates = !1,
+    isUnbatchingUpdates = !1,
+    isBatchingInteractiveUpdates = !1,
+    completedBatches = null,
+    NESTED_UPDATE_LIMIT = 1e3,
+    nestedUpdateCount = 0,
+    timeHeuristicForUnitOfWork = 1;
+  return {
+    recalculateCurrentTime: recalculateCurrentTime,
+    computeExpirationForFiber: computeExpirationForFiber,
+    scheduleWork: scheduleWork,
+    requestWork: requestWork,
+    flushRoot: function(root, expirationTime) {
+      invariant(
+        !isRendering,
+        "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
+      );
+      nextFlushedRoot = root;
+      nextFlushedExpirationTime = expirationTime;
+      performWorkOnRoot(root, expirationTime, !1);
+      performSyncWork();
+      finishRendering();
+    },
+    batchedUpdates: function(fn, a) {
+      var previousIsBatchingUpdates = isBatchingUpdates;
+      isBatchingUpdates = !0;
+      try {
+        return fn(a);
+      } finally {
+        (isBatchingUpdates = previousIsBatchingUpdates) ||
+          isRendering ||
+          performSyncWork();
+      }
+    },
+    unbatchedUpdates: function(fn, a) {
+      if (isBatchingUpdates && !isUnbatchingUpdates) {
+        isUnbatchingUpdates = !0;
+        try {
+          return fn(a);
+        } finally {
+          isUnbatchingUpdates = !1;
+        }
+      }
+      return fn(a);
+    },
+    flushSync: function(fn, a) {
+      invariant(
+        !isRendering,
+        "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
+      );
+      var previousIsBatchingUpdates = isBatchingUpdates;
+      isBatchingUpdates = !0;
+      try {
+        return syncUpdates(fn, a);
+      } finally {
+        (isBatchingUpdates = previousIsBatchingUpdates), performSyncWork();
+      }
+    },
+    flushControlled: function(fn) {
+      var previousIsBatchingUpdates = isBatchingUpdates;
+      isBatchingUpdates = !0;
+      try {
+        syncUpdates(fn);
+      } finally {
+        (isBatchingUpdates = previousIsBatchingUpdates) ||
+          isRendering ||
+          performWork(1, !1, null);
+      }
+    },
+    deferredUpdates: function(fn) {
+      var previousExpirationContext = expirationContext;
+      expirationContext =
+        25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
+      try {
+        return fn();
+      } finally {
+        expirationContext = previousExpirationContext;
+      }
+    },
+    syncUpdates: syncUpdates,
+    interactiveUpdates: function(fn, a, b) {
+      if (isBatchingInteractiveUpdates) return fn(a, b);
+      isBatchingUpdates ||
+        isRendering ||
+        0 === lowestPendingInteractiveExpirationTime ||
+        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
+        (lowestPendingInteractiveExpirationTime = 0));
+      var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
+        previousIsBatchingUpdates = isBatchingUpdates;
+      isBatchingUpdates = isBatchingInteractiveUpdates = !0;
+      try {
+        return fn(a, b);
+      } finally {
+        (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
+          (isBatchingUpdates = previousIsBatchingUpdates) ||
+            isRendering ||
+            performSyncWork();
+      }
+    },
+    flushInteractiveUpdates: function() {
+      isRendering ||
+        0 === lowestPendingInteractiveExpirationTime ||
+        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
+        (lowestPendingInteractiveExpirationTime = 0));
+    },
+    computeUniqueAsyncExpiration: function() {
+      var result = 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
+      result <= lastUniqueAsyncExpiration &&
+        (result = lastUniqueAsyncExpiration + 1);
+      return (lastUniqueAsyncExpiration = result);
+    },
+    legacyContext: legacyContext
+  };
+}
+function ReactFiberReconciler$1(config) {
+  function updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    currentTime,
+    expirationTime,
+    callback
+  ) {
+    currentTime = container.current;
+    if (parentComponent) {
+      parentComponent = parentComponent._reactInternalFiber;
+      var parentContext = findCurrentUnmaskedContext(parentComponent);
+      parentComponent = isContextProvider(parentComponent)
+        ? processChildContext(parentComponent, parentContext)
+        : parentContext;
+    } else parentComponent = emptyObject;
+    null === container.context
+      ? (container.context = parentComponent)
+      : (container.pendingContext = parentComponent);
+    container = callback;
+    insertUpdateIntoFiber(currentTime, {
+      expirationTime: expirationTime,
+      partialState: { element: element },
+      callback: void 0 === container ? null : container,
+      isReplace: !1,
+      isForced: !1,
+      capturedValue: null,
+      next: null
+    });
+    scheduleWork(currentTime, expirationTime);
+    return expirationTime;
+  }
+  var getPublicInstance = config.getPublicInstance;
+  config = ReactFiberScheduler(config);
+  var recalculateCurrentTime = config.recalculateCurrentTime,
+    computeExpirationForFiber = config.computeExpirationForFiber,
+    scheduleWork = config.scheduleWork,
+    legacyContext = config.legacyContext,
+    findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
+  return {
+    createContainer: function(containerInfo, isAsync, hydrate) {
+      isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
+      containerInfo = {
+        current: isAsync,
+        containerInfo: containerInfo,
+        pendingChildren: null,
+        pendingCommitExpirationTime: 0,
+        finishedWork: null,
+        context: null,
+        pendingContext: null,
+        hydrate: hydrate,
+        remainingExpirationTime: 0,
+        firstBatch: null,
+        nextScheduledRoot: null
+      };
+      return (isAsync.stateNode = containerInfo);
+    },
+    updateContainer: function(element, container, parentComponent, callback) {
+      var current = container.current,
+        currentTime = recalculateCurrentTime();
+      current = computeExpirationForFiber(current);
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        currentTime,
+        current,
+        callback
+      );
+    },
+    updateContainerAtExpirationTime: function(
+      element,
+      container,
+      parentComponent,
+      expirationTime,
+      callback
+    ) {
+      var currentTime = recalculateCurrentTime();
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        currentTime,
+        expirationTime,
+        callback
+      );
+    },
+    flushRoot: config.flushRoot,
+    requestWork: config.requestWork,
+    computeUniqueAsyncExpiration: config.computeUniqueAsyncExpiration,
+    batchedUpdates: config.batchedUpdates,
+    unbatchedUpdates: config.unbatchedUpdates,
+    deferredUpdates: config.deferredUpdates,
+    syncUpdates: config.syncUpdates,
+    interactiveUpdates: config.interactiveUpdates,
+    flushInteractiveUpdates: config.flushInteractiveUpdates,
+    flushControlled: config.flushControlled,
+    flushSync: config.flushSync,
+    getPublicRootInstance: function(container) {
+      container = container.current;
+      if (!container.child) return null;
+      switch (container.child.tag) {
+        case 5:
+          return getPublicInstance(container.child.stateNode);
+        default:
+          return container.child.stateNode;
+      }
+    },
+    findHostInstance: function(component) {
+      var fiber = component._reactInternalFiber;
+      void 0 === fiber &&
+        ("function" === typeof component.render
+          ? invariant(!1, "Unable to find node on an unmounted component.")
+          : invariant(
+              !1,
+              "Argument appears to not be a ReactComponent. Keys: %s",
+              Object.keys(component)
+            ));
+      component = findCurrentHostFiber(fiber);
+      return null === component ? null : component.stateNode;
+    },
+    findHostInstanceWithNoPortals: function(fiber) {
+      fiber = findCurrentHostFiberWithNoPortals(fiber);
+      return null === fiber ? null : fiber.stateNode;
+    },
+    injectIntoDevTools: function(devToolsConfig) {
+      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+      return injectInternals(
+        Object.assign({}, devToolsConfig, {
+          findHostInstanceByFiber: function(fiber) {
+            fiber = findCurrentHostFiber(fiber);
+            return null === fiber ? null : fiber.stateNode;
+          },
+          findFiberByHostInstance: function(instance) {
+            return findFiberByHostInstance
+              ? findFiberByHostInstance(instance)
+              : null;
+          }
+        })
+      );
+    }
+  };
+}
+var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
+  ReactFiberReconciler$3 =
+    (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
+    ReactFiberReconciler$2,
+  reactReconciler = ReactFiberReconciler$3["default"]
+    ? ReactFiberReconciler$3["default"]
+    : ReactFiberReconciler$3,
+  ReactNativeFiberHostComponent = (function() {
+    function ReactNativeFiberHostComponent(tag, viewConfig) {
+      if (!(this instanceof ReactNativeFiberHostComponent))
+        throw new TypeError("Cannot call a class as a function");
+      this._nativeTag = tag;
+      this._children = [];
+      this.viewConfig = viewConfig;
+    }
+    ReactNativeFiberHostComponent.prototype.blur = function() {
+      TextInputState.blurTextInput(this._nativeTag);
+    };
+    ReactNativeFiberHostComponent.prototype.focus = function() {
+      TextInputState.focusTextInput(this._nativeTag);
+    };
+    ReactNativeFiberHostComponent.prototype.measure = function(callback) {
+      UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+    };
+    ReactNativeFiberHostComponent.prototype.measureInWindow = function(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        this._nativeTag,
+        mountSafeCallback(this, callback)
+      );
+    };
+    ReactNativeFiberHostComponent.prototype.measureLayout = function(
+      relativeToNativeNode,
+      onSuccess,
+      onFail
+    ) {
+      UIManager.measureLayout(
+        this._nativeTag,
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
+    ReactNativeFiberHostComponent.prototype.setNativeProps = function(
+      nativeProps
+    ) {
+      nativeProps = diffProperties(
+        null,
+        emptyObject$1,
+        nativeProps,
+        this.viewConfig.validAttributes
+      );
+      null != nativeProps &&
+        UIManager.updateView(
+          this._nativeTag,
+          this.viewConfig.uiViewClassName,
+          nativeProps
+        );
+    };
+    return ReactNativeFiberHostComponent;
+  })(),
+  now =
+    "object" === typeof performance && "function" === typeof performance.now
+      ? function() {
+          return performance.now();
+        }
+      : function() {
+          return Date.now();
+        },
+  scheduledCallback = null,
+  frameDeadline = 0,
+  frameDeadlineObject = {
+    timeRemaining: function() {
+      return frameDeadline - now();
+    },
+    didTimeout: !1
+  };
+function setTimeoutCallback() {
+  frameDeadline = now() + 5;
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  null !== callback && callback(frameDeadlineObject);
+}
+var nextReactTag = 3;
+function allocateTag() {
+  var tag = nextReactTag;
+  1 === tag % 10 && (tag += 2);
+  nextReactTag = tag + 2;
+  return tag;
+}
+function recursivelyUncacheFiberNode(node) {
+  "number" === typeof node
+    ? uncacheFiberNode(node)
+    : (uncacheFiberNode(node._nativeTag),
+      node._children.forEach(recursivelyUncacheFiberNode));
+}
+var NativeRenderer = reactReconciler({
+    appendInitialChild: function(parentInstance, child) {
+      parentInstance._children.push(child);
+    },
+    createInstance: function(
+      type,
+      props,
+      rootContainerInstance,
+      hostContext,
+      internalInstanceHandle
+    ) {
+      hostContext = allocateTag();
+      type = ReactNativeViewConfigRegistry.get(type);
+      var updatePayload = diffProperties(
+        null,
+        emptyObject$1,
+        props,
+        type.validAttributes
+      );
+      UIManager.createView(
+        hostContext,
+        type.uiViewClassName,
+        rootContainerInstance,
+        updatePayload
+      );
+      rootContainerInstance = new ReactNativeFiberHostComponent(
+        hostContext,
+        type
+      );
+      instanceCache[hostContext] = internalInstanceHandle;
+      instanceProps[hostContext] = props;
+      return rootContainerInstance;
+    },
+    createTextInstance: function(
+      text,
+      rootContainerInstance,
+      hostContext,
+      internalInstanceHandle
+    ) {
+      hostContext = allocateTag();
+      UIManager.createView(hostContext, "RCTRawText", rootContainerInstance, {
+        text: text
+      });
+      instanceCache[hostContext] = internalInstanceHandle;
+      return hostContext;
+    },
+    finalizeInitialChildren: function(parentInstance) {
+      if (0 === parentInstance._children.length) return !1;
+      var nativeTags = parentInstance._children.map(function(child) {
+        return "number" === typeof child ? child : child._nativeTag;
+      });
+      UIManager.setChildren(parentInstance._nativeTag, nativeTags);
+      return !1;
+    },
+    getRootHostContext: function() {
+      return emptyObject;
+    },
+    getChildHostContext: function() {
+      return emptyObject;
+    },
+    getPublicInstance: function(instance) {
+      return instance;
+    },
+    now: now,
+    prepareForCommit: function() {},
+    prepareUpdate: function() {
+      return emptyObject;
+    },
+    resetAfterCommit: function() {},
+    scheduleDeferredCallback: function(callback) {
+      scheduledCallback = callback;
+      return setTimeout(setTimeoutCallback, 1);
+    },
+    cancelDeferredCallback: function(callbackID) {
+      scheduledCallback = null;
+      clearTimeout(callbackID);
+    },
+    shouldDeprioritizeSubtree: function() {
+      return !1;
+    },
+    shouldSetTextContent: function() {
+      return !1;
+    },
+    mutation: {
+      appendChild: function(parentInstance, child) {
+        var childTag = "number" === typeof child ? child : child._nativeTag,
+          children = parentInstance._children,
+          index = children.indexOf(child);
+        0 <= index
+          ? (children.splice(index, 1),
+            children.push(child),
+            UIManager.manageChildren(
+              parentInstance._nativeTag,
+              [index],
+              [children.length - 1],
+              [],
+              [],
+              []
+            ))
+          : (children.push(child),
+            UIManager.manageChildren(
+              parentInstance._nativeTag,
+              [],
+              [],
+              [childTag],
+              [children.length - 1],
+              []
+            ));
+      },
+      appendChildToContainer: function(parentInstance, child) {
+        UIManager.setChildren(parentInstance, [
+          "number" === typeof child ? child : child._nativeTag
+        ]);
+      },
+      commitTextUpdate: function(textInstance, oldText, newText) {
+        UIManager.updateView(textInstance, "RCTRawText", { text: newText });
+      },
+      commitMount: function() {},
+      commitUpdate: function(
+        instance,
+        updatePayloadTODO,
+        type,
+        oldProps,
+        newProps
+      ) {
+        updatePayloadTODO = instance.viewConfig;
+        instanceProps[instance._nativeTag] = newProps;
+        oldProps = diffProperties(
+          null,
+          oldProps,
+          newProps,
+          updatePayloadTODO.validAttributes
+        );
+        null != oldProps &&
+          UIManager.updateView(
+            instance._nativeTag,
+            updatePayloadTODO.uiViewClassName,
+            oldProps
+          );
+      },
+      insertBefore: function(parentInstance, child, beforeChild) {
+        var children = parentInstance._children,
+          index = children.indexOf(child);
+        0 <= index
+          ? (children.splice(index, 1),
+            (beforeChild = children.indexOf(beforeChild)),
+            children.splice(beforeChild, 0, child),
+            UIManager.manageChildren(
+              parentInstance._nativeTag,
+              [index],
+              [beforeChild],
+              [],
+              [],
+              []
+            ))
+          : ((index = children.indexOf(beforeChild)),
+            children.splice(index, 0, child),
+            UIManager.manageChildren(
+              parentInstance._nativeTag,
+              [],
+              [],
+              ["number" === typeof child ? child : child._nativeTag],
+              [index],
+              []
+            ));
+      },
+      insertInContainerBefore: function(parentInstance) {
+        invariant(
+          "number" !== typeof parentInstance,
+          "Container does not support insertBefore operation"
+        );
+      },
+      removeChild: function(parentInstance, child) {
+        recursivelyUncacheFiberNode(child);
+        var children = parentInstance._children;
+        child = children.indexOf(child);
+        children.splice(child, 1);
+        UIManager.manageChildren(
+          parentInstance._nativeTag,
+          [],
+          [],
+          [],
+          [],
+          [child]
+        );
+      },
+      removeChildFromContainer: function(parentInstance, child) {
+        recursivelyUncacheFiberNode(child);
+        UIManager.manageChildren(parentInstance, [], [], [], [], [0]);
+      },
+      resetTextContent: function() {}
+    }
+  }),
+  getInspectorDataForViewTag = void 0;
+getInspectorDataForViewTag = function() {
+  invariant(!1, "getInspectorDataForViewTag() is not available in production");
+};
+var findHostInstance = NativeRenderer.findHostInstance;
+function findNodeHandle(componentOrHandle) {
+  if (null == componentOrHandle) return null;
+  if ("number" === typeof componentOrHandle) return componentOrHandle;
+  if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
+    return componentOrHandle.canonical._nativeTag;
+  componentOrHandle = findHostInstance(componentOrHandle);
+  return null == componentOrHandle
+    ? componentOrHandle
+    : componentOrHandle.canonical
+      ? componentOrHandle.canonical._nativeTag
+      : componentOrHandle._nativeTag;
+}
+_batchedUpdates = NativeRenderer.batchedUpdates;
+_flushInteractiveUpdates = NativeRenderer.flushInteractiveUpdates;
+var roots = new Map(),
+  ReactNativeRenderer = {
+    NativeComponent: (function(findNodeHandle, findHostInstance) {
+      return (function(_React$Component) {
+        function ReactNativeComponent() {
+          if (!(this instanceof ReactNativeComponent))
+            throw new TypeError("Cannot call a class as a function");
+          var call = _React$Component.apply(this, arguments);
+          if (!this)
+            throw new ReferenceError(
+              "this hasn't been initialised - super() hasn't been called"
+            );
+          return !call ||
+            ("object" !== typeof call && "function" !== typeof call)
+            ? this
+            : call;
+        }
+        _inherits(ReactNativeComponent, _React$Component);
+        ReactNativeComponent.prototype.blur = function() {
+          TextInputState.blurTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.focus = function() {
+          TextInputState.focusTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.measure = function(callback) {
+          UIManager.measure(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureInWindow = function(callback) {
+          UIManager.measureInWindow(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureLayout = function(
+          relativeToNativeNode,
+          onSuccess,
+          onFail
+        ) {
+          UIManager.measureLayout(
+            findNodeHandle(this),
+            relativeToNativeNode,
+            mountSafeCallback(this, onFail),
+            mountSafeCallback(this, onSuccess)
+          );
+        };
+        ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
+          var maybeInstance = void 0;
+          try {
+            maybeInstance = findHostInstance(this);
+          } catch (error) {}
+          if (null != maybeInstance) {
+            var viewConfig =
+              maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+            nativeProps = diffProperties(
+              null,
+              emptyObject$1,
+              nativeProps,
+              viewConfig.validAttributes
+            );
+            null != nativeProps &&
+              UIManager.updateView(
+                maybeInstance._nativeTag,
+                viewConfig.uiViewClassName,
+                nativeProps
+              );
+          }
+        };
+        return ReactNativeComponent;
+      })(React.Component);
+    })(findNodeHandle, findHostInstance),
+    findNodeHandle: findNodeHandle,
+    render: function(element, containerTag, callback) {
+      var root = roots.get(containerTag);
+      root ||
+        ((root = NativeRenderer.createContainer(containerTag, !1, !1)),
+        roots.set(containerTag, root));
+      NativeRenderer.updateContainer(element, root, null, callback);
+      return NativeRenderer.getPublicRootInstance(root);
+    },
+    unmountComponentAtNode: function(containerTag) {
+      var root = roots.get(containerTag);
+      root &&
+        NativeRenderer.updateContainer(null, root, null, function() {
+          roots["delete"](containerTag);
+        });
+    },
+    unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
+      ReactNativeRenderer.unmountComponentAtNode(containerTag);
+      UIManager.removeRootView(containerTag);
+    },
+    createPortal: function(children, containerTag) {
+      return createPortal(
+        children,
+        containerTag,
+        null,
+        2 < arguments.length && void 0 !== arguments[2] ? arguments[2] : null
+      );
+    },
+    unstable_batchedUpdates: batchedUpdates,
+    __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
+      NativeMethodsMixin: (function(findNodeHandle, findHostInstance) {
+        return {
+          measure: function(callback) {
+            UIManager.measure(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureInWindow: function(callback) {
+            UIManager.measureInWindow(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
+            UIManager.measureLayout(
+              findNodeHandle(this),
+              relativeToNativeNode,
+              mountSafeCallback(this, onFail),
+              mountSafeCallback(this, onSuccess)
+            );
+          },
+          setNativeProps: function(nativeProps) {
+            var maybeInstance = void 0;
+            try {
+              maybeInstance = findHostInstance(this);
+            } catch (error) {}
+            if (null != maybeInstance) {
+              var viewConfig = maybeInstance.viewConfig;
+              nativeProps = diffProperties(
+                null,
+                emptyObject$1,
+                nativeProps,
+                viewConfig.validAttributes
+              );
+              null != nativeProps &&
+                UIManager.updateView(
+                  maybeInstance._nativeTag,
+                  viewConfig.uiViewClassName,
+                  nativeProps
+                );
+            }
+          },
+          focus: function() {
+            TextInputState.focusTextInput(findNodeHandle(this));
+          },
+          blur: function() {
+            TextInputState.blurTextInput(findNodeHandle(this));
+          }
+        };
+      })(findNodeHandle, findHostInstance),
+      ReactNativeComponentTree: ReactNativeComponentTree,
+      computeComponentStackForErrorReporting: function(reactTag) {
+        return (reactTag = getInstanceFromTag(reactTag))
+          ? getStackAddendumByWorkInProgressFiber(reactTag)
+          : "";
+      }
+    }
+  };
+NativeRenderer.injectIntoDevTools({
+  findFiberByHostInstance: getInstanceFromTag,
+  getInspectorDataForViewTag: getInspectorDataForViewTag,
+  bundleType: 0,
+  version: "16.3.2",
+  rendererPackageName: "react-native-renderer"
+});
+var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
+  ReactNativeRenderer$3 =
+    (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
+module.exports = ReactNativeRenderer$3["default"]
+  ? ReactNativeRenderer$3["default"]
+  : ReactNativeRenderer$3;
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index 1f7f5d0015a2..bf9411973933 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -77,6 +77,11 @@ type SecretInternalsType = {
   // And how much information to fill in for the above types.
 };
 
+type SecretInternalsFabricType = {
+  NativeMethodsMixin: NativeMethodsMixinType,
+  ReactNativeComponentTree: any,
+};
+
 /**
  * Flat ReactNative renderer bundles are too big for Flow to parse efficiently.
  * Provide minimal Flow typing for the high-level RN API and call it a day.
@@ -106,5 +111,5 @@ export type ReactFabricType = {
   ): any,
   unmountComponentAtNode(containerTag: number): any,
 
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: SecretInternalsType,
+  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: SecretInternalsFabricType,
 };
diff --git a/package.json b/package.json
index 066c873aa89f..c28da3b6dc12 100644
--- a/package.json
+++ b/package.json
@@ -142,7 +142,7 @@
     "react-native": "local-cli/wrong-react-native.js"
   },
   "peerDependencies": {
-    "react": "16.3.1"
+    "react": "16.3.2"
   },
   "dependencies": {
     "absolute-path": "^0.0.0",
@@ -210,8 +210,8 @@
     "jest": "23.0.0-alpha.4",
     "jest-junit": "3.6.0",
     "prettier": "1.9.1",
-    "react": "16.3.1",
-    "react-test-renderer": "16.3.1",
+    "react": "16.3.2",
+    "react-test-renderer": "16.3.2",
     "shelljs": "^0.7.8",
     "sinon": "^2.2.0"
   }

From b92b38acf9c7e5c8c16e082e898716c840fa3e89 Mon Sep 17 00:00:00 2001
From: Hugo Sousa <hsousa@me.com>
Date: Wed, 18 Apr 2018 17:37:26 -0700
Subject: [PATCH 0332/1109] Remove extra space in source_files
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
This was causing tvOS builds to fail because .m files weren’t being included.

 - Add `tvOS` subspec to your project with a tvOS target.
 - Build
 - Profit.

[TVOS] [BREAKING] [React.podspec] - Fix building for tvOS with CocoaPods
Closes https://github.com/facebook/react-native/pull/18812

Differential Revision: D7680224

Pulled By: hramos

fbshipit-source-id: c6c3b6fb0acd2004579d85c3f72e4edd88e26ed8
---
 React.podspec | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React.podspec b/React.podspec
index 027016aa07cb..030989c3d317 100644
--- a/React.podspec
+++ b/React.podspec
@@ -105,7 +105,7 @@ Pod::Spec.new do |s|
 
   s.subspec "tvOS" do |ss|
     ss.dependency             "React/Core"
-    ss.source_files         = "React/**/RCTTV*.{h, m}"
+    ss.source_files         = "React/**/RCTTV*.{h,m}"
   end
 
   s.subspec "jschelpers" do |ss|

From 4fcd9970bd2dfb24890bc87e9c82e16dab71ec09 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 18 Apr 2018 18:10:22 -0700
Subject: [PATCH 0333/1109] Fix crash when reloading with Perf Monitor enabled

Reviewed By: mdvacca

Differential Revision: D7678392

fbshipit-source-id: 5fcf3bda545896f48543a95d4885c6492fac961e
---
 .../devsupport/DebugOverlayController.java    | 44 +++++++++++--------
 1 file changed, 25 insertions(+), 19 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DebugOverlayController.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DebugOverlayController.java
index b56cbfc7e8c7..9450e27dc4bb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DebugOverlayController.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DebugOverlayController.java
@@ -21,6 +21,7 @@
 
 import com.facebook.common.logging.FLog;
 import com.facebook.react.bridge.ReactContext;
+import com.facebook.react.bridge.UiThreadUtil;
 import com.facebook.react.common.ReactConstants;
 
 import javax.annotation.Nullable;
@@ -94,25 +95,30 @@ public DebugOverlayController(ReactContext reactContext) {
     mWindowManager = (WindowManager) reactContext.getSystemService(Context.WINDOW_SERVICE);
   }
 
-  public void setFpsDebugViewVisible(boolean fpsDebugViewVisible) {
-    if (fpsDebugViewVisible && mFPSDebugViewContainer == null) {
-      if (!permissionCheck(mReactContext)) {
-        FLog.d(ReactConstants.TAG, "Wait for overlay permission to be set");
-        return;
-      }
-      mFPSDebugViewContainer = new FpsView(mReactContext);
-      WindowManager.LayoutParams params = new WindowManager.LayoutParams(
-          WindowManager.LayoutParams.MATCH_PARENT,
-          WindowManager.LayoutParams.MATCH_PARENT,
-          WindowOverlayCompat.TYPE_SYSTEM_OVERLAY,
-          WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
+  public void setFpsDebugViewVisible(final boolean fpsDebugViewVisible) {
+    UiThreadUtil.runOnUiThread(new Runnable() {
+      @Override
+      public void run() {
+        if (fpsDebugViewVisible && mFPSDebugViewContainer == null) {
+          if (!permissionCheck(mReactContext)) {
+            FLog.d(ReactConstants.TAG, "Wait for overlay permission to be set");
+            return;
+          }
+          mFPSDebugViewContainer = new FpsView(mReactContext);
+          WindowManager.LayoutParams params = new WindowManager.LayoutParams(
+            WindowManager.LayoutParams.MATCH_PARENT,
+            WindowManager.LayoutParams.MATCH_PARENT,
+            WindowOverlayCompat.TYPE_SYSTEM_OVERLAY,
+            WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
               | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE,
-          PixelFormat.TRANSLUCENT);
-      mWindowManager.addView(mFPSDebugViewContainer, params);
-    } else if (!fpsDebugViewVisible && mFPSDebugViewContainer != null) {
-      mFPSDebugViewContainer.removeAllViews();
-      mWindowManager.removeView(mFPSDebugViewContainer);
-      mFPSDebugViewContainer = null;
-    }
+            PixelFormat.TRANSLUCENT);
+          mWindowManager.addView(mFPSDebugViewContainer, params);
+        } else if (!fpsDebugViewVisible && mFPSDebugViewContainer != null) {
+          mFPSDebugViewContainer.removeAllViews();
+          mWindowManager.removeView(mFPSDebugViewContainer);
+          mFPSDebugViewContainer = null;
+        }
+      }
+    });
   }
 }

From 49655c6eb38e4354e368a5fbc387bc7981f1d9bd Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 18 Apr 2018 18:13:12 -0700
Subject: [PATCH 0334/1109] Fix BadtokenException thrown when opening Android
 Catalyst app

Reviewed By: achen1

Differential Revision: D7676053

fbshipit-source-id: e0cf9541de131b7c21de9a2647e4270f78b0a107
---
 .../devsupport/DevLoadingViewController.java   | 18 +++++++++---------
 1 file changed, 9 insertions(+), 9 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevLoadingViewController.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevLoadingViewController.java
index 7641b25a3d9d..bc6e6c3b7a7f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevLoadingViewController.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevLoadingViewController.java
@@ -7,6 +7,7 @@
 
 package com.facebook.react.devsupport;
 
+import android.annotation.TargetApi;
 import android.app.Activity;
 import android.content.Context;
 import android.graphics.Color;
@@ -33,6 +34,7 @@
 /**
  * Controller to display loading messages on top of the screen. All methods are thread safe.
  */
+@TargetApi(Build.VERSION_CODES.CUPCAKE)
 public class DevLoadingViewController {
   private static final int COLOR_DARK_GREEN = Color.parseColor("#035900");
 
@@ -158,18 +160,16 @@ private void showInternal() {
       topOffset = rectangle.top;
     }
 
-    mDevLoadingPopup = new PopupWindow(
-            mDevLoadingView,
-            ViewGroup.LayoutParams.MATCH_PARENT,
-            ViewGroup.LayoutParams.WRAP_CONTENT);
+    mDevLoadingPopup = new PopupWindow(currentActivity);
     mDevLoadingPopup.setTouchable(false);
+    mDevLoadingPopup.setWidth(ViewGroup.LayoutParams.MATCH_PARENT);
+    mDevLoadingPopup.setHeight(ViewGroup.LayoutParams.WRAP_CONTENT);
 
     mDevLoadingPopup.showAtLocation(
-            currentActivity.getWindow().getDecorView(),
-            Gravity.NO_GRAVITY,
-
-            0,
-            topOffset);
+      currentActivity.getWindow().getDecorView(),
+      Gravity.NO_GRAVITY,
+      0,
+      topOffset);
   }
 
   private void hideInternal() {

From 7e824867ca9f6acb2e15905a44fdf887308d5b91 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 18 Apr 2018 18:17:50 -0700
Subject: [PATCH 0335/1109] Make Spacing cloneable

Reviewed By: achen1

Differential Revision: D7626745

fbshipit-source-id: ca6070a99d561ee5d5dd27456116dd2de75d2bf3
---
 .../react/uimanager/ReactShadowNodeImpl.java        |  4 +++-
 .../java/com/facebook/react/uimanager/Spacing.java  | 12 ++++++++++--
 .../facebook/react/fabric/FabricUIManagerTest.java  | 13 +++++++++++++
 3 files changed, 26 insertions(+), 3 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index d0eb127f6e29..a8118b1841d0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -106,7 +106,7 @@ public YogaNode cloneNode(YogaNode oldYogaNode,
   private int mScreenY;
   private int mScreenWidth;
   private int mScreenHeight;
-  private final Spacing mDefaultPadding = new Spacing(0);
+  private final Spacing mDefaultPadding;
   private final float[] mPadding = new float[Spacing.ALL + 1];
   private final boolean[] mPaddingIsPercent = new boolean[Spacing.ALL + 1];
   private YogaNode mYogaNode;
@@ -115,6 +115,7 @@ public YogaNode cloneNode(YogaNode oldYogaNode,
   private @Nullable ReactStylesDiffMap mNewProps;
 
   public ReactShadowNodeImpl() {
+    mDefaultPadding = new Spacing(0);
     if (!isVirtual()) {
       YogaNode node = YogaNodePool.get().acquire();
       mYogaNode = node == null ? new YogaNode(sYogaConfig) : node;
@@ -133,6 +134,7 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     mShouldNotifyOnLayout = original.mShouldNotifyOnLayout;
     mIsLayoutOnly = original.mIsLayoutOnly;
     mNativeParent = original.mNativeParent;
+    mDefaultPadding = new Spacing(original.mDefaultPadding);
     // Cloned nodes should be always updated.
     mNodeUpdated = true;
     // "cached" screen coordinates are not cloned because FabricJS not always clone the last
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/Spacing.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/Spacing.java
index 53bea8824d76..e386db4db664 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/Spacing.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/Spacing.java
@@ -68,9 +68,9 @@ public class Spacing {
     256, /*ALL*/
   };
 
-  private final float[] mSpacing = newFullSpacingArray();
+  private final float[] mSpacing;
   private int mValueFlags = 0;
-  private float mDefaultValue;
+  private final float mDefaultValue;
   private boolean mHasAliasesSet;
 
   public Spacing() {
@@ -79,6 +79,14 @@ public Spacing() {
 
   public Spacing(float defaultValue) {
     mDefaultValue = defaultValue;
+    mSpacing = newFullSpacingArray();
+  }
+
+  public Spacing(Spacing original) {
+    mDefaultValue = original.mDefaultValue;
+    mSpacing = Arrays.copyOf(original.mSpacing, original.mSpacing.length);
+    mValueFlags = original.mValueFlags;
+    mHasAliasesSet = original.mHasAliasesSet;
   }
 
   /**
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 40c8b2e78d55..441003004bd1 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -29,6 +29,7 @@
 import java.util.Collections;
 import java.util.LinkedList;
 import java.util.List;
+import org.fest.assertions.data.Offset;
 import org.junit.Before;
 import org.junit.Test;
 import org.junit.runner.RunWith;
@@ -113,6 +114,18 @@ public void testCloneNode() {
     assertThat(clonedNode.getChildAt(0)).isEqualTo(child);
   }
 
+  @Test
+  public void testDefaultSpacingCloning() {
+    ReactShadowNode node = createViewNode();
+    node.setDefaultPadding(Spacing.LEFT, 10);
+
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node);
+
+    node.setDefaultPadding(Spacing.LEFT, 20);
+    assertThat(clonedNode.getStylePadding(Spacing.LEFT).value).isEqualTo(10f, Offset.offset(0.01f));
+    assertThat(node.getStylePadding(Spacing.LEFT).value).isEqualTo(20f, Offset.offset(0.01f));
+  }
+
   @Test
   public void testCloneVirtualNode() {
     ReactRawTextShadowNode node = new ReactRawTextShadowNode();

From 3c0b8922e2c45760cd5635f4402563ae95ac5628 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 19 Apr 2018 02:30:39 -0700
Subject: [PATCH 0336/1109] Upgrade Prettier to v1.12.1 on fbsource

Reviewed By: benjaffe, ryanmce, yungsters

Differential Revision: D7652946

fbshipit-source-id: 396d45c675e93f2298cd2920d927630c81867447
---
 Libraries/Image/Image.android.js        | 16 ++++++++++------
 Libraries/Lists/VirtualizedList.js      |  8 +++++---
 Libraries/StyleSheet/StyleSheetTypes.js | 10 ++++++----
 package.json                            |  2 +-
 4 files changed, 22 insertions(+), 14 deletions(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index 870b31cd8f92..4c8fa6e7fd17 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -75,8 +75,8 @@ var Image = createReactClass({
      */
     blurRadius: PropTypes.number,
     /**
-    * See https://facebook.github.io/react-native/docs/image.html#defaultsource
-    */
+     * See https://facebook.github.io/react-native/docs/image.html#defaultsource
+     */
     defaultSource: PropTypes.number,
     /**
      * See https://facebook.github.io/react-native/docs/image.html#loadingindicatorsource
@@ -123,7 +123,13 @@ var Image = createReactClass({
      *
      * See https://facebook.github.io/react-native/docs/image.html#resizemode
      */
-    resizeMode: PropTypes.oneOf(['cover', 'contain', 'stretch', 'repeat', 'center']),
+    resizeMode: PropTypes.oneOf([
+      'cover',
+      'contain',
+      'stretch',
+      'repeat',
+      'center',
+    ]),
   },
 
   statics: {
@@ -254,9 +260,7 @@ var Image = createReactClass({
         ),
         src: sources,
         headers: source.headers,
-        defaultSrc: defaultSource
-          ? defaultSource.uri
-          : null,
+        defaultSrc: defaultSource ? defaultSource.uri : null,
         loadingIndicatorSrc: loadingIndicatorSource
           ? loadingIndicatorSource.uri
           : null,
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 2b1b83ff41bb..30e8777eaee4 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -852,14 +852,14 @@ class VirtualizedList extends React.PureComponent<Props, State> {
         );
       }
     } else if (ListEmptyComponent) {
-      const element: React.Element<any> = (React.isValidElement(
+      const element: React.Element<any> = ((React.isValidElement(
         ListEmptyComponent,
       ) ? (
         ListEmptyComponent
       ) : (
         // $FlowFixMe
         <ListEmptyComponent />
-      ): any);
+      )): any);
       cells.push(
         React.cloneElement(element, {
           key: '$empty',
@@ -1670,7 +1670,9 @@ class CellRenderer extends React.Component<
       ? horizontal
         ? [{flexDirection: 'row-reverse'}, inversionStyle]
         : [{flexDirection: 'column-reverse'}, inversionStyle]
-      : horizontal ? [{flexDirection: 'row'}, inversionStyle] : inversionStyle;
+      : horizontal
+        ? [{flexDirection: 'row'}, inversionStyle]
+        : inversionStyle;
     if (!CellRendererComponent) {
       return (
         <View style={cellStyle} onLayout={onLayout}>
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index ffec5b54bc79..a176ca1e8107 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -103,14 +103,16 @@ export type ____TransformStyle_Internal = $ReadOnly<{|
     | {|+translateX: number | AnimatedNode|}
     | {|+translateY: number | AnimatedNode|}
     | {|
-      +translate: [number | AnimatedNode, number | AnimatedNode] | AnimatedNode,
-    |}
+        +translate:
+          | [number | AnimatedNode, number | AnimatedNode]
+          | AnimatedNode,
+      |}
     | {|+skewX: string|}
     | {|+skewY: string|}
     // TODO: what is the actual type it expects?
     | {|
-      +matrix: $ReadOnlyArray<number | AnimatedNode> | AnimatedNode,
-    |},
+        +matrix: $ReadOnlyArray<number | AnimatedNode> | AnimatedNode,
+      |},
   >,
 |}>;
 
diff --git a/package.json b/package.json
index c28da3b6dc12..8cadfda93457 100644
--- a/package.json
+++ b/package.json
@@ -209,7 +209,7 @@
     "flow-bin": "^0.70.0",
     "jest": "23.0.0-alpha.4",
     "jest-junit": "3.6.0",
-    "prettier": "1.9.1",
+    "prettier": "1.12.1",
     "react": "16.3.2",
     "react-test-renderer": "16.3.2",
     "shelljs": "^0.7.8",

From 34bd776af2f2529009188fced91083203a48fd40 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 19 Apr 2018 03:53:40 -0700
Subject: [PATCH 0337/1109] Bump babel-preset-react-native version to 5.0.0 for
 Babel 7

Reviewed By: rafeca

Differential Revision: D7685340

fbshipit-source-id: f229fb5da71f2f1d277d3d55eaa0f400aa76471b
---
 babel-preset/package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/babel-preset/package.json b/babel-preset/package.json
index 066af5f61b15..120c8b7a68ee 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -1,6 +1,6 @@
 {
   "name": "babel-preset-react-native",
-  "version": "4.0.0",
+  "version": "5.0.0",
   "description": "Babel preset for React Native applications",
   "main": "index.js",
   "repository": "https://github.com/facebook/react-native/tree/master/babel-preset",

From 0f2e46e84b1513039e4bc6633ba04e69a44ed8ed Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 19 Apr 2018 08:14:59 -0700
Subject: [PATCH 0338/1109] Remove `Color` workspace

Reviewed By: mjesun

Differential Revision: D7637457

fbshipit-source-id: befee31c649edde654c05e7ba889f7c55b105b86
---
 Libraries/Color/package.json | 5 -----
 1 file changed, 5 deletions(-)
 delete mode 100644 Libraries/Color/package.json

diff --git a/Libraries/Color/package.json b/Libraries/Color/package.json
deleted file mode 100644
index 1781e2e3d60b..000000000000
--- a/Libraries/Color/package.json
+++ /dev/null
@@ -1,5 +0,0 @@
-{
-  "name": "Color",
-  "private": true,
-  "version": "0.0.0"
-}

From d408de0438bc186cf460f01c075a055cbb96dcda Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 19 Apr 2018 09:09:05 -0700
Subject: [PATCH 0339/1109] Drop confusing comment

Summary:
Just removing a comment

As per https://github.com/facebook/react-native/commit/f8d6b97140cffe8d18b2558f94570c8d1b410d5c#r28569388

While the comment was more to notify about this in general, I suppose it doesn't matter.

Reviewed By: rafeca

Differential Revision: D7685277

fbshipit-source-id: 2d526aeccc2e89b42ae25cbce21af5fe96f1348d
---
 babel-preset/configs/main.js | 1 -
 jest/preprocessor.js         | 1 -
 2 files changed, 2 deletions(-)

diff --git a/babel-preset/configs/main.js b/babel-preset/configs/main.js
index d17db86969f7..0b972f595b74 100644
--- a/babel-preset/configs/main.js
+++ b/babel-preset/configs/main.js
@@ -15,7 +15,6 @@ const defaultPlugins = [
   [
     require('@babel/plugin-proposal-class-properties'),
     // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
-    // (Makes the properties enumerable)
     {loose: true},
   ],
   [require('@babel/plugin-transform-computed-properties')],
diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index a7c52411f190..5e43175de95e 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -62,7 +62,6 @@ module.exports = {
         [
           require('@babel/plugin-proposal-class-properties'),
           // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
-          // (Makes the properties enumerable)
           {loose: true},
         ],
         [require('@babel/plugin-transform-computed-properties')],

From c18684a2931ea407fef58755304c0b3f57c0dbef Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 19 Apr 2018 09:09:06 -0700
Subject: [PATCH 0340/1109] Fix the metro paths for files detected as nodejs

Summary: Fix the path lookup for files to be considered to run in nodejs.

Reviewed By: mjesun

Differential Revision: D7685278

fbshipit-source-id: c921d40b60d795820448842aec464e7ff82b6eab
---
 jest/preprocessor.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index 5e43175de95e..563ad0389b22 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -24,7 +24,7 @@ const generate = require('@babel/generator').default;
 
 const nodeFiles = RegExp([
   '/local-cli/',
-  '/metro(-bundler)?/',
+  '/metro(?:-[^\/]*)?/', // metro, metro-core, metro-source-map, metro-etc
 ].join('|'));
 const nodeOptions = babelRegisterOnly.config([nodeFiles]);
 

From da57ae740d30b1c8d1616028139eb96e82157170 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 19 Apr 2018 09:09:08 -0700
Subject: [PATCH 0341/1109] Add `ast: true` to transform options for jest

Summary:
This should (at least partially) fix testing for OSS as per https://github.com/facebook/react-native/commit/f8d6b97140cffe8d18b2558f94570c8d1b410d5c#r28647044

Might be related to not locking down the Babel version, will do that in a different commit.

Reviewed By: mjesun

Differential Revision: D7685279

fbshipit-source-id: f00febfad2cec31b7e11996ee8efa2c96b44477b
---
 jest/preprocessor.js | 1 +
 1 file changed, 1 insertion(+)

diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index 563ad0389b22..18ef328e5f44 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -46,6 +46,7 @@ module.exports = {
       localPath: file,
       options: {
         assetDataPlugins: [],
+        ast: true, // needed for open source (?) https://github.com/facebook/react-native/commit/f8d6b97140cffe8d18b2558f94570c8d1b410d5c#r28647044
         dev: true,
         inlineRequires: true,
         minify: false,

From 864235636787cf7888938070df5dec030547df19 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 19 Apr 2018 09:09:10 -0700
Subject: [PATCH 0342/1109] Drop workspace from metro lookup

Summary: Fix the path lookup for metro root.

Reviewed By: mjesun

Differential Revision: D7685280

fbshipit-source-id: 8d506bbf9c5af297d4050d2fa73475fd280bb186
---
 setupBabel.js | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/setupBabel.js b/setupBabel.js
index 0b21ffe31f5c..6bac7dde43ae 100644
--- a/setupBabel.js
+++ b/setupBabel.js
@@ -23,8 +23,8 @@ function buildRegExps(basePath, dirPaths) {
     folderPath =>
       folderPath === 'metro'
         // metro uses flow (for example) which needs to be stripped out w/babel.
-        // it'll resolve to .../metro/packages/metro/src/index.js we want root
-        ? path.resolve(require.resolve('metro'), '..', '..', '..', '..')
+        // it'll resolve to .../metro/src/index.js we want root
+        ? path.resolve(require.resolve('metro'), '..')
         // Babel `only` option works with forward slashes in the RegExp so replace
         // backslashes for Windows.
         : folderPath instanceof RegExp

From 3aa453d975794faa38f21a78c232628c6f4233db Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 19 Apr 2018 09:53:11 -0700
Subject: [PATCH 0343/1109] Add sourceType as a new mandatory option

Summary:
The `sourceType` option is a new mandatory option for Babel which determines whether to parse the file with the module or script goal. The value "disambiguous" determines this state by parsing.

See https://github.com/babel/babel/pull/7417

Reviewed By: mjesun

Differential Revision: D7685610

fbshipit-source-id: 3958c5ad396592bb1d790e2df4ce315737421a2f
---
 jest/preprocessor.js | 1 +
 1 file changed, 1 insertion(+)

diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index 18ef328e5f44..170f7091c308 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -53,6 +53,7 @@ module.exports = {
         platform: '',
         projectRoot: '',
         retainLines: true,
+        sourceType: 'unambiguous', // b7 required. detects module vs script mode
       },
       src,
       plugins: [

From dc836780cbe71c5152a4861bd6a2dba1549bc53f Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Thu, 19 Apr 2018 10:46:33 -0700
Subject: [PATCH 0344/1109] Make ShadowNodeRegistry thread safe

Reviewed By: achen1

Differential Revision: D7679621

fbshipit-source-id: 1003578edcf9107b736d876dac969f22f9e62b6d
---
 .../com/facebook/react/uimanager/ShadowNodeRegistry.java   | 4 +---
 .../com/facebook/react/uimanager/UIImplementation.java     | 7 ++++++-
 2 files changed, 7 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ShadowNodeRegistry.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ShadowNodeRegistry.java
index 1b3cebc1fb24..bc68ab326079 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ShadowNodeRegistry.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ShadowNodeRegistry.java
@@ -28,9 +28,7 @@ public ShadowNodeRegistry() {
   }
 
   public void addRootNode(ReactShadowNode node) {
-    // TODO(6242243): This should be asserted... but UIManagerModule is
-    // thread-unsafe and calls this on the wrong thread.
-    //mThreadAsserter.assertNow();
+    mThreadAsserter.assertNow();
     int tag = node.getReactTag();
     mTagsToCSSNodes.put(tag, node);
     mRootTags.put(tag, true);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
index 186a4d4357c3..5f124ab88ab4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
@@ -205,7 +205,12 @@ public <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> void register
     int heightMeasureSpec = rootView.getHeightMeasureSpec();
     updateRootView(rootCSSNode, widthMeasureSpec, heightMeasureSpec);
 
-    mShadowNodeRegistry.addRootNode(rootCSSNode);
+    context.runOnNativeModulesQueueThread(new Runnable() {
+      @Override
+      public void run() {
+        mShadowNodeRegistry.addRootNode(rootCSSNode);
+      }
+    });
 
     // register it within NativeViewHierarchyManager
     mOperationsQueue.addRootView(tag, rootView, context);

From 60b05133baafe9ec4020d5ddf99b71a2302ba3dc Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 19 Apr 2018 11:03:50 -0700
Subject: [PATCH 0345/1109] Unforked renderApplication()

Summary: This allows toggling fabric renderer via the same renderApplication()

Reviewed By: mdvacca

Differential Revision: D7682524

fbshipit-source-id: 59be1d2bea15f5e13e64e2d72304d79f9cb7d084
---
 Libraries/ReactNative/AppContainer.js        |  4 +-
 Libraries/ReactNative/AppRegistry.js         | 19 +------
 Libraries/ReactNative/renderApplication.js   |  8 ++-
 Libraries/ReactNative/renderFabricSurface.js | 59 --------------------
 4 files changed, 10 insertions(+), 80 deletions(-)
 delete mode 100644 Libraries/ReactNative/renderFabricSurface.js

diff --git a/Libraries/ReactNative/AppContainer.js b/Libraries/ReactNative/AppContainer.js
index 3060d6de4500..cb1ea048e4ad 100644
--- a/Libraries/ReactNative/AppContainer.js
+++ b/Libraries/ReactNative/AppContainer.js
@@ -27,7 +27,6 @@ type Props = {|
    * suppresses an error when upgrading Flow's support for React. To see the
    * error delete this comment and run Flow. */
   children?: React.Children,
-  fabric?: boolean,
   rootTag: number,
   WrapperComponent?: ?React.ComponentType<*>,
 |};
@@ -91,8 +90,7 @@ class AppContainer extends React.Component<Props, State> {
   render(): React.Node {
     let yellowBox = null;
     if (__DEV__) {
-      if (!global.__RCTProfileIsProfiling && !this.props.fabric) {
-        // TODO: Fabric doesn't support YellowBox.
+      if (!global.__RCTProfileIsProfiling) {
         const YellowBox = require('YellowBox');
         yellowBox = <YellowBox />;
       }
diff --git a/Libraries/ReactNative/AppRegistry.js b/Libraries/ReactNative/AppRegistry.js
index 8ddfb64118d0..efe8e5584f2f 100644
--- a/Libraries/ReactNative/AppRegistry.js
+++ b/Libraries/ReactNative/AppRegistry.js
@@ -20,10 +20,6 @@ const infoLog = require('infoLog');
 const invariant = require('fbjs/lib/invariant');
 const renderApplication = require('renderApplication');
 
-// Renderer provider must be supplied by each app. If none, traditional
-// renderApplication() will be used.
-let fabricRendererProvider: ?() => typeof renderApplication = null;
-
 type Task = (taskData: any) => Promise<void>;
 type TaskProvider = () => Task;
 export type ComponentProvider = () => React$ComponentType<any>;
@@ -102,19 +98,12 @@ const AppRegistry = {
     runnables[appKey] = {
       componentProvider,
       run: appParameters => {
-        let renderFunc = renderApplication;
-        if (appParameters.fabric) {
-          invariant(
-            fabricRendererProvider != null,
-            'A Fabric renderer provider must be set to render Fabric components',
-          );
-          renderFunc = fabricRendererProvider();
-        }
-        renderFunc(
+        renderApplication(
           componentProviderInstrumentationHook(componentProvider),
           appParameters.initialProps,
           appParameters.rootTag,
           wrapperComponentProvider && wrapperComponentProvider(appParameters),
+          appParameters.fabric,
         );
       },
     };
@@ -249,10 +238,6 @@ const AppRegistry = {
         NativeModules.HeadlessJsTaskSupport.notifyTaskFinished(taskId);
       });
   },
-
-  setFabricRendererProvider(provider: () => typeof renderApplication): void {
-    fabricRendererProvider = provider;
-  },
 };
 
 BatchedBridge.registerCallableModule('AppRegistry', AppRegistry);
diff --git a/Libraries/ReactNative/renderApplication.js b/Libraries/ReactNative/renderApplication.js
index 896c88207eb0..8abfed260402 100644
--- a/Libraries/ReactNative/renderApplication.js
+++ b/Libraries/ReactNative/renderApplication.js
@@ -13,6 +13,7 @@
 
 const AppContainer = require('AppContainer');
 const React = require('React');
+const ReactFabric = require('ReactFabric');
 const ReactNative = require('ReactNative');
 
 const invariant = require('fbjs/lib/invariant');
@@ -25,6 +26,7 @@ function renderApplication<Props: Object>(
   initialProps: Props,
   rootTag: any,
   WrapperComponent?: ?React.ComponentType<*>,
+  fabric?: boolean,
 ) {
   invariant(rootTag, 'Expect to have a valid rootTag, instead got ', rootTag);
 
@@ -49,7 +51,11 @@ function renderApplication<Props: Object>(
     renderable = <AsyncMode>{renderable}</AsyncMode>;
   }
 
-  ReactNative.render(renderable, rootTag);
+  if (fabric) {
+    ReactFabric.render(renderable, rootTag);
+  } else {
+    ReactNative.render(renderable, rootTag);
+  }
 }
 
 module.exports = renderApplication;
diff --git a/Libraries/ReactNative/renderFabricSurface.js b/Libraries/ReactNative/renderFabricSurface.js
deleted file mode 100644
index 0279f1759926..000000000000
--- a/Libraries/ReactNative/renderFabricSurface.js
+++ /dev/null
@@ -1,59 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule renderFabricSurface
- * @format
- * @flow
- */
-
-'use strict';
-
-const AppContainer = require('AppContainer');
-const React = require('React');
-const ReactFabric = require('ReactFabric');
-
-const invariant = require('fbjs/lib/invariant');
-
-// require BackHandler so it sets the default handler that exits the app if no listeners respond
-require('BackHandler');
-
-// Note: this is a fork of renderApplication.js to simply invoke ReactFabric.
-function renderFabricSurface<Props: Object>(
-  RootComponent: React.ComponentType<Props>,
-  initialProps: Props,
-  rootTag: any,
-  WrapperComponent?: ?React.ComponentType<*>,
-) {
-  invariant(rootTag, 'Expect to have a valid rootTag, instead got ', rootTag);
-
-  let renderable = (
-    <AppContainer
-      fabric={true}
-      rootTag={rootTag}
-      WrapperComponent={WrapperComponent}>
-      <RootComponent {...initialProps} rootTag={rootTag} />
-    </AppContainer>
-  );
-
-  // If the root component is async, the user probably wants the initial render
-  // to be async also. To do this, wrap AppContainer with an async marker.
-  // For more info see https://fb.me/is-component-async
-  if (
-    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
-     * error found when Flow v0.68 was deployed. To see the error delete this
-     * comment and run Flow. */
-    RootComponent.prototype != null &&
-    RootComponent.prototype.unstable_isAsyncReactComponent === true
-  ) {
-    // $FlowFixMe This is not yet part of the official public API
-    const AsyncMode = React.unstable_AsyncMode;
-    renderable = <AsyncMode>{renderable}</AsyncMode>;
-  }
-
-  ReactFabric.render(renderable, rootTag);
-}
-
-module.exports = renderFabricSurface;

From c5ca26a0e5c0660196300ee34d6007c63879611f Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Thu, 19 Apr 2018 11:06:28 -0700
Subject: [PATCH 0346/1109] Correct draw path dimensions while doing even
 border

Reviewed By: achen1

Differential Revision: D7678473

fbshipit-source-id: 8aa5eb29d22379eaabf9951a901e237fb7569632
---
 .../view/ReactViewBackgroundDrawable.java     | 227 +++++++++++-------
 1 file changed, 139 insertions(+), 88 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
index 9e374b4c502e..1a31a0cc38bd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundDrawable.java
@@ -90,9 +90,11 @@ private static enum BorderStyle {
   private @Nullable Path mOuterClipPathForBorderRadius;
   private @Nullable Path mPathForBorderRadiusOutline;
   private @Nullable Path mPathForBorder;
+  private @Nullable Path mCenterDrawPath;
   private @Nullable RectF mInnerClipTempRectForBorderRadius;
   private @Nullable RectF mOuterClipTempRectForBorderRadius;
   private @Nullable RectF mTempRectForBorderRadiusOutline;
+  private @Nullable RectF mTempRectForCenterDrawPath;
   private @Nullable PointF mInnerTopLeftCorner;
   private @Nullable PointF mInnerTopRightCorner;
   private @Nullable PointF mInnerBottomRightCorner;
@@ -343,110 +345,130 @@ private void drawRoundedBackgroundWithBorders(Canvas canvas) {
         || borderWidth.bottom > 0
         || borderWidth.left > 0
         || borderWidth.right > 0) {
-      mPaint.setStyle(Paint.Style.FILL);
 
-      // Draw border
-      canvas.clipPath(mOuterClipPathForBorderRadius, Region.Op.INTERSECT);
-      canvas.clipPath(mInnerClipPathForBorderRadius, Region.Op.DIFFERENCE);
+      //If it's a full and even border draw inner rect path with stroke
+      final float fullBorderWidth = getFullBorderWidth();
+      if (borderWidth.top == fullBorderWidth &&
+        borderWidth.bottom == fullBorderWidth &&
+        borderWidth.left == fullBorderWidth &&
+        borderWidth.right == fullBorderWidth) {
+        if (fullBorderWidth > 0) {
+          int borderColor = getBorderColor(Spacing.ALL);
+          mPaint.setColor(ColorUtil.multiplyColorAlpha(borderColor, mAlpha));
+          mPaint.setStyle(Paint.Style.STROKE);
+          mPaint.setStrokeWidth(fullBorderWidth);
+          canvas.drawPath(mCenterDrawPath, mPaint);
+        }
+      }
+      //In the case of uneven border widths/colors draw quadrilateral in each direction
+      else {
+        mPaint.setStyle(Paint.Style.FILL);
 
-      int colorLeft = getBorderColor(Spacing.LEFT);
-      int colorTop = getBorderColor(Spacing.TOP);
-      int colorRight = getBorderColor(Spacing.RIGHT);
-      int colorBottom = getBorderColor(Spacing.BOTTOM);
+        // Draw border
+        canvas.clipPath(mOuterClipPathForBorderRadius, Region.Op.INTERSECT);
+        canvas.clipPath(mInnerClipPathForBorderRadius, Region.Op.DIFFERENCE);
 
-      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
-        final boolean isRTL = getResolvedLayoutDirection() == View.LAYOUT_DIRECTION_RTL;
-        int colorStart = getBorderColor(Spacing.START);
-        int colorEnd = getBorderColor(Spacing.END);
+        int colorLeft = getBorderColor(Spacing.LEFT);
+        int colorTop = getBorderColor(Spacing.TOP);
+        int colorRight = getBorderColor(Spacing.RIGHT);
+        int colorBottom = getBorderColor(Spacing.BOTTOM);
 
-        if (I18nUtil.getInstance().doLeftAndRightSwapInRTL(mContext)) {
-          if (!isBorderColorDefined(Spacing.START)) {
-            colorStart = colorLeft;
-          }
+        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
+          final boolean isRTL = getResolvedLayoutDirection() == View.LAYOUT_DIRECTION_RTL;
+          int colorStart = getBorderColor(Spacing.START);
+          int colorEnd = getBorderColor(Spacing.END);
 
-          if (!isBorderColorDefined(Spacing.END)) {
-            colorEnd = colorRight;
-          }
+          if (I18nUtil.getInstance().doLeftAndRightSwapInRTL(mContext)) {
+            if (!isBorderColorDefined(Spacing.START)) {
+              colorStart = colorLeft;
+            }
 
-          final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
-          final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
+            if (!isBorderColorDefined(Spacing.END)) {
+              colorEnd = colorRight;
+            }
 
-          colorLeft = directionAwareColorLeft;
-          colorRight = directionAwareColorRight;
-        } else {
-          final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
-          final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
+            final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
+            final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
 
-          final boolean isColorStartDefined = isBorderColorDefined(Spacing.START);
-          final boolean isColorEndDefined = isBorderColorDefined(Spacing.END);
-          final boolean isDirectionAwareColorLeftDefined = isRTL ? isColorEndDefined : isColorStartDefined;
-          final boolean isDirectionAwareColorRightDefined = isRTL ? isColorStartDefined : isColorEndDefined;
-
-          if (isDirectionAwareColorLeftDefined) {
             colorLeft = directionAwareColorLeft;
-          }
-
-          if (isDirectionAwareColorRightDefined) {
             colorRight = directionAwareColorRight;
+          } else {
+            final int directionAwareColorLeft = isRTL ? colorEnd : colorStart;
+            final int directionAwareColorRight = isRTL ? colorStart : colorEnd;
+
+            final boolean isColorStartDefined = isBorderColorDefined(Spacing.START);
+            final boolean isColorEndDefined = isBorderColorDefined(Spacing.END);
+            final boolean isDirectionAwareColorLeftDefined =
+              isRTL ? isColorEndDefined : isColorStartDefined;
+            final boolean isDirectionAwareColorRightDefined =
+              isRTL ? isColorStartDefined : isColorEndDefined;
+
+            if (isDirectionAwareColorLeftDefined) {
+              colorLeft = directionAwareColorLeft;
+            }
+
+            if (isDirectionAwareColorRightDefined) {
+              colorRight = directionAwareColorRight;
+            }
           }
         }
-      }
 
-      final float left = mOuterClipTempRectForBorderRadius.left;
-      final float right = mOuterClipTempRectForBorderRadius.right;
-      final float top = mOuterClipTempRectForBorderRadius.top;
-      final float bottom = mOuterClipTempRectForBorderRadius.bottom;
-
-      if (borderWidth.left > 0) {
-        final float x1 = left;
-        final float y1 = top;
-        final float x2 = mInnerTopLeftCorner.x;
-        final float y2 = mInnerTopLeftCorner.y;
-        final float x3 = mInnerBottomLeftCorner.x;
-        final float y3 = mInnerBottomLeftCorner.y;
-        final float x4 = left;
-        final float y4 = bottom;
-
-        drawQuadrilateral(canvas, colorLeft, x1, y1, x2, y2, x3, y3, x4, y4);
-      }
+        final float left = mOuterClipTempRectForBorderRadius.left;
+        final float right = mOuterClipTempRectForBorderRadius.right;
+        final float top = mOuterClipTempRectForBorderRadius.top;
+        final float bottom = mOuterClipTempRectForBorderRadius.bottom;
 
-      if (borderWidth.top > 0) {
-        final float x1 = left;
-        final float y1 = top;
-        final float x2 = mInnerTopLeftCorner.x;
-        final float y2 = mInnerTopLeftCorner.y;
-        final float x3 = mInnerTopRightCorner.x;
-        final float y3 = mInnerTopRightCorner.y;
-        final float x4 = right;
-        final float y4 = top;
-
-        drawQuadrilateral(canvas, colorTop, x1, y1, x2, y2, x3, y3, x4, y4);
-      }
+        if (borderWidth.left > 0) {
+          final float x1 = left;
+          final float y1 = top;
+          final float x2 = mInnerTopLeftCorner.x;
+          final float y2 = mInnerTopLeftCorner.y;
+          final float x3 = mInnerBottomLeftCorner.x;
+          final float y3 = mInnerBottomLeftCorner.y;
+          final float x4 = left;
+          final float y4 = bottom;
 
-      if (borderWidth.right > 0) {
-        final float x1 = right;
-        final float y1 = top;
-        final float x2 = mInnerTopRightCorner.x;
-        final float y2 = mInnerTopRightCorner.y;
-        final float x3 = mInnerBottomRightCorner.x;
-        final float y3 = mInnerBottomRightCorner.y;
-        final float x4 = right;
-        final float y4 = bottom;
-
-        drawQuadrilateral(canvas, colorRight, x1, y1, x2, y2, x3, y3, x4, y4);
-      }
+          drawQuadrilateral(canvas, colorLeft, x1, y1, x2, y2, x3, y3, x4, y4);
+        }
+
+        if (borderWidth.top > 0) {
+          final float x1 = left;
+          final float y1 = top;
+          final float x2 = mInnerTopLeftCorner.x;
+          final float y2 = mInnerTopLeftCorner.y;
+          final float x3 = mInnerTopRightCorner.x;
+          final float y3 = mInnerTopRightCorner.y;
+          final float x4 = right;
+          final float y4 = top;
+
+          drawQuadrilateral(canvas, colorTop, x1, y1, x2, y2, x3, y3, x4, y4);
+        }
+
+        if (borderWidth.right > 0) {
+          final float x1 = right;
+          final float y1 = top;
+          final float x2 = mInnerTopRightCorner.x;
+          final float y2 = mInnerTopRightCorner.y;
+          final float x3 = mInnerBottomRightCorner.x;
+          final float y3 = mInnerBottomRightCorner.y;
+          final float x4 = right;
+          final float y4 = bottom;
 
-      if (borderWidth.bottom > 0) {
-        final float x1 = left;
-        final float y1 = bottom;
-        final float x2 = mInnerBottomLeftCorner.x;
-        final float y2 = mInnerBottomLeftCorner.y;
-        final float x3 = mInnerBottomRightCorner.x;
-        final float y3 = mInnerBottomRightCorner.y;
-        final float x4 = right;
-        final float y4 = bottom;
-
-        drawQuadrilateral(canvas, colorBottom, x1, y1, x2, y2, x3, y3, x4, y4);
+          drawQuadrilateral(canvas, colorRight, x1, y1, x2, y2, x3, y3, x4, y4);
+        }
+
+        if (borderWidth.bottom > 0) {
+          final float x1 = left;
+          final float y1 = bottom;
+          final float x2 = mInnerBottomLeftCorner.x;
+          final float y2 = mInnerBottomLeftCorner.y;
+          final float x3 = mInnerBottomRightCorner.x;
+          final float y3 = mInnerBottomRightCorner.y;
+          final float x4 = right;
+          final float y4 = bottom;
+
+          drawQuadrilateral(canvas, colorBottom, x1, y1, x2, y2, x3, y3, x4, y4);
+        }
       }
     }
 
@@ -472,6 +494,10 @@ private void updatePath() {
       mPathForBorderRadiusOutline = new Path();
     }
 
+    if (mCenterDrawPath == null) {
+      mCenterDrawPath = new Path();
+    }
+
     if (mInnerClipTempRectForBorderRadius == null) {
       mInnerClipTempRectForBorderRadius = new RectF();
     }
@@ -484,13 +510,24 @@ private void updatePath() {
       mTempRectForBorderRadiusOutline = new RectF();
     }
 
+    if (mTempRectForCenterDrawPath == null) {
+      mTempRectForCenterDrawPath = new RectF();
+    }
+
     mInnerClipPathForBorderRadius.reset();
     mOuterClipPathForBorderRadius.reset();
     mPathForBorderRadiusOutline.reset();
+    mCenterDrawPath.reset();
 
     mInnerClipTempRectForBorderRadius.set(getBounds());
     mOuterClipTempRectForBorderRadius.set(getBounds());
     mTempRectForBorderRadiusOutline.set(getBounds());
+    mTempRectForCenterDrawPath.set(getBounds());
+
+    float fullBorderWidth = getFullBorderWidth();
+    if (fullBorderWidth > 0) {
+      mTempRectForCenterDrawPath.inset(fullBorderWidth * 0.5f, fullBorderWidth * 0.5f);
+    }
 
     final RectF borderWidth = getDirectionAwareBorderInsets();
 
@@ -623,6 +660,20 @@ private void updatePath() {
       },
       Path.Direction.CW);
 
+    mCenterDrawPath.addRoundRect(
+      mTempRectForCenterDrawPath,
+      new float[] {
+        innerTopLeftRadiusX + extraRadiusForOutline,
+        innerTopLeftRadiusY + extraRadiusForOutline,
+        innerTopRightRadiusX + extraRadiusForOutline,
+        innerTopRightRadiusY + extraRadiusForOutline,
+        innerBottomRightRadiusX + extraRadiusForOutline,
+        innerBottomRightRadiusY + extraRadiusForOutline,
+        innerBottomLeftRadiusX + extraRadiusForOutline,
+        innerBottomLeftRadiusY + extraRadiusForOutline
+      },
+      Path.Direction.CW);
+
     /**
      * Rounded Multi-Colored Border Algorithm:
      *

From 654435d1ed9e584e65fff601e1fa50591e042664 Mon Sep 17 00:00:00 2001
From: Knott Wittawat <kntt@fb.com>
Date: Thu, 19 Apr 2018 13:13:10 -0700
Subject: [PATCH 0347/1109] Fix VoiceOver not identifying the header correctly

Reviewed By: sophiebits

Differential Revision: D7678644

fbshipit-source-id: ee6c57f2a603eed1c41f22a4142474ab6957ccdf
---
 Libraries/Text/TextProps.js | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/Libraries/Text/TextProps.js b/Libraries/Text/TextProps.js
index 20eb363765e2..effc8b05480b 100644
--- a/Libraries/Text/TextProps.js
+++ b/Libraries/Text/TextProps.js
@@ -11,6 +11,8 @@
 
 'use strict';
 
+import type {AccessibilityTrait} from 'ViewAccessibility';
+
 import type {Node} from 'react';
 
 import type {LayoutEvent, PressEvent} from 'CoreEventTypes';
@@ -28,6 +30,7 @@ type PressRetentionOffset = {
  */
 export type TextProps = $ReadOnly<{
   accessible?: ?boolean,
+  accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
   allowFontScaling?: ?boolean,
   children?: Node,
   ellipsizeMode?: 'clip' | 'head' | 'middle' | 'tail',

From d69e55060fd76d91eccc45905d250a9fce4b2c49 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Thu, 19 Apr 2018 15:42:49 -0700
Subject: [PATCH 0348/1109] RN: Support `flexWrap: 'wrap-reverse'`

Reviewed By: fkgozali

Differential Revision: D7684403

fbshipit-source-id: 6c247ba86b8ad1bb4dcc8f44f5609c939afe0f06
---
 Libraries/StyleSheet/LayoutPropTypes.js                       | 3 ++-
 Libraries/StyleSheet/StyleSheetTypes.js                       | 2 +-
 React/Base/RCTConvert.m                                       | 3 ++-
 .../java/com/facebook/react/uimanager/LayoutShadowNode.java   | 4 ++++
 4 files changed, 9 insertions(+), 3 deletions(-)

diff --git a/Libraries/StyleSheet/LayoutPropTypes.js b/Libraries/StyleSheet/LayoutPropTypes.js
index 5921334c5b7c..02ec8733f6bb 100644
--- a/Libraries/StyleSheet/LayoutPropTypes.js
+++ b/Libraries/StyleSheet/LayoutPropTypes.js
@@ -432,7 +432,8 @@ var LayoutPropTypes = {
    */
   flexWrap: ReactPropTypes.oneOf([
     'wrap',
-    'nowrap'
+    'nowrap',
+    'wrap-reverse'
   ]),
 
   /** `justifyContent` aligns children in the main direction.
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index a176ca1e8107..1134c252deeb 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -57,7 +57,7 @@ export type ____LayoutStyle_Internal = $ReadOnly<{|
   borderTopWidth?: number,
   position?: 'absolute' | 'relative',
   flexDirection?: 'row' | 'row-reverse' | 'column' | 'column-reverse',
-  flexWrap?: 'wrap' | 'nowrap',
+  flexWrap?: 'wrap' | 'nowrap' | 'wrap-reverse',
   justifyContent?:
     | 'flex-start'
     | 'flex-end'
diff --git a/React/Base/RCTConvert.m b/React/Base/RCTConvert.m
index 173c90475304..7528259fda00 100644
--- a/React/Base/RCTConvert.m
+++ b/React/Base/RCTConvert.m
@@ -685,7 +685,8 @@ + (NSPropertyList)NSPropertyList:(id)json
 
 RCT_ENUM_CONVERTER(YGWrap, (@{
   @"wrap": @(YGWrapWrap),
-  @"nowrap": @(YGWrapNoWrap)
+  @"nowrap": @(YGWrapNoWrap),
+  @"wrap-reverse": @(YGWrapWrapReverse)
 }), YGWrapNoWrap, intValue)
 
 RCT_ENUM_CONVERTER(RCTPointerEvents, (@{
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
index 86c1a7832ba7..ae85bbdccd76 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
@@ -315,6 +315,10 @@ public void setFlexWrap(@Nullable String flexWrap) {
         setFlexWrap(YogaWrap.WRAP);
         break;
       }
+      case "wrap-reverse": {
+        setFlexWrap(YogaWrap.WRAP_REVERSE);
+        break;
+      }
       default: {
         throw new JSApplicationIllegalArgumentException(
             "invalid value for flexWrap: " + flexWrap);

From 2e7dfd5213a664bb6aaac19f6449985d977b605b Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Fri, 20 Apr 2018 05:06:41 -0700
Subject: [PATCH 0349/1109] Lock down Babel to 7-beta.40

Summary: This will lock down the plugins to babel version 7-beta.40

Reviewed By: davidaurelio

Differential Revision: D7707160

fbshipit-source-id: 6aec7f98348cac6ddd680c73ea4e36e0fb23e2a8
---
 babel-preset/package.json | 50 +++++++++++++++++++--------------------
 1 file changed, 25 insertions(+), 25 deletions(-)

diff --git a/babel-preset/package.json b/babel-preset/package.json
index 120c8b7a68ee..ce1c169a82f9 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -15,31 +15,31 @@
   },
   "homepage": "https://github.com/facebook/react-native/tree/master/babel-preset/README.md",
   "dependencies": {
-    "@babel/plugin-proposal-class-properties": "^7.0.0-beta",
-    "@babel/plugin-proposal-object-rest-spread": "^7.0.0-beta",
-    "@babel/plugin-transform-arrow-functions": "^7.0.0-beta",
-    "@babel/plugin-transform-block-scoping": "^7.0.0-beta",
-    "@babel/plugin-transform-classes": "^7.0.0-beta",
-    "@babel/plugin-transform-computed-properties": "^7.0.0-beta",
-    "@babel/plugin-transform-destructuring": "^7.0.0-beta",
-    "@babel/plugin-transform-exponentiation-operator": "^7.0.0-beta",
-    "@babel/plugin-transform-flow-strip-types": "^7.0.0-beta",
-    "@babel/plugin-transform-for-of": "^7.0.0-beta",
-    "@babel/plugin-transform-function-name": "^7.0.0-beta",
-    "@babel/plugin-transform-literals": "^7.0.0-beta",
-    "@babel/plugin-transform-modules-commonjs": "^7.0.0-beta",
-    "@babel/plugin-transform-object-assign": "^7.0.0-beta",
-    "@babel/plugin-transform-parameters": "^7.0.0-beta",
-    "@babel/plugin-transform-shorthand-properties": "^7.0.0-beta",
-    "@babel/plugin-transform-react-display-name": "^7.0.0-beta",
-    "@babel/plugin-transform-react-jsx": "^7.0.0-beta",
-    "@babel/plugin-transform-react-jsx-source": "^7.0.0-beta",
-    "@babel/plugin-transform-regenerator": "^7.0.0-beta",
-    "@babel/plugin-transform-spread": "^7.0.0-beta",
-    "@babel/plugin-transform-sticky-regex": "^7.0.0-beta",
-    "@babel/plugin-transform-unicode-regex": "^7.0.0-beta",
-    "@babel/plugin-transform-template-literals": "^7.0.0-beta",
-    "@babel/template": "^7.0.0-beta",
+    "@babel/plugin-proposal-class-properties": "7.0.0-beta.40",
+    "@babel/plugin-proposal-object-rest-spread": "7.0.0-beta.40",
+    "@babel/plugin-transform-arrow-functions": "7.0.0-beta.40",
+    "@babel/plugin-transform-block-scoping": "7.0.0-beta.40",
+    "@babel/plugin-transform-classes": "7.0.0-beta.40",
+    "@babel/plugin-transform-computed-properties": "7.0.0-beta.40",
+    "@babel/plugin-transform-destructuring": "7.0.0-beta.40",
+    "@babel/plugin-transform-exponentiation-operator": "7.0.0-beta.40",
+    "@babel/plugin-transform-flow-strip-types": "7.0.0-beta.40",
+    "@babel/plugin-transform-for-of": "7.0.0-beta.40",
+    "@babel/plugin-transform-function-name": "7.0.0-beta.40",
+    "@babel/plugin-transform-literals": "7.0.0-beta.40",
+    "@babel/plugin-transform-modules-commonjs": "7.0.0-beta.40",
+    "@babel/plugin-transform-object-assign": "7.0.0-beta.40",
+    "@babel/plugin-transform-parameters": "7.0.0-beta.40",
+    "@babel/plugin-transform-react-display-name": "7.0.0-beta.40",
+    "@babel/plugin-transform-react-jsx": "7.0.0-beta.40",
+    "@babel/plugin-transform-react-jsx-source": "7.0.0-beta.40",
+    "@babel/plugin-transform-regenerator": "7.0.0-beta.40",
+    "@babel/plugin-transform-shorthand-properties": "7.0.0-beta.40",
+    "@babel/plugin-transform-spread": "7.0.0-beta.40",
+    "@babel/plugin-transform-sticky-regex": "7.0.0-beta.40",
+    "@babel/plugin-transform-template-literals": "7.0.0-beta.40",
+    "@babel/plugin-transform-unicode-regex": "7.0.0-beta.40",
+    "@babel/template": "7.0.0-beta.40",
     "metro-babel7-plugin-react-transform": "0.32.0"
   }
 }

From 5fd92f90af4abb3bada372aed0ec376dc6d66891 Mon Sep 17 00:00:00 2001
From: Jean Lauliac <jeanlauliac@fb.com>
Date: Fri, 20 Apr 2018 06:31:26 -0700
Subject: [PATCH 0350/1109] cxxreact: executors: insert ID of segment reliably
 into the bundle path

Reviewed By: fromcelticpark

Differential Revision: D7623232

fbshipit-source-id: df833d18f0445d52e3098b58aac347a2e9aa0040
---
 React/React.xcodeproj/project.pbxproj |  4 ++++
 ReactCommon/cxxreact/Android.mk       |  1 +
 ReactCommon/cxxreact/BUCK             |  1 +
 ReactCommon/cxxreact/JSCExecutor.cpp  |  9 ++++++---
 ReactCommon/cxxreact/JSCUtils.cpp     |  2 ++
 ReactCommon/cxxreact/JSExecutor.cpp   | 22 ++++++++++++++++++++++
 ReactCommon/cxxreact/JSExecutor.h     |  4 ++++
 7 files changed, 40 insertions(+), 3 deletions(-)
 create mode 100644 ReactCommon/cxxreact/JSExecutor.cpp

diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index 5232e06f72a0..8c89419471d0 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -1215,6 +1215,7 @@
 		CF2731C11E7B8DE40044CA4F /* RCTDeviceInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = CF2731BF1E7B8DE40044CA4F /* RCTDeviceInfo.m */; };
 		CF2731C21E7B8DEF0044CA4F /* RCTDeviceInfo.h in Headers */ = {isa = PBXBuildFile; fileRef = CF2731BE1E7B8DE40044CA4F /* RCTDeviceInfo.h */; };
 		CF2731C31E7B8DF30044CA4F /* RCTDeviceInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = CF2731BF1E7B8DE40044CA4F /* RCTDeviceInfo.m */; };
+		E223624420875A8000108244 /* JSExecutor.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E223624320875A8000108244 /* JSExecutor.cpp */; };
 		E9B20B7B1B500126007A2DA7 /* RCTAccessibilityManager.m in Sources */ = {isa = PBXBuildFile; fileRef = E9B20B7A1B500126007A2DA7 /* RCTAccessibilityManager.m */; };
 		EBF21BBC1FC498270052F4D5 /* InspectorInterfaces.h in Headers */ = {isa = PBXBuildFile; fileRef = EBF21BBA1FC498270052F4D5 /* InspectorInterfaces.h */; };
 		EBF21BBD1FC498270052F4D5 /* InspectorInterfaces.cpp in Sources */ = {isa = PBXBuildFile; fileRef = EBF21BBB1FC498270052F4D5 /* InspectorInterfaces.cpp */; };
@@ -2305,6 +2306,7 @@
 		C6D380191F71D75B00621378 /* RAMBundleRegistry.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = RAMBundleRegistry.cpp; sourceTree = "<group>"; };
 		CF2731BE1E7B8DE40044CA4F /* RCTDeviceInfo.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTDeviceInfo.h; sourceTree = "<group>"; };
 		CF2731BF1E7B8DE40044CA4F /* RCTDeviceInfo.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTDeviceInfo.m; sourceTree = "<group>"; };
+		E223624320875A8000108244 /* JSExecutor.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSExecutor.cpp; sourceTree = "<group>"; };
 		E3BBC8EB1ADE6F47001BBD81 /* RCTTextDecorationLineType.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = RCTTextDecorationLineType.h; sourceTree = "<group>"; };
 		E9B20B791B500126007A2DA7 /* RCTAccessibilityManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTAccessibilityManager.h; sourceTree = "<group>"; };
 		E9B20B7A1B500126007A2DA7 /* RCTAccessibilityManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTAccessibilityManager.m; sourceTree = "<group>"; };
@@ -3034,6 +3036,7 @@
 		AC70D2EA1DE489FC002E6351 /* cxxreact */ = {
 			isa = PBXGroup;
 			children = (
+				E223624320875A8000108244 /* JSExecutor.cpp */,
 				3D92B0A71E03699D0018521A /* CxxModule.h */,
 				3D92B0A81E03699D0018521A /* CxxNativeModule.cpp */,
 				3D92B0A91E03699D0018521A /* CxxNativeModule.h */,
@@ -4440,6 +4443,7 @@
 			buildActionMask = 2147483647;
 			files = (
 				13134C9A1E296B2A00B9F3CB /* RCTCxxMethod.mm in Sources */,
+				E223624420875A8000108244 /* JSExecutor.cpp in Sources */,
 				59500D451F71C63F00B122B7 /* RCTUIManagerUtils.m in Sources */,
 				597633361F4E021D005BE8A4 /* RCTShadowView+Internal.m in Sources */,
 				13723B501A82FD3C00F88898 /* RCTStatusBarManager.m in Sources */,
diff --git a/ReactCommon/cxxreact/Android.mk b/ReactCommon/cxxreact/Android.mk
index 56ffdb1b3c52..1c22c761e6ef 100644
--- a/ReactCommon/cxxreact/Android.mk
+++ b/ReactCommon/cxxreact/Android.mk
@@ -17,6 +17,7 @@ LOCAL_SRC_FILES := \
   JSCSamplingProfiler.cpp \
   JSCTracing.cpp \
   JSCUtils.cpp \
+	JSExecutor.cpp \
   JSIndexedRAMBundle.cpp \
   MethodCall.cpp \
   ModuleRegistry.cpp \
diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 8bf767e82897..14aa2e3c999d 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -89,6 +89,7 @@ CXXREACT_PUBLIC_HEADERS = [
     "JSExecutor.h",
     "JSCExecutor.h",
     "JSCNativeModules.h",
+    "JSCUtils.h",
     "JSIndexedRAMBundle.h",
     "JSModulesUnbundle.h",
     "MessageQueueThread.h",
diff --git a/ReactCommon/cxxreact/JSCExecutor.cpp b/ReactCommon/cxxreact/JSCExecutor.cpp
index a7d8c72cbf70..01a68fb4d5a7 100644
--- a/ReactCommon/cxxreact/JSCExecutor.cpp
+++ b/ReactCommon/cxxreact/JSCExecutor.cpp
@@ -458,13 +458,16 @@ namespace facebook {
       m_bundleRegistry = std::move(bundleRegistry);
     }
 
-    void JSCExecutor::registerBundle(uint32_t bundleId, const std::string& bundlePath) {
+    void JSCExecutor::registerBundle(
+        uint32_t bundleId,
+        const std::string& bundlePath) {
       if (m_bundleRegistry) {
         m_bundleRegistry->registerBundle(bundleId, bundlePath);
       } else {
-        auto sourceUrl = String(m_context, bundlePath.c_str());
+        auto stPath = JSCExecutor::getSyntheticBundlePath(bundleId, bundlePath);
+        auto sourceUrlStr = String(m_context, stPath.c_str());
         auto source = adoptString(JSBigFileString::fromPath(bundlePath));
-        evaluateScript(m_context, source, sourceUrl);
+        evaluateScript(m_context, source, sourceUrlStr);
       }
     }
 
diff --git a/ReactCommon/cxxreact/JSCUtils.cpp b/ReactCommon/cxxreact/JSCUtils.cpp
index 8681faa443f4..45cc591bf76d 100644
--- a/ReactCommon/cxxreact/JSCUtils.cpp
+++ b/ReactCommon/cxxreact/JSCUtils.cpp
@@ -2,6 +2,8 @@
 
 #include "JSCUtils.h"
 
+#include "RAMBundleRegistry.h"
+
 #include <folly/Conv.h>
 
 namespace facebook {
diff --git a/ReactCommon/cxxreact/JSExecutor.cpp b/ReactCommon/cxxreact/JSExecutor.cpp
new file mode 100644
index 000000000000..9548f9664acb
--- /dev/null
+++ b/ReactCommon/cxxreact/JSExecutor.cpp
@@ -0,0 +1,22 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include "JSExecutor.h"
+
+#include "RAMBundleRegistry.h"
+
+#include <folly/Conv.h>
+
+namespace facebook {
+namespace react {
+
+std::string JSExecutor::getSyntheticBundlePath(
+    uint32_t bundleId,
+    const std::string& bundlePath) {
+  if (bundleId == RAMBundleRegistry::MAIN_BUNDLE_ID) {
+    return bundlePath;
+  }
+  return folly::to<std::string>("seg-", bundleId, ".js");
+}
+
+}
+}
diff --git a/ReactCommon/cxxreact/JSExecutor.h b/ReactCommon/cxxreact/JSExecutor.h
index 85b4bfcb0364..35338cd0876b 100644
--- a/ReactCommon/cxxreact/JSExecutor.h
+++ b/ReactCommon/cxxreact/JSExecutor.h
@@ -101,6 +101,10 @@ class JSExecutor {
 
   virtual void destroy() {}
   virtual ~JSExecutor() {}
+
+  static std::string getSyntheticBundlePath(
+      uint32_t bundleId,
+      const std::string& bundlePath);
 };
 
 } }

From 11f102373d74669d57fd048c4288beca7f47059e Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Fri, 20 Apr 2018 07:24:14 -0700
Subject: [PATCH 0351/1109] Clean server.js and runServer.js

Reviewed By: davidaurelio

Differential Revision: D7628734

fbshipit-source-id: 3788b35b0f9b5034d9152c5c3b297313fbec231a
---
 local-cli/server/runServer.js | 5 -----
 1 file changed, 5 deletions(-)

diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 1ccedf77765e..47c11535bdf4 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -43,9 +43,6 @@ const statusPageMiddleware = require('./middleware/statusPageMiddleware.js');
 const systraceProfileMiddleware = require('./middleware/systraceProfileMiddleware.js');
 const webSocketProxy = require('./util/webSocketProxy.js');
 
-/* $FlowFixMe(site=react_native_oss) */
-const TransformCaching = require('metro/src/lib/TransformCaching');
-
 const {ASSET_REGISTRY_PATH} = require('../core/Constants');
 
 import type {ConfigT} from 'metro';
@@ -191,7 +188,6 @@ function getPackagerServer(args, config, reporter) {
     getPolyfills: config.getPolyfills,
     getRunModuleStatement: config.getRunModuleStatement,
     getTransformOptions: config.getTransformOptions,
-    globalTransformCache: null,
     hasteImplModulePath: config.hasteImplModulePath,
     maxWorkers: args.maxWorkers,
     platforms: defaultPlatforms.concat(args.platforms),
@@ -205,7 +201,6 @@ function getPackagerServer(args, config, reporter) {
     resolveRequest: config.resolveRequest,
     sourceExts: args.sourceExts.concat(defaultSourceExts),
     transformModulePath: transformModulePath,
-    transformCache: TransformCaching.useTempDir(),
     verbose: args.verbose,
     watch: !args.nonPersistent,
     workerPath: config.getWorkerPath(),

From fc694fef6663f8fefc529caa27ac8467c77773aa Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Fri, 20 Apr 2018 07:24:20 -0700
Subject: [PATCH 0352/1109] Clean buildBundle.js, index.js and Flow types

Reviewed By: davidaurelio

Differential Revision: D7628725

fbshipit-source-id: 3873e5c7a0c9b988335dcf9b8a11fcf0598a9f50
---
 local-cli/bundle/buildBundle.js | 1 -
 1 file changed, 1 deletion(-)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index 5b1f5be06534..99c45ddc08db 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -90,7 +90,6 @@ async function buildBundle(
     getPolyfills: config.getPolyfills,
     getRunModuleStatement: config.getRunModuleStatement,
     getTransformOptions: config.getTransformOptions,
-    globalTransformCache: null,
     hasteImplModulePath: config.hasteImplModulePath,
     maxWorkers: args.maxWorkers,
     platforms: defaultPlatforms.concat(platforms),

From 9bbe736f23657e9acc263e480d59ac7def260e9d Mon Sep 17 00:00:00 2001
From: Peter Ammon <pca@fb.com>
Date: Fri, 20 Apr 2018 08:56:02 -0700
Subject: [PATCH 0353/1109] Teach JS stack-parsing regex about alternative
 formats

Reviewed By: adamjernst

Differential Revision: D7706535

fbshipit-source-id: 83cc2defbcad3faa6bdbf4a5b2072b9c023e1c04
---
 React/Base/RCTJSStackFrame.m | 29 ++++++++++++++++++++++++++++-
 1 file changed, 28 insertions(+), 1 deletion(-)

diff --git a/React/Base/RCTJSStackFrame.m b/React/Base/RCTJSStackFrame.m
index 60976f673ba5..a60d78b1093b 100644
--- a/React/Base/RCTJSStackFrame.m
+++ b/React/Base/RCTJSStackFrame.m
@@ -10,13 +10,40 @@
 #import "RCTLog.h"
 #import "RCTUtils.h"
 
+/**
+* The RegEx used to parse Error.stack.
+*
+* JavaScriptCore has the following format:
+*
+*   Exception: Error: argh
+*     func1@/path/to/file.js:2:18
+*     func2@/path/to/file.js:6:8
+*     eval@[native code]
+*     global code@/path/to/file.js:13:5
+*
+* Another supported format:
+*
+*  Error: argh
+*   at func1 (/path/to/file.js:2:18)
+*   at func2 (/path/to/file.js:6:8)
+*   at eval (native)
+*   at global (/path/to/file.js:13:5)
+*/
 static NSRegularExpression *RCTJSStackFrameRegex()
 {
   static dispatch_once_t onceToken;
   static NSRegularExpression *_regex;
   dispatch_once(&onceToken, ^{
+    NSString *pattern =
+      @"\\s*(?:at)?\\s*" // Skip leading "at" and whitespace, noncapturing
+      @"(.+?)"           // Capture the function name (group 1)
+      @"\\s*[@(]"        // Skip whitespace, then @ or (
+      @"(.*):"           // Capture the file name (group 2), then colon
+      @"(\\d+):(\\d+)"   // Line and column number (groups 3 and 4)
+      @"\\)?$"           // Optional closing paren and EOL
+    ;
     NSError *regexError;
-    _regex = [NSRegularExpression regularExpressionWithPattern:@"^(?:([^@]+)@)?(.*):(\\d+):(\\d+)$" options:0 error:&regexError];
+    _regex = [NSRegularExpression regularExpressionWithPattern:pattern options:0 error:&regexError];
     if (regexError) {
       RCTLogError(@"Failed to build regex: %@", [regexError localizedDescription]);
     }

From cf1569c556d28779edbba92edb658a881a68516c Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 20 Apr 2018 09:17:39 -0700
Subject: [PATCH 0354/1109] Export the hmr plugin directly

Summary: This will allow to configure the HMR plugin directly from `.babelrc` again, instead of having to create a bridge file: https://github.com/rafeca/metro-sample-app/blob/master/metro-babel7-plugin-react-transform.js#L3

Reviewed By: davidaurelio

Differential Revision: D7707314

fbshipit-source-id: 4c5612e1e5d27874807f2dce50d99ec0f6354bbc
---
 babel-preset/configs/hmr.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/babel-preset/configs/hmr.js b/babel-preset/configs/hmr.js
index cdf5a022c202..e2b4a0f3dec0 100644
--- a/babel-preset/configs/hmr.js
+++ b/babel-preset/configs/hmr.js
@@ -24,7 +24,7 @@ module.exports = function(options, filename) {
   return {
     plugins: [
       [
-        require('metro-babel7-plugin-react-transform').default,
+        require('metro-babel7-plugin-react-transform'),
         {
           transforms: [{
             transform: transform,

From e512a4ae300ff1057f98e2e6375a432efa8c0241 Mon Sep 17 00:00:00 2001
From: Naris Siamwalla <naris@fb.com>
Date: Fri, 20 Apr 2018 09:40:06 -0700
Subject: [PATCH 0355/1109] Fix dtor declaration for clang-6

Reviewed By: smeenai

Differential Revision: D7690428

fbshipit-source-id: 4b02a6f6cbccda3446f0a19b1b35c266a33560bd
---
 ReactCommon/fabric/uimanager/Scheduler.h         | 2 +-
 ReactCommon/fabric/uimanager/SchedulerDelegate.h | 3 +++
 2 files changed, 4 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index 4f4ff203b54a..b48d6e848af4 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -29,7 +29,7 @@ class Scheduler:
 
 public:
   Scheduler();
-  ~Scheduler();
+  virtual ~Scheduler();
 
 #pragma mark - Root Nodes Managerment
 
diff --git a/ReactCommon/fabric/uimanager/SchedulerDelegate.h b/ReactCommon/fabric/uimanager/SchedulerDelegate.h
index 2fe3da02ace1..3f2d9bf5fd24 100644
--- a/ReactCommon/fabric/uimanager/SchedulerDelegate.h
+++ b/ReactCommon/fabric/uimanager/SchedulerDelegate.h
@@ -16,6 +16,9 @@ namespace react {
  */
 class SchedulerDelegate {
 public:
+
+  virtual ~SchedulerDelegate() = default;
+
   /*
    * Called right after Scheduler computed (and laid out) a new updated version
    * of the tree and calculated a set of mutation instructions which are

From bc8e42a5e6a2c0161d5820e62047f5103b94a33f Mon Sep 17 00:00:00 2001
From: Brian Vaughn <brian.david.vaughn@gmail.com>
Date: Fri, 20 Apr 2018 10:18:05 -0700
Subject: [PATCH 0356/1109] Removed fb-specific RN bundle. This should not have
 been synced.

---
 Libraries/Renderer/fb/ReactFabric-dev.js      | 13862 ---------------
 Libraries/Renderer/fb/ReactFabric-prod.js     |  5875 -------
 Libraries/Renderer/fb/ReactFeatureFlags.js    |    18 -
 .../Renderer/fb/ReactNativeRenderer-dev.js    | 14437 ----------------
 .../Renderer/fb/ReactNativeRenderer-prod.js   |  6395 -------
 5 files changed, 40587 deletions(-)
 delete mode 100644 Libraries/Renderer/fb/ReactFabric-dev.js
 delete mode 100644 Libraries/Renderer/fb/ReactFabric-prod.js
 delete mode 100644 Libraries/Renderer/fb/ReactFeatureFlags.js
 delete mode 100644 Libraries/Renderer/fb/ReactNativeRenderer-dev.js
 delete mode 100644 Libraries/Renderer/fb/ReactNativeRenderer-prod.js

diff --git a/Libraries/Renderer/fb/ReactFabric-dev.js b/Libraries/Renderer/fb/ReactFabric-dev.js
deleted file mode 100644
index 0424315c8ed6..000000000000
--- a/Libraries/Renderer/fb/ReactFabric-dev.js
+++ /dev/null
@@ -1,13862 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @noflow
- * @preventMunge
- */
-
-'use strict';
-
-if (__DEV__) {
-  (function() {
-"use strict";
-
-require("InitializeCore");
-var invariant = require("fbjs/lib/invariant");
-var warning = require("fbjs/lib/warning");
-var emptyFunction = require("fbjs/lib/emptyFunction");
-var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
-var UIManager = require("UIManager");
-var TextInputState = require("TextInputState");
-var deepDiffer = require("deepDiffer");
-var flattenStyle = require("flattenStyle");
-var React = require("react");
-var emptyObject = require("fbjs/lib/emptyObject");
-var shallowEqual = require("fbjs/lib/shallowEqual");
-var checkPropTypes = require("prop-types/checkPropTypes");
-var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
-var FabricUIManager = require("FabricUIManager");
-
-var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
-  this._hasCaughtError = false;
-  this._caughtError = null;
-  var funcArgs = Array.prototype.slice.call(arguments, 3);
-  try {
-    func.apply(context, funcArgs);
-  } catch (error) {
-    this._caughtError = error;
-    this._hasCaughtError = true;
-  }
-};
-
-{
-  // In DEV mode, we swap out invokeGuardedCallback for a special version
-  // that plays more nicely with the browser's DevTools. The idea is to preserve
-  // "Pause on exceptions" behavior. Because React wraps all user-provided
-  // functions in invokeGuardedCallback, and the production version of
-  // invokeGuardedCallback uses a try-catch, all user exceptions are treated
-  // like caught exceptions, and the DevTools won't pause unless the developer
-  // takes the extra step of enabling pause on caught exceptions. This is
-  // untintuitive, though, because even though React has caught the error, from
-  // the developer's perspective, the error is uncaught.
-  //
-  // To preserve the expected "Pause on exceptions" behavior, we don't use a
-  // try-catch in DEV. Instead, we synchronously dispatch a fake event to a fake
-  // DOM node, and call the user-provided callback from inside an event handler
-  // for that fake event. If the callback throws, the error is "captured" using
-  // a global event handler. But because the error happens in a different
-  // event loop context, it does not interrupt the normal program flow.
-  // Effectively, this gives us try-catch behavior without actually using
-  // try-catch. Neat!
-
-  // Check that the browser supports the APIs we need to implement our special
-  // DEV version of invokeGuardedCallback
-  if (
-    typeof window !== "undefined" &&
-    typeof window.dispatchEvent === "function" &&
-    typeof document !== "undefined" &&
-    typeof document.createEvent === "function"
-  ) {
-    var fakeNode = document.createElement("react");
-
-    var invokeGuardedCallbackDev = function(
-      name,
-      func,
-      context,
-      a,
-      b,
-      c,
-      d,
-      e,
-      f
-    ) {
-      // If document doesn't exist we know for sure we will crash in this method
-      // when we call document.createEvent(). However this can cause confusing
-      // errors: https://github.com/facebookincubator/create-react-app/issues/3482
-      // So we preemptively throw with a better message instead.
-      invariant(
-        typeof document !== "undefined",
-        "The `document` global was defined when React was initialized, but is not " +
-          "defined anymore. This can happen in a test environment if a component " +
-          "schedules an update from an asynchronous callback, but the test has already " +
-          "finished running. To solve this, you can either unmount the component at " +
-          "the end of your test (and ensure that any asynchronous operations get " +
-          "canceled in `componentWillUnmount`), or you can change the test itself " +
-          "to be asynchronous."
-      );
-      var evt = document.createEvent("Event");
-
-      // Keeps track of whether the user-provided callback threw an error. We
-      // set this to true at the beginning, then set it to false right after
-      // calling the function. If the function errors, `didError` will never be
-      // set to false. This strategy works even if the browser is flaky and
-      // fails to call our global error handler, because it doesn't rely on
-      // the error event at all.
-      var didError = true;
-
-      // Create an event handler for our fake event. We will synchronously
-      // dispatch our fake event using `dispatchEvent`. Inside the handler, we
-      // call the user-provided callback.
-      var funcArgs = Array.prototype.slice.call(arguments, 3);
-      function callCallback() {
-        // We immediately remove the callback from event listeners so that
-        // nested `invokeGuardedCallback` calls do not clash. Otherwise, a
-        // nested call would trigger the fake event handlers of any call higher
-        // in the stack.
-        fakeNode.removeEventListener(evtType, callCallback, false);
-        func.apply(context, funcArgs);
-        didError = false;
-      }
-
-      // Create a global error event handler. We use this to capture the value
-      // that was thrown. It's possible that this error handler will fire more
-      // than once; for example, if non-React code also calls `dispatchEvent`
-      // and a handler for that event throws. We should be resilient to most of
-      // those cases. Even if our error event handler fires more than once, the
-      // last error event is always used. If the callback actually does error,
-      // we know that the last error event is the correct one, because it's not
-      // possible for anything else to have happened in between our callback
-      // erroring and the code that follows the `dispatchEvent` call below. If
-      // the callback doesn't error, but the error event was fired, we know to
-      // ignore it because `didError` will be false, as described above.
-      var error = void 0;
-      // Use this to track whether the error event is ever called.
-      var didSetError = false;
-      var isCrossOriginError = false;
-
-      function onError(event) {
-        error = event.error;
-        didSetError = true;
-        if (error === null && event.colno === 0 && event.lineno === 0) {
-          isCrossOriginError = true;
-        }
-      }
-
-      // Create a fake event type.
-      var evtType = "react-" + (name ? name : "invokeguardedcallback");
-
-      // Attach our event handlers
-      window.addEventListener("error", onError);
-      fakeNode.addEventListener(evtType, callCallback, false);
-
-      // Synchronously dispatch our fake event. If the user-provided function
-      // errors, it will trigger our global error handler.
-      evt.initEvent(evtType, false, false);
-      fakeNode.dispatchEvent(evt);
-
-      if (didError) {
-        if (!didSetError) {
-          // The callback errored, but the error event never fired.
-          error = new Error(
-            "An error was thrown inside one of your components, but React " +
-              "doesn't know what it was. This is likely due to browser " +
-              'flakiness. React does its best to preserve the "Pause on ' +
-              'exceptions" behavior of the DevTools, which requires some ' +
-              "DEV-mode only tricks. It's possible that these don't work in " +
-              "your browser. Try triggering the error in production mode, " +
-              "or switching to a modern browser. If you suspect that this is " +
-              "actually an issue with React, please file an issue."
-          );
-        } else if (isCrossOriginError) {
-          error = new Error(
-            "A cross-origin error was thrown. React doesn't have access to " +
-              "the actual error object in development. " +
-              "See https://fb.me/react-crossorigin-error for more information."
-          );
-        }
-        this._hasCaughtError = true;
-        this._caughtError = error;
-      } else {
-        this._hasCaughtError = false;
-        this._caughtError = null;
-      }
-
-      // Remove our event listeners
-      window.removeEventListener("error", onError);
-    };
-
-    invokeGuardedCallback = invokeGuardedCallbackDev;
-  }
-}
-
-var invokeGuardedCallback$1 = invokeGuardedCallback;
-
-var ReactErrorUtils = {
-  // Used by Fiber to simulate a try-catch.
-  _caughtError: null,
-  _hasCaughtError: false,
-
-  // Used by event system to capture/rethrow the first error.
-  _rethrowError: null,
-  _hasRethrowError: false,
-
-  /**
-   * Call a function while guarding against errors that happens within it.
-   * Returns an error if it throws, otherwise null.
-   *
-   * In production, this is implemented using a try-catch. The reason we don't
-   * use a try-catch directly is so that we can swap out a different
-   * implementation in DEV mode.
-   *
-   * @param {String} name of the guard to use for logging or debugging
-   * @param {Function} func The function to invoke
-   * @param {*} context The context to use when calling the function
-   * @param {...*} args Arguments for function
-   */
-  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
-    invokeGuardedCallback$1.apply(ReactErrorUtils, arguments);
-  },
-
-  /**
-   * Same as invokeGuardedCallback, but instead of returning an error, it stores
-   * it in a global so it can be rethrown by `rethrowCaughtError` later.
-   * TODO: See if _caughtError and _rethrowError can be unified.
-   *
-   * @param {String} name of the guard to use for logging or debugging
-   * @param {Function} func The function to invoke
-   * @param {*} context The context to use when calling the function
-   * @param {...*} args Arguments for function
-   */
-  invokeGuardedCallbackAndCatchFirstError: function(
-    name,
-    func,
-    context,
-    a,
-    b,
-    c,
-    d,
-    e,
-    f
-  ) {
-    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
-    if (ReactErrorUtils.hasCaughtError()) {
-      var error = ReactErrorUtils.clearCaughtError();
-      if (!ReactErrorUtils._hasRethrowError) {
-        ReactErrorUtils._hasRethrowError = true;
-        ReactErrorUtils._rethrowError = error;
-      }
-    }
-  },
-
-  /**
-   * During execution of guarded functions we will capture the first error which
-   * we will rethrow to be handled by the top level error handler.
-   */
-  rethrowCaughtError: function() {
-    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
-  },
-
-  hasCaughtError: function() {
-    return ReactErrorUtils._hasCaughtError;
-  },
-
-  clearCaughtError: function() {
-    if (ReactErrorUtils._hasCaughtError) {
-      var error = ReactErrorUtils._caughtError;
-      ReactErrorUtils._caughtError = null;
-      ReactErrorUtils._hasCaughtError = false;
-      return error;
-    } else {
-      invariant(
-        false,
-        "clearCaughtError was called but no error was captured. This error " +
-          "is likely caused by a bug in React. Please file an issue."
-      );
-    }
-  }
-};
-
-var rethrowCaughtError = function() {
-  if (ReactErrorUtils._hasRethrowError) {
-    var error = ReactErrorUtils._rethrowError;
-    ReactErrorUtils._rethrowError = null;
-    ReactErrorUtils._hasRethrowError = false;
-    throw error;
-  }
-};
-
-/**
- * Injectable ordering of event plugins.
- */
-var eventPluginOrder = null;
-
-/**
- * Injectable mapping from names to event plugin modules.
- */
-var namesToPlugins = {};
-
-/**
- * Recomputes the plugin list using the injected plugins and plugin ordering.
- *
- * @private
- */
-function recomputePluginOrdering() {
-  if (!eventPluginOrder) {
-    // Wait until an `eventPluginOrder` is injected.
-    return;
-  }
-  for (var pluginName in namesToPlugins) {
-    var pluginModule = namesToPlugins[pluginName];
-    var pluginIndex = eventPluginOrder.indexOf(pluginName);
-    invariant(
-      pluginIndex > -1,
-      "EventPluginRegistry: Cannot inject event plugins that do not exist in " +
-        "the plugin ordering, `%s`.",
-      pluginName
-    );
-    if (plugins[pluginIndex]) {
-      continue;
-    }
-    invariant(
-      pluginModule.extractEvents,
-      "EventPluginRegistry: Event plugins must implement an `extractEvents` " +
-        "method, but `%s` does not.",
-      pluginName
-    );
-    plugins[pluginIndex] = pluginModule;
-    var publishedEvents = pluginModule.eventTypes;
-    for (var eventName in publishedEvents) {
-      invariant(
-        publishEventForPlugin(
-          publishedEvents[eventName],
-          pluginModule,
-          eventName
-        ),
-        "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
-        eventName,
-        pluginName
-      );
-    }
-  }
-}
-
-/**
- * Publishes an event so that it can be dispatched by the supplied plugin.
- *
- * @param {object} dispatchConfig Dispatch configuration for the event.
- * @param {object} PluginModule Plugin publishing the event.
- * @return {boolean} True if the event was successfully published.
- * @private
- */
-function publishEventForPlugin(dispatchConfig, pluginModule, eventName) {
-  invariant(
-    !eventNameDispatchConfigs.hasOwnProperty(eventName),
-    "EventPluginHub: More than one plugin attempted to publish the same " +
-      "event name, `%s`.",
-    eventName
-  );
-  eventNameDispatchConfigs[eventName] = dispatchConfig;
-
-  var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
-  if (phasedRegistrationNames) {
-    for (var phaseName in phasedRegistrationNames) {
-      if (phasedRegistrationNames.hasOwnProperty(phaseName)) {
-        var phasedRegistrationName = phasedRegistrationNames[phaseName];
-        publishRegistrationName(
-          phasedRegistrationName,
-          pluginModule,
-          eventName
-        );
-      }
-    }
-    return true;
-  } else if (dispatchConfig.registrationName) {
-    publishRegistrationName(
-      dispatchConfig.registrationName,
-      pluginModule,
-      eventName
-    );
-    return true;
-  }
-  return false;
-}
-
-/**
- * Publishes a registration name that is used to identify dispatched events.
- *
- * @param {string} registrationName Registration name to add.
- * @param {object} PluginModule Plugin publishing the event.
- * @private
- */
-function publishRegistrationName(registrationName, pluginModule, eventName) {
-  invariant(
-    !registrationNameModules[registrationName],
-    "EventPluginHub: More than one plugin attempted to publish the same " +
-      "registration name, `%s`.",
-    registrationName
-  );
-  registrationNameModules[registrationName] = pluginModule;
-  registrationNameDependencies[registrationName] =
-    pluginModule.eventTypes[eventName].dependencies;
-
-  {
-    var lowerCasedName = registrationName.toLowerCase();
-  }
-}
-
-/**
- * Registers plugins so that they can extract and dispatch events.
- *
- * @see {EventPluginHub}
- */
-
-/**
- * Ordered list of injected plugins.
- */
-var plugins = [];
-
-/**
- * Mapping from event name to dispatch config
- */
-var eventNameDispatchConfigs = {};
-
-/**
- * Mapping from registration name to plugin module
- */
-var registrationNameModules = {};
-
-/**
- * Mapping from registration name to event name
- */
-var registrationNameDependencies = {};
-
-/**
- * Mapping from lowercase registration names to the properly cased version,
- * used to warn in the case of missing event handlers. Available
- * only in true.
- * @type {Object}
- */
-
-// Trust the developer to only use possibleRegistrationNames in true
-
-/**
- * Injects an ordering of plugins (by plugin name). This allows the ordering
- * to be decoupled from injection of the actual plugins so that ordering is
- * always deterministic regardless of packaging, on-the-fly injection, etc.
- *
- * @param {array} InjectedEventPluginOrder
- * @internal
- * @see {EventPluginHub.injection.injectEventPluginOrder}
- */
-function injectEventPluginOrder(injectedEventPluginOrder) {
-  invariant(
-    !eventPluginOrder,
-    "EventPluginRegistry: Cannot inject event plugin ordering more than " +
-      "once. You are likely trying to load more than one copy of React."
-  );
-  // Clone the ordering so it cannot be dynamically mutated.
-  eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
-  recomputePluginOrdering();
-}
-
-/**
- * Injects plugins to be used by `EventPluginHub`. The plugin names must be
- * in the ordering injected by `injectEventPluginOrder`.
- *
- * Plugins can be injected as part of page initialization or on-the-fly.
- *
- * @param {object} injectedNamesToPlugins Map from names to plugin modules.
- * @internal
- * @see {EventPluginHub.injection.injectEventPluginsByName}
- */
-function injectEventPluginsByName(injectedNamesToPlugins) {
-  var isOrderingDirty = false;
-  for (var pluginName in injectedNamesToPlugins) {
-    if (!injectedNamesToPlugins.hasOwnProperty(pluginName)) {
-      continue;
-    }
-    var pluginModule = injectedNamesToPlugins[pluginName];
-    if (
-      !namesToPlugins.hasOwnProperty(pluginName) ||
-      namesToPlugins[pluginName] !== pluginModule
-    ) {
-      invariant(
-        !namesToPlugins[pluginName],
-        "EventPluginRegistry: Cannot inject two different event plugins " +
-          "using the same name, `%s`.",
-        pluginName
-      );
-      namesToPlugins[pluginName] = pluginModule;
-      isOrderingDirty = true;
-    }
-  }
-  if (isOrderingDirty) {
-    recomputePluginOrdering();
-  }
-}
-
-var getFiberCurrentPropsFromNode = null;
-var getInstanceFromNode = null;
-var getNodeFromInstance = null;
-
-var injection$1 = {
-  injectComponentTree: function(Injected) {
-    getFiberCurrentPropsFromNode = Injected.getFiberCurrentPropsFromNode;
-    getInstanceFromNode = Injected.getInstanceFromNode;
-    getNodeFromInstance = Injected.getNodeFromInstance;
-
-    {
-      !(getNodeFromInstance && getInstanceFromNode)
-        ? warning(
-            false,
-            "EventPluginUtils.injection.injectComponentTree(...): Injected " +
-              "module is missing getNodeFromInstance or getInstanceFromNode."
-          )
-        : void 0;
-    }
-  }
-};
-
-function isEndish(topLevelType) {
-  return (
-    topLevelType === "topMouseUp" ||
-    topLevelType === "topTouchEnd" ||
-    topLevelType === "topTouchCancel"
-  );
-}
-
-function isMoveish(topLevelType) {
-  return topLevelType === "topMouseMove" || topLevelType === "topTouchMove";
-}
-function isStartish(topLevelType) {
-  return topLevelType === "topMouseDown" || topLevelType === "topTouchStart";
-}
-
-var validateEventDispatches = void 0;
-{
-  validateEventDispatches = function(event) {
-    var dispatchListeners = event._dispatchListeners;
-    var dispatchInstances = event._dispatchInstances;
-
-    var listenersIsArr = Array.isArray(dispatchListeners);
-    var listenersLen = listenersIsArr
-      ? dispatchListeners.length
-      : dispatchListeners ? 1 : 0;
-
-    var instancesIsArr = Array.isArray(dispatchInstances);
-    var instancesLen = instancesIsArr
-      ? dispatchInstances.length
-      : dispatchInstances ? 1 : 0;
-
-    !(instancesIsArr === listenersIsArr && instancesLen === listenersLen)
-      ? warning(false, "EventPluginUtils: Invalid `event`.")
-      : void 0;
-  };
-}
-
-/**
- * Standard/simple iteration through an event's collected dispatches.
- */
-
-/**
- * Standard/simple iteration through an event's collected dispatches, but stops
- * at the first dispatch execution returning true, and returns that id.
- *
- * @return {?string} id of the first dispatch execution who's listener returns
- * true, or null if no listener returned true.
- */
-function executeDispatchesInOrderStopAtTrueImpl(event) {
-  var dispatchListeners = event._dispatchListeners;
-  var dispatchInstances = event._dispatchInstances;
-  {
-    validateEventDispatches(event);
-  }
-  if (Array.isArray(dispatchListeners)) {
-    for (var i = 0; i < dispatchListeners.length; i++) {
-      if (event.isPropagationStopped()) {
-        break;
-      }
-      // Listeners and Instances are two parallel arrays that are always in sync.
-      if (dispatchListeners[i](event, dispatchInstances[i])) {
-        return dispatchInstances[i];
-      }
-    }
-  } else if (dispatchListeners) {
-    if (dispatchListeners(event, dispatchInstances)) {
-      return dispatchInstances;
-    }
-  }
-  return null;
-}
-
-/**
- * @see executeDispatchesInOrderStopAtTrueImpl
- */
-function executeDispatchesInOrderStopAtTrue(event) {
-  var ret = executeDispatchesInOrderStopAtTrueImpl(event);
-  event._dispatchInstances = null;
-  event._dispatchListeners = null;
-  return ret;
-}
-
-/**
- * Execution of a "direct" dispatch - there must be at most one dispatch
- * accumulated on the event or it is considered an error. It doesn't really make
- * sense for an event with multiple dispatches (bubbled) to keep track of the
- * return values at each dispatch execution, but it does tend to make sense when
- * dealing with "direct" dispatches.
- *
- * @return {*} The return value of executing the single dispatch.
- */
-function executeDirectDispatch(event) {
-  {
-    validateEventDispatches(event);
-  }
-  var dispatchListener = event._dispatchListeners;
-  var dispatchInstance = event._dispatchInstances;
-  invariant(
-    !Array.isArray(dispatchListener),
-    "executeDirectDispatch(...): Invalid `event`."
-  );
-  event.currentTarget = dispatchListener
-    ? getNodeFromInstance(dispatchInstance)
-    : null;
-  var res = dispatchListener ? dispatchListener(event) : null;
-  event.currentTarget = null;
-  event._dispatchListeners = null;
-  event._dispatchInstances = null;
-  return res;
-}
-
-/**
- * @param {SyntheticEvent} event
- * @return {boolean} True iff number of dispatches accumulated is greater than 0.
- */
-function hasDispatches(event) {
-  return !!event._dispatchListeners;
-}
-
-/**
- * Accumulates items that must not be null or undefined into the first one. This
- * is used to conserve memory by avoiding array allocations, and thus sacrifices
- * API cleanness. Since `current` can be null before being passed in and not
- * null after this function, make sure to assign it back to `current`:
- *
- * `a = accumulateInto(a, b);`
- *
- * This API should be sparingly used. Try `accumulate` for something cleaner.
- *
- * @return {*|array<*>} An accumulation of items.
- */
-
-function accumulateInto(current, next) {
-  invariant(
-    next != null,
-    "accumulateInto(...): Accumulated items must not be null or undefined."
-  );
-
-  if (current == null) {
-    return next;
-  }
-
-  // Both are not empty. Warning: Never call x.concat(y) when you are not
-  // certain that x is an Array (x could be a string with concat method).
-  if (Array.isArray(current)) {
-    if (Array.isArray(next)) {
-      current.push.apply(current, next);
-      return current;
-    }
-    current.push(next);
-    return current;
-  }
-
-  if (Array.isArray(next)) {
-    // A bit too dangerous to mutate `next`.
-    return [current].concat(next);
-  }
-
-  return [current, next];
-}
-
-/**
- * @param {array} arr an "accumulation" of items which is either an Array or
- * a single item. Useful when paired with the `accumulate` module. This is a
- * simple utility that allows us to reason about a collection of items, but
- * handling the case when there is exactly one item (and we do not need to
- * allocate an array).
- * @param {function} cb Callback invoked with each element or a collection.
- * @param {?} [scope] Scope used as `this` in a callback.
- */
-function forEachAccumulated(arr, cb, scope) {
-  if (Array.isArray(arr)) {
-    arr.forEach(cb, scope);
-  } else if (arr) {
-    cb.call(scope, arr);
-  }
-}
-
-function isInteractive(tag) {
-  return (
-    tag === "button" ||
-    tag === "input" ||
-    tag === "select" ||
-    tag === "textarea"
-  );
-}
-
-function shouldPreventMouseEvent(name, type, props) {
-  switch (name) {
-    case "onClick":
-    case "onClickCapture":
-    case "onDoubleClick":
-    case "onDoubleClickCapture":
-    case "onMouseDown":
-    case "onMouseDownCapture":
-    case "onMouseMove":
-    case "onMouseMoveCapture":
-    case "onMouseUp":
-    case "onMouseUpCapture":
-      return !!(props.disabled && isInteractive(type));
-    default:
-      return false;
-  }
-}
-
-/**
- * This is a unified interface for event plugins to be installed and configured.
- *
- * Event plugins can implement the following properties:
- *
- *   `extractEvents` {function(string, DOMEventTarget, string, object): *}
- *     Required. When a top-level event is fired, this method is expected to
- *     extract synthetic events that will in turn be queued and dispatched.
- *
- *   `eventTypes` {object}
- *     Optional, plugins that fire events must publish a mapping of registration
- *     names that are used to register listeners. Values of this mapping must
- *     be objects that contain `registrationName` or `phasedRegistrationNames`.
- *
- *   `executeDispatch` {function(object, function, string)}
- *     Optional, allows plugins to override how an event gets dispatched. By
- *     default, the listener is simply invoked.
- *
- * Each plugin that is injected into `EventsPluginHub` is immediately operable.
- *
- * @public
- */
-
-/**
- * Methods for injecting dependencies.
- */
-var injection = {
-  /**
-   * @param {array} InjectedEventPluginOrder
-   * @public
-   */
-  injectEventPluginOrder: injectEventPluginOrder,
-
-  /**
-   * @param {object} injectedNamesToPlugins Map from names to plugin modules.
-   */
-  injectEventPluginsByName: injectEventPluginsByName
-};
-
-/**
- * @param {object} inst The instance, which is the source of events.
- * @param {string} registrationName Name of listener (e.g. `onClick`).
- * @return {?function} The stored callback.
- */
-function getListener(inst, registrationName) {
-  var listener = void 0;
-
-  // TODO: shouldPreventMouseEvent is DOM-specific and definitely should not
-  // live here; needs to be moved to a better place soon
-  var stateNode = inst.stateNode;
-  if (!stateNode) {
-    // Work in progress (ex: onload events in incremental mode).
-    return null;
-  }
-  var props = getFiberCurrentPropsFromNode(stateNode);
-  if (!props) {
-    // Work in progress.
-    return null;
-  }
-  listener = props[registrationName];
-  if (shouldPreventMouseEvent(registrationName, inst.type, props)) {
-    return null;
-  }
-  invariant(
-    !listener || typeof listener === "function",
-    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
-    registrationName,
-    typeof listener
-  );
-  return listener;
-}
-
-var IndeterminateComponent = 0; // Before we know whether it is functional or class
-var FunctionalComponent = 1;
-var ClassComponent = 2;
-var HostRoot = 3; // Root of a host tree. Could be nested inside another node.
-var HostPortal = 4; // A subtree. Could be an entry point to a different renderer.
-var HostComponent = 5;
-var HostText = 6;
-var CallComponent = 7;
-var CallHandlerPhase = 8;
-var ReturnComponent = 9;
-var Fragment = 10;
-var Mode = 11;
-var ContextConsumer = 12;
-var ContextProvider = 13;
-var ForwardRef = 14;
-
-function getParent(inst) {
-  do {
-    inst = inst["return"];
-    // TODO: If this is a HostRoot we might want to bail out.
-    // That is depending on if we want nested subtrees (layers) to bubble
-    // events to their parent. We could also go through parentNode on the
-    // host node but that wouldn't work for React Native and doesn't let us
-    // do the portal feature.
-  } while (inst && inst.tag !== HostComponent);
-  if (inst) {
-    return inst;
-  }
-  return null;
-}
-
-/**
- * Return the lowest common ancestor of A and B, or null if they are in
- * different trees.
- */
-function getLowestCommonAncestor(instA, instB) {
-  var depthA = 0;
-  for (var tempA = instA; tempA; tempA = getParent(tempA)) {
-    depthA++;
-  }
-  var depthB = 0;
-  for (var tempB = instB; tempB; tempB = getParent(tempB)) {
-    depthB++;
-  }
-
-  // If A is deeper, crawl up.
-  while (depthA - depthB > 0) {
-    instA = getParent(instA);
-    depthA--;
-  }
-
-  // If B is deeper, crawl up.
-  while (depthB - depthA > 0) {
-    instB = getParent(instB);
-    depthB--;
-  }
-
-  // Walk in lockstep until we find a match.
-  var depth = depthA;
-  while (depth--) {
-    if (instA === instB || instA === instB.alternate) {
-      return instA;
-    }
-    instA = getParent(instA);
-    instB = getParent(instB);
-  }
-  return null;
-}
-
-/**
- * Return if A is an ancestor of B.
- */
-function isAncestor(instA, instB) {
-  while (instB) {
-    if (instA === instB || instA === instB.alternate) {
-      return true;
-    }
-    instB = getParent(instB);
-  }
-  return false;
-}
-
-/**
- * Return the parent instance of the passed-in instance.
- */
-function getParentInstance(inst) {
-  return getParent(inst);
-}
-
-/**
- * Simulates the traversal of a two-phase, capture/bubble event dispatch.
- */
-function traverseTwoPhase(inst, fn, arg) {
-  var path = [];
-  while (inst) {
-    path.push(inst);
-    inst = getParent(inst);
-  }
-  var i = void 0;
-  for (i = path.length; i-- > 0; ) {
-    fn(path[i], "captured", arg);
-  }
-  for (i = 0; i < path.length; i++) {
-    fn(path[i], "bubbled", arg);
-  }
-}
-
-/**
- * Traverses the ID hierarchy and invokes the supplied `cb` on any IDs that
- * should would receive a `mouseEnter` or `mouseLeave` event.
- *
- * Does not invoke the callback on the nearest common ancestor because nothing
- * "entered" or "left" that element.
- */
-
-/**
- * Some event types have a notion of different registration names for different
- * "phases" of propagation. This finds listeners by a given phase.
- */
-function listenerAtPhase(inst, event, propagationPhase) {
-  var registrationName =
-    event.dispatchConfig.phasedRegistrationNames[propagationPhase];
-  return getListener(inst, registrationName);
-}
-
-/**
- * A small set of propagation patterns, each of which will accept a small amount
- * of information, and generate a set of "dispatch ready event objects" - which
- * are sets of events that have already been annotated with a set of dispatched
- * listener functions/ids. The API is designed this way to discourage these
- * propagation strategies from actually executing the dispatches, since we
- * always want to collect the entire set of dispatches before executing even a
- * single one.
- */
-
-/**
- * Tags a `SyntheticEvent` with dispatched listeners. Creating this function
- * here, allows us to not have to bind or create functions for each event.
- * Mutating the event's members allows us to not have to create a wrapping
- * "dispatch" object that pairs the event with the listener.
- */
-function accumulateDirectionalDispatches(inst, phase, event) {
-  {
-    !inst ? warning(false, "Dispatching inst must not be null") : void 0;
-  }
-  var listener = listenerAtPhase(inst, event, phase);
-  if (listener) {
-    event._dispatchListeners = accumulateInto(
-      event._dispatchListeners,
-      listener
-    );
-    event._dispatchInstances = accumulateInto(event._dispatchInstances, inst);
-  }
-}
-
-/**
- * Collect dispatches (must be entirely collected before dispatching - see unit
- * tests). Lazily allocate the array to conserve memory.  We must loop through
- * each event and perform the traversal for each one. We cannot perform a
- * single traversal for the entire collection of events because each event may
- * have a different target.
- */
-function accumulateTwoPhaseDispatchesSingle(event) {
-  if (event && event.dispatchConfig.phasedRegistrationNames) {
-    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
-  }
-}
-
-/**
- * Same as `accumulateTwoPhaseDispatchesSingle`, but skips over the targetID.
- */
-function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
-  if (event && event.dispatchConfig.phasedRegistrationNames) {
-    var targetInst = event._targetInst;
-    var parentInst = targetInst ? getParentInstance(targetInst) : null;
-    traverseTwoPhase(parentInst, accumulateDirectionalDispatches, event);
-  }
-}
-
-/**
- * Accumulates without regard to direction, does not look for phased
- * registration names. Same as `accumulateDirectDispatchesSingle` but without
- * requiring that the `dispatchMarker` be the same as the dispatched ID.
- */
-function accumulateDispatches(inst, ignoredDirection, event) {
-  if (inst && event && event.dispatchConfig.registrationName) {
-    var registrationName = event.dispatchConfig.registrationName;
-    var listener = getListener(inst, registrationName);
-    if (listener) {
-      event._dispatchListeners = accumulateInto(
-        event._dispatchListeners,
-        listener
-      );
-      event._dispatchInstances = accumulateInto(event._dispatchInstances, inst);
-    }
-  }
-}
-
-/**
- * Accumulates dispatches on an `SyntheticEvent`, but only for the
- * `dispatchMarker`.
- * @param {SyntheticEvent} event
- */
-function accumulateDirectDispatchesSingle(event) {
-  if (event && event.dispatchConfig.registrationName) {
-    accumulateDispatches(event._targetInst, null, event);
-  }
-}
-
-function accumulateTwoPhaseDispatches(events) {
-  forEachAccumulated(events, accumulateTwoPhaseDispatchesSingle);
-}
-
-function accumulateTwoPhaseDispatchesSkipTarget(events) {
-  forEachAccumulated(events, accumulateTwoPhaseDispatchesSingleSkipTarget);
-}
-
-function accumulateDirectDispatches(events) {
-  forEachAccumulated(events, accumulateDirectDispatchesSingle);
-}
-
-/* eslint valid-typeof: 0 */
-
-var didWarnForAddedNewProperty = false;
-var EVENT_POOL_SIZE = 10;
-
-var shouldBeReleasedProperties = [
-  "dispatchConfig",
-  "_targetInst",
-  "nativeEvent",
-  "isDefaultPrevented",
-  "isPropagationStopped",
-  "_dispatchListeners",
-  "_dispatchInstances"
-];
-
-/**
- * @interface Event
- * @see http://www.w3.org/TR/DOM-Level-3-Events/
- */
-var EventInterface = {
-  type: null,
-  target: null,
-  // currentTarget is set when dispatching; no use in copying it here
-  currentTarget: emptyFunction.thatReturnsNull,
-  eventPhase: null,
-  bubbles: null,
-  cancelable: null,
-  timeStamp: function(event) {
-    return event.timeStamp || Date.now();
-  },
-  defaultPrevented: null,
-  isTrusted: null
-};
-
-/**
- * Synthetic events are dispatched by event plugins, typically in response to a
- * top-level event delegation handler.
- *
- * These systems should generally use pooling to reduce the frequency of garbage
- * collection. The system should check `isPersistent` to determine whether the
- * event should be released into the pool after being dispatched. Users that
- * need a persisted event should invoke `persist`.
- *
- * Synthetic events (and subclasses) implement the DOM Level 3 Events API by
- * normalizing browser quirks. Subclasses do not necessarily have to implement a
- * DOM interface; custom application-specific events can also subclass this.
- *
- * @param {object} dispatchConfig Configuration used to dispatch this event.
- * @param {*} targetInst Marker identifying the event target.
- * @param {object} nativeEvent Native browser event.
- * @param {DOMEventTarget} nativeEventTarget Target node.
- */
-function SyntheticEvent(
-  dispatchConfig,
-  targetInst,
-  nativeEvent,
-  nativeEventTarget
-) {
-  {
-    // these have a getter/setter for warnings
-    delete this.nativeEvent;
-    delete this.preventDefault;
-    delete this.stopPropagation;
-  }
-
-  this.dispatchConfig = dispatchConfig;
-  this._targetInst = targetInst;
-  this.nativeEvent = nativeEvent;
-
-  var Interface = this.constructor.Interface;
-  for (var propName in Interface) {
-    if (!Interface.hasOwnProperty(propName)) {
-      continue;
-    }
-    {
-      delete this[propName]; // this has a getter/setter for warnings
-    }
-    var normalize = Interface[propName];
-    if (normalize) {
-      this[propName] = normalize(nativeEvent);
-    } else {
-      if (propName === "target") {
-        this.target = nativeEventTarget;
-      } else {
-        this[propName] = nativeEvent[propName];
-      }
-    }
-  }
-
-  var defaultPrevented =
-    nativeEvent.defaultPrevented != null
-      ? nativeEvent.defaultPrevented
-      : nativeEvent.returnValue === false;
-  if (defaultPrevented) {
-    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
-  } else {
-    this.isDefaultPrevented = emptyFunction.thatReturnsFalse;
-  }
-  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
-  return this;
-}
-
-Object.assign(SyntheticEvent.prototype, {
-  preventDefault: function() {
-    this.defaultPrevented = true;
-    var event = this.nativeEvent;
-    if (!event) {
-      return;
-    }
-
-    if (event.preventDefault) {
-      event.preventDefault();
-    } else if (typeof event.returnValue !== "unknown") {
-      event.returnValue = false;
-    }
-    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
-  },
-
-  stopPropagation: function() {
-    var event = this.nativeEvent;
-    if (!event) {
-      return;
-    }
-
-    if (event.stopPropagation) {
-      event.stopPropagation();
-    } else if (typeof event.cancelBubble !== "unknown") {
-      // The ChangeEventPlugin registers a "propertychange" event for
-      // IE. This event does not support bubbling or cancelling, and
-      // any references to cancelBubble throw "Member not found".  A
-      // typeof check of "unknown" circumvents this issue (and is also
-      // IE specific).
-      event.cancelBubble = true;
-    }
-
-    this.isPropagationStopped = emptyFunction.thatReturnsTrue;
-  },
-
-  /**
-   * We release all dispatched `SyntheticEvent`s after each event loop, adding
-   * them back into the pool. This allows a way to hold onto a reference that
-   * won't be added back into the pool.
-   */
-  persist: function() {
-    this.isPersistent = emptyFunction.thatReturnsTrue;
-  },
-
-  /**
-   * Checks if this event should be released back into the pool.
-   *
-   * @return {boolean} True if this should not be released, false otherwise.
-   */
-  isPersistent: emptyFunction.thatReturnsFalse,
-
-  /**
-   * `PooledClass` looks for `destructor` on each instance it releases.
-   */
-  destructor: function() {
-    var Interface = this.constructor.Interface;
-    for (var propName in Interface) {
-      {
-        Object.defineProperty(
-          this,
-          propName,
-          getPooledWarningPropertyDefinition(propName, Interface[propName])
-        );
-      }
-    }
-    for (var i = 0; i < shouldBeReleasedProperties.length; i++) {
-      this[shouldBeReleasedProperties[i]] = null;
-    }
-    {
-      Object.defineProperty(
-        this,
-        "nativeEvent",
-        getPooledWarningPropertyDefinition("nativeEvent", null)
-      );
-      Object.defineProperty(
-        this,
-        "preventDefault",
-        getPooledWarningPropertyDefinition("preventDefault", emptyFunction)
-      );
-      Object.defineProperty(
-        this,
-        "stopPropagation",
-        getPooledWarningPropertyDefinition("stopPropagation", emptyFunction)
-      );
-    }
-  }
-});
-
-SyntheticEvent.Interface = EventInterface;
-
-/**
- * Helper to reduce boilerplate when creating subclasses.
- */
-SyntheticEvent.extend = function(Interface) {
-  var Super = this;
-
-  var E = function() {};
-  E.prototype = Super.prototype;
-  var prototype = new E();
-
-  function Class() {
-    return Super.apply(this, arguments);
-  }
-  Object.assign(prototype, Class.prototype);
-  Class.prototype = prototype;
-  Class.prototype.constructor = Class;
-
-  Class.Interface = Object.assign({}, Super.Interface, Interface);
-  Class.extend = Super.extend;
-  addEventPoolingTo(Class);
-
-  return Class;
-};
-
-/** Proxying after everything set on SyntheticEvent
- * to resolve Proxy issue on some WebKit browsers
- * in which some Event properties are set to undefined (GH#10010)
- */
-{
-  var isProxySupported =
-    typeof Proxy === "function" &&
-    // https://github.com/facebook/react/issues/12011
-    !Object.isSealed(new Proxy({}, {}));
-
-  if (isProxySupported) {
-    /*eslint-disable no-func-assign */
-    SyntheticEvent = new Proxy(SyntheticEvent, {
-      construct: function(target, args) {
-        return this.apply(target, Object.create(target.prototype), args);
-      },
-      apply: function(constructor, that, args) {
-        return new Proxy(constructor.apply(that, args), {
-          set: function(target, prop, value) {
-            if (
-              prop !== "isPersistent" &&
-              !target.constructor.Interface.hasOwnProperty(prop) &&
-              shouldBeReleasedProperties.indexOf(prop) === -1
-            ) {
-              !(didWarnForAddedNewProperty || target.isPersistent())
-                ? warning(
-                    false,
-                    "This synthetic event is reused for performance reasons. If you're " +
-                      "seeing this, you're adding a new property in the synthetic event object. " +
-                      "The property is never released. See " +
-                      "https://fb.me/react-event-pooling for more information."
-                  )
-                : void 0;
-              didWarnForAddedNewProperty = true;
-            }
-            target[prop] = value;
-            return true;
-          }
-        });
-      }
-    });
-    /*eslint-enable no-func-assign */
-  }
-}
-
-addEventPoolingTo(SyntheticEvent);
-
-/**
- * Helper to nullify syntheticEvent instance properties when destructing
- *
- * @param {String} propName
- * @param {?object} getVal
- * @return {object} defineProperty object
- */
-function getPooledWarningPropertyDefinition(propName, getVal) {
-  var isFunction = typeof getVal === "function";
-  return {
-    configurable: true,
-    set: set,
-    get: get$$1
-  };
-
-  function set(val) {
-    var action = isFunction ? "setting the method" : "setting the property";
-    warn(action, "This is effectively a no-op");
-    return val;
-  }
-
-  function get$$1() {
-    var action = isFunction ? "accessing the method" : "accessing the property";
-    var result = isFunction
-      ? "This is a no-op function"
-      : "This is set to null";
-    warn(action, result);
-    return getVal;
-  }
-
-  function warn(action, result) {
-    var warningCondition = false;
-    !warningCondition
-      ? warning(
-          false,
-          "This synthetic event is reused for performance reasons. If you're seeing this, " +
-            "you're %s `%s` on a released/nullified synthetic event. %s. " +
-            "If you must keep the original synthetic event around, use event.persist(). " +
-            "See https://fb.me/react-event-pooling for more information.",
-          action,
-          propName,
-          result
-        )
-      : void 0;
-  }
-}
-
-function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
-  var EventConstructor = this;
-  if (EventConstructor.eventPool.length) {
-    var instance = EventConstructor.eventPool.pop();
-    EventConstructor.call(
-      instance,
-      dispatchConfig,
-      targetInst,
-      nativeEvent,
-      nativeInst
-    );
-    return instance;
-  }
-  return new EventConstructor(
-    dispatchConfig,
-    targetInst,
-    nativeEvent,
-    nativeInst
-  );
-}
-
-function releasePooledEvent(event) {
-  var EventConstructor = this;
-  invariant(
-    event instanceof EventConstructor,
-    "Trying to release an event instance  into a pool of a different type."
-  );
-  event.destructor();
-  if (EventConstructor.eventPool.length < EVENT_POOL_SIZE) {
-    EventConstructor.eventPool.push(event);
-  }
-}
-
-function addEventPoolingTo(EventConstructor) {
-  EventConstructor.eventPool = [];
-  EventConstructor.getPooled = getPooledEvent;
-  EventConstructor.release = releasePooledEvent;
-}
-
-var SyntheticEvent$1 = SyntheticEvent;
-
-/**
- * `touchHistory` isn't actually on the native event, but putting it in the
- * interface will ensure that it is cleaned up when pooled/destroyed. The
- * `ResponderEventPlugin` will populate it appropriately.
- */
-var ResponderSyntheticEvent = SyntheticEvent$1.extend({
-  touchHistory: function(nativeEvent) {
-    return null; // Actually doesn't even look at the native event.
-  }
-});
-
-/**
- * Tracks the position and time of each active touch by `touch.identifier`. We
- * should typically only see IDs in the range of 1-20 because IDs get recycled
- * when touches end and start again.
- */
-
-var MAX_TOUCH_BANK = 20;
-var touchBank = [];
-var touchHistory = {
-  touchBank: touchBank,
-  numberActiveTouches: 0,
-  // If there is only one active touch, we remember its location. This prevents
-  // us having to loop through all of the touches all the time in the most
-  // common case.
-  indexOfSingleActiveTouch: -1,
-  mostRecentTimeStamp: 0
-};
-
-function timestampForTouch(touch) {
-  // The legacy internal implementation provides "timeStamp", which has been
-  // renamed to "timestamp". Let both work for now while we iron it out
-  // TODO (evv): rename timeStamp to timestamp in internal code
-  return touch.timeStamp || touch.timestamp;
-}
-
-/**
- * TODO: Instead of making gestures recompute filtered velocity, we could
- * include a built in velocity computation that can be reused globally.
- */
-function createTouchRecord(touch) {
-  return {
-    touchActive: true,
-    startPageX: touch.pageX,
-    startPageY: touch.pageY,
-    startTimeStamp: timestampForTouch(touch),
-    currentPageX: touch.pageX,
-    currentPageY: touch.pageY,
-    currentTimeStamp: timestampForTouch(touch),
-    previousPageX: touch.pageX,
-    previousPageY: touch.pageY,
-    previousTimeStamp: timestampForTouch(touch)
-  };
-}
-
-function resetTouchRecord(touchRecord, touch) {
-  touchRecord.touchActive = true;
-  touchRecord.startPageX = touch.pageX;
-  touchRecord.startPageY = touch.pageY;
-  touchRecord.startTimeStamp = timestampForTouch(touch);
-  touchRecord.currentPageX = touch.pageX;
-  touchRecord.currentPageY = touch.pageY;
-  touchRecord.currentTimeStamp = timestampForTouch(touch);
-  touchRecord.previousPageX = touch.pageX;
-  touchRecord.previousPageY = touch.pageY;
-  touchRecord.previousTimeStamp = timestampForTouch(touch);
-}
-
-function getTouchIdentifier(_ref) {
-  var identifier = _ref.identifier;
-
-  invariant(identifier != null, "Touch object is missing identifier.");
-  {
-    !(identifier <= MAX_TOUCH_BANK)
-      ? warning(
-          false,
-          "Touch identifier %s is greater than maximum supported %s which causes " +
-            "performance issues backfilling array locations for all of the indices.",
-          identifier,
-          MAX_TOUCH_BANK
-        )
-      : void 0;
-  }
-  return identifier;
-}
-
-function recordTouchStart(touch) {
-  var identifier = getTouchIdentifier(touch);
-  var touchRecord = touchBank[identifier];
-  if (touchRecord) {
-    resetTouchRecord(touchRecord, touch);
-  } else {
-    touchBank[identifier] = createTouchRecord(touch);
-  }
-  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
-}
-
-function recordTouchMove(touch) {
-  var touchRecord = touchBank[getTouchIdentifier(touch)];
-  if (touchRecord) {
-    touchRecord.touchActive = true;
-    touchRecord.previousPageX = touchRecord.currentPageX;
-    touchRecord.previousPageY = touchRecord.currentPageY;
-    touchRecord.previousTimeStamp = touchRecord.currentTimeStamp;
-    touchRecord.currentPageX = touch.pageX;
-    touchRecord.currentPageY = touch.pageY;
-    touchRecord.currentTimeStamp = timestampForTouch(touch);
-    touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
-  } else {
-    console.error(
-      "Cannot record touch move without a touch start.\n" + "Touch Move: %s\n",
-      "Touch Bank: %s",
-      printTouch(touch),
-      printTouchBank()
-    );
-  }
-}
-
-function recordTouchEnd(touch) {
-  var touchRecord = touchBank[getTouchIdentifier(touch)];
-  if (touchRecord) {
-    touchRecord.touchActive = false;
-    touchRecord.previousPageX = touchRecord.currentPageX;
-    touchRecord.previousPageY = touchRecord.currentPageY;
-    touchRecord.previousTimeStamp = touchRecord.currentTimeStamp;
-    touchRecord.currentPageX = touch.pageX;
-    touchRecord.currentPageY = touch.pageY;
-    touchRecord.currentTimeStamp = timestampForTouch(touch);
-    touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
-  } else {
-    console.error(
-      "Cannot record touch end without a touch start.\n" + "Touch End: %s\n",
-      "Touch Bank: %s",
-      printTouch(touch),
-      printTouchBank()
-    );
-  }
-}
-
-function printTouch(touch) {
-  return JSON.stringify({
-    identifier: touch.identifier,
-    pageX: touch.pageX,
-    pageY: touch.pageY,
-    timestamp: timestampForTouch(touch)
-  });
-}
-
-function printTouchBank() {
-  var printed = JSON.stringify(touchBank.slice(0, MAX_TOUCH_BANK));
-  if (touchBank.length > MAX_TOUCH_BANK) {
-    printed += " (original size: " + touchBank.length + ")";
-  }
-  return printed;
-}
-
-var ResponderTouchHistoryStore = {
-  recordTouchTrack: function(topLevelType, nativeEvent) {
-    if (isMoveish(topLevelType)) {
-      nativeEvent.changedTouches.forEach(recordTouchMove);
-    } else if (isStartish(topLevelType)) {
-      nativeEvent.changedTouches.forEach(recordTouchStart);
-      touchHistory.numberActiveTouches = nativeEvent.touches.length;
-      if (touchHistory.numberActiveTouches === 1) {
-        touchHistory.indexOfSingleActiveTouch =
-          nativeEvent.touches[0].identifier;
-      }
-    } else if (isEndish(topLevelType)) {
-      nativeEvent.changedTouches.forEach(recordTouchEnd);
-      touchHistory.numberActiveTouches = nativeEvent.touches.length;
-      if (touchHistory.numberActiveTouches === 1) {
-        for (var i = 0; i < touchBank.length; i++) {
-          var touchTrackToCheck = touchBank[i];
-          if (touchTrackToCheck != null && touchTrackToCheck.touchActive) {
-            touchHistory.indexOfSingleActiveTouch = i;
-            break;
-          }
-        }
-        {
-          var activeRecord = touchBank[touchHistory.indexOfSingleActiveTouch];
-          !(activeRecord != null && activeRecord.touchActive)
-            ? warning(false, "Cannot find single active touch.")
-            : void 0;
-        }
-      }
-    }
-  },
-
-  touchHistory: touchHistory
-};
-
-/**
- * Accumulates items that must not be null or undefined.
- *
- * This is used to conserve memory by avoiding array allocations.
- *
- * @return {*|array<*>} An accumulation of items.
- */
-function accumulate(current, next) {
-  invariant(
-    next != null,
-    "accumulate(...): Accumulated items must be not be null or undefined."
-  );
-
-  if (current == null) {
-    return next;
-  }
-
-  // Both are not empty. Warning: Never call x.concat(y) when you are not
-  // certain that x is an Array (x could be a string with concat method).
-  if (Array.isArray(current)) {
-    return current.concat(next);
-  }
-
-  if (Array.isArray(next)) {
-    return [current].concat(next);
-  }
-
-  return [current, next];
-}
-
-/**
- * Instance of element that should respond to touch/move types of interactions,
- * as indicated explicitly by relevant callbacks.
- */
-var responderInst = null;
-
-/**
- * Count of current touches. A textInput should become responder iff the
- * selection changes while there is a touch on the screen.
- */
-var trackedTouchCount = 0;
-
-/**
- * Last reported number of active touches.
- */
-var previousActiveTouches = 0;
-
-var changeResponder = function(nextResponderInst, blockHostResponder) {
-  var oldResponderInst = responderInst;
-  responderInst = nextResponderInst;
-  if (ResponderEventPlugin.GlobalResponderHandler !== null) {
-    ResponderEventPlugin.GlobalResponderHandler.onChange(
-      oldResponderInst,
-      nextResponderInst,
-      blockHostResponder
-    );
-  }
-};
-
-var eventTypes$1 = {
-  /**
-   * On a `touchStart`/`mouseDown`, is it desired that this element become the
-   * responder?
-   */
-  startShouldSetResponder: {
-    phasedRegistrationNames: {
-      bubbled: "onStartShouldSetResponder",
-      captured: "onStartShouldSetResponderCapture"
-    }
-  },
-
-  /**
-   * On a `scroll`, is it desired that this element become the responder? This
-   * is usually not needed, but should be used to retroactively infer that a
-   * `touchStart` had occurred during momentum scroll. During a momentum scroll,
-   * a touch start will be immediately followed by a scroll event if the view is
-   * currently scrolling.
-   *
-   * TODO: This shouldn't bubble.
-   */
-  scrollShouldSetResponder: {
-    phasedRegistrationNames: {
-      bubbled: "onScrollShouldSetResponder",
-      captured: "onScrollShouldSetResponderCapture"
-    }
-  },
-
-  /**
-   * On text selection change, should this element become the responder? This
-   * is needed for text inputs or other views with native selection, so the
-   * JS view can claim the responder.
-   *
-   * TODO: This shouldn't bubble.
-   */
-  selectionChangeShouldSetResponder: {
-    phasedRegistrationNames: {
-      bubbled: "onSelectionChangeShouldSetResponder",
-      captured: "onSelectionChangeShouldSetResponderCapture"
-    }
-  },
-
-  /**
-   * On a `touchMove`/`mouseMove`, is it desired that this element become the
-   * responder?
-   */
-  moveShouldSetResponder: {
-    phasedRegistrationNames: {
-      bubbled: "onMoveShouldSetResponder",
-      captured: "onMoveShouldSetResponderCapture"
-    }
-  },
-
-  /**
-   * Direct responder events dispatched directly to responder. Do not bubble.
-   */
-  responderStart: { registrationName: "onResponderStart" },
-  responderMove: { registrationName: "onResponderMove" },
-  responderEnd: { registrationName: "onResponderEnd" },
-  responderRelease: { registrationName: "onResponderRelease" },
-  responderTerminationRequest: {
-    registrationName: "onResponderTerminationRequest"
-  },
-  responderGrant: { registrationName: "onResponderGrant" },
-  responderReject: { registrationName: "onResponderReject" },
-  responderTerminate: { registrationName: "onResponderTerminate" }
-};
-
-/**
- *
- * Responder System:
- * ----------------
- *
- * - A global, solitary "interaction lock" on a view.
- * - If a node becomes the responder, it should convey visual feedback
- *   immediately to indicate so, either by highlighting or moving accordingly.
- * - To be the responder means, that touches are exclusively important to that
- *   responder view, and no other view.
- * - While touches are still occurring, the responder lock can be transferred to
- *   a new view, but only to increasingly "higher" views (meaning ancestors of
- *   the current responder).
- *
- * Responder being granted:
- * ------------------------
- *
- * - Touch starts, moves, and scrolls can cause an ID to become the responder.
- * - We capture/bubble `startShouldSetResponder`/`moveShouldSetResponder` to
- *   the "appropriate place".
- * - If nothing is currently the responder, the "appropriate place" is the
- *   initiating event's `targetID`.
- * - If something *is* already the responder, the "appropriate place" is the
- *   first common ancestor of the event target and the current `responderInst`.
- * - Some negotiation happens: See the timing diagram below.
- * - Scrolled views automatically become responder. The reasoning is that a
- *   platform scroll view that isn't built on top of the responder system has
- *   began scrolling, and the active responder must now be notified that the
- *   interaction is no longer locked to it - the system has taken over.
- *
- * - Responder being released:
- *   As soon as no more touches that *started* inside of descendants of the
- *   *current* responderInst, an `onResponderRelease` event is dispatched to the
- *   current responder, and the responder lock is released.
- *
- * TODO:
- * - on "end", a callback hook for `onResponderEndShouldRemainResponder` that
- *   determines if the responder lock should remain.
- * - If a view shouldn't "remain" the responder, any active touches should by
- *   default be considered "dead" and do not influence future negotiations or
- *   bubble paths. It should be as if those touches do not exist.
- * -- For multitouch: Usually a translate-z will choose to "remain" responder
- *  after one out of many touches ended. For translate-y, usually the view
- *  doesn't wish to "remain" responder after one of many touches end.
- * - Consider building this on top of a `stopPropagation` model similar to
- *   `W3C` events.
- * - Ensure that `onResponderTerminate` is called on touch cancels, whether or
- *   not `onResponderTerminationRequest` returns `true` or `false`.
- *
- */
-
-/*                                             Negotiation Performed
-                                             +-----------------------+
-                                            /                         \
-Process low level events to    +     Current Responder      +   wantsResponderID
-determine who to perform negot-|   (if any exists at all)   |
-iation/transition              | Otherwise just pass through|
--------------------------------+----------------------------+------------------+
-Bubble to find first ID        |                            |
-to return true:wantsResponderID|                            |
-                               |                            |
-     +-------------+           |                            |
-     | onTouchStart|           |                            |
-     +------+------+     none  |                            |
-            |            return|                            |
-+-----------v-------------+true| +------------------------+ |
-|onStartShouldSetResponder|----->|onResponderStart (cur)  |<-----------+
-+-----------+-------------+    | +------------------------+ |          |
-            |                  |                            | +--------+-------+
-            | returned true for|       false:REJECT +-------->|onResponderReject
-            | wantsResponderID |                    |       | +----------------+
-            | (now attempt     | +------------------+-----+ |
-            |  handoff)        | |   onResponder          | |
-            +------------------->|      TerminationRequest| |
-                               | +------------------+-----+ |
-                               |                    |       | +----------------+
-                               |         true:GRANT +-------->|onResponderGrant|
-                               |                            | +--------+-------+
-                               | +------------------------+ |          |
-                               | |   onResponderTerminate |<-----------+
-                               | +------------------+-----+ |
-                               |                    |       | +----------------+
-                               |                    +-------->|onResponderStart|
-                               |                            | +----------------+
-Bubble to find first ID        |                            |
-to return true:wantsResponderID|                            |
-                               |                            |
-     +-------------+           |                            |
-     | onTouchMove |           |                            |
-     +------+------+     none  |                            |
-            |            return|                            |
-+-----------v-------------+true| +------------------------+ |
-|onMoveShouldSetResponder |----->|onResponderMove (cur)   |<-----------+
-+-----------+-------------+    | +------------------------+ |          |
-            |                  |                            | +--------+-------+
-            | returned true for|       false:REJECT +-------->|onResponderRejec|
-            | wantsResponderID |                    |       | +----------------+
-            | (now attempt     | +------------------+-----+ |
-            |  handoff)        | |   onResponder          | |
-            +------------------->|      TerminationRequest| |
-                               | +------------------+-----+ |
-                               |                    |       | +----------------+
-                               |         true:GRANT +-------->|onResponderGrant|
-                               |                            | +--------+-------+
-                               | +------------------------+ |          |
-                               | |   onResponderTerminate |<-----------+
-                               | +------------------+-----+ |
-                               |                    |       | +----------------+
-                               |                    +-------->|onResponderMove |
-                               |                            | +----------------+
-                               |                            |
-                               |                            |
-      Some active touch started|                            |
-      inside current responder | +------------------------+ |
-      +------------------------->|      onResponderEnd    | |
-      |                        | +------------------------+ |
-  +---+---------+              |                            |
-  | onTouchEnd  |              |                            |
-  +---+---------+              |                            |
-      |                        | +------------------------+ |
-      +------------------------->|     onResponderEnd     | |
-      No active touches started| +-----------+------------+ |
-      inside current responder |             |              |
-                               |             v              |
-                               | +------------------------+ |
-                               | |    onResponderRelease  | |
-                               | +------------------------+ |
-                               |                            |
-                               +                            + */
-
-/**
- * A note about event ordering in the `EventPluginHub`.
- *
- * Suppose plugins are injected in the following order:
- *
- * `[R, S, C]`
- *
- * To help illustrate the example, assume `S` is `SimpleEventPlugin` (for
- * `onClick` etc) and `R` is `ResponderEventPlugin`.
- *
- * "Deferred-Dispatched Events":
- *
- * - The current event plugin system will traverse the list of injected plugins,
- *   in order, and extract events by collecting the plugin's return value of
- *   `extractEvents()`.
- * - These events that are returned from `extractEvents` are "deferred
- *   dispatched events".
- * - When returned from `extractEvents`, deferred-dispatched events contain an
- *   "accumulation" of deferred dispatches.
- * - These deferred dispatches are accumulated/collected before they are
- *   returned, but processed at a later time by the `EventPluginHub` (hence the
- *   name deferred).
- *
- * In the process of returning their deferred-dispatched events, event plugins
- * themselves can dispatch events on-demand without returning them from
- * `extractEvents`. Plugins might want to do this, so that they can use event
- * dispatching as a tool that helps them decide which events should be extracted
- * in the first place.
- *
- * "On-Demand-Dispatched Events":
- *
- * - On-demand-dispatched events are not returned from `extractEvents`.
- * - On-demand-dispatched events are dispatched during the process of returning
- *   the deferred-dispatched events.
- * - They should not have side effects.
- * - They should be avoided, and/or eventually be replaced with another
- *   abstraction that allows event plugins to perform multiple "rounds" of event
- *   extraction.
- *
- * Therefore, the sequence of event dispatches becomes:
- *
- * - `R`s on-demand events (if any)   (dispatched by `R` on-demand)
- * - `S`s on-demand events (if any)   (dispatched by `S` on-demand)
- * - `C`s on-demand events (if any)   (dispatched by `C` on-demand)
- * - `R`s extracted events (if any)   (dispatched by `EventPluginHub`)
- * - `S`s extracted events (if any)   (dispatched by `EventPluginHub`)
- * - `C`s extracted events (if any)   (dispatched by `EventPluginHub`)
- *
- * In the case of `ResponderEventPlugin`: If the `startShouldSetResponder`
- * on-demand dispatch returns `true` (and some other details are satisfied) the
- * `onResponderGrant` deferred dispatched event is returned from
- * `extractEvents`. The sequence of dispatch executions in this case
- * will appear as follows:
- *
- * - `startShouldSetResponder` (`ResponderEventPlugin` dispatches on-demand)
- * - `touchStartCapture`       (`EventPluginHub` dispatches as usual)
- * - `touchStart`              (`EventPluginHub` dispatches as usual)
- * - `responderGrant/Reject`   (`EventPluginHub` dispatches as usual)
- */
-
-function setResponderAndExtractTransfer(
-  topLevelType,
-  targetInst,
-  nativeEvent,
-  nativeEventTarget
-) {
-  var shouldSetEventType = isStartish(topLevelType)
-    ? eventTypes$1.startShouldSetResponder
-    : isMoveish(topLevelType)
-      ? eventTypes$1.moveShouldSetResponder
-      : topLevelType === "topSelectionChange"
-        ? eventTypes$1.selectionChangeShouldSetResponder
-        : eventTypes$1.scrollShouldSetResponder;
-
-  // TODO: stop one short of the current responder.
-  var bubbleShouldSetFrom = !responderInst
-    ? targetInst
-    : getLowestCommonAncestor(responderInst, targetInst);
-
-  // When capturing/bubbling the "shouldSet" event, we want to skip the target
-  // (deepest ID) if it happens to be the current responder. The reasoning:
-  // It's strange to get an `onMoveShouldSetResponder` when you're *already*
-  // the responder.
-  var skipOverBubbleShouldSetFrom = bubbleShouldSetFrom === responderInst;
-  var shouldSetEvent = ResponderSyntheticEvent.getPooled(
-    shouldSetEventType,
-    bubbleShouldSetFrom,
-    nativeEvent,
-    nativeEventTarget
-  );
-  shouldSetEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-  if (skipOverBubbleShouldSetFrom) {
-    accumulateTwoPhaseDispatchesSkipTarget(shouldSetEvent);
-  } else {
-    accumulateTwoPhaseDispatches(shouldSetEvent);
-  }
-  var wantsResponderInst = executeDispatchesInOrderStopAtTrue(shouldSetEvent);
-  if (!shouldSetEvent.isPersistent()) {
-    shouldSetEvent.constructor.release(shouldSetEvent);
-  }
-
-  if (!wantsResponderInst || wantsResponderInst === responderInst) {
-    return null;
-  }
-  var extracted = void 0;
-  var grantEvent = ResponderSyntheticEvent.getPooled(
-    eventTypes$1.responderGrant,
-    wantsResponderInst,
-    nativeEvent,
-    nativeEventTarget
-  );
-  grantEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-
-  accumulateDirectDispatches(grantEvent);
-  var blockHostResponder = executeDirectDispatch(grantEvent) === true;
-  if (responderInst) {
-    var terminationRequestEvent = ResponderSyntheticEvent.getPooled(
-      eventTypes$1.responderTerminationRequest,
-      responderInst,
-      nativeEvent,
-      nativeEventTarget
-    );
-    terminationRequestEvent.touchHistory =
-      ResponderTouchHistoryStore.touchHistory;
-    accumulateDirectDispatches(terminationRequestEvent);
-    var shouldSwitch =
-      !hasDispatches(terminationRequestEvent) ||
-      executeDirectDispatch(terminationRequestEvent);
-    if (!terminationRequestEvent.isPersistent()) {
-      terminationRequestEvent.constructor.release(terminationRequestEvent);
-    }
-
-    if (shouldSwitch) {
-      var terminateEvent = ResponderSyntheticEvent.getPooled(
-        eventTypes$1.responderTerminate,
-        responderInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      terminateEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-      accumulateDirectDispatches(terminateEvent);
-      extracted = accumulate(extracted, [grantEvent, terminateEvent]);
-      changeResponder(wantsResponderInst, blockHostResponder);
-    } else {
-      var rejectEvent = ResponderSyntheticEvent.getPooled(
-        eventTypes$1.responderReject,
-        wantsResponderInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      rejectEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-      accumulateDirectDispatches(rejectEvent);
-      extracted = accumulate(extracted, rejectEvent);
-    }
-  } else {
-    extracted = accumulate(extracted, grantEvent);
-    changeResponder(wantsResponderInst, blockHostResponder);
-  }
-  return extracted;
-}
-
-/**
- * A transfer is a negotiation between a currently set responder and the next
- * element to claim responder status. Any start event could trigger a transfer
- * of responderInst. Any move event could trigger a transfer.
- *
- * @param {string} topLevelType Record from `BrowserEventConstants`.
- * @return {boolean} True if a transfer of responder could possibly occur.
- */
-function canTriggerTransfer(topLevelType, topLevelInst, nativeEvent) {
-  return (
-    topLevelInst &&
-    // responderIgnoreScroll: We are trying to migrate away from specifically
-    // tracking native scroll events here and responderIgnoreScroll indicates we
-    // will send topTouchCancel to handle canceling touch events instead
-    ((topLevelType === "topScroll" && !nativeEvent.responderIgnoreScroll) ||
-      (trackedTouchCount > 0 && topLevelType === "topSelectionChange") ||
-      isStartish(topLevelType) ||
-      isMoveish(topLevelType))
-  );
-}
-
-/**
- * Returns whether or not this touch end event makes it such that there are no
- * longer any touches that started inside of the current `responderInst`.
- *
- * @param {NativeEvent} nativeEvent Native touch end event.
- * @return {boolean} Whether or not this touch end event ends the responder.
- */
-function noResponderTouches(nativeEvent) {
-  var touches = nativeEvent.touches;
-  if (!touches || touches.length === 0) {
-    return true;
-  }
-  for (var i = 0; i < touches.length; i++) {
-    var activeTouch = touches[i];
-    var target = activeTouch.target;
-    if (target !== null && target !== undefined && target !== 0) {
-      // Is the original touch location inside of the current responder?
-      var targetInst = getInstanceFromNode(target);
-      if (isAncestor(responderInst, targetInst)) {
-        return false;
-      }
-    }
-  }
-  return true;
-}
-
-var ResponderEventPlugin = {
-  /* For unit testing only */
-  _getResponder: function() {
-    return responderInst;
-  },
-
-  eventTypes: eventTypes$1,
-
-  /**
-   * We must be resilient to `targetInst` being `null` on `touchMove` or
-   * `touchEnd`. On certain platforms, this means that a native scroll has
-   * assumed control and the original touch targets are destroyed.
-   */
-  extractEvents: function(
-    topLevelType,
-    targetInst,
-    nativeEvent,
-    nativeEventTarget
-  ) {
-    if (isStartish(topLevelType)) {
-      trackedTouchCount += 1;
-    } else if (isEndish(topLevelType)) {
-      if (trackedTouchCount >= 0) {
-        trackedTouchCount -= 1;
-      } else {
-        console.error(
-          "Ended a touch event which was not counted in `trackedTouchCount`."
-        );
-        return null;
-      }
-    }
-
-    ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
-
-    var extracted = canTriggerTransfer(topLevelType, targetInst, nativeEvent)
-      ? setResponderAndExtractTransfer(
-          topLevelType,
-          targetInst,
-          nativeEvent,
-          nativeEventTarget
-        )
-      : null;
-    // Responder may or may not have transferred on a new touch start/move.
-    // Regardless, whoever is the responder after any potential transfer, we
-    // direct all touch start/move/ends to them in the form of
-    // `onResponderMove/Start/End`. These will be called for *every* additional
-    // finger that move/start/end, dispatched directly to whoever is the
-    // current responder at that moment, until the responder is "released".
-    //
-    // These multiple individual change touch events are are always bookended
-    // by `onResponderGrant`, and one of
-    // (`onResponderRelease/onResponderTerminate`).
-    var isResponderTouchStart = responderInst && isStartish(topLevelType);
-    var isResponderTouchMove = responderInst && isMoveish(topLevelType);
-    var isResponderTouchEnd = responderInst && isEndish(topLevelType);
-    var incrementalTouch = isResponderTouchStart
-      ? eventTypes$1.responderStart
-      : isResponderTouchMove
-        ? eventTypes$1.responderMove
-        : isResponderTouchEnd ? eventTypes$1.responderEnd : null;
-
-    if (incrementalTouch) {
-      var gesture = ResponderSyntheticEvent.getPooled(
-        incrementalTouch,
-        responderInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      gesture.touchHistory = ResponderTouchHistoryStore.touchHistory;
-      accumulateDirectDispatches(gesture);
-      extracted = accumulate(extracted, gesture);
-    }
-
-    var isResponderTerminate =
-      responderInst && topLevelType === "topTouchCancel";
-    var isResponderRelease =
-      responderInst &&
-      !isResponderTerminate &&
-      isEndish(topLevelType) &&
-      noResponderTouches(nativeEvent);
-    var finalTouch = isResponderTerminate
-      ? eventTypes$1.responderTerminate
-      : isResponderRelease ? eventTypes$1.responderRelease : null;
-    if (finalTouch) {
-      var finalEvent = ResponderSyntheticEvent.getPooled(
-        finalTouch,
-        responderInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      finalEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-      accumulateDirectDispatches(finalEvent);
-      extracted = accumulate(extracted, finalEvent);
-      changeResponder(null);
-    }
-
-    var numberActiveTouches =
-      ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
-    if (
-      ResponderEventPlugin.GlobalInteractionHandler &&
-      numberActiveTouches !== previousActiveTouches
-    ) {
-      ResponderEventPlugin.GlobalInteractionHandler.onChange(
-        numberActiveTouches
-      );
-    }
-    previousActiveTouches = numberActiveTouches;
-
-    return extracted;
-  },
-
-  GlobalResponderHandler: null,
-  GlobalInteractionHandler: null,
-
-  injection: {
-    /**
-     * @param {{onChange: (ReactID, ReactID) => void} GlobalResponderHandler
-     * Object that handles any change in responder. Use this to inject
-     * integration with an existing touch handling system etc.
-     */
-    injectGlobalResponderHandler: function(GlobalResponderHandler) {
-      ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
-    },
-
-    /**
-     * @param {{onChange: (numberActiveTouches) => void} GlobalInteractionHandler
-     * Object that handles any change in the number of active touches.
-     */
-    injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
-      ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
-    }
-  }
-};
-
-var customBubblingEventTypes$1 =
-  ReactNativeViewConfigRegistry.customBubblingEventTypes;
-var customDirectEventTypes$1 =
-  ReactNativeViewConfigRegistry.customDirectEventTypes;
-var eventTypes$2 = ReactNativeViewConfigRegistry.eventTypes;
-
-var ReactNativeBridgeEventPlugin = {
-  eventTypes: eventTypes$2,
-
-  /**
-   * @see {EventPluginHub.extractEvents}
-   */
-  extractEvents: function(
-    topLevelType,
-    targetInst,
-    nativeEvent,
-    nativeEventTarget
-  ) {
-    if (targetInst == null) {
-      // Probably a node belonging to another renderer's tree.
-      return null;
-    }
-    var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType];
-    var directDispatchConfig = customDirectEventTypes$1[topLevelType];
-    invariant(
-      bubbleDispatchConfig || directDispatchConfig,
-      'Unsupported top level event type "%s" dispatched',
-      topLevelType
-    );
-    var event = SyntheticEvent$1.getPooled(
-      bubbleDispatchConfig || directDispatchConfig,
-      targetInst,
-      nativeEvent,
-      nativeEventTarget
-    );
-    if (bubbleDispatchConfig) {
-      accumulateTwoPhaseDispatches(event);
-    } else if (directDispatchConfig) {
-      accumulateDirectDispatches(event);
-    } else {
-      return null;
-    }
-    return event;
-  }
-};
-
-var instanceCache = {};
-var instanceProps = {};
-
-function precacheFiberNode(hostInst, tag) {
-  instanceCache[tag] = hostInst;
-}
-
-function uncacheFiberNode(tag) {
-  delete instanceCache[tag];
-  delete instanceProps[tag];
-}
-
-function getInstanceFromTag(tag) {
-  if (typeof tag === "number") {
-    return instanceCache[tag] || null;
-  } else {
-    // Fabric will invoke event emitters on a direct fiber reference
-    return tag;
-  }
-}
-
-function getTagFromInstance(inst) {
-  var tag = inst.stateNode._nativeTag;
-  if (tag === undefined) {
-    tag = inst.stateNode.canonical._nativeTag;
-  }
-  invariant(tag, "All native instances should have a tag.");
-  return tag;
-}
-
-function getFiberCurrentPropsFromNode$1(stateNode) {
-  return instanceProps[stateNode._nativeTag] || null;
-}
-
-function updateFiberProps(tag, props) {
-  instanceProps[tag] = props;
-}
-
-var ReactNativeComponentTree = Object.freeze({
-  precacheFiberNode: precacheFiberNode,
-  uncacheFiberNode: uncacheFiberNode,
-  getClosestInstanceFromNode: getInstanceFromTag,
-  getInstanceFromNode: getInstanceFromTag,
-  getNodeFromInstance: getTagFromInstance,
-  getFiberCurrentPropsFromNode: getFiberCurrentPropsFromNode$1,
-  updateFiberProps: updateFiberProps
-});
-
-var ReactNativeEventPluginOrder = [
-  "ResponderEventPlugin",
-  "ReactNativeBridgeEventPlugin"
-];
-
-// Module provided by RN:
-var ReactNativeGlobalResponderHandler = {
-  onChange: function(from, to, blockNativeResponder) {
-    if (to !== null) {
-      var tag = to.stateNode._nativeTag;
-      UIManager.setJSResponder(tag, blockNativeResponder);
-    } else {
-      UIManager.clearJSResponder();
-    }
-  }
-};
-
-/**
- * Make sure essential globals are available and are patched correctly. Please don't remove this
- * line. Bundles created by react-packager `require` it before executing any application code. This
- * ensures it exists in the dependency graph and can be `require`d.
- * TODO: require this in packager, not in React #10932517
- */
-// Module provided by RN:
-/**
- * Inject module for resolving DOM hierarchy and plugin ordering.
- */
-injection.injectEventPluginOrder(ReactNativeEventPluginOrder);
-injection$1.injectComponentTree(ReactNativeComponentTree);
-
-ResponderEventPlugin.injection.injectGlobalResponderHandler(
-  ReactNativeGlobalResponderHandler
-);
-
-/**
- * Some important event plugins included by default (without having to require
- * them).
- */
-injection.injectEventPluginsByName({
-  ResponderEventPlugin: ResponderEventPlugin,
-  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
-});
-
-// TODO: The event emitter registration is interfering with the existing
-// ReactNative renderer. So disable it for Fabric for now.
-
-// import * as ReactNativeEventEmitter from './ReactNativeEventEmitter';
-
-// Module provided by RN:
-// import RCTEventEmitter from 'RCTEventEmitter';
-
-/**
- * Register the event emitter with the native bridge
- */
-// RCTEventEmitter.register(ReactNativeEventEmitter);
-
-// The Symbol used to tag the ReactElement-like types. If there is no native Symbol
-// nor polyfill, then a plain number is used for performance.
-var hasSymbol = typeof Symbol === "function" && Symbol["for"];
-
-var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
-var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
-var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
-var REACT_STRICT_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.strict_mode")
-  : 0xeacc;
-var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
-var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
-var REACT_ASYNC_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.async_mode")
-  : 0xeacf;
-var REACT_FORWARD_REF_TYPE = hasSymbol
-  ? Symbol["for"]("react.forward_ref")
-  : 0xead0;
-
-var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
-var FAUX_ITERATOR_SYMBOL = "@@iterator";
-
-function getIteratorFn(maybeIterable) {
-  if (maybeIterable === null || typeof maybeIterable === "undefined") {
-    return null;
-  }
-  var maybeIterator =
-    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
-    maybeIterable[FAUX_ITERATOR_SYMBOL];
-  if (typeof maybeIterator === "function") {
-    return maybeIterator;
-  }
-  return null;
-}
-
-function createPortal(
-  children,
-  containerInfo,
-  // TODO: figure out the API for cross-renderer implementation.
-  implementation
-) {
-  var key =
-    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
-
-  return {
-    // This tag allow us to uniquely identify this as a React Portal
-    $$typeof: REACT_PORTAL_TYPE,
-    key: key == null ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
-}
-
-// Used as a way to call batchedUpdates when we don't have a reference to
-// the renderer. Such as when we're dispatching events or if third party
-// libraries need to call batchedUpdates. Eventually, this API will go away when
-// everything is batched by default. We'll then have a similar API to opt-out of
-// scheduled work and instead do synchronous work.
-
-// Defaults
-var _batchedUpdates = function(fn, bookkeeping) {
-  return fn(bookkeeping);
-};
-var _interactiveUpdates = function(fn, a, b) {
-  return fn(a, b);
-};
-var _flushInteractiveUpdates = function() {};
-
-var injection$2 = {
-  injectRenderer: function(renderer) {
-    _batchedUpdates = renderer.batchedUpdates;
-    _interactiveUpdates = renderer.interactiveUpdates;
-    _flushInteractiveUpdates = renderer.flushInteractiveUpdates;
-  }
-};
-
-// TODO: this is special because it gets imported during build.
-
-var ReactVersion = "16.3.2";
-
-// Modules provided by RN:
-var emptyObject$1 = {};
-
-/**
- * Create a payload that contains all the updates between two sets of props.
- *
- * These helpers are all encapsulated into a single module, because they use
- * mutation as a performance optimization which leads to subtle shared
- * dependencies between the code paths. To avoid this mutable state leaking
- * across modules, I've kept them isolated to this module.
- */
-
-// Tracks removed keys
-var removedKeys = null;
-var removedKeyCount = 0;
-
-function defaultDiffer(prevProp, nextProp) {
-  if (typeof nextProp !== "object" || nextProp === null) {
-    // Scalars have already been checked for equality
-    return true;
-  } else {
-    // For objects and arrays, the default diffing algorithm is a deep compare
-    return deepDiffer(prevProp, nextProp);
-  }
-}
-
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node)) {
-    var i = node.length;
-    while (i-- && removedKeyCount > 0) {
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
-    }
-  } else if (node && removedKeyCount > 0) {
-    var obj = node;
-    for (var propKey in removedKeys) {
-      if (!removedKeys[propKey]) {
-        continue;
-      }
-      var _nextProp = obj[propKey];
-      if (_nextProp === undefined) {
-        continue;
-      }
-
-      var attributeConfig = validAttributes[propKey];
-      if (!attributeConfig) {
-        continue; // not a valid native prop
-      }
-
-      if (typeof _nextProp === "function") {
-        _nextProp = true;
-      }
-      if (typeof _nextProp === "undefined") {
-        _nextProp = null;
-      }
-
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = _nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(_nextProp)
-            : _nextProp;
-        updatePayload[propKey] = nextValue;
-      }
-      removedKeys[propKey] = false;
-      removedKeyCount--;
-    }
-  }
-}
-
-function diffNestedArrayProperty(
-  updatePayload,
-  prevArray,
-  nextArray,
-  validAttributes
-) {
-  var minLength =
-    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
-  var i = void 0;
-  for (i = 0; i < minLength; i++) {
-    // Diff any items in the array in the forward direction. Repeated keys
-    // will be overwritten by later values.
-    updatePayload = diffNestedProperty(
-      updatePayload,
-      prevArray[i],
-      nextArray[i],
-      validAttributes
-    );
-  }
-  for (; i < prevArray.length; i++) {
-    // Clear out all remaining properties.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevArray[i],
-      validAttributes
-    );
-  }
-  for (; i < nextArray.length; i++) {
-    // Add all remaining properties.
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextArray[i],
-      validAttributes
-    );
-  }
-  return updatePayload;
-}
-
-function diffNestedProperty(
-  updatePayload,
-  prevProp,
-  nextProp,
-  validAttributes
-) {
-  if (!updatePayload && prevProp === nextProp) {
-    // If no properties have been added, then we can bail out quickly on object
-    // equality.
-    return updatePayload;
-  }
-
-  if (!prevProp || !nextProp) {
-    if (nextProp) {
-      return addNestedProperty(updatePayload, nextProp, validAttributes);
-    }
-    if (prevProp) {
-      return clearNestedProperty(updatePayload, prevProp, validAttributes);
-    }
-    return updatePayload;
-  }
-
-  if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
-    // Both are leaves, we can diff the leaves.
-    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
-  }
-
-  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
-    // Both are arrays, we can diff the arrays.
-    return diffNestedArrayProperty(
-      updatePayload,
-      prevProp,
-      nextProp,
-      validAttributes
-    );
-  }
-
-  if (Array.isArray(prevProp)) {
-    return diffProperties(
-      updatePayload,
-      // $FlowFixMe - We know that this is always an object when the input is.
-      flattenStyle(prevProp),
-      // $FlowFixMe - We know that this isn't an array because of above flow.
-      nextProp,
-      validAttributes
-    );
-  }
-
-  return diffProperties(
-    updatePayload,
-    prevProp,
-    // $FlowFixMe - We know that this is always an object when the input is.
-    flattenStyle(nextProp),
-    validAttributes
-  );
-}
-
-/**
- * addNestedProperty takes a single set of props and valid attribute
- * attribute configurations. It processes each prop and adds it to the
- * updatePayload.
- */
-function addNestedProperty(updatePayload, nextProp, validAttributes) {
-  if (!nextProp) {
-    return updatePayload;
-  }
-
-  if (!Array.isArray(nextProp)) {
-    // Add each property of the leaf.
-    return addProperties(updatePayload, nextProp, validAttributes);
-  }
-
-  for (var i = 0; i < nextProp.length; i++) {
-    // Add all the properties of the array.
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextProp[i],
-      validAttributes
-    );
-  }
-
-  return updatePayload;
-}
-
-/**
- * clearNestedProperty takes a single set of props and valid attributes. It
- * adds a null sentinel to the updatePayload, for each prop key.
- */
-function clearNestedProperty(updatePayload, prevProp, validAttributes) {
-  if (!prevProp) {
-    return updatePayload;
-  }
-
-  if (!Array.isArray(prevProp)) {
-    // Add each property of the leaf.
-    return clearProperties(updatePayload, prevProp, validAttributes);
-  }
-
-  for (var i = 0; i < prevProp.length; i++) {
-    // Add all the properties of the array.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevProp[i],
-      validAttributes
-    );
-  }
-  return updatePayload;
-}
-
-/**
- * diffProperties takes two sets of props and a set of valid attributes
- * and write to updatePayload the values that changed or were deleted.
- * If no updatePayload is provided, a new one is created and returned if
- * anything changed.
- */
-function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
-  var attributeConfig = void 0;
-  var nextProp = void 0;
-  var prevProp = void 0;
-
-  for (var propKey in nextProps) {
-    attributeConfig = validAttributes[propKey];
-    if (!attributeConfig) {
-      continue; // not a valid native prop
-    }
-
-    prevProp = prevProps[propKey];
-    nextProp = nextProps[propKey];
-
-    // functions are converted to booleans as markers that the associated
-    // events should be sent from native.
-    if (typeof nextProp === "function") {
-      nextProp = true;
-      // If nextProp is not a function, then don't bother changing prevProp
-      // since nextProp will win and go into the updatePayload regardless.
-      if (typeof prevProp === "function") {
-        prevProp = true;
-      }
-    }
-
-    // An explicit value of undefined is treated as a null because it overrides
-    // any other preceding value.
-    if (typeof nextProp === "undefined") {
-      nextProp = null;
-      if (typeof prevProp === "undefined") {
-        prevProp = null;
-      }
-    }
-
-    if (removedKeys) {
-      removedKeys[propKey] = false;
-    }
-
-    if (updatePayload && updatePayload[propKey] !== undefined) {
-      // Something else already triggered an update to this key because another
-      // value diffed. Since we're now later in the nested arrays our value is
-      // more important so we need to calculate it and override the existing
-      // value. It doesn't matter if nothing changed, we'll set it anyway.
-
-      // Pattern match on: attributeConfig
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(nextProp)
-            : nextProp;
-        updatePayload[propKey] = nextValue;
-      }
-      continue;
-    }
-
-    if (prevProp === nextProp) {
-      continue; // nothing changed
-    }
-
-    // Pattern match on: attributeConfig
-    if (typeof attributeConfig !== "object") {
-      // case: !Object is the default case
-      if (defaultDiffer(prevProp, nextProp)) {
-        // a normal leaf has changed
-        (updatePayload || (updatePayload = {}))[propKey] = nextProp;
-      }
-    } else if (
-      typeof attributeConfig.diff === "function" ||
-      typeof attributeConfig.process === "function"
-    ) {
-      // case: CustomAttributeConfiguration
-      var shouldUpdate =
-        prevProp === undefined ||
-        (typeof attributeConfig.diff === "function"
-          ? attributeConfig.diff(prevProp, nextProp)
-          : defaultDiffer(prevProp, nextProp));
-      if (shouldUpdate) {
-        var _nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(nextProp)
-            : nextProp;
-        (updatePayload || (updatePayload = {}))[propKey] = _nextValue;
-      }
-    } else {
-      // default: fallthrough case when nested properties are defined
-      removedKeys = null;
-      removedKeyCount = 0;
-      // We think that attributeConfig is not CustomAttributeConfiguration at
-      // this point so we assume it must be AttributeConfiguration.
-      updatePayload = diffNestedProperty(
-        updatePayload,
-        prevProp,
-        nextProp,
-        attributeConfig
-      );
-      if (removedKeyCount > 0 && updatePayload) {
-        restoreDeletedValuesInNestedArray(
-          updatePayload,
-          nextProp,
-          attributeConfig
-        );
-        removedKeys = null;
-      }
-    }
-  }
-
-  // Also iterate through all the previous props to catch any that have been
-  // removed and make sure native gets the signal so it can reset them to the
-  // default.
-  for (var _propKey in prevProps) {
-    if (nextProps[_propKey] !== undefined) {
-      continue; // we've already covered this key in the previous pass
-    }
-    attributeConfig = validAttributes[_propKey];
-    if (!attributeConfig) {
-      continue; // not a valid native prop
-    }
-
-    if (updatePayload && updatePayload[_propKey] !== undefined) {
-      // This was already updated to a diff result earlier.
-      continue;
-    }
-
-    prevProp = prevProps[_propKey];
-    if (prevProp === undefined) {
-      continue; // was already empty anyway
-    }
-    // Pattern match on: attributeConfig
-    if (
-      typeof attributeConfig !== "object" ||
-      typeof attributeConfig.diff === "function" ||
-      typeof attributeConfig.process === "function"
-    ) {
-      // case: CustomAttributeConfiguration | !Object
-      // Flag the leaf property for removal by sending a sentinel.
-      (updatePayload || (updatePayload = {}))[_propKey] = null;
-      if (!removedKeys) {
-        removedKeys = {};
-      }
-      if (!removedKeys[_propKey]) {
-        removedKeys[_propKey] = true;
-        removedKeyCount++;
-      }
-    } else {
-      // default:
-      // This is a nested attribute configuration where all the properties
-      // were removed so we need to go through and clear out all of them.
-      updatePayload = clearNestedProperty(
-        updatePayload,
-        prevProp,
-        attributeConfig
-      );
-    }
-  }
-  return updatePayload;
-}
-
-/**
- * addProperties adds all the valid props to the payload after being processed.
- */
-function addProperties(updatePayload, props, validAttributes) {
-  // TODO: Fast path
-  return diffProperties(updatePayload, emptyObject$1, props, validAttributes);
-}
-
-/**
- * clearProperties clears all the previous props by adding a null sentinel
- * to the payload for each valid key.
- */
-function clearProperties(updatePayload, prevProps, validAttributes) {
-  // TODO: Fast path
-  return diffProperties(
-    updatePayload,
-    prevProps,
-    emptyObject$1,
-    validAttributes
-  );
-}
-
-function create(props, validAttributes) {
-  return addProperties(
-    null, // updatePayload
-    props,
-    validAttributes
-  );
-}
-
-function diff(prevProps, nextProps, validAttributes) {
-  return diffProperties(
-    null, // updatePayload
-    prevProps,
-    nextProps,
-    validAttributes
-  );
-}
-
-/**
- * In the future, we should cleanup callbacks by cancelling them instead of
- * using this.
- */
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (!callback) {
-      return undefined;
-    }
-    if (typeof context.__isMounted === "boolean") {
-      // TODO(gaearon): this is gross and should be removed.
-      // It is currently necessary because View uses createClass,
-      // and so any measure() calls on View (which are done by React
-      // DevTools) trigger the isMounted() deprecation warning.
-      if (!context.__isMounted) {
-        return undefined;
-      }
-      // The else branch is important so that we don't
-      // trigger the deprecation warning by calling isMounted.
-    } else if (typeof context.isMounted === "function") {
-      if (!context.isMounted()) {
-        return undefined;
-      }
-    }
-    return callback.apply(context, arguments);
-  };
-}
-
-function throwOnStylesProp(component, props) {
-  if (props.styles !== undefined) {
-    var owner = component._owner || null;
-    var name = component.constructor.displayName;
-    var msg =
-      "`styles` is not a supported property of `" +
-      name +
-      "`, did " +
-      "you mean `style` (singular)?";
-    if (owner && owner.constructor && owner.constructor.displayName) {
-      msg +=
-        "\n\nCheck the `" +
-        owner.constructor.displayName +
-        "` parent " +
-        " component.";
-    }
-    throw new Error(msg);
-  }
-}
-
-function warnForStyleProps(props, validAttributes) {
-  for (var key in validAttributes.style) {
-    if (!(validAttributes[key] || props[key] === undefined)) {
-      console.error(
-        "You are setting the style `{ " +
-          key +
-          ": ... }` as a prop. You " +
-          "should nest it in a style object. " +
-          "E.g. `{ style: { " +
-          key +
-          ": ... } }`"
-      );
-    }
-  }
-}
-
-// Modules provided by RN:
-var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
-  /**
-   * `NativeMethodsMixin` provides methods to access the underlying native
-   * component directly. This can be useful in cases when you want to focus
-   * a view or measure its on-screen dimensions, for example.
-   *
-   * The methods described here are available on most of the default components
-   * provided by React Native. Note, however, that they are *not* available on
-   * composite components that aren't directly backed by a native view. This will
-   * generally include most components that you define in your own app. For more
-   * information, see [Direct
-   * Manipulation](docs/direct-manipulation.html).
-   *
-   * Note the Flow $Exact<> syntax is required to support mixins.
-   * React createClass mixins can only be used with exact types.
-   */
-  var NativeMethodsMixin = {
-    /**
-     * Determines the location on screen, width, and height of the given view and
-     * returns the values via an async callback. If successful, the callback will
-     * be called with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *  - pageX
-     *  - pageY
-     *
-     * Note that these measurements are not available until after the rendering
-     * has been completed in native. If you need the measurements as soon as
-     * possible, consider using the [`onLayout`
-     * prop](docs/view.html#onlayout) instead.
-     */
-    measure: function(callback) {
-      UIManager.measure(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    },
-
-    /**
-     * Determines the location of the given view in the window and returns the
-     * values via an async callback. If the React root view is embedded in
-     * another native view, this will give you the absolute coordinates. If
-     * successful, the callback will be called with the following
-     * arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *
-     * Note that these measurements are not available until after the rendering
-     * has been completed in native.
-     */
-    measureInWindow: function(callback) {
-      UIManager.measureInWindow(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    },
-
-    /**
-     * Like [`measure()`](#measure), but measures the view relative an ancestor,
-     * specified as `relativeToNativeNode`. This means that the returned x, y
-     * are relative to the origin x, y of the ancestor view.
-     *
-     * As always, to obtain a native node handle for a component, you can use
-     * `findNodeHandle(component)`.
-     */
-    measureLayout: function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail /* currently unused */
-    ) {
-      UIManager.measureLayout(
-        findNodeHandle(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    },
-
-    /**
-     * This function sends props straight to native. They will not participate in
-     * future diff process - this means that if you do not include them in the
-     * next render, they will remain active (see [Direct
-     * Manipulation](docs/direct-manipulation.html)).
-     */
-    setNativeProps: function(nativeProps) {
-      // Class components don't have viewConfig -> validateAttributes.
-      // Nor does it make sense to set native props on a non-native component.
-      // Instead, find the nearest host component and set props on it.
-      // Use findNodeHandle() rather than findNodeHandle() because
-      // We want the instance/wrapper (not the native tag).
-      var maybeInstance = void 0;
-
-      // Fiber errors if findNodeHandle is called for an umounted component.
-      // Tests using ReactTestRenderer will trigger this case indirectly.
-      // Mimicking stack behavior, we should silently ignore this case.
-      // TODO Fix ReactTestRenderer so we can remove this try/catch.
-      try {
-        maybeInstance = findHostInstance(this);
-      } catch (error) {}
-
-      // If there is no host component beneath this we should fail silently.
-      // This is not an error; it could mean a class component rendered null.
-      if (maybeInstance == null) {
-        return;
-      }
-
-      var viewConfig = maybeInstance.viewConfig;
-
-      {
-        warnForStyleProps(nativeProps, viewConfig.validAttributes);
-      }
-
-      var updatePayload = create(nativeProps, viewConfig.validAttributes);
-
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          updatePayload
-        );
-      }
-    },
-
-    /**
-     * Requests focus for the given input or view. The exact behavior triggered
-     * will depend on the platform and type of view.
-     */
-    focus: function() {
-      TextInputState.focusTextInput(findNodeHandle(this));
-    },
-
-    /**
-     * Removes focus from an input or view. This is the opposite of `focus()`.
-     */
-    blur: function() {
-      TextInputState.blurTextInput(findNodeHandle(this));
-    }
-  };
-
-  {
-    // hide this from Flow since we can't define these properties outside of
-    // true without actually implementing them (setting them to undefined
-    // isn't allowed by ReactClass)
-    var NativeMethodsMixin_DEV = NativeMethodsMixin;
-    invariant(
-      !NativeMethodsMixin_DEV.componentWillMount &&
-        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
-        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
-        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
-      "Do not override existing functions."
-    );
-    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
-    // Once these lifecycles have been remove from the reconciler.
-    NativeMethodsMixin_DEV.componentWillMount = function() {
-      throwOnStylesProp(this, this.props);
-    };
-    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
-      throwOnStylesProp(this, newProps);
-    };
-    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
-      throwOnStylesProp(this, this.props);
-    };
-    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
-      newProps
-    ) {
-      throwOnStylesProp(this, newProps);
-    };
-
-    // React may warn about cWM/cWRP/cWU methods being deprecated.
-    // Add a flag to suppress these warnings for this special case.
-    // TODO (bvaughn) Remove this flag once the above methods have been removed.
-    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
-    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
-  }
-
-  return NativeMethodsMixin;
-};
-
-function _classCallCheck(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
-  }
-}
-
-function _possibleConstructorReturn(self, call) {
-  if (!self) {
-    throw new ReferenceError(
-      "this hasn't been initialised - super() hasn't been called"
-    );
-  }
-  return call && (typeof call === "object" || typeof call === "function")
-    ? call
-    : self;
-}
-
-function _inherits(subClass, superClass) {
-  if (typeof superClass !== "function" && superClass !== null) {
-    throw new TypeError(
-      "Super expression must either be null or a function, not " +
-        typeof superClass
-    );
-  }
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: false,
-      writable: true,
-      configurable: true
-    }
-  });
-  if (superClass)
-    Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass);
-}
-
-// Modules provided by RN:
-var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
-  /**
-   * Superclass that provides methods to access the underlying native component.
-   * This can be useful when you want to focus a view or measure its dimensions.
-   *
-   * Methods implemented by this class are available on most default components
-   * provided by React Native. However, they are *not* available on composite
-   * components that are not directly backed by a native view. For more
-   * information, see [Direct Manipulation](docs/direct-manipulation.html).
-   *
-   * @abstract
-   */
-  var ReactNativeComponent = (function(_React$Component) {
-    _inherits(ReactNativeComponent, _React$Component);
-
-    function ReactNativeComponent() {
-      _classCallCheck(this, ReactNativeComponent);
-
-      return _possibleConstructorReturn(
-        this,
-        _React$Component.apply(this, arguments)
-      );
-    }
-
-    /**
-     * Removes focus. This is the opposite of `focus()`.
-     */
-
-    /**
-     * Due to bugs in Flow's handling of React.createClass, some fields already
-     * declared in the base class need to be redeclared below.
-     */
-    ReactNativeComponent.prototype.blur = function blur() {
-      TextInputState.blurTextInput(findNodeHandle(this));
-    };
-
-    /**
-     * Requests focus. The exact behavior depends on the platform and view.
-     */
-
-    ReactNativeComponent.prototype.focus = function focus() {
-      TextInputState.focusTextInput(findNodeHandle(this));
-    };
-
-    /**
-     * Measures the on-screen location and dimensions. If successful, the callback
-     * will be called asynchronously with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *  - pageX
-     *  - pageY
-     *
-     * These values are not available until after natives rendering completes. If
-     * you need the measurements as soon as possible, consider using the
-     * [`onLayout` prop](docs/view.html#onlayout) instead.
-     */
-
-    ReactNativeComponent.prototype.measure = function measure(callback) {
-      UIManager.measure(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    };
-
-    /**
-     * Measures the on-screen location and dimensions. Even if the React Native
-     * root view is embedded within another native view, this method will give you
-     * the absolute coordinates measured from the window. If successful, the
-     * callback will be called asynchronously with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *
-     * These values are not available until after natives rendering completes.
-     */
-
-    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
-      callback
-    ) {
-      UIManager.measureInWindow(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    };
-
-    /**
-     * Similar to [`measure()`](#measure), but the resulting location will be
-     * relative to the supplied ancestor's location.
-     *
-     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
-     */
-
-    ReactNativeComponent.prototype.measureLayout = function measureLayout(
-      relativeToNativeNode,
-      onSuccess,
-      onFail /* currently unused */
-    ) {
-      UIManager.measureLayout(
-        findNodeHandle(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    };
-
-    /**
-     * This function sends props straight to native. They will not participate in
-     * future diff process - this means that if you do not include them in the
-     * next render, they will remain active (see [Direct
-     * Manipulation](docs/direct-manipulation.html)).
-     */
-
-    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
-      nativeProps
-    ) {
-      // Class components don't have viewConfig -> validateAttributes.
-      // Nor does it make sense to set native props on a non-native component.
-      // Instead, find the nearest host component and set props on it.
-      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
-      // We want the instance/wrapper (not the native tag).
-      var maybeInstance = void 0;
-
-      // Fiber errors if findNodeHandle is called for an umounted component.
-      // Tests using ReactTestRenderer will trigger this case indirectly.
-      // Mimicking stack behavior, we should silently ignore this case.
-      // TODO Fix ReactTestRenderer so we can remove this try/catch.
-      try {
-        maybeInstance = findHostInstance(this);
-      } catch (error) {}
-
-      // If there is no host component beneath this we should fail silently.
-      // This is not an error; it could mean a class component rendered null.
-      if (maybeInstance == null) {
-        return;
-      }
-
-      var viewConfig =
-        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
-
-      var updatePayload = create(nativeProps, viewConfig.validAttributes);
-
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          updatePayload
-        );
-      }
-    };
-
-    return ReactNativeComponent;
-  })(React.Component);
-
-  // eslint-disable-next-line no-unused-expressions
-
-  return ReactNativeComponent;
-};
-
-var hasNativePerformanceNow =
-  typeof performance === "object" && typeof performance.now === "function";
-
-var now = hasNativePerformanceNow
-  ? function() {
-      return performance.now();
-    }
-  : function() {
-      return Date.now();
-    };
-
-var scheduledCallback = null;
-var frameDeadline = 0;
-
-var frameDeadlineObject = {
-  timeRemaining: function() {
-    return frameDeadline - now();
-  },
-  didTimeout: false
-};
-
-function setTimeoutCallback() {
-  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
-  // React API probably changing to boolean rather than time remaining.
-  // Longer-term plan is to rewrite this using shared memory,
-  // And just return the value of the bit as the boolean.
-  frameDeadline = now() + 5;
-
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  if (callback !== null) {
-    callback(frameDeadlineObject);
-  }
-}
-
-// RN has a poor polyfill for requestIdleCallback so we aren't using it.
-// This implementation is only intended for short-term use anyway.
-// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
-function scheduleDeferredCallback(callback) {
-  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
-  scheduledCallback = callback;
-  return setTimeout(setTimeoutCallback, 1);
-}
-
-function cancelDeferredCallback(callbackID) {
-  scheduledCallback = null;
-  clearTimeout(callbackID);
-}
-
-/**
- * `ReactInstanceMap` maintains a mapping from a public facing stateful
- * instance (key) and the internal representation (value). This allows public
- * methods to accept the user facing instance as an argument and map them back
- * to internal methods.
- *
- * Note that this module is currently shared and assumed to be stateless.
- * If this becomes an actual Map, that will break.
- */
-
-/**
- * This API should be called `delete` but we'd have to make sure to always
- * transform these to strings for IE support. When this transform is fully
- * supported we can rename it.
- */
-
-function get$1(key) {
-  return key._reactInternalFiber;
-}
-
-function set(key, value) {
-  key._reactInternalFiber = value;
-}
-
-var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
-
-var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
-var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
-
-function getComponentName(fiber) {
-  var type = fiber.type;
-
-  if (typeof type === "function") {
-    return type.displayName || type.name;
-  }
-  if (typeof type === "string") {
-    return type;
-  }
-  switch (type) {
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
-  }
-  if (typeof type === "object" && type !== null) {
-    switch (type.$$typeof) {
-      case REACT_FORWARD_REF_TYPE:
-        var functionName = type.render.displayName || type.render.name || "";
-        return functionName !== ""
-          ? "ForwardRef(" + functionName + ")"
-          : "ForwardRef";
-    }
-  }
-  return null;
-}
-
-// Don't change these two values. They're used by React Dev Tools.
-var NoEffect = /*              */ 0;
-var PerformedWork = /*         */ 1;
-
-// You can change the rest (and add more).
-var Placement = /*             */ 2;
-var Update = /*                */ 4;
-var PlacementAndUpdate = /*    */ 6;
-var Deletion = /*              */ 8;
-var ContentReset = /*          */ 16;
-var Callback = /*              */ 32;
-var DidCapture = /*            */ 64;
-var Ref = /*                   */ 128;
-var ErrLog = /*                */ 256;
-var Snapshot = /*              */ 2048;
-
-// Union of all host effects
-var HostEffectMask = /*        */ 2559;
-
-var Incomplete = /*            */ 512;
-var ShouldCapture = /*         */ 1024;
-
-var MOUNTING = 1;
-var MOUNTED = 2;
-var UNMOUNTED = 3;
-
-function isFiberMountedImpl(fiber) {
-  var node = fiber;
-  if (!fiber.alternate) {
-    // If there is no alternate, this might be a new tree that isn't inserted
-    // yet. If it is, then it will have a pending insertion effect on it.
-    if ((node.effectTag & Placement) !== NoEffect) {
-      return MOUNTING;
-    }
-    while (node["return"]) {
-      node = node["return"];
-      if ((node.effectTag & Placement) !== NoEffect) {
-        return MOUNTING;
-      }
-    }
-  } else {
-    while (node["return"]) {
-      node = node["return"];
-    }
-  }
-  if (node.tag === HostRoot) {
-    // TODO: Check if this was a nested HostRoot when used with
-    // renderContainerIntoSubtree.
-    return MOUNTED;
-  }
-  // If we didn't hit the root, that means that we're in an disconnected tree
-  // that has been unmounted.
-  return UNMOUNTED;
-}
-
-function isFiberMounted(fiber) {
-  return isFiberMountedImpl(fiber) === MOUNTED;
-}
-
-function isMounted(component) {
-  {
-    var owner = ReactCurrentOwner.current;
-    if (owner !== null && owner.tag === ClassComponent) {
-      var ownerFiber = owner;
-      var instance = ownerFiber.stateNode;
-      !instance._warnedAboutRefsInRender
-        ? warning(
-            false,
-            "%s is accessing isMounted inside its render() function. " +
-              "render() should be a pure function of props and state. It should " +
-              "never access something that requires stale data from the previous " +
-              "render, such as refs. Move this logic to componentDidMount and " +
-              "componentDidUpdate instead.",
-            getComponentName(ownerFiber) || "A component"
-          )
-        : void 0;
-      instance._warnedAboutRefsInRender = true;
-    }
-  }
-
-  var fiber = get$1(component);
-  if (!fiber) {
-    return false;
-  }
-  return isFiberMountedImpl(fiber) === MOUNTED;
-}
-
-function assertIsMounted(fiber) {
-  invariant(
-    isFiberMountedImpl(fiber) === MOUNTED,
-    "Unable to find node on an unmounted component."
-  );
-}
-
-function findCurrentFiberUsingSlowPath(fiber) {
-  var alternate = fiber.alternate;
-  if (!alternate) {
-    // If there is no alternate, then we only need to check if it is mounted.
-    var state = isFiberMountedImpl(fiber);
-    invariant(
-      state !== UNMOUNTED,
-      "Unable to find node on an unmounted component."
-    );
-    if (state === MOUNTING) {
-      return null;
-    }
-    return fiber;
-  }
-  // If we have two possible branches, we'll walk backwards up to the root
-  // to see what path the root points to. On the way we may hit one of the
-  // special cases and we'll deal with them.
-  var a = fiber;
-  var b = alternate;
-  while (true) {
-    var parentA = a["return"];
-    var parentB = parentA ? parentA.alternate : null;
-    if (!parentA || !parentB) {
-      // We're at the root.
-      break;
-    }
-
-    // If both copies of the parent fiber point to the same child, we can
-    // assume that the child is current. This happens when we bailout on low
-    // priority: the bailed out fiber's child reuses the current child.
-    if (parentA.child === parentB.child) {
-      var child = parentA.child;
-      while (child) {
-        if (child === a) {
-          // We've determined that A is the current branch.
-          assertIsMounted(parentA);
-          return fiber;
-        }
-        if (child === b) {
-          // We've determined that B is the current branch.
-          assertIsMounted(parentA);
-          return alternate;
-        }
-        child = child.sibling;
-      }
-      // We should never have an alternate for any mounting node. So the only
-      // way this could possibly happen is if this was unmounted, if at all.
-      invariant(false, "Unable to find node on an unmounted component.");
-    }
-
-    if (a["return"] !== b["return"]) {
-      // The return pointer of A and the return pointer of B point to different
-      // fibers. We assume that return pointers never criss-cross, so A must
-      // belong to the child set of A.return, and B must belong to the child
-      // set of B.return.
-      a = parentA;
-      b = parentB;
-    } else {
-      // The return pointers point to the same fiber. We'll have to use the
-      // default, slow path: scan the child sets of each parent alternate to see
-      // which child belongs to which set.
-      //
-      // Search parent A's child set
-      var didFindChild = false;
-      var _child = parentA.child;
-      while (_child) {
-        if (_child === a) {
-          didFindChild = true;
-          a = parentA;
-          b = parentB;
-          break;
-        }
-        if (_child === b) {
-          didFindChild = true;
-          b = parentA;
-          a = parentB;
-          break;
-        }
-        _child = _child.sibling;
-      }
-      if (!didFindChild) {
-        // Search parent B's child set
-        _child = parentB.child;
-        while (_child) {
-          if (_child === a) {
-            didFindChild = true;
-            a = parentB;
-            b = parentA;
-            break;
-          }
-          if (_child === b) {
-            didFindChild = true;
-            b = parentB;
-            a = parentA;
-            break;
-          }
-          _child = _child.sibling;
-        }
-        invariant(
-          didFindChild,
-          "Child was not found in either parent set. This indicates a bug " +
-            "in React related to the return pointer. Please file an issue."
-        );
-      }
-    }
-
-    invariant(
-      a.alternate === b,
-      "Return fibers should always be each others' alternates. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  // If the root is not a host container, we're in a disconnected tree. I.e.
-  // unmounted.
-  invariant(
-    a.tag === HostRoot,
-    "Unable to find node on an unmounted component."
-  );
-  if (a.stateNode.current === a) {
-    // We've determined that A is the current branch.
-    return fiber;
-  }
-  // Otherwise B has to be current branch.
-  return alternate;
-}
-
-function findCurrentHostFiber(parent) {
-  var currentParent = findCurrentFiberUsingSlowPath(parent);
-  if (!currentParent) {
-    return null;
-  }
-
-  // Next we'll drill down this component to find the first HostComponent/Text.
-  var node = currentParent;
-  while (true) {
-    if (node.tag === HostComponent || node.tag === HostText) {
-      return node;
-    } else if (node.child) {
-      node.child["return"] = node;
-      node = node.child;
-      continue;
-    }
-    if (node === currentParent) {
-      return null;
-    }
-    while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
-        return null;
-      }
-      node = node["return"];
-    }
-    node.sibling["return"] = node["return"];
-    node = node.sibling;
-  }
-  // Flow needs the return null here, but ESLint complains about it.
-  // eslint-disable-next-line no-unreachable
-  return null;
-}
-
-function findCurrentHostFiberWithNoPortals(parent) {
-  var currentParent = findCurrentFiberUsingSlowPath(parent);
-  if (!currentParent) {
-    return null;
-  }
-
-  // Next we'll drill down this component to find the first HostComponent/Text.
-  var node = currentParent;
-  while (true) {
-    if (node.tag === HostComponent || node.tag === HostText) {
-      return node;
-    } else if (node.child && node.tag !== HostPortal) {
-      node.child["return"] = node;
-      node = node.child;
-      continue;
-    }
-    if (node === currentParent) {
-      return null;
-    }
-    while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
-        return null;
-      }
-      node = node["return"];
-    }
-    node.sibling["return"] = node["return"];
-    node = node.sibling;
-  }
-  // Flow needs the return null here, but ESLint complains about it.
-  // eslint-disable-next-line no-unreachable
-  return null;
-}
-
-// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
-// Math.pow(2, 30) - 1
-// 0b111111111111111111111111111111
-var MAX_SIGNED_31_BIT_INT = 1073741823;
-
-// TODO: Use an opaque type once ESLint et al support the syntax
-
-var NoWork = 0;
-var Sync = 1;
-var Never = MAX_SIGNED_31_BIT_INT;
-
-var UNIT_SIZE = 10;
-var MAGIC_NUMBER_OFFSET = 2;
-
-// 1 unit of expiration time represents 10ms.
-function msToExpirationTime(ms) {
-  // Always add an offset so that we don't clash with the magic number for NoWork.
-  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
-}
-
-function expirationTimeToMs(expirationTime) {
-  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
-}
-
-function ceiling(num, precision) {
-  return (((num / precision) | 0) + 1) * precision;
-}
-
-function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
-  return ceiling(
-    currentTime + expirationInMs / UNIT_SIZE,
-    bucketSizeMs / UNIT_SIZE
-  );
-}
-
-var NoContext = 0;
-var AsyncMode = 1;
-var StrictMode = 2;
-
-var hasBadMapPolyfill = void 0;
-
-{
-  hasBadMapPolyfill = false;
-  try {
-    var nonExtensibleObject = Object.preventExtensions({});
-    var testMap = new Map([[nonExtensibleObject, null]]);
-    var testSet = new Set([nonExtensibleObject]);
-    // This is necessary for Rollup to not consider these unused.
-    // https://github.com/rollup/rollup/issues/1771
-    // TODO: we can remove these if Rollup fixes the bug.
-    testMap.set(0, 0);
-    testSet.add(0);
-  } catch (e) {
-    // TODO: Consider warning about bad polyfills
-    hasBadMapPolyfill = true;
-  }
-}
-
-// A Fiber is work on a Component that needs to be done or was done. There can
-// be more than one per component.
-
-var debugCounter = void 0;
-
-{
-  debugCounter = 1;
-}
-
-function FiberNode(tag, pendingProps, key, mode) {
-  // Instance
-  this.tag = tag;
-  this.key = key;
-  this.type = null;
-  this.stateNode = null;
-
-  // Fiber
-  this["return"] = null;
-  this.child = null;
-  this.sibling = null;
-  this.index = 0;
-
-  this.ref = null;
-
-  this.pendingProps = pendingProps;
-  this.memoizedProps = null;
-  this.updateQueue = null;
-  this.memoizedState = null;
-
-  this.mode = mode;
-
-  // Effects
-  this.effectTag = NoEffect;
-  this.nextEffect = null;
-
-  this.firstEffect = null;
-  this.lastEffect = null;
-
-  this.expirationTime = NoWork;
-
-  this.alternate = null;
-
-  {
-    this._debugID = debugCounter++;
-    this._debugSource = null;
-    this._debugOwner = null;
-    this._debugIsCurrentlyTiming = false;
-    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
-      Object.preventExtensions(this);
-    }
-  }
-}
-
-// This is a constructor function, rather than a POJO constructor, still
-// please ensure we do the following:
-// 1) Nobody should add any instance methods on this. Instance methods can be
-//    more difficult to predict when they get optimized and they are almost
-//    never inlined properly in static compilers.
-// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
-//    always know when it is a fiber.
-// 3) We might want to experiment with using numeric keys since they are easier
-//    to optimize in a non-JIT environment.
-// 4) We can easily go from a constructor to a createFiber object literal if that
-//    is faster.
-// 5) It should be easy to port this to a C struct and keep a C implementation
-//    compatible.
-var createFiber = function(tag, pendingProps, key, mode) {
-  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
-  return new FiberNode(tag, pendingProps, key, mode);
-};
-
-function shouldConstruct(Component) {
-  return !!(Component.prototype && Component.prototype.isReactComponent);
-}
-
-// This is used to create an alternate fiber to do work on.
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  if (workInProgress === null) {
-    // We use a double buffering pooling technique because we know that we'll
-    // only ever need at most two versions of a tree. We pool the "other" unused
-    // node that we're free to reuse. This is lazily created to avoid allocating
-    // extra objects for things that are never updated. It also allow us to
-    // reclaim the extra memory if needed.
-    workInProgress = createFiber(
-      current.tag,
-      pendingProps,
-      current.key,
-      current.mode
-    );
-    workInProgress.type = current.type;
-    workInProgress.stateNode = current.stateNode;
-
-    {
-      // DEV-only fields
-      workInProgress._debugID = current._debugID;
-      workInProgress._debugSource = current._debugSource;
-      workInProgress._debugOwner = current._debugOwner;
-    }
-
-    workInProgress.alternate = current;
-    current.alternate = workInProgress;
-  } else {
-    workInProgress.pendingProps = pendingProps;
-
-    // We already have an alternate.
-    // Reset the effect tag.
-    workInProgress.effectTag = NoEffect;
-
-    // The effect list is no longer valid.
-    workInProgress.nextEffect = null;
-    workInProgress.firstEffect = null;
-    workInProgress.lastEffect = null;
-  }
-
-  workInProgress.expirationTime = expirationTime;
-
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
-
-  // These will be overridden during the parent's reconciliation
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
-
-  return workInProgress;
-}
-
-function createHostRootFiber(isAsync) {
-  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
-  return createFiber(HostRoot, null, null, mode);
-}
-
-function createFiberFromElement(element, mode, expirationTime) {
-  var owner = null;
-  {
-    owner = element._owner;
-  }
-
-  var fiber = void 0;
-  var type = element.type;
-  var key = element.key;
-  var pendingProps = element.props;
-
-  var fiberTag = void 0;
-  if (typeof type === "function") {
-    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
-  } else if (typeof type === "string") {
-    fiberTag = HostComponent;
-  } else {
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          pendingProps.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= AsyncMode | StrictMode;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= StrictMode;
-        break;
-      case REACT_CALL_TYPE:
-        fiberTag = CallComponent;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = ReturnComponent;
-        break;
-      default: {
-        if (typeof type === "object" && type !== null) {
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = ContextProvider;
-              break;
-            case REACT_CONTEXT_TYPE:
-              // This is a consumer
-              fiberTag = ContextConsumer;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = ForwardRef;
-              break;
-            default:
-              if (typeof type.tag === "number") {
-                // Currently assumed to be a continuation and therefore is a
-                // fiber already.
-                // TODO: The yield system is currently broken for updates in
-                // some cases. The reified yield stores a fiber, but we don't
-                // know which fiber that is; the current or a workInProgress?
-                // When the continuation gets rendered here we don't know if we
-                // can reuse that fiber or if we need to clone it. There is
-                // probably a clever way to restructure this.
-                fiber = type;
-                fiber.pendingProps = pendingProps;
-                fiber.expirationTime = expirationTime;
-                return fiber;
-              } else {
-                throwOnInvalidElementType(type, owner);
-              }
-              break;
-          }
-        } else {
-          throwOnInvalidElementType(type, owner);
-        }
-      }
-    }
-  }
-
-  fiber = createFiber(fiberTag, pendingProps, key, mode);
-  fiber.type = type;
-  fiber.expirationTime = expirationTime;
-
-  {
-    fiber._debugSource = element._source;
-    fiber._debugOwner = element._owner;
-  }
-
-  return fiber;
-}
-
-function throwOnInvalidElementType(type, owner) {
-  var info = "";
-  {
-    if (
-      type === undefined ||
-      (typeof type === "object" &&
-        type !== null &&
-        Object.keys(type).length === 0)
-    ) {
-      info +=
-        " You likely forgot to export your component from the file " +
-        "it's defined in, or you might have mixed up default and " +
-        "named imports.";
-    }
-    var ownerName = owner ? getComponentName(owner) : null;
-    if (ownerName) {
-      info += "\n\nCheck the render method of `" + ownerName + "`.";
-    }
-  }
-  invariant(
-    false,
-    "Element type is invalid: expected a string (for built-in " +
-      "components) or a class/function (for composite components) " +
-      "but got: %s.%s",
-    type == null ? type : typeof type,
-    info
-  );
-}
-
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  var fiber = createFiber(Fragment, elements, key, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
-
-function createFiberFromText(content, mode, expirationTime) {
-  var fiber = createFiber(HostText, content, null, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
-
-function createFiberFromHostInstanceForDeletion() {
-  var fiber = createFiber(HostComponent, null, null, NoContext);
-  fiber.type = "DELETED";
-  return fiber;
-}
-
-function createFiberFromPortal(portal, mode, expirationTime) {
-  var pendingProps = portal.children !== null ? portal.children : [];
-  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null, // Used by persistent updates
-    implementation: portal.implementation
-  };
-  return fiber;
-}
-
-// Used for stashing WIP properties to replay failed work in DEV.
-function assignFiberPropertiesInDEV(target, source) {
-  if (target === null) {
-    // This Fiber's initial properties will always be overwritten.
-    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
-    target = createFiber(IndeterminateComponent, null, null, NoContext);
-  }
-
-  // This is intentionally written as a list of all properties.
-  // We tried to use Object.assign() instead but this is called in
-  // the hottest path, and Object.assign() was too slow:
-  // https://github.com/facebook/react/issues/12502
-  // This code is DEV-only so size is not a concern.
-
-  target.tag = source.tag;
-  target.key = source.key;
-  target.type = source.type;
-  target.stateNode = source.stateNode;
-  target["return"] = source["return"];
-  target.child = source.child;
-  target.sibling = source.sibling;
-  target.index = source.index;
-  target.ref = source.ref;
-  target.pendingProps = source.pendingProps;
-  target.memoizedProps = source.memoizedProps;
-  target.updateQueue = source.updateQueue;
-  target.memoizedState = source.memoizedState;
-  target.mode = source.mode;
-  target.effectTag = source.effectTag;
-  target.nextEffect = source.nextEffect;
-  target.firstEffect = source.firstEffect;
-  target.lastEffect = source.lastEffect;
-  target.expirationTime = source.expirationTime;
-  target.alternate = source.alternate;
-  target._debugID = source._debugID;
-  target._debugSource = source._debugSource;
-  target._debugOwner = source._debugOwner;
-  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
-  return target;
-}
-
-// TODO: This should be lifted into the renderer.
-
-function createFiberRoot(containerInfo, isAsync, hydrate) {
-  // Cyclic construction. This cheats the type system right now because
-  // stateNode is any.
-  var uninitializedFiber = createHostRootFiber(isAsync);
-  var root = {
-    current: uninitializedFiber,
-    containerInfo: containerInfo,
-    pendingChildren: null,
-    pendingCommitExpirationTime: NoWork,
-    finishedWork: null,
-    context: null,
-    pendingContext: null,
-    hydrate: hydrate,
-    remainingExpirationTime: NoWork,
-    firstBatch: null,
-    nextScheduledRoot: null
-  };
-  uninitializedFiber.stateNode = root;
-  return root;
-}
-
-var onCommitFiberRoot = null;
-var onCommitFiberUnmount = null;
-var hasLoggedError = false;
-
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {
-      if (true && !hasLoggedError) {
-        hasLoggedError = true;
-        warning(false, "React DevTools encountered an error: %s", err);
-      }
-    }
-  };
-}
-
-function injectInternals(internals) {
-  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
-    // No DevTools
-    return false;
-  }
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled) {
-    // This isn't a real property on the hook, but it can be set to opt out
-    // of DevTools integration and associated warnings and logs.
-    // https://github.com/facebook/react/issues/3877
-    return true;
-  }
-  if (!hook.supportsFiber) {
-    {
-      warning(
-        false,
-        "The installed version of React DevTools is too old and will not work " +
-          "with the current version of React. Please update React DevTools. " +
-          "https://fb.me/react-devtools"
-      );
-    }
-    // DevTools exists, even though it doesn't support Fiber.
-    return true;
-  }
-  try {
-    var rendererID = hook.inject(internals);
-    // We have successfully injected, so now it is safe to set up hooks.
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {
-    // Catch all errors because it is unsafe to throw during initialization.
-    {
-      warning(false, "React DevTools encountered an error: %s.", err);
-    }
-  }
-  // DevTools exists
-  return true;
-}
-
-function onCommitRoot(root) {
-  if (typeof onCommitFiberRoot === "function") {
-    onCommitFiberRoot(root);
-  }
-}
-
-function onCommitUnmount(fiber) {
-  if (typeof onCommitFiberUnmount === "function") {
-    onCommitFiberUnmount(fiber);
-  }
-}
-
-var describeComponentFrame = function(name, source, ownerName) {
-  return (
-    "\n    in " +
-    (name || "Unknown") +
-    (source
-      ? " (at " +
-        source.fileName.replace(/^.*[\\\/]/, "") +
-        ":" +
-        source.lineNumber +
-        ")"
-      : ownerName ? " (created by " + ownerName + ")" : "")
-  );
-};
-
-function describeFiber(fiber) {
-  switch (fiber.tag) {
-    case IndeterminateComponent:
-    case FunctionalComponent:
-    case ClassComponent:
-    case HostComponent:
-      var owner = fiber._debugOwner;
-      var source = fiber._debugSource;
-      var name = getComponentName(fiber);
-      var ownerName = null;
-      if (owner) {
-        ownerName = getComponentName(owner);
-      }
-      return describeComponentFrame(name, source, ownerName);
-    default:
-      return "";
-  }
-}
-
-// This function can only be called with a work-in-progress fiber and
-// only during begin or complete phase. Do not call it under any other
-// circumstances.
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  var node = workInProgress;
-  do {
-    info += describeFiber(node);
-    // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
-  } while (node);
-  return info;
-}
-
-/**
- * Forked from fbjs/warning:
- * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
- *
- * Only change is we use console.warn instead of console.error,
- * and do nothing when 'console' is not supported.
- * This really simplifies the code.
- * ---
- * Similar to invariant but only logs a warning if the condition is not met.
- * This can be used to log issues in development environments in critical
- * paths. Removing the logging code for production environments will keep the
- * same logic and follow the same code paths.
- */
-
-var lowPriorityWarning = function() {};
-
-{
-  var printWarning = function(format) {
-    for (
-      var _len = arguments.length,
-        args = Array(_len > 1 ? _len - 1 : 0),
-        _key = 1;
-      _key < _len;
-      _key++
-    ) {
-      args[_key - 1] = arguments[_key];
-    }
-
-    var argIndex = 0;
-    var message =
-      "Warning: " +
-      format.replace(/%s/g, function() {
-        return args[argIndex++];
-      });
-    if (typeof console !== "undefined") {
-      console.warn(message);
-    }
-    try {
-      // --- Welcome to debugging React ---
-      // This error was thrown as a convenience so that you can use this stack
-      // to find the callsite that caused this warning to fire.
-      throw new Error(message);
-    } catch (x) {}
-  };
-
-  lowPriorityWarning = function(condition, format) {
-    if (format === undefined) {
-      throw new Error(
-        "`warning(condition, format, ...args)` requires a warning " +
-          "message argument"
-      );
-    }
-    if (!condition) {
-      for (
-        var _len2 = arguments.length,
-          args = Array(_len2 > 2 ? _len2 - 2 : 0),
-          _key2 = 2;
-        _key2 < _len2;
-        _key2++
-      ) {
-        args[_key2 - 2] = arguments[_key2];
-      }
-
-      printWarning.apply(undefined, [format].concat(args));
-    }
-  };
-}
-
-var lowPriorityWarning$1 = lowPriorityWarning;
-
-var ReactStrictModeWarnings = {
-  discardPendingWarnings: function() {},
-  flushPendingDeprecationWarnings: function() {},
-  flushPendingUnsafeLifecycleWarnings: function() {},
-  recordDeprecationWarnings: function(fiber, instance) {},
-  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
-};
-
-{
-  var LIFECYCLE_SUGGESTIONS = {
-    UNSAFE_componentWillMount: "componentDidMount",
-    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
-    UNSAFE_componentWillUpdate: "componentDidUpdate"
-  };
-
-  var pendingComponentWillMountWarnings = [];
-  var pendingComponentWillReceivePropsWarnings = [];
-  var pendingComponentWillUpdateWarnings = [];
-  var pendingUnsafeLifecycleWarnings = new Map();
-
-  // Tracks components we have already warned about.
-  var didWarnAboutDeprecatedLifecycles = new Set();
-  var didWarnAboutUnsafeLifecycles = new Set();
-
-  var setToSortedString = function(set) {
-    var array = [];
-    set.forEach(function(value) {
-      array.push(value);
-    });
-    return array.sort().join(", ");
-  };
-
-  ReactStrictModeWarnings.discardPendingWarnings = function() {
-    pendingComponentWillMountWarnings = [];
-    pendingComponentWillReceivePropsWarnings = [];
-    pendingComponentWillUpdateWarnings = [];
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
-
-  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
-    pendingUnsafeLifecycleWarnings.forEach(function(
-      lifecycleWarningsMap,
-      strictRoot
-    ) {
-      var lifecyclesWarningMesages = [];
-
-      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
-        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
-        if (lifecycleWarnings.length > 0) {
-          var componentNames = new Set();
-          lifecycleWarnings.forEach(function(fiber) {
-            componentNames.add(getComponentName(fiber) || "Component");
-            didWarnAboutUnsafeLifecycles.add(fiber.type);
-          });
-
-          var formatted = lifecycle.replace("UNSAFE_", "");
-          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = setToSortedString(componentNames);
-
-          lifecyclesWarningMesages.push(
-            formatted +
-              ": Please update the following components to use " +
-              (suggestion + " instead: " + sortedComponentNames)
-          );
-        }
-      });
-
-      if (lifecyclesWarningMesages.length > 0) {
-        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
-          strictRoot
-        );
-
-        warning(
-          false,
-          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
-            "\n\n%s" +
-            "\n\nLearn more about this warning here:" +
-            "\nhttps://fb.me/react-strict-mode-warnings",
-          strictRootComponentStack,
-          lifecyclesWarningMesages.join("\n\n")
-        );
-      }
-    });
-
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
-
-  var getStrictRoot = function(fiber) {
-    var maybeStrictRoot = null;
-
-    while (fiber !== null) {
-      if (fiber.mode & StrictMode) {
-        maybeStrictRoot = fiber;
-      }
-
-      fiber = fiber["return"];
-    }
-
-    return maybeStrictRoot;
-  };
-
-  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
-    if (pendingComponentWillMountWarnings.length > 0) {
-      var uniqueNames = new Set();
-      pendingComponentWillMountWarnings.forEach(function(fiber) {
-        uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var sortedNames = setToSortedString(uniqueNames);
-
-      lowPriorityWarning$1(
-        false,
-        "componentWillMount is deprecated and will be removed in the next major version. " +
-          "Use componentDidMount instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillMount." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        sortedNames
-      );
-
-      pendingComponentWillMountWarnings = [];
-    }
-
-    if (pendingComponentWillReceivePropsWarnings.length > 0) {
-      var _uniqueNames = new Set();
-      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
-        _uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames = setToSortedString(_uniqueNames);
-
-      lowPriorityWarning$1(
-        false,
-        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
-          "Use static getDerivedStateFromProps instead." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames
-      );
-
-      pendingComponentWillReceivePropsWarnings = [];
-    }
-
-    if (pendingComponentWillUpdateWarnings.length > 0) {
-      var _uniqueNames2 = new Set();
-      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
-        _uniqueNames2.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames2 = setToSortedString(_uniqueNames2);
-
-      lowPriorityWarning$1(
-        false,
-        "componentWillUpdate is deprecated and will be removed in the next major version. " +
-          "Use componentDidUpdate instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillUpdate." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames2
-      );
-
-      pendingComponentWillUpdateWarnings = [];
-    }
-  };
-
-  ReactStrictModeWarnings.recordDeprecationWarnings = function(
-    fiber,
-    instance
-  ) {
-    // Dedup strategy: Warn once per component.
-    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
-      return;
-    }
-
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillMountWarnings.push(fiber);
-    }
-    if (
-      typeof instance.componentWillReceiveProps === "function" &&
-      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillReceivePropsWarnings.push(fiber);
-    }
-    if (
-      typeof instance.componentWillUpdate === "function" &&
-      instance.componentWillUpdate.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillUpdateWarnings.push(fiber);
-    }
-  };
-
-  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
-    fiber,
-    instance
-  ) {
-    var strictRoot = getStrictRoot(fiber);
-
-    // Dedup strategy: Warn once per component.
-    // This is difficult to track any other way since component names
-    // are often vague and are likely to collide between 3rd party libraries.
-    // An expand property is probably okay to use here since it's DEV-only,
-    // and will only be set in the event of serious warnings.
-    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
-      return;
-    }
-
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    // Note that it is sufficient to check for the presence of a
-    // single lifecycle, componentWillMount, with the polyfill flag.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning === true
-    ) {
-      return;
-    }
-
-    var warningsForRoot = void 0;
-    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
-      warningsForRoot = {
-        UNSAFE_componentWillMount: [],
-        UNSAFE_componentWillReceiveProps: [],
-        UNSAFE_componentWillUpdate: []
-      };
-
-      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
-    } else {
-      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
-    }
-
-    var unsafeLifecycles = [];
-    if (
-      typeof instance.componentWillMount === "function" ||
-      typeof instance.UNSAFE_componentWillMount === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillMount");
-    }
-    if (
-      typeof instance.componentWillReceiveProps === "function" ||
-      typeof instance.UNSAFE_componentWillReceiveProps === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
-    }
-    if (
-      typeof instance.componentWillUpdate === "function" ||
-      typeof instance.UNSAFE_componentWillUpdate === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
-    }
-
-    if (unsafeLifecycles.length > 0) {
-      unsafeLifecycles.forEach(function(lifecycle) {
-        warningsForRoot[lifecycle].push(fiber);
-      });
-    }
-  };
-}
-
-var debugRenderPhaseSideEffects = false;
-var debugRenderPhaseSideEffectsForStrictMode = false;
-var enableUserTimingAPI = true;
-var enableGetDerivedStateFromCatch = false;
-var warnAboutDeprecatedLifecycles = false;
-var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
-
-// React Fabric uses persistent reconciler.
-var enableMutatingReconciler = false;
-var enableNoopReconciler = false;
-var enablePersistentReconciler = true;
-
-// Only used in www builds.
-
-function getCurrentFiberOwnerName() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    var owner = fiber._debugOwner;
-    if (owner !== null && typeof owner !== "undefined") {
-      return getComponentName(owner);
-    }
-  }
-  return null;
-}
-
-function getCurrentFiberStackAddendum() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    // Safe because if current fiber exists, we are reconciling,
-    // and it is guaranteed to be the work-in-progress version.
-    return getStackAddendumByWorkInProgressFiber(fiber);
-  }
-  return null;
-}
-
-function resetCurrentFiber() {
-  ReactDebugCurrentFrame.getCurrentStack = null;
-  ReactDebugCurrentFiber.current = null;
-  ReactDebugCurrentFiber.phase = null;
-}
-
-function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
-  ReactDebugCurrentFiber.current = fiber;
-  ReactDebugCurrentFiber.phase = null;
-}
-
-function setCurrentPhase(phase) {
-  ReactDebugCurrentFiber.phase = phase;
-}
-
-var ReactDebugCurrentFiber = {
-  current: null,
-  phase: null,
-  resetCurrentFiber: resetCurrentFiber,
-  setCurrentFiber: setCurrentFiber,
-  setCurrentPhase: setCurrentPhase,
-  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
-};
-
-// Prefix measurements so that it's possible to filter them.
-// Longer prefixes are hard to read in DevTools.
-var reactEmoji = "\u269B";
-var warningEmoji = "\u26D4";
-var supportsUserTiming =
-  typeof performance !== "undefined" &&
-  typeof performance.mark === "function" &&
-  typeof performance.clearMarks === "function" &&
-  typeof performance.measure === "function" &&
-  typeof performance.clearMeasures === "function";
-
-// Keep track of current fiber so that we know the path to unwind on pause.
-// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
-var currentFiber = null;
-// If we're in the middle of user code, which fiber and method is it?
-// Reusing `currentFiber` would be confusing for this because user code fiber
-// can change during commit phase too, but we don't need to unwind it (since
-// lifecycles in the commit phase don't resemble a tree).
-var currentPhase = null;
-var currentPhaseFiber = null;
-// Did lifecycle hook schedule an update? This is often a performance problem,
-// so we will keep track of it, and include it in the report.
-// Track commits caused by cascading updates.
-var isCommitting = false;
-var hasScheduledUpdateInCurrentCommit = false;
-var hasScheduledUpdateInCurrentPhase = false;
-var commitCountInCurrentWorkLoop = 0;
-var effectCountInCurrentCommit = 0;
-var isWaitingForCallback = false;
-// During commits, we only show a measurement once per method name
-// to avoid stretch the commit phase with measurement overhead.
-var labelsInCurrentCommit = new Set();
-
-var formatMarkName = function(markName) {
-  return reactEmoji + " " + markName;
-};
-
-var formatLabel = function(label, warning$$1) {
-  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
-  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
-  return "" + prefix + label + suffix;
-};
-
-var beginMark = function(markName) {
-  performance.mark(formatMarkName(markName));
-};
-
-var clearMark = function(markName) {
-  performance.clearMarks(formatMarkName(markName));
-};
-
-var endMark = function(label, markName, warning$$1) {
-  var formattedMarkName = formatMarkName(markName);
-  var formattedLabel = formatLabel(label, warning$$1);
-  try {
-    performance.measure(formattedLabel, formattedMarkName);
-  } catch (err) {}
-  // If previous mark was missing for some reason, this will throw.
-  // This could only happen if React crashed in an unexpected place earlier.
-  // Don't pile on with more errors.
-
-  // Clear marks immediately to avoid growing buffer.
-  performance.clearMarks(formattedMarkName);
-  performance.clearMeasures(formattedLabel);
-};
-
-var getFiberMarkName = function(label, debugID) {
-  return label + " (#" + debugID + ")";
-};
-
-var getFiberLabel = function(componentName, isMounted, phase) {
-  if (phase === null) {
-    // These are composite component total time measurements.
-    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
-  } else {
-    // Composite component methods.
-    return componentName + "." + phase;
-  }
-};
-
-var beginFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-
-  if (isCommitting && labelsInCurrentCommit.has(label)) {
-    // During the commit phase, we don't show duplicate labels because
-    // there is a fixed overhead for every measurement, and we don't
-    // want to stretch the commit phase beyond necessary.
-    return false;
-  }
-  labelsInCurrentCommit.add(label);
-
-  var markName = getFiberMarkName(label, debugID);
-  beginMark(markName);
-  return true;
-};
-
-var clearFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  clearMark(markName);
-};
-
-var endFiberMark = function(fiber, phase, warning$$1) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  endMark(label, markName, warning$$1);
-};
-
-var shouldIgnoreFiber = function(fiber) {
-  // Host components should be skipped in the timeline.
-  // We could check typeof fiber.type, but does this work with RN?
-  switch (fiber.tag) {
-    case HostRoot:
-    case HostComponent:
-    case HostText:
-    case HostPortal:
-    case CallComponent:
-    case ReturnComponent:
-    case Fragment:
-    case ContextProvider:
-    case ContextConsumer:
-    case Mode:
-      return true;
-    default:
-      return false;
-  }
-};
-
-var clearPendingPhaseMeasurement = function() {
-  if (currentPhase !== null && currentPhaseFiber !== null) {
-    clearFiberMark(currentPhaseFiber, currentPhase);
-  }
-  currentPhaseFiber = null;
-  currentPhase = null;
-  hasScheduledUpdateInCurrentPhase = false;
-};
-
-var pauseTimers = function() {
-  // Stops all currently active measurements so that they can be resumed
-  // if we continue in a later deferred loop from the same unit of work.
-  var fiber = currentFiber;
-  while (fiber) {
-    if (fiber._debugIsCurrentlyTiming) {
-      endFiberMark(fiber, null, null);
-    }
-    fiber = fiber["return"];
-  }
-};
-
-var resumeTimersRecursively = function(fiber) {
-  if (fiber["return"] !== null) {
-    resumeTimersRecursively(fiber["return"]);
-  }
-  if (fiber._debugIsCurrentlyTiming) {
-    beginFiberMark(fiber, null);
-  }
-};
-
-var resumeTimers = function() {
-  // Resumes all measurements that were active during the last deferred loop.
-  if (currentFiber !== null) {
-    resumeTimersRecursively(currentFiber);
-  }
-};
-
-function recordEffect() {
-  if (enableUserTimingAPI) {
-    effectCountInCurrentCommit++;
-  }
-}
-
-function recordScheduleUpdate() {
-  if (enableUserTimingAPI) {
-    if (isCommitting) {
-      hasScheduledUpdateInCurrentCommit = true;
-    }
-    if (
-      currentPhase !== null &&
-      currentPhase !== "componentWillMount" &&
-      currentPhase !== "componentWillReceiveProps"
-    ) {
-      hasScheduledUpdateInCurrentPhase = true;
-    }
-  }
-}
-
-function startRequestCallbackTimer() {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming && !isWaitingForCallback) {
-      isWaitingForCallback = true;
-      beginMark("(Waiting for async callback...)");
-    }
-  }
-}
-
-function stopRequestCallbackTimer(didExpire, expirationTime) {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming) {
-      isWaitingForCallback = false;
-      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
-      endMark(
-        "(Waiting for async callback... will force flush in " +
-          expirationTime +
-          " ms)",
-        "(Waiting for async callback...)",
-        warning$$1
-      );
-    }
-  }
-}
-
-function startWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, this is the fiber to unwind from.
-    currentFiber = fiber;
-    if (!beginFiberMark(fiber, null)) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = true;
-  }
-}
-
-function cancelWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // Remember we shouldn't complete measurement for this fiber.
-    // Otherwise flamechart will be deep even for small updates.
-    fiber._debugIsCurrentlyTiming = false;
-    clearFiberMark(fiber, null);
-  }
-}
-
-function stopWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    endFiberMark(fiber, null, null);
-  }
-}
-
-function stopFailedWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    var warning$$1 = "An error was thrown inside this error boundary";
-    endFiberMark(fiber, null, warning$$1);
-  }
-}
-
-function startPhaseTimer(fiber, phase) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    clearPendingPhaseMeasurement();
-    if (!beginFiberMark(fiber, phase)) {
-      return;
-    }
-    currentPhaseFiber = fiber;
-    currentPhase = phase;
-  }
-}
-
-function stopPhaseTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    if (currentPhase !== null && currentPhaseFiber !== null) {
-      var warning$$1 = hasScheduledUpdateInCurrentPhase
-        ? "Scheduled a cascading update"
-        : null;
-      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
-    }
-    currentPhase = null;
-    currentPhaseFiber = null;
-  }
-}
-
-function startWorkLoopTimer(nextUnitOfWork) {
-  if (enableUserTimingAPI) {
-    currentFiber = nextUnitOfWork;
-    if (!supportsUserTiming) {
-      return;
-    }
-    commitCountInCurrentWorkLoop = 0;
-    // This is top level call.
-    // Any other measurements are performed within.
-    beginMark("(React Tree Reconciliation)");
-    // Resume any measurements that were in progress during the last loop.
-    resumeTimers();
-  }
-}
-
-function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var warning$$1 = null;
-    if (interruptedBy !== null) {
-      if (interruptedBy.tag === HostRoot) {
-        warning$$1 = "A top-level update interrupted the previous render";
-      } else {
-        var componentName = getComponentName(interruptedBy) || "Unknown";
-        warning$$1 =
-          "An update to " + componentName + " interrupted the previous render";
-      }
-    } else if (commitCountInCurrentWorkLoop > 1) {
-      warning$$1 = "There were cascading updates";
-    }
-    commitCountInCurrentWorkLoop = 0;
-    var label = didCompleteRoot
-      ? "(React Tree Reconciliation: Completed Root)"
-      : "(React Tree Reconciliation: Yielded)";
-    // Pause any measurements until the next loop.
-    pauseTimers();
-    endMark(label, "(React Tree Reconciliation)", warning$$1);
-  }
-}
-
-function startCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    isCommitting = true;
-    hasScheduledUpdateInCurrentCommit = false;
-    labelsInCurrentCommit.clear();
-    beginMark("(Committing Changes)");
-  }
-}
-
-function stopCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-
-    var warning$$1 = null;
-    if (hasScheduledUpdateInCurrentCommit) {
-      warning$$1 = "Lifecycle hook scheduled a cascading update";
-    } else if (commitCountInCurrentWorkLoop > 0) {
-      warning$$1 = "Caused by a cascading update in earlier commit";
-    }
-    hasScheduledUpdateInCurrentCommit = false;
-    commitCountInCurrentWorkLoop++;
-    isCommitting = false;
-    labelsInCurrentCommit.clear();
-
-    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
-  }
-}
-
-function startCommitSnapshotEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Snapshot Effects)");
-  }
-}
-
-function stopCommitSnapshotEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Snapshot Effects: " + count + " Total)",
-      "(Committing Snapshot Effects)",
-      null
-    );
-  }
-}
-
-function startCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Host Effects)");
-  }
-}
-
-function stopCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Host Effects: " + count + " Total)",
-      "(Committing Host Effects)",
-      null
-    );
-  }
-}
-
-function startCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Calling Lifecycle Methods)");
-  }
-}
-
-function stopCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Calling Lifecycle Methods: " + count + " Total)",
-      "(Calling Lifecycle Methods)",
-      null
-    );
-  }
-}
-
-var didWarnUpdateInsideUpdate = void 0;
-
-{
-  didWarnUpdateInsideUpdate = false;
-}
-
-// Callbacks are not validated until invocation
-
-// Singly linked-list of updates. When an update is scheduled, it is added to
-// the queue of the current fiber and the work-in-progress fiber. The two queues
-// are separate but they share a persistent structure.
-//
-// During reconciliation, updates are removed from the work-in-progress fiber,
-// but they remain on the current fiber. That ensures that if a work-in-progress
-// is aborted, the aborted updates are recovered by cloning from current.
-//
-// The work-in-progress queue is always a subset of the current queue.
-//
-// When the tree is committed, the work-in-progress becomes the current.
-
-function createUpdateQueue(baseState) {
-  var queue = {
-    baseState: baseState,
-    expirationTime: NoWork,
-    first: null,
-    last: null,
-    callbackList: null,
-    hasForceUpdate: false,
-    isInitialized: false,
-    capturedValues: null
-  };
-  {
-    queue.isProcessing = false;
-  }
-  return queue;
-}
-
-function insertUpdateIntoQueue(queue, update) {
-  // Append the update to the end of the list.
-  if (queue.last === null) {
-    // Queue is empty
-    queue.first = queue.last = update;
-  } else {
-    queue.last.next = update;
-    queue.last = update;
-  }
-  if (
-    queue.expirationTime === NoWork ||
-    queue.expirationTime > update.expirationTime
-  ) {
-    queue.expirationTime = update.expirationTime;
-  }
-}
-
-var q1 = void 0;
-var q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  // We'll have at least one and at most two distinct update queues.
-  var alternateFiber = fiber.alternate;
-  var queue1 = fiber.updateQueue;
-  if (queue1 === null) {
-    // TODO: We don't know what the base state will be until we begin work.
-    // It depends on which fiber is the next current. Initialize with an empty
-    // base state, then set to the memoizedState when rendering. Not super
-    // happy with this approach.
-    queue1 = fiber.updateQueue = createUpdateQueue(null);
-  }
-
-  var queue2 = void 0;
-  if (alternateFiber !== null) {
-    queue2 = alternateFiber.updateQueue;
-    if (queue2 === null) {
-      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
-    }
-  } else {
-    queue2 = null;
-  }
-  queue2 = queue2 !== queue1 ? queue2 : null;
-
-  // Use module variables instead of returning a tuple
-  q1 = queue1;
-  q2 = queue2;
-}
-
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  var queue1 = q1;
-  var queue2 = q2;
-
-  // Warn if an update is scheduled from inside an updater function.
-  {
-    if (
-      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
-      !didWarnUpdateInsideUpdate
-    ) {
-      warning(
-        false,
-        "An update (setState, replaceState, or forceUpdate) was scheduled " +
-          "from inside an update function. Update functions should be pure, " +
-          "with zero side-effects. Consider using componentDidUpdate or a " +
-          "callback."
-      );
-      didWarnUpdateInsideUpdate = true;
-    }
-  }
-
-  // If there's only one queue, add the update to that queue and exit.
-  if (queue2 === null) {
-    insertUpdateIntoQueue(queue1, update);
-    return;
-  }
-
-  // If either queue is empty, we need to add to both queues.
-  if (queue1.last === null || queue2.last === null) {
-    insertUpdateIntoQueue(queue1, update);
-    insertUpdateIntoQueue(queue2, update);
-    return;
-  }
-
-  // If both lists are not empty, the last update is the same for both lists
-  // because of structural sharing. So, we should only append to one of
-  // the lists.
-  insertUpdateIntoQueue(queue1, update);
-  // But we still need to update the `last` pointer of queue2.
-  queue2.last = update;
-}
-
-function getUpdateExpirationTime(fiber) {
-  switch (fiber.tag) {
-    case HostRoot:
-    case ClassComponent:
-      var updateQueue = fiber.updateQueue;
-      if (updateQueue === null) {
-        return NoWork;
-      }
-      return updateQueue.expirationTime;
-    default:
-      return NoWork;
-  }
-}
-
-function getStateFromUpdate(update, instance, prevState, props) {
-  var partialState = update.partialState;
-  if (typeof partialState === "function") {
-    return partialState.call(instance, prevState, props);
-  } else {
-    return partialState;
-  }
-}
-
-function processUpdateQueue(
-  current,
-  workInProgress,
-  queue,
-  instance,
-  props,
-  renderExpirationTime
-) {
-  if (current !== null && current.updateQueue === queue) {
-    // We need to create a work-in-progress queue, by cloning the current queue.
-    var currentQueue = queue;
-    queue = workInProgress.updateQueue = {
-      baseState: currentQueue.baseState,
-      expirationTime: currentQueue.expirationTime,
-      first: currentQueue.first,
-      last: currentQueue.last,
-      isInitialized: currentQueue.isInitialized,
-      capturedValues: currentQueue.capturedValues,
-      // These fields are no longer valid because they were already committed.
-      // Reset them.
-      callbackList: null,
-      hasForceUpdate: false
-    };
-  }
-
-  {
-    // Set this flag so we can warn if setState is called inside the update
-    // function of another setState.
-    queue.isProcessing = true;
-  }
-
-  // Reset the remaining expiration time. If we skip over any updates, we'll
-  // increase this accordingly.
-  queue.expirationTime = NoWork;
-
-  // TODO: We don't know what the base state will be until we begin work.
-  // It depends on which fiber is the next current. Initialize with an empty
-  // base state, then set to the memoizedState when rendering. Not super
-  // happy with this approach.
-  var state = void 0;
-  if (queue.isInitialized) {
-    state = queue.baseState;
-  } else {
-    state = queue.baseState = workInProgress.memoizedState;
-    queue.isInitialized = true;
-  }
-  var dontMutatePrevState = true;
-  var update = queue.first;
-  var didSkip = false;
-  while (update !== null) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      // This update does not have sufficient priority. Skip it.
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        remainingExpirationTime === NoWork ||
-        remainingExpirationTime > updateExpirationTime
-      ) {
-        // Update the remaining expiration time.
-        queue.expirationTime = updateExpirationTime;
-      }
-      if (!didSkip) {
-        didSkip = true;
-        queue.baseState = state;
-      }
-      // Continue to the next update.
-      update = update.next;
-      continue;
-    }
-
-    // This update does have sufficient priority.
-
-    // If no previous updates were skipped, drop this update from the queue by
-    // advancing the head of the list.
-    if (!didSkip) {
-      queue.first = update.next;
-      if (queue.first === null) {
-        queue.last = null;
-      }
-    }
-
-    // Invoke setState callback an extra time to help detect side-effects.
-    // Ignore the return value in this case.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      getStateFromUpdate(update, instance, state, props);
-    }
-
-    // Process the update
-    var _partialState = void 0;
-    if (update.isReplace) {
-      state = getStateFromUpdate(update, instance, state, props);
-      dontMutatePrevState = true;
-    } else {
-      _partialState = getStateFromUpdate(update, instance, state, props);
-      if (_partialState) {
-        if (dontMutatePrevState) {
-          // $FlowFixMe: Idk how to type this properly.
-          state = Object.assign({}, state, _partialState);
-        } else {
-          state = Object.assign(state, _partialState);
-        }
-        dontMutatePrevState = false;
-      }
-    }
-    if (update.isForced) {
-      queue.hasForceUpdate = true;
-    }
-    if (update.callback !== null) {
-      // Append to list of callbacks.
-      var _callbackList = queue.callbackList;
-      if (_callbackList === null) {
-        _callbackList = queue.callbackList = [];
-      }
-      _callbackList.push(update);
-    }
-    if (update.capturedValue !== null) {
-      var _capturedValues = queue.capturedValues;
-      if (_capturedValues === null) {
-        queue.capturedValues = [update.capturedValue];
-      } else {
-        _capturedValues.push(update.capturedValue);
-      }
-    }
-    update = update.next;
-  }
-
-  if (queue.callbackList !== null) {
-    workInProgress.effectTag |= Callback;
-  } else if (
-    queue.first === null &&
-    !queue.hasForceUpdate &&
-    queue.capturedValues === null
-  ) {
-    // The queue is empty. We can reset it.
-    workInProgress.updateQueue = null;
-  }
-
-  if (!didSkip) {
-    didSkip = true;
-    queue.baseState = state;
-  }
-
-  {
-    // No longer processing.
-    queue.isProcessing = false;
-  }
-
-  return state;
-}
-
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (callbackList === null) {
-    return;
-  }
-  // Set the list to null to make sure they don't get called more than once.
-  queue.callbackList = null;
-  for (var i = 0; i < callbackList.length; i++) {
-    var update = callbackList[i];
-    var _callback = update.callback;
-    // This update might be processed again. Clear the callback so it's only
-    // called once.
-    update.callback = null;
-    invariant(
-      typeof _callback === "function",
-      "Invalid argument passed as callback. Expected a function. Instead " +
-        "received: %s",
-      _callback
-    );
-    _callback.call(context);
-  }
-}
-
-var fakeInternalInstance = {};
-var isArray = Array.isArray;
-
-var didWarnAboutStateAssignmentForComponent = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
-var didWarnAboutUninitializedState = void 0;
-var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
-var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
-var warnOnInvalidCallback = void 0;
-
-{
-  didWarnAboutStateAssignmentForComponent = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
-  didWarnAboutUninitializedState = new Set();
-  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
-  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
-
-  var didWarnOnInvalidCallback = new Set();
-
-  warnOnInvalidCallback = function(callback, callerName) {
-    if (callback === null || typeof callback === "function") {
-      return;
-    }
-    var key = callerName + "_" + callback;
-    if (!didWarnOnInvalidCallback.has(key)) {
-      didWarnOnInvalidCallback.add(key);
-      warning(
-        false,
-        "%s(...): Expected the last optional `callback` argument to be a " +
-          "function. Instead received: %s.",
-        callerName,
-        callback
-      );
-    }
-  };
-
-  // This is so gross but it's at least non-critical and can be removed if
-  // it causes problems. This is meant to give a nicer error message for
-  // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
-  // ...)) which otherwise throws a "_processChildContext is not a function"
-  // exception.
-  Object.defineProperty(fakeInternalInstance, "_processChildContext", {
-    enumerable: false,
-    value: function() {
-      invariant(
-        false,
-        "_processChildContext is not available in React 16+. This likely " +
-          "means you have multiple copies of React and are attempting to nest " +
-          "a React 15 tree inside a React 16 tree using " +
-          "unstable_renderSubtreeIntoContainer, which isn't supported. Try " +
-          "to make sure you have only one copy of React (and ideally, switch " +
-          "to ReactDOM.createPortal)."
-      );
-    }
-  });
-  Object.freeze(fakeInternalInstance);
-}
-function callGetDerivedStateFromCatch(ctor, capturedValues) {
-  var resultState = {};
-  for (var i = 0; i < capturedValues.length; i++) {
-    var capturedValue = capturedValues[i];
-    var error = capturedValue.value;
-    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
-    if (partialState !== null && partialState !== undefined) {
-      Object.assign(resultState, partialState);
-    }
-  }
-  return resultState;
-}
-
-var ReactFiberClassComponent = function(
-  legacyContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState
-) {
-  var cacheContext = legacyContext.cacheContext,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    isContextConsumer = legacyContext.isContextConsumer,
-    hasContextChanged = legacyContext.hasContextChanged;
-
-  // Class component state updater
-
-  var updater = {
-    isMounted: isMounted,
-    enqueueSetState: function(instance, partialState, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "setState");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: partialState,
-        callback: callback,
-        isReplace: false,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
-      scheduleWork(fiber, expirationTime);
-    },
-    enqueueReplaceState: function(instance, state, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "replaceState");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: state,
-        callback: callback,
-        isReplace: true,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
-      scheduleWork(fiber, expirationTime);
-    },
-    enqueueForceUpdate: function(instance, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "forceUpdate");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: null,
-        callback: callback,
-        isReplace: false,
-        isForced: true,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
-      scheduleWork(fiber, expirationTime);
-    }
-  };
-
-  function checkShouldComponentUpdate(
-    workInProgress,
-    oldProps,
-    newProps,
-    oldState,
-    newState,
-    newContext
-  ) {
-    if (
-      oldProps === null ||
-      (workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate)
-    ) {
-      // If the workInProgress already has an Update effect, return true
-      return true;
-    }
-
-    var instance = workInProgress.stateNode;
-    var ctor = workInProgress.type;
-    if (typeof instance.shouldComponentUpdate === "function") {
-      startPhaseTimer(workInProgress, "shouldComponentUpdate");
-      var shouldUpdate = instance.shouldComponentUpdate(
-        newProps,
-        newState,
-        newContext
-      );
-      stopPhaseTimer();
-
-      {
-        !(shouldUpdate !== undefined)
-          ? warning(
-              false,
-              "%s.shouldComponentUpdate(): Returned undefined instead of a " +
-                "boolean value. Make sure to return true or false.",
-              getComponentName(workInProgress) || "Component"
-            )
-          : void 0;
-      }
-
-      return shouldUpdate;
-    }
-
-    if (ctor.prototype && ctor.prototype.isPureReactComponent) {
-      return (
-        !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
-      );
-    }
-
-    return true;
-  }
-
-  function checkClassInstance(workInProgress) {
-    var instance = workInProgress.stateNode;
-    var type = workInProgress.type;
-    {
-      var name = getComponentName(workInProgress) || "Component";
-      var renderPresent = instance.render;
-
-      if (!renderPresent) {
-        if (type.prototype && typeof type.prototype.render === "function") {
-          warning(
-            false,
-            "%s(...): No `render` method found on the returned component " +
-              "instance: did you accidentally return an object from the constructor?",
-            name
-          );
-        } else {
-          warning(
-            false,
-            "%s(...): No `render` method found on the returned component " +
-              "instance: you may have forgotten to define `render`.",
-            name
-          );
-        }
-      }
-
-      var noGetInitialStateOnES6 =
-        !instance.getInitialState ||
-        instance.getInitialState.isReactClassApproved ||
-        instance.state;
-      !noGetInitialStateOnES6
-        ? warning(
-            false,
-            "getInitialState was defined on %s, a plain JavaScript class. " +
-              "This is only supported for classes created using React.createClass. " +
-              "Did you mean to define a state property instead?",
-            name
-          )
-        : void 0;
-      var noGetDefaultPropsOnES6 =
-        !instance.getDefaultProps ||
-        instance.getDefaultProps.isReactClassApproved;
-      !noGetDefaultPropsOnES6
-        ? warning(
-            false,
-            "getDefaultProps was defined on %s, a plain JavaScript class. " +
-              "This is only supported for classes created using React.createClass. " +
-              "Use a static property to define defaultProps instead.",
-            name
-          )
-        : void 0;
-      var noInstancePropTypes = !instance.propTypes;
-      !noInstancePropTypes
-        ? warning(
-            false,
-            "propTypes was defined as an instance property on %s. Use a static " +
-              "property to define propTypes instead.",
-            name
-          )
-        : void 0;
-      var noInstanceContextTypes = !instance.contextTypes;
-      !noInstanceContextTypes
-        ? warning(
-            false,
-            "contextTypes was defined as an instance property on %s. Use a static " +
-              "property to define contextTypes instead.",
-            name
-          )
-        : void 0;
-      var noComponentShouldUpdate =
-        typeof instance.componentShouldUpdate !== "function";
-      !noComponentShouldUpdate
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
-              "The name is phrased as a question because the function is " +
-              "expected to return a value.",
-            name
-          )
-        : void 0;
-      if (
-        type.prototype &&
-        type.prototype.isPureReactComponent &&
-        typeof instance.shouldComponentUpdate !== "undefined"
-      ) {
-        warning(
-          false,
-          "%s has a method called shouldComponentUpdate(). " +
-            "shouldComponentUpdate should not be used when extending React.PureComponent. " +
-            "Please extend React.Component if shouldComponentUpdate is used.",
-          getComponentName(workInProgress) || "A pure component"
-        );
-      }
-      var noComponentDidUnmount =
-        typeof instance.componentDidUnmount !== "function";
-      !noComponentDidUnmount
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentDidUnmount(). But there is no such lifecycle method. " +
-              "Did you mean componentWillUnmount()?",
-            name
-          )
-        : void 0;
-      var noComponentDidReceiveProps =
-        typeof instance.componentDidReceiveProps !== "function";
-      !noComponentDidReceiveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentDidReceiveProps(). But there is no such lifecycle method. " +
-              "If you meant to update the state in response to changing props, " +
-              "use componentWillReceiveProps(). If you meant to fetch data or " +
-              "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
-            name
-          )
-        : void 0;
-      var noComponentWillRecieveProps =
-        typeof instance.componentWillRecieveProps !== "function";
-      !noComponentWillRecieveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
-            name
-          )
-        : void 0;
-      var noUnsafeComponentWillRecieveProps =
-        typeof instance.UNSAFE_componentWillRecieveProps !== "function";
-      !noUnsafeComponentWillRecieveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
-            name
-          )
-        : void 0;
-      var hasMutatedProps = instance.props !== workInProgress.pendingProps;
-      !(instance.props === undefined || !hasMutatedProps)
-        ? warning(
-            false,
-            "%s(...): When calling super() in `%s`, make sure to pass " +
-              "up the same props that your component's constructor was passed.",
-            name,
-            name
-          )
-        : void 0;
-      var noInstanceDefaultProps = !instance.defaultProps;
-      !noInstanceDefaultProps
-        ? warning(
-            false,
-            "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
-              " Instead, define defaultProps as a static property on %s.",
-            name,
-            name
-          )
-        : void 0;
-
-      if (
-        typeof instance.getSnapshotBeforeUpdate === "function" &&
-        typeof instance.componentDidUpdate !== "function" &&
-        !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
-      ) {
-        didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
-        warning(
-          false,
-          "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
-            "This component defines getSnapshotBeforeUpdate() only.",
-          getComponentName(workInProgress)
-        );
-      }
-
-      var noInstanceGetDerivedStateFromProps =
-        typeof instance.getDerivedStateFromProps !== "function";
-      !noInstanceGetDerivedStateFromProps
-        ? warning(
-            false,
-            "%s: getDerivedStateFromProps() is defined as an instance method " +
-              "and will be ignored. Instead, declare it as a static method.",
-            name
-          )
-        : void 0;
-      var noInstanceGetDerivedStateFromCatch =
-        typeof instance.getDerivedStateFromCatch !== "function";
-      !noInstanceGetDerivedStateFromCatch
-        ? warning(
-            false,
-            "%s: getDerivedStateFromCatch() is defined as an instance method " +
-              "and will be ignored. Instead, declare it as a static method.",
-            name
-          )
-        : void 0;
-      var noStaticGetSnapshotBeforeUpdate =
-        typeof type.getSnapshotBeforeUpdate !== "function";
-      !noStaticGetSnapshotBeforeUpdate
-        ? warning(
-            false,
-            "%s: getSnapshotBeforeUpdate() is defined as a static method " +
-              "and will be ignored. Instead, declare it as an instance method.",
-            name
-          )
-        : void 0;
-      var _state = instance.state;
-      if (_state && (typeof _state !== "object" || isArray(_state))) {
-        warning(false, "%s.state: must be set to an object or null", name);
-      }
-      if (typeof instance.getChildContext === "function") {
-        !(typeof type.childContextTypes === "object")
-          ? warning(
-              false,
-              "%s.getChildContext(): childContextTypes must be defined in order to " +
-                "use getChildContext().",
-              name
-            )
-          : void 0;
-      }
-    }
-  }
-
-  function resetInputPointers(workInProgress, instance) {
-    instance.props = workInProgress.memoizedProps;
-    instance.state = workInProgress.memoizedState;
-  }
-
-  function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
-    workInProgress.stateNode = instance;
-    // The instance needs access to the fiber so that it can schedule updates
-    set(instance, workInProgress);
-    {
-      instance._reactInternalInstance = fakeInternalInstance;
-    }
-  }
-
-  function constructClassInstance(workInProgress, props) {
-    var ctor = workInProgress.type;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var needsContext = isContextConsumer(workInProgress);
-    var context = needsContext
-      ? getMaskedContext(workInProgress, unmaskedContext)
-      : emptyObject;
-
-    // Instantiate twice to help detect side-effects.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      new ctor(props, context); // eslint-disable-line no-new
-    }
-
-    var instance = new ctor(props, context);
-    var state =
-      instance.state !== null && instance.state !== undefined
-        ? instance.state
-        : null;
-    adoptClassInstance(workInProgress, instance);
-
-    {
-      if (
-        typeof ctor.getDerivedStateFromProps === "function" &&
-        state === null
-      ) {
-        var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutUninitializedState.has(componentName)) {
-          didWarnAboutUninitializedState.add(componentName);
-          warning(
-            false,
-            "%s: Did not properly initialize state during construction. " +
-              "Expected state to be an object, but it was %s.",
-            componentName,
-            instance.state === null ? "null" : "undefined"
-          );
-        }
-      }
-
-      // If new component APIs are defined, "unsafe" lifecycles won't be called.
-      // Warn about these lifecycles if they are present.
-      // Don't warn about react-lifecycles-compat polyfilled methods though.
-      if (
-        typeof ctor.getDerivedStateFromProps === "function" ||
-        typeof instance.getSnapshotBeforeUpdate === "function"
-      ) {
-        var foundWillMountName = null;
-        var foundWillReceivePropsName = null;
-        var foundWillUpdateName = null;
-        if (
-          typeof instance.componentWillMount === "function" &&
-          instance.componentWillMount.__suppressDeprecationWarning !== true
-        ) {
-          foundWillMountName = "componentWillMount";
-        } else if (typeof instance.UNSAFE_componentWillMount === "function") {
-          foundWillMountName = "UNSAFE_componentWillMount";
-        }
-        if (
-          typeof instance.componentWillReceiveProps === "function" &&
-          instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-            true
-        ) {
-          foundWillReceivePropsName = "componentWillReceiveProps";
-        } else if (
-          typeof instance.UNSAFE_componentWillReceiveProps === "function"
-        ) {
-          foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
-        }
-        if (
-          typeof instance.componentWillUpdate === "function" &&
-          instance.componentWillUpdate.__suppressDeprecationWarning !== true
-        ) {
-          foundWillUpdateName = "componentWillUpdate";
-        } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          foundWillUpdateName = "UNSAFE_componentWillUpdate";
-        }
-        if (
-          foundWillMountName !== null ||
-          foundWillReceivePropsName !== null ||
-          foundWillUpdateName !== null
-        ) {
-          var _componentName = getComponentName(workInProgress) || "Component";
-          var newApiName =
-            typeof ctor.getDerivedStateFromProps === "function"
-              ? "getDerivedStateFromProps()"
-              : "getSnapshotBeforeUpdate()";
-          if (
-            !didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)
-          ) {
-            didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
-            warning(
-              false,
-              "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
-                "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
-                "The above lifecycles should be removed. Learn more about this warning here:\n" +
-                "https://fb.me/react-async-component-lifecycle-hooks",
-              _componentName,
-              newApiName,
-              foundWillMountName !== null ? "\n  " + foundWillMountName : "",
-              foundWillReceivePropsName !== null
-                ? "\n  " + foundWillReceivePropsName
-                : "",
-              foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
-            );
-          }
-        }
-      }
-    }
-
-    workInProgress.memoizedState = state;
-
-    var partialState = callGetDerivedStateFromProps(
-      workInProgress,
-      instance,
-      props,
-      state
-    );
-
-    if (partialState !== null && partialState !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      workInProgress.memoizedState = Object.assign(
-        {},
-        workInProgress.memoizedState,
-        partialState
-      );
-    }
-
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // ReactFiberContext usually updates this cache but can't for newly-created instances.
-    if (needsContext) {
-      cacheContext(workInProgress, unmaskedContext, context);
-    }
-
-    return instance;
-  }
-
-  function callComponentWillMount(workInProgress, instance) {
-    startPhaseTimer(workInProgress, "componentWillMount");
-    var oldState = instance.state;
-
-    if (typeof instance.componentWillMount === "function") {
-      instance.componentWillMount();
-    }
-    if (typeof instance.UNSAFE_componentWillMount === "function") {
-      instance.UNSAFE_componentWillMount();
-    }
-
-    stopPhaseTimer();
-
-    if (oldState !== instance.state) {
-      {
-        warning(
-          false,
-          "%s.componentWillMount(): Assigning directly to this.state is " +
-            "deprecated (except inside a component's " +
-            "constructor). Use setState instead.",
-          getComponentName(workInProgress) || "Component"
-        );
-      }
-      updater.enqueueReplaceState(instance, instance.state, null);
-    }
-  }
-
-  function callComponentWillReceiveProps(
-    workInProgress,
-    instance,
-    newProps,
-    newContext
-  ) {
-    var oldState = instance.state;
-    startPhaseTimer(workInProgress, "componentWillReceiveProps");
-    if (typeof instance.componentWillReceiveProps === "function") {
-      instance.componentWillReceiveProps(newProps, newContext);
-    }
-    if (typeof instance.UNSAFE_componentWillReceiveProps === "function") {
-      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
-    }
-    stopPhaseTimer();
-
-    if (instance.state !== oldState) {
-      {
-        var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
-          didWarnAboutStateAssignmentForComponent.add(componentName);
-          warning(
-            false,
-            "%s.componentWillReceiveProps(): Assigning directly to " +
-              "this.state is deprecated (except inside a component's " +
-              "constructor). Use setState instead.",
-            componentName
-          );
-        }
-      }
-      updater.enqueueReplaceState(instance, instance.state, null);
-    }
-  }
-
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    var type = workInProgress.type;
-
-    if (typeof type.getDerivedStateFromProps === "function") {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        // Invoke method an extra time to help detect side-effects.
-        type.getDerivedStateFromProps.call(null, nextProps, prevState);
-      }
-
-      var partialState = type.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
-
-      {
-        if (partialState === undefined) {
-          var componentName = getComponentName(workInProgress) || "Component";
-          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-            didWarnAboutUndefinedDerivedState.add(componentName);
-            warning(
-              false,
-              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-                "You have returned undefined.",
-              componentName
-            );
-          }
-        }
-      }
-
-      return partialState;
-    }
-  }
-
-  // Invokes the mount life-cycles on a previously never rendered instance.
-  function mountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var current = workInProgress.alternate;
-
-    {
-      checkClassInstance(workInProgress);
-    }
-
-    var instance = workInProgress.stateNode;
-    var props = workInProgress.pendingProps;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-
-    instance.props = props;
-    instance.state = workInProgress.memoizedState;
-    instance.refs = emptyObject;
-    instance.context = getMaskedContext(workInProgress, unmaskedContext);
-
-    {
-      if (workInProgress.mode & StrictMode) {
-        ReactStrictModeWarnings.recordUnsafeLifecycleWarnings(
-          workInProgress,
-          instance
-        );
-      }
-
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.recordDeprecationWarnings(
-          workInProgress,
-          instance
-        );
-      }
-    }
-
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      typeof ctor.getDerivedStateFromProps !== "function" &&
-      typeof instance.getSnapshotBeforeUpdate !== "function" &&
-      (typeof instance.UNSAFE_componentWillMount === "function" ||
-        typeof instance.componentWillMount === "function")
-    ) {
-      callComponentWillMount(workInProgress, instance);
-      // If we had additional state updates during this life-cycle, let's
-      // process them now.
-      var updateQueue = workInProgress.updateQueue;
-      if (updateQueue !== null) {
-        instance.state = processUpdateQueue(
-          current,
-          workInProgress,
-          updateQueue,
-          instance,
-          props,
-          renderExpirationTime
-        );
-      }
-    }
-    if (typeof instance.componentDidMount === "function") {
-      workInProgress.effectTag |= Update;
-    }
-  }
-
-  function resumeMountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
-
-    var oldProps = workInProgress.memoizedProps;
-    var newProps = workInProgress.pendingProps;
-    var oldContext = instance.context;
-    var newUnmaskedContext = getUnmaskedContext(workInProgress);
-    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
-
-    var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
-      typeof instance.getSnapshotBeforeUpdate === "function";
-
-    // Note: During these life-cycles, instance.props/instance.state are what
-    // ever the previously attempted to render - not the "current". However,
-    // during componentDidUpdate we pass the "current" props.
-
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      !hasNewLifecycles &&
-      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function")
-    ) {
-      if (oldProps !== newProps || oldContext !== newContext) {
-        callComponentWillReceiveProps(
-          workInProgress,
-          instance,
-          newProps,
-          newContext
-        );
-      }
-    }
-
-    // Compute the next state using the memoized state and the update queue.
-    var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        null,
-        workInProgress,
-        workInProgress.updateQueue,
-        instance,
-        newProps,
-        renderExpirationTime
-      );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
-    }
-
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
-        instance,
-        newProps,
-        newState
-      );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue = workInProgress.updateQueue;
-      if (_updateQueue !== null) {
-        _updateQueue.baseState = Object.assign(
-          {},
-          _updateQueue.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue2 = workInProgress.updateQueue;
-      if (_updateQueue2 !== null) {
-        _updateQueue2.baseState = Object.assign(
-          {},
-          _updateQueue2.baseState,
-          derivedStateFromCatch
-        );
-      }
-    }
-
-    if (
-      oldProps === newProps &&
-      oldState === newState &&
-      !hasContextChanged() &&
-      !(
-        workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate
-      )
-    ) {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-      return false;
-    }
-
-    var shouldUpdate = checkShouldComponentUpdate(
-      workInProgress,
-      oldProps,
-      newProps,
-      oldState,
-      newState,
-      newContext
-    );
-
-    if (shouldUpdate) {
-      // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for components using the new APIs.
-      if (
-        !hasNewLifecycles &&
-        (typeof instance.UNSAFE_componentWillMount === "function" ||
-          typeof instance.componentWillMount === "function")
-      ) {
-        startPhaseTimer(workInProgress, "componentWillMount");
-        if (typeof instance.componentWillMount === "function") {
-          instance.componentWillMount();
-        }
-        if (typeof instance.UNSAFE_componentWillMount === "function") {
-          instance.UNSAFE_componentWillMount();
-        }
-        stopPhaseTimer();
-      }
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-    } else {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-
-      // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
-    }
-
-    // Update the existing instance's state, props, and context pointers even
-    // if shouldComponentUpdate returns false.
-    instance.props = newProps;
-    instance.state = newState;
-    instance.context = newContext;
-
-    return shouldUpdate;
-  }
-
-  // Invokes the update life-cycles and returns false if it shouldn't rerender.
-  function updateClassInstance(current, workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
-
-    var oldProps = workInProgress.memoizedProps;
-    var newProps = workInProgress.pendingProps;
-    var oldContext = instance.context;
-    var newUnmaskedContext = getUnmaskedContext(workInProgress);
-    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
-
-    var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
-      typeof instance.getSnapshotBeforeUpdate === "function";
-
-    // Note: During these life-cycles, instance.props/instance.state are what
-    // ever the previously attempted to render - not the "current". However,
-    // during componentDidUpdate we pass the "current" props.
-
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      !hasNewLifecycles &&
-      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function")
-    ) {
-      if (oldProps !== newProps || oldContext !== newContext) {
-        callComponentWillReceiveProps(
-          workInProgress,
-          instance,
-          newProps,
-          newContext
-        );
-      }
-    }
-
-    // Compute the next state using the memoized state and the update queue.
-    var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        current,
-        workInProgress,
-        workInProgress.updateQueue,
-        instance,
-        newProps,
-        renderExpirationTime
-      );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
-    }
-
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
-        instance,
-        newProps,
-        newState
-      );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue3 = workInProgress.updateQueue;
-      if (_updateQueue3 !== null) {
-        _updateQueue3.baseState = Object.assign(
-          {},
-          _updateQueue3.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue4 = workInProgress.updateQueue;
-      if (_updateQueue4 !== null) {
-        _updateQueue4.baseState = Object.assign(
-          {},
-          _updateQueue4.baseState,
-          derivedStateFromCatch
-        );
-      }
-    }
-
-    if (
-      oldProps === newProps &&
-      oldState === newState &&
-      !hasContextChanged() &&
-      !(
-        workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate
-      )
-    ) {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Update;
-        }
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Snapshot;
-        }
-      }
-      return false;
-    }
-
-    var shouldUpdate = checkShouldComponentUpdate(
-      workInProgress,
-      oldProps,
-      newProps,
-      oldState,
-      newState,
-      newContext
-    );
-
-    if (shouldUpdate) {
-      // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for components using the new APIs.
-      if (
-        !hasNewLifecycles &&
-        (typeof instance.UNSAFE_componentWillUpdate === "function" ||
-          typeof instance.componentWillUpdate === "function")
-      ) {
-        startPhaseTimer(workInProgress, "componentWillUpdate");
-        if (typeof instance.componentWillUpdate === "function") {
-          instance.componentWillUpdate(newProps, newState, newContext);
-        }
-        if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
-        }
-        stopPhaseTimer();
-      }
-      if (typeof instance.componentDidUpdate === "function") {
-        workInProgress.effectTag |= Update;
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        workInProgress.effectTag |= Snapshot;
-      }
-    } else {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Update;
-        }
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Snapshot;
-        }
-      }
-
-      // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
-    }
-
-    // Update the existing instance's state, props, and context pointers even
-    // if shouldComponentUpdate returns false.
-    instance.props = newProps;
-    instance.state = newState;
-    instance.context = newContext;
-
-    return shouldUpdate;
-  }
-
-  return {
-    adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
-    constructClassInstance: constructClassInstance,
-    mountClassInstance: mountClassInstance,
-    resumeMountClassInstance: resumeMountClassInstance,
-    updateClassInstance: updateClassInstance
-  };
-};
-
-var getCurrentFiberStackAddendum$1 =
-  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
-
-var didWarnAboutMaps = void 0;
-var didWarnAboutStringRefInStrictMode = void 0;
-var ownerHasKeyUseWarning = void 0;
-var ownerHasFunctionTypeWarning = void 0;
-var warnForMissingKey = function(child) {};
-
-{
-  didWarnAboutMaps = false;
-  didWarnAboutStringRefInStrictMode = {};
-
-  /**
-   * Warn if there's no key explicitly set on dynamic arrays of children or
-   * object keys are not valid. This allows us to keep track of children between
-   * updates.
-   */
-  ownerHasKeyUseWarning = {};
-  ownerHasFunctionTypeWarning = {};
-
-  warnForMissingKey = function(child) {
-    if (child === null || typeof child !== "object") {
-      return;
-    }
-    if (!child._store || child._store.validated || child.key != null) {
-      return;
-    }
-    invariant(
-      typeof child._store === "object",
-      "React Component in warnForMissingKey should have a _store. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-    child._store.validated = true;
-
-    var currentComponentErrorInfo =
-      "Each child in an array or iterator should have a unique " +
-      '"key" prop. See https://fb.me/react-warning-keys for ' +
-      "more information." +
-      (getCurrentFiberStackAddendum$1() || "");
-    if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
-      return;
-    }
-    ownerHasKeyUseWarning[currentComponentErrorInfo] = true;
-
-    warning(
-      false,
-      "Each child in an array or iterator should have a unique " +
-        '"key" prop. See https://fb.me/react-warning-keys for ' +
-        "more information.%s",
-      getCurrentFiberStackAddendum$1()
-    );
-  };
-}
-
-var isArray$1 = Array.isArray;
-
-function coerceRef(returnFiber, current, element) {
-  var mixedRef = element.ref;
-  if (
-    mixedRef !== null &&
-    typeof mixedRef !== "function" &&
-    typeof mixedRef !== "object"
-  ) {
-    {
-      if (returnFiber.mode & StrictMode) {
-        var componentName = getComponentName(returnFiber) || "Component";
-        if (!didWarnAboutStringRefInStrictMode[componentName]) {
-          warning(
-            false,
-            'A string ref, "%s", has been found within a strict mode tree. ' +
-              "String refs are a source of potential bugs and should be avoided. " +
-              "We recommend using createRef() instead." +
-              "\n%s" +
-              "\n\nLearn more about using refs safely here:" +
-              "\nhttps://fb.me/react-strict-mode-string-ref",
-            mixedRef,
-            getStackAddendumByWorkInProgressFiber(returnFiber)
-          );
-          didWarnAboutStringRefInStrictMode[componentName] = true;
-        }
-      }
-    }
-
-    if (element._owner) {
-      var owner = element._owner;
-      var inst = void 0;
-      if (owner) {
-        var ownerFiber = owner;
-        invariant(
-          ownerFiber.tag === ClassComponent,
-          "Stateless function components cannot have refs."
-        );
-        inst = ownerFiber.stateNode;
-      }
-      invariant(
-        inst,
-        "Missing owner for string ref %s. This error is likely caused by a " +
-          "bug in React. Please file an issue.",
-        mixedRef
-      );
-      var stringRef = "" + mixedRef;
-      // Check if previous string ref matches new string ref
-      if (
-        current !== null &&
-        current.ref !== null &&
-        current.ref._stringRef === stringRef
-      ) {
-        return current.ref;
-      }
-      var ref = function(value) {
-        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
-        if (value === null) {
-          delete refs[stringRef];
-        } else {
-          refs[stringRef] = value;
-        }
-      };
-      ref._stringRef = stringRef;
-      return ref;
-    } else {
-      invariant(
-        typeof mixedRef === "string",
-        "Expected ref to be a function or a string."
-      );
-      invariant(
-        element._owner,
-        "Element ref was specified as a string (%s) but no owner was set. This could happen for one of" +
-          " the following reasons:\n" +
-          "1. You may be adding a ref to a functional component\n" +
-          "2. You may be adding a ref to a component that was not created inside a component's render method\n" +
-          "3. You have multiple copies of React loaded\n" +
-          "See https://fb.me/react-refs-must-have-owner for more information.",
-        mixedRef
-      );
-    }
-  }
-  return mixedRef;
-}
-
-function throwOnInvalidObjectType(returnFiber, newChild) {
-  if (returnFiber.type !== "textarea") {
-    var addendum = "";
-    {
-      addendum =
-        " If you meant to render a collection of children, use an array " +
-        "instead." +
-        (getCurrentFiberStackAddendum$1() || "");
-    }
-    invariant(
-      false,
-      "Objects are not valid as a React child (found: %s).%s",
-      Object.prototype.toString.call(newChild) === "[object Object]"
-        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
-        : newChild,
-      addendum
-    );
-  }
-}
-
-function warnOnFunctionType() {
-  var currentComponentErrorInfo =
-    "Functions are not valid as a React child. This may happen if " +
-    "you return a Component instead of <Component /> from render. " +
-    "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$1() || "");
-
-  if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
-    return;
-  }
-  ownerHasFunctionTypeWarning[currentComponentErrorInfo] = true;
-
-  warning(
-    false,
-    "Functions are not valid as a React child. This may happen if " +
-      "you return a Component instead of <Component /> from render. " +
-      "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$1() || ""
-  );
-}
-
-// This wrapper function exists because I expect to clone the code in each path
-// to be able to optimize each path individually by branching early. This needs
-// a compiler or we can do it manually. Helpers that don't need this branching
-// live outside of this function.
-function ChildReconciler(shouldTrackSideEffects) {
-  function deleteChild(returnFiber, childToDelete) {
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return;
-    }
-    // Deletions are added in reversed order so we add it to the front.
-    // At this point, the return fiber's effect list is empty except for
-    // deletions, so we can just append the deletion to the list. The remaining
-    // effects aren't added until the complete phase. Once we implement
-    // resuming, this may not be true.
-    var last = returnFiber.lastEffect;
-    if (last !== null) {
-      last.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
-    } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
-    }
-    childToDelete.nextEffect = null;
-    childToDelete.effectTag = Deletion;
-  }
-
-  function deleteRemainingChildren(returnFiber, currentFirstChild) {
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return null;
-    }
-
-    // TODO: For the shouldClone case, this could be micro-optimized a bit by
-    // assuming that after the first child we've already added everything.
-    var childToDelete = currentFirstChild;
-    while (childToDelete !== null) {
-      deleteChild(returnFiber, childToDelete);
-      childToDelete = childToDelete.sibling;
-    }
-    return null;
-  }
-
-  function mapRemainingChildren(returnFiber, currentFirstChild) {
-    // Add the remaining children to a temporary map so that we can find them by
-    // keys quickly. Implicit (null) keys get added to this set with their index
-    var existingChildren = new Map();
-
-    var existingChild = currentFirstChild;
-    while (existingChild !== null) {
-      if (existingChild.key !== null) {
-        existingChildren.set(existingChild.key, existingChild);
-      } else {
-        existingChildren.set(existingChild.index, existingChild);
-      }
-      existingChild = existingChild.sibling;
-    }
-    return existingChildren;
-  }
-
-  function useFiber(fiber, pendingProps, expirationTime) {
-    // We currently set sibling to null and index to 0 here because it is easy
-    // to forget to do before returning it. E.g. for the single child case.
-    var clone = createWorkInProgress(fiber, pendingProps, expirationTime);
-    clone.index = 0;
-    clone.sibling = null;
-    return clone;
-  }
-
-  function placeChild(newFiber, lastPlacedIndex, newIndex) {
-    newFiber.index = newIndex;
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return lastPlacedIndex;
-    }
-    var current = newFiber.alternate;
-    if (current !== null) {
-      var oldIndex = current.index;
-      if (oldIndex < lastPlacedIndex) {
-        // This is a move.
-        newFiber.effectTag = Placement;
-        return lastPlacedIndex;
-      } else {
-        // This item can stay in place.
-        return oldIndex;
-      }
-    } else {
-      // This is an insertion.
-      newFiber.effectTag = Placement;
-      return lastPlacedIndex;
-    }
-  }
-
-  function placeSingleChild(newFiber) {
-    // This is simpler for the single child case. We only need to do a
-    // placement for inserting new children.
-    if (shouldTrackSideEffects && newFiber.alternate === null) {
-      newFiber.effectTag = Placement;
-    }
-    return newFiber;
-  }
-
-  function updateTextNode(returnFiber, current, textContent, expirationTime) {
-    if (current === null || current.tag !== HostText) {
-      // Insert
-      var created = createFiberFromText(
-        textContent,
-        returnFiber.mode,
-        expirationTime
-      );
-      created["return"] = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, textContent, expirationTime);
-      existing["return"] = returnFiber;
-      return existing;
-    }
-  }
-
-  function updateElement(returnFiber, current, element, expirationTime) {
-    if (current !== null && current.type === element.type) {
-      // Move based on index
-      var existing = useFiber(current, element.props, expirationTime);
-      existing.ref = coerceRef(returnFiber, current, element);
-      existing["return"] = returnFiber;
-      {
-        existing._debugSource = element._source;
-        existing._debugOwner = element._owner;
-      }
-      return existing;
-    } else {
-      // Insert
-      var created = createFiberFromElement(
-        element,
-        returnFiber.mode,
-        expirationTime
-      );
-      created.ref = coerceRef(returnFiber, current, element);
-      created["return"] = returnFiber;
-      return created;
-    }
-  }
-
-  function updatePortal(returnFiber, current, portal, expirationTime) {
-    if (
-      current === null ||
-      current.tag !== HostPortal ||
-      current.stateNode.containerInfo !== portal.containerInfo ||
-      current.stateNode.implementation !== portal.implementation
-    ) {
-      // Insert
-      var created = createFiberFromPortal(
-        portal,
-        returnFiber.mode,
-        expirationTime
-      );
-      created["return"] = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, portal.children || [], expirationTime);
-      existing["return"] = returnFiber;
-      return existing;
-    }
-  }
-
-  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
-    if (current === null || current.tag !== Fragment) {
-      // Insert
-      var created = createFiberFromFragment(
-        fragment,
-        returnFiber.mode,
-        expirationTime,
-        key
-      );
-      created["return"] = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, fragment, expirationTime);
-      existing["return"] = returnFiber;
-      return existing;
-    }
-  }
-
-  function createChild(returnFiber, newChild, expirationTime) {
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys. If the previous node is implicitly keyed
-      // we can continue to replace it without aborting even if it is not a text
-      // node.
-      var created = createFiberFromText(
-        "" + newChild,
-        returnFiber.mode,
-        expirationTime
-      );
-      created["return"] = returnFiber;
-      return created;
-    }
-
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          var _created = createFiberFromElement(
-            newChild,
-            returnFiber.mode,
-            expirationTime
-          );
-          _created.ref = coerceRef(returnFiber, null, newChild);
-          _created["return"] = returnFiber;
-          return _created;
-        }
-        case REACT_PORTAL_TYPE: {
-          var _created2 = createFiberFromPortal(
-            newChild,
-            returnFiber.mode,
-            expirationTime
-          );
-          _created2["return"] = returnFiber;
-          return _created2;
-        }
-      }
-
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        var _created3 = createFiberFromFragment(
-          newChild,
-          returnFiber.mode,
-          expirationTime,
-          null
-        );
-        _created3["return"] = returnFiber;
-        return _created3;
-      }
-
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-
-    return null;
-  }
-
-  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
-    // Update the fiber if the keys match, otherwise return null.
-
-    var key = oldFiber !== null ? oldFiber.key : null;
-
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys. If the previous node is implicitly keyed
-      // we can continue to replace it without aborting even if it is not a text
-      // node.
-      if (key !== null) {
-        return null;
-      }
-      return updateTextNode(
-        returnFiber,
-        oldFiber,
-        "" + newChild,
-        expirationTime
-      );
-    }
-
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          if (newChild.key === key) {
-            if (newChild.type === REACT_FRAGMENT_TYPE) {
-              return updateFragment(
-                returnFiber,
-                oldFiber,
-                newChild.props.children,
-                expirationTime,
-                key
-              );
-            }
-            return updateElement(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime
-            );
-          } else {
-            return null;
-          }
-        }
-        case REACT_PORTAL_TYPE: {
-          if (newChild.key === key) {
-            return updatePortal(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime
-            );
-          } else {
-            return null;
-          }
-        }
-      }
-
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        if (key !== null) {
-          return null;
-        }
-
-        return updateFragment(
-          returnFiber,
-          oldFiber,
-          newChild,
-          expirationTime,
-          null
-        );
-      }
-
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-
-    return null;
-  }
-
-  function updateFromMap(
-    existingChildren,
-    returnFiber,
-    newIdx,
-    newChild,
-    expirationTime
-  ) {
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys, so we neither have to check the old nor
-      // new node for the key. If both are text nodes, they match.
-      var matchedFiber = existingChildren.get(newIdx) || null;
-      return updateTextNode(
-        returnFiber,
-        matchedFiber,
-        "" + newChild,
-        expirationTime
-      );
-    }
-
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          var _matchedFiber =
-            existingChildren.get(
-              newChild.key === null ? newIdx : newChild.key
-            ) || null;
-          if (newChild.type === REACT_FRAGMENT_TYPE) {
-            return updateFragment(
-              returnFiber,
-              _matchedFiber,
-              newChild.props.children,
-              expirationTime,
-              newChild.key
-            );
-          }
-          return updateElement(
-            returnFiber,
-            _matchedFiber,
-            newChild,
-            expirationTime
-          );
-        }
-        case REACT_PORTAL_TYPE: {
-          var _matchedFiber2 =
-            existingChildren.get(
-              newChild.key === null ? newIdx : newChild.key
-            ) || null;
-          return updatePortal(
-            returnFiber,
-            _matchedFiber2,
-            newChild,
-            expirationTime
-          );
-        }
-      }
-
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        var _matchedFiber3 = existingChildren.get(newIdx) || null;
-        return updateFragment(
-          returnFiber,
-          _matchedFiber3,
-          newChild,
-          expirationTime,
-          null
-        );
-      }
-
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-
-    return null;
-  }
-
-  /**
-   * Warns if there is a duplicate or missing key
-   */
-  function warnOnInvalidKey(child, knownKeys) {
-    {
-      if (typeof child !== "object" || child === null) {
-        return knownKeys;
-      }
-      switch (child.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-        case REACT_PORTAL_TYPE:
-          warnForMissingKey(child);
-          var key = child.key;
-          if (typeof key !== "string") {
-            break;
-          }
-          if (knownKeys === null) {
-            knownKeys = new Set();
-            knownKeys.add(key);
-            break;
-          }
-          if (!knownKeys.has(key)) {
-            knownKeys.add(key);
-            break;
-          }
-          warning(
-            false,
-            "Encountered two children with the same key, `%s`. " +
-              "Keys should be unique so that components maintain their identity " +
-              "across updates. Non-unique keys may cause children to be " +
-              "duplicated and/or omitted — the behavior is unsupported and " +
-              "could change in a future version.%s",
-            key,
-            getCurrentFiberStackAddendum$1()
-          );
-          break;
-        default:
-          break;
-      }
-    }
-    return knownKeys;
-  }
-
-  function reconcileChildrenArray(
-    returnFiber,
-    currentFirstChild,
-    newChildren,
-    expirationTime
-  ) {
-    // This algorithm can't optimize by searching from boths ends since we
-    // don't have backpointers on fibers. I'm trying to see how far we can get
-    // with that model. If it ends up not being worth the tradeoffs, we can
-    // add it later.
-
-    // Even with a two ended optimization, we'd want to optimize for the case
-    // where there are few changes and brute force the comparison instead of
-    // going for the Map. It'd like to explore hitting that path first in
-    // forward-only mode and only go for the Map once we notice that we need
-    // lots of look ahead. This doesn't handle reversal as well as two ended
-    // search but that's unusual. Besides, for the two ended optimization to
-    // work on Iterables, we'd need to copy the whole set.
-
-    // In this first iteration, we'll just live with hitting the bad case
-    // (adding everything to a Map) in for every insert/move.
-
-    // If you change this code, also update reconcileChildrenIterator() which
-    // uses the same algorithm.
-
-    {
-      // First, validate keys.
-      var knownKeys = null;
-      for (var i = 0; i < newChildren.length; i++) {
-        var child = newChildren[i];
-        knownKeys = warnOnInvalidKey(child, knownKeys);
-      }
-    }
-
-    var resultingFirstChild = null;
-    var previousNewFiber = null;
-
-    var oldFiber = currentFirstChild;
-    var lastPlacedIndex = 0;
-    var newIdx = 0;
-    var nextOldFiber = null;
-    for (; oldFiber !== null && newIdx < newChildren.length; newIdx++) {
-      if (oldFiber.index > newIdx) {
-        nextOldFiber = oldFiber;
-        oldFiber = null;
-      } else {
-        nextOldFiber = oldFiber.sibling;
-      }
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        newChildren[newIdx],
-        expirationTime
-      );
-      if (newFiber === null) {
-        // TODO: This breaks on empty slots like null children. That's
-        // unfortunate because it triggers the slow path all the time. We need
-        // a better way to communicate whether this was a miss or null,
-        // boolean, undefined, etc.
-        if (oldFiber === null) {
-          oldFiber = nextOldFiber;
-        }
-        break;
-      }
-      if (shouldTrackSideEffects) {
-        if (oldFiber && newFiber.alternate === null) {
-          // We matched the slot, but we didn't reuse the existing fiber, so we
-          // need to delete the existing child.
-          deleteChild(returnFiber, oldFiber);
-        }
-      }
-      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
-      if (previousNewFiber === null) {
-        // TODO: Move out of the loop. This only happens for the first run.
-        resultingFirstChild = newFiber;
-      } else {
-        // TODO: Defer siblings if we're not at the right index for this slot.
-        // I.e. if we had null values before, then we want to defer this
-        // for each null value. However, we also don't want to call updateSlot
-        // with the previous one.
-        previousNewFiber.sibling = newFiber;
-      }
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-
-    if (newIdx === newChildren.length) {
-      // We've reached the end of the new children. We can delete the rest.
-      deleteRemainingChildren(returnFiber, oldFiber);
-      return resultingFirstChild;
-    }
-
-    if (oldFiber === null) {
-      // If we don't have any more existing children we can choose a fast path
-      // since the rest will all be insertions.
-      for (; newIdx < newChildren.length; newIdx++) {
-        var _newFiber = createChild(
-          returnFiber,
-          newChildren[newIdx],
-          expirationTime
-        );
-        if (!_newFiber) {
-          continue;
-        }
-        lastPlacedIndex = placeChild(_newFiber, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          // TODO: Move out of the loop. This only happens for the first run.
-          resultingFirstChild = _newFiber;
-        } else {
-          previousNewFiber.sibling = _newFiber;
-        }
-        previousNewFiber = _newFiber;
-      }
-      return resultingFirstChild;
-    }
-
-    // Add all children to a key map for quick lookups.
-    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
-
-    // Keep scanning and use the map to restore deleted items as moves.
-    for (; newIdx < newChildren.length; newIdx++) {
-      var _newFiber2 = updateFromMap(
-        existingChildren,
-        returnFiber,
-        newIdx,
-        newChildren[newIdx],
-        expirationTime
-      );
-      if (_newFiber2) {
-        if (shouldTrackSideEffects) {
-          if (_newFiber2.alternate !== null) {
-            // The new fiber is a work in progress, but if there exists a
-            // current, that means that we reused the fiber. We need to delete
-            // it from the child list so that we don't add it to the deletion
-            // list.
-            existingChildren["delete"](
-              _newFiber2.key === null ? newIdx : _newFiber2.key
-            );
-          }
-        }
-        lastPlacedIndex = placeChild(_newFiber2, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          resultingFirstChild = _newFiber2;
-        } else {
-          previousNewFiber.sibling = _newFiber2;
-        }
-        previousNewFiber = _newFiber2;
-      }
-    }
-
-    if (shouldTrackSideEffects) {
-      // Any existing children that weren't consumed above were deleted. We need
-      // to add them to the deletion list.
-      existingChildren.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    }
-
-    return resultingFirstChild;
-  }
-
-  function reconcileChildrenIterator(
-    returnFiber,
-    currentFirstChild,
-    newChildrenIterable,
-    expirationTime
-  ) {
-    // This is the same implementation as reconcileChildrenArray(),
-    // but using the iterator instead.
-
-    var iteratorFn = getIteratorFn(newChildrenIterable);
-    invariant(
-      typeof iteratorFn === "function",
-      "An object is not an iterable. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-
-    {
-      // Warn about using Maps as children
-      if (typeof newChildrenIterable.entries === "function") {
-        var possibleMap = newChildrenIterable;
-        if (possibleMap.entries === iteratorFn) {
-          !didWarnAboutMaps
-            ? warning(
-                false,
-                "Using Maps as children is unsupported and will likely yield " +
-                  "unexpected results. Convert it to a sequence/iterable of keyed " +
-                  "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$1()
-              )
-            : void 0;
-          didWarnAboutMaps = true;
-        }
-      }
-
-      // First, validate keys.
-      // We'll get a different iterator later for the main pass.
-      var _newChildren = iteratorFn.call(newChildrenIterable);
-      if (_newChildren) {
-        var knownKeys = null;
-        var _step = _newChildren.next();
-        for (; !_step.done; _step = _newChildren.next()) {
-          var child = _step.value;
-          knownKeys = warnOnInvalidKey(child, knownKeys);
-        }
-      }
-    }
-
-    var newChildren = iteratorFn.call(newChildrenIterable);
-    invariant(newChildren != null, "An iterable object provided no iterator.");
-
-    var resultingFirstChild = null;
-    var previousNewFiber = null;
-
-    var oldFiber = currentFirstChild;
-    var lastPlacedIndex = 0;
-    var newIdx = 0;
-    var nextOldFiber = null;
-
-    var step = newChildren.next();
-    for (
-      ;
-      oldFiber !== null && !step.done;
-      newIdx++, step = newChildren.next()
-    ) {
-      if (oldFiber.index > newIdx) {
-        nextOldFiber = oldFiber;
-        oldFiber = null;
-      } else {
-        nextOldFiber = oldFiber.sibling;
-      }
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        step.value,
-        expirationTime
-      );
-      if (newFiber === null) {
-        // TODO: This breaks on empty slots like null children. That's
-        // unfortunate because it triggers the slow path all the time. We need
-        // a better way to communicate whether this was a miss or null,
-        // boolean, undefined, etc.
-        if (!oldFiber) {
-          oldFiber = nextOldFiber;
-        }
-        break;
-      }
-      if (shouldTrackSideEffects) {
-        if (oldFiber && newFiber.alternate === null) {
-          // We matched the slot, but we didn't reuse the existing fiber, so we
-          // need to delete the existing child.
-          deleteChild(returnFiber, oldFiber);
-        }
-      }
-      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
-      if (previousNewFiber === null) {
-        // TODO: Move out of the loop. This only happens for the first run.
-        resultingFirstChild = newFiber;
-      } else {
-        // TODO: Defer siblings if we're not at the right index for this slot.
-        // I.e. if we had null values before, then we want to defer this
-        // for each null value. However, we also don't want to call updateSlot
-        // with the previous one.
-        previousNewFiber.sibling = newFiber;
-      }
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-
-    if (step.done) {
-      // We've reached the end of the new children. We can delete the rest.
-      deleteRemainingChildren(returnFiber, oldFiber);
-      return resultingFirstChild;
-    }
-
-    if (oldFiber === null) {
-      // If we don't have any more existing children we can choose a fast path
-      // since the rest will all be insertions.
-      for (; !step.done; newIdx++, step = newChildren.next()) {
-        var _newFiber3 = createChild(returnFiber, step.value, expirationTime);
-        if (_newFiber3 === null) {
-          continue;
-        }
-        lastPlacedIndex = placeChild(_newFiber3, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          // TODO: Move out of the loop. This only happens for the first run.
-          resultingFirstChild = _newFiber3;
-        } else {
-          previousNewFiber.sibling = _newFiber3;
-        }
-        previousNewFiber = _newFiber3;
-      }
-      return resultingFirstChild;
-    }
-
-    // Add all children to a key map for quick lookups.
-    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
-
-    // Keep scanning and use the map to restore deleted items as moves.
-    for (; !step.done; newIdx++, step = newChildren.next()) {
-      var _newFiber4 = updateFromMap(
-        existingChildren,
-        returnFiber,
-        newIdx,
-        step.value,
-        expirationTime
-      );
-      if (_newFiber4 !== null) {
-        if (shouldTrackSideEffects) {
-          if (_newFiber4.alternate !== null) {
-            // The new fiber is a work in progress, but if there exists a
-            // current, that means that we reused the fiber. We need to delete
-            // it from the child list so that we don't add it to the deletion
-            // list.
-            existingChildren["delete"](
-              _newFiber4.key === null ? newIdx : _newFiber4.key
-            );
-          }
-        }
-        lastPlacedIndex = placeChild(_newFiber4, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          resultingFirstChild = _newFiber4;
-        } else {
-          previousNewFiber.sibling = _newFiber4;
-        }
-        previousNewFiber = _newFiber4;
-      }
-    }
-
-    if (shouldTrackSideEffects) {
-      // Any existing children that weren't consumed above were deleted. We need
-      // to add them to the deletion list.
-      existingChildren.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    }
-
-    return resultingFirstChild;
-  }
-
-  function reconcileSingleTextNode(
-    returnFiber,
-    currentFirstChild,
-    textContent,
-    expirationTime
-  ) {
-    // There's no need to check for keys on text nodes since we don't have a
-    // way to define them.
-    if (currentFirstChild !== null && currentFirstChild.tag === HostText) {
-      // We already have an existing node so let's just update it and delete
-      // the rest.
-      deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
-      var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing["return"] = returnFiber;
-      return existing;
-    }
-    // The existing first child is not a text node so we need to create one
-    // and delete the existing ones.
-    deleteRemainingChildren(returnFiber, currentFirstChild);
-    var created = createFiberFromText(
-      textContent,
-      returnFiber.mode,
-      expirationTime
-    );
-    created["return"] = returnFiber;
-    return created;
-  }
-
-  function reconcileSingleElement(
-    returnFiber,
-    currentFirstChild,
-    element,
-    expirationTime
-  ) {
-    var key = element.key;
-    var child = currentFirstChild;
-    while (child !== null) {
-      // TODO: If key === null and child.key === null, then this only applies to
-      // the first item in the list.
-      if (child.key === key) {
-        if (
-          child.tag === Fragment
-            ? element.type === REACT_FRAGMENT_TYPE
-            : child.type === element.type
-        ) {
-          deleteRemainingChildren(returnFiber, child.sibling);
-          var existing = useFiber(
-            child,
-            element.type === REACT_FRAGMENT_TYPE
-              ? element.props.children
-              : element.props,
-            expirationTime
-          );
-          existing.ref = coerceRef(returnFiber, child, element);
-          existing["return"] = returnFiber;
-          {
-            existing._debugSource = element._source;
-            existing._debugOwner = element._owner;
-          }
-          return existing;
-        } else {
-          deleteRemainingChildren(returnFiber, child);
-          break;
-        }
-      } else {
-        deleteChild(returnFiber, child);
-      }
-      child = child.sibling;
-    }
-
-    if (element.type === REACT_FRAGMENT_TYPE) {
-      var created = createFiberFromFragment(
-        element.props.children,
-        returnFiber.mode,
-        expirationTime,
-        element.key
-      );
-      created["return"] = returnFiber;
-      return created;
-    } else {
-      var _created4 = createFiberFromElement(
-        element,
-        returnFiber.mode,
-        expirationTime
-      );
-      _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4["return"] = returnFiber;
-      return _created4;
-    }
-  }
-
-  function reconcileSinglePortal(
-    returnFiber,
-    currentFirstChild,
-    portal,
-    expirationTime
-  ) {
-    var key = portal.key;
-    var child = currentFirstChild;
-    while (child !== null) {
-      // TODO: If key === null and child.key === null, then this only applies to
-      // the first item in the list.
-      if (child.key === key) {
-        if (
-          child.tag === HostPortal &&
-          child.stateNode.containerInfo === portal.containerInfo &&
-          child.stateNode.implementation === portal.implementation
-        ) {
-          deleteRemainingChildren(returnFiber, child.sibling);
-          var existing = useFiber(child, portal.children || [], expirationTime);
-          existing["return"] = returnFiber;
-          return existing;
-        } else {
-          deleteRemainingChildren(returnFiber, child);
-          break;
-        }
-      } else {
-        deleteChild(returnFiber, child);
-      }
-      child = child.sibling;
-    }
-
-    var created = createFiberFromPortal(
-      portal,
-      returnFiber.mode,
-      expirationTime
-    );
-    created["return"] = returnFiber;
-    return created;
-  }
-
-  // This API will tag the children with the side-effect of the reconciliation
-  // itself. They will be added to the side-effect list as we pass through the
-  // children and the parent.
-  function reconcileChildFibers(
-    returnFiber,
-    currentFirstChild,
-    newChild,
-    expirationTime
-  ) {
-    // This function is not recursive.
-    // If the top level item is an array, we treat it as a set of children,
-    // not as a fragment. Nested arrays on the other hand will be treated as
-    // fragment nodes. Recursion happens at the normal flow.
-
-    // Handle top level unkeyed fragments as if they were arrays.
-    // This leads to an ambiguity between <>{[...]}</> and <>...</>.
-    // We treat the ambiguous cases above the same.
-    if (
-      typeof newChild === "object" &&
-      newChild !== null &&
-      newChild.type === REACT_FRAGMENT_TYPE &&
-      newChild.key === null
-    ) {
-      newChild = newChild.props.children;
-    }
-
-    // Handle object types
-    var isObject = typeof newChild === "object" && newChild !== null;
-
-    if (isObject) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return placeSingleChild(
-            reconcileSingleElement(
-              returnFiber,
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )
-          );
-        case REACT_PORTAL_TYPE:
-          return placeSingleChild(
-            reconcileSinglePortal(
-              returnFiber,
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )
-          );
-      }
-    }
-
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      return placeSingleChild(
-        reconcileSingleTextNode(
-          returnFiber,
-          currentFirstChild,
-          "" + newChild,
-          expirationTime
-        )
-      );
-    }
-
-    if (isArray$1(newChild)) {
-      return reconcileChildrenArray(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    }
-
-    if (getIteratorFn(newChild)) {
-      return reconcileChildrenIterator(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    }
-
-    if (isObject) {
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-    if (typeof newChild === "undefined") {
-      // If the new child is undefined, and the return fiber is a composite
-      // component, throw an error. If Fiber return types are disabled,
-      // we already threw above.
-      switch (returnFiber.tag) {
-        case ClassComponent: {
-          {
-            var instance = returnFiber.stateNode;
-            if (instance.render._isMockFunction) {
-              // We allow auto-mocks to proceed as if they're returning null.
-              break;
-            }
-          }
-        }
-        // Intentionally fall through to the next case, which handles both
-        // functions and classes
-        // eslint-disable-next-lined no-fallthrough
-        case FunctionalComponent: {
-          var Component = returnFiber.type;
-          invariant(
-            false,
-            "%s(...): Nothing was returned from render. This usually means a " +
-              "return statement is missing. Or, to render nothing, " +
-              "return null.",
-            Component.displayName || Component.name || "Component"
-          );
-        }
-      }
-    }
-
-    // Remaining cases are all treated as empty.
-    return deleteRemainingChildren(returnFiber, currentFirstChild);
-  }
-
-  return reconcileChildFibers;
-}
-
-var reconcileChildFibers = ChildReconciler(true);
-var mountChildFibers = ChildReconciler(false);
-
-function cloneChildFibers(current, workInProgress) {
-  invariant(
-    current === null || workInProgress.child === current.child,
-    "Resuming work not yet implemented."
-  );
-
-  if (workInProgress.child === null) {
-    return;
-  }
-
-  var currentChild = workInProgress.child;
-  var newChild = createWorkInProgress(
-    currentChild,
-    currentChild.pendingProps,
-    currentChild.expirationTime
-  );
-  workInProgress.child = newChild;
-
-  newChild["return"] = workInProgress;
-  while (currentChild.sibling !== null) {
-    currentChild = currentChild.sibling;
-    newChild = newChild.sibling = createWorkInProgress(
-      currentChild,
-      currentChild.pendingProps,
-      currentChild.expirationTime
-    );
-    newChild["return"] = workInProgress;
-  }
-  newChild.sibling = null;
-}
-
-var didWarnAboutBadClass = void 0;
-var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
-var didWarnAboutStatelessRefs = void 0;
-
-{
-  didWarnAboutBadClass = {};
-  didWarnAboutGetDerivedStateOnFunctionalComponent = {};
-  didWarnAboutStatelessRefs = {};
-}
-
-var ReactFiberBeginWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  scheduleWork,
-  computeExpirationForFiber
-) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
-  var pushHostContext = hostContext.pushHostContext,
-    pushHostContainer = hostContext.pushHostContainer;
-  var pushProvider = newContext.pushProvider;
-  var getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    hasLegacyContextChanged = legacyContext.hasContextChanged,
-    pushLegacyContextProvider = legacyContext.pushContextProvider,
-    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
-    invalidateContextProvider = legacyContext.invalidateContextProvider;
-  var enterHydrationState = hydrationContext.enterHydrationState,
-    resetHydrationState = hydrationContext.resetHydrationState,
-    tryToClaimNextHydratableInstance =
-      hydrationContext.tryToClaimNextHydratableInstance;
-
-  var _ReactFiberClassCompo = ReactFiberClassComponent(
-      legacyContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      memoizeProps,
-      memoizeState
-    ),
-    adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
-    callGetDerivedStateFromProps =
-      _ReactFiberClassCompo.callGetDerivedStateFromProps,
-    constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
-    mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
-    resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
-    updateClassInstance = _ReactFiberClassCompo.updateClassInstance;
-
-  // TODO: Remove this and use reconcileChildrenAtExpirationTime directly.
-
-  function reconcileChildren(current, workInProgress, nextChildren) {
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      workInProgress.expirationTime
-    );
-  }
-
-  function reconcileChildrenAtExpirationTime(
-    current,
-    workInProgress,
-    nextChildren,
-    renderExpirationTime
-  ) {
-    if (current === null) {
-      // If this is a fresh new component that hasn't been rendered yet, we
-      // won't update its child set by applying minimal side-effects. Instead,
-      // we will add them all to the child before it gets rendered. That means
-      // we can optimize this reconciliation pass by not tracking side-effects.
-      workInProgress.child = mountChildFibers(
-        workInProgress,
-        null,
-        nextChildren,
-        renderExpirationTime
-      );
-    } else {
-      // If the current child is the same as the work in progress, it means that
-      // we haven't yet started any work on these children. Therefore, we use
-      // the clone algorithm to create a copy of all the current children.
-
-      // If we had any progressed work already, that is invalid at this point so
-      // let's throw it out.
-      workInProgress.child = reconcileChildFibers(
-        workInProgress,
-        current.child,
-        nextChildren,
-        renderExpirationTime
-      );
-    }
-  }
-
-  function updateForwardRef(current, workInProgress) {
-    var render = workInProgress.type.render;
-    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
-  }
-
-  function updateFragment(current, workInProgress) {
-    var nextChildren = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextChildren) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
-  }
-
-  function updateMode(current, workInProgress) {
-    var nextChildren = workInProgress.pendingProps.children;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (
-      nextChildren === null ||
-      workInProgress.memoizedProps === nextChildren
-    ) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
-  }
-
-  function markRef(current, workInProgress) {
-    var ref = workInProgress.ref;
-    if (
-      (current === null && ref !== null) ||
-      (current !== null && current.ref !== ref)
-    ) {
-      // Schedule a Ref effect
-      workInProgress.effectTag |= Ref;
-    }
-  }
-
-  function updateFunctionalComponent(current, workInProgress) {
-    var fn = workInProgress.type;
-    var nextProps = workInProgress.pendingProps;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else {
-      if (workInProgress.memoizedProps === nextProps) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-      // TODO: consider bringing fn.shouldComponentUpdate() back.
-      // It used to be here.
-    }
-
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var context = getMaskedContext(workInProgress, unmaskedContext);
-
-    var nextChildren = void 0;
-
-    {
-      ReactCurrentOwner.current = workInProgress;
-      ReactDebugCurrentFiber.setCurrentPhase("render");
-      nextChildren = fn(nextProps, context);
-      ReactDebugCurrentFiber.setCurrentPhase(null);
-    }
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
-  }
-
-  function updateClassComponent(current, workInProgress, renderExpirationTime) {
-    // Push context providers early to prevent context stack mismatches.
-    // During mounting we don't know the child context yet as the instance doesn't exist.
-    // We will invalidate the child context in finishClassComponent() right after rendering.
-    var hasContext = pushLegacyContextProvider(workInProgress);
-    var shouldUpdate = void 0;
-    if (current === null) {
-      if (workInProgress.stateNode === null) {
-        // In the initial pass we might need to construct the instance.
-        constructClassInstance(workInProgress, workInProgress.pendingProps);
-        mountClassInstance(workInProgress, renderExpirationTime);
-
-        shouldUpdate = true;
-      } else {
-        // In a resume, we'll already have an instance we can reuse.
-        shouldUpdate = resumeMountClassInstance(
-          workInProgress,
-          renderExpirationTime
-        );
-      }
-    } else {
-      shouldUpdate = updateClassInstance(
-        current,
-        workInProgress,
-        renderExpirationTime
-      );
-    }
-
-    // We processed the update queue inside updateClassInstance. It may have
-    // included some errors that were dispatched during the commit phase.
-    // TODO: Refactor class components so this is less awkward.
-    var didCaptureError = false;
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null && updateQueue.capturedValues !== null) {
-      shouldUpdate = true;
-      didCaptureError = true;
-    }
-    return finishClassComponent(
-      current,
-      workInProgress,
-      shouldUpdate,
-      hasContext,
-      didCaptureError,
-      renderExpirationTime
-    );
-  }
-
-  function finishClassComponent(
-    current,
-    workInProgress,
-    shouldUpdate,
-    hasContext,
-    didCaptureError,
-    renderExpirationTime
-  ) {
-    // Refs should update even if shouldComponentUpdate returns false
-    markRef(current, workInProgress);
-
-    if (!shouldUpdate && !didCaptureError) {
-      // Context providers should defer to sCU for rendering
-      if (hasContext) {
-        invalidateContextProvider(workInProgress, false);
-      }
-
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-
-    // Rerender
-    ReactCurrentOwner.current = workInProgress;
-    var nextChildren = void 0;
-    if (
-      didCaptureError &&
-      (!enableGetDerivedStateFromCatch ||
-        typeof ctor.getDerivedStateFromCatch !== "function")
-    ) {
-      // If we captured an error, but getDerivedStateFrom catch is not defined,
-      // unmount all the children. componentDidCatch will schedule an update to
-      // re-render a fallback. This is temporary until we migrate everyone to
-      // the new API.
-      // TODO: Warn in a future release.
-      nextChildren = null;
-    } else {
-      {
-        ReactDebugCurrentFiber.setCurrentPhase("render");
-        nextChildren = instance.render();
-        if (
-          debugRenderPhaseSideEffects ||
-          (debugRenderPhaseSideEffectsForStrictMode &&
-            workInProgress.mode & StrictMode)
-        ) {
-          instance.render();
-        }
-        ReactDebugCurrentFiber.setCurrentPhase(null);
-      }
-    }
-
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    if (didCaptureError) {
-      // If we're recovering from an error, reconcile twice: first to delete
-      // all the existing children.
-      reconcileChildrenAtExpirationTime(
-        current,
-        workInProgress,
-        null,
-        renderExpirationTime
-      );
-      workInProgress.child = null;
-      // Now we can continue reconciling like normal. This has the effect of
-      // remounting all children regardless of whether their their
-      // identity matches.
-    }
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      renderExpirationTime
-    );
-    // Memoize props and state using the values we just used to render.
-    // TODO: Restructure so we never read values from the instance.
-    memoizeState(workInProgress, instance.state);
-    memoizeProps(workInProgress, instance.props);
-
-    // The context might have changed so we need to recalculate it.
-    if (hasContext) {
-      invalidateContextProvider(workInProgress, true);
-    }
-
-    return workInProgress.child;
-  }
-
-  function pushHostRootContext(workInProgress) {
-    var root = workInProgress.stateNode;
-    if (root.pendingContext) {
-      pushTopLevelContextObject(
-        workInProgress,
-        root.pendingContext,
-        root.pendingContext !== root.context
-      );
-    } else if (root.context) {
-      // Should always be set
-      pushTopLevelContextObject(workInProgress, root.context, false);
-    }
-    pushHostContainer(workInProgress, root.containerInfo);
-  }
-
-  function updateHostRoot(current, workInProgress, renderExpirationTime) {
-    pushHostRootContext(workInProgress);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      var prevState = workInProgress.memoizedState;
-      var state = processUpdateQueue(
-        current,
-        workInProgress,
-        updateQueue,
-        null,
-        null,
-        renderExpirationTime
-      );
-      memoizeState(workInProgress, state);
-      updateQueue = workInProgress.updateQueue;
-
-      var element = void 0;
-      if (updateQueue !== null && updateQueue.capturedValues !== null) {
-        // There's an uncaught error. Unmount the whole root.
-        element = null;
-      } else if (prevState === state) {
-        // If the state is the same as before, that's a bailout because we had
-        // no work that expires at this time.
-        resetHydrationState();
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      } else {
-        element = state.element;
-      }
-      var root = workInProgress.stateNode;
-      if (
-        (current === null || current.child === null) &&
-        root.hydrate &&
-        enterHydrationState(workInProgress)
-      ) {
-        // If we don't have any current children this might be the first pass.
-        // We always try to hydrate. If this isn't a hydration pass there won't
-        // be any children to hydrate which is effectively the same thing as
-        // not hydrating.
-
-        // This is a bit of a hack. We track the host root as a placement to
-        // know that we're currently in a mounting state. That way isMounted
-        // works as expected. We must reset this before committing.
-        // TODO: Delete this when we delete isMounted and findDOMNode.
-        workInProgress.effectTag |= Placement;
-
-        // Ensure that children mount into this root without tracking
-        // side-effects. This ensures that we don't store Placement effects on
-        // nodes that will be hydrated.
-        workInProgress.child = mountChildFibers(
-          workInProgress,
-          null,
-          element,
-          renderExpirationTime
-        );
-      } else {
-        // Otherwise reset hydration state in case we aborted and resumed another
-        // root.
-        resetHydrationState();
-        reconcileChildren(current, workInProgress, element);
-      }
-      memoizeState(workInProgress, state);
-      return workInProgress.child;
-    }
-    resetHydrationState();
-    // If there is no update queue, that's a bailout because the root has no props.
-    return bailoutOnAlreadyFinishedWork(current, workInProgress);
-  }
-
-  function updateHostComponent(current, workInProgress, renderExpirationTime) {
-    pushHostContext(workInProgress);
-
-    if (current === null) {
-      tryToClaimNextHydratableInstance(workInProgress);
-    }
-
-    var type = workInProgress.type;
-    var memoizedProps = workInProgress.memoizedProps;
-    var nextProps = workInProgress.pendingProps;
-    var prevProps = current !== null ? current.memoizedProps : null;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (memoizedProps === nextProps) {
-      var isHidden =
-        workInProgress.mode & AsyncMode &&
-        shouldDeprioritizeSubtree(type, nextProps);
-      if (isHidden) {
-        // Before bailing out, make sure we've deprioritized a hidden component.
-        workInProgress.expirationTime = Never;
-      }
-      if (!isHidden || renderExpirationTime !== Never) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-      // If we're rendering a hidden node at hidden priority, don't bailout. The
-      // parent is complete, but the children may not be.
-    }
-
-    var nextChildren = nextProps.children;
-    var isDirectTextChild = shouldSetTextContent(type, nextProps);
-
-    if (isDirectTextChild) {
-      // We special case a direct text child of a host node. This is a common
-      // case. We won't handle it as a reified child. We will instead handle
-      // this in the host environment that also have access to this prop. That
-      // avoids allocating another HostText fiber and traversing it.
-      nextChildren = null;
-    } else if (prevProps && shouldSetTextContent(type, prevProps)) {
-      // If we're switching from a direct text child to a normal child, or to
-      // empty, we need to schedule the text content to be reset.
-      workInProgress.effectTag |= ContentReset;
-    }
-
-    markRef(current, workInProgress);
-
-    // Check the host config to see if the children are offscreen/hidden.
-    if (
-      renderExpirationTime !== Never &&
-      workInProgress.mode & AsyncMode &&
-      shouldDeprioritizeSubtree(type, nextProps)
-    ) {
-      // Down-prioritize the children.
-      workInProgress.expirationTime = Never;
-      // Bailout and come back to this fiber later.
-      workInProgress.memoizedProps = nextProps;
-      return null;
-    }
-
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
-  }
-
-  function updateHostText(current, workInProgress) {
-    if (current === null) {
-      tryToClaimNextHydratableInstance(workInProgress);
-    }
-    var nextProps = workInProgress.pendingProps;
-    memoizeProps(workInProgress, nextProps);
-    // Nothing to do here. This is terminal. We'll do the completion step
-    // immediately after.
-    return null;
-  }
-
-  function mountIndeterminateComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    invariant(
-      current === null,
-      "An indeterminate component should never have mounted. This error is " +
-        "likely caused by a bug in React. Please file an issue."
-    );
-    var fn = workInProgress.type;
-    var props = workInProgress.pendingProps;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var context = getMaskedContext(workInProgress, unmaskedContext);
-
-    var value = void 0;
-
-    {
-      if (fn.prototype && typeof fn.prototype.render === "function") {
-        var componentName = getComponentName(workInProgress) || "Unknown";
-
-        if (!didWarnAboutBadClass[componentName]) {
-          warning(
-            false,
-            "The <%s /> component appears to have a render method, but doesn't extend React.Component. " +
-              "This is likely to cause errors. Change %s to extend React.Component instead.",
-            componentName,
-            componentName
-          );
-          didWarnAboutBadClass[componentName] = true;
-        }
-      }
-      ReactCurrentOwner.current = workInProgress;
-      value = fn(props, context);
-    }
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-
-    if (
-      typeof value === "object" &&
-      value !== null &&
-      typeof value.render === "function" &&
-      value.$$typeof === undefined
-    ) {
-      var Component = workInProgress.type;
-
-      // Proceed under the assumption that this is a class instance
-      workInProgress.tag = ClassComponent;
-
-      workInProgress.memoizedState =
-        value.state !== null && value.state !== undefined ? value.state : null;
-
-      if (typeof Component.getDerivedStateFromProps === "function") {
-        var partialState = callGetDerivedStateFromProps(
-          workInProgress,
-          value,
-          props,
-          workInProgress.memoizedState
-        );
-
-        if (partialState !== null && partialState !== undefined) {
-          workInProgress.memoizedState = Object.assign(
-            {},
-            workInProgress.memoizedState,
-            partialState
-          );
-        }
-      }
-
-      // Push context providers early to prevent context stack mismatches.
-      // During mounting we don't know the child context yet as the instance doesn't exist.
-      // We will invalidate the child context in finishClassComponent() right after rendering.
-      var hasContext = pushLegacyContextProvider(workInProgress);
-      adoptClassInstance(workInProgress, value);
-      mountClassInstance(workInProgress, renderExpirationTime);
-      return finishClassComponent(
-        current,
-        workInProgress,
-        true,
-        hasContext,
-        false,
-        renderExpirationTime
-      );
-    } else {
-      // Proceed under the assumption that this is a functional component
-      workInProgress.tag = FunctionalComponent;
-      {
-        var _Component = workInProgress.type;
-
-        if (_Component) {
-          !!_Component.childContextTypes
-            ? warning(
-                false,
-                "%s(...): childContextTypes cannot be defined on a functional component.",
-                _Component.displayName || _Component.name || "Component"
-              )
-            : void 0;
-        }
-        if (workInProgress.ref !== null) {
-          var info = "";
-          var ownerName = ReactDebugCurrentFiber.getCurrentFiberOwnerName();
-          if (ownerName) {
-            info += "\n\nCheck the render method of `" + ownerName + "`.";
-          }
-
-          var warningKey = ownerName || workInProgress._debugID || "";
-          var debugSource = workInProgress._debugSource;
-          if (debugSource) {
-            warningKey = debugSource.fileName + ":" + debugSource.lineNumber;
-          }
-          if (!didWarnAboutStatelessRefs[warningKey]) {
-            didWarnAboutStatelessRefs[warningKey] = true;
-            warning(
-              false,
-              "Stateless function components cannot be given refs. " +
-                "Attempts to access this ref will fail.%s%s",
-              info,
-              ReactDebugCurrentFiber.getCurrentFiberStackAddendum()
-            );
-          }
-        }
-
-        if (typeof fn.getDerivedStateFromProps === "function") {
-          var _componentName = getComponentName(workInProgress) || "Unknown";
-
-          if (
-            !didWarnAboutGetDerivedStateOnFunctionalComponent[_componentName]
-          ) {
-            warning(
-              false,
-              "%s: Stateless functional components do not support getDerivedStateFromProps.",
-              _componentName
-            );
-            didWarnAboutGetDerivedStateOnFunctionalComponent[
-              _componentName
-            ] = true;
-          }
-        }
-      }
-      reconcileChildren(current, workInProgress, value);
-      memoizeProps(workInProgress, props);
-      return workInProgress.child;
-    }
-  }
-
-  function updateCallComponent(current, workInProgress, renderExpirationTime) {
-    var nextProps = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextProps) {
-      nextProps = workInProgress.memoizedProps;
-      // TODO: When bailing out, we might need to return the stateNode instead
-      // of the child. To check it for work.
-      // return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var nextChildren = nextProps.children;
-
-    // The following is a fork of reconcileChildrenAtExpirationTime but using
-    // stateNode to store the child.
-    if (current === null) {
-      workInProgress.stateNode = mountChildFibers(
-        workInProgress,
-        workInProgress.stateNode,
-        nextChildren,
-        renderExpirationTime
-      );
-    } else {
-      workInProgress.stateNode = reconcileChildFibers(
-        workInProgress,
-        current.stateNode,
-        nextChildren,
-        renderExpirationTime
-      );
-    }
-
-    memoizeProps(workInProgress, nextProps);
-    // This doesn't take arbitrary time so we could synchronously just begin
-    // eagerly do the work of workInProgress.child as an optimization.
-    return workInProgress.stateNode;
-  }
-
-  function updatePortalComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
-    var nextChildren = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextChildren) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    if (current === null) {
-      // Portals are special because we don't append the children during mount
-      // but at commit. Therefore we need to track insertions which the normal
-      // flow doesn't do during mount. This doesn't happen at the root because
-      // the root always starts with a "current" with a null child.
-      // TODO: Consider unifying this with how the root works.
-      workInProgress.child = reconcileChildFibers(
-        workInProgress,
-        null,
-        nextChildren,
-        renderExpirationTime
-      );
-      memoizeProps(workInProgress, nextChildren);
-    } else {
-      reconcileChildren(current, workInProgress, nextChildren);
-      memoizeProps(workInProgress, nextChildren);
-    }
-    return workInProgress.child;
-  }
-
-  function propagateContextChange(
-    workInProgress,
-    context,
-    changedBits,
-    renderExpirationTime
-  ) {
-    var fiber = workInProgress.child;
-    if (fiber !== null) {
-      // Set the return pointer of the child to the work-in-progress fiber.
-      fiber["return"] = workInProgress;
-    }
-    while (fiber !== null) {
-      var nextFiber = void 0;
-      // Visit this fiber.
-      switch (fiber.tag) {
-        case ContextConsumer:
-          // Check if the context matches.
-          var observedBits = fiber.stateNode | 0;
-          if (fiber.type === context && (observedBits & changedBits) !== 0) {
-            // Update the expiration time of all the ancestors, including
-            // the alternates.
-            var node = fiber;
-            while (node !== null) {
-              var alternate = node.alternate;
-              if (
-                node.expirationTime === NoWork ||
-                node.expirationTime > renderExpirationTime
-              ) {
-                node.expirationTime = renderExpirationTime;
-                if (
-                  alternate !== null &&
-                  (alternate.expirationTime === NoWork ||
-                    alternate.expirationTime > renderExpirationTime)
-                ) {
-                  alternate.expirationTime = renderExpirationTime;
-                }
-              } else if (
-                alternate !== null &&
-                (alternate.expirationTime === NoWork ||
-                  alternate.expirationTime > renderExpirationTime)
-              ) {
-                alternate.expirationTime = renderExpirationTime;
-              } else {
-                // Neither alternate was updated, which means the rest of the
-                // ancestor path already has sufficient priority.
-                break;
-              }
-              node = node["return"];
-            }
-            // Don't scan deeper than a matching consumer. When we render the
-            // consumer, we'll continue scanning from that point. This way the
-            // scanning work is time-sliced.
-            nextFiber = null;
-          } else {
-            // Traverse down.
-            nextFiber = fiber.child;
-          }
-          break;
-        case ContextProvider:
-          // Don't scan deeper if this is a matching provider
-          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
-          break;
-        default:
-          // Traverse down.
-          nextFiber = fiber.child;
-          break;
-      }
-      if (nextFiber !== null) {
-        // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber["return"] = fiber;
-      } else {
-        // No child. Traverse to next sibling.
-        nextFiber = fiber;
-        while (nextFiber !== null) {
-          if (nextFiber === workInProgress) {
-            // We're back to the root of this subtree. Exit.
-            nextFiber = null;
-            break;
-          }
-          var sibling = nextFiber.sibling;
-          if (sibling !== null) {
-            nextFiber = sibling;
-            break;
-          }
-          // No more siblings. Traverse up.
-          nextFiber = nextFiber["return"];
-        }
-      }
-      fiber = nextFiber;
-    }
-  }
-
-  function updateContextProvider(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var providerType = workInProgress.type;
-    var context = providerType._context;
-
-    var newProps = workInProgress.pendingProps;
-    var oldProps = workInProgress.memoizedProps;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (oldProps === newProps) {
-      workInProgress.stateNode = 0;
-      pushProvider(workInProgress);
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var newValue = newProps.value;
-    workInProgress.memoizedProps = newProps;
-
-    var changedBits = void 0;
-    if (oldProps === null) {
-      // Initial render
-      changedBits = MAX_SIGNED_31_BIT_INT;
-    } else {
-      if (oldProps.value === newProps.value) {
-        // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children) {
-          workInProgress.stateNode = 0;
-          pushProvider(workInProgress);
-          return bailoutOnAlreadyFinishedWork(current, workInProgress);
-        }
-        changedBits = 0;
-      } else {
-        var oldValue = oldProps.value;
-        // Use Object.is to compare the new context value to the old value.
-        // Inlined Object.is polyfill.
-        // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
-        if (
-          (oldValue === newValue &&
-            (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
-          (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
-        ) {
-          // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children) {
-            workInProgress.stateNode = 0;
-            pushProvider(workInProgress);
-            return bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
-          changedBits = 0;
-        } else {
-          changedBits =
-            typeof context._calculateChangedBits === "function"
-              ? context._calculateChangedBits(oldValue, newValue)
-              : MAX_SIGNED_31_BIT_INT;
-          {
-            !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
-              ? warning(
-                  false,
-                  "calculateChangedBits: Expected the return value to be a " +
-                    "31-bit integer. Instead received: %s",
-                  changedBits
-                )
-              : void 0;
-          }
-          changedBits |= 0;
-
-          if (changedBits === 0) {
-            // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children) {
-              workInProgress.stateNode = 0;
-              pushProvider(workInProgress);
-              return bailoutOnAlreadyFinishedWork(current, workInProgress);
-            }
-          } else {
-            propagateContextChange(
-              workInProgress,
-              context,
-              changedBits,
-              renderExpirationTime
-            );
-          }
-        }
-      }
-    }
-
-    workInProgress.stateNode = changedBits;
-    pushProvider(workInProgress);
-
-    var newChildren = newProps.children;
-    reconcileChildren(current, workInProgress, newChildren);
-    return workInProgress.child;
-  }
-
-  function updateContextConsumer(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var context = workInProgress.type;
-    var newProps = workInProgress.pendingProps;
-    var oldProps = workInProgress.memoizedProps;
-
-    var newValue = context._currentValue;
-    var changedBits = context._changedBits;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (changedBits === 0 && oldProps === newProps) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    workInProgress.memoizedProps = newProps;
-
-    var observedBits = newProps.unstable_observedBits;
-    if (observedBits === undefined || observedBits === null) {
-      // Subscribe to all changes by default
-      observedBits = MAX_SIGNED_31_BIT_INT;
-    }
-    // Store the observedBits on the fiber's stateNode for quick access.
-    workInProgress.stateNode = observedBits;
-
-    if ((changedBits & observedBits) !== 0) {
-      // Context change propagation stops at matching consumers, for time-
-      // slicing. Continue the propagation here.
-      propagateContextChange(
-        workInProgress,
-        context,
-        changedBits,
-        renderExpirationTime
-      );
-    } else if (oldProps === newProps) {
-      // Skip over a memoized parent with a bitmask bailout even
-      // if we began working on it because of a deeper matching child.
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    // There is no bailout on `children` equality because we expect people
-    // to often pass a bound method as a child, but it may reference
-    // `this.state` or `this.props` (and thus needs to re-render on `setState`).
-
-    var render = newProps.children;
-
-    {
-      !(typeof render === "function")
-        ? warning(
-            false,
-            "A context consumer was rendered with multiple children, or a child " +
-              "that isn't a function. A context consumer expects a single child " +
-              "that is a function. If you did pass a function, make sure there " +
-              "is no trailing or leading whitespace around it."
-          )
-        : void 0;
-    }
-
-    var newChildren = render(newValue);
-    reconcileChildren(current, workInProgress, newChildren);
-    return workInProgress.child;
-  }
-
-  /*
-  function reuseChildrenEffects(returnFiber : Fiber, firstChild : Fiber) {
-    let child = firstChild;
-    do {
-      // Ensure that the first and last effect of the parent corresponds
-      // to the children's first and last effect.
-      if (!returnFiber.firstEffect) {
-        returnFiber.firstEffect = child.firstEffect;
-      }
-      if (child.lastEffect) {
-        if (returnFiber.lastEffect) {
-          returnFiber.lastEffect.nextEffect = child.firstEffect;
-        }
-        returnFiber.lastEffect = child.lastEffect;
-      }
-    } while (child = child.sibling);
-  }
-  */
-
-  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
-    cancelWorkTimer(workInProgress);
-
-    // TODO: We should ideally be able to bail out early if the children have no
-    // more work to do. However, since we don't have a separation of this
-    // Fiber's priority and its children yet - we don't know without doing lots
-    // of the same work we do anyway. Once we have that separation we can just
-    // bail out here if the children has no more work at this priority level.
-    // if (workInProgress.priorityOfChildren <= priorityLevel) {
-    //   // If there are side-effects in these children that have not yet been
-    //   // committed we need to ensure that they get properly transferred up.
-    //   if (current && current.child !== workInProgress.child) {
-    //     reuseChildrenEffects(workInProgress, child);
-    //   }
-    //   return null;
-    // }
-
-    cloneChildFibers(current, workInProgress);
-    return workInProgress.child;
-  }
-
-  function bailoutOnLowPriority(current, workInProgress) {
-    cancelWorkTimer(workInProgress);
-
-    // TODO: Handle HostComponent tags here as well and call pushHostContext()?
-    // See PR 8590 discussion for context
-    switch (workInProgress.tag) {
-      case HostRoot:
-        pushHostRootContext(workInProgress);
-        break;
-      case ClassComponent:
-        pushLegacyContextProvider(workInProgress);
-        break;
-      case HostPortal:
-        pushHostContainer(
-          workInProgress,
-          workInProgress.stateNode.containerInfo
-        );
-        break;
-      case ContextProvider:
-        pushProvider(workInProgress);
-        break;
-    }
-    // TODO: What if this is currently in progress?
-    // How can that happen? How is this not being cloned?
-    return null;
-  }
-
-  // TODO: Delete memoizeProps/State and move to reconcile/bailout instead
-  function memoizeProps(workInProgress, nextProps) {
-    workInProgress.memoizedProps = nextProps;
-  }
-
-  function memoizeState(workInProgress, nextState) {
-    workInProgress.memoizedState = nextState;
-    // Don't reset the updateQueue, in case there are pending updates. Resetting
-    // is handled by processUpdateQueue.
-  }
-
-  function beginWork(current, workInProgress, renderExpirationTime) {
-    if (
-      workInProgress.expirationTime === NoWork ||
-      workInProgress.expirationTime > renderExpirationTime
-    ) {
-      return bailoutOnLowPriority(current, workInProgress);
-    }
-
-    switch (workInProgress.tag) {
-      case IndeterminateComponent:
-        return mountIndeterminateComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case FunctionalComponent:
-        return updateFunctionalComponent(current, workInProgress);
-      case ClassComponent:
-        return updateClassComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostRoot:
-        return updateHostRoot(current, workInProgress, renderExpirationTime);
-      case HostComponent:
-        return updateHostComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostText:
-        return updateHostText(current, workInProgress);
-      case CallHandlerPhase:
-        // This is a restart. Reset the tag to the initial phase.
-        workInProgress.tag = CallComponent;
-      // Intentionally fall through since this is now the same.
-      case CallComponent:
-        return updateCallComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ReturnComponent:
-        // A return component is just a placeholder, we can just run through the
-        // next one immediately.
-        return null;
-      case HostPortal:
-        return updatePortalComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ForwardRef:
-        return updateForwardRef(current, workInProgress);
-      case Fragment:
-        return updateFragment(current, workInProgress);
-      case Mode:
-        return updateMode(current, workInProgress);
-      case ContextProvider:
-        return updateContextProvider(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ContextConsumer:
-        return updateContextConsumer(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      default:
-        invariant(
-          false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
-        );
-    }
-  }
-
-  return {
-    beginWork: beginWork
-  };
-};
-
-var ReactFiberCompleteWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext
-) {
-  var createInstance = config.createInstance,
-    createTextInstance = config.createTextInstance,
-    appendInitialChild = config.appendInitialChild,
-    finalizeInitialChildren = config.finalizeInitialChildren,
-    prepareUpdate = config.prepareUpdate,
-    mutation = config.mutation,
-    persistence = config.persistence;
-  var getRootHostContainer = hostContext.getRootHostContainer,
-    popHostContext = hostContext.popHostContext,
-    getHostContext = hostContext.getHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-  var prepareToHydrateHostInstance =
-      hydrationContext.prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance =
-      hydrationContext.prepareToHydrateHostTextInstance,
-    popHydrationState = hydrationContext.popHydrationState;
-
-  function markUpdate(workInProgress) {
-    // Tag the fiber with an update effect. This turns a Placement into
-    // a PlacementAndUpdate.
-    workInProgress.effectTag |= Update;
-  }
-
-  function markRef(workInProgress) {
-    workInProgress.effectTag |= Ref;
-  }
-
-  function appendAllReturns(returns, workInProgress) {
-    var node = workInProgress.stateNode;
-    if (node) {
-      node["return"] = workInProgress;
-    }
-    while (node !== null) {
-      if (
-        node.tag === HostComponent ||
-        node.tag === HostText ||
-        node.tag === HostPortal
-      ) {
-        invariant(false, "A call cannot have host component children.");
-      } else if (node.tag === ReturnComponent) {
-        returns.push(node.pendingProps.value);
-      } else if (node.child !== null) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  function moveCallToHandlerPhase(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var props = workInProgress.memoizedProps;
-    invariant(
-      props,
-      "Should be resolved by now. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-
-    // First step of the call has completed. Now we need to do the second.
-    // TODO: It would be nice to have a multi stage call represented by a
-    // single component, or at least tail call optimize nested ones. Currently
-    // that requires additional fields that we don't want to add to the fiber.
-    // So this requires nested handlers.
-    // Note: This doesn't mutate the alternate node. I don't think it needs to
-    // since this stage is reset for every pass.
-    workInProgress.tag = CallHandlerPhase;
-
-    // Build up the returns.
-    // TODO: Compare this to a generator or opaque helpers like Children.
-    var returns = [];
-    appendAllReturns(returns, workInProgress);
-    var fn = props.handler;
-    var childProps = props.props;
-    var nextChildren = fn(childProps, returns);
-
-    var currentFirstChild = current !== null ? current.child : null;
-    workInProgress.child = reconcileChildFibers(
-      workInProgress,
-      currentFirstChild,
-      nextChildren,
-      renderExpirationTime
-    );
-    return workInProgress.child;
-  }
-
-  function appendAllChildren(parent, workInProgress) {
-    // We only have the top Fiber that was created but we need recurse down its
-    // children to find all the terminal nodes.
-    var node = workInProgress.child;
-    while (node !== null) {
-      if (node.tag === HostComponent || node.tag === HostText) {
-        appendInitialChild(parent, node.stateNode);
-      } else if (node.tag === HostPortal) {
-        // If we have a portal child, then we don't want to traverse
-        // down its children. Instead, we'll get insertions from each child in
-        // the portal directly.
-      } else if (node.child !== null) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === workInProgress) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  var updateHostContainer = void 0;
-  var updateHostComponent = void 0;
-  var updateHostText = void 0;
-  if (mutation) {
-    if (enableMutatingReconciler) {
-      // Mutation mode
-      updateHostContainer = function(workInProgress) {
-        // Noop
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // TODO: Type this specific to this type of component.
-        workInProgress.updateQueue = updatePayload;
-        // If the update payload indicates that there is a change or if there
-        // is a new ref we mark this as an update. All the work is done in commitWork.
-        if (updatePayload) {
-          markUpdate(workInProgress);
-        }
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        // If the text differs, mark it as an update. All the work in done in commitWork.
-        if (oldText !== newText) {
-          markUpdate(workInProgress);
-        }
-      };
-    } else {
-      invariant(false, "Mutating reconciler is disabled.");
-    }
-  } else if (persistence) {
-    if (enablePersistentReconciler) {
-      // Persistent host tree mode
-      var cloneInstance = persistence.cloneInstance,
-        createContainerChildSet = persistence.createContainerChildSet,
-        appendChildToContainerChildSet =
-          persistence.appendChildToContainerChildSet,
-        finalizeContainerChildren = persistence.finalizeContainerChildren;
-
-      // An unfortunate fork of appendAllChildren because we have two different parent types.
-
-      var appendAllChildrenToContainer = function(
-        containerChildSet,
-        workInProgress
-      ) {
-        // We only have the top Fiber that was created but we need recurse down its
-        // children to find all the terminal nodes.
-        var node = workInProgress.child;
-        while (node !== null) {
-          if (node.tag === HostComponent || node.tag === HostText) {
-            appendChildToContainerChildSet(containerChildSet, node.stateNode);
-          } else if (node.tag === HostPortal) {
-            // If we have a portal child, then we don't want to traverse
-            // down its children. Instead, we'll get insertions from each child in
-            // the portal directly.
-          } else if (node.child !== null) {
-            node.child["return"] = node;
-            node = node.child;
-            continue;
-          }
-          if (node === workInProgress) {
-            return;
-          }
-          while (node.sibling === null) {
-            if (node["return"] === null || node["return"] === workInProgress) {
-              return;
-            }
-            node = node["return"];
-          }
-          node.sibling["return"] = node["return"];
-          node = node.sibling;
-        }
-      };
-      updateHostContainer = function(workInProgress) {
-        var portalOrRoot = workInProgress.stateNode;
-        var childrenUnchanged = workInProgress.firstEffect === null;
-        if (childrenUnchanged) {
-          // No changes, just reuse the existing instance.
-        } else {
-          var container = portalOrRoot.containerInfo;
-          var newChildSet = createContainerChildSet(container);
-          // If children might have changed, we have to add them all to the set.
-          appendAllChildrenToContainer(newChildSet, workInProgress);
-          portalOrRoot.pendingChildren = newChildSet;
-          // Schedule an update on the container to swap out the container.
-          markUpdate(workInProgress);
-          finalizeContainerChildren(container, newChildSet);
-        }
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // If there are no effects associated with this node, then none of our children had any updates.
-        // This guarantees that we can reuse all of them.
-        var childrenUnchanged = workInProgress.firstEffect === null;
-        var currentInstance = current.stateNode;
-        if (childrenUnchanged && updatePayload === null) {
-          // No changes, just reuse the existing instance.
-          // Note that this might release a previous clone.
-          workInProgress.stateNode = currentInstance;
-        } else {
-          var recyclableInstance = workInProgress.stateNode;
-          var newInstance = cloneInstance(
-            currentInstance,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            workInProgress,
-            childrenUnchanged,
-            recyclableInstance
-          );
-          if (
-            finalizeInitialChildren(
-              newInstance,
-              type,
-              newProps,
-              rootContainerInstance,
-              currentHostContext
-            )
-          ) {
-            markUpdate(workInProgress);
-          }
-          workInProgress.stateNode = newInstance;
-          if (childrenUnchanged) {
-            // If there are no other effects in this tree, we need to flag this node as having one.
-            // Even though we're not going to use it for anything.
-            // Otherwise parents won't know that there are new children to propagate upwards.
-            markUpdate(workInProgress);
-          } else {
-            // If children might have changed, we have to add them all to the set.
-            appendAllChildren(newInstance, workInProgress);
-          }
-        }
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        if (oldText !== newText) {
-          // If the text content differs, we'll create a new text instance for it.
-          var rootContainerInstance = getRootHostContainer();
-          var currentHostContext = getHostContext();
-          workInProgress.stateNode = createTextInstance(
-            newText,
-            rootContainerInstance,
-            currentHostContext,
-            workInProgress
-          );
-          // We'll have to mark it as having an effect, even though we won't use the effect for anything.
-          // This lets the parents know that at least one of their children has changed.
-          markUpdate(workInProgress);
-        }
-      };
-    } else {
-      invariant(false, "Persistent reconciler is disabled.");
-    }
-  } else {
-    if (enableNoopReconciler) {
-      // No host operations
-      updateHostContainer = function(workInProgress) {
-        // Noop
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // Noop
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        // Noop
-      };
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
-    }
-  }
-
-  function completeWork(current, workInProgress, renderExpirationTime) {
-    var newProps = workInProgress.pendingProps;
-    switch (workInProgress.tag) {
-      case FunctionalComponent:
-        return null;
-      case ClassComponent: {
-        // We are leaving this subtree, so pop context if any.
-        popLegacyContextProvider(workInProgress);
-
-        // If this component caught an error, schedule an error log effect.
-        var instance = workInProgress.stateNode;
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null && updateQueue.capturedValues !== null) {
-          workInProgress.effectTag &= ~DidCapture;
-          if (typeof instance.componentDidCatch === "function") {
-            workInProgress.effectTag |= ErrLog;
-          } else {
-            // Normally we clear this in the commit phase, but since we did not
-            // schedule an effect, we need to reset it here.
-            updateQueue.capturedValues = null;
-          }
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var fiberRoot = workInProgress.stateNode;
-        if (fiberRoot.pendingContext) {
-          fiberRoot.context = fiberRoot.pendingContext;
-          fiberRoot.pendingContext = null;
-        }
-        if (current === null || current.child === null) {
-          // If we hydrated, pop so that we can delete any remaining children
-          // that weren't hydrated.
-          popHydrationState(workInProgress);
-          // This resets the hacky state to fix isMounted before committing.
-          // TODO: Delete this when we delete isMounted and findDOMNode.
-          workInProgress.effectTag &= ~Placement;
-        }
-        updateHostContainer(workInProgress);
-
-        var _updateQueue = workInProgress.updateQueue;
-        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
-          workInProgress.effectTag |= ErrLog;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        var rootContainerInstance = getRootHostContainer();
-        var type = workInProgress.type;
-        if (current !== null && workInProgress.stateNode != null) {
-          // If we have an alternate, that means this is an update and we need to
-          // schedule a side-effect to do the updates.
-          var oldProps = current.memoizedProps;
-          // If we get updated because one of our children updated, we don't
-          // have newProps so we'll have to reuse them.
-          // TODO: Split the update API as separate for the props vs. children.
-          // Even better would be if children weren't special cased at all tho.
-          var _instance = workInProgress.stateNode;
-          var currentHostContext = getHostContext();
-          // TODO: Experiencing an error where oldProps is null. Suggests a host
-          // component is hitting the resume path. Figure out why. Possibly
-          // related to `hidden`.
-          var updatePayload = prepareUpdate(
-            _instance,
-            type,
-            oldProps,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          );
-
-          updateHostComponent(
-            current,
-            workInProgress,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          );
-
-          if (current.ref !== workInProgress.ref) {
-            markRef(workInProgress);
-          }
-        } else {
-          if (!newProps) {
-            invariant(
-              workInProgress.stateNode !== null,
-              "We must have new props for new mounts. This error is likely " +
-                "caused by a bug in React. Please file an issue."
-            );
-            // This can happen when we abort work.
-            return null;
-          }
-
-          var _currentHostContext = getHostContext();
-          // TODO: Move createInstance to beginWork and keep it on a context
-          // "stack" as the parent. Then append children as we go in beginWork
-          // or completeWork depending on we want to add then top->down or
-          // bottom->up. Top->down is faster in IE11.
-          var wasHydrated = popHydrationState(workInProgress);
-          if (wasHydrated) {
-            // TODO: Move this and createInstance step into the beginPhase
-            // to consolidate.
-            if (
-              prepareToHydrateHostInstance(
-                workInProgress,
-                rootContainerInstance,
-                _currentHostContext
-              )
-            ) {
-              // If changes to the hydrated node needs to be applied at the
-              // commit-phase we mark this as such.
-              markUpdate(workInProgress);
-            }
-          } else {
-            var _instance2 = createInstance(
-              type,
-              newProps,
-              rootContainerInstance,
-              _currentHostContext,
-              workInProgress
-            );
-
-            appendAllChildren(_instance2, workInProgress);
-
-            // Certain renderers require commit-time effects for initial mount.
-            // (eg DOM renderer supports auto-focus for certain elements).
-            // Make sure such renderers get scheduled for later work.
-            if (
-              finalizeInitialChildren(
-                _instance2,
-                type,
-                newProps,
-                rootContainerInstance,
-                _currentHostContext
-              )
-            ) {
-              markUpdate(workInProgress);
-            }
-            workInProgress.stateNode = _instance2;
-          }
-
-          if (workInProgress.ref !== null) {
-            // If there is a ref on a host node we need to schedule a callback
-            markRef(workInProgress);
-          }
-        }
-        return null;
-      }
-      case HostText: {
-        var newText = newProps;
-        if (current && workInProgress.stateNode != null) {
-          var oldText = current.memoizedProps;
-          // If we have an alternate, that means this is an update and we need
-          // to schedule a side-effect to do the updates.
-          updateHostText(current, workInProgress, oldText, newText);
-        } else {
-          if (typeof newText !== "string") {
-            invariant(
-              workInProgress.stateNode !== null,
-              "We must have new props for new mounts. This error is likely " +
-                "caused by a bug in React. Please file an issue."
-            );
-            // This can happen when we abort work.
-            return null;
-          }
-          var _rootContainerInstance = getRootHostContainer();
-          var _currentHostContext2 = getHostContext();
-          var _wasHydrated = popHydrationState(workInProgress);
-          if (_wasHydrated) {
-            if (prepareToHydrateHostTextInstance(workInProgress)) {
-              markUpdate(workInProgress);
-            }
-          } else {
-            workInProgress.stateNode = createTextInstance(
-              newText,
-              _rootContainerInstance,
-              _currentHostContext2,
-              workInProgress
-            );
-          }
-        }
-        return null;
-      }
-      case CallComponent:
-        return moveCallToHandlerPhase(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case CallHandlerPhase:
-        // Reset the tag to now be a first phase call.
-        workInProgress.tag = CallComponent;
-        return null;
-      case ReturnComponent:
-        // Does nothing.
-        return null;
-      case ForwardRef:
-        return null;
-      case Fragment:
-        return null;
-      case Mode:
-        return null;
-      case HostPortal:
-        popHostContainer(workInProgress);
-        updateHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        // Pop provider fiber
-        popProvider(workInProgress);
-        return null;
-      case ContextConsumer:
-        return null;
-      // Error cases
-      case IndeterminateComponent:
-        invariant(
-          false,
-          "An indeterminate component should have become determinate before " +
-            "completing. This error is likely caused by a bug in React. Please " +
-            "file an issue."
-        );
-      // eslint-disable-next-line no-fallthrough
-      default:
-        invariant(
-          false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
-        );
-    }
-  }
-
-  return {
-    completeWork: completeWork
-  };
-};
-
-function createCapturedValue(value, source) {
-  // If the value is an error, call this function immediately after it is thrown
-  // so the stack is accurate.
-  return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
-  };
-}
-
-var ReactFiberUnwindWork = function(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-
-  function throwException(returnFiber, sourceFiber, rawValue) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-
-    var value = createCapturedValue(rawValue, sourceFiber);
-
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          // Uncaught error
-          var errorInfo = value;
-          ensureUpdateQueues(workInProgress);
-          var updateQueue = workInProgress.updateQueue;
-          updateQueue.capturedValues = [errorInfo];
-          workInProgress.effectTag |= ShouldCapture;
-          return;
-        }
-        case ClassComponent:
-          // Capture and retry
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
-          if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            ensureUpdateQueues(workInProgress);
-            var _updateQueue = workInProgress.updateQueue;
-            var capturedValues = _updateQueue.capturedValues;
-            if (capturedValues === null) {
-              _updateQueue.capturedValues = [value];
-            } else {
-              capturedValues.push(value);
-            }
-            workInProgress.effectTag |= ShouldCapture;
-            return;
-          }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress["return"];
-    } while (workInProgress !== null);
-  }
-
-  function unwindWork(workInProgress) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
-    }
-  }
-
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      default:
-        break;
-    }
-  }
-
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork
-  };
-};
-
-// This module is forked in different environments.
-// By default, return `true` to log errors to the console.
-// Forks can return `false` if this isn't desirable.
-function showErrorDialog(capturedError) {
-  return true;
-}
-
-function logCapturedError(capturedError) {
-  var logError = showErrorDialog(capturedError);
-
-  // Allow injected showErrorDialog() to prevent default console.error logging.
-  // This enables renderers like ReactNative to better manage redbox behavior.
-  if (logError === false) {
-    return;
-  }
-
-  var error = capturedError.error;
-  var suppressLogging = error && error.suppressReactErrorLogging;
-  if (suppressLogging) {
-    return;
-  }
-
-  {
-    var componentName = capturedError.componentName,
-      componentStack = capturedError.componentStack,
-      errorBoundaryName = capturedError.errorBoundaryName,
-      errorBoundaryFound = capturedError.errorBoundaryFound,
-      willRetry = capturedError.willRetry;
-
-    var componentNameMessage = componentName
-      ? "The above error occurred in the <" + componentName + "> component:"
-      : "The above error occurred in one of your React components:";
-
-    var errorBoundaryMessage = void 0;
-    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
-    if (errorBoundaryFound && errorBoundaryName) {
-      if (willRetry) {
-        errorBoundaryMessage =
-          "React will try to recreate this component tree from scratch " +
-          ("using the error boundary you provided, " + errorBoundaryName + ".");
-      } else {
-        errorBoundaryMessage =
-          "This error was initially handled by the error boundary " +
-          errorBoundaryName +
-          ".\n" +
-          "Recreating the tree from scratch failed so React will unmount the tree.";
-      }
-    } else {
-      errorBoundaryMessage =
-        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
-        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
-    }
-    var combinedMessage =
-      "" +
-      componentNameMessage +
-      componentStack +
-      "\n\n" +
-      ("" + errorBoundaryMessage);
-
-    // In development, we provide our own message with just the component stack.
-    // We don't include the original error message and JS stack because the browser
-    // has already printed it. Even if the application swallows the error, it is still
-    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
-    console.error(combinedMessage);
-  }
-}
-
-var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
-var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
-
-var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
-{
-  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
-}
-
-function logError(boundary, errorInfo) {
-  var source = errorInfo.source;
-  var stack = errorInfo.stack;
-  if (stack === null) {
-    stack = getStackAddendumByWorkInProgressFiber(source);
-  }
-
-  var capturedError = {
-    componentName: source !== null ? getComponentName(source) : null,
-    componentStack: stack !== null ? stack : "",
-    error: errorInfo.value,
-    errorBoundary: null,
-    errorBoundaryName: null,
-    errorBoundaryFound: false,
-    willRetry: false
-  };
-
-  if (boundary !== null && boundary.tag === ClassComponent) {
-    capturedError.errorBoundary = boundary.stateNode;
-    capturedError.errorBoundaryName = getComponentName(boundary);
-    capturedError.errorBoundaryFound = true;
-    capturedError.willRetry = true;
-  }
-
-  try {
-    logCapturedError(capturedError);
-  } catch (e) {
-    // Prevent cycle if logCapturedError() throws.
-    // A cycle may still occur if logCapturedError renders a component that throws.
-    var suppressLogging = e && e.suppressReactErrorLogging;
-    if (!suppressLogging) {
-      console.error(e);
-    }
-  }
-}
-
-var ReactFiberCommitWork = function(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed,
-  recalculateCurrentTime
-) {
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation,
-    persistence = config.persistence;
-
-  var callComponentWillUnmountWithTimer = function(current, instance) {
-    startPhaseTimer(current, "componentWillUnmount");
-    instance.props = current.memoizedProps;
-    instance.state = current.memoizedState;
-    instance.componentWillUnmount();
-    stopPhaseTimer();
-  };
-
-  // Capture errors so they don't interrupt unmounting.
-  function safelyCallComponentWillUnmount(current, instance) {
-    {
-      invokeGuardedCallback$3(
-        null,
-        callComponentWillUnmountWithTimer,
-        null,
-        current,
-        instance
-      );
-      if (hasCaughtError$1()) {
-        var unmountError = clearCaughtError$1();
-        captureError(current, unmountError);
-      }
-    }
-  }
-
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (ref !== null) {
-      if (typeof ref === "function") {
-        {
-          invokeGuardedCallback$3(null, ref, null, null);
-          if (hasCaughtError$1()) {
-            var refError = clearCaughtError$1();
-            captureError(current, refError);
-          }
-        }
-      } else {
-        ref.current = null;
-      }
-    }
-  }
-
-  function commitBeforeMutationLifeCycles(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        if (finishedWork.effectTag & Snapshot) {
-          if (current !== null) {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
-            var _instance = finishedWork.stateNode;
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            var snapshot = _instance.getSnapshotBeforeUpdate(
-              prevProps,
-              prevState
-            );
-            {
-              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
-              if (
-                snapshot === undefined &&
-                !didWarnSet.has(finishedWork.type)
-              ) {
-                didWarnSet.add(finishedWork.type);
-                warning(
-                  false,
-                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
-                    "must be returned. You have returned undefined.",
-                  getComponentName(finishedWork)
-                );
-              }
-            }
-            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
-            stopPhaseTimer();
-          }
-        }
-        return;
-      }
-      case HostRoot:
-      case HostComponent:
-      case HostText:
-      case HostPortal:
-        // Nothing to do for these component types
-        return;
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
-    }
-  }
-
-  function commitLifeCycles(
-    finishedRoot,
-    current,
-    finishedWork,
-    currentTime,
-    committedExpirationTime
-  ) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        var _instance2 = finishedWork.stateNode;
-        if (finishedWork.effectTag & Update) {
-          if (current === null) {
-            startPhaseTimer(finishedWork, "componentDidMount");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidMount();
-            stopPhaseTimer();
-          } else {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "componentDidUpdate");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidUpdate(
-              prevProps,
-              prevState,
-              _instance2.__reactInternalSnapshotBeforeUpdate
-            );
-            stopPhaseTimer();
-          }
-        }
-        var updateQueue = finishedWork.updateQueue;
-        if (updateQueue !== null) {
-          commitCallbacks(updateQueue, _instance2);
-        }
-        return;
-      }
-      case HostRoot: {
-        var _updateQueue = finishedWork.updateQueue;
-        if (_updateQueue !== null) {
-          var _instance3 = null;
-          if (finishedWork.child !== null) {
-            switch (finishedWork.child.tag) {
-              case HostComponent:
-                _instance3 = getPublicInstance(finishedWork.child.stateNode);
-                break;
-              case ClassComponent:
-                _instance3 = finishedWork.child.stateNode;
-                break;
-            }
-          }
-          commitCallbacks(_updateQueue, _instance3);
-        }
-        return;
-      }
-      case HostComponent: {
-        var _instance4 = finishedWork.stateNode;
-
-        // Renderers may schedule work to be done after host components are mounted
-        // (eg DOM renderer may schedule auto-focus for inputs and form controls).
-        // These effects should only be committed when components are first mounted,
-        // aka when there is no current/alternate.
-        if (current === null && finishedWork.effectTag & Update) {
-          var type = finishedWork.type;
-          var props = finishedWork.memoizedProps;
-          commitMount(_instance4, type, props, finishedWork);
-        }
-
-        return;
-      }
-      case HostText: {
-        // We have no life-cycles associated with text.
-        return;
-      }
-      case HostPortal: {
-        // We have no life-cycles associated with portals.
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
-    }
-  }
-
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case ClassComponent:
-        {
-          var ctor = finishedWork.type;
-          var _instance5 = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            updateQueue !== null && updateQueue.capturedValues !== null,
-            "An error logging effect should not have been scheduled if no errors " +
-              "were captured. This error is likely caused by a bug in React. " +
-              "Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-
-          if (typeof ctor.getDerivedStateFromCatch !== "function") {
-            // To preserve the preexisting retry behavior of error boundaries,
-            // we keep track of which ones already failed during this batch.
-            // This gets reset before we yield back to the browser.
-            // TODO: Warn in strict mode if getDerivedStateFromCatch is
-            // not defined.
-            markLegacyErrorBoundaryAsFailed(_instance5);
-          }
-
-          _instance5.props = finishedWork.memoizedProps;
-          _instance5.state = finishedWork.memoizedState;
-          for (var i = 0; i < capturedErrors.length; i++) {
-            var errorInfo = capturedErrors[i];
-            var _error = errorInfo.value;
-            var stack = errorInfo.stack;
-            logError(finishedWork, errorInfo);
-            _instance5.componentDidCatch(_error, {
-              componentStack: stack !== null ? stack : ""
-            });
-          }
-        }
-        break;
-      case HostRoot: {
-        var _updateQueue2 = finishedWork.updateQueue;
-        invariant(
-          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
-          "An error logging effect should not have been scheduled if no errors " +
-            "were captured. This error is likely caused by a bug in React. " +
-            "Please file an issue."
-        );
-        var _capturedErrors = _updateQueue2.capturedValues;
-        _updateQueue2.capturedValues = null;
-        for (var _i = 0; _i < _capturedErrors.length; _i++) {
-          var _errorInfo = _capturedErrors[_i];
-          logError(finishedWork, _errorInfo);
-          onUncaughtError(_errorInfo.value);
-        }
-        break;
-      }
-      default:
-        invariant(
-          false,
-          "This unit of work tag cannot capture errors.  This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-
-  function commitAttachRef(finishedWork) {
-    var ref = finishedWork.ref;
-    if (ref !== null) {
-      var _instance6 = finishedWork.stateNode;
-      var instanceToUse = void 0;
-      switch (finishedWork.tag) {
-        case HostComponent:
-          instanceToUse = getPublicInstance(_instance6);
-          break;
-        default:
-          instanceToUse = _instance6;
-      }
-      if (typeof ref === "function") {
-        ref(instanceToUse);
-      } else {
-        {
-          if (!ref.hasOwnProperty("current")) {
-            warning(
-              false,
-              "Unexpected ref object provided for %s. " +
-                "Use either a ref-setter function or React.createRef().%s",
-              getComponentName(finishedWork),
-              getStackAddendumByWorkInProgressFiber(finishedWork)
-            );
-          }
-        }
-
-        ref.current = instanceToUse;
-      }
-    }
-  }
-
-  function commitDetachRef(current) {
-    var currentRef = current.ref;
-    if (currentRef !== null) {
-      if (typeof currentRef === "function") {
-        currentRef(null);
-      } else {
-        currentRef.current = null;
-      }
-    }
-  }
-
-  // User-originating errors (lifecycles and refs) should not interrupt
-  // deletion, so don't let them throw. Host-originating errors should
-  // interrupt deletion, so it's okay
-  function commitUnmount(current) {
-    if (typeof onCommitUnmount === "function") {
-      onCommitUnmount(current);
-    }
-
-    switch (current.tag) {
-      case ClassComponent: {
-        safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if (typeof _instance7.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance7);
-        }
-        return;
-      }
-      case HostComponent: {
-        safelyDetachRef(current);
-        return;
-      }
-      case CallComponent: {
-        commitNestedUnmounts(current.stateNode);
-        return;
-      }
-      case HostPortal: {
-        // TODO: this is recursive.
-        // We are also not using this parent because
-        // the portal will get pushed immediately.
-        if (enableMutatingReconciler && mutation) {
-          unmountHostComponents(current);
-        } else if (enablePersistentReconciler && persistence) {
-          emptyPortalContainer(current);
-        }
-        return;
-      }
-    }
-  }
-
-  function commitNestedUnmounts(root) {
-    // While we're inside a removed host node we don't want to call
-    // removeChild on the inner nodes because they're removed by the top
-    // call anyway. We also want to call componentWillUnmount on all
-    // composites before this host node is removed from the tree. Therefore
-    var node = root;
-    while (true) {
-      commitUnmount(node);
-      // Visit children because they may contain more composite or host nodes.
-      // Skip portals because commitUnmount() currently visits them recursively.
-      if (
-        node.child !== null &&
-        // If we use mutation we drill down into portals using commitUnmount above.
-        // If we don't use mutation we drill down into portals here instead.
-        (!mutation || node.tag !== HostPortal)
-      ) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === root) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === root) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  function detachFiber(current) {
-    // Cut off the return pointers to disconnect it from the tree. Ideally, we
-    // should clear the child pointer of the parent alternate to let this
-    // get GC:ed but we don't know which for sure which parent is the current
-    // one so we'll settle for GC:ing the subtree of this child. This child
-    // itself will be GC:ed when the parent updates the next time.
-    current["return"] = null;
-    current.child = null;
-    if (current.alternate) {
-      current.alternate.child = null;
-      current.alternate["return"] = null;
-    }
-  }
-
-  var emptyPortalContainer = void 0;
-
-  if (!mutation) {
-    var commitContainer = void 0;
-    if (persistence) {
-      var replaceContainerChildren = persistence.replaceContainerChildren,
-        createContainerChildSet = persistence.createContainerChildSet;
-
-      emptyPortalContainer = function(current) {
-        var portal = current.stateNode;
-        var containerInfo = portal.containerInfo;
-
-        var emptyChildSet = createContainerChildSet(containerInfo);
-        replaceContainerChildren(containerInfo, emptyChildSet);
-      };
-      commitContainer = function(finishedWork) {
-        switch (finishedWork.tag) {
-          case ClassComponent: {
-            return;
-          }
-          case HostComponent: {
-            return;
-          }
-          case HostText: {
-            return;
-          }
-          case HostRoot:
-          case HostPortal: {
-            var portalOrRoot = finishedWork.stateNode;
-            var containerInfo = portalOrRoot.containerInfo,
-              _pendingChildren = portalOrRoot.pendingChildren;
-
-            replaceContainerChildren(containerInfo, _pendingChildren);
-            return;
-          }
-          default: {
-            invariant(
-              false,
-              "This unit of work tag should not have side-effects. This error is " +
-                "likely caused by a bug in React. Please file an issue."
-            );
-          }
-        }
-      };
-    } else {
-      commitContainer = function(finishedWork) {
-        // Noop
-      };
-    }
-    if (enablePersistentReconciler || enableNoopReconciler) {
-      return {
-        commitResetTextContent: function(finishedWork) {},
-        commitPlacement: function(finishedWork) {},
-        commitDeletion: function(current) {
-          // Detach refs and call componentWillUnmount() on the whole subtree.
-          commitNestedUnmounts(current);
-          detachFiber(current);
-        },
-        commitWork: function(current, finishedWork) {
-          commitContainer(finishedWork);
-        },
-
-        commitLifeCycles: commitLifeCycles,
-        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-        commitErrorLogging: commitErrorLogging,
-        commitAttachRef: commitAttachRef,
-        commitDetachRef: commitDetachRef
-      };
-    } else if (persistence) {
-      invariant(false, "Persistent reconciler is disabled.");
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
-    }
-  }
-  var commitMount = mutation.commitMount,
-    commitUpdate = mutation.commitUpdate,
-    resetTextContent = mutation.resetTextContent,
-    commitTextUpdate = mutation.commitTextUpdate,
-    appendChild = mutation.appendChild,
-    appendChildToContainer = mutation.appendChildToContainer,
-    insertBefore = mutation.insertBefore,
-    insertInContainerBefore = mutation.insertInContainerBefore,
-    removeChild = mutation.removeChild,
-    removeChildFromContainer = mutation.removeChildFromContainer;
-
-  function getHostParentFiber(fiber) {
-    var parent = fiber["return"];
-    while (parent !== null) {
-      if (isHostParent(parent)) {
-        return parent;
-      }
-      parent = parent["return"];
-    }
-    invariant(
-      false,
-      "Expected to find a host parent. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-  }
-
-  function isHostParent(fiber) {
-    return (
-      fiber.tag === HostComponent ||
-      fiber.tag === HostRoot ||
-      fiber.tag === HostPortal
-    );
-  }
-
-  function getHostSibling(fiber) {
-    // We're going to search forward into the tree until we find a sibling host
-    // node. Unfortunately, if multiple insertions are done in a row we have to
-    // search past them. This leads to exponential search for the next sibling.
-    var node = fiber;
-    siblings: while (true) {
-      // If we didn't find anything, let's try the next sibling.
-      while (node.sibling === null) {
-        if (node["return"] === null || isHostParent(node["return"])) {
-          // If we pop out of the root or hit the parent the fiber we are the
-          // last sibling.
-          return null;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-      while (node.tag !== HostComponent && node.tag !== HostText) {
-        // If it is not host node and, we might have a host node inside it.
-        // Try to search down until we find one.
-        if (node.effectTag & Placement) {
-          // If we don't have a child, try the siblings instead.
-          continue siblings;
-        }
-        // If we don't have a child, try the siblings instead.
-        // We also skip portals because they are not part of this host tree.
-        if (node.child === null || node.tag === HostPortal) {
-          continue siblings;
-        } else {
-          node.child["return"] = node;
-          node = node.child;
-        }
-      }
-      // Check if this host node is stable or about to be placed.
-      if (!(node.effectTag & Placement)) {
-        // Found it!
-        return node.stateNode;
-      }
-    }
-  }
-
-  function commitPlacement(finishedWork) {
-    // Recursively insert all host nodes into the parent.
-    var parentFiber = getHostParentFiber(finishedWork);
-    var parent = void 0;
-    var isContainer = void 0;
-    switch (parentFiber.tag) {
-      case HostComponent:
-        parent = parentFiber.stateNode;
-        isContainer = false;
-        break;
-      case HostRoot:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      case HostPortal:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      default:
-        invariant(
-          false,
-          "Invalid host parent fiber. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-    }
-    if (parentFiber.effectTag & ContentReset) {
-      // Reset the text content of the parent before doing any insertions
-      resetTextContent(parent);
-      // Clear ContentReset from the effect tag
-      parentFiber.effectTag &= ~ContentReset;
-    }
-
-    var before = getHostSibling(finishedWork);
-    // We only have the top Fiber that was inserted but we need recurse down its
-    // children to find all the terminal nodes.
-    var node = finishedWork;
-    while (true) {
-      if (node.tag === HostComponent || node.tag === HostText) {
-        if (before) {
-          if (isContainer) {
-            insertInContainerBefore(parent, node.stateNode, before);
-          } else {
-            insertBefore(parent, node.stateNode, before);
-          }
-        } else {
-          if (isContainer) {
-            appendChildToContainer(parent, node.stateNode);
-          } else {
-            appendChild(parent, node.stateNode);
-          }
-        }
-      } else if (node.tag === HostPortal) {
-        // If the insertion itself is a portal, then we don't want to traverse
-        // down its children. Instead, we'll get insertions from each child in
-        // the portal directly.
-      } else if (node.child !== null) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === finishedWork) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === finishedWork) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  function unmountHostComponents(current) {
-    // We only have the top Fiber that was inserted but we need recurse down its
-    var node = current;
-
-    // Each iteration, currentParent is populated with node's host parent if not
-    // currentParentIsValid.
-    var currentParentIsValid = false;
-    var currentParent = void 0;
-    var currentParentIsContainer = void 0;
-
-    while (true) {
-      if (!currentParentIsValid) {
-        var parent = node["return"];
-        findParent: while (true) {
-          invariant(
-            parent !== null,
-            "Expected to find a host parent. This error is likely caused by " +
-              "a bug in React. Please file an issue."
-          );
-          switch (parent.tag) {
-            case HostComponent:
-              currentParent = parent.stateNode;
-              currentParentIsContainer = false;
-              break findParent;
-            case HostRoot:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-            case HostPortal:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-          }
-          parent = parent["return"];
-        }
-        currentParentIsValid = true;
-      }
-
-      if (node.tag === HostComponent || node.tag === HostText) {
-        commitNestedUnmounts(node);
-        // After all the children have unmounted, it is now safe to remove the
-        // node from the tree.
-        if (currentParentIsContainer) {
-          removeChildFromContainer(currentParent, node.stateNode);
-        } else {
-          removeChild(currentParent, node.stateNode);
-        }
-        // Don't visit children because we already visited them.
-      } else if (node.tag === HostPortal) {
-        // When we go into a portal, it becomes the parent to remove from.
-        // We will reassign it back when we pop the portal on the way up.
-        currentParent = node.stateNode.containerInfo;
-        // Visit children because portals might contain host components.
-        if (node.child !== null) {
-          node.child["return"] = node;
-          node = node.child;
-          continue;
-        }
-      } else {
-        commitUnmount(node);
-        // Visit children because we may find more host components below.
-        if (node.child !== null) {
-          node.child["return"] = node;
-          node = node.child;
-          continue;
-        }
-      }
-      if (node === current) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === current) {
-          return;
-        }
-        node = node["return"];
-        if (node.tag === HostPortal) {
-          // When we go out of the portal, we need to restore the parent.
-          // Since we don't keep a stack of them, we will search for it.
-          currentParentIsValid = false;
-        }
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  function commitDeletion(current) {
-    // Recursively delete all host nodes from the parent.
-    // Detach refs and call componentWillUnmount() on the whole subtree.
-    unmountHostComponents(current);
-    detachFiber(current);
-  }
-
-  function commitWork(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        return;
-      }
-      case HostComponent: {
-        var _instance8 = finishedWork.stateNode;
-        if (_instance8 != null) {
-          // Commit the work prepared earlier.
-          var newProps = finishedWork.memoizedProps;
-          // For hydration we reuse the update path but we treat the oldProps
-          // as the newProps. The updatePayload will contain the real change in
-          // this case.
-          var oldProps = current !== null ? current.memoizedProps : newProps;
-          var type = finishedWork.type;
-          // TODO: Type the updateQueue to be specific to host components.
-          var updatePayload = finishedWork.updateQueue;
-          finishedWork.updateQueue = null;
-          if (updatePayload !== null) {
-            commitUpdate(
-              _instance8,
-              updatePayload,
-              type,
-              oldProps,
-              newProps,
-              finishedWork
-            );
-          }
-        }
-        return;
-      }
-      case HostText: {
-        invariant(
-          finishedWork.stateNode !== null,
-          "This should have a text node initialized. This error is likely " +
-            "caused by a bug in React. Please file an issue."
-        );
-        var textInstance = finishedWork.stateNode;
-        var newText = finishedWork.memoizedProps;
-        // For hydration we reuse the update path but we treat the oldProps
-        // as the newProps. The updatePayload will contain the real change in
-        // this case.
-        var oldText = current !== null ? current.memoizedProps : newText;
-        commitTextUpdate(textInstance, oldText, newText);
-        return;
-      }
-      case HostRoot: {
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
-    }
-  }
-
-  function commitResetTextContent(current) {
-    resetTextContent(current.stateNode);
-  }
-
-  if (enableMutatingReconciler) {
-    return {
-      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitResetTextContent: commitResetTextContent,
-      commitPlacement: commitPlacement,
-      commitDeletion: commitDeletion,
-      commitWork: commitWork,
-      commitLifeCycles: commitLifeCycles,
-      commitErrorLogging: commitErrorLogging,
-      commitAttachRef: commitAttachRef,
-      commitDetachRef: commitDetachRef
-    };
-  } else {
-    invariant(false, "Mutating reconciler is disabled.");
-  }
-};
-
-var NO_CONTEXT = {};
-
-var ReactFiberHostContext = function(config, stack) {
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
-
-  var contextStackCursor = createCursor(NO_CONTEXT);
-  var contextFiberStackCursor = createCursor(NO_CONTEXT);
-  var rootInstanceStackCursor = createCursor(NO_CONTEXT);
-
-  function requiredContext(c) {
-    invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-    return c;
-  }
-
-  function getRootHostContainer() {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    return rootInstance;
-  }
-
-  function pushHostContainer(fiber, nextRootInstance) {
-    // Push current root instance onto the stack;
-    // This allows us to reset root when portals are popped.
-    push(rootInstanceStackCursor, nextRootInstance, fiber);
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
-
-    // Finally, we need to push the host context to the stack.
-    // However, we can't just call getRootHostContext() and push it because
-    // we'd have a different number of entries on the stack depending on
-    // whether getRootHostContext() throws somewhere in renderer code or not.
-    // So we push an empty value first. This lets us safely unwind on errors.
-    push(contextStackCursor, NO_CONTEXT, fiber);
-    var nextRootContext = getRootHostContext(nextRootInstance);
-    // Now that we know this function doesn't throw, replace it.
-    pop(contextStackCursor, fiber);
-    push(contextStackCursor, nextRootContext, fiber);
-  }
-
-  function popHostContainer(fiber) {
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
-    pop(rootInstanceStackCursor, fiber);
-  }
-
-  function getHostContext() {
-    var context = requiredContext(contextStackCursor.current);
-    return context;
-  }
-
-  function pushHostContext(fiber) {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    var context = requiredContext(contextStackCursor.current);
-    var nextContext = getChildHostContext(context, fiber.type, rootInstance);
-
-    // Don't push this Fiber's context unless it's unique.
-    if (context === nextContext) {
-      return;
-    }
-
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
-    push(contextStackCursor, nextContext, fiber);
-  }
-
-  function popHostContext(fiber) {
-    // Do not pop unless this Fiber provided the current context.
-    // pushHostContext() only pushes Fibers that provide unique contexts.
-    if (contextFiberStackCursor.current !== fiber) {
-      return;
-    }
-
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
-  }
-
-  return {
-    getHostContext: getHostContext,
-    getRootHostContainer: getRootHostContainer,
-    popHostContainer: popHostContainer,
-    popHostContext: popHostContext,
-    pushHostContainer: pushHostContainer,
-    pushHostContext: pushHostContext
-  };
-};
-
-var ReactFiberHydrationContext = function(config) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    hydration = config.hydration;
-
-  // If this doesn't have hydration mode.
-
-  if (!hydration) {
-    return {
-      enterHydrationState: function() {
-        return false;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostTextInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      popHydrationState: function(fiber) {
-        return false;
-      }
-    };
-  }
-
-  var canHydrateInstance = hydration.canHydrateInstance,
-    canHydrateTextInstance = hydration.canHydrateTextInstance,
-    getNextHydratableSibling = hydration.getNextHydratableSibling,
-    getFirstHydratableChild = hydration.getFirstHydratableChild,
-    hydrateInstance = hydration.hydrateInstance,
-    hydrateTextInstance = hydration.hydrateTextInstance,
-    didNotMatchHydratedContainerTextInstance =
-      hydration.didNotMatchHydratedContainerTextInstance,
-    didNotMatchHydratedTextInstance = hydration.didNotMatchHydratedTextInstance,
-    didNotHydrateContainerInstance = hydration.didNotHydrateContainerInstance,
-    didNotHydrateInstance = hydration.didNotHydrateInstance,
-    didNotFindHydratableContainerInstance =
-      hydration.didNotFindHydratableContainerInstance,
-    didNotFindHydratableContainerTextInstance =
-      hydration.didNotFindHydratableContainerTextInstance,
-    didNotFindHydratableInstance = hydration.didNotFindHydratableInstance,
-    didNotFindHydratableTextInstance =
-      hydration.didNotFindHydratableTextInstance;
-
-  // The deepest Fiber on the stack involved in a hydration context.
-  // This may have been an insertion or a hydration.
-
-  var hydrationParentFiber = null;
-  var nextHydratableInstance = null;
-  var isHydrating = false;
-
-  function enterHydrationState(fiber) {
-    var parentInstance = fiber.stateNode.containerInfo;
-    nextHydratableInstance = getFirstHydratableChild(parentInstance);
-    hydrationParentFiber = fiber;
-    isHydrating = true;
-    return true;
-  }
-
-  function deleteHydratableInstance(returnFiber, instance) {
-    {
-      switch (returnFiber.tag) {
-        case HostRoot:
-          didNotHydrateContainerInstance(
-            returnFiber.stateNode.containerInfo,
-            instance
-          );
-          break;
-        case HostComponent:
-          didNotHydrateInstance(
-            returnFiber.type,
-            returnFiber.memoizedProps,
-            returnFiber.stateNode,
-            instance
-          );
-          break;
-      }
-    }
-
-    var childToDelete = createFiberFromHostInstanceForDeletion();
-    childToDelete.stateNode = instance;
-    childToDelete["return"] = returnFiber;
-    childToDelete.effectTag = Deletion;
-
-    // This might seem like it belongs on progressedFirstDeletion. However,
-    // these children are not part of the reconciliation list of children.
-    // Even if we abort and rereconcile the children, that will try to hydrate
-    // again and the nodes are still in the host tree so these will be
-    // recreated.
-    if (returnFiber.lastEffect !== null) {
-      returnFiber.lastEffect.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
-    } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
-    }
-  }
-
-  function insertNonHydratedInstance(returnFiber, fiber) {
-    fiber.effectTag |= Placement;
-    {
-      switch (returnFiber.tag) {
-        case HostRoot: {
-          var parentContainer = returnFiber.stateNode.containerInfo;
-          switch (fiber.tag) {
-            case HostComponent:
-              var type = fiber.type;
-              var props = fiber.pendingProps;
-              didNotFindHydratableContainerInstance(
-                parentContainer,
-                type,
-                props
-              );
-              break;
-            case HostText:
-              var text = fiber.pendingProps;
-              didNotFindHydratableContainerTextInstance(parentContainer, text);
-              break;
-          }
-          break;
-        }
-        case HostComponent: {
-          var parentType = returnFiber.type;
-          var parentProps = returnFiber.memoizedProps;
-          var parentInstance = returnFiber.stateNode;
-          switch (fiber.tag) {
-            case HostComponent:
-              var _type = fiber.type;
-              var _props = fiber.pendingProps;
-              didNotFindHydratableInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _type,
-                _props
-              );
-              break;
-            case HostText:
-              var _text = fiber.pendingProps;
-              didNotFindHydratableTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _text
-              );
-              break;
-          }
-          break;
-        }
-        default:
-          return;
-      }
-    }
-  }
-
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case HostComponent: {
-        var type = fiber.type;
-        var props = fiber.pendingProps;
-        var instance = canHydrateInstance(nextInstance, type, props);
-        if (instance !== null) {
-          fiber.stateNode = instance;
-          return true;
-        }
-        return false;
-      }
-      case HostText: {
-        var text = fiber.pendingProps;
-        var textInstance = canHydrateTextInstance(nextInstance, text);
-        if (textInstance !== null) {
-          fiber.stateNode = textInstance;
-          return true;
-        }
-        return false;
-      }
-      default:
-        return false;
-    }
-  }
-
-  function tryToClaimNextHydratableInstance(fiber) {
-    if (!isHydrating) {
-      return;
-    }
-    var nextInstance = nextHydratableInstance;
-    if (!nextInstance) {
-      // Nothing to hydrate. Make it an insertion.
-      insertNonHydratedInstance(hydrationParentFiber, fiber);
-      isHydrating = false;
-      hydrationParentFiber = fiber;
-      return;
-    }
-    if (!tryHydrate(fiber, nextInstance)) {
-      // If we can't hydrate this instance let's try the next one.
-      // We use this as a heuristic. It's based on intuition and not data so it
-      // might be flawed or unnecessary.
-      nextInstance = getNextHydratableSibling(nextInstance);
-      if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-        // Nothing to hydrate. Make it an insertion.
-        insertNonHydratedInstance(hydrationParentFiber, fiber);
-        isHydrating = false;
-        hydrationParentFiber = fiber;
-        return;
-      }
-      // We matched the next one, we'll now assume that the first one was
-      // superfluous and we'll delete it. Since we can't eagerly delete it
-      // we'll have to schedule a deletion. To do that, this node needs a dummy
-      // fiber associated with it.
-      deleteHydratableInstance(hydrationParentFiber, nextHydratableInstance);
-    }
-    hydrationParentFiber = fiber;
-    nextHydratableInstance = getFirstHydratableChild(nextInstance);
-  }
-
-  function prepareToHydrateHostInstance(
-    fiber,
-    rootContainerInstance,
-    hostContext
-  ) {
-    var instance = fiber.stateNode;
-    var updatePayload = hydrateInstance(
-      instance,
-      fiber.type,
-      fiber.memoizedProps,
-      rootContainerInstance,
-      hostContext,
-      fiber
-    );
-    // TODO: Type this specific to this type of component.
-    fiber.updateQueue = updatePayload;
-    // If the update payload indicates that there is a change or if there
-    // is a new ref we mark this as an update.
-    if (updatePayload !== null) {
-      return true;
-    }
-    return false;
-  }
-
-  function prepareToHydrateHostTextInstance(fiber) {
-    var textInstance = fiber.stateNode;
-    var textContent = fiber.memoizedProps;
-    var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
-    {
-      if (shouldUpdate) {
-        // We assume that prepareToHydrateHostTextInstance is called in a context where the
-        // hydration parent is the parent host component of this host text.
-        var returnFiber = hydrationParentFiber;
-        if (returnFiber !== null) {
-          switch (returnFiber.tag) {
-            case HostRoot: {
-              var parentContainer = returnFiber.stateNode.containerInfo;
-              didNotMatchHydratedContainerTextInstance(
-                parentContainer,
-                textInstance,
-                textContent
-              );
-              break;
-            }
-            case HostComponent: {
-              var parentType = returnFiber.type;
-              var parentProps = returnFiber.memoizedProps;
-              var parentInstance = returnFiber.stateNode;
-              didNotMatchHydratedTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                textInstance,
-                textContent
-              );
-              break;
-            }
-          }
-        }
-      }
-    }
-    return shouldUpdate;
-  }
-
-  function popToNextHostParent(fiber) {
-    var parent = fiber["return"];
-    while (
-      parent !== null &&
-      parent.tag !== HostComponent &&
-      parent.tag !== HostRoot
-    ) {
-      parent = parent["return"];
-    }
-    hydrationParentFiber = parent;
-  }
-
-  function popHydrationState(fiber) {
-    if (fiber !== hydrationParentFiber) {
-      // We're deeper than the current hydration context, inside an inserted
-      // tree.
-      return false;
-    }
-    if (!isHydrating) {
-      // If we're not currently hydrating but we're in a hydration context, then
-      // we were an insertion and now need to pop up reenter hydration of our
-      // siblings.
-      popToNextHostParent(fiber);
-      isHydrating = true;
-      return false;
-    }
-
-    var type = fiber.type;
-
-    // If we have any remaining hydratable nodes, we need to delete them now.
-    // We only do this deeper than head and body since they tend to have random
-    // other nodes in them. We also ignore components with pure text content in
-    // side of them.
-    // TODO: Better heuristic.
-    if (
-      fiber.tag !== HostComponent ||
-      (type !== "head" &&
-        type !== "body" &&
-        !shouldSetTextContent(type, fiber.memoizedProps))
-    ) {
-      var nextInstance = nextHydratableInstance;
-      while (nextInstance) {
-        deleteHydratableInstance(fiber, nextInstance);
-        nextInstance = getNextHydratableSibling(nextInstance);
-      }
-    }
-
-    popToNextHostParent(fiber);
-    nextHydratableInstance = hydrationParentFiber
-      ? getNextHydratableSibling(fiber.stateNode)
-      : null;
-    return true;
-  }
-
-  function resetHydrationState() {
-    hydrationParentFiber = null;
-    nextHydratableInstance = null;
-    isHydrating = false;
-  }
-
-  return {
-    enterHydrationState: enterHydrationState,
-    resetHydrationState: resetHydrationState,
-    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
-    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
-    popHydrationState: popHydrationState
-  };
-};
-
-// This lets us hook into Fiber to debug what it's doing.
-// See https://github.com/facebook/react/pull/8033.
-// This is not part of the public API, not even for React DevTools.
-// You may only inject a debugTool if you work on React Fiber itself.
-var ReactFiberInstrumentation = {
-  debugTool: null
-};
-
-var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
-
-var warnedAboutMissingGetChildContext = void 0;
-
-{
-  warnedAboutMissingGetChildContext = {};
-}
-
-var ReactFiberLegacyContext = function(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
-
-  // A cursor to the current merged context object on the stack.
-
-  var contextStackCursor = createCursor(emptyObject);
-  // A cursor to a boolean indicating whether the context has changed.
-  var didPerformWorkStackCursor = createCursor(false);
-  // Keep track of the previous context object that was on the stack.
-  // We use this to get access to the parent context after we have already
-  // pushed the next context provider, and now need to merge their contexts.
-  var previousContext = emptyObject;
-
-  function getUnmaskedContext(workInProgress) {
-    var hasOwnContext = isContextProvider(workInProgress);
-    if (hasOwnContext) {
-      // If the fiber is a context provider itself, when we read its context
-      // we have already pushed its own child context on the stack. A context
-      // provider should not "see" its own child context. Therefore we read the
-      // previous (parent) context instead for a context provider.
-      return previousContext;
-    }
-    return contextStackCursor.current;
-  }
-
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    var instance = workInProgress.stateNode;
-    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
-  }
-
-  function getMaskedContext(workInProgress, unmaskedContext) {
-    var type = workInProgress.type;
-    var contextTypes = type.contextTypes;
-    if (!contextTypes) {
-      return emptyObject;
-    }
-
-    // Avoid recreating masked context unless unmasked context has changed.
-    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
-    // This may trigger infinite loops if componentWillReceiveProps calls setState.
-    var instance = workInProgress.stateNode;
-    if (
-      instance &&
-      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-    ) {
-      return instance.__reactInternalMemoizedMaskedChildContext;
-    }
-
-    var context = {};
-    for (var key in contextTypes) {
-      context[key] = unmaskedContext[key];
-    }
-
-    {
-      var name = getComponentName(workInProgress) || "Unknown";
-      checkPropTypes(
-        contextTypes,
-        context,
-        "context",
-        name,
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-      );
-    }
-
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // Context is created before the class component is instantiated so check for instance.
-    if (instance) {
-      cacheContext(workInProgress, unmaskedContext, context);
-    }
-
-    return context;
-  }
-
-  function hasContextChanged() {
-    return didPerformWorkStackCursor.current;
-  }
-
-  function isContextConsumer(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
-  }
-
-  function isContextProvider(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
-  }
-
-  function popContextProvider(fiber) {
-    if (!isContextProvider(fiber)) {
-      return;
-    }
-
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
-  }
-
-  function popTopLevelContextObject(fiber) {
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
-  }
-
-  function pushTopLevelContextObject(fiber, context, didChange) {
-    invariant(
-      contextStackCursor.cursor == null,
-      "Unexpected context found on stack. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    push(contextStackCursor, context, fiber);
-    push(didPerformWorkStackCursor, didChange, fiber);
-  }
-
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode;
-    var childContextTypes = fiber.type.childContextTypes;
-
-    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
-    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
-    if (typeof instance.getChildContext !== "function") {
-      {
-        var componentName = getComponentName(fiber) || "Unknown";
-
-        if (!warnedAboutMissingGetChildContext[componentName]) {
-          warnedAboutMissingGetChildContext[componentName] = true;
-          warning(
-            false,
-            "%s.childContextTypes is specified but there is no getChildContext() method " +
-              "on the instance. You can either define getChildContext() on %s or remove " +
-              "childContextTypes from it.",
-            componentName,
-            componentName
-          );
-        }
-      }
-      return parentContext;
-    }
-
-    var childContext = void 0;
-    {
-      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
-    }
-    startPhaseTimer(fiber, "getChildContext");
-    childContext = instance.getChildContext();
-    stopPhaseTimer();
-    {
-      ReactDebugCurrentFiber.setCurrentPhase(null);
-    }
-    for (var contextKey in childContext) {
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
-      );
-    }
-    {
-      var name = getComponentName(fiber) || "Unknown";
-      checkPropTypes(
-        childContextTypes,
-        childContext,
-        "child context",
-        name,
-        // In practice, there is one case in which we won't get a stack. It's when
-        // somebody calls unstable_renderSubtreeIntoContainer() and we process
-        // context from the parent component instance. The stack will be missing
-        // because it's outside of the reconciliation, and so the pointer has not
-        // been set. This is rare and doesn't matter. We'll also remove that API.
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-      );
-    }
-
-    return Object.assign({}, parentContext, childContext);
-  }
-
-  function pushContextProvider(workInProgress) {
-    if (!isContextProvider(workInProgress)) {
-      return false;
-    }
-
-    var instance = workInProgress.stateNode;
-    // We push the context as early as possible to ensure stack integrity.
-    // If the instance does not exist yet, we will push null at first,
-    // and replace it on the stack later when invalidating the context.
-    var memoizedMergedChildContext =
-      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-      emptyObject;
-
-    // Remember the parent context so we can merge with it later.
-    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
-    previousContext = contextStackCursor.current;
-    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
-    push(
-      didPerformWorkStackCursor,
-      didPerformWorkStackCursor.current,
-      workInProgress
-    );
-
-    return true;
-  }
-
-  function invalidateContextProvider(workInProgress, didChange) {
-    var instance = workInProgress.stateNode;
-    invariant(
-      instance,
-      "Expected to have an instance by this point. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    if (didChange) {
-      // Merge parent and own context.
-      // Skip this if we're not updating due to sCU.
-      // This avoids unnecessarily recomputing memoized values.
-      var mergedContext = processChildContext(workInProgress, previousContext);
-      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-
-      // Replace the old (or empty) context with the new one.
-      // It is important to unwind the context in the reverse order.
-      pop(didPerformWorkStackCursor, workInProgress);
-      pop(contextStackCursor, workInProgress);
-      // Now push the new context and mark that it has changed.
-      push(contextStackCursor, mergedContext, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    } else {
-      pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    }
-  }
-
-  function findCurrentUnmaskedContext(fiber) {
-    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
-    // makes sense elsewhere
-    invariant(
-      isFiberMounted(fiber) && fiber.tag === ClassComponent,
-      "Expected subtree parent to be a mounted class component. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    var node = fiber;
-    while (node.tag !== HostRoot) {
-      if (isContextProvider(node)) {
-        return node.stateNode.__reactInternalMemoizedMergedChildContext;
-      }
-      var parent = node["return"];
-      invariant(
-        parent,
-        "Found unexpected detached subtree parent. " +
-          "This error is likely caused by a bug in React. Please file an issue."
-      );
-      node = parent;
-    }
-    return node.stateNode.context;
-  }
-
-  return {
-    getUnmaskedContext: getUnmaskedContext,
-    cacheContext: cacheContext,
-    getMaskedContext: getMaskedContext,
-    hasContextChanged: hasContextChanged,
-    isContextConsumer: isContextConsumer,
-    isContextProvider: isContextProvider,
-    popContextProvider: popContextProvider,
-    popTopLevelContextObject: popTopLevelContextObject,
-    pushTopLevelContextObject: pushTopLevelContextObject,
-    processChildContext: processChildContext,
-    pushContextProvider: pushContextProvider,
-    invalidateContextProvider: invalidateContextProvider,
-    findCurrentUnmaskedContext: findCurrentUnmaskedContext
-  };
-};
-
-var ReactFiberNewContext = function(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
-
-  var providerCursor = createCursor(null);
-  var valueCursor = createCursor(null);
-  var changedBitsCursor = createCursor(0);
-
-  var rendererSigil = void 0;
-  {
-    // Use this to detect multiple renderers using the same context
-    rendererSigil = {};
-  }
-
-  function pushProvider(providerFiber) {
-    var context = providerFiber.type._context;
-
-    push(changedBitsCursor, context._changedBits, providerFiber);
-    push(valueCursor, context._currentValue, providerFiber);
-    push(providerCursor, providerFiber, providerFiber);
-
-    context._currentValue = providerFiber.pendingProps.value;
-    context._changedBits = providerFiber.stateNode;
-
-    {
-      !(
-        context._currentRenderer === null ||
-        context._currentRenderer === rendererSigil
-      )
-        ? warning(
-            false,
-            "Detected multiple renderers concurrently rendering the " +
-              "same context provider. This is currently unsupported."
-          )
-        : void 0;
-      context._currentRenderer = rendererSigil;
-    }
-  }
-
-  function popProvider(providerFiber) {
-    var changedBits = changedBitsCursor.current;
-    var currentValue = valueCursor.current;
-
-    pop(providerCursor, providerFiber);
-    pop(valueCursor, providerFiber);
-    pop(changedBitsCursor, providerFiber);
-
-    var context = providerFiber.type._context;
-    context._currentValue = currentValue;
-    context._changedBits = changedBits;
-  }
-
-  return {
-    pushProvider: pushProvider,
-    popProvider: popProvider
-  };
-};
-
-var ReactFiberStack = function() {
-  var valueStack = [];
-
-  var fiberStack = void 0;
-
-  {
-    fiberStack = [];
-  }
-
-  var index = -1;
-
-  function createCursor(defaultValue) {
-    return {
-      current: defaultValue
-    };
-  }
-
-  function isEmpty() {
-    return index === -1;
-  }
-
-  function pop(cursor, fiber) {
-    if (index < 0) {
-      {
-        warning(false, "Unexpected pop.");
-      }
-      return;
-    }
-
-    {
-      if (fiber !== fiberStack[index]) {
-        warning(false, "Unexpected Fiber popped.");
-      }
-    }
-
-    cursor.current = valueStack[index];
-
-    valueStack[index] = null;
-
-    {
-      fiberStack[index] = null;
-    }
-
-    index--;
-  }
-
-  function push(cursor, value, fiber) {
-    index++;
-
-    valueStack[index] = cursor.current;
-
-    {
-      fiberStack[index] = fiber;
-    }
-
-    cursor.current = value;
-  }
-
-  function checkThatStackIsEmpty() {
-    {
-      if (index !== -1) {
-        warning(
-          false,
-          "Expected an empty stack. Something was not reset properly."
-        );
-      }
-    }
-  }
-
-  function resetStackAfterFatalErrorInDev() {
-    {
-      index = -1;
-      valueStack.length = 0;
-      fiberStack.length = 0;
-    }
-  }
-
-  return {
-    createCursor: createCursor,
-    isEmpty: isEmpty,
-    pop: pop,
-    push: push,
-    checkThatStackIsEmpty: checkThatStackIsEmpty,
-    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
-  };
-};
-
-var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError = ReactErrorUtils.hasCaughtError;
-var clearCaughtError = ReactErrorUtils.clearCaughtError;
-
-var didWarnAboutStateTransition = void 0;
-var didWarnSetStateChildContext = void 0;
-var warnAboutUpdateOnUnmounted = void 0;
-var warnAboutInvalidUpdates = void 0;
-
-{
-  didWarnAboutStateTransition = false;
-  didWarnSetStateChildContext = false;
-  var didWarnStateUpdateForUnmountedComponent = {};
-
-  warnAboutUpdateOnUnmounted = function(fiber) {
-    // We show the whole stack but dedupe on the top component's name because
-    // the problematic code almost always lies inside that component.
-    var componentName = getComponentName(fiber) || "ReactClass";
-    if (didWarnStateUpdateForUnmountedComponent[componentName]) {
-      return;
-    }
-    warning(
-      false,
-      "Can't call setState (or forceUpdate) on an unmounted component. This " +
-        "is a no-op, but it indicates a memory leak in your application. To " +
-        "fix, cancel all subscriptions and asynchronous tasks in the " +
-        "componentWillUnmount method.%s",
-      getStackAddendumByWorkInProgressFiber(fiber)
-    );
-    didWarnStateUpdateForUnmountedComponent[componentName] = true;
-  };
-
-  warnAboutInvalidUpdates = function(instance) {
-    switch (ReactDebugCurrentFiber.phase) {
-      case "getChildContext":
-        if (didWarnSetStateChildContext) {
-          return;
-        }
-        warning(
-          false,
-          "setState(...): Cannot call setState() inside getChildContext()"
-        );
-        didWarnSetStateChildContext = true;
-        break;
-      case "render":
-        if (didWarnAboutStateTransition) {
-          return;
-        }
-        warning(
-          false,
-          "Cannot update during an existing state transition (such as within " +
-            "`render` or another component's constructor). Render methods should " +
-            "be a pure function of props and state; constructor side-effects are " +
-            "an anti-pattern, but can be moved to `componentWillMount`."
-        );
-        didWarnAboutStateTransition = true;
-        break;
-    }
-  };
-}
-
-var ReactFiberScheduler = function(config) {
-  var stack = ReactFiberStack();
-  var hostContext = ReactFiberHostContext(config, stack);
-  var legacyContext = ReactFiberLegacyContext(stack);
-  var newContext = ReactFiberNewContext(stack);
-  var popHostContext = hostContext.popHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popLegacyContextProvider = legacyContext.popContextProvider;
-  var popProvider = newContext.popProvider;
-
-  var hydrationContext = ReactFiberHydrationContext(config);
-
-  var _ReactFiberBeginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber
-    ),
-    beginWork = _ReactFiberBeginWork.beginWork;
-
-  var _ReactFiberCompleteWo = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext
-    ),
-    completeWork = _ReactFiberCompleteWo.completeWork;
-
-  var _ReactFiberUnwindWork = ReactFiberUnwindWork(
-      hostContext,
-      legacyContext,
-      newContext,
-      scheduleWork,
-      isAlreadyFailedLegacyErrorBoundary
-    ),
-    throwException = _ReactFiberUnwindWork.throwException,
-    unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
-
-  var _ReactFiberCommitWork = ReactFiberCommitWork(
-      config,
-      onCommitPhaseError,
-      scheduleWork,
-      computeExpirationForFiber,
-      markLegacyErrorBoundaryAsFailed,
-      recalculateCurrentTime
-    ),
-    commitBeforeMutationLifeCycles =
-      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
-    commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
-    commitPlacement = _ReactFiberCommitWork.commitPlacement,
-    commitDeletion = _ReactFiberCommitWork.commitDeletion,
-    commitWork = _ReactFiberCommitWork.commitWork,
-    commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
-    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
-    commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
-    commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
-
-  var now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit;
-
-  // Represents the current time in ms.
-
-  var originalStartTimeMs = now();
-  var mostRecentCurrentTime = msToExpirationTime(0);
-  var mostRecentCurrentTimeMs = originalStartTimeMs;
-
-  // Used to ensure computeUniqueAsyncExpiration is monotonically increases.
-  var lastUniqueAsyncExpiration = 0;
-
-  // Represents the expiration time that incoming updates should use. (If this
-  // is NoWork, use the default strategy: async updates in async mode, sync
-  // updates in sync mode.)
-  var expirationContext = NoWork;
-
-  var isWorking = false;
-
-  // The next work in progress fiber that we're currently working on.
-  var nextUnitOfWork = null;
-  var nextRoot = null;
-  // The time at which we're currently rendering work.
-  var nextRenderExpirationTime = NoWork;
-
-  // The next fiber with an effect that we're currently committing.
-  var nextEffect = null;
-
-  var isCommitting = false;
-
-  var isRootReadyForCommit = false;
-
-  var legacyErrorBoundariesThatAlreadyFailed = null;
-
-  // Used for performance tracking.
-  var interruptedBy = null;
-
-  var stashedWorkInProgressProperties = void 0;
-  var replayUnitOfWork = void 0;
-  var isReplayingFailedUnitOfWork = void 0;
-  var originalReplayError = void 0;
-  var rethrowOriginalError = void 0;
-  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-    stashedWorkInProgressProperties = null;
-    isReplayingFailedUnitOfWork = false;
-    originalReplayError = null;
-    replayUnitOfWork = function(failedUnitOfWork, error, isAsync) {
-      // Restore the original state of the work-in-progress
-      assignFiberPropertiesInDEV(
-        failedUnitOfWork,
-        stashedWorkInProgressProperties
-      );
-      switch (failedUnitOfWork.tag) {
-        case HostRoot:
-          popHostContainer(failedUnitOfWork);
-          popTopLevelLegacyContextObject(failedUnitOfWork);
-          break;
-        case HostComponent:
-          popHostContext(failedUnitOfWork);
-          break;
-        case ClassComponent:
-          popLegacyContextProvider(failedUnitOfWork);
-          break;
-        case HostPortal:
-          popHostContainer(failedUnitOfWork);
-          break;
-        case ContextProvider:
-          popProvider(failedUnitOfWork);
-          break;
-      }
-      // Replay the begin phase.
-      isReplayingFailedUnitOfWork = true;
-      originalReplayError = error;
-      invokeGuardedCallback$2(null, workLoop, null, isAsync);
-      isReplayingFailedUnitOfWork = false;
-      originalReplayError = null;
-      if (hasCaughtError()) {
-        clearCaughtError();
-      } else {
-        // If the begin phase did not fail the second time, set this pointer
-        // back to the original value.
-        nextUnitOfWork = failedUnitOfWork;
-      }
-    };
-    rethrowOriginalError = function() {
-      throw originalReplayError;
-    };
-  }
-
-  function resetStack() {
-    if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork["return"];
-      while (interruptedWork !== null) {
-        unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork["return"];
-      }
-    }
-
-    {
-      ReactStrictModeWarnings.discardPendingWarnings();
-      stack.checkThatStackIsEmpty();
-    }
-
-    nextRoot = null;
-    nextRenderExpirationTime = NoWork;
-    nextUnitOfWork = null;
-
-    isRootReadyForCommit = false;
-  }
-
-  function commitAllHostEffects() {
-    while (nextEffect !== null) {
-      {
-        ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
-      }
-      recordEffect();
-
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & ContentReset) {
-        commitResetTextContent(nextEffect);
-      }
-
-      if (effectTag & Ref) {
-        var current = nextEffect.alternate;
-        if (current !== null) {
-          commitDetachRef(current);
-        }
-      }
-
-      // The following switch statement is only concerned about placement,
-      // updates, and deletions. To avoid needing to add a case for every
-      // possible bitmap value, we remove the secondary effects from the
-      // effect tag and switch on that value.
-      var primaryEffectTag = effectTag & (Placement | Update | Deletion);
-      switch (primaryEffectTag) {
-        case Placement: {
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          // TODO: findDOMNode doesn't rely on this any more but isMounted
-          // does and isMounted is deprecated anyway so we should be able
-          // to kill this.
-          nextEffect.effectTag &= ~Placement;
-          break;
-        }
-        case PlacementAndUpdate: {
-          // Placement
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          nextEffect.effectTag &= ~Placement;
-
-          // Update
-          var _current = nextEffect.alternate;
-          commitWork(_current, nextEffect);
-          break;
-        }
-        case Update: {
-          var _current2 = nextEffect.alternate;
-          commitWork(_current2, nextEffect);
-          break;
-        }
-        case Deletion: {
-          commitDeletion(nextEffect);
-          break;
-        }
-      }
-      nextEffect = nextEffect.nextEffect;
-    }
-
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
-    }
-  }
-
-  function commitBeforeMutationLifecycles() {
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & Snapshot) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitBeforeMutationLifeCycles(current, nextEffect);
-      }
-
-      // Don't cleanup effects yet;
-      // This will be done by commitAllLifeCycles()
-      nextEffect = nextEffect.nextEffect;
-    }
-  }
-
-  function commitAllLifeCycles(
-    finishedRoot,
-    currentTime,
-    committedExpirationTime
-  ) {
-    {
-      ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
-
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.flushPendingDeprecationWarnings();
-      }
-    }
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & (Update | Callback)) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitLifeCycles(
-          finishedRoot,
-          current,
-          nextEffect,
-          currentTime,
-          committedExpirationTime
-        );
-      }
-
-      if (effectTag & ErrLog) {
-        commitErrorLogging(nextEffect, onUncaughtError);
-      }
-
-      if (effectTag & Ref) {
-        recordEffect();
-        commitAttachRef(nextEffect);
-      }
-
-      var next = nextEffect.nextEffect;
-      // Ensure that we clean these up so that we don't accidentally keep them.
-      // I'm not actually sure this matters because we can't reset firstEffect
-      // and lastEffect since they're on every node, not just the effectful
-      // ones. So we have to clean everything as we reuse nodes anyway.
-      nextEffect.nextEffect = null;
-      // Ensure that we reset the effectTag here so that we can rely on effect
-      // tags to reason about the current life-cycle.
-      nextEffect = next;
-    }
-  }
-
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      legacyErrorBoundariesThatAlreadyFailed !== null &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
-  }
-
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    if (legacyErrorBoundariesThatAlreadyFailed === null) {
-      legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
-    } else {
-      legacyErrorBoundariesThatAlreadyFailed.add(instance);
-    }
-  }
-
-  function commitRoot(finishedWork) {
-    isWorking = true;
-    isCommitting = true;
-    startCommitTimer();
-
-    var root = finishedWork.stateNode;
-    invariant(
-      root.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug " +
-        "related to the return field. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-    var committedExpirationTime = root.pendingCommitExpirationTime;
-    invariant(
-      committedExpirationTime !== NoWork,
-      "Cannot commit an incomplete root. This error is likely caused by a " +
-        "bug in React. Please file an issue."
-    );
-    root.pendingCommitExpirationTime = NoWork;
-
-    var currentTime = recalculateCurrentTime();
-
-    // Reset this to null before calling lifecycles
-    ReactCurrentOwner.current = null;
-
-    var firstEffect = void 0;
-    if (finishedWork.effectTag > PerformedWork) {
-      // A fiber's effect list consists only of its children, not itself. So if
-      // the root has an effect, we need to add it to the end of the list. The
-      // resulting list is the set that would belong to the root's parent, if
-      // it had one; that is, all the effects in the tree including the root.
-      if (finishedWork.lastEffect !== null) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        firstEffect = finishedWork.firstEffect;
-      } else {
-        firstEffect = finishedWork;
-      }
-    } else {
-      // There is no effect on the root.
-      firstEffect = finishedWork.firstEffect;
-    }
-
-    prepareForCommit(root.containerInfo);
-
-    // Invoke instances of getSnapshotBeforeUpdate before mutation.
-    nextEffect = firstEffect;
-    startCommitSnapshotEffectsTimer();
-    while (nextEffect !== null) {
-      var didError = false;
-      var error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
-        if (hasCaughtError()) {
-          didError = true;
-          error = clearCaughtError();
-        }
-      }
-      if (didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
-    stopCommitSnapshotEffectsTimer();
-
-    // Commit all the side-effects within a tree. We'll do this in two passes.
-    // The first pass performs all the host insertions, updates, deletions and
-    // ref unmounts.
-    nextEffect = firstEffect;
-    startCommitHostEffectsTimer();
-    while (nextEffect !== null) {
-      var _didError = false;
-      var _error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitAllHostEffects, null);
-        if (hasCaughtError()) {
-          _didError = true;
-          _error = clearCaughtError();
-        }
-      }
-      if (_didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
-    stopCommitHostEffectsTimer();
-
-    resetAfterCommit(root.containerInfo);
-
-    // The work-in-progress tree is now the current tree. This must come after
-    // the first pass of the commit phase, so that the previous tree is still
-    // current during componentWillUnmount, but before the second pass, so that
-    // the finished work is current during componentDidMount/Update.
-    root.current = finishedWork;
-
-    // In the second pass we'll perform all life-cycles and ref callbacks.
-    // Life-cycles happen as a separate pass so that all placements, updates,
-    // and deletions in the entire tree have already been invoked.
-    // This pass also triggers any renderer-specific initial effects.
-    nextEffect = firstEffect;
-    startCommitLifeCyclesTimer();
-    while (nextEffect !== null) {
-      var _didError2 = false;
-      var _error2 = void 0;
-      {
-        invokeGuardedCallback$2(
-          null,
-          commitAllLifeCycles,
-          null,
-          root,
-          currentTime,
-          committedExpirationTime
-        );
-        if (hasCaughtError()) {
-          _didError2 = true;
-          _error2 = clearCaughtError();
-        }
-      }
-      if (_didError2) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error2);
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
-
-    isCommitting = false;
-    isWorking = false;
-    stopCommitLifeCyclesTimer();
-    stopCommitTimer();
-    if (typeof onCommitRoot === "function") {
-      onCommitRoot(finishedWork.stateNode);
-    }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
-    }
-
-    var remainingTime = root.current.expirationTime;
-    if (remainingTime === NoWork) {
-      // If there's no remaining work, we can clear the set of already failed
-      // error boundaries.
-      legacyErrorBoundariesThatAlreadyFailed = null;
-    }
-    return remainingTime;
-  }
-
-  function resetExpirationTime(workInProgress, renderTime) {
-    if (renderTime !== Never && workInProgress.expirationTime === Never) {
-      // The children of this component are hidden. Don't bubble their
-      // expiration times.
-      return;
-    }
-
-    // Check for pending updates.
-    var newExpirationTime = getUpdateExpirationTime(workInProgress);
-
-    // TODO: Calls need to visit stateNode
-
-    // Bubble up the earliest expiration time.
-    var child = workInProgress.child;
-    while (child !== null) {
-      if (
-        child.expirationTime !== NoWork &&
-        (newExpirationTime === NoWork ||
-          newExpirationTime > child.expirationTime)
-      ) {
-        newExpirationTime = child.expirationTime;
-      }
-      child = child.sibling;
-    }
-    workInProgress.expirationTime = newExpirationTime;
-  }
-
-  function completeUnitOfWork(workInProgress) {
-    // Attempt to complete the current unit of work, then move to the
-    // next sibling. If there are no more siblings, return to the
-    // parent fiber.
-    while (true) {
-      // The current, flushed, state of this fiber is the alternate.
-      // Ideally nothing should rely on this, but relying on it here
-      // means that we don't need an additional field on the work in
-      // progress.
-      var current = workInProgress.alternate;
-      {
-        ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
-      }
-
-      var returnFiber = workInProgress["return"];
-      var siblingFiber = workInProgress.sibling;
-
-      if ((workInProgress.effectTag & Incomplete) === NoEffect) {
-        // This fiber completed.
-        var next = completeWork(
-          current,
-          workInProgress,
-          nextRenderExpirationTime
-        );
-        stopWorkTimer(workInProgress);
-        resetExpirationTime(workInProgress, nextRenderExpirationTime);
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
-
-        if (next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
-          }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          return next;
-        }
-
-        if (
-          returnFiber !== null &&
-          // Do not append effects to parents if a sibling failed to complete
-          (returnFiber.effectTag & Incomplete) === NoEffect
-        ) {
-          // Append all the effects of the subtree and this fiber onto the effect
-          // list of the parent. The completion order of the children affects the
-          // side-effect order.
-          if (returnFiber.firstEffect === null) {
-            returnFiber.firstEffect = workInProgress.firstEffect;
-          }
-          if (workInProgress.lastEffect !== null) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
-            }
-            returnFiber.lastEffect = workInProgress.lastEffect;
-          }
-
-          // If this fiber had side-effects, we append it AFTER the children's
-          // side-effects. We can perform certain side-effects earlier if
-          // needed, by doing multiple passes over the effect list. We don't want
-          // to schedule our own side-effect on our own list because if end up
-          // reusing children we'll schedule this effect onto itself since we're
-          // at the end.
-          var effectTag = workInProgress.effectTag;
-          // Skip both NoWork and PerformedWork tags when creating the effect list.
-          // PerformedWork effect is read by React DevTools but shouldn't be committed.
-          if (effectTag > PerformedWork) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress;
-            } else {
-              returnFiber.firstEffect = workInProgress;
-            }
-            returnFiber.lastEffect = workInProgress;
-          }
-        }
-
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
-        }
-
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
-        } else {
-          // We've reached the root.
-          isRootReadyForCommit = true;
-          return null;
-        }
-      } else {
-        // This fiber did not complete because something threw. Pop values off
-        // the stack without entering the complete phase. If this is a boundary,
-        // capture values if possible.
-        var _next = unwindWork(workInProgress);
-        // Because this fiber did not complete, don't reset its expiration time.
-        if (workInProgress.effectTag & DidCapture) {
-          // Restarting an error boundary
-          stopFailedWorkTimer(workInProgress);
-        } else {
-          stopWorkTimer(workInProgress);
-        }
-
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
-
-        if (_next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
-          }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          // Since we're restarting, remove anything that is not a host effect
-          // from the effect tag.
-          _next.effectTag &= HostEffectMask;
-          return _next;
-        }
-
-        if (returnFiber !== null) {
-          // Mark the parent fiber as incomplete and clear its effect list.
-          returnFiber.firstEffect = returnFiber.lastEffect = null;
-          returnFiber.effectTag |= Incomplete;
-        }
-
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
-        }
-
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
-        } else {
-          return null;
-        }
-      }
-    }
-
-    // Without this explicit null return Flow complains of invalid return type
-    // TODO Remove the above while(true) loop
-    // eslint-disable-next-line no-unreachable
-    return null;
-  }
-
-  function performUnitOfWork(workInProgress) {
-    // The current, flushed, state of this fiber is the alternate.
-    // Ideally nothing should rely on this, but relying on it here
-    // means that we don't need an additional field on the work in
-    // progress.
-    var current = workInProgress.alternate;
-
-    // See if beginning this work spawns more work.
-    startWorkTimer(workInProgress);
-    {
-      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
-    }
-
-    if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
-        stashedWorkInProgressProperties,
-        workInProgress
-      );
-    }
-    var next = beginWork(current, workInProgress, nextRenderExpirationTime);
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
-      if (isReplayingFailedUnitOfWork) {
-        // Currently replaying a failed unit of work. This should be unreachable,
-        // because the render phase is meant to be idempotent, and it should
-        // have thrown again. Since it didn't, rethrow the original error, so
-        // React's internal stack is not misaligned.
-        rethrowOriginalError();
-      }
-    }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
-    }
-
-    if (next === null) {
-      // If this doesn't spawn new work, complete the current work.
-      next = completeUnitOfWork(workInProgress);
-    }
-
-    ReactCurrentOwner.current = null;
-
-    return next;
-  }
-
-  function workLoop(isAsync) {
-    if (!isAsync) {
-      // Flush all expired work.
-      while (nextUnitOfWork !== null) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      }
-    } else {
-      // Flush asynchronous work until the deadline runs out of time.
-      while (nextUnitOfWork !== null && !shouldYield()) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      }
-    }
-  }
-
-  function renderRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
-    );
-    isWorking = true;
-
-    // Check if we're starting from a fresh stack, or if we're resuming from
-    // previously yielded work.
-    if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      nextUnitOfWork === null
-    ) {
-      // Reset the stack and start working from the root.
-      resetStack();
-      nextRoot = root;
-      nextRenderExpirationTime = expirationTime;
-      nextUnitOfWork = createWorkInProgress(
-        nextRoot.current,
-        null,
-        nextRenderExpirationTime
-      );
-      root.pendingCommitExpirationTime = NoWork;
-    }
-
-    var didFatal = false;
-
-    startWorkLoopTimer(nextUnitOfWork);
-
-    do {
-      try {
-        workLoop(isAsync);
-      } catch (thrownValue) {
-        if (nextUnitOfWork === null) {
-          // This is a fatal error.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-          break;
-        }
-
-        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-          var failedUnitOfWork = nextUnitOfWork;
-          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
-        }
-
-        var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber["return"];
-        if (returnFiber === null) {
-          // This is the root. The root could capture its own errors. However,
-          // we don't know if it errors before or after we pushed the host
-          // context. This information is needed to avoid a stack mismatch.
-          // Because we're not sure, treat this as a fatal error. We could track
-          // which phase it fails in, but doesn't seem worth it. At least
-          // for now.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        throwException(returnFiber, sourceFiber, thrownValue);
-        nextUnitOfWork = completeUnitOfWork(sourceFiber);
-      }
-      break;
-    } while (true);
-
-    // We're done performing work. Time to clean up.
-    var didCompleteRoot = false;
-    isWorking = false;
-
-    // Yield back to main thread.
-    if (didFatal) {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There was a fatal error.
-      {
-        stack.resetStackAfterFatalErrorInDev();
-      }
-      return null;
-    } else if (nextUnitOfWork === null) {
-      // We reached the root.
-      if (isRootReadyForCommit) {
-        didCompleteRoot = true;
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        // The root successfully completed. It's ready for commit.
-        root.pendingCommitExpirationTime = expirationTime;
-        var finishedWork = root.current.alternate;
-        return finishedWork;
-      } else {
-        // The root did not complete.
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        invariant(
-          false,
-          "Expired work should have completed. This error is likely caused " +
-            "by a bug in React. Please file an issue."
-        );
-      }
-    } else {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There's more work to do, but we ran out of time. Yield back to
-      // the renderer.
-      return null;
-    }
-  }
-
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    // TODO: We only support dispatching errors.
-    var capturedValue = createCapturedValue(value, sourceFiber);
-    var update = {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: false,
-      isForced: false,
-      capturedValue: capturedValue,
-      next: null
-    };
-    insertUpdateIntoFiber(boundaryFiber, update);
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-
-  function dispatch(sourceFiber, value, expirationTime) {
-    invariant(
-      !isWorking || isCommitting,
-      "dispatch: Cannot dispatch during the render phase."
-    );
-
-    // TODO: Handle arrays
-
-    var fiber = sourceFiber["return"];
-    while (fiber !== null) {
-      switch (fiber.tag) {
-        case ClassComponent:
-          var ctor = fiber.type;
-          var instance = fiber.stateNode;
-          if (
-            typeof ctor.getDerivedStateFromCatch === "function" ||
-            (typeof instance.componentDidCatch === "function" &&
-              !isAlreadyFailedLegacyErrorBoundary(instance))
-          ) {
-            scheduleCapture(sourceFiber, fiber, value, expirationTime);
-            return;
-          }
-          break;
-        // TODO: Handle async boundaries
-        case HostRoot:
-          scheduleCapture(sourceFiber, fiber, value, expirationTime);
-          return;
-      }
-      fiber = fiber["return"];
-    }
-
-    if (sourceFiber.tag === HostRoot) {
-      // Error was thrown at the root. There is no parent, so the root
-      // itself should capture it.
-      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
-    }
-  }
-
-  function onCommitPhaseError(fiber, error) {
-    return dispatch(fiber, error, Sync);
-  }
-
-  function computeAsyncExpiration(currentTime) {
-    // Given the current clock time, returns an expiration time. We use rounding
-    // to batch like updates together.
-    // Should complete within ~1000ms. 1200ms max.
-    var expirationMs = 5000;
-    var bucketSizeMs = 250;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
-
-  function computeInteractiveExpiration(currentTime) {
-    var expirationMs = void 0;
-    // We intentionally set a higher expiration time for interactive updates in
-    // dev than in production.
-    // If the main thread is being blocked so long that you hit the expiration,
-    // it's a problem that could be solved with better scheduling.
-    // People will be more likely to notice this and fix it with the long
-    // expiration time in development.
-    // In production we opt for better UX at the risk of masking scheduling
-    // problems, by expiring fast.
-    {
-      // Should complete within ~500ms. 600ms max.
-      expirationMs = 500;
-    }
-    var bucketSizeMs = 100;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
-
-  // Creates a unique async expiration time.
-  function computeUniqueAsyncExpiration() {
-    var currentTime = recalculateCurrentTime();
-    var result = computeAsyncExpiration(currentTime);
-    if (result <= lastUniqueAsyncExpiration) {
-      // Since we assume the current time monotonically increases, we only hit
-      // this branch when computeUniqueAsyncExpiration is fired multiple times
-      // within a 200ms window (or whatever the async bucket size is).
-      result = lastUniqueAsyncExpiration + 1;
-    }
-    lastUniqueAsyncExpiration = result;
-    return lastUniqueAsyncExpiration;
-  }
-
-  function computeExpirationForFiber(fiber) {
-    var expirationTime = void 0;
-    if (expirationContext !== NoWork) {
-      // An explicit expiration context was set;
-      expirationTime = expirationContext;
-    } else if (isWorking) {
-      if (isCommitting) {
-        // Updates that occur during the commit phase should have sync priority
-        // by default.
-        expirationTime = Sync;
-      } else {
-        // Updates during the render phase should expire at the same time as
-        // the work that is being rendered.
-        expirationTime = nextRenderExpirationTime;
-      }
-    } else {
-      // No explicit expiration context was set, and we're not currently
-      // performing work. Calculate a new expiration time.
-      if (fiber.mode & AsyncMode) {
-        if (isBatchingInteractiveUpdates) {
-          // This is an interactive update
-          var currentTime = recalculateCurrentTime();
-          expirationTime = computeInteractiveExpiration(currentTime);
-        } else {
-          // This is an async update
-          var _currentTime = recalculateCurrentTime();
-          expirationTime = computeAsyncExpiration(_currentTime);
-        }
-      } else {
-        // This is a sync update
-        expirationTime = Sync;
-      }
-    }
-    if (isBatchingInteractiveUpdates) {
-      // This is an interactive update. Keep track of the lowest pending
-      // interactive expiration time. This allows us to synchronously flush
-      // all interactive updates when needed.
-      if (
-        lowestPendingInteractiveExpirationTime === NoWork ||
-        expirationTime > lowestPendingInteractiveExpirationTime
-      ) {
-        lowestPendingInteractiveExpirationTime = expirationTime;
-      }
-    }
-    return expirationTime;
-  }
-
-  function scheduleWork(fiber, expirationTime) {
-    return scheduleWorkImpl(fiber, expirationTime, false);
-  }
-
-  function scheduleWorkImpl(fiber, expirationTime, isErrorRecovery) {
-    recordScheduleUpdate();
-
-    {
-      if (!isErrorRecovery && fiber.tag === ClassComponent) {
-        var instance = fiber.stateNode;
-        warnAboutInvalidUpdates(instance);
-      }
-    }
-
-    var node = fiber;
-    while (node !== null) {
-      // Walk the parent path to the root and update each node's
-      // expiration time.
-      if (
-        node.expirationTime === NoWork ||
-        node.expirationTime > expirationTime
-      ) {
-        node.expirationTime = expirationTime;
-      }
-      if (node.alternate !== null) {
-        if (
-          node.alternate.expirationTime === NoWork ||
-          node.alternate.expirationTime > expirationTime
-        ) {
-          node.alternate.expirationTime = expirationTime;
-        }
-      }
-      if (node["return"] === null) {
-        if (node.tag === HostRoot) {
-          var root = node.stateNode;
-          if (
-            !isWorking &&
-            nextRenderExpirationTime !== NoWork &&
-            expirationTime < nextRenderExpirationTime
-          ) {
-            // This is an interruption. (Used for performance tracking.)
-            interruptedBy = fiber;
-            resetStack();
-          }
-          if (
-            // If we're in the render phase, we don't need to schedule this root
-            // for an update, because we'll do it before we exit...
-            !isWorking ||
-            isCommitting ||
-            // ...unless this is a different root than the one we're rendering.
-            nextRoot !== root
-          ) {
-            // Add this root to the root schedule.
-            requestWork(root, expirationTime);
-          }
-          if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
-            invariant(
-              false,
-              "Maximum update depth exceeded. This can happen when a " +
-                "component repeatedly calls setState inside " +
-                "componentWillUpdate or componentDidUpdate. React limits " +
-                "the number of nested updates to prevent infinite loops."
-            );
-          }
-        } else {
-          {
-            if (!isErrorRecovery && fiber.tag === ClassComponent) {
-              warnAboutUpdateOnUnmounted(fiber);
-            }
-          }
-          return;
-        }
-      }
-      node = node["return"];
-    }
-  }
-
-  function recalculateCurrentTime() {
-    // Subtract initial time so it fits inside 32bits
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
-    return mostRecentCurrentTime;
-  }
-
-  function deferredUpdates(fn) {
-    var previousExpirationContext = expirationContext;
-    var currentTime = recalculateCurrentTime();
-    expirationContext = computeAsyncExpiration(currentTime);
-    try {
-      return fn();
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = Sync;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-
-  // TODO: Everything below this is written as if it has been lifted to the
-  // renderers. I'll do this in a follow-up.
-
-  // Linked-list of roots
-  var firstScheduledRoot = null;
-  var lastScheduledRoot = null;
-
-  var callbackExpirationTime = NoWork;
-  var callbackID = -1;
-  var isRendering = false;
-  var nextFlushedRoot = null;
-  var nextFlushedExpirationTime = NoWork;
-  var lowestPendingInteractiveExpirationTime = NoWork;
-  var deadlineDidExpire = false;
-  var hasUnhandledError = false;
-  var unhandledError = null;
-  var deadline = null;
-
-  var isBatchingUpdates = false;
-  var isUnbatchingUpdates = false;
-  var isBatchingInteractiveUpdates = false;
-
-  var completedBatches = null;
-
-  // Use these to prevent an infinite loop of nested updates
-  var NESTED_UPDATE_LIMIT = 1000;
-  var nestedUpdateCount = 0;
-
-  var timeHeuristicForUnitOfWork = 1;
-
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (callbackExpirationTime !== NoWork) {
-      // A callback is already scheduled. Check its expiration time (timeout).
-      if (expirationTime > callbackExpirationTime) {
-        // Existing callback has sufficient timeout. Exit.
-        return;
-      } else {
-        // Existing callback has insufficient timeout. Cancel and schedule a
-        // new one.
-        cancelDeferredCallback(callbackID);
-      }
-      // The request callback timer is already running. Don't start a new one.
-    } else {
-      startRequestCallbackTimer();
-    }
-
-    // Compute a timeout for the given expiration time.
-    var currentMs = now() - originalStartTimeMs;
-    var expirationMs = expirationTimeToMs(expirationTime);
-    var timeout = expirationMs - currentMs;
-
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: timeout
-    });
-  }
-
-  // requestWork is called by the scheduler whenever a root receives an update.
-  // It's up to the renderer to call renderRoot at some point in the future.
-  function requestWork(root, expirationTime) {
-    addRootToSchedule(root, expirationTime);
-
-    if (isRendering) {
-      // Prevent reentrancy. Remaining work will be scheduled at the end of
-      // the currently rendering batch.
-      return;
-    }
-
-    if (isBatchingUpdates) {
-      // Flush work at the end of the batch.
-      if (isUnbatchingUpdates) {
-        // ...unless we're inside unbatchedUpdates, in which case we should
-        // flush it now.
-        nextFlushedRoot = root;
-        nextFlushedExpirationTime = Sync;
-        performWorkOnRoot(root, Sync, false);
-      }
-      return;
-    }
-
-    // TODO: Get rid of Sync and use current time?
-    if (expirationTime === Sync) {
-      performSyncWork();
-    } else {
-      scheduleCallbackWithExpiration(expirationTime);
-    }
-  }
-
-  function addRootToSchedule(root, expirationTime) {
-    // Add the root to the schedule.
-    // Check if this root is already part of the schedule.
-    if (root.nextScheduledRoot === null) {
-      // This root is not already scheduled. Add it.
-      root.remainingExpirationTime = expirationTime;
-      if (lastScheduledRoot === null) {
-        firstScheduledRoot = lastScheduledRoot = root;
-        root.nextScheduledRoot = root;
-      } else {
-        lastScheduledRoot.nextScheduledRoot = root;
-        lastScheduledRoot = root;
-        lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-      }
-    } else {
-      // This root is already scheduled, but its priority may have increased.
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        remainingExpirationTime === NoWork ||
-        expirationTime < remainingExpirationTime
-      ) {
-        // Update the priority.
-        root.remainingExpirationTime = expirationTime;
-      }
-    }
-  }
-
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = NoWork;
-    var highestPriorityRoot = null;
-    if (lastScheduledRoot !== null) {
-      var previousScheduledRoot = lastScheduledRoot;
-      var root = firstScheduledRoot;
-      while (root !== null) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (remainingExpirationTime === NoWork) {
-          // This root no longer has work. Remove it from the scheduler.
-
-          // TODO: This check is redudant, but Flow is confused by the branch
-          // below where we set lastScheduledRoot to null, even though we break
-          // from the loop right after.
-          invariant(
-            previousScheduledRoot !== null && lastScheduledRoot !== null,
-            "Should have a previous and last root. This error is likely " +
-              "caused by a bug in React. Please file an issue."
-          );
-          if (root === root.nextScheduledRoot) {
-            // This is the only root in the list.
-            root.nextScheduledRoot = null;
-            firstScheduledRoot = lastScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot) {
-            // This is the first root in the list.
-            var next = root.nextScheduledRoot;
-            firstScheduledRoot = next;
-            lastScheduledRoot.nextScheduledRoot = next;
-            root.nextScheduledRoot = null;
-          } else if (root === lastScheduledRoot) {
-            // This is the last root in the list.
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else {
-            previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
-            root.nextScheduledRoot = null;
-          }
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            highestPriorityWork === NoWork ||
-            remainingExpirationTime < highestPriorityWork
-          ) {
-            // Update the priority, if it's higher
-            highestPriorityWork = remainingExpirationTime;
-            highestPriorityRoot = root;
-          }
-          if (root === lastScheduledRoot) {
-            break;
-          }
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
-        }
-      }
-    }
-
-    // If the next root is the same as the previous root, this is a nested
-    // update. To prevent an infinite loop, increment the nested update count.
-    var previousFlushedRoot = nextFlushedRoot;
-    if (
-      previousFlushedRoot !== null &&
-      previousFlushedRoot === highestPriorityRoot &&
-      highestPriorityWork === Sync
-    ) {
-      nestedUpdateCount++;
-    } else {
-      // Reset whenever we switch roots.
-      nestedUpdateCount = 0;
-    }
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
-  }
-
-  function performAsyncWork(dl) {
-    performWork(NoWork, true, dl);
-  }
-
-  function performSyncWork() {
-    performWork(Sync, false, null);
-  }
-
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
-
-    // Keep working on roots until there's no more work, or until the we reach
-    // the deadline.
-    findHighestPriorityRoot();
-
-    if (enableUserTimingAPI && deadline !== null) {
-      var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
-      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
-      stopRequestCallbackTimer(didExpire, timeout);
-    }
-
-    if (isAsync) {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime)
-      ) {
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        );
-        findHighestPriorityRoot();
-      }
-    } else {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime)
-      ) {
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
-        findHighestPriorityRoot();
-      }
-    }
-
-    // We're done flushing work. Either we ran out of time in this callback,
-    // or there's no more work left with sufficient priority.
-
-    // If we're inside a callback, set this to false since we just completed it.
-    if (deadline !== null) {
-      callbackExpirationTime = NoWork;
-      callbackID = -1;
-    }
-    // If there's work left over, schedule a new callback.
-    if (nextFlushedExpirationTime !== NoWork) {
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
-    }
-
-    // Clean-up.
-    deadline = null;
-    deadlineDidExpire = false;
-
-    finishRendering();
-  }
-
-  function flushRoot(root, expirationTime) {
-    invariant(
-      !isRendering,
-      "work.commit(): Cannot commit while already rendering. This likely " +
-        "means you attempted to commit from inside a lifecycle method."
-    );
-    // Perform work on root as if the given expiration time is the current time.
-    // This has the effect of synchronously flushing all work up to and
-    // including the given time.
-    nextFlushedRoot = root;
-    nextFlushedExpirationTime = expirationTime;
-    performWorkOnRoot(root, expirationTime, false);
-    // Flush any sync work that was scheduled by lifecycles
-    performSyncWork();
-    finishRendering();
-  }
-
-  function finishRendering() {
-    nestedUpdateCount = 0;
-
-    if (completedBatches !== null) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          if (!hasUnhandledError) {
-            hasUnhandledError = true;
-            unhandledError = error;
-          }
-        }
-      }
-    }
-
-    if (hasUnhandledError) {
-      var error = unhandledError;
-      unhandledError = null;
-      hasUnhandledError = false;
-      throw error;
-    }
-  }
-
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
-    );
-
-    isRendering = true;
-
-    // Check if this is async work or sync/expired work.
-    if (!isAsync) {
-      // Flush sync work.
-      var finishedWork = root.finishedWork;
-      if (finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot(root, finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        finishedWork = renderRoot(root, expirationTime, false);
-        if (finishedWork !== null) {
-          // We've completed the root. Commit it.
-          completeRoot(root, finishedWork, expirationTime);
-        }
-      }
-    } else {
-      // Flush async work.
-      var _finishedWork = root.finishedWork;
-      if (_finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot(root, _finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        _finishedWork = renderRoot(root, expirationTime, true);
-        if (_finishedWork !== null) {
-          // We've completed the root. Check the deadline one more time
-          // before committing.
-          if (!shouldYield()) {
-            // Still time left. Commit the root.
-            completeRoot(root, _finishedWork, expirationTime);
-          } else {
-            // There's no time left. Mark this root as complete. We'll come
-            // back and commit it later.
-            root.finishedWork = _finishedWork;
-          }
-        }
-      }
-    }
-
-    isRendering = false;
-  }
-
-  function completeRoot(root, finishedWork, expirationTime) {
-    // Check if there's a batch that matches this expiration time.
-    var firstBatch = root.firstBatch;
-    if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
-      if (completedBatches === null) {
-        completedBatches = [firstBatch];
-      } else {
-        completedBatches.push(firstBatch);
-      }
-      if (firstBatch._defer) {
-        // This root is blocked from committing by a batch. Unschedule it until
-        // we receive another update.
-        root.finishedWork = finishedWork;
-        root.remainingExpirationTime = NoWork;
-        return;
-      }
-    }
-
-    // Commit the root.
-    root.finishedWork = null;
-    root.remainingExpirationTime = commitRoot(finishedWork);
-  }
-
-  // When working on async work, the reconciler asks the renderer if it should
-  // yield execution. For DOM, we implement this with requestIdleCallback.
-  function shouldYield() {
-    if (deadline === null) {
-      return false;
-    }
-    if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
-      // Disregard deadline.didTimeout. Only expired work should be flushed
-      // during a timeout. This path is only hit for non-expired work.
-      return false;
-    }
-    deadlineDidExpire = true;
-    return true;
-  }
-
-  function onUncaughtError(error) {
-    invariant(
-      nextFlushedRoot !== null,
-      "Should be working on a root. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-    // Unschedule this root so we don't work on it again until there's
-    // another update.
-    nextFlushedRoot.remainingExpirationTime = NoWork;
-    if (!hasUnhandledError) {
-      hasUnhandledError = true;
-      unhandledError = error;
-    }
-  }
-
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function batchedUpdates(fn, a) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return fn(a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
-      }
-    }
-  }
-
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function unbatchedUpdates(fn, a) {
-    if (isBatchingUpdates && !isUnbatchingUpdates) {
-      isUnbatchingUpdates = true;
-      try {
-        return fn(a);
-      } finally {
-        isUnbatchingUpdates = false;
-      }
-    }
-    return fn(a);
-  }
-
-  // TODO: Batching should be implemented at the renderer level, not within
-  // the reconciler.
-  function flushSync(fn, a) {
-    invariant(
-      !isRendering,
-      "flushSync was called from inside a lifecycle method. It cannot be " +
-        "called when React is already rendering."
-    );
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return syncUpdates(fn, a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      performSyncWork();
-    }
-  }
-
-  function interactiveUpdates(fn, a, b) {
-    if (isBatchingInteractiveUpdates) {
-      return fn(a, b);
-    }
-    // If there are any pending interactive updates, synchronously flush them.
-    // This needs to happen before we read any handlers, because the effect of
-    // the previous event may influence which handlers are called during
-    // this event.
-    if (
-      !isBatchingUpdates &&
-      !isRendering &&
-      lowestPendingInteractiveExpirationTime !== NoWork
-    ) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
-    }
-    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingInteractiveUpdates = true;
-    isBatchingUpdates = true;
-    try {
-      return fn(a, b);
-    } finally {
-      isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
-      }
-    }
-  }
-
-  function flushInteractiveUpdates() {
-    if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
-    }
-  }
-
-  function flushControlled(fn) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      syncUpdates(fn);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performWork(Sync, false, null);
-      }
-    }
-  }
-
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: flushRoot,
-    batchedUpdates: batchedUpdates,
-    unbatchedUpdates: unbatchedUpdates,
-    flushSync: flushSync,
-    flushControlled: flushControlled,
-    deferredUpdates: deferredUpdates,
-    syncUpdates: syncUpdates,
-    interactiveUpdates: interactiveUpdates,
-    flushInteractiveUpdates: flushInteractiveUpdates,
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-    legacyContext: legacyContext
-  };
-};
-
-var didWarnAboutNestedUpdates = void 0;
-
-{
-  didWarnAboutNestedUpdates = false;
-}
-
-// 0 is PROD, 1 is DEV.
-// Might add PROFILE later.
-
-var ReactFiberReconciler$1 = function(config) {
-  var getPublicInstance = config.getPublicInstance;
-
-  var _ReactFiberScheduler = ReactFiberScheduler(config),
-    computeUniqueAsyncExpiration =
-      _ReactFiberScheduler.computeUniqueAsyncExpiration,
-    recalculateCurrentTime = _ReactFiberScheduler.recalculateCurrentTime,
-    computeExpirationForFiber = _ReactFiberScheduler.computeExpirationForFiber,
-    scheduleWork = _ReactFiberScheduler.scheduleWork,
-    requestWork = _ReactFiberScheduler.requestWork,
-    flushRoot = _ReactFiberScheduler.flushRoot,
-    batchedUpdates = _ReactFiberScheduler.batchedUpdates,
-    unbatchedUpdates = _ReactFiberScheduler.unbatchedUpdates,
-    flushSync = _ReactFiberScheduler.flushSync,
-    flushControlled = _ReactFiberScheduler.flushControlled,
-    deferredUpdates = _ReactFiberScheduler.deferredUpdates,
-    syncUpdates = _ReactFiberScheduler.syncUpdates,
-    interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
-    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
-    legacyContext = _ReactFiberScheduler.legacyContext;
-
-  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
-
-  function getContextForSubtree(parentComponent) {
-    if (!parentComponent) {
-      return emptyObject;
-    }
-
-    var fiber = get$1(parentComponent);
-    var parentContext = findCurrentUnmaskedContext(fiber);
-    return isContextProvider(fiber)
-      ? processChildContext(fiber, parentContext)
-      : parentContext;
-  }
-
-  function scheduleRootUpdate(
-    current,
-    element,
-    currentTime,
-    expirationTime,
-    callback
-  ) {
-    {
-      if (
-        ReactDebugCurrentFiber.phase === "render" &&
-        ReactDebugCurrentFiber.current !== null &&
-        !didWarnAboutNestedUpdates
-      ) {
-        didWarnAboutNestedUpdates = true;
-        warning(
-          false,
-          "Render methods should be a pure function of props and state; " +
-            "triggering nested component updates from render is not allowed. " +
-            "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
-            "Check the render method of %s.",
-          getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
-        );
-      }
-    }
-
-    callback = callback === undefined ? null : callback;
-    {
-      !(callback === null || typeof callback === "function")
-        ? warning(
-            false,
-            "render(...): Expected the last optional `callback` argument to be a " +
-              "function. Instead received: %s.",
-            callback
-          )
-        : void 0;
-    }
-
-    var update = {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: callback,
-      isReplace: false,
-      isForced: false,
-      capturedValue: null,
-      next: null
-    };
-    insertUpdateIntoFiber(current, update);
-    scheduleWork(current, expirationTime);
-
-    return expirationTime;
-  }
-
-  function updateContainerAtExpirationTime(
-    element,
-    container,
-    parentComponent,
-    currentTime,
-    expirationTime,
-    callback
-  ) {
-    // TODO: If this is a nested container, this won't be the root.
-    var current = container.current;
-
-    {
-      if (ReactFiberInstrumentation_1.debugTool) {
-        if (current.alternate === null) {
-          ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
-        } else if (element === null) {
-          ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
-        } else {
-          ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
-        }
-      }
-    }
-
-    var context = getContextForSubtree(parentComponent);
-    if (container.context === null) {
-      container.context = context;
-    } else {
-      container.pendingContext = context;
-    }
-
-    return scheduleRootUpdate(
-      current,
-      element,
-      currentTime,
-      expirationTime,
-      callback
-    );
-  }
-
-  function findHostInstance(component) {
-    var fiber = get$1(component);
-    if (fiber === undefined) {
-      if (typeof component.render === "function") {
-        invariant(false, "Unable to find node on an unmounted component.");
-      } else {
-        invariant(
-          false,
-          "Argument appears to not be a ReactComponent. Keys: %s",
-          Object.keys(component)
-        );
-      }
-    }
-    var hostFiber = findCurrentHostFiber(fiber);
-    if (hostFiber === null) {
-      return null;
-    }
-    return hostFiber.stateNode;
-  }
-
-  return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      return createFiberRoot(containerInfo, isAsync, hydrate);
-    },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current;
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        expirationTime,
-        callback
-      );
-    },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
-    ) {
-      var currentTime = recalculateCurrentTime();
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        expirationTime,
-        callback
-      );
-    },
-
-    flushRoot: flushRoot,
-
-    requestWork: requestWork,
-
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-
-    batchedUpdates: batchedUpdates,
-
-    unbatchedUpdates: unbatchedUpdates,
-
-    deferredUpdates: deferredUpdates,
-
-    syncUpdates: syncUpdates,
-
-    interactiveUpdates: interactiveUpdates,
-
-    flushInteractiveUpdates: flushInteractiveUpdates,
-
-    flushControlled: flushControlled,
-
-    flushSync: flushSync,
-
-    getPublicRootInstance: function(container) {
-      var containerFiber = container.current;
-      if (!containerFiber.child) {
-        return null;
-      }
-      switch (containerFiber.child.tag) {
-        case HostComponent:
-          return getPublicInstance(containerFiber.child.stateNode);
-        default:
-          return containerFiber.child.stateNode;
-      }
-    },
-
-    findHostInstance: findHostInstance,
-
-    findHostInstanceWithNoPortals: function(fiber) {
-      var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
-      if (hostFiber === null) {
-        return null;
-      }
-      return hostFiber.stateNode;
-    },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            var hostFiber = findCurrentHostFiber(fiber);
-            if (hostFiber === null) {
-              return null;
-            }
-            return hostFiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            if (!findFiberByHostInstance) {
-              // Might not be implemented by the renderer.
-              return null;
-            }
-            return findFiberByHostInstance(instance);
-          }
-        })
-      );
-    }
-  };
-};
-
-var ReactFiberReconciler$2 = Object.freeze({
-  default: ReactFiberReconciler$1
-});
-
-var ReactFiberReconciler$3 =
-  (ReactFiberReconciler$2 && ReactFiberReconciler$1) || ReactFiberReconciler$2;
-
-// TODO: bundle Flow types with the package.
-
-// TODO: decide on the top-level export form.
-// This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3["default"]
-  ? ReactFiberReconciler$3["default"]
-  : ReactFiberReconciler$3;
-
-function _classCallCheck$1(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
-  }
-}
-
-// Modules provided by RN:
-// Counter for uniquely identifying views.
-// % 10 === 1 means it is a rootTag.
-// % 2 === 0 means it is a Fabric tag.
-// This means that they never overlap.
-var nextReactTag = 2;
-
-/**
- * This is used for refs on host components.
- */
-
-var ReactFabricHostComponent = (function() {
-  function ReactFabricHostComponent(tag, viewConfig, props) {
-    _classCallCheck$1(this, ReactFabricHostComponent);
-
-    this._nativeTag = tag;
-    this.viewConfig = viewConfig;
-    this.currentProps = props;
-  }
-
-  ReactFabricHostComponent.prototype.blur = function blur() {
-    TextInputState.blurTextInput(this._nativeTag);
-  };
-
-  ReactFabricHostComponent.prototype.focus = function focus() {
-    TextInputState.focusTextInput(this._nativeTag);
-  };
-
-  ReactFabricHostComponent.prototype.measure = function measure(callback) {
-    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-  };
-
-  ReactFabricHostComponent.prototype.measureInWindow = function measureInWindow(
-    callback
-  ) {
-    UIManager.measureInWindow(
-      this._nativeTag,
-      mountSafeCallback(this, callback)
-    );
-  };
-
-  ReactFabricHostComponent.prototype.measureLayout = function measureLayout(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      this._nativeTag,
-      relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  };
-
-  ReactFabricHostComponent.prototype.setNativeProps = function setNativeProps(
-    nativeProps
-  ) {
-    {
-      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
-    }
-
-    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
-
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        this._nativeTag,
-        this.viewConfig.uiViewClassName,
-        updatePayload
-      );
-    }
-  };
-
-  return ReactFabricHostComponent;
-})();
-
-var ReactFabricRenderer = reactReconciler({
-  appendInitialChild: function(parentInstance, child) {
-    FabricUIManager.appendChild(parentInstance.node, child.node);
-  },
-  createInstance: function(
-    type,
-    props,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    var tag = nextReactTag;
-    nextReactTag += 2;
-
-    var viewConfig = ReactNativeViewConfigRegistry.get(type);
-
-    {
-      for (var key in viewConfig.validAttributes) {
-        if (props.hasOwnProperty(key)) {
-          deepFreezeAndThrowOnMutationInDev(props[key]);
-        }
-      }
-    }
-
-    var updatePayload = create(props, viewConfig.validAttributes);
-
-    var node = FabricUIManager.createNode(
-      tag, // reactTag
-      viewConfig.uiViewClassName, // viewName
-      rootContainerInstance, // rootTag
-      updatePayload, // props
-      internalInstanceHandle
-    );
-
-    var component = new ReactFabricHostComponent(tag, viewConfig, props);
-
-    return {
-      node: node,
-      canonical: component
-    };
-  },
-  createTextInstance: function(
-    text,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    var tag = nextReactTag;
-    nextReactTag += 2;
-
-    var node = FabricUIManager.createNode(
-      tag, // reactTag
-      "RCTRawText", // viewName
-      rootContainerInstance, // rootTag
-      { text: text }, // props
-      internalInstanceHandle
-    );
-
-    return {
-      node: node
-    };
-  },
-  finalizeInitialChildren: function(
-    parentInstance,
-    type,
-    props,
-    rootContainerInstance
-  ) {
-    return false;
-  },
-  getRootHostContext: function() {
-    return emptyObject;
-  },
-  getChildHostContext: function() {
-    return emptyObject;
-  },
-  getPublicInstance: function(instance) {
-    return instance.canonical;
-  },
-
-  now: now,
-
-  prepareForCommit: function() {
-    // Noop
-  },
-  prepareUpdate: function(
-    instance,
-    type,
-    oldProps,
-    newProps,
-    rootContainerInstance,
-    hostContext
-  ) {
-    var viewConfig = instance.canonical.viewConfig;
-    var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
-    // TODO: If the event handlers have changed, we need to update the current props
-    // in the commit phase but there is no host config hook to do it yet.
-    return updatePayload;
-  },
-  resetAfterCommit: function() {
-    // Noop
-  },
-
-  scheduleDeferredCallback: scheduleDeferredCallback,
-  cancelDeferredCallback: cancelDeferredCallback,
-
-  shouldDeprioritizeSubtree: function(type, props) {
-    return false;
-  },
-  shouldSetTextContent: function(type, props) {
-    // TODO (bvaughn) Revisit this decision.
-    // Always returning false simplifies the createInstance() implementation,
-    // But creates an additional child Fiber for raw text children.
-    // No additional native views are created though.
-    // It's not clear to me which is better so I'm deferring for now.
-    // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
-    return false;
-  },
-
-  persistence: {
-    cloneInstance: function(
-      instance,
-      updatePayload,
-      type,
-      oldProps,
-      newProps,
-      internalInstanceHandle,
-      keepChildren,
-      recyclableInstance
-    ) {
-      var node = instance.node;
-      var clone = void 0;
-      if (keepChildren) {
-        if (updatePayload !== null) {
-          clone = FabricUIManager.cloneNodeWithNewProps(node, updatePayload);
-        } else {
-          clone = FabricUIManager.cloneNode(node);
-        }
-      } else {
-        if (updatePayload !== null) {
-          clone = FabricUIManager.cloneNodeWithNewChildrenAndProps(
-            node,
-            updatePayload
-          );
-        } else {
-          clone = FabricUIManager.cloneNodeWithNewChildren(node);
-        }
-      }
-      return {
-        node: clone,
-        canonical: instance.canonical
-      };
-    },
-    createContainerChildSet: function(container) {
-      return FabricUIManager.createChildSet(container);
-    },
-    appendChildToContainerChildSet: function(childSet, child) {
-      FabricUIManager.appendChildToSet(childSet, child.node);
-    },
-    finalizeContainerChildren: function(container, newChildren) {
-      FabricUIManager.completeRoot(container, newChildren);
-    },
-    replaceContainerChildren: function(container, newChildren) {}
-  }
-});
-
-// Module provided by RN:
-var getInspectorDataForViewTag = void 0;
-
-{
-  var traverseOwnerTreeUp = function(hierarchy, instance) {
-    if (instance) {
-      hierarchy.unshift(instance);
-      traverseOwnerTreeUp(hierarchy, instance._debugOwner);
-    }
-  };
-
-  var getOwnerHierarchy = function(instance) {
-    var hierarchy = [];
-    traverseOwnerTreeUp(hierarchy, instance);
-    return hierarchy;
-  };
-
-  var lastNonHostInstance = function(hierarchy) {
-    for (var i = hierarchy.length - 1; i > 1; i--) {
-      var instance = hierarchy[i];
-
-      if (instance.tag !== HostComponent) {
-        return instance;
-      }
-    }
-    return hierarchy[0];
-  };
-
-  var getHostProps = function(fiber) {
-    var host = findCurrentHostFiber(fiber);
-    if (host) {
-      return host.memoizedProps || emptyObject;
-    }
-    return emptyObject;
-  };
-
-  var getHostNode = function(fiber, findNodeHandle) {
-    var hostNode = void 0;
-    // look for children first for the hostNode
-    // as composite fibers do not have a hostNode
-    while (fiber) {
-      if (fiber.stateNode !== null && fiber.tag === HostComponent) {
-        hostNode = findNodeHandle(fiber.stateNode);
-      }
-      if (hostNode) {
-        return hostNode;
-      }
-      fiber = fiber.child;
-    }
-    return null;
-  };
-
-  var createHierarchy = function(fiberHierarchy) {
-    return fiberHierarchy.map(function(fiber) {
-      return {
-        name: getComponentName(fiber),
-        getInspectorData: function(findNodeHandle) {
-          return {
-            measure: function(callback) {
-              return UIManager.measure(
-                getHostNode(fiber, findNodeHandle),
-                callback
-              );
-            },
-            props: getHostProps(fiber),
-            source: fiber._debugSource
-          };
-        }
-      };
-    });
-  };
-
-  getInspectorDataForViewTag = function(viewTag) {
-    var closestInstance = getInstanceFromTag(viewTag);
-
-    // Handle case where user clicks outside of ReactNative
-    if (!closestInstance) {
-      return {
-        hierarchy: [],
-        props: emptyObject,
-        selection: null,
-        source: null
-      };
-    }
-
-    var fiber = findCurrentFiberUsingSlowPath(closestInstance);
-    var fiberHierarchy = getOwnerHierarchy(fiber);
-    var instance = lastNonHostInstance(fiberHierarchy);
-    var hierarchy = createHierarchy(fiberHierarchy);
-    var props = getHostProps(instance);
-    var source = instance._debugSource;
-    var selection = fiberHierarchy.indexOf(instance);
-
-    return {
-      hierarchy: hierarchy,
-      props: props,
-      selection: selection,
-      source: source
-    };
-  };
-}
-
-var findHostInstance = ReactFabricRenderer.findHostInstance;
-
-function findNodeHandle(componentOrHandle) {
-  {
-    var owner = ReactCurrentOwner.current;
-    if (owner !== null && owner.stateNode !== null) {
-      !owner.stateNode._warnedAboutRefsInRender
-        ? warning(
-            false,
-            "%s is accessing findNodeHandle inside its render(). " +
-              "render() should be a pure function of props and state. It should " +
-              "never access something that requires stale data from the previous " +
-              "render, such as refs. Move this logic to componentDidMount and " +
-              "componentDidUpdate instead.",
-            getComponentName(owner) || "A component"
-          )
-        : void 0;
-
-      owner.stateNode._warnedAboutRefsInRender = true;
-    }
-  }
-  if (componentOrHandle == null) {
-    return null;
-  }
-  if (typeof componentOrHandle === "number") {
-    // Already a node handle
-    return componentOrHandle;
-  }
-  if (componentOrHandle._nativeTag) {
-    return componentOrHandle._nativeTag;
-  }
-  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag) {
-    return componentOrHandle.canonical._nativeTag;
-  }
-  var hostInstance = findHostInstance(componentOrHandle);
-  if (hostInstance == null) {
-    return hostInstance;
-  }
-  if (hostInstance.canonical) {
-    // Fabric
-    return hostInstance.canonical._nativeTag;
-  }
-  return hostInstance._nativeTag;
-}
-
-injection$2.injectRenderer(ReactFabricRenderer);
-
-var roots = new Map();
-
-var ReactFabric = {
-  NativeComponent: ReactNativeComponent(findNodeHandle, findHostInstance),
-
-  findNodeHandle: findNodeHandle,
-
-  render: function(element, containerTag, callback) {
-    var root = roots.get(containerTag);
-
-    if (!root) {
-      // TODO (bvaughn): If we decide to keep the wrapper component,
-      // We could create a wrapper for containerTag as well to reduce special casing.
-      root = ReactFabricRenderer.createContainer(containerTag, false, false);
-      roots.set(containerTag, root);
-    }
-    ReactFabricRenderer.updateContainer(element, root, null, callback);
-
-    return ReactFabricRenderer.getPublicRootInstance(root);
-  },
-  unmountComponentAtNode: function(containerTag) {
-    var root = roots.get(containerTag);
-    if (root) {
-      // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
-      ReactFabricRenderer.updateContainer(null, root, null, function() {
-        roots["delete"](containerTag);
-      });
-    }
-  },
-  createPortal: function(children, containerTag) {
-    var key =
-      arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : null;
-
-    return createPortal(children, containerTag, null, key);
-  },
-
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
-    // Used as a mixin in many createClass-based components
-    NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
-    // Used by react-native-github/Libraries/ components
-    ReactNativeComponentTree: ReactNativeComponentTree
-  }
-};
-
-{
-  // $FlowFixMe
-  Object.assign(
-    ReactFabric.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-    {
-      // TODO: none of these work since Fiber. Remove these dependencies.
-      // Used by RCTRenderingPerf, Systrace:
-      ReactDebugTool: {
-        addHook: function() {},
-        removeHook: function() {}
-      },
-      // Used by ReactPerfStallHandler, RCTRenderingPerf:
-      ReactPerf: {
-        start: function() {},
-        stop: function() {},
-        printInclusive: function() {},
-        printWasted: function() {}
-      }
-    }
-  );
-}
-
-ReactFabricRenderer.injectIntoDevTools({
-  findFiberByHostInstance: getInstanceFromTag,
-  getInspectorDataForViewTag: getInspectorDataForViewTag,
-  bundleType: 1,
-  version: ReactVersion,
-  rendererPackageName: "react-native-renderer"
-});
-
-var ReactFabric$2 = Object.freeze({
-  default: ReactFabric
-});
-
-var ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
-
-// TODO: decide on the top-level export form.
-// This is hacky but makes it work with both Rollup and Jest.
-var fabric = ReactFabric$3["default"]
-  ? ReactFabric$3["default"]
-  : ReactFabric$3;
-
-module.exports = fabric;
-
-  })();
-}
diff --git a/Libraries/Renderer/fb/ReactFabric-prod.js b/Libraries/Renderer/fb/ReactFabric-prod.js
deleted file mode 100644
index 19ca0dde9e33..000000000000
--- a/Libraries/Renderer/fb/ReactFabric-prod.js
+++ /dev/null
@@ -1,5875 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @noflow
- * @preventMunge
- */
-
-"use strict";
-require("InitializeCore");
-var invariant = require("fbjs/lib/invariant"),
-  emptyFunction = require("fbjs/lib/emptyFunction"),
-  ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
-  UIManager = require("UIManager"),
-  TextInputState = require("TextInputState"),
-  deepDiffer = require("deepDiffer"),
-  flattenStyle = require("flattenStyle"),
-  React = require("react"),
-  emptyObject = require("fbjs/lib/emptyObject"),
-  shallowEqual = require("fbjs/lib/shallowEqual"),
-  FabricUIManager = require("FabricUIManager"),
-  eventPluginOrder = null,
-  namesToPlugins = {};
-function recomputePluginOrdering() {
-  if (eventPluginOrder)
-    for (var pluginName in namesToPlugins) {
-      var pluginModule = namesToPlugins[pluginName],
-        pluginIndex = eventPluginOrder.indexOf(pluginName);
-      invariant(
-        -1 < pluginIndex,
-        "EventPluginRegistry: Cannot inject event plugins that do not exist in the plugin ordering, `%s`.",
-        pluginName
-      );
-      if (!plugins[pluginIndex]) {
-        invariant(
-          pluginModule.extractEvents,
-          "EventPluginRegistry: Event plugins must implement an `extractEvents` method, but `%s` does not.",
-          pluginName
-        );
-        plugins[pluginIndex] = pluginModule;
-        pluginIndex = pluginModule.eventTypes;
-        for (var eventName in pluginIndex) {
-          var JSCompiler_inline_result = void 0;
-          var dispatchConfig = pluginIndex[eventName],
-            pluginModule$jscomp$0 = pluginModule,
-            eventName$jscomp$0 = eventName;
-          invariant(
-            !eventNameDispatchConfigs.hasOwnProperty(eventName$jscomp$0),
-            "EventPluginHub: More than one plugin attempted to publish the same event name, `%s`.",
-            eventName$jscomp$0
-          );
-          eventNameDispatchConfigs[eventName$jscomp$0] = dispatchConfig;
-          var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
-          if (phasedRegistrationNames) {
-            for (JSCompiler_inline_result in phasedRegistrationNames)
-              phasedRegistrationNames.hasOwnProperty(
-                JSCompiler_inline_result
-              ) &&
-                publishRegistrationName(
-                  phasedRegistrationNames[JSCompiler_inline_result],
-                  pluginModule$jscomp$0,
-                  eventName$jscomp$0
-                );
-            JSCompiler_inline_result = !0;
-          } else
-            dispatchConfig.registrationName
-              ? (publishRegistrationName(
-                  dispatchConfig.registrationName,
-                  pluginModule$jscomp$0,
-                  eventName$jscomp$0
-                ),
-                (JSCompiler_inline_result = !0))
-              : (JSCompiler_inline_result = !1);
-          invariant(
-            JSCompiler_inline_result,
-            "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
-            eventName,
-            pluginName
-          );
-        }
-      }
-    }
-}
-function publishRegistrationName(registrationName, pluginModule) {
-  invariant(
-    !registrationNameModules[registrationName],
-    "EventPluginHub: More than one plugin attempted to publish the same registration name, `%s`.",
-    registrationName
-  );
-  registrationNameModules[registrationName] = pluginModule;
-}
-var plugins = [],
-  eventNameDispatchConfigs = {},
-  registrationNameModules = {},
-  getFiberCurrentPropsFromNode = null,
-  getInstanceFromNode = null,
-  getNodeFromInstance = null;
-function isEndish(topLevelType) {
-  return (
-    "topMouseUp" === topLevelType ||
-    "topTouchEnd" === topLevelType ||
-    "topTouchCancel" === topLevelType
-  );
-}
-function isMoveish(topLevelType) {
-  return "topMouseMove" === topLevelType || "topTouchMove" === topLevelType;
-}
-function isStartish(topLevelType) {
-  return "topMouseDown" === topLevelType || "topTouchStart" === topLevelType;
-}
-function executeDirectDispatch(event) {
-  var dispatchListener = event._dispatchListeners,
-    dispatchInstance = event._dispatchInstances;
-  invariant(
-    !Array.isArray(dispatchListener),
-    "executeDirectDispatch(...): Invalid `event`."
-  );
-  event.currentTarget = dispatchListener
-    ? getNodeFromInstance(dispatchInstance)
-    : null;
-  dispatchListener = dispatchListener ? dispatchListener(event) : null;
-  event.currentTarget = null;
-  event._dispatchListeners = null;
-  event._dispatchInstances = null;
-  return dispatchListener;
-}
-function accumulateInto(current, next) {
-  invariant(
-    null != next,
-    "accumulateInto(...): Accumulated items must not be null or undefined."
-  );
-  if (null == current) return next;
-  if (Array.isArray(current)) {
-    if (Array.isArray(next)) return current.push.apply(current, next), current;
-    current.push(next);
-    return current;
-  }
-  return Array.isArray(next) ? [current].concat(next) : [current, next];
-}
-function forEachAccumulated(arr, cb, scope) {
-  Array.isArray(arr) ? arr.forEach(cb, scope) : arr && cb.call(scope, arr);
-}
-var injection = {
-  injectEventPluginOrder: function(injectedEventPluginOrder) {
-    invariant(
-      !eventPluginOrder,
-      "EventPluginRegistry: Cannot inject event plugin ordering more than once. You are likely trying to load more than one copy of React."
-    );
-    eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
-    recomputePluginOrdering();
-  },
-  injectEventPluginsByName: function(injectedNamesToPlugins) {
-    var isOrderingDirty = !1,
-      pluginName;
-    for (pluginName in injectedNamesToPlugins)
-      if (injectedNamesToPlugins.hasOwnProperty(pluginName)) {
-        var pluginModule = injectedNamesToPlugins[pluginName];
-        (namesToPlugins.hasOwnProperty(pluginName) &&
-          namesToPlugins[pluginName] === pluginModule) ||
-          (invariant(
-            !namesToPlugins[pluginName],
-            "EventPluginRegistry: Cannot inject two different event plugins using the same name, `%s`.",
-            pluginName
-          ),
-          (namesToPlugins[pluginName] = pluginModule),
-          (isOrderingDirty = !0));
-      }
-    isOrderingDirty && recomputePluginOrdering();
-  }
-};
-function getListener(inst, registrationName) {
-  var listener = inst.stateNode;
-  if (!listener) return null;
-  var props = getFiberCurrentPropsFromNode(listener);
-  if (!props) return null;
-  listener = props[registrationName];
-  a: switch (registrationName) {
-    case "onClick":
-    case "onClickCapture":
-    case "onDoubleClick":
-    case "onDoubleClickCapture":
-    case "onMouseDown":
-    case "onMouseDownCapture":
-    case "onMouseMove":
-    case "onMouseMoveCapture":
-    case "onMouseUp":
-    case "onMouseUpCapture":
-      (props = !props.disabled) ||
-        ((inst = inst.type),
-        (props = !(
-          "button" === inst ||
-          "input" === inst ||
-          "select" === inst ||
-          "textarea" === inst
-        )));
-      inst = !props;
-      break a;
-    default:
-      inst = !1;
-  }
-  if (inst) return null;
-  invariant(
-    !listener || "function" === typeof listener,
-    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
-    registrationName,
-    typeof listener
-  );
-  return listener;
-}
-function getParent(inst) {
-  do inst = inst["return"];
-  while (inst && 5 !== inst.tag);
-  return inst ? inst : null;
-}
-function traverseTwoPhase(inst, fn, arg) {
-  for (var path = []; inst; ) path.push(inst), (inst = getParent(inst));
-  for (inst = path.length; 0 < inst--; ) fn(path[inst], "captured", arg);
-  for (inst = 0; inst < path.length; inst++) fn(path[inst], "bubbled", arg);
-}
-function accumulateDirectionalDispatches(inst, phase, event) {
-  if (
-    (phase = getListener(
-      inst,
-      event.dispatchConfig.phasedRegistrationNames[phase]
-    ))
-  )
-    (event._dispatchListeners = accumulateInto(
-      event._dispatchListeners,
-      phase
-    )),
-      (event._dispatchInstances = accumulateInto(
-        event._dispatchInstances,
-        inst
-      ));
-}
-function accumulateTwoPhaseDispatchesSingle(event) {
-  event &&
-    event.dispatchConfig.phasedRegistrationNames &&
-    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
-}
-function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
-  if (event && event.dispatchConfig.phasedRegistrationNames) {
-    var targetInst = event._targetInst;
-    targetInst = targetInst ? getParent(targetInst) : null;
-    traverseTwoPhase(targetInst, accumulateDirectionalDispatches, event);
-  }
-}
-function accumulateDirectDispatchesSingle(event) {
-  if (event && event.dispatchConfig.registrationName) {
-    var inst = event._targetInst;
-    if (inst && event && event.dispatchConfig.registrationName) {
-      var listener = getListener(inst, event.dispatchConfig.registrationName);
-      listener &&
-        ((event._dispatchListeners = accumulateInto(
-          event._dispatchListeners,
-          listener
-        )),
-        (event._dispatchInstances = accumulateInto(
-          event._dispatchInstances,
-          inst
-        )));
-    }
-  }
-}
-var shouldBeReleasedProperties = "dispatchConfig _targetInst nativeEvent isDefaultPrevented isPropagationStopped _dispatchListeners _dispatchInstances".split(
-    " "
-  ),
-  EventInterface = {
-    type: null,
-    target: null,
-    currentTarget: emptyFunction.thatReturnsNull,
-    eventPhase: null,
-    bubbles: null,
-    cancelable: null,
-    timeStamp: function(event) {
-      return event.timeStamp || Date.now();
-    },
-    defaultPrevented: null,
-    isTrusted: null
-  };
-function SyntheticEvent(
-  dispatchConfig,
-  targetInst,
-  nativeEvent,
-  nativeEventTarget
-) {
-  this.dispatchConfig = dispatchConfig;
-  this._targetInst = targetInst;
-  this.nativeEvent = nativeEvent;
-  dispatchConfig = this.constructor.Interface;
-  for (var propName in dispatchConfig)
-    dispatchConfig.hasOwnProperty(propName) &&
-      ((targetInst = dispatchConfig[propName])
-        ? (this[propName] = targetInst(nativeEvent))
-        : "target" === propName
-          ? (this.target = nativeEventTarget)
-          : (this[propName] = nativeEvent[propName]));
-  this.isDefaultPrevented = (null != nativeEvent.defaultPrevented
-  ? nativeEvent.defaultPrevented
-  : !1 === nativeEvent.returnValue)
-    ? emptyFunction.thatReturnsTrue
-    : emptyFunction.thatReturnsFalse;
-  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
-  return this;
-}
-Object.assign(SyntheticEvent.prototype, {
-  preventDefault: function() {
-    this.defaultPrevented = !0;
-    var event = this.nativeEvent;
-    event &&
-      (event.preventDefault
-        ? event.preventDefault()
-        : "unknown" !== typeof event.returnValue && (event.returnValue = !1),
-      (this.isDefaultPrevented = emptyFunction.thatReturnsTrue));
-  },
-  stopPropagation: function() {
-    var event = this.nativeEvent;
-    event &&
-      (event.stopPropagation
-        ? event.stopPropagation()
-        : "unknown" !== typeof event.cancelBubble && (event.cancelBubble = !0),
-      (this.isPropagationStopped = emptyFunction.thatReturnsTrue));
-  },
-  persist: function() {
-    this.isPersistent = emptyFunction.thatReturnsTrue;
-  },
-  isPersistent: emptyFunction.thatReturnsFalse,
-  destructor: function() {
-    var Interface = this.constructor.Interface,
-      propName;
-    for (propName in Interface) this[propName] = null;
-    for (
-      Interface = 0;
-      Interface < shouldBeReleasedProperties.length;
-      Interface++
-    )
-      this[shouldBeReleasedProperties[Interface]] = null;
-  }
-});
-SyntheticEvent.Interface = EventInterface;
-SyntheticEvent.extend = function(Interface) {
-  function E() {}
-  function Class() {
-    return Super.apply(this, arguments);
-  }
-  var Super = this;
-  E.prototype = Super.prototype;
-  var prototype = new E();
-  Object.assign(prototype, Class.prototype);
-  Class.prototype = prototype;
-  Class.prototype.constructor = Class;
-  Class.Interface = Object.assign({}, Super.Interface, Interface);
-  Class.extend = Super.extend;
-  addEventPoolingTo(Class);
-  return Class;
-};
-addEventPoolingTo(SyntheticEvent);
-function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
-  if (this.eventPool.length) {
-    var instance = this.eventPool.pop();
-    this.call(instance, dispatchConfig, targetInst, nativeEvent, nativeInst);
-    return instance;
-  }
-  return new this(dispatchConfig, targetInst, nativeEvent, nativeInst);
-}
-function releasePooledEvent(event) {
-  invariant(
-    event instanceof this,
-    "Trying to release an event instance  into a pool of a different type."
-  );
-  event.destructor();
-  10 > this.eventPool.length && this.eventPool.push(event);
-}
-function addEventPoolingTo(EventConstructor) {
-  EventConstructor.eventPool = [];
-  EventConstructor.getPooled = getPooledEvent;
-  EventConstructor.release = releasePooledEvent;
-}
-var ResponderSyntheticEvent = SyntheticEvent.extend({
-    touchHistory: function() {
-      return null;
-    }
-  }),
-  touchBank = [],
-  touchHistory = {
-    touchBank: touchBank,
-    numberActiveTouches: 0,
-    indexOfSingleActiveTouch: -1,
-    mostRecentTimeStamp: 0
-  };
-function timestampForTouch(touch) {
-  return touch.timeStamp || touch.timestamp;
-}
-function getTouchIdentifier(_ref) {
-  _ref = _ref.identifier;
-  invariant(null != _ref, "Touch object is missing identifier.");
-  return _ref;
-}
-function recordTouchStart(touch) {
-  var identifier = getTouchIdentifier(touch),
-    touchRecord = touchBank[identifier];
-  touchRecord
-    ? ((touchRecord.touchActive = !0),
-      (touchRecord.startPageX = touch.pageX),
-      (touchRecord.startPageY = touch.pageY),
-      (touchRecord.startTimeStamp = timestampForTouch(touch)),
-      (touchRecord.currentPageX = touch.pageX),
-      (touchRecord.currentPageY = touch.pageY),
-      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
-      (touchRecord.previousPageX = touch.pageX),
-      (touchRecord.previousPageY = touch.pageY),
-      (touchRecord.previousTimeStamp = timestampForTouch(touch)))
-    : ((touchRecord = {
-        touchActive: !0,
-        startPageX: touch.pageX,
-        startPageY: touch.pageY,
-        startTimeStamp: timestampForTouch(touch),
-        currentPageX: touch.pageX,
-        currentPageY: touch.pageY,
-        currentTimeStamp: timestampForTouch(touch),
-        previousPageX: touch.pageX,
-        previousPageY: touch.pageY,
-        previousTimeStamp: timestampForTouch(touch)
-      }),
-      (touchBank[identifier] = touchRecord));
-  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
-}
-function recordTouchMove(touch) {
-  var touchRecord = touchBank[getTouchIdentifier(touch)];
-  touchRecord
-    ? ((touchRecord.touchActive = !0),
-      (touchRecord.previousPageX = touchRecord.currentPageX),
-      (touchRecord.previousPageY = touchRecord.currentPageY),
-      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
-      (touchRecord.currentPageX = touch.pageX),
-      (touchRecord.currentPageY = touch.pageY),
-      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
-      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
-    : console.error(
-        "Cannot record touch move without a touch start.\nTouch Move: %s\n",
-        "Touch Bank: %s",
-        printTouch(touch),
-        printTouchBank()
-      );
-}
-function recordTouchEnd(touch) {
-  var touchRecord = touchBank[getTouchIdentifier(touch)];
-  touchRecord
-    ? ((touchRecord.touchActive = !1),
-      (touchRecord.previousPageX = touchRecord.currentPageX),
-      (touchRecord.previousPageY = touchRecord.currentPageY),
-      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
-      (touchRecord.currentPageX = touch.pageX),
-      (touchRecord.currentPageY = touch.pageY),
-      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
-      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
-    : console.error(
-        "Cannot record touch end without a touch start.\nTouch End: %s\n",
-        "Touch Bank: %s",
-        printTouch(touch),
-        printTouchBank()
-      );
-}
-function printTouch(touch) {
-  return JSON.stringify({
-    identifier: touch.identifier,
-    pageX: touch.pageX,
-    pageY: touch.pageY,
-    timestamp: timestampForTouch(touch)
-  });
-}
-function printTouchBank() {
-  var printed = JSON.stringify(touchBank.slice(0, 20));
-  20 < touchBank.length &&
-    (printed += " (original size: " + touchBank.length + ")");
-  return printed;
-}
-var ResponderTouchHistoryStore = {
-  recordTouchTrack: function(topLevelType, nativeEvent) {
-    if (isMoveish(topLevelType))
-      nativeEvent.changedTouches.forEach(recordTouchMove);
-    else if (isStartish(topLevelType))
-      nativeEvent.changedTouches.forEach(recordTouchStart),
-        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
-        1 === touchHistory.numberActiveTouches &&
-          (touchHistory.indexOfSingleActiveTouch =
-            nativeEvent.touches[0].identifier);
-    else if (
-      isEndish(topLevelType) &&
-      (nativeEvent.changedTouches.forEach(recordTouchEnd),
-      (touchHistory.numberActiveTouches = nativeEvent.touches.length),
-      1 === touchHistory.numberActiveTouches)
-    )
-      for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
-        if (
-          ((nativeEvent = touchBank[topLevelType]),
-          null != nativeEvent && nativeEvent.touchActive)
-        ) {
-          touchHistory.indexOfSingleActiveTouch = topLevelType;
-          break;
-        }
-  },
-  touchHistory: touchHistory
-};
-function accumulate(current, next) {
-  invariant(
-    null != next,
-    "accumulate(...): Accumulated items must be not be null or undefined."
-  );
-  return null == current
-    ? next
-    : Array.isArray(current)
-      ? current.concat(next)
-      : Array.isArray(next) ? [current].concat(next) : [current, next];
-}
-var responderInst = null,
-  trackedTouchCount = 0,
-  previousActiveTouches = 0;
-function changeResponder(nextResponderInst, blockHostResponder) {
-  var oldResponderInst = responderInst;
-  responderInst = nextResponderInst;
-  if (null !== ResponderEventPlugin.GlobalResponderHandler)
-    ResponderEventPlugin.GlobalResponderHandler.onChange(
-      oldResponderInst,
-      nextResponderInst,
-      blockHostResponder
-    );
-}
-var eventTypes$1 = {
-    startShouldSetResponder: {
-      phasedRegistrationNames: {
-        bubbled: "onStartShouldSetResponder",
-        captured: "onStartShouldSetResponderCapture"
-      }
-    },
-    scrollShouldSetResponder: {
-      phasedRegistrationNames: {
-        bubbled: "onScrollShouldSetResponder",
-        captured: "onScrollShouldSetResponderCapture"
-      }
-    },
-    selectionChangeShouldSetResponder: {
-      phasedRegistrationNames: {
-        bubbled: "onSelectionChangeShouldSetResponder",
-        captured: "onSelectionChangeShouldSetResponderCapture"
-      }
-    },
-    moveShouldSetResponder: {
-      phasedRegistrationNames: {
-        bubbled: "onMoveShouldSetResponder",
-        captured: "onMoveShouldSetResponderCapture"
-      }
-    },
-    responderStart: { registrationName: "onResponderStart" },
-    responderMove: { registrationName: "onResponderMove" },
-    responderEnd: { registrationName: "onResponderEnd" },
-    responderRelease: { registrationName: "onResponderRelease" },
-    responderTerminationRequest: {
-      registrationName: "onResponderTerminationRequest"
-    },
-    responderGrant: { registrationName: "onResponderGrant" },
-    responderReject: { registrationName: "onResponderReject" },
-    responderTerminate: { registrationName: "onResponderTerminate" }
-  },
-  ResponderEventPlugin = {
-    _getResponder: function() {
-      return responderInst;
-    },
-    eventTypes: eventTypes$1,
-    extractEvents: function(
-      topLevelType,
-      targetInst,
-      nativeEvent,
-      nativeEventTarget
-    ) {
-      if (isStartish(topLevelType)) trackedTouchCount += 1;
-      else if (isEndish(topLevelType))
-        if (0 <= trackedTouchCount) --trackedTouchCount;
-        else
-          return (
-            console.error(
-              "Ended a touch event which was not counted in `trackedTouchCount`."
-            ),
-            null
-          );
-      ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
-      if (
-        targetInst &&
-        (("topScroll" === topLevelType && !nativeEvent.responderIgnoreScroll) ||
-          (0 < trackedTouchCount && "topSelectionChange" === topLevelType) ||
-          isStartish(topLevelType) ||
-          isMoveish(topLevelType))
-      ) {
-        var JSCompiler_temp = isStartish(topLevelType)
-          ? eventTypes$1.startShouldSetResponder
-          : isMoveish(topLevelType)
-            ? eventTypes$1.moveShouldSetResponder
-            : "topSelectionChange" === topLevelType
-              ? eventTypes$1.selectionChangeShouldSetResponder
-              : eventTypes$1.scrollShouldSetResponder;
-        if (responderInst)
-          b: {
-            var JSCompiler_temp$jscomp$0 = responderInst;
-            for (
-              var depthA = 0, tempA = JSCompiler_temp$jscomp$0;
-              tempA;
-              tempA = getParent(tempA)
-            )
-              depthA++;
-            tempA = 0;
-            for (var tempB = targetInst; tempB; tempB = getParent(tempB))
-              tempA++;
-            for (; 0 < depthA - tempA; )
-              (JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0)),
-                depthA--;
-            for (; 0 < tempA - depthA; )
-              (targetInst = getParent(targetInst)), tempA--;
-            for (; depthA--; ) {
-              if (
-                JSCompiler_temp$jscomp$0 === targetInst ||
-                JSCompiler_temp$jscomp$0 === targetInst.alternate
-              )
-                break b;
-              JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0);
-              targetInst = getParent(targetInst);
-            }
-            JSCompiler_temp$jscomp$0 = null;
-          }
-        else JSCompiler_temp$jscomp$0 = targetInst;
-        targetInst = JSCompiler_temp$jscomp$0 === responderInst;
-        JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
-          JSCompiler_temp,
-          JSCompiler_temp$jscomp$0,
-          nativeEvent,
-          nativeEventTarget
-        );
-        JSCompiler_temp$jscomp$0.touchHistory =
-          ResponderTouchHistoryStore.touchHistory;
-        targetInst
-          ? forEachAccumulated(
-              JSCompiler_temp$jscomp$0,
-              accumulateTwoPhaseDispatchesSingleSkipTarget
-            )
-          : forEachAccumulated(
-              JSCompiler_temp$jscomp$0,
-              accumulateTwoPhaseDispatchesSingle
-            );
-        b: {
-          JSCompiler_temp = JSCompiler_temp$jscomp$0._dispatchListeners;
-          targetInst = JSCompiler_temp$jscomp$0._dispatchInstances;
-          if (Array.isArray(JSCompiler_temp))
-            for (
-              depthA = 0;
-              depthA < JSCompiler_temp.length &&
-              !JSCompiler_temp$jscomp$0.isPropagationStopped();
-              depthA++
-            ) {
-              if (
-                JSCompiler_temp[depthA](
-                  JSCompiler_temp$jscomp$0,
-                  targetInst[depthA]
-                )
-              ) {
-                JSCompiler_temp = targetInst[depthA];
-                break b;
-              }
-            }
-          else if (
-            JSCompiler_temp &&
-            JSCompiler_temp(JSCompiler_temp$jscomp$0, targetInst)
-          ) {
-            JSCompiler_temp = targetInst;
-            break b;
-          }
-          JSCompiler_temp = null;
-        }
-        JSCompiler_temp$jscomp$0._dispatchInstances = null;
-        JSCompiler_temp$jscomp$0._dispatchListeners = null;
-        JSCompiler_temp$jscomp$0.isPersistent() ||
-          JSCompiler_temp$jscomp$0.constructor.release(
-            JSCompiler_temp$jscomp$0
-          );
-        JSCompiler_temp && JSCompiler_temp !== responderInst
-          ? ((JSCompiler_temp$jscomp$0 = void 0),
-            (targetInst = ResponderSyntheticEvent.getPooled(
-              eventTypes$1.responderGrant,
-              JSCompiler_temp,
-              nativeEvent,
-              nativeEventTarget
-            )),
-            (targetInst.touchHistory = ResponderTouchHistoryStore.touchHistory),
-            forEachAccumulated(targetInst, accumulateDirectDispatchesSingle),
-            (depthA = !0 === executeDirectDispatch(targetInst)),
-            responderInst
-              ? ((tempA = ResponderSyntheticEvent.getPooled(
-                  eventTypes$1.responderTerminationRequest,
-                  responderInst,
-                  nativeEvent,
-                  nativeEventTarget
-                )),
-                (tempA.touchHistory = ResponderTouchHistoryStore.touchHistory),
-                forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
-                (tempB =
-                  !tempA._dispatchListeners || executeDirectDispatch(tempA)),
-                tempA.isPersistent() || tempA.constructor.release(tempA),
-                tempB
-                  ? ((tempA = ResponderSyntheticEvent.getPooled(
-                      eventTypes$1.responderTerminate,
-                      responderInst,
-                      nativeEvent,
-                      nativeEventTarget
-                    )),
-                    (tempA.touchHistory =
-                      ResponderTouchHistoryStore.touchHistory),
-                    forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
-                    (JSCompiler_temp$jscomp$0 = accumulate(
-                      JSCompiler_temp$jscomp$0,
-                      [targetInst, tempA]
-                    )),
-                    changeResponder(JSCompiler_temp, depthA))
-                  : ((JSCompiler_temp = ResponderSyntheticEvent.getPooled(
-                      eventTypes$1.responderReject,
-                      JSCompiler_temp,
-                      nativeEvent,
-                      nativeEventTarget
-                    )),
-                    (JSCompiler_temp.touchHistory =
-                      ResponderTouchHistoryStore.touchHistory),
-                    forEachAccumulated(
-                      JSCompiler_temp,
-                      accumulateDirectDispatchesSingle
-                    ),
-                    (JSCompiler_temp$jscomp$0 = accumulate(
-                      JSCompiler_temp$jscomp$0,
-                      JSCompiler_temp
-                    ))))
-              : ((JSCompiler_temp$jscomp$0 = accumulate(
-                  JSCompiler_temp$jscomp$0,
-                  targetInst
-                )),
-                changeResponder(JSCompiler_temp, depthA)),
-            (JSCompiler_temp = JSCompiler_temp$jscomp$0))
-          : (JSCompiler_temp = null);
-      } else JSCompiler_temp = null;
-      JSCompiler_temp$jscomp$0 = responderInst && isStartish(topLevelType);
-      targetInst = responderInst && isMoveish(topLevelType);
-      depthA = responderInst && isEndish(topLevelType);
-      if (
-        (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
-          ? eventTypes$1.responderStart
-          : targetInst
-            ? eventTypes$1.responderMove
-            : depthA ? eventTypes$1.responderEnd : null)
-      )
-        (JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
-          JSCompiler_temp$jscomp$0,
-          responderInst,
-          nativeEvent,
-          nativeEventTarget
-        )),
-          (JSCompiler_temp$jscomp$0.touchHistory =
-            ResponderTouchHistoryStore.touchHistory),
-          forEachAccumulated(
-            JSCompiler_temp$jscomp$0,
-            accumulateDirectDispatchesSingle
-          ),
-          (JSCompiler_temp = accumulate(
-            JSCompiler_temp,
-            JSCompiler_temp$jscomp$0
-          ));
-      JSCompiler_temp$jscomp$0 =
-        responderInst && "topTouchCancel" === topLevelType;
-      if (
-        (topLevelType =
-          responderInst && !JSCompiler_temp$jscomp$0 && isEndish(topLevelType))
-      )
-        a: {
-          if ((topLevelType = nativeEvent.touches) && 0 !== topLevelType.length)
-            for (targetInst = 0; targetInst < topLevelType.length; targetInst++)
-              if (
-                ((depthA = topLevelType[targetInst].target),
-                null !== depthA && void 0 !== depthA && 0 !== depthA)
-              ) {
-                tempA = getInstanceFromNode(depthA);
-                b: {
-                  for (depthA = responderInst; tempA; ) {
-                    if (depthA === tempA || depthA === tempA.alternate) {
-                      depthA = !0;
-                      break b;
-                    }
-                    tempA = getParent(tempA);
-                  }
-                  depthA = !1;
-                }
-                if (depthA) {
-                  topLevelType = !1;
-                  break a;
-                }
-              }
-          topLevelType = !0;
-        }
-      if (
-        (topLevelType = JSCompiler_temp$jscomp$0
-          ? eventTypes$1.responderTerminate
-          : topLevelType ? eventTypes$1.responderRelease : null)
-      )
-        (nativeEvent = ResponderSyntheticEvent.getPooled(
-          topLevelType,
-          responderInst,
-          nativeEvent,
-          nativeEventTarget
-        )),
-          (nativeEvent.touchHistory = ResponderTouchHistoryStore.touchHistory),
-          forEachAccumulated(nativeEvent, accumulateDirectDispatchesSingle),
-          (JSCompiler_temp = accumulate(JSCompiler_temp, nativeEvent)),
-          changeResponder(null);
-      nativeEvent = ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
-      if (
-        ResponderEventPlugin.GlobalInteractionHandler &&
-        nativeEvent !== previousActiveTouches
-      )
-        ResponderEventPlugin.GlobalInteractionHandler.onChange(nativeEvent);
-      previousActiveTouches = nativeEvent;
-      return JSCompiler_temp;
-    },
-    GlobalResponderHandler: null,
-    GlobalInteractionHandler: null,
-    injection: {
-      injectGlobalResponderHandler: function(GlobalResponderHandler) {
-        ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
-      },
-      injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
-        ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
-      }
-    }
-  },
-  customBubblingEventTypes$1 =
-    ReactNativeViewConfigRegistry.customBubblingEventTypes,
-  customDirectEventTypes$1 =
-    ReactNativeViewConfigRegistry.customDirectEventTypes,
-  ReactNativeBridgeEventPlugin = {
-    eventTypes: ReactNativeViewConfigRegistry.eventTypes,
-    extractEvents: function(
-      topLevelType,
-      targetInst,
-      nativeEvent,
-      nativeEventTarget
-    ) {
-      if (null == targetInst) return null;
-      var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType],
-        directDispatchConfig = customDirectEventTypes$1[topLevelType];
-      invariant(
-        bubbleDispatchConfig || directDispatchConfig,
-        'Unsupported top level event type "%s" dispatched',
-        topLevelType
-      );
-      topLevelType = SyntheticEvent.getPooled(
-        bubbleDispatchConfig || directDispatchConfig,
-        targetInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      if (bubbleDispatchConfig)
-        forEachAccumulated(topLevelType, accumulateTwoPhaseDispatchesSingle);
-      else if (directDispatchConfig)
-        forEachAccumulated(topLevelType, accumulateDirectDispatchesSingle);
-      else return null;
-      return topLevelType;
-    }
-  },
-  instanceCache = {},
-  instanceProps = {};
-function getInstanceFromTag(tag) {
-  return "number" === typeof tag ? instanceCache[tag] || null : tag;
-}
-var ReactNativeComponentTree = Object.freeze({
-  precacheFiberNode: function(hostInst, tag) {
-    instanceCache[tag] = hostInst;
-  },
-  uncacheFiberNode: function(tag) {
-    delete instanceCache[tag];
-    delete instanceProps[tag];
-  },
-  getClosestInstanceFromNode: getInstanceFromTag,
-  getInstanceFromNode: getInstanceFromTag,
-  getNodeFromInstance: function(inst) {
-    var tag = inst.stateNode._nativeTag;
-    void 0 === tag && (tag = inst.stateNode.canonical._nativeTag);
-    invariant(tag, "All native instances should have a tag.");
-    return tag;
-  },
-  getFiberCurrentPropsFromNode: function(stateNode) {
-    return instanceProps[stateNode._nativeTag] || null;
-  },
-  updateFiberProps: function(tag, props) {
-    instanceProps[tag] = props;
-  }
-});
-injection.injectEventPluginOrder([
-  "ResponderEventPlugin",
-  "ReactNativeBridgeEventPlugin"
-]);
-getFiberCurrentPropsFromNode =
-  ReactNativeComponentTree.getFiberCurrentPropsFromNode;
-getInstanceFromNode = ReactNativeComponentTree.getInstanceFromNode;
-getNodeFromInstance = ReactNativeComponentTree.getNodeFromInstance;
-ResponderEventPlugin.injection.injectGlobalResponderHandler({
-  onChange: function(from, to, blockNativeResponder) {
-    null !== to
-      ? UIManager.setJSResponder(to.stateNode._nativeTag, blockNativeResponder)
-      : UIManager.clearJSResponder();
-  }
-});
-injection.injectEventPluginsByName({
-  ResponderEventPlugin: ResponderEventPlugin,
-  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
-});
-var hasSymbol = "function" === typeof Symbol && Symbol["for"],
-  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
-  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
-  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
-  REACT_STRICT_MODE_TYPE = hasSymbol
-    ? Symbol["for"]("react.strict_mode")
-    : 60108,
-  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
-  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
-  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
-  REACT_FORWARD_REF_TYPE = hasSymbol
-    ? Symbol["for"]("react.forward_ref")
-    : 60112,
-  MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
-function getIteratorFn(maybeIterable) {
-  if (null === maybeIterable || "undefined" === typeof maybeIterable)
-    return null;
-  maybeIterable =
-    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
-    maybeIterable["@@iterator"];
-  return "function" === typeof maybeIterable ? maybeIterable : null;
-}
-function createPortal(children, containerInfo, implementation) {
-  var key =
-    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
-  return {
-    $$typeof: REACT_PORTAL_TYPE,
-    key: null == key ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
-}
-var emptyObject$1 = {},
-  removedKeys = null,
-  removedKeyCount = 0;
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node))
-    for (var i = node.length; i-- && 0 < removedKeyCount; )
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
-  else if (node && 0 < removedKeyCount)
-    for (i in removedKeys)
-      if (removedKeys[i]) {
-        var _nextProp = node[i];
-        if (void 0 !== _nextProp) {
-          var attributeConfig = validAttributes[i];
-          if (attributeConfig) {
-            "function" === typeof _nextProp && (_nextProp = !0);
-            "undefined" === typeof _nextProp && (_nextProp = null);
-            if ("object" !== typeof attributeConfig)
-              updatePayload[i] = _nextProp;
-            else if (
-              "function" === typeof attributeConfig.diff ||
-              "function" === typeof attributeConfig.process
-            )
-              (_nextProp =
-                "function" === typeof attributeConfig.process
-                  ? attributeConfig.process(_nextProp)
-                  : _nextProp),
-                (updatePayload[i] = _nextProp);
-            removedKeys[i] = !1;
-            removedKeyCount--;
-          }
-        }
-      }
-}
-function diffNestedProperty(
-  updatePayload,
-  prevProp,
-  nextProp,
-  validAttributes
-) {
-  if (!updatePayload && prevProp === nextProp) return updatePayload;
-  if (!prevProp || !nextProp)
-    return nextProp
-      ? addNestedProperty(updatePayload, nextProp, validAttributes)
-      : prevProp
-        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
-        : updatePayload;
-  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
-    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
-  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
-    var minLength =
-        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
-      i;
-    for (i = 0; i < minLength; i++)
-      updatePayload = diffNestedProperty(
-        updatePayload,
-        prevProp[i],
-        nextProp[i],
-        validAttributes
-      );
-    for (; i < prevProp.length; i++)
-      updatePayload = clearNestedProperty(
-        updatePayload,
-        prevProp[i],
-        validAttributes
-      );
-    for (; i < nextProp.length; i++)
-      updatePayload = addNestedProperty(
-        updatePayload,
-        nextProp[i],
-        validAttributes
-      );
-    return updatePayload;
-  }
-  return Array.isArray(prevProp)
-    ? diffProperties(
-        updatePayload,
-        flattenStyle(prevProp),
-        nextProp,
-        validAttributes
-      )
-    : diffProperties(
-        updatePayload,
-        prevProp,
-        flattenStyle(nextProp),
-        validAttributes
-      );
-}
-function addNestedProperty(updatePayload, nextProp, validAttributes) {
-  if (!nextProp) return updatePayload;
-  if (!Array.isArray(nextProp))
-    return diffProperties(
-      updatePayload,
-      emptyObject$1,
-      nextProp,
-      validAttributes
-    );
-  for (var i = 0; i < nextProp.length; i++)
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextProp[i],
-      validAttributes
-    );
-  return updatePayload;
-}
-function clearNestedProperty(updatePayload, prevProp, validAttributes) {
-  if (!prevProp) return updatePayload;
-  if (!Array.isArray(prevProp))
-    return diffProperties(
-      updatePayload,
-      prevProp,
-      emptyObject$1,
-      validAttributes
-    );
-  for (var i = 0; i < prevProp.length; i++)
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevProp[i],
-      validAttributes
-    );
-  return updatePayload;
-}
-function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
-  var attributeConfig, propKey;
-  for (propKey in nextProps)
-    if ((attributeConfig = validAttributes[propKey])) {
-      var prevProp = prevProps[propKey];
-      var nextProp = nextProps[propKey];
-      "function" === typeof nextProp &&
-        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
-      "undefined" === typeof nextProp &&
-        ((nextProp = null),
-        "undefined" === typeof prevProp && (prevProp = null));
-      removedKeys && (removedKeys[propKey] = !1);
-      if (updatePayload && void 0 !== updatePayload[propKey])
-        if ("object" !== typeof attributeConfig)
-          updatePayload[propKey] = nextProp;
-        else {
-          if (
-            "function" === typeof attributeConfig.diff ||
-            "function" === typeof attributeConfig.process
-          )
-            (attributeConfig =
-              "function" === typeof attributeConfig.process
-                ? attributeConfig.process(nextProp)
-                : nextProp),
-              (updatePayload[propKey] = attributeConfig);
-        }
-      else if (prevProp !== nextProp)
-        if ("object" !== typeof attributeConfig)
-          ("object" !== typeof nextProp ||
-            null === nextProp ||
-            deepDiffer(prevProp, nextProp)) &&
-            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
-        else if (
-          "function" === typeof attributeConfig.diff ||
-          "function" === typeof attributeConfig.process
-        ) {
-          if (
-            void 0 === prevProp ||
-            ("function" === typeof attributeConfig.diff
-              ? attributeConfig.diff(prevProp, nextProp)
-              : "object" !== typeof nextProp ||
-                null === nextProp ||
-                deepDiffer(prevProp, nextProp))
-          )
-            (attributeConfig =
-              "function" === typeof attributeConfig.process
-                ? attributeConfig.process(nextProp)
-                : nextProp),
-              ((updatePayload || (updatePayload = {}))[
-                propKey
-              ] = attributeConfig);
-        } else
-          (removedKeys = null),
-            (removedKeyCount = 0),
-            (updatePayload = diffNestedProperty(
-              updatePayload,
-              prevProp,
-              nextProp,
-              attributeConfig
-            )),
-            0 < removedKeyCount &&
-              updatePayload &&
-              (restoreDeletedValuesInNestedArray(
-                updatePayload,
-                nextProp,
-                attributeConfig
-              ),
-              (removedKeys = null));
-    }
-  for (var _propKey in prevProps)
-    void 0 === nextProps[_propKey] &&
-      (!(attributeConfig = validAttributes[_propKey]) ||
-        (updatePayload && void 0 !== updatePayload[_propKey]) ||
-        ((prevProp = prevProps[_propKey]),
-        void 0 !== prevProp &&
-          ("object" !== typeof attributeConfig ||
-          "function" === typeof attributeConfig.diff ||
-          "function" === typeof attributeConfig.process
-            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
-              removedKeys || (removedKeys = {}),
-              removedKeys[_propKey] ||
-                ((removedKeys[_propKey] = !0), removedKeyCount++))
-            : (updatePayload = clearNestedProperty(
-                updatePayload,
-                prevProp,
-                attributeConfig
-              )))));
-  return updatePayload;
-}
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (callback) {
-      if ("boolean" === typeof context.__isMounted) {
-        if (!context.__isMounted) return;
-      } else if (
-        "function" === typeof context.isMounted &&
-        !context.isMounted()
-      )
-        return;
-      return callback.apply(context, arguments);
-    }
-  };
-}
-function _inherits(subClass, superClass) {
-  if ("function" !== typeof superClass && null !== superClass)
-    throw new TypeError(
-      "Super expression must either be null or a function, not " +
-        typeof superClass
-    );
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: !1,
-      writable: !0,
-      configurable: !0
-    }
-  });
-  superClass &&
-    (Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass));
-}
-var now =
-    "object" === typeof performance && "function" === typeof performance.now
-      ? function() {
-          return performance.now();
-        }
-      : function() {
-          return Date.now();
-        },
-  scheduledCallback = null,
-  frameDeadline = 0,
-  frameDeadlineObject = {
-    timeRemaining: function() {
-      return frameDeadline - now();
-    },
-    didTimeout: !1
-  };
-function setTimeoutCallback() {
-  frameDeadline = now() + 5;
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  null !== callback && callback(frameDeadlineObject);
-}
-var ReactCurrentOwner =
-  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
-function getComponentName(fiber) {
-  fiber = fiber.type;
-  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
-  if ("string" === typeof fiber) return fiber;
-  switch (fiber) {
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
-  }
-  if ("object" === typeof fiber && null !== fiber)
-    switch (fiber.$$typeof) {
-      case REACT_FORWARD_REF_TYPE:
-        return (
-          (fiber = fiber.render.displayName || fiber.render.name || ""),
-          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
-        );
-    }
-  return null;
-}
-function isFiberMountedImpl(fiber) {
-  var node = fiber;
-  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
-  else {
-    if (0 !== (node.effectTag & 2)) return 1;
-    for (; node["return"]; )
-      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
-  }
-  return 3 === node.tag ? 2 : 3;
-}
-function isMounted(component) {
-  return (component = component._reactInternalFiber)
-    ? 2 === isFiberMountedImpl(component)
-    : !1;
-}
-function assertIsMounted(fiber) {
-  invariant(
-    2 === isFiberMountedImpl(fiber),
-    "Unable to find node on an unmounted component."
-  );
-}
-function findCurrentFiberUsingSlowPath(fiber) {
-  var alternate = fiber.alternate;
-  if (!alternate)
-    return (
-      (alternate = isFiberMountedImpl(fiber)),
-      invariant(
-        3 !== alternate,
-        "Unable to find node on an unmounted component."
-      ),
-      1 === alternate ? null : fiber
-    );
-  for (var a = fiber, b = alternate; ; ) {
-    var parentA = a["return"],
-      parentB = parentA ? parentA.alternate : null;
-    if (!parentA || !parentB) break;
-    if (parentA.child === parentB.child) {
-      for (var child = parentA.child; child; ) {
-        if (child === a) return assertIsMounted(parentA), fiber;
-        if (child === b) return assertIsMounted(parentA), alternate;
-        child = child.sibling;
-      }
-      invariant(!1, "Unable to find node on an unmounted component.");
-    }
-    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
-    else {
-      child = !1;
-      for (var _child = parentA.child; _child; ) {
-        if (_child === a) {
-          child = !0;
-          a = parentA;
-          b = parentB;
-          break;
-        }
-        if (_child === b) {
-          child = !0;
-          b = parentA;
-          a = parentB;
-          break;
-        }
-        _child = _child.sibling;
-      }
-      if (!child) {
-        for (_child = parentB.child; _child; ) {
-          if (_child === a) {
-            child = !0;
-            a = parentB;
-            b = parentA;
-            break;
-          }
-          if (_child === b) {
-            child = !0;
-            b = parentB;
-            a = parentA;
-            break;
-          }
-          _child = _child.sibling;
-        }
-        invariant(
-          child,
-          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
-        );
-      }
-    }
-    invariant(
-      a.alternate === b,
-      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
-  return a.stateNode.current === a ? fiber : alternate;
-}
-function findCurrentHostFiber(parent) {
-  parent = findCurrentFiberUsingSlowPath(parent);
-  if (!parent) return null;
-  for (var node = parent; ; ) {
-    if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child["return"] = node), (node = node.child);
-    else {
-      if (node === parent) break;
-      for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-  return null;
-}
-function findCurrentHostFiberWithNoPortals(parent) {
-  parent = findCurrentFiberUsingSlowPath(parent);
-  if (!parent) return null;
-  for (var node = parent; ; ) {
-    if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child && 4 !== node.tag)
-      (node.child["return"] = node), (node = node.child);
-    else {
-      if (node === parent) break;
-      for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-  return null;
-}
-function FiberNode(tag, pendingProps, key, mode) {
-  this.tag = tag;
-  this.key = key;
-  this.stateNode = this.type = null;
-  this.sibling = this.child = this["return"] = null;
-  this.index = 0;
-  this.ref = null;
-  this.pendingProps = pendingProps;
-  this.memoizedState = this.updateQueue = this.memoizedProps = null;
-  this.mode = mode;
-  this.effectTag = 0;
-  this.lastEffect = this.firstEffect = this.nextEffect = null;
-  this.expirationTime = 0;
-  this.alternate = null;
-}
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  null === workInProgress
-    ? ((workInProgress = new FiberNode(
-        current.tag,
-        pendingProps,
-        current.key,
-        current.mode
-      )),
-      (workInProgress.type = current.type),
-      (workInProgress.stateNode = current.stateNode),
-      (workInProgress.alternate = current),
-      (current.alternate = workInProgress))
-    : ((workInProgress.pendingProps = pendingProps),
-      (workInProgress.effectTag = 0),
-      (workInProgress.nextEffect = null),
-      (workInProgress.firstEffect = null),
-      (workInProgress.lastEffect = null));
-  workInProgress.expirationTime = expirationTime;
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
-  return workInProgress;
-}
-function createFiberFromElement(element, mode, expirationTime) {
-  var type = element.type,
-    key = element.key;
-  element = element.props;
-  var fiberTag = void 0;
-  if ("function" === typeof type)
-    fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
-  else if ("string" === typeof type) fiberTag = 5;
-  else
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          element.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = 11;
-        mode |= 3;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = 11;
-        mode |= 2;
-        break;
-      case REACT_CALL_TYPE:
-        fiberTag = 7;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = 9;
-        break;
-      default:
-        if ("object" === typeof type && null !== type)
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = 13;
-              break;
-            case REACT_CONTEXT_TYPE:
-              fiberTag = 12;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = 14;
-              break;
-            default:
-              if ("number" === typeof type.tag)
-                return (
-                  (mode = type),
-                  (mode.pendingProps = element),
-                  (mode.expirationTime = expirationTime),
-                  mode
-                );
-              throwOnInvalidElementType(type, null);
-          }
-        else throwOnInvalidElementType(type, null);
-    }
-  mode = new FiberNode(fiberTag, element, key, mode);
-  mode.type = type;
-  mode.expirationTime = expirationTime;
-  return mode;
-}
-function throwOnInvalidElementType(type) {
-  invariant(
-    !1,
-    "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
-    null == type ? type : typeof type,
-    ""
-  );
-}
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  elements = new FiberNode(10, elements, key, mode);
-  elements.expirationTime = expirationTime;
-  return elements;
-}
-function createFiberFromText(content, mode, expirationTime) {
-  content = new FiberNode(6, content, null, mode);
-  content.expirationTime = expirationTime;
-  return content;
-}
-function createFiberFromPortal(portal, mode, expirationTime) {
-  mode = new FiberNode(
-    4,
-    null !== portal.children ? portal.children : [],
-    portal.key,
-    mode
-  );
-  mode.expirationTime = expirationTime;
-  mode.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null,
-    implementation: portal.implementation
-  };
-  return mode;
-}
-var onCommitFiberRoot = null,
-  onCommitFiberUnmount = null;
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {}
-  };
-}
-function injectInternals(internals) {
-  if ("undefined" === typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) return !1;
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled || !hook.supportsFiber) return !0;
-  try {
-    var rendererID = hook.inject(internals);
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {}
-  return !0;
-}
-function onCommitRoot(root) {
-  "function" === typeof onCommitFiberRoot && onCommitFiberRoot(root);
-}
-function onCommitUnmount(fiber) {
-  "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
-}
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  do {
-    a: switch (workInProgress.tag) {
-      case 0:
-      case 1:
-      case 2:
-      case 5:
-        var owner = workInProgress._debugOwner,
-          source = workInProgress._debugSource;
-        var JSCompiler_inline_result = getComponentName(workInProgress);
-        var ownerName = null;
-        owner && (ownerName = getComponentName(owner));
-        owner = source;
-        JSCompiler_inline_result =
-          "\n    in " +
-          (JSCompiler_inline_result || "Unknown") +
-          (owner
-            ? " (at " +
-              owner.fileName.replace(/^.*[\\\/]/, "") +
-              ":" +
-              owner.lineNumber +
-              ")"
-            : ownerName ? " (created by " + ownerName + ")" : "");
-        break a;
-      default:
-        JSCompiler_inline_result = "";
-    }
-    info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
-  } while (workInProgress);
-  return info;
-}
-new Set();
-function createUpdateQueue(baseState) {
-  return {
-    baseState: baseState,
-    expirationTime: 0,
-    first: null,
-    last: null,
-    callbackList: null,
-    hasForceUpdate: !1,
-    isInitialized: !1,
-    capturedValues: null
-  };
-}
-function insertUpdateIntoQueue(queue, update) {
-  null === queue.last
-    ? (queue.first = queue.last = update)
-    : ((queue.last.next = update), (queue.last = update));
-  if (
-    0 === queue.expirationTime ||
-    queue.expirationTime > update.expirationTime
-  )
-    queue.expirationTime = update.expirationTime;
-}
-var q1 = void 0,
-  q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  var alternateFiber = fiber.alternate,
-    queue1 = fiber.updateQueue;
-  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
-  null !== alternateFiber
-    ? ((fiber = alternateFiber.updateQueue),
-      null === fiber &&
-        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
-    : (fiber = null);
-  q1 = queue1;
-  q2 = fiber !== queue1 ? fiber : null;
-}
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  fiber = q1;
-  var queue2 = q2;
-  null === queue2
-    ? insertUpdateIntoQueue(fiber, update)
-    : null === fiber.last || null === queue2.last
-      ? (insertUpdateIntoQueue(fiber, update),
-        insertUpdateIntoQueue(queue2, update))
-      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
-}
-function getStateFromUpdate(update, instance, prevState, props) {
-  update = update.partialState;
-  return "function" === typeof update
-    ? update.call(instance, prevState, props)
-    : update;
-}
-function processUpdateQueue(
-  current,
-  workInProgress,
-  queue,
-  instance,
-  props,
-  renderExpirationTime
-) {
-  null !== current &&
-    current.updateQueue === queue &&
-    (queue = workInProgress.updateQueue = {
-      baseState: queue.baseState,
-      expirationTime: queue.expirationTime,
-      first: queue.first,
-      last: queue.last,
-      isInitialized: queue.isInitialized,
-      capturedValues: queue.capturedValues,
-      callbackList: null,
-      hasForceUpdate: !1
-    });
-  queue.expirationTime = 0;
-  queue.isInitialized
-    ? (current = queue.baseState)
-    : ((current = queue.baseState = workInProgress.memoizedState),
-      (queue.isInitialized = !0));
-  for (
-    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
-    null !== update;
-
-  ) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        remainingExpirationTime > updateExpirationTime
-      )
-        queue.expirationTime = updateExpirationTime;
-      didSkip || ((didSkip = !0), (queue.baseState = current));
-    } else {
-      didSkip ||
-        ((queue.first = update.next),
-        null === queue.first && (queue.last = null));
-      if (update.isReplace)
-        (current = getStateFromUpdate(update, instance, current, props)),
-          (dontMutatePrevState = !0);
-      else if (
-        (updateExpirationTime = getStateFromUpdate(
-          update,
-          instance,
-          current,
-          props
-        ))
-      )
-        (current = dontMutatePrevState
-          ? Object.assign({}, current, updateExpirationTime)
-          : Object.assign(current, updateExpirationTime)),
-          (dontMutatePrevState = !1);
-      update.isForced && (queue.hasForceUpdate = !0);
-      null !== update.callback &&
-        ((updateExpirationTime = queue.callbackList),
-        null === updateExpirationTime &&
-          (updateExpirationTime = queue.callbackList = []),
-        updateExpirationTime.push(update));
-      null !== update.capturedValue &&
-        ((updateExpirationTime = queue.capturedValues),
-        null === updateExpirationTime
-          ? (queue.capturedValues = [update.capturedValue])
-          : updateExpirationTime.push(update.capturedValue));
-    }
-    update = update.next;
-  }
-  null !== queue.callbackList
-    ? (workInProgress.effectTag |= 32)
-    : null !== queue.first ||
-      queue.hasForceUpdate ||
-      null !== queue.capturedValues ||
-      (workInProgress.updateQueue = null);
-  didSkip || (queue.baseState = current);
-  return current;
-}
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (null !== callbackList)
-    for (
-      queue.callbackList = null, queue = 0;
-      queue < callbackList.length;
-      queue++
-    ) {
-      var update = callbackList[queue],
-        _callback = update.callback;
-      update.callback = null;
-      invariant(
-        "function" === typeof _callback,
-        "Invalid argument passed as callback. Expected a function. Instead received: %s",
-        _callback
-      );
-      _callback.call(context);
-    }
-}
-function ReactFiberClassComponent(
-  legacyContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState
-) {
-  function checkShouldComponentUpdate(
-    workInProgress,
-    oldProps,
-    newProps,
-    oldState,
-    newState,
-    newContext
-  ) {
-    if (
-      null === oldProps ||
-      (null !== workInProgress.updateQueue &&
-        workInProgress.updateQueue.hasForceUpdate)
-    )
-      return !0;
-    var instance = workInProgress.stateNode;
-    workInProgress = workInProgress.type;
-    return "function" === typeof instance.shouldComponentUpdate
-      ? instance.shouldComponentUpdate(newProps, newState, newContext)
-      : workInProgress.prototype &&
-        workInProgress.prototype.isPureReactComponent
-        ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
-        : !0;
-  }
-  function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
-    workInProgress.stateNode = instance;
-    instance._reactInternalFiber = workInProgress;
-  }
-  function callComponentWillReceiveProps(
-    workInProgress,
-    instance,
-    newProps,
-    newContext
-  ) {
-    workInProgress = instance.state;
-    "function" === typeof instance.componentWillReceiveProps &&
-      instance.componentWillReceiveProps(newProps, newContext);
-    "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
-      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
-    instance.state !== workInProgress &&
-      updater.enqueueReplaceState(instance, instance.state, null);
-  }
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    workInProgress = workInProgress.type;
-    if ("function" === typeof workInProgress.getDerivedStateFromProps)
-      return workInProgress.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
-  }
-  var cacheContext = legacyContext.cacheContext,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    isContextConsumer = legacyContext.isContextConsumer,
-    hasContextChanged = legacyContext.hasContextChanged,
-    updater = {
-      isMounted: isMounted,
-      enqueueSetState: function(instance, partialState, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: partialState,
-          callback: callback,
-          isReplace: !1,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
-      },
-      enqueueReplaceState: function(instance, state, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: state,
-          callback: callback,
-          isReplace: !0,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
-      },
-      enqueueForceUpdate: function(instance, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: null,
-          callback: callback,
-          isReplace: !1,
-          isForced: !0,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
-      }
-    };
-  return {
-    adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
-    constructClassInstance: function(workInProgress, props) {
-      var ctor = workInProgress.type,
-        unmaskedContext = getUnmaskedContext(workInProgress),
-        needsContext = isContextConsumer(workInProgress),
-        context = needsContext
-          ? getMaskedContext(workInProgress, unmaskedContext)
-          : emptyObject;
-      ctor = new ctor(props, context);
-      var state =
-        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
-      adoptClassInstance(workInProgress, ctor);
-      workInProgress.memoizedState = state;
-      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
-      null !== props &&
-        void 0 !== props &&
-        (workInProgress.memoizedState = Object.assign(
-          {},
-          workInProgress.memoizedState,
-          props
-        ));
-      needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return ctor;
-    },
-    mountClassInstance: function(workInProgress, renderExpirationTime) {
-      var ctor = workInProgress.type,
-        current = workInProgress.alternate,
-        instance = workInProgress.stateNode,
-        props = workInProgress.pendingProps,
-        unmaskedContext = getUnmaskedContext(workInProgress);
-      instance.props = props;
-      instance.state = workInProgress.memoizedState;
-      instance.refs = emptyObject;
-      instance.context = getMaskedContext(workInProgress, unmaskedContext);
-      "function" === typeof ctor.getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate ||
-        ("function" !== typeof instance.UNSAFE_componentWillMount &&
-          "function" !== typeof instance.componentWillMount) ||
-        ((ctor = instance.state),
-        "function" === typeof instance.componentWillMount &&
-          instance.componentWillMount(),
-        "function" === typeof instance.UNSAFE_componentWillMount &&
-          instance.UNSAFE_componentWillMount(),
-        ctor !== instance.state &&
-          updater.enqueueReplaceState(instance, instance.state, null),
-        (ctor = workInProgress.updateQueue),
-        null !== ctor &&
-          (instance.state = processUpdateQueue(
-            current,
-            workInProgress,
-            ctor,
-            instance,
-            props,
-            renderExpirationTime
-          )));
-      "function" === typeof instance.componentDidMount &&
-        (workInProgress.effectTag |= 4);
-    },
-    resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
-        newUnmaskedContext = getUnmaskedContext(workInProgress);
-      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate) ||
-        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-          "function" !== typeof instance.componentWillReceiveProps) ||
-        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
-          callComponentWillReceiveProps(
-            workInProgress,
-            instance,
-            newProps,
-            newUnmaskedContext
-          ));
-      oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              null,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
-          workInProgress,
-          instance,
-          newProps,
-          renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue = workInProgress.updateQueue;
-        null !== _updateQueue &&
-          (_updateQueue.baseState = Object.assign(
-            {},
-            _updateQueue.baseState,
-            derivedStateFromProps
-          ));
-      }
-      if (
-        !(
-          oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
-          hasContextChanged() ||
-          (null !== workInProgress.updateQueue &&
-            workInProgress.updateQueue.hasForceUpdate)
-        )
-      )
-        return (
-          "function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4),
-          !1
-        );
-      (oldProps = checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldContext,
-        renderExpirationTime,
-        newUnmaskedContext
-      ))
-        ? (ctor ||
-            ("function" !== typeof instance.UNSAFE_componentWillMount &&
-              "function" !== typeof instance.componentWillMount) ||
-            ("function" === typeof instance.componentWillMount &&
-              instance.componentWillMount(),
-            "function" === typeof instance.UNSAFE_componentWillMount &&
-              instance.UNSAFE_componentWillMount()),
-          "function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4))
-        : ("function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
-      instance.props = newProps;
-      instance.state = renderExpirationTime;
-      instance.context = newUnmaskedContext;
-      return oldProps;
-    },
-    updateClassInstance: function(
-      current,
-      workInProgress,
-      renderExpirationTime
-    ) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
-        newUnmaskedContext = getUnmaskedContext(workInProgress);
-      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate) ||
-        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-          "function" !== typeof instance.componentWillReceiveProps) ||
-        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
-          callComponentWillReceiveProps(
-            workInProgress,
-            instance,
-            newProps,
-            newUnmaskedContext
-          ));
-      oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              current,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
-          workInProgress,
-          instance,
-          newProps,
-          renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue3 = workInProgress.updateQueue;
-        null !== _updateQueue3 &&
-          (_updateQueue3.baseState = Object.assign(
-            {},
-            _updateQueue3.baseState,
-            derivedStateFromProps
-          ));
-      }
-      if (
-        !(
-          oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
-          hasContextChanged() ||
-          (null !== workInProgress.updateQueue &&
-            workInProgress.updateQueue.hasForceUpdate)
-        )
-      )
-        return (
-          "function" !== typeof instance.componentDidUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 4),
-          "function" !== typeof instance.getSnapshotBeforeUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
-          !1
-        );
-      (derivedStateFromProps = checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldContext,
-        renderExpirationTime,
-        newUnmaskedContext
-      ))
-        ? (ctor ||
-            ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
-              "function" !== typeof instance.componentWillUpdate) ||
-            ("function" === typeof instance.componentWillUpdate &&
-              instance.componentWillUpdate(
-                newProps,
-                renderExpirationTime,
-                newUnmaskedContext
-              ),
-            "function" === typeof instance.UNSAFE_componentWillUpdate &&
-              instance.UNSAFE_componentWillUpdate(
-                newProps,
-                renderExpirationTime,
-                newUnmaskedContext
-              )),
-          "function" === typeof instance.componentDidUpdate &&
-            (workInProgress.effectTag |= 4),
-          "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 2048))
-        : ("function" !== typeof instance.componentDidUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 4),
-          "function" !== typeof instance.getSnapshotBeforeUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
-      instance.props = newProps;
-      instance.state = renderExpirationTime;
-      instance.context = newUnmaskedContext;
-      return derivedStateFromProps;
-    }
-  };
-}
-var isArray$1 = Array.isArray;
-function coerceRef(returnFiber, current, element) {
-  returnFiber = element.ref;
-  if (
-    null !== returnFiber &&
-    "function" !== typeof returnFiber &&
-    "object" !== typeof returnFiber
-  ) {
-    if (element._owner) {
-      element = element._owner;
-      var inst = void 0;
-      element &&
-        (invariant(
-          2 === element.tag,
-          "Stateless function components cannot have refs."
-        ),
-        (inst = element.stateNode));
-      invariant(
-        inst,
-        "Missing owner for string ref %s. This error is likely caused by a bug in React. Please file an issue.",
-        returnFiber
-      );
-      var stringRef = "" + returnFiber;
-      if (
-        null !== current &&
-        null !== current.ref &&
-        current.ref._stringRef === stringRef
-      )
-        return current.ref;
-      current = function(value) {
-        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
-        null === value ? delete refs[stringRef] : (refs[stringRef] = value);
-      };
-      current._stringRef = stringRef;
-      return current;
-    }
-    invariant(
-      "string" === typeof returnFiber,
-      "Expected ref to be a function or a string."
-    );
-    invariant(
-      element._owner,
-      "Element ref was specified as a string (%s) but no owner was set. This could happen for one of the following reasons:\n1. You may be adding a ref to a functional component\n2. You may be adding a ref to a component that was not created inside a component's render method\n3. You have multiple copies of React loaded\nSee https://fb.me/react-refs-must-have-owner for more information.",
-      returnFiber
-    );
-  }
-  return returnFiber;
-}
-function throwOnInvalidObjectType(returnFiber, newChild) {
-  "textarea" !== returnFiber.type &&
-    invariant(
-      !1,
-      "Objects are not valid as a React child (found: %s).%s",
-      "[object Object]" === Object.prototype.toString.call(newChild)
-        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
-        : newChild,
-      ""
-    );
-}
-function ChildReconciler(shouldTrackSideEffects) {
-  function deleteChild(returnFiber, childToDelete) {
-    if (shouldTrackSideEffects) {
-      var last = returnFiber.lastEffect;
-      null !== last
-        ? ((last.nextEffect = childToDelete),
-          (returnFiber.lastEffect = childToDelete))
-        : (returnFiber.firstEffect = returnFiber.lastEffect = childToDelete);
-      childToDelete.nextEffect = null;
-      childToDelete.effectTag = 8;
-    }
-  }
-  function deleteRemainingChildren(returnFiber, currentFirstChild) {
-    if (!shouldTrackSideEffects) return null;
-    for (; null !== currentFirstChild; )
-      deleteChild(returnFiber, currentFirstChild),
-        (currentFirstChild = currentFirstChild.sibling);
-    return null;
-  }
-  function mapRemainingChildren(returnFiber, currentFirstChild) {
-    for (returnFiber = new Map(); null !== currentFirstChild; )
-      null !== currentFirstChild.key
-        ? returnFiber.set(currentFirstChild.key, currentFirstChild)
-        : returnFiber.set(currentFirstChild.index, currentFirstChild),
-        (currentFirstChild = currentFirstChild.sibling);
-    return returnFiber;
-  }
-  function useFiber(fiber, pendingProps, expirationTime) {
-    fiber = createWorkInProgress(fiber, pendingProps, expirationTime);
-    fiber.index = 0;
-    fiber.sibling = null;
-    return fiber;
-  }
-  function placeChild(newFiber, lastPlacedIndex, newIndex) {
-    newFiber.index = newIndex;
-    if (!shouldTrackSideEffects) return lastPlacedIndex;
-    newIndex = newFiber.alternate;
-    if (null !== newIndex)
-      return (
-        (newIndex = newIndex.index),
-        newIndex < lastPlacedIndex
-          ? ((newFiber.effectTag = 2), lastPlacedIndex)
-          : newIndex
-      );
-    newFiber.effectTag = 2;
-    return lastPlacedIndex;
-  }
-  function placeSingleChild(newFiber) {
-    shouldTrackSideEffects &&
-      null === newFiber.alternate &&
-      (newFiber.effectTag = 2);
-    return newFiber;
-  }
-  function updateTextNode(returnFiber, current, textContent, expirationTime) {
-    if (null === current || 6 !== current.tag)
-      return (
-        (current = createFiberFromText(
-          textContent,
-          returnFiber.mode,
-          expirationTime
-        )),
-        (current["return"] = returnFiber),
-        current
-      );
-    current = useFiber(current, textContent, expirationTime);
-    current["return"] = returnFiber;
-    return current;
-  }
-  function updateElement(returnFiber, current, element, expirationTime) {
-    if (null !== current && current.type === element.type)
-      return (
-        (expirationTime = useFiber(current, element.props, expirationTime)),
-        (expirationTime.ref = coerceRef(returnFiber, current, element)),
-        (expirationTime["return"] = returnFiber),
-        expirationTime
-      );
-    expirationTime = createFiberFromElement(
-      element,
-      returnFiber.mode,
-      expirationTime
-    );
-    expirationTime.ref = coerceRef(returnFiber, current, element);
-    expirationTime["return"] = returnFiber;
-    return expirationTime;
-  }
-  function updatePortal(returnFiber, current, portal, expirationTime) {
-    if (
-      null === current ||
-      4 !== current.tag ||
-      current.stateNode.containerInfo !== portal.containerInfo ||
-      current.stateNode.implementation !== portal.implementation
-    )
-      return (
-        (current = createFiberFromPortal(
-          portal,
-          returnFiber.mode,
-          expirationTime
-        )),
-        (current["return"] = returnFiber),
-        current
-      );
-    current = useFiber(current, portal.children || [], expirationTime);
-    current["return"] = returnFiber;
-    return current;
-  }
-  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
-    if (null === current || 10 !== current.tag)
-      return (
-        (current = createFiberFromFragment(
-          fragment,
-          returnFiber.mode,
-          expirationTime,
-          key
-        )),
-        (current["return"] = returnFiber),
-        current
-      );
-    current = useFiber(current, fragment, expirationTime);
-    current["return"] = returnFiber;
-    return current;
-  }
-  function createChild(returnFiber, newChild, expirationTime) {
-    if ("string" === typeof newChild || "number" === typeof newChild)
-      return (
-        (newChild = createFiberFromText(
-          "" + newChild,
-          returnFiber.mode,
-          expirationTime
-        )),
-        (newChild["return"] = returnFiber),
-        newChild
-      );
-    if ("object" === typeof newChild && null !== newChild) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return (
-            (expirationTime = createFiberFromElement(
-              newChild,
-              returnFiber.mode,
-              expirationTime
-            )),
-            (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
-            (expirationTime["return"] = returnFiber),
-            expirationTime
-          );
-        case REACT_PORTAL_TYPE:
-          return (
-            (newChild = createFiberFromPortal(
-              newChild,
-              returnFiber.mode,
-              expirationTime
-            )),
-            (newChild["return"] = returnFiber),
-            newChild
-          );
-      }
-      if (isArray$1(newChild) || getIteratorFn(newChild))
-        return (
-          (newChild = createFiberFromFragment(
-            newChild,
-            returnFiber.mode,
-            expirationTime,
-            null
-          )),
-          (newChild["return"] = returnFiber),
-          newChild
-        );
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-    return null;
-  }
-  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
-    var key = null !== oldFiber ? oldFiber.key : null;
-    if ("string" === typeof newChild || "number" === typeof newChild)
-      return null !== key
-        ? null
-        : updateTextNode(returnFiber, oldFiber, "" + newChild, expirationTime);
-    if ("object" === typeof newChild && null !== newChild) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return newChild.key === key
-            ? newChild.type === REACT_FRAGMENT_TYPE
-              ? updateFragment(
-                  returnFiber,
-                  oldFiber,
-                  newChild.props.children,
-                  expirationTime,
-                  key
-                )
-              : updateElement(returnFiber, oldFiber, newChild, expirationTime)
-            : null;
-        case REACT_PORTAL_TYPE:
-          return newChild.key === key
-            ? updatePortal(returnFiber, oldFiber, newChild, expirationTime)
-            : null;
-      }
-      if (isArray$1(newChild) || getIteratorFn(newChild))
-        return null !== key
-          ? null
-          : updateFragment(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime,
-              null
-            );
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-    return null;
-  }
-  function updateFromMap(
-    existingChildren,
-    returnFiber,
-    newIdx,
-    newChild,
-    expirationTime
-  ) {
-    if ("string" === typeof newChild || "number" === typeof newChild)
-      return (
-        (existingChildren = existingChildren.get(newIdx) || null),
-        updateTextNode(
-          returnFiber,
-          existingChildren,
-          "" + newChild,
-          expirationTime
-        )
-      );
-    if ("object" === typeof newChild && null !== newChild) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return (
-            (existingChildren =
-              existingChildren.get(
-                null === newChild.key ? newIdx : newChild.key
-              ) || null),
-            newChild.type === REACT_FRAGMENT_TYPE
-              ? updateFragment(
-                  returnFiber,
-                  existingChildren,
-                  newChild.props.children,
-                  expirationTime,
-                  newChild.key
-                )
-              : updateElement(
-                  returnFiber,
-                  existingChildren,
-                  newChild,
-                  expirationTime
-                )
-          );
-        case REACT_PORTAL_TYPE:
-          return (
-            (existingChildren =
-              existingChildren.get(
-                null === newChild.key ? newIdx : newChild.key
-              ) || null),
-            updatePortal(
-              returnFiber,
-              existingChildren,
-              newChild,
-              expirationTime
-            )
-          );
-      }
-      if (isArray$1(newChild) || getIteratorFn(newChild))
-        return (
-          (existingChildren = existingChildren.get(newIdx) || null),
-          updateFragment(
-            returnFiber,
-            existingChildren,
-            newChild,
-            expirationTime,
-            null
-          )
-        );
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-    return null;
-  }
-  function reconcileChildrenArray(
-    returnFiber,
-    currentFirstChild,
-    newChildren,
-    expirationTime
-  ) {
-    for (
-      var resultingFirstChild = null,
-        previousNewFiber = null,
-        oldFiber = currentFirstChild,
-        newIdx = (currentFirstChild = 0),
-        nextOldFiber = null;
-      null !== oldFiber && newIdx < newChildren.length;
-      newIdx++
-    ) {
-      oldFiber.index > newIdx
-        ? ((nextOldFiber = oldFiber), (oldFiber = null))
-        : (nextOldFiber = oldFiber.sibling);
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        newChildren[newIdx],
-        expirationTime
-      );
-      if (null === newFiber) {
-        null === oldFiber && (oldFiber = nextOldFiber);
-        break;
-      }
-      shouldTrackSideEffects &&
-        oldFiber &&
-        null === newFiber.alternate &&
-        deleteChild(returnFiber, oldFiber);
-      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
-      null === previousNewFiber
-        ? (resultingFirstChild = newFiber)
-        : (previousNewFiber.sibling = newFiber);
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-    if (newIdx === newChildren.length)
-      return (
-        deleteRemainingChildren(returnFiber, oldFiber), resultingFirstChild
-      );
-    if (null === oldFiber) {
-      for (; newIdx < newChildren.length; newIdx++)
-        if (
-          (oldFiber = createChild(
-            returnFiber,
-            newChildren[newIdx],
-            expirationTime
-          ))
-        )
-          (currentFirstChild = placeChild(oldFiber, currentFirstChild, newIdx)),
-            null === previousNewFiber
-              ? (resultingFirstChild = oldFiber)
-              : (previousNewFiber.sibling = oldFiber),
-            (previousNewFiber = oldFiber);
-      return resultingFirstChild;
-    }
-    for (
-      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
-      newIdx < newChildren.length;
-      newIdx++
-    )
-      if (
-        (nextOldFiber = updateFromMap(
-          oldFiber,
-          returnFiber,
-          newIdx,
-          newChildren[newIdx],
-          expirationTime
-        ))
-      ) {
-        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
-          oldFiber["delete"](
-            null === nextOldFiber.key ? newIdx : nextOldFiber.key
-          );
-        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (resultingFirstChild = nextOldFiber)
-          : (previousNewFiber.sibling = nextOldFiber);
-        previousNewFiber = nextOldFiber;
-      }
-    shouldTrackSideEffects &&
-      oldFiber.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    return resultingFirstChild;
-  }
-  function reconcileChildrenIterator(
-    returnFiber,
-    currentFirstChild,
-    newChildrenIterable,
-    expirationTime
-  ) {
-    var iteratorFn = getIteratorFn(newChildrenIterable);
-    invariant(
-      "function" === typeof iteratorFn,
-      "An object is not an iterable. This error is likely caused by a bug in React. Please file an issue."
-    );
-    newChildrenIterable = iteratorFn.call(newChildrenIterable);
-    invariant(
-      null != newChildrenIterable,
-      "An iterable object provided no iterator."
-    );
-    for (
-      var previousNewFiber = (iteratorFn = null),
-        oldFiber = currentFirstChild,
-        newIdx = (currentFirstChild = 0),
-        nextOldFiber = null,
-        step = newChildrenIterable.next();
-      null !== oldFiber && !step.done;
-      newIdx++, step = newChildrenIterable.next()
-    ) {
-      oldFiber.index > newIdx
-        ? ((nextOldFiber = oldFiber), (oldFiber = null))
-        : (nextOldFiber = oldFiber.sibling);
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        step.value,
-        expirationTime
-      );
-      if (null === newFiber) {
-        oldFiber || (oldFiber = nextOldFiber);
-        break;
-      }
-      shouldTrackSideEffects &&
-        oldFiber &&
-        null === newFiber.alternate &&
-        deleteChild(returnFiber, oldFiber);
-      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
-      null === previousNewFiber
-        ? (iteratorFn = newFiber)
-        : (previousNewFiber.sibling = newFiber);
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-    if (step.done)
-      return deleteRemainingChildren(returnFiber, oldFiber), iteratorFn;
-    if (null === oldFiber) {
-      for (; !step.done; newIdx++, step = newChildrenIterable.next())
-        (step = createChild(returnFiber, step.value, expirationTime)),
-          null !== step &&
-            ((currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
-            null === previousNewFiber
-              ? (iteratorFn = step)
-              : (previousNewFiber.sibling = step),
-            (previousNewFiber = step));
-      return iteratorFn;
-    }
-    for (
-      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
-      !step.done;
-      newIdx++, step = newChildrenIterable.next()
-    )
-      if (
-        ((step = updateFromMap(
-          oldFiber,
-          returnFiber,
-          newIdx,
-          step.value,
-          expirationTime
-        )),
-        null !== step)
-      ) {
-        if (shouldTrackSideEffects && null !== step.alternate)
-          oldFiber["delete"](null === step.key ? newIdx : step.key);
-        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (iteratorFn = step)
-          : (previousNewFiber.sibling = step);
-        previousNewFiber = step;
-      }
-    shouldTrackSideEffects &&
-      oldFiber.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    return iteratorFn;
-  }
-  return function(returnFiber, currentFirstChild, newChild, expirationTime) {
-    "object" === typeof newChild &&
-      null !== newChild &&
-      newChild.type === REACT_FRAGMENT_TYPE &&
-      null === newChild.key &&
-      (newChild = newChild.props.children);
-    var isObject = "object" === typeof newChild && null !== newChild;
-    if (isObject)
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          a: {
-            var key = newChild.key;
-            for (isObject = currentFirstChild; null !== isObject; ) {
-              if (isObject.key === key)
-                if (
-                  10 === isObject.tag
-                    ? newChild.type === REACT_FRAGMENT_TYPE
-                    : isObject.type === newChild.type
-                ) {
-                  deleteRemainingChildren(returnFiber, isObject.sibling);
-                  currentFirstChild = useFiber(
-                    isObject,
-                    newChild.type === REACT_FRAGMENT_TYPE
-                      ? newChild.props.children
-                      : newChild.props,
-                    expirationTime
-                  );
-                  currentFirstChild.ref = coerceRef(
-                    returnFiber,
-                    isObject,
-                    newChild
-                  );
-                  currentFirstChild["return"] = returnFiber;
-                  returnFiber = currentFirstChild;
-                  break a;
-                } else {
-                  deleteRemainingChildren(returnFiber, isObject);
-                  break;
-                }
-              else deleteChild(returnFiber, isObject);
-              isObject = isObject.sibling;
-            }
-            newChild.type === REACT_FRAGMENT_TYPE
-              ? ((currentFirstChild = createFiberFromFragment(
-                  newChild.props.children,
-                  returnFiber.mode,
-                  expirationTime,
-                  newChild.key
-                )),
-                (currentFirstChild["return"] = returnFiber),
-                (returnFiber = currentFirstChild))
-              : ((expirationTime = createFiberFromElement(
-                  newChild,
-                  returnFiber.mode,
-                  expirationTime
-                )),
-                (expirationTime.ref = coerceRef(
-                  returnFiber,
-                  currentFirstChild,
-                  newChild
-                )),
-                (expirationTime["return"] = returnFiber),
-                (returnFiber = expirationTime));
-          }
-          return placeSingleChild(returnFiber);
-        case REACT_PORTAL_TYPE:
-          a: {
-            for (isObject = newChild.key; null !== currentFirstChild; ) {
-              if (currentFirstChild.key === isObject)
-                if (
-                  4 === currentFirstChild.tag &&
-                  currentFirstChild.stateNode.containerInfo ===
-                    newChild.containerInfo &&
-                  currentFirstChild.stateNode.implementation ===
-                    newChild.implementation
-                ) {
-                  deleteRemainingChildren(
-                    returnFiber,
-                    currentFirstChild.sibling
-                  );
-                  currentFirstChild = useFiber(
-                    currentFirstChild,
-                    newChild.children || [],
-                    expirationTime
-                  );
-                  currentFirstChild["return"] = returnFiber;
-                  returnFiber = currentFirstChild;
-                  break a;
-                } else {
-                  deleteRemainingChildren(returnFiber, currentFirstChild);
-                  break;
-                }
-              else deleteChild(returnFiber, currentFirstChild);
-              currentFirstChild = currentFirstChild.sibling;
-            }
-            currentFirstChild = createFiberFromPortal(
-              newChild,
-              returnFiber.mode,
-              expirationTime
-            );
-            currentFirstChild["return"] = returnFiber;
-            returnFiber = currentFirstChild;
-          }
-          return placeSingleChild(returnFiber);
-      }
-    if ("string" === typeof newChild || "number" === typeof newChild)
-      return (
-        (newChild = "" + newChild),
-        null !== currentFirstChild && 6 === currentFirstChild.tag
-          ? (deleteRemainingChildren(returnFiber, currentFirstChild.sibling),
-            (currentFirstChild = useFiber(
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )),
-            (currentFirstChild["return"] = returnFiber),
-            (returnFiber = currentFirstChild))
-          : (deleteRemainingChildren(returnFiber, currentFirstChild),
-            (currentFirstChild = createFiberFromText(
-              newChild,
-              returnFiber.mode,
-              expirationTime
-            )),
-            (currentFirstChild["return"] = returnFiber),
-            (returnFiber = currentFirstChild)),
-        placeSingleChild(returnFiber)
-      );
-    if (isArray$1(newChild))
-      return reconcileChildrenArray(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    if (getIteratorFn(newChild))
-      return reconcileChildrenIterator(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    isObject && throwOnInvalidObjectType(returnFiber, newChild);
-    if ("undefined" === typeof newChild)
-      switch (returnFiber.tag) {
-        case 2:
-        case 1:
-          (expirationTime = returnFiber.type),
-            invariant(
-              !1,
-              "%s(...): Nothing was returned from render. This usually means a return statement is missing. Or, to render nothing, return null.",
-              expirationTime.displayName || expirationTime.name || "Component"
-            );
-      }
-    return deleteRemainingChildren(returnFiber, currentFirstChild);
-  };
-}
-var reconcileChildFibers = ChildReconciler(!0),
-  mountChildFibers = ChildReconciler(!1);
-function ReactFiberBeginWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  scheduleWork,
-  computeExpirationForFiber
-) {
-  function reconcileChildren(current, workInProgress, nextChildren) {
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      workInProgress.expirationTime
-    );
-  }
-  function reconcileChildrenAtExpirationTime(
-    current,
-    workInProgress,
-    nextChildren,
-    renderExpirationTime
-  ) {
-    workInProgress.child =
-      null === current
-        ? mountChildFibers(
-            workInProgress,
-            null,
-            nextChildren,
-            renderExpirationTime
-          )
-        : reconcileChildFibers(
-            workInProgress,
-            current.child,
-            nextChildren,
-            renderExpirationTime
-          );
-  }
-  function markRef(current, workInProgress) {
-    var ref = workInProgress.ref;
-    if (
-      (null === current && null !== ref) ||
-      (null !== current && current.ref !== ref)
-    )
-      workInProgress.effectTag |= 128;
-  }
-  function finishClassComponent(
-    current,
-    workInProgress,
-    shouldUpdate,
-    hasContext,
-    didCaptureError,
-    renderExpirationTime
-  ) {
-    markRef(current, workInProgress);
-    if (!shouldUpdate && !didCaptureError)
-      return (
-        hasContext && invalidateContextProvider(workInProgress, !1),
-        bailoutOnAlreadyFinishedWork(current, workInProgress)
-      );
-    shouldUpdate = workInProgress.stateNode;
-    ReactCurrentOwner.current = workInProgress;
-    var nextChildren = didCaptureError ? null : shouldUpdate.render();
-    workInProgress.effectTag |= 1;
-    didCaptureError &&
-      (reconcileChildrenAtExpirationTime(
-        current,
-        workInProgress,
-        null,
-        renderExpirationTime
-      ),
-      (workInProgress.child = null));
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      renderExpirationTime
-    );
-    workInProgress.memoizedState = shouldUpdate.state;
-    workInProgress.memoizedProps = shouldUpdate.props;
-    hasContext && invalidateContextProvider(workInProgress, !0);
-    return workInProgress.child;
-  }
-  function pushHostRootContext(workInProgress) {
-    var root = workInProgress.stateNode;
-    root.pendingContext
-      ? pushTopLevelContextObject(
-          workInProgress,
-          root.pendingContext,
-          root.pendingContext !== root.context
-        )
-      : root.context &&
-        pushTopLevelContextObject(workInProgress, root.context, !1);
-    pushHostContainer(workInProgress, root.containerInfo);
-  }
-  function propagateContextChange(
-    workInProgress,
-    context,
-    changedBits,
-    renderExpirationTime
-  ) {
-    var fiber = workInProgress.child;
-    for (
-      null !== fiber && (fiber["return"] = workInProgress);
-      null !== fiber;
-
-    ) {
-      switch (fiber.tag) {
-        case 12:
-          var nextFiber = fiber.stateNode | 0;
-          if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
-            for (nextFiber = fiber; null !== nextFiber; ) {
-              var alternate = nextFiber.alternate;
-              if (
-                0 === nextFiber.expirationTime ||
-                nextFiber.expirationTime > renderExpirationTime
-              )
-                (nextFiber.expirationTime = renderExpirationTime),
-                  null !== alternate &&
-                    (0 === alternate.expirationTime ||
-                      alternate.expirationTime > renderExpirationTime) &&
-                    (alternate.expirationTime = renderExpirationTime);
-              else if (
-                null !== alternate &&
-                (0 === alternate.expirationTime ||
-                  alternate.expirationTime > renderExpirationTime)
-              )
-                alternate.expirationTime = renderExpirationTime;
-              else break;
-              nextFiber = nextFiber["return"];
-            }
-            nextFiber = null;
-          } else nextFiber = fiber.child;
-          break;
-        case 13:
-          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
-          break;
-        default:
-          nextFiber = fiber.child;
-      }
-      if (null !== nextFiber) nextFiber["return"] = fiber;
-      else
-        for (nextFiber = fiber; null !== nextFiber; ) {
-          if (nextFiber === workInProgress) {
-            nextFiber = null;
-            break;
-          }
-          fiber = nextFiber.sibling;
-          if (null !== fiber) {
-            nextFiber = fiber;
-            break;
-          }
-          nextFiber = nextFiber["return"];
-        }
-      fiber = nextFiber;
-    }
-  }
-  function updateContextProvider(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var context = workInProgress.type._context,
-      newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps;
-    if (!hasLegacyContextChanged() && oldProps === newProps)
-      return (
-        (workInProgress.stateNode = 0),
-        pushProvider(workInProgress),
-        bailoutOnAlreadyFinishedWork(current, workInProgress)
-      );
-    var newValue = newProps.value;
-    workInProgress.memoizedProps = newProps;
-    if (null === oldProps) newValue = 1073741823;
-    else if (oldProps.value === newProps.value) {
-      if (oldProps.children === newProps.children)
-        return (
-          (workInProgress.stateNode = 0),
-          pushProvider(workInProgress),
-          bailoutOnAlreadyFinishedWork(current, workInProgress)
-        );
-      newValue = 0;
-    } else {
-      var oldValue = oldProps.value;
-      if (
-        (oldValue === newValue &&
-          (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
-        (oldValue !== oldValue && newValue !== newValue)
-      ) {
-        if (oldProps.children === newProps.children)
-          return (
-            (workInProgress.stateNode = 0),
-            pushProvider(workInProgress),
-            bailoutOnAlreadyFinishedWork(current, workInProgress)
-          );
-        newValue = 0;
-      } else if (
-        ((newValue =
-          "function" === typeof context._calculateChangedBits
-            ? context._calculateChangedBits(oldValue, newValue)
-            : 1073741823),
-        (newValue |= 0),
-        0 === newValue)
-      ) {
-        if (oldProps.children === newProps.children)
-          return (
-            (workInProgress.stateNode = 0),
-            pushProvider(workInProgress),
-            bailoutOnAlreadyFinishedWork(current, workInProgress)
-          );
-      } else
-        propagateContextChange(
-          workInProgress,
-          context,
-          newValue,
-          renderExpirationTime
-        );
-    }
-    workInProgress.stateNode = newValue;
-    pushProvider(workInProgress);
-    reconcileChildren(current, workInProgress, newProps.children);
-    return workInProgress.child;
-  }
-  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
-    invariant(
-      null === current || workInProgress.child === current.child,
-      "Resuming work not yet implemented."
-    );
-    if (null !== workInProgress.child) {
-      current = workInProgress.child;
-      var newChild = createWorkInProgress(
-        current,
-        current.pendingProps,
-        current.expirationTime
-      );
-      workInProgress.child = newChild;
-      for (newChild["return"] = workInProgress; null !== current.sibling; )
-        (current = current.sibling),
-          (newChild = newChild.sibling = createWorkInProgress(
-            current,
-            current.pendingProps,
-            current.expirationTime
-          )),
-          (newChild["return"] = workInProgress);
-      newChild.sibling = null;
-    }
-    return workInProgress.child;
-  }
-  var shouldSetTextContent = config.shouldSetTextContent,
-    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree,
-    pushHostContext = hostContext.pushHostContext,
-    pushHostContainer = hostContext.pushHostContainer,
-    pushProvider = newContext.pushProvider,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    hasLegacyContextChanged = legacyContext.hasContextChanged,
-    pushLegacyContextProvider = legacyContext.pushContextProvider,
-    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
-    invalidateContextProvider = legacyContext.invalidateContextProvider,
-    enterHydrationState = hydrationContext.enterHydrationState,
-    resetHydrationState = hydrationContext.resetHydrationState,
-    tryToClaimNextHydratableInstance =
-      hydrationContext.tryToClaimNextHydratableInstance;
-  config = ReactFiberClassComponent(
-    legacyContext,
-    scheduleWork,
-    computeExpirationForFiber,
-    function(workInProgress, nextProps) {
-      workInProgress.memoizedProps = nextProps;
-    },
-    function(workInProgress, nextState) {
-      workInProgress.memoizedState = nextState;
-    }
-  );
-  var adoptClassInstance = config.adoptClassInstance,
-    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
-    constructClassInstance = config.constructClassInstance,
-    mountClassInstance = config.mountClassInstance,
-    resumeMountClassInstance = config.resumeMountClassInstance,
-    updateClassInstance = config.updateClassInstance;
-  return {
-    beginWork: function(current, workInProgress, renderExpirationTime) {
-      if (
-        0 === workInProgress.expirationTime ||
-        workInProgress.expirationTime > renderExpirationTime
-      ) {
-        switch (workInProgress.tag) {
-          case 3:
-            pushHostRootContext(workInProgress);
-            break;
-          case 2:
-            pushLegacyContextProvider(workInProgress);
-            break;
-          case 4:
-            pushHostContainer(
-              workInProgress,
-              workInProgress.stateNode.containerInfo
-            );
-            break;
-          case 13:
-            pushProvider(workInProgress);
-        }
-        return null;
-      }
-      switch (workInProgress.tag) {
-        case 0:
-          invariant(
-            null === current,
-            "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
-          );
-          var fn = workInProgress.type,
-            props = workInProgress.pendingProps,
-            unmaskedContext = getUnmaskedContext(workInProgress);
-          unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
-          fn = fn(props, unmaskedContext);
-          workInProgress.effectTag |= 1;
-          "object" === typeof fn &&
-          null !== fn &&
-          "function" === typeof fn.render &&
-          void 0 === fn.$$typeof
-            ? ((unmaskedContext = workInProgress.type),
-              (workInProgress.tag = 2),
-              (workInProgress.memoizedState =
-                null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
-                ((props = callGetDerivedStateFromProps(
-                  workInProgress,
-                  fn,
-                  props,
-                  workInProgress.memoizedState
-                )),
-                null !== props &&
-                  void 0 !== props &&
-                  (workInProgress.memoizedState = Object.assign(
-                    {},
-                    workInProgress.memoizedState,
-                    props
-                  ))),
-              (props = pushLegacyContextProvider(workInProgress)),
-              adoptClassInstance(workInProgress, fn),
-              mountClassInstance(workInProgress, renderExpirationTime),
-              (current = finishClassComponent(
-                current,
-                workInProgress,
-                !0,
-                props,
-                !1,
-                renderExpirationTime
-              )))
-            : ((workInProgress.tag = 1),
-              reconcileChildren(current, workInProgress, fn),
-              (workInProgress.memoizedProps = props),
-              (current = workInProgress.child));
-          return current;
-        case 1:
-          return (
-            (props = workInProgress.type),
-            (renderExpirationTime = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime
-              ? ((fn = getUnmaskedContext(workInProgress)),
-                (fn = getMaskedContext(workInProgress, fn)),
-                (props = props(renderExpirationTime, fn)),
-                (workInProgress.effectTag |= 1),
-                reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 2:
-          props = pushLegacyContextProvider(workInProgress);
-          null === current
-            ? null === workInProgress.stateNode
-              ? (constructClassInstance(
-                  workInProgress,
-                  workInProgress.pendingProps
-                ),
-                mountClassInstance(workInProgress, renderExpirationTime),
-                (fn = !0))
-              : (fn = resumeMountClassInstance(
-                  workInProgress,
-                  renderExpirationTime
-                ))
-            : (fn = updateClassInstance(
-                current,
-                workInProgress,
-                renderExpirationTime
-              ));
-          unmaskedContext = !1;
-          var updateQueue = workInProgress.updateQueue;
-          null !== updateQueue &&
-            null !== updateQueue.capturedValues &&
-            (unmaskedContext = fn = !0);
-          return finishClassComponent(
-            current,
-            workInProgress,
-            fn,
-            props,
-            unmaskedContext,
-            renderExpirationTime
-          );
-        case 3:
-          a: if (
-            (pushHostRootContext(workInProgress),
-            (fn = workInProgress.updateQueue),
-            null !== fn)
-          ) {
-            unmaskedContext = workInProgress.memoizedState;
-            props = processUpdateQueue(
-              current,
-              workInProgress,
-              fn,
-              null,
-              null,
-              renderExpirationTime
-            );
-            workInProgress.memoizedState = props;
-            fn = workInProgress.updateQueue;
-            if (null !== fn && null !== fn.capturedValues) fn = null;
-            else if (unmaskedContext === props) {
-              resetHydrationState();
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-              break a;
-            } else fn = props.element;
-            unmaskedContext = workInProgress.stateNode;
-            (null === current || null === current.child) &&
-            unmaskedContext.hydrate &&
-            enterHydrationState(workInProgress)
-              ? ((workInProgress.effectTag |= 2),
-                (workInProgress.child = mountChildFibers(
-                  workInProgress,
-                  null,
-                  fn,
-                  renderExpirationTime
-                )))
-              : (resetHydrationState(),
-                reconcileChildren(current, workInProgress, fn));
-            workInProgress.memoizedState = props;
-            current = workInProgress.child;
-          } else
-            resetHydrationState(),
-              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
-          return current;
-        case 5:
-          a: {
-            pushHostContext(workInProgress);
-            null === current &&
-              tryToClaimNextHydratableInstance(workInProgress);
-            props = workInProgress.type;
-            updateQueue = workInProgress.memoizedProps;
-            fn = workInProgress.pendingProps;
-            unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && updateQueue === fn) {
-              if (
-                (updateQueue =
-                  workInProgress.mode & 1 &&
-                  shouldDeprioritizeSubtree(props, fn))
-              )
-                workInProgress.expirationTime = 1073741823;
-              if (!updateQueue || 1073741823 !== renderExpirationTime) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-            }
-            updateQueue = fn.children;
-            shouldSetTextContent(props, fn)
-              ? (updateQueue = null)
-              : unmaskedContext &&
-                shouldSetTextContent(props, unmaskedContext) &&
-                (workInProgress.effectTag |= 16);
-            markRef(current, workInProgress);
-            1073741823 !== renderExpirationTime &&
-            workInProgress.mode & 1 &&
-            shouldDeprioritizeSubtree(props, fn)
-              ? ((workInProgress.expirationTime = 1073741823),
-                (workInProgress.memoizedProps = fn),
-                (current = null))
-              : (reconcileChildren(current, workInProgress, updateQueue),
-                (workInProgress.memoizedProps = fn),
-                (current = workInProgress.child));
-          }
-          return current;
-        case 6:
-          return (
-            null === current &&
-              tryToClaimNextHydratableInstance(workInProgress),
-            (workInProgress.memoizedProps = workInProgress.pendingProps),
-            null
-          );
-        case 8:
-          workInProgress.tag = 7;
-        case 7:
-          return (
-            (props = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-              workInProgress.memoizedProps !== props ||
-              (props = workInProgress.memoizedProps),
-            (fn = props.children),
-            (workInProgress.stateNode =
-              null === current
-                ? mountChildFibers(
-                    workInProgress,
-                    workInProgress.stateNode,
-                    fn,
-                    renderExpirationTime
-                  )
-                : reconcileChildFibers(
-                    workInProgress,
-                    current.stateNode,
-                    fn,
-                    renderExpirationTime
-                  )),
-            (workInProgress.memoizedProps = props),
-            workInProgress.stateNode
-          );
-        case 9:
-          return null;
-        case 4:
-          return (
-            pushHostContainer(
-              workInProgress,
-              workInProgress.stateNode.containerInfo
-            ),
-            (props = workInProgress.pendingProps),
-            hasLegacyContextChanged() || workInProgress.memoizedProps !== props
-              ? (null === current
-                  ? (workInProgress.child = reconcileChildFibers(
-                      workInProgress,
-                      null,
-                      props,
-                      renderExpirationTime
-                    ))
-                  : reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = props),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 14:
-          return (
-            (renderExpirationTime = workInProgress.type.render),
-            (renderExpirationTime = renderExpirationTime(
-              workInProgress.pendingProps,
-              workInProgress.ref
-            )),
-            reconcileChildren(current, workInProgress, renderExpirationTime),
-            (workInProgress.memoizedProps = renderExpirationTime),
-            workInProgress.child
-          );
-        case 10:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime
-              ? (reconcileChildren(
-                  current,
-                  workInProgress,
-                  renderExpirationTime
-                ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 11:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps.children),
-            hasLegacyContextChanged() ||
-            (null !== renderExpirationTime &&
-              workInProgress.memoizedProps !== renderExpirationTime)
-              ? (reconcileChildren(
-                  current,
-                  workInProgress,
-                  renderExpirationTime
-                ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 13:
-          return updateContextProvider(
-            current,
-            workInProgress,
-            renderExpirationTime
-          );
-        case 12:
-          a: {
-            fn = workInProgress.type;
-            unmaskedContext = workInProgress.pendingProps;
-            updateQueue = workInProgress.memoizedProps;
-            props = fn._currentValue;
-            var changedBits = fn._changedBits;
-            if (
-              hasLegacyContextChanged() ||
-              0 !== changedBits ||
-              updateQueue !== unmaskedContext
-            ) {
-              workInProgress.memoizedProps = unmaskedContext;
-              var observedBits = unmaskedContext.unstable_observedBits;
-              if (void 0 === observedBits || null === observedBits)
-                observedBits = 1073741823;
-              workInProgress.stateNode = observedBits;
-              if (0 !== (changedBits & observedBits))
-                propagateContextChange(
-                  workInProgress,
-                  fn,
-                  changedBits,
-                  renderExpirationTime
-                );
-              else if (updateQueue === unmaskedContext) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-              renderExpirationTime = unmaskedContext.children;
-              renderExpirationTime = renderExpirationTime(props);
-              reconcileChildren(current, workInProgress, renderExpirationTime);
-              current = workInProgress.child;
-            } else
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
-          return current;
-        default:
-          invariant(
-            !1,
-            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    }
-  };
-}
-function ReactFiberCompleteWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext
-) {
-  function markUpdate(workInProgress) {
-    workInProgress.effectTag |= 4;
-  }
-  function appendAllChildren(parent, workInProgress) {
-    for (var node = workInProgress.child; null !== node; ) {
-      if (5 === node.tag || 6 === node.tag)
-        appendInitialChild(parent, node.stateNode);
-      else if (4 !== node.tag && null !== node.child) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === workInProgress) break;
-      for (; null === node.sibling; ) {
-        if (null === node["return"] || node["return"] === workInProgress)
-          return;
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-  var createInstance = config.createInstance,
-    createTextInstance = config.createTextInstance,
-    appendInitialChild = config.appendInitialChild,
-    finalizeInitialChildren = config.finalizeInitialChildren,
-    prepareUpdate = config.prepareUpdate,
-    persistence = config.persistence,
-    getRootHostContainer = hostContext.getRootHostContainer,
-    popHostContext = hostContext.popHostContext,
-    getHostContext = hostContext.getHostContext,
-    popHostContainer = hostContext.popHostContainer,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider,
-    prepareToHydrateHostInstance =
-      hydrationContext.prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance =
-      hydrationContext.prepareToHydrateHostTextInstance,
-    popHydrationState = hydrationContext.popHydrationState,
-    updateHostContainer = void 0,
-    updateHostComponent = void 0,
-    updateHostText = void 0;
-  if (config.mutation) invariant(!1, "Mutating reconciler is disabled.");
-  else if (persistence) {
-    var cloneInstance = persistence.cloneInstance,
-      createContainerChildSet = persistence.createContainerChildSet,
-      appendChildToContainerChildSet =
-        persistence.appendChildToContainerChildSet,
-      finalizeContainerChildren = persistence.finalizeContainerChildren;
-    updateHostContainer = function(workInProgress) {
-      var portalOrRoot = workInProgress.stateNode;
-      if (null !== workInProgress.firstEffect) {
-        var container = portalOrRoot.containerInfo,
-          newChildSet = createContainerChildSet(container);
-        a: for (var node = workInProgress.child; null !== node; ) {
-          if (5 === node.tag || 6 === node.tag)
-            appendChildToContainerChildSet(newChildSet, node.stateNode);
-          else if (4 !== node.tag && null !== node.child) {
-            node.child["return"] = node;
-            node = node.child;
-            continue;
-          }
-          if (node === workInProgress) break a;
-          for (; null === node.sibling; ) {
-            if (null === node["return"] || node["return"] === workInProgress)
-              break a;
-            node = node["return"];
-          }
-          node.sibling["return"] = node["return"];
-          node = node.sibling;
-        }
-        portalOrRoot.pendingChildren = newChildSet;
-        markUpdate(workInProgress);
-        finalizeContainerChildren(container, newChildSet);
-      }
-    };
-    updateHostComponent = function(
-      current,
-      workInProgress,
-      updatePayload,
-      type,
-      oldProps,
-      newProps,
-      rootContainerInstance,
-      currentHostContext
-    ) {
-      var childrenUnchanged = null === workInProgress.firstEffect;
-      current = current.stateNode;
-      childrenUnchanged && null === updatePayload
-        ? (workInProgress.stateNode = current)
-        : ((updatePayload = cloneInstance(
-            current,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            workInProgress,
-            childrenUnchanged,
-            workInProgress.stateNode
-          )),
-          finalizeInitialChildren(
-            updatePayload,
-            type,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          ) && markUpdate(workInProgress),
-          (workInProgress.stateNode = updatePayload),
-          childrenUnchanged
-            ? markUpdate(workInProgress)
-            : appendAllChildren(updatePayload, workInProgress));
-    };
-    updateHostText = function(current, workInProgress, oldText, newText) {
-      oldText !== newText &&
-        ((current = getRootHostContainer()),
-        (oldText = getHostContext()),
-        (workInProgress.stateNode = createTextInstance(
-          newText,
-          current,
-          oldText,
-          workInProgress
-        )),
-        markUpdate(workInProgress));
-    };
-  } else invariant(!1, "Noop reconciler is disabled.");
-  return {
-    completeWork: function(current, workInProgress, renderExpirationTime) {
-      var newProps = workInProgress.pendingProps;
-      switch (workInProgress.tag) {
-        case 1:
-          return null;
-        case 2:
-          return (
-            popLegacyContextProvider(workInProgress),
-            (current = workInProgress.stateNode),
-            (newProps = workInProgress.updateQueue),
-            null !== newProps &&
-              null !== newProps.capturedValues &&
-              ((workInProgress.effectTag &= -65),
-              "function" === typeof current.componentDidCatch
-                ? (workInProgress.effectTag |= 256)
-                : (newProps.capturedValues = null)),
-            null
-          );
-        case 3:
-          popHostContainer(workInProgress);
-          popTopLevelLegacyContextObject(workInProgress);
-          newProps = workInProgress.stateNode;
-          newProps.pendingContext &&
-            ((newProps.context = newProps.pendingContext),
-            (newProps.pendingContext = null));
-          if (null === current || null === current.child)
-            popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
-          updateHostContainer(workInProgress);
-          current = workInProgress.updateQueue;
-          null !== current &&
-            null !== current.capturedValues &&
-            (workInProgress.effectTag |= 256);
-          return null;
-        case 5:
-          popHostContext(workInProgress);
-          renderExpirationTime = getRootHostContainer();
-          var type = workInProgress.type;
-          if (null !== current && null != workInProgress.stateNode) {
-            var oldProps = current.memoizedProps,
-              _instance = workInProgress.stateNode,
-              currentHostContext = getHostContext();
-            _instance = prepareUpdate(
-              _instance,
-              type,
-              oldProps,
-              newProps,
-              renderExpirationTime,
-              currentHostContext
-            );
-            updateHostComponent(
-              current,
-              workInProgress,
-              _instance,
-              type,
-              oldProps,
-              newProps,
-              renderExpirationTime,
-              currentHostContext
-            );
-            current.ref !== workInProgress.ref &&
-              (workInProgress.effectTag |= 128);
-          } else {
-            if (!newProps)
-              return (
-                invariant(
-                  null !== workInProgress.stateNode,
-                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
-                ),
-                null
-              );
-            current = getHostContext();
-            popHydrationState(workInProgress)
-              ? prepareToHydrateHostInstance(
-                  workInProgress,
-                  renderExpirationTime,
-                  current
-                ) && markUpdate(workInProgress)
-              : ((oldProps = createInstance(
-                  type,
-                  newProps,
-                  renderExpirationTime,
-                  current,
-                  workInProgress
-                )),
-                appendAllChildren(oldProps, workInProgress),
-                finalizeInitialChildren(
-                  oldProps,
-                  type,
-                  newProps,
-                  renderExpirationTime,
-                  current
-                ) && markUpdate(workInProgress),
-                (workInProgress.stateNode = oldProps));
-            null !== workInProgress.ref && (workInProgress.effectTag |= 128);
-          }
-          return null;
-        case 6:
-          if (current && null != workInProgress.stateNode)
-            updateHostText(
-              current,
-              workInProgress,
-              current.memoizedProps,
-              newProps
-            );
-          else {
-            if ("string" !== typeof newProps)
-              return (
-                invariant(
-                  null !== workInProgress.stateNode,
-                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
-                ),
-                null
-              );
-            current = getRootHostContainer();
-            renderExpirationTime = getHostContext();
-            popHydrationState(workInProgress)
-              ? prepareToHydrateHostTextInstance(workInProgress) &&
-                markUpdate(workInProgress)
-              : (workInProgress.stateNode = createTextInstance(
-                  newProps,
-                  current,
-                  renderExpirationTime,
-                  workInProgress
-                ));
-          }
-          return null;
-        case 7:
-          newProps = workInProgress.memoizedProps;
-          invariant(
-            newProps,
-            "Should be resolved by now. This error is likely caused by a bug in React. Please file an issue."
-          );
-          workInProgress.tag = 8;
-          type = [];
-          a: for (
-            (oldProps = workInProgress.stateNode) &&
-            (oldProps["return"] = workInProgress);
-            null !== oldProps;
-
-          ) {
-            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
-              invariant(!1, "A call cannot have host component children.");
-            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
-            else if (null !== oldProps.child) {
-              oldProps.child["return"] = oldProps;
-              oldProps = oldProps.child;
-              continue;
-            }
-            for (; null === oldProps.sibling; ) {
-              if (
-                null === oldProps["return"] ||
-                oldProps["return"] === workInProgress
-              )
-                break a;
-              oldProps = oldProps["return"];
-            }
-            oldProps.sibling["return"] = oldProps["return"];
-            oldProps = oldProps.sibling;
-          }
-          oldProps = newProps.handler;
-          newProps = oldProps(newProps.props, type);
-          workInProgress.child = reconcileChildFibers(
-            workInProgress,
-            null !== current ? current.child : null,
-            newProps,
-            renderExpirationTime
-          );
-          return workInProgress.child;
-        case 8:
-          return (workInProgress.tag = 7), null;
-        case 9:
-          return null;
-        case 14:
-          return null;
-        case 10:
-          return null;
-        case 11:
-          return null;
-        case 4:
-          return (
-            popHostContainer(workInProgress),
-            updateHostContainer(workInProgress),
-            null
-          );
-        case 13:
-          return popProvider(workInProgress), null;
-        case 12:
-          return null;
-        case 0:
-          invariant(
-            !1,
-            "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
-          );
-        default:
-          invariant(
-            !1,
-            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    }
-  };
-}
-function ReactFiberUnwindWork(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
-  return {
-    throwException: function(returnFiber, sourceFiber, rawValue) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      sourceFiber = {
-        value: rawValue,
-        source: sourceFiber,
-        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-      };
-      do {
-        switch (returnFiber.tag) {
-          case 3:
-            ensureUpdateQueues(returnFiber);
-            returnFiber.updateQueue.capturedValues = [sourceFiber];
-            returnFiber.effectTag |= 1024;
-            return;
-          case 2:
-            if (
-              ((rawValue = returnFiber.stateNode),
-              0 === (returnFiber.effectTag & 64) &&
-                null !== rawValue &&
-                "function" === typeof rawValue.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(rawValue))
-            ) {
-              ensureUpdateQueues(returnFiber);
-              rawValue = returnFiber.updateQueue;
-              var capturedValues = rawValue.capturedValues;
-              null === capturedValues
-                ? (rawValue.capturedValues = [sourceFiber])
-                : capturedValues.push(sourceFiber);
-              returnFiber.effectTag |= 1024;
-              return;
-            }
-        }
-        returnFiber = returnFiber["return"];
-      } while (null !== returnFiber);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
-      }
-    }
-  };
-}
-function logError(boundary, errorInfo) {
-  var source = errorInfo.source;
-  null === errorInfo.stack && getStackAddendumByWorkInProgressFiber(source);
-  null !== source && getComponentName(source);
-  errorInfo = errorInfo.value;
-  null !== boundary && 2 === boundary.tag && getComponentName(boundary);
-  try {
-    (errorInfo && errorInfo.suppressReactErrorLogging) ||
-      console.error(errorInfo);
-  } catch (e) {
-    (e && e.suppressReactErrorLogging) || console.error(e);
-  }
-}
-function ReactFiberCommitWork(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed
-) {
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (null !== ref)
-      if ("function" === typeof ref)
-        try {
-          ref(null);
-        } catch (refError) {
-          captureError(current, refError);
-        }
-      else ref.current = null;
-  }
-  function commitBeforeMutationLifeCycles(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case 2:
-        if (finishedWork.effectTag & 2048 && null !== current) {
-          var prevProps = current.memoizedProps,
-            prevState = current.memoizedState;
-          current = finishedWork.stateNode;
-          current.props = finishedWork.memoizedProps;
-          current.state = finishedWork.memoizedState;
-          finishedWork = current.getSnapshotBeforeUpdate(prevProps, prevState);
-          current.__reactInternalSnapshotBeforeUpdate = finishedWork;
-        }
-        break;
-      case 3:
-      case 5:
-      case 6:
-      case 4:
-        break;
-      default:
-        invariant(
-          !1,
-          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-  function commitLifeCycles(finishedRoot, current, finishedWork) {
-    switch (finishedWork.tag) {
-      case 2:
-        finishedRoot = finishedWork.stateNode;
-        if (finishedWork.effectTag & 4)
-          if (null === current)
-            (finishedRoot.props = finishedWork.memoizedProps),
-              (finishedRoot.state = finishedWork.memoizedState),
-              finishedRoot.componentDidMount();
-          else {
-            var prevProps = current.memoizedProps;
-            current = current.memoizedState;
-            finishedRoot.props = finishedWork.memoizedProps;
-            finishedRoot.state = finishedWork.memoizedState;
-            finishedRoot.componentDidUpdate(
-              prevProps,
-              current,
-              finishedRoot.__reactInternalSnapshotBeforeUpdate
-            );
-          }
-        finishedWork = finishedWork.updateQueue;
-        null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
-        break;
-      case 3:
-        current = finishedWork.updateQueue;
-        if (null !== current) {
-          finishedRoot = null;
-          if (null !== finishedWork.child)
-            switch (finishedWork.child.tag) {
-              case 5:
-                finishedRoot = getPublicInstance(finishedWork.child.stateNode);
-                break;
-              case 2:
-                finishedRoot = finishedWork.child.stateNode;
-            }
-          commitCallbacks(current, finishedRoot);
-        }
-        break;
-      case 5:
-        finishedRoot = finishedWork.stateNode;
-        null === current &&
-          finishedWork.effectTag & 4 &&
-          commitMount(
-            finishedRoot,
-            finishedWork.type,
-            finishedWork.memoizedProps,
-            finishedWork
-          );
-        break;
-      case 6:
-        break;
-      case 4:
-        break;
-      default:
-        invariant(
-          !1,
-          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case 2:
-        var ctor = finishedWork.type;
-        onUncaughtError = finishedWork.stateNode;
-        var updateQueue = finishedWork.updateQueue;
-        invariant(
-          null !== updateQueue && null !== updateQueue.capturedValues,
-          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-        );
-        var capturedErrors = updateQueue.capturedValues;
-        updateQueue.capturedValues = null;
-        "function" !== typeof ctor.getDerivedStateFromCatch &&
-          markLegacyErrorBoundaryAsFailed(onUncaughtError);
-        onUncaughtError.props = finishedWork.memoizedProps;
-        onUncaughtError.state = finishedWork.memoizedState;
-        for (ctor = 0; ctor < capturedErrors.length; ctor++) {
-          updateQueue = capturedErrors[ctor];
-          var _error = updateQueue.value,
-            stack = updateQueue.stack;
-          logError(finishedWork, updateQueue);
-          onUncaughtError.componentDidCatch(_error, {
-            componentStack: null !== stack ? stack : ""
-          });
-        }
-        break;
-      case 3:
-        ctor = finishedWork.updateQueue;
-        invariant(
-          null !== ctor && null !== ctor.capturedValues,
-          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-        );
-        capturedErrors = ctor.capturedValues;
-        ctor.capturedValues = null;
-        for (ctor = 0; ctor < capturedErrors.length; ctor++)
-          (updateQueue = capturedErrors[ctor]),
-            logError(finishedWork, updateQueue),
-            onUncaughtError(updateQueue.value);
-        break;
-      default:
-        invariant(
-          !1,
-          "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-  function commitAttachRef(finishedWork) {
-    var ref = finishedWork.ref;
-    if (null !== ref) {
-      var _instance6 = finishedWork.stateNode;
-      switch (finishedWork.tag) {
-        case 5:
-          finishedWork = getPublicInstance(_instance6);
-          break;
-        default:
-          finishedWork = _instance6;
-      }
-      "function" === typeof ref
-        ? ref(finishedWork)
-        : (ref.current = finishedWork);
-    }
-  }
-  function commitDetachRef(current) {
-    current = current.ref;
-    null !== current &&
-      ("function" === typeof current
-        ? current(null)
-        : (current.current = null));
-  }
-  function commitNestedUnmounts(root) {
-    for (var node = root; ; ) {
-      var current = node;
-      "function" === typeof onCommitUnmount && onCommitUnmount(current);
-      switch (current.tag) {
-        case 2:
-          safelyDetachRef(current);
-          var _instance7 = current.stateNode;
-          if ("function" === typeof _instance7.componentWillUnmount)
-            try {
-              (_instance7.props = current.memoizedProps),
-                (_instance7.state = current.memoizedState),
-                _instance7.componentWillUnmount();
-            } catch (unmountError) {
-              captureError(current, unmountError);
-            }
-          break;
-        case 5:
-          safelyDetachRef(current);
-          break;
-        case 7:
-          commitNestedUnmounts(current.stateNode);
-          break;
-        case 4:
-          persistence && emptyPortalContainer(current);
-      }
-      if (null === node.child || (mutation && 4 === node.tag)) {
-        if (node === root) break;
-        for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === root) return;
-          node = node["return"];
-        }
-        node.sibling["return"] = node["return"];
-        node = node.sibling;
-      } else (node.child["return"] = node), (node = node.child);
-    }
-  }
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation,
-    persistence = config.persistence,
-    emptyPortalContainer = void 0;
-  if (!mutation) {
-    var commitContainer = void 0;
-    if (persistence) {
-      var replaceContainerChildren = persistence.replaceContainerChildren,
-        createContainerChildSet = persistence.createContainerChildSet;
-      emptyPortalContainer = function(current) {
-        current = current.stateNode.containerInfo;
-        var emptyChildSet = createContainerChildSet(current);
-        replaceContainerChildren(current, emptyChildSet);
-      };
-      commitContainer = function(finishedWork) {
-        switch (finishedWork.tag) {
-          case 2:
-            break;
-          case 5:
-            break;
-          case 6:
-            break;
-          case 3:
-          case 4:
-            finishedWork = finishedWork.stateNode;
-            replaceContainerChildren(
-              finishedWork.containerInfo,
-              finishedWork.pendingChildren
-            );
-            break;
-          default:
-            invariant(
-              !1,
-              "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-            );
-        }
-      };
-    } else commitContainer = function() {};
-    return {
-      commitResetTextContent: function() {},
-      commitPlacement: function() {},
-      commitDeletion: function(current) {
-        commitNestedUnmounts(current);
-        current["return"] = null;
-        current.child = null;
-        current.alternate &&
-          ((current.alternate.child = null),
-          (current.alternate["return"] = null));
-      },
-      commitWork: function(current, finishedWork) {
-        commitContainer(finishedWork);
-      },
-      commitLifeCycles: commitLifeCycles,
-      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitErrorLogging: commitErrorLogging,
-      commitAttachRef: commitAttachRef,
-      commitDetachRef: commitDetachRef
-    };
-  }
-  var commitMount = mutation.commitMount;
-  invariant(!1, "Mutating reconciler is disabled.");
-}
-var NO_CONTEXT = {};
-function ReactFiberHostContext(config, stack) {
-  function requiredContext(c) {
-    invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
-    );
-    return c;
-  }
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  config = stack.createCursor;
-  var push = stack.push,
-    pop = stack.pop,
-    contextStackCursor = config(NO_CONTEXT),
-    contextFiberStackCursor = config(NO_CONTEXT),
-    rootInstanceStackCursor = config(NO_CONTEXT);
-  return {
-    getHostContext: function() {
-      return requiredContext(contextStackCursor.current);
-    },
-    getRootHostContainer: function() {
-      return requiredContext(rootInstanceStackCursor.current);
-    },
-    popHostContainer: function(fiber) {
-      pop(contextStackCursor, fiber);
-      pop(contextFiberStackCursor, fiber);
-      pop(rootInstanceStackCursor, fiber);
-    },
-    popHostContext: function(fiber) {
-      contextFiberStackCursor.current === fiber &&
-        (pop(contextStackCursor, fiber), pop(contextFiberStackCursor, fiber));
-    },
-    pushHostContainer: function(fiber, nextRootInstance) {
-      push(rootInstanceStackCursor, nextRootInstance, fiber);
-      push(contextFiberStackCursor, fiber, fiber);
-      push(contextStackCursor, NO_CONTEXT, fiber);
-      nextRootInstance = getRootHostContext(nextRootInstance);
-      pop(contextStackCursor, fiber);
-      push(contextStackCursor, nextRootInstance, fiber);
-    },
-    pushHostContext: function(fiber) {
-      var rootInstance = requiredContext(rootInstanceStackCursor.current),
-        context = requiredContext(contextStackCursor.current);
-      rootInstance = getChildHostContext(context, fiber.type, rootInstance);
-      context !== rootInstance &&
-        (push(contextFiberStackCursor, fiber, fiber),
-        push(contextStackCursor, rootInstance, fiber));
-    }
-  };
-}
-function ReactFiberHydrationContext(config) {
-  function deleteHydratableInstance(returnFiber, instance) {
-    var fiber = new FiberNode(5, null, null, 0);
-    fiber.type = "DELETED";
-    fiber.stateNode = instance;
-    fiber["return"] = returnFiber;
-    fiber.effectTag = 8;
-    null !== returnFiber.lastEffect
-      ? ((returnFiber.lastEffect.nextEffect = fiber),
-        (returnFiber.lastEffect = fiber))
-      : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
-  }
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case 5:
-        return (
-          (nextInstance = canHydrateInstance(
-            nextInstance,
-            fiber.type,
-            fiber.pendingProps
-          )),
-          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
-        );
-      case 6:
-        return (
-          (nextInstance = canHydrateTextInstance(
-            nextInstance,
-            fiber.pendingProps
-          )),
-          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
-        );
-      default:
-        return !1;
-    }
-  }
-  function popToNextHostParent(fiber) {
-    for (
-      fiber = fiber["return"];
-      null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
-
-    )
-      fiber = fiber["return"];
-    hydrationParentFiber = fiber;
-  }
-  var shouldSetTextContent = config.shouldSetTextContent;
-  config = config.hydration;
-  if (!config)
-    return {
-      enterHydrationState: function() {
-        return !1;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          !1,
-          "Expected prepareToHydrateHostInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
-        invariant(
-          !1,
-          "Expected prepareToHydrateHostTextInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      popHydrationState: function() {
-        return !1;
-      }
-    };
-  var canHydrateInstance = config.canHydrateInstance,
-    canHydrateTextInstance = config.canHydrateTextInstance,
-    getNextHydratableSibling = config.getNextHydratableSibling,
-    getFirstHydratableChild = config.getFirstHydratableChild,
-    hydrateInstance = config.hydrateInstance,
-    hydrateTextInstance = config.hydrateTextInstance,
-    hydrationParentFiber = null,
-    nextHydratableInstance = null,
-    isHydrating = !1;
-  return {
-    enterHydrationState: function(fiber) {
-      nextHydratableInstance = getFirstHydratableChild(
-        fiber.stateNode.containerInfo
-      );
-      hydrationParentFiber = fiber;
-      return (isHydrating = !0);
-    },
-    resetHydrationState: function() {
-      nextHydratableInstance = hydrationParentFiber = null;
-      isHydrating = !1;
-    },
-    tryToClaimNextHydratableInstance: function(fiber) {
-      if (isHydrating) {
-        var nextInstance = nextHydratableInstance;
-        if (nextInstance) {
-          if (!tryHydrate(fiber, nextInstance)) {
-            nextInstance = getNextHydratableSibling(nextInstance);
-            if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-              fiber.effectTag |= 2;
-              isHydrating = !1;
-              hydrationParentFiber = fiber;
-              return;
-            }
-            deleteHydratableInstance(
-              hydrationParentFiber,
-              nextHydratableInstance
-            );
-          }
-          hydrationParentFiber = fiber;
-          nextHydratableInstance = getFirstHydratableChild(nextInstance);
-        } else
-          (fiber.effectTag |= 2),
-            (isHydrating = !1),
-            (hydrationParentFiber = fiber);
-      }
-    },
-    prepareToHydrateHostInstance: function(
-      fiber,
-      rootContainerInstance,
-      hostContext
-    ) {
-      rootContainerInstance = hydrateInstance(
-        fiber.stateNode,
-        fiber.type,
-        fiber.memoizedProps,
-        rootContainerInstance,
-        hostContext,
-        fiber
-      );
-      fiber.updateQueue = rootContainerInstance;
-      return null !== rootContainerInstance ? !0 : !1;
-    },
-    prepareToHydrateHostTextInstance: function(fiber) {
-      return hydrateTextInstance(fiber.stateNode, fiber.memoizedProps, fiber);
-    },
-    popHydrationState: function(fiber) {
-      if (fiber !== hydrationParentFiber) return !1;
-      if (!isHydrating)
-        return popToNextHostParent(fiber), (isHydrating = !0), !1;
-      var type = fiber.type;
-      if (
-        5 !== fiber.tag ||
-        ("head" !== type &&
-          "body" !== type &&
-          !shouldSetTextContent(type, fiber.memoizedProps))
-      )
-        for (type = nextHydratableInstance; type; )
-          deleteHydratableInstance(fiber, type),
-            (type = getNextHydratableSibling(type));
-      popToNextHostParent(fiber);
-      nextHydratableInstance = hydrationParentFiber
-        ? getNextHydratableSibling(fiber.stateNode)
-        : null;
-      return !0;
-    }
-  };
-}
-function ReactFiberLegacyContext(stack) {
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    workInProgress = workInProgress.stateNode;
-    workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    workInProgress.__reactInternalMemoizedMaskedChildContext = maskedContext;
-  }
-  function isContextProvider(fiber) {
-    return 2 === fiber.tag && null != fiber.type.childContextTypes;
-  }
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode,
-      childContextTypes = fiber.type.childContextTypes;
-    if ("function" !== typeof instance.getChildContext) return parentContext;
-    instance = instance.getChildContext();
-    for (var contextKey in instance)
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
-      );
-    return Object.assign({}, parentContext, instance);
-  }
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop,
-    contextStackCursor = createCursor(emptyObject),
-    didPerformWorkStackCursor = createCursor(!1),
-    previousContext = emptyObject;
-  return {
-    getUnmaskedContext: function(workInProgress) {
-      return isContextProvider(workInProgress)
-        ? previousContext
-        : contextStackCursor.current;
-    },
-    cacheContext: cacheContext,
-    getMaskedContext: function(workInProgress, unmaskedContext) {
-      var contextTypes = workInProgress.type.contextTypes;
-      if (!contextTypes) return emptyObject;
-      var instance = workInProgress.stateNode;
-      if (
-        instance &&
-        instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-      )
-        return instance.__reactInternalMemoizedMaskedChildContext;
-      var context = {},
-        key;
-      for (key in contextTypes) context[key] = unmaskedContext[key];
-      instance && cacheContext(workInProgress, unmaskedContext, context);
-      return context;
-    },
-    hasContextChanged: function() {
-      return didPerformWorkStackCursor.current;
-    },
-    isContextConsumer: function(fiber) {
-      return 2 === fiber.tag && null != fiber.type.contextTypes;
-    },
-    isContextProvider: isContextProvider,
-    popContextProvider: function(fiber) {
-      isContextProvider(fiber) &&
-        (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
-    },
-    popTopLevelContextObject: function(fiber) {
-      pop(didPerformWorkStackCursor, fiber);
-      pop(contextStackCursor, fiber);
-    },
-    pushTopLevelContextObject: function(fiber, context, didChange) {
-      invariant(
-        null == contextStackCursor.cursor,
-        "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
-      );
-      push(contextStackCursor, context, fiber);
-      push(didPerformWorkStackCursor, didChange, fiber);
-    },
-    processChildContext: processChildContext,
-    pushContextProvider: function(workInProgress) {
-      if (!isContextProvider(workInProgress)) return !1;
-      var instance = workInProgress.stateNode;
-      instance =
-        (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-        emptyObject;
-      previousContext = contextStackCursor.current;
-      push(contextStackCursor, instance, workInProgress);
-      push(
-        didPerformWorkStackCursor,
-        didPerformWorkStackCursor.current,
-        workInProgress
-      );
-      return !0;
-    },
-    invalidateContextProvider: function(workInProgress, didChange) {
-      var instance = workInProgress.stateNode;
-      invariant(
-        instance,
-        "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
-      );
-      if (didChange) {
-        var mergedContext = processChildContext(
-          workInProgress,
-          previousContext
-        );
-        instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-        pop(didPerformWorkStackCursor, workInProgress);
-        pop(contextStackCursor, workInProgress);
-        push(contextStackCursor, mergedContext, workInProgress);
-      } else pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    },
-    findCurrentUnmaskedContext: function(fiber) {
-      for (
-        invariant(
-          2 === isFiberMountedImpl(fiber) && 2 === fiber.tag,
-          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
-        );
-        3 !== fiber.tag;
-
-      ) {
-        if (isContextProvider(fiber))
-          return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber["return"];
-        invariant(
-          fiber,
-          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
-        );
-      }
-      return fiber.stateNode.context;
-    }
-  };
-}
-function ReactFiberNewContext(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop,
-    providerCursor = createCursor(null),
-    valueCursor = createCursor(null),
-    changedBitsCursor = createCursor(0);
-  return {
-    pushProvider: function(providerFiber) {
-      var context = providerFiber.type._context;
-      push(changedBitsCursor, context._changedBits, providerFiber);
-      push(valueCursor, context._currentValue, providerFiber);
-      push(providerCursor, providerFiber, providerFiber);
-      context._currentValue = providerFiber.pendingProps.value;
-      context._changedBits = providerFiber.stateNode;
-    },
-    popProvider: function(providerFiber) {
-      var changedBits = changedBitsCursor.current,
-        currentValue = valueCursor.current;
-      pop(providerCursor, providerFiber);
-      pop(valueCursor, providerFiber);
-      pop(changedBitsCursor, providerFiber);
-      providerFiber = providerFiber.type._context;
-      providerFiber._currentValue = currentValue;
-      providerFiber._changedBits = changedBits;
-    }
-  };
-}
-function ReactFiberStack() {
-  var valueStack = [],
-    index = -1;
-  return {
-    createCursor: function(defaultValue) {
-      return { current: defaultValue };
-    },
-    isEmpty: function() {
-      return -1 === index;
-    },
-    pop: function(cursor) {
-      0 > index ||
-        ((cursor.current = valueStack[index]),
-        (valueStack[index] = null),
-        index--);
-    },
-    push: function(cursor, value) {
-      index++;
-      valueStack[index] = cursor.current;
-      cursor.current = value;
-    },
-    checkThatStackIsEmpty: function() {},
-    resetStackAfterFatalErrorInDev: function() {}
-  };
-}
-function ReactFiberScheduler(config) {
-  function resetStack() {
-    if (null !== nextUnitOfWork)
-      for (
-        var interruptedWork = nextUnitOfWork["return"];
-        null !== interruptedWork;
-
-      )
-        unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork["return"]);
-    nextRoot = null;
-    nextRenderExpirationTime = 0;
-    nextUnitOfWork = null;
-    isRootReadyForCommit = !1;
-  }
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      null !== legacyErrorBoundariesThatAlreadyFailed &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
-  }
-  function completeUnitOfWork(workInProgress$jscomp$0) {
-    for (;;) {
-      var current = workInProgress$jscomp$0.alternate,
-        returnFiber = workInProgress$jscomp$0["return"],
-        siblingFiber = workInProgress$jscomp$0.sibling;
-      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
-        current = completeWork(
-          current,
-          workInProgress$jscomp$0,
-          nextRenderExpirationTime
-        );
-        var workInProgress = workInProgress$jscomp$0;
-        if (
-          1073741823 === nextRenderExpirationTime ||
-          1073741823 !== workInProgress.expirationTime
-        ) {
-          b: switch (workInProgress.tag) {
-            case 3:
-            case 2:
-              var newExpirationTime = workInProgress.updateQueue;
-              newExpirationTime =
-                null === newExpirationTime
-                  ? 0
-                  : newExpirationTime.expirationTime;
-              break b;
-            default:
-              newExpirationTime = 0;
-          }
-          for (var child = workInProgress.child; null !== child; )
-            0 !== child.expirationTime &&
-              (0 === newExpirationTime ||
-                newExpirationTime > child.expirationTime) &&
-              (newExpirationTime = child.expirationTime),
-              (child = child.sibling);
-          workInProgress.expirationTime = newExpirationTime;
-        }
-        if (null !== current) return current;
-        null !== returnFiber &&
-          0 === (returnFiber.effectTag & 512) &&
-          (null === returnFiber.firstEffect &&
-            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
-          null !== workInProgress$jscomp$0.lastEffect &&
-            (null !== returnFiber.lastEffect &&
-              (returnFiber.lastEffect.nextEffect =
-                workInProgress$jscomp$0.firstEffect),
-            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
-          1 < workInProgress$jscomp$0.effectTag &&
-            (null !== returnFiber.lastEffect
-              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
-              : (returnFiber.firstEffect = workInProgress$jscomp$0),
-            (returnFiber.lastEffect = workInProgress$jscomp$0)));
-        if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
-        else {
-          isRootReadyForCommit = !0;
-          break;
-        }
-      } else {
-        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
-        if (null !== workInProgress$jscomp$0)
-          return (
-            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
-          );
-        null !== returnFiber &&
-          ((returnFiber.firstEffect = returnFiber.lastEffect = null),
-          (returnFiber.effectTag |= 512));
-        if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
-        else break;
-      }
-    }
-    return null;
-  }
-  function performUnitOfWork(workInProgress) {
-    var next = beginWork(
-      workInProgress.alternate,
-      workInProgress,
-      nextRenderExpirationTime
-    );
-    null === next && (next = completeUnitOfWork(workInProgress));
-    ReactCurrentOwner.current = null;
-    return next;
-  }
-  function renderRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
-    );
-    isWorking = !0;
-    if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      null === nextUnitOfWork
-    )
-      resetStack(),
-        (nextRoot = root),
-        (nextRenderExpirationTime = expirationTime),
-        (nextUnitOfWork = createWorkInProgress(
-          nextRoot.current,
-          null,
-          nextRenderExpirationTime
-        )),
-        (root.pendingCommitExpirationTime = 0);
-    var didFatal = !1;
-    do {
-      try {
-        if (isAsync)
-          for (; null !== nextUnitOfWork && !shouldYield(); )
-            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-        else
-          for (; null !== nextUnitOfWork; )
-            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      } catch (thrownValue) {
-        if (null === nextUnitOfWork) {
-          didFatal = !0;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        isAsync = nextUnitOfWork;
-        var returnFiber = isAsync["return"];
-        if (null === returnFiber) {
-          didFatal = !0;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        throwException(returnFiber, isAsync, thrownValue);
-        nextUnitOfWork = completeUnitOfWork(isAsync);
-      }
-      break;
-    } while (1);
-    isWorking = !1;
-    if (didFatal || null !== nextUnitOfWork) return null;
-    if (isRootReadyForCommit)
-      return (
-        (root.pendingCommitExpirationTime = expirationTime),
-        root.current.alternate
-      );
-    invariant(
-      !1,
-      "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    sourceFiber = {
-      value: value,
-      source: sourceFiber,
-      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-    };
-    insertUpdateIntoFiber(boundaryFiber, {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: sourceFiber,
-      next: null
-    });
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-  function onCommitPhaseError(fiber$jscomp$0, error) {
-    a: {
-      invariant(
-        !isWorking || isCommitting,
-        "dispatch: Cannot dispatch during the render phase."
-      );
-      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
-        switch (fiber.tag) {
-          case 2:
-            var instance = fiber.stateNode;
-            if (
-              "function" === typeof fiber.type.getDerivedStateFromCatch ||
-              ("function" === typeof instance.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(instance))
-            ) {
-              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-              fiber$jscomp$0 = void 0;
-              break a;
-            }
-            break;
-          case 3:
-            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-            fiber$jscomp$0 = void 0;
-            break a;
-        }
-        fiber = fiber["return"];
-      }
-      3 === fiber$jscomp$0.tag &&
-        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
-      fiber$jscomp$0 = void 0;
-    }
-    return fiber$jscomp$0;
-  }
-  function computeExpirationForFiber(fiber) {
-    fiber =
-      0 !== expirationContext
-        ? expirationContext
-        : isWorking
-          ? isCommitting ? 1 : nextRenderExpirationTime
-          : fiber.mode & 1
-            ? isBatchingInteractiveUpdates
-              ? 10 * ((((recalculateCurrentTime() + 15) / 10) | 0) + 1)
-              : 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1)
-            : 1;
-    isBatchingInteractiveUpdates &&
-      (0 === lowestPendingInteractiveExpirationTime ||
-        fiber > lowestPendingInteractiveExpirationTime) &&
-      (lowestPendingInteractiveExpirationTime = fiber);
-    return fiber;
-  }
-  function scheduleWork(fiber, expirationTime) {
-    a: {
-      for (; null !== fiber; ) {
-        if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
-          fiber.expirationTime = expirationTime;
-        null !== fiber.alternate &&
-          (0 === fiber.alternate.expirationTime ||
-            fiber.alternate.expirationTime > expirationTime) &&
-          (fiber.alternate.expirationTime = expirationTime);
-        if (null === fiber["return"])
-          if (3 === fiber.tag) {
-            var root = fiber.stateNode;
-            !isWorking &&
-              0 !== nextRenderExpirationTime &&
-              expirationTime < nextRenderExpirationTime &&
-              resetStack();
-            (isWorking && !isCommitting && nextRoot === root) ||
-              requestWork(root, expirationTime);
-            nestedUpdateCount > NESTED_UPDATE_LIMIT &&
-              invariant(
-                !1,
-                "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
-              );
-          } else {
-            expirationTime = void 0;
-            break a;
-          }
-        fiber = fiber["return"];
-      }
-      expirationTime = void 0;
-    }
-    return expirationTime;
-  }
-  function recalculateCurrentTime() {
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
-  }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = 1;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (0 !== callbackExpirationTime) {
-      if (expirationTime > callbackExpirationTime) return;
-      cancelDeferredCallback(callbackID);
-    }
-    var currentMs = now() - originalStartTimeMs;
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: 10 * (expirationTime - 2) - currentMs
-    });
-  }
-  function requestWork(root, expirationTime) {
-    if (null === root.nextScheduledRoot)
-      (root.remainingExpirationTime = expirationTime),
-        null === lastScheduledRoot
-          ? ((firstScheduledRoot = lastScheduledRoot = root),
-            (root.nextScheduledRoot = root))
-          : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
-            (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
-    else {
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        expirationTime < remainingExpirationTime
-      )
-        root.remainingExpirationTime = expirationTime;
-    }
-    isRendering ||
-      (isBatchingUpdates
-        ? isUnbatchingUpdates &&
-          ((nextFlushedRoot = root),
-          (nextFlushedExpirationTime = 1),
-          performWorkOnRoot(root, 1, !1))
-        : 1 === expirationTime
-          ? performSyncWork()
-          : scheduleCallbackWithExpiration(expirationTime));
-  }
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = 0,
-      highestPriorityRoot = null;
-    if (null !== lastScheduledRoot)
-      for (
-        var previousScheduledRoot = lastScheduledRoot,
-          root = firstScheduledRoot;
-        null !== root;
-
-      ) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (0 === remainingExpirationTime) {
-          invariant(
-            null !== previousScheduledRoot && null !== lastScheduledRoot,
-            "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
-          );
-          if (root === root.nextScheduledRoot) {
-            firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot)
-            (firstScheduledRoot = remainingExpirationTime =
-              root.nextScheduledRoot),
-              (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
-              (root.nextScheduledRoot = null);
-          else if (root === lastScheduledRoot) {
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else
-            (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
-              (root.nextScheduledRoot = null);
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            0 === highestPriorityWork ||
-            remainingExpirationTime < highestPriorityWork
-          )
-            (highestPriorityWork = remainingExpirationTime),
-              (highestPriorityRoot = root);
-          if (root === lastScheduledRoot) break;
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
-        }
-      }
-    previousScheduledRoot = nextFlushedRoot;
-    null !== previousScheduledRoot &&
-    previousScheduledRoot === highestPriorityRoot &&
-    1 === highestPriorityWork
-      ? nestedUpdateCount++
-      : (nestedUpdateCount = 0);
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
-  }
-  function performAsyncWork(dl) {
-    performWork(0, !0, dl);
-  }
-  function performSyncWork() {
-    performWork(1, !1, null);
-  }
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
-    findHighestPriorityRoot();
-    if (isAsync)
-      for (
-        ;
-        null !== nextFlushedRoot &&
-        0 !== nextFlushedExpirationTime &&
-        (0 === minExpirationTime ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime);
-
-      )
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        ),
-          findHighestPriorityRoot();
-    else
-      for (
-        ;
-        null !== nextFlushedRoot &&
-        0 !== nextFlushedExpirationTime &&
-        (0 === minExpirationTime ||
-          minExpirationTime >= nextFlushedExpirationTime);
-
-      )
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
-          findHighestPriorityRoot();
-    null !== deadline && ((callbackExpirationTime = 0), (callbackID = -1));
-    0 !== nextFlushedExpirationTime &&
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
-    deadline = null;
-    deadlineDidExpire = !1;
-    finishRendering();
-  }
-  function finishRendering() {
-    nestedUpdateCount = 0;
-    if (null !== completedBatches) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          hasUnhandledError ||
-            ((hasUnhandledError = !0), (unhandledError = error));
-        }
-      }
-    }
-    if (hasUnhandledError)
-      throw ((batches = unhandledError),
-      (unhandledError = null),
-      (hasUnhandledError = !1),
-      batches);
-  }
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
-    );
-    isRendering = !0;
-    isAsync
-      ? ((isAsync = root.finishedWork),
-        null !== isAsync
-          ? completeRoot(root, isAsync, expirationTime)
-          : ((root.finishedWork = null),
-            (isAsync = renderRoot(root, expirationTime, !0)),
-            null !== isAsync &&
-              (shouldYield()
-                ? (root.finishedWork = isAsync)
-                : completeRoot(root, isAsync, expirationTime))))
-      : ((isAsync = root.finishedWork),
-        null !== isAsync
-          ? completeRoot(root, isAsync, expirationTime)
-          : ((root.finishedWork = null),
-            (isAsync = renderRoot(root, expirationTime, !1)),
-            null !== isAsync && completeRoot(root, isAsync, expirationTime)));
-    isRendering = !1;
-  }
-  function completeRoot(root, finishedWork, expirationTime) {
-    var firstBatch = root.firstBatch;
-    if (
-      null !== firstBatch &&
-      firstBatch._expirationTime <= expirationTime &&
-      (null === completedBatches
-        ? (completedBatches = [firstBatch])
-        : completedBatches.push(firstBatch),
-      firstBatch._defer)
-    ) {
-      root.finishedWork = finishedWork;
-      root.remainingExpirationTime = 0;
-      return;
-    }
-    root.finishedWork = null;
-    isCommitting = isWorking = !0;
-    expirationTime = finishedWork.stateNode;
-    invariant(
-      expirationTime.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
-    );
-    firstBatch = expirationTime.pendingCommitExpirationTime;
-    invariant(
-      0 !== firstBatch,
-      "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    expirationTime.pendingCommitExpirationTime = 0;
-    var currentTime = recalculateCurrentTime();
-    ReactCurrentOwner.current = null;
-    if (1 < finishedWork.effectTag)
-      if (null !== finishedWork.lastEffect) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        var firstEffect = finishedWork.firstEffect;
-      } else firstEffect = finishedWork;
-    else firstEffect = finishedWork.firstEffect;
-    prepareForCommit(expirationTime.containerInfo);
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      var didError = !1,
-        error = void 0;
-      try {
-        for (; null !== nextEffect; )
-          nextEffect.effectTag & 2048 &&
-            commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
-            (nextEffect = nextEffect.nextEffect);
-      } catch (e) {
-        (didError = !0), (error = e);
-      }
-      didError &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, error),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      didError = !1;
-      error = void 0;
-      try {
-        for (; null !== nextEffect; ) {
-          var effectTag = nextEffect.effectTag;
-          effectTag & 16 && commitResetTextContent(nextEffect);
-          if (effectTag & 128) {
-            var current = nextEffect.alternate;
-            null !== current && commitDetachRef(current);
-          }
-          switch (effectTag & 14) {
-            case 2:
-              commitPlacement(nextEffect);
-              nextEffect.effectTag &= -3;
-              break;
-            case 6:
-              commitPlacement(nextEffect);
-              nextEffect.effectTag &= -3;
-              commitWork(nextEffect.alternate, nextEffect);
-              break;
-            case 4:
-              commitWork(nextEffect.alternate, nextEffect);
-              break;
-            case 8:
-              commitDeletion(nextEffect);
-          }
-          nextEffect = nextEffect.nextEffect;
-        }
-      } catch (e) {
-        (didError = !0), (error = e);
-      }
-      didError &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, error),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    resetAfterCommit(expirationTime.containerInfo);
-    expirationTime.current = finishedWork;
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      effectTag = !1;
-      current = void 0;
-      try {
-        for (
-          firstEffect = expirationTime,
-            didError = currentTime,
-            error = firstBatch;
-          null !== nextEffect;
-
-        ) {
-          var effectTag$jscomp$0 = nextEffect.effectTag;
-          effectTag$jscomp$0 & 36 &&
-            commitLifeCycles(
-              firstEffect,
-              nextEffect.alternate,
-              nextEffect,
-              didError,
-              error
-            );
-          effectTag$jscomp$0 & 256 &&
-            commitErrorLogging(nextEffect, onUncaughtError);
-          effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
-          var next = nextEffect.nextEffect;
-          nextEffect.nextEffect = null;
-          nextEffect = next;
-        }
-      } catch (e) {
-        (effectTag = !0), (current = e);
-      }
-      effectTag &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, current),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    isWorking = isCommitting = !1;
-    "function" === typeof onCommitRoot && onCommitRoot(finishedWork.stateNode);
-    finishedWork = expirationTime.current.expirationTime;
-    0 === finishedWork && (legacyErrorBoundariesThatAlreadyFailed = null);
-    root.remainingExpirationTime = finishedWork;
-  }
-  function shouldYield() {
-    return null === deadline ||
-      deadline.timeRemaining() > timeHeuristicForUnitOfWork
-      ? !1
-      : (deadlineDidExpire = !0);
-  }
-  function onUncaughtError(error) {
-    invariant(
-      null !== nextFlushedRoot,
-      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    nextFlushedRoot.remainingExpirationTime = 0;
-    hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
-  }
-  var stack = ReactFiberStack(),
-    hostContext = ReactFiberHostContext(config, stack),
-    legacyContext = ReactFiberLegacyContext(stack);
-  stack = ReactFiberNewContext(stack);
-  var hydrationContext = ReactFiberHydrationContext(config),
-    beginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      stack,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber
-    ).beginWork,
-    completeWork = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      stack,
-      hydrationContext
-    ).completeWork;
-  hostContext = ReactFiberUnwindWork(
-    hostContext,
-    legacyContext,
-    stack,
-    scheduleWork,
-    isAlreadyFailedLegacyErrorBoundary
-  );
-  var throwException = hostContext.throwException,
-    unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork;
-  hostContext = ReactFiberCommitWork(
-    config,
-    onCommitPhaseError,
-    scheduleWork,
-    computeExpirationForFiber,
-    function(instance) {
-      null === legacyErrorBoundariesThatAlreadyFailed
-        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-    },
-    recalculateCurrentTime
-  );
-  var commitBeforeMutationLifeCycles =
-      hostContext.commitBeforeMutationLifeCycles,
-    commitResetTextContent = hostContext.commitResetTextContent,
-    commitPlacement = hostContext.commitPlacement,
-    commitDeletion = hostContext.commitDeletion,
-    commitWork = hostContext.commitWork,
-    commitLifeCycles = hostContext.commitLifeCycles,
-    commitErrorLogging = hostContext.commitErrorLogging,
-    commitAttachRef = hostContext.commitAttachRef,
-    commitDetachRef = hostContext.commitDetachRef,
-    now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit,
-    originalStartTimeMs = now(),
-    mostRecentCurrentTime = 2,
-    mostRecentCurrentTimeMs = originalStartTimeMs,
-    lastUniqueAsyncExpiration = 0,
-    expirationContext = 0,
-    isWorking = !1,
-    nextUnitOfWork = null,
-    nextRoot = null,
-    nextRenderExpirationTime = 0,
-    nextEffect = null,
-    isCommitting = !1,
-    isRootReadyForCommit = !1,
-    legacyErrorBoundariesThatAlreadyFailed = null,
-    firstScheduledRoot = null,
-    lastScheduledRoot = null,
-    callbackExpirationTime = 0,
-    callbackID = -1,
-    isRendering = !1,
-    nextFlushedRoot = null,
-    nextFlushedExpirationTime = 0,
-    lowestPendingInteractiveExpirationTime = 0,
-    deadlineDidExpire = !1,
-    hasUnhandledError = !1,
-    unhandledError = null,
-    deadline = null,
-    isBatchingUpdates = !1,
-    isUnbatchingUpdates = !1,
-    isBatchingInteractiveUpdates = !1,
-    completedBatches = null,
-    NESTED_UPDATE_LIMIT = 1e3,
-    nestedUpdateCount = 0,
-    timeHeuristicForUnitOfWork = 1;
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: function(root, expirationTime) {
-      invariant(
-        !isRendering,
-        "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
-      );
-      nextFlushedRoot = root;
-      nextFlushedExpirationTime = expirationTime;
-      performWorkOnRoot(root, expirationTime, !1);
-      performSyncWork();
-      finishRendering();
-    },
-    batchedUpdates: function(fn, a) {
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        return fn(a);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates) ||
-          isRendering ||
-          performSyncWork();
-      }
-    },
-    unbatchedUpdates: function(fn, a) {
-      if (isBatchingUpdates && !isUnbatchingUpdates) {
-        isUnbatchingUpdates = !0;
-        try {
-          return fn(a);
-        } finally {
-          isUnbatchingUpdates = !1;
-        }
-      }
-      return fn(a);
-    },
-    flushSync: function(fn, a) {
-      invariant(
-        !isRendering,
-        "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
-      );
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        return syncUpdates(fn, a);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates), performSyncWork();
-      }
-    },
-    flushControlled: function(fn) {
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        syncUpdates(fn);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates) ||
-          isRendering ||
-          performWork(1, !1, null);
-      }
-    },
-    deferredUpdates: function(fn) {
-      var previousExpirationContext = expirationContext;
-      expirationContext =
-        25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
-      try {
-        return fn();
-      } finally {
-        expirationContext = previousExpirationContext;
-      }
-    },
-    syncUpdates: syncUpdates,
-    interactiveUpdates: function(fn, a, b) {
-      if (isBatchingInteractiveUpdates) return fn(a, b);
-      isBatchingUpdates ||
-        isRendering ||
-        0 === lowestPendingInteractiveExpirationTime ||
-        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
-        (lowestPendingInteractiveExpirationTime = 0));
-      var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
-        previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = isBatchingInteractiveUpdates = !0;
-      try {
-        return fn(a, b);
-      } finally {
-        (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
-          (isBatchingUpdates = previousIsBatchingUpdates) ||
-            isRendering ||
-            performSyncWork();
-      }
-    },
-    flushInteractiveUpdates: function() {
-      isRendering ||
-        0 === lowestPendingInteractiveExpirationTime ||
-        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
-        (lowestPendingInteractiveExpirationTime = 0));
-    },
-    computeUniqueAsyncExpiration: function() {
-      var result = 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
-      result <= lastUniqueAsyncExpiration &&
-        (result = lastUniqueAsyncExpiration + 1);
-      return (lastUniqueAsyncExpiration = result);
-    },
-    legacyContext: legacyContext
-  };
-}
-function ReactFiberReconciler$1(config) {
-  function updateContainerAtExpirationTime(
-    element,
-    container,
-    parentComponent,
-    currentTime,
-    expirationTime,
-    callback
-  ) {
-    currentTime = container.current;
-    if (parentComponent) {
-      parentComponent = parentComponent._reactInternalFiber;
-      var parentContext = findCurrentUnmaskedContext(parentComponent);
-      parentComponent = isContextProvider(parentComponent)
-        ? processChildContext(parentComponent, parentContext)
-        : parentContext;
-    } else parentComponent = emptyObject;
-    null === container.context
-      ? (container.context = parentComponent)
-      : (container.pendingContext = parentComponent);
-    container = callback;
-    insertUpdateIntoFiber(currentTime, {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: void 0 === container ? null : container,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: null,
-      next: null
-    });
-    scheduleWork(currentTime, expirationTime);
-    return expirationTime;
-  }
-  var getPublicInstance = config.getPublicInstance;
-  config = ReactFiberScheduler(config);
-  var recalculateCurrentTime = config.recalculateCurrentTime,
-    computeExpirationForFiber = config.computeExpirationForFiber,
-    scheduleWork = config.scheduleWork,
-    legacyContext = config.legacyContext,
-    findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
-  return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
-      containerInfo = {
-        current: isAsync,
-        containerInfo: containerInfo,
-        pendingChildren: null,
-        pendingCommitExpirationTime: 0,
-        finishedWork: null,
-        context: null,
-        pendingContext: null,
-        hydrate: hydrate,
-        remainingExpirationTime: 0,
-        firstBatch: null,
-        nextScheduledRoot: null
-      };
-      return (isAsync.stateNode = containerInfo);
-    },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current,
-        currentTime = recalculateCurrentTime();
-      current = computeExpirationForFiber(current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        current,
-        callback
-      );
-    },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
-    ) {
-      var currentTime = recalculateCurrentTime();
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        expirationTime,
-        callback
-      );
-    },
-    flushRoot: config.flushRoot,
-    requestWork: config.requestWork,
-    computeUniqueAsyncExpiration: config.computeUniqueAsyncExpiration,
-    batchedUpdates: config.batchedUpdates,
-    unbatchedUpdates: config.unbatchedUpdates,
-    deferredUpdates: config.deferredUpdates,
-    syncUpdates: config.syncUpdates,
-    interactiveUpdates: config.interactiveUpdates,
-    flushInteractiveUpdates: config.flushInteractiveUpdates,
-    flushControlled: config.flushControlled,
-    flushSync: config.flushSync,
-    getPublicRootInstance: function(container) {
-      container = container.current;
-      if (!container.child) return null;
-      switch (container.child.tag) {
-        case 5:
-          return getPublicInstance(container.child.stateNode);
-        default:
-          return container.child.stateNode;
-      }
-    },
-    findHostInstance: function(component) {
-      var fiber = component._reactInternalFiber;
-      void 0 === fiber &&
-        ("function" === typeof component.render
-          ? invariant(!1, "Unable to find node on an unmounted component.")
-          : invariant(
-              !1,
-              "Argument appears to not be a ReactComponent. Keys: %s",
-              Object.keys(component)
-            ));
-      component = findCurrentHostFiber(fiber);
-      return null === component ? null : component.stateNode;
-    },
-    findHostInstanceWithNoPortals: function(fiber) {
-      fiber = findCurrentHostFiberWithNoPortals(fiber);
-      return null === fiber ? null : fiber.stateNode;
-    },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            fiber = findCurrentHostFiber(fiber);
-            return null === fiber ? null : fiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            return findFiberByHostInstance
-              ? findFiberByHostInstance(instance)
-              : null;
-          }
-        })
-      );
-    }
-  };
-}
-var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
-  ReactFiberReconciler$3 =
-    (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
-    ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3["default"]
-    ? ReactFiberReconciler$3["default"]
-    : ReactFiberReconciler$3,
-  nextReactTag = 2,
-  ReactFabricHostComponent = (function() {
-    function ReactFabricHostComponent(tag, viewConfig, props) {
-      if (!(this instanceof ReactFabricHostComponent))
-        throw new TypeError("Cannot call a class as a function");
-      this._nativeTag = tag;
-      this.viewConfig = viewConfig;
-      this.currentProps = props;
-    }
-    ReactFabricHostComponent.prototype.blur = function() {
-      TextInputState.blurTextInput(this._nativeTag);
-    };
-    ReactFabricHostComponent.prototype.focus = function() {
-      TextInputState.focusTextInput(this._nativeTag);
-    };
-    ReactFabricHostComponent.prototype.measure = function(callback) {
-      UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-    };
-    ReactFabricHostComponent.prototype.measureInWindow = function(callback) {
-      UIManager.measureInWindow(
-        this._nativeTag,
-        mountSafeCallback(this, callback)
-      );
-    };
-    ReactFabricHostComponent.prototype.measureLayout = function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail
-    ) {
-      UIManager.measureLayout(
-        this._nativeTag,
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    };
-    ReactFabricHostComponent.prototype.setNativeProps = function(nativeProps) {
-      nativeProps = diffProperties(
-        null,
-        emptyObject$1,
-        nativeProps,
-        this.viewConfig.validAttributes
-      );
-      null != nativeProps &&
-        UIManager.updateView(
-          this._nativeTag,
-          this.viewConfig.uiViewClassName,
-          nativeProps
-        );
-    };
-    return ReactFabricHostComponent;
-  })(),
-  ReactFabricRenderer = reactReconciler({
-    appendInitialChild: function(parentInstance, child) {
-      FabricUIManager.appendChild(parentInstance.node, child.node);
-    },
-    createInstance: function(
-      type,
-      props,
-      rootContainerInstance,
-      hostContext,
-      internalInstanceHandle
-    ) {
-      hostContext = nextReactTag;
-      nextReactTag += 2;
-      type = ReactNativeViewConfigRegistry.get(type);
-      var updatePayload = diffProperties(
-        null,
-        emptyObject$1,
-        props,
-        type.validAttributes
-      );
-      rootContainerInstance = FabricUIManager.createNode(
-        hostContext,
-        type.uiViewClassName,
-        rootContainerInstance,
-        updatePayload,
-        internalInstanceHandle
-      );
-      props = new ReactFabricHostComponent(hostContext, type, props);
-      return { node: rootContainerInstance, canonical: props };
-    },
-    createTextInstance: function(
-      text,
-      rootContainerInstance,
-      hostContext,
-      internalInstanceHandle
-    ) {
-      hostContext = nextReactTag;
-      nextReactTag += 2;
-      return {
-        node: FabricUIManager.createNode(
-          hostContext,
-          "RCTRawText",
-          rootContainerInstance,
-          { text: text },
-          internalInstanceHandle
-        )
-      };
-    },
-    finalizeInitialChildren: function() {
-      return !1;
-    },
-    getRootHostContext: function() {
-      return emptyObject;
-    },
-    getChildHostContext: function() {
-      return emptyObject;
-    },
-    getPublicInstance: function(instance) {
-      return instance.canonical;
-    },
-    now: now,
-    prepareForCommit: function() {},
-    prepareUpdate: function(instance, type, oldProps, newProps) {
-      return diffProperties(
-        null,
-        oldProps,
-        newProps,
-        instance.canonical.viewConfig.validAttributes
-      );
-    },
-    resetAfterCommit: function() {},
-    scheduleDeferredCallback: function(callback) {
-      scheduledCallback = callback;
-      return setTimeout(setTimeoutCallback, 1);
-    },
-    cancelDeferredCallback: function(callbackID) {
-      scheduledCallback = null;
-      clearTimeout(callbackID);
-    },
-    shouldDeprioritizeSubtree: function() {
-      return !1;
-    },
-    shouldSetTextContent: function() {
-      return !1;
-    },
-    persistence: {
-      cloneInstance: function(
-        instance,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        internalInstanceHandle,
-        keepChildren
-      ) {
-        type = instance.node;
-        return {
-          node: keepChildren
-            ? null !== updatePayload
-              ? FabricUIManager.cloneNodeWithNewProps(type, updatePayload)
-              : FabricUIManager.cloneNode(type)
-            : null !== updatePayload
-              ? FabricUIManager.cloneNodeWithNewChildrenAndProps(
-                  type,
-                  updatePayload
-                )
-              : FabricUIManager.cloneNodeWithNewChildren(type),
-          canonical: instance.canonical
-        };
-      },
-      createContainerChildSet: function(container) {
-        return FabricUIManager.createChildSet(container);
-      },
-      appendChildToContainerChildSet: function(childSet, child) {
-        FabricUIManager.appendChildToSet(childSet, child.node);
-      },
-      finalizeContainerChildren: function(container, newChildren) {
-        FabricUIManager.completeRoot(container, newChildren);
-      },
-      replaceContainerChildren: function() {}
-    }
-  }),
-  getInspectorDataForViewTag = void 0;
-getInspectorDataForViewTag = function() {
-  invariant(!1, "getInspectorDataForViewTag() is not available in production");
-};
-var findHostInstance = ReactFabricRenderer.findHostInstance;
-function findNodeHandle(componentOrHandle) {
-  if (null == componentOrHandle) return null;
-  if ("number" === typeof componentOrHandle) return componentOrHandle;
-  if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
-  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
-    return componentOrHandle.canonical._nativeTag;
-  componentOrHandle = findHostInstance(componentOrHandle);
-  return null == componentOrHandle
-    ? componentOrHandle
-    : componentOrHandle.canonical
-      ? componentOrHandle.canonical._nativeTag
-      : componentOrHandle._nativeTag;
-}
-var roots = new Map(),
-  ReactFabric = {
-    NativeComponent: (function(findNodeHandle, findHostInstance) {
-      return (function(_React$Component) {
-        function ReactNativeComponent() {
-          if (!(this instanceof ReactNativeComponent))
-            throw new TypeError("Cannot call a class as a function");
-          var call = _React$Component.apply(this, arguments);
-          if (!this)
-            throw new ReferenceError(
-              "this hasn't been initialised - super() hasn't been called"
-            );
-          return !call ||
-            ("object" !== typeof call && "function" !== typeof call)
-            ? this
-            : call;
-        }
-        _inherits(ReactNativeComponent, _React$Component);
-        ReactNativeComponent.prototype.blur = function() {
-          TextInputState.blurTextInput(findNodeHandle(this));
-        };
-        ReactNativeComponent.prototype.focus = function() {
-          TextInputState.focusTextInput(findNodeHandle(this));
-        };
-        ReactNativeComponent.prototype.measure = function(callback) {
-          UIManager.measure(
-            findNodeHandle(this),
-            mountSafeCallback(this, callback)
-          );
-        };
-        ReactNativeComponent.prototype.measureInWindow = function(callback) {
-          UIManager.measureInWindow(
-            findNodeHandle(this),
-            mountSafeCallback(this, callback)
-          );
-        };
-        ReactNativeComponent.prototype.measureLayout = function(
-          relativeToNativeNode,
-          onSuccess,
-          onFail
-        ) {
-          UIManager.measureLayout(
-            findNodeHandle(this),
-            relativeToNativeNode,
-            mountSafeCallback(this, onFail),
-            mountSafeCallback(this, onSuccess)
-          );
-        };
-        ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
-          var maybeInstance = void 0;
-          try {
-            maybeInstance = findHostInstance(this);
-          } catch (error) {}
-          if (null != maybeInstance) {
-            var viewConfig =
-              maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
-            nativeProps = diffProperties(
-              null,
-              emptyObject$1,
-              nativeProps,
-              viewConfig.validAttributes
-            );
-            null != nativeProps &&
-              UIManager.updateView(
-                maybeInstance._nativeTag,
-                viewConfig.uiViewClassName,
-                nativeProps
-              );
-          }
-        };
-        return ReactNativeComponent;
-      })(React.Component);
-    })(findNodeHandle, findHostInstance),
-    findNodeHandle: findNodeHandle,
-    render: function(element, containerTag, callback) {
-      var root = roots.get(containerTag);
-      root ||
-        ((root = ReactFabricRenderer.createContainer(containerTag, !1, !1)),
-        roots.set(containerTag, root));
-      ReactFabricRenderer.updateContainer(element, root, null, callback);
-      return ReactFabricRenderer.getPublicRootInstance(root);
-    },
-    unmountComponentAtNode: function(containerTag) {
-      var root = roots.get(containerTag);
-      root &&
-        ReactFabricRenderer.updateContainer(null, root, null, function() {
-          roots["delete"](containerTag);
-        });
-    },
-    createPortal: function(children, containerTag) {
-      return createPortal(
-        children,
-        containerTag,
-        null,
-        2 < arguments.length && void 0 !== arguments[2] ? arguments[2] : null
-      );
-    },
-    __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
-      NativeMethodsMixin: (function(findNodeHandle, findHostInstance) {
-        return {
-          measure: function(callback) {
-            UIManager.measure(
-              findNodeHandle(this),
-              mountSafeCallback(this, callback)
-            );
-          },
-          measureInWindow: function(callback) {
-            UIManager.measureInWindow(
-              findNodeHandle(this),
-              mountSafeCallback(this, callback)
-            );
-          },
-          measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
-            UIManager.measureLayout(
-              findNodeHandle(this),
-              relativeToNativeNode,
-              mountSafeCallback(this, onFail),
-              mountSafeCallback(this, onSuccess)
-            );
-          },
-          setNativeProps: function(nativeProps) {
-            var maybeInstance = void 0;
-            try {
-              maybeInstance = findHostInstance(this);
-            } catch (error) {}
-            if (null != maybeInstance) {
-              var viewConfig = maybeInstance.viewConfig;
-              nativeProps = diffProperties(
-                null,
-                emptyObject$1,
-                nativeProps,
-                viewConfig.validAttributes
-              );
-              null != nativeProps &&
-                UIManager.updateView(
-                  maybeInstance._nativeTag,
-                  viewConfig.uiViewClassName,
-                  nativeProps
-                );
-            }
-          },
-          focus: function() {
-            TextInputState.focusTextInput(findNodeHandle(this));
-          },
-          blur: function() {
-            TextInputState.blurTextInput(findNodeHandle(this));
-          }
-        };
-      })(findNodeHandle, findHostInstance),
-      ReactNativeComponentTree: ReactNativeComponentTree
-    }
-  };
-ReactFabricRenderer.injectIntoDevTools({
-  findFiberByHostInstance: getInstanceFromTag,
-  getInspectorDataForViewTag: getInspectorDataForViewTag,
-  bundleType: 0,
-  version: "16.3.2",
-  rendererPackageName: "react-native-renderer"
-});
-var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
-  ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
-module.exports = ReactFabric$3["default"]
-  ? ReactFabric$3["default"]
-  : ReactFabric$3;
diff --git a/Libraries/Renderer/fb/ReactFeatureFlags.js b/Libraries/Renderer/fb/ReactFeatureFlags.js
deleted file mode 100644
index 44add71fc5c5..000000000000
--- a/Libraries/Renderer/fb/ReactFeatureFlags.js
+++ /dev/null
@@ -1,18 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @providesModule ReactFeatureFlags
- */
-
-'use strict';
-
-const ReactFeatureFlags = {
-  debugRenderPhaseSideEffects: false,
-  debugRenderPhaseSideEffectsForStrictMode: false,
-  warnAboutDeprecatedLifecycles: true,
-};
-
-module.exports = ReactFeatureFlags;
diff --git a/Libraries/Renderer/fb/ReactNativeRenderer-dev.js b/Libraries/Renderer/fb/ReactNativeRenderer-dev.js
deleted file mode 100644
index bcdfa4c607aa..000000000000
--- a/Libraries/Renderer/fb/ReactNativeRenderer-dev.js
+++ /dev/null
@@ -1,14437 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @noflow
- * @preventMunge
- */
-
-'use strict';
-
-if (__DEV__) {
-  (function() {
-"use strict";
-
-require("InitializeCore");
-var invariant = require("fbjs/lib/invariant");
-var warning = require("fbjs/lib/warning");
-var emptyFunction = require("fbjs/lib/emptyFunction");
-var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
-var UIManager = require("UIManager");
-var RCTEventEmitter = require("RCTEventEmitter");
-var TextInputState = require("TextInputState");
-var deepDiffer = require("deepDiffer");
-var flattenStyle = require("flattenStyle");
-var React = require("react");
-var emptyObject = require("fbjs/lib/emptyObject");
-var shallowEqual = require("fbjs/lib/shallowEqual");
-var ExceptionsManager = require("ExceptionsManager");
-var checkPropTypes = require("prop-types/checkPropTypes");
-var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
-
-var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
-  this._hasCaughtError = false;
-  this._caughtError = null;
-  var funcArgs = Array.prototype.slice.call(arguments, 3);
-  try {
-    func.apply(context, funcArgs);
-  } catch (error) {
-    this._caughtError = error;
-    this._hasCaughtError = true;
-  }
-};
-
-{
-  // In DEV mode, we swap out invokeGuardedCallback for a special version
-  // that plays more nicely with the browser's DevTools. The idea is to preserve
-  // "Pause on exceptions" behavior. Because React wraps all user-provided
-  // functions in invokeGuardedCallback, and the production version of
-  // invokeGuardedCallback uses a try-catch, all user exceptions are treated
-  // like caught exceptions, and the DevTools won't pause unless the developer
-  // takes the extra step of enabling pause on caught exceptions. This is
-  // untintuitive, though, because even though React has caught the error, from
-  // the developer's perspective, the error is uncaught.
-  //
-  // To preserve the expected "Pause on exceptions" behavior, we don't use a
-  // try-catch in DEV. Instead, we synchronously dispatch a fake event to a fake
-  // DOM node, and call the user-provided callback from inside an event handler
-  // for that fake event. If the callback throws, the error is "captured" using
-  // a global event handler. But because the error happens in a different
-  // event loop context, it does not interrupt the normal program flow.
-  // Effectively, this gives us try-catch behavior without actually using
-  // try-catch. Neat!
-
-  // Check that the browser supports the APIs we need to implement our special
-  // DEV version of invokeGuardedCallback
-  if (
-    typeof window !== "undefined" &&
-    typeof window.dispatchEvent === "function" &&
-    typeof document !== "undefined" &&
-    typeof document.createEvent === "function"
-  ) {
-    var fakeNode = document.createElement("react");
-
-    var invokeGuardedCallbackDev = function(
-      name,
-      func,
-      context,
-      a,
-      b,
-      c,
-      d,
-      e,
-      f
-    ) {
-      // If document doesn't exist we know for sure we will crash in this method
-      // when we call document.createEvent(). However this can cause confusing
-      // errors: https://github.com/facebookincubator/create-react-app/issues/3482
-      // So we preemptively throw with a better message instead.
-      invariant(
-        typeof document !== "undefined",
-        "The `document` global was defined when React was initialized, but is not " +
-          "defined anymore. This can happen in a test environment if a component " +
-          "schedules an update from an asynchronous callback, but the test has already " +
-          "finished running. To solve this, you can either unmount the component at " +
-          "the end of your test (and ensure that any asynchronous operations get " +
-          "canceled in `componentWillUnmount`), or you can change the test itself " +
-          "to be asynchronous."
-      );
-      var evt = document.createEvent("Event");
-
-      // Keeps track of whether the user-provided callback threw an error. We
-      // set this to true at the beginning, then set it to false right after
-      // calling the function. If the function errors, `didError` will never be
-      // set to false. This strategy works even if the browser is flaky and
-      // fails to call our global error handler, because it doesn't rely on
-      // the error event at all.
-      var didError = true;
-
-      // Create an event handler for our fake event. We will synchronously
-      // dispatch our fake event using `dispatchEvent`. Inside the handler, we
-      // call the user-provided callback.
-      var funcArgs = Array.prototype.slice.call(arguments, 3);
-      function callCallback() {
-        // We immediately remove the callback from event listeners so that
-        // nested `invokeGuardedCallback` calls do not clash. Otherwise, a
-        // nested call would trigger the fake event handlers of any call higher
-        // in the stack.
-        fakeNode.removeEventListener(evtType, callCallback, false);
-        func.apply(context, funcArgs);
-        didError = false;
-      }
-
-      // Create a global error event handler. We use this to capture the value
-      // that was thrown. It's possible that this error handler will fire more
-      // than once; for example, if non-React code also calls `dispatchEvent`
-      // and a handler for that event throws. We should be resilient to most of
-      // those cases. Even if our error event handler fires more than once, the
-      // last error event is always used. If the callback actually does error,
-      // we know that the last error event is the correct one, because it's not
-      // possible for anything else to have happened in between our callback
-      // erroring and the code that follows the `dispatchEvent` call below. If
-      // the callback doesn't error, but the error event was fired, we know to
-      // ignore it because `didError` will be false, as described above.
-      var error = void 0;
-      // Use this to track whether the error event is ever called.
-      var didSetError = false;
-      var isCrossOriginError = false;
-
-      function onError(event) {
-        error = event.error;
-        didSetError = true;
-        if (error === null && event.colno === 0 && event.lineno === 0) {
-          isCrossOriginError = true;
-        }
-      }
-
-      // Create a fake event type.
-      var evtType = "react-" + (name ? name : "invokeguardedcallback");
-
-      // Attach our event handlers
-      window.addEventListener("error", onError);
-      fakeNode.addEventListener(evtType, callCallback, false);
-
-      // Synchronously dispatch our fake event. If the user-provided function
-      // errors, it will trigger our global error handler.
-      evt.initEvent(evtType, false, false);
-      fakeNode.dispatchEvent(evt);
-
-      if (didError) {
-        if (!didSetError) {
-          // The callback errored, but the error event never fired.
-          error = new Error(
-            "An error was thrown inside one of your components, but React " +
-              "doesn't know what it was. This is likely due to browser " +
-              'flakiness. React does its best to preserve the "Pause on ' +
-              'exceptions" behavior of the DevTools, which requires some ' +
-              "DEV-mode only tricks. It's possible that these don't work in " +
-              "your browser. Try triggering the error in production mode, " +
-              "or switching to a modern browser. If you suspect that this is " +
-              "actually an issue with React, please file an issue."
-          );
-        } else if (isCrossOriginError) {
-          error = new Error(
-            "A cross-origin error was thrown. React doesn't have access to " +
-              "the actual error object in development. " +
-              "See https://fb.me/react-crossorigin-error for more information."
-          );
-        }
-        this._hasCaughtError = true;
-        this._caughtError = error;
-      } else {
-        this._hasCaughtError = false;
-        this._caughtError = null;
-      }
-
-      // Remove our event listeners
-      window.removeEventListener("error", onError);
-    };
-
-    invokeGuardedCallback = invokeGuardedCallbackDev;
-  }
-}
-
-var invokeGuardedCallback$1 = invokeGuardedCallback;
-
-var ReactErrorUtils = {
-  // Used by Fiber to simulate a try-catch.
-  _caughtError: null,
-  _hasCaughtError: false,
-
-  // Used by event system to capture/rethrow the first error.
-  _rethrowError: null,
-  _hasRethrowError: false,
-
-  /**
-   * Call a function while guarding against errors that happens within it.
-   * Returns an error if it throws, otherwise null.
-   *
-   * In production, this is implemented using a try-catch. The reason we don't
-   * use a try-catch directly is so that we can swap out a different
-   * implementation in DEV mode.
-   *
-   * @param {String} name of the guard to use for logging or debugging
-   * @param {Function} func The function to invoke
-   * @param {*} context The context to use when calling the function
-   * @param {...*} args Arguments for function
-   */
-  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
-    invokeGuardedCallback$1.apply(ReactErrorUtils, arguments);
-  },
-
-  /**
-   * Same as invokeGuardedCallback, but instead of returning an error, it stores
-   * it in a global so it can be rethrown by `rethrowCaughtError` later.
-   * TODO: See if _caughtError and _rethrowError can be unified.
-   *
-   * @param {String} name of the guard to use for logging or debugging
-   * @param {Function} func The function to invoke
-   * @param {*} context The context to use when calling the function
-   * @param {...*} args Arguments for function
-   */
-  invokeGuardedCallbackAndCatchFirstError: function(
-    name,
-    func,
-    context,
-    a,
-    b,
-    c,
-    d,
-    e,
-    f
-  ) {
-    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
-    if (ReactErrorUtils.hasCaughtError()) {
-      var error = ReactErrorUtils.clearCaughtError();
-      if (!ReactErrorUtils._hasRethrowError) {
-        ReactErrorUtils._hasRethrowError = true;
-        ReactErrorUtils._rethrowError = error;
-      }
-    }
-  },
-
-  /**
-   * During execution of guarded functions we will capture the first error which
-   * we will rethrow to be handled by the top level error handler.
-   */
-  rethrowCaughtError: function() {
-    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
-  },
-
-  hasCaughtError: function() {
-    return ReactErrorUtils._hasCaughtError;
-  },
-
-  clearCaughtError: function() {
-    if (ReactErrorUtils._hasCaughtError) {
-      var error = ReactErrorUtils._caughtError;
-      ReactErrorUtils._caughtError = null;
-      ReactErrorUtils._hasCaughtError = false;
-      return error;
-    } else {
-      invariant(
-        false,
-        "clearCaughtError was called but no error was captured. This error " +
-          "is likely caused by a bug in React. Please file an issue."
-      );
-    }
-  }
-};
-
-var rethrowCaughtError = function() {
-  if (ReactErrorUtils._hasRethrowError) {
-    var error = ReactErrorUtils._rethrowError;
-    ReactErrorUtils._rethrowError = null;
-    ReactErrorUtils._hasRethrowError = false;
-    throw error;
-  }
-};
-
-/**
- * Injectable ordering of event plugins.
- */
-var eventPluginOrder = null;
-
-/**
- * Injectable mapping from names to event plugin modules.
- */
-var namesToPlugins = {};
-
-/**
- * Recomputes the plugin list using the injected plugins and plugin ordering.
- *
- * @private
- */
-function recomputePluginOrdering() {
-  if (!eventPluginOrder) {
-    // Wait until an `eventPluginOrder` is injected.
-    return;
-  }
-  for (var pluginName in namesToPlugins) {
-    var pluginModule = namesToPlugins[pluginName];
-    var pluginIndex = eventPluginOrder.indexOf(pluginName);
-    invariant(
-      pluginIndex > -1,
-      "EventPluginRegistry: Cannot inject event plugins that do not exist in " +
-        "the plugin ordering, `%s`.",
-      pluginName
-    );
-    if (plugins[pluginIndex]) {
-      continue;
-    }
-    invariant(
-      pluginModule.extractEvents,
-      "EventPluginRegistry: Event plugins must implement an `extractEvents` " +
-        "method, but `%s` does not.",
-      pluginName
-    );
-    plugins[pluginIndex] = pluginModule;
-    var publishedEvents = pluginModule.eventTypes;
-    for (var eventName in publishedEvents) {
-      invariant(
-        publishEventForPlugin(
-          publishedEvents[eventName],
-          pluginModule,
-          eventName
-        ),
-        "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
-        eventName,
-        pluginName
-      );
-    }
-  }
-}
-
-/**
- * Publishes an event so that it can be dispatched by the supplied plugin.
- *
- * @param {object} dispatchConfig Dispatch configuration for the event.
- * @param {object} PluginModule Plugin publishing the event.
- * @return {boolean} True if the event was successfully published.
- * @private
- */
-function publishEventForPlugin(dispatchConfig, pluginModule, eventName) {
-  invariant(
-    !eventNameDispatchConfigs.hasOwnProperty(eventName),
-    "EventPluginHub: More than one plugin attempted to publish the same " +
-      "event name, `%s`.",
-    eventName
-  );
-  eventNameDispatchConfigs[eventName] = dispatchConfig;
-
-  var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
-  if (phasedRegistrationNames) {
-    for (var phaseName in phasedRegistrationNames) {
-      if (phasedRegistrationNames.hasOwnProperty(phaseName)) {
-        var phasedRegistrationName = phasedRegistrationNames[phaseName];
-        publishRegistrationName(
-          phasedRegistrationName,
-          pluginModule,
-          eventName
-        );
-      }
-    }
-    return true;
-  } else if (dispatchConfig.registrationName) {
-    publishRegistrationName(
-      dispatchConfig.registrationName,
-      pluginModule,
-      eventName
-    );
-    return true;
-  }
-  return false;
-}
-
-/**
- * Publishes a registration name that is used to identify dispatched events.
- *
- * @param {string} registrationName Registration name to add.
- * @param {object} PluginModule Plugin publishing the event.
- * @private
- */
-function publishRegistrationName(registrationName, pluginModule, eventName) {
-  invariant(
-    !registrationNameModules[registrationName],
-    "EventPluginHub: More than one plugin attempted to publish the same " +
-      "registration name, `%s`.",
-    registrationName
-  );
-  registrationNameModules[registrationName] = pluginModule;
-  registrationNameDependencies[registrationName] =
-    pluginModule.eventTypes[eventName].dependencies;
-
-  {
-    var lowerCasedName = registrationName.toLowerCase();
-  }
-}
-
-/**
- * Registers plugins so that they can extract and dispatch events.
- *
- * @see {EventPluginHub}
- */
-
-/**
- * Ordered list of injected plugins.
- */
-var plugins = [];
-
-/**
- * Mapping from event name to dispatch config
- */
-var eventNameDispatchConfigs = {};
-
-/**
- * Mapping from registration name to plugin module
- */
-var registrationNameModules = {};
-
-/**
- * Mapping from registration name to event name
- */
-var registrationNameDependencies = {};
-
-/**
- * Mapping from lowercase registration names to the properly cased version,
- * used to warn in the case of missing event handlers. Available
- * only in true.
- * @type {Object}
- */
-
-// Trust the developer to only use possibleRegistrationNames in true
-
-/**
- * Injects an ordering of plugins (by plugin name). This allows the ordering
- * to be decoupled from injection of the actual plugins so that ordering is
- * always deterministic regardless of packaging, on-the-fly injection, etc.
- *
- * @param {array} InjectedEventPluginOrder
- * @internal
- * @see {EventPluginHub.injection.injectEventPluginOrder}
- */
-function injectEventPluginOrder(injectedEventPluginOrder) {
-  invariant(
-    !eventPluginOrder,
-    "EventPluginRegistry: Cannot inject event plugin ordering more than " +
-      "once. You are likely trying to load more than one copy of React."
-  );
-  // Clone the ordering so it cannot be dynamically mutated.
-  eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
-  recomputePluginOrdering();
-}
-
-/**
- * Injects plugins to be used by `EventPluginHub`. The plugin names must be
- * in the ordering injected by `injectEventPluginOrder`.
- *
- * Plugins can be injected as part of page initialization or on-the-fly.
- *
- * @param {object} injectedNamesToPlugins Map from names to plugin modules.
- * @internal
- * @see {EventPluginHub.injection.injectEventPluginsByName}
- */
-function injectEventPluginsByName(injectedNamesToPlugins) {
-  var isOrderingDirty = false;
-  for (var pluginName in injectedNamesToPlugins) {
-    if (!injectedNamesToPlugins.hasOwnProperty(pluginName)) {
-      continue;
-    }
-    var pluginModule = injectedNamesToPlugins[pluginName];
-    if (
-      !namesToPlugins.hasOwnProperty(pluginName) ||
-      namesToPlugins[pluginName] !== pluginModule
-    ) {
-      invariant(
-        !namesToPlugins[pluginName],
-        "EventPluginRegistry: Cannot inject two different event plugins " +
-          "using the same name, `%s`.",
-        pluginName
-      );
-      namesToPlugins[pluginName] = pluginModule;
-      isOrderingDirty = true;
-    }
-  }
-  if (isOrderingDirty) {
-    recomputePluginOrdering();
-  }
-}
-
-var getFiberCurrentPropsFromNode = null;
-var getInstanceFromNode = null;
-var getNodeFromInstance = null;
-
-var injection$1 = {
-  injectComponentTree: function(Injected) {
-    getFiberCurrentPropsFromNode = Injected.getFiberCurrentPropsFromNode;
-    getInstanceFromNode = Injected.getInstanceFromNode;
-    getNodeFromInstance = Injected.getNodeFromInstance;
-
-    {
-      !(getNodeFromInstance && getInstanceFromNode)
-        ? warning(
-            false,
-            "EventPluginUtils.injection.injectComponentTree(...): Injected " +
-              "module is missing getNodeFromInstance or getInstanceFromNode."
-          )
-        : void 0;
-    }
-  }
-};
-
-function isEndish(topLevelType) {
-  return (
-    topLevelType === "topMouseUp" ||
-    topLevelType === "topTouchEnd" ||
-    topLevelType === "topTouchCancel"
-  );
-}
-
-function isMoveish(topLevelType) {
-  return topLevelType === "topMouseMove" || topLevelType === "topTouchMove";
-}
-function isStartish(topLevelType) {
-  return topLevelType === "topMouseDown" || topLevelType === "topTouchStart";
-}
-
-var validateEventDispatches = void 0;
-{
-  validateEventDispatches = function(event) {
-    var dispatchListeners = event._dispatchListeners;
-    var dispatchInstances = event._dispatchInstances;
-
-    var listenersIsArr = Array.isArray(dispatchListeners);
-    var listenersLen = listenersIsArr
-      ? dispatchListeners.length
-      : dispatchListeners ? 1 : 0;
-
-    var instancesIsArr = Array.isArray(dispatchInstances);
-    var instancesLen = instancesIsArr
-      ? dispatchInstances.length
-      : dispatchInstances ? 1 : 0;
-
-    !(instancesIsArr === listenersIsArr && instancesLen === listenersLen)
-      ? warning(false, "EventPluginUtils: Invalid `event`.")
-      : void 0;
-  };
-}
-
-/**
- * Dispatch the event to the listener.
- * @param {SyntheticEvent} event SyntheticEvent to handle
- * @param {boolean} simulated If the event is simulated (changes exn behavior)
- * @param {function} listener Application-level callback
- * @param {*} inst Internal component instance
- */
-function executeDispatch(event, simulated, listener, inst) {
-  var type = event.type || "unknown-event";
-  event.currentTarget = getNodeFromInstance(inst);
-  ReactErrorUtils.invokeGuardedCallbackAndCatchFirstError(
-    type,
-    listener,
-    undefined,
-    event
-  );
-  event.currentTarget = null;
-}
-
-/**
- * Standard/simple iteration through an event's collected dispatches.
- */
-function executeDispatchesInOrder(event, simulated) {
-  var dispatchListeners = event._dispatchListeners;
-  var dispatchInstances = event._dispatchInstances;
-  {
-    validateEventDispatches(event);
-  }
-  if (Array.isArray(dispatchListeners)) {
-    for (var i = 0; i < dispatchListeners.length; i++) {
-      if (event.isPropagationStopped()) {
-        break;
-      }
-      // Listeners and Instances are two parallel arrays that are always in sync.
-      executeDispatch(
-        event,
-        simulated,
-        dispatchListeners[i],
-        dispatchInstances[i]
-      );
-    }
-  } else if (dispatchListeners) {
-    executeDispatch(event, simulated, dispatchListeners, dispatchInstances);
-  }
-  event._dispatchListeners = null;
-  event._dispatchInstances = null;
-}
-
-/**
- * Standard/simple iteration through an event's collected dispatches, but stops
- * at the first dispatch execution returning true, and returns that id.
- *
- * @return {?string} id of the first dispatch execution who's listener returns
- * true, or null if no listener returned true.
- */
-function executeDispatchesInOrderStopAtTrueImpl(event) {
-  var dispatchListeners = event._dispatchListeners;
-  var dispatchInstances = event._dispatchInstances;
-  {
-    validateEventDispatches(event);
-  }
-  if (Array.isArray(dispatchListeners)) {
-    for (var i = 0; i < dispatchListeners.length; i++) {
-      if (event.isPropagationStopped()) {
-        break;
-      }
-      // Listeners and Instances are two parallel arrays that are always in sync.
-      if (dispatchListeners[i](event, dispatchInstances[i])) {
-        return dispatchInstances[i];
-      }
-    }
-  } else if (dispatchListeners) {
-    if (dispatchListeners(event, dispatchInstances)) {
-      return dispatchInstances;
-    }
-  }
-  return null;
-}
-
-/**
- * @see executeDispatchesInOrderStopAtTrueImpl
- */
-function executeDispatchesInOrderStopAtTrue(event) {
-  var ret = executeDispatchesInOrderStopAtTrueImpl(event);
-  event._dispatchInstances = null;
-  event._dispatchListeners = null;
-  return ret;
-}
-
-/**
- * Execution of a "direct" dispatch - there must be at most one dispatch
- * accumulated on the event or it is considered an error. It doesn't really make
- * sense for an event with multiple dispatches (bubbled) to keep track of the
- * return values at each dispatch execution, but it does tend to make sense when
- * dealing with "direct" dispatches.
- *
- * @return {*} The return value of executing the single dispatch.
- */
-function executeDirectDispatch(event) {
-  {
-    validateEventDispatches(event);
-  }
-  var dispatchListener = event._dispatchListeners;
-  var dispatchInstance = event._dispatchInstances;
-  invariant(
-    !Array.isArray(dispatchListener),
-    "executeDirectDispatch(...): Invalid `event`."
-  );
-  event.currentTarget = dispatchListener
-    ? getNodeFromInstance(dispatchInstance)
-    : null;
-  var res = dispatchListener ? dispatchListener(event) : null;
-  event.currentTarget = null;
-  event._dispatchListeners = null;
-  event._dispatchInstances = null;
-  return res;
-}
-
-/**
- * @param {SyntheticEvent} event
- * @return {boolean} True iff number of dispatches accumulated is greater than 0.
- */
-function hasDispatches(event) {
-  return !!event._dispatchListeners;
-}
-
-/**
- * Accumulates items that must not be null or undefined into the first one. This
- * is used to conserve memory by avoiding array allocations, and thus sacrifices
- * API cleanness. Since `current` can be null before being passed in and not
- * null after this function, make sure to assign it back to `current`:
- *
- * `a = accumulateInto(a, b);`
- *
- * This API should be sparingly used. Try `accumulate` for something cleaner.
- *
- * @return {*|array<*>} An accumulation of items.
- */
-
-function accumulateInto(current, next) {
-  invariant(
-    next != null,
-    "accumulateInto(...): Accumulated items must not be null or undefined."
-  );
-
-  if (current == null) {
-    return next;
-  }
-
-  // Both are not empty. Warning: Never call x.concat(y) when you are not
-  // certain that x is an Array (x could be a string with concat method).
-  if (Array.isArray(current)) {
-    if (Array.isArray(next)) {
-      current.push.apply(current, next);
-      return current;
-    }
-    current.push(next);
-    return current;
-  }
-
-  if (Array.isArray(next)) {
-    // A bit too dangerous to mutate `next`.
-    return [current].concat(next);
-  }
-
-  return [current, next];
-}
-
-/**
- * @param {array} arr an "accumulation" of items which is either an Array or
- * a single item. Useful when paired with the `accumulate` module. This is a
- * simple utility that allows us to reason about a collection of items, but
- * handling the case when there is exactly one item (and we do not need to
- * allocate an array).
- * @param {function} cb Callback invoked with each element or a collection.
- * @param {?} [scope] Scope used as `this` in a callback.
- */
-function forEachAccumulated(arr, cb, scope) {
-  if (Array.isArray(arr)) {
-    arr.forEach(cb, scope);
-  } else if (arr) {
-    cb.call(scope, arr);
-  }
-}
-
-/**
- * Internal queue of events that have accumulated their dispatches and are
- * waiting to have their dispatches executed.
- */
-var eventQueue = null;
-
-/**
- * Dispatches an event and releases it back into the pool, unless persistent.
- *
- * @param {?object} event Synthetic event to be dispatched.
- * @param {boolean} simulated If the event is simulated (changes exn behavior)
- * @private
- */
-var executeDispatchesAndRelease = function(event, simulated) {
-  if (event) {
-    executeDispatchesInOrder(event, simulated);
-
-    if (!event.isPersistent()) {
-      event.constructor.release(event);
-    }
-  }
-};
-var executeDispatchesAndReleaseSimulated = function(e) {
-  return executeDispatchesAndRelease(e, true);
-};
-var executeDispatchesAndReleaseTopLevel = function(e) {
-  return executeDispatchesAndRelease(e, false);
-};
-
-function isInteractive(tag) {
-  return (
-    tag === "button" ||
-    tag === "input" ||
-    tag === "select" ||
-    tag === "textarea"
-  );
-}
-
-function shouldPreventMouseEvent(name, type, props) {
-  switch (name) {
-    case "onClick":
-    case "onClickCapture":
-    case "onDoubleClick":
-    case "onDoubleClickCapture":
-    case "onMouseDown":
-    case "onMouseDownCapture":
-    case "onMouseMove":
-    case "onMouseMoveCapture":
-    case "onMouseUp":
-    case "onMouseUpCapture":
-      return !!(props.disabled && isInteractive(type));
-    default:
-      return false;
-  }
-}
-
-/**
- * This is a unified interface for event plugins to be installed and configured.
- *
- * Event plugins can implement the following properties:
- *
- *   `extractEvents` {function(string, DOMEventTarget, string, object): *}
- *     Required. When a top-level event is fired, this method is expected to
- *     extract synthetic events that will in turn be queued and dispatched.
- *
- *   `eventTypes` {object}
- *     Optional, plugins that fire events must publish a mapping of registration
- *     names that are used to register listeners. Values of this mapping must
- *     be objects that contain `registrationName` or `phasedRegistrationNames`.
- *
- *   `executeDispatch` {function(object, function, string)}
- *     Optional, allows plugins to override how an event gets dispatched. By
- *     default, the listener is simply invoked.
- *
- * Each plugin that is injected into `EventsPluginHub` is immediately operable.
- *
- * @public
- */
-
-/**
- * Methods for injecting dependencies.
- */
-var injection = {
-  /**
-   * @param {array} InjectedEventPluginOrder
-   * @public
-   */
-  injectEventPluginOrder: injectEventPluginOrder,
-
-  /**
-   * @param {object} injectedNamesToPlugins Map from names to plugin modules.
-   */
-  injectEventPluginsByName: injectEventPluginsByName
-};
-
-/**
- * @param {object} inst The instance, which is the source of events.
- * @param {string} registrationName Name of listener (e.g. `onClick`).
- * @return {?function} The stored callback.
- */
-function getListener(inst, registrationName) {
-  var listener = void 0;
-
-  // TODO: shouldPreventMouseEvent is DOM-specific and definitely should not
-  // live here; needs to be moved to a better place soon
-  var stateNode = inst.stateNode;
-  if (!stateNode) {
-    // Work in progress (ex: onload events in incremental mode).
-    return null;
-  }
-  var props = getFiberCurrentPropsFromNode(stateNode);
-  if (!props) {
-    // Work in progress.
-    return null;
-  }
-  listener = props[registrationName];
-  if (shouldPreventMouseEvent(registrationName, inst.type, props)) {
-    return null;
-  }
-  invariant(
-    !listener || typeof listener === "function",
-    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
-    registrationName,
-    typeof listener
-  );
-  return listener;
-}
-
-/**
- * Allows registered plugins an opportunity to extract events from top-level
- * native browser events.
- *
- * @return {*} An accumulation of synthetic events.
- * @internal
- */
-function extractEvents(
-  topLevelType,
-  targetInst,
-  nativeEvent,
-  nativeEventTarget
-) {
-  var events = null;
-  for (var i = 0; i < plugins.length; i++) {
-    // Not every plugin in the ordering may be loaded at runtime.
-    var possiblePlugin = plugins[i];
-    if (possiblePlugin) {
-      var extractedEvents = possiblePlugin.extractEvents(
-        topLevelType,
-        targetInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      if (extractedEvents) {
-        events = accumulateInto(events, extractedEvents);
-      }
-    }
-  }
-  return events;
-}
-
-function runEventsInBatch(events, simulated) {
-  if (events !== null) {
-    eventQueue = accumulateInto(eventQueue, events);
-  }
-
-  // Set `eventQueue` to null before processing it so that we can tell if more
-  // events get enqueued while processing.
-  var processingEventQueue = eventQueue;
-  eventQueue = null;
-
-  if (!processingEventQueue) {
-    return;
-  }
-
-  if (simulated) {
-    forEachAccumulated(
-      processingEventQueue,
-      executeDispatchesAndReleaseSimulated
-    );
-  } else {
-    forEachAccumulated(
-      processingEventQueue,
-      executeDispatchesAndReleaseTopLevel
-    );
-  }
-  invariant(
-    !eventQueue,
-    "processEventQueue(): Additional events were enqueued while processing " +
-      "an event queue. Support for this has not yet been implemented."
-  );
-  // This would be a good time to rethrow if any of the event handlers threw.
-  ReactErrorUtils.rethrowCaughtError();
-}
-
-function runExtractedEventsInBatch(
-  topLevelType,
-  targetInst,
-  nativeEvent,
-  nativeEventTarget
-) {
-  var events = extractEvents(
-    topLevelType,
-    targetInst,
-    nativeEvent,
-    nativeEventTarget
-  );
-  runEventsInBatch(events, false);
-}
-
-var IndeterminateComponent = 0; // Before we know whether it is functional or class
-var FunctionalComponent = 1;
-var ClassComponent = 2;
-var HostRoot = 3; // Root of a host tree. Could be nested inside another node.
-var HostPortal = 4; // A subtree. Could be an entry point to a different renderer.
-var HostComponent = 5;
-var HostText = 6;
-var CallComponent = 7;
-var CallHandlerPhase = 8;
-var ReturnComponent = 9;
-var Fragment = 10;
-var Mode = 11;
-var ContextConsumer = 12;
-var ContextProvider = 13;
-var ForwardRef = 14;
-
-function getParent(inst) {
-  do {
-    inst = inst["return"];
-    // TODO: If this is a HostRoot we might want to bail out.
-    // That is depending on if we want nested subtrees (layers) to bubble
-    // events to their parent. We could also go through parentNode on the
-    // host node but that wouldn't work for React Native and doesn't let us
-    // do the portal feature.
-  } while (inst && inst.tag !== HostComponent);
-  if (inst) {
-    return inst;
-  }
-  return null;
-}
-
-/**
- * Return the lowest common ancestor of A and B, or null if they are in
- * different trees.
- */
-function getLowestCommonAncestor(instA, instB) {
-  var depthA = 0;
-  for (var tempA = instA; tempA; tempA = getParent(tempA)) {
-    depthA++;
-  }
-  var depthB = 0;
-  for (var tempB = instB; tempB; tempB = getParent(tempB)) {
-    depthB++;
-  }
-
-  // If A is deeper, crawl up.
-  while (depthA - depthB > 0) {
-    instA = getParent(instA);
-    depthA--;
-  }
-
-  // If B is deeper, crawl up.
-  while (depthB - depthA > 0) {
-    instB = getParent(instB);
-    depthB--;
-  }
-
-  // Walk in lockstep until we find a match.
-  var depth = depthA;
-  while (depth--) {
-    if (instA === instB || instA === instB.alternate) {
-      return instA;
-    }
-    instA = getParent(instA);
-    instB = getParent(instB);
-  }
-  return null;
-}
-
-/**
- * Return if A is an ancestor of B.
- */
-function isAncestor(instA, instB) {
-  while (instB) {
-    if (instA === instB || instA === instB.alternate) {
-      return true;
-    }
-    instB = getParent(instB);
-  }
-  return false;
-}
-
-/**
- * Return the parent instance of the passed-in instance.
- */
-function getParentInstance(inst) {
-  return getParent(inst);
-}
-
-/**
- * Simulates the traversal of a two-phase, capture/bubble event dispatch.
- */
-function traverseTwoPhase(inst, fn, arg) {
-  var path = [];
-  while (inst) {
-    path.push(inst);
-    inst = getParent(inst);
-  }
-  var i = void 0;
-  for (i = path.length; i-- > 0; ) {
-    fn(path[i], "captured", arg);
-  }
-  for (i = 0; i < path.length; i++) {
-    fn(path[i], "bubbled", arg);
-  }
-}
-
-/**
- * Traverses the ID hierarchy and invokes the supplied `cb` on any IDs that
- * should would receive a `mouseEnter` or `mouseLeave` event.
- *
- * Does not invoke the callback on the nearest common ancestor because nothing
- * "entered" or "left" that element.
- */
-
-/**
- * Some event types have a notion of different registration names for different
- * "phases" of propagation. This finds listeners by a given phase.
- */
-function listenerAtPhase(inst, event, propagationPhase) {
-  var registrationName =
-    event.dispatchConfig.phasedRegistrationNames[propagationPhase];
-  return getListener(inst, registrationName);
-}
-
-/**
- * A small set of propagation patterns, each of which will accept a small amount
- * of information, and generate a set of "dispatch ready event objects" - which
- * are sets of events that have already been annotated with a set of dispatched
- * listener functions/ids. The API is designed this way to discourage these
- * propagation strategies from actually executing the dispatches, since we
- * always want to collect the entire set of dispatches before executing even a
- * single one.
- */
-
-/**
- * Tags a `SyntheticEvent` with dispatched listeners. Creating this function
- * here, allows us to not have to bind or create functions for each event.
- * Mutating the event's members allows us to not have to create a wrapping
- * "dispatch" object that pairs the event with the listener.
- */
-function accumulateDirectionalDispatches(inst, phase, event) {
-  {
-    !inst ? warning(false, "Dispatching inst must not be null") : void 0;
-  }
-  var listener = listenerAtPhase(inst, event, phase);
-  if (listener) {
-    event._dispatchListeners = accumulateInto(
-      event._dispatchListeners,
-      listener
-    );
-    event._dispatchInstances = accumulateInto(event._dispatchInstances, inst);
-  }
-}
-
-/**
- * Collect dispatches (must be entirely collected before dispatching - see unit
- * tests). Lazily allocate the array to conserve memory.  We must loop through
- * each event and perform the traversal for each one. We cannot perform a
- * single traversal for the entire collection of events because each event may
- * have a different target.
- */
-function accumulateTwoPhaseDispatchesSingle(event) {
-  if (event && event.dispatchConfig.phasedRegistrationNames) {
-    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
-  }
-}
-
-/**
- * Same as `accumulateTwoPhaseDispatchesSingle`, but skips over the targetID.
- */
-function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
-  if (event && event.dispatchConfig.phasedRegistrationNames) {
-    var targetInst = event._targetInst;
-    var parentInst = targetInst ? getParentInstance(targetInst) : null;
-    traverseTwoPhase(parentInst, accumulateDirectionalDispatches, event);
-  }
-}
-
-/**
- * Accumulates without regard to direction, does not look for phased
- * registration names. Same as `accumulateDirectDispatchesSingle` but without
- * requiring that the `dispatchMarker` be the same as the dispatched ID.
- */
-function accumulateDispatches(inst, ignoredDirection, event) {
-  if (inst && event && event.dispatchConfig.registrationName) {
-    var registrationName = event.dispatchConfig.registrationName;
-    var listener = getListener(inst, registrationName);
-    if (listener) {
-      event._dispatchListeners = accumulateInto(
-        event._dispatchListeners,
-        listener
-      );
-      event._dispatchInstances = accumulateInto(event._dispatchInstances, inst);
-    }
-  }
-}
-
-/**
- * Accumulates dispatches on an `SyntheticEvent`, but only for the
- * `dispatchMarker`.
- * @param {SyntheticEvent} event
- */
-function accumulateDirectDispatchesSingle(event) {
-  if (event && event.dispatchConfig.registrationName) {
-    accumulateDispatches(event._targetInst, null, event);
-  }
-}
-
-function accumulateTwoPhaseDispatches(events) {
-  forEachAccumulated(events, accumulateTwoPhaseDispatchesSingle);
-}
-
-function accumulateTwoPhaseDispatchesSkipTarget(events) {
-  forEachAccumulated(events, accumulateTwoPhaseDispatchesSingleSkipTarget);
-}
-
-function accumulateDirectDispatches(events) {
-  forEachAccumulated(events, accumulateDirectDispatchesSingle);
-}
-
-/* eslint valid-typeof: 0 */
-
-var didWarnForAddedNewProperty = false;
-var EVENT_POOL_SIZE = 10;
-
-var shouldBeReleasedProperties = [
-  "dispatchConfig",
-  "_targetInst",
-  "nativeEvent",
-  "isDefaultPrevented",
-  "isPropagationStopped",
-  "_dispatchListeners",
-  "_dispatchInstances"
-];
-
-/**
- * @interface Event
- * @see http://www.w3.org/TR/DOM-Level-3-Events/
- */
-var EventInterface = {
-  type: null,
-  target: null,
-  // currentTarget is set when dispatching; no use in copying it here
-  currentTarget: emptyFunction.thatReturnsNull,
-  eventPhase: null,
-  bubbles: null,
-  cancelable: null,
-  timeStamp: function(event) {
-    return event.timeStamp || Date.now();
-  },
-  defaultPrevented: null,
-  isTrusted: null
-};
-
-/**
- * Synthetic events are dispatched by event plugins, typically in response to a
- * top-level event delegation handler.
- *
- * These systems should generally use pooling to reduce the frequency of garbage
- * collection. The system should check `isPersistent` to determine whether the
- * event should be released into the pool after being dispatched. Users that
- * need a persisted event should invoke `persist`.
- *
- * Synthetic events (and subclasses) implement the DOM Level 3 Events API by
- * normalizing browser quirks. Subclasses do not necessarily have to implement a
- * DOM interface; custom application-specific events can also subclass this.
- *
- * @param {object} dispatchConfig Configuration used to dispatch this event.
- * @param {*} targetInst Marker identifying the event target.
- * @param {object} nativeEvent Native browser event.
- * @param {DOMEventTarget} nativeEventTarget Target node.
- */
-function SyntheticEvent(
-  dispatchConfig,
-  targetInst,
-  nativeEvent,
-  nativeEventTarget
-) {
-  {
-    // these have a getter/setter for warnings
-    delete this.nativeEvent;
-    delete this.preventDefault;
-    delete this.stopPropagation;
-  }
-
-  this.dispatchConfig = dispatchConfig;
-  this._targetInst = targetInst;
-  this.nativeEvent = nativeEvent;
-
-  var Interface = this.constructor.Interface;
-  for (var propName in Interface) {
-    if (!Interface.hasOwnProperty(propName)) {
-      continue;
-    }
-    {
-      delete this[propName]; // this has a getter/setter for warnings
-    }
-    var normalize = Interface[propName];
-    if (normalize) {
-      this[propName] = normalize(nativeEvent);
-    } else {
-      if (propName === "target") {
-        this.target = nativeEventTarget;
-      } else {
-        this[propName] = nativeEvent[propName];
-      }
-    }
-  }
-
-  var defaultPrevented =
-    nativeEvent.defaultPrevented != null
-      ? nativeEvent.defaultPrevented
-      : nativeEvent.returnValue === false;
-  if (defaultPrevented) {
-    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
-  } else {
-    this.isDefaultPrevented = emptyFunction.thatReturnsFalse;
-  }
-  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
-  return this;
-}
-
-Object.assign(SyntheticEvent.prototype, {
-  preventDefault: function() {
-    this.defaultPrevented = true;
-    var event = this.nativeEvent;
-    if (!event) {
-      return;
-    }
-
-    if (event.preventDefault) {
-      event.preventDefault();
-    } else if (typeof event.returnValue !== "unknown") {
-      event.returnValue = false;
-    }
-    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
-  },
-
-  stopPropagation: function() {
-    var event = this.nativeEvent;
-    if (!event) {
-      return;
-    }
-
-    if (event.stopPropagation) {
-      event.stopPropagation();
-    } else if (typeof event.cancelBubble !== "unknown") {
-      // The ChangeEventPlugin registers a "propertychange" event for
-      // IE. This event does not support bubbling or cancelling, and
-      // any references to cancelBubble throw "Member not found".  A
-      // typeof check of "unknown" circumvents this issue (and is also
-      // IE specific).
-      event.cancelBubble = true;
-    }
-
-    this.isPropagationStopped = emptyFunction.thatReturnsTrue;
-  },
-
-  /**
-   * We release all dispatched `SyntheticEvent`s after each event loop, adding
-   * them back into the pool. This allows a way to hold onto a reference that
-   * won't be added back into the pool.
-   */
-  persist: function() {
-    this.isPersistent = emptyFunction.thatReturnsTrue;
-  },
-
-  /**
-   * Checks if this event should be released back into the pool.
-   *
-   * @return {boolean} True if this should not be released, false otherwise.
-   */
-  isPersistent: emptyFunction.thatReturnsFalse,
-
-  /**
-   * `PooledClass` looks for `destructor` on each instance it releases.
-   */
-  destructor: function() {
-    var Interface = this.constructor.Interface;
-    for (var propName in Interface) {
-      {
-        Object.defineProperty(
-          this,
-          propName,
-          getPooledWarningPropertyDefinition(propName, Interface[propName])
-        );
-      }
-    }
-    for (var i = 0; i < shouldBeReleasedProperties.length; i++) {
-      this[shouldBeReleasedProperties[i]] = null;
-    }
-    {
-      Object.defineProperty(
-        this,
-        "nativeEvent",
-        getPooledWarningPropertyDefinition("nativeEvent", null)
-      );
-      Object.defineProperty(
-        this,
-        "preventDefault",
-        getPooledWarningPropertyDefinition("preventDefault", emptyFunction)
-      );
-      Object.defineProperty(
-        this,
-        "stopPropagation",
-        getPooledWarningPropertyDefinition("stopPropagation", emptyFunction)
-      );
-    }
-  }
-});
-
-SyntheticEvent.Interface = EventInterface;
-
-/**
- * Helper to reduce boilerplate when creating subclasses.
- */
-SyntheticEvent.extend = function(Interface) {
-  var Super = this;
-
-  var E = function() {};
-  E.prototype = Super.prototype;
-  var prototype = new E();
-
-  function Class() {
-    return Super.apply(this, arguments);
-  }
-  Object.assign(prototype, Class.prototype);
-  Class.prototype = prototype;
-  Class.prototype.constructor = Class;
-
-  Class.Interface = Object.assign({}, Super.Interface, Interface);
-  Class.extend = Super.extend;
-  addEventPoolingTo(Class);
-
-  return Class;
-};
-
-/** Proxying after everything set on SyntheticEvent
- * to resolve Proxy issue on some WebKit browsers
- * in which some Event properties are set to undefined (GH#10010)
- */
-{
-  var isProxySupported =
-    typeof Proxy === "function" &&
-    // https://github.com/facebook/react/issues/12011
-    !Object.isSealed(new Proxy({}, {}));
-
-  if (isProxySupported) {
-    /*eslint-disable no-func-assign */
-    SyntheticEvent = new Proxy(SyntheticEvent, {
-      construct: function(target, args) {
-        return this.apply(target, Object.create(target.prototype), args);
-      },
-      apply: function(constructor, that, args) {
-        return new Proxy(constructor.apply(that, args), {
-          set: function(target, prop, value) {
-            if (
-              prop !== "isPersistent" &&
-              !target.constructor.Interface.hasOwnProperty(prop) &&
-              shouldBeReleasedProperties.indexOf(prop) === -1
-            ) {
-              !(didWarnForAddedNewProperty || target.isPersistent())
-                ? warning(
-                    false,
-                    "This synthetic event is reused for performance reasons. If you're " +
-                      "seeing this, you're adding a new property in the synthetic event object. " +
-                      "The property is never released. See " +
-                      "https://fb.me/react-event-pooling for more information."
-                  )
-                : void 0;
-              didWarnForAddedNewProperty = true;
-            }
-            target[prop] = value;
-            return true;
-          }
-        });
-      }
-    });
-    /*eslint-enable no-func-assign */
-  }
-}
-
-addEventPoolingTo(SyntheticEvent);
-
-/**
- * Helper to nullify syntheticEvent instance properties when destructing
- *
- * @param {String} propName
- * @param {?object} getVal
- * @return {object} defineProperty object
- */
-function getPooledWarningPropertyDefinition(propName, getVal) {
-  var isFunction = typeof getVal === "function";
-  return {
-    configurable: true,
-    set: set,
-    get: get$$1
-  };
-
-  function set(val) {
-    var action = isFunction ? "setting the method" : "setting the property";
-    warn(action, "This is effectively a no-op");
-    return val;
-  }
-
-  function get$$1() {
-    var action = isFunction ? "accessing the method" : "accessing the property";
-    var result = isFunction
-      ? "This is a no-op function"
-      : "This is set to null";
-    warn(action, result);
-    return getVal;
-  }
-
-  function warn(action, result) {
-    var warningCondition = false;
-    !warningCondition
-      ? warning(
-          false,
-          "This synthetic event is reused for performance reasons. If you're seeing this, " +
-            "you're %s `%s` on a released/nullified synthetic event. %s. " +
-            "If you must keep the original synthetic event around, use event.persist(). " +
-            "See https://fb.me/react-event-pooling for more information.",
-          action,
-          propName,
-          result
-        )
-      : void 0;
-  }
-}
-
-function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
-  var EventConstructor = this;
-  if (EventConstructor.eventPool.length) {
-    var instance = EventConstructor.eventPool.pop();
-    EventConstructor.call(
-      instance,
-      dispatchConfig,
-      targetInst,
-      nativeEvent,
-      nativeInst
-    );
-    return instance;
-  }
-  return new EventConstructor(
-    dispatchConfig,
-    targetInst,
-    nativeEvent,
-    nativeInst
-  );
-}
-
-function releasePooledEvent(event) {
-  var EventConstructor = this;
-  invariant(
-    event instanceof EventConstructor,
-    "Trying to release an event instance  into a pool of a different type."
-  );
-  event.destructor();
-  if (EventConstructor.eventPool.length < EVENT_POOL_SIZE) {
-    EventConstructor.eventPool.push(event);
-  }
-}
-
-function addEventPoolingTo(EventConstructor) {
-  EventConstructor.eventPool = [];
-  EventConstructor.getPooled = getPooledEvent;
-  EventConstructor.release = releasePooledEvent;
-}
-
-var SyntheticEvent$1 = SyntheticEvent;
-
-/**
- * `touchHistory` isn't actually on the native event, but putting it in the
- * interface will ensure that it is cleaned up when pooled/destroyed. The
- * `ResponderEventPlugin` will populate it appropriately.
- */
-var ResponderSyntheticEvent = SyntheticEvent$1.extend({
-  touchHistory: function(nativeEvent) {
-    return null; // Actually doesn't even look at the native event.
-  }
-});
-
-/**
- * Tracks the position and time of each active touch by `touch.identifier`. We
- * should typically only see IDs in the range of 1-20 because IDs get recycled
- * when touches end and start again.
- */
-
-var MAX_TOUCH_BANK = 20;
-var touchBank = [];
-var touchHistory = {
-  touchBank: touchBank,
-  numberActiveTouches: 0,
-  // If there is only one active touch, we remember its location. This prevents
-  // us having to loop through all of the touches all the time in the most
-  // common case.
-  indexOfSingleActiveTouch: -1,
-  mostRecentTimeStamp: 0
-};
-
-function timestampForTouch(touch) {
-  // The legacy internal implementation provides "timeStamp", which has been
-  // renamed to "timestamp". Let both work for now while we iron it out
-  // TODO (evv): rename timeStamp to timestamp in internal code
-  return touch.timeStamp || touch.timestamp;
-}
-
-/**
- * TODO: Instead of making gestures recompute filtered velocity, we could
- * include a built in velocity computation that can be reused globally.
- */
-function createTouchRecord(touch) {
-  return {
-    touchActive: true,
-    startPageX: touch.pageX,
-    startPageY: touch.pageY,
-    startTimeStamp: timestampForTouch(touch),
-    currentPageX: touch.pageX,
-    currentPageY: touch.pageY,
-    currentTimeStamp: timestampForTouch(touch),
-    previousPageX: touch.pageX,
-    previousPageY: touch.pageY,
-    previousTimeStamp: timestampForTouch(touch)
-  };
-}
-
-function resetTouchRecord(touchRecord, touch) {
-  touchRecord.touchActive = true;
-  touchRecord.startPageX = touch.pageX;
-  touchRecord.startPageY = touch.pageY;
-  touchRecord.startTimeStamp = timestampForTouch(touch);
-  touchRecord.currentPageX = touch.pageX;
-  touchRecord.currentPageY = touch.pageY;
-  touchRecord.currentTimeStamp = timestampForTouch(touch);
-  touchRecord.previousPageX = touch.pageX;
-  touchRecord.previousPageY = touch.pageY;
-  touchRecord.previousTimeStamp = timestampForTouch(touch);
-}
-
-function getTouchIdentifier(_ref) {
-  var identifier = _ref.identifier;
-
-  invariant(identifier != null, "Touch object is missing identifier.");
-  {
-    !(identifier <= MAX_TOUCH_BANK)
-      ? warning(
-          false,
-          "Touch identifier %s is greater than maximum supported %s which causes " +
-            "performance issues backfilling array locations for all of the indices.",
-          identifier,
-          MAX_TOUCH_BANK
-        )
-      : void 0;
-  }
-  return identifier;
-}
-
-function recordTouchStart(touch) {
-  var identifier = getTouchIdentifier(touch);
-  var touchRecord = touchBank[identifier];
-  if (touchRecord) {
-    resetTouchRecord(touchRecord, touch);
-  } else {
-    touchBank[identifier] = createTouchRecord(touch);
-  }
-  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
-}
-
-function recordTouchMove(touch) {
-  var touchRecord = touchBank[getTouchIdentifier(touch)];
-  if (touchRecord) {
-    touchRecord.touchActive = true;
-    touchRecord.previousPageX = touchRecord.currentPageX;
-    touchRecord.previousPageY = touchRecord.currentPageY;
-    touchRecord.previousTimeStamp = touchRecord.currentTimeStamp;
-    touchRecord.currentPageX = touch.pageX;
-    touchRecord.currentPageY = touch.pageY;
-    touchRecord.currentTimeStamp = timestampForTouch(touch);
-    touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
-  } else {
-    console.error(
-      "Cannot record touch move without a touch start.\n" + "Touch Move: %s\n",
-      "Touch Bank: %s",
-      printTouch(touch),
-      printTouchBank()
-    );
-  }
-}
-
-function recordTouchEnd(touch) {
-  var touchRecord = touchBank[getTouchIdentifier(touch)];
-  if (touchRecord) {
-    touchRecord.touchActive = false;
-    touchRecord.previousPageX = touchRecord.currentPageX;
-    touchRecord.previousPageY = touchRecord.currentPageY;
-    touchRecord.previousTimeStamp = touchRecord.currentTimeStamp;
-    touchRecord.currentPageX = touch.pageX;
-    touchRecord.currentPageY = touch.pageY;
-    touchRecord.currentTimeStamp = timestampForTouch(touch);
-    touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
-  } else {
-    console.error(
-      "Cannot record touch end without a touch start.\n" + "Touch End: %s\n",
-      "Touch Bank: %s",
-      printTouch(touch),
-      printTouchBank()
-    );
-  }
-}
-
-function printTouch(touch) {
-  return JSON.stringify({
-    identifier: touch.identifier,
-    pageX: touch.pageX,
-    pageY: touch.pageY,
-    timestamp: timestampForTouch(touch)
-  });
-}
-
-function printTouchBank() {
-  var printed = JSON.stringify(touchBank.slice(0, MAX_TOUCH_BANK));
-  if (touchBank.length > MAX_TOUCH_BANK) {
-    printed += " (original size: " + touchBank.length + ")";
-  }
-  return printed;
-}
-
-var ResponderTouchHistoryStore = {
-  recordTouchTrack: function(topLevelType, nativeEvent) {
-    if (isMoveish(topLevelType)) {
-      nativeEvent.changedTouches.forEach(recordTouchMove);
-    } else if (isStartish(topLevelType)) {
-      nativeEvent.changedTouches.forEach(recordTouchStart);
-      touchHistory.numberActiveTouches = nativeEvent.touches.length;
-      if (touchHistory.numberActiveTouches === 1) {
-        touchHistory.indexOfSingleActiveTouch =
-          nativeEvent.touches[0].identifier;
-      }
-    } else if (isEndish(topLevelType)) {
-      nativeEvent.changedTouches.forEach(recordTouchEnd);
-      touchHistory.numberActiveTouches = nativeEvent.touches.length;
-      if (touchHistory.numberActiveTouches === 1) {
-        for (var i = 0; i < touchBank.length; i++) {
-          var touchTrackToCheck = touchBank[i];
-          if (touchTrackToCheck != null && touchTrackToCheck.touchActive) {
-            touchHistory.indexOfSingleActiveTouch = i;
-            break;
-          }
-        }
-        {
-          var activeRecord = touchBank[touchHistory.indexOfSingleActiveTouch];
-          !(activeRecord != null && activeRecord.touchActive)
-            ? warning(false, "Cannot find single active touch.")
-            : void 0;
-        }
-      }
-    }
-  },
-
-  touchHistory: touchHistory
-};
-
-/**
- * Accumulates items that must not be null or undefined.
- *
- * This is used to conserve memory by avoiding array allocations.
- *
- * @return {*|array<*>} An accumulation of items.
- */
-function accumulate(current, next) {
-  invariant(
-    next != null,
-    "accumulate(...): Accumulated items must be not be null or undefined."
-  );
-
-  if (current == null) {
-    return next;
-  }
-
-  // Both are not empty. Warning: Never call x.concat(y) when you are not
-  // certain that x is an Array (x could be a string with concat method).
-  if (Array.isArray(current)) {
-    return current.concat(next);
-  }
-
-  if (Array.isArray(next)) {
-    return [current].concat(next);
-  }
-
-  return [current, next];
-}
-
-/**
- * Instance of element that should respond to touch/move types of interactions,
- * as indicated explicitly by relevant callbacks.
- */
-var responderInst = null;
-
-/**
- * Count of current touches. A textInput should become responder iff the
- * selection changes while there is a touch on the screen.
- */
-var trackedTouchCount = 0;
-
-/**
- * Last reported number of active touches.
- */
-var previousActiveTouches = 0;
-
-var changeResponder = function(nextResponderInst, blockHostResponder) {
-  var oldResponderInst = responderInst;
-  responderInst = nextResponderInst;
-  if (ResponderEventPlugin.GlobalResponderHandler !== null) {
-    ResponderEventPlugin.GlobalResponderHandler.onChange(
-      oldResponderInst,
-      nextResponderInst,
-      blockHostResponder
-    );
-  }
-};
-
-var eventTypes$1 = {
-  /**
-   * On a `touchStart`/`mouseDown`, is it desired that this element become the
-   * responder?
-   */
-  startShouldSetResponder: {
-    phasedRegistrationNames: {
-      bubbled: "onStartShouldSetResponder",
-      captured: "onStartShouldSetResponderCapture"
-    }
-  },
-
-  /**
-   * On a `scroll`, is it desired that this element become the responder? This
-   * is usually not needed, but should be used to retroactively infer that a
-   * `touchStart` had occurred during momentum scroll. During a momentum scroll,
-   * a touch start will be immediately followed by a scroll event if the view is
-   * currently scrolling.
-   *
-   * TODO: This shouldn't bubble.
-   */
-  scrollShouldSetResponder: {
-    phasedRegistrationNames: {
-      bubbled: "onScrollShouldSetResponder",
-      captured: "onScrollShouldSetResponderCapture"
-    }
-  },
-
-  /**
-   * On text selection change, should this element become the responder? This
-   * is needed for text inputs or other views with native selection, so the
-   * JS view can claim the responder.
-   *
-   * TODO: This shouldn't bubble.
-   */
-  selectionChangeShouldSetResponder: {
-    phasedRegistrationNames: {
-      bubbled: "onSelectionChangeShouldSetResponder",
-      captured: "onSelectionChangeShouldSetResponderCapture"
-    }
-  },
-
-  /**
-   * On a `touchMove`/`mouseMove`, is it desired that this element become the
-   * responder?
-   */
-  moveShouldSetResponder: {
-    phasedRegistrationNames: {
-      bubbled: "onMoveShouldSetResponder",
-      captured: "onMoveShouldSetResponderCapture"
-    }
-  },
-
-  /**
-   * Direct responder events dispatched directly to responder. Do not bubble.
-   */
-  responderStart: { registrationName: "onResponderStart" },
-  responderMove: { registrationName: "onResponderMove" },
-  responderEnd: { registrationName: "onResponderEnd" },
-  responderRelease: { registrationName: "onResponderRelease" },
-  responderTerminationRequest: {
-    registrationName: "onResponderTerminationRequest"
-  },
-  responderGrant: { registrationName: "onResponderGrant" },
-  responderReject: { registrationName: "onResponderReject" },
-  responderTerminate: { registrationName: "onResponderTerminate" }
-};
-
-/**
- *
- * Responder System:
- * ----------------
- *
- * - A global, solitary "interaction lock" on a view.
- * - If a node becomes the responder, it should convey visual feedback
- *   immediately to indicate so, either by highlighting or moving accordingly.
- * - To be the responder means, that touches are exclusively important to that
- *   responder view, and no other view.
- * - While touches are still occurring, the responder lock can be transferred to
- *   a new view, but only to increasingly "higher" views (meaning ancestors of
- *   the current responder).
- *
- * Responder being granted:
- * ------------------------
- *
- * - Touch starts, moves, and scrolls can cause an ID to become the responder.
- * - We capture/bubble `startShouldSetResponder`/`moveShouldSetResponder` to
- *   the "appropriate place".
- * - If nothing is currently the responder, the "appropriate place" is the
- *   initiating event's `targetID`.
- * - If something *is* already the responder, the "appropriate place" is the
- *   first common ancestor of the event target and the current `responderInst`.
- * - Some negotiation happens: See the timing diagram below.
- * - Scrolled views automatically become responder. The reasoning is that a
- *   platform scroll view that isn't built on top of the responder system has
- *   began scrolling, and the active responder must now be notified that the
- *   interaction is no longer locked to it - the system has taken over.
- *
- * - Responder being released:
- *   As soon as no more touches that *started* inside of descendants of the
- *   *current* responderInst, an `onResponderRelease` event is dispatched to the
- *   current responder, and the responder lock is released.
- *
- * TODO:
- * - on "end", a callback hook for `onResponderEndShouldRemainResponder` that
- *   determines if the responder lock should remain.
- * - If a view shouldn't "remain" the responder, any active touches should by
- *   default be considered "dead" and do not influence future negotiations or
- *   bubble paths. It should be as if those touches do not exist.
- * -- For multitouch: Usually a translate-z will choose to "remain" responder
- *  after one out of many touches ended. For translate-y, usually the view
- *  doesn't wish to "remain" responder after one of many touches end.
- * - Consider building this on top of a `stopPropagation` model similar to
- *   `W3C` events.
- * - Ensure that `onResponderTerminate` is called on touch cancels, whether or
- *   not `onResponderTerminationRequest` returns `true` or `false`.
- *
- */
-
-/*                                             Negotiation Performed
-                                             +-----------------------+
-                                            /                         \
-Process low level events to    +     Current Responder      +   wantsResponderID
-determine who to perform negot-|   (if any exists at all)   |
-iation/transition              | Otherwise just pass through|
--------------------------------+----------------------------+------------------+
-Bubble to find first ID        |                            |
-to return true:wantsResponderID|                            |
-                               |                            |
-     +-------------+           |                            |
-     | onTouchStart|           |                            |
-     +------+------+     none  |                            |
-            |            return|                            |
-+-----------v-------------+true| +------------------------+ |
-|onStartShouldSetResponder|----->|onResponderStart (cur)  |<-----------+
-+-----------+-------------+    | +------------------------+ |          |
-            |                  |                            | +--------+-------+
-            | returned true for|       false:REJECT +-------->|onResponderReject
-            | wantsResponderID |                    |       | +----------------+
-            | (now attempt     | +------------------+-----+ |
-            |  handoff)        | |   onResponder          | |
-            +------------------->|      TerminationRequest| |
-                               | +------------------+-----+ |
-                               |                    |       | +----------------+
-                               |         true:GRANT +-------->|onResponderGrant|
-                               |                            | +--------+-------+
-                               | +------------------------+ |          |
-                               | |   onResponderTerminate |<-----------+
-                               | +------------------+-----+ |
-                               |                    |       | +----------------+
-                               |                    +-------->|onResponderStart|
-                               |                            | +----------------+
-Bubble to find first ID        |                            |
-to return true:wantsResponderID|                            |
-                               |                            |
-     +-------------+           |                            |
-     | onTouchMove |           |                            |
-     +------+------+     none  |                            |
-            |            return|                            |
-+-----------v-------------+true| +------------------------+ |
-|onMoveShouldSetResponder |----->|onResponderMove (cur)   |<-----------+
-+-----------+-------------+    | +------------------------+ |          |
-            |                  |                            | +--------+-------+
-            | returned true for|       false:REJECT +-------->|onResponderRejec|
-            | wantsResponderID |                    |       | +----------------+
-            | (now attempt     | +------------------+-----+ |
-            |  handoff)        | |   onResponder          | |
-            +------------------->|      TerminationRequest| |
-                               | +------------------+-----+ |
-                               |                    |       | +----------------+
-                               |         true:GRANT +-------->|onResponderGrant|
-                               |                            | +--------+-------+
-                               | +------------------------+ |          |
-                               | |   onResponderTerminate |<-----------+
-                               | +------------------+-----+ |
-                               |                    |       | +----------------+
-                               |                    +-------->|onResponderMove |
-                               |                            | +----------------+
-                               |                            |
-                               |                            |
-      Some active touch started|                            |
-      inside current responder | +------------------------+ |
-      +------------------------->|      onResponderEnd    | |
-      |                        | +------------------------+ |
-  +---+---------+              |                            |
-  | onTouchEnd  |              |                            |
-  +---+---------+              |                            |
-      |                        | +------------------------+ |
-      +------------------------->|     onResponderEnd     | |
-      No active touches started| +-----------+------------+ |
-      inside current responder |             |              |
-                               |             v              |
-                               | +------------------------+ |
-                               | |    onResponderRelease  | |
-                               | +------------------------+ |
-                               |                            |
-                               +                            + */
-
-/**
- * A note about event ordering in the `EventPluginHub`.
- *
- * Suppose plugins are injected in the following order:
- *
- * `[R, S, C]`
- *
- * To help illustrate the example, assume `S` is `SimpleEventPlugin` (for
- * `onClick` etc) and `R` is `ResponderEventPlugin`.
- *
- * "Deferred-Dispatched Events":
- *
- * - The current event plugin system will traverse the list of injected plugins,
- *   in order, and extract events by collecting the plugin's return value of
- *   `extractEvents()`.
- * - These events that are returned from `extractEvents` are "deferred
- *   dispatched events".
- * - When returned from `extractEvents`, deferred-dispatched events contain an
- *   "accumulation" of deferred dispatches.
- * - These deferred dispatches are accumulated/collected before they are
- *   returned, but processed at a later time by the `EventPluginHub` (hence the
- *   name deferred).
- *
- * In the process of returning their deferred-dispatched events, event plugins
- * themselves can dispatch events on-demand without returning them from
- * `extractEvents`. Plugins might want to do this, so that they can use event
- * dispatching as a tool that helps them decide which events should be extracted
- * in the first place.
- *
- * "On-Demand-Dispatched Events":
- *
- * - On-demand-dispatched events are not returned from `extractEvents`.
- * - On-demand-dispatched events are dispatched during the process of returning
- *   the deferred-dispatched events.
- * - They should not have side effects.
- * - They should be avoided, and/or eventually be replaced with another
- *   abstraction that allows event plugins to perform multiple "rounds" of event
- *   extraction.
- *
- * Therefore, the sequence of event dispatches becomes:
- *
- * - `R`s on-demand events (if any)   (dispatched by `R` on-demand)
- * - `S`s on-demand events (if any)   (dispatched by `S` on-demand)
- * - `C`s on-demand events (if any)   (dispatched by `C` on-demand)
- * - `R`s extracted events (if any)   (dispatched by `EventPluginHub`)
- * - `S`s extracted events (if any)   (dispatched by `EventPluginHub`)
- * - `C`s extracted events (if any)   (dispatched by `EventPluginHub`)
- *
- * In the case of `ResponderEventPlugin`: If the `startShouldSetResponder`
- * on-demand dispatch returns `true` (and some other details are satisfied) the
- * `onResponderGrant` deferred dispatched event is returned from
- * `extractEvents`. The sequence of dispatch executions in this case
- * will appear as follows:
- *
- * - `startShouldSetResponder` (`ResponderEventPlugin` dispatches on-demand)
- * - `touchStartCapture`       (`EventPluginHub` dispatches as usual)
- * - `touchStart`              (`EventPluginHub` dispatches as usual)
- * - `responderGrant/Reject`   (`EventPluginHub` dispatches as usual)
- */
-
-function setResponderAndExtractTransfer(
-  topLevelType,
-  targetInst,
-  nativeEvent,
-  nativeEventTarget
-) {
-  var shouldSetEventType = isStartish(topLevelType)
-    ? eventTypes$1.startShouldSetResponder
-    : isMoveish(topLevelType)
-      ? eventTypes$1.moveShouldSetResponder
-      : topLevelType === "topSelectionChange"
-        ? eventTypes$1.selectionChangeShouldSetResponder
-        : eventTypes$1.scrollShouldSetResponder;
-
-  // TODO: stop one short of the current responder.
-  var bubbleShouldSetFrom = !responderInst
-    ? targetInst
-    : getLowestCommonAncestor(responderInst, targetInst);
-
-  // When capturing/bubbling the "shouldSet" event, we want to skip the target
-  // (deepest ID) if it happens to be the current responder. The reasoning:
-  // It's strange to get an `onMoveShouldSetResponder` when you're *already*
-  // the responder.
-  var skipOverBubbleShouldSetFrom = bubbleShouldSetFrom === responderInst;
-  var shouldSetEvent = ResponderSyntheticEvent.getPooled(
-    shouldSetEventType,
-    bubbleShouldSetFrom,
-    nativeEvent,
-    nativeEventTarget
-  );
-  shouldSetEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-  if (skipOverBubbleShouldSetFrom) {
-    accumulateTwoPhaseDispatchesSkipTarget(shouldSetEvent);
-  } else {
-    accumulateTwoPhaseDispatches(shouldSetEvent);
-  }
-  var wantsResponderInst = executeDispatchesInOrderStopAtTrue(shouldSetEvent);
-  if (!shouldSetEvent.isPersistent()) {
-    shouldSetEvent.constructor.release(shouldSetEvent);
-  }
-
-  if (!wantsResponderInst || wantsResponderInst === responderInst) {
-    return null;
-  }
-  var extracted = void 0;
-  var grantEvent = ResponderSyntheticEvent.getPooled(
-    eventTypes$1.responderGrant,
-    wantsResponderInst,
-    nativeEvent,
-    nativeEventTarget
-  );
-  grantEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-
-  accumulateDirectDispatches(grantEvent);
-  var blockHostResponder = executeDirectDispatch(grantEvent) === true;
-  if (responderInst) {
-    var terminationRequestEvent = ResponderSyntheticEvent.getPooled(
-      eventTypes$1.responderTerminationRequest,
-      responderInst,
-      nativeEvent,
-      nativeEventTarget
-    );
-    terminationRequestEvent.touchHistory =
-      ResponderTouchHistoryStore.touchHistory;
-    accumulateDirectDispatches(terminationRequestEvent);
-    var shouldSwitch =
-      !hasDispatches(terminationRequestEvent) ||
-      executeDirectDispatch(terminationRequestEvent);
-    if (!terminationRequestEvent.isPersistent()) {
-      terminationRequestEvent.constructor.release(terminationRequestEvent);
-    }
-
-    if (shouldSwitch) {
-      var terminateEvent = ResponderSyntheticEvent.getPooled(
-        eventTypes$1.responderTerminate,
-        responderInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      terminateEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-      accumulateDirectDispatches(terminateEvent);
-      extracted = accumulate(extracted, [grantEvent, terminateEvent]);
-      changeResponder(wantsResponderInst, blockHostResponder);
-    } else {
-      var rejectEvent = ResponderSyntheticEvent.getPooled(
-        eventTypes$1.responderReject,
-        wantsResponderInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      rejectEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-      accumulateDirectDispatches(rejectEvent);
-      extracted = accumulate(extracted, rejectEvent);
-    }
-  } else {
-    extracted = accumulate(extracted, grantEvent);
-    changeResponder(wantsResponderInst, blockHostResponder);
-  }
-  return extracted;
-}
-
-/**
- * A transfer is a negotiation between a currently set responder and the next
- * element to claim responder status. Any start event could trigger a transfer
- * of responderInst. Any move event could trigger a transfer.
- *
- * @param {string} topLevelType Record from `BrowserEventConstants`.
- * @return {boolean} True if a transfer of responder could possibly occur.
- */
-function canTriggerTransfer(topLevelType, topLevelInst, nativeEvent) {
-  return (
-    topLevelInst &&
-    // responderIgnoreScroll: We are trying to migrate away from specifically
-    // tracking native scroll events here and responderIgnoreScroll indicates we
-    // will send topTouchCancel to handle canceling touch events instead
-    ((topLevelType === "topScroll" && !nativeEvent.responderIgnoreScroll) ||
-      (trackedTouchCount > 0 && topLevelType === "topSelectionChange") ||
-      isStartish(topLevelType) ||
-      isMoveish(topLevelType))
-  );
-}
-
-/**
- * Returns whether or not this touch end event makes it such that there are no
- * longer any touches that started inside of the current `responderInst`.
- *
- * @param {NativeEvent} nativeEvent Native touch end event.
- * @return {boolean} Whether or not this touch end event ends the responder.
- */
-function noResponderTouches(nativeEvent) {
-  var touches = nativeEvent.touches;
-  if (!touches || touches.length === 0) {
-    return true;
-  }
-  for (var i = 0; i < touches.length; i++) {
-    var activeTouch = touches[i];
-    var target = activeTouch.target;
-    if (target !== null && target !== undefined && target !== 0) {
-      // Is the original touch location inside of the current responder?
-      var targetInst = getInstanceFromNode(target);
-      if (isAncestor(responderInst, targetInst)) {
-        return false;
-      }
-    }
-  }
-  return true;
-}
-
-var ResponderEventPlugin = {
-  /* For unit testing only */
-  _getResponder: function() {
-    return responderInst;
-  },
-
-  eventTypes: eventTypes$1,
-
-  /**
-   * We must be resilient to `targetInst` being `null` on `touchMove` or
-   * `touchEnd`. On certain platforms, this means that a native scroll has
-   * assumed control and the original touch targets are destroyed.
-   */
-  extractEvents: function(
-    topLevelType,
-    targetInst,
-    nativeEvent,
-    nativeEventTarget
-  ) {
-    if (isStartish(topLevelType)) {
-      trackedTouchCount += 1;
-    } else if (isEndish(topLevelType)) {
-      if (trackedTouchCount >= 0) {
-        trackedTouchCount -= 1;
-      } else {
-        console.error(
-          "Ended a touch event which was not counted in `trackedTouchCount`."
-        );
-        return null;
-      }
-    }
-
-    ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
-
-    var extracted = canTriggerTransfer(topLevelType, targetInst, nativeEvent)
-      ? setResponderAndExtractTransfer(
-          topLevelType,
-          targetInst,
-          nativeEvent,
-          nativeEventTarget
-        )
-      : null;
-    // Responder may or may not have transferred on a new touch start/move.
-    // Regardless, whoever is the responder after any potential transfer, we
-    // direct all touch start/move/ends to them in the form of
-    // `onResponderMove/Start/End`. These will be called for *every* additional
-    // finger that move/start/end, dispatched directly to whoever is the
-    // current responder at that moment, until the responder is "released".
-    //
-    // These multiple individual change touch events are are always bookended
-    // by `onResponderGrant`, and one of
-    // (`onResponderRelease/onResponderTerminate`).
-    var isResponderTouchStart = responderInst && isStartish(topLevelType);
-    var isResponderTouchMove = responderInst && isMoveish(topLevelType);
-    var isResponderTouchEnd = responderInst && isEndish(topLevelType);
-    var incrementalTouch = isResponderTouchStart
-      ? eventTypes$1.responderStart
-      : isResponderTouchMove
-        ? eventTypes$1.responderMove
-        : isResponderTouchEnd ? eventTypes$1.responderEnd : null;
-
-    if (incrementalTouch) {
-      var gesture = ResponderSyntheticEvent.getPooled(
-        incrementalTouch,
-        responderInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      gesture.touchHistory = ResponderTouchHistoryStore.touchHistory;
-      accumulateDirectDispatches(gesture);
-      extracted = accumulate(extracted, gesture);
-    }
-
-    var isResponderTerminate =
-      responderInst && topLevelType === "topTouchCancel";
-    var isResponderRelease =
-      responderInst &&
-      !isResponderTerminate &&
-      isEndish(topLevelType) &&
-      noResponderTouches(nativeEvent);
-    var finalTouch = isResponderTerminate
-      ? eventTypes$1.responderTerminate
-      : isResponderRelease ? eventTypes$1.responderRelease : null;
-    if (finalTouch) {
-      var finalEvent = ResponderSyntheticEvent.getPooled(
-        finalTouch,
-        responderInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      finalEvent.touchHistory = ResponderTouchHistoryStore.touchHistory;
-      accumulateDirectDispatches(finalEvent);
-      extracted = accumulate(extracted, finalEvent);
-      changeResponder(null);
-    }
-
-    var numberActiveTouches =
-      ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
-    if (
-      ResponderEventPlugin.GlobalInteractionHandler &&
-      numberActiveTouches !== previousActiveTouches
-    ) {
-      ResponderEventPlugin.GlobalInteractionHandler.onChange(
-        numberActiveTouches
-      );
-    }
-    previousActiveTouches = numberActiveTouches;
-
-    return extracted;
-  },
-
-  GlobalResponderHandler: null,
-  GlobalInteractionHandler: null,
-
-  injection: {
-    /**
-     * @param {{onChange: (ReactID, ReactID) => void} GlobalResponderHandler
-     * Object that handles any change in responder. Use this to inject
-     * integration with an existing touch handling system etc.
-     */
-    injectGlobalResponderHandler: function(GlobalResponderHandler) {
-      ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
-    },
-
-    /**
-     * @param {{onChange: (numberActiveTouches) => void} GlobalInteractionHandler
-     * Object that handles any change in the number of active touches.
-     */
-    injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
-      ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
-    }
-  }
-};
-
-var customBubblingEventTypes$1 =
-  ReactNativeViewConfigRegistry.customBubblingEventTypes;
-var customDirectEventTypes$1 =
-  ReactNativeViewConfigRegistry.customDirectEventTypes;
-var eventTypes$2 = ReactNativeViewConfigRegistry.eventTypes;
-
-var ReactNativeBridgeEventPlugin = {
-  eventTypes: eventTypes$2,
-
-  /**
-   * @see {EventPluginHub.extractEvents}
-   */
-  extractEvents: function(
-    topLevelType,
-    targetInst,
-    nativeEvent,
-    nativeEventTarget
-  ) {
-    if (targetInst == null) {
-      // Probably a node belonging to another renderer's tree.
-      return null;
-    }
-    var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType];
-    var directDispatchConfig = customDirectEventTypes$1[topLevelType];
-    invariant(
-      bubbleDispatchConfig || directDispatchConfig,
-      'Unsupported top level event type "%s" dispatched',
-      topLevelType
-    );
-    var event = SyntheticEvent$1.getPooled(
-      bubbleDispatchConfig || directDispatchConfig,
-      targetInst,
-      nativeEvent,
-      nativeEventTarget
-    );
-    if (bubbleDispatchConfig) {
-      accumulateTwoPhaseDispatches(event);
-    } else if (directDispatchConfig) {
-      accumulateDirectDispatches(event);
-    } else {
-      return null;
-    }
-    return event;
-  }
-};
-
-var instanceCache = {};
-var instanceProps = {};
-
-function precacheFiberNode(hostInst, tag) {
-  instanceCache[tag] = hostInst;
-}
-
-function uncacheFiberNode(tag) {
-  delete instanceCache[tag];
-  delete instanceProps[tag];
-}
-
-function getInstanceFromTag(tag) {
-  if (typeof tag === "number") {
-    return instanceCache[tag] || null;
-  } else {
-    // Fabric will invoke event emitters on a direct fiber reference
-    return tag;
-  }
-}
-
-function getTagFromInstance(inst) {
-  var tag = inst.stateNode._nativeTag;
-  if (tag === undefined) {
-    tag = inst.stateNode.canonical._nativeTag;
-  }
-  invariant(tag, "All native instances should have a tag.");
-  return tag;
-}
-
-function getFiberCurrentPropsFromNode$1(stateNode) {
-  return instanceProps[stateNode._nativeTag] || null;
-}
-
-function updateFiberProps(tag, props) {
-  instanceProps[tag] = props;
-}
-
-var ReactNativeComponentTree = Object.freeze({
-  precacheFiberNode: precacheFiberNode,
-  uncacheFiberNode: uncacheFiberNode,
-  getClosestInstanceFromNode: getInstanceFromTag,
-  getInstanceFromNode: getInstanceFromTag,
-  getNodeFromInstance: getTagFromInstance,
-  getFiberCurrentPropsFromNode: getFiberCurrentPropsFromNode$1,
-  updateFiberProps: updateFiberProps
-});
-
-var ReactNativeEventPluginOrder = [
-  "ResponderEventPlugin",
-  "ReactNativeBridgeEventPlugin"
-];
-
-// Module provided by RN:
-var ReactNativeGlobalResponderHandler = {
-  onChange: function(from, to, blockNativeResponder) {
-    if (to !== null) {
-      var tag = to.stateNode._nativeTag;
-      UIManager.setJSResponder(tag, blockNativeResponder);
-    } else {
-      UIManager.clearJSResponder();
-    }
-  }
-};
-
-/**
- * Make sure essential globals are available and are patched correctly. Please don't remove this
- * line. Bundles created by react-packager `require` it before executing any application code. This
- * ensures it exists in the dependency graph and can be `require`d.
- * TODO: require this in packager, not in React #10932517
- */
-// Module provided by RN:
-/**
- * Inject module for resolving DOM hierarchy and plugin ordering.
- */
-injection.injectEventPluginOrder(ReactNativeEventPluginOrder);
-injection$1.injectComponentTree(ReactNativeComponentTree);
-
-ResponderEventPlugin.injection.injectGlobalResponderHandler(
-  ReactNativeGlobalResponderHandler
-);
-
-/**
- * Some important event plugins included by default (without having to require
- * them).
- */
-injection.injectEventPluginsByName({
-  ResponderEventPlugin: ResponderEventPlugin,
-  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
-});
-
-// Use to restore controlled state after a change event has fired.
-
-var fiberHostComponent = null;
-
-var restoreTarget = null;
-var restoreQueue = null;
-
-function restoreStateOfTarget(target) {
-  // We perform this translation at the end of the event loop so that we
-  // always receive the correct fiber here
-  var internalInstance = getInstanceFromNode(target);
-  if (!internalInstance) {
-    // Unmounted
-    return;
-  }
-  invariant(
-    fiberHostComponent &&
-      typeof fiberHostComponent.restoreControlledState === "function",
-    "Fiber needs to be injected to handle a fiber target for controlled " +
-      "events. This error is likely caused by a bug in React. Please file an issue."
-  );
-  var props = getFiberCurrentPropsFromNode(internalInstance.stateNode);
-  fiberHostComponent.restoreControlledState(
-    internalInstance.stateNode,
-    internalInstance.type,
-    props
-  );
-}
-
-function needsStateRestore() {
-  return restoreTarget !== null || restoreQueue !== null;
-}
-
-function restoreStateIfNeeded() {
-  if (!restoreTarget) {
-    return;
-  }
-  var target = restoreTarget;
-  var queuedTargets = restoreQueue;
-  restoreTarget = null;
-  restoreQueue = null;
-
-  restoreStateOfTarget(target);
-  if (queuedTargets) {
-    for (var i = 0; i < queuedTargets.length; i++) {
-      restoreStateOfTarget(queuedTargets[i]);
-    }
-  }
-}
-
-// Used as a way to call batchedUpdates when we don't have a reference to
-// the renderer. Such as when we're dispatching events or if third party
-// libraries need to call batchedUpdates. Eventually, this API will go away when
-// everything is batched by default. We'll then have a similar API to opt-out of
-// scheduled work and instead do synchronous work.
-
-// Defaults
-var _batchedUpdates = function(fn, bookkeeping) {
-  return fn(bookkeeping);
-};
-var _interactiveUpdates = function(fn, a, b) {
-  return fn(a, b);
-};
-var _flushInteractiveUpdates = function() {};
-
-var isBatching = false;
-function batchedUpdates(fn, bookkeeping) {
-  if (isBatching) {
-    // If we are currently inside another batch, we need to wait until it
-    // fully completes before restoring state.
-    return fn(bookkeeping);
-  }
-  isBatching = true;
-  try {
-    return _batchedUpdates(fn, bookkeeping);
-  } finally {
-    // Here we wait until all updates have propagated, which is important
-    // when using controlled components within layers:
-    // https://github.com/facebook/react/issues/1698
-    // Then we restore state of any controlled component.
-    isBatching = false;
-    var controlledComponentsHavePendingUpdates = needsStateRestore();
-    if (controlledComponentsHavePendingUpdates) {
-      // If a controlled event was fired, we may need to restore the state of
-      // the DOM node back to the controlled value. This is necessary when React
-      // bails out of the update without touching the DOM.
-      _flushInteractiveUpdates();
-      restoreStateIfNeeded();
-    }
-  }
-}
-
-var injection$2 = {
-  injectRenderer: function(renderer) {
-    _batchedUpdates = renderer.batchedUpdates;
-    _interactiveUpdates = renderer.interactiveUpdates;
-    _flushInteractiveUpdates = renderer.flushInteractiveUpdates;
-  }
-};
-
-/**
- * Version of `ReactBrowserEventEmitter` that works on the receiving side of a
- * serialized worker boundary.
- */
-
-// Shared default empty native event - conserve memory.
-var EMPTY_NATIVE_EVENT = {};
-
-/**
- * Selects a subsequence of `Touch`es, without destroying `touches`.
- *
- * @param {Array<Touch>} touches Deserialized touch objects.
- * @param {Array<number>} indices Indices by which to pull subsequence.
- * @return {Array<Touch>} Subsequence of touch objects.
- */
-var touchSubsequence = function(touches, indices) {
-  var ret = [];
-  for (var i = 0; i < indices.length; i++) {
-    ret.push(touches[indices[i]]);
-  }
-  return ret;
-};
-
-/**
- * TODO: Pool all of this.
- *
- * Destroys `touches` by removing touch objects at indices `indices`. This is
- * to maintain compatibility with W3C touch "end" events, where the active
- * touches don't include the set that has just been "ended".
- *
- * @param {Array<Touch>} touches Deserialized touch objects.
- * @param {Array<number>} indices Indices to remove from `touches`.
- * @return {Array<Touch>} Subsequence of removed touch objects.
- */
-var removeTouchesAtIndices = function(touches, indices) {
-  var rippedOut = [];
-  // use an unsafe downcast to alias to nullable elements,
-  // so we can delete and then compact.
-  var temp = touches;
-  for (var i = 0; i < indices.length; i++) {
-    var index = indices[i];
-    rippedOut.push(touches[index]);
-    temp[index] = null;
-  }
-  var fillAt = 0;
-  for (var j = 0; j < temp.length; j++) {
-    var cur = temp[j];
-    if (cur !== null) {
-      temp[fillAt++] = cur;
-    }
-  }
-  temp.length = fillAt;
-  return rippedOut;
-};
-
-/**
- * Internal version of `receiveEvent` in terms of normalized (non-tag)
- * `rootNodeID`.
- *
- * @see receiveEvent.
- *
- * @param {rootNodeID} rootNodeID React root node ID that event occurred on.
- * @param {TopLevelType} topLevelType Top level type of event.
- * @param {?object} nativeEventParam Object passed from native.
- */
-function _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam) {
-  var nativeEvent = nativeEventParam || EMPTY_NATIVE_EVENT;
-  var inst = getInstanceFromTag(rootNodeID);
-  batchedUpdates(function() {
-    runExtractedEventsInBatch(
-      topLevelType,
-      inst,
-      nativeEvent,
-      nativeEvent.target
-    );
-  });
-  // React Native doesn't use ReactControlledComponent but if it did, here's
-  // where it would do it.
-}
-
-/**
- * Publicly exposed method on module for native objc to invoke when a top
- * level event is extracted.
- * @param {rootNodeID} rootNodeID React root node ID that event occurred on.
- * @param {TopLevelType} topLevelType Top level type of event.
- * @param {object} nativeEventParam Object passed from native.
- */
-function receiveEvent(rootNodeID, topLevelType, nativeEventParam) {
-  _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam);
-}
-
-/**
- * Simple multi-wrapper around `receiveEvent` that is intended to receive an
- * efficient representation of `Touch` objects, and other information that
- * can be used to construct W3C compliant `Event` and `Touch` lists.
- *
- * This may create dispatch behavior that differs than web touch handling. We
- * loop through each of the changed touches and receive it as a single event.
- * So two `touchStart`/`touchMove`s that occur simultaneously are received as
- * two separate touch event dispatches - when they arguably should be one.
- *
- * This implementation reuses the `Touch` objects themselves as the `Event`s
- * since we dispatch an event for each touch (though that might not be spec
- * compliant). The main purpose of reusing them is to save allocations.
- *
- * TODO: Dispatch multiple changed touches in one event. The bubble path
- * could be the first common ancestor of all the `changedTouches`.
- *
- * One difference between this behavior and W3C spec: cancelled touches will
- * not appear in `.touches`, or in any future `.touches`, though they may
- * still be "actively touching the surface".
- *
- * Web desktop polyfills only need to construct a fake touch event with
- * identifier 0, also abandoning traditional click handlers.
- */
-function receiveTouches(eventTopLevelType, touches, changedIndices) {
-  var changedTouches =
-    eventTopLevelType === "topTouchEnd" ||
-    eventTopLevelType === "topTouchCancel"
-      ? removeTouchesAtIndices(touches, changedIndices)
-      : touchSubsequence(touches, changedIndices);
-
-  for (var jj = 0; jj < changedTouches.length; jj++) {
-    var touch = changedTouches[jj];
-    // Touch objects can fulfill the role of `DOM` `Event` objects if we set
-    // the `changedTouches`/`touches`. This saves allocations.
-    touch.changedTouches = changedTouches;
-    touch.touches = touches;
-    var nativeEvent = touch;
-    var rootNodeID = null;
-    var target = nativeEvent.target;
-    if (target !== null && target !== undefined) {
-      if (target < 1) {
-        {
-          warning(
-            false,
-            "A view is reporting that a touch occurred on tag zero."
-          );
-        }
-      } else {
-        rootNodeID = target;
-      }
-    }
-    // $FlowFixMe Shouldn't we *not* call it if rootNodeID is null?
-    _receiveRootNodeIDEvent(rootNodeID, eventTopLevelType, nativeEvent);
-  }
-}
-
-var ReactNativeEventEmitter = Object.freeze({
-  getListener: getListener,
-  registrationNames: registrationNameModules,
-  _receiveRootNodeIDEvent: _receiveRootNodeIDEvent,
-  receiveEvent: receiveEvent,
-  receiveTouches: receiveTouches
-});
-
-// Module provided by RN:
-/**
- * Register the event emitter with the native bridge
- */
-RCTEventEmitter.register(ReactNativeEventEmitter);
-
-// The Symbol used to tag the ReactElement-like types. If there is no native Symbol
-// nor polyfill, then a plain number is used for performance.
-var hasSymbol = typeof Symbol === "function" && Symbol["for"];
-
-var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
-var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
-var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
-var REACT_STRICT_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.strict_mode")
-  : 0xeacc;
-var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
-var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
-var REACT_ASYNC_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.async_mode")
-  : 0xeacf;
-var REACT_FORWARD_REF_TYPE = hasSymbol
-  ? Symbol["for"]("react.forward_ref")
-  : 0xead0;
-
-var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
-var FAUX_ITERATOR_SYMBOL = "@@iterator";
-
-function getIteratorFn(maybeIterable) {
-  if (maybeIterable === null || typeof maybeIterable === "undefined") {
-    return null;
-  }
-  var maybeIterator =
-    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
-    maybeIterable[FAUX_ITERATOR_SYMBOL];
-  if (typeof maybeIterator === "function") {
-    return maybeIterator;
-  }
-  return null;
-}
-
-function createPortal(
-  children,
-  containerInfo,
-  // TODO: figure out the API for cross-renderer implementation.
-  implementation
-) {
-  var key =
-    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
-
-  return {
-    // This tag allow us to uniquely identify this as a React Portal
-    $$typeof: REACT_PORTAL_TYPE,
-    key: key == null ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
-}
-
-// TODO: this is special because it gets imported during build.
-
-var ReactVersion = "16.3.2";
-
-var describeComponentFrame = function(name, source, ownerName) {
-  return (
-    "\n    in " +
-    (name || "Unknown") +
-    (source
-      ? " (at " +
-        source.fileName.replace(/^.*[\\\/]/, "") +
-        ":" +
-        source.lineNumber +
-        ")"
-      : ownerName ? " (created by " + ownerName + ")" : "")
-  );
-};
-
-function getComponentName(fiber) {
-  var type = fiber.type;
-
-  if (typeof type === "function") {
-    return type.displayName || type.name;
-  }
-  if (typeof type === "string") {
-    return type;
-  }
-  switch (type) {
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
-  }
-  if (typeof type === "object" && type !== null) {
-    switch (type.$$typeof) {
-      case REACT_FORWARD_REF_TYPE:
-        var functionName = type.render.displayName || type.render.name || "";
-        return functionName !== ""
-          ? "ForwardRef(" + functionName + ")"
-          : "ForwardRef";
-    }
-  }
-  return null;
-}
-
-function describeFiber(fiber) {
-  switch (fiber.tag) {
-    case IndeterminateComponent:
-    case FunctionalComponent:
-    case ClassComponent:
-    case HostComponent:
-      var owner = fiber._debugOwner;
-      var source = fiber._debugSource;
-      var name = getComponentName(fiber);
-      var ownerName = null;
-      if (owner) {
-        ownerName = getComponentName(owner);
-      }
-      return describeComponentFrame(name, source, ownerName);
-    default:
-      return "";
-  }
-}
-
-// This function can only be called with a work-in-progress fiber and
-// only during begin or complete phase. Do not call it under any other
-// circumstances.
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  var node = workInProgress;
-  do {
-    info += describeFiber(node);
-    // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
-  } while (node);
-  return info;
-}
-
-// Modules provided by RN:
-var emptyObject$1 = {};
-
-/**
- * Create a payload that contains all the updates between two sets of props.
- *
- * These helpers are all encapsulated into a single module, because they use
- * mutation as a performance optimization which leads to subtle shared
- * dependencies between the code paths. To avoid this mutable state leaking
- * across modules, I've kept them isolated to this module.
- */
-
-// Tracks removed keys
-var removedKeys = null;
-var removedKeyCount = 0;
-
-function defaultDiffer(prevProp, nextProp) {
-  if (typeof nextProp !== "object" || nextProp === null) {
-    // Scalars have already been checked for equality
-    return true;
-  } else {
-    // For objects and arrays, the default diffing algorithm is a deep compare
-    return deepDiffer(prevProp, nextProp);
-  }
-}
-
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node)) {
-    var i = node.length;
-    while (i-- && removedKeyCount > 0) {
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
-    }
-  } else if (node && removedKeyCount > 0) {
-    var obj = node;
-    for (var propKey in removedKeys) {
-      if (!removedKeys[propKey]) {
-        continue;
-      }
-      var _nextProp = obj[propKey];
-      if (_nextProp === undefined) {
-        continue;
-      }
-
-      var attributeConfig = validAttributes[propKey];
-      if (!attributeConfig) {
-        continue; // not a valid native prop
-      }
-
-      if (typeof _nextProp === "function") {
-        _nextProp = true;
-      }
-      if (typeof _nextProp === "undefined") {
-        _nextProp = null;
-      }
-
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = _nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(_nextProp)
-            : _nextProp;
-        updatePayload[propKey] = nextValue;
-      }
-      removedKeys[propKey] = false;
-      removedKeyCount--;
-    }
-  }
-}
-
-function diffNestedArrayProperty(
-  updatePayload,
-  prevArray,
-  nextArray,
-  validAttributes
-) {
-  var minLength =
-    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
-  var i = void 0;
-  for (i = 0; i < minLength; i++) {
-    // Diff any items in the array in the forward direction. Repeated keys
-    // will be overwritten by later values.
-    updatePayload = diffNestedProperty(
-      updatePayload,
-      prevArray[i],
-      nextArray[i],
-      validAttributes
-    );
-  }
-  for (; i < prevArray.length; i++) {
-    // Clear out all remaining properties.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevArray[i],
-      validAttributes
-    );
-  }
-  for (; i < nextArray.length; i++) {
-    // Add all remaining properties.
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextArray[i],
-      validAttributes
-    );
-  }
-  return updatePayload;
-}
-
-function diffNestedProperty(
-  updatePayload,
-  prevProp,
-  nextProp,
-  validAttributes
-) {
-  if (!updatePayload && prevProp === nextProp) {
-    // If no properties have been added, then we can bail out quickly on object
-    // equality.
-    return updatePayload;
-  }
-
-  if (!prevProp || !nextProp) {
-    if (nextProp) {
-      return addNestedProperty(updatePayload, nextProp, validAttributes);
-    }
-    if (prevProp) {
-      return clearNestedProperty(updatePayload, prevProp, validAttributes);
-    }
-    return updatePayload;
-  }
-
-  if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
-    // Both are leaves, we can diff the leaves.
-    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
-  }
-
-  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
-    // Both are arrays, we can diff the arrays.
-    return diffNestedArrayProperty(
-      updatePayload,
-      prevProp,
-      nextProp,
-      validAttributes
-    );
-  }
-
-  if (Array.isArray(prevProp)) {
-    return diffProperties(
-      updatePayload,
-      // $FlowFixMe - We know that this is always an object when the input is.
-      flattenStyle(prevProp),
-      // $FlowFixMe - We know that this isn't an array because of above flow.
-      nextProp,
-      validAttributes
-    );
-  }
-
-  return diffProperties(
-    updatePayload,
-    prevProp,
-    // $FlowFixMe - We know that this is always an object when the input is.
-    flattenStyle(nextProp),
-    validAttributes
-  );
-}
-
-/**
- * addNestedProperty takes a single set of props and valid attribute
- * attribute configurations. It processes each prop and adds it to the
- * updatePayload.
- */
-function addNestedProperty(updatePayload, nextProp, validAttributes) {
-  if (!nextProp) {
-    return updatePayload;
-  }
-
-  if (!Array.isArray(nextProp)) {
-    // Add each property of the leaf.
-    return addProperties(updatePayload, nextProp, validAttributes);
-  }
-
-  for (var i = 0; i < nextProp.length; i++) {
-    // Add all the properties of the array.
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextProp[i],
-      validAttributes
-    );
-  }
-
-  return updatePayload;
-}
-
-/**
- * clearNestedProperty takes a single set of props and valid attributes. It
- * adds a null sentinel to the updatePayload, for each prop key.
- */
-function clearNestedProperty(updatePayload, prevProp, validAttributes) {
-  if (!prevProp) {
-    return updatePayload;
-  }
-
-  if (!Array.isArray(prevProp)) {
-    // Add each property of the leaf.
-    return clearProperties(updatePayload, prevProp, validAttributes);
-  }
-
-  for (var i = 0; i < prevProp.length; i++) {
-    // Add all the properties of the array.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevProp[i],
-      validAttributes
-    );
-  }
-  return updatePayload;
-}
-
-/**
- * diffProperties takes two sets of props and a set of valid attributes
- * and write to updatePayload the values that changed or were deleted.
- * If no updatePayload is provided, a new one is created and returned if
- * anything changed.
- */
-function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
-  var attributeConfig = void 0;
-  var nextProp = void 0;
-  var prevProp = void 0;
-
-  for (var propKey in nextProps) {
-    attributeConfig = validAttributes[propKey];
-    if (!attributeConfig) {
-      continue; // not a valid native prop
-    }
-
-    prevProp = prevProps[propKey];
-    nextProp = nextProps[propKey];
-
-    // functions are converted to booleans as markers that the associated
-    // events should be sent from native.
-    if (typeof nextProp === "function") {
-      nextProp = true;
-      // If nextProp is not a function, then don't bother changing prevProp
-      // since nextProp will win and go into the updatePayload regardless.
-      if (typeof prevProp === "function") {
-        prevProp = true;
-      }
-    }
-
-    // An explicit value of undefined is treated as a null because it overrides
-    // any other preceding value.
-    if (typeof nextProp === "undefined") {
-      nextProp = null;
-      if (typeof prevProp === "undefined") {
-        prevProp = null;
-      }
-    }
-
-    if (removedKeys) {
-      removedKeys[propKey] = false;
-    }
-
-    if (updatePayload && updatePayload[propKey] !== undefined) {
-      // Something else already triggered an update to this key because another
-      // value diffed. Since we're now later in the nested arrays our value is
-      // more important so we need to calculate it and override the existing
-      // value. It doesn't matter if nothing changed, we'll set it anyway.
-
-      // Pattern match on: attributeConfig
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(nextProp)
-            : nextProp;
-        updatePayload[propKey] = nextValue;
-      }
-      continue;
-    }
-
-    if (prevProp === nextProp) {
-      continue; // nothing changed
-    }
-
-    // Pattern match on: attributeConfig
-    if (typeof attributeConfig !== "object") {
-      // case: !Object is the default case
-      if (defaultDiffer(prevProp, nextProp)) {
-        // a normal leaf has changed
-        (updatePayload || (updatePayload = {}))[propKey] = nextProp;
-      }
-    } else if (
-      typeof attributeConfig.diff === "function" ||
-      typeof attributeConfig.process === "function"
-    ) {
-      // case: CustomAttributeConfiguration
-      var shouldUpdate =
-        prevProp === undefined ||
-        (typeof attributeConfig.diff === "function"
-          ? attributeConfig.diff(prevProp, nextProp)
-          : defaultDiffer(prevProp, nextProp));
-      if (shouldUpdate) {
-        var _nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(nextProp)
-            : nextProp;
-        (updatePayload || (updatePayload = {}))[propKey] = _nextValue;
-      }
-    } else {
-      // default: fallthrough case when nested properties are defined
-      removedKeys = null;
-      removedKeyCount = 0;
-      // We think that attributeConfig is not CustomAttributeConfiguration at
-      // this point so we assume it must be AttributeConfiguration.
-      updatePayload = diffNestedProperty(
-        updatePayload,
-        prevProp,
-        nextProp,
-        attributeConfig
-      );
-      if (removedKeyCount > 0 && updatePayload) {
-        restoreDeletedValuesInNestedArray(
-          updatePayload,
-          nextProp,
-          attributeConfig
-        );
-        removedKeys = null;
-      }
-    }
-  }
-
-  // Also iterate through all the previous props to catch any that have been
-  // removed and make sure native gets the signal so it can reset them to the
-  // default.
-  for (var _propKey in prevProps) {
-    if (nextProps[_propKey] !== undefined) {
-      continue; // we've already covered this key in the previous pass
-    }
-    attributeConfig = validAttributes[_propKey];
-    if (!attributeConfig) {
-      continue; // not a valid native prop
-    }
-
-    if (updatePayload && updatePayload[_propKey] !== undefined) {
-      // This was already updated to a diff result earlier.
-      continue;
-    }
-
-    prevProp = prevProps[_propKey];
-    if (prevProp === undefined) {
-      continue; // was already empty anyway
-    }
-    // Pattern match on: attributeConfig
-    if (
-      typeof attributeConfig !== "object" ||
-      typeof attributeConfig.diff === "function" ||
-      typeof attributeConfig.process === "function"
-    ) {
-      // case: CustomAttributeConfiguration | !Object
-      // Flag the leaf property for removal by sending a sentinel.
-      (updatePayload || (updatePayload = {}))[_propKey] = null;
-      if (!removedKeys) {
-        removedKeys = {};
-      }
-      if (!removedKeys[_propKey]) {
-        removedKeys[_propKey] = true;
-        removedKeyCount++;
-      }
-    } else {
-      // default:
-      // This is a nested attribute configuration where all the properties
-      // were removed so we need to go through and clear out all of them.
-      updatePayload = clearNestedProperty(
-        updatePayload,
-        prevProp,
-        attributeConfig
-      );
-    }
-  }
-  return updatePayload;
-}
-
-/**
- * addProperties adds all the valid props to the payload after being processed.
- */
-function addProperties(updatePayload, props, validAttributes) {
-  // TODO: Fast path
-  return diffProperties(updatePayload, emptyObject$1, props, validAttributes);
-}
-
-/**
- * clearProperties clears all the previous props by adding a null sentinel
- * to the payload for each valid key.
- */
-function clearProperties(updatePayload, prevProps, validAttributes) {
-  // TODO: Fast path
-  return diffProperties(
-    updatePayload,
-    prevProps,
-    emptyObject$1,
-    validAttributes
-  );
-}
-
-function create(props, validAttributes) {
-  return addProperties(
-    null, // updatePayload
-    props,
-    validAttributes
-  );
-}
-
-function diff(prevProps, nextProps, validAttributes) {
-  return diffProperties(
-    null, // updatePayload
-    prevProps,
-    nextProps,
-    validAttributes
-  );
-}
-
-/**
- * In the future, we should cleanup callbacks by cancelling them instead of
- * using this.
- */
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (!callback) {
-      return undefined;
-    }
-    if (typeof context.__isMounted === "boolean") {
-      // TODO(gaearon): this is gross and should be removed.
-      // It is currently necessary because View uses createClass,
-      // and so any measure() calls on View (which are done by React
-      // DevTools) trigger the isMounted() deprecation warning.
-      if (!context.__isMounted) {
-        return undefined;
-      }
-      // The else branch is important so that we don't
-      // trigger the deprecation warning by calling isMounted.
-    } else if (typeof context.isMounted === "function") {
-      if (!context.isMounted()) {
-        return undefined;
-      }
-    }
-    return callback.apply(context, arguments);
-  };
-}
-
-function throwOnStylesProp(component, props) {
-  if (props.styles !== undefined) {
-    var owner = component._owner || null;
-    var name = component.constructor.displayName;
-    var msg =
-      "`styles` is not a supported property of `" +
-      name +
-      "`, did " +
-      "you mean `style` (singular)?";
-    if (owner && owner.constructor && owner.constructor.displayName) {
-      msg +=
-        "\n\nCheck the `" +
-        owner.constructor.displayName +
-        "` parent " +
-        " component.";
-    }
-    throw new Error(msg);
-  }
-}
-
-function warnForStyleProps(props, validAttributes) {
-  for (var key in validAttributes.style) {
-    if (!(validAttributes[key] || props[key] === undefined)) {
-      console.error(
-        "You are setting the style `{ " +
-          key +
-          ": ... }` as a prop. You " +
-          "should nest it in a style object. " +
-          "E.g. `{ style: { " +
-          key +
-          ": ... } }`"
-      );
-    }
-  }
-}
-
-// Modules provided by RN:
-var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
-  /**
-   * `NativeMethodsMixin` provides methods to access the underlying native
-   * component directly. This can be useful in cases when you want to focus
-   * a view or measure its on-screen dimensions, for example.
-   *
-   * The methods described here are available on most of the default components
-   * provided by React Native. Note, however, that they are *not* available on
-   * composite components that aren't directly backed by a native view. This will
-   * generally include most components that you define in your own app. For more
-   * information, see [Direct
-   * Manipulation](docs/direct-manipulation.html).
-   *
-   * Note the Flow $Exact<> syntax is required to support mixins.
-   * React createClass mixins can only be used with exact types.
-   */
-  var NativeMethodsMixin = {
-    /**
-     * Determines the location on screen, width, and height of the given view and
-     * returns the values via an async callback. If successful, the callback will
-     * be called with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *  - pageX
-     *  - pageY
-     *
-     * Note that these measurements are not available until after the rendering
-     * has been completed in native. If you need the measurements as soon as
-     * possible, consider using the [`onLayout`
-     * prop](docs/view.html#onlayout) instead.
-     */
-    measure: function(callback) {
-      UIManager.measure(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    },
-
-    /**
-     * Determines the location of the given view in the window and returns the
-     * values via an async callback. If the React root view is embedded in
-     * another native view, this will give you the absolute coordinates. If
-     * successful, the callback will be called with the following
-     * arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *
-     * Note that these measurements are not available until after the rendering
-     * has been completed in native.
-     */
-    measureInWindow: function(callback) {
-      UIManager.measureInWindow(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    },
-
-    /**
-     * Like [`measure()`](#measure), but measures the view relative an ancestor,
-     * specified as `relativeToNativeNode`. This means that the returned x, y
-     * are relative to the origin x, y of the ancestor view.
-     *
-     * As always, to obtain a native node handle for a component, you can use
-     * `findNodeHandle(component)`.
-     */
-    measureLayout: function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail /* currently unused */
-    ) {
-      UIManager.measureLayout(
-        findNodeHandle(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    },
-
-    /**
-     * This function sends props straight to native. They will not participate in
-     * future diff process - this means that if you do not include them in the
-     * next render, they will remain active (see [Direct
-     * Manipulation](docs/direct-manipulation.html)).
-     */
-    setNativeProps: function(nativeProps) {
-      // Class components don't have viewConfig -> validateAttributes.
-      // Nor does it make sense to set native props on a non-native component.
-      // Instead, find the nearest host component and set props on it.
-      // Use findNodeHandle() rather than findNodeHandle() because
-      // We want the instance/wrapper (not the native tag).
-      var maybeInstance = void 0;
-
-      // Fiber errors if findNodeHandle is called for an umounted component.
-      // Tests using ReactTestRenderer will trigger this case indirectly.
-      // Mimicking stack behavior, we should silently ignore this case.
-      // TODO Fix ReactTestRenderer so we can remove this try/catch.
-      try {
-        maybeInstance = findHostInstance(this);
-      } catch (error) {}
-
-      // If there is no host component beneath this we should fail silently.
-      // This is not an error; it could mean a class component rendered null.
-      if (maybeInstance == null) {
-        return;
-      }
-
-      var viewConfig = maybeInstance.viewConfig;
-
-      {
-        warnForStyleProps(nativeProps, viewConfig.validAttributes);
-      }
-
-      var updatePayload = create(nativeProps, viewConfig.validAttributes);
-
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          updatePayload
-        );
-      }
-    },
-
-    /**
-     * Requests focus for the given input or view. The exact behavior triggered
-     * will depend on the platform and type of view.
-     */
-    focus: function() {
-      TextInputState.focusTextInput(findNodeHandle(this));
-    },
-
-    /**
-     * Removes focus from an input or view. This is the opposite of `focus()`.
-     */
-    blur: function() {
-      TextInputState.blurTextInput(findNodeHandle(this));
-    }
-  };
-
-  {
-    // hide this from Flow since we can't define these properties outside of
-    // true without actually implementing them (setting them to undefined
-    // isn't allowed by ReactClass)
-    var NativeMethodsMixin_DEV = NativeMethodsMixin;
-    invariant(
-      !NativeMethodsMixin_DEV.componentWillMount &&
-        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
-        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
-        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
-      "Do not override existing functions."
-    );
-    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
-    // Once these lifecycles have been remove from the reconciler.
-    NativeMethodsMixin_DEV.componentWillMount = function() {
-      throwOnStylesProp(this, this.props);
-    };
-    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
-      throwOnStylesProp(this, newProps);
-    };
-    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
-      throwOnStylesProp(this, this.props);
-    };
-    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
-      newProps
-    ) {
-      throwOnStylesProp(this, newProps);
-    };
-
-    // React may warn about cWM/cWRP/cWU methods being deprecated.
-    // Add a flag to suppress these warnings for this special case.
-    // TODO (bvaughn) Remove this flag once the above methods have been removed.
-    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
-    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
-  }
-
-  return NativeMethodsMixin;
-};
-
-function _classCallCheck(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
-  }
-}
-
-function _possibleConstructorReturn(self, call) {
-  if (!self) {
-    throw new ReferenceError(
-      "this hasn't been initialised - super() hasn't been called"
-    );
-  }
-  return call && (typeof call === "object" || typeof call === "function")
-    ? call
-    : self;
-}
-
-function _inherits(subClass, superClass) {
-  if (typeof superClass !== "function" && superClass !== null) {
-    throw new TypeError(
-      "Super expression must either be null or a function, not " +
-        typeof superClass
-    );
-  }
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: false,
-      writable: true,
-      configurable: true
-    }
-  });
-  if (superClass)
-    Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass);
-}
-
-// Modules provided by RN:
-var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
-  /**
-   * Superclass that provides methods to access the underlying native component.
-   * This can be useful when you want to focus a view or measure its dimensions.
-   *
-   * Methods implemented by this class are available on most default components
-   * provided by React Native. However, they are *not* available on composite
-   * components that are not directly backed by a native view. For more
-   * information, see [Direct Manipulation](docs/direct-manipulation.html).
-   *
-   * @abstract
-   */
-  var ReactNativeComponent = (function(_React$Component) {
-    _inherits(ReactNativeComponent, _React$Component);
-
-    function ReactNativeComponent() {
-      _classCallCheck(this, ReactNativeComponent);
-
-      return _possibleConstructorReturn(
-        this,
-        _React$Component.apply(this, arguments)
-      );
-    }
-
-    /**
-     * Removes focus. This is the opposite of `focus()`.
-     */
-
-    /**
-     * Due to bugs in Flow's handling of React.createClass, some fields already
-     * declared in the base class need to be redeclared below.
-     */
-    ReactNativeComponent.prototype.blur = function blur() {
-      TextInputState.blurTextInput(findNodeHandle(this));
-    };
-
-    /**
-     * Requests focus. The exact behavior depends on the platform and view.
-     */
-
-    ReactNativeComponent.prototype.focus = function focus() {
-      TextInputState.focusTextInput(findNodeHandle(this));
-    };
-
-    /**
-     * Measures the on-screen location and dimensions. If successful, the callback
-     * will be called asynchronously with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *  - pageX
-     *  - pageY
-     *
-     * These values are not available until after natives rendering completes. If
-     * you need the measurements as soon as possible, consider using the
-     * [`onLayout` prop](docs/view.html#onlayout) instead.
-     */
-
-    ReactNativeComponent.prototype.measure = function measure(callback) {
-      UIManager.measure(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    };
-
-    /**
-     * Measures the on-screen location and dimensions. Even if the React Native
-     * root view is embedded within another native view, this method will give you
-     * the absolute coordinates measured from the window. If successful, the
-     * callback will be called asynchronously with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *
-     * These values are not available until after natives rendering completes.
-     */
-
-    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
-      callback
-    ) {
-      UIManager.measureInWindow(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    };
-
-    /**
-     * Similar to [`measure()`](#measure), but the resulting location will be
-     * relative to the supplied ancestor's location.
-     *
-     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
-     */
-
-    ReactNativeComponent.prototype.measureLayout = function measureLayout(
-      relativeToNativeNode,
-      onSuccess,
-      onFail /* currently unused */
-    ) {
-      UIManager.measureLayout(
-        findNodeHandle(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    };
-
-    /**
-     * This function sends props straight to native. They will not participate in
-     * future diff process - this means that if you do not include them in the
-     * next render, they will remain active (see [Direct
-     * Manipulation](docs/direct-manipulation.html)).
-     */
-
-    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
-      nativeProps
-    ) {
-      // Class components don't have viewConfig -> validateAttributes.
-      // Nor does it make sense to set native props on a non-native component.
-      // Instead, find the nearest host component and set props on it.
-      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
-      // We want the instance/wrapper (not the native tag).
-      var maybeInstance = void 0;
-
-      // Fiber errors if findNodeHandle is called for an umounted component.
-      // Tests using ReactTestRenderer will trigger this case indirectly.
-      // Mimicking stack behavior, we should silently ignore this case.
-      // TODO Fix ReactTestRenderer so we can remove this try/catch.
-      try {
-        maybeInstance = findHostInstance(this);
-      } catch (error) {}
-
-      // If there is no host component beneath this we should fail silently.
-      // This is not an error; it could mean a class component rendered null.
-      if (maybeInstance == null) {
-        return;
-      }
-
-      var viewConfig =
-        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
-
-      var updatePayload = create(nativeProps, viewConfig.validAttributes);
-
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          updatePayload
-        );
-      }
-    };
-
-    return ReactNativeComponent;
-  })(React.Component);
-
-  // eslint-disable-next-line no-unused-expressions
-
-  return ReactNativeComponent;
-};
-
-/**
- * `ReactInstanceMap` maintains a mapping from a public facing stateful
- * instance (key) and the internal representation (value). This allows public
- * methods to accept the user facing instance as an argument and map them back
- * to internal methods.
- *
- * Note that this module is currently shared and assumed to be stateless.
- * If this becomes an actual Map, that will break.
- */
-
-/**
- * This API should be called `delete` but we'd have to make sure to always
- * transform these to strings for IE support. When this transform is fully
- * supported we can rename it.
- */
-
-function get$1(key) {
-  return key._reactInternalFiber;
-}
-
-function set(key, value) {
-  key._reactInternalFiber = value;
-}
-
-var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
-
-var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
-var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
-
-// Don't change these two values. They're used by React Dev Tools.
-var NoEffect = /*              */ 0;
-var PerformedWork = /*         */ 1;
-
-// You can change the rest (and add more).
-var Placement = /*             */ 2;
-var Update = /*                */ 4;
-var PlacementAndUpdate = /*    */ 6;
-var Deletion = /*              */ 8;
-var ContentReset = /*          */ 16;
-var Callback = /*              */ 32;
-var DidCapture = /*            */ 64;
-var Ref = /*                   */ 128;
-var ErrLog = /*                */ 256;
-var Snapshot = /*              */ 2048;
-
-// Union of all host effects
-var HostEffectMask = /*        */ 2559;
-
-var Incomplete = /*            */ 512;
-var ShouldCapture = /*         */ 1024;
-
-var MOUNTING = 1;
-var MOUNTED = 2;
-var UNMOUNTED = 3;
-
-function isFiberMountedImpl(fiber) {
-  var node = fiber;
-  if (!fiber.alternate) {
-    // If there is no alternate, this might be a new tree that isn't inserted
-    // yet. If it is, then it will have a pending insertion effect on it.
-    if ((node.effectTag & Placement) !== NoEffect) {
-      return MOUNTING;
-    }
-    while (node["return"]) {
-      node = node["return"];
-      if ((node.effectTag & Placement) !== NoEffect) {
-        return MOUNTING;
-      }
-    }
-  } else {
-    while (node["return"]) {
-      node = node["return"];
-    }
-  }
-  if (node.tag === HostRoot) {
-    // TODO: Check if this was a nested HostRoot when used with
-    // renderContainerIntoSubtree.
-    return MOUNTED;
-  }
-  // If we didn't hit the root, that means that we're in an disconnected tree
-  // that has been unmounted.
-  return UNMOUNTED;
-}
-
-function isFiberMounted(fiber) {
-  return isFiberMountedImpl(fiber) === MOUNTED;
-}
-
-function isMounted(component) {
-  {
-    var owner = ReactCurrentOwner.current;
-    if (owner !== null && owner.tag === ClassComponent) {
-      var ownerFiber = owner;
-      var instance = ownerFiber.stateNode;
-      !instance._warnedAboutRefsInRender
-        ? warning(
-            false,
-            "%s is accessing isMounted inside its render() function. " +
-              "render() should be a pure function of props and state. It should " +
-              "never access something that requires stale data from the previous " +
-              "render, such as refs. Move this logic to componentDidMount and " +
-              "componentDidUpdate instead.",
-            getComponentName(ownerFiber) || "A component"
-          )
-        : void 0;
-      instance._warnedAboutRefsInRender = true;
-    }
-  }
-
-  var fiber = get$1(component);
-  if (!fiber) {
-    return false;
-  }
-  return isFiberMountedImpl(fiber) === MOUNTED;
-}
-
-function assertIsMounted(fiber) {
-  invariant(
-    isFiberMountedImpl(fiber) === MOUNTED,
-    "Unable to find node on an unmounted component."
-  );
-}
-
-function findCurrentFiberUsingSlowPath(fiber) {
-  var alternate = fiber.alternate;
-  if (!alternate) {
-    // If there is no alternate, then we only need to check if it is mounted.
-    var state = isFiberMountedImpl(fiber);
-    invariant(
-      state !== UNMOUNTED,
-      "Unable to find node on an unmounted component."
-    );
-    if (state === MOUNTING) {
-      return null;
-    }
-    return fiber;
-  }
-  // If we have two possible branches, we'll walk backwards up to the root
-  // to see what path the root points to. On the way we may hit one of the
-  // special cases and we'll deal with them.
-  var a = fiber;
-  var b = alternate;
-  while (true) {
-    var parentA = a["return"];
-    var parentB = parentA ? parentA.alternate : null;
-    if (!parentA || !parentB) {
-      // We're at the root.
-      break;
-    }
-
-    // If both copies of the parent fiber point to the same child, we can
-    // assume that the child is current. This happens when we bailout on low
-    // priority: the bailed out fiber's child reuses the current child.
-    if (parentA.child === parentB.child) {
-      var child = parentA.child;
-      while (child) {
-        if (child === a) {
-          // We've determined that A is the current branch.
-          assertIsMounted(parentA);
-          return fiber;
-        }
-        if (child === b) {
-          // We've determined that B is the current branch.
-          assertIsMounted(parentA);
-          return alternate;
-        }
-        child = child.sibling;
-      }
-      // We should never have an alternate for any mounting node. So the only
-      // way this could possibly happen is if this was unmounted, if at all.
-      invariant(false, "Unable to find node on an unmounted component.");
-    }
-
-    if (a["return"] !== b["return"]) {
-      // The return pointer of A and the return pointer of B point to different
-      // fibers. We assume that return pointers never criss-cross, so A must
-      // belong to the child set of A.return, and B must belong to the child
-      // set of B.return.
-      a = parentA;
-      b = parentB;
-    } else {
-      // The return pointers point to the same fiber. We'll have to use the
-      // default, slow path: scan the child sets of each parent alternate to see
-      // which child belongs to which set.
-      //
-      // Search parent A's child set
-      var didFindChild = false;
-      var _child = parentA.child;
-      while (_child) {
-        if (_child === a) {
-          didFindChild = true;
-          a = parentA;
-          b = parentB;
-          break;
-        }
-        if (_child === b) {
-          didFindChild = true;
-          b = parentA;
-          a = parentB;
-          break;
-        }
-        _child = _child.sibling;
-      }
-      if (!didFindChild) {
-        // Search parent B's child set
-        _child = parentB.child;
-        while (_child) {
-          if (_child === a) {
-            didFindChild = true;
-            a = parentB;
-            b = parentA;
-            break;
-          }
-          if (_child === b) {
-            didFindChild = true;
-            b = parentB;
-            a = parentA;
-            break;
-          }
-          _child = _child.sibling;
-        }
-        invariant(
-          didFindChild,
-          "Child was not found in either parent set. This indicates a bug " +
-            "in React related to the return pointer. Please file an issue."
-        );
-      }
-    }
-
-    invariant(
-      a.alternate === b,
-      "Return fibers should always be each others' alternates. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  // If the root is not a host container, we're in a disconnected tree. I.e.
-  // unmounted.
-  invariant(
-    a.tag === HostRoot,
-    "Unable to find node on an unmounted component."
-  );
-  if (a.stateNode.current === a) {
-    // We've determined that A is the current branch.
-    return fiber;
-  }
-  // Otherwise B has to be current branch.
-  return alternate;
-}
-
-function findCurrentHostFiber(parent) {
-  var currentParent = findCurrentFiberUsingSlowPath(parent);
-  if (!currentParent) {
-    return null;
-  }
-
-  // Next we'll drill down this component to find the first HostComponent/Text.
-  var node = currentParent;
-  while (true) {
-    if (node.tag === HostComponent || node.tag === HostText) {
-      return node;
-    } else if (node.child) {
-      node.child["return"] = node;
-      node = node.child;
-      continue;
-    }
-    if (node === currentParent) {
-      return null;
-    }
-    while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
-        return null;
-      }
-      node = node["return"];
-    }
-    node.sibling["return"] = node["return"];
-    node = node.sibling;
-  }
-  // Flow needs the return null here, but ESLint complains about it.
-  // eslint-disable-next-line no-unreachable
-  return null;
-}
-
-function findCurrentHostFiberWithNoPortals(parent) {
-  var currentParent = findCurrentFiberUsingSlowPath(parent);
-  if (!currentParent) {
-    return null;
-  }
-
-  // Next we'll drill down this component to find the first HostComponent/Text.
-  var node = currentParent;
-  while (true) {
-    if (node.tag === HostComponent || node.tag === HostText) {
-      return node;
-    } else if (node.child && node.tag !== HostPortal) {
-      node.child["return"] = node;
-      node = node.child;
-      continue;
-    }
-    if (node === currentParent) {
-      return null;
-    }
-    while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
-        return null;
-      }
-      node = node["return"];
-    }
-    node.sibling["return"] = node["return"];
-    node = node.sibling;
-  }
-  // Flow needs the return null here, but ESLint complains about it.
-  // eslint-disable-next-line no-unreachable
-  return null;
-}
-
-// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
-// Math.pow(2, 30) - 1
-// 0b111111111111111111111111111111
-var MAX_SIGNED_31_BIT_INT = 1073741823;
-
-// TODO: Use an opaque type once ESLint et al support the syntax
-
-var NoWork = 0;
-var Sync = 1;
-var Never = MAX_SIGNED_31_BIT_INT;
-
-var UNIT_SIZE = 10;
-var MAGIC_NUMBER_OFFSET = 2;
-
-// 1 unit of expiration time represents 10ms.
-function msToExpirationTime(ms) {
-  // Always add an offset so that we don't clash with the magic number for NoWork.
-  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
-}
-
-function expirationTimeToMs(expirationTime) {
-  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
-}
-
-function ceiling(num, precision) {
-  return (((num / precision) | 0) + 1) * precision;
-}
-
-function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
-  return ceiling(
-    currentTime + expirationInMs / UNIT_SIZE,
-    bucketSizeMs / UNIT_SIZE
-  );
-}
-
-var NoContext = 0;
-var AsyncMode = 1;
-var StrictMode = 2;
-
-var hasBadMapPolyfill = void 0;
-
-{
-  hasBadMapPolyfill = false;
-  try {
-    var nonExtensibleObject = Object.preventExtensions({});
-    var testMap = new Map([[nonExtensibleObject, null]]);
-    var testSet = new Set([nonExtensibleObject]);
-    // This is necessary for Rollup to not consider these unused.
-    // https://github.com/rollup/rollup/issues/1771
-    // TODO: we can remove these if Rollup fixes the bug.
-    testMap.set(0, 0);
-    testSet.add(0);
-  } catch (e) {
-    // TODO: Consider warning about bad polyfills
-    hasBadMapPolyfill = true;
-  }
-}
-
-// A Fiber is work on a Component that needs to be done or was done. There can
-// be more than one per component.
-
-var debugCounter = void 0;
-
-{
-  debugCounter = 1;
-}
-
-function FiberNode(tag, pendingProps, key, mode) {
-  // Instance
-  this.tag = tag;
-  this.key = key;
-  this.type = null;
-  this.stateNode = null;
-
-  // Fiber
-  this["return"] = null;
-  this.child = null;
-  this.sibling = null;
-  this.index = 0;
-
-  this.ref = null;
-
-  this.pendingProps = pendingProps;
-  this.memoizedProps = null;
-  this.updateQueue = null;
-  this.memoizedState = null;
-
-  this.mode = mode;
-
-  // Effects
-  this.effectTag = NoEffect;
-  this.nextEffect = null;
-
-  this.firstEffect = null;
-  this.lastEffect = null;
-
-  this.expirationTime = NoWork;
-
-  this.alternate = null;
-
-  {
-    this._debugID = debugCounter++;
-    this._debugSource = null;
-    this._debugOwner = null;
-    this._debugIsCurrentlyTiming = false;
-    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
-      Object.preventExtensions(this);
-    }
-  }
-}
-
-// This is a constructor function, rather than a POJO constructor, still
-// please ensure we do the following:
-// 1) Nobody should add any instance methods on this. Instance methods can be
-//    more difficult to predict when they get optimized and they are almost
-//    never inlined properly in static compilers.
-// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
-//    always know when it is a fiber.
-// 3) We might want to experiment with using numeric keys since they are easier
-//    to optimize in a non-JIT environment.
-// 4) We can easily go from a constructor to a createFiber object literal if that
-//    is faster.
-// 5) It should be easy to port this to a C struct and keep a C implementation
-//    compatible.
-var createFiber = function(tag, pendingProps, key, mode) {
-  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
-  return new FiberNode(tag, pendingProps, key, mode);
-};
-
-function shouldConstruct(Component) {
-  return !!(Component.prototype && Component.prototype.isReactComponent);
-}
-
-// This is used to create an alternate fiber to do work on.
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  if (workInProgress === null) {
-    // We use a double buffering pooling technique because we know that we'll
-    // only ever need at most two versions of a tree. We pool the "other" unused
-    // node that we're free to reuse. This is lazily created to avoid allocating
-    // extra objects for things that are never updated. It also allow us to
-    // reclaim the extra memory if needed.
-    workInProgress = createFiber(
-      current.tag,
-      pendingProps,
-      current.key,
-      current.mode
-    );
-    workInProgress.type = current.type;
-    workInProgress.stateNode = current.stateNode;
-
-    {
-      // DEV-only fields
-      workInProgress._debugID = current._debugID;
-      workInProgress._debugSource = current._debugSource;
-      workInProgress._debugOwner = current._debugOwner;
-    }
-
-    workInProgress.alternate = current;
-    current.alternate = workInProgress;
-  } else {
-    workInProgress.pendingProps = pendingProps;
-
-    // We already have an alternate.
-    // Reset the effect tag.
-    workInProgress.effectTag = NoEffect;
-
-    // The effect list is no longer valid.
-    workInProgress.nextEffect = null;
-    workInProgress.firstEffect = null;
-    workInProgress.lastEffect = null;
-  }
-
-  workInProgress.expirationTime = expirationTime;
-
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
-
-  // These will be overridden during the parent's reconciliation
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
-
-  return workInProgress;
-}
-
-function createHostRootFiber(isAsync) {
-  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
-  return createFiber(HostRoot, null, null, mode);
-}
-
-function createFiberFromElement(element, mode, expirationTime) {
-  var owner = null;
-  {
-    owner = element._owner;
-  }
-
-  var fiber = void 0;
-  var type = element.type;
-  var key = element.key;
-  var pendingProps = element.props;
-
-  var fiberTag = void 0;
-  if (typeof type === "function") {
-    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
-  } else if (typeof type === "string") {
-    fiberTag = HostComponent;
-  } else {
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          pendingProps.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= AsyncMode | StrictMode;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= StrictMode;
-        break;
-      case REACT_CALL_TYPE:
-        fiberTag = CallComponent;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = ReturnComponent;
-        break;
-      default: {
-        if (typeof type === "object" && type !== null) {
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = ContextProvider;
-              break;
-            case REACT_CONTEXT_TYPE:
-              // This is a consumer
-              fiberTag = ContextConsumer;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = ForwardRef;
-              break;
-            default:
-              if (typeof type.tag === "number") {
-                // Currently assumed to be a continuation and therefore is a
-                // fiber already.
-                // TODO: The yield system is currently broken for updates in
-                // some cases. The reified yield stores a fiber, but we don't
-                // know which fiber that is; the current or a workInProgress?
-                // When the continuation gets rendered here we don't know if we
-                // can reuse that fiber or if we need to clone it. There is
-                // probably a clever way to restructure this.
-                fiber = type;
-                fiber.pendingProps = pendingProps;
-                fiber.expirationTime = expirationTime;
-                return fiber;
-              } else {
-                throwOnInvalidElementType(type, owner);
-              }
-              break;
-          }
-        } else {
-          throwOnInvalidElementType(type, owner);
-        }
-      }
-    }
-  }
-
-  fiber = createFiber(fiberTag, pendingProps, key, mode);
-  fiber.type = type;
-  fiber.expirationTime = expirationTime;
-
-  {
-    fiber._debugSource = element._source;
-    fiber._debugOwner = element._owner;
-  }
-
-  return fiber;
-}
-
-function throwOnInvalidElementType(type, owner) {
-  var info = "";
-  {
-    if (
-      type === undefined ||
-      (typeof type === "object" &&
-        type !== null &&
-        Object.keys(type).length === 0)
-    ) {
-      info +=
-        " You likely forgot to export your component from the file " +
-        "it's defined in, or you might have mixed up default and " +
-        "named imports.";
-    }
-    var ownerName = owner ? getComponentName(owner) : null;
-    if (ownerName) {
-      info += "\n\nCheck the render method of `" + ownerName + "`.";
-    }
-  }
-  invariant(
-    false,
-    "Element type is invalid: expected a string (for built-in " +
-      "components) or a class/function (for composite components) " +
-      "but got: %s.%s",
-    type == null ? type : typeof type,
-    info
-  );
-}
-
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  var fiber = createFiber(Fragment, elements, key, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
-
-function createFiberFromText(content, mode, expirationTime) {
-  var fiber = createFiber(HostText, content, null, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
-
-function createFiberFromHostInstanceForDeletion() {
-  var fiber = createFiber(HostComponent, null, null, NoContext);
-  fiber.type = "DELETED";
-  return fiber;
-}
-
-function createFiberFromPortal(portal, mode, expirationTime) {
-  var pendingProps = portal.children !== null ? portal.children : [];
-  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null, // Used by persistent updates
-    implementation: portal.implementation
-  };
-  return fiber;
-}
-
-// Used for stashing WIP properties to replay failed work in DEV.
-function assignFiberPropertiesInDEV(target, source) {
-  if (target === null) {
-    // This Fiber's initial properties will always be overwritten.
-    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
-    target = createFiber(IndeterminateComponent, null, null, NoContext);
-  }
-
-  // This is intentionally written as a list of all properties.
-  // We tried to use Object.assign() instead but this is called in
-  // the hottest path, and Object.assign() was too slow:
-  // https://github.com/facebook/react/issues/12502
-  // This code is DEV-only so size is not a concern.
-
-  target.tag = source.tag;
-  target.key = source.key;
-  target.type = source.type;
-  target.stateNode = source.stateNode;
-  target["return"] = source["return"];
-  target.child = source.child;
-  target.sibling = source.sibling;
-  target.index = source.index;
-  target.ref = source.ref;
-  target.pendingProps = source.pendingProps;
-  target.memoizedProps = source.memoizedProps;
-  target.updateQueue = source.updateQueue;
-  target.memoizedState = source.memoizedState;
-  target.mode = source.mode;
-  target.effectTag = source.effectTag;
-  target.nextEffect = source.nextEffect;
-  target.firstEffect = source.firstEffect;
-  target.lastEffect = source.lastEffect;
-  target.expirationTime = source.expirationTime;
-  target.alternate = source.alternate;
-  target._debugID = source._debugID;
-  target._debugSource = source._debugSource;
-  target._debugOwner = source._debugOwner;
-  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
-  return target;
-}
-
-// TODO: This should be lifted into the renderer.
-
-function createFiberRoot(containerInfo, isAsync, hydrate) {
-  // Cyclic construction. This cheats the type system right now because
-  // stateNode is any.
-  var uninitializedFiber = createHostRootFiber(isAsync);
-  var root = {
-    current: uninitializedFiber,
-    containerInfo: containerInfo,
-    pendingChildren: null,
-    pendingCommitExpirationTime: NoWork,
-    finishedWork: null,
-    context: null,
-    pendingContext: null,
-    hydrate: hydrate,
-    remainingExpirationTime: NoWork,
-    firstBatch: null,
-    nextScheduledRoot: null
-  };
-  uninitializedFiber.stateNode = root;
-  return root;
-}
-
-var onCommitFiberRoot = null;
-var onCommitFiberUnmount = null;
-var hasLoggedError = false;
-
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {
-      if (true && !hasLoggedError) {
-        hasLoggedError = true;
-        warning(false, "React DevTools encountered an error: %s", err);
-      }
-    }
-  };
-}
-
-function injectInternals(internals) {
-  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
-    // No DevTools
-    return false;
-  }
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled) {
-    // This isn't a real property on the hook, but it can be set to opt out
-    // of DevTools integration and associated warnings and logs.
-    // https://github.com/facebook/react/issues/3877
-    return true;
-  }
-  if (!hook.supportsFiber) {
-    {
-      warning(
-        false,
-        "The installed version of React DevTools is too old and will not work " +
-          "with the current version of React. Please update React DevTools. " +
-          "https://fb.me/react-devtools"
-      );
-    }
-    // DevTools exists, even though it doesn't support Fiber.
-    return true;
-  }
-  try {
-    var rendererID = hook.inject(internals);
-    // We have successfully injected, so now it is safe to set up hooks.
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {
-    // Catch all errors because it is unsafe to throw during initialization.
-    {
-      warning(false, "React DevTools encountered an error: %s.", err);
-    }
-  }
-  // DevTools exists
-  return true;
-}
-
-function onCommitRoot(root) {
-  if (typeof onCommitFiberRoot === "function") {
-    onCommitFiberRoot(root);
-  }
-}
-
-function onCommitUnmount(fiber) {
-  if (typeof onCommitFiberUnmount === "function") {
-    onCommitFiberUnmount(fiber);
-  }
-}
-
-/**
- * Forked from fbjs/warning:
- * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
- *
- * Only change is we use console.warn instead of console.error,
- * and do nothing when 'console' is not supported.
- * This really simplifies the code.
- * ---
- * Similar to invariant but only logs a warning if the condition is not met.
- * This can be used to log issues in development environments in critical
- * paths. Removing the logging code for production environments will keep the
- * same logic and follow the same code paths.
- */
-
-var lowPriorityWarning = function() {};
-
-{
-  var printWarning = function(format) {
-    for (
-      var _len = arguments.length,
-        args = Array(_len > 1 ? _len - 1 : 0),
-        _key = 1;
-      _key < _len;
-      _key++
-    ) {
-      args[_key - 1] = arguments[_key];
-    }
-
-    var argIndex = 0;
-    var message =
-      "Warning: " +
-      format.replace(/%s/g, function() {
-        return args[argIndex++];
-      });
-    if (typeof console !== "undefined") {
-      console.warn(message);
-    }
-    try {
-      // --- Welcome to debugging React ---
-      // This error was thrown as a convenience so that you can use this stack
-      // to find the callsite that caused this warning to fire.
-      throw new Error(message);
-    } catch (x) {}
-  };
-
-  lowPriorityWarning = function(condition, format) {
-    if (format === undefined) {
-      throw new Error(
-        "`warning(condition, format, ...args)` requires a warning " +
-          "message argument"
-      );
-    }
-    if (!condition) {
-      for (
-        var _len2 = arguments.length,
-          args = Array(_len2 > 2 ? _len2 - 2 : 0),
-          _key2 = 2;
-        _key2 < _len2;
-        _key2++
-      ) {
-        args[_key2 - 2] = arguments[_key2];
-      }
-
-      printWarning.apply(undefined, [format].concat(args));
-    }
-  };
-}
-
-var lowPriorityWarning$1 = lowPriorityWarning;
-
-var ReactStrictModeWarnings = {
-  discardPendingWarnings: function() {},
-  flushPendingDeprecationWarnings: function() {},
-  flushPendingUnsafeLifecycleWarnings: function() {},
-  recordDeprecationWarnings: function(fiber, instance) {},
-  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
-};
-
-{
-  var LIFECYCLE_SUGGESTIONS = {
-    UNSAFE_componentWillMount: "componentDidMount",
-    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
-    UNSAFE_componentWillUpdate: "componentDidUpdate"
-  };
-
-  var pendingComponentWillMountWarnings = [];
-  var pendingComponentWillReceivePropsWarnings = [];
-  var pendingComponentWillUpdateWarnings = [];
-  var pendingUnsafeLifecycleWarnings = new Map();
-
-  // Tracks components we have already warned about.
-  var didWarnAboutDeprecatedLifecycles = new Set();
-  var didWarnAboutUnsafeLifecycles = new Set();
-
-  var setToSortedString = function(set) {
-    var array = [];
-    set.forEach(function(value) {
-      array.push(value);
-    });
-    return array.sort().join(", ");
-  };
-
-  ReactStrictModeWarnings.discardPendingWarnings = function() {
-    pendingComponentWillMountWarnings = [];
-    pendingComponentWillReceivePropsWarnings = [];
-    pendingComponentWillUpdateWarnings = [];
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
-
-  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
-    pendingUnsafeLifecycleWarnings.forEach(function(
-      lifecycleWarningsMap,
-      strictRoot
-    ) {
-      var lifecyclesWarningMesages = [];
-
-      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
-        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
-        if (lifecycleWarnings.length > 0) {
-          var componentNames = new Set();
-          lifecycleWarnings.forEach(function(fiber) {
-            componentNames.add(getComponentName(fiber) || "Component");
-            didWarnAboutUnsafeLifecycles.add(fiber.type);
-          });
-
-          var formatted = lifecycle.replace("UNSAFE_", "");
-          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = setToSortedString(componentNames);
-
-          lifecyclesWarningMesages.push(
-            formatted +
-              ": Please update the following components to use " +
-              (suggestion + " instead: " + sortedComponentNames)
-          );
-        }
-      });
-
-      if (lifecyclesWarningMesages.length > 0) {
-        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
-          strictRoot
-        );
-
-        warning(
-          false,
-          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
-            "\n\n%s" +
-            "\n\nLearn more about this warning here:" +
-            "\nhttps://fb.me/react-strict-mode-warnings",
-          strictRootComponentStack,
-          lifecyclesWarningMesages.join("\n\n")
-        );
-      }
-    });
-
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
-
-  var getStrictRoot = function(fiber) {
-    var maybeStrictRoot = null;
-
-    while (fiber !== null) {
-      if (fiber.mode & StrictMode) {
-        maybeStrictRoot = fiber;
-      }
-
-      fiber = fiber["return"];
-    }
-
-    return maybeStrictRoot;
-  };
-
-  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
-    if (pendingComponentWillMountWarnings.length > 0) {
-      var uniqueNames = new Set();
-      pendingComponentWillMountWarnings.forEach(function(fiber) {
-        uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var sortedNames = setToSortedString(uniqueNames);
-
-      lowPriorityWarning$1(
-        false,
-        "componentWillMount is deprecated and will be removed in the next major version. " +
-          "Use componentDidMount instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillMount." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        sortedNames
-      );
-
-      pendingComponentWillMountWarnings = [];
-    }
-
-    if (pendingComponentWillReceivePropsWarnings.length > 0) {
-      var _uniqueNames = new Set();
-      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
-        _uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames = setToSortedString(_uniqueNames);
-
-      lowPriorityWarning$1(
-        false,
-        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
-          "Use static getDerivedStateFromProps instead." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames
-      );
-
-      pendingComponentWillReceivePropsWarnings = [];
-    }
-
-    if (pendingComponentWillUpdateWarnings.length > 0) {
-      var _uniqueNames2 = new Set();
-      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
-        _uniqueNames2.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames2 = setToSortedString(_uniqueNames2);
-
-      lowPriorityWarning$1(
-        false,
-        "componentWillUpdate is deprecated and will be removed in the next major version. " +
-          "Use componentDidUpdate instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillUpdate." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames2
-      );
-
-      pendingComponentWillUpdateWarnings = [];
-    }
-  };
-
-  ReactStrictModeWarnings.recordDeprecationWarnings = function(
-    fiber,
-    instance
-  ) {
-    // Dedup strategy: Warn once per component.
-    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
-      return;
-    }
-
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillMountWarnings.push(fiber);
-    }
-    if (
-      typeof instance.componentWillReceiveProps === "function" &&
-      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillReceivePropsWarnings.push(fiber);
-    }
-    if (
-      typeof instance.componentWillUpdate === "function" &&
-      instance.componentWillUpdate.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillUpdateWarnings.push(fiber);
-    }
-  };
-
-  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
-    fiber,
-    instance
-  ) {
-    var strictRoot = getStrictRoot(fiber);
-
-    // Dedup strategy: Warn once per component.
-    // This is difficult to track any other way since component names
-    // are often vague and are likely to collide between 3rd party libraries.
-    // An expand property is probably okay to use here since it's DEV-only,
-    // and will only be set in the event of serious warnings.
-    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
-      return;
-    }
-
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    // Note that it is sufficient to check for the presence of a
-    // single lifecycle, componentWillMount, with the polyfill flag.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning === true
-    ) {
-      return;
-    }
-
-    var warningsForRoot = void 0;
-    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
-      warningsForRoot = {
-        UNSAFE_componentWillMount: [],
-        UNSAFE_componentWillReceiveProps: [],
-        UNSAFE_componentWillUpdate: []
-      };
-
-      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
-    } else {
-      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
-    }
-
-    var unsafeLifecycles = [];
-    if (
-      typeof instance.componentWillMount === "function" ||
-      typeof instance.UNSAFE_componentWillMount === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillMount");
-    }
-    if (
-      typeof instance.componentWillReceiveProps === "function" ||
-      typeof instance.UNSAFE_componentWillReceiveProps === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
-    }
-    if (
-      typeof instance.componentWillUpdate === "function" ||
-      typeof instance.UNSAFE_componentWillUpdate === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
-    }
-
-    if (unsafeLifecycles.length > 0) {
-      unsafeLifecycles.forEach(function(lifecycle) {
-        warningsForRoot[lifecycle].push(fiber);
-      });
-    }
-  };
-}
-
-// Re-export dynamic flags from the fbsource version.
-var _require = require("ReactFeatureFlags");
-
-var enableGetDerivedStateFromCatch = _require.enableGetDerivedStateFromCatch;
-var debugRenderPhaseSideEffects = _require.debugRenderPhaseSideEffects;
-var debugRenderPhaseSideEffectsForStrictMode =
-  _require.debugRenderPhaseSideEffectsForStrictMode;
-var warnAboutDeprecatedLifecycles = _require.warnAboutDeprecatedLifecycles;
-var replayFailedUnitOfWorkWithInvokeGuardedCallback =
-  _require.replayFailedUnitOfWorkWithInvokeGuardedCallback;
-
-var enableUserTimingAPI = true;
-var enableMutatingReconciler = true;
-var enableNoopReconciler = false;
-var enablePersistentReconciler = false;
-
-// Only used in www builds.
-
-function getCurrentFiberOwnerName() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    var owner = fiber._debugOwner;
-    if (owner !== null && typeof owner !== "undefined") {
-      return getComponentName(owner);
-    }
-  }
-  return null;
-}
-
-function getCurrentFiberStackAddendum() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    // Safe because if current fiber exists, we are reconciling,
-    // and it is guaranteed to be the work-in-progress version.
-    return getStackAddendumByWorkInProgressFiber(fiber);
-  }
-  return null;
-}
-
-function resetCurrentFiber() {
-  ReactDebugCurrentFrame.getCurrentStack = null;
-  ReactDebugCurrentFiber.current = null;
-  ReactDebugCurrentFiber.phase = null;
-}
-
-function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
-  ReactDebugCurrentFiber.current = fiber;
-  ReactDebugCurrentFiber.phase = null;
-}
-
-function setCurrentPhase(phase) {
-  ReactDebugCurrentFiber.phase = phase;
-}
-
-var ReactDebugCurrentFiber = {
-  current: null,
-  phase: null,
-  resetCurrentFiber: resetCurrentFiber,
-  setCurrentFiber: setCurrentFiber,
-  setCurrentPhase: setCurrentPhase,
-  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
-};
-
-// Prefix measurements so that it's possible to filter them.
-// Longer prefixes are hard to read in DevTools.
-var reactEmoji = "\u269B";
-var warningEmoji = "\u26D4";
-var supportsUserTiming =
-  typeof performance !== "undefined" &&
-  typeof performance.mark === "function" &&
-  typeof performance.clearMarks === "function" &&
-  typeof performance.measure === "function" &&
-  typeof performance.clearMeasures === "function";
-
-// Keep track of current fiber so that we know the path to unwind on pause.
-// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
-var currentFiber = null;
-// If we're in the middle of user code, which fiber and method is it?
-// Reusing `currentFiber` would be confusing for this because user code fiber
-// can change during commit phase too, but we don't need to unwind it (since
-// lifecycles in the commit phase don't resemble a tree).
-var currentPhase = null;
-var currentPhaseFiber = null;
-// Did lifecycle hook schedule an update? This is often a performance problem,
-// so we will keep track of it, and include it in the report.
-// Track commits caused by cascading updates.
-var isCommitting = false;
-var hasScheduledUpdateInCurrentCommit = false;
-var hasScheduledUpdateInCurrentPhase = false;
-var commitCountInCurrentWorkLoop = 0;
-var effectCountInCurrentCommit = 0;
-var isWaitingForCallback = false;
-// During commits, we only show a measurement once per method name
-// to avoid stretch the commit phase with measurement overhead.
-var labelsInCurrentCommit = new Set();
-
-var formatMarkName = function(markName) {
-  return reactEmoji + " " + markName;
-};
-
-var formatLabel = function(label, warning$$1) {
-  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
-  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
-  return "" + prefix + label + suffix;
-};
-
-var beginMark = function(markName) {
-  performance.mark(formatMarkName(markName));
-};
-
-var clearMark = function(markName) {
-  performance.clearMarks(formatMarkName(markName));
-};
-
-var endMark = function(label, markName, warning$$1) {
-  var formattedMarkName = formatMarkName(markName);
-  var formattedLabel = formatLabel(label, warning$$1);
-  try {
-    performance.measure(formattedLabel, formattedMarkName);
-  } catch (err) {}
-  // If previous mark was missing for some reason, this will throw.
-  // This could only happen if React crashed in an unexpected place earlier.
-  // Don't pile on with more errors.
-
-  // Clear marks immediately to avoid growing buffer.
-  performance.clearMarks(formattedMarkName);
-  performance.clearMeasures(formattedLabel);
-};
-
-var getFiberMarkName = function(label, debugID) {
-  return label + " (#" + debugID + ")";
-};
-
-var getFiberLabel = function(componentName, isMounted, phase) {
-  if (phase === null) {
-    // These are composite component total time measurements.
-    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
-  } else {
-    // Composite component methods.
-    return componentName + "." + phase;
-  }
-};
-
-var beginFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-
-  if (isCommitting && labelsInCurrentCommit.has(label)) {
-    // During the commit phase, we don't show duplicate labels because
-    // there is a fixed overhead for every measurement, and we don't
-    // want to stretch the commit phase beyond necessary.
-    return false;
-  }
-  labelsInCurrentCommit.add(label);
-
-  var markName = getFiberMarkName(label, debugID);
-  beginMark(markName);
-  return true;
-};
-
-var clearFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  clearMark(markName);
-};
-
-var endFiberMark = function(fiber, phase, warning$$1) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  endMark(label, markName, warning$$1);
-};
-
-var shouldIgnoreFiber = function(fiber) {
-  // Host components should be skipped in the timeline.
-  // We could check typeof fiber.type, but does this work with RN?
-  switch (fiber.tag) {
-    case HostRoot:
-    case HostComponent:
-    case HostText:
-    case HostPortal:
-    case CallComponent:
-    case ReturnComponent:
-    case Fragment:
-    case ContextProvider:
-    case ContextConsumer:
-    case Mode:
-      return true;
-    default:
-      return false;
-  }
-};
-
-var clearPendingPhaseMeasurement = function() {
-  if (currentPhase !== null && currentPhaseFiber !== null) {
-    clearFiberMark(currentPhaseFiber, currentPhase);
-  }
-  currentPhaseFiber = null;
-  currentPhase = null;
-  hasScheduledUpdateInCurrentPhase = false;
-};
-
-var pauseTimers = function() {
-  // Stops all currently active measurements so that they can be resumed
-  // if we continue in a later deferred loop from the same unit of work.
-  var fiber = currentFiber;
-  while (fiber) {
-    if (fiber._debugIsCurrentlyTiming) {
-      endFiberMark(fiber, null, null);
-    }
-    fiber = fiber["return"];
-  }
-};
-
-var resumeTimersRecursively = function(fiber) {
-  if (fiber["return"] !== null) {
-    resumeTimersRecursively(fiber["return"]);
-  }
-  if (fiber._debugIsCurrentlyTiming) {
-    beginFiberMark(fiber, null);
-  }
-};
-
-var resumeTimers = function() {
-  // Resumes all measurements that were active during the last deferred loop.
-  if (currentFiber !== null) {
-    resumeTimersRecursively(currentFiber);
-  }
-};
-
-function recordEffect() {
-  if (enableUserTimingAPI) {
-    effectCountInCurrentCommit++;
-  }
-}
-
-function recordScheduleUpdate() {
-  if (enableUserTimingAPI) {
-    if (isCommitting) {
-      hasScheduledUpdateInCurrentCommit = true;
-    }
-    if (
-      currentPhase !== null &&
-      currentPhase !== "componentWillMount" &&
-      currentPhase !== "componentWillReceiveProps"
-    ) {
-      hasScheduledUpdateInCurrentPhase = true;
-    }
-  }
-}
-
-function startRequestCallbackTimer() {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming && !isWaitingForCallback) {
-      isWaitingForCallback = true;
-      beginMark("(Waiting for async callback...)");
-    }
-  }
-}
-
-function stopRequestCallbackTimer(didExpire, expirationTime) {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming) {
-      isWaitingForCallback = false;
-      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
-      endMark(
-        "(Waiting for async callback... will force flush in " +
-          expirationTime +
-          " ms)",
-        "(Waiting for async callback...)",
-        warning$$1
-      );
-    }
-  }
-}
-
-function startWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, this is the fiber to unwind from.
-    currentFiber = fiber;
-    if (!beginFiberMark(fiber, null)) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = true;
-  }
-}
-
-function cancelWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // Remember we shouldn't complete measurement for this fiber.
-    // Otherwise flamechart will be deep even for small updates.
-    fiber._debugIsCurrentlyTiming = false;
-    clearFiberMark(fiber, null);
-  }
-}
-
-function stopWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    endFiberMark(fiber, null, null);
-  }
-}
-
-function stopFailedWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    var warning$$1 = "An error was thrown inside this error boundary";
-    endFiberMark(fiber, null, warning$$1);
-  }
-}
-
-function startPhaseTimer(fiber, phase) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    clearPendingPhaseMeasurement();
-    if (!beginFiberMark(fiber, phase)) {
-      return;
-    }
-    currentPhaseFiber = fiber;
-    currentPhase = phase;
-  }
-}
-
-function stopPhaseTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    if (currentPhase !== null && currentPhaseFiber !== null) {
-      var warning$$1 = hasScheduledUpdateInCurrentPhase
-        ? "Scheduled a cascading update"
-        : null;
-      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
-    }
-    currentPhase = null;
-    currentPhaseFiber = null;
-  }
-}
-
-function startWorkLoopTimer(nextUnitOfWork) {
-  if (enableUserTimingAPI) {
-    currentFiber = nextUnitOfWork;
-    if (!supportsUserTiming) {
-      return;
-    }
-    commitCountInCurrentWorkLoop = 0;
-    // This is top level call.
-    // Any other measurements are performed within.
-    beginMark("(React Tree Reconciliation)");
-    // Resume any measurements that were in progress during the last loop.
-    resumeTimers();
-  }
-}
-
-function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var warning$$1 = null;
-    if (interruptedBy !== null) {
-      if (interruptedBy.tag === HostRoot) {
-        warning$$1 = "A top-level update interrupted the previous render";
-      } else {
-        var componentName = getComponentName(interruptedBy) || "Unknown";
-        warning$$1 =
-          "An update to " + componentName + " interrupted the previous render";
-      }
-    } else if (commitCountInCurrentWorkLoop > 1) {
-      warning$$1 = "There were cascading updates";
-    }
-    commitCountInCurrentWorkLoop = 0;
-    var label = didCompleteRoot
-      ? "(React Tree Reconciliation: Completed Root)"
-      : "(React Tree Reconciliation: Yielded)";
-    // Pause any measurements until the next loop.
-    pauseTimers();
-    endMark(label, "(React Tree Reconciliation)", warning$$1);
-  }
-}
-
-function startCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    isCommitting = true;
-    hasScheduledUpdateInCurrentCommit = false;
-    labelsInCurrentCommit.clear();
-    beginMark("(Committing Changes)");
-  }
-}
-
-function stopCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-
-    var warning$$1 = null;
-    if (hasScheduledUpdateInCurrentCommit) {
-      warning$$1 = "Lifecycle hook scheduled a cascading update";
-    } else if (commitCountInCurrentWorkLoop > 0) {
-      warning$$1 = "Caused by a cascading update in earlier commit";
-    }
-    hasScheduledUpdateInCurrentCommit = false;
-    commitCountInCurrentWorkLoop++;
-    isCommitting = false;
-    labelsInCurrentCommit.clear();
-
-    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
-  }
-}
-
-function startCommitSnapshotEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Snapshot Effects)");
-  }
-}
-
-function stopCommitSnapshotEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Snapshot Effects: " + count + " Total)",
-      "(Committing Snapshot Effects)",
-      null
-    );
-  }
-}
-
-function startCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Host Effects)");
-  }
-}
-
-function stopCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Host Effects: " + count + " Total)",
-      "(Committing Host Effects)",
-      null
-    );
-  }
-}
-
-function startCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Calling Lifecycle Methods)");
-  }
-}
-
-function stopCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Calling Lifecycle Methods: " + count + " Total)",
-      "(Calling Lifecycle Methods)",
-      null
-    );
-  }
-}
-
-var didWarnUpdateInsideUpdate = void 0;
-
-{
-  didWarnUpdateInsideUpdate = false;
-}
-
-// Callbacks are not validated until invocation
-
-// Singly linked-list of updates. When an update is scheduled, it is added to
-// the queue of the current fiber and the work-in-progress fiber. The two queues
-// are separate but they share a persistent structure.
-//
-// During reconciliation, updates are removed from the work-in-progress fiber,
-// but they remain on the current fiber. That ensures that if a work-in-progress
-// is aborted, the aborted updates are recovered by cloning from current.
-//
-// The work-in-progress queue is always a subset of the current queue.
-//
-// When the tree is committed, the work-in-progress becomes the current.
-
-function createUpdateQueue(baseState) {
-  var queue = {
-    baseState: baseState,
-    expirationTime: NoWork,
-    first: null,
-    last: null,
-    callbackList: null,
-    hasForceUpdate: false,
-    isInitialized: false,
-    capturedValues: null
-  };
-  {
-    queue.isProcessing = false;
-  }
-  return queue;
-}
-
-function insertUpdateIntoQueue(queue, update) {
-  // Append the update to the end of the list.
-  if (queue.last === null) {
-    // Queue is empty
-    queue.first = queue.last = update;
-  } else {
-    queue.last.next = update;
-    queue.last = update;
-  }
-  if (
-    queue.expirationTime === NoWork ||
-    queue.expirationTime > update.expirationTime
-  ) {
-    queue.expirationTime = update.expirationTime;
-  }
-}
-
-var q1 = void 0;
-var q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  // We'll have at least one and at most two distinct update queues.
-  var alternateFiber = fiber.alternate;
-  var queue1 = fiber.updateQueue;
-  if (queue1 === null) {
-    // TODO: We don't know what the base state will be until we begin work.
-    // It depends on which fiber is the next current. Initialize with an empty
-    // base state, then set to the memoizedState when rendering. Not super
-    // happy with this approach.
-    queue1 = fiber.updateQueue = createUpdateQueue(null);
-  }
-
-  var queue2 = void 0;
-  if (alternateFiber !== null) {
-    queue2 = alternateFiber.updateQueue;
-    if (queue2 === null) {
-      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
-    }
-  } else {
-    queue2 = null;
-  }
-  queue2 = queue2 !== queue1 ? queue2 : null;
-
-  // Use module variables instead of returning a tuple
-  q1 = queue1;
-  q2 = queue2;
-}
-
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  var queue1 = q1;
-  var queue2 = q2;
-
-  // Warn if an update is scheduled from inside an updater function.
-  {
-    if (
-      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
-      !didWarnUpdateInsideUpdate
-    ) {
-      warning(
-        false,
-        "An update (setState, replaceState, or forceUpdate) was scheduled " +
-          "from inside an update function. Update functions should be pure, " +
-          "with zero side-effects. Consider using componentDidUpdate or a " +
-          "callback."
-      );
-      didWarnUpdateInsideUpdate = true;
-    }
-  }
-
-  // If there's only one queue, add the update to that queue and exit.
-  if (queue2 === null) {
-    insertUpdateIntoQueue(queue1, update);
-    return;
-  }
-
-  // If either queue is empty, we need to add to both queues.
-  if (queue1.last === null || queue2.last === null) {
-    insertUpdateIntoQueue(queue1, update);
-    insertUpdateIntoQueue(queue2, update);
-    return;
-  }
-
-  // If both lists are not empty, the last update is the same for both lists
-  // because of structural sharing. So, we should only append to one of
-  // the lists.
-  insertUpdateIntoQueue(queue1, update);
-  // But we still need to update the `last` pointer of queue2.
-  queue2.last = update;
-}
-
-function getUpdateExpirationTime(fiber) {
-  switch (fiber.tag) {
-    case HostRoot:
-    case ClassComponent:
-      var updateQueue = fiber.updateQueue;
-      if (updateQueue === null) {
-        return NoWork;
-      }
-      return updateQueue.expirationTime;
-    default:
-      return NoWork;
-  }
-}
-
-function getStateFromUpdate(update, instance, prevState, props) {
-  var partialState = update.partialState;
-  if (typeof partialState === "function") {
-    return partialState.call(instance, prevState, props);
-  } else {
-    return partialState;
-  }
-}
-
-function processUpdateQueue(
-  current,
-  workInProgress,
-  queue,
-  instance,
-  props,
-  renderExpirationTime
-) {
-  if (current !== null && current.updateQueue === queue) {
-    // We need to create a work-in-progress queue, by cloning the current queue.
-    var currentQueue = queue;
-    queue = workInProgress.updateQueue = {
-      baseState: currentQueue.baseState,
-      expirationTime: currentQueue.expirationTime,
-      first: currentQueue.first,
-      last: currentQueue.last,
-      isInitialized: currentQueue.isInitialized,
-      capturedValues: currentQueue.capturedValues,
-      // These fields are no longer valid because they were already committed.
-      // Reset them.
-      callbackList: null,
-      hasForceUpdate: false
-    };
-  }
-
-  {
-    // Set this flag so we can warn if setState is called inside the update
-    // function of another setState.
-    queue.isProcessing = true;
-  }
-
-  // Reset the remaining expiration time. If we skip over any updates, we'll
-  // increase this accordingly.
-  queue.expirationTime = NoWork;
-
-  // TODO: We don't know what the base state will be until we begin work.
-  // It depends on which fiber is the next current. Initialize with an empty
-  // base state, then set to the memoizedState when rendering. Not super
-  // happy with this approach.
-  var state = void 0;
-  if (queue.isInitialized) {
-    state = queue.baseState;
-  } else {
-    state = queue.baseState = workInProgress.memoizedState;
-    queue.isInitialized = true;
-  }
-  var dontMutatePrevState = true;
-  var update = queue.first;
-  var didSkip = false;
-  while (update !== null) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      // This update does not have sufficient priority. Skip it.
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        remainingExpirationTime === NoWork ||
-        remainingExpirationTime > updateExpirationTime
-      ) {
-        // Update the remaining expiration time.
-        queue.expirationTime = updateExpirationTime;
-      }
-      if (!didSkip) {
-        didSkip = true;
-        queue.baseState = state;
-      }
-      // Continue to the next update.
-      update = update.next;
-      continue;
-    }
-
-    // This update does have sufficient priority.
-
-    // If no previous updates were skipped, drop this update from the queue by
-    // advancing the head of the list.
-    if (!didSkip) {
-      queue.first = update.next;
-      if (queue.first === null) {
-        queue.last = null;
-      }
-    }
-
-    // Invoke setState callback an extra time to help detect side-effects.
-    // Ignore the return value in this case.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      getStateFromUpdate(update, instance, state, props);
-    }
-
-    // Process the update
-    var _partialState = void 0;
-    if (update.isReplace) {
-      state = getStateFromUpdate(update, instance, state, props);
-      dontMutatePrevState = true;
-    } else {
-      _partialState = getStateFromUpdate(update, instance, state, props);
-      if (_partialState) {
-        if (dontMutatePrevState) {
-          // $FlowFixMe: Idk how to type this properly.
-          state = Object.assign({}, state, _partialState);
-        } else {
-          state = Object.assign(state, _partialState);
-        }
-        dontMutatePrevState = false;
-      }
-    }
-    if (update.isForced) {
-      queue.hasForceUpdate = true;
-    }
-    if (update.callback !== null) {
-      // Append to list of callbacks.
-      var _callbackList = queue.callbackList;
-      if (_callbackList === null) {
-        _callbackList = queue.callbackList = [];
-      }
-      _callbackList.push(update);
-    }
-    if (update.capturedValue !== null) {
-      var _capturedValues = queue.capturedValues;
-      if (_capturedValues === null) {
-        queue.capturedValues = [update.capturedValue];
-      } else {
-        _capturedValues.push(update.capturedValue);
-      }
-    }
-    update = update.next;
-  }
-
-  if (queue.callbackList !== null) {
-    workInProgress.effectTag |= Callback;
-  } else if (
-    queue.first === null &&
-    !queue.hasForceUpdate &&
-    queue.capturedValues === null
-  ) {
-    // The queue is empty. We can reset it.
-    workInProgress.updateQueue = null;
-  }
-
-  if (!didSkip) {
-    didSkip = true;
-    queue.baseState = state;
-  }
-
-  {
-    // No longer processing.
-    queue.isProcessing = false;
-  }
-
-  return state;
-}
-
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (callbackList === null) {
-    return;
-  }
-  // Set the list to null to make sure they don't get called more than once.
-  queue.callbackList = null;
-  for (var i = 0; i < callbackList.length; i++) {
-    var update = callbackList[i];
-    var _callback = update.callback;
-    // This update might be processed again. Clear the callback so it's only
-    // called once.
-    update.callback = null;
-    invariant(
-      typeof _callback === "function",
-      "Invalid argument passed as callback. Expected a function. Instead " +
-        "received: %s",
-      _callback
-    );
-    _callback.call(context);
-  }
-}
-
-var fakeInternalInstance = {};
-var isArray = Array.isArray;
-
-var didWarnAboutStateAssignmentForComponent = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
-var didWarnAboutUninitializedState = void 0;
-var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
-var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
-var warnOnInvalidCallback = void 0;
-
-{
-  didWarnAboutStateAssignmentForComponent = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
-  didWarnAboutUninitializedState = new Set();
-  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
-  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
-
-  var didWarnOnInvalidCallback = new Set();
-
-  warnOnInvalidCallback = function(callback, callerName) {
-    if (callback === null || typeof callback === "function") {
-      return;
-    }
-    var key = callerName + "_" + callback;
-    if (!didWarnOnInvalidCallback.has(key)) {
-      didWarnOnInvalidCallback.add(key);
-      warning(
-        false,
-        "%s(...): Expected the last optional `callback` argument to be a " +
-          "function. Instead received: %s.",
-        callerName,
-        callback
-      );
-    }
-  };
-
-  // This is so gross but it's at least non-critical and can be removed if
-  // it causes problems. This is meant to give a nicer error message for
-  // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
-  // ...)) which otherwise throws a "_processChildContext is not a function"
-  // exception.
-  Object.defineProperty(fakeInternalInstance, "_processChildContext", {
-    enumerable: false,
-    value: function() {
-      invariant(
-        false,
-        "_processChildContext is not available in React 16+. This likely " +
-          "means you have multiple copies of React and are attempting to nest " +
-          "a React 15 tree inside a React 16 tree using " +
-          "unstable_renderSubtreeIntoContainer, which isn't supported. Try " +
-          "to make sure you have only one copy of React (and ideally, switch " +
-          "to ReactDOM.createPortal)."
-      );
-    }
-  });
-  Object.freeze(fakeInternalInstance);
-}
-function callGetDerivedStateFromCatch(ctor, capturedValues) {
-  var resultState = {};
-  for (var i = 0; i < capturedValues.length; i++) {
-    var capturedValue = capturedValues[i];
-    var error = capturedValue.value;
-    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
-    if (partialState !== null && partialState !== undefined) {
-      Object.assign(resultState, partialState);
-    }
-  }
-  return resultState;
-}
-
-var ReactFiberClassComponent = function(
-  legacyContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState
-) {
-  var cacheContext = legacyContext.cacheContext,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    isContextConsumer = legacyContext.isContextConsumer,
-    hasContextChanged = legacyContext.hasContextChanged;
-
-  // Class component state updater
-
-  var updater = {
-    isMounted: isMounted,
-    enqueueSetState: function(instance, partialState, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "setState");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: partialState,
-        callback: callback,
-        isReplace: false,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
-      scheduleWork(fiber, expirationTime);
-    },
-    enqueueReplaceState: function(instance, state, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "replaceState");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: state,
-        callback: callback,
-        isReplace: true,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
-      scheduleWork(fiber, expirationTime);
-    },
-    enqueueForceUpdate: function(instance, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "forceUpdate");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: null,
-        callback: callback,
-        isReplace: false,
-        isForced: true,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
-      scheduleWork(fiber, expirationTime);
-    }
-  };
-
-  function checkShouldComponentUpdate(
-    workInProgress,
-    oldProps,
-    newProps,
-    oldState,
-    newState,
-    newContext
-  ) {
-    if (
-      oldProps === null ||
-      (workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate)
-    ) {
-      // If the workInProgress already has an Update effect, return true
-      return true;
-    }
-
-    var instance = workInProgress.stateNode;
-    var ctor = workInProgress.type;
-    if (typeof instance.shouldComponentUpdate === "function") {
-      startPhaseTimer(workInProgress, "shouldComponentUpdate");
-      var shouldUpdate = instance.shouldComponentUpdate(
-        newProps,
-        newState,
-        newContext
-      );
-      stopPhaseTimer();
-
-      {
-        !(shouldUpdate !== undefined)
-          ? warning(
-              false,
-              "%s.shouldComponentUpdate(): Returned undefined instead of a " +
-                "boolean value. Make sure to return true or false.",
-              getComponentName(workInProgress) || "Component"
-            )
-          : void 0;
-      }
-
-      return shouldUpdate;
-    }
-
-    if (ctor.prototype && ctor.prototype.isPureReactComponent) {
-      return (
-        !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
-      );
-    }
-
-    return true;
-  }
-
-  function checkClassInstance(workInProgress) {
-    var instance = workInProgress.stateNode;
-    var type = workInProgress.type;
-    {
-      var name = getComponentName(workInProgress) || "Component";
-      var renderPresent = instance.render;
-
-      if (!renderPresent) {
-        if (type.prototype && typeof type.prototype.render === "function") {
-          warning(
-            false,
-            "%s(...): No `render` method found on the returned component " +
-              "instance: did you accidentally return an object from the constructor?",
-            name
-          );
-        } else {
-          warning(
-            false,
-            "%s(...): No `render` method found on the returned component " +
-              "instance: you may have forgotten to define `render`.",
-            name
-          );
-        }
-      }
-
-      var noGetInitialStateOnES6 =
-        !instance.getInitialState ||
-        instance.getInitialState.isReactClassApproved ||
-        instance.state;
-      !noGetInitialStateOnES6
-        ? warning(
-            false,
-            "getInitialState was defined on %s, a plain JavaScript class. " +
-              "This is only supported for classes created using React.createClass. " +
-              "Did you mean to define a state property instead?",
-            name
-          )
-        : void 0;
-      var noGetDefaultPropsOnES6 =
-        !instance.getDefaultProps ||
-        instance.getDefaultProps.isReactClassApproved;
-      !noGetDefaultPropsOnES6
-        ? warning(
-            false,
-            "getDefaultProps was defined on %s, a plain JavaScript class. " +
-              "This is only supported for classes created using React.createClass. " +
-              "Use a static property to define defaultProps instead.",
-            name
-          )
-        : void 0;
-      var noInstancePropTypes = !instance.propTypes;
-      !noInstancePropTypes
-        ? warning(
-            false,
-            "propTypes was defined as an instance property on %s. Use a static " +
-              "property to define propTypes instead.",
-            name
-          )
-        : void 0;
-      var noInstanceContextTypes = !instance.contextTypes;
-      !noInstanceContextTypes
-        ? warning(
-            false,
-            "contextTypes was defined as an instance property on %s. Use a static " +
-              "property to define contextTypes instead.",
-            name
-          )
-        : void 0;
-      var noComponentShouldUpdate =
-        typeof instance.componentShouldUpdate !== "function";
-      !noComponentShouldUpdate
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
-              "The name is phrased as a question because the function is " +
-              "expected to return a value.",
-            name
-          )
-        : void 0;
-      if (
-        type.prototype &&
-        type.prototype.isPureReactComponent &&
-        typeof instance.shouldComponentUpdate !== "undefined"
-      ) {
-        warning(
-          false,
-          "%s has a method called shouldComponentUpdate(). " +
-            "shouldComponentUpdate should not be used when extending React.PureComponent. " +
-            "Please extend React.Component if shouldComponentUpdate is used.",
-          getComponentName(workInProgress) || "A pure component"
-        );
-      }
-      var noComponentDidUnmount =
-        typeof instance.componentDidUnmount !== "function";
-      !noComponentDidUnmount
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentDidUnmount(). But there is no such lifecycle method. " +
-              "Did you mean componentWillUnmount()?",
-            name
-          )
-        : void 0;
-      var noComponentDidReceiveProps =
-        typeof instance.componentDidReceiveProps !== "function";
-      !noComponentDidReceiveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentDidReceiveProps(). But there is no such lifecycle method. " +
-              "If you meant to update the state in response to changing props, " +
-              "use componentWillReceiveProps(). If you meant to fetch data or " +
-              "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
-            name
-          )
-        : void 0;
-      var noComponentWillRecieveProps =
-        typeof instance.componentWillRecieveProps !== "function";
-      !noComponentWillRecieveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
-            name
-          )
-        : void 0;
-      var noUnsafeComponentWillRecieveProps =
-        typeof instance.UNSAFE_componentWillRecieveProps !== "function";
-      !noUnsafeComponentWillRecieveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
-            name
-          )
-        : void 0;
-      var hasMutatedProps = instance.props !== workInProgress.pendingProps;
-      !(instance.props === undefined || !hasMutatedProps)
-        ? warning(
-            false,
-            "%s(...): When calling super() in `%s`, make sure to pass " +
-              "up the same props that your component's constructor was passed.",
-            name,
-            name
-          )
-        : void 0;
-      var noInstanceDefaultProps = !instance.defaultProps;
-      !noInstanceDefaultProps
-        ? warning(
-            false,
-            "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
-              " Instead, define defaultProps as a static property on %s.",
-            name,
-            name
-          )
-        : void 0;
-
-      if (
-        typeof instance.getSnapshotBeforeUpdate === "function" &&
-        typeof instance.componentDidUpdate !== "function" &&
-        !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
-      ) {
-        didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
-        warning(
-          false,
-          "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
-            "This component defines getSnapshotBeforeUpdate() only.",
-          getComponentName(workInProgress)
-        );
-      }
-
-      var noInstanceGetDerivedStateFromProps =
-        typeof instance.getDerivedStateFromProps !== "function";
-      !noInstanceGetDerivedStateFromProps
-        ? warning(
-            false,
-            "%s: getDerivedStateFromProps() is defined as an instance method " +
-              "and will be ignored. Instead, declare it as a static method.",
-            name
-          )
-        : void 0;
-      var noInstanceGetDerivedStateFromCatch =
-        typeof instance.getDerivedStateFromCatch !== "function";
-      !noInstanceGetDerivedStateFromCatch
-        ? warning(
-            false,
-            "%s: getDerivedStateFromCatch() is defined as an instance method " +
-              "and will be ignored. Instead, declare it as a static method.",
-            name
-          )
-        : void 0;
-      var noStaticGetSnapshotBeforeUpdate =
-        typeof type.getSnapshotBeforeUpdate !== "function";
-      !noStaticGetSnapshotBeforeUpdate
-        ? warning(
-            false,
-            "%s: getSnapshotBeforeUpdate() is defined as a static method " +
-              "and will be ignored. Instead, declare it as an instance method.",
-            name
-          )
-        : void 0;
-      var _state = instance.state;
-      if (_state && (typeof _state !== "object" || isArray(_state))) {
-        warning(false, "%s.state: must be set to an object or null", name);
-      }
-      if (typeof instance.getChildContext === "function") {
-        !(typeof type.childContextTypes === "object")
-          ? warning(
-              false,
-              "%s.getChildContext(): childContextTypes must be defined in order to " +
-                "use getChildContext().",
-              name
-            )
-          : void 0;
-      }
-    }
-  }
-
-  function resetInputPointers(workInProgress, instance) {
-    instance.props = workInProgress.memoizedProps;
-    instance.state = workInProgress.memoizedState;
-  }
-
-  function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
-    workInProgress.stateNode = instance;
-    // The instance needs access to the fiber so that it can schedule updates
-    set(instance, workInProgress);
-    {
-      instance._reactInternalInstance = fakeInternalInstance;
-    }
-  }
-
-  function constructClassInstance(workInProgress, props) {
-    var ctor = workInProgress.type;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var needsContext = isContextConsumer(workInProgress);
-    var context = needsContext
-      ? getMaskedContext(workInProgress, unmaskedContext)
-      : emptyObject;
-
-    // Instantiate twice to help detect side-effects.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      new ctor(props, context); // eslint-disable-line no-new
-    }
-
-    var instance = new ctor(props, context);
-    var state =
-      instance.state !== null && instance.state !== undefined
-        ? instance.state
-        : null;
-    adoptClassInstance(workInProgress, instance);
-
-    {
-      if (
-        typeof ctor.getDerivedStateFromProps === "function" &&
-        state === null
-      ) {
-        var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutUninitializedState.has(componentName)) {
-          didWarnAboutUninitializedState.add(componentName);
-          warning(
-            false,
-            "%s: Did not properly initialize state during construction. " +
-              "Expected state to be an object, but it was %s.",
-            componentName,
-            instance.state === null ? "null" : "undefined"
-          );
-        }
-      }
-
-      // If new component APIs are defined, "unsafe" lifecycles won't be called.
-      // Warn about these lifecycles if they are present.
-      // Don't warn about react-lifecycles-compat polyfilled methods though.
-      if (
-        typeof ctor.getDerivedStateFromProps === "function" ||
-        typeof instance.getSnapshotBeforeUpdate === "function"
-      ) {
-        var foundWillMountName = null;
-        var foundWillReceivePropsName = null;
-        var foundWillUpdateName = null;
-        if (
-          typeof instance.componentWillMount === "function" &&
-          instance.componentWillMount.__suppressDeprecationWarning !== true
-        ) {
-          foundWillMountName = "componentWillMount";
-        } else if (typeof instance.UNSAFE_componentWillMount === "function") {
-          foundWillMountName = "UNSAFE_componentWillMount";
-        }
-        if (
-          typeof instance.componentWillReceiveProps === "function" &&
-          instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-            true
-        ) {
-          foundWillReceivePropsName = "componentWillReceiveProps";
-        } else if (
-          typeof instance.UNSAFE_componentWillReceiveProps === "function"
-        ) {
-          foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
-        }
-        if (
-          typeof instance.componentWillUpdate === "function" &&
-          instance.componentWillUpdate.__suppressDeprecationWarning !== true
-        ) {
-          foundWillUpdateName = "componentWillUpdate";
-        } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          foundWillUpdateName = "UNSAFE_componentWillUpdate";
-        }
-        if (
-          foundWillMountName !== null ||
-          foundWillReceivePropsName !== null ||
-          foundWillUpdateName !== null
-        ) {
-          var _componentName = getComponentName(workInProgress) || "Component";
-          var newApiName =
-            typeof ctor.getDerivedStateFromProps === "function"
-              ? "getDerivedStateFromProps()"
-              : "getSnapshotBeforeUpdate()";
-          if (
-            !didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)
-          ) {
-            didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
-            warning(
-              false,
-              "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
-                "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
-                "The above lifecycles should be removed. Learn more about this warning here:\n" +
-                "https://fb.me/react-async-component-lifecycle-hooks",
-              _componentName,
-              newApiName,
-              foundWillMountName !== null ? "\n  " + foundWillMountName : "",
-              foundWillReceivePropsName !== null
-                ? "\n  " + foundWillReceivePropsName
-                : "",
-              foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
-            );
-          }
-        }
-      }
-    }
-
-    workInProgress.memoizedState = state;
-
-    var partialState = callGetDerivedStateFromProps(
-      workInProgress,
-      instance,
-      props,
-      state
-    );
-
-    if (partialState !== null && partialState !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      workInProgress.memoizedState = Object.assign(
-        {},
-        workInProgress.memoizedState,
-        partialState
-      );
-    }
-
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // ReactFiberContext usually updates this cache but can't for newly-created instances.
-    if (needsContext) {
-      cacheContext(workInProgress, unmaskedContext, context);
-    }
-
-    return instance;
-  }
-
-  function callComponentWillMount(workInProgress, instance) {
-    startPhaseTimer(workInProgress, "componentWillMount");
-    var oldState = instance.state;
-
-    if (typeof instance.componentWillMount === "function") {
-      instance.componentWillMount();
-    }
-    if (typeof instance.UNSAFE_componentWillMount === "function") {
-      instance.UNSAFE_componentWillMount();
-    }
-
-    stopPhaseTimer();
-
-    if (oldState !== instance.state) {
-      {
-        warning(
-          false,
-          "%s.componentWillMount(): Assigning directly to this.state is " +
-            "deprecated (except inside a component's " +
-            "constructor). Use setState instead.",
-          getComponentName(workInProgress) || "Component"
-        );
-      }
-      updater.enqueueReplaceState(instance, instance.state, null);
-    }
-  }
-
-  function callComponentWillReceiveProps(
-    workInProgress,
-    instance,
-    newProps,
-    newContext
-  ) {
-    var oldState = instance.state;
-    startPhaseTimer(workInProgress, "componentWillReceiveProps");
-    if (typeof instance.componentWillReceiveProps === "function") {
-      instance.componentWillReceiveProps(newProps, newContext);
-    }
-    if (typeof instance.UNSAFE_componentWillReceiveProps === "function") {
-      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
-    }
-    stopPhaseTimer();
-
-    if (instance.state !== oldState) {
-      {
-        var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
-          didWarnAboutStateAssignmentForComponent.add(componentName);
-          warning(
-            false,
-            "%s.componentWillReceiveProps(): Assigning directly to " +
-              "this.state is deprecated (except inside a component's " +
-              "constructor). Use setState instead.",
-            componentName
-          );
-        }
-      }
-      updater.enqueueReplaceState(instance, instance.state, null);
-    }
-  }
-
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    var type = workInProgress.type;
-
-    if (typeof type.getDerivedStateFromProps === "function") {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        // Invoke method an extra time to help detect side-effects.
-        type.getDerivedStateFromProps.call(null, nextProps, prevState);
-      }
-
-      var partialState = type.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
-
-      {
-        if (partialState === undefined) {
-          var componentName = getComponentName(workInProgress) || "Component";
-          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-            didWarnAboutUndefinedDerivedState.add(componentName);
-            warning(
-              false,
-              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-                "You have returned undefined.",
-              componentName
-            );
-          }
-        }
-      }
-
-      return partialState;
-    }
-  }
-
-  // Invokes the mount life-cycles on a previously never rendered instance.
-  function mountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var current = workInProgress.alternate;
-
-    {
-      checkClassInstance(workInProgress);
-    }
-
-    var instance = workInProgress.stateNode;
-    var props = workInProgress.pendingProps;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-
-    instance.props = props;
-    instance.state = workInProgress.memoizedState;
-    instance.refs = emptyObject;
-    instance.context = getMaskedContext(workInProgress, unmaskedContext);
-
-    {
-      if (workInProgress.mode & StrictMode) {
-        ReactStrictModeWarnings.recordUnsafeLifecycleWarnings(
-          workInProgress,
-          instance
-        );
-      }
-
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.recordDeprecationWarnings(
-          workInProgress,
-          instance
-        );
-      }
-    }
-
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      typeof ctor.getDerivedStateFromProps !== "function" &&
-      typeof instance.getSnapshotBeforeUpdate !== "function" &&
-      (typeof instance.UNSAFE_componentWillMount === "function" ||
-        typeof instance.componentWillMount === "function")
-    ) {
-      callComponentWillMount(workInProgress, instance);
-      // If we had additional state updates during this life-cycle, let's
-      // process them now.
-      var updateQueue = workInProgress.updateQueue;
-      if (updateQueue !== null) {
-        instance.state = processUpdateQueue(
-          current,
-          workInProgress,
-          updateQueue,
-          instance,
-          props,
-          renderExpirationTime
-        );
-      }
-    }
-    if (typeof instance.componentDidMount === "function") {
-      workInProgress.effectTag |= Update;
-    }
-  }
-
-  function resumeMountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
-
-    var oldProps = workInProgress.memoizedProps;
-    var newProps = workInProgress.pendingProps;
-    var oldContext = instance.context;
-    var newUnmaskedContext = getUnmaskedContext(workInProgress);
-    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
-
-    var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
-      typeof instance.getSnapshotBeforeUpdate === "function";
-
-    // Note: During these life-cycles, instance.props/instance.state are what
-    // ever the previously attempted to render - not the "current". However,
-    // during componentDidUpdate we pass the "current" props.
-
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      !hasNewLifecycles &&
-      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function")
-    ) {
-      if (oldProps !== newProps || oldContext !== newContext) {
-        callComponentWillReceiveProps(
-          workInProgress,
-          instance,
-          newProps,
-          newContext
-        );
-      }
-    }
-
-    // Compute the next state using the memoized state and the update queue.
-    var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        null,
-        workInProgress,
-        workInProgress.updateQueue,
-        instance,
-        newProps,
-        renderExpirationTime
-      );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
-    }
-
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
-        instance,
-        newProps,
-        newState
-      );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue = workInProgress.updateQueue;
-      if (_updateQueue !== null) {
-        _updateQueue.baseState = Object.assign(
-          {},
-          _updateQueue.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue2 = workInProgress.updateQueue;
-      if (_updateQueue2 !== null) {
-        _updateQueue2.baseState = Object.assign(
-          {},
-          _updateQueue2.baseState,
-          derivedStateFromCatch
-        );
-      }
-    }
-
-    if (
-      oldProps === newProps &&
-      oldState === newState &&
-      !hasContextChanged() &&
-      !(
-        workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate
-      )
-    ) {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-      return false;
-    }
-
-    var shouldUpdate = checkShouldComponentUpdate(
-      workInProgress,
-      oldProps,
-      newProps,
-      oldState,
-      newState,
-      newContext
-    );
-
-    if (shouldUpdate) {
-      // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for components using the new APIs.
-      if (
-        !hasNewLifecycles &&
-        (typeof instance.UNSAFE_componentWillMount === "function" ||
-          typeof instance.componentWillMount === "function")
-      ) {
-        startPhaseTimer(workInProgress, "componentWillMount");
-        if (typeof instance.componentWillMount === "function") {
-          instance.componentWillMount();
-        }
-        if (typeof instance.UNSAFE_componentWillMount === "function") {
-          instance.UNSAFE_componentWillMount();
-        }
-        stopPhaseTimer();
-      }
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-    } else {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-
-      // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
-    }
-
-    // Update the existing instance's state, props, and context pointers even
-    // if shouldComponentUpdate returns false.
-    instance.props = newProps;
-    instance.state = newState;
-    instance.context = newContext;
-
-    return shouldUpdate;
-  }
-
-  // Invokes the update life-cycles and returns false if it shouldn't rerender.
-  function updateClassInstance(current, workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
-
-    var oldProps = workInProgress.memoizedProps;
-    var newProps = workInProgress.pendingProps;
-    var oldContext = instance.context;
-    var newUnmaskedContext = getUnmaskedContext(workInProgress);
-    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
-
-    var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
-      typeof instance.getSnapshotBeforeUpdate === "function";
-
-    // Note: During these life-cycles, instance.props/instance.state are what
-    // ever the previously attempted to render - not the "current". However,
-    // during componentDidUpdate we pass the "current" props.
-
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      !hasNewLifecycles &&
-      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function")
-    ) {
-      if (oldProps !== newProps || oldContext !== newContext) {
-        callComponentWillReceiveProps(
-          workInProgress,
-          instance,
-          newProps,
-          newContext
-        );
-      }
-    }
-
-    // Compute the next state using the memoized state and the update queue.
-    var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        current,
-        workInProgress,
-        workInProgress.updateQueue,
-        instance,
-        newProps,
-        renderExpirationTime
-      );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
-    }
-
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
-        instance,
-        newProps,
-        newState
-      );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue3 = workInProgress.updateQueue;
-      if (_updateQueue3 !== null) {
-        _updateQueue3.baseState = Object.assign(
-          {},
-          _updateQueue3.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue4 = workInProgress.updateQueue;
-      if (_updateQueue4 !== null) {
-        _updateQueue4.baseState = Object.assign(
-          {},
-          _updateQueue4.baseState,
-          derivedStateFromCatch
-        );
-      }
-    }
-
-    if (
-      oldProps === newProps &&
-      oldState === newState &&
-      !hasContextChanged() &&
-      !(
-        workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate
-      )
-    ) {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Update;
-        }
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Snapshot;
-        }
-      }
-      return false;
-    }
-
-    var shouldUpdate = checkShouldComponentUpdate(
-      workInProgress,
-      oldProps,
-      newProps,
-      oldState,
-      newState,
-      newContext
-    );
-
-    if (shouldUpdate) {
-      // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for components using the new APIs.
-      if (
-        !hasNewLifecycles &&
-        (typeof instance.UNSAFE_componentWillUpdate === "function" ||
-          typeof instance.componentWillUpdate === "function")
-      ) {
-        startPhaseTimer(workInProgress, "componentWillUpdate");
-        if (typeof instance.componentWillUpdate === "function") {
-          instance.componentWillUpdate(newProps, newState, newContext);
-        }
-        if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
-        }
-        stopPhaseTimer();
-      }
-      if (typeof instance.componentDidUpdate === "function") {
-        workInProgress.effectTag |= Update;
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        workInProgress.effectTag |= Snapshot;
-      }
-    } else {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Update;
-        }
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Snapshot;
-        }
-      }
-
-      // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
-    }
-
-    // Update the existing instance's state, props, and context pointers even
-    // if shouldComponentUpdate returns false.
-    instance.props = newProps;
-    instance.state = newState;
-    instance.context = newContext;
-
-    return shouldUpdate;
-  }
-
-  return {
-    adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
-    constructClassInstance: constructClassInstance,
-    mountClassInstance: mountClassInstance,
-    resumeMountClassInstance: resumeMountClassInstance,
-    updateClassInstance: updateClassInstance
-  };
-};
-
-var getCurrentFiberStackAddendum$1 =
-  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
-
-var didWarnAboutMaps = void 0;
-var didWarnAboutStringRefInStrictMode = void 0;
-var ownerHasKeyUseWarning = void 0;
-var ownerHasFunctionTypeWarning = void 0;
-var warnForMissingKey = function(child) {};
-
-{
-  didWarnAboutMaps = false;
-  didWarnAboutStringRefInStrictMode = {};
-
-  /**
-   * Warn if there's no key explicitly set on dynamic arrays of children or
-   * object keys are not valid. This allows us to keep track of children between
-   * updates.
-   */
-  ownerHasKeyUseWarning = {};
-  ownerHasFunctionTypeWarning = {};
-
-  warnForMissingKey = function(child) {
-    if (child === null || typeof child !== "object") {
-      return;
-    }
-    if (!child._store || child._store.validated || child.key != null) {
-      return;
-    }
-    invariant(
-      typeof child._store === "object",
-      "React Component in warnForMissingKey should have a _store. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-    child._store.validated = true;
-
-    var currentComponentErrorInfo =
-      "Each child in an array or iterator should have a unique " +
-      '"key" prop. See https://fb.me/react-warning-keys for ' +
-      "more information." +
-      (getCurrentFiberStackAddendum$1() || "");
-    if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
-      return;
-    }
-    ownerHasKeyUseWarning[currentComponentErrorInfo] = true;
-
-    warning(
-      false,
-      "Each child in an array or iterator should have a unique " +
-        '"key" prop. See https://fb.me/react-warning-keys for ' +
-        "more information.%s",
-      getCurrentFiberStackAddendum$1()
-    );
-  };
-}
-
-var isArray$1 = Array.isArray;
-
-function coerceRef(returnFiber, current, element) {
-  var mixedRef = element.ref;
-  if (
-    mixedRef !== null &&
-    typeof mixedRef !== "function" &&
-    typeof mixedRef !== "object"
-  ) {
-    {
-      if (returnFiber.mode & StrictMode) {
-        var componentName = getComponentName(returnFiber) || "Component";
-        if (!didWarnAboutStringRefInStrictMode[componentName]) {
-          warning(
-            false,
-            'A string ref, "%s", has been found within a strict mode tree. ' +
-              "String refs are a source of potential bugs and should be avoided. " +
-              "We recommend using createRef() instead." +
-              "\n%s" +
-              "\n\nLearn more about using refs safely here:" +
-              "\nhttps://fb.me/react-strict-mode-string-ref",
-            mixedRef,
-            getStackAddendumByWorkInProgressFiber(returnFiber)
-          );
-          didWarnAboutStringRefInStrictMode[componentName] = true;
-        }
-      }
-    }
-
-    if (element._owner) {
-      var owner = element._owner;
-      var inst = void 0;
-      if (owner) {
-        var ownerFiber = owner;
-        invariant(
-          ownerFiber.tag === ClassComponent,
-          "Stateless function components cannot have refs."
-        );
-        inst = ownerFiber.stateNode;
-      }
-      invariant(
-        inst,
-        "Missing owner for string ref %s. This error is likely caused by a " +
-          "bug in React. Please file an issue.",
-        mixedRef
-      );
-      var stringRef = "" + mixedRef;
-      // Check if previous string ref matches new string ref
-      if (
-        current !== null &&
-        current.ref !== null &&
-        current.ref._stringRef === stringRef
-      ) {
-        return current.ref;
-      }
-      var ref = function(value) {
-        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
-        if (value === null) {
-          delete refs[stringRef];
-        } else {
-          refs[stringRef] = value;
-        }
-      };
-      ref._stringRef = stringRef;
-      return ref;
-    } else {
-      invariant(
-        typeof mixedRef === "string",
-        "Expected ref to be a function or a string."
-      );
-      invariant(
-        element._owner,
-        "Element ref was specified as a string (%s) but no owner was set. This could happen for one of" +
-          " the following reasons:\n" +
-          "1. You may be adding a ref to a functional component\n" +
-          "2. You may be adding a ref to a component that was not created inside a component's render method\n" +
-          "3. You have multiple copies of React loaded\n" +
-          "See https://fb.me/react-refs-must-have-owner for more information.",
-        mixedRef
-      );
-    }
-  }
-  return mixedRef;
-}
-
-function throwOnInvalidObjectType(returnFiber, newChild) {
-  if (returnFiber.type !== "textarea") {
-    var addendum = "";
-    {
-      addendum =
-        " If you meant to render a collection of children, use an array " +
-        "instead." +
-        (getCurrentFiberStackAddendum$1() || "");
-    }
-    invariant(
-      false,
-      "Objects are not valid as a React child (found: %s).%s",
-      Object.prototype.toString.call(newChild) === "[object Object]"
-        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
-        : newChild,
-      addendum
-    );
-  }
-}
-
-function warnOnFunctionType() {
-  var currentComponentErrorInfo =
-    "Functions are not valid as a React child. This may happen if " +
-    "you return a Component instead of <Component /> from render. " +
-    "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$1() || "");
-
-  if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
-    return;
-  }
-  ownerHasFunctionTypeWarning[currentComponentErrorInfo] = true;
-
-  warning(
-    false,
-    "Functions are not valid as a React child. This may happen if " +
-      "you return a Component instead of <Component /> from render. " +
-      "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$1() || ""
-  );
-}
-
-// This wrapper function exists because I expect to clone the code in each path
-// to be able to optimize each path individually by branching early. This needs
-// a compiler or we can do it manually. Helpers that don't need this branching
-// live outside of this function.
-function ChildReconciler(shouldTrackSideEffects) {
-  function deleteChild(returnFiber, childToDelete) {
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return;
-    }
-    // Deletions are added in reversed order so we add it to the front.
-    // At this point, the return fiber's effect list is empty except for
-    // deletions, so we can just append the deletion to the list. The remaining
-    // effects aren't added until the complete phase. Once we implement
-    // resuming, this may not be true.
-    var last = returnFiber.lastEffect;
-    if (last !== null) {
-      last.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
-    } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
-    }
-    childToDelete.nextEffect = null;
-    childToDelete.effectTag = Deletion;
-  }
-
-  function deleteRemainingChildren(returnFiber, currentFirstChild) {
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return null;
-    }
-
-    // TODO: For the shouldClone case, this could be micro-optimized a bit by
-    // assuming that after the first child we've already added everything.
-    var childToDelete = currentFirstChild;
-    while (childToDelete !== null) {
-      deleteChild(returnFiber, childToDelete);
-      childToDelete = childToDelete.sibling;
-    }
-    return null;
-  }
-
-  function mapRemainingChildren(returnFiber, currentFirstChild) {
-    // Add the remaining children to a temporary map so that we can find them by
-    // keys quickly. Implicit (null) keys get added to this set with their index
-    var existingChildren = new Map();
-
-    var existingChild = currentFirstChild;
-    while (existingChild !== null) {
-      if (existingChild.key !== null) {
-        existingChildren.set(existingChild.key, existingChild);
-      } else {
-        existingChildren.set(existingChild.index, existingChild);
-      }
-      existingChild = existingChild.sibling;
-    }
-    return existingChildren;
-  }
-
-  function useFiber(fiber, pendingProps, expirationTime) {
-    // We currently set sibling to null and index to 0 here because it is easy
-    // to forget to do before returning it. E.g. for the single child case.
-    var clone = createWorkInProgress(fiber, pendingProps, expirationTime);
-    clone.index = 0;
-    clone.sibling = null;
-    return clone;
-  }
-
-  function placeChild(newFiber, lastPlacedIndex, newIndex) {
-    newFiber.index = newIndex;
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return lastPlacedIndex;
-    }
-    var current = newFiber.alternate;
-    if (current !== null) {
-      var oldIndex = current.index;
-      if (oldIndex < lastPlacedIndex) {
-        // This is a move.
-        newFiber.effectTag = Placement;
-        return lastPlacedIndex;
-      } else {
-        // This item can stay in place.
-        return oldIndex;
-      }
-    } else {
-      // This is an insertion.
-      newFiber.effectTag = Placement;
-      return lastPlacedIndex;
-    }
-  }
-
-  function placeSingleChild(newFiber) {
-    // This is simpler for the single child case. We only need to do a
-    // placement for inserting new children.
-    if (shouldTrackSideEffects && newFiber.alternate === null) {
-      newFiber.effectTag = Placement;
-    }
-    return newFiber;
-  }
-
-  function updateTextNode(returnFiber, current, textContent, expirationTime) {
-    if (current === null || current.tag !== HostText) {
-      // Insert
-      var created = createFiberFromText(
-        textContent,
-        returnFiber.mode,
-        expirationTime
-      );
-      created["return"] = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, textContent, expirationTime);
-      existing["return"] = returnFiber;
-      return existing;
-    }
-  }
-
-  function updateElement(returnFiber, current, element, expirationTime) {
-    if (current !== null && current.type === element.type) {
-      // Move based on index
-      var existing = useFiber(current, element.props, expirationTime);
-      existing.ref = coerceRef(returnFiber, current, element);
-      existing["return"] = returnFiber;
-      {
-        existing._debugSource = element._source;
-        existing._debugOwner = element._owner;
-      }
-      return existing;
-    } else {
-      // Insert
-      var created = createFiberFromElement(
-        element,
-        returnFiber.mode,
-        expirationTime
-      );
-      created.ref = coerceRef(returnFiber, current, element);
-      created["return"] = returnFiber;
-      return created;
-    }
-  }
-
-  function updatePortal(returnFiber, current, portal, expirationTime) {
-    if (
-      current === null ||
-      current.tag !== HostPortal ||
-      current.stateNode.containerInfo !== portal.containerInfo ||
-      current.stateNode.implementation !== portal.implementation
-    ) {
-      // Insert
-      var created = createFiberFromPortal(
-        portal,
-        returnFiber.mode,
-        expirationTime
-      );
-      created["return"] = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, portal.children || [], expirationTime);
-      existing["return"] = returnFiber;
-      return existing;
-    }
-  }
-
-  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
-    if (current === null || current.tag !== Fragment) {
-      // Insert
-      var created = createFiberFromFragment(
-        fragment,
-        returnFiber.mode,
-        expirationTime,
-        key
-      );
-      created["return"] = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, fragment, expirationTime);
-      existing["return"] = returnFiber;
-      return existing;
-    }
-  }
-
-  function createChild(returnFiber, newChild, expirationTime) {
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys. If the previous node is implicitly keyed
-      // we can continue to replace it without aborting even if it is not a text
-      // node.
-      var created = createFiberFromText(
-        "" + newChild,
-        returnFiber.mode,
-        expirationTime
-      );
-      created["return"] = returnFiber;
-      return created;
-    }
-
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          var _created = createFiberFromElement(
-            newChild,
-            returnFiber.mode,
-            expirationTime
-          );
-          _created.ref = coerceRef(returnFiber, null, newChild);
-          _created["return"] = returnFiber;
-          return _created;
-        }
-        case REACT_PORTAL_TYPE: {
-          var _created2 = createFiberFromPortal(
-            newChild,
-            returnFiber.mode,
-            expirationTime
-          );
-          _created2["return"] = returnFiber;
-          return _created2;
-        }
-      }
-
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        var _created3 = createFiberFromFragment(
-          newChild,
-          returnFiber.mode,
-          expirationTime,
-          null
-        );
-        _created3["return"] = returnFiber;
-        return _created3;
-      }
-
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-
-    return null;
-  }
-
-  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
-    // Update the fiber if the keys match, otherwise return null.
-
-    var key = oldFiber !== null ? oldFiber.key : null;
-
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys. If the previous node is implicitly keyed
-      // we can continue to replace it without aborting even if it is not a text
-      // node.
-      if (key !== null) {
-        return null;
-      }
-      return updateTextNode(
-        returnFiber,
-        oldFiber,
-        "" + newChild,
-        expirationTime
-      );
-    }
-
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          if (newChild.key === key) {
-            if (newChild.type === REACT_FRAGMENT_TYPE) {
-              return updateFragment(
-                returnFiber,
-                oldFiber,
-                newChild.props.children,
-                expirationTime,
-                key
-              );
-            }
-            return updateElement(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime
-            );
-          } else {
-            return null;
-          }
-        }
-        case REACT_PORTAL_TYPE: {
-          if (newChild.key === key) {
-            return updatePortal(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime
-            );
-          } else {
-            return null;
-          }
-        }
-      }
-
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        if (key !== null) {
-          return null;
-        }
-
-        return updateFragment(
-          returnFiber,
-          oldFiber,
-          newChild,
-          expirationTime,
-          null
-        );
-      }
-
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-
-    return null;
-  }
-
-  function updateFromMap(
-    existingChildren,
-    returnFiber,
-    newIdx,
-    newChild,
-    expirationTime
-  ) {
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys, so we neither have to check the old nor
-      // new node for the key. If both are text nodes, they match.
-      var matchedFiber = existingChildren.get(newIdx) || null;
-      return updateTextNode(
-        returnFiber,
-        matchedFiber,
-        "" + newChild,
-        expirationTime
-      );
-    }
-
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          var _matchedFiber =
-            existingChildren.get(
-              newChild.key === null ? newIdx : newChild.key
-            ) || null;
-          if (newChild.type === REACT_FRAGMENT_TYPE) {
-            return updateFragment(
-              returnFiber,
-              _matchedFiber,
-              newChild.props.children,
-              expirationTime,
-              newChild.key
-            );
-          }
-          return updateElement(
-            returnFiber,
-            _matchedFiber,
-            newChild,
-            expirationTime
-          );
-        }
-        case REACT_PORTAL_TYPE: {
-          var _matchedFiber2 =
-            existingChildren.get(
-              newChild.key === null ? newIdx : newChild.key
-            ) || null;
-          return updatePortal(
-            returnFiber,
-            _matchedFiber2,
-            newChild,
-            expirationTime
-          );
-        }
-      }
-
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        var _matchedFiber3 = existingChildren.get(newIdx) || null;
-        return updateFragment(
-          returnFiber,
-          _matchedFiber3,
-          newChild,
-          expirationTime,
-          null
-        );
-      }
-
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-
-    return null;
-  }
-
-  /**
-   * Warns if there is a duplicate or missing key
-   */
-  function warnOnInvalidKey(child, knownKeys) {
-    {
-      if (typeof child !== "object" || child === null) {
-        return knownKeys;
-      }
-      switch (child.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-        case REACT_PORTAL_TYPE:
-          warnForMissingKey(child);
-          var key = child.key;
-          if (typeof key !== "string") {
-            break;
-          }
-          if (knownKeys === null) {
-            knownKeys = new Set();
-            knownKeys.add(key);
-            break;
-          }
-          if (!knownKeys.has(key)) {
-            knownKeys.add(key);
-            break;
-          }
-          warning(
-            false,
-            "Encountered two children with the same key, `%s`. " +
-              "Keys should be unique so that components maintain their identity " +
-              "across updates. Non-unique keys may cause children to be " +
-              "duplicated and/or omitted — the behavior is unsupported and " +
-              "could change in a future version.%s",
-            key,
-            getCurrentFiberStackAddendum$1()
-          );
-          break;
-        default:
-          break;
-      }
-    }
-    return knownKeys;
-  }
-
-  function reconcileChildrenArray(
-    returnFiber,
-    currentFirstChild,
-    newChildren,
-    expirationTime
-  ) {
-    // This algorithm can't optimize by searching from boths ends since we
-    // don't have backpointers on fibers. I'm trying to see how far we can get
-    // with that model. If it ends up not being worth the tradeoffs, we can
-    // add it later.
-
-    // Even with a two ended optimization, we'd want to optimize for the case
-    // where there are few changes and brute force the comparison instead of
-    // going for the Map. It'd like to explore hitting that path first in
-    // forward-only mode and only go for the Map once we notice that we need
-    // lots of look ahead. This doesn't handle reversal as well as two ended
-    // search but that's unusual. Besides, for the two ended optimization to
-    // work on Iterables, we'd need to copy the whole set.
-
-    // In this first iteration, we'll just live with hitting the bad case
-    // (adding everything to a Map) in for every insert/move.
-
-    // If you change this code, also update reconcileChildrenIterator() which
-    // uses the same algorithm.
-
-    {
-      // First, validate keys.
-      var knownKeys = null;
-      for (var i = 0; i < newChildren.length; i++) {
-        var child = newChildren[i];
-        knownKeys = warnOnInvalidKey(child, knownKeys);
-      }
-    }
-
-    var resultingFirstChild = null;
-    var previousNewFiber = null;
-
-    var oldFiber = currentFirstChild;
-    var lastPlacedIndex = 0;
-    var newIdx = 0;
-    var nextOldFiber = null;
-    for (; oldFiber !== null && newIdx < newChildren.length; newIdx++) {
-      if (oldFiber.index > newIdx) {
-        nextOldFiber = oldFiber;
-        oldFiber = null;
-      } else {
-        nextOldFiber = oldFiber.sibling;
-      }
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        newChildren[newIdx],
-        expirationTime
-      );
-      if (newFiber === null) {
-        // TODO: This breaks on empty slots like null children. That's
-        // unfortunate because it triggers the slow path all the time. We need
-        // a better way to communicate whether this was a miss or null,
-        // boolean, undefined, etc.
-        if (oldFiber === null) {
-          oldFiber = nextOldFiber;
-        }
-        break;
-      }
-      if (shouldTrackSideEffects) {
-        if (oldFiber && newFiber.alternate === null) {
-          // We matched the slot, but we didn't reuse the existing fiber, so we
-          // need to delete the existing child.
-          deleteChild(returnFiber, oldFiber);
-        }
-      }
-      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
-      if (previousNewFiber === null) {
-        // TODO: Move out of the loop. This only happens for the first run.
-        resultingFirstChild = newFiber;
-      } else {
-        // TODO: Defer siblings if we're not at the right index for this slot.
-        // I.e. if we had null values before, then we want to defer this
-        // for each null value. However, we also don't want to call updateSlot
-        // with the previous one.
-        previousNewFiber.sibling = newFiber;
-      }
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-
-    if (newIdx === newChildren.length) {
-      // We've reached the end of the new children. We can delete the rest.
-      deleteRemainingChildren(returnFiber, oldFiber);
-      return resultingFirstChild;
-    }
-
-    if (oldFiber === null) {
-      // If we don't have any more existing children we can choose a fast path
-      // since the rest will all be insertions.
-      for (; newIdx < newChildren.length; newIdx++) {
-        var _newFiber = createChild(
-          returnFiber,
-          newChildren[newIdx],
-          expirationTime
-        );
-        if (!_newFiber) {
-          continue;
-        }
-        lastPlacedIndex = placeChild(_newFiber, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          // TODO: Move out of the loop. This only happens for the first run.
-          resultingFirstChild = _newFiber;
-        } else {
-          previousNewFiber.sibling = _newFiber;
-        }
-        previousNewFiber = _newFiber;
-      }
-      return resultingFirstChild;
-    }
-
-    // Add all children to a key map for quick lookups.
-    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
-
-    // Keep scanning and use the map to restore deleted items as moves.
-    for (; newIdx < newChildren.length; newIdx++) {
-      var _newFiber2 = updateFromMap(
-        existingChildren,
-        returnFiber,
-        newIdx,
-        newChildren[newIdx],
-        expirationTime
-      );
-      if (_newFiber2) {
-        if (shouldTrackSideEffects) {
-          if (_newFiber2.alternate !== null) {
-            // The new fiber is a work in progress, but if there exists a
-            // current, that means that we reused the fiber. We need to delete
-            // it from the child list so that we don't add it to the deletion
-            // list.
-            existingChildren["delete"](
-              _newFiber2.key === null ? newIdx : _newFiber2.key
-            );
-          }
-        }
-        lastPlacedIndex = placeChild(_newFiber2, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          resultingFirstChild = _newFiber2;
-        } else {
-          previousNewFiber.sibling = _newFiber2;
-        }
-        previousNewFiber = _newFiber2;
-      }
-    }
-
-    if (shouldTrackSideEffects) {
-      // Any existing children that weren't consumed above were deleted. We need
-      // to add them to the deletion list.
-      existingChildren.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    }
-
-    return resultingFirstChild;
-  }
-
-  function reconcileChildrenIterator(
-    returnFiber,
-    currentFirstChild,
-    newChildrenIterable,
-    expirationTime
-  ) {
-    // This is the same implementation as reconcileChildrenArray(),
-    // but using the iterator instead.
-
-    var iteratorFn = getIteratorFn(newChildrenIterable);
-    invariant(
-      typeof iteratorFn === "function",
-      "An object is not an iterable. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-
-    {
-      // Warn about using Maps as children
-      if (typeof newChildrenIterable.entries === "function") {
-        var possibleMap = newChildrenIterable;
-        if (possibleMap.entries === iteratorFn) {
-          !didWarnAboutMaps
-            ? warning(
-                false,
-                "Using Maps as children is unsupported and will likely yield " +
-                  "unexpected results. Convert it to a sequence/iterable of keyed " +
-                  "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$1()
-              )
-            : void 0;
-          didWarnAboutMaps = true;
-        }
-      }
-
-      // First, validate keys.
-      // We'll get a different iterator later for the main pass.
-      var _newChildren = iteratorFn.call(newChildrenIterable);
-      if (_newChildren) {
-        var knownKeys = null;
-        var _step = _newChildren.next();
-        for (; !_step.done; _step = _newChildren.next()) {
-          var child = _step.value;
-          knownKeys = warnOnInvalidKey(child, knownKeys);
-        }
-      }
-    }
-
-    var newChildren = iteratorFn.call(newChildrenIterable);
-    invariant(newChildren != null, "An iterable object provided no iterator.");
-
-    var resultingFirstChild = null;
-    var previousNewFiber = null;
-
-    var oldFiber = currentFirstChild;
-    var lastPlacedIndex = 0;
-    var newIdx = 0;
-    var nextOldFiber = null;
-
-    var step = newChildren.next();
-    for (
-      ;
-      oldFiber !== null && !step.done;
-      newIdx++, step = newChildren.next()
-    ) {
-      if (oldFiber.index > newIdx) {
-        nextOldFiber = oldFiber;
-        oldFiber = null;
-      } else {
-        nextOldFiber = oldFiber.sibling;
-      }
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        step.value,
-        expirationTime
-      );
-      if (newFiber === null) {
-        // TODO: This breaks on empty slots like null children. That's
-        // unfortunate because it triggers the slow path all the time. We need
-        // a better way to communicate whether this was a miss or null,
-        // boolean, undefined, etc.
-        if (!oldFiber) {
-          oldFiber = nextOldFiber;
-        }
-        break;
-      }
-      if (shouldTrackSideEffects) {
-        if (oldFiber && newFiber.alternate === null) {
-          // We matched the slot, but we didn't reuse the existing fiber, so we
-          // need to delete the existing child.
-          deleteChild(returnFiber, oldFiber);
-        }
-      }
-      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
-      if (previousNewFiber === null) {
-        // TODO: Move out of the loop. This only happens for the first run.
-        resultingFirstChild = newFiber;
-      } else {
-        // TODO: Defer siblings if we're not at the right index for this slot.
-        // I.e. if we had null values before, then we want to defer this
-        // for each null value. However, we also don't want to call updateSlot
-        // with the previous one.
-        previousNewFiber.sibling = newFiber;
-      }
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-
-    if (step.done) {
-      // We've reached the end of the new children. We can delete the rest.
-      deleteRemainingChildren(returnFiber, oldFiber);
-      return resultingFirstChild;
-    }
-
-    if (oldFiber === null) {
-      // If we don't have any more existing children we can choose a fast path
-      // since the rest will all be insertions.
-      for (; !step.done; newIdx++, step = newChildren.next()) {
-        var _newFiber3 = createChild(returnFiber, step.value, expirationTime);
-        if (_newFiber3 === null) {
-          continue;
-        }
-        lastPlacedIndex = placeChild(_newFiber3, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          // TODO: Move out of the loop. This only happens for the first run.
-          resultingFirstChild = _newFiber3;
-        } else {
-          previousNewFiber.sibling = _newFiber3;
-        }
-        previousNewFiber = _newFiber3;
-      }
-      return resultingFirstChild;
-    }
-
-    // Add all children to a key map for quick lookups.
-    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
-
-    // Keep scanning and use the map to restore deleted items as moves.
-    for (; !step.done; newIdx++, step = newChildren.next()) {
-      var _newFiber4 = updateFromMap(
-        existingChildren,
-        returnFiber,
-        newIdx,
-        step.value,
-        expirationTime
-      );
-      if (_newFiber4 !== null) {
-        if (shouldTrackSideEffects) {
-          if (_newFiber4.alternate !== null) {
-            // The new fiber is a work in progress, but if there exists a
-            // current, that means that we reused the fiber. We need to delete
-            // it from the child list so that we don't add it to the deletion
-            // list.
-            existingChildren["delete"](
-              _newFiber4.key === null ? newIdx : _newFiber4.key
-            );
-          }
-        }
-        lastPlacedIndex = placeChild(_newFiber4, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          resultingFirstChild = _newFiber4;
-        } else {
-          previousNewFiber.sibling = _newFiber4;
-        }
-        previousNewFiber = _newFiber4;
-      }
-    }
-
-    if (shouldTrackSideEffects) {
-      // Any existing children that weren't consumed above were deleted. We need
-      // to add them to the deletion list.
-      existingChildren.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    }
-
-    return resultingFirstChild;
-  }
-
-  function reconcileSingleTextNode(
-    returnFiber,
-    currentFirstChild,
-    textContent,
-    expirationTime
-  ) {
-    // There's no need to check for keys on text nodes since we don't have a
-    // way to define them.
-    if (currentFirstChild !== null && currentFirstChild.tag === HostText) {
-      // We already have an existing node so let's just update it and delete
-      // the rest.
-      deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
-      var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing["return"] = returnFiber;
-      return existing;
-    }
-    // The existing first child is not a text node so we need to create one
-    // and delete the existing ones.
-    deleteRemainingChildren(returnFiber, currentFirstChild);
-    var created = createFiberFromText(
-      textContent,
-      returnFiber.mode,
-      expirationTime
-    );
-    created["return"] = returnFiber;
-    return created;
-  }
-
-  function reconcileSingleElement(
-    returnFiber,
-    currentFirstChild,
-    element,
-    expirationTime
-  ) {
-    var key = element.key;
-    var child = currentFirstChild;
-    while (child !== null) {
-      // TODO: If key === null and child.key === null, then this only applies to
-      // the first item in the list.
-      if (child.key === key) {
-        if (
-          child.tag === Fragment
-            ? element.type === REACT_FRAGMENT_TYPE
-            : child.type === element.type
-        ) {
-          deleteRemainingChildren(returnFiber, child.sibling);
-          var existing = useFiber(
-            child,
-            element.type === REACT_FRAGMENT_TYPE
-              ? element.props.children
-              : element.props,
-            expirationTime
-          );
-          existing.ref = coerceRef(returnFiber, child, element);
-          existing["return"] = returnFiber;
-          {
-            existing._debugSource = element._source;
-            existing._debugOwner = element._owner;
-          }
-          return existing;
-        } else {
-          deleteRemainingChildren(returnFiber, child);
-          break;
-        }
-      } else {
-        deleteChild(returnFiber, child);
-      }
-      child = child.sibling;
-    }
-
-    if (element.type === REACT_FRAGMENT_TYPE) {
-      var created = createFiberFromFragment(
-        element.props.children,
-        returnFiber.mode,
-        expirationTime,
-        element.key
-      );
-      created["return"] = returnFiber;
-      return created;
-    } else {
-      var _created4 = createFiberFromElement(
-        element,
-        returnFiber.mode,
-        expirationTime
-      );
-      _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4["return"] = returnFiber;
-      return _created4;
-    }
-  }
-
-  function reconcileSinglePortal(
-    returnFiber,
-    currentFirstChild,
-    portal,
-    expirationTime
-  ) {
-    var key = portal.key;
-    var child = currentFirstChild;
-    while (child !== null) {
-      // TODO: If key === null and child.key === null, then this only applies to
-      // the first item in the list.
-      if (child.key === key) {
-        if (
-          child.tag === HostPortal &&
-          child.stateNode.containerInfo === portal.containerInfo &&
-          child.stateNode.implementation === portal.implementation
-        ) {
-          deleteRemainingChildren(returnFiber, child.sibling);
-          var existing = useFiber(child, portal.children || [], expirationTime);
-          existing["return"] = returnFiber;
-          return existing;
-        } else {
-          deleteRemainingChildren(returnFiber, child);
-          break;
-        }
-      } else {
-        deleteChild(returnFiber, child);
-      }
-      child = child.sibling;
-    }
-
-    var created = createFiberFromPortal(
-      portal,
-      returnFiber.mode,
-      expirationTime
-    );
-    created["return"] = returnFiber;
-    return created;
-  }
-
-  // This API will tag the children with the side-effect of the reconciliation
-  // itself. They will be added to the side-effect list as we pass through the
-  // children and the parent.
-  function reconcileChildFibers(
-    returnFiber,
-    currentFirstChild,
-    newChild,
-    expirationTime
-  ) {
-    // This function is not recursive.
-    // If the top level item is an array, we treat it as a set of children,
-    // not as a fragment. Nested arrays on the other hand will be treated as
-    // fragment nodes. Recursion happens at the normal flow.
-
-    // Handle top level unkeyed fragments as if they were arrays.
-    // This leads to an ambiguity between <>{[...]}</> and <>...</>.
-    // We treat the ambiguous cases above the same.
-    if (
-      typeof newChild === "object" &&
-      newChild !== null &&
-      newChild.type === REACT_FRAGMENT_TYPE &&
-      newChild.key === null
-    ) {
-      newChild = newChild.props.children;
-    }
-
-    // Handle object types
-    var isObject = typeof newChild === "object" && newChild !== null;
-
-    if (isObject) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return placeSingleChild(
-            reconcileSingleElement(
-              returnFiber,
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )
-          );
-        case REACT_PORTAL_TYPE:
-          return placeSingleChild(
-            reconcileSinglePortal(
-              returnFiber,
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )
-          );
-      }
-    }
-
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      return placeSingleChild(
-        reconcileSingleTextNode(
-          returnFiber,
-          currentFirstChild,
-          "" + newChild,
-          expirationTime
-        )
-      );
-    }
-
-    if (isArray$1(newChild)) {
-      return reconcileChildrenArray(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    }
-
-    if (getIteratorFn(newChild)) {
-      return reconcileChildrenIterator(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    }
-
-    if (isObject) {
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-    if (typeof newChild === "undefined") {
-      // If the new child is undefined, and the return fiber is a composite
-      // component, throw an error. If Fiber return types are disabled,
-      // we already threw above.
-      switch (returnFiber.tag) {
-        case ClassComponent: {
-          {
-            var instance = returnFiber.stateNode;
-            if (instance.render._isMockFunction) {
-              // We allow auto-mocks to proceed as if they're returning null.
-              break;
-            }
-          }
-        }
-        // Intentionally fall through to the next case, which handles both
-        // functions and classes
-        // eslint-disable-next-lined no-fallthrough
-        case FunctionalComponent: {
-          var Component = returnFiber.type;
-          invariant(
-            false,
-            "%s(...): Nothing was returned from render. This usually means a " +
-              "return statement is missing. Or, to render nothing, " +
-              "return null.",
-            Component.displayName || Component.name || "Component"
-          );
-        }
-      }
-    }
-
-    // Remaining cases are all treated as empty.
-    return deleteRemainingChildren(returnFiber, currentFirstChild);
-  }
-
-  return reconcileChildFibers;
-}
-
-var reconcileChildFibers = ChildReconciler(true);
-var mountChildFibers = ChildReconciler(false);
-
-function cloneChildFibers(current, workInProgress) {
-  invariant(
-    current === null || workInProgress.child === current.child,
-    "Resuming work not yet implemented."
-  );
-
-  if (workInProgress.child === null) {
-    return;
-  }
-
-  var currentChild = workInProgress.child;
-  var newChild = createWorkInProgress(
-    currentChild,
-    currentChild.pendingProps,
-    currentChild.expirationTime
-  );
-  workInProgress.child = newChild;
-
-  newChild["return"] = workInProgress;
-  while (currentChild.sibling !== null) {
-    currentChild = currentChild.sibling;
-    newChild = newChild.sibling = createWorkInProgress(
-      currentChild,
-      currentChild.pendingProps,
-      currentChild.expirationTime
-    );
-    newChild["return"] = workInProgress;
-  }
-  newChild.sibling = null;
-}
-
-var didWarnAboutBadClass = void 0;
-var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
-var didWarnAboutStatelessRefs = void 0;
-
-{
-  didWarnAboutBadClass = {};
-  didWarnAboutGetDerivedStateOnFunctionalComponent = {};
-  didWarnAboutStatelessRefs = {};
-}
-
-var ReactFiberBeginWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  scheduleWork,
-  computeExpirationForFiber
-) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
-  var pushHostContext = hostContext.pushHostContext,
-    pushHostContainer = hostContext.pushHostContainer;
-  var pushProvider = newContext.pushProvider;
-  var getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    hasLegacyContextChanged = legacyContext.hasContextChanged,
-    pushLegacyContextProvider = legacyContext.pushContextProvider,
-    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
-    invalidateContextProvider = legacyContext.invalidateContextProvider;
-  var enterHydrationState = hydrationContext.enterHydrationState,
-    resetHydrationState = hydrationContext.resetHydrationState,
-    tryToClaimNextHydratableInstance =
-      hydrationContext.tryToClaimNextHydratableInstance;
-
-  var _ReactFiberClassCompo = ReactFiberClassComponent(
-      legacyContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      memoizeProps,
-      memoizeState
-    ),
-    adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
-    callGetDerivedStateFromProps =
-      _ReactFiberClassCompo.callGetDerivedStateFromProps,
-    constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
-    mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
-    resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
-    updateClassInstance = _ReactFiberClassCompo.updateClassInstance;
-
-  // TODO: Remove this and use reconcileChildrenAtExpirationTime directly.
-
-  function reconcileChildren(current, workInProgress, nextChildren) {
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      workInProgress.expirationTime
-    );
-  }
-
-  function reconcileChildrenAtExpirationTime(
-    current,
-    workInProgress,
-    nextChildren,
-    renderExpirationTime
-  ) {
-    if (current === null) {
-      // If this is a fresh new component that hasn't been rendered yet, we
-      // won't update its child set by applying minimal side-effects. Instead,
-      // we will add them all to the child before it gets rendered. That means
-      // we can optimize this reconciliation pass by not tracking side-effects.
-      workInProgress.child = mountChildFibers(
-        workInProgress,
-        null,
-        nextChildren,
-        renderExpirationTime
-      );
-    } else {
-      // If the current child is the same as the work in progress, it means that
-      // we haven't yet started any work on these children. Therefore, we use
-      // the clone algorithm to create a copy of all the current children.
-
-      // If we had any progressed work already, that is invalid at this point so
-      // let's throw it out.
-      workInProgress.child = reconcileChildFibers(
-        workInProgress,
-        current.child,
-        nextChildren,
-        renderExpirationTime
-      );
-    }
-  }
-
-  function updateForwardRef(current, workInProgress) {
-    var render = workInProgress.type.render;
-    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
-  }
-
-  function updateFragment(current, workInProgress) {
-    var nextChildren = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextChildren) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
-  }
-
-  function updateMode(current, workInProgress) {
-    var nextChildren = workInProgress.pendingProps.children;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (
-      nextChildren === null ||
-      workInProgress.memoizedProps === nextChildren
-    ) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
-  }
-
-  function markRef(current, workInProgress) {
-    var ref = workInProgress.ref;
-    if (
-      (current === null && ref !== null) ||
-      (current !== null && current.ref !== ref)
-    ) {
-      // Schedule a Ref effect
-      workInProgress.effectTag |= Ref;
-    }
-  }
-
-  function updateFunctionalComponent(current, workInProgress) {
-    var fn = workInProgress.type;
-    var nextProps = workInProgress.pendingProps;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else {
-      if (workInProgress.memoizedProps === nextProps) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-      // TODO: consider bringing fn.shouldComponentUpdate() back.
-      // It used to be here.
-    }
-
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var context = getMaskedContext(workInProgress, unmaskedContext);
-
-    var nextChildren = void 0;
-
-    {
-      ReactCurrentOwner.current = workInProgress;
-      ReactDebugCurrentFiber.setCurrentPhase("render");
-      nextChildren = fn(nextProps, context);
-      ReactDebugCurrentFiber.setCurrentPhase(null);
-    }
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
-  }
-
-  function updateClassComponent(current, workInProgress, renderExpirationTime) {
-    // Push context providers early to prevent context stack mismatches.
-    // During mounting we don't know the child context yet as the instance doesn't exist.
-    // We will invalidate the child context in finishClassComponent() right after rendering.
-    var hasContext = pushLegacyContextProvider(workInProgress);
-    var shouldUpdate = void 0;
-    if (current === null) {
-      if (workInProgress.stateNode === null) {
-        // In the initial pass we might need to construct the instance.
-        constructClassInstance(workInProgress, workInProgress.pendingProps);
-        mountClassInstance(workInProgress, renderExpirationTime);
-
-        shouldUpdate = true;
-      } else {
-        // In a resume, we'll already have an instance we can reuse.
-        shouldUpdate = resumeMountClassInstance(
-          workInProgress,
-          renderExpirationTime
-        );
-      }
-    } else {
-      shouldUpdate = updateClassInstance(
-        current,
-        workInProgress,
-        renderExpirationTime
-      );
-    }
-
-    // We processed the update queue inside updateClassInstance. It may have
-    // included some errors that were dispatched during the commit phase.
-    // TODO: Refactor class components so this is less awkward.
-    var didCaptureError = false;
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null && updateQueue.capturedValues !== null) {
-      shouldUpdate = true;
-      didCaptureError = true;
-    }
-    return finishClassComponent(
-      current,
-      workInProgress,
-      shouldUpdate,
-      hasContext,
-      didCaptureError,
-      renderExpirationTime
-    );
-  }
-
-  function finishClassComponent(
-    current,
-    workInProgress,
-    shouldUpdate,
-    hasContext,
-    didCaptureError,
-    renderExpirationTime
-  ) {
-    // Refs should update even if shouldComponentUpdate returns false
-    markRef(current, workInProgress);
-
-    if (!shouldUpdate && !didCaptureError) {
-      // Context providers should defer to sCU for rendering
-      if (hasContext) {
-        invalidateContextProvider(workInProgress, false);
-      }
-
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-
-    // Rerender
-    ReactCurrentOwner.current = workInProgress;
-    var nextChildren = void 0;
-    if (
-      didCaptureError &&
-      (!enableGetDerivedStateFromCatch ||
-        typeof ctor.getDerivedStateFromCatch !== "function")
-    ) {
-      // If we captured an error, but getDerivedStateFrom catch is not defined,
-      // unmount all the children. componentDidCatch will schedule an update to
-      // re-render a fallback. This is temporary until we migrate everyone to
-      // the new API.
-      // TODO: Warn in a future release.
-      nextChildren = null;
-    } else {
-      {
-        ReactDebugCurrentFiber.setCurrentPhase("render");
-        nextChildren = instance.render();
-        if (
-          debugRenderPhaseSideEffects ||
-          (debugRenderPhaseSideEffectsForStrictMode &&
-            workInProgress.mode & StrictMode)
-        ) {
-          instance.render();
-        }
-        ReactDebugCurrentFiber.setCurrentPhase(null);
-      }
-    }
-
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    if (didCaptureError) {
-      // If we're recovering from an error, reconcile twice: first to delete
-      // all the existing children.
-      reconcileChildrenAtExpirationTime(
-        current,
-        workInProgress,
-        null,
-        renderExpirationTime
-      );
-      workInProgress.child = null;
-      // Now we can continue reconciling like normal. This has the effect of
-      // remounting all children regardless of whether their their
-      // identity matches.
-    }
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      renderExpirationTime
-    );
-    // Memoize props and state using the values we just used to render.
-    // TODO: Restructure so we never read values from the instance.
-    memoizeState(workInProgress, instance.state);
-    memoizeProps(workInProgress, instance.props);
-
-    // The context might have changed so we need to recalculate it.
-    if (hasContext) {
-      invalidateContextProvider(workInProgress, true);
-    }
-
-    return workInProgress.child;
-  }
-
-  function pushHostRootContext(workInProgress) {
-    var root = workInProgress.stateNode;
-    if (root.pendingContext) {
-      pushTopLevelContextObject(
-        workInProgress,
-        root.pendingContext,
-        root.pendingContext !== root.context
-      );
-    } else if (root.context) {
-      // Should always be set
-      pushTopLevelContextObject(workInProgress, root.context, false);
-    }
-    pushHostContainer(workInProgress, root.containerInfo);
-  }
-
-  function updateHostRoot(current, workInProgress, renderExpirationTime) {
-    pushHostRootContext(workInProgress);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      var prevState = workInProgress.memoizedState;
-      var state = processUpdateQueue(
-        current,
-        workInProgress,
-        updateQueue,
-        null,
-        null,
-        renderExpirationTime
-      );
-      memoizeState(workInProgress, state);
-      updateQueue = workInProgress.updateQueue;
-
-      var element = void 0;
-      if (updateQueue !== null && updateQueue.capturedValues !== null) {
-        // There's an uncaught error. Unmount the whole root.
-        element = null;
-      } else if (prevState === state) {
-        // If the state is the same as before, that's a bailout because we had
-        // no work that expires at this time.
-        resetHydrationState();
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      } else {
-        element = state.element;
-      }
-      var root = workInProgress.stateNode;
-      if (
-        (current === null || current.child === null) &&
-        root.hydrate &&
-        enterHydrationState(workInProgress)
-      ) {
-        // If we don't have any current children this might be the first pass.
-        // We always try to hydrate. If this isn't a hydration pass there won't
-        // be any children to hydrate which is effectively the same thing as
-        // not hydrating.
-
-        // This is a bit of a hack. We track the host root as a placement to
-        // know that we're currently in a mounting state. That way isMounted
-        // works as expected. We must reset this before committing.
-        // TODO: Delete this when we delete isMounted and findDOMNode.
-        workInProgress.effectTag |= Placement;
-
-        // Ensure that children mount into this root without tracking
-        // side-effects. This ensures that we don't store Placement effects on
-        // nodes that will be hydrated.
-        workInProgress.child = mountChildFibers(
-          workInProgress,
-          null,
-          element,
-          renderExpirationTime
-        );
-      } else {
-        // Otherwise reset hydration state in case we aborted and resumed another
-        // root.
-        resetHydrationState();
-        reconcileChildren(current, workInProgress, element);
-      }
-      memoizeState(workInProgress, state);
-      return workInProgress.child;
-    }
-    resetHydrationState();
-    // If there is no update queue, that's a bailout because the root has no props.
-    return bailoutOnAlreadyFinishedWork(current, workInProgress);
-  }
-
-  function updateHostComponent(current, workInProgress, renderExpirationTime) {
-    pushHostContext(workInProgress);
-
-    if (current === null) {
-      tryToClaimNextHydratableInstance(workInProgress);
-    }
-
-    var type = workInProgress.type;
-    var memoizedProps = workInProgress.memoizedProps;
-    var nextProps = workInProgress.pendingProps;
-    var prevProps = current !== null ? current.memoizedProps : null;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (memoizedProps === nextProps) {
-      var isHidden =
-        workInProgress.mode & AsyncMode &&
-        shouldDeprioritizeSubtree(type, nextProps);
-      if (isHidden) {
-        // Before bailing out, make sure we've deprioritized a hidden component.
-        workInProgress.expirationTime = Never;
-      }
-      if (!isHidden || renderExpirationTime !== Never) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-      // If we're rendering a hidden node at hidden priority, don't bailout. The
-      // parent is complete, but the children may not be.
-    }
-
-    var nextChildren = nextProps.children;
-    var isDirectTextChild = shouldSetTextContent(type, nextProps);
-
-    if (isDirectTextChild) {
-      // We special case a direct text child of a host node. This is a common
-      // case. We won't handle it as a reified child. We will instead handle
-      // this in the host environment that also have access to this prop. That
-      // avoids allocating another HostText fiber and traversing it.
-      nextChildren = null;
-    } else if (prevProps && shouldSetTextContent(type, prevProps)) {
-      // If we're switching from a direct text child to a normal child, or to
-      // empty, we need to schedule the text content to be reset.
-      workInProgress.effectTag |= ContentReset;
-    }
-
-    markRef(current, workInProgress);
-
-    // Check the host config to see if the children are offscreen/hidden.
-    if (
-      renderExpirationTime !== Never &&
-      workInProgress.mode & AsyncMode &&
-      shouldDeprioritizeSubtree(type, nextProps)
-    ) {
-      // Down-prioritize the children.
-      workInProgress.expirationTime = Never;
-      // Bailout and come back to this fiber later.
-      workInProgress.memoizedProps = nextProps;
-      return null;
-    }
-
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
-  }
-
-  function updateHostText(current, workInProgress) {
-    if (current === null) {
-      tryToClaimNextHydratableInstance(workInProgress);
-    }
-    var nextProps = workInProgress.pendingProps;
-    memoizeProps(workInProgress, nextProps);
-    // Nothing to do here. This is terminal. We'll do the completion step
-    // immediately after.
-    return null;
-  }
-
-  function mountIndeterminateComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    invariant(
-      current === null,
-      "An indeterminate component should never have mounted. This error is " +
-        "likely caused by a bug in React. Please file an issue."
-    );
-    var fn = workInProgress.type;
-    var props = workInProgress.pendingProps;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var context = getMaskedContext(workInProgress, unmaskedContext);
-
-    var value = void 0;
-
-    {
-      if (fn.prototype && typeof fn.prototype.render === "function") {
-        var componentName = getComponentName(workInProgress) || "Unknown";
-
-        if (!didWarnAboutBadClass[componentName]) {
-          warning(
-            false,
-            "The <%s /> component appears to have a render method, but doesn't extend React.Component. " +
-              "This is likely to cause errors. Change %s to extend React.Component instead.",
-            componentName,
-            componentName
-          );
-          didWarnAboutBadClass[componentName] = true;
-        }
-      }
-      ReactCurrentOwner.current = workInProgress;
-      value = fn(props, context);
-    }
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-
-    if (
-      typeof value === "object" &&
-      value !== null &&
-      typeof value.render === "function" &&
-      value.$$typeof === undefined
-    ) {
-      var Component = workInProgress.type;
-
-      // Proceed under the assumption that this is a class instance
-      workInProgress.tag = ClassComponent;
-
-      workInProgress.memoizedState =
-        value.state !== null && value.state !== undefined ? value.state : null;
-
-      if (typeof Component.getDerivedStateFromProps === "function") {
-        var partialState = callGetDerivedStateFromProps(
-          workInProgress,
-          value,
-          props,
-          workInProgress.memoizedState
-        );
-
-        if (partialState !== null && partialState !== undefined) {
-          workInProgress.memoizedState = Object.assign(
-            {},
-            workInProgress.memoizedState,
-            partialState
-          );
-        }
-      }
-
-      // Push context providers early to prevent context stack mismatches.
-      // During mounting we don't know the child context yet as the instance doesn't exist.
-      // We will invalidate the child context in finishClassComponent() right after rendering.
-      var hasContext = pushLegacyContextProvider(workInProgress);
-      adoptClassInstance(workInProgress, value);
-      mountClassInstance(workInProgress, renderExpirationTime);
-      return finishClassComponent(
-        current,
-        workInProgress,
-        true,
-        hasContext,
-        false,
-        renderExpirationTime
-      );
-    } else {
-      // Proceed under the assumption that this is a functional component
-      workInProgress.tag = FunctionalComponent;
-      {
-        var _Component = workInProgress.type;
-
-        if (_Component) {
-          !!_Component.childContextTypes
-            ? warning(
-                false,
-                "%s(...): childContextTypes cannot be defined on a functional component.",
-                _Component.displayName || _Component.name || "Component"
-              )
-            : void 0;
-        }
-        if (workInProgress.ref !== null) {
-          var info = "";
-          var ownerName = ReactDebugCurrentFiber.getCurrentFiberOwnerName();
-          if (ownerName) {
-            info += "\n\nCheck the render method of `" + ownerName + "`.";
-          }
-
-          var warningKey = ownerName || workInProgress._debugID || "";
-          var debugSource = workInProgress._debugSource;
-          if (debugSource) {
-            warningKey = debugSource.fileName + ":" + debugSource.lineNumber;
-          }
-          if (!didWarnAboutStatelessRefs[warningKey]) {
-            didWarnAboutStatelessRefs[warningKey] = true;
-            warning(
-              false,
-              "Stateless function components cannot be given refs. " +
-                "Attempts to access this ref will fail.%s%s",
-              info,
-              ReactDebugCurrentFiber.getCurrentFiberStackAddendum()
-            );
-          }
-        }
-
-        if (typeof fn.getDerivedStateFromProps === "function") {
-          var _componentName = getComponentName(workInProgress) || "Unknown";
-
-          if (
-            !didWarnAboutGetDerivedStateOnFunctionalComponent[_componentName]
-          ) {
-            warning(
-              false,
-              "%s: Stateless functional components do not support getDerivedStateFromProps.",
-              _componentName
-            );
-            didWarnAboutGetDerivedStateOnFunctionalComponent[
-              _componentName
-            ] = true;
-          }
-        }
-      }
-      reconcileChildren(current, workInProgress, value);
-      memoizeProps(workInProgress, props);
-      return workInProgress.child;
-    }
-  }
-
-  function updateCallComponent(current, workInProgress, renderExpirationTime) {
-    var nextProps = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextProps) {
-      nextProps = workInProgress.memoizedProps;
-      // TODO: When bailing out, we might need to return the stateNode instead
-      // of the child. To check it for work.
-      // return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var nextChildren = nextProps.children;
-
-    // The following is a fork of reconcileChildrenAtExpirationTime but using
-    // stateNode to store the child.
-    if (current === null) {
-      workInProgress.stateNode = mountChildFibers(
-        workInProgress,
-        workInProgress.stateNode,
-        nextChildren,
-        renderExpirationTime
-      );
-    } else {
-      workInProgress.stateNode = reconcileChildFibers(
-        workInProgress,
-        current.stateNode,
-        nextChildren,
-        renderExpirationTime
-      );
-    }
-
-    memoizeProps(workInProgress, nextProps);
-    // This doesn't take arbitrary time so we could synchronously just begin
-    // eagerly do the work of workInProgress.child as an optimization.
-    return workInProgress.stateNode;
-  }
-
-  function updatePortalComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
-    var nextChildren = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextChildren) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    if (current === null) {
-      // Portals are special because we don't append the children during mount
-      // but at commit. Therefore we need to track insertions which the normal
-      // flow doesn't do during mount. This doesn't happen at the root because
-      // the root always starts with a "current" with a null child.
-      // TODO: Consider unifying this with how the root works.
-      workInProgress.child = reconcileChildFibers(
-        workInProgress,
-        null,
-        nextChildren,
-        renderExpirationTime
-      );
-      memoizeProps(workInProgress, nextChildren);
-    } else {
-      reconcileChildren(current, workInProgress, nextChildren);
-      memoizeProps(workInProgress, nextChildren);
-    }
-    return workInProgress.child;
-  }
-
-  function propagateContextChange(
-    workInProgress,
-    context,
-    changedBits,
-    renderExpirationTime
-  ) {
-    var fiber = workInProgress.child;
-    if (fiber !== null) {
-      // Set the return pointer of the child to the work-in-progress fiber.
-      fiber["return"] = workInProgress;
-    }
-    while (fiber !== null) {
-      var nextFiber = void 0;
-      // Visit this fiber.
-      switch (fiber.tag) {
-        case ContextConsumer:
-          // Check if the context matches.
-          var observedBits = fiber.stateNode | 0;
-          if (fiber.type === context && (observedBits & changedBits) !== 0) {
-            // Update the expiration time of all the ancestors, including
-            // the alternates.
-            var node = fiber;
-            while (node !== null) {
-              var alternate = node.alternate;
-              if (
-                node.expirationTime === NoWork ||
-                node.expirationTime > renderExpirationTime
-              ) {
-                node.expirationTime = renderExpirationTime;
-                if (
-                  alternate !== null &&
-                  (alternate.expirationTime === NoWork ||
-                    alternate.expirationTime > renderExpirationTime)
-                ) {
-                  alternate.expirationTime = renderExpirationTime;
-                }
-              } else if (
-                alternate !== null &&
-                (alternate.expirationTime === NoWork ||
-                  alternate.expirationTime > renderExpirationTime)
-              ) {
-                alternate.expirationTime = renderExpirationTime;
-              } else {
-                // Neither alternate was updated, which means the rest of the
-                // ancestor path already has sufficient priority.
-                break;
-              }
-              node = node["return"];
-            }
-            // Don't scan deeper than a matching consumer. When we render the
-            // consumer, we'll continue scanning from that point. This way the
-            // scanning work is time-sliced.
-            nextFiber = null;
-          } else {
-            // Traverse down.
-            nextFiber = fiber.child;
-          }
-          break;
-        case ContextProvider:
-          // Don't scan deeper if this is a matching provider
-          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
-          break;
-        default:
-          // Traverse down.
-          nextFiber = fiber.child;
-          break;
-      }
-      if (nextFiber !== null) {
-        // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber["return"] = fiber;
-      } else {
-        // No child. Traverse to next sibling.
-        nextFiber = fiber;
-        while (nextFiber !== null) {
-          if (nextFiber === workInProgress) {
-            // We're back to the root of this subtree. Exit.
-            nextFiber = null;
-            break;
-          }
-          var sibling = nextFiber.sibling;
-          if (sibling !== null) {
-            nextFiber = sibling;
-            break;
-          }
-          // No more siblings. Traverse up.
-          nextFiber = nextFiber["return"];
-        }
-      }
-      fiber = nextFiber;
-    }
-  }
-
-  function updateContextProvider(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var providerType = workInProgress.type;
-    var context = providerType._context;
-
-    var newProps = workInProgress.pendingProps;
-    var oldProps = workInProgress.memoizedProps;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (oldProps === newProps) {
-      workInProgress.stateNode = 0;
-      pushProvider(workInProgress);
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var newValue = newProps.value;
-    workInProgress.memoizedProps = newProps;
-
-    var changedBits = void 0;
-    if (oldProps === null) {
-      // Initial render
-      changedBits = MAX_SIGNED_31_BIT_INT;
-    } else {
-      if (oldProps.value === newProps.value) {
-        // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children) {
-          workInProgress.stateNode = 0;
-          pushProvider(workInProgress);
-          return bailoutOnAlreadyFinishedWork(current, workInProgress);
-        }
-        changedBits = 0;
-      } else {
-        var oldValue = oldProps.value;
-        // Use Object.is to compare the new context value to the old value.
-        // Inlined Object.is polyfill.
-        // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
-        if (
-          (oldValue === newValue &&
-            (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
-          (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
-        ) {
-          // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children) {
-            workInProgress.stateNode = 0;
-            pushProvider(workInProgress);
-            return bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
-          changedBits = 0;
-        } else {
-          changedBits =
-            typeof context._calculateChangedBits === "function"
-              ? context._calculateChangedBits(oldValue, newValue)
-              : MAX_SIGNED_31_BIT_INT;
-          {
-            !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
-              ? warning(
-                  false,
-                  "calculateChangedBits: Expected the return value to be a " +
-                    "31-bit integer. Instead received: %s",
-                  changedBits
-                )
-              : void 0;
-          }
-          changedBits |= 0;
-
-          if (changedBits === 0) {
-            // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children) {
-              workInProgress.stateNode = 0;
-              pushProvider(workInProgress);
-              return bailoutOnAlreadyFinishedWork(current, workInProgress);
-            }
-          } else {
-            propagateContextChange(
-              workInProgress,
-              context,
-              changedBits,
-              renderExpirationTime
-            );
-          }
-        }
-      }
-    }
-
-    workInProgress.stateNode = changedBits;
-    pushProvider(workInProgress);
-
-    var newChildren = newProps.children;
-    reconcileChildren(current, workInProgress, newChildren);
-    return workInProgress.child;
-  }
-
-  function updateContextConsumer(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var context = workInProgress.type;
-    var newProps = workInProgress.pendingProps;
-    var oldProps = workInProgress.memoizedProps;
-
-    var newValue = context._currentValue;
-    var changedBits = context._changedBits;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (changedBits === 0 && oldProps === newProps) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    workInProgress.memoizedProps = newProps;
-
-    var observedBits = newProps.unstable_observedBits;
-    if (observedBits === undefined || observedBits === null) {
-      // Subscribe to all changes by default
-      observedBits = MAX_SIGNED_31_BIT_INT;
-    }
-    // Store the observedBits on the fiber's stateNode for quick access.
-    workInProgress.stateNode = observedBits;
-
-    if ((changedBits & observedBits) !== 0) {
-      // Context change propagation stops at matching consumers, for time-
-      // slicing. Continue the propagation here.
-      propagateContextChange(
-        workInProgress,
-        context,
-        changedBits,
-        renderExpirationTime
-      );
-    } else if (oldProps === newProps) {
-      // Skip over a memoized parent with a bitmask bailout even
-      // if we began working on it because of a deeper matching child.
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    // There is no bailout on `children` equality because we expect people
-    // to often pass a bound method as a child, but it may reference
-    // `this.state` or `this.props` (and thus needs to re-render on `setState`).
-
-    var render = newProps.children;
-
-    {
-      !(typeof render === "function")
-        ? warning(
-            false,
-            "A context consumer was rendered with multiple children, or a child " +
-              "that isn't a function. A context consumer expects a single child " +
-              "that is a function. If you did pass a function, make sure there " +
-              "is no trailing or leading whitespace around it."
-          )
-        : void 0;
-    }
-
-    var newChildren = render(newValue);
-    reconcileChildren(current, workInProgress, newChildren);
-    return workInProgress.child;
-  }
-
-  /*
-  function reuseChildrenEffects(returnFiber : Fiber, firstChild : Fiber) {
-    let child = firstChild;
-    do {
-      // Ensure that the first and last effect of the parent corresponds
-      // to the children's first and last effect.
-      if (!returnFiber.firstEffect) {
-        returnFiber.firstEffect = child.firstEffect;
-      }
-      if (child.lastEffect) {
-        if (returnFiber.lastEffect) {
-          returnFiber.lastEffect.nextEffect = child.firstEffect;
-        }
-        returnFiber.lastEffect = child.lastEffect;
-      }
-    } while (child = child.sibling);
-  }
-  */
-
-  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
-    cancelWorkTimer(workInProgress);
-
-    // TODO: We should ideally be able to bail out early if the children have no
-    // more work to do. However, since we don't have a separation of this
-    // Fiber's priority and its children yet - we don't know without doing lots
-    // of the same work we do anyway. Once we have that separation we can just
-    // bail out here if the children has no more work at this priority level.
-    // if (workInProgress.priorityOfChildren <= priorityLevel) {
-    //   // If there are side-effects in these children that have not yet been
-    //   // committed we need to ensure that they get properly transferred up.
-    //   if (current && current.child !== workInProgress.child) {
-    //     reuseChildrenEffects(workInProgress, child);
-    //   }
-    //   return null;
-    // }
-
-    cloneChildFibers(current, workInProgress);
-    return workInProgress.child;
-  }
-
-  function bailoutOnLowPriority(current, workInProgress) {
-    cancelWorkTimer(workInProgress);
-
-    // TODO: Handle HostComponent tags here as well and call pushHostContext()?
-    // See PR 8590 discussion for context
-    switch (workInProgress.tag) {
-      case HostRoot:
-        pushHostRootContext(workInProgress);
-        break;
-      case ClassComponent:
-        pushLegacyContextProvider(workInProgress);
-        break;
-      case HostPortal:
-        pushHostContainer(
-          workInProgress,
-          workInProgress.stateNode.containerInfo
-        );
-        break;
-      case ContextProvider:
-        pushProvider(workInProgress);
-        break;
-    }
-    // TODO: What if this is currently in progress?
-    // How can that happen? How is this not being cloned?
-    return null;
-  }
-
-  // TODO: Delete memoizeProps/State and move to reconcile/bailout instead
-  function memoizeProps(workInProgress, nextProps) {
-    workInProgress.memoizedProps = nextProps;
-  }
-
-  function memoizeState(workInProgress, nextState) {
-    workInProgress.memoizedState = nextState;
-    // Don't reset the updateQueue, in case there are pending updates. Resetting
-    // is handled by processUpdateQueue.
-  }
-
-  function beginWork(current, workInProgress, renderExpirationTime) {
-    if (
-      workInProgress.expirationTime === NoWork ||
-      workInProgress.expirationTime > renderExpirationTime
-    ) {
-      return bailoutOnLowPriority(current, workInProgress);
-    }
-
-    switch (workInProgress.tag) {
-      case IndeterminateComponent:
-        return mountIndeterminateComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case FunctionalComponent:
-        return updateFunctionalComponent(current, workInProgress);
-      case ClassComponent:
-        return updateClassComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostRoot:
-        return updateHostRoot(current, workInProgress, renderExpirationTime);
-      case HostComponent:
-        return updateHostComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostText:
-        return updateHostText(current, workInProgress);
-      case CallHandlerPhase:
-        // This is a restart. Reset the tag to the initial phase.
-        workInProgress.tag = CallComponent;
-      // Intentionally fall through since this is now the same.
-      case CallComponent:
-        return updateCallComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ReturnComponent:
-        // A return component is just a placeholder, we can just run through the
-        // next one immediately.
-        return null;
-      case HostPortal:
-        return updatePortalComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ForwardRef:
-        return updateForwardRef(current, workInProgress);
-      case Fragment:
-        return updateFragment(current, workInProgress);
-      case Mode:
-        return updateMode(current, workInProgress);
-      case ContextProvider:
-        return updateContextProvider(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ContextConsumer:
-        return updateContextConsumer(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      default:
-        invariant(
-          false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
-        );
-    }
-  }
-
-  return {
-    beginWork: beginWork
-  };
-};
-
-var ReactFiberCompleteWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext
-) {
-  var createInstance = config.createInstance,
-    createTextInstance = config.createTextInstance,
-    appendInitialChild = config.appendInitialChild,
-    finalizeInitialChildren = config.finalizeInitialChildren,
-    prepareUpdate = config.prepareUpdate,
-    mutation = config.mutation,
-    persistence = config.persistence;
-  var getRootHostContainer = hostContext.getRootHostContainer,
-    popHostContext = hostContext.popHostContext,
-    getHostContext = hostContext.getHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-  var prepareToHydrateHostInstance =
-      hydrationContext.prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance =
-      hydrationContext.prepareToHydrateHostTextInstance,
-    popHydrationState = hydrationContext.popHydrationState;
-
-  function markUpdate(workInProgress) {
-    // Tag the fiber with an update effect. This turns a Placement into
-    // a PlacementAndUpdate.
-    workInProgress.effectTag |= Update;
-  }
-
-  function markRef(workInProgress) {
-    workInProgress.effectTag |= Ref;
-  }
-
-  function appendAllReturns(returns, workInProgress) {
-    var node = workInProgress.stateNode;
-    if (node) {
-      node["return"] = workInProgress;
-    }
-    while (node !== null) {
-      if (
-        node.tag === HostComponent ||
-        node.tag === HostText ||
-        node.tag === HostPortal
-      ) {
-        invariant(false, "A call cannot have host component children.");
-      } else if (node.tag === ReturnComponent) {
-        returns.push(node.pendingProps.value);
-      } else if (node.child !== null) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  function moveCallToHandlerPhase(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var props = workInProgress.memoizedProps;
-    invariant(
-      props,
-      "Should be resolved by now. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-
-    // First step of the call has completed. Now we need to do the second.
-    // TODO: It would be nice to have a multi stage call represented by a
-    // single component, or at least tail call optimize nested ones. Currently
-    // that requires additional fields that we don't want to add to the fiber.
-    // So this requires nested handlers.
-    // Note: This doesn't mutate the alternate node. I don't think it needs to
-    // since this stage is reset for every pass.
-    workInProgress.tag = CallHandlerPhase;
-
-    // Build up the returns.
-    // TODO: Compare this to a generator or opaque helpers like Children.
-    var returns = [];
-    appendAllReturns(returns, workInProgress);
-    var fn = props.handler;
-    var childProps = props.props;
-    var nextChildren = fn(childProps, returns);
-
-    var currentFirstChild = current !== null ? current.child : null;
-    workInProgress.child = reconcileChildFibers(
-      workInProgress,
-      currentFirstChild,
-      nextChildren,
-      renderExpirationTime
-    );
-    return workInProgress.child;
-  }
-
-  function appendAllChildren(parent, workInProgress) {
-    // We only have the top Fiber that was created but we need recurse down its
-    // children to find all the terminal nodes.
-    var node = workInProgress.child;
-    while (node !== null) {
-      if (node.tag === HostComponent || node.tag === HostText) {
-        appendInitialChild(parent, node.stateNode);
-      } else if (node.tag === HostPortal) {
-        // If we have a portal child, then we don't want to traverse
-        // down its children. Instead, we'll get insertions from each child in
-        // the portal directly.
-      } else if (node.child !== null) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === workInProgress) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  var updateHostContainer = void 0;
-  var updateHostComponent = void 0;
-  var updateHostText = void 0;
-  if (mutation) {
-    if (enableMutatingReconciler) {
-      // Mutation mode
-      updateHostContainer = function(workInProgress) {
-        // Noop
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // TODO: Type this specific to this type of component.
-        workInProgress.updateQueue = updatePayload;
-        // If the update payload indicates that there is a change or if there
-        // is a new ref we mark this as an update. All the work is done in commitWork.
-        if (updatePayload) {
-          markUpdate(workInProgress);
-        }
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        // If the text differs, mark it as an update. All the work in done in commitWork.
-        if (oldText !== newText) {
-          markUpdate(workInProgress);
-        }
-      };
-    } else {
-      invariant(false, "Mutating reconciler is disabled.");
-    }
-  } else if (persistence) {
-    if (enablePersistentReconciler) {
-      // Persistent host tree mode
-      var cloneInstance = persistence.cloneInstance,
-        createContainerChildSet = persistence.createContainerChildSet,
-        appendChildToContainerChildSet =
-          persistence.appendChildToContainerChildSet,
-        finalizeContainerChildren = persistence.finalizeContainerChildren;
-
-      // An unfortunate fork of appendAllChildren because we have two different parent types.
-
-      var appendAllChildrenToContainer = function(
-        containerChildSet,
-        workInProgress
-      ) {
-        // We only have the top Fiber that was created but we need recurse down its
-        // children to find all the terminal nodes.
-        var node = workInProgress.child;
-        while (node !== null) {
-          if (node.tag === HostComponent || node.tag === HostText) {
-            appendChildToContainerChildSet(containerChildSet, node.stateNode);
-          } else if (node.tag === HostPortal) {
-            // If we have a portal child, then we don't want to traverse
-            // down its children. Instead, we'll get insertions from each child in
-            // the portal directly.
-          } else if (node.child !== null) {
-            node.child["return"] = node;
-            node = node.child;
-            continue;
-          }
-          if (node === workInProgress) {
-            return;
-          }
-          while (node.sibling === null) {
-            if (node["return"] === null || node["return"] === workInProgress) {
-              return;
-            }
-            node = node["return"];
-          }
-          node.sibling["return"] = node["return"];
-          node = node.sibling;
-        }
-      };
-      updateHostContainer = function(workInProgress) {
-        var portalOrRoot = workInProgress.stateNode;
-        var childrenUnchanged = workInProgress.firstEffect === null;
-        if (childrenUnchanged) {
-          // No changes, just reuse the existing instance.
-        } else {
-          var container = portalOrRoot.containerInfo;
-          var newChildSet = createContainerChildSet(container);
-          // If children might have changed, we have to add them all to the set.
-          appendAllChildrenToContainer(newChildSet, workInProgress);
-          portalOrRoot.pendingChildren = newChildSet;
-          // Schedule an update on the container to swap out the container.
-          markUpdate(workInProgress);
-          finalizeContainerChildren(container, newChildSet);
-        }
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // If there are no effects associated with this node, then none of our children had any updates.
-        // This guarantees that we can reuse all of them.
-        var childrenUnchanged = workInProgress.firstEffect === null;
-        var currentInstance = current.stateNode;
-        if (childrenUnchanged && updatePayload === null) {
-          // No changes, just reuse the existing instance.
-          // Note that this might release a previous clone.
-          workInProgress.stateNode = currentInstance;
-        } else {
-          var recyclableInstance = workInProgress.stateNode;
-          var newInstance = cloneInstance(
-            currentInstance,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            workInProgress,
-            childrenUnchanged,
-            recyclableInstance
-          );
-          if (
-            finalizeInitialChildren(
-              newInstance,
-              type,
-              newProps,
-              rootContainerInstance,
-              currentHostContext
-            )
-          ) {
-            markUpdate(workInProgress);
-          }
-          workInProgress.stateNode = newInstance;
-          if (childrenUnchanged) {
-            // If there are no other effects in this tree, we need to flag this node as having one.
-            // Even though we're not going to use it for anything.
-            // Otherwise parents won't know that there are new children to propagate upwards.
-            markUpdate(workInProgress);
-          } else {
-            // If children might have changed, we have to add them all to the set.
-            appendAllChildren(newInstance, workInProgress);
-          }
-        }
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        if (oldText !== newText) {
-          // If the text content differs, we'll create a new text instance for it.
-          var rootContainerInstance = getRootHostContainer();
-          var currentHostContext = getHostContext();
-          workInProgress.stateNode = createTextInstance(
-            newText,
-            rootContainerInstance,
-            currentHostContext,
-            workInProgress
-          );
-          // We'll have to mark it as having an effect, even though we won't use the effect for anything.
-          // This lets the parents know that at least one of their children has changed.
-          markUpdate(workInProgress);
-        }
-      };
-    } else {
-      invariant(false, "Persistent reconciler is disabled.");
-    }
-  } else {
-    if (enableNoopReconciler) {
-      // No host operations
-      updateHostContainer = function(workInProgress) {
-        // Noop
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // Noop
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        // Noop
-      };
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
-    }
-  }
-
-  function completeWork(current, workInProgress, renderExpirationTime) {
-    var newProps = workInProgress.pendingProps;
-    switch (workInProgress.tag) {
-      case FunctionalComponent:
-        return null;
-      case ClassComponent: {
-        // We are leaving this subtree, so pop context if any.
-        popLegacyContextProvider(workInProgress);
-
-        // If this component caught an error, schedule an error log effect.
-        var instance = workInProgress.stateNode;
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null && updateQueue.capturedValues !== null) {
-          workInProgress.effectTag &= ~DidCapture;
-          if (typeof instance.componentDidCatch === "function") {
-            workInProgress.effectTag |= ErrLog;
-          } else {
-            // Normally we clear this in the commit phase, but since we did not
-            // schedule an effect, we need to reset it here.
-            updateQueue.capturedValues = null;
-          }
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var fiberRoot = workInProgress.stateNode;
-        if (fiberRoot.pendingContext) {
-          fiberRoot.context = fiberRoot.pendingContext;
-          fiberRoot.pendingContext = null;
-        }
-        if (current === null || current.child === null) {
-          // If we hydrated, pop so that we can delete any remaining children
-          // that weren't hydrated.
-          popHydrationState(workInProgress);
-          // This resets the hacky state to fix isMounted before committing.
-          // TODO: Delete this when we delete isMounted and findDOMNode.
-          workInProgress.effectTag &= ~Placement;
-        }
-        updateHostContainer(workInProgress);
-
-        var _updateQueue = workInProgress.updateQueue;
-        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
-          workInProgress.effectTag |= ErrLog;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        var rootContainerInstance = getRootHostContainer();
-        var type = workInProgress.type;
-        if (current !== null && workInProgress.stateNode != null) {
-          // If we have an alternate, that means this is an update and we need to
-          // schedule a side-effect to do the updates.
-          var oldProps = current.memoizedProps;
-          // If we get updated because one of our children updated, we don't
-          // have newProps so we'll have to reuse them.
-          // TODO: Split the update API as separate for the props vs. children.
-          // Even better would be if children weren't special cased at all tho.
-          var _instance = workInProgress.stateNode;
-          var currentHostContext = getHostContext();
-          // TODO: Experiencing an error where oldProps is null. Suggests a host
-          // component is hitting the resume path. Figure out why. Possibly
-          // related to `hidden`.
-          var updatePayload = prepareUpdate(
-            _instance,
-            type,
-            oldProps,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          );
-
-          updateHostComponent(
-            current,
-            workInProgress,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          );
-
-          if (current.ref !== workInProgress.ref) {
-            markRef(workInProgress);
-          }
-        } else {
-          if (!newProps) {
-            invariant(
-              workInProgress.stateNode !== null,
-              "We must have new props for new mounts. This error is likely " +
-                "caused by a bug in React. Please file an issue."
-            );
-            // This can happen when we abort work.
-            return null;
-          }
-
-          var _currentHostContext = getHostContext();
-          // TODO: Move createInstance to beginWork and keep it on a context
-          // "stack" as the parent. Then append children as we go in beginWork
-          // or completeWork depending on we want to add then top->down or
-          // bottom->up. Top->down is faster in IE11.
-          var wasHydrated = popHydrationState(workInProgress);
-          if (wasHydrated) {
-            // TODO: Move this and createInstance step into the beginPhase
-            // to consolidate.
-            if (
-              prepareToHydrateHostInstance(
-                workInProgress,
-                rootContainerInstance,
-                _currentHostContext
-              )
-            ) {
-              // If changes to the hydrated node needs to be applied at the
-              // commit-phase we mark this as such.
-              markUpdate(workInProgress);
-            }
-          } else {
-            var _instance2 = createInstance(
-              type,
-              newProps,
-              rootContainerInstance,
-              _currentHostContext,
-              workInProgress
-            );
-
-            appendAllChildren(_instance2, workInProgress);
-
-            // Certain renderers require commit-time effects for initial mount.
-            // (eg DOM renderer supports auto-focus for certain elements).
-            // Make sure such renderers get scheduled for later work.
-            if (
-              finalizeInitialChildren(
-                _instance2,
-                type,
-                newProps,
-                rootContainerInstance,
-                _currentHostContext
-              )
-            ) {
-              markUpdate(workInProgress);
-            }
-            workInProgress.stateNode = _instance2;
-          }
-
-          if (workInProgress.ref !== null) {
-            // If there is a ref on a host node we need to schedule a callback
-            markRef(workInProgress);
-          }
-        }
-        return null;
-      }
-      case HostText: {
-        var newText = newProps;
-        if (current && workInProgress.stateNode != null) {
-          var oldText = current.memoizedProps;
-          // If we have an alternate, that means this is an update and we need
-          // to schedule a side-effect to do the updates.
-          updateHostText(current, workInProgress, oldText, newText);
-        } else {
-          if (typeof newText !== "string") {
-            invariant(
-              workInProgress.stateNode !== null,
-              "We must have new props for new mounts. This error is likely " +
-                "caused by a bug in React. Please file an issue."
-            );
-            // This can happen when we abort work.
-            return null;
-          }
-          var _rootContainerInstance = getRootHostContainer();
-          var _currentHostContext2 = getHostContext();
-          var _wasHydrated = popHydrationState(workInProgress);
-          if (_wasHydrated) {
-            if (prepareToHydrateHostTextInstance(workInProgress)) {
-              markUpdate(workInProgress);
-            }
-          } else {
-            workInProgress.stateNode = createTextInstance(
-              newText,
-              _rootContainerInstance,
-              _currentHostContext2,
-              workInProgress
-            );
-          }
-        }
-        return null;
-      }
-      case CallComponent:
-        return moveCallToHandlerPhase(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case CallHandlerPhase:
-        // Reset the tag to now be a first phase call.
-        workInProgress.tag = CallComponent;
-        return null;
-      case ReturnComponent:
-        // Does nothing.
-        return null;
-      case ForwardRef:
-        return null;
-      case Fragment:
-        return null;
-      case Mode:
-        return null;
-      case HostPortal:
-        popHostContainer(workInProgress);
-        updateHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        // Pop provider fiber
-        popProvider(workInProgress);
-        return null;
-      case ContextConsumer:
-        return null;
-      // Error cases
-      case IndeterminateComponent:
-        invariant(
-          false,
-          "An indeterminate component should have become determinate before " +
-            "completing. This error is likely caused by a bug in React. Please " +
-            "file an issue."
-        );
-      // eslint-disable-next-line no-fallthrough
-      default:
-        invariant(
-          false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
-        );
-    }
-  }
-
-  return {
-    completeWork: completeWork
-  };
-};
-
-function createCapturedValue(value, source) {
-  // If the value is an error, call this function immediately after it is thrown
-  // so the stack is accurate.
-  return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
-  };
-}
-
-var ReactFiberUnwindWork = function(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-
-  function throwException(returnFiber, sourceFiber, rawValue) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-
-    var value = createCapturedValue(rawValue, sourceFiber);
-
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          // Uncaught error
-          var errorInfo = value;
-          ensureUpdateQueues(workInProgress);
-          var updateQueue = workInProgress.updateQueue;
-          updateQueue.capturedValues = [errorInfo];
-          workInProgress.effectTag |= ShouldCapture;
-          return;
-        }
-        case ClassComponent:
-          // Capture and retry
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
-          if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            ensureUpdateQueues(workInProgress);
-            var _updateQueue = workInProgress.updateQueue;
-            var capturedValues = _updateQueue.capturedValues;
-            if (capturedValues === null) {
-              _updateQueue.capturedValues = [value];
-            } else {
-              capturedValues.push(value);
-            }
-            workInProgress.effectTag |= ShouldCapture;
-            return;
-          }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress["return"];
-    } while (workInProgress !== null);
-  }
-
-  function unwindWork(workInProgress) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
-    }
-  }
-
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      default:
-        break;
-    }
-  }
-
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork
-  };
-};
-
-// Module provided by RN:
-/**
- * Intercept lifecycle errors and ensure they are shown with the correct stack
- * trace within the native redbox component.
- */
-function showErrorDialog(capturedError) {
-  var componentStack = capturedError.componentStack,
-    error = capturedError.error;
-
-  var errorToHandle = void 0;
-
-  // Typically Errors are thrown but eg strings or null can be thrown as well.
-  if (error instanceof Error) {
-    var message = error.message,
-      name = error.name;
-
-    var summary = message ? name + ": " + message : name;
-
-    errorToHandle = error;
-
-    try {
-      errorToHandle.message =
-        summary + "\n\nThis error is located at:" + componentStack;
-    } catch (e) {}
-  } else if (typeof error === "string") {
-    errorToHandle = new Error(
-      error + "\n\nThis error is located at:" + componentStack
-    );
-  } else {
-    errorToHandle = new Error("Unspecified error at:" + componentStack);
-  }
-
-  ExceptionsManager.handleException(errorToHandle, false);
-
-  // Return false here to prevent ReactFiberErrorLogger default behavior of
-  // logging error details to console.error. Calls to console.error are
-  // automatically routed to the native redbox controller, which we've already
-  // done above by calling ExceptionsManager.
-  return false;
-}
-
-function logCapturedError(capturedError) {
-  var logError = showErrorDialog(capturedError);
-
-  // Allow injected showErrorDialog() to prevent default console.error logging.
-  // This enables renderers like ReactNative to better manage redbox behavior.
-  if (logError === false) {
-    return;
-  }
-
-  var error = capturedError.error;
-  var suppressLogging = error && error.suppressReactErrorLogging;
-  if (suppressLogging) {
-    return;
-  }
-
-  {
-    var componentName = capturedError.componentName,
-      componentStack = capturedError.componentStack,
-      errorBoundaryName = capturedError.errorBoundaryName,
-      errorBoundaryFound = capturedError.errorBoundaryFound,
-      willRetry = capturedError.willRetry;
-
-    var componentNameMessage = componentName
-      ? "The above error occurred in the <" + componentName + "> component:"
-      : "The above error occurred in one of your React components:";
-
-    var errorBoundaryMessage = void 0;
-    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
-    if (errorBoundaryFound && errorBoundaryName) {
-      if (willRetry) {
-        errorBoundaryMessage =
-          "React will try to recreate this component tree from scratch " +
-          ("using the error boundary you provided, " + errorBoundaryName + ".");
-      } else {
-        errorBoundaryMessage =
-          "This error was initially handled by the error boundary " +
-          errorBoundaryName +
-          ".\n" +
-          "Recreating the tree from scratch failed so React will unmount the tree.";
-      }
-    } else {
-      errorBoundaryMessage =
-        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
-        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
-    }
-    var combinedMessage =
-      "" +
-      componentNameMessage +
-      componentStack +
-      "\n\n" +
-      ("" + errorBoundaryMessage);
-
-    // In development, we provide our own message with just the component stack.
-    // We don't include the original error message and JS stack because the browser
-    // has already printed it. Even if the application swallows the error, it is still
-    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
-    console.error(combinedMessage);
-  }
-}
-
-var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
-var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
-
-var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
-{
-  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
-}
-
-function logError(boundary, errorInfo) {
-  var source = errorInfo.source;
-  var stack = errorInfo.stack;
-  if (stack === null) {
-    stack = getStackAddendumByWorkInProgressFiber(source);
-  }
-
-  var capturedError = {
-    componentName: source !== null ? getComponentName(source) : null,
-    componentStack: stack !== null ? stack : "",
-    error: errorInfo.value,
-    errorBoundary: null,
-    errorBoundaryName: null,
-    errorBoundaryFound: false,
-    willRetry: false
-  };
-
-  if (boundary !== null && boundary.tag === ClassComponent) {
-    capturedError.errorBoundary = boundary.stateNode;
-    capturedError.errorBoundaryName = getComponentName(boundary);
-    capturedError.errorBoundaryFound = true;
-    capturedError.willRetry = true;
-  }
-
-  try {
-    logCapturedError(capturedError);
-  } catch (e) {
-    // Prevent cycle if logCapturedError() throws.
-    // A cycle may still occur if logCapturedError renders a component that throws.
-    var suppressLogging = e && e.suppressReactErrorLogging;
-    if (!suppressLogging) {
-      console.error(e);
-    }
-  }
-}
-
-var ReactFiberCommitWork = function(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed,
-  recalculateCurrentTime
-) {
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation,
-    persistence = config.persistence;
-
-  var callComponentWillUnmountWithTimer = function(current, instance) {
-    startPhaseTimer(current, "componentWillUnmount");
-    instance.props = current.memoizedProps;
-    instance.state = current.memoizedState;
-    instance.componentWillUnmount();
-    stopPhaseTimer();
-  };
-
-  // Capture errors so they don't interrupt unmounting.
-  function safelyCallComponentWillUnmount(current, instance) {
-    {
-      invokeGuardedCallback$3(
-        null,
-        callComponentWillUnmountWithTimer,
-        null,
-        current,
-        instance
-      );
-      if (hasCaughtError$1()) {
-        var unmountError = clearCaughtError$1();
-        captureError(current, unmountError);
-      }
-    }
-  }
-
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (ref !== null) {
-      if (typeof ref === "function") {
-        {
-          invokeGuardedCallback$3(null, ref, null, null);
-          if (hasCaughtError$1()) {
-            var refError = clearCaughtError$1();
-            captureError(current, refError);
-          }
-        }
-      } else {
-        ref.current = null;
-      }
-    }
-  }
-
-  function commitBeforeMutationLifeCycles(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        if (finishedWork.effectTag & Snapshot) {
-          if (current !== null) {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
-            var _instance = finishedWork.stateNode;
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            var snapshot = _instance.getSnapshotBeforeUpdate(
-              prevProps,
-              prevState
-            );
-            {
-              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
-              if (
-                snapshot === undefined &&
-                !didWarnSet.has(finishedWork.type)
-              ) {
-                didWarnSet.add(finishedWork.type);
-                warning(
-                  false,
-                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
-                    "must be returned. You have returned undefined.",
-                  getComponentName(finishedWork)
-                );
-              }
-            }
-            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
-            stopPhaseTimer();
-          }
-        }
-        return;
-      }
-      case HostRoot:
-      case HostComponent:
-      case HostText:
-      case HostPortal:
-        // Nothing to do for these component types
-        return;
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
-    }
-  }
-
-  function commitLifeCycles(
-    finishedRoot,
-    current,
-    finishedWork,
-    currentTime,
-    committedExpirationTime
-  ) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        var _instance2 = finishedWork.stateNode;
-        if (finishedWork.effectTag & Update) {
-          if (current === null) {
-            startPhaseTimer(finishedWork, "componentDidMount");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidMount();
-            stopPhaseTimer();
-          } else {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "componentDidUpdate");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidUpdate(
-              prevProps,
-              prevState,
-              _instance2.__reactInternalSnapshotBeforeUpdate
-            );
-            stopPhaseTimer();
-          }
-        }
-        var updateQueue = finishedWork.updateQueue;
-        if (updateQueue !== null) {
-          commitCallbacks(updateQueue, _instance2);
-        }
-        return;
-      }
-      case HostRoot: {
-        var _updateQueue = finishedWork.updateQueue;
-        if (_updateQueue !== null) {
-          var _instance3 = null;
-          if (finishedWork.child !== null) {
-            switch (finishedWork.child.tag) {
-              case HostComponent:
-                _instance3 = getPublicInstance(finishedWork.child.stateNode);
-                break;
-              case ClassComponent:
-                _instance3 = finishedWork.child.stateNode;
-                break;
-            }
-          }
-          commitCallbacks(_updateQueue, _instance3);
-        }
-        return;
-      }
-      case HostComponent: {
-        var _instance4 = finishedWork.stateNode;
-
-        // Renderers may schedule work to be done after host components are mounted
-        // (eg DOM renderer may schedule auto-focus for inputs and form controls).
-        // These effects should only be committed when components are first mounted,
-        // aka when there is no current/alternate.
-        if (current === null && finishedWork.effectTag & Update) {
-          var type = finishedWork.type;
-          var props = finishedWork.memoizedProps;
-          commitMount(_instance4, type, props, finishedWork);
-        }
-
-        return;
-      }
-      case HostText: {
-        // We have no life-cycles associated with text.
-        return;
-      }
-      case HostPortal: {
-        // We have no life-cycles associated with portals.
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
-    }
-  }
-
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case ClassComponent:
-        {
-          var ctor = finishedWork.type;
-          var _instance5 = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            updateQueue !== null && updateQueue.capturedValues !== null,
-            "An error logging effect should not have been scheduled if no errors " +
-              "were captured. This error is likely caused by a bug in React. " +
-              "Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-
-          if (typeof ctor.getDerivedStateFromCatch !== "function") {
-            // To preserve the preexisting retry behavior of error boundaries,
-            // we keep track of which ones already failed during this batch.
-            // This gets reset before we yield back to the browser.
-            // TODO: Warn in strict mode if getDerivedStateFromCatch is
-            // not defined.
-            markLegacyErrorBoundaryAsFailed(_instance5);
-          }
-
-          _instance5.props = finishedWork.memoizedProps;
-          _instance5.state = finishedWork.memoizedState;
-          for (var i = 0; i < capturedErrors.length; i++) {
-            var errorInfo = capturedErrors[i];
-            var _error = errorInfo.value;
-            var stack = errorInfo.stack;
-            logError(finishedWork, errorInfo);
-            _instance5.componentDidCatch(_error, {
-              componentStack: stack !== null ? stack : ""
-            });
-          }
-        }
-        break;
-      case HostRoot: {
-        var _updateQueue2 = finishedWork.updateQueue;
-        invariant(
-          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
-          "An error logging effect should not have been scheduled if no errors " +
-            "were captured. This error is likely caused by a bug in React. " +
-            "Please file an issue."
-        );
-        var _capturedErrors = _updateQueue2.capturedValues;
-        _updateQueue2.capturedValues = null;
-        for (var _i = 0; _i < _capturedErrors.length; _i++) {
-          var _errorInfo = _capturedErrors[_i];
-          logError(finishedWork, _errorInfo);
-          onUncaughtError(_errorInfo.value);
-        }
-        break;
-      }
-      default:
-        invariant(
-          false,
-          "This unit of work tag cannot capture errors.  This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-
-  function commitAttachRef(finishedWork) {
-    var ref = finishedWork.ref;
-    if (ref !== null) {
-      var _instance6 = finishedWork.stateNode;
-      var instanceToUse = void 0;
-      switch (finishedWork.tag) {
-        case HostComponent:
-          instanceToUse = getPublicInstance(_instance6);
-          break;
-        default:
-          instanceToUse = _instance6;
-      }
-      if (typeof ref === "function") {
-        ref(instanceToUse);
-      } else {
-        {
-          if (!ref.hasOwnProperty("current")) {
-            warning(
-              false,
-              "Unexpected ref object provided for %s. " +
-                "Use either a ref-setter function or React.createRef().%s",
-              getComponentName(finishedWork),
-              getStackAddendumByWorkInProgressFiber(finishedWork)
-            );
-          }
-        }
-
-        ref.current = instanceToUse;
-      }
-    }
-  }
-
-  function commitDetachRef(current) {
-    var currentRef = current.ref;
-    if (currentRef !== null) {
-      if (typeof currentRef === "function") {
-        currentRef(null);
-      } else {
-        currentRef.current = null;
-      }
-    }
-  }
-
-  // User-originating errors (lifecycles and refs) should not interrupt
-  // deletion, so don't let them throw. Host-originating errors should
-  // interrupt deletion, so it's okay
-  function commitUnmount(current) {
-    if (typeof onCommitUnmount === "function") {
-      onCommitUnmount(current);
-    }
-
-    switch (current.tag) {
-      case ClassComponent: {
-        safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if (typeof _instance7.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance7);
-        }
-        return;
-      }
-      case HostComponent: {
-        safelyDetachRef(current);
-        return;
-      }
-      case CallComponent: {
-        commitNestedUnmounts(current.stateNode);
-        return;
-      }
-      case HostPortal: {
-        // TODO: this is recursive.
-        // We are also not using this parent because
-        // the portal will get pushed immediately.
-        if (enableMutatingReconciler && mutation) {
-          unmountHostComponents(current);
-        } else if (enablePersistentReconciler && persistence) {
-          emptyPortalContainer(current);
-        }
-        return;
-      }
-    }
-  }
-
-  function commitNestedUnmounts(root) {
-    // While we're inside a removed host node we don't want to call
-    // removeChild on the inner nodes because they're removed by the top
-    // call anyway. We also want to call componentWillUnmount on all
-    // composites before this host node is removed from the tree. Therefore
-    var node = root;
-    while (true) {
-      commitUnmount(node);
-      // Visit children because they may contain more composite or host nodes.
-      // Skip portals because commitUnmount() currently visits them recursively.
-      if (
-        node.child !== null &&
-        // If we use mutation we drill down into portals using commitUnmount above.
-        // If we don't use mutation we drill down into portals here instead.
-        (!mutation || node.tag !== HostPortal)
-      ) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === root) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === root) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  function detachFiber(current) {
-    // Cut off the return pointers to disconnect it from the tree. Ideally, we
-    // should clear the child pointer of the parent alternate to let this
-    // get GC:ed but we don't know which for sure which parent is the current
-    // one so we'll settle for GC:ing the subtree of this child. This child
-    // itself will be GC:ed when the parent updates the next time.
-    current["return"] = null;
-    current.child = null;
-    if (current.alternate) {
-      current.alternate.child = null;
-      current.alternate["return"] = null;
-    }
-  }
-
-  var emptyPortalContainer = void 0;
-
-  if (!mutation) {
-    var commitContainer = void 0;
-    if (persistence) {
-      var replaceContainerChildren = persistence.replaceContainerChildren,
-        createContainerChildSet = persistence.createContainerChildSet;
-
-      emptyPortalContainer = function(current) {
-        var portal = current.stateNode;
-        var containerInfo = portal.containerInfo;
-
-        var emptyChildSet = createContainerChildSet(containerInfo);
-        replaceContainerChildren(containerInfo, emptyChildSet);
-      };
-      commitContainer = function(finishedWork) {
-        switch (finishedWork.tag) {
-          case ClassComponent: {
-            return;
-          }
-          case HostComponent: {
-            return;
-          }
-          case HostText: {
-            return;
-          }
-          case HostRoot:
-          case HostPortal: {
-            var portalOrRoot = finishedWork.stateNode;
-            var containerInfo = portalOrRoot.containerInfo,
-              _pendingChildren = portalOrRoot.pendingChildren;
-
-            replaceContainerChildren(containerInfo, _pendingChildren);
-            return;
-          }
-          default: {
-            invariant(
-              false,
-              "This unit of work tag should not have side-effects. This error is " +
-                "likely caused by a bug in React. Please file an issue."
-            );
-          }
-        }
-      };
-    } else {
-      commitContainer = function(finishedWork) {
-        // Noop
-      };
-    }
-    if (enablePersistentReconciler || enableNoopReconciler) {
-      return {
-        commitResetTextContent: function(finishedWork) {},
-        commitPlacement: function(finishedWork) {},
-        commitDeletion: function(current) {
-          // Detach refs and call componentWillUnmount() on the whole subtree.
-          commitNestedUnmounts(current);
-          detachFiber(current);
-        },
-        commitWork: function(current, finishedWork) {
-          commitContainer(finishedWork);
-        },
-
-        commitLifeCycles: commitLifeCycles,
-        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-        commitErrorLogging: commitErrorLogging,
-        commitAttachRef: commitAttachRef,
-        commitDetachRef: commitDetachRef
-      };
-    } else if (persistence) {
-      invariant(false, "Persistent reconciler is disabled.");
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
-    }
-  }
-  var commitMount = mutation.commitMount,
-    commitUpdate = mutation.commitUpdate,
-    resetTextContent = mutation.resetTextContent,
-    commitTextUpdate = mutation.commitTextUpdate,
-    appendChild = mutation.appendChild,
-    appendChildToContainer = mutation.appendChildToContainer,
-    insertBefore = mutation.insertBefore,
-    insertInContainerBefore = mutation.insertInContainerBefore,
-    removeChild = mutation.removeChild,
-    removeChildFromContainer = mutation.removeChildFromContainer;
-
-  function getHostParentFiber(fiber) {
-    var parent = fiber["return"];
-    while (parent !== null) {
-      if (isHostParent(parent)) {
-        return parent;
-      }
-      parent = parent["return"];
-    }
-    invariant(
-      false,
-      "Expected to find a host parent. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-  }
-
-  function isHostParent(fiber) {
-    return (
-      fiber.tag === HostComponent ||
-      fiber.tag === HostRoot ||
-      fiber.tag === HostPortal
-    );
-  }
-
-  function getHostSibling(fiber) {
-    // We're going to search forward into the tree until we find a sibling host
-    // node. Unfortunately, if multiple insertions are done in a row we have to
-    // search past them. This leads to exponential search for the next sibling.
-    var node = fiber;
-    siblings: while (true) {
-      // If we didn't find anything, let's try the next sibling.
-      while (node.sibling === null) {
-        if (node["return"] === null || isHostParent(node["return"])) {
-          // If we pop out of the root or hit the parent the fiber we are the
-          // last sibling.
-          return null;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-      while (node.tag !== HostComponent && node.tag !== HostText) {
-        // If it is not host node and, we might have a host node inside it.
-        // Try to search down until we find one.
-        if (node.effectTag & Placement) {
-          // If we don't have a child, try the siblings instead.
-          continue siblings;
-        }
-        // If we don't have a child, try the siblings instead.
-        // We also skip portals because they are not part of this host tree.
-        if (node.child === null || node.tag === HostPortal) {
-          continue siblings;
-        } else {
-          node.child["return"] = node;
-          node = node.child;
-        }
-      }
-      // Check if this host node is stable or about to be placed.
-      if (!(node.effectTag & Placement)) {
-        // Found it!
-        return node.stateNode;
-      }
-    }
-  }
-
-  function commitPlacement(finishedWork) {
-    // Recursively insert all host nodes into the parent.
-    var parentFiber = getHostParentFiber(finishedWork);
-    var parent = void 0;
-    var isContainer = void 0;
-    switch (parentFiber.tag) {
-      case HostComponent:
-        parent = parentFiber.stateNode;
-        isContainer = false;
-        break;
-      case HostRoot:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      case HostPortal:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      default:
-        invariant(
-          false,
-          "Invalid host parent fiber. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-    }
-    if (parentFiber.effectTag & ContentReset) {
-      // Reset the text content of the parent before doing any insertions
-      resetTextContent(parent);
-      // Clear ContentReset from the effect tag
-      parentFiber.effectTag &= ~ContentReset;
-    }
-
-    var before = getHostSibling(finishedWork);
-    // We only have the top Fiber that was inserted but we need recurse down its
-    // children to find all the terminal nodes.
-    var node = finishedWork;
-    while (true) {
-      if (node.tag === HostComponent || node.tag === HostText) {
-        if (before) {
-          if (isContainer) {
-            insertInContainerBefore(parent, node.stateNode, before);
-          } else {
-            insertBefore(parent, node.stateNode, before);
-          }
-        } else {
-          if (isContainer) {
-            appendChildToContainer(parent, node.stateNode);
-          } else {
-            appendChild(parent, node.stateNode);
-          }
-        }
-      } else if (node.tag === HostPortal) {
-        // If the insertion itself is a portal, then we don't want to traverse
-        // down its children. Instead, we'll get insertions from each child in
-        // the portal directly.
-      } else if (node.child !== null) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === finishedWork) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === finishedWork) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  function unmountHostComponents(current) {
-    // We only have the top Fiber that was inserted but we need recurse down its
-    var node = current;
-
-    // Each iteration, currentParent is populated with node's host parent if not
-    // currentParentIsValid.
-    var currentParentIsValid = false;
-    var currentParent = void 0;
-    var currentParentIsContainer = void 0;
-
-    while (true) {
-      if (!currentParentIsValid) {
-        var parent = node["return"];
-        findParent: while (true) {
-          invariant(
-            parent !== null,
-            "Expected to find a host parent. This error is likely caused by " +
-              "a bug in React. Please file an issue."
-          );
-          switch (parent.tag) {
-            case HostComponent:
-              currentParent = parent.stateNode;
-              currentParentIsContainer = false;
-              break findParent;
-            case HostRoot:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-            case HostPortal:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-          }
-          parent = parent["return"];
-        }
-        currentParentIsValid = true;
-      }
-
-      if (node.tag === HostComponent || node.tag === HostText) {
-        commitNestedUnmounts(node);
-        // After all the children have unmounted, it is now safe to remove the
-        // node from the tree.
-        if (currentParentIsContainer) {
-          removeChildFromContainer(currentParent, node.stateNode);
-        } else {
-          removeChild(currentParent, node.stateNode);
-        }
-        // Don't visit children because we already visited them.
-      } else if (node.tag === HostPortal) {
-        // When we go into a portal, it becomes the parent to remove from.
-        // We will reassign it back when we pop the portal on the way up.
-        currentParent = node.stateNode.containerInfo;
-        // Visit children because portals might contain host components.
-        if (node.child !== null) {
-          node.child["return"] = node;
-          node = node.child;
-          continue;
-        }
-      } else {
-        commitUnmount(node);
-        // Visit children because we may find more host components below.
-        if (node.child !== null) {
-          node.child["return"] = node;
-          node = node.child;
-          continue;
-        }
-      }
-      if (node === current) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === current) {
-          return;
-        }
-        node = node["return"];
-        if (node.tag === HostPortal) {
-          // When we go out of the portal, we need to restore the parent.
-          // Since we don't keep a stack of them, we will search for it.
-          currentParentIsValid = false;
-        }
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-
-  function commitDeletion(current) {
-    // Recursively delete all host nodes from the parent.
-    // Detach refs and call componentWillUnmount() on the whole subtree.
-    unmountHostComponents(current);
-    detachFiber(current);
-  }
-
-  function commitWork(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        return;
-      }
-      case HostComponent: {
-        var _instance8 = finishedWork.stateNode;
-        if (_instance8 != null) {
-          // Commit the work prepared earlier.
-          var newProps = finishedWork.memoizedProps;
-          // For hydration we reuse the update path but we treat the oldProps
-          // as the newProps. The updatePayload will contain the real change in
-          // this case.
-          var oldProps = current !== null ? current.memoizedProps : newProps;
-          var type = finishedWork.type;
-          // TODO: Type the updateQueue to be specific to host components.
-          var updatePayload = finishedWork.updateQueue;
-          finishedWork.updateQueue = null;
-          if (updatePayload !== null) {
-            commitUpdate(
-              _instance8,
-              updatePayload,
-              type,
-              oldProps,
-              newProps,
-              finishedWork
-            );
-          }
-        }
-        return;
-      }
-      case HostText: {
-        invariant(
-          finishedWork.stateNode !== null,
-          "This should have a text node initialized. This error is likely " +
-            "caused by a bug in React. Please file an issue."
-        );
-        var textInstance = finishedWork.stateNode;
-        var newText = finishedWork.memoizedProps;
-        // For hydration we reuse the update path but we treat the oldProps
-        // as the newProps. The updatePayload will contain the real change in
-        // this case.
-        var oldText = current !== null ? current.memoizedProps : newText;
-        commitTextUpdate(textInstance, oldText, newText);
-        return;
-      }
-      case HostRoot: {
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
-    }
-  }
-
-  function commitResetTextContent(current) {
-    resetTextContent(current.stateNode);
-  }
-
-  if (enableMutatingReconciler) {
-    return {
-      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitResetTextContent: commitResetTextContent,
-      commitPlacement: commitPlacement,
-      commitDeletion: commitDeletion,
-      commitWork: commitWork,
-      commitLifeCycles: commitLifeCycles,
-      commitErrorLogging: commitErrorLogging,
-      commitAttachRef: commitAttachRef,
-      commitDetachRef: commitDetachRef
-    };
-  } else {
-    invariant(false, "Mutating reconciler is disabled.");
-  }
-};
-
-var NO_CONTEXT = {};
-
-var ReactFiberHostContext = function(config, stack) {
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
-
-  var contextStackCursor = createCursor(NO_CONTEXT);
-  var contextFiberStackCursor = createCursor(NO_CONTEXT);
-  var rootInstanceStackCursor = createCursor(NO_CONTEXT);
-
-  function requiredContext(c) {
-    invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-    return c;
-  }
-
-  function getRootHostContainer() {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    return rootInstance;
-  }
-
-  function pushHostContainer(fiber, nextRootInstance) {
-    // Push current root instance onto the stack;
-    // This allows us to reset root when portals are popped.
-    push(rootInstanceStackCursor, nextRootInstance, fiber);
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
-
-    // Finally, we need to push the host context to the stack.
-    // However, we can't just call getRootHostContext() and push it because
-    // we'd have a different number of entries on the stack depending on
-    // whether getRootHostContext() throws somewhere in renderer code or not.
-    // So we push an empty value first. This lets us safely unwind on errors.
-    push(contextStackCursor, NO_CONTEXT, fiber);
-    var nextRootContext = getRootHostContext(nextRootInstance);
-    // Now that we know this function doesn't throw, replace it.
-    pop(contextStackCursor, fiber);
-    push(contextStackCursor, nextRootContext, fiber);
-  }
-
-  function popHostContainer(fiber) {
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
-    pop(rootInstanceStackCursor, fiber);
-  }
-
-  function getHostContext() {
-    var context = requiredContext(contextStackCursor.current);
-    return context;
-  }
-
-  function pushHostContext(fiber) {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    var context = requiredContext(contextStackCursor.current);
-    var nextContext = getChildHostContext(context, fiber.type, rootInstance);
-
-    // Don't push this Fiber's context unless it's unique.
-    if (context === nextContext) {
-      return;
-    }
-
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
-    push(contextStackCursor, nextContext, fiber);
-  }
-
-  function popHostContext(fiber) {
-    // Do not pop unless this Fiber provided the current context.
-    // pushHostContext() only pushes Fibers that provide unique contexts.
-    if (contextFiberStackCursor.current !== fiber) {
-      return;
-    }
-
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
-  }
-
-  return {
-    getHostContext: getHostContext,
-    getRootHostContainer: getRootHostContainer,
-    popHostContainer: popHostContainer,
-    popHostContext: popHostContext,
-    pushHostContainer: pushHostContainer,
-    pushHostContext: pushHostContext
-  };
-};
-
-var ReactFiberHydrationContext = function(config) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    hydration = config.hydration;
-
-  // If this doesn't have hydration mode.
-
-  if (!hydration) {
-    return {
-      enterHydrationState: function() {
-        return false;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostTextInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      popHydrationState: function(fiber) {
-        return false;
-      }
-    };
-  }
-
-  var canHydrateInstance = hydration.canHydrateInstance,
-    canHydrateTextInstance = hydration.canHydrateTextInstance,
-    getNextHydratableSibling = hydration.getNextHydratableSibling,
-    getFirstHydratableChild = hydration.getFirstHydratableChild,
-    hydrateInstance = hydration.hydrateInstance,
-    hydrateTextInstance = hydration.hydrateTextInstance,
-    didNotMatchHydratedContainerTextInstance =
-      hydration.didNotMatchHydratedContainerTextInstance,
-    didNotMatchHydratedTextInstance = hydration.didNotMatchHydratedTextInstance,
-    didNotHydrateContainerInstance = hydration.didNotHydrateContainerInstance,
-    didNotHydrateInstance = hydration.didNotHydrateInstance,
-    didNotFindHydratableContainerInstance =
-      hydration.didNotFindHydratableContainerInstance,
-    didNotFindHydratableContainerTextInstance =
-      hydration.didNotFindHydratableContainerTextInstance,
-    didNotFindHydratableInstance = hydration.didNotFindHydratableInstance,
-    didNotFindHydratableTextInstance =
-      hydration.didNotFindHydratableTextInstance;
-
-  // The deepest Fiber on the stack involved in a hydration context.
-  // This may have been an insertion or a hydration.
-
-  var hydrationParentFiber = null;
-  var nextHydratableInstance = null;
-  var isHydrating = false;
-
-  function enterHydrationState(fiber) {
-    var parentInstance = fiber.stateNode.containerInfo;
-    nextHydratableInstance = getFirstHydratableChild(parentInstance);
-    hydrationParentFiber = fiber;
-    isHydrating = true;
-    return true;
-  }
-
-  function deleteHydratableInstance(returnFiber, instance) {
-    {
-      switch (returnFiber.tag) {
-        case HostRoot:
-          didNotHydrateContainerInstance(
-            returnFiber.stateNode.containerInfo,
-            instance
-          );
-          break;
-        case HostComponent:
-          didNotHydrateInstance(
-            returnFiber.type,
-            returnFiber.memoizedProps,
-            returnFiber.stateNode,
-            instance
-          );
-          break;
-      }
-    }
-
-    var childToDelete = createFiberFromHostInstanceForDeletion();
-    childToDelete.stateNode = instance;
-    childToDelete["return"] = returnFiber;
-    childToDelete.effectTag = Deletion;
-
-    // This might seem like it belongs on progressedFirstDeletion. However,
-    // these children are not part of the reconciliation list of children.
-    // Even if we abort and rereconcile the children, that will try to hydrate
-    // again and the nodes are still in the host tree so these will be
-    // recreated.
-    if (returnFiber.lastEffect !== null) {
-      returnFiber.lastEffect.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
-    } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
-    }
-  }
-
-  function insertNonHydratedInstance(returnFiber, fiber) {
-    fiber.effectTag |= Placement;
-    {
-      switch (returnFiber.tag) {
-        case HostRoot: {
-          var parentContainer = returnFiber.stateNode.containerInfo;
-          switch (fiber.tag) {
-            case HostComponent:
-              var type = fiber.type;
-              var props = fiber.pendingProps;
-              didNotFindHydratableContainerInstance(
-                parentContainer,
-                type,
-                props
-              );
-              break;
-            case HostText:
-              var text = fiber.pendingProps;
-              didNotFindHydratableContainerTextInstance(parentContainer, text);
-              break;
-          }
-          break;
-        }
-        case HostComponent: {
-          var parentType = returnFiber.type;
-          var parentProps = returnFiber.memoizedProps;
-          var parentInstance = returnFiber.stateNode;
-          switch (fiber.tag) {
-            case HostComponent:
-              var _type = fiber.type;
-              var _props = fiber.pendingProps;
-              didNotFindHydratableInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _type,
-                _props
-              );
-              break;
-            case HostText:
-              var _text = fiber.pendingProps;
-              didNotFindHydratableTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _text
-              );
-              break;
-          }
-          break;
-        }
-        default:
-          return;
-      }
-    }
-  }
-
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case HostComponent: {
-        var type = fiber.type;
-        var props = fiber.pendingProps;
-        var instance = canHydrateInstance(nextInstance, type, props);
-        if (instance !== null) {
-          fiber.stateNode = instance;
-          return true;
-        }
-        return false;
-      }
-      case HostText: {
-        var text = fiber.pendingProps;
-        var textInstance = canHydrateTextInstance(nextInstance, text);
-        if (textInstance !== null) {
-          fiber.stateNode = textInstance;
-          return true;
-        }
-        return false;
-      }
-      default:
-        return false;
-    }
-  }
-
-  function tryToClaimNextHydratableInstance(fiber) {
-    if (!isHydrating) {
-      return;
-    }
-    var nextInstance = nextHydratableInstance;
-    if (!nextInstance) {
-      // Nothing to hydrate. Make it an insertion.
-      insertNonHydratedInstance(hydrationParentFiber, fiber);
-      isHydrating = false;
-      hydrationParentFiber = fiber;
-      return;
-    }
-    if (!tryHydrate(fiber, nextInstance)) {
-      // If we can't hydrate this instance let's try the next one.
-      // We use this as a heuristic. It's based on intuition and not data so it
-      // might be flawed or unnecessary.
-      nextInstance = getNextHydratableSibling(nextInstance);
-      if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-        // Nothing to hydrate. Make it an insertion.
-        insertNonHydratedInstance(hydrationParentFiber, fiber);
-        isHydrating = false;
-        hydrationParentFiber = fiber;
-        return;
-      }
-      // We matched the next one, we'll now assume that the first one was
-      // superfluous and we'll delete it. Since we can't eagerly delete it
-      // we'll have to schedule a deletion. To do that, this node needs a dummy
-      // fiber associated with it.
-      deleteHydratableInstance(hydrationParentFiber, nextHydratableInstance);
-    }
-    hydrationParentFiber = fiber;
-    nextHydratableInstance = getFirstHydratableChild(nextInstance);
-  }
-
-  function prepareToHydrateHostInstance(
-    fiber,
-    rootContainerInstance,
-    hostContext
-  ) {
-    var instance = fiber.stateNode;
-    var updatePayload = hydrateInstance(
-      instance,
-      fiber.type,
-      fiber.memoizedProps,
-      rootContainerInstance,
-      hostContext,
-      fiber
-    );
-    // TODO: Type this specific to this type of component.
-    fiber.updateQueue = updatePayload;
-    // If the update payload indicates that there is a change or if there
-    // is a new ref we mark this as an update.
-    if (updatePayload !== null) {
-      return true;
-    }
-    return false;
-  }
-
-  function prepareToHydrateHostTextInstance(fiber) {
-    var textInstance = fiber.stateNode;
-    var textContent = fiber.memoizedProps;
-    var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
-    {
-      if (shouldUpdate) {
-        // We assume that prepareToHydrateHostTextInstance is called in a context where the
-        // hydration parent is the parent host component of this host text.
-        var returnFiber = hydrationParentFiber;
-        if (returnFiber !== null) {
-          switch (returnFiber.tag) {
-            case HostRoot: {
-              var parentContainer = returnFiber.stateNode.containerInfo;
-              didNotMatchHydratedContainerTextInstance(
-                parentContainer,
-                textInstance,
-                textContent
-              );
-              break;
-            }
-            case HostComponent: {
-              var parentType = returnFiber.type;
-              var parentProps = returnFiber.memoizedProps;
-              var parentInstance = returnFiber.stateNode;
-              didNotMatchHydratedTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                textInstance,
-                textContent
-              );
-              break;
-            }
-          }
-        }
-      }
-    }
-    return shouldUpdate;
-  }
-
-  function popToNextHostParent(fiber) {
-    var parent = fiber["return"];
-    while (
-      parent !== null &&
-      parent.tag !== HostComponent &&
-      parent.tag !== HostRoot
-    ) {
-      parent = parent["return"];
-    }
-    hydrationParentFiber = parent;
-  }
-
-  function popHydrationState(fiber) {
-    if (fiber !== hydrationParentFiber) {
-      // We're deeper than the current hydration context, inside an inserted
-      // tree.
-      return false;
-    }
-    if (!isHydrating) {
-      // If we're not currently hydrating but we're in a hydration context, then
-      // we were an insertion and now need to pop up reenter hydration of our
-      // siblings.
-      popToNextHostParent(fiber);
-      isHydrating = true;
-      return false;
-    }
-
-    var type = fiber.type;
-
-    // If we have any remaining hydratable nodes, we need to delete them now.
-    // We only do this deeper than head and body since they tend to have random
-    // other nodes in them. We also ignore components with pure text content in
-    // side of them.
-    // TODO: Better heuristic.
-    if (
-      fiber.tag !== HostComponent ||
-      (type !== "head" &&
-        type !== "body" &&
-        !shouldSetTextContent(type, fiber.memoizedProps))
-    ) {
-      var nextInstance = nextHydratableInstance;
-      while (nextInstance) {
-        deleteHydratableInstance(fiber, nextInstance);
-        nextInstance = getNextHydratableSibling(nextInstance);
-      }
-    }
-
-    popToNextHostParent(fiber);
-    nextHydratableInstance = hydrationParentFiber
-      ? getNextHydratableSibling(fiber.stateNode)
-      : null;
-    return true;
-  }
-
-  function resetHydrationState() {
-    hydrationParentFiber = null;
-    nextHydratableInstance = null;
-    isHydrating = false;
-  }
-
-  return {
-    enterHydrationState: enterHydrationState,
-    resetHydrationState: resetHydrationState,
-    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
-    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
-    popHydrationState: popHydrationState
-  };
-};
-
-// This lets us hook into Fiber to debug what it's doing.
-// See https://github.com/facebook/react/pull/8033.
-// This is not part of the public API, not even for React DevTools.
-// You may only inject a debugTool if you work on React Fiber itself.
-var ReactFiberInstrumentation = {
-  debugTool: null
-};
-
-var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
-
-var warnedAboutMissingGetChildContext = void 0;
-
-{
-  warnedAboutMissingGetChildContext = {};
-}
-
-var ReactFiberLegacyContext = function(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
-
-  // A cursor to the current merged context object on the stack.
-
-  var contextStackCursor = createCursor(emptyObject);
-  // A cursor to a boolean indicating whether the context has changed.
-  var didPerformWorkStackCursor = createCursor(false);
-  // Keep track of the previous context object that was on the stack.
-  // We use this to get access to the parent context after we have already
-  // pushed the next context provider, and now need to merge their contexts.
-  var previousContext = emptyObject;
-
-  function getUnmaskedContext(workInProgress) {
-    var hasOwnContext = isContextProvider(workInProgress);
-    if (hasOwnContext) {
-      // If the fiber is a context provider itself, when we read its context
-      // we have already pushed its own child context on the stack. A context
-      // provider should not "see" its own child context. Therefore we read the
-      // previous (parent) context instead for a context provider.
-      return previousContext;
-    }
-    return contextStackCursor.current;
-  }
-
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    var instance = workInProgress.stateNode;
-    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
-  }
-
-  function getMaskedContext(workInProgress, unmaskedContext) {
-    var type = workInProgress.type;
-    var contextTypes = type.contextTypes;
-    if (!contextTypes) {
-      return emptyObject;
-    }
-
-    // Avoid recreating masked context unless unmasked context has changed.
-    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
-    // This may trigger infinite loops if componentWillReceiveProps calls setState.
-    var instance = workInProgress.stateNode;
-    if (
-      instance &&
-      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-    ) {
-      return instance.__reactInternalMemoizedMaskedChildContext;
-    }
-
-    var context = {};
-    for (var key in contextTypes) {
-      context[key] = unmaskedContext[key];
-    }
-
-    {
-      var name = getComponentName(workInProgress) || "Unknown";
-      checkPropTypes(
-        contextTypes,
-        context,
-        "context",
-        name,
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-      );
-    }
-
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // Context is created before the class component is instantiated so check for instance.
-    if (instance) {
-      cacheContext(workInProgress, unmaskedContext, context);
-    }
-
-    return context;
-  }
-
-  function hasContextChanged() {
-    return didPerformWorkStackCursor.current;
-  }
-
-  function isContextConsumer(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
-  }
-
-  function isContextProvider(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
-  }
-
-  function popContextProvider(fiber) {
-    if (!isContextProvider(fiber)) {
-      return;
-    }
-
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
-  }
-
-  function popTopLevelContextObject(fiber) {
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
-  }
-
-  function pushTopLevelContextObject(fiber, context, didChange) {
-    invariant(
-      contextStackCursor.cursor == null,
-      "Unexpected context found on stack. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    push(contextStackCursor, context, fiber);
-    push(didPerformWorkStackCursor, didChange, fiber);
-  }
-
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode;
-    var childContextTypes = fiber.type.childContextTypes;
-
-    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
-    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
-    if (typeof instance.getChildContext !== "function") {
-      {
-        var componentName = getComponentName(fiber) || "Unknown";
-
-        if (!warnedAboutMissingGetChildContext[componentName]) {
-          warnedAboutMissingGetChildContext[componentName] = true;
-          warning(
-            false,
-            "%s.childContextTypes is specified but there is no getChildContext() method " +
-              "on the instance. You can either define getChildContext() on %s or remove " +
-              "childContextTypes from it.",
-            componentName,
-            componentName
-          );
-        }
-      }
-      return parentContext;
-    }
-
-    var childContext = void 0;
-    {
-      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
-    }
-    startPhaseTimer(fiber, "getChildContext");
-    childContext = instance.getChildContext();
-    stopPhaseTimer();
-    {
-      ReactDebugCurrentFiber.setCurrentPhase(null);
-    }
-    for (var contextKey in childContext) {
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
-      );
-    }
-    {
-      var name = getComponentName(fiber) || "Unknown";
-      checkPropTypes(
-        childContextTypes,
-        childContext,
-        "child context",
-        name,
-        // In practice, there is one case in which we won't get a stack. It's when
-        // somebody calls unstable_renderSubtreeIntoContainer() and we process
-        // context from the parent component instance. The stack will be missing
-        // because it's outside of the reconciliation, and so the pointer has not
-        // been set. This is rare and doesn't matter. We'll also remove that API.
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-      );
-    }
-
-    return Object.assign({}, parentContext, childContext);
-  }
-
-  function pushContextProvider(workInProgress) {
-    if (!isContextProvider(workInProgress)) {
-      return false;
-    }
-
-    var instance = workInProgress.stateNode;
-    // We push the context as early as possible to ensure stack integrity.
-    // If the instance does not exist yet, we will push null at first,
-    // and replace it on the stack later when invalidating the context.
-    var memoizedMergedChildContext =
-      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-      emptyObject;
-
-    // Remember the parent context so we can merge with it later.
-    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
-    previousContext = contextStackCursor.current;
-    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
-    push(
-      didPerformWorkStackCursor,
-      didPerformWorkStackCursor.current,
-      workInProgress
-    );
-
-    return true;
-  }
-
-  function invalidateContextProvider(workInProgress, didChange) {
-    var instance = workInProgress.stateNode;
-    invariant(
-      instance,
-      "Expected to have an instance by this point. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    if (didChange) {
-      // Merge parent and own context.
-      // Skip this if we're not updating due to sCU.
-      // This avoids unnecessarily recomputing memoized values.
-      var mergedContext = processChildContext(workInProgress, previousContext);
-      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-
-      // Replace the old (or empty) context with the new one.
-      // It is important to unwind the context in the reverse order.
-      pop(didPerformWorkStackCursor, workInProgress);
-      pop(contextStackCursor, workInProgress);
-      // Now push the new context and mark that it has changed.
-      push(contextStackCursor, mergedContext, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    } else {
-      pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    }
-  }
-
-  function findCurrentUnmaskedContext(fiber) {
-    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
-    // makes sense elsewhere
-    invariant(
-      isFiberMounted(fiber) && fiber.tag === ClassComponent,
-      "Expected subtree parent to be a mounted class component. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    var node = fiber;
-    while (node.tag !== HostRoot) {
-      if (isContextProvider(node)) {
-        return node.stateNode.__reactInternalMemoizedMergedChildContext;
-      }
-      var parent = node["return"];
-      invariant(
-        parent,
-        "Found unexpected detached subtree parent. " +
-          "This error is likely caused by a bug in React. Please file an issue."
-      );
-      node = parent;
-    }
-    return node.stateNode.context;
-  }
-
-  return {
-    getUnmaskedContext: getUnmaskedContext,
-    cacheContext: cacheContext,
-    getMaskedContext: getMaskedContext,
-    hasContextChanged: hasContextChanged,
-    isContextConsumer: isContextConsumer,
-    isContextProvider: isContextProvider,
-    popContextProvider: popContextProvider,
-    popTopLevelContextObject: popTopLevelContextObject,
-    pushTopLevelContextObject: pushTopLevelContextObject,
-    processChildContext: processChildContext,
-    pushContextProvider: pushContextProvider,
-    invalidateContextProvider: invalidateContextProvider,
-    findCurrentUnmaskedContext: findCurrentUnmaskedContext
-  };
-};
-
-var ReactFiberNewContext = function(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
-
-  var providerCursor = createCursor(null);
-  var valueCursor = createCursor(null);
-  var changedBitsCursor = createCursor(0);
-
-  var rendererSigil = void 0;
-  {
-    // Use this to detect multiple renderers using the same context
-    rendererSigil = {};
-  }
-
-  function pushProvider(providerFiber) {
-    var context = providerFiber.type._context;
-
-    push(changedBitsCursor, context._changedBits, providerFiber);
-    push(valueCursor, context._currentValue, providerFiber);
-    push(providerCursor, providerFiber, providerFiber);
-
-    context._currentValue = providerFiber.pendingProps.value;
-    context._changedBits = providerFiber.stateNode;
-
-    {
-      !(
-        context._currentRenderer === null ||
-        context._currentRenderer === rendererSigil
-      )
-        ? warning(
-            false,
-            "Detected multiple renderers concurrently rendering the " +
-              "same context provider. This is currently unsupported."
-          )
-        : void 0;
-      context._currentRenderer = rendererSigil;
-    }
-  }
-
-  function popProvider(providerFiber) {
-    var changedBits = changedBitsCursor.current;
-    var currentValue = valueCursor.current;
-
-    pop(providerCursor, providerFiber);
-    pop(valueCursor, providerFiber);
-    pop(changedBitsCursor, providerFiber);
-
-    var context = providerFiber.type._context;
-    context._currentValue = currentValue;
-    context._changedBits = changedBits;
-  }
-
-  return {
-    pushProvider: pushProvider,
-    popProvider: popProvider
-  };
-};
-
-var ReactFiberStack = function() {
-  var valueStack = [];
-
-  var fiberStack = void 0;
-
-  {
-    fiberStack = [];
-  }
-
-  var index = -1;
-
-  function createCursor(defaultValue) {
-    return {
-      current: defaultValue
-    };
-  }
-
-  function isEmpty() {
-    return index === -1;
-  }
-
-  function pop(cursor, fiber) {
-    if (index < 0) {
-      {
-        warning(false, "Unexpected pop.");
-      }
-      return;
-    }
-
-    {
-      if (fiber !== fiberStack[index]) {
-        warning(false, "Unexpected Fiber popped.");
-      }
-    }
-
-    cursor.current = valueStack[index];
-
-    valueStack[index] = null;
-
-    {
-      fiberStack[index] = null;
-    }
-
-    index--;
-  }
-
-  function push(cursor, value, fiber) {
-    index++;
-
-    valueStack[index] = cursor.current;
-
-    {
-      fiberStack[index] = fiber;
-    }
-
-    cursor.current = value;
-  }
-
-  function checkThatStackIsEmpty() {
-    {
-      if (index !== -1) {
-        warning(
-          false,
-          "Expected an empty stack. Something was not reset properly."
-        );
-      }
-    }
-  }
-
-  function resetStackAfterFatalErrorInDev() {
-    {
-      index = -1;
-      valueStack.length = 0;
-      fiberStack.length = 0;
-    }
-  }
-
-  return {
-    createCursor: createCursor,
-    isEmpty: isEmpty,
-    pop: pop,
-    push: push,
-    checkThatStackIsEmpty: checkThatStackIsEmpty,
-    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
-  };
-};
-
-var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError = ReactErrorUtils.hasCaughtError;
-var clearCaughtError = ReactErrorUtils.clearCaughtError;
-
-var didWarnAboutStateTransition = void 0;
-var didWarnSetStateChildContext = void 0;
-var warnAboutUpdateOnUnmounted = void 0;
-var warnAboutInvalidUpdates = void 0;
-
-{
-  didWarnAboutStateTransition = false;
-  didWarnSetStateChildContext = false;
-  var didWarnStateUpdateForUnmountedComponent = {};
-
-  warnAboutUpdateOnUnmounted = function(fiber) {
-    // We show the whole stack but dedupe on the top component's name because
-    // the problematic code almost always lies inside that component.
-    var componentName = getComponentName(fiber) || "ReactClass";
-    if (didWarnStateUpdateForUnmountedComponent[componentName]) {
-      return;
-    }
-    warning(
-      false,
-      "Can't call setState (or forceUpdate) on an unmounted component. This " +
-        "is a no-op, but it indicates a memory leak in your application. To " +
-        "fix, cancel all subscriptions and asynchronous tasks in the " +
-        "componentWillUnmount method.%s",
-      getStackAddendumByWorkInProgressFiber(fiber)
-    );
-    didWarnStateUpdateForUnmountedComponent[componentName] = true;
-  };
-
-  warnAboutInvalidUpdates = function(instance) {
-    switch (ReactDebugCurrentFiber.phase) {
-      case "getChildContext":
-        if (didWarnSetStateChildContext) {
-          return;
-        }
-        warning(
-          false,
-          "setState(...): Cannot call setState() inside getChildContext()"
-        );
-        didWarnSetStateChildContext = true;
-        break;
-      case "render":
-        if (didWarnAboutStateTransition) {
-          return;
-        }
-        warning(
-          false,
-          "Cannot update during an existing state transition (such as within " +
-            "`render` or another component's constructor). Render methods should " +
-            "be a pure function of props and state; constructor side-effects are " +
-            "an anti-pattern, but can be moved to `componentWillMount`."
-        );
-        didWarnAboutStateTransition = true;
-        break;
-    }
-  };
-}
-
-var ReactFiberScheduler = function(config) {
-  var stack = ReactFiberStack();
-  var hostContext = ReactFiberHostContext(config, stack);
-  var legacyContext = ReactFiberLegacyContext(stack);
-  var newContext = ReactFiberNewContext(stack);
-  var popHostContext = hostContext.popHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popLegacyContextProvider = legacyContext.popContextProvider;
-  var popProvider = newContext.popProvider;
-
-  var hydrationContext = ReactFiberHydrationContext(config);
-
-  var _ReactFiberBeginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber
-    ),
-    beginWork = _ReactFiberBeginWork.beginWork;
-
-  var _ReactFiberCompleteWo = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext
-    ),
-    completeWork = _ReactFiberCompleteWo.completeWork;
-
-  var _ReactFiberUnwindWork = ReactFiberUnwindWork(
-      hostContext,
-      legacyContext,
-      newContext,
-      scheduleWork,
-      isAlreadyFailedLegacyErrorBoundary
-    ),
-    throwException = _ReactFiberUnwindWork.throwException,
-    unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
-
-  var _ReactFiberCommitWork = ReactFiberCommitWork(
-      config,
-      onCommitPhaseError,
-      scheduleWork,
-      computeExpirationForFiber,
-      markLegacyErrorBoundaryAsFailed,
-      recalculateCurrentTime
-    ),
-    commitBeforeMutationLifeCycles =
-      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
-    commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
-    commitPlacement = _ReactFiberCommitWork.commitPlacement,
-    commitDeletion = _ReactFiberCommitWork.commitDeletion,
-    commitWork = _ReactFiberCommitWork.commitWork,
-    commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
-    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
-    commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
-    commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
-
-  var now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit;
-
-  // Represents the current time in ms.
-
-  var originalStartTimeMs = now();
-  var mostRecentCurrentTime = msToExpirationTime(0);
-  var mostRecentCurrentTimeMs = originalStartTimeMs;
-
-  // Used to ensure computeUniqueAsyncExpiration is monotonically increases.
-  var lastUniqueAsyncExpiration = 0;
-
-  // Represents the expiration time that incoming updates should use. (If this
-  // is NoWork, use the default strategy: async updates in async mode, sync
-  // updates in sync mode.)
-  var expirationContext = NoWork;
-
-  var isWorking = false;
-
-  // The next work in progress fiber that we're currently working on.
-  var nextUnitOfWork = null;
-  var nextRoot = null;
-  // The time at which we're currently rendering work.
-  var nextRenderExpirationTime = NoWork;
-
-  // The next fiber with an effect that we're currently committing.
-  var nextEffect = null;
-
-  var isCommitting = false;
-
-  var isRootReadyForCommit = false;
-
-  var legacyErrorBoundariesThatAlreadyFailed = null;
-
-  // Used for performance tracking.
-  var interruptedBy = null;
-
-  var stashedWorkInProgressProperties = void 0;
-  var replayUnitOfWork = void 0;
-  var isReplayingFailedUnitOfWork = void 0;
-  var originalReplayError = void 0;
-  var rethrowOriginalError = void 0;
-  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-    stashedWorkInProgressProperties = null;
-    isReplayingFailedUnitOfWork = false;
-    originalReplayError = null;
-    replayUnitOfWork = function(failedUnitOfWork, error, isAsync) {
-      // Restore the original state of the work-in-progress
-      assignFiberPropertiesInDEV(
-        failedUnitOfWork,
-        stashedWorkInProgressProperties
-      );
-      switch (failedUnitOfWork.tag) {
-        case HostRoot:
-          popHostContainer(failedUnitOfWork);
-          popTopLevelLegacyContextObject(failedUnitOfWork);
-          break;
-        case HostComponent:
-          popHostContext(failedUnitOfWork);
-          break;
-        case ClassComponent:
-          popLegacyContextProvider(failedUnitOfWork);
-          break;
-        case HostPortal:
-          popHostContainer(failedUnitOfWork);
-          break;
-        case ContextProvider:
-          popProvider(failedUnitOfWork);
-          break;
-      }
-      // Replay the begin phase.
-      isReplayingFailedUnitOfWork = true;
-      originalReplayError = error;
-      invokeGuardedCallback$2(null, workLoop, null, isAsync);
-      isReplayingFailedUnitOfWork = false;
-      originalReplayError = null;
-      if (hasCaughtError()) {
-        clearCaughtError();
-      } else {
-        // If the begin phase did not fail the second time, set this pointer
-        // back to the original value.
-        nextUnitOfWork = failedUnitOfWork;
-      }
-    };
-    rethrowOriginalError = function() {
-      throw originalReplayError;
-    };
-  }
-
-  function resetStack() {
-    if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork["return"];
-      while (interruptedWork !== null) {
-        unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork["return"];
-      }
-    }
-
-    {
-      ReactStrictModeWarnings.discardPendingWarnings();
-      stack.checkThatStackIsEmpty();
-    }
-
-    nextRoot = null;
-    nextRenderExpirationTime = NoWork;
-    nextUnitOfWork = null;
-
-    isRootReadyForCommit = false;
-  }
-
-  function commitAllHostEffects() {
-    while (nextEffect !== null) {
-      {
-        ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
-      }
-      recordEffect();
-
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & ContentReset) {
-        commitResetTextContent(nextEffect);
-      }
-
-      if (effectTag & Ref) {
-        var current = nextEffect.alternate;
-        if (current !== null) {
-          commitDetachRef(current);
-        }
-      }
-
-      // The following switch statement is only concerned about placement,
-      // updates, and deletions. To avoid needing to add a case for every
-      // possible bitmap value, we remove the secondary effects from the
-      // effect tag and switch on that value.
-      var primaryEffectTag = effectTag & (Placement | Update | Deletion);
-      switch (primaryEffectTag) {
-        case Placement: {
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          // TODO: findDOMNode doesn't rely on this any more but isMounted
-          // does and isMounted is deprecated anyway so we should be able
-          // to kill this.
-          nextEffect.effectTag &= ~Placement;
-          break;
-        }
-        case PlacementAndUpdate: {
-          // Placement
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          nextEffect.effectTag &= ~Placement;
-
-          // Update
-          var _current = nextEffect.alternate;
-          commitWork(_current, nextEffect);
-          break;
-        }
-        case Update: {
-          var _current2 = nextEffect.alternate;
-          commitWork(_current2, nextEffect);
-          break;
-        }
-        case Deletion: {
-          commitDeletion(nextEffect);
-          break;
-        }
-      }
-      nextEffect = nextEffect.nextEffect;
-    }
-
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
-    }
-  }
-
-  function commitBeforeMutationLifecycles() {
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & Snapshot) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitBeforeMutationLifeCycles(current, nextEffect);
-      }
-
-      // Don't cleanup effects yet;
-      // This will be done by commitAllLifeCycles()
-      nextEffect = nextEffect.nextEffect;
-    }
-  }
-
-  function commitAllLifeCycles(
-    finishedRoot,
-    currentTime,
-    committedExpirationTime
-  ) {
-    {
-      ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
-
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.flushPendingDeprecationWarnings();
-      }
-    }
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & (Update | Callback)) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitLifeCycles(
-          finishedRoot,
-          current,
-          nextEffect,
-          currentTime,
-          committedExpirationTime
-        );
-      }
-
-      if (effectTag & ErrLog) {
-        commitErrorLogging(nextEffect, onUncaughtError);
-      }
-
-      if (effectTag & Ref) {
-        recordEffect();
-        commitAttachRef(nextEffect);
-      }
-
-      var next = nextEffect.nextEffect;
-      // Ensure that we clean these up so that we don't accidentally keep them.
-      // I'm not actually sure this matters because we can't reset firstEffect
-      // and lastEffect since they're on every node, not just the effectful
-      // ones. So we have to clean everything as we reuse nodes anyway.
-      nextEffect.nextEffect = null;
-      // Ensure that we reset the effectTag here so that we can rely on effect
-      // tags to reason about the current life-cycle.
-      nextEffect = next;
-    }
-  }
-
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      legacyErrorBoundariesThatAlreadyFailed !== null &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
-  }
-
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    if (legacyErrorBoundariesThatAlreadyFailed === null) {
-      legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
-    } else {
-      legacyErrorBoundariesThatAlreadyFailed.add(instance);
-    }
-  }
-
-  function commitRoot(finishedWork) {
-    isWorking = true;
-    isCommitting = true;
-    startCommitTimer();
-
-    var root = finishedWork.stateNode;
-    invariant(
-      root.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug " +
-        "related to the return field. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-    var committedExpirationTime = root.pendingCommitExpirationTime;
-    invariant(
-      committedExpirationTime !== NoWork,
-      "Cannot commit an incomplete root. This error is likely caused by a " +
-        "bug in React. Please file an issue."
-    );
-    root.pendingCommitExpirationTime = NoWork;
-
-    var currentTime = recalculateCurrentTime();
-
-    // Reset this to null before calling lifecycles
-    ReactCurrentOwner.current = null;
-
-    var firstEffect = void 0;
-    if (finishedWork.effectTag > PerformedWork) {
-      // A fiber's effect list consists only of its children, not itself. So if
-      // the root has an effect, we need to add it to the end of the list. The
-      // resulting list is the set that would belong to the root's parent, if
-      // it had one; that is, all the effects in the tree including the root.
-      if (finishedWork.lastEffect !== null) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        firstEffect = finishedWork.firstEffect;
-      } else {
-        firstEffect = finishedWork;
-      }
-    } else {
-      // There is no effect on the root.
-      firstEffect = finishedWork.firstEffect;
-    }
-
-    prepareForCommit(root.containerInfo);
-
-    // Invoke instances of getSnapshotBeforeUpdate before mutation.
-    nextEffect = firstEffect;
-    startCommitSnapshotEffectsTimer();
-    while (nextEffect !== null) {
-      var didError = false;
-      var error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
-        if (hasCaughtError()) {
-          didError = true;
-          error = clearCaughtError();
-        }
-      }
-      if (didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
-    stopCommitSnapshotEffectsTimer();
-
-    // Commit all the side-effects within a tree. We'll do this in two passes.
-    // The first pass performs all the host insertions, updates, deletions and
-    // ref unmounts.
-    nextEffect = firstEffect;
-    startCommitHostEffectsTimer();
-    while (nextEffect !== null) {
-      var _didError = false;
-      var _error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitAllHostEffects, null);
-        if (hasCaughtError()) {
-          _didError = true;
-          _error = clearCaughtError();
-        }
-      }
-      if (_didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
-    stopCommitHostEffectsTimer();
-
-    resetAfterCommit(root.containerInfo);
-
-    // The work-in-progress tree is now the current tree. This must come after
-    // the first pass of the commit phase, so that the previous tree is still
-    // current during componentWillUnmount, but before the second pass, so that
-    // the finished work is current during componentDidMount/Update.
-    root.current = finishedWork;
-
-    // In the second pass we'll perform all life-cycles and ref callbacks.
-    // Life-cycles happen as a separate pass so that all placements, updates,
-    // and deletions in the entire tree have already been invoked.
-    // This pass also triggers any renderer-specific initial effects.
-    nextEffect = firstEffect;
-    startCommitLifeCyclesTimer();
-    while (nextEffect !== null) {
-      var _didError2 = false;
-      var _error2 = void 0;
-      {
-        invokeGuardedCallback$2(
-          null,
-          commitAllLifeCycles,
-          null,
-          root,
-          currentTime,
-          committedExpirationTime
-        );
-        if (hasCaughtError()) {
-          _didError2 = true;
-          _error2 = clearCaughtError();
-        }
-      }
-      if (_didError2) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error2);
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
-
-    isCommitting = false;
-    isWorking = false;
-    stopCommitLifeCyclesTimer();
-    stopCommitTimer();
-    if (typeof onCommitRoot === "function") {
-      onCommitRoot(finishedWork.stateNode);
-    }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
-    }
-
-    var remainingTime = root.current.expirationTime;
-    if (remainingTime === NoWork) {
-      // If there's no remaining work, we can clear the set of already failed
-      // error boundaries.
-      legacyErrorBoundariesThatAlreadyFailed = null;
-    }
-    return remainingTime;
-  }
-
-  function resetExpirationTime(workInProgress, renderTime) {
-    if (renderTime !== Never && workInProgress.expirationTime === Never) {
-      // The children of this component are hidden. Don't bubble their
-      // expiration times.
-      return;
-    }
-
-    // Check for pending updates.
-    var newExpirationTime = getUpdateExpirationTime(workInProgress);
-
-    // TODO: Calls need to visit stateNode
-
-    // Bubble up the earliest expiration time.
-    var child = workInProgress.child;
-    while (child !== null) {
-      if (
-        child.expirationTime !== NoWork &&
-        (newExpirationTime === NoWork ||
-          newExpirationTime > child.expirationTime)
-      ) {
-        newExpirationTime = child.expirationTime;
-      }
-      child = child.sibling;
-    }
-    workInProgress.expirationTime = newExpirationTime;
-  }
-
-  function completeUnitOfWork(workInProgress) {
-    // Attempt to complete the current unit of work, then move to the
-    // next sibling. If there are no more siblings, return to the
-    // parent fiber.
-    while (true) {
-      // The current, flushed, state of this fiber is the alternate.
-      // Ideally nothing should rely on this, but relying on it here
-      // means that we don't need an additional field on the work in
-      // progress.
-      var current = workInProgress.alternate;
-      {
-        ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
-      }
-
-      var returnFiber = workInProgress["return"];
-      var siblingFiber = workInProgress.sibling;
-
-      if ((workInProgress.effectTag & Incomplete) === NoEffect) {
-        // This fiber completed.
-        var next = completeWork(
-          current,
-          workInProgress,
-          nextRenderExpirationTime
-        );
-        stopWorkTimer(workInProgress);
-        resetExpirationTime(workInProgress, nextRenderExpirationTime);
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
-
-        if (next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
-          }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          return next;
-        }
-
-        if (
-          returnFiber !== null &&
-          // Do not append effects to parents if a sibling failed to complete
-          (returnFiber.effectTag & Incomplete) === NoEffect
-        ) {
-          // Append all the effects of the subtree and this fiber onto the effect
-          // list of the parent. The completion order of the children affects the
-          // side-effect order.
-          if (returnFiber.firstEffect === null) {
-            returnFiber.firstEffect = workInProgress.firstEffect;
-          }
-          if (workInProgress.lastEffect !== null) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
-            }
-            returnFiber.lastEffect = workInProgress.lastEffect;
-          }
-
-          // If this fiber had side-effects, we append it AFTER the children's
-          // side-effects. We can perform certain side-effects earlier if
-          // needed, by doing multiple passes over the effect list. We don't want
-          // to schedule our own side-effect on our own list because if end up
-          // reusing children we'll schedule this effect onto itself since we're
-          // at the end.
-          var effectTag = workInProgress.effectTag;
-          // Skip both NoWork and PerformedWork tags when creating the effect list.
-          // PerformedWork effect is read by React DevTools but shouldn't be committed.
-          if (effectTag > PerformedWork) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress;
-            } else {
-              returnFiber.firstEffect = workInProgress;
-            }
-            returnFiber.lastEffect = workInProgress;
-          }
-        }
-
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
-        }
-
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
-        } else {
-          // We've reached the root.
-          isRootReadyForCommit = true;
-          return null;
-        }
-      } else {
-        // This fiber did not complete because something threw. Pop values off
-        // the stack without entering the complete phase. If this is a boundary,
-        // capture values if possible.
-        var _next = unwindWork(workInProgress);
-        // Because this fiber did not complete, don't reset its expiration time.
-        if (workInProgress.effectTag & DidCapture) {
-          // Restarting an error boundary
-          stopFailedWorkTimer(workInProgress);
-        } else {
-          stopWorkTimer(workInProgress);
-        }
-
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
-
-        if (_next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
-          }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          // Since we're restarting, remove anything that is not a host effect
-          // from the effect tag.
-          _next.effectTag &= HostEffectMask;
-          return _next;
-        }
-
-        if (returnFiber !== null) {
-          // Mark the parent fiber as incomplete and clear its effect list.
-          returnFiber.firstEffect = returnFiber.lastEffect = null;
-          returnFiber.effectTag |= Incomplete;
-        }
-
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
-        }
-
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
-        } else {
-          return null;
-        }
-      }
-    }
-
-    // Without this explicit null return Flow complains of invalid return type
-    // TODO Remove the above while(true) loop
-    // eslint-disable-next-line no-unreachable
-    return null;
-  }
-
-  function performUnitOfWork(workInProgress) {
-    // The current, flushed, state of this fiber is the alternate.
-    // Ideally nothing should rely on this, but relying on it here
-    // means that we don't need an additional field on the work in
-    // progress.
-    var current = workInProgress.alternate;
-
-    // See if beginning this work spawns more work.
-    startWorkTimer(workInProgress);
-    {
-      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
-    }
-
-    if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
-        stashedWorkInProgressProperties,
-        workInProgress
-      );
-    }
-    var next = beginWork(current, workInProgress, nextRenderExpirationTime);
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
-      if (isReplayingFailedUnitOfWork) {
-        // Currently replaying a failed unit of work. This should be unreachable,
-        // because the render phase is meant to be idempotent, and it should
-        // have thrown again. Since it didn't, rethrow the original error, so
-        // React's internal stack is not misaligned.
-        rethrowOriginalError();
-      }
-    }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
-    }
-
-    if (next === null) {
-      // If this doesn't spawn new work, complete the current work.
-      next = completeUnitOfWork(workInProgress);
-    }
-
-    ReactCurrentOwner.current = null;
-
-    return next;
-  }
-
-  function workLoop(isAsync) {
-    if (!isAsync) {
-      // Flush all expired work.
-      while (nextUnitOfWork !== null) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      }
-    } else {
-      // Flush asynchronous work until the deadline runs out of time.
-      while (nextUnitOfWork !== null && !shouldYield()) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      }
-    }
-  }
-
-  function renderRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
-    );
-    isWorking = true;
-
-    // Check if we're starting from a fresh stack, or if we're resuming from
-    // previously yielded work.
-    if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      nextUnitOfWork === null
-    ) {
-      // Reset the stack and start working from the root.
-      resetStack();
-      nextRoot = root;
-      nextRenderExpirationTime = expirationTime;
-      nextUnitOfWork = createWorkInProgress(
-        nextRoot.current,
-        null,
-        nextRenderExpirationTime
-      );
-      root.pendingCommitExpirationTime = NoWork;
-    }
-
-    var didFatal = false;
-
-    startWorkLoopTimer(nextUnitOfWork);
-
-    do {
-      try {
-        workLoop(isAsync);
-      } catch (thrownValue) {
-        if (nextUnitOfWork === null) {
-          // This is a fatal error.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-          break;
-        }
-
-        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-          var failedUnitOfWork = nextUnitOfWork;
-          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
-        }
-
-        var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber["return"];
-        if (returnFiber === null) {
-          // This is the root. The root could capture its own errors. However,
-          // we don't know if it errors before or after we pushed the host
-          // context. This information is needed to avoid a stack mismatch.
-          // Because we're not sure, treat this as a fatal error. We could track
-          // which phase it fails in, but doesn't seem worth it. At least
-          // for now.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        throwException(returnFiber, sourceFiber, thrownValue);
-        nextUnitOfWork = completeUnitOfWork(sourceFiber);
-      }
-      break;
-    } while (true);
-
-    // We're done performing work. Time to clean up.
-    var didCompleteRoot = false;
-    isWorking = false;
-
-    // Yield back to main thread.
-    if (didFatal) {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There was a fatal error.
-      {
-        stack.resetStackAfterFatalErrorInDev();
-      }
-      return null;
-    } else if (nextUnitOfWork === null) {
-      // We reached the root.
-      if (isRootReadyForCommit) {
-        didCompleteRoot = true;
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        // The root successfully completed. It's ready for commit.
-        root.pendingCommitExpirationTime = expirationTime;
-        var finishedWork = root.current.alternate;
-        return finishedWork;
-      } else {
-        // The root did not complete.
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        invariant(
-          false,
-          "Expired work should have completed. This error is likely caused " +
-            "by a bug in React. Please file an issue."
-        );
-      }
-    } else {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There's more work to do, but we ran out of time. Yield back to
-      // the renderer.
-      return null;
-    }
-  }
-
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    // TODO: We only support dispatching errors.
-    var capturedValue = createCapturedValue(value, sourceFiber);
-    var update = {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: false,
-      isForced: false,
-      capturedValue: capturedValue,
-      next: null
-    };
-    insertUpdateIntoFiber(boundaryFiber, update);
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-
-  function dispatch(sourceFiber, value, expirationTime) {
-    invariant(
-      !isWorking || isCommitting,
-      "dispatch: Cannot dispatch during the render phase."
-    );
-
-    // TODO: Handle arrays
-
-    var fiber = sourceFiber["return"];
-    while (fiber !== null) {
-      switch (fiber.tag) {
-        case ClassComponent:
-          var ctor = fiber.type;
-          var instance = fiber.stateNode;
-          if (
-            typeof ctor.getDerivedStateFromCatch === "function" ||
-            (typeof instance.componentDidCatch === "function" &&
-              !isAlreadyFailedLegacyErrorBoundary(instance))
-          ) {
-            scheduleCapture(sourceFiber, fiber, value, expirationTime);
-            return;
-          }
-          break;
-        // TODO: Handle async boundaries
-        case HostRoot:
-          scheduleCapture(sourceFiber, fiber, value, expirationTime);
-          return;
-      }
-      fiber = fiber["return"];
-    }
-
-    if (sourceFiber.tag === HostRoot) {
-      // Error was thrown at the root. There is no parent, so the root
-      // itself should capture it.
-      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
-    }
-  }
-
-  function onCommitPhaseError(fiber, error) {
-    return dispatch(fiber, error, Sync);
-  }
-
-  function computeAsyncExpiration(currentTime) {
-    // Given the current clock time, returns an expiration time. We use rounding
-    // to batch like updates together.
-    // Should complete within ~1000ms. 1200ms max.
-    var expirationMs = 5000;
-    var bucketSizeMs = 250;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
-
-  function computeInteractiveExpiration(currentTime) {
-    var expirationMs = void 0;
-    // We intentionally set a higher expiration time for interactive updates in
-    // dev than in production.
-    // If the main thread is being blocked so long that you hit the expiration,
-    // it's a problem that could be solved with better scheduling.
-    // People will be more likely to notice this and fix it with the long
-    // expiration time in development.
-    // In production we opt for better UX at the risk of masking scheduling
-    // problems, by expiring fast.
-    {
-      // Should complete within ~500ms. 600ms max.
-      expirationMs = 500;
-    }
-    var bucketSizeMs = 100;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
-
-  // Creates a unique async expiration time.
-  function computeUniqueAsyncExpiration() {
-    var currentTime = recalculateCurrentTime();
-    var result = computeAsyncExpiration(currentTime);
-    if (result <= lastUniqueAsyncExpiration) {
-      // Since we assume the current time monotonically increases, we only hit
-      // this branch when computeUniqueAsyncExpiration is fired multiple times
-      // within a 200ms window (or whatever the async bucket size is).
-      result = lastUniqueAsyncExpiration + 1;
-    }
-    lastUniqueAsyncExpiration = result;
-    return lastUniqueAsyncExpiration;
-  }
-
-  function computeExpirationForFiber(fiber) {
-    var expirationTime = void 0;
-    if (expirationContext !== NoWork) {
-      // An explicit expiration context was set;
-      expirationTime = expirationContext;
-    } else if (isWorking) {
-      if (isCommitting) {
-        // Updates that occur during the commit phase should have sync priority
-        // by default.
-        expirationTime = Sync;
-      } else {
-        // Updates during the render phase should expire at the same time as
-        // the work that is being rendered.
-        expirationTime = nextRenderExpirationTime;
-      }
-    } else {
-      // No explicit expiration context was set, and we're not currently
-      // performing work. Calculate a new expiration time.
-      if (fiber.mode & AsyncMode) {
-        if (isBatchingInteractiveUpdates) {
-          // This is an interactive update
-          var currentTime = recalculateCurrentTime();
-          expirationTime = computeInteractiveExpiration(currentTime);
-        } else {
-          // This is an async update
-          var _currentTime = recalculateCurrentTime();
-          expirationTime = computeAsyncExpiration(_currentTime);
-        }
-      } else {
-        // This is a sync update
-        expirationTime = Sync;
-      }
-    }
-    if (isBatchingInteractiveUpdates) {
-      // This is an interactive update. Keep track of the lowest pending
-      // interactive expiration time. This allows us to synchronously flush
-      // all interactive updates when needed.
-      if (
-        lowestPendingInteractiveExpirationTime === NoWork ||
-        expirationTime > lowestPendingInteractiveExpirationTime
-      ) {
-        lowestPendingInteractiveExpirationTime = expirationTime;
-      }
-    }
-    return expirationTime;
-  }
-
-  function scheduleWork(fiber, expirationTime) {
-    return scheduleWorkImpl(fiber, expirationTime, false);
-  }
-
-  function scheduleWorkImpl(fiber, expirationTime, isErrorRecovery) {
-    recordScheduleUpdate();
-
-    {
-      if (!isErrorRecovery && fiber.tag === ClassComponent) {
-        var instance = fiber.stateNode;
-        warnAboutInvalidUpdates(instance);
-      }
-    }
-
-    var node = fiber;
-    while (node !== null) {
-      // Walk the parent path to the root and update each node's
-      // expiration time.
-      if (
-        node.expirationTime === NoWork ||
-        node.expirationTime > expirationTime
-      ) {
-        node.expirationTime = expirationTime;
-      }
-      if (node.alternate !== null) {
-        if (
-          node.alternate.expirationTime === NoWork ||
-          node.alternate.expirationTime > expirationTime
-        ) {
-          node.alternate.expirationTime = expirationTime;
-        }
-      }
-      if (node["return"] === null) {
-        if (node.tag === HostRoot) {
-          var root = node.stateNode;
-          if (
-            !isWorking &&
-            nextRenderExpirationTime !== NoWork &&
-            expirationTime < nextRenderExpirationTime
-          ) {
-            // This is an interruption. (Used for performance tracking.)
-            interruptedBy = fiber;
-            resetStack();
-          }
-          if (
-            // If we're in the render phase, we don't need to schedule this root
-            // for an update, because we'll do it before we exit...
-            !isWorking ||
-            isCommitting ||
-            // ...unless this is a different root than the one we're rendering.
-            nextRoot !== root
-          ) {
-            // Add this root to the root schedule.
-            requestWork(root, expirationTime);
-          }
-          if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
-            invariant(
-              false,
-              "Maximum update depth exceeded. This can happen when a " +
-                "component repeatedly calls setState inside " +
-                "componentWillUpdate or componentDidUpdate. React limits " +
-                "the number of nested updates to prevent infinite loops."
-            );
-          }
-        } else {
-          {
-            if (!isErrorRecovery && fiber.tag === ClassComponent) {
-              warnAboutUpdateOnUnmounted(fiber);
-            }
-          }
-          return;
-        }
-      }
-      node = node["return"];
-    }
-  }
-
-  function recalculateCurrentTime() {
-    // Subtract initial time so it fits inside 32bits
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
-    return mostRecentCurrentTime;
-  }
-
-  function deferredUpdates(fn) {
-    var previousExpirationContext = expirationContext;
-    var currentTime = recalculateCurrentTime();
-    expirationContext = computeAsyncExpiration(currentTime);
-    try {
-      return fn();
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = Sync;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-
-  // TODO: Everything below this is written as if it has been lifted to the
-  // renderers. I'll do this in a follow-up.
-
-  // Linked-list of roots
-  var firstScheduledRoot = null;
-  var lastScheduledRoot = null;
-
-  var callbackExpirationTime = NoWork;
-  var callbackID = -1;
-  var isRendering = false;
-  var nextFlushedRoot = null;
-  var nextFlushedExpirationTime = NoWork;
-  var lowestPendingInteractiveExpirationTime = NoWork;
-  var deadlineDidExpire = false;
-  var hasUnhandledError = false;
-  var unhandledError = null;
-  var deadline = null;
-
-  var isBatchingUpdates = false;
-  var isUnbatchingUpdates = false;
-  var isBatchingInteractiveUpdates = false;
-
-  var completedBatches = null;
-
-  // Use these to prevent an infinite loop of nested updates
-  var NESTED_UPDATE_LIMIT = 1000;
-  var nestedUpdateCount = 0;
-
-  var timeHeuristicForUnitOfWork = 1;
-
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (callbackExpirationTime !== NoWork) {
-      // A callback is already scheduled. Check its expiration time (timeout).
-      if (expirationTime > callbackExpirationTime) {
-        // Existing callback has sufficient timeout. Exit.
-        return;
-      } else {
-        // Existing callback has insufficient timeout. Cancel and schedule a
-        // new one.
-        cancelDeferredCallback(callbackID);
-      }
-      // The request callback timer is already running. Don't start a new one.
-    } else {
-      startRequestCallbackTimer();
-    }
-
-    // Compute a timeout for the given expiration time.
-    var currentMs = now() - originalStartTimeMs;
-    var expirationMs = expirationTimeToMs(expirationTime);
-    var timeout = expirationMs - currentMs;
-
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: timeout
-    });
-  }
-
-  // requestWork is called by the scheduler whenever a root receives an update.
-  // It's up to the renderer to call renderRoot at some point in the future.
-  function requestWork(root, expirationTime) {
-    addRootToSchedule(root, expirationTime);
-
-    if (isRendering) {
-      // Prevent reentrancy. Remaining work will be scheduled at the end of
-      // the currently rendering batch.
-      return;
-    }
-
-    if (isBatchingUpdates) {
-      // Flush work at the end of the batch.
-      if (isUnbatchingUpdates) {
-        // ...unless we're inside unbatchedUpdates, in which case we should
-        // flush it now.
-        nextFlushedRoot = root;
-        nextFlushedExpirationTime = Sync;
-        performWorkOnRoot(root, Sync, false);
-      }
-      return;
-    }
-
-    // TODO: Get rid of Sync and use current time?
-    if (expirationTime === Sync) {
-      performSyncWork();
-    } else {
-      scheduleCallbackWithExpiration(expirationTime);
-    }
-  }
-
-  function addRootToSchedule(root, expirationTime) {
-    // Add the root to the schedule.
-    // Check if this root is already part of the schedule.
-    if (root.nextScheduledRoot === null) {
-      // This root is not already scheduled. Add it.
-      root.remainingExpirationTime = expirationTime;
-      if (lastScheduledRoot === null) {
-        firstScheduledRoot = lastScheduledRoot = root;
-        root.nextScheduledRoot = root;
-      } else {
-        lastScheduledRoot.nextScheduledRoot = root;
-        lastScheduledRoot = root;
-        lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-      }
-    } else {
-      // This root is already scheduled, but its priority may have increased.
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        remainingExpirationTime === NoWork ||
-        expirationTime < remainingExpirationTime
-      ) {
-        // Update the priority.
-        root.remainingExpirationTime = expirationTime;
-      }
-    }
-  }
-
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = NoWork;
-    var highestPriorityRoot = null;
-    if (lastScheduledRoot !== null) {
-      var previousScheduledRoot = lastScheduledRoot;
-      var root = firstScheduledRoot;
-      while (root !== null) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (remainingExpirationTime === NoWork) {
-          // This root no longer has work. Remove it from the scheduler.
-
-          // TODO: This check is redudant, but Flow is confused by the branch
-          // below where we set lastScheduledRoot to null, even though we break
-          // from the loop right after.
-          invariant(
-            previousScheduledRoot !== null && lastScheduledRoot !== null,
-            "Should have a previous and last root. This error is likely " +
-              "caused by a bug in React. Please file an issue."
-          );
-          if (root === root.nextScheduledRoot) {
-            // This is the only root in the list.
-            root.nextScheduledRoot = null;
-            firstScheduledRoot = lastScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot) {
-            // This is the first root in the list.
-            var next = root.nextScheduledRoot;
-            firstScheduledRoot = next;
-            lastScheduledRoot.nextScheduledRoot = next;
-            root.nextScheduledRoot = null;
-          } else if (root === lastScheduledRoot) {
-            // This is the last root in the list.
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else {
-            previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
-            root.nextScheduledRoot = null;
-          }
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            highestPriorityWork === NoWork ||
-            remainingExpirationTime < highestPriorityWork
-          ) {
-            // Update the priority, if it's higher
-            highestPriorityWork = remainingExpirationTime;
-            highestPriorityRoot = root;
-          }
-          if (root === lastScheduledRoot) {
-            break;
-          }
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
-        }
-      }
-    }
-
-    // If the next root is the same as the previous root, this is a nested
-    // update. To prevent an infinite loop, increment the nested update count.
-    var previousFlushedRoot = nextFlushedRoot;
-    if (
-      previousFlushedRoot !== null &&
-      previousFlushedRoot === highestPriorityRoot &&
-      highestPriorityWork === Sync
-    ) {
-      nestedUpdateCount++;
-    } else {
-      // Reset whenever we switch roots.
-      nestedUpdateCount = 0;
-    }
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
-  }
-
-  function performAsyncWork(dl) {
-    performWork(NoWork, true, dl);
-  }
-
-  function performSyncWork() {
-    performWork(Sync, false, null);
-  }
-
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
-
-    // Keep working on roots until there's no more work, or until the we reach
-    // the deadline.
-    findHighestPriorityRoot();
-
-    if (enableUserTimingAPI && deadline !== null) {
-      var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
-      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
-      stopRequestCallbackTimer(didExpire, timeout);
-    }
-
-    if (isAsync) {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime)
-      ) {
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        );
-        findHighestPriorityRoot();
-      }
-    } else {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime)
-      ) {
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
-        findHighestPriorityRoot();
-      }
-    }
-
-    // We're done flushing work. Either we ran out of time in this callback,
-    // or there's no more work left with sufficient priority.
-
-    // If we're inside a callback, set this to false since we just completed it.
-    if (deadline !== null) {
-      callbackExpirationTime = NoWork;
-      callbackID = -1;
-    }
-    // If there's work left over, schedule a new callback.
-    if (nextFlushedExpirationTime !== NoWork) {
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
-    }
-
-    // Clean-up.
-    deadline = null;
-    deadlineDidExpire = false;
-
-    finishRendering();
-  }
-
-  function flushRoot(root, expirationTime) {
-    invariant(
-      !isRendering,
-      "work.commit(): Cannot commit while already rendering. This likely " +
-        "means you attempted to commit from inside a lifecycle method."
-    );
-    // Perform work on root as if the given expiration time is the current time.
-    // This has the effect of synchronously flushing all work up to and
-    // including the given time.
-    nextFlushedRoot = root;
-    nextFlushedExpirationTime = expirationTime;
-    performWorkOnRoot(root, expirationTime, false);
-    // Flush any sync work that was scheduled by lifecycles
-    performSyncWork();
-    finishRendering();
-  }
-
-  function finishRendering() {
-    nestedUpdateCount = 0;
-
-    if (completedBatches !== null) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          if (!hasUnhandledError) {
-            hasUnhandledError = true;
-            unhandledError = error;
-          }
-        }
-      }
-    }
-
-    if (hasUnhandledError) {
-      var error = unhandledError;
-      unhandledError = null;
-      hasUnhandledError = false;
-      throw error;
-    }
-  }
-
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
-    );
-
-    isRendering = true;
-
-    // Check if this is async work or sync/expired work.
-    if (!isAsync) {
-      // Flush sync work.
-      var finishedWork = root.finishedWork;
-      if (finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot(root, finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        finishedWork = renderRoot(root, expirationTime, false);
-        if (finishedWork !== null) {
-          // We've completed the root. Commit it.
-          completeRoot(root, finishedWork, expirationTime);
-        }
-      }
-    } else {
-      // Flush async work.
-      var _finishedWork = root.finishedWork;
-      if (_finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot(root, _finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        _finishedWork = renderRoot(root, expirationTime, true);
-        if (_finishedWork !== null) {
-          // We've completed the root. Check the deadline one more time
-          // before committing.
-          if (!shouldYield()) {
-            // Still time left. Commit the root.
-            completeRoot(root, _finishedWork, expirationTime);
-          } else {
-            // There's no time left. Mark this root as complete. We'll come
-            // back and commit it later.
-            root.finishedWork = _finishedWork;
-          }
-        }
-      }
-    }
-
-    isRendering = false;
-  }
-
-  function completeRoot(root, finishedWork, expirationTime) {
-    // Check if there's a batch that matches this expiration time.
-    var firstBatch = root.firstBatch;
-    if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
-      if (completedBatches === null) {
-        completedBatches = [firstBatch];
-      } else {
-        completedBatches.push(firstBatch);
-      }
-      if (firstBatch._defer) {
-        // This root is blocked from committing by a batch. Unschedule it until
-        // we receive another update.
-        root.finishedWork = finishedWork;
-        root.remainingExpirationTime = NoWork;
-        return;
-      }
-    }
-
-    // Commit the root.
-    root.finishedWork = null;
-    root.remainingExpirationTime = commitRoot(finishedWork);
-  }
-
-  // When working on async work, the reconciler asks the renderer if it should
-  // yield execution. For DOM, we implement this with requestIdleCallback.
-  function shouldYield() {
-    if (deadline === null) {
-      return false;
-    }
-    if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
-      // Disregard deadline.didTimeout. Only expired work should be flushed
-      // during a timeout. This path is only hit for non-expired work.
-      return false;
-    }
-    deadlineDidExpire = true;
-    return true;
-  }
-
-  function onUncaughtError(error) {
-    invariant(
-      nextFlushedRoot !== null,
-      "Should be working on a root. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-    // Unschedule this root so we don't work on it again until there's
-    // another update.
-    nextFlushedRoot.remainingExpirationTime = NoWork;
-    if (!hasUnhandledError) {
-      hasUnhandledError = true;
-      unhandledError = error;
-    }
-  }
-
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function batchedUpdates(fn, a) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return fn(a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
-      }
-    }
-  }
-
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function unbatchedUpdates(fn, a) {
-    if (isBatchingUpdates && !isUnbatchingUpdates) {
-      isUnbatchingUpdates = true;
-      try {
-        return fn(a);
-      } finally {
-        isUnbatchingUpdates = false;
-      }
-    }
-    return fn(a);
-  }
-
-  // TODO: Batching should be implemented at the renderer level, not within
-  // the reconciler.
-  function flushSync(fn, a) {
-    invariant(
-      !isRendering,
-      "flushSync was called from inside a lifecycle method. It cannot be " +
-        "called when React is already rendering."
-    );
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return syncUpdates(fn, a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      performSyncWork();
-    }
-  }
-
-  function interactiveUpdates(fn, a, b) {
-    if (isBatchingInteractiveUpdates) {
-      return fn(a, b);
-    }
-    // If there are any pending interactive updates, synchronously flush them.
-    // This needs to happen before we read any handlers, because the effect of
-    // the previous event may influence which handlers are called during
-    // this event.
-    if (
-      !isBatchingUpdates &&
-      !isRendering &&
-      lowestPendingInteractiveExpirationTime !== NoWork
-    ) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
-    }
-    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingInteractiveUpdates = true;
-    isBatchingUpdates = true;
-    try {
-      return fn(a, b);
-    } finally {
-      isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
-      }
-    }
-  }
-
-  function flushInteractiveUpdates() {
-    if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
-    }
-  }
-
-  function flushControlled(fn) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      syncUpdates(fn);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performWork(Sync, false, null);
-      }
-    }
-  }
-
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: flushRoot,
-    batchedUpdates: batchedUpdates,
-    unbatchedUpdates: unbatchedUpdates,
-    flushSync: flushSync,
-    flushControlled: flushControlled,
-    deferredUpdates: deferredUpdates,
-    syncUpdates: syncUpdates,
-    interactiveUpdates: interactiveUpdates,
-    flushInteractiveUpdates: flushInteractiveUpdates,
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-    legacyContext: legacyContext
-  };
-};
-
-var didWarnAboutNestedUpdates = void 0;
-
-{
-  didWarnAboutNestedUpdates = false;
-}
-
-// 0 is PROD, 1 is DEV.
-// Might add PROFILE later.
-
-var ReactFiberReconciler$1 = function(config) {
-  var getPublicInstance = config.getPublicInstance;
-
-  var _ReactFiberScheduler = ReactFiberScheduler(config),
-    computeUniqueAsyncExpiration =
-      _ReactFiberScheduler.computeUniqueAsyncExpiration,
-    recalculateCurrentTime = _ReactFiberScheduler.recalculateCurrentTime,
-    computeExpirationForFiber = _ReactFiberScheduler.computeExpirationForFiber,
-    scheduleWork = _ReactFiberScheduler.scheduleWork,
-    requestWork = _ReactFiberScheduler.requestWork,
-    flushRoot = _ReactFiberScheduler.flushRoot,
-    batchedUpdates = _ReactFiberScheduler.batchedUpdates,
-    unbatchedUpdates = _ReactFiberScheduler.unbatchedUpdates,
-    flushSync = _ReactFiberScheduler.flushSync,
-    flushControlled = _ReactFiberScheduler.flushControlled,
-    deferredUpdates = _ReactFiberScheduler.deferredUpdates,
-    syncUpdates = _ReactFiberScheduler.syncUpdates,
-    interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
-    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
-    legacyContext = _ReactFiberScheduler.legacyContext;
-
-  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
-
-  function getContextForSubtree(parentComponent) {
-    if (!parentComponent) {
-      return emptyObject;
-    }
-
-    var fiber = get$1(parentComponent);
-    var parentContext = findCurrentUnmaskedContext(fiber);
-    return isContextProvider(fiber)
-      ? processChildContext(fiber, parentContext)
-      : parentContext;
-  }
-
-  function scheduleRootUpdate(
-    current,
-    element,
-    currentTime,
-    expirationTime,
-    callback
-  ) {
-    {
-      if (
-        ReactDebugCurrentFiber.phase === "render" &&
-        ReactDebugCurrentFiber.current !== null &&
-        !didWarnAboutNestedUpdates
-      ) {
-        didWarnAboutNestedUpdates = true;
-        warning(
-          false,
-          "Render methods should be a pure function of props and state; " +
-            "triggering nested component updates from render is not allowed. " +
-            "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
-            "Check the render method of %s.",
-          getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
-        );
-      }
-    }
-
-    callback = callback === undefined ? null : callback;
-    {
-      !(callback === null || typeof callback === "function")
-        ? warning(
-            false,
-            "render(...): Expected the last optional `callback` argument to be a " +
-              "function. Instead received: %s.",
-            callback
-          )
-        : void 0;
-    }
-
-    var update = {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: callback,
-      isReplace: false,
-      isForced: false,
-      capturedValue: null,
-      next: null
-    };
-    insertUpdateIntoFiber(current, update);
-    scheduleWork(current, expirationTime);
-
-    return expirationTime;
-  }
-
-  function updateContainerAtExpirationTime(
-    element,
-    container,
-    parentComponent,
-    currentTime,
-    expirationTime,
-    callback
-  ) {
-    // TODO: If this is a nested container, this won't be the root.
-    var current = container.current;
-
-    {
-      if (ReactFiberInstrumentation_1.debugTool) {
-        if (current.alternate === null) {
-          ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
-        } else if (element === null) {
-          ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
-        } else {
-          ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
-        }
-      }
-    }
-
-    var context = getContextForSubtree(parentComponent);
-    if (container.context === null) {
-      container.context = context;
-    } else {
-      container.pendingContext = context;
-    }
-
-    return scheduleRootUpdate(
-      current,
-      element,
-      currentTime,
-      expirationTime,
-      callback
-    );
-  }
-
-  function findHostInstance(component) {
-    var fiber = get$1(component);
-    if (fiber === undefined) {
-      if (typeof component.render === "function") {
-        invariant(false, "Unable to find node on an unmounted component.");
-      } else {
-        invariant(
-          false,
-          "Argument appears to not be a ReactComponent. Keys: %s",
-          Object.keys(component)
-        );
-      }
-    }
-    var hostFiber = findCurrentHostFiber(fiber);
-    if (hostFiber === null) {
-      return null;
-    }
-    return hostFiber.stateNode;
-  }
-
-  return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      return createFiberRoot(containerInfo, isAsync, hydrate);
-    },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current;
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        expirationTime,
-        callback
-      );
-    },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
-    ) {
-      var currentTime = recalculateCurrentTime();
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        expirationTime,
-        callback
-      );
-    },
-
-    flushRoot: flushRoot,
-
-    requestWork: requestWork,
-
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-
-    batchedUpdates: batchedUpdates,
-
-    unbatchedUpdates: unbatchedUpdates,
-
-    deferredUpdates: deferredUpdates,
-
-    syncUpdates: syncUpdates,
-
-    interactiveUpdates: interactiveUpdates,
-
-    flushInteractiveUpdates: flushInteractiveUpdates,
-
-    flushControlled: flushControlled,
-
-    flushSync: flushSync,
-
-    getPublicRootInstance: function(container) {
-      var containerFiber = container.current;
-      if (!containerFiber.child) {
-        return null;
-      }
-      switch (containerFiber.child.tag) {
-        case HostComponent:
-          return getPublicInstance(containerFiber.child.stateNode);
-        default:
-          return containerFiber.child.stateNode;
-      }
-    },
-
-    findHostInstance: findHostInstance,
-
-    findHostInstanceWithNoPortals: function(fiber) {
-      var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
-      if (hostFiber === null) {
-        return null;
-      }
-      return hostFiber.stateNode;
-    },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            var hostFiber = findCurrentHostFiber(fiber);
-            if (hostFiber === null) {
-              return null;
-            }
-            return hostFiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            if (!findFiberByHostInstance) {
-              // Might not be implemented by the renderer.
-              return null;
-            }
-            return findFiberByHostInstance(instance);
-          }
-        })
-      );
-    }
-  };
-};
-
-var ReactFiberReconciler$2 = Object.freeze({
-  default: ReactFiberReconciler$1
-});
-
-var ReactFiberReconciler$3 =
-  (ReactFiberReconciler$2 && ReactFiberReconciler$1) || ReactFiberReconciler$2;
-
-// TODO: bundle Flow types with the package.
-
-// TODO: decide on the top-level export form.
-// This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3["default"]
-  ? ReactFiberReconciler$3["default"]
-  : ReactFiberReconciler$3;
-
-function _classCallCheck$1(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
-  }
-}
-
-// Modules provided by RN:
-/**
- * This component defines the same methods as NativeMethodsMixin but without the
- * findNodeHandle wrapper. This wrapper is unnecessary for HostComponent views
- * and would also result in a circular require.js dependency (since
- * ReactNativeFiber depends on this component and NativeMethodsMixin depends on
- * ReactNativeFiber).
- */
-
-var ReactNativeFiberHostComponent = (function() {
-  function ReactNativeFiberHostComponent(tag, viewConfig) {
-    _classCallCheck$1(this, ReactNativeFiberHostComponent);
-
-    this._nativeTag = tag;
-    this._children = [];
-    this.viewConfig = viewConfig;
-  }
-
-  ReactNativeFiberHostComponent.prototype.blur = function blur() {
-    TextInputState.blurTextInput(this._nativeTag);
-  };
-
-  ReactNativeFiberHostComponent.prototype.focus = function focus() {
-    TextInputState.focusTextInput(this._nativeTag);
-  };
-
-  ReactNativeFiberHostComponent.prototype.measure = function measure(callback) {
-    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-  };
-
-  ReactNativeFiberHostComponent.prototype.measureInWindow = function measureInWindow(
-    callback
-  ) {
-    UIManager.measureInWindow(
-      this._nativeTag,
-      mountSafeCallback(this, callback)
-    );
-  };
-
-  ReactNativeFiberHostComponent.prototype.measureLayout = function measureLayout(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      this._nativeTag,
-      relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  };
-
-  ReactNativeFiberHostComponent.prototype.setNativeProps = function setNativeProps(
-    nativeProps
-  ) {
-    {
-      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
-    }
-
-    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
-
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        this._nativeTag,
-        this.viewConfig.uiViewClassName,
-        updatePayload
-      );
-    }
-  };
-
-  return ReactNativeFiberHostComponent;
-})();
-
-var hasNativePerformanceNow =
-  typeof performance === "object" && typeof performance.now === "function";
-
-var now = hasNativePerformanceNow
-  ? function() {
-      return performance.now();
-    }
-  : function() {
-      return Date.now();
-    };
-
-var scheduledCallback = null;
-var frameDeadline = 0;
-
-var frameDeadlineObject = {
-  timeRemaining: function() {
-    return frameDeadline - now();
-  },
-  didTimeout: false
-};
-
-function setTimeoutCallback() {
-  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
-  // React API probably changing to boolean rather than time remaining.
-  // Longer-term plan is to rewrite this using shared memory,
-  // And just return the value of the bit as the boolean.
-  frameDeadline = now() + 5;
-
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  if (callback !== null) {
-    callback(frameDeadlineObject);
-  }
-}
-
-// RN has a poor polyfill for requestIdleCallback so we aren't using it.
-// This implementation is only intended for short-term use anyway.
-// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
-function scheduleDeferredCallback(callback) {
-  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
-  scheduledCallback = callback;
-  return setTimeout(setTimeoutCallback, 1);
-}
-
-function cancelDeferredCallback(callbackID) {
-  scheduledCallback = null;
-  clearTimeout(callbackID);
-}
-
-// Modules provided by RN:
-// Counter for uniquely identifying views.
-// % 10 === 1 means it is a rootTag.
-// % 2 === 0 means it is a Fabric tag.
-var nextReactTag = 3;
-function allocateTag() {
-  var tag = nextReactTag;
-  if (tag % 10 === 1) {
-    tag += 2;
-  }
-  nextReactTag = tag + 2;
-  return tag;
-}
-
-function recursivelyUncacheFiberNode(node) {
-  if (typeof node === "number") {
-    // Leaf node (eg text)
-    uncacheFiberNode(node);
-  } else {
-    uncacheFiberNode(node._nativeTag);
-
-    node._children.forEach(recursivelyUncacheFiberNode);
-  }
-}
-
-var NativeRenderer = reactReconciler({
-  appendInitialChild: function(parentInstance, child) {
-    parentInstance._children.push(child);
-  },
-  createInstance: function(
-    type,
-    props,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    var tag = allocateTag();
-    var viewConfig = ReactNativeViewConfigRegistry.get(type);
-
-    {
-      for (var key in viewConfig.validAttributes) {
-        if (props.hasOwnProperty(key)) {
-          deepFreezeAndThrowOnMutationInDev(props[key]);
-        }
-      }
-    }
-
-    var updatePayload = create(props, viewConfig.validAttributes);
-
-    UIManager.createView(
-      tag, // reactTag
-      viewConfig.uiViewClassName, // viewName
-      rootContainerInstance, // rootTag
-      updatePayload
-    );
-
-    var component = new ReactNativeFiberHostComponent(tag, viewConfig);
-
-    precacheFiberNode(internalInstanceHandle, tag);
-    updateFiberProps(tag, props);
-
-    // Not sure how to avoid this cast. Flow is okay if the component is defined
-    // in the same file but if it's external it can't see the types.
-    return component;
-  },
-  createTextInstance: function(
-    text,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    var tag = allocateTag();
-
-    UIManager.createView(
-      tag, // reactTag
-      "RCTRawText", // viewName
-      rootContainerInstance, // rootTag
-      { text: text }
-    );
-
-    precacheFiberNode(internalInstanceHandle, tag);
-
-    return tag;
-  },
-  finalizeInitialChildren: function(
-    parentInstance,
-    type,
-    props,
-    rootContainerInstance
-  ) {
-    // Don't send a no-op message over the bridge.
-    if (parentInstance._children.length === 0) {
-      return false;
-    }
-
-    // Map from child objects to native tags.
-    // Either way we need to pass a copy of the Array to prevent it from being frozen.
-    var nativeTags = parentInstance._children.map(function(child) {
-      return typeof child === "number"
-        ? child // Leaf node (eg text)
-        : child._nativeTag;
-    });
-
-    UIManager.setChildren(
-      parentInstance._nativeTag, // containerTag
-      nativeTags
-    );
-
-    return false;
-  },
-  getRootHostContext: function() {
-    return emptyObject;
-  },
-  getChildHostContext: function() {
-    return emptyObject;
-  },
-  getPublicInstance: function(instance) {
-    return instance;
-  },
-
-  now: now,
-
-  prepareForCommit: function() {
-    // Noop
-  },
-  prepareUpdate: function(
-    instance,
-    type,
-    oldProps,
-    newProps,
-    rootContainerInstance,
-    hostContext
-  ) {
-    return emptyObject;
-  },
-  resetAfterCommit: function() {
-    // Noop
-  },
-
-  scheduleDeferredCallback: scheduleDeferredCallback,
-  cancelDeferredCallback: cancelDeferredCallback,
-
-  shouldDeprioritizeSubtree: function(type, props) {
-    return false;
-  },
-  shouldSetTextContent: function(type, props) {
-    // TODO (bvaughn) Revisit this decision.
-    // Always returning false simplifies the createInstance() implementation,
-    // But creates an additional child Fiber for raw text children.
-    // No additional native views are created though.
-    // It's not clear to me which is better so I'm deferring for now.
-    // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
-    return false;
-  },
-
-  mutation: {
-    appendChild: function(parentInstance, child) {
-      var childTag = typeof child === "number" ? child : child._nativeTag;
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
-
-      if (index >= 0) {
-        children.splice(index, 1);
-        children.push(child);
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerTag
-          [index], // moveFromIndices
-          [children.length - 1], // moveToIndices
-          [], // addChildReactTags
-          [], // addAtIndices
-          []
-        );
-      } else {
-        children.push(child);
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerTag
-          [], // moveFromIndices
-          [], // moveToIndices
-          [childTag], // addChildReactTags
-          [children.length - 1], // addAtIndices
-          []
-        );
-      }
-    },
-    appendChildToContainer: function(parentInstance, child) {
-      var childTag = typeof child === "number" ? child : child._nativeTag;
-      UIManager.setChildren(
-        parentInstance, // containerTag
-        [childTag]
-      );
-    },
-    commitTextUpdate: function(textInstance, oldText, newText) {
-      UIManager.updateView(
-        textInstance, // reactTag
-        "RCTRawText", // viewName
-        { text: newText }
-      );
-    },
-    commitMount: function(instance, type, newProps, internalInstanceHandle) {
-      // Noop
-    },
-    commitUpdate: function(
-      instance,
-      updatePayloadTODO,
-      type,
-      oldProps,
-      newProps,
-      internalInstanceHandle
-    ) {
-      var viewConfig = instance.viewConfig;
-
-      updateFiberProps(instance._nativeTag, newProps);
-
-      var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
-
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          instance._nativeTag, // reactTag
-          viewConfig.uiViewClassName, // viewName
-          updatePayload
-        );
-      }
-    },
-    insertBefore: function(parentInstance, child, beforeChild) {
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
-
-      // Move existing child or add new child?
-      if (index >= 0) {
-        children.splice(index, 1);
-        var beforeChildIndex = children.indexOf(beforeChild);
-        children.splice(beforeChildIndex, 0, child);
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerID
-          [index], // moveFromIndices
-          [beforeChildIndex], // moveToIndices
-          [], // addChildReactTags
-          [], // addAtIndices
-          []
-        );
-      } else {
-        var _beforeChildIndex = children.indexOf(beforeChild);
-        children.splice(_beforeChildIndex, 0, child);
-
-        var childTag = typeof child === "number" ? child : child._nativeTag;
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerID
-          [], // moveFromIndices
-          [], // moveToIndices
-          [childTag], // addChildReactTags
-          [_beforeChildIndex], // addAtIndices
-          []
-        );
-      }
-    },
-    insertInContainerBefore: function(parentInstance, child, beforeChild) {
-      // TODO (bvaughn): Remove this check when...
-      // We create a wrapper object for the container in ReactNative render()
-      // Or we refactor to remove wrapper objects entirely.
-      // For more info on pros/cons see PR #8560 description.
-      invariant(
-        typeof parentInstance !== "number",
-        "Container does not support insertBefore operation"
-      );
-    },
-    removeChild: function(parentInstance, child) {
-      recursivelyUncacheFiberNode(child);
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
-
-      children.splice(index, 1);
-
-      UIManager.manageChildren(
-        parentInstance._nativeTag, // containerID
-        [], // moveFromIndices
-        [], // moveToIndices
-        [], // addChildReactTags
-        [], // addAtIndices
-        [index]
-      );
-    },
-    removeChildFromContainer: function(parentInstance, child) {
-      recursivelyUncacheFiberNode(child);
-      UIManager.manageChildren(
-        parentInstance, // containerID
-        [], // moveFromIndices
-        [], // moveToIndices
-        [], // addChildReactTags
-        [], // addAtIndices
-        [0]
-      );
-    },
-    resetTextContent: function(instance) {
-      // Noop
-    }
-  }
-});
-
-// Module provided by RN:
-var getInspectorDataForViewTag = void 0;
-
-{
-  var traverseOwnerTreeUp = function(hierarchy, instance) {
-    if (instance) {
-      hierarchy.unshift(instance);
-      traverseOwnerTreeUp(hierarchy, instance._debugOwner);
-    }
-  };
-
-  var getOwnerHierarchy = function(instance) {
-    var hierarchy = [];
-    traverseOwnerTreeUp(hierarchy, instance);
-    return hierarchy;
-  };
-
-  var lastNonHostInstance = function(hierarchy) {
-    for (var i = hierarchy.length - 1; i > 1; i--) {
-      var instance = hierarchy[i];
-
-      if (instance.tag !== HostComponent) {
-        return instance;
-      }
-    }
-    return hierarchy[0];
-  };
-
-  var getHostProps = function(fiber) {
-    var host = findCurrentHostFiber(fiber);
-    if (host) {
-      return host.memoizedProps || emptyObject;
-    }
-    return emptyObject;
-  };
-
-  var getHostNode = function(fiber, findNodeHandle) {
-    var hostNode = void 0;
-    // look for children first for the hostNode
-    // as composite fibers do not have a hostNode
-    while (fiber) {
-      if (fiber.stateNode !== null && fiber.tag === HostComponent) {
-        hostNode = findNodeHandle(fiber.stateNode);
-      }
-      if (hostNode) {
-        return hostNode;
-      }
-      fiber = fiber.child;
-    }
-    return null;
-  };
-
-  var createHierarchy = function(fiberHierarchy) {
-    return fiberHierarchy.map(function(fiber) {
-      return {
-        name: getComponentName(fiber),
-        getInspectorData: function(findNodeHandle) {
-          return {
-            measure: function(callback) {
-              return UIManager.measure(
-                getHostNode(fiber, findNodeHandle),
-                callback
-              );
-            },
-            props: getHostProps(fiber),
-            source: fiber._debugSource
-          };
-        }
-      };
-    });
-  };
-
-  getInspectorDataForViewTag = function(viewTag) {
-    var closestInstance = getInstanceFromTag(viewTag);
-
-    // Handle case where user clicks outside of ReactNative
-    if (!closestInstance) {
-      return {
-        hierarchy: [],
-        props: emptyObject,
-        selection: null,
-        source: null
-      };
-    }
-
-    var fiber = findCurrentFiberUsingSlowPath(closestInstance);
-    var fiberHierarchy = getOwnerHierarchy(fiber);
-    var instance = lastNonHostInstance(fiberHierarchy);
-    var hierarchy = createHierarchy(fiberHierarchy);
-    var props = getHostProps(instance);
-    var source = instance._debugSource;
-    var selection = fiberHierarchy.indexOf(instance);
-
-    return {
-      hierarchy: hierarchy,
-      props: props,
-      selection: selection,
-      source: source
-    };
-  };
-}
-
-// Module provided by RN:
-var findHostInstance = NativeRenderer.findHostInstance;
-
-function findNodeHandle(componentOrHandle) {
-  {
-    var owner = ReactCurrentOwner.current;
-    if (owner !== null && owner.stateNode !== null) {
-      !owner.stateNode._warnedAboutRefsInRender
-        ? warning(
-            false,
-            "%s is accessing findNodeHandle inside its render(). " +
-              "render() should be a pure function of props and state. It should " +
-              "never access something that requires stale data from the previous " +
-              "render, such as refs. Move this logic to componentDidMount and " +
-              "componentDidUpdate instead.",
-            getComponentName(owner) || "A component"
-          )
-        : void 0;
-
-      owner.stateNode._warnedAboutRefsInRender = true;
-    }
-  }
-  if (componentOrHandle == null) {
-    return null;
-  }
-  if (typeof componentOrHandle === "number") {
-    // Already a node handle
-    return componentOrHandle;
-  }
-  if (componentOrHandle._nativeTag) {
-    return componentOrHandle._nativeTag;
-  }
-  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag) {
-    return componentOrHandle.canonical._nativeTag;
-  }
-  var hostInstance = findHostInstance(componentOrHandle);
-  if (hostInstance == null) {
-    return hostInstance;
-  }
-  if (hostInstance.canonical) {
-    // Fabric
-    return hostInstance.canonical._nativeTag;
-  }
-  return hostInstance._nativeTag;
-}
-
-injection$2.injectRenderer(NativeRenderer);
-
-function computeComponentStackForErrorReporting(reactTag) {
-  var fiber = getInstanceFromTag(reactTag);
-  if (!fiber) {
-    return "";
-  }
-  return getStackAddendumByWorkInProgressFiber(fiber);
-}
-
-var roots = new Map();
-
-var ReactNativeRenderer = {
-  NativeComponent: ReactNativeComponent(findNodeHandle, findHostInstance),
-
-  findNodeHandle: findNodeHandle,
-
-  render: function(element, containerTag, callback) {
-    var root = roots.get(containerTag);
-
-    if (!root) {
-      // TODO (bvaughn): If we decide to keep the wrapper component,
-      // We could create a wrapper for containerTag as well to reduce special casing.
-      root = NativeRenderer.createContainer(containerTag, false, false);
-      roots.set(containerTag, root);
-    }
-    NativeRenderer.updateContainer(element, root, null, callback);
-
-    return NativeRenderer.getPublicRootInstance(root);
-  },
-  unmountComponentAtNode: function(containerTag) {
-    var root = roots.get(containerTag);
-    if (root) {
-      // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
-      NativeRenderer.updateContainer(null, root, null, function() {
-        roots["delete"](containerTag);
-      });
-    }
-  },
-  unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
-    ReactNativeRenderer.unmountComponentAtNode(containerTag);
-
-    // Call back into native to remove all of the subviews from this container
-    UIManager.removeRootView(containerTag);
-  },
-  createPortal: function(children, containerTag) {
-    var key =
-      arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : null;
-
-    return createPortal(children, containerTag, null, key);
-  },
-
-  unstable_batchedUpdates: batchedUpdates,
-
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
-    // Used as a mixin in many createClass-based components
-    NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
-    // Used by react-native-github/Libraries/ components
-    ReactNativeComponentTree: ReactNativeComponentTree, // ScrollResponder
-    computeComponentStackForErrorReporting: computeComponentStackForErrorReporting
-  }
-};
-
-{
-  // $FlowFixMe
-  Object.assign(
-    ReactNativeRenderer.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-    {
-      // TODO: none of these work since Fiber. Remove these dependencies.
-      // Used by RCTRenderingPerf, Systrace:
-      ReactDebugTool: {
-        addHook: function() {},
-        removeHook: function() {}
-      },
-      // Used by ReactPerfStallHandler, RCTRenderingPerf:
-      ReactPerf: {
-        start: function() {},
-        stop: function() {},
-        printInclusive: function() {},
-        printWasted: function() {}
-      }
-    }
-  );
-}
-
-NativeRenderer.injectIntoDevTools({
-  findFiberByHostInstance: getInstanceFromTag,
-  getInspectorDataForViewTag: getInspectorDataForViewTag,
-  bundleType: 1,
-  version: ReactVersion,
-  rendererPackageName: "react-native-renderer"
-});
-
-var ReactNativeRenderer$2 = Object.freeze({
-  default: ReactNativeRenderer
-});
-
-var ReactNativeRenderer$3 =
-  (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
-
-// TODO: decide on the top-level export form.
-// This is hacky but makes it work with both Rollup and Jest.
-var reactNativeRenderer = ReactNativeRenderer$3["default"]
-  ? ReactNativeRenderer$3["default"]
-  : ReactNativeRenderer$3;
-
-module.exports = reactNativeRenderer;
-
-  })();
-}
diff --git a/Libraries/Renderer/fb/ReactNativeRenderer-prod.js b/Libraries/Renderer/fb/ReactNativeRenderer-prod.js
deleted file mode 100644
index 08b70c789b54..000000000000
--- a/Libraries/Renderer/fb/ReactNativeRenderer-prod.js
+++ /dev/null
@@ -1,6395 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @noflow
- * @preventMunge
- */
-
-"use strict";
-require("InitializeCore");
-var invariant = require("fbjs/lib/invariant"),
-  emptyFunction = require("fbjs/lib/emptyFunction"),
-  ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
-  UIManager = require("UIManager"),
-  RCTEventEmitter = require("RCTEventEmitter"),
-  TextInputState = require("TextInputState"),
-  deepDiffer = require("deepDiffer"),
-  flattenStyle = require("flattenStyle"),
-  React = require("react"),
-  emptyObject = require("fbjs/lib/emptyObject"),
-  shallowEqual = require("fbjs/lib/shallowEqual"),
-  ExceptionsManager = require("ExceptionsManager");
-function invokeGuardedCallback(name, func, context, a, b, c, d, e, f) {
-  this._hasCaughtError = !1;
-  this._caughtError = null;
-  var funcArgs = Array.prototype.slice.call(arguments, 3);
-  try {
-    func.apply(context, funcArgs);
-  } catch (error) {
-    (this._caughtError = error), (this._hasCaughtError = !0);
-  }
-}
-var ReactErrorUtils = {
-  _caughtError: null,
-  _hasCaughtError: !1,
-  _rethrowError: null,
-  _hasRethrowError: !1,
-  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
-    invokeGuardedCallback.apply(ReactErrorUtils, arguments);
-  },
-  invokeGuardedCallbackAndCatchFirstError: function(
-    name,
-    func,
-    context,
-    a,
-    b,
-    c,
-    d,
-    e,
-    f
-  ) {
-    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
-    if (ReactErrorUtils.hasCaughtError()) {
-      var error = ReactErrorUtils.clearCaughtError();
-      ReactErrorUtils._hasRethrowError ||
-        ((ReactErrorUtils._hasRethrowError = !0),
-        (ReactErrorUtils._rethrowError = error));
-    }
-  },
-  rethrowCaughtError: function() {
-    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
-  },
-  hasCaughtError: function() {
-    return ReactErrorUtils._hasCaughtError;
-  },
-  clearCaughtError: function() {
-    if (ReactErrorUtils._hasCaughtError) {
-      var error = ReactErrorUtils._caughtError;
-      ReactErrorUtils._caughtError = null;
-      ReactErrorUtils._hasCaughtError = !1;
-      return error;
-    }
-    invariant(
-      !1,
-      "clearCaughtError was called but no error was captured. This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-};
-function rethrowCaughtError() {
-  if (ReactErrorUtils._hasRethrowError) {
-    var error = ReactErrorUtils._rethrowError;
-    ReactErrorUtils._rethrowError = null;
-    ReactErrorUtils._hasRethrowError = !1;
-    throw error;
-  }
-}
-var eventPluginOrder = null,
-  namesToPlugins = {};
-function recomputePluginOrdering() {
-  if (eventPluginOrder)
-    for (var pluginName in namesToPlugins) {
-      var pluginModule = namesToPlugins[pluginName],
-        pluginIndex = eventPluginOrder.indexOf(pluginName);
-      invariant(
-        -1 < pluginIndex,
-        "EventPluginRegistry: Cannot inject event plugins that do not exist in the plugin ordering, `%s`.",
-        pluginName
-      );
-      if (!plugins[pluginIndex]) {
-        invariant(
-          pluginModule.extractEvents,
-          "EventPluginRegistry: Event plugins must implement an `extractEvents` method, but `%s` does not.",
-          pluginName
-        );
-        plugins[pluginIndex] = pluginModule;
-        pluginIndex = pluginModule.eventTypes;
-        for (var eventName in pluginIndex) {
-          var JSCompiler_inline_result = void 0;
-          var dispatchConfig = pluginIndex[eventName],
-            pluginModule$jscomp$0 = pluginModule,
-            eventName$jscomp$0 = eventName;
-          invariant(
-            !eventNameDispatchConfigs.hasOwnProperty(eventName$jscomp$0),
-            "EventPluginHub: More than one plugin attempted to publish the same event name, `%s`.",
-            eventName$jscomp$0
-          );
-          eventNameDispatchConfigs[eventName$jscomp$0] = dispatchConfig;
-          var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
-          if (phasedRegistrationNames) {
-            for (JSCompiler_inline_result in phasedRegistrationNames)
-              phasedRegistrationNames.hasOwnProperty(
-                JSCompiler_inline_result
-              ) &&
-                publishRegistrationName(
-                  phasedRegistrationNames[JSCompiler_inline_result],
-                  pluginModule$jscomp$0,
-                  eventName$jscomp$0
-                );
-            JSCompiler_inline_result = !0;
-          } else
-            dispatchConfig.registrationName
-              ? (publishRegistrationName(
-                  dispatchConfig.registrationName,
-                  pluginModule$jscomp$0,
-                  eventName$jscomp$0
-                ),
-                (JSCompiler_inline_result = !0))
-              : (JSCompiler_inline_result = !1);
-          invariant(
-            JSCompiler_inline_result,
-            "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
-            eventName,
-            pluginName
-          );
-        }
-      }
-    }
-}
-function publishRegistrationName(registrationName, pluginModule) {
-  invariant(
-    !registrationNameModules[registrationName],
-    "EventPluginHub: More than one plugin attempted to publish the same registration name, `%s`.",
-    registrationName
-  );
-  registrationNameModules[registrationName] = pluginModule;
-}
-var plugins = [],
-  eventNameDispatchConfigs = {},
-  registrationNameModules = {},
-  getFiberCurrentPropsFromNode = null,
-  getInstanceFromNode = null,
-  getNodeFromInstance = null;
-function isEndish(topLevelType) {
-  return (
-    "topMouseUp" === topLevelType ||
-    "topTouchEnd" === topLevelType ||
-    "topTouchCancel" === topLevelType
-  );
-}
-function isMoveish(topLevelType) {
-  return "topMouseMove" === topLevelType || "topTouchMove" === topLevelType;
-}
-function isStartish(topLevelType) {
-  return "topMouseDown" === topLevelType || "topTouchStart" === topLevelType;
-}
-function executeDispatch(event, simulated, listener, inst) {
-  simulated = event.type || "unknown-event";
-  event.currentTarget = getNodeFromInstance(inst);
-  ReactErrorUtils.invokeGuardedCallbackAndCatchFirstError(
-    simulated,
-    listener,
-    void 0,
-    event
-  );
-  event.currentTarget = null;
-}
-function executeDirectDispatch(event) {
-  var dispatchListener = event._dispatchListeners,
-    dispatchInstance = event._dispatchInstances;
-  invariant(
-    !Array.isArray(dispatchListener),
-    "executeDirectDispatch(...): Invalid `event`."
-  );
-  event.currentTarget = dispatchListener
-    ? getNodeFromInstance(dispatchInstance)
-    : null;
-  dispatchListener = dispatchListener ? dispatchListener(event) : null;
-  event.currentTarget = null;
-  event._dispatchListeners = null;
-  event._dispatchInstances = null;
-  return dispatchListener;
-}
-function accumulateInto(current, next) {
-  invariant(
-    null != next,
-    "accumulateInto(...): Accumulated items must not be null or undefined."
-  );
-  if (null == current) return next;
-  if (Array.isArray(current)) {
-    if (Array.isArray(next)) return current.push.apply(current, next), current;
-    current.push(next);
-    return current;
-  }
-  return Array.isArray(next) ? [current].concat(next) : [current, next];
-}
-function forEachAccumulated(arr, cb, scope) {
-  Array.isArray(arr) ? arr.forEach(cb, scope) : arr && cb.call(scope, arr);
-}
-var eventQueue = null;
-function executeDispatchesAndReleaseTopLevel(e) {
-  if (e) {
-    var dispatchListeners = e._dispatchListeners,
-      dispatchInstances = e._dispatchInstances;
-    if (Array.isArray(dispatchListeners))
-      for (
-        var i = 0;
-        i < dispatchListeners.length && !e.isPropagationStopped();
-        i++
-      )
-        executeDispatch(e, !1, dispatchListeners[i], dispatchInstances[i]);
-    else
-      dispatchListeners &&
-        executeDispatch(e, !1, dispatchListeners, dispatchInstances);
-    e._dispatchListeners = null;
-    e._dispatchInstances = null;
-    e.isPersistent() || e.constructor.release(e);
-  }
-}
-var injection = {
-  injectEventPluginOrder: function(injectedEventPluginOrder) {
-    invariant(
-      !eventPluginOrder,
-      "EventPluginRegistry: Cannot inject event plugin ordering more than once. You are likely trying to load more than one copy of React."
-    );
-    eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
-    recomputePluginOrdering();
-  },
-  injectEventPluginsByName: function(injectedNamesToPlugins) {
-    var isOrderingDirty = !1,
-      pluginName;
-    for (pluginName in injectedNamesToPlugins)
-      if (injectedNamesToPlugins.hasOwnProperty(pluginName)) {
-        var pluginModule = injectedNamesToPlugins[pluginName];
-        (namesToPlugins.hasOwnProperty(pluginName) &&
-          namesToPlugins[pluginName] === pluginModule) ||
-          (invariant(
-            !namesToPlugins[pluginName],
-            "EventPluginRegistry: Cannot inject two different event plugins using the same name, `%s`.",
-            pluginName
-          ),
-          (namesToPlugins[pluginName] = pluginModule),
-          (isOrderingDirty = !0));
-      }
-    isOrderingDirty && recomputePluginOrdering();
-  }
-};
-function getListener(inst, registrationName) {
-  var listener = inst.stateNode;
-  if (!listener) return null;
-  var props = getFiberCurrentPropsFromNode(listener);
-  if (!props) return null;
-  listener = props[registrationName];
-  a: switch (registrationName) {
-    case "onClick":
-    case "onClickCapture":
-    case "onDoubleClick":
-    case "onDoubleClickCapture":
-    case "onMouseDown":
-    case "onMouseDownCapture":
-    case "onMouseMove":
-    case "onMouseMoveCapture":
-    case "onMouseUp":
-    case "onMouseUpCapture":
-      (props = !props.disabled) ||
-        ((inst = inst.type),
-        (props = !(
-          "button" === inst ||
-          "input" === inst ||
-          "select" === inst ||
-          "textarea" === inst
-        )));
-      inst = !props;
-      break a;
-    default:
-      inst = !1;
-  }
-  if (inst) return null;
-  invariant(
-    !listener || "function" === typeof listener,
-    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
-    registrationName,
-    typeof listener
-  );
-  return listener;
-}
-function getParent(inst) {
-  do inst = inst["return"];
-  while (inst && 5 !== inst.tag);
-  return inst ? inst : null;
-}
-function traverseTwoPhase(inst, fn, arg) {
-  for (var path = []; inst; ) path.push(inst), (inst = getParent(inst));
-  for (inst = path.length; 0 < inst--; ) fn(path[inst], "captured", arg);
-  for (inst = 0; inst < path.length; inst++) fn(path[inst], "bubbled", arg);
-}
-function accumulateDirectionalDispatches(inst, phase, event) {
-  if (
-    (phase = getListener(
-      inst,
-      event.dispatchConfig.phasedRegistrationNames[phase]
-    ))
-  )
-    (event._dispatchListeners = accumulateInto(
-      event._dispatchListeners,
-      phase
-    )),
-      (event._dispatchInstances = accumulateInto(
-        event._dispatchInstances,
-        inst
-      ));
-}
-function accumulateTwoPhaseDispatchesSingle(event) {
-  event &&
-    event.dispatchConfig.phasedRegistrationNames &&
-    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
-}
-function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
-  if (event && event.dispatchConfig.phasedRegistrationNames) {
-    var targetInst = event._targetInst;
-    targetInst = targetInst ? getParent(targetInst) : null;
-    traverseTwoPhase(targetInst, accumulateDirectionalDispatches, event);
-  }
-}
-function accumulateDirectDispatchesSingle(event) {
-  if (event && event.dispatchConfig.registrationName) {
-    var inst = event._targetInst;
-    if (inst && event && event.dispatchConfig.registrationName) {
-      var listener = getListener(inst, event.dispatchConfig.registrationName);
-      listener &&
-        ((event._dispatchListeners = accumulateInto(
-          event._dispatchListeners,
-          listener
-        )),
-        (event._dispatchInstances = accumulateInto(
-          event._dispatchInstances,
-          inst
-        )));
-    }
-  }
-}
-var shouldBeReleasedProperties = "dispatchConfig _targetInst nativeEvent isDefaultPrevented isPropagationStopped _dispatchListeners _dispatchInstances".split(
-    " "
-  ),
-  EventInterface = {
-    type: null,
-    target: null,
-    currentTarget: emptyFunction.thatReturnsNull,
-    eventPhase: null,
-    bubbles: null,
-    cancelable: null,
-    timeStamp: function(event) {
-      return event.timeStamp || Date.now();
-    },
-    defaultPrevented: null,
-    isTrusted: null
-  };
-function SyntheticEvent(
-  dispatchConfig,
-  targetInst,
-  nativeEvent,
-  nativeEventTarget
-) {
-  this.dispatchConfig = dispatchConfig;
-  this._targetInst = targetInst;
-  this.nativeEvent = nativeEvent;
-  dispatchConfig = this.constructor.Interface;
-  for (var propName in dispatchConfig)
-    dispatchConfig.hasOwnProperty(propName) &&
-      ((targetInst = dispatchConfig[propName])
-        ? (this[propName] = targetInst(nativeEvent))
-        : "target" === propName
-          ? (this.target = nativeEventTarget)
-          : (this[propName] = nativeEvent[propName]));
-  this.isDefaultPrevented = (null != nativeEvent.defaultPrevented
-  ? nativeEvent.defaultPrevented
-  : !1 === nativeEvent.returnValue)
-    ? emptyFunction.thatReturnsTrue
-    : emptyFunction.thatReturnsFalse;
-  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
-  return this;
-}
-Object.assign(SyntheticEvent.prototype, {
-  preventDefault: function() {
-    this.defaultPrevented = !0;
-    var event = this.nativeEvent;
-    event &&
-      (event.preventDefault
-        ? event.preventDefault()
-        : "unknown" !== typeof event.returnValue && (event.returnValue = !1),
-      (this.isDefaultPrevented = emptyFunction.thatReturnsTrue));
-  },
-  stopPropagation: function() {
-    var event = this.nativeEvent;
-    event &&
-      (event.stopPropagation
-        ? event.stopPropagation()
-        : "unknown" !== typeof event.cancelBubble && (event.cancelBubble = !0),
-      (this.isPropagationStopped = emptyFunction.thatReturnsTrue));
-  },
-  persist: function() {
-    this.isPersistent = emptyFunction.thatReturnsTrue;
-  },
-  isPersistent: emptyFunction.thatReturnsFalse,
-  destructor: function() {
-    var Interface = this.constructor.Interface,
-      propName;
-    for (propName in Interface) this[propName] = null;
-    for (
-      Interface = 0;
-      Interface < shouldBeReleasedProperties.length;
-      Interface++
-    )
-      this[shouldBeReleasedProperties[Interface]] = null;
-  }
-});
-SyntheticEvent.Interface = EventInterface;
-SyntheticEvent.extend = function(Interface) {
-  function E() {}
-  function Class() {
-    return Super.apply(this, arguments);
-  }
-  var Super = this;
-  E.prototype = Super.prototype;
-  var prototype = new E();
-  Object.assign(prototype, Class.prototype);
-  Class.prototype = prototype;
-  Class.prototype.constructor = Class;
-  Class.Interface = Object.assign({}, Super.Interface, Interface);
-  Class.extend = Super.extend;
-  addEventPoolingTo(Class);
-  return Class;
-};
-addEventPoolingTo(SyntheticEvent);
-function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
-  if (this.eventPool.length) {
-    var instance = this.eventPool.pop();
-    this.call(instance, dispatchConfig, targetInst, nativeEvent, nativeInst);
-    return instance;
-  }
-  return new this(dispatchConfig, targetInst, nativeEvent, nativeInst);
-}
-function releasePooledEvent(event) {
-  invariant(
-    event instanceof this,
-    "Trying to release an event instance  into a pool of a different type."
-  );
-  event.destructor();
-  10 > this.eventPool.length && this.eventPool.push(event);
-}
-function addEventPoolingTo(EventConstructor) {
-  EventConstructor.eventPool = [];
-  EventConstructor.getPooled = getPooledEvent;
-  EventConstructor.release = releasePooledEvent;
-}
-var ResponderSyntheticEvent = SyntheticEvent.extend({
-    touchHistory: function() {
-      return null;
-    }
-  }),
-  touchBank = [],
-  touchHistory = {
-    touchBank: touchBank,
-    numberActiveTouches: 0,
-    indexOfSingleActiveTouch: -1,
-    mostRecentTimeStamp: 0
-  };
-function timestampForTouch(touch) {
-  return touch.timeStamp || touch.timestamp;
-}
-function getTouchIdentifier(_ref) {
-  _ref = _ref.identifier;
-  invariant(null != _ref, "Touch object is missing identifier.");
-  return _ref;
-}
-function recordTouchStart(touch) {
-  var identifier = getTouchIdentifier(touch),
-    touchRecord = touchBank[identifier];
-  touchRecord
-    ? ((touchRecord.touchActive = !0),
-      (touchRecord.startPageX = touch.pageX),
-      (touchRecord.startPageY = touch.pageY),
-      (touchRecord.startTimeStamp = timestampForTouch(touch)),
-      (touchRecord.currentPageX = touch.pageX),
-      (touchRecord.currentPageY = touch.pageY),
-      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
-      (touchRecord.previousPageX = touch.pageX),
-      (touchRecord.previousPageY = touch.pageY),
-      (touchRecord.previousTimeStamp = timestampForTouch(touch)))
-    : ((touchRecord = {
-        touchActive: !0,
-        startPageX: touch.pageX,
-        startPageY: touch.pageY,
-        startTimeStamp: timestampForTouch(touch),
-        currentPageX: touch.pageX,
-        currentPageY: touch.pageY,
-        currentTimeStamp: timestampForTouch(touch),
-        previousPageX: touch.pageX,
-        previousPageY: touch.pageY,
-        previousTimeStamp: timestampForTouch(touch)
-      }),
-      (touchBank[identifier] = touchRecord));
-  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
-}
-function recordTouchMove(touch) {
-  var touchRecord = touchBank[getTouchIdentifier(touch)];
-  touchRecord
-    ? ((touchRecord.touchActive = !0),
-      (touchRecord.previousPageX = touchRecord.currentPageX),
-      (touchRecord.previousPageY = touchRecord.currentPageY),
-      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
-      (touchRecord.currentPageX = touch.pageX),
-      (touchRecord.currentPageY = touch.pageY),
-      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
-      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
-    : console.error(
-        "Cannot record touch move without a touch start.\nTouch Move: %s\n",
-        "Touch Bank: %s",
-        printTouch(touch),
-        printTouchBank()
-      );
-}
-function recordTouchEnd(touch) {
-  var touchRecord = touchBank[getTouchIdentifier(touch)];
-  touchRecord
-    ? ((touchRecord.touchActive = !1),
-      (touchRecord.previousPageX = touchRecord.currentPageX),
-      (touchRecord.previousPageY = touchRecord.currentPageY),
-      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
-      (touchRecord.currentPageX = touch.pageX),
-      (touchRecord.currentPageY = touch.pageY),
-      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
-      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
-    : console.error(
-        "Cannot record touch end without a touch start.\nTouch End: %s\n",
-        "Touch Bank: %s",
-        printTouch(touch),
-        printTouchBank()
-      );
-}
-function printTouch(touch) {
-  return JSON.stringify({
-    identifier: touch.identifier,
-    pageX: touch.pageX,
-    pageY: touch.pageY,
-    timestamp: timestampForTouch(touch)
-  });
-}
-function printTouchBank() {
-  var printed = JSON.stringify(touchBank.slice(0, 20));
-  20 < touchBank.length &&
-    (printed += " (original size: " + touchBank.length + ")");
-  return printed;
-}
-var ResponderTouchHistoryStore = {
-  recordTouchTrack: function(topLevelType, nativeEvent) {
-    if (isMoveish(topLevelType))
-      nativeEvent.changedTouches.forEach(recordTouchMove);
-    else if (isStartish(topLevelType))
-      nativeEvent.changedTouches.forEach(recordTouchStart),
-        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
-        1 === touchHistory.numberActiveTouches &&
-          (touchHistory.indexOfSingleActiveTouch =
-            nativeEvent.touches[0].identifier);
-    else if (
-      isEndish(topLevelType) &&
-      (nativeEvent.changedTouches.forEach(recordTouchEnd),
-      (touchHistory.numberActiveTouches = nativeEvent.touches.length),
-      1 === touchHistory.numberActiveTouches)
-    )
-      for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
-        if (
-          ((nativeEvent = touchBank[topLevelType]),
-          null != nativeEvent && nativeEvent.touchActive)
-        ) {
-          touchHistory.indexOfSingleActiveTouch = topLevelType;
-          break;
-        }
-  },
-  touchHistory: touchHistory
-};
-function accumulate(current, next) {
-  invariant(
-    null != next,
-    "accumulate(...): Accumulated items must be not be null or undefined."
-  );
-  return null == current
-    ? next
-    : Array.isArray(current)
-      ? current.concat(next)
-      : Array.isArray(next) ? [current].concat(next) : [current, next];
-}
-var responderInst = null,
-  trackedTouchCount = 0,
-  previousActiveTouches = 0;
-function changeResponder(nextResponderInst, blockHostResponder) {
-  var oldResponderInst = responderInst;
-  responderInst = nextResponderInst;
-  if (null !== ResponderEventPlugin.GlobalResponderHandler)
-    ResponderEventPlugin.GlobalResponderHandler.onChange(
-      oldResponderInst,
-      nextResponderInst,
-      blockHostResponder
-    );
-}
-var eventTypes$1 = {
-    startShouldSetResponder: {
-      phasedRegistrationNames: {
-        bubbled: "onStartShouldSetResponder",
-        captured: "onStartShouldSetResponderCapture"
-      }
-    },
-    scrollShouldSetResponder: {
-      phasedRegistrationNames: {
-        bubbled: "onScrollShouldSetResponder",
-        captured: "onScrollShouldSetResponderCapture"
-      }
-    },
-    selectionChangeShouldSetResponder: {
-      phasedRegistrationNames: {
-        bubbled: "onSelectionChangeShouldSetResponder",
-        captured: "onSelectionChangeShouldSetResponderCapture"
-      }
-    },
-    moveShouldSetResponder: {
-      phasedRegistrationNames: {
-        bubbled: "onMoveShouldSetResponder",
-        captured: "onMoveShouldSetResponderCapture"
-      }
-    },
-    responderStart: { registrationName: "onResponderStart" },
-    responderMove: { registrationName: "onResponderMove" },
-    responderEnd: { registrationName: "onResponderEnd" },
-    responderRelease: { registrationName: "onResponderRelease" },
-    responderTerminationRequest: {
-      registrationName: "onResponderTerminationRequest"
-    },
-    responderGrant: { registrationName: "onResponderGrant" },
-    responderReject: { registrationName: "onResponderReject" },
-    responderTerminate: { registrationName: "onResponderTerminate" }
-  },
-  ResponderEventPlugin = {
-    _getResponder: function() {
-      return responderInst;
-    },
-    eventTypes: eventTypes$1,
-    extractEvents: function(
-      topLevelType,
-      targetInst,
-      nativeEvent,
-      nativeEventTarget
-    ) {
-      if (isStartish(topLevelType)) trackedTouchCount += 1;
-      else if (isEndish(topLevelType))
-        if (0 <= trackedTouchCount) --trackedTouchCount;
-        else
-          return (
-            console.error(
-              "Ended a touch event which was not counted in `trackedTouchCount`."
-            ),
-            null
-          );
-      ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
-      if (
-        targetInst &&
-        (("topScroll" === topLevelType && !nativeEvent.responderIgnoreScroll) ||
-          (0 < trackedTouchCount && "topSelectionChange" === topLevelType) ||
-          isStartish(topLevelType) ||
-          isMoveish(topLevelType))
-      ) {
-        var JSCompiler_temp = isStartish(topLevelType)
-          ? eventTypes$1.startShouldSetResponder
-          : isMoveish(topLevelType)
-            ? eventTypes$1.moveShouldSetResponder
-            : "topSelectionChange" === topLevelType
-              ? eventTypes$1.selectionChangeShouldSetResponder
-              : eventTypes$1.scrollShouldSetResponder;
-        if (responderInst)
-          b: {
-            var JSCompiler_temp$jscomp$0 = responderInst;
-            for (
-              var depthA = 0, tempA = JSCompiler_temp$jscomp$0;
-              tempA;
-              tempA = getParent(tempA)
-            )
-              depthA++;
-            tempA = 0;
-            for (var tempB = targetInst; tempB; tempB = getParent(tempB))
-              tempA++;
-            for (; 0 < depthA - tempA; )
-              (JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0)),
-                depthA--;
-            for (; 0 < tempA - depthA; )
-              (targetInst = getParent(targetInst)), tempA--;
-            for (; depthA--; ) {
-              if (
-                JSCompiler_temp$jscomp$0 === targetInst ||
-                JSCompiler_temp$jscomp$0 === targetInst.alternate
-              )
-                break b;
-              JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0);
-              targetInst = getParent(targetInst);
-            }
-            JSCompiler_temp$jscomp$0 = null;
-          }
-        else JSCompiler_temp$jscomp$0 = targetInst;
-        targetInst = JSCompiler_temp$jscomp$0 === responderInst;
-        JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
-          JSCompiler_temp,
-          JSCompiler_temp$jscomp$0,
-          nativeEvent,
-          nativeEventTarget
-        );
-        JSCompiler_temp$jscomp$0.touchHistory =
-          ResponderTouchHistoryStore.touchHistory;
-        targetInst
-          ? forEachAccumulated(
-              JSCompiler_temp$jscomp$0,
-              accumulateTwoPhaseDispatchesSingleSkipTarget
-            )
-          : forEachAccumulated(
-              JSCompiler_temp$jscomp$0,
-              accumulateTwoPhaseDispatchesSingle
-            );
-        b: {
-          JSCompiler_temp = JSCompiler_temp$jscomp$0._dispatchListeners;
-          targetInst = JSCompiler_temp$jscomp$0._dispatchInstances;
-          if (Array.isArray(JSCompiler_temp))
-            for (
-              depthA = 0;
-              depthA < JSCompiler_temp.length &&
-              !JSCompiler_temp$jscomp$0.isPropagationStopped();
-              depthA++
-            ) {
-              if (
-                JSCompiler_temp[depthA](
-                  JSCompiler_temp$jscomp$0,
-                  targetInst[depthA]
-                )
-              ) {
-                JSCompiler_temp = targetInst[depthA];
-                break b;
-              }
-            }
-          else if (
-            JSCompiler_temp &&
-            JSCompiler_temp(JSCompiler_temp$jscomp$0, targetInst)
-          ) {
-            JSCompiler_temp = targetInst;
-            break b;
-          }
-          JSCompiler_temp = null;
-        }
-        JSCompiler_temp$jscomp$0._dispatchInstances = null;
-        JSCompiler_temp$jscomp$0._dispatchListeners = null;
-        JSCompiler_temp$jscomp$0.isPersistent() ||
-          JSCompiler_temp$jscomp$0.constructor.release(
-            JSCompiler_temp$jscomp$0
-          );
-        JSCompiler_temp && JSCompiler_temp !== responderInst
-          ? ((JSCompiler_temp$jscomp$0 = void 0),
-            (targetInst = ResponderSyntheticEvent.getPooled(
-              eventTypes$1.responderGrant,
-              JSCompiler_temp,
-              nativeEvent,
-              nativeEventTarget
-            )),
-            (targetInst.touchHistory = ResponderTouchHistoryStore.touchHistory),
-            forEachAccumulated(targetInst, accumulateDirectDispatchesSingle),
-            (depthA = !0 === executeDirectDispatch(targetInst)),
-            responderInst
-              ? ((tempA = ResponderSyntheticEvent.getPooled(
-                  eventTypes$1.responderTerminationRequest,
-                  responderInst,
-                  nativeEvent,
-                  nativeEventTarget
-                )),
-                (tempA.touchHistory = ResponderTouchHistoryStore.touchHistory),
-                forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
-                (tempB =
-                  !tempA._dispatchListeners || executeDirectDispatch(tempA)),
-                tempA.isPersistent() || tempA.constructor.release(tempA),
-                tempB
-                  ? ((tempA = ResponderSyntheticEvent.getPooled(
-                      eventTypes$1.responderTerminate,
-                      responderInst,
-                      nativeEvent,
-                      nativeEventTarget
-                    )),
-                    (tempA.touchHistory =
-                      ResponderTouchHistoryStore.touchHistory),
-                    forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
-                    (JSCompiler_temp$jscomp$0 = accumulate(
-                      JSCompiler_temp$jscomp$0,
-                      [targetInst, tempA]
-                    )),
-                    changeResponder(JSCompiler_temp, depthA))
-                  : ((JSCompiler_temp = ResponderSyntheticEvent.getPooled(
-                      eventTypes$1.responderReject,
-                      JSCompiler_temp,
-                      nativeEvent,
-                      nativeEventTarget
-                    )),
-                    (JSCompiler_temp.touchHistory =
-                      ResponderTouchHistoryStore.touchHistory),
-                    forEachAccumulated(
-                      JSCompiler_temp,
-                      accumulateDirectDispatchesSingle
-                    ),
-                    (JSCompiler_temp$jscomp$0 = accumulate(
-                      JSCompiler_temp$jscomp$0,
-                      JSCompiler_temp
-                    ))))
-              : ((JSCompiler_temp$jscomp$0 = accumulate(
-                  JSCompiler_temp$jscomp$0,
-                  targetInst
-                )),
-                changeResponder(JSCompiler_temp, depthA)),
-            (JSCompiler_temp = JSCompiler_temp$jscomp$0))
-          : (JSCompiler_temp = null);
-      } else JSCompiler_temp = null;
-      JSCompiler_temp$jscomp$0 = responderInst && isStartish(topLevelType);
-      targetInst = responderInst && isMoveish(topLevelType);
-      depthA = responderInst && isEndish(topLevelType);
-      if (
-        (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
-          ? eventTypes$1.responderStart
-          : targetInst
-            ? eventTypes$1.responderMove
-            : depthA ? eventTypes$1.responderEnd : null)
-      )
-        (JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
-          JSCompiler_temp$jscomp$0,
-          responderInst,
-          nativeEvent,
-          nativeEventTarget
-        )),
-          (JSCompiler_temp$jscomp$0.touchHistory =
-            ResponderTouchHistoryStore.touchHistory),
-          forEachAccumulated(
-            JSCompiler_temp$jscomp$0,
-            accumulateDirectDispatchesSingle
-          ),
-          (JSCompiler_temp = accumulate(
-            JSCompiler_temp,
-            JSCompiler_temp$jscomp$0
-          ));
-      JSCompiler_temp$jscomp$0 =
-        responderInst && "topTouchCancel" === topLevelType;
-      if (
-        (topLevelType =
-          responderInst && !JSCompiler_temp$jscomp$0 && isEndish(topLevelType))
-      )
-        a: {
-          if ((topLevelType = nativeEvent.touches) && 0 !== topLevelType.length)
-            for (targetInst = 0; targetInst < topLevelType.length; targetInst++)
-              if (
-                ((depthA = topLevelType[targetInst].target),
-                null !== depthA && void 0 !== depthA && 0 !== depthA)
-              ) {
-                tempA = getInstanceFromNode(depthA);
-                b: {
-                  for (depthA = responderInst; tempA; ) {
-                    if (depthA === tempA || depthA === tempA.alternate) {
-                      depthA = !0;
-                      break b;
-                    }
-                    tempA = getParent(tempA);
-                  }
-                  depthA = !1;
-                }
-                if (depthA) {
-                  topLevelType = !1;
-                  break a;
-                }
-              }
-          topLevelType = !0;
-        }
-      if (
-        (topLevelType = JSCompiler_temp$jscomp$0
-          ? eventTypes$1.responderTerminate
-          : topLevelType ? eventTypes$1.responderRelease : null)
-      )
-        (nativeEvent = ResponderSyntheticEvent.getPooled(
-          topLevelType,
-          responderInst,
-          nativeEvent,
-          nativeEventTarget
-        )),
-          (nativeEvent.touchHistory = ResponderTouchHistoryStore.touchHistory),
-          forEachAccumulated(nativeEvent, accumulateDirectDispatchesSingle),
-          (JSCompiler_temp = accumulate(JSCompiler_temp, nativeEvent)),
-          changeResponder(null);
-      nativeEvent = ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
-      if (
-        ResponderEventPlugin.GlobalInteractionHandler &&
-        nativeEvent !== previousActiveTouches
-      )
-        ResponderEventPlugin.GlobalInteractionHandler.onChange(nativeEvent);
-      previousActiveTouches = nativeEvent;
-      return JSCompiler_temp;
-    },
-    GlobalResponderHandler: null,
-    GlobalInteractionHandler: null,
-    injection: {
-      injectGlobalResponderHandler: function(GlobalResponderHandler) {
-        ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
-      },
-      injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
-        ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
-      }
-    }
-  },
-  customBubblingEventTypes$1 =
-    ReactNativeViewConfigRegistry.customBubblingEventTypes,
-  customDirectEventTypes$1 =
-    ReactNativeViewConfigRegistry.customDirectEventTypes,
-  ReactNativeBridgeEventPlugin = {
-    eventTypes: ReactNativeViewConfigRegistry.eventTypes,
-    extractEvents: function(
-      topLevelType,
-      targetInst,
-      nativeEvent,
-      nativeEventTarget
-    ) {
-      if (null == targetInst) return null;
-      var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType],
-        directDispatchConfig = customDirectEventTypes$1[topLevelType];
-      invariant(
-        bubbleDispatchConfig || directDispatchConfig,
-        'Unsupported top level event type "%s" dispatched',
-        topLevelType
-      );
-      topLevelType = SyntheticEvent.getPooled(
-        bubbleDispatchConfig || directDispatchConfig,
-        targetInst,
-        nativeEvent,
-        nativeEventTarget
-      );
-      if (bubbleDispatchConfig)
-        forEachAccumulated(topLevelType, accumulateTwoPhaseDispatchesSingle);
-      else if (directDispatchConfig)
-        forEachAccumulated(topLevelType, accumulateDirectDispatchesSingle);
-      else return null;
-      return topLevelType;
-    }
-  },
-  instanceCache = {},
-  instanceProps = {};
-function uncacheFiberNode(tag) {
-  delete instanceCache[tag];
-  delete instanceProps[tag];
-}
-function getInstanceFromTag(tag) {
-  return "number" === typeof tag ? instanceCache[tag] || null : tag;
-}
-var ReactNativeComponentTree = Object.freeze({
-  precacheFiberNode: function(hostInst, tag) {
-    instanceCache[tag] = hostInst;
-  },
-  uncacheFiberNode: uncacheFiberNode,
-  getClosestInstanceFromNode: getInstanceFromTag,
-  getInstanceFromNode: getInstanceFromTag,
-  getNodeFromInstance: function(inst) {
-    var tag = inst.stateNode._nativeTag;
-    void 0 === tag && (tag = inst.stateNode.canonical._nativeTag);
-    invariant(tag, "All native instances should have a tag.");
-    return tag;
-  },
-  getFiberCurrentPropsFromNode: function(stateNode) {
-    return instanceProps[stateNode._nativeTag] || null;
-  },
-  updateFiberProps: function(tag, props) {
-    instanceProps[tag] = props;
-  }
-});
-injection.injectEventPluginOrder([
-  "ResponderEventPlugin",
-  "ReactNativeBridgeEventPlugin"
-]);
-getFiberCurrentPropsFromNode =
-  ReactNativeComponentTree.getFiberCurrentPropsFromNode;
-getInstanceFromNode = ReactNativeComponentTree.getInstanceFromNode;
-getNodeFromInstance = ReactNativeComponentTree.getNodeFromInstance;
-ResponderEventPlugin.injection.injectGlobalResponderHandler({
-  onChange: function(from, to, blockNativeResponder) {
-    null !== to
-      ? UIManager.setJSResponder(to.stateNode._nativeTag, blockNativeResponder)
-      : UIManager.clearJSResponder();
-  }
-});
-injection.injectEventPluginsByName({
-  ResponderEventPlugin: ResponderEventPlugin,
-  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
-});
-var restoreTarget = null,
-  restoreQueue = null;
-function restoreStateOfTarget(target) {
-  if ((target = getInstanceFromNode(target))) {
-    invariant(
-      null,
-      "Fiber needs to be injected to handle a fiber target for controlled events. This error is likely caused by a bug in React. Please file an issue."
-    );
-    var props = getFiberCurrentPropsFromNode(target.stateNode);
-    null.restoreControlledState(target.stateNode, target.type, props);
-  }
-}
-function _batchedUpdates(fn, bookkeeping) {
-  return fn(bookkeeping);
-}
-function _flushInteractiveUpdates() {}
-var isBatching = !1;
-function batchedUpdates(fn, bookkeeping) {
-  if (isBatching) return fn(bookkeeping);
-  isBatching = !0;
-  try {
-    return _batchedUpdates(fn, bookkeeping);
-  } finally {
-    if (((isBatching = !1), null !== restoreTarget || null !== restoreQueue))
-      if (
-        (_flushInteractiveUpdates(),
-        restoreTarget &&
-          ((bookkeeping = restoreTarget),
-          (fn = restoreQueue),
-          (restoreQueue = restoreTarget = null),
-          restoreStateOfTarget(bookkeeping),
-          fn))
-      )
-        for (bookkeeping = 0; bookkeeping < fn.length; bookkeeping++)
-          restoreStateOfTarget(fn[bookkeeping]);
-  }
-}
-var EMPTY_NATIVE_EVENT = {};
-function _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam) {
-  var nativeEvent = nativeEventParam || EMPTY_NATIVE_EVENT,
-    inst = getInstanceFromTag(rootNodeID);
-  batchedUpdates(function() {
-    var events = nativeEvent.target;
-    for (var events$jscomp$0 = null, i = 0; i < plugins.length; i++) {
-      var possiblePlugin = plugins[i];
-      possiblePlugin &&
-        (possiblePlugin = possiblePlugin.extractEvents(
-          topLevelType,
-          inst,
-          nativeEvent,
-          events
-        )) &&
-        (events$jscomp$0 = accumulateInto(events$jscomp$0, possiblePlugin));
-    }
-    events = events$jscomp$0;
-    null !== events && (eventQueue = accumulateInto(eventQueue, events));
-    events = eventQueue;
-    eventQueue = null;
-    events &&
-      (forEachAccumulated(events, executeDispatchesAndReleaseTopLevel),
-      invariant(
-        !eventQueue,
-        "processEventQueue(): Additional events were enqueued while processing an event queue. Support for this has not yet been implemented."
-      ),
-      ReactErrorUtils.rethrowCaughtError());
-  });
-}
-var ReactNativeEventEmitter = Object.freeze({
-  getListener: getListener,
-  registrationNames: registrationNameModules,
-  _receiveRootNodeIDEvent: _receiveRootNodeIDEvent,
-  receiveEvent: function(rootNodeID, topLevelType, nativeEventParam) {
-    _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam);
-  },
-  receiveTouches: function(eventTopLevelType, touches, changedIndices) {
-    if (
-      "topTouchEnd" === eventTopLevelType ||
-      "topTouchCancel" === eventTopLevelType
-    ) {
-      var JSCompiler_temp = [];
-      for (var i = 0; i < changedIndices.length; i++) {
-        var index = changedIndices[i];
-        JSCompiler_temp.push(touches[index]);
-        touches[index] = null;
-      }
-      for (i = changedIndices = 0; i < touches.length; i++)
-        (index = touches[i]),
-          null !== index && (touches[changedIndices++] = index);
-      touches.length = changedIndices;
-    } else
-      for (JSCompiler_temp = [], i = 0; i < changedIndices.length; i++)
-        JSCompiler_temp.push(touches[changedIndices[i]]);
-    for (
-      changedIndices = 0;
-      changedIndices < JSCompiler_temp.length;
-      changedIndices++
-    ) {
-      i = JSCompiler_temp[changedIndices];
-      i.changedTouches = JSCompiler_temp;
-      i.touches = touches;
-      index = null;
-      var target = i.target;
-      null === target || void 0 === target || 1 > target || (index = target);
-      _receiveRootNodeIDEvent(index, eventTopLevelType, i);
-    }
-  }
-});
-RCTEventEmitter.register(ReactNativeEventEmitter);
-var hasSymbol = "function" === typeof Symbol && Symbol["for"],
-  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
-  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
-  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
-  REACT_STRICT_MODE_TYPE = hasSymbol
-    ? Symbol["for"]("react.strict_mode")
-    : 60108,
-  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
-  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
-  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
-  REACT_FORWARD_REF_TYPE = hasSymbol
-    ? Symbol["for"]("react.forward_ref")
-    : 60112,
-  MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
-function getIteratorFn(maybeIterable) {
-  if (null === maybeIterable || "undefined" === typeof maybeIterable)
-    return null;
-  maybeIterable =
-    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
-    maybeIterable["@@iterator"];
-  return "function" === typeof maybeIterable ? maybeIterable : null;
-}
-function createPortal(children, containerInfo, implementation) {
-  var key =
-    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
-  return {
-    $$typeof: REACT_PORTAL_TYPE,
-    key: null == key ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
-}
-function getComponentName(fiber) {
-  fiber = fiber.type;
-  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
-  if ("string" === typeof fiber) return fiber;
-  switch (fiber) {
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
-  }
-  if ("object" === typeof fiber && null !== fiber)
-    switch (fiber.$$typeof) {
-      case REACT_FORWARD_REF_TYPE:
-        return (
-          (fiber = fiber.render.displayName || fiber.render.name || ""),
-          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
-        );
-    }
-  return null;
-}
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  do {
-    a: switch (workInProgress.tag) {
-      case 0:
-      case 1:
-      case 2:
-      case 5:
-        var owner = workInProgress._debugOwner,
-          source = workInProgress._debugSource;
-        var JSCompiler_inline_result = getComponentName(workInProgress);
-        var ownerName = null;
-        owner && (ownerName = getComponentName(owner));
-        owner = source;
-        JSCompiler_inline_result =
-          "\n    in " +
-          (JSCompiler_inline_result || "Unknown") +
-          (owner
-            ? " (at " +
-              owner.fileName.replace(/^.*[\\\/]/, "") +
-              ":" +
-              owner.lineNumber +
-              ")"
-            : ownerName ? " (created by " + ownerName + ")" : "");
-        break a;
-      default:
-        JSCompiler_inline_result = "";
-    }
-    info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
-  } while (workInProgress);
-  return info;
-}
-var emptyObject$1 = {},
-  removedKeys = null,
-  removedKeyCount = 0;
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node))
-    for (var i = node.length; i-- && 0 < removedKeyCount; )
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
-  else if (node && 0 < removedKeyCount)
-    for (i in removedKeys)
-      if (removedKeys[i]) {
-        var _nextProp = node[i];
-        if (void 0 !== _nextProp) {
-          var attributeConfig = validAttributes[i];
-          if (attributeConfig) {
-            "function" === typeof _nextProp && (_nextProp = !0);
-            "undefined" === typeof _nextProp && (_nextProp = null);
-            if ("object" !== typeof attributeConfig)
-              updatePayload[i] = _nextProp;
-            else if (
-              "function" === typeof attributeConfig.diff ||
-              "function" === typeof attributeConfig.process
-            )
-              (_nextProp =
-                "function" === typeof attributeConfig.process
-                  ? attributeConfig.process(_nextProp)
-                  : _nextProp),
-                (updatePayload[i] = _nextProp);
-            removedKeys[i] = !1;
-            removedKeyCount--;
-          }
-        }
-      }
-}
-function diffNestedProperty(
-  updatePayload,
-  prevProp,
-  nextProp,
-  validAttributes
-) {
-  if (!updatePayload && prevProp === nextProp) return updatePayload;
-  if (!prevProp || !nextProp)
-    return nextProp
-      ? addNestedProperty(updatePayload, nextProp, validAttributes)
-      : prevProp
-        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
-        : updatePayload;
-  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
-    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
-  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
-    var minLength =
-        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
-      i;
-    for (i = 0; i < minLength; i++)
-      updatePayload = diffNestedProperty(
-        updatePayload,
-        prevProp[i],
-        nextProp[i],
-        validAttributes
-      );
-    for (; i < prevProp.length; i++)
-      updatePayload = clearNestedProperty(
-        updatePayload,
-        prevProp[i],
-        validAttributes
-      );
-    for (; i < nextProp.length; i++)
-      updatePayload = addNestedProperty(
-        updatePayload,
-        nextProp[i],
-        validAttributes
-      );
-    return updatePayload;
-  }
-  return Array.isArray(prevProp)
-    ? diffProperties(
-        updatePayload,
-        flattenStyle(prevProp),
-        nextProp,
-        validAttributes
-      )
-    : diffProperties(
-        updatePayload,
-        prevProp,
-        flattenStyle(nextProp),
-        validAttributes
-      );
-}
-function addNestedProperty(updatePayload, nextProp, validAttributes) {
-  if (!nextProp) return updatePayload;
-  if (!Array.isArray(nextProp))
-    return diffProperties(
-      updatePayload,
-      emptyObject$1,
-      nextProp,
-      validAttributes
-    );
-  for (var i = 0; i < nextProp.length; i++)
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextProp[i],
-      validAttributes
-    );
-  return updatePayload;
-}
-function clearNestedProperty(updatePayload, prevProp, validAttributes) {
-  if (!prevProp) return updatePayload;
-  if (!Array.isArray(prevProp))
-    return diffProperties(
-      updatePayload,
-      prevProp,
-      emptyObject$1,
-      validAttributes
-    );
-  for (var i = 0; i < prevProp.length; i++)
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevProp[i],
-      validAttributes
-    );
-  return updatePayload;
-}
-function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
-  var attributeConfig, propKey;
-  for (propKey in nextProps)
-    if ((attributeConfig = validAttributes[propKey])) {
-      var prevProp = prevProps[propKey];
-      var nextProp = nextProps[propKey];
-      "function" === typeof nextProp &&
-        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
-      "undefined" === typeof nextProp &&
-        ((nextProp = null),
-        "undefined" === typeof prevProp && (prevProp = null));
-      removedKeys && (removedKeys[propKey] = !1);
-      if (updatePayload && void 0 !== updatePayload[propKey])
-        if ("object" !== typeof attributeConfig)
-          updatePayload[propKey] = nextProp;
-        else {
-          if (
-            "function" === typeof attributeConfig.diff ||
-            "function" === typeof attributeConfig.process
-          )
-            (attributeConfig =
-              "function" === typeof attributeConfig.process
-                ? attributeConfig.process(nextProp)
-                : nextProp),
-              (updatePayload[propKey] = attributeConfig);
-        }
-      else if (prevProp !== nextProp)
-        if ("object" !== typeof attributeConfig)
-          ("object" !== typeof nextProp ||
-            null === nextProp ||
-            deepDiffer(prevProp, nextProp)) &&
-            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
-        else if (
-          "function" === typeof attributeConfig.diff ||
-          "function" === typeof attributeConfig.process
-        ) {
-          if (
-            void 0 === prevProp ||
-            ("function" === typeof attributeConfig.diff
-              ? attributeConfig.diff(prevProp, nextProp)
-              : "object" !== typeof nextProp ||
-                null === nextProp ||
-                deepDiffer(prevProp, nextProp))
-          )
-            (attributeConfig =
-              "function" === typeof attributeConfig.process
-                ? attributeConfig.process(nextProp)
-                : nextProp),
-              ((updatePayload || (updatePayload = {}))[
-                propKey
-              ] = attributeConfig);
-        } else
-          (removedKeys = null),
-            (removedKeyCount = 0),
-            (updatePayload = diffNestedProperty(
-              updatePayload,
-              prevProp,
-              nextProp,
-              attributeConfig
-            )),
-            0 < removedKeyCount &&
-              updatePayload &&
-              (restoreDeletedValuesInNestedArray(
-                updatePayload,
-                nextProp,
-                attributeConfig
-              ),
-              (removedKeys = null));
-    }
-  for (var _propKey in prevProps)
-    void 0 === nextProps[_propKey] &&
-      (!(attributeConfig = validAttributes[_propKey]) ||
-        (updatePayload && void 0 !== updatePayload[_propKey]) ||
-        ((prevProp = prevProps[_propKey]),
-        void 0 !== prevProp &&
-          ("object" !== typeof attributeConfig ||
-          "function" === typeof attributeConfig.diff ||
-          "function" === typeof attributeConfig.process
-            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
-              removedKeys || (removedKeys = {}),
-              removedKeys[_propKey] ||
-                ((removedKeys[_propKey] = !0), removedKeyCount++))
-            : (updatePayload = clearNestedProperty(
-                updatePayload,
-                prevProp,
-                attributeConfig
-              )))));
-  return updatePayload;
-}
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (callback) {
-      if ("boolean" === typeof context.__isMounted) {
-        if (!context.__isMounted) return;
-      } else if (
-        "function" === typeof context.isMounted &&
-        !context.isMounted()
-      )
-        return;
-      return callback.apply(context, arguments);
-    }
-  };
-}
-function _inherits(subClass, superClass) {
-  if ("function" !== typeof superClass && null !== superClass)
-    throw new TypeError(
-      "Super expression must either be null or a function, not " +
-        typeof superClass
-    );
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: !1,
-      writable: !0,
-      configurable: !0
-    }
-  });
-  superClass &&
-    (Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass));
-}
-var ReactCurrentOwner =
-  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
-function isFiberMountedImpl(fiber) {
-  var node = fiber;
-  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
-  else {
-    if (0 !== (node.effectTag & 2)) return 1;
-    for (; node["return"]; )
-      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
-  }
-  return 3 === node.tag ? 2 : 3;
-}
-function isMounted(component) {
-  return (component = component._reactInternalFiber)
-    ? 2 === isFiberMountedImpl(component)
-    : !1;
-}
-function assertIsMounted(fiber) {
-  invariant(
-    2 === isFiberMountedImpl(fiber),
-    "Unable to find node on an unmounted component."
-  );
-}
-function findCurrentFiberUsingSlowPath(fiber) {
-  var alternate = fiber.alternate;
-  if (!alternate)
-    return (
-      (alternate = isFiberMountedImpl(fiber)),
-      invariant(
-        3 !== alternate,
-        "Unable to find node on an unmounted component."
-      ),
-      1 === alternate ? null : fiber
-    );
-  for (var a = fiber, b = alternate; ; ) {
-    var parentA = a["return"],
-      parentB = parentA ? parentA.alternate : null;
-    if (!parentA || !parentB) break;
-    if (parentA.child === parentB.child) {
-      for (var child = parentA.child; child; ) {
-        if (child === a) return assertIsMounted(parentA), fiber;
-        if (child === b) return assertIsMounted(parentA), alternate;
-        child = child.sibling;
-      }
-      invariant(!1, "Unable to find node on an unmounted component.");
-    }
-    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
-    else {
-      child = !1;
-      for (var _child = parentA.child; _child; ) {
-        if (_child === a) {
-          child = !0;
-          a = parentA;
-          b = parentB;
-          break;
-        }
-        if (_child === b) {
-          child = !0;
-          b = parentA;
-          a = parentB;
-          break;
-        }
-        _child = _child.sibling;
-      }
-      if (!child) {
-        for (_child = parentB.child; _child; ) {
-          if (_child === a) {
-            child = !0;
-            a = parentB;
-            b = parentA;
-            break;
-          }
-          if (_child === b) {
-            child = !0;
-            b = parentB;
-            a = parentA;
-            break;
-          }
-          _child = _child.sibling;
-        }
-        invariant(
-          child,
-          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
-        );
-      }
-    }
-    invariant(
-      a.alternate === b,
-      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
-  return a.stateNode.current === a ? fiber : alternate;
-}
-function findCurrentHostFiber(parent) {
-  parent = findCurrentFiberUsingSlowPath(parent);
-  if (!parent) return null;
-  for (var node = parent; ; ) {
-    if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child["return"] = node), (node = node.child);
-    else {
-      if (node === parent) break;
-      for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-  return null;
-}
-function findCurrentHostFiberWithNoPortals(parent) {
-  parent = findCurrentFiberUsingSlowPath(parent);
-  if (!parent) return null;
-  for (var node = parent; ; ) {
-    if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child && 4 !== node.tag)
-      (node.child["return"] = node), (node = node.child);
-    else {
-      if (node === parent) break;
-      for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-  return null;
-}
-function FiberNode(tag, pendingProps, key, mode) {
-  this.tag = tag;
-  this.key = key;
-  this.stateNode = this.type = null;
-  this.sibling = this.child = this["return"] = null;
-  this.index = 0;
-  this.ref = null;
-  this.pendingProps = pendingProps;
-  this.memoizedState = this.updateQueue = this.memoizedProps = null;
-  this.mode = mode;
-  this.effectTag = 0;
-  this.lastEffect = this.firstEffect = this.nextEffect = null;
-  this.expirationTime = 0;
-  this.alternate = null;
-}
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  null === workInProgress
-    ? ((workInProgress = new FiberNode(
-        current.tag,
-        pendingProps,
-        current.key,
-        current.mode
-      )),
-      (workInProgress.type = current.type),
-      (workInProgress.stateNode = current.stateNode),
-      (workInProgress.alternate = current),
-      (current.alternate = workInProgress))
-    : ((workInProgress.pendingProps = pendingProps),
-      (workInProgress.effectTag = 0),
-      (workInProgress.nextEffect = null),
-      (workInProgress.firstEffect = null),
-      (workInProgress.lastEffect = null));
-  workInProgress.expirationTime = expirationTime;
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
-  return workInProgress;
-}
-function createFiberFromElement(element, mode, expirationTime) {
-  var type = element.type,
-    key = element.key;
-  element = element.props;
-  var fiberTag = void 0;
-  if ("function" === typeof type)
-    fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
-  else if ("string" === typeof type) fiberTag = 5;
-  else
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          element.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = 11;
-        mode |= 3;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = 11;
-        mode |= 2;
-        break;
-      case REACT_CALL_TYPE:
-        fiberTag = 7;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = 9;
-        break;
-      default:
-        if ("object" === typeof type && null !== type)
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = 13;
-              break;
-            case REACT_CONTEXT_TYPE:
-              fiberTag = 12;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = 14;
-              break;
-            default:
-              if ("number" === typeof type.tag)
-                return (
-                  (mode = type),
-                  (mode.pendingProps = element),
-                  (mode.expirationTime = expirationTime),
-                  mode
-                );
-              throwOnInvalidElementType(type, null);
-          }
-        else throwOnInvalidElementType(type, null);
-    }
-  mode = new FiberNode(fiberTag, element, key, mode);
-  mode.type = type;
-  mode.expirationTime = expirationTime;
-  return mode;
-}
-function throwOnInvalidElementType(type) {
-  invariant(
-    !1,
-    "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
-    null == type ? type : typeof type,
-    ""
-  );
-}
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  elements = new FiberNode(10, elements, key, mode);
-  elements.expirationTime = expirationTime;
-  return elements;
-}
-function createFiberFromText(content, mode, expirationTime) {
-  content = new FiberNode(6, content, null, mode);
-  content.expirationTime = expirationTime;
-  return content;
-}
-function createFiberFromPortal(portal, mode, expirationTime) {
-  mode = new FiberNode(
-    4,
-    null !== portal.children ? portal.children : [],
-    portal.key,
-    mode
-  );
-  mode.expirationTime = expirationTime;
-  mode.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null,
-    implementation: portal.implementation
-  };
-  return mode;
-}
-var onCommitFiberRoot = null,
-  onCommitFiberUnmount = null;
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {}
-  };
-}
-function injectInternals(internals) {
-  if ("undefined" === typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) return !1;
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled || !hook.supportsFiber) return !0;
-  try {
-    var rendererID = hook.inject(internals);
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {}
-  return !0;
-}
-function onCommitRoot(root) {
-  "function" === typeof onCommitFiberRoot && onCommitFiberRoot(root);
-}
-function onCommitUnmount(fiber) {
-  "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
-}
-var _require = require("ReactFeatureFlags"),
-  enableGetDerivedStateFromCatch = _require.enableGetDerivedStateFromCatch,
-  debugRenderPhaseSideEffects = _require.debugRenderPhaseSideEffects,
-  debugRenderPhaseSideEffectsForStrictMode =
-    _require.debugRenderPhaseSideEffectsForStrictMode;
-new Set();
-function createUpdateQueue(baseState) {
-  return {
-    baseState: baseState,
-    expirationTime: 0,
-    first: null,
-    last: null,
-    callbackList: null,
-    hasForceUpdate: !1,
-    isInitialized: !1,
-    capturedValues: null
-  };
-}
-function insertUpdateIntoQueue(queue, update) {
-  null === queue.last
-    ? (queue.first = queue.last = update)
-    : ((queue.last.next = update), (queue.last = update));
-  if (
-    0 === queue.expirationTime ||
-    queue.expirationTime > update.expirationTime
-  )
-    queue.expirationTime = update.expirationTime;
-}
-var q1 = void 0,
-  q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  var alternateFiber = fiber.alternate,
-    queue1 = fiber.updateQueue;
-  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
-  null !== alternateFiber
-    ? ((fiber = alternateFiber.updateQueue),
-      null === fiber &&
-        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
-    : (fiber = null);
-  q1 = queue1;
-  q2 = fiber !== queue1 ? fiber : null;
-}
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  fiber = q1;
-  var queue2 = q2;
-  null === queue2
-    ? insertUpdateIntoQueue(fiber, update)
-    : null === fiber.last || null === queue2.last
-      ? (insertUpdateIntoQueue(fiber, update),
-        insertUpdateIntoQueue(queue2, update))
-      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
-}
-function getStateFromUpdate(update, instance, prevState, props) {
-  update = update.partialState;
-  return "function" === typeof update
-    ? update.call(instance, prevState, props)
-    : update;
-}
-function processUpdateQueue(
-  current,
-  workInProgress,
-  queue,
-  instance,
-  props,
-  renderExpirationTime
-) {
-  null !== current &&
-    current.updateQueue === queue &&
-    (queue = workInProgress.updateQueue = {
-      baseState: queue.baseState,
-      expirationTime: queue.expirationTime,
-      first: queue.first,
-      last: queue.last,
-      isInitialized: queue.isInitialized,
-      capturedValues: queue.capturedValues,
-      callbackList: null,
-      hasForceUpdate: !1
-    });
-  queue.expirationTime = 0;
-  queue.isInitialized
-    ? (current = queue.baseState)
-    : ((current = queue.baseState = workInProgress.memoizedState),
-      (queue.isInitialized = !0));
-  for (
-    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
-    null !== update;
-
-  ) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        remainingExpirationTime > updateExpirationTime
-      )
-        queue.expirationTime = updateExpirationTime;
-      didSkip || ((didSkip = !0), (queue.baseState = current));
-    } else {
-      didSkip ||
-        ((queue.first = update.next),
-        null === queue.first && (queue.last = null));
-      (debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & 2)) &&
-        getStateFromUpdate(update, instance, current, props);
-      if (update.isReplace)
-        (current = getStateFromUpdate(update, instance, current, props)),
-          (dontMutatePrevState = !0);
-      else if (
-        (updateExpirationTime = getStateFromUpdate(
-          update,
-          instance,
-          current,
-          props
-        ))
-      )
-        (current = dontMutatePrevState
-          ? Object.assign({}, current, updateExpirationTime)
-          : Object.assign(current, updateExpirationTime)),
-          (dontMutatePrevState = !1);
-      update.isForced && (queue.hasForceUpdate = !0);
-      null !== update.callback &&
-        ((updateExpirationTime = queue.callbackList),
-        null === updateExpirationTime &&
-          (updateExpirationTime = queue.callbackList = []),
-        updateExpirationTime.push(update));
-      null !== update.capturedValue &&
-        ((updateExpirationTime = queue.capturedValues),
-        null === updateExpirationTime
-          ? (queue.capturedValues = [update.capturedValue])
-          : updateExpirationTime.push(update.capturedValue));
-    }
-    update = update.next;
-  }
-  null !== queue.callbackList
-    ? (workInProgress.effectTag |= 32)
-    : null !== queue.first ||
-      queue.hasForceUpdate ||
-      null !== queue.capturedValues ||
-      (workInProgress.updateQueue = null);
-  didSkip || (queue.baseState = current);
-  return current;
-}
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (null !== callbackList)
-    for (
-      queue.callbackList = null, queue = 0;
-      queue < callbackList.length;
-      queue++
-    ) {
-      var update = callbackList[queue],
-        _callback = update.callback;
-      update.callback = null;
-      invariant(
-        "function" === typeof _callback,
-        "Invalid argument passed as callback. Expected a function. Instead received: %s",
-        _callback
-      );
-      _callback.call(context);
-    }
-}
-function callGetDerivedStateFromCatch(ctor, capturedValues) {
-  for (var resultState = {}, i = 0; i < capturedValues.length; i++) {
-    var partialState = ctor.getDerivedStateFromCatch.call(
-      null,
-      capturedValues[i].value
-    );
-    null !== partialState &&
-      void 0 !== partialState &&
-      Object.assign(resultState, partialState);
-  }
-  return resultState;
-}
-function ReactFiberClassComponent(
-  legacyContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState
-) {
-  function checkShouldComponentUpdate(
-    workInProgress,
-    oldProps,
-    newProps,
-    oldState,
-    newState,
-    newContext
-  ) {
-    if (
-      null === oldProps ||
-      (null !== workInProgress.updateQueue &&
-        workInProgress.updateQueue.hasForceUpdate)
-    )
-      return !0;
-    var instance = workInProgress.stateNode;
-    workInProgress = workInProgress.type;
-    return "function" === typeof instance.shouldComponentUpdate
-      ? instance.shouldComponentUpdate(newProps, newState, newContext)
-      : workInProgress.prototype &&
-        workInProgress.prototype.isPureReactComponent
-        ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
-        : !0;
-  }
-  function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
-    workInProgress.stateNode = instance;
-    instance._reactInternalFiber = workInProgress;
-  }
-  function callComponentWillReceiveProps(
-    workInProgress,
-    instance,
-    newProps,
-    newContext
-  ) {
-    workInProgress = instance.state;
-    "function" === typeof instance.componentWillReceiveProps &&
-      instance.componentWillReceiveProps(newProps, newContext);
-    "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
-      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
-    instance.state !== workInProgress &&
-      updater.enqueueReplaceState(instance, instance.state, null);
-  }
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    instance = workInProgress.type;
-    if ("function" === typeof instance.getDerivedStateFromProps)
-      return (
-        (debugRenderPhaseSideEffects ||
-          (debugRenderPhaseSideEffectsForStrictMode &&
-            workInProgress.mode & 2)) &&
-          instance.getDerivedStateFromProps.call(null, nextProps, prevState),
-        instance.getDerivedStateFromProps.call(null, nextProps, prevState)
-      );
-  }
-  var cacheContext = legacyContext.cacheContext,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    isContextConsumer = legacyContext.isContextConsumer,
-    hasContextChanged = legacyContext.hasContextChanged,
-    updater = {
-      isMounted: isMounted,
-      enqueueSetState: function(instance, partialState, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: partialState,
-          callback: callback,
-          isReplace: !1,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
-      },
-      enqueueReplaceState: function(instance, state, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: state,
-          callback: callback,
-          isReplace: !0,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
-      },
-      enqueueForceUpdate: function(instance, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: null,
-          callback: callback,
-          isReplace: !1,
-          isForced: !0,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
-      }
-    };
-  return {
-    adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
-    constructClassInstance: function(workInProgress, props) {
-      var ctor = workInProgress.type,
-        unmaskedContext = getUnmaskedContext(workInProgress),
-        needsContext = isContextConsumer(workInProgress),
-        context = needsContext
-          ? getMaskedContext(workInProgress, unmaskedContext)
-          : emptyObject;
-      (debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & 2)) &&
-        new ctor(props, context);
-      ctor = new ctor(props, context);
-      var state =
-        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
-      adoptClassInstance(workInProgress, ctor);
-      workInProgress.memoizedState = state;
-      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
-      null !== props &&
-        void 0 !== props &&
-        (workInProgress.memoizedState = Object.assign(
-          {},
-          workInProgress.memoizedState,
-          props
-        ));
-      needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return ctor;
-    },
-    mountClassInstance: function(workInProgress, renderExpirationTime) {
-      var ctor = workInProgress.type,
-        current = workInProgress.alternate,
-        instance = workInProgress.stateNode,
-        props = workInProgress.pendingProps,
-        unmaskedContext = getUnmaskedContext(workInProgress);
-      instance.props = props;
-      instance.state = workInProgress.memoizedState;
-      instance.refs = emptyObject;
-      instance.context = getMaskedContext(workInProgress, unmaskedContext);
-      "function" === typeof ctor.getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate ||
-        ("function" !== typeof instance.UNSAFE_componentWillMount &&
-          "function" !== typeof instance.componentWillMount) ||
-        ((ctor = instance.state),
-        "function" === typeof instance.componentWillMount &&
-          instance.componentWillMount(),
-        "function" === typeof instance.UNSAFE_componentWillMount &&
-          instance.UNSAFE_componentWillMount(),
-        ctor !== instance.state &&
-          updater.enqueueReplaceState(instance, instance.state, null),
-        (ctor = workInProgress.updateQueue),
-        null !== ctor &&
-          (instance.state = processUpdateQueue(
-            current,
-            workInProgress,
-            ctor,
-            instance,
-            props,
-            renderExpirationTime
-          )));
-      "function" === typeof instance.componentDidMount &&
-        (workInProgress.effectTag |= 4);
-    },
-    resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
-        newUnmaskedContext = getUnmaskedContext(workInProgress);
-      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var hasNewLifecycles =
-        "function" === typeof ctor.getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate;
-      hasNewLifecycles ||
-        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-          "function" !== typeof instance.componentWillReceiveProps) ||
-        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
-          callComponentWillReceiveProps(
-            workInProgress,
-            instance,
-            newProps,
-            newUnmaskedContext
-          ));
-      oldContext = workInProgress.memoizedState;
-      var derivedStateFromCatch = void 0;
-      if (null !== workInProgress.updateQueue) {
-        renderExpirationTime = processUpdateQueue(
-          null,
-          workInProgress,
-          workInProgress.updateQueue,
-          instance,
-          newProps,
-          renderExpirationTime
-        );
-        var updateQueue = workInProgress.updateQueue;
-        null !== updateQueue &&
-          null !== updateQueue.capturedValues &&
-          enableGetDerivedStateFromCatch &&
-          "function" === typeof ctor.getDerivedStateFromCatch &&
-          (derivedStateFromCatch = callGetDerivedStateFromCatch(
-            ctor,
-            updateQueue.capturedValues
-          ));
-      } else renderExpirationTime = oldContext;
-      ctor = void 0;
-      oldProps !== newProps &&
-        (ctor = callGetDerivedStateFromProps(
-          workInProgress,
-          instance,
-          newProps,
-          renderExpirationTime
-        ));
-      null !== ctor &&
-        void 0 !== ctor &&
-        ((renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? ctor
-            : Object.assign({}, renderExpirationTime, ctor)),
-        (updateQueue = workInProgress.updateQueue),
-        null !== updateQueue &&
-          (updateQueue.baseState = Object.assign(
-            {},
-            updateQueue.baseState,
-            ctor
-          )));
-      null !== derivedStateFromCatch &&
-        void 0 !== derivedStateFromCatch &&
-        ((renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromCatch
-            : Object.assign({}, renderExpirationTime, derivedStateFromCatch)),
-        (ctor = workInProgress.updateQueue),
-        null !== ctor &&
-          (ctor.baseState = Object.assign(
-            {},
-            ctor.baseState,
-            derivedStateFromCatch
-          )));
-      if (
-        !(
-          oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
-          hasContextChanged() ||
-          (null !== workInProgress.updateQueue &&
-            workInProgress.updateQueue.hasForceUpdate)
-        )
-      )
-        return (
-          "function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4),
-          !1
-        );
-      (oldProps = checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldContext,
-        renderExpirationTime,
-        newUnmaskedContext
-      ))
-        ? (hasNewLifecycles ||
-            ("function" !== typeof instance.UNSAFE_componentWillMount &&
-              "function" !== typeof instance.componentWillMount) ||
-            ("function" === typeof instance.componentWillMount &&
-              instance.componentWillMount(),
-            "function" === typeof instance.UNSAFE_componentWillMount &&
-              instance.UNSAFE_componentWillMount()),
-          "function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4))
-        : ("function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
-      instance.props = newProps;
-      instance.state = renderExpirationTime;
-      instance.context = newUnmaskedContext;
-      return oldProps;
-    },
-    updateClassInstance: function(
-      current,
-      workInProgress,
-      renderExpirationTime
-    ) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
-        newUnmaskedContext = getUnmaskedContext(workInProgress);
-      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var hasNewLifecycles =
-        "function" === typeof ctor.getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate;
-      hasNewLifecycles ||
-        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-          "function" !== typeof instance.componentWillReceiveProps) ||
-        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
-          callComponentWillReceiveProps(
-            workInProgress,
-            instance,
-            newProps,
-            newUnmaskedContext
-          ));
-      oldContext = workInProgress.memoizedState;
-      var derivedStateFromCatch = void 0;
-      if (null !== workInProgress.updateQueue) {
-        renderExpirationTime = processUpdateQueue(
-          current,
-          workInProgress,
-          workInProgress.updateQueue,
-          instance,
-          newProps,
-          renderExpirationTime
-        );
-        var updateQueue = workInProgress.updateQueue;
-        null !== updateQueue &&
-          null !== updateQueue.capturedValues &&
-          enableGetDerivedStateFromCatch &&
-          "function" === typeof ctor.getDerivedStateFromCatch &&
-          (derivedStateFromCatch = callGetDerivedStateFromCatch(
-            ctor,
-            updateQueue.capturedValues
-          ));
-      } else renderExpirationTime = oldContext;
-      ctor = void 0;
-      oldProps !== newProps &&
-        (ctor = callGetDerivedStateFromProps(
-          workInProgress,
-          instance,
-          newProps,
-          renderExpirationTime
-        ));
-      null !== ctor &&
-        void 0 !== ctor &&
-        ((renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? ctor
-            : Object.assign({}, renderExpirationTime, ctor)),
-        (updateQueue = workInProgress.updateQueue),
-        null !== updateQueue &&
-          (updateQueue.baseState = Object.assign(
-            {},
-            updateQueue.baseState,
-            ctor
-          )));
-      null !== derivedStateFromCatch &&
-        void 0 !== derivedStateFromCatch &&
-        ((renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromCatch
-            : Object.assign({}, renderExpirationTime, derivedStateFromCatch)),
-        (ctor = workInProgress.updateQueue),
-        null !== ctor &&
-          (ctor.baseState = Object.assign(
-            {},
-            ctor.baseState,
-            derivedStateFromCatch
-          )));
-      if (
-        !(
-          oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
-          hasContextChanged() ||
-          (null !== workInProgress.updateQueue &&
-            workInProgress.updateQueue.hasForceUpdate)
-        )
-      )
-        return (
-          "function" !== typeof instance.componentDidUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 4),
-          "function" !== typeof instance.getSnapshotBeforeUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
-          !1
-        );
-      (derivedStateFromCatch = checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldContext,
-        renderExpirationTime,
-        newUnmaskedContext
-      ))
-        ? (hasNewLifecycles ||
-            ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
-              "function" !== typeof instance.componentWillUpdate) ||
-            ("function" === typeof instance.componentWillUpdate &&
-              instance.componentWillUpdate(
-                newProps,
-                renderExpirationTime,
-                newUnmaskedContext
-              ),
-            "function" === typeof instance.UNSAFE_componentWillUpdate &&
-              instance.UNSAFE_componentWillUpdate(
-                newProps,
-                renderExpirationTime,
-                newUnmaskedContext
-              )),
-          "function" === typeof instance.componentDidUpdate &&
-            (workInProgress.effectTag |= 4),
-          "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 2048))
-        : ("function" !== typeof instance.componentDidUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 4),
-          "function" !== typeof instance.getSnapshotBeforeUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
-      instance.props = newProps;
-      instance.state = renderExpirationTime;
-      instance.context = newUnmaskedContext;
-      return derivedStateFromCatch;
-    }
-  };
-}
-var isArray$1 = Array.isArray;
-function coerceRef(returnFiber, current, element) {
-  returnFiber = element.ref;
-  if (
-    null !== returnFiber &&
-    "function" !== typeof returnFiber &&
-    "object" !== typeof returnFiber
-  ) {
-    if (element._owner) {
-      element = element._owner;
-      var inst = void 0;
-      element &&
-        (invariant(
-          2 === element.tag,
-          "Stateless function components cannot have refs."
-        ),
-        (inst = element.stateNode));
-      invariant(
-        inst,
-        "Missing owner for string ref %s. This error is likely caused by a bug in React. Please file an issue.",
-        returnFiber
-      );
-      var stringRef = "" + returnFiber;
-      if (
-        null !== current &&
-        null !== current.ref &&
-        current.ref._stringRef === stringRef
-      )
-        return current.ref;
-      current = function(value) {
-        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
-        null === value ? delete refs[stringRef] : (refs[stringRef] = value);
-      };
-      current._stringRef = stringRef;
-      return current;
-    }
-    invariant(
-      "string" === typeof returnFiber,
-      "Expected ref to be a function or a string."
-    );
-    invariant(
-      element._owner,
-      "Element ref was specified as a string (%s) but no owner was set. This could happen for one of the following reasons:\n1. You may be adding a ref to a functional component\n2. You may be adding a ref to a component that was not created inside a component's render method\n3. You have multiple copies of React loaded\nSee https://fb.me/react-refs-must-have-owner for more information.",
-      returnFiber
-    );
-  }
-  return returnFiber;
-}
-function throwOnInvalidObjectType(returnFiber, newChild) {
-  "textarea" !== returnFiber.type &&
-    invariant(
-      !1,
-      "Objects are not valid as a React child (found: %s).%s",
-      "[object Object]" === Object.prototype.toString.call(newChild)
-        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
-        : newChild,
-      ""
-    );
-}
-function ChildReconciler(shouldTrackSideEffects) {
-  function deleteChild(returnFiber, childToDelete) {
-    if (shouldTrackSideEffects) {
-      var last = returnFiber.lastEffect;
-      null !== last
-        ? ((last.nextEffect = childToDelete),
-          (returnFiber.lastEffect = childToDelete))
-        : (returnFiber.firstEffect = returnFiber.lastEffect = childToDelete);
-      childToDelete.nextEffect = null;
-      childToDelete.effectTag = 8;
-    }
-  }
-  function deleteRemainingChildren(returnFiber, currentFirstChild) {
-    if (!shouldTrackSideEffects) return null;
-    for (; null !== currentFirstChild; )
-      deleteChild(returnFiber, currentFirstChild),
-        (currentFirstChild = currentFirstChild.sibling);
-    return null;
-  }
-  function mapRemainingChildren(returnFiber, currentFirstChild) {
-    for (returnFiber = new Map(); null !== currentFirstChild; )
-      null !== currentFirstChild.key
-        ? returnFiber.set(currentFirstChild.key, currentFirstChild)
-        : returnFiber.set(currentFirstChild.index, currentFirstChild),
-        (currentFirstChild = currentFirstChild.sibling);
-    return returnFiber;
-  }
-  function useFiber(fiber, pendingProps, expirationTime) {
-    fiber = createWorkInProgress(fiber, pendingProps, expirationTime);
-    fiber.index = 0;
-    fiber.sibling = null;
-    return fiber;
-  }
-  function placeChild(newFiber, lastPlacedIndex, newIndex) {
-    newFiber.index = newIndex;
-    if (!shouldTrackSideEffects) return lastPlacedIndex;
-    newIndex = newFiber.alternate;
-    if (null !== newIndex)
-      return (
-        (newIndex = newIndex.index),
-        newIndex < lastPlacedIndex
-          ? ((newFiber.effectTag = 2), lastPlacedIndex)
-          : newIndex
-      );
-    newFiber.effectTag = 2;
-    return lastPlacedIndex;
-  }
-  function placeSingleChild(newFiber) {
-    shouldTrackSideEffects &&
-      null === newFiber.alternate &&
-      (newFiber.effectTag = 2);
-    return newFiber;
-  }
-  function updateTextNode(returnFiber, current, textContent, expirationTime) {
-    if (null === current || 6 !== current.tag)
-      return (
-        (current = createFiberFromText(
-          textContent,
-          returnFiber.mode,
-          expirationTime
-        )),
-        (current["return"] = returnFiber),
-        current
-      );
-    current = useFiber(current, textContent, expirationTime);
-    current["return"] = returnFiber;
-    return current;
-  }
-  function updateElement(returnFiber, current, element, expirationTime) {
-    if (null !== current && current.type === element.type)
-      return (
-        (expirationTime = useFiber(current, element.props, expirationTime)),
-        (expirationTime.ref = coerceRef(returnFiber, current, element)),
-        (expirationTime["return"] = returnFiber),
-        expirationTime
-      );
-    expirationTime = createFiberFromElement(
-      element,
-      returnFiber.mode,
-      expirationTime
-    );
-    expirationTime.ref = coerceRef(returnFiber, current, element);
-    expirationTime["return"] = returnFiber;
-    return expirationTime;
-  }
-  function updatePortal(returnFiber, current, portal, expirationTime) {
-    if (
-      null === current ||
-      4 !== current.tag ||
-      current.stateNode.containerInfo !== portal.containerInfo ||
-      current.stateNode.implementation !== portal.implementation
-    )
-      return (
-        (current = createFiberFromPortal(
-          portal,
-          returnFiber.mode,
-          expirationTime
-        )),
-        (current["return"] = returnFiber),
-        current
-      );
-    current = useFiber(current, portal.children || [], expirationTime);
-    current["return"] = returnFiber;
-    return current;
-  }
-  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
-    if (null === current || 10 !== current.tag)
-      return (
-        (current = createFiberFromFragment(
-          fragment,
-          returnFiber.mode,
-          expirationTime,
-          key
-        )),
-        (current["return"] = returnFiber),
-        current
-      );
-    current = useFiber(current, fragment, expirationTime);
-    current["return"] = returnFiber;
-    return current;
-  }
-  function createChild(returnFiber, newChild, expirationTime) {
-    if ("string" === typeof newChild || "number" === typeof newChild)
-      return (
-        (newChild = createFiberFromText(
-          "" + newChild,
-          returnFiber.mode,
-          expirationTime
-        )),
-        (newChild["return"] = returnFiber),
-        newChild
-      );
-    if ("object" === typeof newChild && null !== newChild) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return (
-            (expirationTime = createFiberFromElement(
-              newChild,
-              returnFiber.mode,
-              expirationTime
-            )),
-            (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
-            (expirationTime["return"] = returnFiber),
-            expirationTime
-          );
-        case REACT_PORTAL_TYPE:
-          return (
-            (newChild = createFiberFromPortal(
-              newChild,
-              returnFiber.mode,
-              expirationTime
-            )),
-            (newChild["return"] = returnFiber),
-            newChild
-          );
-      }
-      if (isArray$1(newChild) || getIteratorFn(newChild))
-        return (
-          (newChild = createFiberFromFragment(
-            newChild,
-            returnFiber.mode,
-            expirationTime,
-            null
-          )),
-          (newChild["return"] = returnFiber),
-          newChild
-        );
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-    return null;
-  }
-  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
-    var key = null !== oldFiber ? oldFiber.key : null;
-    if ("string" === typeof newChild || "number" === typeof newChild)
-      return null !== key
-        ? null
-        : updateTextNode(returnFiber, oldFiber, "" + newChild, expirationTime);
-    if ("object" === typeof newChild && null !== newChild) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return newChild.key === key
-            ? newChild.type === REACT_FRAGMENT_TYPE
-              ? updateFragment(
-                  returnFiber,
-                  oldFiber,
-                  newChild.props.children,
-                  expirationTime,
-                  key
-                )
-              : updateElement(returnFiber, oldFiber, newChild, expirationTime)
-            : null;
-        case REACT_PORTAL_TYPE:
-          return newChild.key === key
-            ? updatePortal(returnFiber, oldFiber, newChild, expirationTime)
-            : null;
-      }
-      if (isArray$1(newChild) || getIteratorFn(newChild))
-        return null !== key
-          ? null
-          : updateFragment(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime,
-              null
-            );
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-    return null;
-  }
-  function updateFromMap(
-    existingChildren,
-    returnFiber,
-    newIdx,
-    newChild,
-    expirationTime
-  ) {
-    if ("string" === typeof newChild || "number" === typeof newChild)
-      return (
-        (existingChildren = existingChildren.get(newIdx) || null),
-        updateTextNode(
-          returnFiber,
-          existingChildren,
-          "" + newChild,
-          expirationTime
-        )
-      );
-    if ("object" === typeof newChild && null !== newChild) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return (
-            (existingChildren =
-              existingChildren.get(
-                null === newChild.key ? newIdx : newChild.key
-              ) || null),
-            newChild.type === REACT_FRAGMENT_TYPE
-              ? updateFragment(
-                  returnFiber,
-                  existingChildren,
-                  newChild.props.children,
-                  expirationTime,
-                  newChild.key
-                )
-              : updateElement(
-                  returnFiber,
-                  existingChildren,
-                  newChild,
-                  expirationTime
-                )
-          );
-        case REACT_PORTAL_TYPE:
-          return (
-            (existingChildren =
-              existingChildren.get(
-                null === newChild.key ? newIdx : newChild.key
-              ) || null),
-            updatePortal(
-              returnFiber,
-              existingChildren,
-              newChild,
-              expirationTime
-            )
-          );
-      }
-      if (isArray$1(newChild) || getIteratorFn(newChild))
-        return (
-          (existingChildren = existingChildren.get(newIdx) || null),
-          updateFragment(
-            returnFiber,
-            existingChildren,
-            newChild,
-            expirationTime,
-            null
-          )
-        );
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
-    return null;
-  }
-  function reconcileChildrenArray(
-    returnFiber,
-    currentFirstChild,
-    newChildren,
-    expirationTime
-  ) {
-    for (
-      var resultingFirstChild = null,
-        previousNewFiber = null,
-        oldFiber = currentFirstChild,
-        newIdx = (currentFirstChild = 0),
-        nextOldFiber = null;
-      null !== oldFiber && newIdx < newChildren.length;
-      newIdx++
-    ) {
-      oldFiber.index > newIdx
-        ? ((nextOldFiber = oldFiber), (oldFiber = null))
-        : (nextOldFiber = oldFiber.sibling);
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        newChildren[newIdx],
-        expirationTime
-      );
-      if (null === newFiber) {
-        null === oldFiber && (oldFiber = nextOldFiber);
-        break;
-      }
-      shouldTrackSideEffects &&
-        oldFiber &&
-        null === newFiber.alternate &&
-        deleteChild(returnFiber, oldFiber);
-      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
-      null === previousNewFiber
-        ? (resultingFirstChild = newFiber)
-        : (previousNewFiber.sibling = newFiber);
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-    if (newIdx === newChildren.length)
-      return (
-        deleteRemainingChildren(returnFiber, oldFiber), resultingFirstChild
-      );
-    if (null === oldFiber) {
-      for (; newIdx < newChildren.length; newIdx++)
-        if (
-          (oldFiber = createChild(
-            returnFiber,
-            newChildren[newIdx],
-            expirationTime
-          ))
-        )
-          (currentFirstChild = placeChild(oldFiber, currentFirstChild, newIdx)),
-            null === previousNewFiber
-              ? (resultingFirstChild = oldFiber)
-              : (previousNewFiber.sibling = oldFiber),
-            (previousNewFiber = oldFiber);
-      return resultingFirstChild;
-    }
-    for (
-      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
-      newIdx < newChildren.length;
-      newIdx++
-    )
-      if (
-        (nextOldFiber = updateFromMap(
-          oldFiber,
-          returnFiber,
-          newIdx,
-          newChildren[newIdx],
-          expirationTime
-        ))
-      ) {
-        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
-          oldFiber["delete"](
-            null === nextOldFiber.key ? newIdx : nextOldFiber.key
-          );
-        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (resultingFirstChild = nextOldFiber)
-          : (previousNewFiber.sibling = nextOldFiber);
-        previousNewFiber = nextOldFiber;
-      }
-    shouldTrackSideEffects &&
-      oldFiber.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    return resultingFirstChild;
-  }
-  function reconcileChildrenIterator(
-    returnFiber,
-    currentFirstChild,
-    newChildrenIterable,
-    expirationTime
-  ) {
-    var iteratorFn = getIteratorFn(newChildrenIterable);
-    invariant(
-      "function" === typeof iteratorFn,
-      "An object is not an iterable. This error is likely caused by a bug in React. Please file an issue."
-    );
-    newChildrenIterable = iteratorFn.call(newChildrenIterable);
-    invariant(
-      null != newChildrenIterable,
-      "An iterable object provided no iterator."
-    );
-    for (
-      var previousNewFiber = (iteratorFn = null),
-        oldFiber = currentFirstChild,
-        newIdx = (currentFirstChild = 0),
-        nextOldFiber = null,
-        step = newChildrenIterable.next();
-      null !== oldFiber && !step.done;
-      newIdx++, step = newChildrenIterable.next()
-    ) {
-      oldFiber.index > newIdx
-        ? ((nextOldFiber = oldFiber), (oldFiber = null))
-        : (nextOldFiber = oldFiber.sibling);
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        step.value,
-        expirationTime
-      );
-      if (null === newFiber) {
-        oldFiber || (oldFiber = nextOldFiber);
-        break;
-      }
-      shouldTrackSideEffects &&
-        oldFiber &&
-        null === newFiber.alternate &&
-        deleteChild(returnFiber, oldFiber);
-      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
-      null === previousNewFiber
-        ? (iteratorFn = newFiber)
-        : (previousNewFiber.sibling = newFiber);
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-    if (step.done)
-      return deleteRemainingChildren(returnFiber, oldFiber), iteratorFn;
-    if (null === oldFiber) {
-      for (; !step.done; newIdx++, step = newChildrenIterable.next())
-        (step = createChild(returnFiber, step.value, expirationTime)),
-          null !== step &&
-            ((currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
-            null === previousNewFiber
-              ? (iteratorFn = step)
-              : (previousNewFiber.sibling = step),
-            (previousNewFiber = step));
-      return iteratorFn;
-    }
-    for (
-      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
-      !step.done;
-      newIdx++, step = newChildrenIterable.next()
-    )
-      if (
-        ((step = updateFromMap(
-          oldFiber,
-          returnFiber,
-          newIdx,
-          step.value,
-          expirationTime
-        )),
-        null !== step)
-      ) {
-        if (shouldTrackSideEffects && null !== step.alternate)
-          oldFiber["delete"](null === step.key ? newIdx : step.key);
-        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (iteratorFn = step)
-          : (previousNewFiber.sibling = step);
-        previousNewFiber = step;
-      }
-    shouldTrackSideEffects &&
-      oldFiber.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    return iteratorFn;
-  }
-  return function(returnFiber, currentFirstChild, newChild, expirationTime) {
-    "object" === typeof newChild &&
-      null !== newChild &&
-      newChild.type === REACT_FRAGMENT_TYPE &&
-      null === newChild.key &&
-      (newChild = newChild.props.children);
-    var isObject = "object" === typeof newChild && null !== newChild;
-    if (isObject)
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          a: {
-            var key = newChild.key;
-            for (isObject = currentFirstChild; null !== isObject; ) {
-              if (isObject.key === key)
-                if (
-                  10 === isObject.tag
-                    ? newChild.type === REACT_FRAGMENT_TYPE
-                    : isObject.type === newChild.type
-                ) {
-                  deleteRemainingChildren(returnFiber, isObject.sibling);
-                  currentFirstChild = useFiber(
-                    isObject,
-                    newChild.type === REACT_FRAGMENT_TYPE
-                      ? newChild.props.children
-                      : newChild.props,
-                    expirationTime
-                  );
-                  currentFirstChild.ref = coerceRef(
-                    returnFiber,
-                    isObject,
-                    newChild
-                  );
-                  currentFirstChild["return"] = returnFiber;
-                  returnFiber = currentFirstChild;
-                  break a;
-                } else {
-                  deleteRemainingChildren(returnFiber, isObject);
-                  break;
-                }
-              else deleteChild(returnFiber, isObject);
-              isObject = isObject.sibling;
-            }
-            newChild.type === REACT_FRAGMENT_TYPE
-              ? ((currentFirstChild = createFiberFromFragment(
-                  newChild.props.children,
-                  returnFiber.mode,
-                  expirationTime,
-                  newChild.key
-                )),
-                (currentFirstChild["return"] = returnFiber),
-                (returnFiber = currentFirstChild))
-              : ((expirationTime = createFiberFromElement(
-                  newChild,
-                  returnFiber.mode,
-                  expirationTime
-                )),
-                (expirationTime.ref = coerceRef(
-                  returnFiber,
-                  currentFirstChild,
-                  newChild
-                )),
-                (expirationTime["return"] = returnFiber),
-                (returnFiber = expirationTime));
-          }
-          return placeSingleChild(returnFiber);
-        case REACT_PORTAL_TYPE:
-          a: {
-            for (isObject = newChild.key; null !== currentFirstChild; ) {
-              if (currentFirstChild.key === isObject)
-                if (
-                  4 === currentFirstChild.tag &&
-                  currentFirstChild.stateNode.containerInfo ===
-                    newChild.containerInfo &&
-                  currentFirstChild.stateNode.implementation ===
-                    newChild.implementation
-                ) {
-                  deleteRemainingChildren(
-                    returnFiber,
-                    currentFirstChild.sibling
-                  );
-                  currentFirstChild = useFiber(
-                    currentFirstChild,
-                    newChild.children || [],
-                    expirationTime
-                  );
-                  currentFirstChild["return"] = returnFiber;
-                  returnFiber = currentFirstChild;
-                  break a;
-                } else {
-                  deleteRemainingChildren(returnFiber, currentFirstChild);
-                  break;
-                }
-              else deleteChild(returnFiber, currentFirstChild);
-              currentFirstChild = currentFirstChild.sibling;
-            }
-            currentFirstChild = createFiberFromPortal(
-              newChild,
-              returnFiber.mode,
-              expirationTime
-            );
-            currentFirstChild["return"] = returnFiber;
-            returnFiber = currentFirstChild;
-          }
-          return placeSingleChild(returnFiber);
-      }
-    if ("string" === typeof newChild || "number" === typeof newChild)
-      return (
-        (newChild = "" + newChild),
-        null !== currentFirstChild && 6 === currentFirstChild.tag
-          ? (deleteRemainingChildren(returnFiber, currentFirstChild.sibling),
-            (currentFirstChild = useFiber(
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )),
-            (currentFirstChild["return"] = returnFiber),
-            (returnFiber = currentFirstChild))
-          : (deleteRemainingChildren(returnFiber, currentFirstChild),
-            (currentFirstChild = createFiberFromText(
-              newChild,
-              returnFiber.mode,
-              expirationTime
-            )),
-            (currentFirstChild["return"] = returnFiber),
-            (returnFiber = currentFirstChild)),
-        placeSingleChild(returnFiber)
-      );
-    if (isArray$1(newChild))
-      return reconcileChildrenArray(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    if (getIteratorFn(newChild))
-      return reconcileChildrenIterator(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    isObject && throwOnInvalidObjectType(returnFiber, newChild);
-    if ("undefined" === typeof newChild)
-      switch (returnFiber.tag) {
-        case 2:
-        case 1:
-          (expirationTime = returnFiber.type),
-            invariant(
-              !1,
-              "%s(...): Nothing was returned from render. This usually means a return statement is missing. Or, to render nothing, return null.",
-              expirationTime.displayName || expirationTime.name || "Component"
-            );
-      }
-    return deleteRemainingChildren(returnFiber, currentFirstChild);
-  };
-}
-var reconcileChildFibers = ChildReconciler(!0),
-  mountChildFibers = ChildReconciler(!1);
-function ReactFiberBeginWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  scheduleWork,
-  computeExpirationForFiber
-) {
-  function reconcileChildren(current, workInProgress, nextChildren) {
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      workInProgress.expirationTime
-    );
-  }
-  function reconcileChildrenAtExpirationTime(
-    current,
-    workInProgress,
-    nextChildren,
-    renderExpirationTime
-  ) {
-    workInProgress.child =
-      null === current
-        ? mountChildFibers(
-            workInProgress,
-            null,
-            nextChildren,
-            renderExpirationTime
-          )
-        : reconcileChildFibers(
-            workInProgress,
-            current.child,
-            nextChildren,
-            renderExpirationTime
-          );
-  }
-  function markRef(current, workInProgress) {
-    var ref = workInProgress.ref;
-    if (
-      (null === current && null !== ref) ||
-      (null !== current && current.ref !== ref)
-    )
-      workInProgress.effectTag |= 128;
-  }
-  function finishClassComponent(
-    current,
-    workInProgress,
-    shouldUpdate,
-    hasContext,
-    didCaptureError,
-    renderExpirationTime
-  ) {
-    markRef(current, workInProgress);
-    if (!shouldUpdate && !didCaptureError)
-      return (
-        hasContext && invalidateContextProvider(workInProgress, !1),
-        bailoutOnAlreadyFinishedWork(current, workInProgress)
-      );
-    var ctor = workInProgress.type;
-    shouldUpdate = workInProgress.stateNode;
-    ReactCurrentOwner.current = workInProgress;
-    !didCaptureError ||
-    (enableGetDerivedStateFromCatch &&
-      "function" === typeof ctor.getDerivedStateFromCatch)
-      ? ((debugRenderPhaseSideEffects ||
-          (debugRenderPhaseSideEffectsForStrictMode &&
-            workInProgress.mode & 2)) &&
-          shouldUpdate.render(),
-        (ctor = shouldUpdate.render()))
-      : (ctor = null);
-    workInProgress.effectTag |= 1;
-    didCaptureError &&
-      (reconcileChildrenAtExpirationTime(
-        current,
-        workInProgress,
-        null,
-        renderExpirationTime
-      ),
-      (workInProgress.child = null));
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      ctor,
-      renderExpirationTime
-    );
-    workInProgress.memoizedState = shouldUpdate.state;
-    workInProgress.memoizedProps = shouldUpdate.props;
-    hasContext && invalidateContextProvider(workInProgress, !0);
-    return workInProgress.child;
-  }
-  function pushHostRootContext(workInProgress) {
-    var root = workInProgress.stateNode;
-    root.pendingContext
-      ? pushTopLevelContextObject(
-          workInProgress,
-          root.pendingContext,
-          root.pendingContext !== root.context
-        )
-      : root.context &&
-        pushTopLevelContextObject(workInProgress, root.context, !1);
-    pushHostContainer(workInProgress, root.containerInfo);
-  }
-  function propagateContextChange(
-    workInProgress,
-    context,
-    changedBits,
-    renderExpirationTime
-  ) {
-    var fiber = workInProgress.child;
-    for (
-      null !== fiber && (fiber["return"] = workInProgress);
-      null !== fiber;
-
-    ) {
-      switch (fiber.tag) {
-        case 12:
-          var nextFiber = fiber.stateNode | 0;
-          if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
-            for (nextFiber = fiber; null !== nextFiber; ) {
-              var alternate = nextFiber.alternate;
-              if (
-                0 === nextFiber.expirationTime ||
-                nextFiber.expirationTime > renderExpirationTime
-              )
-                (nextFiber.expirationTime = renderExpirationTime),
-                  null !== alternate &&
-                    (0 === alternate.expirationTime ||
-                      alternate.expirationTime > renderExpirationTime) &&
-                    (alternate.expirationTime = renderExpirationTime);
-              else if (
-                null !== alternate &&
-                (0 === alternate.expirationTime ||
-                  alternate.expirationTime > renderExpirationTime)
-              )
-                alternate.expirationTime = renderExpirationTime;
-              else break;
-              nextFiber = nextFiber["return"];
-            }
-            nextFiber = null;
-          } else nextFiber = fiber.child;
-          break;
-        case 13:
-          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
-          break;
-        default:
-          nextFiber = fiber.child;
-      }
-      if (null !== nextFiber) nextFiber["return"] = fiber;
-      else
-        for (nextFiber = fiber; null !== nextFiber; ) {
-          if (nextFiber === workInProgress) {
-            nextFiber = null;
-            break;
-          }
-          fiber = nextFiber.sibling;
-          if (null !== fiber) {
-            nextFiber = fiber;
-            break;
-          }
-          nextFiber = nextFiber["return"];
-        }
-      fiber = nextFiber;
-    }
-  }
-  function updateContextProvider(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var context = workInProgress.type._context,
-      newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps;
-    if (!hasLegacyContextChanged() && oldProps === newProps)
-      return (
-        (workInProgress.stateNode = 0),
-        pushProvider(workInProgress),
-        bailoutOnAlreadyFinishedWork(current, workInProgress)
-      );
-    var newValue = newProps.value;
-    workInProgress.memoizedProps = newProps;
-    if (null === oldProps) newValue = 1073741823;
-    else if (oldProps.value === newProps.value) {
-      if (oldProps.children === newProps.children)
-        return (
-          (workInProgress.stateNode = 0),
-          pushProvider(workInProgress),
-          bailoutOnAlreadyFinishedWork(current, workInProgress)
-        );
-      newValue = 0;
-    } else {
-      var oldValue = oldProps.value;
-      if (
-        (oldValue === newValue &&
-          (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
-        (oldValue !== oldValue && newValue !== newValue)
-      ) {
-        if (oldProps.children === newProps.children)
-          return (
-            (workInProgress.stateNode = 0),
-            pushProvider(workInProgress),
-            bailoutOnAlreadyFinishedWork(current, workInProgress)
-          );
-        newValue = 0;
-      } else if (
-        ((newValue =
-          "function" === typeof context._calculateChangedBits
-            ? context._calculateChangedBits(oldValue, newValue)
-            : 1073741823),
-        (newValue |= 0),
-        0 === newValue)
-      ) {
-        if (oldProps.children === newProps.children)
-          return (
-            (workInProgress.stateNode = 0),
-            pushProvider(workInProgress),
-            bailoutOnAlreadyFinishedWork(current, workInProgress)
-          );
-      } else
-        propagateContextChange(
-          workInProgress,
-          context,
-          newValue,
-          renderExpirationTime
-        );
-    }
-    workInProgress.stateNode = newValue;
-    pushProvider(workInProgress);
-    reconcileChildren(current, workInProgress, newProps.children);
-    return workInProgress.child;
-  }
-  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
-    invariant(
-      null === current || workInProgress.child === current.child,
-      "Resuming work not yet implemented."
-    );
-    if (null !== workInProgress.child) {
-      current = workInProgress.child;
-      var newChild = createWorkInProgress(
-        current,
-        current.pendingProps,
-        current.expirationTime
-      );
-      workInProgress.child = newChild;
-      for (newChild["return"] = workInProgress; null !== current.sibling; )
-        (current = current.sibling),
-          (newChild = newChild.sibling = createWorkInProgress(
-            current,
-            current.pendingProps,
-            current.expirationTime
-          )),
-          (newChild["return"] = workInProgress);
-      newChild.sibling = null;
-    }
-    return workInProgress.child;
-  }
-  var shouldSetTextContent = config.shouldSetTextContent,
-    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree,
-    pushHostContext = hostContext.pushHostContext,
-    pushHostContainer = hostContext.pushHostContainer,
-    pushProvider = newContext.pushProvider,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    hasLegacyContextChanged = legacyContext.hasContextChanged,
-    pushLegacyContextProvider = legacyContext.pushContextProvider,
-    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
-    invalidateContextProvider = legacyContext.invalidateContextProvider,
-    enterHydrationState = hydrationContext.enterHydrationState,
-    resetHydrationState = hydrationContext.resetHydrationState,
-    tryToClaimNextHydratableInstance =
-      hydrationContext.tryToClaimNextHydratableInstance;
-  config = ReactFiberClassComponent(
-    legacyContext,
-    scheduleWork,
-    computeExpirationForFiber,
-    function(workInProgress, nextProps) {
-      workInProgress.memoizedProps = nextProps;
-    },
-    function(workInProgress, nextState) {
-      workInProgress.memoizedState = nextState;
-    }
-  );
-  var adoptClassInstance = config.adoptClassInstance,
-    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
-    constructClassInstance = config.constructClassInstance,
-    mountClassInstance = config.mountClassInstance,
-    resumeMountClassInstance = config.resumeMountClassInstance,
-    updateClassInstance = config.updateClassInstance;
-  return {
-    beginWork: function(current, workInProgress, renderExpirationTime) {
-      if (
-        0 === workInProgress.expirationTime ||
-        workInProgress.expirationTime > renderExpirationTime
-      ) {
-        switch (workInProgress.tag) {
-          case 3:
-            pushHostRootContext(workInProgress);
-            break;
-          case 2:
-            pushLegacyContextProvider(workInProgress);
-            break;
-          case 4:
-            pushHostContainer(
-              workInProgress,
-              workInProgress.stateNode.containerInfo
-            );
-            break;
-          case 13:
-            pushProvider(workInProgress);
-        }
-        return null;
-      }
-      switch (workInProgress.tag) {
-        case 0:
-          invariant(
-            null === current,
-            "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
-          );
-          var fn = workInProgress.type,
-            props = workInProgress.pendingProps,
-            unmaskedContext = getUnmaskedContext(workInProgress);
-          unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
-          fn = fn(props, unmaskedContext);
-          workInProgress.effectTag |= 1;
-          "object" === typeof fn &&
-          null !== fn &&
-          "function" === typeof fn.render &&
-          void 0 === fn.$$typeof
-            ? ((unmaskedContext = workInProgress.type),
-              (workInProgress.tag = 2),
-              (workInProgress.memoizedState =
-                null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
-                ((props = callGetDerivedStateFromProps(
-                  workInProgress,
-                  fn,
-                  props,
-                  workInProgress.memoizedState
-                )),
-                null !== props &&
-                  void 0 !== props &&
-                  (workInProgress.memoizedState = Object.assign(
-                    {},
-                    workInProgress.memoizedState,
-                    props
-                  ))),
-              (props = pushLegacyContextProvider(workInProgress)),
-              adoptClassInstance(workInProgress, fn),
-              mountClassInstance(workInProgress, renderExpirationTime),
-              (current = finishClassComponent(
-                current,
-                workInProgress,
-                !0,
-                props,
-                !1,
-                renderExpirationTime
-              )))
-            : ((workInProgress.tag = 1),
-              reconcileChildren(current, workInProgress, fn),
-              (workInProgress.memoizedProps = props),
-              (current = workInProgress.child));
-          return current;
-        case 1:
-          return (
-            (props = workInProgress.type),
-            (renderExpirationTime = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime
-              ? ((fn = getUnmaskedContext(workInProgress)),
-                (fn = getMaskedContext(workInProgress, fn)),
-                (props = props(renderExpirationTime, fn)),
-                (workInProgress.effectTag |= 1),
-                reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 2:
-          props = pushLegacyContextProvider(workInProgress);
-          null === current
-            ? null === workInProgress.stateNode
-              ? (constructClassInstance(
-                  workInProgress,
-                  workInProgress.pendingProps
-                ),
-                mountClassInstance(workInProgress, renderExpirationTime),
-                (fn = !0))
-              : (fn = resumeMountClassInstance(
-                  workInProgress,
-                  renderExpirationTime
-                ))
-            : (fn = updateClassInstance(
-                current,
-                workInProgress,
-                renderExpirationTime
-              ));
-          unmaskedContext = !1;
-          var updateQueue = workInProgress.updateQueue;
-          null !== updateQueue &&
-            null !== updateQueue.capturedValues &&
-            (unmaskedContext = fn = !0);
-          return finishClassComponent(
-            current,
-            workInProgress,
-            fn,
-            props,
-            unmaskedContext,
-            renderExpirationTime
-          );
-        case 3:
-          a: if (
-            (pushHostRootContext(workInProgress),
-            (fn = workInProgress.updateQueue),
-            null !== fn)
-          ) {
-            unmaskedContext = workInProgress.memoizedState;
-            props = processUpdateQueue(
-              current,
-              workInProgress,
-              fn,
-              null,
-              null,
-              renderExpirationTime
-            );
-            workInProgress.memoizedState = props;
-            fn = workInProgress.updateQueue;
-            if (null !== fn && null !== fn.capturedValues) fn = null;
-            else if (unmaskedContext === props) {
-              resetHydrationState();
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-              break a;
-            } else fn = props.element;
-            unmaskedContext = workInProgress.stateNode;
-            (null === current || null === current.child) &&
-            unmaskedContext.hydrate &&
-            enterHydrationState(workInProgress)
-              ? ((workInProgress.effectTag |= 2),
-                (workInProgress.child = mountChildFibers(
-                  workInProgress,
-                  null,
-                  fn,
-                  renderExpirationTime
-                )))
-              : (resetHydrationState(),
-                reconcileChildren(current, workInProgress, fn));
-            workInProgress.memoizedState = props;
-            current = workInProgress.child;
-          } else
-            resetHydrationState(),
-              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
-          return current;
-        case 5:
-          a: {
-            pushHostContext(workInProgress);
-            null === current &&
-              tryToClaimNextHydratableInstance(workInProgress);
-            props = workInProgress.type;
-            updateQueue = workInProgress.memoizedProps;
-            fn = workInProgress.pendingProps;
-            unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && updateQueue === fn) {
-              if (
-                (updateQueue =
-                  workInProgress.mode & 1 &&
-                  shouldDeprioritizeSubtree(props, fn))
-              )
-                workInProgress.expirationTime = 1073741823;
-              if (!updateQueue || 1073741823 !== renderExpirationTime) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-            }
-            updateQueue = fn.children;
-            shouldSetTextContent(props, fn)
-              ? (updateQueue = null)
-              : unmaskedContext &&
-                shouldSetTextContent(props, unmaskedContext) &&
-                (workInProgress.effectTag |= 16);
-            markRef(current, workInProgress);
-            1073741823 !== renderExpirationTime &&
-            workInProgress.mode & 1 &&
-            shouldDeprioritizeSubtree(props, fn)
-              ? ((workInProgress.expirationTime = 1073741823),
-                (workInProgress.memoizedProps = fn),
-                (current = null))
-              : (reconcileChildren(current, workInProgress, updateQueue),
-                (workInProgress.memoizedProps = fn),
-                (current = workInProgress.child));
-          }
-          return current;
-        case 6:
-          return (
-            null === current &&
-              tryToClaimNextHydratableInstance(workInProgress),
-            (workInProgress.memoizedProps = workInProgress.pendingProps),
-            null
-          );
-        case 8:
-          workInProgress.tag = 7;
-        case 7:
-          return (
-            (props = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-              workInProgress.memoizedProps !== props ||
-              (props = workInProgress.memoizedProps),
-            (fn = props.children),
-            (workInProgress.stateNode =
-              null === current
-                ? mountChildFibers(
-                    workInProgress,
-                    workInProgress.stateNode,
-                    fn,
-                    renderExpirationTime
-                  )
-                : reconcileChildFibers(
-                    workInProgress,
-                    current.stateNode,
-                    fn,
-                    renderExpirationTime
-                  )),
-            (workInProgress.memoizedProps = props),
-            workInProgress.stateNode
-          );
-        case 9:
-          return null;
-        case 4:
-          return (
-            pushHostContainer(
-              workInProgress,
-              workInProgress.stateNode.containerInfo
-            ),
-            (props = workInProgress.pendingProps),
-            hasLegacyContextChanged() || workInProgress.memoizedProps !== props
-              ? (null === current
-                  ? (workInProgress.child = reconcileChildFibers(
-                      workInProgress,
-                      null,
-                      props,
-                      renderExpirationTime
-                    ))
-                  : reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = props),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 14:
-          return (
-            (renderExpirationTime = workInProgress.type.render),
-            (renderExpirationTime = renderExpirationTime(
-              workInProgress.pendingProps,
-              workInProgress.ref
-            )),
-            reconcileChildren(current, workInProgress, renderExpirationTime),
-            (workInProgress.memoizedProps = renderExpirationTime),
-            workInProgress.child
-          );
-        case 10:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime
-              ? (reconcileChildren(
-                  current,
-                  workInProgress,
-                  renderExpirationTime
-                ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 11:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps.children),
-            hasLegacyContextChanged() ||
-            (null !== renderExpirationTime &&
-              workInProgress.memoizedProps !== renderExpirationTime)
-              ? (reconcileChildren(
-                  current,
-                  workInProgress,
-                  renderExpirationTime
-                ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 13:
-          return updateContextProvider(
-            current,
-            workInProgress,
-            renderExpirationTime
-          );
-        case 12:
-          a: {
-            fn = workInProgress.type;
-            unmaskedContext = workInProgress.pendingProps;
-            updateQueue = workInProgress.memoizedProps;
-            props = fn._currentValue;
-            var changedBits = fn._changedBits;
-            if (
-              hasLegacyContextChanged() ||
-              0 !== changedBits ||
-              updateQueue !== unmaskedContext
-            ) {
-              workInProgress.memoizedProps = unmaskedContext;
-              var observedBits = unmaskedContext.unstable_observedBits;
-              if (void 0 === observedBits || null === observedBits)
-                observedBits = 1073741823;
-              workInProgress.stateNode = observedBits;
-              if (0 !== (changedBits & observedBits))
-                propagateContextChange(
-                  workInProgress,
-                  fn,
-                  changedBits,
-                  renderExpirationTime
-                );
-              else if (updateQueue === unmaskedContext) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-              renderExpirationTime = unmaskedContext.children;
-              renderExpirationTime = renderExpirationTime(props);
-              reconcileChildren(current, workInProgress, renderExpirationTime);
-              current = workInProgress.child;
-            } else
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
-          return current;
-        default:
-          invariant(
-            !1,
-            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    }
-  };
-}
-function ReactFiberCompleteWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext
-) {
-  function markUpdate(workInProgress) {
-    workInProgress.effectTag |= 4;
-  }
-  var createInstance = config.createInstance,
-    createTextInstance = config.createTextInstance,
-    appendInitialChild = config.appendInitialChild,
-    finalizeInitialChildren = config.finalizeInitialChildren,
-    prepareUpdate = config.prepareUpdate,
-    persistence = config.persistence,
-    getRootHostContainer = hostContext.getRootHostContainer,
-    popHostContext = hostContext.popHostContext,
-    getHostContext = hostContext.getHostContext,
-    popHostContainer = hostContext.popHostContainer,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider,
-    prepareToHydrateHostInstance =
-      hydrationContext.prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance =
-      hydrationContext.prepareToHydrateHostTextInstance,
-    popHydrationState = hydrationContext.popHydrationState,
-    updateHostContainer = void 0,
-    updateHostComponent = void 0,
-    updateHostText = void 0;
-  config.mutation
-    ? ((updateHostContainer = function() {}),
-      (updateHostComponent = function(current, workInProgress, updatePayload) {
-        (workInProgress.updateQueue = updatePayload) &&
-          markUpdate(workInProgress);
-      }),
-      (updateHostText = function(current, workInProgress, oldText, newText) {
-        oldText !== newText && markUpdate(workInProgress);
-      }))
-    : persistence
-      ? invariant(!1, "Persistent reconciler is disabled.")
-      : invariant(!1, "Noop reconciler is disabled.");
-  return {
-    completeWork: function(current, workInProgress, renderExpirationTime) {
-      var newProps = workInProgress.pendingProps;
-      switch (workInProgress.tag) {
-        case 1:
-          return null;
-        case 2:
-          return (
-            popLegacyContextProvider(workInProgress),
-            (current = workInProgress.stateNode),
-            (newProps = workInProgress.updateQueue),
-            null !== newProps &&
-              null !== newProps.capturedValues &&
-              ((workInProgress.effectTag &= -65),
-              "function" === typeof current.componentDidCatch
-                ? (workInProgress.effectTag |= 256)
-                : (newProps.capturedValues = null)),
-            null
-          );
-        case 3:
-          popHostContainer(workInProgress);
-          popTopLevelLegacyContextObject(workInProgress);
-          newProps = workInProgress.stateNode;
-          newProps.pendingContext &&
-            ((newProps.context = newProps.pendingContext),
-            (newProps.pendingContext = null));
-          if (null === current || null === current.child)
-            popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
-          updateHostContainer(workInProgress);
-          current = workInProgress.updateQueue;
-          null !== current &&
-            null !== current.capturedValues &&
-            (workInProgress.effectTag |= 256);
-          return null;
-        case 5:
-          popHostContext(workInProgress);
-          renderExpirationTime = getRootHostContainer();
-          var type = workInProgress.type;
-          if (null !== current && null != workInProgress.stateNode) {
-            var oldProps = current.memoizedProps,
-              _instance = workInProgress.stateNode,
-              currentHostContext = getHostContext();
-            _instance = prepareUpdate(
-              _instance,
-              type,
-              oldProps,
-              newProps,
-              renderExpirationTime,
-              currentHostContext
-            );
-            updateHostComponent(
-              current,
-              workInProgress,
-              _instance,
-              type,
-              oldProps,
-              newProps,
-              renderExpirationTime,
-              currentHostContext
-            );
-            current.ref !== workInProgress.ref &&
-              (workInProgress.effectTag |= 128);
-          } else {
-            if (!newProps)
-              return (
-                invariant(
-                  null !== workInProgress.stateNode,
-                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
-                ),
-                null
-              );
-            current = getHostContext();
-            if (popHydrationState(workInProgress))
-              prepareToHydrateHostInstance(
-                workInProgress,
-                renderExpirationTime,
-                current
-              ) && markUpdate(workInProgress);
-            else {
-              oldProps = createInstance(
-                type,
-                newProps,
-                renderExpirationTime,
-                current,
-                workInProgress
-              );
-              a: for (
-                currentHostContext = workInProgress.child;
-                null !== currentHostContext;
-
-              ) {
-                if (
-                  5 === currentHostContext.tag ||
-                  6 === currentHostContext.tag
-                )
-                  appendInitialChild(oldProps, currentHostContext.stateNode);
-                else if (
-                  4 !== currentHostContext.tag &&
-                  null !== currentHostContext.child
-                ) {
-                  currentHostContext.child["return"] = currentHostContext;
-                  currentHostContext = currentHostContext.child;
-                  continue;
-                }
-                if (currentHostContext === workInProgress) break;
-                for (; null === currentHostContext.sibling; ) {
-                  if (
-                    null === currentHostContext["return"] ||
-                    currentHostContext["return"] === workInProgress
-                  )
-                    break a;
-                  currentHostContext = currentHostContext["return"];
-                }
-                currentHostContext.sibling["return"] =
-                  currentHostContext["return"];
-                currentHostContext = currentHostContext.sibling;
-              }
-              finalizeInitialChildren(
-                oldProps,
-                type,
-                newProps,
-                renderExpirationTime,
-                current
-              ) && markUpdate(workInProgress);
-              workInProgress.stateNode = oldProps;
-            }
-            null !== workInProgress.ref && (workInProgress.effectTag |= 128);
-          }
-          return null;
-        case 6:
-          if (current && null != workInProgress.stateNode)
-            updateHostText(
-              current,
-              workInProgress,
-              current.memoizedProps,
-              newProps
-            );
-          else {
-            if ("string" !== typeof newProps)
-              return (
-                invariant(
-                  null !== workInProgress.stateNode,
-                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
-                ),
-                null
-              );
-            current = getRootHostContainer();
-            renderExpirationTime = getHostContext();
-            popHydrationState(workInProgress)
-              ? prepareToHydrateHostTextInstance(workInProgress) &&
-                markUpdate(workInProgress)
-              : (workInProgress.stateNode = createTextInstance(
-                  newProps,
-                  current,
-                  renderExpirationTime,
-                  workInProgress
-                ));
-          }
-          return null;
-        case 7:
-          newProps = workInProgress.memoizedProps;
-          invariant(
-            newProps,
-            "Should be resolved by now. This error is likely caused by a bug in React. Please file an issue."
-          );
-          workInProgress.tag = 8;
-          type = [];
-          a: for (
-            (oldProps = workInProgress.stateNode) &&
-            (oldProps["return"] = workInProgress);
-            null !== oldProps;
-
-          ) {
-            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
-              invariant(!1, "A call cannot have host component children.");
-            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
-            else if (null !== oldProps.child) {
-              oldProps.child["return"] = oldProps;
-              oldProps = oldProps.child;
-              continue;
-            }
-            for (; null === oldProps.sibling; ) {
-              if (
-                null === oldProps["return"] ||
-                oldProps["return"] === workInProgress
-              )
-                break a;
-              oldProps = oldProps["return"];
-            }
-            oldProps.sibling["return"] = oldProps["return"];
-            oldProps = oldProps.sibling;
-          }
-          oldProps = newProps.handler;
-          newProps = oldProps(newProps.props, type);
-          workInProgress.child = reconcileChildFibers(
-            workInProgress,
-            null !== current ? current.child : null,
-            newProps,
-            renderExpirationTime
-          );
-          return workInProgress.child;
-        case 8:
-          return (workInProgress.tag = 7), null;
-        case 9:
-          return null;
-        case 14:
-          return null;
-        case 10:
-          return null;
-        case 11:
-          return null;
-        case 4:
-          return (
-            popHostContainer(workInProgress),
-            updateHostContainer(workInProgress),
-            null
-          );
-        case 13:
-          return popProvider(workInProgress), null;
-        case 12:
-          return null;
-        case 0:
-          invariant(
-            !1,
-            "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
-          );
-        default:
-          invariant(
-            !1,
-            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    }
-  };
-}
-function ReactFiberUnwindWork(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
-  return {
-    throwException: function(returnFiber, sourceFiber, rawValue) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      sourceFiber = {
-        value: rawValue,
-        source: sourceFiber,
-        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-      };
-      do {
-        switch (returnFiber.tag) {
-          case 3:
-            ensureUpdateQueues(returnFiber);
-            returnFiber.updateQueue.capturedValues = [sourceFiber];
-            returnFiber.effectTag |= 1024;
-            return;
-          case 2:
-            rawValue = returnFiber.type;
-            var _instance = returnFiber.stateNode;
-            if (
-              0 === (returnFiber.effectTag & 64) &&
-              (("function" === typeof rawValue.getDerivedStateFromCatch &&
-                enableGetDerivedStateFromCatch) ||
-                (null !== _instance &&
-                  "function" === typeof _instance.componentDidCatch &&
-                  !isAlreadyFailedLegacyErrorBoundary(_instance)))
-            ) {
-              ensureUpdateQueues(returnFiber);
-              rawValue = returnFiber.updateQueue;
-              _instance = rawValue.capturedValues;
-              null === _instance
-                ? (rawValue.capturedValues = [sourceFiber])
-                : _instance.push(sourceFiber);
-              returnFiber.effectTag |= 1024;
-              return;
-            }
-        }
-        returnFiber = returnFiber["return"];
-      } while (null !== returnFiber);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
-      }
-    }
-  };
-}
-function logError(boundary, errorInfo) {
-  var source = errorInfo.source,
-    stack = errorInfo.stack;
-  null === stack && (stack = getStackAddendumByWorkInProgressFiber(source));
-  null !== source && getComponentName(source);
-  source = null !== stack ? stack : "";
-  errorInfo = errorInfo.value;
-  null !== boundary && 2 === boundary.tag && getComponentName(boundary);
-  try {
-    if (errorInfo instanceof Error) {
-      var message = errorInfo.message,
-        name = errorInfo.name;
-      var errorToHandle = errorInfo;
-      try {
-        errorToHandle.message =
-          (message ? name + ": " + message : name) +
-          "\n\nThis error is located at:" +
-          source;
-      } catch (e) {}
-    } else
-      errorToHandle =
-        "string" === typeof errorInfo
-          ? Error(errorInfo + "\n\nThis error is located at:" + source)
-          : Error("Unspecified error at:" + source);
-    ExceptionsManager.handleException(errorToHandle, !1);
-  } catch (e) {
-    (e && e.suppressReactErrorLogging) || console.error(e);
-  }
-}
-function ReactFiberCommitWork(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed
-) {
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (null !== ref)
-      if ("function" === typeof ref)
-        try {
-          ref(null);
-        } catch (refError) {
-          captureError(current, refError);
-        }
-      else ref.current = null;
-  }
-  function commitUnmount(current) {
-    "function" === typeof onCommitUnmount && onCommitUnmount(current);
-    switch (current.tag) {
-      case 2:
-        safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if ("function" === typeof _instance7.componentWillUnmount)
-          try {
-            (_instance7.props = current.memoizedProps),
-              (_instance7.state = current.memoizedState),
-              _instance7.componentWillUnmount();
-          } catch (unmountError) {
-            captureError(current, unmountError);
-          }
-        break;
-      case 5:
-        safelyDetachRef(current);
-        break;
-      case 7:
-        commitNestedUnmounts(current.stateNode);
-        break;
-      case 4:
-        mutation && unmountHostComponents(current);
-    }
-  }
-  function commitNestedUnmounts(root) {
-    for (var node = root; ; )
-      if (
-        (commitUnmount(node),
-        null === node.child || (mutation && 4 === node.tag))
-      ) {
-        if (node === root) break;
-        for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === root) return;
-          node = node["return"];
-        }
-        node.sibling["return"] = node["return"];
-        node = node.sibling;
-      } else (node.child["return"] = node), (node = node.child);
-  }
-  function isHostParent(fiber) {
-    return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
-  }
-  function unmountHostComponents(current) {
-    for (
-      var node = current,
-        currentParentIsValid = !1,
-        currentParent = void 0,
-        currentParentIsContainer = void 0;
-      ;
-
-    ) {
-      if (!currentParentIsValid) {
-        currentParentIsValid = node["return"];
-        a: for (;;) {
-          invariant(
-            null !== currentParentIsValid,
-            "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
-          );
-          switch (currentParentIsValid.tag) {
-            case 5:
-              currentParent = currentParentIsValid.stateNode;
-              currentParentIsContainer = !1;
-              break a;
-            case 3:
-              currentParent = currentParentIsValid.stateNode.containerInfo;
-              currentParentIsContainer = !0;
-              break a;
-            case 4:
-              currentParent = currentParentIsValid.stateNode.containerInfo;
-              currentParentIsContainer = !0;
-              break a;
-          }
-          currentParentIsValid = currentParentIsValid["return"];
-        }
-        currentParentIsValid = !0;
-      }
-      if (5 === node.tag || 6 === node.tag)
-        commitNestedUnmounts(node),
-          currentParentIsContainer
-            ? removeChildFromContainer(currentParent, node.stateNode)
-            : removeChild(currentParent, node.stateNode);
-      else if (
-        (4 === node.tag
-          ? (currentParent = node.stateNode.containerInfo)
-          : commitUnmount(node),
-        null !== node.child)
-      ) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === current) break;
-      for (; null === node.sibling; ) {
-        if (null === node["return"] || node["return"] === current) return;
-        node = node["return"];
-        4 === node.tag && (currentParentIsValid = !1);
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation;
-  config = config.persistence;
-  mutation ||
-    (config
-      ? invariant(!1, "Persistent reconciler is disabled.")
-      : invariant(!1, "Noop reconciler is disabled."));
-  var commitMount = mutation.commitMount,
-    commitUpdate = mutation.commitUpdate,
-    resetTextContent = mutation.resetTextContent,
-    commitTextUpdate = mutation.commitTextUpdate,
-    appendChild = mutation.appendChild,
-    appendChildToContainer = mutation.appendChildToContainer,
-    insertBefore = mutation.insertBefore,
-    insertInContainerBefore = mutation.insertInContainerBefore,
-    removeChild = mutation.removeChild,
-    removeChildFromContainer = mutation.removeChildFromContainer;
-  return {
-    commitBeforeMutationLifeCycles: function(current, finishedWork) {
-      switch (finishedWork.tag) {
-        case 2:
-          if (finishedWork.effectTag & 2048 && null !== current) {
-            var prevProps = current.memoizedProps,
-              prevState = current.memoizedState;
-            current = finishedWork.stateNode;
-            current.props = finishedWork.memoizedProps;
-            current.state = finishedWork.memoizedState;
-            finishedWork = current.getSnapshotBeforeUpdate(
-              prevProps,
-              prevState
-            );
-            current.__reactInternalSnapshotBeforeUpdate = finishedWork;
-          }
-          break;
-        case 3:
-        case 5:
-        case 6:
-        case 4:
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitResetTextContent: function(current) {
-      resetTextContent(current.stateNode);
-    },
-    commitPlacement: function(finishedWork) {
-      a: {
-        for (var parent = finishedWork["return"]; null !== parent; ) {
-          if (isHostParent(parent)) {
-            var parentFiber = parent;
-            break a;
-          }
-          parent = parent["return"];
-        }
-        invariant(
-          !1,
-          "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
-        );
-        parentFiber = void 0;
-      }
-      var isContainer = (parent = void 0);
-      switch (parentFiber.tag) {
-        case 5:
-          parent = parentFiber.stateNode;
-          isContainer = !1;
-          break;
-        case 3:
-          parent = parentFiber.stateNode.containerInfo;
-          isContainer = !0;
-          break;
-        case 4:
-          parent = parentFiber.stateNode.containerInfo;
-          isContainer = !0;
-          break;
-        default:
-          invariant(
-            !1,
-            "Invalid host parent fiber. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-      parentFiber.effectTag & 16 &&
-        (resetTextContent(parent), (parentFiber.effectTag &= -17));
-      a: b: for (parentFiber = finishedWork; ; ) {
-        for (; null === parentFiber.sibling; ) {
-          if (
-            null === parentFiber["return"] ||
-            isHostParent(parentFiber["return"])
-          ) {
-            parentFiber = null;
-            break a;
-          }
-          parentFiber = parentFiber["return"];
-        }
-        parentFiber.sibling["return"] = parentFiber["return"];
-        for (
-          parentFiber = parentFiber.sibling;
-          5 !== parentFiber.tag && 6 !== parentFiber.tag;
-
-        ) {
-          if (parentFiber.effectTag & 2) continue b;
-          if (null === parentFiber.child || 4 === parentFiber.tag) continue b;
-          else
-            (parentFiber.child["return"] = parentFiber),
-              (parentFiber = parentFiber.child);
-        }
-        if (!(parentFiber.effectTag & 2)) {
-          parentFiber = parentFiber.stateNode;
-          break a;
-        }
-      }
-      for (var node = finishedWork; ; ) {
-        if (5 === node.tag || 6 === node.tag)
-          parentFiber
-            ? isContainer
-              ? insertInContainerBefore(parent, node.stateNode, parentFiber)
-              : insertBefore(parent, node.stateNode, parentFiber)
-            : isContainer
-              ? appendChildToContainer(parent, node.stateNode)
-              : appendChild(parent, node.stateNode);
-        else if (4 !== node.tag && null !== node.child) {
-          node.child["return"] = node;
-          node = node.child;
-          continue;
-        }
-        if (node === finishedWork) break;
-        for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === finishedWork)
-            return;
-          node = node["return"];
-        }
-        node.sibling["return"] = node["return"];
-        node = node.sibling;
-      }
-    },
-    commitDeletion: function(current) {
-      unmountHostComponents(current);
-      current["return"] = null;
-      current.child = null;
-      current.alternate &&
-        ((current.alternate.child = null),
-        (current.alternate["return"] = null));
-    },
-    commitWork: function(current, finishedWork) {
-      switch (finishedWork.tag) {
-        case 2:
-          break;
-        case 5:
-          var _instance8 = finishedWork.stateNode;
-          if (null != _instance8) {
-            var newProps = finishedWork.memoizedProps;
-            current = null !== current ? current.memoizedProps : newProps;
-            var type = finishedWork.type,
-              updatePayload = finishedWork.updateQueue;
-            finishedWork.updateQueue = null;
-            null !== updatePayload &&
-              commitUpdate(
-                _instance8,
-                updatePayload,
-                type,
-                current,
-                newProps,
-                finishedWork
-              );
-          }
-          break;
-        case 6:
-          invariant(
-            null !== finishedWork.stateNode,
-            "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
-          );
-          _instance8 = finishedWork.memoizedProps;
-          commitTextUpdate(
-            finishedWork.stateNode,
-            null !== current ? current.memoizedProps : _instance8,
-            _instance8
-          );
-          break;
-        case 3:
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitLifeCycles: function(finishedRoot, current, finishedWork) {
-      switch (finishedWork.tag) {
-        case 2:
-          finishedRoot = finishedWork.stateNode;
-          if (finishedWork.effectTag & 4)
-            if (null === current)
-              (finishedRoot.props = finishedWork.memoizedProps),
-                (finishedRoot.state = finishedWork.memoizedState),
-                finishedRoot.componentDidMount();
-            else {
-              var prevProps = current.memoizedProps;
-              current = current.memoizedState;
-              finishedRoot.props = finishedWork.memoizedProps;
-              finishedRoot.state = finishedWork.memoizedState;
-              finishedRoot.componentDidUpdate(
-                prevProps,
-                current,
-                finishedRoot.__reactInternalSnapshotBeforeUpdate
-              );
-            }
-          finishedWork = finishedWork.updateQueue;
-          null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
-          break;
-        case 3:
-          current = finishedWork.updateQueue;
-          if (null !== current) {
-            finishedRoot = null;
-            if (null !== finishedWork.child)
-              switch (finishedWork.child.tag) {
-                case 5:
-                  finishedRoot = getPublicInstance(
-                    finishedWork.child.stateNode
-                  );
-                  break;
-                case 2:
-                  finishedRoot = finishedWork.child.stateNode;
-              }
-            commitCallbacks(current, finishedRoot);
-          }
-          break;
-        case 5:
-          finishedRoot = finishedWork.stateNode;
-          null === current &&
-            finishedWork.effectTag & 4 &&
-            commitMount(
-              finishedRoot,
-              finishedWork.type,
-              finishedWork.memoizedProps,
-              finishedWork
-            );
-          break;
-        case 6:
-          break;
-        case 4:
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitErrorLogging: function(finishedWork, onUncaughtError) {
-      switch (finishedWork.tag) {
-        case 2:
-          var ctor = finishedWork.type;
-          onUncaughtError = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            null !== updateQueue && null !== updateQueue.capturedValues,
-            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-          "function" !== typeof ctor.getDerivedStateFromCatch &&
-            markLegacyErrorBoundaryAsFailed(onUncaughtError);
-          onUncaughtError.props = finishedWork.memoizedProps;
-          onUncaughtError.state = finishedWork.memoizedState;
-          for (ctor = 0; ctor < capturedErrors.length; ctor++) {
-            updateQueue = capturedErrors[ctor];
-            var _error = updateQueue.value,
-              stack = updateQueue.stack;
-            logError(finishedWork, updateQueue);
-            onUncaughtError.componentDidCatch(_error, {
-              componentStack: null !== stack ? stack : ""
-            });
-          }
-          break;
-        case 3:
-          ctor = finishedWork.updateQueue;
-          invariant(
-            null !== ctor && null !== ctor.capturedValues,
-            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-          );
-          capturedErrors = ctor.capturedValues;
-          ctor.capturedValues = null;
-          for (ctor = 0; ctor < capturedErrors.length; ctor++)
-            (updateQueue = capturedErrors[ctor]),
-              logError(finishedWork, updateQueue),
-              onUncaughtError(updateQueue.value);
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitAttachRef: function(finishedWork) {
-      var ref = finishedWork.ref;
-      if (null !== ref) {
-        var _instance6 = finishedWork.stateNode;
-        switch (finishedWork.tag) {
-          case 5:
-            finishedWork = getPublicInstance(_instance6);
-            break;
-          default:
-            finishedWork = _instance6;
-        }
-        "function" === typeof ref
-          ? ref(finishedWork)
-          : (ref.current = finishedWork);
-      }
-    },
-    commitDetachRef: function(current) {
-      current = current.ref;
-      null !== current &&
-        ("function" === typeof current
-          ? current(null)
-          : (current.current = null));
-    }
-  };
-}
-var NO_CONTEXT = {};
-function ReactFiberHostContext(config, stack) {
-  function requiredContext(c) {
-    invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
-    );
-    return c;
-  }
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  config = stack.createCursor;
-  var push = stack.push,
-    pop = stack.pop,
-    contextStackCursor = config(NO_CONTEXT),
-    contextFiberStackCursor = config(NO_CONTEXT),
-    rootInstanceStackCursor = config(NO_CONTEXT);
-  return {
-    getHostContext: function() {
-      return requiredContext(contextStackCursor.current);
-    },
-    getRootHostContainer: function() {
-      return requiredContext(rootInstanceStackCursor.current);
-    },
-    popHostContainer: function(fiber) {
-      pop(contextStackCursor, fiber);
-      pop(contextFiberStackCursor, fiber);
-      pop(rootInstanceStackCursor, fiber);
-    },
-    popHostContext: function(fiber) {
-      contextFiberStackCursor.current === fiber &&
-        (pop(contextStackCursor, fiber), pop(contextFiberStackCursor, fiber));
-    },
-    pushHostContainer: function(fiber, nextRootInstance) {
-      push(rootInstanceStackCursor, nextRootInstance, fiber);
-      push(contextFiberStackCursor, fiber, fiber);
-      push(contextStackCursor, NO_CONTEXT, fiber);
-      nextRootInstance = getRootHostContext(nextRootInstance);
-      pop(contextStackCursor, fiber);
-      push(contextStackCursor, nextRootInstance, fiber);
-    },
-    pushHostContext: function(fiber) {
-      var rootInstance = requiredContext(rootInstanceStackCursor.current),
-        context = requiredContext(contextStackCursor.current);
-      rootInstance = getChildHostContext(context, fiber.type, rootInstance);
-      context !== rootInstance &&
-        (push(contextFiberStackCursor, fiber, fiber),
-        push(contextStackCursor, rootInstance, fiber));
-    }
-  };
-}
-function ReactFiberHydrationContext(config) {
-  function deleteHydratableInstance(returnFiber, instance) {
-    var fiber = new FiberNode(5, null, null, 0);
-    fiber.type = "DELETED";
-    fiber.stateNode = instance;
-    fiber["return"] = returnFiber;
-    fiber.effectTag = 8;
-    null !== returnFiber.lastEffect
-      ? ((returnFiber.lastEffect.nextEffect = fiber),
-        (returnFiber.lastEffect = fiber))
-      : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
-  }
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case 5:
-        return (
-          (nextInstance = canHydrateInstance(
-            nextInstance,
-            fiber.type,
-            fiber.pendingProps
-          )),
-          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
-        );
-      case 6:
-        return (
-          (nextInstance = canHydrateTextInstance(
-            nextInstance,
-            fiber.pendingProps
-          )),
-          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
-        );
-      default:
-        return !1;
-    }
-  }
-  function popToNextHostParent(fiber) {
-    for (
-      fiber = fiber["return"];
-      null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
-
-    )
-      fiber = fiber["return"];
-    hydrationParentFiber = fiber;
-  }
-  var shouldSetTextContent = config.shouldSetTextContent;
-  config = config.hydration;
-  if (!config)
-    return {
-      enterHydrationState: function() {
-        return !1;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          !1,
-          "Expected prepareToHydrateHostInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
-        invariant(
-          !1,
-          "Expected prepareToHydrateHostTextInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      popHydrationState: function() {
-        return !1;
-      }
-    };
-  var canHydrateInstance = config.canHydrateInstance,
-    canHydrateTextInstance = config.canHydrateTextInstance,
-    getNextHydratableSibling = config.getNextHydratableSibling,
-    getFirstHydratableChild = config.getFirstHydratableChild,
-    hydrateInstance = config.hydrateInstance,
-    hydrateTextInstance = config.hydrateTextInstance,
-    hydrationParentFiber = null,
-    nextHydratableInstance = null,
-    isHydrating = !1;
-  return {
-    enterHydrationState: function(fiber) {
-      nextHydratableInstance = getFirstHydratableChild(
-        fiber.stateNode.containerInfo
-      );
-      hydrationParentFiber = fiber;
-      return (isHydrating = !0);
-    },
-    resetHydrationState: function() {
-      nextHydratableInstance = hydrationParentFiber = null;
-      isHydrating = !1;
-    },
-    tryToClaimNextHydratableInstance: function(fiber) {
-      if (isHydrating) {
-        var nextInstance = nextHydratableInstance;
-        if (nextInstance) {
-          if (!tryHydrate(fiber, nextInstance)) {
-            nextInstance = getNextHydratableSibling(nextInstance);
-            if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-              fiber.effectTag |= 2;
-              isHydrating = !1;
-              hydrationParentFiber = fiber;
-              return;
-            }
-            deleteHydratableInstance(
-              hydrationParentFiber,
-              nextHydratableInstance
-            );
-          }
-          hydrationParentFiber = fiber;
-          nextHydratableInstance = getFirstHydratableChild(nextInstance);
-        } else
-          (fiber.effectTag |= 2),
-            (isHydrating = !1),
-            (hydrationParentFiber = fiber);
-      }
-    },
-    prepareToHydrateHostInstance: function(
-      fiber,
-      rootContainerInstance,
-      hostContext
-    ) {
-      rootContainerInstance = hydrateInstance(
-        fiber.stateNode,
-        fiber.type,
-        fiber.memoizedProps,
-        rootContainerInstance,
-        hostContext,
-        fiber
-      );
-      fiber.updateQueue = rootContainerInstance;
-      return null !== rootContainerInstance ? !0 : !1;
-    },
-    prepareToHydrateHostTextInstance: function(fiber) {
-      return hydrateTextInstance(fiber.stateNode, fiber.memoizedProps, fiber);
-    },
-    popHydrationState: function(fiber) {
-      if (fiber !== hydrationParentFiber) return !1;
-      if (!isHydrating)
-        return popToNextHostParent(fiber), (isHydrating = !0), !1;
-      var type = fiber.type;
-      if (
-        5 !== fiber.tag ||
-        ("head" !== type &&
-          "body" !== type &&
-          !shouldSetTextContent(type, fiber.memoizedProps))
-      )
-        for (type = nextHydratableInstance; type; )
-          deleteHydratableInstance(fiber, type),
-            (type = getNextHydratableSibling(type));
-      popToNextHostParent(fiber);
-      nextHydratableInstance = hydrationParentFiber
-        ? getNextHydratableSibling(fiber.stateNode)
-        : null;
-      return !0;
-    }
-  };
-}
-function ReactFiberLegacyContext(stack) {
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    workInProgress = workInProgress.stateNode;
-    workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    workInProgress.__reactInternalMemoizedMaskedChildContext = maskedContext;
-  }
-  function isContextProvider(fiber) {
-    return 2 === fiber.tag && null != fiber.type.childContextTypes;
-  }
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode,
-      childContextTypes = fiber.type.childContextTypes;
-    if ("function" !== typeof instance.getChildContext) return parentContext;
-    instance = instance.getChildContext();
-    for (var contextKey in instance)
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
-      );
-    return Object.assign({}, parentContext, instance);
-  }
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop,
-    contextStackCursor = createCursor(emptyObject),
-    didPerformWorkStackCursor = createCursor(!1),
-    previousContext = emptyObject;
-  return {
-    getUnmaskedContext: function(workInProgress) {
-      return isContextProvider(workInProgress)
-        ? previousContext
-        : contextStackCursor.current;
-    },
-    cacheContext: cacheContext,
-    getMaskedContext: function(workInProgress, unmaskedContext) {
-      var contextTypes = workInProgress.type.contextTypes;
-      if (!contextTypes) return emptyObject;
-      var instance = workInProgress.stateNode;
-      if (
-        instance &&
-        instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-      )
-        return instance.__reactInternalMemoizedMaskedChildContext;
-      var context = {},
-        key;
-      for (key in contextTypes) context[key] = unmaskedContext[key];
-      instance && cacheContext(workInProgress, unmaskedContext, context);
-      return context;
-    },
-    hasContextChanged: function() {
-      return didPerformWorkStackCursor.current;
-    },
-    isContextConsumer: function(fiber) {
-      return 2 === fiber.tag && null != fiber.type.contextTypes;
-    },
-    isContextProvider: isContextProvider,
-    popContextProvider: function(fiber) {
-      isContextProvider(fiber) &&
-        (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
-    },
-    popTopLevelContextObject: function(fiber) {
-      pop(didPerformWorkStackCursor, fiber);
-      pop(contextStackCursor, fiber);
-    },
-    pushTopLevelContextObject: function(fiber, context, didChange) {
-      invariant(
-        null == contextStackCursor.cursor,
-        "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
-      );
-      push(contextStackCursor, context, fiber);
-      push(didPerformWorkStackCursor, didChange, fiber);
-    },
-    processChildContext: processChildContext,
-    pushContextProvider: function(workInProgress) {
-      if (!isContextProvider(workInProgress)) return !1;
-      var instance = workInProgress.stateNode;
-      instance =
-        (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-        emptyObject;
-      previousContext = contextStackCursor.current;
-      push(contextStackCursor, instance, workInProgress);
-      push(
-        didPerformWorkStackCursor,
-        didPerformWorkStackCursor.current,
-        workInProgress
-      );
-      return !0;
-    },
-    invalidateContextProvider: function(workInProgress, didChange) {
-      var instance = workInProgress.stateNode;
-      invariant(
-        instance,
-        "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
-      );
-      if (didChange) {
-        var mergedContext = processChildContext(
-          workInProgress,
-          previousContext
-        );
-        instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-        pop(didPerformWorkStackCursor, workInProgress);
-        pop(contextStackCursor, workInProgress);
-        push(contextStackCursor, mergedContext, workInProgress);
-      } else pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    },
-    findCurrentUnmaskedContext: function(fiber) {
-      for (
-        invariant(
-          2 === isFiberMountedImpl(fiber) && 2 === fiber.tag,
-          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
-        );
-        3 !== fiber.tag;
-
-      ) {
-        if (isContextProvider(fiber))
-          return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber["return"];
-        invariant(
-          fiber,
-          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
-        );
-      }
-      return fiber.stateNode.context;
-    }
-  };
-}
-function ReactFiberNewContext(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop,
-    providerCursor = createCursor(null),
-    valueCursor = createCursor(null),
-    changedBitsCursor = createCursor(0);
-  return {
-    pushProvider: function(providerFiber) {
-      var context = providerFiber.type._context;
-      push(changedBitsCursor, context._changedBits, providerFiber);
-      push(valueCursor, context._currentValue, providerFiber);
-      push(providerCursor, providerFiber, providerFiber);
-      context._currentValue = providerFiber.pendingProps.value;
-      context._changedBits = providerFiber.stateNode;
-    },
-    popProvider: function(providerFiber) {
-      var changedBits = changedBitsCursor.current,
-        currentValue = valueCursor.current;
-      pop(providerCursor, providerFiber);
-      pop(valueCursor, providerFiber);
-      pop(changedBitsCursor, providerFiber);
-      providerFiber = providerFiber.type._context;
-      providerFiber._currentValue = currentValue;
-      providerFiber._changedBits = changedBits;
-    }
-  };
-}
-function ReactFiberStack() {
-  var valueStack = [],
-    index = -1;
-  return {
-    createCursor: function(defaultValue) {
-      return { current: defaultValue };
-    },
-    isEmpty: function() {
-      return -1 === index;
-    },
-    pop: function(cursor) {
-      0 > index ||
-        ((cursor.current = valueStack[index]),
-        (valueStack[index] = null),
-        index--);
-    },
-    push: function(cursor, value) {
-      index++;
-      valueStack[index] = cursor.current;
-      cursor.current = value;
-    },
-    checkThatStackIsEmpty: function() {},
-    resetStackAfterFatalErrorInDev: function() {}
-  };
-}
-function ReactFiberScheduler(config) {
-  function resetStack() {
-    if (null !== nextUnitOfWork)
-      for (
-        var interruptedWork = nextUnitOfWork["return"];
-        null !== interruptedWork;
-
-      )
-        unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork["return"]);
-    nextRoot = null;
-    nextRenderExpirationTime = 0;
-    nextUnitOfWork = null;
-    isRootReadyForCommit = !1;
-  }
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      null !== legacyErrorBoundariesThatAlreadyFailed &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
-  }
-  function completeUnitOfWork(workInProgress$jscomp$0) {
-    for (;;) {
-      var current = workInProgress$jscomp$0.alternate,
-        returnFiber = workInProgress$jscomp$0["return"],
-        siblingFiber = workInProgress$jscomp$0.sibling;
-      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
-        current = completeWork(
-          current,
-          workInProgress$jscomp$0,
-          nextRenderExpirationTime
-        );
-        var workInProgress = workInProgress$jscomp$0;
-        if (
-          1073741823 === nextRenderExpirationTime ||
-          1073741823 !== workInProgress.expirationTime
-        ) {
-          b: switch (workInProgress.tag) {
-            case 3:
-            case 2:
-              var newExpirationTime = workInProgress.updateQueue;
-              newExpirationTime =
-                null === newExpirationTime
-                  ? 0
-                  : newExpirationTime.expirationTime;
-              break b;
-            default:
-              newExpirationTime = 0;
-          }
-          for (var child = workInProgress.child; null !== child; )
-            0 !== child.expirationTime &&
-              (0 === newExpirationTime ||
-                newExpirationTime > child.expirationTime) &&
-              (newExpirationTime = child.expirationTime),
-              (child = child.sibling);
-          workInProgress.expirationTime = newExpirationTime;
-        }
-        if (null !== current) return current;
-        null !== returnFiber &&
-          0 === (returnFiber.effectTag & 512) &&
-          (null === returnFiber.firstEffect &&
-            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
-          null !== workInProgress$jscomp$0.lastEffect &&
-            (null !== returnFiber.lastEffect &&
-              (returnFiber.lastEffect.nextEffect =
-                workInProgress$jscomp$0.firstEffect),
-            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
-          1 < workInProgress$jscomp$0.effectTag &&
-            (null !== returnFiber.lastEffect
-              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
-              : (returnFiber.firstEffect = workInProgress$jscomp$0),
-            (returnFiber.lastEffect = workInProgress$jscomp$0)));
-        if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
-        else {
-          isRootReadyForCommit = !0;
-          break;
-        }
-      } else {
-        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
-        if (null !== workInProgress$jscomp$0)
-          return (
-            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
-          );
-        null !== returnFiber &&
-          ((returnFiber.firstEffect = returnFiber.lastEffect = null),
-          (returnFiber.effectTag |= 512));
-        if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
-        else break;
-      }
-    }
-    return null;
-  }
-  function performUnitOfWork(workInProgress) {
-    var next = beginWork(
-      workInProgress.alternate,
-      workInProgress,
-      nextRenderExpirationTime
-    );
-    null === next && (next = completeUnitOfWork(workInProgress));
-    ReactCurrentOwner.current = null;
-    return next;
-  }
-  function renderRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
-    );
-    isWorking = !0;
-    if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      null === nextUnitOfWork
-    )
-      resetStack(),
-        (nextRoot = root),
-        (nextRenderExpirationTime = expirationTime),
-        (nextUnitOfWork = createWorkInProgress(
-          nextRoot.current,
-          null,
-          nextRenderExpirationTime
-        )),
-        (root.pendingCommitExpirationTime = 0);
-    var didFatal = !1;
-    do {
-      try {
-        if (isAsync)
-          for (; null !== nextUnitOfWork && !shouldYield(); )
-            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-        else
-          for (; null !== nextUnitOfWork; )
-            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      } catch (thrownValue) {
-        if (null === nextUnitOfWork) {
-          didFatal = !0;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        isAsync = nextUnitOfWork;
-        var returnFiber = isAsync["return"];
-        if (null === returnFiber) {
-          didFatal = !0;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        throwException(returnFiber, isAsync, thrownValue);
-        nextUnitOfWork = completeUnitOfWork(isAsync);
-      }
-      break;
-    } while (1);
-    isWorking = !1;
-    if (didFatal || null !== nextUnitOfWork) return null;
-    if (isRootReadyForCommit)
-      return (
-        (root.pendingCommitExpirationTime = expirationTime),
-        root.current.alternate
-      );
-    invariant(
-      !1,
-      "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    sourceFiber = {
-      value: value,
-      source: sourceFiber,
-      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-    };
-    insertUpdateIntoFiber(boundaryFiber, {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: sourceFiber,
-      next: null
-    });
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-  function onCommitPhaseError(fiber$jscomp$0, error) {
-    a: {
-      invariant(
-        !isWorking || isCommitting,
-        "dispatch: Cannot dispatch during the render phase."
-      );
-      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
-        switch (fiber.tag) {
-          case 2:
-            var instance = fiber.stateNode;
-            if (
-              "function" === typeof fiber.type.getDerivedStateFromCatch ||
-              ("function" === typeof instance.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(instance))
-            ) {
-              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-              fiber$jscomp$0 = void 0;
-              break a;
-            }
-            break;
-          case 3:
-            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-            fiber$jscomp$0 = void 0;
-            break a;
-        }
-        fiber = fiber["return"];
-      }
-      3 === fiber$jscomp$0.tag &&
-        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
-      fiber$jscomp$0 = void 0;
-    }
-    return fiber$jscomp$0;
-  }
-  function computeExpirationForFiber(fiber) {
-    fiber =
-      0 !== expirationContext
-        ? expirationContext
-        : isWorking
-          ? isCommitting ? 1 : nextRenderExpirationTime
-          : fiber.mode & 1
-            ? isBatchingInteractiveUpdates
-              ? 10 * ((((recalculateCurrentTime() + 15) / 10) | 0) + 1)
-              : 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1)
-            : 1;
-    isBatchingInteractiveUpdates &&
-      (0 === lowestPendingInteractiveExpirationTime ||
-        fiber > lowestPendingInteractiveExpirationTime) &&
-      (lowestPendingInteractiveExpirationTime = fiber);
-    return fiber;
-  }
-  function scheduleWork(fiber, expirationTime) {
-    a: {
-      for (; null !== fiber; ) {
-        if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
-          fiber.expirationTime = expirationTime;
-        null !== fiber.alternate &&
-          (0 === fiber.alternate.expirationTime ||
-            fiber.alternate.expirationTime > expirationTime) &&
-          (fiber.alternate.expirationTime = expirationTime);
-        if (null === fiber["return"])
-          if (3 === fiber.tag) {
-            var root = fiber.stateNode;
-            !isWorking &&
-              0 !== nextRenderExpirationTime &&
-              expirationTime < nextRenderExpirationTime &&
-              resetStack();
-            (isWorking && !isCommitting && nextRoot === root) ||
-              requestWork(root, expirationTime);
-            nestedUpdateCount > NESTED_UPDATE_LIMIT &&
-              invariant(
-                !1,
-                "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
-              );
-          } else {
-            expirationTime = void 0;
-            break a;
-          }
-        fiber = fiber["return"];
-      }
-      expirationTime = void 0;
-    }
-    return expirationTime;
-  }
-  function recalculateCurrentTime() {
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
-  }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = 1;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (0 !== callbackExpirationTime) {
-      if (expirationTime > callbackExpirationTime) return;
-      cancelDeferredCallback(callbackID);
-    }
-    var currentMs = now() - originalStartTimeMs;
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: 10 * (expirationTime - 2) - currentMs
-    });
-  }
-  function requestWork(root, expirationTime) {
-    if (null === root.nextScheduledRoot)
-      (root.remainingExpirationTime = expirationTime),
-        null === lastScheduledRoot
-          ? ((firstScheduledRoot = lastScheduledRoot = root),
-            (root.nextScheduledRoot = root))
-          : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
-            (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
-    else {
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        expirationTime < remainingExpirationTime
-      )
-        root.remainingExpirationTime = expirationTime;
-    }
-    isRendering ||
-      (isBatchingUpdates
-        ? isUnbatchingUpdates &&
-          ((nextFlushedRoot = root),
-          (nextFlushedExpirationTime = 1),
-          performWorkOnRoot(root, 1, !1))
-        : 1 === expirationTime
-          ? performSyncWork()
-          : scheduleCallbackWithExpiration(expirationTime));
-  }
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = 0,
-      highestPriorityRoot = null;
-    if (null !== lastScheduledRoot)
-      for (
-        var previousScheduledRoot = lastScheduledRoot,
-          root = firstScheduledRoot;
-        null !== root;
-
-      ) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (0 === remainingExpirationTime) {
-          invariant(
-            null !== previousScheduledRoot && null !== lastScheduledRoot,
-            "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
-          );
-          if (root === root.nextScheduledRoot) {
-            firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot)
-            (firstScheduledRoot = remainingExpirationTime =
-              root.nextScheduledRoot),
-              (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
-              (root.nextScheduledRoot = null);
-          else if (root === lastScheduledRoot) {
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else
-            (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
-              (root.nextScheduledRoot = null);
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            0 === highestPriorityWork ||
-            remainingExpirationTime < highestPriorityWork
-          )
-            (highestPriorityWork = remainingExpirationTime),
-              (highestPriorityRoot = root);
-          if (root === lastScheduledRoot) break;
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
-        }
-      }
-    previousScheduledRoot = nextFlushedRoot;
-    null !== previousScheduledRoot &&
-    previousScheduledRoot === highestPriorityRoot &&
-    1 === highestPriorityWork
-      ? nestedUpdateCount++
-      : (nestedUpdateCount = 0);
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
-  }
-  function performAsyncWork(dl) {
-    performWork(0, !0, dl);
-  }
-  function performSyncWork() {
-    performWork(1, !1, null);
-  }
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
-    findHighestPriorityRoot();
-    if (isAsync)
-      for (
-        ;
-        null !== nextFlushedRoot &&
-        0 !== nextFlushedExpirationTime &&
-        (0 === minExpirationTime ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime);
-
-      )
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        ),
-          findHighestPriorityRoot();
-    else
-      for (
-        ;
-        null !== nextFlushedRoot &&
-        0 !== nextFlushedExpirationTime &&
-        (0 === minExpirationTime ||
-          minExpirationTime >= nextFlushedExpirationTime);
-
-      )
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
-          findHighestPriorityRoot();
-    null !== deadline && ((callbackExpirationTime = 0), (callbackID = -1));
-    0 !== nextFlushedExpirationTime &&
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
-    deadline = null;
-    deadlineDidExpire = !1;
-    finishRendering();
-  }
-  function finishRendering() {
-    nestedUpdateCount = 0;
-    if (null !== completedBatches) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          hasUnhandledError ||
-            ((hasUnhandledError = !0), (unhandledError = error));
-        }
-      }
-    }
-    if (hasUnhandledError)
-      throw ((batches = unhandledError),
-      (unhandledError = null),
-      (hasUnhandledError = !1),
-      batches);
-  }
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
-    );
-    isRendering = !0;
-    isAsync
-      ? ((isAsync = root.finishedWork),
-        null !== isAsync
-          ? completeRoot(root, isAsync, expirationTime)
-          : ((root.finishedWork = null),
-            (isAsync = renderRoot(root, expirationTime, !0)),
-            null !== isAsync &&
-              (shouldYield()
-                ? (root.finishedWork = isAsync)
-                : completeRoot(root, isAsync, expirationTime))))
-      : ((isAsync = root.finishedWork),
-        null !== isAsync
-          ? completeRoot(root, isAsync, expirationTime)
-          : ((root.finishedWork = null),
-            (isAsync = renderRoot(root, expirationTime, !1)),
-            null !== isAsync && completeRoot(root, isAsync, expirationTime)));
-    isRendering = !1;
-  }
-  function completeRoot(root, finishedWork, expirationTime) {
-    var firstBatch = root.firstBatch;
-    if (
-      null !== firstBatch &&
-      firstBatch._expirationTime <= expirationTime &&
-      (null === completedBatches
-        ? (completedBatches = [firstBatch])
-        : completedBatches.push(firstBatch),
-      firstBatch._defer)
-    ) {
-      root.finishedWork = finishedWork;
-      root.remainingExpirationTime = 0;
-      return;
-    }
-    root.finishedWork = null;
-    isCommitting = isWorking = !0;
-    expirationTime = finishedWork.stateNode;
-    invariant(
-      expirationTime.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
-    );
-    firstBatch = expirationTime.pendingCommitExpirationTime;
-    invariant(
-      0 !== firstBatch,
-      "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    expirationTime.pendingCommitExpirationTime = 0;
-    var currentTime = recalculateCurrentTime();
-    ReactCurrentOwner.current = null;
-    if (1 < finishedWork.effectTag)
-      if (null !== finishedWork.lastEffect) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        var firstEffect = finishedWork.firstEffect;
-      } else firstEffect = finishedWork;
-    else firstEffect = finishedWork.firstEffect;
-    prepareForCommit(expirationTime.containerInfo);
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      var didError = !1,
-        error = void 0;
-      try {
-        for (; null !== nextEffect; )
-          nextEffect.effectTag & 2048 &&
-            commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
-            (nextEffect = nextEffect.nextEffect);
-      } catch (e) {
-        (didError = !0), (error = e);
-      }
-      didError &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, error),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      didError = !1;
-      error = void 0;
-      try {
-        for (; null !== nextEffect; ) {
-          var effectTag = nextEffect.effectTag;
-          effectTag & 16 && commitResetTextContent(nextEffect);
-          if (effectTag & 128) {
-            var current = nextEffect.alternate;
-            null !== current && commitDetachRef(current);
-          }
-          switch (effectTag & 14) {
-            case 2:
-              commitPlacement(nextEffect);
-              nextEffect.effectTag &= -3;
-              break;
-            case 6:
-              commitPlacement(nextEffect);
-              nextEffect.effectTag &= -3;
-              commitWork(nextEffect.alternate, nextEffect);
-              break;
-            case 4:
-              commitWork(nextEffect.alternate, nextEffect);
-              break;
-            case 8:
-              commitDeletion(nextEffect);
-          }
-          nextEffect = nextEffect.nextEffect;
-        }
-      } catch (e) {
-        (didError = !0), (error = e);
-      }
-      didError &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, error),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    resetAfterCommit(expirationTime.containerInfo);
-    expirationTime.current = finishedWork;
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      effectTag = !1;
-      current = void 0;
-      try {
-        for (
-          firstEffect = expirationTime,
-            didError = currentTime,
-            error = firstBatch;
-          null !== nextEffect;
-
-        ) {
-          var effectTag$jscomp$0 = nextEffect.effectTag;
-          effectTag$jscomp$0 & 36 &&
-            commitLifeCycles(
-              firstEffect,
-              nextEffect.alternate,
-              nextEffect,
-              didError,
-              error
-            );
-          effectTag$jscomp$0 & 256 &&
-            commitErrorLogging(nextEffect, onUncaughtError);
-          effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
-          var next = nextEffect.nextEffect;
-          nextEffect.nextEffect = null;
-          nextEffect = next;
-        }
-      } catch (e) {
-        (effectTag = !0), (current = e);
-      }
-      effectTag &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, current),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    isWorking = isCommitting = !1;
-    "function" === typeof onCommitRoot && onCommitRoot(finishedWork.stateNode);
-    finishedWork = expirationTime.current.expirationTime;
-    0 === finishedWork && (legacyErrorBoundariesThatAlreadyFailed = null);
-    root.remainingExpirationTime = finishedWork;
-  }
-  function shouldYield() {
-    return null === deadline ||
-      deadline.timeRemaining() > timeHeuristicForUnitOfWork
-      ? !1
-      : (deadlineDidExpire = !0);
-  }
-  function onUncaughtError(error) {
-    invariant(
-      null !== nextFlushedRoot,
-      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    nextFlushedRoot.remainingExpirationTime = 0;
-    hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
-  }
-  var stack = ReactFiberStack(),
-    hostContext = ReactFiberHostContext(config, stack),
-    legacyContext = ReactFiberLegacyContext(stack);
-  stack = ReactFiberNewContext(stack);
-  var hydrationContext = ReactFiberHydrationContext(config),
-    beginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      stack,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber
-    ).beginWork,
-    completeWork = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      stack,
-      hydrationContext
-    ).completeWork;
-  hostContext = ReactFiberUnwindWork(
-    hostContext,
-    legacyContext,
-    stack,
-    scheduleWork,
-    isAlreadyFailedLegacyErrorBoundary
-  );
-  var throwException = hostContext.throwException,
-    unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork;
-  hostContext = ReactFiberCommitWork(
-    config,
-    onCommitPhaseError,
-    scheduleWork,
-    computeExpirationForFiber,
-    function(instance) {
-      null === legacyErrorBoundariesThatAlreadyFailed
-        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-    },
-    recalculateCurrentTime
-  );
-  var commitBeforeMutationLifeCycles =
-      hostContext.commitBeforeMutationLifeCycles,
-    commitResetTextContent = hostContext.commitResetTextContent,
-    commitPlacement = hostContext.commitPlacement,
-    commitDeletion = hostContext.commitDeletion,
-    commitWork = hostContext.commitWork,
-    commitLifeCycles = hostContext.commitLifeCycles,
-    commitErrorLogging = hostContext.commitErrorLogging,
-    commitAttachRef = hostContext.commitAttachRef,
-    commitDetachRef = hostContext.commitDetachRef,
-    now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit,
-    originalStartTimeMs = now(),
-    mostRecentCurrentTime = 2,
-    mostRecentCurrentTimeMs = originalStartTimeMs,
-    lastUniqueAsyncExpiration = 0,
-    expirationContext = 0,
-    isWorking = !1,
-    nextUnitOfWork = null,
-    nextRoot = null,
-    nextRenderExpirationTime = 0,
-    nextEffect = null,
-    isCommitting = !1,
-    isRootReadyForCommit = !1,
-    legacyErrorBoundariesThatAlreadyFailed = null,
-    firstScheduledRoot = null,
-    lastScheduledRoot = null,
-    callbackExpirationTime = 0,
-    callbackID = -1,
-    isRendering = !1,
-    nextFlushedRoot = null,
-    nextFlushedExpirationTime = 0,
-    lowestPendingInteractiveExpirationTime = 0,
-    deadlineDidExpire = !1,
-    hasUnhandledError = !1,
-    unhandledError = null,
-    deadline = null,
-    isBatchingUpdates = !1,
-    isUnbatchingUpdates = !1,
-    isBatchingInteractiveUpdates = !1,
-    completedBatches = null,
-    NESTED_UPDATE_LIMIT = 1e3,
-    nestedUpdateCount = 0,
-    timeHeuristicForUnitOfWork = 1;
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: function(root, expirationTime) {
-      invariant(
-        !isRendering,
-        "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
-      );
-      nextFlushedRoot = root;
-      nextFlushedExpirationTime = expirationTime;
-      performWorkOnRoot(root, expirationTime, !1);
-      performSyncWork();
-      finishRendering();
-    },
-    batchedUpdates: function(fn, a) {
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        return fn(a);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates) ||
-          isRendering ||
-          performSyncWork();
-      }
-    },
-    unbatchedUpdates: function(fn, a) {
-      if (isBatchingUpdates && !isUnbatchingUpdates) {
-        isUnbatchingUpdates = !0;
-        try {
-          return fn(a);
-        } finally {
-          isUnbatchingUpdates = !1;
-        }
-      }
-      return fn(a);
-    },
-    flushSync: function(fn, a) {
-      invariant(
-        !isRendering,
-        "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
-      );
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        return syncUpdates(fn, a);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates), performSyncWork();
-      }
-    },
-    flushControlled: function(fn) {
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        syncUpdates(fn);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates) ||
-          isRendering ||
-          performWork(1, !1, null);
-      }
-    },
-    deferredUpdates: function(fn) {
-      var previousExpirationContext = expirationContext;
-      expirationContext =
-        25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
-      try {
-        return fn();
-      } finally {
-        expirationContext = previousExpirationContext;
-      }
-    },
-    syncUpdates: syncUpdates,
-    interactiveUpdates: function(fn, a, b) {
-      if (isBatchingInteractiveUpdates) return fn(a, b);
-      isBatchingUpdates ||
-        isRendering ||
-        0 === lowestPendingInteractiveExpirationTime ||
-        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
-        (lowestPendingInteractiveExpirationTime = 0));
-      var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
-        previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = isBatchingInteractiveUpdates = !0;
-      try {
-        return fn(a, b);
-      } finally {
-        (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
-          (isBatchingUpdates = previousIsBatchingUpdates) ||
-            isRendering ||
-            performSyncWork();
-      }
-    },
-    flushInteractiveUpdates: function() {
-      isRendering ||
-        0 === lowestPendingInteractiveExpirationTime ||
-        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
-        (lowestPendingInteractiveExpirationTime = 0));
-    },
-    computeUniqueAsyncExpiration: function() {
-      var result = 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
-      result <= lastUniqueAsyncExpiration &&
-        (result = lastUniqueAsyncExpiration + 1);
-      return (lastUniqueAsyncExpiration = result);
-    },
-    legacyContext: legacyContext
-  };
-}
-function ReactFiberReconciler$1(config) {
-  function updateContainerAtExpirationTime(
-    element,
-    container,
-    parentComponent,
-    currentTime,
-    expirationTime,
-    callback
-  ) {
-    currentTime = container.current;
-    if (parentComponent) {
-      parentComponent = parentComponent._reactInternalFiber;
-      var parentContext = findCurrentUnmaskedContext(parentComponent);
-      parentComponent = isContextProvider(parentComponent)
-        ? processChildContext(parentComponent, parentContext)
-        : parentContext;
-    } else parentComponent = emptyObject;
-    null === container.context
-      ? (container.context = parentComponent)
-      : (container.pendingContext = parentComponent);
-    container = callback;
-    insertUpdateIntoFiber(currentTime, {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: void 0 === container ? null : container,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: null,
-      next: null
-    });
-    scheduleWork(currentTime, expirationTime);
-    return expirationTime;
-  }
-  var getPublicInstance = config.getPublicInstance;
-  config = ReactFiberScheduler(config);
-  var recalculateCurrentTime = config.recalculateCurrentTime,
-    computeExpirationForFiber = config.computeExpirationForFiber,
-    scheduleWork = config.scheduleWork,
-    legacyContext = config.legacyContext,
-    findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
-  return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
-      containerInfo = {
-        current: isAsync,
-        containerInfo: containerInfo,
-        pendingChildren: null,
-        pendingCommitExpirationTime: 0,
-        finishedWork: null,
-        context: null,
-        pendingContext: null,
-        hydrate: hydrate,
-        remainingExpirationTime: 0,
-        firstBatch: null,
-        nextScheduledRoot: null
-      };
-      return (isAsync.stateNode = containerInfo);
-    },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current,
-        currentTime = recalculateCurrentTime();
-      current = computeExpirationForFiber(current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        current,
-        callback
-      );
-    },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
-    ) {
-      var currentTime = recalculateCurrentTime();
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        expirationTime,
-        callback
-      );
-    },
-    flushRoot: config.flushRoot,
-    requestWork: config.requestWork,
-    computeUniqueAsyncExpiration: config.computeUniqueAsyncExpiration,
-    batchedUpdates: config.batchedUpdates,
-    unbatchedUpdates: config.unbatchedUpdates,
-    deferredUpdates: config.deferredUpdates,
-    syncUpdates: config.syncUpdates,
-    interactiveUpdates: config.interactiveUpdates,
-    flushInteractiveUpdates: config.flushInteractiveUpdates,
-    flushControlled: config.flushControlled,
-    flushSync: config.flushSync,
-    getPublicRootInstance: function(container) {
-      container = container.current;
-      if (!container.child) return null;
-      switch (container.child.tag) {
-        case 5:
-          return getPublicInstance(container.child.stateNode);
-        default:
-          return container.child.stateNode;
-      }
-    },
-    findHostInstance: function(component) {
-      var fiber = component._reactInternalFiber;
-      void 0 === fiber &&
-        ("function" === typeof component.render
-          ? invariant(!1, "Unable to find node on an unmounted component.")
-          : invariant(
-              !1,
-              "Argument appears to not be a ReactComponent. Keys: %s",
-              Object.keys(component)
-            ));
-      component = findCurrentHostFiber(fiber);
-      return null === component ? null : component.stateNode;
-    },
-    findHostInstanceWithNoPortals: function(fiber) {
-      fiber = findCurrentHostFiberWithNoPortals(fiber);
-      return null === fiber ? null : fiber.stateNode;
-    },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            fiber = findCurrentHostFiber(fiber);
-            return null === fiber ? null : fiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            return findFiberByHostInstance
-              ? findFiberByHostInstance(instance)
-              : null;
-          }
-        })
-      );
-    }
-  };
-}
-var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
-  ReactFiberReconciler$3 =
-    (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
-    ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3["default"]
-    ? ReactFiberReconciler$3["default"]
-    : ReactFiberReconciler$3,
-  ReactNativeFiberHostComponent = (function() {
-    function ReactNativeFiberHostComponent(tag, viewConfig) {
-      if (!(this instanceof ReactNativeFiberHostComponent))
-        throw new TypeError("Cannot call a class as a function");
-      this._nativeTag = tag;
-      this._children = [];
-      this.viewConfig = viewConfig;
-    }
-    ReactNativeFiberHostComponent.prototype.blur = function() {
-      TextInputState.blurTextInput(this._nativeTag);
-    };
-    ReactNativeFiberHostComponent.prototype.focus = function() {
-      TextInputState.focusTextInput(this._nativeTag);
-    };
-    ReactNativeFiberHostComponent.prototype.measure = function(callback) {
-      UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-    };
-    ReactNativeFiberHostComponent.prototype.measureInWindow = function(
-      callback
-    ) {
-      UIManager.measureInWindow(
-        this._nativeTag,
-        mountSafeCallback(this, callback)
-      );
-    };
-    ReactNativeFiberHostComponent.prototype.measureLayout = function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail
-    ) {
-      UIManager.measureLayout(
-        this._nativeTag,
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    };
-    ReactNativeFiberHostComponent.prototype.setNativeProps = function(
-      nativeProps
-    ) {
-      nativeProps = diffProperties(
-        null,
-        emptyObject$1,
-        nativeProps,
-        this.viewConfig.validAttributes
-      );
-      null != nativeProps &&
-        UIManager.updateView(
-          this._nativeTag,
-          this.viewConfig.uiViewClassName,
-          nativeProps
-        );
-    };
-    return ReactNativeFiberHostComponent;
-  })(),
-  now =
-    "object" === typeof performance && "function" === typeof performance.now
-      ? function() {
-          return performance.now();
-        }
-      : function() {
-          return Date.now();
-        },
-  scheduledCallback = null,
-  frameDeadline = 0,
-  frameDeadlineObject = {
-    timeRemaining: function() {
-      return frameDeadline - now();
-    },
-    didTimeout: !1
-  };
-function setTimeoutCallback() {
-  frameDeadline = now() + 5;
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  null !== callback && callback(frameDeadlineObject);
-}
-var nextReactTag = 3;
-function allocateTag() {
-  var tag = nextReactTag;
-  1 === tag % 10 && (tag += 2);
-  nextReactTag = tag + 2;
-  return tag;
-}
-function recursivelyUncacheFiberNode(node) {
-  "number" === typeof node
-    ? uncacheFiberNode(node)
-    : (uncacheFiberNode(node._nativeTag),
-      node._children.forEach(recursivelyUncacheFiberNode));
-}
-var NativeRenderer = reactReconciler({
-    appendInitialChild: function(parentInstance, child) {
-      parentInstance._children.push(child);
-    },
-    createInstance: function(
-      type,
-      props,
-      rootContainerInstance,
-      hostContext,
-      internalInstanceHandle
-    ) {
-      hostContext = allocateTag();
-      type = ReactNativeViewConfigRegistry.get(type);
-      var updatePayload = diffProperties(
-        null,
-        emptyObject$1,
-        props,
-        type.validAttributes
-      );
-      UIManager.createView(
-        hostContext,
-        type.uiViewClassName,
-        rootContainerInstance,
-        updatePayload
-      );
-      rootContainerInstance = new ReactNativeFiberHostComponent(
-        hostContext,
-        type
-      );
-      instanceCache[hostContext] = internalInstanceHandle;
-      instanceProps[hostContext] = props;
-      return rootContainerInstance;
-    },
-    createTextInstance: function(
-      text,
-      rootContainerInstance,
-      hostContext,
-      internalInstanceHandle
-    ) {
-      hostContext = allocateTag();
-      UIManager.createView(hostContext, "RCTRawText", rootContainerInstance, {
-        text: text
-      });
-      instanceCache[hostContext] = internalInstanceHandle;
-      return hostContext;
-    },
-    finalizeInitialChildren: function(parentInstance) {
-      if (0 === parentInstance._children.length) return !1;
-      var nativeTags = parentInstance._children.map(function(child) {
-        return "number" === typeof child ? child : child._nativeTag;
-      });
-      UIManager.setChildren(parentInstance._nativeTag, nativeTags);
-      return !1;
-    },
-    getRootHostContext: function() {
-      return emptyObject;
-    },
-    getChildHostContext: function() {
-      return emptyObject;
-    },
-    getPublicInstance: function(instance) {
-      return instance;
-    },
-    now: now,
-    prepareForCommit: function() {},
-    prepareUpdate: function() {
-      return emptyObject;
-    },
-    resetAfterCommit: function() {},
-    scheduleDeferredCallback: function(callback) {
-      scheduledCallback = callback;
-      return setTimeout(setTimeoutCallback, 1);
-    },
-    cancelDeferredCallback: function(callbackID) {
-      scheduledCallback = null;
-      clearTimeout(callbackID);
-    },
-    shouldDeprioritizeSubtree: function() {
-      return !1;
-    },
-    shouldSetTextContent: function() {
-      return !1;
-    },
-    mutation: {
-      appendChild: function(parentInstance, child) {
-        var childTag = "number" === typeof child ? child : child._nativeTag,
-          children = parentInstance._children,
-          index = children.indexOf(child);
-        0 <= index
-          ? (children.splice(index, 1),
-            children.push(child),
-            UIManager.manageChildren(
-              parentInstance._nativeTag,
-              [index],
-              [children.length - 1],
-              [],
-              [],
-              []
-            ))
-          : (children.push(child),
-            UIManager.manageChildren(
-              parentInstance._nativeTag,
-              [],
-              [],
-              [childTag],
-              [children.length - 1],
-              []
-            ));
-      },
-      appendChildToContainer: function(parentInstance, child) {
-        UIManager.setChildren(parentInstance, [
-          "number" === typeof child ? child : child._nativeTag
-        ]);
-      },
-      commitTextUpdate: function(textInstance, oldText, newText) {
-        UIManager.updateView(textInstance, "RCTRawText", { text: newText });
-      },
-      commitMount: function() {},
-      commitUpdate: function(
-        instance,
-        updatePayloadTODO,
-        type,
-        oldProps,
-        newProps
-      ) {
-        updatePayloadTODO = instance.viewConfig;
-        instanceProps[instance._nativeTag] = newProps;
-        oldProps = diffProperties(
-          null,
-          oldProps,
-          newProps,
-          updatePayloadTODO.validAttributes
-        );
-        null != oldProps &&
-          UIManager.updateView(
-            instance._nativeTag,
-            updatePayloadTODO.uiViewClassName,
-            oldProps
-          );
-      },
-      insertBefore: function(parentInstance, child, beforeChild) {
-        var children = parentInstance._children,
-          index = children.indexOf(child);
-        0 <= index
-          ? (children.splice(index, 1),
-            (beforeChild = children.indexOf(beforeChild)),
-            children.splice(beforeChild, 0, child),
-            UIManager.manageChildren(
-              parentInstance._nativeTag,
-              [index],
-              [beforeChild],
-              [],
-              [],
-              []
-            ))
-          : ((index = children.indexOf(beforeChild)),
-            children.splice(index, 0, child),
-            UIManager.manageChildren(
-              parentInstance._nativeTag,
-              [],
-              [],
-              ["number" === typeof child ? child : child._nativeTag],
-              [index],
-              []
-            ));
-      },
-      insertInContainerBefore: function(parentInstance) {
-        invariant(
-          "number" !== typeof parentInstance,
-          "Container does not support insertBefore operation"
-        );
-      },
-      removeChild: function(parentInstance, child) {
-        recursivelyUncacheFiberNode(child);
-        var children = parentInstance._children;
-        child = children.indexOf(child);
-        children.splice(child, 1);
-        UIManager.manageChildren(
-          parentInstance._nativeTag,
-          [],
-          [],
-          [],
-          [],
-          [child]
-        );
-      },
-      removeChildFromContainer: function(parentInstance, child) {
-        recursivelyUncacheFiberNode(child);
-        UIManager.manageChildren(parentInstance, [], [], [], [], [0]);
-      },
-      resetTextContent: function() {}
-    }
-  }),
-  getInspectorDataForViewTag = void 0;
-getInspectorDataForViewTag = function() {
-  invariant(!1, "getInspectorDataForViewTag() is not available in production");
-};
-var findHostInstance = NativeRenderer.findHostInstance;
-function findNodeHandle(componentOrHandle) {
-  if (null == componentOrHandle) return null;
-  if ("number" === typeof componentOrHandle) return componentOrHandle;
-  if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
-  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
-    return componentOrHandle.canonical._nativeTag;
-  componentOrHandle = findHostInstance(componentOrHandle);
-  return null == componentOrHandle
-    ? componentOrHandle
-    : componentOrHandle.canonical
-      ? componentOrHandle.canonical._nativeTag
-      : componentOrHandle._nativeTag;
-}
-_batchedUpdates = NativeRenderer.batchedUpdates;
-_flushInteractiveUpdates = NativeRenderer.flushInteractiveUpdates;
-var roots = new Map(),
-  ReactNativeRenderer = {
-    NativeComponent: (function(findNodeHandle, findHostInstance) {
-      return (function(_React$Component) {
-        function ReactNativeComponent() {
-          if (!(this instanceof ReactNativeComponent))
-            throw new TypeError("Cannot call a class as a function");
-          var call = _React$Component.apply(this, arguments);
-          if (!this)
-            throw new ReferenceError(
-              "this hasn't been initialised - super() hasn't been called"
-            );
-          return !call ||
-            ("object" !== typeof call && "function" !== typeof call)
-            ? this
-            : call;
-        }
-        _inherits(ReactNativeComponent, _React$Component);
-        ReactNativeComponent.prototype.blur = function() {
-          TextInputState.blurTextInput(findNodeHandle(this));
-        };
-        ReactNativeComponent.prototype.focus = function() {
-          TextInputState.focusTextInput(findNodeHandle(this));
-        };
-        ReactNativeComponent.prototype.measure = function(callback) {
-          UIManager.measure(
-            findNodeHandle(this),
-            mountSafeCallback(this, callback)
-          );
-        };
-        ReactNativeComponent.prototype.measureInWindow = function(callback) {
-          UIManager.measureInWindow(
-            findNodeHandle(this),
-            mountSafeCallback(this, callback)
-          );
-        };
-        ReactNativeComponent.prototype.measureLayout = function(
-          relativeToNativeNode,
-          onSuccess,
-          onFail
-        ) {
-          UIManager.measureLayout(
-            findNodeHandle(this),
-            relativeToNativeNode,
-            mountSafeCallback(this, onFail),
-            mountSafeCallback(this, onSuccess)
-          );
-        };
-        ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
-          var maybeInstance = void 0;
-          try {
-            maybeInstance = findHostInstance(this);
-          } catch (error) {}
-          if (null != maybeInstance) {
-            var viewConfig =
-              maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
-            nativeProps = diffProperties(
-              null,
-              emptyObject$1,
-              nativeProps,
-              viewConfig.validAttributes
-            );
-            null != nativeProps &&
-              UIManager.updateView(
-                maybeInstance._nativeTag,
-                viewConfig.uiViewClassName,
-                nativeProps
-              );
-          }
-        };
-        return ReactNativeComponent;
-      })(React.Component);
-    })(findNodeHandle, findHostInstance),
-    findNodeHandle: findNodeHandle,
-    render: function(element, containerTag, callback) {
-      var root = roots.get(containerTag);
-      root ||
-        ((root = NativeRenderer.createContainer(containerTag, !1, !1)),
-        roots.set(containerTag, root));
-      NativeRenderer.updateContainer(element, root, null, callback);
-      return NativeRenderer.getPublicRootInstance(root);
-    },
-    unmountComponentAtNode: function(containerTag) {
-      var root = roots.get(containerTag);
-      root &&
-        NativeRenderer.updateContainer(null, root, null, function() {
-          roots["delete"](containerTag);
-        });
-    },
-    unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
-      ReactNativeRenderer.unmountComponentAtNode(containerTag);
-      UIManager.removeRootView(containerTag);
-    },
-    createPortal: function(children, containerTag) {
-      return createPortal(
-        children,
-        containerTag,
-        null,
-        2 < arguments.length && void 0 !== arguments[2] ? arguments[2] : null
-      );
-    },
-    unstable_batchedUpdates: batchedUpdates,
-    __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
-      NativeMethodsMixin: (function(findNodeHandle, findHostInstance) {
-        return {
-          measure: function(callback) {
-            UIManager.measure(
-              findNodeHandle(this),
-              mountSafeCallback(this, callback)
-            );
-          },
-          measureInWindow: function(callback) {
-            UIManager.measureInWindow(
-              findNodeHandle(this),
-              mountSafeCallback(this, callback)
-            );
-          },
-          measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
-            UIManager.measureLayout(
-              findNodeHandle(this),
-              relativeToNativeNode,
-              mountSafeCallback(this, onFail),
-              mountSafeCallback(this, onSuccess)
-            );
-          },
-          setNativeProps: function(nativeProps) {
-            var maybeInstance = void 0;
-            try {
-              maybeInstance = findHostInstance(this);
-            } catch (error) {}
-            if (null != maybeInstance) {
-              var viewConfig = maybeInstance.viewConfig;
-              nativeProps = diffProperties(
-                null,
-                emptyObject$1,
-                nativeProps,
-                viewConfig.validAttributes
-              );
-              null != nativeProps &&
-                UIManager.updateView(
-                  maybeInstance._nativeTag,
-                  viewConfig.uiViewClassName,
-                  nativeProps
-                );
-            }
-          },
-          focus: function() {
-            TextInputState.focusTextInput(findNodeHandle(this));
-          },
-          blur: function() {
-            TextInputState.blurTextInput(findNodeHandle(this));
-          }
-        };
-      })(findNodeHandle, findHostInstance),
-      ReactNativeComponentTree: ReactNativeComponentTree,
-      computeComponentStackForErrorReporting: function(reactTag) {
-        return (reactTag = getInstanceFromTag(reactTag))
-          ? getStackAddendumByWorkInProgressFiber(reactTag)
-          : "";
-      }
-    }
-  };
-NativeRenderer.injectIntoDevTools({
-  findFiberByHostInstance: getInstanceFromTag,
-  getInspectorDataForViewTag: getInspectorDataForViewTag,
-  bundleType: 0,
-  version: "16.3.2",
-  rendererPackageName: "react-native-renderer"
-});
-var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
-  ReactNativeRenderer$3 =
-    (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
-module.exports = ReactNativeRenderer$3["default"]
-  ? ReactNativeRenderer$3["default"]
-  : ReactNativeRenderer$3;

From 931930ae63d8866cd0d5bfa001a6c872f751df0c Mon Sep 17 00:00:00 2001
From: Nat Mote <nmote@fb.com>
Date: Fri, 20 Apr 2018 10:40:28 -0700
Subject: [PATCH 0357/1109] Remove non-top-level export from JSTimers

Reviewed By: davidaurelio

Differential Revision: D7705416

fbshipit-source-id: 1252789c2cd59b8666b57edcf17948c102e63888
---
 Libraries/Core/Timers/JSTimers.js | 7 +++++--
 1 file changed, 5 insertions(+), 2 deletions(-)

diff --git a/Libraries/Core/Timers/JSTimers.js b/Libraries/Core/Timers/JSTimers.js
index 5fae3408aa51..e0b4fbbd8866 100644
--- a/Libraries/Core/Timers/JSTimers.js
+++ b/Libraries/Core/Timers/JSTimers.js
@@ -483,13 +483,16 @@ const JSTimers = {
   },
 };
 
+let ExportedJSTimers;
 if (!Timing) {
   console.warn("Timing native module is not available, can't set timers.");
   // $FlowFixMe: we can assume timers are generally available
-  module.exports = ({
+  ExportedJSTimers = ({
     callImmediates: JSTimers.callImmediates,
     setImmediate: JSTimers.setImmediate,
   }: typeof JSTimers);
 } else {
-  module.exports = JSTimers;
+  ExportedJSTimers = JSTimers;
 }
+
+module.exports = ExportedJSTimers;

From 06ec0f0fd1b85c07dd76f9cd37a1c36264196b08 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 20 Apr 2018 14:03:33 -0700
Subject: [PATCH 0358/1109] Expose the asyncRequireModulePath param

Reviewed By: mjesun

Differential Revision: D7709569

fbshipit-source-id: 871dd9c178b1e5c81163558201ef983315561211
---
 local-cli/bundle/buildBundle.js | 1 +
 local-cli/server/runServer.js   | 1 +
 2 files changed, 2 insertions(+)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index 99c45ddc08db..c5d231480529 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -78,6 +78,7 @@ async function buildBundle(
   const terminal = new Terminal(process.stdout);
 
   const server = new Server({
+    asyncRequireModulePath: config.getAsyncRequireModulePath(),
     assetExts: defaultAssetExts.concat(assetExts),
     assetRegistryPath: ASSET_REGISTRY_PATH,
     blacklistRE: config.getBlacklistRE(),
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 47c11535bdf4..e9b5f3e35bba 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -176,6 +176,7 @@ function getPackagerServer(args, config, reporter) {
     args.providesModuleNodeModules || defaultProvidesModuleNodeModules;
 
   return Metro.createServer({
+    asyncRequireModulePath: config.getAsyncRequireModulePath(),
     assetExts: defaultAssetExts.concat(args.assetExts),
     assetRegistryPath: ASSET_REGISTRY_PATH,
     blacklistRE: config.getBlacklistRE(),

From 57919a3edd3d09f595224e0d92f95da1df75e884 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 20 Apr 2018 14:03:35 -0700
Subject: [PATCH 0359/1109] Bump metro@0.34.0

Differential Revision: D7708906

fbshipit-source-id: 3d8cdfd2745baf73c92f90e0960f7cd73a289f77
---
 babel-preset/package.json | 2 +-
 package.json              | 4 ++--
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/babel-preset/package.json b/babel-preset/package.json
index ce1c169a82f9..691941cf378b 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -40,6 +40,6 @@
     "@babel/plugin-transform-template-literals": "7.0.0-beta.40",
     "@babel/plugin-transform-unicode-regex": "7.0.0-beta.40",
     "@babel/template": "7.0.0-beta.40",
-    "metro-babel7-plugin-react-transform": "0.32.0"
+    "metro-babel7-plugin-react-transform": "0.34.0"
   }
 }
diff --git a/package.json b/package.json
index 8cadfda93457..5974c35feebf 100644
--- a/package.json
+++ b/package.json
@@ -166,8 +166,8 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.33.0",
-    "metro-core": "^0.33.0",
+    "metro": "^0.34.0",
+    "metro-core": "^0.34.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 5c8596dabe8bc63bc10ab6820ba8d5db70433663 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Sat, 21 Apr 2018 11:20:59 -0700
Subject: [PATCH 0360/1109] Upgrade Jest to 23.0.0-beta.1

Reviewed By: cpojer

Differential Revision: D7722547

fbshipit-source-id: 711617c5c88fced5a38067a66fda86d2b281c0a2
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 5974c35feebf..6f013d4aa1e8 100644
--- a/package.json
+++ b/package.json
@@ -207,7 +207,7 @@
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
     "flow-bin": "^0.70.0",
-    "jest": "23.0.0-alpha.4",
+    "jest": "23.0.0-beta.1",
     "jest-junit": "3.6.0",
     "prettier": "1.12.1",
     "react": "16.3.2",

From 2690ba5e591fb67aea1d528e96b3999c6ddd272f Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Mon, 23 Apr 2018 03:52:15 -0700
Subject: [PATCH 0361/1109] Move worker protocol and babelRegisterOnly into
 their own packages
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary: Moves the implementation of Buck’s worker protocol into its own package and babelRegisterOnly for better reusability.

Reviewed By: rafeca

Differential Revision: D7666896

fbshipit-source-id: ae297494ced3b8dd1f9d90983a640643d6ce7896
---
 jest/preprocessor.js | 2 +-
 package.json         | 1 +
 setupBabel.js        | 2 +-
 3 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index 170f7091c308..6d9e60de675f 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -15,7 +15,7 @@ const {transformSync: babelTransformSync} = require('@babel/core');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-const babelRegisterOnly = require('metro/src/babelRegisterOnly');
+const babelRegisterOnly = require('metro-babel-register');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
diff --git a/package.json b/package.json
index 6f013d4aa1e8..a2ee96304c1e 100644
--- a/package.json
+++ b/package.json
@@ -167,6 +167,7 @@
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
     "metro": "^0.34.0",
+    "metro-babel-register": "^0.34.1",
     "metro-core": "^0.34.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
diff --git a/setupBabel.js b/setupBabel.js
index 6bac7dde43ae..28b208e05a99 100644
--- a/setupBabel.js
+++ b/setupBabel.js
@@ -7,7 +7,7 @@
 
 'use strict';
 
-const babelRegisterOnly = require('metro/src/babelRegisterOnly');
+const babelRegisterOnly = require('metro-babel-register');
 const escapeRegExp = require('lodash/escapeRegExp');
 const path = require('path');
 

From e85799faed7ccfad34d1e7d9ec827f6e70d8f330 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Mon, 23 Apr 2018 05:48:20 -0700
Subject: [PATCH 0362/1109] Add @babel/core to RN dev deps for testing

Summary:
This adds a locked down version of Babel 7 (beta.40) to the dev dependencies for RN because it's used in testing.

See also; https://github.com/facebook/react-native/commit/f8d6b97140cffe8d18b2558f94570c8d1b410d5c#r28569573

Reviewed By: davidaurelio

Differential Revision: D7685590

fbshipit-source-id: eae8379b586d82527788e9812a573ab321dfc8e3
---
 package.json | 1 +
 1 file changed, 1 insertion(+)

diff --git a/package.json b/package.json
index a2ee96304c1e..3ecb3625c2cb 100644
--- a/package.json
+++ b/package.json
@@ -198,6 +198,7 @@
     "yargs": "^9.0.0"
   },
   "devDependencies": {
+    "@babel/core": "7.0.0-beta.40",
     "babel-eslint": "8.2.1",
     "eslint": "4.17.0",
     "eslint-config-fb-strict": "22.1.0",

From fc42f9cca24a9f8023db0ad908807e003a583a73 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Ma=C3=ABl=20Nison?= <mael@fb.com>
Date: Mon, 23 Apr 2018 10:26:28 -0700
Subject: [PATCH 0363/1109] Adds async & babel-generator to the devDependencies

Reviewed By: mjesun

Differential Revision: D7707199

fbshipit-source-id: 30635f44b24c156ef1947652ef78850b4d9d68b6
---
 package.json | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/package.json b/package.json
index 3ecb3625c2cb..603b8808007d 100644
--- a/package.json
+++ b/package.json
@@ -199,7 +199,9 @@
   },
   "devDependencies": {
     "@babel/core": "7.0.0-beta.40",
+    "async": "^2.4.0",
     "babel-eslint": "8.2.1",
+    "babel-generator": "^6.26.0",
     "eslint": "4.17.0",
     "eslint-config-fb-strict": "22.1.0",
     "eslint-config-fbjs": "2.0.1",

From 05b75b9ebfa3ce6d67b2a3aee446ff0cd515311b Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 23 Apr 2018 11:13:07 -0700
Subject: [PATCH 0364/1109] Revert D7612904: [react-native][PR] Fix view
 indices with Android LayoutAnimation

Differential Revision:
D7612904

Original commit changeset: a04cf47ab80e

fbshipit-source-id: fd22a1243f770aab486f6c6d09726547c92841c0
---
 .../react/uimanager/NativeViewHierarchyManager.java | 13 +++++--------
 .../facebook/react/uimanager/ViewGroupManager.java  |  8 --------
 2 files changed, 5 insertions(+), 16 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
index 2b72a0a33330..a57205b861eb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
@@ -373,13 +373,12 @@ public synchronized void manageChildren(
         if (mLayoutAnimationEnabled &&
             mLayoutAnimator.shouldAnimateLayout(viewToRemove) &&
             arrayContains(tagsToDelete, viewToRemove.getId())) {
-          // Display the view in the parent after removal for the duration of the layout animation,
-          // but pretend that it doesn't exist when calling other ViewGroup methods.
-          viewManager.startViewTransition(viewToManage, viewToRemove);
+          // The view will be removed and dropped by the 'delete' layout animation
+          // instead, so do nothing
+        } else {
+          viewManager.removeViewAt(viewToManage, indexToRemove);
         }
 
-        viewManager.removeViewAt(viewToManage, indexToRemove);
-
         lastIndexToRemove = indexToRemove;
       }
     }
@@ -424,9 +423,7 @@ public synchronized void manageChildren(
           mLayoutAnimator.deleteView(viewToDestroy, new LayoutAnimationListener() {
             @Override
             public void onAnimationEnd() {
-              // Already removed from the ViewGroup, we can just end the transition here to
-              // release the child.
-              viewManager.endViewTransition(viewToManage, viewToDestroy);
+              viewManager.removeView(viewToManage, viewToDestroy);
               dropView(viewToDestroy);
             }
           });
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewGroupManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewGroupManager.java
index c4d5eed429dd..017fb5764e72 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewGroupManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewGroupManager.java
@@ -93,14 +93,6 @@ public void removeAllViews(T parent) {
     }
   }
 
-  public void startViewTransition(T parent, View view) {
-    parent.startViewTransition(view);
-  }
-
-  public void endViewTransition(T parent, View view) {
-    parent.endViewTransition(view);
-  }
-
   /**
    * Returns whether this View type needs to handle laying out its own children instead of
    * deferring to the standard css-layout algorithm.

From f80000b9e72596392567a3deda59441e43f6327d Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Mon, 23 Apr 2018 13:37:19 -0700
Subject: [PATCH 0365/1109] Move `buildRegExps` from `react-native` to
 `metro-babel-register`

Summary: Moves the `buildRegExps` function from `react-native` to `metro-babel-register`. This way, it is easier to reuse, and we can remove FB-specific logic from React Native.

Reviewed By: jeanlauliac, mjesun

Differential Revision: D7727483

fbshipit-source-id: 0f7773ff044033c465f0712c523a0aef61bf8444
---
 package.json  |  2 +-
 setupBabel.js | 41 ++---------------------------------------
 2 files changed, 3 insertions(+), 40 deletions(-)

diff --git a/package.json b/package.json
index 603b8808007d..ced5fcabbd63 100644
--- a/package.json
+++ b/package.json
@@ -167,7 +167,7 @@
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
     "metro": "^0.34.0",
-    "metro-babel-register": "^0.34.1",
+    "metro-babel-register": "^0.34.2",
     "metro-core": "^0.34.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
diff --git a/setupBabel.js b/setupBabel.js
index 28b208e05a99..96b54429d7cf 100644
--- a/setupBabel.js
+++ b/setupBabel.js
@@ -8,43 +8,8 @@
 'use strict';
 
 const babelRegisterOnly = require('metro-babel-register');
-const escapeRegExp = require('lodash/escapeRegExp');
-const path = require('path');
 
-const BABEL_ENABLED_PATHS = ['local-cli', 'metro'];
-
-/**
- * We use absolute paths for matching only the top-level folders reliably. For
- * example, we would not want to match some deeply nested forder that happens to
- * have the same name as one of `BABEL_ENABLED_PATHS`.
- */
-function buildRegExps(basePath, dirPaths) {
-  return dirPaths.map(
-    folderPath =>
-      folderPath === 'metro'
-        // metro uses flow (for example) which needs to be stripped out w/babel.
-        // it'll resolve to .../metro/src/index.js we want root
-        ? path.resolve(require.resolve('metro'), '..')
-        // Babel `only` option works with forward slashes in the RegExp so replace
-        // backslashes for Windows.
-        : folderPath instanceof RegExp
-          ? new RegExp(
-              `^${escapeRegExp(
-                path.resolve(basePath, '.').replace(/\\/g, '/')
-              )}/${folderPath.source}`,
-              folderPath.flags
-            )
-          : new RegExp(
-              `^${escapeRegExp(
-                path.resolve(basePath, folderPath).replace(/\\/g, '/')
-              )}`
-            )
-  );
-}
-
-function getOnlyList() {
-  return buildRegExps(__dirname, BABEL_ENABLED_PATHS);
-}
+const BABEL_ENABLED_PATHS = ['local-cli'];
 
 /**
  * Centralized place to register all the directories that need a Babel
@@ -52,9 +17,7 @@ function getOnlyList() {
  * support Flow type annotations.
  */
 function setupBabel() {
-  babelRegisterOnly(getOnlyList());
+  babelRegisterOnly(babelRegisterOnly.buildRegExps(__dirname, BABEL_ENABLED_PATHS));
 }
 
-setupBabel.buildRegExps = buildRegExps;
-setupBabel.getOnlyList = getOnlyList;
 module.exports = setupBabel;

From 37d28be2d97df0310d1918b258b40815c8346209 Mon Sep 17 00:00:00 2001
From: Max Sherman <jonaldislarry@fb.com>
Date: Mon, 23 Apr 2018 22:05:32 -0700
Subject: [PATCH 0366/1109] Fix stacktrace parsing for JS

Reviewed By: adamjernst, indragiek

Differential Revision: D7734756

fbshipit-source-id: 7111932386bb5fede83b5f55a946549b1dc6c402
---
 .../react/devsupport/StackTraceHelper.java    | 24 ++++++++++++-------
 .../devsupport/StackTraceHelperTest.java      | 10 ++++++++
 2 files changed, 26 insertions(+), 8 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/StackTraceHelper.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/StackTraceHelper.java
index 75ca90d53291..3e66d52e61ac 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/StackTraceHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/StackTraceHelper.java
@@ -28,8 +28,10 @@ public class StackTraceHelper {
   public static final java.lang.String COLUMN_KEY = "column";
   public static final java.lang.String LINE_NUMBER_KEY = "lineNumber";
 
-  private static final Pattern STACK_FRAME_PATTERN = Pattern.compile(
+  private static final Pattern STACK_FRAME_PATTERN1 = Pattern.compile(
       "^(?:(.*?)@)?(.*?)\\:([0-9]+)\\:([0-9]+)$");
+  private static final Pattern STACK_FRAME_PATTERN2 = Pattern.compile(
+      "\\s*(?:at)\\s*(.+?)\\s*[@(](.*):([0-9]+):([0-9]+)[)]$");
 
   /**
    * Represents a generic entry in a stack trace, be it originally from JS or Java.
@@ -175,16 +177,22 @@ public static StackFrame[] convertJsStackTrace(String stack) {
     String[] stackTrace = stack.split("\n");
     StackFrame[] result = new StackFrame[stackTrace.length];
     for (int i = 0; i < stackTrace.length; ++i) {
-      Matcher matcher = STACK_FRAME_PATTERN.matcher(stackTrace[i]);
-      if (matcher.find()) {
-        result[i] = new StackFrameImpl(
-          matcher.group(2),
-          matcher.group(1) == null ? "(unknown)" : matcher.group(1),
-          Integer.parseInt(matcher.group(3)),
-          Integer.parseInt(matcher.group(4)));
+      Matcher matcher1 = STACK_FRAME_PATTERN1.matcher(stackTrace[i]);
+      Matcher matcher2 = STACK_FRAME_PATTERN2.matcher(stackTrace[i]);
+      Matcher matcher;
+      if (matcher2.find()) {
+        matcher = matcher2;
+      } else if (matcher1.find()) {
+        matcher = matcher1;
       } else {
         result[i] = new StackFrameImpl(null, stackTrace[i], -1, -1);
+        continue;
       }
+      result[i] = new StackFrameImpl(
+        matcher.group(2),
+        matcher.group(1) == null ? "(unknown)" : matcher.group(1),
+        Integer.parseInt(matcher.group(3)),
+        Integer.parseInt(matcher.group(4)));
     }
     return result;
   }
diff --git a/ReactAndroid/src/test/java/com/facebook/react/devsupport/StackTraceHelperTest.java b/ReactAndroid/src/test/java/com/facebook/react/devsupport/StackTraceHelperTest.java
index b348bd14995d..70b64184bcb5 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/devsupport/StackTraceHelperTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/devsupport/StackTraceHelperTest.java
@@ -17,6 +17,16 @@
 @RunWith(RobolectricTestRunner.class)
 public class StackTraceHelperTest {
 
+  @Test
+  public void testParseAlternateFormatStackFrameWithMethod() {
+    final StackFrame frame = StackTraceHelper.convertJsStackTrace(
+        "at func1 (/path/to/file.js:2:18)")[0];
+    assertThat(frame.getMethod()).isEqualTo("func1");
+    assertThat(frame.getFileName()).isEqualTo("file.js");
+    assertThat(frame.getLine()).isEqualTo(2);
+    assertThat(frame.getColumn()).isEqualTo(18);
+  }
+
   @Test
   public void testParseStackFrameWithMethod() {
     final StackFrame frame = StackTraceHelper.convertJsStackTrace(

From 9909a4243f7154c8f817489599702e8155c2beb2 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 24 Apr 2018 02:00:09 -0700
Subject: [PATCH 0367/1109] iOS: RCTTestRunner should deallocate rootview
 before invalidating the bridge

Summary: There are cases of race condition where the react component being mounted is calling a nativemodule from JS *right after* the test runner starts invalidating the bridge. This causes assertion failure deep in the RCTModuleData such that the bridge doesn't complete the invalidation. To avoid this, unmount and deallocate the RCTRootView before invalidating the bridge.

Reviewed By: sahrens

Differential Revision: D7727249

fbshipit-source-id: 8b82edc3b795ceb2e32441f16e225d723fcd9be1
---
 Libraries/RCTTest/RCTTestRunner.m | 61 ++++++++++++++++++++-----------
 1 file changed, 40 insertions(+), 21 deletions(-)

diff --git a/Libraries/RCTTest/RCTTestRunner.m b/Libraries/RCTTest/RCTTestRunner.m
index 00e97137282d..315371f4abfb 100644
--- a/Libraries/RCTTest/RCTTestRunner.m
+++ b/Libraries/RCTTest/RCTTestRunner.m
@@ -12,6 +12,7 @@
 #import <React/RCTDevSettings.h>
 #import <React/RCTLog.h>
 #import <React/RCTRootView.h>
+#import <React/RCTUIManager.h>
 #import <React/RCTUtils.h>
 
 #import "FBSnapshotTestController.h"
@@ -113,6 +114,7 @@ - (void)runTest:(SEL)test module:(NSString *)moduleName
 expectErrorBlock:(BOOL(^)(NSString *error))expectErrorBlock
 {
   __weak RCTBridge *batchedBridge;
+  NSNumber *rootTag;
 
   @autoreleasepool {
     __block NSMutableArray<NSString *> *errors = nil;
@@ -133,35 +135,42 @@ - (void)runTest:(SEL)test module:(NSString *)moduleName
     [bridge.devSettings setIsDebuggingRemotely:_useJSDebugger];
     batchedBridge = [bridge batchedBridge];
 
-    RCTRootView *rootView = [[RCTRootView alloc] initWithBridge:bridge moduleName:moduleName initialProperties:initialProps];
-#if TARGET_OS_TV
-    rootView.frame = CGRectMake(0, 0, 1920, 1080); // Standard screen size for tvOS
-#else
-    rootView.frame = CGRectMake(0, 0, 320, 2000); // Constant size for testing on multiple devices
-#endif
+    UIViewController *vc = RCTSharedApplication().delegate.window.rootViewController;
+    vc.view = [UIView new];
 
-    RCTTestModule *testModule = [rootView.bridge moduleForClass:[RCTTestModule class]];
+    RCTTestModule *testModule = [bridge moduleForClass:[RCTTestModule class]];
     RCTAssert(_testController != nil, @"_testController should not be nil");
     testModule.controller = _testController;
     testModule.testSelector = test;
     testModule.testSuffix = _testSuffix;
-    testModule.view = rootView;
 
-    UIViewController *vc = RCTSharedApplication().delegate.window.rootViewController;
-    vc.view = [UIView new];
-    [vc.view addSubview:rootView]; // Add as subview so it doesn't get resized
+    @autoreleasepool {
+      // The rootView needs to be deallocated after this @autoreleasepool block exits.
+      RCTRootView *rootView = [[RCTRootView alloc] initWithBridge:bridge moduleName:moduleName initialProperties:initialProps];
+#if TARGET_OS_TV
+      rootView.frame = CGRectMake(0, 0, 1920, 1080); // Standard screen size for tvOS
+#else
+      rootView.frame = CGRectMake(0, 0, 320, 2000); // Constant size for testing on multiple devices
+#endif
 
-    if (configurationBlock) {
-      configurationBlock(rootView);
-    }
+      rootTag = rootView.reactTag;
+      testModule.view = rootView;
 
-    NSDate *date = [NSDate dateWithTimeIntervalSinceNow:kTestTimeoutSeconds];
-    while (date.timeIntervalSinceNow > 0 && testModule.status == RCTTestStatusPending && errors == nil) {
-      [[NSRunLoop mainRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]];
-      [[NSRunLoop mainRunLoop] runMode:NSRunLoopCommonModes beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]];
-    }
+      [vc.view addSubview:rootView]; // Add as subview so it doesn't get resized
+
+      if (configurationBlock) {
+        configurationBlock(rootView);
+      }
 
-    [rootView removeFromSuperview];
+      NSDate *date = [NSDate dateWithTimeIntervalSinceNow:kTestTimeoutSeconds];
+      while (date.timeIntervalSinceNow > 0 && testModule.status == RCTTestStatusPending && errors == nil) {
+        [[NSRunLoop mainRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]];
+        [[NSRunLoop mainRunLoop] runMode:NSRunLoopCommonModes beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]];
+      }
+
+      [rootView removeFromSuperview];
+      testModule.view = nil;
+    }
 
     RCTSetLogFunction(defaultLogFunction);
 
@@ -181,15 +190,25 @@ - (void)runTest:(SEL)test module:(NSString *)moduleName
       RCTAssert(testModule.status == RCTTestStatusPassed, @"Test failed");
     }
 
+    // Wait for the rootView to be deallocated completely before invalidating the bridge.
+    RCTUIManager *uiManager = [bridge moduleForClass:[RCTUIManager class]];
+    NSDate *date = [NSDate dateWithTimeIntervalSinceNow:5];
+    while (date.timeIntervalSinceNow > 0 && [uiManager viewForReactTag:rootTag]) {
+      [[NSRunLoop mainRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]];
+      [[NSRunLoop mainRunLoop] runMode:NSRunLoopCommonModes beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]];
+    }
+    RCTAssert([uiManager viewForReactTag:rootTag] == nil, @"RootView should have been deallocated after removed.");
+
     [bridge invalidate];
   }
 
-  // Give the bridge a chance to disappear before continuing to the next test.
+  // Wait for the bridge to disappear before continuing to the next test.
   NSDate *invalidateTimeout = [NSDate dateWithTimeIntervalSinceNow:30];
   while (invalidateTimeout.timeIntervalSinceNow > 0 && batchedBridge != nil) {
     [[NSRunLoop mainRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]];
     [[NSRunLoop mainRunLoop] runMode:NSRunLoopCommonModes beforeDate:[NSDate dateWithTimeIntervalSinceNow:0.1]];
   }
+  RCTAssert(batchedBridge == nil, @"Bridge should be deallocated after the test");
 }
 
 @end

From 6b07602915157f54c39adbf0f9746ac056ad2d13 Mon Sep 17 00:00:00 2001
From: liangtongchuan <liangtongchuan@bantus.com>
Date: Tue, 24 Apr 2018 09:43:16 -0700
Subject: [PATCH 0368/1109] Update fresco to v1.9.0, okhttp3 to v3.10.0

Summary:
I found many crash reports of imagepipeline in our android app,
this is caused by fresco webp native memory leak, they have fixed it in v1.9.0
fixed wrong pull request of [18848](https://github.com/facebook/react-native/pull/18848)

    Test with local build.
    Check CI passes.

    [ANDROID] [ENHANCEMENT] [Fresco/OkHttp] - Updates Fresco to 1.9.0, OkHttp to 3.10.0
Closes https://github.com/facebook/react-native/pull/18849

Differential Revision: D7651377

Pulled By: mdvacca

fbshipit-source-id: 0bfe79fd3d232b11a6a9380c961b9401c9e0ced9
---
 ReactAndroid/build.gradle                     |  8 +++----
 .../libraries/fresco/fresco-react-native/BUCK | 24 +++++++++----------
 .../src/main/third-party/java/okhttp/BUCK     |  8 +++----
 3 files changed, 20 insertions(+), 20 deletions(-)

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index eecfe6929779..503b814f32ac 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -294,12 +294,12 @@ dependencies {
     compile 'javax.inject:javax.inject:1'
     compile 'com.android.support:appcompat-v7:23.0.1'
     compile 'com.facebook.fbui.textlayoutbuilder:textlayoutbuilder:1.0.0'
-    compile 'com.facebook.fresco:fresco:1.8.1'
-    compile 'com.facebook.fresco:imagepipeline-okhttp3:1.8.1'
+    compile 'com.facebook.fresco:fresco:1.9.0'
+    compile 'com.facebook.fresco:imagepipeline-okhttp3:1.9.0'
     compile 'com.facebook.soloader:soloader:0.3.0'
     compile 'com.google.code.findbugs:jsr305:3.0.0'
-    compile 'com.squareup.okhttp3:okhttp:3.8.0'
-    compile 'com.squareup.okhttp3:okhttp-urlconnection:3.8.0'
+    compile 'com.squareup.okhttp3:okhttp:3.10.0'
+    compile 'com.squareup.okhttp3:okhttp-urlconnection:3.10.0'
     compile 'com.squareup.okio:okio:1.14.0'
     compile 'org.webkit:android-jsc:r174650'
 
diff --git a/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK b/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
index 33ceb77095e7..e4a46ecc3f86 100644
--- a/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
+++ b/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
@@ -8,8 +8,8 @@ rn_android_prebuilt_aar(
 
 remote_file(
     name = "fresco-binary-aar",
-    sha1 = "c6ed3f696ed47dca3b20d4ffbd0600c94b9119b2",
-    url = "mvn:com.facebook.fresco:fresco:aar:1.8.1",
+    sha1 = "f4415e8676eef4d12fdc8ddbd784bb752cf0c5e3",
+    url = "mvn:com.facebook.fresco:fresco:aar:1.9.0",
 )
 
 android_prebuilt_aar(
@@ -20,8 +20,8 @@ android_prebuilt_aar(
 
 remote_file(
     name = "drawee-binary-aar",
-    sha1 = "6bc689901ddcac8f3df5ba4db1f8aabeb8e80107",
-    url = "mvn:com.facebook.fresco:drawee:aar:1.8.1",
+    sha1 = "e0c3b0fa64fc7525f05a852476bc8723ae6ddc90",
+    url = "mvn:com.facebook.fresco:drawee:aar:1.9.0",
 )
 
 rn_android_library(
@@ -42,8 +42,8 @@ rn_android_prebuilt_aar(
 
 remote_file(
     name = "imagepipeline-base-aar",
-    sha1 = "42fd80c46a853850dfc0d71808b982fef401c841",
-    url = "mvn:com.facebook.fresco:imagepipeline-base:aar:1.8.1",
+    sha1 = "8034e5c8a75385bd20e72ff51489b0673029fcf7",
+    url = "mvn:com.facebook.fresco:imagepipeline-base:aar:1.9.0",
 )
 
 rn_android_prebuilt_aar(
@@ -54,8 +54,8 @@ rn_android_prebuilt_aar(
 
 remote_file(
     name = "imagepipeline-aar",
-    sha1 = "06a2a4c3e1d9a7fb7d7f1ad14db63e2d32ef0b61",
-    url = "mvn:com.facebook.fresco:imagepipeline:aar:1.8.1",
+    sha1 = "8043733b1bf3713d3a3c7fc7896205c96c050fd7",
+    url = "mvn:com.facebook.fresco:imagepipeline:aar:1.9.0",
 )
 
 rn_prebuilt_jar(
@@ -78,8 +78,8 @@ android_prebuilt_aar(
 
 remote_file(
     name = "fbcore-aar",
-    sha1 = "99b7a83946e16f037149e4cd3abfd6840a09445d",
-    url = "mvn:com.facebook.fresco:fbcore:aar:1.8.1",
+    sha1 = "fc3703511dc7b135bcd0e76d8015cdaf247b1760",
+    url = "mvn:com.facebook.fresco:fbcore:aar:1.9.0",
 )
 
 android_prebuilt_aar(
@@ -90,6 +90,6 @@ android_prebuilt_aar(
 
 remote_file(
     name = "imagepipeline-okhttp3-binary-aar",
-    sha1 = "751f19412e1843b1c1e76eae46e388fb1deddbcc",
-    url = "mvn:com.facebook.fresco:imagepipeline-okhttp3:aar:1.8.1",
+    sha1 = "4ac95941c1761a1ba5647ed551f7e47a5c417c7b",
+    url = "mvn:com.facebook.fresco:imagepipeline-okhttp3:aar:1.9.0",
 )
diff --git a/ReactAndroid/src/main/third-party/java/okhttp/BUCK b/ReactAndroid/src/main/third-party/java/okhttp/BUCK
index 84be571ad87c..549c3f457862 100644
--- a/ReactAndroid/src/main/third-party/java/okhttp/BUCK
+++ b/ReactAndroid/src/main/third-party/java/okhttp/BUCK
@@ -6,8 +6,8 @@ prebuilt_jar(
 
 remote_file(
     name = "okhttp3-binary-jar",
-    sha1 = "5a11f020cce2d11eb71ba916700600e18c4547e7",
-    url = "mvn:com.squareup.okhttp3:okhttp:jar:3.8.0",
+    sha1 = "7ef0f1d95bf4c0b3ba30bbae25e0e562b05cf75e",
+    url = "mvn:com.squareup.okhttp3:okhttp:jar:3.10.0",
 )
 
 prebuilt_jar(
@@ -18,6 +18,6 @@ prebuilt_jar(
 
 remote_file(
     name = "okhttp3-urlconnection-binary-jar",
-    sha1 = "265257b82f20bb0371a926cc8ceb5f7bb17c0df8",
-    url = "mvn:com.squareup.okhttp3:okhttp-urlconnection:jar:3.8.0",
+    sha1 = "ec614c05825ddd2267677a99f585d3913474b125",
+    url = "mvn:com.squareup.okhttp3:okhttp-urlconnection:jar:3.10.0",
 )

From 16a5324ca610e7841a2e06b73110ae968aaadd7c Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 24 Apr 2018 12:31:56 -0700
Subject: [PATCH 0369/1109] Introducing ViewType in native code

Reviewed By: achen1

Differential Revision: D7729477

fbshipit-source-id: e8d1af87489522c4ae8b52b6a9e4c0a680abf4f6
---
 .../com/facebook/react/uimanager/common/BUCK  |  4 +++
 .../react/uimanager/common/ViewType.java      | 21 ++++++++++++++
 .../react/uimanager/common/ViewUtil.java      | 29 +++++++++++++++++++
 3 files changed, 54 insertions(+)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewType.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewUtil.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/BUCK b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/BUCK
index 5c4a5b26df61..08230b0a0be1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/BUCK
@@ -3,6 +3,10 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_
 rn_android_library(
     name = "common",
     srcs = glob(["*.java"]),
+    provided_deps = [
+        react_native_dep("third-party/android/support/v4:lib-support-v4"),
+        react_native_dep("third-party/android/support-annotations:android-support-annotations"),
+    ],
     visibility = [
         "PUBLIC",
     ],
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewType.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewType.java
new file mode 100644
index 000000000000..66e4fdbecd44
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewType.java
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+package com.facebook.react.uimanager.common;
+
+import static com.facebook.react.uimanager.common.ViewType.FABRIC;
+import static com.facebook.react.uimanager.common.ViewType.PAPER;
+import static java.lang.annotation.RetentionPolicy.SOURCE;
+
+import java.lang.annotation.Retention;
+import android.support.annotation.IntDef;
+
+@Retention(SOURCE)
+@IntDef({PAPER, FABRIC})
+public @interface ViewType {
+  int PAPER = 1;
+  int FABRIC = 2;
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewUtil.java
new file mode 100644
index 000000000000..cc7a3ddcbd04
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewUtil.java
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.uimanager.common;
+
+import static com.facebook.react.uimanager.common.ViewType.FABRIC;
+import static com.facebook.react.uimanager.common.ViewType.PAPER;
+
+public class ViewUtil {
+
+  /**
+   * Counter for uniquely identifying views.
+   * - % 10 === 1 means it is a rootTag.
+   * - % 2 === 0 means it is a Fabric tag.
+   * See https://github.com/facebook/react/pull/12587
+   *
+   * @param reactTag {@link }
+   */
+  @ViewType
+  public static int getViewType(int reactTag) {
+    if (reactTag % 2 == 0) return FABRIC;
+    return PAPER;
+  }
+
+}

From f44e78df55a3b4b794c32fc6682130160ed1d6f2 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 24 Apr 2018 12:37:08 -0700
Subject: [PATCH 0370/1109] Add InstanceHandle parameter into FabricJSC/JSI

Reviewed By: achen1

Differential Revision: D7644487

fbshipit-source-id: b49381a58a791043bf61b8ac5f065817caff7c95
---
 .../react/fabric/FabricUIManager.java         |  2 +-
 .../react/fabric/jsc/jni/FabricJSCBinding.cpp |  7 +++---
 .../react/fabric/FabricUIManagerTest.java     | 22 +++++++++++--------
 3 files changed, 17 insertions(+), 14 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 191d463ab725..cd6045f00d88 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -67,7 +67,7 @@ public FabricUIManager(
   /** Creates a new {@link ReactShadowNode} */
   @Nullable
   public ReactShadowNode createNode(
-      int reactTag, String viewName, int rootTag, ReadableNativeMap props) {
+      int reactTag, String viewName, int rootTag, ReadableNativeMap props, int instanceHandle) {
     if (DEBUG) {
       Log.d(TAG, "createNode \n\ttag: " + reactTag +
           "\n\tviewName: " + viewName +
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
index 6ce8b9976e34..83023f488aa7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
@@ -83,17 +83,16 @@ JSValueRef createNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisOb
 
   static auto createNode =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(jint, jstring, jint, ReadableNativeMap::javaobject)>("createNode");
+      ->getMethod<alias_ref<JShadowNode>(jint, jstring, jint, ReadableNativeMap::javaobject, jint)>("createNode");
 
   int reactTag = (int)JSC_JSValueToNumber(ctx, arguments[0], NULL);
   auto viewName = JSValueToJString(ctx, arguments[1]);
   int rootTag = (int)JSC_JSValueToNumber(ctx, arguments[2], NULL);
   auto props = JSC_JSValueIsNull(ctx, arguments[3]) ? local_ref<ReadableNativeMap::jhybridobject>(nullptr) :
                JSValueToReadableMapViaJSON(ctx, arguments[3]);;
+  int instanceHandle = (int)JSC_JSValueToNumber(ctx, arguments[4], NULL);
 
-  // TODO: Retain object in arguments[4] using a weak ref.
-
-  auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get());
+  auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get(), instanceHandle);
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(node.get()));
 }
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 441003004bd1..32a0bbb40015 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -47,6 +47,7 @@ public class FabricUIManagerTest {
   private FabricUIManager mFabricUIManager;
   private ThemedReactContext mThemedReactContext;
   private int mNextReactTag;
+  private int mNextInstanceHandle;
 
   @Before
   public void setUp() throws Exception {
@@ -70,8 +71,10 @@ public void testCreateNode() {
         new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
     int rootTag = mFabricUIManager.addRootView(rootView);
     int reactTag = mNextReactTag++;
+    int instanceHandle = mNextInstanceHandle++;
     String viewClass = ReactViewManager.REACT_CLASS;
-    ReactShadowNode node = mFabricUIManager.createNode(reactTag, viewClass, rootTag, null);
+    ReactShadowNode node =
+        mFabricUIManager.createNode(reactTag, viewClass, rootTag, null, instanceHandle);
 
     assertThat(reactTag).isEqualTo(node.getReactTag());
     assertThat(viewClass).isEqualTo(node.getViewClass());
@@ -89,8 +92,10 @@ private int createAndRenderRootView() {
         new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
     int rootTag = mFabricUIManager.addRootView(rootView);
     int reactTag = mNextReactTag++;
+    int instanceHandle = mNextInstanceHandle++;
     String viewClass = ReactViewManager.REACT_CLASS;
-    ReactShadowNode node = mFabricUIManager.createNode(reactTag, viewClass, rootTag, null);
+    ReactShadowNode node =
+        mFabricUIManager.createNode(reactTag, viewClass, rootTag, null, instanceHandle);
 
     List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(rootTag);
     mFabricUIManager.appendChildToSet(childSet, node);
@@ -220,9 +225,8 @@ public void testTextMutableClone() {
     ReactRootView rootView =
         new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
     int rootTag = mFabricUIManager.addRootView(rootView);
-
     ReactShadowNode text =
-        mFabricUIManager.createNode(0, ReactTextViewManager.REACT_CLASS, rootTag, null);
+        mFabricUIManager.createNode(0, ReactTextViewManager.REACT_CLASS, rootTag, null, mNextInstanceHandle++);
     assertThat(text.isMeasureDefined()).isTrue();
 
     ReactShadowNode textCopy = text.mutableCopy();
@@ -248,13 +252,13 @@ public void testRemoveOriginalNodeReferences() {
     int rootTag = mFabricUIManager.addRootView(rootView);
     String viewClass = ReactViewManager.REACT_CLASS;
 
-    ReactShadowNode aa = mFabricUIManager.createNode(2, viewClass, rootTag, null);
-    ReactShadowNode a = mFabricUIManager.createNode(3, viewClass, rootTag, null);
+    ReactShadowNode aa = mFabricUIManager.createNode(2, viewClass, rootTag, null, mNextInstanceHandle++);
+    ReactShadowNode a = mFabricUIManager.createNode(3, viewClass, rootTag, null, mNextInstanceHandle++);
     mFabricUIManager.appendChild(a, aa);
-    ReactShadowNode bb = mFabricUIManager.createNode(4, viewClass, rootTag, null);
-    ReactShadowNode b = mFabricUIManager.createNode(5, viewClass, rootTag, null);
+    ReactShadowNode bb = mFabricUIManager.createNode(4, viewClass, rootTag, null, mNextInstanceHandle++);
+    ReactShadowNode b = mFabricUIManager.createNode(5, viewClass, rootTag, null, mNextInstanceHandle++);
     mFabricUIManager.appendChild(b, bb);
-    ReactShadowNode container = mFabricUIManager.createNode(6, viewClass, rootTag, null);
+    ReactShadowNode container = mFabricUIManager.createNode(6, viewClass, rootTag, null, mNextInstanceHandle++);
     mFabricUIManager.appendChild(container, a);
     mFabricUIManager.appendChild(container, b);
     List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(rootTag);

From 4a802100d16ee9f52e6e4caea6e54b9a49694351 Mon Sep 17 00:00:00 2001
From: Alex McKelvey <alexmck@fb.com>
Date: Tue, 24 Apr 2018 13:40:27 -0700
Subject: [PATCH 0371/1109] Improve VirtualizedList yellow-box warning when
 item is missing a key

Reviewed By: sahrens

Differential Revision: D7746659

fbshipit-source-id: b271dcd604d9adb85d0996dce5b8af1a6efd37d2
---
 Libraries/Lists/VirtualizedList.js | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 30e8777eaee4..bbfc6cf3bdec 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -218,6 +218,7 @@ type OptionalProps = {
 export type Props = RequiredProps & OptionalProps;
 
 let _usedIndexForKey = false;
+let _keylessItemComponentName: string = '';
 
 type Frame = {
   offset: number,
@@ -431,6 +432,9 @@ class VirtualizedList extends React.PureComponent<Props, State> {
         return item.key;
       }
       _usedIndexForKey = true;
+      if (item.type && item.type.displayName) {
+        _keylessItemComponentName = item.type.displayName;
+      }
       return String(index);
     },
     maxToRenderPerBatch: 10,
@@ -762,6 +766,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
     const itemCount = this.props.getItemCount(data);
     if (itemCount > 0) {
       _usedIndexForKey = false;
+      _keylessItemComponentName = '';
       const spacerKey = !horizontal ? 'height' : 'width';
       const lastInitialIndex = this.props.initialScrollIndex
         ? -1
@@ -831,6 +836,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
         console.warn(
           'VirtualizedList: missing keys for items, make sure to specify a key property on each ' +
             'item or provide a custom keyExtractor.',
+          _keylessItemComponentName,
         );
         this._hasWarned.keys = true;
       }

From d5e9e55fa38c574bce6c04cbcaf6b144b87fa17f Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rub=C3=A9n=20Norte?= <rubennorte@fb.com>
Date: Wed, 25 Apr 2018 07:00:46 -0700
Subject: [PATCH 0372/1109] Remove @providesModule from all modules

Summary:
This PR removes the need for having the `providesModule` tags in all the modules in the repository.

It configures Flow, Jest and Metro to get the module names from the filenames (`Libraries/Animated/src/nodes/AnimatedInterpolation.js` => `AnimatedInterpolation`)

* Checked the Flow configuration by running flow on the project root (no errors):

```
yarn flow
```

* Checked the Jest configuration by running the tests with a clean cache:

```
yarn jest --clearCache && yarn test
```

* Checked the Metro configuration by starting the server with a clean cache and requesting some bundles:

```
yarn run start --reset-cache
curl 'localhost:8081/IntegrationTests/AccessibilityManagerTest.bundle?platform=android'
curl 'localhost:8081/Libraries/Alert/Alert.bundle?platform=ios'
```

[INTERNAL] [FEATURE] [All] - Removed providesModule from all modules and configured tools.
Closes https://github.com/facebook/react-native/pull/18995

Reviewed By: mjesun

Differential Revision: D7729509

Pulled By: rubennorte

fbshipit-source-id: 892f760a05ce1fddb088ff0cd2e97e521fb8e825
---
 .flowconfig                                   | 17 +++++
 IntegrationTests/AccessibilityManagerTest.js  |  1 -
 IntegrationTests/AppEventsTest.js             |  1 -
 IntegrationTests/AsyncStorageTest.js          |  1 -
 IntegrationTests/ImageCachePolicyTest.js      |  1 -
 IntegrationTests/ImageSnapshotTest.js         |  1 -
 .../IntegrationTestHarnessTest.js             |  1 -
 IntegrationTests/IntegrationTestsApp.js       |  1 -
 IntegrationTests/LayoutEventsTest.js          |  1 -
 IntegrationTests/LoggingTestModule.js         |  1 -
 IntegrationTests/PromiseTest.js               |  1 -
 IntegrationTests/PropertiesUpdateTest.js      |  1 -
 .../RCTRootViewIntegrationTestApp.js          |  1 -
 .../ReactContentSizeUpdateTest.js             |  1 -
 IntegrationTests/SimpleSnapshotTest.js        |  1 -
 IntegrationTests/SizeFlexibilityUpdateTest.js |  1 -
 IntegrationTests/SyncMethodTest.js            |  1 -
 IntegrationTests/TimersTest.js                |  1 -
 IntegrationTests/WebSocketTest.js             |  1 -
 IntegrationTests/WebViewTest.js               |  1 -
 .../websocket_integration_test_server.js      |  1 -
 Libraries/ART/ARTSerializablePath.js          |  1 -
 Libraries/ART/ReactNativeART.js               |  1 -
 Libraries/ActionSheetIOS/ActionSheetIOS.js    |  1 -
 Libraries/Alert/Alert.js                      |  1 -
 Libraries/Alert/AlertIOS.js                   |  1 -
 Libraries/Alert/RCTAlertManager.android.js    |  1 -
 Libraries/Alert/RCTAlertManager.ios.js        |  1 -
 Libraries/Animated/release/gulpfile.js        |  1 -
 Libraries/Animated/src/Animated.js            |  1 -
 Libraries/Animated/src/AnimatedEvent.js       |  1 -
 .../Animated/src/AnimatedImplementation.js    |  1 -
 Libraries/Animated/src/AnimatedWeb.js         |  1 -
 Libraries/Animated/src/Easing.js              |  1 -
 .../Animated/src/NativeAnimatedHelper.js      |  1 -
 Libraries/Animated/src/SpringConfig.js        |  1 -
 .../Animated/src/animations/Animation.js      |  1 -
 .../Animated/src/animations/DecayAnimation.js |  1 -
 .../src/animations/SpringAnimation.js         |  1 -
 .../src/animations/TimingAnimation.js         |  1 -
 Libraries/Animated/src/bezier.js              |  1 -
 .../Animated/src/createAnimatedComponent.js   |  1 -
 .../Animated/src/nodes/AnimatedAddition.js    |  1 -
 .../Animated/src/nodes/AnimatedDiffClamp.js   |  1 -
 .../Animated/src/nodes/AnimatedDivision.js    |  1 -
 .../src/nodes/AnimatedInterpolation.js        |  1 -
 .../Animated/src/nodes/AnimatedModulo.js      |  1 -
 .../src/nodes/AnimatedMultiplication.js       |  1 -
 Libraries/Animated/src/nodes/AnimatedNode.js  |  1 -
 Libraries/Animated/src/nodes/AnimatedProps.js |  1 -
 Libraries/Animated/src/nodes/AnimatedStyle.js |  1 -
 .../Animated/src/nodes/AnimatedSubtraction.js |  1 -
 .../Animated/src/nodes/AnimatedTracking.js    |  1 -
 .../Animated/src/nodes/AnimatedTransform.js   |  1 -
 Libraries/Animated/src/nodes/AnimatedValue.js |  1 -
 .../Animated/src/nodes/AnimatedValueXY.js     |  1 -
 .../src/nodes/AnimatedWithChildren.js         |  1 -
 Libraries/AppState/AppState.js                |  1 -
 Libraries/BatchedBridge/BatchedBridge.js      |  1 -
 Libraries/BatchedBridge/MessageQueue.js       |  1 -
 Libraries/BatchedBridge/NativeModules.js      |  1 -
 Libraries/Blob/Blob.js                        |  1 -
 Libraries/Blob/BlobManager.js                 |  1 -
 Libraries/Blob/BlobRegistry.js                |  1 -
 Libraries/Blob/BlobTypes.js                   |  1 -
 Libraries/Blob/File.js                        |  1 -
 Libraries/Blob/FileReader.js                  |  1 -
 Libraries/Blob/URL.js                         |  1 -
 Libraries/BugReporting/BugReporting.js        |  1 -
 Libraries/BugReporting/dumpReactTree.js       |  1 -
 Libraries/BugReporting/getReactData.js        |  1 -
 Libraries/CameraRoll/CameraRoll.js            |  1 -
 Libraries/CameraRoll/ImagePickerIOS.js        |  1 -
 Libraries/Color/normalizeColor.js             |  1 -
 .../AccessibilityInfo.android.js              |  1 -
 .../AccessibilityInfo.ios.js                  |  1 -
 .../ActivityIndicator/ActivityIndicator.js    |  1 -
 .../Components/AppleTV/TVEventHandler.js      |  1 -
 .../Components/AppleTV/TVViewPropTypes.js     |  1 -
 Libraries/Components/Button.js                |  1 -
 .../Components/CheckBox/CheckBox.android.js   |  1 -
 Libraries/Components/CheckBox/CheckBox.ios.js |  1 -
 Libraries/Components/Clipboard/Clipboard.js   |  1 -
 .../DatePicker/DatePickerIOS.android.js       |  1 -
 .../DatePicker/DatePickerIOS.ios.js           |  1 -
 .../DatePickerAndroid.android.js              |  1 -
 .../DatePickerAndroid.ios.js                  |  1 -
 .../DrawerLayoutAndroid.android.js            |  1 -
 .../DrawerAndroid/DrawerLayoutAndroid.ios.js  |  1 -
 Libraries/Components/Keyboard/Keyboard.js     |  1 -
 .../Keyboard/KeyboardAvoidingView.js          |  1 -
 Libraries/Components/LazyRenderer.js          |  1 -
 .../MaskedView/MaskedViewIOS.android.js       |  1 -
 .../MaskedView/MaskedViewIOS.ios.js           |  1 -
 .../Navigation/NavigatorIOS.android.js        |  1 -
 .../Components/Navigation/NavigatorIOS.ios.js |  1 -
 Libraries/Components/Picker/Picker.js         |  1 -
 .../Picker/PickerAndroid.android.js           |  1 -
 .../Components/Picker/PickerAndroid.ios.js    |  1 -
 .../Components/Picker/PickerIOS.android.js    |  1 -
 Libraries/Components/Picker/PickerIOS.ios.js  |  1 -
 .../ProgressBarAndroid.android.js             |  1 -
 .../ProgressBarAndroid.ios.js                 |  1 -
 .../ProgressViewIOS.android.js                |  1 -
 .../ProgressViewIOS/ProgressViewIOS.ios.js    |  1 -
 .../RefreshControl/RefreshControl.js          |  1 -
 .../SafeAreaView/SafeAreaView.android.js      |  1 -
 .../SafeAreaView/SafeAreaView.ios.js          |  1 -
 Libraries/Components/ScrollResponder.js       |  1 -
 Libraries/Components/ScrollView/ScrollView.js |  1 -
 .../ScrollView/ScrollViewStickyHeader.js      |  1 -
 .../ScrollView/processDecelerationRate.js     |  1 -
 .../SegmentedControlIOS.android.js            |  1 -
 .../SegmentedControlIOS.ios.js                |  1 -
 Libraries/Components/Slider/Slider.js         |  1 -
 Libraries/Components/StaticContainer.react.js |  1 -
 Libraries/Components/StaticRenderer.js        |  1 -
 Libraries/Components/StatusBar/StatusBar.js   |  1 -
 .../StatusBar/StatusBarIOS.android.js         |  1 -
 .../Components/StatusBar/StatusBarIOS.ios.js  |  1 -
 Libraries/Components/Subscribable.js          |  1 -
 Libraries/Components/Switch/Switch.js         |  1 -
 .../Components/TabBarIOS/TabBarIOS.android.js |  1 -
 .../Components/TabBarIOS/TabBarIOS.ios.js     |  1 -
 .../TabBarIOS/TabBarItemIOS.android.js        |  1 -
 .../Components/TabBarIOS/TabBarItemIOS.ios.js |  1 -
 .../TextInput/InputAccessoryView.js           |  1 -
 Libraries/Components/TextInput/TextInput.js   |  1 -
 .../Components/TextInput/TextInputState.js    |  1 -
 .../TimePickerAndroid.android.js              |  1 -
 .../TimePickerAndroid.ios.js                  |  1 -
 .../ToastAndroid/ToastAndroid.android.js      |  1 -
 .../ToastAndroid/ToastAndroid.ios.js          |  1 -
 .../ToolbarAndroid/ToolbarAndroid.android.js  |  1 -
 .../ToolbarAndroid/ToolbarAndroid.ios.js      |  1 -
 .../Touchable/BoundingDimensions.js           |  1 -
 Libraries/Components/Touchable/PooledClass.js |  1 -
 Libraries/Components/Touchable/Position.js    |  1 -
 Libraries/Components/Touchable/Touchable.js   |  1 -
 .../Components/Touchable/TouchableBounce.js   |  1 -
 .../Touchable/TouchableHighlight.js           |  1 -
 .../TouchableNativeFeedback.android.js        |  1 -
 .../Touchable/TouchableNativeFeedback.ios.js  |  1 -
 .../Components/Touchable/TouchableOpacity.js  |  1 -
 .../Touchable/TouchableWithoutFeedback.js     |  1 -
 .../Touchable/ensureComponentIsNative.js      |  1 -
 .../Touchable/ensurePositiveDelayProps.js     |  1 -
 .../UnimplementedViews/UnimplementedView.js   |  1 -
 .../Components/View/PlatformViewPropTypes.js  |  1 -
 .../View/ReactNativeStyleAttributes.js        |  1 -
 .../View/ReactNativeViewAttributes.js         |  1 -
 .../Components/View/ShadowPropTypesIOS.js     |  1 -
 Libraries/Components/View/View.js             |  1 -
 .../Components/View/ViewAccessibility.js      |  1 -
 Libraries/Components/View/ViewContext.js      |  1 -
 Libraries/Components/View/ViewPropTypes.js    |  1 -
 .../Components/View/ViewStylePropTypes.js     |  1 -
 .../ViewPager/ViewPagerAndroid.android.js     |  1 -
 .../ViewPager/ViewPagerAndroid.ios.js         |  1 -
 .../Components/WebView/WebView.android.js     |  1 -
 Libraries/Components/WebView/WebView.ios.js   |  1 -
 Libraries/Core/Devtools/getDevServer.js       |  1 -
 Libraries/Core/Devtools/openFileInEditor.js   |  1 -
 Libraries/Core/Devtools/parseErrorStack.js    |  1 -
 Libraries/Core/Devtools/setupDevtools.js      |  1 -
 .../Core/Devtools/symbolicateStackTrace.js    |  1 -
 Libraries/Core/ExceptionsManager.js           |  1 -
 Libraries/Core/InitializeCore.js              |  1 -
 Libraries/Core/ReactNativeVersion.js          |  1 -
 Libraries/Core/ReactNativeVersionCheck.js     |  1 -
 Libraries/Core/Timers/JSTimers.js             |  1 -
 .../MissingNativeEventEmitterShim.js          |  1 -
 Libraries/EventEmitter/NativeEventEmitter.js  |  1 -
 .../EventEmitter/RCTDeviceEventEmitter.js     |  1 -
 Libraries/EventEmitter/RCTEventEmitter.js     |  1 -
 .../EventEmitter/RCTNativeAppEventEmitter.js  |  1 -
 Libraries/Experimental/Incremental.js         |  1 -
 Libraries/Experimental/IncrementalExample.js  |  1 -
 Libraries/Experimental/IncrementalGroup.js    |  1 -
 .../Experimental/IncrementalPresenter.js      |  1 -
 .../SwipeableRow/SwipeableFlatList.js         |  1 -
 .../SwipeableRow/SwipeableListView.js         |  1 -
 .../SwipeableListViewDataSource.js            |  1 -
 .../SwipeableQuickActionButton.js             |  1 -
 .../SwipeableRow/SwipeableQuickActions.js     |  1 -
 .../Experimental/SwipeableRow/SwipeableRow.js |  1 -
 Libraries/Experimental/WindowedListView.js    |  1 -
 Libraries/Geolocation/Geolocation.js          |  1 -
 Libraries/Image/AssetRegistry.js              |  1 -
 Libraries/Image/AssetSourceResolver.js        |  1 -
 Libraries/Image/Image.android.js              |  1 -
 Libraries/Image/Image.ios.js                  |  1 -
 Libraries/Image/ImageBackground.js            |  1 -
 Libraries/Image/ImageEditor.js                |  1 -
 Libraries/Image/ImageProps.js                 |  1 -
 Libraries/Image/ImageResizeMode.js            |  1 -
 Libraries/Image/ImageSource.js                |  1 -
 Libraries/Image/ImageSourcePropType.js        |  1 -
 Libraries/Image/ImageStore.js                 |  1 -
 Libraries/Image/ImageStylePropTypes.js        |  1 -
 Libraries/Image/RelativeImageStub.js          |  1 -
 Libraries/Image/nativeImageSource.js          |  1 -
 Libraries/Image/resolveAssetSource.js         |  1 -
 Libraries/Inspector/BorderBox.js              |  1 -
 Libraries/Inspector/BoxInspector.js           |  1 -
 Libraries/Inspector/ElementBox.js             |  1 -
 Libraries/Inspector/ElementProperties.js      |  1 -
 Libraries/Inspector/Inspector.js              |  1 -
 Libraries/Inspector/InspectorOverlay.js       |  1 -
 Libraries/Inspector/InspectorPanel.js         |  1 -
 Libraries/Inspector/NetworkOverlay.js         |  1 -
 Libraries/Inspector/PerformanceOverlay.js     |  1 -
 Libraries/Inspector/StyleInspector.js         |  1 -
 Libraries/Inspector/resolveBoxStyle.js        |  1 -
 Libraries/Interaction/Batchinator.js          |  1 -
 .../Interaction/BridgeSpyStallHandler.js      |  1 -
 Libraries/Interaction/FrameRateLogger.js      |  1 -
 Libraries/Interaction/InteractionManager.js   |  1 -
 Libraries/Interaction/InteractionMixin.js     |  1 -
 .../Interaction/InteractionStallDebugger.js   |  1 -
 Libraries/Interaction/JSEventLoopWatchdog.js  |  1 -
 Libraries/Interaction/PanResponder.js         |  1 -
 .../Interaction/ReactPerfStallHandler.js      |  1 -
 Libraries/Interaction/TaskQueue.js            |  1 -
 Libraries/JSInspector/InspectorAgent.js       |  1 -
 Libraries/JSInspector/JSInspector.js          |  1 -
 Libraries/JSInspector/NetworkAgent.js         |  1 -
 Libraries/LayoutAnimation/LayoutAnimation.js  |  1 -
 Libraries/Linking/Linking.js                  |  1 -
 Libraries/Lists/FillRateHelper.js             |  1 -
 Libraries/Lists/FlatList.js                   |  1 -
 Libraries/Lists/ListView/ListView.js          |  1 -
 .../Lists/ListView/ListViewDataSource.js      |  1 -
 Libraries/Lists/MetroListView.js              |  1 -
 Libraries/Lists/SectionList.js                |  1 -
 Libraries/Lists/ViewabilityHelper.js          |  1 -
 Libraries/Lists/VirtualizeUtils.js            |  1 -
 Libraries/Lists/VirtualizedList.js            |  1 -
 Libraries/Lists/VirtualizedSectionList.js     |  1 -
 Libraries/Modal/Modal.js                      |  1 -
 Libraries/Network/FormData.js                 |  1 -
 Libraries/Network/NetInfo.js                  |  1 -
 Libraries/Network/RCTNetworking.android.js    |  1 -
 Libraries/Network/RCTNetworking.ios.js        |  1 -
 Libraries/Network/XHRInterceptor.js           |  1 -
 Libraries/Network/XMLHttpRequest.js           |  1 -
 Libraries/Network/convertRequestBody.js       |  1 -
 Libraries/Network/fetch.js                    |  1 -
 .../Performance/QuickPerformanceLogger.js     |  1 -
 Libraries/Performance/SamplingProfiler.js     |  1 -
 Libraries/Performance/Systrace.js             |  1 -
 .../PermissionsAndroid/PermissionsAndroid.js  |  1 -
 Libraries/Promise.js                          |  1 -
 .../PushNotificationIOS.js                    |  1 -
 Libraries/RCTTest/SnapshotViewIOS.android.js  |  1 -
 Libraries/RCTTest/SnapshotViewIOS.ios.js      |  1 -
 Libraries/ReactNative/AppContainer.js         |  1 -
 Libraries/ReactNative/AppRegistry.js          |  1 -
 Libraries/ReactNative/FabricUIManager.js      |  1 -
 Libraries/ReactNative/I18nManager.js          |  1 -
 Libraries/ReactNative/ReactFabricInternals.js |  1 -
 Libraries/ReactNative/UIManager.js            |  1 -
 Libraries/ReactNative/UIManagerStatTracker.js |  1 -
 Libraries/ReactNative/YellowBox.js            |  1 -
 Libraries/ReactNative/queryLayoutByID.js      |  1 -
 Libraries/ReactNative/renderApplication.js    |  1 -
 .../ReactNative/requireNativeComponent.js     |  1 -
 Libraries/ReactNative/takeSnapshot.js         |  1 -
 Libraries/ReactNative/verifyPropTypes.js      |  1 -
 Libraries/Renderer/oss/ReactFabric-dev.js     |  1 -
 Libraries/Renderer/oss/ReactFabric-prod.js    |  1 -
 .../Renderer/oss/ReactNativeRenderer-dev.js   |  1 -
 .../Renderer/oss/ReactNativeRenderer-prod.js  |  1 -
 .../Renderer/shims/NativeMethodsMixin.js      |  1 -
 Libraries/Renderer/shims/ReactDebugTool.js    |  1 -
 Libraries/Renderer/shims/ReactFabric.js       |  1 -
 Libraries/Renderer/shims/ReactNative.js       |  1 -
 .../shims/ReactNativeComponentTree.js         |  1 -
 Libraries/Renderer/shims/ReactNativeTypes.js  |  1 -
 .../shims/ReactNativeViewConfigRegistry.js    |  1 -
 Libraries/Renderer/shims/ReactPerf.js         |  1 -
 Libraries/Renderer/shims/ReactTypes.js        |  1 -
 .../shims/createReactNativeComponentClass.js  |  1 -
 Libraries/Sample/Sample.android.js            |  1 -
 Libraries/Sample/Sample.ios.js                |  1 -
 Libraries/Settings/Settings.android.js        |  1 -
 Libraries/Settings/Settings.ios.js            |  1 -
 Libraries/Share/Share.js                      |  1 -
 Libraries/Storage/AsyncStorage.js             |  1 -
 Libraries/StyleSheet/ColorPropType.js         |  1 -
 Libraries/StyleSheet/EdgeInsetsPropType.js    |  1 -
 Libraries/StyleSheet/LayoutPropTypes.js       |  1 -
 Libraries/StyleSheet/PointPropType.js         |  1 -
 Libraries/StyleSheet/StyleSheet.js            |  1 -
 Libraries/StyleSheet/StyleSheetPropType.js    |  1 -
 Libraries/StyleSheet/StyleSheetTypes.js       |  1 -
 Libraries/StyleSheet/StyleSheetValidation.js  |  1 -
 Libraries/StyleSheet/TransformPropTypes.js    |  1 -
 Libraries/StyleSheet/flattenStyle.js          |  1 -
 Libraries/StyleSheet/processColor.js          |  1 -
 Libraries/StyleSheet/processTransform.js      |  1 -
 .../StyleSheet/setNormalizedColorAlpha.js     |  1 -
 Libraries/Text/Text.js                        |  1 -
 Libraries/Text/TextPropTypes.js               |  1 -
 Libraries/Text/TextProps.js                   |  1 -
 Libraries/Text/TextStylePropTypes.js          |  1 -
 Libraries/Text/TextUpdateTest.js              |  1 -
 Libraries/Types/CoreEventTypes.js             |  1 -
 Libraries/UTFSequence.js                      |  1 -
 Libraries/Utilities/BackAndroid.js            |  1 -
 Libraries/Utilities/BackHandler.android.js    |  1 -
 Libraries/Utilities/BackHandler.ios.js        |  1 -
 Libraries/Utilities/DeviceInfo.js             |  1 -
 Libraries/Utilities/Dimensions.js             |  1 -
 Libraries/Utilities/HMRClient.js              |  1 -
 Libraries/Utilities/HMRLoadingView.android.js |  1 -
 Libraries/Utilities/HMRLoadingView.ios.js     |  1 -
 Libraries/Utilities/HeapCapture.js            |  1 -
 Libraries/Utilities/JSDevSupportModule.js     |  1 -
 Libraries/Utilities/MatrixMath.js             |  1 -
 Libraries/Utilities/PerformanceLogger.js      |  1 -
 Libraries/Utilities/PixelRatio.js             |  1 -
 Libraries/Utilities/Platform.android.js       |  1 -
 Libraries/Utilities/Platform.ios.js           |  1 -
 Libraries/Utilities/PlatformOS.android.js     |  1 -
 Libraries/Utilities/PlatformOS.ios.js         |  1 -
 Libraries/Utilities/PolyfillFunctions.js      |  1 -
 Libraries/Utilities/RCTLog.js                 |  1 -
 Libraries/Utilities/SceneTracker.js           |  1 -
 Libraries/Utilities/binaryToBase64.js         |  1 -
 Libraries/Utilities/buildStyleInterpolator.js |  1 -
 Libraries/Utilities/clamp.js                  |  1 -
 .../Utilities/createStrictShapeTypeChecker.js |  1 -
 .../deepFreezeAndThrowOnMutationInDev.js      |  1 -
 .../Utilities/defineLazyObjectProperty.js     |  1 -
 Libraries/Utilities/deprecatedPropType.js     |  1 -
 Libraries/Utilities/differ/deepDiffer.js      |  1 -
 Libraries/Utilities/differ/insetsDiffer.js    |  1 -
 Libraries/Utilities/differ/matricesDiffer.js  |  1 -
 Libraries/Utilities/differ/pointsDiffer.js    |  1 -
 Libraries/Utilities/differ/sizesDiffer.js     |  1 -
 Libraries/Utilities/dismissKeyboard.js        |  1 -
 Libraries/Utilities/groupByEveryN.js          |  1 -
 Libraries/Utilities/infoLog.js                |  1 -
 Libraries/Utilities/logError.js               |  1 -
 Libraries/Utilities/mapWithSeparator.js       |  1 -
 Libraries/Utilities/mergeFast.js              |  1 -
 Libraries/Utilities/mergeIntoFast.js          |  1 -
 Libraries/Utilities/stringifySafe.js          |  1 -
 Libraries/Utilities/truncate.js               |  1 -
 Libraries/Vibration/Vibration.js              |  1 -
 Libraries/Vibration/VibrationIOS.android.js   |  1 -
 Libraries/Vibration/VibrationIOS.ios.js       |  1 -
 Libraries/WebSocket/WebSocket.js              |  1 -
 Libraries/WebSocket/WebSocketEvent.js         |  1 -
 Libraries/WebSocket/WebSocketInterceptor.js   |  1 -
 Libraries/polyfills/Array.es6.js              |  1 -
 Libraries/polyfills/Array.prototype.es6.js    |  1 -
 Libraries/polyfills/Number.es6.js             |  1 -
 Libraries/polyfills/Object.es6.js             |  1 -
 Libraries/polyfills/Object.es7.js             |  1 -
 Libraries/polyfills/String.prototype.es6.js   |  1 -
 Libraries/polyfills/babelHelpers.js           |  1 -
 Libraries/polyfills/console.js                |  1 -
 Libraries/polyfills/error-guard.js            |  1 -
 Libraries/promiseRejectionIsError.js          |  1 -
 Libraries/react-native/React.js               |  1 -
 .../react-native-implementation.js            |  1 -
 .../react-native/react-native-interface.js    |  1 -
 Libraries/vendor/core/ErrorUtils.js           |  1 -
 Libraries/vendor/core/Map.js                  |  1 -
 Libraries/vendor/core/Set.js                  |  1 -
 .../core/_shouldPolyfillES6Collection.js      |  1 -
 Libraries/vendor/core/getObjectValues.js      |  1 -
 Libraries/vendor/core/guid.js                 |  1 -
 Libraries/vendor/core/isEmpty.js              |  1 -
 Libraries/vendor/core/merge.js                |  3 +-
 Libraries/vendor/core/mergeHelpers.js         |  1 -
 Libraries/vendor/core/mergeInto.js            |  3 +-
 Libraries/vendor/core/toIterator.js           |  1 -
 .../selection/DocumentSelectionState.js       |  1 -
 .../vendor/emitter/EmitterSubscription.js     |  1 -
 Libraries/vendor/emitter/EventEmitter.js      |  1 -
 .../vendor/emitter/EventEmitterWithHolding.js |  1 -
 Libraries/vendor/emitter/EventHolder.js       |  1 -
 Libraries/vendor/emitter/EventSubscription.js |  1 -
 .../vendor/emitter/EventSubscriptionVendor.js |  1 -
 Libraries/vendor/emitter/EventValidator.js    |  1 -
 Libraries/vendor/emitter/mixInEventEmitter.js |  1 -
 .../RNTesterUnitTestsBundle.js                |  1 -
 RNTester/js/ARTExample.js                     |  1 -
 .../js/AccessibilityAndroidExample.android.js |  1 -
 RNTester/js/AccessibilityIOSExample.js        |  1 -
 RNTester/js/ActionSheetIOSExample.js          |  1 -
 RNTester/js/ActivityIndicatorExample.js       |  1 -
 RNTester/js/AlertExample.js                   |  1 -
 RNTester/js/AlertIOSExample.js                |  1 -
 RNTester/js/AnimatedExample.js                |  1 -
 RNTester/js/AnimatedGratuitousApp/AnExApp.js  |  1 -
 .../js/AnimatedGratuitousApp/AnExBobble.js    |  1 -
 .../js/AnimatedGratuitousApp/AnExChained.js   |  1 -
 .../js/AnimatedGratuitousApp/AnExScroll.js    |  1 -
 RNTester/js/AnimatedGratuitousApp/AnExSet.js  |  1 -
 RNTester/js/AnimatedGratuitousApp/AnExTilt.js |  1 -
 RNTester/js/AppStateExample.js                |  1 -
 RNTester/js/AssetScaledImageExample.js        |  1 -
 RNTester/js/AsyncStorageExample.js            |  1 -
 RNTester/js/BorderExample.js                  |  1 -
 RNTester/js/BoxShadowExample.js               |  1 -
 RNTester/js/ButtonExample.js                  |  1 -
 RNTester/js/CameraRollExample.js              |  1 -
 RNTester/js/CameraRollView.js                 |  1 -
 RNTester/js/CheckBoxExample.js                |  1 -
 RNTester/js/ClipboardExample.js               |  1 -
 RNTester/js/DatePickerAndroidExample.js       |  1 -
 RNTester/js/DatePickerIOSExample.js           |  1 -
 RNTester/js/DimensionsExample.js              |  1 -
 RNTester/js/ExampleTypes.js                   |  1 -
 RNTester/js/FlatListExample.js                |  1 -
 RNTester/js/GeolocationExample.js             |  1 -
 RNTester/js/ImageCapInsetsExample.js          |  1 -
 RNTester/js/ImageEditingExample.js            |  1 -
 RNTester/js/ImageExample.js                   |  1 -
 RNTester/js/InputAccessoryViewExample.js      |  1 -
 RNTester/js/KeyboardAvoidingViewExample.js    |  1 -
 RNTester/js/LayoutAnimationExample.js         |  1 -
 RNTester/js/LayoutEventsExample.js            |  1 -
 RNTester/js/LayoutExample.js                  |  1 -
 RNTester/js/LinkingExample.js                 |  1 -
 RNTester/js/ListExampleShared.js              |  1 -
 RNTester/js/ListViewExample.js                |  1 -
 RNTester/js/ListViewGridLayoutExample.js      |  1 -
 RNTester/js/ListViewPagingExample.js          |  1 -
 RNTester/js/MaskedViewExample.js              |  1 -
 RNTester/js/ModalExample.js                   |  1 -
 RNTester/js/MultiColumnExample.js             |  1 -
 RNTester/js/NativeAnimationsExample.js        |  1 -
 RNTester/js/NavigatorIOSBarStyleExample.js    |  1 -
 RNTester/js/NavigatorIOSColorsExample.js      |  1 -
 RNTester/js/NavigatorIOSExample.js            |  1 -
 RNTester/js/NetInfoExample.js                 |  1 -
 RNTester/js/OrientationChangeExample.js       |  1 -
 RNTester/js/PanResponderExample.js            |  1 -
 .../js/PermissionsExampleAndroid.android.js   |  1 -
 RNTester/js/PickerExample.js                  |  1 -
 RNTester/js/PickerIOSExample.js               |  1 -
 RNTester/js/PointerEventsExample.js           |  1 -
 .../js/ProgressBarAndroidExample.android.js   |  1 -
 RNTester/js/ProgressViewIOSExample.js         |  1 -
 RNTester/js/PushNotificationIOSExample.js     |  1 -
 RNTester/js/RCTRootViewIOSExample.js          |  1 -
 RNTester/js/RNTesterActions.js                |  1 -
 RNTester/js/RNTesterApp.android.js            |  1 -
 RNTester/js/RNTesterApp.ios.js                |  1 -
 RNTester/js/RNTesterBlock.js                  |  1 -
 RNTester/js/RNTesterButton.js                 |  1 -
 RNTester/js/RNTesterExampleContainer.js       |  1 -
 RNTester/js/RNTesterExampleList.js            |  1 -
 RNTester/js/RNTesterList.android.js           |  1 -
 RNTester/js/RNTesterList.ios.js               |  1 -
 RNTester/js/RNTesterNavigationReducer.js      |  1 -
 RNTester/js/RNTesterPage.js                   |  1 -
 RNTester/js/RNTesterSettingSwitchRow.js       |  1 -
 RNTester/js/RNTesterStatePersister.js         |  1 -
 RNTester/js/RNTesterTitle.js                  |  1 -
 RNTester/js/RTLExample.js                     |  1 -
 RNTester/js/RefreshControlExample.js          |  1 -
 .../js/RootViewSizeFlexibilityExampleApp.js   |  1 -
 RNTester/js/SafeAreaViewExample.js            |  1 -
 RNTester/js/ScrollViewExample.js              |  1 -
 RNTester/js/ScrollViewSimpleExample.js        |  1 -
 RNTester/js/SectionListExample.js             |  1 -
 RNTester/js/SegmentedControlIOSExample.js     |  1 -
 RNTester/js/SetPropertiesExampleApp.js        |  1 -
 RNTester/js/ShareExample.js                   |  1 -
 RNTester/js/SliderExample.js                  |  1 -
 RNTester/js/SnapshotExample.js                |  1 -
 RNTester/js/StatusBarExample.js               |  1 -
 RNTester/js/SwipeableFlatListExample.js       |  1 -
 RNTester/js/SwipeableListViewExample.js       |  1 -
 RNTester/js/SwitchExample.js                  |  1 -
 RNTester/js/TVEventHandlerExample.js          |  1 -
 RNTester/js/TabBarIOSBarStyleExample.js       |  1 -
 RNTester/js/TabBarIOSExample.js               |  1 -
 RNTester/js/TextExample.android.js            |  1 -
 RNTester/js/TextExample.ios.js                |  1 -
 RNTester/js/TextInputExample.android.js       |  1 -
 RNTester/js/TextInputExample.ios.js           |  1 -
 RNTester/js/TimePickerAndroidExample.js       |  1 -
 RNTester/js/TimerExample.js                   |  1 -
 RNTester/js/ToastAndroidExample.android.js    |  1 -
 RNTester/js/ToolbarAndroidExample.android.js  |  1 -
 RNTester/js/ToolbarAndroidExample.ios.js      |  1 -
 RNTester/js/TouchableExample.js               |  1 -
 RNTester/js/TransformExample.js               |  1 -
 RNTester/js/TransparentHitTestExample.js      |  1 -
 RNTester/js/URIActionMap.js                   |  1 -
 RNTester/js/VibrationExample.js               |  1 -
 RNTester/js/VibrationIOSExample.js            |  1 -
 RNTester/js/ViewExample.js                    |  1 -
 .../js/ViewPagerAndroidExample.android.js     |  1 -
 RNTester/js/WebSocketExample.js               |  1 -
 RNTester/js/WebViewExample.js                 |  1 -
 RNTester/js/XHRExample.js                     |  1 -
 RNTester/js/XHRExampleBinaryUpload.js         |  1 -
 RNTester/js/XHRExampleCookies.js              |  1 -
 RNTester/js/XHRExampleDownload.js             |  1 -
 RNTester/js/XHRExampleFetch.js                |  1 -
 RNTester/js/XHRExampleFormData.js             |  1 -
 RNTester/js/XHRExampleHeaders.js              |  1 -
 RNTester/js/XHRExampleOnTimeOut.js            |  1 -
 RNTester/js/createExamplePage.js              |  1 -
 RNTester/js/http_test_server.js               |  1 -
 RNTester/js/websocket_test_server.js          |  1 -
 ReactAndroid/src/androidTest/js/Asserts.js    |  1 -
 .../js/CatalystRootViewTestModule.js          |  1 -
 .../js/DatePickerDialogTestModule.js          |  1 -
 .../src/androidTest/js/InitialPropsTestApp.js |  1 -
 .../src/androidTest/js/JSResponderTestApp.js  |  1 -
 .../src/androidTest/js/LayoutEventsTestApp.js |  1 -
 .../androidTest/js/MeasureLayoutTestModule.js |  1 -
 .../js/MultitouchHandlingTestAppModule.js     |  1 -
 .../src/androidTest/js/NativeIdTestModule.js  |  1 -
 .../androidTest/js/PickerAndroidTestModule.js |  1 -
 .../androidTest/js/ProgressBarTestModule.js   |  1 -
 .../androidTest/js/ScrollViewTestModule.js    |  1 -
 .../src/androidTest/js/ShareTestModule.js     |  1 -
 .../js/SubviewsClippingTestModule.js          |  1 -
 .../js/SwipeRefreshLayoutTestModule.js        |  1 -
 ReactAndroid/src/androidTest/js/TestBundle.js |  1 -
 .../src/androidTest/js/TestIdTestModule.js    |  1 -
 .../src/androidTest/js/TestJSLocaleModule.js  |  1 -
 .../js/TestJSToJavaParametersModule.js        |  1 -
 .../js/TestJavaToJSArgumentsModule.js         |  1 -
 .../js/TestJavaToJSReturnValuesModule.js      |  1 -
 .../src/androidTest/js/TextInputTestModule.js |  1 -
 .../js/TimePickerDialogTestModule.js          |  1 -
 .../js/TouchBubblingTestAppModule.js          |  1 -
 .../src/androidTest/js/UIManagerTestModule.js |  1 -
 .../androidTest/js/ViewRenderingTestModule.js |  1 -
 jest/hasteImpl.js                             | 75 +++++++++++++++++++
 local-cli/core/index.js                       |  2 +
 package.json                                  |  1 +
 543 files changed, 97 insertions(+), 541 deletions(-)
 create mode 100644 jest/hasteImpl.js

diff --git a/.flowconfig b/.flowconfig
index 386c9389a498..cd3dd707a722 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -36,6 +36,23 @@ flow-github/
 emoji=true
 
 module.system=haste
+module.system.haste.use_name_reducers=true
+# keep the following in sync with server/haste/hasteImpl.js
+# get basename
+module.system.haste.name_reducers='^.*/\([a-zA-Z0-9$_.-]+\.js\(\.flow\)?\)$' -> '\1'
+# strip .js or .js.flow suffix
+module.system.haste.name_reducers='^\(.*\)\.js\(\.flow\)?$' -> '\1'
+# strip .ios suffix
+module.system.haste.name_reducers='^\(.*\)\.ios$' -> '\1'
+module.system.haste.name_reducers='^\(.*\)\.android$' -> '\1'
+module.system.haste.name_reducers='^\(.*\)\.native$' -> '\1'
+module.system.haste.paths.blacklist=.*/__tests__/.*
+module.system.haste.paths.blacklist=.*/__mocks__/.*
+module.system.haste.paths.blacklist=<PROJECT_ROOT>/Libraries/Animated/src/polyfills/.*
+module.system.haste.paths.whitelist=<PROJECT_ROOT>/Libraries/.*
+module.system.haste.paths.whitelist=<PROJECT_ROOT>/RNTester/.*
+module.system.haste.paths.whitelist=<PROJECT_ROOT>/IntegrationTests/.*
+module.system.haste.paths.blacklist=<PROJECT_ROOT>/Libraries/Animated/src/polyfills/.*
 
 munge_underscores=true
 
diff --git a/IntegrationTests/AccessibilityManagerTest.js b/IntegrationTests/AccessibilityManagerTest.js
index 74dbe9ba19ed..4287094d3759 100644
--- a/IntegrationTests/AccessibilityManagerTest.js
+++ b/IntegrationTests/AccessibilityManagerTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule AccessibilityManagerTest
  */
 'use strict';
 
diff --git a/IntegrationTests/AppEventsTest.js b/IntegrationTests/AppEventsTest.js
index ae061e167b86..af04819b38fd 100644
--- a/IntegrationTests/AppEventsTest.js
+++ b/IntegrationTests/AppEventsTest.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AppEventsTest
  * @flow
  */
 'use strict';
diff --git a/IntegrationTests/AsyncStorageTest.js b/IntegrationTests/AsyncStorageTest.js
index 3ce0265dd8ce..2d951dab3984 100644
--- a/IntegrationTests/AsyncStorageTest.js
+++ b/IntegrationTests/AsyncStorageTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule AsyncStorageTest
  */
 'use strict';
 
diff --git a/IntegrationTests/ImageCachePolicyTest.js b/IntegrationTests/ImageCachePolicyTest.js
index d6fa4f544a1b..a095b4ec9912 100644
--- a/IntegrationTests/ImageCachePolicyTest.js
+++ b/IntegrationTests/ImageCachePolicyTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ImageCachePolicyTest
  */
 'use strict';
 
diff --git a/IntegrationTests/ImageSnapshotTest.js b/IntegrationTests/ImageSnapshotTest.js
index 8ba7734286d6..3d024d569da6 100644
--- a/IntegrationTests/ImageSnapshotTest.js
+++ b/IntegrationTests/ImageSnapshotTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ImageSnapshotTest
  */
 'use strict';
 
diff --git a/IntegrationTests/IntegrationTestHarnessTest.js b/IntegrationTests/IntegrationTestHarnessTest.js
index 6291c915d686..9b34065b8fd6 100644
--- a/IntegrationTests/IntegrationTestHarnessTest.js
+++ b/IntegrationTests/IntegrationTestHarnessTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule IntegrationTestHarnessTest
  */
 'use strict';
 
diff --git a/IntegrationTests/IntegrationTestsApp.js b/IntegrationTests/IntegrationTestsApp.js
index 6b255c2befe5..62f6fa83057b 100644
--- a/IntegrationTests/IntegrationTestsApp.js
+++ b/IntegrationTests/IntegrationTestsApp.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule IntegrationTestsApp
  */
 'use strict';
 
diff --git a/IntegrationTests/LayoutEventsTest.js b/IntegrationTests/LayoutEventsTest.js
index 769ff98f6be8..31dd1839c86c 100644
--- a/IntegrationTests/LayoutEventsTest.js
+++ b/IntegrationTests/LayoutEventsTest.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule LayoutEventsTest
  * @flow
  */
 'use strict';
diff --git a/IntegrationTests/LoggingTestModule.js b/IntegrationTests/LoggingTestModule.js
index 25b409353ce1..df2b0e59b524 100644
--- a/IntegrationTests/LoggingTestModule.js
+++ b/IntegrationTests/LoggingTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule LoggingTestModule
  */
 'use strict';
 
diff --git a/IntegrationTests/PromiseTest.js b/IntegrationTests/PromiseTest.js
index f6a81e3d6d5d..21005576d678 100644
--- a/IntegrationTests/PromiseTest.js
+++ b/IntegrationTests/PromiseTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule PromiseTest
  */
 'use strict';
 
diff --git a/IntegrationTests/PropertiesUpdateTest.js b/IntegrationTests/PropertiesUpdateTest.js
index 623dc82c8ee9..3d93d9d0ac23 100644
--- a/IntegrationTests/PropertiesUpdateTest.js
+++ b/IntegrationTests/PropertiesUpdateTest.js
@@ -3,7 +3,6 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
- * @providesModule PropertiesUpdateTest
  */
 'use strict';
 
diff --git a/IntegrationTests/RCTRootViewIntegrationTestApp.js b/IntegrationTests/RCTRootViewIntegrationTestApp.js
index a97873d2c322..aef56f975992 100644
--- a/IntegrationTests/RCTRootViewIntegrationTestApp.js
+++ b/IntegrationTests/RCTRootViewIntegrationTestApp.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTRootViewIntegrationTestApp
  */
 'use strict';
 
diff --git a/IntegrationTests/ReactContentSizeUpdateTest.js b/IntegrationTests/ReactContentSizeUpdateTest.js
index c5f5ae80c246..dda42b4df9c8 100644
--- a/IntegrationTests/ReactContentSizeUpdateTest.js
+++ b/IntegrationTests/ReactContentSizeUpdateTest.js
@@ -3,7 +3,6 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
- * @providesModule ReactContentSizeUpdateTest
  */
 'use strict';
 
diff --git a/IntegrationTests/SimpleSnapshotTest.js b/IntegrationTests/SimpleSnapshotTest.js
index 1c0be2a431d4..dd8bf9ac8731 100644
--- a/IntegrationTests/SimpleSnapshotTest.js
+++ b/IntegrationTests/SimpleSnapshotTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SimpleSnapshotTest
  */
 'use strict';
 
diff --git a/IntegrationTests/SizeFlexibilityUpdateTest.js b/IntegrationTests/SizeFlexibilityUpdateTest.js
index 679694a0d631..ce0be9e6e222 100644
--- a/IntegrationTests/SizeFlexibilityUpdateTest.js
+++ b/IntegrationTests/SizeFlexibilityUpdateTest.js
@@ -3,7 +3,6 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
- * @providesModule SizeFlexibilityUpdateTest
  */
 'use strict';
 
diff --git a/IntegrationTests/SyncMethodTest.js b/IntegrationTests/SyncMethodTest.js
index 6318eaa4f142..f61f52b36106 100644
--- a/IntegrationTests/SyncMethodTest.js
+++ b/IntegrationTests/SyncMethodTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SyncMethodTest
  */
 'use strict';
 
diff --git a/IntegrationTests/TimersTest.js b/IntegrationTests/TimersTest.js
index 23da99dc6edb..f40742c9a8b0 100644
--- a/IntegrationTests/TimersTest.js
+++ b/IntegrationTests/TimersTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TimersTest
  */
 'use strict';
 
diff --git a/IntegrationTests/WebSocketTest.js b/IntegrationTests/WebSocketTest.js
index 6e459f913bab..de8428f79e6a 100644
--- a/IntegrationTests/WebSocketTest.js
+++ b/IntegrationTests/WebSocketTest.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule WebSocketTest
  */
 'use strict';
 
diff --git a/IntegrationTests/WebViewTest.js b/IntegrationTests/WebViewTest.js
index a41e244b58be..499e1c095400 100644
--- a/IntegrationTests/WebViewTest.js
+++ b/IntegrationTests/WebViewTest.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule WebViewTest
  */
 'use strict';
 
diff --git a/IntegrationTests/websocket_integration_test_server.js b/IntegrationTests/websocket_integration_test_server.js
index e338d85ae3b8..763668f3275d 100755
--- a/IntegrationTests/websocket_integration_test_server.js
+++ b/IntegrationTests/websocket_integration_test_server.js
@@ -7,7 +7,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule websocket_integration_test_server
  */
 'use strict';
 
diff --git a/Libraries/ART/ARTSerializablePath.js b/Libraries/ART/ARTSerializablePath.js
index 7f52bc6540ed..08c4530222df 100644
--- a/Libraries/ART/ARTSerializablePath.js
+++ b/Libraries/ART/ARTSerializablePath.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ARTSerializablePath
  */
 'use strict';
 
diff --git a/Libraries/ART/ReactNativeART.js b/Libraries/ART/ReactNativeART.js
index 7d9f1b590634..9b0a725cd140 100644
--- a/Libraries/ART/ReactNativeART.js
+++ b/Libraries/ART/ReactNativeART.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNativeART
  */
 'use strict';
 
diff --git a/Libraries/ActionSheetIOS/ActionSheetIOS.js b/Libraries/ActionSheetIOS/ActionSheetIOS.js
index 23db7680ab34..b135a23e5fc9 100644
--- a/Libraries/ActionSheetIOS/ActionSheetIOS.js
+++ b/Libraries/ActionSheetIOS/ActionSheetIOS.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ActionSheetIOS
  * @flow
  * @format
  */
diff --git a/Libraries/Alert/Alert.js b/Libraries/Alert/Alert.js
index bcb517144404..ed78335043c5 100644
--- a/Libraries/Alert/Alert.js
+++ b/Libraries/Alert/Alert.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Alert
  * @flow
  */
 'use strict';
diff --git a/Libraries/Alert/AlertIOS.js b/Libraries/Alert/AlertIOS.js
index b25440646239..eb15d1cdee03 100644
--- a/Libraries/Alert/AlertIOS.js
+++ b/Libraries/Alert/AlertIOS.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AlertIOS
  * @flow
  * @jsdoc
  */
diff --git a/Libraries/Alert/RCTAlertManager.android.js b/Libraries/Alert/RCTAlertManager.android.js
index f819b55e1b3d..25297171c4ce 100644
--- a/Libraries/Alert/RCTAlertManager.android.js
+++ b/Libraries/Alert/RCTAlertManager.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTAlertManager
 */
 'use strict';
 
diff --git a/Libraries/Alert/RCTAlertManager.ios.js b/Libraries/Alert/RCTAlertManager.ios.js
index 3aef740abed4..220b72c3d91d 100644
--- a/Libraries/Alert/RCTAlertManager.ios.js
+++ b/Libraries/Alert/RCTAlertManager.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTAlertManager
  * @flow
  */
 'use strict';
diff --git a/Libraries/Animated/release/gulpfile.js b/Libraries/Animated/release/gulpfile.js
index b454ea790c27..f5e87b4c9987 100644
--- a/Libraries/Animated/release/gulpfile.js
+++ b/Libraries/Animated/release/gulpfile.js
@@ -3,7 +3,6 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
- * @providesModule gulpfile
  */
 
 'use strict';
diff --git a/Libraries/Animated/src/Animated.js b/Libraries/Animated/src/Animated.js
index 32ec9ff80469..f25d2a0796a1 100644
--- a/Libraries/Animated/src/Animated.js
+++ b/Libraries/Animated/src/Animated.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Animated
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/AnimatedEvent.js b/Libraries/Animated/src/AnimatedEvent.js
index f9300feb4e79..084632737c66 100644
--- a/Libraries/Animated/src/AnimatedEvent.js
+++ b/Libraries/Animated/src/AnimatedEvent.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedEvent
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/AnimatedImplementation.js b/Libraries/Animated/src/AnimatedImplementation.js
index 9291a7956531..2c1ce431d106 100644
--- a/Libraries/Animated/src/AnimatedImplementation.js
+++ b/Libraries/Animated/src/AnimatedImplementation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedImplementation
  * @flow
  * @format
  * @preventMunge
diff --git a/Libraries/Animated/src/AnimatedWeb.js b/Libraries/Animated/src/AnimatedWeb.js
index f3af397b7409..a22bd075ec51 100644
--- a/Libraries/Animated/src/AnimatedWeb.js
+++ b/Libraries/Animated/src/AnimatedWeb.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule AnimatedWeb
  */
 'use strict';
 
diff --git a/Libraries/Animated/src/Easing.js b/Libraries/Animated/src/Easing.js
index f5c00fd813f7..5fb4478eef63 100644
--- a/Libraries/Animated/src/Easing.js
+++ b/Libraries/Animated/src/Easing.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Easing
  * @flow
  */
 'use strict';
diff --git a/Libraries/Animated/src/NativeAnimatedHelper.js b/Libraries/Animated/src/NativeAnimatedHelper.js
index 68bf4563fa95..61b2bde64a4d 100644
--- a/Libraries/Animated/src/NativeAnimatedHelper.js
+++ b/Libraries/Animated/src/NativeAnimatedHelper.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NativeAnimatedHelper
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/SpringConfig.js b/Libraries/Animated/src/SpringConfig.js
index 5b476f672346..6227c28301b4 100644
--- a/Libraries/Animated/src/SpringConfig.js
+++ b/Libraries/Animated/src/SpringConfig.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SpringConfig
  * @flow
  */
 
diff --git a/Libraries/Animated/src/animations/Animation.js b/Libraries/Animated/src/animations/Animation.js
index 000e44d77f9b..b4e38016dba5 100644
--- a/Libraries/Animated/src/animations/Animation.js
+++ b/Libraries/Animated/src/animations/Animation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Animation
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/animations/DecayAnimation.js b/Libraries/Animated/src/animations/DecayAnimation.js
index 7df0e104b72f..78f6e2b7cc85 100644
--- a/Libraries/Animated/src/animations/DecayAnimation.js
+++ b/Libraries/Animated/src/animations/DecayAnimation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DecayAnimation
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/animations/SpringAnimation.js b/Libraries/Animated/src/animations/SpringAnimation.js
index 8b6f96fe67bd..2bc610eed752 100644
--- a/Libraries/Animated/src/animations/SpringAnimation.js
+++ b/Libraries/Animated/src/animations/SpringAnimation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SpringAnimation
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/animations/TimingAnimation.js b/Libraries/Animated/src/animations/TimingAnimation.js
index 1b6a4ae94cd9..694a52c0a39f 100644
--- a/Libraries/Animated/src/animations/TimingAnimation.js
+++ b/Libraries/Animated/src/animations/TimingAnimation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TimingAnimation
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/bezier.js b/Libraries/Animated/src/bezier.js
index 2bd594930064..9aa777a12493 100644
--- a/Libraries/Animated/src/bezier.js
+++ b/Libraries/Animated/src/bezier.js
@@ -3,7 +3,6 @@
  * https://github.com/gre/bezier-easing
  *
  * @copyright 2014-2015 Gaëtan Renaudeau. MIT License.
- * @providesModule bezier
  * @noflow
  */
 'use strict';
diff --git a/Libraries/Animated/src/createAnimatedComponent.js b/Libraries/Animated/src/createAnimatedComponent.js
index 357ee0bd59bc..d876af645c4e 100644
--- a/Libraries/Animated/src/createAnimatedComponent.js
+++ b/Libraries/Animated/src/createAnimatedComponent.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule createAnimatedComponent
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedAddition.js b/Libraries/Animated/src/nodes/AnimatedAddition.js
index 2e3453965565..60713da50021 100644
--- a/Libraries/Animated/src/nodes/AnimatedAddition.js
+++ b/Libraries/Animated/src/nodes/AnimatedAddition.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedAddition
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedDiffClamp.js b/Libraries/Animated/src/nodes/AnimatedDiffClamp.js
index 0f64e75c723c..4219eccfb377 100644
--- a/Libraries/Animated/src/nodes/AnimatedDiffClamp.js
+++ b/Libraries/Animated/src/nodes/AnimatedDiffClamp.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedDiffClamp
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedDivision.js b/Libraries/Animated/src/nodes/AnimatedDivision.js
index 606e63937b9a..3498d322211f 100644
--- a/Libraries/Animated/src/nodes/AnimatedDivision.js
+++ b/Libraries/Animated/src/nodes/AnimatedDivision.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedDivision
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedInterpolation.js b/Libraries/Animated/src/nodes/AnimatedInterpolation.js
index bc7b1365879d..e8f9823c20e4 100644
--- a/Libraries/Animated/src/nodes/AnimatedInterpolation.js
+++ b/Libraries/Animated/src/nodes/AnimatedInterpolation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedInterpolation
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedModulo.js b/Libraries/Animated/src/nodes/AnimatedModulo.js
index 24cd3f0b077c..6699ded50a65 100644
--- a/Libraries/Animated/src/nodes/AnimatedModulo.js
+++ b/Libraries/Animated/src/nodes/AnimatedModulo.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedModulo
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedMultiplication.js b/Libraries/Animated/src/nodes/AnimatedMultiplication.js
index dc01f7f17127..889f530c76ba 100644
--- a/Libraries/Animated/src/nodes/AnimatedMultiplication.js
+++ b/Libraries/Animated/src/nodes/AnimatedMultiplication.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedMultiplication
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedNode.js b/Libraries/Animated/src/nodes/AnimatedNode.js
index e75cfaf0e5c8..34e010a62f8c 100644
--- a/Libraries/Animated/src/nodes/AnimatedNode.js
+++ b/Libraries/Animated/src/nodes/AnimatedNode.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedNode
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedProps.js b/Libraries/Animated/src/nodes/AnimatedProps.js
index 78cd11189edf..75c9c2548713 100644
--- a/Libraries/Animated/src/nodes/AnimatedProps.js
+++ b/Libraries/Animated/src/nodes/AnimatedProps.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedProps
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedStyle.js b/Libraries/Animated/src/nodes/AnimatedStyle.js
index c7bb24e3b42b..990b960a3368 100644
--- a/Libraries/Animated/src/nodes/AnimatedStyle.js
+++ b/Libraries/Animated/src/nodes/AnimatedStyle.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedStyle
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedSubtraction.js b/Libraries/Animated/src/nodes/AnimatedSubtraction.js
index 610fc226eb65..3fe8bbb69207 100644
--- a/Libraries/Animated/src/nodes/AnimatedSubtraction.js
+++ b/Libraries/Animated/src/nodes/AnimatedSubtraction.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedSubtraction
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedTracking.js b/Libraries/Animated/src/nodes/AnimatedTracking.js
index cf20d6e8bbf3..699da167c7b2 100644
--- a/Libraries/Animated/src/nodes/AnimatedTracking.js
+++ b/Libraries/Animated/src/nodes/AnimatedTracking.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedTracking
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedTransform.js b/Libraries/Animated/src/nodes/AnimatedTransform.js
index 48f82f9fe344..1706923394ec 100644
--- a/Libraries/Animated/src/nodes/AnimatedTransform.js
+++ b/Libraries/Animated/src/nodes/AnimatedTransform.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedTransform
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedValue.js b/Libraries/Animated/src/nodes/AnimatedValue.js
index 9d06c751cefb..a3fb3a325b83 100644
--- a/Libraries/Animated/src/nodes/AnimatedValue.js
+++ b/Libraries/Animated/src/nodes/AnimatedValue.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedValue
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedValueXY.js b/Libraries/Animated/src/nodes/AnimatedValueXY.js
index 52c207c0f42f..3de5bbaf9d3a 100644
--- a/Libraries/Animated/src/nodes/AnimatedValueXY.js
+++ b/Libraries/Animated/src/nodes/AnimatedValueXY.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedValueXY
  * @flow
  * @format
  */
diff --git a/Libraries/Animated/src/nodes/AnimatedWithChildren.js b/Libraries/Animated/src/nodes/AnimatedWithChildren.js
index 1f58cd834e16..9cd5fb49e140 100644
--- a/Libraries/Animated/src/nodes/AnimatedWithChildren.js
+++ b/Libraries/Animated/src/nodes/AnimatedWithChildren.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnimatedWithChildren
  * @flow
  * @format
  */
diff --git a/Libraries/AppState/AppState.js b/Libraries/AppState/AppState.js
index f2faa9480d2b..ecb106bb24e8 100644
--- a/Libraries/AppState/AppState.js
+++ b/Libraries/AppState/AppState.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AppState
  * @flow
  */
 'use strict';
diff --git a/Libraries/BatchedBridge/BatchedBridge.js b/Libraries/BatchedBridge/BatchedBridge.js
index 516c2ac1e223..bc66ae32f9f4 100644
--- a/Libraries/BatchedBridge/BatchedBridge.js
+++ b/Libraries/BatchedBridge/BatchedBridge.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BatchedBridge
  * @flow
  */
 'use strict';
diff --git a/Libraries/BatchedBridge/MessageQueue.js b/Libraries/BatchedBridge/MessageQueue.js
index ef689333917d..5c2338d033e8 100644
--- a/Libraries/BatchedBridge/MessageQueue.js
+++ b/Libraries/BatchedBridge/MessageQueue.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule MessageQueue
  * @flow
  * @format
  */
diff --git a/Libraries/BatchedBridge/NativeModules.js b/Libraries/BatchedBridge/NativeModules.js
index 324c4f6e995b..a5f991149995 100644
--- a/Libraries/BatchedBridge/NativeModules.js
+++ b/Libraries/BatchedBridge/NativeModules.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NativeModules
  * @flow
  */
 'use strict';
diff --git a/Libraries/Blob/Blob.js b/Libraries/Blob/Blob.js
index eca13a6a309e..0e36b07f7f4e 100644
--- a/Libraries/Blob/Blob.js
+++ b/Libraries/Blob/Blob.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Blob
  * @flow
  * @format
  */
diff --git a/Libraries/Blob/BlobManager.js b/Libraries/Blob/BlobManager.js
index dd7cc00eabc6..b08082e35e15 100644
--- a/Libraries/Blob/BlobManager.js
+++ b/Libraries/Blob/BlobManager.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BlobManager
  * @flow
  * @format
  */
diff --git a/Libraries/Blob/BlobRegistry.js b/Libraries/Blob/BlobRegistry.js
index 330c1659ae42..d78a9d26656e 100644
--- a/Libraries/Blob/BlobRegistry.js
+++ b/Libraries/Blob/BlobRegistry.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BlobRegistry
  * @flow
  * @format
  */
diff --git a/Libraries/Blob/BlobTypes.js b/Libraries/Blob/BlobTypes.js
index 8e895d900610..b03922f24f32 100644
--- a/Libraries/Blob/BlobTypes.js
+++ b/Libraries/Blob/BlobTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BlobTypes
  * @flow
  * @format
  */
diff --git a/Libraries/Blob/File.js b/Libraries/Blob/File.js
index f5b03d85f7f1..2f57183cdb3f 100644
--- a/Libraries/Blob/File.js
+++ b/Libraries/Blob/File.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule File
  * @flow
  * @format
  */
diff --git a/Libraries/Blob/FileReader.js b/Libraries/Blob/FileReader.js
index b3ed89dc9318..309e4577a455 100644
--- a/Libraries/Blob/FileReader.js
+++ b/Libraries/Blob/FileReader.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule FileReader
  * @flow
  * @format
  */
diff --git a/Libraries/Blob/URL.js b/Libraries/Blob/URL.js
index 7349f7752f26..de73affac2af 100644
--- a/Libraries/Blob/URL.js
+++ b/Libraries/Blob/URL.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule URL
  * @format
  * @flow
  */
diff --git a/Libraries/BugReporting/BugReporting.js b/Libraries/BugReporting/BugReporting.js
index 11a59e6d5222..f196276c36fa 100644
--- a/Libraries/BugReporting/BugReporting.js
+++ b/Libraries/BugReporting/BugReporting.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BugReporting
  * @flow
  */
 'use strict';
diff --git a/Libraries/BugReporting/dumpReactTree.js b/Libraries/BugReporting/dumpReactTree.js
index f8a137ceff7f..6ffe64244e50 100644
--- a/Libraries/BugReporting/dumpReactTree.js
+++ b/Libraries/BugReporting/dumpReactTree.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule dumpReactTree
  * @flow
  */
 'use strict';
diff --git a/Libraries/BugReporting/getReactData.js b/Libraries/BugReporting/getReactData.js
index 53c8fb6ccfc1..3f7a1a903d66 100644
--- a/Libraries/BugReporting/getReactData.js
+++ b/Libraries/BugReporting/getReactData.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule getReactData
  * @flow
  */
 'use strict';
diff --git a/Libraries/CameraRoll/CameraRoll.js b/Libraries/CameraRoll/CameraRoll.js
index 3bc48664f35d..f2a4f65aa809 100644
--- a/Libraries/CameraRoll/CameraRoll.js
+++ b/Libraries/CameraRoll/CameraRoll.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule CameraRoll
  * @flow
  * @format
  */
diff --git a/Libraries/CameraRoll/ImagePickerIOS.js b/Libraries/CameraRoll/ImagePickerIOS.js
index 24d1309d2e1b..fe50825da142 100644
--- a/Libraries/CameraRoll/ImagePickerIOS.js
+++ b/Libraries/CameraRoll/ImagePickerIOS.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImagePickerIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/Color/normalizeColor.js b/Libraries/Color/normalizeColor.js
index 09c2e1525d54..de62e68dad0a 100755
--- a/Libraries/Color/normalizeColor.js
+++ b/Libraries/Color/normalizeColor.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule normalizeColor
  * @flow
  */
 /* eslint no-bitwise: 0 */
diff --git a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
index afc4abe1533a..232370b5cbf8 100644
--- a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
+++ b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AccessibilityInfo
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
index 6e39b5e477d5..d1b36494e99a 100644
--- a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
+++ b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AccessibilityInfo
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/ActivityIndicator/ActivityIndicator.js b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
index a520b6579047..9692cbf8073e 100644
--- a/Libraries/Components/ActivityIndicator/ActivityIndicator.js
+++ b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ActivityIndicator
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/AppleTV/TVEventHandler.js b/Libraries/Components/AppleTV/TVEventHandler.js
index 363d50d903d8..303e07617f98 100644
--- a/Libraries/Components/AppleTV/TVEventHandler.js
+++ b/Libraries/Components/AppleTV/TVEventHandler.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TVEventHandler
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/AppleTV/TVViewPropTypes.js b/Libraries/Components/AppleTV/TVViewPropTypes.js
index 2b6a6d4e53dc..831d5c3992d7 100644
--- a/Libraries/Components/AppleTV/TVViewPropTypes.js
+++ b/Libraries/Components/AppleTV/TVViewPropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TVViewPropTypes
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/Button.js b/Libraries/Components/Button.js
index 51ca2aa636c3..2956b1a1245b 100644
--- a/Libraries/Components/Button.js
+++ b/Libraries/Components/Button.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Button
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/CheckBox/CheckBox.android.js b/Libraries/Components/CheckBox/CheckBox.android.js
index e4a14c6f73da..5417a0e811de 100644
--- a/Libraries/Components/CheckBox/CheckBox.android.js
+++ b/Libraries/Components/CheckBox/CheckBox.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule CheckBox
  * @flow
  * @format
  */
diff --git a/Libraries/Components/CheckBox/CheckBox.ios.js b/Libraries/Components/CheckBox/CheckBox.ios.js
index 386255541d47..5fda2cd5ec2b 100644
--- a/Libraries/Components/CheckBox/CheckBox.ios.js
+++ b/Libraries/Components/CheckBox/CheckBox.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule CheckBox
  * @flow
  * @format
  */
diff --git a/Libraries/Components/Clipboard/Clipboard.js b/Libraries/Components/Clipboard/Clipboard.js
index 80d067cce257..0bf3b470774c 100644
--- a/Libraries/Components/Clipboard/Clipboard.js
+++ b/Libraries/Components/Clipboard/Clipboard.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Clipboard
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/DatePicker/DatePickerIOS.android.js b/Libraries/Components/DatePicker/DatePickerIOS.android.js
index 2a0d8998bfb5..d2053808699c 100644
--- a/Libraries/Components/DatePicker/DatePickerIOS.android.js
+++ b/Libraries/Components/DatePicker/DatePickerIOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DatePickerIOS
  */
 
 'use strict';
diff --git a/Libraries/Components/DatePicker/DatePickerIOS.ios.js b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
index b08bf8f93412..41b0a88969ab 100644
--- a/Libraries/Components/DatePicker/DatePickerIOS.ios.js
+++ b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DatePickerIOS
  * @flow
  *
  * This is a controlled component version of RCTDatePickerIOS
diff --git a/Libraries/Components/DatePickerAndroid/DatePickerAndroid.android.js b/Libraries/Components/DatePickerAndroid/DatePickerAndroid.android.js
index 750ed921f068..23691ce10882 100644
--- a/Libraries/Components/DatePickerAndroid/DatePickerAndroid.android.js
+++ b/Libraries/Components/DatePickerAndroid/DatePickerAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DatePickerAndroid
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/DatePickerAndroid/DatePickerAndroid.ios.js b/Libraries/Components/DatePickerAndroid/DatePickerAndroid.ios.js
index a23602128078..4895dfd8286d 100644
--- a/Libraries/Components/DatePickerAndroid/DatePickerAndroid.ios.js
+++ b/Libraries/Components/DatePickerAndroid/DatePickerAndroid.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DatePickerAndroid
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
index 6a20d894f4f4..f9d84442448b 100644
--- a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
+++ b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DrawerLayoutAndroid
  */
 'use strict';
 
diff --git a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.ios.js b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.ios.js
index d5b950c5b41e..ebd42dd5b18b 100644
--- a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.ios.js
+++ b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DrawerLayoutAndroid
  */
 'use strict';
 
diff --git a/Libraries/Components/Keyboard/Keyboard.js b/Libraries/Components/Keyboard/Keyboard.js
index 55d9891902ea..d61b07a88670 100644
--- a/Libraries/Components/Keyboard/Keyboard.js
+++ b/Libraries/Components/Keyboard/Keyboard.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Keyboard
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/Keyboard/KeyboardAvoidingView.js b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
index ffb6c58fe637..87a0172f2091 100644
--- a/Libraries/Components/Keyboard/KeyboardAvoidingView.js
+++ b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule KeyboardAvoidingView
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/LazyRenderer.js b/Libraries/Components/LazyRenderer.js
index 851bf55feee0..b1217aa1f3a2 100644
--- a/Libraries/Components/LazyRenderer.js
+++ b/Libraries/Components/LazyRenderer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule LazyRenderer
  */
 'use strict';
 
diff --git a/Libraries/Components/MaskedView/MaskedViewIOS.android.js b/Libraries/Components/MaskedView/MaskedViewIOS.android.js
index ad37017e1c20..9684447d0fea 100644
--- a/Libraries/Components/MaskedView/MaskedViewIOS.android.js
+++ b/Libraries/Components/MaskedView/MaskedViewIOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule MaskedViewIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/MaskedView/MaskedViewIOS.ios.js b/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
index 0d61728c4b29..0407d3be089f 100644
--- a/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
+++ b/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule MaskedViewIOS
  * @flow
  */
 
diff --git a/Libraries/Components/Navigation/NavigatorIOS.android.js b/Libraries/Components/Navigation/NavigatorIOS.android.js
index 271f7ea0143f..ebd42dd5b18b 100644
--- a/Libraries/Components/Navigation/NavigatorIOS.android.js
+++ b/Libraries/Components/Navigation/NavigatorIOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NavigatorIOS
  */
 'use strict';
 
diff --git a/Libraries/Components/Navigation/NavigatorIOS.ios.js b/Libraries/Components/Navigation/NavigatorIOS.ios.js
index 289680bf6fc6..36223bfadca3 100644
--- a/Libraries/Components/Navigation/NavigatorIOS.ios.js
+++ b/Libraries/Components/Navigation/NavigatorIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NavigatorIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/Picker/Picker.js b/Libraries/Components/Picker/Picker.js
index 1df316249d7c..121299319106 100644
--- a/Libraries/Components/Picker/Picker.js
+++ b/Libraries/Components/Picker/Picker.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Picker
  * @flow
  */
 
diff --git a/Libraries/Components/Picker/PickerAndroid.android.js b/Libraries/Components/Picker/PickerAndroid.android.js
index bd9c664a8fa5..6bc912bd6d33 100644
--- a/Libraries/Components/Picker/PickerAndroid.android.js
+++ b/Libraries/Components/Picker/PickerAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PickerAndroid
  * @flow
  */
 
diff --git a/Libraries/Components/Picker/PickerAndroid.ios.js b/Libraries/Components/Picker/PickerAndroid.ios.js
index b84e15bad67a..ebd42dd5b18b 100644
--- a/Libraries/Components/Picker/PickerAndroid.ios.js
+++ b/Libraries/Components/Picker/PickerAndroid.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PickerAndroid
  */
 'use strict';
 
diff --git a/Libraries/Components/Picker/PickerIOS.android.js b/Libraries/Components/Picker/PickerIOS.android.js
index ce50c2ad4e41..2977696844b0 100644
--- a/Libraries/Components/Picker/PickerIOS.android.js
+++ b/Libraries/Components/Picker/PickerIOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PickerIOS
  *
  * This is a controlled component version of RCTPickerIOS
  */
diff --git a/Libraries/Components/Picker/PickerIOS.ios.js b/Libraries/Components/Picker/PickerIOS.ios.js
index d1fe0761d5cc..fcd5b12c1633 100644
--- a/Libraries/Components/Picker/PickerIOS.ios.js
+++ b/Libraries/Components/Picker/PickerIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PickerIOS
  *
  * This is a controlled component version of RCTPickerIOS
  */
diff --git a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
index f5dcb10cfb95..db20d579db0a 100644
--- a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
+++ b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ProgressBarAndroid
  */
 'use strict';
 
diff --git a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.ios.js b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.ios.js
index 92bae8066abe..ebd42dd5b18b 100644
--- a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.ios.js
+++ b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ProgressBarAndroid
  */
 'use strict';
 
diff --git a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.android.js b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.android.js
index f467db1ff51f..dcc8c3fc7489 100644
--- a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.android.js
+++ b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.android.js
@@ -5,7 +5,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ProgressViewIOS
  */
 
 'use strict';
diff --git a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
index 55ae1b83abe1..2c14b4cddff7 100644
--- a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
+++ b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ProgressViewIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/RefreshControl/RefreshControl.js b/Libraries/Components/RefreshControl/RefreshControl.js
index 8aac1ebf3e57..07415276261a 100644
--- a/Libraries/Components/RefreshControl/RefreshControl.js
+++ b/Libraries/Components/RefreshControl/RefreshControl.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RefreshControl
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/SafeAreaView/SafeAreaView.android.js b/Libraries/Components/SafeAreaView/SafeAreaView.android.js
index 62a81a8a2843..fbc940205383 100644
--- a/Libraries/Components/SafeAreaView/SafeAreaView.android.js
+++ b/Libraries/Components/SafeAreaView/SafeAreaView.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SafeAreaView
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/SafeAreaView/SafeAreaView.ios.js b/Libraries/Components/SafeAreaView/SafeAreaView.ios.js
index 344cbe5f301e..65daa32fd754 100644
--- a/Libraries/Components/SafeAreaView/SafeAreaView.ios.js
+++ b/Libraries/Components/SafeAreaView/SafeAreaView.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SafeAreaView
  * @flow
  * @format
  */
diff --git a/Libraries/Components/ScrollResponder.js b/Libraries/Components/ScrollResponder.js
index 6c926b9d40e1..93431293a348 100644
--- a/Libraries/Components/ScrollResponder.js
+++ b/Libraries/Components/ScrollResponder.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ScrollResponder
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 2d9d031027ca..0ec0f188abd8 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ScrollView
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/ScrollView/ScrollViewStickyHeader.js b/Libraries/Components/ScrollView/ScrollViewStickyHeader.js
index af9dc9b8b635..e17467b264cd 100644
--- a/Libraries/Components/ScrollView/ScrollViewStickyHeader.js
+++ b/Libraries/Components/ScrollView/ScrollViewStickyHeader.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ScrollViewStickyHeader
  * @flow
  * @format
  */
diff --git a/Libraries/Components/ScrollView/processDecelerationRate.js b/Libraries/Components/ScrollView/processDecelerationRate.js
index 9cb5a52a5577..f46755fda278 100644
--- a/Libraries/Components/ScrollView/processDecelerationRate.js
+++ b/Libraries/Components/ScrollView/processDecelerationRate.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule processDecelerationRate
  */
 'use strict';
 
diff --git a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.android.js b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.android.js
index a5b4c0b339bf..a8b791e2f6ef 100644
--- a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.android.js
+++ b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.android.js
@@ -5,7 +5,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SegmentedControlIOS
  */
 
 'use strict';
diff --git a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
index 3eb4249fa2db..620a8a3ec5c0 100644
--- a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
+++ b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SegmentedControlIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index 5a163fe176d1..c0f3d015badb 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Slider
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/StaticContainer.react.js b/Libraries/Components/StaticContainer.react.js
index 81e06ace1fdb..a6a4454c8118 100644
--- a/Libraries/Components/StaticContainer.react.js
+++ b/Libraries/Components/StaticContainer.react.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StaticContainer.react
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/StaticRenderer.js b/Libraries/Components/StaticRenderer.js
index 777fe900e120..5bb9cb99f484 100644
--- a/Libraries/Components/StaticRenderer.js
+++ b/Libraries/Components/StaticRenderer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StaticRenderer
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/StatusBar/StatusBar.js b/Libraries/Components/StatusBar/StatusBar.js
index 0562a3154938..05bd9177ccd4 100644
--- a/Libraries/Components/StatusBar/StatusBar.js
+++ b/Libraries/Components/StatusBar/StatusBar.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StatusBar
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/StatusBar/StatusBarIOS.android.js b/Libraries/Components/StatusBar/StatusBarIOS.android.js
index 5c69c15339ad..28ad139b8969 100644
--- a/Libraries/Components/StatusBar/StatusBarIOS.android.js
+++ b/Libraries/Components/StatusBar/StatusBarIOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StatusBarIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/StatusBar/StatusBarIOS.ios.js b/Libraries/Components/StatusBar/StatusBarIOS.ios.js
index f132f005696d..3ccab44da625 100644
--- a/Libraries/Components/StatusBar/StatusBarIOS.ios.js
+++ b/Libraries/Components/StatusBar/StatusBarIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StatusBarIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/Subscribable.js b/Libraries/Components/Subscribable.js
index 6825acd02f70..a4fc660b5b9f 100644
--- a/Libraries/Components/Subscribable.js
+++ b/Libraries/Components/Subscribable.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Subscribable
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/Switch/Switch.js b/Libraries/Components/Switch/Switch.js
index f259229c3538..ad613e2c85d4 100644
--- a/Libraries/Components/Switch/Switch.js
+++ b/Libraries/Components/Switch/Switch.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Switch
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/TabBarIOS/TabBarIOS.android.js b/Libraries/Components/TabBarIOS/TabBarIOS.android.js
index c52d947ebd32..62a6bbac8fb9 100644
--- a/Libraries/Components/TabBarIOS/TabBarIOS.android.js
+++ b/Libraries/Components/TabBarIOS/TabBarIOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TabBarIOS
  * @flow
  */
 
diff --git a/Libraries/Components/TabBarIOS/TabBarIOS.ios.js b/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
index 9d1b63567ba8..57e32df01e5b 100644
--- a/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
+++ b/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TabBarIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/TabBarIOS/TabBarItemIOS.android.js b/Libraries/Components/TabBarIOS/TabBarItemIOS.android.js
index ff891312c21a..6f6ff5618923 100644
--- a/Libraries/Components/TabBarIOS/TabBarItemIOS.android.js
+++ b/Libraries/Components/TabBarIOS/TabBarItemIOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TabBarItemIOS
  */
 
 'use strict';
diff --git a/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js b/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
index 6b56cf78ecb8..3f0b85a0c501 100644
--- a/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
+++ b/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TabBarItemIOS
  * @noflow
  */
 'use strict';
diff --git a/Libraries/Components/TextInput/InputAccessoryView.js b/Libraries/Components/TextInput/InputAccessoryView.js
index 73d83c03a22b..731476bc7138 100644
--- a/Libraries/Components/TextInput/InputAccessoryView.js
+++ b/Libraries/Components/TextInput/InputAccessoryView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InputAccessoryView
  * @flow
  * @format
  */
diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index fd67b8ec55fc..e887b07438f4 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TextInput
  * @flow
  * @format
  */
diff --git a/Libraries/Components/TextInput/TextInputState.js b/Libraries/Components/TextInput/TextInputState.js
index cb41eef0c529..47eeddf12189 100644
--- a/Libraries/Components/TextInput/TextInputState.js
+++ b/Libraries/Components/TextInput/TextInputState.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TextInputState
  * @flow
  *
  * This class is responsible for coordinating the "focused"
diff --git a/Libraries/Components/TimePickerAndroid/TimePickerAndroid.android.js b/Libraries/Components/TimePickerAndroid/TimePickerAndroid.android.js
index be7f4c4f9286..b2b8c759e595 100644
--- a/Libraries/Components/TimePickerAndroid/TimePickerAndroid.android.js
+++ b/Libraries/Components/TimePickerAndroid/TimePickerAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TimePickerAndroid
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/TimePickerAndroid/TimePickerAndroid.ios.js b/Libraries/Components/TimePickerAndroid/TimePickerAndroid.ios.js
index a6b630d7c394..3813b6522b00 100644
--- a/Libraries/Components/TimePickerAndroid/TimePickerAndroid.ios.js
+++ b/Libraries/Components/TimePickerAndroid/TimePickerAndroid.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TimePickerAndroid
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/ToastAndroid/ToastAndroid.android.js b/Libraries/Components/ToastAndroid/ToastAndroid.android.js
index 15a8a597a5b6..b0a242ed5ffe 100644
--- a/Libraries/Components/ToastAndroid/ToastAndroid.android.js
+++ b/Libraries/Components/ToastAndroid/ToastAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ToastAndroid
  * @flow
  */
 
diff --git a/Libraries/Components/ToastAndroid/ToastAndroid.ios.js b/Libraries/Components/ToastAndroid/ToastAndroid.ios.js
index 83db0cfa82ca..94d0487647ac 100644
--- a/Libraries/Components/ToastAndroid/ToastAndroid.ios.js
+++ b/Libraries/Components/ToastAndroid/ToastAndroid.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ToastAndroid
  * @noflow
  */
 'use strict';
diff --git a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
index 1d845e5b65ba..de6fd5aad12b 100644
--- a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
+++ b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ToolbarAndroid
  */
 
 'use strict';
diff --git a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.ios.js b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.ios.js
index 68ef4ef8300a..ebd42dd5b18b 100644
--- a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.ios.js
+++ b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ToolbarAndroid
  */
 'use strict';
 
diff --git a/Libraries/Components/Touchable/BoundingDimensions.js b/Libraries/Components/Touchable/BoundingDimensions.js
index 9bc78e515d8e..898244979d28 100644
--- a/Libraries/Components/Touchable/BoundingDimensions.js
+++ b/Libraries/Components/Touchable/BoundingDimensions.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BoundingDimensions
  */
 
 'use strict';
diff --git a/Libraries/Components/Touchable/PooledClass.js b/Libraries/Components/Touchable/PooledClass.js
index a3ae190aa3d2..42cb503d07b7 100644
--- a/Libraries/Components/Touchable/PooledClass.js
+++ b/Libraries/Components/Touchable/PooledClass.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PooledClass
  * @flow
  */
 
diff --git a/Libraries/Components/Touchable/Position.js b/Libraries/Components/Touchable/Position.js
index 572d1132f038..ce09d00a8e36 100644
--- a/Libraries/Components/Touchable/Position.js
+++ b/Libraries/Components/Touchable/Position.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Position
  */
 
 'use strict';
diff --git a/Libraries/Components/Touchable/Touchable.js b/Libraries/Components/Touchable/Touchable.js
index f39457b82725..208315332716 100644
--- a/Libraries/Components/Touchable/Touchable.js
+++ b/Libraries/Components/Touchable/Touchable.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Touchable
  */
 
 'use strict';
diff --git a/Libraries/Components/Touchable/TouchableBounce.js b/Libraries/Components/Touchable/TouchableBounce.js
index 2afef30637b5..1ebb1a877415 100644
--- a/Libraries/Components/Touchable/TouchableBounce.js
+++ b/Libraries/Components/Touchable/TouchableBounce.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TouchableBounce
  * @flow
  * @format
  */
diff --git a/Libraries/Components/Touchable/TouchableHighlight.js b/Libraries/Components/Touchable/TouchableHighlight.js
index 19680b236528..4d8f63eecdd0 100644
--- a/Libraries/Components/Touchable/TouchableHighlight.js
+++ b/Libraries/Components/Touchable/TouchableHighlight.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TouchableHighlight
  * @flow
  * @format
  */
diff --git a/Libraries/Components/Touchable/TouchableNativeFeedback.android.js b/Libraries/Components/Touchable/TouchableNativeFeedback.android.js
index 4f3887642dce..00f67818bf45 100644
--- a/Libraries/Components/Touchable/TouchableNativeFeedback.android.js
+++ b/Libraries/Components/Touchable/TouchableNativeFeedback.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TouchableNativeFeedback
  */
 'use strict';
 
diff --git a/Libraries/Components/Touchable/TouchableNativeFeedback.ios.js b/Libraries/Components/Touchable/TouchableNativeFeedback.ios.js
index e898d20ab64a..8c195b9549bd 100644
--- a/Libraries/Components/Touchable/TouchableNativeFeedback.ios.js
+++ b/Libraries/Components/Touchable/TouchableNativeFeedback.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TouchableNativeFeedback
  */
 
 'use strict';
diff --git a/Libraries/Components/Touchable/TouchableOpacity.js b/Libraries/Components/Touchable/TouchableOpacity.js
index 8ff2ab8d0f2a..4ae20db8fb28 100644
--- a/Libraries/Components/Touchable/TouchableOpacity.js
+++ b/Libraries/Components/Touchable/TouchableOpacity.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TouchableOpacity
  * @noflow
  */
 'use strict';
diff --git a/Libraries/Components/Touchable/TouchableWithoutFeedback.js b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
index 642c8593cbe0..d59d04cf4e6c 100755
--- a/Libraries/Components/Touchable/TouchableWithoutFeedback.js
+++ b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TouchableWithoutFeedback
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/Touchable/ensureComponentIsNative.js b/Libraries/Components/Touchable/ensureComponentIsNative.js
index 63c1e8bf8d02..9b82aeb45ec6 100644
--- a/Libraries/Components/Touchable/ensureComponentIsNative.js
+++ b/Libraries/Components/Touchable/ensureComponentIsNative.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ensureComponentIsNative
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/Touchable/ensurePositiveDelayProps.js b/Libraries/Components/Touchable/ensurePositiveDelayProps.js
index 51b97f5ca42e..9d0be5ccdc5e 100644
--- a/Libraries/Components/Touchable/ensurePositiveDelayProps.js
+++ b/Libraries/Components/Touchable/ensurePositiveDelayProps.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ensurePositiveDelayProps
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/UnimplementedViews/UnimplementedView.js b/Libraries/Components/UnimplementedViews/UnimplementedView.js
index 5da72d04f354..7be6f1ac77f7 100644
--- a/Libraries/Components/UnimplementedViews/UnimplementedView.js
+++ b/Libraries/Components/UnimplementedViews/UnimplementedView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule UnimplementedView
  * @flow
  * @format
  */
diff --git a/Libraries/Components/View/PlatformViewPropTypes.js b/Libraries/Components/View/PlatformViewPropTypes.js
index 891fa34572a4..70ab6694192f 100644
--- a/Libraries/Components/View/PlatformViewPropTypes.js
+++ b/Libraries/Components/View/PlatformViewPropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PlatformViewPropTypes
  * @flow
  */
 
diff --git a/Libraries/Components/View/ReactNativeStyleAttributes.js b/Libraries/Components/View/ReactNativeStyleAttributes.js
index a9441cad97f1..7c8422413579 100644
--- a/Libraries/Components/View/ReactNativeStyleAttributes.js
+++ b/Libraries/Components/View/ReactNativeStyleAttributes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNativeStyleAttributes
  * @flow
  */
 
diff --git a/Libraries/Components/View/ReactNativeViewAttributes.js b/Libraries/Components/View/ReactNativeViewAttributes.js
index 26fb368aceb9..f18b70281935 100644
--- a/Libraries/Components/View/ReactNativeViewAttributes.js
+++ b/Libraries/Components/View/ReactNativeViewAttributes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNativeViewAttributes
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/View/ShadowPropTypesIOS.js b/Libraries/Components/View/ShadowPropTypesIOS.js
index f4f2f0ab4c48..2dfc021735ad 100644
--- a/Libraries/Components/View/ShadowPropTypesIOS.js
+++ b/Libraries/Components/View/ShadowPropTypesIOS.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ShadowPropTypesIOS
  * @flow
  * @format
  */
diff --git a/Libraries/Components/View/View.js b/Libraries/Components/View/View.js
index 0a77bff8a407..558f40a5d408 100644
--- a/Libraries/Components/View/View.js
+++ b/Libraries/Components/View/View.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule View
  * @flow
  * @format
  */
diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index b45366fd0797..edab2a569511 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewAccessibility
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/View/ViewContext.js b/Libraries/Components/View/ViewContext.js
index f9f98000409d..81879aa35ecf 100644
--- a/Libraries/Components/View/ViewContext.js
+++ b/Libraries/Components/View/ViewContext.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewContext
  * @flow
  * @format
  */
diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 574bd577cc99..f5f03bf10efd 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewPropTypes
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/View/ViewStylePropTypes.js b/Libraries/Components/View/ViewStylePropTypes.js
index c21ce5934ac3..e252cf5d2c78 100644
--- a/Libraries/Components/View/ViewStylePropTypes.js
+++ b/Libraries/Components/View/ViewStylePropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewStylePropTypes
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/ViewPager/ViewPagerAndroid.android.js b/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
index 8463503bd793..19421ccc6436 100644
--- a/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
+++ b/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewPagerAndroid
  * @flow
  */
 'use strict';
diff --git a/Libraries/Components/ViewPager/ViewPagerAndroid.ios.js b/Libraries/Components/ViewPager/ViewPagerAndroid.ios.js
index ee0022ae5453..ebd42dd5b18b 100644
--- a/Libraries/Components/ViewPager/ViewPagerAndroid.ios.js
+++ b/Libraries/Components/ViewPager/ViewPagerAndroid.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewPagerAndroid
  */
 'use strict';
 
diff --git a/Libraries/Components/WebView/WebView.android.js b/Libraries/Components/WebView/WebView.android.js
index 16f2991df1e7..a457298f96f6 100644
--- a/Libraries/Components/WebView/WebView.android.js
+++ b/Libraries/Components/WebView/WebView.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule WebView
  */
 'use strict';
 
diff --git a/Libraries/Components/WebView/WebView.ios.js b/Libraries/Components/WebView/WebView.ios.js
index f01cfae537dd..56a4465fea6b 100644
--- a/Libraries/Components/WebView/WebView.ios.js
+++ b/Libraries/Components/WebView/WebView.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule WebView
  * @noflow
  */
 'use strict';
diff --git a/Libraries/Core/Devtools/getDevServer.js b/Libraries/Core/Devtools/getDevServer.js
index 975a75f827b2..1087f6ead2b7 100644
--- a/Libraries/Core/Devtools/getDevServer.js
+++ b/Libraries/Core/Devtools/getDevServer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule getDevServer
  * @flow
  */
 'use strict';
diff --git a/Libraries/Core/Devtools/openFileInEditor.js b/Libraries/Core/Devtools/openFileInEditor.js
index a5f9da59e6b1..1f4437a5ef8c 100644
--- a/Libraries/Core/Devtools/openFileInEditor.js
+++ b/Libraries/Core/Devtools/openFileInEditor.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule openFileInEditor
  * @flow
  */
 'use strict';
diff --git a/Libraries/Core/Devtools/parseErrorStack.js b/Libraries/Core/Devtools/parseErrorStack.js
index e1ae27294fee..efcad10191d4 100644
--- a/Libraries/Core/Devtools/parseErrorStack.js
+++ b/Libraries/Core/Devtools/parseErrorStack.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule parseErrorStack
  * @flow
  */
 'use strict';
diff --git a/Libraries/Core/Devtools/setupDevtools.js b/Libraries/Core/Devtools/setupDevtools.js
index cbfb8df3983b..fec7ea6160cc 100644
--- a/Libraries/Core/Devtools/setupDevtools.js
+++ b/Libraries/Core/Devtools/setupDevtools.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule setupDevtools
  * @flow
  */
 'use strict';
diff --git a/Libraries/Core/Devtools/symbolicateStackTrace.js b/Libraries/Core/Devtools/symbolicateStackTrace.js
index 5ac25fe03e98..8933394ba92d 100644
--- a/Libraries/Core/Devtools/symbolicateStackTrace.js
+++ b/Libraries/Core/Devtools/symbolicateStackTrace.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule symbolicateStackTrace
  * @flow
  */
 'use strict';
diff --git a/Libraries/Core/ExceptionsManager.js b/Libraries/Core/ExceptionsManager.js
index 8a63ec3bff4b..6a0ba132dc81 100644
--- a/Libraries/Core/ExceptionsManager.js
+++ b/Libraries/Core/ExceptionsManager.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ExceptionsManager
  * @flow
  */
 'use strict';
diff --git a/Libraries/Core/InitializeCore.js b/Libraries/Core/InitializeCore.js
index c97576397a94..d739ab782317 100644
--- a/Libraries/Core/InitializeCore.js
+++ b/Libraries/Core/InitializeCore.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InitializeCore
  * @flow
  */
 
diff --git a/Libraries/Core/ReactNativeVersion.js b/Libraries/Core/ReactNativeVersion.js
index 52b8f9c47b8f..1b2b2155f551 100644
--- a/Libraries/Core/ReactNativeVersion.js
+++ b/Libraries/Core/ReactNativeVersion.js
@@ -7,7 +7,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ReactNativeVersion
  */
 
 exports.version = {
diff --git a/Libraries/Core/ReactNativeVersionCheck.js b/Libraries/Core/ReactNativeVersionCheck.js
index acbac3337baf..8a937c769d99 100644
--- a/Libraries/Core/ReactNativeVersionCheck.js
+++ b/Libraries/Core/ReactNativeVersionCheck.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNativeVersionCheck
  * @flow
  * @format
  */
diff --git a/Libraries/Core/Timers/JSTimers.js b/Libraries/Core/Timers/JSTimers.js
index e0b4fbbd8866..dbd23f807f81 100644
--- a/Libraries/Core/Timers/JSTimers.js
+++ b/Libraries/Core/Timers/JSTimers.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule JSTimers
  * @format
  * @flow
  */
diff --git a/Libraries/EventEmitter/MissingNativeEventEmitterShim.js b/Libraries/EventEmitter/MissingNativeEventEmitterShim.js
index d4abfc228a4b..e9c11b925c8e 100644
--- a/Libraries/EventEmitter/MissingNativeEventEmitterShim.js
+++ b/Libraries/EventEmitter/MissingNativeEventEmitterShim.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule MissingNativeEventEmitterShim
  * @flow
  */
 'use strict';
diff --git a/Libraries/EventEmitter/NativeEventEmitter.js b/Libraries/EventEmitter/NativeEventEmitter.js
index f453cbc5184e..582cf9561f16 100644
--- a/Libraries/EventEmitter/NativeEventEmitter.js
+++ b/Libraries/EventEmitter/NativeEventEmitter.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NativeEventEmitter
  * @flow
  */
 'use strict';
diff --git a/Libraries/EventEmitter/RCTDeviceEventEmitter.js b/Libraries/EventEmitter/RCTDeviceEventEmitter.js
index 57ce4fa08990..9378a5f5310b 100644
--- a/Libraries/EventEmitter/RCTDeviceEventEmitter.js
+++ b/Libraries/EventEmitter/RCTDeviceEventEmitter.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTDeviceEventEmitter
  * @flow
  */
 'use strict';
diff --git a/Libraries/EventEmitter/RCTEventEmitter.js b/Libraries/EventEmitter/RCTEventEmitter.js
index 581515482f1c..976356b7aa07 100644
--- a/Libraries/EventEmitter/RCTEventEmitter.js
+++ b/Libraries/EventEmitter/RCTEventEmitter.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTEventEmitter
  * @flow
  */
 'use strict';
diff --git a/Libraries/EventEmitter/RCTNativeAppEventEmitter.js b/Libraries/EventEmitter/RCTNativeAppEventEmitter.js
index 9fe0a1573fe1..43245aba558e 100644
--- a/Libraries/EventEmitter/RCTNativeAppEventEmitter.js
+++ b/Libraries/EventEmitter/RCTNativeAppEventEmitter.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTNativeAppEventEmitter
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/Incremental.js b/Libraries/Experimental/Incremental.js
index 45c0a7dce5a0..237e5dbc32e7 100644
--- a/Libraries/Experimental/Incremental.js
+++ b/Libraries/Experimental/Incremental.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Incremental
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/IncrementalExample.js b/Libraries/Experimental/IncrementalExample.js
index 280d36f198cf..e46510b5e4e9 100644
--- a/Libraries/Experimental/IncrementalExample.js
+++ b/Libraries/Experimental/IncrementalExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule IncrementalExample
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/IncrementalGroup.js b/Libraries/Experimental/IncrementalGroup.js
index e2aefae6836f..f630ba66c8c5 100644
--- a/Libraries/Experimental/IncrementalGroup.js
+++ b/Libraries/Experimental/IncrementalGroup.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule IncrementalGroup
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/IncrementalPresenter.js b/Libraries/Experimental/IncrementalPresenter.js
index 03c69d1fcdcf..05520a3ec487 100644
--- a/Libraries/Experimental/IncrementalPresenter.js
+++ b/Libraries/Experimental/IncrementalPresenter.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule IncrementalPresenter
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableFlatList.js b/Libraries/Experimental/SwipeableRow/SwipeableFlatList.js
index f7f78b40103a..b01fea760dd0 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableFlatList.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableFlatList.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SwipeableFlatList
  * @flow
  * @format
  */
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableListView.js b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
index c6623be75b3b..4187684ddb67 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableListView.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SwipeableListView
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableListViewDataSource.js b/Libraries/Experimental/SwipeableRow/SwipeableListViewDataSource.js
index bda3bd3b5306..da4377acad8f 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableListViewDataSource.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableListViewDataSource.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SwipeableListViewDataSource
  */
 'use strict';
 
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js b/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
index 315b8a2f64c3..704f315961ce 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SwipeableQuickActionButton
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableQuickActions.js b/Libraries/Experimental/SwipeableRow/SwipeableQuickActions.js
index 96fe1d23daab..42d2f2cc060b 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableQuickActions.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableQuickActions.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SwipeableQuickActions
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableRow.js b/Libraries/Experimental/SwipeableRow/SwipeableRow.js
index 80e627376e84..0c072611aaca 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableRow.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableRow.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SwipeableRow
  * @flow
  */
 'use strict';
diff --git a/Libraries/Experimental/WindowedListView.js b/Libraries/Experimental/WindowedListView.js
index 2a102b23f3c4..bf7ef3324b81 100644
--- a/Libraries/Experimental/WindowedListView.js
+++ b/Libraries/Experimental/WindowedListView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule WindowedListView
  * @flow
  */
 'use strict';
diff --git a/Libraries/Geolocation/Geolocation.js b/Libraries/Geolocation/Geolocation.js
index a4efe4c0201c..29bb0aa13a99 100644
--- a/Libraries/Geolocation/Geolocation.js
+++ b/Libraries/Geolocation/Geolocation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Geolocation
  * @flow
  */
 'use strict';
diff --git a/Libraries/Image/AssetRegistry.js b/Libraries/Image/AssetRegistry.js
index 7dabcfb9b535..5f5f0980f432 100644
--- a/Libraries/Image/AssetRegistry.js
+++ b/Libraries/Image/AssetRegistry.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AssetRegistry
  * @flow
  * @format
  */
diff --git a/Libraries/Image/AssetSourceResolver.js b/Libraries/Image/AssetSourceResolver.js
index 819353e03846..d7b583ebcb8d 100644
--- a/Libraries/Image/AssetSourceResolver.js
+++ b/Libraries/Image/AssetSourceResolver.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AssetSourceResolver
  * @flow
  * @format
  */
diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index 4c8fa6e7fd17..7b0ec83a8738 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Image
  * @flow
  * @format
  */
diff --git a/Libraries/Image/Image.ios.js b/Libraries/Image/Image.ios.js
index c3e9ad5359c1..eb0d0241af52 100644
--- a/Libraries/Image/Image.ios.js
+++ b/Libraries/Image/Image.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Image
  * @flow
  * @format
  */
diff --git a/Libraries/Image/ImageBackground.js b/Libraries/Image/ImageBackground.js
index 405bced59ce2..7b86d9c5f529 100644
--- a/Libraries/Image/ImageBackground.js
+++ b/Libraries/Image/ImageBackground.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageBackground
  * @flow
  * @format
  */
diff --git a/Libraries/Image/ImageEditor.js b/Libraries/Image/ImageEditor.js
index ddd7fd381285..66504b501293 100644
--- a/Libraries/Image/ImageEditor.js
+++ b/Libraries/Image/ImageEditor.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageEditor
  * @flow
  * @format
  */
diff --git a/Libraries/Image/ImageProps.js b/Libraries/Image/ImageProps.js
index f075d9cceced..63015586296d 100644
--- a/Libraries/Image/ImageProps.js
+++ b/Libraries/Image/ImageProps.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageProps
  * @flow
  * @format
  */
diff --git a/Libraries/Image/ImageResizeMode.js b/Libraries/Image/ImageResizeMode.js
index 25d937d60efe..89e74bcc502e 100644
--- a/Libraries/Image/ImageResizeMode.js
+++ b/Libraries/Image/ImageResizeMode.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageResizeMode
  * @flow
  * @format
  */
diff --git a/Libraries/Image/ImageSource.js b/Libraries/Image/ImageSource.js
index 533eb513219c..b729863234ff 100644
--- a/Libraries/Image/ImageSource.js
+++ b/Libraries/Image/ImageSource.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageSource
  * @flow
  * @format
  */
diff --git a/Libraries/Image/ImageSourcePropType.js b/Libraries/Image/ImageSourcePropType.js
index af9dac3c4794..6f67113fe1bf 100644
--- a/Libraries/Image/ImageSourcePropType.js
+++ b/Libraries/Image/ImageSourcePropType.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageSourcePropType
  * @no-flow
  * @format
  */
diff --git a/Libraries/Image/ImageStore.js b/Libraries/Image/ImageStore.js
index 215bdec246cb..5373020376a5 100644
--- a/Libraries/Image/ImageStore.js
+++ b/Libraries/Image/ImageStore.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageStore
  * @flow
  * @format
  */
diff --git a/Libraries/Image/ImageStylePropTypes.js b/Libraries/Image/ImageStylePropTypes.js
index 9a688ac7f9d4..c88c19ea3cec 100644
--- a/Libraries/Image/ImageStylePropTypes.js
+++ b/Libraries/Image/ImageStylePropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageStylePropTypes
  * @flow
  * @format
  */
diff --git a/Libraries/Image/RelativeImageStub.js b/Libraries/Image/RelativeImageStub.js
index 4adf66b806b4..866488eecc83 100644
--- a/Libraries/Image/RelativeImageStub.js
+++ b/Libraries/Image/RelativeImageStub.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RelativeImageStub
  * @flow
  */
 'use strict';
diff --git a/Libraries/Image/nativeImageSource.js b/Libraries/Image/nativeImageSource.js
index 26b194ace776..1fdbe1caa976 100644
--- a/Libraries/Image/nativeImageSource.js
+++ b/Libraries/Image/nativeImageSource.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule nativeImageSource
  * @flow
  * @format
  */
diff --git a/Libraries/Image/resolveAssetSource.js b/Libraries/Image/resolveAssetSource.js
index 0d160a28077d..fefb28ff5f7b 100644
--- a/Libraries/Image/resolveAssetSource.js
+++ b/Libraries/Image/resolveAssetSource.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule resolveAssetSource
  * @flow
  *
  * Resolves an asset into a `source` for `Image`.
diff --git a/Libraries/Inspector/BorderBox.js b/Libraries/Inspector/BorderBox.js
index c121de5ea1da..7ed32e73ae49 100644
--- a/Libraries/Inspector/BorderBox.js
+++ b/Libraries/Inspector/BorderBox.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BorderBox
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/BoxInspector.js b/Libraries/Inspector/BoxInspector.js
index 31bedeecdaa0..6009e78ea441 100644
--- a/Libraries/Inspector/BoxInspector.js
+++ b/Libraries/Inspector/BoxInspector.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BoxInspector
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/ElementBox.js b/Libraries/Inspector/ElementBox.js
index b9caef093cc3..7eebb22f337a 100644
--- a/Libraries/Inspector/ElementBox.js
+++ b/Libraries/Inspector/ElementBox.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ElementBox
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/ElementProperties.js b/Libraries/Inspector/ElementProperties.js
index 460e1c2df810..75beaf93e233 100644
--- a/Libraries/Inspector/ElementProperties.js
+++ b/Libraries/Inspector/ElementProperties.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ElementProperties
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/Inspector.js b/Libraries/Inspector/Inspector.js
index 963b616fca3b..73ce0719b36d 100644
--- a/Libraries/Inspector/Inspector.js
+++ b/Libraries/Inspector/Inspector.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Inspector
  * @flow
  */
 
diff --git a/Libraries/Inspector/InspectorOverlay.js b/Libraries/Inspector/InspectorOverlay.js
index d441ba59884e..3ef8ae60f350 100644
--- a/Libraries/Inspector/InspectorOverlay.js
+++ b/Libraries/Inspector/InspectorOverlay.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InspectorOverlay
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/InspectorPanel.js b/Libraries/Inspector/InspectorPanel.js
index c4031a355d5c..b2dd639c4a89 100644
--- a/Libraries/Inspector/InspectorPanel.js
+++ b/Libraries/Inspector/InspectorPanel.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InspectorPanel
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/NetworkOverlay.js b/Libraries/Inspector/NetworkOverlay.js
index 789ac6de824c..3651aa351189 100644
--- a/Libraries/Inspector/NetworkOverlay.js
+++ b/Libraries/Inspector/NetworkOverlay.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NetworkOverlay
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/PerformanceOverlay.js b/Libraries/Inspector/PerformanceOverlay.js
index 8240a43244ac..d414ea2db298 100644
--- a/Libraries/Inspector/PerformanceOverlay.js
+++ b/Libraries/Inspector/PerformanceOverlay.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PerformanceOverlay
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/StyleInspector.js b/Libraries/Inspector/StyleInspector.js
index 7bd137bdea7d..a65e02799652 100644
--- a/Libraries/Inspector/StyleInspector.js
+++ b/Libraries/Inspector/StyleInspector.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StyleInspector
  * @flow
  */
 'use strict';
diff --git a/Libraries/Inspector/resolveBoxStyle.js b/Libraries/Inspector/resolveBoxStyle.js
index 28f4af50525b..43026ada8f76 100644
--- a/Libraries/Inspector/resolveBoxStyle.js
+++ b/Libraries/Inspector/resolveBoxStyle.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule resolveBoxStyle
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/Batchinator.js b/Libraries/Interaction/Batchinator.js
index 3f3b4e069a01..84097514ba64 100644
--- a/Libraries/Interaction/Batchinator.js
+++ b/Libraries/Interaction/Batchinator.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Batchinator
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/BridgeSpyStallHandler.js b/Libraries/Interaction/BridgeSpyStallHandler.js
index f47f0751d8ad..88f892442d09 100644
--- a/Libraries/Interaction/BridgeSpyStallHandler.js
+++ b/Libraries/Interaction/BridgeSpyStallHandler.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BridgeSpyStallHandler
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/FrameRateLogger.js b/Libraries/Interaction/FrameRateLogger.js
index 072adeb930f8..252fc465a3d4 100644
--- a/Libraries/Interaction/FrameRateLogger.js
+++ b/Libraries/Interaction/FrameRateLogger.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule FrameRateLogger
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/InteractionManager.js b/Libraries/Interaction/InteractionManager.js
index 227e1b05bd3a..7373575a0cae 100644
--- a/Libraries/Interaction/InteractionManager.js
+++ b/Libraries/Interaction/InteractionManager.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InteractionManager
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/InteractionMixin.js b/Libraries/Interaction/InteractionMixin.js
index 9e81a4fddaec..e4310ad91d86 100644
--- a/Libraries/Interaction/InteractionMixin.js
+++ b/Libraries/Interaction/InteractionMixin.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InteractionMixin
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/InteractionStallDebugger.js b/Libraries/Interaction/InteractionStallDebugger.js
index 8d2bcc82e5f9..f62e8d244444 100644
--- a/Libraries/Interaction/InteractionStallDebugger.js
+++ b/Libraries/Interaction/InteractionStallDebugger.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InteractionStallDebugger
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/JSEventLoopWatchdog.js b/Libraries/Interaction/JSEventLoopWatchdog.js
index 2d1866a0c77f..8e2f00eef41d 100644
--- a/Libraries/Interaction/JSEventLoopWatchdog.js
+++ b/Libraries/Interaction/JSEventLoopWatchdog.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule JSEventLoopWatchdog
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/PanResponder.js b/Libraries/Interaction/PanResponder.js
index d927fa5fc14d..92438d904656 100644
--- a/Libraries/Interaction/PanResponder.js
+++ b/Libraries/Interaction/PanResponder.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PanResponder
  */
 
 'use strict';
diff --git a/Libraries/Interaction/ReactPerfStallHandler.js b/Libraries/Interaction/ReactPerfStallHandler.js
index 394bc7533ca1..09c57dabc5f4 100644
--- a/Libraries/Interaction/ReactPerfStallHandler.js
+++ b/Libraries/Interaction/ReactPerfStallHandler.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactPerfStallHandler
  * @flow
  */
 'use strict';
diff --git a/Libraries/Interaction/TaskQueue.js b/Libraries/Interaction/TaskQueue.js
index 0ee5e4500af9..6660d84f4719 100644
--- a/Libraries/Interaction/TaskQueue.js
+++ b/Libraries/Interaction/TaskQueue.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TaskQueue
  * @flow
  */
 'use strict';
diff --git a/Libraries/JSInspector/InspectorAgent.js b/Libraries/JSInspector/InspectorAgent.js
index a5b6cca0da3d..b419a6c2aadf 100644
--- a/Libraries/JSInspector/InspectorAgent.js
+++ b/Libraries/JSInspector/InspectorAgent.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InspectorAgent
  * @flow
  */
 'use strict';
diff --git a/Libraries/JSInspector/JSInspector.js b/Libraries/JSInspector/JSInspector.js
index 9a6b13ffb7c6..e62669aee6a3 100644
--- a/Libraries/JSInspector/JSInspector.js
+++ b/Libraries/JSInspector/JSInspector.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule JSInspector
  * @flow
  */
 'use strict';
diff --git a/Libraries/JSInspector/NetworkAgent.js b/Libraries/JSInspector/NetworkAgent.js
index 56f6f2a37fdc..bf1de686ae91 100644
--- a/Libraries/JSInspector/NetworkAgent.js
+++ b/Libraries/JSInspector/NetworkAgent.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NetworkAgent
  * @flow
  */
 'use strict';
diff --git a/Libraries/LayoutAnimation/LayoutAnimation.js b/Libraries/LayoutAnimation/LayoutAnimation.js
index f04feca9331a..e739ec859515 100644
--- a/Libraries/LayoutAnimation/LayoutAnimation.js
+++ b/Libraries/LayoutAnimation/LayoutAnimation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule LayoutAnimation
  * @flow
  * @format
  */
diff --git a/Libraries/Linking/Linking.js b/Libraries/Linking/Linking.js
index a621e647adcc..a4ad9b3b5932 100644
--- a/Libraries/Linking/Linking.js
+++ b/Libraries/Linking/Linking.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Linking
  * @flow
  */
 'use strict';
diff --git a/Libraries/Lists/FillRateHelper.js b/Libraries/Lists/FillRateHelper.js
index f060897356b7..82b0612cdcf8 100644
--- a/Libraries/Lists/FillRateHelper.js
+++ b/Libraries/Lists/FillRateHelper.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule FillRateHelper
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/FlatList.js b/Libraries/Lists/FlatList.js
index 13b87ed995b7..5a0827be1df8 100644
--- a/Libraries/Lists/FlatList.js
+++ b/Libraries/Lists/FlatList.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule FlatList
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/ListView/ListView.js b/Libraries/Lists/ListView/ListView.js
index 9aefd2ea9222..b36150510e2c 100644
--- a/Libraries/Lists/ListView/ListView.js
+++ b/Libraries/Lists/ListView/ListView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ListView
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/ListView/ListViewDataSource.js b/Libraries/Lists/ListView/ListViewDataSource.js
index ec63c94d0f46..dda74b50cb83 100644
--- a/Libraries/Lists/ListView/ListViewDataSource.js
+++ b/Libraries/Lists/ListView/ListViewDataSource.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ListViewDataSource
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/MetroListView.js b/Libraries/Lists/MetroListView.js
index 5f22eb264ee8..f2447760f9ee 100644
--- a/Libraries/Lists/MetroListView.js
+++ b/Libraries/Lists/MetroListView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule MetroListView
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/SectionList.js b/Libraries/Lists/SectionList.js
index 2404d26f54c7..17a4f84711e0 100644
--- a/Libraries/Lists/SectionList.js
+++ b/Libraries/Lists/SectionList.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SectionList
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/ViewabilityHelper.js b/Libraries/Lists/ViewabilityHelper.js
index 0c0a83560190..415e77895360 100644
--- a/Libraries/Lists/ViewabilityHelper.js
+++ b/Libraries/Lists/ViewabilityHelper.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewabilityHelper
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/VirtualizeUtils.js b/Libraries/Lists/VirtualizeUtils.js
index 663b36b8cc6e..b47ceda1fece 100644
--- a/Libraries/Lists/VirtualizeUtils.js
+++ b/Libraries/Lists/VirtualizeUtils.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule VirtualizeUtils
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index bbfc6cf3bdec..ca6d9fc7fe56 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule VirtualizedList
  * @flow
  * @format
  */
diff --git a/Libraries/Lists/VirtualizedSectionList.js b/Libraries/Lists/VirtualizedSectionList.js
index 2bb196814abf..6da08dc1ab66 100644
--- a/Libraries/Lists/VirtualizedSectionList.js
+++ b/Libraries/Lists/VirtualizedSectionList.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule VirtualizedSectionList
  * @flow
  * @format
  */
diff --git a/Libraries/Modal/Modal.js b/Libraries/Modal/Modal.js
index dabdbc5d92f6..b1cc4a1cb7bb 100644
--- a/Libraries/Modal/Modal.js
+++ b/Libraries/Modal/Modal.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Modal
  * @flow
  */
 'use strict';
diff --git a/Libraries/Network/FormData.js b/Libraries/Network/FormData.js
index 669bf0f2a30c..6028a06bf876 100644
--- a/Libraries/Network/FormData.js
+++ b/Libraries/Network/FormData.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule FormData
  * @flow
  */
 'use strict';
diff --git a/Libraries/Network/NetInfo.js b/Libraries/Network/NetInfo.js
index 0db9d4eab268..474ce79144e0 100644
--- a/Libraries/Network/NetInfo.js
+++ b/Libraries/Network/NetInfo.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NetInfo
  * @flow
  */
 'use strict';
diff --git a/Libraries/Network/RCTNetworking.android.js b/Libraries/Network/RCTNetworking.android.js
index 9ec01dccecb8..30162a0e88c8 100644
--- a/Libraries/Network/RCTNetworking.android.js
+++ b/Libraries/Network/RCTNetworking.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTNetworking
  * @flow
  */
 'use strict';
diff --git a/Libraries/Network/RCTNetworking.ios.js b/Libraries/Network/RCTNetworking.ios.js
index 004322a080f1..2b834577809e 100644
--- a/Libraries/Network/RCTNetworking.ios.js
+++ b/Libraries/Network/RCTNetworking.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTNetworking
  * @flow
  */
 'use strict';
diff --git a/Libraries/Network/XHRInterceptor.js b/Libraries/Network/XHRInterceptor.js
index 09cc3b22038a..22c6cf853fe0 100644
--- a/Libraries/Network/XHRInterceptor.js
+++ b/Libraries/Network/XHRInterceptor.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule XHRInterceptor
  */
  'use strict';
 
diff --git a/Libraries/Network/XMLHttpRequest.js b/Libraries/Network/XMLHttpRequest.js
index d17001d3743f..dd43fa40c86c 100644
--- a/Libraries/Network/XMLHttpRequest.js
+++ b/Libraries/Network/XMLHttpRequest.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule XMLHttpRequest
  * @flow
  */
 'use strict';
diff --git a/Libraries/Network/convertRequestBody.js b/Libraries/Network/convertRequestBody.js
index 2d3ecc7353aa..84cc9c569078 100644
--- a/Libraries/Network/convertRequestBody.js
+++ b/Libraries/Network/convertRequestBody.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule convertRequestBody
  * @flow
  * @format
  */
diff --git a/Libraries/Network/fetch.js b/Libraries/Network/fetch.js
index 1e1c934316d6..10be3631d26b 100644
--- a/Libraries/Network/fetch.js
+++ b/Libraries/Network/fetch.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule fetch
  *
  */
 
diff --git a/Libraries/Performance/QuickPerformanceLogger.js b/Libraries/Performance/QuickPerformanceLogger.js
index 4eec7220a7cc..bdf6d952e1e8 100644
--- a/Libraries/Performance/QuickPerformanceLogger.js
+++ b/Libraries/Performance/QuickPerformanceLogger.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule QuickPerformanceLogger
  * @flow
  */
 
diff --git a/Libraries/Performance/SamplingProfiler.js b/Libraries/Performance/SamplingProfiler.js
index 739274399bde..ec4323e12575 100644
--- a/Libraries/Performance/SamplingProfiler.js
+++ b/Libraries/Performance/SamplingProfiler.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SamplingProfiler
  * @flow
  */
 'use strict';
diff --git a/Libraries/Performance/Systrace.js b/Libraries/Performance/Systrace.js
index 2e38d8298d1e..19105ad30397 100644
--- a/Libraries/Performance/Systrace.js
+++ b/Libraries/Performance/Systrace.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Systrace
  * @flow
  * @format
  */
diff --git a/Libraries/PermissionsAndroid/PermissionsAndroid.js b/Libraries/PermissionsAndroid/PermissionsAndroid.js
index 18858e1669db..6febce80ffd1 100644
--- a/Libraries/PermissionsAndroid/PermissionsAndroid.js
+++ b/Libraries/PermissionsAndroid/PermissionsAndroid.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PermissionsAndroid
  * @flow
  */
 'use strict';
diff --git a/Libraries/Promise.js b/Libraries/Promise.js
index 288ee75f6f0f..aee5ad7e7d0c 100644
--- a/Libraries/Promise.js
+++ b/Libraries/Promise.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Promise
  * @flow
  */
 'use strict';
diff --git a/Libraries/PushNotificationIOS/PushNotificationIOS.js b/Libraries/PushNotificationIOS/PushNotificationIOS.js
index 955bdf8c1adc..9f013436c991 100644
--- a/Libraries/PushNotificationIOS/PushNotificationIOS.js
+++ b/Libraries/PushNotificationIOS/PushNotificationIOS.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PushNotificationIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/RCTTest/SnapshotViewIOS.android.js b/Libraries/RCTTest/SnapshotViewIOS.android.js
index ef8eb9d7bf67..ebd42dd5b18b 100644
--- a/Libraries/RCTTest/SnapshotViewIOS.android.js
+++ b/Libraries/RCTTest/SnapshotViewIOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SnapshotViewIOS
  */
 'use strict';
 
diff --git a/Libraries/RCTTest/SnapshotViewIOS.ios.js b/Libraries/RCTTest/SnapshotViewIOS.ios.js
index 494830cd4ff3..050ec5d633dd 100644
--- a/Libraries/RCTTest/SnapshotViewIOS.ios.js
+++ b/Libraries/RCTTest/SnapshotViewIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SnapshotViewIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/ReactNative/AppContainer.js b/Libraries/ReactNative/AppContainer.js
index cb1ea048e4ad..8cdbd6dec15c 100644
--- a/Libraries/ReactNative/AppContainer.js
+++ b/Libraries/ReactNative/AppContainer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AppContainer
  * @format
  * @flow
  */
diff --git a/Libraries/ReactNative/AppRegistry.js b/Libraries/ReactNative/AppRegistry.js
index efe8e5584f2f..a2fdf91e632d 100644
--- a/Libraries/ReactNative/AppRegistry.js
+++ b/Libraries/ReactNative/AppRegistry.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AppRegistry
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/FabricUIManager.js b/Libraries/ReactNative/FabricUIManager.js
index 602b5459101b..f1b06ede5c17 100644
--- a/Libraries/ReactNative/FabricUIManager.js
+++ b/Libraries/ReactNative/FabricUIManager.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule FabricUIManager
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/I18nManager.js b/Libraries/ReactNative/I18nManager.js
index a8a256d515f4..5212d1100dac 100644
--- a/Libraries/ReactNative/I18nManager.js
+++ b/Libraries/ReactNative/I18nManager.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule I18nManager
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/ReactFabricInternals.js b/Libraries/ReactNative/ReactFabricInternals.js
index 72f37a41232d..47855a8b7c0c 100644
--- a/Libraries/ReactNative/ReactFabricInternals.js
+++ b/Libraries/ReactNative/ReactFabricInternals.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactFabricInternals
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/UIManager.js b/Libraries/ReactNative/UIManager.js
index 946d2233c5f1..9f34734a731c 100644
--- a/Libraries/ReactNative/UIManager.js
+++ b/Libraries/ReactNative/UIManager.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule UIManager
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/UIManagerStatTracker.js b/Libraries/ReactNative/UIManagerStatTracker.js
index 31f0a83613ff..3e1a6afd0739 100644
--- a/Libraries/ReactNative/UIManagerStatTracker.js
+++ b/Libraries/ReactNative/UIManagerStatTracker.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule UIManagerStatTracker
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/YellowBox.js b/Libraries/ReactNative/YellowBox.js
index 8c3eb1f2cb71..aa5d9788ab9f 100644
--- a/Libraries/ReactNative/YellowBox.js
+++ b/Libraries/ReactNative/YellowBox.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule YellowBox
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/queryLayoutByID.js b/Libraries/ReactNative/queryLayoutByID.js
index d484405920d2..b4d001e04d98 100644
--- a/Libraries/ReactNative/queryLayoutByID.js
+++ b/Libraries/ReactNative/queryLayoutByID.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule queryLayoutByID
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/renderApplication.js b/Libraries/ReactNative/renderApplication.js
index 8abfed260402..42e9673dbc48 100644
--- a/Libraries/ReactNative/renderApplication.js
+++ b/Libraries/ReactNative/renderApplication.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule renderApplication
  * @format
  * @flow
  */
diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index 77141b1c049a..83a071c7066f 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule requireNativeComponent
  * @flow
  * @format
  */
diff --git a/Libraries/ReactNative/takeSnapshot.js b/Libraries/ReactNative/takeSnapshot.js
index 212e6338faca..5c9e248e5e4a 100644
--- a/Libraries/ReactNative/takeSnapshot.js
+++ b/Libraries/ReactNative/takeSnapshot.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule takeSnapshot
  * @format
  * @flow
  */
diff --git a/Libraries/ReactNative/verifyPropTypes.js b/Libraries/ReactNative/verifyPropTypes.js
index 7791899d298b..b7b04d013c23 100644
--- a/Libraries/ReactNative/verifyPropTypes.js
+++ b/Libraries/ReactNative/verifyPropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule verifyPropTypes
  * @flow
  * @format
  */
diff --git a/Libraries/Renderer/oss/ReactFabric-dev.js b/Libraries/Renderer/oss/ReactFabric-dev.js
index a24f4f6a50dd..0424315c8ed6 100644
--- a/Libraries/Renderer/oss/ReactFabric-dev.js
+++ b/Libraries/Renderer/oss/ReactFabric-dev.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactFabric-dev
  * @preventMunge
  */
 
diff --git a/Libraries/Renderer/oss/ReactFabric-prod.js b/Libraries/Renderer/oss/ReactFabric-prod.js
index 48099a5351cb..19ca0dde9e33 100644
--- a/Libraries/Renderer/oss/ReactFabric-prod.js
+++ b/Libraries/Renderer/oss/ReactFabric-prod.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactFabric-prod
  * @preventMunge
  */
 
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
index 9e14a0c266e9..21d9a6c1d543 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactNativeRenderer-dev
  * @preventMunge
  */
 
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
index 32b4729f3c96..f7eb9e09f0dc 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactNativeRenderer-prod
  * @preventMunge
  */
 
diff --git a/Libraries/Renderer/shims/NativeMethodsMixin.js b/Libraries/Renderer/shims/NativeMethodsMixin.js
index cd0e673b3bff..7acdf99bbd39 100644
--- a/Libraries/Renderer/shims/NativeMethodsMixin.js
+++ b/Libraries/Renderer/shims/NativeMethodsMixin.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NativeMethodsMixin
  * @flow
  */
 
diff --git a/Libraries/Renderer/shims/ReactDebugTool.js b/Libraries/Renderer/shims/ReactDebugTool.js
index e45af4fb0994..8ea7ba5c1433 100644
--- a/Libraries/Renderer/shims/ReactDebugTool.js
+++ b/Libraries/Renderer/shims/ReactDebugTool.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactDebugTool
  */
 
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactFabric.js b/Libraries/Renderer/shims/ReactFabric.js
index 4162ca62fef7..8dce288d28a7 100644
--- a/Libraries/Renderer/shims/ReactFabric.js
+++ b/Libraries/Renderer/shims/ReactFabric.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactFabric
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactNative.js b/Libraries/Renderer/shims/ReactNative.js
index a648cafbc30c..43c5002e05f5 100644
--- a/Libraries/Renderer/shims/ReactNative.js
+++ b/Libraries/Renderer/shims/ReactNative.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNative
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactNativeComponentTree.js b/Libraries/Renderer/shims/ReactNativeComponentTree.js
index 30ec5257f424..8e8ce6ae06c1 100644
--- a/Libraries/Renderer/shims/ReactNativeComponentTree.js
+++ b/Libraries/Renderer/shims/ReactNativeComponentTree.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNativeComponentTree
  * @flow
  */
 
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index bf9411973933..485ce162ecc6 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ReactNativeTypes
  */
 
 export type MeasureOnSuccessCallback = (
diff --git a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
index ffb0fa213f3b..c8ed940a8609 100644
--- a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
+++ b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNativeViewConfigRegistry
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactPerf.js b/Libraries/Renderer/shims/ReactPerf.js
index bb6777fff0b9..e94c87501c7d 100644
--- a/Libraries/Renderer/shims/ReactPerf.js
+++ b/Libraries/Renderer/shims/ReactPerf.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactPerf
  */
 
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactTypes.js b/Libraries/Renderer/shims/ReactTypes.js
index 689ed18bf952..747a6c07b6f3 100644
--- a/Libraries/Renderer/shims/ReactTypes.js
+++ b/Libraries/Renderer/shims/ReactTypes.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ReactTypes
  */
 
 export type ReactNode =
diff --git a/Libraries/Renderer/shims/createReactNativeComponentClass.js b/Libraries/Renderer/shims/createReactNativeComponentClass.js
index 1a050e8b3cf0..cacaedab88f2 100644
--- a/Libraries/Renderer/shims/createReactNativeComponentClass.js
+++ b/Libraries/Renderer/shims/createReactNativeComponentClass.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule createReactNativeComponentClass
  * @flow
  */
 
diff --git a/Libraries/Sample/Sample.android.js b/Libraries/Sample/Sample.android.js
index 1a66fb9bf575..dbb43949f6f6 100644
--- a/Libraries/Sample/Sample.android.js
+++ b/Libraries/Sample/Sample.android.js
@@ -1,7 +1,6 @@
 /**
  * Stub of Sample for Android.
  *
- * @providesModule Sample
  * @flow
  */
 'use strict';
diff --git a/Libraries/Sample/Sample.ios.js b/Libraries/Sample/Sample.ios.js
index fd94afe0a68e..ae51247cc635 100644
--- a/Libraries/Sample/Sample.ios.js
+++ b/Libraries/Sample/Sample.ios.js
@@ -1,5 +1,4 @@
 /**
- * @providesModule Sample
  * @flow
  */
 'use strict';
diff --git a/Libraries/Settings/Settings.android.js b/Libraries/Settings/Settings.android.js
index 946c4aa9cde2..220c04e8b159 100644
--- a/Libraries/Settings/Settings.android.js
+++ b/Libraries/Settings/Settings.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Settings
  * @flow
  */
 'use strict';
diff --git a/Libraries/Settings/Settings.ios.js b/Libraries/Settings/Settings.ios.js
index 08f1be6a1c8a..46f0a8bebdd7 100644
--- a/Libraries/Settings/Settings.ios.js
+++ b/Libraries/Settings/Settings.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Settings
  * @flow
  */
 'use strict';
diff --git a/Libraries/Share/Share.js b/Libraries/Share/Share.js
index e41b29db8e54..b6066c11da54 100644
--- a/Libraries/Share/Share.js
+++ b/Libraries/Share/Share.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Share
  * @flow
  */
 'use strict';
diff --git a/Libraries/Storage/AsyncStorage.js b/Libraries/Storage/AsyncStorage.js
index 4e262e6150c3..f953aecbce26 100644
--- a/Libraries/Storage/AsyncStorage.js
+++ b/Libraries/Storage/AsyncStorage.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AsyncStorage
  * @noflow
  * @flow-weak
  * @jsdoc
diff --git a/Libraries/StyleSheet/ColorPropType.js b/Libraries/StyleSheet/ColorPropType.js
index 60e362275bfb..28bc93f45fa9 100644
--- a/Libraries/StyleSheet/ColorPropType.js
+++ b/Libraries/StyleSheet/ColorPropType.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ColorPropType
  */
 'use strict';
 
diff --git a/Libraries/StyleSheet/EdgeInsetsPropType.js b/Libraries/StyleSheet/EdgeInsetsPropType.js
index 307c6be2e5da..0bab3a58e65a 100644
--- a/Libraries/StyleSheet/EdgeInsetsPropType.js
+++ b/Libraries/StyleSheet/EdgeInsetsPropType.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule EdgeInsetsPropType
  * @flow
  */
 'use strict';
diff --git a/Libraries/StyleSheet/LayoutPropTypes.js b/Libraries/StyleSheet/LayoutPropTypes.js
index 02ec8733f6bb..6ff1844c7fac 100644
--- a/Libraries/StyleSheet/LayoutPropTypes.js
+++ b/Libraries/StyleSheet/LayoutPropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule LayoutPropTypes
  * @flow
  */
 'use strict';
diff --git a/Libraries/StyleSheet/PointPropType.js b/Libraries/StyleSheet/PointPropType.js
index a55628adbee7..44efc2d5fc40 100644
--- a/Libraries/StyleSheet/PointPropType.js
+++ b/Libraries/StyleSheet/PointPropType.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PointPropType
  * @flow
  */
 'use strict';
diff --git a/Libraries/StyleSheet/StyleSheet.js b/Libraries/StyleSheet/StyleSheet.js
index 5aab99d15762..4384ce9dbfc0 100644
--- a/Libraries/StyleSheet/StyleSheet.js
+++ b/Libraries/StyleSheet/StyleSheet.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StyleSheet
  * @flow
  * @format
  */
diff --git a/Libraries/StyleSheet/StyleSheetPropType.js b/Libraries/StyleSheet/StyleSheetPropType.js
index ac779f915393..9fed3d207a63 100644
--- a/Libraries/StyleSheet/StyleSheetPropType.js
+++ b/Libraries/StyleSheet/StyleSheetPropType.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StyleSheetPropType
  * @flow
  */
 'use strict';
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index 1134c252deeb..321bdc86922d 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StyleSheetTypes
  * @flow
  * @format
  */
diff --git a/Libraries/StyleSheet/StyleSheetValidation.js b/Libraries/StyleSheet/StyleSheetValidation.js
index 3e1af7bc1dd2..ae6c843de4f7 100644
--- a/Libraries/StyleSheet/StyleSheetValidation.js
+++ b/Libraries/StyleSheet/StyleSheetValidation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule StyleSheetValidation
  * @flow
  */
 'use strict';
diff --git a/Libraries/StyleSheet/TransformPropTypes.js b/Libraries/StyleSheet/TransformPropTypes.js
index bd1f3d352e11..13a58fdd7ff8 100644
--- a/Libraries/StyleSheet/TransformPropTypes.js
+++ b/Libraries/StyleSheet/TransformPropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TransformPropTypes
  * @flow
  */
 'use strict';
diff --git a/Libraries/StyleSheet/flattenStyle.js b/Libraries/StyleSheet/flattenStyle.js
index 176f5492a7e7..f62e35ea70f4 100644
--- a/Libraries/StyleSheet/flattenStyle.js
+++ b/Libraries/StyleSheet/flattenStyle.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule flattenStyle
  * @flow
  * @format
  */
diff --git a/Libraries/StyleSheet/processColor.js b/Libraries/StyleSheet/processColor.js
index 7d3a802bbbe3..dba665255110 100644
--- a/Libraries/StyleSheet/processColor.js
+++ b/Libraries/StyleSheet/processColor.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule processColor
  * @flow
  */
 'use strict';
diff --git a/Libraries/StyleSheet/processTransform.js b/Libraries/StyleSheet/processTransform.js
index 09cc7ca95d18..3c8d30ea0e0e 100644
--- a/Libraries/StyleSheet/processTransform.js
+++ b/Libraries/StyleSheet/processTransform.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule processTransform
  * @flow
  */
 'use strict';
diff --git a/Libraries/StyleSheet/setNormalizedColorAlpha.js b/Libraries/StyleSheet/setNormalizedColorAlpha.js
index 309d86cea12e..83a0873e577f 100644
--- a/Libraries/StyleSheet/setNormalizedColorAlpha.js
+++ b/Libraries/StyleSheet/setNormalizedColorAlpha.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule setNormalizedColorAlpha
  * @flow
  */
 /* eslint no-bitwise: 0 */
diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index 83b02877b883..d6fd56fcc62e 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Text
  * @flow
  * @format
  */
diff --git a/Libraries/Text/TextPropTypes.js b/Libraries/Text/TextPropTypes.js
index 81a7af03f605..5a3c99d73785 100644
--- a/Libraries/Text/TextPropTypes.js
+++ b/Libraries/Text/TextPropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TextPropTypes
  * @flow
  * @format
  */
diff --git a/Libraries/Text/TextProps.js b/Libraries/Text/TextProps.js
index effc8b05480b..56229632a01b 100644
--- a/Libraries/Text/TextProps.js
+++ b/Libraries/Text/TextProps.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TextProps
  * @flow
  * @format
  */
diff --git a/Libraries/Text/TextStylePropTypes.js b/Libraries/Text/TextStylePropTypes.js
index 872497ecf2ee..532f2e3d3ede 100644
--- a/Libraries/Text/TextStylePropTypes.js
+++ b/Libraries/Text/TextStylePropTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TextStylePropTypes
  * @flow
  */
 'use strict';
diff --git a/Libraries/Text/TextUpdateTest.js b/Libraries/Text/TextUpdateTest.js
index ec81ddab1c79..18a3ac5084b7 100644
--- a/Libraries/Text/TextUpdateTest.js
+++ b/Libraries/Text/TextUpdateTest.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TextUpdateTest
  * @flow
  */
 'use strict';
diff --git a/Libraries/Types/CoreEventTypes.js b/Libraries/Types/CoreEventTypes.js
index 56d4eecf8c34..ede607f0c706 100644
--- a/Libraries/Types/CoreEventTypes.js
+++ b/Libraries/Types/CoreEventTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule CoreEventTypes
  * @flow
  * @format
  */
diff --git a/Libraries/UTFSequence.js b/Libraries/UTFSequence.js
index 9bff51555d55..f1e9e28e505e 100644
--- a/Libraries/UTFSequence.js
+++ b/Libraries/UTFSequence.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule UTFSequence
  * @flow
  * @format
  */
diff --git a/Libraries/Utilities/BackAndroid.js b/Libraries/Utilities/BackAndroid.js
index 4fc029341f4b..51a68a7671f8 100644
--- a/Libraries/Utilities/BackAndroid.js
+++ b/Libraries/Utilities/BackAndroid.js
@@ -7,7 +7,6 @@
  * BackAndroid has been moved to BackHandler.  This stub calls BackHandler methods
  * after generating a warning to remind users to move to the new BackHandler module.
  *
- * @providesModule BackAndroid
  */
 
 'use strict';
diff --git a/Libraries/Utilities/BackHandler.android.js b/Libraries/Utilities/BackHandler.android.js
index 8f34cfacd1c3..b2e3a74bc448 100644
--- a/Libraries/Utilities/BackHandler.android.js
+++ b/Libraries/Utilities/BackHandler.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BackHandler
  */
 
 'use strict';
diff --git a/Libraries/Utilities/BackHandler.ios.js b/Libraries/Utilities/BackHandler.ios.js
index 33c6a8c1d6aa..0c0d7d437870 100644
--- a/Libraries/Utilities/BackHandler.ios.js
+++ b/Libraries/Utilities/BackHandler.ios.js
@@ -7,7 +7,6 @@
  * On Apple TV, this implements back navigation using the TV remote's menu button.
  * On iOS, this just implements a stub.
  *
- * @providesModule BackHandler
  */
 
 'use strict';
diff --git a/Libraries/Utilities/DeviceInfo.js b/Libraries/Utilities/DeviceInfo.js
index 8503ac75ca31..427ed495232d 100644
--- a/Libraries/Utilities/DeviceInfo.js
+++ b/Libraries/Utilities/DeviceInfo.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DeviceInfo
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/Dimensions.js b/Libraries/Utilities/Dimensions.js
index d13b14f1bd18..f27ecc0976b8 100644
--- a/Libraries/Utilities/Dimensions.js
+++ b/Libraries/Utilities/Dimensions.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Dimensions
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/HMRClient.js b/Libraries/Utilities/HMRClient.js
index ff897afda8bf..77169a2efcb5 100644
--- a/Libraries/Utilities/HMRClient.js
+++ b/Libraries/Utilities/HMRClient.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule HMRClient
  * @format
  * @flow
  */
diff --git a/Libraries/Utilities/HMRLoadingView.android.js b/Libraries/Utilities/HMRLoadingView.android.js
index ebda3ee65c81..f4c0c5c73122 100644
--- a/Libraries/Utilities/HMRLoadingView.android.js
+++ b/Libraries/Utilities/HMRLoadingView.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule HMRLoadingView
  * @flow
  */
 
diff --git a/Libraries/Utilities/HMRLoadingView.ios.js b/Libraries/Utilities/HMRLoadingView.ios.js
index 7100164d4ca6..4e9ad8fbf93f 100644
--- a/Libraries/Utilities/HMRLoadingView.ios.js
+++ b/Libraries/Utilities/HMRLoadingView.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule HMRLoadingView
  * @flow
  */
 
diff --git a/Libraries/Utilities/HeapCapture.js b/Libraries/Utilities/HeapCapture.js
index 49e9d678e1ee..519a2e94370b 100644
--- a/Libraries/Utilities/HeapCapture.js
+++ b/Libraries/Utilities/HeapCapture.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule HeapCapture
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/JSDevSupportModule.js b/Libraries/Utilities/JSDevSupportModule.js
index dc45030bf3b5..c25123284613 100644
--- a/Libraries/Utilities/JSDevSupportModule.js
+++ b/Libraries/Utilities/JSDevSupportModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule JSDevSupportModule
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/MatrixMath.js b/Libraries/Utilities/MatrixMath.js
index b36b316833fc..be329c2e645d 100755
--- a/Libraries/Utilities/MatrixMath.js
+++ b/Libraries/Utilities/MatrixMath.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule MatrixMath
  * @noflow
  */
 /* eslint-disable space-infix-ops */
diff --git a/Libraries/Utilities/PerformanceLogger.js b/Libraries/Utilities/PerformanceLogger.js
index 95b5f4924e89..aa4633fceb9c 100644
--- a/Libraries/Utilities/PerformanceLogger.js
+++ b/Libraries/Utilities/PerformanceLogger.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PerformanceLogger
  * @flow
  * @format
  */
diff --git a/Libraries/Utilities/PixelRatio.js b/Libraries/Utilities/PixelRatio.js
index bd8a6a0b9571..5f52bdc0f5b8 100644
--- a/Libraries/Utilities/PixelRatio.js
+++ b/Libraries/Utilities/PixelRatio.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PixelRatio
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/Platform.android.js b/Libraries/Utilities/Platform.android.js
index f0e80633f2f2..56b0d2494478 100644
--- a/Libraries/Utilities/Platform.android.js
+++ b/Libraries/Utilities/Platform.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Platform
  * @flow
  */
 
diff --git a/Libraries/Utilities/Platform.ios.js b/Libraries/Utilities/Platform.ios.js
index 776880b7fa40..9780ec75d274 100644
--- a/Libraries/Utilities/Platform.ios.js
+++ b/Libraries/Utilities/Platform.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Platform
  * @flow
  */
 
diff --git a/Libraries/Utilities/PlatformOS.android.js b/Libraries/Utilities/PlatformOS.android.js
index ff2a383759c4..d2183c41682c 100644
--- a/Libraries/Utilities/PlatformOS.android.js
+++ b/Libraries/Utilities/PlatformOS.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PlatformOS
  * @flow
  */
 
diff --git a/Libraries/Utilities/PlatformOS.ios.js b/Libraries/Utilities/PlatformOS.ios.js
index 11fed5978096..95b275712a08 100644
--- a/Libraries/Utilities/PlatformOS.ios.js
+++ b/Libraries/Utilities/PlatformOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PlatformOS
  * @flow
  */
 
diff --git a/Libraries/Utilities/PolyfillFunctions.js b/Libraries/Utilities/PolyfillFunctions.js
index 5bf31ee118b4..28cb44d5402b 100644
--- a/Libraries/Utilities/PolyfillFunctions.js
+++ b/Libraries/Utilities/PolyfillFunctions.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PolyfillFunctions
  * @flow
  * @format
  */
diff --git a/Libraries/Utilities/RCTLog.js b/Libraries/Utilities/RCTLog.js
index 2514d9b4039d..7259b79761f7 100644
--- a/Libraries/Utilities/RCTLog.js
+++ b/Libraries/Utilities/RCTLog.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RCTLog
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/SceneTracker.js b/Libraries/Utilities/SceneTracker.js
index 9cebe76a99d5..ae41ec03e08b 100644
--- a/Libraries/Utilities/SceneTracker.js
+++ b/Libraries/Utilities/SceneTracker.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SceneTracker
  * @flow
  */
 
diff --git a/Libraries/Utilities/binaryToBase64.js b/Libraries/Utilities/binaryToBase64.js
index d17c4d403c87..74a01a0bcad4 100644
--- a/Libraries/Utilities/binaryToBase64.js
+++ b/Libraries/Utilities/binaryToBase64.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule binaryToBase64
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/buildStyleInterpolator.js b/Libraries/Utilities/buildStyleInterpolator.js
index ec1744411739..a22526e45cf3 100644
--- a/Libraries/Utilities/buildStyleInterpolator.js
+++ b/Libraries/Utilities/buildStyleInterpolator.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule buildStyleInterpolator
  */
 
 'use strict';
diff --git a/Libraries/Utilities/clamp.js b/Libraries/Utilities/clamp.js
index 5d15d8b3b12f..dcfc93d855dd 100644
--- a/Libraries/Utilities/clamp.js
+++ b/Libraries/Utilities/clamp.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule clamp
  * @typechecks
  */
 'use strict';
diff --git a/Libraries/Utilities/createStrictShapeTypeChecker.js b/Libraries/Utilities/createStrictShapeTypeChecker.js
index 89347d15e0b8..5cde7eb53157 100644
--- a/Libraries/Utilities/createStrictShapeTypeChecker.js
+++ b/Libraries/Utilities/createStrictShapeTypeChecker.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule createStrictShapeTypeChecker
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js b/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
index 19cb60a9c56d..041691a67f7a 100644
--- a/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
+++ b/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule deepFreezeAndThrowOnMutationInDev
  * @flow
  */
 
diff --git a/Libraries/Utilities/defineLazyObjectProperty.js b/Libraries/Utilities/defineLazyObjectProperty.js
index 87e893037913..cd01de5c2709 100644
--- a/Libraries/Utilities/defineLazyObjectProperty.js
+++ b/Libraries/Utilities/defineLazyObjectProperty.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule defineLazyObjectProperty
  * @flow
  */
 
diff --git a/Libraries/Utilities/deprecatedPropType.js b/Libraries/Utilities/deprecatedPropType.js
index 8b08854fabb0..398410545ed8 100644
--- a/Libraries/Utilities/deprecatedPropType.js
+++ b/Libraries/Utilities/deprecatedPropType.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule deprecatedPropType
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/differ/deepDiffer.js b/Libraries/Utilities/differ/deepDiffer.js
index af0bd295694b..700733f51f6b 100644
--- a/Libraries/Utilities/differ/deepDiffer.js
+++ b/Libraries/Utilities/differ/deepDiffer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule deepDiffer
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/differ/insetsDiffer.js b/Libraries/Utilities/differ/insetsDiffer.js
index 1d497c0948e5..7214ab6d7638 100644
--- a/Libraries/Utilities/differ/insetsDiffer.js
+++ b/Libraries/Utilities/differ/insetsDiffer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule insetsDiffer
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/differ/matricesDiffer.js b/Libraries/Utilities/differ/matricesDiffer.js
index 25e741a4ff82..177a7a110ac4 100644
--- a/Libraries/Utilities/differ/matricesDiffer.js
+++ b/Libraries/Utilities/differ/matricesDiffer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule matricesDiffer
  */
 'use strict';
 
diff --git a/Libraries/Utilities/differ/pointsDiffer.js b/Libraries/Utilities/differ/pointsDiffer.js
index cb41cec85494..e019124e76d1 100644
--- a/Libraries/Utilities/differ/pointsDiffer.js
+++ b/Libraries/Utilities/differ/pointsDiffer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule pointsDiffer
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/differ/sizesDiffer.js b/Libraries/Utilities/differ/sizesDiffer.js
index 55ea66ded36c..c4e104a1439b 100644
--- a/Libraries/Utilities/differ/sizesDiffer.js
+++ b/Libraries/Utilities/differ/sizesDiffer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule sizesDiffer
  */
 'use strict';
 
diff --git a/Libraries/Utilities/dismissKeyboard.js b/Libraries/Utilities/dismissKeyboard.js
index febcc82bfa9a..a5b9e2f00dd9 100644
--- a/Libraries/Utilities/dismissKeyboard.js
+++ b/Libraries/Utilities/dismissKeyboard.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule dismissKeyboard
  *
  * This function dismisses the currently-open keyboard, if any
  */
diff --git a/Libraries/Utilities/groupByEveryN.js b/Libraries/Utilities/groupByEveryN.js
index ea4003922912..2cda280be6f1 100644
--- a/Libraries/Utilities/groupByEveryN.js
+++ b/Libraries/Utilities/groupByEveryN.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule groupByEveryN
  * @flow
  */
 
diff --git a/Libraries/Utilities/infoLog.js b/Libraries/Utilities/infoLog.js
index 66278f520e84..9437179b163d 100644
--- a/Libraries/Utilities/infoLog.js
+++ b/Libraries/Utilities/infoLog.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule infoLog
  */
 'use strict';
 
diff --git a/Libraries/Utilities/logError.js b/Libraries/Utilities/logError.js
index 6cf212b1f147..5482448ae20b 100644
--- a/Libraries/Utilities/logError.js
+++ b/Libraries/Utilities/logError.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule logError
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/mapWithSeparator.js b/Libraries/Utilities/mapWithSeparator.js
index 0beceda0174c..09fe19cec897 100644
--- a/Libraries/Utilities/mapWithSeparator.js
+++ b/Libraries/Utilities/mapWithSeparator.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule mapWithSeparator
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/mergeFast.js b/Libraries/Utilities/mergeFast.js
index 60ad36c20464..42e357e5dbda 100644
--- a/Libraries/Utilities/mergeFast.js
+++ b/Libraries/Utilities/mergeFast.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule mergeFast
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/mergeIntoFast.js b/Libraries/Utilities/mergeIntoFast.js
index ff048311403a..e657de7c3d9d 100644
--- a/Libraries/Utilities/mergeIntoFast.js
+++ b/Libraries/Utilities/mergeIntoFast.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule mergeIntoFast
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/stringifySafe.js b/Libraries/Utilities/stringifySafe.js
index 39ada6227142..f8f7ab8f0e40 100644
--- a/Libraries/Utilities/stringifySafe.js
+++ b/Libraries/Utilities/stringifySafe.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule stringifySafe
  * @flow
  */
 'use strict';
diff --git a/Libraries/Utilities/truncate.js b/Libraries/Utilities/truncate.js
index 0e0d8c643ea5..5b89e8ff2007 100644
--- a/Libraries/Utilities/truncate.js
+++ b/Libraries/Utilities/truncate.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule truncate
  * @flow
  */
 'use strict';
diff --git a/Libraries/Vibration/Vibration.js b/Libraries/Vibration/Vibration.js
index 7f10cda29f8f..c0ee75203fcd 100644
--- a/Libraries/Vibration/Vibration.js
+++ b/Libraries/Vibration/Vibration.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Vibration
  * @flow
  * @jsdoc
  */
diff --git a/Libraries/Vibration/VibrationIOS.android.js b/Libraries/Vibration/VibrationIOS.android.js
index 0b2279b696cc..b57279a73844 100644
--- a/Libraries/Vibration/VibrationIOS.android.js
+++ b/Libraries/Vibration/VibrationIOS.android.js
@@ -6,7 +6,6 @@
  *
  * Stub of VibrationIOS for Android.
  *
- * @providesModule VibrationIOS
  */
 'use strict';
 
diff --git a/Libraries/Vibration/VibrationIOS.ios.js b/Libraries/Vibration/VibrationIOS.ios.js
index ec55640442f6..5ce5f4019bb5 100644
--- a/Libraries/Vibration/VibrationIOS.ios.js
+++ b/Libraries/Vibration/VibrationIOS.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule VibrationIOS
  * @flow
  */
 'use strict';
diff --git a/Libraries/WebSocket/WebSocket.js b/Libraries/WebSocket/WebSocket.js
index 1b401d236c28..ef28c6ce464d 100644
--- a/Libraries/WebSocket/WebSocket.js
+++ b/Libraries/WebSocket/WebSocket.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule WebSocket
  * @flow
  */
 'use strict';
diff --git a/Libraries/WebSocket/WebSocketEvent.js b/Libraries/WebSocket/WebSocketEvent.js
index 93133902a94a..b72188d34b8c 100644
--- a/Libraries/WebSocket/WebSocketEvent.js
+++ b/Libraries/WebSocket/WebSocketEvent.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule WebSocketEvent
  */
 
 'use strict';
diff --git a/Libraries/WebSocket/WebSocketInterceptor.js b/Libraries/WebSocket/WebSocketInterceptor.js
index 10251dfa1a20..0ab63cf662a9 100644
--- a/Libraries/WebSocket/WebSocketInterceptor.js
+++ b/Libraries/WebSocket/WebSocketInterceptor.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule WebSocketInterceptor
  */
  'use strict';
 
diff --git a/Libraries/polyfills/Array.es6.js b/Libraries/polyfills/Array.es6.js
index 0075d7ae1e07..252d996b919f 100644
--- a/Libraries/polyfills/Array.es6.js
+++ b/Libraries/polyfills/Array.es6.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Array.es6
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/polyfills/Array.prototype.es6.js b/Libraries/polyfills/Array.prototype.es6.js
index 2bf044144eb7..a3c8da5415fa 100644
--- a/Libraries/polyfills/Array.prototype.es6.js
+++ b/Libraries/polyfills/Array.prototype.es6.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Array.prototype.es6
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/polyfills/Number.es6.js b/Libraries/polyfills/Number.es6.js
index ef7d4ac88e4f..b95166205be6 100644
--- a/Libraries/polyfills/Number.es6.js
+++ b/Libraries/polyfills/Number.es6.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Number.es6
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/polyfills/Object.es6.js b/Libraries/polyfills/Object.es6.js
index 0aa884e8be95..3d521e0a630d 100644
--- a/Libraries/polyfills/Object.es6.js
+++ b/Libraries/polyfills/Object.es6.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Object.es6
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/polyfills/Object.es7.js b/Libraries/polyfills/Object.es7.js
index 294756b11c36..a891057b9e7b 100644
--- a/Libraries/polyfills/Object.es7.js
+++ b/Libraries/polyfills/Object.es7.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Object.es7
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/polyfills/String.prototype.es6.js b/Libraries/polyfills/String.prototype.es6.js
index b3bd95be6b88..02b33dd1e199 100644
--- a/Libraries/polyfills/String.prototype.es6.js
+++ b/Libraries/polyfills/String.prototype.es6.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule String.prototype.es6
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/polyfills/babelHelpers.js b/Libraries/polyfills/babelHelpers.js
index 7d251ea34748..11123e0f3bc0 100644
--- a/Libraries/polyfills/babelHelpers.js
+++ b/Libraries/polyfills/babelHelpers.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule babelHelpers
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/polyfills/console.js b/Libraries/polyfills/console.js
index 794a89c4f49f..47970958a066 100644
--- a/Libraries/polyfills/console.js
+++ b/Libraries/polyfills/console.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule console
  * @polyfill
  * @nolint
  * @format
diff --git a/Libraries/polyfills/error-guard.js b/Libraries/polyfills/error-guard.js
index 632e7e0e4f02..17181d102192 100644
--- a/Libraries/polyfills/error-guard.js
+++ b/Libraries/polyfills/error-guard.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule error-guard
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/promiseRejectionIsError.js b/Libraries/promiseRejectionIsError.js
index ce3ee915cff4..672949116911 100644
--- a/Libraries/promiseRejectionIsError.js
+++ b/Libraries/promiseRejectionIsError.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule promiseRejectionIsError
  * @flow
  */
 'use strict';
diff --git a/Libraries/react-native/React.js b/Libraries/react-native/React.js
index f000f1403b5d..ff4c2454459f 100644
--- a/Libraries/react-native/React.js
+++ b/Libraries/react-native/React.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule React
  */
 
 'use strict';
diff --git a/Libraries/react-native/react-native-implementation.js b/Libraries/react-native/react-native-implementation.js
index e3b19adc459c..5a6f9759e8ce 100644
--- a/Libraries/react-native/react-native-implementation.js
+++ b/Libraries/react-native/react-native-implementation.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule react-native-implementation
  * @flow
  */
 'use strict';
diff --git a/Libraries/react-native/react-native-interface.js b/Libraries/react-native/react-native-interface.js
index fd4ad545c31b..5f2cdf2c1cf6 100644
--- a/Libraries/react-native/react-native-interface.js
+++ b/Libraries/react-native/react-native-interface.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule react-native-interface
  */
 'use strict';
 
diff --git a/Libraries/vendor/core/ErrorUtils.js b/Libraries/vendor/core/ErrorUtils.js
index 8b36c611105d..2fb0272d347a 100644
--- a/Libraries/vendor/core/ErrorUtils.js
+++ b/Libraries/vendor/core/ErrorUtils.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ErrorUtils
  * @flow
  */
 
diff --git a/Libraries/vendor/core/Map.js b/Libraries/vendor/core/Map.js
index e9e687a15ce9..115e2f855eaf 100644
--- a/Libraries/vendor/core/Map.js
+++ b/Libraries/vendor/core/Map.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Map
  * @preventMunge
  * @typechecks
  */
diff --git a/Libraries/vendor/core/Set.js b/Libraries/vendor/core/Set.js
index b43313205ef7..16e3cecae21f 100644
--- a/Libraries/vendor/core/Set.js
+++ b/Libraries/vendor/core/Set.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Set
  * @preventMunge
  * @typechecks
  */
diff --git a/Libraries/vendor/core/_shouldPolyfillES6Collection.js b/Libraries/vendor/core/_shouldPolyfillES6Collection.js
index e3f77b169dec..84ed51ded55e 100644
--- a/Libraries/vendor/core/_shouldPolyfillES6Collection.js
+++ b/Libraries/vendor/core/_shouldPolyfillES6Collection.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule _shouldPolyfillES6Collection
  * @preventMunge
  * @flow
  */
diff --git a/Libraries/vendor/core/getObjectValues.js b/Libraries/vendor/core/getObjectValues.js
index aac327c2eaed..398788c1e02f 100644
--- a/Libraries/vendor/core/getObjectValues.js
+++ b/Libraries/vendor/core/getObjectValues.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule getObjectValues
  * @typechecks
  */
 'use strict';
diff --git a/Libraries/vendor/core/guid.js b/Libraries/vendor/core/guid.js
index 74c97cf383de..b6195ef6b691 100644
--- a/Libraries/vendor/core/guid.js
+++ b/Libraries/vendor/core/guid.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule guid
  */
 
 /* eslint-disable no-bitwise */
diff --git a/Libraries/vendor/core/isEmpty.js b/Libraries/vendor/core/isEmpty.js
index 1f55d4519ff3..6d451729c7c8 100644
--- a/Libraries/vendor/core/isEmpty.js
+++ b/Libraries/vendor/core/isEmpty.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule isEmpty
  */
 'use strict';
 
diff --git a/Libraries/vendor/core/merge.js b/Libraries/vendor/core/merge.js
index 800c08c1be26..6963eddd5628 100644
--- a/Libraries/vendor/core/merge.js
+++ b/Libraries/vendor/core/merge.js
@@ -1,5 +1,5 @@
 /**
- * @generated SignedSource<<0e3063b19e14ed191102b1dffe45551f>>
+ * @generated SignedSource<<148d1974f94f5c9597e86f946bdf0d4e>>
  *
  * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
  * !! This file is a check-in of a static_upstream project!      !!
@@ -26,7 +26,6 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  *
- * @providesModule merge
  */
 
 "use strict";
diff --git a/Libraries/vendor/core/mergeHelpers.js b/Libraries/vendor/core/mergeHelpers.js
index 4eb2d9d2aec8..e24559ddb50c 100644
--- a/Libraries/vendor/core/mergeHelpers.js
+++ b/Libraries/vendor/core/mergeHelpers.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule mergeHelpers
  *
  * requiresPolyfills: Array.isArray
  */
diff --git a/Libraries/vendor/core/mergeInto.js b/Libraries/vendor/core/mergeInto.js
index 0da86a50cdb4..d42b3dcf36ed 100644
--- a/Libraries/vendor/core/mergeInto.js
+++ b/Libraries/vendor/core/mergeInto.js
@@ -1,5 +1,5 @@
 /**
- * @generated SignedSource<<d3caa35be27b17ea4dd4c76bef72d1ab>>
+ * @generated SignedSource<<f2a1f14b3c1d2b563e2a0619ef427c6d>>
  *
  * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
  * !! This file is a check-in of a static_upstream project!      !!
@@ -26,7 +26,6 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  *
- * @providesModule mergeInto
  * @typechecks static-only
  */
 
diff --git a/Libraries/vendor/core/toIterator.js b/Libraries/vendor/core/toIterator.js
index b396c469c03f..cabd1e2b0667 100644
--- a/Libraries/vendor/core/toIterator.js
+++ b/Libraries/vendor/core/toIterator.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule toIterator
  */
 'use strict';
 
diff --git a/Libraries/vendor/document/selection/DocumentSelectionState.js b/Libraries/vendor/document/selection/DocumentSelectionState.js
index a702582c6965..28b93e343906 100644
--- a/Libraries/vendor/document/selection/DocumentSelectionState.js
+++ b/Libraries/vendor/document/selection/DocumentSelectionState.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DocumentSelectionState
  * @typechecks
  */
 
diff --git a/Libraries/vendor/emitter/EmitterSubscription.js b/Libraries/vendor/emitter/EmitterSubscription.js
index e352e71675c9..844c28e386c8 100644
--- a/Libraries/vendor/emitter/EmitterSubscription.js
+++ b/Libraries/vendor/emitter/EmitterSubscription.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule EmitterSubscription
  * @flow
  */
 'use strict';
diff --git a/Libraries/vendor/emitter/EventEmitter.js b/Libraries/vendor/emitter/EventEmitter.js
index 4fdb10a05159..4b9307e49292 100644
--- a/Libraries/vendor/emitter/EventEmitter.js
+++ b/Libraries/vendor/emitter/EventEmitter.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule EventEmitter
  * @noflow
  * @typecheck
  */
diff --git a/Libraries/vendor/emitter/EventEmitterWithHolding.js b/Libraries/vendor/emitter/EventEmitterWithHolding.js
index 8c082222e8f7..a9f232a567a8 100644
--- a/Libraries/vendor/emitter/EventEmitterWithHolding.js
+++ b/Libraries/vendor/emitter/EventEmitterWithHolding.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule EventEmitterWithHolding
  * @flow
  */
 'use strict';
diff --git a/Libraries/vendor/emitter/EventHolder.js b/Libraries/vendor/emitter/EventHolder.js
index 3bb7062e020f..2faa43eb19a8 100644
--- a/Libraries/vendor/emitter/EventHolder.js
+++ b/Libraries/vendor/emitter/EventHolder.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule EventHolder
  * @flow
  */
 'use strict';
diff --git a/Libraries/vendor/emitter/EventSubscription.js b/Libraries/vendor/emitter/EventSubscription.js
index 82cb06fc4fd5..1d809c371d14 100644
--- a/Libraries/vendor/emitter/EventSubscription.js
+++ b/Libraries/vendor/emitter/EventSubscription.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule EventSubscription
  * @flow
  */
 'use strict';
diff --git a/Libraries/vendor/emitter/EventSubscriptionVendor.js b/Libraries/vendor/emitter/EventSubscriptionVendor.js
index aa2a4e76b90b..779952898c8b 100644
--- a/Libraries/vendor/emitter/EventSubscriptionVendor.js
+++ b/Libraries/vendor/emitter/EventSubscriptionVendor.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule EventSubscriptionVendor
  * @flow
  */
 'use strict';
diff --git a/Libraries/vendor/emitter/EventValidator.js b/Libraries/vendor/emitter/EventValidator.js
index 9930236776b2..16b469791037 100644
--- a/Libraries/vendor/emitter/EventValidator.js
+++ b/Libraries/vendor/emitter/EventValidator.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule EventValidator
  * @flow
  */
 'use strict';
diff --git a/Libraries/vendor/emitter/mixInEventEmitter.js b/Libraries/vendor/emitter/mixInEventEmitter.js
index 6ee08d6d31ac..5b23f891d883 100644
--- a/Libraries/vendor/emitter/mixInEventEmitter.js
+++ b/Libraries/vendor/emitter/mixInEventEmitter.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule mixInEventEmitter
  * @flow
  */
 'use strict';
diff --git a/RNTester/RNTesterUnitTests/RNTesterUnitTestsBundle.js b/RNTester/RNTesterUnitTests/RNTesterUnitTestsBundle.js
index f0a455ff3552..e6ff98a10ac1 100644
--- a/RNTester/RNTesterUnitTests/RNTesterUnitTestsBundle.js
+++ b/RNTester/RNTesterUnitTests/RNTesterUnitTestsBundle.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RNTesterUnitTestsBundle
  */
 'use strict';
 
diff --git a/RNTester/js/ARTExample.js b/RNTester/js/ARTExample.js
index 704a9c06bbdc..fb8d0378c862 100644
--- a/RNTester/js/ARTExample.js
+++ b/RNTester/js/ARTExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ARTExample
  */
 'use strict';
 
diff --git a/RNTester/js/AccessibilityAndroidExample.android.js b/RNTester/js/AccessibilityAndroidExample.android.js
index 54b087fa207f..6c6a80d416c0 100644
--- a/RNTester/js/AccessibilityAndroidExample.android.js
+++ b/RNTester/js/AccessibilityAndroidExample.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AccessibilityAndroidExample
  */
 'use strict';
 
diff --git a/RNTester/js/AccessibilityIOSExample.js b/RNTester/js/AccessibilityIOSExample.js
index 0deead7538d6..dabce101ce1e 100644
--- a/RNTester/js/AccessibilityIOSExample.js
+++ b/RNTester/js/AccessibilityIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule AccessibilityIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/ActionSheetIOSExample.js b/RNTester/js/ActionSheetIOSExample.js
index ac9d97378637..1b04190b253a 100644
--- a/RNTester/js/ActionSheetIOSExample.js
+++ b/RNTester/js/ActionSheetIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ActionSheetIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/ActivityIndicatorExample.js b/RNTester/js/ActivityIndicatorExample.js
index 692acd01c7d1..05c9e06d4060 100644
--- a/RNTester/js/ActivityIndicatorExample.js
+++ b/RNTester/js/ActivityIndicatorExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ActivityIndicatorExample
  */
 'use strict';
 
diff --git a/RNTester/js/AlertExample.js b/RNTester/js/AlertExample.js
index 93c82e4069c9..dee922a66abf 100644
--- a/RNTester/js/AlertExample.js
+++ b/RNTester/js/AlertExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AlertExample
  */
 
 'use strict';
diff --git a/RNTester/js/AlertIOSExample.js b/RNTester/js/AlertIOSExample.js
index b8b1cee43f85..8f4a898a5726 100644
--- a/RNTester/js/AlertIOSExample.js
+++ b/RNTester/js/AlertIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule AlertIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/AnimatedExample.js b/RNTester/js/AnimatedExample.js
index 8130a9d9f629..9e60a81cb105 100644
--- a/RNTester/js/AnimatedExample.js
+++ b/RNTester/js/AnimatedExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule AnimatedExample
  */
 'use strict';
 
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExApp.js b/RNTester/js/AnimatedGratuitousApp/AnExApp.js
index 1116a84ee982..c723f40f7e11 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExApp.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExApp.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnExApp
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExBobble.js b/RNTester/js/AnimatedGratuitousApp/AnExBobble.js
index d3f8885275eb..7f56bbe68e97 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExBobble.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExBobble.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnExBobble
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExChained.js b/RNTester/js/AnimatedGratuitousApp/AnExChained.js
index 63a83804ed34..00d72dafb12a 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExChained.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExChained.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnExChained
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExScroll.js b/RNTester/js/AnimatedGratuitousApp/AnExScroll.js
index b7f69425437f..c0f7495e4baa 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExScroll.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExScroll.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnExScroll
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExSet.js b/RNTester/js/AnimatedGratuitousApp/AnExSet.js
index a89fd2008a3f..873d5251c2eb 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExSet.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExSet.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnExSet
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExTilt.js b/RNTester/js/AnimatedGratuitousApp/AnExTilt.js
index a5678b686507..c7540de730eb 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExTilt.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExTilt.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AnExTilt
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/AppStateExample.js b/RNTester/js/AppStateExample.js
index 8088d77fc06f..f6b4265c84c3 100644
--- a/RNTester/js/AppStateExample.js
+++ b/RNTester/js/AppStateExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule AppStateExample
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/AssetScaledImageExample.js b/RNTester/js/AssetScaledImageExample.js
index b723d8f50ea5..51e97a8aee92 100644
--- a/RNTester/js/AssetScaledImageExample.js
+++ b/RNTester/js/AssetScaledImageExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule AssetScaledImageExample
  */
 'use strict';
 
diff --git a/RNTester/js/AsyncStorageExample.js b/RNTester/js/AsyncStorageExample.js
index 5e16a6b847c4..eb354b2db633 100644
--- a/RNTester/js/AsyncStorageExample.js
+++ b/RNTester/js/AsyncStorageExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule AsyncStorageExample
  */
 'use strict';
 
diff --git a/RNTester/js/BorderExample.js b/RNTester/js/BorderExample.js
index 8885537fb35b..6f64581dfbda 100644
--- a/RNTester/js/BorderExample.js
+++ b/RNTester/js/BorderExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BorderExample
  */
 'use strict';
 
diff --git a/RNTester/js/BoxShadowExample.js b/RNTester/js/BoxShadowExample.js
index bddce0490b3b..056b61aee33a 100644
--- a/RNTester/js/BoxShadowExample.js
+++ b/RNTester/js/BoxShadowExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule BoxShadowExample
  */
 'use strict';
 
diff --git a/RNTester/js/ButtonExample.js b/RNTester/js/ButtonExample.js
index 6c850a2121a7..8ba4876ed74e 100644
--- a/RNTester/js/ButtonExample.js
+++ b/RNTester/js/ButtonExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ButtonExample
  */
 'use strict';
 
diff --git a/RNTester/js/CameraRollExample.js b/RNTester/js/CameraRollExample.js
index 508980d47196..f289a2b61077 100644
--- a/RNTester/js/CameraRollExample.js
+++ b/RNTester/js/CameraRollExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule CameraRollExample
  * @format
  */
 'use strict';
diff --git a/RNTester/js/CameraRollView.js b/RNTester/js/CameraRollView.js
index c08aeb71e833..29eb070223a9 100644
--- a/RNTester/js/CameraRollView.js
+++ b/RNTester/js/CameraRollView.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule CameraRollView
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/CheckBoxExample.js b/RNTester/js/CheckBoxExample.js
index 98685fac4be7..1ef830cabd12 100644
--- a/RNTester/js/CheckBoxExample.js
+++ b/RNTester/js/CheckBoxExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule CheckBoxExample
  * @format
  */
 'use strict';
diff --git a/RNTester/js/ClipboardExample.js b/RNTester/js/ClipboardExample.js
index 8526cea43340..57ee1e172e73 100644
--- a/RNTester/js/ClipboardExample.js
+++ b/RNTester/js/ClipboardExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ClipboardExample
  */
 'use strict';
 
diff --git a/RNTester/js/DatePickerAndroidExample.js b/RNTester/js/DatePickerAndroidExample.js
index 926071b66d7a..2b6706e06be5 100644
--- a/RNTester/js/DatePickerAndroidExample.js
+++ b/RNTester/js/DatePickerAndroidExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DatePickerAndroidExample
  */
 'use strict';
 
diff --git a/RNTester/js/DatePickerIOSExample.js b/RNTester/js/DatePickerIOSExample.js
index b11e0644c20d..a0b6234e8225 100644
--- a/RNTester/js/DatePickerIOSExample.js
+++ b/RNTester/js/DatePickerIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule DatePickerIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/DimensionsExample.js b/RNTester/js/DimensionsExample.js
index 9611eedd482d..d0274f15a185 100644
--- a/RNTester/js/DimensionsExample.js
+++ b/RNTester/js/DimensionsExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DimensionsExample
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/ExampleTypes.js b/RNTester/js/ExampleTypes.js
index e747e43be9f9..4e42bf4cf3da 100644
--- a/RNTester/js/ExampleTypes.js
+++ b/RNTester/js/ExampleTypes.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ExampleTypes
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/FlatListExample.js b/RNTester/js/FlatListExample.js
index 9ec623fc86aa..0c47ebc69f68 100644
--- a/RNTester/js/FlatListExample.js
+++ b/RNTester/js/FlatListExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule FlatListExample
  */
 'use strict';
 
diff --git a/RNTester/js/GeolocationExample.js b/RNTester/js/GeolocationExample.js
index 1282673f0acb..2cbd091f50f5 100644
--- a/RNTester/js/GeolocationExample.js
+++ b/RNTester/js/GeolocationExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule GeolocationExample
  */
 'use strict';
 
diff --git a/RNTester/js/ImageCapInsetsExample.js b/RNTester/js/ImageCapInsetsExample.js
index 645d002b9be4..97b407f08e11 100644
--- a/RNTester/js/ImageCapInsetsExample.js
+++ b/RNTester/js/ImageCapInsetsExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ImageCapInsetsExample
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/ImageEditingExample.js b/RNTester/js/ImageEditingExample.js
index d9defa775f5a..76bf871273a4 100644
--- a/RNTester/js/ImageEditingExample.js
+++ b/RNTester/js/ImageEditingExample.js
@@ -5,5 +5,4 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ImageEditingExample
  */
diff --git a/RNTester/js/ImageExample.js b/RNTester/js/ImageExample.js
index 37f36b697de3..65c6380509b2 100644
--- a/RNTester/js/ImageExample.js
+++ b/RNTester/js/ImageExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ImageExample
  */
 'use strict';
 
diff --git a/RNTester/js/InputAccessoryViewExample.js b/RNTester/js/InputAccessoryViewExample.js
index 9287fb7e1e68..45b63e20d9f5 100644
--- a/RNTester/js/InputAccessoryViewExample.js
+++ b/RNTester/js/InputAccessoryViewExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InputAccessoryViewExample
  * @flow
  * @format
  */
diff --git a/RNTester/js/KeyboardAvoidingViewExample.js b/RNTester/js/KeyboardAvoidingViewExample.js
index 3b52f3accbb7..3c84590822d6 100644
--- a/RNTester/js/KeyboardAvoidingViewExample.js
+++ b/RNTester/js/KeyboardAvoidingViewExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule KeyboardAvoidingViewExample
  */
 'use strict';
 
diff --git a/RNTester/js/LayoutAnimationExample.js b/RNTester/js/LayoutAnimationExample.js
index d815712bba4f..a62143d2b04a 100644
--- a/RNTester/js/LayoutAnimationExample.js
+++ b/RNTester/js/LayoutAnimationExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule LayoutAnimationExample
  */
 'use strict';
 
diff --git a/RNTester/js/LayoutEventsExample.js b/RNTester/js/LayoutEventsExample.js
index 37b9811d8d40..b90bc27fd5ca 100644
--- a/RNTester/js/LayoutEventsExample.js
+++ b/RNTester/js/LayoutEventsExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule LayoutEventsExample
  */
 'use strict';
 
diff --git a/RNTester/js/LayoutExample.js b/RNTester/js/LayoutExample.js
index eec0faa433d2..b6edcaef7297 100644
--- a/RNTester/js/LayoutExample.js
+++ b/RNTester/js/LayoutExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule LayoutExample
  */
 'use strict';
 
diff --git a/RNTester/js/LinkingExample.js b/RNTester/js/LinkingExample.js
index 52297f07cf8e..4ee6a27421b6 100644
--- a/RNTester/js/LinkingExample.js
+++ b/RNTester/js/LinkingExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule LinkingExample
  */
 'use strict';
 
diff --git a/RNTester/js/ListExampleShared.js b/RNTester/js/ListExampleShared.js
index 75ef6bb4b65c..2aab97161657 100644
--- a/RNTester/js/ListExampleShared.js
+++ b/RNTester/js/ListExampleShared.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ListExampleShared
  */
 'use strict';
 
diff --git a/RNTester/js/ListViewExample.js b/RNTester/js/ListViewExample.js
index ee8284236187..ea1e07bafe5e 100644
--- a/RNTester/js/ListViewExample.js
+++ b/RNTester/js/ListViewExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ListViewExample
  */
 'use strict';
 
diff --git a/RNTester/js/ListViewGridLayoutExample.js b/RNTester/js/ListViewGridLayoutExample.js
index 636db62fccec..5f389596ea86 100644
--- a/RNTester/js/ListViewGridLayoutExample.js
+++ b/RNTester/js/ListViewGridLayoutExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ListViewGridLayoutExample
  */
 'use strict';
 
diff --git a/RNTester/js/ListViewPagingExample.js b/RNTester/js/ListViewPagingExample.js
index 3d68e7ec5468..88548ec0b985 100644
--- a/RNTester/js/ListViewPagingExample.js
+++ b/RNTester/js/ListViewPagingExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ListViewPagingExample
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/MaskedViewExample.js b/RNTester/js/MaskedViewExample.js
index cca734b53576..6548b7e49570 100644
--- a/RNTester/js/MaskedViewExample.js
+++ b/RNTester/js/MaskedViewExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule MaskedViewExample
  */
 'use strict';
 
diff --git a/RNTester/js/ModalExample.js b/RNTester/js/ModalExample.js
index 12093f4d8f4e..eba8a646cfc9 100644
--- a/RNTester/js/ModalExample.js
+++ b/RNTester/js/ModalExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ModalExample
  */
 'use strict';
 
diff --git a/RNTester/js/MultiColumnExample.js b/RNTester/js/MultiColumnExample.js
index cc323cfcdad8..52fdaa2721d4 100644
--- a/RNTester/js/MultiColumnExample.js
+++ b/RNTester/js/MultiColumnExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule MultiColumnExample
  */
 'use strict';
 
diff --git a/RNTester/js/NativeAnimationsExample.js b/RNTester/js/NativeAnimationsExample.js
index 5a6e5df55e84..52cb766c8aec 100644
--- a/RNTester/js/NativeAnimationsExample.js
+++ b/RNTester/js/NativeAnimationsExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule NativeAnimationsExample
  */
 'use strict';
 
diff --git a/RNTester/js/NavigatorIOSBarStyleExample.js b/RNTester/js/NavigatorIOSBarStyleExample.js
index d9d53edd3c99..62e331e22f5a 100644
--- a/RNTester/js/NavigatorIOSBarStyleExample.js
+++ b/RNTester/js/NavigatorIOSBarStyleExample.js
@@ -16,7 +16,6 @@
  * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  *
- * @providesModule NavigatorIOSBarStyleExample
  */
 
 'use strict';
diff --git a/RNTester/js/NavigatorIOSColorsExample.js b/RNTester/js/NavigatorIOSColorsExample.js
index f34c9c9d10af..cdcf6edb7bbd 100644
--- a/RNTester/js/NavigatorIOSColorsExample.js
+++ b/RNTester/js/NavigatorIOSColorsExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NavigatorIOSColorsExample
  */
 'use strict';
 
diff --git a/RNTester/js/NavigatorIOSExample.js b/RNTester/js/NavigatorIOSExample.js
index 79ee6f0fd070..3712b7c4dba8 100644
--- a/RNTester/js/NavigatorIOSExample.js
+++ b/RNTester/js/NavigatorIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule NavigatorIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/NetInfoExample.js b/RNTester/js/NetInfoExample.js
index 0ba8dd2ff8c8..b81251949dad 100644
--- a/RNTester/js/NetInfoExample.js
+++ b/RNTester/js/NetInfoExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule NetInfoExample
  */
 'use strict';
 
diff --git a/RNTester/js/OrientationChangeExample.js b/RNTester/js/OrientationChangeExample.js
index af6f9b1feeca..0c07d21a02b3 100644
--- a/RNTester/js/OrientationChangeExample.js
+++ b/RNTester/js/OrientationChangeExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule OrientationChangeExample
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/PanResponderExample.js b/RNTester/js/PanResponderExample.js
index 27d9a8016677..598de1eac80c 100644
--- a/RNTester/js/PanResponderExample.js
+++ b/RNTester/js/PanResponderExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow weak
- * @providesModule PanResponderExample
  */
 'use strict';
 
diff --git a/RNTester/js/PermissionsExampleAndroid.android.js b/RNTester/js/PermissionsExampleAndroid.android.js
index cb837183a629..322307f32706 100644
--- a/RNTester/js/PermissionsExampleAndroid.android.js
+++ b/RNTester/js/PermissionsExampleAndroid.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PermissionsExampleAndroid
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/PickerExample.js b/RNTester/js/PickerExample.js
index 1a1005cdaa2d..4bd2fd2c3622 100644
--- a/RNTester/js/PickerExample.js
+++ b/RNTester/js/PickerExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule PickerExample
  */
 'use strict';
 
diff --git a/RNTester/js/PickerIOSExample.js b/RNTester/js/PickerIOSExample.js
index a4d5de63a046..4202fd517e50 100644
--- a/RNTester/js/PickerIOSExample.js
+++ b/RNTester/js/PickerIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule PickerIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/PointerEventsExample.js b/RNTester/js/PointerEventsExample.js
index ac15811c96dd..1fc85702a38d 100644
--- a/RNTester/js/PointerEventsExample.js
+++ b/RNTester/js/PointerEventsExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule PointerEventsExample
  */
 'use strict';
 
diff --git a/RNTester/js/ProgressBarAndroidExample.android.js b/RNTester/js/ProgressBarAndroidExample.android.js
index baa75b9ff1e6..1d55779d5780 100644
--- a/RNTester/js/ProgressBarAndroidExample.android.js
+++ b/RNTester/js/ProgressBarAndroidExample.android.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ProgressBarAndroidExample
  */
 'use strict';
 
diff --git a/RNTester/js/ProgressViewIOSExample.js b/RNTester/js/ProgressViewIOSExample.js
index d0641760965c..821fe2e2520e 100644
--- a/RNTester/js/ProgressViewIOSExample.js
+++ b/RNTester/js/ProgressViewIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ProgressViewIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/PushNotificationIOSExample.js b/RNTester/js/PushNotificationIOSExample.js
index c2368e9a782b..b2c54165a1c5 100644
--- a/RNTester/js/PushNotificationIOSExample.js
+++ b/RNTester/js/PushNotificationIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule PushNotificationIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/RCTRootViewIOSExample.js b/RNTester/js/RCTRootViewIOSExample.js
index f6b3b20536ef..5eba0e8cae70 100644
--- a/RNTester/js/RCTRootViewIOSExample.js
+++ b/RNTester/js/RCTRootViewIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RCTRootViewIOSExample
  */
 
 'use strict';
diff --git a/RNTester/js/RNTesterActions.js b/RNTester/js/RNTesterActions.js
index 2bf967b3c2e6..cc89277dcf9c 100644
--- a/RNTester/js/RNTesterActions.js
+++ b/RNTester/js/RNTesterActions.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RNTesterActions
  */
 'use strict';
 
diff --git a/RNTester/js/RNTesterApp.android.js b/RNTester/js/RNTesterApp.android.js
index d5f05d12a90a..ad377b85a54f 100644
--- a/RNTester/js/RNTesterApp.android.js
+++ b/RNTester/js/RNTesterApp.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RNTesterApp
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/RNTesterApp.ios.js b/RNTester/js/RNTesterApp.ios.js
index 26ee1ebbdd97..a72ebb724edb 100644
--- a/RNTester/js/RNTesterApp.ios.js
+++ b/RNTester/js/RNTesterApp.ios.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RNTesterApp
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/RNTesterBlock.js b/RNTester/js/RNTesterBlock.js
index 58ca4d0a5f0c..fa3c44f7873b 100644
--- a/RNTester/js/RNTesterBlock.js
+++ b/RNTester/js/RNTesterBlock.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RNTesterBlock
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/RNTesterButton.js b/RNTester/js/RNTesterButton.js
index 835eb9db113e..9ac5f6e8e818 100644
--- a/RNTester/js/RNTesterButton.js
+++ b/RNTester/js/RNTesterButton.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RNTesterButton
  */
 'use strict';
 
diff --git a/RNTester/js/RNTesterExampleContainer.js b/RNTester/js/RNTesterExampleContainer.js
index e5d1ab816d1d..02e010771f45 100644
--- a/RNTester/js/RNTesterExampleContainer.js
+++ b/RNTester/js/RNTesterExampleContainer.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RNTesterExampleContainer
  */
 'use strict';
 
diff --git a/RNTester/js/RNTesterExampleList.js b/RNTester/js/RNTesterExampleList.js
index e043e2d5cba1..c7d974c48409 100644
--- a/RNTester/js/RNTesterExampleList.js
+++ b/RNTester/js/RNTesterExampleList.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RNTesterExampleList
  */
 'use strict';
 
diff --git a/RNTester/js/RNTesterList.android.js b/RNTester/js/RNTesterList.android.js
index feea07f72cdb..d038354b25c7 100644
--- a/RNTester/js/RNTesterList.android.js
+++ b/RNTester/js/RNTesterList.android.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RNTesterList
  */
 'use strict';
 
diff --git a/RNTester/js/RNTesterList.ios.js b/RNTester/js/RNTesterList.ios.js
index fa95044d77dd..812abde4fe71 100644
--- a/RNTester/js/RNTesterList.ios.js
+++ b/RNTester/js/RNTesterList.ios.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RNTesterList
  */
 'use strict';
 
diff --git a/RNTester/js/RNTesterNavigationReducer.js b/RNTester/js/RNTesterNavigationReducer.js
index c8ffa5a5fe7c..60c21a7106a2 100644
--- a/RNTester/js/RNTesterNavigationReducer.js
+++ b/RNTester/js/RNTesterNavigationReducer.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RNTesterNavigationReducer
  */
 'use strict';
 
diff --git a/RNTester/js/RNTesterPage.js b/RNTester/js/RNTesterPage.js
index 96b016a00000..4af103ea8166 100644
--- a/RNTester/js/RNTesterPage.js
+++ b/RNTester/js/RNTesterPage.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RNTesterPage
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/RNTesterSettingSwitchRow.js b/RNTester/js/RNTesterSettingSwitchRow.js
index 97d2f8d60be4..01cca6336c9e 100644
--- a/RNTester/js/RNTesterSettingSwitchRow.js
+++ b/RNTester/js/RNTesterSettingSwitchRow.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RNTesterSettingSwitchRow
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/RNTesterStatePersister.js b/RNTester/js/RNTesterStatePersister.js
index 310386c49bb7..455f429225a7 100644
--- a/RNTester/js/RNTesterStatePersister.js
+++ b/RNTester/js/RNTesterStatePersister.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RNTesterStatePersister
  */
 'use strict';
 
diff --git a/RNTester/js/RNTesterTitle.js b/RNTester/js/RNTesterTitle.js
index 9afd68a66a7c..17687d98bd8f 100644
--- a/RNTester/js/RNTesterTitle.js
+++ b/RNTester/js/RNTesterTitle.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RNTesterTitle
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/RTLExample.js b/RNTester/js/RTLExample.js
index aad38a9fedc9..67120d06bb2d 100644
--- a/RNTester/js/RTLExample.js
+++ b/RNTester/js/RTLExample.js
@@ -6,7 +6,6 @@
  *
  * @flow
  * @format
- * @providesModule RTLExample
  */
 'use strict';
 
diff --git a/RNTester/js/RefreshControlExample.js b/RNTester/js/RefreshControlExample.js
index 7962a457e29b..055a85c5f644 100644
--- a/RNTester/js/RefreshControlExample.js
+++ b/RNTester/js/RefreshControlExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule RefreshControlExample
  */
 'use strict';
 
diff --git a/RNTester/js/RootViewSizeFlexibilityExampleApp.js b/RNTester/js/RootViewSizeFlexibilityExampleApp.js
index 066a6d425e92..c08a2ec578d5 100644
--- a/RNTester/js/RootViewSizeFlexibilityExampleApp.js
+++ b/RNTester/js/RootViewSizeFlexibilityExampleApp.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule RootViewSizeFlexibilityExampleApp
  */
 'use strict';
 
diff --git a/RNTester/js/SafeAreaViewExample.js b/RNTester/js/SafeAreaViewExample.js
index c3d5a99f8208..927a26651a4f 100644
--- a/RNTester/js/SafeAreaViewExample.js
+++ b/RNTester/js/SafeAreaViewExample.js
@@ -6,7 +6,6 @@
  *
  * @flow
  * @format
- * @providesModule SafeAreaViewExample
  */
 'use strict';
 
diff --git a/RNTester/js/ScrollViewExample.js b/RNTester/js/ScrollViewExample.js
index 66bedc93552c..c1d634b8ebf5 100644
--- a/RNTester/js/ScrollViewExample.js
+++ b/RNTester/js/ScrollViewExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ScrollViewExample
  * @format
  */
 'use strict';
diff --git a/RNTester/js/ScrollViewSimpleExample.js b/RNTester/js/ScrollViewSimpleExample.js
index 0a6713122a88..a4fc25fe14e2 100644
--- a/RNTester/js/ScrollViewSimpleExample.js
+++ b/RNTester/js/ScrollViewSimpleExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ScrollViewSimpleExample
  */
 'use strict';
 
diff --git a/RNTester/js/SectionListExample.js b/RNTester/js/SectionListExample.js
index 920be1768644..5410251853ed 100644
--- a/RNTester/js/SectionListExample.js
+++ b/RNTester/js/SectionListExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SectionListExample
  */
 'use strict';
 
diff --git a/RNTester/js/SegmentedControlIOSExample.js b/RNTester/js/SegmentedControlIOSExample.js
index c5441e7cc4dc..c0098b5fafd4 100644
--- a/RNTester/js/SegmentedControlIOSExample.js
+++ b/RNTester/js/SegmentedControlIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SegmentedControlIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/SetPropertiesExampleApp.js b/RNTester/js/SetPropertiesExampleApp.js
index 8113f5279570..95034438b0a1 100644
--- a/RNTester/js/SetPropertiesExampleApp.js
+++ b/RNTester/js/SetPropertiesExampleApp.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SetPropertiesExampleApp
  */
 'use strict';
 
diff --git a/RNTester/js/ShareExample.js b/RNTester/js/ShareExample.js
index 00d3330d83c2..7df3edd360f7 100644
--- a/RNTester/js/ShareExample.js
+++ b/RNTester/js/ShareExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ShareExample
  */
 'use strict';
 
diff --git a/RNTester/js/SliderExample.js b/RNTester/js/SliderExample.js
index 3b4980ac8004..b05877572e70 100644
--- a/RNTester/js/SliderExample.js
+++ b/RNTester/js/SliderExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SliderExample
  */
 'use strict';
 
diff --git a/RNTester/js/SnapshotExample.js b/RNTester/js/SnapshotExample.js
index 160434b53b26..f77277a53cbf 100644
--- a/RNTester/js/SnapshotExample.js
+++ b/RNTester/js/SnapshotExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SnapshotExample
  * @format
  */
 'use strict';
diff --git a/RNTester/js/StatusBarExample.js b/RNTester/js/StatusBarExample.js
index e5dae5c77c49..b9949c17cce1 100644
--- a/RNTester/js/StatusBarExample.js
+++ b/RNTester/js/StatusBarExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule StatusBarExample
  */
 'use strict';
 
diff --git a/RNTester/js/SwipeableFlatListExample.js b/RNTester/js/SwipeableFlatListExample.js
index 432e6d813d50..4c8716e8c838 100644
--- a/RNTester/js/SwipeableFlatListExample.js
+++ b/RNTester/js/SwipeableFlatListExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SwipeableFlatListExample
  * @flow
  * @format
  */
diff --git a/RNTester/js/SwipeableListViewExample.js b/RNTester/js/SwipeableListViewExample.js
index c004f86e3e6a..db91633962cf 100644
--- a/RNTester/js/SwipeableListViewExample.js
+++ b/RNTester/js/SwipeableListViewExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SwipeableListViewExample
  */
 'use strict';
 
diff --git a/RNTester/js/SwitchExample.js b/RNTester/js/SwitchExample.js
index ca721ce4488e..e040c76a1c79 100644
--- a/RNTester/js/SwitchExample.js
+++ b/RNTester/js/SwitchExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule SwitchExample
  */
 'use strict';
 
diff --git a/RNTester/js/TVEventHandlerExample.js b/RNTester/js/TVEventHandlerExample.js
index bc6346d0d2b0..84067863268c 100644
--- a/RNTester/js/TVEventHandlerExample.js
+++ b/RNTester/js/TVEventHandlerExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TVEventHandlerExample
  */
 'use strict';
 
diff --git a/RNTester/js/TabBarIOSBarStyleExample.js b/RNTester/js/TabBarIOSBarStyleExample.js
index 5c42c5ccf1ef..972235698133 100644
--- a/RNTester/js/TabBarIOSBarStyleExample.js
+++ b/RNTester/js/TabBarIOSBarStyleExample.js
@@ -16,7 +16,6 @@
  * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  *
- * @providesModule TabBarIOSBarStyleExample
  * @flow
  */
 
diff --git a/RNTester/js/TabBarIOSExample.js b/RNTester/js/TabBarIOSExample.js
index 82c47cccdfe2..12906b0e176e 100644
--- a/RNTester/js/TabBarIOSExample.js
+++ b/RNTester/js/TabBarIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TabBarIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/TextExample.android.js b/RNTester/js/TextExample.android.js
index b912337827a2..6f824e01132e 100644
--- a/RNTester/js/TextExample.android.js
+++ b/RNTester/js/TextExample.android.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TextExample
  */
 'use strict';
 
diff --git a/RNTester/js/TextExample.ios.js b/RNTester/js/TextExample.ios.js
index 939774aa06a0..968e0a42c8f8 100644
--- a/RNTester/js/TextExample.ios.js
+++ b/RNTester/js/TextExample.ios.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TextExample
  */
 'use strict';
 
diff --git a/RNTester/js/TextInputExample.android.js b/RNTester/js/TextInputExample.android.js
index 358d3fd043b0..f0b3403d618f 100644
--- a/RNTester/js/TextInputExample.android.js
+++ b/RNTester/js/TextInputExample.android.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TextInputExample
  */
 'use strict';
 
diff --git a/RNTester/js/TextInputExample.ios.js b/RNTester/js/TextInputExample.ios.js
index 9ace0a94ae6f..fdcddc1f793d 100644
--- a/RNTester/js/TextInputExample.ios.js
+++ b/RNTester/js/TextInputExample.ios.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TextInputExample
  */
 'use strict';
 
diff --git a/RNTester/js/TimePickerAndroidExample.js b/RNTester/js/TimePickerAndroidExample.js
index 7e1afa6367d7..517f674665ac 100644
--- a/RNTester/js/TimePickerAndroidExample.js
+++ b/RNTester/js/TimePickerAndroidExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TimePickerAndroidExample
  */
 'use strict';
 
diff --git a/RNTester/js/TimerExample.js b/RNTester/js/TimerExample.js
index d7e966010f9a..a56fd5ad3fe0 100644
--- a/RNTester/js/TimerExample.js
+++ b/RNTester/js/TimerExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TimerExample
  */
 'use strict';
 
diff --git a/RNTester/js/ToastAndroidExample.android.js b/RNTester/js/ToastAndroidExample.android.js
index e86a21cb83ef..6ca7b9c4f8b7 100644
--- a/RNTester/js/ToastAndroidExample.android.js
+++ b/RNTester/js/ToastAndroidExample.android.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ToastAndroidExample
  */
 
 'use strict';
diff --git a/RNTester/js/ToolbarAndroidExample.android.js b/RNTester/js/ToolbarAndroidExample.android.js
index e19751870474..7a17105698c4 100644
--- a/RNTester/js/ToolbarAndroidExample.android.js
+++ b/RNTester/js/ToolbarAndroidExample.android.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ToolbarAndroidExample
  */
 'use strict';
 
diff --git a/RNTester/js/ToolbarAndroidExample.ios.js b/RNTester/js/ToolbarAndroidExample.ios.js
index b2553dc1b2bc..5e8c57f7a81d 100644
--- a/RNTester/js/ToolbarAndroidExample.ios.js
+++ b/RNTester/js/ToolbarAndroidExample.ios.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ToolbarAndroidExample
  */
 'use strict';
 
diff --git a/RNTester/js/TouchableExample.js b/RNTester/js/TouchableExample.js
index e0c227d9ca3f..069dff9d26c0 100644
--- a/RNTester/js/TouchableExample.js
+++ b/RNTester/js/TouchableExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TouchableExample
  */
 'use strict';
 
diff --git a/RNTester/js/TransformExample.js b/RNTester/js/TransformExample.js
index 17e2a89fc98d..4271e074a017 100644
--- a/RNTester/js/TransformExample.js
+++ b/RNTester/js/TransformExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TransformExample
  */
 'use strict';
 
diff --git a/RNTester/js/TransparentHitTestExample.js b/RNTester/js/TransparentHitTestExample.js
index 89db856a4735..e1baa00964ed 100644
--- a/RNTester/js/TransparentHitTestExample.js
+++ b/RNTester/js/TransparentHitTestExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule TransparentHitTestExample
  */
 
 'use strict';
diff --git a/RNTester/js/URIActionMap.js b/RNTester/js/URIActionMap.js
index fb47214aadd5..f303fa21a499 100644
--- a/RNTester/js/URIActionMap.js
+++ b/RNTester/js/URIActionMap.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule URIActionMap
  */
 'use strict';
 
diff --git a/RNTester/js/VibrationExample.js b/RNTester/js/VibrationExample.js
index 9e6d6d7d768b..a213799902f8 100644
--- a/RNTester/js/VibrationExample.js
+++ b/RNTester/js/VibrationExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule VibrationExample
  */
 'use strict';
 
diff --git a/RNTester/js/VibrationIOSExample.js b/RNTester/js/VibrationIOSExample.js
index 9093ff87af28..5f642519da18 100644
--- a/RNTester/js/VibrationIOSExample.js
+++ b/RNTester/js/VibrationIOSExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule VibrationIOSExample
  */
 'use strict';
 
diff --git a/RNTester/js/ViewExample.js b/RNTester/js/ViewExample.js
index b4c4a6c2a658..5d643a12fa09 100644
--- a/RNTester/js/ViewExample.js
+++ b/RNTester/js/ViewExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ViewExample
  */
 'use strict';
 
diff --git a/RNTester/js/ViewPagerAndroidExample.android.js b/RNTester/js/ViewPagerAndroidExample.android.js
index 1f2ac75d8f22..1c5da99bae64 100644
--- a/RNTester/js/ViewPagerAndroidExample.android.js
+++ b/RNTester/js/ViewPagerAndroidExample.android.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewPagerAndroidExample
  */
 'use strict';
 
diff --git a/RNTester/js/WebSocketExample.js b/RNTester/js/WebSocketExample.js
index ad4a6f8be471..b1cffe3e5dc6 100644
--- a/RNTester/js/WebSocketExample.js
+++ b/RNTester/js/WebSocketExample.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule WebSocketExample
  * @format
  */
 'use strict';
diff --git a/RNTester/js/WebViewExample.js b/RNTester/js/WebViewExample.js
index d3bc575361e5..d55d17ca60ec 100644
--- a/RNTester/js/WebViewExample.js
+++ b/RNTester/js/WebViewExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule WebViewExample
  */
 'use strict';
 
diff --git a/RNTester/js/XHRExample.js b/RNTester/js/XHRExample.js
index 1ee8315d03ba..fc7cb8c21376 100644
--- a/RNTester/js/XHRExample.js
+++ b/RNTester/js/XHRExample.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule XHRExample
  */
 'use strict';
 
diff --git a/RNTester/js/XHRExampleBinaryUpload.js b/RNTester/js/XHRExampleBinaryUpload.js
index e56357243786..efe96dea0f22 100644
--- a/RNTester/js/XHRExampleBinaryUpload.js
+++ b/RNTester/js/XHRExampleBinaryUpload.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule XHRExampleBinaryUpload
  */
 'use strict';
 
diff --git a/RNTester/js/XHRExampleCookies.js b/RNTester/js/XHRExampleCookies.js
index 08ff72b369cb..2050f555eb91 100644
--- a/RNTester/js/XHRExampleCookies.js
+++ b/RNTester/js/XHRExampleCookies.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule XHRExampleCookies
  */
 'use strict';
 
diff --git a/RNTester/js/XHRExampleDownload.js b/RNTester/js/XHRExampleDownload.js
index a419f9ba539e..2ffe801fbcc1 100644
--- a/RNTester/js/XHRExampleDownload.js
+++ b/RNTester/js/XHRExampleDownload.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule XHRExampleDownload
  */
 'use strict';
 
diff --git a/RNTester/js/XHRExampleFetch.js b/RNTester/js/XHRExampleFetch.js
index 2aea3be975f4..c4915ce5677a 100644
--- a/RNTester/js/XHRExampleFetch.js
+++ b/RNTester/js/XHRExampleFetch.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule XHRExampleFetch
  */
 'use strict';
 
diff --git a/RNTester/js/XHRExampleFormData.js b/RNTester/js/XHRExampleFormData.js
index 228af6345bd4..8c0080ea11b7 100644
--- a/RNTester/js/XHRExampleFormData.js
+++ b/RNTester/js/XHRExampleFormData.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule XHRExampleFormData
  */
 'use strict';
 
diff --git a/RNTester/js/XHRExampleHeaders.js b/RNTester/js/XHRExampleHeaders.js
index 8476b1600ef6..b3dc69edc21a 100644
--- a/RNTester/js/XHRExampleHeaders.js
+++ b/RNTester/js/XHRExampleHeaders.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule XHRExampleHeaders
  */
 'use strict';
 
diff --git a/RNTester/js/XHRExampleOnTimeOut.js b/RNTester/js/XHRExampleOnTimeOut.js
index d3c50025c2d0..1afb39904201 100644
--- a/RNTester/js/XHRExampleOnTimeOut.js
+++ b/RNTester/js/XHRExampleOnTimeOut.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule XHRExampleOnTimeOut
  */
 'use strict';
 
diff --git a/RNTester/js/createExamplePage.js b/RNTester/js/createExamplePage.js
index e381f05b8d2c..1ae3733b969a 100644
--- a/RNTester/js/createExamplePage.js
+++ b/RNTester/js/createExamplePage.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule createExamplePage
  * @flow
  */
 'use strict';
diff --git a/RNTester/js/http_test_server.js b/RNTester/js/http_test_server.js
index cd9e18e5407d..998d73dbf194 100755
--- a/RNTester/js/http_test_server.js
+++ b/RNTester/js/http_test_server.js
@@ -6,7 +6,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule http_test_server
  */
 'use strict';
 
diff --git a/RNTester/js/websocket_test_server.js b/RNTester/js/websocket_test_server.js
index 83a48ed213f0..3f3a23cfa04c 100755
--- a/RNTester/js/websocket_test_server.js
+++ b/RNTester/js/websocket_test_server.js
@@ -6,7 +6,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule websocket_test_server
  */
 'use strict';
 
diff --git a/ReactAndroid/src/androidTest/js/Asserts.js b/ReactAndroid/src/androidTest/js/Asserts.js
index 0cebeea419d2..95fd89f272d1 100644
--- a/ReactAndroid/src/androidTest/js/Asserts.js
+++ b/ReactAndroid/src/androidTest/js/Asserts.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule Asserts
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/CatalystRootViewTestModule.js b/ReactAndroid/src/androidTest/js/CatalystRootViewTestModule.js
index 33f0592a4832..b0e5571b277a 100644
--- a/ReactAndroid/src/androidTest/js/CatalystRootViewTestModule.js
+++ b/ReactAndroid/src/androidTest/js/CatalystRootViewTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule CatalystRootViewTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/DatePickerDialogTestModule.js b/ReactAndroid/src/androidTest/js/DatePickerDialogTestModule.js
index 0cd5685820ca..4ba296cc757a 100644
--- a/ReactAndroid/src/androidTest/js/DatePickerDialogTestModule.js
+++ b/ReactAndroid/src/androidTest/js/DatePickerDialogTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule DatePickerDialogTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/InitialPropsTestApp.js b/ReactAndroid/src/androidTest/js/InitialPropsTestApp.js
index 173ef647f482..002ebf0cc68b 100644
--- a/ReactAndroid/src/androidTest/js/InitialPropsTestApp.js
+++ b/ReactAndroid/src/androidTest/js/InitialPropsTestApp.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule InitialPropsTestApp
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/JSResponderTestApp.js b/ReactAndroid/src/androidTest/js/JSResponderTestApp.js
index 50612afb9e2e..d6e7f878defb 100644
--- a/ReactAndroid/src/androidTest/js/JSResponderTestApp.js
+++ b/ReactAndroid/src/androidTest/js/JSResponderTestApp.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule JSResponderTestApp
  */
 'use strict';
 
diff --git a/ReactAndroid/src/androidTest/js/LayoutEventsTestApp.js b/ReactAndroid/src/androidTest/js/LayoutEventsTestApp.js
index d9ecf2ca1b54..153089437e4c 100644
--- a/ReactAndroid/src/androidTest/js/LayoutEventsTestApp.js
+++ b/ReactAndroid/src/androidTest/js/LayoutEventsTestApp.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule LayoutEventsTestApp
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/MeasureLayoutTestModule.js b/ReactAndroid/src/androidTest/js/MeasureLayoutTestModule.js
index 92ac114b6cc7..baf4f7bc03ba 100644
--- a/ReactAndroid/src/androidTest/js/MeasureLayoutTestModule.js
+++ b/ReactAndroid/src/androidTest/js/MeasureLayoutTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule MeasureLayoutTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/MultitouchHandlingTestAppModule.js b/ReactAndroid/src/androidTest/js/MultitouchHandlingTestAppModule.js
index 7daa884359fa..0c591483f6c1 100644
--- a/ReactAndroid/src/androidTest/js/MultitouchHandlingTestAppModule.js
+++ b/ReactAndroid/src/androidTest/js/MultitouchHandlingTestAppModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule MultitouchHandlingTestAppModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/NativeIdTestModule.js b/ReactAndroid/src/androidTest/js/NativeIdTestModule.js
index 2e1acad34227..be457b3c5699 100644
--- a/ReactAndroid/src/androidTest/js/NativeIdTestModule.js
+++ b/ReactAndroid/src/androidTest/js/NativeIdTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NativeIdTestModule
  * @flow
  */
 
diff --git a/ReactAndroid/src/androidTest/js/PickerAndroidTestModule.js b/ReactAndroid/src/androidTest/js/PickerAndroidTestModule.js
index 0f7255d15640..237dacba21bf 100644
--- a/ReactAndroid/src/androidTest/js/PickerAndroidTestModule.js
+++ b/ReactAndroid/src/androidTest/js/PickerAndroidTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule PickerAndroidTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/ProgressBarTestModule.js b/ReactAndroid/src/androidTest/js/ProgressBarTestModule.js
index bd466144c522..a6e3849e0d23 100644
--- a/ReactAndroid/src/androidTest/js/ProgressBarTestModule.js
+++ b/ReactAndroid/src/androidTest/js/ProgressBarTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ProgressBarTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/ScrollViewTestModule.js b/ReactAndroid/src/androidTest/js/ScrollViewTestModule.js
index 24371b0f7657..7654f106087a 100644
--- a/ReactAndroid/src/androidTest/js/ScrollViewTestModule.js
+++ b/ReactAndroid/src/androidTest/js/ScrollViewTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ScrollViewTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/ShareTestModule.js b/ReactAndroid/src/androidTest/js/ShareTestModule.js
index f7311f656041..dd0f7fc9646d 100644
--- a/ReactAndroid/src/androidTest/js/ShareTestModule.js
+++ b/ReactAndroid/src/androidTest/js/ShareTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ShareTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js b/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
index 70fa837eed6b..859acfc92c6a 100644
--- a/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
+++ b/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SubviewsClippingTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/SwipeRefreshLayoutTestModule.js b/ReactAndroid/src/androidTest/js/SwipeRefreshLayoutTestModule.js
index 277a768e9430..5a126772ef56 100644
--- a/ReactAndroid/src/androidTest/js/SwipeRefreshLayoutTestModule.js
+++ b/ReactAndroid/src/androidTest/js/SwipeRefreshLayoutTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule SwipeRefreshLayoutTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/TestBundle.js b/ReactAndroid/src/androidTest/js/TestBundle.js
index 21fd06247e41..64d2c57d26f3 100644
--- a/ReactAndroid/src/androidTest/js/TestBundle.js
+++ b/ReactAndroid/src/androidTest/js/TestBundle.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TestBundle
  */
 'use strict';
 
diff --git a/ReactAndroid/src/androidTest/js/TestIdTestModule.js b/ReactAndroid/src/androidTest/js/TestIdTestModule.js
index eee76fbc05c0..0320f3cf8be7 100644
--- a/ReactAndroid/src/androidTest/js/TestIdTestModule.js
+++ b/ReactAndroid/src/androidTest/js/TestIdTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TestIdTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/TestJSLocaleModule.js b/ReactAndroid/src/androidTest/js/TestJSLocaleModule.js
index be6bfc12a3a2..a9aca7983d23 100644
--- a/ReactAndroid/src/androidTest/js/TestJSLocaleModule.js
+++ b/ReactAndroid/src/androidTest/js/TestJSLocaleModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TestJSLocaleModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/TestJSToJavaParametersModule.js b/ReactAndroid/src/androidTest/js/TestJSToJavaParametersModule.js
index bc526e7722ba..5e5527846ae0 100644
--- a/ReactAndroid/src/androidTest/js/TestJSToJavaParametersModule.js
+++ b/ReactAndroid/src/androidTest/js/TestJSToJavaParametersModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TestJSToJavaParametersModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/TestJavaToJSArgumentsModule.js b/ReactAndroid/src/androidTest/js/TestJavaToJSArgumentsModule.js
index b5abe26a8eeb..6e71061666bf 100644
--- a/ReactAndroid/src/androidTest/js/TestJavaToJSArgumentsModule.js
+++ b/ReactAndroid/src/androidTest/js/TestJavaToJSArgumentsModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TestJavaToJSArgumentsModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/TestJavaToJSReturnValuesModule.js b/ReactAndroid/src/androidTest/js/TestJavaToJSReturnValuesModule.js
index 135816a5c9d6..1aa72f0b8572 100644
--- a/ReactAndroid/src/androidTest/js/TestJavaToJSReturnValuesModule.js
+++ b/ReactAndroid/src/androidTest/js/TestJavaToJSReturnValuesModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TestJavaToJSReturnValuesModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/TextInputTestModule.js b/ReactAndroid/src/androidTest/js/TextInputTestModule.js
index 94593a3ab714..fff1fc5bca68 100644
--- a/ReactAndroid/src/androidTest/js/TextInputTestModule.js
+++ b/ReactAndroid/src/androidTest/js/TextInputTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TextInputTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/TimePickerDialogTestModule.js b/ReactAndroid/src/androidTest/js/TimePickerDialogTestModule.js
index ebf8cdb4f127..80e355c951ec 100644
--- a/ReactAndroid/src/androidTest/js/TimePickerDialogTestModule.js
+++ b/ReactAndroid/src/androidTest/js/TimePickerDialogTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TimePickerDialogTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/TouchBubblingTestAppModule.js b/ReactAndroid/src/androidTest/js/TouchBubblingTestAppModule.js
index cd8bcb51c528..6f8e6226ad58 100644
--- a/ReactAndroid/src/androidTest/js/TouchBubblingTestAppModule.js
+++ b/ReactAndroid/src/androidTest/js/TouchBubblingTestAppModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule TouchBubblingTestAppModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/UIManagerTestModule.js b/ReactAndroid/src/androidTest/js/UIManagerTestModule.js
index 5c976ce76dc3..93f73d44c0d6 100644
--- a/ReactAndroid/src/androidTest/js/UIManagerTestModule.js
+++ b/ReactAndroid/src/androidTest/js/UIManagerTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule UIManagerTestModule
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/ViewRenderingTestModule.js b/ReactAndroid/src/androidTest/js/ViewRenderingTestModule.js
index 36d9328c93e2..0ddaa86f07e9 100644
--- a/ReactAndroid/src/androidTest/js/ViewRenderingTestModule.js
+++ b/ReactAndroid/src/androidTest/js/ViewRenderingTestModule.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ViewRenderingTestModule
  */
 
 'use strict';
diff --git a/jest/hasteImpl.js b/jest/hasteImpl.js
new file mode 100644
index 000000000000..cb5ac4a049c4
--- /dev/null
+++ b/jest/hasteImpl.js
@@ -0,0 +1,75 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ */
+
+'use strict';
+
+const path = require('path');
+
+const ROOT = path.join(__dirname, '..');
+
+const BLACKLISTED_PATTERNS/*: Array<RegExp>*/ = [
+  /.*\/__(mocks|tests)__\/.*/,
+  /^Libraries\/Animated\/src\/polyfills\/.*/,
+];
+
+const WHITELISTED_PREFIXES/*: Array<string>*/ = [
+  'IntegrationTests',
+  'Libraries',
+  'ReactAndroid',
+  'RNTester',
+];
+
+const NAME_REDUCERS/*: Array<[RegExp, string]>*/ = [
+  // extract basename
+  [/^(?:.*\/)?([a-zA-Z0-9$_.-]+)$/, '$1'],
+  // strip .js/.js.flow suffix
+  [/^(.*)\.js(\.flow)?$/, '$1'],
+  // strip .android/.ios/.native/.web suffix
+  [/^(.*)\.(android|ios|native|web)$/, '$1'],
+];
+
+const haste = {
+  /*
+   * @return {string|void} hasteName for module at filePath; or undefined if
+   *                       filePath is not a haste module
+   */
+  getHasteName(
+    filePath/*: string*/,
+    sourceCode/* : ?string*/
+  )/*: (string | void)*/ {
+    if (!isHastePath(filePath)) {
+      return undefined;
+    }
+
+    const hasteName = NAME_REDUCERS.reduce(
+      (name, [pattern, replacement]) => name.replace(pattern, replacement),
+      filePath
+    );
+
+    return hasteName;
+  },
+};
+
+function isHastePath(filePath/*: string*/)/*: bool*/ {
+  if (!filePath.endsWith('.js') && !filePath.endsWith('.js.flow')) {
+    return false;
+  }
+
+  if (!filePath.startsWith(ROOT)) {
+    return false;
+  }
+
+  filePath = filePath.substr(ROOT.length + 1);
+  if (BLACKLISTED_PATTERNS.some(pattern => pattern.test(filePath))) {
+    return false;
+  }
+  return WHITELISTED_PREFIXES.some(prefix => filePath.startsWith(prefix));
+}
+
+module.exports = haste;
diff --git a/local-cli/core/index.js b/local-cli/core/index.js
index e5f2ba33af6b..f3059be0a627 100644
--- a/local-cli/core/index.js
+++ b/local-cli/core/index.js
@@ -68,6 +68,8 @@ const pluginPlatforms = plugins
 
 const defaultRNConfig = {
 
+  hasteImplModulePath: require.resolve('../../jest/hasteImpl'),
+
   getProjectCommands(): Array<CommandT> {
     const commands = plugins
       .commands
diff --git a/package.json b/package.json
index ced5fcabbd63..d95183357888 100644
--- a/package.json
+++ b/package.json
@@ -37,6 +37,7 @@
     ],
     "haste": {
       "defaultPlatform": "ios",
+      "hasteImplModulePath": "<rootDir>/jest/hasteImpl.js",
       "providesModuleNodeModules": [
         "react-native"
       ],

From c6b96c0df789717d53ec520ad28ba0ae00db6ec2 Mon Sep 17 00:00:00 2001
From: Jean Lauliac <jeanlauliac@fb.com>
Date: Wed, 25 Apr 2018 07:03:24 -0700
Subject: [PATCH 0373/1109] react-native-github: remove old fs mock
 implementation

Reviewed By: rafeca

Differential Revision: D7652914

fbshipit-source-id: 5494305750e7616b5120169266c519f460ae7e6d
---
 local-cli/__mocks__/fs.js                     | 437 +-----------------
 local-cli/__tests__/fs-mock-test.js           |  89 ----
 .../link/__tests__/ios/writePlist.spec.js     |   3 +
 package.json                                  |   1 +
 4 files changed, 26 insertions(+), 504 deletions(-)
 delete mode 100644 local-cli/__tests__/fs-mock-test.js

diff --git a/local-cli/__mocks__/fs.js b/local-cli/__mocks__/fs.js
index bd4d5c10001c..0ac81ced62db 100644
--- a/local-cli/__mocks__/fs.js
+++ b/local-cli/__mocks__/fs.js
@@ -9,428 +9,35 @@
 
 'use strict';
 
-const asyncify = require('async/asyncify');
-const {EventEmitter} = require('events');
-const {dirname} = require.requireActual('path');
-const fs = jest.genMockFromModule('fs');
-const invariant = require('fbjs/lib/invariant');
-const path = require('path');
-const stream = require.requireActual('stream');
+const fs = new (require('metro-memory-fs'))();
 
-const noop = () => {};
-
-function asyncCallback(cb) {
-  return function() {
-    setImmediate(() => cb.apply(this, arguments));
-  };
+function setMockFilesystem(object) {
+  fs.reset();
+  const root = process.platform === 'win32' ? 'c:\\' : '/';
+  mockDir(root, {...object});
 }
 
-const mtime = {
-  getTime: () => Math.ceil(Math.random() * 10000000),
-};
-
-fs.realpath.mockImplementation((filepath, callback) => {
-  callback = asyncCallback(callback);
-  let node;
-  try {
-    node = getToNode(filepath);
-  } catch (e) {
-    return callback(e);
-  }
-  if (node && typeof node === 'object' && node.SYMLINK != null) {
-    return callback(null, node.SYMLINK);
-  }
-  return callback(null, filepath);
-});
-
-fs.readdirSync.mockImplementation(filepath => Object.keys(getToNode(filepath)));
-
-fs.readdir.mockImplementation((filepath, callback) => {
-  callback = asyncCallback(callback);
-  let node;
-  try {
-    node = getToNode(filepath);
-    if (node && typeof node === 'object' && node.SYMLINK != null) {
-      node = getToNode(node.SYMLINK);
+function mockDir(dirPath, desc) {
+  for (const entName in desc) {
+    const ent = desc[entName];
+    const entPath = require('path').join(dirPath, entName);
+    if (typeof ent === 'string' || ent instanceof Buffer) {
+      fs.writeFileSync(entPath, ent);
+      continue;
     }
-  } catch (e) {
-    return callback(e);
-  }
-
-  if (!(node && typeof node === 'object' && node.SYMLINK == null)) {
-    return callback(new Error(filepath + ' is not a directory.'));
-  }
-
-  return callback(null, Object.keys(node));
-});
-
-fs.readFile.mockImplementation(asyncify(fs.readFileSync));
-
-fs.readFileSync.mockImplementation(function(filepath, encoding) {
-  filepath = path.normalize(filepath);
-  const node = getToNode(filepath);
-  if (isDirNode(node)) {
-    throw new Error('Error readFileSync a dir: ' + filepath);
-  }
-  if (Buffer.isBuffer(node) && typeof encoding !== 'undefined') {
-    return node.toString();
-  }
-  return node;
-});
-
-fs.writeFile.mockImplementation(asyncify(fs.writeFileSync));
-
-fs.writeFileSync.mockImplementation((filePath, content, options) => {
-  filePath = path.normalize(filePath);
-  if (options == null || typeof options === 'string') {
-    options = {encoding: options};
-  }
-  invariant(
-    options.encoding == null || options.encoding === 'utf8',
-    '`options` argument supports only `null` or `"utf8"`',
-  );
-  const dirPath = path.dirname(filePath);
-  const node = getToNode(dirPath);
-  if (!isDirNode(node)) {
-    throw fsError('ENOTDIR', 'not a directory: ' + dirPath);
-  }
-  node[path.basename(filePath)] = content;
-});
-
-const openFds = new Map();
-let nextFd = 3;
-
-fs.openSync.mockImplementation((filePath, flags) => {
-  const dirPath = path.dirname(filePath);
-  const node = getToNode(dirPath);
-  if (!isDirNode(node)) {
-    throw fsError('ENOTDIR', 'not a directory: ' + dirPath);
-  }
-  node[path.basename(filePath)] = '';
-  openFds.set(nextFd, {filePath, flags, node});
-  return nextFd++;
-});
-
-fs.writeSync.mockImplementation((fd, str) => {
-  invariant(typeof str === 'string', 'only strings supported');
-  const data = openFds.get(fd);
-  if (data == null || data.flags !== 'w') {
-    throw fsError('EBADF', 'bad file descriptor, write');
-  }
-  data.node[path.basename(data.filePath)] += str;
-});
-
-fs.closeSync.mockImplementation(fd => {
-  openFds.delete(fd);
-});
-
-fs.mkdir.mockImplementation(asyncify(fs.mkdirSync));
-
-fs.mkdirSync.mockImplementation((dirPath, mode) => {
-  const parentPath = path.dirname(dirPath);
-  const node = getToNode(parentPath);
-  if (!isDirNode(node)) {
-    throw fsError('ENOTDIR', 'not a directory: ' + parentPath);
-  }
-  if (node[path.basename(dirPath)] == null) {
-    node[path.basename(dirPath)] = {};
-  }
-});
-
-function fsError(code, message) {
-  const error = new Error(code + ': ' + message);
-  error.code = code;
-  return error;
-}
-
-function isDirNode(node) {
-  return (
-    node &&
-    typeof node === 'object' &&
-    node.SYMLINK == null &&
-    Buffer.isBuffer(node) === false
-  );
-}
-
-function readlinkSync(filepath) {
-  const node = getToNode(filepath);
-  if (node !== null && typeof node === 'object' && !!node.SYMLINK) {
-    return node.SYMLINK;
-  } else {
-    throw new Error(`EINVAL: invalid argument, readlink '${filepath}'`);
-  }
-}
-
-fs.readlink.mockImplementation((filepath, callback) => {
-  callback = asyncCallback(callback);
-  let result;
-  try {
-    result = readlinkSync(filepath);
-  } catch (e) {
-    callback(e);
-    return;
-  }
-  callback(null, result);
-});
-
-fs.readlinkSync.mockImplementation(readlinkSync);
-
-function existsSync(filepath) {
-  try {
-    const node = getToNode(filepath);
-    return node !== null;
-  } catch (e) {
-    return false;
-  }
-}
-
-fs.exists.mockImplementation((filepath, callback) => {
-  callback = asyncCallback(callback);
-  let result;
-  try {
-    result = existsSync(filepath);
-  } catch (e) {
-    callback(e);
-    return;
-  }
-  callback(null, result);
-});
-
-fs.existsSync.mockImplementation(existsSync);
-
-function makeStatResult(node) {
-  const isSymlink = node != null && node.SYMLINK != null;
-  return {
-    isBlockDevice: () => false,
-    isCharacterDevice: () => false,
-    isDirectory: () => node != null && typeof node === 'object' && !isSymlink,
-    isFIFO: () => false,
-    isFile: () => node != null && typeof node === 'string',
-    isSocket: () => false,
-    isSymbolicLink: () => isSymlink,
-    mtime,
-  };
-}
-
-function statSync(filepath) {
-  const node = getToNode(filepath);
-  if (node != null && node.SYMLINK) {
-    return statSync(node.SYMLINK);
-  }
-  return makeStatResult(node);
-}
-
-fs.stat.mockImplementation((filepath, callback) => {
-  callback = asyncCallback(callback);
-  let result;
-  try {
-    result = statSync(filepath);
-  } catch (e) {
-    callback(e);
-    return;
-  }
-  callback(null, result);
-});
-
-fs.statSync.mockImplementation(statSync);
-
-function lstatSync(filepath) {
-  const node = getToNode(filepath);
-  return makeStatResult(node);
-}
-
-fs.lstat.mockImplementation((filepath, callback) => {
-  callback = asyncCallback(callback);
-  let result;
-  try {
-    result = lstatSync(filepath);
-  } catch (e) {
-    callback(e);
-    return;
-  }
-  callback(null, result);
-});
-
-fs.lstatSync.mockImplementation(lstatSync);
-
-fs.open.mockImplementation(function(filepath) {
-  const callback = arguments[arguments.length - 1] || noop;
-  let data, error, fd;
-  try {
-    data = getToNode(filepath);
-  } catch (e) {
-    error = e;
-  }
-
-  if (error || data == null) {
-    error = Error(`ENOENT: no such file or directory: \`${filepath}\``);
-  }
-  if (data != null) {
-    /* global Buffer: true */
-    fd = {buffer: new Buffer(data, 'utf8'), position: 0};
-  }
-
-  callback(error, fd);
-});
-
-fs.read.mockImplementation(
-  (fd, buffer, writeOffset, length, position, callback = noop) => {
-    let bytesWritten;
-    try {
-      if (position == null || position < 0) {
-        ({position} = fd);
-      }
-      bytesWritten = fd.buffer.copy(
-        buffer,
-        writeOffset,
-        position,
-        position + length,
-      );
-      fd.position = position + bytesWritten;
-    } catch (e) {
-      callback(Error('invalid argument'));
-      return;
-    }
-    callback(null, bytesWritten, buffer);
-  },
-);
-
-fs.close.mockImplementation((fd, callback = noop) => {
-  try {
-    fd.buffer = fs.position = undefined;
-  } catch (e) {
-    callback(Error('invalid argument'));
-    return;
-  }
-  callback(null);
-});
-
-let filesystem = {};
-
-fs.mock = {
-  clear() {
-    filesystem = {};
-  },
-};
-
-fs.createReadStream.mockImplementation(filepath => {
-  if (!filepath.startsWith('/')) {
-    throw Error('Cannot open file ' + filepath);
-  }
-
-  const parts = filepath.split('/').slice(1);
-  let file = filesystem;
-
-  for (const part of parts) {
-    file = file[part];
-    if (!file) {
-      break;
+    if (typeof ent !== 'object') {
+      throw new Error(require('util').format('invalid entity:', ent));
     }
-  }
-
-  if (typeof file !== 'string') {
-    throw Error('Cannot open file ' + filepath);
-  }
-
-  return new stream.Readable({
-    read() {
-      this.push(file, 'utf8');
-      this.push(null);
-    },
-  });
-});
-
-fs.createWriteStream.mockImplementation(filePath => {
-  let node;
-  const writeStream = new stream.Writable({
-    write(chunk, encoding, callback) {
-      this.__chunks.push(chunk);
-      node[path.basename(filePath)] = this.__chunks.join('');
-      callback();
-    },
-  });
-  writeStream.__file = filePath;
-  writeStream.__chunks = [];
-  writeStream.end = jest.fn(writeStream.end);
-  fs.createWriteStream.mock.returned.push(writeStream);
-  try {
-    const dirPath = dirname(filePath);
-    node = getToNode(dirPath);
-    if (!isDirNode(node)) {
-      throw fsError('ENOTDIR', 'not a directory: ' + dirPath);
+    if (ent.SYMLINK != null) {
+      fs.symlinkSync(ent.SYMLINK, entPath);
+      continue;
     }
-    // Truncate the file on opening.
-    node[path.basename(filePath)] = '';
-  } catch (error) {
-    process.nextTick(() => writeStream.emit('error', error));
-  }
-  return writeStream;
-});
-fs.createWriteStream.mock.returned = [];
-
-fs.__setMockFilesystem = object => (filesystem = object);
-
-const watcherListByPath = new Map();
-
-fs.watch.mockImplementation((filename, options, listener) => {
-  if (options.recursive) {
-    throw new Error('recursive watch not implemented');
+    fs.mkdirSync(entPath);
+    mockDir(entPath, ent);
   }
-  let watcherList = watcherListByPath.get(filename);
-  if (watcherList == null) {
-    watcherList = [];
-    watcherListByPath.set(filename, watcherList);
-  }
-  const fsWatcher = new EventEmitter();
-  fsWatcher.on('change', listener);
-  fsWatcher.close = () => {
-    watcherList.splice(watcherList.indexOf(fsWatcher), 1);
-    fsWatcher.close = () => {
-      throw new Error('FSWatcher is already closed');
-    };
-  };
-  watcherList.push(fsWatcher);
-});
-
-fs.__triggerWatchEvent = (eventType, filename) => {
-  const directWatchers = watcherListByPath.get(filename) || [];
-  directWatchers.forEach(wtc => wtc.emit('change', eventType));
-  const dirPath = path.dirname(filename);
-  const dirWatchers = watcherListByPath.get(dirPath) || [];
-  dirWatchers.forEach(wtc =>
-    wtc.emit('change', eventType, path.relative(dirPath, filename)),
-  );
-};
-
-function getToNode(filepath) {
-  // Ignore the drive for Windows paths.
-  if (filepath.match(/^[a-zA-Z]:\\/)) {
-    filepath = filepath.substring(2);
-  }
-
-  if (filepath.endsWith(path.sep)) {
-    filepath = filepath.slice(0, -1);
-  }
-  const parts = filepath.split(/[\/\\]/);
-  if (parts[0] !== '') {
-    throw new Error('Make sure all paths are absolute.');
-  }
-  let node = filesystem;
-  parts.slice(1).forEach(part => {
-    if (node && node.SYMLINK) {
-      node = getToNode(node.SYMLINK);
-    }
-    node = node[part];
-    if (node == null) {
-      const err = new Error(
-        `ENOENT: no such file or directory: \`${filepath}\``,
-      );
-      err.code = 'ENOENT';
-      throw err;
-    }
-  });
-
-  return node;
 }
 
+fs.__setMockFilesystem = setMockFilesystem;
+fs.mock = {clear: () => fs.reset()};
+
 module.exports = fs;
diff --git a/local-cli/__tests__/fs-mock-test.js b/local-cli/__tests__/fs-mock-test.js
deleted file mode 100644
index 4928f3bd9ecf..000000000000
--- a/local-cli/__tests__/fs-mock-test.js
+++ /dev/null
@@ -1,89 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @emails oncall+javascript_foundation
- * @flow
- * @format
- */
-
-'use strict';
-
-declare var jest: any;
-declare var describe: any;
-declare var beforeEach: any;
-declare var expect: any;
-declare var it: any;
-
-jest.mock('fs');
-
-const fs = require('fs');
-
-describe('fs mock', () => {
-  beforeEach(() => {
-    (fs: $FlowFixMe).mock.clear();
-  });
-
-  describe('writeFileSync()', () => {
-    it('stores content correctly', () => {
-      fs.writeFileSync('/test', 'foobar', 'utf8');
-      const content = fs.readFileSync('/test', 'utf8');
-      expect(content).toEqual('foobar');
-    });
-
-    it('fails on missing path', () => {
-      expect(() =>
-        fs.writeFileSync('/dir/test', 'foobar', 'utf8'),
-      ).toThrowError('ENOENT: no such file or directory');
-    });
-
-    it('properly normalizes paths', () => {
-      fs.writeFileSync('/test/foo/../bar/../../tadam', 'beep', 'utf8');
-      const content = fs.readFileSync('/glo/../tadam', 'utf8');
-      expect(content).toEqual('beep');
-    });
-  });
-
-  describe('mkdirSync()', () => {
-    it('creates folders that we can write files in', () => {
-      fs.mkdirSync('/dir', 0o777);
-      fs.writeFileSync('/dir/test', 'foobar', 'utf8');
-      const content = fs.readFileSync('/dir/test', 'utf8');
-      expect(content).toEqual('foobar');
-    });
-
-    it('does not erase directories', () => {
-      fs.mkdirSync('/dir', 0o777);
-      fs.writeFileSync('/dir/test', 'foobar', 'utf8');
-      fs.mkdirSync('/dir', 0o777);
-      const content = fs.readFileSync('/dir/test', 'utf8');
-      expect(content).toEqual('foobar');
-    });
-  });
-
-  describe('createWriteStream()', () => {
-    it('writes content', done => {
-      const stream = fs.createWriteStream('/test');
-      stream.write('hello, ');
-      stream.write('world');
-      stream.end('!');
-      process.nextTick(() => {
-        const content = fs.readFileSync('/test', 'utf8');
-        expect(content).toEqual('hello, world!');
-        done();
-      });
-    });
-  });
-
-  describe('writeSync()', () => {
-    it('writes content', () => {
-      const fd = fs.openSync('/test', 'w');
-      fs.writeSync(fd, 'hello, world!');
-      fs.closeSync(fd);
-      const content = fs.readFileSync('/test', 'utf8');
-      expect(content).toEqual('hello, world!');
-    });
-  });
-});
diff --git a/local-cli/link/__tests__/ios/writePlist.spec.js b/local-cli/link/__tests__/ios/writePlist.spec.js
index 0d2e086d0013..7e32b72aacc8 100644
--- a/local-cli/link/__tests__/ios/writePlist.spec.js
+++ b/local-cli/link/__tests__/ios/writePlist.spec.js
@@ -26,6 +26,9 @@ const infoPlistPath = path.join(__dirname, '../../__fixtures__/Info.plist');
 
 fs.readFileSync = jest.fn(() => readFileSync(projectPath).toString());
 
+const {writeFileSync} = fs;
+fs.writeFileSync = jest.fn(writeFileSync);
+
 const project = xcode.project('/Basic/project.pbxproj');
 
 const plist = {
diff --git a/package.json b/package.json
index d95183357888..9e2e48f7ecd7 100644
--- a/package.json
+++ b/package.json
@@ -170,6 +170,7 @@
     "metro": "^0.34.0",
     "metro-babel-register": "^0.34.2",
     "metro-core": "^0.34.0",
+    "metro-memory-fs": "^0.34.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 409dbd2057ad440afa08725bc8f8c5f69ed7abac Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 25 Apr 2018 09:43:27 -0700
Subject: [PATCH 0374/1109] Fix setMeasureFunction during cloning

Reviewed By: achen1

Differential Revision: D7753602

fbshipit-source-id: 284ec13b4cd784dfc61eeb0205f5779847854aac
---
 .../progressbar/ProgressBarShadowNode.java    | 22 +++++++++++--
 .../views/slider/ReactSliderManager.java      | 15 +++++++++
 .../views/switchview/ReactSwitchManager.java  | 16 +++++++++-
 .../textinput/ReactTextInputShadowNode.java   | 10 ++++--
 .../test/java/com/facebook/react/fabric/BUCK  |  1 +
 .../react/fabric/FabricUIManagerTest.java     | 31 ++++++++-----------
 6 files changed, 71 insertions(+), 24 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
index 367f4a90bd3d..779d647f658b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
@@ -7,6 +7,7 @@
 
 package com.facebook.react.views.progressbar;
 
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import javax.annotation.Nullable;
 
 import java.util.HashSet;
@@ -41,7 +42,7 @@ public ProgressBarShadowNode() {
     mHeight = new SparseIntArray();
     mWidth = new SparseIntArray();
     mMeasured = new HashSet<>();
-    setMeasureFunction(this);
+    initMeasureFunction();
   }
 
   public ProgressBarShadowNode(ProgressBarShadowNode node) {
@@ -49,11 +50,28 @@ public ProgressBarShadowNode(ProgressBarShadowNode node) {
     mWidth = node.mWidth.clone();
     mHeight = node.mHeight.clone();
     mMeasured = new HashSet<>(node.mMeasured);
+  }
+
+  @Override
+  public ReactShadowNodeImpl mutableCopyWithNewChildren() {
+    ProgressBarShadowNode node = (ProgressBarShadowNode) super.mutableCopyWithNewChildren();
+    node.initMeasureFunction();
+    return node;
+  }
+
+  private void initMeasureFunction() {
     setMeasureFunction(this);
   }
 
   @Override
-  protected ProgressBarShadowNode copy() {
+  public ReactShadowNodeImpl mutableCopy() {
+    ProgressBarShadowNode node = (ProgressBarShadowNode) super.mutableCopy();
+    node.initMeasureFunction();
+    return node;
+  }
+
+  @Override
+  public ProgressBarShadowNode copy() {
     return new ProgressBarShadowNode(this);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
index a73aa6ec72f6..10f714c94297 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
@@ -17,6 +17,7 @@
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.uimanager.LayoutShadowNode;
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.UIManagerModule;
@@ -63,6 +64,20 @@ private void initMeasureFunction() {
       setMeasureFunction(this);
     }
 
+    @Override
+    public ReactShadowNodeImpl mutableCopy() {
+      ReactSliderShadowNode reactShadowNode = (ReactSliderShadowNode) super.mutableCopy();
+      reactShadowNode.initMeasureFunction();
+      return reactShadowNode;
+    }
+
+    @Override
+    public ReactShadowNodeImpl mutableCopyWithNewChildren() {
+      ReactSliderShadowNode reactShadowNode = (ReactSliderShadowNode) super.mutableCopyWithNewChildren();
+      reactShadowNode.initMeasureFunction();
+      return reactShadowNode;
+    }
+
     @Override
     protected ReactSliderShadowNode copy() {
       return new ReactSliderShadowNode(this);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
index 1c9bff1ce1b9..70c5a5123e94 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
@@ -13,6 +13,7 @@
 import android.view.ViewGroup;
 import android.widget.CompoundButton;
 
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.yoga.YogaMeasureMode;
 import com.facebook.yoga.YogaMeasureFunction;
 import com.facebook.yoga.YogaNode;
@@ -48,13 +49,26 @@ private ReactSwitchShadowNode(ReactSwitchShadowNode node) {
       mWidth = node.mWidth;
       mHeight = node.mHeight;
       mMeasured = node.mMeasured;
-      initMeasureFunction();
     }
 
     private void initMeasureFunction() {
       setMeasureFunction(this);
     }
 
+    @Override
+    public ReactShadowNodeImpl mutableCopy() {
+      ReactSwitchShadowNode reactShadowNode = (ReactSwitchShadowNode) super.mutableCopy();
+      reactShadowNode.initMeasureFunction();
+      return reactShadowNode;
+    }
+
+    @Override
+    public ReactShadowNodeImpl mutableCopyWithNewChildren() {
+      ReactSwitchShadowNode reactShadowNode = (ReactSwitchShadowNode) super.mutableCopyWithNewChildren();
+      reactShadowNode.initMeasureFunction();
+      return reactShadowNode;
+    }
+
     @Override
     protected ReactSwitchShadowNode copy() {
       return new ReactSwitchShadowNode(this);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
index 1336314cdae3..7ff8d488d728 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
@@ -46,7 +46,7 @@ public ReactTextInputShadowNode() {
     mTextBreakStrategy = (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) ?
         0 : Layout.BREAK_STRATEGY_SIMPLE;
 
-    setMeasureFunction(this);
+    initMeasureFunction();
   }
 
   private ReactTextInputShadowNode(ReactTextInputShadowNode node) {
@@ -64,7 +64,7 @@ protected ReactTextInputShadowNode copy() {
   @Override
   public ReactTextInputShadowNode mutableCopy() {
     ReactTextInputShadowNode node = (ReactTextInputShadowNode) super.mutableCopy();
-    node.setMeasureFunction(this);
+    node.initMeasureFunction();
     ThemedReactContext themedContext = getThemedContext();
     if (themedContext != null) {
       node.setThemedContext(themedContext);
@@ -72,10 +72,14 @@ public ReactTextInputShadowNode mutableCopy() {
     return node;
   }
 
+  private void initMeasureFunction() {
+    setMeasureFunction(this);
+  }
+
   @Override
   public ReactTextInputShadowNode mutableCopyWithNewChildren() {
     ReactTextInputShadowNode node = (ReactTextInputShadowNode) super.mutableCopyWithNewChildren();
-    node.setMeasureFunction(this);
+    node.initMeasureFunction();
     ThemedReactContext themedContext = getThemedContext();
     if (themedContext != null) {
       node.setThemedContext(themedContext);
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
index 55eb26ebc3e6..faa1e3fa21a8 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
@@ -34,6 +34,7 @@ rn_robolectric_test(
         react_native_target("java/com/facebook/react/uimanager:uimanager"),
         react_native_target("java/com/facebook/react/views/text:text"),
         react_native_target("java/com/facebook/react/views/view:view"),
+        react_native_target("java/com/facebook/react/views/progressbar:progressbar"),
         react_native_tests_target("java/com/facebook/react/bridge:testhelpers"),
     ],
 )
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 32a0bbb40015..159352c776fe 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -2,41 +2,29 @@
 package com.facebook.react.fabric;
 
 import static org.fest.assertions.api.Assertions.assertThat;
-import static org.mockito.Matchers.any;
-import static org.mockito.Mockito.doAnswer;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
 
 import com.facebook.react.ReactRootView;
-import com.facebook.react.bridge.CatalystInstance;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReactTestHelper;
 import com.facebook.react.bridge.ReadableNativeMap;
-import com.facebook.react.common.ClearableSynchronizedPool;
-import com.facebook.react.fabric.FabricUIManager;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.Spacing;
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
+import com.facebook.react.views.progressbar.ProgressBarShadowNode;
 import com.facebook.react.views.text.ReactRawTextManager;
 import com.facebook.react.views.text.ReactRawTextShadowNode;
 import com.facebook.react.views.text.ReactTextViewManager;
 import com.facebook.react.views.view.ReactViewManager;
 import java.util.ArrayList;
 import java.util.Arrays;
-import java.util.Collections;
-import java.util.LinkedList;
 import java.util.List;
 import org.fest.assertions.data.Offset;
 import org.junit.Before;
 import org.junit.Test;
 import org.junit.runner.RunWith;
-import org.mockito.invocation.InvocationOnMock;
-import org.mockito.stubbing.Answer;
-import org.powermock.api.mockito.PowerMockito;
-import org.powermock.core.classloader.annotations.PrepareForTest;
 import org.robolectric.RobolectricTestRunner;
 import org.robolectric.RuntimeEnvironment;
 
@@ -52,11 +40,10 @@ public class FabricUIManagerTest {
   @Before
   public void setUp() throws Exception {
     mNextReactTag = 2;
-    mThemedReactContext = mock(ThemedReactContext.class);
-    CatalystInstance catalystInstance = ReactTestHelper.createMockCatalystInstance();
-    ReactApplicationContext reactContext =
-        new ReactApplicationContext(RuntimeEnvironment.application);
-    reactContext.initializeWithInstance(catalystInstance);
+    ReactApplicationContext reactContext = new ReactApplicationContext(RuntimeEnvironment.application);
+    reactContext.initializeWithInstance(ReactTestHelper.createMockCatalystInstance());
+    mThemedReactContext = new ThemedReactContext(reactContext, reactContext);
+
     List<ViewManager> viewManagers =
         Arrays.<ViewManager>asList(
             new ReactViewManager(), new ReactTextViewManager(), new ReactRawTextManager());
@@ -143,6 +130,14 @@ public void testCloneVirtualNode() {
     assertThat(clonedNode).isNotEqualTo(node);
   }
 
+  @Test
+  public void testLayoutProgressBarAfterClonning() {
+    ProgressBarShadowNode node = new ProgressBarShadowNode();
+    node.setThemedContext(mThemedReactContext);
+    ProgressBarShadowNode clone = (ProgressBarShadowNode) node.mutableCopy();
+    clone.calculateLayout();
+  }
+
   @Test
   public void testCloneNodeWithNewChildren() {
     ReactShadowNode node = createViewNode();

From a62aac5952c2d94120b7ed63d518da2bfbf4316d Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 25 Apr 2018 09:43:32 -0700
Subject: [PATCH 0375/1109] Fix rootview layout when using flex

Reviewed By: achen1

Differential Revision: D7753463

fbshipit-source-id: 5d2d70f9b5130ffe3b59a5364c589f437988ef37
---
 .../react/fabric/FabricUIManager.java         | 42 ++++++++++++++++---
 1 file changed, 37 insertions(+), 5 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index cd6045f00d88..ce8046092b29 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -14,10 +14,12 @@
 import android.util.Log;
 import android.view.View;
 import com.facebook.infer.annotation.Assertions;
+import com.facebook.react.bridge.GuardedRunnable;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.ReadableNativeMap;
 import com.facebook.react.bridge.UIManager;
+import com.facebook.react.common.ReactConstants;
 import com.facebook.react.common.annotations.VisibleForTesting;
 import com.facebook.react.modules.i18nmanager.I18nUtil;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
@@ -33,6 +35,7 @@
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 import java.util.ArrayList;
+import java.util.LinkedList;
 import java.util.List;
 import javax.annotation.Nullable;
 
@@ -248,11 +251,12 @@ public void appendChildToSet(List<ReactShadowNode> childList, ReactShadowNode ch
     childList.add(child);
   }
 
-  public synchronized void completeRoot(int rootTag, List<ReactShadowNode> childList) {
-    if (DEBUG) {
-      Log.d(TAG, "completeRoot rootTag: " + rootTag + ", childList: " + childList);
-    }
+  public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNode> childList) {
     try {
+      childList = childList == null ? new LinkedList<ReactShadowNode>() : childList;
+      if (DEBUG) {
+        Log.d(TAG, "completeRoot rootTag: " + rootTag + ", childList: " + childList);
+      }
       ReactShadowNode currentRootShadowNode = getRootNode(rootTag);
       Assertions.assertNotNull(
           currentRootShadowNode,
@@ -340,7 +344,7 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
   @Override
   public <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(
       final T rootView) {
-    int rootTag = ReactRootViewTagGenerator.getNextRootViewTag();
+    final int rootTag = ReactRootViewTagGenerator.getNextRootViewTag();
     ThemedReactContext themedRootContext =
         new ThemedReactContext(mReactApplicationContext, rootView.getContext());
 
@@ -350,11 +354,39 @@ public <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootVi
     int heightMeasureSpec = rootView.getHeightMeasureSpec();
     updateRootView(rootShadowNode, widthMeasureSpec, heightMeasureSpec);
 
+    rootView.setOnSizeChangedListener(
+      new SizeMonitoringFrameLayout.OnSizeChangedListener() {
+        @Override
+        public void onSizeChanged(final int width, final int height, int oldW, int oldH) {
+          updateRootSize(rootTag, width, height);
+        }
+      });
+
     mRootShadowNodeRegistry.registerNode(rootShadowNode);
     mUIViewOperationQueue.addRootView(rootTag, rootView, themedRootContext);
     return rootTag;
   }
 
+  /**
+   * Updates the root view size and re-render the RN surface.
+   *
+   * //TODO: change synchronization to integrate with new #render loop.
+   */
+  private synchronized void updateRootSize(int rootTag, int newWidth, int newHeight) {
+    ReactShadowNode rootNode = mRootShadowNodeRegistry.getNode(rootTag);
+    if (rootNode == null) {
+      Log.w(
+        ReactConstants.TAG,
+        "Tried to update size of non-existent tag: " + rootTag);
+      return;
+    }
+    int newWidthSpec = View.MeasureSpec.makeMeasureSpec(newWidth, View.MeasureSpec.EXACTLY);
+    int newHeightSpec = View.MeasureSpec.makeMeasureSpec(newHeight, View.MeasureSpec.EXACTLY);
+    updateRootView(rootNode, newWidthSpec, newHeightSpec);
+
+    completeRoot(rootTag, rootNode.getChildrenList());
+  }
+
   public void removeRootView(int rootTag) {
     mRootShadowNodeRegistry.removeNode(rootTag);
   }

From a3a98eb1c7fa0054a236d45421393874ce8ce558 Mon Sep 17 00:00:00 2001
From: Mika Andrianarijaona <mikaoelitiana@gmail.com>
Date: Wed, 25 Apr 2018 23:27:48 -0700
Subject: [PATCH 0376/1109] BREAKING - default underlineColorAndroid to
 transparent

Summary:
Set default `underlineColorAndroid` to `transparent`.
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

Fixes #18938

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Use a TextInput in a component without defining `underlineColorAndroid`, the underline color should be transparent.

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [BREAKING] [TextInput] - set default underlineColorAndroid to transparent

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18988

Reviewed By: mdvacca

Differential Revision: D7765569

Pulled By: yungsters

fbshipit-source-id: f7ad57a46fc0d18b47271ca39faae8c635995fbb
---
 Libraries/Components/TextInput/TextInput.js | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index e887b07438f4..f0cf5b955e96 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -637,6 +637,7 @@ const TextInput = createReactClass({
   getDefaultProps(): Object {
     return {
       allowFontScaling: true,
+      underlineColorAndroid: 'transparent',
     };
   },
   /**

From c656fa80724489f4e92695ddb594bb7c6af9d572 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rub=C3=A9n=20Norte?= <rubennorte@fb.com>
Date: Thu, 26 Apr 2018 05:56:48 -0700
Subject: [PATCH 0377/1109] Removed some @providesModule tags and references

Reviewed By: jeanlauliac

Differential Revision: D7758118

fbshipit-source-id: 556bdcac54f92e3143d98e0ae3d9016a5b7de2bd
---
 Libraries/Components/ScrollResponder.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/Components/ScrollResponder.js b/Libraries/Components/ScrollResponder.js
index 93431293a348..6a38cc7523dd 100644
--- a/Libraries/Components/ScrollResponder.js
+++ b/Libraries/Components/ScrollResponder.js
@@ -574,7 +574,7 @@ const ScrollResponderMixin = {
    * - willHide {startCoordinates, endCoordinates} several times
    * - didHide several times
    *
-   * The `ScrollResponder` providesModule callbacks for each of these events.
+   * The `ScrollResponder` module callbacks for each of these events.
    * Even though any user could have easily listened to keyboard events
    * themselves, using these `props` callbacks ensures that ordering of events
    * is consistent - and not dependent on the order that the keyboard events are

From 34ee828b2e8e37b5c54bb9664139e2c791af6be7 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Thu, 26 Apr 2018 06:05:16 -0700
Subject: [PATCH 0378/1109] Bump metro@0.35.0

Reviewed By: mjesun

Differential Revision: D7759224

fbshipit-source-id: d21a371c196ff5c6e691fb7cce8c73dade02d385
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 9e2e48f7ecd7..63695f29a6a9 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.34.0",
-    "metro-babel-register": "^0.34.2",
-    "metro-core": "^0.34.0",
-    "metro-memory-fs": "^0.34.0",
+    "metro": "^0.35.0",
+    "metro-babel-register": "^0.35.0",
+    "metro-core": "^0.35.0",
+    "metro-memory-fs": "^0.35.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From eeab57aa26385656cc69f057c9db5c7f4da293ff Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rub=C3=A9n=20Norte?= <rubennorte@fb.com>
Date: Thu, 26 Apr 2018 07:48:16 -0700
Subject: [PATCH 0379/1109] Removed last traces of @providesModule from React
 Native

Reviewed By: jeanlauliac

Differential Revision: D7774204

fbshipit-source-id: d80e4b4d1dc5fe7686aff7340368d0f2670e449f
---
 CONTRIBUTING.md                                         | 2 --
 scripts/versiontemplates/ReactNativeVersion.js.template | 1 -
 2 files changed, 3 deletions(-)

diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index bc151d02603d..25ba2d5c1e1d 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -147,8 +147,6 @@ Copy and paste this to the top of your new file(s):
  */
 ```
 
-If you've added a new module, add a `@providesModule <moduleName>` at the end of the comment. This will allow the haste package manager to find it.
-
 #### Contributor License Agreement (CLA)
 
 In order to accept your pull request, we need you to submit a CLA. You only need to do this once, so if you've done this for another Facebook open source project, you're good to go. If you are submitting a pull request for the first time, the Facebook GitHub Bot will reply with a link to the CLA form. You may also [complete your CLA here](https://code.facebook.com/cla).
diff --git a/scripts/versiontemplates/ReactNativeVersion.js.template b/scripts/versiontemplates/ReactNativeVersion.js.template
index 1f1ccdd741dd..80f4b280a86f 100644
--- a/scripts/versiontemplates/ReactNativeVersion.js.template
+++ b/scripts/versiontemplates/ReactNativeVersion.js.template
@@ -7,7 +7,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ReactNativeVersion
  */
 
 exports.version = {

From de08f4ab6c799e9610688e72be7b4cacbc15472b Mon Sep 17 00:00:00 2001
From: Brian Vaughn <bvaughn@fb.com>
Date: Thu, 26 Apr 2018 08:46:32 -0700
Subject: [PATCH 0380/1109] Blacklist FB RN renderer for RN GitHub OSS tests

Reviewed By: rubennorte

Differential Revision: D7774634

fbshipit-source-id: f293e897e31daf1e7230f55cc932c25ee6f8558a
---
 jest/hasteImpl.js | 1 +
 1 file changed, 1 insertion(+)

diff --git a/jest/hasteImpl.js b/jest/hasteImpl.js
index cb5ac4a049c4..ec838a1d47d0 100644
--- a/jest/hasteImpl.js
+++ b/jest/hasteImpl.js
@@ -16,6 +16,7 @@ const ROOT = path.join(__dirname, '..');
 const BLACKLISTED_PATTERNS/*: Array<RegExp>*/ = [
   /.*\/__(mocks|tests)__\/.*/,
   /^Libraries\/Animated\/src\/polyfills\/.*/,
+  /^Libraries\/Renderer\/fb\/.*/,
 ];
 
 const WHITELISTED_PREFIXES/*: Array<string>*/ = [

From 2e7dbc82b3e604de2195790085c2a025dc5f06a6 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Thu, 26 Apr 2018 14:17:09 -0700
Subject: [PATCH 0381/1109] Center align image in a span

Reviewed By: achen1

Differential Revision: D7750114

fbshipit-source-id: 84b4eaa2da01ac9c49a569d37f7a32eab1e5aca8
---
 .../frescosupport/FrescoBasedReactTextInlineImageSpan.java  | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
index 39cd24c6fd3c..08d3ed9d2f76 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/FrescoBasedReactTextInlineImageSpan.java
@@ -160,8 +160,10 @@ public void draw(
 
     canvas.save();
 
-    // Align to baseline by default
-    int transY = y - mDrawable.getBounds().bottom;
+    // Align to center
+    int fontHeight = (int)(paint.descent() - paint.ascent());
+    int centerY = y + (int)paint.descent() - fontHeight / 2;
+    int transY = centerY - (mDrawable.getBounds().bottom - mDrawable.getBounds().top) / 2;
 
     canvas.translate(x, transY);
     mDrawable.draw(canvas);

From bd91eaf6647d94d216e49520ff75e7a962084078 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:27 -0700
Subject: [PATCH 0382/1109] Fabric/Text: ShadowNode::clone() - dynamic
 self-cloning mechanism

Summary:
The previous approach simply didn't work. :(
As you might notice, in previous implementation of ViewShadowNode::cloneAndReplaceChild we used `ViewShadowNode` class for cloning `childNode`, and this is incorrect becasue `childNode` might be instance of any class.

Reviewed By: fkgozali

Differential Revision: D7595016

fbshipit-source-id: 2215414926f2f7a2e2fd05ca2d065f10d6d32b74
---
 .../ConcreteComponentDescriptor.h             | 22 +++++++++++-
 .../core/shadownode/ConcreteShadowNode.h      |  6 ++--
 .../fabric/core/shadownode/ShadowNode.cpp     | 13 ++++++-
 .../fabric/core/shadownode/ShadowNode.h       | 23 ++++++++++--
 .../fabric/core/tests/ShadowNodeTest.cpp      | 35 +++++++++++++++++++
 ReactCommon/fabric/view/ViewShadowNode.cpp    | 19 +++++-----
 ReactCommon/fabric/view/ViewShadowNode.h      |  3 +-
 7 files changed, 106 insertions(+), 15 deletions(-)

diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 8739d849a4a1..2e2ee37fd208 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -8,6 +8,7 @@
 #pragma once
 
 #include <memory>
+#include <functional>
 
 #include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/Props.h>
@@ -40,7 +41,14 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     const InstanceHandle &instanceHandle,
     const SharedProps &props
   ) const override {
-    return std::make_shared<ShadowNodeT>(tag, rootTag, instanceHandle, std::static_pointer_cast<const ConcreteProps>(props));
+    return std::make_shared<ShadowNodeT>(
+      tag,
+      rootTag,
+      instanceHandle,
+      std::static_pointer_cast<const ConcreteProps>(props),
+      ShadowNode::emptySharedShadowNodeSharedList(),
+      getCloneFunction()
+    );
   }
 
   SharedShadowNode cloneShadowNode(
@@ -67,6 +75,18 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     return ShadowNodeT::Props(rawProps, props);
   };
 
+private:
+  mutable ShadowNodeCloneFunction cloneFunction_;
+
+  ShadowNodeCloneFunction getCloneFunction() const {
+    if (!cloneFunction_) {
+      cloneFunction_ = [this](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedShadowNodeSharedList &children) {
+        return this->cloneShadowNode(shadowNode, props, children);
+      };
+    }
+
+    return cloneFunction_;
+  }
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index 278d448708c8..9a18cf7e1edc 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -51,14 +51,16 @@ class ConcreteShadowNode: public ShadowNode {
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
     const SharedConcreteProps &props = ConcreteShadowNode::defaultSharedProps(),
-    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList()
+    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList(),
+    const ShadowNodeCloneFunction &cloneFunction = nullptr
   ):
     ShadowNode(
       tag,
       rootTag,
       instanceHandle,
       (SharedProps)props,
-      children
+      children,
+      cloneFunction
     ) {};
 
   ConcreteShadowNode(
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index e7c6b68f22ef..f1272c32696f 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -25,13 +25,15 @@ ShadowNode::ShadowNode(
   const Tag &rootTag,
   const InstanceHandle &instanceHandle,
   const SharedProps &props,
-  const SharedShadowNodeSharedList &children
+  const SharedShadowNodeSharedList &children,
+  const ShadowNodeCloneFunction &cloneFunction
 ):
   tag_(tag),
   rootTag_(rootTag),
   instanceHandle_(instanceHandle),
   props_(props),
   children_(std::make_shared<SharedShadowNodeList>(*children)),
+  cloneFunction_(cloneFunction),
   revision_(1) {}
 
 ShadowNode::ShadowNode(
@@ -45,8 +47,17 @@ ShadowNode::ShadowNode(
   props_(props ? props : shadowNode->props_),
   children_(std::make_shared<SharedShadowNodeList>(*(children ? children : shadowNode->children_))),
   sourceNode_(shadowNode),
+  cloneFunction_(shadowNode->cloneFunction_),
   revision_(shadowNode->revision_ + 1) {}
 
+SharedShadowNode ShadowNode::clone(
+  const SharedProps &props,
+  const SharedShadowNodeSharedList &children
+) const {
+  assert(cloneFunction_);
+  return cloneFunction_(shared_from_this(), props_, children_);
+}
+
 #pragma mark - Getters
 
 SharedShadowNodeSharedList ShadowNode::getChildren() const {
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index a5b8a2ff9da6..e83e62276342 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -8,6 +8,7 @@
 #pragma once
 
 #include <string>
+#include <memory>
 #include <vector>
 
 #include <fabric/core/Props.h>
@@ -26,9 +27,12 @@ using SharedShadowNodeSharedList = std::shared_ptr<const SharedShadowNodeList>;
 using SharedShadowNodeUnsharedList = std::shared_ptr<SharedShadowNodeList>;
 using WeakShadowNode = std::weak_ptr<const ShadowNode>;
 
+using ShadowNodeCloneFunction = std::function<SharedShadowNode(SharedShadowNode shadowNode, SharedProps props, SharedShadowNodeSharedList children)>;
+
 class ShadowNode:
   public virtual Sealable,
-  public virtual DebugStringConvertible {
+  public virtual DebugStringConvertible,
+  public std::enable_shared_from_this<ShadowNode> {
 public:
   static SharedShadowNodeSharedList emptySharedShadowNodeSharedList();
 
@@ -39,7 +43,8 @@ class ShadowNode:
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
     const SharedProps &props = SharedProps(),
-    const SharedShadowNodeSharedList &children = SharedShadowNodeSharedList()
+    const SharedShadowNodeSharedList &children = SharedShadowNodeSharedList(),
+    const ShadowNodeCloneFunction &cloneFunction = nullptr
   );
 
   ShadowNode(
@@ -48,6 +53,14 @@ class ShadowNode:
     const SharedShadowNodeSharedList &children = nullptr
   );
 
+  /*
+   * Clones the shadow node using stored `cloneFunction`.
+   */
+  SharedShadowNode clone(
+    const SharedProps &props = nullptr,
+    const SharedShadowNodeSharedList &children = nullptr
+  ) const;
+
 #pragma mark - Getters
 
   virtual ComponentHandle getComponentHandle() const = 0;
@@ -112,6 +125,12 @@ class ShadowNode:
 
 private:
 
+  /*
+   * A reference to a cloning function that understands how to clone
+   * the specific type of ShadowNode.
+   */
+  ShadowNodeCloneFunction cloneFunction_;
+
   /*
    * A number of the generation of the ShadowNode instance;
    * is used and useful for debug-printing purposes *only*.
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index 168cf4886985..8c8204684b78 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -115,3 +115,38 @@ TEST(ShadowNodeTest, handleSourceNode) {
   ASSERT_EQ(nodeThirdGeneration->getSourceNode(), nodeSecondGeneration);
   ASSERT_EQ(nodeSecondGeneration->getSourceNode(), nodeFirstGeneration);
 }
+
+TEST(ShadowNodeTest, handleCloneFunction) {
+  auto firstNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+
+  // The shadow node is not clonable if `cloneFunction` is not provided,
+  ASSERT_DEATH_IF_SUPPORTED(firstNode->clone(), "cloneFunction_");
+
+  auto secondNode = std::make_shared<TestShadowNode>(
+    9,
+    1,
+    (void *)NULL,
+    std::make_shared<const TestProps>(),
+    ShadowNode::emptySharedShadowNodeSharedList(),
+    [](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedShadowNodeSharedList &children) {
+      return std::make_shared<const TestShadowNode>(
+        std::static_pointer_cast<const TestShadowNode>(shadowNode),
+        props,
+        children
+      );
+    }
+  );
+
+  auto secondNodeClone = secondNode->clone();
+
+  // Those two nodes are *not* same.
+  ASSERT_NE(secondNode, secondNodeClone);
+
+  // `secondNodeClone` is an instance of `TestShadowNode`.
+  ASSERT_NE(std::dynamic_pointer_cast<const TestShadowNode>(secondNodeClone), nullptr);
+
+  // Both nodes have same content.
+  ASSERT_EQ(secondNode->getTag(), secondNodeClone->getTag());
+  ASSERT_EQ(secondNode->getRootTag(), secondNodeClone->getRootTag());
+  ASSERT_EQ(secondNode->getProps(), secondNodeClone->getProps());
+}
diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/view/ViewShadowNode.cpp
index 111d220ec12d..51d4be23ba38 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.cpp
+++ b/ReactCommon/fabric/view/ViewShadowNode.cpp
@@ -21,14 +21,16 @@ ViewShadowNode::ViewShadowNode(
   const Tag &rootTag,
   const InstanceHandle &instanceHandle,
   const SharedViewProps &props,
-  const SharedShadowNodeSharedList &children
+  const SharedShadowNodeSharedList &children,
+  const ShadowNodeCloneFunction &cloneFunction
 ):
   ConcreteShadowNode(
     tag,
     rootTag,
     instanceHandle,
     props,
-    children
+    children,
+    cloneFunction
   ),
   AccessibleShadowNode(
     props
@@ -92,9 +94,9 @@ SharedLayoutableShadowNodeList ViewShadowNode::getLayoutableChildNodes() const {
 SharedLayoutableShadowNode ViewShadowNode::cloneAndReplaceChild(const SharedLayoutableShadowNode &child) {
   ensureUnsealed();
 
-  auto viewShadowNodeChild = std::dynamic_pointer_cast<const ViewShadowNode>(child);
-  assert(viewShadowNodeChild);
-  auto viewShadowNodeChildClone = std::make_shared<ViewShadowNode>(viewShadowNodeChild);
+  auto childShadowNode = std::dynamic_pointer_cast<const ShadowNode>(child);
+  assert(childShadowNode);
+  auto childShadowNodeClone = childShadowNode->clone();
 
   // This is overloading of `SharedLayoutableShadowNode::cloneAndReplaceChild`,
   // the method is used to clone some node as a preparation for future mutation
@@ -107,10 +109,11 @@ SharedLayoutableShadowNode ViewShadowNode::cloneAndReplaceChild(const SharedLayo
   // In other words, if we don't compensate this change here,
   // the Diffing algorithm will compare wrong trees
   // ("new-but-not-laid-out-yet vs. new" instead of "committed vs. new").
-  viewShadowNodeChildClone->shallowSourceNode();
+  auto nonConstChildShadowNodeClone = std::const_pointer_cast<ShadowNode>(childShadowNodeClone);
+  nonConstChildShadowNodeClone->shallowSourceNode();
 
-  ShadowNode::replaceChild(viewShadowNodeChild, viewShadowNodeChildClone);
-  return std::static_pointer_cast<const LayoutableShadowNode>(viewShadowNodeChildClone);
+  ShadowNode::replaceChild(childShadowNode, childShadowNodeClone);
+  return std::dynamic_pointer_cast<const LayoutableShadowNode>(childShadowNodeClone);
 }
 
 #pragma mark - Equality
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/view/ViewShadowNode.h
index 230aad5694fe..5809430df67b 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.h
+++ b/ReactCommon/fabric/view/ViewShadowNode.h
@@ -35,7 +35,8 @@ class ViewShadowNode:
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
     const SharedViewProps &props = ViewShadowNode::defaultSharedProps(),
-    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList()
+    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList(),
+    const ShadowNodeCloneFunction &cloneFunction = nullptr
   );
 
   ViewShadowNode(

From f72df7a6e71fcc32f1cc33a8427f548c51e9b759 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:29 -0700
Subject: [PATCH 0383/1109] Fabric/Text: ConcreteViewShadowNode - base class
 for all `View`-like shadow nodes

Summary: Quite trivial split ViewShadowNode into concrete class and templace class.

Reviewed By: fkgozali

Differential Revision: D7595017

fbshipit-source-id: b1ac1dfa187e5cfd0a34fbf84b3e1ae308bb0c99
---
 .../fabric/view/ConcreteViewShadowNode.h      | 167 ++++++++++++++++++
 ReactCommon/fabric/view/ViewShadowNode.cpp    | 126 -------------
 ReactCommon/fabric/view/ViewShadowNode.h      |  48 +----
 3 files changed, 173 insertions(+), 168 deletions(-)
 create mode 100644 ReactCommon/fabric/view/ConcreteViewShadowNode.h

diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
new file mode 100644
index 000000000000..320fbb0d4eb5
--- /dev/null
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -0,0 +1,167 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ConcreteShadowNode.h>
+#include <fabric/core/LayoutableShadowNode.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/view/AccessibleShadowNode.h>
+#include <fabric/view/ViewProps.h>
+#include <fabric/view/YogaLayoutableShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Template for all <View>-like classes (classes which have all same props
+ * as <View> and similar basic behaviour).
+ * For example: <Paragraph>, <Image>, but not <Text>, <RawText>.
+ */
+template <typename ViewPropsT>
+class ConcreteViewShadowNode:
+  public ConcreteShadowNode<ViewPropsT>,
+  public AccessibleShadowNode,
+  public YogaLayoutableShadowNode {
+
+  static_assert(std::is_base_of<ViewProps, ViewPropsT>::value, "ViewPropsT must be a descendant of ViewProps");
+  static_assert(std::is_base_of<YogaStylableProps, ViewPropsT>::value, "ViewPropsT must be a descendant of YogaStylableProps");
+  static_assert(std::is_base_of<AccessibilityProps, ViewPropsT>::value, "ViewPropsT must be a descendant of AccessibilityProps");
+
+public:
+
+  using ConcreteViewProps = ViewPropsT;
+  using SharedConcreteViewProps = std::shared_ptr<const ViewPropsT>;
+  using SharedConcreteViewShadowNode = std::shared_ptr<const ConcreteViewShadowNode>;
+
+  ConcreteViewShadowNode(
+    const Tag &tag,
+    const Tag &rootTag,
+    const InstanceHandle &instanceHandle,
+    const SharedViewProps &props = ConcreteViewShadowNode::defaultSharedProps(),
+    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList(),
+    const ShadowNodeCloneFunction &cloneFunction = nullptr
+  ):
+    ConcreteShadowNode<ViewPropsT>(
+      tag,
+      rootTag,
+      instanceHandle,
+      props,
+      children,
+      cloneFunction
+    ),
+    AccessibleShadowNode(
+      props
+    ),
+    YogaLayoutableShadowNode(
+      props,
+      children
+    ) {};
+
+  ConcreteViewShadowNode(
+    const SharedConcreteViewShadowNode &shadowNode,
+    const SharedViewProps &props = nullptr,
+    const SharedShadowNodeSharedList &children = nullptr
+  ):
+    ConcreteShadowNode<ViewPropsT>(
+      shadowNode,
+      props,
+      children
+    ),
+    AccessibleShadowNode(
+      shadowNode,
+      props
+    ),
+    YogaLayoutableShadowNode(
+      shadowNode,
+      props,
+      children
+    ) {};
+
+  void appendChild(const SharedShadowNode &child) {
+    ensureUnsealed();
+
+    ShadowNode::appendChild(child);
+
+    auto yogaLayoutableChild = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(child);
+    if (yogaLayoutableChild) {
+      YogaLayoutableShadowNode::appendChild(yogaLayoutableChild);
+    }
+  }
+
+  SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child) override {
+    ensureUnsealed();
+
+    auto childShadowNode = std::dynamic_pointer_cast<const ShadowNode>(child);
+    assert(childShadowNode);
+    auto childShadowNodeClone = childShadowNode->clone();
+
+    // This is overloading of `SharedLayoutableShadowNode::cloneAndReplaceChild`,
+    // the method is used to clone some node as a preparation for future mutation
+    // caused by relayout.
+    // Because those changes are not requested by UIManager, they add a layer
+    // of node generation (between the committed stage and new proposed stage).
+    // That additional layer confuses the Diffing algorithm which uses
+    // `sourceNode` for referencing the previous (aka committed) stage
+    // of the tree to produce mutation instructions.
+    // In other words, if we don't compensate this change here,
+    // the Diffing algorithm will compare wrong trees
+    // ("new-but-not-laid-out-yet vs. new" instead of "committed vs. new").
+    auto nonConstChildShadowNodeClone = std::const_pointer_cast<ShadowNode>(childShadowNodeClone);
+    nonConstChildShadowNodeClone->shallowSourceNode();
+
+    ShadowNode::replaceChild(childShadowNode, childShadowNodeClone);
+    return std::dynamic_pointer_cast<const LayoutableShadowNode>(childShadowNodeClone);
+  }
+
+#pragma mark - Equality
+
+  bool operator==(const ShadowNode& rhs) const override {
+    if (!ShadowNode::operator==(rhs)) {
+      return false;
+    }
+
+    auto &&other = static_cast<const ConcreteViewShadowNode&>(rhs);
+    return getLayoutMetrics() == other.getLayoutMetrics();
+  }
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override {
+    SharedDebugStringConvertibleList list = {};
+
+    auto basePropsList = ShadowNode::getDebugProps();
+    std::move(basePropsList.begin(), basePropsList.end(), std::back_inserter(list));
+
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("layout", "", YogaLayoutableShadowNode::getDebugProps()));
+
+    return list;
+  }
+
+private:
+
+#pragma mark - LayoutableShadowNode
+
+  SharedLayoutableShadowNodeList getLayoutableChildNodes() const override {
+    SharedLayoutableShadowNodeList sharedLayoutableShadowNodeList = {};
+    for (auto child : *ShadowNode::children_) {
+      const SharedLayoutableShadowNode layoutableShadowNode = std::dynamic_pointer_cast<const LayoutableShadowNode>(child);
+      if (!layoutableShadowNode) {
+        continue;
+      }
+
+      sharedLayoutableShadowNodeList.push_back(layoutableShadowNode);
+    }
+
+    return sharedLayoutableShadowNodeList;
+  }
+
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/view/ViewShadowNode.cpp
index 51d4be23ba38..2bf7f30d76ae 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.cpp
+++ b/ReactCommon/fabric/view/ViewShadowNode.cpp
@@ -7,138 +7,12 @@
 
 #include "ViewShadowNode.h"
 
-#include <algorithm>
-
-#include <fabric/debug/DebugStringConvertibleItem.h>
-
 namespace facebook {
 namespace react {
 
-#pragma mark - Constructors
-
-ViewShadowNode::ViewShadowNode(
-  const Tag &tag,
-  const Tag &rootTag,
-  const InstanceHandle &instanceHandle,
-  const SharedViewProps &props,
-  const SharedShadowNodeSharedList &children,
-  const ShadowNodeCloneFunction &cloneFunction
-):
-  ConcreteShadowNode(
-    tag,
-    rootTag,
-    instanceHandle,
-    props,
-    children,
-    cloneFunction
-  ),
-  AccessibleShadowNode(
-    props
-  ),
-  YogaLayoutableShadowNode(
-    props,
-    children
-  ) {};
-
-ViewShadowNode::ViewShadowNode(
-  const SharedViewShadowNode &shadowNode,
-  const SharedViewProps &props,
-  const SharedShadowNodeSharedList &children
-):
-  ConcreteShadowNode(
-    shadowNode,
-    props,
-    children
-  ),
-  AccessibleShadowNode(
-    shadowNode,
-    props
-  ),
-  YogaLayoutableShadowNode(
-    shadowNode,
-    props,
-    children
-  ) {};
-
 ComponentName ViewShadowNode::getComponentName() const {
   return ComponentName("View");
 }
 
-void ViewShadowNode::appendChild(const SharedShadowNode &child) {
-  ensureUnsealed();
-
-  ShadowNode::appendChild(child);
-
-  auto yogaLayoutableChild = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(child);
-  if (yogaLayoutableChild) {
-    YogaLayoutableShadowNode::appendChild(yogaLayoutableChild);
-  }
-}
-
-#pragma mark - YogaLayoutableShadowNode
-
-SharedLayoutableShadowNodeList ViewShadowNode::getLayoutableChildNodes() const {
-  SharedLayoutableShadowNodeList sharedLayoutableShadowNodeList = {};
-  for (auto child : *children_) {
-    const SharedLayoutableShadowNode layoutableShadowNode = std::dynamic_pointer_cast<const LayoutableShadowNode>(child);
-    if (!layoutableShadowNode) {
-      continue;
-    }
-
-    sharedLayoutableShadowNodeList.push_back(layoutableShadowNode);
-  }
-
-  return sharedLayoutableShadowNodeList;
-}
-
-SharedLayoutableShadowNode ViewShadowNode::cloneAndReplaceChild(const SharedLayoutableShadowNode &child) {
-  ensureUnsealed();
-
-  auto childShadowNode = std::dynamic_pointer_cast<const ShadowNode>(child);
-  assert(childShadowNode);
-  auto childShadowNodeClone = childShadowNode->clone();
-
-  // This is overloading of `SharedLayoutableShadowNode::cloneAndReplaceChild`,
-  // the method is used to clone some node as a preparation for future mutation
-  // caused by relayout.
-  // Because those changes are not requested by UIManager, they add a layer
-  // of node generation (between the committed stage and new proposed stage).
-  // That additional layer confuses the Diffing algorithm which uses
-  // `sourceNode` for referencing the previous (aka committed) stage
-  // of the tree to produce mutation instructions.
-  // In other words, if we don't compensate this change here,
-  // the Diffing algorithm will compare wrong trees
-  // ("new-but-not-laid-out-yet vs. new" instead of "committed vs. new").
-  auto nonConstChildShadowNodeClone = std::const_pointer_cast<ShadowNode>(childShadowNodeClone);
-  nonConstChildShadowNodeClone->shallowSourceNode();
-
-  ShadowNode::replaceChild(childShadowNode, childShadowNodeClone);
-  return std::dynamic_pointer_cast<const LayoutableShadowNode>(childShadowNodeClone);
-}
-
-#pragma mark - Equality
-
-bool ViewShadowNode::operator==(const ShadowNode& rhs) const {
-  if (!ShadowNode::operator==(rhs)) {
-    return false;
-  }
-
-  auto &&other = static_cast<const ViewShadowNode&>(rhs);
-  return getLayoutMetrics() == other.getLayoutMetrics();
-}
-
-#pragma mark - DebugStringConvertible
-
-SharedDebugStringConvertibleList ViewShadowNode::getDebugProps() const {
-  SharedDebugStringConvertibleList list = {};
-
-  auto basePropsList = ShadowNode::getDebugProps();
-  std::move(basePropsList.begin(), basePropsList.end(), std::back_inserter(list));
-
-  list.push_back(std::make_shared<DebugStringConvertibleItem>("layout", "", YogaLayoutableShadowNode::getDebugProps()));
-
-  return list;
-}
-
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/view/ViewShadowNode.h
index 5809430df67b..d063b0196fc3 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.h
+++ b/ReactCommon/fabric/view/ViewShadowNode.h
@@ -7,12 +7,10 @@
 
 #pragma once
 
-#include <fabric/core/ConcreteShadowNode.h>
-#include <fabric/core/LayoutableShadowNode.h>
-#include <fabric/core/ShadowNode.h>
-#include <fabric/view/AccessibleShadowNode.h>
+#include <memory>
+
 #include <fabric/view/ViewProps.h>
-#include <fabric/view/YogaLayoutableShadowNode.h>
+#include <fabric/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
 namespace react {
@@ -21,48 +19,14 @@ class ViewShadowNode;
 
 using SharedViewShadowNode = std::shared_ptr<const ViewShadowNode>;
 
-class ViewShadowNode:
-  public ConcreteShadowNode<ViewProps>,
-  public AccessibleShadowNode,
-  public YogaLayoutableShadowNode {
-
-  static_assert(std::is_base_of<YogaStylableProps, ViewProps>::value, "ViewProps must be a descendant of YogaStylableProps");
-  static_assert(std::is_base_of<AccessibilityProps, ViewProps>::value, "ViewProps must be a descendant of AccessibilityProps");
+class ViewShadowNode final:
+  public ConcreteViewShadowNode<ViewProps> {
 
 public:
-  ViewShadowNode(
-    const Tag &tag,
-    const Tag &rootTag,
-    const InstanceHandle &instanceHandle,
-    const SharedViewProps &props = ViewShadowNode::defaultSharedProps(),
-    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList(),
-    const ShadowNodeCloneFunction &cloneFunction = nullptr
-  );
 
-  ViewShadowNode(
-    const SharedViewShadowNode &shadowNode,
-    const SharedViewProps &props = nullptr,
-    const SharedShadowNodeSharedList &children = nullptr
-  );
+  using ConcreteViewShadowNode::ConcreteViewShadowNode;
 
   ComponentName getComponentName() const override;
-
-  void appendChild(const SharedShadowNode &child);
-
-#pragma mark - Equality
-
-  bool operator==(const ShadowNode& rhs) const override;
-
-#pragma mark - DebugStringConvertible
-
-  SharedDebugStringConvertibleList getDebugProps() const override;
-
-private:
-
-#pragma mark - LayoutableShadowNode
-
-  SharedLayoutableShadowNodeList getLayoutableChildNodes() const override;
-  SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child) override;
 };
 
 } // namespace react

From 88c368b488139ad7e25aa55065fde53ef4727d30 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:31 -0700
Subject: [PATCH 0384/1109] Fabric/Graphics: New graphic values conversion
 functions and type refinments

Summary: Quite trivial. We need this to debug print LayoutMetrics.

Reviewed By: fkgozali

Differential Revision: D7607417

fbshipit-source-id: f4fa52ad04be9757545a8ac627db184f171288e5
---
 .../graphics/graphicValuesConversions.cpp     | 26 +++++++++++++++++--
 .../graphics/graphicValuesConversions.h       | 14 ++++++++--
 2 files changed, 36 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp b/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
index cfd80a4a1149..8a09a460f279 100644
--- a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
+++ b/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
@@ -7,10 +7,12 @@
 
 #include "graphicValuesConversions.h"
 
+#include <folly/Conv.h>
+
 namespace facebook {
 namespace react {
 
-SharedColor colorFromDynamic(folly::dynamic value) {
+SharedColor colorFromDynamic(const folly::dynamic &value) {
   float red;
   float green;
   float blue;
@@ -37,7 +39,7 @@ SharedColor colorFromDynamic(folly::dynamic value) {
   return colorFromComponents(red, green, blue, alpha);
 }
 
-std::string colorNameFromColor(SharedColor value) {
+std::string colorNameFromColor(const SharedColor &value) {
   ColorComponents components = colorComponentsFromColor(value);
   const float ratio = 256;
   return "rgba(" +
@@ -47,5 +49,25 @@ std::string colorNameFromColor(SharedColor value) {
     folly::to<std::string>(round(components.alpha * ratio)) + ")";
 }
 
+std::string stringFromPoint(const Point &point) {
+  return "{" + folly::to<std::string>(point.x) + ", " + folly::to<std::string>(point.y) + "}";
+}
+
+std::string stringFromSize(const Size &size) {
+  return "{" + folly::to<std::string>(size.width) + ", " + folly::to<std::string>(size.height) + "}";
+}
+
+std::string stringFromRect(const Rect &rect) {
+  return "{" + stringFromPoint(rect.origin) + ", " + stringFromSize(rect.size) + "}";
+}
+
+std::string stringFromEdgeInsets(const EdgeInsets &edgeInsets) {
+  return "{" +
+    folly::to<std::string>(edgeInsets.left) + ", " +
+    folly::to<std::string>(edgeInsets.top) + ", " +
+    folly::to<std::string>(edgeInsets.right) + ", " +
+    folly::to<std::string>(edgeInsets.bottom) + "}";
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.h b/ReactCommon/fabric/graphics/graphicValuesConversions.h
index 8ee9e2799d35..99774a41fe09 100644
--- a/ReactCommon/fabric/graphics/graphicValuesConversions.h
+++ b/ReactCommon/fabric/graphics/graphicValuesConversions.h
@@ -9,12 +9,22 @@
 
 #include <folly/dynamic.h>
 #include <fabric/graphics/Color.h>
+#include <fabric/graphics/Geometry.h>
 
 namespace facebook {
 namespace react {
 
-SharedColor colorFromDynamic(folly::dynamic value);
-std::string colorNameFromColor(SharedColor value);
+#pragma mark - Color
+
+SharedColor colorFromDynamic(const folly::dynamic &value);
+std::string colorNameFromColor(const SharedColor &value);
+
+#pragma mark - Geometry
+
+std::string stringFromPoint(const Point &point);
+std::string stringFromSize(const Size &size);
+std::string stringFromRect(const Rect &rect);
+std::string stringFromEdgeInsets(const EdgeInsets &edgeInsets);
 
 } // namespace react
 } // namespace facebook

From 98b4747041fe64ff9b7c85d96d00b9530abb2828 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:35 -0700
Subject: [PATCH 0385/1109] Fabric/View: Debug printing logic in
 YogaLayoutableShadowNode was moved to superclass

Summary:
It's more useful and consistent now because:
 - We print compound layout metrics from the correct storage (not from Yoga nodes);
 - It works fro any kind of layout now (but we still have just one);
 - It's much clear and straight-forward.

Reviewed By: fkgozali

Differential Revision: D7607422

fbshipit-source-id: 4c3cd2848e785a7f77c7f591e376d00c7c09ade9
---
 .../core/layout/LayoutableShadowNode.cpp      | 37 +++++++++++++++++++
 .../fabric/core/layout/LayoutableShadowNode.h |  5 +++
 .../fabric/view/ConcreteViewShadowNode.h      |  2 +-
 .../view/yoga/YogaLayoutableShadowNode.cpp    | 36 ------------------
 .../view/yoga/YogaLayoutableShadowNode.h      |  4 --
 5 files changed, 43 insertions(+), 41 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index 3e2b4a0e8f7b..a1fd9623fb86 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -10,6 +10,8 @@
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/core/LayoutContext.h>
 #include <fabric/core/LayoutMetrics.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/graphics/graphicValuesConversions.h>
 
 namespace facebook {
 namespace react {
@@ -94,5 +96,40 @@ void LayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
   // Default implementation does nothing.
 }
 
+SharedDebugStringConvertibleList LayoutableShadowNode::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+
+  if (getHasNewLayout()) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("hasNewLayout"));
+  }
+
+  if (!getIsLayoutClean()) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("dirty"));
+  }
+
+  LayoutMetrics layoutMetrics = getLayoutMetrics();
+  LayoutMetrics defaultLayoutMetrics = LayoutMetrics();
+
+  list.push_back(std::make_shared<DebugStringConvertibleItem>("frame", stringFromRect(layoutMetrics.frame)));
+
+  if (layoutMetrics.borderWidth != defaultLayoutMetrics.borderWidth) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("borderWidth", stringFromEdgeInsets(layoutMetrics.borderWidth)));
+  }
+
+  if (layoutMetrics.contentInsets != defaultLayoutMetrics.contentInsets) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("contentInsets", stringFromEdgeInsets(layoutMetrics.contentInsets)));
+  }
+
+  if (layoutMetrics.displayType == DisplayType::None) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("hidden"));
+  }
+
+  if (layoutMetrics.layoutDirection == LayoutDirection::RightToLeft) {
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("rtl"));
+  }
+
+  return list;
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
index d1c9ce1d6a3e..d664498779dc 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
@@ -13,6 +13,7 @@
 
 #include <fabric/core/LayoutMetrics.h>
 #include <fabric/core/Sealable.h>
+#include <fabric/debug/DebugStringConvertible.h>
 
 namespace facebook {
 namespace react {
@@ -102,6 +103,10 @@ class LayoutableShadowNode:
    */
   virtual bool setLayoutMetrics(LayoutMetrics layoutMetrics);
 
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const;
+
 private:
   LayoutMetrics layoutMetrics_ {};
   bool hasNewLayout_ {false};
diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
index 320fbb0d4eb5..a6994fe3e232 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -138,7 +138,7 @@ class ConcreteViewShadowNode:
     auto basePropsList = ShadowNode::getDebugProps();
     std::move(basePropsList.begin(), basePropsList.end(), std::back_inserter(list));
 
-    list.push_back(std::make_shared<DebugStringConvertibleItem>("layout", "", YogaLayoutableShadowNode::getDebugProps()));
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("layout", "", LayoutableShadowNode::getDebugProps()));
 
     return list;
   }
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 2851fa4d985b..2b6a6e233ef3 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -130,42 +130,6 @@ void YogaLayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
   }
 }
 
-#pragma mark - DebugStringConvertible
-
-SharedDebugStringConvertibleList YogaLayoutableShadowNode::getDebugProps() const {
-  // TODO: Move to the base class and return `layoutMetrics` instead.
-
-  SharedDebugStringConvertibleList list = {};
-
-  if (getHasNewLayout()) {
-    list.push_back(std::make_shared<DebugStringConvertibleItem>("hasNewLayout"));
-  }
-
-  YGLayout defaultYogaLayout = YGLayout();
-  defaultYogaLayout.direction = YGDirectionLTR;
-  YGLayout currentYogaLayout = std::const_pointer_cast<YGNode>(yogaNode_)->getLayout();
-
-#define YOGA_LAYOUT_PROPS_ADD_TO_SET(stringName, propertyName, accessor, convertor) \
-  { \
-    auto currentValueString = convertor(currentYogaLayout.propertyName accessor); \
-    auto defaultValueString = convertor(defaultYogaLayout.propertyName accessor); \
-    if (currentValueString != defaultValueString) { \
-      list.push_back(std::make_shared<DebugStringConvertibleItem>(#stringName, currentValueString)); \
-    } \
-  }
-
-  YOGA_LAYOUT_PROPS_ADD_TO_SET(position, position, , stringFromYogaPosition)
-  YOGA_LAYOUT_PROPS_ADD_TO_SET(dimensions, dimensions, , stringFromYogaDimensions)
-  YOGA_LAYOUT_PROPS_ADD_TO_SET(margin, margin, , stringFromYogaEdges)
-  YOGA_LAYOUT_PROPS_ADD_TO_SET(border, border, , stringFromYogaEdges)
-  YOGA_LAYOUT_PROPS_ADD_TO_SET(padding, padding, , stringFromYogaEdges)
-  YOGA_LAYOUT_PROPS_ADD_TO_SET(direction, direction, , stringFromYogaStyleDirection)
-
-  return list;
-}
-
-#pragma mark - Helpers
-
 #pragma mark - Yoga Connectors
 
 YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex) {
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index 15f25cdf4043..8b367e5e9e3c 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -76,10 +76,6 @@ class YogaLayoutableShadowNode:
   
   void layoutChildren(LayoutContext layoutContext) override;
 
-#pragma mark - DebugStringConvertible
-
-  SharedDebugStringConvertibleList getDebugProps() const override;
-
 private:
   mutable SharedYogaNode yogaNode_;
 

From 3428808b97bf8390d802d7863295d8625fbda64a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:39 -0700
Subject: [PATCH 0386/1109] Fabric: Using view name argument in
 `FabricUIManager.createNode()`

Summary: We are going to have not only <View> component soon!

Reviewed By: mdvacca

Differential Revision: D7738579

fbshipit-source-id: 5165762b98d94f74d40d016722be36a04d45f264
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 14 +++++++++++++-
 1 file changed, 13 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 202073283121..dc73808f4c3d 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -38,6 +38,16 @@ static const RawProps rawPropsFromDynamic(const folly::dynamic object) {
   return result;
 }
 
+static const std::string componentNameByReactViewName(std::string viewName) {
+  std::string rctPrefix("RCT");
+  if (std::mismatch(rctPrefix.begin(), rctPrefix.end(), viewName.begin()).first == rctPrefix.end()) {
+    // If `viewName` has "RCT" prefix, remove it.
+    viewName.erase(0, 3);
+  }
+
+  return viewName;
+}
+
 FabricUIManager::FabricUIManager(SharedComponentDescriptorRegistry componentDescriptorRegistry) {
   componentDescriptorRegistry_ = componentDescriptorRegistry;
 }
@@ -52,7 +62,9 @@ UIManagerDelegate *FabricUIManager::getDelegate() {
 
 SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
   LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
-  const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)["View"];
+
+  ComponentName componentName = componentNameByReactViewName(viewName);
+  const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[componentName];
   RawProps rawProps = rawPropsFromDynamic(props);
 
   SharedShadowNode shadowNode =

From 6aa52f2684301ee2fd5afa192c6790b426cf0d6a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:41 -0700
Subject: [PATCH 0387/1109] Fabric: Using a proper Component Descriptor for
 node cloning

Summary: To clone a ShadowNode we must use node's ComponentDescriptot, not parent node's one.

Reviewed By: mdvacca

Differential Revision: D7738583

fbshipit-source-id: 83656f9a761530cdaedf65663ae28b3119af75f5
---
 .../core/componentdescriptor/ConcreteComponentDescriptor.h     | 1 +
 ReactCommon/fabric/uimanager/FabricUIManager.cpp               | 3 ++-
 2 files changed, 3 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 2e2ee37fd208..11b82b32feb3 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -81,6 +81,7 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   ShadowNodeCloneFunction getCloneFunction() const {
     if (!cloneFunction_) {
       cloneFunction_ = [this](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedShadowNodeSharedList &children) {
+        assert(std::dynamic_pointer_cast<const ShadowNodeT>(shadowNode));
         return this->cloneShadowNode(shadowNode, props, children);
       };
     }
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index dc73808f4c3d..3b8786b29889 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -151,7 +151,8 @@ void FabricUIManager::appendChild(const SharedShadowNode &parentShadowNode, cons
 
   // TODO: Remove this after we move this to JS side.
   if (childShadowNode->getSealed()) {
-    auto clonedChildShadowNode = componentDescriptor->cloneShadowNode(childShadowNode);
+    auto childComponentDescriptor = (*componentDescriptorRegistry_)[childShadowNode];
+    auto clonedChildShadowNode = childComponentDescriptor->cloneShadowNode(childShadowNode);
     auto nonConstClonedChildShadowNode = std::const_pointer_cast<ShadowNode>(clonedChildShadowNode);
     nonConstClonedChildShadowNode->shallowSourceNode();
     componentDescriptor->appendChild(parentShadowNode, clonedChildShadowNode);

From 139db66a3ed5ac55f71173d99428d8a656e4d6a3 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:44 -0700
Subject: [PATCH 0388/1109] Fabric: More graphic values conversions from
 dynamic type

Summary: Trivial.

Reviewed By: mdvacca

Differential Revision: D7738578

fbshipit-source-id: 3112e523dd1cdceff90a8596033f9516aa2c8156
---
 .../graphics/graphicValuesConversions.cpp      | 18 ++++++++++++++++++
 .../fabric/graphics/graphicValuesConversions.h |  4 ++++
 2 files changed, 22 insertions(+)

diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp b/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
index 8a09a460f279..85909b3a01cd 100644
--- a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
+++ b/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
@@ -69,5 +69,23 @@ std::string stringFromEdgeInsets(const EdgeInsets &edgeInsets) {
     folly::to<std::string>(edgeInsets.bottom) + "}";
 }
 
+Float floatFromDynamic(const folly::dynamic &value) {
+  return value.asDouble();
+}
+
+Point pointFromDynamic(const folly::dynamic &value) {
+  if (value.isArray()) {
+    return Point {(Float)value[0].asDouble(), (Float)value[1].asDouble()};
+  }
+  abort();
+}
+
+Size sizeFromDynamic(const folly::dynamic &value) {
+  if (value.isArray()) {
+    return Size {(Float)value[0].asDouble(), (Float)value[1].asDouble()};
+  }
+  abort();
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.h b/ReactCommon/fabric/graphics/graphicValuesConversions.h
index 99774a41fe09..7d49cdf97058 100644
--- a/ReactCommon/fabric/graphics/graphicValuesConversions.h
+++ b/ReactCommon/fabric/graphics/graphicValuesConversions.h
@@ -26,5 +26,9 @@ std::string stringFromSize(const Size &size);
 std::string stringFromRect(const Rect &rect);
 std::string stringFromEdgeInsets(const EdgeInsets &edgeInsets);
 
+Float floatFromDynamic(const folly::dynamic &value);
+Point pointFromDynamic(const folly::dynamic &value);
+Size sizeFromDynamic(const folly::dynamic &value);
+
 } // namespace react
 } // namespace facebook

From 9d08e2afaef0081cccff69cf292f251c7015f582 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:46 -0700
Subject: [PATCH 0389/1109] Fabric: Using `ColorComponents` in
 `colorFromComponents` function

Summary: Trivial. We have a special data structure for it, why do not use it here?

Reviewed By: mdvacca

Differential Revision: D7738577

fbshipit-source-id: 750aa649b06f17d27906d44df07172a907cde2e5
---
 ReactCommon/fabric/graphics/Color.cpp                | 12 +++++++++---
 ReactCommon/fabric/graphics/Color.h                  |  2 +-
 .../fabric/graphics/graphicValuesConversions.cpp     |  2 +-
 3 files changed, 11 insertions(+), 5 deletions(-)

diff --git a/ReactCommon/fabric/graphics/Color.cpp b/ReactCommon/fabric/graphics/Color.cpp
index ba6c897b4932..151e2923a403 100644
--- a/ReactCommon/fabric/graphics/Color.cpp
+++ b/ReactCommon/fabric/graphics/Color.cpp
@@ -13,11 +13,17 @@
 namespace facebook {
 namespace react {
 
-SharedColor colorFromComponents(float red, float green, float blue, float alpha) {
-  const CGFloat components[] = {red, green, blue, alpha};
+SharedColor colorFromComponents(ColorComponents components) {
+  const CGFloat componentsArray[] = {
+    components.red,
+    components.green,
+    components.blue,
+    components.alpha
+  };
+
   CGColorRef color = CGColorCreate(
     CGColorSpaceCreateDeviceRGB(),
-    components
+    componentsArray
   );
 
   return SharedColor(color, CFRelease);
diff --git a/ReactCommon/fabric/graphics/Color.h b/ReactCommon/fabric/graphics/Color.h
index 0a84e7b3a970..f7622d213bae 100644
--- a/ReactCommon/fabric/graphics/Color.h
+++ b/ReactCommon/fabric/graphics/Color.h
@@ -23,7 +23,7 @@ struct ColorComponents {
   float alpha {0};
 };
 
-SharedColor colorFromComponents(float red, float green, float blue, float alpha);
+SharedColor colorFromComponents(ColorComponents components);
 ColorComponents colorComponentsFromColor(SharedColor color);
 
 } // namespace react
diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp b/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
index 85909b3a01cd..874c70b69045 100644
--- a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
+++ b/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
@@ -36,7 +36,7 @@ SharedColor colorFromDynamic(const folly::dynamic &value) {
     abort();
   }
 
-  return colorFromComponents(red, green, blue, alpha);
+  return colorFromComponents({red, green, blue, alpha});
 }
 
 std::string colorNameFromColor(const SharedColor &value) {

From 368388bfc88f42cadecc21923767c0c7a1f72712 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:49 -0700
Subject: [PATCH 0390/1109] Fabric: Introducing `LocalData` concept

Summary:
LocalData might be used to communicate some infomation between `ShadowNode`s
and native component views.

We will use it soon to store (and transmit to mounting layer) prepared for rendering attributed text in Text component.

Reviewed By: mdvacca

Differential Revision: D7738582

fbshipit-source-id: 1ead23ffd105cce0b3d9aeb9fc1d0df47673be50
---
 .../fabric/core/shadownode/LocalData.h        | 36 +++++++++++++++++++
 .../fabric/core/shadownode/ShadowNode.cpp     | 13 ++++++-
 .../fabric/core/shadownode/ShadowNode.h       | 19 +++++++++-
 .../fabric/core/tests/ShadowNodeTest.cpp      | 29 +++++++++++++++
 ReactCommon/fabric/core/tests/TestComponent.h | 15 ++++++++
 5 files changed, 110 insertions(+), 2 deletions(-)
 create mode 100644 ReactCommon/fabric/core/shadownode/LocalData.h

diff --git a/ReactCommon/fabric/core/shadownode/LocalData.h b/ReactCommon/fabric/core/shadownode/LocalData.h
new file mode 100644
index 000000000000..8b5b0fca093b
--- /dev/null
+++ b/ReactCommon/fabric/core/shadownode/LocalData.h
@@ -0,0 +1,36 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/Sealable.h>
+#include <fabric/debug/DebugStringConvertible.h>
+
+namespace facebook {
+namespace react {
+
+class LocalData;
+
+using SharedLocalData = std::shared_ptr<const LocalData>;
+
+/*
+ * Abstract class for any kind of concrete pieces of local data specific for
+ * some kinds of `ShadowNode`s.
+ * LocalData might be used to communicate some infomation between `ShadowNode`s
+ * and native component views.
+ * All `LocalData` objects *must* be immutable (sealed) when they became
+ * a part of the shadow tree.
+ */
+class LocalData:
+  public Sealable,
+  public DebugStringConvertible {
+
+  // Nothing.
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index f1272c32696f..b4883c22f4d8 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -47,6 +47,7 @@ ShadowNode::ShadowNode(
   props_(props ? props : shadowNode->props_),
   children_(std::make_shared<SharedShadowNodeList>(*(children ? children : shadowNode->children_))),
   sourceNode_(shadowNode),
+  localData_(shadowNode->localData_),
   cloneFunction_(shadowNode->cloneFunction_),
   revision_(shadowNode->revision_ + 1) {}
 
@@ -84,6 +85,10 @@ SharedShadowNode ShadowNode::getSourceNode() const {
   return sourceNode_.lock();
 }
 
+SharedLocalData ShadowNode::getLocalData() const {
+  return localData_;
+}
+
 void ShadowNode::sealRecursive() const {
   if (getSealed()) {
     return;
@@ -119,6 +124,11 @@ void ShadowNode::clearSourceNode() {
   sourceNode_.reset();
 }
 
+void ShadowNode::setLocalData(const SharedLocalData &localData) {
+  ensureUnsealed();
+  localData_ = localData;
+}
+
 void ShadowNode::shallowSourceNode() {
   ensureUnsealed();
 
@@ -135,7 +145,8 @@ bool ShadowNode::operator==(const ShadowNode& rhs) const {
   return
     tag_ == rhs.tag_ &&
     rootTag_ == rhs.rootTag_ &&
-    props_ == rhs.props_;
+    props_ == rhs.props_ &&
+    localData_ == rhs.localData_;
 }
 
 bool ShadowNode::operator!=(const ShadowNode& rhs) const {
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index e83e62276342..9cad65eadfb9 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -11,9 +11,10 @@
 #include <memory>
 #include <vector>
 
+#include <fabric/core/LocalData.h>
 #include <fabric/core/Props.h>
-#include <fabric/core/Sealable.h>
 #include <fabric/core/ReactPrimitives.h>
+#include <fabric/core/Sealable.h>
 #include <fabric/debug/DebugStringConvertible.h>
 
 namespace facebook {
@@ -80,6 +81,14 @@ class ShadowNode:
    */
   SharedShadowNode getSourceNode() const;
 
+  /*
+   * Returns a local data associated with the node.
+   * `LocalData` object might be used for data exchange between native view and
+   * shadow node instances.
+   * Concrete type of the object depends on concrete type of the `ShadowNode`.
+   */
+  SharedLocalData getLocalData() const;
+
   void sealRecursive() const;
 
 #pragma mark - Mutating Methods
@@ -88,11 +97,18 @@ class ShadowNode:
   void replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild);
   void clearSourceNode();
 
+  /*
+   * Sets local data assosiated with the node.
+   * The node must be unsealed at this point.
+   */
+  void setLocalData(const SharedLocalData &localData);
+
   /*
    * Replaces the current source node with its source node.
    * This method might be used for illuminating side-effects caused by the last
    * cloning operation which are not desirable from the diffing algorithm
    * perspective.
+   * The node must be unsealed at this point.
    */
   void shallowSourceNode();
 
@@ -122,6 +138,7 @@ class ShadowNode:
   SharedProps props_;
   SharedShadowNodeSharedList children_;
   WeakShadowNode sourceNode_;
+  SharedLocalData localData_;
 
 private:
 
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index 8c8204684b78..7a945bf40fb1 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -150,3 +150,32 @@ TEST(ShadowNodeTest, handleCloneFunction) {
   ASSERT_EQ(secondNode->getRootTag(), secondNodeClone->getRootTag());
   ASSERT_EQ(secondNode->getProps(), secondNodeClone->getProps());
 }
+
+TEST(ShadowNodeTest, handleLocalData) {
+  auto localData42 = std::make_shared<TestLocalData>();
+  localData42->setNumber(42);
+
+  auto anotherLocalData42 = std::make_shared<TestLocalData>();
+  anotherLocalData42->setNumber(42);
+
+  auto localDataOver9000 = std::make_shared<TestLocalData>();
+  localDataOver9000->setNumber(9001);
+
+  auto firstNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+  auto secondNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+  auto thirdNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+
+  firstNode->setLocalData(localData42);
+  secondNode->setLocalData(localData42);
+  thirdNode->setLocalData(localDataOver9000);
+
+  // LocalData object are compared by pointer, not by value.
+  ASSERT_EQ(*firstNode, *secondNode);
+  ASSERT_NE(*firstNode, *thirdNode);
+  secondNode->setLocalData(anotherLocalData42);
+  ASSERT_NE(*firstNode, *secondNode);
+
+  // LocalData cannot be changed for sealed shadow node.
+  secondNode->sealRecursive();
+  ASSERT_ANY_THROW(secondNode->setLocalData(localDataOver9000));
+}
diff --git a/ReactCommon/fabric/core/tests/TestComponent.h b/ReactCommon/fabric/core/tests/TestComponent.h
index 18890daeb03d..87372ffea8c2 100644
--- a/ReactCommon/fabric/core/tests/TestComponent.h
+++ b/ReactCommon/fabric/core/tests/TestComponent.h
@@ -11,6 +11,7 @@
 
 #include <fabric/core/ConcreteComponentDescriptor.h>
 #include <fabric/core/ConcreteShadowNode.h>
+#include <fabric/core/LocalData.h>
 #include <fabric/core/ShadowNode.h>
 
 using namespace facebook::react;
@@ -20,6 +21,20 @@ using namespace facebook::react;
  * To be used for testing purpose.
  */
 
+class TestLocalData: public LocalData {
+public:
+  void setNumber(const int &number) {
+    number_ = number;
+  }
+
+  int getNumber() const {
+    return number_;
+  }
+
+private:
+  int number_ {0};
+};
+
 class TestProps : public Props {
 public:
   TestProps() {

From 9f46f425f4809d0a266f350a2e8a34bdef4fda1f Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:52 -0700
Subject: [PATCH 0391/1109] Fabric: Managing `LocalData` instances in mounting
 pipeline

Summary: Managing and transmitting LocalData object to native views.

Reviewed By: mdvacca

Differential Revision: D7738580

fbshipit-source-id: c889da58d3afe7ac14f411576afe659bd079f641
---
 .../MountItems/RCTUpdateLocalDataMountItem.h  | 27 +++++++++++++
 .../MountItems/RCTUpdateLocalDataMountItem.mm | 39 +++++++++++++++++++
 .../Mounting/RCTComponentViewProtocol.h       |  9 +++++
 React/Fabric/Mounting/RCTMountingManager.mm   | 17 ++++++++
 .../Mounting/UIView+ComponentViewProtocol.h   |  3 ++
 .../Mounting/UIView+ComponentViewProtocol.mm  |  6 +++
 6 files changed, 101 insertions(+)
 create mode 100644 React/Fabric/Mounting/MountItems/RCTUpdateLocalDataMountItem.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTUpdateLocalDataMountItem.mm

diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateLocalDataMountItem.h b/React/Fabric/Mounting/MountItems/RCTUpdateLocalDataMountItem.h
new file mode 100644
index 000000000000..b5aedcadecd1
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateLocalDataMountItem.h
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTMountItemProtocol.h>
+#import <React/RCTPrimitives.h>
+#import <fabric/core/LocalData.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Updates local data of a component view.
+ */
+@interface RCTUpdateLocalDataMountItem : NSObject <RCTMountItemProtocol>
+
+- (instancetype)initWithTag:(ReactTag)tag
+               oldLocalData:(facebook::react::SharedLocalData)oldLocalData
+               newLocalData:(facebook::react::SharedLocalData)newLocalData;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateLocalDataMountItem.mm b/React/Fabric/Mounting/MountItems/RCTUpdateLocalDataMountItem.mm
new file mode 100644
index 000000000000..c10bc3c4b40f
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateLocalDataMountItem.mm
@@ -0,0 +1,39 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTUpdateLocalDataMountItem.h"
+
+#import "RCTComponentViewRegistry.h"
+
+using namespace facebook::react;
+
+@implementation RCTUpdateLocalDataMountItem {
+  ReactTag _tag;
+  SharedLocalData _oldLocalData;
+  SharedLocalData _newLocalData;
+}
+
+- (instancetype)initWithTag:(ReactTag)tag
+               oldLocalData:(facebook::react::SharedLocalData)oldLocalData
+               newLocalData:(facebook::react::SharedLocalData)newLocalData
+{
+  if (self = [super init]) {
+    _tag = tag;
+    _oldLocalData = oldLocalData;
+    _newLocalData = newLocalData;
+  }
+
+  return self;
+}
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
+{
+  UIView<RCTComponentViewProtocol> *componentView = [registry componentViewByTag:_tag];
+  [componentView updateLocalData:_newLocalData oldLocalData:_oldLocalData];
+}
+
+@end
diff --git a/React/Fabric/Mounting/RCTComponentViewProtocol.h b/React/Fabric/Mounting/RCTComponentViewProtocol.h
index d23ac72adfef..fc56aa7e08e9 100644
--- a/React/Fabric/Mounting/RCTComponentViewProtocol.h
+++ b/React/Fabric/Mounting/RCTComponentViewProtocol.h
@@ -7,6 +7,7 @@
 
 #import <UIKit/UIKit.h>
 
+#import <fabric/core/LocalData.h>
 #import <fabric/core/Props.h>
 #import <fabric/core/LayoutMetrics.h>
 #import <React/RCTPrimitives.h>
@@ -44,6 +45,14 @@ NS_ASSUME_NONNULL_BEGIN
 - (void)updateProps:(facebook::react::SharedProps)props
            oldProps:(facebook::react::SharedProps)oldProps;
 
+/*
+ * Called for updating component's local data.
+ * Receiver must update native view props accordingly changed local data.
+ */
+- (void)updateLocalData:(facebook::react::SharedLocalData)localData
+           oldLocalData:(facebook::react::SharedLocalData)oldLocalData;
+
+
 /*
  * Called for updating component's layout metrics.
  * Receiver must update `UIView` layout-related fields (such as `frame`,
diff --git a/React/Fabric/Mounting/RCTMountingManager.mm b/React/Fabric/Mounting/RCTMountingManager.mm
index 5f16ac2513dc..5b7e7f1311d5 100644
--- a/React/Fabric/Mounting/RCTMountingManager.mm
+++ b/React/Fabric/Mounting/RCTMountingManager.mm
@@ -20,6 +20,7 @@
 #import "RCTInsertMountItem.h"
 #import "RCTRemoveMountItem.h"
 #import "RCTUpdatePropsMountItem.h"
+#import "RCTUpdateLocalDataMountItem.h"
 #import "RCTUpdateLayoutMetricsMountItem.h"
 
 using namespace facebook::react;
@@ -74,6 +75,13 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
                                                                   oldProps:nullptr
                                                                   newProps:instruction.getNewChildNode()->getProps()]];
 
+        // LocalData
+        if (instruction.getNewChildNode()->getLocalData()) {
+          [mountItems addObject:[[RCTUpdateLocalDataMountItem alloc] initWithTag:instruction.getNewChildNode()->getTag()
+                                                                    oldLocalData:nullptr
+                                                                    newLocalData:instruction.getNewChildNode()->getLocalData()]];
+        }
+
         // Layout
         SharedLayoutableShadowNode layoutableNewShadowNode =
           std::dynamic_pointer_cast<const LayoutableShadowNode>(instruction.getNewChildNode());
@@ -108,6 +116,15 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
           [mountItems addObject:mountItem];
         }
 
+        // LocalData
+        if (oldShadowNode->getLocalData() != newShadowNode->getLocalData()) {
+          RCTUpdateLocalDataMountItem *mountItem =
+            [[RCTUpdateLocalDataMountItem alloc] initWithTag:newShadowNode->getTag()
+                                                oldLocalData:oldShadowNode->getLocalData()
+                                                newLocalData:newShadowNode->getLocalData()];
+          [mountItems addObject:mountItem];
+        }
+
         // Layout
         SharedLayoutableShadowNode layoutableOldShadowNode =
           std::dynamic_pointer_cast<const LayoutableShadowNode>(oldShadowNode);
diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.h b/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
index b38b41ba5cfb..cffe51a2f851 100644
--- a/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
@@ -25,6 +25,9 @@ NS_ASSUME_NONNULL_BEGIN
 - (void)updateProps:(facebook::react::SharedProps)props
            oldProps:(facebook::react::SharedProps)oldProps;
 
+- (void)updateLocalData:(facebook::react::SharedLocalData)localData
+           oldLocalData:(facebook::react::SharedLocalData)oldLocalData;
+
 - (void)updateLayoutMetrics:(facebook::react::LayoutMetrics)layoutMetrics
            oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics;
 
diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
index 93b5784e3d92..1a4136cfd511 100644
--- a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
@@ -30,6 +30,12 @@ - (void)updateProps:(facebook::react::SharedProps)props
   // Default implementation does nothing.
 }
 
+- (void)updateLocalData:(facebook::react::SharedLocalData)localData
+           oldLocalData:(facebook::react::SharedLocalData)oldLocalData
+{
+  // Default implementation does nothing.
+}
+
 - (void)updateLayoutMetrics:(facebook::react::LayoutMetrics)layoutMetrics
            oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics
 {

From 6bbc2ec921597ec26e68a41278e3514f88b9bb12 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:54 -0700
Subject: [PATCH 0392/1109] Fabric: Introcucing
 `ConcreteComponentDescriptor::adopt()`

Summary: Overriding `adopt` method allows subclasses to configure just created or cloned shadow nodes without overriding `create` and `clone` methods.

Reviewed By: mdvacca

Differential Revision: D7738581

fbshipit-source-id: bfe4e4e2d3d448591a3267b5ea7ca4e0800f5ba0
---
 .../ConcreteComponentDescriptor.h              | 18 +++++++++++++++---
 .../core/shadownode/ConcreteShadowNode.h       |  3 +++
 .../fabric/core/shadownode/ShadowNode.h        |  1 +
 3 files changed, 19 insertions(+), 3 deletions(-)

diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 11b82b32feb3..f690cb652f7b 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -41,7 +41,7 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     const InstanceHandle &instanceHandle,
     const SharedProps &props
   ) const override {
-    return std::make_shared<ShadowNodeT>(
+    UnsharedShadowNode shadowNode = std::make_shared<ShadowNodeT>(
       tag,
       rootTag,
       instanceHandle,
@@ -49,14 +49,19 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
       ShadowNode::emptySharedShadowNodeSharedList(),
       getCloneFunction()
     );
+    adopt(shadowNode);
+    return shadowNode;
   }
 
   SharedShadowNode cloneShadowNode(
-    const SharedShadowNode &shadowNode,
+    const SharedShadowNode &sourceShadowNode,
     const SharedProps &props = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ) const override {
-    return std::make_shared<ShadowNodeT>(std::static_pointer_cast<const ShadowNodeT>(shadowNode), std::static_pointer_cast<const ConcreteProps>(props), children);
+    assert(std::dynamic_pointer_cast<const ShadowNodeT>(sourceShadowNode));
+    UnsharedShadowNode shadowNode = std::make_shared<ShadowNodeT>(std::static_pointer_cast<const ShadowNodeT>(sourceShadowNode), std::static_pointer_cast<const ConcreteProps>(props), children);
+    adopt(shadowNode);
+    return shadowNode;
   }
 
   void appendChild(
@@ -75,7 +80,14 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     return ShadowNodeT::Props(rawProps, props);
   };
 
+protected:
+
+  virtual void adopt(UnsharedShadowNode shadowNode) const {
+    // Default implementation does nothing.
+  }
+
 private:
+
   mutable ShadowNodeCloneFunction cloneFunction_;
 
   ShadowNodeCloneFunction getCloneFunction() const {
diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index 9a18cf7e1edc..aca5fc32bea8 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -36,6 +36,7 @@ class ConcreteShadowNode: public ShadowNode {
     }
 
     auto concreteBaseProps = std::dynamic_pointer_cast<const PropsT>(baseProps);
+    assert(concreteBaseProps);
     auto props = std::make_shared<PropsT>(*concreteBaseProps);
     props->apply(rawProps);
     return props;
@@ -79,6 +80,8 @@ class ConcreteShadowNode: public ShadowNode {
   }
 
   const SharedConcreteProps getProps() const {
+    assert(std::dynamic_pointer_cast<const PropsT>(props_));
+
     return std::static_pointer_cast<const PropsT>(props_);
   }
 
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 9cad65eadfb9..fec74d3ab9dd 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -23,6 +23,7 @@ namespace react {
 class ShadowNode;
 
 using SharedShadowNode = std::shared_ptr<const ShadowNode>;
+using UnsharedShadowNode = std::shared_ptr<ShadowNode>;
 using SharedShadowNodeList = std::vector<std::shared_ptr<const ShadowNode>>;
 using SharedShadowNodeSharedList = std::shared_ptr<const SharedShadowNodeList>;
 using SharedShadowNodeUnsharedList = std::shared_ptr<SharedShadowNodeList>;

From f8ab0e0b08da5a2318a6a583983ab4dc9b0867a0 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:57 -0700
Subject: [PATCH 0393/1109] Fabric:
 YogaLayoutableShadowNode::enableMeasurement() enables custom measuring for
 Yoga based shadow nodes

Summary:
YogaLayoutableShadowNode::enableMeasurement() connects Yoga's measuring API and Fabric measuring API.
`enableMeasurement` should be called for leaf Yoga nodes with custom content which should be measured manually during layout.

Reviewed By: mdvacca

Differential Revision: D7738574

fbshipit-source-id: ffe883905c4809290d4d973ad29dc5f0e1ec7573
---
 ReactCommon/fabric/graphics/Geometry.h        |  3 ++
 .../view/yoga/YogaLayoutableShadowNode.cpp    | 46 +++++++++++++++++++
 .../view/yoga/YogaLayoutableShadowNode.h      |  7 +++
 3 files changed, 56 insertions(+)

diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index 6c2b0f041fae..00efbe62f2ac 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -20,6 +20,9 @@ using Float = CGFloat;
  */
 const Float kFloatUndefined = CGFLOAT_MAX;
 
+const Float kFloatMax = CGFLOAT_MAX;
+const Float kFloatMin = CGFLOAT_MIN;
+
 /*
  * Point
  */
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 2b6a6e233ef3..d91def613c2d 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -12,6 +12,7 @@
 
 #include <yoga/Yoga.h>
 #include <fabric/core/LayoutContext.h>
+#include <fabric/core/LayoutConstraints.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
 
 #include "yogaValuesConversions.h"
@@ -90,6 +91,12 @@ void YogaLayoutableShadowNode::setHasNewLayout(bool hasNewLayout) {
 
 #pragma mark - Mutating Methods
 
+void YogaLayoutableShadowNode::enableMeasurement() {
+  ensureUnsealed();
+
+  yogaNode_->setMeasureFunc(YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector);
+}
+
 void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child) {
   ensureUnsealed();
 
@@ -164,6 +171,45 @@ YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYoga
   return newShadowNode->yogaNode_.get();
 }
 
+YGSize YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector(YGNode *yogaNode, float width, YGMeasureMode widthMode, float height, YGMeasureMode heightMode) {
+  YogaLayoutableShadowNode *shadowNodeRawPtr = (YogaLayoutableShadowNode *)yogaNode->getContext();
+  assert(shadowNodeRawPtr);
+
+  Size minimumSize = Size {0, 0};
+  Size maximumSize = Size {kFloatMax, kFloatMax};
+
+  switch (widthMode) {
+    case YGMeasureModeUndefined:
+      break;
+    case YGMeasureModeExactly:
+      minimumSize.width = fabricFloatFromYogaFloat(width);
+      maximumSize.width = fabricFloatFromYogaFloat(width);
+      break;
+    case YGMeasureModeAtMost:
+      maximumSize.width = fabricFloatFromYogaFloat(width);
+      break;
+  }
+
+  switch (heightMode) {
+    case YGMeasureModeUndefined:
+      break;
+    case YGMeasureModeExactly:
+      minimumSize.height = fabricFloatFromYogaFloat(height);
+      maximumSize.height = fabricFloatFromYogaFloat(height);
+      break;
+    case YGMeasureModeAtMost:
+      maximumSize.height = fabricFloatFromYogaFloat(height);
+      break;
+  }
+
+  Size size = shadowNodeRawPtr->measure(LayoutConstraints {minimumSize, maximumSize});
+
+  return YGSize {
+    yogaFloatFromFabricFloat(size.width),
+    yogaFloatFromFabricFloat(size.height)
+  };
+}
+
 void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children) {
   auto yogaNodeChildren = YGVector();
 
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index 8b367e5e9e3c..0d00a3f3690b 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -54,6 +54,12 @@ class YogaLayoutableShadowNode:
 
 #pragma mark - Mutating Methods
 
+  /*
+   * Connects `measureFunc` function of Yoga node with
+   * `LayoutableShadowNode::measure()` method.
+   */
+  void enableMeasurement();
+
   /*
    * Appends `child`'s Yoga node to the own Yoga node.
    * So, it complements `ShadowNode::appendChild(...)` functionality from Yoga
@@ -82,6 +88,7 @@ class YogaLayoutableShadowNode:
   static SharedYogaConfig suitableYogaConfig();
   static void setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children);
   static YGNode *yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex);
+  static YGSize yogaNodeMeasureCallbackConnector(YGNode *yogaNode, float width, YGMeasureMode widthMode, float height, YGMeasureMode heightMode);
 };
 
 } // namespace react

From edc6cb571110592b7aa0378b852da6e417d3a28c Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:51:59 -0700
Subject: [PATCH 0394/1109] Fabric: New, much fancier, approach to parse
 dynamic props

Summary:
The new approach uses C++ overloading feature instead of specifying exact types in macros manually.
*Almost* macro-free!

Reviewed By: mdvacca

Differential Revision: D7738584

fbshipit-source-id: 85f8e4c1037b452df5e73b093dced9392cb2f73e
---
 ReactCommon/fabric/core/shadownode/Props.cpp  | 10 +---
 .../fabric/core/shadownode/propsConversions.h | 52 +++++++++++++++++++
 ReactCommon/fabric/view/ViewProps.cpp         | 31 ++---------
 ReactCommon/fabric/view/ViewProps.h           | 10 ++--
 4 files changed, 64 insertions(+), 39 deletions(-)
 create mode 100644 ReactCommon/fabric/core/shadownode/propsConversions.h

diff --git a/ReactCommon/fabric/core/shadownode/Props.cpp b/ReactCommon/fabric/core/shadownode/Props.cpp
index cd5655ee588a..688b288fd508 100644
--- a/ReactCommon/fabric/core/shadownode/Props.cpp
+++ b/ReactCommon/fabric/core/shadownode/Props.cpp
@@ -7,6 +7,7 @@
 
 #include "Props.h"
 
+#include <fabric/core/propsConversions.h>
 #include <folly/dynamic.h>
 
 namespace facebook {
@@ -15,14 +16,7 @@ namespace react {
 void Props::apply(const RawProps &rawProps) {
   ensureUnsealed();
 
-  for (auto const &pair : rawProps) {
-    auto const &name = pair.first;
-    auto const &value = pair.second;
-
-    if (name == "nativeID") {
-      nativeId_ = value.asString();
-    }
-  }
+  applyRawProp(rawProps, "nativeID", nativeId_);
 }
 
 const std::string &Props::getNativeId() const {
diff --git a/ReactCommon/fabric/core/shadownode/propsConversions.h b/ReactCommon/fabric/core/shadownode/propsConversions.h
new file mode 100644
index 000000000000..689caf0ed801
--- /dev/null
+++ b/ReactCommon/fabric/core/shadownode/propsConversions.h
@@ -0,0 +1,52 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <folly/dynamic.h>
+#include <fabric/graphics/Color.h>
+#include <fabric/graphics/Geometry.h>
+#include <fabric/graphics/graphicValuesConversions.h>
+
+namespace facebook {
+namespace react {
+
+inline bool boolFromDynamic(const folly::dynamic &value) { return value.getBool(); }
+inline int intFromDynamic(const folly::dynamic &value) { return value.getInt(); }
+inline Float floatFromDynamic(const folly::dynamic &value) { return value.getDouble(); }
+inline std::string stringFromDynamic(const folly::dynamic &value) { return value.getString(); }
+
+#define APPLY_RAW_PROP_TEMPLATE(type, converter) \
+inline static void applyRawProp(const RawProps &rawProps, const std::string &name, type &property) { \
+  auto &&iterator = rawProps.find(name); \
+  if (iterator != rawProps.end()) { \
+    property = converter(iterator->second); \
+  } \
+} \
+\
+inline static void applyRawProp(const RawProps &rawProps, const std::string &name, folly::Optional<type> &property) { \
+  auto &&iterator = rawProps.find(name); \
+  if (iterator != rawProps.end()) { \
+    auto &&value = iterator->second; \
+    if (value.isNull()) { \
+      property = {}; \
+    } else { \
+      property = converter(value); \
+    } \
+  } \
+}
+
+APPLY_RAW_PROP_TEMPLATE(bool, boolFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(int, intFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(Float, floatFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(std::string, stringFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(SharedColor, colorFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(Point, pointFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(Size, sizeFromDynamic)
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index 725c2014bc27..e49de1a6fe48 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -9,6 +9,7 @@
 
 #include <fabric/debug/DebugStringConvertibleItem.h>
 #include <fabric/graphics/graphicValuesConversions.h>
+#include <fabric/core/propsConversions.h>
 
 namespace facebook {
 namespace react {
@@ -17,32 +18,10 @@ void ViewProps::apply(const RawProps &rawProps) {
   Props::apply(rawProps);
   YogaStylableProps::apply(rawProps);
 
-  for (auto const &pair : rawProps) {
-    auto const &name = pair.first;
-    auto const &value = pair.second;
-
-    #pragma mark View Specific Properties
-
-    if (name == "zIndex") {
-      zIndex_ = value.asInt();
-      continue;
-    }
-
-    if (name == "opacity") {
-      opacity_ = value.asDouble();
-      continue;
-    }
-
-    if (name == "color") {
-      foregroundColor_ = colorFromDynamic(value);
-      continue;
-    }
-
-    if (name == "backgroundColor") {
-      backgroundColor_ = colorFromDynamic(value);
-      continue;
-    }
-  }
+  applyRawProp(rawProps, "zIndex", zIndex_);
+  applyRawProp(rawProps, "opacity", opacity_);
+  applyRawProp(rawProps, "color", foregroundColor_);
+  applyRawProp(rawProps, "backgroundColor", backgroundColor_);
 }
 
 #pragma mark - Getters
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
index 365d469f746b..4aceb7f11748 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -33,19 +33,19 @@ class ViewProps:
   SharedColor getForegroundColor() const;
   SharedColor getBackgroundColor() const;
 
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
 private:
   int zIndex_ {0};
-  float opacity_ {1.0};
+  Float opacity_ {1.0};
 
   SharedColor foregroundColor_ {nullptr};
   SharedColor backgroundColor_ {nullptr};
 
   SharedColor shadowColor_ {nullptr};
   Point shadowOffset_ {0, 0};
-
-#pragma mark - DebugStringConvertible
-
-  SharedDebugStringConvertibleList getDebugProps() const override;
 };
 
 } // namespace react

From 6ce2823afe26d63e3828c5fbd7171dbe80b45385 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 26 Apr 2018 17:52:02 -0700
Subject: [PATCH 0395/1109] Fabric: Proper types and default arguments in
 ConcreteViewShadowNode

Summary: Trivial. Those are artefacts from copy-pasting from `ViewShadowNode`.

Reviewed By: mdvacca

Differential Revision: D7738576

fbshipit-source-id: 2d362cd0ff56420d54cdd0e339458ebe57049ddc
---
 ReactCommon/fabric/view/ConcreteViewShadowNode.h | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
index a6994fe3e232..02ee969427f1 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -43,7 +43,7 @@ class ConcreteViewShadowNode:
     const Tag &tag,
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
-    const SharedViewProps &props = ConcreteViewShadowNode::defaultSharedProps(),
+    const SharedConcreteViewProps &props = ConcreteViewShadowNode::defaultSharedProps(),
     const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList(),
     const ShadowNodeCloneFunction &cloneFunction = nullptr
   ):
@@ -65,7 +65,7 @@ class ConcreteViewShadowNode:
 
   ConcreteViewShadowNode(
     const SharedConcreteViewShadowNode &shadowNode,
-    const SharedViewProps &props = nullptr,
+    const SharedConcreteViewProps &props = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ):
     ConcreteShadowNode<ViewPropsT>(

From 7b6dd2a661d13a4bd3c5ea97705fbd8caf176062 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Fri, 27 Apr 2018 00:26:10 -0700
Subject: [PATCH 0396/1109] Metro v0.36.0

Summary: bumps the version after cache updates.

Reviewed By: mjesun

Differential Revision: D7776561

fbshipit-source-id: 8afe97323544116f147b93b92e5aa42ec1124d3a
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 63695f29a6a9..b8979e9ab59c 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.35.0",
-    "metro-babel-register": "^0.35.0",
-    "metro-core": "^0.35.0",
-    "metro-memory-fs": "^0.35.0",
+    "metro": "^0.36.0",
+    "metro-babel-register": "^0.36.0",
+    "metro-core": "^0.36.0",
+    "metro-memory-fs": "^0.36.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 57774a4a981e2f12cfe9b029447e34f203221b18 Mon Sep 17 00:00:00 2001
From: Chirag Shah <shahchirag1709@gmail.com>
Date: Fri, 27 Apr 2018 05:58:42 -0700
Subject: [PATCH 0397/1109] Use app name from app.json for registering
 application

Summary:
Currently when we change the app name in `app.json`, run `react-native eject` and then run the application, we get the following error `Application HelloWorld2 has not been registered`

<img src="https://user-images.githubusercontent.com/6805530/34646396-9a68ccd0-f38c-11e7-9a49-9f985dc20f14.png" width="33%" />

This PR picks up the app name from app.json while registering the application, which prevents the additional step for the user to change the app name while registering in the `index.js`

Tested using sinopia. The new app generated with the `react-native init HelloWorld` contains the changes made.

[CLI] [ENHANCEMENT] [index.js] - App name picked from from app.json for registering application.
Closes https://github.com/facebook/react-native/pull/17472

Differential Revision: D7788652

Pulled By: hramos

fbshipit-source-id: bf23318ae1994b06e5d5908f53818040db1ad5af
---
 local-cli/templates/HelloWorld/index.js | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/local-cli/templates/HelloWorld/index.js b/local-cli/templates/HelloWorld/index.js
index 2d090c1de7b1..ab0ecbf4f878 100644
--- a/local-cli/templates/HelloWorld/index.js
+++ b/local-cli/templates/HelloWorld/index.js
@@ -1,4 +1,5 @@
 import { AppRegistry } from 'react-native';
 import App from './App';
+import { name as appName } from './app.json';
 
-AppRegistry.registerComponent('HelloWorld', () => App);
+AppRegistry.registerComponent(appName, () => App);

From e2bea00c33c85e88935aadf7644c26087a0025d7 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Fri, 27 Apr 2018 06:08:15 -0700
Subject: [PATCH 0398/1109] Remove TransformCaching.js

Reviewed By: jeanlauliac

Differential Revision: D7707146

fbshipit-source-id: 47f4c47b22cf65cfee05f63ad7dd81a5faf9c504
---
 local-cli/bundle/buildBundle.js | 3 ---
 1 file changed, 3 deletions(-)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index c5d231480529..66872a9c8162 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -14,8 +14,6 @@ const log = require('../util/log').out('bundle');
 const Server = require('metro/src/Server');
 const {Terminal} = require('metro-core');
 const TerminalReporter = require('metro/src/lib/TerminalReporter');
-/* $FlowFixMe(site=react_native_oss) */
-const TransformCaching = require('metro/src/lib/TransformCaching');
 
 const {defaults} = require('metro');
 /* $FlowFixMe(site=react_native_oss) */
@@ -102,7 +100,6 @@ async function buildBundle(
     resetCache: args.resetCache,
     resolveRequest: config.resolveRequest,
     sourceExts: sourceExts.concat(defaultSourceExts),
-    transformCache: TransformCaching.useTempDir(),
     transformModulePath: transformModulePath,
     watch: false,
     workerPath: config.getWorkerPath && config.getWorkerPath(),

From 5b0a5b98562f1092363ae36b6c16c8631b7a6a7f Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Fri, 27 Apr 2018 06:59:09 -0700
Subject: [PATCH 0399/1109] Remove shelljs(?) leftover

Summary:
`try-n-times` is used in some integration tests of React Native, but was using a non-existent `echo` function.
Here, we replace that with `console.warn`

Reviewed By: mjesun

Differential Revision: D7788436

fbshipit-source-id: 0f42a00b7be780ee31cbf397fdd12ad4ccd500b1
---
 scripts/try-n-times.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/scripts/try-n-times.js b/scripts/try-n-times.js
index 51cba900c22b..59abeca17317 100644
--- a/scripts/try-n-times.js
+++ b/scripts/try-n-times.js
@@ -26,7 +26,7 @@ function tryExecNTimes(funcToRetry, retriesLeft, onEveryError) {
       onEveryError();
     }
     retriesLeft--;
-    echo(`Command failed, ${retriesLeft} retries left`);
+    console.warn(`Command failed, ${retriesLeft} retries left`);
     if (retriesLeft === 0) {
       return exitCode;
     } else {

From 065b9991a98a43d381d1653b57a26bb27a3e46a3 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Fri, 27 Apr 2018 06:59:11 -0700
Subject: [PATCH 0400/1109] Metro v0.36.1

Summary: contains fixes to `metro-babel-register` necessary for node 6 compat (as supported by React Native)

Reviewed By: mjesun

Differential Revision: D7788437

fbshipit-source-id: 805b185dd970bf376f11664aeabea0bb8ac94b8b
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index b8979e9ab59c..794c13d1ac2e 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.36.0",
-    "metro-babel-register": "^0.36.0",
-    "metro-core": "^0.36.0",
-    "metro-memory-fs": "^0.36.0",
+    "metro": "^0.36.1",
+    "metro-babel-register": "^0.36.1",
+    "metro-core": "^0.36.1",
+    "metro-memory-fs": "^0.36.1",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 333602b9f2cc23c43ea75d5b74993e75c1d8a82a Mon Sep 17 00:00:00 2001
From: Alex Dvornikov <advornikov@fb.com>
Date: Fri, 27 Apr 2018 14:49:12 -0700
Subject: [PATCH 0401/1109] Introduce "Options" argument to "fetchSegment()"
 function

Reviewed By: jeanlauliac

Differential Revision: D7791186

fbshipit-source-id: e3954a525e6e3b02a48ac19f78cc3716969dd6bf
---
 Libraries/Core/InitializeCore.js | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/Libraries/Core/InitializeCore.js b/Libraries/Core/InitializeCore.js
index d739ab782317..2f10d5fc0e05 100644
--- a/Libraries/Core/InitializeCore.js
+++ b/Libraries/Core/InitializeCore.js
@@ -162,6 +162,7 @@ BatchedBridge.registerLazyCallableModule('JSDevSupportModule', () => require('JS
 
 global.__fetchSegment = function(
   segmentId: number,
+  options: {|+otaBuildNumber: ?string|},
   callback: (?Error) => void,
 ) {
   const {SegmentFetcher} = require('NativeModules');
@@ -170,7 +171,7 @@ global.__fetchSegment = function(
       'included as a NativeModule.');
   }
 
-  SegmentFetcher.fetchSegment(segmentId, (errorObject: ?{message: string, code: string}) => {
+  SegmentFetcher.fetchSegment(segmentId, options, (errorObject: ?{message: string, code: string}) => {
     if (errorObject) {
       const error = new Error(errorObject.message);
       (error: any).code = errorObject.code;

From 5fa9d789784f2960945ac021b16c833052b7f90c Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 27 Apr 2018 18:44:11 -0700
Subject: [PATCH 0402/1109] Fix viewflattening for views with on_layout props

Reviewed By: achen1

Differential Revision: D7796986

fbshipit-source-id: beb0725d4edc15ec23deba592e53b700abb3bcb5
---
 .../src/main/java/com/facebook/react/uimanager/ViewProps.java   | 2 --
 1 file changed, 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
index aee1a0c7d9a7..f85236d4842d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
@@ -254,8 +254,6 @@ public static boolean isLayoutOnly(ReadableMap map, String prop) {
           return map.isNull(BORDER_RIGHT_WIDTH) || map.getDouble(BORDER_RIGHT_WIDTH) == 0d;
         case BORDER_BOTTOM_WIDTH:
           return map.isNull(BORDER_BOTTOM_WIDTH) || map.getDouble(BORDER_BOTTOM_WIDTH) == 0d;
-        case ON_LAYOUT:
-          return true;
         case OVERFLOW: // We do nothing with this right now.
           return true;
         default:

From be32cbef007dada23bf830b3b12df8beefbbdac6 Mon Sep 17 00:00:00 2001
From: Nikolai Tillmann <nikolait@fb.com>
Date: Fri, 27 Apr 2018 19:09:34 -0700
Subject: [PATCH 0403/1109] Make UIManager prepackable

Reviewed By: sebmarkbage

Differential Revision: D7736403

fbshipit-source-id: 6154b76d9d948658394488fe4472d8b5bbcd3d9f
---
 Libraries/ReactNative/UIManager.js | 21 +++++++++++++++++----
 1 file changed, 17 insertions(+), 4 deletions(-)

diff --git a/Libraries/ReactNative/UIManager.js b/Libraries/ReactNative/UIManager.js
index 9f34734a731c..5f6c61619d9b 100644
--- a/Libraries/ReactNative/UIManager.js
+++ b/Libraries/ReactNative/UIManager.js
@@ -77,11 +77,24 @@ if (Platform.OS === 'ios') {
     }
   });
 } else if (UIManager.ViewManagerNames) {
-  UIManager.ViewManagerNames.forEach(viewManagerName => {
-    defineLazyObjectProperty(UIManager, viewManagerName, {
-      get: () => UIManager.getConstantsForViewManager(viewManagerName),
+  // We want to add all the view managers to the UIManager.
+  // However, the way things are set up, the list of view managers is not known at compile time.
+  // As Prepack runs at compile it, it cannot process this loop.
+  // So we wrap it in a special __residual call, which basically tells Prepack to ignore it.
+  let residual = global.__residual ? global.__residual : (_, f, ...args) => f.apply(undefined, args);
+  residual("void", (UIManager, defineLazyObjectProperty) => {
+    UIManager.ViewManagerNames.forEach(viewManagerName => {
+      defineLazyObjectProperty(UIManager, viewManagerName, {
+        get: () => UIManager.getConstantsForViewManager(viewManagerName),
+      });
     });
-  });
+  }, UIManager, defineLazyObjectProperty);
+
+  // As Prepack now no longer knows which properties exactly the UIManager has,
+  // we also tell Prepack that it has only partial knowledge of the UIManager,
+  // so that any accesses to unknown properties along the global code will fail
+  // when Prepack encounters them.
+  if (global.__makePartial) global.__makePartial(UIManager);
 }
 
 module.exports = UIManager;

From c18d2a9669825228b0c26d01a3819d3fb4babbd9 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Fri, 27 Apr 2018 20:17:14 -0700
Subject: [PATCH 0404/1109] Upgrade Jest to 23.0.0-beta.2

Reviewed By: davidaurelio

Differential Revision: D7789525

fbshipit-source-id: 0d0ebe30d66dbc5cd07c7517a513ac7be2c1e128
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index 794c13d1ac2e..62b09618c926 100644
--- a/package.json
+++ b/package.json
@@ -213,8 +213,8 @@
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
     "flow-bin": "^0.70.0",
-    "jest": "23.0.0-beta.1",
-    "jest-junit": "3.6.0",
+    "jest": "23.0.0-beta.2",
+    "jest-junit": "3.7.0",
     "prettier": "1.12.1",
     "react": "16.3.2",
     "react-test-renderer": "16.3.2",

From d0822c3bccebd9f0573c571dd1b1c2d05c714367 Mon Sep 17 00:00:00 2001
From: Mayank Patke <fishythefish@fb.com>
Date: Sat, 28 Apr 2018 01:57:37 -0700
Subject: [PATCH 0405/1109] v0.71.0 in xplat/js

Reviewed By: yungsters

Differential Revision: D7787035

fbshipit-source-id: 07defbbaa6fdc8f3016727fe6d6b1640efbf8ab6
---
 .flowconfig                                | 2 +-
 local-cli/core/index.js                    | 2 --
 local-cli/templates/HelloWorld/_flowconfig | 2 +-
 package.json                               | 2 +-
 4 files changed, 3 insertions(+), 5 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index cd3dd707a722..aea408653180 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -69,4 +69,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.70.0
+^0.71.0
diff --git a/local-cli/core/index.js b/local-cli/core/index.js
index f3059be0a627..3bb0481421b8 100644
--- a/local-cli/core/index.js
+++ b/local-cli/core/index.js
@@ -77,9 +77,7 @@ const defaultRNConfig = {
         const name = pathToCommands.split(path.sep)[0];
 
         return attachPackage(
-          // $FlowFixMe non-literal require
           require(path.join(appRoot, 'node_modules', pathToCommands)),
-          // $FlowFixMe non-literal require
           require(path.join(appRoot, 'node_modules', name, 'package.json'))
         );
       });
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 4f75b3cb1405..187b25e48158 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -51,4 +51,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.70.0
+^0.71.0
diff --git a/package.json b/package.json
index 62b09618c926..37b3feb4ca0b 100644
--- a/package.json
+++ b/package.json
@@ -212,7 +212,7 @@
     "eslint-plugin-jest": "21.8.0",
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
-    "flow-bin": "^0.70.0",
+    "flow-bin": "^0.71.0",
     "jest": "23.0.0-beta.2",
     "jest-junit": "3.7.0",
     "prettier": "1.12.1",

From 62784f35d84a331ad04139ca7877808796feb393 Mon Sep 17 00:00:00 2001
From: Jonathan Kim <jjkim@fb.com>
Date: Sun, 29 Apr 2018 15:57:49 -0700
Subject: [PATCH 0406/1109] load in platform macros

Reviewed By: ttsugriy

Differential Revision: D7809673

fbshipit-source-id: aacff1a99ba50393ed8f74842afa59384b846e63
---
 ReactCommon/cxxreact/BUCK   | 10 ++++++----
 ReactCommon/jschelpers/BUCK |  2 +-
 ReactNative/DEFS.bzl        | 11 ++++++++++-
 3 files changed, 17 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 14aa2e3c999d..515ff8cb35df 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -1,5 +1,4 @@
-load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_android_inspector_flags", "get_apple_inspector_flags", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "react_native_xplat_target")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_android_inspector_flags", "get_apple_inspector_flags", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "react_native_xplat_target", "ANDROID", "APPLE")
 
 CXX_LIBRARY_COMPILER_FLAGS = [
     "-std=c++14",
@@ -8,9 +7,12 @@ CXX_LIBRARY_COMPILER_FLAGS = [
 
 APPLE_COMPILER_FLAGS = []
 
+DEBUG_PREPROCESSOR_FLAGS = []
+
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags", "get_static_library_ios_flags", "flags")
     APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    DEBUG_PREPROCESSOR_FLAGS = get_debug_preprocessor_flags()
 
 rn_xplat_cxx_library(
     name = "module",
@@ -140,7 +142,7 @@ rn_xplat_cxx_library(
     fbobjc_frameworks = [
         "$SDKROOT/System/Library/Frameworks/JavaScriptCore.framework",
     ],
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_preprocessor_flags = DEBUG_PREPROCESSOR_FLAGS + get_apple_inspector_flags(),
     force_static = True,
     macosx_tests_override = [],
     platforms = (ANDROID, APPLE),
diff --git a/ReactCommon/jschelpers/BUCK b/ReactCommon/jschelpers/BUCK
index 37dc1abb0df5..c0bb888ea0c9 100644
--- a/ReactCommon/jschelpers/BUCK
+++ b/ReactCommon/jschelpers/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library", "react_native_xplat_target", "ANDROID_JSC_INTERNAL_DEPS", "APPLE_JSC_INTERNAL_DEPS")
+load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library", "react_native_xplat_target", "ANDROID_JSC_INTERNAL_DEPS", "APPLE_JSC_INTERNAL_DEPS", "ANDROID", "APPLE")
 
 EXPORTED_HEADERS = [
     "JavaScriptCore.h",
diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index 135bacfbc93d..b0c85a1aaf7e 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -4,7 +4,7 @@ This lets us build React Native:
  - At Facebook by running buck from the root of the fb repo
  - Outside of Facebook by running buck in the root of the git repo
 """
-# @lint-ignore-every SKYLINT
+# @lint-ignore-every SKYLINT BUCKRESTRICTEDSYNTAX
 
 IS_OSS_BUILD = True
 
@@ -22,6 +22,7 @@ ANDROID_JSC_INTERNAL_DEPS = [
 ]
 ANDROID_JSC_DEPS = ANDROID_JSC_INTERNAL_DEPS
 ANDROID = "Android"
+APPLE = ""
 
 YOGA_TARGET = '//ReactAndroid/src/main/java/com/facebook:yoga'
 FBGLOGINIT_TARGET = '//ReactAndroid/src/main/jni/first-party/fbgloginit:fbgloginit'
@@ -33,6 +34,14 @@ with allow_unsafe_import():
     import os
 
 
+def get_apple_inspector_flags():
+    return []
+
+
+def get_android_inspector_flags():
+    return []
+
+
 # Building is not supported in OSS right now
 def rn_xplat_cxx_library(name, **kwargs):
     new_kwargs = {

From 5b923e0eafb44cef50b18838308889d2330dbf2a Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Mon, 30 Apr 2018 09:52:34 -0700
Subject: [PATCH 0407/1109] Add args to bridge function call systrace markers

Reviewed By: yungsters

Differential Revision: D7797728

fbshipit-source-id: 615affc57e658d4dd08a88f829d38be930804372
---
 Libraries/BatchedBridge/MessageQueue.js | 6 +++++-
 1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/Libraries/BatchedBridge/MessageQueue.js b/Libraries/BatchedBridge/MessageQueue.js
index 5c2338d033e8..93a759154cb0 100644
--- a/Libraries/BatchedBridge/MessageQueue.js
+++ b/Libraries/BatchedBridge/MessageQueue.js
@@ -328,7 +328,11 @@ class MessageQueue {
   __callFunction(module: string, method: string, args: any[]): any {
     this._lastFlush = new Date().getTime();
     this._eventLoopStartTime = this._lastFlush;
-    Systrace.beginEvent(`${module}.${method}()`);
+    if (__DEV__ || this.__spy) {
+      Systrace.beginEvent(`${module}.${method}(${stringifySafe(args)})`);
+    } else {
+      Systrace.beginEvent(`${module}.${method}(...)`);
+    }
     if (this.__spy) {
       this.__spy({type: TO_JS, module, method, args});
     }

From 0f6762ba50b92a16fa11f10142b4416aace57f5e Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Mon, 30 Apr 2018 11:41:14 -0700
Subject: [PATCH 0408/1109] improve console logging

Summary:
* Always log when PRINT_TO_CONSOLE true - o reason to also check DEV.
* Log when `clearExceptTimespans` is called.
* Type `PRINT_TO_CONSOLE: false` to prevent accidental commits setting it true.

Reviewed By: alexeylang

Differential Revision: D7816623

fbshipit-source-id: 47cf7e158133045e20b345139efb1a79e5e6553b
---
 Libraries/Utilities/PerformanceLogger.js | 13 ++++++++-----
 1 file changed, 8 insertions(+), 5 deletions(-)

diff --git a/Libraries/Utilities/PerformanceLogger.js b/Libraries/Utilities/PerformanceLogger.js
index aa4633fceb9c..a48f1adb4b6e 100644
--- a/Libraries/Utilities/PerformanceLogger.js
+++ b/Libraries/Utilities/PerformanceLogger.js
@@ -29,7 +29,7 @@ let timespans: {[key: string]: Timespan} = {};
 let extras: {[key: string]: any} = {};
 const cookies: {[key: string]: number} = {};
 
-const PRINT_TO_CONSOLE = false;
+const PRINT_TO_CONSOLE: false = false; // Type as false to prevent accidentally committing `true`;
 
 /**
  * This is meant to collect and log performance data in production, which means
@@ -69,7 +69,7 @@ const PerformanceLogger = {
       startTime: performanceNow(),
     };
     cookies[key] = Systrace.beginAsyncEvent(key);
-    if (__DEV__ && PRINT_TO_CONSOLE) {
+    if (PRINT_TO_CONSOLE) {
       infoLog('PerformanceLogger.js', 'start: ' + key);
     }
   },
@@ -97,7 +97,7 @@ const PerformanceLogger = {
 
     timespan.endTime = performanceNow();
     timespan.totalTime = timespan.endTime - (timespan.startTime || 0);
-    if (__DEV__ && PRINT_TO_CONSOLE) {
+    if (PRINT_TO_CONSOLE) {
       infoLog('PerformanceLogger.js', 'end: ' + key);
     }
 
@@ -108,7 +108,7 @@ const PerformanceLogger = {
   clear() {
     timespans = {};
     extras = {};
-    if (__DEV__ && PRINT_TO_CONSOLE) {
+    if (PRINT_TO_CONSOLE) {
       infoLog('PerformanceLogger.js', 'clear');
     }
   },
@@ -120,7 +120,7 @@ const PerformanceLogger = {
       }
     }
     extras = {};
-    if (__DEV__ && PRINT_TO_CONSOLE) {
+    if (PRINT_TO_CONSOLE) {
       infoLog('PerformanceLogger.js', 'clearCompleted');
     }
   },
@@ -133,6 +133,9 @@ const PerformanceLogger = {
       return previous;
     }, {});
     extras = {};
+    if (PRINT_TO_CONSOLE) {
+      infoLog('PerformanceLogger.js', 'clearExceptTimespans', keys);
+    }
   },
 
   currentTimestamp() {

From f99ca3c03fbd92995ef2559198a8b7fa7721ca92 Mon Sep 17 00:00:00 2001
From: Brent Erickson <berickson1@users.noreply.github.com>
Date: Mon, 30 Apr 2018 17:25:02 -0700
Subject: [PATCH 0409/1109] Fix a race condition in AppState that prevents
 listeners from being notified

Summary:
If someone has setup a subscription on AppState and we correct AppState via getCurrentAppState call, we need to notify all the subscribers of AppState.
1 ) Initial AppState.currentState = 'active'
2-start) Subscribe to AppState Changes
3-start) Fetch Current AppState
4 ) App Code subscribes to AppState module
5 ) App becomes backgrounded
2-finish) AppState listeners are setup (missing background event)
3-finish) AppState.currentState updated to background

At this point the subscription setup in 4) will never be called with the change.

AppState should always call subscribers on change

This is very difficult to formally test since it's due to a race condition. We've seen this condition via bug reports but have had no local repro.

[GENERAL][BUGFIX][AppState] - Fix a race condition that could prevent AppState subscription change listener from firing on initial launch
Closes https://github.com/facebook/react-native/pull/18236

Differential Revision: D7823370

Pulled By: hramos

fbshipit-source-id: 99b174df70262ceaf9da141d005131facd624594
---
 Libraries/AppState/AppState.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/Libraries/AppState/AppState.js b/Libraries/AppState/AppState.js
index ecb106bb24e8..904bf2b0e658 100644
--- a/Libraries/AppState/AppState.js
+++ b/Libraries/AppState/AppState.js
@@ -60,8 +60,10 @@ class AppState extends NativeEventEmitter {
     // prop and expose `getCurrentAppState` method directly.
     RCTAppState.getCurrentAppState(
       (appStateData) => {
-        if (!eventUpdated) {
+        // It's possible that the state will have changed here & listeners need to be notified
+        if (!eventUpdated && this.currentState !== appStateData.app_state) {
           this.currentState = appStateData.app_state;
+          this.emit('appStateDidChange', appStateData);
         }
       },
       logError

From 2d9e2f30e17b8e79f2c44ef533ecdd550671304c Mon Sep 17 00:00:00 2001
From: John Shelley <john.shelley.p@gmail.com>
Date: Tue, 1 May 2018 04:01:29 -0700
Subject: [PATCH 0410/1109] Android - Fix Drawable v4 paths in Android Artifact
 Resources (Libraries)

Summary:
_Quick apologies for the lengthiness of this description. Want to make sure I'm clear and it is understood what is being altered._

Thanks for submitting a PR! Please read these instructions carefully:

- [x] Explain the **motivation** for making this change.
- [x] Provide a **test plan** demonstrating that the code is solid.
- [x] Match the **code formatting** of the rest of the codebase.
- [x] Target the `master` branch, NOT a "stable" branch.

https://github.com/facebook/react-native/issues/5787
```
Unknown source file : /home/tom/projects/blueprint-native/android/app/build/intermediates/res/merged/release/drawable-mdpi-v4/images_google.png: error: Duplicate file.

Unknown source file : /home/tom/projects/blueprint-native/android/app/build/intermediates/res/merged/release/drawable-mdpi/images_google.png: Original is here. The version qualifier may be implied.
```

At Hudl, we've been attempting to package our React Native code into Library Dependencies _(Cocoapods / Android Artifact Resource (aar))_. Recently in React Native 0.42.0, there was an upgrade to the Android Project's gradle plugin from 1.3.1 to 2.2.3. This update drastically effected the outcome of drawable resources in Android without anyone noticing.

**There are 4 outcomes to consider with this change:**
1. You are developing in an Android Application using Gradle 1.3.1 or lower
2. You are developing in an Android Application using Gradle 2.2.3 or higher
3. You are developing in an Android Library Module using Gradle 1.3.1 or lower
4. You are developing in an Android Library Module using Gradle 2.2.3 or higher

With the upgrade to 2.2.3, Android changed the way aapt builds its resources. Any Library created with 2.2.3, has its resources ending with a `v4` suffix. The reasoning behind this I'm not sure of but assume it deals with Vector support that was added around that time.

The change I've added checks if React Native is being ran in an Android Library vs an Application, and appends the v4 suffix to the merged asset folders.

Multiple test were performed.

1. I first started out validating my assumption about the asset merger by creating a new Android Project to verify my assumptions above.
   1. [Application +  >= 2.2.3](https://github.com/jpshelley/TestAndroidLibraryDrawables/tree/master/app/build/intermediates/res/merged/debug) -- `hdpi` contains my drawable. `hdpi-v4` contains dependency's drawables.
   2. [Application + <= 1.3.1](https://github.com/jpshelley/TestAndroidLibraryDrawables/tree/Android-LegacyVersion/app/build/intermediates/res/merged/debug) -- Same as above (I expect because deps are compiled against gradle 2.2.3+ themselves.
   3. [Library + >= 2.2.3](https://github.com/jpshelley/TestAndroidLibraryDrawables/tree/Android-UsingAndroidLibrary/library/build/intermediates/res/merged/debug) -- Only `-v4` folders found! Resources from the library are packages in the app's build output in similar `-v4` folder too.
   4. [Library + <= 1.3.1](https://github.com/jpshelley/TestAndroidLibraryDrawables/tree/Android-UsingAndroidLibraryLegacyVersion/library/build/intermediates/res/merged/debug) -- Same as ii. & iii. `-v4` contains other resources, but my resources are located in non -v4 folder.

2. I then wanted to validate against React Native itself. So I updated my react native code using this PR/Branch, and tested against my project locally. Unfortunately I cannot share that code as it is private, but before this change I was getting the same error as mentioned in #5787 and now my build runs as intended with the assets being placed where they should be.

Additional resources:
* https://github.com/facebook/react-native/issues/5787
* http://stackoverflow.com/questions/35700272/android-build-tool-adds-v4-qualifier-to-drawable-folders-by-default-in-generated
* https://github.com/facebook/react-native/issues/12710

Please let me know if more information is needed, further test plans, etc. With this change we should be able to upgrade to Gradle 2.3.0 as well to support the latest version of Android Studio.
Closes https://github.com/facebook/react-native/pull/13128

Differential Revision: D7828618

Pulled By: hramos

fbshipit-source-id: a7ad7b63b1b51cbfd2ea7656e4d77321306ce33a
---
 react.gradle | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)

diff --git a/react.gradle b/react.gradle
index bdf392ad9a71..f048c07d4e3e 100644
--- a/react.gradle
+++ b/react.gradle
@@ -24,6 +24,7 @@ void runBefore(String dependentTaskName, Task task) {
 }
 
 afterEvaluate {
+    def isAndroidLibrary = plugins.hasPlugin("com.android.library")
     // Grab all build types and product flavors
     def buildTypes = android.buildTypes.collect { type -> type.name }
     def productFlavors = android.productFlavors.collect { flavor -> flavor.name }
@@ -101,6 +102,24 @@ afterEvaluate {
                 enabled config."bundleIn${targetName}" ||
                     config."bundleIn${buildTypeName.capitalize()}" ?:
                             targetName.toLowerCase().contains("release")
+
+                if (isAndroidLibrary) {
+                    doLast {
+                        def moveFunc = { resSuffix ->
+                            File originalDir = file("${resourcesDir}/drawable-${resSuffix}")
+                            if (originalDir.exists()) {
+                                File destDir = file("${resourcesDir}/drawable-${resSuffix}-v4")
+                                ant.move(file: originalDir, tofile: destDir)
+                            }
+                        }
+                        moveFunc.curry("ldpi").call()
+                        moveFunc.curry("mdpi").call()
+                        moveFunc.curry("hdpi").call()
+                        moveFunc.curry("xhdpi").call()
+                        moveFunc.curry("xxhdpi").call()
+                        moveFunc.curry("xxxhdpi").call()
+                    }
+                }
             }
 
             // Hook bundle${productFlavor}${buildType}JsAndAssets into the android build process

From 837d496ac8fd8da5528ecbb21dfa7f7a611d6cbf Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 1 May 2018 08:01:48 -0700
Subject: [PATCH 0411/1109] Fix clone of MutableYogaValue inside
 LayoutShadowNode

Reviewed By: achen1

Differential Revision: D7815809

fbshipit-source-id: 833af43387895b0b5193d6bef54c99023da01c9c
---
 .../java/com/facebook/react/uimanager/LayoutShadowNode.java    | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
index ae85bbdccd76..c9d8de0eaef7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
@@ -74,7 +74,7 @@ public LayoutShadowNode() {
 
   protected LayoutShadowNode(LayoutShadowNode node) {
     super(node);
-    mTempYogaValue = new MutableYogaValue();
+    mTempYogaValue = new MutableYogaValue(node.mTempYogaValue);
   }
 
   @Override
@@ -527,7 +527,6 @@ public void setOverflow(@Nullable String overflow) {
     if (isVirtual()) {
       return;
     }
-
     if (overflow == null) {
       setOverflow(YogaOverflow.VISIBLE);
       return;

From 8e3105dbcecd9b7c400cff031c22ecd74719704d Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Tue, 1 May 2018 13:02:32 -0700
Subject: [PATCH 0412/1109] Add `getName()` method

Summary: adds a `getName()` method to all `JavaScriptExecutor` classes that can be used by `ReactInstanceManager` to identify the bridge type when logging markers.

Reviewed By: fromcelticpark

Differential Revision: D7790531

fbshipit-source-id: efe485588738a38936accc4a7956840784b2dd08
---
 .../com/facebook/react/bridge/JSCJavaScriptExecutor.java    | 6 ++++++
 .../java/com/facebook/react/bridge/JavaScriptExecutor.java  | 5 +++++
 .../com/facebook/react/bridge/ProxyJavaScriptExecutor.java  | 5 +++++
 3 files changed, 16 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSCJavaScriptExecutor.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSCJavaScriptExecutor.java
index ee77eda70b98..ead9806f5096 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSCJavaScriptExecutor.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSCJavaScriptExecutor.java
@@ -20,5 +20,11 @@
     super(initHybrid(jscConfig));
   }
 
+  @Override
+  public String getName() {
+    return "JSCJavaScriptExecutor";
+  }
+
+
   private native static HybridData initHybrid(ReadableNativeMap jscConfig);
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JavaScriptExecutor.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JavaScriptExecutor.java
index e4195aff3328..9c72fd1f8e54 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JavaScriptExecutor.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JavaScriptExecutor.java
@@ -26,4 +26,9 @@ protected JavaScriptExecutor(HybridData hybridData) {
   public void close() {
     mHybridData.resetNative();
   }
+
+  /**
+   * Returns the name of the executor, identifying the underlying runtime.
+   */
+  abstract public String getName();
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ProxyJavaScriptExecutor.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ProxyJavaScriptExecutor.java
index db04655d3547..5442daa3a96c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ProxyJavaScriptExecutor.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ProxyJavaScriptExecutor.java
@@ -59,5 +59,10 @@ public void close() {
     }
   }
 
+  @Override
+  public String getName() {
+    return "ProxyJavaScriptExecutor";
+  }
+
   private native static HybridData initHybrid(JavaJSExecutor executor);
 }

From fa25311d274e380773e0ef2d71fc510ec3e3c85a Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Tue, 1 May 2018 13:02:38 -0700
Subject: [PATCH 0413/1109] ReactInstanceManager: post executor name with
 `CREATE_REACT_CONTEXT_START` marker

Summary: Adds the name of the active JS executor when logging the `CREATE_REACT_CONTEXT_START` marker.

Reviewed By: fromcelticpark

Differential Revision: D7800760

fbshipit-source-id: d5090a9f90cf4b7bcfb7218e75621becebd70675
---
 .../src/main/java/com/facebook/react/ReactInstanceManager.java  | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 26ee98a9a034..b97f6f45bab2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -1067,7 +1067,7 @@ private ReactApplicationContext createReactContext(
       JavaScriptExecutor jsExecutor,
       JSBundleLoader jsBundleLoader) {
     Log.d(ReactConstants.TAG, "ReactInstanceManager.createReactContext()");
-    ReactMarker.logMarker(CREATE_REACT_CONTEXT_START);
+    ReactMarker.logMarker(CREATE_REACT_CONTEXT_START, jsExecutor.getName());
     final ReactApplicationContext reactContext = new ReactApplicationContext(mApplicationContext);
 
     NativeModuleCallExceptionHandler exceptionHandler = mNativeModuleCallExceptionHandler != null

From bf83600996298f21698fc1fd0b90ab597d411d92 Mon Sep 17 00:00:00 2001
From: Eric Samelson <samelson.e@gmail.com>
Date: Tue, 1 May 2018 13:57:58 -0700
Subject: [PATCH 0414/1109] Remove race condition in initial layout of
 ReactRootView

Summary:
There is a race condition stemming from `ReactRootView.onCreate` that occasionally causes the initial root layout calculation to never occur. In this method currently, `updateRootLayoutSpecs(...)` is called before `enableLayoutCalculation()`, meaning that it's possible for the native modules thread to reach `UIImplementation.updateViewHierarchy` before layout calculation has been enabled (i.e. before the rootViewTag is added to `UIImplementation.mMeasuredRootNodes` on the UI thread).

When this occurs, `UIImplementation.applyUpdatesRecursive` is never called. This causes the app to hang on the splash screen indefinitely, the JS never gets past the first call to `render`, and no layout events are ever sent to the JS.

This PR reverses the order of those two method calls to ensure that the rootViewTag is always added to `mMeasuredRootNodes` before `UIImplementation.updateViewHierarchy` expects it. We inspected all of the code paths of both `enableLayoutCalculation()` and `updateRootLayoutSpecs()` to ensure that in this new order, the rootViewTag will *always* be added to `mMeasuredRootNodes` before the call to `updateViewHierarchy` is dispatched, and that no other side effects would be introduced.

Tested with an app that reliably had this issue (hanging splash screen) on 1 out of every ~10 launches. Logged values to ensure that empty `mMeasuredRootNodes` was the difference between failed and successful launches. After this change, I launched the same app 50+ times without any issues.

[ANDROID][BUGFIX][ReactRootView] - remove race condition in initial layout of ReactRootView
Closes https://github.com/facebook/react-native/pull/19038

Differential Revision: D7834270

Pulled By: hramos

fbshipit-source-id: 6040da900f807dcacbc86ae2c36b4ca004f80178
---
 .../src/main/java/com/facebook/react/ReactRootView.java       | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index baa2a6e30d96..4c4a7952990d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -147,12 +147,12 @@ protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
       // Check if we were waiting for onMeasure to attach the root view.
       if (mReactInstanceManager != null && !mIsAttachedToInstance) {
         attachToReactInstanceManager();
+        enableLayoutCalculation();
       } else {
+        enableLayoutCalculation();
         updateRootLayoutSpecs(mWidthMeasureSpec, mHeightMeasureSpec);
       }
 
-      enableLayoutCalculation();
-
     } finally {
       Systrace.endSection(TRACE_TAG_REACT_JAVA_BRIDGE);
     }

From 99a6c0af405b9cde9ecefc1666afcd537a52f710 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 1 May 2018 19:19:45 -0700
Subject: [PATCH 0415/1109] Fix NPE in ReactSliderManager.initMeasureFunction

Reviewed By: fkgozali

Differential Revision: D7825102

fbshipit-source-id: af7502a5e6ffa83965a66a0a099d729152d7627f
---
 .../java/com/facebook/react/views/slider/ReactSliderManager.java | 1 -
 1 file changed, 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
index 10f714c94297..1cd9c261103e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
@@ -57,7 +57,6 @@ private ReactSliderShadowNode(ReactSliderShadowNode node) {
       mWidth = node.mWidth;
       mHeight = node.mHeight;
       mMeasured = node.mMeasured;
-      initMeasureFunction();
     }
 
     private void initMeasureFunction() {

From 37c820f16e33746241af05e188d69502f518f80d Mon Sep 17 00:00:00 2001
From: Jerry Horton <jerry.horton@trane.com>
Date: Tue, 1 May 2018 19:25:06 -0700
Subject: [PATCH 0416/1109] =?UTF-8?q?Fix=20for=20issue=20#19086=20RCTHasFo?=
 =?UTF-8?q?ntHandlerSet();=20This=20function=20definition=E2=80=A6?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
… is not a protoype #19086

Thank you for sending the PR! We appreciate you spending the time to work on these changes.
Help us understand your motivation by explaining why you decided to make this change.

<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

Fixes #19086

Related to react-native-navigation issue #3019

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Created a fresh react native >= 0.55.2 project and only install React Native Navigation. The error "This function declaration is not a prototype" message occurs.

Downgrading to React Native 0.54.4 builds fine.

![screen shot 2018-05-01 at 3 17 51 pm](https://user-images.githubusercontent.com/5680239/39491718-ddfdd6a0-4d52-11e8-937f-7ed9702a2e30.png)

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

No documentation change

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->
[iOS] [BUGFIX] [react-native-navigation] - For compatibility with react-native-navigation >= 2.0.2237 https://github.com/facebook/react-native/issues/19086
<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/19089

Differential Revision: D7841198

Pulled By: shergin

fbshipit-source-id: 31638274055c3f143342d2d6dde6d4af7a2ac304
---
 React/Views/RCTFont.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/Views/RCTFont.h b/React/Views/RCTFont.h
index e812f69df353..a8f347a7d52f 100644
--- a/React/Views/RCTFont.h
+++ b/React/Views/RCTFont.h
@@ -18,7 +18,7 @@ typedef UIFont *(^RCTFontHandler)(CGFloat fontSize, NSString *fontWeightDescript
  * "semibold", "extrabold", "bold", "heavy", or "black".
  */
 RCT_EXTERN void RCTSetDefaultFontHandler(RCTFontHandler handler);
-RCT_EXTERN BOOL RCTHasFontHandlerSet();
+RCT_EXTERN BOOL RCTHasFontHandlerSet(void);
 
 @interface RCTFont : NSObject
 

From 5b2a2bee7a88cd25e30d8767622a8e20b3753e9d Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Tue, 1 May 2018 19:35:48 -0700
Subject: [PATCH 0417/1109] PureComponentDebug

Summary:
Drop in replacement for `React.PureComponent` or can replace `React.PureComponent` for all components.

Logs out what exactly triggered a re-render of a `PureComponent` to make it easier to track down why a component is re-rendering. With some other changes we'll also get component stacks in the YellowBox to make it even easier.

I thought about logging the values, but it's too easy to render something gross or cyclical like react components, so I figured people could break in the debugger to get more detail as needed.

Special flow type should cause errors if people try to commit any usage of this - it should only be used for local debugging.

Reviewed By: yungsters

Differential Revision: D7826325

fbshipit-source-id: fdf7910336452ac1c7acd328c04d441dfb186b59
---
 Libraries/Performance/PureComponentDebug.js | 73 +++++++++++++++++++++
 1 file changed, 73 insertions(+)
 create mode 100644 Libraries/Performance/PureComponentDebug.js

diff --git a/Libraries/Performance/PureComponentDebug.js b/Libraries/Performance/PureComponentDebug.js
new file mode 100644
index 000000000000..c06dbbb71431
--- /dev/null
+++ b/Libraries/Performance/PureComponentDebug.js
@@ -0,0 +1,73 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ * @format
+ */
+
+'use strict';
+
+const React = require('React');
+
+opaque type DoNotCommitUsageOfPureComponentDebug = {};
+
+/**
+ * Identifies which prop or state changes triggered a re-render of a PureComponent. Usage:
+ *
+ * Change `extends React.PureComponent` to `extends PureComponentDebug` or inject it
+ * everywhere by putting this line in your app setup:
+ *
+ *    React.PureComponent = require('PureComponentDebug');
+ *
+ * Should only be used for local testing, and will trigger a flow failure if you try to
+ * commit any usages.
+ */
+class PureComponentDebug<
+  P: DoNotCommitUsageOfPureComponentDebug,
+  S: ?Object = void,
+> extends React.Component<P, S> {
+  shouldComponentUpdate(nextProps: P, nextState: S): boolean {
+    const tag = this.constructor.name;
+    let ret = false;
+    const prevPropsKeys = Object.keys(this.props);
+    const nextPropsKeys = Object.keys(nextProps);
+    if (prevPropsKeys.length !== nextPropsKeys.length) {
+      ret = true;
+      console.warn(
+        'PureComponentDebug: different prop keys',
+        tag,
+        prevPropsKeys.filter(key => !nextPropsKeys.includes(key)),
+        nextPropsKeys.filter(key => !prevPropsKeys.includes(key)),
+      );
+    }
+    const prevStateKeys = Object.keys(this.state || {});
+    const nextStateKeys = Object.keys(nextState || {});
+    if (prevStateKeys.length !== nextStateKeys.length) {
+      ret = true;
+      console.warn(
+        'PureComponentDebug: different state keys',
+        tag,
+        prevStateKeys.filter(key => !nextStateKeys.includes(key)),
+        nextStateKeys.filter(key => !prevStateKeys.includes(key)),
+      );
+    }
+    for (const key in this.props) {
+      if (this.props[key] !== nextProps[key]) {
+        ret = true;
+        console.warn('PureComponentDebug: different prop values', tag, key);
+      }
+    }
+    for (const key in this.state) {
+      if (this.state[key] !== (nextState || {})[key]) {
+        ret = true;
+        console.warn('PureComponentDebug: different state values', tag, key);
+      }
+    }
+    return ret;
+  }
+}
+
+module.exports = PureComponentDebug;

From fffae996406537595696bbb03a0c8ad6c87cd6d9 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Tue, 1 May 2018 21:53:22 -0700
Subject: [PATCH 0418/1109] deepDiffer: add maxDepth arg

Reviewed By: blairvanderhoof

Differential Revision: D7839729

fbshipit-source-id: fe9a06d2aaed9dfbfb3e52779ba4b1b98007b9ce
---
 .../Utilities/differ/__tests__/deepDiffer-test.js    | 12 ++++++++++++
 Libraries/Utilities/differ/deepDiffer.js             |  9 ++++++---
 2 files changed, 18 insertions(+), 3 deletions(-)

diff --git a/Libraries/Utilities/differ/__tests__/deepDiffer-test.js b/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
index 6fadfdbe5754..4fb31ee05fb3 100644
--- a/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
+++ b/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
@@ -98,4 +98,16 @@ describe('deepDiffer', function() {
     var obj = [1,[2,3]];
     expect(deepDiffer(obj, obj)).toBe(false);
   });
+  it('should respect maxDepth arg', () => {
+    expect(deepDiffer(
+      {a: {A: {aA: 1, bB: 1}}, b: 1},
+      {a: {A: {aA: 1, bB: 1}}, b: 1},
+      3
+    )).toBe(true);
+    expect(deepDiffer(
+      {a: {A: {aA: 1, bB: 1}}, b: 1},
+      {a: {A: {aA: 1, bB: 1}}, b: 1},
+      4
+    )).toBe(false);
+  });
 });
diff --git a/Libraries/Utilities/differ/deepDiffer.js b/Libraries/Utilities/differ/deepDiffer.js
index 700733f51f6b..f3f826fe9116 100644
--- a/Libraries/Utilities/differ/deepDiffer.js
+++ b/Libraries/Utilities/differ/deepDiffer.js
@@ -11,7 +11,10 @@
 /*
  * @returns {bool} true if different, false if equal
  */
-var deepDiffer = function(one: any, two: any): bool {
+var deepDiffer = function(one: any, two: any, maxDepth: number = -1): bool {
+  if (maxDepth === 0) {
+    return true;
+  }
   if (one === two) {
     // Short circuit on identical object references instead of traversing them.
     return false;
@@ -39,13 +42,13 @@ var deepDiffer = function(one: any, two: any): bool {
       return true;
     }
     for (var ii = 0; ii < len; ii++) {
-      if (deepDiffer(one[ii], two[ii])) {
+      if (deepDiffer(one[ii], two[ii], maxDepth - 1)) {
         return true;
       }
     }
   } else {
     for (var key in one) {
-      if (deepDiffer(one[key], two[key])) {
+      if (deepDiffer(one[key], two[key], maxDepth - 1)) {
         return true;
       }
     }

From 9927d209271a4d29326f79546b6501f556eeea92 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rub=C3=A9n=20Norte?= <rubennorte@fb.com>
Date: Wed, 2 May 2018 03:42:56 -0700
Subject: [PATCH 0419/1109] Set hasteImplModulePath in React Native Jest preset

Reviewed By: cpojer

Differential Revision: D7843566

fbshipit-source-id: 98be0d7286351475248f53b7c028e6c85d411a10
---
 jest-preset.json | 1 +
 1 file changed, 1 insertion(+)

diff --git a/jest-preset.json b/jest-preset.json
index a5ef95af6773..afd12eb96e73 100644
--- a/jest-preset.json
+++ b/jest-preset.json
@@ -2,6 +2,7 @@
   "haste": {
     "defaultPlatform": "ios",
     "platforms": ["android", "ios", "native"],
+    "hasteImplModulePath": "<rootDir>/node_modules/react-native/jest/hasteImpl.js",
     "providesModuleNodeModules": [
       "react-native"
     ]

From aa6f394c4236e5a4998c3be8ed61ec1bab950775 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Wed, 2 May 2018 07:37:35 -0700
Subject: [PATCH 0420/1109] Enable `?.` plugins in RN

Summary: Enable the optional chaining operator plugins for React Native.

Reviewed By: rafeca

Differential Revision: D7828244

fbshipit-source-id: 659a8a82ff6d656a5cb2f33377d85b668b93a9ea
---
 babel-preset/configs/main.js | 4 ++++
 babel-preset/package.json    | 1 +
 2 files changed, 5 insertions(+)

diff --git a/babel-preset/configs/main.js b/babel-preset/configs/main.js
index 0b972f595b74..e6aeeec39865 100644
--- a/babel-preset/configs/main.js
+++ b/babel-preset/configs/main.js
@@ -52,6 +52,7 @@ const exponentiationOperator = [
 ];
 const objectAssign = [require('@babel/plugin-transform-object-assign')];
 const objectRestSpread = [require('@babel/plugin-proposal-object-rest-spread')];
+const optionalChaining = [require('@babel/plugin-proposal-optional-chaining')];
 const reactDisplayName = [
   require('@babel/plugin-transform-react-display-name'),
 ];
@@ -98,6 +99,9 @@ const getPreset = (src, options) => {
   ) {
     extraPlugins.push(reactDisplayName);
   }
+  if (isNull || src.indexOf('?.') !== -1) {
+    extraPlugins.push(optionalChaining);
+  }
 
   if (options && options.dev) {
     extraPlugins.push(reactJsxSource);
diff --git a/babel-preset/package.json b/babel-preset/package.json
index 691941cf378b..b69d3d301cc8 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -17,6 +17,7 @@
   "dependencies": {
     "@babel/plugin-proposal-class-properties": "7.0.0-beta.40",
     "@babel/plugin-proposal-object-rest-spread": "7.0.0-beta.40",
+    "@babel/plugin-proposal-optional-chaining": "7.0.0-beta.40",
     "@babel/plugin-transform-arrow-functions": "7.0.0-beta.40",
     "@babel/plugin-transform-block-scoping": "7.0.0-beta.40",
     "@babel/plugin-transform-classes": "7.0.0-beta.40",

From ba88292130de42fa4117d1ad1c079f779746593e Mon Sep 17 00:00:00 2001
From: Eric Rozell <erozell@outlook.com>
Date: Wed, 2 May 2018 10:56:23 -0700
Subject: [PATCH 0421/1109] Support platform-specific prop type overrides

Summary:
Moves `PlatformViewPropTypes` to the end of `ViewPropTypes` so platforms can override prop type values. An example of this is in `react-native-windows`, we want to support additional values for the `importantForAccessibility` prop type that are specific to Windows (more details in [this PR](https://github.com/Microsoft/react-native-windows/pull/1807)).

Thank you for sending the PR! We appreciate you spending the time to work on these changes.
Help us understand your motivation by explaining why you decided to make this change.

<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Run jest tests, test RNTester on iOS and Android. Did not test tvOS, but this should not impact tvOS as the only props included from `PlatformViewPropTypes` are unique (i.e., are not overridden in this file).

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

https://github.com/Microsoft/react-native-windows/pull/1807

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[CATEGORY] [TYPE] [LOCATION] - Message

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->

[GENERAL][Enhancement][View] - Make `ViewPropTypes` more friendly to platform extensions.
Closes https://github.com/facebook/react-native/pull/19090

Differential Revision: D7846438

Pulled By: shergin

fbshipit-source-id: e51ee3256d1c21001b371bd07da21319f3ecd810
---
 Libraries/Components/View/ViewPropTypes.js | 7 +++++--
 1 file changed, 5 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index f5f03bf10efd..40cd8121cd99 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -73,8 +73,6 @@ export type ViewProps = {
 } & TVViewProps;
 
 module.exports = {
-  ...PlatformViewPropTypes,
-
   /**
    * When `true`, indicates that the view is an accessibility element.
    * By default, all the touchable elements are accessible.
@@ -427,4 +425,9 @@ module.exports = {
    * See http://facebook.github.io/react-native/docs/view.html#needsoffscreenalphacompositing
    */
   needsOffscreenAlphaCompositing: PropTypes.bool,
+  
+  /**
+   * Any additional platform-specific view prop types, or prop type overrides.
+   */
+  ...PlatformViewPropTypes,
 };

From 23d61b35fb6fdbfb84f77b6d99ff155a0ff868e6 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 2 May 2018 15:19:50 -0700
Subject: [PATCH 0422/1109] Breaking change - Disable WebView geolocation by
 default

Reviewed By: yungsters

Differential Revision: D7846198

fbshipit-source-id: 8d6daff4b794d3569b5ddba2d8d62af8c7ff5b03
---
 Libraries/Components/WebView/WebView.android.js           | 7 +++++++
 .../facebook/react/views/webview/ReactWebViewManager.java | 8 ++++++++
 2 files changed, 15 insertions(+)

diff --git a/Libraries/Components/WebView/WebView.android.js b/Libraries/Components/WebView/WebView.android.js
index a457298f96f6..6f0ac9b57fb0 100644
--- a/Libraries/Components/WebView/WebView.android.js
+++ b/Libraries/Components/WebView/WebView.android.js
@@ -138,6 +138,12 @@ class WebView extends React.Component {
      */
     domStorageEnabled: PropTypes.bool,
 
+    /**
+     * Sets whether Geolocation is enabled. The default is false.
+     * @platform android
+     */
+    geolocationEnabled: PropTypes.bool,
+
     /**
      * Sets the JS to be injected when the webpage loads.
      */
@@ -310,6 +316,7 @@ class WebView extends React.Component {
         onLoadingFinish={this.onLoadingFinish}
         onLoadingError={this.onLoadingError}
         testID={this.props.testID}
+        geolocationEnabled={this.props.geolocationEnabled}
         mediaPlaybackRequiresUserAction={this.props.mediaPlaybackRequiresUserAction}
         allowUniversalAccessFromFileURLs={this.props.allowUniversalAccessFromFileURLs}
         mixedContentMode={this.props.mixedContentMode}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
index 3097beea5aad..a580a2bc4a18 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
@@ -384,6 +384,7 @@ public void onGeolocationPermissionsShowPrompt(String origin, GeolocationPermiss
             new LayoutParams(LayoutParams.MATCH_PARENT,
                 LayoutParams.MATCH_PARENT));
 
+    setGeolocationEnabled(webView, false);
     if (ReactBuildConfig.DEBUG && Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
       WebView.setWebContentsDebuggingEnabled(true);
     }
@@ -538,6 +539,13 @@ public void setUrlPrefixesForDefaultIntent(
     }
   }
 
+  @ReactProp(name = "geolocationEnabled")
+  public void setGeolocationEnabled(
+    WebView view,
+    @Nullable Boolean isGeolocationEnabled) {
+    view.getSettings().setGeolocationEnabled(isGeolocationEnabled != null && isGeolocationEnabled);
+  }
+
   @Override
   protected void addEventEmitters(ThemedReactContext reactContext, WebView view) {
     // Do not register default touch emitter and let WebView implementation handle touches

From 56d48bd9ecd2d0f08625259121312531064a09f2 Mon Sep 17 00:00:00 2001
From: Jacky Wijaya <jekiwijaya@hotmail.com>
Date: Wed, 2 May 2018 18:49:17 -0700
Subject: [PATCH 0423/1109] Fix Android, DevServerHelper from calling okhttp3
 response.body.string() twice

Summary:
Fixing from call response.body.string() twice in DevServerHelper.java.
https://github.com/square/okhttp/issues/1240#issuecomment-68142603

I'm getting error like this
```
05-01 21:16:47.080 22836-23064/com.my.company.bundle E/AndroidRuntime: FATAL EXCEPTION: OkHttp Dispatcher
                                                                               Process: com.my.company.bundle, PID: 22836
                                                                               java.lang.IllegalStateException: closed
                                                                                   at okio.RealBufferedSource.rangeEquals(RealBufferedSource.java:398)
                                                                                   at okio.RealBufferedSource.rangeEquals(RealBufferedSource.java:392)
                                                                                   at okhttp3.internal.c.a(Util.java:449)
                                                                                   at okhttp3.v.string(ResponseBody.java:174)
                                                                                   at com.facebook.react.devsupport.f$8.onResponse(DevServerHelper.java:487)
                                                                                   at com.newrelic.agent.android.instrumentation.okhttp3.CallbackExtension.onResponse(CallbackExtension.java:41)
                                                                                   at okhttp3.s$a.c(RealCall.java:153)
                                                                                   at okhttp3.internal.b.run(NamedRunnable.java:32)
                                                                                   at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162)
                                                                                   at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636)
                                                                                   at java.lang.Thread.run(Thread.java:764)
```

<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

- In my case, My device is using a Proxy, and tried to connect the packager. When it failed from connecting packager through websocket, It crash by this line of code.
<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [BUGFIX] [DevServerHelper] - fixing from calling body.string() twice.

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/19088

Differential Revision: D7853822

Pulled By: mdvacca

fbshipit-source-id: c11a73ce2fa6d40b0a7bd8bc0fca7b07c6bc27ed
---
 .../java/com/facebook/react/devsupport/DevServerHelper.java  | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
index 09d87f280880..946377680e69 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
@@ -479,10 +479,11 @@ public void onResponse(Call call, Response response) throws IOException {
               callback.onPackagerStatusFetched(false);
               return;
             }
-            if (!PACKAGER_OK_STATUS.equals(body.string())) {
+            String bodyString = body.string(); // cannot call body.string() twice, stored it into variable. https://github.com/square/okhttp/issues/1240#issuecomment-68142603
+            if (!PACKAGER_OK_STATUS.equals(bodyString)) {
               FLog.e(
                   ReactConstants.TAG,
-                  "Got unexpected response from packager when requesting status: " + body.string());
+                  "Got unexpected response from packager when requesting status: " + bodyString);
               callback.onPackagerStatusFetched(false);
               return;
             }

From be379efc9b677eac039a3d241d03aa4bb10d6a64 Mon Sep 17 00:00:00 2001
From: Jonathan Kim <jjkim@fb.com>
Date: Wed, 2 May 2018 22:09:17 -0700
Subject: [PATCH 0424/1109] Minimize included defs by adding a level of
 indirection

Reviewed By: zertosh

Differential Revision: D7851714

fbshipit-source-id: aa14e003a612173c6f316cb76a26f7e78e7f15d4
---
 ReactCommon/fabric/uimanager/BUCK | 7 +++----
 ReactCommon/fabric/view/BUCK      | 8 +++-----
 2 files changed, 6 insertions(+), 9 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 209502316d2b..6745136cf817 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -1,5 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "ANDROID", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -57,9 +57,8 @@ rn_xplat_cxx_library(
 )
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
-
-    cxx_test(
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+    fb_xplat_cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
         headers = glob(["tests/**/*.h"]),
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index d6ef5a048cfb..1f2cff2c3fc7 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -1,6 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags")
-load("//ReactNative:DEFS.bzl", "react_native_xplat_target")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -61,9 +60,8 @@ rn_xplat_cxx_library(
 )
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
-
-    cxx_test(
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+    fb_xplat_cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
         headers = glob(["tests/**/*.h"]),

From e8662a2123a0dfd4caefb2233a6df29faa0774b0 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 3 May 2018 08:38:00 -0700
Subject: [PATCH 0425/1109] Add react dev menu setting for cpp deltas

Summary:
Adds a menu item to enable handling of JS module deltas in native code.
The check box is dependent on JS Deltas being activated in the first place.

Reviewed By: cpojer

Differential Revision: D7380167

fbshipit-source-id: 3001d12140542b4e52b1ce96be3c5f56e52a15f8
---
 .../react/devsupport/DevInternalSettings.java        | 12 ++++++++++++
 .../src/main/res/devsupport/xml/preferences.xml      |  7 +++++++
 2 files changed, 19 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevInternalSettings.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevInternalSettings.java
index e3204e6457bf..5c07b7ead430 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevInternalSettings.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevInternalSettings.java
@@ -30,6 +30,7 @@ public class DevInternalSettings implements
   private static final String PREFS_JS_DEV_MODE_DEBUG_KEY = "js_dev_mode_debug";
   private static final String PREFS_JS_MINIFY_DEBUG_KEY = "js_minify_debug";
   private static final String PREFS_JS_BUNDLE_DELTAS_KEY = "js_bundle_deltas";
+  private static final String PREFS_JS_BUNDLE_DELTAS_CPP_KEY = "js_bundle_deltas_cpp";
   private static final String PREFS_ANIMATIONS_DEBUG_KEY = "animations_debug";
   private static final String PREFS_RELOAD_ON_JS_CHANGE_KEY = "reload_on_js_change";
   private static final String PREFS_INSPECTOR_DEBUG_KEY = "inspector_debug";
@@ -83,6 +84,7 @@ public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, Strin
           || PREFS_RELOAD_ON_JS_CHANGE_KEY.equals(key)
           || PREFS_JS_DEV_MODE_DEBUG_KEY.equals(key)
           || PREFS_JS_BUNDLE_DELTAS_KEY.equals(key)
+          || PREFS_JS_BUNDLE_DELTAS_CPP_KEY.equals(key)
           || PREFS_JS_MINIFY_DEBUG_KEY.equals(key)) {
         mListener.onInternalSettingsChanged();
       }
@@ -123,6 +125,16 @@ public void setBundleDeltasEnabled(boolean enabled) {
     mPreferences.edit().putBoolean(PREFS_JS_BUNDLE_DELTAS_KEY, enabled).apply();
   }
 
+  @SuppressLint("SharedPreferencesUse")
+  public boolean isBundleDeltasCppEnabled() {
+    return mPreferences.getBoolean(PREFS_JS_BUNDLE_DELTAS_CPP_KEY, false);
+  }
+
+  @SuppressLint("SharedPreferencesUse")
+  public void setBundleDeltasCppEnabled(boolean enabled) {
+    mPreferences.edit().putBoolean(PREFS_JS_BUNDLE_DELTAS_CPP_KEY, enabled).apply();
+  }
+
   @Override
   public boolean isNuclideJSDebugEnabled() {
     return ReactBuildConfig.IS_INTERNAL_BUILD && ReactBuildConfig.DEBUG;
diff --git a/ReactAndroid/src/main/res/devsupport/xml/preferences.xml b/ReactAndroid/src/main/res/devsupport/xml/preferences.xml
index 7ce20de3fa5b..bb98248b93f0 100644
--- a/ReactAndroid/src/main/res/devsupport/xml/preferences.xml
+++ b/ReactAndroid/src/main/res/devsupport/xml/preferences.xml
@@ -25,6 +25,13 @@
       android:summary="Request delta bundles from metro to get faster reloads (Experimental)"
       android:defaultValue="true"
       />
+    <CheckBoxPreference
+      android:key="js_bundle_deltas_cpp"
+      android:title="Native Delta Handling"
+      android:summary="Handles delta bundles in native code without writing code to disk (Experimental)."
+      android:defaultValue="false"
+      android:dependency="js_bundle_deltas"
+      />
     <CheckBoxPreference
         android:key="animations_debug"
         android:title="Animations FPS Summaries"

From 4d931d529ef15f3fd4eeafa577c537e16670c4c2 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 3 May 2018 08:38:01 -0700
Subject: [PATCH 0426/1109] Add native delta client for Metro

Summary:
Adds C++ delta client that keeps modules in memory, and can be used as a RAM bundle.

For now, this client expects a `folly::dynamic` object as payload for patches, i.e. the JSON response retrieved from Metro needs to be parsed with `folly::parseJson` by the caller.

In the future, we will replace JSON with a streaming friendly binary format.

Reviewed By: fromcelticpark

Differential Revision: D7845136

fbshipit-source-id: f003f98a2607c8354c427a7e60e01e19e20295b1
---
 .../jni/react/jni/JniJSModulesUnbundle.cpp    |  2 +-
 ReactCommon/cxxreact/Android.mk               |  1 +
 ReactCommon/cxxreact/BUCK                     |  1 +
 ReactCommon/cxxreact/JSDeltaBundleClient.cpp  | 72 +++++++++++++++++++
 ReactCommon/cxxreact/JSDeltaBundleClient.h    | 42 +++++++++++
 ReactCommon/cxxreact/JSModulesUnbundle.h      |  4 ++
 6 files changed, 121 insertions(+), 1 deletion(-)
 create mode 100644 ReactCommon/cxxreact/JSDeltaBundleClient.cpp
 create mode 100644 ReactCommon/cxxreact/JSDeltaBundleClient.h

diff --git a/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.cpp b/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.cpp
index be00bfdcbee2..504f937c0cf2 100644
--- a/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.cpp
@@ -82,7 +82,7 @@ JSModulesUnbundle::Module JniJSModulesUnbundle::getModule(uint32_t moduleId) con
     buffer = static_cast<const char *>(AAsset_getBuffer(asset.get()));
   }
   if (buffer == nullptr) {
-    throw ModuleNotFound("Module not found: " + sourceUrl);
+    throw ModuleNotFound(moduleId);
   }
   return {sourceUrl, std::string(buffer, AAsset_getLength(asset.get()))};
 }
diff --git a/ReactCommon/cxxreact/Android.mk b/ReactCommon/cxxreact/Android.mk
index 1c22c761e6ef..8efb42a3a150 100644
--- a/ReactCommon/cxxreact/Android.mk
+++ b/ReactCommon/cxxreact/Android.mk
@@ -17,6 +17,7 @@ LOCAL_SRC_FILES := \
   JSCSamplingProfiler.cpp \
   JSCTracing.cpp \
   JSCUtils.cpp \
+  JSDeltaBundleClient.cpp \
 	JSExecutor.cpp \
   JSIndexedRAMBundle.cpp \
   MethodCall.cpp \
diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 515ff8cb35df..c5b958918f7b 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -92,6 +92,7 @@ CXXREACT_PUBLIC_HEADERS = [
     "JSCExecutor.h",
     "JSCNativeModules.h",
     "JSCUtils.h",
+    "JSDeltaBundleClient.h",
     "JSIndexedRAMBundle.h",
     "JSModulesUnbundle.h",
     "MessageQueueThread.h",
diff --git a/ReactCommon/cxxreact/JSDeltaBundleClient.cpp b/ReactCommon/cxxreact/JSDeltaBundleClient.cpp
new file mode 100644
index 000000000000..8c082d04c8fb
--- /dev/null
+++ b/ReactCommon/cxxreact/JSDeltaBundleClient.cpp
@@ -0,0 +1,72 @@
+#include "JSDeltaBundleClient.h"
+
+#include <sstream>
+
+#include <folly/Memory.h>
+
+namespace facebook {
+namespace react {
+
+namespace {
+  std::string startupCode(const folly::dynamic *pre, const folly::dynamic *post) {
+    std::ostringstream startupCode;
+
+    for (auto section : {pre, post}) {
+      if (section != nullptr) {
+        for (folly::dynamic pair : *section) {
+          startupCode << pair[1].getString() << '\n';
+        }
+      }
+    }
+
+    return startupCode.str();
+  }
+} // namespace
+
+void JSDeltaBundleClient::patch(const folly::dynamic& delta) {
+  auto const reset = delta.get_ptr("reset");
+  if (reset != nullptr && reset->asBool()) {
+    clear();
+  }
+
+  auto const pre = delta.get_ptr("pre");
+  auto const post = delta.get_ptr("post");
+
+  if ((pre != nullptr && pre->size() > 0) || (post != nullptr && post->size() > 0)) {
+    startupCode_ = startupCode(pre, post);
+  }
+
+  const folly::dynamic *modules = delta.get_ptr("delta");
+  if (modules != nullptr) {
+    for (const folly::dynamic pair : *modules) {
+      auto id = pair[0].getInt();
+      auto module = pair[1];
+      if (module.isNull()) {
+        modules_.erase(id);
+      } else {
+        modules_.emplace(id, module.getString());
+      }
+    }
+  }
+}
+
+JSModulesUnbundle::Module JSDeltaBundleClient::getModule(uint32_t moduleId) const {
+  auto search = modules_.find(moduleId);
+  if (search != modules_.end()) {
+    return {folly::to<std::string>(search->first, ".js"), search->second};
+  }
+
+  throw JSModulesUnbundle::ModuleNotFound(moduleId);
+}
+
+std::unique_ptr<const JSBigString> JSDeltaBundleClient::getStartupCode() const {
+  return folly::make_unique<JSBigStdString>(startupCode_);
+}
+
+void JSDeltaBundleClient::clear() {
+  modules_.clear();
+  startupCode_.clear();
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/cxxreact/JSDeltaBundleClient.h b/ReactCommon/cxxreact/JSDeltaBundleClient.h
new file mode 100644
index 000000000000..107bd39880df
--- /dev/null
+++ b/ReactCommon/cxxreact/JSDeltaBundleClient.h
@@ -0,0 +1,42 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <cstdint>
+#include <memory>
+#include <string>
+#include <unordered_map>
+
+#include <cxxreact/JSBigString.h>
+#include <cxxreact/JSModulesUnbundle.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+class JSDeltaBundleClient {
+public:
+  void patch(const folly::dynamic& delta);
+  JSModulesUnbundle::Module getModule(uint32_t moduleId) const;
+  std::unique_ptr<const JSBigString> getStartupCode() const;
+  void clear();
+
+private:
+  std::unordered_map<uint32_t, std::string> modules_;
+  std::string startupCode_;
+};
+
+class JSDeltaBundleClientRAMBundle : public JSModulesUnbundle {
+public:
+  JSDeltaBundleClientRAMBundle(
+    std::shared_ptr<const JSDeltaBundleClient> client) : client_(client) {}
+
+  Module getModule(uint32_t moduleId) const override {
+    return client_->getModule(moduleId);
+  }
+private:
+  const std::shared_ptr<const JSDeltaBundleClient> client_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/cxxreact/JSModulesUnbundle.h b/ReactCommon/cxxreact/JSModulesUnbundle.h
index a04d5808ccd7..bbf3a6c8d8c0 100644
--- a/ReactCommon/cxxreact/JSModulesUnbundle.h
+++ b/ReactCommon/cxxreact/JSModulesUnbundle.h
@@ -6,6 +6,7 @@
 #include <string>
 #include <stdexcept>
 
+#include <folly/Conv.h>
 #include <jschelpers/noncopyable.h>
 
 namespace facebook {
@@ -21,7 +22,10 @@ class JSModulesUnbundle : noncopyable {
    */
 public:
   class ModuleNotFound : public std::out_of_range {
+  public:
     using std::out_of_range::out_of_range;
+    ModuleNotFound(uint32_t moduleId) : std::out_of_range::out_of_range(
+      folly::to<std::string>("Module not found: ", moduleId)) {}
   };
   struct Module {
     std::string name;

From 82b8a9221ace6e13340d9e0dba27f69dca4edd99 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 3 May 2018 08:38:03 -0700
Subject: [PATCH 0427/1109] Add hybrid class to hold native delta client

Summary:
Adds hybrid JNI wrapper class that can hold a native delta client.

This class allows Java code in the `devsupport` package to hold onto a native delta client across reloads.
It also takes care of passing `okhttp` response objects to native code, where we build a `std::string` to hold JSON messages coming from Metro, and parse them with `folly::parseJson`.

In a follow-up, we will switch to a streaming-friendly binary format that will make allocating memory for the whole message unnecessary.

Reviewed By: fromcelticpark

Differential Revision: D7845138

fbshipit-source-id: 7a29b30645331addf843097dd0d05c03b3143991
---
 .../react/bridge/NativeDeltaClient.java       | 25 +++++++++
 .../src/main/jni/react/jni/Android.mk         |  1 +
 .../main/jni/react/jni/NativeDeltaClient.cpp  | 54 +++++++++++++++++++
 .../main/jni/react/jni/NativeDeltaClient.h    | 38 +++++++++++++
 .../src/main/jni/react/jni/OnLoad.cpp         |  2 +
 5 files changed, 120 insertions(+)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/bridge/NativeDeltaClient.java
 create mode 100644 ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp
 create mode 100644 ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/NativeDeltaClient.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/NativeDeltaClient.java
new file mode 100644
index 000000000000..6b87c972c275
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/NativeDeltaClient.java
@@ -0,0 +1,25 @@
+/**
+ * Copyright (c) 2018-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.bridge;
+
+import java.nio.channels.ReadableByteChannel;
+
+import com.facebook.jni.HybridData;
+
+public class NativeDeltaClient {
+  static {
+    ReactBridge.staticInit();
+  }
+
+  // C++ parts
+  private final HybridData mHybridData = initHybrid();
+  private native static HybridData initHybrid();
+
+  public native void reset();
+  public native void processDelta(ReadableByteChannel deltaMessage);
+}
diff --git a/ReactAndroid/src/main/jni/react/jni/Android.mk b/ReactAndroid/src/main/jni/react/jni/Android.mk
index 8d8b992d5243..313950674e13 100644
--- a/ReactAndroid/src/main/jni/react/jni/Android.mk
+++ b/ReactAndroid/src/main/jni/react/jni/Android.mk
@@ -18,6 +18,7 @@ LOCAL_SRC_FILES := \
   ModuleRegistryBuilder.cpp \
   NativeArray.cpp \
   NativeCommon.cpp \
+  NativeDeltaClient.cpp \
   NativeMap.cpp \
   OnLoad.cpp \
   ProxyExecutor.cpp \
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp b/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp
new file mode 100644
index 000000000000..2c35306caf84
--- /dev/null
+++ b/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp
@@ -0,0 +1,54 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include "NativeDeltaClient.h"
+
+#include <sstream>
+#include <fb/fbjni/ByteBuffer.h>
+#include <folly/json.h>
+
+namespace facebook {
+namespace react {
+
+jni::local_ref<NativeDeltaClient::jhybriddata> NativeDeltaClient::initHybrid(
+    jni::alias_ref<jclass>) {
+  return makeCxxInstance();
+}
+
+void NativeDeltaClient::registerNatives() {
+  registerHybrid({
+    makeNativeMethod("initHybrid", NativeDeltaClient::initHybrid),
+    makeNativeMethod("processDelta", NativeDeltaClient::jniProcessDelta),
+    makeNativeMethod("reset", NativeDeltaClient::jniReset),
+  });
+}
+
+void NativeDeltaClient::jniProcessDelta(
+    jni::alias_ref<jni::JReadableByteChannel> delta) {
+
+  std::ostringstream deltaMessage;
+  std::vector<uint8_t> buffer(8192);
+  auto byteBuffer = jni::JByteBuffer::wrapBytes(buffer.data(), buffer.size());
+
+  size_t pos = 0;
+  int read = 0;
+  do {
+    read = delta->read(byteBuffer);
+    if (read < 1) {
+      deltaMessage.write(reinterpret_cast<const char *>(buffer.data()), pos);
+      byteBuffer->rewind();
+      pos = 0;
+    } else {
+      pos += read;
+    }
+  } while (read != -1);
+
+
+  deltaClient_->patch(folly::parseJson(deltaMessage.str()));
+}
+
+void NativeDeltaClient::jniReset() {
+  deltaClient_->clear();
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h b/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h
new file mode 100644
index 000000000000..5e2eea14ae22
--- /dev/null
+++ b/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h
@@ -0,0 +1,38 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <memory>
+
+#include <cxxreact/JSDeltaBundleClient.h>
+#include <fb/fbjni.h>
+#include <fb/fbjni/Hybrid.h>
+#include <fb/fbjni/ReadableByteChannel.h>
+
+namespace facebook {
+namespace react {
+
+class NativeDeltaClient : public jni::HybridClass<NativeDeltaClient> {
+
+public:
+  static constexpr auto kJavaDescriptor =
+    "Lcom/facebook/react/bridge/NativeDeltaClient;";
+  static jni::local_ref<jhybriddata> initHybrid(jni::alias_ref<jclass>);
+  static void registerNatives();
+
+  ~NativeDeltaClient() override = default;
+
+  std::shared_ptr<const JSDeltaBundleClient> getDeltaClient() {
+    return deltaClient_;
+  }
+
+private:
+  friend HybridBase;
+  void jniProcessDelta(jni::alias_ref<jni::JReadableByteChannel> delta);
+  void jniReset();
+  const std::shared_ptr<JSDeltaBundleClient> deltaClient_ =
+    std::make_shared<JSDeltaBundleClient>();
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp b/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
index ec97e56e5b1d..81cc8f334196 100644
--- a/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
@@ -16,6 +16,7 @@
 #include "CxxModuleWrapper.h"
 #include "JavaScriptExecutorHolder.h"
 #include "JCallback.h"
+#include "NativeDeltaClient.h"
 #include "ProxyExecutor.h"
 #include "WritableNativeArray.h"
 #include "WritableNativeMap.h"
@@ -91,6 +92,7 @@ extern "C" JNIEXPORT jint JNI_OnLoad(JavaVM* vm, void* reserved) {
     CxxModuleWrapper::registerNatives();
     JCxxCallbackImpl::registerNatives();
     NativeArray::registerNatives();
+    NativeDeltaClient::registerNatives();
     ReadableNativeArray::registerNatives();
     WritableNativeArray::registerNatives();
     NativeMap::registerNatives();

From 36f254aa75316d3605d4becee8a6dc8fb2e202cc Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 3 May 2018 08:38:06 -0700
Subject: [PATCH 0428/1109] `CatalystInstanceImpl`: Method for loading from
 delta client

Summary:
Adds `loadScriptFromDeltaBundle` / `jniLoadScriptFromDeltaBundle` methods to `CatalystInstanceImpl`.

These methods allow to run JS coming from a native delta client as RAM bundles, to leverage the RAM bundle mechanism for development / reload scenarios.

Reviewed By: fromcelticpark

Differential Revision: D7845140

fbshipit-source-id: b79b340f36c28939a31eb63a3c463d0792a208f7
---
 .../react/bridge/CatalystInstanceImpl.java     |  9 +++++++++
 .../jni/react/jni/CatalystInstanceImpl.cpp     | 18 ++++++++++++++++++
 .../main/jni/react/jni/CatalystInstanceImpl.h  |  2 ++
 3 files changed, 29 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
index 7ab1216267db..b8930d1a4154 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
@@ -221,10 +221,19 @@ public void registerSegment(int segmentId, String path) {
     jniLoadScriptFromFile(fileName, sourceURL, loadSynchronously);
   }
 
+  /* package */ void loadScriptFromDeltaBundle(
+    String sourceURL,
+    NativeDeltaClient deltaClient,
+    boolean loadSynchronously) {
+    mSourceURL = sourceURL;
+    jniLoadScriptFromDeltaBundle(sourceURL, deltaClient, loadSynchronously);
+  }
+
   private native void jniSetSourceURL(String sourceURL);
   private native void jniRegisterSegment(int segmentId, String path);
   private native void jniLoadScriptFromAssets(AssetManager assetManager, String assetURL, boolean loadSynchronously);
   private native void jniLoadScriptFromFile(String fileName, String sourceURL, boolean loadSynchronously);
+  private native void jniLoadScriptFromDeltaBundle(String sourceURL, NativeDeltaClient deltaClient, boolean loadSynchronously);
 
   @Override
   public void runJSBundle() {
diff --git a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
index 7b136f0d0cdf..aeb4cc55e109 100644
--- a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
@@ -4,17 +4,21 @@
 
 #include <mutex>
 #include <condition_variable>
+#include <sstream>
+#include <vector>
 
 #include <cxxreact/CxxNativeModule.h>
 #include <cxxreact/Instance.h>
 #include <cxxreact/JSBigString.h>
 #include <cxxreact/JSBundleType.h>
+#include <cxxreact/JSDeltaBundleClient.h>
 #include <cxxreact/JSIndexedRAMBundle.h>
 #include <cxxreact/MethodCall.h>
 #include <cxxreact/ModuleRegistry.h>
 #include <cxxreact/RecoverableError.h>
 #include <cxxreact/RAMBundleRegistry.h>
 #include <fb/log.h>
+#include <fb/fbjni/ByteBuffer.h>
 #include <folly/dynamic.h>
 #include <folly/Memory.h>
 #include <jni/Countable.h>
@@ -100,6 +104,7 @@ void CatalystInstanceImpl::registerNatives() {
     makeNativeMethod("jniRegisterSegment", CatalystInstanceImpl::jniRegisterSegment),
     makeNativeMethod("jniLoadScriptFromAssets", CatalystInstanceImpl::jniLoadScriptFromAssets),
     makeNativeMethod("jniLoadScriptFromFile", CatalystInstanceImpl::jniLoadScriptFromFile),
+    makeNativeMethod("jniLoadScriptFromDeltaBundle", CatalystInstanceImpl::jniLoadScriptFromDeltaBundle),
     makeNativeMethod("jniCallJSFunction", CatalystInstanceImpl::jniCallJSFunction),
     makeNativeMethod("jniCallJSCallback", CatalystInstanceImpl::jniCallJSCallback),
     makeNativeMethod("setGlobalVariable", CatalystInstanceImpl::setGlobalVariable),
@@ -210,6 +215,19 @@ void CatalystInstanceImpl::jniLoadScriptFromFile(const std::string& fileName,
   }
 }
 
+void CatalystInstanceImpl::jniLoadScriptFromDeltaBundle(
+    const std::string& sourceURL,
+    jni::alias_ref<NativeDeltaClient::jhybridobject> jDeltaClient,
+    bool loadSynchronously) {
+
+  auto deltaClient = jDeltaClient->cthis()->getDeltaClient();
+  auto registry = RAMBundleRegistry::singleBundleRegistry(
+    folly::make_unique<JSDeltaBundleClientRAMBundle>(deltaClient));
+
+  instance_->loadRAMBundle(
+    std::move(registry), deltaClient->getStartupCode(), sourceURL, loadSynchronously);
+}
+
 void CatalystInstanceImpl::jniCallJSFunction(std::string module, std::string method, NativeArray* arguments) {
   // We want to share the C++ code, and on iOS, modules pass module/method
   // names as strings all the way through to JS, and there's no way to do
diff --git a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h
index 5f7b1be15157..622edb769d0f 100644
--- a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h
+++ b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h
@@ -10,6 +10,7 @@
 #include "JMessageQueueThread.h"
 #include "JSLoader.h"
 #include "ModuleRegistryBuilder.h"
+#include "NativeDeltaClient.h"
 
 namespace facebook {
 namespace react {
@@ -66,6 +67,7 @@ class CatalystInstanceImpl : public jni::HybridClass<CatalystInstanceImpl> {
 
   void jniLoadScriptFromAssets(jni::alias_ref<JAssetManager::javaobject> assetManager, const std::string& assetURL, bool loadSynchronously);
   void jniLoadScriptFromFile(const std::string& fileName, const std::string& sourceURL, bool loadSynchronously);
+  void jniLoadScriptFromDeltaBundle(const std::string& sourceURL, jni::alias_ref<NativeDeltaClient::jhybridobject> deltaClient, bool loadSynchronously);
   void jniCallJSFunction(std::string module, std::string method, NativeArray* arguments);
   void jniCallJSCallback(jint callbackId, NativeArray* arguments);
   void setGlobalVariable(std::string propName,

From 3e730528eea3c2a8dc4dda58bed87377122a288a Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 3 May 2018 08:38:08 -0700
Subject: [PATCH 0429/1109] Allow to not use native delta client

Summary:
Adds the possibility to disable native delta clients in `DevInternalSettings`

Depending on the bridge in use, there might not be support for native delta clients, but since the settings are shared app-wide, it can not be enabled individually.

Reviewed By: johnislarry

Differential Revision: D7845137

fbshipit-source-id: ab368e6fed0f4bec49032c4a20466e156d20fdae
---
 .../react/devsupport/DevInternalSettings.java   | 17 ++++++++++++++++-
 1 file changed, 16 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevInternalSettings.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevInternalSettings.java
index 5c07b7ead430..e9ebe0c2492f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevInternalSettings.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevInternalSettings.java
@@ -40,14 +40,29 @@ public class DevInternalSettings implements
   private final SharedPreferences mPreferences;
   private final Listener mListener;
   private final PackagerConnectionSettings mPackagerConnectionSettings;
+  private final boolean mSupportsNativeDeltaClients;
+
+  public static DevInternalSettings withoutNativeDeltaClient(
+      Context applicationContext,
+      Listener listener) {
+    return new DevInternalSettings(applicationContext, listener, false);
+  }
 
   public DevInternalSettings(
       Context applicationContext,
       Listener listener) {
+    this(applicationContext, listener, true);
+  }
+
+  private DevInternalSettings(
+      Context applicationContext,
+      Listener listener,
+      boolean supportsNativeDeltaClients) {
     mListener = listener;
     mPreferences = PreferenceManager.getDefaultSharedPreferences(applicationContext);
     mPreferences.registerOnSharedPreferenceChangeListener(this);
     mPackagerConnectionSettings = new PackagerConnectionSettings(applicationContext);
+    mSupportsNativeDeltaClients = supportsNativeDeltaClients;
   }
 
   public PackagerConnectionSettings getPackagerConnectionSettings() {
@@ -127,7 +142,7 @@ public void setBundleDeltasEnabled(boolean enabled) {
 
   @SuppressLint("SharedPreferencesUse")
   public boolean isBundleDeltasCppEnabled() {
-    return mPreferences.getBoolean(PREFS_JS_BUNDLE_DELTAS_CPP_KEY, false);
+    return mSupportsNativeDeltaClients && mPreferences.getBoolean(PREFS_JS_BUNDLE_DELTAS_CPP_KEY, false);
   }
 
   @SuppressLint("SharedPreferencesUse")

From 8f85abdb14b4e4abf521e23cf69e15d06a8c3480 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 3 May 2018 08:38:11 -0700
Subject: [PATCH 0430/1109] `JSBundleLoader`: allow to load with delta client

Summary: Adds glue between `CatalystInstance` and `JSBundleLoader`: Adds the possibility to create a `JSBundleLoader` instance that calls into `CatalystInstanceImpl#loadScriptFromDeltaBundle(...)`.

Reviewed By: fromcelticpark

Differential Revision: D7845134

fbshipit-source-id: 9585b44a6e7c63245c9f634543642be55c928896
---
 .../facebook/react/bridge/JSBundleLoader.java | 23 +++++++++++++++++++
 1 file changed, 23 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSBundleLoader.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSBundleLoader.java
index 61bc6f018162..c62b1675aa0f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSBundleLoader.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSBundleLoader.java
@@ -8,6 +8,7 @@
 package com.facebook.react.bridge;
 
 import android.content.Context;
+import com.facebook.react.bridge.NativeDeltaClient;
 import com.facebook.react.common.DebugServerException;
 
 /**
@@ -78,6 +79,28 @@ public String loadScript(CatalystInstanceImpl instance) {
     };
   }
 
+  /**
+   * This loader is used to load delta bundles from the dev server. We pass each delta message to
+   * the loader and process it in C++. Passing it as a string leads to inefficiencies due to memory
+   * copies, which will have to be addressed in a follow-up.
+   * @param nativeDeltaClient
+   */
+  public static JSBundleLoader createDeltaFromNetworkLoader(
+    final String sourceURL,
+    final NativeDeltaClient nativeDeltaClient) {
+    return new JSBundleLoader() {
+      @Override
+      public String loadScript(CatalystInstanceImpl instance) {
+        try {
+          instance.loadScriptFromDeltaBundle(sourceURL, nativeDeltaClient, false);
+          return sourceURL;
+        } catch (Exception e) {
+          throw DebugServerException.makeGeneric(e.getMessage(), e);
+        }
+      }
+    };
+  }
+
   /**
    * This loader is used when proxy debugging is enabled. In that case there is no point in fetching
    * the bundle from device as remote executor will have to do it anyway.

From dd036c23284c52da693302727b4d1b112c37e807 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 3 May 2018 08:38:13 -0700
Subject: [PATCH 0431/1109] Hook up native delta client

Summary:
Adds support for native clients to `ReactAndroid`:
- `.devsupport.BundleDeltaClient` is now abstract with two implementations: the existing Java client, and a native client
- `BundleDeltaClient#processDelta(...)` can now return a native delta client object
- if that client object is non-null, the bridge is started up with that client rather than a script written to disk

Reviewed By: fromcelticpark

Differential Revision: D7845135

fbshipit-source-id: 379a9c6f9319c62eec3c370cda9ffa0969266a29
---
 .../facebook/react/ReactInstanceManager.java  |  23 +-
 .../react/devsupport/BundleDeltaClient.java   | 224 ++++++++++++------
 .../react/devsupport/BundleDownloader.java    |  52 ++--
 .../react/devsupport/DevServerHelper.java     |  12 +-
 .../devsupport/DevSupportManagerImpl.java     |   7 +-
 .../ReactInstanceManagerDevHelper.java        |   4 +-
 .../interfaces/DevBundleDownloadListener.java |   3 +-
 7 files changed, 222 insertions(+), 103 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index b97f6f45bab2..24a57c759b15 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -50,6 +50,7 @@
 import com.facebook.react.bridge.JavaJSExecutor;
 import com.facebook.react.bridge.JavaScriptExecutor;
 import com.facebook.react.bridge.JavaScriptExecutorFactory;
+import com.facebook.react.bridge.NativeDeltaClient;
 import com.facebook.react.bridge.NativeModuleCallExceptionHandler;
 import com.facebook.react.bridge.NativeModuleRegistry;
 import com.facebook.react.bridge.NotThreadSafeBridgeIdleDebugListener;
@@ -84,6 +85,7 @@
 import com.facebook.soloader.SoLoader;
 import com.facebook.systrace.Systrace;
 import com.facebook.systrace.SystraceMessage;
+
 import java.util.ArrayList;
 import java.util.Collection;
 import java.util.Collections;
@@ -270,8 +272,8 @@ public void onReloadWithJSDebugger(JavaJSExecutor.Factory jsExecutorFactory) {
       }
 
       @Override
-      public void onJSBundleLoadedFromServer() {
-        ReactInstanceManager.this.onJSBundleLoadedFromServer();
+      public void onJSBundleLoadedFromServer(@Nullable NativeDeltaClient nativeDeltaClient) {
+        ReactInstanceManager.this.onJSBundleLoadedFromServer(nativeDeltaClient);
       }
 
       @Override
@@ -360,7 +362,7 @@ private void recreateReactContextInBackgroundInner() {
           !devSettings.isRemoteJSDebugEnabled()) {
         // If there is a up-to-date bundle downloaded from server,
         // with remote JS debugging disabled, always use that.
-        onJSBundleLoadedFromServer();
+        onJSBundleLoadedFromServer(null);
       } else if (mBundleLoader == null) {
         mDevSupportManager.handleReloadJS();
       } else {
@@ -848,12 +850,17 @@ private void onReloadWithJSDebugger(JavaJSExecutor.Factory jsExecutorFactory) {
   }
 
   @ThreadConfined(UI)
-  private void onJSBundleLoadedFromServer() {
+  private void onJSBundleLoadedFromServer(@Nullable NativeDeltaClient nativeDeltaClient) {
     Log.d(ReactConstants.TAG, "ReactInstanceManager.onJSBundleLoadedFromServer()");
-    recreateReactContextInBackground(
-        mJavaScriptExecutorFactory,
-        JSBundleLoader.createCachedBundleFromNetworkLoader(
-            mDevSupportManager.getSourceUrl(), mDevSupportManager.getDownloadedJSBundleFile()));
+
+    JSBundleLoader bundleLoader = nativeDeltaClient == null
+        ? JSBundleLoader.createCachedBundleFromNetworkLoader(
+            mDevSupportManager.getSourceUrl(),
+            mDevSupportManager.getDownloadedJSBundleFile())
+        : JSBundleLoader.createDeltaFromNetworkLoader(
+            mDevSupportManager.getSourceUrl(), nativeDeltaClient);
+
+    recreateReactContextInBackground(mJavaScriptExecutorFactory, bundleLoader);
   }
 
   @ThreadConfined(UI)
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDeltaClient.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDeltaClient.java
index 68ef0ce138ae..93fbb49679e7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDeltaClient.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDeltaClient.java
@@ -1,121 +1,197 @@
+/**
+ * Copyright (c) 2018-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
 package com.facebook.react.devsupport;
 
-import android.util.JsonReader;
-import android.util.JsonToken;
 import java.io.File;
 import java.io.FileOutputStream;
 import java.io.IOException;
 import java.io.InputStreamReader;
 import java.util.LinkedHashMap;
 import javax.annotation.Nullable;
+
+import android.util.JsonReader;
+import android.util.JsonToken;
+import android.util.Pair;
+import com.facebook.react.bridge.NativeDeltaClient;
+import okhttp3.Headers;
+import okio.Buffer;
 import okio.BufferedSource;
 
-public class BundleDeltaClient {
+public abstract class BundleDeltaClient {
 
-  final LinkedHashMap<Number, byte[]> mPreModules = new LinkedHashMap<Number, byte[]>();
-  final LinkedHashMap<Number, byte[]> mDeltaModules = new LinkedHashMap<Number, byte[]>();
-  final LinkedHashMap<Number, byte[]> mPostModules = new LinkedHashMap<Number, byte[]>();
-  @Nullable String mDeltaId;
+  private static final String METRO_DELTA_ID_HEADER = "X-Metro-Delta-ID";
+  @Nullable private String mDeltaId;
 
-  static boolean isDeltaUrl(String bundleUrl) {
-    return bundleUrl.indexOf(".delta?") != -1;
+  public enum ClientType {
+    NONE,
+    DEV_SUPPORT,
+    NATIVE
   }
 
-  public void reset() {
-    mDeltaId = null;
-    mDeltaModules.clear();
-    mPreModules.clear();
-    mPostModules.clear();
+  static boolean isDeltaUrl(String bundleUrl) {
+    return bundleUrl.indexOf(".delta?") != -1;
   }
 
-  public String toDeltaUrl(String bundleURL) {
-    if (isDeltaUrl(bundleURL) && mDeltaId != null) {
-      return bundleURL + "&deltaBundleId=" + mDeltaId;
+  @Nullable
+  static BundleDeltaClient create(ClientType type) {
+    switch (type) {
+      case DEV_SUPPORT:
+        return new BundleDeltaJavaClient();
+      case NATIVE:
+        return new BundleDeltaNativeClient();
     }
-    return bundleURL;
+    return null;
   }
 
-  public synchronized boolean storeDeltaInFile(BufferedSource body, File outputFile)
-    throws IOException {
+  abstract public boolean canHandle(ClientType type);
 
-    JsonReader jsonReader = new JsonReader(new InputStreamReader(body.inputStream()));
+  abstract protected Pair<Boolean, NativeDeltaClient> processDelta(
+    BufferedSource body,
+    File outputFile) throws IOException;
 
-    jsonReader.beginObject();
+  final public String extendUrlForDelta(String bundleURL) {
+    return mDeltaId != null ? bundleURL + "&deltaBundleId=" + mDeltaId : bundleURL;
+  }
 
-    int numChangedModules = 0;
+  public void reset() {
+    mDeltaId = null;
+  }
 
-    while (jsonReader.hasNext()) {
-      String name = jsonReader.nextName();
-      if (name.equals("id")) {
-        mDeltaId = jsonReader.nextString();
-      } else if (name.equals("pre")) {
-        numChangedModules += patchDelta(jsonReader, mPreModules);
-      } else if (name.equals("post")) {
-        numChangedModules += patchDelta(jsonReader, mPostModules);
-      } else if (name.equals("delta")) {
-        numChangedModules += patchDelta(jsonReader, mDeltaModules);
-      } else {
-        jsonReader.skipValue();
-      }
-    }
+  public Pair<Boolean, NativeDeltaClient> processDelta(
+    Headers headers,
+    BufferedSource body,
+    File outputFile) throws IOException {
+
+    mDeltaId = headers.get(METRO_DELTA_ID_HEADER);
+    return processDelta(body, outputFile);
+  }
 
-    jsonReader.endObject();
-    jsonReader.close();
+  private static class BundleDeltaJavaClient extends BundleDeltaClient {
 
-    if (numChangedModules == 0) {
-      // If we receive an empty delta, we don't need to save the file again (it'll have the
-      // same content).
-      return false;
+    final LinkedHashMap<Number, byte[]> mPreModules = new LinkedHashMap<Number, byte[]>();
+    final LinkedHashMap<Number, byte[]> mDeltaModules = new LinkedHashMap<Number, byte[]>();
+    final LinkedHashMap<Number, byte[]> mPostModules = new LinkedHashMap<Number, byte[]>();
+
+    @Override
+    public boolean canHandle(ClientType type) {
+      return type == ClientType.DEV_SUPPORT;
     }
 
-    FileOutputStream fileOutputStream = new FileOutputStream(outputFile);
+    public void reset() {
+      super.reset();
+      mDeltaModules.clear();
+      mPreModules.clear();
+      mPostModules.clear();
+    }
 
-    try {
-      for (byte[] code : mPreModules.values()) {
-        fileOutputStream.write(code);
-        fileOutputStream.write('\n');
+    @Override
+    public synchronized Pair<Boolean, NativeDeltaClient> processDelta(
+      BufferedSource body,
+      File outputFile) throws IOException {
+
+      JsonReader jsonReader = new JsonReader(new InputStreamReader(body.inputStream()));
+      jsonReader.beginObject();
+      int numChangedModules = 0;
+
+      while (jsonReader.hasNext()) {
+        String name = jsonReader.nextName();
+        if (name.equals("pre")) {
+          numChangedModules += patchDelta(jsonReader, mPreModules);
+        } else if (name.equals("post")) {
+          numChangedModules += patchDelta(jsonReader, mPostModules);
+        } else if (name.equals("delta")) {
+          numChangedModules += patchDelta(jsonReader, mDeltaModules);
+        } else {
+          jsonReader.skipValue();
+        }
       }
 
-      for (byte[] code : mDeltaModules.values()) {
-        fileOutputStream.write(code);
-        fileOutputStream.write('\n');
+      jsonReader.endObject();
+      jsonReader.close();
+
+      if (numChangedModules == 0) {
+        // If we receive an empty delta, we don't need to save the file again (it'll have the
+        // same content).
+        return Pair.create(Boolean.FALSE, null);
       }
 
-      for (byte[] code : mPostModules.values()) {
-        fileOutputStream.write(code);
-        fileOutputStream.write('\n');
+      FileOutputStream fileOutputStream = new FileOutputStream(outputFile);
+
+      try {
+        for (byte[] code : mPreModules.values()) {
+          fileOutputStream.write(code);
+          fileOutputStream.write('\n');
+        }
+
+        for (byte[] code : mDeltaModules.values()) {
+          fileOutputStream.write(code);
+          fileOutputStream.write('\n');
+        }
+
+        for (byte[] code : mPostModules.values()) {
+          fileOutputStream.write(code);
+          fileOutputStream.write('\n');
+        }
+      } finally {
+        fileOutputStream.flush();
+        fileOutputStream.close();
       }
-    } finally {
-      fileOutputStream.flush();
-      fileOutputStream.close();
+
+      return Pair.create(Boolean.TRUE, null);
     }
 
-    return true;
-  }
+    private static int patchDelta(JsonReader jsonReader, LinkedHashMap<Number, byte[]> map)
+      throws IOException {
+      jsonReader.beginArray();
 
-  private static int patchDelta(JsonReader jsonReader, LinkedHashMap<Number, byte[]> map)
-    throws IOException {
-    jsonReader.beginArray();
+      int numModules = 0;
+      while (jsonReader.hasNext()) {
+        jsonReader.beginArray();
 
-    int numModules = 0;
-    while (jsonReader.hasNext()) {
-      jsonReader.beginArray();
+        int moduleId = jsonReader.nextInt();
 
-      int moduleId = jsonReader.nextInt();
+        if (jsonReader.peek() == JsonToken.NULL) {
+          jsonReader.skipValue();
+          map.remove(moduleId);
+        } else {
+          map.put(moduleId, jsonReader.nextString().getBytes());
+        }
 
-      if (jsonReader.peek() == JsonToken.NULL) {
-        jsonReader.skipValue();
-        map.remove(moduleId);
-      } else {
-        map.put(moduleId, jsonReader.nextString().getBytes());
+        jsonReader.endArray();
+        numModules++;
       }
 
       jsonReader.endArray();
-      numModules++;
+
+      return numModules;
+    }
+  }
+
+  private static class BundleDeltaNativeClient extends BundleDeltaClient {
+    private final NativeDeltaClient nativeClient = new NativeDeltaClient();
+
+    @Override
+    public boolean canHandle(ClientType type) {
+      return type == ClientType.NATIVE;
     }
 
-    jsonReader.endArray();
+    @Override
+    protected Pair<Boolean, NativeDeltaClient> processDelta(
+        BufferedSource body,
+        File outputFile) throws IOException {
+      nativeClient.processDelta(body);
+      return Pair.create(Boolean.FALSE, nativeClient);
+    }
 
-    return numModules;
+    @Override
+    public void reset() {
+      super.reset();
+      nativeClient.reset();
+    }
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
index b7c7ed7b962a..69f50a832e98 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
@@ -8,8 +8,10 @@
 package com.facebook.react.devsupport;
 
 import android.util.Log;
+import android.util.Pair;
 import com.facebook.common.logging.FLog;
 import com.facebook.infer.annotation.Assertions;
+import com.facebook.react.bridge.NativeDeltaClient;
 import com.facebook.react.common.DebugServerException;
 import com.facebook.react.common.ReactConstants;
 import com.facebook.react.devsupport.interfaces.DevBundleDownloadListener;
@@ -40,7 +42,7 @@ public class BundleDownloader {
 
   private final OkHttpClient mClient;
 
-  private final BundleDeltaClient mBundleDeltaClient = new BundleDeltaClient();
+  private BundleDeltaClient mBundleDeltaClient;
 
   private @Nullable Call mDownloadBundleFromURLCall;
 
@@ -95,14 +97,15 @@ public BundleDownloader(OkHttpClient client) {
   }
 
   public void downloadBundleFromURL(
-      final DevBundleDownloadListener callback,
-      final File outputFile,
-      final String bundleURL,
-      final @Nullable BundleInfo bundleInfo) {
+    final DevBundleDownloadListener callback,
+    final File outputFile,
+    final String bundleURL,
+    final @Nullable BundleInfo bundleInfo,
+    final BundleDeltaClient.ClientType clientType) {
 
     final Request request =
         new Request.Builder()
-            .url(mBundleDeltaClient.toDeltaUrl(bundleURL))
+            .url(formatBundleUrl(bundleURL, clientType))
             // FIXME: there is a bug that makes MultipartStreamReader to never find the end of the
             // multipart message. This temporarily disables the multipart mode to work around it,
             // but
@@ -146,7 +149,7 @@ public void onResponse(Call call, final Response response) throws IOException {
             try (Response r = response) {
               if (match.find()) {
                 processMultipartResponse(
-                  url, r, match.group(1), outputFile, bundleInfo, callback);
+                  url, r, match.group(1), outputFile, bundleInfo, clientType, callback);
               } else {
                 // In case the server doesn't support multipart/mixed responses, fallback to normal
                 // download.
@@ -157,6 +160,7 @@ public void onResponse(Call call, final Response response) throws IOException {
                   Okio.buffer(r.body().source()),
                   outputFile,
                   bundleInfo,
+                  clientType,
                   callback);
               }
             }
@@ -164,12 +168,19 @@ public void onResponse(Call call, final Response response) throws IOException {
         });
   }
 
+  private String formatBundleUrl(String bundleURL, BundleDeltaClient.ClientType clientType) {
+    return BundleDeltaClient.isDeltaUrl(bundleURL) && mBundleDeltaClient != null && mBundleDeltaClient.canHandle(clientType)
+      ? mBundleDeltaClient.extendUrlForDelta(bundleURL)
+      : bundleURL;
+  }
+
   private void processMultipartResponse(
       final String url,
       final Response response,
       String boundary,
       final File outputFile,
       @Nullable final BundleInfo bundleInfo,
+      final BundleDeltaClient.ClientType clientType,
       final DevBundleDownloadListener callback)
       throws IOException {
 
@@ -193,7 +204,7 @@ public void onChunkComplete(
                     status = Integer.parseInt(headers.get("X-Http-Status"));
                   }
                   processBundleResult(
-                      url, status, Headers.of(headers), body, outputFile, bundleInfo, callback);
+                      url, status, Headers.of(headers), body, outputFile, bundleInfo, clientType, callback);
                 } else {
                   if (!headers.containsKey("Content-Type")
                       || !headers.get("Content-Type").equals("application/json")) {
@@ -249,6 +260,7 @@ private void processBundleResult(
       BufferedSource body,
       File outputFile,
       BundleInfo bundleInfo,
+      BundleDeltaClient.ClientType clientType,
       DevBundleDownloadListener callback)
       throws IOException {
     // Check for server errors. If the server error has the expected form, fail with more info.
@@ -274,24 +286,36 @@ private void processBundleResult(
 
     File tmpFile = new File(outputFile.getPath() + ".tmp");
 
-    boolean bundleUpdated;
+    boolean bundleWritten;
+    NativeDeltaClient nativeDeltaClient = null;
 
     if (BundleDeltaClient.isDeltaUrl(url)) {
       // If the bundle URL has the delta extension, we need to use the delta patching logic.
-      bundleUpdated = mBundleDeltaClient.storeDeltaInFile(body, tmpFile);
+      BundleDeltaClient deltaClient = getBundleDeltaClient(clientType);
+      Assertions.assertNotNull(deltaClient);
+      Pair<Boolean, NativeDeltaClient> result = deltaClient.processDelta(headers, body, tmpFile);
+      bundleWritten = result.first;
+      nativeDeltaClient = result.second;
     } else {
-      mBundleDeltaClient.reset();
-      bundleUpdated = storePlainJSInFile(body, tmpFile);
+      mBundleDeltaClient = null;
+      bundleWritten = storePlainJSInFile(body, tmpFile);
     }
 
-    if (bundleUpdated) {
+    if (bundleWritten) {
       // If we have received a new bundle from the server, move it to its final destination.
       if (!tmpFile.renameTo(outputFile)) {
         throw new IOException("Couldn't rename " + tmpFile + " to " + outputFile);
       }
     }
 
-    callback.onSuccess();
+    callback.onSuccess(nativeDeltaClient);
+  }
+
+  private BundleDeltaClient getBundleDeltaClient(BundleDeltaClient.ClientType clientType) {
+    if (mBundleDeltaClient == null || !mBundleDeltaClient.canHandle(clientType)) {
+      mBundleDeltaClient = BundleDeltaClient.create(clientType);
+    }
+    return mBundleDeltaClient;
   }
 
   private static boolean storePlainJSInFile(BufferedSource body, File outputFile)
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
index 946377680e69..f0638b0b41c2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
@@ -375,7 +375,17 @@ private String getInspectorAttachUrl(String title) {
   public void downloadBundleFromURL(
     DevBundleDownloadListener callback,
     File outputFile, String bundleURL, BundleDownloader.BundleInfo bundleInfo) {
-    mBundleDownloader.downloadBundleFromURL(callback, outputFile, bundleURL, bundleInfo);
+    mBundleDownloader.downloadBundleFromURL(callback, outputFile, bundleURL, bundleInfo, getDeltaClientType());
+  }
+
+  private BundleDeltaClient.ClientType getDeltaClientType() {
+    if (mSettings.isBundleDeltasCppEnabled()) {
+      return BundleDeltaClient.ClientType.NATIVE;
+    } else if (mSettings.isBundleDeltasEnabled()) {
+      return BundleDeltaClient.ClientType.DEV_SUPPORT;
+    } else {
+      return BundleDeltaClient.ClientType.NONE;
+    }
   }
 
   /**
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
index ea25bf86c42a..6673503703d7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
@@ -32,6 +32,7 @@
 import com.facebook.react.bridge.DefaultNativeModuleCallExceptionHandler;
 import com.facebook.react.bridge.JavaJSExecutor;
 import com.facebook.react.bridge.JavaScriptContextHolder;
+import com.facebook.react.bridge.NativeDeltaClient;
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.bridge.ReactMarker;
 import com.facebook.react.bridge.ReactMarkerConstants;
@@ -973,7 +974,7 @@ public void reloadJSFromServer(final String bundleURL) {
     mDevServerHelper.downloadBundleFromURL(
         new DevBundleDownloadListener() {
           @Override
-          public void onSuccess() {
+          public void onSuccess(final @Nullable NativeDeltaClient nativeDeltaClient) {
             mDevLoadingViewController.hide();
             mDevLoadingViewVisible = false;
             synchronized (DevSupportManagerImpl.this) {
@@ -981,14 +982,14 @@ public void onSuccess() {
               mBundleStatus.updateTimestamp = System.currentTimeMillis();
             }
             if (mBundleDownloadListener != null) {
-              mBundleDownloadListener.onSuccess();
+              mBundleDownloadListener.onSuccess(nativeDeltaClient);
             }
             UiThreadUtil.runOnUiThread(
                 new Runnable() {
                   @Override
                   public void run() {
                     ReactMarker.logMarker(ReactMarkerConstants.DOWNLOAD_END, bundleInfo.toJSONString());
-                    mReactInstanceManagerHelper.onJSBundleLoadedFromServer();
+                    mReactInstanceManagerHelper.onJSBundleLoadedFromServer(nativeDeltaClient);
                   }
                 });
           }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/ReactInstanceManagerDevHelper.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/ReactInstanceManagerDevHelper.java
index 7694c68db9db..7033a21fda47 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/ReactInstanceManagerDevHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/ReactInstanceManagerDevHelper.java
@@ -8,9 +8,9 @@
 package com.facebook.react.devsupport;
 
 import android.app.Activity;
-
 import com.facebook.react.bridge.JavaJSExecutor;
 
+import com.facebook.react.bridge.NativeDeltaClient;
 import javax.annotation.Nullable;
 
 /**
@@ -27,7 +27,7 @@ public interface ReactInstanceManagerDevHelper {
   /**
    * Notify react instance manager about new JS bundle version downloaded from the server.
    */
-  void onJSBundleLoadedFromServer();
+  void onJSBundleLoadedFromServer(@Nullable NativeDeltaClient nativeDeltaClient);
 
   /**
    * Request to toggle the react element inspector.
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/interfaces/DevBundleDownloadListener.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/interfaces/DevBundleDownloadListener.java
index 661a8cba2436..b08ba97066a3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/interfaces/DevBundleDownloadListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/interfaces/DevBundleDownloadListener.java
@@ -7,10 +7,11 @@
 
 package com.facebook.react.devsupport.interfaces;
 
+import com.facebook.react.bridge.NativeDeltaClient;
 import javax.annotation.Nullable;
 
 public interface DevBundleDownloadListener {
-  void onSuccess();
+  void onSuccess(@Nullable NativeDeltaClient nativeDeltaClient);
   void onProgress(@Nullable String status, @Nullable Integer done, @Nullable Integer total);
   void onFailure(Exception cause);
 }

From 786c1ecc2a6856967d676da68eb02f89eb38fb79 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 3 May 2018 08:38:15 -0700
Subject: [PATCH 0432/1109] Markers: add info about type of delta client

Summary: Adds information which type of delta client is used (if at all) to the `BundleInfo` object.

Reviewed By: fromcelticpark

Differential Revision: D7845139

fbshipit-source-id: e4bf6cda62c71a78aaff97aa69daec263e6d3cdf
---
 .../facebook/react/devsupport/BundleDownloader.java  | 12 ++++++++++--
 1 file changed, 10 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
index 69f50a832e98..e64d02edbb97 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
@@ -47,6 +47,7 @@ public class BundleDownloader {
   private @Nullable Call mDownloadBundleFromURLCall;
 
   public static class BundleInfo {
+    private @Nullable String mDeltaClientName;
     private @Nullable String mUrl;
     private int mFilesChangedCount;
 
@@ -59,6 +60,7 @@ public static class BundleInfo {
 
       try {
         JSONObject obj = new JSONObject(jsonStr);
+        info.mDeltaClientName = obj.getString("deltaClient");
         info.mUrl = obj.getString("url");
         info.mFilesChangedCount = obj.getInt("filesChangedCount");
       } catch (JSONException e) {
@@ -73,6 +75,7 @@ public static class BundleInfo {
       JSONObject obj = new JSONObject();
 
       try {
+        obj.put("deltaClient", mDeltaClientName);
         obj.put("url", mUrl);
         obj.put("filesChangedCount", mFilesChangedCount);
       } catch (JSONException e) {
@@ -83,6 +86,10 @@ public static class BundleInfo {
       return obj.toString();
     }
 
+    public @Nullable String getDeltaClient() {
+      return mDeltaClientName;
+    }
+
     public String getUrl() {
       return mUrl != null ? mUrl : "unknown";
     }
@@ -281,7 +288,7 @@ private void processBundleResult(
     }
 
     if (bundleInfo != null) {
-      populateBundleInfo(url, headers, bundleInfo);
+      populateBundleInfo(url, headers, clientType, bundleInfo);
     }
 
     File tmpFile = new File(outputFile.getPath() + ".tmp");
@@ -333,7 +340,8 @@ private static boolean storePlainJSInFile(BufferedSource body, File outputFile)
     return true;
   }
 
-  private static void populateBundleInfo(String url, Headers headers, BundleInfo bundleInfo) {
+  private static void populateBundleInfo(String url, Headers headers, BundleDeltaClient.ClientType clientType, BundleInfo bundleInfo) {
+    bundleInfo.mDeltaClientName = clientType == BundleDeltaClient.ClientType.NONE ? null : clientType.name();
     bundleInfo.mUrl = url;
 
     String filesChangedCountStr = headers.get("X-Metro-Files-Changed-Count");

From 5a6147c4f8e66183be40cc0646226b066daaaed7 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Thu, 3 May 2018 13:01:28 -0700
Subject: [PATCH 0433/1109] Fix DevLoadingViewController

Reviewed By: mdvacca

Differential Revision: D7860219

fbshipit-source-id: 3770a2064808bf4ae4c61f15c6d68c3b93fe9f38
---
 .../devsupport/DevLoadingViewController.java  | 92 +++++++++----------
 .../devsupport/DevSupportManagerImpl.java     |  2 +-
 .../devsupport/layout/dev_loading_view.xml    |  9 +-
 3 files changed, 48 insertions(+), 55 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevLoadingViewController.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevLoadingViewController.java
index bc6e6c3b7a7f..9d8ed683a858 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevLoadingViewController.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevLoadingViewController.java
@@ -7,28 +7,25 @@
 
 package com.facebook.react.devsupport;
 
+import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
+import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT;
+
 import android.annotation.TargetApi;
 import android.app.Activity;
 import android.content.Context;
-import android.graphics.Color;
 import android.graphics.Rect;
 import android.os.Build;
 import android.view.Gravity;
 import android.view.LayoutInflater;
-import android.view.ViewGroup;
-import android.view.Window;
 import android.widget.PopupWindow;
 import android.widget.TextView;
-
 import com.facebook.common.logging.FLog;
 import com.facebook.react.R;
 import com.facebook.react.bridge.UiThreadUtil;
 import com.facebook.react.common.ReactConstants;
-
 import java.net.MalformedURLException;
 import java.net.URL;
 import java.util.Locale;
-
 import javax.annotation.Nullable;
 
 /**
@@ -36,12 +33,9 @@
  */
 @TargetApi(Build.VERSION_CODES.CUPCAKE)
 public class DevLoadingViewController {
-  private static final int COLOR_DARK_GREEN = Color.parseColor("#035900");
-
   private static boolean sEnabled = true;
-  private final Context mContext;
   private final ReactInstanceManagerDevHelper mReactInstanceManagerHelper;
-  private final TextView mDevLoadingView;
+  private @Nullable TextView mDevLoadingView;
   private @Nullable PopupWindow mDevLoadingPopup;
 
   public static void setDevLoadingEnabled(boolean enabled) {
@@ -49,13 +43,10 @@ public static void setDevLoadingEnabled(boolean enabled) {
   }
 
   public DevLoadingViewController(Context context, ReactInstanceManagerDevHelper reactInstanceManagerHelper) {
-    mContext = context;
     mReactInstanceManagerHelper = reactInstanceManagerHelper;
-    LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
-    mDevLoadingView = (TextView) inflater.inflate(R.layout.dev_loading_view, null);
   }
 
-  public void showMessage(final String message, final int color, final int backgroundColor) {
+  public void showMessage(final String message) {
     if (!sEnabled) {
       return;
     }
@@ -63,16 +54,17 @@ public void showMessage(final String message, final int color, final int backgro
     UiThreadUtil.runOnUiThread(new Runnable() {
       @Override
       public void run() {
-        mDevLoadingView.setBackgroundColor(backgroundColor);
-        mDevLoadingView.setText(message);
-        mDevLoadingView.setTextColor(color);
-
-        showInternal();
+        showInternal(message);
       }
     });
   }
 
   public void showForUrl(String url) {
+    Context context = getContext();
+    if (context == null) {
+      return;
+    }
+
     URL parsedURL;
     try {
       parsedURL = new URL(url);
@@ -82,13 +74,17 @@ public void showForUrl(String url) {
     }
 
     showMessage(
-      mContext.getString(R.string.catalyst_loading_from_url, parsedURL.getHost() + ":" + parsedURL.getPort()),
-      Color.WHITE,
-      COLOR_DARK_GREEN);
+        context.getString(R.string.catalyst_loading_from_url,
+        parsedURL.getHost() + ":" + parsedURL.getPort()));
   }
 
   public void showForRemoteJSEnabled() {
-    showMessage(mContext.getString(R.string.catalyst_remotedbg_message), Color.WHITE, COLOR_DARK_GREEN);
+    Context context = getContext();
+    if (context == null) {
+      return;
+    }
+
+    showMessage(context.getString(R.string.catalyst_remotedbg_message));
   }
 
   public void updateProgress(final @Nullable String status, final @Nullable Integer done, final @Nullable Integer total) {
@@ -105,21 +101,9 @@ public void run() {
           message.append(String.format(Locale.getDefault(), " %.1f%% (%d/%d)", (float) done / total * 100, done, total));
         }
         message.append("\u2026"); // `...` character
-
-        mDevLoadingView.setText(message);
-      }
-    });
-  }
-
-  public void show() {
-    if (!sEnabled) {
-      return;
-    }
-
-    UiThreadUtil.runOnUiThread(new Runnable() {
-      @Override
-      public void run() {
-        showInternal();
+        if (mDevLoadingView != null) {
+          mDevLoadingView.setText(message);
+        }
       }
     });
   }
@@ -137,7 +121,7 @@ public void run() {
     });
   }
 
-  private void showInternal() {
+  private void showInternal(String message) {
     if (mDevLoadingPopup != null && mDevLoadingPopup.isShowing()) {
       // already showing
       return;
@@ -150,20 +134,21 @@ private void showInternal() {
       return;
     }
 
-    int topOffset = 0;
-    if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.KITKAT) {
-      // On Android SDK <= 19 PopupWindow#showAtLocation uses absolute screen position. In order for
-      // loading view to be placed below status bar (if the status bar is present) we need to pass
-      // an appropriate Y offset.
-      Rect rectangle = new Rect();
-      currentActivity.getWindow().getDecorView().getWindowVisibleDisplayFrame(rectangle);
-      topOffset = rectangle.top;
-    }
+    // PopupWindow#showAtLocation uses absolute screen position. In order for
+    // loading view to be placed below status bar (if the status bar is present) we need to pass
+    // an appropriate Y offset.
+    Rect rectangle = new Rect();
+    currentActivity.getWindow().getDecorView().getWindowVisibleDisplayFrame(rectangle);
+    int topOffset = rectangle.top;
+
+    LayoutInflater inflater =
+      (LayoutInflater) currentActivity.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
 
-    mDevLoadingPopup = new PopupWindow(currentActivity);
+    mDevLoadingView = (TextView) inflater.inflate(R.layout.dev_loading_view, null);
+    mDevLoadingView.setText(message);
+
+    mDevLoadingPopup = new PopupWindow(mDevLoadingView, MATCH_PARENT, WRAP_CONTENT);
     mDevLoadingPopup.setTouchable(false);
-    mDevLoadingPopup.setWidth(ViewGroup.LayoutParams.MATCH_PARENT);
-    mDevLoadingPopup.setHeight(ViewGroup.LayoutParams.WRAP_CONTENT);
 
     mDevLoadingPopup.showAtLocation(
       currentActivity.getWindow().getDecorView(),
@@ -176,6 +161,11 @@ private void hideInternal() {
     if (mDevLoadingPopup != null && mDevLoadingPopup.isShowing()) {
       mDevLoadingPopup.dismiss();
       mDevLoadingPopup = null;
+      mDevLoadingView = null;
     }
   }
+
+  private @Nullable Context getContext() {
+    return mReactInstanceManagerHelper.getCurrentActivity();
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
index 6673503703d7..241bd0dbf1dd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
@@ -1073,7 +1073,7 @@ private void reload() {
 
       // show the dev loading if it should be
       if (mDevLoadingViewVisible) {
-        mDevLoadingViewController.show();
+        mDevLoadingViewController.showMessage("Reloading...");
       }
 
       mDevServerHelper.openPackagerConnection(this.getClass().getSimpleName(), this);
diff --git a/ReactAndroid/src/main/res/devsupport/layout/dev_loading_view.xml b/ReactAndroid/src/main/res/devsupport/layout/dev_loading_view.xml
index c503c9c7d01e..9bf8bca6aabd 100644
--- a/ReactAndroid/src/main/res/devsupport/layout/dev_loading_view.xml
+++ b/ReactAndroid/src/main/res/devsupport/layout/dev_loading_view.xml
@@ -4,11 +4,14 @@
   xmlns:android="http://schemas.android.com/apk/res/android"
   android:layout_width="match_parent"
   android:layout_height="wrap_content"
+  android:background="#035900"
+  android:ellipsize="end"
+  android:gravity="center"
   android:paddingTop="5dp"
   android:paddingBottom="5dp"
   android:paddingStart="8dp"
   android:paddingEnd="8dp"
-  android:textSize="12sp"
   android:maxLines="1"
-  android:ellipsize="end"
-  android:gravity="center"/>
+  android:textColor="@android:color/white"
+  android:textSize="12sp"
+  />

From b63015d34ef51585c452142f666d4f36ceaa1b56 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Ma=C3=ABl=20Nison?= <mael@fb.com>
Date: Thu, 3 May 2018 14:05:30 -0700
Subject: [PATCH 0434/1109] Bumps Jest to 23.0.0-charlie.1 [fbsource]

Differential Revision: D7859604

fbshipit-source-id: 6a2d74679f5eae3cb0102f461272b7cbd5716cba
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 37b3feb4ca0b..3be9d818e675 100644
--- a/package.json
+++ b/package.json
@@ -213,7 +213,7 @@
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
     "flow-bin": "^0.71.0",
-    "jest": "23.0.0-beta.2",
+    "jest": "23.0.0-charlie.1",
     "jest-junit": "3.7.0",
     "prettier": "1.12.1",
     "react": "16.3.2",

From 255b97ddd1e0baaf180069a6994e4711e22603a2 Mon Sep 17 00:00:00 2001
From: Jonathan Kim <jjkim@fb.com>
Date: Thu, 3 May 2018 15:42:23 -0700
Subject: [PATCH 0435/1109] Load and use fb_xplat_cxx_test

Reviewed By: mzlee

Differential Revision: D7854278

fbshipit-source-id: 2a4c4fc27fc665a192fc04a8c8fae19f7f221566
---
 ReactCommon/cxxreact/tests/BUCK   | 4 ++--
 ReactCommon/fabric/core/BUCK      | 6 +++---
 ReactCommon/fabric/debug/BUCK     | 6 +++---
 ReactCommon/fabric/graphics/BUCK  | 6 +++---
 ReactCommon/fabric/uimanager/BUCK | 1 +
 ReactCommon/fabric/view/BUCK      | 1 +
 6 files changed, 13 insertions(+), 11 deletions(-)

diff --git a/ReactCommon/cxxreact/tests/BUCK b/ReactCommon/cxxreact/tests/BUCK
index 1d7657cc01ec..e78b7692b1d7 100644
--- a/ReactCommon/cxxreact/tests/BUCK
+++ b/ReactCommon/cxxreact/tests/BUCK
@@ -11,7 +11,7 @@ TEST_SRCS = [
 ]
 
 if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "cxx_test")
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
     load("@xplat//configurations/buck/android:jni_instrumentation_test", "jni_instrumentation_test_lib")
     load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
     jni_instrumentation_test_lib(
@@ -34,7 +34,7 @@ if not IS_OSS_BUILD:
         ],
     )
 
-    cxx_test(
+    fb_xplat_cxx_test(
         name = 'tests',
         srcs = TEST_SRCS,
         compiler_flags = [
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 23a9f30cfc0c..981dd874f400 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -1,5 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -58,9 +58,9 @@ rn_xplat_cxx_library(
 )
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
 
-    cxx_test(
+    fb_xplat_cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
         headers = glob(["tests/**/*.h"]),
diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index 88f7bc47828c..782b7452253f 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -1,5 +1,5 @@
 load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -49,9 +49,9 @@ rn_xplat_cxx_library(
 )
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
 
-    cxx_test(
+    fb_xplat_cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
         headers = glob(["tests/**/*.h"]),
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index 7cdb8c59b90f..52a42e39208f 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -1,5 +1,5 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -53,9 +53,9 @@ rn_xplat_cxx_library(
 )
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
 
-    cxx_test(
+    fb_xplat_cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
         headers = glob(["tests/**/*.h"]),
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 6745136cf817..4a3eeae2ba5f 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -58,6 +58,7 @@ rn_xplat_cxx_library(
 
 if not IS_OSS_BUILD:
     load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
     fb_xplat_cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 1f2cff2c3fc7..20b7108c25c7 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -61,6 +61,7 @@ rn_xplat_cxx_library(
 
 if not IS_OSS_BUILD:
     load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+    
     fb_xplat_cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),

From f5fcebabeb6d5f93e7eb912f26bfcb755bf0eb66 Mon Sep 17 00:00:00 2001
From: Logan Daniels <logand@fb.com>
Date: Thu, 3 May 2018 16:14:34 -0700
Subject: [PATCH 0436/1109] PerformanceLogger: log extras to console in DEV
 mode

Differential Revision: D7862011

fbshipit-source-id: 591caf37d6c91ccb07f13005c0f6c57dcaaa22c5
---
 Libraries/Utilities/PerformanceLogger.js | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/Libraries/Utilities/PerformanceLogger.js b/Libraries/Utilities/PerformanceLogger.js
index a48f1adb4b6e..23fcac7951f7 100644
--- a/Libraries/Utilities/PerformanceLogger.js
+++ b/Libraries/Utilities/PerformanceLogger.js
@@ -185,6 +185,10 @@ const PerformanceLogger = {
   getExtras() {
     return extras;
   },
+
+  logExtras() {
+    infoLog(extras);
+  },
 };
 
 module.exports = PerformanceLogger;

From cd48a6130b13562467a5e1a93b2fc0f30f03bb1c Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Fri, 4 May 2018 10:56:14 -0700
Subject: [PATCH 0437/1109] RN: Disable testImageCachePolicyTest

Reviewed By: fkgozali

Differential Revision: D7878430

fbshipit-source-id: 60f0ca3f2b59987d618982c91a7e91a2f4b6a18b
---
 RNTester/RNTesterIntegrationTests/RNTesterIntegrationTests.m | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/RNTester/RNTesterIntegrationTests/RNTesterIntegrationTests.m b/RNTester/RNTesterIntegrationTests/RNTesterIntegrationTests.m
index 5f432ec0580d..1549898e4377 100644
--- a/RNTester/RNTesterIntegrationTests/RNTesterIntegrationTests.m
+++ b/RNTester/RNTesterIntegrationTests/RNTesterIntegrationTests.m
@@ -65,7 +65,7 @@ - (void)testTheTester_ExpectError
 RCT_TEST(TimersTest)
 RCT_TEST(AsyncStorageTest)
 RCT_TEST(AppEventsTest)
-RCT_TEST(ImageCachePolicyTest)
+//RCT_TEST(ImageCachePolicyTest) // This test never passed.
 RCT_TEST(ImageSnapshotTest)
 //RCT_TEST(LayoutEventsTest) // Disabled due to flakiness: #8686784
 RCT_TEST(SimpleSnapshotTest)

From 634e7e11e3ad39e0b13bf20cc7722c0cfd3c3e28 Mon Sep 17 00:00:00 2001
From: Mehdi Mulani <mehdi@fb.com>
Date: Fri, 4 May 2018 13:47:42 -0700
Subject: [PATCH 0438/1109] iOS only: Breaking Change: Restrict WebView to only
 http(s) URLs

Summary:
To prevent people from linking file:// or other URLs inside RN WebViews, default <WebView> to not allowing those types of URLs.
This adds the originWhitelist to specify other schemes or domains to be allowed.

If the url is not allowed, it will be opened in Safari/by the OS instead.

Reviewed By: yungsters

Differential Revision: D7833203

fbshipit-source-id: 6881acd3b434d17910240e4edd585c0a10b5df8c
---
 IntegrationTests/WebViewTest.js               |  1 +
 Libraries/Components/WebView/WebView.ios.js   | 32 ++++++++++++---
 Libraries/Components/WebView/WebViewShared.js | 24 +++++++++++
 .../WebView/__tests__/WebViewShared-test.js   | 41 +++++++++++++++++++
 package.json                                  |  1 +
 5 files changed, 94 insertions(+), 5 deletions(-)
 create mode 100644 Libraries/Components/WebView/WebViewShared.js
 create mode 100644 Libraries/Components/WebView/__tests__/WebViewShared-test.js

diff --git a/IntegrationTests/WebViewTest.js b/IntegrationTests/WebViewTest.js
index 499e1c095400..818b4e980216 100644
--- a/IntegrationTests/WebViewTest.js
+++ b/IntegrationTests/WebViewTest.js
@@ -48,6 +48,7 @@ class WebViewTest extends React.Component {
       <WebView
         source={source}
         onMessage = {processMessage}
+        originWhitelist={['about:blank']}
         />
     );
   }
diff --git a/Libraries/Components/WebView/WebView.ios.js b/Libraries/Components/WebView/WebView.ios.js
index 56a4465fea6b..1d54f663f01b 100644
--- a/Libraries/Components/WebView/WebView.ios.js
+++ b/Libraries/Components/WebView/WebView.ios.js
@@ -10,15 +10,17 @@
 
 const ActivityIndicator = require('ActivityIndicator');
 const EdgeInsetsPropType = require('EdgeInsetsPropType');
-const React = require('React');
+const Linking = require('Linking');
 const PropTypes = require('prop-types');
+const React = require('React');
 const ReactNative = require('ReactNative');
+const ScrollView = require('ScrollView');
 const StyleSheet = require('StyleSheet');
 const Text = require('Text');
 const UIManager = require('UIManager');
 const View = require('View');
 const ViewPropTypes = require('ViewPropTypes');
-const ScrollView = require('ScrollView');
+const WebViewShared = require('WebViewShared');
 
 const deprecatedPropType = require('deprecatedPropType');
 const invariant = require('fbjs/lib/invariant');
@@ -353,6 +355,15 @@ class WebView extends React.Component {
      */
     mediaPlaybackRequiresUserAction: PropTypes.bool,
 
+    /**
+     * List of origin strings to allow being navigated to. The strings allow
+     * wildcards and get matched against *just* the origin (not the full URL).
+     * If the user taps to navigate to a new page but the new page is not in
+     * this whitelist, we will open the URL in Safari.
+     * The default whitelisted origins are "http://*" and "https://*".
+     */
+    originWhitelist: PropTypes.arrayOf(PropTypes.string),
+
     /**
      * Function that accepts a string that will be passed to the WebView and
      * executed immediately as JavaScript.
@@ -398,6 +409,7 @@ class WebView extends React.Component {
   };
 
   static defaultProps = {
+    originWhitelist: WebViewShared.defaultOriginWhitelist,
     scalesPageToFit: true,
   };
 
@@ -446,9 +458,19 @@ class WebView extends React.Component {
 
     const viewManager = nativeConfig.viewManager || RCTWebViewManager;
 
-    const onShouldStartLoadWithRequest = this.props.onShouldStartLoadWithRequest && ((event: Event) => {
-      const shouldStart = this.props.onShouldStartLoadWithRequest &&
-        this.props.onShouldStartLoadWithRequest(event.nativeEvent);
+    const compiledWhitelist = (this.props.originWhitelist || []).map(WebViewShared.originWhitelistToRegex);
+    const onShouldStartLoadWithRequest = ((event: Event) => {
+      let shouldStart = true;
+      const {url} = event.nativeEvent;
+      const origin = WebViewShared.extractOrigin(url);
+      const passesWhitelist = compiledWhitelist.some(x => new RegExp(x).test(origin));
+      shouldStart = shouldStart && passesWhitelist;
+      if (!passesWhitelist) {
+        Linking.openURL(url);
+      }
+      if (this.props.onShouldStartLoadWithRequest) {
+        shouldStart = shouldStart && this.props.onShouldStartLoadWithRequest(event.nativeEvent);
+      }
       viewManager.startLoadWithResult(!!shouldStart, event.nativeEvent.lockIdentifier);
     });
 
diff --git a/Libraries/Components/WebView/WebViewShared.js b/Libraries/Components/WebView/WebViewShared.js
new file mode 100644
index 000000000000..744ea201f467
--- /dev/null
+++ b/Libraries/Components/WebView/WebViewShared.js
@@ -0,0 +1,24 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ */
+'use strict';
+
+const escapeStringRegexp = require('escape-string-regexp');
+
+const WebViewShared = {
+  defaultOriginWhitelist: ['http://*', 'https://*'],
+  extractOrigin: (url: string): ?string => {
+    const result = /^[A-Za-z0-9]+:(\/\/)?[^/]*/.exec(url);
+    return result === null ? null : result[0];
+  },
+  originWhitelistToRegex: (originWhitelist: string): string => {
+    return escapeStringRegexp(originWhitelist).replace(/\\\*/g, '.*');
+  },
+};
+
+module.exports = WebViewShared;
diff --git a/Libraries/Components/WebView/__tests__/WebViewShared-test.js b/Libraries/Components/WebView/__tests__/WebViewShared-test.js
new file mode 100644
index 000000000000..37f52064c431
--- /dev/null
+++ b/Libraries/Components/WebView/__tests__/WebViewShared-test.js
@@ -0,0 +1,41 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @emails oncall+react_native
+ */
+
+ 'use strict';
+
+const WebViewShared = require('WebViewShared');
+
+describe('WebViewShared', () => {
+  it('extracts the origin correctly', () => {
+    expect(WebViewShared.extractOrigin('http://facebook.com')).toBe('http://facebook.com');
+    expect(WebViewShared.extractOrigin('https://facebook.com')).toBe('https://facebook.com');
+    expect(WebViewShared.extractOrigin('http://facebook.com:8081')).toBe('http://facebook.com:8081');
+    expect(WebViewShared.extractOrigin('ftp://facebook.com')).toBe('ftp://facebook.com');
+    expect(WebViewShared.extractOrigin('myweirdscheme://')).toBe('myweirdscheme://');
+    expect(WebViewShared.extractOrigin('http://facebook.com/')).toBe('http://facebook.com');
+    expect(WebViewShared.extractOrigin('http://facebook.com/longerurl')).toBe('http://facebook.com');
+    expect(WebViewShared.extractOrigin('http://facebook.com/http://facebook.com')).toBe('http://facebook.com');
+    expect(WebViewShared.extractOrigin('http://facebook.com//http://facebook.com')).toBe('http://facebook.com');
+    expect(WebViewShared.extractOrigin('http://facebook.com//http://facebook.com//')).toBe('http://facebook.com');
+    expect(WebViewShared.extractOrigin('about:blank')).toBe('about:blank');
+  });
+
+  it('rejects bad urls', () => {
+    expect(WebViewShared.extractOrigin('a/b')).toBeNull();
+    expect(WebViewShared.extractOrigin('a//b')).toBeNull();
+  });
+
+  it('creates a whitelist regex correctly', () => {
+    expect(WebViewShared.originWhitelistToRegex('http://*')).toBe('http://.*');
+    expect(WebViewShared.originWhitelistToRegex('*')).toBe('.*');
+    expect(WebViewShared.originWhitelistToRegex('*//test')).toBe('.*//test');
+    expect(WebViewShared.originWhitelistToRegex('*/*')).toBe('.*/.*');
+    expect(WebViewShared.originWhitelistToRegex('*.com')).toBe('.*\\.com');
+  });
+});
diff --git a/package.json b/package.json
index 3be9d818e675..02d8deb8c636 100644
--- a/package.json
+++ b/package.json
@@ -158,6 +158,7 @@
     "denodeify": "^1.2.1",
     "envinfo": "^3.0.0",
     "errorhandler": "^1.5.0",
+    "escape-string-regexp": "^1.0.5",
     "eslint-plugin-react-native": "^3.2.1",
     "event-target-shim": "^1.0.5",
     "fbjs": "^0.8.14",

From b7562818e651785ed869b6ea52688f4a2cc578e8 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 4 May 2018 17:28:40 -0700
Subject: [PATCH 0439/1109] Add molly dependency in Fabric/jsc/jni project

Reviewed By: fkgozali

Differential Revision: D7816676

fbshipit-source-id: 8f227482eb1129f51d758bc13e619af30d6c2b1f
---
 .../src/main/java/com/facebook/react/fabric/jsc/jni/BUCK         | 1 +
 1 file changed, 1 insertion(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
index 4c4dd27047f9..9998937d4703 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
@@ -14,6 +14,7 @@ rn_xplat_cxx_library(
     visibility = ["PUBLIC"],
     deps = [
         FBJNI_TARGET,
+        "xplat//folly:molly",
         react_native_xplat_target("jschelpers:jschelpers"),
         react_native_target("jni/react/jni:jni"),
     ],

From 1e68ca7dc817771ee7e9b749f391f53288d91c13 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 4 May 2018 17:50:37 -0700
Subject: [PATCH 0440/1109] Cleanup android warnings related to static
 interface declarations

Reviewed By: fkgozali

Differential Revision: D7853681

fbshipit-source-id: d342e9dc9a1efa921d1421d545798e0b706745b4
---
 .../java/com/facebook/react/testing/ReactTestFactory.java       | 2 +-
 .../react/testing/network/NetworkRecordingModuleMock.java       | 2 +-
 .../src/main/java/com/facebook/react/common/ShakeDetector.java  | 2 +-
 .../react/uimanager/common/SizeMonitoringFrameLayout.java       | 2 +-
 4 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactTestFactory.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactTestFactory.java
index c15ffc29f259..20cbfb938b40 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactTestFactory.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactTestFactory.java
@@ -14,7 +14,7 @@
 import com.facebook.react.bridge.NativeModule;
 
 public interface ReactTestFactory {
-  public static interface ReactInstanceEasyBuilder {
+  interface ReactInstanceEasyBuilder {
     ReactInstanceEasyBuilder setContext(Context context);
     ReactInstanceEasyBuilder addNativeModule(NativeModule module);
     CatalystInstance build();
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/network/NetworkRecordingModuleMock.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/network/NetworkRecordingModuleMock.java
index 9a6917078c78..0f5c96831099 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/network/NetworkRecordingModuleMock.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/network/NetworkRecordingModuleMock.java
@@ -47,7 +47,7 @@ public NetworkRecordingModuleMock(ReactApplicationContext reactContext, boolean
     mCompleteRequest = completeRequest;
   }
 
-  public static interface RequestListener {
+  public interface RequestListener {
     public void onRequest(String method, String url, ReadableArray header, ReadableMap data);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/common/ShakeDetector.java b/ReactAndroid/src/main/java/com/facebook/react/common/ShakeDetector.java
index 5d14415072fd..ad45c64d2d5d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/common/ShakeDetector.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/common/ShakeDetector.java
@@ -34,7 +34,7 @@ public class ShakeDetector implements SensorEventListener {
 
   private float mAccelerationX, mAccelerationY, mAccelerationZ;
 
-  public static interface ShakeListener {
+  public interface ShakeListener {
     void onShake();
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/SizeMonitoringFrameLayout.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/SizeMonitoringFrameLayout.java
index 19af1031a8e8..f7dd744c4b11 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/SizeMonitoringFrameLayout.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/SizeMonitoringFrameLayout.java
@@ -20,7 +20,7 @@
  */
 public class SizeMonitoringFrameLayout extends FrameLayout {
 
-  public static interface OnSizeChangedListener {
+  public interface OnSizeChangedListener {
     void onSizeChanged(int width, int height, int oldWidth, int oldHeight);
   }
 

From 23f8f7aecb1f21f4f5e44fb9e4a7456ea97935c9 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 4 May 2018 22:44:30 -0700
Subject: [PATCH 0441/1109] Breaking Change: Restrict WebView to only manage
 navigation of whitelisted URLs: http(s) by default

Reviewed By: achen1

Differential Revision: D7834050

fbshipit-source-id: 80f7fd3cd20979590b75804819e154afc14a3c64
---
 .../Components/WebView/WebView.android.js     |  16 ++-
 .../views/webview/ReactWebViewManager.java    | 100 +++++++++++++-----
 2 files changed, 91 insertions(+), 25 deletions(-)

diff --git a/Libraries/Components/WebView/WebView.android.js b/Libraries/Components/WebView/WebView.android.js
index 6f0ac9b57fb0..b6995458e590 100644
--- a/Libraries/Components/WebView/WebView.android.js
+++ b/Libraries/Components/WebView/WebView.android.js
@@ -16,6 +16,7 @@ const StyleSheet = require('StyleSheet');
 const UIManager = require('UIManager');
 const View = require('View');
 const ViewPropTypes = require('ViewPropTypes');
+const WebViewShared = require('WebViewShared');
 
 const deprecatedPropType = require('deprecatedPropType');
 const keyMirror = require('fbjs/lib/keyMirror');
@@ -179,6 +180,15 @@ class WebView extends React.Component {
      */
     allowUniversalAccessFromFileURLs: PropTypes.bool,
 
+    /**
+     * List of origin strings to allow being navigated to. The strings allow
+     * wildcards and get matched against *just* the origin (not the full URL).
+     * If the user taps to navigate to a new page but the new page is not in
+     * this whitelist, the URL will be oppened by the Android OS.
+     * The default whitelisted origins are "http://*" and "https://*".
+     */
+    originWhitelist: PropTypes.arrayOf(PropTypes.string),
+
     /**
      * Function that accepts a string that will be passed to the WebView and
      * executed immediately as JavaScript.
@@ -241,7 +251,8 @@ class WebView extends React.Component {
     javaScriptEnabled : true,
     thirdPartyCookiesEnabled: true,
     scalesPageToFit: true,
-    saveFormDataDisabled: false
+    saveFormDataDisabled: false,
+    originWhitelist: WebViewShared.defaultOriginWhitelist,
   };
 
   state = {
@@ -293,6 +304,8 @@ class WebView extends React.Component {
 
     const nativeConfig = this.props.nativeConfig || {};
 
+    const originWhitelist = (this.props.originWhitelist || []).map(WebViewShared.originWhitelistToRegex);
+
     let NativeWebView = nativeConfig.component || RCTWebView;
 
     const webView =
@@ -319,6 +332,7 @@ class WebView extends React.Component {
         geolocationEnabled={this.props.geolocationEnabled}
         mediaPlaybackRequiresUserAction={this.props.mediaPlaybackRequiresUserAction}
         allowUniversalAccessFromFileURLs={this.props.allowUniversalAccessFromFileURLs}
+        originWhitelist={originWhitelist}
         mixedContentMode={this.props.mixedContentMode}
         saveFormDataDisabled={this.props.saveFormDataDisabled}
         urlPrefixesForDefaultIntent={this.props.urlPrefixesForDefaultIntent}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
index a580a2bc4a18..7f07b2742677 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
@@ -7,6 +7,11 @@
 
 package com.facebook.react.views.webview;
 
+import android.annotation.TargetApi;
+import android.content.Context;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.regex.Pattern;
 import javax.annotation.Nullable;
 
 import java.io.UnsupportedEncodingException;
@@ -110,6 +115,7 @@ protected static class ReactWebViewClient extends WebViewClient {
 
     protected boolean mLastLoadFailed = false;
     protected @Nullable ReadableArray mUrlPrefixesForDefaultIntent;
+    protected @Nullable List<Pattern> mOriginWhitelist;
 
     @Override
     public void onPageFinished(WebView webView, String url) {
@@ -137,32 +143,50 @@ public void onPageStarted(WebView webView, String url, Bitmap favicon) {
 
     @Override
     public boolean shouldOverrideUrlLoading(WebView view, String url) {
-        boolean useDefaultIntent = false;
-        if (mUrlPrefixesForDefaultIntent != null && mUrlPrefixesForDefaultIntent.size() > 0) {
-          ArrayList<Object> urlPrefixesForDefaultIntent =
-              mUrlPrefixesForDefaultIntent.toArrayList();
-          for (Object urlPrefix : urlPrefixesForDefaultIntent) {
-            if (url.startsWith((String) urlPrefix)) {
-              useDefaultIntent = true;
-              break;
-            }
+      if (url.equals(BLANK_URL)) return false;
+
+      // url blacklisting
+      if (mUrlPrefixesForDefaultIntent != null && mUrlPrefixesForDefaultIntent.size() > 0) {
+        ArrayList<Object> urlPrefixesForDefaultIntent =
+            mUrlPrefixesForDefaultIntent.toArrayList();
+        for (Object urlPrefix : urlPrefixesForDefaultIntent) {
+          if (url.startsWith((String) urlPrefix)) {
+            launchIntent(view.getContext(), url);
+            return true;
           }
         }
+      }
 
-        if (!useDefaultIntent &&
-            (url.startsWith("http://") || url.startsWith("https://") ||
-            url.startsWith("file://") || url.equals("about:blank"))) {
-          return false;
-        } else {
-          try {
-            Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
-            intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
-            view.getContext().startActivity(intent);
-          } catch (ActivityNotFoundException e) {
-            FLog.w(ReactConstants.TAG, "activity not found to handle uri scheme for: " + url, e);
-          }
+      if (mOriginWhitelist != null && shouldHandleURL(mOriginWhitelist, url)) {
+        return false;
+      }
+
+      launchIntent(view.getContext(), url);
+      return true;
+    }
+
+    private void launchIntent(Context context, String url) {
+      try {
+        Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
+        intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+        intent.addCategory(Intent.CATEGORY_BROWSABLE);
+        context.startActivity(intent);
+      } catch (ActivityNotFoundException e) {
+        FLog.w(ReactConstants.TAG, "activity not found to handle uri scheme for: " + url, e);
+      }
+    }
+
+    private boolean shouldHandleURL(List<Pattern> originWhitelist, String url) {
+      Uri uri = Uri.parse(url);
+      String scheme = uri.getScheme() != null ? uri.getScheme() : "";
+      String authority = uri.getAuthority() != null ? uri.getAuthority() : "";
+      String urlToCheck = scheme + "://" + authority;
+      for (Pattern pattern : originWhitelist) {
+        if (pattern.matcher(urlToCheck).matches()) {
           return true;
         }
+      }
+      return false;
     }
 
     @Override
@@ -211,6 +235,10 @@ protected WritableMap createWebViewEvent(WebView webView, String url) {
     public void setUrlPrefixesForDefaultIntent(ReadableArray specialUrls) {
       mUrlPrefixesForDefaultIntent = specialUrls;
     }
+
+    public void setOriginWhitelist(List<Pattern> originWhitelist) {
+      mOriginWhitelist = originWhitelist;
+    }
   }
 
   /**
@@ -356,6 +384,7 @@ protected ReactWebView createReactWebViewInstance(ThemedReactContext reactContex
   }
 
   @Override
+  @TargetApi(Build.VERSION_CODES.LOLLIPOP)
   protected WebView createViewInstance(ThemedReactContext reactContext) {
     ReactWebView webView = createReactWebViewInstance(reactContext);
     webView.setWebChromeClient(new WebChromeClient() {
@@ -375,9 +404,18 @@ public void onGeolocationPermissionsShowPrompt(String origin, GeolocationPermiss
     });
     reactContext.addLifecycleEventListener(webView);
     mWebViewConfig.configWebView(webView);
-    webView.getSettings().setBuiltInZoomControls(true);
-    webView.getSettings().setDisplayZoomControls(false);
-    webView.getSettings().setDomStorageEnabled(true);
+    WebSettings settings = webView.getSettings();
+    settings.setBuiltInZoomControls(true);
+    settings.setDisplayZoomControls(false);
+    settings.setDomStorageEnabled(true);
+
+    settings.setAllowFileAccess(false);
+    settings.setAllowContentAccess(false);
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+      settings.setAllowFileAccessFromFileURLs(false);
+      setAllowUniversalAccessFromFileURLs(webView, false);
+    }
+    setMixedContentMode(webView, "never");
 
     // Fixes broken full-screen modals/galleries due to body height being 0.
     webView.setLayoutParams(
@@ -546,6 +584,20 @@ public void setGeolocationEnabled(
     view.getSettings().setGeolocationEnabled(isGeolocationEnabled != null && isGeolocationEnabled);
   }
 
+  @ReactProp(name = "originWhitelist")
+  public void setOriginWhitelist(
+    WebView view,
+    @Nullable ReadableArray originWhitelist) {
+    ReactWebViewClient client = ((ReactWebView) view).getReactWebViewClient();
+    if (client != null && originWhitelist != null) {
+      List<Pattern> whiteList = new LinkedList<>();
+      for (int i = 0 ; i < originWhitelist.size() ; i++) {
+        whiteList.add(Pattern.compile(originWhitelist.getString(i)));
+      }
+      client.setOriginWhitelist(whiteList);
+    }
+  }
+
   @Override
   protected void addEventEmitters(ThemedReactContext reactContext, WebView view) {
     // Do not register default touch emitter and let WebView implementation handle touches

From 1ab7d49c2df5673dd214eb8a9b7fd3defb0ff857 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 7 May 2018 09:41:48 -0700
Subject: [PATCH 0442/1109] RN: Cleanup `__propTypesSecretDontUseThesePlease`

Reviewed By: bvaughn

Differential Revision: D7892903

fbshipit-source-id: aab0537fe508ac740d0a2798a04f54411c8c038d
---
 .../ReactNative/requireNativeComponent.js     | 20 ++-----------------
 Libraries/ReactNative/verifyPropTypes.js      |  9 +--------
 2 files changed, 3 insertions(+), 26 deletions(-)

diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index 83a071c7066f..0e09ad9f8096 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -108,24 +108,8 @@ function requireNativeComponent(
 
     viewConfig.uiViewClassName = viewName;
     viewConfig.validAttributes = {};
-
-    // ReactNative `View.propTypes` have been deprecated in favor of
-    // `ViewPropTypes`. In their place a temporary getter has been added with a
-    // deprecated warning message. Avoid triggering that warning here by using
-    // temporary workaround, __propTypesSecretDontUseThesePlease.
-    // TODO (bvaughn) Revert this particular change any time after April 1
-    if (componentInterface) {
-      viewConfig.propTypes =
-        /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
-         * error found when Flow v0.68 was deployed. To see the error delete
-         * this comment and run Flow. */
-        typeof componentInterface.__propTypesSecretDontUseThesePlease ===
-        'object'
-          ? componentInterface.__propTypesSecretDontUseThesePlease
-          : componentInterface.propTypes;
-    } else {
-      viewConfig.propTypes = null;
-    }
+    viewConfig.propTypes =
+      componentInterface == null ? null : componentInterface.propTypes;
 
     let baseModuleName = viewConfig.baseModuleName;
     let bubblingEventTypes = viewConfig.bubblingEventTypes;
diff --git a/Libraries/ReactNative/verifyPropTypes.js b/Libraries/ReactNative/verifyPropTypes.js
index b7b04d013c23..c88f9c1c8029 100644
--- a/Libraries/ReactNative/verifyPropTypes.js
+++ b/Libraries/ReactNative/verifyPropTypes.js
@@ -30,14 +30,7 @@ function verifyPropTypes(
   var componentName =
     componentInterface.displayName || componentInterface.name || 'unknown';
 
-  // ReactNative `View.propTypes` have been deprecated in favor of
-  // `ViewPropTypes`. In their place a temporary getter has been added with a
-  // deprecated warning message. Avoid triggering that warning here by using
-  // temporary workaround, __propTypesSecretDontUseThesePlease.
-  // TODO (bvaughn) Revert this particular change any time after April 1
-  var propTypes =
-    (componentInterface: any).__propTypesSecretDontUseThesePlease ||
-    componentInterface.propTypes;
+  var propTypes = componentInterface.propTypes;
 
   if (!propTypes) {
     return;

From 0125813f213662ec1d9bb4a456f5671adcff9d83 Mon Sep 17 00:00:00 2001
From: Andrew Clark <acdlite@fb.com>
Date: Mon, 7 May 2018 11:06:52 -0700
Subject: [PATCH 0443/1109] React sync for revisions 0887c7d...25dda90

Reviewed By: sebmarkbage

Differential Revision: D7886956

fbshipit-source-id: 5a94df618ce26dee0876b627fbbaaf0a14a403fe
---
 Libraries/Renderer/REVISION                   |    2 +-
 Libraries/Renderer/oss/ReactFabric-dev.js     | 2162 +++++++++--------
 Libraries/Renderer/oss/ReactFabric-prod.js    | 1757 +++++++-------
 .../Renderer/oss/ReactNativeRenderer-dev.js   | 2162 +++++++++--------
 .../Renderer/oss/ReactNativeRenderer-prod.js  | 1797 +++++++-------
 .../Renderer/shims/NativeMethodsMixin.js      |    1 +
 Libraries/Renderer/shims/ReactDebugTool.js    |    1 +
 Libraries/Renderer/shims/ReactFabric.js       |    1 +
 Libraries/Renderer/shims/ReactNative.js       |    1 +
 .../shims/ReactNativeComponentTree.js         |    1 +
 Libraries/Renderer/shims/ReactNativeTypes.js  |    1 +
 .../shims/ReactNativeViewConfigRegistry.js    |    1 +
 Libraries/Renderer/shims/ReactPerf.js         |    1 +
 Libraries/Renderer/shims/ReactTypes.js        |    1 +
 .../shims/createReactNativeComponentClass.js  |    1 +
 15 files changed, 4130 insertions(+), 3760 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index ba0ce2996c48..1899fb635260 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-0887c7d56cb9b83f36dcb490b4245d7bc33bda1f
\ No newline at end of file
+25dda90c1ecb0c662ab06e2c80c1ee31e0ae9d36
\ No newline at end of file
diff --git a/Libraries/Renderer/oss/ReactFabric-dev.js b/Libraries/Renderer/oss/ReactFabric-dev.js
index 0424315c8ed6..3b52fb146ce8 100644
--- a/Libraries/Renderer/oss/ReactFabric-dev.js
+++ b/Libraries/Renderer/oss/ReactFabric-dev.js
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
+ * @providesModule ReactFabric-dev
  * @preventMunge
  */
 
@@ -25,8 +26,8 @@ var deepDiffer = require("deepDiffer");
 var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
-var shallowEqual = require("fbjs/lib/shallowEqual");
 var checkPropTypes = require("prop-types/checkPropTypes");
+var shallowEqual = require("fbjs/lib/shallowEqual");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
 var FabricUIManager = require("FabricUIManager");
 
@@ -815,7 +816,7 @@ var ForwardRef = 14;
 
 function getParent(inst) {
   do {
-    inst = inst["return"];
+    inst = inst.return;
     // TODO: If this is a HostRoot we might want to bail out.
     // That is depending on if we want nested subtrees (layers) to bubble
     // events to their parent. We could also go through parentNode on the
@@ -2312,23 +2313,21 @@ injection.injectEventPluginsByName({
 
 // The Symbol used to tag the ReactElement-like types. If there is no native Symbol
 // nor polyfill, then a plain number is used for performance.
-var hasSymbol = typeof Symbol === "function" && Symbol["for"];
+var hasSymbol = typeof Symbol === "function" && Symbol.for;
 
-var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
-var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
-var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 0xeac7;
+var REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 0xeac8;
+var REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 0xeac9;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.strict_mode")
+  ? Symbol.for("react.strict_mode")
   : 0xeacc;
-var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
-var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
-var REACT_ASYNC_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.async_mode")
-  : 0xeacf;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 0xeace;
+var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 0xeacf;
 var REACT_FORWARD_REF_TYPE = hasSymbol
-  ? Symbol["for"]("react.forward_ref")
+  ? Symbol.for("react.forward_ref")
   : 0xead0;
 
 var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
@@ -3411,11 +3410,10 @@ var ContentReset = /*          */ 16;
 var Callback = /*              */ 32;
 var DidCapture = /*            */ 64;
 var Ref = /*                   */ 128;
-var ErrLog = /*                */ 256;
-var Snapshot = /*              */ 2048;
+var Snapshot = /*              */ 256;
 
 // Union of all host effects
-var HostEffectMask = /*        */ 2559;
+var HostEffectMask = /*        */ 511;
 
 var Incomplete = /*            */ 512;
 var ShouldCapture = /*         */ 1024;
@@ -3432,15 +3430,15 @@ function isFiberMountedImpl(fiber) {
     if ((node.effectTag & Placement) !== NoEffect) {
       return MOUNTING;
     }
-    while (node["return"]) {
-      node = node["return"];
+    while (node.return) {
+      node = node.return;
       if ((node.effectTag & Placement) !== NoEffect) {
         return MOUNTING;
       }
     }
   } else {
-    while (node["return"]) {
-      node = node["return"];
+    while (node.return) {
+      node = node.return;
     }
   }
   if (node.tag === HostRoot) {
@@ -3512,7 +3510,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
   var a = fiber;
   var b = alternate;
   while (true) {
-    var parentA = a["return"];
+    var parentA = a.return;
     var parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) {
       // We're at the root.
@@ -3542,7 +3540,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       invariant(false, "Unable to find node on an unmounted component.");
     }
 
-    if (a["return"] !== b["return"]) {
+    if (a.return !== b.return) {
       // The return pointer of A and the return pointer of B point to different
       // fibers. We assume that return pointers never criss-cross, so A must
       // belong to the child set of A.return, and B must belong to the child
@@ -3630,7 +3628,7 @@ function findCurrentHostFiber(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child) {
-      node.child["return"] = node;
+      node.child.return = node;
       node = node.child;
       continue;
     }
@@ -3638,12 +3636,12 @@ function findCurrentHostFiber(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
+      if (!node.return || node.return === currentParent) {
         return null;
       }
-      node = node["return"];
+      node = node.return;
     }
-    node.sibling["return"] = node["return"];
+    node.sibling.return = node.return;
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -3663,7 +3661,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child && node.tag !== HostPortal) {
-      node.child["return"] = node;
+      node.child.return = node;
       node = node.child;
       continue;
     }
@@ -3671,12 +3669,12 @@ function findCurrentHostFiberWithNoPortals(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
+      if (!node.return || node.return === currentParent) {
         return null;
       }
-      node = node["return"];
+      node = node.return;
     }
-    node.sibling["return"] = node["return"];
+    node.sibling.return = node.return;
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -3759,7 +3757,7 @@ function FiberNode(tag, pendingProps, key, mode) {
   this.stateNode = null;
 
   // Fiber
-  this["return"] = null;
+  this.return = null;
   this.child = null;
   this.sibling = null;
   this.index = 0;
@@ -4044,7 +4042,7 @@ function assignFiberPropertiesInDEV(target, source) {
   target.key = source.key;
   target.type = source.type;
   target.stateNode = source.stateNode;
-  target["return"] = source["return"];
+  target.return = source.return;
   target.child = source.child;
   target.sibling = source.sibling;
   target.index = source.index;
@@ -4204,7 +4202,7 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
   do {
     info += describeFiber(node);
     // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
+    node = node.return;
   } while (node);
   return info;
 }
@@ -4374,7 +4372,7 @@ var ReactStrictModeWarnings = {
         maybeStrictRoot = fiber;
       }
 
-      fiber = fiber["return"];
+      fiber = fiber.return;
     }
 
     return maybeStrictRoot;
@@ -4495,16 +4493,6 @@ var ReactStrictModeWarnings = {
       return;
     }
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    // Note that it is sufficient to check for the presence of a
-    // single lifecycle, componentWillMount, with the polyfill flag.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning === true
-    ) {
-      return;
-    }
-
     var warningsForRoot = void 0;
     if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
       warningsForRoot = {
@@ -4520,19 +4508,23 @@ var ReactStrictModeWarnings = {
 
     var unsafeLifecycles = [];
     if (
-      typeof instance.componentWillMount === "function" ||
+      (typeof instance.componentWillMount === "function" &&
+        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
       typeof instance.UNSAFE_componentWillMount === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillMount");
     }
     if (
-      typeof instance.componentWillReceiveProps === "function" ||
+      (typeof instance.componentWillReceiveProps === "function" &&
+        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+          true) ||
       typeof instance.UNSAFE_componentWillReceiveProps === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
     }
     if (
-      typeof instance.componentWillUpdate === "function" ||
+      (typeof instance.componentWillUpdate === "function" &&
+        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
       typeof instance.UNSAFE_componentWillUpdate === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillUpdate");
@@ -4574,7 +4566,7 @@ function getCurrentFiberOwnerName() {
   return null;
 }
 
-function getCurrentFiberStackAddendum() {
+function getCurrentFiberStackAddendum$1() {
   {
     var fiber = ReactDebugCurrentFiber.current;
     if (fiber === null) {
@@ -4594,7 +4586,7 @@ function resetCurrentFiber() {
 }
 
 function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum$1;
   ReactDebugCurrentFiber.current = fiber;
   ReactDebugCurrentFiber.phase = null;
 }
@@ -4610,7 +4602,7 @@ var ReactDebugCurrentFiber = {
   setCurrentFiber: setCurrentFiber,
   setCurrentPhase: setCurrentPhase,
   getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum$1
 };
 
 // Prefix measurements so that it's possible to filter them.
@@ -4767,13 +4759,13 @@ var pauseTimers = function() {
     if (fiber._debugIsCurrentlyTiming) {
       endFiberMark(fiber, null, null);
     }
-    fiber = fiber["return"];
+    fiber = fiber.return;
   }
 };
 
 var resumeTimersRecursively = function(fiber) {
-  if (fiber["return"] !== null) {
-    resumeTimersRecursively(fiber["return"]);
+  if (fiber.return !== null) {
+    resumeTimersRecursively(fiber.return);
   }
   if (fiber._debugIsCurrentlyTiming) {
     beginFiberMark(fiber, null);
@@ -4865,7 +4857,7 @@ function stopWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
+    currentFiber = fiber.return;
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -4880,7 +4872,7 @@ function stopFailedWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
+    currentFiber = fiber.return;
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -5070,100 +5062,232 @@ function stopCommitLifeCyclesTimer() {
   }
 }
 
-var didWarnUpdateInsideUpdate = void 0;
+// UpdateQueue is a linked list of prioritized updates.
+//
+// Like fibers, update queues come in pairs: a current queue, which represents
+// the visible state of the screen, and a work-in-progress queue, which is
+// can be mutated and processed asynchronously before it is committed — a form
+// of double buffering. If a work-in-progress render is discarded before
+// finishing, we create a new work-in-progress by cloning the current queue.
+//
+// Both queues share a persistent, singly-linked list structure. To schedule an
+// update, we append it to the end of both queues. Each queue maintains a
+// pointer to first update in the persistent list that hasn't been processed.
+// The work-in-progress pointer always has a position equal to or greater than
+// the current queue, since we always work on that one. The current queue's
+// pointer is only updated during the commit phase, when we swap in the
+// work-in-progress.
+//
+// For example:
+//
+//   Current pointer:           A - B - C - D - E - F
+//   Work-in-progress pointer:              D - E - F
+//                                          ^
+//                                          The work-in-progress queue has
+//                                          processed more updates than current.
+//
+// The reason we append to both queues is because otherwise we might drop
+// updates without ever processing them. For example, if we only add updates to
+// the work-in-progress queue, some updates could be lost whenever a work-in
+// -progress render restarts by cloning from current. Similarly, if we only add
+// updates to the current queue, the updates will be lost whenever an already
+// in-progress queue commits and swaps with the current queue. However, by
+// adding to both queues, we guarantee that the update will be part of the next
+// work-in-progress. (And because the work-in-progress queue becomes the
+// current queue once it commits, there's no danger of applying the same
+// update twice.)
+//
+// Prioritization
+// --------------
+//
+// Updates are not sorted by priority, but by insertion; new updates are always
+// appended to the end of the list.
+//
+// The priority is still important, though. When processing the update queue
+// during the render phase, only the updates with sufficient priority are
+// included in the result. If we skip an update because it has insufficient
+// priority, it remains in the queue to be processed later, during a lower
+// priority render. Crucially, all updates subsequent to a skipped update also
+// remain in the queue *regardless of their priority*. That means high priority
+// updates are sometimes processed twice, at two separate priorities. We also
+// keep track of a base state, that represents the state before the first
+// update in the queue is applied.
+//
+// For example:
+//
+//   Given a base state of '', and the following queue of updates
+//
+//     A1 - B2 - C1 - D2
+//
+//   where the number indicates the priority, and the update is applied to the
+//   previous state by appending a letter, React will process these updates as
+//   two separate renders, one per distinct priority level:
+//
+//   First render, at priority 1:
+//     Base state: ''
+//     Updates: [A1, C1]
+//     Result state: 'AC'
+//
+//   Second render, at priority 2:
+//     Base state: 'A'            <-  The base state does not include C1,
+//                                    because B2 was skipped.
+//     Updates: [B2, C1, D2]      <-  C1 was rebased on top of B2
+//     Result state: 'ABCD'
+//
+// Because we process updates in insertion order, and rebase high priority
+// updates when preceding updates are skipped, the final result is deterministic
+// regardless of priority. Intermediate state may vary according to system
+// resources, but the final state is always the same.
+
+var UpdateState = 0;
+var ReplaceState = 1;
+var ForceUpdate = 2;
+var CaptureUpdate = 3;
 
+var didWarnUpdateInsideUpdate = void 0;
+var currentlyProcessingQueue = void 0;
+var resetCurrentlyProcessingQueue = void 0;
 {
   didWarnUpdateInsideUpdate = false;
+  currentlyProcessingQueue = null;
+  resetCurrentlyProcessingQueue = function() {
+    currentlyProcessingQueue = null;
+  };
 }
 
-// Callbacks are not validated until invocation
-
-// Singly linked-list of updates. When an update is scheduled, it is added to
-// the queue of the current fiber and the work-in-progress fiber. The two queues
-// are separate but they share a persistent structure.
-//
-// During reconciliation, updates are removed from the work-in-progress fiber,
-// but they remain on the current fiber. That ensures that if a work-in-progress
-// is aborted, the aborted updates are recovered by cloning from current.
-//
-// The work-in-progress queue is always a subset of the current queue.
-//
-// When the tree is committed, the work-in-progress becomes the current.
-
 function createUpdateQueue(baseState) {
   var queue = {
-    baseState: baseState,
     expirationTime: NoWork,
-    first: null,
-    last: null,
-    callbackList: null,
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null,
+    hasForceUpdate: false
+  };
+  return queue;
+}
+
+function cloneUpdateQueue(currentQueue) {
+  var queue = {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+
+    // TODO: With resuming, if we bail out and resuse the child tree, we should
+    // keep these effects.
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+
     hasForceUpdate: false,
-    isInitialized: false,
-    capturedValues: null
+
+    firstEffect: null,
+    lastEffect: null,
+
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
   };
-  {
-    queue.isProcessing = false;
-  }
   return queue;
 }
 
-function insertUpdateIntoQueue(queue, update) {
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+
+    tag: UpdateState,
+    payload: null,
+    callback: null,
+
+    next: null,
+    nextEffect: null
+  };
+}
+
+function appendUpdateToQueue(queue, update, expirationTime) {
   // Append the update to the end of the list.
-  if (queue.last === null) {
+  if (queue.lastUpdate === null) {
     // Queue is empty
-    queue.first = queue.last = update;
+    queue.firstUpdate = queue.lastUpdate = update;
   } else {
-    queue.last.next = update;
-    queue.last = update;
+    queue.lastUpdate.next = update;
+    queue.lastUpdate = update;
   }
   if (
     queue.expirationTime === NoWork ||
-    queue.expirationTime > update.expirationTime
+    queue.expirationTime > expirationTime
   ) {
-    queue.expirationTime = update.expirationTime;
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    queue.expirationTime = expirationTime;
   }
 }
 
-var q1 = void 0;
-var q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  // We'll have at least one and at most two distinct update queues.
-  var alternateFiber = fiber.alternate;
-  var queue1 = fiber.updateQueue;
-  if (queue1 === null) {
-    // TODO: We don't know what the base state will be until we begin work.
-    // It depends on which fiber is the next current. Initialize with an empty
-    // base state, then set to the memoizedState when rendering. Not super
-    // happy with this approach.
-    queue1 = fiber.updateQueue = createUpdateQueue(null);
-  }
-
+function enqueueUpdate(fiber, update, expirationTime) {
+  // Update queues are created lazily.
+  var alternate = fiber.alternate;
+  var queue1 = void 0;
   var queue2 = void 0;
-  if (alternateFiber !== null) {
-    queue2 = alternateFiber.updateQueue;
-    if (queue2 === null) {
-      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
+  if (alternate === null) {
+    // There's only one fiber.
+    queue1 = fiber.updateQueue;
+    queue2 = null;
+    if (queue1 === null) {
+      queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
     }
   } else {
-    queue2 = null;
+    // There are two owners.
+    queue1 = fiber.updateQueue;
+    queue2 = alternate.updateQueue;
+    if (queue1 === null) {
+      if (queue2 === null) {
+        // Neither fiber has an update queue. Create new ones.
+        queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
+        queue2 = alternate.updateQueue = createUpdateQueue(
+          alternate.memoizedState
+        );
+      } else {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue1 = fiber.updateQueue = cloneUpdateQueue(queue2);
+      }
+    } else {
+      if (queue2 === null) {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue2 = alternate.updateQueue = cloneUpdateQueue(queue1);
+      } else {
+        // Both owners have an update queue.
+      }
+    }
+  }
+  if (queue2 === null || queue1 === queue2) {
+    // There's only a single queue.
+    appendUpdateToQueue(queue1, update, expirationTime);
+  } else {
+    // There are two queues. We need to append the update to both queues,
+    // while accounting for the persistent structure of the list — we don't
+    // want the same update to be added multiple times.
+    if (queue1.lastUpdate === null || queue2.lastUpdate === null) {
+      // One of the queues is not empty. We must add the update to both queues.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      appendUpdateToQueue(queue2, update, expirationTime);
+    } else {
+      // Both queues are non-empty. The last update is the same in both lists,
+      // because of structural sharing. So, only append to one of the lists.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      // But we still need to update the `lastUpdate` pointer of queue2.
+      queue2.lastUpdate = update;
+    }
   }
-  queue2 = queue2 !== queue1 ? queue2 : null;
-
-  // Use module variables instead of returning a tuple
-  q1 = queue1;
-  q2 = queue2;
-}
-
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  var queue1 = q1;
-  var queue2 = q2;
 
-  // Warn if an update is scheduled from inside an updater function.
   {
     if (
-      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
+      fiber.tag === ClassComponent &&
+      (currentlyProcessingQueue === queue1 ||
+        (queue2 !== null && currentlyProcessingQueue === queue2)) &&
       !didWarnUpdateInsideUpdate
     ) {
       warning(
@@ -5176,225 +5300,328 @@ function insertUpdateIntoFiber(fiber, update) {
       didWarnUpdateInsideUpdate = true;
     }
   }
+}
 
-  // If there's only one queue, add the update to that queue and exit.
-  if (queue2 === null) {
-    insertUpdateIntoQueue(queue1, update);
-    return;
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  // Captured updates go into a separate list, and only on the work-in-
+  // progress queue.
+  var workInProgressQueue = workInProgress.updateQueue;
+  if (workInProgressQueue === null) {
+    workInProgressQueue = workInProgress.updateQueue = createUpdateQueue(
+      workInProgress.memoizedState
+    );
+  } else {
+    // TODO: I put this here rather than createWorkInProgress so that we don't
+    // clone the queue unnecessarily. There's probably a better way to
+    // structure this.
+    workInProgressQueue = ensureWorkInProgressQueueIsAClone(
+      workInProgress,
+      workInProgressQueue
+    );
   }
 
-  // If either queue is empty, we need to add to both queues.
-  if (queue1.last === null || queue2.last === null) {
-    insertUpdateIntoQueue(queue1, update);
-    insertUpdateIntoQueue(queue2, update);
-    return;
+  // Append the update to the end of the list.
+  if (workInProgressQueue.lastCapturedUpdate === null) {
+    // This is the first render phase update
+    workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update;
+  } else {
+    workInProgressQueue.lastCapturedUpdate.next = update;
+    workInProgressQueue.lastCapturedUpdate = update;
+  }
+  if (
+    workInProgressQueue.expirationTime === NoWork ||
+    workInProgressQueue.expirationTime > renderExpirationTime
+  ) {
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    workInProgressQueue.expirationTime = renderExpirationTime;
   }
-
-  // If both lists are not empty, the last update is the same for both lists
-  // because of structural sharing. So, we should only append to one of
-  // the lists.
-  insertUpdateIntoQueue(queue1, update);
-  // But we still need to update the `last` pointer of queue2.
-  queue2.last = update;
 }
 
-function getUpdateExpirationTime(fiber) {
-  switch (fiber.tag) {
-    case HostRoot:
-    case ClassComponent:
-      var updateQueue = fiber.updateQueue;
-      if (updateQueue === null) {
-        return NoWork;
-      }
-      return updateQueue.expirationTime;
-    default:
-      return NoWork;
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  if (current !== null) {
+    // If the work-in-progress queue is equal to the current queue,
+    // we need to clone it first.
+    if (queue === current.updateQueue) {
+      queue = workInProgress.updateQueue = cloneUpdateQueue(queue);
+    }
   }
+  return queue;
 }
 
-function getStateFromUpdate(update, instance, prevState, props) {
-  var partialState = update.partialState;
-  if (typeof partialState === "function") {
-    return partialState.call(instance, prevState, props);
-  } else {
-    return partialState;
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case ReplaceState: {
+      var _payload = update.payload;
+      if (typeof _payload === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload.call(instance, prevState, nextProps);
+          }
+        }
+        return _payload.call(instance, prevState, nextProps);
+      }
+      // State object
+      return _payload;
+    }
+    case CaptureUpdate: {
+      workInProgress.effectTag =
+        (workInProgress.effectTag & ~ShouldCapture) | DidCapture;
+    }
+    // Intentional fallthrough
+    case UpdateState: {
+      var _payload2 = update.payload;
+      var partialState = void 0;
+      if (typeof _payload2 === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload2.call(instance, prevState, nextProps);
+          }
+        }
+        partialState = _payload2.call(instance, prevState, nextProps);
+      } else {
+        // Partial state object
+        partialState = _payload2;
+      }
+      if (partialState === null || partialState === undefined) {
+        // Null and undefined are treated as no-ops.
+        return prevState;
+      }
+      // Merge the partial state and the previous state.
+      return Object.assign({}, prevState, partialState);
+    }
+    case ForceUpdate: {
+      queue.hasForceUpdate = true;
+      return prevState;
+    }
   }
+  return prevState;
 }
 
 function processUpdateQueue(
-  current,
   workInProgress,
   queue,
-  instance,
   props,
+  instance,
   renderExpirationTime
 ) {
-  if (current !== null && current.updateQueue === queue) {
-    // We need to create a work-in-progress queue, by cloning the current queue.
-    var currentQueue = queue;
-    queue = workInProgress.updateQueue = {
-      baseState: currentQueue.baseState,
-      expirationTime: currentQueue.expirationTime,
-      first: currentQueue.first,
-      last: currentQueue.last,
-      isInitialized: currentQueue.isInitialized,
-      capturedValues: currentQueue.capturedValues,
-      // These fields are no longer valid because they were already committed.
-      // Reset them.
-      callbackList: null,
-      hasForceUpdate: false
-    };
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > renderExpirationTime
+  ) {
+    // Insufficient priority. Bailout.
+    return;
   }
 
+  queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+
   {
-    // Set this flag so we can warn if setState is called inside the update
-    // function of another setState.
-    queue.isProcessing = true;
-  }
-
-  // Reset the remaining expiration time. If we skip over any updates, we'll
-  // increase this accordingly.
-  queue.expirationTime = NoWork;
-
-  // TODO: We don't know what the base state will be until we begin work.
-  // It depends on which fiber is the next current. Initialize with an empty
-  // base state, then set to the memoizedState when rendering. Not super
-  // happy with this approach.
-  var state = void 0;
-  if (queue.isInitialized) {
-    state = queue.baseState;
-  } else {
-    state = queue.baseState = workInProgress.memoizedState;
-    queue.isInitialized = true;
+    currentlyProcessingQueue = queue;
   }
-  var dontMutatePrevState = true;
-  var update = queue.first;
-  var didSkip = false;
+
+  // These values may change as we process the queue.
+  var newBaseState = queue.baseState;
+  var newFirstUpdate = null;
+  var newExpirationTime = NoWork;
+
+  // Iterate through the list of updates to compute the result.
+  var update = queue.firstUpdate;
+  var resultState = newBaseState;
   while (update !== null) {
     var updateExpirationTime = update.expirationTime;
     if (updateExpirationTime > renderExpirationTime) {
       // This update does not have sufficient priority. Skip it.
-      var remainingExpirationTime = queue.expirationTime;
+      if (newFirstUpdate === null) {
+        // This is the first skipped update. It will be the first update in
+        // the new list.
+        newFirstUpdate = update;
+        // Since this is the first update that was skipped, the current result
+        // is the new base state.
+        newBaseState = resultState;
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
       if (
-        remainingExpirationTime === NoWork ||
-        remainingExpirationTime > updateExpirationTime
+        newExpirationTime === NoWork ||
+        newExpirationTime > updateExpirationTime
       ) {
-        // Update the remaining expiration time.
-        queue.expirationTime = updateExpirationTime;
+        newExpirationTime = updateExpirationTime;
       }
-      if (!didSkip) {
-        didSkip = true;
-        queue.baseState = state;
+    } else {
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback = update.callback;
+      if (_callback !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastEffect === null) {
+          queue.firstEffect = queue.lastEffect = update;
+        } else {
+          queue.lastEffect.nextEffect = update;
+          queue.lastEffect = update;
+        }
       }
-      // Continue to the next update.
-      update = update.next;
-      continue;
     }
+    // Continue to the next update.
+    update = update.next;
+  }
 
-    // This update does have sufficient priority.
-
-    // If no previous updates were skipped, drop this update from the queue by
-    // advancing the head of the list.
-    if (!didSkip) {
-      queue.first = update.next;
-      if (queue.first === null) {
-        queue.last = null;
+  // Separately, iterate though the list of captured updates.
+  var newFirstCapturedUpdate = null;
+  update = queue.firstCapturedUpdate;
+  while (update !== null) {
+    var _updateExpirationTime = update.expirationTime;
+    if (_updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      if (newFirstCapturedUpdate === null) {
+        // This is the first skipped captured update. It will be the first
+        // update in the new list.
+        newFirstCapturedUpdate = update;
+        // If this is the first update that was skipped, the current result is
+        // the new base state.
+        if (newFirstUpdate === null) {
+          newBaseState = resultState;
+        }
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
+      if (
+        newExpirationTime === NoWork ||
+        newExpirationTime > _updateExpirationTime
+      ) {
+        newExpirationTime = _updateExpirationTime;
       }
-    }
-
-    // Invoke setState callback an extra time to help detect side-effects.
-    // Ignore the return value in this case.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      getStateFromUpdate(update, instance, state, props);
-    }
-
-    // Process the update
-    var _partialState = void 0;
-    if (update.isReplace) {
-      state = getStateFromUpdate(update, instance, state, props);
-      dontMutatePrevState = true;
     } else {
-      _partialState = getStateFromUpdate(update, instance, state, props);
-      if (_partialState) {
-        if (dontMutatePrevState) {
-          // $FlowFixMe: Idk how to type this properly.
-          state = Object.assign({}, state, _partialState);
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback2 = update.callback;
+      if (_callback2 !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastCapturedEffect === null) {
+          queue.firstCapturedEffect = queue.lastCapturedEffect = update;
         } else {
-          state = Object.assign(state, _partialState);
+          queue.lastCapturedEffect.nextEffect = update;
+          queue.lastCapturedEffect = update;
         }
-        dontMutatePrevState = false;
-      }
-    }
-    if (update.isForced) {
-      queue.hasForceUpdate = true;
-    }
-    if (update.callback !== null) {
-      // Append to list of callbacks.
-      var _callbackList = queue.callbackList;
-      if (_callbackList === null) {
-        _callbackList = queue.callbackList = [];
-      }
-      _callbackList.push(update);
-    }
-    if (update.capturedValue !== null) {
-      var _capturedValues = queue.capturedValues;
-      if (_capturedValues === null) {
-        queue.capturedValues = [update.capturedValue];
-      } else {
-        _capturedValues.push(update.capturedValue);
       }
     }
     update = update.next;
   }
 
-  if (queue.callbackList !== null) {
+  if (newFirstUpdate === null) {
+    queue.lastUpdate = null;
+  }
+  if (newFirstCapturedUpdate === null) {
+    queue.lastCapturedUpdate = null;
+  } else {
     workInProgress.effectTag |= Callback;
-  } else if (
-    queue.first === null &&
-    !queue.hasForceUpdate &&
-    queue.capturedValues === null
-  ) {
-    // The queue is empty. We can reset it.
-    workInProgress.updateQueue = null;
   }
-
-  if (!didSkip) {
-    didSkip = true;
-    queue.baseState = state;
+  if (newFirstUpdate === null && newFirstCapturedUpdate === null) {
+    // We processed every update, without skipping. That means the new base
+    // state is the same as the result state.
+    newBaseState = resultState;
   }
 
+  queue.baseState = newBaseState;
+  queue.firstUpdate = newFirstUpdate;
+  queue.firstCapturedUpdate = newFirstCapturedUpdate;
+  queue.expirationTime = newExpirationTime;
+
+  workInProgress.memoizedState = resultState;
+
   {
-    // No longer processing.
-    queue.isProcessing = false;
+    currentlyProcessingQueue = null;
   }
+}
 
-  return state;
+function callCallback(callback, context) {
+  invariant(
+    typeof callback === "function",
+    "Invalid argument passed as callback. Expected a function. Instead " +
+      "received: %s",
+    callback
+  );
+  callback.call(context);
 }
 
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (callbackList === null) {
-    return;
+function commitUpdateQueue(
+  finishedWork,
+  finishedQueue,
+  instance,
+  renderExpirationTime
+) {
+  // If the finished render included captured updates, and there are still
+  // lower priority updates left over, we need to keep the captured updates
+  // in the queue so that they are rebased and not dropped once we process the
+  // queue again at the lower priority.
+  if (finishedQueue.firstCapturedUpdate !== null) {
+    // Join the captured update list to the end of the normal list.
+    if (finishedQueue.lastUpdate !== null) {
+      finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate;
+      finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate;
+    }
+    // Clear the list of captured updates.
+    finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null;
   }
-  // Set the list to null to make sure they don't get called more than once.
-  queue.callbackList = null;
-  for (var i = 0; i < callbackList.length; i++) {
-    var update = callbackList[i];
-    var _callback = update.callback;
-    // This update might be processed again. Clear the callback so it's only
-    // called once.
-    update.callback = null;
-    invariant(
-      typeof _callback === "function",
-      "Invalid argument passed as callback. Expected a function. Instead " +
-        "received: %s",
-      _callback
-    );
-    _callback.call(context);
+
+  // Commit the effects
+  var effect = finishedQueue.firstEffect;
+  finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+  while (effect !== null) {
+    var _callback3 = effect.callback;
+    if (_callback3 !== null) {
+      effect.callback = null;
+      callCallback(_callback3, instance);
+    }
+    effect = effect.nextEffect;
+  }
+
+  effect = finishedQueue.firstCapturedEffect;
+  finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+  while (effect !== null) {
+    var _callback4 = effect.callback;
+    if (_callback4 !== null) {
+      effect.callback = null;
+      callCallback(_callback4, instance);
+    }
+    effect = effect.nextEffect;
   }
 }
 
@@ -5402,18 +5629,19 @@ var fakeInternalInstance = {};
 var isArray = Array.isArray;
 
 var didWarnAboutStateAssignmentForComponent = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
 var didWarnAboutUninitializedState = void 0;
 var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
 var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
+var warnOnUndefinedDerivedState = void 0;
 var warnOnInvalidCallback = void 0;
 
 {
   didWarnAboutStateAssignmentForComponent = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
   didWarnAboutUninitializedState = new Set();
   didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
   didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
 
   var didWarnOnInvalidCallback = new Set();
 
@@ -5434,6 +5662,21 @@ var warnOnInvalidCallback = void 0;
     }
   };
 
+  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
+    if (partialState === undefined) {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+        didWarnAboutUndefinedDerivedState.add(componentName);
+        warning(
+          false,
+          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+            "You have returned undefined.",
+          componentName
+        );
+      }
+    }
+  };
+
   // This is so gross but it's at least non-critical and can be removed if
   // it causes problems. This is meant to give a nicer error message for
   // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
@@ -5455,17 +5698,43 @@ var warnOnInvalidCallback = void 0;
   });
   Object.freeze(fakeInternalInstance);
 }
-function callGetDerivedStateFromCatch(ctor, capturedValues) {
-  var resultState = {};
-  for (var i = 0; i < capturedValues.length; i++) {
-    var capturedValue = capturedValues[i];
-    var error = capturedValue.value;
-    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
-    if (partialState !== null && partialState !== undefined) {
-      Object.assign(resultState, partialState);
+
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+
+  {
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      // Invoke the function an extra time to help detect side-effects.
+      getDerivedStateFromProps(nextProps, prevState);
     }
   }
-  return resultState;
+
+  var partialState = getDerivedStateFromProps(nextProps, prevState);
+
+  {
+    warnOnUndefinedDerivedState(workInProgress, partialState);
+  }
+  // Merge the partial state and the previous state.
+  var memoizedState =
+    partialState === null || partialState === undefined
+      ? prevState
+      : Object.assign({}, prevState, partialState);
+  workInProgress.memoizedState = memoizedState;
+
+  // Once the update queue is empty, persist the derived state onto the
+  // base state.
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
+    updateQueue.baseState = memoizedState;
+  }
 }
 
 var ReactFiberClassComponent = function(
@@ -5481,65 +5750,57 @@ var ReactFiberClassComponent = function(
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged;
 
-  // Class component state updater
-
-  var updater = {
+  var classComponentUpdater = {
     isMounted: isMounted,
-    enqueueSetState: function(instance, partialState, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "setState");
-      }
+    enqueueSetState: function(inst, payload, callback) {
+      var fiber = get$1(inst);
       var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: partialState,
-        callback: callback,
-        isReplace: false,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+
+      var update = createUpdate(expirationTime);
+      update.payload = payload;
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "setState");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueReplaceState: function(instance, state, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "replaceState");
-      }
+    enqueueReplaceState: function(inst, payload, callback) {
+      var fiber = get$1(inst);
       var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: state,
-        callback: callback,
-        isReplace: true,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+
+      var update = createUpdate(expirationTime);
+      update.tag = ReplaceState;
+      update.payload = payload;
+
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "replaceState");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueForceUpdate: function(instance, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "forceUpdate");
-      }
+    enqueueForceUpdate: function(inst, callback) {
+      var fiber = get$1(inst);
       var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: null,
-        callback: callback,
-        isReplace: false,
-        isForced: true,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+
+      var update = createUpdate(expirationTime);
+      update.tag = ForceUpdate;
+
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "forceUpdate");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     }
   };
@@ -5553,11 +5814,10 @@ var ReactFiberClassComponent = function(
     newContext
   ) {
     if (
-      oldProps === null ||
-      (workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate)
+      workInProgress.updateQueue !== null &&
+      workInProgress.updateQueue.hasForceUpdate
     ) {
-      // If the workInProgress already has an Update effect, return true
+      // If forceUpdate was called, disregard sCU.
       return true;
     }
 
@@ -5814,13 +6074,8 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function resetInputPointers(workInProgress, instance) {
-    instance.props = workInProgress.memoizedProps;
-    instance.state = workInProgress.memoizedState;
-  }
-
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
+    instance.updater = classComponentUpdater;
     workInProgress.stateNode = instance;
     // The instance needs access to the fiber so that it can schedule updates
     set(instance, workInProgress);
@@ -5829,7 +6084,7 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function constructClassInstance(workInProgress, props) {
+  function constructClassInstance(workInProgress, props, renderExpirationTime) {
     var ctor = workInProgress.type;
     var unmaskedContext = getUnmaskedContext(workInProgress);
     var needsContext = isContextConsumer(workInProgress);
@@ -5838,19 +6093,21 @@ var ReactFiberClassComponent = function(
       : emptyObject;
 
     // Instantiate twice to help detect side-effects.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      new ctor(props, context); // eslint-disable-line no-new
+    {
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        new ctor(props, context); // eslint-disable-line no-new
+      }
     }
 
     var instance = new ctor(props, context);
-    var state =
+    var state = (workInProgress.memoizedState =
       instance.state !== null && instance.state !== undefined
         ? instance.state
-        : null;
+        : null);
     adoptClassInstance(workInProgress, instance);
 
     {
@@ -5941,26 +6198,6 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    workInProgress.memoizedState = state;
-
-    var partialState = callGetDerivedStateFromProps(
-      workInProgress,
-      instance,
-      props,
-      state
-    );
-
-    if (partialState !== null && partialState !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      workInProgress.memoizedState = Object.assign(
-        {},
-        workInProgress.memoizedState,
-        partialState
-      );
-    }
-
     // Cache unmasked context so we can avoid recreating masked context unless necessary.
     // ReactFiberContext usually updates this cache but can't for newly-created instances.
     if (needsContext) {
@@ -5993,7 +6230,7 @@ var ReactFiberClassComponent = function(
           getComponentName(workInProgress) || "Component"
         );
       }
-      updater.enqueueReplaceState(instance, instance.state, null);
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
@@ -6027,57 +6264,13 @@ var ReactFiberClassComponent = function(
           );
         }
       }
-      updater.enqueueReplaceState(instance, instance.state, null);
-    }
-  }
-
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    var type = workInProgress.type;
-
-    if (typeof type.getDerivedStateFromProps === "function") {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        // Invoke method an extra time to help detect side-effects.
-        type.getDerivedStateFromProps.call(null, nextProps, prevState);
-      }
-
-      var partialState = type.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
-
-      {
-        if (partialState === undefined) {
-          var componentName = getComponentName(workInProgress) || "Component";
-          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-            didWarnAboutUndefinedDerivedState.add(componentName);
-            warning(
-              false,
-              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-                "You have returned undefined.",
-              componentName
-            );
-          }
-        }
-      }
-
-      return partialState;
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
   // Invokes the mount life-cycles on a previously never rendered instance.
   function mountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
-    var current = workInProgress.alternate;
 
     {
       checkClassInstance(workInProgress);
@@ -6108,6 +6301,28 @@ var ReactFiberClassComponent = function(
       }
     }
 
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
+        workInProgress,
+        updateQueue,
+        props,
+        instance,
+        renderExpirationTime
+      );
+      instance.state = workInProgress.memoizedState;
+    }
+
+    var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
+        workInProgress,
+        getDerivedStateFromProps,
+        props
+      );
+      instance.state = workInProgress.memoizedState;
+    }
+
     // In order to support react-lifecycles-compat polyfilled components,
     // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
@@ -6119,18 +6334,19 @@ var ReactFiberClassComponent = function(
       callComponentWillMount(workInProgress, instance);
       // If we had additional state updates during this life-cycle, let's
       // process them now.
-      var updateQueue = workInProgress.updateQueue;
+      updateQueue = workInProgress.updateQueue;
       if (updateQueue !== null) {
-        instance.state = processUpdateQueue(
-          current,
+        processUpdateQueue(
           workInProgress,
           updateQueue,
-          instance,
           props,
+          instance,
           renderExpirationTime
         );
+        instance.state = workInProgress.memoizedState;
       }
     }
+
     if (typeof instance.componentDidMount === "function") {
       workInProgress.effectTag |= Update;
     }
@@ -6139,16 +6355,18 @@ var ReactFiberClassComponent = function(
   function resumeMountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
+    instance.props = oldProps;
+
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6172,93 +6390,27 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        null,
+    var newState = (instance.state = oldState);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
         workInProgress,
-        workInProgress.updateQueue,
-        instance,
+        updateQueue,
         newProps,
+        instance,
         renderExpirationTime
       );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
+      newState = workInProgress.memoizedState;
     }
 
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
         workInProgress,
-        instance,
-        newProps,
-        newState
+        getDerivedStateFromProps,
+        newProps
       );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue = workInProgress.updateQueue;
-      if (_updateQueue !== null) {
-        _updateQueue.baseState = Object.assign(
-          {},
-          _updateQueue.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue2 = workInProgress.updateQueue;
-      if (_updateQueue2 !== null) {
-        _updateQueue2.baseState = Object.assign(
-          {},
-          _updateQueue2.baseState,
-          derivedStateFromCatch
-        );
-      }
+      newState = workInProgress.memoizedState;
     }
 
     if (
@@ -6315,9 +6467,9 @@ var ReactFiberClassComponent = function(
       }
 
       // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
+      // memoized state to indicate that this work can be reused.
+      workInProgress.memoizedProps = newProps;
+      workInProgress.memoizedState = newState;
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6333,16 +6485,18 @@ var ReactFiberClassComponent = function(
   function updateClassInstance(current, workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
+    instance.props = oldProps;
+
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6366,94 +6520,27 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        current,
+    var newState = (instance.state = oldState);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
         workInProgress,
-        workInProgress.updateQueue,
-        instance,
+        updateQueue,
         newProps,
+        instance,
         renderExpirationTime
       );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
+      newState = workInProgress.memoizedState;
     }
 
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
         workInProgress,
-        instance,
-        newProps,
-        newState
+        getDerivedStateFromProps,
+        newProps
       );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue3 = workInProgress.updateQueue;
-      if (_updateQueue3 !== null) {
-        _updateQueue3.baseState = Object.assign(
-          {},
-          _updateQueue3.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue4 = workInProgress.updateQueue;
-      if (_updateQueue4 !== null) {
-        _updateQueue4.baseState = Object.assign(
-          {},
-          _updateQueue4.baseState,
-          derivedStateFromCatch
-        );
-      }
+      newState = workInProgress.memoizedState;
     }
 
     if (
@@ -6540,8 +6627,8 @@ var ReactFiberClassComponent = function(
 
       // If shouldComponentUpdate returned false, we should still update the
       // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
+      workInProgress.memoizedProps = newProps;
+      workInProgress.memoizedState = newState;
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6555,7 +6642,6 @@ var ReactFiberClassComponent = function(
 
   return {
     adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: constructClassInstance,
     mountClassInstance: mountClassInstance,
     resumeMountClassInstance: resumeMountClassInstance,
@@ -6563,7 +6649,7 @@ var ReactFiberClassComponent = function(
   };
 };
 
-var getCurrentFiberStackAddendum$1 =
+var getCurrentFiberStackAddendum$2 =
   ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
 
 var didWarnAboutMaps = void 0;
@@ -6602,7 +6688,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
       '"key" prop. See https://fb.me/react-warning-keys for ' +
       "more information." +
-      (getCurrentFiberStackAddendum$1() || "");
+      (getCurrentFiberStackAddendum$2() || "");
     if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
       return;
     }
@@ -6613,7 +6699,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
         '"key" prop. See https://fb.me/react-warning-keys for ' +
         "more information.%s",
-      getCurrentFiberStackAddendum$1()
+      getCurrentFiberStackAddendum$2()
     );
   };
 }
@@ -6710,7 +6796,7 @@ function throwOnInvalidObjectType(returnFiber, newChild) {
       addendum =
         " If you meant to render a collection of children, use an array " +
         "instead." +
-        (getCurrentFiberStackAddendum$1() || "");
+        (getCurrentFiberStackAddendum$2() || "");
     }
     invariant(
       false,
@@ -6728,7 +6814,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
     "you return a Component instead of <Component /> from render. " +
     "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$1() || "");
+    (getCurrentFiberStackAddendum$2() || "");
 
   if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
     return;
@@ -6740,7 +6826,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
       "you return a Component instead of <Component /> from render. " +
       "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$1() || ""
+    getCurrentFiberStackAddendum$2() || ""
   );
 }
 
@@ -6853,12 +6939,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, textContent, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -6868,7 +6954,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // Move based on index
       var existing = useFiber(current, element.props, expirationTime);
       existing.ref = coerceRef(returnFiber, current, element);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       {
         existing._debugSource = element._source;
         existing._debugOwner = element._owner;
@@ -6882,7 +6968,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       created.ref = coerceRef(returnFiber, current, element);
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     }
   }
@@ -6900,12 +6986,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, portal.children || [], expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -6919,12 +7005,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         key
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, fragment, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -6939,7 +7025,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     }
 
@@ -6952,7 +7038,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           _created.ref = coerceRef(returnFiber, null, newChild);
-          _created["return"] = returnFiber;
+          _created.return = returnFiber;
           return _created;
         }
         case REACT_PORTAL_TYPE: {
@@ -6961,7 +7047,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             returnFiber.mode,
             expirationTime
           );
-          _created2["return"] = returnFiber;
+          _created2.return = returnFiber;
           return _created2;
         }
       }
@@ -6973,7 +7059,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           null
         );
-        _created3["return"] = returnFiber;
+        _created3.return = returnFiber;
         return _created3;
       }
 
@@ -7184,7 +7270,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               "duplicated and/or omitted — the behavior is unsupported and " +
               "could change in a future version.%s",
             key,
-            getCurrentFiberStackAddendum$1()
+            getCurrentFiberStackAddendum$2()
           );
           break;
         default:
@@ -7329,7 +7415,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren["delete"](
+            existingChildren.delete(
               _newFiber2.key === null ? newIdx : _newFiber2.key
             );
           }
@@ -7382,7 +7468,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                 "Using Maps as children is unsupported and will likely yield " +
                   "unexpected results. Convert it to a sequence/iterable of keyed " +
                   "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$1()
+                getCurrentFiberStackAddendum$2()
               )
             : void 0;
           didWarnAboutMaps = true;
@@ -7508,7 +7594,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren["delete"](
+            existingChildren.delete(
               _newFiber4.key === null ? newIdx : _newFiber4.key
             );
           }
@@ -7547,7 +7633,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // the rest.
       deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
       var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
     // The existing first child is not a text node so we need to create one
@@ -7558,7 +7644,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created["return"] = returnFiber;
+    created.return = returnFiber;
     return created;
   }
 
@@ -7588,7 +7674,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           existing.ref = coerceRef(returnFiber, child, element);
-          existing["return"] = returnFiber;
+          existing.return = returnFiber;
           {
             existing._debugSource = element._source;
             existing._debugOwner = element._owner;
@@ -7611,7 +7697,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         element.key
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       var _created4 = createFiberFromElement(
@@ -7620,7 +7706,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4["return"] = returnFiber;
+      _created4.return = returnFiber;
       return _created4;
     }
   }
@@ -7644,7 +7730,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         ) {
           deleteRemainingChildren(returnFiber, child.sibling);
           var existing = useFiber(child, portal.children || [], expirationTime);
-          existing["return"] = returnFiber;
+          existing.return = returnFiber;
           return existing;
         } else {
           deleteRemainingChildren(returnFiber, child);
@@ -7661,7 +7747,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created["return"] = returnFiber;
+    created.return = returnFiber;
     return created;
   }
 
@@ -7813,7 +7899,7 @@ function cloneChildFibers(current, workInProgress) {
   );
   workInProgress.child = newChild;
 
-  newChild["return"] = workInProgress;
+  newChild.return = workInProgress;
   while (currentChild.sibling !== null) {
     currentChild = currentChild.sibling;
     newChild = newChild.sibling = createWorkInProgress(
@@ -7821,11 +7907,14 @@ function cloneChildFibers(current, workInProgress) {
       currentChild.pendingProps,
       currentChild.expirationTime
     );
-    newChild["return"] = workInProgress;
+    newChild.return = workInProgress;
   }
   newChild.sibling = null;
 }
 
+var getCurrentFiberStackAddendum =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+
 var didWarnAboutBadClass = void 0;
 var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
 var didWarnAboutStatelessRefs = void 0;
@@ -7869,8 +7958,6 @@ var ReactFiberBeginWork = function(
       memoizeState
     ),
     adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
-    callGetDerivedStateFromProps =
-      _ReactFiberClassCompo.callGetDerivedStateFromProps,
     constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
     mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
     resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
@@ -7922,9 +8009,20 @@ var ReactFiberBeginWork = function(
 
   function updateForwardRef(current, workInProgress) {
     var render = workInProgress.type.render;
-    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
+    var nextProps = workInProgress.pendingProps;
+    var ref = workInProgress.ref;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextProps) {
+      var currentRef = current !== null ? current.ref : null;
+      if (ref === currentRef) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+    }
+    var nextChildren = render(nextProps, ref);
     reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
     return workInProgress.child;
   }
 
@@ -8010,7 +8108,11 @@ var ReactFiberBeginWork = function(
     if (current === null) {
       if (workInProgress.stateNode === null) {
         // In the initial pass we might need to construct the instance.
-        constructClassInstance(workInProgress, workInProgress.pendingProps);
+        constructClassInstance(
+          workInProgress,
+          workInProgress.pendingProps,
+          renderExpirationTime
+        );
         mountClassInstance(workInProgress, renderExpirationTime);
 
         shouldUpdate = true;
@@ -8028,22 +8130,11 @@ var ReactFiberBeginWork = function(
         renderExpirationTime
       );
     }
-
-    // We processed the update queue inside updateClassInstance. It may have
-    // included some errors that were dispatched during the commit phase.
-    // TODO: Refactor class components so this is less awkward.
-    var didCaptureError = false;
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null && updateQueue.capturedValues !== null) {
-      shouldUpdate = true;
-      didCaptureError = true;
-    }
     return finishClassComponent(
       current,
       workInProgress,
       shouldUpdate,
       hasContext,
-      didCaptureError,
       renderExpirationTime
     );
   }
@@ -8053,12 +8144,13 @@ var ReactFiberBeginWork = function(
     workInProgress,
     shouldUpdate,
     hasContext,
-    didCaptureError,
     renderExpirationTime
   ) {
     // Refs should update even if shouldComponentUpdate returns false
     markRef(current, workInProgress);
 
+    var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
+
     if (!shouldUpdate && !didCaptureError) {
       // Context providers should defer to sCU for rendering
       if (hasContext) {
@@ -8154,29 +8246,26 @@ var ReactFiberBeginWork = function(
     pushHostRootContext(workInProgress);
     var updateQueue = workInProgress.updateQueue;
     if (updateQueue !== null) {
+      var nextProps = workInProgress.pendingProps;
       var prevState = workInProgress.memoizedState;
-      var state = processUpdateQueue(
-        current,
+      var prevChildren = prevState !== null ? prevState.element : null;
+      processUpdateQueue(
         workInProgress,
         updateQueue,
-        null,
+        nextProps,
         null,
         renderExpirationTime
       );
-      memoizeState(workInProgress, state);
-      updateQueue = workInProgress.updateQueue;
+      var nextState = workInProgress.memoizedState;
+      // Caution: React DevTools currently depends on this property
+      // being called "element".
+      var nextChildren = nextState.element;
 
-      var element = void 0;
-      if (updateQueue !== null && updateQueue.capturedValues !== null) {
-        // There's an uncaught error. Unmount the whole root.
-        element = null;
-      } else if (prevState === state) {
+      if (nextChildren === prevChildren) {
         // If the state is the same as before, that's a bailout because we had
         // no work that expires at this time.
         resetHydrationState();
         return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      } else {
-        element = state.element;
       }
       var root = workInProgress.stateNode;
       if (
@@ -8201,16 +8290,15 @@ var ReactFiberBeginWork = function(
         workInProgress.child = mountChildFibers(
           workInProgress,
           null,
-          element,
+          nextChildren,
           renderExpirationTime
         );
       } else {
         // Otherwise reset hydration state in case we aborted and resumed another
         // root.
         resetHydrationState();
-        reconcileChildren(current, workInProgress, element);
+        reconcileChildren(current, workInProgress, nextChildren);
       }
-      memoizeState(workInProgress, state);
       return workInProgress.child;
     }
     resetHydrationState();
@@ -8346,21 +8434,13 @@ var ReactFiberBeginWork = function(
       workInProgress.memoizedState =
         value.state !== null && value.state !== undefined ? value.state : null;
 
-      if (typeof Component.getDerivedStateFromProps === "function") {
-        var partialState = callGetDerivedStateFromProps(
+      var getDerivedStateFromProps = Component.getDerivedStateFromProps;
+      if (typeof getDerivedStateFromProps === "function") {
+        applyDerivedStateFromProps(
           workInProgress,
-          value,
-          props,
-          workInProgress.memoizedState
+          getDerivedStateFromProps,
+          props
         );
-
-        if (partialState !== null && partialState !== undefined) {
-          workInProgress.memoizedState = Object.assign(
-            {},
-            workInProgress.memoizedState,
-            partialState
-          );
-        }
       }
 
       // Push context providers early to prevent context stack mismatches.
@@ -8374,7 +8454,6 @@ var ReactFiberBeginWork = function(
         workInProgress,
         true,
         hasContext,
-        false,
         renderExpirationTime
       );
     } else {
@@ -8520,7 +8599,7 @@ var ReactFiberBeginWork = function(
     var fiber = workInProgress.child;
     if (fiber !== null) {
       // Set the return pointer of the child to the work-in-progress fiber.
-      fiber["return"] = workInProgress;
+      fiber.return = workInProgress;
     }
     while (fiber !== null) {
       var nextFiber = void 0;
@@ -8558,7 +8637,7 @@ var ReactFiberBeginWork = function(
                 // ancestor path already has sufficient priority.
                 break;
               }
-              node = node["return"];
+              node = node.return;
             }
             // Don't scan deeper than a matching consumer. When we render the
             // consumer, we'll continue scanning from that point. This way the
@@ -8580,7 +8659,7 @@ var ReactFiberBeginWork = function(
       }
       if (nextFiber !== null) {
         // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber["return"] = fiber;
+        nextFiber.return = fiber;
       } else {
         // No child. Traverse to next sibling.
         nextFiber = fiber;
@@ -8592,11 +8671,13 @@ var ReactFiberBeginWork = function(
           }
           var sibling = nextFiber.sibling;
           if (sibling !== null) {
+            // Set the return pointer of the sibling to the work-in-progress fiber.
+            sibling.return = nextFiber.return;
             nextFiber = sibling;
             break;
           }
           // No more siblings. Traverse up.
-          nextFiber = nextFiber["return"];
+          nextFiber = nextFiber.return;
         }
       }
       fiber = nextFiber;
@@ -8613,8 +8694,10 @@ var ReactFiberBeginWork = function(
 
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
+    var canBailOnProps = true;
 
     if (hasLegacyContextChanged()) {
+      canBailOnProps = false;
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (oldProps === newProps) {
@@ -8626,6 +8709,20 @@ var ReactFiberBeginWork = function(
     var newValue = newProps.value;
     workInProgress.memoizedProps = newProps;
 
+    {
+      var providerPropTypes = workInProgress.type.propTypes;
+
+      if (providerPropTypes) {
+        checkPropTypes(
+          providerPropTypes,
+          newProps,
+          "prop",
+          "Context.Provider",
+          getCurrentFiberStackAddendum
+        );
+      }
+    }
+
     var changedBits = void 0;
     if (oldProps === null) {
       // Initial render
@@ -8633,7 +8730,7 @@ var ReactFiberBeginWork = function(
     } else {
       if (oldProps.value === newProps.value) {
         // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children) {
+        if (oldProps.children === newProps.children && canBailOnProps) {
           workInProgress.stateNode = 0;
           pushProvider(workInProgress);
           return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8650,7 +8747,7 @@ var ReactFiberBeginWork = function(
           (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
         ) {
           // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children) {
+          if (oldProps.children === newProps.children && canBailOnProps) {
             workInProgress.stateNode = 0;
             pushProvider(workInProgress);
             return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8675,7 +8772,7 @@ var ReactFiberBeginWork = function(
 
           if (changedBits === 0) {
             // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children) {
+            if (oldProps.children === newProps.children && canBailOnProps) {
               workInProgress.stateNode = 0;
               pushProvider(workInProgress);
               return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8761,6 +8858,8 @@ var ReactFiberBeginWork = function(
     }
 
     var newChildren = render(newValue);
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
     reconcileChildren(current, workInProgress, newChildren);
     return workInProgress.child;
   }
@@ -8968,7 +9067,7 @@ var ReactFiberCompleteWork = function(
   function appendAllReturns(returns, workInProgress) {
     var node = workInProgress.stateNode;
     if (node) {
-      node["return"] = workInProgress;
+      node.return = workInProgress;
     }
     while (node !== null) {
       if (
@@ -8980,17 +9079,17 @@ var ReactFiberCompleteWork = function(
       } else if (node.tag === ReturnComponent) {
         returns.push(node.pendingProps.value);
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -9046,7 +9145,7 @@ var ReactFiberCompleteWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -9054,12 +9153,12 @@ var ReactFiberCompleteWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -9126,7 +9225,7 @@ var ReactFiberCompleteWork = function(
             // down its children. Instead, we'll get insertions from each child in
             // the portal directly.
           } else if (node.child !== null) {
-            node.child["return"] = node;
+            node.child.return = node;
             node = node.child;
             continue;
           }
@@ -9134,12 +9233,12 @@ var ReactFiberCompleteWork = function(
             return;
           }
           while (node.sibling === null) {
-            if (node["return"] === null || node["return"] === workInProgress) {
+            if (node.return === null || node.return === workInProgress) {
               return;
             }
-            node = node["return"];
+            node = node.return;
           }
-          node.sibling["return"] = node["return"];
+          node.sibling.return = node.return;
           node = node.sibling;
         }
       };
@@ -9265,20 +9364,6 @@ var ReactFiberCompleteWork = function(
       case ClassComponent: {
         // We are leaving this subtree, so pop context if any.
         popLegacyContextProvider(workInProgress);
-
-        // If this component caught an error, schedule an error log effect.
-        var instance = workInProgress.stateNode;
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null && updateQueue.capturedValues !== null) {
-          workInProgress.effectTag &= ~DidCapture;
-          if (typeof instance.componentDidCatch === "function") {
-            workInProgress.effectTag |= ErrLog;
-          } else {
-            // Normally we clear this in the commit phase, but since we did not
-            // schedule an effect, we need to reset it here.
-            updateQueue.capturedValues = null;
-          }
-        }
         return null;
       }
       case HostRoot: {
@@ -9298,11 +9383,6 @@ var ReactFiberCompleteWork = function(
           workInProgress.effectTag &= ~Placement;
         }
         updateHostContainer(workInProgress);
-
-        var _updateQueue = workInProgress.updateQueue;
-        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
-          workInProgress.effectTag |= ErrLog;
-        }
         return null;
       }
       case HostComponent: {
@@ -9317,13 +9397,13 @@ var ReactFiberCompleteWork = function(
           // have newProps so we'll have to reuse them.
           // TODO: Split the update API as separate for the props vs. children.
           // Even better would be if children weren't special cased at all tho.
-          var _instance = workInProgress.stateNode;
+          var instance = workInProgress.stateNode;
           var currentHostContext = getHostContext();
           // TODO: Experiencing an error where oldProps is null. Suggests a host
           // component is hitting the resume path. Figure out why. Possibly
           // related to `hidden`.
           var updatePayload = prepareUpdate(
-            _instance,
+            instance,
             type,
             oldProps,
             newProps,
@@ -9377,7 +9457,7 @@ var ReactFiberCompleteWork = function(
               markUpdate(workInProgress);
             }
           } else {
-            var _instance2 = createInstance(
+            var _instance = createInstance(
               type,
               newProps,
               rootContainerInstance,
@@ -9385,14 +9465,14 @@ var ReactFiberCompleteWork = function(
               workInProgress
             );
 
-            appendAllChildren(_instance2, workInProgress);
+            appendAllChildren(_instance, workInProgress);
 
             // Certain renderers require commit-time effects for initial mount.
             // (eg DOM renderer supports auto-focus for certain elements).
             // Make sure such renderers get scheduled for later work.
             if (
               finalizeInitialChildren(
-                _instance2,
+                _instance,
                 type,
                 newProps,
                 rootContainerInstance,
@@ -9401,7 +9481,7 @@ var ReactFiberCompleteWork = function(
             ) {
               markUpdate(workInProgress);
             }
-            workInProgress.stateNode = _instance2;
+            workInProgress.stateNode = _instance;
           }
 
           if (workInProgress.ref !== null) {
@@ -9508,139 +9588,6 @@ function createCapturedValue(value, source) {
   };
 }
 
-var ReactFiberUnwindWork = function(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-
-  function throwException(returnFiber, sourceFiber, rawValue) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-
-    var value = createCapturedValue(rawValue, sourceFiber);
-
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          // Uncaught error
-          var errorInfo = value;
-          ensureUpdateQueues(workInProgress);
-          var updateQueue = workInProgress.updateQueue;
-          updateQueue.capturedValues = [errorInfo];
-          workInProgress.effectTag |= ShouldCapture;
-          return;
-        }
-        case ClassComponent:
-          // Capture and retry
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
-          if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            ensureUpdateQueues(workInProgress);
-            var _updateQueue = workInProgress.updateQueue;
-            var capturedValues = _updateQueue.capturedValues;
-            if (capturedValues === null) {
-              _updateQueue.capturedValues = [value];
-            } else {
-              capturedValues.push(value);
-            }
-            workInProgress.effectTag |= ShouldCapture;
-            return;
-          }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress["return"];
-    } while (workInProgress !== null);
-  }
-
-  function unwindWork(workInProgress) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
-    }
-  }
-
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      default:
-        break;
-    }
-  }
-
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork
-  };
-};
-
 // This module is forked in different environments.
 // By default, return `true` to log errors to the console.
 // Forks can return `false` if this isn't desirable.
@@ -9892,7 +9839,14 @@ var ReactFiberCommitWork = function(
         }
         var updateQueue = finishedWork.updateQueue;
         if (updateQueue !== null) {
-          commitCallbacks(updateQueue, _instance2);
+          _instance2.props = finishedWork.memoizedProps;
+          _instance2.state = finishedWork.memoizedState;
+          commitUpdateQueue(
+            finishedWork,
+            updateQueue,
+            _instance2,
+            committedExpirationTime
+          );
         }
         return;
       }
@@ -9910,7 +9864,12 @@ var ReactFiberCommitWork = function(
                 break;
             }
           }
-          commitCallbacks(_updateQueue, _instance3);
+          commitUpdateQueue(
+            finishedWork,
+            _updateQueue,
+            _instance3,
+            committedExpirationTime
+          );
         }
         return;
       }
@@ -9947,81 +9906,17 @@ var ReactFiberCommitWork = function(
     }
   }
 
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case ClassComponent:
-        {
-          var ctor = finishedWork.type;
-          var _instance5 = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            updateQueue !== null && updateQueue.capturedValues !== null,
-            "An error logging effect should not have been scheduled if no errors " +
-              "were captured. This error is likely caused by a bug in React. " +
-              "Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-
-          if (typeof ctor.getDerivedStateFromCatch !== "function") {
-            // To preserve the preexisting retry behavior of error boundaries,
-            // we keep track of which ones already failed during this batch.
-            // This gets reset before we yield back to the browser.
-            // TODO: Warn in strict mode if getDerivedStateFromCatch is
-            // not defined.
-            markLegacyErrorBoundaryAsFailed(_instance5);
-          }
-
-          _instance5.props = finishedWork.memoizedProps;
-          _instance5.state = finishedWork.memoizedState;
-          for (var i = 0; i < capturedErrors.length; i++) {
-            var errorInfo = capturedErrors[i];
-            var _error = errorInfo.value;
-            var stack = errorInfo.stack;
-            logError(finishedWork, errorInfo);
-            _instance5.componentDidCatch(_error, {
-              componentStack: stack !== null ? stack : ""
-            });
-          }
-        }
-        break;
-      case HostRoot: {
-        var _updateQueue2 = finishedWork.updateQueue;
-        invariant(
-          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
-          "An error logging effect should not have been scheduled if no errors " +
-            "were captured. This error is likely caused by a bug in React. " +
-            "Please file an issue."
-        );
-        var _capturedErrors = _updateQueue2.capturedValues;
-        _updateQueue2.capturedValues = null;
-        for (var _i = 0; _i < _capturedErrors.length; _i++) {
-          var _errorInfo = _capturedErrors[_i];
-          logError(finishedWork, _errorInfo);
-          onUncaughtError(_errorInfo.value);
-        }
-        break;
-      }
-      default:
-        invariant(
-          false,
-          "This unit of work tag cannot capture errors.  This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (ref !== null) {
-      var _instance6 = finishedWork.stateNode;
+      var _instance5 = finishedWork.stateNode;
       var instanceToUse = void 0;
       switch (finishedWork.tag) {
         case HostComponent:
-          instanceToUse = getPublicInstance(_instance6);
+          instanceToUse = getPublicInstance(_instance5);
           break;
         default:
-          instanceToUse = _instance6;
+          instanceToUse = _instance5;
       }
       if (typeof ref === "function") {
         ref(instanceToUse);
@@ -10065,9 +9960,9 @@ var ReactFiberCommitWork = function(
     switch (current.tag) {
       case ClassComponent: {
         safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if (typeof _instance7.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance7);
+        var _instance6 = current.stateNode;
+        if (typeof _instance6.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance6);
         }
         return;
       }
@@ -10109,7 +10004,7 @@ var ReactFiberCommitWork = function(
         // If we don't use mutation we drill down into portals here instead.
         (!mutation || node.tag !== HostPortal)
       ) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -10117,12 +10012,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === root) {
+        if (node.return === null || node.return === root) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10133,11 +10028,11 @@ var ReactFiberCommitWork = function(
     // get GC:ed but we don't know which for sure which parent is the current
     // one so we'll settle for GC:ing the subtree of this child. This child
     // itself will be GC:ed when the parent updates the next time.
-    current["return"] = null;
+    current.return = null;
     current.child = null;
     if (current.alternate) {
       current.alternate.child = null;
-      current.alternate["return"] = null;
+      current.alternate.return = null;
     }
   }
 
@@ -10205,7 +10100,6 @@ var ReactFiberCommitWork = function(
 
         commitLifeCycles: commitLifeCycles,
         commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-        commitErrorLogging: commitErrorLogging,
         commitAttachRef: commitAttachRef,
         commitDetachRef: commitDetachRef
       };
@@ -10227,12 +10121,12 @@ var ReactFiberCommitWork = function(
     removeChildFromContainer = mutation.removeChildFromContainer;
 
   function getHostParentFiber(fiber) {
-    var parent = fiber["return"];
+    var parent = fiber.return;
     while (parent !== null) {
       if (isHostParent(parent)) {
         return parent;
       }
-      parent = parent["return"];
+      parent = parent.return;
     }
     invariant(
       false,
@@ -10257,14 +10151,14 @@ var ReactFiberCommitWork = function(
     siblings: while (true) {
       // If we didn't find anything, let's try the next sibling.
       while (node.sibling === null) {
-        if (node["return"] === null || isHostParent(node["return"])) {
+        if (node.return === null || isHostParent(node.return)) {
           // If we pop out of the root or hit the parent the fiber we are the
           // last sibling.
           return null;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
       while (node.tag !== HostComponent && node.tag !== HostText) {
         // If it is not host node and, we might have a host node inside it.
@@ -10278,7 +10172,7 @@ var ReactFiberCommitWork = function(
         if (node.child === null || node.tag === HostPortal) {
           continue siblings;
         } else {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
         }
       }
@@ -10346,7 +10240,7 @@ var ReactFiberCommitWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -10354,12 +10248,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === finishedWork) {
+        if (node.return === null || node.return === finishedWork) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10376,7 +10270,7 @@ var ReactFiberCommitWork = function(
 
     while (true) {
       if (!currentParentIsValid) {
-        var parent = node["return"];
+        var parent = node.return;
         findParent: while (true) {
           invariant(
             parent !== null,
@@ -10397,7 +10291,7 @@ var ReactFiberCommitWork = function(
               currentParentIsContainer = true;
               break findParent;
           }
-          parent = parent["return"];
+          parent = parent.return;
         }
         currentParentIsValid = true;
       }
@@ -10418,7 +10312,7 @@ var ReactFiberCommitWork = function(
         currentParent = node.stateNode.containerInfo;
         // Visit children because portals might contain host components.
         if (node.child !== null) {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
           continue;
         }
@@ -10426,7 +10320,7 @@ var ReactFiberCommitWork = function(
         commitUnmount(node);
         // Visit children because we may find more host components below.
         if (node.child !== null) {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
           continue;
         }
@@ -10435,17 +10329,17 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === current) {
+        if (node.return === null || node.return === current) {
           return;
         }
-        node = node["return"];
+        node = node.return;
         if (node.tag === HostPortal) {
           // When we go out of the portal, we need to restore the parent.
           // Since we don't keep a stack of them, we will search for it.
           currentParentIsValid = false;
         }
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10463,8 +10357,8 @@ var ReactFiberCommitWork = function(
         return;
       }
       case HostComponent: {
-        var _instance8 = finishedWork.stateNode;
-        if (_instance8 != null) {
+        var _instance7 = finishedWork.stateNode;
+        if (_instance7 != null) {
           // Commit the work prepared earlier.
           var newProps = finishedWork.memoizedProps;
           // For hydration we reuse the update path but we treat the oldProps
@@ -10477,7 +10371,7 @@ var ReactFiberCommitWork = function(
           finishedWork.updateQueue = null;
           if (updatePayload !== null) {
             commitUpdate(
-              _instance8,
+              _instance7,
               updatePayload,
               type,
               oldProps,
@@ -10528,7 +10422,6 @@ var ReactFiberCommitWork = function(
       commitDeletion: commitDeletion,
       commitWork: commitWork,
       commitLifeCycles: commitLifeCycles,
-      commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
     };
@@ -10537,6 +10430,208 @@ var ReactFiberCommitWork = function(
   }
 };
 
+var ReactFiberUnwindWork = function(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  markLegacyErrorBoundaryAsFailed,
+  isAlreadyFailedLegacyErrorBoundary,
+  onUncaughtError
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+
+  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+    var update = createUpdate(expirationTime);
+    // Unmount the root by rendering null.
+    update.tag = CaptureUpdate;
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    update.payload = { element: null };
+    var error = errorInfo.value;
+    update.callback = function() {
+      onUncaughtError(error);
+      logError(fiber, errorInfo);
+    };
+    return update;
+  }
+
+  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+    var update = createUpdate(expirationTime);
+    update.tag = CaptureUpdate;
+    var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
+    if (
+      enableGetDerivedStateFromCatch &&
+      typeof getDerivedStateFromCatch === "function"
+    ) {
+      var _error = errorInfo.value;
+      update.payload = function() {
+        return getDerivedStateFromCatch(_error);
+      };
+    }
+
+    var inst = fiber.stateNode;
+    if (inst !== null && typeof inst.componentDidCatch === "function") {
+      update.callback = function callback() {
+        if (
+          !enableGetDerivedStateFromCatch ||
+          getDerivedStateFromCatch !== "function"
+        ) {
+          // To preserve the preexisting retry behavior of error boundaries,
+          // we keep track of which ones already failed during this batch.
+          // This gets reset before we yield back to the browser.
+          // TODO: Warn in strict mode if getDerivedStateFromCatch is
+          // not defined.
+          markLegacyErrorBoundaryAsFailed(this);
+        }
+        var error = errorInfo.value;
+        var stack = errorInfo.stack;
+        logError(fiber, errorInfo);
+        this.componentDidCatch(error, {
+          componentStack: stack !== null ? stack : ""
+        });
+      };
+    }
+    return update;
+  }
+
+  function throwException(
+    returnFiber,
+    sourceFiber,
+    rawValue,
+    renderExpirationTime
+  ) {
+    // The source fiber did not complete.
+    sourceFiber.effectTag |= Incomplete;
+    // Its effect list is no longer valid.
+    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+
+    var value = createCapturedValue(rawValue, sourceFiber);
+
+    var workInProgress = returnFiber;
+    do {
+      switch (workInProgress.tag) {
+        case HostRoot: {
+          var _errorInfo = value;
+          workInProgress.effectTag |= ShouldCapture;
+          var update = createRootErrorUpdate(
+            workInProgress,
+            _errorInfo,
+            renderExpirationTime
+          );
+          enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
+          return;
+        }
+        case ClassComponent:
+          // Capture and retry
+          var errorInfo = value;
+          var ctor = workInProgress.type;
+          var _instance = workInProgress.stateNode;
+          if (
+            (workInProgress.effectTag & DidCapture) === NoEffect &&
+            ((typeof ctor.getDerivedStateFromCatch === "function" &&
+              enableGetDerivedStateFromCatch) ||
+              (_instance !== null &&
+                typeof _instance.componentDidCatch === "function" &&
+                !isAlreadyFailedLegacyErrorBoundary(_instance)))
+          ) {
+            workInProgress.effectTag |= ShouldCapture;
+            // Schedule the error boundary to re-render using updated state
+            var _update = createClassErrorUpdate(
+              workInProgress,
+              errorInfo,
+              renderExpirationTime
+            );
+            enqueueCapturedUpdate(
+              workInProgress,
+              _update,
+              renderExpirationTime
+            );
+            return;
+          }
+          break;
+        default:
+          break;
+      }
+      workInProgress = workInProgress.return;
+    } while (workInProgress !== null);
+  }
+
+  function unwindWork(workInProgress) {
+    switch (workInProgress.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(workInProgress);
+        var effectTag = workInProgress.effectTag;
+        if (effectTag & ShouldCapture) {
+          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var _effectTag = workInProgress.effectTag;
+        if (_effectTag & ShouldCapture) {
+          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        return null;
+      }
+      case HostPortal:
+        popHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        popProvider(workInProgress);
+        return null;
+      default:
+        return null;
+    }
+  }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      default:
+        break;
+    }
+  }
+
+  return {
+    throwException: throwException,
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork,
+    createRootErrorUpdate: createRootErrorUpdate,
+    createClassErrorUpdate: createClassErrorUpdate
+  };
+};
+
 var NO_CONTEXT = {};
 
 var ReactFiberHostContext = function(config, stack) {
@@ -10721,7 +10816,7 @@ var ReactFiberHydrationContext = function(config) {
 
     var childToDelete = createFiberFromHostInstanceForDeletion();
     childToDelete.stateNode = instance;
-    childToDelete["return"] = returnFiber;
+    childToDelete.return = returnFiber;
     childToDelete.effectTag = Deletion;
 
     // This might seem like it belongs on progressedFirstDeletion. However,
@@ -10919,13 +11014,13 @@ var ReactFiberHydrationContext = function(config) {
   }
 
   function popToNextHostParent(fiber) {
-    var parent = fiber["return"];
+    var parent = fiber.return;
     while (
       parent !== null &&
       parent.tag !== HostComponent &&
       parent.tag !== HostRoot
     ) {
-      parent = parent["return"];
+      parent = parent.return;
     }
     hydrationParentFiber = parent;
   }
@@ -11247,7 +11342,7 @@ var ReactFiberLegacyContext = function(stack) {
       if (isContextProvider(node)) {
         return node.stateNode.__reactInternalMemoizedMergedChildContext;
       }
-      var parent = node["return"];
+      var parent = node.return;
       invariant(
         parent,
         "Found unexpected detached subtree parent. " +
@@ -11520,11 +11615,15 @@ var ReactFiberScheduler = function(config) {
       legacyContext,
       newContext,
       scheduleWork,
-      isAlreadyFailedLegacyErrorBoundary
+      markLegacyErrorBoundaryAsFailed,
+      isAlreadyFailedLegacyErrorBoundary,
+      onUncaughtError
     ),
     throwException = _ReactFiberUnwindWork.throwException,
     unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork,
+    createRootErrorUpdate = _ReactFiberUnwindWork.createRootErrorUpdate,
+    createClassErrorUpdate = _ReactFiberUnwindWork.createClassErrorUpdate;
 
   var _ReactFiberCommitWork = ReactFiberCommitWork(
       config,
@@ -11541,7 +11640,6 @@ var ReactFiberScheduler = function(config) {
     commitDeletion = _ReactFiberCommitWork.commitDeletion,
     commitWork = _ReactFiberCommitWork.commitWork,
     commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
-    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
     commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
     commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
 
@@ -11639,10 +11737,10 @@ var ReactFiberScheduler = function(config) {
 
   function resetStack() {
     if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork["return"];
+      var interruptedWork = nextUnitOfWork.return;
       while (interruptedWork !== null) {
         unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork["return"];
+        interruptedWork = interruptedWork.return;
       }
     }
 
@@ -11767,10 +11865,6 @@ var ReactFiberScheduler = function(config) {
         );
       }
 
-      if (effectTag & ErrLog) {
-        commitErrorLogging(nextEffect, onUncaughtError);
-      }
-
       if (effectTag & Ref) {
         recordEffect();
         commitAttachRef(nextEffect);
@@ -11977,7 +12071,16 @@ var ReactFiberScheduler = function(config) {
     }
 
     // Check for pending updates.
-    var newExpirationTime = getUpdateExpirationTime(workInProgress);
+    var newExpirationTime = NoWork;
+    switch (workInProgress.tag) {
+      case HostRoot:
+      case ClassComponent: {
+        var updateQueue = workInProgress.updateQueue;
+        if (updateQueue !== null) {
+          newExpirationTime = updateQueue.expirationTime;
+        }
+      }
+    }
 
     // TODO: Calls need to visit stateNode
 
@@ -12010,7 +12113,7 @@ var ReactFiberScheduler = function(config) {
         ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
       }
 
-      var returnFiber = workInProgress["return"];
+      var returnFiber = workInProgress.return;
       var siblingFiber = workInProgress.sibling;
 
       if ((workInProgress.effectTag & Incomplete) === NoEffect) {
@@ -12252,13 +12355,19 @@ var ReactFiberScheduler = function(config) {
           break;
         }
 
+        {
+          // Reset global debug state
+          // We assume this is defined in DEV
+          resetCurrentlyProcessingQueue();
+        }
+
         if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
           replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
         }
 
         var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber["return"];
+        var returnFiber = sourceFiber.return;
         if (returnFiber === null) {
           // This is the root. The root could capture its own errors. However,
           // we don't know if it errors before or after we pushed the host
@@ -12270,7 +12379,12 @@ var ReactFiberScheduler = function(config) {
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(returnFiber, sourceFiber, thrownValue);
+        throwException(
+          returnFiber,
+          sourceFiber,
+          thrownValue,
+          nextRenderExpirationTime
+        );
         nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
       break;
@@ -12318,31 +12432,13 @@ var ReactFiberScheduler = function(config) {
     }
   }
 
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    // TODO: We only support dispatching errors.
-    var capturedValue = createCapturedValue(value, sourceFiber);
-    var update = {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: false,
-      isForced: false,
-      capturedValue: capturedValue,
-      next: null
-    };
-    insertUpdateIntoFiber(boundaryFiber, update);
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-
   function dispatch(sourceFiber, value, expirationTime) {
     invariant(
       !isWorking || isCommitting,
       "dispatch: Cannot dispatch during the render phase."
     );
 
-    // TODO: Handle arrays
-
-    var fiber = sourceFiber["return"];
+    var fiber = sourceFiber.return;
     while (fiber !== null) {
       switch (fiber.tag) {
         case ClassComponent:
@@ -12353,22 +12449,44 @@ var ReactFiberScheduler = function(config) {
             (typeof instance.componentDidCatch === "function" &&
               !isAlreadyFailedLegacyErrorBoundary(instance))
           ) {
-            scheduleCapture(sourceFiber, fiber, value, expirationTime);
+            var errorInfo = createCapturedValue(value, sourceFiber);
+            var update = createClassErrorUpdate(
+              fiber,
+              errorInfo,
+              expirationTime
+            );
+            enqueueUpdate(fiber, update, expirationTime);
+            scheduleWork(fiber, expirationTime);
             return;
           }
           break;
-        // TODO: Handle async boundaries
-        case HostRoot:
-          scheduleCapture(sourceFiber, fiber, value, expirationTime);
+        case HostRoot: {
+          var _errorInfo = createCapturedValue(value, sourceFiber);
+          var _update = createRootErrorUpdate(
+            fiber,
+            _errorInfo,
+            expirationTime
+          );
+          enqueueUpdate(fiber, _update, expirationTime);
+          scheduleWork(fiber, expirationTime);
           return;
+        }
       }
-      fiber = fiber["return"];
+      fiber = fiber.return;
     }
 
     if (sourceFiber.tag === HostRoot) {
       // Error was thrown at the root. There is no parent, so the root
       // itself should capture it.
-      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
+      var rootFiber = sourceFiber;
+      var _errorInfo2 = createCapturedValue(value, rootFiber);
+      var _update2 = createRootErrorUpdate(
+        rootFiber,
+        _errorInfo2,
+        expirationTime
+      );
+      enqueueUpdate(rootFiber, _update2, expirationTime);
+      scheduleWork(rootFiber, expirationTime);
     }
   }
 
@@ -12496,7 +12614,7 @@ var ReactFiberScheduler = function(config) {
           node.alternate.expirationTime = expirationTime;
         }
       }
-      if (node["return"] === null) {
+      if (node.return === null) {
         if (node.tag === HostRoot) {
           var root = node.stateNode;
           if (
@@ -12537,7 +12655,7 @@ var ReactFiberScheduler = function(config) {
           return;
         }
       }
-      node = node["return"];
+      node = node.return;
     }
   }
 
@@ -13166,9 +13284,14 @@ var ReactFiberReconciler$1 = function(config) {
       }
     }
 
+    var update = createUpdate(expirationTime);
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    update.payload = { element: element };
+
     callback = callback === undefined ? null : callback;
-    {
-      !(callback === null || typeof callback === "function")
+    if (callback !== null) {
+      !(typeof callback === "function")
         ? warning(
             false,
             "render(...): Expected the last optional `callback` argument to be a " +
@@ -13176,20 +13299,11 @@ var ReactFiberReconciler$1 = function(config) {
             callback
           )
         : void 0;
+      update.callback = callback;
     }
+    enqueueUpdate(current, update, expirationTime);
 
-    var update = {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: callback,
-      isReplace: false,
-      isForced: false,
-      capturedValue: null,
-      next: null
-    };
-    insertUpdateIntoFiber(current, update);
     scheduleWork(current, expirationTime);
-
     return expirationTime;
   }
 
@@ -13367,8 +13481,8 @@ var ReactFiberReconciler$3 =
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3["default"]
-  ? ReactFiberReconciler$3["default"]
+var reactReconciler = ReactFiberReconciler$3.default
+  ? ReactFiberReconciler$3.default
   : ReactFiberReconciler$3;
 
 function _classCallCheck$1(instance, Constructor) {
@@ -13795,7 +13909,7 @@ var ReactFabric = {
     if (root) {
       // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
       ReactFabricRenderer.updateContainer(null, root, null, function() {
-        roots["delete"](containerTag);
+        roots.delete(containerTag);
       });
     }
   },
@@ -13852,9 +13966,7 @@ var ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var fabric = ReactFabric$3["default"]
-  ? ReactFabric$3["default"]
-  : ReactFabric$3;
+var fabric = ReactFabric$3.default ? ReactFabric$3.default : ReactFabric$3;
 
 module.exports = fabric;
 
diff --git a/Libraries/Renderer/oss/ReactFabric-prod.js b/Libraries/Renderer/oss/ReactFabric-prod.js
index 19ca0dde9e33..32b02cc83875 100644
--- a/Libraries/Renderer/oss/ReactFabric-prod.js
+++ b/Libraries/Renderer/oss/ReactFabric-prod.js
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
+ * @providesModule ReactFabric-prod
  * @preventMunge
  */
 
@@ -210,7 +211,7 @@ function getListener(inst, registrationName) {
   return listener;
 }
 function getParent(inst) {
-  do inst = inst["return"];
+  do inst = inst.return;
   while (inst && 5 !== inst.tag);
   return inst ? inst : null;
 }
@@ -917,21 +918,17 @@ injection.injectEventPluginsByName({
   ResponderEventPlugin: ResponderEventPlugin,
   ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
 });
-var hasSymbol = "function" === typeof Symbol && Symbol["for"],
-  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
-  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
-  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
-  REACT_STRICT_MODE_TYPE = hasSymbol
-    ? Symbol["for"]("react.strict_mode")
-    : 60108,
-  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
-  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
-  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
-  REACT_FORWARD_REF_TYPE = hasSymbol
-    ? Symbol["for"]("react.forward_ref")
-    : 60112,
+var hasSymbol = "function" === typeof Symbol && Symbol.for,
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
+  REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 60104,
+  REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 60105,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for("react.forward_ref") : 60112,
   MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
 function getIteratorFn(maybeIterable) {
   if (null === maybeIterable || "undefined" === typeof maybeIterable)
@@ -1253,11 +1250,11 @@ function getComponentName(fiber) {
 }
 function isFiberMountedImpl(fiber) {
   var node = fiber;
-  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
+  if (fiber.alternate) for (; node.return; ) node = node.return;
   else {
     if (0 !== (node.effectTag & 2)) return 1;
-    for (; node["return"]; )
-      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
+    for (; node.return; )
+      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
   }
   return 3 === node.tag ? 2 : 3;
 }
@@ -1284,7 +1281,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       1 === alternate ? null : fiber
     );
   for (var a = fiber, b = alternate; ; ) {
-    var parentA = a["return"],
+    var parentA = a.return,
       parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) break;
     if (parentA.child === parentB.child) {
@@ -1295,7 +1292,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       }
       invariant(!1, "Unable to find node on an unmounted component.");
     }
-    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
+    if (a.return !== b.return) (a = parentA), (b = parentB);
     else {
       child = !1;
       for (var _child = parentA.child; _child; ) {
@@ -1348,14 +1345,14 @@ function findCurrentHostFiber(parent) {
   if (!parent) return null;
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child["return"] = node), (node = node.child);
+    if (node.child) (node.child.return = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -1367,14 +1364,14 @@ function findCurrentHostFiberWithNoPortals(parent) {
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
     if (node.child && 4 !== node.tag)
-      (node.child["return"] = node), (node = node.child);
+      (node.child.return = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -1383,8 +1380,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
   this.key = key;
-  this.stateNode = this.type = null;
-  this.sibling = this.child = this["return"] = null;
+  this.sibling = this.child = this.return = this.stateNode = this.type = null;
   this.index = 0;
   this.ref = null;
   this.pendingProps = pendingProps;
@@ -1575,171 +1571,289 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
         JSCompiler_inline_result = "";
     }
     info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
+    workInProgress = workInProgress.return;
   } while (workInProgress);
   return info;
 }
 new Set();
 function createUpdateQueue(baseState) {
   return {
-    baseState: baseState,
     expirationTime: 0,
-    first: null,
-    last: null,
-    callbackList: null,
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null,
+    hasForceUpdate: !1
+  };
+}
+function cloneUpdateQueue(currentQueue) {
+  return {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
     hasForceUpdate: !1,
-    isInitialized: !1,
-    capturedValues: null
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+    tag: 0,
+    payload: null,
+    callback: null,
+    next: null,
+    nextEffect: null
   };
 }
-function insertUpdateIntoQueue(queue, update) {
-  null === queue.last
-    ? (queue.first = queue.last = update)
-    : ((queue.last.next = update), (queue.last = update));
+function appendUpdateToQueue(queue, update, expirationTime) {
+  null === queue.lastUpdate
+    ? (queue.firstUpdate = queue.lastUpdate = update)
+    : ((queue.lastUpdate.next = update), (queue.lastUpdate = update));
+  if (0 === queue.expirationTime || queue.expirationTime > expirationTime)
+    queue.expirationTime = expirationTime;
+}
+function enqueueUpdate(fiber, update, expirationTime) {
+  var alternate = fiber.alternate;
+  if (null === alternate) {
+    var queue1 = fiber.updateQueue;
+    var queue2 = null;
+    null === queue1 &&
+      (queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState));
+  } else
+    (queue1 = fiber.updateQueue),
+      (queue2 = alternate.updateQueue),
+      null === queue1
+        ? null === queue2
+          ? ((queue1 = fiber.updateQueue = createUpdateQueue(
+              fiber.memoizedState
+            )),
+            (queue2 = alternate.updateQueue = createUpdateQueue(
+              alternate.memoizedState
+            )))
+          : (queue1 = fiber.updateQueue = cloneUpdateQueue(queue2))
+        : null === queue2 &&
+          (queue2 = alternate.updateQueue = cloneUpdateQueue(queue1));
+  null === queue2 || queue1 === queue2
+    ? appendUpdateToQueue(queue1, update, expirationTime)
+    : null === queue1.lastUpdate || null === queue2.lastUpdate
+      ? (appendUpdateToQueue(queue1, update, expirationTime),
+        appendUpdateToQueue(queue2, update, expirationTime))
+      : (appendUpdateToQueue(queue1, update, expirationTime),
+        (queue2.lastUpdate = update));
+}
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  var workInProgressQueue = workInProgress.updateQueue;
+  workInProgressQueue =
+    null === workInProgressQueue
+      ? (workInProgress.updateQueue = createUpdateQueue(
+          workInProgress.memoizedState
+        ))
+      : ensureWorkInProgressQueueIsAClone(workInProgress, workInProgressQueue);
+  null === workInProgressQueue.lastCapturedUpdate
+    ? (workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update)
+    : ((workInProgressQueue.lastCapturedUpdate.next = update),
+      (workInProgressQueue.lastCapturedUpdate = update));
   if (
-    0 === queue.expirationTime ||
-    queue.expirationTime > update.expirationTime
+    0 === workInProgressQueue.expirationTime ||
+    workInProgressQueue.expirationTime > renderExpirationTime
   )
-    queue.expirationTime = update.expirationTime;
-}
-var q1 = void 0,
-  q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  var alternateFiber = fiber.alternate,
-    queue1 = fiber.updateQueue;
-  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
-  null !== alternateFiber
-    ? ((fiber = alternateFiber.updateQueue),
-      null === fiber &&
-        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
-    : (fiber = null);
-  q1 = queue1;
-  q2 = fiber !== queue1 ? fiber : null;
+    workInProgressQueue.expirationTime = renderExpirationTime;
 }
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  fiber = q1;
-  var queue2 = q2;
-  null === queue2
-    ? insertUpdateIntoQueue(fiber, update)
-    : null === fiber.last || null === queue2.last
-      ? (insertUpdateIntoQueue(fiber, update),
-        insertUpdateIntoQueue(queue2, update))
-      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  null !== current &&
+    queue === current.updateQueue &&
+    (queue = workInProgress.updateQueue = cloneUpdateQueue(queue));
+  return queue;
 }
-function getStateFromUpdate(update, instance, prevState, props) {
-  update = update.partialState;
-  return "function" === typeof update
-    ? update.call(instance, prevState, props)
-    : update;
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case 1:
+      return (
+        (workInProgress = update.payload),
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress
+      );
+    case 3:
+      workInProgress.effectTag = (workInProgress.effectTag & -1025) | 64;
+    case 0:
+      workInProgress = update.payload;
+      nextProps =
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress;
+      if (null === nextProps || void 0 === nextProps) break;
+      return Object.assign({}, prevState, nextProps);
+    case 2:
+      queue.hasForceUpdate = !0;
+  }
+  return prevState;
 }
 function processUpdateQueue(
-  current,
   workInProgress,
   queue,
-  instance,
   props,
+  instance,
   renderExpirationTime
 ) {
-  null !== current &&
-    current.updateQueue === queue &&
-    (queue = workInProgress.updateQueue = {
-      baseState: queue.baseState,
-      expirationTime: queue.expirationTime,
-      first: queue.first,
-      last: queue.last,
-      isInitialized: queue.isInitialized,
-      capturedValues: queue.capturedValues,
-      callbackList: null,
-      hasForceUpdate: !1
-    });
-  queue.expirationTime = 0;
-  queue.isInitialized
-    ? (current = queue.baseState)
-    : ((current = queue.baseState = workInProgress.memoizedState),
-      (queue.isInitialized = !0));
-  for (
-    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
-    null !== update;
-
+  if (
+    !(0 === queue.expirationTime || queue.expirationTime > renderExpirationTime)
   ) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        remainingExpirationTime > updateExpirationTime
-      )
-        queue.expirationTime = updateExpirationTime;
-      didSkip || ((didSkip = !0), (queue.baseState = current));
-    } else {
-      didSkip ||
-        ((queue.first = update.next),
-        null === queue.first && (queue.last = null));
-      if (update.isReplace)
-        (current = getStateFromUpdate(update, instance, current, props)),
-          (dontMutatePrevState = !0);
-      else if (
-        (updateExpirationTime = getStateFromUpdate(
+    queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+    for (
+      var newBaseState = queue.baseState,
+        newFirstUpdate = null,
+        newExpirationTime = 0,
+        update = queue.firstUpdate,
+        resultState = newBaseState;
+      null !== update;
+
+    ) {
+      var updateExpirationTime = update.expirationTime;
+      if (updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === newFirstUpdate &&
+            ((newFirstUpdate = update), (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > updateExpirationTime)
+        )
+          newExpirationTime = updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
           update,
-          instance,
-          current,
-          props
-        ))
-      )
-        (current = dontMutatePrevState
-          ? Object.assign({}, current, updateExpirationTime)
-          : Object.assign(current, updateExpirationTime)),
-          (dontMutatePrevState = !1);
-      update.isForced && (queue.hasForceUpdate = !0);
-      null !== update.callback &&
-        ((updateExpirationTime = queue.callbackList),
-        null === updateExpirationTime &&
-          (updateExpirationTime = queue.callbackList = []),
-        updateExpirationTime.push(update));
-      null !== update.capturedValue &&
-        ((updateExpirationTime = queue.capturedValues),
-        null === updateExpirationTime
-          ? (queue.capturedValues = [update.capturedValue])
-          : updateExpirationTime.push(update.capturedValue));
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastEffect
+              ? (queue.firstEffect = queue.lastEffect = update)
+              : ((queue.lastEffect.nextEffect = update),
+                (queue.lastEffect = update)));
+      update = update.next;
+    }
+    updateExpirationTime = null;
+    for (update = queue.firstCapturedUpdate; null !== update; ) {
+      var _updateExpirationTime = update.expirationTime;
+      if (_updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === updateExpirationTime &&
+            ((updateExpirationTime = update),
+            null === newFirstUpdate && (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > _updateExpirationTime)
+        )
+          newExpirationTime = _updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
+          update,
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastCapturedEffect
+              ? (queue.firstCapturedEffect = queue.lastCapturedEffect = update)
+              : ((queue.lastCapturedEffect.nextEffect = update),
+                (queue.lastCapturedEffect = update)));
+      update = update.next;
     }
-    update = update.next;
+    null === newFirstUpdate && (queue.lastUpdate = null);
+    null === updateExpirationTime
+      ? (queue.lastCapturedUpdate = null)
+      : (workInProgress.effectTag |= 32);
+    null === newFirstUpdate &&
+      null === updateExpirationTime &&
+      (newBaseState = resultState);
+    queue.baseState = newBaseState;
+    queue.firstUpdate = newFirstUpdate;
+    queue.firstCapturedUpdate = updateExpirationTime;
+    queue.expirationTime = newExpirationTime;
+    workInProgress.memoizedState = resultState;
   }
-  null !== queue.callbackList
-    ? (workInProgress.effectTag |= 32)
-    : null !== queue.first ||
-      queue.hasForceUpdate ||
-      null !== queue.capturedValues ||
-      (workInProgress.updateQueue = null);
-  didSkip || (queue.baseState = current);
-  return current;
 }
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (null !== callbackList)
-    for (
-      queue.callbackList = null, queue = 0;
-      queue < callbackList.length;
-      queue++
-    ) {
-      var update = callbackList[queue],
-        _callback = update.callback;
-      update.callback = null;
-      invariant(
-        "function" === typeof _callback,
-        "Invalid argument passed as callback. Expected a function. Instead received: %s",
-        _callback
-      );
-      _callback.call(context);
-    }
+function callCallback(callback, context) {
+  invariant(
+    "function" === typeof callback,
+    "Invalid argument passed as callback. Expected a function. Instead received: %s",
+    callback
+  );
+  callback.call(context);
+}
+function commitUpdateQueue(finishedWork, finishedQueue, instance) {
+  null !== finishedQueue.firstCapturedUpdate &&
+    (null !== finishedQueue.lastUpdate &&
+      ((finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate),
+      (finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate)),
+    (finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null));
+  finishedWork = finishedQueue.firstEffect;
+  for (
+    finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+    null !== finishedWork;
+
+  ) {
+    var _callback3 = finishedWork.callback;
+    null !== _callback3 &&
+      ((finishedWork.callback = null), callCallback(_callback3, instance));
+    finishedWork = finishedWork.nextEffect;
+  }
+  finishedWork = finishedQueue.firstCapturedEffect;
+  for (
+    finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+    null !== finishedWork;
+
+  )
+    (finishedQueue = finishedWork.callback),
+      null !== finishedQueue &&
+        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
+      (finishedWork = finishedWork.nextEffect);
+}
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+  getDerivedStateFromProps = getDerivedStateFromProps(nextProps, prevState);
+  prevState =
+    null === getDerivedStateFromProps || void 0 === getDerivedStateFromProps
+      ? prevState
+      : Object.assign({}, prevState, getDerivedStateFromProps);
+  workInProgress.memoizedState = prevState;
+  workInProgress = workInProgress.updateQueue;
+  null !== workInProgress &&
+    0 === workInProgress.expirationTime &&
+    (workInProgress.baseState = prevState);
 }
 function ReactFiberClassComponent(
   legacyContext,
   scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState
+  computeExpirationForFiber
 ) {
   function checkShouldComponentUpdate(
     workInProgress,
@@ -1750,9 +1864,8 @@ function ReactFiberClassComponent(
     newContext
   ) {
     if (
-      null === oldProps ||
-      (null !== workInProgress.updateQueue &&
-        workInProgress.updateQueue.hasForceUpdate)
+      null !== workInProgress.updateQueue &&
+      workInProgress.updateQueue.hasForceUpdate
     )
       return !0;
     var instance = workInProgress.stateNode;
@@ -1765,7 +1878,7 @@ function ReactFiberClassComponent(
         : !0;
   }
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
+    instance.updater = classComponentUpdater;
     workInProgress.stateNode = instance;
     instance._reactInternalFiber = workInProgress;
   }
@@ -1781,78 +1894,52 @@ function ReactFiberClassComponent(
     "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
       instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
     instance.state !== workInProgress &&
-      updater.enqueueReplaceState(instance, instance.state, null);
-  }
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    workInProgress = workInProgress.type;
-    if ("function" === typeof workInProgress.getDerivedStateFromProps)
-      return workInProgress.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
   }
   var cacheContext = legacyContext.cacheContext,
     getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged,
-    updater = {
+    classComponentUpdater = {
       isMounted: isMounted,
-      enqueueSetState: function(instance, partialState, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: partialState,
-          callback: callback,
-          isReplace: !1,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueSetState: function(inst, payload, callback) {
+        inst = inst._reactInternalFiber;
+        var expirationTime = computeExpirationForFiber(inst),
+          update = createUpdate(expirationTime);
+        update.payload = payload;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, expirationTime);
+        scheduleWork(inst, expirationTime);
       },
-      enqueueReplaceState: function(instance, state, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: state,
-          callback: callback,
-          isReplace: !0,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueReplaceState: function(inst, payload, callback) {
+        inst = inst._reactInternalFiber;
+        var expirationTime = computeExpirationForFiber(inst),
+          update = createUpdate(expirationTime);
+        update.tag = 1;
+        update.payload = payload;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, expirationTime);
+        scheduleWork(inst, expirationTime);
       },
-      enqueueForceUpdate: function(instance, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: null,
-          callback: callback,
-          isReplace: !1,
-          isForced: !0,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueForceUpdate: function(inst, callback) {
+        inst = inst._reactInternalFiber;
+        var expirationTime = computeExpirationForFiber(inst),
+          update = createUpdate(expirationTime);
+        update.tag = 2;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, expirationTime);
+        scheduleWork(inst, expirationTime);
       }
     };
   return {
     adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: function(workInProgress, props) {
       var ctor = workInProgress.type,
         unmaskedContext = getUnmaskedContext(workInProgress),
@@ -1860,25 +1947,15 @@ function ReactFiberClassComponent(
         context = needsContext
           ? getMaskedContext(workInProgress, unmaskedContext)
           : emptyObject;
-      ctor = new ctor(props, context);
-      var state =
-        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
-      adoptClassInstance(workInProgress, ctor);
-      workInProgress.memoizedState = state;
-      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
-      null !== props &&
-        void 0 !== props &&
-        (workInProgress.memoizedState = Object.assign(
-          {},
-          workInProgress.memoizedState,
-          props
-        ));
+      props = new ctor(props, context);
+      workInProgress.memoizedState =
+        null !== props.state && void 0 !== props.state ? props.state : null;
+      adoptClassInstance(workInProgress, props);
       needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return ctor;
+      return props;
     },
     mountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        current = workInProgress.alternate,
         instance = workInProgress.stateNode,
         props = workInProgress.pendingProps,
         unmaskedContext = getUnmaskedContext(workInProgress);
@@ -1886,6 +1963,20 @@ function ReactFiberClassComponent(
       instance.state = workInProgress.memoizedState;
       instance.refs = emptyObject;
       instance.context = getMaskedContext(workInProgress, unmaskedContext);
+      unmaskedContext = workInProgress.updateQueue;
+      null !== unmaskedContext &&
+        (processUpdateQueue(
+          workInProgress,
+          unmaskedContext,
+          props,
+          instance,
+          renderExpirationTime
+        ),
+        (instance.state = workInProgress.memoizedState));
+      unmaskedContext = workInProgress.type.getDerivedStateFromProps;
+      "function" === typeof unmaskedContext &&
+        (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+        (instance.state = workInProgress.memoizedState));
       "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate ||
         ("function" !== typeof instance.UNSAFE_componentWillMount &&
@@ -1896,32 +1987,36 @@ function ReactFiberClassComponent(
         "function" === typeof instance.UNSAFE_componentWillMount &&
           instance.UNSAFE_componentWillMount(),
         ctor !== instance.state &&
-          updater.enqueueReplaceState(instance, instance.state, null),
-        (ctor = workInProgress.updateQueue),
-        null !== ctor &&
-          (instance.state = processUpdateQueue(
-            current,
-            workInProgress,
-            ctor,
+          classComponentUpdater.enqueueReplaceState(
             instance,
+            instance.state,
+            null
+          ),
+        (unmaskedContext = workInProgress.updateQueue),
+        null !== unmaskedContext &&
+          (processUpdateQueue(
+            workInProgress,
+            unmaskedContext,
             props,
+            instance,
             renderExpirationTime
-          )));
+          ),
+          (instance.state = workInProgress.memoizedState)));
       "function" === typeof instance.componentDidMount &&
         (workInProgress.effectTag |= 4);
     },
     resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
+        instance = workInProgress.stateNode,
+        oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps;
+      instance.props = oldProps;
+      var oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -1932,43 +2027,29 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              null,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
+      var oldState = workInProgress.memoizedState;
+      oldContext = instance.state = oldState;
+      var updateQueue = workInProgress.updateQueue;
+      null !== updateQueue &&
+        (processUpdateQueue(
           workInProgress,
-          instance,
+          updateQueue,
           newProps,
+          instance,
           renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue = workInProgress.updateQueue;
-        null !== _updateQueue &&
-          (_updateQueue.baseState = Object.assign(
-            {},
-            _updateQueue.baseState,
-            derivedStateFromProps
-          ));
-      }
+        ),
+        (oldContext = workInProgress.memoizedState));
+      "function" === typeof getDerivedStateFromProps &&
+        (applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        ),
+        (oldContext = workInProgress.memoizedState));
       if (
         !(
           oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
+          oldState !== oldContext ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -1979,12 +2060,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4),
           !1
         );
-      (oldProps = checkShouldComponentUpdate(
+      (renderExpirationTime = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
+        oldState,
         oldContext,
-        renderExpirationTime,
         newUnmaskedContext
       ))
         ? (ctor ||
@@ -1998,12 +2079,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4))
         : ("function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
+          (workInProgress.memoizedProps = newProps),
+          (workInProgress.memoizedState = oldContext));
       instance.props = newProps;
-      instance.state = renderExpirationTime;
+      instance.state = oldContext;
       instance.context = newUnmaskedContext;
-      return oldProps;
+      return renderExpirationTime;
     },
     updateClassInstance: function(
       current,
@@ -2011,16 +2092,16 @@ function ReactFiberClassComponent(
       renderExpirationTime
     ) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
+        instance = workInProgress.stateNode,
+        oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps;
+      instance.props = oldProps;
+      var oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2032,42 +2113,28 @@ function ReactFiberClassComponent(
             newUnmaskedContext
           ));
       oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              current,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
+      var newState = (instance.state = oldContext),
+        updateQueue = workInProgress.updateQueue;
+      null !== updateQueue &&
+        (processUpdateQueue(
           workInProgress,
-          instance,
+          updateQueue,
           newProps,
+          instance,
           renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue3 = workInProgress.updateQueue;
-        null !== _updateQueue3 &&
-          (_updateQueue3.baseState = Object.assign(
-            {},
-            _updateQueue3.baseState,
-            derivedStateFromProps
-          ));
-      }
+        ),
+        (newState = workInProgress.memoizedState));
+      "function" === typeof getDerivedStateFromProps &&
+        (applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        ),
+        (newState = workInProgress.memoizedState));
       if (
         !(
           oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
+          oldContext !== newState ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2081,15 +2148,15 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
+            (workInProgress.effectTag |= 256),
           !1
         );
-      (derivedStateFromProps = checkShouldComponentUpdate(
+      (renderExpirationTime = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
         oldContext,
-        renderExpirationTime,
+        newState,
         newUnmaskedContext
       ))
         ? (ctor ||
@@ -2098,19 +2165,19 @@ function ReactFiberClassComponent(
             ("function" === typeof instance.componentWillUpdate &&
               instance.componentWillUpdate(
                 newProps,
-                renderExpirationTime,
+                newState,
                 newUnmaskedContext
               ),
             "function" === typeof instance.UNSAFE_componentWillUpdate &&
               instance.UNSAFE_componentWillUpdate(
                 newProps,
-                renderExpirationTime,
+                newState,
                 newUnmaskedContext
               )),
           "function" === typeof instance.componentDidUpdate &&
             (workInProgress.effectTag |= 4),
           "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 2048))
+            (workInProgress.effectTag |= 256))
         : ("function" !== typeof instance.componentDidUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
@@ -2118,13 +2185,13 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
+            (workInProgress.effectTag |= 256),
+          (workInProgress.memoizedProps = newProps),
+          (workInProgress.memoizedState = newState));
       instance.props = newProps;
-      instance.state = renderExpirationTime;
+      instance.state = newState;
       instance.context = newUnmaskedContext;
-      return derivedStateFromProps;
+      return renderExpirationTime;
     }
   };
 }
@@ -2248,11 +2315,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, textContent, expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function updateElement(returnFiber, current, element, expirationTime) {
@@ -2260,7 +2327,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       return (
         (expirationTime = useFiber(current, element.props, expirationTime)),
         (expirationTime.ref = coerceRef(returnFiber, current, element)),
-        (expirationTime["return"] = returnFiber),
+        (expirationTime.return = returnFiber),
         expirationTime
       );
     expirationTime = createFiberFromElement(
@@ -2269,7 +2336,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       expirationTime
     );
     expirationTime.ref = coerceRef(returnFiber, current, element);
-    expirationTime["return"] = returnFiber;
+    expirationTime.return = returnFiber;
     return expirationTime;
   }
   function updatePortal(returnFiber, current, portal, expirationTime) {
@@ -2285,11 +2352,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, portal.children || [], expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function updateFragment(returnFiber, current, fragment, expirationTime, key) {
@@ -2301,11 +2368,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           key
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, fragment, expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function createChild(returnFiber, newChild, expirationTime) {
@@ -2316,7 +2383,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (newChild["return"] = returnFiber),
+        (newChild.return = returnFiber),
         newChild
       );
     if ("object" === typeof newChild && null !== newChild) {
@@ -2329,7 +2396,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               expirationTime
             )),
             (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
-            (expirationTime["return"] = returnFiber),
+            (expirationTime.return = returnFiber),
             expirationTime
           );
         case REACT_PORTAL_TYPE:
@@ -2339,7 +2406,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (newChild["return"] = returnFiber),
+            (newChild.return = returnFiber),
             newChild
           );
       }
@@ -2351,7 +2418,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime,
             null
           )),
-          (newChild["return"] = returnFiber),
+          (newChild.return = returnFiber),
           newChild
         );
       throwOnInvalidObjectType(returnFiber, newChild);
@@ -2538,17 +2605,21 @@ function ChildReconciler(shouldTrackSideEffects) {
           newChildren[newIdx],
           expirationTime
         ))
-      ) {
-        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
-          oldFiber["delete"](
+      )
+        shouldTrackSideEffects &&
+          null !== nextOldFiber.alternate &&
+          oldFiber.delete(
             null === nextOldFiber.key ? newIdx : nextOldFiber.key
-          );
-        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (resultingFirstChild = nextOldFiber)
-          : (previousNewFiber.sibling = nextOldFiber);
-        previousNewFiber = nextOldFiber;
-      }
+          ),
+          (currentFirstChild = placeChild(
+            nextOldFiber,
+            currentFirstChild,
+            newIdx
+          )),
+          null === previousNewFiber
+            ? (resultingFirstChild = nextOldFiber)
+            : (previousNewFiber.sibling = nextOldFiber),
+          (previousNewFiber = nextOldFiber);
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2622,24 +2693,22 @@ function ChildReconciler(shouldTrackSideEffects) {
       !step.done;
       newIdx++, step = newChildrenIterable.next()
     )
-      if (
-        ((step = updateFromMap(
-          oldFiber,
-          returnFiber,
-          newIdx,
-          step.value,
-          expirationTime
-        )),
-        null !== step)
-      ) {
-        if (shouldTrackSideEffects && null !== step.alternate)
-          oldFiber["delete"](null === step.key ? newIdx : step.key);
-        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (iteratorFn = step)
-          : (previousNewFiber.sibling = step);
-        previousNewFiber = step;
-      }
+      (step = updateFromMap(
+        oldFiber,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      )),
+        null !== step &&
+          (shouldTrackSideEffects &&
+            null !== step.alternate &&
+            oldFiber.delete(null === step.key ? newIdx : step.key),
+          (currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+          null === previousNewFiber
+            ? (iteratorFn = step)
+            : (previousNewFiber.sibling = step),
+          (previousNewFiber = step));
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2678,7 +2747,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     isObject,
                     newChild
                   );
-                  currentFirstChild["return"] = returnFiber;
+                  currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2695,7 +2764,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   expirationTime,
                   newChild.key
                 )),
-                (currentFirstChild["return"] = returnFiber),
+                (currentFirstChild.return = returnFiber),
                 (returnFiber = currentFirstChild))
               : ((expirationTime = createFiberFromElement(
                   newChild,
@@ -2707,7 +2776,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   currentFirstChild,
                   newChild
                 )),
-                (expirationTime["return"] = returnFiber),
+                (expirationTime.return = returnFiber),
                 (returnFiber = expirationTime));
           }
           return placeSingleChild(returnFiber);
@@ -2731,7 +2800,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     newChild.children || [],
                     expirationTime
                   );
-                  currentFirstChild["return"] = returnFiber;
+                  currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2746,7 +2815,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             );
-            currentFirstChild["return"] = returnFiber;
+            currentFirstChild.return = returnFiber;
             returnFiber = currentFirstChild;
           }
           return placeSingleChild(returnFiber);
@@ -2761,7 +2830,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               newChild,
               expirationTime
             )),
-            (currentFirstChild["return"] = returnFiber),
+            (currentFirstChild.return = returnFiber),
             (returnFiber = currentFirstChild))
           : (deleteRemainingChildren(returnFiber, currentFirstChild),
             (currentFirstChild = createFiberFromText(
@@ -2769,7 +2838,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (currentFirstChild["return"] = returnFiber),
+            (currentFirstChild.return = returnFiber),
             (returnFiber = currentFirstChild)),
         placeSingleChild(returnFiber)
       );
@@ -2855,10 +2924,10 @@ function ReactFiberBeginWork(
     workInProgress,
     shouldUpdate,
     hasContext,
-    didCaptureError,
     renderExpirationTime
   ) {
     markRef(current, workInProgress);
+    var didCaptureError = 0 !== (workInProgress.effectTag & 64);
     if (!shouldUpdate && !didCaptureError)
       return (
         hasContext && invalidateContextProvider(workInProgress, !1),
@@ -2906,11 +2975,8 @@ function ReactFiberBeginWork(
     renderExpirationTime
   ) {
     var fiber = workInProgress.child;
-    for (
-      null !== fiber && (fiber["return"] = workInProgress);
-      null !== fiber;
-
-    ) {
+    null !== fiber && (fiber.return = workInProgress);
+    for (; null !== fiber; ) {
       switch (fiber.tag) {
         case 12:
           var nextFiber = fiber.stateNode | 0;
@@ -2933,7 +2999,7 @@ function ReactFiberBeginWork(
               )
                 alternate.expirationTime = renderExpirationTime;
               else break;
-              nextFiber = nextFiber["return"];
+              nextFiber = nextFiber.return;
             }
             nextFiber = null;
           } else nextFiber = fiber.child;
@@ -2944,7 +3010,7 @@ function ReactFiberBeginWork(
         default:
           nextFiber = fiber.child;
       }
-      if (null !== nextFiber) nextFiber["return"] = fiber;
+      if (null !== nextFiber) nextFiber.return = fiber;
       else
         for (nextFiber = fiber; null !== nextFiber; ) {
           if (nextFiber === workInProgress) {
@@ -2953,10 +3019,11 @@ function ReactFiberBeginWork(
           }
           fiber = nextFiber.sibling;
           if (null !== fiber) {
+            fiber.return = nextFiber.return;
             nextFiber = fiber;
             break;
           }
-          nextFiber = nextFiber["return"];
+          nextFiber = nextFiber.return;
         }
       fiber = nextFiber;
     }
@@ -2968,8 +3035,10 @@ function ReactFiberBeginWork(
   ) {
     var context = workInProgress.type._context,
       newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps;
-    if (!hasLegacyContextChanged() && oldProps === newProps)
+      oldProps = workInProgress.memoizedProps,
+      canBailOnProps = !0;
+    if (hasLegacyContextChanged()) canBailOnProps = !1;
+    else if (oldProps === newProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
@@ -2979,7 +3048,7 @@ function ReactFiberBeginWork(
     workInProgress.memoizedProps = newProps;
     if (null === oldProps) newValue = 1073741823;
     else if (oldProps.value === newProps.value) {
-      if (oldProps.children === newProps.children)
+      if (oldProps.children === newProps.children && canBailOnProps)
         return (
           (workInProgress.stateNode = 0),
           pushProvider(workInProgress),
@@ -2993,7 +3062,7 @@ function ReactFiberBeginWork(
           (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
         (oldValue !== oldValue && newValue !== newValue)
       ) {
-        if (oldProps.children === newProps.children)
+        if (oldProps.children === newProps.children && canBailOnProps)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3008,7 +3077,7 @@ function ReactFiberBeginWork(
         (newValue |= 0),
         0 === newValue)
       ) {
-        if (oldProps.children === newProps.children)
+        if (oldProps.children === newProps.children && canBailOnProps)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3040,14 +3109,14 @@ function ReactFiberBeginWork(
         current.expirationTime
       );
       workInProgress.child = newChild;
-      for (newChild["return"] = workInProgress; null !== current.sibling; )
+      for (newChild.return = workInProgress; null !== current.sibling; )
         (current = current.sibling),
           (newChild = newChild.sibling = createWorkInProgress(
             current,
             current.pendingProps,
             current.expirationTime
           )),
-          (newChild["return"] = workInProgress);
+          (newChild.return = workInProgress);
       newChild.sibling = null;
     }
     return workInProgress.child;
@@ -3079,7 +3148,6 @@ function ReactFiberBeginWork(
     }
   );
   var adoptClassInstance = config.adoptClassInstance,
-    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
     constructClassInstance = config.constructClassInstance,
     mountClassInstance = config.mountClassInstance,
     resumeMountClassInstance = config.resumeMountClassInstance,
@@ -3128,20 +3196,13 @@ function ReactFiberBeginWork(
               (workInProgress.tag = 2),
               (workInProgress.memoizedState =
                 null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
-                ((props = callGetDerivedStateFromProps(
+              (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
+              "function" === typeof unmaskedContext &&
+                applyDerivedStateFromProps(
                   workInProgress,
-                  fn,
-                  props,
-                  workInProgress.memoizedState
-                )),
-                null !== props &&
-                  void 0 !== props &&
-                  (workInProgress.memoizedState = Object.assign(
-                    {},
-                    workInProgress.memoizedState,
-                    props
-                  ))),
+                  unmaskedContext,
+                  props
+                ),
               (props = pushLegacyContextProvider(workInProgress)),
               adoptClassInstance(workInProgress, fn),
               mountClassInstance(workInProgress, renderExpirationTime),
@@ -3150,7 +3211,6 @@ function ReactFiberBeginWork(
                 workInProgress,
                 !0,
                 props,
-                !1,
                 renderExpirationTime
               )))
             : ((workInProgress.tag = 1),
@@ -3178,103 +3238,100 @@ function ReactFiberBeginWork(
             current
           );
         case 2:
-          props = pushLegacyContextProvider(workInProgress);
-          null === current
-            ? null === workInProgress.stateNode
-              ? (constructClassInstance(
-                  workInProgress,
-                  workInProgress.pendingProps
-                ),
-                mountClassInstance(workInProgress, renderExpirationTime),
-                (fn = !0))
-              : (fn = resumeMountClassInstance(
+          return (
+            (props = pushLegacyContextProvider(workInProgress)),
+            null === current
+              ? null === workInProgress.stateNode
+                ? (constructClassInstance(
+                    workInProgress,
+                    workInProgress.pendingProps,
+                    renderExpirationTime
+                  ),
+                  mountClassInstance(workInProgress, renderExpirationTime),
+                  (fn = !0))
+                : (fn = resumeMountClassInstance(
+                    workInProgress,
+                    renderExpirationTime
+                  ))
+              : (fn = updateClassInstance(
+                  current,
                   workInProgress,
                   renderExpirationTime
-                ))
-            : (fn = updateClassInstance(
-                current,
-                workInProgress,
-                renderExpirationTime
-              ));
-          unmaskedContext = !1;
-          var updateQueue = workInProgress.updateQueue;
-          null !== updateQueue &&
-            null !== updateQueue.capturedValues &&
-            (unmaskedContext = fn = !0);
-          return finishClassComponent(
-            current,
-            workInProgress,
-            fn,
-            props,
-            unmaskedContext,
-            renderExpirationTime
-          );
-        case 3:
-          a: if (
-            (pushHostRootContext(workInProgress),
-            (fn = workInProgress.updateQueue),
-            null !== fn)
-          ) {
-            unmaskedContext = workInProgress.memoizedState;
-            props = processUpdateQueue(
+                )),
+            finishClassComponent(
               current,
               workInProgress,
               fn,
-              null,
-              null,
+              props,
               renderExpirationTime
-            );
-            workInProgress.memoizedState = props;
-            fn = workInProgress.updateQueue;
-            if (null !== fn && null !== fn.capturedValues) fn = null;
-            else if (unmaskedContext === props) {
-              resetHydrationState();
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-              break a;
-            } else fn = props.element;
-            unmaskedContext = workInProgress.stateNode;
-            (null === current || null === current.child) &&
-            unmaskedContext.hydrate &&
-            enterHydrationState(workInProgress)
-              ? ((workInProgress.effectTag |= 2),
-                (workInProgress.child = mountChildFibers(
+            )
+          );
+        case 3:
+          return (
+            pushHostRootContext(workInProgress),
+            (props = workInProgress.updateQueue),
+            null !== props
+              ? ((fn = workInProgress.memoizedState),
+                (fn = null !== fn ? fn.element : null),
+                processUpdateQueue(
                   workInProgress,
+                  props,
+                  workInProgress.pendingProps,
                   null,
-                  fn,
                   renderExpirationTime
-                )))
+                ),
+                (props = workInProgress.memoizedState.element),
+                props === fn
+                  ? (resetHydrationState(),
+                    (current = bailoutOnAlreadyFinishedWork(
+                      current,
+                      workInProgress
+                    )))
+                  : ((fn = workInProgress.stateNode),
+                    (null === current || null === current.child) &&
+                    fn.hydrate &&
+                    enterHydrationState(workInProgress)
+                      ? ((workInProgress.effectTag |= 2),
+                        (workInProgress.child = mountChildFibers(
+                          workInProgress,
+                          null,
+                          props,
+                          renderExpirationTime
+                        )))
+                      : (resetHydrationState(),
+                        reconcileChildren(current, workInProgress, props)),
+                    (current = workInProgress.child)))
               : (resetHydrationState(),
-                reconcileChildren(current, workInProgress, fn));
-            workInProgress.memoizedState = props;
-            current = workInProgress.child;
-          } else
-            resetHydrationState(),
-              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
-          return current;
+                (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                ))),
+            current
+          );
         case 5:
           a: {
             pushHostContext(workInProgress);
             null === current &&
               tryToClaimNextHydratableInstance(workInProgress);
             props = workInProgress.type;
-            updateQueue = workInProgress.memoizedProps;
+            var memoizedProps = workInProgress.memoizedProps;
             fn = workInProgress.pendingProps;
             unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && updateQueue === fn) {
+            if (!hasLegacyContextChanged() && memoizedProps === fn) {
               if (
-                (updateQueue =
+                (memoizedProps =
                   workInProgress.mode & 1 &&
                   shouldDeprioritizeSubtree(props, fn))
               )
                 workInProgress.expirationTime = 1073741823;
-              if (!updateQueue || 1073741823 !== renderExpirationTime) {
+              if (!memoizedProps || 1073741823 !== renderExpirationTime) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
             }
-            updateQueue = fn.children;
+            memoizedProps = fn.children;
             shouldSetTextContent(props, fn)
-              ? (updateQueue = null)
+              ? (memoizedProps = null)
               : unmaskedContext &&
                 shouldSetTextContent(props, unmaskedContext) &&
                 (workInProgress.effectTag |= 16);
@@ -3285,7 +3342,7 @@ function ReactFiberBeginWork(
               ? ((workInProgress.expirationTime = 1073741823),
                 (workInProgress.memoizedProps = fn),
                 (current = null))
-              : (reconcileChildren(current, workInProgress, updateQueue),
+              : (reconcileChildren(current, workInProgress, memoizedProps),
                 (workInProgress.memoizedProps = fn),
                 (current = workInProgress.child));
           }
@@ -3351,14 +3408,21 @@ function ReactFiberBeginWork(
           );
         case 14:
           return (
-            (renderExpirationTime = workInProgress.type.render),
-            (renderExpirationTime = renderExpirationTime(
-              workInProgress.pendingProps,
-              workInProgress.ref
-            )),
-            reconcileChildren(current, workInProgress, renderExpirationTime),
-            (workInProgress.memoizedProps = renderExpirationTime),
-            workInProgress.child
+            (props = workInProgress.type.render),
+            (renderExpirationTime = workInProgress.pendingProps),
+            (fn = workInProgress.ref),
+            hasLegacyContextChanged() ||
+            workInProgress.memoizedProps !== renderExpirationTime ||
+            fn !== (null !== current ? current.ref : null)
+              ? ((props = props(renderExpirationTime, fn)),
+                reconcileChildren(current, workInProgress, props),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
           );
         case 10:
           return (
@@ -3407,13 +3471,13 @@ function ReactFiberBeginWork(
           a: {
             fn = workInProgress.type;
             unmaskedContext = workInProgress.pendingProps;
-            updateQueue = workInProgress.memoizedProps;
+            memoizedProps = workInProgress.memoizedProps;
             props = fn._currentValue;
             var changedBits = fn._changedBits;
             if (
               hasLegacyContextChanged() ||
               0 !== changedBits ||
-              updateQueue !== unmaskedContext
+              memoizedProps !== unmaskedContext
             ) {
               workInProgress.memoizedProps = unmaskedContext;
               var observedBits = unmaskedContext.unstable_observedBits;
@@ -3427,12 +3491,13 @@ function ReactFiberBeginWork(
                   changedBits,
                   renderExpirationTime
                 );
-              else if (updateQueue === unmaskedContext) {
+              else if (memoizedProps === unmaskedContext) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
               renderExpirationTime = unmaskedContext.children;
               renderExpirationTime = renderExpirationTime(props);
+              workInProgress.effectTag |= 1;
               reconcileChildren(current, workInProgress, renderExpirationTime);
               current = workInProgress.child;
             } else
@@ -3463,17 +3528,16 @@ function ReactFiberCompleteWork(
       if (5 === node.tag || 6 === node.tag)
         appendInitialChild(parent, node.stateNode);
       else if (4 !== node.tag && null !== node.child) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
       if (node === workInProgress) break;
       for (; null === node.sibling; ) {
-        if (null === node["return"] || node["return"] === workInProgress)
-          return;
-        node = node["return"];
+        if (null === node.return || node.return === workInProgress) return;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -3514,17 +3578,16 @@ function ReactFiberCompleteWork(
           if (5 === node.tag || 6 === node.tag)
             appendChildToContainerChildSet(newChildSet, node.stateNode);
           else if (4 !== node.tag && null !== node.child) {
-            node.child["return"] = node;
+            node.child.return = node;
             node = node.child;
             continue;
           }
           if (node === workInProgress) break a;
           for (; null === node.sibling; ) {
-            if (null === node["return"] || node["return"] === workInProgress)
-              break a;
-            node = node["return"];
+            if (null === node.return || node.return === workInProgress) break a;
+            node = node.return;
           }
-          node.sibling["return"] = node["return"];
+          node.sibling.return = node.return;
           node = node.sibling;
         }
         portalOrRoot.pendingChildren = newChildSet;
@@ -3588,18 +3651,7 @@ function ReactFiberCompleteWork(
         case 1:
           return null;
         case 2:
-          return (
-            popLegacyContextProvider(workInProgress),
-            (current = workInProgress.stateNode),
-            (newProps = workInProgress.updateQueue),
-            null !== newProps &&
-              null !== newProps.capturedValues &&
-              ((workInProgress.effectTag &= -65),
-              "function" === typeof current.componentDidCatch
-                ? (workInProgress.effectTag |= 256)
-                : (newProps.capturedValues = null)),
-            null
-          );
+          return popLegacyContextProvider(workInProgress), null;
         case 3:
           popHostContainer(workInProgress);
           popTopLevelLegacyContextObject(workInProgress);
@@ -3610,10 +3662,6 @@ function ReactFiberCompleteWork(
           if (null === current || null === current.child)
             popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
           updateHostContainer(workInProgress);
-          current = workInProgress.updateQueue;
-          null !== current &&
-            null !== current.capturedValues &&
-            (workInProgress.effectTag |= 256);
           return null;
         case 5:
           popHostContext(workInProgress);
@@ -3621,10 +3669,10 @@ function ReactFiberCompleteWork(
           var type = workInProgress.type;
           if (null !== current && null != workInProgress.stateNode) {
             var oldProps = current.memoizedProps,
-              _instance = workInProgress.stateNode,
+              instance = workInProgress.stateNode,
               currentHostContext = getHostContext();
-            _instance = prepareUpdate(
-              _instance,
+            instance = prepareUpdate(
+              instance,
               type,
               oldProps,
               newProps,
@@ -3634,7 +3682,7 @@ function ReactFiberCompleteWork(
             updateHostComponent(
               current,
               workInProgress,
-              _instance,
+              instance,
               type,
               oldProps,
               newProps,
@@ -3716,30 +3764,34 @@ function ReactFiberCompleteWork(
           );
           workInProgress.tag = 8;
           type = [];
-          a: for (
-            (oldProps = workInProgress.stateNode) &&
-            (oldProps["return"] = workInProgress);
-            null !== oldProps;
-
-          ) {
-            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
-              invariant(!1, "A call cannot have host component children.");
-            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
-            else if (null !== oldProps.child) {
-              oldProps.child["return"] = oldProps;
-              oldProps = oldProps.child;
-              continue;
-            }
-            for (; null === oldProps.sibling; ) {
+          a: {
+            if ((oldProps = workInProgress.stateNode))
+              oldProps.return = workInProgress;
+            for (; null !== oldProps; ) {
               if (
-                null === oldProps["return"] ||
-                oldProps["return"] === workInProgress
+                5 === oldProps.tag ||
+                6 === oldProps.tag ||
+                4 === oldProps.tag
               )
-                break a;
-              oldProps = oldProps["return"];
+                invariant(!1, "A call cannot have host component children.");
+              else if (9 === oldProps.tag)
+                type.push(oldProps.pendingProps.value);
+              else if (null !== oldProps.child) {
+                oldProps.child.return = oldProps;
+                oldProps = oldProps.child;
+                continue;
+              }
+              for (; null === oldProps.sibling; ) {
+                if (
+                  null === oldProps.return ||
+                  oldProps.return === workInProgress
+                )
+                  break a;
+                oldProps = oldProps.return;
+              }
+              oldProps.sibling.return = oldProps.return;
+              oldProps = oldProps.sibling;
             }
-            oldProps.sibling["return"] = oldProps["return"];
-            oldProps = oldProps.sibling;
           }
           oldProps = newProps.handler;
           newProps = oldProps(newProps.props, type);
@@ -3784,103 +3836,11 @@ function ReactFiberCompleteWork(
     }
   };
 }
-function ReactFiberUnwindWork(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
+function createCapturedValue(value, source) {
   return {
-    throwException: function(returnFiber, sourceFiber, rawValue) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      sourceFiber = {
-        value: rawValue,
-        source: sourceFiber,
-        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-      };
-      do {
-        switch (returnFiber.tag) {
-          case 3:
-            ensureUpdateQueues(returnFiber);
-            returnFiber.updateQueue.capturedValues = [sourceFiber];
-            returnFiber.effectTag |= 1024;
-            return;
-          case 2:
-            if (
-              ((rawValue = returnFiber.stateNode),
-              0 === (returnFiber.effectTag & 64) &&
-                null !== rawValue &&
-                "function" === typeof rawValue.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(rawValue))
-            ) {
-              ensureUpdateQueues(returnFiber);
-              rawValue = returnFiber.updateQueue;
-              var capturedValues = rawValue.capturedValues;
-              null === capturedValues
-                ? (rawValue.capturedValues = [sourceFiber])
-                : capturedValues.push(sourceFiber);
-              returnFiber.effectTag |= 1024;
-              return;
-            }
-        }
-        returnFiber = returnFiber["return"];
-      } while (null !== returnFiber);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
-      }
-    }
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
   };
 }
 function logError(boundary, errorInfo) {
@@ -3896,13 +3856,7 @@ function logError(boundary, errorInfo) {
     (e && e.suppressReactErrorLogging) || console.error(e);
   }
 }
-function ReactFiberCommitWork(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed
-) {
+function ReactFiberCommitWork(config, captureError) {
   function safelyDetachRef(current) {
     var ref = current.ref;
     if (null !== ref)
@@ -3917,7 +3871,7 @@ function ReactFiberCommitWork(
   function commitBeforeMutationLifeCycles(current, finishedWork) {
     switch (finishedWork.tag) {
       case 2:
-        if (finishedWork.effectTag & 2048 && null !== current) {
+        if (finishedWork.effectTag & 256 && null !== current) {
           var prevProps = current.memoizedProps,
             prevState = current.memoizedState;
           current = finishedWork.stateNode;
@@ -3939,28 +3893,40 @@ function ReactFiberCommitWork(
         );
     }
   }
-  function commitLifeCycles(finishedRoot, current, finishedWork) {
+  function commitLifeCycles(
+    finishedRoot,
+    current,
+    finishedWork,
+    currentTime,
+    committedExpirationTime
+  ) {
     switch (finishedWork.tag) {
       case 2:
         finishedRoot = finishedWork.stateNode;
-        if (finishedWork.effectTag & 4)
-          if (null === current)
-            (finishedRoot.props = finishedWork.memoizedProps),
+        finishedWork.effectTag & 4 &&
+          (null === current
+            ? ((finishedRoot.props = finishedWork.memoizedProps),
               (finishedRoot.state = finishedWork.memoizedState),
-              finishedRoot.componentDidMount();
-          else {
-            var prevProps = current.memoizedProps;
-            current = current.memoizedState;
-            finishedRoot.props = finishedWork.memoizedProps;
-            finishedRoot.state = finishedWork.memoizedState;
-            finishedRoot.componentDidUpdate(
-              prevProps,
-              current,
-              finishedRoot.__reactInternalSnapshotBeforeUpdate
-            );
-          }
-        finishedWork = finishedWork.updateQueue;
-        null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
+              finishedRoot.componentDidMount())
+            : ((currentTime = current.memoizedProps),
+              (current = current.memoizedState),
+              (finishedRoot.props = finishedWork.memoizedProps),
+              (finishedRoot.state = finishedWork.memoizedState),
+              finishedRoot.componentDidUpdate(
+                currentTime,
+                current,
+                finishedRoot.__reactInternalSnapshotBeforeUpdate
+              )));
+        current = finishedWork.updateQueue;
+        null !== current &&
+          ((finishedRoot.props = finishedWork.memoizedProps),
+          (finishedRoot.state = finishedWork.memoizedState),
+          commitUpdateQueue(
+            finishedWork,
+            current,
+            finishedRoot,
+            committedExpirationTime
+          ));
         break;
       case 3:
         current = finishedWork.updateQueue;
@@ -3974,15 +3940,20 @@ function ReactFiberCommitWork(
               case 2:
                 finishedRoot = finishedWork.child.stateNode;
             }
-          commitCallbacks(current, finishedRoot);
+          commitUpdateQueue(
+            finishedWork,
+            current,
+            finishedRoot,
+            committedExpirationTime
+          );
         }
         break;
       case 5:
-        finishedRoot = finishedWork.stateNode;
+        committedExpirationTime = finishedWork.stateNode;
         null === current &&
           finishedWork.effectTag & 4 &&
           commitMount(
-            finishedRoot,
+            committedExpirationTime,
             finishedWork.type,
             finishedWork.memoizedProps,
             finishedWork
@@ -3999,62 +3970,16 @@ function ReactFiberCommitWork(
         );
     }
   }
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case 2:
-        var ctor = finishedWork.type;
-        onUncaughtError = finishedWork.stateNode;
-        var updateQueue = finishedWork.updateQueue;
-        invariant(
-          null !== updateQueue && null !== updateQueue.capturedValues,
-          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-        );
-        var capturedErrors = updateQueue.capturedValues;
-        updateQueue.capturedValues = null;
-        "function" !== typeof ctor.getDerivedStateFromCatch &&
-          markLegacyErrorBoundaryAsFailed(onUncaughtError);
-        onUncaughtError.props = finishedWork.memoizedProps;
-        onUncaughtError.state = finishedWork.memoizedState;
-        for (ctor = 0; ctor < capturedErrors.length; ctor++) {
-          updateQueue = capturedErrors[ctor];
-          var _error = updateQueue.value,
-            stack = updateQueue.stack;
-          logError(finishedWork, updateQueue);
-          onUncaughtError.componentDidCatch(_error, {
-            componentStack: null !== stack ? stack : ""
-          });
-        }
-        break;
-      case 3:
-        ctor = finishedWork.updateQueue;
-        invariant(
-          null !== ctor && null !== ctor.capturedValues,
-          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-        );
-        capturedErrors = ctor.capturedValues;
-        ctor.capturedValues = null;
-        for (ctor = 0; ctor < capturedErrors.length; ctor++)
-          (updateQueue = capturedErrors[ctor]),
-            logError(finishedWork, updateQueue),
-            onUncaughtError(updateQueue.value);
-        break;
-      default:
-        invariant(
-          !1,
-          "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (null !== ref) {
-      var _instance6 = finishedWork.stateNode;
+      var _instance5 = finishedWork.stateNode;
       switch (finishedWork.tag) {
         case 5:
-          finishedWork = getPublicInstance(_instance6);
+          finishedWork = getPublicInstance(_instance5);
           break;
         default:
-          finishedWork = _instance6;
+          finishedWork = _instance5;
       }
       "function" === typeof ref
         ? ref(finishedWork)
@@ -4075,12 +4000,12 @@ function ReactFiberCommitWork(
       switch (current.tag) {
         case 2:
           safelyDetachRef(current);
-          var _instance7 = current.stateNode;
-          if ("function" === typeof _instance7.componentWillUnmount)
+          var _instance6 = current.stateNode;
+          if ("function" === typeof _instance6.componentWillUnmount)
             try {
-              (_instance7.props = current.memoizedProps),
-                (_instance7.state = current.memoizedState),
-                _instance7.componentWillUnmount();
+              (_instance6.props = current.memoizedProps),
+                (_instance6.state = current.memoizedState),
+                _instance6.componentWillUnmount();
             } catch (unmountError) {
               captureError(current, unmountError);
             }
@@ -4097,12 +4022,12 @@ function ReactFiberCommitWork(
       if (null === node.child || (mutation && 4 === node.tag)) {
         if (node === root) break;
         for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === root) return;
-          node = node["return"];
+          if (null === node.return || node.return === root) return;
+          node = node.return;
         }
-        node.sibling["return"] = node["return"];
+        node.sibling.return = node.return;
         node = node.sibling;
-      } else (node.child["return"] = node), (node = node.child);
+      } else (node.child.return = node), (node = node.child);
     }
   }
   var getPublicInstance = config.getPublicInstance,
@@ -4148,18 +4073,16 @@ function ReactFiberCommitWork(
       commitPlacement: function() {},
       commitDeletion: function(current) {
         commitNestedUnmounts(current);
-        current["return"] = null;
+        current.return = null;
         current.child = null;
         current.alternate &&
-          ((current.alternate.child = null),
-          (current.alternate["return"] = null));
+          ((current.alternate.child = null), (current.alternate.return = null));
       },
       commitWork: function(current, finishedWork) {
         commitContainer(finishedWork);
       },
       commitLifeCycles: commitLifeCycles,
       commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
     };
@@ -4167,6 +4090,151 @@ function ReactFiberCommitWork(
   var commitMount = mutation.commitMount;
   invariant(!1, "Mutating reconciler is disabled.");
 }
+function ReactFiberUnwindWork(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  markLegacyErrorBoundaryAsFailed,
+  isAlreadyFailedLegacyErrorBoundary,
+  onUncaughtError
+) {
+  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+    expirationTime = createUpdate(expirationTime);
+    expirationTime.tag = 3;
+    expirationTime.payload = { element: null };
+    var error = errorInfo.value;
+    expirationTime.callback = function() {
+      onUncaughtError(error);
+      logError(fiber, errorInfo);
+    };
+    return expirationTime;
+  }
+  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+    expirationTime = createUpdate(expirationTime);
+    expirationTime.tag = 3;
+    var inst = fiber.stateNode;
+    null !== inst &&
+      "function" === typeof inst.componentDidCatch &&
+      (expirationTime.callback = function() {
+        markLegacyErrorBoundaryAsFailed(this);
+        var error = errorInfo.value,
+          stack = errorInfo.stack;
+        logError(fiber, errorInfo);
+        this.componentDidCatch(error, {
+          componentStack: null !== stack ? stack : ""
+        });
+      });
+    return expirationTime;
+  }
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
+  return {
+    throwException: function(
+      returnFiber,
+      sourceFiber,
+      rawValue,
+      renderExpirationTime
+    ) {
+      sourceFiber.effectTag |= 512;
+      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+      sourceFiber = createCapturedValue(rawValue, sourceFiber);
+      do {
+        switch (returnFiber.tag) {
+          case 3:
+            returnFiber.effectTag |= 1024;
+            sourceFiber = createRootErrorUpdate(
+              returnFiber,
+              sourceFiber,
+              renderExpirationTime
+            );
+            enqueueCapturedUpdate(
+              returnFiber,
+              sourceFiber,
+              renderExpirationTime
+            );
+            return;
+          case 2:
+            rawValue = sourceFiber;
+            var _instance = returnFiber.stateNode;
+            if (
+              0 === (returnFiber.effectTag & 64) &&
+              null !== _instance &&
+              "function" === typeof _instance.componentDidCatch &&
+              !isAlreadyFailedLegacyErrorBoundary(_instance)
+            ) {
+              returnFiber.effectTag |= 1024;
+              sourceFiber = createClassErrorUpdate(
+                returnFiber,
+                rawValue,
+                renderExpirationTime
+              );
+              enqueueCapturedUpdate(
+                returnFiber,
+                sourceFiber,
+                renderExpirationTime
+              );
+              return;
+            }
+        }
+        returnFiber = returnFiber.return;
+      } while (null !== returnFiber);
+    },
+    unwindWork: function(workInProgress) {
+      switch (workInProgress.tag) {
+        case 2:
+          popLegacyContextProvider(workInProgress);
+          var effectTag = workInProgress.effectTag;
+          return effectTag & 1024
+            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+              workInProgress)
+            : null;
+        case 3:
+          return (
+            popHostContainer(workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 5:
+          return popHostContext(workInProgress), null;
+        case 4:
+          return popHostContainer(workInProgress), null;
+        case 13:
+          return popProvider(workInProgress), null;
+        default:
+          return null;
+      }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
+    },
+    createRootErrorUpdate: createRootErrorUpdate,
+    createClassErrorUpdate: createClassErrorUpdate
+  };
+}
 var NO_CONTEXT = {};
 function ReactFiberHostContext(config, stack) {
   function requiredContext(c) {
@@ -4223,7 +4291,7 @@ function ReactFiberHydrationContext(config) {
     var fiber = new FiberNode(5, null, null, 0);
     fiber.type = "DELETED";
     fiber.stateNode = instance;
-    fiber["return"] = returnFiber;
+    fiber.return = returnFiber;
     fiber.effectTag = 8;
     null !== returnFiber.lastEffect
       ? ((returnFiber.lastEffect.nextEffect = fiber),
@@ -4255,11 +4323,11 @@ function ReactFiberHydrationContext(config) {
   }
   function popToNextHostParent(fiber) {
     for (
-      fiber = fiber["return"];
+      fiber = fiber.return;
       null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
 
     )
-      fiber = fiber["return"];
+      fiber = fiber.return;
     hydrationParentFiber = fiber;
   }
   var shouldSetTextContent = config.shouldSetTextContent;
@@ -4493,7 +4561,7 @@ function ReactFiberLegacyContext(stack) {
       ) {
         if (isContextProvider(fiber))
           return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber["return"];
+        fiber = fiber.return;
         invariant(
           fiber,
           "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
@@ -4560,12 +4628,12 @@ function ReactFiberScheduler(config) {
   function resetStack() {
     if (null !== nextUnitOfWork)
       for (
-        var interruptedWork = nextUnitOfWork["return"];
+        var interruptedWork = nextUnitOfWork.return;
         null !== interruptedWork;
 
       )
         unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork["return"]);
+          (interruptedWork = interruptedWork.return);
     nextRoot = null;
     nextRenderExpirationTime = 0;
     nextUnitOfWork = null;
@@ -4577,74 +4645,71 @@ function ReactFiberScheduler(config) {
       legacyErrorBoundariesThatAlreadyFailed.has(instance)
     );
   }
-  function completeUnitOfWork(workInProgress$jscomp$0) {
+  function markLegacyErrorBoundaryAsFailed(instance) {
+    null === legacyErrorBoundariesThatAlreadyFailed
+      ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
+      : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+  }
+  function completeUnitOfWork(workInProgress) {
     for (;;) {
-      var current = workInProgress$jscomp$0.alternate,
-        returnFiber = workInProgress$jscomp$0["return"],
-        siblingFiber = workInProgress$jscomp$0.sibling;
-      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
+      var current = workInProgress.alternate,
+        returnFiber = workInProgress.return,
+        siblingFiber = workInProgress.sibling;
+      if (0 === (workInProgress.effectTag & 512)) {
         current = completeWork(
           current,
-          workInProgress$jscomp$0,
+          workInProgress,
           nextRenderExpirationTime
         );
-        var workInProgress = workInProgress$jscomp$0;
         if (
           1073741823 === nextRenderExpirationTime ||
           1073741823 !== workInProgress.expirationTime
         ) {
-          b: switch (workInProgress.tag) {
+          var newExpirationTime = 0;
+          switch (workInProgress.tag) {
             case 3:
             case 2:
-              var newExpirationTime = workInProgress.updateQueue;
-              newExpirationTime =
-                null === newExpirationTime
-                  ? 0
-                  : newExpirationTime.expirationTime;
-              break b;
-            default:
-              newExpirationTime = 0;
+              var updateQueue = workInProgress.updateQueue;
+              null !== updateQueue &&
+                (newExpirationTime = updateQueue.expirationTime);
           }
-          for (var child = workInProgress.child; null !== child; )
-            0 !== child.expirationTime &&
+          for (updateQueue = workInProgress.child; null !== updateQueue; )
+            0 !== updateQueue.expirationTime &&
               (0 === newExpirationTime ||
-                newExpirationTime > child.expirationTime) &&
-              (newExpirationTime = child.expirationTime),
-              (child = child.sibling);
+                newExpirationTime > updateQueue.expirationTime) &&
+              (newExpirationTime = updateQueue.expirationTime),
+              (updateQueue = updateQueue.sibling);
           workInProgress.expirationTime = newExpirationTime;
         }
         if (null !== current) return current;
         null !== returnFiber &&
           0 === (returnFiber.effectTag & 512) &&
           (null === returnFiber.firstEffect &&
-            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
-          null !== workInProgress$jscomp$0.lastEffect &&
+            (returnFiber.firstEffect = workInProgress.firstEffect),
+          null !== workInProgress.lastEffect &&
             (null !== returnFiber.lastEffect &&
-              (returnFiber.lastEffect.nextEffect =
-                workInProgress$jscomp$0.firstEffect),
-            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
-          1 < workInProgress$jscomp$0.effectTag &&
+              (returnFiber.lastEffect.nextEffect = workInProgress.firstEffect),
+            (returnFiber.lastEffect = workInProgress.lastEffect)),
+          1 < workInProgress.effectTag &&
             (null !== returnFiber.lastEffect
-              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
-              : (returnFiber.firstEffect = workInProgress$jscomp$0),
-            (returnFiber.lastEffect = workInProgress$jscomp$0)));
+              ? (returnFiber.lastEffect.nextEffect = workInProgress)
+              : (returnFiber.firstEffect = workInProgress),
+            (returnFiber.lastEffect = workInProgress)));
         if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+        if (null !== returnFiber) workInProgress = returnFiber;
         else {
           isRootReadyForCommit = !0;
           break;
         }
       } else {
-        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
-        if (null !== workInProgress$jscomp$0)
-          return (
-            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
-          );
+        workInProgress = unwindWork(workInProgress);
+        if (null !== workInProgress)
+          return (workInProgress.effectTag &= 511), workInProgress;
         null !== returnFiber &&
           ((returnFiber.firstEffect = returnFiber.lastEffect = null),
           (returnFiber.effectTag |= 512));
         if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+        if (null !== returnFiber) workInProgress = returnFiber;
         else break;
       }
     }
@@ -4696,13 +4761,18 @@ function ReactFiberScheduler(config) {
           break;
         }
         isAsync = nextUnitOfWork;
-        var returnFiber = isAsync["return"];
+        var returnFiber = isAsync.return;
         if (null === returnFiber) {
           didFatal = !0;
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(returnFiber, isAsync, thrownValue);
+        throwException(
+          returnFiber,
+          isAsync,
+          thrownValue,
+          nextRenderExpirationTime
+        );
         nextUnitOfWork = completeUnitOfWork(isAsync);
       }
       break;
@@ -4719,55 +4789,61 @@ function ReactFiberScheduler(config) {
       "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
     );
   }
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    sourceFiber = {
-      value: value,
-      source: sourceFiber,
-      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-    };
-    insertUpdateIntoFiber(boundaryFiber, {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: sourceFiber,
-      next: null
-    });
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-  function onCommitPhaseError(fiber$jscomp$0, error) {
+  function onCommitPhaseError(fiber, error) {
+    var JSCompiler_inline_result;
     a: {
       invariant(
         !isWorking || isCommitting,
         "dispatch: Cannot dispatch during the render phase."
       );
-      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
-        switch (fiber.tag) {
+      for (
+        JSCompiler_inline_result = fiber.return;
+        null !== JSCompiler_inline_result;
+
+      ) {
+        switch (JSCompiler_inline_result.tag) {
           case 2:
-            var instance = fiber.stateNode;
+            var instance = JSCompiler_inline_result.stateNode;
             if (
-              "function" === typeof fiber.type.getDerivedStateFromCatch ||
+              "function" ===
+                typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
               ("function" === typeof instance.componentDidCatch &&
                 !isAlreadyFailedLegacyErrorBoundary(instance))
             ) {
-              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-              fiber$jscomp$0 = void 0;
+              fiber = createCapturedValue(error, fiber);
+              fiber = createClassErrorUpdate(
+                JSCompiler_inline_result,
+                fiber,
+                1
+              );
+              enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+              scheduleWork(JSCompiler_inline_result, 1);
+              JSCompiler_inline_result = void 0;
               break a;
             }
             break;
           case 3:
-            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-            fiber$jscomp$0 = void 0;
+            fiber = createCapturedValue(error, fiber);
+            fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+            enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+            scheduleWork(JSCompiler_inline_result, 1);
+            JSCompiler_inline_result = void 0;
             break a;
         }
-        fiber = fiber["return"];
+        JSCompiler_inline_result = JSCompiler_inline_result.return;
       }
-      3 === fiber$jscomp$0.tag &&
-        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
-      fiber$jscomp$0 = void 0;
+      3 === fiber.tag &&
+        ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
+        (JSCompiler_inline_result = createRootErrorUpdate(
+          fiber,
+          JSCompiler_inline_result,
+          1
+        )),
+        enqueueUpdate(fiber, JSCompiler_inline_result, 1),
+        scheduleWork(fiber, 1));
+      JSCompiler_inline_result = void 0;
     }
-    return fiber$jscomp$0;
+    return JSCompiler_inline_result;
   }
   function computeExpirationForFiber(fiber) {
     fiber =
@@ -4795,7 +4871,7 @@ function ReactFiberScheduler(config) {
           (0 === fiber.alternate.expirationTime ||
             fiber.alternate.expirationTime > expirationTime) &&
           (fiber.alternate.expirationTime = expirationTime);
-        if (null === fiber["return"])
+        if (null === fiber.return)
           if (3 === fiber.tag) {
             var root = fiber.stateNode;
             !isWorking &&
@@ -4813,7 +4889,7 @@ function ReactFiberScheduler(config) {
             expirationTime = void 0;
             break a;
           }
-        fiber = fiber["return"];
+        fiber = fiber.return;
       }
       expirationTime = void 0;
     }
@@ -5053,7 +5129,7 @@ function ReactFiberScheduler(config) {
         error = void 0;
       try {
         for (; null !== nextEffect; )
-          nextEffect.effectTag & 2048 &&
+          nextEffect.effectTag & 256 &&
             commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
             (nextEffect = nextEffect.nextEffect);
       } catch (e) {
@@ -5129,8 +5205,6 @@ function ReactFiberScheduler(config) {
               didError,
               error
             );
-          effectTag$jscomp$0 & 256 &&
-            commitErrorLogging(nextEffect, onUncaughtError);
           effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
           var next = nextEffect.nextEffect;
           nextEffect.nextEffect = null;
@@ -5193,21 +5267,21 @@ function ReactFiberScheduler(config) {
     legacyContext,
     stack,
     scheduleWork,
-    isAlreadyFailedLegacyErrorBoundary
+    markLegacyErrorBoundaryAsFailed,
+    isAlreadyFailedLegacyErrorBoundary,
+    onUncaughtError
   );
   var throwException = hostContext.throwException,
     unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork;
+    unwindInterruptedWork = hostContext.unwindInterruptedWork,
+    createRootErrorUpdate = hostContext.createRootErrorUpdate,
+    createClassErrorUpdate = hostContext.createClassErrorUpdate;
   hostContext = ReactFiberCommitWork(
     config,
     onCommitPhaseError,
     scheduleWork,
     computeExpirationForFiber,
-    function(instance) {
-      null === legacyErrorBoundariesThatAlreadyFailed
-        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-    },
+    markLegacyErrorBoundaryAsFailed,
     recalculateCurrentTime
   );
   var commitBeforeMutationLifeCycles =
@@ -5217,7 +5291,6 @@ function ReactFiberScheduler(config) {
     commitDeletion = hostContext.commitDeletion,
     commitWork = hostContext.commitWork,
     commitLifeCycles = hostContext.commitLifeCycles,
-    commitErrorLogging = hostContext.commitErrorLogging,
     commitAttachRef = hostContext.commitAttachRef,
     commitDetachRef = hostContext.commitDetachRef,
     now = config.now,
@@ -5385,15 +5458,11 @@ function ReactFiberReconciler$1(config) {
       ? (container.context = parentComponent)
       : (container.pendingContext = parentComponent);
     container = callback;
-    insertUpdateIntoFiber(currentTime, {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: void 0 === container ? null : container,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: null,
-      next: null
-    });
+    callback = createUpdate(expirationTime);
+    callback.payload = { element: element };
+    container = void 0 === container ? null : container;
+    null !== container && (callback.callback = container);
+    enqueueUpdate(currentTime, callback, expirationTime);
     scheduleWork(currentTime, expirationTime);
     return expirationTime;
   }
@@ -5514,8 +5583,8 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
   ReactFiberReconciler$3 =
     (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
     ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3["default"]
-    ? ReactFiberReconciler$3["default"]
+  reactReconciler = ReactFiberReconciler$3.default
+    ? ReactFiberReconciler$3.default
     : ReactFiberReconciler$3,
   nextReactTag = 2,
   ReactFabricHostComponent = (function() {
@@ -5795,7 +5864,7 @@ var roots = new Map(),
       var root = roots.get(containerTag);
       root &&
         ReactFabricRenderer.updateContainer(null, root, null, function() {
-          roots["delete"](containerTag);
+          roots.delete(containerTag);
         });
     },
     createPortal: function(children, containerTag) {
@@ -5870,6 +5939,4 @@ ReactFabricRenderer.injectIntoDevTools({
 });
 var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
   ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
-module.exports = ReactFabric$3["default"]
-  ? ReactFabric$3["default"]
-  : ReactFabric$3;
+module.exports = ReactFabric$3.default ? ReactFabric$3.default : ReactFabric$3;
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
index 21d9a6c1d543..6c6430d3eff1 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
+ * @providesModule ReactNativeRenderer-dev
  * @preventMunge
  */
 
@@ -26,9 +27,9 @@ var deepDiffer = require("deepDiffer");
 var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
+var checkPropTypes = require("prop-types/checkPropTypes");
 var shallowEqual = require("fbjs/lib/shallowEqual");
 var ExceptionsManager = require("ExceptionsManager");
-var checkPropTypes = require("prop-types/checkPropTypes");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
 
 var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
@@ -970,7 +971,7 @@ var ForwardRef = 14;
 
 function getParent(inst) {
   do {
-    inst = inst["return"];
+    inst = inst.return;
     // TODO: If this is a HostRoot we might want to bail out.
     // That is depending on if we want nested subtrees (layers) to bubble
     // events to their parent. We could also go through parentNode on the
@@ -2716,23 +2717,21 @@ RCTEventEmitter.register(ReactNativeEventEmitter);
 
 // The Symbol used to tag the ReactElement-like types. If there is no native Symbol
 // nor polyfill, then a plain number is used for performance.
-var hasSymbol = typeof Symbol === "function" && Symbol["for"];
+var hasSymbol = typeof Symbol === "function" && Symbol.for;
 
-var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
-var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
-var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 0xeac7;
+var REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 0xeac8;
+var REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 0xeac9;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.strict_mode")
+  ? Symbol.for("react.strict_mode")
   : 0xeacc;
-var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
-var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
-var REACT_ASYNC_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.async_mode")
-  : 0xeacf;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 0xeace;
+var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 0xeacf;
 var REACT_FORWARD_REF_TYPE = hasSymbol
-  ? Symbol["for"]("react.forward_ref")
+  ? Symbol.for("react.forward_ref")
   : 0xead0;
 
 var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
@@ -2847,7 +2846,7 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
   do {
     info += describeFiber(node);
     // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
+    node = node.return;
   } while (node);
   return info;
 }
@@ -3790,11 +3789,10 @@ var ContentReset = /*          */ 16;
 var Callback = /*              */ 32;
 var DidCapture = /*            */ 64;
 var Ref = /*                   */ 128;
-var ErrLog = /*                */ 256;
-var Snapshot = /*              */ 2048;
+var Snapshot = /*              */ 256;
 
 // Union of all host effects
-var HostEffectMask = /*        */ 2559;
+var HostEffectMask = /*        */ 511;
 
 var Incomplete = /*            */ 512;
 var ShouldCapture = /*         */ 1024;
@@ -3811,15 +3809,15 @@ function isFiberMountedImpl(fiber) {
     if ((node.effectTag & Placement) !== NoEffect) {
       return MOUNTING;
     }
-    while (node["return"]) {
-      node = node["return"];
+    while (node.return) {
+      node = node.return;
       if ((node.effectTag & Placement) !== NoEffect) {
         return MOUNTING;
       }
     }
   } else {
-    while (node["return"]) {
-      node = node["return"];
+    while (node.return) {
+      node = node.return;
     }
   }
   if (node.tag === HostRoot) {
@@ -3891,7 +3889,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
   var a = fiber;
   var b = alternate;
   while (true) {
-    var parentA = a["return"];
+    var parentA = a.return;
     var parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) {
       // We're at the root.
@@ -3921,7 +3919,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       invariant(false, "Unable to find node on an unmounted component.");
     }
 
-    if (a["return"] !== b["return"]) {
+    if (a.return !== b.return) {
       // The return pointer of A and the return pointer of B point to different
       // fibers. We assume that return pointers never criss-cross, so A must
       // belong to the child set of A.return, and B must belong to the child
@@ -4009,7 +4007,7 @@ function findCurrentHostFiber(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child) {
-      node.child["return"] = node;
+      node.child.return = node;
       node = node.child;
       continue;
     }
@@ -4017,12 +4015,12 @@ function findCurrentHostFiber(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
+      if (!node.return || node.return === currentParent) {
         return null;
       }
-      node = node["return"];
+      node = node.return;
     }
-    node.sibling["return"] = node["return"];
+    node.sibling.return = node.return;
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -4042,7 +4040,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child && node.tag !== HostPortal) {
-      node.child["return"] = node;
+      node.child.return = node;
       node = node.child;
       continue;
     }
@@ -4050,12 +4048,12 @@ function findCurrentHostFiberWithNoPortals(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
+      if (!node.return || node.return === currentParent) {
         return null;
       }
-      node = node["return"];
+      node = node.return;
     }
-    node.sibling["return"] = node["return"];
+    node.sibling.return = node.return;
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -4138,7 +4136,7 @@ function FiberNode(tag, pendingProps, key, mode) {
   this.stateNode = null;
 
   // Fiber
-  this["return"] = null;
+  this.return = null;
   this.child = null;
   this.sibling = null;
   this.index = 0;
@@ -4423,7 +4421,7 @@ function assignFiberPropertiesInDEV(target, source) {
   target.key = source.key;
   target.type = source.type;
   target.stateNode = source.stateNode;
-  target["return"] = source["return"];
+  target.return = source.return;
   target.child = source.child;
   target.sibling = source.sibling;
   target.index = source.index;
@@ -4706,7 +4704,7 @@ var ReactStrictModeWarnings = {
         maybeStrictRoot = fiber;
       }
 
-      fiber = fiber["return"];
+      fiber = fiber.return;
     }
 
     return maybeStrictRoot;
@@ -4827,16 +4825,6 @@ var ReactStrictModeWarnings = {
       return;
     }
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    // Note that it is sufficient to check for the presence of a
-    // single lifecycle, componentWillMount, with the polyfill flag.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning === true
-    ) {
-      return;
-    }
-
     var warningsForRoot = void 0;
     if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
       warningsForRoot = {
@@ -4852,19 +4840,23 @@ var ReactStrictModeWarnings = {
 
     var unsafeLifecycles = [];
     if (
-      typeof instance.componentWillMount === "function" ||
+      (typeof instance.componentWillMount === "function" &&
+        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
       typeof instance.UNSAFE_componentWillMount === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillMount");
     }
     if (
-      typeof instance.componentWillReceiveProps === "function" ||
+      (typeof instance.componentWillReceiveProps === "function" &&
+        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+          true) ||
       typeof instance.UNSAFE_componentWillReceiveProps === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
     }
     if (
-      typeof instance.componentWillUpdate === "function" ||
+      (typeof instance.componentWillUpdate === "function" &&
+        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
       typeof instance.UNSAFE_componentWillUpdate === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillUpdate");
@@ -4904,7 +4896,7 @@ function getCurrentFiberOwnerName() {
   return null;
 }
 
-function getCurrentFiberStackAddendum() {
+function getCurrentFiberStackAddendum$1() {
   {
     var fiber = ReactDebugCurrentFiber.current;
     if (fiber === null) {
@@ -4924,7 +4916,7 @@ function resetCurrentFiber() {
 }
 
 function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum$1;
   ReactDebugCurrentFiber.current = fiber;
   ReactDebugCurrentFiber.phase = null;
 }
@@ -4940,7 +4932,7 @@ var ReactDebugCurrentFiber = {
   setCurrentFiber: setCurrentFiber,
   setCurrentPhase: setCurrentPhase,
   getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum$1
 };
 
 // Prefix measurements so that it's possible to filter them.
@@ -5097,13 +5089,13 @@ var pauseTimers = function() {
     if (fiber._debugIsCurrentlyTiming) {
       endFiberMark(fiber, null, null);
     }
-    fiber = fiber["return"];
+    fiber = fiber.return;
   }
 };
 
 var resumeTimersRecursively = function(fiber) {
-  if (fiber["return"] !== null) {
-    resumeTimersRecursively(fiber["return"]);
+  if (fiber.return !== null) {
+    resumeTimersRecursively(fiber.return);
   }
   if (fiber._debugIsCurrentlyTiming) {
     beginFiberMark(fiber, null);
@@ -5195,7 +5187,7 @@ function stopWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
+    currentFiber = fiber.return;
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -5210,7 +5202,7 @@ function stopFailedWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
+    currentFiber = fiber.return;
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -5400,100 +5392,232 @@ function stopCommitLifeCyclesTimer() {
   }
 }
 
-var didWarnUpdateInsideUpdate = void 0;
+// UpdateQueue is a linked list of prioritized updates.
+//
+// Like fibers, update queues come in pairs: a current queue, which represents
+// the visible state of the screen, and a work-in-progress queue, which is
+// can be mutated and processed asynchronously before it is committed — a form
+// of double buffering. If a work-in-progress render is discarded before
+// finishing, we create a new work-in-progress by cloning the current queue.
+//
+// Both queues share a persistent, singly-linked list structure. To schedule an
+// update, we append it to the end of both queues. Each queue maintains a
+// pointer to first update in the persistent list that hasn't been processed.
+// The work-in-progress pointer always has a position equal to or greater than
+// the current queue, since we always work on that one. The current queue's
+// pointer is only updated during the commit phase, when we swap in the
+// work-in-progress.
+//
+// For example:
+//
+//   Current pointer:           A - B - C - D - E - F
+//   Work-in-progress pointer:              D - E - F
+//                                          ^
+//                                          The work-in-progress queue has
+//                                          processed more updates than current.
+//
+// The reason we append to both queues is because otherwise we might drop
+// updates without ever processing them. For example, if we only add updates to
+// the work-in-progress queue, some updates could be lost whenever a work-in
+// -progress render restarts by cloning from current. Similarly, if we only add
+// updates to the current queue, the updates will be lost whenever an already
+// in-progress queue commits and swaps with the current queue. However, by
+// adding to both queues, we guarantee that the update will be part of the next
+// work-in-progress. (And because the work-in-progress queue becomes the
+// current queue once it commits, there's no danger of applying the same
+// update twice.)
+//
+// Prioritization
+// --------------
+//
+// Updates are not sorted by priority, but by insertion; new updates are always
+// appended to the end of the list.
+//
+// The priority is still important, though. When processing the update queue
+// during the render phase, only the updates with sufficient priority are
+// included in the result. If we skip an update because it has insufficient
+// priority, it remains in the queue to be processed later, during a lower
+// priority render. Crucially, all updates subsequent to a skipped update also
+// remain in the queue *regardless of their priority*. That means high priority
+// updates are sometimes processed twice, at two separate priorities. We also
+// keep track of a base state, that represents the state before the first
+// update in the queue is applied.
+//
+// For example:
+//
+//   Given a base state of '', and the following queue of updates
+//
+//     A1 - B2 - C1 - D2
+//
+//   where the number indicates the priority, and the update is applied to the
+//   previous state by appending a letter, React will process these updates as
+//   two separate renders, one per distinct priority level:
+//
+//   First render, at priority 1:
+//     Base state: ''
+//     Updates: [A1, C1]
+//     Result state: 'AC'
+//
+//   Second render, at priority 2:
+//     Base state: 'A'            <-  The base state does not include C1,
+//                                    because B2 was skipped.
+//     Updates: [B2, C1, D2]      <-  C1 was rebased on top of B2
+//     Result state: 'ABCD'
+//
+// Because we process updates in insertion order, and rebase high priority
+// updates when preceding updates are skipped, the final result is deterministic
+// regardless of priority. Intermediate state may vary according to system
+// resources, but the final state is always the same.
+
+var UpdateState = 0;
+var ReplaceState = 1;
+var ForceUpdate = 2;
+var CaptureUpdate = 3;
 
+var didWarnUpdateInsideUpdate = void 0;
+var currentlyProcessingQueue = void 0;
+var resetCurrentlyProcessingQueue = void 0;
 {
   didWarnUpdateInsideUpdate = false;
+  currentlyProcessingQueue = null;
+  resetCurrentlyProcessingQueue = function() {
+    currentlyProcessingQueue = null;
+  };
 }
 
-// Callbacks are not validated until invocation
-
-// Singly linked-list of updates. When an update is scheduled, it is added to
-// the queue of the current fiber and the work-in-progress fiber. The two queues
-// are separate but they share a persistent structure.
-//
-// During reconciliation, updates are removed from the work-in-progress fiber,
-// but they remain on the current fiber. That ensures that if a work-in-progress
-// is aborted, the aborted updates are recovered by cloning from current.
-//
-// The work-in-progress queue is always a subset of the current queue.
-//
-// When the tree is committed, the work-in-progress becomes the current.
-
 function createUpdateQueue(baseState) {
   var queue = {
-    baseState: baseState,
     expirationTime: NoWork,
-    first: null,
-    last: null,
-    callbackList: null,
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null,
+    hasForceUpdate: false
+  };
+  return queue;
+}
+
+function cloneUpdateQueue(currentQueue) {
+  var queue = {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+
+    // TODO: With resuming, if we bail out and resuse the child tree, we should
+    // keep these effects.
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+
     hasForceUpdate: false,
-    isInitialized: false,
-    capturedValues: null
+
+    firstEffect: null,
+    lastEffect: null,
+
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
   };
-  {
-    queue.isProcessing = false;
-  }
   return queue;
 }
 
-function insertUpdateIntoQueue(queue, update) {
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+
+    tag: UpdateState,
+    payload: null,
+    callback: null,
+
+    next: null,
+    nextEffect: null
+  };
+}
+
+function appendUpdateToQueue(queue, update, expirationTime) {
   // Append the update to the end of the list.
-  if (queue.last === null) {
+  if (queue.lastUpdate === null) {
     // Queue is empty
-    queue.first = queue.last = update;
+    queue.firstUpdate = queue.lastUpdate = update;
   } else {
-    queue.last.next = update;
-    queue.last = update;
+    queue.lastUpdate.next = update;
+    queue.lastUpdate = update;
   }
   if (
     queue.expirationTime === NoWork ||
-    queue.expirationTime > update.expirationTime
+    queue.expirationTime > expirationTime
   ) {
-    queue.expirationTime = update.expirationTime;
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    queue.expirationTime = expirationTime;
   }
 }
 
-var q1 = void 0;
-var q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  // We'll have at least one and at most two distinct update queues.
-  var alternateFiber = fiber.alternate;
-  var queue1 = fiber.updateQueue;
-  if (queue1 === null) {
-    // TODO: We don't know what the base state will be until we begin work.
-    // It depends on which fiber is the next current. Initialize with an empty
-    // base state, then set to the memoizedState when rendering. Not super
-    // happy with this approach.
-    queue1 = fiber.updateQueue = createUpdateQueue(null);
-  }
-
+function enqueueUpdate(fiber, update, expirationTime) {
+  // Update queues are created lazily.
+  var alternate = fiber.alternate;
+  var queue1 = void 0;
   var queue2 = void 0;
-  if (alternateFiber !== null) {
-    queue2 = alternateFiber.updateQueue;
-    if (queue2 === null) {
-      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
+  if (alternate === null) {
+    // There's only one fiber.
+    queue1 = fiber.updateQueue;
+    queue2 = null;
+    if (queue1 === null) {
+      queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
     }
   } else {
-    queue2 = null;
+    // There are two owners.
+    queue1 = fiber.updateQueue;
+    queue2 = alternate.updateQueue;
+    if (queue1 === null) {
+      if (queue2 === null) {
+        // Neither fiber has an update queue. Create new ones.
+        queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
+        queue2 = alternate.updateQueue = createUpdateQueue(
+          alternate.memoizedState
+        );
+      } else {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue1 = fiber.updateQueue = cloneUpdateQueue(queue2);
+      }
+    } else {
+      if (queue2 === null) {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue2 = alternate.updateQueue = cloneUpdateQueue(queue1);
+      } else {
+        // Both owners have an update queue.
+      }
+    }
+  }
+  if (queue2 === null || queue1 === queue2) {
+    // There's only a single queue.
+    appendUpdateToQueue(queue1, update, expirationTime);
+  } else {
+    // There are two queues. We need to append the update to both queues,
+    // while accounting for the persistent structure of the list — we don't
+    // want the same update to be added multiple times.
+    if (queue1.lastUpdate === null || queue2.lastUpdate === null) {
+      // One of the queues is not empty. We must add the update to both queues.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      appendUpdateToQueue(queue2, update, expirationTime);
+    } else {
+      // Both queues are non-empty. The last update is the same in both lists,
+      // because of structural sharing. So, only append to one of the lists.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      // But we still need to update the `lastUpdate` pointer of queue2.
+      queue2.lastUpdate = update;
+    }
   }
-  queue2 = queue2 !== queue1 ? queue2 : null;
-
-  // Use module variables instead of returning a tuple
-  q1 = queue1;
-  q2 = queue2;
-}
-
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  var queue1 = q1;
-  var queue2 = q2;
 
-  // Warn if an update is scheduled from inside an updater function.
   {
     if (
-      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
+      fiber.tag === ClassComponent &&
+      (currentlyProcessingQueue === queue1 ||
+        (queue2 !== null && currentlyProcessingQueue === queue2)) &&
       !didWarnUpdateInsideUpdate
     ) {
       warning(
@@ -5506,225 +5630,328 @@ function insertUpdateIntoFiber(fiber, update) {
       didWarnUpdateInsideUpdate = true;
     }
   }
+}
 
-  // If there's only one queue, add the update to that queue and exit.
-  if (queue2 === null) {
-    insertUpdateIntoQueue(queue1, update);
-    return;
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  // Captured updates go into a separate list, and only on the work-in-
+  // progress queue.
+  var workInProgressQueue = workInProgress.updateQueue;
+  if (workInProgressQueue === null) {
+    workInProgressQueue = workInProgress.updateQueue = createUpdateQueue(
+      workInProgress.memoizedState
+    );
+  } else {
+    // TODO: I put this here rather than createWorkInProgress so that we don't
+    // clone the queue unnecessarily. There's probably a better way to
+    // structure this.
+    workInProgressQueue = ensureWorkInProgressQueueIsAClone(
+      workInProgress,
+      workInProgressQueue
+    );
   }
 
-  // If either queue is empty, we need to add to both queues.
-  if (queue1.last === null || queue2.last === null) {
-    insertUpdateIntoQueue(queue1, update);
-    insertUpdateIntoQueue(queue2, update);
-    return;
+  // Append the update to the end of the list.
+  if (workInProgressQueue.lastCapturedUpdate === null) {
+    // This is the first render phase update
+    workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update;
+  } else {
+    workInProgressQueue.lastCapturedUpdate.next = update;
+    workInProgressQueue.lastCapturedUpdate = update;
+  }
+  if (
+    workInProgressQueue.expirationTime === NoWork ||
+    workInProgressQueue.expirationTime > renderExpirationTime
+  ) {
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    workInProgressQueue.expirationTime = renderExpirationTime;
   }
-
-  // If both lists are not empty, the last update is the same for both lists
-  // because of structural sharing. So, we should only append to one of
-  // the lists.
-  insertUpdateIntoQueue(queue1, update);
-  // But we still need to update the `last` pointer of queue2.
-  queue2.last = update;
 }
 
-function getUpdateExpirationTime(fiber) {
-  switch (fiber.tag) {
-    case HostRoot:
-    case ClassComponent:
-      var updateQueue = fiber.updateQueue;
-      if (updateQueue === null) {
-        return NoWork;
-      }
-      return updateQueue.expirationTime;
-    default:
-      return NoWork;
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  if (current !== null) {
+    // If the work-in-progress queue is equal to the current queue,
+    // we need to clone it first.
+    if (queue === current.updateQueue) {
+      queue = workInProgress.updateQueue = cloneUpdateQueue(queue);
+    }
   }
+  return queue;
 }
 
-function getStateFromUpdate(update, instance, prevState, props) {
-  var partialState = update.partialState;
-  if (typeof partialState === "function") {
-    return partialState.call(instance, prevState, props);
-  } else {
-    return partialState;
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case ReplaceState: {
+      var _payload = update.payload;
+      if (typeof _payload === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload.call(instance, prevState, nextProps);
+          }
+        }
+        return _payload.call(instance, prevState, nextProps);
+      }
+      // State object
+      return _payload;
+    }
+    case CaptureUpdate: {
+      workInProgress.effectTag =
+        (workInProgress.effectTag & ~ShouldCapture) | DidCapture;
+    }
+    // Intentional fallthrough
+    case UpdateState: {
+      var _payload2 = update.payload;
+      var partialState = void 0;
+      if (typeof _payload2 === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload2.call(instance, prevState, nextProps);
+          }
+        }
+        partialState = _payload2.call(instance, prevState, nextProps);
+      } else {
+        // Partial state object
+        partialState = _payload2;
+      }
+      if (partialState === null || partialState === undefined) {
+        // Null and undefined are treated as no-ops.
+        return prevState;
+      }
+      // Merge the partial state and the previous state.
+      return Object.assign({}, prevState, partialState);
+    }
+    case ForceUpdate: {
+      queue.hasForceUpdate = true;
+      return prevState;
+    }
   }
+  return prevState;
 }
 
 function processUpdateQueue(
-  current,
   workInProgress,
   queue,
-  instance,
   props,
+  instance,
   renderExpirationTime
 ) {
-  if (current !== null && current.updateQueue === queue) {
-    // We need to create a work-in-progress queue, by cloning the current queue.
-    var currentQueue = queue;
-    queue = workInProgress.updateQueue = {
-      baseState: currentQueue.baseState,
-      expirationTime: currentQueue.expirationTime,
-      first: currentQueue.first,
-      last: currentQueue.last,
-      isInitialized: currentQueue.isInitialized,
-      capturedValues: currentQueue.capturedValues,
-      // These fields are no longer valid because they were already committed.
-      // Reset them.
-      callbackList: null,
-      hasForceUpdate: false
-    };
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > renderExpirationTime
+  ) {
+    // Insufficient priority. Bailout.
+    return;
   }
 
+  queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+
   {
-    // Set this flag so we can warn if setState is called inside the update
-    // function of another setState.
-    queue.isProcessing = true;
-  }
-
-  // Reset the remaining expiration time. If we skip over any updates, we'll
-  // increase this accordingly.
-  queue.expirationTime = NoWork;
-
-  // TODO: We don't know what the base state will be until we begin work.
-  // It depends on which fiber is the next current. Initialize with an empty
-  // base state, then set to the memoizedState when rendering. Not super
-  // happy with this approach.
-  var state = void 0;
-  if (queue.isInitialized) {
-    state = queue.baseState;
-  } else {
-    state = queue.baseState = workInProgress.memoizedState;
-    queue.isInitialized = true;
+    currentlyProcessingQueue = queue;
   }
-  var dontMutatePrevState = true;
-  var update = queue.first;
-  var didSkip = false;
+
+  // These values may change as we process the queue.
+  var newBaseState = queue.baseState;
+  var newFirstUpdate = null;
+  var newExpirationTime = NoWork;
+
+  // Iterate through the list of updates to compute the result.
+  var update = queue.firstUpdate;
+  var resultState = newBaseState;
   while (update !== null) {
     var updateExpirationTime = update.expirationTime;
     if (updateExpirationTime > renderExpirationTime) {
       // This update does not have sufficient priority. Skip it.
-      var remainingExpirationTime = queue.expirationTime;
+      if (newFirstUpdate === null) {
+        // This is the first skipped update. It will be the first update in
+        // the new list.
+        newFirstUpdate = update;
+        // Since this is the first update that was skipped, the current result
+        // is the new base state.
+        newBaseState = resultState;
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
       if (
-        remainingExpirationTime === NoWork ||
-        remainingExpirationTime > updateExpirationTime
+        newExpirationTime === NoWork ||
+        newExpirationTime > updateExpirationTime
       ) {
-        // Update the remaining expiration time.
-        queue.expirationTime = updateExpirationTime;
+        newExpirationTime = updateExpirationTime;
       }
-      if (!didSkip) {
-        didSkip = true;
-        queue.baseState = state;
+    } else {
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback = update.callback;
+      if (_callback !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastEffect === null) {
+          queue.firstEffect = queue.lastEffect = update;
+        } else {
+          queue.lastEffect.nextEffect = update;
+          queue.lastEffect = update;
+        }
       }
-      // Continue to the next update.
-      update = update.next;
-      continue;
     }
+    // Continue to the next update.
+    update = update.next;
+  }
 
-    // This update does have sufficient priority.
-
-    // If no previous updates were skipped, drop this update from the queue by
-    // advancing the head of the list.
-    if (!didSkip) {
-      queue.first = update.next;
-      if (queue.first === null) {
-        queue.last = null;
+  // Separately, iterate though the list of captured updates.
+  var newFirstCapturedUpdate = null;
+  update = queue.firstCapturedUpdate;
+  while (update !== null) {
+    var _updateExpirationTime = update.expirationTime;
+    if (_updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      if (newFirstCapturedUpdate === null) {
+        // This is the first skipped captured update. It will be the first
+        // update in the new list.
+        newFirstCapturedUpdate = update;
+        // If this is the first update that was skipped, the current result is
+        // the new base state.
+        if (newFirstUpdate === null) {
+          newBaseState = resultState;
+        }
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
+      if (
+        newExpirationTime === NoWork ||
+        newExpirationTime > _updateExpirationTime
+      ) {
+        newExpirationTime = _updateExpirationTime;
       }
-    }
-
-    // Invoke setState callback an extra time to help detect side-effects.
-    // Ignore the return value in this case.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      getStateFromUpdate(update, instance, state, props);
-    }
-
-    // Process the update
-    var _partialState = void 0;
-    if (update.isReplace) {
-      state = getStateFromUpdate(update, instance, state, props);
-      dontMutatePrevState = true;
     } else {
-      _partialState = getStateFromUpdate(update, instance, state, props);
-      if (_partialState) {
-        if (dontMutatePrevState) {
-          // $FlowFixMe: Idk how to type this properly.
-          state = Object.assign({}, state, _partialState);
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback2 = update.callback;
+      if (_callback2 !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastCapturedEffect === null) {
+          queue.firstCapturedEffect = queue.lastCapturedEffect = update;
         } else {
-          state = Object.assign(state, _partialState);
+          queue.lastCapturedEffect.nextEffect = update;
+          queue.lastCapturedEffect = update;
         }
-        dontMutatePrevState = false;
-      }
-    }
-    if (update.isForced) {
-      queue.hasForceUpdate = true;
-    }
-    if (update.callback !== null) {
-      // Append to list of callbacks.
-      var _callbackList = queue.callbackList;
-      if (_callbackList === null) {
-        _callbackList = queue.callbackList = [];
-      }
-      _callbackList.push(update);
-    }
-    if (update.capturedValue !== null) {
-      var _capturedValues = queue.capturedValues;
-      if (_capturedValues === null) {
-        queue.capturedValues = [update.capturedValue];
-      } else {
-        _capturedValues.push(update.capturedValue);
       }
     }
     update = update.next;
   }
 
-  if (queue.callbackList !== null) {
+  if (newFirstUpdate === null) {
+    queue.lastUpdate = null;
+  }
+  if (newFirstCapturedUpdate === null) {
+    queue.lastCapturedUpdate = null;
+  } else {
     workInProgress.effectTag |= Callback;
-  } else if (
-    queue.first === null &&
-    !queue.hasForceUpdate &&
-    queue.capturedValues === null
-  ) {
-    // The queue is empty. We can reset it.
-    workInProgress.updateQueue = null;
   }
-
-  if (!didSkip) {
-    didSkip = true;
-    queue.baseState = state;
+  if (newFirstUpdate === null && newFirstCapturedUpdate === null) {
+    // We processed every update, without skipping. That means the new base
+    // state is the same as the result state.
+    newBaseState = resultState;
   }
 
+  queue.baseState = newBaseState;
+  queue.firstUpdate = newFirstUpdate;
+  queue.firstCapturedUpdate = newFirstCapturedUpdate;
+  queue.expirationTime = newExpirationTime;
+
+  workInProgress.memoizedState = resultState;
+
   {
-    // No longer processing.
-    queue.isProcessing = false;
+    currentlyProcessingQueue = null;
   }
+}
 
-  return state;
+function callCallback(callback, context) {
+  invariant(
+    typeof callback === "function",
+    "Invalid argument passed as callback. Expected a function. Instead " +
+      "received: %s",
+    callback
+  );
+  callback.call(context);
 }
 
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (callbackList === null) {
-    return;
+function commitUpdateQueue(
+  finishedWork,
+  finishedQueue,
+  instance,
+  renderExpirationTime
+) {
+  // If the finished render included captured updates, and there are still
+  // lower priority updates left over, we need to keep the captured updates
+  // in the queue so that they are rebased and not dropped once we process the
+  // queue again at the lower priority.
+  if (finishedQueue.firstCapturedUpdate !== null) {
+    // Join the captured update list to the end of the normal list.
+    if (finishedQueue.lastUpdate !== null) {
+      finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate;
+      finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate;
+    }
+    // Clear the list of captured updates.
+    finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null;
   }
-  // Set the list to null to make sure they don't get called more than once.
-  queue.callbackList = null;
-  for (var i = 0; i < callbackList.length; i++) {
-    var update = callbackList[i];
-    var _callback = update.callback;
-    // This update might be processed again. Clear the callback so it's only
-    // called once.
-    update.callback = null;
-    invariant(
-      typeof _callback === "function",
-      "Invalid argument passed as callback. Expected a function. Instead " +
-        "received: %s",
-      _callback
-    );
-    _callback.call(context);
+
+  // Commit the effects
+  var effect = finishedQueue.firstEffect;
+  finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+  while (effect !== null) {
+    var _callback3 = effect.callback;
+    if (_callback3 !== null) {
+      effect.callback = null;
+      callCallback(_callback3, instance);
+    }
+    effect = effect.nextEffect;
+  }
+
+  effect = finishedQueue.firstCapturedEffect;
+  finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+  while (effect !== null) {
+    var _callback4 = effect.callback;
+    if (_callback4 !== null) {
+      effect.callback = null;
+      callCallback(_callback4, instance);
+    }
+    effect = effect.nextEffect;
   }
 }
 
@@ -5732,18 +5959,19 @@ var fakeInternalInstance = {};
 var isArray = Array.isArray;
 
 var didWarnAboutStateAssignmentForComponent = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
 var didWarnAboutUninitializedState = void 0;
 var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
 var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
+var warnOnUndefinedDerivedState = void 0;
 var warnOnInvalidCallback = void 0;
 
 {
   didWarnAboutStateAssignmentForComponent = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
   didWarnAboutUninitializedState = new Set();
   didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
   didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
 
   var didWarnOnInvalidCallback = new Set();
 
@@ -5764,6 +5992,21 @@ var warnOnInvalidCallback = void 0;
     }
   };
 
+  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
+    if (partialState === undefined) {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+        didWarnAboutUndefinedDerivedState.add(componentName);
+        warning(
+          false,
+          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+            "You have returned undefined.",
+          componentName
+        );
+      }
+    }
+  };
+
   // This is so gross but it's at least non-critical and can be removed if
   // it causes problems. This is meant to give a nicer error message for
   // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
@@ -5785,17 +6028,43 @@ var warnOnInvalidCallback = void 0;
   });
   Object.freeze(fakeInternalInstance);
 }
-function callGetDerivedStateFromCatch(ctor, capturedValues) {
-  var resultState = {};
-  for (var i = 0; i < capturedValues.length; i++) {
-    var capturedValue = capturedValues[i];
-    var error = capturedValue.value;
-    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
-    if (partialState !== null && partialState !== undefined) {
-      Object.assign(resultState, partialState);
+
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+
+  {
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      // Invoke the function an extra time to help detect side-effects.
+      getDerivedStateFromProps(nextProps, prevState);
     }
   }
-  return resultState;
+
+  var partialState = getDerivedStateFromProps(nextProps, prevState);
+
+  {
+    warnOnUndefinedDerivedState(workInProgress, partialState);
+  }
+  // Merge the partial state and the previous state.
+  var memoizedState =
+    partialState === null || partialState === undefined
+      ? prevState
+      : Object.assign({}, prevState, partialState);
+  workInProgress.memoizedState = memoizedState;
+
+  // Once the update queue is empty, persist the derived state onto the
+  // base state.
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
+    updateQueue.baseState = memoizedState;
+  }
 }
 
 var ReactFiberClassComponent = function(
@@ -5811,65 +6080,57 @@ var ReactFiberClassComponent = function(
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged;
 
-  // Class component state updater
-
-  var updater = {
+  var classComponentUpdater = {
     isMounted: isMounted,
-    enqueueSetState: function(instance, partialState, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "setState");
-      }
+    enqueueSetState: function(inst, payload, callback) {
+      var fiber = get$1(inst);
       var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: partialState,
-        callback: callback,
-        isReplace: false,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+
+      var update = createUpdate(expirationTime);
+      update.payload = payload;
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "setState");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueReplaceState: function(instance, state, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "replaceState");
-      }
+    enqueueReplaceState: function(inst, payload, callback) {
+      var fiber = get$1(inst);
       var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: state,
-        callback: callback,
-        isReplace: true,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+
+      var update = createUpdate(expirationTime);
+      update.tag = ReplaceState;
+      update.payload = payload;
+
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "replaceState");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueForceUpdate: function(instance, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "forceUpdate");
-      }
+    enqueueForceUpdate: function(inst, callback) {
+      var fiber = get$1(inst);
       var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: null,
-        callback: callback,
-        isReplace: false,
-        isForced: true,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+
+      var update = createUpdate(expirationTime);
+      update.tag = ForceUpdate;
+
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "forceUpdate");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     }
   };
@@ -5883,11 +6144,10 @@ var ReactFiberClassComponent = function(
     newContext
   ) {
     if (
-      oldProps === null ||
-      (workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate)
+      workInProgress.updateQueue !== null &&
+      workInProgress.updateQueue.hasForceUpdate
     ) {
-      // If the workInProgress already has an Update effect, return true
+      // If forceUpdate was called, disregard sCU.
       return true;
     }
 
@@ -6144,13 +6404,8 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function resetInputPointers(workInProgress, instance) {
-    instance.props = workInProgress.memoizedProps;
-    instance.state = workInProgress.memoizedState;
-  }
-
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
+    instance.updater = classComponentUpdater;
     workInProgress.stateNode = instance;
     // The instance needs access to the fiber so that it can schedule updates
     set(instance, workInProgress);
@@ -6159,7 +6414,7 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function constructClassInstance(workInProgress, props) {
+  function constructClassInstance(workInProgress, props, renderExpirationTime) {
     var ctor = workInProgress.type;
     var unmaskedContext = getUnmaskedContext(workInProgress);
     var needsContext = isContextConsumer(workInProgress);
@@ -6168,19 +6423,21 @@ var ReactFiberClassComponent = function(
       : emptyObject;
 
     // Instantiate twice to help detect side-effects.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      new ctor(props, context); // eslint-disable-line no-new
+    {
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        new ctor(props, context); // eslint-disable-line no-new
+      }
     }
 
     var instance = new ctor(props, context);
-    var state =
+    var state = (workInProgress.memoizedState =
       instance.state !== null && instance.state !== undefined
         ? instance.state
-        : null;
+        : null);
     adoptClassInstance(workInProgress, instance);
 
     {
@@ -6271,26 +6528,6 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    workInProgress.memoizedState = state;
-
-    var partialState = callGetDerivedStateFromProps(
-      workInProgress,
-      instance,
-      props,
-      state
-    );
-
-    if (partialState !== null && partialState !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      workInProgress.memoizedState = Object.assign(
-        {},
-        workInProgress.memoizedState,
-        partialState
-      );
-    }
-
     // Cache unmasked context so we can avoid recreating masked context unless necessary.
     // ReactFiberContext usually updates this cache but can't for newly-created instances.
     if (needsContext) {
@@ -6323,7 +6560,7 @@ var ReactFiberClassComponent = function(
           getComponentName(workInProgress) || "Component"
         );
       }
-      updater.enqueueReplaceState(instance, instance.state, null);
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
@@ -6357,57 +6594,13 @@ var ReactFiberClassComponent = function(
           );
         }
       }
-      updater.enqueueReplaceState(instance, instance.state, null);
-    }
-  }
-
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    var type = workInProgress.type;
-
-    if (typeof type.getDerivedStateFromProps === "function") {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        // Invoke method an extra time to help detect side-effects.
-        type.getDerivedStateFromProps.call(null, nextProps, prevState);
-      }
-
-      var partialState = type.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
-
-      {
-        if (partialState === undefined) {
-          var componentName = getComponentName(workInProgress) || "Component";
-          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-            didWarnAboutUndefinedDerivedState.add(componentName);
-            warning(
-              false,
-              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-                "You have returned undefined.",
-              componentName
-            );
-          }
-        }
-      }
-
-      return partialState;
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
   // Invokes the mount life-cycles on a previously never rendered instance.
   function mountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
-    var current = workInProgress.alternate;
 
     {
       checkClassInstance(workInProgress);
@@ -6438,6 +6631,28 @@ var ReactFiberClassComponent = function(
       }
     }
 
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
+        workInProgress,
+        updateQueue,
+        props,
+        instance,
+        renderExpirationTime
+      );
+      instance.state = workInProgress.memoizedState;
+    }
+
+    var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
+        workInProgress,
+        getDerivedStateFromProps,
+        props
+      );
+      instance.state = workInProgress.memoizedState;
+    }
+
     // In order to support react-lifecycles-compat polyfilled components,
     // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
@@ -6449,18 +6664,19 @@ var ReactFiberClassComponent = function(
       callComponentWillMount(workInProgress, instance);
       // If we had additional state updates during this life-cycle, let's
       // process them now.
-      var updateQueue = workInProgress.updateQueue;
+      updateQueue = workInProgress.updateQueue;
       if (updateQueue !== null) {
-        instance.state = processUpdateQueue(
-          current,
+        processUpdateQueue(
           workInProgress,
           updateQueue,
-          instance,
           props,
+          instance,
           renderExpirationTime
         );
+        instance.state = workInProgress.memoizedState;
       }
     }
+
     if (typeof instance.componentDidMount === "function") {
       workInProgress.effectTag |= Update;
     }
@@ -6469,16 +6685,18 @@ var ReactFiberClassComponent = function(
   function resumeMountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
+    instance.props = oldProps;
+
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6502,93 +6720,27 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        null,
+    var newState = (instance.state = oldState);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
         workInProgress,
-        workInProgress.updateQueue,
-        instance,
+        updateQueue,
         newProps,
+        instance,
         renderExpirationTime
       );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
+      newState = workInProgress.memoizedState;
     }
 
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
         workInProgress,
-        instance,
-        newProps,
-        newState
+        getDerivedStateFromProps,
+        newProps
       );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue = workInProgress.updateQueue;
-      if (_updateQueue !== null) {
-        _updateQueue.baseState = Object.assign(
-          {},
-          _updateQueue.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue2 = workInProgress.updateQueue;
-      if (_updateQueue2 !== null) {
-        _updateQueue2.baseState = Object.assign(
-          {},
-          _updateQueue2.baseState,
-          derivedStateFromCatch
-        );
-      }
+      newState = workInProgress.memoizedState;
     }
 
     if (
@@ -6645,9 +6797,9 @@ var ReactFiberClassComponent = function(
       }
 
       // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
+      // memoized state to indicate that this work can be reused.
+      workInProgress.memoizedProps = newProps;
+      workInProgress.memoizedState = newState;
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6663,16 +6815,18 @@ var ReactFiberClassComponent = function(
   function updateClassInstance(current, workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
+    instance.props = oldProps;
+
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6696,94 +6850,27 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        current,
+    var newState = (instance.state = oldState);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
         workInProgress,
-        workInProgress.updateQueue,
-        instance,
+        updateQueue,
         newProps,
+        instance,
         renderExpirationTime
       );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
+      newState = workInProgress.memoizedState;
     }
 
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
         workInProgress,
-        instance,
-        newProps,
-        newState
+        getDerivedStateFromProps,
+        newProps
       );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue3 = workInProgress.updateQueue;
-      if (_updateQueue3 !== null) {
-        _updateQueue3.baseState = Object.assign(
-          {},
-          _updateQueue3.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue4 = workInProgress.updateQueue;
-      if (_updateQueue4 !== null) {
-        _updateQueue4.baseState = Object.assign(
-          {},
-          _updateQueue4.baseState,
-          derivedStateFromCatch
-        );
-      }
+      newState = workInProgress.memoizedState;
     }
 
     if (
@@ -6870,8 +6957,8 @@ var ReactFiberClassComponent = function(
 
       // If shouldComponentUpdate returned false, we should still update the
       // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
+      workInProgress.memoizedProps = newProps;
+      workInProgress.memoizedState = newState;
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6885,7 +6972,6 @@ var ReactFiberClassComponent = function(
 
   return {
     adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: constructClassInstance,
     mountClassInstance: mountClassInstance,
     resumeMountClassInstance: resumeMountClassInstance,
@@ -6893,7 +6979,7 @@ var ReactFiberClassComponent = function(
   };
 };
 
-var getCurrentFiberStackAddendum$1 =
+var getCurrentFiberStackAddendum$2 =
   ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
 
 var didWarnAboutMaps = void 0;
@@ -6932,7 +7018,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
       '"key" prop. See https://fb.me/react-warning-keys for ' +
       "more information." +
-      (getCurrentFiberStackAddendum$1() || "");
+      (getCurrentFiberStackAddendum$2() || "");
     if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
       return;
     }
@@ -6943,7 +7029,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
         '"key" prop. See https://fb.me/react-warning-keys for ' +
         "more information.%s",
-      getCurrentFiberStackAddendum$1()
+      getCurrentFiberStackAddendum$2()
     );
   };
 }
@@ -7040,7 +7126,7 @@ function throwOnInvalidObjectType(returnFiber, newChild) {
       addendum =
         " If you meant to render a collection of children, use an array " +
         "instead." +
-        (getCurrentFiberStackAddendum$1() || "");
+        (getCurrentFiberStackAddendum$2() || "");
     }
     invariant(
       false,
@@ -7058,7 +7144,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
     "you return a Component instead of <Component /> from render. " +
     "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$1() || "");
+    (getCurrentFiberStackAddendum$2() || "");
 
   if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
     return;
@@ -7070,7 +7156,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
       "you return a Component instead of <Component /> from render. " +
       "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$1() || ""
+    getCurrentFiberStackAddendum$2() || ""
   );
 }
 
@@ -7183,12 +7269,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, textContent, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -7198,7 +7284,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // Move based on index
       var existing = useFiber(current, element.props, expirationTime);
       existing.ref = coerceRef(returnFiber, current, element);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       {
         existing._debugSource = element._source;
         existing._debugOwner = element._owner;
@@ -7212,7 +7298,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       created.ref = coerceRef(returnFiber, current, element);
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     }
   }
@@ -7230,12 +7316,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, portal.children || [], expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -7249,12 +7335,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         key
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, fragment, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -7269,7 +7355,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     }
 
@@ -7282,7 +7368,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           _created.ref = coerceRef(returnFiber, null, newChild);
-          _created["return"] = returnFiber;
+          _created.return = returnFiber;
           return _created;
         }
         case REACT_PORTAL_TYPE: {
@@ -7291,7 +7377,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             returnFiber.mode,
             expirationTime
           );
-          _created2["return"] = returnFiber;
+          _created2.return = returnFiber;
           return _created2;
         }
       }
@@ -7303,7 +7389,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           null
         );
-        _created3["return"] = returnFiber;
+        _created3.return = returnFiber;
         return _created3;
       }
 
@@ -7514,7 +7600,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               "duplicated and/or omitted — the behavior is unsupported and " +
               "could change in a future version.%s",
             key,
-            getCurrentFiberStackAddendum$1()
+            getCurrentFiberStackAddendum$2()
           );
           break;
         default:
@@ -7659,7 +7745,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren["delete"](
+            existingChildren.delete(
               _newFiber2.key === null ? newIdx : _newFiber2.key
             );
           }
@@ -7712,7 +7798,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                 "Using Maps as children is unsupported and will likely yield " +
                   "unexpected results. Convert it to a sequence/iterable of keyed " +
                   "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$1()
+                getCurrentFiberStackAddendum$2()
               )
             : void 0;
           didWarnAboutMaps = true;
@@ -7838,7 +7924,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren["delete"](
+            existingChildren.delete(
               _newFiber4.key === null ? newIdx : _newFiber4.key
             );
           }
@@ -7877,7 +7963,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // the rest.
       deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
       var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
     // The existing first child is not a text node so we need to create one
@@ -7888,7 +7974,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created["return"] = returnFiber;
+    created.return = returnFiber;
     return created;
   }
 
@@ -7918,7 +8004,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           existing.ref = coerceRef(returnFiber, child, element);
-          existing["return"] = returnFiber;
+          existing.return = returnFiber;
           {
             existing._debugSource = element._source;
             existing._debugOwner = element._owner;
@@ -7941,7 +8027,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         element.key
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       var _created4 = createFiberFromElement(
@@ -7950,7 +8036,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4["return"] = returnFiber;
+      _created4.return = returnFiber;
       return _created4;
     }
   }
@@ -7974,7 +8060,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         ) {
           deleteRemainingChildren(returnFiber, child.sibling);
           var existing = useFiber(child, portal.children || [], expirationTime);
-          existing["return"] = returnFiber;
+          existing.return = returnFiber;
           return existing;
         } else {
           deleteRemainingChildren(returnFiber, child);
@@ -7991,7 +8077,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created["return"] = returnFiber;
+    created.return = returnFiber;
     return created;
   }
 
@@ -8143,7 +8229,7 @@ function cloneChildFibers(current, workInProgress) {
   );
   workInProgress.child = newChild;
 
-  newChild["return"] = workInProgress;
+  newChild.return = workInProgress;
   while (currentChild.sibling !== null) {
     currentChild = currentChild.sibling;
     newChild = newChild.sibling = createWorkInProgress(
@@ -8151,11 +8237,14 @@ function cloneChildFibers(current, workInProgress) {
       currentChild.pendingProps,
       currentChild.expirationTime
     );
-    newChild["return"] = workInProgress;
+    newChild.return = workInProgress;
   }
   newChild.sibling = null;
 }
 
+var getCurrentFiberStackAddendum =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+
 var didWarnAboutBadClass = void 0;
 var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
 var didWarnAboutStatelessRefs = void 0;
@@ -8199,8 +8288,6 @@ var ReactFiberBeginWork = function(
       memoizeState
     ),
     adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
-    callGetDerivedStateFromProps =
-      _ReactFiberClassCompo.callGetDerivedStateFromProps,
     constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
     mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
     resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
@@ -8252,9 +8339,20 @@ var ReactFiberBeginWork = function(
 
   function updateForwardRef(current, workInProgress) {
     var render = workInProgress.type.render;
-    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
+    var nextProps = workInProgress.pendingProps;
+    var ref = workInProgress.ref;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextProps) {
+      var currentRef = current !== null ? current.ref : null;
+      if (ref === currentRef) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+    }
+    var nextChildren = render(nextProps, ref);
     reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
     return workInProgress.child;
   }
 
@@ -8340,7 +8438,11 @@ var ReactFiberBeginWork = function(
     if (current === null) {
       if (workInProgress.stateNode === null) {
         // In the initial pass we might need to construct the instance.
-        constructClassInstance(workInProgress, workInProgress.pendingProps);
+        constructClassInstance(
+          workInProgress,
+          workInProgress.pendingProps,
+          renderExpirationTime
+        );
         mountClassInstance(workInProgress, renderExpirationTime);
 
         shouldUpdate = true;
@@ -8358,22 +8460,11 @@ var ReactFiberBeginWork = function(
         renderExpirationTime
       );
     }
-
-    // We processed the update queue inside updateClassInstance. It may have
-    // included some errors that were dispatched during the commit phase.
-    // TODO: Refactor class components so this is less awkward.
-    var didCaptureError = false;
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null && updateQueue.capturedValues !== null) {
-      shouldUpdate = true;
-      didCaptureError = true;
-    }
     return finishClassComponent(
       current,
       workInProgress,
       shouldUpdate,
       hasContext,
-      didCaptureError,
       renderExpirationTime
     );
   }
@@ -8383,12 +8474,13 @@ var ReactFiberBeginWork = function(
     workInProgress,
     shouldUpdate,
     hasContext,
-    didCaptureError,
     renderExpirationTime
   ) {
     // Refs should update even if shouldComponentUpdate returns false
     markRef(current, workInProgress);
 
+    var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
+
     if (!shouldUpdate && !didCaptureError) {
       // Context providers should defer to sCU for rendering
       if (hasContext) {
@@ -8484,29 +8576,26 @@ var ReactFiberBeginWork = function(
     pushHostRootContext(workInProgress);
     var updateQueue = workInProgress.updateQueue;
     if (updateQueue !== null) {
+      var nextProps = workInProgress.pendingProps;
       var prevState = workInProgress.memoizedState;
-      var state = processUpdateQueue(
-        current,
+      var prevChildren = prevState !== null ? prevState.element : null;
+      processUpdateQueue(
         workInProgress,
         updateQueue,
-        null,
+        nextProps,
         null,
         renderExpirationTime
       );
-      memoizeState(workInProgress, state);
-      updateQueue = workInProgress.updateQueue;
+      var nextState = workInProgress.memoizedState;
+      // Caution: React DevTools currently depends on this property
+      // being called "element".
+      var nextChildren = nextState.element;
 
-      var element = void 0;
-      if (updateQueue !== null && updateQueue.capturedValues !== null) {
-        // There's an uncaught error. Unmount the whole root.
-        element = null;
-      } else if (prevState === state) {
+      if (nextChildren === prevChildren) {
         // If the state is the same as before, that's a bailout because we had
         // no work that expires at this time.
         resetHydrationState();
         return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      } else {
-        element = state.element;
       }
       var root = workInProgress.stateNode;
       if (
@@ -8531,16 +8620,15 @@ var ReactFiberBeginWork = function(
         workInProgress.child = mountChildFibers(
           workInProgress,
           null,
-          element,
+          nextChildren,
           renderExpirationTime
         );
       } else {
         // Otherwise reset hydration state in case we aborted and resumed another
         // root.
         resetHydrationState();
-        reconcileChildren(current, workInProgress, element);
+        reconcileChildren(current, workInProgress, nextChildren);
       }
-      memoizeState(workInProgress, state);
       return workInProgress.child;
     }
     resetHydrationState();
@@ -8676,21 +8764,13 @@ var ReactFiberBeginWork = function(
       workInProgress.memoizedState =
         value.state !== null && value.state !== undefined ? value.state : null;
 
-      if (typeof Component.getDerivedStateFromProps === "function") {
-        var partialState = callGetDerivedStateFromProps(
+      var getDerivedStateFromProps = Component.getDerivedStateFromProps;
+      if (typeof getDerivedStateFromProps === "function") {
+        applyDerivedStateFromProps(
           workInProgress,
-          value,
-          props,
-          workInProgress.memoizedState
+          getDerivedStateFromProps,
+          props
         );
-
-        if (partialState !== null && partialState !== undefined) {
-          workInProgress.memoizedState = Object.assign(
-            {},
-            workInProgress.memoizedState,
-            partialState
-          );
-        }
       }
 
       // Push context providers early to prevent context stack mismatches.
@@ -8704,7 +8784,6 @@ var ReactFiberBeginWork = function(
         workInProgress,
         true,
         hasContext,
-        false,
         renderExpirationTime
       );
     } else {
@@ -8850,7 +8929,7 @@ var ReactFiberBeginWork = function(
     var fiber = workInProgress.child;
     if (fiber !== null) {
       // Set the return pointer of the child to the work-in-progress fiber.
-      fiber["return"] = workInProgress;
+      fiber.return = workInProgress;
     }
     while (fiber !== null) {
       var nextFiber = void 0;
@@ -8888,7 +8967,7 @@ var ReactFiberBeginWork = function(
                 // ancestor path already has sufficient priority.
                 break;
               }
-              node = node["return"];
+              node = node.return;
             }
             // Don't scan deeper than a matching consumer. When we render the
             // consumer, we'll continue scanning from that point. This way the
@@ -8910,7 +8989,7 @@ var ReactFiberBeginWork = function(
       }
       if (nextFiber !== null) {
         // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber["return"] = fiber;
+        nextFiber.return = fiber;
       } else {
         // No child. Traverse to next sibling.
         nextFiber = fiber;
@@ -8922,11 +9001,13 @@ var ReactFiberBeginWork = function(
           }
           var sibling = nextFiber.sibling;
           if (sibling !== null) {
+            // Set the return pointer of the sibling to the work-in-progress fiber.
+            sibling.return = nextFiber.return;
             nextFiber = sibling;
             break;
           }
           // No more siblings. Traverse up.
-          nextFiber = nextFiber["return"];
+          nextFiber = nextFiber.return;
         }
       }
       fiber = nextFiber;
@@ -8943,8 +9024,10 @@ var ReactFiberBeginWork = function(
 
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
+    var canBailOnProps = true;
 
     if (hasLegacyContextChanged()) {
+      canBailOnProps = false;
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (oldProps === newProps) {
@@ -8956,6 +9039,20 @@ var ReactFiberBeginWork = function(
     var newValue = newProps.value;
     workInProgress.memoizedProps = newProps;
 
+    {
+      var providerPropTypes = workInProgress.type.propTypes;
+
+      if (providerPropTypes) {
+        checkPropTypes(
+          providerPropTypes,
+          newProps,
+          "prop",
+          "Context.Provider",
+          getCurrentFiberStackAddendum
+        );
+      }
+    }
+
     var changedBits = void 0;
     if (oldProps === null) {
       // Initial render
@@ -8963,7 +9060,7 @@ var ReactFiberBeginWork = function(
     } else {
       if (oldProps.value === newProps.value) {
         // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children) {
+        if (oldProps.children === newProps.children && canBailOnProps) {
           workInProgress.stateNode = 0;
           pushProvider(workInProgress);
           return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8980,7 +9077,7 @@ var ReactFiberBeginWork = function(
           (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
         ) {
           // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children) {
+          if (oldProps.children === newProps.children && canBailOnProps) {
             workInProgress.stateNode = 0;
             pushProvider(workInProgress);
             return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -9005,7 +9102,7 @@ var ReactFiberBeginWork = function(
 
           if (changedBits === 0) {
             // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children) {
+            if (oldProps.children === newProps.children && canBailOnProps) {
               workInProgress.stateNode = 0;
               pushProvider(workInProgress);
               return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -9091,6 +9188,8 @@ var ReactFiberBeginWork = function(
     }
 
     var newChildren = render(newValue);
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
     reconcileChildren(current, workInProgress, newChildren);
     return workInProgress.child;
   }
@@ -9298,7 +9397,7 @@ var ReactFiberCompleteWork = function(
   function appendAllReturns(returns, workInProgress) {
     var node = workInProgress.stateNode;
     if (node) {
-      node["return"] = workInProgress;
+      node.return = workInProgress;
     }
     while (node !== null) {
       if (
@@ -9310,17 +9409,17 @@ var ReactFiberCompleteWork = function(
       } else if (node.tag === ReturnComponent) {
         returns.push(node.pendingProps.value);
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -9376,7 +9475,7 @@ var ReactFiberCompleteWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -9384,12 +9483,12 @@ var ReactFiberCompleteWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -9456,7 +9555,7 @@ var ReactFiberCompleteWork = function(
             // down its children. Instead, we'll get insertions from each child in
             // the portal directly.
           } else if (node.child !== null) {
-            node.child["return"] = node;
+            node.child.return = node;
             node = node.child;
             continue;
           }
@@ -9464,12 +9563,12 @@ var ReactFiberCompleteWork = function(
             return;
           }
           while (node.sibling === null) {
-            if (node["return"] === null || node["return"] === workInProgress) {
+            if (node.return === null || node.return === workInProgress) {
               return;
             }
-            node = node["return"];
+            node = node.return;
           }
-          node.sibling["return"] = node["return"];
+          node.sibling.return = node.return;
           node = node.sibling;
         }
       };
@@ -9595,20 +9694,6 @@ var ReactFiberCompleteWork = function(
       case ClassComponent: {
         // We are leaving this subtree, so pop context if any.
         popLegacyContextProvider(workInProgress);
-
-        // If this component caught an error, schedule an error log effect.
-        var instance = workInProgress.stateNode;
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null && updateQueue.capturedValues !== null) {
-          workInProgress.effectTag &= ~DidCapture;
-          if (typeof instance.componentDidCatch === "function") {
-            workInProgress.effectTag |= ErrLog;
-          } else {
-            // Normally we clear this in the commit phase, but since we did not
-            // schedule an effect, we need to reset it here.
-            updateQueue.capturedValues = null;
-          }
-        }
         return null;
       }
       case HostRoot: {
@@ -9628,11 +9713,6 @@ var ReactFiberCompleteWork = function(
           workInProgress.effectTag &= ~Placement;
         }
         updateHostContainer(workInProgress);
-
-        var _updateQueue = workInProgress.updateQueue;
-        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
-          workInProgress.effectTag |= ErrLog;
-        }
         return null;
       }
       case HostComponent: {
@@ -9647,13 +9727,13 @@ var ReactFiberCompleteWork = function(
           // have newProps so we'll have to reuse them.
           // TODO: Split the update API as separate for the props vs. children.
           // Even better would be if children weren't special cased at all tho.
-          var _instance = workInProgress.stateNode;
+          var instance = workInProgress.stateNode;
           var currentHostContext = getHostContext();
           // TODO: Experiencing an error where oldProps is null. Suggests a host
           // component is hitting the resume path. Figure out why. Possibly
           // related to `hidden`.
           var updatePayload = prepareUpdate(
-            _instance,
+            instance,
             type,
             oldProps,
             newProps,
@@ -9707,7 +9787,7 @@ var ReactFiberCompleteWork = function(
               markUpdate(workInProgress);
             }
           } else {
-            var _instance2 = createInstance(
+            var _instance = createInstance(
               type,
               newProps,
               rootContainerInstance,
@@ -9715,14 +9795,14 @@ var ReactFiberCompleteWork = function(
               workInProgress
             );
 
-            appendAllChildren(_instance2, workInProgress);
+            appendAllChildren(_instance, workInProgress);
 
             // Certain renderers require commit-time effects for initial mount.
             // (eg DOM renderer supports auto-focus for certain elements).
             // Make sure such renderers get scheduled for later work.
             if (
               finalizeInitialChildren(
-                _instance2,
+                _instance,
                 type,
                 newProps,
                 rootContainerInstance,
@@ -9731,7 +9811,7 @@ var ReactFiberCompleteWork = function(
             ) {
               markUpdate(workInProgress);
             }
-            workInProgress.stateNode = _instance2;
+            workInProgress.stateNode = _instance;
           }
 
           if (workInProgress.ref !== null) {
@@ -9838,139 +9918,6 @@ function createCapturedValue(value, source) {
   };
 }
 
-var ReactFiberUnwindWork = function(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-
-  function throwException(returnFiber, sourceFiber, rawValue) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-
-    var value = createCapturedValue(rawValue, sourceFiber);
-
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          // Uncaught error
-          var errorInfo = value;
-          ensureUpdateQueues(workInProgress);
-          var updateQueue = workInProgress.updateQueue;
-          updateQueue.capturedValues = [errorInfo];
-          workInProgress.effectTag |= ShouldCapture;
-          return;
-        }
-        case ClassComponent:
-          // Capture and retry
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
-          if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            ensureUpdateQueues(workInProgress);
-            var _updateQueue = workInProgress.updateQueue;
-            var capturedValues = _updateQueue.capturedValues;
-            if (capturedValues === null) {
-              _updateQueue.capturedValues = [value];
-            } else {
-              capturedValues.push(value);
-            }
-            workInProgress.effectTag |= ShouldCapture;
-            return;
-          }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress["return"];
-    } while (workInProgress !== null);
-  }
-
-  function unwindWork(workInProgress) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
-    }
-  }
-
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      default:
-        break;
-    }
-  }
-
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork
-  };
-};
-
 // Module provided by RN:
 /**
  * Intercept lifecycle errors and ensure they are shown with the correct stack
@@ -10256,7 +10203,14 @@ var ReactFiberCommitWork = function(
         }
         var updateQueue = finishedWork.updateQueue;
         if (updateQueue !== null) {
-          commitCallbacks(updateQueue, _instance2);
+          _instance2.props = finishedWork.memoizedProps;
+          _instance2.state = finishedWork.memoizedState;
+          commitUpdateQueue(
+            finishedWork,
+            updateQueue,
+            _instance2,
+            committedExpirationTime
+          );
         }
         return;
       }
@@ -10274,7 +10228,12 @@ var ReactFiberCommitWork = function(
                 break;
             }
           }
-          commitCallbacks(_updateQueue, _instance3);
+          commitUpdateQueue(
+            finishedWork,
+            _updateQueue,
+            _instance3,
+            committedExpirationTime
+          );
         }
         return;
       }
@@ -10311,81 +10270,17 @@ var ReactFiberCommitWork = function(
     }
   }
 
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case ClassComponent:
-        {
-          var ctor = finishedWork.type;
-          var _instance5 = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            updateQueue !== null && updateQueue.capturedValues !== null,
-            "An error logging effect should not have been scheduled if no errors " +
-              "were captured. This error is likely caused by a bug in React. " +
-              "Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-
-          if (typeof ctor.getDerivedStateFromCatch !== "function") {
-            // To preserve the preexisting retry behavior of error boundaries,
-            // we keep track of which ones already failed during this batch.
-            // This gets reset before we yield back to the browser.
-            // TODO: Warn in strict mode if getDerivedStateFromCatch is
-            // not defined.
-            markLegacyErrorBoundaryAsFailed(_instance5);
-          }
-
-          _instance5.props = finishedWork.memoizedProps;
-          _instance5.state = finishedWork.memoizedState;
-          for (var i = 0; i < capturedErrors.length; i++) {
-            var errorInfo = capturedErrors[i];
-            var _error = errorInfo.value;
-            var stack = errorInfo.stack;
-            logError(finishedWork, errorInfo);
-            _instance5.componentDidCatch(_error, {
-              componentStack: stack !== null ? stack : ""
-            });
-          }
-        }
-        break;
-      case HostRoot: {
-        var _updateQueue2 = finishedWork.updateQueue;
-        invariant(
-          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
-          "An error logging effect should not have been scheduled if no errors " +
-            "were captured. This error is likely caused by a bug in React. " +
-            "Please file an issue."
-        );
-        var _capturedErrors = _updateQueue2.capturedValues;
-        _updateQueue2.capturedValues = null;
-        for (var _i = 0; _i < _capturedErrors.length; _i++) {
-          var _errorInfo = _capturedErrors[_i];
-          logError(finishedWork, _errorInfo);
-          onUncaughtError(_errorInfo.value);
-        }
-        break;
-      }
-      default:
-        invariant(
-          false,
-          "This unit of work tag cannot capture errors.  This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (ref !== null) {
-      var _instance6 = finishedWork.stateNode;
+      var _instance5 = finishedWork.stateNode;
       var instanceToUse = void 0;
       switch (finishedWork.tag) {
         case HostComponent:
-          instanceToUse = getPublicInstance(_instance6);
+          instanceToUse = getPublicInstance(_instance5);
           break;
         default:
-          instanceToUse = _instance6;
+          instanceToUse = _instance5;
       }
       if (typeof ref === "function") {
         ref(instanceToUse);
@@ -10429,9 +10324,9 @@ var ReactFiberCommitWork = function(
     switch (current.tag) {
       case ClassComponent: {
         safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if (typeof _instance7.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance7);
+        var _instance6 = current.stateNode;
+        if (typeof _instance6.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance6);
         }
         return;
       }
@@ -10473,7 +10368,7 @@ var ReactFiberCommitWork = function(
         // If we don't use mutation we drill down into portals here instead.
         (!mutation || node.tag !== HostPortal)
       ) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -10481,12 +10376,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === root) {
+        if (node.return === null || node.return === root) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10497,11 +10392,11 @@ var ReactFiberCommitWork = function(
     // get GC:ed but we don't know which for sure which parent is the current
     // one so we'll settle for GC:ing the subtree of this child. This child
     // itself will be GC:ed when the parent updates the next time.
-    current["return"] = null;
+    current.return = null;
     current.child = null;
     if (current.alternate) {
       current.alternate.child = null;
-      current.alternate["return"] = null;
+      current.alternate.return = null;
     }
   }
 
@@ -10569,7 +10464,6 @@ var ReactFiberCommitWork = function(
 
         commitLifeCycles: commitLifeCycles,
         commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-        commitErrorLogging: commitErrorLogging,
         commitAttachRef: commitAttachRef,
         commitDetachRef: commitDetachRef
       };
@@ -10591,12 +10485,12 @@ var ReactFiberCommitWork = function(
     removeChildFromContainer = mutation.removeChildFromContainer;
 
   function getHostParentFiber(fiber) {
-    var parent = fiber["return"];
+    var parent = fiber.return;
     while (parent !== null) {
       if (isHostParent(parent)) {
         return parent;
       }
-      parent = parent["return"];
+      parent = parent.return;
     }
     invariant(
       false,
@@ -10621,14 +10515,14 @@ var ReactFiberCommitWork = function(
     siblings: while (true) {
       // If we didn't find anything, let's try the next sibling.
       while (node.sibling === null) {
-        if (node["return"] === null || isHostParent(node["return"])) {
+        if (node.return === null || isHostParent(node.return)) {
           // If we pop out of the root or hit the parent the fiber we are the
           // last sibling.
           return null;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
       while (node.tag !== HostComponent && node.tag !== HostText) {
         // If it is not host node and, we might have a host node inside it.
@@ -10642,7 +10536,7 @@ var ReactFiberCommitWork = function(
         if (node.child === null || node.tag === HostPortal) {
           continue siblings;
         } else {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
         }
       }
@@ -10710,7 +10604,7 @@ var ReactFiberCommitWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -10718,12 +10612,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === finishedWork) {
+        if (node.return === null || node.return === finishedWork) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10740,7 +10634,7 @@ var ReactFiberCommitWork = function(
 
     while (true) {
       if (!currentParentIsValid) {
-        var parent = node["return"];
+        var parent = node.return;
         findParent: while (true) {
           invariant(
             parent !== null,
@@ -10761,7 +10655,7 @@ var ReactFiberCommitWork = function(
               currentParentIsContainer = true;
               break findParent;
           }
-          parent = parent["return"];
+          parent = parent.return;
         }
         currentParentIsValid = true;
       }
@@ -10782,7 +10676,7 @@ var ReactFiberCommitWork = function(
         currentParent = node.stateNode.containerInfo;
         // Visit children because portals might contain host components.
         if (node.child !== null) {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
           continue;
         }
@@ -10790,7 +10684,7 @@ var ReactFiberCommitWork = function(
         commitUnmount(node);
         // Visit children because we may find more host components below.
         if (node.child !== null) {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
           continue;
         }
@@ -10799,17 +10693,17 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === current) {
+        if (node.return === null || node.return === current) {
           return;
         }
-        node = node["return"];
+        node = node.return;
         if (node.tag === HostPortal) {
           // When we go out of the portal, we need to restore the parent.
           // Since we don't keep a stack of them, we will search for it.
           currentParentIsValid = false;
         }
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10827,8 +10721,8 @@ var ReactFiberCommitWork = function(
         return;
       }
       case HostComponent: {
-        var _instance8 = finishedWork.stateNode;
-        if (_instance8 != null) {
+        var _instance7 = finishedWork.stateNode;
+        if (_instance7 != null) {
           // Commit the work prepared earlier.
           var newProps = finishedWork.memoizedProps;
           // For hydration we reuse the update path but we treat the oldProps
@@ -10841,7 +10735,7 @@ var ReactFiberCommitWork = function(
           finishedWork.updateQueue = null;
           if (updatePayload !== null) {
             commitUpdate(
-              _instance8,
+              _instance7,
               updatePayload,
               type,
               oldProps,
@@ -10892,7 +10786,6 @@ var ReactFiberCommitWork = function(
       commitDeletion: commitDeletion,
       commitWork: commitWork,
       commitLifeCycles: commitLifeCycles,
-      commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
     };
@@ -10901,6 +10794,208 @@ var ReactFiberCommitWork = function(
   }
 };
 
+var ReactFiberUnwindWork = function(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  markLegacyErrorBoundaryAsFailed,
+  isAlreadyFailedLegacyErrorBoundary,
+  onUncaughtError
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+
+  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+    var update = createUpdate(expirationTime);
+    // Unmount the root by rendering null.
+    update.tag = CaptureUpdate;
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    update.payload = { element: null };
+    var error = errorInfo.value;
+    update.callback = function() {
+      onUncaughtError(error);
+      logError(fiber, errorInfo);
+    };
+    return update;
+  }
+
+  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+    var update = createUpdate(expirationTime);
+    update.tag = CaptureUpdate;
+    var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
+    if (
+      enableGetDerivedStateFromCatch &&
+      typeof getDerivedStateFromCatch === "function"
+    ) {
+      var _error = errorInfo.value;
+      update.payload = function() {
+        return getDerivedStateFromCatch(_error);
+      };
+    }
+
+    var inst = fiber.stateNode;
+    if (inst !== null && typeof inst.componentDidCatch === "function") {
+      update.callback = function callback() {
+        if (
+          !enableGetDerivedStateFromCatch ||
+          getDerivedStateFromCatch !== "function"
+        ) {
+          // To preserve the preexisting retry behavior of error boundaries,
+          // we keep track of which ones already failed during this batch.
+          // This gets reset before we yield back to the browser.
+          // TODO: Warn in strict mode if getDerivedStateFromCatch is
+          // not defined.
+          markLegacyErrorBoundaryAsFailed(this);
+        }
+        var error = errorInfo.value;
+        var stack = errorInfo.stack;
+        logError(fiber, errorInfo);
+        this.componentDidCatch(error, {
+          componentStack: stack !== null ? stack : ""
+        });
+      };
+    }
+    return update;
+  }
+
+  function throwException(
+    returnFiber,
+    sourceFiber,
+    rawValue,
+    renderExpirationTime
+  ) {
+    // The source fiber did not complete.
+    sourceFiber.effectTag |= Incomplete;
+    // Its effect list is no longer valid.
+    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+
+    var value = createCapturedValue(rawValue, sourceFiber);
+
+    var workInProgress = returnFiber;
+    do {
+      switch (workInProgress.tag) {
+        case HostRoot: {
+          var _errorInfo = value;
+          workInProgress.effectTag |= ShouldCapture;
+          var update = createRootErrorUpdate(
+            workInProgress,
+            _errorInfo,
+            renderExpirationTime
+          );
+          enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
+          return;
+        }
+        case ClassComponent:
+          // Capture and retry
+          var errorInfo = value;
+          var ctor = workInProgress.type;
+          var _instance = workInProgress.stateNode;
+          if (
+            (workInProgress.effectTag & DidCapture) === NoEffect &&
+            ((typeof ctor.getDerivedStateFromCatch === "function" &&
+              enableGetDerivedStateFromCatch) ||
+              (_instance !== null &&
+                typeof _instance.componentDidCatch === "function" &&
+                !isAlreadyFailedLegacyErrorBoundary(_instance)))
+          ) {
+            workInProgress.effectTag |= ShouldCapture;
+            // Schedule the error boundary to re-render using updated state
+            var _update = createClassErrorUpdate(
+              workInProgress,
+              errorInfo,
+              renderExpirationTime
+            );
+            enqueueCapturedUpdate(
+              workInProgress,
+              _update,
+              renderExpirationTime
+            );
+            return;
+          }
+          break;
+        default:
+          break;
+      }
+      workInProgress = workInProgress.return;
+    } while (workInProgress !== null);
+  }
+
+  function unwindWork(workInProgress) {
+    switch (workInProgress.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(workInProgress);
+        var effectTag = workInProgress.effectTag;
+        if (effectTag & ShouldCapture) {
+          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var _effectTag = workInProgress.effectTag;
+        if (_effectTag & ShouldCapture) {
+          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        return null;
+      }
+      case HostPortal:
+        popHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        popProvider(workInProgress);
+        return null;
+      default:
+        return null;
+    }
+  }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      default:
+        break;
+    }
+  }
+
+  return {
+    throwException: throwException,
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork,
+    createRootErrorUpdate: createRootErrorUpdate,
+    createClassErrorUpdate: createClassErrorUpdate
+  };
+};
+
 var NO_CONTEXT = {};
 
 var ReactFiberHostContext = function(config, stack) {
@@ -11085,7 +11180,7 @@ var ReactFiberHydrationContext = function(config) {
 
     var childToDelete = createFiberFromHostInstanceForDeletion();
     childToDelete.stateNode = instance;
-    childToDelete["return"] = returnFiber;
+    childToDelete.return = returnFiber;
     childToDelete.effectTag = Deletion;
 
     // This might seem like it belongs on progressedFirstDeletion. However,
@@ -11283,13 +11378,13 @@ var ReactFiberHydrationContext = function(config) {
   }
 
   function popToNextHostParent(fiber) {
-    var parent = fiber["return"];
+    var parent = fiber.return;
     while (
       parent !== null &&
       parent.tag !== HostComponent &&
       parent.tag !== HostRoot
     ) {
-      parent = parent["return"];
+      parent = parent.return;
     }
     hydrationParentFiber = parent;
   }
@@ -11611,7 +11706,7 @@ var ReactFiberLegacyContext = function(stack) {
       if (isContextProvider(node)) {
         return node.stateNode.__reactInternalMemoizedMergedChildContext;
       }
-      var parent = node["return"];
+      var parent = node.return;
       invariant(
         parent,
         "Found unexpected detached subtree parent. " +
@@ -11884,11 +11979,15 @@ var ReactFiberScheduler = function(config) {
       legacyContext,
       newContext,
       scheduleWork,
-      isAlreadyFailedLegacyErrorBoundary
+      markLegacyErrorBoundaryAsFailed,
+      isAlreadyFailedLegacyErrorBoundary,
+      onUncaughtError
     ),
     throwException = _ReactFiberUnwindWork.throwException,
     unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork,
+    createRootErrorUpdate = _ReactFiberUnwindWork.createRootErrorUpdate,
+    createClassErrorUpdate = _ReactFiberUnwindWork.createClassErrorUpdate;
 
   var _ReactFiberCommitWork = ReactFiberCommitWork(
       config,
@@ -11905,7 +12004,6 @@ var ReactFiberScheduler = function(config) {
     commitDeletion = _ReactFiberCommitWork.commitDeletion,
     commitWork = _ReactFiberCommitWork.commitWork,
     commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
-    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
     commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
     commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
 
@@ -12003,10 +12101,10 @@ var ReactFiberScheduler = function(config) {
 
   function resetStack() {
     if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork["return"];
+      var interruptedWork = nextUnitOfWork.return;
       while (interruptedWork !== null) {
         unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork["return"];
+        interruptedWork = interruptedWork.return;
       }
     }
 
@@ -12131,10 +12229,6 @@ var ReactFiberScheduler = function(config) {
         );
       }
 
-      if (effectTag & ErrLog) {
-        commitErrorLogging(nextEffect, onUncaughtError);
-      }
-
       if (effectTag & Ref) {
         recordEffect();
         commitAttachRef(nextEffect);
@@ -12341,7 +12435,16 @@ var ReactFiberScheduler = function(config) {
     }
 
     // Check for pending updates.
-    var newExpirationTime = getUpdateExpirationTime(workInProgress);
+    var newExpirationTime = NoWork;
+    switch (workInProgress.tag) {
+      case HostRoot:
+      case ClassComponent: {
+        var updateQueue = workInProgress.updateQueue;
+        if (updateQueue !== null) {
+          newExpirationTime = updateQueue.expirationTime;
+        }
+      }
+    }
 
     // TODO: Calls need to visit stateNode
 
@@ -12374,7 +12477,7 @@ var ReactFiberScheduler = function(config) {
         ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
       }
 
-      var returnFiber = workInProgress["return"];
+      var returnFiber = workInProgress.return;
       var siblingFiber = workInProgress.sibling;
 
       if ((workInProgress.effectTag & Incomplete) === NoEffect) {
@@ -12616,13 +12719,19 @@ var ReactFiberScheduler = function(config) {
           break;
         }
 
+        {
+          // Reset global debug state
+          // We assume this is defined in DEV
+          resetCurrentlyProcessingQueue();
+        }
+
         if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
           replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
         }
 
         var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber["return"];
+        var returnFiber = sourceFiber.return;
         if (returnFiber === null) {
           // This is the root. The root could capture its own errors. However,
           // we don't know if it errors before or after we pushed the host
@@ -12634,7 +12743,12 @@ var ReactFiberScheduler = function(config) {
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(returnFiber, sourceFiber, thrownValue);
+        throwException(
+          returnFiber,
+          sourceFiber,
+          thrownValue,
+          nextRenderExpirationTime
+        );
         nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
       break;
@@ -12682,31 +12796,13 @@ var ReactFiberScheduler = function(config) {
     }
   }
 
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    // TODO: We only support dispatching errors.
-    var capturedValue = createCapturedValue(value, sourceFiber);
-    var update = {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: false,
-      isForced: false,
-      capturedValue: capturedValue,
-      next: null
-    };
-    insertUpdateIntoFiber(boundaryFiber, update);
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-
   function dispatch(sourceFiber, value, expirationTime) {
     invariant(
       !isWorking || isCommitting,
       "dispatch: Cannot dispatch during the render phase."
     );
 
-    // TODO: Handle arrays
-
-    var fiber = sourceFiber["return"];
+    var fiber = sourceFiber.return;
     while (fiber !== null) {
       switch (fiber.tag) {
         case ClassComponent:
@@ -12717,22 +12813,44 @@ var ReactFiberScheduler = function(config) {
             (typeof instance.componentDidCatch === "function" &&
               !isAlreadyFailedLegacyErrorBoundary(instance))
           ) {
-            scheduleCapture(sourceFiber, fiber, value, expirationTime);
+            var errorInfo = createCapturedValue(value, sourceFiber);
+            var update = createClassErrorUpdate(
+              fiber,
+              errorInfo,
+              expirationTime
+            );
+            enqueueUpdate(fiber, update, expirationTime);
+            scheduleWork(fiber, expirationTime);
             return;
           }
           break;
-        // TODO: Handle async boundaries
-        case HostRoot:
-          scheduleCapture(sourceFiber, fiber, value, expirationTime);
+        case HostRoot: {
+          var _errorInfo = createCapturedValue(value, sourceFiber);
+          var _update = createRootErrorUpdate(
+            fiber,
+            _errorInfo,
+            expirationTime
+          );
+          enqueueUpdate(fiber, _update, expirationTime);
+          scheduleWork(fiber, expirationTime);
           return;
+        }
       }
-      fiber = fiber["return"];
+      fiber = fiber.return;
     }
 
     if (sourceFiber.tag === HostRoot) {
       // Error was thrown at the root. There is no parent, so the root
       // itself should capture it.
-      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
+      var rootFiber = sourceFiber;
+      var _errorInfo2 = createCapturedValue(value, rootFiber);
+      var _update2 = createRootErrorUpdate(
+        rootFiber,
+        _errorInfo2,
+        expirationTime
+      );
+      enqueueUpdate(rootFiber, _update2, expirationTime);
+      scheduleWork(rootFiber, expirationTime);
     }
   }
 
@@ -12860,7 +12978,7 @@ var ReactFiberScheduler = function(config) {
           node.alternate.expirationTime = expirationTime;
         }
       }
-      if (node["return"] === null) {
+      if (node.return === null) {
         if (node.tag === HostRoot) {
           var root = node.stateNode;
           if (
@@ -12901,7 +13019,7 @@ var ReactFiberScheduler = function(config) {
           return;
         }
       }
-      node = node["return"];
+      node = node.return;
     }
   }
 
@@ -13530,9 +13648,14 @@ var ReactFiberReconciler$1 = function(config) {
       }
     }
 
+    var update = createUpdate(expirationTime);
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    update.payload = { element: element };
+
     callback = callback === undefined ? null : callback;
-    {
-      !(callback === null || typeof callback === "function")
+    if (callback !== null) {
+      !(typeof callback === "function")
         ? warning(
             false,
             "render(...): Expected the last optional `callback` argument to be a " +
@@ -13540,20 +13663,11 @@ var ReactFiberReconciler$1 = function(config) {
             callback
           )
         : void 0;
+      update.callback = callback;
     }
+    enqueueUpdate(current, update, expirationTime);
 
-    var update = {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: callback,
-      isReplace: false,
-      isForced: false,
-      capturedValue: null,
-      next: null
-    };
-    insertUpdateIntoFiber(current, update);
     scheduleWork(current, expirationTime);
-
     return expirationTime;
   }
 
@@ -13731,8 +13845,8 @@ var ReactFiberReconciler$3 =
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3["default"]
-  ? ReactFiberReconciler$3["default"]
+var reactReconciler = ReactFiberReconciler$3.default
+  ? ReactFiberReconciler$3.default
   : ReactFiberReconciler$3;
 
 function _classCallCheck$1(instance, Constructor) {
@@ -14354,7 +14468,7 @@ var ReactNativeRenderer = {
     if (root) {
       // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
       NativeRenderer.updateContainer(null, root, null, function() {
-        roots["delete"](containerTag);
+        roots.delete(containerTag);
       });
     }
   },
@@ -14421,8 +14535,8 @@ var ReactNativeRenderer$3 =
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var reactNativeRenderer = ReactNativeRenderer$3["default"]
-  ? ReactNativeRenderer$3["default"]
+var reactNativeRenderer = ReactNativeRenderer$3.default
+  ? ReactNativeRenderer$3.default
   : ReactNativeRenderer$3;
 
 module.exports = reactNativeRenderer;
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
index f7eb9e09f0dc..09031ec3a6c9 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
+ * @providesModule ReactNativeRenderer-prod
  * @preventMunge
  */
 
@@ -306,7 +307,7 @@ function getListener(inst, registrationName) {
   return listener;
 }
 function getParent(inst) {
-  do inst = inst["return"];
+  do inst = inst.return;
   while (inst && 5 !== inst.tag);
   return inst ? inst : null;
 }
@@ -1122,21 +1123,17 @@ var ReactNativeEventEmitter = Object.freeze({
   }
 });
 RCTEventEmitter.register(ReactNativeEventEmitter);
-var hasSymbol = "function" === typeof Symbol && Symbol["for"],
-  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
-  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
-  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
-  REACT_STRICT_MODE_TYPE = hasSymbol
-    ? Symbol["for"]("react.strict_mode")
-    : 60108,
-  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
-  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
-  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
-  REACT_FORWARD_REF_TYPE = hasSymbol
-    ? Symbol["for"]("react.forward_ref")
-    : 60112,
+var hasSymbol = "function" === typeof Symbol && Symbol.for,
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
+  REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 60104,
+  REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 60105,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for("react.forward_ref") : 60112,
   MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
 function getIteratorFn(maybeIterable) {
   if (null === maybeIterable || "undefined" === typeof maybeIterable)
@@ -1210,7 +1207,7 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
         JSCompiler_inline_result = "";
     }
     info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
+    workInProgress = workInProgress.return;
   } while (workInProgress);
   return info;
 }
@@ -1469,11 +1466,11 @@ var ReactCurrentOwner =
   React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
 function isFiberMountedImpl(fiber) {
   var node = fiber;
-  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
+  if (fiber.alternate) for (; node.return; ) node = node.return;
   else {
     if (0 !== (node.effectTag & 2)) return 1;
-    for (; node["return"]; )
-      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
+    for (; node.return; )
+      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
   }
   return 3 === node.tag ? 2 : 3;
 }
@@ -1500,7 +1497,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       1 === alternate ? null : fiber
     );
   for (var a = fiber, b = alternate; ; ) {
-    var parentA = a["return"],
+    var parentA = a.return,
       parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) break;
     if (parentA.child === parentB.child) {
@@ -1511,7 +1508,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       }
       invariant(!1, "Unable to find node on an unmounted component.");
     }
-    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
+    if (a.return !== b.return) (a = parentA), (b = parentB);
     else {
       child = !1;
       for (var _child = parentA.child; _child; ) {
@@ -1564,14 +1561,14 @@ function findCurrentHostFiber(parent) {
   if (!parent) return null;
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child["return"] = node), (node = node.child);
+    if (node.child) (node.child.return = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -1583,14 +1580,14 @@ function findCurrentHostFiberWithNoPortals(parent) {
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
     if (node.child && 4 !== node.tag)
-      (node.child["return"] = node), (node = node.child);
+      (node.child.return = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -1599,8 +1596,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
   this.key = key;
-  this.stateNode = this.type = null;
-  this.sibling = this.child = this["return"] = null;
+  this.sibling = this.child = this.return = this.stateNode = this.type = null;
   this.index = 0;
   this.ref = null;
   this.pendingProps = pendingProps;
@@ -1765,164 +1761,282 @@ function onCommitUnmount(fiber) {
 new Set();
 function createUpdateQueue(baseState) {
   return {
-    baseState: baseState,
     expirationTime: 0,
-    first: null,
-    last: null,
-    callbackList: null,
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null,
+    hasForceUpdate: !1
+  };
+}
+function cloneUpdateQueue(currentQueue) {
+  return {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
     hasForceUpdate: !1,
-    isInitialized: !1,
-    capturedValues: null
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+    tag: 0,
+    payload: null,
+    callback: null,
+    next: null,
+    nextEffect: null
   };
 }
-function insertUpdateIntoQueue(queue, update) {
-  null === queue.last
-    ? (queue.first = queue.last = update)
-    : ((queue.last.next = update), (queue.last = update));
+function appendUpdateToQueue(queue, update, expirationTime) {
+  null === queue.lastUpdate
+    ? (queue.firstUpdate = queue.lastUpdate = update)
+    : ((queue.lastUpdate.next = update), (queue.lastUpdate = update));
+  if (0 === queue.expirationTime || queue.expirationTime > expirationTime)
+    queue.expirationTime = expirationTime;
+}
+function enqueueUpdate(fiber, update, expirationTime) {
+  var alternate = fiber.alternate;
+  if (null === alternate) {
+    var queue1 = fiber.updateQueue;
+    var queue2 = null;
+    null === queue1 &&
+      (queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState));
+  } else
+    (queue1 = fiber.updateQueue),
+      (queue2 = alternate.updateQueue),
+      null === queue1
+        ? null === queue2
+          ? ((queue1 = fiber.updateQueue = createUpdateQueue(
+              fiber.memoizedState
+            )),
+            (queue2 = alternate.updateQueue = createUpdateQueue(
+              alternate.memoizedState
+            )))
+          : (queue1 = fiber.updateQueue = cloneUpdateQueue(queue2))
+        : null === queue2 &&
+          (queue2 = alternate.updateQueue = cloneUpdateQueue(queue1));
+  null === queue2 || queue1 === queue2
+    ? appendUpdateToQueue(queue1, update, expirationTime)
+    : null === queue1.lastUpdate || null === queue2.lastUpdate
+      ? (appendUpdateToQueue(queue1, update, expirationTime),
+        appendUpdateToQueue(queue2, update, expirationTime))
+      : (appendUpdateToQueue(queue1, update, expirationTime),
+        (queue2.lastUpdate = update));
+}
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  var workInProgressQueue = workInProgress.updateQueue;
+  workInProgressQueue =
+    null === workInProgressQueue
+      ? (workInProgress.updateQueue = createUpdateQueue(
+          workInProgress.memoizedState
+        ))
+      : ensureWorkInProgressQueueIsAClone(workInProgress, workInProgressQueue);
+  null === workInProgressQueue.lastCapturedUpdate
+    ? (workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update)
+    : ((workInProgressQueue.lastCapturedUpdate.next = update),
+      (workInProgressQueue.lastCapturedUpdate = update));
   if (
-    0 === queue.expirationTime ||
-    queue.expirationTime > update.expirationTime
+    0 === workInProgressQueue.expirationTime ||
+    workInProgressQueue.expirationTime > renderExpirationTime
   )
-    queue.expirationTime = update.expirationTime;
-}
-var q1 = void 0,
-  q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  var alternateFiber = fiber.alternate,
-    queue1 = fiber.updateQueue;
-  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
-  null !== alternateFiber
-    ? ((fiber = alternateFiber.updateQueue),
-      null === fiber &&
-        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
-    : (fiber = null);
-  q1 = queue1;
-  q2 = fiber !== queue1 ? fiber : null;
+    workInProgressQueue.expirationTime = renderExpirationTime;
 }
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  fiber = q1;
-  var queue2 = q2;
-  null === queue2
-    ? insertUpdateIntoQueue(fiber, update)
-    : null === fiber.last || null === queue2.last
-      ? (insertUpdateIntoQueue(fiber, update),
-        insertUpdateIntoQueue(queue2, update))
-      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  null !== current &&
+    queue === current.updateQueue &&
+    (queue = workInProgress.updateQueue = cloneUpdateQueue(queue));
+  return queue;
 }
-function getStateFromUpdate(update, instance, prevState, props) {
-  update = update.partialState;
-  return "function" === typeof update
-    ? update.call(instance, prevState, props)
-    : update;
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case 1:
+      return (
+        (workInProgress = update.payload),
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress
+      );
+    case 3:
+      workInProgress.effectTag = (workInProgress.effectTag & -1025) | 64;
+    case 0:
+      workInProgress = update.payload;
+      nextProps =
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress;
+      if (null === nextProps || void 0 === nextProps) break;
+      return Object.assign({}, prevState, nextProps);
+    case 2:
+      queue.hasForceUpdate = !0;
+  }
+  return prevState;
 }
 function processUpdateQueue(
-  current,
   workInProgress,
   queue,
-  instance,
   props,
+  instance,
   renderExpirationTime
 ) {
-  null !== current &&
-    current.updateQueue === queue &&
-    (queue = workInProgress.updateQueue = {
-      baseState: queue.baseState,
-      expirationTime: queue.expirationTime,
-      first: queue.first,
-      last: queue.last,
-      isInitialized: queue.isInitialized,
-      capturedValues: queue.capturedValues,
-      callbackList: null,
-      hasForceUpdate: !1
-    });
-  queue.expirationTime = 0;
-  queue.isInitialized
-    ? (current = queue.baseState)
-    : ((current = queue.baseState = workInProgress.memoizedState),
-      (queue.isInitialized = !0));
-  for (
-    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
-    null !== update;
-
+  if (
+    !(0 === queue.expirationTime || queue.expirationTime > renderExpirationTime)
   ) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        remainingExpirationTime > updateExpirationTime
-      )
-        queue.expirationTime = updateExpirationTime;
-      didSkip || ((didSkip = !0), (queue.baseState = current));
-    } else {
-      didSkip ||
-        ((queue.first = update.next),
-        null === queue.first && (queue.last = null));
-      if (update.isReplace)
-        (current = getStateFromUpdate(update, instance, current, props)),
-          (dontMutatePrevState = !0);
-      else if (
-        (updateExpirationTime = getStateFromUpdate(
+    queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+    for (
+      var newBaseState = queue.baseState,
+        newFirstUpdate = null,
+        newExpirationTime = 0,
+        update = queue.firstUpdate,
+        resultState = newBaseState;
+      null !== update;
+
+    ) {
+      var updateExpirationTime = update.expirationTime;
+      if (updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === newFirstUpdate &&
+            ((newFirstUpdate = update), (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > updateExpirationTime)
+        )
+          newExpirationTime = updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
           update,
-          instance,
-          current,
-          props
-        ))
-      )
-        (current = dontMutatePrevState
-          ? Object.assign({}, current, updateExpirationTime)
-          : Object.assign(current, updateExpirationTime)),
-          (dontMutatePrevState = !1);
-      update.isForced && (queue.hasForceUpdate = !0);
-      null !== update.callback &&
-        ((updateExpirationTime = queue.callbackList),
-        null === updateExpirationTime &&
-          (updateExpirationTime = queue.callbackList = []),
-        updateExpirationTime.push(update));
-      null !== update.capturedValue &&
-        ((updateExpirationTime = queue.capturedValues),
-        null === updateExpirationTime
-          ? (queue.capturedValues = [update.capturedValue])
-          : updateExpirationTime.push(update.capturedValue));
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastEffect
+              ? (queue.firstEffect = queue.lastEffect = update)
+              : ((queue.lastEffect.nextEffect = update),
+                (queue.lastEffect = update)));
+      update = update.next;
+    }
+    updateExpirationTime = null;
+    for (update = queue.firstCapturedUpdate; null !== update; ) {
+      var _updateExpirationTime = update.expirationTime;
+      if (_updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === updateExpirationTime &&
+            ((updateExpirationTime = update),
+            null === newFirstUpdate && (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > _updateExpirationTime)
+        )
+          newExpirationTime = _updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
+          update,
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastCapturedEffect
+              ? (queue.firstCapturedEffect = queue.lastCapturedEffect = update)
+              : ((queue.lastCapturedEffect.nextEffect = update),
+                (queue.lastCapturedEffect = update)));
+      update = update.next;
     }
-    update = update.next;
+    null === newFirstUpdate && (queue.lastUpdate = null);
+    null === updateExpirationTime
+      ? (queue.lastCapturedUpdate = null)
+      : (workInProgress.effectTag |= 32);
+    null === newFirstUpdate &&
+      null === updateExpirationTime &&
+      (newBaseState = resultState);
+    queue.baseState = newBaseState;
+    queue.firstUpdate = newFirstUpdate;
+    queue.firstCapturedUpdate = updateExpirationTime;
+    queue.expirationTime = newExpirationTime;
+    workInProgress.memoizedState = resultState;
   }
-  null !== queue.callbackList
-    ? (workInProgress.effectTag |= 32)
-    : null !== queue.first ||
-      queue.hasForceUpdate ||
-      null !== queue.capturedValues ||
-      (workInProgress.updateQueue = null);
-  didSkip || (queue.baseState = current);
-  return current;
 }
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (null !== callbackList)
-    for (
-      queue.callbackList = null, queue = 0;
-      queue < callbackList.length;
-      queue++
-    ) {
-      var update = callbackList[queue],
-        _callback = update.callback;
-      update.callback = null;
-      invariant(
-        "function" === typeof _callback,
-        "Invalid argument passed as callback. Expected a function. Instead received: %s",
-        _callback
-      );
-      _callback.call(context);
-    }
+function callCallback(callback, context) {
+  invariant(
+    "function" === typeof callback,
+    "Invalid argument passed as callback. Expected a function. Instead received: %s",
+    callback
+  );
+  callback.call(context);
+}
+function commitUpdateQueue(finishedWork, finishedQueue, instance) {
+  null !== finishedQueue.firstCapturedUpdate &&
+    (null !== finishedQueue.lastUpdate &&
+      ((finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate),
+      (finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate)),
+    (finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null));
+  finishedWork = finishedQueue.firstEffect;
+  for (
+    finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+    null !== finishedWork;
+
+  ) {
+    var _callback3 = finishedWork.callback;
+    null !== _callback3 &&
+      ((finishedWork.callback = null), callCallback(_callback3, instance));
+    finishedWork = finishedWork.nextEffect;
+  }
+  finishedWork = finishedQueue.firstCapturedEffect;
+  for (
+    finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+    null !== finishedWork;
+
+  )
+    (finishedQueue = finishedWork.callback),
+      null !== finishedQueue &&
+        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
+      (finishedWork = finishedWork.nextEffect);
+}
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+  getDerivedStateFromProps = getDerivedStateFromProps(nextProps, prevState);
+  prevState =
+    null === getDerivedStateFromProps || void 0 === getDerivedStateFromProps
+      ? prevState
+      : Object.assign({}, prevState, getDerivedStateFromProps);
+  workInProgress.memoizedState = prevState;
+  workInProgress = workInProgress.updateQueue;
+  null !== workInProgress &&
+    0 === workInProgress.expirationTime &&
+    (workInProgress.baseState = prevState);
 }
 function ReactFiberClassComponent(
   legacyContext,
   scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState
+  computeExpirationForFiber
 ) {
   function checkShouldComponentUpdate(
     workInProgress,
@@ -1933,9 +2047,8 @@ function ReactFiberClassComponent(
     newContext
   ) {
     if (
-      null === oldProps ||
-      (null !== workInProgress.updateQueue &&
-        workInProgress.updateQueue.hasForceUpdate)
+      null !== workInProgress.updateQueue &&
+      workInProgress.updateQueue.hasForceUpdate
     )
       return !0;
     var instance = workInProgress.stateNode;
@@ -1948,7 +2061,7 @@ function ReactFiberClassComponent(
         : !0;
   }
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
+    instance.updater = classComponentUpdater;
     workInProgress.stateNode = instance;
     instance._reactInternalFiber = workInProgress;
   }
@@ -1964,78 +2077,52 @@ function ReactFiberClassComponent(
     "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
       instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
     instance.state !== workInProgress &&
-      updater.enqueueReplaceState(instance, instance.state, null);
-  }
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    workInProgress = workInProgress.type;
-    if ("function" === typeof workInProgress.getDerivedStateFromProps)
-      return workInProgress.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
   }
   var cacheContext = legacyContext.cacheContext,
     getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged,
-    updater = {
+    classComponentUpdater = {
       isMounted: isMounted,
-      enqueueSetState: function(instance, partialState, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: partialState,
-          callback: callback,
-          isReplace: !1,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueSetState: function(inst, payload, callback) {
+        inst = inst._reactInternalFiber;
+        var expirationTime = computeExpirationForFiber(inst),
+          update = createUpdate(expirationTime);
+        update.payload = payload;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, expirationTime);
+        scheduleWork(inst, expirationTime);
       },
-      enqueueReplaceState: function(instance, state, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: state,
-          callback: callback,
-          isReplace: !0,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueReplaceState: function(inst, payload, callback) {
+        inst = inst._reactInternalFiber;
+        var expirationTime = computeExpirationForFiber(inst),
+          update = createUpdate(expirationTime);
+        update.tag = 1;
+        update.payload = payload;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, expirationTime);
+        scheduleWork(inst, expirationTime);
       },
-      enqueueForceUpdate: function(instance, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: null,
-          callback: callback,
-          isReplace: !1,
-          isForced: !0,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueForceUpdate: function(inst, callback) {
+        inst = inst._reactInternalFiber;
+        var expirationTime = computeExpirationForFiber(inst),
+          update = createUpdate(expirationTime);
+        update.tag = 2;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, expirationTime);
+        scheduleWork(inst, expirationTime);
       }
     };
   return {
     adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: function(workInProgress, props) {
       var ctor = workInProgress.type,
         unmaskedContext = getUnmaskedContext(workInProgress),
@@ -2043,25 +2130,15 @@ function ReactFiberClassComponent(
         context = needsContext
           ? getMaskedContext(workInProgress, unmaskedContext)
           : emptyObject;
-      ctor = new ctor(props, context);
-      var state =
-        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
-      adoptClassInstance(workInProgress, ctor);
-      workInProgress.memoizedState = state;
-      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
-      null !== props &&
-        void 0 !== props &&
-        (workInProgress.memoizedState = Object.assign(
-          {},
-          workInProgress.memoizedState,
-          props
-        ));
+      props = new ctor(props, context);
+      workInProgress.memoizedState =
+        null !== props.state && void 0 !== props.state ? props.state : null;
+      adoptClassInstance(workInProgress, props);
       needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return ctor;
+      return props;
     },
     mountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        current = workInProgress.alternate,
         instance = workInProgress.stateNode,
         props = workInProgress.pendingProps,
         unmaskedContext = getUnmaskedContext(workInProgress);
@@ -2069,6 +2146,20 @@ function ReactFiberClassComponent(
       instance.state = workInProgress.memoizedState;
       instance.refs = emptyObject;
       instance.context = getMaskedContext(workInProgress, unmaskedContext);
+      unmaskedContext = workInProgress.updateQueue;
+      null !== unmaskedContext &&
+        (processUpdateQueue(
+          workInProgress,
+          unmaskedContext,
+          props,
+          instance,
+          renderExpirationTime
+        ),
+        (instance.state = workInProgress.memoizedState));
+      unmaskedContext = workInProgress.type.getDerivedStateFromProps;
+      "function" === typeof unmaskedContext &&
+        (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+        (instance.state = workInProgress.memoizedState));
       "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate ||
         ("function" !== typeof instance.UNSAFE_componentWillMount &&
@@ -2079,32 +2170,36 @@ function ReactFiberClassComponent(
         "function" === typeof instance.UNSAFE_componentWillMount &&
           instance.UNSAFE_componentWillMount(),
         ctor !== instance.state &&
-          updater.enqueueReplaceState(instance, instance.state, null),
-        (ctor = workInProgress.updateQueue),
-        null !== ctor &&
-          (instance.state = processUpdateQueue(
-            current,
-            workInProgress,
-            ctor,
+          classComponentUpdater.enqueueReplaceState(
             instance,
+            instance.state,
+            null
+          ),
+        (unmaskedContext = workInProgress.updateQueue),
+        null !== unmaskedContext &&
+          (processUpdateQueue(
+            workInProgress,
+            unmaskedContext,
             props,
+            instance,
             renderExpirationTime
-          )));
+          ),
+          (instance.state = workInProgress.memoizedState)));
       "function" === typeof instance.componentDidMount &&
         (workInProgress.effectTag |= 4);
     },
     resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
+        instance = workInProgress.stateNode,
+        oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps;
+      instance.props = oldProps;
+      var oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2115,43 +2210,29 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              null,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
+      var oldState = workInProgress.memoizedState;
+      oldContext = instance.state = oldState;
+      var updateQueue = workInProgress.updateQueue;
+      null !== updateQueue &&
+        (processUpdateQueue(
           workInProgress,
-          instance,
+          updateQueue,
           newProps,
+          instance,
           renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue = workInProgress.updateQueue;
-        null !== _updateQueue &&
-          (_updateQueue.baseState = Object.assign(
-            {},
-            _updateQueue.baseState,
-            derivedStateFromProps
-          ));
-      }
+        ),
+        (oldContext = workInProgress.memoizedState));
+      "function" === typeof getDerivedStateFromProps &&
+        (applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        ),
+        (oldContext = workInProgress.memoizedState));
       if (
         !(
           oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
+          oldState !== oldContext ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2162,12 +2243,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4),
           !1
         );
-      (oldProps = checkShouldComponentUpdate(
+      (renderExpirationTime = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
+        oldState,
         oldContext,
-        renderExpirationTime,
         newUnmaskedContext
       ))
         ? (ctor ||
@@ -2181,12 +2262,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4))
         : ("function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
+          (workInProgress.memoizedProps = newProps),
+          (workInProgress.memoizedState = oldContext));
       instance.props = newProps;
-      instance.state = renderExpirationTime;
+      instance.state = oldContext;
       instance.context = newUnmaskedContext;
-      return oldProps;
+      return renderExpirationTime;
     },
     updateClassInstance: function(
       current,
@@ -2194,16 +2275,16 @@ function ReactFiberClassComponent(
       renderExpirationTime
     ) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
+        instance = workInProgress.stateNode,
+        oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps;
+      instance.props = oldProps;
+      var oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2215,42 +2296,28 @@ function ReactFiberClassComponent(
             newUnmaskedContext
           ));
       oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              current,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
+      var newState = (instance.state = oldContext),
+        updateQueue = workInProgress.updateQueue;
+      null !== updateQueue &&
+        (processUpdateQueue(
           workInProgress,
-          instance,
+          updateQueue,
           newProps,
+          instance,
           renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue3 = workInProgress.updateQueue;
-        null !== _updateQueue3 &&
-          (_updateQueue3.baseState = Object.assign(
-            {},
-            _updateQueue3.baseState,
-            derivedStateFromProps
-          ));
-      }
+        ),
+        (newState = workInProgress.memoizedState));
+      "function" === typeof getDerivedStateFromProps &&
+        (applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        ),
+        (newState = workInProgress.memoizedState));
       if (
         !(
           oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
+          oldContext !== newState ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2264,15 +2331,15 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
+            (workInProgress.effectTag |= 256),
           !1
         );
-      (derivedStateFromProps = checkShouldComponentUpdate(
+      (renderExpirationTime = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
         oldContext,
-        renderExpirationTime,
+        newState,
         newUnmaskedContext
       ))
         ? (ctor ||
@@ -2281,19 +2348,19 @@ function ReactFiberClassComponent(
             ("function" === typeof instance.componentWillUpdate &&
               instance.componentWillUpdate(
                 newProps,
-                renderExpirationTime,
+                newState,
                 newUnmaskedContext
               ),
             "function" === typeof instance.UNSAFE_componentWillUpdate &&
               instance.UNSAFE_componentWillUpdate(
                 newProps,
-                renderExpirationTime,
+                newState,
                 newUnmaskedContext
               )),
           "function" === typeof instance.componentDidUpdate &&
             (workInProgress.effectTag |= 4),
           "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 2048))
+            (workInProgress.effectTag |= 256))
         : ("function" !== typeof instance.componentDidUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
@@ -2301,13 +2368,13 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
+            (workInProgress.effectTag |= 256),
+          (workInProgress.memoizedProps = newProps),
+          (workInProgress.memoizedState = newState));
       instance.props = newProps;
-      instance.state = renderExpirationTime;
+      instance.state = newState;
       instance.context = newUnmaskedContext;
-      return derivedStateFromProps;
+      return renderExpirationTime;
     }
   };
 }
@@ -2431,11 +2498,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, textContent, expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function updateElement(returnFiber, current, element, expirationTime) {
@@ -2443,7 +2510,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       return (
         (expirationTime = useFiber(current, element.props, expirationTime)),
         (expirationTime.ref = coerceRef(returnFiber, current, element)),
-        (expirationTime["return"] = returnFiber),
+        (expirationTime.return = returnFiber),
         expirationTime
       );
     expirationTime = createFiberFromElement(
@@ -2452,7 +2519,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       expirationTime
     );
     expirationTime.ref = coerceRef(returnFiber, current, element);
-    expirationTime["return"] = returnFiber;
+    expirationTime.return = returnFiber;
     return expirationTime;
   }
   function updatePortal(returnFiber, current, portal, expirationTime) {
@@ -2468,11 +2535,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, portal.children || [], expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function updateFragment(returnFiber, current, fragment, expirationTime, key) {
@@ -2484,11 +2551,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           key
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, fragment, expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function createChild(returnFiber, newChild, expirationTime) {
@@ -2499,7 +2566,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (newChild["return"] = returnFiber),
+        (newChild.return = returnFiber),
         newChild
       );
     if ("object" === typeof newChild && null !== newChild) {
@@ -2512,7 +2579,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               expirationTime
             )),
             (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
-            (expirationTime["return"] = returnFiber),
+            (expirationTime.return = returnFiber),
             expirationTime
           );
         case REACT_PORTAL_TYPE:
@@ -2522,7 +2589,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (newChild["return"] = returnFiber),
+            (newChild.return = returnFiber),
             newChild
           );
       }
@@ -2534,7 +2601,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime,
             null
           )),
-          (newChild["return"] = returnFiber),
+          (newChild.return = returnFiber),
           newChild
         );
       throwOnInvalidObjectType(returnFiber, newChild);
@@ -2721,17 +2788,21 @@ function ChildReconciler(shouldTrackSideEffects) {
           newChildren[newIdx],
           expirationTime
         ))
-      ) {
-        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
-          oldFiber["delete"](
+      )
+        shouldTrackSideEffects &&
+          null !== nextOldFiber.alternate &&
+          oldFiber.delete(
             null === nextOldFiber.key ? newIdx : nextOldFiber.key
-          );
-        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (resultingFirstChild = nextOldFiber)
-          : (previousNewFiber.sibling = nextOldFiber);
-        previousNewFiber = nextOldFiber;
-      }
+          ),
+          (currentFirstChild = placeChild(
+            nextOldFiber,
+            currentFirstChild,
+            newIdx
+          )),
+          null === previousNewFiber
+            ? (resultingFirstChild = nextOldFiber)
+            : (previousNewFiber.sibling = nextOldFiber),
+          (previousNewFiber = nextOldFiber);
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2805,24 +2876,22 @@ function ChildReconciler(shouldTrackSideEffects) {
       !step.done;
       newIdx++, step = newChildrenIterable.next()
     )
-      if (
-        ((step = updateFromMap(
-          oldFiber,
-          returnFiber,
-          newIdx,
-          step.value,
-          expirationTime
-        )),
-        null !== step)
-      ) {
-        if (shouldTrackSideEffects && null !== step.alternate)
-          oldFiber["delete"](null === step.key ? newIdx : step.key);
-        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (iteratorFn = step)
-          : (previousNewFiber.sibling = step);
-        previousNewFiber = step;
-      }
+      (step = updateFromMap(
+        oldFiber,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      )),
+        null !== step &&
+          (shouldTrackSideEffects &&
+            null !== step.alternate &&
+            oldFiber.delete(null === step.key ? newIdx : step.key),
+          (currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+          null === previousNewFiber
+            ? (iteratorFn = step)
+            : (previousNewFiber.sibling = step),
+          (previousNewFiber = step));
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2861,7 +2930,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     isObject,
                     newChild
                   );
-                  currentFirstChild["return"] = returnFiber;
+                  currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2878,7 +2947,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   expirationTime,
                   newChild.key
                 )),
-                (currentFirstChild["return"] = returnFiber),
+                (currentFirstChild.return = returnFiber),
                 (returnFiber = currentFirstChild))
               : ((expirationTime = createFiberFromElement(
                   newChild,
@@ -2890,7 +2959,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   currentFirstChild,
                   newChild
                 )),
-                (expirationTime["return"] = returnFiber),
+                (expirationTime.return = returnFiber),
                 (returnFiber = expirationTime));
           }
           return placeSingleChild(returnFiber);
@@ -2914,7 +2983,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     newChild.children || [],
                     expirationTime
                   );
-                  currentFirstChild["return"] = returnFiber;
+                  currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2929,7 +2998,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             );
-            currentFirstChild["return"] = returnFiber;
+            currentFirstChild.return = returnFiber;
             returnFiber = currentFirstChild;
           }
           return placeSingleChild(returnFiber);
@@ -2944,7 +3013,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               newChild,
               expirationTime
             )),
-            (currentFirstChild["return"] = returnFiber),
+            (currentFirstChild.return = returnFiber),
             (returnFiber = currentFirstChild))
           : (deleteRemainingChildren(returnFiber, currentFirstChild),
             (currentFirstChild = createFiberFromText(
@@ -2952,7 +3021,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (currentFirstChild["return"] = returnFiber),
+            (currentFirstChild.return = returnFiber),
             (returnFiber = currentFirstChild)),
         placeSingleChild(returnFiber)
       );
@@ -3038,10 +3107,10 @@ function ReactFiberBeginWork(
     workInProgress,
     shouldUpdate,
     hasContext,
-    didCaptureError,
     renderExpirationTime
   ) {
     markRef(current, workInProgress);
+    var didCaptureError = 0 !== (workInProgress.effectTag & 64);
     if (!shouldUpdate && !didCaptureError)
       return (
         hasContext && invalidateContextProvider(workInProgress, !1),
@@ -3089,11 +3158,8 @@ function ReactFiberBeginWork(
     renderExpirationTime
   ) {
     var fiber = workInProgress.child;
-    for (
-      null !== fiber && (fiber["return"] = workInProgress);
-      null !== fiber;
-
-    ) {
+    null !== fiber && (fiber.return = workInProgress);
+    for (; null !== fiber; ) {
       switch (fiber.tag) {
         case 12:
           var nextFiber = fiber.stateNode | 0;
@@ -3116,7 +3182,7 @@ function ReactFiberBeginWork(
               )
                 alternate.expirationTime = renderExpirationTime;
               else break;
-              nextFiber = nextFiber["return"];
+              nextFiber = nextFiber.return;
             }
             nextFiber = null;
           } else nextFiber = fiber.child;
@@ -3127,7 +3193,7 @@ function ReactFiberBeginWork(
         default:
           nextFiber = fiber.child;
       }
-      if (null !== nextFiber) nextFiber["return"] = fiber;
+      if (null !== nextFiber) nextFiber.return = fiber;
       else
         for (nextFiber = fiber; null !== nextFiber; ) {
           if (nextFiber === workInProgress) {
@@ -3136,10 +3202,11 @@ function ReactFiberBeginWork(
           }
           fiber = nextFiber.sibling;
           if (null !== fiber) {
+            fiber.return = nextFiber.return;
             nextFiber = fiber;
             break;
           }
-          nextFiber = nextFiber["return"];
+          nextFiber = nextFiber.return;
         }
       fiber = nextFiber;
     }
@@ -3151,8 +3218,10 @@ function ReactFiberBeginWork(
   ) {
     var context = workInProgress.type._context,
       newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps;
-    if (!hasLegacyContextChanged() && oldProps === newProps)
+      oldProps = workInProgress.memoizedProps,
+      canBailOnProps = !0;
+    if (hasLegacyContextChanged()) canBailOnProps = !1;
+    else if (oldProps === newProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
@@ -3162,7 +3231,7 @@ function ReactFiberBeginWork(
     workInProgress.memoizedProps = newProps;
     if (null === oldProps) newValue = 1073741823;
     else if (oldProps.value === newProps.value) {
-      if (oldProps.children === newProps.children)
+      if (oldProps.children === newProps.children && canBailOnProps)
         return (
           (workInProgress.stateNode = 0),
           pushProvider(workInProgress),
@@ -3176,7 +3245,7 @@ function ReactFiberBeginWork(
           (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
         (oldValue !== oldValue && newValue !== newValue)
       ) {
-        if (oldProps.children === newProps.children)
+        if (oldProps.children === newProps.children && canBailOnProps)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3191,7 +3260,7 @@ function ReactFiberBeginWork(
         (newValue |= 0),
         0 === newValue)
       ) {
-        if (oldProps.children === newProps.children)
+        if (oldProps.children === newProps.children && canBailOnProps)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3223,14 +3292,14 @@ function ReactFiberBeginWork(
         current.expirationTime
       );
       workInProgress.child = newChild;
-      for (newChild["return"] = workInProgress; null !== current.sibling; )
+      for (newChild.return = workInProgress; null !== current.sibling; )
         (current = current.sibling),
           (newChild = newChild.sibling = createWorkInProgress(
             current,
             current.pendingProps,
             current.expirationTime
           )),
-          (newChild["return"] = workInProgress);
+          (newChild.return = workInProgress);
       newChild.sibling = null;
     }
     return workInProgress.child;
@@ -3262,7 +3331,6 @@ function ReactFiberBeginWork(
     }
   );
   var adoptClassInstance = config.adoptClassInstance,
-    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
     constructClassInstance = config.constructClassInstance,
     mountClassInstance = config.mountClassInstance,
     resumeMountClassInstance = config.resumeMountClassInstance,
@@ -3311,20 +3379,13 @@ function ReactFiberBeginWork(
               (workInProgress.tag = 2),
               (workInProgress.memoizedState =
                 null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
-                ((props = callGetDerivedStateFromProps(
+              (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
+              "function" === typeof unmaskedContext &&
+                applyDerivedStateFromProps(
                   workInProgress,
-                  fn,
-                  props,
-                  workInProgress.memoizedState
-                )),
-                null !== props &&
-                  void 0 !== props &&
-                  (workInProgress.memoizedState = Object.assign(
-                    {},
-                    workInProgress.memoizedState,
-                    props
-                  ))),
+                  unmaskedContext,
+                  props
+                ),
               (props = pushLegacyContextProvider(workInProgress)),
               adoptClassInstance(workInProgress, fn),
               mountClassInstance(workInProgress, renderExpirationTime),
@@ -3333,7 +3394,6 @@ function ReactFiberBeginWork(
                 workInProgress,
                 !0,
                 props,
-                !1,
                 renderExpirationTime
               )))
             : ((workInProgress.tag = 1),
@@ -3361,103 +3421,100 @@ function ReactFiberBeginWork(
             current
           );
         case 2:
-          props = pushLegacyContextProvider(workInProgress);
-          null === current
-            ? null === workInProgress.stateNode
-              ? (constructClassInstance(
-                  workInProgress,
-                  workInProgress.pendingProps
-                ),
-                mountClassInstance(workInProgress, renderExpirationTime),
-                (fn = !0))
-              : (fn = resumeMountClassInstance(
+          return (
+            (props = pushLegacyContextProvider(workInProgress)),
+            null === current
+              ? null === workInProgress.stateNode
+                ? (constructClassInstance(
+                    workInProgress,
+                    workInProgress.pendingProps,
+                    renderExpirationTime
+                  ),
+                  mountClassInstance(workInProgress, renderExpirationTime),
+                  (fn = !0))
+                : (fn = resumeMountClassInstance(
+                    workInProgress,
+                    renderExpirationTime
+                  ))
+              : (fn = updateClassInstance(
+                  current,
                   workInProgress,
                   renderExpirationTime
-                ))
-            : (fn = updateClassInstance(
-                current,
-                workInProgress,
-                renderExpirationTime
-              ));
-          unmaskedContext = !1;
-          var updateQueue = workInProgress.updateQueue;
-          null !== updateQueue &&
-            null !== updateQueue.capturedValues &&
-            (unmaskedContext = fn = !0);
-          return finishClassComponent(
-            current,
-            workInProgress,
-            fn,
-            props,
-            unmaskedContext,
-            renderExpirationTime
-          );
-        case 3:
-          a: if (
-            (pushHostRootContext(workInProgress),
-            (fn = workInProgress.updateQueue),
-            null !== fn)
-          ) {
-            unmaskedContext = workInProgress.memoizedState;
-            props = processUpdateQueue(
+                )),
+            finishClassComponent(
               current,
               workInProgress,
               fn,
-              null,
-              null,
+              props,
               renderExpirationTime
-            );
-            workInProgress.memoizedState = props;
-            fn = workInProgress.updateQueue;
-            if (null !== fn && null !== fn.capturedValues) fn = null;
-            else if (unmaskedContext === props) {
-              resetHydrationState();
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-              break a;
-            } else fn = props.element;
-            unmaskedContext = workInProgress.stateNode;
-            (null === current || null === current.child) &&
-            unmaskedContext.hydrate &&
-            enterHydrationState(workInProgress)
-              ? ((workInProgress.effectTag |= 2),
-                (workInProgress.child = mountChildFibers(
+            )
+          );
+        case 3:
+          return (
+            pushHostRootContext(workInProgress),
+            (props = workInProgress.updateQueue),
+            null !== props
+              ? ((fn = workInProgress.memoizedState),
+                (fn = null !== fn ? fn.element : null),
+                processUpdateQueue(
                   workInProgress,
+                  props,
+                  workInProgress.pendingProps,
                   null,
-                  fn,
                   renderExpirationTime
-                )))
+                ),
+                (props = workInProgress.memoizedState.element),
+                props === fn
+                  ? (resetHydrationState(),
+                    (current = bailoutOnAlreadyFinishedWork(
+                      current,
+                      workInProgress
+                    )))
+                  : ((fn = workInProgress.stateNode),
+                    (null === current || null === current.child) &&
+                    fn.hydrate &&
+                    enterHydrationState(workInProgress)
+                      ? ((workInProgress.effectTag |= 2),
+                        (workInProgress.child = mountChildFibers(
+                          workInProgress,
+                          null,
+                          props,
+                          renderExpirationTime
+                        )))
+                      : (resetHydrationState(),
+                        reconcileChildren(current, workInProgress, props)),
+                    (current = workInProgress.child)))
               : (resetHydrationState(),
-                reconcileChildren(current, workInProgress, fn));
-            workInProgress.memoizedState = props;
-            current = workInProgress.child;
-          } else
-            resetHydrationState(),
-              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
-          return current;
+                (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                ))),
+            current
+          );
         case 5:
           a: {
             pushHostContext(workInProgress);
             null === current &&
               tryToClaimNextHydratableInstance(workInProgress);
             props = workInProgress.type;
-            updateQueue = workInProgress.memoizedProps;
+            var memoizedProps = workInProgress.memoizedProps;
             fn = workInProgress.pendingProps;
             unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && updateQueue === fn) {
+            if (!hasLegacyContextChanged() && memoizedProps === fn) {
               if (
-                (updateQueue =
+                (memoizedProps =
                   workInProgress.mode & 1 &&
                   shouldDeprioritizeSubtree(props, fn))
               )
                 workInProgress.expirationTime = 1073741823;
-              if (!updateQueue || 1073741823 !== renderExpirationTime) {
+              if (!memoizedProps || 1073741823 !== renderExpirationTime) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
             }
-            updateQueue = fn.children;
+            memoizedProps = fn.children;
             shouldSetTextContent(props, fn)
-              ? (updateQueue = null)
+              ? (memoizedProps = null)
               : unmaskedContext &&
                 shouldSetTextContent(props, unmaskedContext) &&
                 (workInProgress.effectTag |= 16);
@@ -3468,7 +3525,7 @@ function ReactFiberBeginWork(
               ? ((workInProgress.expirationTime = 1073741823),
                 (workInProgress.memoizedProps = fn),
                 (current = null))
-              : (reconcileChildren(current, workInProgress, updateQueue),
+              : (reconcileChildren(current, workInProgress, memoizedProps),
                 (workInProgress.memoizedProps = fn),
                 (current = workInProgress.child));
           }
@@ -3534,14 +3591,21 @@ function ReactFiberBeginWork(
           );
         case 14:
           return (
-            (renderExpirationTime = workInProgress.type.render),
-            (renderExpirationTime = renderExpirationTime(
-              workInProgress.pendingProps,
-              workInProgress.ref
-            )),
-            reconcileChildren(current, workInProgress, renderExpirationTime),
-            (workInProgress.memoizedProps = renderExpirationTime),
-            workInProgress.child
+            (props = workInProgress.type.render),
+            (renderExpirationTime = workInProgress.pendingProps),
+            (fn = workInProgress.ref),
+            hasLegacyContextChanged() ||
+            workInProgress.memoizedProps !== renderExpirationTime ||
+            fn !== (null !== current ? current.ref : null)
+              ? ((props = props(renderExpirationTime, fn)),
+                reconcileChildren(current, workInProgress, props),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
           );
         case 10:
           return (
@@ -3590,13 +3654,13 @@ function ReactFiberBeginWork(
           a: {
             fn = workInProgress.type;
             unmaskedContext = workInProgress.pendingProps;
-            updateQueue = workInProgress.memoizedProps;
+            memoizedProps = workInProgress.memoizedProps;
             props = fn._currentValue;
             var changedBits = fn._changedBits;
             if (
               hasLegacyContextChanged() ||
               0 !== changedBits ||
-              updateQueue !== unmaskedContext
+              memoizedProps !== unmaskedContext
             ) {
               workInProgress.memoizedProps = unmaskedContext;
               var observedBits = unmaskedContext.unstable_observedBits;
@@ -3610,12 +3674,13 @@ function ReactFiberBeginWork(
                   changedBits,
                   renderExpirationTime
                 );
-              else if (updateQueue === unmaskedContext) {
+              else if (memoizedProps === unmaskedContext) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
               renderExpirationTime = unmaskedContext.children;
               renderExpirationTime = renderExpirationTime(props);
+              workInProgress.effectTag |= 1;
               reconcileChildren(current, workInProgress, renderExpirationTime);
               current = workInProgress.child;
             } else
@@ -3681,18 +3746,7 @@ function ReactFiberCompleteWork(
         case 1:
           return null;
         case 2:
-          return (
-            popLegacyContextProvider(workInProgress),
-            (current = workInProgress.stateNode),
-            (newProps = workInProgress.updateQueue),
-            null !== newProps &&
-              null !== newProps.capturedValues &&
-              ((workInProgress.effectTag &= -65),
-              "function" === typeof current.componentDidCatch
-                ? (workInProgress.effectTag |= 256)
-                : (newProps.capturedValues = null)),
-            null
-          );
+          return popLegacyContextProvider(workInProgress), null;
         case 3:
           popHostContainer(workInProgress);
           popTopLevelLegacyContextObject(workInProgress);
@@ -3703,10 +3757,6 @@ function ReactFiberCompleteWork(
           if (null === current || null === current.child)
             popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
           updateHostContainer(workInProgress);
-          current = workInProgress.updateQueue;
-          null !== current &&
-            null !== current.capturedValues &&
-            (workInProgress.effectTag |= 256);
           return null;
         case 5:
           popHostContext(workInProgress);
@@ -3714,10 +3764,10 @@ function ReactFiberCompleteWork(
           var type = workInProgress.type;
           if (null !== current && null != workInProgress.stateNode) {
             var oldProps = current.memoizedProps,
-              _instance = workInProgress.stateNode,
+              instance = workInProgress.stateNode,
               currentHostContext = getHostContext();
-            _instance = prepareUpdate(
-              _instance,
+            instance = prepareUpdate(
+              instance,
               type,
               oldProps,
               newProps,
@@ -3727,7 +3777,7 @@ function ReactFiberCompleteWork(
             updateHostComponent(
               current,
               workInProgress,
-              _instance,
+              instance,
               type,
               oldProps,
               newProps,
@@ -3774,21 +3824,20 @@ function ReactFiberCompleteWork(
                   4 !== currentHostContext.tag &&
                   null !== currentHostContext.child
                 ) {
-                  currentHostContext.child["return"] = currentHostContext;
+                  currentHostContext.child.return = currentHostContext;
                   currentHostContext = currentHostContext.child;
                   continue;
                 }
                 if (currentHostContext === workInProgress) break;
                 for (; null === currentHostContext.sibling; ) {
                   if (
-                    null === currentHostContext["return"] ||
-                    currentHostContext["return"] === workInProgress
+                    null === currentHostContext.return ||
+                    currentHostContext.return === workInProgress
                   )
                     break a;
-                  currentHostContext = currentHostContext["return"];
+                  currentHostContext = currentHostContext.return;
                 }
-                currentHostContext.sibling["return"] =
-                  currentHostContext["return"];
+                currentHostContext.sibling.return = currentHostContext.return;
                 currentHostContext = currentHostContext.sibling;
               }
               finalizeInitialChildren(
@@ -3841,30 +3890,34 @@ function ReactFiberCompleteWork(
           );
           workInProgress.tag = 8;
           type = [];
-          a: for (
-            (oldProps = workInProgress.stateNode) &&
-            (oldProps["return"] = workInProgress);
-            null !== oldProps;
-
-          ) {
-            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
-              invariant(!1, "A call cannot have host component children.");
-            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
-            else if (null !== oldProps.child) {
-              oldProps.child["return"] = oldProps;
-              oldProps = oldProps.child;
-              continue;
-            }
-            for (; null === oldProps.sibling; ) {
+          a: {
+            if ((oldProps = workInProgress.stateNode))
+              oldProps.return = workInProgress;
+            for (; null !== oldProps; ) {
               if (
-                null === oldProps["return"] ||
-                oldProps["return"] === workInProgress
+                5 === oldProps.tag ||
+                6 === oldProps.tag ||
+                4 === oldProps.tag
               )
-                break a;
-              oldProps = oldProps["return"];
+                invariant(!1, "A call cannot have host component children.");
+              else if (9 === oldProps.tag)
+                type.push(oldProps.pendingProps.value);
+              else if (null !== oldProps.child) {
+                oldProps.child.return = oldProps;
+                oldProps = oldProps.child;
+                continue;
+              }
+              for (; null === oldProps.sibling; ) {
+                if (
+                  null === oldProps.return ||
+                  oldProps.return === workInProgress
+                )
+                  break a;
+                oldProps = oldProps.return;
+              }
+              oldProps.sibling.return = oldProps.return;
+              oldProps = oldProps.sibling;
             }
-            oldProps.sibling["return"] = oldProps["return"];
-            oldProps = oldProps.sibling;
           }
           oldProps = newProps.handler;
           newProps = oldProps(newProps.props, type);
@@ -3909,103 +3962,11 @@ function ReactFiberCompleteWork(
     }
   };
 }
-function ReactFiberUnwindWork(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
+function createCapturedValue(value, source) {
   return {
-    throwException: function(returnFiber, sourceFiber, rawValue) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      sourceFiber = {
-        value: rawValue,
-        source: sourceFiber,
-        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-      };
-      do {
-        switch (returnFiber.tag) {
-          case 3:
-            ensureUpdateQueues(returnFiber);
-            returnFiber.updateQueue.capturedValues = [sourceFiber];
-            returnFiber.effectTag |= 1024;
-            return;
-          case 2:
-            if (
-              ((rawValue = returnFiber.stateNode),
-              0 === (returnFiber.effectTag & 64) &&
-                null !== rawValue &&
-                "function" === typeof rawValue.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(rawValue))
-            ) {
-              ensureUpdateQueues(returnFiber);
-              rawValue = returnFiber.updateQueue;
-              var capturedValues = rawValue.capturedValues;
-              null === capturedValues
-                ? (rawValue.capturedValues = [sourceFiber])
-                : capturedValues.push(sourceFiber);
-              returnFiber.effectTag |= 1024;
-              return;
-            }
-        }
-        returnFiber = returnFiber["return"];
-      } while (null !== returnFiber);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
-      }
-    }
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
   };
 }
 function logError(boundary, errorInfo) {
@@ -4037,13 +3998,7 @@ function logError(boundary, errorInfo) {
     (e && e.suppressReactErrorLogging) || console.error(e);
   }
 }
-function ReactFiberCommitWork(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed
-) {
+function ReactFiberCommitWork(config, captureError) {
   function safelyDetachRef(current) {
     var ref = current.ref;
     if (null !== ref)
@@ -4060,12 +4015,12 @@ function ReactFiberCommitWork(
     switch (current.tag) {
       case 2:
         safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if ("function" === typeof _instance7.componentWillUnmount)
+        var _instance6 = current.stateNode;
+        if ("function" === typeof _instance6.componentWillUnmount)
           try {
-            (_instance7.props = current.memoizedProps),
-              (_instance7.state = current.memoizedState),
-              _instance7.componentWillUnmount();
+            (_instance6.props = current.memoizedProps),
+              (_instance6.state = current.memoizedState),
+              _instance6.componentWillUnmount();
           } catch (unmountError) {
             captureError(current, unmountError);
           }
@@ -4088,12 +4043,12 @@ function ReactFiberCommitWork(
       ) {
         if (node === root) break;
         for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === root) return;
-          node = node["return"];
+          if (null === node.return || node.return === root) return;
+          node = node.return;
         }
-        node.sibling["return"] = node["return"];
+        node.sibling.return = node.return;
         node = node.sibling;
-      } else (node.child["return"] = node), (node = node.child);
+      } else (node.child.return = node), (node = node.child);
   }
   function isHostParent(fiber) {
     return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
@@ -4108,7 +4063,7 @@ function ReactFiberCommitWork(
 
     ) {
       if (!currentParentIsValid) {
-        currentParentIsValid = node["return"];
+        currentParentIsValid = node.return;
         a: for (;;) {
           invariant(
             null !== currentParentIsValid,
@@ -4128,7 +4083,7 @@ function ReactFiberCommitWork(
               currentParentIsContainer = !0;
               break a;
           }
-          currentParentIsValid = currentParentIsValid["return"];
+          currentParentIsValid = currentParentIsValid.return;
         }
         currentParentIsValid = !0;
       }
@@ -4143,17 +4098,17 @@ function ReactFiberCommitWork(
           : commitUnmount(node),
         null !== node.child)
       ) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
       if (node === current) break;
       for (; null === node.sibling; ) {
-        if (null === node["return"] || node["return"] === current) return;
-        node = node["return"];
+        if (null === node.return || node.return === current) return;
+        node = node.return;
         4 === node.tag && (currentParentIsValid = !1);
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -4178,7 +4133,7 @@ function ReactFiberCommitWork(
     commitBeforeMutationLifeCycles: function(current, finishedWork) {
       switch (finishedWork.tag) {
         case 2:
-          if (finishedWork.effectTag & 2048 && null !== current) {
+          if (finishedWork.effectTag & 256 && null !== current) {
             var prevProps = current.memoizedProps,
               prevState = current.memoizedState;
             current = finishedWork.stateNode;
@@ -4208,12 +4163,12 @@ function ReactFiberCommitWork(
     },
     commitPlacement: function(finishedWork) {
       a: {
-        for (var parent = finishedWork["return"]; null !== parent; ) {
+        for (var parent = finishedWork.return; null !== parent; ) {
           if (isHostParent(parent)) {
             var parentFiber = parent;
             break a;
           }
-          parent = parent["return"];
+          parent = parent.return;
         }
         invariant(
           !1,
@@ -4245,16 +4200,13 @@ function ReactFiberCommitWork(
         (resetTextContent(parent), (parentFiber.effectTag &= -17));
       a: b: for (parentFiber = finishedWork; ; ) {
         for (; null === parentFiber.sibling; ) {
-          if (
-            null === parentFiber["return"] ||
-            isHostParent(parentFiber["return"])
-          ) {
+          if (null === parentFiber.return || isHostParent(parentFiber.return)) {
             parentFiber = null;
             break a;
           }
-          parentFiber = parentFiber["return"];
+          parentFiber = parentFiber.return;
         }
-        parentFiber.sibling["return"] = parentFiber["return"];
+        parentFiber.sibling.return = parentFiber.return;
         for (
           parentFiber = parentFiber.sibling;
           5 !== parentFiber.tag && 6 !== parentFiber.tag;
@@ -4263,7 +4215,7 @@ function ReactFiberCommitWork(
           if (parentFiber.effectTag & 2) continue b;
           if (null === parentFiber.child || 4 === parentFiber.tag) continue b;
           else
-            (parentFiber.child["return"] = parentFiber),
+            (parentFiber.child.return = parentFiber),
               (parentFiber = parentFiber.child);
         }
         if (!(parentFiber.effectTag & 2)) {
@@ -4281,35 +4233,33 @@ function ReactFiberCommitWork(
               ? appendChildToContainer(parent, node.stateNode)
               : appendChild(parent, node.stateNode);
         else if (4 !== node.tag && null !== node.child) {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
           continue;
         }
         if (node === finishedWork) break;
         for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === finishedWork)
-            return;
-          node = node["return"];
+          if (null === node.return || node.return === finishedWork) return;
+          node = node.return;
         }
-        node.sibling["return"] = node["return"];
+        node.sibling.return = node.return;
         node = node.sibling;
       }
     },
     commitDeletion: function(current) {
       unmountHostComponents(current);
-      current["return"] = null;
+      current.return = null;
       current.child = null;
       current.alternate &&
-        ((current.alternate.child = null),
-        (current.alternate["return"] = null));
+        ((current.alternate.child = null), (current.alternate.return = null));
     },
     commitWork: function(current, finishedWork) {
       switch (finishedWork.tag) {
         case 2:
           break;
         case 5:
-          var _instance8 = finishedWork.stateNode;
-          if (null != _instance8) {
+          var _instance7 = finishedWork.stateNode;
+          if (null != _instance7) {
             var newProps = finishedWork.memoizedProps;
             current = null !== current ? current.memoizedProps : newProps;
             var type = finishedWork.type,
@@ -4317,7 +4267,7 @@ function ReactFiberCommitWork(
             finishedWork.updateQueue = null;
             null !== updatePayload &&
               commitUpdate(
-                _instance8,
+                _instance7,
                 updatePayload,
                 type,
                 current,
@@ -4331,11 +4281,11 @@ function ReactFiberCommitWork(
             null !== finishedWork.stateNode,
             "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
           );
-          _instance8 = finishedWork.memoizedProps;
+          _instance7 = finishedWork.memoizedProps;
           commitTextUpdate(
             finishedWork.stateNode,
-            null !== current ? current.memoizedProps : _instance8,
-            _instance8
+            null !== current ? current.memoizedProps : _instance7,
+            _instance7
           );
           break;
         case 3:
@@ -4347,28 +4297,40 @@ function ReactFiberCommitWork(
           );
       }
     },
-    commitLifeCycles: function(finishedRoot, current, finishedWork) {
+    commitLifeCycles: function(
+      finishedRoot,
+      current,
+      finishedWork,
+      currentTime,
+      committedExpirationTime
+    ) {
       switch (finishedWork.tag) {
         case 2:
           finishedRoot = finishedWork.stateNode;
-          if (finishedWork.effectTag & 4)
-            if (null === current)
-              (finishedRoot.props = finishedWork.memoizedProps),
+          finishedWork.effectTag & 4 &&
+            (null === current
+              ? ((finishedRoot.props = finishedWork.memoizedProps),
                 (finishedRoot.state = finishedWork.memoizedState),
-                finishedRoot.componentDidMount();
-            else {
-              var prevProps = current.memoizedProps;
-              current = current.memoizedState;
-              finishedRoot.props = finishedWork.memoizedProps;
-              finishedRoot.state = finishedWork.memoizedState;
-              finishedRoot.componentDidUpdate(
-                prevProps,
-                current,
-                finishedRoot.__reactInternalSnapshotBeforeUpdate
-              );
-            }
-          finishedWork = finishedWork.updateQueue;
-          null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
+                finishedRoot.componentDidMount())
+              : ((currentTime = current.memoizedProps),
+                (current = current.memoizedState),
+                (finishedRoot.props = finishedWork.memoizedProps),
+                (finishedRoot.state = finishedWork.memoizedState),
+                finishedRoot.componentDidUpdate(
+                  currentTime,
+                  current,
+                  finishedRoot.__reactInternalSnapshotBeforeUpdate
+                )));
+          current = finishedWork.updateQueue;
+          null !== current &&
+            ((finishedRoot.props = finishedWork.memoizedProps),
+            (finishedRoot.state = finishedWork.memoizedState),
+            commitUpdateQueue(
+              finishedWork,
+              current,
+              finishedRoot,
+              committedExpirationTime
+            ));
           break;
         case 3:
           current = finishedWork.updateQueue;
@@ -4384,15 +4346,20 @@ function ReactFiberCommitWork(
                 case 2:
                   finishedRoot = finishedWork.child.stateNode;
               }
-            commitCallbacks(current, finishedRoot);
+            commitUpdateQueue(
+              finishedWork,
+              current,
+              finishedRoot,
+              committedExpirationTime
+            );
           }
           break;
         case 5:
-          finishedRoot = finishedWork.stateNode;
+          committedExpirationTime = finishedWork.stateNode;
           null === current &&
             finishedWork.effectTag & 4 &&
             commitMount(
-              finishedRoot,
+              committedExpirationTime,
               finishedWork.type,
               finishedWork.memoizedProps,
               finishedWork
@@ -4409,62 +4376,16 @@ function ReactFiberCommitWork(
           );
       }
     },
-    commitErrorLogging: function(finishedWork, onUncaughtError) {
-      switch (finishedWork.tag) {
-        case 2:
-          var ctor = finishedWork.type;
-          onUncaughtError = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            null !== updateQueue && null !== updateQueue.capturedValues,
-            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-          "function" !== typeof ctor.getDerivedStateFromCatch &&
-            markLegacyErrorBoundaryAsFailed(onUncaughtError);
-          onUncaughtError.props = finishedWork.memoizedProps;
-          onUncaughtError.state = finishedWork.memoizedState;
-          for (ctor = 0; ctor < capturedErrors.length; ctor++) {
-            updateQueue = capturedErrors[ctor];
-            var _error = updateQueue.value,
-              stack = updateQueue.stack;
-            logError(finishedWork, updateQueue);
-            onUncaughtError.componentDidCatch(_error, {
-              componentStack: null !== stack ? stack : ""
-            });
-          }
-          break;
-        case 3:
-          ctor = finishedWork.updateQueue;
-          invariant(
-            null !== ctor && null !== ctor.capturedValues,
-            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-          );
-          capturedErrors = ctor.capturedValues;
-          ctor.capturedValues = null;
-          for (ctor = 0; ctor < capturedErrors.length; ctor++)
-            (updateQueue = capturedErrors[ctor]),
-              logError(finishedWork, updateQueue),
-              onUncaughtError(updateQueue.value);
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
     commitAttachRef: function(finishedWork) {
       var ref = finishedWork.ref;
       if (null !== ref) {
-        var _instance6 = finishedWork.stateNode;
+        var _instance5 = finishedWork.stateNode;
         switch (finishedWork.tag) {
           case 5:
-            finishedWork = getPublicInstance(_instance6);
+            finishedWork = getPublicInstance(_instance5);
             break;
           default:
-            finishedWork = _instance6;
+            finishedWork = _instance5;
         }
         "function" === typeof ref
           ? ref(finishedWork)
@@ -4480,6 +4401,151 @@ function ReactFiberCommitWork(
     }
   };
 }
+function ReactFiberUnwindWork(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  markLegacyErrorBoundaryAsFailed,
+  isAlreadyFailedLegacyErrorBoundary,
+  onUncaughtError
+) {
+  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+    expirationTime = createUpdate(expirationTime);
+    expirationTime.tag = 3;
+    expirationTime.payload = { element: null };
+    var error = errorInfo.value;
+    expirationTime.callback = function() {
+      onUncaughtError(error);
+      logError(fiber, errorInfo);
+    };
+    return expirationTime;
+  }
+  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+    expirationTime = createUpdate(expirationTime);
+    expirationTime.tag = 3;
+    var inst = fiber.stateNode;
+    null !== inst &&
+      "function" === typeof inst.componentDidCatch &&
+      (expirationTime.callback = function() {
+        markLegacyErrorBoundaryAsFailed(this);
+        var error = errorInfo.value,
+          stack = errorInfo.stack;
+        logError(fiber, errorInfo);
+        this.componentDidCatch(error, {
+          componentStack: null !== stack ? stack : ""
+        });
+      });
+    return expirationTime;
+  }
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
+  return {
+    throwException: function(
+      returnFiber,
+      sourceFiber,
+      rawValue,
+      renderExpirationTime
+    ) {
+      sourceFiber.effectTag |= 512;
+      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+      sourceFiber = createCapturedValue(rawValue, sourceFiber);
+      do {
+        switch (returnFiber.tag) {
+          case 3:
+            returnFiber.effectTag |= 1024;
+            sourceFiber = createRootErrorUpdate(
+              returnFiber,
+              sourceFiber,
+              renderExpirationTime
+            );
+            enqueueCapturedUpdate(
+              returnFiber,
+              sourceFiber,
+              renderExpirationTime
+            );
+            return;
+          case 2:
+            rawValue = sourceFiber;
+            var _instance = returnFiber.stateNode;
+            if (
+              0 === (returnFiber.effectTag & 64) &&
+              null !== _instance &&
+              "function" === typeof _instance.componentDidCatch &&
+              !isAlreadyFailedLegacyErrorBoundary(_instance)
+            ) {
+              returnFiber.effectTag |= 1024;
+              sourceFiber = createClassErrorUpdate(
+                returnFiber,
+                rawValue,
+                renderExpirationTime
+              );
+              enqueueCapturedUpdate(
+                returnFiber,
+                sourceFiber,
+                renderExpirationTime
+              );
+              return;
+            }
+        }
+        returnFiber = returnFiber.return;
+      } while (null !== returnFiber);
+    },
+    unwindWork: function(workInProgress) {
+      switch (workInProgress.tag) {
+        case 2:
+          popLegacyContextProvider(workInProgress);
+          var effectTag = workInProgress.effectTag;
+          return effectTag & 1024
+            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+              workInProgress)
+            : null;
+        case 3:
+          return (
+            popHostContainer(workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 5:
+          return popHostContext(workInProgress), null;
+        case 4:
+          return popHostContainer(workInProgress), null;
+        case 13:
+          return popProvider(workInProgress), null;
+        default:
+          return null;
+      }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
+    },
+    createRootErrorUpdate: createRootErrorUpdate,
+    createClassErrorUpdate: createClassErrorUpdate
+  };
+}
 var NO_CONTEXT = {};
 function ReactFiberHostContext(config, stack) {
   function requiredContext(c) {
@@ -4536,7 +4602,7 @@ function ReactFiberHydrationContext(config) {
     var fiber = new FiberNode(5, null, null, 0);
     fiber.type = "DELETED";
     fiber.stateNode = instance;
-    fiber["return"] = returnFiber;
+    fiber.return = returnFiber;
     fiber.effectTag = 8;
     null !== returnFiber.lastEffect
       ? ((returnFiber.lastEffect.nextEffect = fiber),
@@ -4568,11 +4634,11 @@ function ReactFiberHydrationContext(config) {
   }
   function popToNextHostParent(fiber) {
     for (
-      fiber = fiber["return"];
+      fiber = fiber.return;
       null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
 
     )
-      fiber = fiber["return"];
+      fiber = fiber.return;
     hydrationParentFiber = fiber;
   }
   var shouldSetTextContent = config.shouldSetTextContent;
@@ -4806,7 +4872,7 @@ function ReactFiberLegacyContext(stack) {
       ) {
         if (isContextProvider(fiber))
           return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber["return"];
+        fiber = fiber.return;
         invariant(
           fiber,
           "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
@@ -4873,12 +4939,12 @@ function ReactFiberScheduler(config) {
   function resetStack() {
     if (null !== nextUnitOfWork)
       for (
-        var interruptedWork = nextUnitOfWork["return"];
+        var interruptedWork = nextUnitOfWork.return;
         null !== interruptedWork;
 
       )
         unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork["return"]);
+          (interruptedWork = interruptedWork.return);
     nextRoot = null;
     nextRenderExpirationTime = 0;
     nextUnitOfWork = null;
@@ -4890,74 +4956,71 @@ function ReactFiberScheduler(config) {
       legacyErrorBoundariesThatAlreadyFailed.has(instance)
     );
   }
-  function completeUnitOfWork(workInProgress$jscomp$0) {
+  function markLegacyErrorBoundaryAsFailed(instance) {
+    null === legacyErrorBoundariesThatAlreadyFailed
+      ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
+      : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+  }
+  function completeUnitOfWork(workInProgress) {
     for (;;) {
-      var current = workInProgress$jscomp$0.alternate,
-        returnFiber = workInProgress$jscomp$0["return"],
-        siblingFiber = workInProgress$jscomp$0.sibling;
-      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
+      var current = workInProgress.alternate,
+        returnFiber = workInProgress.return,
+        siblingFiber = workInProgress.sibling;
+      if (0 === (workInProgress.effectTag & 512)) {
         current = completeWork(
           current,
-          workInProgress$jscomp$0,
+          workInProgress,
           nextRenderExpirationTime
         );
-        var workInProgress = workInProgress$jscomp$0;
         if (
           1073741823 === nextRenderExpirationTime ||
           1073741823 !== workInProgress.expirationTime
         ) {
-          b: switch (workInProgress.tag) {
+          var newExpirationTime = 0;
+          switch (workInProgress.tag) {
             case 3:
             case 2:
-              var newExpirationTime = workInProgress.updateQueue;
-              newExpirationTime =
-                null === newExpirationTime
-                  ? 0
-                  : newExpirationTime.expirationTime;
-              break b;
-            default:
-              newExpirationTime = 0;
+              var updateQueue = workInProgress.updateQueue;
+              null !== updateQueue &&
+                (newExpirationTime = updateQueue.expirationTime);
           }
-          for (var child = workInProgress.child; null !== child; )
-            0 !== child.expirationTime &&
+          for (updateQueue = workInProgress.child; null !== updateQueue; )
+            0 !== updateQueue.expirationTime &&
               (0 === newExpirationTime ||
-                newExpirationTime > child.expirationTime) &&
-              (newExpirationTime = child.expirationTime),
-              (child = child.sibling);
+                newExpirationTime > updateQueue.expirationTime) &&
+              (newExpirationTime = updateQueue.expirationTime),
+              (updateQueue = updateQueue.sibling);
           workInProgress.expirationTime = newExpirationTime;
         }
         if (null !== current) return current;
         null !== returnFiber &&
           0 === (returnFiber.effectTag & 512) &&
           (null === returnFiber.firstEffect &&
-            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
-          null !== workInProgress$jscomp$0.lastEffect &&
+            (returnFiber.firstEffect = workInProgress.firstEffect),
+          null !== workInProgress.lastEffect &&
             (null !== returnFiber.lastEffect &&
-              (returnFiber.lastEffect.nextEffect =
-                workInProgress$jscomp$0.firstEffect),
-            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
-          1 < workInProgress$jscomp$0.effectTag &&
+              (returnFiber.lastEffect.nextEffect = workInProgress.firstEffect),
+            (returnFiber.lastEffect = workInProgress.lastEffect)),
+          1 < workInProgress.effectTag &&
             (null !== returnFiber.lastEffect
-              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
-              : (returnFiber.firstEffect = workInProgress$jscomp$0),
-            (returnFiber.lastEffect = workInProgress$jscomp$0)));
+              ? (returnFiber.lastEffect.nextEffect = workInProgress)
+              : (returnFiber.firstEffect = workInProgress),
+            (returnFiber.lastEffect = workInProgress)));
         if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+        if (null !== returnFiber) workInProgress = returnFiber;
         else {
           isRootReadyForCommit = !0;
           break;
         }
       } else {
-        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
-        if (null !== workInProgress$jscomp$0)
-          return (
-            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
-          );
+        workInProgress = unwindWork(workInProgress);
+        if (null !== workInProgress)
+          return (workInProgress.effectTag &= 511), workInProgress;
         null !== returnFiber &&
           ((returnFiber.firstEffect = returnFiber.lastEffect = null),
           (returnFiber.effectTag |= 512));
         if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+        if (null !== returnFiber) workInProgress = returnFiber;
         else break;
       }
     }
@@ -5009,13 +5072,18 @@ function ReactFiberScheduler(config) {
           break;
         }
         isAsync = nextUnitOfWork;
-        var returnFiber = isAsync["return"];
+        var returnFiber = isAsync.return;
         if (null === returnFiber) {
           didFatal = !0;
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(returnFiber, isAsync, thrownValue);
+        throwException(
+          returnFiber,
+          isAsync,
+          thrownValue,
+          nextRenderExpirationTime
+        );
         nextUnitOfWork = completeUnitOfWork(isAsync);
       }
       break;
@@ -5032,55 +5100,61 @@ function ReactFiberScheduler(config) {
       "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
     );
   }
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    sourceFiber = {
-      value: value,
-      source: sourceFiber,
-      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-    };
-    insertUpdateIntoFiber(boundaryFiber, {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: sourceFiber,
-      next: null
-    });
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-  function onCommitPhaseError(fiber$jscomp$0, error) {
+  function onCommitPhaseError(fiber, error) {
+    var JSCompiler_inline_result;
     a: {
       invariant(
         !isWorking || isCommitting,
         "dispatch: Cannot dispatch during the render phase."
       );
-      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
-        switch (fiber.tag) {
+      for (
+        JSCompiler_inline_result = fiber.return;
+        null !== JSCompiler_inline_result;
+
+      ) {
+        switch (JSCompiler_inline_result.tag) {
           case 2:
-            var instance = fiber.stateNode;
+            var instance = JSCompiler_inline_result.stateNode;
             if (
-              "function" === typeof fiber.type.getDerivedStateFromCatch ||
+              "function" ===
+                typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
               ("function" === typeof instance.componentDidCatch &&
                 !isAlreadyFailedLegacyErrorBoundary(instance))
             ) {
-              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-              fiber$jscomp$0 = void 0;
+              fiber = createCapturedValue(error, fiber);
+              fiber = createClassErrorUpdate(
+                JSCompiler_inline_result,
+                fiber,
+                1
+              );
+              enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+              scheduleWork(JSCompiler_inline_result, 1);
+              JSCompiler_inline_result = void 0;
               break a;
             }
             break;
           case 3:
-            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-            fiber$jscomp$0 = void 0;
+            fiber = createCapturedValue(error, fiber);
+            fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+            enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+            scheduleWork(JSCompiler_inline_result, 1);
+            JSCompiler_inline_result = void 0;
             break a;
         }
-        fiber = fiber["return"];
+        JSCompiler_inline_result = JSCompiler_inline_result.return;
       }
-      3 === fiber$jscomp$0.tag &&
-        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
-      fiber$jscomp$0 = void 0;
+      3 === fiber.tag &&
+        ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
+        (JSCompiler_inline_result = createRootErrorUpdate(
+          fiber,
+          JSCompiler_inline_result,
+          1
+        )),
+        enqueueUpdate(fiber, JSCompiler_inline_result, 1),
+        scheduleWork(fiber, 1));
+      JSCompiler_inline_result = void 0;
     }
-    return fiber$jscomp$0;
+    return JSCompiler_inline_result;
   }
   function computeExpirationForFiber(fiber) {
     fiber =
@@ -5108,7 +5182,7 @@ function ReactFiberScheduler(config) {
           (0 === fiber.alternate.expirationTime ||
             fiber.alternate.expirationTime > expirationTime) &&
           (fiber.alternate.expirationTime = expirationTime);
-        if (null === fiber["return"])
+        if (null === fiber.return)
           if (3 === fiber.tag) {
             var root = fiber.stateNode;
             !isWorking &&
@@ -5126,7 +5200,7 @@ function ReactFiberScheduler(config) {
             expirationTime = void 0;
             break a;
           }
-        fiber = fiber["return"];
+        fiber = fiber.return;
       }
       expirationTime = void 0;
     }
@@ -5366,7 +5440,7 @@ function ReactFiberScheduler(config) {
         error = void 0;
       try {
         for (; null !== nextEffect; )
-          nextEffect.effectTag & 2048 &&
+          nextEffect.effectTag & 256 &&
             commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
             (nextEffect = nextEffect.nextEffect);
       } catch (e) {
@@ -5442,8 +5516,6 @@ function ReactFiberScheduler(config) {
               didError,
               error
             );
-          effectTag$jscomp$0 & 256 &&
-            commitErrorLogging(nextEffect, onUncaughtError);
           effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
           var next = nextEffect.nextEffect;
           nextEffect.nextEffect = null;
@@ -5506,21 +5578,21 @@ function ReactFiberScheduler(config) {
     legacyContext,
     stack,
     scheduleWork,
-    isAlreadyFailedLegacyErrorBoundary
+    markLegacyErrorBoundaryAsFailed,
+    isAlreadyFailedLegacyErrorBoundary,
+    onUncaughtError
   );
   var throwException = hostContext.throwException,
     unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork;
+    unwindInterruptedWork = hostContext.unwindInterruptedWork,
+    createRootErrorUpdate = hostContext.createRootErrorUpdate,
+    createClassErrorUpdate = hostContext.createClassErrorUpdate;
   hostContext = ReactFiberCommitWork(
     config,
     onCommitPhaseError,
     scheduleWork,
     computeExpirationForFiber,
-    function(instance) {
-      null === legacyErrorBoundariesThatAlreadyFailed
-        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-    },
+    markLegacyErrorBoundaryAsFailed,
     recalculateCurrentTime
   );
   var commitBeforeMutationLifeCycles =
@@ -5530,7 +5602,6 @@ function ReactFiberScheduler(config) {
     commitDeletion = hostContext.commitDeletion,
     commitWork = hostContext.commitWork,
     commitLifeCycles = hostContext.commitLifeCycles,
-    commitErrorLogging = hostContext.commitErrorLogging,
     commitAttachRef = hostContext.commitAttachRef,
     commitDetachRef = hostContext.commitDetachRef,
     now = config.now,
@@ -5698,15 +5769,11 @@ function ReactFiberReconciler$1(config) {
       ? (container.context = parentComponent)
       : (container.pendingContext = parentComponent);
     container = callback;
-    insertUpdateIntoFiber(currentTime, {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: void 0 === container ? null : container,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: null,
-      next: null
-    });
+    callback = createUpdate(expirationTime);
+    callback.payload = { element: element };
+    container = void 0 === container ? null : container;
+    null !== container && (callback.callback = container);
+    enqueueUpdate(currentTime, callback, expirationTime);
     scheduleWork(currentTime, expirationTime);
     return expirationTime;
   }
@@ -5827,8 +5894,8 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
   ReactFiberReconciler$3 =
     (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
     ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3["default"]
-    ? ReactFiberReconciler$3["default"]
+  reactReconciler = ReactFiberReconciler$3.default
+    ? ReactFiberReconciler$3.default
     : ReactFiberReconciler$3,
   ReactNativeFiberHostComponent = (function() {
     function ReactNativeFiberHostComponent(tag, viewConfig) {
@@ -6219,7 +6286,7 @@ var roots = new Map(),
       var root = roots.get(containerTag);
       root &&
         NativeRenderer.updateContainer(null, root, null, function() {
-          roots["delete"](containerTag);
+          roots.delete(containerTag);
         });
     },
     unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
@@ -6305,6 +6372,6 @@ NativeRenderer.injectIntoDevTools({
 var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
   ReactNativeRenderer$3 =
     (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
-module.exports = ReactNativeRenderer$3["default"]
-  ? ReactNativeRenderer$3["default"]
+module.exports = ReactNativeRenderer$3.default
+  ? ReactNativeRenderer$3.default
   : ReactNativeRenderer$3;
diff --git a/Libraries/Renderer/shims/NativeMethodsMixin.js b/Libraries/Renderer/shims/NativeMethodsMixin.js
index 7acdf99bbd39..cd0e673b3bff 100644
--- a/Libraries/Renderer/shims/NativeMethodsMixin.js
+++ b/Libraries/Renderer/shims/NativeMethodsMixin.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @providesModule NativeMethodsMixin
  * @flow
  */
 
diff --git a/Libraries/Renderer/shims/ReactDebugTool.js b/Libraries/Renderer/shims/ReactDebugTool.js
index 8ea7ba5c1433..e45af4fb0994 100644
--- a/Libraries/Renderer/shims/ReactDebugTool.js
+++ b/Libraries/Renderer/shims/ReactDebugTool.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @providesModule ReactDebugTool
  */
 
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactFabric.js b/Libraries/Renderer/shims/ReactFabric.js
index 8dce288d28a7..4162ca62fef7 100644
--- a/Libraries/Renderer/shims/ReactFabric.js
+++ b/Libraries/Renderer/shims/ReactFabric.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @providesModule ReactFabric
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactNative.js b/Libraries/Renderer/shims/ReactNative.js
index 43c5002e05f5..a648cafbc30c 100644
--- a/Libraries/Renderer/shims/ReactNative.js
+++ b/Libraries/Renderer/shims/ReactNative.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @providesModule ReactNative
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactNativeComponentTree.js b/Libraries/Renderer/shims/ReactNativeComponentTree.js
index 8e8ce6ae06c1..30ec5257f424 100644
--- a/Libraries/Renderer/shims/ReactNativeComponentTree.js
+++ b/Libraries/Renderer/shims/ReactNativeComponentTree.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @providesModule ReactNativeComponentTree
  * @flow
  */
 
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index 485ce162ecc6..bf9411973933 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @providesModule ReactNativeTypes
  */
 
 export type MeasureOnSuccessCallback = (
diff --git a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
index c8ed940a8609..ffb0fa213f3b 100644
--- a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
+++ b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @providesModule ReactNativeViewConfigRegistry
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactPerf.js b/Libraries/Renderer/shims/ReactPerf.js
index e94c87501c7d..bb6777fff0b9 100644
--- a/Libraries/Renderer/shims/ReactPerf.js
+++ b/Libraries/Renderer/shims/ReactPerf.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @providesModule ReactPerf
  */
 
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactTypes.js b/Libraries/Renderer/shims/ReactTypes.js
index 747a6c07b6f3..689ed18bf952 100644
--- a/Libraries/Renderer/shims/ReactTypes.js
+++ b/Libraries/Renderer/shims/ReactTypes.js
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @providesModule ReactTypes
  */
 
 export type ReactNode =
diff --git a/Libraries/Renderer/shims/createReactNativeComponentClass.js b/Libraries/Renderer/shims/createReactNativeComponentClass.js
index cacaedab88f2..1a050e8b3cf0 100644
--- a/Libraries/Renderer/shims/createReactNativeComponentClass.js
+++ b/Libraries/Renderer/shims/createReactNativeComponentClass.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @providesModule createReactNativeComponentClass
  * @flow
  */
 

From 30d06b42862fc5e8704e109db652d62f86f8eabc Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Mon, 7 May 2018 12:16:28 -0700
Subject: [PATCH 0444/1109] Better error messages for ReadableNativeMap
 ClassCastExceptions

Reviewed By: mdvacca

Differential Revision: D7800266

fbshipit-source-id: 3fa224d3adc54a7bc59a6a37b9ad6928ac33ceb6
---
 .../react/bridge/ReadableNativeMap.java       | 34 +++++++++++++++----
 1 file changed, 28 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReadableNativeMap.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReadableNativeMap.java
index 0cb9c10ef1c6..40cbe0d8d22f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReadableNativeMap.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReadableNativeMap.java
@@ -121,6 +121,13 @@ private Object getValue(String name) {
     }
     throw new NoSuchKeyException(name);
   }
+
+  private <T> T getValue(String name, Class<T> type) {
+    Object value = getValue(name);
+    checkInstance(name, value, type);
+    return (T) value;
+  }
+
   private @Nullable Object getNullableValue(String name) {
     if (hasKey(name)) {
       return getLocalMap().get(name);
@@ -128,13 +135,27 @@ private Object getValue(String name) {
     throw new NoSuchKeyException(name);
   }
 
+  private @Nullable <T> T getNullableValue(String name, Class<T> type) {
+    Object value = getNullableValue(name);
+    checkInstance(name, value, type);
+    return (T) value;
+  }
+
+  private void checkInstance(String name, Object value, Class type) {
+    if (value != null && !type.isInstance(value)) {
+      throw new ClassCastException(
+        "Value for " + name + " cannot be cast from " +
+          value.getClass().getSimpleName() + " to " + type.getSimpleName());
+    }
+  }
+
   @Override
   public boolean getBoolean(String name) {
     if (mUseNativeAccessor) {
       mJniCallCounter++;
       return getBooleanNative(name);
     }
-    return ((Boolean) getValue(name)).booleanValue();
+    return getValue(name, Boolean.class).booleanValue();
   }
   private native boolean getBooleanNative(String name);
 
@@ -144,7 +165,7 @@ public double getDouble(String name) {
       mJniCallCounter++;
       return getDoubleNative(name);
     }
-    return ((Double) getValue(name)).doubleValue();
+    return getValue(name, Double.class).doubleValue();
   }
   private native double getDoubleNative(String name);
 
@@ -154,8 +175,9 @@ public int getInt(String name) {
       mJniCallCounter++;
       return getIntNative(name);
     }
+
     // All numbers coming out of native are doubles, so cast here then truncate
-    return ((Double) getValue(name)).intValue();
+    return getValue(name, Double.class).intValue();
   }
   private native int getIntNative(String name);
 
@@ -165,7 +187,7 @@ public int getInt(String name) {
       mJniCallCounter++;
       return getStringNative(name);
     }
-    return (String) getNullableValue(name);
+    return getNullableValue(name, String.class);
   }
   private native String getStringNative(String name);
 
@@ -175,7 +197,7 @@ public int getInt(String name) {
       mJniCallCounter++;
       return getArrayNative(name);
     }
-    return (ReadableArray) getNullableValue(name);
+    return getNullableValue(name, ReadableArray.class);
   }
   private native ReadableNativeArray getArrayNative(String name);
 
@@ -185,7 +207,7 @@ public int getInt(String name) {
       mJniCallCounter++;
       return getMapNative(name);
     }
-    return (ReadableNativeMap) getNullableValue(name);
+    return getNullableValue(name, ReadableNativeMap.class);
   }
   private native ReadableNativeMap getMapNative(String name);
 

From 4d99daaa914398b24e9783b47858434e25bb5fcb Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 7 May 2018 12:23:50 -0700
Subject: [PATCH 0445/1109] Fix RNTester WebBrowser example

Reviewed By: yungsters

Differential Revision: D7890708

fbshipit-source-id: e96c2283f92ae151152f89bebd95141852ff40b1
---
 RNTester/js/WebViewExample.js | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/RNTester/js/WebViewExample.js b/RNTester/js/WebViewExample.js
index d55d17ca60ec..84b99001ecf5 100644
--- a/RNTester/js/WebViewExample.js
+++ b/RNTester/js/WebViewExample.js
@@ -27,6 +27,7 @@ var DISABLED_WASH = 'rgba(255,255,255,0.25)';
 var TEXT_INPUT_REF = 'urlInput';
 var WEBVIEW_REF = 'webview';
 var DEFAULT_URL = 'https://m.facebook.com';
+const FILE_SYSTEM_ORIGIN_WHITE_LIST = ['file://*', 'http://*', 'https://*'];
 
 class WebViewExample extends React.Component<{}, $FlowFixMeState> {
   state = {
@@ -241,6 +242,7 @@ class MessagingTest extends React.Component<{}, $FlowFixMeState> {
               backgroundColor: BGWASH,
               height: 100,
             }}
+            originWhitelist={FILE_SYSTEM_ORIGIN_WHITE_LIST}
             source={require('./messagingtest.html')}
             onMessage={this.onMessage}
           />
@@ -414,6 +416,7 @@ exports.examples = [
             backgroundColor: BGWASH,
             height: 100,
           }}
+          originWhitelist={FILE_SYSTEM_ORIGIN_WHITE_LIST}
           source={require('./helloworld.html')}
           scalesPageToFit={true}
         />

From 15f8d7013c2308fe708599f82eba08d2c9ba743f Mon Sep 17 00:00:00 2001
From: Chirag Jain <jain_chirag04@yahoo.com>
Date: Mon, 7 May 2018 14:24:32 -0700
Subject: [PATCH 0446/1109] CI: fix watchman install errors and update ios
 simulators to version 11.2

Summary:
Fixes watchman install errors.

Check that iphone 5s is booted properly on circle. Check brew install watchman succeeds.

[CI] - Fix ios version on circleci and fixes brew install watchman error
Closes https://github.com/facebook/react-native/pull/19166

Differential Revision: D7899295

Pulled By: hramos

fbshipit-source-id: 2260a2675879cf97fb0b2f11139d9bb84ce7444e
---
 .circleci/config.yml | 56 ++++++++++++++++++++++++--------------------
 1 file changed, 30 insertions(+), 26 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 7452d4bd43a7..23c9472731c6 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -147,7 +147,7 @@ aliases:
         git clone https://github.com/uber/okbuck.git ~/okbuck --depth=1
       fi
       mkdir -p ~/react-native/tooling/junit
-      cp -R ~/okbuck/tooling/junit/* ~/react-native/tooling/junit/.      
+      cp -R ~/okbuck/tooling/junit/* ~/react-native/tooling/junit/.
 
 
   - &install-node
@@ -214,7 +214,7 @@ aliases:
   - &gradle-download-deps
     name: Download C++ Dependencies
     command: ./scripts/circleci/gradle_download_deps.sh
-    
+
   - &build-android-app
     name: Build Android App
     command: |
@@ -224,7 +224,7 @@ aliases:
   - &create-avd
     name: Create Android Virtual Device
     command: source scripts/circle-ci-android-setup.sh && createAVD
- 
+
   - &launch-avd
     name: Launch Android Virtual Device in Background
     command: source scripts/circle-ci-android-setup.sh && launchAVD
@@ -250,11 +250,11 @@ aliases:
   - &run-android-instrumentation-tests
     name: Run Instrumentation Tests
     command: |
-      if [[ ! -e ReactAndroid/src/androidTest/assets/AndroidTestBundle.js ]]; then	
+      if [[ ! -e ReactAndroid/src/androidTest/assets/AndroidTestBundle.js ]]; then
         echo "JavaScript bundle missing, cannot run instrumentation tests. Verify build-js-bundle step completed successfully."; exit 1;
       fi
       source scripts/circle-ci-android-setup.sh && NO_BUCKD=1 retry3 timeout 300 buck install ReactAndroid/src/androidTest/buck-runner:instrumentation-tests --config build.threads=$BUILD_THREADS
-  
+
   - &collect-android-test-results
     name: Collect Test Results
     command: |
@@ -266,12 +266,12 @@ aliases:
 
   - &setup-artifacts
     name: Initial Setup
-    command: | 
+    command: |
       mkdir -p ~/react-native/reports/buck/
       mkdir -p ~/react-native/reports/build/
       mkdir -p ~/react-native/reports/junit/
       mkdir -p ~/react-native/reports/outputs/
-  
+
   - &run-objc-ios-tests
     name: iOS Test Suite
     command: ./scripts/objc-test-ios.sh test
@@ -390,7 +390,9 @@ jobs:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "iPhone 5s (11.1)" || true
+      - run: xcrun instruments -w "iPhone 5s (11.2)" || true
+      # See https://github.com/Homebrew/homebrew-core/issues/26358.
+      - run: brew upgrade python > /dev/null
       - run: brew install watchman
       - run: *run-objc-ios-tests
 
@@ -404,7 +406,9 @@ jobs:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "Apple TV 1080p (11.1)" || true
+      - run: xcrun instruments -w "Apple TV 1080p (11.2)" || true
+      # See https://github.com/Homebrew/homebrew-core/issues/26358.
+      - run: brew upgrade python > /dev/null
       - run: brew install watchman
       - run: *run-objc-tvos-tests
 
@@ -418,7 +422,7 @@ jobs:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "iPhone 5s (11.1)" || true
+      - run: xcrun instruments -w "iPhone 5s (11.2)" || true
       - run: *run-objc-ios-e2e-tests
 
       - store_test_results:
@@ -432,14 +436,14 @@ jobs:
           at: ~/react-native
 
       - run: ./scripts/process-podspecs.sh
-      
+
   # Publishes new version onto npm
   publish_npm_package:
     <<: *android_defaults
     steps:
       # Checkout code so that we can work with `git` in publish.js
       - checkout
-      
+
       # Configure Android SDK and related dependencies
       - run: *configure-android-path
       - run: *install-android-build-dependencies
@@ -472,7 +476,7 @@ jobs:
       - restore-cache: *restore-cache-yarn
       - run: *yarn
       - save-cache: *save-cache-yarn
-      
+
       - run:
           name: Publish React Native Package
           command: |
@@ -483,7 +487,7 @@ jobs:
               echo "machine github.com login reactjs-bot password $GITHUB_TOKEN" > ~/.netrc
               node ./scripts/publish-npm.js
             else
-              echo "Skipping deploy."            
+              echo "Skipping deploy."
             fi
 
   # Set up an Android environment for downstream jobs
@@ -505,7 +509,7 @@ jobs:
 
       - run: *validate-android-sdk
 
-      # Starting emulator in advance as it takes some time to boot.      
+      # Starting emulator in advance as it takes some time to boot.
       - run: *create-avd
       - run: *launch-avd
 
@@ -547,7 +551,7 @@ jobs:
       # Test Suite
       - run: *run-android-unit-tests
       - run: *run-android-instrumentation-tests
-      
+
       # Collect Results
       - run: *collect-android-test-results
       - store_test_results:
@@ -572,7 +576,7 @@ jobs:
               cd bots
               yarn install --non-interactive --cache-folder ~/.cache/yarn
             else
-              echo "Skipping dependency installation."            
+              echo "Skipping dependency installation."
             fi
       - save-cache: *save-cache-analysis
 
@@ -583,7 +587,7 @@ jobs:
             if [ -n "$CIRCLE_PR_NUMBER" ]; then
               cd bots && DANGER_GITHUB_API_TOKEN="b186c9a82bab3b08ec80""c0818117619eec6f281a" yarn danger
             else
-              echo "Skipping pull request analysis."            
+              echo "Skipping pull request analysis."
             fi
           when: always
       - run:
@@ -593,7 +597,7 @@ jobs:
             if [ -n "$CIRCLE_PR_NUMBER" ]; then
               GITHUB_TOKEN="af6ef0d15709bc91d""06a6217a5a826a226fb57b7" CI_USER=$CIRCLE_PROJECT_USERNAME CI_REPO=$CIRCLE_PROJECT_REPONAME PULL_REQUEST_NUMBER=$CIRCLE_PR_NUMBER scripts/circleci/analyze_code.sh
             else
-              echo "Skipping code analysis."            
+              echo "Skipping code analysis."
             fi
           when: always
 
@@ -652,16 +656,16 @@ workflows:
       # Checkout repo and run Yarn
       - checkout_code:
           filters: *filter-ignore-master-stable
-          
+
       # Run code checks
-      - analyze_pr:            
+      - analyze_pr:
           filters: *filter-ignore-master-stable
-          requires:            
+          requires:
             - checkout_code
 
   # Only runs on NN-stable branches
   deploy:
-    jobs:          
+    jobs:
       # If we are on a stable branch, wait for approval to deploy to npm
       - approve_publish_npm_package:
           filters: *filter-only-stable
@@ -671,9 +675,9 @@ workflows:
           requires:
             - approve_publish_npm_package
 
-  # These tests are flaky or are yet to be fixed. They are placed on their own 
+  # These tests are flaky or are yet to be fixed. They are placed on their own
   # workflow to avoid marking benign PRs as broken.
-  # To run them, uncomment the entire block and open a PR (do not merge). 
+  # To run them, uncomment the entire block and open a PR (do not merge).
   # Once a test is fixed, move the test definition to the 'tests' workflow.
   # disabled_tests:
   #   jobs:
@@ -681,7 +685,7 @@ workflows:
   #     - checkout_code:
   #         filters: *filter-ignore-gh-pages
 
-  #     # The following were DISABLED because they have not run since 
+  #     # The following were DISABLED because they have not run since
   #     # the migration from Travis, and they have broken since then,
   #     # CocoaPods
   #     - test_podspec:

From 3145b1e62aca20b6a8bc69f76036c853db3aeaae Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Mon, 7 May 2018 14:25:32 -0700
Subject: [PATCH 0447/1109] Update IssueCommands.txt

Summary:
Use new labels.
Closes https://github.com/facebook/react-native/pull/19165

Differential Revision: D7899306

Pulled By: hramos

fbshipit-source-id: 9a36426bcdd4af110b5c29e186b66e7eadcf69cd
---
 bots/IssueCommands.txt | 18 +++++++++---------
 1 file changed, 9 insertions(+), 9 deletions(-)

diff --git a/bots/IssueCommands.txt b/bots/IssueCommands.txt
index 20ef511ff76b..0c73a582e065 100644
--- a/bots/IssueCommands.txt
+++ b/bots/IssueCommands.txt
@@ -14,7 +14,7 @@ close
 
 @facebook-github-bot stack-overflow
 comment Hey {issue_author}, thanks for posting this! {author} tells me this issue looks like a question that would be best asked on [Stack Overflow](https://stackoverflow.com/questions/tagged/react-native). Stack Overflow is amazing for Q&A: it has a reputation system, voting, the ability to mark a question as answered. Because of the reputation system it is likely the community will see and answer your question there. This also helps us use the GitHub bug tracker for bugs only.<br/><br/><sub>[How to Contribute](https://facebook.github.io/react-native/docs/contributing.html#bugs) • [What to Expect from Maintainers](https://facebook.github.io/react-native/docs/maintainers.html#handling-issues)</sub>
-add-label For Stack Overflow
+add-label ":no_entry_sign:For Stack Overflow"
 close
 
 @facebook-github-bot label (.*)
@@ -22,12 +22,12 @@ add-label {match0}
 
 @facebook-github-bot no-reply
 comment Closing this issue as more information is needed to debug this and we haven't heard back from the author.
-add-label Needs Response from Author
+add-label ":grey_question:Needs More Information"
 close
 
 @facebook-github-bot no-template
 comment Hey {issue_author}, thanks for posting this! It looks like your issue is missing some required information. Can you please add all the details specified in the [Issue Template](https://raw.githubusercontent.com/facebook/react-native/master/.github/ISSUE_TEMPLATE.md)? This is necessary for people to be able to understand and reproduce your issue. I am going to close this, but please feel free to open a new issue with the additional information provided. Thanks!<br/><br/><sub>[How to Contribute](https://facebook.github.io/react-native/docs/contributing.html#bugs) • [What to Expect from Maintainers](https://facebook.github.io/react-native/docs/maintainers.html#handling-issues)</sub>
-add-label Needs more information
+add-label ":grey_question:Needs More Information"
 close
 
 @facebook-github-bot close
@@ -36,16 +36,16 @@ close
 
 @facebook-github-bot large-pr
 comment Thank you for your contribution. Unfortunately, this pull request seems relatively large.<br/><br/>In order to reduce the load on maintainers, it would be valuable if you could [split this into small, targeted PRs that changed one thing at a time](https://graysonkoonce.com/stacked-pull-requests-keeping-github-diffs-small/).<br/><br/>If doing this requires more than a few pull requests, please open (or update) an issue specifying your goal and the different steps you will take in your PRs. This will ensure maintainers have context on the relationship between the PRs.<br/><br/>If this is a codemod or other formatting change that is simple but inherently touches many files, please comment on this and let us know and we will reopen the PR.
-add-label Large PR
+add-label ":clipboard:Large PR :bangbang:"
 close
 
 @facebook-github-bot bugfix
 comment Hey {issue_author}, if you're sure this is a bug, can you send a pull request with a fix?<br/><br/><sub>[How to Contribute](https://facebook.github.io/react-native/docs/contributing.html#bugs) • [What to Expect from Maintainers](https://facebook.github.io/react-native/docs/maintainers.html#handling-issues)</sub>
-add-label Help Wanted
+add-label "Help Wanted :octocat:"
 
 @facebook-github-bot needs-repro
 comment Can you reproduce the issue using [Snack](https://snack.expo.io)? This step is necessary for people to be able to see and debug the issue being reported.<br/><br/><sub>[How to Contribute](https://facebook.github.io/react-native/docs/contributing.html#bugs) • [What to Expect from Maintainers](https://facebook.github.io/react-native/docs/maintainers.html#handling-issues)</sub>
-add-label Needs more information
+add-label ":grey_question:Needs More Information"
 
 @facebook-github-bot cannot-repro
 comment Thanks for opening the issue! It does not appear like a community member will be able to reliably reproduce this issue. This may be for several reasons; perhaps it affects a particular app but a minimal repro has not been provided, or the issue may be sporadic. As it happens, we need a concrete set of steps that can demonstrably reproduce the issue as this will allow your fellow community members to validate a fix. We'll close the issue for now, but feel free to submit a new issue once you're able to reliably reproduce the issue locally. Thanks for your understanding!<br/><br/><sub>[How to Contribute](https://facebook.github.io/react-native/docs/contributing.html#bugs) • [What to Expect from Maintainers](https://facebook.github.io/react-native/docs/maintainers.html#handling-issues)</sub>
@@ -57,14 +57,14 @@ reopen
 
 @facebook-github-bot feature
 comment Hey {issue_author}! Thanks for opening the issue, however it looks like a feature request. As noted in the [Issue template](https://raw.githubusercontent.com/facebook/react-native/master/.github/ISSUE_TEMPLATE.md) we'd like to use the GitHub issues to track bugs only. Can you implement the feature as a standalone npm module? If not, consider sending a pull request or a creating an entry on [Canny](https://react-native.canny.io/feature-requests/). It has a voting system and if the feature gets upvoted enough it might get implemented. Closing this now, thanks for understanding!<br/><br/><sub>[How to Contribute](https://facebook.github.io/react-native/docs/contributing.html#bugs) • [What to Expect from Maintainers](https://facebook.github.io/react-native/docs/maintainers.html#handling-issues)</sub>
-add-label Feature Request
+add-label ":star2:Feature Request"
 close
 
 @facebook-github-bot cla
 comment Hey {issue_author}! Thanks for sending this pull request! We would love to review your changes however it looks like you haven't signed the CLA yet. You can do so at https://code.facebook.com/cla. See ["How to Contribute"](https://facebook.github.io/react-native/docs/contributing.html#pull-requests) to learn more.
-add-label Needs Response from Author
+add-label ":grey_question:Needs More Information"
 
 @facebook-github-bot icebox
 comment {author} tells me to close this issue because it has been inactive for a while. Maybe the issue has been fixed in a recent release, or perhaps it is not affecting a lot of people. Either way, we're automatically closing issues after a period of inactivity. Please do not take it personally!<br/><br/>If you think this issue should definitely remain open, please let us know. The following information is helpful when it comes to determining if the issue should be re-opened: <ul><li>Does the issue still reproduce on the latest release candidate? Post a comment with the version you tested.</li><li>If so, is there any information missing from the bug report? Post a comment with all the information required by the [issue template](https://github.com/facebook/react-native/blob/master/.github/ISSUE_TEMPLATE.md).</li><li>Is there a pull request that addresses this issue? Post a comment with the PR number so we can follow up.</li></ul>If you would like to work on a patch to fix the issue, *contributions are very welcome*! Read through the [contribution guide](https://facebook.github.io/react-native/docs/contributing.html), and feel free to hop into [#react-native](https://discordapp.com/invite/0ZcbPKXt5bZjGY5n) if you need help planning your contribution.<br/><br/><sub>[How to Contribute](https://facebook.github.io/react-native/docs/contributing.html#bugs) • [What to Expect from Maintainers](https://facebook.github.io/react-native/docs/maintainers.html#handling-issues)</sub>
-add-label Icebox
+add-label Stale
 close

From 1be2541ce2bbe328362d19e3eff65f3e89527105 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Mon, 7 May 2018 14:53:28 -0700
Subject: [PATCH 0448/1109] Add assertion to ensure copied shadow nodes are of
 the same type as the original

Reviewed By: mdvacca

Differential Revision: D7664638

fbshipit-source-id: e1b7acbafd8a8fd9d6301d8afbb3e5959dc15b7a
---
 .../react/uimanager/ReactShadowNodeImpl.java  |  6 ++++++
 .../react/fabric/ReactShadowNodeTest.java     | 20 +++++++++++++++++++
 2 files changed, 26 insertions(+)
 create mode 100644 ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index a8118b1841d0..ff009b5b2c29 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -166,6 +166,9 @@ protected ReactShadowNodeImpl copy() {
   @Override
   public ReactShadowNodeImpl mutableCopy() {
     ReactShadowNodeImpl copy = copy();
+    Assertions.assertCondition(
+        getClass() == copy.getClass(),
+        "Copied shadow node must use the same class");
     if (mYogaNode != null) {
       copy.mYogaNode = mYogaNode.clone();
       copy.mYogaNode.setData(copy);
@@ -182,6 +185,9 @@ public ReactShadowNodeImpl mutableCopy() {
   @Override
   public ReactShadowNodeImpl mutableCopyWithNewChildren() {
     ReactShadowNodeImpl copy = copy();
+    Assertions.assertCondition(
+        getClass() == copy.getClass(),
+        "Copied shadow node must use the same class");
     if (mYogaNode != null) {
       copy.mYogaNode = mYogaNode.cloneWithNewChildren();
       copy.mYogaNode.setData(copy);
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
new file mode 100644
index 000000000000..1b14c9fc9c42
--- /dev/null
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
@@ -0,0 +1,20 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+package com.facebook.react.fabric;
+
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
+import com.facebook.testing.robolectric.v3.WithTestDefaultsRunner;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+/** Tests {@link ReactShadowNode} */
+@RunWith(WithTestDefaultsRunner.class)
+public class ReactShadowNodeTest {
+
+  @Test(expected = AssertionError.class)
+  public void testClonedInstance() {
+    TestReactShadowNode node = new TestReactShadowNode();
+    node.mutableCopy();
+  }
+
+  private static class TestReactShadowNode extends ReactShadowNodeImpl {}
+}

From 1c90a2b47b420a4b6aa16a55a344cc08f0eacbe3 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 7 May 2018 16:45:11 -0700
Subject: [PATCH 0449/1109] RN: Fix `requireNativeComponent` Check

Reviewed By: sahrens, TheSavior

Differential Revision: D7893594

fbshipit-source-id: 83f6995842e9480382c0b2abf6b6e72c6c107a49
---
 Libraries/ReactNative/requireNativeComponent.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index 0e09ad9f8096..6d215e79fb77 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -101,7 +101,7 @@ function requireNativeComponent(
     const viewConfig = UIManager[viewName];
 
     invariant(
-      viewConfig != null && !viewConfig.NativeProps != null,
+      viewConfig != null && viewConfig.NativeProps != null,
       'Native component for "%s" does not exist',
       viewName,
     );

From 28d37781c6589574de1113bd12077f6d54053ffb Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 7 May 2018 16:45:14 -0700
Subject: [PATCH 0450/1109] RN: Optimize View Attribute Initialization

Reviewed By: sahrens

Differential Revision: D7893593

fbshipit-source-id: a425e841c9c86b063803878c7b07704c8a90a83a
---
 .../ReactNative/requireNativeComponent.js     | 85 ++++++++++---------
 1 file changed, 46 insertions(+), 39 deletions(-)

diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index 6d215e79fb77..dd44ea60b936 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -141,22 +141,12 @@ function requireNativeComponent(
     viewConfig.directEventTypes = directEventTypes;
 
     for (const key in nativeProps) {
-      let useAttribute = false;
-      const attribute = {};
+      const typeName = nativeProps[key];
+      const diff = getDifferForType(typeName);
+      const process = getProcessorForType(typeName);
 
-      const differ = TypeToDifferMap[nativeProps[key]];
-      if (differ) {
-        attribute.diff = differ;
-        useAttribute = true;
-      }
-
-      const processor = TypeToProcessorMap[nativeProps[key]];
-      if (processor) {
-        attribute.process = processor;
-        useAttribute = true;
-      }
-
-      viewConfig.validAttributes[key] = useAttribute ? attribute : true;
+      viewConfig.validAttributes[key] =
+        diff == null && process == null ? true : {diff, process};
     }
 
     // Unfortunately, the current set up puts the style properties on the top
@@ -186,32 +176,49 @@ function requireNativeComponent(
   return createReactNativeComponentClass(viewName, getViewConfig);
 }
 
-const TypeToDifferMap = {
-  // iOS Types
-  CATransform3D: matricesDiffer,
-  CGPoint: pointsDiffer,
-  CGSize: sizesDiffer,
-  UIEdgeInsets: insetsDiffer,
-  // Android Types
-  // (not yet implemented)
-};
+function getDifferForType(
+  typeName: string,
+): ?(prevProp: any, nextProp: any) => boolean {
+  switch (typeName) {
+    // iOS Types
+    case 'CATransform3D':
+      return matricesDiffer;
+    case 'CGPoint':
+      return pointsDiffer;
+    case 'CGSize':
+      return sizesDiffer;
+    case 'UIEdgeInsets':
+      return insetsDiffer;
+    // Android Types
+    // (not yet implemented)
+  }
+  return null;
+}
+
+function getProcessorForType(typeName: string): ?(nextProp: any) => any {
+  switch (typeName) {
+    // iOS Types
+    case 'CGColor':
+    case 'UIColor':
+      return processColor;
+    case 'CGColorArray':
+    case 'UIColorArray':
+      return processColorArray;
+    case 'CGImage':
+    case 'UIImage':
+    case 'RCTImageSource':
+      return resolveAssetSource;
+    // Android Types
+    case 'Color':
+      return processColor;
+    case 'ColorArray':
+      return processColorArray;
+  }
+  return null;
+}
 
 function processColorArray(colors: ?Array<any>): ?Array<?number> {
-  return colors && colors.map(processColor);
+  return colors == null ? null : colors.map(processColor);
 }
 
-const TypeToProcessorMap = {
-  // iOS Types
-  CGColor: processColor,
-  CGColorArray: processColorArray,
-  UIColor: processColor,
-  UIColorArray: processColorArray,
-  CGImage: resolveAssetSource,
-  UIImage: resolveAssetSource,
-  RCTImageSource: resolveAssetSource,
-  // Android Types
-  Color: processColor,
-  ColorArray: processColorArray,
-};
-
 module.exports = requireNativeComponent;

From b549e364e0025e0e1b4005f04a9de2d767006da1 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 7 May 2018 16:45:16 -0700
Subject: [PATCH 0451/1109] RN: Simpify `requireNativeComponent`

Reviewed By: sahrens

Differential Revision: D7893592

fbshipit-source-id: bfe7772ff2fa785fc7c5ad1f7dc0dbe97b6ffb11
---
 .../ReactNative/requireNativeComponent.js     | 163 +++++++++---------
 1 file changed, 85 insertions(+), 78 deletions(-)

diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index dd44ea60b936..fae553f27ce6 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -7,6 +7,7 @@
  * @flow
  * @format
  */
+
 'use strict';
 
 const Platform = require('Platform');
@@ -24,6 +25,14 @@ const verifyPropTypes = require('verifyPropTypes');
 const invariant = require('fbjs/lib/invariant');
 const warning = require('fbjs/lib/warning');
 
+import type {ComponentInterface} from 'verifyPropTypes';
+
+type ExtraOptions = $ReadOnly<{|
+  nativeOnly?: $ReadOnly<{
+    [propName: string]: boolean,
+  }>,
+|}>;
+
 /**
  * Used to create React components that directly wrap native component
  * implementations.  Config information is extracted from data exported from the
@@ -39,81 +48,23 @@ const warning = require('fbjs/lib/warning');
  * Common types are lined up with the appropriate prop differs with
  * `TypeToDifferMap`.  Non-scalar types not in the map default to `deepDiffer`.
  */
-import type {ComponentInterface} from 'verifyPropTypes';
-
-let hasAttachedDefaultEventTypes: boolean = false;
-
-function requireNativeComponent(
+const requireNativeComponent = (
   viewName: string,
   componentInterface?: ?ComponentInterface,
-  extraConfig?: ?{nativeOnly?: Object},
-): React$ComponentType<any> | string {
-  function attachDefaultEventTypes(viewConfig: any) {
-    // This is supported on UIManager platforms (ex: Android),
-    // as lazy view managers are not implemented for all platforms.
-    // See [UIManager] for details on constants and implementations.
-    if (UIManager.ViewManagerNames) {
-      // Lazy view managers enabled.
-      viewConfig = merge(viewConfig, UIManager.getDefaultEventTypes());
-    } else {
-      viewConfig.bubblingEventTypes = merge(
-        viewConfig.bubblingEventTypes,
-        UIManager.genericBubblingEventTypes,
-      );
-      viewConfig.directEventTypes = merge(
-        viewConfig.directEventTypes,
-        UIManager.genericDirectEventTypes,
-      );
-    }
-  }
-
-  function merge(destination: ?Object, source: ?Object): ?Object {
-    if (!source) {
-      return destination;
-    }
-    if (!destination) {
-      return source;
-    }
-
-    for (const key in source) {
-      if (!source.hasOwnProperty(key)) {
-        continue;
-      }
-
-      var sourceValue = source[key];
-      if (destination.hasOwnProperty(key)) {
-        const destinationValue = destination[key];
-        if (
-          typeof sourceValue === 'object' &&
-          typeof destinationValue === 'object'
-        ) {
-          sourceValue = merge(destinationValue, sourceValue);
-        }
-      }
-      destination[key] = sourceValue;
-    }
-    return destination;
-  }
-
-  // Don't load the ViewConfig from UIManager until it's needed for rendering.
-  // Lazy-loading this can help avoid Prepack deopts.
-  function getViewConfig() {
+  extraConfig?: ?ExtraOptions,
+): string =>
+  createReactNativeComponentClass(viewName, () => {
     const viewConfig = UIManager[viewName];
 
     invariant(
       viewConfig != null && viewConfig.NativeProps != null,
-      'Native component for "%s" does not exist',
+      'requireNativeComponent: "%s" was not found in the UIManager.',
       viewName,
     );
 
-    viewConfig.uiViewClassName = viewName;
-    viewConfig.validAttributes = {};
-    viewConfig.propTypes =
-      componentInterface == null ? null : componentInterface.propTypes;
-
-    let baseModuleName = viewConfig.baseModuleName;
-    let bubblingEventTypes = viewConfig.bubblingEventTypes;
-    let directEventTypes = viewConfig.directEventTypes;
+    // TODO: This seems like a whole lot of runtime initialization for every
+    // native component that can be either avoided or simplified.
+    let {baseModuleName, bubblingEventTypes, directEventTypes} = viewConfig;
     let nativeProps = viewConfig.NativeProps;
     while (baseModuleName) {
       const baseModule = UIManager[baseModuleName];
@@ -137,32 +88,40 @@ function requireNativeComponent(
       }
     }
 
-    viewConfig.bubblingEventTypes = bubblingEventTypes;
-    viewConfig.directEventTypes = directEventTypes;
+    const viewAttributes = {};
 
     for (const key in nativeProps) {
       const typeName = nativeProps[key];
       const diff = getDifferForType(typeName);
       const process = getProcessorForType(typeName);
 
-      viewConfig.validAttributes[key] =
+      viewAttributes[key] =
         diff == null && process == null ? true : {diff, process};
     }
 
-    // Unfortunately, the current set up puts the style properties on the top
-    // level props object. We also need to add the nested form for API
-    // compatibility. This allows these props on both the top level and the
-    // nested style level. TODO: Move these to nested declarations on the
-    // native side.
-    viewConfig.validAttributes.style = ReactNativeStyleAttributes;
+    // Unfortunately, the current setup declares style properties as top-level
+    // props. This makes it so we allow style properties in the `style` prop.
+    // TODO: Move style properties into a `style` prop and disallow them as
+    // top-level props on the native side.
+    viewAttributes.style = ReactNativeStyleAttributes;
+
+    Object.assign(viewConfig, {
+      uiViewClassName: viewName,
+      validAttributes: viewAttributes,
+      propTypes:
+        componentInterface == null ? null : componentInterface.propTypes,
+      bubblingEventTypes,
+      directEventTypes,
+    });
 
     if (__DEV__) {
-      componentInterface &&
+      if (componentInterface != null) {
         verifyPropTypes(
           componentInterface,
           viewConfig,
-          extraConfig && extraConfig.nativeOnly,
+          extraConfig == null ? null : extraConfig.nativeOnly,
         );
+      }
     }
 
     if (!hasAttachedDefaultEventTypes) {
@@ -171,9 +130,57 @@ function requireNativeComponent(
     }
 
     return viewConfig;
+  });
+
+// TODO: Figure out how this makes sense. We're using a global boolean to only
+// initialize this on the first eagerly initialized native component.
+let hasAttachedDefaultEventTypes = false;
+function attachDefaultEventTypes(viewConfig: any) {
+  // This is supported on UIManager platforms (ex: Android),
+  // as lazy view managers are not implemented for all platforms.
+  // See [UIManager] for details on constants and implementations.
+  if (UIManager.ViewManagerNames) {
+    // Lazy view managers enabled.
+    viewConfig = merge(viewConfig, UIManager.getDefaultEventTypes());
+  } else {
+    viewConfig.bubblingEventTypes = merge(
+      viewConfig.bubblingEventTypes,
+      UIManager.genericBubblingEventTypes,
+    );
+    viewConfig.directEventTypes = merge(
+      viewConfig.directEventTypes,
+      UIManager.genericDirectEventTypes,
+    );
   }
+}
 
-  return createReactNativeComponentClass(viewName, getViewConfig);
+// TODO: Figure out how to avoid all this runtime initialization cost.
+function merge(destination: ?Object, source: ?Object): ?Object {
+  if (!source) {
+    return destination;
+  }
+  if (!destination) {
+    return source;
+  }
+
+  for (const key in source) {
+    if (!source.hasOwnProperty(key)) {
+      continue;
+    }
+
+    let sourceValue = source[key];
+    if (destination.hasOwnProperty(key)) {
+      const destinationValue = destination[key];
+      if (
+        typeof sourceValue === 'object' &&
+        typeof destinationValue === 'object'
+      ) {
+        sourceValue = merge(destinationValue, sourceValue);
+      }
+    }
+    destination[key] = sourceValue;
+  }
+  return destination;
 }
 
 function getDifferForType(

From 820673e7076b5906ba50e09e40fb9a32cf500c1b Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 7 May 2018 16:45:19 -0700
Subject: [PATCH 0452/1109] RN: Simplify `verifyPropTypes`

Reviewed By: sahrens

Differential Revision: D7893675

fbshipit-source-id: 74d1eff57201a2af4a12c39c4335e28ff9f14090
---
 Libraries/Components/View/ViewPropTypes.js    |  2 +-
 .../ReactNative/requireNativeComponent.js     | 19 ++--
 Libraries/ReactNative/verifyPropTypes.js      | 94 ++++++++-----------
 3 files changed, 52 insertions(+), 63 deletions(-)

diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 40cd8121cd99..332059ab0a22 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -425,7 +425,7 @@ module.exports = {
    * See http://facebook.github.io/react-native/docs/view.html#needsoffscreenalphacompositing
    */
   needsOffscreenAlphaCompositing: PropTypes.bool,
-  
+
   /**
    * Any additional platform-specific view prop types, or prop type overrides.
    */
diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index fae553f27ce6..c6f2a35d352a 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -25,7 +25,13 @@ const verifyPropTypes = require('verifyPropTypes');
 const invariant = require('fbjs/lib/invariant');
 const warning = require('fbjs/lib/warning');
 
-import type {ComponentInterface} from 'verifyPropTypes';
+type ComponentInterface =
+  | React$ComponentType<any>
+  | $ReadOnly<{
+      propTypes?: $ReadOnly<{
+        [propName: string]: mixed,
+      }>,
+    }>;
 
 type ExtraOptions = $ReadOnly<{|
   nativeOnly?: $ReadOnly<{
@@ -115,13 +121,10 @@ const requireNativeComponent = (
     });
 
     if (__DEV__) {
-      if (componentInterface != null) {
-        verifyPropTypes(
-          componentInterface,
-          viewConfig,
-          extraConfig == null ? null : extraConfig.nativeOnly,
-        );
-      }
+      verifyPropTypes(
+        viewConfig,
+        extraConfig == null ? null : extraConfig.nativeOnly,
+      );
     }
 
     if (!hasAttachedDefaultEventTypes) {
diff --git a/Libraries/ReactNative/verifyPropTypes.js b/Libraries/ReactNative/verifyPropTypes.js
index c88f9c1c8029..6193b1ac1c03 100644
--- a/Libraries/ReactNative/verifyPropTypes.js
+++ b/Libraries/ReactNative/verifyPropTypes.js
@@ -4,73 +4,59 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
  * @format
+ * @flow
  */
-'use strict';
 
-var ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
+'use strict';
 
-export type ComponentInterface =
-  | React$ComponentType<any>
-  | {
-      name?: string,
-      displayName?: string,
-      propTypes?: Object,
-    };
+const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
 
 function verifyPropTypes(
-  componentInterface: ComponentInterface,
-  viewConfig: Object,
-  nativePropsToIgnore?: ?Object,
+  viewConfig: $ReadOnly<{
+    NativeProps: $ReadOnly<{
+      [propName: string]: mixed,
+    }>,
+    propTypes: ?$ReadOnly<{
+      [propName: string]: mixed,
+    }>,
+    uiViewClassName: string,
+  }>,
+  nativePropsToIgnore: ?$ReadOnly<{
+    [propName: string]: boolean,
+  }>,
 ) {
-  if (!viewConfig) {
-    return; // This happens for UnimplementedView.
-  }
-  var componentName =
-    componentInterface.displayName || componentInterface.name || 'unknown';
-
-  var propTypes = componentInterface.propTypes;
+  const {NativeProps, propTypes, uiViewClassName} = viewConfig;
 
-  if (!propTypes) {
+  if (propTypes == null) {
     return;
   }
 
-  var nativeProps = viewConfig.NativeProps;
-  for (var prop in nativeProps) {
+  for (const propName in NativeProps) {
     if (
-      !propTypes[prop] &&
-      !ReactNativeStyleAttributes[prop] &&
-      (!nativePropsToIgnore || !nativePropsToIgnore[prop])
+      propTypes[propName] ||
+      ReactNativeStyleAttributes[propName] ||
+      (nativePropsToIgnore && nativePropsToIgnore[propName])
     ) {
-      var message;
-      if (propTypes.hasOwnProperty(prop)) {
-        message =
-          '`' +
-          componentName +
-          '` has incorrectly defined propType for native prop `' +
-          viewConfig.uiViewClassName +
-          '.' +
-          prop +
-          '` of native type `' +
-          nativeProps[prop];
-      } else {
-        message =
-          '`' +
-          componentName +
-          '` has no propType for native prop `' +
-          viewConfig.uiViewClassName +
-          '.' +
-          prop +
-          '` of native type `' +
-          nativeProps[prop] +
-          '`';
-      }
-      message +=
-        "\nIf you haven't changed this prop yourself, this usually means that " +
-        'your versions of the native code and JavaScript code are out of sync. Updating both ' +
-        'should make this error go away.';
-      throw new Error(message);
+      continue;
+    }
+    const prettyName = `${uiViewClassName}.${propName}`;
+    const nativeType = String(NativeProps[propName]);
+    const suggestion =
+      '\n\nIf you have not changed this prop yourself, this usually means ' +
+      'that the versions of your native and JavaScript code are out of sync. ' +
+      'Updating both should make this error go away.';
+
+    if (propTypes.hasOwnProperty(propName)) {
+      console.error(
+        `Invalid propType to configure \`${prettyName}\` (${nativeType}).` +
+          suggestion,
+      );
+    } else {
+      console.error(
+        `Missing a propType to configure \`${prettyName}\` (${nativeType}).` +
+          suggestion,
+      );
     }
   }
 }

From 6611fefef7559c4cd3d1824235d263bff210d5e2 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Mon, 7 May 2018 17:22:26 -0700
Subject: [PATCH 0453/1109] iOS: Exposes the RCTFont size overrides so unit
 tests can use the same values

Summary:
`RCTFontTests` test in RNTester is broken if the target deployment is <= OS 8.2. This is because RCTFont.mm overrides the OS-defined values, but the override is only visible to RCTFont.mm internals. As the result, when the Unit test tries to create UIFont of the "same" weight, it got a different font - most likely due to internal floating rounding errors.

To mitigate, code that wants to test out internals of RCTFont should import RCTFontConstantsOverride.h

Reviewed By: mmmulani

Differential Revision: D7900954

fbshipit-source-id: e5814ef059a8afdfb5205ca1af46c41b3cfd4318
---
 RNTester/RNTesterUnitTests/RCTFontTests.m |  1 +
 React/React.xcodeproj/project.pbxproj     |  6 +++++
 React/Views/RCTFont.mm                    | 20 +---------------
 React/Views/RCTFontConstantsOverride.h    | 29 +++++++++++++++++++++++
 4 files changed, 37 insertions(+), 19 deletions(-)
 create mode 100644 React/Views/RCTFontConstantsOverride.h

diff --git a/RNTester/RNTesterUnitTests/RCTFontTests.m b/RNTester/RNTesterUnitTests/RCTFontTests.m
index 1d9573b489e1..5d6a3bd1b4d9 100644
--- a/RNTester/RNTesterUnitTests/RCTFontTests.m
+++ b/RNTester/RNTesterUnitTests/RCTFontTests.m
@@ -10,6 +10,7 @@
 #import <XCTest/XCTest.h>
 
 #import <React/RCTFont.h>
+#import <React/RCTFontConstantsOverride.h>
 
 @interface RCTFontTests : XCTestCase
 
diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index 8c89419471d0..ab260bb49534 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -1147,6 +1147,8 @@
 		59EDBCC61FDF4E55003573DE /* (null) in Copy Headers */ = {isa = PBXBuildFile; };
 		59EDBCC71FDF4E55003573DE /* RCTScrollView.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 59EDBCA31FDF4E0C003573DE /* RCTScrollView.h */; };
 		59EDBCC81FDF4E55003573DE /* RCTScrollViewManager.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 59EDBCA51FDF4E0C003573DE /* RCTScrollViewManager.h */; };
+		5C70426020A1004800FBEEF7 /* RCTFontConstantsOverride.h in Headers */ = {isa = PBXBuildFile; fileRef = 5C70425F20A1004800FBEEF7 /* RCTFontConstantsOverride.h */; };
+		5C70426120A1022C00FBEEF7 /* RCTFontConstantsOverride.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5C70425F20A1004800FBEEF7 /* RCTFontConstantsOverride.h */; };
 		5CE2080220772F7D009A43B3 /* YGConfig.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 5CE2080020772F7C009A43B3 /* YGConfig.cpp */; };
 		5CE2080320772F7D009A43B3 /* YGConfig.h in Headers */ = {isa = PBXBuildFile; fileRef = 5CE2080120772F7C009A43B3 /* YGConfig.h */; };
 		657734841EE834C900A0E9EA /* RCTInspectorDevServerHelper.h in Headers */ = {isa = PBXBuildFile; fileRef = 657734821EE834C900A0E9EA /* RCTInspectorDevServerHelper.h */; };
@@ -1599,6 +1601,7 @@
 			dstPath = include/React;
 			dstSubfolderSpec = 16;
 			files = (
+				5C70426120A1022C00FBEEF7 /* RCTFontConstantsOverride.h in Copy Headers */,
 				39C50FF92046EACF00CEE534 /* RCTVersion.h in Copy Headers */,
 				591F78DE202ADB8F004A668C /* RCTLayout.h in Copy Headers */,
 				59EDBCBD1FDF4E43003573DE /* RCTScrollableProtocol.h in Copy Headers */,
@@ -2240,6 +2243,7 @@
 		59EDBCA41FDF4E0C003573DE /* RCTScrollView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTScrollView.m; sourceTree = "<group>"; };
 		59EDBCA51FDF4E0C003573DE /* RCTScrollViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTScrollViewManager.h; sourceTree = "<group>"; };
 		59EDBCA61FDF4E0C003573DE /* RCTScrollViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTScrollViewManager.m; sourceTree = "<group>"; };
+		5C70425F20A1004800FBEEF7 /* RCTFontConstantsOverride.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTFontConstantsOverride.h; sourceTree = "<group>"; };
 		5CE2080020772F7C009A43B3 /* YGConfig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = YGConfig.cpp; sourceTree = "<group>"; };
 		5CE2080120772F7C009A43B3 /* YGConfig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = YGConfig.h; sourceTree = "<group>"; };
 		657734821EE834C900A0E9EA /* RCTInspectorDevServerHelper.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInspectorDevServerHelper.h; sourceTree = "<group>"; };
@@ -2561,6 +2565,7 @@
 		13B07FF31A6947C200A75B9A /* Views */ = {
 			isa = PBXGroup;
 			children = (
+				5C70425F20A1004800FBEEF7 /* RCTFontConstantsOverride.h */,
 				B95154301D1B34B200FE7B80 /* RCTActivityIndicatorView.h */,
 				B95154311D1B34B200FE7B80 /* RCTActivityIndicatorView.m */,
 				13B080181A69489C00A75B9A /* RCTActivityIndicatorViewManager.h */,
@@ -3568,6 +3573,7 @@
 				3D80DA621DF820620028D040 /* RCTAutoInsetsProtocol.h in Headers */,
 				C60128AB1F3D1258009DF9FF /* RCTCxxConvert.h in Headers */,
 				59EDBCAD1FDF4E0C003573DE /* RCTScrollContentView.h in Headers */,
+				5C70426020A1004800FBEEF7 /* RCTFontConstantsOverride.h in Headers */,
 				59EDBCA71FDF4E0C003573DE /* RCTScrollableProtocol.h in Headers */,
 				591F78DC202ADB22004A668C /* RCTLayout.h in Headers */,
 				5CE2080320772F7D009A43B3 /* YGConfig.h in Headers */,
diff --git a/React/Views/RCTFont.mm b/React/Views/RCTFont.mm
index 3fb3e36177cd..8753510d9165 100644
--- a/React/Views/RCTFont.mm
+++ b/React/Views/RCTFont.mm
@@ -7,31 +7,13 @@
 
 #import "RCTAssert.h"
 #import "RCTFont.h"
+#import "RCTFontConstantsOverride.h"
 #import "RCTLog.h"
 
 #import <CoreText/CoreText.h>
 
 #import <mutex>
 
-#if !defined(__IPHONE_8_2) || __IPHONE_OS_VERSION_MIN_REQUIRED < __IPHONE_8_2
-
-// These constants are defined in iPhone SDK 8.2, but the app cannot run on
-// iOS < 8.2 unless we redefine them here. If you target iOS 8.2 or above
-// as a base target, the standard constants will be used instead.
-// These constants can only be removed when React Native drops iOS8 support.
-
-#define UIFontWeightUltraLight -0.8
-#define UIFontWeightThin -0.6
-#define UIFontWeightLight -0.4
-#define UIFontWeightRegular 0
-#define UIFontWeightMedium 0.23
-#define UIFontWeightSemibold 0.3
-#define UIFontWeightBold 0.4
-#define UIFontWeightHeavy 0.56
-#define UIFontWeightBlack 0.62
-
-#endif
-
 typedef CGFloat RCTFontWeight;
 static RCTFontWeight weightOfFont(UIFont *font)
 {
diff --git a/React/Views/RCTFontConstantsOverride.h b/React/Views/RCTFontConstantsOverride.h
new file mode 100644
index 000000000000..1563e92e7bca
--- /dev/null
+++ b/React/Views/RCTFontConstantsOverride.h
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+// NOTE: Include this header file to ensure consistency of the constants defined here.
+// The values are the ones used in RCTFont.mm.
+// Example: import it for testing RCTFont internals in a unit test.
+
+#if !defined(__IPHONE_8_2) || __IPHONE_OS_VERSION_MIN_REQUIRED < __IPHONE_8_2
+
+// These constants are defined in iPhone SDK 8.2, but the app cannot run on
+// iOS < 8.2 unless we redefine them here. If you target iOS 8.2 or above
+// as a base target, the standard constants will be used instead.
+// These constants can only be removed when React Native drops iOS8 support.
+
+#define UIFontWeightUltraLight -0.8
+#define UIFontWeightThin -0.6
+#define UIFontWeightLight -0.4
+#define UIFontWeightRegular 0
+#define UIFontWeightMedium 0.23
+#define UIFontWeightSemibold 0.3
+#define UIFontWeightBold 0.4
+#define UIFontWeightHeavy 0.56
+#define UIFontWeightBlack 0.62
+
+#endif

From e2287976f369ed741a2ef8c2954a629a23b003cf Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 7 May 2018 17:43:07 -0700
Subject: [PATCH 0454/1109] Fabric/Text: attributedstring module, the first
 part

Summary:
`fabric/attributedstring` is a simple, cross-platfrom, react-specific implementation of attributed string (aka spanned string).
This diff is the first part of this which contains text primitives (types) and conversions.

Reviewed By: fkgozali

Differential Revision: D7748704

fbshipit-source-id: d76e31807e5ac7ab1a16fd6ee6445c59de5b89a2
---
 React.podspec                                 |  10 +-
 ReactCommon/fabric/attributedstring/BUCK      |  78 ++++++++++++
 .../attributedstring/ParagraphAttributes.cpp  |  37 ++++++
 .../attributedstring/ParagraphAttributes.h    |  65 ++++++++++
 .../fabric/attributedstring/TextPrimitives.h  |  94 ++++++++++++++
 .../tests/AttributedStringTest.cpp            |  18 +++
 .../attributedstring/textValuesConversions.h  | 120 ++++++++++++++++++
 7 files changed, 421 insertions(+), 1 deletion(-)
 create mode 100644 ReactCommon/fabric/attributedstring/BUCK
 create mode 100644 ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
 create mode 100644 ReactCommon/fabric/attributedstring/ParagraphAttributes.h
 create mode 100644 ReactCommon/fabric/attributedstring/TextPrimitives.h
 create mode 100644 ReactCommon/fabric/attributedstring/tests/AttributedStringTest.cpp
 create mode 100644 ReactCommon/fabric/attributedstring/textValuesConversions.h

diff --git a/React.podspec b/React.podspec
index 030989c3d317..b985ee3ea9c4 100644
--- a/React.podspec
+++ b/React.podspec
@@ -149,6 +149,15 @@ Pod::Spec.new do |s|
   end
 
   s.subspec "fabric" do |ss|
+    ss.subspec "attributedstring" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/attributedstring/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/attributedstring"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
     ss.subspec "core" do |sss|
       sss.dependency             "Folly", folly_version
       sss.compiler_flags       = folly_compiler_flags
@@ -194,7 +203,6 @@ Pod::Spec.new do |s|
       sss.header_dir           = "fabric/view"
       sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
     end
-
   end
 
   s.subspec "ART" do |ss|
diff --git a/ReactCommon/fabric/attributedstring/BUCK b/ReactCommon/fabric/attributedstring/BUCK
new file mode 100644
index 000000000000..625639db36ef
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/BUCK
@@ -0,0 +1,78 @@
+load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+
+rn_xplat_cxx_library(
+    name = "attributedstring",
+    srcs = glob(
+        ["**/*.cpp"],
+        excludes = glob(["tests/**/*.cpp"]),
+    ),
+    headers = glob(
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
+    ),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/attributedstring",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    force_static = True,
+    macosx_tests_override = [],
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":attributedstring",
+        ],
+    )
diff --git a/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp b/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
new file mode 100644
index 000000000000..3901c18cf38b
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
@@ -0,0 +1,37 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ParagraphAttributes.h"
+
+#include <fabric/attributedstring/textValuesConversions.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+namespace facebook {
+namespace react {
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList ParagraphAttributes::getDebugProps() const {
+  ParagraphAttributes defaultParagraphAttributes = {};
+  SharedDebugStringConvertibleList list = {};
+
+#define PARAGRAPH_ATTRIBUTE(stringName, propertyName, accessor, convertor) \
+  if (propertyName != defaultParagraphAttributes.propertyName) { \
+    list.push_back(std::make_shared<DebugStringConvertibleItem>(#stringName, convertor(propertyName accessor))); \
+  }
+
+  PARAGRAPH_ATTRIBUTE(maximumNumberOfLines, maximumNumberOfLines, , std::to_string)
+  PARAGRAPH_ATTRIBUTE(ellipsizeMode, ellipsizeMode, , stringFromEllipsizeMode)
+  PARAGRAPH_ATTRIBUTE(adjustsFontSizeToFit, adjustsFontSizeToFit, , std::to_string)
+  PARAGRAPH_ATTRIBUTE(minimumFontSize, minimumFontSize, , std::to_string)
+  PARAGRAPH_ATTRIBUTE(maximumFontSize, maximumFontSize, , std::to_string)
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/attributedstring/ParagraphAttributes.h b/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
new file mode 100644
index 000000000000..42eb1aa0ab06
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
@@ -0,0 +1,65 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <limits>
+
+#include <fabric/attributedstring/TextPrimitives.h>
+#include <fabric/debug/DebugStringConvertible.h>
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+class ParagraphAttributes;
+
+using SharedParagraphAttributes = std::shared_ptr<const ParagraphAttributes>;
+
+/*
+ * Represents all visual attributes of a paragraph of text.
+ * Two data structures, ParagraphAttributes and AttributedText, should be
+ * enough to define visual representation of a piece of text on the screen.
+ */
+class ParagraphAttributes:
+  public DebugStringConvertible {
+
+public:
+
+#pragma mark - Fields
+
+  /*
+   * Maximum number of lines which paragraph can take.
+   * Zero value represents "no limit".
+   */
+  int maximumNumberOfLines {0};
+
+  /*
+   * In case if a text cannot fit given boudaures, defines a place where
+   * an ellipsize should be placed.
+   */
+  EllipsizeMode ellipsizeMode {EllipsizeMode::Clip};
+
+  /*
+   * Enables font size adjustment to fit constrained boundaries.
+   */
+  bool adjustsFontSizeToFit {false};
+
+  /*
+   * In case of font size adjustment enabled, defines minimum and maximum
+   * font sizes.
+   */
+  Float minimumFontSize {std::numeric_limits<Float>::quiet_NaN()};
+  Float maximumFontSize {std::numeric_limits<Float>::quiet_NaN()};
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/attributedstring/TextPrimitives.h b/ReactCommon/fabric/attributedstring/TextPrimitives.h
new file mode 100644
index 000000000000..7d6d0a79b7cc
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/TextPrimitives.h
@@ -0,0 +1,94 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+namespace facebook {
+namespace react {
+
+enum class FontStyle {
+  Normal,
+  Italic,
+  Oblique
+};
+
+enum class FontWeight: int {
+  Weight100 = 100,
+  UltraLight = 100,
+  Weight200 = 200,
+  Thin = 200,
+  Weight300 = 300,
+  Light = 300,
+  Weight400 = 400,
+  Regular = 400,
+  Weight500 = 500,
+  Medium = 500,
+  Weight600 = 600,
+  Semibold = 600,
+  Demibold = 600,
+  Weight700 = 700,
+  Bold = 700,
+  Weight800 = 800,
+  Heavy = 800,
+  Weight900 = 900,
+  Black = 900
+};
+
+enum class FontVariant: int {
+  Default = 0,
+  SmallCaps = 1 << 1,
+  OldstyleNums = 1 << 2,
+  LiningNums = 1 << 3,
+  TabularNums = 1 << 4,
+  ProportionalNums = 1 << 5
+};
+
+enum class EllipsizeMode {
+  Clip,  // Do not add ellipsize, simply clip.
+  Head,  // Truncate at head of line: "...wxyz".
+  Tail,  // Truncate at tail of line: "abcd...".
+  Middle // Truncate middle of line: "ab...yz".
+};
+
+enum class TextAlignment {
+  Natural,  // Indicates the default alignment for script.
+  Left,     // Visually left aligned.
+  Center,   // Visually centered.
+  Right,    // Visually right aligned.
+  Justified // Fully-justified. The last line in a paragraph is natural-aligned.
+};
+
+enum class WritingDirection {
+  Natural,     // Determines direction using the Unicode Bidi Algorithm rules P2 and P3.
+  LeftToRight, // Left to right writing direction.
+  RightToLeft  // Right to left writing direction.
+};
+
+enum class TextDecorationLineType {
+  None,
+  Underline,
+  Strikethrough,
+  UnderlineStrikethrough
+};
+
+enum class TextDecorationLineStyle {
+  Single,
+  Thick,
+  Double
+};
+
+enum class TextDecorationLinePattern {
+  Solid,
+  Dot,
+  Dash,
+  DashDot,
+  DashDotDot,
+};
+
+} // namespace react
+} // namespace facebook
+
diff --git a/ReactCommon/fabric/attributedstring/tests/AttributedStringTest.cpp b/ReactCommon/fabric/attributedstring/tests/AttributedStringTest.cpp
new file mode 100644
index 000000000000..b3a8eddd343d
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/tests/AttributedStringTest.cpp
@@ -0,0 +1,18 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+#include <fabric/attributedstring/TextPrimitives.h>
+
+using namespace facebook::react;
+
+TEST(AttributedStringTest, testSomething) {
+  // TODO
+}
diff --git a/ReactCommon/fabric/attributedstring/textValuesConversions.h b/ReactCommon/fabric/attributedstring/textValuesConversions.h
new file mode 100644
index 000000000000..88480b6ff2e5
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/textValuesConversions.h
@@ -0,0 +1,120 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/attributedstring/TextPrimitives.h>
+#include <fabric/graphics/Geometry.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+inline std::string stringFromEllipsizeMode(const EllipsizeMode &ellipsisMode) {
+  switch (ellipsisMode) {
+    case EllipsizeMode::Clip: return "clip";
+    case EllipsizeMode::Head: return "head";
+    case EllipsizeMode::Tail: return "tail";
+    case EllipsizeMode::Middle: return "middle";
+  }
+}
+
+inline EllipsizeMode ellipsizeModeFromDynamic(const folly::dynamic &value) {
+  auto string = value.getString();
+  if (string == "clip") { return EllipsizeMode::Clip; }
+  if (string == "head") { return EllipsizeMode::Head; }
+  if (string == "tail") { return EllipsizeMode::Tail; }
+  if (string == "middle") { return EllipsizeMode::Middle; }
+  abort();
+}
+
+inline FontWeight fontWeightFromDynamic(const folly::dynamic &value) {
+  auto string = value.asString();
+  if (string == "normal") { return FontWeight::Regular; }
+  if (string == "regular") { return FontWeight::Regular; }
+  if (string == "bold") { return FontWeight::Bold; }
+  if (string == "100") { return FontWeight::Weight100; }
+  if (string == "200") { return FontWeight::Weight200; }
+  if (string == "300") { return FontWeight::Weight300; }
+  if (string == "400") { return FontWeight::Weight400; }
+  if (string == "500") { return FontWeight::Weight500; }
+  if (string == "600") { return FontWeight::Weight600; }
+  if (string == "700") { return FontWeight::Weight700; }
+  if (string == "800") { return FontWeight::Weight800; }
+  if (string == "900") { return FontWeight::Weight900; }
+  abort();
+}
+
+inline FontStyle fontStyleFromDynamic(const folly::dynamic &value) {
+  auto string = value.asString();
+  if (string == "normal") { return FontStyle::Normal; }
+  if (string == "italic") { return FontStyle::Italic; }
+  if (string == "oblique") { return FontStyle::Oblique; }
+  abort();
+}
+
+inline FontVariant fontVariantFromDynamic(const folly::dynamic &value) {
+  assert(value.isArray());
+  FontVariant fontVariant = FontVariant::Default;
+  for (auto &&item : value) {
+    auto string = item.asString();
+    if (string == "small-caps") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::SmallCaps); continue; }
+    if (string == "oldstyle-nums") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::OldstyleNums); continue; }
+    if (string == "lining-nums") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::LiningNums); continue; }
+    if (string == "tabular-nums") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::TabularNums); continue; }
+    if (string == "proportional-nums") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::ProportionalNums); continue; }
+  }
+  return fontVariant;
+}
+
+inline TextAlignment textAlignmentFromDynamic(const folly::dynamic &value) {
+  auto string = value.asString();
+  if (string == "natural") { return TextAlignment::Natural; }
+  if (string == "left") { return TextAlignment::Left; }
+  if (string == "center") { return TextAlignment::Center; }
+  if (string == "right") { return TextAlignment::Right; }
+  if (string == "justified") { return TextAlignment::Justified; }
+  abort();
+}
+
+inline WritingDirection writingDirectionFromDynamic(const folly::dynamic &value) {
+  auto string = value.asString();
+  if (string == "natural") { return WritingDirection::Natural; }
+  if (string == "ltr") { return WritingDirection::LeftToRight; }
+  if (string == "rtl") { return WritingDirection::RightToLeft; }
+  abort();
+}
+
+inline TextDecorationLineType textDecorationLineTypeFromDynamic(const folly::dynamic &value) {
+  auto string = value.asString();
+  if (string == "none") { return TextDecorationLineType::None; }
+  if (string == "underline") { return TextDecorationLineType::Underline; }
+  if (string == "strikethrough") { return TextDecorationLineType::Strikethrough; }
+  if (string == "underline-strikethrough") { return TextDecorationLineType::UnderlineStrikethrough; }
+  abort();
+}
+
+inline TextDecorationLineStyle textDecorationLineStyleFromDynamic(const folly::dynamic &value) {
+  auto string = value.asString();
+  if (string == "single") { return TextDecorationLineStyle::Single; }
+  if (string == "thick") { return TextDecorationLineStyle::Thick; }
+  if (string == "double") { return TextDecorationLineStyle::Double; }
+  abort();
+}
+
+inline TextDecorationLinePattern textDecorationLinePatternFromDynamic(const folly::dynamic &value) {
+  auto string = value.asString();
+  if (string == "solid") { return TextDecorationLinePattern::Solid; }
+  if (string == "dot") { return TextDecorationLinePattern::Dot; }
+  if (string == "dash") { return TextDecorationLinePattern::Dash; }
+  if (string == "dash-dot") { return TextDecorationLinePattern::DashDot; }
+  if (string == "dash-dot-dot") { return TextDecorationLinePattern::DashDotDot; }
+  abort();
+}
+
+} // namespace react
+} // namespace facebook

From 62576bcb7832e08c6fd9f9482285882c37a2ece5 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 7 May 2018 17:43:08 -0700
Subject: [PATCH 0455/1109] Fabric/Text: attributedstring module, the second
 part

Reviewed By: mdvacca

Differential Revision: D7748711

fbshipit-source-id: 57b37cb2eaa20b85c6f6719b38eac2a2c0479485
---
 .../attributedstring/AttributedString.cpp     | 68 ++++++++++++++++
 .../attributedstring/AttributedString.h       | 75 ++++++++++++++++++
 .../attributedstring/TextAttributes.cpp       | 79 +++++++++++++++++++
 .../fabric/attributedstring/TextAttributes.h  | 79 +++++++++++++++++++
 4 files changed, 301 insertions(+)
 create mode 100644 ReactCommon/fabric/attributedstring/AttributedString.cpp
 create mode 100644 ReactCommon/fabric/attributedstring/AttributedString.h
 create mode 100644 ReactCommon/fabric/attributedstring/TextAttributes.cpp
 create mode 100644 ReactCommon/fabric/attributedstring/TextAttributes.h

diff --git a/ReactCommon/fabric/attributedstring/AttributedString.cpp b/ReactCommon/fabric/attributedstring/AttributedString.cpp
new file mode 100644
index 000000000000..b5eb74af1aa2
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/AttributedString.cpp
@@ -0,0 +1,68 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "AttributedString.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+namespace facebook {
+namespace react {
+
+using Fragment = AttributedString::Fragment;
+using Fragments = AttributedString::Fragments;
+
+void AttributedString::appendFragment(const Fragment &fragment) {
+  ensureUnsealed();
+  fragments_.push_back(fragment);
+}
+
+void AttributedString::prependFragment(const Fragment &fragment) {
+  ensureUnsealed();
+  fragments_.insert(fragments_.begin(), fragment);
+}
+
+void AttributedString::appendAttributedString(const AttributedString &attributedString) {
+  ensureUnsealed();
+  fragments_.insert(fragments_.end(), attributedString.fragments_.begin(), attributedString.fragments_.end());
+}
+
+void AttributedString::prependAttributedString(const AttributedString &attributedString) {
+  ensureUnsealed();
+  fragments_.insert(fragments_.begin(), attributedString.fragments_.begin(), attributedString.fragments_.end());
+}
+
+const std::vector<Fragment> &AttributedString::getFragments() const {
+  return fragments_;
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList AttributedString::getDebugChildren() const {
+  SharedDebugStringConvertibleList list = {};
+
+  for (auto &&fragment : fragments_) {
+    auto propsList = fragment.textAttributes.DebugStringConvertible::getDebugProps();
+
+    if (fragment.shadowNode) {
+      propsList.push_back(std::make_shared<DebugStringConvertibleItem>("shadowNode", fragment.shadowNode->getDebugDescription()));
+    }
+
+    list.push_back(
+      std::make_shared<DebugStringConvertibleItem>(
+        "Fragment",
+        fragment.string,
+        SharedDebugStringConvertibleList(),
+        propsList
+      )
+    );
+  }
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/attributedstring/AttributedString.h b/ReactCommon/fabric/attributedstring/AttributedString.h
new file mode 100644
index 000000000000..07cc47603e45
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/AttributedString.h
@@ -0,0 +1,75 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/attributedstring/TextAttributes.h>
+#include <fabric/core/Sealable.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/debug/DebugStringConvertible.h>
+#include <folly/Optional.h>
+
+namespace facebook {
+namespace react {
+
+class AttributedString;
+
+using SharedAttributedString = std::shared_ptr<const AttributedString>;
+
+/*
+ * Simple, cross-platfrom, React-specific implementation of attributed string
+ * (aka spanned string).
+ * `AttributedString` is basically a list of `Fragments` which have `string` and
+ * `textAttributes` + `shadowNode` associated with the `string`.
+ */
+class AttributedString:
+  public Sealable,
+  public DebugStringConvertible {
+
+public:
+
+  class Fragment {
+  public:
+    std::string string;
+    TextAttributes textAttributes;
+    SharedShadowNode shadowNode;
+  };
+
+  using Fragments = std::vector<Fragment>;
+
+  /*
+   * Appends and prepends a `fragment` to the string.
+   */
+  void appendFragment(const Fragment &fragment);
+  void prependFragment(const Fragment &fragment);
+
+  /*
+   * Appends and prepends an `attributedString` (all its fragments) to
+   * the string.
+   */
+  void appendAttributedString(const AttributedString &attributedString);
+  void prependAttributedString(const AttributedString &attributedString);
+
+  /*
+   * Returns read-only reference to a list of fragments.
+   */
+  const Fragments &getFragments() const;
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugChildren() const override;
+
+private:
+
+  Fragments fragments_;
+};
+
+} // namespace react
+} // namespace facebook
+
diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.cpp b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
new file mode 100644
index 000000000000..984aba5d377f
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
@@ -0,0 +1,79 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "TextAttributes.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/graphics/graphicValuesConversions.h>
+
+namespace facebook {
+namespace react {
+
+void TextAttributes::apply(TextAttributes textAttributes) {
+  // Color
+  foregroundColor = textAttributes.foregroundColor ? textAttributes.foregroundColor : foregroundColor;
+  backgroundColor = textAttributes.backgroundColor ? textAttributes.backgroundColor : backgroundColor;
+  opacity = !isnan(textAttributes.opacity) ? textAttributes.opacity : opacity;
+
+  // Font
+  fontFamily = !textAttributes.fontFamily.empty() ? textAttributes.fontFamily : fontFamily;
+  fontSize = !isnan(textAttributes.fontSize) ? textAttributes.fontSize : fontSize;
+  fontSizeMultiplier = !isnan(textAttributes.fontSizeMultiplier) ? textAttributes.fontSizeMultiplier : fontSizeMultiplier;
+  fontWeight = textAttributes.fontWeight.has_value() ? textAttributes.fontWeight : fontWeight;
+  fontStyle = textAttributes.fontStyle.has_value() ? textAttributes.fontStyle : fontStyle;
+  fontVariant = textAttributes.fontVariant.has_value() ? textAttributes.fontVariant : fontVariant;
+  allowFontScaling = textAttributes.allowFontScaling.has_value() ? textAttributes.allowFontScaling : allowFontScaling;
+  letterSpacing = !isnan(textAttributes.letterSpacing) ? textAttributes.letterSpacing : letterSpacing;
+
+  // Paragraph Styles
+  lineHeight = !isnan(textAttributes.lineHeight) ? textAttributes.lineHeight : lineHeight;
+  alignment = textAttributes.alignment.has_value() ? textAttributes.alignment : alignment;
+  baseWritingDirection = textAttributes.baseWritingDirection.has_value() ? textAttributes.baseWritingDirection : baseWritingDirection;
+
+  // Decoration
+  textDecorationColor = textAttributes.textDecorationColor ? textAttributes.textDecorationColor : textDecorationColor;
+  textDecorationLineType = textAttributes.textDecorationLineType.has_value() ? textAttributes.textDecorationLineType : textDecorationLineType;
+  textDecorationLineStyle = textAttributes.textDecorationLineStyle.has_value() ? textAttributes.textDecorationLineStyle : textDecorationLineStyle;
+  textDecorationLinePattern = textAttributes.textDecorationLinePattern.has_value() ? textAttributes.textDecorationLinePattern : textDecorationLinePattern;
+
+  // Shadow
+  textShadowOffset = textAttributes.textShadowOffset.has_value() ? textAttributes.textShadowOffset.value() : textShadowOffset;
+  textShadowRadius = !isnan(textAttributes.textShadowRadius) ? textAttributes.textShadowRadius : textShadowRadius;
+  textShadowColor = textAttributes.textShadowColor ? textAttributes.textShadowColor : textShadowColor;
+
+  // Special
+  isHighlighted = textAttributes.isHighlighted.has_value() ? textAttributes.isHighlighted : isHighlighted;
+  layoutDirection = textAttributes.layoutDirection.has_value() ? textAttributes.layoutDirection : layoutDirection;
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList TextAttributes::getDebugProps() const {
+  TextAttributes defaultAttributes = {};
+
+  SharedDebugStringConvertibleList list = {};
+
+#define PROPS_ADD_TO_SET(propertyName, accessor, convertor) \
+  if (propertyName != defaultAttributes.propertyName) { \
+    list.push_back(std::make_shared<DebugStringConvertibleItem>(#propertyName, convertor(propertyName accessor))); \
+  }
+
+  PROPS_ADD_TO_SET(backgroundColor, , colorNameFromColor)
+  PROPS_ADD_TO_SET(foregroundColor, , colorNameFromColor)
+  PROPS_ADD_TO_SET(opacity, , std::to_string)
+
+  PROPS_ADD_TO_SET(fontFamily, , )
+  PROPS_ADD_TO_SET(fontSize, , std::to_string)
+  PROPS_ADD_TO_SET(fontSizeMultiplier, , std::to_string)
+
+  // TODO: Implement all fields.
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.h b/ReactCommon/fabric/attributedstring/TextAttributes.h
new file mode 100644
index 000000000000..30159eb5c8f4
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.h
@@ -0,0 +1,79 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <limits>
+
+#include <fabric/attributedstring/TextPrimitives.h>
+#include <fabric/core/LayoutPrimitives.h>
+#include <fabric/core/ReactPrimitives.h>
+#include <fabric/debug/DebugStringConvertible.h>
+#include <fabric/graphics/Color.h>
+#include <fabric/graphics/Geometry.h>
+#include <folly/Optional.h>
+
+namespace facebook {
+namespace react {
+
+class TextAttributes;
+
+using SharedTextAttributes = std::shared_ptr<const TextAttributes>;
+
+class TextAttributes:
+  public DebugStringConvertible {
+public:
+
+#pragma mark - Fields
+
+  // Color
+  SharedColor foregroundColor {nullptr};
+  SharedColor backgroundColor {nullptr};
+  Float opacity {std::numeric_limits<Float>::quiet_NaN()};
+
+  // Font
+  std::string fontFamily {""};
+  Float fontSize {std::numeric_limits<Float>::quiet_NaN()};
+  Float fontSizeMultiplier {std::numeric_limits<Float>::quiet_NaN()};
+  folly::Optional<FontWeight> fontWeight {};
+  folly::Optional<FontStyle> fontStyle {};
+  folly::Optional<FontVariant> fontVariant {};
+  folly::Optional<bool> allowFontScaling {};
+  Float letterSpacing {std::numeric_limits<Float>::quiet_NaN()};
+
+  // Paragraph Styles
+  Float lineHeight {std::numeric_limits<Float>::quiet_NaN()};
+  folly::Optional<TextAlignment> alignment {};
+  folly::Optional<WritingDirection> baseWritingDirection {};
+
+  // Decoration
+  SharedColor textDecorationColor {nullptr};
+  folly::Optional<TextDecorationLineType> textDecorationLineType {};
+  folly::Optional<TextDecorationLineStyle> textDecorationLineStyle {};
+  folly::Optional<TextDecorationLinePattern> textDecorationLinePattern {};
+
+  // Shadow
+  folly::Optional<Point> textShadowOffset {};
+  Float textShadowRadius {std::numeric_limits<Float>::quiet_NaN()};
+  SharedColor textShadowColor {nullptr};
+
+  // Special
+  folly::Optional<bool> isHighlighted {};
+  folly::Optional<LayoutDirection> layoutDirection {};
+
+#pragma mark - Operations
+
+  void apply(TextAttributes textAttributes);
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+};
+
+} // namespace react
+} // namespace facebook
+

From 05890a5942e7e268934860bfbea648b858adfb72 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 7 May 2018 18:58:06 -0700
Subject: [PATCH 0456/1109] Fabric/Text: textlayoutmanager

Summary:
TextLayoutManager measures and renders text using iOS specific APIs (CoreText & TextKit).
By desing, only this module should contain platfrom-specific text functionality.

Reviewed By: mdvacca

Differential Revision: D7751852

fbshipit-source-id: fd6e1907df617fe5a4479ea08f207946765b3a45
---
 React.podspec                                 |   9 +
 ReactCommon/fabric/textlayoutmanager/BUCK     |  88 +++++++
 .../NSTextStorage+FontScaling.h               |  20 ++
 .../NSTextStorage+FontScaling.m               | 137 +++++++++++
 .../RCTAttributedTextUtils.h                  |  23 ++
 .../RCTAttributedTextUtils.mm                 | 227 ++++++++++++++++++
 .../textlayoutmanager/RCTFontProperties.h     |  38 +++
 .../fabric/textlayoutmanager/RCTFontUtils.h   |  19 ++
 .../fabric/textlayoutmanager/RCTFontUtils.mm  | 153 ++++++++++++
 .../textlayoutmanager/RCTTextLayoutManager.h  |  32 +++
 .../textlayoutmanager/RCTTextLayoutManager.mm |  97 ++++++++
 .../RCTTextPrimitivesConversions.h            |  75 ++++++
 .../textlayoutmanager/TextLayoutManager.h     |  51 ++++
 .../textlayoutmanager/TextLayoutManager.mm    |  40 +++
 .../tests/TextLayoutManagerTest.cpp           |  18 ++
 15 files changed, 1027 insertions(+)
 create mode 100644 ReactCommon/fabric/textlayoutmanager/BUCK
 create mode 100644 ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.h
 create mode 100644 ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.m
 create mode 100644 ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.h
 create mode 100644 ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
 create mode 100644 ReactCommon/fabric/textlayoutmanager/RCTFontProperties.h
 create mode 100644 ReactCommon/fabric/textlayoutmanager/RCTFontUtils.h
 create mode 100644 ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm
 create mode 100644 ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.h
 create mode 100644 ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm
 create mode 100644 ReactCommon/fabric/textlayoutmanager/RCTTextPrimitivesConversions.h
 create mode 100644 ReactCommon/fabric/textlayoutmanager/TextLayoutManager.h
 create mode 100644 ReactCommon/fabric/textlayoutmanager/TextLayoutManager.mm
 create mode 100644 ReactCommon/fabric/textlayoutmanager/tests/TextLayoutManagerTest.cpp

diff --git a/React.podspec b/React.podspec
index b985ee3ea9c4..44d6ef7f5886 100644
--- a/React.podspec
+++ b/React.podspec
@@ -185,6 +185,15 @@ Pod::Spec.new do |s|
       sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
     end
 
+    ss.subspec "textlayoutmanager" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/textlayoutmanager/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/textlayoutmanager"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
     ss.subspec "uimanager" do |sss|
       sss.dependency             "Folly", folly_version
       sss.compiler_flags       = folly_compiler_flags
diff --git a/ReactCommon/fabric/textlayoutmanager/BUCK b/ReactCommon/fabric/textlayoutmanager/BUCK
new file mode 100644
index 000000000000..c7bb2f92ec06
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/BUCK
@@ -0,0 +1,88 @@
+load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags", "get_fbobjc_enable_exception_lang_compiler_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+
+rn_xplat_cxx_library(
+    name = "textlayoutmanager",
+    srcs = glob(
+        [
+            "**/*.cpp",
+            "**/*.mm",
+        ],
+        excludes = glob(["tests/**/*.cpp"]),
+    ),
+    headers = glob(
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
+    ),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/textlayoutmanager",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    force_static = True,
+    macosx_tests_override = [],
+    frameworks = [
+        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
+        "$SDKROOT/System/Library/Frameworks/QuartzCore.framework",
+        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
+    ],
+    lang_compiler_flags = get_fbobjc_enable_exception_lang_compiler_flags(),
+    preprocessor_flags = get_debug_preprocessor_flags() + [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        react_native_xplat_target("fabric/attributedstring:attributedstring"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":textlayoutmanager",
+        ],
+    )
diff --git a/ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.h b/ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.h
new file mode 100644
index 000000000000..8372a0d2be91
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.h
@@ -0,0 +1,20 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+@interface NSTextStorage (FontScaling)
+
+- (void)scaleFontSizeToFitSize:(CGSize)size
+               minimumFontSize:(CGFloat)minimumFontSize
+               maximumFontSize:(CGFloat)maximumFontSize;
+
+- (void)scaleFontSizeWithRatio:(CGFloat)ratio
+               minimumFontSize:(CGFloat)minimumFontSize
+               maximumFontSize:(CGFloat)maximumFontSize;
+
+@end
diff --git a/ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.m b/ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.m
new file mode 100644
index 000000000000..5002dddd8a42
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.m
@@ -0,0 +1,137 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "NSTextStorage+FontScaling.h"
+
+typedef NS_OPTIONS(NSInteger, RCTTextSizeComparisonOptions) {
+  RCTTextSizeComparisonSmaller     = 1 << 0,
+  RCTTextSizeComparisonLarger      = 1 << 1,
+  RCTTextSizeComparisonWithinRange = 1 << 2,
+};
+
+@implementation NSTextStorage (FontScaling)
+
+- (void)scaleFontSizeToFitSize:(CGSize)size
+               minimumFontSize:(CGFloat)minimumFontSize
+               maximumFontSize:(CGFloat)maximumFontSize
+{
+  CGFloat bottomRatio = 1.0/128.0;
+  CGFloat topRatio = 128.0;
+  CGFloat ratio = 1.0;
+
+  NSAttributedString *originalAttributedString = [self copy];
+
+  CGFloat lastRatioWhichFits = 0.02;
+
+  while (true) {
+    [self scaleFontSizeWithRatio:ratio
+                 minimumFontSize:minimumFontSize
+                 maximumFontSize:maximumFontSize];
+
+    RCTTextSizeComparisonOptions comparsion =
+      [self compareToSize:size thresholdRatio:0.01];
+
+    if (
+        (comparsion & RCTTextSizeComparisonWithinRange) &&
+        (comparsion & RCTTextSizeComparisonSmaller)
+    ) {
+      return;
+    } else if (comparsion & RCTTextSizeComparisonSmaller) {
+      bottomRatio = ratio;
+      lastRatioWhichFits = ratio;
+    } else {
+      topRatio = ratio;
+    }
+
+    ratio = (topRatio + bottomRatio) / 2.0;
+
+    CGFloat kRatioThreshold = 0.005;
+    if (
+        ABS(topRatio - bottomRatio) < kRatioThreshold ||
+        ABS(topRatio - ratio) < kRatioThreshold ||
+        ABS(bottomRatio - ratio) < kRatioThreshold
+    ) {
+      [self replaceCharactersInRange:(NSRange){0, self.length}
+                withAttributedString:originalAttributedString];
+
+      [self scaleFontSizeWithRatio:lastRatioWhichFits
+                   minimumFontSize:minimumFontSize
+                   maximumFontSize:maximumFontSize];
+      return;
+    }
+
+    [self replaceCharactersInRange:(NSRange){0, self.length}
+              withAttributedString:originalAttributedString];
+  }
+}
+
+
+- (RCTTextSizeComparisonOptions)compareToSize:(CGSize)size thresholdRatio:(CGFloat)thresholdRatio
+{
+  NSLayoutManager *layoutManager = self.layoutManagers.firstObject;
+  NSTextContainer *textContainer = layoutManager.textContainers.firstObject;
+
+  [layoutManager ensureLayoutForTextContainer:textContainer];
+
+  // Does it fit the text container?
+  NSRange glyphRange = [layoutManager glyphRangeForTextContainer:textContainer];
+  NSRange truncatedGlyphRange = [layoutManager truncatedGlyphRangeInLineFragmentForGlyphAtIndex:glyphRange.length - 1];
+
+  if (truncatedGlyphRange.location != NSNotFound) {
+    return RCTTextSizeComparisonLarger;
+  }
+
+  CGSize measuredSize = [layoutManager usedRectForTextContainer:textContainer].size;
+
+  // Does it fit the size?
+  BOOL fitsSize =
+    size.width >= measuredSize.width &&
+    size.height >= measuredSize.height;
+
+  CGSize thresholdSize = (CGSize){
+    size.width * thresholdRatio,
+    size.height * thresholdRatio,
+  };
+
+  RCTTextSizeComparisonOptions result = 0;
+
+  result |= (fitsSize) ? RCTTextSizeComparisonSmaller : RCTTextSizeComparisonLarger;
+
+  if (ABS(measuredSize.width - size.width) < thresholdSize.width) {
+    result = result | RCTTextSizeComparisonWithinRange;
+  }
+
+  return result;
+}
+
+- (void)scaleFontSizeWithRatio:(CGFloat)ratio
+               minimumFontSize:(CGFloat)minimumFontSize
+               maximumFontSize:(CGFloat)maximumFontSize
+{
+  [self beginEditing];
+
+  [self enumerateAttribute:NSFontAttributeName
+                   inRange:(NSRange){0, self.length}
+                   options:NSAttributedStringEnumerationLongestEffectiveRangeNotRequired
+                usingBlock:
+    ^(UIFont *_Nullable font, NSRange range, BOOL *_Nonnull stop) {
+      if (!font) {
+        return;
+      }
+
+      CGFloat fontSize = MAX(MIN(font.pointSize * ratio, maximumFontSize), minimumFontSize);
+
+      [self addAttribute:NSFontAttributeName
+                   value:[font fontWithSize:fontSize]
+                   range:range];
+    }
+  ];
+
+  [self endEditing];
+}
+
+@end
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.h b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.h
new file mode 100644
index 000000000000..32b0a387d856
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.h
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#include <fabric/attributedstring/AttributedString.h>
+#include <fabric/attributedstring/TextAttributes.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+NSString *const RCTAttributedStringIsHighlightedAttributeName = @"IsHighlighted";
+NSString *const RCTAttributedStringReactTagAttributeName = @"ReactTag";
+
+/**
+ * Constructs ready-to-render `NSAttributedString` by given `AttributedString`.
+ */
+NSAttributedString *RCTNSAttributedStringFromAttributedString(const facebook::react::AttributedString &attributedString);
+
+NS_ASSUME_NONNULL_END
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
new file mode 100644
index 000000000000..da7c70fd0c6e
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
@@ -0,0 +1,227 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTAttributedTextUtils.h"
+
+#include <fabric/core/LayoutableShadowNode.h>
+#include <fabric/textlayoutmanager/RCTFontProperties.h>
+#include <fabric/textlayoutmanager/RCTFontUtils.h>
+#include <fabric/textlayoutmanager/RCTTextPrimitivesConversions.h>
+
+inline static UIFont *RCTEffectiveFontFromTextAttributes(const TextAttributes &textAttributes) {
+  NSString *fontFamily = [NSString stringWithCString:textAttributes.fontFamily.c_str()
+                                            encoding:NSASCIIStringEncoding];
+
+  RCTFontProperties fontProperties;
+  fontProperties.family = fontFamily;
+  fontProperties.size = textAttributes.fontSize;
+  fontProperties.style = textAttributes.fontStyle.has_value() ? RCTFontStyleFromFontStyle(textAttributes.fontStyle.value()) : RCTFontStyleUndefined;
+  fontProperties.variant = textAttributes.fontVariant.has_value() ? RCTFontVariantFromFontVariant(textAttributes.fontVariant.value()) : RCTFontVariantDefault;
+  fontProperties.weight = textAttributes.fontWeight.has_value() ? CGFloat(textAttributes.fontWeight.value()) : NAN;
+  fontProperties.sizeMultiplier = textAttributes.fontSizeMultiplier;
+
+  return RCTFontWithFontProperties(fontProperties);
+}
+
+inline static CGFloat RCTEffectiveFontSizeMultiplierFromTextAttributes(const TextAttributes &textAttributes) {
+  return textAttributes.allowFontScaling.value_or(true) && !isnan(textAttributes.fontSizeMultiplier) ? textAttributes.fontSizeMultiplier : 1.0;
+}
+
+inline static UIColor *RCTEffectiveForegroundColorFromTextAttributes(const TextAttributes &textAttributes) {
+  UIColor *effectiveForegroundColor = RCTUIColorFromSharedColor(textAttributes.foregroundColor) ?: [UIColor blackColor];
+
+  if (!isnan(textAttributes.opacity)) {
+    effectiveForegroundColor =
+      [effectiveForegroundColor colorWithAlphaComponent:CGColorGetAlpha(effectiveForegroundColor.CGColor) * textAttributes.opacity];
+  }
+
+  return effectiveForegroundColor;
+}
+
+inline static UIColor *RCTEffectiveBackgroundColorFromTextAttributes(const TextAttributes &textAttributes) {
+  UIColor *effectiveBackgroundColor = RCTUIColorFromSharedColor(textAttributes.backgroundColor);
+
+  if (effectiveBackgroundColor && !isnan(textAttributes.opacity)) {
+    effectiveBackgroundColor =
+      [effectiveBackgroundColor colorWithAlphaComponent:CGColorGetAlpha(effectiveBackgroundColor.CGColor) * textAttributes.opacity];
+  }
+
+  return effectiveBackgroundColor ?: [UIColor clearColor];
+}
+
+static NSDictionary<NSAttributedStringKey, id> *RCTNSTextAttributesFromTextAttributes(const TextAttributes &textAttributes) {
+  NSMutableDictionary<NSAttributedStringKey, id> *attributes =
+    [NSMutableDictionary dictionaryWithCapacity:10];
+
+  // Font
+  UIFont *font = RCTEffectiveFontFromTextAttributes(textAttributes);
+  if (font) {
+    attributes[NSFontAttributeName] = font;
+  }
+
+  // Colors
+  UIColor *effectiveForegroundColor = RCTEffectiveForegroundColorFromTextAttributes(textAttributes);
+
+  if (textAttributes.foregroundColor || !isnan(textAttributes.opacity)) {
+    attributes[NSForegroundColorAttributeName] = effectiveForegroundColor;
+  }
+
+  if (textAttributes.backgroundColor || !isnan(textAttributes.opacity)) {
+    attributes[NSBackgroundColorAttributeName] = RCTEffectiveBackgroundColorFromTextAttributes(textAttributes);
+  }
+
+  // Kerning
+  if (!isnan(textAttributes.letterSpacing)) {
+    attributes[NSKernAttributeName] = @(textAttributes.letterSpacing);
+  }
+
+  // Paragraph Style
+  NSMutableParagraphStyle *paragraphStyle = [NSMutableParagraphStyle new];
+  BOOL isParagraphStyleUsed = NO;
+  if (textAttributes.alignment.has_value()) {
+    TextAlignment textAlignment = textAttributes.alignment.value_or(TextAlignment::Natural);
+    if (textAttributes.layoutDirection.value_or(LayoutDirection::LeftToRight) == LayoutDirection::RightToLeft) {
+      if (textAlignment == TextAlignment::Right) {
+        textAlignment = TextAlignment::Left;
+      } else if (textAlignment == TextAlignment::Left) {
+        textAlignment = TextAlignment::Right;
+      }
+    }
+
+    paragraphStyle.alignment =
+      RCTNSTextAlignmentFromTextAlignment(textAlignment);
+    isParagraphStyleUsed = YES;
+  }
+
+  if (textAttributes.baseWritingDirection.has_value()) {
+    paragraphStyle.baseWritingDirection =
+      RCTNSWritingDirectionFromWritingDirection(textAttributes.baseWritingDirection.value());
+    isParagraphStyleUsed = YES;
+  }
+
+  if (!isnan(textAttributes.lineHeight)) {
+    CGFloat lineHeight =
+      textAttributes.lineHeight * RCTEffectiveFontSizeMultiplierFromTextAttributes(textAttributes);
+    paragraphStyle.minimumLineHeight = lineHeight;
+    paragraphStyle.maximumLineHeight = lineHeight;
+    isParagraphStyleUsed = YES;
+  }
+
+  if (isParagraphStyleUsed) {
+    attributes[NSParagraphStyleAttributeName] = paragraphStyle;
+  }
+
+  // Decoration
+  if (textAttributes.textDecorationLineType.value_or(TextDecorationLineType::None) != TextDecorationLineType::None) {
+    auto textDecorationLineType = textAttributes.textDecorationLineType.value();
+
+    NSUnderlineStyle style =
+      RCTNSUnderlineStyleFromStyleAndPattern(
+        textAttributes.textDecorationLineStyle.value_or(TextDecorationLineStyle::Single),
+        textAttributes.textDecorationLinePattern.value_or(TextDecorationLinePattern::Solid)
+      );
+
+    UIColor *textDecorationColor = RCTUIColorFromSharedColor(textAttributes.textDecorationColor);
+
+    // Underline
+    if (textDecorationLineType == TextDecorationLineType::Underline ||
+        textDecorationLineType == TextDecorationLineType::UnderlineStrikethrough) {
+
+      attributes[NSUnderlineStyleAttributeName] = @(style);
+
+      if (textDecorationColor) {
+        attributes[NSUnderlineColorAttributeName] = textDecorationColor;
+      }
+    }
+
+    // Strikethrough
+    if (textDecorationLineType == TextDecorationLineType::Strikethrough ||
+        textDecorationLineType == TextDecorationLineType::UnderlineStrikethrough) {
+
+      attributes[NSStrikethroughStyleAttributeName] = @(style);
+
+      if (textDecorationColor) {
+        attributes[NSStrikethroughColorAttributeName] = textDecorationColor;
+      }
+    }
+  }
+
+  // Shadow
+  if (textAttributes.textShadowOffset.has_value()) {
+    auto textShadowOffset = textAttributes.textShadowOffset.value();
+    NSShadow *shadow = [NSShadow new];
+    shadow.shadowOffset = CGSize {textShadowOffset.x, textShadowOffset.y};
+    shadow.shadowBlurRadius = textAttributes.textShadowRadius;
+    shadow.shadowColor = RCTUIColorFromSharedColor(textAttributes.textShadowColor);
+    attributes[NSShadowAttributeName] = shadow;
+  }
+
+  // Special
+  if (textAttributes.isHighlighted) {
+    attributes[RCTAttributedStringIsHighlightedAttributeName] = @YES;
+  }
+
+  return [attributes copy];
+}
+
+NSAttributedString *RCTNSAttributedStringFromAttributedString(const AttributedString &attributedString) {
+  NSMutableAttributedString *nsAttributedString = [[NSMutableAttributedString alloc] init];
+
+  [nsAttributedString beginEditing];
+
+  for (auto fragment : attributedString.getFragments()) {
+    NSAttributedString *nsAttributedStringFragment;
+
+    SharedLayoutableShadowNode layoutableShadowNode =
+      std::dynamic_pointer_cast<const LayoutableShadowNode>(fragment.shadowNode);
+
+    if (layoutableShadowNode) {
+      auto layoutMetrics = layoutableShadowNode->getLayoutMetrics();
+      CGRect bounds = {
+        .origin = {
+          .x = layoutMetrics.frame.origin.x,
+          .y = layoutMetrics.frame.origin.y
+        },
+        .size = {
+          .width = layoutMetrics.frame.size.width,
+          .height = layoutMetrics.frame.size.height
+        }
+      };
+
+      NSTextAttachment *attachment = [NSTextAttachment new];
+      attachment.bounds = bounds;
+
+      nsAttributedStringFragment = [NSAttributedString attributedStringWithAttachment:attachment];
+    } else {
+      NSString *string =
+        [NSString stringWithCString:fragment.string.c_str()
+                           encoding:NSASCIIStringEncoding];
+
+      nsAttributedStringFragment =
+        [[NSAttributedString alloc] initWithString:string
+                                        attributes:RCTNSTextAttributesFromTextAttributes(fragment.textAttributes)];
+    }
+
+    NSMutableAttributedString *nsMutableAttributedStringFragment =
+      [[NSMutableAttributedString alloc] initWithAttributedString:nsAttributedStringFragment];
+
+    if (fragment.shadowNode) {
+      NSDictionary<NSAttributedStringKey, id> *additionalTextAttributes = @{
+        RCTAttributedStringReactTagAttributeName: @(fragment.shadowNode->getTag())
+      };
+
+      [nsMutableAttributedStringFragment setAttributes:additionalTextAttributes
+                                                 range:NSMakeRange(0, nsMutableAttributedStringFragment.length)];
+    }
+
+    [nsAttributedString appendAttributedString:nsMutableAttributedStringFragment];
+  }
+
+  [nsAttributedString endEditing];
+
+  return nsAttributedString;
+}
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTFontProperties.h b/ReactCommon/fabric/textlayoutmanager/RCTFontProperties.h
new file mode 100644
index 000000000000..9f8680b47a4a
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/RCTFontProperties.h
@@ -0,0 +1,38 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+typedef NS_ENUM(NSInteger, RCTFontStyle) {
+  RCTFontStyleUndefined = -1,
+  RCTFontStyleNormal,
+  RCTFontStyleItalic,
+  RCTFontStyleOblique,
+};
+
+typedef NS_OPTIONS(NSInteger, RCTFontVariant) {
+  RCTFontVariantUndefined = -1,
+  RCTFontVariantDefault = 0,
+  RCTFontVariantSmallCaps = 1 << 1,
+  RCTFontVariantOldstyleNums = 1 << 2,
+  RCTFontVariantLiningNums = 1 << 3,
+  RCTFontVariantTabularNums = 1 << 4,
+  RCTFontVariantProportionalNums = 1 << 5,
+};
+
+struct RCTFontProperties {
+  NSString *family;
+  CGFloat size;
+  UIFontWeight weight;
+  RCTFontStyle style;
+  RCTFontVariant variant;
+  CGFloat sizeMultiplier;
+};
+
+NS_ASSUME_NONNULL_END
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.h b/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.h
new file mode 100644
index 000000000000..084a2b24dd0b
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.h
@@ -0,0 +1,19 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <fabric/textlayoutmanager/RCTFontProperties.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Returns UIFont instance corresponded to given font properties.
+ */
+UIFont *RCTFontWithFontProperties(RCTFontProperties fontProperties);
+
+NS_ASSUME_NONNULL_END
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm b/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm
new file mode 100644
index 000000000000..38a3d80f5a5d
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm
@@ -0,0 +1,153 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTFontUtils.h"
+
+#import <mutex>
+
+static RCTFontProperties RCTDefaultFontProperties() {
+  static RCTFontProperties defaultFontProperties;
+  static dispatch_once_t onceToken;
+
+  dispatch_once(&onceToken, ^{
+    defaultFontProperties.size = 14;
+    defaultFontProperties.family =
+      [UIFont systemFontOfSize:defaultFontProperties.size].familyName;
+    defaultFontProperties.style = RCTFontStyleNormal;
+    defaultFontProperties.variant = RCTFontVariantDefault;
+    defaultFontProperties.sizeMultiplier = 1.0;
+  });
+
+  return defaultFontProperties;
+}
+
+static RCTFontProperties RCTResolveFontProperties(RCTFontProperties fontProperties) {
+  RCTFontProperties defaultFontProperties = RCTDefaultFontProperties();
+  fontProperties.family = fontProperties.family.length && ![fontProperties.family isEqualToString:@"System"] ? fontProperties.family : defaultFontProperties.family;
+  fontProperties.size = !isnan(fontProperties.size) ? fontProperties.size : defaultFontProperties.size;
+  fontProperties.weight = !isnan(fontProperties.weight) ? fontProperties.weight : defaultFontProperties.weight;
+  fontProperties.style = fontProperties.style != RCTFontStyleUndefined  ? fontProperties.style : defaultFontProperties.style;
+  fontProperties.variant = fontProperties.variant != RCTFontVariantUndefined  ? fontProperties.variant : defaultFontProperties.variant;
+  return fontProperties;
+}
+
+static UIFontWeight RCTGetFontWeight(UIFont *font) {
+  NSDictionary *traits = [font.fontDescriptor objectForKey:UIFontDescriptorTraitsAttribute];
+  return [traits[UIFontWeightTrait] doubleValue];
+}
+
+static RCTFontStyle RCTGetFontStyle(UIFont *font) {
+  NSDictionary *traits = [font.fontDescriptor objectForKey:UIFontDescriptorTraitsAttribute];
+  UIFontDescriptorSymbolicTraits symbolicTraits = [traits[UIFontSymbolicTrait] unsignedIntValue];
+  if (symbolicTraits & UIFontDescriptorTraitItalic) {
+    return RCTFontStyleItalic;
+  }
+
+  return RCTFontStyleNormal;
+}
+
+static NSArray *RCTFontFeatures(RCTFontVariant fontVariant) {
+  // FIXME:
+  return @[];
+}
+
+static UIFont *RCTDefaultFontWithFontProperties(RCTFontProperties fontProperties) {
+  static NSCache *fontCache;
+  static std::mutex fontCacheMutex;
+
+  NSString *cacheKey = [NSString stringWithFormat:@"%.1f/%.2f", fontProperties.size, fontProperties.weight];
+  UIFont *font;
+
+  {
+    std::lock_guard<std::mutex> lock(fontCacheMutex);
+    if (!fontCache) {
+      fontCache = [NSCache new];
+    }
+    font = [fontCache objectForKey:cacheKey];
+  }
+
+  if (!font) {
+    font = [UIFont systemFontOfSize:fontProperties.size
+                             weight:fontProperties.weight];
+
+    if (fontProperties.variant == RCTFontStyleItalic) {
+      UIFontDescriptor *fontDescriptor = [font fontDescriptor];
+      UIFontDescriptorSymbolicTraits symbolicTraits = fontDescriptor.symbolicTraits;
+
+      symbolicTraits |= UIFontDescriptorTraitItalic;
+
+      fontDescriptor = [fontDescriptor fontDescriptorWithSymbolicTraits:symbolicTraits];
+      font = [UIFont fontWithDescriptor:fontDescriptor size:fontProperties.size];
+    }
+
+    {
+      std::lock_guard<std::mutex> lock(fontCacheMutex);
+      [fontCache setObject:font forKey:cacheKey];
+    }
+  }
+
+  return font;
+}
+
+UIFont *RCTFontWithFontProperties(RCTFontProperties fontProperties) {
+  RCTFontProperties defaultFontProperties = RCTDefaultFontProperties();
+  fontProperties = RCTResolveFontProperties(fontProperties);
+
+  CGFloat effectiveFontSize = fontProperties.sizeMultiplier * fontProperties.size;
+  UIFont *font;
+  if ([fontProperties.family isEqualToString:defaultFontProperties.family]) {
+    // Handle system font as special case. This ensures that we preserve
+    // the specific metrics of the standard system font as closely as possible.
+    font = RCTDefaultFontWithFontProperties(fontProperties);
+  } else {
+    NSArray<NSString *> *fontNames =
+      [UIFont fontNamesForFamilyName:fontProperties.family];
+
+    if (fontNames.count == 0) {
+      // Gracefully handle being given a font name rather than font family, for
+      // example: "Helvetica Light Oblique" rather than just "Helvetica".
+      font = [UIFont fontWithName:fontProperties.family size:effectiveFontSize];
+
+      if (!font) {
+        // Failback to system font.
+        font = [UIFont systemFontOfSize:effectiveFontSize weight:fontProperties.weight];
+      }
+    } else {
+      // Get the closest font that matches the given weight for the fontFamily
+      CGFloat closestWeight = INFINITY;
+      for (NSString *name in fontNames) {
+        UIFont *fontMatch = [UIFont fontWithName:name size:effectiveFontSize];
+
+        if (RCTGetFontStyle(fontMatch) != fontProperties.style) {
+          continue;
+        }
+
+        CGFloat testWeight = RCTGetFontWeight(fontMatch);
+        if (ABS(testWeight - fontProperties.weight) < ABS(closestWeight - fontProperties.weight)) {
+          font = fontMatch;
+          closestWeight = testWeight;
+        }
+      }
+
+      if (!font) {
+        // If we still don't have a match at least return the first font in the fontFamily
+        // This is to support built-in font Zapfino and other custom single font families like Impact
+        font = [UIFont fontWithName:fontNames[0] size:effectiveFontSize];
+      }
+    }
+  }
+
+  // Apply font variants to font object.
+  if (fontProperties.variant != RCTFontVariantDefault) {
+    NSArray *fontFeatures = RCTFontFeatures(fontProperties.variant);
+    UIFontDescriptor *fontDescriptor =
+      [font.fontDescriptor fontDescriptorByAddingAttributes:@{UIFontDescriptorFeatureSettingsAttribute: fontFeatures}];
+    font = [UIFont fontWithDescriptor:fontDescriptor size:effectiveFontSize];
+  }
+
+  return font;
+}
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.h b/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.h
new file mode 100644
index 000000000000..8a745aa4a60b
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.h
@@ -0,0 +1,32 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <fabric/core/LayoutConstraints.h>
+#import <fabric/graphics/Geometry.h>
+#import <fabric/attributedstring/AttributedString.h>
+#import <fabric/attributedstring/ParagraphAttributes.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * iOS-specific TextLayoutManager
+ */
+@interface RCTTextLayoutManager : NSObject
+
+- (facebook::react::Size)measureWithAttributedString:(facebook::react::AttributedString)attributedString
+                                 paragraphAttributes:(facebook::react::ParagraphAttributes)paragraphAttributes
+                                   layoutConstraints:(facebook::react::LayoutConstraints)layoutConstraints;
+
+- (void)drawAttributedString:(facebook::react::AttributedString)attributedString
+         paragraphAttributes:(facebook::react::ParagraphAttributes)paragraphAttributes
+                       frame:(CGRect)frame;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm b/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm
new file mode 100644
index 000000000000..f729c9c814c7
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm
@@ -0,0 +1,97 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTTextLayoutManager.h"
+
+#import "NSTextStorage+FontScaling.h"
+#import "RCTAttributedTextUtils.h"
+
+using namespace facebook::react;
+
+@implementation RCTTextLayoutManager
+
+static NSLineBreakMode RCTNSLineBreakModeFromWritingDirection(EllipsizeMode ellipsizeMode) {
+  switch (ellipsizeMode) {
+    case EllipsizeMode::Clip: return NSLineBreakByClipping;
+    case EllipsizeMode::Head: return NSLineBreakByTruncatingHead;
+    case EllipsizeMode::Tail: return NSLineBreakByTruncatingTail;
+    case EllipsizeMode::Middle: return NSLineBreakByTruncatingMiddle;
+  }
+}
+
+- (facebook::react::Size)measureWithAttributedString:(AttributedString)attributedString
+                                 paragraphAttributes:(ParagraphAttributes)paragraphAttributes
+                                   layoutConstraints:(LayoutConstraints)layoutConstraints
+{
+  CGSize maximumSize = CGSize {layoutConstraints.maximumSize.width, layoutConstraints.maximumSize.height};
+  NSTextStorage *textStorage =
+    [self _textStorageAndLayoutManagerWithAttributesString:RCTNSAttributedStringFromAttributedString(attributedString)
+                                       paragraphAttributes:paragraphAttributes
+                                                      size:maximumSize];
+
+  NSLayoutManager *layoutManager = textStorage.layoutManagers.firstObject;
+  NSTextContainer *textContainer = layoutManager.textContainers.firstObject;
+  [layoutManager ensureLayoutForTextContainer:textContainer];
+
+  CGSize size = [layoutManager usedRectForTextContainer:textContainer].size;
+
+  size = (CGSize){
+    MIN(size.width, maximumSize.width),
+    MIN(size.height, maximumSize.height)
+  };
+
+  return facebook::react::Size {size.width, size.height};
+}
+
+- (void)drawAttributedString:(AttributedString)attributedString
+         paragraphAttributes:(ParagraphAttributes)paragraphAttributes
+                       frame:(CGRect)frame
+{
+  NSTextStorage *textStorage =
+    [self _textStorageAndLayoutManagerWithAttributesString:RCTNSAttributedStringFromAttributedString(attributedString)
+                                       paragraphAttributes:paragraphAttributes
+                                                      size:frame.size];
+   NSLayoutManager *layoutManager = textStorage.layoutManagers.firstObject;
+   NSTextContainer *textContainer = layoutManager.textContainers.firstObject;
+
+   NSRange glyphRange = [layoutManager glyphRangeForTextContainer:textContainer];
+   [layoutManager drawBackgroundForGlyphRange:glyphRange atPoint:frame.origin];
+   [layoutManager drawGlyphsForGlyphRange:glyphRange atPoint:frame.origin];
+}
+
+
+- (NSTextStorage *)_textStorageAndLayoutManagerWithAttributesString:(NSAttributedString *)attributedString
+                                                paragraphAttributes:(ParagraphAttributes)paragraphAttributes
+                                                               size:(CGSize)size
+{
+  NSTextContainer *textContainer = [[NSTextContainer alloc] initWithSize:size];
+
+  textContainer.lineFragmentPadding = 0.0; // Note, the default value is 5.
+  textContainer.lineBreakMode =
+    paragraphAttributes.maximumNumberOfLines > 0 ? RCTNSLineBreakModeFromWritingDirection(paragraphAttributes.ellipsizeMode) : NSLineBreakByClipping;
+  textContainer.maximumNumberOfLines = paragraphAttributes.maximumNumberOfLines;
+
+  NSLayoutManager *layoutManager = [NSLayoutManager new];
+  [layoutManager addTextContainer:textContainer];
+
+  NSTextStorage *textStorage =
+    [[NSTextStorage alloc] initWithAttributedString:attributedString];
+
+  [textStorage addLayoutManager:layoutManager];
+
+  if (paragraphAttributes.adjustsFontSizeToFit) {
+    CGFloat minimumFontSize = !isnan(paragraphAttributes.minimumFontSize) ? paragraphAttributes.minimumFontSize : 4.0;
+    CGFloat maximumFontSize = !isnan(paragraphAttributes.maximumFontSize) ? paragraphAttributes.maximumFontSize : 96.0;
+    [textStorage scaleFontSizeToFitSize:size
+                        minimumFontSize:minimumFontSize
+                        maximumFontSize:maximumFontSize];
+  }
+
+  return textStorage;
+}
+
+@end
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTTextPrimitivesConversions.h b/ReactCommon/fabric/textlayoutmanager/RCTTextPrimitivesConversions.h
new file mode 100644
index 000000000000..354952d9c833
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/RCTTextPrimitivesConversions.h
@@ -0,0 +1,75 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#include <fabric/textlayoutmanager/RCTFontProperties.h>
+#include <fabric/textlayoutmanager/RCTFontUtils.h>
+
+using namespace facebook::react;
+
+inline static NSTextAlignment RCTNSTextAlignmentFromTextAlignment(TextAlignment textAlignment) {
+  switch (textAlignment) {
+    case TextAlignment::Natural: return NSTextAlignmentNatural;
+    case TextAlignment::Left: return NSTextAlignmentLeft;
+    case TextAlignment::Right: return NSTextAlignmentRight;
+    case TextAlignment::Center: return NSTextAlignmentCenter;
+    case TextAlignment::Justified: return NSTextAlignmentJustified;
+  }
+}
+
+inline static NSWritingDirection RCTNSWritingDirectionFromWritingDirection(WritingDirection writingDirection) {
+  switch (writingDirection) {
+    case WritingDirection::Natural: return NSWritingDirectionNatural;
+    case WritingDirection::LeftToRight: return NSWritingDirectionLeftToRight;
+    case WritingDirection::RightToLeft: return NSWritingDirectionRightToLeft;
+  }
+}
+
+inline static RCTFontStyle RCTFontStyleFromFontStyle(FontStyle fontStyle) {
+  switch (fontStyle) {
+    case FontStyle::Normal: return RCTFontStyleNormal;
+    case FontStyle::Italic: return RCTFontStyleItalic;
+    case FontStyle::Oblique: return RCTFontStyleOblique;
+  }
+}
+
+inline static RCTFontVariant RCTFontVariantFromFontVariant(FontVariant fontVariant) {
+  return (RCTFontVariant)fontVariant;
+}
+
+inline static NSUnderlineStyle RCTNSUnderlineStyleFromStyleAndPattern(TextDecorationLineStyle textDecorationLineStyle, TextDecorationLinePattern textDecorationLinePattern) {
+  NSUnderlineStyle style = NSUnderlineStyleNone;
+
+  switch (textDecorationLineStyle) {
+    case TextDecorationLineStyle::Single:
+      style = NSUnderlineStyle(style | NSUnderlineStyleSingle); break;
+    case TextDecorationLineStyle::Thick:
+      style = NSUnderlineStyle(style | NSUnderlineStyleThick); break;
+    case TextDecorationLineStyle::Double:
+      style = NSUnderlineStyle(style | NSUnderlineStyleDouble); break;
+  }
+
+  switch (textDecorationLinePattern) {
+    case TextDecorationLinePattern::Solid:
+      style = NSUnderlineStyle(style | NSUnderlinePatternSolid); break;
+    case TextDecorationLinePattern::Dash:
+      style = NSUnderlineStyle(style | NSUnderlinePatternDash); break;
+    case TextDecorationLinePattern::Dot:
+      style = NSUnderlineStyle(style | NSUnderlinePatternDot); break;
+    case TextDecorationLinePattern::DashDot:
+      style = NSUnderlineStyle(style | NSUnderlinePatternDashDot); break;
+    case TextDecorationLinePattern::DashDotDot:
+      style = NSUnderlineStyle(style | NSUnderlinePatternDashDotDot); break;
+  }
+
+  return style;
+}
+
+inline static UIColor *RCTUIColorFromSharedColor(const SharedColor &color) {
+  return color ? [UIColor colorWithCGColor:color.get()] : nil;
+}
diff --git a/ReactCommon/fabric/textlayoutmanager/TextLayoutManager.h b/ReactCommon/fabric/textlayoutmanager/TextLayoutManager.h
new file mode 100644
index 000000000000..dd54980ffd73
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/TextLayoutManager.h
@@ -0,0 +1,51 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/attributedstring/AttributedString.h>
+#include <fabric/attributedstring/ParagraphAttributes.h>
+#include <fabric/core/LayoutConstraints.h>
+
+namespace facebook {
+namespace react {
+
+class TextLayoutManager;
+
+using SharedTextLayoutManager = std::shared_ptr<const TextLayoutManager>;
+
+/*
+ * Cross platform facade for iOS-specific RCTTTextLayoutManager.
+ */
+class TextLayoutManager {
+public:
+  TextLayoutManager();
+  ~TextLayoutManager();
+
+  /*
+   * Measures `attributedString` using native text rendering infrastructure.
+   */
+  Size measure(
+    AttributedString attributedString,
+    ParagraphAttributes paragraphAttributes,
+    LayoutConstraints layoutConstraints
+  ) const;
+
+  /*
+   * Returns an opaque pointer to platform-specific TextLayoutManager.
+   * Is used on a native views layer to delegate text rendering to the manager.
+   */
+  void *getNativeTextLayoutManager() const;
+
+private:
+  void *self_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/textlayoutmanager/TextLayoutManager.mm b/ReactCommon/fabric/textlayoutmanager/TextLayoutManager.mm
new file mode 100644
index 000000000000..f7658211522f
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/TextLayoutManager.mm
@@ -0,0 +1,40 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "TextLayoutManager.h"
+
+#import "RCTTextLayoutManager.h"
+
+namespace facebook {
+namespace react {
+
+TextLayoutManager::TextLayoutManager() {
+  self_ = (__bridge_retained void *)[RCTTextLayoutManager new];
+}
+
+TextLayoutManager::~TextLayoutManager() {
+  CFRelease(self_);
+  self_ = nullptr;
+}
+
+void *TextLayoutManager::getNativeTextLayoutManager() const {
+  return self_;
+}
+
+Size TextLayoutManager::measure(
+  AttributedString attributedString,
+  ParagraphAttributes paragraphAttributes,
+  LayoutConstraints layoutConstraints
+) const {
+  RCTTextLayoutManager *textLayoutManager = (__bridge RCTTextLayoutManager *)self_;
+  return [textLayoutManager measureWithAttributedString:attributedString
+                                    paragraphAttributes:paragraphAttributes
+                                      layoutConstraints:layoutConstraints];
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/textlayoutmanager/tests/TextLayoutManagerTest.cpp b/ReactCommon/fabric/textlayoutmanager/tests/TextLayoutManagerTest.cpp
new file mode 100644
index 000000000000..d873c6eed80e
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/tests/TextLayoutManagerTest.cpp
@@ -0,0 +1,18 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+#include <fabric/textlayoutmanager/TextLayoutManager.h>
+
+using namespace facebook::react;
+
+TEST(TextLayoutManagerTest, testSomething) {
+  // TODO:
+}

From 02c3cd4c4e712dea004713c271f0ae0d5a03ac96 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 7 May 2018 21:49:19 -0700
Subject: [PATCH 0457/1109] Fabric/Text: text module, rawtext part

Summary: <RawText> component represents a purely regular string object in React.

Reviewed By: mdvacca

Differential Revision: D7751850

fbshipit-source-id: 54afe43e0c1ac063862f109ea07f0e7de3593573
---
 React.podspec                                 |  9 ++
 ReactCommon/fabric/text/BUCK                  | 84 +++++++++++++++++++
 .../text/rawtext/RawTextComponentDescriptor.h | 27 ++++++
 .../fabric/text/rawtext/RawTextProps.cpp      | 37 ++++++++
 .../fabric/text/rawtext/RawTextProps.h        | 43 ++++++++++
 .../fabric/text/rawtext/RawTextShadowNode.cpp | 20 +++++
 .../fabric/text/rawtext/RawTextShadowNode.h   | 39 +++++++++
 ReactCommon/fabric/text/tests/TextTest.cpp    | 14 ++++
 8 files changed, 273 insertions(+)
 create mode 100644 ReactCommon/fabric/text/BUCK
 create mode 100644 ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/text/rawtext/RawTextProps.cpp
 create mode 100644 ReactCommon/fabric/text/rawtext/RawTextProps.h
 create mode 100644 ReactCommon/fabric/text/rawtext/RawTextShadowNode.cpp
 create mode 100644 ReactCommon/fabric/text/rawtext/RawTextShadowNode.h
 create mode 100644 ReactCommon/fabric/text/tests/TextTest.cpp

diff --git a/React.podspec b/React.podspec
index 44d6ef7f5886..9305d94ea484 100644
--- a/React.podspec
+++ b/React.podspec
@@ -185,6 +185,15 @@ Pod::Spec.new do |s|
       sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
     end
 
+    ss.subspec "text" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/text/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/text"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
     ss.subspec "textlayoutmanager" do |sss|
       sss.dependency             "Folly", folly_version
       sss.compiler_flags       = folly_compiler_flags
diff --git a/ReactCommon/fabric/text/BUCK b/ReactCommon/fabric/text/BUCK
new file mode 100644
index 000000000000..20a30de39663
--- /dev/null
+++ b/ReactCommon/fabric/text/BUCK
@@ -0,0 +1,84 @@
+load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags", "get_fbobjc_enable_exception_lang_compiler_flags")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+
+rn_xplat_cxx_library(
+    name = "text",
+    srcs = glob(
+        ["**/*.cpp"],
+        excludes = glob(["tests/**/*.cpp"]),
+    ),
+    headers = glob(
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
+    ),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+            ("paragraph", "*.h"),
+            ("text", "*.h"),
+            ("rawtext", "*.h"),
+        ],
+        prefix = "fabric/text",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    force_static = True,
+    macosx_tests_override = [],
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        react_native_xplat_target("fabric/attributedstring:attributedstring"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+        react_native_xplat_target("fabric/textlayoutmanager:textlayoutmanager"),
+        react_native_xplat_target("fabric/view:view"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":text",
+        ],
+    )
diff --git a/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h b/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h
new file mode 100644
index 000000000000..6f615fa3c620
--- /dev/null
+++ b/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h
@@ -0,0 +1,27 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ConcreteComponentDescriptor.h>
+#include <fabric/text/RawTextShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Descriptor for <RawText> component.
+ */
+class RawTextComponentDescriptor: public ConcreteComponentDescriptor<RawTextShadowNode> {
+public:
+  ComponentName getComponentName() const override {
+    return "RawText";
+  }
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/rawtext/RawTextProps.cpp b/ReactCommon/fabric/text/rawtext/RawTextProps.cpp
new file mode 100644
index 000000000000..d985188c9dd8
--- /dev/null
+++ b/ReactCommon/fabric/text/rawtext/RawTextProps.cpp
@@ -0,0 +1,37 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "RawTextProps.h"
+
+#include <fabric/core/propsConversions.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+namespace facebook {
+namespace react {
+
+void RawTextProps::apply(const RawProps &rawProps) {
+  Props::apply(rawProps);
+
+  applyRawProp(rawProps, "text", text_);
+}
+
+#pragma mark - Getters
+
+std::string RawTextProps::getText() const {
+  return text_;
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList RawTextProps::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+  list.push_back(std::make_shared<DebugStringConvertibleItem>("text", text_));
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/rawtext/RawTextProps.h b/ReactCommon/fabric/text/rawtext/RawTextProps.h
new file mode 100644
index 000000000000..4dd84f8fba5a
--- /dev/null
+++ b/ReactCommon/fabric/text/rawtext/RawTextProps.h
@@ -0,0 +1,43 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/Props.h>
+#include <fabric/debug/DebugStringConvertible.h>
+
+namespace facebook {
+namespace react {
+
+class RawTextProps;
+
+using SharedRawTextProps = std::shared_ptr<const RawTextProps>;
+
+class RawTextProps:
+  public Props {
+
+public:
+
+  void apply(const RawProps &rawProps) override;
+
+#pragma mark - Getters
+
+  std::string getText() const;
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+private:
+
+  std::string text_ {""};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/rawtext/RawTextShadowNode.cpp b/ReactCommon/fabric/text/rawtext/RawTextShadowNode.cpp
new file mode 100644
index 000000000000..730e4aabb264
--- /dev/null
+++ b/ReactCommon/fabric/text/rawtext/RawTextShadowNode.cpp
@@ -0,0 +1,20 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "RawTextShadowNode.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+namespace facebook {
+namespace react {
+
+ComponentName RawTextShadowNode::getComponentName() const {
+  return ComponentName("RawText");
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/rawtext/RawTextShadowNode.h b/ReactCommon/fabric/text/rawtext/RawTextShadowNode.h
new file mode 100644
index 000000000000..f4a2e2ffceba
--- /dev/null
+++ b/ReactCommon/fabric/text/rawtext/RawTextShadowNode.h
@@ -0,0 +1,39 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ConcreteShadowNode.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/text/RawTextProps.h>
+
+namespace facebook {
+namespace react {
+
+class RawTextShadowNode;
+
+using SharedRawTextShadowNode = std::shared_ptr<const RawTextShadowNode>;
+
+/*
+ * `ShadowNode` for <RawText> component, represents a purely regular string
+ * object in React. In a code fragment `<Text>Hello!</Text>`, "Hello!" part
+ * is represented as `<RawText text="Hello!"/>`.
+ * <RawText> component must not have any children.
+ */
+class RawTextShadowNode:
+  public ConcreteShadowNode<RawTextProps> {
+
+public:
+  using ConcreteShadowNode::ConcreteShadowNode;
+
+  ComponentName getComponentName() const override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/tests/TextTest.cpp b/ReactCommon/fabric/text/tests/TextTest.cpp
new file mode 100644
index 000000000000..55ae97a50fad
--- /dev/null
+++ b/ReactCommon/fabric/text/tests/TextTest.cpp
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+TEST(TextLayoutManagerTest, testSomething) {
+  // TODO:
+}

From dc7a87e7377ebb2a3e08cdf00c7ba8961fac453a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 7 May 2018 21:49:21 -0700
Subject: [PATCH 0458/1109] Fabric/Text: text module, text part

Summary: <Text> component is used to describe text attributes in React.

Reviewed By: mdvacca

Differential Revision: D7751851

fbshipit-source-id: f90a4367cad64283ee64828b0d5e24470ee3d9f7
---
 ReactCommon/fabric/text/propsConversions.h    | 29 +++++++
 ReactCommon/fabric/text/tests/TextTest.cpp    |  2 +-
 .../text/text/TextComponentDescriptor.h       | 25 +++++++
 ReactCommon/fabric/text/text/TextProps.cpp    | 75 +++++++++++++++++++
 ReactCommon/fabric/text/text/TextProps.h      | 46 ++++++++++++
 .../fabric/text/text/TextShadowNode.cpp       | 59 +++++++++++++++
 ReactCommon/fabric/text/text/TextShadowNode.h | 40 ++++++++++
 7 files changed, 275 insertions(+), 1 deletion(-)
 create mode 100644 ReactCommon/fabric/text/propsConversions.h
 create mode 100644 ReactCommon/fabric/text/text/TextComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/text/text/TextProps.cpp
 create mode 100644 ReactCommon/fabric/text/text/TextProps.h
 create mode 100644 ReactCommon/fabric/text/text/TextShadowNode.cpp
 create mode 100644 ReactCommon/fabric/text/text/TextShadowNode.h

diff --git a/ReactCommon/fabric/text/propsConversions.h b/ReactCommon/fabric/text/propsConversions.h
new file mode 100644
index 000000000000..1656e82af44f
--- /dev/null
+++ b/ReactCommon/fabric/text/propsConversions.h
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/attributedstring/TextPrimitives.h>
+#include <fabric/attributedstring/textValuesConversions.h>
+#include <fabric/core/propsConversions.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+APPLY_RAW_PROP_TEMPLATE(EllipsizeMode, ellipsizeModeFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(FontWeight, fontWeightFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(FontStyle, fontStyleFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(FontVariant, fontVariantFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(WritingDirection, writingDirectionFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(TextAlignment, textAlignmentFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(TextDecorationLineType, textDecorationLineTypeFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(TextDecorationLineStyle, textDecorationLineStyleFromDynamic)
+APPLY_RAW_PROP_TEMPLATE(TextDecorationLinePattern, textDecorationLinePatternFromDynamic)
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/tests/TextTest.cpp b/ReactCommon/fabric/text/tests/TextTest.cpp
index 55ae97a50fad..6b995ae90d7b 100644
--- a/ReactCommon/fabric/text/tests/TextTest.cpp
+++ b/ReactCommon/fabric/text/tests/TextTest.cpp
@@ -9,6 +9,6 @@
 
 #include <gtest/gtest.h>
 
-TEST(TextLayoutManagerTest, testSomething) {
+TEST(TextTest, testSomething) {
   // TODO:
 }
diff --git a/ReactCommon/fabric/text/text/TextComponentDescriptor.h b/ReactCommon/fabric/text/text/TextComponentDescriptor.h
new file mode 100644
index 000000000000..043492f21e91
--- /dev/null
+++ b/ReactCommon/fabric/text/text/TextComponentDescriptor.h
@@ -0,0 +1,25 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ConcreteComponentDescriptor.h>
+#include <fabric/text/TextProps.h>
+#include <fabric/text/TextShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class TextComponentDescriptor: public ConcreteComponentDescriptor<TextShadowNode> {
+public:
+  ComponentName getComponentName() const override {
+    return "Text";
+  }
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/text/TextProps.cpp b/ReactCommon/fabric/text/text/TextProps.cpp
new file mode 100644
index 000000000000..402d2ea67129
--- /dev/null
+++ b/ReactCommon/fabric/text/text/TextProps.cpp
@@ -0,0 +1,75 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "TextProps.h"
+
+#include <fabric/attributedstring/textValuesConversions.h>
+#include <fabric/core/propsConversions.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/graphics/graphicValuesConversions.h>
+#include <fabric/text/propsConversions.h>
+
+namespace facebook {
+namespace react {
+
+void TextProps::apply(const RawProps &rawProps) {
+  Props::apply(rawProps);
+
+  // Color
+  applyRawProp(rawProps, "color", textAttributes_.foregroundColor);
+  applyRawProp(rawProps, "backgroundColor", textAttributes_.backgroundColor);
+  applyRawProp(rawProps, "opacity", textAttributes_.opacity);
+
+  // Font
+  applyRawProp(rawProps, "fontFamily", textAttributes_.fontFamily);
+  applyRawProp(rawProps, "fontSize", textAttributes_.fontSize);
+  applyRawProp(rawProps, "fontSizeMultiplier", textAttributes_.fontSizeMultiplier);
+  applyRawProp(rawProps, "fontWeight", textAttributes_.fontWeight);
+  applyRawProp(rawProps, "fontStyle", textAttributes_.fontStyle);
+  applyRawProp(rawProps, "fontVariant", textAttributes_.fontVariant);
+  applyRawProp(rawProps, "allowFontScaling", textAttributes_.allowFontScaling);
+  applyRawProp(rawProps, "letterSpacing", textAttributes_.letterSpacing);
+
+  // Paragraph
+  applyRawProp(rawProps, "lineHeight", textAttributes_.lineHeight);
+  applyRawProp(rawProps, "alignment", textAttributes_.alignment);
+  applyRawProp(rawProps, "baseWritingDirection", textAttributes_.baseWritingDirection);
+
+  // Decoration
+  applyRawProp(rawProps, "textDecorationColor", textAttributes_.textDecorationColor);
+  applyRawProp(rawProps, "textDecorationLineType", textAttributes_.textDecorationLineType);
+  applyRawProp(rawProps, "textDecorationLineStyle", textAttributes_.textDecorationLineStyle);
+  applyRawProp(rawProps, "textDecorationLinePattern", textAttributes_.textDecorationLinePattern);
+
+  // Shadow
+  applyRawProp(rawProps, "textShadowOffset", textAttributes_.textShadowOffset);
+  applyRawProp(rawProps, "textShadowRadius", textAttributes_.textShadowRadius);
+  applyRawProp(rawProps, "textShadowColor", textAttributes_.textShadowColor);
+
+  // Special
+  applyRawProp(rawProps, "isHighlighted", textAttributes_.isHighlighted);
+}
+
+#pragma mark - Getters
+
+TextAttributes TextProps::getTextAttributes() const {
+  return textAttributes_;
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList TextProps::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+
+  auto textAttributesPropsList = textAttributes_.getDebugProps();
+  std::move(textAttributesPropsList.begin(), textAttributesPropsList.end(), std::back_inserter(list));
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/text/TextProps.h b/ReactCommon/fabric/text/text/TextProps.h
new file mode 100644
index 000000000000..1a96b5519fb8
--- /dev/null
+++ b/ReactCommon/fabric/text/text/TextProps.h
@@ -0,0 +1,46 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/attributedstring/TextAttributes.h>
+#include <fabric/core/Props.h>
+#include <fabric/graphics/Color.h>
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+class TextProps;
+
+using SharedTextProps = std::shared_ptr<const TextProps>;
+
+class TextProps:
+  public Props {
+
+public:
+  void apply(const RawProps &rawProps) override;
+
+#pragma mark - Getters
+
+  TextAttributes getTextAttributes() const;
+
+private:
+
+  /*
+   * Not all `TextAttributes` fields make sense and is used as TextProps values.
+   */
+  TextAttributes textAttributes_;
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+};
+
+} // namespace react
+} // namespace facebook
+
diff --git a/ReactCommon/fabric/text/text/TextShadowNode.cpp b/ReactCommon/fabric/text/text/TextShadowNode.cpp
new file mode 100644
index 000000000000..5429c7ba6063
--- /dev/null
+++ b/ReactCommon/fabric/text/text/TextShadowNode.cpp
@@ -0,0 +1,59 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "TextShadowNode.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+#include "RawTextShadowNode.h"
+#include "RawTextProps.h"
+
+namespace facebook {
+namespace react {
+
+ComponentName TextShadowNode::getComponentName() const {
+  return ComponentName("Text");
+}
+
+AttributedString TextShadowNode::getAttributedString(const TextAttributes &baseTextAttributes) const {
+  // TODO: Implement caching.
+
+  TextAttributes textAttributes = baseTextAttributes;
+  textAttributes.apply(getProps()->getTextAttributes());
+
+  AttributedString attributedString;
+
+  for (auto &&childNode : *getChildren()) {
+    // RawShadowNode
+    SharedRawTextShadowNode rawTextShadowNode = std::dynamic_pointer_cast<const RawTextShadowNode>(childNode);
+    if (rawTextShadowNode) {
+      AttributedString::Fragment fragment;
+      fragment.string = rawTextShadowNode->getProps()->getText();
+      fragment.textAttributes = textAttributes;
+      attributedString.appendFragment(fragment);
+      continue;
+    }
+
+    // TextShadowNode
+    SharedTextShadowNode textShadowNode = std::dynamic_pointer_cast<const TextShadowNode>(childNode);
+    if (textShadowNode) {
+      attributedString.appendAttributedString(textShadowNode->getAttributedString(textAttributes));
+      continue;
+    }
+
+    // Any other kind of ShadowNode
+    AttributedString::Fragment fragment;
+    fragment.shadowNode = childNode;
+    fragment.textAttributes = textAttributes;
+    attributedString.appendFragment(fragment);
+  }
+
+  return attributedString;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/text/TextShadowNode.h b/ReactCommon/fabric/text/text/TextShadowNode.h
new file mode 100644
index 000000000000..0eb421a96630
--- /dev/null
+++ b/ReactCommon/fabric/text/text/TextShadowNode.h
@@ -0,0 +1,40 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/attributedstring/AttributedString.h>
+#include <fabric/attributedstring/TextAttributes.h>
+#include <fabric/core/ConcreteShadowNode.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/text/TextProps.h>
+#include <fabric/text/TextShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class TextShadowNode;
+
+using SharedTextShadowNode = std::shared_ptr<const TextShadowNode>;
+
+class TextShadowNode:
+  public ConcreteShadowNode<TextProps> {
+
+public:
+
+  using ConcreteShadowNode::ConcreteShadowNode;
+
+  ComponentName getComponentName() const override;
+
+  /*
+   * Returns a `AttributedString` which represents text content of the node.
+   */
+  AttributedString getAttributedString(const TextAttributes &baseTextAttributes) const;
+};
+
+} // namespace react
+} // namespace facebook

From b5a780608e7c48f370f6aabb5db4c6d6c6923848 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 7 May 2018 21:49:23 -0700
Subject: [PATCH 0459/1109] Fabric/Text: text module, paragraph part

Summary: <Paragraph> component represents <View>-like component containing and displaying text.

Reviewed By: mdvacca

Differential Revision: D7751854

fbshipit-source-id: 1acdfebf6f96a5da068ce985e15288e958266855
---
 ReactCommon/fabric/text/BUCK                  |  6 +-
 .../paragraph/ParagraphComponentDescriptor.h  | 55 +++++++++++++
 .../text/paragraph/ParagraphLocalData.cpp     | 46 +++++++++++
 .../text/paragraph/ParagraphLocalData.h       | 56 +++++++++++++
 .../fabric/text/paragraph/ParagraphProps.cpp  | 59 ++++++++++++++
 .../fabric/text/paragraph/ParagraphProps.h    | 60 ++++++++++++++
 .../text/paragraph/ParagraphShadowNode.cpp    | 63 +++++++++++++++
 .../text/paragraph/ParagraphShadowNode.h      | 78 +++++++++++++++++++
 8 files changed, 421 insertions(+), 2 deletions(-)
 create mode 100644 ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
 create mode 100644 ReactCommon/fabric/text/paragraph/ParagraphLocalData.h
 create mode 100644 ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
 create mode 100644 ReactCommon/fabric/text/paragraph/ParagraphProps.h
 create mode 100644 ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
 create mode 100644 ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h

diff --git a/ReactCommon/fabric/text/BUCK b/ReactCommon/fabric/text/BUCK
index 20a30de39663..04fbad8d1749 100644
--- a/ReactCommon/fabric/text/BUCK
+++ b/ReactCommon/fabric/text/BUCK
@@ -1,5 +1,5 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags", "get_fbobjc_enable_exception_lang_compiler_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -40,6 +40,7 @@ rn_xplat_cxx_library(
     ],
     force_static = True,
     macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
@@ -52,6 +53,7 @@ rn_xplat_cxx_library(
         "xplat//folly:memory",
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
         react_native_xplat_target("fabric/attributedstring:attributedstring"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/debug:debug"),
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h b/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
new file mode 100644
index 000000000000..d77676783006
--- /dev/null
+++ b/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
@@ -0,0 +1,55 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ConcreteComponentDescriptor.h>
+#include <fabric/text/ParagraphShadowNode.h>
+#include <fabric/textlayoutmanager/TextLayoutManager.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Descriptor for <Paragraph> component.
+ */
+class ParagraphComponentDescriptor: public ConcreteComponentDescriptor<ParagraphShadowNode> {
+public:
+
+  ParagraphComponentDescriptor():
+    ConcreteComponentDescriptor<ParagraphShadowNode>() {
+    // Every single `ParagraphShadowNode` will have a reference to
+    // a shared `TextLayoutManager`.
+    textLayoutManager_ = std::make_shared<TextLayoutManager>();
+  }
+
+  ComponentName getComponentName() const override {
+    return "Paragraph";
+  }
+
+  void adopt(UnsharedShadowNode shadowNode) const override {
+    ConcreteComponentDescriptor<ParagraphShadowNode>::adopt(shadowNode);
+
+    assert(std::dynamic_pointer_cast<ParagraphShadowNode>(shadowNode));
+    auto paragraphShadowNode = std::static_pointer_cast<ParagraphShadowNode>(shadowNode);
+
+    // `ParagraphShadowNode` uses `TextLayoutManager` to measure text content
+    // and communicate text rendering metrics to mounting layer.
+    paragraphShadowNode->setTextLayoutManager(textLayoutManager_);
+
+    // All `ParagraphShadowNode`s must have leaf Yoga nodes with properly
+    // setup measure function.
+    paragraphShadowNode->enableMeasurement();
+  }
+
+private:
+
+  SharedTextLayoutManager textLayoutManager_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
new file mode 100644
index 000000000000..0390313b689c
--- /dev/null
+++ b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
@@ -0,0 +1,46 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ParagraphLocalData.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+namespace facebook {
+namespace react {
+
+AttributedString ParagraphLocalData::getAttributedString() const {
+  return attributedString_;
+}
+
+void ParagraphLocalData::setAttributedString(AttributedString attributedString) {
+  ensureUnsealed();
+  attributedString_ = attributedString;
+}
+
+SharedTextLayoutManager ParagraphLocalData::getTextLayoutManager() const {
+  return textLayoutManager_;
+}
+
+void ParagraphLocalData::setTextLayoutManager(SharedTextLayoutManager textLayoutManager) {
+  ensureUnsealed();
+  textLayoutManager_ = textLayoutManager;
+}
+
+#pragma mark - DebugStringConvertible
+
+std::string ParagraphLocalData::getDebugName() const {
+  return "ParagraphLocalData";
+}
+
+SharedDebugStringConvertibleList ParagraphLocalData::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+  list.push_back(std::make_shared<DebugStringConvertibleItem>("attributedString", attributedString_.getDebugDescription()));
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.h b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.h
new file mode 100644
index 000000000000..7f3ad4007a33
--- /dev/null
+++ b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.h
@@ -0,0 +1,56 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/attributedstring/AttributedString.h>
+#include <fabric/core/LocalData.h>
+#include <fabric/textlayoutmanager/TextLayoutManager.h>
+
+namespace facebook {
+namespace react {
+
+class ParagraphLocalData;
+
+using SharedParagraphLocalData = std::shared_ptr<const ParagraphLocalData>;
+
+/*
+ * LocalData for <Paragraph> component.
+ * Represents what to render and how to render.
+ */
+class ParagraphLocalData:
+  public LocalData {
+
+public:
+
+  /*
+   * All content of <Paragraph> component represented as an `AttributedString`.
+   */
+  AttributedString getAttributedString() const;
+  void setAttributedString(AttributedString attributedString);
+
+  /*
+   * `TextLayoutManager` provides a connection to platform-specific
+   * text rendering infrastructure which is capable to render the
+   * `AttributedString`.
+   */
+  SharedTextLayoutManager getTextLayoutManager() const;
+  void setTextLayoutManager(SharedTextLayoutManager textLayoutManager);
+
+#pragma mark - DebugStringConvertible
+
+  std::string getDebugName() const override;
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+private:
+
+  AttributedString attributedString_;
+  SharedTextLayoutManager textLayoutManager_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
new file mode 100644
index 000000000000..89faa944565a
--- /dev/null
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
@@ -0,0 +1,59 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ParagraphProps.h"
+
+#include <fabric/attributedstring/textValuesConversions.h>
+#include <fabric/core/propsConversions.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/text/propsConversions.h>
+
+namespace facebook {
+namespace react {
+
+void ParagraphProps::apply(const RawProps &rawProps) {
+  ViewProps::apply(rawProps);
+
+  // Paragraph Attributes
+  applyRawProp(rawProps, "numberOfLines", paragraphAttributes_.maximumNumberOfLines);
+  applyRawProp(rawProps, "ellipsizeMode", paragraphAttributes_.ellipsizeMode);
+  applyRawProp(rawProps, "adjustsFontSizeToFit", paragraphAttributes_.adjustsFontSizeToFit);
+  applyRawProp(rawProps, "minimumFontSize", paragraphAttributes_.minimumFontSize);
+  applyRawProp(rawProps, "maximumFontSize", paragraphAttributes_.maximumFontSize);
+
+  // Other Props
+  applyRawProp(rawProps, "selectable", isSelectable_);
+}
+
+#pragma mark - Getters
+
+ParagraphAttributes ParagraphProps::getParagraphAttributes() const {
+  return paragraphAttributes_;
+}
+
+bool ParagraphProps::getIsSelectable() const {
+  return isSelectable_;
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList ParagraphProps::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+
+  // Paragraph Props
+  auto &&paragraphAttributePropsList = paragraphAttributes_.getDebugProps();
+  std::move(paragraphAttributePropsList.begin(), paragraphAttributePropsList.end(), std::back_inserter(list));
+
+  // View Props
+  auto &&viewPropsList = ViewProps::getDebugProps();
+  std::move(viewPropsList.begin(), viewPropsList.end(), std::back_inserter(list));
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.h b/ReactCommon/fabric/text/paragraph/ParagraphProps.h
new file mode 100644
index 000000000000..42d630f04d0f
--- /dev/null
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.h
@@ -0,0 +1,60 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <limits>
+#include <memory>
+
+#include <fabric/attributedstring/ParagraphAttributes.h>
+#include <fabric/core/Props.h>
+#include <fabric/view/ViewProps.h>
+
+namespace facebook {
+namespace react {
+
+class ParagraphProps;
+
+using SharedParagraphProps = std::shared_ptr<const ParagraphProps>;
+
+/*
+ * Props of <Paragraph> component.
+ * Most of the props are directly stored in composed `ParagraphAttributes`
+ * object.
+ */
+class ParagraphProps:
+  public ViewProps {
+
+public:
+
+  void apply(const RawProps &rawProps) override;
+
+#pragma mark - Getters
+
+  /*
+   * Returns `ParagraphAttributes` object which has all prop values that affect
+   * visual representation of the paragraph.
+   */
+  ParagraphAttributes getParagraphAttributes() const;
+
+  /*
+   * Defines can the text be selected (and copied) or not.
+   */
+  bool getIsSelectable() const;
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+private:
+
+  ParagraphAttributes paragraphAttributes_ {};
+  bool isSelectable_ {false};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
new file mode 100644
index 000000000000..76e90f9b9bca
--- /dev/null
+++ b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
@@ -0,0 +1,63 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ParagraphShadowNode.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+#import "ParagraphLocalData.h"
+
+namespace facebook {
+namespace react {
+
+ComponentName ParagraphShadowNode::getComponentName() const {
+  return ComponentName("Paragraph");
+}
+  
+SharedTextShadowNode ParagraphShadowNode::getTextChildNode() const {
+  // <Paragraph> component must always have a single <Text> child component.
+  assert(getChildren()->size() == 1);
+  auto childNode = getChildren()->front();
+  assert(std::dynamic_pointer_cast<const TextShadowNode>(childNode));
+  return std::static_pointer_cast<const TextShadowNode>(childNode);
+}
+
+AttributedString ParagraphShadowNode::getAttributedString() const {
+  return getTextChildNode()->getAttributedString(TextAttributes());
+}
+
+void ParagraphShadowNode::setTextLayoutManager(SharedTextLayoutManager textLayoutManager) {
+  ensureUnsealed();
+  textLayoutManager_ = textLayoutManager;
+}
+
+void ParagraphShadowNode::updateLocalData() {
+  ensureUnsealed();
+
+  auto localData = std::make_shared<ParagraphLocalData>();
+  localData->setAttributedString(getAttributedString());
+  localData->setTextLayoutManager(textLayoutManager_);
+  setLocalData(localData);
+}
+
+#pragma mark - LayoutableShadowNode
+
+Size ParagraphShadowNode::measure(LayoutConstraints layoutConstraints) const {
+  return textLayoutManager_->measure(
+    getAttributedString(),
+    getProps()->getParagraphAttributes(),
+    layoutConstraints
+  );
+}
+
+void ParagraphShadowNode::layout(LayoutContext layoutContext) {
+  updateLocalData();
+  ConcreteViewShadowNode<ParagraphProps>::layout(layoutContext);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
new file mode 100644
index 000000000000..2348d84655d0
--- /dev/null
+++ b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
@@ -0,0 +1,78 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ConcreteShadowNode.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/core/LayoutContext.h>
+#include <fabric/text/ParagraphProps.h>
+#include <fabric/text/TextShadowNode.h>
+#include <fabric/textlayoutmanager/TextLayoutManager.h>
+#include <fabric/view/ConcreteViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class ParagraphShadowNode;
+
+using SharedParagraphShadowNode = std::shared_ptr<const ParagraphShadowNode>;
+
+/*
+ * `ShadowNode` for <Paragraph> component, represents <View>-like component
+ * containing and displaying text. Text content is represented as nested <Text>
+ * and <RawText> components.
+ * Note some Hierarchical constraints:
+ *  * <Paragraph> component must have only one <Text> component.
+ *  * <Text> component might have nested <Text>, <RawText>, and <View>-like
+ *    components.
+ *  * <RawText> component must not have any children.
+ */
+class ParagraphShadowNode:
+  public ConcreteViewShadowNode<ParagraphProps> {
+
+public:
+
+  using ConcreteViewShadowNode::ConcreteViewShadowNode;
+
+  ComponentName getComponentName() const override;
+
+  /*
+   * Returns a single nested <Text> shadow node.
+   */
+  SharedTextShadowNode getTextChildNode() const;
+
+  /*
+   * Returns a `AttributedString` which represents text content of the node.
+   */
+  AttributedString getAttributedString() const;
+
+  /*
+   * Associates a shared TextLayoutManager with the node.
+   * `ParagraphShadowNode` uses the manager to measure text content
+   * and construct `ParagraphLocalData` objects.
+   */
+  void setTextLayoutManager(SharedTextLayoutManager textLayoutManager);
+
+#pragma mark - LayoutableShadowNode
+
+  void layout(LayoutContext layoutContext) override;
+  Size measure(LayoutConstraints layoutConstraints) const override;
+
+private:
+
+  /*
+   * Creates a `LocalData` object (with `AttributedText` and
+   * `TextLayoutManager`) if needed.
+   */
+  void updateLocalData();
+
+  SharedTextLayoutManager textLayoutManager_;
+};
+
+} // namespace react
+} // namespace facebook

From 7e97ed00bc5c7cd6a5b8bbc711ddf0e0730ccb8a Mon Sep 17 00:00:00 2001
From: Riley Dulin <dulinr@fb.com>
Date: Tue, 8 May 2018 17:57:51 -0700
Subject: [PATCH 0460/1109] Fix prepack warning in RN bridge code

Reviewed By: yungsters

Differential Revision: D7903364

fbshipit-source-id: 4ef888f4e7f773f9fbc5183db2470b0f7b368d8a
---
 Libraries/Interaction/FrameRateLogger.js | 13 ++++++++++++-
 1 file changed, 12 insertions(+), 1 deletion(-)

diff --git a/Libraries/Interaction/FrameRateLogger.js b/Libraries/Interaction/FrameRateLogger.js
index 252fc465a3d4..1653b85915a2 100644
--- a/Libraries/Interaction/FrameRateLogger.js
+++ b/Libraries/Interaction/FrameRateLogger.js
@@ -40,7 +40,18 @@ const FrameRateLogger = {
         'Trying to debug FrameRateLogger without the native module!',
       );
     }
-    NativeModules.FrameRateLogger && NativeModules.FrameRateLogger.setGlobalOptions(options);
+    if (NativeModules.FrameRateLogger) {
+      // Freeze the object to avoid the prepack warning (PP0017) about leaking
+      // unfrozen objects.
+      // Needs to clone the object first to avoid modifying the argument.
+      const optionsClone = {
+        debug: !!options.debug,
+        reportStackTraces: !!options.reportStackTraces,
+      };
+      Object.freeze(optionsClone);
+      Object.seal(optionsClone);
+      NativeModules.FrameRateLogger.setGlobalOptions(optionsClone);
+    }
   },
 
   /**

From 9646c5cb3c40ef29be4bdbf39775ccfaddd8e489 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 18:50:05 -0700
Subject: [PATCH 0461/1109] Fabric: RCTViewComponentView, storing just applied
 `layoutMetrics`

Summary:
This will be useful for this class and for subclasses soon.
For instance, when we draw something in `drawRect:`, we need to know exact content frame for rendering.

Reviewed By: mdvacca

Differential Revision: D7751855

fbshipit-source-id: 5d688368edd7b4f3c8c19d54ca701a9cc361270b
---
 React/Fabric/Mounting/RCTViewComponentView.h  | 6 +++++-
 React/Fabric/Mounting/RCTViewComponentView.mm | 8 ++++++++
 2 files changed, 13 insertions(+), 1 deletion(-)

diff --git a/React/Fabric/Mounting/RCTViewComponentView.h b/React/Fabric/Mounting/RCTViewComponentView.h
index 046030a8faa3..8dc5fc2e12df 100644
--- a/React/Fabric/Mounting/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/RCTViewComponentView.h
@@ -9,13 +9,17 @@
 
 #import <React/RCTComponentViewProtocol.h>
 #import <React/UIView+ComponentViewProtocol.h>
+#import <fabric/core/LayoutMetrics.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
 /**
  * UIView class for <View> component.
  */
-@interface RCTViewComponentView : UIView <RCTComponentViewProtocol>
+@interface RCTViewComponentView : UIView <RCTComponentViewProtocol> {
+@protected
+  facebook::react::LayoutMetrics _layoutMetrics;
+}
 
 @end
 
diff --git a/React/Fabric/Mounting/RCTViewComponentView.mm b/React/Fabric/Mounting/RCTViewComponentView.mm
index 24a985949012..cc3c0772bd75 100644
--- a/React/Fabric/Mounting/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/RCTViewComponentView.mm
@@ -30,4 +30,12 @@ - (void)updateProps:(facebook::react::SharedProps)props
   // TODO: Implement all sutable non-layout <View> props.
 }
 
+- (void)updateLayoutMetrics:(LayoutMetrics)layoutMetrics
+           oldLayoutMetrics:(LayoutMetrics)oldLayoutMetrics
+{
+  [super updateLayoutMetrics:layoutMetrics oldLayoutMetrics:oldLayoutMetrics];
+
+  _layoutMetrics = layoutMetrics;
+}
+
 @end

From 81bdd36204f246938dbe2ee108d280525e5b8476 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 18:50:10 -0700
Subject: [PATCH 0462/1109] Fabric/Text: RCTParagraphComponentView

Summary: RCTParagraphComponentView is a UIView which can render text using TextLayoutManager.

Reviewed By: mdvacca

Differential Revision: D7751853

fbshipit-source-id: e6ee9a0f989cdf6e878390d37dbcf8a11ef90bf4
---
 .../Mounting/RCTParagraphComponentView.h      | 21 +++++
 .../Mounting/RCTParagraphComponentView.mm     | 80 +++++++++++++++++++
 .../fabric/core/layout/LayoutMetrics.h        |  7 ++
 3 files changed, 108 insertions(+)
 create mode 100644 React/Fabric/Mounting/RCTParagraphComponentView.h
 create mode 100644 React/Fabric/Mounting/RCTParagraphComponentView.mm

diff --git a/React/Fabric/Mounting/RCTParagraphComponentView.h b/React/Fabric/Mounting/RCTParagraphComponentView.h
new file mode 100644
index 000000000000..92700da77d64
--- /dev/null
+++ b/React/Fabric/Mounting/RCTParagraphComponentView.h
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTViewComponentView.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * UIView class for <Paragraph> component.
+ */
+@interface RCTParagraphComponentView : RCTViewComponentView
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/RCTParagraphComponentView.mm b/React/Fabric/Mounting/RCTParagraphComponentView.mm
new file mode 100644
index 000000000000..6709bd2b2223
--- /dev/null
+++ b/React/Fabric/Mounting/RCTParagraphComponentView.mm
@@ -0,0 +1,80 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTParagraphComponentView.h"
+
+#import <fabric/core/LocalData.h>
+#import <fabric/graphics/Geometry.h>
+#import <fabric/text/ParagraphLocalData.h>
+#import <fabric/text/ParagraphProps.h>
+#import <fabric/textlayoutmanager/TextLayoutManager.h>
+#import <fabric/textlayoutmanager/RCTTextLayoutManager.h>
+
+using namespace facebook::react;
+
+@implementation RCTParagraphComponentView {
+  SharedParagraphLocalData _paragraphLocalData;
+  ParagraphAttributes _paragraphAttributes;
+}
+
+- (instancetype)initWithFrame:(CGRect)frame
+{
+  if (self = [super initWithFrame:frame]) {
+    self.isAccessibilityElement = YES;
+    self.accessibilityTraits |= UIAccessibilityTraitStaticText;
+    self.opaque = NO;
+    self.contentMode = UIViewContentModeRedraw;
+  }
+
+  return self;
+}
+
+- (void)updateProps:(SharedProps)props oldProps:(SharedProps)oldProps
+{
+  [super updateProps:props oldProps:oldProps];
+  auto paragraphProps = std::static_pointer_cast<const ParagraphProps>(props);
+  assert(paragraphProps);
+  _paragraphAttributes = paragraphProps->getParagraphAttributes();
+}
+
+- (void)updateLocalData:(SharedLocalData)localData
+           oldLocalData:(SharedLocalData)oldLocalData
+{
+  _paragraphLocalData = std::static_pointer_cast<const ParagraphLocalData>(localData);
+  assert(_paragraphLocalData);
+  [self setNeedsDisplay];
+}
+
+- (void)drawRect:(CGRect)rect
+{
+  if (!_paragraphLocalData) {
+    return;
+  }
+
+  SharedTextLayoutManager textLayoutManager =
+    _paragraphLocalData->getTextLayoutManager();
+  RCTTextLayoutManager *nativeTextLayoutManager =
+    (__bridge RCTTextLayoutManager *)textLayoutManager->getNativeTextLayoutManager();
+
+  auto contentFrame = _layoutMetrics.getContentFrame();
+  CGRect frame = {
+    .origin = {
+      .x = contentFrame.origin.x,
+      .y = contentFrame.origin.y
+    },
+    .size = {
+      .width = contentFrame.size.width,
+      .height = contentFrame.size.height
+    }
+  };
+
+  [nativeTextLayoutManager drawAttributedString:_paragraphLocalData->getAttributedString()
+                            paragraphAttributes:_paragraphAttributes
+                                          frame:frame];
+}
+
+@end
diff --git a/ReactCommon/fabric/core/layout/LayoutMetrics.h b/ReactCommon/fabric/core/layout/LayoutMetrics.h
index 22cff2d7cc1e..e1c74359e8e7 100644
--- a/ReactCommon/fabric/core/layout/LayoutMetrics.h
+++ b/ReactCommon/fabric/core/layout/LayoutMetrics.h
@@ -23,6 +23,13 @@ struct LayoutMetrics {
   DisplayType displayType {DisplayType::Flex};
   LayoutDirection layoutDirection {LayoutDirection::Undefined};
 
+  Rect getContentFrame() const {
+    return Rect {
+      Point {contentInsets.left, contentInsets.top},
+      Size {frame.size.width - contentInsets.left - contentInsets.right, frame.size.height - contentInsets.top - contentInsets.bottom}
+    };
+  }
+
   bool operator ==(const LayoutMetrics& rhs) const {
     return
       std::tie(this->frame, this->contentInsets, this->borderWidth, this->displayType, this->layoutDirection) ==

From f3893aab3b069ec3dba04bd1181231704bec899b Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 18:50:15 -0700
Subject: [PATCH 0463/1109] Fabric/Text: Connecting the dots

Summary: This change registers the Text module.

Reviewed By: mdvacca

Differential Revision: D7784509

fbshipit-source-id: 0de3e432b8f975927547ba990586f99655e8322d
---
 .../textlayoutmanager/RCTTextLayoutManager.mm |  1 -
 ReactCommon/fabric/uimanager/BUCK             |  1 +
 .../fabric/uimanager/FabricUIManager.cpp      | 21 +++++++++++++++++++
 ReactCommon/fabric/uimanager/Scheduler.cpp    | 10 +++++++--
 4 files changed, 30 insertions(+), 3 deletions(-)

diff --git a/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm b/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm
index f729c9c814c7..33a2fdb702d8 100644
--- a/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm
+++ b/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm
@@ -63,7 +63,6 @@ - (void)drawAttributedString:(AttributedString)attributedString
    [layoutManager drawGlyphsForGlyphRange:glyphRange atPoint:frame.origin];
 }
 
-
 - (NSTextStorage *)_textStorageAndLayoutManagerWithAttributesString:(NSAttributedString *)attributedString
                                                 paragraphAttributes:(ParagraphAttributes)paragraphAttributes
                                                                size:(CGSize)size
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 4a3eeae2ba5f..39004b1e121d 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -52,6 +52,7 @@ rn_xplat_cxx_library(
         "xplat//third-party/glog:glog",
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/text:text"),
         react_native_xplat_target("fabric/view:view"),
     ],
 )
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 3b8786b29889..b9a5cd57fcb7 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -39,12 +39,33 @@ static const RawProps rawPropsFromDynamic(const folly::dynamic object) {
 }
 
 static const std::string componentNameByReactViewName(std::string viewName) {
+  // We need this function only for the transition period;
+  // eventually, all names will be unified.
+
   std::string rctPrefix("RCT");
   if (std::mismatch(rctPrefix.begin(), rctPrefix.end(), viewName.begin()).first == rctPrefix.end()) {
     // If `viewName` has "RCT" prefix, remove it.
     viewName.erase(0, 3);
   }
 
+  // Fabric uses slightly new names for Text components because of differences
+  // in semantic.
+  if (viewName == "Text") {
+    return "Paragraph";
+  }
+  if (viewName == "VirtualText") {
+    return "Text";
+  }
+
+  // We need this temporarly for testing purposes until we have proper
+  // implementation of <ScrollView> component.
+  if (
+    viewName == "ScrollContentView" ||
+    viewName == "ScrollView"
+  ) {
+    return "View";
+  }
+
   return viewName;
 }
 
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index b2571ebf6168..8b5038c31f7c 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -5,6 +5,9 @@
 #include <fabric/core/LayoutContext.h>
 #include <fabric/uimanager/ComponentDescriptorRegistry.h>
 #include <fabric/uimanager/FabricUIManager.h>
+#include <fabric/text/ParagraphComponentDescriptor.h>
+#include <fabric/text/TextComponentDescriptor.h>
+#include <fabric/text/RawTextComponentDescriptor.h>
 #include <fabric/view/ViewComponentDescriptor.h>
 #include <fabric/view/ViewProps.h>
 #include <fabric/view/ViewShadowNode.h>
@@ -16,8 +19,11 @@ namespace react {
 
 Scheduler::Scheduler() {
   auto componentDescriptorRegistry = std::make_shared<ComponentDescriptorRegistry>();
-  SharedComponentDescriptor viewComponentDescriptor = std::make_shared<ViewComponentDescriptor>();
-  componentDescriptorRegistry->registerComponentDescriptor(viewComponentDescriptor);
+
+  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ViewComponentDescriptor>());
+  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ParagraphComponentDescriptor>());
+  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<TextComponentDescriptor>());
+  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<RawTextComponentDescriptor>());
 
   uiManager_ = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
   uiManager_->setDelegate(this);

From 9ea7957958c3f7acdaec6309117af61072986818 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 18:50:19 -0700
Subject: [PATCH 0464/1109] Fabric: Do not crash in attempt to mount
 layout-only components

Summary: We do not have a clear strategy how to deal with layout-only (view-less) components. Even if this particular solution is not so fancy, it prevents crashing during text rendering.

Reviewed By: mdvacca

Differential Revision: D7785885

fbshipit-source-id: f3ed8988aa2b41349fd1693c2a7f8c9368daee43
---
 React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm | 5 +++++
 React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm | 4 ++++
 React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm | 4 ++++
 3 files changed, 13 insertions(+)

diff --git a/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm b/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm
index 99909f450cc2..ed4a884e411c 100644
--- a/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm
+++ b/React/Fabric/Mounting/MountItems/RCTDeleteMountItem.mm
@@ -28,6 +28,11 @@ - (instancetype)initWithComponentName:(NSString *)componentName
 - (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
 {
   UIView<RCTComponentViewProtocol> *componentView = [registry componentViewByTag:_tag];
+
+  if (componentView == nil) {
+    return;
+  }
+
   [registry enqueueComponentViewWithName:_componentName tag:_tag componentView:componentView];
 }
 
diff --git a/React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm b/React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm
index f714cb0a70db..740718b963d5 100644
--- a/React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm
+++ b/React/Fabric/Mounting/MountItems/RCTInsertMountItem.mm
@@ -33,6 +33,10 @@ - (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
   UIView<RCTComponentViewProtocol> *childComponentView = [registry componentViewByTag:_childTag];
   UIView<RCTComponentViewProtocol> *parentComponentView = [registry componentViewByTag:_parentTag];
 
+  if (childComponentView == nil || parentComponentView == nil) {
+    return;
+  }
+
   [parentComponentView mountChildComponentView:childComponentView
                                          index:_index];
 }
diff --git a/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm b/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm
index d46b936dd044..3279b939438f 100644
--- a/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm
+++ b/React/Fabric/Mounting/MountItems/RCTRemoveMountItem.mm
@@ -33,6 +33,10 @@ - (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
   UIView<RCTComponentViewProtocol> *childComponentView = [registry componentViewByTag:_childTag];
   UIView<RCTComponentViewProtocol> *parentComponentView = [registry componentViewByTag:_parentTag];
 
+  if (childComponentView == nil || parentComponentView == nil) {
+    return;
+  }
+
   [parentComponentView unmountChildComponentView:childComponentView
                                            index:_index];
 }

From d9ff1769aaff704ae612b4e0532fc2737a91c4ff Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 18:50:25 -0700
Subject: [PATCH 0465/1109] Fabric/Text: <Paragraph> is now supporting text
 attributes

Summary:
I was shamed by Sebastian's sebmarkbage concerns (totally unrelated to this topic) about introducing another level of indirection into the system and decided to change my original plan not to support text attributes for the <Paragraph> component.

So, now <Paragraph> shares <View>, <Text> and <Paragraph> itself capabilities. That reduces the minimum amount of required components for trivial text fragment from three (Paragraph, Text, RawText) to two (Paragraph and RawText).

Special thanks for C++ for supporting multiple inheritance.

Reviewed By: mdvacca

Differential Revision: D7785889

fbshipit-source-id: dd9f2e2650bfbfd76d7d4b538adaf409f9429df3
---
 ReactCommon/fabric/attributedstring/BUCK      |  5 +-
 ReactCommon/fabric/core/BUCK                  |  5 +-
 ReactCommon/fabric/debug/BUCK                 | 10 ++-
 ReactCommon/fabric/graphics/BUCK              | 14 +++-
 ReactCommon/fabric/text/BUCK                  |  1 +
 .../fabric/text/basetext/BaseTextProps.cpp    | 73 +++++++++++++++++++
 .../fabric/text/basetext/BaseTextProps.h      | 48 ++++++++++++
 .../text/basetext/BaseTextShadowNode.cpp      | 59 +++++++++++++++
 .../fabric/text/basetext/BaseTextShadowNode.h | 33 +++++++++
 .../fabric/text/paragraph/ParagraphProps.cpp  | 11 ++-
 .../fabric/text/paragraph/ParagraphProps.h    |  4 +-
 .../text/paragraph/ParagraphShadowNode.cpp    | 10 +--
 .../text/paragraph/ParagraphShadowNode.h      | 13 +---
 ReactCommon/fabric/text/text/TextProps.cpp    | 48 +-----------
 ReactCommon/fabric/text/text/TextProps.h      | 16 +---
 .../fabric/text/text/TextShadowNode.cpp       | 39 ----------
 ReactCommon/fabric/text/text/TextShadowNode.h |  9 +--
 ReactCommon/fabric/textlayoutmanager/BUCK     | 13 ++--
 ReactCommon/fabric/view/BUCK                  |  4 +-
 19 files changed, 268 insertions(+), 147 deletions(-)
 create mode 100644 ReactCommon/fabric/text/basetext/BaseTextProps.cpp
 create mode 100644 ReactCommon/fabric/text/basetext/BaseTextProps.h
 create mode 100644 ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
 create mode 100644 ReactCommon/fabric/text/basetext/BaseTextShadowNode.h

diff --git a/ReactCommon/fabric/attributedstring/BUCK b/ReactCommon/fabric/attributedstring/BUCK
index 625639db36ef..e6aa5bab5567 100644
--- a/ReactCommon/fabric/attributedstring/BUCK
+++ b/ReactCommon/fabric/attributedstring/BUCK
@@ -1,5 +1,5 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -37,6 +37,7 @@ rn_xplat_cxx_library(
     ],
     force_static = True,
     macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 981dd874f400..4c732efc470e 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -1,5 +1,5 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -40,6 +40,7 @@ rn_xplat_cxx_library(
     ],
     force_static = True,
     macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index 782b7452253f..41fe3bcc5c77 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -1,11 +1,11 @@
-load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
     load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
 
 rn_xplat_cxx_library(
     name = "debug",
@@ -37,6 +37,7 @@ rn_xplat_cxx_library(
     ],
     force_static = True,
     macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
@@ -44,7 +45,10 @@ rn_xplat_cxx_library(
     tests = [],
     visibility = ["PUBLIC"],
     deps = [
+        "xplat//fbsystrace:fbsystrace",
         "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
     ],
 )
 
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index 52a42e39208f..2cd6abacfdf0 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -1,5 +1,5 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -25,10 +25,10 @@ rn_xplat_cxx_library(
         prefix = "fabric/graphics",
     ),
     compiler_flags = [
-        "-std=c++14",
-        "-Wall",
         "-fexceptions",
         "-frtti",
+        "-std=c++14",
+        "-Wall",
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
@@ -36,7 +36,13 @@ rn_xplat_cxx_library(
         ":tests",
     ],
     force_static = True,
+    frameworks = [
+        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
+        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
+        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
+    ],
     macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
     preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
diff --git a/ReactCommon/fabric/text/BUCK b/ReactCommon/fabric/text/BUCK
index 04fbad8d1749..9ee6fca05f03 100644
--- a/ReactCommon/fabric/text/BUCK
+++ b/ReactCommon/fabric/text/BUCK
@@ -21,6 +21,7 @@ rn_xplat_cxx_library(
     exported_headers = subdir_glob(
         [
             ("", "*.h"),
+            ("basetext", "*.h"),
             ("paragraph", "*.h"),
             ("text", "*.h"),
             ("rawtext", "*.h"),
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
new file mode 100644
index 000000000000..4b3e1a80e5ff
--- /dev/null
+++ b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
@@ -0,0 +1,73 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "BaseTextProps.h"
+
+#include <fabric/attributedstring/textValuesConversions.h>
+#include <fabric/core/propsConversions.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/graphics/graphicValuesConversions.h>
+#include <fabric/text/propsConversions.h>
+
+namespace facebook {
+namespace react {
+
+void BaseTextProps::apply(const RawProps &rawProps) {
+  // Color
+  applyRawProp(rawProps, "color", textAttributes_.foregroundColor);
+  applyRawProp(rawProps, "backgroundColor", textAttributes_.backgroundColor);
+  applyRawProp(rawProps, "opacity", textAttributes_.opacity);
+
+  // Font
+  applyRawProp(rawProps, "fontFamily", textAttributes_.fontFamily);
+  applyRawProp(rawProps, "fontSize", textAttributes_.fontSize);
+  applyRawProp(rawProps, "fontSizeMultiplier", textAttributes_.fontSizeMultiplier);
+  applyRawProp(rawProps, "fontWeight", textAttributes_.fontWeight);
+  applyRawProp(rawProps, "fontStyle", textAttributes_.fontStyle);
+  applyRawProp(rawProps, "fontVariant", textAttributes_.fontVariant);
+  applyRawProp(rawProps, "allowFontScaling", textAttributes_.allowFontScaling);
+  applyRawProp(rawProps, "letterSpacing", textAttributes_.letterSpacing);
+
+  // Paragraph
+  applyRawProp(rawProps, "lineHeight", textAttributes_.lineHeight);
+  applyRawProp(rawProps, "alignment", textAttributes_.alignment);
+  applyRawProp(rawProps, "baseWritingDirection", textAttributes_.baseWritingDirection);
+
+  // Decoration
+  applyRawProp(rawProps, "textDecorationColor", textAttributes_.textDecorationColor);
+  applyRawProp(rawProps, "textDecorationLineType", textAttributes_.textDecorationLineType);
+  applyRawProp(rawProps, "textDecorationLineStyle", textAttributes_.textDecorationLineStyle);
+  applyRawProp(rawProps, "textDecorationLinePattern", textAttributes_.textDecorationLinePattern);
+
+  // Shadow
+  applyRawProp(rawProps, "textShadowOffset", textAttributes_.textShadowOffset);
+  applyRawProp(rawProps, "textShadowRadius", textAttributes_.textShadowRadius);
+  applyRawProp(rawProps, "textShadowColor", textAttributes_.textShadowColor);
+
+  // Special
+  applyRawProp(rawProps, "isHighlighted", textAttributes_.isHighlighted);
+}
+
+#pragma mark - Getters
+
+TextAttributes BaseTextProps::getTextAttributes() const {
+  return textAttributes_;
+}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList BaseTextProps::getDebugProps() const {
+  SharedDebugStringConvertibleList list = {};
+
+  auto textAttributesPropsList = textAttributes_.getDebugProps();
+  std::move(textAttributesPropsList.begin(), textAttributesPropsList.end(), std::back_inserter(list));
+
+  return list;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.h b/ReactCommon/fabric/text/basetext/BaseTextProps.h
new file mode 100644
index 000000000000..9d3909a3b354
--- /dev/null
+++ b/ReactCommon/fabric/text/basetext/BaseTextProps.h
@@ -0,0 +1,48 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/attributedstring/TextAttributes.h>
+#include <fabric/core/Props.h>
+#include <fabric/graphics/Color.h>
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * `Props`-like class which is used as a base class for all Props classes
+ * that can have text attributes (such as Text and Paragraph).
+ */
+class BaseTextProps {
+public:
+
+  /*
+   * Same semantic as `Props::apply(...)`.
+   */
+  void apply(const RawProps &rawProps);
+
+#pragma mark - Getters
+
+  /*
+   * Returns all props values as `TextAttributes` object.
+   */
+  TextAttributes getTextAttributes() const;
+
+#pragma mark - DebugStringConvertible (partially)
+
+  SharedDebugStringConvertibleList getDebugProps() const;
+
+private:
+
+  TextAttributes textAttributes_;
+};
+
+} // namespace react
+} // namespace facebook
+
diff --git a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
new file mode 100644
index 000000000000..f37f534b880d
--- /dev/null
+++ b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
@@ -0,0 +1,59 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "BaseTextShadowNode.h"
+
+#include <fabric/debug/DebugStringConvertibleItem.h>
+
+#include "RawTextShadowNode.h"
+#include "RawTextProps.h"
+#include "TextShadowNode.h"
+#include "TextProps.h"
+
+namespace facebook {
+namespace react {
+
+AttributedString BaseTextShadowNode::getAttributedString(
+  const TextAttributes &textAttributes,
+  const SharedShadowNodeSharedList &childNodes
+) const {
+  // TODO: Implement caching.
+
+  AttributedString attributedString;
+
+  for (auto &&childNode : *childNodes) {
+    // RawShadowNode
+    SharedRawTextShadowNode rawTextShadowNode = std::dynamic_pointer_cast<const RawTextShadowNode>(childNode);
+    if (rawTextShadowNode) {
+      AttributedString::Fragment fragment;
+      fragment.string = rawTextShadowNode->getProps()->getText();
+      fragment.textAttributes = textAttributes;
+      attributedString.appendFragment(fragment);
+      continue;
+    }
+
+    // TextShadowNode
+    SharedTextShadowNode textShadowNode = std::dynamic_pointer_cast<const TextShadowNode>(childNode);
+    if (textShadowNode) {
+      TextAttributes localTextAttributes = textAttributes;
+      localTextAttributes.apply(textShadowNode->getProps()->getTextAttributes());
+      attributedString.appendAttributedString(textShadowNode->getAttributedString(localTextAttributes, textShadowNode->getChildren()));
+      continue;
+    }
+
+    // Any other kind of ShadowNode
+    AttributedString::Fragment fragment;
+    fragment.shadowNode = childNode;
+    fragment.textAttributes = textAttributes;
+    attributedString.appendFragment(fragment);
+  }
+
+  return attributedString;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.h b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.h
new file mode 100644
index 000000000000..9d52b9c5ebe9
--- /dev/null
+++ b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.h
@@ -0,0 +1,33 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/attributedstring/AttributedString.h>
+#include <fabric/attributedstring/TextAttributes.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Base class (one of) for shadow nodes that represents attributed text,
+ * such as Text and Paragraph (but not RawText).
+ */
+class BaseTextShadowNode {
+public:
+
+  /*
+   * Returns a `AttributedString` which represents text content of the node.
+   */
+  AttributedString getAttributedString(
+    const TextAttributes &baseTextAttributes,
+    const SharedShadowNodeSharedList &childNodes
+  ) const;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
index 89faa944565a..95be162bb5a7 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
@@ -17,6 +17,7 @@ namespace react {
 
 void ParagraphProps::apply(const RawProps &rawProps) {
   ViewProps::apply(rawProps);
+  BaseTextProps::apply(rawProps);
 
   // Paragraph Attributes
   applyRawProp(rawProps, "numberOfLines", paragraphAttributes_.maximumNumberOfLines);
@@ -44,13 +45,17 @@ bool ParagraphProps::getIsSelectable() const {
 SharedDebugStringConvertibleList ParagraphProps::getDebugProps() const {
   SharedDebugStringConvertibleList list = {};
 
+  // View Props
+  auto &&viewPropsList = ViewProps::getDebugProps();
+  std::move(viewPropsList.begin(), viewPropsList.end(), std::back_inserter(list));
+
   // Paragraph Props
   auto &&paragraphAttributePropsList = paragraphAttributes_.getDebugProps();
   std::move(paragraphAttributePropsList.begin(), paragraphAttributePropsList.end(), std::back_inserter(list));
 
-  // View Props
-  auto &&viewPropsList = ViewProps::getDebugProps();
-  std::move(viewPropsList.begin(), viewPropsList.end(), std::back_inserter(list));
+  // Base Text Props
+  auto &&baseTextPropsList = BaseTextProps::getDebugProps();
+  std::move(baseTextPropsList.begin(), baseTextPropsList.end(), std::back_inserter(list));
 
   return list;
 }
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.h b/ReactCommon/fabric/text/paragraph/ParagraphProps.h
index 42d630f04d0f..4918f47b9787 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.h
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.h
@@ -12,6 +12,7 @@
 
 #include <fabric/attributedstring/ParagraphAttributes.h>
 #include <fabric/core/Props.h>
+#include <fabric/text/BaseTextProps.h>
 #include <fabric/view/ViewProps.h>
 
 namespace facebook {
@@ -27,7 +28,8 @@ using SharedParagraphProps = std::shared_ptr<const ParagraphProps>;
  * object.
  */
 class ParagraphProps:
-  public ViewProps {
+  public ViewProps,
+  public BaseTextProps {
 
 public:
 
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
index 76e90f9b9bca..57d13d7ed66f 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
@@ -17,17 +17,9 @@ namespace react {
 ComponentName ParagraphShadowNode::getComponentName() const {
   return ComponentName("Paragraph");
 }
-  
-SharedTextShadowNode ParagraphShadowNode::getTextChildNode() const {
-  // <Paragraph> component must always have a single <Text> child component.
-  assert(getChildren()->size() == 1);
-  auto childNode = getChildren()->front();
-  assert(std::dynamic_pointer_cast<const TextShadowNode>(childNode));
-  return std::static_pointer_cast<const TextShadowNode>(childNode);
-}
 
 AttributedString ParagraphShadowNode::getAttributedString() const {
-  return getTextChildNode()->getAttributedString(TextAttributes());
+  return BaseTextShadowNode::getAttributedString(getProps()->getTextAttributes(), getChildren());
 }
 
 void ParagraphShadowNode::setTextLayoutManager(SharedTextLayoutManager textLayoutManager) {
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
index 2348d84655d0..df16aee1b797 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
+++ b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
@@ -26,14 +26,10 @@ using SharedParagraphShadowNode = std::shared_ptr<const ParagraphShadowNode>;
  * `ShadowNode` for <Paragraph> component, represents <View>-like component
  * containing and displaying text. Text content is represented as nested <Text>
  * and <RawText> components.
- * Note some Hierarchical constraints:
- *  * <Paragraph> component must have only one <Text> component.
- *  * <Text> component might have nested <Text>, <RawText>, and <View>-like
- *    components.
- *  * <RawText> component must not have any children.
  */
 class ParagraphShadowNode:
-  public ConcreteViewShadowNode<ParagraphProps> {
+  public ConcreteViewShadowNode<ParagraphProps>,
+  public BaseTextShadowNode {
 
 public:
 
@@ -41,11 +37,6 @@ class ParagraphShadowNode:
 
   ComponentName getComponentName() const override;
 
-  /*
-   * Returns a single nested <Text> shadow node.
-   */
-  SharedTextShadowNode getTextChildNode() const;
-
   /*
    * Returns a `AttributedString` which represents text content of the node.
    */
diff --git a/ReactCommon/fabric/text/text/TextProps.cpp b/ReactCommon/fabric/text/text/TextProps.cpp
index 402d2ea67129..c752a5f0ec01 100644
--- a/ReactCommon/fabric/text/text/TextProps.cpp
+++ b/ReactCommon/fabric/text/text/TextProps.cpp
@@ -18,57 +18,13 @@ namespace react {
 
 void TextProps::apply(const RawProps &rawProps) {
   Props::apply(rawProps);
-
-  // Color
-  applyRawProp(rawProps, "color", textAttributes_.foregroundColor);
-  applyRawProp(rawProps, "backgroundColor", textAttributes_.backgroundColor);
-  applyRawProp(rawProps, "opacity", textAttributes_.opacity);
-
-  // Font
-  applyRawProp(rawProps, "fontFamily", textAttributes_.fontFamily);
-  applyRawProp(rawProps, "fontSize", textAttributes_.fontSize);
-  applyRawProp(rawProps, "fontSizeMultiplier", textAttributes_.fontSizeMultiplier);
-  applyRawProp(rawProps, "fontWeight", textAttributes_.fontWeight);
-  applyRawProp(rawProps, "fontStyle", textAttributes_.fontStyle);
-  applyRawProp(rawProps, "fontVariant", textAttributes_.fontVariant);
-  applyRawProp(rawProps, "allowFontScaling", textAttributes_.allowFontScaling);
-  applyRawProp(rawProps, "letterSpacing", textAttributes_.letterSpacing);
-
-  // Paragraph
-  applyRawProp(rawProps, "lineHeight", textAttributes_.lineHeight);
-  applyRawProp(rawProps, "alignment", textAttributes_.alignment);
-  applyRawProp(rawProps, "baseWritingDirection", textAttributes_.baseWritingDirection);
-
-  // Decoration
-  applyRawProp(rawProps, "textDecorationColor", textAttributes_.textDecorationColor);
-  applyRawProp(rawProps, "textDecorationLineType", textAttributes_.textDecorationLineType);
-  applyRawProp(rawProps, "textDecorationLineStyle", textAttributes_.textDecorationLineStyle);
-  applyRawProp(rawProps, "textDecorationLinePattern", textAttributes_.textDecorationLinePattern);
-
-  // Shadow
-  applyRawProp(rawProps, "textShadowOffset", textAttributes_.textShadowOffset);
-  applyRawProp(rawProps, "textShadowRadius", textAttributes_.textShadowRadius);
-  applyRawProp(rawProps, "textShadowColor", textAttributes_.textShadowColor);
-
-  // Special
-  applyRawProp(rawProps, "isHighlighted", textAttributes_.isHighlighted);
-}
-
-#pragma mark - Getters
-
-TextAttributes TextProps::getTextAttributes() const {
-  return textAttributes_;
+  BaseTextProps::apply(rawProps);
 }
 
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList TextProps::getDebugProps() const {
-  SharedDebugStringConvertibleList list = {};
-
-  auto textAttributesPropsList = textAttributes_.getDebugProps();
-  std::move(textAttributesPropsList.begin(), textAttributesPropsList.end(), std::back_inserter(list));
-
-  return list;
+  return BaseTextProps::getDebugProps();
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/text/text/TextProps.h b/ReactCommon/fabric/text/text/TextProps.h
index 1a96b5519fb8..8762642bb02e 100644
--- a/ReactCommon/fabric/text/text/TextProps.h
+++ b/ReactCommon/fabric/text/text/TextProps.h
@@ -11,6 +11,7 @@
 #include <fabric/core/Props.h>
 #include <fabric/graphics/Color.h>
 #include <fabric/graphics/Geometry.h>
+#include <fabric/text/BaseTextProps.h>
 
 namespace facebook {
 namespace react {
@@ -20,22 +21,12 @@ class TextProps;
 using SharedTextProps = std::shared_ptr<const TextProps>;
 
 class TextProps:
-  public Props {
+  public Props,
+  public BaseTextProps {
 
 public:
   void apply(const RawProps &rawProps) override;
 
-#pragma mark - Getters
-
-  TextAttributes getTextAttributes() const;
-
-private:
-
-  /*
-   * Not all `TextAttributes` fields make sense and is used as TextProps values.
-   */
-  TextAttributes textAttributes_;
-
 #pragma mark - DebugStringConvertible
 
   SharedDebugStringConvertibleList getDebugProps() const override;
@@ -43,4 +34,3 @@ class TextProps:
 
 } // namespace react
 } // namespace facebook
-
diff --git a/ReactCommon/fabric/text/text/TextShadowNode.cpp b/ReactCommon/fabric/text/text/TextShadowNode.cpp
index 5429c7ba6063..c49c8bfd243c 100644
--- a/ReactCommon/fabric/text/text/TextShadowNode.cpp
+++ b/ReactCommon/fabric/text/text/TextShadowNode.cpp
@@ -9,9 +9,6 @@
 
 #include <fabric/debug/DebugStringConvertibleItem.h>
 
-#include "RawTextShadowNode.h"
-#include "RawTextProps.h"
-
 namespace facebook {
 namespace react {
 
@@ -19,41 +16,5 @@ ComponentName TextShadowNode::getComponentName() const {
   return ComponentName("Text");
 }
 
-AttributedString TextShadowNode::getAttributedString(const TextAttributes &baseTextAttributes) const {
-  // TODO: Implement caching.
-
-  TextAttributes textAttributes = baseTextAttributes;
-  textAttributes.apply(getProps()->getTextAttributes());
-
-  AttributedString attributedString;
-
-  for (auto &&childNode : *getChildren()) {
-    // RawShadowNode
-    SharedRawTextShadowNode rawTextShadowNode = std::dynamic_pointer_cast<const RawTextShadowNode>(childNode);
-    if (rawTextShadowNode) {
-      AttributedString::Fragment fragment;
-      fragment.string = rawTextShadowNode->getProps()->getText();
-      fragment.textAttributes = textAttributes;
-      attributedString.appendFragment(fragment);
-      continue;
-    }
-
-    // TextShadowNode
-    SharedTextShadowNode textShadowNode = std::dynamic_pointer_cast<const TextShadowNode>(childNode);
-    if (textShadowNode) {
-      attributedString.appendAttributedString(textShadowNode->getAttributedString(textAttributes));
-      continue;
-    }
-
-    // Any other kind of ShadowNode
-    AttributedString::Fragment fragment;
-    fragment.shadowNode = childNode;
-    fragment.textAttributes = textAttributes;
-    attributedString.appendFragment(fragment);
-  }
-
-  return attributedString;
-}
-
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/text/text/TextShadowNode.h b/ReactCommon/fabric/text/text/TextShadowNode.h
index 0eb421a96630..12c73e1a17e3 100644
--- a/ReactCommon/fabric/text/text/TextShadowNode.h
+++ b/ReactCommon/fabric/text/text/TextShadowNode.h
@@ -11,6 +11,7 @@
 #include <fabric/attributedstring/TextAttributes.h>
 #include <fabric/core/ConcreteShadowNode.h>
 #include <fabric/core/ShadowNode.h>
+#include <fabric/text/BaseTextShadowNode.h>
 #include <fabric/text/TextProps.h>
 #include <fabric/text/TextShadowNode.h>
 
@@ -22,18 +23,14 @@ class TextShadowNode;
 using SharedTextShadowNode = std::shared_ptr<const TextShadowNode>;
 
 class TextShadowNode:
-  public ConcreteShadowNode<TextProps> {
+  public ConcreteShadowNode<TextProps>,
+  public BaseTextShadowNode {
 
 public:
 
   using ConcreteShadowNode::ConcreteShadowNode;
 
   ComponentName getComponentName() const override;
-
-  /*
-   * Returns a `AttributedString` which represents text content of the node.
-   */
-  AttributedString getAttributedString(const TextAttributes &baseTextAttributes) const;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/textlayoutmanager/BUCK b/ReactCommon/fabric/textlayoutmanager/BUCK
index c7bb2f92ec06..be8ed19c2885 100644
--- a/ReactCommon/fabric/textlayoutmanager/BUCK
+++ b/ReactCommon/fabric/textlayoutmanager/BUCK
@@ -1,5 +1,5 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags", "get_fbobjc_enable_exception_lang_compiler_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
 
 APPLE_COMPILER_FLAGS = []
 
@@ -39,14 +39,14 @@ rn_xplat_cxx_library(
         ":tests",
     ],
     force_static = True,
-    macosx_tests_override = [],
     frameworks = [
+        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
         "$SDKROOT/System/Library/Frameworks/Foundation.framework",
-        "$SDKROOT/System/Library/Frameworks/QuartzCore.framework",
         "$SDKROOT/System/Library/Frameworks/UIKit.framework",
     ],
-    lang_compiler_flags = get_fbobjc_enable_exception_lang_compiler_flags(),
-    preprocessor_flags = get_debug_preprocessor_flags() + [
+    macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
+    preprocessor_flags = [
         "-DLOG_TAG=\"ReactNative\"",
         "-DWITH_FBSYSTRACE=1",
     ],
@@ -58,6 +58,7 @@ rn_xplat_cxx_library(
         "xplat//folly:memory",
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
         react_native_xplat_target("fabric/attributedstring:attributedstring"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/debug:debug"),
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 20b7108c25c7..221ea2c10555 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -53,15 +53,15 @@ rn_xplat_cxx_library(
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
         "xplat//yoga:yoga",
-        react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/graphics:graphics"),
     ],
 )
 
 if not IS_OSS_BUILD:
     load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-    
+
     fb_xplat_cxx_test(
         name = "tests",
         srcs = glob(["tests/**/*.cpp"]),

From 6e537b000bb4778759879dc922acf6bcb28c28df Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:02 -0700
Subject: [PATCH 0466/1109] Fabric: New nice way to deal with
 DebugStringConvertible items

Summary:
No macros in product code.
(Not all callsites are converted yet.)

Reviewed By: mdvacca

Differential Revision: D7797561

fbshipit-source-id: da899421bf99669a0e0a2b83df6004daf14355c2
---
 .../attributedstring/ParagraphAttributes.cpp  | 24 +++-----
 .../attributedstring/TextAttributes.cpp       | 57 ++++++++++++-------
 .../debugStringConvertibleUtils.h             | 21 +++++++
 .../attributedstring/textValuesConversions.h  | 12 ++++
 .../fabric/debug/DebugStringConvertible.cpp   |  8 +++
 .../debug/debugStringConvertibleUtils.cpp     | 25 ++++++++
 .../debug/debugStringConvertibleUtils.h       | 53 +++++++++++++++++
 .../graphics/debugStringConvertibleUtils.h    | 22 +++++++
 .../fabric/text/basetext/BaseTextProps.cpp    |  7 +--
 .../text/paragraph/ParagraphLocalData.cpp     |  8 +--
 .../fabric/text/paragraph/ParagraphProps.cpp  | 21 ++-----
 11 files changed, 198 insertions(+), 60 deletions(-)
 create mode 100644 ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
 create mode 100644 ReactCommon/fabric/debug/debugStringConvertibleUtils.cpp
 create mode 100644 ReactCommon/fabric/debug/debugStringConvertibleUtils.h
 create mode 100644 ReactCommon/fabric/graphics/debugStringConvertibleUtils.h

diff --git a/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp b/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
index 3901c18cf38b..43d895e7608c 100644
--- a/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
@@ -10,27 +10,21 @@
 #include <fabric/attributedstring/textValuesConversions.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
 
+#include "debugStringConvertibleUtils.h"
+
 namespace facebook {
 namespace react {
 
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList ParagraphAttributes::getDebugProps() const {
-  ParagraphAttributes defaultParagraphAttributes = {};
-  SharedDebugStringConvertibleList list = {};
-
-#define PARAGRAPH_ATTRIBUTE(stringName, propertyName, accessor, convertor) \
-  if (propertyName != defaultParagraphAttributes.propertyName) { \
-    list.push_back(std::make_shared<DebugStringConvertibleItem>(#stringName, convertor(propertyName accessor))); \
-  }
-
-  PARAGRAPH_ATTRIBUTE(maximumNumberOfLines, maximumNumberOfLines, , std::to_string)
-  PARAGRAPH_ATTRIBUTE(ellipsizeMode, ellipsizeMode, , stringFromEllipsizeMode)
-  PARAGRAPH_ATTRIBUTE(adjustsFontSizeToFit, adjustsFontSizeToFit, , std::to_string)
-  PARAGRAPH_ATTRIBUTE(minimumFontSize, minimumFontSize, , std::to_string)
-  PARAGRAPH_ATTRIBUTE(maximumFontSize, maximumFontSize, , std::to_string)
-
-  return list;
+  return {
+    debugStringConvertibleItem("maximumNumberOfLines", maximumNumberOfLines),
+    debugStringConvertibleItem("ellipsizeMode", ellipsizeMode),
+    debugStringConvertibleItem("adjustsFontSizeToFit", adjustsFontSizeToFit),
+    debugStringConvertibleItem("minimumFontSize", minimumFontSize),
+    debugStringConvertibleItem("maximumFontSize", maximumFontSize)
+  };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.cpp b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
index 984aba5d377f..4f85297dc713 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
@@ -7,8 +7,9 @@
 
 #include "TextAttributes.h"
 
-#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/graphics/debugStringConvertibleUtils.h>
 #include <fabric/graphics/graphicValuesConversions.h>
+#include "debugStringConvertibleUtils.h"
 
 namespace facebook {
 namespace react {
@@ -53,26 +54,44 @@ void TextAttributes::apply(TextAttributes textAttributes) {
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList TextAttributes::getDebugProps() const {
-  TextAttributes defaultAttributes = {};
-
-  SharedDebugStringConvertibleList list = {};
-
-#define PROPS_ADD_TO_SET(propertyName, accessor, convertor) \
-  if (propertyName != defaultAttributes.propertyName) { \
-    list.push_back(std::make_shared<DebugStringConvertibleItem>(#propertyName, convertor(propertyName accessor))); \
-  }
-
-  PROPS_ADD_TO_SET(backgroundColor, , colorNameFromColor)
-  PROPS_ADD_TO_SET(foregroundColor, , colorNameFromColor)
-  PROPS_ADD_TO_SET(opacity, , std::to_string)
-
-  PROPS_ADD_TO_SET(fontFamily, , )
-  PROPS_ADD_TO_SET(fontSize, , std::to_string)
-  PROPS_ADD_TO_SET(fontSizeMultiplier, , std::to_string)
-
   // TODO: Implement all fields.
 
-  return list;
+  return {
+    // Color
+    debugStringConvertibleItem("backgroundColor", backgroundColor),
+    debugStringConvertibleItem("foregroundColor", foregroundColor),
+    debugStringConvertibleItem("opacity", opacity),
+
+    // Font
+    debugStringConvertibleItem("fontFamily", fontFamily),
+    debugStringConvertibleItem("fontSize", fontSize),
+    debugStringConvertibleItem("fontSizeMultiplier", fontSizeMultiplier),
+    debugStringConvertibleItem("fontWeight", fontWeight),
+    debugStringConvertibleItem("fontStyle", fontStyle),
+    //debugStringConvertibleItem("fontVariant", fontVariant),
+    debugStringConvertibleItem("allowFontScaling", allowFontScaling),
+    debugStringConvertibleItem("letterSpacing", letterSpacing),
+
+    // Paragraph Styles
+    debugStringConvertibleItem("lineHeight", lineHeight),
+    //debugStringConvertibleItem("alignment", alignment),
+    //debugStringConvertibleItem("baseWritingDirection", baseWritingDirection),
+
+    // Decoration
+    debugStringConvertibleItem("textDecorationColor", textDecorationColor),
+    //debugStringConvertibleItem("textDecorationLineType", textDecorationLineType),
+    //debugStringConvertibleItem("textDecorationLineStyle", textDecorationLineStyle),
+    //debugStringConvertibleItem("textDecorationLinePattern", textDecorationLinePattern),
+
+    // Shadow
+    debugStringConvertibleItem("textShadowOffset", textShadowOffset),
+    debugStringConvertibleItem("textShadowRadius", textShadowRadius),
+    debugStringConvertibleItem("textShadowColor", textShadowColor),
+
+    // Special
+    debugStringConvertibleItem("isHighlighted", isHighlighted),
+    //debugStringConvertibleItem("layoutDirection", layoutDirection),
+  };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h b/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
new file mode 100644
index 000000000000..617efb4c19cd
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/debug/debugStringConvertibleUtils.h>
+#include <fabric/attributedstring/textValuesConversions.h>
+
+namespace facebook {
+namespace react {
+
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(EllipsizeMode, stringFromEllipsizeMode)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(FontWeight, stringFromFontWeight)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(FontStyle, stringFromFontStyle)
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/attributedstring/textValuesConversions.h b/ReactCommon/fabric/attributedstring/textValuesConversions.h
index 88480b6ff2e5..deb5660e2f76 100644
--- a/ReactCommon/fabric/attributedstring/textValuesConversions.h
+++ b/ReactCommon/fabric/attributedstring/textValuesConversions.h
@@ -49,6 +49,10 @@ inline FontWeight fontWeightFromDynamic(const folly::dynamic &value) {
   abort();
 }
 
+inline std::string stringFromFontWeight(const FontWeight &fontWeight) {
+  return std::to_string((int)fontWeight);
+}
+
 inline FontStyle fontStyleFromDynamic(const folly::dynamic &value) {
   auto string = value.asString();
   if (string == "normal") { return FontStyle::Normal; }
@@ -57,6 +61,14 @@ inline FontStyle fontStyleFromDynamic(const folly::dynamic &value) {
   abort();
 }
 
+inline std::string stringFromFontStyle(const FontStyle &fontStyle) {
+  switch (fontStyle) {
+    case FontStyle::Normal: return "normal";
+    case FontStyle::Italic: return "italic";
+    case FontStyle::Oblique: return "oblique";
+  }
+}
+
 inline FontVariant fontVariantFromDynamic(const folly::dynamic &value) {
   assert(value.isArray());
   FontVariant fontVariant = FontVariant::Default;
diff --git a/ReactCommon/fabric/debug/DebugStringConvertible.cpp b/ReactCommon/fabric/debug/DebugStringConvertible.cpp
index ce2c91611af9..08d885d96746 100644
--- a/ReactCommon/fabric/debug/DebugStringConvertible.cpp
+++ b/ReactCommon/fabric/debug/DebugStringConvertible.cpp
@@ -18,6 +18,10 @@ std::string DebugStringConvertible::getDebugChildrenDescription(DebugStringConve
   std::string childrenString = "";
 
   for (auto child : getDebugChildren()) {
+    if (!child) {
+      continue;
+    }
+
     childrenString += child->getDebugDescription(options, depth + 1);
   }
 
@@ -32,6 +36,10 @@ std::string DebugStringConvertible::getDebugPropsDescription(DebugStringConverti
   std::string propsString = "";
 
   for (auto prop : getDebugProps()) {
+    if (!prop) {
+      continue;
+    }
+
     auto name = prop->getDebugName();
     auto value = prop->getDebugValue();
     auto children = prop->getDebugPropsDescription(options, depth + 1);
diff --git a/ReactCommon/fabric/debug/debugStringConvertibleUtils.cpp b/ReactCommon/fabric/debug/debugStringConvertibleUtils.cpp
new file mode 100644
index 000000000000..de9817d4999f
--- /dev/null
+++ b/ReactCommon/fabric/debug/debugStringConvertibleUtils.cpp
@@ -0,0 +1,25 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "debugStringConvertibleUtils.h"
+
+namespace facebook {
+namespace react {
+
+SharedDebugStringConvertibleList operator+(const SharedDebugStringConvertibleList &lhs, const SharedDebugStringConvertibleList &rhs) {
+  SharedDebugStringConvertibleList result = {};
+  std::move(lhs.begin(), lhs.end(), std::back_inserter(result));
+  std::move(rhs.begin(), rhs.end(), std::back_inserter(result));
+  return result;
+}
+
+SharedDebugStringConvertible debugStringConvertibleItem(std::string name, DebugStringConvertible value, std::string defaultValue) {
+  return debugStringConvertibleItem(name, value.getDebugDescription(), defaultValue);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
new file mode 100644
index 000000000000..d6be81b3c6be
--- /dev/null
+++ b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
@@ -0,0 +1,53 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <string>
+#include <limits>
+#include <memory>
+#include <vector>
+
+#include <fabric/debug/DebugStringConvertible.h>
+#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <folly/Conv.h>
+
+namespace facebook {
+namespace react {
+
+SharedDebugStringConvertibleList operator+(const SharedDebugStringConvertibleList &lhs, const SharedDebugStringConvertibleList &rhs);
+SharedDebugStringConvertible debugStringConvertibleItem(std::string name, DebugStringConvertible value, std::string defaultValue = "");
+
+#define IS_EQUAL(a, b) ((a) == (b))
+#define IS_EQUAL_FLOAT(a, b) ((isnan(a) == isnan(b)) || ((a) == (b)))
+
+#define DEBUG_STRING_CONVERTIBLE_TEMPLATE(type, converter) \
+DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(type, converter, {}, IS_EQUAL)
+
+#define DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(type, converter, defaults, comparator) \
+inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, type value, type defaultValue = defaults) { \
+  if (comparator(value, defaultValue)) { \
+    return nullptr; \
+  } \
+  return std::make_shared<DebugStringConvertibleItem>(name, converter(value)); \
+} \
+\
+inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, folly::Optional<type> value, type defaultValue = defaults) { \
+  if (value.has_value()) { \
+    return nullptr; \
+  } \
+  return debugStringConvertibleItem(name, value.value_or(defaultValue), defaultValue); \
+}
+
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(std::string, )
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(int, folly::to<std::string>)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(bool, folly::to<std::string>)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(float, folly::to<std::string>, std::numeric_limits<float>::quiet_NaN(), IS_EQUAL_FLOAT)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(double, folly::to<std::string>, std::numeric_limits<float>::quiet_NaN(), IS_EQUAL_FLOAT)
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/debugStringConvertibleUtils.h b/ReactCommon/fabric/graphics/debugStringConvertibleUtils.h
new file mode 100644
index 000000000000..d67dd14cce13
--- /dev/null
+++ b/ReactCommon/fabric/graphics/debugStringConvertibleUtils.h
@@ -0,0 +1,22 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/debug/debugStringConvertibleUtils.h>
+#include <fabric/graphics/graphicValuesConversions.h>
+
+namespace facebook {
+namespace react {
+
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(Point, stringFromPoint)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(Size, stringFromSize)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(Rect, stringFromRect)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(SharedColor, colorNameFromColor)
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
index 4b3e1a80e5ff..5b03c924d5eb 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
+++ b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
@@ -61,12 +61,7 @@ TextAttributes BaseTextProps::getTextAttributes() const {
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList BaseTextProps::getDebugProps() const {
-  SharedDebugStringConvertibleList list = {};
-
-  auto textAttributesPropsList = textAttributes_.getDebugProps();
-  std::move(textAttributesPropsList.begin(), textAttributesPropsList.end(), std::back_inserter(list));
-
-  return list;
+  return textAttributes_.getDebugProps();
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
index 0390313b689c..0064ee862e7f 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
@@ -7,7 +7,7 @@
 
 #include "ParagraphLocalData.h"
 
-#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
 
 namespace facebook {
 namespace react {
@@ -37,9 +37,9 @@ std::string ParagraphLocalData::getDebugName() const {
 }
 
 SharedDebugStringConvertibleList ParagraphLocalData::getDebugProps() const {
-  SharedDebugStringConvertibleList list = {};
-  list.push_back(std::make_shared<DebugStringConvertibleItem>("attributedString", attributedString_.getDebugDescription()));
-  return list;
+  return {
+    debugStringConvertibleItem("attributedString", attributedString_)
+  };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
index 95be162bb5a7..a4481e138366 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
@@ -9,7 +9,7 @@
 
 #include <fabric/attributedstring/textValuesConversions.h>
 #include <fabric/core/propsConversions.h>
-#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
 #include <fabric/text/propsConversions.h>
 
 namespace facebook {
@@ -43,21 +43,10 @@ bool ParagraphProps::getIsSelectable() const {
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList ParagraphProps::getDebugProps() const {
-  SharedDebugStringConvertibleList list = {};
-
-  // View Props
-  auto &&viewPropsList = ViewProps::getDebugProps();
-  std::move(viewPropsList.begin(), viewPropsList.end(), std::back_inserter(list));
-
-  // Paragraph Props
-  auto &&paragraphAttributePropsList = paragraphAttributes_.getDebugProps();
-  std::move(paragraphAttributePropsList.begin(), paragraphAttributePropsList.end(), std::back_inserter(list));
-
-  // Base Text Props
-  auto &&baseTextPropsList = BaseTextProps::getDebugProps();
-  std::move(baseTextPropsList.begin(), baseTextPropsList.end(), std::back_inserter(list));
-
-  return list;
+  return
+    ViewProps::getDebugProps() +
+    paragraphAttributes_.getDebugProps() +
+    BaseTextProps::getDebugProps();
 }
 
 } // namespace react

From 7cf7028092bcb4f3c0fc391893c2682523abc6e3 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:04 -0700
Subject: [PATCH 0467/1109] Fabric: Support for view recycling in
 RCTComponentViewRegistry
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary: Quite trivial but still very cool recycling of native view instances is finnally here, in React Native. �

Reviewed By: mdvacca

Differential Revision: D7804085

fbshipit-source-id: 644804da3185f9ed3fdea42d4d76c93e86934448
---
 .../Mounting/RCTComponentViewRegistry.mm      | 53 +++++++++++++++++--
 React/Fabric/Mounting/RCTViewComponentView.h  |  2 +
 React/Fabric/Mounting/RCTViewComponentView.mm |  3 +-
 3 files changed, 54 insertions(+), 4 deletions(-)

diff --git a/React/Fabric/Mounting/RCTComponentViewRegistry.mm b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
index c9d8224007e4..83b0afb85a9d 100644
--- a/React/Fabric/Mounting/RCTComponentViewRegistry.mm
+++ b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
@@ -10,8 +10,11 @@
 #import <Foundation/NSMapTable.h>
 #import <React/RCTAssert.h>
 
+const NSInteger RCTComponentViewRegistryRecyclePoolMaxSize = 256;
+
 @implementation RCTComponentViewRegistry {
   NSMapTable<id, UIView<RCTComponentViewProtocol> *> *_registry;
+  NSMapTable<NSString *, NSHashTable<UIView<RCTComponentViewProtocol> *> *> *_recyclePool;
 }
 
 - (instancetype)init
@@ -19,6 +22,8 @@ - (instancetype)init
   if (self = [super init]) {
     _registry = [NSMapTable mapTableWithKeyOptions:NSPointerFunctionsIntegerPersonality | NSPointerFunctionsOpaqueMemory
                                       valueOptions:NSPointerFunctionsObjectPersonality];
+    _recyclePool = [NSMapTable mapTableWithKeyOptions:NSPointerFunctionsObjectPersonality
+                                         valueOptions:NSPointerFunctionsObjectPersonality];
   }
 
   return self;
@@ -28,9 +33,8 @@ - (instancetype)init
                                                                tag:(ReactTag)tag
 {
   RCTAssertMainQueue();
-  // This is temporary approach.
-  NSString *className = [NSString stringWithFormat:@"RCT%@ComponentView", componentName];
-  UIView<RCTComponentViewProtocol> *componentView = [[NSClassFromString(className) alloc] init];
+  UIView<RCTComponentViewProtocol> *componentView =
+    [self _dequeueComponentViewWithName:componentName];
   componentView.tag = tag;
   [_registry setObject:componentView forKey:(__bridge id)(void *)tag];
   return componentView;
@@ -42,6 +46,8 @@ - (void)enqueueComponentViewWithName:(NSString *)componentName
 {
   RCTAssertMainQueue();
   [_registry removeObjectForKey:(__bridge id)(void *)tag];
+  componentView.tag = 0;
+  [self _enqueueComponentViewWithName:componentName componentView:componentView];
 }
 
 - (UIView<RCTComponentViewProtocol> *)componentViewByTag:(ReactTag)tag
@@ -56,4 +62,45 @@ - (ReactTag)tagByComponentView:(UIView<RCTComponentViewProtocol> *)componentView
   return componentView.tag;
 }
 
+- (UIView<RCTComponentViewProtocol> *)_createComponentViewWithName:(NSString *)componentName
+{
+  RCTAssertMainQueue();
+  // This is temporary approach.
+  NSString *className = [NSString stringWithFormat:@"RCT%@ComponentView", componentName];
+  UIView<RCTComponentViewProtocol> *componentView = [[NSClassFromString(className) alloc] init];
+  return componentView;
+}
+
+- (nullable UIView<RCTComponentViewProtocol> *)_dequeueComponentViewWithName:(NSString *)componentName
+{
+  RCTAssertMainQueue();
+  NSHashTable<UIView<RCTComponentViewProtocol> *> *componentViews = [_recyclePool objectForKey:componentName];
+  if (!componentViews || componentViews.count == 0) {
+    return [self _createComponentViewWithName:componentName];
+  }
+
+  UIView<RCTComponentViewProtocol> *componentView = [componentViews anyObject];
+  [componentViews removeObject:componentView];
+  return componentView;
+}
+
+- (void)_enqueueComponentViewWithName:(NSString *)componentName
+                        componentView:(UIView<RCTComponentViewProtocol> *)componentView
+{
+  RCTAssertMainQueue();
+  [componentView prepareForRecycle];
+
+  NSHashTable<UIView<RCTComponentViewProtocol> *> *componentViews = [_recyclePool objectForKey:componentName];
+  if (!componentViews) {
+    componentViews = [NSHashTable hashTableWithOptions:NSPointerFunctionsObjectPersonality];
+    [_recyclePool setObject:componentViews forKey:componentName];
+  }
+
+  if (componentViews.count >= RCTComponentViewRegistryRecyclePoolMaxSize) {
+    return;
+  }
+
+  [componentViews addObject:componentView];
+}
+
 @end
diff --git a/React/Fabric/Mounting/RCTViewComponentView.h b/React/Fabric/Mounting/RCTViewComponentView.h
index 8dc5fc2e12df..8ae84d138f50 100644
--- a/React/Fabric/Mounting/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/RCTViewComponentView.h
@@ -10,6 +10,7 @@
 #import <React/RCTComponentViewProtocol.h>
 #import <React/UIView+ComponentViewProtocol.h>
 #import <fabric/core/LayoutMetrics.h>
+#import <fabric/core/Props.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
@@ -19,6 +20,7 @@ NS_ASSUME_NONNULL_BEGIN
 @interface RCTViewComponentView : UIView <RCTComponentViewProtocol> {
 @protected
   facebook::react::LayoutMetrics _layoutMetrics;
+  facebook::react::SharedProps _props;
 }
 
 @end
diff --git a/React/Fabric/Mounting/RCTViewComponentView.mm b/React/Fabric/Mounting/RCTViewComponentView.mm
index cc3c0772bd75..26fff3a50a62 100644
--- a/React/Fabric/Mounting/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/RCTViewComponentView.mm
@@ -17,8 +17,9 @@ - (void)updateProps:(facebook::react::SharedProps)props
            oldProps:(facebook::react::SharedProps)oldProps
 {
   if (!oldProps) {
-    oldProps = std::make_shared<ViewProps>();
+    oldProps = _props ?: std::make_shared<ViewProps>();
   }
+  _props = props;
 
   auto oldViewProps = *std::dynamic_pointer_cast<const ViewProps>(oldProps);
   auto newViewProps = *std::dynamic_pointer_cast<const ViewProps>(props);

From e028631513e535898834dc4e5e6d089bb37fda79 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:07 -0700
Subject: [PATCH 0468/1109] Fabric: Implementation of `yogaStyleValueFromFloat`

Summary: Quite obvious.

Reviewed By: mdvacca

Differential Revision: D7857047

fbshipit-source-id: 876664b3ab5c19b7c66a38579664f18a38a1a371
---
 ReactCommon/fabric/view/yoga/YogaStylableProps.h    |  4 ++--
 .../fabric/view/yoga/yogaValuesConversions.cpp      | 13 ++++++++++---
 .../fabric/view/yoga/yogaValuesConversions.h        |  2 ++
 3 files changed, 14 insertions(+), 5 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.h b/ReactCommon/fabric/view/yoga/YogaStylableProps.h
index 61d935a22f27..14f721c0594b 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.h
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.h
@@ -20,8 +20,8 @@ class YogaStylableProps;
 typedef std::shared_ptr<const YogaStylableProps> SharedYogaStylableProps;
 
 class YogaStylableProps:
-  public virtual DebugStringConvertible
-{
+  public virtual DebugStringConvertible {
+
 public:
   const YGStyle &getYogaStyle() const;
 
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
index f13744de7577..328ea9f18332 100644
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
@@ -46,6 +46,14 @@ YGFloatOptional yogaOptionalFloatFromFabricFloat(Float value) {
   return YGFloatOptional(yogaFloatFromFabricFloat(value));
 }
 
+YGValue yogaStyleValueFromFloat(const Float &value) {
+  if (isnan(value) || value == kFloatUndefined) {
+    return YGValueUndefined;
+  }
+
+  return {(float)value, YGUnitPoint};
+}
+
 LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode) {
   LayoutMetrics layoutMetrics;
 
@@ -182,12 +190,11 @@ YGDisplay yogaStyleDisplayFromDynamic(const folly::dynamic &value) {
 
 YGValue yogaStyleValueFromDynamic(const folly::dynamic &value) {
   if (value.isNumber()) {
-    float x = value.asDouble();
-    return { x, YGUnitPoint };
+    return yogaStyleValueFromFloat(value.asDouble());
   } else if (value.isString()) {
     const auto stringValue = value.asString();
     if (stringValue == "auto") {
-      return { YGUndefined, YGUnitAuto };
+      return YGValueUndefined;
     } else {
       if (stringValue.back() == '%') {
         return { folly::to<float>(stringValue.substr(stringValue.length() - 1)), YGUnitPercent };
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.h b/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
index 6c5156598300..6837f9e10b32 100644
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
@@ -24,6 +24,8 @@ float yogaFloatFromFabricFloat(Float value);
 Float fabricFloatFromYogaOptionalFloat(YGFloatOptional value);
 YGFloatOptional yogaOptionalFloatFromFabricFloat(Float value);
 
+YGValue yogaStyleValueFromFloat(const Float &value);
+
 LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode);
 
 YGDirection yogaStyleDirectionFromDynamic(const folly::dynamic &value);

From cb48fa4d494e7352e11d23cf60fcf23884345564 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:10 -0700
Subject: [PATCH 0469/1109] Fabric: `LayoutContext::affectedShadowNodes` was
 removed

Summary:
Apparently, we don't need this functionality in Fabric because we compute mutation instactions during diffing anyways.
But we still need (will need) `LayoutContext` for sure.

Reviewed By: mdvacca

Differential Revision: D7857045

fbshipit-source-id: 4be2744d9abea473ead847f35f698104f94af33d
---
 ReactCommon/fabric/core/layout/LayoutContext.h            | 6 ------
 ReactCommon/fabric/uimanager/Scheduler.cpp                | 1 -
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 5 +----
 3 files changed, 1 insertion(+), 11 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutContext.h b/ReactCommon/fabric/core/layout/LayoutContext.h
index 6f8d49ff4a18..1046fd00147f 100644
--- a/ReactCommon/fabric/core/layout/LayoutContext.h
+++ b/ReactCommon/fabric/core/layout/LayoutContext.h
@@ -24,12 +24,6 @@ struct LayoutContext {
    * Compound absolute position of the node relative to the root node.
    */
   Point absolutePosition {0, 0};
-
-  /*
-   * Collection of shadow nodes which were chanded during the layout pass,
-   * and which associated views might need to be updated.
-   */
-  std::shared_ptr<std::unordered_set<SharedLayoutableShadowNode>> affectedShadowNodes {nullptr};
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index 8b5038c31f7c..6ad2f45f0080 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -65,7 +65,6 @@ void Scheduler::uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNod
   auto nonConstNewRootShadowNode = std::const_pointer_cast<RootShadowNode>(newRootShadowNode);
 
   LayoutContext layoutContext = LayoutContext();
-  layoutContext.affectedShadowNodes = std::make_shared<std::unordered_set<SharedLayoutableShadowNode>>();
 
   LOG(INFO) << "Old Shadow Tree: \n" << oldRootShadowNode->getDebugDescription();
   LOG(INFO) << "New Shadow Tree *before* layout: \n" << newRootShadowNode->getDebugDescription();
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index d91def613c2d..bce88ce68ada 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -130,10 +130,7 @@ void YogaLayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
     auto nonConstYogaLayoutableChild = std::const_pointer_cast<YogaLayoutableShadowNode>(yogaLayoutableChild);
 
     LayoutMetrics childLayoutMetrics = layoutMetricsFromYogaNode(*nonConstYogaLayoutableChild->yogaNode_);
-    bool isAffected = nonConstYogaLayoutableChild->setLayoutMetrics(childLayoutMetrics);
-    if (isAffected) {
-      layoutContext.affectedShadowNodes->insert(child);
-    }
+    nonConstYogaLayoutableChild->setLayoutMetrics(childLayoutMetrics);
   }
 }
 

From 2bb41031baaec7ca9fe97e8574407209db2c229e Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:14 -0700
Subject: [PATCH 0470/1109] Fabric: Introducing `RootShadowNode`

Summary: `RootShadowNode` is a dedicated class for managing the root node.

Reviewed By: mdvacca

Differential Revision: D7857050

fbshipit-source-id: f15f4b177f03cea4c0fd5a60d761ee2745319d77
---
 .../core/shadownode/ConcreteShadowNode.h      |  1 -
 ReactCommon/fabric/uimanager/Scheduler.h      |  7 +--
 ReactCommon/fabric/view/BUCK                  |  1 +
 ReactCommon/fabric/view/root/RootProps.cpp    | 45 +++++++++++++++++
 ReactCommon/fabric/view/root/RootProps.h      | 44 ++++++++++++++++
 .../fabric/view/root/RootShadowNode.cpp       | 23 +++++++++
 ReactCommon/fabric/view/root/RootShadowNode.h | 50 +++++++++++++++++++
 7 files changed, 164 insertions(+), 7 deletions(-)
 create mode 100644 ReactCommon/fabric/view/root/RootProps.cpp
 create mode 100644 ReactCommon/fabric/view/root/RootProps.h
 create mode 100644 ReactCommon/fabric/view/root/RootShadowNode.cpp
 create mode 100644 ReactCommon/fabric/view/root/RootShadowNode.h

diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index aca5fc32bea8..06a1afa7c989 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -81,7 +81,6 @@ class ConcreteShadowNode: public ShadowNode {
 
   const SharedConcreteProps getProps() const {
     assert(std::dynamic_pointer_cast<const PropsT>(props_));
-
     return std::static_pointer_cast<const PropsT>(props_);
   }
 
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index b48d6e848af4..5082f9bb6095 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -9,16 +9,11 @@
 #include <fabric/uimanager/SchedulerDelegate.h>
 #include <fabric/uimanager/UIManagerDelegate.h>
 #include <fabric/view/ViewShadowNode.h>
+#include <fabric/view/RootShadowNode.h>
 
 namespace facebook {
 namespace react {
 
-/*
- * We expect having a dedicated subclass for root shadow node.
- */
-using SharedRootShadowNode = SharedViewShadowNode;
-using RootShadowNode = ViewShadowNode;
-
 class FabricUIManager;
 
 /*
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 221ea2c10555..5665baed32ee 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -22,6 +22,7 @@ rn_xplat_cxx_library(
         [
             ("", "*.h"),
             ("accessibility", "*.h"),
+            ("root", "*.h"),
             ("yoga", "*.h"),
         ],
         prefix = "fabric/view",
diff --git a/ReactCommon/fabric/view/root/RootProps.cpp b/ReactCommon/fabric/view/root/RootProps.cpp
new file mode 100644
index 000000000000..e8f0becede97
--- /dev/null
+++ b/ReactCommon/fabric/view/root/RootProps.cpp
@@ -0,0 +1,45 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "RootProps.h"
+
+#include "yogaValuesConversions.h"
+
+namespace facebook {
+namespace react {
+
+void RootProps::applyLayoutConstraints(const LayoutConstraints &layoutConstraints) {
+  ensureUnsealed();
+
+  layoutConstraints_ = layoutConstraints;
+
+  yogaStyle_.minDimensions[YGDimensionWidth] =
+    yogaStyleValueFromFloat(layoutConstraints.minimumSize.width);
+  yogaStyle_.minDimensions[YGDimensionHeight] =
+    yogaStyleValueFromFloat(layoutConstraints.minimumSize.height);
+
+  yogaStyle_.maxDimensions[YGDimensionWidth] =
+    yogaStyleValueFromFloat(layoutConstraints.maximumSize.width);
+  yogaStyle_.maxDimensions[YGDimensionHeight] =
+    yogaStyleValueFromFloat(layoutConstraints.maximumSize.height);
+}
+
+void RootProps::applyLayoutContext(const LayoutContext &layoutContext) {
+  ensureUnsealed();
+  layoutContext_ = layoutContext;
+}
+
+LayoutConstraints RootProps::getLayoutConstraints() const {
+  return layoutConstraints_;
+}
+
+LayoutContext RootProps::getLayoutContext() const {
+  return layoutContext_;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/root/RootProps.h b/ReactCommon/fabric/view/root/RootProps.h
new file mode 100644
index 000000000000..f8c40f361914
--- /dev/null
+++ b/ReactCommon/fabric/view/root/RootProps.h
@@ -0,0 +1,44 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/LayoutConstraints.h>
+#include <fabric/core/LayoutContext.h>
+#include <fabric/view/ViewProps.h>
+
+namespace facebook {
+namespace react {
+
+class RootProps;
+
+using SharedRootProps = std::shared_ptr<const RootProps>;
+
+class RootProps final:
+  public ViewProps {
+
+public:
+
+  /*
+   * Same semantic as `apply()` but LayoutConstraints & LayoutContext specific.
+   */
+  void applyLayoutConstraints(const LayoutConstraints &layoutConstraints);
+  void applyLayoutContext(const LayoutContext &layoutContext);
+
+  LayoutConstraints getLayoutConstraints() const;
+  LayoutContext getLayoutContext() const;
+
+private:
+
+  LayoutConstraints layoutConstraints_;
+  LayoutContext layoutContext_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/root/RootShadowNode.cpp b/ReactCommon/fabric/view/root/RootShadowNode.cpp
new file mode 100644
index 000000000000..97dc7dd011e5
--- /dev/null
+++ b/ReactCommon/fabric/view/root/RootShadowNode.cpp
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "RootShadowNode.h"
+
+namespace facebook {
+namespace react {
+
+ComponentName RootShadowNode::getComponentName() const {
+  return ComponentName("RootView");
+}
+
+void RootShadowNode::layout() {
+  ensureUnsealed();
+  layout(getProps()->getLayoutContext());
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/root/RootShadowNode.h b/ReactCommon/fabric/view/root/RootShadowNode.h
new file mode 100644
index 000000000000..6508fa587218
--- /dev/null
+++ b/ReactCommon/fabric/view/root/RootShadowNode.h
@@ -0,0 +1,50 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/LayoutContext.h>
+#include <fabric/view/RootProps.h>
+#include <fabric/view/ConcreteViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class RootShadowNode;
+
+using SharedRootShadowNode = std::shared_ptr<const RootShadowNode>;
+using UnsharedRootShadowNode = std::shared_ptr<RootShadowNode>;
+
+/*
+ * `ShadowNode` for the root component.
+ * Besides all functionality of the `View` component, `RootShadowNode` contains
+ * props which represent external layout constraints and context of the
+ * shadow tree.
+ */
+class RootShadowNode final:
+  public ConcreteViewShadowNode<RootProps> {
+
+public:
+
+  using ConcreteViewShadowNode::ConcreteViewShadowNode;
+
+  ComponentName getComponentName() const override;
+
+  /*
+   * Layouts the shadow tree.
+   */
+  void layout();
+
+private:
+
+  using YogaLayoutableShadowNode::layout;
+};
+
+} // namespace react
+} // namespace facebook

From a879842033385dc342970692a987cdf08d407e2a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:16 -0700
Subject: [PATCH 0471/1109] Fabric: Introducing `ShadowTree`

Summary: ShadowTree is an abstraction around (commited) root shadow node and managing its lifecycle.

Reviewed By: mdvacca

Differential Revision: D7857049

fbshipit-source-id: 8d530e0366fc703e4aef4ec88dd8ea990dafaaf1
---
 ReactCommon/fabric/uimanager/Scheduler.cpp    |  78 ++++++-------
 ReactCommon/fabric/uimanager/Scheduler.h      |  26 +++--
 ReactCommon/fabric/uimanager/ShadowTree.cpp   | 107 ++++++++++++++++++
 ReactCommon/fabric/uimanager/ShadowTree.h     |  87 ++++++++++++++
 .../fabric/uimanager/ShadowTreeDelegate.h     |  25 ++++
 5 files changed, 268 insertions(+), 55 deletions(-)
 create mode 100644 ReactCommon/fabric/uimanager/ShadowTree.cpp
 create mode 100644 ReactCommon/fabric/uimanager/ShadowTree.h
 create mode 100644 ReactCommon/fabric/uimanager/ShadowTreeDelegate.h

diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index 6ad2f45f0080..f4ffe53a3b11 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -19,7 +19,6 @@ namespace react {
 
 Scheduler::Scheduler() {
   auto componentDescriptorRegistry = std::make_shared<ComponentDescriptorRegistry>();
-
   componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ViewComponentDescriptor>());
   componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ParagraphComponentDescriptor>());
   componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<TextComponentDescriptor>());
@@ -34,12 +33,29 @@ Scheduler::~Scheduler() {
 }
 
 void Scheduler::registerRootTag(Tag rootTag) {
-  auto rootShadowNode = std::make_shared<RootShadowNode>(rootTag, rootTag, nullptr);
-  rootNodeRegistry_.insert({rootTag, rootShadowNode});
+  auto &&shadowTree = std::make_shared<ShadowTree>(rootTag);
+  shadowTree->setDelegate(this);
+  shadowTreeRegistry_.insert({rootTag, shadowTree});
 }
 
 void Scheduler::unregisterRootTag(Tag rootTag) {
-  rootNodeRegistry_.erase(rootTag);
+  auto &&iterator = shadowTreeRegistry_.find(rootTag);
+  auto &&shadowTree = iterator->second;
+  assert(shadowTree);
+  shadowTree->setDelegate(nullptr);
+  shadowTreeRegistry_.erase(iterator);
+}
+
+Size Scheduler::measure(const Tag &rootTag, const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const {
+  auto &&shadowTree = shadowTreeRegistry_.at(rootTag);
+  assert(shadowTree);
+  return shadowTree->measure(layoutConstraints, layoutContext);
+}
+
+void Scheduler::constraintLayout(const Tag &rootTag, const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) {
+  auto &&shadowTree = shadowTreeRegistry_.at(rootTag);
+  assert(shadowTree);
+  return shadowTree->constraintLayout(layoutConstraints, layoutContext);
 }
 
 #pragma mark - Delegate
@@ -48,55 +64,27 @@ void Scheduler::setDelegate(SchedulerDelegate *delegate) {
   delegate_ = delegate;
 }
 
-SchedulerDelegate *Scheduler::getDelegate() {
+SchedulerDelegate *Scheduler::getDelegate() const {
   return delegate_;
 }
 
-#pragma mark - UIManagerDelegate
-  
-void Scheduler::uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNodeUnsharedList &rootChildNodes) {
-  SharedRootShadowNode oldRootShadowNode = rootNodeRegistry_[rootTag];
-  assert(oldRootShadowNode);
-
-  SharedRootShadowNode newRootShadowNode =
-    std::make_shared<RootShadowNode>(oldRootShadowNode, nullptr, SharedShadowNodeSharedList(rootChildNodes));
-
-  auto nonConstOldRootShadowNode = std::const_pointer_cast<RootShadowNode>(oldRootShadowNode);
-  auto nonConstNewRootShadowNode = std::const_pointer_cast<RootShadowNode>(newRootShadowNode);
-
-  LayoutContext layoutContext = LayoutContext();
-
-  LOG(INFO) << "Old Shadow Tree: \n" << oldRootShadowNode->getDebugDescription();
-  LOG(INFO) << "New Shadow Tree *before* layout: \n" << newRootShadowNode->getDebugDescription();
-
-  nonConstNewRootShadowNode->layout(layoutContext);
-
-  nonConstNewRootShadowNode->sealRecursive();
-
-  LOG(INFO) << "New Shadow Tree *after* layout: \n" << nonConstNewRootShadowNode->getDebugDescription();
-
-  TreeMutationInstructionList instructions = TreeMutationInstructionList();
-
-  calculateMutationInstructions(
-    instructions,
-    oldRootShadowNode,
-    oldRootShadowNode->ShadowNode::getChildren(),
-    newRootShadowNode->ShadowNode::getChildren()
-  );
-
-  LOG(INFO) << "TreeMutationInstructionList:";
-
-  for (auto instruction : instructions) {
-    LOG(INFO) << "Instruction: " << instruction.getDebugDescription();
-  }
-
-  rootNodeRegistry_[rootTag] = newRootShadowNode;
+#pragma mark - ShadowTreeDelegate
 
+void Scheduler::shadowTreeDidCommit(const SharedShadowTree &shadowTree, const TreeMutationInstructionList &instructions) {
   if (delegate_) {
-    delegate_->schedulerDidComputeMutationInstructions(rootTag, instructions);
+    delegate_->schedulerDidComputeMutationInstructions(shadowTree->getRootTag(), instructions);
   }
 }
 
+#pragma mark - UIManagerDelegate
+  
+void Scheduler::uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNodeUnsharedList &rootChildNodes) {
+  auto &&iterator = shadowTreeRegistry_.find(rootTag);
+  auto &&shadowTree = iterator->second;
+  assert(shadowTree);
+  return shadowTree->complete(rootChildNodes);
+}
+
 void Scheduler::uiManagerDidCreateShadowNode(const SharedShadowNode &shadowNode) {
   if (delegate_) {
     delegate_->schedulerDidRequestPreliminaryViewAllocation(shadowNode->getComponentName());
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index 5082f9bb6095..cadbc4caa2ed 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -8,6 +8,8 @@
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/uimanager/SchedulerDelegate.h>
 #include <fabric/uimanager/UIManagerDelegate.h>
+#include <fabric/uimanager/ShadowTree.h>
+#include <fabric/uimanager/ShadowTreeDelegate.h>
 #include <fabric/view/ViewShadowNode.h>
 #include <fabric/view/RootShadowNode.h>
 
@@ -20,18 +22,21 @@ class FabricUIManager;
  * Scheduler coordinates Shadow Tree updates and event flows.
  */
 class Scheduler:
-  public UIManagerDelegate {
+  public UIManagerDelegate,
+  public ShadowTreeDelegate {
 
 public:
+
   Scheduler();
-  virtual ~Scheduler();
+  ~Scheduler();
 
-#pragma mark - Root Nodes Managerment
+#pragma mark - Shadow Tree Management
 
   void registerRootTag(Tag rootTag);
   void unregisterRootTag(Tag rootTag);
 
-  void setLayoutConstraints(Tag rootTag, LayoutConstraints layoutConstraints);
+  Size measure(const Tag &rootTag, const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const;
+  void constraintLayout(const Tag &rootTag, const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext);
 
 #pragma mark - Delegate
 
@@ -41,13 +46,17 @@ class Scheduler:
    * the pointer before being destroyed.
    */
   void setDelegate(SchedulerDelegate *delegate);
-  SchedulerDelegate *getDelegate();
+  SchedulerDelegate *getDelegate() const;
 
 #pragma mark - UIManagerDelegate
 
   void uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNodeUnsharedList &rootChildNodes) override;
   void uiManagerDidCreateShadowNode(const SharedShadowNode &shadowNode) override;
 
+#pragma mark - ShadowTreeDelegate
+
+  void shadowTreeDidCommit(const SharedShadowTree &shadowTree, const TreeMutationInstructionList &instructions) override;
+
 #pragma mark - Deprecated
 
   /*
@@ -56,13 +65,10 @@ class Scheduler:
   std::shared_ptr<FabricUIManager> getUIManager_DO_NOT_USE();
 
 private:
+
   SchedulerDelegate *delegate_;
   std::shared_ptr<FabricUIManager> uiManager_;
-
-  /*
-   * All commited `RootShadowNode` instances to differentiate against.
-   */
-  std::unordered_map<Tag, SharedRootShadowNode> rootNodeRegistry_;
+  std::unordered_map<Tag, SharedShadowTree> shadowTreeRegistry_;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
new file mode 100644
index 000000000000..66d2e23068c8
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -0,0 +1,107 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include "ShadowTree.h"
+
+#include <fabric/core/LayoutContext.h>
+#include <fabric/core/LayoutPrimitives.h>
+
+#include "ShadowTreeDelegate.h"
+#include "Differentiator.h"
+#include "TreeMutationInstruction.h"
+
+namespace facebook {
+namespace react {
+
+ShadowTree::ShadowTree(Tag rootTag):
+  rootTag_(rootTag) {
+
+  rootShadowNode_ = std::make_shared<RootShadowNode>(
+    rootTag,
+    rootTag,
+    nullptr,
+    RootShadowNode::defaultSharedProps()
+  );
+}
+
+Tag ShadowTree::getRootTag() const {
+  return rootTag_;
+}
+
+#pragma mark - Layout
+
+Size ShadowTree::measure(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const {
+  auto newRootShadowNode = cloneRootShadowNode(layoutConstraints, layoutContext);
+  newRootShadowNode->layout();
+  return newRootShadowNode->getLayoutMetrics().frame.size;
+}
+
+void ShadowTree::constraintLayout(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) {
+  auto newRootShadowNode = cloneRootShadowNode(layoutConstraints, layoutContext);
+  complete(newRootShadowNode);
+}
+
+#pragma mark - Commiting
+
+UnsharedRootShadowNode ShadowTree::cloneRootShadowNode(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const {
+  auto oldRootShadowNode = rootShadowNode_;
+  auto &&props = std::make_shared<RootProps>(*oldRootShadowNode->getProps());
+  props->applyLayoutConstraints(layoutConstraints);
+  props->applyLayoutContext(layoutContext);
+  auto newRootShadowNode = std::make_shared<RootShadowNode>(oldRootShadowNode, props, nullptr);
+  return newRootShadowNode;
+}
+
+void ShadowTree::complete(const SharedShadowNodeUnsharedList &rootChildNodes) {
+  auto oldRootShadowNode = rootShadowNode_;
+  auto newRootShadowNode =
+    std::make_shared<RootShadowNode>(oldRootShadowNode, nullptr, SharedShadowNodeSharedList(rootChildNodes));
+
+  complete(newRootShadowNode);
+}
+
+void ShadowTree::complete(UnsharedRootShadowNode newRootShadowNode) {
+  SharedRootShadowNode oldRootShadowNode = rootShadowNode_;
+
+  newRootShadowNode->layout();
+
+  newRootShadowNode->sealRecursive();
+
+  TreeMutationInstructionList instructions = TreeMutationInstructionList();
+
+  calculateMutationInstructions(
+    instructions,
+    oldRootShadowNode,
+    oldRootShadowNode->ShadowNode::getChildren(),
+    newRootShadowNode->ShadowNode::getChildren()
+  );
+
+  if (commit(newRootShadowNode)) {
+    if (delegate_) {
+      delegate_->shadowTreeDidCommit(shared_from_this(), instructions);
+    }
+  }
+}
+
+bool ShadowTree::commit(const SharedRootShadowNode &newRootShadowNode) {
+  std::lock_guard<std::mutex> lock(commitMutex_);
+
+  if (newRootShadowNode->getSourceNode() != rootShadowNode_) {
+    return false;
+  }
+
+  rootShadowNode_ = newRootShadowNode;
+  return true;
+}
+
+#pragma mark - Delegate
+
+void ShadowTree::setDelegate(ShadowTreeDelegate *delegate) {
+  delegate_ = delegate;
+}
+
+ShadowTreeDelegate *ShadowTree::getDelegate() const {
+  return delegate_;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.h b/ReactCommon/fabric/uimanager/ShadowTree.h
new file mode 100644
index 000000000000..e2abea7a37cc
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/ShadowTree.h
@@ -0,0 +1,87 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <memory>
+#include <mutex>
+#include <stdatomic.h>
+
+#include <fabric/core/LayoutConstraints.h>
+#include <fabric/core/ReactPrimitives.h>
+#include <fabric/core/ShadowNode.h>
+#include <fabric/uimanager/ShadowTreeDelegate.h>
+#include <fabric/view/RootShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class ShadowTree;
+
+using SharedShadowTree = std::shared_ptr<ShadowTree>;
+
+/*
+ * Represents the shadow tree and its lifecycle.
+ */
+class ShadowTree final:
+  public std::enable_shared_from_this<ShadowTree> {
+
+public:
+
+  /*
+   * Creates a new shadow tree instance with given `rootTag`.
+   */
+  ShadowTree(Tag rootTag);
+
+  /*
+   * Returns the rootTag associated with the shadow tree (the tag of the
+   * root shadow node).
+   */
+  Tag getRootTag() const;
+
+#pragma mark - Layout
+
+  /*
+   * Measures the shadow tree with given `layoutConstraints` and `layoutContext`.
+   * Can be called from any thread, side-effect-less.
+   */
+  Size measure(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const;
+
+  /*
+   * Applies given `layoutConstraints` and `layoutContext` and commit
+   * the new shadow tree.
+   * Can be called from any thread.
+   */
+  void constraintLayout(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext);
+
+#pragma mark - Application
+
+  /*
+   * Create a new shadow tree with given `rootChildNodes` and commit.
+   * Can be called from any thread.
+   */
+  void complete(const SharedShadowNodeUnsharedList &rootChildNodes);
+
+#pragma mark - Delegate
+
+  /*
+   * Sets and gets the delegate.
+   * The delegate is stored as a raw pointer, so the owner must null
+   * the pointer before being destroyed.
+   */
+  void setDelegate(ShadowTreeDelegate *delegate);
+  ShadowTreeDelegate *getDelegate() const;
+
+private:
+
+  UnsharedRootShadowNode cloneRootShadowNode(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const;
+  void complete(UnsharedRootShadowNode newRootShadowNode);
+  bool commit(const SharedRootShadowNode &newRootShadowNode);
+
+  const Tag rootTag_;
+  SharedRootShadowNode rootShadowNode_;
+  ShadowTreeDelegate *delegate_;
+  mutable std::mutex commitMutex_ {};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/ShadowTreeDelegate.h b/ReactCommon/fabric/uimanager/ShadowTreeDelegate.h
new file mode 100644
index 000000000000..59ca85f46be5
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/ShadowTreeDelegate.h
@@ -0,0 +1,25 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#include <fabric/uimanager/TreeMutationInstruction.h>
+
+namespace facebook {
+namespace react {
+
+class ShadowTree;
+
+/*
+ * Abstract class for ShadowTree's delegate.
+ */
+class ShadowTreeDelegate {
+public:
+
+  /*
+   * Called right after Shadow Tree commit a new state of the the tree.
+   */
+  virtual void shadowTreeDidCommit(const std::shared_ptr<ShadowTree> &shadowTree, const TreeMutationInstructionList &instructions) = 0;
+};
+
+} // namespace react
+} // namespace facebook

From e052685ffc633a5b42f9658833d4ec3bc9d64710 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:19 -0700
Subject: [PATCH 0472/1109] Fabric: Resonable default values for
 LayoutConstraints members

Summary: Trivial.

Reviewed By: mdvacca

Differential Revision: D7857046

fbshipit-source-id: 88400f1831bf66ccd3d880ddf1de3df27287b5be
---
 ReactCommon/fabric/core/layout/LayoutConstraints.h | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutConstraints.h b/ReactCommon/fabric/core/layout/LayoutConstraints.h
index 432a8aad324d..8f92cc22c1cc 100644
--- a/ReactCommon/fabric/core/layout/LayoutConstraints.h
+++ b/ReactCommon/fabric/core/layout/LayoutConstraints.h
@@ -17,8 +17,8 @@ namespace react {
  * Unified layout constraints for measuring.
  */
 struct LayoutConstraints {
-  Size minimumSize;
-  Size maximumSize;
+  Size minimumSize {0, 0};
+  Size maximumSize {kFloatUndefined, kFloatUndefined};
   LayoutDirection layoutDirection;
 };
 

From 25664cc48c042319067ee26c87608fa6a1bed821 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:21 -0700
Subject: [PATCH 0473/1109] Fabric: RCTConversions unified way to covert
 primitives between Fabric and UIKit

Summary: Quite obvious.

Reviewed By: mdvacca

Differential Revision: D7857051

fbshipit-source-id: 85aa6a9c064e5aebe65486acd011d445efaf0ce8
---
 .../Mounting/RCTParagraphComponentView.mm     | 13 ++-----
 .../Mounting/UIView+ComponentViewProtocol.mm  | 12 ++-----
 React/Fabric/RCTConversions.h                 | 34 +++++++++++++++++++
 3 files changed, 38 insertions(+), 21 deletions(-)
 create mode 100644 React/Fabric/RCTConversions.h

diff --git a/React/Fabric/Mounting/RCTParagraphComponentView.mm b/React/Fabric/Mounting/RCTParagraphComponentView.mm
index 6709bd2b2223..29175e9f535e 100644
--- a/React/Fabric/Mounting/RCTParagraphComponentView.mm
+++ b/React/Fabric/Mounting/RCTParagraphComponentView.mm
@@ -13,6 +13,7 @@
 #import <fabric/text/ParagraphProps.h>
 #import <fabric/textlayoutmanager/TextLayoutManager.h>
 #import <fabric/textlayoutmanager/RCTTextLayoutManager.h>
+#import "RCTConversions.h"
 
 using namespace facebook::react;
 
@@ -60,17 +61,7 @@ - (void)drawRect:(CGRect)rect
   RCTTextLayoutManager *nativeTextLayoutManager =
     (__bridge RCTTextLayoutManager *)textLayoutManager->getNativeTextLayoutManager();
 
-  auto contentFrame = _layoutMetrics.getContentFrame();
-  CGRect frame = {
-    .origin = {
-      .x = contentFrame.origin.x,
-      .y = contentFrame.origin.y
-    },
-    .size = {
-      .width = contentFrame.size.width,
-      .height = contentFrame.size.height
-    }
-  };
+  CGRect frame = RCTCGRectFromRect(_layoutMetrics.getContentFrame());
 
   [nativeTextLayoutManager drawAttributedString:_paragraphLocalData->getAttributedString()
                             paragraphAttributes:_paragraphAttributes
diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
index 1a4136cfd511..5627a699d252 100644
--- a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
@@ -8,6 +8,7 @@
 #import "UIView+ComponentViewProtocol.h"
 
 #import <React/RCTAssert.h>
+#import "RCTConversions.h"
 
 @implementation UIView (ComponentViewProtocol)
 
@@ -40,16 +41,7 @@ - (void)updateLayoutMetrics:(facebook::react::LayoutMetrics)layoutMetrics
            oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics
 {
   if (layoutMetrics.frame != oldLayoutMetrics.frame) {
-    self.frame = {
-      .origin = {
-        .x = layoutMetrics.frame.origin.x,
-        .y = layoutMetrics.frame.origin.y
-      },
-      .size = {
-        .width = layoutMetrics.frame.size.width,
-        .height = layoutMetrics.frame.size.height
-      }
-    };
+    self.frame = RCTCGRectFromRect(layoutMetrics.frame);
   }
 
   // TODO: Apply another layout metrics here.
diff --git a/React/Fabric/RCTConversions.h b/React/Fabric/RCTConversions.h
new file mode 100644
index 000000000000..9e4184651da4
--- /dev/null
+++ b/React/Fabric/RCTConversions.h
@@ -0,0 +1,34 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <fabric/graphics/Geometry.h>
+
+inline CGPoint RCTCGPointFromPoint(facebook::react::Point point) {
+  return {point.x, point.y};
+}
+
+inline CGSize RCTCGSizeFromSize(facebook::react::Size size) {
+  return {size.width, size.height};
+}
+
+inline CGRect RCTCGRectFromRect(facebook::react::Rect rect) {
+  return {RCTCGPointFromPoint(rect.origin), RCTCGSizeFromSize(rect.size)};
+}
+
+inline facebook::react::Point RCTPointFromCGPoint(CGPoint point) {
+  return {point.x, point.y};
+}
+
+inline facebook::react::Size RCTSizeFromCGSize(CGSize size) {
+  return {size.width, size.height};
+}
+
+inline facebook::react::Rect RCTRectFromCGRect(CGRect rect) {
+  return {RCTPointFromCGPoint(rect.origin), RCTSizeFromCGSize(rect.size)};
+}

From 20e88e9ac4b1e162cf9ac514c82b663212bb9dda Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:24 -0700
Subject: [PATCH 0474/1109] Fabric: Deprecating `-[RCTSurface rootViewTag]`

Summary:
This diff deprecates `-[RCTSurface rootViewTag]` in favour of `-[RCTSurface rootTag]` which returns
same value but represented as `ReactTag` (`long`) instead of `NSNumber *`.

Reviewed By: mdvacca

Differential Revision: D7857044

fbshipit-source-id: f5427c30d3de2d3563e830f2caac70b7dc9631f9
---
 React/Fabric/Surface/RCTFabricSurface.h  | 12 +++++++++++-
 React/Fabric/Surface/RCTFabricSurface.mm |  1 -
 2 files changed, 11 insertions(+), 2 deletions(-)

diff --git a/React/Fabric/Surface/RCTFabricSurface.h b/React/Fabric/Surface/RCTFabricSurface.h
index 498fe1807c89..c0a88c0729a3 100644
--- a/React/Fabric/Surface/RCTFabricSurface.h
+++ b/React/Fabric/Surface/RCTFabricSurface.h
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  */
 
+#import <React/RCTPrimitives.h>
 #import <React/RCTSurfaceStage.h>
 
 NS_ASSUME_NONNULL_BEGIN
@@ -37,7 +38,7 @@ NS_ASSUME_NONNULL_BEGIN
 @property (atomic, readonly) RCTSurfaceStage stage;
 @property (atomic, readonly) RCTBridge *bridge;
 @property (atomic, readonly) NSString *moduleName;
-@property (atomic, readonly) NSNumber *rootViewTag;
+@property (atomic, readonly) ReactTag rootTag;
 
 @property (atomic, readwrite, weak, nullable) id<RCTSurfaceDelegate> delegate;
 
@@ -124,4 +125,13 @@ NS_ASSUME_NONNULL_BEGIN
 
 @end
 
+@interface RCTFabricSurface (Deprecated)
+
+/**
+ * Deprecated. Use `rootTag` instead.
+ */
+@property (atomic, readonly) NSNumber *rootViewTag;
+
+@end
+
 NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Surface/RCTFabricSurface.mm b/React/Fabric/Surface/RCTFabricSurface.mm
index babdc28c7c3d..060d05675d65 100644
--- a/React/Fabric/Surface/RCTFabricSurface.mm
+++ b/React/Fabric/Surface/RCTFabricSurface.mm
@@ -28,7 +28,6 @@ @implementation RCTFabricSurface {
   // Immutable
   RCTSurfacePresenter *_surfacePresenter;
   NSString *_moduleName;
-  ReactTag _rootTag;
 
   // Protected by the `_mutex`
   std::mutex _mutex;

From 67dbcbd57e8e69a397faaab8daffd61f27b90db4 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 8 May 2018 22:56:27 -0700
Subject: [PATCH 0475/1109] Fabric: Wiring layout pipeline between Surface and
 ShadowTree

Summary:
The layout pipeline is quite long:
UIKit <-> Surface <-> SurfacePresenter <-> [RCTScheduler <|-|> Scheduler] <-> ShadowTree <-> RootShadowNode <-> YogaNode.

Reviewed By: mdvacca

Differential Revision: D7857048

fbshipit-source-id: 06c92ef1639465d17e2489667f99d0114b80dcff
---
 React/Fabric/RCTScheduler.h              | 10 +++++++
 React/Fabric/RCTScheduler.mm             | 16 +++++++++++
 React/Fabric/RCTSurfacePresenter.h       | 15 +++++++++-
 React/Fabric/RCTSurfacePresenter.mm      | 36 ++++++++++++++++++++++--
 React/Fabric/Surface/RCTFabricSurface.mm |  9 ++++--
 5 files changed, 79 insertions(+), 7 deletions(-)

diff --git a/React/Fabric/RCTScheduler.h b/React/Fabric/RCTScheduler.h
index 1f1e367060f5..e6a730b788ca 100644
--- a/React/Fabric/RCTScheduler.h
+++ b/React/Fabric/RCTScheduler.h
@@ -9,6 +9,8 @@
 #import <memory>
 
 #import <React/RCTPrimitives.h>
+#import <fabric/core/LayoutConstraints.h>
+#import <fabric/core/LayoutContext.h>
 #import <fabric/uimanager/FabricUIManager.h>
 #import <fabric/uimanager/TreeMutationInstruction.h>
 
@@ -38,6 +40,14 @@ NS_ASSUME_NONNULL_BEGIN
 
 - (void)unregisterRootTag:(ReactTag)tag;
 
+- (CGSize)measureWithLayoutConstraints:(facebook::react::LayoutConstraints)layoutConstraints
+                         layoutContext:(facebook::react::LayoutContext)layoutContext
+                               rootTag:(ReactTag)rootTag;
+
+- (void)constraintLayoutWithLayoutConstraints:(facebook::react::LayoutConstraints)layoutConstraints
+                                layoutContext:(facebook::react::LayoutContext)layoutContext
+                                      rootTag:(ReactTag)rootTag;
+
 @end
 
 @interface RCTScheduler (Deprecated)
diff --git a/React/Fabric/RCTScheduler.mm b/React/Fabric/RCTScheduler.mm
index 0fe06175ee4d..fcd1a9d8b86d 100644
--- a/React/Fabric/RCTScheduler.mm
+++ b/React/Fabric/RCTScheduler.mm
@@ -10,6 +10,8 @@
 #import <fabric/uimanager/Scheduler.h>
 #import <fabric/uimanager/SchedulerDelegate.h>
 
+#import "RCTConversions.h"
+
 using namespace facebook::react;
 
 class SchedulerDelegateProxy: public SchedulerDelegate {
@@ -61,6 +63,20 @@ - (void)unregisterRootTag:(ReactTag)tag
   _scheduler->unregisterRootTag(tag);
 }
 
+- (CGSize)measureWithLayoutConstraints:(LayoutConstraints)layoutConstraints
+                         layoutContext:(LayoutContext)layoutContext
+                               rootTag:(ReactTag)rootTag
+{
+  return RCTCGSizeFromSize(_scheduler->measure(rootTag, layoutConstraints, layoutContext));
+}
+
+- (void)constraintLayoutWithLayoutConstraints:(LayoutConstraints)layoutConstraints
+                                layoutContext:(LayoutContext)layoutContext
+                                      rootTag:(ReactTag)rootTag
+{
+  _scheduler->constraintLayout(rootTag, layoutConstraints, layoutContext);
+}
+
 @end
 
 @implementation RCTScheduler (Deprecated)
diff --git a/React/Fabric/RCTSurfacePresenter.h b/React/Fabric/RCTSurfacePresenter.h
index d99133d59a91..65456cbf53e6 100644
--- a/React/Fabric/RCTSurfacePresenter.h
+++ b/React/Fabric/RCTSurfacePresenter.h
@@ -29,7 +29,7 @@ NS_ASSUME_NONNULL_BEGIN
 
 @end
 
-@interface RCTSurfacePresenter (Internal)
+@interface RCTSurfacePresenter (Surface)
 
 /**
  * Surface uses those methods to register itself in the Presenter.
@@ -38,6 +38,19 @@ NS_ASSUME_NONNULL_BEGIN
 - (void)registerSurface:(RCTFabricSurface *)surface;
 - (void)unregisterSurface:(RCTFabricSurface *)surface;
 
+/**
+ * Measures the Surface with given constraints.
+ */
+- (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize
+                      maximumSize:(CGSize)maximumSize
+                          surface:(RCTFabricSurface *)surface;
+
+/**
+ * Sets `minimumSize` and `maximumSize` layout constraints for the Surface.
+ */
+- (void)setMinimumSize:(CGSize)minimumSize
+           maximumSize:(CGSize)maximumSize
+               surface:(RCTFabricSurface *)surface;
 @end
 
 @interface RCTSurfacePresenter (Deprecated)
diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
index 8e88548c8d78..1e0164f2b9fd 100644
--- a/React/Fabric/RCTSurfacePresenter.mm
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -19,6 +19,11 @@
 #import <React/RCTSurfaceView.h>
 #import <React/RCTSurfaceView+Internal.h>
 
+#import <fabric/core/LayoutContext.h>
+#import <fabric/core/LayoutConstraints.h>
+
+#import "RCTConversions.h"
+
 using namespace facebook::react;
 
 @interface RCTSurfacePresenter () <RCTSchedulerDelegate, RCTMountingManagerDelegate>
@@ -87,6 +92,34 @@ - (void)unregisterSurface:(RCTFabricSurface *)surface
   [_surfaceRegistry unregisterSurface:surface];
 }
 
+- (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize
+                      maximumSize:(CGSize)maximumSize
+                          surface:(RCTFabricSurface *)surface
+{
+  LayoutContext layoutContext;
+  LayoutConstraints layoutConstraints = {};
+  layoutConstraints.minimumSize = RCTSizeFromCGSize(minimumSize);
+  layoutConstraints.maximumSize = RCTSizeFromCGSize(maximumSize);
+
+  return [_scheduler measureWithLayoutConstraints:layoutConstraints
+                                    layoutContext:layoutContext
+                                          rootTag:surface.rootTag];
+}
+
+- (void)setMinimumSize:(CGSize)minimumSize
+           maximumSize:(CGSize)maximumSize
+               surface:(RCTFabricSurface *)surface
+{
+  LayoutContext layoutContext;
+  LayoutConstraints layoutConstraints = {};
+  layoutConstraints.minimumSize = RCTSizeFromCGSize(minimumSize);
+  layoutConstraints.maximumSize = RCTSizeFromCGSize(maximumSize);
+
+  [_scheduler constraintLayoutWithLayoutConstraints:layoutConstraints
+                                      layoutContext:layoutContext
+                                            rootTag:surface.rootTag];
+}
+
 - (void)runSurface:(RCTFabricSurface *)surface
 {
   NSDictionary *applicationParameters = @{
@@ -122,9 +155,6 @@ - (void)mountingManager:(RCTMountingManager *)mountingManager didMountComponents
 
   UIView *rootComponentView = [_mountingManager.componentViewRegistry componentViewByTag:rootTag];
 
-  // FIXME: Remove this.
-  rootComponentView.frame = CGRectMake(0, 0, 400, 400);
-
   surface.view.rootView = (RCTSurfaceRootView *)rootComponentView;
 }
 
diff --git a/React/Fabric/Surface/RCTFabricSurface.mm b/React/Fabric/Surface/RCTFabricSurface.mm
index 060d05675d65..3028a204e97e 100644
--- a/React/Fabric/Surface/RCTFabricSurface.mm
+++ b/React/Fabric/Surface/RCTFabricSurface.mm
@@ -188,8 +188,9 @@ - (void)_stop
 - (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize
                       maximumSize:(CGSize)maximumSize
 {
-  // TODO: Not supported yet.
-  return CGSizeZero;
+  return [_surfacePresenter sizeThatFitsMinimumSize:minimumSize
+                                        maximumSize:maximumSize
+                                            surface:self];
 }
 
 #pragma mark - Size Constraints
@@ -213,7 +214,9 @@ - (void)setMinimumSize:(CGSize)minimumSize
     _minimumSize = minimumSize;
   }
 
-  // TODO: Not supported yet.
+  return [_surfacePresenter setMinimumSize:minimumSize
+                               maximumSize:maximumSize
+                                   surface:self];
 }
 
 - (CGSize)minimumSize

From 5d4c542c58d84bbe05f76bf01d9efdd9d438572c Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 9 May 2018 00:47:45 -0700
Subject: [PATCH 0476/1109] RN: Refactor `MockNativeMethods` in Jest

Reviewed By: sahrens

Differential Revision: D7917498

fbshipit-source-id: 97636080588bf2641a56256688cb0f2ec81ae463
---
 jest/MockNativeMethods.js | 38 ++++++++++++++++++++++++++++++++++++++
 jest/setup.js             | 29 +++--------------------------
 2 files changed, 41 insertions(+), 26 deletions(-)
 create mode 100644 jest/MockNativeMethods.js

diff --git a/jest/MockNativeMethods.js b/jest/MockNativeMethods.js
new file mode 100644
index 000000000000..9b44fc45fec6
--- /dev/null
+++ b/jest/MockNativeMethods.js
@@ -0,0 +1,38 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @format
+ */
+
+'use strict';
+
+const mockNativeFunction = methodName => {
+  let warned = false;
+  return function() {
+    if (warned) {
+      return;
+    }
+    warned = true;
+    console.warn(
+      'Calling .' +
+        methodName +
+        '() in the test renderer environment is not supported. Instead, mock ' +
+        'out your components that use findNodeHandle with replacements that ' +
+        "don't rely on the native environment.",
+    );
+  };
+};
+
+const MockNativeMethods = {
+  measure: mockNativeFunction('measure'),
+  measureInWindow: mockNativeFunction('measureInWindow'),
+  measureLayout: mockNativeFunction('measureLayout'),
+  setNativeProps: mockNativeFunction('setNativeProps'),
+  focus: mockNativeFunction('focus'),
+  blur: mockNativeFunction('blur'),
+};
+
+module.exports = MockNativeMethods;
diff --git a/jest/setup.js b/jest/setup.js
index 25fed46877e9..b40bcebae25d 100644
--- a/jest/setup.js
+++ b/jest/setup.js
@@ -6,6 +6,7 @@
  */
 'use strict';
 
+const MockNativeMethods = require.requireActual('./MockNativeMethods');
 const mockComponent = require.requireActual('./mockComponent');
 
 require.requireActual('../Libraries/polyfills/babelHelpers.js');
@@ -81,33 +82,9 @@ jest
     const NativeMethodsMixin =
       ReactNative.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.NativeMethodsMixin;
 
-    const mockFunction = (key) => {
-      let warned = false;
-      return function() {
-        if (warned) {
-          return;
-        }
-        warned = true;
-        console.warn(
-          'Calling .' + key + '() in the test renderer environment is not ' +
-            'supported. Instead, mock out your components that use ' +
-            'findNodeHandle with replacements that don\'t rely on the ' +
-            'native environment.',
-        );
-      };
-    };
+    Object.assign(NativeMethodsMixin, MockNativeMethods);
+    Object.assign(ReactNative.NativeComponent.prototype, MockNativeMethods);
 
-    [
-      'measure',
-      'measureInWindow',
-      'measureLayout',
-      'setNativeProps',
-      'focus',
-      'blur',
-    ].forEach((key) => {
-      NativeMethodsMixin[key] = mockFunction(key);
-      ReactNative.NativeComponent.prototype[key] = mockFunction(key);
-    });
     return ReactNative;
   })
   .mock('ensureComponentIsNative', () => () => true);

From e1339bc18303ca5394cd0c9dc97cededb2261581 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 9 May 2018 00:47:46 -0700
Subject: [PATCH 0477/1109] RN: Replace `context.isInAParentText` w/
 React.createContext

Reviewed By: sahrens

Differential Revision: D7895382

fbshipit-source-id: 4affcecd147b8e8c506e0d94f223bac3e6dfdf66
---
 Libraries/Components/TextInput/TextInput.js   | 21 ++---
 Libraries/Components/View/View.js             | 38 +++++-----
 Libraries/Image/Image.android.js              | 76 +++++++++----------
 Libraries/Text/Text.js                        | 29 ++++---
 .../ViewContext.js => Text/TextAncestor.js}   | 16 ++--
 5 files changed, 85 insertions(+), 95 deletions(-)
 rename Libraries/{Components/View/ViewContext.js => Text/TextAncestor.js} (53%)

diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index f0cf5b955e96..754af17e1bcb 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -20,6 +20,7 @@ const PropTypes = require('prop-types');
 const ReactNative = require('ReactNative');
 const StyleSheet = require('StyleSheet');
 const Text = require('Text');
+const TextAncestor = require('TextAncestor');
 const TextInputState = require('TextInputState');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
@@ -28,7 +29,6 @@ const TimerMixin = require('react-timer-mixin');
 const TouchableWithoutFeedback = require('TouchableWithoutFeedback');
 const UIManager = require('UIManager');
 const ViewPropTypes = require('ViewPropTypes');
-const {ViewContextTypes} = require('ViewContext');
 
 const emptyFunction = require('fbjs/lib/emptyFunction');
 const invariant = require('fbjs/lib/invariant');
@@ -47,8 +47,6 @@ const onlyMultiline = {
   children: true,
 };
 
-import type {ViewChildContext} from 'ViewContext';
-
 if (Platform.OS === 'android') {
   AndroidTextInput = requireNativeComponent('AndroidTextInput', null);
 } else if (Platform.OS === 'ios') {
@@ -701,16 +699,7 @@ const TextInput = createReactClass({
     }
   },
 
-  getChildContext(): ViewChildContext {
-    return {
-      isInAParentText: true,
-    };
-  },
-
-  childContextTypes: ViewContextTypes,
-
   contextTypes: {
-    ...ViewContextTypes,
     onFocusRequested: PropTypes.func,
     focusEmitter: PropTypes.instanceOf(EventEmitter),
   },
@@ -723,13 +712,17 @@ const TextInput = createReactClass({
   },
 
   render: function() {
+    let textInput;
     if (Platform.OS === 'ios') {
-      return UIManager.RCTVirtualText
+      textInput = UIManager.RCTVirtualText
         ? this._renderIOS()
         : this._renderIOSLegacy();
     } else if (Platform.OS === 'android') {
-      return this._renderAndroid();
+      textInput = this._renderAndroid();
     }
+    return (
+      <TextAncestor.Provider value={true}>{textInput}</TextAncestor.Provider>
+    );
   },
 
   _getText: function(): ?string {
diff --git a/Libraries/Components/View/View.js b/Libraries/Components/View/View.js
index 558f40a5d408..1e79f88a5483 100644
--- a/Libraries/Components/View/View.js
+++ b/Libraries/Components/View/View.js
@@ -7,6 +7,7 @@
  * @flow
  * @format
  */
+
 'use strict';
 
 const Platform = require('Platform');
@@ -14,13 +15,13 @@ const React = require('React');
 const ReactNative = require('ReactNative');
 const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
 const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
+const TextAncestor = require('TextAncestor');
 const ViewPropTypes = require('ViewPropTypes');
-const {ViewContextTypes} = require('ViewContext');
+
 const invariant = require('fbjs/lib/invariant');
 const requireNativeComponent = require('requireNativeComponent');
 
 import type {ViewProps} from 'ViewPropTypes';
-import type {ViewChildContext} from 'ViewContext';
 
 export type Props = ViewProps;
 
@@ -33,30 +34,31 @@ export type Props = ViewProps;
  */
 class View extends ReactNative.NativeComponent<Props> {
   static propTypes = ViewPropTypes;
-  static childContextTypes = ViewContextTypes;
 
   viewConfig = {
     uiViewClassName: 'RCTView',
     validAttributes: ReactNativeViewAttributes.RCTView,
   };
 
-  getChildContext(): ViewChildContext {
-    return {
-      isInAParentText: false,
-    };
-  }
-
+  /**
+   * WARNING: This method will not be used in production mode as in that mode we
+   * replace wrapper component View with generated native wrapper RCTView. Avoid
+   * adding functionality this component that you'd want to be available in both
+   * dev and prod modes.
+   */
   render() {
-    invariant(
-      !(this.context.isInAParentText && Platform.OS === 'android'),
-      'Nesting of <View> within <Text> is not supported on Android.',
+    return (
+      <TextAncestor.Consumer>
+        {hasTextAncestor => {
+          // TODO: Change iOS to behave the same as Android.
+          invariant(
+            !hasTextAncestor || Platform.OS !== 'android',
+            'Nesting of <View> within <Text> is not supported on Android.',
+          );
+          return <RCTView {...this.props} />;
+        }}
+      </TextAncestor.Consumer>
     );
-
-    // WARNING: This method will not be used in production mode as in that mode we
-    // replace wrapper component View with generated native wrapper RCTView. Avoid
-    // adding functionality this component that you'd want to be available in both
-    // dev and prod modes.
-    return <RCTView {...this.props} />;
   }
 }
 
diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index 7b0ec83a8738..d9702700be59 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -7,6 +7,7 @@
  * @flow
  * @format
  */
+
 'use strict';
 
 var ImageResizeMode = require('ImageResizeMode');
@@ -18,6 +19,7 @@ var PropTypes = require('prop-types');
 var ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 var StyleSheet = require('StyleSheet');
 var StyleSheetPropType = require('StyleSheetPropType');
+const TextAncestor = require('TextAncestor');
 var ViewPropTypes = require('ViewPropTypes');
 
 var createReactClass = require('create-react-class');
@@ -26,8 +28,6 @@ var merge = require('merge');
 var requireNativeComponent = require('requireNativeComponent');
 var resolveAssetSource = require('resolveAssetSource');
 
-const {ViewContextTypes} = require('ViewContext');
-
 var {ImageLoader} = NativeModules;
 
 let _requestId = 1;
@@ -202,8 +202,6 @@ var Image = createReactClass({
     validAttributes: ReactNativeViewAttributes.RCTView,
   },
 
-  contextTypes: ViewContextTypes,
-
   render: function() {
     const source = resolveAssetSource(this.props.source);
     const defaultSource = resolveAssetSource(this.props.defaultSource);
@@ -236,42 +234,44 @@ var Image = createReactClass({
       );
     }
 
-    if (source && (source.uri || Array.isArray(source))) {
-      let style;
-      let sources;
-      if (source.uri) {
-        const {width, height} = source;
-        style = flattenStyle([{width, height}, styles.base, this.props.style]);
-        sources = [{uri: source.uri}];
-      } else {
-        style = flattenStyle([styles.base, this.props.style]);
-        sources = source;
-      }
-
-      const {onLoadStart, onLoad, onLoadEnd, onError} = this.props;
-      const nativeProps = merge(this.props, {
-        style,
-        shouldNotifyLoadEvents: !!(
-          onLoadStart ||
-          onLoad ||
-          onLoadEnd ||
-          onError
-        ),
-        src: sources,
-        headers: source.headers,
-        defaultSrc: defaultSource ? defaultSource.uri : null,
-        loadingIndicatorSrc: loadingIndicatorSource
-          ? loadingIndicatorSource.uri
-          : null,
-      });
+    if (!source || (!source.uri && !Array.isArray(source))) {
+      return null;
+    }
 
-      if (this.context.isInAParentText) {
-        return <RCTTextInlineImage {...nativeProps} />;
-      } else {
-        return <RKImage {...nativeProps} />;
-      }
+    let style;
+    let sources;
+    if (source.uri) {
+      const {width, height} = source;
+      style = flattenStyle([{width, height}, styles.base, this.props.style]);
+      sources = [{uri: source.uri}];
+    } else {
+      style = flattenStyle([styles.base, this.props.style]);
+      sources = source;
     }
-    return null;
+
+    const {onLoadStart, onLoad, onLoadEnd, onError} = this.props;
+    const nativeProps = merge(this.props, {
+      style,
+      shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),
+      src: sources,
+      headers: source.headers,
+      defaultSrc: defaultSource ? defaultSource.uri : null,
+      loadingIndicatorSrc: loadingIndicatorSource
+        ? loadingIndicatorSource.uri
+        : null,
+    });
+
+    return (
+      <TextAncestor.Consumer>
+        {hasTextAncestor =>
+          hasTextAncestor ? (
+            <RCTTextInlineImage {...nativeProps} />
+          ) : (
+            <RKImage {...nativeProps} />
+          )
+        }
+      </TextAncestor.Consumer>
+    );
   },
 });
 
diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index d6fd56fcc62e..d983638ac5f1 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -12,6 +12,7 @@
 const React = require('React');
 const ReactNative = require('ReactNative');
 const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
+const TextAncestor = require('TextAncestor');
 const TextPropTypes = require('TextPropTypes');
 const Touchable = require('Touchable');
 const UIManager = require('UIManager');
@@ -19,11 +20,9 @@ const UIManager = require('UIManager');
 const createReactNativeComponentClass = require('createReactNativeComponentClass');
 const mergeFast = require('mergeFast');
 const processColor = require('processColor');
-const {ViewContextTypes} = require('ViewContext');
 
 import type {PressEvent} from 'CoreEventTypes';
 import type {TextProps} from 'TextProps';
-import type {ViewChildContext} from 'ViewContext';
 
 type State = {
   isHighlighted: boolean,
@@ -61,8 +60,6 @@ const viewConfig = {
  */
 class Text extends ReactNative.NativeComponent<TextProps, State> {
   static propTypes = TextPropTypes;
-  static childContextTypes = ViewContextTypes;
-  static contextTypes = ViewContextTypes;
 
   static defaultProps = {
     accessible: true,
@@ -76,12 +73,6 @@ class Text extends ReactNative.NativeComponent<TextProps, State> {
 
   viewConfig = viewConfig;
 
-  getChildContext(): ViewChildContext {
-    return {
-      isInAParentText: true,
-    };
-  }
-
   _handlers: ?Object;
 
   _hasPressHandler(): boolean {
@@ -215,11 +206,19 @@ class Text extends ReactNative.NativeComponent<TextProps, State> {
         style: [this.props.style, {color: 'magenta'}],
       };
     }
-    if (this.context.isInAParentText) {
-      return <RCTVirtualText {...newProps} />;
-    } else {
-      return <RCTText {...newProps} />;
-    }
+    return (
+      <TextAncestor.Consumer>
+        {hasTextAncestor =>
+          hasTextAncestor ? (
+            <RCTVirtualText {...newProps} />
+          ) : (
+            <TextAncestor.Provider value={true}>
+              <RCTText {...newProps} />
+            </TextAncestor.Provider>
+          )
+        }
+      </TextAncestor.Consumer>
+    );
   }
 }
 
diff --git a/Libraries/Components/View/ViewContext.js b/Libraries/Text/TextAncestor.js
similarity index 53%
rename from Libraries/Components/View/ViewContext.js
rename to Libraries/Text/TextAncestor.js
index 81879aa35ecf..147d9763b2d6 100644
--- a/Libraries/Components/View/ViewContext.js
+++ b/Libraries/Text/TextAncestor.js
@@ -7,16 +7,12 @@
  * @flow
  * @format
  */
-'use strict';
 
-const PropTypes = require('prop-types');
+'use strict';
 
-export type ViewChildContext = {|
-  +isInAParentText: boolean,
-|};
+const React = require('React');
 
-module.exports = {
-  ViewContextTypes: {
-    isInAParentText: PropTypes.bool,
-  },
-};
+/**
+ * Whether the current element is the descendant of a <Text> element.
+ */
+module.exports = React.createContext(false);

From 3e534b9aab5156adac67762877b2457408fe8934 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 9 May 2018 00:47:48 -0700
Subject: [PATCH 0478/1109] RN: Switch `View` to `React.forwardRef`

Reviewed By: bvaughn, sophiebits

Differential Revision: D7896711

fbshipit-source-id: c10c8a14a00ac2d67605e6e4fe1a341b4688fdd8
---
 .../Animated/src/createAnimatedComponent.js   |  2 +-
 Libraries/Components/View/View.js             | 72 ++++++++-----------
 jest/mockComponent.js                         | 17 ++++-
 jest/setup.js                                 |  2 +-
 4 files changed, 45 insertions(+), 48 deletions(-)

diff --git a/Libraries/Animated/src/createAnimatedComponent.js b/Libraries/Animated/src/createAnimatedComponent.js
index d876af645c4e..a4177d65be0e 100644
--- a/Libraries/Animated/src/createAnimatedComponent.js
+++ b/Libraries/Animated/src/createAnimatedComponent.js
@@ -18,7 +18,7 @@ const invariant = require('fbjs/lib/invariant');
 
 function createAnimatedComponent(Component: any): any {
   invariant(
-    typeof Component === 'string' ||
+    typeof Component !== 'function' ||
       (Component.prototype && Component.prototype.isReactComponent),
     '`createAnimatedComponent` does not support stateless functional components; ' +
       'use a class component instead.',
diff --git a/Libraries/Components/View/View.js b/Libraries/Components/View/View.js
index 1e79f88a5483..337f77d1aae5 100644
--- a/Libraries/Components/View/View.js
+++ b/Libraries/Components/View/View.js
@@ -4,23 +4,22 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
  * @format
+ * @flow
  */
 
 'use strict';
 
 const Platform = require('Platform');
 const React = require('React');
-const ReactNative = require('ReactNative');
 const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
-const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const TextAncestor = require('TextAncestor');
 const ViewPropTypes = require('ViewPropTypes');
 
 const invariant = require('fbjs/lib/invariant');
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {NativeComponent} from 'ReactNative';
 import type {ViewProps} from 'ViewPropTypes';
 
 export type Props = ViewProps;
@@ -32,50 +31,25 @@ export type Props = ViewProps;
  *
  * @see http://facebook.github.io/react-native/docs/view.html
  */
-class View extends ReactNative.NativeComponent<Props> {
-  static propTypes = ViewPropTypes;
-
-  viewConfig = {
-    uiViewClassName: 'RCTView',
-    validAttributes: ReactNativeViewAttributes.RCTView,
-  };
-
-  /**
-   * WARNING: This method will not be used in production mode as in that mode we
-   * replace wrapper component View with generated native wrapper RCTView. Avoid
-   * adding functionality this component that you'd want to be available in both
-   * dev and prod modes.
-   */
-  render() {
-    return (
-      <TextAncestor.Consumer>
-        {hasTextAncestor => {
-          // TODO: Change iOS to behave the same as Android.
-          invariant(
-            !hasTextAncestor || Platform.OS !== 'android',
-            'Nesting of <View> within <Text> is not supported on Android.',
-          );
-          return <RCTView {...this.props} />;
-        }}
-      </TextAncestor.Consumer>
-    );
-  }
-}
-
-const RCTView = requireNativeComponent('RCTView', View, {
-  nativeOnly: {
-    nativeBackgroundAndroid: true,
-    nativeForegroundAndroid: true,
+const RCTView = requireNativeComponent(
+  'RCTView',
+  {
+    propTypes: ViewPropTypes,
+  },
+  {
+    nativeOnly: {
+      nativeBackgroundAndroid: true,
+      nativeForegroundAndroid: true,
+    },
   },
-});
+);
 
 if (__DEV__) {
   const UIManager = require('UIManager');
   const viewConfig =
     (UIManager.viewConfigs && UIManager.viewConfigs.RCTView) || {};
   for (const prop in viewConfig.nativeProps) {
-    const viewAny: any = View; // Appease flow
-    if (!viewAny.propTypes[prop] && !ReactNativeStyleAttributes[prop]) {
+    if (!ViewPropTypes[prop] && !ReactNativeStyleAttributes[prop]) {
       throw new Error(
         'View is missing propType for native prop `' + prop + '`',
       );
@@ -85,8 +59,20 @@ if (__DEV__) {
 
 let ViewToExport = RCTView;
 if (__DEV__) {
-  ViewToExport = View;
+  // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+  ViewToExport = React.forwardRef((props, ref) => (
+    <TextAncestor.Consumer>
+      {hasTextAncestor => {
+        // TODO: Change iOS to behave the same as Android.
+        invariant(
+          !hasTextAncestor || Platform.OS !== 'android',
+          'Nesting of <View> within <Text> is not supported on Android.',
+        );
+        return <RCTView {...props} ref={ref} />;
+      }}
+    </TextAncestor.Consumer>
+  ));
+  ViewToExport.displayName = 'View';
 }
 
-// No one should depend on the DEV-mode createClass View wrapper.
-module.exports = ((ViewToExport: any): typeof View);
+module.exports = ((ViewToExport: any): Class<NativeComponent<ViewProps, any>>);
diff --git a/jest/mockComponent.js b/jest/mockComponent.js
index 84c162d867f4..bdc16d805dcb 100644
--- a/jest/mockComponent.js
+++ b/jest/mockComponent.js
@@ -3,23 +3,34 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
-module.exports = moduleName => {
+module.exports = (moduleName, instanceMethods) => {
   const RealComponent = require.requireActual(moduleName);
   const React = require('react');
 
-  const Component = class extends RealComponent {
+  const SuperClass =
+    typeof RealComponent === 'function' ? RealComponent : React.Component;
+
+  const Component = class extends SuperClass {
     render() {
       const name = RealComponent.displayName || RealComponent.name;
 
       return React.createElement(
-        name.replace(/^(RCT|RK)/,''),
+        name.replace(/^(RCT|RK)/, ''),
         this.props,
         this.props.children,
       );
     }
   };
+
+  if (instanceMethods != null) {
+    Object.assign(Component.prototype, instanceMethods);
+  }
+
   return Component;
 };
diff --git a/jest/setup.js b/jest/setup.js
index b40bcebae25d..2aef9f1b39fe 100644
--- a/jest/setup.js
+++ b/jest/setup.js
@@ -38,7 +38,7 @@ jest
   .mock('Text', () => mockComponent('Text'))
   .mock('TextInput', () => mockComponent('TextInput'))
   .mock('Modal', () => mockComponent('Modal'))
-  .mock('View', () => mockComponent('View'))
+  .mock('View', () => mockComponent('View', MockNativeMethods))
   .mock('RefreshControl', () => require.requireMock('RefreshControlMock'))
   .mock('ScrollView', () => require.requireMock('ScrollViewMock'))
   .mock(

From 6a1b41643a5f5035c61a96263220d11d3462e8f2 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 9 May 2018 00:47:50 -0700
Subject: [PATCH 0479/1109] RN: Consistently Throw for <Text><View /></Text>

Reviewed By: sahrens

Differential Revision: D7898238

fbshipit-source-id: a2b74e691a116b1beae3c6bb266252a722aacbb1
---
 Libraries/Components/View/View.js   | 5 ++---
 RNTester/js/TextInputExample.ios.js | 8 --------
 2 files changed, 2 insertions(+), 11 deletions(-)

diff --git a/Libraries/Components/View/View.js b/Libraries/Components/View/View.js
index 337f77d1aae5..9694a2fb39a2 100644
--- a/Libraries/Components/View/View.js
+++ b/Libraries/Components/View/View.js
@@ -63,10 +63,9 @@ if (__DEV__) {
   ViewToExport = React.forwardRef((props, ref) => (
     <TextAncestor.Consumer>
       {hasTextAncestor => {
-        // TODO: Change iOS to behave the same as Android.
         invariant(
-          !hasTextAncestor || Platform.OS !== 'android',
-          'Nesting of <View> within <Text> is not supported on Android.',
+          !hasTextAncestor,
+          'Nesting of <View> within <Text> is not currently supported.',
         );
         return <RCTView {...props} ref={ref} />;
       }}
diff --git a/RNTester/js/TextInputExample.ios.js b/RNTester/js/TextInputExample.ios.js
index fdcddc1f793d..704278796f06 100644
--- a/RNTester/js/TextInputExample.ios.js
+++ b/RNTester/js/TextInputExample.ios.js
@@ -872,14 +872,6 @@ exports.examples = [
             style={styles.multiline}
             dataDetectorTypes="phoneNumber"
           />
-          <TextInput
-            placeholder="multiline with children"
-            multiline={true}
-            enablesReturnKeyAutomatically={true}
-            returnKeyType="go"
-            style={styles.multiline}>
-            <View style={styles.multilineChild}/>
-          </TextInput>
         </View>
       );
     }

From a1f2076aae13dd973932b0ecb90529402ab3f09f Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 9 May 2018 00:47:54 -0700
Subject: [PATCH 0480/1109] RN: Delete `mergeFast` from `Text`

Reviewed By: sahrens, TheSavior

Differential Revision: D7899406

fbshipit-source-id: 35fb14c5af3d01404896342a47af9fa280226c7f
---
 Libraries/Text/Text.js           | 35 ++++++++++++++++----------------
 Libraries/Text/TextProps.js      |  4 ++--
 Libraries/Utilities/mergeFast.js | 31 ----------------------------
 3 files changed, 19 insertions(+), 51 deletions(-)
 delete mode 100644 Libraries/Utilities/mergeFast.js

diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index d983638ac5f1..1727e8f26842 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -18,27 +18,24 @@ const Touchable = require('Touchable');
 const UIManager = require('UIManager');
 
 const createReactNativeComponentClass = require('createReactNativeComponentClass');
-const mergeFast = require('mergeFast');
 const processColor = require('processColor');
 
 import type {PressEvent} from 'CoreEventTypes';
-import type {TextProps} from 'TextProps';
+import type {PressRetentionOffset, TextProps} from 'TextProps';
 
-type State = {
+type State = {|
+  touchable: {|
+    touchState: ?string,
+    responderID: ?number,
+  |},
   isHighlighted: boolean,
-};
-
-type RectOffset = {
-  top: number,
-  left: number,
-  right: number,
-  bottom: number,
-};
+|};
 
 const PRESS_RECT_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
 
 const viewConfig = {
-  validAttributes: mergeFast(ReactNativeViewAttributes.UIView, {
+  validAttributes: {
+    ...ReactNativeViewAttributes.UIView,
     isHighlighted: true,
     numberOfLines: true,
     ellipsizeMode: true,
@@ -49,7 +46,7 @@ const viewConfig = {
     adjustsFontSizeToFit: true,
     minimumFontScale: true,
     textBreakStrategy: true,
-  }),
+  },
   uiViewClassName: 'RCTText',
 };
 
@@ -67,9 +64,10 @@ class Text extends ReactNative.NativeComponent<TextProps, State> {
     ellipsizeMode: 'tail',
   };
 
-  state = mergeFast(Touchable.Mixin.touchableGetInitialState(), {
+  state = {
+    ...Touchable.Mixin.touchableGetInitialState(),
     isHighlighted: false,
-  });
+  };
 
   viewConfig = viewConfig;
 
@@ -143,7 +141,7 @@ class Text extends ReactNative.NativeComponent<TextProps, State> {
                 this.props.onLongPress && this.props.onLongPress(e);
               };
 
-              this.touchableGetPressRectOffset = function(): RectOffset {
+              this.touchableGetPressRectOffset = function(): PressRetentionOffset {
                 return this.props.pressRetentionOffset || PRESS_RECT_OFFSET;
               };
             }
@@ -230,9 +228,10 @@ var RCTVirtualText = RCTText;
 
 if (UIManager.RCTVirtualText) {
   RCTVirtualText = createReactNativeComponentClass('RCTVirtualText', () => ({
-    validAttributes: mergeFast(ReactNativeViewAttributes.UIView, {
+    validAttributes: {
+      ...ReactNativeViewAttributes.UIView,
       isHighlighted: true,
-    }),
+    },
     uiViewClassName: 'RCTVirtualText',
   }));
 }
diff --git a/Libraries/Text/TextProps.js b/Libraries/Text/TextProps.js
index 56229632a01b..474c8fef802b 100644
--- a/Libraries/Text/TextProps.js
+++ b/Libraries/Text/TextProps.js
@@ -17,12 +17,12 @@ import type {Node} from 'react';
 import type {LayoutEvent, PressEvent} from 'CoreEventTypes';
 import type {DangerouslyImpreciseStyleProp} from 'StyleSheet';
 
-type PressRetentionOffset = {
+export type PressRetentionOffset = $ReadOnly<{|
   top: number,
   left: number,
   bottom: number,
   right: number,
-};
+|}>;
 
 /**
  * @see https://facebook.github.io/react-native/docs/text.html#reference
diff --git a/Libraries/Utilities/mergeFast.js b/Libraries/Utilities/mergeFast.js
deleted file mode 100644
index 42e357e5dbda..000000000000
--- a/Libraries/Utilities/mergeFast.js
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @flow
- */
-'use strict';
-
-/**
- * Faster version of `merge` that doesn't check its arguments and
- * also merges prototype inherited properties.
- *
- * @param {object} one Any non-null object.
- * @param {object} two Any non-null object.
- * @return {object} Merging of two objects, including prototype
- * inherited properties.
- */
-var mergeFast = function(one: Object, two: Object): Object {
-  var ret = {};
-  for (var keyOne in one) {
-    ret[keyOne] = one[keyOne];
-  }
-  for (var keyTwo in two) {
-    ret[keyTwo] = two[keyTwo];
-  }
-  return ret;
-};
-
-module.exports = mergeFast;

From 06c05e744d8af9582bde348210f254d76dae48b9 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 9 May 2018 00:47:55 -0700
Subject: [PATCH 0481/1109] RN: Cleanup `Text` Implementation

Reviewed By: sahrens, TheSavior

Differential Revision: D7901531

fbshipit-source-id: dfaba402c1c26e34e9d2df01f2bbb8c26dfcd17e
---
 Libraries/Text/Text.js | 308 ++++++++++++++++++++++-------------------
 1 file changed, 166 insertions(+), 142 deletions(-)

diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index 1727e8f26842..adde971751b7 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -7,6 +7,7 @@
  * @flow
  * @format
  */
+
 'use strict';
 
 const React = require('React');
@@ -18,17 +19,31 @@ const Touchable = require('Touchable');
 const UIManager = require('UIManager');
 
 const createReactNativeComponentClass = require('createReactNativeComponentClass');
+const nullthrows = require('fbjs/lib/nullthrows');
 const processColor = require('processColor');
 
 import type {PressEvent} from 'CoreEventTypes';
 import type {PressRetentionOffset, TextProps} from 'TextProps';
 
+type ResponseHandlers = $ReadOnly<{|
+  onStartShouldSetResponder: () => boolean,
+  onResponderGrant: (event: SyntheticEvent<>, dispatchID: string) => void,
+  onResponderMove: (event: SyntheticEvent<>) => void,
+  onResponderRelease: (event: SyntheticEvent<>) => void,
+  onResponderTerminate: (event: SyntheticEvent<>) => void,
+  onResponderTerminationRequest: () => boolean,
+|}>;
+
+type Props = TextProps;
+
 type State = {|
   touchable: {|
     touchState: ?string,
     responderID: ?number,
   |},
   isHighlighted: boolean,
+  createResponderHandlers: () => ResponseHandlers,
+  responseHandlers: ?ResponseHandlers,
 |};
 
 const PRESS_RECT_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
@@ -55,7 +70,7 @@ const viewConfig = {
  *
  * See https://facebook.github.io/react-native/docs/text.html
  */
-class Text extends ReactNative.NativeComponent<TextProps, State> {
+class Text extends ReactNative.NativeComponent<Props, State> {
   static propTypes = TextPropTypes;
 
   static defaultProps = {
@@ -64,176 +79,185 @@ class Text extends ReactNative.NativeComponent<TextProps, State> {
     ellipsizeMode: 'tail',
   };
 
+  touchableGetPressRectOffset: ?() => PressRetentionOffset;
+  touchableHandleActivePressIn: ?() => void;
+  touchableHandleActivePressOut: ?() => void;
+  touchableHandleLongPress: ?(event: PressEvent) => void;
+  touchableHandlePress: ?(event: PressEvent) => void;
+  touchableHandleResponderGrant: ?(
+    event: SyntheticEvent<>,
+    dispatchID: string,
+  ) => void;
+  touchableHandleResponderMove: ?(event: SyntheticEvent<>) => void;
+  touchableHandleResponderRelease: ?(event: SyntheticEvent<>) => void;
+  touchableHandleResponderTerminate: ?(event: SyntheticEvent<>) => void;
+  touchableHandleResponderTerminationRequest: ?() => boolean;
+
   state = {
     ...Touchable.Mixin.touchableGetInitialState(),
     isHighlighted: false,
+    createResponderHandlers: this._createResponseHandlers.bind(this),
+    responseHandlers: null,
   };
 
-  viewConfig = viewConfig;
+  static getDerivedStateFromProps(nextProps: Props, prevState: State): ?State {
+    return prevState.responseHandlers == null && isTouchable(nextProps)
+      ? {
+          ...prevState,
+          responseHandlers: prevState.createResponderHandlers(),
+        }
+      : null;
+  }
 
-  _handlers: ?Object;
+  static viewConfig = viewConfig;
 
-  _hasPressHandler(): boolean {
-    return !!this.props.onPress || !!this.props.onLongPress;
-  }
-  /**
-   * These are assigned lazily the first time the responder is set to make plain
-   * text nodes as cheap as possible.
-   */
-  touchableHandleActivePressIn: ?Function;
-  touchableHandleActivePressOut: ?Function;
-  touchableHandlePress: ?Function;
-  touchableHandleLongPress: ?Function;
-  touchableHandleResponderGrant: ?Function;
-  touchableHandleResponderMove: ?Function;
-  touchableHandleResponderRelease: ?Function;
-  touchableHandleResponderTerminate: ?Function;
-  touchableHandleResponderTerminationRequest: ?Function;
-  touchableGetPressRectOffset: ?Function;
-
-  render(): React.Element<any> {
-    let newProps = this.props;
-    if (this.props.onStartShouldSetResponder || this._hasPressHandler()) {
-      if (!this._handlers) {
-        this._handlers = {
-          onStartShouldSetResponder: (): boolean => {
-            const shouldSetFromProps =
-              this.props.onStartShouldSetResponder &&
-              this.props.onStartShouldSetResponder();
-            const setResponder = shouldSetFromProps || this._hasPressHandler();
-            if (setResponder && !this.touchableHandleActivePressIn) {
-              // Attach and bind all the other handlers only the first time a touch
-              // actually happens.
-              for (const key in Touchable.Mixin) {
-                if (typeof Touchable.Mixin[key] === 'function') {
-                  (this: any)[key] = Touchable.Mixin[key].bind(this);
-                }
-              }
-              this.touchableHandleActivePressIn = () => {
-                if (
-                  this.props.suppressHighlighting ||
-                  !this._hasPressHandler()
-                ) {
-                  return;
-                }
-                this.setState({
-                  isHighlighted: true,
-                });
-              };
-
-              this.touchableHandleActivePressOut = () => {
-                if (
-                  this.props.suppressHighlighting ||
-                  !this._hasPressHandler()
-                ) {
-                  return;
-                }
-                this.setState({
-                  isHighlighted: false,
-                });
-              };
-
-              this.touchableHandlePress = (e: PressEvent) => {
-                this.props.onPress && this.props.onPress(e);
-              };
-
-              this.touchableHandleLongPress = (e: PressEvent) => {
-                this.props.onLongPress && this.props.onLongPress(e);
-              };
-
-              this.touchableGetPressRectOffset = function(): PressRetentionOffset {
-                return this.props.pressRetentionOffset || PRESS_RECT_OFFSET;
-              };
-            }
-            return setResponder;
-          },
-          onResponderGrant: function(e: SyntheticEvent<>, dispatchID: string) {
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            this.touchableHandleResponderGrant(e, dispatchID);
-            this.props.onResponderGrant &&
-              this.props.onResponderGrant.apply(this, arguments);
-          }.bind(this),
-          onResponderMove: function(e: SyntheticEvent<>) {
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            this.touchableHandleResponderMove(e);
-            this.props.onResponderMove &&
-              this.props.onResponderMove.apply(this, arguments);
-          }.bind(this),
-          onResponderRelease: function(e: SyntheticEvent<>) {
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            this.touchableHandleResponderRelease(e);
-            this.props.onResponderRelease &&
-              this.props.onResponderRelease.apply(this, arguments);
-          }.bind(this),
-          onResponderTerminate: function(e: SyntheticEvent<>) {
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            this.touchableHandleResponderTerminate(e);
-            this.props.onResponderTerminate &&
-              this.props.onResponderTerminate.apply(this, arguments);
-          }.bind(this),
-          onResponderTerminationRequest: function(): boolean {
-            // Allow touchable or props.onResponderTerminationRequest to deny
-            // the request
-            // $FlowFixMe TouchableMixin handlers couldn't actually be null
-            var allowTermination = this.touchableHandleResponderTerminationRequest();
-            if (allowTermination && this.props.onResponderTerminationRequest) {
-              allowTermination = this.props.onResponderTerminationRequest.apply(
-                this,
-                arguments,
-              );
-            }
-            return allowTermination;
-          }.bind(this),
-        };
-      }
-      newProps = {
-        ...this.props,
-        ...this._handlers,
+  render(): React.Node {
+    let props = this.props;
+    if (isTouchable(props)) {
+      props = {
+        ...props,
+        ...this.state.responseHandlers,
         isHighlighted: this.state.isHighlighted,
       };
     }
-    if (newProps.selectionColor != null) {
-      newProps = {
-        ...newProps,
-        selectionColor: processColor(newProps.selectionColor),
+    if (props.selectionColor != null) {
+      props = {
+        ...props,
+        selectionColor: processColor(props.selectionColor),
       };
     }
-    if (Touchable.TOUCH_TARGET_DEBUG && newProps.onPress) {
-      newProps = {
-        ...newProps,
-        style: [this.props.style, {color: 'magenta'}],
-      };
+    if (__DEV__) {
+      if (Touchable.TOUCH_TARGET_DEBUG && props.onPress != null) {
+        props = {
+          ...props,
+          style: [props.style, {color: 'magenta'}],
+        };
+      }
     }
     return (
       <TextAncestor.Consumer>
         {hasTextAncestor =>
           hasTextAncestor ? (
-            <RCTVirtualText {...newProps} />
+            <RCTVirtualText {...props} />
           ) : (
             <TextAncestor.Provider value={true}>
-              <RCTText {...newProps} />
+              <RCTText {...props} />
             </TextAncestor.Provider>
           )
         }
       </TextAncestor.Consumer>
     );
   }
+
+  _createResponseHandlers(): ResponseHandlers {
+    return {
+      onStartShouldSetResponder: (): boolean => {
+        const {onStartShouldSetResponder} = this.props;
+        const shouldSetResponder =
+          (onStartShouldSetResponder == null
+            ? false
+            : onStartShouldSetResponder()) || isTouchable(this.props);
+
+        if (shouldSetResponder) {
+          this._attachTouchHandlers();
+        }
+        return shouldSetResponder;
+      },
+      onResponderGrant: (event: SyntheticEvent<>, dispatchID: string): void => {
+        nullthrows(this.touchableHandleResponderGrant)(event, dispatchID);
+        if (this.props.onResponderGrant != null) {
+          this.props.onResponderGrant.apply(this, arguments);
+        }
+      },
+      onResponderMove: (event: SyntheticEvent<>): void => {
+        nullthrows(this.touchableHandleResponderMove)(event);
+        if (this.props.onResponderMove != null) {
+          this.props.onResponderMove.apply(this, arguments);
+        }
+      },
+      onResponderRelease: (event: SyntheticEvent<>): void => {
+        nullthrows(this.touchableHandleResponderRelease)(event);
+        if (this.props.onResponderRelease != null) {
+          this.props.onResponderRelease.apply(this, arguments);
+        }
+      },
+      onResponderTerminate: (event: SyntheticEvent<>): void => {
+        nullthrows(this.touchableHandleResponderTerminate)(event);
+        if (this.props.onResponderTerminate != null) {
+          this.props.onResponderTerminate.apply(this, arguments);
+        }
+      },
+      onResponderTerminationRequest: (): boolean => {
+        const {onResponderTerminationRequest} = this.props;
+        if (!nullthrows(this.touchableHandleResponderTerminationRequest)()) {
+          return false;
+        }
+        if (onResponderTerminationRequest == null) {
+          return true;
+        }
+        return onResponderTerminationRequest();
+      },
+    };
+  }
+
+  /**
+   * Lazily attaches Touchable.Mixin handlers.
+   */
+  _attachTouchHandlers(): void {
+    if (this.touchableGetPressRectOffset != null) {
+      return;
+    }
+    for (const key in Touchable.Mixin) {
+      if (typeof Touchable.Mixin[key] === 'function') {
+        (this: any)[key] = Touchable.Mixin[key].bind(this);
+      }
+    }
+    this.touchableHandleActivePressIn = (): void => {
+      if (!this.props.suppressHighlighting && isTouchable(this.props)) {
+        this.setState({isHighlighted: true});
+      }
+    };
+    this.touchableHandleActivePressOut = (): void => {
+      if (!this.props.suppressHighlighting && isTouchable(this.props)) {
+        this.setState({isHighlighted: false});
+      }
+    };
+    this.touchableHandlePress = (event: PressEvent): void => {
+      if (this.props.onPress != null) {
+        this.props.onPress(event);
+      }
+    };
+    this.touchableHandleLongPress = (event: PressEvent): void => {
+      if (this.props.onLongPress != null) {
+        this.props.onLongPress(event);
+      }
+    };
+    this.touchableGetPressRectOffset = (): PressRetentionOffset =>
+      this.props.pressRetentionOffset == null
+        ? PRESS_RECT_OFFSET
+        : this.props.pressRetentionOffset;
+  }
 }
 
-var RCTText = createReactNativeComponentClass(
+const isTouchable = (props: Props): boolean =>
+  props.onPress != null ||
+  props.onLongPress != null ||
+  props.onStartShouldSetResponder != null;
+
+const RCTText = createReactNativeComponentClass(
   viewConfig.uiViewClassName,
   () => viewConfig,
 );
-var RCTVirtualText = RCTText;
-
-if (UIManager.RCTVirtualText) {
-  RCTVirtualText = createReactNativeComponentClass('RCTVirtualText', () => ({
-    validAttributes: {
-      ...ReactNativeViewAttributes.UIView,
-      isHighlighted: true,
-    },
-    uiViewClassName: 'RCTVirtualText',
-  }));
-}
+
+const RCTVirtualText =
+  UIManager.RCTVirtualText == null
+    ? RCTText
+    : createReactNativeComponentClass('RCTVirtualText', () => ({
+        validAttributes: {
+          ...ReactNativeViewAttributes.UIView,
+          isHighlighted: true,
+        },
+        uiViewClassName: 'RCTVirtualText',
+      }));
 
 module.exports = Text;

From e708010d18f938e2d6b6424cfc9485d8e5dd2800 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 9 May 2018 00:47:57 -0700
Subject: [PATCH 0482/1109] RN: Switch `Text` to `React.forwardRef`

Reviewed By: sahrens

Differential Revision: D7902262

fbshipit-source-id: 218f95cde6d77f21d9362a2f2bd47c5f83d5ee15
---
 .../TouchableHighlight-test.js.snap           |  3 ---
 Libraries/Text/Text.js                        | 26 +++++++++++++------
 jest/mockComponent.js                         |  4 +++
 jest/setup.js                                 |  2 +-
 4 files changed, 23 insertions(+), 12 deletions(-)

diff --git a/Libraries/Components/Touchable/__tests__/__snapshots__/TouchableHighlight-test.js.snap b/Libraries/Components/Touchable/__tests__/__snapshots__/TouchableHighlight-test.js.snap
index 4596f0307d0e..6028d74aaa8a 100644
--- a/Libraries/Components/Touchable/__tests__/__snapshots__/TouchableHighlight-test.js.snap
+++ b/Libraries/Components/Touchable/__tests__/__snapshots__/TouchableHighlight-test.js.snap
@@ -22,9 +22,6 @@ exports[`TouchableHighlight renders correctly 1`] = `
   tvParallaxProperties={undefined}
 >
   <Text
-    accessible={true}
-    allowFontScaling={true}
-    ellipsizeMode="tail"
     style={null}
   >
     Touchable
diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index adde971751b7..1dcac7c1a759 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -11,7 +11,6 @@
 'use strict';
 
 const React = require('React');
-const ReactNative = require('ReactNative');
 const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const TextAncestor = require('TextAncestor');
 const TextPropTypes = require('TextPropTypes');
@@ -23,6 +22,7 @@ const nullthrows = require('fbjs/lib/nullthrows');
 const processColor = require('processColor');
 
 import type {PressEvent} from 'CoreEventTypes';
+import type {NativeComponent} from 'ReactNative';
 import type {PressRetentionOffset, TextProps} from 'TextProps';
 
 type ResponseHandlers = $ReadOnly<{|
@@ -34,7 +34,10 @@ type ResponseHandlers = $ReadOnly<{|
   onResponderTerminationRequest: () => boolean,
 |}>;
 
-type Props = TextProps;
+type Props = $ReadOnly<{
+  ...TextProps,
+  forwardedRef: ?React.Ref<NativeComponent<TextProps, any>>,
+}>;
 
 type State = {|
   touchable: {|
@@ -70,9 +73,7 @@ const viewConfig = {
  *
  * See https://facebook.github.io/react-native/docs/text.html
  */
-class Text extends ReactNative.NativeComponent<Props, State> {
-  static propTypes = TextPropTypes;
-
+class TouchableText extends React.Component<Props, State> {
   static defaultProps = {
     accessible: true,
     allowFontScaling: true,
@@ -138,10 +139,10 @@ class Text extends ReactNative.NativeComponent<Props, State> {
       <TextAncestor.Consumer>
         {hasTextAncestor =>
           hasTextAncestor ? (
-            <RCTVirtualText {...props} />
+            <RCTVirtualText {...props} ref={props.forwardedRef} />
           ) : (
             <TextAncestor.Provider value={true}>
-              <RCTText {...props} />
+              <RCTText {...props} ref={props.forwardedRef} />
             </TextAncestor.Provider>
           )
         }
@@ -260,4 +261,13 @@ const RCTVirtualText =
         uiViewClassName: 'RCTVirtualText',
       }));
 
-module.exports = Text;
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+const Text = React.forwardRef((props, ref) => (
+  <TouchableText {...props} forwardedRef={ref} />
+));
+Text.displayName = 'Text';
+
+// TODO: Deprecate this.
+Text.propTypes = TextPropTypes;
+
+module.exports = ((Text: any): NativeComponent<TextProps, any>);
diff --git a/jest/mockComponent.js b/jest/mockComponent.js
index bdc16d805dcb..e22c34ccaa43 100644
--- a/jest/mockComponent.js
+++ b/jest/mockComponent.js
@@ -28,6 +28,10 @@ module.exports = (moduleName, instanceMethods) => {
     }
   };
 
+  if (RealComponent.propTypes != null) {
+    Component.propTypes = RealComponent.propTypes;
+  }
+
   if (instanceMethods != null) {
     Object.assign(Component.prototype, instanceMethods);
   }
diff --git a/jest/setup.js b/jest/setup.js
index 2aef9f1b39fe..18cb7dfbddd7 100644
--- a/jest/setup.js
+++ b/jest/setup.js
@@ -35,7 +35,7 @@ jest.setMock('ErrorUtils', require('ErrorUtils'));
 jest
   .mock('InitializeCore', () => {})
   .mock('Image', () => mockComponent('Image'))
-  .mock('Text', () => mockComponent('Text'))
+  .mock('Text', () => mockComponent('Text', MockNativeMethods))
   .mock('TextInput', () => mockComponent('TextInput'))
   .mock('Modal', () => mockComponent('Modal'))
   .mock('View', () => mockComponent('View', MockNativeMethods))

From c18cf5bd4a130534e1019722453443c5e610a406 Mon Sep 17 00:00:00 2001
From: Payton Yao <payton.yao@gmail.com>
Date: Wed, 9 May 2018 10:26:06 -0700
Subject: [PATCH 0483/1109] Prevent unintended VirtualizedList high priority
 rendering

Summary:
VirtualizedList sets high priority rendering when scrolled to the top of a list even if the bottom of the rendered list is still far away and there's nothing further to render above. This causes severe non-responsiveness while dozens of items are waiting to be rendered and user inputs can't get through.

The fix is simply to not consider it high priority to render more items when we reach the top and the first item has already been rendered, or when we reach the bottom and the last item has been rendered.

The code change just splits the two cases (hitting the top and bottom) instead of combining them into one.

I wrote a small application that switches between two FlatLists.

Demo of the original VirtualizedList
<img src="https://user-images.githubusercontent.com/3090032/39456709-2c87069e-4d1b-11e8-8535-5bda6d59400c.gif" width="270" height="480">

I'm clicking pretty often on the button, but you can see that it only switches lists a split second after the rendering is all done because the javascript thread was being blocked.

Demo of the fixed VirtualizedList
<img src="https://user-images.githubusercontent.com/3090032/39456844-00312448-4d1c-11e8-805f-cbe17aa3f95e.gif" width="270" height="480">
You can see this one is significantly more responsive than the previous one.

The source code for the demo application is available [here](https://gist.github.com/jabbawookiees/ba93a4e7b4f9b8f3acbc157e4fd04877)

[ GENERAL ] [ ENHANCEMENT ] [ Libraries/Lists/VirtualizedList.js  ] - Prevent high priority rendering at the top or bottom of a list.
Closes https://github.com/facebook/react-native/pull/19081

Differential Revision: D7933994

Pulled By: sahrens

fbshipit-source-id: 13c9f73baeb3487620b720854a753287ac0aa1fa
---
 Libraries/Lists/VirtualizedList.js | 24 ++++++++++++++----------
 1 file changed, 14 insertions(+), 10 deletions(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index ca6d9fc7fe56..7c54eba55c39 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -1344,19 +1344,23 @@ class VirtualizedList extends React.PureComponent<Props, State> {
     const {offset, visibleLength, velocity} = this._scrollMetrics;
     const itemCount = this.props.getItemCount(this.props.data);
     let hiPri = false;
-    if (first > 0 || last < itemCount - 1) {
+    const scrollingThreshold =
+      /* $FlowFixMe(>=0.63.0 site=react_native_fb) This comment suppresses an
+       * error found when Flow v0.63 was deployed. To see the error delete
+       * this comment and run Flow. */
+      this.props.onEndReachedThreshold * visibleLength / 2;
+    // Mark as high priority if we're close to the start of the first item
+    // But only if there are items before the first rendered item
+    if (first > 0) {
       const distTop = offset - this._getFrameMetricsApprox(first).offset;
+      hiPri = hiPri || distTop < 0 || (velocity < -2 && distTop < scrollingThreshold);
+    }
+    // Mark as high priority if we're close to the end of the last item
+    // But only if there are items after the last rendered item
+    if (last < itemCount - 1) {
       const distBottom =
         this._getFrameMetricsApprox(last).offset - (offset + visibleLength);
-      const scrollingThreshold =
-        /* $FlowFixMe(>=0.63.0 site=react_native_fb) This comment suppresses an
-         * error found when Flow v0.63 was deployed. To see the error delete
-         * this comment and run Flow. */
-        this.props.onEndReachedThreshold * visibleLength / 2;
-      hiPri =
-        Math.min(distTop, distBottom) < 0 ||
-        (velocity < -2 && distTop < scrollingThreshold) ||
-        (velocity > 2 && distBottom < scrollingThreshold);
+      hiPri = hiPri || distBottom < 0 || (velocity > 2 && distBottom < scrollingThreshold);
     }
     // Only trigger high-priority updates if we've actually rendered cells,
     // and with that size estimate, accurately compute how many cells we should render.

From 16b955bd1f6b321cbe88cc628c5e8bdd1ba57cc2 Mon Sep 17 00:00:00 2001
From: Andrew Jack <me@andrewjack.uk>
Date: Wed, 9 May 2018 13:04:40 -0700
Subject: [PATCH 0484/1109] Fix Android modal crash:
 android.view.WindowManager$BadTokenException

Summary:
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

Fixes a crash with the Android Dialog. This occurs when the Activity is finishing or has been removed and React Native requests the modal to be shown.

Stacktrace here:
```
Caused by android.view.WindowManager$BadTokenException: Unable to add window -- token android.os.BinderProxy@f125ea3 is not valid; is your activity running?
       at android.view.ViewRootImpl.setView(ViewRootImpl.java:683)
       at android.view.WindowManagerGlobal.addView(WindowManagerGlobal.java:319)
       at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:85)
       at android.app.Dialog.show(Dialog.java:326)
       at com.facebook.react.views.modal.ReactModalHostView.showOrUpdate(ReactModalHostView.java:256)
       at com.facebook.react.views.modal.ReactModalHostManager.onAfterUpdateTransaction(ReactModalHostManager.java:107)
       at com.facebook.react.views.modal.ReactModalHostManager.onAfterUpdateTransaction(ReactModalHostManager.java:28)
       at com.facebook.react.uimanager.ViewManager.updateProperties(ViewManager.java:35)
       at com.facebook.react.uimanager.NativeViewHierarchyManager.createView(NativeViewHierarchyManager.java:233)
       at com.facebook.react.uimanager.UIViewOperationQueue$CreateViewOperation.execute(UIViewOperationQueue.java:153)
       at com.facebook.react.uimanager.UIViewOperationQueue$1.run(UIViewOperationQueue.java:816)
       at com.facebook.react.uimanager.UIViewOperationQueue.flushPendingBatches(UIViewOperationQueue.java:929)
       at com.facebook.react.uimanager.UIViewOperationQueue.access$2100(UIViewOperationQueue.java:47)
       at com.facebook.react.uimanager.UIViewOperationQueue$2.runGuarded(UIViewOperationQueue.java:887)
       at com.facebook.react.bridge.GuardedRunnable.run(GuardedRunnable.java:21)
       at android.os.Handler.handleCallback(Handler.java:815)
       at android.os.Handler.dispatchMessage(Handler.java:104)
       at android.os.Looper.loop(Looper.java:207)
       at android.app.ActivityThread.main(ActivityThread.java:5728)
       at java.lang.reflect.Method.invoke(Method.java)
       at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:789)
       at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:679)
```

Related issues: #18570 & #18634

mdvacca added to this file in https://github.com/facebook/react-native/commit/e5c2a66897b9c562c549e63adcf70783ea34c418
Doesn't look like the issue was introduced in the above change, but it masks the issue. The wrapping if block should not allow a null activity to display a dialog.

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Run sample app on Android and display dialog when app is about to close.

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [BUGFIX] [Modal] - Fix Android BadTokenException crash

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18996

Differential Revision: D7938147

Pulled By: hramos

fbshipit-source-id: f4ffd1746304d6184d727339072a7e926ffdaf39
---
 .../java/com/facebook/react/views/modal/ReactModalHostView.java | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
index 00eac510ab8f..ab0491fe4619 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
@@ -250,7 +250,7 @@ public boolean onKey(DialogInterface dialog, int keyCode, KeyEvent event) {
     if (mHardwareAccelerated) {
       mDialog.getWindow().addFlags(WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED);
     }
-    if (currentActivity == null || !currentActivity.isFinishing()) {
+    if (currentActivity != null && !currentActivity.isFinishing()) {
       mDialog.show();
     }
   }

From 8799047dd0bc8dd93f05fa97d4b9a59f7dfeb324 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Wed, 9 May 2018 13:09:44 -0700
Subject: [PATCH 0485/1109] Fix Modal + FlatList scrolling

Summary:
`FlatList` (actually `VirtualizedList`) allows recursive nesting of itself for easy and complex composition of lists such that it can support seemless virtualization and VPV events. It does this by only rendering a `ScrollView` for the outermost `VirtualizedList` and simply stacking `View`s for all the internal ones.

However, if a `Modal` is in a `FlatList` and also hosts a `FlatList`, e.g.:
```
<FlatList ListFooterComponent={<Modal><Foo /></Modal>} />
```
Then React context will propogate through to the inner `FlatList` and cause it to render as a plain `View`. Because the `Modal` actually portals the views into a different native hierarchy, one without a `ScrollView`, the `FlatList` won't scroll as expected.

The fix is to wipe out the context - not sure if there is a better way, but this doesn't seem terrible.

Differential Revision: D7863625

fbshipit-source-id: 38f41d72ed32b9f0eb1c9c82893f21d83a83f9ad
---
 Libraries/Modal/Modal.js | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/Libraries/Modal/Modal.js b/Libraries/Modal/Modal.js
index b1cc4a1cb7bb..52ed8c7a2b9e 100644
--- a/Libraries/Modal/Modal.js
+++ b/Libraries/Modal/Modal.js
@@ -129,6 +129,18 @@ class Modal extends React.Component<Object> {
     this._identifier = uniqueModalIdentifier++;
   }
 
+  static childContextTypes = {
+    virtualizedList: PropTypes.object,
+  };
+
+  getChildContext() {
+    // Reset the context so VirtualizedList doesn't get confused by nesting
+    // in the React tree that doesn't reflect the native component heirarchy.
+    return {
+      virtualizedList: null,
+    };
+  }
+
   componentDidMount() {
     if (ModalEventEmitter) {
       this._eventSubscription = ModalEventEmitter.addListener(

From 11cc7be821683e258b3adf5d09f46e0b54fb10b7 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 9 May 2018 15:18:18 -0700
Subject: [PATCH 0486/1109] RN: Switch `ProgressBarAndroid` to
 `React.forwardRef`

Reviewed By: sahrens

Differential Revision: D7904339

fbshipit-source-id: a4fe54acee7af12f1bc9b7c0d5e02a690f57ca0d
---
 .../ProgressBarAndroid.android.js             | 21 ++++++++++++-------
 1 file changed, 14 insertions(+), 7 deletions(-)

diff --git a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
index db20d579db0a..9ee432f56bd5 100644
--- a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
+++ b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -30,7 +32,9 @@ const indeterminateType = function(props, propName, componentName, ...rest) {
     const indeterminate = props[propName];
     const styleAttr = props.styleAttr;
     if (!indeterminate && styleAttr !== 'Horizontal') {
-      return new Error('indeterminate=false is only valid for styleAttr=Horizontal');
+      return new Error(
+        'indeterminate=false is only valid for styleAttr=Horizontal',
+      );
     }
   };
 
@@ -38,8 +42,8 @@ const indeterminateType = function(props, propName, componentName, ...rest) {
 };
 
 /**
- * React component that wraps the Android-only `ProgressBar`. This component is used to indicate
- * that the app is loading or there is some activity in the app.
+ * React component that wraps the Android-only `ProgressBar`. This component is
+ * used to indicate that the app is loading or there is activity in the app.
  *
  * Example:
  *
@@ -60,7 +64,7 @@ const indeterminateType = function(props, propName, componentName, ...rest) {
  * },
  * ```
  */
-class ProgressBarAndroid extends ReactNative.NativeComponent {
+class ProgressBarAndroid extends React.Component {
   static propTypes = {
     ...ViewPropTypes,
 
@@ -106,7 +110,8 @@ class ProgressBarAndroid extends ReactNative.NativeComponent {
   };
 
   render() {
-    return <AndroidProgressBar {...this.props} />;
+    const {forwardedRef, ...props} = this.props;
+    return <AndroidProgressBar {...props} ref={forwardedRef} />;
   }
 }
 
@@ -117,7 +122,9 @@ const AndroidProgressBar = requireNativeComponent(
     nativeOnly: {
       animating: true,
     },
-  }
+  },
 );
 
-module.exports = ProgressBarAndroid;
+module.exports = React.forwardRef((props, ref) => (
+  <ProgressBarAndroid {...props} forwardedRef={ref} />
+));

From 522640cf3aebc30580dd492d8c4eb863dac3d8b4 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Wed, 9 May 2018 15:51:30 -0700
Subject: [PATCH 0487/1109] OSS exclude Xcode artifacts in ReactCommon subdir

Summary: ReactCommon subdir is supposed to be focused on C++, so Xcode projects shouldn't creep in.

Reviewed By: PeteTheHeat

Differential Revision: D7939858

fbshipit-source-id: 2e90491bdaec92829485aded071f74d004b24b21
---
 .gitignore | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/.gitignore b/.gitignore
index 6b290712dbd6..1b46fc1ee1ba 100644
--- a/.gitignore
+++ b/.gitignore
@@ -66,3 +66,7 @@ package-lock.json
 
 /coverage
 /third-party
+
+# ReactCommon subdir shouldn't have Xcode project
+/ReactCommon/**/*.xcodeproj
+

From d11fdcfb9305a57d0256aad045624a5a06c0077c Mon Sep 17 00:00:00 2001
From: Michael Schneider <mischneider1@gmail.com>
Date: Wed, 9 May 2018 20:16:30 -0700
Subject: [PATCH 0488/1109] Prevent console logging on iOS 11.3+ within
 WebSocket

Summary:
Fixes Xcode console output for web socket connections. Apple uses OSLog for logging within libnetworking starting 11.3+. The old way we hook into logging to prevent it will not work anymore.

Let's hook into `__nwlog_pack` that is exclusively used by libnetworking and prevent the logging in there.
Closes https://github.com/facebook/react-native/pull/18948

Reviewed By: fkgozali

Differential Revision: D7940969

Pulled By: mmmulani

fbshipit-source-id: a61beea34377044bfad7e3c446b2ec1138d6d1f5
---
 .../WebSocket/RCTReconnectingWebSocket.m      | 28 +++++++++++++++++++
 1 file changed, 28 insertions(+)

diff --git a/Libraries/WebSocket/RCTReconnectingWebSocket.m b/Libraries/WebSocket/RCTReconnectingWebSocket.m
index 04e5dee57b67..55ed86f7b229 100644
--- a/Libraries/WebSocket/RCTReconnectingWebSocket.m
+++ b/Libraries/WebSocket/RCTReconnectingWebSocket.m
@@ -19,6 +19,29 @@
 
 #if RCT_DEV // Only supported in dev mode
 
+#if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 100300 /* __IPHONE_10_3 */
+
+// From https://github.com/apple/swift/blob/ad40c770bfe372f879b530443a3d94761fe258a6/stdlib/public/SDK/os/os_log.m
+typedef struct os_log_pack_s {
+  uint64_t olp_continuous_time;
+  struct timespec olp_wall_time;
+  const void *olp_mh;
+  const void *olp_pc;
+  const char *olp_format;
+  uint8_t olp_data[0];
+} os_log_pack_s, *os_log_pack_t;
+
+static void (*orig__nwlog_pack)(os_log_pack_t pack, os_log_type_t logType);
+
+static void my__nwlog_pack(os_log_pack_t pack, os_log_type_t logType)
+{
+  if (logType == OS_LOG_TYPE_ERROR && strstr(pack->olp_format, "Connection has no connected handler") == NULL) {
+    orig__nwlog_pack(pack, logType);
+  }
+}
+
+#endif /* __IPHONE_10_3 */
+
 static void (*orig_nwlog_legacy_v)(int, char*, va_list);
 
 static void my_nwlog_legacy_v(int level, char *format, va_list args) {
@@ -63,6 +86,11 @@ + (void)load
     rebind_symbols((struct rebinding[1]){
       {"nwlog_legacy_v", my_nwlog_legacy_v, (void *)&orig_nwlog_legacy_v}
     }, 1);
+#if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 100300 /* __IPHONE_10_3 */
+    rebind_symbols((struct rebinding[1]){
+      {"__nwlog_pack", my__nwlog_pack, (void *)&orig__nwlog_pack}
+    }, 1);
+#endif /* __IPHONE_10_3 */
 #if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
     rebind_symbols((struct rebinding[1]){
       {"_os_log_error_impl", my_os_log_error_impl, (void *)&orig_os_log_error_impl}

From ef258b0106652e9cd60f41058d610865251559fa Mon Sep 17 00:00:00 2001
From: Marc Horowitz <mhorowitz@fb.com>
Date: Wed, 9 May 2018 22:01:34 -0700
Subject: [PATCH 0489/1109] Remove unnecessary #includes to reduce dependencies

Reviewed By: davidaurelio

Differential Revision: D7803909

fbshipit-source-id: 2ccafdbfcb786c4c5f703714fb0c92cda1026cef
---
 ReactAndroid/src/main/jni/react/jni/JInspector.cpp | 1 -
 ReactAndroid/src/main/jni/react/jni/OnLoad.cpp     | 5 -----
 ReactCommon/cxxreact/JSModulesUnbundle.h           | 7 +++++--
 ReactCommon/cxxreact/RAMBundleRegistry.h           | 3 +--
 4 files changed, 6 insertions(+), 10 deletions(-)

diff --git a/ReactAndroid/src/main/jni/react/jni/JInspector.cpp b/ReactAndroid/src/main/jni/react/jni/JInspector.cpp
index 47000279487e..1d326e3e7337 100644
--- a/ReactAndroid/src/main/jni/react/jni/JInspector.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JInspector.cpp
@@ -1,7 +1,6 @@
 // Copyright 2004-present Facebook. All Rights Reserved.
 
 #include "JInspector.h"
-#include <jschelpers/JavaScriptCore.h>
 
 #ifdef WITH_INSPECTOR
 
diff --git a/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp b/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
index 81cc8f334196..7e7184e71124 100644
--- a/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
@@ -2,14 +2,9 @@
 
 #include <string>
 
-#include <jschelpers/JSCHelpers.h>
-#include <cxxreact/JSCExecutor.h>
-#include <cxxreact/Platform.h>
 #include <fb/fbjni.h>
 #include <fb/glog_init.h>
 #include <fb/log.h>
-#include <folly/dynamic.h>
-#include <jschelpers/Value.h>
 
 #include "AndroidJSCFactory.h"
 #include "CatalystInstanceImpl.h"
diff --git a/ReactCommon/cxxreact/JSModulesUnbundle.h b/ReactCommon/cxxreact/JSModulesUnbundle.h
index bbf3a6c8d8c0..83a997f5495d 100644
--- a/ReactCommon/cxxreact/JSModulesUnbundle.h
+++ b/ReactCommon/cxxreact/JSModulesUnbundle.h
@@ -7,12 +7,11 @@
 #include <stdexcept>
 
 #include <folly/Conv.h>
-#include <jschelpers/noncopyable.h>
 
 namespace facebook {
 namespace react {
 
-class JSModulesUnbundle : noncopyable {
+class JSModulesUnbundle {
   /**
    * Represents the set of JavaScript modules that the application consists of.
    * The source code of each module can be retrieved by module ID.
@@ -31,8 +30,12 @@ class JSModulesUnbundle : noncopyable {
     std::string name;
     std::string code;
   };
+  JSModulesUnbundle() {}
   virtual ~JSModulesUnbundle() {}
   virtual Module getModule(uint32_t moduleId) const = 0;
+
+private:
+  JSModulesUnbundle(const JSModulesUnbundle&) = delete;
 };
 
 }
diff --git a/ReactCommon/cxxreact/RAMBundleRegistry.h b/ReactCommon/cxxreact/RAMBundleRegistry.h
index 9fb546066bed..6314dce036ed 100644
--- a/ReactCommon/cxxreact/RAMBundleRegistry.h
+++ b/ReactCommon/cxxreact/RAMBundleRegistry.h
@@ -9,7 +9,6 @@
 #include <utility>
 
 #include <cxxreact/JSModulesUnbundle.h>
-#include <jschelpers/noncopyable.h>
 
 #ifndef RN_EXPORT
 #define RN_EXPORT __attribute__((visibility("default")))
@@ -18,7 +17,7 @@
 namespace facebook {
 namespace react {
 
-class RN_EXPORT RAMBundleRegistry : noncopyable {
+class RN_EXPORT RAMBundleRegistry {
 public:
   constexpr static uint32_t MAIN_BUNDLE_ID = 0;
 

From d1d09c208acb623b3759d604a1e90d9faca28eb1 Mon Sep 17 00:00:00 2001
From: Marc Horowitz <mhorowitz@fb.com>
Date: Wed, 9 May 2018 22:01:36 -0700
Subject: [PATCH 0490/1109] Remove unused JS Sampling Profiler code

Reviewed By: cwdick

Differential Revision: D7803915

fbshipit-source-id: 3edb42d449ff7b272f7d25ac8f16a646839f8c20
---
 .../react/devsupport/DevServerHelper.java     |  7 ---
 .../devsupport/DevSupportManagerImpl.java     | 23 --------
 .../facebook/react/packagerconnection/BUCK    |  3 +-
 .../SamplingProfilerPackagerMethod.java       | 53 -------------------
 .../main/jni/packagerconnection/Android.mk    | 29 ----------
 .../src/main/jni/packagerconnection/BUCK      | 35 ------------
 .../JSPackagerClientResponder.cpp             | 32 -----------
 .../JSPackagerClientResponder.h               | 22 --------
 .../main/jni/packagerconnection/OnLoad.cpp    | 17 ------
 .../SamplingProfilerJniMethod.cpp             | 53 -------------------
 .../SamplingProfilerJniMethod.h               | 33 ------------
 11 files changed, 1 insertion(+), 306 deletions(-)
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/packagerconnection/SamplingProfilerPackagerMethod.java
 delete mode 100644 ReactAndroid/src/main/jni/packagerconnection/Android.mk
 delete mode 100644 ReactAndroid/src/main/jni/packagerconnection/BUCK
 delete mode 100644 ReactAndroid/src/main/jni/packagerconnection/JSPackagerClientResponder.cpp
 delete mode 100644 ReactAndroid/src/main/jni/packagerconnection/JSPackagerClientResponder.h
 delete mode 100644 ReactAndroid/src/main/jni/packagerconnection/OnLoad.cpp
 delete mode 100644 ReactAndroid/src/main/jni/packagerconnection/SamplingProfilerJniMethod.cpp
 delete mode 100644 ReactAndroid/src/main/jni/packagerconnection/SamplingProfilerJniMethod.h

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
index f0638b0b41c2..3fb603f9c519 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
@@ -81,7 +81,6 @@ public interface PackagerCommandListener {
     void onPackagerReloadCommand();
     void onPackagerDevMenuCommand();
     void onCaptureHeapCommand(final Responder responder);
-    void onPokeSamplingProfilerCommand(final Responder responder);
   }
 
   public interface SymbolicationListener {
@@ -163,12 +162,6 @@ public void onRequest(@Nullable Object params, Responder responder) {
             commandListener.onCaptureHeapCommand(responder);
           }
         });
-        handlers.put("pokeSamplingProfiler", new RequestOnlyHandler() {
-          @Override
-          public void onRequest(@Nullable Object params, Responder responder) {
-            commandListener.onPokeSamplingProfilerCommand(responder);
-          }
-        });
         handlers.putAll(new FileIoHandler().handlers());
 
         ConnectionCallback onPackagerConnectedCallback =
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
index 241bd0dbf1dd..b951ef2ff222 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
@@ -841,29 +841,6 @@ public void run() {
     });
   }
 
-  @Override
-  public void onPokeSamplingProfilerCommand(final Responder responder) {
-    UiThreadUtil.runOnUiThread(new Runnable() {
-      @Override
-      public void run() {
-        if (mCurrentContext == null) {
-          responder.error("JSCContext is missing, unable to profile");
-          return;
-        }
-        try {
-          JavaScriptContextHolder jsContext = mCurrentContext.getJavaScriptContextHolder();
-          synchronized (jsContext) {
-            Class clazz = Class.forName("com.facebook.react.packagerconnection.SamplingProfilerPackagerMethod");
-            RequestHandler handler = (RequestHandler)clazz.getConstructor(long.class).newInstance(jsContext.get());
-            handler.onRequest(null, responder);
-          }
-        } catch (Exception e) {
-          // Module not present
-        }
-      }
-    });
-  }
-
   private void handleCaptureHeap(final Responder responder) {
     if (mCurrentContext == null) {
       return;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/BUCK b/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/BUCK
index 540e9b3496c4..3b27ea6f3626 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/BUCK
@@ -4,7 +4,6 @@ rn_android_library(
     name = "packagerconnection",
     srcs = glob(
         ["**/*.java"],
-        excludes = ["SamplingProfilerPackagerMethod.java"] if IS_OSS_BUILD else [],
     ),
     visibility = [
         "PUBLIC",
@@ -19,5 +18,5 @@ rn_android_library(
         react_native_dep("third-party/java/okhttp:okhttp3"),
         react_native_dep("third-party/java/okio:okio"),
         react_native_target("java/com/facebook/react/modules/systeminfo:systeminfo-moduleless"),
-    ] + ([react_native_target("jni/packagerconnection:jni")] if not IS_OSS_BUILD else []),
+    ],
 )
diff --git a/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/SamplingProfilerPackagerMethod.java b/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/SamplingProfilerPackagerMethod.java
deleted file mode 100644
index f1de5e198efe..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/SamplingProfilerPackagerMethod.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.packagerconnection;
-
-import javax.annotation.Nullable;
-
-import android.os.Looper;
-
-import com.facebook.jni.HybridData;
-import com.facebook.proguard.annotations.DoNotStrip;
-import com.facebook.soloader.SoLoader;
-
-public class SamplingProfilerPackagerMethod extends RequestOnlyHandler {
-  static {
-    SoLoader.loadLibrary("packagerconnectionjnifb");
-  }
-
-  final private static class SamplingProfilerJniMethod {
-
-    @DoNotStrip
-    private final HybridData mHybridData;
-
-    public SamplingProfilerJniMethod(long javaScriptContext) {
-      if (Looper.myLooper() == null) {
-        Looper.prepare();
-      }
-
-      mHybridData = initHybrid(javaScriptContext);
-    }
-
-    @DoNotStrip
-    private native void poke(Responder responder);
-
-    @DoNotStrip
-    private static native HybridData initHybrid(long javaScriptContext);
-  }
-
-  private SamplingProfilerJniMethod mJniMethod;
-
-  public SamplingProfilerPackagerMethod(long javaScriptContext) {
-    mJniMethod = new SamplingProfilerJniMethod(javaScriptContext);
-  }
-
-  @Override
-  public void onRequest(@Nullable Object params, Responder responder) {
-    mJniMethod.poke(responder);
-  }
-}
diff --git a/ReactAndroid/src/main/jni/packagerconnection/Android.mk b/ReactAndroid/src/main/jni/packagerconnection/Android.mk
deleted file mode 100644
index ba09a7e689d4..000000000000
--- a/ReactAndroid/src/main/jni/packagerconnection/Android.mk
+++ /dev/null
@@ -1,29 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-
-include $(CLEAR_VARS)
-
-LOCAL_MODULE := packagerconnectionjnifb
-
-LOCAL_SRC_FILES := \
-  JSPackagerClientResponder.h \
-  SamplingProfilerPackagerMethod.cpp \
-
-LOCAL_C_INCLUDES := $(LOCAL_PATH)
-LOCAL_C_INCLUDES := $(LOCAL_PATH)/../../
-
-LOCAL_CFLAGS += -Wall -Werror -fvisibility=hidden -fexceptions -frtti
-CXX11_FLAGS := -std=c++11
-LOCAL_CFLAGS += $(CXX11_FLAGS)
-LOCAL_EXPORT_CPPFLAGS := $(CXX11_FLAGS)
-
-LOCAL_LDLIBS += -landroid
-LOCAL_SHARED_LIBRARIES := libfolly_json libfbjni libjsc libglog_init
-
-include $(BUILD_SHARED_LIBRARY)
-
-$(call import-module,fb)
-$(call import-module,jsc)
-$(call import-module,folly)
-$(call import-module,fbgloginit)
-$(call import-module,jni)
-$(call import-module,jscwrapper)
diff --git a/ReactAndroid/src/main/jni/packagerconnection/BUCK b/ReactAndroid/src/main/jni/packagerconnection/BUCK
deleted file mode 100644
index caede999292b..000000000000
--- a/ReactAndroid/src/main/jni/packagerconnection/BUCK
+++ /dev/null
@@ -1,35 +0,0 @@
-load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library", "FBJNI_TARGET", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "ANDROID", "IS_OSS_BUILD", "react_native_xplat_target")
-
-rn_xplat_cxx_library(
-    name = "jni",
-    srcs = glob(["*.cpp"]),
-    headers = glob(
-        ["*.h"],
-    ),
-    header_namespace = "",
-    compiler_flags = [
-        "-Wall",
-        "-Werror",
-        "-fexceptions",
-        "-std=c++1y",
-        "-frtti",
-    ],
-    fbandroid_deps = ANDROID_JSC_DEPS,
-    fbobjc_deps = APPLE_JSC_DEPS,
-    platforms = ANDROID,
-    preprocessor_flags = [
-        "-DLOG_TAG=\"PackagerConnectionJNI\"",
-        "-DWITH_FBSYSTRACE=1",
-        "-DWITH_INSPECTOR=1",
-    ],
-    soname = "libpackagerconnectionjnifb.$(ext)",
-    visibility = [
-        "PUBLIC",
-    ],
-    deps = ([
-        FBJNI_TARGET,
-        "xplat//folly:molly",
-        react_native_xplat_target("jschelpers:jschelpers"),
-        react_native_xplat_target("jsinspector:jsinspector"),
-    ]) if not IS_OSS_BUILD else [],
-)
diff --git a/ReactAndroid/src/main/jni/packagerconnection/JSPackagerClientResponder.cpp b/ReactAndroid/src/main/jni/packagerconnection/JSPackagerClientResponder.cpp
deleted file mode 100644
index 786af299cc75..000000000000
--- a/ReactAndroid/src/main/jni/packagerconnection/JSPackagerClientResponder.cpp
+++ /dev/null
@@ -1,32 +0,0 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
-#include "JSPackagerClientResponder.h"
-
-#include <jni/LocalString.h>
-
-using namespace facebook::jni;
-
-namespace facebook {
-namespace react {
-
-void JSPackagerClientResponder::respond(alias_ref<jobject> result) {
-  static auto method =
-      javaClassStatic()->getMethod<void(alias_ref<jobject>)>("respond");
-  method(self(), result);
-}
-
-void JSPackagerClientResponder::respond(const std::string &result) {
-  respond(LocalString(result).string());
-}
-
-void JSPackagerClientResponder::error(alias_ref<jobject> result) {
-  static auto method =
-      javaClassStatic()->getMethod<void(alias_ref<jobject>)>("error");
-  method(self(), result);
-}
-
-void JSPackagerClientResponder::error(const std::string &result) {
-  error(LocalString(result).string());
-}
-}
-}
diff --git a/ReactAndroid/src/main/jni/packagerconnection/JSPackagerClientResponder.h b/ReactAndroid/src/main/jni/packagerconnection/JSPackagerClientResponder.h
deleted file mode 100644
index 243a409c78c0..000000000000
--- a/ReactAndroid/src/main/jni/packagerconnection/JSPackagerClientResponder.h
+++ /dev/null
@@ -1,22 +0,0 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
-#include <fb/fbjni.h>
-
-namespace facebook {
-namespace react {
-
-class JSPackagerClientResponder
-    : public jni::JavaClass<JSPackagerClientResponder> {
-public:
-  static constexpr auto kJavaDescriptor =
-    "Lcom/facebook/react/packagerconnection/Responder;";
-
-  void respond(jni::alias_ref<jobject> result);
-  void respond(const std::string& result);
-
-  void error(jni::alias_ref<jobject> result);
-  void error(const std::string& result);
-};
-
-}
-}
diff --git a/ReactAndroid/src/main/jni/packagerconnection/OnLoad.cpp b/ReactAndroid/src/main/jni/packagerconnection/OnLoad.cpp
deleted file mode 100644
index d9b6b8cad443..000000000000
--- a/ReactAndroid/src/main/jni/packagerconnection/OnLoad.cpp
+++ /dev/null
@@ -1,17 +0,0 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
-#include <fb/fbjni.h>
-#include <jni.h>
-
-#include "SamplingProfilerJniMethod.h"
-
-using namespace facebook::jni;
-
-namespace facebook {
-namespace react {
-
-extern "C" JNIEXPORT jint JNI_OnLoad(JavaVM *vm, void *reserved) {
-  return initialize(vm, [] { SamplingProfilerJniMethod::registerNatives(); });
-}
-}
-}
diff --git a/ReactAndroid/src/main/jni/packagerconnection/SamplingProfilerJniMethod.cpp b/ReactAndroid/src/main/jni/packagerconnection/SamplingProfilerJniMethod.cpp
deleted file mode 100644
index 738d3e4fafef..000000000000
--- a/ReactAndroid/src/main/jni/packagerconnection/SamplingProfilerJniMethod.cpp
+++ /dev/null
@@ -1,53 +0,0 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
-#include "SamplingProfilerJniMethod.h"
-
-#include <JavaScriptCore/JSProfilerPrivate.h>
-
-#include <jschelpers/JSCHelpers.h>
-#include <jni.h>
-#include <string>
-
-using namespace facebook::jni;
-
-namespace facebook {
-namespace react {
-
-/* static */ jni::local_ref<SamplingProfilerJniMethod::jhybriddata>
-SamplingProfilerJniMethod::initHybrid(jni::alias_ref<jclass>,
-                                      jlong javaScriptContext) {
-  return makeCxxInstance(javaScriptContext);
-}
-
-/* static */ void SamplingProfilerJniMethod::registerNatives() {
-  registerHybrid(
-      {makeNativeMethod("initHybrid", SamplingProfilerJniMethod::initHybrid),
-       makeNativeMethod("poke", SamplingProfilerJniMethod::poke)});
-}
-
-SamplingProfilerJniMethod::SamplingProfilerJniMethod(jlong javaScriptContext) {
-  context_ = reinterpret_cast<JSGlobalContextRef>(javaScriptContext);
-}
-
-void SamplingProfilerJniMethod::poke(
-    jni::alias_ref<JSPackagerClientResponder::javaobject> responder) {
-  if (!JSC_JSSamplingProfilerEnabled(context_)) {
-    responder->error("The JSSamplingProfiler is disabled. See this "
-                     "https://fburl.com/u4lw7xeq for some help");
-    return;
-  }
-
-  JSValueRef jsResult = JSC_JSPokeSamplingProfiler(context_);
-  if (JSC_JSValueGetType(context_, jsResult) == kJSTypeNull) {
-    responder->respond("started");
-  } else {
-    JSStringRef resultStrRef = JSValueToStringCopy(context_, jsResult, nullptr);
-    size_t length = JSStringGetLength(resultStrRef);
-    char buffer[length + 1];
-    JSStringGetUTF8CString(resultStrRef, buffer, length + 1);
-    JSStringRelease(resultStrRef);
-    responder->respond(buffer);
-  }
-}
-}
-}
diff --git a/ReactAndroid/src/main/jni/packagerconnection/SamplingProfilerJniMethod.h b/ReactAndroid/src/main/jni/packagerconnection/SamplingProfilerJniMethod.h
deleted file mode 100644
index da83ec4cf5a7..000000000000
--- a/ReactAndroid/src/main/jni/packagerconnection/SamplingProfilerJniMethod.h
+++ /dev/null
@@ -1,33 +0,0 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
-#include <fb/fbjni.h>
-#include <JavaScriptCore/JSValueRef.h>
-
-#include "JSPackagerClientResponder.h"
-
-namespace facebook {
-namespace react {
-
-class SamplingProfilerJniMethod
-    : public jni::HybridClass<SamplingProfilerJniMethod> {
-public:
-  static constexpr auto kJavaDescriptor =
-      "Lcom/facebook/react/packagerconnection/"
-      "SamplingProfilerPackagerMethod$SamplingProfilerJniMethod;";
-
-  static jni::local_ref<jhybriddata> initHybrid(jni::alias_ref<jclass> jthis,
-                                                jlong javaScriptContext);
-
-  static void registerNatives();
-
-private:
-  friend HybridBase;
-
-  explicit SamplingProfilerJniMethod(jlong javaScriptContext);
-
-  void poke(jni::alias_ref<JSPackagerClientResponder::javaobject> responder);
-
-  JSGlobalContextRef context_;
-};
-}
-}

From 09f3d7ab492409a0d60f92c09a80e7f9b90d664a Mon Sep 17 00:00:00 2001
From: Marc Horowitz <mhorowitz@fb.com>
Date: Wed, 9 May 2018 22:01:48 -0700
Subject: [PATCH 0491/1109] reformat JSCExecutor.cpp

Reviewed By: fromcelticpark

Differential Revision: D7803913

fbshipit-source-id: fc4637d0f9ab8c01f2f257e34e435c9573ecf948
---
 ReactCommon/cxxreact/JSCExecutor.cpp | 1275 ++++++++++++++------------
 1 file changed, 676 insertions(+), 599 deletions(-)

diff --git a/ReactCommon/cxxreact/JSCExecutor.cpp b/ReactCommon/cxxreact/JSCExecutor.cpp
index 01a68fb4d5a7..c88da5f5b7a3 100644
--- a/ReactCommon/cxxreact/JSCExecutor.cpp
+++ b/ReactCommon/cxxreact/JSCExecutor.cpp
@@ -2,22 +2,22 @@
 
 #include "JSCExecutor.h"
 
+#include <fcntl.h>
+#include <sys/socket.h>
+#include <sys/time.h>
 #include <algorithm>
 #include <condition_variable>
-#include <fcntl.h>
 #include <mutex>
 #include <sstream>
 #include <string>
-#include <sys/time.h>
-#include <sys/socket.h>
 #include <system_error>
 
 #include <arpa/inet.h>
 #include <folly/Conv.h>
 #include <folly/Exception.h>
-#include <folly/json.h>
 #include <folly/Memory.h>
 #include <folly/String.h>
+#include <folly/json.h>
 #include <glog/logging.h>
 #include <jschelpers/JSCHelpers.h>
 #include <jschelpers/Value.h>
@@ -44,682 +44,759 @@
 #endif
 
 namespace facebook {
-  namespace react {
-
-    namespace {
-
-      template<JSValueRef (JSCExecutor::*method)(size_t, const JSValueRef[])>
-      inline JSObjectCallAsFunctionCallback exceptionWrapMethod() {
-        struct funcWrapper {
-          static JSValueRef call(
-                                 JSContextRef ctx,
-                                 JSObjectRef function,
-                                 JSObjectRef thisObject,
-                                 size_t argumentCount,
-                                 const JSValueRef arguments[],
-                                 JSValueRef *exception) {
-            try {
-              auto executor = Object::getGlobalObject(ctx).getPrivate<JSCExecutor>();
-              if (executor && executor->getJavaScriptContext()) { // Executor not invalidated
-                return (executor->*method)(argumentCount, arguments);
-              }
-            } catch (...) {
-              *exception = translatePendingCppExceptionToJSError(ctx, function);
-            }
-            return Value::makeUndefined(ctx);
-          }
-        };
-
-        return &funcWrapper::call;
-      }
-
-      template<JSValueRef (JSCExecutor::*method)(JSObjectRef object, JSStringRef propertyName)>
-      inline JSObjectGetPropertyCallback exceptionWrapMethod() {
-        struct funcWrapper {
-          static JSValueRef call(
-                                 JSContextRef ctx,
-                                 JSObjectRef object,
-                                 JSStringRef propertyName,
-                                 JSValueRef *exception) {
-            try {
-              auto executor = Object::getGlobalObject(ctx).getPrivate<JSCExecutor>();
-              if (executor && executor->getJavaScriptContext()) { // Executor not invalidated
-                return (executor->*method)(object, propertyName);
-              }
-            } catch (...) {
-              *exception = translatePendingCppExceptionToJSError(ctx, object);
-            }
-            return Value::makeUndefined(ctx);
-          }
-        };
-
-        return &funcWrapper::call;
+namespace react {
+
+namespace {
+
+template <JSValueRef (JSCExecutor::*method)(size_t, const JSValueRef[])>
+inline JSObjectCallAsFunctionCallback exceptionWrapMethod() {
+  struct funcWrapper {
+    static JSValueRef call(
+        JSContextRef ctx,
+        JSObjectRef function,
+        JSObjectRef thisObject,
+        size_t argumentCount,
+        const JSValueRef arguments[],
+        JSValueRef* exception) {
+      try {
+        auto executor = Object::getGlobalObject(ctx).getPrivate<JSCExecutor>();
+        if (executor &&
+            executor->getJavaScriptContext()) { // Executor not invalidated
+          return (executor->*method)(argumentCount, arguments);
+        }
+      } catch (...) {
+        *exception = translatePendingCppExceptionToJSError(ctx, function);
       }
-
-    }
-
-#if DEBUG
-    static JSValueRef nativeInjectHMRUpdate(
-                                            JSContextRef ctx,
-                                            JSObjectRef function,
-                                            JSObjectRef thisObject,
-                                            size_t argumentCount,
-                                            const JSValueRef arguments[],
-                                            JSValueRef *exception) {
-      String execJSString = Value(ctx, arguments[0]).toString();
-      String jsURL = Value(ctx, arguments[1]).toString();
-      evaluateScript(ctx, execJSString, jsURL);
       return Value::makeUndefined(ctx);
     }
-#endif
+  };
 
-    std::unique_ptr<JSExecutor> JSCExecutorFactory::createJSExecutor(
-                                                                     std::shared_ptr<ExecutorDelegate> delegate, std::shared_ptr<MessageQueueThread> jsQueue) {
-      return folly::make_unique<JSCExecutor>(delegate, jsQueue, m_jscConfig, m_nativeExtensionsProvider);
-    }
+  return &funcWrapper::call;
+}
 
-    JSCExecutor::JSCExecutor(std::shared_ptr<ExecutorDelegate> delegate,
-                             std::shared_ptr<MessageQueueThread> messageQueueThread,
-                             const folly::dynamic& jscConfig,
-                             NativeExtensionsProvider nativeExtensionsProvider) throw(JSException) :
-    m_delegate(delegate),
-    m_messageQueueThread(messageQueueThread),
-    m_nativeModules(delegate ? delegate->getModuleRegistry() : nullptr),
-    m_jscConfig(jscConfig),
-    m_nativeExtensionsProvider(nativeExtensionsProvider) {
-      initOnJSVMThread();
-
-      {
-        SystraceSection s("nativeModuleProxy object");
-        installGlobalProxy(m_context, "nativeModuleProxy",
-                           exceptionWrapMethod<&JSCExecutor::getNativeModule>());
-      }
-      if (nativeExtensionsProvider) {
-        installGlobalProxy(m_context, "nativeExtensions",
-                           exceptionWrapMethod<&JSCExecutor::getNativeExtension>());
+template <JSValueRef (
+    JSCExecutor::*method)(JSObjectRef object, JSStringRef propertyName)>
+inline JSObjectGetPropertyCallback exceptionWrapMethod() {
+  struct funcWrapper {
+    static JSValueRef call(
+        JSContextRef ctx,
+        JSObjectRef object,
+        JSStringRef propertyName,
+        JSValueRef* exception) {
+      try {
+        auto executor = Object::getGlobalObject(ctx).getPrivate<JSCExecutor>();
+        if (executor &&
+            executor->getJavaScriptContext()) { // Executor not invalidated
+          return (executor->*method)(object, propertyName);
+        }
+      } catch (...) {
+        *exception = translatePendingCppExceptionToJSError(ctx, object);
       }
+      return Value::makeUndefined(ctx);
     }
+  };
 
-    JSCExecutor::~JSCExecutor() {
-      CHECK(*m_isDestroyed) << "JSCExecutor::destroy() must be called before its destructor!";
-    }
+  return &funcWrapper::call;
+}
 
-    void JSCExecutor::destroy() {
-      *m_isDestroyed = true;
-      if (m_messageQueueThread.get()) {
-        m_messageQueueThread->runOnQueueSync([this] () {
-          terminateOnJSVMThread();
-        });
-      } else {
-        terminateOnJSVMThread();
-      }
-    }
+} // namespace
 
-    void JSCExecutor::setContextName(const std::string& name) {
-      String jsName = String(m_context, name.c_str());
-      JSC_JSGlobalContextSetName(m_context, jsName);
-    }
+#if DEBUG
+static JSValueRef nativeInjectHMRUpdate(
+    JSContextRef ctx,
+    JSObjectRef function,
+    JSObjectRef thisObject,
+    size_t argumentCount,
+    const JSValueRef arguments[],
+    JSValueRef* exception) {
+  String execJSString = Value(ctx, arguments[0]).toString();
+  String jsURL = Value(ctx, arguments[1]).toString();
+  evaluateScript(ctx, execJSString, jsURL);
+  return Value::makeUndefined(ctx);
+}
+#endif
 
-    static bool canUseInspector(JSContextRef context) {
+std::unique_ptr<JSExecutor> JSCExecutorFactory::createJSExecutor(
+    std::shared_ptr<ExecutorDelegate> delegate,
+    std::shared_ptr<MessageQueueThread> jsQueue) {
+  return folly::make_unique<JSCExecutor>(
+      delegate, jsQueue, m_jscConfig, m_nativeExtensionsProvider);
+}
+
+JSCExecutor::JSCExecutor(
+    std::shared_ptr<ExecutorDelegate> delegate,
+    std::shared_ptr<MessageQueueThread> messageQueueThread,
+    const folly::dynamic& jscConfig,
+    NativeExtensionsProvider nativeExtensionsProvider) throw(JSException)
+    : m_delegate(delegate),
+      m_messageQueueThread(messageQueueThread),
+      m_nativeModules(delegate ? delegate->getModuleRegistry() : nullptr),
+      m_jscConfig(jscConfig),
+      m_nativeExtensionsProvider(nativeExtensionsProvider) {
+  initOnJSVMThread();
+
+  {
+    SystraceSection s("nativeModuleProxy object");
+    installGlobalProxy(
+        m_context,
+        "nativeModuleProxy",
+        exceptionWrapMethod<&JSCExecutor::getNativeModule>());
+  }
+  if (nativeExtensionsProvider) {
+    installGlobalProxy(
+        m_context,
+        "nativeExtensions",
+        exceptionWrapMethod<&JSCExecutor::getNativeExtension>());
+  }
+}
+
+JSCExecutor::~JSCExecutor() {
+  CHECK(*m_isDestroyed)
+      << "JSCExecutor::destroy() must be called before its destructor!";
+}
+
+void JSCExecutor::destroy() {
+  *m_isDestroyed = true;
+  if (m_messageQueueThread.get()) {
+    m_messageQueueThread->runOnQueueSync([this]() { terminateOnJSVMThread(); });
+  } else {
+    terminateOnJSVMThread();
+  }
+}
+
+void JSCExecutor::setContextName(const std::string& name) {
+  String jsName = String(m_context, name.c_str());
+  JSC_JSGlobalContextSetName(m_context, jsName);
+}
+
+static bool canUseInspector(JSContextRef context) {
 #ifdef WITH_INSPECTOR
 #if defined(__APPLE__)
-      return isCustomJSCPtr(context); // WITH_INSPECTOR && Apple
+  return isCustomJSCPtr(context); // WITH_INSPECTOR && Apple
 #else
-      return true; // WITH_INSPECTOR && Android
+  return true; // WITH_INSPECTOR && Android
 #endif
 #else
-      return false; // !WITH_INSPECTOR
+  return false; // !WITH_INSPECTOR
 #endif
-    }
+}
 
-    static bool canUseSamplingProfiler(JSContextRef context) {
+static bool canUseSamplingProfiler(JSContextRef context) {
 #if defined(__APPLE__) || defined(WITH_JSC_EXTRA_TRACING)
-      return JSC_JSSamplingProfilerEnabled(context);
+  return JSC_JSSamplingProfilerEnabled(context);
 #else
-      return false;
+  return false;
 #endif
-    }
+}
 
-    void JSCExecutor::initOnJSVMThread() throw(JSException) {
-      SystraceSection s("JSCExecutor::initOnJSVMThread");
+void JSCExecutor::initOnJSVMThread() throw(JSException) {
+  SystraceSection s("JSCExecutor::initOnJSVMThread");
 
 #if defined(__APPLE__)
-      const bool useCustomJSC = m_jscConfig.getDefault("UseCustomJSC", false).getBool();
-      if (useCustomJSC) {
-        JSC_configureJSCForIOS(true, toJson(m_jscConfig));
-      }
+  const bool useCustomJSC =
+      m_jscConfig.getDefault("UseCustomJSC", false).getBool();
+  if (useCustomJSC) {
+    JSC_configureJSCForIOS(true, toJson(m_jscConfig));
+  }
 #else
-      const bool useCustomJSC = false;
+  const bool useCustomJSC = false;
 #endif
 
 #if defined(WITH_FB_JSC_TUNING) && defined(__ANDROID__)
-      configureJSCForAndroid(m_jscConfig);
+  configureJSCForAndroid(m_jscConfig);
 #endif
 
-      // Create a custom global class, so we can store data in it later using JSObjectSetPrivate
-      JSClassRef globalClass = nullptr;
-      {
-        SystraceSection s_("JSClassCreate");
-        JSClassDefinition definition = kJSClassDefinitionEmpty;
-        definition.attributes |= kJSClassAttributeNoAutomaticPrototype;
-        globalClass = JSC_JSClassCreate(useCustomJSC, &definition);
-      }
-      {
-        SystraceSection s_("JSGlobalContextCreateInGroup");
-        m_context = JSC_JSGlobalContextCreateInGroup(useCustomJSC, nullptr, globalClass);
-      }
-      JSC_JSClassRelease(useCustomJSC, globalClass);
-
-      // Add a pointer to ourselves so we can retrieve it later in our hooks
-      Object::getGlobalObject(m_context).setPrivate(this);
-
-      if (canUseInspector(m_context)) {
-        const std::string ownerId = m_jscConfig.getDefault("OwnerIdentity", "unknown").getString();
-        const std::string appId = m_jscConfig.getDefault("AppIdentity", "unknown").getString();
-        const std::string deviceId = m_jscConfig.getDefault("DeviceIdentity", "unknown").getString();
-        auto checkIsInspectedRemote = [ownerId, appId, deviceId]() {
-          return isNetworkInspected(ownerId, appId, deviceId);
-        };
-
-        auto& globalInspector = facebook::react::getInspectorInstance();
-        JSC_JSGlobalContextEnableDebugger(m_context, globalInspector, ownerId.c_str(), checkIsInspectedRemote);
-      }
-
-      installNativeHook<&JSCExecutor::nativeFlushQueueImmediate>("nativeFlushQueueImmediate");
-      installNativeHook<&JSCExecutor::nativeCallSyncHook>("nativeCallSyncHook");
-
-      installGlobalFunction(m_context, "nativeLoggingHook", JSCNativeHooks::loggingHook);
-      installGlobalFunction(m_context, "nativePerformanceNow", JSCNativeHooks::nowHook);
+  // Create a custom global class, so we can store data in it later using
+  // JSObjectSetPrivate
+  JSClassRef globalClass = nullptr;
+  {
+    SystraceSection s_("JSClassCreate");
+    JSClassDefinition definition = kJSClassDefinitionEmpty;
+    definition.attributes |= kJSClassAttributeNoAutomaticPrototype;
+    globalClass = JSC_JSClassCreate(useCustomJSC, &definition);
+  }
+  {
+    SystraceSection s_("JSGlobalContextCreateInGroup");
+    m_context =
+        JSC_JSGlobalContextCreateInGroup(useCustomJSC, nullptr, globalClass);
+  }
+  JSC_JSClassRelease(useCustomJSC, globalClass);
+
+  // Add a pointer to ourselves so we can retrieve it later in our hooks
+  Object::getGlobalObject(m_context).setPrivate(this);
+
+  if (canUseInspector(m_context)) {
+    const std::string ownerId =
+        m_jscConfig.getDefault("OwnerIdentity", "unknown").getString();
+    const std::string appId =
+        m_jscConfig.getDefault("AppIdentity", "unknown").getString();
+    const std::string deviceId =
+        m_jscConfig.getDefault("DeviceIdentity", "unknown").getString();
+    auto checkIsInspectedRemote = [ownerId, appId, deviceId]() {
+      return isNetworkInspected(ownerId, appId, deviceId);
+    };
+
+    auto& globalInspector = facebook::react::getInspectorInstance();
+    JSC_JSGlobalContextEnableDebugger(
+        m_context, globalInspector, ownerId.c_str(), checkIsInspectedRemote);
+  }
+
+  installNativeHook<&JSCExecutor::nativeFlushQueueImmediate>(
+      "nativeFlushQueueImmediate");
+  installNativeHook<&JSCExecutor::nativeCallSyncHook>("nativeCallSyncHook");
+
+  installGlobalFunction(
+      m_context, "nativeLoggingHook", JSCNativeHooks::loggingHook);
+  installGlobalFunction(
+      m_context, "nativePerformanceNow", JSCNativeHooks::nowHook);
 
 #if DEBUG
-      installGlobalFunction(m_context, "nativeInjectHMRUpdate", nativeInjectHMRUpdate);
+  installGlobalFunction(
+      m_context, "nativeInjectHMRUpdate", nativeInjectHMRUpdate);
 #endif
 
-      addNativeTracingHooks(m_context);
-      addNativeTracingLegacyHooks(m_context);
-      addJSCMemoryHooks(m_context);
-      addJSCPerfStatsHooks(m_context);
+  addNativeTracingHooks(m_context);
+  addNativeTracingLegacyHooks(m_context);
+  addJSCMemoryHooks(m_context);
+  addJSCPerfStatsHooks(m_context);
 
-      JSCNativeHooks::installPerfHooks(m_context);
+  JSCNativeHooks::installPerfHooks(m_context);
 
-      if (canUseSamplingProfiler(m_context)) {
-        initSamplingProfilerOnMainJSCThread(m_context);
-      }
-    }
+  if (canUseSamplingProfiler(m_context)) {
+    initSamplingProfilerOnMainJSCThread(m_context);
+  }
+}
 
-    bool JSCExecutor::isNetworkInspected(const std::string &owner, const std::string &app, const std::string &device) {
+bool JSCExecutor::isNetworkInspected(
+    const std::string& owner,
+    const std::string& app,
+    const std::string& device) {
 #ifdef WITH_FB_DBG_ATTACH_BEFORE_EXEC
-      auto connect_socket = [](int socket_desc, std::string address, int port) {
-        if (socket_desc < 0) {
-          ::close(socket_desc);
-          return false;
-        }
-
-        struct timeval tv;
-        tv.tv_sec = 1;
-        tv.tv_usec = 0;
-        auto sock_opt_rcv_resp = setsockopt(socket_desc, SOL_SOCKET, SO_RCVTIMEO, (const char*)&tv, sizeof(struct timeval));
-        if (sock_opt_rcv_resp < 0) {
-          ::close(socket_desc);
-          return false;
-        }
-
-        auto sock_opt_snd_resp = setsockopt(socket_desc, SOL_SOCKET, SO_SNDTIMEO, (const char*)&tv, sizeof(struct timeval));
-        if (sock_opt_snd_resp < 0) {
-          ::close(socket_desc);
-          return false;
-        }
-
-        struct sockaddr_in server;
-        server.sin_addr.s_addr = inet_addr(address.c_str());
-        server.sin_family = AF_INET;
-        server.sin_port = htons(port);
-        auto connect_resp = ::connect(socket_desc, (struct sockaddr *)&server, sizeof(server));
-        if (connect_resp < 0) {
-          ::close(socket_desc);
-          return false;
-        }
-
-        return true;
-      };
-
-      int socket_desc = socket(AF_INET, SOCK_STREAM, 0);
-
-      if (!connect_socket(socket_desc, "127.0.0.1", 8082)) {
-#if defined(__ANDROID__)
-        socket_desc = socket(AF_INET, SOCK_STREAM, 0);
-        if (!connect_socket(socket_desc, "10.0.2.2", 8082) /* emulator */) {
-          socket_desc = socket(AF_INET, SOCK_STREAM, 0);
-          if (!connect_socket(socket_desc, "10.0.3.2", 8082) /* genymotion */) {
-            return false;
-          }
-        }
-#else //!defined(__ANDROID__)
-        return false;
-#endif //defined(__ANDROID__)
-      }
+  auto connect_socket = [](int socket_desc, std::string address, int port) {
+    if (socket_desc < 0) {
+      ::close(socket_desc);
+      return false;
+    }
 
-      std::string escapedOwner = folly::uriEscape<std::string>(owner, folly::UriEscapeMode::QUERY);
-      std::string escapedApp = folly::uriEscape<std::string>(app, folly::UriEscapeMode::QUERY);
-      std::string escapedDevice = folly::uriEscape<std::string>(device, folly::UriEscapeMode::QUERY);
-      std::string msg = folly::to<std::string>(
-        "GET /autoattach?title=", escapedOwner,
-        "&app=" , escapedApp,
-        "&device=" , escapedDevice,
-        " HTTP/1.1\r\n\r\n");
-      auto send_resp = ::send(socket_desc, msg.c_str(), msg.length(), 0);
-      if (send_resp < 0) {
-        ::close(socket_desc);
-        return false;
-      }
+    struct timeval tv;
+    tv.tv_sec = 1;
+    tv.tv_usec = 0;
+    auto sock_opt_rcv_resp = setsockopt(
+        socket_desc,
+        SOL_SOCKET,
+        SO_RCVTIMEO,
+        (const char*)&tv,
+        sizeof(struct timeval));
+    if (sock_opt_rcv_resp < 0) {
+      ::close(socket_desc);
+      return false;
+    }
 
-      char server_reply[200];
-      server_reply[199] = '\0';
-      auto recv_resp = ::recv(socket_desc, server_reply,
-                              sizeof(server_reply) - 1, 0);
-      if (recv_resp < 0) {
-        ::close(socket_desc);
-        return false;
-      }
+    auto sock_opt_snd_resp = setsockopt(
+        socket_desc,
+        SOL_SOCKET,
+        SO_SNDTIMEO,
+        (const char*)&tv,
+        sizeof(struct timeval));
+    if (sock_opt_snd_resp < 0) {
+      ::close(socket_desc);
+      return false;
+    }
 
-      std::string response(server_reply);
-      if (response.size() < 25) {
-        ::close(socket_desc);
-        return false;
-      }
-      auto responseCandidate = response.substr(response.size() - 25);
-      auto found = responseCandidate.find("{\"autoattach\":true}") != std::string::npos;
+    struct sockaddr_in server;
+    server.sin_addr.s_addr = inet_addr(address.c_str());
+    server.sin_family = AF_INET;
+    server.sin_port = htons(port);
+    auto connect_resp =
+        ::connect(socket_desc, (struct sockaddr*)&server, sizeof(server));
+    if (connect_resp < 0) {
       ::close(socket_desc);
-      return found;
-#else //!WITH_FB_DBG_ATTACH_BEFORE_EXEC
       return false;
-#endif //WITH_FB_DBG_ATTACH_BEFORE_EXEC
     }
 
-    void JSCExecutor::terminateOnJSVMThread() {
-      JSGlobalContextRef context = m_context;
-      m_context = nullptr;
-      Object::getGlobalObject(context).setPrivate(nullptr);
-      m_nativeModules.reset();
+    return true;
+  };
 
-      if (canUseInspector(context)) {
-        auto &globalInspector = facebook::react::getInspectorInstance();
-        JSC_JSGlobalContextDisableDebugger(context, globalInspector);
-      }
+  int socket_desc = socket(AF_INET, SOCK_STREAM, 0);
 
-      JSC_JSGlobalContextRelease(context);
+  if (!connect_socket(socket_desc, "127.0.0.1", 8082)) {
+#if defined(__ANDROID__)
+    socket_desc = socket(AF_INET, SOCK_STREAM, 0);
+    if (!connect_socket(socket_desc, "10.0.2.2", 8082) /* emulator */) {
+      socket_desc = socket(AF_INET, SOCK_STREAM, 0);
+      if (!connect_socket(socket_desc, "10.0.3.2", 8082) /* genymotion */) {
+        return false;
+      }
     }
+#else //! defined(__ANDROID__)
+    return false;
+#endif // defined(__ANDROID__)
+  }
+
+  std::string escapedOwner =
+      folly::uriEscape<std::string>(owner, folly::UriEscapeMode::QUERY);
+  std::string escapedApp =
+      folly::uriEscape<std::string>(app, folly::UriEscapeMode::QUERY);
+  std::string escapedDevice =
+      folly::uriEscape<std::string>(device, folly::UriEscapeMode::QUERY);
+  std::string msg = folly::to<std::string>(
+      "GET /autoattach?title=",
+      escapedOwner,
+      "&app=",
+      escapedApp,
+      "&device=",
+      escapedDevice,
+      " HTTP/1.1\r\n\r\n");
+  auto send_resp = ::send(socket_desc, msg.c_str(), msg.length(), 0);
+  if (send_resp < 0) {
+    ::close(socket_desc);
+    return false;
+  }
+
+  char server_reply[200];
+  server_reply[199] = '\0';
+  auto recv_resp =
+      ::recv(socket_desc, server_reply, sizeof(server_reply) - 1, 0);
+  if (recv_resp < 0) {
+    ::close(socket_desc);
+    return false;
+  }
+
+  std::string response(server_reply);
+  if (response.size() < 25) {
+    ::close(socket_desc);
+    return false;
+  }
+  auto responseCandidate = response.substr(response.size() - 25);
+  auto found =
+      responseCandidate.find("{\"autoattach\":true}") != std::string::npos;
+  ::close(socket_desc);
+  return found;
+#else //! WITH_FB_DBG_ATTACH_BEFORE_EXEC
+  return false;
+#endif // WITH_FB_DBG_ATTACH_BEFORE_EXEC
+}
+
+void JSCExecutor::terminateOnJSVMThread() {
+  JSGlobalContextRef context = m_context;
+  m_context = nullptr;
+  Object::getGlobalObject(context).setPrivate(nullptr);
+  m_nativeModules.reset();
+
+  if (canUseInspector(context)) {
+    auto& globalInspector = facebook::react::getInspectorInstance();
+    JSC_JSGlobalContextDisableDebugger(context, globalInspector);
+  }
+
+  JSC_JSGlobalContextRelease(context);
+}
 
 #ifdef WITH_FBJSCEXTENSIONS
-    static const char* explainLoadSourceStatus(JSLoadSourceStatus status) {
-      switch (status) {
-        case JSLoadSourceIsCompiled:
-          return "No error encountered during source load";
+static const char* explainLoadSourceStatus(JSLoadSourceStatus status) {
+  switch (status) {
+    case JSLoadSourceIsCompiled:
+      return "No error encountered during source load";
 
-        case JSLoadSourceErrorOnRead:
-          return "Error reading source";
+    case JSLoadSourceErrorOnRead:
+      return "Error reading source";
 
-        case JSLoadSourceIsNotCompiled:
-          return "Source is not compiled";
+    case JSLoadSourceIsNotCompiled:
+      return "Source is not compiled";
 
-        case JSLoadSourceErrorVersionMismatch:
-          return "Source version not supported";
+    case JSLoadSourceErrorVersionMismatch:
+      return "Source version not supported";
 
-        default:
-          return "Bad error code";
-      }
-    }
+    default:
+      return "Bad error code";
+  }
+}
 #endif
 
-    // basename_r isn't in all iOS SDKs, so use this simple version instead.
-    static std::string simpleBasename(const std::string &path) {
-      size_t pos = path.rfind("/");
-      return (pos != std::string::npos) ? path.substr(pos) : path;
-    }
+// basename_r isn't in all iOS SDKs, so use this simple version instead.
+static std::string simpleBasename(const std::string& path) {
+  size_t pos = path.rfind("/");
+  return (pos != std::string::npos) ? path.substr(pos) : path;
+}
 
-    void JSCExecutor::loadApplicationScript(std::unique_ptr<const JSBigString> script, std::string sourceURL) {
-      SystraceSection s("JSCExecutor::loadApplicationScript",
-                        "sourceURL", sourceURL);
+void JSCExecutor::loadApplicationScript(
+    std::unique_ptr<const JSBigString> script,
+    std::string sourceURL) {
+  SystraceSection s(
+      "JSCExecutor::loadApplicationScript", "sourceURL", sourceURL);
 
-      std::string scriptName = simpleBasename(sourceURL);
-      ReactMarker::logTaggedMarker(ReactMarker::RUN_JS_BUNDLE_START, scriptName.c_str());
-      String jsSourceURL(m_context, sourceURL.c_str());
+  std::string scriptName = simpleBasename(sourceURL);
+  ReactMarker::logTaggedMarker(
+      ReactMarker::RUN_JS_BUNDLE_START, scriptName.c_str());
+  String jsSourceURL(m_context, sourceURL.c_str());
 
-      // TODO t15069155: reduce the number of overrides here
+// TODO t15069155: reduce the number of overrides here
 #ifdef WITH_FBJSCEXTENSIONS
-      if (auto fileStr = dynamic_cast<const JSBigFileString *>(script.get())) {
-        JSContextLock lock(m_context);
-        JSLoadSourceStatus jsStatus;
-        auto bcSourceCode = JSCreateSourceCodeFromFile(fileStr->fd(), jsSourceURL, nullptr, &jsStatus);
-
-        switch (jsStatus) {
-          case JSLoadSourceIsCompiled:
-            if (!bcSourceCode) {
-              throw std::runtime_error("Unexpected error opening compiled bundle");
-            }
-            evaluateSourceCode(m_context, bcSourceCode, jsSourceURL);
-
-            flush();
-
-            ReactMarker::logMarker(ReactMarker::CREATE_REACT_CONTEXT_STOP);
-            ReactMarker::logTaggedMarker(ReactMarker::RUN_JS_BUNDLE_STOP, scriptName.c_str());
-            return;
-
-          case JSLoadSourceErrorVersionMismatch:
-            throw RecoverableError(explainLoadSourceStatus(jsStatus));
-
-          case JSLoadSourceErrorOnRead:
-          case JSLoadSourceIsNotCompiled:
-            // Not bytecode, fall through.
-            break;
+  if (auto fileStr = dynamic_cast<const JSBigFileString*>(script.get())) {
+    JSContextLock lock(m_context);
+    JSLoadSourceStatus jsStatus;
+    auto bcSourceCode = JSCreateSourceCodeFromFile(
+        fileStr->fd(), jsSourceURL, nullptr, &jsStatus);
+
+    switch (jsStatus) {
+      case JSLoadSourceIsCompiled:
+        if (!bcSourceCode) {
+          throw std::runtime_error("Unexpected error opening compiled bundle");
         }
-      }
-#elif defined(__APPLE__)
-      BundleHeader header;
-      memcpy(&header, script->c_str(), std::min(script->size(), sizeof(BundleHeader)));
-      auto scriptTag = parseTypeFromHeader(header);
-
-      if (scriptTag == ScriptTag::BCBundle) {
-        using file_ptr = std::unique_ptr<FILE, decltype(&fclose)>;
-        file_ptr source(fopen(sourceURL.c_str(), "r"), fclose);
-        int sourceFD = fileno(source.get());
-
-        JSValueRef jsError;
-        JSValueRef result = JSC_JSEvaluateBytecodeBundle(m_context, NULL, sourceFD, jsSourceURL, &jsError);
-        if (result == nullptr) {
-          throw JSException(m_context, jsError, jsSourceURL);
-        }
-      } else
-#endif
-      {
-        String jsScript;
-        JSContextLock lock(m_context);
-        {
-          SystraceSection s_("JSCExecutor::loadApplicationScript-createExpectingAscii");
-          ReactMarker::logMarker(ReactMarker::JS_BUNDLE_STRING_CONVERT_START);
-          jsScript = adoptString(std::move(script));
-          ReactMarker::logMarker(ReactMarker::JS_BUNDLE_STRING_CONVERT_STOP);
-        }
-
-        SystraceSection s_("JSCExecutor::loadApplicationScript-evaluateScript");
-        evaluateScript(m_context, jsScript, jsSourceURL);
-      }
-
-      flush();
-
-      ReactMarker::logMarker(ReactMarker::CREATE_REACT_CONTEXT_STOP);
-      ReactMarker::logTaggedMarker(ReactMarker::RUN_JS_BUNDLE_STOP, scriptName.c_str());
-    }
+        evaluateSourceCode(m_context, bcSourceCode, jsSourceURL);
 
-    void JSCExecutor::setBundleRegistry(std::unique_ptr<RAMBundleRegistry> bundleRegistry) {
-      if (!m_bundleRegistry) {
-        installNativeHook<&JSCExecutor::nativeRequire>("nativeRequire");
-      }
-      m_bundleRegistry = std::move(bundleRegistry);
-    }
-
-    void JSCExecutor::registerBundle(
-        uint32_t bundleId,
-        const std::string& bundlePath) {
-      if (m_bundleRegistry) {
-        m_bundleRegistry->registerBundle(bundleId, bundlePath);
-      } else {
-        auto stPath = JSCExecutor::getSyntheticBundlePath(bundleId, bundlePath);
-        auto sourceUrlStr = String(m_context, stPath.c_str());
-        auto source = adoptString(JSBigFileString::fromPath(bundlePath));
-        evaluateScript(m_context, source, sourceUrlStr);
-      }
-    }
+        flush();
 
-    void JSCExecutor::bindBridge() throw(JSException) {
-      SystraceSection s("JSCExecutor::bindBridge");
-      std::call_once(m_bindFlag, [this] {
-        auto global = Object::getGlobalObject(m_context);
-        auto batchedBridgeValue = global.getProperty("__fbBatchedBridge");
-        if (batchedBridgeValue.isUndefined()) {
-          auto requireBatchedBridge = global.getProperty("__fbRequireBatchedBridge");
-          if (!requireBatchedBridge.isUndefined()) {
-            batchedBridgeValue = requireBatchedBridge.asObject().callAsFunction({});
-          }
-          if (batchedBridgeValue.isUndefined()) {
-            throw JSException("Could not get BatchedBridge, make sure your bundle is packaged correctly");
-          }
-        }
+        ReactMarker::logMarker(ReactMarker::CREATE_REACT_CONTEXT_STOP);
+        ReactMarker::logTaggedMarker(
+            ReactMarker::RUN_JS_BUNDLE_STOP, scriptName.c_str());
+        return;
 
-        auto batchedBridge = batchedBridgeValue.asObject();
-        m_callFunctionReturnFlushedQueueJS = batchedBridge.getProperty("callFunctionReturnFlushedQueue").asObject();
-        m_invokeCallbackAndReturnFlushedQueueJS = batchedBridge.getProperty("invokeCallbackAndReturnFlushedQueue").asObject();
-        m_flushedQueueJS = batchedBridge.getProperty("flushedQueue").asObject();
-        m_callFunctionReturnResultAndFlushedQueueJS = batchedBridge.getProperty("callFunctionReturnResultAndFlushedQueue").asObject();
-      });
-    }
+      case JSLoadSourceErrorVersionMismatch:
+        throw RecoverableError(explainLoadSourceStatus(jsStatus));
 
-    void JSCExecutor::callNativeModules(Value&& value) {
-      SystraceSection s("JSCExecutor::callNativeModules");
-      // If this fails, you need to pass a fully functional delegate with a
-      // module registry to the factory/ctor.
-      CHECK(m_delegate) << "Attempting to use native modules without a delegate";
-      try {
-        auto calls = value.toJSONString();
-        m_delegate->callNativeModules(*this, folly::parseJson(calls), true);
-      } catch (...) {
-        std::string message = "Error in callNativeModules()";
-        try {
-          message += ":" + value.toString().str();
-        } catch (...) {
-          // ignored
-        }
-        std::throw_with_nested(std::runtime_error(message));
-      }
+      case JSLoadSourceErrorOnRead:
+      case JSLoadSourceIsNotCompiled:
+        // Not bytecode, fall through.
+        break;
     }
-
-    void JSCExecutor::flush() {
-      SystraceSection s("JSCExecutor::flush");
-
-      if (m_flushedQueueJS) {
-        callNativeModules(m_flushedQueueJS->callAsFunction({}));
-        return;
-      }
-
-      // When a native module is called from JS, BatchedBridge.enqueueNativeCall()
-      // is invoked.  For that to work, require('BatchedBridge') has to be called,
-      // and when that happens, __fbBatchedBridge is set as a side effect.
-      auto global = Object::getGlobalObject(m_context);
-      auto batchedBridgeValue = global.getProperty("__fbBatchedBridge");
-      // So here, if __fbBatchedBridge doesn't exist, then we know no native calls
-      // have happened, and we were able to determine this without forcing
-      // BatchedBridge to be loaded as a side effect.
-      if (!batchedBridgeValue.isUndefined()) {
-        // If calls were made, we bind to the JS bridge methods, and use them to
-        // get the pending queue of native calls.
+  }
+#elif defined(__APPLE__)
+  BundleHeader header;
+  memcpy(
+      &header, script->c_str(), std::min(script->size(), sizeof(BundleHeader)));
+  auto scriptTag = parseTypeFromHeader(header);
+
+  if (scriptTag == ScriptTag::BCBundle) {
+    using file_ptr = std::unique_ptr<FILE, decltype(&fclose)>;
+    file_ptr source(fopen(sourceURL.c_str(), "r"), fclose);
+    int sourceFD = fileno(source.get());
+
+    JSValueRef jsError;
+    JSValueRef result = JSC_JSEvaluateBytecodeBundle(
+        m_context, NULL, sourceFD, jsSourceURL, &jsError);
+    if (result == nullptr) {
+      throw JSException(m_context, jsError, jsSourceURL);
+    }
+  } else
+#endif
+  {
+    String jsScript;
+    JSContextLock lock(m_context);
+    {
+      SystraceSection s_(
+          "JSCExecutor::loadApplicationScript-createExpectingAscii");
+      ReactMarker::logMarker(ReactMarker::JS_BUNDLE_STRING_CONVERT_START);
+      jsScript = adoptString(std::move(script));
+      ReactMarker::logMarker(ReactMarker::JS_BUNDLE_STRING_CONVERT_STOP);
+    }
+
+    SystraceSection s_("JSCExecutor::loadApplicationScript-evaluateScript");
+    evaluateScript(m_context, jsScript, jsSourceURL);
+  }
+
+  flush();
+
+  ReactMarker::logMarker(ReactMarker::CREATE_REACT_CONTEXT_STOP);
+  ReactMarker::logTaggedMarker(
+      ReactMarker::RUN_JS_BUNDLE_STOP, scriptName.c_str());
+}
+
+void JSCExecutor::setBundleRegistry(
+    std::unique_ptr<RAMBundleRegistry> bundleRegistry) {
+  if (!m_bundleRegistry) {
+    installNativeHook<&JSCExecutor::nativeRequire>("nativeRequire");
+  }
+  m_bundleRegistry = std::move(bundleRegistry);
+}
+
+void JSCExecutor::registerBundle(
+    uint32_t bundleId,
+    const std::string& bundlePath) {
+  if (m_bundleRegistry) {
+    m_bundleRegistry->registerBundle(bundleId, bundlePath);
+  } else {
+    auto stPath = JSCExecutor::getSyntheticBundlePath(bundleId, bundlePath);
+    auto sourceUrlStr = String(m_context, stPath.c_str());
+    auto source = adoptString(JSBigFileString::fromPath(bundlePath));
+    evaluateScript(m_context, source, sourceUrlStr);
+  }
+}
+
+void JSCExecutor::bindBridge() throw(JSException) {
+  SystraceSection s("JSCExecutor::bindBridge");
+  std::call_once(m_bindFlag, [this] {
+    auto global = Object::getGlobalObject(m_context);
+    auto batchedBridgeValue = global.getProperty("__fbBatchedBridge");
+    if (batchedBridgeValue.isUndefined()) {
+      auto requireBatchedBridge =
+          global.getProperty("__fbRequireBatchedBridge");
+      if (!requireBatchedBridge.isUndefined()) {
+        batchedBridgeValue = requireBatchedBridge.asObject().callAsFunction({});
+      }
+      if (batchedBridgeValue.isUndefined()) {
+        throw JSException(
+            "Could not get BatchedBridge, make sure your bundle is packaged correctly");
+      }
+    }
+
+    auto batchedBridge = batchedBridgeValue.asObject();
+    m_callFunctionReturnFlushedQueueJS =
+        batchedBridge.getProperty("callFunctionReturnFlushedQueue").asObject();
+    m_invokeCallbackAndReturnFlushedQueueJS =
+        batchedBridge.getProperty("invokeCallbackAndReturnFlushedQueue")
+            .asObject();
+    m_flushedQueueJS = batchedBridge.getProperty("flushedQueue").asObject();
+    m_callFunctionReturnResultAndFlushedQueueJS =
+        batchedBridge.getProperty("callFunctionReturnResultAndFlushedQueue")
+            .asObject();
+  });
+}
+
+void JSCExecutor::callNativeModules(Value&& value) {
+  SystraceSection s("JSCExecutor::callNativeModules");
+  // If this fails, you need to pass a fully functional delegate with a
+  // module registry to the factory/ctor.
+  CHECK(m_delegate) << "Attempting to use native modules without a delegate";
+  try {
+    auto calls = value.toJSONString();
+    m_delegate->callNativeModules(*this, folly::parseJson(calls), true);
+  } catch (...) {
+    std::string message = "Error in callNativeModules()";
+    try {
+      message += ":" + value.toString().str();
+    } catch (...) {
+      // ignored
+    }
+    std::throw_with_nested(std::runtime_error(message));
+  }
+}
+
+void JSCExecutor::flush() {
+  SystraceSection s("JSCExecutor::flush");
+
+  if (m_flushedQueueJS) {
+    callNativeModules(m_flushedQueueJS->callAsFunction({}));
+    return;
+  }
+
+  // When a native module is called from JS, BatchedBridge.enqueueNativeCall()
+  // is invoked.  For that to work, require('BatchedBridge') has to be called,
+  // and when that happens, __fbBatchedBridge is set as a side effect.
+  auto global = Object::getGlobalObject(m_context);
+  auto batchedBridgeValue = global.getProperty("__fbBatchedBridge");
+  // So here, if __fbBatchedBridge doesn't exist, then we know no native calls
+  // have happened, and we were able to determine this without forcing
+  // BatchedBridge to be loaded as a side effect.
+  if (!batchedBridgeValue.isUndefined()) {
+    // If calls were made, we bind to the JS bridge methods, and use them to
+    // get the pending queue of native calls.
+    bindBridge();
+    callNativeModules(m_flushedQueueJS->callAsFunction({}));
+  } else if (m_delegate) {
+    // If we have a delegate, we need to call it; we pass a null list to
+    // callNativeModules, since we know there are no native calls, without
+    // calling into JS again.  If no calls were made and there's no delegate,
+    // nothing happens, which is correct.
+    callNativeModules(Value::makeNull(m_context));
+  }
+}
+
+void JSCExecutor::callFunction(
+    const std::string& moduleId,
+    const std::string& methodId,
+    const folly::dynamic& arguments) {
+  SystraceSection s("JSCExecutor::callFunction");
+  // This weird pattern is because Value is not default constructible.
+  // The lambda is inlined, so there's no overhead.
+  auto result = [&] {
+    JSContextLock lock(m_context);
+    try {
+      if (!m_callFunctionReturnResultAndFlushedQueueJS) {
         bindBridge();
-        callNativeModules(m_flushedQueueJS->callAsFunction({}));
-      } else if (m_delegate) {
-        // If we have a delegate, we need to call it; we pass a null list to
-        // callNativeModules, since we know there are no native calls, without
-        // calling into JS again.  If no calls were made and there's no delegate,
-        // nothing happens, which is correct.
-        callNativeModules(Value::makeNull(m_context));
       }
-    }
-
-    void JSCExecutor::callFunction(const std::string& moduleId, const std::string& methodId, const folly::dynamic& arguments) {
-      SystraceSection s("JSCExecutor::callFunction");
-      // This weird pattern is because Value is not default constructible.
-      // The lambda is inlined, so there's no overhead.
-      auto result = [&] {
-        JSContextLock lock(m_context);
-        try {
-          if (!m_callFunctionReturnResultAndFlushedQueueJS) {
-            bindBridge();
-          }
-          return m_callFunctionReturnFlushedQueueJS->callAsFunction({
-            Value(m_context, String::createExpectingAscii(m_context, moduleId)),
-            Value(m_context, String::createExpectingAscii(m_context, methodId)),
-            Value::fromDynamic(m_context, std::move(arguments))
-          });
-        } catch (...) {
-          std::throw_with_nested(
-                                 std::runtime_error("Error calling " + moduleId + "." + methodId));
-        }
-      }();
-      callNativeModules(std::move(result));
-    }
-
-    void JSCExecutor::invokeCallback(const double callbackId, const folly::dynamic& arguments) {
-      SystraceSection s("JSCExecutor::invokeCallback");
-      auto result = [&] {
-        JSContextLock lock(m_context);
-        try {
-          if (!m_invokeCallbackAndReturnFlushedQueueJS) {
-            bindBridge();
-          }
-          return m_invokeCallbackAndReturnFlushedQueueJS->callAsFunction({
-            Value::makeNumber(m_context, callbackId),
-            Value::fromDynamic(m_context, std::move(arguments))
-          });
-        } catch (...) {
-          std::throw_with_nested(
-                                 std::runtime_error(folly::to<std::string>("Error invoking callback ", callbackId)));
-        }
-      }();
-      callNativeModules(std::move(result));
-    }
-
-    void JSCExecutor::setGlobalVariable(std::string propName, std::unique_ptr<const JSBigString> jsonValue) {
-      try {
-        SystraceSection s("JSCExecutor::setGlobalVariable", "propName", propName);
-        auto valueToInject = Value::fromJSON(adoptString(std::move(jsonValue)));
-        Object::getGlobalObject(m_context).setProperty(propName.c_str(), valueToInject);
-      } catch (...) {
-        std::throw_with_nested(std::runtime_error("Error setting global variable: " + propName));
+      return m_callFunctionReturnFlushedQueueJS->callAsFunction(
+          {Value(m_context, String::createExpectingAscii(m_context, moduleId)),
+           Value(m_context, String::createExpectingAscii(m_context, methodId)),
+           Value::fromDynamic(m_context, std::move(arguments))});
+    } catch (...) {
+      std::throw_with_nested(
+          std::runtime_error("Error calling " + moduleId + "." + methodId));
+    }
+  }();
+  callNativeModules(std::move(result));
+}
+
+void JSCExecutor::invokeCallback(
+    const double callbackId,
+    const folly::dynamic& arguments) {
+  SystraceSection s("JSCExecutor::invokeCallback");
+  auto result = [&] {
+    JSContextLock lock(m_context);
+    try {
+      if (!m_invokeCallbackAndReturnFlushedQueueJS) {
+        bindBridge();
       }
-    }
-
-    std::string JSCExecutor::getDescription() {
+      return m_invokeCallbackAndReturnFlushedQueueJS->callAsFunction(
+          {Value::makeNumber(m_context, callbackId),
+           Value::fromDynamic(m_context, std::move(arguments))});
+    } catch (...) {
+      std::throw_with_nested(std::runtime_error(
+          folly::to<std::string>("Error invoking callback ", callbackId)));
+    }
+  }();
+  callNativeModules(std::move(result));
+}
+
+void JSCExecutor::setGlobalVariable(
+    std::string propName,
+    std::unique_ptr<const JSBigString> jsonValue) {
+  try {
+    SystraceSection s("JSCExecutor::setGlobalVariable", "propName", propName);
+    auto valueToInject = Value::fromJSON(adoptString(std::move(jsonValue)));
+    Object::getGlobalObject(m_context).setProperty(
+        propName.c_str(), valueToInject);
+  } catch (...) {
+    std::throw_with_nested(
+        std::runtime_error("Error setting global variable: " + propName));
+  }
+}
+
+std::string JSCExecutor::getDescription() {
 #if defined(__APPLE__)
-      if (isCustomJSCPtr(m_context)) {
-        return "Custom JSC";
-      } else {
-        return "System JSC";
-      }
+  if (isCustomJSCPtr(m_context)) {
+    return "Custom JSC";
+  } else {
+    return "System JSC";
+  }
 #else
-      return "JSC";
+  return "JSC";
 #endif
-    }
+}
 
-    String JSCExecutor::adoptString(std::unique_ptr<const JSBigString> script) {
+String JSCExecutor::adoptString(std::unique_ptr<const JSBigString> script) {
 #if defined(WITH_FBJSCEXTENSIONS)
-      const JSBigString* string = script.release();
-      auto jsString = JSStringCreateAdoptingExternal(string->c_str(), string->size(), (void*)string, [](void* s) {
+  const JSBigString* string = script.release();
+  auto jsString = JSStringCreateAdoptingExternal(
+      string->c_str(), string->size(), (void*)string, [](void* s) {
         delete static_cast<JSBigString*>(s);
       });
-      return String::adopt(m_context, jsString);
+  return String::adopt(m_context, jsString);
 #else
-      return script->isAscii()
-          ? String::createExpectingAscii(m_context, script->c_str(), script->size())
-          : String(m_context, script->c_str());
+  return script->isAscii()
+      ? String::createExpectingAscii(m_context, script->c_str(), script->size())
+      : String(m_context, script->c_str());
 #endif
-    }
+}
 
-    void* JSCExecutor::getJavaScriptContext() {
-      return m_context;
-    }
+void* JSCExecutor::getJavaScriptContext() {
+  return m_context;
+}
 
-    bool JSCExecutor::isInspectable() {
-      return canUseInspector(m_context);
-    }
+bool JSCExecutor::isInspectable() {
+  return canUseInspector(m_context);
+}
 
 #ifdef WITH_JSC_MEMORY_PRESSURE
-    void JSCExecutor::handleMemoryPressure(int pressureLevel) {
-      JSHandleMemoryPressure(this, m_context, static_cast<JSMemoryPressure>(pressureLevel));
-    }
+void JSCExecutor::handleMemoryPressure(int pressureLevel) {
+  JSHandleMemoryPressure(
+      this, m_context, static_cast<JSMemoryPressure>(pressureLevel));
+}
 #endif
 
-    void JSCExecutor::flushQueueImmediate(Value&& queue) {
-      auto queueStr = queue.toJSONString();
-      m_delegate->callNativeModules(*this, folly::parseJson(queueStr), false);
-    }
-
-    void JSCExecutor::loadModule(uint32_t bundleId, uint32_t moduleId) {
-      auto module = m_bundleRegistry->getModule(bundleId, moduleId);
-      auto sourceUrl = String::createExpectingAscii(m_context, module.name);
-      auto source = adoptString(std::unique_ptr<JSBigString>(new JSBigStdString(module.code)));
-      evaluateScript(m_context, source, sourceUrl);
-    }
-
-    // Native JS hooks
-    template<JSValueRef (JSCExecutor::*method)(size_t, const JSValueRef[])>
-    void JSCExecutor::installNativeHook(const char* name) {
-      installGlobalFunction(m_context, name, exceptionWrapMethod<method>());
-    }
-
-    JSValueRef JSCExecutor::getNativeModule(JSObjectRef object, JSStringRef propertyName) {
-      if (JSC_JSStringIsEqualToUTF8CString(m_context, propertyName, "name")) {
-        return Value(m_context, String(m_context, "NativeModules"));
-      }
-
-      return m_nativeModules.getModule(m_context, propertyName);
-    }
-
-    JSValueRef JSCExecutor::getNativeExtension(JSObjectRef object, JSStringRef propertyName) {
-      if (m_nativeExtensionsProvider) {
-        folly::dynamic value = m_nativeExtensionsProvider(String::ref(m_context, propertyName).str());
-        return Value::fromDynamic(m_context, std::move(value));
-      }
-      return JSC_JSValueMakeUndefined(m_context);
-    }
-
-    JSValueRef JSCExecutor::nativeRequire(size_t count, const JSValueRef arguments[]) {
-      if (count > 2 || count == 0) {
-        throw std::invalid_argument("Got wrong number of args");
-      }
-
-      uint32_t moduleId = folly::to<uint32_t>(Value(m_context, arguments[0]).getNumberOrThrow());
-      uint32_t bundleId = count == 2 ? folly::to<uint32_t>(Value(m_context, arguments[1]).getNumberOrThrow()) : 0;
-
-      ReactMarker::logMarker(ReactMarker::NATIVE_REQUIRE_START);
-      loadModule(bundleId, moduleId);
-      ReactMarker::logMarker(ReactMarker::NATIVE_REQUIRE_STOP);
-      return Value::makeUndefined(m_context);
-    }
-
-    JSValueRef JSCExecutor::nativeFlushQueueImmediate(
-                                                      size_t argumentCount,
-                                                      const JSValueRef arguments[]) {
-      if (argumentCount != 1) {
-        throw std::invalid_argument("Got wrong number of args");
-      }
-
-      flushQueueImmediate(Value(m_context, arguments[0]));
-      return Value::makeUndefined(m_context);
-    }
-
-    JSValueRef JSCExecutor::nativeCallSyncHook(
-                                               size_t argumentCount,
-                                               const JSValueRef arguments[]) {
-      if (argumentCount != 3) {
-        throw std::invalid_argument("Got wrong number of args");
-      }
-
-      unsigned int moduleId = Value(m_context, arguments[0]).asUnsignedInteger();
-      unsigned int methodId = Value(m_context, arguments[1]).asUnsignedInteger();
-      folly::dynamic args = folly::parseJson(Value(m_context, arguments[2]).toJSONString());
-
-      if (!args.isArray()) {
-        throw std::invalid_argument(
-                                    folly::to<std::string>("method parameters should be array, but are ", args.typeName()));
-      }
-
-      MethodCallResult result = m_delegate->callSerializableNativeHook(
-                                                                       *this,
-                                                                       moduleId,
-                                                                       methodId,
-                                                                       std::move(args));
-      if (!result.hasValue()) {
-        return Value::makeUndefined(m_context);
-      }
-      return Value::fromDynamic(m_context, result.value());
-    }
-
-  } }
+void JSCExecutor::flushQueueImmediate(Value&& queue) {
+  auto queueStr = queue.toJSONString();
+  m_delegate->callNativeModules(*this, folly::parseJson(queueStr), false);
+}
+
+void JSCExecutor::loadModule(uint32_t bundleId, uint32_t moduleId) {
+  auto module = m_bundleRegistry->getModule(bundleId, moduleId);
+  auto sourceUrl = String::createExpectingAscii(m_context, module.name);
+  auto source = adoptString(
+      std::unique_ptr<JSBigString>(new JSBigStdString(module.code)));
+  evaluateScript(m_context, source, sourceUrl);
+}
+
+// Native JS hooks
+template <JSValueRef (JSCExecutor::*method)(size_t, const JSValueRef[])>
+void JSCExecutor::installNativeHook(const char* name) {
+  installGlobalFunction(m_context, name, exceptionWrapMethod<method>());
+}
+
+JSValueRef JSCExecutor::getNativeModule(
+    JSObjectRef object,
+    JSStringRef propertyName) {
+  if (JSC_JSStringIsEqualToUTF8CString(m_context, propertyName, "name")) {
+    return Value(m_context, String(m_context, "NativeModules"));
+  }
+
+  return m_nativeModules.getModule(m_context, propertyName);
+}
+
+JSValueRef JSCExecutor::getNativeExtension(
+    JSObjectRef object,
+    JSStringRef propertyName) {
+  if (m_nativeExtensionsProvider) {
+    folly::dynamic value =
+        m_nativeExtensionsProvider(String::ref(m_context, propertyName).str());
+    return Value::fromDynamic(m_context, std::move(value));
+  }
+  return JSC_JSValueMakeUndefined(m_context);
+}
+
+JSValueRef JSCExecutor::nativeRequire(
+    size_t count,
+    const JSValueRef arguments[]) {
+  if (count > 2 || count == 0) {
+    throw std::invalid_argument("Got wrong number of args");
+  }
+
+  uint32_t moduleId =
+      folly::to<uint32_t>(Value(m_context, arguments[0]).getNumberOrThrow());
+  uint32_t bundleId = count == 2
+      ? folly::to<uint32_t>(Value(m_context, arguments[1]).getNumberOrThrow())
+      : 0;
+
+  ReactMarker::logMarker(ReactMarker::NATIVE_REQUIRE_START);
+  loadModule(bundleId, moduleId);
+  ReactMarker::logMarker(ReactMarker::NATIVE_REQUIRE_STOP);
+  return Value::makeUndefined(m_context);
+}
+
+JSValueRef JSCExecutor::nativeFlushQueueImmediate(
+    size_t argumentCount,
+    const JSValueRef arguments[]) {
+  if (argumentCount != 1) {
+    throw std::invalid_argument("Got wrong number of args");
+  }
+
+  flushQueueImmediate(Value(m_context, arguments[0]));
+  return Value::makeUndefined(m_context);
+}
+
+JSValueRef JSCExecutor::nativeCallSyncHook(
+    size_t argumentCount,
+    const JSValueRef arguments[]) {
+  if (argumentCount != 3) {
+    throw std::invalid_argument("Got wrong number of args");
+  }
+
+  unsigned int moduleId = Value(m_context, arguments[0]).asUnsignedInteger();
+  unsigned int methodId = Value(m_context, arguments[1]).asUnsignedInteger();
+  folly::dynamic args =
+      folly::parseJson(Value(m_context, arguments[2]).toJSONString());
+
+  if (!args.isArray()) {
+    throw std::invalid_argument(folly::to<std::string>(
+        "method parameters should be array, but are ", args.typeName()));
+  }
+
+  MethodCallResult result = m_delegate->callSerializableNativeHook(
+      *this, moduleId, methodId, std::move(args));
+  if (!result.hasValue()) {
+    return Value::makeUndefined(m_context);
+  }
+  return Value::fromDynamic(m_context, result.value());
+}
+
+} // namespace react
+} // namespace facebook

From 042449f24adbf1b36036fbe6bf1c8a869021010e Mon Sep 17 00:00:00 2001
From: Marc Horowitz <mhorowitz@fb.com>
Date: Wed, 9 May 2018 22:01:50 -0700
Subject: [PATCH 0492/1109] simplify handleMemoryPressure conditionalization,
 delete some dead code

Reviewed By: javache

Differential Revision: D7803912

fbshipit-source-id: 0bab4be07fc006a208caa75f94b5716c99b5d265
---
 ReactAndroid/src/main/jni/react/jni/BUCK                     | 1 -
 ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp | 2 --
 ReactCommon/cxxreact/Instance.cpp                            | 2 --
 ReactCommon/cxxreact/Instance.h                              | 3 ---
 ReactCommon/cxxreact/JSCExecutor.cpp                         | 4 ++--
 ReactCommon/cxxreact/JSCExecutor.h                           | 2 --
 ReactCommon/cxxreact/NativeToJsBridge.cpp                    | 3 +--
 ReactCommon/cxxreact/NativeToJsBridge.h                      | 3 ---
 8 files changed, 3 insertions(+), 17 deletions(-)

diff --git a/ReactAndroid/src/main/jni/react/jni/BUCK b/ReactAndroid/src/main/jni/react/jni/BUCK
index dc0f2a76d55c..e79a63dbde71 100644
--- a/ReactAndroid/src/main/jni/react/jni/BUCK
+++ b/ReactAndroid/src/main/jni/react/jni/BUCK
@@ -47,7 +47,6 @@ rn_xplat_cxx_library(
         "-DLOG_TAG=\"ReactNativeJNI\"",
         "-DWITH_FBSYSTRACE=1",
         "-DWITH_INSPECTOR=1",
-        "-DWITH_JSC_MEMORY_PRESSURE=1",
     ],
     soname = "libreactnativejni.$(ext)",
     visibility = [
diff --git a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
index aeb4cc55e109..0c5cf5c8f68e 100644
--- a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
@@ -259,9 +259,7 @@ jlong CatalystInstanceImpl::getJavaScriptContext() {
 }
 
 void CatalystInstanceImpl::handleMemoryPressure(int pressureLevel) {
-  #ifdef WITH_JSC_MEMORY_PRESSURE
   instance_->handleMemoryPressure(pressureLevel);
-  #endif
 }
 
 }}
diff --git a/ReactCommon/cxxreact/Instance.cpp b/ReactCommon/cxxreact/Instance.cpp
index c3fd8cf607dd..534f4b981cd8 100644
--- a/ReactCommon/cxxreact/Instance.cpp
+++ b/ReactCommon/cxxreact/Instance.cpp
@@ -170,11 +170,9 @@ const ModuleRegistry &Instance::getModuleRegistry() const {
 
 ModuleRegistry &Instance::getModuleRegistry() { return *moduleRegistry_; }
 
-#ifdef WITH_JSC_MEMORY_PRESSURE
 void Instance::handleMemoryPressure(int pressureLevel) {
   nativeToJsBridge_->handleMemoryPressure(pressureLevel);
 }
-#endif
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/cxxreact/Instance.h b/ReactCommon/cxxreact/Instance.h
index e35ce4bbe2ac..dffbe72465dd 100644
--- a/ReactCommon/cxxreact/Instance.h
+++ b/ReactCommon/cxxreact/Instance.h
@@ -6,7 +6,6 @@
 #include <memory>
 
 #include <cxxreact/NativeToJsBridge.h>
-#include <jschelpers/Value.h>
 
 #ifndef RN_EXPORT
 #define RN_EXPORT __attribute__((visibility("default")))
@@ -66,9 +65,7 @@ class RN_EXPORT Instance {
   const ModuleRegistry &getModuleRegistry() const;
   ModuleRegistry &getModuleRegistry();
 
-#ifdef WITH_JSC_MEMORY_PRESSURE
   void handleMemoryPressure(int pressureLevel);
-#endif
 
 private:
   void callNativeModules(folly::dynamic &&calls, bool isEndOfBatch);
diff --git a/ReactCommon/cxxreact/JSCExecutor.cpp b/ReactCommon/cxxreact/JSCExecutor.cpp
index c88da5f5b7a3..d20c97a15424 100644
--- a/ReactCommon/cxxreact/JSCExecutor.cpp
+++ b/ReactCommon/cxxreact/JSCExecutor.cpp
@@ -696,12 +696,12 @@ bool JSCExecutor::isInspectable() {
   return canUseInspector(m_context);
 }
 
-#ifdef WITH_JSC_MEMORY_PRESSURE
 void JSCExecutor::handleMemoryPressure(int pressureLevel) {
+#ifdef WITH_JSC_MEMORY_PRESSURE
   JSHandleMemoryPressure(
       this, m_context, static_cast<JSMemoryPressure>(pressureLevel));
-}
 #endif
+}
 
 void JSCExecutor::flushQueueImmediate(Value&& queue) {
   auto queueStr = queue.toJSONString();
diff --git a/ReactCommon/cxxreact/JSCExecutor.h b/ReactCommon/cxxreact/JSCExecutor.h
index 44b13aa94b2a..b85e590d7136 100644
--- a/ReactCommon/cxxreact/JSCExecutor.h
+++ b/ReactCommon/cxxreact/JSCExecutor.h
@@ -89,9 +89,7 @@ class RN_EXPORT JSCExecutor : public JSExecutor, public PrivateDataBase {
 
   virtual bool isInspectable() override;
 
-#ifdef WITH_JSC_MEMORY_PRESSURE
   virtual void handleMemoryPressure(int pressureLevel) override;
-#endif
 
   virtual void destroy() override;
 
diff --git a/ReactCommon/cxxreact/NativeToJsBridge.cpp b/ReactCommon/cxxreact/NativeToJsBridge.cpp
index f8ae2856e602..3cf374f068df 100644
--- a/ReactCommon/cxxreact/NativeToJsBridge.cpp
+++ b/ReactCommon/cxxreact/NativeToJsBridge.cpp
@@ -11,6 +11,7 @@
 #include "SystraceSection.h"
 #include "MethodCall.h"
 #include "MessageQueueThread.h"
+#include "ModuleRegistry.h"
 #include "RAMBundleRegistry.h"
 
 #ifdef WITH_FBSYSTRACE
@@ -194,13 +195,11 @@ bool NativeToJsBridge::isInspectable() {
   return m_executor->isInspectable();
 }
 
-#ifdef WITH_JSC_MEMORY_PRESSURE
 void NativeToJsBridge::handleMemoryPressure(int pressureLevel) {
   runOnExecutorQueue([=] (JSExecutor* executor) {
     executor->handleMemoryPressure(pressureLevel);
   });
 }
-#endif
 
 void NativeToJsBridge::destroy() {
   // All calls made through runOnExecutorQueue have an early exit if
diff --git a/ReactCommon/cxxreact/NativeToJsBridge.h b/ReactCommon/cxxreact/NativeToJsBridge.h
index 78d960a08a45..7e7aaf77ee21 100644
--- a/ReactCommon/cxxreact/NativeToJsBridge.h
+++ b/ReactCommon/cxxreact/NativeToJsBridge.h
@@ -7,7 +7,6 @@
 #include <map>
 #include <vector>
 
-#include <cxxreact/JSCExecutor.h>
 #include <cxxreact/JSExecutor.h>
 
 namespace folly {
@@ -74,9 +73,7 @@ class NativeToJsBridge {
   void* getJavaScriptContext();
   bool isInspectable();
 
-  #ifdef WITH_JSC_MEMORY_PRESSURE
   void handleMemoryPressure(int pressureLevel);
-  #endif
 
   /**
    * Synchronously tears down the bridge and the main executor.

From a363a7b501dece8fcc9ba8c95689d2177e8862a3 Mon Sep 17 00:00:00 2001
From: Marc Horowitz <mhorowitz@fb.com>
Date: Wed, 9 May 2018 22:01:53 -0700
Subject: [PATCH 0493/1109] Refactor ReactMarker out of Platform

Reviewed By: fromcelticpark

Differential Revision: D7803908

fbshipit-source-id: 957e80519c209732b163ece2bccb7c8c36ff8107
---
 React/CxxBridge/RCTCxxBridge.mm               |  1 +
 React/React.xcodeproj/project.pbxproj         | 14 +++++++
 .../src/main/jni/react/jni/Android.mk         |  2 +-
 .../main/jni/react/jni/AndroidJSCFactory.cpp  |  2 +-
 ReactAndroid/src/main/jni/react/jni/BUCK      |  2 +-
 .../jni/{ReactMarker.cpp => JReactMarker.cpp} |  5 +--
 .../jni/{ReactMarker.h => JReactMarker.h}     |  3 +-
 ReactCommon/cxxreact/Android.mk               |  3 +-
 ReactCommon/cxxreact/BUCK                     |  1 +
 ReactCommon/cxxreact/JSCExecutor.cpp          |  2 +-
 ReactCommon/cxxreact/JSCNativeModules.cpp     |  3 +-
 ReactCommon/cxxreact/JSCNativeModules.h       |  3 +-
 ReactCommon/cxxreact/Platform.cpp             |  9 ----
 ReactCommon/cxxreact/Platform.h               | 28 +------------
 ReactCommon/cxxreact/ReactMarker.cpp          | 26 ++++++++++++
 ReactCommon/cxxreact/ReactMarker.h            | 41 +++++++++++++++++++
 16 files changed, 98 insertions(+), 47 deletions(-)
 rename ReactAndroid/src/main/jni/react/jni/{ReactMarker.cpp => JReactMarker.cpp} (95%)
 rename ReactAndroid/src/main/jni/react/jni/{ReactMarker.h => JReactMarker.h} (94%)
 create mode 100644 ReactCommon/cxxreact/ReactMarker.cpp
 create mode 100644 ReactCommon/cxxreact/ReactMarker.h

diff --git a/React/CxxBridge/RCTCxxBridge.mm b/React/CxxBridge/RCTCxxBridge.mm
index 2517e2949192..6fa0813996e9 100644
--- a/React/CxxBridge/RCTCxxBridge.mm
+++ b/React/CxxBridge/RCTCxxBridge.mm
@@ -33,6 +33,7 @@
 #import <cxxreact/JSBundleType.h>
 #import <cxxreact/JSCExecutor.h>
 #import <cxxreact/JSIndexedRAMBundle.h>
+#import <cxxreact/ModuleRegistry.h>
 #import <cxxreact/Platform.h>
 #import <cxxreact/RAMBundleRegistry.h>
 #import <jschelpers/Value.h>
diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index ab260bb49534..1f6f9f2eef69 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -51,6 +51,7 @@
 		133957881DF76D3500EC27BE /* YGEnums.h in Headers */ = {isa = PBXBuildFile; fileRef = 130A77031DF767AF001F9587 /* YGEnums.h */; };
 		133957891DF76D3500EC27BE /* YGMacros.h in Headers */ = {isa = PBXBuildFile; fileRef = 130A77041DF767AF001F9587 /* YGMacros.h */; };
 		1339578B1DF76D3500EC27BE /* Yoga.h in Headers */ = {isa = PBXBuildFile; fileRef = 130A77081DF767AF001F9587 /* Yoga.h */; };
+		133EA4E52098F6E30035B1D8 /* ReactMarker.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 13DA8A2F2097A90A00276ED4 /* ReactMarker.h */; };
 		13456E931ADAD2DE009F94A7 /* RCTConvert+CoreLocation.m in Sources */ = {isa = PBXBuildFile; fileRef = 13456E921ADAD2DE009F94A7 /* RCTConvert+CoreLocation.m */; };
 		134D63C31F1FEC4B008872B5 /* RCTCxxBridgeDelegate.h in Headers */ = {isa = PBXBuildFile; fileRef = 134D63C21F1FEC4B008872B5 /* RCTCxxBridgeDelegate.h */; };
 		134D63C41F1FEC65008872B5 /* RCTCxxBridgeDelegate.h in Headers */ = {isa = PBXBuildFile; fileRef = 134D63C21F1FEC4B008872B5 /* RCTCxxBridgeDelegate.h */; };
@@ -127,6 +128,10 @@
 		13D033631C1837FE0021DC29 /* RCTClipboard.m in Sources */ = {isa = PBXBuildFile; fileRef = 13D033621C1837FE0021DC29 /* RCTClipboard.m */; };
 		13D9FEEB1CDCCECF00158BD7 /* RCTEventEmitter.m in Sources */ = {isa = PBXBuildFile; fileRef = 13D9FEEA1CDCCECF00158BD7 /* RCTEventEmitter.m */; };
 		13D9FEEE1CDCD93000158BD7 /* RCTKeyboardObserver.m in Sources */ = {isa = PBXBuildFile; fileRef = 13D9FEED1CDCD93000158BD7 /* RCTKeyboardObserver.m */; };
+		13DA8A312097A90B00276ED4 /* ReactMarker.h in Headers */ = {isa = PBXBuildFile; fileRef = 13DA8A2F2097A90A00276ED4 /* ReactMarker.h */; };
+		13DA8A322097A90B00276ED4 /* ReactMarker.h in Headers */ = {isa = PBXBuildFile; fileRef = 13DA8A2F2097A90A00276ED4 /* ReactMarker.h */; };
+		13DA8A332097A90B00276ED4 /* ReactMarker.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 13DA8A302097A90B00276ED4 /* ReactMarker.cpp */; };
+		13DA8A342097A90B00276ED4 /* ReactMarker.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 13DA8A302097A90B00276ED4 /* ReactMarker.cpp */; };
 		13E0674A1A70F434002CDEE1 /* RCTUIManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E067491A70F434002CDEE1 /* RCTUIManager.m */; };
 		13E067561A70F44B002CDEE1 /* RCTViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E0674E1A70F44B002CDEE1 /* RCTViewManager.m */; };
 		13E067571A70F44B002CDEE1 /* RCTView.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E067501A70F44B002CDEE1 /* RCTView.m */; };
@@ -1756,6 +1761,7 @@
 			dstPath = include/cxxreact;
 			dstSubfolderSpec = 16;
 			files = (
+				133EA4E52098F6E30035B1D8 /* ReactMarker.h in Copy Headers */,
 				C669D8981F72E3DE006748EB /* RAMBundleRegistry.h in Copy Headers */,
 				3DA981A01E5B0E34004F2374 /* CxxModule.h in Copy Headers */,
 				3DA981A11E5B0E34004F2374 /* CxxNativeModule.h in Copy Headers */,
@@ -2017,6 +2023,8 @@
 		13D9FEEA1CDCCECF00158BD7 /* RCTEventEmitter.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTEventEmitter.m; sourceTree = "<group>"; };
 		13D9FEEC1CDCD93000158BD7 /* RCTKeyboardObserver.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTKeyboardObserver.h; sourceTree = "<group>"; };
 		13D9FEED1CDCD93000158BD7 /* RCTKeyboardObserver.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTKeyboardObserver.m; sourceTree = "<group>"; };
+		13DA8A2F2097A90A00276ED4 /* ReactMarker.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ReactMarker.h; sourceTree = "<group>"; };
+		13DA8A302097A90B00276ED4 /* ReactMarker.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ReactMarker.cpp; sourceTree = "<group>"; };
 		13E067481A70F434002CDEE1 /* RCTUIManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTUIManager.h; sourceTree = "<group>"; };
 		13E067491A70F434002CDEE1 /* RCTUIManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTUIManager.m; sourceTree = "<group>"; };
 		13E0674B1A70F44B002CDEE1 /* RCTShadowView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTShadowView.h; sourceTree = "<group>"; };
@@ -3041,6 +3049,8 @@
 		AC70D2EA1DE489FC002E6351 /* cxxreact */ = {
 			isa = PBXGroup;
 			children = (
+				13DA8A302097A90B00276ED4 /* ReactMarker.cpp */,
+				13DA8A2F2097A90A00276ED4 /* ReactMarker.h */,
 				E223624320875A8000108244 /* JSExecutor.cpp */,
 				3D92B0A71E03699D0018521A /* CxxModule.h */,
 				3D92B0A81E03699D0018521A /* CxxNativeModule.cpp */,
@@ -3329,6 +3339,7 @@
 			isa = PBXHeadersBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
+				13DA8A322097A90B00276ED4 /* ReactMarker.h in Headers */,
 				3D74547E1E54759A00E74ADD /* JSModulesUnbundle.h in Headers */,
 				C6D3801B1F71D76200621378 /* RAMBundleRegistry.h in Headers */,
 				27595AD51E575C7800CCE2B1 /* NativeToJsBridge.h in Headers */,
@@ -3423,6 +3434,7 @@
 			isa = PBXHeadersBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
+				13DA8A312097A90B00276ED4 /* ReactMarker.h in Headers */,
 				3D74547F1E54759E00E74ADD /* JSModulesUnbundle.h in Headers */,
 				C6D3801A1F71D76100621378 /* RAMBundleRegistry.h in Headers */,
 				27595ABA1E575C7800CCE2B1 /* NativeToJsBridge.h in Headers */,
@@ -4405,6 +4417,7 @@
 				13F8876E1E29726200C3C7A1 /* CxxNativeModule.cpp in Sources */,
 				13F887721E29726200C3C7A1 /* JSCExecutor.cpp in Sources */,
 				13F887741E29726200C3C7A1 /* JSCLegacyTracing.cpp in Sources */,
+				13DA8A332097A90B00276ED4 /* ReactMarker.cpp in Sources */,
 				13F887771E29726200C3C7A1 /* JSCPerfStats.cpp in Sources */,
 				13F887711E29726200C3C7A1 /* JSBundleType.cpp in Sources */,
 				13F887791E29726200C3C7A1 /* JSCUtils.cpp in Sources */,
@@ -4430,6 +4443,7 @@
 				13F887851E29726300C3C7A1 /* JSCExecutor.cpp in Sources */,
 				13F887871E29726300C3C7A1 /* JSCLegacyTracing.cpp in Sources */,
 				13F8878A1E29726300C3C7A1 /* JSCPerfStats.cpp in Sources */,
+				13DA8A342097A90B00276ED4 /* ReactMarker.cpp in Sources */,
 				13F887841E29726300C3C7A1 /* Instance.cpp in Sources */,
 				13F8878C1E29726300C3C7A1 /* JSCUtils.cpp in Sources */,
 				13F8878B1E29726300C3C7A1 /* JSCSamplingProfiler.cpp in Sources */,
diff --git a/ReactAndroid/src/main/jni/react/jni/Android.mk b/ReactAndroid/src/main/jni/react/jni/Android.mk
index 313950674e13..8fe31894cdff 100644
--- a/ReactAndroid/src/main/jni/react/jni/Android.mk
+++ b/ReactAndroid/src/main/jni/react/jni/Android.mk
@@ -9,6 +9,7 @@ LOCAL_SRC_FILES := \
   CatalystInstanceImpl.cpp \
   CxxModuleWrapper.cpp \
   JavaModuleWrapper.cpp \
+  JReactMarker.cpp \
   JMessageQueueThread.cpp \
   JSCPerfLogging.cpp \
   JSLoader.cpp \
@@ -22,7 +23,6 @@ LOCAL_SRC_FILES := \
   NativeMap.cpp \
   OnLoad.cpp \
   ProxyExecutor.cpp \
-  ReactMarker.cpp \
   ReadableNativeArray.cpp \
   ReadableNativeMap.cpp \
   WritableNativeArray.cpp \
diff --git a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
index 73d774e7d5d8..88b80bd47d6b 100644
--- a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
@@ -13,7 +13,7 @@
 
 #include "JSCPerfLogging.h"
 #include "JSLogging.h"
-#include "ReactMarker.h"
+#include "JReactMarker.h"
 
 using namespace facebook::jni;
 
diff --git a/ReactAndroid/src/main/jni/react/jni/BUCK b/ReactAndroid/src/main/jni/react/jni/BUCK
index e79a63dbde71..1272b44f4abd 100644
--- a/ReactAndroid/src/main/jni/react/jni/BUCK
+++ b/ReactAndroid/src/main/jni/react/jni/BUCK
@@ -7,6 +7,7 @@ EXPORTED_HEADERS = [
     "CxxSharedModuleWrapper.h",
     "JavaModuleWrapper.h",
     "JavaScriptExecutorHolder.h",
+    "JReactMarker.h",
     "JSLoader.h",
     "JSLogging.h",
     "MethodInvoker.h",
@@ -14,7 +15,6 @@ EXPORTED_HEADERS = [
     "NativeArray.h",
     "NativeCommon.h",
     "NativeMap.h",
-    "ReactMarker.h",
     "ReadableNativeArray.h",
     "ReadableNativeMap.h",
     "WritableNativeArray.h",
diff --git a/ReactAndroid/src/main/jni/react/jni/ReactMarker.cpp b/ReactAndroid/src/main/jni/react/jni/JReactMarker.cpp
similarity index 95%
rename from ReactAndroid/src/main/jni/react/jni/ReactMarker.cpp
rename to ReactAndroid/src/main/jni/react/jni/JReactMarker.cpp
index c4680eedff24..e210aedca7fb 100644
--- a/ReactAndroid/src/main/jni/react/jni/ReactMarker.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JReactMarker.cpp
@@ -1,9 +1,8 @@
 // Copyright 2004-present Facebook. All Rights Reserved.
 
-#include "ReactMarker.h"
+#include "JReactMarker.h"
 #include <mutex>
-#include <cxxreact/Platform.h>
-#include <jschelpers/JSCHelpers.h>
+#include <cxxreact/ReactMarker.h>
 #include <fb/fbjni.h>
 
 namespace facebook {
diff --git a/ReactAndroid/src/main/jni/react/jni/ReactMarker.h b/ReactAndroid/src/main/jni/react/jni/JReactMarker.h
similarity index 94%
rename from ReactAndroid/src/main/jni/react/jni/ReactMarker.h
rename to ReactAndroid/src/main/jni/react/jni/JReactMarker.h
index 7f918c77cbcf..6a46d083c40e 100644
--- a/ReactAndroid/src/main/jni/react/jni/ReactMarker.h
+++ b/ReactAndroid/src/main/jni/react/jni/JReactMarker.h
@@ -4,7 +4,8 @@
 
 #include <string>
 #include <fb/fbjni.h>
-#include <cxxreact/Platform.h>
+
+#include <cxxreact/ReactMarker.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/cxxreact/Android.mk b/ReactCommon/cxxreact/Android.mk
index 8efb42a3a150..d4b294fc17fe 100644
--- a/ReactCommon/cxxreact/Android.mk
+++ b/ReactCommon/cxxreact/Android.mk
@@ -24,7 +24,8 @@ LOCAL_SRC_FILES := \
   ModuleRegistry.cpp \
   NativeToJsBridge.cpp \
   Platform.cpp \
-	RAMBundleRegistry.cpp \
+  RAMBundleRegistry.cpp \
+  ReactMarker.cpp \
 
 LOCAL_C_INCLUDES := $(LOCAL_PATH)/..
 LOCAL_EXPORT_C_INCLUDES := $(LOCAL_C_INCLUDES)
diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index c5b958918f7b..4a30b0e11c28 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -102,6 +102,7 @@ CXXREACT_PUBLIC_HEADERS = [
     "NativeToJsBridge.h",
     "Platform.h",
     "RAMBundleRegistry.h",
+    "ReactMarker.h",
     "RecoverableError.h",
     "SharedProxyCxxModule.h",
     "SystraceSection.h",
diff --git a/ReactCommon/cxxreact/JSCExecutor.cpp b/ReactCommon/cxxreact/JSCExecutor.cpp
index d20c97a15424..2f1f24fd9676 100644
--- a/ReactCommon/cxxreact/JSCExecutor.cpp
+++ b/ReactCommon/cxxreact/JSCExecutor.cpp
@@ -27,12 +27,12 @@
 #include "JSBundleType.h"
 #include "JSCLegacyTracing.h"
 #include "JSCMemory.h"
-#include "JSCNativeModules.h"
 #include "JSCPerfStats.h"
 #include "JSCSamplingProfiler.h"
 #include "JSCTracing.h"
 #include "JSCUtils.h"
 #include "JSModulesUnbundle.h"
+#include "MessageQueueThread.h"
 #include "ModuleRegistry.h"
 #include "Platform.h"
 #include "RAMBundleRegistry.h"
diff --git a/ReactCommon/cxxreact/JSCNativeModules.cpp b/ReactCommon/cxxreact/JSCNativeModules.cpp
index 63380dfa6806..1a440086c486 100644
--- a/ReactCommon/cxxreact/JSCNativeModules.cpp
+++ b/ReactCommon/cxxreact/JSCNativeModules.cpp
@@ -4,7 +4,8 @@
 
 #include <string>
 
-#include "Platform.h"
+#include "ModuleRegistry.h"
+#include "ReactMarker.h"
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/cxxreact/JSCNativeModules.h b/ReactCommon/cxxreact/JSCNativeModules.h
index 38b2c1d30d90..e81e98d2a795 100644
--- a/ReactCommon/cxxreact/JSCNativeModules.h
+++ b/ReactCommon/cxxreact/JSCNativeModules.h
@@ -5,13 +5,14 @@
 #include <memory>
 #include <string>
 
-#include <cxxreact/ModuleRegistry.h>
 #include <folly/Optional.h>
 #include <jschelpers/Value.h>
 
 namespace facebook {
 namespace react {
 
+class ModuleRegistry;
+
 /**
  * Holds and creates JS representations of the modules in ModuleRegistry
  */
diff --git a/ReactCommon/cxxreact/Platform.cpp b/ReactCommon/cxxreact/Platform.cpp
index b1a069d489c2..c4aeb2e0e700 100644
--- a/ReactCommon/cxxreact/Platform.cpp
+++ b/ReactCommon/cxxreact/Platform.cpp
@@ -10,15 +10,6 @@ namespace react {
 #pragma clang diagnostic ignored "-Wglobal-constructors"
 #endif
 
-namespace ReactMarker {
-
-LogTaggedMarker logTaggedMarker = nullptr;
-void logMarker(const ReactMarkerId markerId) {
-  logTaggedMarker(markerId, nullptr);
-}
-
-}
-
 namespace JSCNativeHooks {
 
 Hook loggingHook = nullptr;
diff --git a/ReactCommon/cxxreact/Platform.h b/ReactCommon/cxxreact/Platform.h
index c8a63c746bca..be9c1737ec15 100644
--- a/ReactCommon/cxxreact/Platform.h
+++ b/ReactCommon/cxxreact/Platform.h
@@ -6,8 +6,7 @@
 #include <memory>
 #include <string>
 
-#include <cxxreact/JSExecutor.h>
-#include <cxxreact/MessageQueueThread.h>
+#include <cxxreact/ReactMarker.h>
 #include <jschelpers/JavaScriptCore.h>
 
 #ifndef RN_EXPORT
@@ -17,31 +16,6 @@
 namespace facebook {
 namespace react {
 
-namespace ReactMarker {
-
-enum ReactMarkerId {
-  NATIVE_REQUIRE_START,
-  NATIVE_REQUIRE_STOP,
-  RUN_JS_BUNDLE_START,
-  RUN_JS_BUNDLE_STOP,
-  CREATE_REACT_CONTEXT_STOP,
-  JS_BUNDLE_STRING_CONVERT_START,
-  JS_BUNDLE_STRING_CONVERT_STOP,
-  NATIVE_MODULE_SETUP_START,
-  NATIVE_MODULE_SETUP_STOP,
-};
-
-#ifdef __APPLE__
-using LogTaggedMarker = std::function<void(const ReactMarkerId, const char* tag)>;
-#else
-typedef void(*LogTaggedMarker)(const ReactMarkerId, const char* tag);
-#endif
-extern RN_EXPORT LogTaggedMarker logTaggedMarker;
-
-extern void logMarker(const ReactMarkerId markerId);
-
-}
-
 namespace JSCNativeHooks {
 
 using Hook = JSValueRef(*)(
diff --git a/ReactCommon/cxxreact/ReactMarker.cpp b/ReactCommon/cxxreact/ReactMarker.cpp
new file mode 100644
index 000000000000..f2c28c404b37
--- /dev/null
+++ b/ReactCommon/cxxreact/ReactMarker.cpp
@@ -0,0 +1,26 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#include "ReactMarker.h"
+
+namespace facebook {
+namespace react {
+namespace ReactMarker {
+
+#if __clang__
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wglobal-constructors"
+#endif
+
+LogTaggedMarker logTaggedMarker = nullptr;
+
+#if __clang__
+#pragma clang diagnostic pop
+#endif
+
+void logMarker(const ReactMarkerId markerId) {
+  logTaggedMarker(markerId, nullptr);
+}
+
+}
+}
+}
diff --git a/ReactCommon/cxxreact/ReactMarker.h b/ReactCommon/cxxreact/ReactMarker.h
new file mode 100644
index 000000000000..26f84ea35e73
--- /dev/null
+++ b/ReactCommon/cxxreact/ReactMarker.h
@@ -0,0 +1,41 @@
+// Copyright 2004-present Facebook. All Rights Reserved.
+
+#pragma once
+
+#ifdef __APPLE__
+#include <functional>
+#endif
+
+namespace facebook {
+namespace react {
+namespace ReactMarker {
+
+enum ReactMarkerId {
+  NATIVE_REQUIRE_START,
+  NATIVE_REQUIRE_STOP,
+  RUN_JS_BUNDLE_START,
+  RUN_JS_BUNDLE_STOP,
+  CREATE_REACT_CONTEXT_STOP,
+  JS_BUNDLE_STRING_CONVERT_START,
+  JS_BUNDLE_STRING_CONVERT_STOP,
+  NATIVE_MODULE_SETUP_START,
+  NATIVE_MODULE_SETUP_STOP,
+};
+
+#ifdef __APPLE__
+using LogTaggedMarker = std::function<void(const ReactMarkerId, const char* tag)>;
+#else
+typedef void(*LogTaggedMarker)(const ReactMarkerId, const char* tag);
+#endif
+
+#ifndef RN_EXPORT
+#define RN_EXPORT __attribute__((visibility("default")))
+#endif
+
+extern RN_EXPORT LogTaggedMarker logTaggedMarker;
+
+extern void logMarker(const ReactMarkerId markerId);
+
+}
+}
+}

From a810e6875fc5b6d1e1545c34910a109450b5aacd Mon Sep 17 00:00:00 2001
From: Marc Horowitz <mhorowitz@fb.com>
Date: Wed, 9 May 2018 22:01:58 -0700
Subject: [PATCH 0494/1109] move nativeLoggingHook into AndroidJSCFactory

Reviewed By: fromcelticpark

Differential Revision: D7803905

fbshipit-source-id: 797f5250a4a129a8dff3fb447c01837d68bea452
---
 .../main/jni/react/jni/AndroidJSCFactory.cpp  | 23 ++++++++++++++++
 .../src/main/jni/react/jni/JSLogging.cpp      | 26 -------------------
 .../src/main/jni/react/jni/JSLogging.h        | 10 -------
 3 files changed, 23 insertions(+), 36 deletions(-)

diff --git a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
index 88b80bd47d6b..5208152f54a9 100644
--- a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
@@ -74,6 +74,29 @@ JSValueRef nativePerformanceNow(
   return Value::makeNumber(ctx, (nano / (double)NANOSECONDS_IN_MILLISECOND));
 }
 
+JSValueRef nativeLoggingHook(
+  JSContextRef ctx,
+  JSObjectRef function,
+  JSObjectRef thisObject,
+  size_t argumentCount,
+  const JSValueRef arguments[],
+  JSValueRef* exception) {
+  android_LogPriority logLevel = ANDROID_LOG_DEBUG;
+  if (argumentCount > 1) {
+    int level = (int)Value(ctx, arguments[1]).asNumber();
+    // The lowest log level we get from JS is 0. We shift and cap it to be
+    // in the range the Android logging method expects.
+    logLevel = std::min(
+      static_cast<android_LogPriority>(level + ANDROID_LOG_DEBUG),
+      ANDROID_LOG_FATAL);
+  }
+  if (argumentCount > 0) {
+    String message = Value(ctx, arguments[0]).toString();
+    reactAndroidLoggingHook(message.str(), logLevel);
+  }
+  return Value::makeUndefined(ctx);
+}
+
 }
 
 namespace detail {
diff --git a/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp b/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
index e178542157e0..02cd21ddd755 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
@@ -3,36 +3,10 @@
 #include "JSLogging.h"
 
 #include <fb/log.h>
-#include <algorithm>
-
-#include <jschelpers/Value.h>
 
 namespace facebook {
 namespace react {
 
-JSValueRef nativeLoggingHook(
-    JSContextRef ctx,
-    JSObjectRef function,
-    JSObjectRef thisObject,
-    size_t argumentCount,
-    const JSValueRef arguments[],
-    JSValueRef* exception) {
-  android_LogPriority logLevel = ANDROID_LOG_DEBUG;
-  if (argumentCount > 1) {
-    int level = (int)Value(ctx, arguments[1]).asNumber();
-    // The lowest log level we get from JS is 0. We shift and cap it to be
-    // in the range the Android logging method expects.
-    logLevel = std::min(
-        static_cast<android_LogPriority>(level + ANDROID_LOG_DEBUG),
-        ANDROID_LOG_FATAL);
-  }
-  if (argumentCount > 0) {
-    String message = Value(ctx, arguments[0]).toString();
-    reactAndroidLoggingHook(message.str(), logLevel);
-  }
-  return Value::makeUndefined(ctx);
-}
-
 void reactAndroidLoggingHook(
     const std::string& message,
     android_LogPriority logLevel) {
diff --git a/ReactAndroid/src/main/jni/react/jni/JSLogging.h b/ReactAndroid/src/main/jni/react/jni/JSLogging.h
index 5e4e99143a29..aaf5718ccf15 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSLogging.h
+++ b/ReactAndroid/src/main/jni/react/jni/JSLogging.h
@@ -5,19 +5,9 @@
 #include <android/log.h>
 #include <string>
 
-#include <JavaScriptCore/JSContextRef.h>
-
 namespace facebook {
 namespace react {
 
-JSValueRef nativeLoggingHook(
-    JSContextRef ctx,
-    JSObjectRef function,
-    JSObjectRef thisObject,
-    size_t argumentCount,
-    const JSValueRef arguments[],
-    JSValueRef* exception);
-
 void reactAndroidLoggingHook(
     const std::string& message,
     android_LogPriority logLevel);

From 9d0b7d8f31c7045d6b68ec03d48e617c4c0f07bb Mon Sep 17 00:00:00 2001
From: Marc Horowitz <mhorowitz@fb.com>
Date: Wed, 9 May 2018 22:02:01 -0700
Subject: [PATCH 0495/1109] Fix BUCK bugs which were breaking tests after
 refactoring

Reviewed By: johnislarry

Differential Revision: D7874275

fbshipit-source-id: 7f9c8648571bc7f41649ec4ef547e7c34b479221
---
 ReactCommon/cxxreact/BUCK       | 1 +
 ReactCommon/cxxreact/tests/BUCK | 6 +++---
 2 files changed, 4 insertions(+), 3 deletions(-)

diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 4a30b0e11c28..9fa2e3aa4043 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -141,6 +141,7 @@ rn_xplat_cxx_library(
     ],
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_deps = APPLE_JSC_DEPS,
+    fbobjc_force_static = True,
     fbobjc_frameworks = [
         "$SDKROOT/System/Library/Frameworks/JavaScriptCore.framework",
     ],
diff --git a/ReactCommon/cxxreact/tests/BUCK b/ReactCommon/cxxreact/tests/BUCK
index e78b7692b1d7..67160139c882 100644
--- a/ReactCommon/cxxreact/tests/BUCK
+++ b/ReactCommon/cxxreact/tests/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "APPLE_JSC_DEPS", "ANDROID_JSC_DEPS")
 
 TEST_SRCS = [
     "RecoverableErrorTest.cpp",
@@ -28,7 +28,7 @@ if not IS_OSS_BUILD:
             'xplat//third-party/linker_lib:android',
             'xplat//third-party/gmock:gtest',
             react_native_xplat_target('cxxreact:bridge'),
-        ],
+        ] + ANDROID_JSC_DEPS,
         visibility = [
             'fbandroid//instrumentation_tests/...'
         ],
@@ -47,7 +47,7 @@ if not IS_OSS_BUILD:
             'xplat//third-party/gmock:gtest',
             react_native_xplat_target('cxxreact:bridge'),
             react_native_xplat_target('jschelpers:jschelpers'),
-        ],
+        ] + APPLE_JSC_DEPS,
         visibility = [
             react_native_xplat_target('cxxreact/...'),
         ],

From 3bc2696d652184fc4676f2fbba1d56e604428d03 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Wed, 9 May 2018 23:26:39 -0700
Subject: [PATCH 0496/1109] Update Android docker images

Summary:
Quick update to switch to a new React Native CI org on Docker Hub. Note that the images are not yet automatically generated on CI. We could do this on Circle CI in certain scenarios:

- Base image needs to be updated whenever the Android development environment has changed (e.g. switch to a new SDK version, build tools, etc)
- Tests image should ideally be updated on each commit

This PR should be safe to land as Circle CI is not yet using these images.
Closes https://github.com/facebook/react-native/pull/19192

Differential Revision: D7939209

Pulled By: hramos

fbshipit-source-id: 0f845a8fffbf8f5b9cecef4fa0ba802bc755f7aa
---
 ContainerShip/Dockerfile.android      | 10 +++++++++-
 ContainerShip/Dockerfile.android-base | 15 +++++++++++++++
 package.json                          |  6 +++---
 3 files changed, 27 insertions(+), 4 deletions(-)

diff --git a/ContainerShip/Dockerfile.android b/ContainerShip/Dockerfile.android
index f7a207aea3e5..a72a4b64403e 100644
--- a/ContainerShip/Dockerfile.android
+++ b/ContainerShip/Dockerfile.android
@@ -1,4 +1,12 @@
-FROM hramos/android-base:latest
+# React Native Android Unit Tests
+#
+# This image builds upon the React Native Base Android Development Environment
+# image. Ideally, this image would be rebuilt with any new commit to the master
+# branch. Doing so will catch issues such as BUCK failing to fetch dependencies
+# or run tests, as well as unit test failures.
+FROM reactnativeci/android-base:latest
+
+LABEL Description="This image prepares and runs React Native's Android tests." maintainer "Héctor Ramos <hector@fb.com>"
 
 # set default environment variables
 ENV GRADLE_OPTS="-Dorg.gradle.daemon=false -Dorg.gradle.jvmargs=\"-Xmx512m -XX:+HeapDumpOnOutOfMemoryError\""
diff --git a/ContainerShip/Dockerfile.android-base b/ContainerShip/Dockerfile.android-base
index 93a1aafa8117..083903341e07 100644
--- a/ContainerShip/Dockerfile.android-base
+++ b/ContainerShip/Dockerfile.android-base
@@ -1,5 +1,20 @@
+# React Native Base Android Development Environment
+#
+# This image provides a base Android development environment for React Native,
+# including, but not limited to, the Android SDK, Android NDK, Node, and BUCK.
+# These are required in order to run React Native's Android unit and integration
+# tests.
+#
+# This image is not currently built automatically as part of React Native's CI
+# infrastructure. It should not be necessary to rebuild this image while the
+# Android dependencies (Android SDK version, build tools version, etc) remain
+# equal. The operations performed to build this image are those that tend to
+# remain stable across commits in any given React Native release.
+
 FROM library/ubuntu:16.04
 
+LABEL Description="This image provides a base Android development environment for React Native, and may be used to run tests." maintainer "Héctor Ramos <hector@fb.com>"
+
 # set default build arguments
 ARG ANDROID_TOOLS_VERSION=25.2.5
 ARG BUCK_VERSION=v2018.02.16.01
diff --git a/package.json b/package.json
index 02d8deb8c636..f345d3909531 100644
--- a/package.json
+++ b/package.json
@@ -128,9 +128,9 @@
     "lint": "eslint .",
     "prettier": "find . -name node_modules -prune -or -name '*.js' -print | xargs prettier --write",
     "start": "/usr/bin/env bash -c './scripts/packager.sh \"$@\" || true' --",
-    "docker-setup-android": "docker pull hramos/android-base:latest",
-    "docker-build-android-base": "docker build -t hramos/android-base -f ContainerShip/Dockerfile.android-base .",
-    "docker-build-android": "docker build -t react/android -f ContainerShip/Dockerfile.android .",
+    "docker-setup-android": "docker pull reactnativeci/android-base:latest",
+    "docker-build-android-base": "docker build -t reactnativeci/android-base -f ContainerShip/Dockerfile.android-base .",
+    "docker-build-android": "docker build -t reactnativeci/android -f ContainerShip/Dockerfile.android .",
     "test-android-run-instrumentation": "docker run --cap-add=SYS_ADMIN -it react/android bash ContainerShip/scripts/run-android-docker-instrumentation-tests.sh",
     "test-android-run-unit": "docker run --cap-add=SYS_ADMIN -it react/android bash ContainerShip/scripts/run-android-docker-unit-tests.sh",
     "test-android-run-e2e": "docker run --privileged -it react/android bash ContainerShip/scripts/run-ci-e2e-tests.sh --android --js",

From c2c352024f3cc5c3f26cc4cc75b6672b53d4982a Mon Sep 17 00:00:00 2001
From: Andrey Mishanin <amishanin@fb.com>
Date: Thu, 10 May 2018 01:43:01 -0700
Subject: [PATCH 0497/1109] Back out "[react-native][PR] Prevent console
 logging on iOS 11.3+ within WebSocket"

Differential Revision:
D7947829
Ninja: master broken

fbshipit-source-id: 282c574897684ce48e9e7461067805a3ec5c1de1
---
 .../WebSocket/RCTReconnectingWebSocket.m      | 28 -------------------
 1 file changed, 28 deletions(-)

diff --git a/Libraries/WebSocket/RCTReconnectingWebSocket.m b/Libraries/WebSocket/RCTReconnectingWebSocket.m
index 55ed86f7b229..04e5dee57b67 100644
--- a/Libraries/WebSocket/RCTReconnectingWebSocket.m
+++ b/Libraries/WebSocket/RCTReconnectingWebSocket.m
@@ -19,29 +19,6 @@
 
 #if RCT_DEV // Only supported in dev mode
 
-#if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 100300 /* __IPHONE_10_3 */
-
-// From https://github.com/apple/swift/blob/ad40c770bfe372f879b530443a3d94761fe258a6/stdlib/public/SDK/os/os_log.m
-typedef struct os_log_pack_s {
-  uint64_t olp_continuous_time;
-  struct timespec olp_wall_time;
-  const void *olp_mh;
-  const void *olp_pc;
-  const char *olp_format;
-  uint8_t olp_data[0];
-} os_log_pack_s, *os_log_pack_t;
-
-static void (*orig__nwlog_pack)(os_log_pack_t pack, os_log_type_t logType);
-
-static void my__nwlog_pack(os_log_pack_t pack, os_log_type_t logType)
-{
-  if (logType == OS_LOG_TYPE_ERROR && strstr(pack->olp_format, "Connection has no connected handler") == NULL) {
-    orig__nwlog_pack(pack, logType);
-  }
-}
-
-#endif /* __IPHONE_10_3 */
-
 static void (*orig_nwlog_legacy_v)(int, char*, va_list);
 
 static void my_nwlog_legacy_v(int level, char *format, va_list args) {
@@ -86,11 +63,6 @@ + (void)load
     rebind_symbols((struct rebinding[1]){
       {"nwlog_legacy_v", my_nwlog_legacy_v, (void *)&orig_nwlog_legacy_v}
     }, 1);
-#if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 100300 /* __IPHONE_10_3 */
-    rebind_symbols((struct rebinding[1]){
-      {"__nwlog_pack", my__nwlog_pack, (void *)&orig__nwlog_pack}
-    }, 1);
-#endif /* __IPHONE_10_3 */
 #if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
     rebind_symbols((struct rebinding[1]){
       {"_os_log_error_impl", my_os_log_error_impl, (void *)&orig_os_log_error_impl}

From d4d515cdc34858ba2c41353184ed83f7922033c0 Mon Sep 17 00:00:00 2001
From: Riley Dulin <dulinr@fb.com>
Date: Thu, 10 May 2018 10:45:36 -0700
Subject: [PATCH 0498/1109] MessageQueue not initializing inCall

Reviewed By: yungsters

Differential Revision: D7898700

fbshipit-source-id: c2b4d6e75e7f5871cd40b00bd173e6f1a929b26a
---
 Libraries/BatchedBridge/MessageQueue.js | 6 +-----
 1 file changed, 1 insertion(+), 5 deletions(-)

diff --git a/Libraries/BatchedBridge/MessageQueue.js b/Libraries/BatchedBridge/MessageQueue.js
index 93a759154cb0..a5208d81b70d 100644
--- a/Libraries/BatchedBridge/MessageQueue.js
+++ b/Libraries/BatchedBridge/MessageQueue.js
@@ -46,7 +46,6 @@ class MessageQueue {
   _successCallbacks: {[key: number]: ?Function};
   _failureCallbacks: {[key: number]: ?Function};
   _callID: number;
-  _inCall: number;
   _lastFlush: number;
   _eventLoopStartTime: number;
 
@@ -248,8 +247,7 @@ class MessageQueue {
     const now = new Date().getTime();
     if (
       global.nativeFlushQueueImmediate &&
-      (now - this._lastFlush >= MIN_TIME_BETWEEN_FLUSHES_MS ||
-        this._inCall === 0)
+      now - this._lastFlush >= MIN_TIME_BETWEEN_FLUSHES_MS
     ) {
       var queue = this._queue;
       this._queue = [[], [], [], this._callID];
@@ -286,7 +284,6 @@ class MessageQueue {
    */
 
   __guard(fn: () => void) {
-    this._inCall++;
     if (this.__shouldPauseOnThrow()) {
       fn();
     } else {
@@ -296,7 +293,6 @@ class MessageQueue {
         ErrorUtils.reportFatalError(error);
       }
     }
-    this._inCall--;
   }
 
   // MessageQueue installs a global handler to catch all exceptions where JS users can register their own behavior

From 266016c521f9f5c0effe56ade85036b300eaa684 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 10 May 2018 15:00:30 -0700
Subject: [PATCH 0499/1109] iOS: Mark Scheduler class as final

Summary:
This fixes some build flavor:

```
error: destructor called on non-final 'facebook::react::Scheduler' that has virtual functions but non-virtual destructor [-Werror,-Wdelete-non-virtual-dtor]
```

Reviewed By: shergin

Differential Revision: D7958022

fbshipit-source-id: 6ff64bdaa221b5c6430a98244d40d6d3789ba937
---
 ReactCommon/fabric/uimanager/Scheduler.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index cadbc4caa2ed..c3730a03346f 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -21,7 +21,7 @@ class FabricUIManager;
 /*
  * Scheduler coordinates Shadow Tree updates and event flows.
  */
-class Scheduler:
+class Scheduler final:
   public UIManagerDelegate,
   public ShadowTreeDelegate {
 

From 8f5ebe5952d0675b463137103a82f3fb0c26ae0d Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Thu, 10 May 2018 15:44:52 -0700
Subject: [PATCH 0500/1109] Convert react-native-github/Libraries to let/const

Reviewed By: sahrens

Differential Revision: D7956042

fbshipit-source-id: 221851aa311f3cdd6326497352b366048db0a1bb
---
 Libraries/ART/ARTSerializablePath.js          |  16 +-
 Libraries/ART/ReactNativeART.js               | 158 ++++++-------
 Libraries/Alert/Alert.js                      |  10 +-
 Libraries/Alert/AlertIOS.js                   |  16 +-
 Libraries/Alert/RCTAlertManager.android.js    |   2 +-
 Libraries/Alert/RCTAlertManager.ios.js        |   2 +-
 Libraries/Animated/src/AnimatedWeb.js         |   2 +-
 .../Animated/src/NativeAnimatedHelper.js      |   4 +-
 Libraries/Animated/src/SpringConfig.js        |   8 +-
 .../Animated/src/__tests__/Animated-test.js   | 210 +++++++++---------
 .../Animated/src/__tests__/Easing-test.js     |  42 ++--
 .../src/__tests__/Interpolation-test.js       |  42 ++--
 .../Animated/src/__tests__/bezier-test.js     |  49 ++--
 Libraries/Animated/src/bezier.js              |  38 ++--
 .../__mocks__/MessageQueueTestConfig.js       |   4 +-
 .../__mocks__/MessageQueueTestModule.js       |   2 +-
 Libraries/Blob/__tests__/Blob-test.js         |   2 +-
 Libraries/Blob/__tests__/BlobManager-test.js  |   4 +-
 Libraries/Blob/__tests__/FileReader-test.js   |   4 +-
 Libraries/BugReporting/getReactData.js        |  36 +--
 Libraries/CameraRoll/ImagePickerIOS.js        |   4 +-
 Libraries/Color/normalizeColor.js             |  36 +--
 .../__tests__/parseErrorStack-test.js         |  10 +-
 Libraries/Core/__mocks__/ErrorUtils.js        |   2 +-
 Libraries/Experimental/IncrementalExample.js  |   2 +-
 Libraries/Geolocation/Geolocation.js          |  22 +-
 Libraries/Image/AssetRegistry.js              |   2 +-
 Libraries/Image/AssetSourceResolver.js        |  14 +-
 Libraries/Image/Image.android.js              |  42 ++--
 Libraries/Image/ImageResizeMode.js            |   4 +-
 Libraries/Image/ImageStylePropTypes.js        |  14 +-
 Libraries/Image/RelativeImageStub.js          |   2 +-
 .../__tests__/resolveAssetSource-test.js      |  14 +-
 Libraries/Image/resolveAssetSource.js         |   2 +-
 Libraries/Inspector/BorderBox.js              |   8 +-
 Libraries/Inspector/BoxInspector.js           |  24 +-
 Libraries/Inspector/ElementBox.js             |  24 +-
 Libraries/Inspector/InspectorOverlay.js       |  20 +-
 Libraries/Inspector/PerformanceOverlay.js     |  20 +-
 Libraries/Inspector/StyleInspector.js         |  14 +-
 Libraries/Inspector/resolveBoxStyle.js        |   8 +-
 Libraries/Interaction/InteractionManager.js   |   8 +-
 Libraries/Interaction/InteractionMixin.js     |   6 +-
 .../__tests__/InteractionMixin-test.js        |  12 +-
 Libraries/Lists/ListView/ListView.js          | 138 ++++++------
 .../Lists/ListView/ListViewDataSource.js      |  60 ++---
 Libraries/Modal/Modal.js                      |   2 +-
 Libraries/Network/FormData.js                 |   4 +-
 Libraries/Network/XHRInterceptor.js           |  12 +-
 Libraries/Network/XMLHttpRequest.js           |   6 +-
 .../PushNotificationIOS.js                    |   8 +-
 Libraries/RCTTest/SnapshotViewIOS.ios.js      |  20 +-
 Libraries/ReactNative/UIManagerStatTracker.js |  16 +-
 Libraries/ReactNative/YellowBox.js            |   2 +-
 Libraries/ReactNative/queryLayoutByID.js      |   4 +-
 Libraries/Sample/Sample.android.js            |   4 +-
 Libraries/Sample/Sample.ios.js                |   4 +-
 Libraries/Settings/Settings.android.js        |   2 +-
 Libraries/Settings/Settings.ios.js            |  16 +-
 Libraries/Storage/AsyncStorage.js             |  24 +-
 Libraries/StyleSheet/ColorPropType.js         |   8 +-
 Libraries/StyleSheet/LayoutPropTypes.js       |   4 +-
 Libraries/StyleSheet/PointPropType.js         |   6 +-
 Libraries/StyleSheet/StyleSheetPropType.js    |   8 +-
 Libraries/StyleSheet/StyleSheetValidation.js  |  22 +-
 Libraries/StyleSheet/TransformPropTypes.js    |  10 +-
 .../StyleSheet/__tests__/flattenStyle-test.js |  24 +-
 .../__tests__/normalizeColor-test.js          |   2 +-
 .../StyleSheet/__tests__/processColor-test.js |  36 +--
 .../__tests__/setNormalizedColorAlpha-test.js |   6 +-
 Libraries/StyleSheet/flattenStyle.js          |   8 +-
 Libraries/StyleSheet/processTransform.js      |  28 +--
 Libraries/Text/TextUpdateTest.js              |  16 +-
 Libraries/Utilities/BackAndroid.js            |   6 +-
 Libraries/Utilities/BackHandler.android.js    |  16 +-
 Libraries/Utilities/BackHandler.ios.js        |   8 +-
 Libraries/Utilities/Dimensions.js             |  14 +-
 Libraries/Utilities/HMRLoadingView.android.js |   2 +-
 Libraries/Utilities/HeapCapture.js            |   4 +-
 Libraries/Utilities/MatrixMath.js             | 111 +++++----
 Libraries/Utilities/PixelRatio.js             |   4 +-
 .../Utilities/__tests__/MatrixMath-test.js    |   8 +-
 .../Utilities/__tests__/Platform-test.js      |   4 +-
 .../__tests__/buildStyleInterpolator-test.js  |  68 +++---
 .../deepFreezeAndThrowOnMutationInDev-test.js |  20 +-
 .../Utilities/__tests__/groupByEveryN-test.js |   2 +-
 .../Utilities/__tests__/truncate-test.js      |   2 +-
 Libraries/Utilities/buildStyleInterpolator.js |  86 +++----
 .../Utilities/createStrictShapeTypeChecker.js |  18 +-
 .../deepFreezeAndThrowOnMutationInDev.js      |   2 +-
 .../differ/__tests__/deepDiffer-test.js       |   4 +-
 Libraries/Utilities/differ/deepDiffer.js      |  10 +-
 Libraries/Utilities/differ/insetsDiffer.js    |   4 +-
 Libraries/Utilities/differ/matricesDiffer.js  |   2 +-
 Libraries/Utilities/differ/pointsDiffer.js    |   4 +-
 Libraries/Utilities/differ/sizesDiffer.js     |   4 +-
 Libraries/Utilities/dismissKeyboard.js        |   2 +-
 Libraries/Utilities/groupByEveryN.js          |   6 +-
 Libraries/Utilities/logError.js               |   4 +-
 Libraries/Utilities/mergeIntoFast.js          |   4 +-
 Libraries/Utilities/stringifySafe.js          |   4 +-
 Libraries/Utilities/truncate.js               |   4 +-
 Libraries/Vibration/Vibration.js              |  10 +-
 Libraries/Vibration/VibrationIOS.android.js   |   4 +-
 Libraries/Vibration/VibrationIOS.ios.js       |   6 +-
 .../WebSocket/__tests__/WebSocket-test.js     |   2 +-
 Libraries/vendor/core/Map.js                  |  72 +++---
 Libraries/vendor/core/Set.js                  |  18 +-
 .../core/_shouldPolyfillES6Collection.js      |   4 +-
 Libraries/vendor/core/getObjectValues.js      |   4 +-
 Libraries/vendor/core/isEmpty.js              |   2 +-
 Libraries/vendor/core/mergeHelpers.js         |   8 +-
 Libraries/vendor/core/toIterator.js           |  30 +--
 .../selection/DocumentSelectionState.js       |   2 +-
 114 files changed, 1018 insertions(+), 1036 deletions(-)

diff --git a/Libraries/ART/ARTSerializablePath.js b/Libraries/ART/ARTSerializablePath.js
index 08c4530222df..de02f9498d06 100644
--- a/Libraries/ART/ARTSerializablePath.js
+++ b/Libraries/ART/ARTSerializablePath.js
@@ -9,16 +9,16 @@
 
 // TODO: Move this into an ART mode called "serialized" or something
 
-var Class = require('art/core/class.js');
-var Path = require('art/core/path.js');
+const Class = require('art/core/class.js');
+const Path = require('art/core/path.js');
 
-var MOVE_TO = 0;
-var CLOSE = 1;
-var LINE_TO = 2;
-var CURVE_TO = 3;
-var ARC = 4;
+const MOVE_TO = 0;
+const CLOSE = 1;
+const LINE_TO = 2;
+const CURVE_TO = 3;
+const ARC = 4;
 
-var SerializablePath = Class(Path, {
+const SerializablePath = Class(Path, {
 
   initialize: function(path) {
     this.reset();
diff --git a/Libraries/ART/ReactNativeART.js b/Libraries/ART/ReactNativeART.js
index 9b0a725cd140..0f32fa2dae2a 100644
--- a/Libraries/ART/ReactNativeART.js
+++ b/Libraries/ART/ReactNativeART.js
@@ -7,17 +7,17 @@
  */
 'use strict';
 
-var Color = require('art/core/color');
-var Path = require('ARTSerializablePath');
-var Transform = require('art/core/transform');
+const Color = require('art/core/color');
+const Path = require('ARTSerializablePath');
+const Transform = require('art/core/transform');
 
-var React = require('React');
-var PropTypes = require('prop-types');
-var ReactNativeViewAttributes = require('ReactNativeViewAttributes');
+const React = require('React');
+const PropTypes = require('prop-types');
+const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 
-var createReactNativeComponentClass = require('createReactNativeComponentClass');
-var merge = require('merge');
-var invariant = require('fbjs/lib/invariant');
+const createReactNativeComponentClass = require('createReactNativeComponentClass');
+const merge = require('merge');
+const invariant = require('fbjs/lib/invariant');
 
 // Diff Helpers
 
@@ -28,7 +28,7 @@ function arrayDiffer(a, b) {
   if (a.length !== b.length) {
     return true;
   }
-  for (var i = 0; i < a.length; i++) {
+  for (let i = 0; i < a.length; i++) {
     if (a[i] !== b[i]) {
       return true;
     }
@@ -62,22 +62,22 @@ function fontAndLinesDiffer(a, b) {
 
 // Native Attributes
 
-var SurfaceViewAttributes = merge(ReactNativeViewAttributes.UIView, {
+const SurfaceViewAttributes = merge(ReactNativeViewAttributes.UIView, {
   // This should contain pixel information such as width, height and
   // resolution to know what kind of buffer needs to be allocated.
   // Currently we rely on UIViews and style to figure that out.
 });
 
-var NodeAttributes = {
+const NodeAttributes = {
   transform: { diff: arrayDiffer },
   opacity: true,
 };
 
-var GroupAttributes = merge(NodeAttributes, {
+const GroupAttributes = merge(NodeAttributes, {
   clipping: { diff: arrayDiffer }
 });
 
-var RenderableAttributes = merge(NodeAttributes, {
+const RenderableAttributes = merge(NodeAttributes, {
   fill: { diff: arrayDiffer },
   stroke: { diff: arrayDiffer },
   strokeWidth: true,
@@ -86,11 +86,11 @@ var RenderableAttributes = merge(NodeAttributes, {
   strokeDash: { diff: arrayDiffer },
 });
 
-var ShapeAttributes = merge(RenderableAttributes, {
+const ShapeAttributes = merge(RenderableAttributes, {
   d: { diff: arrayDiffer },
 });
 
-var TextAttributes = merge(RenderableAttributes, {
+const TextAttributes = merge(RenderableAttributes, {
   alignment: true,
   frame: { diff: fontAndLinesDiffer },
   path: { diff: arrayDiffer }
@@ -98,25 +98,25 @@ var TextAttributes = merge(RenderableAttributes, {
 
 // Native Components
 
-var NativeSurfaceView = createReactNativeComponentClass('ARTSurfaceView',
+const NativeSurfaceView = createReactNativeComponentClass('ARTSurfaceView',
   () => ({
     validAttributes: SurfaceViewAttributes,
     uiViewClassName: 'ARTSurfaceView',
   }));
 
-var NativeGroup = createReactNativeComponentClass('ARTGroup',
+const NativeGroup = createReactNativeComponentClass('ARTGroup',
   () => ({
     validAttributes: GroupAttributes,
     uiViewClassName: 'ARTGroup',
   }));
 
-var NativeShape = createReactNativeComponentClass('ARTShape',
+const NativeShape = createReactNativeComponentClass('ARTShape',
   () => ({
     validAttributes: ShapeAttributes,
     uiViewClassName: 'ARTShape',
   }));
 
-var NativeText = createReactNativeComponentClass('ARTText',
+const NativeText = createReactNativeComponentClass('ARTText',
   () => ({
     validAttributes: TextAttributes,
     uiViewClassName: 'ARTText',
@@ -149,9 +149,9 @@ class Surface extends React.Component {
   }
 
   render() {
-    var props = this.props;
-    var w = extractNumber(props.width, 0);
-    var h = extractNumber(props.height, 0);
+    const props = this.props;
+    const w = extractNumber(props.width, 0);
+    const h = extractNumber(props.height, 0);
     return (
       <NativeSurfaceView style={[props.style, { width: w, height: h }]}>
         {this.props.children}
@@ -172,12 +172,12 @@ function extractNumber(value, defaultValue) {
   return +value;
 }
 
-var pooledTransform = new Transform();
+const pooledTransform = new Transform();
 
 function extractTransform(props) {
-  var scaleX = props.scaleX != null ? props.scaleX :
+  const scaleX = props.scaleX != null ? props.scaleX :
                props.scale != null ? props.scale : 1;
-  var scaleY = props.scaleY != null ? props.scaleY :
+  const scaleY = props.scaleY != null ? props.scaleY :
                props.scale != null ? props.scale : 1;
 
   pooledTransform
@@ -219,7 +219,7 @@ class Group extends React.Component {
   };
 
   render() {
-    var props = this.props;
+    const props = this.props;
     invariant(
       this.context.isInSurface,
       'ART: <Group /> must be a child of a <Surface />'
@@ -236,14 +236,14 @@ class Group extends React.Component {
 
 class ClippingRectangle extends React.Component {
   render() {
-    var props = this.props;
-    var x = extractNumber(props.x, 0);
-    var y = extractNumber(props.y, 0);
-    var w = extractNumber(props.width, 0);
-    var h = extractNumber(props.height, 0);
-    var clipping = [x, y, w, h];
+    const props = this.props;
+    const x = extractNumber(props.x, 0);
+    const y = extractNumber(props.y, 0);
+    const w = extractNumber(props.width, 0);
+    const h = extractNumber(props.height, 0);
+    const clipping = [x, y, w, h];
     // The current clipping API requires x and y to be ignored in the transform
-    var propsExcludingXAndY = merge(props);
+    const propsExcludingXAndY = merge(props);
     delete propsExcludingXAndY.x;
     delete propsExcludingXAndY.y;
     return (
@@ -259,13 +259,13 @@ class ClippingRectangle extends React.Component {
 
 // Renderables
 
-var SOLID_COLOR = 0;
-var LINEAR_GRADIENT = 1;
-var RADIAL_GRADIENT = 2;
-var PATTERN = 3;
+const SOLID_COLOR = 0;
+const LINEAR_GRADIENT = 1;
+const RADIAL_GRADIENT = 2;
+const PATTERN = 3;
 
 function insertColorIntoArray(color, targetArray, atIndex) {
-  var c = new Color(color);
+  const c = new Color(color);
   targetArray[atIndex + 0] = c.red / 255;
   targetArray[atIndex + 1] = c.green / 255;
   targetArray[atIndex + 2] = c.blue / 255;
@@ -273,14 +273,14 @@ function insertColorIntoArray(color, targetArray, atIndex) {
 }
 
 function insertColorsIntoArray(stops, targetArray, atIndex) {
-  var i = 0;
+  let i = 0;
   if ('length' in stops) {
     while (i < stops.length) {
       insertColorIntoArray(stops[i], targetArray, atIndex + i * 4);
       i++;
     }
   } else {
-    for (var offset in stops) {
+    for (const offset in stops) {
       insertColorIntoArray(stops[offset], targetArray, atIndex + i * 4);
       i++;
     }
@@ -289,8 +289,8 @@ function insertColorsIntoArray(stops, targetArray, atIndex) {
 }
 
 function insertOffsetsIntoArray(stops, targetArray, atIndex, multi, reverse) {
-  var offsetNumber;
-  var i = 0;
+  let offsetNumber;
+  let i = 0;
   if ('length' in stops) {
     while (i < stops.length) {
       offsetNumber = i / (stops.length - 1) * multi;
@@ -298,7 +298,7 @@ function insertOffsetsIntoArray(stops, targetArray, atIndex, multi, reverse) {
       i++;
     }
   } else {
-    for (var offsetString in stops) {
+    for (const offsetString in stops) {
       offsetNumber = (+offsetString) * multi;
       targetArray[atIndex + i] = reverse ? 1 - offsetNumber : offsetNumber;
       i++;
@@ -308,21 +308,21 @@ function insertOffsetsIntoArray(stops, targetArray, atIndex, multi, reverse) {
 }
 
 function insertColorStopsIntoArray(stops, targetArray, atIndex) {
-  var lastIndex = insertColorsIntoArray(stops, targetArray, atIndex);
+  const lastIndex = insertColorsIntoArray(stops, targetArray, atIndex);
   insertOffsetsIntoArray(stops, targetArray, lastIndex, 1, false);
 }
 
 function insertDoubleColorStopsIntoArray(stops, targetArray, atIndex) {
-  var lastIndex = insertColorsIntoArray(stops, targetArray, atIndex);
+  let lastIndex = insertColorsIntoArray(stops, targetArray, atIndex);
   lastIndex = insertColorsIntoArray(stops, targetArray, lastIndex);
   lastIndex = insertOffsetsIntoArray(stops, targetArray, lastIndex, 0.5, false);
   insertOffsetsIntoArray(stops, targetArray, lastIndex, 0.5, true);
 }
 
 function applyBoundingBoxToBrushData(brushData, props) {
-  var type = brushData[0];
-  var width = +props.width;
-  var height = +props.height;
+  const type = brushData[0];
+  const width = +props.width;
+  const height = +props.height;
   if (type === LINEAR_GRADIENT) {
     brushData[1] *= width;
     brushData[2] *= height;
@@ -356,7 +356,7 @@ function extractBrush(colorOrBrush, props) {
     }
     return colorOrBrush._brush;
   }
-  var c = new Color(colorOrBrush);
+  const c = new Color(colorOrBrush);
   return [SOLID_COLOR, c.red / 255, c.green / 255, c.blue / 255, c.alpha];
 }
 
@@ -364,7 +364,7 @@ function extractColor(color) {
   if (color == null) {
     return null;
   }
-  var c = new Color(color);
+  const c = new Color(color);
   return [c.red / 255, c.green / 255, c.blue / 255, c.alpha];
 }
 
@@ -391,9 +391,9 @@ function extractStrokeJoin(strokeJoin) {
 
 class Shape extends React.Component {
   render() {
-    var props = this.props;
-    var path = props.d || childrenAsString(props.children);
-    var d = (path instanceof Path ? path : new Path(path)).toJSON();
+    const props = this.props;
+    const path = props.d || childrenAsString(props.children);
+    const d = (path instanceof Path ? path : new Path(path)).toJSON();
     return (
       <NativeShape
         fill={extractBrush(props.fill, props)}
@@ -413,10 +413,10 @@ class Shape extends React.Component {
 
 // Text
 
-var cachedFontObjectsFromString = {};
+const cachedFontObjectsFromString = {};
 
-var fontFamilyPrefix = /^[\s"']*/;
-var fontFamilySuffix = /[\s"']*$/;
+const fontFamilyPrefix = /^[\s"']*/;
+const fontFamilySuffix = /[\s"']*$/;
 
 function extractSingleFontFamily(fontFamilyString) {
   // ART on the web allows for multiple font-families to be specified.
@@ -431,15 +431,15 @@ function parseFontString(font) {
   if (cachedFontObjectsFromString.hasOwnProperty(font)) {
     return cachedFontObjectsFromString[font];
   }
-  var regexp = /^\s*((?:(?:normal|bold|italic)\s+)*)(?:(\d+(?:\.\d+)?)[ptexm\%]*(?:\s*\/.*?)?\s+)?\s*\"?([^\"]*)/i;
-  var match = regexp.exec(font);
+  const regexp = /^\s*((?:(?:normal|bold|italic)\s+)*)(?:(\d+(?:\.\d+)?)[ptexm\%]*(?:\s*\/.*?)?\s+)?\s*\"?([^\"]*)/i;
+  const match = regexp.exec(font);
   if (!match) {
     return null;
   }
-  var fontFamily = extractSingleFontFamily(match[3]);
-  var fontSize = +match[2] || 12;
-  var isBold = /bold/.exec(match[1]);
-  var isItalic = /italic/.exec(match[1]);
+  const fontFamily = extractSingleFontFamily(match[3]);
+  const fontSize = +match[2] || 12;
+  const isBold = /bold/.exec(match[1]);
+  const isItalic = /italic/.exec(match[1]);
   cachedFontObjectsFromString[font] = {
     fontFamily: fontFamily,
     fontSize: fontSize,
@@ -456,9 +456,9 @@ function extractFont(font) {
   if (typeof font === 'string') {
     return parseFontString(font);
   }
-  var fontFamily = extractSingleFontFamily(font.fontFamily);
-  var fontSize = +font.fontSize || 12;
-  var fontWeight = font.fontWeight != null ? font.fontWeight.toString() : '400';
+  const fontFamily = extractSingleFontFamily(font.fontFamily);
+  const fontSize = +font.fontSize || 12;
+  const fontWeight = font.fontWeight != null ? font.fontWeight.toString() : '400';
   return {
     // Normalize
     fontFamily: fontFamily,
@@ -468,7 +468,7 @@ function extractFont(font) {
   };
 }
 
-var newLine = /\n/g;
+const newLine = /\n/g;
 function extractFontAndLines(font, text) {
   return { font: extractFont(font), lines: text.split(newLine) };
 }
@@ -486,10 +486,10 @@ function extractAlignment(alignment) {
 
 class Text extends React.Component {
   render() {
-    var props = this.props;
-    var path = props.path;
-    var textPath = path ? (path instanceof Path ? path : new Path(path)).toJSON() : null;
-    var textFrame = extractFontAndLines(
+    const props = this.props;
+    const path = props.path;
+    const textPath = path ? (path instanceof Path ? path : new Path(path)).toJSON() : null;
+    const textFrame = extractFontAndLines(
       props.font,
       childrenAsString(props.children)
     );
@@ -515,14 +515,14 @@ class Text extends React.Component {
 // Declarative fill type objects - API design not finalized
 
 function LinearGradient(stops, x1, y1, x2, y2) {
-  var type = LINEAR_GRADIENT;
+  const type = LINEAR_GRADIENT;
 
   if (arguments.length < 5) {
-    var angle = ((x1 == null) ? 270 : x1) * Math.PI / 180;
+    const angle = ((x1 == null) ? 270 : x1) * Math.PI / 180;
 
-    var x = Math.cos(angle);
-    var y = -Math.sin(angle);
-    var l = (Math.abs(x) + Math.abs(y)) / 2;
+    let x = Math.cos(angle);
+    let y = -Math.sin(angle);
+    const l = (Math.abs(x) + Math.abs(y)) / 2;
 
     x *= l; y *= l;
 
@@ -535,7 +535,7 @@ function LinearGradient(stops, x1, y1, x2, y2) {
     this._bb = false;
   }
 
-  var brushData = [type, +x1, +y1, +x2, +y2];
+  const brushData = [type, +x1, +y1, +x2, +y2];
   insertColorStopsIntoArray(stops, brushData, 5);
   this._brush = brushData;
 }
@@ -562,7 +562,7 @@ function RadialGradient(stops, fx, fy, rx, ry, cx, cy) {
   // To simulate this we render the gradient twice as large and add double
   // color stops. Ideally this API would become more restrictive so that this
   // extra work isn't needed.
-  var brushData = [RADIAL_GRADIENT, +fx, +fy, +rx * 2, +ry * 2, +cx, +cy];
+  const brushData = [RADIAL_GRADIENT, +fx, +fy, +rx * 2, +ry * 2, +cx, +cy];
   insertDoubleColorStopsIntoArray(stops, brushData, 7);
   this._brush = brushData;
 }
@@ -571,7 +571,7 @@ function Pattern(url, width, height, left, top) {
   this._brush = [PATTERN, url, +left || 0, +top || 0, +width, +height];
 }
 
-var ReactART = {
+const ReactART = {
   LinearGradient: LinearGradient,
   RadialGradient: RadialGradient,
   Pattern: Pattern,
diff --git a/Libraries/Alert/Alert.js b/Libraries/Alert/Alert.js
index ed78335043c5..76c1f516db72 100644
--- a/Libraries/Alert/Alert.js
+++ b/Libraries/Alert/Alert.js
@@ -68,7 +68,7 @@ class AlertAndroid {
     buttons?: Buttons,
     options?: Options,
   ): void {
-    var config = {
+    let config = {
       title: title || '',
       message: message || '',
     };
@@ -78,10 +78,10 @@ class AlertAndroid {
     }
     // At most three buttons (neutral, negative, positive). Ignore rest.
     // The text 'OK' should be probably localized. iOS Alert does that in native.
-    var validButtons: Buttons = buttons ? buttons.slice(0, 3) : [{text: 'OK'}];
-    var buttonPositive = validButtons.pop();
-    var buttonNegative = validButtons.pop();
-    var buttonNeutral = validButtons.pop();
+    const validButtons: Buttons = buttons ? buttons.slice(0, 3) : [{text: 'OK'}];
+    const buttonPositive = validButtons.pop();
+    const buttonNegative = validButtons.pop();
+    const buttonNeutral = validButtons.pop();
     if (buttonNeutral) {
       config = {...config, buttonNeutral: buttonNeutral.text || '' };
     }
diff --git a/Libraries/Alert/AlertIOS.js b/Libraries/Alert/AlertIOS.js
index eb15d1cdee03..082e3779da88 100644
--- a/Libraries/Alert/AlertIOS.js
+++ b/Libraries/Alert/AlertIOS.js
@@ -9,7 +9,7 @@
  */
 'use strict';
 
-var RCTAlertManager = require('NativeModules').AlertManager;
+const RCTAlertManager = require('NativeModules').AlertManager;
 
 /**
  * An Alert button type
@@ -118,7 +118,7 @@ class AlertIOS {
         'signature. The current signature is AlertIOS.prompt(title, message, callbackOrButtons, type, defaultValue, ' +
         'keyboardType) and the old syntax will be removed in a future version.');
 
-      var callback = type;
+      const callback = type;
       RCTAlertManager.alertWithArgs({
         title: title || '',
         type: 'plain-text',
@@ -129,10 +129,10 @@ class AlertIOS {
       return;
     }
 
-    var callbacks = [];
-    var buttons = [];
-    var cancelButtonKey;
-    var destructiveButtonKey;
+    let callbacks = [];
+    const buttons = [];
+    let cancelButtonKey;
+    let destructiveButtonKey;
     if (typeof callbackOrButtons === 'function') {
       callbacks = [callbackOrButtons];
     }
@@ -145,7 +145,7 @@ class AlertIOS {
           destructiveButtonKey = String(index);
         }
         if (btn.text || index < (callbackOrButtons || []).length - 1) {
-          var btnDef = {};
+          const btnDef = {};
           btnDef[index] = btn.text || '';
           buttons.push(btnDef);
         }
@@ -162,7 +162,7 @@ class AlertIOS {
       destructiveButtonKey,
       keyboardType,
     }, (id, value) => {
-      var cb = callbacks[id];
+      const cb = callbacks[id];
       cb && cb(value);
     });
   }
diff --git a/Libraries/Alert/RCTAlertManager.android.js b/Libraries/Alert/RCTAlertManager.android.js
index 25297171c4ce..57bd4740e8fc 100644
--- a/Libraries/Alert/RCTAlertManager.android.js
+++ b/Libraries/Alert/RCTAlertManager.android.js
@@ -7,7 +7,7 @@
 */
 'use strict';
 
-var NativeModules = require('NativeModules');
+const NativeModules = require('NativeModules');
 
 function emptyCallback() {}
 
diff --git a/Libraries/Alert/RCTAlertManager.ios.js b/Libraries/Alert/RCTAlertManager.ios.js
index 220b72c3d91d..d64bce5b4f12 100644
--- a/Libraries/Alert/RCTAlertManager.ios.js
+++ b/Libraries/Alert/RCTAlertManager.ios.js
@@ -8,6 +8,6 @@
  */
 'use strict';
 
-var RCTAlertManager = require('NativeModules').AlertManager;
+const RCTAlertManager = require('NativeModules').AlertManager;
 
 module.exports = RCTAlertManager;
diff --git a/Libraries/Animated/src/AnimatedWeb.js b/Libraries/Animated/src/AnimatedWeb.js
index a22bd075ec51..5538eb9b64c3 100644
--- a/Libraries/Animated/src/AnimatedWeb.js
+++ b/Libraries/Animated/src/AnimatedWeb.js
@@ -8,7 +8,7 @@
  */
 'use strict';
 
-var AnimatedImplementation = require('AnimatedImplementation');
+const AnimatedImplementation = require('AnimatedImplementation');
 
 module.exports = {
   ...AnimatedImplementation,
diff --git a/Libraries/Animated/src/NativeAnimatedHelper.js b/Libraries/Animated/src/NativeAnimatedHelper.js
index 61b2bde64a4d..3142ea24c084 100644
--- a/Libraries/Animated/src/NativeAnimatedHelper.js
+++ b/Libraries/Animated/src/NativeAnimatedHelper.js
@@ -208,7 +208,7 @@ function validateTransform(configs: Array<Object>): void {
 }
 
 function validateStyles(styles: Object): void {
-  for (var key in styles) {
+  for (const key in styles) {
     if (!STYLES_WHITELIST.hasOwnProperty(key)) {
       throw new Error(
         `Style property '${key}' is not supported by native animated module`,
@@ -218,7 +218,7 @@ function validateStyles(styles: Object): void {
 }
 
 function validateInterpolation(config: Object): void {
-  for (var key in config) {
+  for (const key in config) {
     if (!SUPPORTED_INTERPOLATION_PARAMS.hasOwnProperty(key)) {
       throw new Error(
         `Interpolation property '${key}' is not supported by native animated module`,
diff --git a/Libraries/Animated/src/SpringConfig.js b/Libraries/Animated/src/SpringConfig.js
index 6227c28301b4..b71fda2eacce 100644
--- a/Libraries/Animated/src/SpringConfig.js
+++ b/Libraries/Animated/src/SpringConfig.js
@@ -77,11 +77,11 @@ function fromBouncinessAndSpeed(
     }
   }
 
-  var b = normalize(bounciness / 1.7, 0, 20);
+  let b = normalize(bounciness / 1.7, 0, 20);
   b = projectNormal(b, 0, 0.8);
-  var s = normalize(speed / 1.7, 0, 20);
-  var bouncyTension = projectNormal(s, 0.5, 200);
-  var bouncyFriction = quadraticOutInterpolation(
+  const s = normalize(speed / 1.7, 0, 20);
+  const bouncyTension = projectNormal(s, 0.5, 200);
+  const bouncyFriction = quadraticOutInterpolation(
     b,
     b3Nobounce(bouncyTension),
     0.01
diff --git a/Libraries/Animated/src/__tests__/Animated-test.js b/Libraries/Animated/src/__tests__/Animated-test.js
index d6409d7f8a92..36b4d2a40a50 100644
--- a/Libraries/Animated/src/__tests__/Animated-test.js
+++ b/Libraries/Animated/src/__tests__/Animated-test.js
@@ -8,7 +8,7 @@
  */
 'use strict';
 
-var Animated = require('Animated');
+let Animated = require('Animated');
 describe('Animated tests', () => {
   beforeEach(() => {
     jest.resetModules();
@@ -17,11 +17,11 @@ describe('Animated tests', () => {
   describe('Animated', () => {
 
     it('works end to end', () => {
-      var anim = new Animated.Value(0);
+      const anim = new Animated.Value(0);
 
-      var callback = jest.fn();
+      const callback = jest.fn();
 
-      var node = new Animated.__PropsOnlyForTests({
+      const node = new Animated.__PropsOnlyForTests({
         style: {
           backgroundColor: 'red',
           opacity: anim,
@@ -83,10 +83,10 @@ describe('Animated tests', () => {
     });
 
     it('does not detach on updates', () => {
-      var anim = new Animated.Value(0);
+      const anim = new Animated.Value(0);
       anim.__detach = jest.fn();
 
-      var c = new Animated.View();
+      const c = new Animated.View();
       c.props = {
         style: {
           opacity: anim,
@@ -109,10 +109,10 @@ describe('Animated tests', () => {
 
 
     it('stops animation when detached', () => {
-      var anim = new Animated.Value(0);
-      var callback = jest.fn();
+      const anim = new Animated.Value(0);
+      const callback = jest.fn();
 
-      var c = new Animated.View();
+      const c = new Animated.View();
       c.props = {
         style: {
           opacity: anim,
@@ -129,31 +129,31 @@ describe('Animated tests', () => {
     });
 
     it('triggers callback when spring is at rest', () => {
-      var anim = new Animated.Value(0);
-      var callback = jest.fn();
+      const anim = new Animated.Value(0);
+      const callback = jest.fn();
       Animated.spring(anim, {toValue: 0, velocity: 0}).start(callback);
       expect(callback).toBeCalled();
     });
 
     it('send toValue when an underdamped spring stops', () => {
-      var anim = new Animated.Value(0);
-      var listener = jest.fn();
+      const anim = new Animated.Value(0);
+      const listener = jest.fn();
       anim.addListener(listener);
       Animated.spring(anim, {toValue: 15}).start();
       jest.runAllTimers();
-      var lastValue = listener.mock.calls[listener.mock.calls.length - 2][0].value;
+      const lastValue = listener.mock.calls[listener.mock.calls.length - 2][0].value;
       expect(lastValue).not.toBe(15);
       expect(lastValue).toBeCloseTo(15);
       expect(anim.__getValue()).toBe(15);
     });
 
     it('send toValue when a critically damped spring stops', () => {
-      var anim = new Animated.Value(0);
-      var listener = jest.fn();
+      const anim = new Animated.Value(0);
+      const listener = jest.fn();
       anim.addListener(listener);
       Animated.spring(anim, {stiffness: 8000, damping: 2000, toValue: 15}).start();
       jest.runAllTimers();
-      var lastValue = listener.mock.calls[listener.mock.calls.length - 2][0].value;
+      const lastValue = listener.mock.calls[listener.mock.calls.length - 2][0].value;
       expect(lastValue).not.toBe(15);
       expect(lastValue).toBeCloseTo(15);
       expect(anim.__getValue()).toBe(15);
@@ -168,17 +168,17 @@ describe('Animated tests', () => {
   describe('Animated Sequence', () => {
 
     it('works with an empty sequence', () => {
-      var cb = jest.fn();
+      const cb = jest.fn();
       Animated.sequence([]).start(cb);
       expect(cb).toBeCalledWith({finished: true});
     });
 
     it('sequences well', () => {
-      var anim1 = {start: jest.fn()};
-      var anim2 = {start: jest.fn()};
-      var cb = jest.fn();
+      const anim1 = {start: jest.fn()};
+      const anim2 = {start: jest.fn()};
+      const cb = jest.fn();
 
-      var seq = Animated.sequence([anim1, anim2]);
+      const seq = Animated.sequence([anim1, anim2]);
 
       expect(anim1.start).not.toBeCalled();
       expect(anim2.start).not.toBeCalled();
@@ -199,9 +199,9 @@ describe('Animated tests', () => {
     });
 
     it('supports interrupting sequence', () => {
-      var anim1 = {start: jest.fn()};
-      var anim2 = {start: jest.fn()};
-      var cb = jest.fn();
+      const anim1 = {start: jest.fn()};
+      const anim2 = {start: jest.fn()};
+      const cb = jest.fn();
 
       Animated.sequence([anim1, anim2]).start(cb);
 
@@ -213,11 +213,11 @@ describe('Animated tests', () => {
     });
 
     it('supports stopping sequence', () => {
-      var anim1 = {start: jest.fn(), stop: jest.fn()};
-      var anim2 = {start: jest.fn(), stop: jest.fn()};
-      var cb = jest.fn();
+      const anim1 = {start: jest.fn(), stop: jest.fn()};
+      const anim2 = {start: jest.fn(), stop: jest.fn()};
+      const cb = jest.fn();
 
-      var seq = Animated.sequence([anim1, anim2]);
+      const seq = Animated.sequence([anim1, anim2]);
       seq.start(cb);
       seq.stop();
 
@@ -234,10 +234,10 @@ describe('Animated tests', () => {
   describe('Animated Loop', () => {
 
     it('loops indefinitely if config not specified', () => {
-      var animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
-      var cb = jest.fn();
+      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const cb = jest.fn();
 
-      var loop = Animated.loop(animation);
+      const loop = Animated.loop(animation);
 
       expect(animation.start).not.toBeCalled();
 
@@ -261,10 +261,10 @@ describe('Animated tests', () => {
     });
 
     it('loops indefinitely if iterations is -1', () => {
-      var animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
-      var cb = jest.fn();
+      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const cb = jest.fn();
 
-      var loop = Animated.loop(animation, { iterations: -1 });
+      const loop = Animated.loop(animation, { iterations: -1 });
 
       expect(animation.start).not.toBeCalled();
 
@@ -288,10 +288,10 @@ describe('Animated tests', () => {
     });
 
     it('loops indefinitely if iterations not specified', () => {
-      var animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
-      var cb = jest.fn();
+      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const cb = jest.fn();
 
-      var loop = Animated.loop(animation, { anotherKey: 'value' });
+      const loop = Animated.loop(animation, { anotherKey: 'value' });
 
       expect(animation.start).not.toBeCalled();
 
@@ -315,10 +315,10 @@ describe('Animated tests', () => {
     });
 
     it('loops three times if iterations is 3', () => {
-      var animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
-      var cb = jest.fn();
+      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const cb = jest.fn();
 
-      var loop = Animated.loop(animation, { iterations: 3 });
+      const loop = Animated.loop(animation, { iterations: 3 });
 
       expect(animation.start).not.toBeCalled();
 
@@ -342,10 +342,10 @@ describe('Animated tests', () => {
     });
 
     it('does not loop if iterations is 1', () => {
-      var animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
-      var cb = jest.fn();
+      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const cb = jest.fn();
 
-      var loop = Animated.loop(animation, { iterations: 1 });
+      const loop = Animated.loop(animation, { iterations: 1 });
 
       expect(animation.start).not.toBeCalled();
 
@@ -359,10 +359,10 @@ describe('Animated tests', () => {
     });
 
     it('does not animate if iterations is 0', () => {
-      var animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
-      var cb = jest.fn();
+      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const cb = jest.fn();
 
-      var loop = Animated.loop(animation, { iterations: 0 });
+      const loop = Animated.loop(animation, { iterations: 0 });
 
       expect(animation.start).not.toBeCalled();
 
@@ -373,8 +373,8 @@ describe('Animated tests', () => {
     });
 
     it('supports interrupting an indefinite loop', () => {
-      var animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
-      var cb = jest.fn();
+      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const cb = jest.fn();
 
       Animated.loop(animation).start(cb);
       expect(animation.start).toBeCalled();
@@ -391,10 +391,10 @@ describe('Animated tests', () => {
     });
 
     it('supports stopping loop', () => {
-      var animation = {start: jest.fn(), stop: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
-      var cb = jest.fn();
+      const animation = {start: jest.fn(), stop: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const cb = jest.fn();
 
-      var loop = Animated.loop(animation);
+      const loop = Animated.loop(animation);
       loop.start(cb);
       loop.stop();
 
@@ -411,14 +411,14 @@ describe('Animated tests', () => {
   describe('Animated Parallel', () => {
 
     it('works with an empty parallel', () => {
-      var cb = jest.fn();
+      const cb = jest.fn();
       Animated.parallel([]).start(cb);
       expect(cb).toBeCalledWith({finished: true});
     });
 
     it('works with an empty element in array', () => {
-      var anim1 = {start: jest.fn()};
-      var cb = jest.fn();
+      const anim1 = {start: jest.fn()};
+      const cb = jest.fn();
       Animated.parallel([null, anim1]).start(cb);
 
       expect(anim1.start).toBeCalled();
@@ -428,11 +428,11 @@ describe('Animated tests', () => {
     });
 
     it('parellelizes well', () => {
-      var anim1 = {start: jest.fn()};
-      var anim2 = {start: jest.fn()};
-      var cb = jest.fn();
+      const anim1 = {start: jest.fn()};
+      const anim2 = {start: jest.fn()};
+      const cb = jest.fn();
 
-      var par = Animated.parallel([anim1, anim2]);
+      const par = Animated.parallel([anim1, anim2]);
 
       expect(anim1.start).not.toBeCalled();
       expect(anim2.start).not.toBeCalled();
@@ -451,11 +451,11 @@ describe('Animated tests', () => {
     });
 
     it('supports stopping parallel', () => {
-      var anim1 = {start: jest.fn(), stop: jest.fn()};
-      var anim2 = {start: jest.fn(), stop: jest.fn()};
-      var cb = jest.fn();
+      const anim1 = {start: jest.fn(), stop: jest.fn()};
+      const anim2 = {start: jest.fn(), stop: jest.fn()};
+      const cb = jest.fn();
 
-      var seq = Animated.parallel([anim1, anim2]);
+      const seq = Animated.parallel([anim1, anim2]);
       seq.start(cb);
       seq.stop();
 
@@ -472,12 +472,12 @@ describe('Animated tests', () => {
 
 
     it('does not call stop more than once when stopping', () => {
-      var anim1 = {start: jest.fn(), stop: jest.fn()};
-      var anim2 = {start: jest.fn(), stop: jest.fn()};
-      var anim3 = {start: jest.fn(), stop: jest.fn()};
-      var cb = jest.fn();
+      const anim1 = {start: jest.fn(), stop: jest.fn()};
+      const anim2 = {start: jest.fn(), stop: jest.fn()};
+      const anim3 = {start: jest.fn(), stop: jest.fn()};
+      const cb = jest.fn();
 
-      var seq = Animated.parallel([anim1, anim2, anim3]);
+      const seq = Animated.parallel([anim1, anim2, anim3]);
       seq.start(cb);
 
       anim1.start.mock.calls[0][0]({finished: false});
@@ -502,8 +502,8 @@ describe('Animated tests', () => {
 
   describe('Animated delays', () => {
     it('should call anim after delay in sequence', () => {
-      var anim = {start: jest.fn(), stop: jest.fn()};
-      var cb = jest.fn();
+      const anim = {start: jest.fn(), stop: jest.fn()};
+      const cb = jest.fn();
       Animated.sequence([
         Animated.delay(1000),
         anim,
@@ -515,7 +515,7 @@ describe('Animated tests', () => {
       expect(cb).toBeCalledWith({finished: true});
     });
     it('should run stagger to end', () => {
-      var cb = jest.fn();
+      const cb = jest.fn();
       Animated.stagger(1000, [
         Animated.delay(1000),
         Animated.delay(1000),
@@ -528,17 +528,17 @@ describe('Animated tests', () => {
 
   describe('Animated Events', () => {
     it('should map events', () => {
-      var value = new Animated.Value(0);
-      var handler = Animated.event(
+      const value = new Animated.Value(0);
+      const handler = Animated.event(
         [null, {state: {foo: value}}],
       );
       handler({bar: 'ignoreBar'}, {state: {baz: 'ignoreBaz', foo: 42}});
       expect(value.__getValue()).toBe(42);
     });
     it('should call listeners', () => {
-      var value = new Animated.Value(0);
-      var listener = jest.fn();
-      var handler = Animated.event(
+      const value = new Animated.Value(0);
+      const listener = jest.fn();
+      const handler = Animated.event(
         [{foo: value}],
         {listener},
       );
@@ -548,14 +548,14 @@ describe('Animated tests', () => {
       expect(listener).toBeCalledWith({foo: 42});
     });
     it('should call forked event listeners', () => {
-      var value = new Animated.Value(0);
-      var listener = jest.fn();
-      var handler = Animated.event(
+      const value = new Animated.Value(0);
+      const listener = jest.fn();
+      const handler = Animated.event(
         [{foo: value}],
         {listener},
       );
-      var listener2 = jest.fn();
-      var forkedHandler = Animated.forkEvent(handler, listener2);
+      const listener2 = jest.fn();
+      const forkedHandler = Animated.forkEvent(handler, listener2);
       forkedHandler({foo: 42});
       expect(value.__getValue()).toBe(42);
       expect(listener.mock.calls.length).toBe(1);
@@ -567,9 +567,9 @@ describe('Animated tests', () => {
 
   describe('Animated Interactions', () => {
     /*eslint-disable no-shadow*/
-    var Animated;
+    let Animated;
     /*eslint-enable*/
-    var InteractionManager;
+    let InteractionManager;
 
     beforeEach(() => {
       jest.mock('InteractionManager');
@@ -584,8 +584,8 @@ describe('Animated tests', () => {
     it('registers an interaction by default', () => {
       InteractionManager.createInteractionHandle.mockReturnValue(777);
 
-      var value = new Animated.Value(0);
-      var callback = jest.fn();
+      const value = new Animated.Value(0);
+      const callback = jest.fn();
       Animated.timing(value, {
         toValue: 100,
         duration: 100,
@@ -598,8 +598,8 @@ describe('Animated tests', () => {
     });
 
     it('does not register an interaction when specified', () => {
-      var value = new Animated.Value(0);
-      var callback = jest.fn();
+      const value = new Animated.Value(0);
+      const callback = jest.fn();
       Animated.timing(value, {
         toValue: 100,
         duration: 100,
@@ -615,8 +615,8 @@ describe('Animated tests', () => {
 
   describe('Animated Tracking', () => {
     it('should track values', () => {
-      var value1 = new Animated.Value(0);
-      var value2 = new Animated.Value(0);
+      const value1 = new Animated.Value(0);
+      const value2 = new Animated.Value(0);
       Animated.timing(value2, {
         toValue: value1,
         duration: 0,
@@ -628,8 +628,8 @@ describe('Animated tests', () => {
     });
 
     it('should track interpolated values', () => {
-      var value1 = new Animated.Value(0);
-      var value2 = new Animated.Value(0);
+      const value1 = new Animated.Value(0);
+      const value2 = new Animated.Value(0);
       Animated.timing(value2, {
         toValue: value1.interpolate({
           inputRange: [0, 2],
@@ -642,8 +642,8 @@ describe('Animated tests', () => {
     });
 
     it('should stop tracking when animated', () => {
-      var value1 = new Animated.Value(0);
-      var value2 = new Animated.Value(0);
+      const value1 = new Animated.Value(0);
+      const value2 = new Animated.Value(0);
       Animated.timing(value2, {
         toValue: value1,
         duration: 0,
@@ -661,11 +661,11 @@ describe('Animated tests', () => {
 
   describe('Animated Vectors', () => {
     it('should animate vectors', () => {
-      var vec = new Animated.ValueXY();
+      const vec = new Animated.ValueXY();
 
-      var callback = jest.fn();
+      const callback = jest.fn();
 
-      var node = new Animated.__PropsOnlyForTests({
+      const node = new Animated.__PropsOnlyForTests({
         style: {
           opacity: vec.x.interpolate({
             inputRange: [0, 42],
@@ -711,8 +711,8 @@ describe('Animated tests', () => {
     });
 
     it('should track vectors', () => {
-      var value1 = new Animated.ValueXY();
-      var value2 = new Animated.ValueXY();
+      const value1 = new Animated.ValueXY();
+      const value2 = new Animated.ValueXY();
       Animated.timing(value2, {
         toValue: value1,
         duration: 0,
@@ -727,8 +727,8 @@ describe('Animated tests', () => {
     });
 
     it('should track with springs', () => {
-      var value1 = new Animated.ValueXY();
-      var value2 = new Animated.ValueXY();
+      const value1 = new Animated.ValueXY();
+      const value2 = new Animated.ValueXY();
       Animated.spring(value2, {
         toValue: value1,
         tension: 3000, // faster spring for faster test
@@ -747,9 +747,9 @@ describe('Animated tests', () => {
 
   describe('Animated Listeners', () => {
     it('should get updates', () => {
-      var value1 = new Animated.Value(0);
-      var listener = jest.fn();
-      var id = value1.addListener(listener);
+      const value1 = new Animated.Value(0);
+      const listener = jest.fn();
+      const id = value1.addListener(listener);
       value1.setValue(42);
       expect(listener.mock.calls.length).toBe(1);
       expect(listener).toBeCalledWith({value: 42});
@@ -765,8 +765,8 @@ describe('Animated tests', () => {
     });
 
     it('should removeAll', () => {
-      var value1 = new Animated.Value(0);
-      var listener = jest.fn();
+      const value1 = new Animated.Value(0);
+      const listener = jest.fn();
       [1,2,3,4].forEach(() => value1.addListener(listener));
       value1.setValue(42);
       expect(listener.mock.calls.length).toBe(4);
diff --git a/Libraries/Animated/src/__tests__/Easing-test.js b/Libraries/Animated/src/__tests__/Easing-test.js
index 14f18aacd628..ae6cd3368682 100644
--- a/Libraries/Animated/src/__tests__/Easing-test.js
+++ b/Libraries/Animated/src/__tests__/Easing-test.js
@@ -8,10 +8,10 @@
  */
 'use strict';
 
-var Easing = require('Easing');
+const Easing = require('Easing');
 describe('Easing', () => {
   it('should work with linear', () => {
-    var easing = Easing.linear;
+    const easing = Easing.linear;
 
     expect(easing(0)).toBe(0);
     expect(easing(0.5)).toBe(0.5);
@@ -20,7 +20,7 @@ describe('Easing', () => {
   });
 
   it('should work with ease in linear', () => {
-    var easing = Easing.in(Easing.linear);
+    const easing = Easing.in(Easing.linear);
     expect(easing(0)).toBe(0);
     expect(easing(0.5)).toBe(0.5);
     expect(easing(0.8)).toBe(0.8);
@@ -28,7 +28,7 @@ describe('Easing', () => {
   });
 
   it('should work with easy out linear', () => {
-    var easing = Easing.out(Easing.linear);
+    const easing = Easing.out(Easing.linear);
     expect(easing(0)).toBe(0);
     expect(easing(0.5)).toBe(0.5);
     expect(easing(0.6)).toBe(0.6);
@@ -39,8 +39,8 @@ describe('Easing', () => {
     function easeInQuad(t) {
       return t * t;
     }
-    var easing = Easing.in(Easing.quad);
-    for (var t = -0.5; t < 1.5; t += 0.1) {
+    const easing = Easing.in(Easing.quad);
+    for (let t = -0.5; t < 1.5; t += 0.1) {
       expect(easing(t)).toBe(easeInQuad(t));
     }
   });
@@ -49,8 +49,8 @@ describe('Easing', () => {
     function easeOutQuad(t) {
       return -t * (t - 2);
     }
-    var easing = Easing.out(Easing.quad);
-    for (var t = 0; t <= 1; t += 0.1) {
+    const easing = Easing.out(Easing.quad);
+    for (let t = 0; t <= 1; t += 0.1) {
       expect(easing(1)).toBe(easeOutQuad(1));
     }
   });
@@ -63,31 +63,31 @@ describe('Easing', () => {
       }
       return -((t - 1) * (t - 3) - 1) / 2;
     }
-    var easing = Easing.inOut(Easing.quad);
-    for (var t = -0.5; t < 1.5; t += 0.1) {
+    const easing = Easing.inOut(Easing.quad);
+    for (let t = -0.5; t < 1.5; t += 0.1) {
       expect(easing(t)).toBeCloseTo(easeInOutQuad(t), 4);
     }
   });
 
   it('should satisfy boundary conditions with elastic', () => {
-    for (var b = 0; b < 4; b += 0.3) {
-      var easing = Easing.elastic(b);
+    for (let b = 0; b < 4; b += 0.3) {
+      const easing = Easing.elastic(b);
       expect(easing(0)).toBe(0);
       expect(easing(1)).toBe(1);
     }
   });
 
   function sampleEasingFunction(easing) {
-    var DURATION = 300;
-    var tickCount = Math.round(DURATION * 60 / 1000);
-    var samples = [];
-    for (var i = 0; i <= tickCount; i++) {
+    const DURATION = 300;
+    const tickCount = Math.round(DURATION * 60 / 1000);
+    const samples = [];
+    for (let i = 0; i <= tickCount; i++) {
       samples.push(easing(i / tickCount));
     }
     return samples;
   }
 
-  var Samples = {
+  const Samples = {
     in_quad: [0,0.0030864197530864196,0.012345679012345678,0.027777777777777776,0.04938271604938271,0.0771604938271605,0.1111111111111111,0.15123456790123457,0.19753086419753085,0.25,0.308641975308642,0.37345679012345684,0.4444444444444444,0.5216049382716049,0.6049382716049383,0.6944444444444445,0.7901234567901234,0.8919753086419753,1],
     out_quad: [0,0.10802469135802469,0.20987654320987653,0.3055555555555555,0.3950617283950617,0.47839506172839513,0.5555555555555556,0.6265432098765432,0.691358024691358,0.75,0.8024691358024691,0.8487654320987654,0.888888888888889,0.9228395061728394,0.9506172839506174,0.9722222222222221,0.9876543209876543,0.9969135802469136,1],
     inOut_quad: [0,0.006172839506172839,0.024691358024691357,0.05555555555555555,0.09876543209876543,0.154320987654321,0.2222222222222222,0.30246913580246915,0.3950617283950617,0.5,0.6049382716049383,0.697530864197531,0.7777777777777777,0.845679012345679,0.9012345679012346,0.9444444444444444,0.9753086419753086,0.9938271604938271,1],
@@ -109,13 +109,13 @@ describe('Easing', () => {
 
   Object.keys(Samples).forEach(function(type) {
     it('should ease ' + type, function() {
-      var [modeName, easingName, isFunction] = type.split('_');
-      var easing = Easing[easingName];
+      const [modeName, easingName, isFunction] = type.split('_');
+      let easing = Easing[easingName];
       if (isFunction !== undefined) {
         easing = easing();
       }
-      var computed = sampleEasingFunction(Easing[modeName](easing));
-      var samples = Samples[type];
+      const computed = sampleEasingFunction(Easing[modeName](easing));
+      const samples = Samples[type];
 
       computed.forEach((value, key) => {
         expect(value).toBeCloseTo(samples[key], 2);
diff --git a/Libraries/Animated/src/__tests__/Interpolation-test.js b/Libraries/Animated/src/__tests__/Interpolation-test.js
index 27f4438ab156..c2b832bcf5cf 100644
--- a/Libraries/Animated/src/__tests__/Interpolation-test.js
+++ b/Libraries/Animated/src/__tests__/Interpolation-test.js
@@ -8,12 +8,12 @@
  */
 'use strict';
 
-var AnimatedInterpolation = require('../nodes/AnimatedInterpolation');
-var Easing = require('Easing');
+const AnimatedInterpolation = require('../nodes/AnimatedInterpolation');
+const Easing = require('Easing');
 
 describe('Interpolation', () => {
   it('should work with defaults', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: [0, 1],
     });
@@ -25,7 +25,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with output range', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: [100, 200],
     });
@@ -37,7 +37,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with input range', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [100, 200],
       outputRange: [0, 1],
     });
@@ -65,7 +65,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with empty input range', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 10, 10],
       outputRange: [1, 2, 3],
       extrapolate: 'extend',
@@ -79,7 +79,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with empty output range', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [1, 2, 3],
       outputRange: [0, 10, 10],
       extrapolate: 'extend',
@@ -94,7 +94,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with easing', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: [0, 1],
       easing: Easing.quad,
@@ -107,7 +107,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with extrapolate', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    let interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: [0, 1],
       extrapolate: 'extend',
@@ -139,7 +139,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with keyframes with extrapolate', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 10, 100, 1000],
       outputRange: [0, 5, 50, 500],
       extrapolate: true,
@@ -157,7 +157,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with keyframes without extrapolate', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1, 2],
       outputRange: [0.2, 1, 0.2],
       extrapolate: 'clamp',
@@ -183,7 +183,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with negative infinite', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [-Infinity, 0],
       outputRange: [-Infinity, 0],
       easing: Easing.quad,
@@ -199,7 +199,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with positive infinite', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [5, Infinity],
       outputRange: [5, Infinity],
       easing: Easing.quad,
@@ -217,7 +217,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with output ranges as string', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: ['rgba(0, 100, 200, 0)', 'rgba(50, 150, 250, 0.4)'],
     });
@@ -228,7 +228,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with output ranges as short hex string', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: ['#024', '#9BF'],
     });
@@ -239,7 +239,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with output ranges as long hex string', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: ['#FF9500', '#87FC70'],
     });
@@ -250,7 +250,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with output ranges with mixed hex and rgba strings', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: ['rgba(100, 120, 140, .4)', '#87FC70'],
     });
@@ -261,7 +261,7 @@ describe('Interpolation', () => {
   });
 
   it('should work with negative and decimal values in string ranges', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: ['-100.5deg', '100deg'],
     });
@@ -272,7 +272,7 @@ describe('Interpolation', () => {
   });
 
   it('should crash when chaining an interpolation that returns a string', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: [0, 1],
     });
@@ -282,7 +282,7 @@ describe('Interpolation', () => {
   });
 
   it('should support a mix of color patterns', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1, 2],
       outputRange: ['rgba(0, 100, 200, 0)', 'rgb(50, 150, 250)', 'red'],
     });
@@ -303,7 +303,7 @@ describe('Interpolation', () => {
   });
 
   it('should round the alpha channel of a color to the nearest thousandth', () => {
-    var interpolation = AnimatedInterpolation.__createInterpolation({
+    const interpolation = AnimatedInterpolation.__createInterpolation({
       inputRange: [0, 1],
       outputRange: ['rgba(0, 0, 0, 0)', 'rgba(0, 0, 0, 1)'],
     });
diff --git a/Libraries/Animated/src/__tests__/bezier-test.js b/Libraries/Animated/src/__tests__/bezier-test.js
index 3f1070a48fd7..16b7acc0f193 100644
--- a/Libraries/Animated/src/__tests__/bezier-test.js
+++ b/Libraries/Animated/src/__tests__/bezier-test.js
@@ -10,9 +10,9 @@
 
 'use strict';
 
-var bezier = require('bezier');
+const bezier = require('bezier');
 
-var identity = function(x) {
+const identity = function(x) {
   return x;
 };
 
@@ -30,15 +30,15 @@ function allEquals(be1, be2, samples, assertion) {
   if (!assertion) {
     assertion = assertClose;
   }
-  for (var i = 0; i <= samples; ++i) {
-    var x = i / samples;
+  for (let i = 0; i <= samples; ++i) {
+    const x = i / samples;
     assertion(be1(x), be2(x));
   }
 }
 
 function repeat(n) {
   return function(f) {
-    for (var i = 0; i < n; ++i) {
+    for (let i = 0; i < n; ++i) {
       f(i);
     }
   };
@@ -74,11 +74,8 @@ describe('bezier', function() {
   describe('common properties', function() {
     it('should be the right value at extremes', function() {
       repeat(10)(function() {
-        var a = Math.random(),
-          b = 2 * Math.random() - 0.5,
-          c = Math.random(),
-          d = 2 * Math.random() - 0.5;
-        var easing = bezier(a, b, c, d);
+        const a = Math.random(), b = 2 * Math.random() - 0.5, c = Math.random(), d = 2 * Math.random() - 0.5;
+        const easing = bezier(a, b, c, d);
         expect(easing(0)).toBe(0);
         expect(easing(1)).toBe(1);
       });
@@ -86,13 +83,10 @@ describe('bezier', function() {
 
     it('should approach the projected value of its x=y projected curve', function() {
       repeat(10)(function() {
-        var a = Math.random(),
-          b = Math.random(),
-          c = Math.random(),
-          d = Math.random();
-        var easing = bezier(a, b, c, d);
-        var projected = bezier(b, a, d, c);
-        var composed = function(x) {
+        const a = Math.random(), b = Math.random(), c = Math.random(), d = Math.random();
+        const easing = bezier(a, b, c, d);
+        const projected = bezier(b, a, d, c);
+        const composed = function(x) {
           return projected(easing(x));
         };
         allEquals(identity, composed, 100, makeAssertCloseWithPrecision(2));
@@ -102,10 +96,7 @@ describe('bezier', function() {
   describe('two same instances', function() {
     it('should be strictly equals', function() {
       repeat(10)(function() {
-        var a = Math.random(),
-          b = 2 * Math.random() - 0.5,
-          c = Math.random(),
-          d = 2 * Math.random() - 0.5;
+        const a = Math.random(), b = 2 * Math.random() - 0.5, c = Math.random(), d = 2 * Math.random() - 0.5;
         allEquals(bezier(a, b, c, d), bezier(a, b, c, d), 100, 0);
       });
     });
@@ -113,22 +104,16 @@ describe('bezier', function() {
   describe('symetric curves', function() {
     it('should have a central value y~=0.5 at x=0.5', function() {
       repeat(10)(function() {
-        var a = Math.random(),
-          b = 2 * Math.random() - 0.5,
-          c = 1 - a,
-          d = 1 - b;
-        var easing = bezier(a, b, c, d);
+        const a = Math.random(), b = 2 * Math.random() - 0.5, c = 1 - a, d = 1 - b;
+        const easing = bezier(a, b, c, d);
         assertClose(easing(0.5), 0.5, 2);
       });
     });
     it('should be symmetrical', function() {
       repeat(10)(function() {
-        var a = Math.random(),
-          b = 2 * Math.random() - 0.5,
-          c = 1 - a,
-          d = 1 - b;
-        var easing = bezier(a, b, c, d);
-        var sym = function(x) {
+        const a = Math.random(), b = 2 * Math.random() - 0.5, c = 1 - a, d = 1 - b;
+        const easing = bezier(a, b, c, d);
+        const sym = function(x) {
           return 1 - easing(1 - x);
         };
         allEquals(easing, sym, 100, makeAssertCloseWithPrecision(2));
diff --git a/Libraries/Animated/src/bezier.js b/Libraries/Animated/src/bezier.js
index 9aa777a12493..f38ecef8c451 100644
--- a/Libraries/Animated/src/bezier.js
+++ b/Libraries/Animated/src/bezier.js
@@ -8,15 +8,15 @@
 'use strict';
 
  // These values are established by empiricism with tests (tradeoff: performance VS precision)
- var NEWTON_ITERATIONS = 4;
- var NEWTON_MIN_SLOPE = 0.001;
- var SUBDIVISION_PRECISION = 0.0000001;
- var SUBDIVISION_MAX_ITERATIONS = 10;
+ const NEWTON_ITERATIONS = 4;
+ const NEWTON_MIN_SLOPE = 0.001;
+ const SUBDIVISION_PRECISION = 0.0000001;
+ const SUBDIVISION_MAX_ITERATIONS = 10;
 
- var kSplineTableSize = 11;
- var kSampleStepSize = 1.0 / (kSplineTableSize - 1.0);
+ const kSplineTableSize = 11;
+ const kSampleStepSize = 1.0 / (kSplineTableSize - 1.0);
 
- var float32ArraySupported = typeof Float32Array === 'function';
+ const float32ArraySupported = typeof Float32Array === 'function';
 
  function A (aA1, aA2) { return 1.0 - 3.0 * aA2 + 3.0 * aA1; }
  function B (aA1, aA2) { return 3.0 * aA2 - 6.0 * aA1; }
@@ -29,7 +29,7 @@
  function getSlope (aT, aA1, aA2) { return 3.0 * A(aA1, aA2) * aT * aT + 2.0 * B(aA1, aA2) * aT + C(aA1); }
 
  function binarySubdivide (aX, aA, aB, mX1, mX2) {
-   var currentX, currentT, i = 0;
+   let currentX, currentT, i = 0;
    do {
      currentT = aA + (aB - aA) / 2.0;
      currentX = calcBezier(currentT, mX1, mX2) - aX;
@@ -43,12 +43,12 @@
  }
 
  function newtonRaphsonIterate (aX, aGuessT, mX1, mX2) {
-  for (var i = 0; i < NEWTON_ITERATIONS; ++i) {
-    var currentSlope = getSlope(aGuessT, mX1, mX2);
+  for (let i = 0; i < NEWTON_ITERATIONS; ++i) {
+    const currentSlope = getSlope(aGuessT, mX1, mX2);
     if (currentSlope === 0.0) {
       return aGuessT;
     }
-    var currentX = calcBezier(aGuessT, mX1, mX2) - aX;
+    const currentX = calcBezier(aGuessT, mX1, mX2) - aX;
     aGuessT -= currentX / currentSlope;
   }
   return aGuessT;
@@ -60,17 +60,17 @@
    }
 
    // Precompute samples table
-   var sampleValues = float32ArraySupported ? new Float32Array(kSplineTableSize) : new Array(kSplineTableSize);
+   const sampleValues = float32ArraySupported ? new Float32Array(kSplineTableSize) : new Array(kSplineTableSize);
    if (mX1 !== mY1 || mX2 !== mY2) {
-     for (var i = 0; i < kSplineTableSize; ++i) {
+     for (let i = 0; i < kSplineTableSize; ++i) {
        sampleValues[i] = calcBezier(i * kSampleStepSize, mX1, mX2);
      }
    }
 
    function getTForX (aX) {
-     var intervalStart = 0.0;
-     var currentSample = 1;
-     var lastSample = kSplineTableSize - 1;
+     let intervalStart = 0.0;
+     let currentSample = 1;
+     const lastSample = kSplineTableSize - 1;
 
      for (; currentSample !== lastSample && sampleValues[currentSample] <= aX; ++currentSample) {
        intervalStart += kSampleStepSize;
@@ -78,10 +78,10 @@
      --currentSample;
 
      // Interpolate to provide an initial guess for t
-     var dist = (aX - sampleValues[currentSample]) / (sampleValues[currentSample + 1] - sampleValues[currentSample]);
-     var guessForT = intervalStart + dist * kSampleStepSize;
+     const dist = (aX - sampleValues[currentSample]) / (sampleValues[currentSample + 1] - sampleValues[currentSample]);
+     const guessForT = intervalStart + dist * kSampleStepSize;
 
-     var initialSlope = getSlope(guessForT, mX1, mX2);
+     const initialSlope = getSlope(guessForT, mX1, mX2);
      if (initialSlope >= NEWTON_MIN_SLOPE) {
        return newtonRaphsonIterate(aX, guessForT, mX1, mX2);
      } else if (initialSlope === 0.0) {
diff --git a/Libraries/BatchedBridge/__mocks__/MessageQueueTestConfig.js b/Libraries/BatchedBridge/__mocks__/MessageQueueTestConfig.js
index 40ad81f5f5cb..2fa722fb39e8 100644
--- a/Libraries/BatchedBridge/__mocks__/MessageQueueTestConfig.js
+++ b/Libraries/BatchedBridge/__mocks__/MessageQueueTestConfig.js
@@ -7,12 +7,12 @@
  * These don't actually exist anywhere in the code.
  */
 'use strict';
-var remoteModulesConfig = [
+const remoteModulesConfig = [
   ['RemoteModule1',null,['remoteMethod','promiseMethod'],[]],
   ['RemoteModule2',null,['remoteMethod','promiseMethod'],[]],
 ];
 
-var MessageQueueTestConfig = {
+const MessageQueueTestConfig = {
   remoteModuleConfig: remoteModulesConfig,
 };
 
diff --git a/Libraries/BatchedBridge/__mocks__/MessageQueueTestModule.js b/Libraries/BatchedBridge/__mocks__/MessageQueueTestModule.js
index 8c4f7d3c0306..7d4f5f1a565a 100644
--- a/Libraries/BatchedBridge/__mocks__/MessageQueueTestModule.js
+++ b/Libraries/BatchedBridge/__mocks__/MessageQueueTestModule.js
@@ -12,7 +12,7 @@
  * correctly dispatches to commonJS modules. The `testHook` is overriden by test
  * cases.
  */
-var MessageQueueTestModule = {
+const MessageQueueTestModule = {
   testHook1: function() {
   },
   testHook2: function() {
diff --git a/Libraries/Blob/__tests__/Blob-test.js b/Libraries/Blob/__tests__/Blob-test.js
index 8d37915720c9..47bf5fee7c13 100644
--- a/Libraries/Blob/__tests__/Blob-test.js
+++ b/Libraries/Blob/__tests__/Blob-test.js
@@ -13,7 +13,7 @@ jest.setMock('NativeModules', {
   BlobModule: require('../__mocks__/BlobModule'),
 });
 
-var Blob = require('Blob');
+const Blob = require('Blob');
 
 describe('Blob', function() {
   it('should create empty blob', () => {
diff --git a/Libraries/Blob/__tests__/BlobManager-test.js b/Libraries/Blob/__tests__/BlobManager-test.js
index 2ed118b446be..c141d42f1633 100644
--- a/Libraries/Blob/__tests__/BlobManager-test.js
+++ b/Libraries/Blob/__tests__/BlobManager-test.js
@@ -13,8 +13,8 @@ jest.setMock('NativeModules', {
   BlobModule: require('../__mocks__/BlobModule'),
 });
 
-var Blob = require('Blob');
-var BlobManager = require('BlobManager');
+const Blob = require('Blob');
+const BlobManager = require('BlobManager');
 
 describe('BlobManager', function() {
   it('should create blob from parts', () => {
diff --git a/Libraries/Blob/__tests__/FileReader-test.js b/Libraries/Blob/__tests__/FileReader-test.js
index a278a4918a9d..b2237550bf71 100644
--- a/Libraries/Blob/__tests__/FileReader-test.js
+++ b/Libraries/Blob/__tests__/FileReader-test.js
@@ -14,8 +14,8 @@ jest.unmock('event-target-shim').setMock('NativeModules', {
   FileReaderModule: require('../__mocks__/FileReaderModule'),
 });
 
-var Blob = require('Blob');
-var FileReader = require('FileReader');
+const Blob = require('Blob');
+const FileReader = require('FileReader');
 
 describe('FileReader', function() {
   it('should read blob as text', async () => {
diff --git a/Libraries/BugReporting/getReactData.js b/Libraries/BugReporting/getReactData.js
index 3f7a1a903d66..f995e8f41967 100644
--- a/Libraries/BugReporting/getReactData.js
+++ b/Libraries/BugReporting/getReactData.js
@@ -15,16 +15,16 @@
  * https://github.com/facebook/react-devtools/blob/master/backend/getData.js
  */
 function getData(element: Object): Object {
-  var children = null;
-  var props = null;
-  var state = null;
-  var context = null;
-  var updater = null;
-  var name = null;
-  var type = null;
-  var text = null;
-  var publicInstance = null;
-  var nodeType = 'Native';
+  let children = null;
+  let props = null;
+  let state = null;
+  let context = null;
+  let updater = null;
+  let name = null;
+  let type = null;
+  let text = null;
+  let publicInstance = null;
+  let nodeType = 'Native';
   // If the parent is a native node without rendered children, but with
   // multiple string children, then the `element` that gets passed in here is
   // a plain value -- a string or number.
@@ -80,7 +80,7 @@ function getData(element: Object): Object {
   }
 
   if (element._instance) {
-    var inst = element._instance;
+    const inst = element._instance;
     updater = {
       setState: inst.setState && inst.setState.bind(inst),
       forceUpdate: inst.forceUpdate && inst.forceUpdate.bind(inst),
@@ -113,7 +113,7 @@ function getData(element: Object): Object {
 }
 
 function setInProps(internalInst, path: Array<string | number>, value: any) {
-  var element = internalInst._currentElement;
+  const element = internalInst._currentElement;
   internalInst._currentElement = {
     ...element,
     props: copyWithSet(element.props, path, value),
@@ -132,16 +132,16 @@ function setInContext(inst, path: Array<string | number>, value: any) {
 }
 
 function setIn(obj: Object, path: Array<string | number>, value: any) {
-  var last = path.pop();
-  var parent = path.reduce((obj_, attr) => obj_ ? obj_[attr] : null, obj);
+  const last = path.pop();
+  const parent = path.reduce((obj_, attr) => obj_ ? obj_[attr] : null, obj);
   if (parent) {
     parent[last] = value;
   }
 }
 
 function childrenList(children) {
-  var res = [];
-  for (var name in children) {
+  const res = [];
+  for (const name in children) {
     res.push(children[name]);
   }
   return res;
@@ -151,8 +151,8 @@ function copyWithSetImpl(obj, path, idx, value) {
   if (idx >= path.length) {
     return value;
   }
-  var key = path[idx];
-  var updated = Array.isArray(obj) ? obj.slice() : {...obj};
+  const key = path[idx];
+  const updated = Array.isArray(obj) ? obj.slice() : {...obj};
   // $FlowFixMe number or string is fine here
   updated[key] = copyWithSetImpl(obj[key], path, idx + 1, value);
   return updated;
diff --git a/Libraries/CameraRoll/ImagePickerIOS.js b/Libraries/CameraRoll/ImagePickerIOS.js
index fe50825da142..b653c11090e2 100644
--- a/Libraries/CameraRoll/ImagePickerIOS.js
+++ b/Libraries/CameraRoll/ImagePickerIOS.js
@@ -8,9 +8,9 @@
  */
 'use strict';
 
-var RCTImagePicker = require('NativeModules').ImagePickerIOS;
+const RCTImagePicker = require('NativeModules').ImagePickerIOS;
 
-var ImagePickerIOS = {
+const ImagePickerIOS = {
   canRecordVideos: function(callback: Function) {
     return RCTImagePicker.canRecordVideos(callback);
   },
diff --git a/Libraries/Color/normalizeColor.js b/Libraries/Color/normalizeColor.js
index de62e68dad0a..59b3eb33ba5d 100755
--- a/Libraries/Color/normalizeColor.js
+++ b/Libraries/Color/normalizeColor.js
@@ -10,7 +10,7 @@
 'use strict';
 
 function normalizeColor(color: string | number): ?number {
-  var match;
+  let match;
 
   if (typeof color === 'number') {
     if (color >>> 0 === color && color >= 0 && color <= 0xffffffff) {
@@ -31,18 +31,18 @@ function normalizeColor(color: string | number): ?number {
   if ((match = matchers.rgb.exec(color))) {
     return (
       (// b
-      parse255(match[1]) << 24 | // r
+      (parse255(match[1]) << 24 | // r
       parse255(match[2]) << 16 | // g
-      parse255(match[3]) << 8 | 0x000000ff) // a
+      parse255(match[3]) << 8 | 0x000000ff)) // a
     ) >>> 0;
   }
 
   if ((match = matchers.rgba.exec(color))) {
     return (
       (// b
-      parse255(match[1]) << 24 | // r
+      (parse255(match[1]) << 24 | // r
       parse255(match[2]) << 16 | // g
-      parse255(match[3]) << 8 | parse1(match[4])) // a
+      parse255(match[3]) << 8 | parse1(match[4]))) // a
     ) >>> 0;
   }
 
@@ -114,11 +114,11 @@ function hue2rgb(p: number, q: number, t: number): number {
 }
 
 function hslToRgb(h: number, s: number, l: number): number {
-  var q = l < 0.5 ? l * (1 + s) : l + s - l * s;
-  var p = 2 * l - q;
-  var r = hue2rgb(p, q, h + 1 / 3);
-  var g = hue2rgb(p, q, h);
-  var b = hue2rgb(p, q, h - 1 / 3);
+  const q = l < 0.5 ? l * (1 + s) : l + s - l * s;
+  const p = 2 * l - q;
+  const r = hue2rgb(p, q, h + 1 / 3);
+  const g = hue2rgb(p, q, h);
+  const b = hue2rgb(p, q, h - 1 / 3);
 
   return (
     Math.round(r * 255) << 24 |
@@ -128,14 +128,14 @@ function hslToRgb(h: number, s: number, l: number): number {
 }
 
 // var INTEGER = '[-+]?\\d+';
-var NUMBER = '[-+]?\\d*\\.?\\d+';
-var PERCENTAGE = NUMBER + '%';
+const NUMBER = '[-+]?\\d*\\.?\\d+';
+const PERCENTAGE = NUMBER + '%';
 
 function call(...args) {
   return '\\(\\s*(' + args.join(')\\s*,\\s*(') + ')\\s*\\)';
 }
 
-var matchers = {
+const matchers = {
   rgb: new RegExp('rgb' + call(NUMBER, NUMBER, NUMBER)),
   rgba: new RegExp('rgba' + call(NUMBER, NUMBER, NUMBER, NUMBER)),
   hsl: new RegExp('hsl' + call(NUMBER, PERCENTAGE, PERCENTAGE)),
@@ -147,7 +147,7 @@ var matchers = {
 };
 
 function parse255(str: string): number {
-  var int = parseInt(str, 10);
+  const int = parseInt(str, 10);
   if (int < 0) {
     return 0;
   }
@@ -158,12 +158,12 @@ function parse255(str: string): number {
 }
 
 function parse360(str: string): number {
-  var int = parseFloat(str);
+  const int = parseFloat(str);
   return (((int % 360) + 360) % 360) / 360;
 }
 
 function parse1(str: string): number {
-  var num = parseFloat(str);
+  const num = parseFloat(str);
   if (num < 0) {
     return 0;
   }
@@ -175,7 +175,7 @@ function parse1(str: string): number {
 
 function parsePercentage(str: string): number {
   // parseFloat conveniently ignores the final %
-  var int = parseFloat(str);
+  const int = parseFloat(str);
   if (int < 0) {
     return 0;
   }
@@ -185,7 +185,7 @@ function parsePercentage(str: string): number {
   return int / 100;
 }
 
-var names = {
+const names = {
   transparent: 0x00000000,
 
   // http://www.w3.org/TR/css3-color/#svg-color
diff --git a/Libraries/Core/Devtools/__tests__/parseErrorStack-test.js b/Libraries/Core/Devtools/__tests__/parseErrorStack-test.js
index beaa629d765d..7726a6117b9b 100644
--- a/Libraries/Core/Devtools/__tests__/parseErrorStack-test.js
+++ b/Libraries/Core/Devtools/__tests__/parseErrorStack-test.js
@@ -9,7 +9,7 @@
 'use strict';
 
 
-var parseErrorStack = require('parseErrorStack');
+const parseErrorStack = require('parseErrorStack');
 
 function getFakeError() {
   return new Error('Happy Cat');
@@ -18,24 +18,24 @@ function getFakeError() {
 describe('parseErrorStack', function() {
 
   it('parses error stack', function() {
-    var stack = parseErrorStack(getFakeError());
+    const stack = parseErrorStack(getFakeError());
     expect(stack.length).toBeGreaterThan(0);
 
-    var firstFrame = stack[0];
+    const firstFrame = stack[0];
     expect(firstFrame.methodName).toEqual('getFakeError');
     expect(firstFrame.file).toMatch(/parseErrorStack-test\.js$/);
   });
 
   it('supports framesToPop', function() {
     function getWrappedError() {
-      var error = getFakeError();
+      const error = getFakeError();
       error.framesToPop = 1;
       return error;
     }
 
     // Make sure framesToPop == 1 causes it to ignore getFakeError
     // stack frame
-    var stack = parseErrorStack(getWrappedError());
+    const stack = parseErrorStack(getWrappedError());
     expect(stack[0].methodName).toEqual('getWrappedError');
   });
 
diff --git a/Libraries/Core/__mocks__/ErrorUtils.js b/Libraries/Core/__mocks__/ErrorUtils.js
index 2ab128040cff..6b2282672de4 100644
--- a/Libraries/Core/__mocks__/ErrorUtils.js
+++ b/Libraries/Core/__mocks__/ErrorUtils.js
@@ -19,7 +19,7 @@ function reportError(error) {
   throw error;
 }
 
-var ErrorUtils = {
+const ErrorUtils = {
   apply: jest.fn(execute),
   applyWithGuard: jest.fn(execute),
   guard: jest.fn(callback => callback),
diff --git a/Libraries/Experimental/IncrementalExample.js b/Libraries/Experimental/IncrementalExample.js
index e46510b5e4e9..7f006d38b6a7 100644
--- a/Libraries/Experimental/IncrementalExample.js
+++ b/Libraries/Experimental/IncrementalExample.js
@@ -153,7 +153,7 @@ function burnCPU(milliseconds) {
   while (performanceNow() < (start + milliseconds)) {}
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   scrollView: {
     margin: 10,
     backgroundColor: 'white',
diff --git a/Libraries/Geolocation/Geolocation.js b/Libraries/Geolocation/Geolocation.js
index 29bb0aa13a99..8bdc212636be 100644
--- a/Libraries/Geolocation/Geolocation.js
+++ b/Libraries/Geolocation/Geolocation.js
@@ -23,8 +23,8 @@ const LocationEventEmitter = new NativeEventEmitter(RCTLocationObserver);
 const Platform = require('Platform');
 const PermissionsAndroid = require('PermissionsAndroid');
 
-var subscriptions = [];
-var updatesEnabled = false;
+let subscriptions = [];
+let updatesEnabled = false;
 
 type GeoConfiguration = {
   skipPermissionRequests: bool;
@@ -44,7 +44,7 @@ type GeoOptions = {
  *
  * See https://facebook.github.io/react-native/docs/geolocation.html
  */
-var Geolocation = {
+const Geolocation = {
 
   /*
     * Sets configuration options that will be used in all location requests.
@@ -116,7 +116,7 @@ var Geolocation = {
       RCTLocationObserver.startObserving(options || {});
       updatesEnabled = true;
     }
-    var watchID = subscriptions.length;
+    const watchID = subscriptions.length;
     subscriptions.push([
       LocationEventEmitter.addListener(
         'geolocationDidChange',
@@ -131,7 +131,7 @@ var Geolocation = {
   },
 
   clearWatch: function(watchID: number) {
-    var sub = subscriptions[watchID];
+    const sub = subscriptions[watchID];
     if (!sub) {
       // Silently exit when the watchID is invalid or already cleared
       // This is consistent with timers
@@ -140,10 +140,10 @@ var Geolocation = {
 
     sub[0].remove();
     // array element refinements not yet enabled in Flow
-    var sub1 = sub[1]; sub1 && sub1.remove();
+    const sub1 = sub[1]; sub1 && sub1.remove();
     subscriptions[watchID] = undefined;
-    var noWatchers = true;
-    for (var ii = 0; ii < subscriptions.length; ii++) {
+    let noWatchers = true;
+    for (let ii = 0; ii < subscriptions.length; ii++) {
       if (subscriptions[ii]) {
         noWatchers = false; // still valid subscriptions
       }
@@ -157,13 +157,13 @@ var Geolocation = {
     if (updatesEnabled) {
       RCTLocationObserver.stopObserving();
       updatesEnabled = false;
-      for (var ii = 0; ii < subscriptions.length; ii++) {
-        var sub = subscriptions[ii];
+      for (let ii = 0; ii < subscriptions.length; ii++) {
+        const sub = subscriptions[ii];
         if (sub) {
           warning(false, 'Called stopObserving with existing subscriptions.');
           sub[0].remove();
           // array element refinements not yet enabled in Flow
-          var sub1 = sub[1]; sub1 && sub1.remove();
+          const sub1 = sub[1]; sub1 && sub1.remove();
         }
       }
       subscriptions = [];
diff --git a/Libraries/Image/AssetRegistry.js b/Libraries/Image/AssetRegistry.js
index 5f5f0980f432..ad1b495af428 100644
--- a/Libraries/Image/AssetRegistry.js
+++ b/Libraries/Image/AssetRegistry.js
@@ -21,7 +21,7 @@ export type PackagerAsset = {
   +type: string,
 };
 
-var assets: Array<PackagerAsset> = [];
+const assets: Array<PackagerAsset> = [];
 
 function registerAsset(asset: PackagerAsset): number {
   // `push` returns new array length, so the first asset will
diff --git a/Libraries/Image/AssetSourceResolver.js b/Libraries/Image/AssetSourceResolver.js
index d7b583ebcb8d..6ae1a7801d09 100644
--- a/Libraries/Image/AssetSourceResolver.js
+++ b/Libraries/Image/AssetSourceResolver.js
@@ -29,9 +29,9 @@ const invariant = require('fbjs/lib/invariant');
  * Returns a path like 'assets/AwesomeModule/icon@2x.png'
  */
 function getScaledAssetPath(asset): string {
-  var scale = AssetSourceResolver.pickScale(asset.scales, PixelRatio.get());
-  var scaleSuffix = scale === 1 ? '' : '@' + scale + 'x';
-  var assetDir = assetPathUtils.getBasePath(asset);
+  const scale = AssetSourceResolver.pickScale(asset.scales, PixelRatio.get());
+  const scaleSuffix = scale === 1 ? '' : '@' + scale + 'x';
+  const assetDir = assetPathUtils.getBasePath(asset);
   return assetDir + '/' + asset.name + scaleSuffix + '.' + asset.type;
 }
 
@@ -39,9 +39,9 @@ function getScaledAssetPath(asset): string {
  * Returns a path like 'drawable-mdpi/icon.png'
  */
 function getAssetPathInDrawableFolder(asset): string {
-  var scale = AssetSourceResolver.pickScale(asset.scales, PixelRatio.get());
-  var drawbleFolder = assetPathUtils.getAndroidResourceFolderName(asset, scale);
-  var fileName = assetPathUtils.getAndroidResourceIdentifier(asset);
+  const scale = AssetSourceResolver.pickScale(asset.scales, PixelRatio.get());
+  const drawbleFolder = assetPathUtils.getAndroidResourceFolderName(asset, scale);
+  const fileName = assetPathUtils.getAndroidResourceIdentifier(asset);
   return drawbleFolder + '/' + fileName + '.' + asset.type;
 }
 
@@ -151,7 +151,7 @@ class AssetSourceResolver {
 
   static pickScale(scales: Array<number>, deviceScale: number): number {
     // Packager guarantees that `scales` array is sorted
-    for (var i = 0; i < scales.length; i++) {
+    for (let i = 0; i < scales.length; i++) {
       if (scales[i] >= deviceScale) {
         return scales[i];
       }
diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index d9702700be59..b54d624118b1 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -10,25 +10,25 @@
 
 'use strict';
 
-var ImageResizeMode = require('ImageResizeMode');
-var ImageStylePropTypes = require('ImageStylePropTypes');
-var NativeMethodsMixin = require('NativeMethodsMixin');
-var NativeModules = require('NativeModules');
-var React = require('React');
-var PropTypes = require('prop-types');
-var ReactNativeViewAttributes = require('ReactNativeViewAttributes');
-var StyleSheet = require('StyleSheet');
-var StyleSheetPropType = require('StyleSheetPropType');
+const ImageResizeMode = require('ImageResizeMode');
+const ImageStylePropTypes = require('ImageStylePropTypes');
+const NativeMethodsMixin = require('NativeMethodsMixin');
+const NativeModules = require('NativeModules');
+const React = require('React');
+const PropTypes = require('prop-types');
+const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
+const StyleSheet = require('StyleSheet');
+const StyleSheetPropType = require('StyleSheetPropType');
 const TextAncestor = require('TextAncestor');
-var ViewPropTypes = require('ViewPropTypes');
+const ViewPropTypes = require('ViewPropTypes');
 
-var createReactClass = require('create-react-class');
-var flattenStyle = require('flattenStyle');
-var merge = require('merge');
-var requireNativeComponent = require('requireNativeComponent');
-var resolveAssetSource = require('resolveAssetSource');
+const createReactClass = require('create-react-class');
+const flattenStyle = require('flattenStyle');
+const merge = require('merge');
+const requireNativeComponent = require('requireNativeComponent');
+const resolveAssetSource = require('resolveAssetSource');
 
-var {ImageLoader} = NativeModules;
+const {ImageLoader} = NativeModules;
 
 let _requestId = 1;
 function generateRequestId() {
@@ -42,7 +42,7 @@ function generateRequestId() {
  *
  * See https://facebook.github.io/react-native/docs/image.html
  */
-var Image = createReactClass({
+const Image = createReactClass({
   displayName: 'Image',
   propTypes: {
     ...ViewPropTypes,
@@ -275,13 +275,13 @@ var Image = createReactClass({
   },
 });
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   base: {
     overflow: 'hidden',
   },
 });
 
-var cfg = {
+const cfg = {
   nativeOnly: {
     src: true,
     headers: true,
@@ -290,8 +290,8 @@ var cfg = {
     shouldNotifyLoadEvents: true,
   },
 };
-var RKImage = requireNativeComponent('RCTImageView', Image, cfg);
-var RCTTextInlineImage = requireNativeComponent(
+const RKImage = requireNativeComponent('RCTImageView', Image, cfg);
+const RCTTextInlineImage = requireNativeComponent(
   'RCTTextInlineImage',
   Image,
   cfg,
diff --git a/Libraries/Image/ImageResizeMode.js b/Libraries/Image/ImageResizeMode.js
index 89e74bcc502e..48779e383f31 100644
--- a/Libraries/Image/ImageResizeMode.js
+++ b/Libraries/Image/ImageResizeMode.js
@@ -12,13 +12,13 @@
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-var keyMirror = require('fbjs/lib/keyMirror');
+const keyMirror = require('fbjs/lib/keyMirror');
 
 /**
  * ImageResizeMode - Enum for different image resizing modes, set via
  * `resizeMode` style property on `<Image>` components.
  */
-var ImageResizeMode = keyMirror({
+const ImageResizeMode = keyMirror({
   /**
    * contain - The image will be resized such that it will be completely
    * visible, contained within the frame of the View.
diff --git a/Libraries/Image/ImageStylePropTypes.js b/Libraries/Image/ImageStylePropTypes.js
index c88c19ea3cec..54e500994227 100644
--- a/Libraries/Image/ImageStylePropTypes.js
+++ b/Libraries/Image/ImageStylePropTypes.js
@@ -9,14 +9,14 @@
  */
 'use strict';
 
-var ColorPropType = require('ColorPropType');
-var ImageResizeMode = require('ImageResizeMode');
-var LayoutPropTypes = require('LayoutPropTypes');
-var ReactPropTypes = require('prop-types');
-var ShadowPropTypesIOS = require('ShadowPropTypesIOS');
-var TransformPropTypes = require('TransformPropTypes');
+const ColorPropType = require('ColorPropType');
+const ImageResizeMode = require('ImageResizeMode');
+const LayoutPropTypes = require('LayoutPropTypes');
+const ReactPropTypes = require('prop-types');
+const ShadowPropTypesIOS = require('ShadowPropTypesIOS');
+const TransformPropTypes = require('TransformPropTypes');
 
-var ImageStylePropTypes = {
+const ImageStylePropTypes = {
   ...LayoutPropTypes,
   ...ShadowPropTypesIOS,
   ...TransformPropTypes,
diff --git a/Libraries/Image/RelativeImageStub.js b/Libraries/Image/RelativeImageStub.js
index 866488eecc83..1a74c36cb1bd 100644
--- a/Libraries/Image/RelativeImageStub.js
+++ b/Libraries/Image/RelativeImageStub.js
@@ -11,7 +11,7 @@
 // This is a stub for flow to make it understand require('./icon.png')
 // See metro/src/Bundler/index.js
 
-var AssetRegistry = require('AssetRegistry');
+const AssetRegistry = require('AssetRegistry');
 
 module.exports = AssetRegistry.registerAsset({
   __packager_asset: true,
diff --git a/Libraries/Image/__tests__/resolveAssetSource-test.js b/Libraries/Image/__tests__/resolveAssetSource-test.js
index 50a666a5b548..db1a0a853d99 100644
--- a/Libraries/Image/__tests__/resolveAssetSource-test.js
+++ b/Libraries/Image/__tests__/resolveAssetSource-test.js
@@ -8,13 +8,13 @@
  */
 'use strict';
 
-var AssetRegistry = require('AssetRegistry');
-var Platform = require('Platform');
-var NativeModules = require('NativeModules');
-var resolveAssetSource = require('../resolveAssetSource');
+const AssetRegistry = require('AssetRegistry');
+const Platform = require('Platform');
+const NativeModules = require('NativeModules');
+const resolveAssetSource = require('../resolveAssetSource');
 
 function expectResolvesAsset(input, expectedSource) {
-  var assetId = AssetRegistry.registerAsset(input);
+  const assetId = AssetRegistry.registerAsset(input);
   expect(resolveAssetSource(assetId)).toEqual(expectedSource);
 }
 
@@ -24,10 +24,10 @@ describe('resolveAssetSource', () => {
   });
 
   it('returns same source for simple static and network images', () => {
-    var source1 = {uri: 'https://www.facebook.com/logo'};
+    const source1 = {uri: 'https://www.facebook.com/logo'};
     expect(resolveAssetSource(source1)).toBe(source1);
 
-    var source2 = {uri: 'logo'};
+    const source2 = {uri: 'logo'};
     expect(resolveAssetSource(source2)).toBe(source2);
   });
 
diff --git a/Libraries/Image/resolveAssetSource.js b/Libraries/Image/resolveAssetSource.js
index fefb28ff5f7b..fe483beff594 100644
--- a/Libraries/Image/resolveAssetSource.js
+++ b/Libraries/Image/resolveAssetSource.js
@@ -85,7 +85,7 @@ function resolveAssetSource(source: any): ?ResolvedAssetSource {
     return source;
   }
 
-  var asset = AssetRegistry.getAssetByID(source);
+  const asset = AssetRegistry.getAssetByID(source);
   if (!asset) {
     return null;
   }
diff --git a/Libraries/Inspector/BorderBox.js b/Libraries/Inspector/BorderBox.js
index 7ed32e73ae49..21ace69d9c90 100644
--- a/Libraries/Inspector/BorderBox.js
+++ b/Libraries/Inspector/BorderBox.js
@@ -8,16 +8,16 @@
  */
 'use strict';
 
-var React = require('React');
-var View = require('View');
+const React = require('React');
+const View = require('View');
 
 class BorderBox extends React.Component<$FlowFixMeProps> {
   render() {
-    var box = this.props.box;
+    const box = this.props.box;
     if (!box) {
       return this.props.children;
     }
-    var style = {
+    const style = {
       borderTopWidth: box.top,
       borderBottomWidth: box.bottom,
       borderLeftWidth: box.left,
diff --git a/Libraries/Inspector/BoxInspector.js b/Libraries/Inspector/BoxInspector.js
index 6009e78ea441..11fe9c8c9807 100644
--- a/Libraries/Inspector/BoxInspector.js
+++ b/Libraries/Inspector/BoxInspector.js
@@ -8,13 +8,13 @@
  */
 'use strict';
 
-var React = require('React');
-var StyleSheet = require('StyleSheet');
-var Text = require('Text');
-var View = require('View');
-var resolveBoxStyle = require('resolveBoxStyle');
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const View = require('View');
+const resolveBoxStyle = require('resolveBoxStyle');
 
-var blank = {
+const blank = {
   top: 0,
   left: 0,
   right: 0,
@@ -23,10 +23,10 @@ var blank = {
 
 class BoxInspector extends React.Component<$FlowFixMeProps> {
   render() {
-    var frame = this.props.frame;
-    var style = this.props.style;
-    var margin = style && resolveBoxStyle('margin', style) || blank;
-    var padding = style && resolveBoxStyle('padding', style) || blank;
+    const frame = this.props.frame;
+    const style = this.props.style;
+    const margin = style && resolveBoxStyle('margin', style) || blank;
+    const padding = style && resolveBoxStyle('padding', style) || blank;
     return (
       <BoxContainer title="margin" titleStyle={styles.marginLabel} box={margin}>
         <BoxContainer title="padding" box={padding}>
@@ -46,7 +46,7 @@ class BoxInspector extends React.Component<$FlowFixMeProps> {
 
 class BoxContainer extends React.Component<$FlowFixMeProps> {
   render() {
-    var box = this.props.box;
+    const box = this.props.box;
     return (
       <View style={styles.box}>
         <View style={styles.row}>
@@ -66,7 +66,7 @@ class BoxContainer extends React.Component<$FlowFixMeProps> {
   }
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   row: {
     flexDirection: 'row',
     alignItems: 'center',
diff --git a/Libraries/Inspector/ElementBox.js b/Libraries/Inspector/ElementBox.js
index 7eebb22f337a..17b2c8920e8e 100644
--- a/Libraries/Inspector/ElementBox.js
+++ b/Libraries/Inspector/ElementBox.js
@@ -8,20 +8,20 @@
  */
 'use strict';
 
-var React = require('React');
-var View = require('View');
-var StyleSheet = require('StyleSheet');
-var BorderBox = require('BorderBox');
-var resolveBoxStyle = require('resolveBoxStyle');
+const React = require('React');
+const View = require('View');
+const StyleSheet = require('StyleSheet');
+const BorderBox = require('BorderBox');
+const resolveBoxStyle = require('resolveBoxStyle');
 
-var flattenStyle = require('flattenStyle');
+const flattenStyle = require('flattenStyle');
 
 class ElementBox extends React.Component<$FlowFixMeProps> {
   render() {
-    var style = flattenStyle(this.props.style) || {};
-    var margin = resolveBoxStyle('margin', style);
-    var padding = resolveBoxStyle('padding', style);
-    var frameStyle = this.props.frame;
+    const style = flattenStyle(this.props.style) || {};
+    const margin = resolveBoxStyle('margin', style);
+    const padding = resolveBoxStyle('padding', style);
+    let frameStyle = this.props.frame;
     if (margin) {
       frameStyle = {
         top: frameStyle.top - margin.top,
@@ -30,7 +30,7 @@ class ElementBox extends React.Component<$FlowFixMeProps> {
         width: frameStyle.width + margin.left + margin.right,
       };
     }
-    var contentStyle = {
+    let contentStyle = {
       width: this.props.frame.width,
       height: this.props.frame.height,
     };
@@ -52,7 +52,7 @@ class ElementBox extends React.Component<$FlowFixMeProps> {
   }
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   frame: {
     position: 'absolute',
   },
diff --git a/Libraries/Inspector/InspectorOverlay.js b/Libraries/Inspector/InspectorOverlay.js
index 3ef8ae60f350..a2dda0b316c2 100644
--- a/Libraries/Inspector/InspectorOverlay.js
+++ b/Libraries/Inspector/InspectorOverlay.js
@@ -8,13 +8,13 @@
  */
 'use strict';
 
-var Dimensions = require('Dimensions');
-var ElementBox = require('ElementBox');
-var PropTypes = require('prop-types');
-var React = require('React');
-var StyleSheet = require('StyleSheet');
-var UIManager = require('UIManager');
-var View = require('View');
+const Dimensions = require('Dimensions');
+const ElementBox = require('ElementBox');
+const PropTypes = require('prop-types');
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const UIManager = require('UIManager');
+const View = require('View');
 
 type EventLike = {
   nativeEvent: Object,
@@ -38,7 +38,7 @@ class InspectorOverlay extends React.Component<{
   };
 
   findViewForTouchEvent = (e: EventLike) => {
-    var {locationX, locationY} = e.nativeEvent.touches[0];
+    const {locationX, locationY} = e.nativeEvent.touches[0];
     UIManager.findSubviewIn(
       this.props.inspectedViewTag,
       [locationX, locationY],
@@ -54,7 +54,7 @@ class InspectorOverlay extends React.Component<{
   };
 
   render() {
-    var content = null;
+    let content = null;
     if (this.props.inspected) {
       content = <ElementBox frame={this.props.inspected.frame} style={this.props.inspected.style} />;
     }
@@ -70,7 +70,7 @@ class InspectorOverlay extends React.Component<{
   }
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   inspector: {
     backgroundColor: 'transparent',
     position: 'absolute',
diff --git a/Libraries/Inspector/PerformanceOverlay.js b/Libraries/Inspector/PerformanceOverlay.js
index d414ea2db298..b75c8f1b38bc 100644
--- a/Libraries/Inspector/PerformanceOverlay.js
+++ b/Libraries/Inspector/PerformanceOverlay.js
@@ -8,20 +8,20 @@
  */
 'use strict';
 
-var PerformanceLogger = require('PerformanceLogger');
-var React = require('React');
-var StyleSheet = require('StyleSheet');
-var Text = require('Text');
-var View = require('View');
+const PerformanceLogger = require('PerformanceLogger');
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const View = require('View');
 
 class PerformanceOverlay extends React.Component<{}> {
   render() {
-    var perfLogs = PerformanceLogger.getTimespans();
-    var items = [];
+    const perfLogs = PerformanceLogger.getTimespans();
+    const items = [];
 
-    for (var key in perfLogs) {
+    for (const key in perfLogs) {
       if (perfLogs[key].totalTime) {
-        var unit = (key === 'BundleSize') ? 'b' : 'ms';
+        const unit = (key === 'BundleSize') ? 'b' : 'ms';
         items.push(
           <View style={styles.row} key={key}>
             <Text style={[styles.text, styles.label]}>{key}</Text>
@@ -41,7 +41,7 @@ class PerformanceOverlay extends React.Component<{}> {
   }
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   container: {
     height: 100,
     paddingTop: 10,
diff --git a/Libraries/Inspector/StyleInspector.js b/Libraries/Inspector/StyleInspector.js
index a65e02799652..df32a6688de4 100644
--- a/Libraries/Inspector/StyleInspector.js
+++ b/Libraries/Inspector/StyleInspector.js
@@ -8,17 +8,17 @@
  */
 'use strict';
 
-var React = require('React');
-var StyleSheet = require('StyleSheet');
-var Text = require('Text');
-var View = require('View');
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const View = require('View');
 
 class StyleInspector extends React.Component<$FlowFixMeProps> {
   render() {
     if (!this.props.style) {
       return <Text style={styles.noStyle}>No style</Text>;
     }
-    var names = Object.keys(this.props.style);
+    const names = Object.keys(this.props.style);
     return (
       <View style={styles.container}>
         <View>
@@ -27,7 +27,7 @@ class StyleInspector extends React.Component<$FlowFixMeProps> {
 
         <View>
           {names.map(name => {
-            var value = typeof this.props.style[name] === 'object' ? JSON.stringify(this.props.style[name]) : this.props.style[name];
+            const value = typeof this.props.style[name] === 'object' ? JSON.stringify(this.props.style[name]) : this.props.style[name];
             return <Text key={name} style={styles.value}>{value}</Text>;
           } ) }
         </View>
@@ -36,7 +36,7 @@ class StyleInspector extends React.Component<$FlowFixMeProps> {
   }
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   container: {
     flexDirection: 'row',
   },
diff --git a/Libraries/Inspector/resolveBoxStyle.js b/Libraries/Inspector/resolveBoxStyle.js
index 43026ada8f76..27c89de9b6d8 100644
--- a/Libraries/Inspector/resolveBoxStyle.js
+++ b/Libraries/Inspector/resolveBoxStyle.js
@@ -18,9 +18,9 @@
  * If none are set, returns false.
  */
 function resolveBoxStyle(prefix: string, style: Object): ?Object {
-  var res = {};
-  var subs = ['top', 'left', 'bottom', 'right'];
-  var set = false;
+  const res = {};
+  const subs = ['top', 'left', 'bottom', 'right'];
+  let set = false;
   subs.forEach(sub => {
     res[sub] = style[prefix] || 0;
   });
@@ -36,7 +36,7 @@ function resolveBoxStyle(prefix: string, style: Object): ?Object {
     set = true;
   }
   subs.forEach(sub => {
-    var val = style[prefix + capFirst(sub)];
+    const val = style[prefix + capFirst(sub)];
     if (val) {
       res[sub] = val;
       set = true;
diff --git a/Libraries/Interaction/InteractionManager.js b/Libraries/Interaction/InteractionManager.js
index 7373575a0cae..3d2f2fa46e0b 100644
--- a/Libraries/Interaction/InteractionManager.js
+++ b/Libraries/Interaction/InteractionManager.js
@@ -77,7 +77,7 @@ const DEBUG = false;
  * allowing events such as touches to start interactions and block queued tasks
  * from executing, making apps more responsive.
  */
-var InteractionManager = {
+const InteractionManager = {
   Events: keyMirror({
     interactionStart: true,
     interactionComplete: true,
@@ -118,7 +118,7 @@ var InteractionManager = {
   createInteractionHandle(): Handle {
     DEBUG && infoLog('create interaction handle');
     _scheduleUpdate();
-    var handle = ++_inc;
+    const handle = ++_inc;
     _addInteractionSet.add(handle);
     return handle;
   },
@@ -181,14 +181,14 @@ function _scheduleUpdate() {
 function _processUpdate() {
   _nextUpdateHandle = 0;
 
-  var interactionCount = _interactionSet.size;
+  const interactionCount = _interactionSet.size;
   _addInteractionSet.forEach(handle =>
     _interactionSet.add(handle)
   );
   _deleteInteractionSet.forEach(handle =>
     _interactionSet.delete(handle)
   );
-  var nextInteractionCount = _interactionSet.size;
+  const nextInteractionCount = _interactionSet.size;
 
   if (interactionCount !== 0 && nextInteractionCount === 0) {
     // transition from 1+ --> 0 interactions
diff --git a/Libraries/Interaction/InteractionMixin.js b/Libraries/Interaction/InteractionMixin.js
index e4310ad91d86..018ca1bd16d6 100644
--- a/Libraries/Interaction/InteractionMixin.js
+++ b/Libraries/Interaction/InteractionMixin.js
@@ -8,14 +8,14 @@
  */
 'use strict';
 
-var InteractionManager = require('InteractionManager');
+const InteractionManager = require('InteractionManager');
 
 /**
  * This mixin provides safe versions of InteractionManager start/end methods
  * that ensures `clearInteractionHandle` is always called
  * once per start, even if the component is unmounted.
  */
-var InteractionMixin = {
+const InteractionMixin = {
   componentWillUnmount: function() {
     while (this._interactionMixinHandles.length) {
       InteractionManager.clearInteractionHandle(
@@ -27,7 +27,7 @@ var InteractionMixin = {
   _interactionMixinHandles: ([]: Array<number>),
 
   createInteractionHandle: function() {
-    var handle = InteractionManager.createInteractionHandle();
+    const handle = InteractionManager.createInteractionHandle();
     this._interactionMixinHandles.push(handle);
     return handle;
   },
diff --git a/Libraries/Interaction/__tests__/InteractionMixin-test.js b/Libraries/Interaction/__tests__/InteractionMixin-test.js
index 08f33d759f50..7a3675b13f0b 100644
--- a/Libraries/Interaction/__tests__/InteractionMixin-test.js
+++ b/Libraries/Interaction/__tests__/InteractionMixin-test.js
@@ -11,9 +11,9 @@
 jest.enableAutomock().unmock('InteractionMixin');
 
 describe('InteractionMixin', () => {
-  var InteractionManager;
-  var InteractionMixin;
-  var component;
+  let InteractionManager;
+  let InteractionMixin;
+  let component;
 
   beforeEach(() => {
     jest.resetModules();
@@ -29,19 +29,19 @@ describe('InteractionMixin', () => {
   });
 
   it('should end interactions', () => {
-    var handle = {};
+    const handle = {};
     component.clearInteractionHandle(handle);
     expect(InteractionManager.clearInteractionHandle).toBeCalledWith(handle);
   });
 
   it('should schedule tasks', () => {
-    var task = jest.fn();
+    const task = jest.fn();
     component.runAfterInteractions(task);
     expect(InteractionManager.runAfterInteractions).toBeCalledWith(task);
   });
 
   it('should end unfinished interactions in componentWillUnmount', () => {
-    var handle = component.createInteractionHandle();
+    const handle = component.createInteractionHandle();
     component.componentWillUnmount();
     expect(InteractionManager.clearInteractionHandle).toBeCalledWith(handle);
   });
diff --git a/Libraries/Lists/ListView/ListView.js b/Libraries/Lists/ListView/ListView.js
index b36150510e2c..cd168bc656cd 100644
--- a/Libraries/Lists/ListView/ListView.js
+++ b/Libraries/Lists/ListView/ListView.js
@@ -9,34 +9,34 @@
  */
 'use strict';
 
-var ListViewDataSource = require('ListViewDataSource');
-var Platform = require('Platform');
-var React = require('React');
-var PropTypes = require('prop-types');
-var ReactNative = require('ReactNative');
-var RCTScrollViewManager = require('NativeModules').ScrollViewManager;
-var ScrollView = require('ScrollView');
-var ScrollResponder = require('ScrollResponder');
-var StaticRenderer = require('StaticRenderer');
+const ListViewDataSource = require('ListViewDataSource');
+const Platform = require('Platform');
+const React = require('React');
+const PropTypes = require('prop-types');
+const ReactNative = require('ReactNative');
+const RCTScrollViewManager = require('NativeModules').ScrollViewManager;
+const ScrollView = require('ScrollView');
+const ScrollResponder = require('ScrollResponder');
+const StaticRenderer = require('StaticRenderer');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-var TimerMixin = require('react-timer-mixin');
-var View = require('View');
+const TimerMixin = require('react-timer-mixin');
+const View = require('View');
 
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-var cloneReferencedElement = require('react-clone-referenced-element');
-var createReactClass = require('create-react-class');
-var isEmpty = require('isEmpty');
-var merge = require('merge');
+const cloneReferencedElement = require('react-clone-referenced-element');
+const createReactClass = require('create-react-class');
+const isEmpty = require('isEmpty');
+const merge = require('merge');
 
-var DEFAULT_PAGE_SIZE = 1;
-var DEFAULT_INITIAL_ROWS = 10;
-var DEFAULT_SCROLL_RENDER_AHEAD = 1000;
-var DEFAULT_END_REACHED_THRESHOLD = 1000;
-var DEFAULT_SCROLL_CALLBACK_THROTTLE = 50;
+const DEFAULT_PAGE_SIZE = 1;
+const DEFAULT_INITIAL_ROWS = 10;
+const DEFAULT_SCROLL_RENDER_AHEAD = 1000;
+const DEFAULT_END_REACHED_THRESHOLD = 1000;
+const DEFAULT_SCROLL_CALLBACK_THROTTLE = 50;
 
 /**
  * DEPRECATED - use one of the new list components, such as [`FlatList`](docs/flatlist.html)
@@ -95,7 +95,7 @@ var DEFAULT_SCROLL_CALLBACK_THROTTLE = 50;
  *    rendering rows.
  */
 
-var ListView = createReactClass({
+const ListView = createReactClass({
   displayName: 'ListView',
   _childFrames: ([]: Array<Object>),
   _sentEndForContentLength: (null: ?number),
@@ -405,28 +405,28 @@ var ListView = createReactClass({
   },
 
   render: function() {
-    var bodyComponents = [];
+    const bodyComponents = [];
 
-    var dataSource = this.props.dataSource;
-    var allRowIDs = dataSource.rowIdentities;
-    var rowCount = 0;
-    var stickySectionHeaderIndices = [];
+    const dataSource = this.props.dataSource;
+    const allRowIDs = dataSource.rowIdentities;
+    let rowCount = 0;
+    const stickySectionHeaderIndices = [];
 
     const {renderSectionHeader} = this.props;
 
-    var header = this.props.renderHeader && this.props.renderHeader();
-    var footer = this.props.renderFooter && this.props.renderFooter();
-    var totalIndex = header ? 1 : 0;
+    const header = this.props.renderHeader && this.props.renderHeader();
+    const footer = this.props.renderFooter && this.props.renderFooter();
+    let totalIndex = header ? 1 : 0;
 
-    for (var sectionIdx = 0; sectionIdx < allRowIDs.length; sectionIdx++) {
-      var sectionID = dataSource.sectionIdentities[sectionIdx];
-      var rowIDs = allRowIDs[sectionIdx];
+    for (let sectionIdx = 0; sectionIdx < allRowIDs.length; sectionIdx++) {
+      const sectionID = dataSource.sectionIdentities[sectionIdx];
+      const rowIDs = allRowIDs[sectionIdx];
       if (rowIDs.length === 0) {
         if (this.props.enableEmptySections === undefined) {
           /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses
            * an error found when Flow v0.54 was deployed. To see the error
            * delete this comment and run Flow. */
-          var warning = require('fbjs/lib/warning');
+          const warning = require('fbjs/lib/warning');
           warning(
             false,
             'In next release empty section headers will be rendered.' +
@@ -434,7 +434,7 @@ var ListView = createReactClass({
           );
           continue;
         } else {
-          var invariant = require('fbjs/lib/invariant');
+          const invariant = require('fbjs/lib/invariant');
           invariant(
             this.props.enableEmptySections,
             "In next release 'enableEmptySections' flag will be deprecated, empty section headers will always be rendered." +
@@ -460,13 +460,13 @@ var ListView = createReactClass({
         }
       }
 
-      for (var rowIdx = 0; rowIdx < rowIDs.length; rowIdx++) {
-        var rowID = rowIDs[rowIdx];
-        var comboID = sectionID + '_' + rowID;
-        var shouldUpdateRow =
+      for (let rowIdx = 0; rowIdx < rowIDs.length; rowIdx++) {
+        const rowID = rowIDs[rowIdx];
+        const comboID = sectionID + '_' + rowID;
+        const shouldUpdateRow =
           rowCount >= this._prevRenderedRowsCount &&
           dataSource.rowShouldUpdate(sectionIdx, rowIdx);
-        var row = (
+        const row = (
           <StaticRenderer
             key={'r_' + comboID}
             shouldUpdate={!!shouldUpdateRow}
@@ -486,11 +486,11 @@ var ListView = createReactClass({
           this.props.renderSeparator &&
           (rowIdx !== rowIDs.length - 1 || sectionIdx === allRowIDs.length - 1)
         ) {
-          var adjacentRowHighlighted =
+          const adjacentRowHighlighted =
             this.state.highlightedRow.sectionID === sectionID &&
             (this.state.highlightedRow.rowID === rowID ||
               this.state.highlightedRow.rowID === rowIDs[rowIdx + 1]);
-          var separator = this.props.renderSeparator(
+          const separator = this.props.renderSeparator(
             sectionID,
             rowID,
             adjacentRowHighlighted,
@@ -509,7 +509,7 @@ var ListView = createReactClass({
       }
     }
 
-    var {renderScrollComponent, ...props} = this.props;
+    const {renderScrollComponent, ...props} = this.props;
     if (!props.scrollEventThrottle) {
       props.scrollEventThrottle = DEFAULT_SCROLL_CALLBACK_THROTTLE;
     }
@@ -550,7 +550,7 @@ var ListView = createReactClass({
    */
 
   _measureAndUpdateScrollProps: function() {
-    var scrollComponent = this.getScrollResponder();
+    const scrollComponent = this.getScrollResponder();
     if (!scrollComponent || !scrollComponent.getInnerViewNode) {
       return;
     }
@@ -570,7 +570,7 @@ var ListView = createReactClass({
   },
 
   _onContentSizeChange: function(width: number, height: number) {
-    var contentLength = !this.props.horizontal ? height : width;
+    const contentLength = !this.props.horizontal ? height : width;
     if (contentLength !== this.scrollProperties.contentLength) {
       this.scrollProperties.contentLength = contentLength;
       this._updateVisibleRows();
@@ -581,8 +581,8 @@ var ListView = createReactClass({
   },
 
   _onLayout: function(event: Object) {
-    var {width, height} = event.nativeEvent.layout;
-    var visibleLength = !this.props.horizontal ? height : width;
+    const {width, height} = event.nativeEvent.layout;
+    const visibleLength = !this.props.horizontal ? height : width;
     if (visibleLength !== this.scrollProperties.visibleLength) {
       this.scrollProperties.visibleLength = visibleLength;
       this._updateVisibleRows();
@@ -622,7 +622,7 @@ var ListView = createReactClass({
       return;
     }
 
-    var distanceFromEnd = this._getDistanceFromEnd(this.scrollProperties);
+    const distanceFromEnd = this._getDistanceFromEnd(this.scrollProperties);
     if (distanceFromEnd < this.props.scrollRenderAheadDistance) {
       this._pageInNewRows();
     }
@@ -631,7 +631,7 @@ var ListView = createReactClass({
   _pageInNewRows: function() {
     this.setState(
       (state, props) => {
-        var rowsToRender = Math.min(
+        const rowsToRender = Math.min(
           state.curRenderedRowsCount + props.pageSize,
           props.enableEmptySections
             ? props.dataSource.getRowAndSectionCount()
@@ -666,32 +666,32 @@ var ListView = createReactClass({
         this._childFrames[newFrame.index] = merge(newFrame);
       });
     }
-    var isVertical = !this.props.horizontal;
-    var dataSource = this.props.dataSource;
-    var visibleMin = this.scrollProperties.offset;
-    var visibleMax = visibleMin + this.scrollProperties.visibleLength;
-    var allRowIDs = dataSource.rowIdentities;
-
-    var header = this.props.renderHeader && this.props.renderHeader();
-    var totalIndex = header ? 1 : 0;
-    var visibilityChanged = false;
-    var changedRows = {};
-    for (var sectionIdx = 0; sectionIdx < allRowIDs.length; sectionIdx++) {
-      var rowIDs = allRowIDs[sectionIdx];
+    const isVertical = !this.props.horizontal;
+    const dataSource = this.props.dataSource;
+    const visibleMin = this.scrollProperties.offset;
+    const visibleMax = visibleMin + this.scrollProperties.visibleLength;
+    const allRowIDs = dataSource.rowIdentities;
+
+    const header = this.props.renderHeader && this.props.renderHeader();
+    let totalIndex = header ? 1 : 0;
+    let visibilityChanged = false;
+    const changedRows = {};
+    for (let sectionIdx = 0; sectionIdx < allRowIDs.length; sectionIdx++) {
+      const rowIDs = allRowIDs[sectionIdx];
       if (rowIDs.length === 0) {
         continue;
       }
-      var sectionID = dataSource.sectionIdentities[sectionIdx];
+      const sectionID = dataSource.sectionIdentities[sectionIdx];
       if (this.props.renderSectionHeader) {
         totalIndex++;
       }
-      var visibleSection = this._visibleRows[sectionID];
+      let visibleSection = this._visibleRows[sectionID];
       if (!visibleSection) {
         visibleSection = {};
       }
-      for (var rowIdx = 0; rowIdx < rowIDs.length; rowIdx++) {
-        var rowID = rowIDs[rowIdx];
-        var frame = this._childFrames[totalIndex];
+      for (let rowIdx = 0; rowIdx < rowIDs.length; rowIdx++) {
+        const rowID = rowIDs[rowIdx];
+        const frame = this._childFrames[totalIndex];
         totalIndex++;
         if (
           this.props.renderSeparator &&
@@ -702,9 +702,9 @@ var ListView = createReactClass({
         if (!frame) {
           break;
         }
-        var rowVisible = visibleSection[rowID];
-        var min = isVertical ? frame.y : frame.x;
-        var max = min + (isVertical ? frame.height : frame.width);
+        const rowVisible = visibleSection[rowID];
+        const min = isVertical ? frame.y : frame.x;
+        const max = min + (isVertical ? frame.height : frame.width);
         if ((!min && !max) || min === max) {
           break;
         }
@@ -737,7 +737,7 @@ var ListView = createReactClass({
   },
 
   _onScroll: function(e: Object) {
-    var isVertical = !this.props.horizontal;
+    const isVertical = !this.props.horizontal;
     this.scrollProperties.visibleLength =
       e.nativeEvent.layoutMeasurement[isVertical ? 'height' : 'width'];
     this.scrollProperties.contentLength =
diff --git a/Libraries/Lists/ListView/ListViewDataSource.js b/Libraries/Lists/ListView/ListViewDataSource.js
index dda74b50cb83..b046a58bfd2a 100644
--- a/Libraries/Lists/ListView/ListViewDataSource.js
+++ b/Libraries/Lists/ListView/ListViewDataSource.js
@@ -9,12 +9,12 @@
  */
 'use strict';
 
-var invariant = require('fbjs/lib/invariant');
-var isEmpty = require('isEmpty');
+const invariant = require('fbjs/lib/invariant');
+const isEmpty = require('isEmpty');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-var warning = require('fbjs/lib/warning');
+const warning = require('fbjs/lib/warning');
 
 function defaultGetRowData(
   dataBlob: any,
@@ -142,7 +142,7 @@ class ListViewDataSource {
     dataBlob: $ReadOnlyArray<any> | {+[key: string]: any},
     rowIdentities: ?$ReadOnlyArray<string>,
   ): ListViewDataSource {
-    var rowIds = rowIdentities ? [[...rowIdentities]] : null;
+    const rowIds = rowIdentities ? [[...rowIdentities]] : null;
     if (!this._sectionHeaderHasChanged) {
       this._sectionHeaderHasChanged = () => false;
     }
@@ -184,7 +184,7 @@ class ListViewDataSource {
       'row and section ids lengths must be the same',
     );
 
-    var newSource = new ListViewDataSource({
+    const newSource = new ListViewDataSource({
       getRowData: this._getRowData,
       getSectionHeaderData: this._getSectionHeaderData,
       rowHasChanged: this._rowHasChanged,
@@ -237,7 +237,7 @@ class ListViewDataSource {
    * Returns if the row is dirtied and needs to be rerendered
    */
   rowShouldUpdate(sectionIndex: number, rowIndex: number): boolean {
-    var needsUpdate = this._dirtyRows[sectionIndex][rowIndex];
+    const needsUpdate = this._dirtyRows[sectionIndex][rowIndex];
     warning(
       needsUpdate !== undefined,
       'missing dirtyBit for section, row: ' + sectionIndex + ', ' + rowIndex,
@@ -249,8 +249,8 @@ class ListViewDataSource {
    * Gets the data required to render the row.
    */
   getRowData(sectionIndex: number, rowIndex: number): any {
-    var sectionID = this.sectionIdentities[sectionIndex];
-    var rowID = this.rowIdentities[sectionIndex][rowIndex];
+    const sectionID = this.sectionIdentities[sectionIndex];
+    const rowID = this.rowIdentities[sectionIndex][rowIndex];
     warning(
       sectionID !== undefined && rowID !== undefined,
       'rendering invalid section, row: ' + sectionIndex + ', ' + rowIndex,
@@ -263,8 +263,8 @@ class ListViewDataSource {
    * or null of out of range indexes.
    */
   getRowIDForFlatIndex(index: number): ?string {
-    var accessIndex = index;
-    for (var ii = 0; ii < this.sectionIdentities.length; ii++) {
+    let accessIndex = index;
+    for (let ii = 0; ii < this.sectionIdentities.length; ii++) {
       if (accessIndex >= this.rowIdentities[ii].length) {
         accessIndex -= this.rowIdentities[ii].length;
       } else {
@@ -279,8 +279,8 @@ class ListViewDataSource {
    * or null for out of range indexes.
    */
   getSectionIDForFlatIndex(index: number): ?string {
-    var accessIndex = index;
-    for (var ii = 0; ii < this.sectionIdentities.length; ii++) {
+    let accessIndex = index;
+    for (let ii = 0; ii < this.sectionIdentities.length; ii++) {
       if (accessIndex >= this.rowIdentities[ii].length) {
         accessIndex -= this.rowIdentities[ii].length;
       } else {
@@ -294,8 +294,8 @@ class ListViewDataSource {
    * Returns an array containing the number of rows in each section
    */
   getSectionLengths(): Array<number> {
-    var results = [];
-    for (var ii = 0; ii < this.sectionIdentities.length; ii++) {
+    const results = [];
+    for (let ii = 0; ii < this.sectionIdentities.length; ii++) {
       results.push(this.rowIdentities[ii].length);
     }
     return results;
@@ -305,7 +305,7 @@ class ListViewDataSource {
    * Returns if the section header is dirtied and needs to be rerendered
    */
   sectionHeaderShouldUpdate(sectionIndex: number): boolean {
-    var needsUpdate = this._dirtySections[sectionIndex];
+    const needsUpdate = this._dirtySections[sectionIndex];
     warning(
       needsUpdate !== undefined,
       'missing dirtyBit for section: ' + sectionIndex,
@@ -320,7 +320,7 @@ class ListViewDataSource {
     if (!this._getSectionHeaderData) {
       return null;
     }
-    var sectionID = this.sectionIdentities[sectionIndex];
+    const sectionID = this.sectionIdentities[sectionIndex];
     warning(
       sectionID !== undefined,
       'renderSection called on invalid section: ' + sectionIndex,
@@ -353,9 +353,9 @@ class ListViewDataSource {
     prevRowIDs: Array<Array<string>>,
   ): void {
     // construct a hashmap of the existing (old) id arrays
-    var prevSectionsHash = keyedDictionaryFromArray(prevSectionIDs);
-    var prevRowsHash = {};
-    for (var ii = 0; ii < prevRowIDs.length; ii++) {
+    const prevSectionsHash = keyedDictionaryFromArray(prevSectionIDs);
+    const prevRowsHash = {};
+    for (let ii = 0; ii < prevRowIDs.length; ii++) {
       var sectionID = prevSectionIDs[ii];
       warning(
         !prevRowsHash[sectionID],
@@ -368,12 +368,12 @@ class ListViewDataSource {
     this._dirtySections = [];
     this._dirtyRows = [];
 
-    var dirty;
-    for (var sIndex = 0; sIndex < this.sectionIdentities.length; sIndex++) {
+    let dirty;
+    for (let sIndex = 0; sIndex < this.sectionIdentities.length; sIndex++) {
       var sectionID = this.sectionIdentities[sIndex];
       // dirty if the sectionHeader is new or _sectionHasChanged is true
       dirty = !prevSectionsHash[sectionID];
-      var sectionHeaderHasChanged = this._sectionHeaderHasChanged;
+      const sectionHeaderHasChanged = this._sectionHeaderHasChanged;
       if (!dirty && sectionHeaderHasChanged) {
         dirty = sectionHeaderHasChanged(
           this._getSectionHeaderData(prevDataBlob, sectionID),
@@ -384,11 +384,11 @@ class ListViewDataSource {
 
       this._dirtyRows[sIndex] = [];
       for (
-        var rIndex = 0;
+        let rIndex = 0;
         rIndex < this.rowIdentities[sIndex].length;
         rIndex++
       ) {
-        var rowID = this.rowIdentities[sIndex][rIndex];
+        const rowID = this.rowIdentities[sIndex][rIndex];
         // dirty if the section is new, row is new or _rowHasChanged is true
         dirty =
           !prevSectionsHash[sectionID] ||
@@ -404,9 +404,9 @@ class ListViewDataSource {
 }
 
 function countRows(allRowIDs) {
-  var totalRows = 0;
-  for (var sectionIdx = 0; sectionIdx < allRowIDs.length; sectionIdx++) {
-    var rowIDs = allRowIDs[sectionIdx];
+  let totalRows = 0;
+  for (let sectionIdx = 0; sectionIdx < allRowIDs.length; sectionIdx++) {
+    const rowIDs = allRowIDs[sectionIdx];
     totalRows += rowIDs.length;
   }
   return totalRows;
@@ -416,9 +416,9 @@ function keyedDictionaryFromArray(arr) {
   if (isEmpty(arr)) {
     return {};
   }
-  var result = {};
-  for (var ii = 0; ii < arr.length; ii++) {
-    var key = arr[ii];
+  const result = {};
+  for (let ii = 0; ii < arr.length; ii++) {
+    const key = arr[ii];
     warning(!result[key], 'Value appears more than once in array: ' + key);
     result[key] = true;
   }
diff --git a/Libraries/Modal/Modal.js b/Libraries/Modal/Modal.js
index 52ed8c7a2b9e..77f50cf273d7 100644
--- a/Libraries/Modal/Modal.js
+++ b/Libraries/Modal/Modal.js
@@ -36,7 +36,7 @@ import type EmitterSubscription from 'EmitterSubscription';
 // <Modal> on screen. There can be different ones, either nested or as siblings.
 // We cannot pass the onDismiss callback to native as the view will be
 // destroyed before the callback is fired.
-var uniqueModalIdentifier = 0;
+let uniqueModalIdentifier = 0;
 
 class Modal extends React.Component<Object> {
   static propTypes = {
diff --git a/Libraries/Network/FormData.js b/Libraries/Network/FormData.js
index 6028a06bf876..40f351c5a5ee 100644
--- a/Libraries/Network/FormData.js
+++ b/Libraries/Network/FormData.js
@@ -60,9 +60,9 @@ class FormData {
 
   getParts(): Array<FormDataPart> {
     return this._parts.map(([name, value]) => {
-      var contentDisposition = 'form-data; name="' + name + '"';
+      const contentDisposition = 'form-data; name="' + name + '"';
 
-      var headers: Headers = {'content-disposition': contentDisposition};
+      const headers: Headers = {'content-disposition': contentDisposition};
 
       // The body part is a "blob", which in React Native just means
       // an object with a `uri` attribute. Optionally, it can also
diff --git a/Libraries/Network/XHRInterceptor.js b/Libraries/Network/XHRInterceptor.js
index 22c6cf853fe0..f3dd1e03e084 100644
--- a/Libraries/Network/XHRInterceptor.js
+++ b/Libraries/Network/XHRInterceptor.js
@@ -12,13 +12,13 @@ const originalXHROpen = XMLHttpRequest.prototype.open;
 const originalXHRSend = XMLHttpRequest.prototype.send;
 const originalXHRSetRequestHeader = XMLHttpRequest.prototype.setRequestHeader;
 
-var openCallback;
-var sendCallback;
-var requestHeaderCallback;
-var headerReceivedCallback;
-var responseCallback;
+let openCallback;
+let sendCallback;
+let requestHeaderCallback;
+let headerReceivedCallback;
+let responseCallback;
 
-var isInterceptorEnabled = false;
+let isInterceptorEnabled = false;
 
 /**
  * A network interceptor which monkey-patches XMLHttpRequest methods
diff --git a/Libraries/Network/XMLHttpRequest.js b/Libraries/Network/XMLHttpRequest.js
index dd43fa40c86c..afbfc7db68df 100644
--- a/Libraries/Network/XMLHttpRequest.js
+++ b/Libraries/Network/XMLHttpRequest.js
@@ -421,14 +421,14 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
       // according to the spec, return null if no response has been received
       return null;
     }
-    var headers = this.responseHeaders || {};
+    const headers = this.responseHeaders || {};
     return Object.keys(headers).map((headerName) => {
       return headerName + ': ' + headers[headerName];
     }).join('\r\n');
   }
 
   getResponseHeader(header: string): ?string {
-    var value = this._lowerCaseResponseHeaders[header.toLowerCase()];
+    const value = this._lowerCaseResponseHeaders[header.toLowerCase()];
     return value !== undefined ? value : null;
   }
 
@@ -545,7 +545,7 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
 
   setResponseHeaders(responseHeaders: ?Object): void {
     this.responseHeaders = responseHeaders || null;
-    var headers = responseHeaders || {};
+    const headers = responseHeaders || {};
     this._lowerCaseResponseHeaders =
       Object.keys(headers).reduce((lcaseHeaders, headerName) => {
         lcaseHeaders[headerName.toLowerCase()] = headers[headerName];
diff --git a/Libraries/PushNotificationIOS/PushNotificationIOS.js b/Libraries/PushNotificationIOS/PushNotificationIOS.js
index 9f013436c991..fc3db58f2974 100644
--- a/Libraries/PushNotificationIOS/PushNotificationIOS.js
+++ b/Libraries/PushNotificationIOS/PushNotificationIOS.js
@@ -182,7 +182,7 @@ class PushNotificationIOS {
       type === 'notification' || type === 'register' || type === 'registrationError' || type === 'localNotification',
       'PushNotificationIOS only supports `notification`, `register`, `registrationError`, and `localNotification` events'
     );
-    var listener;
+    let listener;
     if (type === 'notification') {
       listener =  PushNotificationEmitter.addListener(
         DEVICE_NOTIF_EVENT,
@@ -226,7 +226,7 @@ class PushNotificationIOS {
       type === 'notification' || type === 'register' || type === 'registrationError' || type === 'localNotification',
       'PushNotificationIOS only supports `notification`, `register`, `registrationError`, and `localNotification` events'
     );
-    var listener = _notifHandlers.get(type);
+    const listener = _notifHandlers.get(type);
     if (!listener) {
       return;
     }
@@ -251,7 +251,7 @@ class PushNotificationIOS {
     badge: boolean,
     sound: boolean
   }> {
-    var requestedPermissions = {};
+    let requestedPermissions = {};
     if (permissions) {
       requestedPermissions = {
         alert: !!permissions.alert,
@@ -321,7 +321,7 @@ class PushNotificationIOS {
       // Extract data from Apple's `aps` dict as defined:
       // https://developer.apple.com/library/ios/documentation/NetworkingInternet/Conceptual/RemoteNotificationsPG/Chapters/ApplePushService.html
       Object.keys(nativeNotif).forEach((notifKey) => {
-        var notifVal = nativeNotif[notifKey];
+        const notifVal = nativeNotif[notifKey];
         if (notifKey === 'aps') {
           this._alert = notifVal.alert;
           this._sound = notifVal.sound;
diff --git a/Libraries/RCTTest/SnapshotViewIOS.ios.js b/Libraries/RCTTest/SnapshotViewIOS.ios.js
index 050ec5d633dd..0a2877a9d642 100644
--- a/Libraries/RCTTest/SnapshotViewIOS.ios.js
+++ b/Libraries/RCTTest/SnapshotViewIOS.ios.js
@@ -8,16 +8,16 @@
  */
 'use strict';
 
-var React = require('React');
+const React = require('React');
 const PropTypes = require('prop-types');
-var StyleSheet = require('StyleSheet');
-var { TestModule } = require('NativeModules');
-var UIManager = require('UIManager');
-var View = require('View');
+const StyleSheet = require('StyleSheet');
+const { TestModule } = require('NativeModules');
+const UIManager = require('UIManager');
+const View = require('View');
 
 const ViewPropTypes = require('ViewPropTypes');
 
-var requireNativeComponent = require('requireNativeComponent');
+const requireNativeComponent = require('requireNativeComponent');
 
 class SnapshotViewIOS extends React.Component<{
   onSnapshotReady?: Function,
@@ -37,8 +37,8 @@ class SnapshotViewIOS extends React.Component<{
   };
 
   render() {
-    var testIdentifier = this.props.testIdentifier || 'test';
-    var onSnapshotReady = this.props.onSnapshotReady || this.onDefaultAction;
+    const testIdentifier = this.props.testIdentifier || 'test';
+    const onSnapshotReady = this.props.onSnapshotReady || this.onDefaultAction;
     return (
       <RCTSnapshot
         style={style.snapshot}
@@ -50,7 +50,7 @@ class SnapshotViewIOS extends React.Component<{
   }
 }
 
-var style = StyleSheet.create({
+const style = StyleSheet.create({
   snapshot: {
     flex: 1,
   },
@@ -59,7 +59,7 @@ var style = StyleSheet.create({
 // Verify that RCTSnapshot is part of the UIManager since it is only loaded
 // if you have linked against RCTTest like in tests, otherwise we will have
 // a warning printed out
-var RCTSnapshot = UIManager.RCTSnapshot ?
+const RCTSnapshot = UIManager.RCTSnapshot ?
   requireNativeComponent('RCTSnapshot', SnapshotViewIOS) :
   View;
 
diff --git a/Libraries/ReactNative/UIManagerStatTracker.js b/Libraries/ReactNative/UIManagerStatTracker.js
index 3e1a6afd0739..f0f47f1b3e22 100644
--- a/Libraries/ReactNative/UIManagerStatTracker.js
+++ b/Libraries/ReactNative/UIManagerStatTracker.js
@@ -9,17 +9,17 @@
  */
 'use strict';
 
-var UIManager = require('UIManager');
+const UIManager = require('UIManager');
 
-var installed = false;
-var UIManagerStatTracker = {
+let installed = false;
+const UIManagerStatTracker = {
   install: function() {
     if (installed) {
       return;
     }
     installed = true;
-    var statLogHandle;
-    var stats = {};
+    let statLogHandle;
+    const stats = {};
     function printStats() {
       console.log({UIManagerStatTracker: stats});
       statLogHandle = null;
@@ -30,19 +30,19 @@ var UIManagerStatTracker = {
         statLogHandle = setImmediate(printStats);
       }
     }
-    var createViewOrig = UIManager.createView;
+    const createViewOrig = UIManager.createView;
     UIManager.createView = function(tag, className, rootTag, props) {
       incStat('createView', 1);
       incStat('setProp', Object.keys(props || []).length);
       createViewOrig(tag, className, rootTag, props);
     };
-    var updateViewOrig = UIManager.updateView;
+    const updateViewOrig = UIManager.updateView;
     UIManager.updateView = function(tag, className, props) {
       incStat('updateView', 1);
       incStat('setProp', Object.keys(props || []).length);
       updateViewOrig(tag, className, props);
     };
-    var manageChildrenOrig = UIManager.manageChildren;
+    const manageChildrenOrig = UIManager.manageChildren;
     UIManager.manageChildren = function(
       tag,
       moveFrom,
diff --git a/Libraries/ReactNative/YellowBox.js b/Libraries/ReactNative/YellowBox.js
index aa5d9788ab9f..f25de5a2a60c 100644
--- a/Libraries/ReactNative/YellowBox.js
+++ b/Libraries/ReactNative/YellowBox.js
@@ -452,7 +452,7 @@ const rowHeight = 46;
 const elevation =
   Platform.OS === 'android' ? Number.MAX_SAFE_INTEGER : undefined;
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   fullScreen: {
     height: '100%',
     width: '100%',
diff --git a/Libraries/ReactNative/queryLayoutByID.js b/Libraries/ReactNative/queryLayoutByID.js
index b4d001e04d98..6703612959a9 100644
--- a/Libraries/ReactNative/queryLayoutByID.js
+++ b/Libraries/ReactNative/queryLayoutByID.js
@@ -9,7 +9,7 @@
  */
 'use strict';
 
-var UIManager = require('UIManager');
+const UIManager = require('UIManager');
 
 type OnSuccessCallback = (
   left: number,
@@ -42,7 +42,7 @@ type OnErrorCallback = (error: any) => void;
  * @param {function} onError `func(error)`
  * @param {function} onSuccess `func(left, top, width, height, pageX, pageY)`
  */
-var queryLayoutByID = function(
+const queryLayoutByID = function(
   tag: ?number,
   onError: OnErrorCallback,
   onSuccess: OnSuccessCallback,
diff --git a/Libraries/Sample/Sample.android.js b/Libraries/Sample/Sample.android.js
index dbb43949f6f6..61b3948415b8 100644
--- a/Libraries/Sample/Sample.android.js
+++ b/Libraries/Sample/Sample.android.js
@@ -5,9 +5,9 @@
  */
 'use strict';
 
-var warning = require('fbjs/lib/warning');
+const warning = require('fbjs/lib/warning');
 
-var Sample = {
+const Sample = {
   test: function() {
     warning('Not yet implemented for Android.');
   }
diff --git a/Libraries/Sample/Sample.ios.js b/Libraries/Sample/Sample.ios.js
index ae51247cc635..0e459eb90ae3 100644
--- a/Libraries/Sample/Sample.ios.js
+++ b/Libraries/Sample/Sample.ios.js
@@ -3,13 +3,13 @@
  */
 'use strict';
 
-var NativeSample = require('NativeModules').Sample;
+const NativeSample = require('NativeModules').Sample;
 
 /**
  * High-level docs for the Sample iOS API can be written here.
  */
 
-var Sample = {
+const Sample = {
   test: function() {
     NativeSample.test();
   }
diff --git a/Libraries/Settings/Settings.android.js b/Libraries/Settings/Settings.android.js
index 220c04e8b159..c87accba5834 100644
--- a/Libraries/Settings/Settings.android.js
+++ b/Libraries/Settings/Settings.android.js
@@ -8,7 +8,7 @@
  */
 'use strict';
 
-var Settings = {
+const Settings = {
   get(key: string): mixed {
     console.warn('Settings is not yet supported on Android');
     return null;
diff --git a/Libraries/Settings/Settings.ios.js b/Libraries/Settings/Settings.ios.js
index 46f0a8bebdd7..d0c893ddfb6d 100644
--- a/Libraries/Settings/Settings.ios.js
+++ b/Libraries/Settings/Settings.ios.js
@@ -8,14 +8,14 @@
  */
 'use strict';
 
-var RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
-var RCTSettingsManager = require('NativeModules').SettingsManager;
+const RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
+const RCTSettingsManager = require('NativeModules').SettingsManager;
 
-var invariant = require('fbjs/lib/invariant');
+const invariant = require('fbjs/lib/invariant');
 
-var subscriptions: Array<{keys: Array<string>, callback: ?Function}> = [];
+const subscriptions: Array<{keys: Array<string>, callback: ?Function}> = [];
 
-var Settings = {
+const Settings = {
   _settings: RCTSettingsManager && RCTSettingsManager.settings,
 
   get(key: string): mixed {
@@ -37,7 +37,7 @@ var Settings = {
       'keys should be a string or array of strings'
     );
 
-    var sid = subscriptions.length;
+    const sid = subscriptions.length;
     subscriptions.push({keys: keys, callback: callback});
     return sid;
   },
@@ -50,8 +50,8 @@ var Settings = {
 
   _sendObservations(body: Object) {
     Object.keys(body).forEach((key) => {
-      var newValue = body[key];
-      var didChange = this._settings[key] !== newValue;
+      const newValue = body[key];
+      const didChange = this._settings[key] !== newValue;
       this._settings[key] = newValue;
 
       if (didChange) {
diff --git a/Libraries/Storage/AsyncStorage.js b/Libraries/Storage/AsyncStorage.js
index f953aecbce26..ed5042edd934 100644
--- a/Libraries/Storage/AsyncStorage.js
+++ b/Libraries/Storage/AsyncStorage.js
@@ -24,7 +24,7 @@ const RCTAsyncStorage = NativeModules.AsyncRocksDBStorage ||
  *
  * See http://facebook.github.io/react-native/docs/asyncstorage.html
  */
-var AsyncStorage = {
+const AsyncStorage = {
   _getRequests: ([]: Array<any>),
   _getKeys: ([]: Array<string>),
   _immediate: (null: ?number),
@@ -41,8 +41,8 @@ var AsyncStorage = {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiGet([key], function(errors, result) {
         // Unpack result to get value from [[key,value]]
-        var value = (result && result[0] && result[0][1]) ? result[0][1] : null;
-        var errs = convertErrors(errors);
+        const value = (result && result[0] && result[0][1]) ? result[0][1] : null;
+        const errs = convertErrors(errors);
         callback && callback(errs && errs[0], value);
         if (errs) {
           reject(errs[0]);
@@ -65,7 +65,7 @@ var AsyncStorage = {
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiSet([[key,value]], function(errors) {
-        var errs = convertErrors(errors);
+        const errs = convertErrors(errors);
         callback && callback(errs && errs[0]);
         if (errs) {
           reject(errs[0]);
@@ -87,7 +87,7 @@ var AsyncStorage = {
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiRemove([key], function(errors) {
-        var errs = convertErrors(errors);
+        const errs = convertErrors(errors);
         callback && callback(errs && errs[0]);
         if (errs) {
           reject(errs[0]);
@@ -113,7 +113,7 @@ var AsyncStorage = {
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiMerge([[key,value]], function(errors) {
-        var errs = convertErrors(errors);
+        const errs = convertErrors(errors);
         callback && callback(errs && errs[0]);
         if (errs) {
           reject(errs[0]);
@@ -222,7 +222,7 @@ var AsyncStorage = {
       });
     }
 
-    var getRequest = {
+    const getRequest = {
       keys: keys,
       callback: callback,
       // do we need this?
@@ -231,7 +231,7 @@ var AsyncStorage = {
       reject: null,
     };
 
-    var promiseResult = new Promise((resolve, reject) => {
+    const promiseResult = new Promise((resolve, reject) => {
       getRequest.resolve = resolve;
       getRequest.reject = reject;
     });
@@ -259,7 +259,7 @@ var AsyncStorage = {
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiSet(keyValuePairs, function(errors) {
-        var error = convertErrors(errors);
+        const error = convertErrors(errors);
         callback && callback(error);
         if (error) {
           reject(error);
@@ -281,7 +281,7 @@ var AsyncStorage = {
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiRemove(keys, function(errors) {
-        var error = convertErrors(errors);
+        const error = convertErrors(errors);
         callback && callback(error);
         if (error) {
           reject(error);
@@ -306,7 +306,7 @@ var AsyncStorage = {
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiMerge(keyValuePairs, function(errors) {
-        var error = convertErrors(errors);
+        const error = convertErrors(errors);
         callback && callback(error);
         if (error) {
           reject(error);
@@ -335,7 +335,7 @@ function convertError(error) {
   if (!error) {
     return null;
   }
-  var out = new Error(error.message);
+  const out = new Error(error.message);
   out.key = error.key; // flow doesn't like this :(
   return out;
 }
diff --git a/Libraries/StyleSheet/ColorPropType.js b/Libraries/StyleSheet/ColorPropType.js
index 28bc93f45fa9..562d3ad89ff8 100644
--- a/Libraries/StyleSheet/ColorPropType.js
+++ b/Libraries/StyleSheet/ColorPropType.js
@@ -7,10 +7,10 @@
  */
 'use strict';
 
-var normalizeColor = require('normalizeColor');
+const normalizeColor = require('normalizeColor');
 
-var colorPropType = function(isRequired, props, propName, componentName, location, propFullName) {
-  var color = props[propName];
+const colorPropType = function(isRequired, props, propName, componentName, location, propFullName) {
+  const color = props[propName];
   if (color === undefined || color === null) {
     if (isRequired) {
       return new Error(
@@ -48,7 +48,7 @@ var colorPropType = function(isRequired, props, propName, componentName, locatio
   }
 };
 
-var ColorPropType = colorPropType.bind(null, false /* isRequired */);
+const ColorPropType = colorPropType.bind(null, false /* isRequired */);
 ColorPropType.isRequired = colorPropType.bind(null, true /* isRequired */);
 
 module.exports = ColorPropType;
diff --git a/Libraries/StyleSheet/LayoutPropTypes.js b/Libraries/StyleSheet/LayoutPropTypes.js
index 6ff1844c7fac..aa755aa4473d 100644
--- a/Libraries/StyleSheet/LayoutPropTypes.js
+++ b/Libraries/StyleSheet/LayoutPropTypes.js
@@ -8,7 +8,7 @@
  */
 'use strict';
 
-var ReactPropTypes = require('prop-types');
+const ReactPropTypes = require('prop-types');
 
 /**
  * React Native's layout system is based on Flexbox and is powered both
@@ -23,7 +23,7 @@ var ReactPropTypes = require('prop-types');
  * These properties are a subset of our styles that are consumed by the layout
  * algorithm and affect the positioning and sizing of views.
  */
-var LayoutPropTypes = {
+const LayoutPropTypes = {
   /** `display` sets the display type of this component.
    *
    *  It works similarly to `display` in CSS, but only support 'flex' and 'none'.
diff --git a/Libraries/StyleSheet/PointPropType.js b/Libraries/StyleSheet/PointPropType.js
index 44efc2d5fc40..8a93b6c54642 100644
--- a/Libraries/StyleSheet/PointPropType.js
+++ b/Libraries/StyleSheet/PointPropType.js
@@ -8,11 +8,11 @@
  */
 'use strict';
 
-var PropTypes = require('prop-types');
+const PropTypes = require('prop-types');
 
-var createStrictShapeTypeChecker = require('createStrictShapeTypeChecker');
+const createStrictShapeTypeChecker = require('createStrictShapeTypeChecker');
 
-var PointPropType = createStrictShapeTypeChecker({
+const PointPropType = createStrictShapeTypeChecker({
   x: PropTypes.number,
   y: PropTypes.number,
 });
diff --git a/Libraries/StyleSheet/StyleSheetPropType.js b/Libraries/StyleSheet/StyleSheetPropType.js
index 9fed3d207a63..e024c9374fea 100644
--- a/Libraries/StyleSheet/StyleSheetPropType.js
+++ b/Libraries/StyleSheet/StyleSheetPropType.js
@@ -8,15 +8,15 @@
  */
 'use strict';
 
-var createStrictShapeTypeChecker = require('createStrictShapeTypeChecker');
-var flattenStyle = require('flattenStyle');
+const createStrictShapeTypeChecker = require('createStrictShapeTypeChecker');
+const flattenStyle = require('flattenStyle');
 
 function StyleSheetPropType(
   shape: {[key: string]: ReactPropsCheckType}
 ): ReactPropsCheckType {
-  var shapePropType = createStrictShapeTypeChecker(shape);
+  const shapePropType = createStrictShapeTypeChecker(shape);
   return function(props, propName, componentName, location?, ...rest) {
-    var newProps = props;
+    let newProps = props;
     if (props[propName]) {
       // Just make a dummy prop object with only the flattened style
       newProps = {};
diff --git a/Libraries/StyleSheet/StyleSheetValidation.js b/Libraries/StyleSheet/StyleSheetValidation.js
index ae6c843de4f7..c7686dcb9e93 100644
--- a/Libraries/StyleSheet/StyleSheetValidation.js
+++ b/Libraries/StyleSheet/StyleSheetValidation.js
@@ -8,11 +8,11 @@
  */
 'use strict';
 
-var ImageStylePropTypes = require('ImageStylePropTypes');
-var TextStylePropTypes = require('TextStylePropTypes');
-var ViewStylePropTypes = require('ViewStylePropTypes');
+const ImageStylePropTypes = require('ImageStylePropTypes');
+const TextStylePropTypes = require('TextStylePropTypes');
+const ViewStylePropTypes = require('ViewStylePropTypes');
 
-var invariant = require('fbjs/lib/invariant');
+const invariant = require('fbjs/lib/invariant');
 
 // Hardcoded because this is a legit case but we don't want to load it from
 // a private API. We might likely want to unify style sheet creation with how it
@@ -26,12 +26,12 @@ class StyleSheetValidation {
       return;
     }
     if (allStylePropTypes[prop] === undefined) {
-      var message1 = '"' + prop + '" is not a valid style property.';
-      var message2 = '\nValid style props: ' +
+      const message1 = '"' + prop + '" is not a valid style property.';
+      const message2 = '\nValid style props: ' +
         JSON.stringify(Object.keys(allStylePropTypes).sort(), null, '  ');
       styleError(message1, style, caller, message2);
     }
-    var error = allStylePropTypes[prop](
+    const error = allStylePropTypes[prop](
       style,
       prop,
       caller,
@@ -48,19 +48,19 @@ class StyleSheetValidation {
     if (!__DEV__) {
       return;
     }
-    for (var prop in styles[name]) {
+    for (const prop in styles[name]) {
       StyleSheetValidation.validateStyleProp(prop, styles[name], 'StyleSheet ' + name);
     }
   }
 
   static addValidStylePropTypes(stylePropTypes) {
-    for (var key in stylePropTypes) {
+    for (const key in stylePropTypes) {
       allStylePropTypes[key] = stylePropTypes[key];
     }
   }
 }
 
-var styleError = function(message1, style, caller?, message2?) {
+const styleError = function(message1, style, caller?, message2?) {
   invariant(
     false,
     message1 + '\n' + (caller || '<<unknown>>') + ': ' +
@@ -68,7 +68,7 @@ var styleError = function(message1, style, caller?, message2?) {
   );
 };
 
-var allStylePropTypes = {};
+const allStylePropTypes = {};
 
 StyleSheetValidation.addValidStylePropTypes(ImageStylePropTypes);
 StyleSheetValidation.addValidStylePropTypes(TextStylePropTypes);
diff --git a/Libraries/StyleSheet/TransformPropTypes.js b/Libraries/StyleSheet/TransformPropTypes.js
index 13a58fdd7ff8..2f9037abf0ad 100644
--- a/Libraries/StyleSheet/TransformPropTypes.js
+++ b/Libraries/StyleSheet/TransformPropTypes.js
@@ -8,11 +8,11 @@
  */
 'use strict';
 
-var ReactPropTypes = require('prop-types');
+const ReactPropTypes = require('prop-types');
 
-var deprecatedPropType = require('deprecatedPropType');
+const deprecatedPropType = require('deprecatedPropType');
 
-var TransformMatrixPropType = function(
+const TransformMatrixPropType = function(
   props : Object,
   propName : string,
   componentName : string
@@ -25,7 +25,7 @@ var TransformMatrixPropType = function(
   }
 };
 
-var DecomposedMatrixPropType = function(
+const DecomposedMatrixPropType = function(
   props : Object,
   propName : string,
   componentName : string
@@ -38,7 +38,7 @@ var DecomposedMatrixPropType = function(
   }
 };
 
-var TransformPropTypes = {
+const TransformPropTypes = {
   /**
    * `transform` accepts an array of transformation objects. Each object specifies
    * the property that will be transformed as the key, and the value to use in the
diff --git a/Libraries/StyleSheet/__tests__/flattenStyle-test.js b/Libraries/StyleSheet/__tests__/flattenStyle-test.js
index 76ce2822d900..0db505ff29b0 100644
--- a/Libraries/StyleSheet/__tests__/flattenStyle-test.js
+++ b/Libraries/StyleSheet/__tests__/flattenStyle-test.js
@@ -83,8 +83,8 @@ describe('flattenStyle', () => {
 
   it('should not allocate an object when there is a single class', () => {
     const fixture = getFixture();
-    var singleStyle = flattenStyle(fixture.elementA);
-    var singleStyleAgain = flattenStyle(fixture.elementA);
+    const singleStyle = flattenStyle(fixture.elementA);
+    const singleStyleAgain = flattenStyle(fixture.elementA);
 
     expect(singleStyle).toBe(singleStyleAgain);
     expect(singleStyle).toEqual({
@@ -95,8 +95,8 @@ describe('flattenStyle', () => {
 
   it('should merge single class and style properly', () => {
     const fixture = getFixture();
-    var style = {styleA: 'overrideA', styleC: 'overrideC'};
-    var arrayStyle = flattenStyle([fixture.elementA, style]);
+    const style = {styleA: 'overrideA', styleC: 'overrideC'};
+    const arrayStyle = flattenStyle([fixture.elementA, style]);
 
     expect(arrayStyle).toEqual({
       styleA: 'overrideA',
@@ -107,8 +107,8 @@ describe('flattenStyle', () => {
 
   it('should merge multiple classes', () => {
     const fixture = getFixture();
-    var AthenB = flattenStyle([fixture.elementA, fixture.elementB]);
-    var BthenA = flattenStyle([fixture.elementB, fixture.elementA]);
+    const AthenB = flattenStyle([fixture.elementA, fixture.elementB]);
+    const BthenA = flattenStyle([fixture.elementB, fixture.elementA]);
 
     expect(AthenB).toEqual({
       styleA: 'moduleA/elementA/styleA',
@@ -122,9 +122,9 @@ describe('flattenStyle', () => {
 
   it('should merge multiple classes with style', () => {
     const fixture = getFixture();
-    var style = {styleA: 'overrideA'};
-    var AthenB = flattenStyle([fixture.elementA, fixture.elementB, style]);
-    var BthenA = flattenStyle([fixture.elementB, fixture.elementA, style]);
+    const style = {styleA: 'overrideA'};
+    const AthenB = flattenStyle([fixture.elementA, fixture.elementB, style]);
+    const BthenA = flattenStyle([fixture.elementB, fixture.elementA, style]);
 
     expect(AthenB).toEqual({
       styleA: 'overrideA',
@@ -138,8 +138,8 @@ describe('flattenStyle', () => {
 
   it('should flatten recursively', () => {
     const fixture = getFixture();
-    var style = [{styleA: 'newA', styleB: 'newB'}, {styleA: 'newA2'}];
-    var AthenB = flattenStyle([fixture.elementA, fixture.elementB, style]);
+    const style = [{styleA: 'newA', styleB: 'newB'}, {styleA: 'newA2'}];
+    const AthenB = flattenStyle([fixture.elementA, fixture.elementB, style]);
 
     expect(AthenB).toEqual({
       styleA: 'newA2',
@@ -148,7 +148,7 @@ describe('flattenStyle', () => {
   });
 
   it('should ignore invalid class names', () => {
-    var invalid = flattenStyle(1234, null);
+    const invalid = flattenStyle(1234, null);
 
     expect(invalid).toEqual(undefined);
     // Invalid class name 1234 skipping ...
diff --git a/Libraries/StyleSheet/__tests__/normalizeColor-test.js b/Libraries/StyleSheet/__tests__/normalizeColor-test.js
index d7482a9c55bd..7edfdb4ac905 100644
--- a/Libraries/StyleSheet/__tests__/normalizeColor-test.js
+++ b/Libraries/StyleSheet/__tests__/normalizeColor-test.js
@@ -8,7 +8,7 @@
  */
 'use strict';
 
-var normalizeColor = require('normalizeColor');
+const normalizeColor = require('normalizeColor');
 
 describe('normalizeColor', function() {
   it('should accept only spec compliant colors', function() {
diff --git a/Libraries/StyleSheet/__tests__/processColor-test.js b/Libraries/StyleSheet/__tests__/processColor-test.js
index 2af0baa108a7..a353a52a6be9 100644
--- a/Libraries/StyleSheet/__tests__/processColor-test.js
+++ b/Libraries/StyleSheet/__tests__/processColor-test.js
@@ -20,26 +20,26 @@ describe('processColor', () => {
   describe('predefined color names', () => {
 
     it('should convert red', () => {
-      var colorFromString = processColor('red');
-      var expectedInt = 0xFFFF0000;
+      const colorFromString = processColor('red');
+      const expectedInt = 0xFFFF0000;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
     it('should convert white', () => {
-      var colorFromString = processColor('white');
-      var expectedInt = 0xFFFFFFFF;
+      const colorFromString = processColor('white');
+      const expectedInt = 0xFFFFFFFF;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
     it('should convert black', () => {
-      var colorFromString = processColor('black');
-      var expectedInt = 0xFF000000;
+      const colorFromString = processColor('black');
+      const expectedInt = 0xFF000000;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
     it('should convert transparent', () => {
-      var colorFromString = processColor('transparent');
-      var expectedInt = 0x00000000;
+      const colorFromString = processColor('transparent');
+      const expectedInt = 0x00000000;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
   });
@@ -47,8 +47,8 @@ describe('processColor', () => {
   describe('RGB strings', () => {
 
     it('should convert rgb(x, y, z)', () => {
-      var colorFromString = processColor('rgb(10, 20, 30)');
-      var expectedInt = 0xFF0A141E;
+      const colorFromString = processColor('rgb(10, 20, 30)');
+      const expectedInt = 0xFF0A141E;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
@@ -57,8 +57,8 @@ describe('processColor', () => {
   describe('RGBA strings', () => {
 
     it('should convert rgba(x, y, z, a)', () => {
-      var colorFromString = processColor('rgba(10, 20, 30, 0.4)');
-      var expectedInt = 0x660A141E;
+      const colorFromString = processColor('rgba(10, 20, 30, 0.4)');
+      const expectedInt = 0x660A141E;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
@@ -67,8 +67,8 @@ describe('processColor', () => {
   describe('HSL strings', () => {
 
     it('should convert hsl(x, y%, z%)', () => {
-      var colorFromString = processColor('hsl(318, 69%, 55%)');
-      var expectedInt = 0xFFDB3DAC;
+      const colorFromString = processColor('hsl(318, 69%, 55%)');
+      const expectedInt = 0xFFDB3DAC;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
@@ -77,8 +77,8 @@ describe('processColor', () => {
   describe('HSLA strings', () => {
 
     it('should convert hsla(x, y%, z%, a)', () => {
-      var colorFromString = processColor('hsla(318, 69%, 55%, 0.25)');
-      var expectedInt = 0x40DB3DAC;
+      const colorFromString = processColor('hsla(318, 69%, 55%, 0.25)');
+      const expectedInt = 0x40DB3DAC;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
@@ -87,8 +87,8 @@ describe('processColor', () => {
   describe('hex strings', () => {
 
     it('should convert #xxxxxx', () => {
-      var colorFromString = processColor('#1e83c9');
-      var expectedInt = 0xFF1E83C9;
+      const colorFromString = processColor('#1e83c9');
+      const expectedInt = 0xFF1E83C9;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
diff --git a/Libraries/StyleSheet/__tests__/setNormalizedColorAlpha-test.js b/Libraries/StyleSheet/__tests__/setNormalizedColorAlpha-test.js
index 13e47aff5657..5fd4a9f735e2 100644
--- a/Libraries/StyleSheet/__tests__/setNormalizedColorAlpha-test.js
+++ b/Libraries/StyleSheet/__tests__/setNormalizedColorAlpha-test.js
@@ -8,8 +8,8 @@
  */
 'use strict';
 
-var setNormalizedColorAlpha = require('setNormalizedColorAlpha');
-var normalizeColor = require('normalizeColor');
+const setNormalizedColorAlpha = require('setNormalizedColorAlpha');
+const normalizeColor = require('normalizeColor');
 
 describe('setNormalizedColorAlpha', function() {
   it('should adjust the alpha of the color passed in', function() {
@@ -27,7 +27,7 @@ describe('setNormalizedColorAlpha', function() {
   });
 
   it('should return the original color when alpha is unchanged', function() {
-    var originalColor = normalizeColor('blue');
+    const originalColor = normalizeColor('blue');
     expect(setNormalizedColorAlpha(originalColor, 1)).toBe(originalColor);
   });
 });
diff --git a/Libraries/StyleSheet/flattenStyle.js b/Libraries/StyleSheet/flattenStyle.js
index f62e35ea70f4..cb5f6ebc96e7 100644
--- a/Libraries/StyleSheet/flattenStyle.js
+++ b/Libraries/StyleSheet/flattenStyle.js
@@ -25,11 +25,11 @@ function flattenStyle(
     return style;
   }
 
-  var result = {};
-  for (var i = 0, styleLength = style.length; i < styleLength; ++i) {
-    var computedStyle = flattenStyle(style[i]);
+  const result = {};
+  for (let i = 0, styleLength = style.length; i < styleLength; ++i) {
+    const computedStyle = flattenStyle(style[i]);
     if (computedStyle) {
-      for (var key in computedStyle) {
+      for (const key in computedStyle) {
         result[key] = computedStyle[key];
       }
     }
diff --git a/Libraries/StyleSheet/processTransform.js b/Libraries/StyleSheet/processTransform.js
index 3c8d30ea0e0e..fb4ed3445e8c 100644
--- a/Libraries/StyleSheet/processTransform.js
+++ b/Libraries/StyleSheet/processTransform.js
@@ -8,11 +8,11 @@
  */
 'use strict';
 
-var MatrixMath = require('MatrixMath');
-var Platform = require('Platform');
+const MatrixMath = require('MatrixMath');
+const Platform = require('Platform');
 
-var invariant = require('fbjs/lib/invariant');
-var stringifySafe = require('stringifySafe');
+const invariant = require('fbjs/lib/invariant');
+const stringifySafe = require('stringifySafe');
 
 /**
  * Generate a transform matrix based on the provided transforms, and use that
@@ -34,11 +34,11 @@ function processTransform(transform: Array<Object>): Array<Object> | Array<numbe
     return transform;
   }
 
-  var result = MatrixMath.createIdentityMatrix();
+  const result = MatrixMath.createIdentityMatrix();
 
   transform.forEach(transformation => {
-    var key = Object.keys(transformation)[0];
-    var value = transformation[key];
+    const key = Object.keys(transformation)[0];
+    const value = transformation[key];
 
     switch (key) {
       case 'matrix':
@@ -97,8 +97,8 @@ function _multiplyTransform(
   matrixMathFunction: Function,
   args: Array<number>
 ): void {
-  var matrixToApply = MatrixMath.createIdentityMatrix();
-  var argsWithIdentity = [matrixToApply].concat(args);
+  const matrixToApply = MatrixMath.createIdentityMatrix();
+  const argsWithIdentity = [matrixToApply].concat(args);
   matrixMathFunction.apply(this, argsWithIdentity);
   MatrixMath.multiplyInto(result, result, matrixToApply);
 }
@@ -108,20 +108,20 @@ function _multiplyTransform(
  * Note that validation on the string is done in `_validateTransform()`.
  */
 function _convertToRadians(value: string): number {
-  var floatValue = parseFloat(value);
+  const floatValue = parseFloat(value);
   return value.indexOf('rad') > -1 ? floatValue : floatValue * Math.PI / 180;
 }
 
 function _validateTransforms(transform: Array<Object>): void {
   transform.forEach(transformation => {
-    var keys = Object.keys(transformation);
+    const keys = Object.keys(transformation);
     invariant(
       keys.length === 1,
       'You must specify exactly one property per transform object. Passed properties: %s',
       stringifySafe(transformation),
     );
-    var key = keys[0];
-    var value = transformation[key];
+    const key = keys[0];
+    const value = transformation[key];
     _validateTransform(key, value, transformation);
   });
 }
@@ -134,7 +134,7 @@ function _validateTransform(key, value, transformation) {
     'replace <View /> by <Animated.View />.'
   );
 
-  var multivalueTransforms = [
+  const multivalueTransforms = [
     'matrix',
     'translate',
   ];
diff --git a/Libraries/Text/TextUpdateTest.js b/Libraries/Text/TextUpdateTest.js
index 18a3ac5084b7..b3dc0949aeed 100644
--- a/Libraries/Text/TextUpdateTest.js
+++ b/Libraries/Text/TextUpdateTest.js
@@ -8,22 +8,22 @@
  */
 'use strict';
 
-var React = require('react');
-var createReactClass = require('create-react-class');
-var ReactNative = require('react-native');
+const React = require('react');
+const createReactClass = require('create-react-class');
+const ReactNative = require('react-native');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-var TimerMixin = require('react-timer-mixin');
-var {
+const TimerMixin = require('react-timer-mixin');
+const {
   NativeModules,
   StyleSheet,
   Text,
 } = ReactNative;
 
-var TestManager = NativeModules.TestManager || NativeModules.SnapshotTestManager;
+const TestManager = NativeModules.TestManager || NativeModules.SnapshotTestManager;
 
-var TextUpdateTest = createReactClass({
+const TextUpdateTest = createReactClass({
   displayName: 'TextUpdateTest',
   mixins: [TimerMixin],
   getInitialState: function() {
@@ -48,7 +48,7 @@ var TextUpdateTest = createReactClass({
   },
 });
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   container: {
     margin: 10,
     marginTop: 100,
diff --git a/Libraries/Utilities/BackAndroid.js b/Libraries/Utilities/BackAndroid.js
index 51a68a7671f8..57e2d8d77a3a 100644
--- a/Libraries/Utilities/BackAndroid.js
+++ b/Libraries/Utilities/BackAndroid.js
@@ -11,14 +11,14 @@
 
 'use strict';
 
-var BackHandler = require('BackHandler');
+const BackHandler = require('BackHandler');
 
-var warning = require('fbjs/lib/warning');
+const warning = require('fbjs/lib/warning');
 
 /**
  * Deprecated.  Use BackHandler instead.
  */
-var BackAndroid = {
+const BackAndroid = {
 
   exitApp: function() {
     warning(false, 'BackAndroid is deprecated.  Please use BackHandler instead.');
diff --git a/Libraries/Utilities/BackHandler.android.js b/Libraries/Utilities/BackHandler.android.js
index b2e3a74bc448..0db35d872098 100644
--- a/Libraries/Utilities/BackHandler.android.js
+++ b/Libraries/Utilities/BackHandler.android.js
@@ -8,22 +8,22 @@
 
 'use strict';
 
-var DeviceEventManager = require('NativeModules').DeviceEventManager;
-var RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
+const DeviceEventManager = require('NativeModules').DeviceEventManager;
+const RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
 
-var DEVICE_BACK_EVENT = 'hardwareBackPress';
+const DEVICE_BACK_EVENT = 'hardwareBackPress';
 
 type BackPressEventName = $Enum<{
   backPress: string,
 }>;
 
-var _backPressSubscriptions = new Set();
+const _backPressSubscriptions = new Set();
 
 RCTDeviceEventEmitter.addListener(DEVICE_BACK_EVENT, function() {
-  var invokeDefault = true;
-  var subscriptions = Array.from(_backPressSubscriptions.values()).reverse();
+  let invokeDefault = true;
+  const subscriptions = Array.from(_backPressSubscriptions.values()).reverse();
 
-  for (var i = 0; i < subscriptions.length; ++i) {
+  for (let i = 0; i < subscriptions.length; ++i) {
     if (subscriptions[i]()) {
       invokeDefault = false;
       break;
@@ -65,7 +65,7 @@ RCTDeviceEventEmitter.addListener(DEVICE_BACK_EVENT, function() {
  * });
  * ```
  */
-var BackHandler = {
+const BackHandler = {
 
   exitApp: function() {
     DeviceEventManager.invokeDefaultBackPressHandler();
diff --git a/Libraries/Utilities/BackHandler.ios.js b/Libraries/Utilities/BackHandler.ios.js
index 0c0d7d437870..4112d6197f07 100644
--- a/Libraries/Utilities/BackHandler.ios.js
+++ b/Libraries/Utilities/BackHandler.ios.js
@@ -54,14 +54,14 @@ let BackHandler;
 
 if (Platform.isTVOS) {
   const _tvEventHandler = new TVEventHandler();
-  var _backPressSubscriptions = new Set();
+  const _backPressSubscriptions = new Set();
 
   _tvEventHandler.enable(this, function(cmp, evt) {
     if (evt && evt.eventType === 'menu') {
-      var invokeDefault = true;
-      var subscriptions = Array.from(_backPressSubscriptions.values()).reverse();
+      let invokeDefault = true;
+      const subscriptions = Array.from(_backPressSubscriptions.values()).reverse();
 
-      for (var i = 0; i < subscriptions.length; ++i) {
+      for (let i = 0; i < subscriptions.length; ++i) {
         if (subscriptions[i]()) {
           invokeDefault = false;
           break;
diff --git a/Libraries/Utilities/Dimensions.js b/Libraries/Utilities/Dimensions.js
index f27ecc0976b8..76bde024355c 100644
--- a/Libraries/Utilities/Dimensions.js
+++ b/Libraries/Utilities/Dimensions.js
@@ -8,15 +8,15 @@
  */
 'use strict';
 
-var EventEmitter = require('EventEmitter');
-var Platform = require('Platform');
-var RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
+const EventEmitter = require('EventEmitter');
+const Platform = require('Platform');
+const RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
 
-var invariant = require('fbjs/lib/invariant');
+const invariant = require('fbjs/lib/invariant');
 
-var eventEmitter = new EventEmitter();
-var dimensionsInitialized = false;
-var dimensions = {};
+const eventEmitter = new EventEmitter();
+let dimensionsInitialized = false;
+const dimensions = {};
 class Dimensions {
   /**
    * This should only be called from native code by sending the
diff --git a/Libraries/Utilities/HMRLoadingView.android.js b/Libraries/Utilities/HMRLoadingView.android.js
index f4c0c5c73122..61bc75c7e517 100644
--- a/Libraries/Utilities/HMRLoadingView.android.js
+++ b/Libraries/Utilities/HMRLoadingView.android.js
@@ -9,7 +9,7 @@
 
 'use strict';
 
-var ToastAndroid = require('ToastAndroid');
+const ToastAndroid = require('ToastAndroid');
 
 const TOAST_SHORT_DELAY = 2000;
 
diff --git a/Libraries/Utilities/HeapCapture.js b/Libraries/Utilities/HeapCapture.js
index 519a2e94370b..91df130ed934 100644
--- a/Libraries/Utilities/HeapCapture.js
+++ b/Libraries/Utilities/HeapCapture.js
@@ -8,9 +8,9 @@
  */
 'use strict';
 
-var HeapCapture = {
+const HeapCapture = {
   captureHeap: function (path: string) {
-    var error = null;
+    let error = null;
     try {
       global.nativeCaptureHeap(path);
       console.log('HeapCapture.captureHeap succeeded: ' + path);
diff --git a/Libraries/Utilities/MatrixMath.js b/Libraries/Utilities/MatrixMath.js
index be329c2e645d..40f934cc88ac 100755
--- a/Libraries/Utilities/MatrixMath.js
+++ b/Libraries/Utilities/MatrixMath.js
@@ -9,13 +9,13 @@
 /* eslint-disable space-infix-ops */
 'use strict';
 
-var invariant = require('fbjs/lib/invariant');
+const invariant = require('fbjs/lib/invariant');
 
 /**
  * Memory conservative (mutative) matrix math utilities. Uses "command"
  * matrices, which are reusable.
  */
-var MatrixMath = {
+const MatrixMath = {
   createIdentityMatrix: function() {
     return [
       1,0,0,0,
@@ -35,13 +35,13 @@ var MatrixMath = {
   },
 
   createOrthographic: function(left, right, bottom, top, near, far) {
-    var a = 2 / (right - left);
-    var b = 2 / (top - bottom);
-    var c = -2 / (far - near);
+    const a = 2 / (right - left);
+    const b = 2 / (top - bottom);
+    const c = -2 / (far - near);
 
-    var tx = -(right + left) / (right - left);
-    var ty = -(top + bottom) / (top - bottom);
-    var tz = -(far + near) / (far - near);
+    const tx = -(right + left) / (right - left);
+    const ty = -(top + bottom) / (top - bottom);
+    const tz = -(far + near) / (far - near);
 
     return [
         a,  0,  0,  0,
@@ -52,15 +52,15 @@ var MatrixMath = {
   },
 
   createFrustum: function(left, right, bottom, top, near, far) {
-    var r_width  = 1 / (right - left);
-    var r_height = 1 / (top - bottom);
-    var r_depth  = 1 / (near - far);
-    var x = 2 * (near * r_width);
-    var y = 2 * (near * r_height);
-    var A = (right + left) * r_width;
-    var B = (top + bottom) * r_height;
-    var C = (far + near) * r_depth;
-    var D = 2 * (far * near * r_depth);
+    const r_width  = 1 / (right - left);
+    const r_height = 1 / (top - bottom);
+    const r_depth  = 1 / (near - far);
+    const x = 2 * (near * r_width);
+    const y = 2 * (near * r_height);
+    const A = (right + left) * r_width;
+    const B = (top + bottom) * r_height;
+    const C = (far + near) * r_depth;
+    const D = 2 * (far * near * r_depth);
     return [
       x, 0, 0, 0,
       0, y, 0, 0,
@@ -76,10 +76,10 @@ var MatrixMath = {
    * @param fovInRadians - field of view in randians
    */
   createPerspective: function(fovInRadians, aspect, near, far) {
-    var h = 1 / Math.tan(fovInRadians / 2);
-    var r_depth  = 1 / (near - far);
-    var C = (far + near) * r_depth;
-    var D = 2 * (far * near * r_depth);
+    const h = 1 / Math.tan(fovInRadians / 2);
+    const r_depth  = 1 / (near - far);
+    const C = (far + near) * r_depth;
+    const D = 2 * (far * near * r_depth);
     return [
       h/aspect, 0, 0, 0,
       0, h, 0, 0,
@@ -89,7 +89,7 @@ var MatrixMath = {
   },
 
   createTranslate2d: function(x, y) {
-    var mat = MatrixMath.createIdentityMatrix();
+    const mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseTranslate2dCommand(mat, x, y);
     return mat;
   },
@@ -106,7 +106,7 @@ var MatrixMath = {
   },
 
   createScale: function(factor) {
-    var mat = MatrixMath.createIdentityMatrix();
+    const mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseScaleCommand(mat, factor);
     return mat;
   },
@@ -161,7 +161,7 @@ var MatrixMath = {
   },
 
   createRotateZ: function(radians) {
-    var mat = MatrixMath.createIdentityMatrix();
+    const mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseRotateZCommand(mat, radians);
     return mat;
   },
@@ -175,12 +175,9 @@ var MatrixMath = {
   },
 
   multiplyInto: function(out, a, b) {
-    var a00 = a[0], a01 = a[1], a02 = a[2], a03 = a[3],
-      a10 = a[4], a11 = a[5], a12 = a[6], a13 = a[7],
-      a20 = a[8], a21 = a[9], a22 = a[10], a23 = a[11],
-      a30 = a[12], a31 = a[13], a32 = a[14], a33 = a[15];
+    const a00 = a[0], a01 = a[1], a02 = a[2], a03 = a[3], a10 = a[4], a11 = a[5], a12 = a[6], a13 = a[7], a20 = a[8], a21 = a[9], a22 = a[10], a23 = a[11], a30 = a[12], a31 = a[13], a32 = a[14], a33 = a[15];
 
-    var b0  = b[0], b1 = b[1], b2 = b[2], b3 = b[3];
+    let b0  = b[0], b1 = b[1], b2 = b[2], b3 = b[3];
     out[0] = b0*a00 + b1*a10 + b2*a20 + b3*a30;
     out[1] = b0*a01 + b1*a11 + b2*a21 + b3*a31;
     out[2] = b0*a02 + b1*a12 + b2*a22 + b3*a32;
@@ -206,7 +203,7 @@ var MatrixMath = {
   },
 
   determinant(matrix: Array<number>): number {
-    var [
+    const [
       m00, m01, m02, m03,
       m10, m11, m12, m13,
       m20, m21, m22, m23,
@@ -236,11 +233,11 @@ var MatrixMath = {
    * http://www.euclideanspace.com/maths/algebra/matrix/functions/inverse/fourD/index.htm
    */
   inverse(matrix: Array<number>): Array<number> {
-    var det = MatrixMath.determinant(matrix);
+    const det = MatrixMath.determinant(matrix);
     if (!det) {
       return matrix;
     }
-    var [
+    const [
       m00, m01, m02, m03,
       m10, m11, m12, m13,
       m20, m21, m22, m23,
@@ -285,7 +282,7 @@ var MatrixMath = {
     v: Array<number>,
     m: Array<number>
   ): Array<number> {
-    var [vx, vy, vz, vw] = v;
+    const [vx, vy, vz, vw] = v;
     return [
       vx * m[0] + vy * m[4] + vz * m[8]  + vw * m[12],
       vx * m[1] + vy * m[5] + vz * m[9]  + vw * m[13],
@@ -308,7 +305,7 @@ var MatrixMath = {
      vector: Array<number>,
      v3Length: number
     ): Array<number> {
-    var im = 1 / (v3Length || MatrixMath.v3Length(vector));
+    const im = 1 / (v3Length || MatrixMath.v3Length(vector));
     return [
       vector[0] * im,
       vector[1] * im,
@@ -372,14 +369,14 @@ var MatrixMath = {
    * roll  === bank               === x-axis
    */
   quaternionToDegreesXYZ(q: Array<number>, matrix, row): Array<number> {
-    var [qx, qy, qz, qw] = q;
-    var qw2 = qw * qw;
-    var qx2 = qx * qx;
-    var qy2 = qy * qy;
-    var qz2 = qz * qz;
-    var test = qx * qy + qz * qw;
-    var unit = qw2 + qx2 + qy2 + qz2;
-    var conv = 180 / Math.PI;
+    const [qx, qy, qz, qw] = q;
+    const qw2 = qw * qw;
+    const qx2 = qx * qx;
+    const qy2 = qy * qy;
+    const qz2 = qz * qz;
+    const test = qx * qy + qz * qw;
+    const unit = qw2 + qx2 + qy2 + qz2;
+    const conv = 180 / Math.PI;
 
     if (test > 0.49999 * unit) {
       return [0, 2 * Math.atan2(qx, qw) * conv, 90];
@@ -406,7 +403,7 @@ var MatrixMath = {
    * https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/round
    */
   roundTo3Places(n: number): number {
-    var arr = n.toString().split('e');
+    const arr = n.toString().split('e');
     return Math.round(arr[0] + 'e' + (arr[1] ? (+arr[1] - 3) : 3)) * 0.001;
   },
 
@@ -431,22 +428,22 @@ var MatrixMath = {
 
     // output values
     var perspective = [];
-    var quaternion = [];
-    var scale = [];
-    var skew = [];
-    var translation = [];
+    const quaternion = [];
+    const scale = [];
+    const skew = [];
+    const translation = [];
 
     // create normalized, 2d array matrix
     // and normalized 1d array perspectiveMatrix with redefined 4th column
     if (!transformMatrix[15]) {
       return;
     }
-    var matrix = [];
-    var perspectiveMatrix = [];
+    const matrix = [];
+    const perspectiveMatrix = [];
     for (var i = 0; i < 4; i++) {
       matrix.push([]);
-      for (var j = 0; j < 4; j++) {
-        var value = transformMatrix[(i * 4) + j] / transformMatrix[15];
+      for (let j = 0; j < 4; j++) {
+        const value = transformMatrix[(i * 4) + j] / transformMatrix[15];
         matrix[i].push(value);
         perspectiveMatrix.push(j === 3 ? 0 : value);
       }
@@ -462,7 +459,7 @@ var MatrixMath = {
     if (matrix[0][3] !== 0 || matrix[1][3] !== 0 || matrix[2][3] !== 0) {
       // rightHandSide is the right hand side of the equation.
       // rightHandSide is a vector, or point in 3d space relative to the origin.
-      var rightHandSide = [
+      const rightHandSide = [
         matrix[0][3],
         matrix[1][3],
         matrix[2][3],
@@ -471,10 +468,10 @@ var MatrixMath = {
 
       // Solve the equation by inverting perspectiveMatrix and multiplying
       // rightHandSide by the inverse.
-      var inversePerspectiveMatrix = MatrixMath.inverse(
+      const inversePerspectiveMatrix = MatrixMath.inverse(
         perspectiveMatrix
       );
-      var transposedInversePerspectiveMatrix = MatrixMath.transpose(
+      const transposedInversePerspectiveMatrix = MatrixMath.transpose(
         inversePerspectiveMatrix
       );
       var perspective = MatrixMath.multiplyVectorByMatrix(
@@ -494,7 +491,7 @@ var MatrixMath = {
 
     // Now get scale and shear.
     // 'row' is a 3 element array of 3 component vectors
-    var row = [];
+    const row = [];
     for (i = 0; i < 3; i++) {
       row[i] = [
         matrix[i][0],
@@ -535,7 +532,7 @@ var MatrixMath = {
     // At this point, the matrix (in rows) is orthonormal.
     // Check for a coordinate system flip.  If the determinant
     // is -1, then negate the matrix and the scaling factors.
-    var pdum3 = MatrixMath.v3Cross(row[1], row[2]);
+    const pdum3 = MatrixMath.v3Cross(row[1], row[2]);
     if (MatrixMath.v3Dot(row[0], pdum3) < 0) {
       for (i = 0; i < 3; i++) {
         scale[i] *= -1;
@@ -566,7 +563,7 @@ var MatrixMath = {
     }
 
     // correct for occasional, weird Euler synonyms for 2d rotation
-    var rotationDegrees;
+    let rotationDegrees;
     if (
       quaternion[0] < 0.001 && quaternion[0] >= 0 &&
       quaternion[1] < 0.001 && quaternion[1] >= 0
diff --git a/Libraries/Utilities/PixelRatio.js b/Libraries/Utilities/PixelRatio.js
index 5f52bdc0f5b8..58b2b02241fe 100644
--- a/Libraries/Utilities/PixelRatio.js
+++ b/Libraries/Utilities/PixelRatio.js
@@ -8,7 +8,7 @@
  */
 'use strict';
 
-var Dimensions = require('Dimensions');
+const Dimensions = require('Dimensions');
 
 /**
  * PixelRatio class gives access to the device pixel density.
@@ -108,7 +108,7 @@ class PixelRatio {
    * exactly (8.33 * 3) = 25 pixels.
    */
   static roundToNearestPixel(layoutSize: number): number {
-    var ratio = PixelRatio.get();
+    const ratio = PixelRatio.get();
     return Math.round(layoutSize * ratio) / ratio;
   }
 
diff --git a/Libraries/Utilities/__tests__/MatrixMath-test.js b/Libraries/Utilities/__tests__/MatrixMath-test.js
index 2eb14cb5ba3c..f8491cec0fd7 100644
--- a/Libraries/Utilities/__tests__/MatrixMath-test.js
+++ b/Libraries/Utilities/__tests__/MatrixMath-test.js
@@ -8,7 +8,7 @@
  */
 'use strict';
 
-var MatrixMath = require('MatrixMath');
+const MatrixMath = require('MatrixMath');
 
 function degreesToRadians(degrees) {
   return degrees * Math.PI / 180;
@@ -26,7 +26,7 @@ describe('MatrixMath', () => {
     ]).rotationDegrees).toEqual([0, 0, 0]);
 
     [30, 45, 60, 75, 90, 100, 115, 120, 133, 167].forEach(angle => {
-      var mat = MatrixMath.createRotateZ(degreesToRadians(angle));
+      let mat = MatrixMath.createRotateZ(degreesToRadians(angle));
       expect(convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees))
         .toEqual([0, 0, angle]);
 
@@ -80,7 +80,7 @@ describe('MatrixMath', () => {
   });
 
   it('decomposes a 4x4 matrix to produce accurate Y-axis angles', () => {
-    var mat;
+    let mat;
     [30, 45, 60, 75, 90, 100, 110, 120, 133, 167].forEach(angle => {
       mat = MatrixMath.createIdentityMatrix();
       MatrixMath.reuseRotateYCommand(mat, degreesToRadians(angle));
@@ -112,7 +112,7 @@ describe('MatrixMath', () => {
   });
 
   it('decomposes a 4x4 matrix to produce accurate X-axis angles', () => {
-    var mat;
+    let mat;
     [30, 45, 60, 75, 90, 100, 110, 120, 133, 167].forEach(angle => {
       mat = MatrixMath.createIdentityMatrix();
       MatrixMath.reuseRotateXCommand(mat, degreesToRadians(angle));
diff --git a/Libraries/Utilities/__tests__/Platform-test.js b/Libraries/Utilities/__tests__/Platform-test.js
index 1fdfaaa1a75c..72dafb4329c7 100644
--- a/Libraries/Utilities/__tests__/Platform-test.js
+++ b/Libraries/Utilities/__tests__/Platform-test.js
@@ -8,8 +8,8 @@
  */
 'use strict';
 
-var PlatformIOS = require('../Platform.ios');
-var PlatformAndroid = require('../Platform.android');
+const PlatformIOS = require('../Platform.ios');
+const PlatformAndroid = require('../Platform.android');
 
 describe('Platform', () => {
 
diff --git a/Libraries/Utilities/__tests__/buildStyleInterpolator-test.js b/Libraries/Utilities/__tests__/buildStyleInterpolator-test.js
index ccb5f7edfb31..78440b640010 100644
--- a/Libraries/Utilities/__tests__/buildStyleInterpolator-test.js
+++ b/Libraries/Utilities/__tests__/buildStyleInterpolator-test.js
@@ -8,11 +8,11 @@
  */
 'use strict';
 
-var buildStyleInterpolator = require('buildStyleInterpolator');
+const buildStyleInterpolator = require('buildStyleInterpolator');
 
-var validateEmpty = function(interpolator, value, validator) {
-  var emptyObject = {};
-  var changed = interpolator(emptyObject, value);
+const validateEmpty = function(interpolator, value, validator) {
+  const emptyObject = {};
+  let changed = interpolator(emptyObject, value);
   validator(emptyObject);
   expect(changed).toBe(true);
   changed = interpolator(emptyObject, value);
@@ -20,7 +20,7 @@ var validateEmpty = function(interpolator, value, validator) {
 };
 describe('buildStyleInterpolator', function() {
   it('should linearly interpolate without extrapolating', function() {
-    var testAnim = {
+    const testAnim = {
       opacity: {
         from: 100,
         to: 200,
@@ -42,7 +42,7 @@ describe('buildStyleInterpolator', function() {
         value: 23.5,
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
+    const interpolator = buildStyleInterpolator(testAnim);
     validateEmpty(interpolator, 0, function(res) {
       expect(res).toEqual({
         opacity: 100,
@@ -80,7 +80,7 @@ describe('buildStyleInterpolator', function() {
     });
   });
   it('should linearly interpolate with extrapolating', function() {
-    var testAnim = {
+    const testAnim = {
       opacity: {
         from: 100,
         to: 200,
@@ -104,7 +104,7 @@ describe('buildStyleInterpolator', function() {
         value: 23.5,
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
+    const interpolator = buildStyleInterpolator(testAnim);
     validateEmpty(interpolator, 0, function(res) {
       expect(res).toEqual({
         opacity: 100,
@@ -142,7 +142,7 @@ describe('buildStyleInterpolator', function() {
     });
   });
   it('should round accordingly', function() {
-    var testAnim = {
+    const testAnim = {
       opacity: {
         from: 0,
         to: 1,
@@ -153,7 +153,7 @@ describe('buildStyleInterpolator', function() {
         extrapolate: true,
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
+    const interpolator = buildStyleInterpolator(testAnim);
     validateEmpty(interpolator, 0, function(res) {
       expect(res).toEqual({
         opacity: 0,
@@ -186,7 +186,7 @@ describe('buildStyleInterpolator', function() {
     });
   });
   it('should detect chnages correctly', function() {
-    var testAnim = {
+    const testAnim = {
       opacity: {
         from: 0,
         to: 1,
@@ -197,9 +197,9 @@ describe('buildStyleInterpolator', function() {
         extrapolate: false,
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
-    var obj = {};
-    var res = interpolator(obj, 0);
+    const interpolator = buildStyleInterpolator(testAnim);
+    const obj = {};
+    let res = interpolator(obj, 0);
     expect(obj).toEqual({
       opacity: 0,
     });
@@ -227,14 +227,14 @@ describe('buildStyleInterpolator', function() {
     expect(res).toBe(false);
   });
   it('should handle identity', function() {
-    var testAnim = {
+    const testAnim = {
       opacity: {
         type: 'identity',
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
-    var obj = {};
-    var res = interpolator(obj, 0.5);
+    const interpolator = buildStyleInterpolator(testAnim);
+    const obj = {};
+    let res = interpolator(obj, 0.5);
     expect(obj).toEqual({
       opacity: 0.5,
     });
@@ -248,7 +248,7 @@ describe('buildStyleInterpolator', function() {
     expect(res).toBe(false);
   });
   it('should translate', function() {
-    var testAnim = {
+    const testAnim = {
       transformTranslate: {
         from: {x: 1, y: 10, z: 100},
         to: {x: 5, y: 50, z: 500},
@@ -257,9 +257,9 @@ describe('buildStyleInterpolator', function() {
         type: 'linear',
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
-    var obj = {};
-    var res = interpolator(obj, 1);
+    const interpolator = buildStyleInterpolator(testAnim);
+    const obj = {};
+    const res = interpolator(obj, 1);
     expect(obj).toEqual({
       transform: [{matrix: [1, 0, 0, 0,
                             0, 1, 0, 0,
@@ -269,7 +269,7 @@ describe('buildStyleInterpolator', function() {
     expect(res).toBe(true);
   });
   it('should scale', function() {
-    var testAnim = {
+    const testAnim = {
       transformScale: {
         from: {x: 1, y: 10, z: 100},
         to: {x: 5, y: 50, z: 500},
@@ -278,9 +278,9 @@ describe('buildStyleInterpolator', function() {
         type: 'linear',
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
-    var obj = {};
-    var res = interpolator(obj, 1);
+    const interpolator = buildStyleInterpolator(testAnim);
+    const obj = {};
+    const res = interpolator(obj, 1);
     expect(obj).toEqual({
       transform: [{matrix: [2, 0, 0, 0,
                             0, 20, 0, 0,
@@ -290,7 +290,7 @@ describe('buildStyleInterpolator', function() {
     expect(res).toBe(true);
   });
   it('should combine scale and translate', function() {
-    var testAnim = {
+    const testAnim = {
       transformScale: {
         from: {x: 1, y: 10, z: 100},
         to: {x: 5, y: 50, z: 500},
@@ -306,9 +306,9 @@ describe('buildStyleInterpolator', function() {
         type: 'linear',
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
-    var obj = {};
-    var res = interpolator(obj, 1);
+    const interpolator = buildStyleInterpolator(testAnim);
+    const obj = {};
+    const res = interpolator(obj, 1);
     expect(obj).toEqual({
       transform: [{matrix: [2, 0, 0, 0,
                             0, 20, 0, 0,
@@ -318,7 +318,7 @@ describe('buildStyleInterpolator', function() {
     expect(res).toBe(true);
   });
   it('should step', function() {
-    var testAnim = {
+    const testAnim = {
       opacity: {
         threshold: 13,
         from: 10,
@@ -326,9 +326,9 @@ describe('buildStyleInterpolator', function() {
         type: 'step',
       },
     };
-    var interpolator = buildStyleInterpolator(testAnim);
-    var obj = {};
-    var res = interpolator(obj, 0);
+    const interpolator = buildStyleInterpolator(testAnim);
+    const obj = {};
+    let res = interpolator(obj, 0);
     expect(obj).toEqual({
       opacity: 10,
     });
diff --git a/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js b/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
index cc307eedac0e..f00b974d95e9 100644
--- a/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
+++ b/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
@@ -6,7 +6,7 @@
  *
  * @emails oncall+react_native
  */
-var deepFreezeAndThrowOnMutationInDev = require('deepFreezeAndThrowOnMutationInDev');
+const deepFreezeAndThrowOnMutationInDev = require('deepFreezeAndThrowOnMutationInDev');
 
 describe('deepFreezeAndThrowOnMutationInDev', function() {
 
@@ -28,7 +28,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
   it('should throw on mutation in dev with strict', () => {
     'use strict';
     __DEV__ = true;
-    var o = {key: 'oldValue'};
+    const o = {key: 'oldValue'};
     deepFreezeAndThrowOnMutationInDev(o);
     expect(() => { o.key = 'newValue'; }).toThrowError(
       'You attempted to set the key `key` with the value `"newValue"` ' +
@@ -39,7 +39,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
 
   it('should throw on mutation in dev without strict', () => {
     __DEV__ = true;
-    var o = {key: 'oldValue'};
+    const o = {key: 'oldValue'};
     deepFreezeAndThrowOnMutationInDev(o);
     expect(() => { o.key = 'newValue'; }).toThrowError(
       'You attempted to set the key `key` with the value `"newValue"` ' +
@@ -51,7 +51,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
   it('should throw on nested mutation in dev with strict', () => {
     'use strict';
     __DEV__ = true;
-    var o = {key1: {key2: {key3: 'oldValue'}}};
+    const o = {key1: {key2: {key3: 'oldValue'}}};
     deepFreezeAndThrowOnMutationInDev(o);
     expect(() => { o.key1.key2.key3 = 'newValue'; }).toThrowError(
       'You attempted to set the key `key3` with the value `"newValue"` ' +
@@ -62,7 +62,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
 
   it('should throw on nested mutation in dev without strict', () => {
     __DEV__ = true;
-    var o = {key1: {key2: {key3: 'oldValue'}}};
+    const o = {key1: {key2: {key3: 'oldValue'}}};
     deepFreezeAndThrowOnMutationInDev(o);
     expect(() => { o.key1.key2.key3 = 'newValue'; }).toThrowError(
       'You attempted to set the key `key3` with the value `"newValue"` ' +
@@ -74,7 +74,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
   it('should throw on insertion in dev with strict', () => {
     'use strict';
     __DEV__ = true;
-    var o = {oldKey: 'value'};
+    const o = {oldKey: 'value'};
     deepFreezeAndThrowOnMutationInDev(o);
     expect(() => { o.newKey = 'value'; })
       .toThrowError(
@@ -85,7 +85,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
 
   it('should not throw on insertion in dev without strict', () => {
     __DEV__ = true;
-    var o = {oldKey: 'value'};
+    const o = {oldKey: 'value'};
     deepFreezeAndThrowOnMutationInDev(o);
     expect(() => { o.newKey = 'value'; }).not.toThrow();
     expect(o.newKey).toBe(undefined);
@@ -94,7 +94,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
   it('should mutate and not throw on mutation in prod', () => {
     'use strict';
     __DEV__ = false;
-    var o = {key: 'oldValue'};
+    const o = {key: 'oldValue'};
     deepFreezeAndThrowOnMutationInDev(o);
     expect(() => { o.key = 'newValue'; }).not.toThrow();
     expect(o.key).toBe('newValue');
@@ -104,7 +104,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
   it('should not deep freeze already frozen objects', () => {
     'use strict';
     __DEV__ = true;
-    var o = {key1: {key2: 'oldValue'}};
+    const o = {key1: {key2: 'oldValue'}};
     Object.freeze(o);
     deepFreezeAndThrowOnMutationInDev(o);
     expect(() => { o.key1.key2 = 'newValue'; }).not.toThrow();
@@ -113,7 +113,7 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
 
   it("shouldn't recurse infinitely", () => {
     __DEV__ = true;
-    var o = {};
+    const o = {};
     o.circular = o;
     deepFreezeAndThrowOnMutationInDev(o);
   });
diff --git a/Libraries/Utilities/__tests__/groupByEveryN-test.js b/Libraries/Utilities/__tests__/groupByEveryN-test.js
index 5fe34833549e..56baa9b0ac62 100644
--- a/Libraries/Utilities/__tests__/groupByEveryN-test.js
+++ b/Libraries/Utilities/__tests__/groupByEveryN-test.js
@@ -9,7 +9,7 @@
 'use strict';
 
 describe('groupByEveryN', () => {
-  var groupByEveryN = require('groupByEveryN');
+  const groupByEveryN = require('groupByEveryN');
 
   it('should group by with different n', () => {
     expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 1))
diff --git a/Libraries/Utilities/__tests__/truncate-test.js b/Libraries/Utilities/__tests__/truncate-test.js
index 9c38d1e1e701..47b2a3ae9803 100644
--- a/Libraries/Utilities/__tests__/truncate-test.js
+++ b/Libraries/Utilities/__tests__/truncate-test.js
@@ -10,7 +10,7 @@
 
 describe('truncate', () => {
 
-  var truncate = require('truncate');
+  const truncate = require('truncate');
 
   it('should truncate', () => {
     expect(truncate('Hello, world.', 5))
diff --git a/Libraries/Utilities/buildStyleInterpolator.js b/Libraries/Utilities/buildStyleInterpolator.js
index a22526e45cf3..2ffed265f1df 100644
--- a/Libraries/Utilities/buildStyleInterpolator.js
+++ b/Libraries/Utilities/buildStyleInterpolator.js
@@ -8,18 +8,18 @@
 
 'use strict';
 
-var keyOf = require('fbjs/lib/keyOf');
+const keyOf = require('fbjs/lib/keyOf');
 
-var X_DIM = keyOf({x: null});
-var Y_DIM = keyOf({y: null});
-var Z_DIM = keyOf({z: null});
+const X_DIM = keyOf({x: null});
+const Y_DIM = keyOf({y: null});
+const Z_DIM = keyOf({z: null});
 
-var InitialOperationField = {
+const InitialOperationField = {
   transformTranslate: [0, 0, 0],
   transformScale: [1, 1, 1],
 };
 
-var InterpolateMatrix = {
+const InterpolateMatrix = {
   transformScale: function(mat, x, y, z) {
     mat[0] = mat[0] * x;
     mat[1] = mat[1] * x;
@@ -42,27 +42,27 @@ var InterpolateMatrix = {
   }
 };
 
-var computeNextValLinear = function(anim, from, to, value) {
-  var hasRoundRatio = 'round' in anim;
-  var roundRatio = anim.round;
-  var ratio = (value - anim.min) / (anim.max - anim.min);
+const computeNextValLinear = function(anim, from, to, value) {
+  const hasRoundRatio = 'round' in anim;
+  const roundRatio = anim.round;
+  let ratio = (value - anim.min) / (anim.max - anim.min);
   if (!anim.extrapolate) {
     ratio = ratio > 1 ? 1 : (ratio < 0 ? 0 : ratio);
   }
-  var nextVal = from * (1 - ratio) + to * ratio;
+  let nextVal = from * (1 - ratio) + to * ratio;
   if (hasRoundRatio) {
     nextVal = Math.round(roundRatio * nextVal) / roundRatio;
   }
   return nextVal;
 };
 
-var computeNextValLinearScalar = function(anim, value) {
+const computeNextValLinearScalar = function(anim, value) {
   return computeNextValLinear(anim, anim.from, anim.to, value);
 };
 
-var setNextValAndDetectChange = function(result, name, nextVal, didChange) {
+const setNextValAndDetectChange = function(result, name, nextVal, didChange) {
   if (!didChange) {
-    var prevVal = result[name];
+    const prevVal = result[name];
     result[name] = nextVal;
     didChange = didChange  || (nextVal !== prevVal);
   } else {
@@ -71,7 +71,7 @@ var setNextValAndDetectChange = function(result, name, nextVal, didChange) {
   return didChange;
 };
 
-var initIdentity = function(mat) {
+const initIdentity = function(mat) {
   mat[0] = 1;
   mat[1] = 0;
   mat[2] = 0;
@@ -90,7 +90,7 @@ var initIdentity = function(mat) {
   mat[15] = 1;
 };
 
-var computeNextMatrixOperationField = function(anim, name, dim, index, value) {
+const computeNextMatrixOperationField = function(anim, name, dim, index, value) {
   if (anim.from[dim] !== undefined && anim.to[dim] !== undefined) {
     return computeNextValLinear(anim, anim.from[dim], anim.to[dim], value);
   } else {
@@ -98,33 +98,33 @@ var computeNextMatrixOperationField = function(anim, name, dim, index, value) {
   }
 };
 
-var computeTransform = function(anim, name, value, result,
+const computeTransform = function(anim, name, value, result,
                                 didChange, didMatrix) {
-  var transform = result.transform !== undefined ?
+  const transform = result.transform !== undefined ?
         result.transform : (result.transform = [{ matrix: [] }]);
-  var mat = transform[0].matrix;
-  var m0 = mat[0];
-  var m1 = mat[1];
-  var m2 = mat[2];
-  var m3 = mat[3];
-  var m4 = mat[4];
-  var m5 = mat[5];
-  var m6 = mat[6];
-  var m7 = mat[7];
-  var m8 = mat[8];
-  var m9 = mat[9];
-  var m10 = mat[10];
-  var m11 = mat[11];
-  var m12 = mat[12];
-  var m13 = mat[13];
-  var m14 = mat[14];
-  var m15 = mat[15];
+  const mat = transform[0].matrix;
+  const m0 = mat[0];
+  const m1 = mat[1];
+  const m2 = mat[2];
+  const m3 = mat[3];
+  const m4 = mat[4];
+  const m5 = mat[5];
+  const m6 = mat[6];
+  const m7 = mat[7];
+  const m8 = mat[8];
+  const m9 = mat[9];
+  const m10 = mat[10];
+  const m11 = mat[11];
+  const m12 = mat[12];
+  const m13 = mat[13];
+  const m14 = mat[14];
+  const m15 = mat[15];
   if (!didMatrix) {
     initIdentity(mat);  // This will be the first transform.
   }
-  var x = computeNextMatrixOperationField(anim, name, X_DIM, 0, value);
-  var y = computeNextMatrixOperationField(anim, name, Y_DIM, 1, value);
-  var z = computeNextMatrixOperationField(anim, name, Z_DIM, 2, value);
+  const x = computeNextMatrixOperationField(anim, name, X_DIM, 0, value);
+  const y = computeNextMatrixOperationField(anim, name, Y_DIM, 1, value);
+  const z = computeNextMatrixOperationField(anim, name, Z_DIM, 2, value);
   InterpolateMatrix[name](mat, x, y, z);
   if (!didChange) {
     didChange = m0 !== mat[0] || m1 !== mat[1] ||
@@ -144,12 +144,12 @@ var computeTransform = function(anim, name, value, result,
  * @return {function} Function accepting style object, that mutates that style
  * object and returns a boolean describing if any update was actually applied.
  */
-var buildStyleInterpolator = function(anims) {
+const buildStyleInterpolator = function(anims) {
   function styleInterpolator(result, value) {
-    var didChange = false;
-    var didMatrix = false;
-    for (var name in anims) {
-      var anim = anims[name];
+    let didChange = false;
+    let didMatrix = false;
+    for (const name in anims) {
+      const anim = anims[name];
       if (anim.type === 'linear') {
         if (name in InterpolateMatrix) {
           didChange = computeTransform(anim, name, value, result,
diff --git a/Libraries/Utilities/createStrictShapeTypeChecker.js b/Libraries/Utilities/createStrictShapeTypeChecker.js
index 5cde7eb53157..558119f6ae04 100644
--- a/Libraries/Utilities/createStrictShapeTypeChecker.js
+++ b/Libraries/Utilities/createStrictShapeTypeChecker.js
@@ -8,8 +8,8 @@
  */
 'use strict';
 
-var invariant = require('fbjs/lib/invariant');
-var merge = require('merge');
+const invariant = require('fbjs/lib/invariant');
+const merge = require('merge');
 
 function createStrictShapeTypeChecker(
   shapeTypes: {[key: string]: ReactPropsCheckType}
@@ -25,9 +25,9 @@ function createStrictShapeTypeChecker(
       }
       return;
     }
-    var propValue = props[propName];
-    var propType = typeof propValue;
-    var locationName = location || '(unknown)';
+    const propValue = props[propName];
+    const propType = typeof propValue;
+    const locationName = location || '(unknown)';
     if (propType !== 'object') {
       invariant(
         false,
@@ -37,9 +37,9 @@ function createStrictShapeTypeChecker(
     }
     // We need to check all keys in case some are required but missing from
     // props.
-    var allKeys = merge(props[propName], shapeTypes);
-    for (var key in allKeys) {
-      var checker = shapeTypes[key];
+    const allKeys = merge(props[propName], shapeTypes);
+    for (const key in allKeys) {
+      const checker = shapeTypes[key];
       if (!checker) {
         invariant(
           false,
@@ -48,7 +48,7 @@ function createStrictShapeTypeChecker(
             '\nValid keys: ' + JSON.stringify(Object.keys(shapeTypes), null, '  ')
         );
       }
-      var error = checker(propValue, key, componentName, location, ...rest);
+      const error = checker(propValue, key, componentName, location, ...rest);
       if (error) {
         invariant(
           false,
diff --git a/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js b/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
index 041691a67f7a..9e21a2aae63c 100644
--- a/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
+++ b/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
@@ -35,7 +35,7 @@ function deepFreezeAndThrowOnMutationInDev<T: Object>(object: T): T {
       return object;
     }
 
-    var keys = Object.keys(object);
+    const keys = Object.keys(object);
 
     for (var i = 0; i < keys.length; i++) {
       var key = keys[i];
diff --git a/Libraries/Utilities/differ/__tests__/deepDiffer-test.js b/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
index 4fb31ee05fb3..cb39370dc5c4 100644
--- a/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
+++ b/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
@@ -8,7 +8,7 @@
  */
 'use strict';
 
-var deepDiffer = require('deepDiffer');
+const deepDiffer = require('deepDiffer');
 
 describe('deepDiffer', function() {
   it('should diff primitives of the same type', () => {
@@ -95,7 +95,7 @@ describe('deepDiffer', function() {
     expect(deepDiffer(['a', 'b'], {length: 2, 0: 'a', 1: 'b'})).toBe(true);
   });
   it('should diff same object', () => {
-    var obj = [1,[2,3]];
+    const obj = [1,[2,3]];
     expect(deepDiffer(obj, obj)).toBe(false);
   });
   it('should respect maxDepth arg', () => {
diff --git a/Libraries/Utilities/differ/deepDiffer.js b/Libraries/Utilities/differ/deepDiffer.js
index f3f826fe9116..94dc0cd71dc2 100644
--- a/Libraries/Utilities/differ/deepDiffer.js
+++ b/Libraries/Utilities/differ/deepDiffer.js
@@ -11,7 +11,7 @@
 /*
  * @returns {bool} true if different, false if equal
  */
-var deepDiffer = function(one: any, two: any, maxDepth: number = -1): bool {
+const deepDiffer = function(one: any, two: any, maxDepth: number = -1): bool {
   if (maxDepth === 0) {
     return true;
   }
@@ -37,22 +37,22 @@ var deepDiffer = function(one: any, two: any, maxDepth: number = -1): bool {
   }
   if (Array.isArray(one)) {
     // We know two is also an array because the constructors are equal
-    var len = one.length;
+    const len = one.length;
     if (two.length !== len) {
       return true;
     }
-    for (var ii = 0; ii < len; ii++) {
+    for (let ii = 0; ii < len; ii++) {
       if (deepDiffer(one[ii], two[ii], maxDepth - 1)) {
         return true;
       }
     }
   } else {
-    for (var key in one) {
+    for (const key in one) {
       if (deepDiffer(one[key], two[key], maxDepth - 1)) {
         return true;
       }
     }
-    for (var twoKey in two) {
+    for (const twoKey in two) {
       // The only case we haven't checked yet is keys that are in two but aren't
       // in one, which means they are different.
       if (one[twoKey] === undefined && two[twoKey] !== undefined) {
diff --git a/Libraries/Utilities/differ/insetsDiffer.js b/Libraries/Utilities/differ/insetsDiffer.js
index 7214ab6d7638..c86f6d17b4e1 100644
--- a/Libraries/Utilities/differ/insetsDiffer.js
+++ b/Libraries/Utilities/differ/insetsDiffer.js
@@ -15,14 +15,14 @@ type Inset = {
   bottom: ?number,
 }
 
-var dummyInsets = {
+const dummyInsets = {
 	top: undefined,
 	left: undefined,
 	right: undefined,
 	bottom: undefined,
 };
 
-var insetsDiffer = function(
+const insetsDiffer = function(
   one: ?Inset,
   two: ?Inset
 ): bool {
diff --git a/Libraries/Utilities/differ/matricesDiffer.js b/Libraries/Utilities/differ/matricesDiffer.js
index 177a7a110ac4..883081fa0ab8 100644
--- a/Libraries/Utilities/differ/matricesDiffer.js
+++ b/Libraries/Utilities/differ/matricesDiffer.js
@@ -16,7 +16,7 @@
  * @param {MatrixMath.Matrix} two Second matrix.
  * @return {boolean} Whether or not the two matrices differ.
  */
-var matricesDiffer = function(one, two) {
+const matricesDiffer = function(one, two) {
   if (one === two) {
     return false;
   }
diff --git a/Libraries/Utilities/differ/pointsDiffer.js b/Libraries/Utilities/differ/pointsDiffer.js
index e019124e76d1..b9d239c7907f 100644
--- a/Libraries/Utilities/differ/pointsDiffer.js
+++ b/Libraries/Utilities/differ/pointsDiffer.js
@@ -13,9 +13,9 @@ type Point = {
   y: ?number,
 }
 
-var dummyPoint = {x: undefined, y: undefined};
+const dummyPoint = {x: undefined, y: undefined};
 
-var pointsDiffer = function(one: ?Point, two: ?Point): bool {
+const pointsDiffer = function(one: ?Point, two: ?Point): bool {
   one = one || dummyPoint;
   two = two || dummyPoint;
   return one !== two && (
diff --git a/Libraries/Utilities/differ/sizesDiffer.js b/Libraries/Utilities/differ/sizesDiffer.js
index c4e104a1439b..ad2939cc71ef 100644
--- a/Libraries/Utilities/differ/sizesDiffer.js
+++ b/Libraries/Utilities/differ/sizesDiffer.js
@@ -7,9 +7,9 @@
  */
 'use strict';
 
-var dummySize = {width: undefined, height: undefined};
+const dummySize = {width: undefined, height: undefined};
 
-var sizesDiffer = function(one, two) {
+const sizesDiffer = function(one, two) {
   one = one || dummySize;
   two = two || dummySize;
   return one !== two && (
diff --git a/Libraries/Utilities/dismissKeyboard.js b/Libraries/Utilities/dismissKeyboard.js
index a5b9e2f00dd9..64f7368a35da 100644
--- a/Libraries/Utilities/dismissKeyboard.js
+++ b/Libraries/Utilities/dismissKeyboard.js
@@ -9,7 +9,7 @@
  */
 'use strict';
 
-var TextInputState = require('TextInputState');
+const TextInputState = require('TextInputState');
 
 function dismissKeyboard() {
   TextInputState.blurTextInput(TextInputState.currentlyFocusedField());
diff --git a/Libraries/Utilities/groupByEveryN.js b/Libraries/Utilities/groupByEveryN.js
index 2cda280be6f1..bdf13b226936 100644
--- a/Libraries/Utilities/groupByEveryN.js
+++ b/Libraries/Utilities/groupByEveryN.js
@@ -25,10 +25,10 @@
 'use strict';
 
 function groupByEveryN<T>(array: Array<T>, n: number): Array<Array<?T>> {
-  var result = [];
-  var temp = [];
+  const result = [];
+  let temp = [];
 
-  for (var i = 0; i < array.length; ++i) {
+  for (let i = 0; i < array.length; ++i) {
     if (i > 0 && i % n === 0) {
       result.push(temp);
       temp = [];
diff --git a/Libraries/Utilities/logError.js b/Libraries/Utilities/logError.js
index 5482448ae20b..e79b340563ce 100644
--- a/Libraries/Utilities/logError.js
+++ b/Libraries/Utilities/logError.js
@@ -13,9 +13,9 @@
  * `console.error` as a failure callback - it's not properly bound.  If passes an
  * `Error` object, it will print the message and stack.
  */
-var logError = function(...args: $ReadOnlyArray<mixed>) {
+const logError = function(...args: $ReadOnlyArray<mixed>) {
   if (args.length === 1 && args[0] instanceof Error) {
-    var err = args[0];
+    const err = args[0];
     console.error('Error: "' + err.message + '".  Stack:\n' + err.stack);
   } else {
     console.error.apply(console, args);
diff --git a/Libraries/Utilities/mergeIntoFast.js b/Libraries/Utilities/mergeIntoFast.js
index e657de7c3d9d..cfbc87923987 100644
--- a/Libraries/Utilities/mergeIntoFast.js
+++ b/Libraries/Utilities/mergeIntoFast.js
@@ -15,8 +15,8 @@
  * @param {object} one Object to assign to.
  * @param {object} two Object to assign from.
  */
-var mergeIntoFast = function(one: Object, two: Object): void {
-  for (var keyTwo in two) {
+const mergeIntoFast = function(one: Object, two: Object): void {
+  for (const keyTwo in two) {
     one[keyTwo] = two[keyTwo];
   }
 };
diff --git a/Libraries/Utilities/stringifySafe.js b/Libraries/Utilities/stringifySafe.js
index f8f7ab8f0e40..4536b8f668be 100644
--- a/Libraries/Utilities/stringifySafe.js
+++ b/Libraries/Utilities/stringifySafe.js
@@ -13,8 +13,8 @@
  * (e.g. from circular objects) and always returns a string and never throws.
  */
 function stringifySafe(arg: any): string {
-  var ret;
-  var type = typeof arg;
+  let ret;
+  const type = typeof arg;
   if (arg === undefined) {
     ret = 'undefined';
   } else if (arg === null) {
diff --git a/Libraries/Utilities/truncate.js b/Libraries/Utilities/truncate.js
index 5b89e8ff2007..017a524912c0 100644
--- a/Libraries/Utilities/truncate.js
+++ b/Libraries/Utilities/truncate.js
@@ -30,12 +30,12 @@ const truncate = function(
   if (str && str.length &&
       str.length - options.minDelta + options.elipsis.length >= maxChars) {
     // If the slice is happening in the middle of a wide char, add one more char
-    var extraChar = str.charCodeAt(maxChars - options.elipsis.length) > 255
+    const extraChar = str.charCodeAt(maxChars - options.elipsis.length) > 255
       ? 1
       : 0;
     str = str.slice(0, maxChars - options.elipsis.length + 1 + extraChar);
     if (options.breakOnWords) {
-      var ii = Math.max(str.lastIndexOf(' '), str.lastIndexOf('\n'));
+      const ii = Math.max(str.lastIndexOf(' '), str.lastIndexOf('\n'));
       str = str.slice(0, ii);
     }
     str = str.trim() + options.elipsis;
diff --git a/Libraries/Vibration/Vibration.js b/Libraries/Vibration/Vibration.js
index c0ee75203fcd..182ca26d9c50 100644
--- a/Libraries/Vibration/Vibration.js
+++ b/Libraries/Vibration/Vibration.js
@@ -9,8 +9,8 @@
  */
 'use strict';
 
-var RCTVibration = require('NativeModules').Vibration;
-var Platform = require('Platform');
+const RCTVibration = require('NativeModules').Vibration;
+const Platform = require('Platform');
 
 /**
  * Vibration API
@@ -18,8 +18,8 @@ var Platform = require('Platform');
  * See https://facebook.github.io/react-native/docs/vibration.html
  */
 
-var _vibrating: boolean = false;
-var _id: number = 0; // _id is necessary to prevent race condition.
+let _vibrating: boolean = false;
+let _id: number = 0; // _id is necessary to prevent race condition.
 
 function vibrateByPattern(pattern: Array<number>, repeat: boolean = false) {
   if (_vibrating) {
@@ -53,7 +53,7 @@ function vibrateScheduler(id, pattern: Array<number>, repeat: boolean, nextIndex
   setTimeout(() => vibrateScheduler(id, pattern, repeat, nextIndex + 1), pattern[nextIndex]);
 }
 
-var Vibration = {
+const Vibration = {
   /**
    * Trigger a vibration with specified `pattern`.
    *
diff --git a/Libraries/Vibration/VibrationIOS.android.js b/Libraries/Vibration/VibrationIOS.android.js
index b57279a73844..93a1aab1af83 100644
--- a/Libraries/Vibration/VibrationIOS.android.js
+++ b/Libraries/Vibration/VibrationIOS.android.js
@@ -9,9 +9,9 @@
  */
 'use strict';
 
-var warning = require('fbjs/lib/warning');
+const warning = require('fbjs/lib/warning');
 
-var VibrationIOS = {
+const VibrationIOS = {
   vibrate: function() {
     warning('VibrationIOS is not supported on this platform!');
   }
diff --git a/Libraries/Vibration/VibrationIOS.ios.js b/Libraries/Vibration/VibrationIOS.ios.js
index 5ce5f4019bb5..29cc3eee02a4 100644
--- a/Libraries/Vibration/VibrationIOS.ios.js
+++ b/Libraries/Vibration/VibrationIOS.ios.js
@@ -8,9 +8,9 @@
  */
 'use strict';
 
-var RCTVibration = require('NativeModules').Vibration;
+const RCTVibration = require('NativeModules').Vibration;
 
-var invariant = require('fbjs/lib/invariant');
+const invariant = require('fbjs/lib/invariant');
 
 /**
  * NOTE: `VibrationIOS` is being deprecated. Use `Vibration` instead.
@@ -25,7 +25,7 @@ var invariant = require('fbjs/lib/invariant');
  * Vibration patterns are currently unsupported.
  */
 
-var VibrationIOS = {
+const VibrationIOS = {
   /**
    * @deprecated
    */
diff --git a/Libraries/WebSocket/__tests__/WebSocket-test.js b/Libraries/WebSocket/__tests__/WebSocket-test.js
index c6e04bf0a6d9..a263caf3ee22 100644
--- a/Libraries/WebSocket/__tests__/WebSocket-test.js
+++ b/Libraries/WebSocket/__tests__/WebSocket-test.js
@@ -15,7 +15,7 @@ jest.setMock('NativeModules', {
   }
 });
 
-var WebSocket = require('WebSocket');
+const WebSocket = require('WebSocket');
 
 describe('WebSocket', function() {
 
diff --git a/Libraries/vendor/core/Map.js b/Libraries/vendor/core/Map.js
index 115e2f855eaf..575a6b1d57c0 100644
--- a/Libraries/vendor/core/Map.js
+++ b/Libraries/vendor/core/Map.js
@@ -12,10 +12,10 @@
 
 'use strict';
 
-var _shouldPolyfillES6Collection = require('_shouldPolyfillES6Collection');
-var guid = require('guid');
-var isNode = require('fbjs/lib/isNode');
-var toIterator = require('toIterator');
+const _shouldPolyfillES6Collection = require('_shouldPolyfillES6Collection');
+const guid = require('guid');
+const isNode = require('fbjs/lib/isNode');
+const toIterator = require('toIterator');
 
 module.exports = (function(global, undefined) {
   // Since our implementation is spec-compliant for the most part we can safely
@@ -81,23 +81,23 @@ module.exports = (function(global, undefined) {
    */
 
   // Kinds of map iterations 23.1.5.3
-  var KIND_KEY = 'key';
-  var KIND_VALUE = 'value';
-  var KIND_KEY_VALUE = 'key+value';
+  const KIND_KEY = 'key';
+  const KIND_VALUE = 'value';
+  const KIND_KEY_VALUE = 'key+value';
 
   // In older browsers we can't create a null-prototype object so we have to
   // defend against key collisions with built-in methods.
-  var KEY_PREFIX = '$map_';
+  const KEY_PREFIX = '$map_';
 
   // This property will be used as the internal size variable to disallow
   // writing and to issue warnings for writings in development.
-  var SECRET_SIZE_PROP;
+  let SECRET_SIZE_PROP;
   if (__DEV__) {
     SECRET_SIZE_PROP = '$size' + guid();
   }
 
   // In oldIE we use the DOM Node `uniqueID` property to get create the hash.
-  var OLD_IE_HASH_PREFIX = 'IE_HASH_';
+  const OLD_IE_HASH_PREFIX = 'IE_HASH_';
 
   class Map {
 
@@ -118,8 +118,8 @@ module.exports = (function(global, undefined) {
       initMap(this);
 
       if (iterable != null) {
-        var it = toIterator(iterable);
-        var next;
+        const it = toIterator(iterable);
+        let next;
         while (!(next = it.next()).done) {
           if (!isObject(next.value)) {
             throw new TypeError('Expected iterable items to be pair objects.');
@@ -145,7 +145,7 @@ module.exports = (function(global, undefined) {
      * @return {boolean}
      */
     has(key) {
-      var index = getIndex(this, key);
+      const index = getIndex(this, key);
       return !!(index != null && this._mapData[index]);
     }
 
@@ -158,7 +158,7 @@ module.exports = (function(global, undefined) {
      * @return {map}
      */
     set(key, value) {
-      var index = getIndex(this, key);
+      let index = getIndex(this, key);
 
       if (index != null && this._mapData[index]) {
         this._mapData[index][1] = value;
@@ -186,7 +186,7 @@ module.exports = (function(global, undefined) {
      * @return {*}
      */
     get(key) {
-      var index = getIndex(this, key);
+      const index = getIndex(this, key);
       if (index == null) {
         return undefined;
       } else {
@@ -203,7 +203,7 @@ module.exports = (function(global, undefined) {
      * @return {boolean} Whether the key was found and deleted.
      */
     delete(key) {
-      var index = getIndex(this, key);
+      const index = getIndex(this, key);
       if (index != null && this._mapData[index]) {
         setIndex(this, key, undefined);
         this._mapData[index] = undefined;
@@ -263,14 +263,14 @@ module.exports = (function(global, undefined) {
         throw new TypeError('Callback must be callable.');
       }
 
-      var boundCallback = callback.bind(thisArg || undefined);
-      var mapData = this._mapData;
+      const boundCallback = callback.bind(thisArg || undefined);
+      const mapData = this._mapData;
 
       // Note that `mapData.length` should be computed on each iteration to
       // support iterating over new items in the map that were added after the
       // start of the iteration.
-      for (var i = 0; i < mapData.length; i++) {
-        var entry = mapData[i];
+      for (let i = 0; i < mapData.length; i++) {
+        const entry = mapData[i];
         if (entry != null) {
           boundCallback(entry[1], entry[0], this);
         }
@@ -316,18 +316,18 @@ module.exports = (function(global, undefined) {
         throw new TypeError('Expected to be called on a MapIterator.');
       }
 
-      var map = this._map;
-      var index = this._nextIndex;
-      var kind = this._kind;
+      const map = this._map;
+      let index = this._nextIndex;
+      const kind = this._kind;
 
       if (map == null) {
         return createIterResultObject(undefined, true);
       }
 
-      var entries = map._mapData;
+      const entries = map._mapData;
 
       while (index < entries.length) {
-        var record = entries[index];
+        const record = entries[index];
 
         index += 1;
         this._nextIndex = index;
@@ -369,10 +369,10 @@ module.exports = (function(global, undefined) {
    */
   function getIndex(map, key) {
     if (isObject(key)) {
-      var hash = getHash(key);
+      const hash = getHash(key);
       return map._objectIndex[hash];
     } else {
-      var prefixedKey = KEY_PREFIX + key;
+      const prefixedKey = KEY_PREFIX + key;
       if (typeof key === 'string') {
         return map._stringIndex[prefixedKey];
       } else {
@@ -388,17 +388,17 @@ module.exports = (function(global, undefined) {
    * @param {*} key
    */
   function setIndex(map, key, index) {
-    var shouldDelete = index == null;
+    const shouldDelete = index == null;
 
     if (isObject(key)) {
-      var hash = getHash(key);
+      const hash = getHash(key);
       if (shouldDelete) {
         delete map._objectIndex[hash];
       } else {
         map._objectIndex[hash] = index;
       }
     } else {
-      var prefixedKey = KEY_PREFIX + key;
+      const prefixedKey = KEY_PREFIX + key;
       if (typeof key === 'string') {
         if (shouldDelete) {
           delete map._stringIndex[prefixedKey];
@@ -505,7 +505,7 @@ module.exports = (function(global, undefined) {
   }
 
   // Are we in a legit ES5 environment. Spoiler alert: that doesn't include IE8.
-  var isES5 = (function() {
+  const isES5 = (function() {
     try {
       Object.defineProperty({}, 'x', {});
       return true;
@@ -537,7 +537,7 @@ module.exports = (function(global, undefined) {
    * @return {?string}
    */
   function getIENodeHash(node) {
-    var uniqueID;
+    let uniqueID;
     switch (node.nodeType) {
       case 1: // Element
         uniqueID = node.uniqueID;
@@ -556,10 +556,10 @@ module.exports = (function(global, undefined) {
     }
   }
 
-  var getHash = (function() {
-    var propIsEnumerable = Object.prototype.propertyIsEnumerable;
-    var hashProperty = guid();
-    var hashCounter = 0;
+  const getHash = (function() {
+    const propIsEnumerable = Object.prototype.propertyIsEnumerable;
+    const hashProperty = guid();
+    let hashCounter = 0;
 
     /**
      * Get the "hash" associated with an object.
diff --git a/Libraries/vendor/core/Set.js b/Libraries/vendor/core/Set.js
index 16e3cecae21f..3ba61c26a993 100644
--- a/Libraries/vendor/core/Set.js
+++ b/Libraries/vendor/core/Set.js
@@ -12,10 +12,10 @@
 
 'use strict';
 
-var Map = require('Map');
+const Map = require('Map');
 
-var _shouldPolyfillES6Collection = require('_shouldPolyfillES6Collection');
-var toIterator = require('toIterator');
+const _shouldPolyfillES6Collection = require('_shouldPolyfillES6Collection');
+const toIterator = require('toIterator');
 
 module.exports = (function(global) {
   // Since our implementation is spec-compliant for the most part we can safely
@@ -88,8 +88,8 @@ module.exports = (function(global) {
       initSet(this);
 
       if (iterable != null) {
-        var it = toIterator(iterable);
-        var next;
+        const it = toIterator(iterable);
+        let next;
         while (!(next = it.next()).done) {
           this.add(next.value);
         }
@@ -129,7 +129,7 @@ module.exports = (function(global) {
      * @return {boolean}
      */
     delete(value) {
-      var ret = this._map.delete(value);
+      const ret = this._map.delete(value);
       this.size = this._map.size;
       return ret;
     }
@@ -151,9 +151,9 @@ module.exports = (function(global) {
      * @param {function} callback
      */
     forEach(callback) {
-      var thisArg = arguments[1];
-      var it = this._map.keys();
-      var next;
+      const thisArg = arguments[1];
+      const it = this._map.keys();
+      let next;
       while (!(next = it.next()).done) {
         callback.call(thisArg, next.value, next.value, this);
       }
diff --git a/Libraries/vendor/core/_shouldPolyfillES6Collection.js b/Libraries/vendor/core/_shouldPolyfillES6Collection.js
index 84ed51ded55e..576d1eb67103 100644
--- a/Libraries/vendor/core/_shouldPolyfillES6Collection.js
+++ b/Libraries/vendor/core/_shouldPolyfillES6Collection.js
@@ -14,7 +14,7 @@
  * that is safe to be used.
  */
 function _shouldActuallyPolyfillES6Collection(collectionName: string): boolean {
-  var Collection = global[collectionName];
+  const Collection = global[collectionName];
   if (Collection == null) {
     return true;
   }
@@ -27,7 +27,7 @@ function _shouldActuallyPolyfillES6Collection(collectionName: string): boolean {
     return true;
   }
 
-  var proto = Collection.prototype;
+  const proto = Collection.prototype;
 
   // These checks are adapted from es6-shim: https://fburl.com/34437854
   // NOTE: `isCallableWithoutNew` and `!supportsSubclassing` are not checked
diff --git a/Libraries/vendor/core/getObjectValues.js b/Libraries/vendor/core/getObjectValues.js
index 398788c1e02f..0a020af5169c 100644
--- a/Libraries/vendor/core/getObjectValues.js
+++ b/Libraries/vendor/core/getObjectValues.js
@@ -18,8 +18,8 @@
  * @return {array}     The object's values.
  */
 function getObjectValues(obj) {
-  var values = [];
-  for (var key in obj) {
+  const values = [];
+  for (const key in obj) {
     values.push(obj[key]);
   }
   return values;
diff --git a/Libraries/vendor/core/isEmpty.js b/Libraries/vendor/core/isEmpty.js
index 6d451729c7c8..c7747c980a56 100644
--- a/Libraries/vendor/core/isEmpty.js
+++ b/Libraries/vendor/core/isEmpty.js
@@ -14,7 +14,7 @@ function isEmpty(obj) {
   if (Array.isArray(obj)) {
     return obj.length === 0;
   } else if (typeof obj === 'object') {
-    for (var i in obj) {
+    for (const i in obj) {
       return false;
     }
     return true;
diff --git a/Libraries/vendor/core/mergeHelpers.js b/Libraries/vendor/core/mergeHelpers.js
index e24559ddb50c..10072ed46335 100644
--- a/Libraries/vendor/core/mergeHelpers.js
+++ b/Libraries/vendor/core/mergeHelpers.js
@@ -10,13 +10,13 @@
 
 'use strict';
 
-var invariant = require('fbjs/lib/invariant');
+const invariant = require('fbjs/lib/invariant');
 
 /**
  * Maximum number of levels to traverse. Will catch circular structures.
  * @const
  */
-var MAX_MERGE_DEPTH = 36;
+const MAX_MERGE_DEPTH = 36;
 
 /**
  * We won't worry about edge cases like new String('x') or new Boolean(true).
@@ -24,11 +24,11 @@ var MAX_MERGE_DEPTH = 36;
  * @param {*} o The item/object/value to test.
  * @return {boolean} true iff the argument is a terminal.
  */
-var isTerminal = function(o) {
+const isTerminal = function(o) {
   return typeof o !== 'object' || o instanceof Date || o === null;
 };
 
-var mergeHelpers = {
+const mergeHelpers = {
 
   MAX_MERGE_DEPTH: MAX_MERGE_DEPTH,
 
diff --git a/Libraries/vendor/core/toIterator.js b/Libraries/vendor/core/toIterator.js
index cabd1e2b0667..728b68c7bda9 100644
--- a/Libraries/vendor/core/toIterator.js
+++ b/Libraries/vendor/core/toIterator.js
@@ -17,15 +17,15 @@
  * Constants
  */
 
-var KIND_KEY = 'key';
-var KIND_VALUE = 'value';
-var KIND_KEY_VAL = 'key+value';
+const KIND_KEY = 'key';
+const KIND_VALUE = 'value';
+const KIND_KEY_VAL = 'key+value';
 /*global Symbol: true*/
-var ITERATOR_SYMBOL = (typeof Symbol === 'function')
+const ITERATOR_SYMBOL = (typeof Symbol === 'function')
     ? Symbol.iterator
     : '@@iterator';
 
-var toIterator = (function() {
+const toIterator = (function() {
   if (!(Array.prototype[ITERATOR_SYMBOL] &&
         String.prototype[ITERATOR_SYMBOL])) {
     // IIFE to avoid creating classes for no reason because of hoisting.
@@ -51,10 +51,10 @@ var toIterator = (function() {
             return createIterResultObject(undefined, true);
           }
 
-          var array = this._iteratedObject;
-          var len = this._iteratedObject.length;
-          var index = this._nextIndex;
-          var kind = this._kind;
+          const array = this._iteratedObject;
+          const len = this._iteratedObject.length;
+          const index = this._nextIndex;
+          const kind = this._kind;
 
           if (index >= len) {
             this._iteratedObject = undefined;
@@ -98,22 +98,22 @@ var toIterator = (function() {
             return createIterResultObject(undefined, true);
           }
 
-          var index = this._nextIndex;
-          var s = this._iteratedString;
-          var len = s.length;
+          const index = this._nextIndex;
+          const s = this._iteratedString;
+          const len = s.length;
 
           if (index >= len) {
             this._iteratedString = undefined;
             return createIterResultObject(undefined, true);
           }
 
-          var ret;
-          var first = s.charCodeAt(index);
+          let ret;
+          const first = s.charCodeAt(index);
 
           if (first < 0xD800 || first > 0xDBFF || index + 1 === len) {
             ret = s[index];
           } else {
-            var second = s.charCodeAt(index + 1);
+            const second = s.charCodeAt(index + 1);
             if (second < 0xDC00 || second > 0xDFFF) {
               ret = s[index];
             } else {
diff --git a/Libraries/vendor/document/selection/DocumentSelectionState.js b/Libraries/vendor/document/selection/DocumentSelectionState.js
index 28b93e343906..350732776f72 100644
--- a/Libraries/vendor/document/selection/DocumentSelectionState.js
+++ b/Libraries/vendor/document/selection/DocumentSelectionState.js
@@ -9,7 +9,7 @@
 
 'use strict';
 
-var mixInEventEmitter = require('mixInEventEmitter');
+const mixInEventEmitter = require('mixInEventEmitter');
 
 /**
  * DocumentSelectionState is responsible for maintaining selection information

From 86b6f5d39ecc571260dee891aa422f8d3cc807e8 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Thu, 10 May 2018 15:44:53 -0700
Subject: [PATCH 0501/1109] Add Prettier to some files

Reviewed By: sahrens

Differential Revision: D7958196

fbshipit-source-id: 05a04380a4a1f3abd4cc3a9034fc70deaa4a444b
---
 babel-preset/configs/hmr.js  | 22 +++++++++++++---------
 babel-preset/configs/main.js |  4 +++-
 flow-github/metro.js         |  1 +
 flow/Map.js                  | 12 +++++++++---
 flow/Position.js             |  7 ++++---
 flow/Promise.js              | 27 ++++++++++++++-------------
 flow/Set.js                  |  8 ++++++--
 flow/console.js              | 19 ++++++++++---------
 flow/fbjs.js                 |  8 +++++++-
 flow/prop-types.js           |  7 ++++---
 10 files changed, 71 insertions(+), 44 deletions(-)

diff --git a/babel-preset/configs/hmr.js b/babel-preset/configs/hmr.js
index e2b4a0f3dec0..05b305c09e6c 100644
--- a/babel-preset/configs/hmr.js
+++ b/babel-preset/configs/hmr.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 'use strict';
 
@@ -13,8 +15,8 @@ var transformPath = require.resolve(hmrTransform);
 
 module.exports = function(options, filename) {
   var transform = filename
-      ? './' + path.relative(path.dirname(filename), transformPath) // packager can't handle absolute paths
-      : hmrTransform;
+    ? './' + path.relative(path.dirname(filename), transformPath) // packager can't handle absolute paths
+    : hmrTransform;
 
   // Fix the module path to use '/' on Windows.
   if (path.sep === '\\') {
@@ -26,13 +28,15 @@ module.exports = function(options, filename) {
       [
         require('metro-babel7-plugin-react-transform'),
         {
-          transforms: [{
-            transform: transform,
-            imports: ['react'],
-            locals: ['module'],
-          }]
+          transforms: [
+            {
+              transform: transform,
+              imports: ['react'],
+              locals: ['module'],
+            },
+          ],
         },
-      ]
-    ]
+      ],
+    ],
   };
 };
diff --git a/babel-preset/configs/main.js b/babel-preset/configs/main.js
index e6aeeec39865..526d6f7f909d 100644
--- a/babel-preset/configs/main.js
+++ b/babel-preset/configs/main.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -31,7 +33,7 @@ const defaultPlugins = [
     require('@babel/plugin-transform-modules-commonjs'),
     {
       strict: false,
-      strictMode : false, // prevent "use strict" injections
+      strictMode: false, // prevent "use strict" injections
       allowTopLevelThis: true, // dont rewrite global `this` -> `undefined`
     },
   ],
diff --git a/flow-github/metro.js b/flow-github/metro.js
index ff06b4277746..db5dbdc28c7a 100644
--- a/flow-github/metro.js
+++ b/flow-github/metro.js
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @format
  */
 
 declare module 'metro' {
diff --git a/flow/Map.js b/flow/Map.js
index f2021affd67a..0723ea4266ec 100644
--- a/flow/Map.js
+++ b/flow/Map.js
@@ -5,23 +5,29 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @format
  */
 
 // These annotations are copy/pasted from the built-in Flow definitions for
 // Native Map.
 
-declare module "Map" {
+declare module 'Map' {
   // Use the name "MapPolyfill" so that we don't get confusing error
   // messages about "Using Map instead of Map".
   declare class MapPolyfill<K, V> {
     @@iterator(): Iterator<[K, V]>;
     constructor<Key, Value>(_: void): MapPolyfill<Key, Value>;
     constructor<Key, Value>(_: null): MapPolyfill<Key, Value>;
-    constructor<Key, Value>(iterable: Iterable<[Key, Value]>): MapPolyfill<Key, Value>;
+    constructor<Key, Value>(
+      iterable: Iterable<[Key, Value]>,
+    ): MapPolyfill<Key, Value>;
     clear(): void;
     delete(key: K): boolean;
     entries(): Iterator<[K, V]>;
-    forEach(callbackfn: (value: V, index: K, map: MapPolyfill<K, V>) => mixed, thisArg?: any): void;
+    forEach(
+      callbackfn: (value: V, index: K, map: MapPolyfill<K, V>) => mixed,
+      thisArg?: any,
+    ): void;
     get(key: K): V | void;
     has(key: K): boolean;
     keys(): Iterator<K>;
diff --git a/flow/Position.js b/flow/Position.js
index 58e3330b0b92..5bd2717c0e74 100644
--- a/flow/Position.js
+++ b/flow/Position.js
@@ -6,10 +6,11 @@
  *
  * @flow
  * @nolint
+ * @format
  */
 
 declare class Position {
-  coords: Coordinates,
-  timestamp: number,
-  mocked: boolean,
+  coords: Coordinates;
+  timestamp: number;
+  mocked: boolean;
 }
diff --git a/flow/Promise.js b/flow/Promise.js
index d69944eb4b47..64350cabc0b5 100644
--- a/flow/Promise.js
+++ b/flow/Promise.js
@@ -5,41 +5,42 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @format
  */
 
 // These annotations are copy/pasted from the built-in Flow definitions for
 // Native Promises with some non-standard APIs added in
 declare class Promise<+R> {
-  constructor(callback: (
-    resolve: (result?: Promise<R> | R) => void,
-    reject: (error?: any) => void
-  ) => mixed): void;
+  constructor(
+    callback: (
+      resolve: (result?: Promise<R> | R) => void,
+      reject: (error?: any) => void,
+    ) => mixed,
+  ): void;
 
   then<U>(
     onFulfill?: ?(value: R) => Promise<U> | ?U,
-    onReject?: ?(error: any) => Promise<U> | ?U
+    onReject?: ?(error: any) => Promise<U> | ?U,
   ): Promise<U>;
 
-  catch<U>(
-    onReject?: (error: any) => ?Promise<U> | U
-  ): Promise<U>;
+  catch<U>(onReject?: (error: any) => ?Promise<U> | U): Promise<U>;
 
   static resolve<T>(object?: Promise<T> | T): Promise<T>;
   static reject<T>(error?: any): Promise<T>;
 
-  static all<T: Iterable<mixed>>(promises: T): Promise<$TupleMap<T, typeof $await>>;
+  static all<T: Iterable<mixed>>(
+    promises: T,
+  ): Promise<$TupleMap<T, typeof $await>>;
   static race<T>(promises: Array<Promise<T>>): Promise<T>;
 
   // Non-standard APIs
 
   // See https://github.com/facebook/fbjs/blob/master/packages/fbjs/src/__forks__/Promise.native.js#L21
-  finally<U>(
-    onFinally?: ?(value: any) => Promise<U> | U
-  ): Promise<U>;
+  finally<U>(onFinally?: ?(value: any) => Promise<U> | U): Promise<U>;
 
   done<U>(
     onFulfill?: ?(value: R) => mixed,
-    onReject?: ?(error: any) => mixed
+    onReject?: ?(error: any) => mixed,
   ): void;
 
   static cast<T>(object?: T): Promise<T>;
diff --git a/flow/Set.js b/flow/Set.js
index 54b997a68a6f..ea3b1533b830 100644
--- a/flow/Set.js
+++ b/flow/Set.js
@@ -6,12 +6,13 @@
  *
  * @flow
  * @nolint
+ * @format
  */
 
 // These annotations are copy/pasted from the built-in Flow definitions for
 // Native Set.
 
-declare module "Set" {
+declare module 'Set' {
   // Use the name "SetPolyfill" so that we don't get confusing error
   // messages about "Using Set instead of Set".
   declare class SetPolyfill<T> {
@@ -21,7 +22,10 @@ declare module "Set" {
     clear(): void;
     delete(value: T): boolean;
     entries(): Iterator<[T, T]>;
-    forEach(callbackfn: (value: T, index: T, set: SetPolyfill<T>) => mixed, thisArg?: any): void;
+    forEach(
+      callbackfn: (value: T, index: T, set: SetPolyfill<T>) => mixed,
+      thisArg?: any,
+    ): void;
     has(value: T): boolean;
     keys(): Iterator<T>;
     size: number;
diff --git a/flow/console.js b/flow/console.js
index 4e57ba953715..a5d0d31bf367 100644
--- a/flow/console.js
+++ b/flow/console.js
@@ -5,6 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @format
  */
 
 declare module 'console' {
@@ -22,17 +23,17 @@ declare module 'console' {
   declare function warn(...data: any): void;
   declare class Console {
     constructor(stdout: stream$Writable, stdin?: stream$Writable): void;
-    assert(value: any, ...message: any): void,
+    assert(value: any, ...message: any): void;
     dir(
       obj: Object,
       options: {showHidden: boolean, depth: number, colors: boolean},
-    ): void,
-    error(...data: any): void,
-    info(...data: any): void,
-    log(...data: any): void,
-    time(label: any): void,
-    timeEnd(label: any): void,
-    trace(first: any, ...rest: any): void,
-    warn(...data: any): void,
+    ): void;
+    error(...data: any): void;
+    info(...data: any): void;
+    log(...data: any): void;
+    time(label: any): void;
+    timeEnd(label: any): void;
+    trace(first: any, ...rest: any): void;
+    warn(...data: any): void;
   }
 }
diff --git a/flow/fbjs.js b/flow/fbjs.js
index f7b41b5a6a3a..9106e436da85 100644
--- a/flow/fbjs.js
+++ b/flow/fbjs.js
@@ -3,10 +3,16 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 declare module 'fbjs/lib/invariant' {
-  declare module.exports: <T>(condition: any, message: string, ...args: Array<any>) => void;
+  declare module.exports: <T>(
+    condition: any,
+    message: string,
+    ...args: Array<any>
+  ) => void;
 }
 
 declare module 'fbjs/lib/nullthrows' {
diff --git a/flow/prop-types.js b/flow/prop-types.js
index c79dab62ba93..be239f5bdfb3 100644
--- a/flow/prop-types.js
+++ b/flow/prop-types.js
@@ -6,6 +6,7 @@
  *
  * @flow
  * @nolint
+ * @format
  */
 
 // TODO (bvaughn) Remove this file once flowtype/flow-typed/pull/773 is merged
@@ -14,7 +15,7 @@ type $npm$propTypes$ReactPropsCheckType = (
   props: any,
   propName: string,
   componentName: string,
-  href?: string
+  href?: string,
 ) => ?Error;
 
 declare module 'prop-types' {
@@ -39,6 +40,6 @@ declare module 'prop-types' {
     values: V,
     location: string,
     componentName: string,
-    getStack: ?(() => ?string)
-  ) : void;
+    getStack: ?() => ?string,
+  ): void;
 }

From dca21c8f234803a32a74a2080b7bc9c8493e7c45 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Thu, 10 May 2018 15:44:55 -0700
Subject: [PATCH 0502/1109] Prettier IntegrationTests

Reviewed By: sahrens

Differential Revision: D7958195

fbshipit-source-id: 253c0eec593228e7b6bc66606584877161c6bfc2
---
 IntegrationTests/AccessibilityManagerTest.js  | 34 +++----
 IntegrationTests/AppEventsTest.js             | 19 ++--
 IntegrationTests/AsyncStorageTest.js          | 98 ++++++++++---------
 IntegrationTests/ImageCachePolicyTest.js      | 70 +++++++------
 IntegrationTests/ImageSnapshotTest.js         | 14 +--
 .../IntegrationTestHarnessTest.js             | 25 ++---
 IntegrationTests/IntegrationTestsApp.js       | 14 +--
 IntegrationTests/LayoutEventsTest.js          | 37 +++----
 IntegrationTests/LoggingTestModule.js         | 11 +--
 IntegrationTests/PromiseTest.js               | 32 +++---
 IntegrationTests/PropertiesUpdateTest.js      | 13 ++-
 .../RCTRootViewIntegrationTestApp.js          | 21 ++--
 .../ReactContentSizeUpdateTest.js             | 28 +++---
 IntegrationTests/SimpleSnapshotTest.js        | 11 +--
 IntegrationTests/SizeFlexibilityUpdateTest.js | 36 ++++---
 IntegrationTests/SyncMethodTest.js            | 14 +--
 IntegrationTests/TimersTest.js                | 44 +++++----
 IntegrationTests/WebSocketTest.js             | 63 ++++++------
 IntegrationTests/WebViewTest.js               | 52 ++++++----
 19 files changed, 342 insertions(+), 294 deletions(-)

diff --git a/IntegrationTests/AccessibilityManagerTest.js b/IntegrationTests/AccessibilityManagerTest.js
index 4287094d3759..41710be91e14 100644
--- a/IntegrationTests/AccessibilityManagerTest.js
+++ b/IntegrationTests/AccessibilityManagerTest.js
@@ -4,35 +4,33 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const { View } = ReactNative;
+const {View} = ReactNative;
 const RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
-const {
-  TestModule,
-  AccessibilityManager,
-} = ReactNative.NativeModules;
-
+const {TestModule, AccessibilityManager} = ReactNative.NativeModules;
 
 class AccessibilityManagerTest extends React.Component<{}> {
   componentDidMount() {
     AccessibilityManager.setAccessibilityContentSizeMultipliers({
-      'extraSmall': 1.0,
-      'small': 2.0,
-      'medium': 3.0,
-      'large': 4.0,
-      'extraLarge': 5.0,
-      'extraExtraLarge': 6.0,
-      'extraExtraExtraLarge': 7.0,
-      'accessibilityMedium': 8.0,
-      'accessibilityLarge': 9.0,
-      'accessibilityExtraLarge': 10.0,
-      'accessibilityExtraExtraLarge': 11.0,
-      'accessibilityExtraExtraExtraLarge': 12.0,
+      extraSmall: 1.0,
+      small: 2.0,
+      medium: 3.0,
+      large: 4.0,
+      extraLarge: 5.0,
+      extraExtraLarge: 6.0,
+      extraExtraExtraLarge: 7.0,
+      accessibilityMedium: 8.0,
+      accessibilityLarge: 9.0,
+      accessibilityExtraLarge: 10.0,
+      accessibilityExtraExtraLarge: 11.0,
+      accessibilityExtraExtraExtraLarge: 12.0,
     });
     RCTDeviceEventEmitter.addListener('didUpdateDimensions', update => {
       TestModule.markTestPassed(update.window.fontScale === 4.0);
diff --git a/IntegrationTests/AppEventsTest.js b/IntegrationTests/AppEventsTest.js
index af04819b38fd..9df430fea983 100644
--- a/IntegrationTests/AppEventsTest.js
+++ b/IntegrationTests/AppEventsTest.js
@@ -4,25 +4,22 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  NativeAppEventEmitter,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {NativeAppEventEmitter, StyleSheet, Text, View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 var deepDiffer = require('deepDiffer');
 
 var TEST_PAYLOAD = {foo: 'bar'};
 
-type AppEvent = { data: Object, ts: number, };
+type AppEvent = {data: Object, ts: number};
 type State = {
   sent: 'none' | AppEvent,
   received: 'none' | AppEvent,
@@ -43,7 +40,7 @@ class AppEventsTest extends React.Component<{}, State> {
     if (deepDiffer(event.data, TEST_PAYLOAD)) {
       throw new Error('Received wrong event: ' + JSON.stringify(event));
     }
-    var elapsed = (Date.now() - event.ts) + 'ms';
+    var elapsed = Date.now() - event.ts + 'ms';
     this.setState({received: event, elapsed}, () => {
       TestModule.markTestCompleted();
     });
@@ -52,9 +49,7 @@ class AppEventsTest extends React.Component<{}, State> {
   render() {
     return (
       <View style={styles.container}>
-        <Text>
-          {JSON.stringify(this.state, null, '  ')}
-        </Text>
+        <Text>{JSON.stringify(this.state, null, '  ')}</Text>
       </View>
     );
   }
diff --git a/IntegrationTests/AsyncStorageTest.js b/IntegrationTests/AsyncStorageTest.js
index 2d951dab3984..9245854e2e01 100644
--- a/IntegrationTests/AsyncStorageTest.js
+++ b/IntegrationTests/AsyncStorageTest.js
@@ -4,18 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  AsyncStorage,
-  Text,
-  View,
-} = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {AsyncStorage, Text, View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 var deepDiffer = require('deepDiffer');
 
@@ -26,31 +24,34 @@ var VAL_1 = 'val_1';
 var KEY_2 = 'key_2';
 var VAL_2 = 'val_2';
 var KEY_MERGE = 'key_merge';
-var VAL_MERGE_1 = {'foo': 1, 'bar': {'hoo': 1, 'boo': 1}, 'moo': {'a': 3}};
-var VAL_MERGE_2 = {'bar': {'hoo': 2}, 'baz': 2, 'moo': {'a': 3}};
-var VAL_MERGE_EXPECT =
-  {'foo': 1, 'bar': {'hoo': 2, 'boo': 1}, 'baz': 2, 'moo': {'a': 3}};
+var VAL_MERGE_1 = {foo: 1, bar: {hoo: 1, boo: 1}, moo: {a: 3}};
+var VAL_MERGE_2 = {bar: {hoo: 2}, baz: 2, moo: {a: 3}};
+var VAL_MERGE_EXPECT = {foo: 1, bar: {hoo: 2, boo: 1}, baz: 2, moo: {a: 3}};
 
 // setup in componentDidMount
-var done = (result : ?boolean) => {};
-var updateMessage = (message : string ) => {};
+var done = (result: ?boolean) => {};
+var updateMessage = (message: string) => {};
 
-function runTestCase(description : string, fn) {
+function runTestCase(description: string, fn) {
   updateMessage(description);
   fn();
 }
 
-function expectTrue(condition : boolean, message : string) {
+function expectTrue(condition: boolean, message: string) {
   if (!condition) {
     throw new Error(message);
   }
 }
 
-function expectEqual(lhs, rhs, testname : string) {
+function expectEqual(lhs, rhs, testname: string) {
   expectTrue(
     !deepDiffer(lhs, rhs),
-    'Error in test ' + testname + ': expected\n' + JSON.stringify(rhs) +
-      '\ngot\n' + JSON.stringify(lhs)
+    'Error in test ' +
+      testname +
+      ': expected\n' +
+      JSON.stringify(rhs) +
+      '\ngot\n' +
+      JSON.stringify(lhs),
   );
 }
 
@@ -58,11 +59,14 @@ function expectAsyncNoError(place, err) {
   if (err instanceof Error) {
     err = err.message;
   }
-  expectTrue(err === null, 'Unexpected error in ' + place + ': ' + JSON.stringify(err));
+  expectTrue(
+    err === null,
+    'Unexpected error in ' + place + ': ' + JSON.stringify(err),
+  );
 }
 
 function testSetAndGet() {
-  AsyncStorage.setItem(KEY_1, VAL_1, (err1) => {
+  AsyncStorage.setItem(KEY_1, VAL_1, err1 => {
     expectAsyncNoError('testSetAndGet/setItem', err1);
     AsyncStorage.getItem(KEY_1, (err2, result) => {
       expectAsyncNoError('testSetAndGet/getItem', err2);
@@ -83,8 +87,8 @@ function testMissingGet() {
 }
 
 function testSetTwice() {
-  AsyncStorage.setItem(KEY_1, VAL_1, ()=>{
-    AsyncStorage.setItem(KEY_1, VAL_1, ()=>{
+  AsyncStorage.setItem(KEY_1, VAL_1, () => {
+    AsyncStorage.setItem(KEY_1, VAL_1, () => {
       AsyncStorage.getItem(KEY_1, (err, result) => {
         expectAsyncNoError('testSetTwice/setItem', err);
         expectEqual(result, VAL_1, 'testSetTwice');
@@ -96,16 +100,16 @@ function testSetTwice() {
 }
 
 function testRemoveItem() {
-  AsyncStorage.setItem(KEY_1, VAL_1, ()=>{
-    AsyncStorage.setItem(KEY_2, VAL_2, ()=>{
+  AsyncStorage.setItem(KEY_1, VAL_1, () => {
+    AsyncStorage.setItem(KEY_2, VAL_2, () => {
       AsyncStorage.getAllKeys((err, result) => {
         expectAsyncNoError('testRemoveItem/getAllKeys', err);
         expectTrue(
           result.indexOf(KEY_1) >= 0 && result.indexOf(KEY_2) >= 0,
-          'Missing KEY_1 or KEY_2 in ' + '(' + result + ')'
+          'Missing KEY_1 or KEY_2 in ' + '(' + result + ')',
         );
         updateMessage('testRemoveItem - add two items');
-        AsyncStorage.removeItem(KEY_1, (err2) => {
+        AsyncStorage.removeItem(KEY_1, err2 => {
           expectAsyncNoError('testRemoveItem/removeItem', err2);
           updateMessage('delete successful ');
           AsyncStorage.getItem(KEY_1, (err3, result2) => {
@@ -113,17 +117,17 @@ function testRemoveItem() {
             expectEqual(
               result2,
               null,
-              'testRemoveItem: key_1 present after delete'
+              'testRemoveItem: key_1 present after delete',
             );
             updateMessage('key properly removed ');
             AsyncStorage.getAllKeys((err4, result3) => {
-             expectAsyncNoError('testRemoveItem/getAllKeys', err4);
-             expectTrue(
-               result3.indexOf(KEY_1) === -1,
-               'Unexpected: KEY_1 present in ' + result3
-             );
-             updateMessage('proper length returned.');
-             runTestCase('should merge values', testMerge);
+              expectAsyncNoError('testRemoveItem/getAllKeys', err4);
+              expectTrue(
+                result3.indexOf(KEY_1) === -1,
+                'Unexpected: KEY_1 present in ' + result3,
+              );
+              updateMessage('proper length returned.');
+              runTestCase('should merge values', testMerge);
             });
           });
         });
@@ -133,9 +137,9 @@ function testRemoveItem() {
 }
 
 function testMerge() {
-  AsyncStorage.setItem(KEY_MERGE, JSON.stringify(VAL_MERGE_1), (err1) => {
+  AsyncStorage.setItem(KEY_MERGE, JSON.stringify(VAL_MERGE_1), err1 => {
     expectAsyncNoError('testMerge/setItem', err1);
-    AsyncStorage.mergeItem(KEY_MERGE, JSON.stringify(VAL_MERGE_2), (err2) => {
+    AsyncStorage.mergeItem(KEY_MERGE, JSON.stringify(VAL_MERGE_2), err2 => {
       expectAsyncNoError('testMerge/mergeItem', err2);
       AsyncStorage.getItem(KEY_MERGE, (err3, result) => {
         expectAsyncNoError('testMerge/setItem', err3);
@@ -150,21 +154,23 @@ function testMerge() {
 function testOptimizedMultiGet() {
   let batch = [[KEY_1, VAL_1], [KEY_2, VAL_2]];
   let keys = batch.map(([key, value]) => key);
-  AsyncStorage.multiSet(batch, (err1) => {
+  AsyncStorage.multiSet(batch, err1 => {
     // yes, twice on purpose
-    [1, 2].forEach((i) => {
+    [1, 2].forEach(i => {
       expectAsyncNoError(`${i} testOptimizedMultiGet/multiSet`, err1);
       AsyncStorage.multiGet(keys, (err2, result) => {
         expectAsyncNoError(`${i} testOptimizedMultiGet/multiGet`, err2);
         expectEqual(result, batch, `${i} testOptimizedMultiGet multiGet`);
-        updateMessage('multiGet([key_1, key_2]) correctly returned ' + JSON.stringify(result));
+        updateMessage(
+          'multiGet([key_1, key_2]) correctly returned ' +
+            JSON.stringify(result),
+        );
         done();
       });
     });
   });
 }
 
-
 class AsyncStorageTest extends React.Component<{}, $FlowFixMeState> {
   state = {
     messages: 'Initializing...',
@@ -172,10 +178,11 @@ class AsyncStorageTest extends React.Component<{}, $FlowFixMeState> {
   };
 
   componentDidMount() {
-    done = () => this.setState({done: true}, () => {
-      TestModule.markTestCompleted();
-    });
-    updateMessage = (msg) => {
+    done = () =>
+      this.setState({done: true}, () => {
+        TestModule.markTestCompleted();
+      });
+    updateMessage = msg => {
       this.setState({messages: this.state.messages.concat('\n' + msg)});
       DEBUG && console.log(msg);
     };
@@ -186,11 +193,10 @@ class AsyncStorageTest extends React.Component<{}, $FlowFixMeState> {
     return (
       <View style={{backgroundColor: 'white', padding: 40}}>
         <Text>
-          {
-            /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This
+          {/* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This
              * comment suppresses an error found when Flow v0.54 was deployed.
              * To see the error delete this comment and run Flow. */
-            this.constructor.displayName + ': '}
+          this.constructor.displayName + ': '}
           {this.state.done ? 'Done' : 'Testing...'}
           {'\n\n' + this.state.messages}
         </Text>
diff --git a/IntegrationTests/ImageCachePolicyTest.js b/IntegrationTests/ImageCachePolicyTest.js
index a095b4ec9912..1c4429389cbb 100644
--- a/IntegrationTests/ImageCachePolicyTest.js
+++ b/IntegrationTests/ImageCachePolicyTest.js
@@ -4,19 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Image,
-  View,
-  Text,
-  StyleSheet,
-} = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {Image, View, Text, StyleSheet} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 /*
  * The reload and force-cache tests don't actually verify that the complete functionality.
@@ -30,22 +27,25 @@ var { TestModule } = ReactNative.NativeModules;
 
 const TESTS = ['only-if-cached', 'default', 'reload', 'force-cache'];
 
-type Props = {}
+type Props = {};
 type State = {
   'only-if-cached'?: boolean,
-  'default'?: boolean,
-  'reload'?: boolean,
+  default?: boolean,
+  reload?: boolean,
   'force-cache'?: boolean,
-}
+};
 
 class ImageCachePolicyTest extends React.Component<Props, $FlowFixMeState> {
-  state = {}
+  state = {};
 
   shouldComponentUpdate(nextProps: Props, nextState: State) {
     const results: Array<?boolean> = TESTS.map(x => nextState[x]);
 
     if (!results.includes(undefined)) {
-      const result: boolean = results.reduce((x,y) => x === y === true, true);
+      const result: boolean = results.reduce(
+        (x, y) => (x === y) === true,
+        true,
+      );
       TestModule.markTestPassed(result);
     }
 
@@ -60,38 +60,46 @@ class ImageCachePolicyTest extends React.Component<Props, $FlowFixMeState> {
     return (
       <View style={{flex: 1}}>
         <Text>Hello</Text>
-      <Image
-        source={{
-              uri: 'https://facebook.github.io/react-native/img/favicon.png?cacheBust=notinCache' + Date.now(),
-              cache: 'only-if-cached'
-            }}
-        onLoad={() => this.testComplete('only-if-cached', false)}
-        onError={() => this.testComplete('only-if-cached', true)}
-        style={styles.base}
-      />
         <Image
           source={{
-              uri: 'https://facebook.github.io/react-native/img/favicon.png?cacheBust=notinCache' + Date.now(),
-              cache: 'default'
-            }}
+            uri:
+              'https://facebook.github.io/react-native/img/favicon.png?cacheBust=notinCache' +
+              Date.now(),
+            cache: 'only-if-cached',
+          }}
+          onLoad={() => this.testComplete('only-if-cached', false)}
+          onError={() => this.testComplete('only-if-cached', true)}
+          style={styles.base}
+        />
+        <Image
+          source={{
+            uri:
+              'https://facebook.github.io/react-native/img/favicon.png?cacheBust=notinCache' +
+              Date.now(),
+            cache: 'default',
+          }}
           onLoad={() => this.testComplete('default', true)}
           onError={() => this.testComplete('default', false)}
           style={styles.base}
         />
         <Image
           source={{
-              uri: 'https://facebook.github.io/react-native/img/favicon.png?cacheBust=notinCache' + Date.now(),
-              cache: 'reload'
-            }}
+            uri:
+              'https://facebook.github.io/react-native/img/favicon.png?cacheBust=notinCache' +
+              Date.now(),
+            cache: 'reload',
+          }}
           onLoad={() => this.testComplete('reload', true)}
           onError={() => this.testComplete('reload', false)}
           style={styles.base}
         />
         <Image
           source={{
-              uri: 'https://facebook.github.io/react-native/img/favicon.png?cacheBust=notinCache' + Date.now(),
-              cache: 'force-cache'
-            }}
+            uri:
+              'https://facebook.github.io/react-native/img/favicon.png?cacheBust=notinCache' +
+              Date.now(),
+            cache: 'force-cache',
+          }}
           onLoad={() => this.testComplete('force-cache', true)}
           onError={() => this.testComplete('force-cache', false)}
           style={styles.base}
diff --git a/IntegrationTests/ImageSnapshotTest.js b/IntegrationTests/ImageSnapshotTest.js
index 3d024d569da6..5c74433a9d40 100644
--- a/IntegrationTests/ImageSnapshotTest.js
+++ b/IntegrationTests/ImageSnapshotTest.js
@@ -4,17 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Image,
-  View,
-} = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {Image, View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 class ImageSnapshotTest extends React.Component<{}> {
   componentDidMount() {
@@ -23,7 +22,7 @@ class ImageSnapshotTest extends React.Component<{}> {
     }
   }
 
-  done = (success : boolean) => {
+  done = (success: boolean) => {
     TestModule.markTestPassed(success);
   };
 
@@ -32,7 +31,8 @@ class ImageSnapshotTest extends React.Component<{}> {
       <Image
         source={require('./blue_square.png')}
         defaultSource={require('./red_square.png')}
-        onLoad={() => TestModule.verifySnapshot(this.done)} />
+        onLoad={() => TestModule.verifySnapshot(this.done)}
+      />
     );
   }
 }
diff --git a/IntegrationTests/IntegrationTestHarnessTest.js b/IntegrationTests/IntegrationTestHarnessTest.js
index 9b34065b8fd6..2a596d068b67 100644
--- a/IntegrationTests/IntegrationTestHarnessTest.js
+++ b/IntegrationTests/IntegrationTestHarnessTest.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
@@ -15,16 +17,16 @@ var requestAnimationFrame = require('fbjs/lib/requestAnimationFrame');
 var React = require('react');
 var PropTypes = require('prop-types');
 var ReactNative = require('react-native');
-var {
-  Text,
-  View,
-} = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {Text, View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
-class IntegrationTestHarnessTest extends React.Component<{
-  shouldThrow?: boolean,
-  waitOneFrame?: boolean,
-}, $FlowFixMeState> {
+class IntegrationTestHarnessTest extends React.Component<
+  {
+    shouldThrow?: boolean,
+    waitOneFrame?: boolean,
+  },
+  $FlowFixMeState,
+> {
   static propTypes = {
     shouldThrow: PropTypes.bool,
     waitOneFrame: PropTypes.bool,
@@ -60,11 +62,10 @@ class IntegrationTestHarnessTest extends React.Component<{
     return (
       <View style={{backgroundColor: 'white', padding: 40}}>
         <Text>
-          {
-            /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This
+          {/* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This
              * comment suppresses an error found when Flow v0.54 was deployed.
              * To see the error delete this comment and run Flow. */
-            this.constructor.displayName + ': '}
+          this.constructor.displayName + ': '}
           {this.state.done ? 'Done' : 'Testing...'}
         </Text>
       </View>
diff --git a/IntegrationTests/IntegrationTestsApp.js b/IntegrationTests/IntegrationTestsApp.js
index 62f6fa83057b..c59f15b3d73a 100644
--- a/IntegrationTests/IntegrationTestsApp.js
+++ b/IntegrationTests/IntegrationTestsApp.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -40,7 +42,7 @@ TESTS.forEach(
   /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
    * suppresses an error found when Flow v0.54 was deployed. To see the error
    * delete this comment and run Flow. */
-  (test) => AppRegistry.registerComponent(test.displayName, () => test)
+  test => AppRegistry.registerComponent(test.displayName, () => test),
 );
 
 // Modules required for integration tests
@@ -68,20 +70,18 @@ class IntegrationTestsApp extends React.Component<{}, $FlowFixMeState> {
       <View style={styles.container}>
         <Text style={styles.row}>
           Click on a test to run it in this shell for easier debugging and
-          development.  Run all tests in the testing environment with cmd+U in
+          development. Run all tests in the testing environment with cmd+U in
           Xcode.
         </Text>
         <View style={styles.separator} />
         <ScrollView>
-          {TESTS.map((test) => [
+          {TESTS.map(test => [
             <TouchableOpacity
               onPress={() => this.setState({test})}
               style={styles.row}>
-              <Text style={styles.testName}>
-                {test.displayName}
-              </Text>
+              <Text style={styles.testName}>{test.displayName}</Text>
             </TouchableOpacity>,
-            <View style={styles.separator} />
+            <View style={styles.separator} />,
           ])}
         </ScrollView>
       </View>
diff --git a/IntegrationTests/LayoutEventsTest.js b/IntegrationTests/LayoutEventsTest.js
index 31dd1839c86c..b9183a34e92e 100644
--- a/IntegrationTests/LayoutEventsTest.js
+++ b/IntegrationTests/LayoutEventsTest.js
@@ -4,21 +4,17 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var createReactClass = require('create-react-class');
 var ReactNative = require('react-native');
-var {
-  Image,
-  LayoutAnimation,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {Image, LayoutAnimation, StyleSheet, Text, View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 var deepDiffer = require('deepDiffer');
 
@@ -55,27 +51,23 @@ var LayoutEventsTest = createReactClass({
   },
   animateViewLayout: function() {
     debug('animateViewLayout invoked');
-    LayoutAnimation.configureNext(
-      LayoutAnimation.Presets.spring,
-      () => {
-        debug('animateViewLayout done');
-        this.checkLayout(this.addWrapText);
-      }
-    );
+    LayoutAnimation.configureNext(LayoutAnimation.Presets.spring, () => {
+      debug('animateViewLayout done');
+      this.checkLayout(this.addWrapText);
+    });
     this.setState({viewStyle: {margin: 60}});
   },
   addWrapText: function() {
     debug('addWrapText invoked');
     this.setState(
       {extraText: '  And a bunch more text to wrap around a few lines.'},
-      () => this.checkLayout(this.changeContainer)
+      () => this.checkLayout(this.changeContainer),
     );
   },
   changeContainer: function() {
     debug('changeContainer invoked');
-    this.setState(
-      {containerStyle: {width: 280}},
-      () => this.checkLayout(TestModule.markTestCompleted)
+    this.setState({containerStyle: {width: 280}}, () =>
+      this.checkLayout(TestModule.markTestCompleted),
     );
   },
   checkLayout: function(next?: ?Function) {
@@ -103,8 +95,9 @@ var LayoutEventsTest = createReactClass({
     if (deepDiffer(measured, onLayout)) {
       var data = {measured, onLayout};
       throw new Error(
-        node + ' onLayout mismatch with measure ' +
-          JSON.stringify(data, null, '  ')
+        node +
+          ' onLayout mismatch with measure ' +
+          JSON.stringify(data, null, '  '),
       );
     }
   },
@@ -145,7 +138,7 @@ var LayoutEventsTest = createReactClass({
         </View>
       </View>
     );
-  }
+  },
 });
 
 var styles = StyleSheet.create({
diff --git a/IntegrationTests/LoggingTestModule.js b/IntegrationTests/LoggingTestModule.js
index df2b0e59b524..76a4fbccd712 100644
--- a/IntegrationTests/LoggingTestModule.js
+++ b/IntegrationTests/LoggingTestModule.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var BatchedBridge = require('BatchedBridge');
@@ -16,7 +18,7 @@ var LoggingTestModule = {
   logToConsole: function(str) {
     console.log(str);
   },
-  logToConsoleAfterWait: function(str,timeout_ms) {
+  logToConsoleAfterWait: function(str, timeout_ms) {
     setTimeout(function() {
       console.log(str);
     }, timeout_ms);
@@ -32,12 +34,9 @@ var LoggingTestModule = {
   },
   throwError: function(str) {
     throw new Error(str);
-  }
+  },
 };
 
-BatchedBridge.registerCallableModule(
-  'LoggingTestModule',
-  LoggingTestModule
-);
+BatchedBridge.registerCallableModule('LoggingTestModule', LoggingTestModule);
 
 module.exports = LoggingTestModule;
diff --git a/IntegrationTests/PromiseTest.js b/IntegrationTests/PromiseTest.js
index 21005576d678..3e919a86712b 100644
--- a/IntegrationTests/PromiseTest.js
+++ b/IntegrationTests/PromiseTest.js
@@ -4,14 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var { View } = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 class PromiseTest extends React.Component<{}> {
   shouldResolve = false;
@@ -25,24 +27,26 @@ class PromiseTest extends React.Component<{}> {
       this.testShouldReject(),
       this.testShouldSucceedAsync(),
       this.testShouldThrowAsync(),
-    ]).then(() => TestModule.markTestPassed(
-      this.shouldResolve && this.shouldReject &&
-      this.shouldSucceedAsync && this.shouldThrowAsync
-    ));
+    ]).then(() =>
+      TestModule.markTestPassed(
+        this.shouldResolve &&
+          this.shouldReject &&
+          this.shouldSucceedAsync &&
+          this.shouldThrowAsync,
+      ),
+    );
   }
 
   testShouldResolve = () => {
-    return TestModule
-      .shouldResolve()
-      .then(() => this.shouldResolve = true)
-      .catch(() => this.shouldResolve = false);
+    return TestModule.shouldResolve()
+      .then(() => (this.shouldResolve = true))
+      .catch(() => (this.shouldResolve = false));
   };
 
   testShouldReject = () => {
-    return TestModule
-      .shouldReject()
-      .then(() => this.shouldReject = false)
-      .catch(() => this.shouldReject = true);
+    return TestModule.shouldReject()
+      .then(() => (this.shouldReject = false))
+      .catch(() => (this.shouldReject = true));
   };
 
   testShouldSucceedAsync = async (): Promise<any> => {
diff --git a/IntegrationTests/PropertiesUpdateTest.js b/IntegrationTests/PropertiesUpdateTest.js
index 3d93d9d0ac23..e2c16f3a6325 100644
--- a/IntegrationTests/PropertiesUpdateTest.js
+++ b/IntegrationTests/PropertiesUpdateTest.js
@@ -3,25 +3,24 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  View,
-} = ReactNative;
+var {View} = ReactNative;
 
-var { TestModule } = ReactNative.NativeModules;
+var {TestModule} = ReactNative.NativeModules;
 
 class PropertiesUpdateTest extends React.Component {
   render() {
     if (this.props.markTestPassed) {
       TestModule.markTestPassed(true);
     }
-    return (
-      <View/>
-    );
+    return <View />;
   }
 }
 
diff --git a/IntegrationTests/RCTRootViewIntegrationTestApp.js b/IntegrationTests/RCTRootViewIntegrationTestApp.js
index aef56f975992..8cb499f3677f 100644
--- a/IntegrationTests/RCTRootViewIntegrationTestApp.js
+++ b/IntegrationTests/RCTRootViewIntegrationTestApp.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 require('regenerator-runtime/runtime');
@@ -28,8 +30,8 @@ var TESTS = [
   require('./SizeFlexibilityUpdateTest'),
 ];
 
-TESTS.forEach(
-  (test) => AppRegistry.registerComponent(test.displayName, () => test)
+TESTS.forEach(test =>
+  AppRegistry.registerComponent(test.displayName, () => test),
 );
 
 class RCTRootViewIntegrationTestApp extends React.Component {
@@ -49,20 +51,18 @@ class RCTRootViewIntegrationTestApp extends React.Component {
       <View style={styles.container}>
         <Text style={styles.row}>
           Click on a test to run it in this shell for easier debugging and
-          development.  Run all tests in the testing environment with cmd+U in
+          development. Run all tests in the testing environment with cmd+U in
           Xcode.
         </Text>
         <View style={styles.separator} />
         <ScrollView>
-          {TESTS.map((test) => [
+          {TESTS.map(test => [
             <TouchableOpacity
               onPress={() => this.setState({test})}
               style={styles.row}>
-              <Text style={styles.testName}>
-                {test.displayName}
-              </Text>
+              <Text style={styles.testName}>{test.displayName}</Text>
             </TouchableOpacity>,
-            <View style={styles.separator} />
+            <View style={styles.separator} />,
           ])}
         </ScrollView>
       </View>
@@ -88,4 +88,7 @@ var styles = StyleSheet.create({
   },
 });
 
-AppRegistry.registerComponent('RCTRootViewIntegrationTestApp', () => RCTRootViewIntegrationTestApp);
+AppRegistry.registerComponent(
+  'RCTRootViewIntegrationTestApp',
+  () => RCTRootViewIntegrationTestApp,
+);
diff --git a/IntegrationTests/ReactContentSizeUpdateTest.js b/IntegrationTests/ReactContentSizeUpdateTest.js
index dda42b4df9c8..1306f8d7aa98 100644
--- a/IntegrationTests/ReactContentSizeUpdateTest.js
+++ b/IntegrationTests/ReactContentSizeUpdateTest.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
@@ -13,9 +16,9 @@ var RCTNativeAppEventEmitter = require('RCTNativeAppEventEmitter');
 var Subscribable = require('Subscribable');
 var TimerMixin = require('react-timer-mixin');
 
-var { View } = ReactNative;
+var {View} = ReactNative;
 
-var { TestModule } = ReactNative.NativeModules;
+var {TestModule} = ReactNative.NativeModules;
 
 var reactViewWidth = 101;
 var reactViewHeight = 102;
@@ -24,14 +27,13 @@ var newReactViewHeight = 202;
 
 var ReactContentSizeUpdateTest = createReactClass({
   displayName: 'ReactContentSizeUpdateTest',
-  mixins: [Subscribable.Mixin,
-           TimerMixin],
+  mixins: [Subscribable.Mixin, TimerMixin],
 
   UNSAFE_componentWillMount: function() {
     this.addListenerOn(
       RCTNativeAppEventEmitter,
       'rootViewDidChangeIntrinsicSize',
-      this.rootViewDidChangeIntrinsicSize
+      this.rootViewDidChangeIntrinsicSize,
     );
   },
 
@@ -50,23 +52,25 @@ var ReactContentSizeUpdateTest = createReactClass({
   },
 
   componentDidMount: function() {
-    this.setTimeout(
-      () => { this.updateViewSize(); },
-      1000
-    );
+    this.setTimeout(() => {
+      this.updateViewSize();
+    }, 1000);
   },
 
   rootViewDidChangeIntrinsicSize: function(intrinsicSize) {
-    if (intrinsicSize.height === newReactViewHeight && intrinsicSize.width === newReactViewWidth) {
+    if (
+      intrinsicSize.height === newReactViewHeight &&
+      intrinsicSize.width === newReactViewWidth
+    ) {
       TestModule.markTestPassed(true);
     }
   },
 
   render() {
     return (
-      <View style={{'height':this.state.height, 'width':this.state.width}}/>
+      <View style={{height: this.state.height, width: this.state.width}} />
     );
-  }
+  },
 });
 
 ReactContentSizeUpdateTest.displayName = 'ReactContentSizeUpdateTest';
diff --git a/IntegrationTests/SimpleSnapshotTest.js b/IntegrationTests/SimpleSnapshotTest.js
index dd8bf9ac8731..ea32c4a9a912 100644
--- a/IntegrationTests/SimpleSnapshotTest.js
+++ b/IntegrationTests/SimpleSnapshotTest.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -15,11 +17,8 @@ var ReactNative = require('react-native');
  * run Flow. */
 var requestAnimationFrame = require('fbjs/lib/requestAnimationFrame');
 
-var {
-  StyleSheet,
-  View,
-} = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {StyleSheet, View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 class SimpleSnapshotTest extends React.Component<{}> {
   componentDidMount() {
@@ -29,7 +28,7 @@ class SimpleSnapshotTest extends React.Component<{}> {
     requestAnimationFrame(() => TestModule.verifySnapshot(this.done));
   }
 
-  done = (success : boolean) => {
+  done = (success: boolean) => {
     TestModule.markTestPassed(success);
   };
 
diff --git a/IntegrationTests/SizeFlexibilityUpdateTest.js b/IntegrationTests/SizeFlexibilityUpdateTest.js
index ce0be9e6e222..5f885ddb7bd7 100644
--- a/IntegrationTests/SizeFlexibilityUpdateTest.js
+++ b/IntegrationTests/SizeFlexibilityUpdateTest.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
@@ -11,9 +14,9 @@ var createReactClass = require('create-react-class');
 var ReactNative = require('react-native');
 var RCTNativeAppEventEmitter = require('RCTNativeAppEventEmitter');
 var Subscribable = require('Subscribable');
-var { View } = ReactNative;
+var {View} = ReactNative;
 
-var { TestModule } = ReactNative.NativeModules;
+var {TestModule} = ReactNative.NativeModules;
 
 var reactViewWidth = 111;
 var reactViewHeight = 222;
@@ -28,7 +31,7 @@ var SizeFlexibilityUpdateTest = createReactClass({
     this.addListenerOn(
       RCTNativeAppEventEmitter,
       'rootViewDidChangeIntrinsicSize',
-      this.rootViewDidChangeIntrinsicSize
+      this.rootViewDidChangeIntrinsicSize,
     );
   },
 
@@ -38,7 +41,6 @@ var SizeFlexibilityUpdateTest = createReactClass({
   },
 
   rootViewDidChangeIntrinsicSize: function(intrinsicSize) {
-
     if (finalState) {
       // If a test reaches its final state, it is not expected to do anything more
       TestModule.markTestPassed(false);
@@ -46,25 +48,37 @@ var SizeFlexibilityUpdateTest = createReactClass({
     }
 
     if (this.props.both) {
-      if (intrinsicSize.width === reactViewWidth && intrinsicSize.height === reactViewHeight) {
+      if (
+        intrinsicSize.width === reactViewWidth &&
+        intrinsicSize.height === reactViewHeight
+      ) {
         this.markPassed();
         return;
       }
     }
     if (this.props.height) {
-      if (intrinsicSize.width !== reactViewWidth && intrinsicSize.height === reactViewHeight) {
+      if (
+        intrinsicSize.width !== reactViewWidth &&
+        intrinsicSize.height === reactViewHeight
+      ) {
         this.markPassed();
         return;
       }
     }
     if (this.props.width) {
-      if (intrinsicSize.width === reactViewWidth && intrinsicSize.height !== reactViewHeight) {
+      if (
+        intrinsicSize.width === reactViewWidth &&
+        intrinsicSize.height !== reactViewHeight
+      ) {
         this.markPassed();
         return;
       }
     }
     if (this.props.none) {
-      if (intrinsicSize.width !== reactViewWidth && intrinsicSize.height !== reactViewHeight) {
+      if (
+        intrinsicSize.width !== reactViewWidth &&
+        intrinsicSize.height !== reactViewHeight
+      ) {
         this.markPassed();
         return;
       }
@@ -72,10 +86,8 @@ var SizeFlexibilityUpdateTest = createReactClass({
   },
 
   render() {
-    return (
-      <View style={{'height':reactViewHeight, 'width':reactViewWidth}}/>
-    );
-  }
+    return <View style={{height: reactViewHeight, width: reactViewWidth}} />;
+  },
 });
 
 SizeFlexibilityUpdateTest.displayName = 'SizeFlexibilityUpdateTest';
diff --git a/IntegrationTests/SyncMethodTest.js b/IntegrationTests/SyncMethodTest.js
index f61f52b36106..eca1df986ba3 100644
--- a/IntegrationTests/SyncMethodTest.js
+++ b/IntegrationTests/SyncMethodTest.js
@@ -4,23 +4,23 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var { View } = ReactNative;
-
-const {
-  TestModule,
-  RNTesterTestModule,
-} = ReactNative.NativeModules;
+var {View} = ReactNative;
 
+const {TestModule, RNTesterTestModule} = ReactNative.NativeModules;
 
 class SyncMethodTest extends React.Component<{}> {
   componentDidMount() {
-    if (RNTesterTestModule.echoString('test string value') !== 'test string value') {
+    if (
+      RNTesterTestModule.echoString('test string value') !== 'test string value'
+    ) {
       throw new Error('Something wrong with sync method export');
     }
     if (RNTesterTestModule.methodThatReturnsNil() != null) {
diff --git a/IntegrationTests/TimersTest.js b/IntegrationTests/TimersTest.js
index f40742c9a8b0..86e1a962175c 100644
--- a/IntegrationTests/TimersTest.js
+++ b/IntegrationTests/TimersTest.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -16,12 +18,8 @@ var ReactNative = require('react-native');
  * run Flow. */
 var TimerMixin = require('react-timer-mixin');
 
-var {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
-var { TestModule  } = ReactNative.NativeModules;
+var {StyleSheet, Text, View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 var TimersTest = createReactClass({
   displayName: 'TimersTest',
@@ -91,7 +89,7 @@ var TimersTest = createReactClass({
     fails.push(this.setTimeout(() => this._fail('testClearMulti-4'), 0));
     fails.push(this.setTimeout(() => this._fail('testClearMulti-5'), 10));
 
-    fails.forEach((timeout) => this.clearTimeout(timeout));
+    fails.forEach(timeout => this.clearTimeout(timeout));
     this.setTimeout(() => this.clearTimeout(delayClear), 20);
 
     this.setTimeout(this.testOrdering, 50);
@@ -102,22 +100,32 @@ var TimersTest = createReactClass({
     var fail0;
     this.setImmediate(() => this.clearTimeout(fail0));
     fail0 = this.setTimeout(
-      () => this._fail('testOrdering-t0, setImmediate should happen before ' +
-        'setTimeout 0'),
-      0
+      () =>
+        this._fail(
+          'testOrdering-t0, setImmediate should happen before ' +
+            'setTimeout 0',
+        ),
+      0,
     );
     var failAnim; // This should fail without the t=0 fastpath feature.
     this.setTimeout(() => this.cancelAnimationFrame(failAnim), 0);
-    failAnim = this.requestAnimationFrame(
-      () => this._fail('testOrdering-Anim, setTimeout 0 should happen before ' +
-        'requestAnimationFrame')
+    failAnim = this.requestAnimationFrame(() =>
+      this._fail(
+        'testOrdering-Anim, setTimeout 0 should happen before ' +
+          'requestAnimationFrame',
+      ),
     );
     var fail25;
-    this.setTimeout(() => { this.clearTimeout(fail25); }, 20);
+    this.setTimeout(() => {
+      this.clearTimeout(fail25);
+    }, 20);
     fail25 = this.setTimeout(
-      () => this._fail('testOrdering-t25, setTimeout 20 should happen before ' +
-        'setTimeout 25'),
-      25
+      () =>
+        this._fail(
+          'testOrdering-t25, setTimeout 20 should happen before ' +
+            'setTimeout 25',
+        ),
+      25,
     );
     this.setTimeout(this.done, 50);
   },
@@ -152,7 +160,7 @@ var TimersTest = createReactClass({
     this.setState({count: this.state.count + 1});
   },
 
-  _fail(caller : string) : void {
+  _fail(caller: string): void {
     throw new Error('_fail called by ' + caller);
   },
 });
diff --git a/IntegrationTests/WebSocketTest.js b/IntegrationTests/WebSocketTest.js
index de8428f79e6a..33d6b2500c5d 100644
--- a/IntegrationTests/WebSocketTest.js
+++ b/IntegrationTests/WebSocketTest.js
@@ -4,23 +4,20 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var { View } = ReactNative;
-var { TestModule } = ReactNative.NativeModules;
+var {View} = ReactNative;
+var {TestModule} = ReactNative.NativeModules;
 
 const DEFAULT_WS_URL = 'ws://localhost:5555/';
 
-const WS_EVENTS = [
-  'close',
-  'error',
-  'message',
-  'open',
-];
+const WS_EVENTS = ['close', 'error', 'message', 'open'];
 const WS_STATES = [
   /* 0 */ 'CONNECTING',
   /* 1 */ 'OPEN',
@@ -29,14 +26,14 @@ const WS_STATES = [
 ];
 
 type State = {
-  url: string;
-  fetchStatus: ?string;
-  socket: ?WebSocket;
-  socketState: ?number;
-  lastSocketEvent: ?string;
-  lastMessage: ?string | ?ArrayBuffer;
-  testMessage: string;
-  testExpectedResponse: string;
+  url: string,
+  fetchStatus: ?string,
+  socket: ?WebSocket,
+  socketState: ?number,
+  lastSocketEvent: ?string,
+  lastMessage: ?string | ?ArrayBuffer,
+  testMessage: string,
+  testExpectedResponse: string,
 };
 
 class WebSocketTest extends React.Component<{}, State> {
@@ -48,13 +45,13 @@ class WebSocketTest extends React.Component<{}, State> {
     lastSocketEvent: null,
     lastMessage: null,
     testMessage: 'testMessage',
-    testExpectedResponse: 'testMessage_response'
+    testExpectedResponse: 'testMessage_response',
   };
 
   _waitFor = (condition: any, timeout: any, callback: any) => {
     var remaining = timeout;
     var t;
-    var timeoutFunction =  function() {
+    var timeoutFunction = function() {
       if (condition()) {
         callback(true);
         return;
@@ -63,11 +60,11 @@ class WebSocketTest extends React.Component<{}, State> {
       if (remaining === 0) {
         callback(false);
       } else {
-        t = setTimeout(timeoutFunction,1000);
+        t = setTimeout(timeoutFunction, 1000);
       }
     };
-    t = setTimeout(timeoutFunction,1000);
-  }
+    t = setTimeout(timeoutFunction, 1000);
+  };
 
   _connect = () => {
     const socket = new WebSocket(this.state.url);
@@ -80,11 +77,11 @@ class WebSocketTest extends React.Component<{}, State> {
 
   _socketIsConnected = () => {
     return this.state.socketState === 1; //'OPEN'
-  }
+  };
 
   _socketIsDisconnected = () => {
     return this.state.socketState === 3; //'CLOSED'
-  }
+  };
 
   _disconnect = () => {
     if (!this.state.socket) {
@@ -116,7 +113,7 @@ class WebSocketTest extends React.Component<{}, State> {
   };
 
   _receivedTestExpectedResponse = () => {
-    return (this.state.lastMessage === this.state.testExpectedResponse);
+    return this.state.lastMessage === this.state.testExpectedResponse;
   };
 
   componentDidMount() {
@@ -126,34 +123,40 @@ class WebSocketTest extends React.Component<{}, State> {
   testConnect = () => {
     var component = this;
     component._connect();
-    component._waitFor(component._socketIsConnected, 5, function(connectSucceeded) {
+    component._waitFor(component._socketIsConnected, 5, function(
+      connectSucceeded,
+    ) {
       if (!connectSucceeded) {
         TestModule.markTestPassed(false);
         return;
       }
       component.testSendAndReceive();
     });
-  }
+  };
 
   testSendAndReceive = () => {
     var component = this;
     component._sendTestMessage();
-    component._waitFor(component._receivedTestExpectedResponse, 5, function(messageReceived) {
+    component._waitFor(component._receivedTestExpectedResponse, 5, function(
+      messageReceived,
+    ) {
       if (!messageReceived) {
         TestModule.markTestPassed(false);
         return;
       }
       component.testDisconnect();
     });
-  }
+  };
 
   testDisconnect = () => {
     var component = this;
     component._disconnect();
-    component._waitFor(component._socketIsDisconnected, 5, function(disconnectSucceeded) {
+    component._waitFor(component._socketIsDisconnected, 5, function(
+      disconnectSucceeded,
+    ) {
       TestModule.markTestPassed(disconnectSucceeded);
     });
-  }
+  };
 
   render(): React.Node {
     return <View />;
diff --git a/IntegrationTests/WebViewTest.js b/IntegrationTests/WebViewTest.js
index 818b4e980216..47b4544cda88 100644
--- a/IntegrationTests/WebViewTest.js
+++ b/IntegrationTests/WebViewTest.js
@@ -4,52 +4,68 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  WebView,
-} = ReactNative;
+var {WebView} = ReactNative;
 
-var { TestModule } = ReactNative.NativeModules;
+var {TestModule} = ReactNative.NativeModules;
 
 class WebViewTest extends React.Component {
-
   render() {
     var firstMessageReceived = false;
     var secondMessageReceived = false;
     function processMessage(e) {
       var message = e.nativeEvent.data;
-      if (message === 'First') {firstMessageReceived = true;}
-      if (message === 'Second') {secondMessageReceived = true;}
+      if (message === 'First') {
+        firstMessageReceived = true;
+      }
+      if (message === 'Second') {
+        secondMessageReceived = true;
+      }
 
       // got both messages
-      if (firstMessageReceived && secondMessageReceived) {TestModule.markTestPassed(true);}
+      if (firstMessageReceived && secondMessageReceived) {
+        TestModule.markTestPassed(true);
+      }
       // wait for next message
-      else if (firstMessageReceived && !secondMessageReceived) {return;}
+      else if (firstMessageReceived && !secondMessageReceived) {
+        return;
+      }
       // first message got lost
-      else if (!firstMessageReceived && secondMessageReceived) {throw new Error('First message got lost');}
+      else if (!firstMessageReceived && secondMessageReceived) {
+        throw new Error('First message got lost');
+      }
     }
-    var html = 'Hello world'
-      + '<script>'
-      + "window.setTimeout(function(){window.postMessage('First'); window.postMessage('Second')}, 0)"
-      + '</script>';
+    var html =
+      'Hello world' +
+      '<script>' +
+      "window.setTimeout(function(){window.postMessage('First'); window.postMessage('Second')}, 0)" +
+      '</script>';
 
     // fail if messages didn't get through;
-    window.setTimeout(function() { throw new Error(firstMessageReceived ? 'Both messages got lost' : 'Second message got lost');}, 10000);
+    window.setTimeout(function() {
+      throw new Error(
+        firstMessageReceived
+          ? 'Both messages got lost'
+          : 'Second message got lost',
+      );
+    }, 10000);
 
     var source = {
       html: html,
-      };
+    };
 
     return (
       <WebView
         source={source}
-        onMessage = {processMessage}
+        onMessage={processMessage}
         originWhitelist={['about:blank']}
-        />
+      />
     );
   }
 }

From cd7c91f35d4b0d7e2a25dc0677bf064b7477d9ac Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Thu, 10 May 2018 19:06:39 -0700
Subject: [PATCH 0503/1109] Convert react-native-github/Libraries to let/const

Reviewed By: sahrens

Differential Revision: D7961763

fbshipit-source-id: ff7dd1d2c7101c8019e0b4f844d8c377b4d13a13
---
 Libraries/BatchedBridge/MessageQueue.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/BatchedBridge/MessageQueue.js b/Libraries/BatchedBridge/MessageQueue.js
index a5208d81b70d..2d22b90a44c3 100644
--- a/Libraries/BatchedBridge/MessageQueue.js
+++ b/Libraries/BatchedBridge/MessageQueue.js
@@ -249,7 +249,7 @@ class MessageQueue {
       global.nativeFlushQueueImmediate &&
       now - this._lastFlush >= MIN_TIME_BETWEEN_FLUSHES_MS
     ) {
-      var queue = this._queue;
+      const queue = this._queue;
       this._queue = [[], [], [], this._callID];
       this._lastFlush = now;
       global.nativeFlushQueueImmediate(queue);

From 1e2de712907e5fe0d17648f0ff5c81d4384ca85b Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Thu, 10 May 2018 19:06:41 -0700
Subject: [PATCH 0504/1109] Allow trailing commas

Summary: This was previously set to disallow trailing commas on function arguments which prettier would add. Since we are dropping support for node < 8, we can now change this setting to require trailing commas everywhere and be consistent with the prettier config at Facebook.

Reviewed By: hramos

Differential Revision: D7961098

fbshipit-source-id: fbe49513183a8c8e027bb05467a767235dbfb15b
---
 .eslintrc | 29 +----------------------------
 1 file changed, 1 insertion(+), 28 deletions(-)

diff --git a/.eslintrc b/.eslintrc
index 9887d1c6d8db..395f7d824349 100644
--- a/.eslintrc
+++ b/.eslintrc
@@ -57,18 +57,7 @@
 
   "rules": {
   // General
-
-    // This must be disallowed in this repo because the minimum supported
-    // version of node is 4 which doesn't support trailing commas.
-    // Once the minimum supported version is 8 or greater this can be changed
-    "comma-dangle": [2, {            // disallow trailing commas in object literals
-        "arrays": "ignore",
-        "objects": "ignore",
-        "imports": "ignore",
-        "exports": "ignore",
-        "functions": "never"
-    }],
-
+    "comma-dangle": [1, "always-multiline"], // allow or disallow trailing commas
     "no-cond-assign": 1,             // disallow assignment in conditional expressions
     "no-console": 0,                 // disallow use of console (off by default in the node environment)
     "no-const-assign": 2,            // disallow assignment to const-declared variables
@@ -267,27 +256,11 @@
   },
 
   "overrides": [
-    {
-      "files": [
-        "Libraries/**/*.js",
-        "RNTester/**/*.js",
-        "jest/**/*.js",
-      ],
-      "rules": {
-        // These folders currently run through babel and don't need to be
-        // compatible with node 4
-        "comma-dangle": 0,
-      },
-    },
     {
       "files": [
         "local-cli/**/*.js",
       ],
       "rules": {
-        // This folder currently runs through babel and doesn't need to be
-        // compatible with node 4
-        "comma-dangle": 0,
-
         "lint/extra-arrow-initializer": 0,
         "no-alert": 0,
         "no-console-disallow": 0,

From d01ab66b47a173a62eef6261e2415f0619fefcbb Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Thu, 10 May 2018 19:06:46 -0700
Subject: [PATCH 0505/1109] Prettier React Native Libraries

Reviewed By: sahrens

Differential Revision: D7961488

fbshipit-source-id: 05f9b8b0b91ae77f9040a5321ccc18f7c3c1ce9a
---
 Libraries/ART/ARTSerializablePath.js          |  19 +-
 Libraries/ART/ReactNativeART.js               | 119 ++---
 Libraries/Alert/Alert.js                      |  32 +-
 Libraries/Alert/AlertIOS.js                   |  76 +--
 Libraries/Alert/RCTAlertManager.android.js    |  11 +-
 Libraries/Alert/RCTAlertManager.ios.js        |   2 +
 Libraries/Animated/release/gulpfile.js        |  84 ++--
 Libraries/Animated/src/AnimatedWeb.js         |   2 +
 Libraries/Animated/src/Easing.js              |  24 +-
 Libraries/Animated/src/SpringConfig.js        |  19 +-
 .../Animated/src/__tests__/Animated-test.js   | 185 ++++----
 .../src/__tests__/AnimatedNative-test.js      | 414 ++++++++++------
 .../Animated/src/__tests__/Easing-test.js     | 376 ++++++++++++++-
 .../src/__tests__/Interpolation-test.js       |   2 +
 .../Animated/src/__tests__/bezier-test.js     |  25 +-
 Libraries/Animated/src/bezier.js              | 210 ++++----
 .../src/polyfills/InteractionManager.js       |   4 +-
 Libraries/Animated/src/polyfills/Set.js       |   2 +
 .../Animated/src/polyfills/flattenStyle.js    |   3 +
 Libraries/AppState/AppState.js                |  67 ++-
 Libraries/BatchedBridge/BatchedBridge.js      |   2 +
 Libraries/BatchedBridge/NativeModules.js      | 145 +++---
 .../__mocks__/MessageQueueTestConfig.js       |   7 +-
 .../__mocks__/MessageQueueTestModule.js       |   8 +-
 .../__tests__/NativeModules-test.js           |  19 +-
 Libraries/BugReporting/BugReporting.js        |  52 +-
 Libraries/BugReporting/dumpReactTree.js       |   4 +-
 Libraries/BugReporting/getReactData.js        |  21 +-
 Libraries/CameraRoll/ImagePickerIOS.js        |  26 +-
 Libraries/Color/normalizeColor.js             |  89 ++--
 .../AccessibilityInfo.android.js              |  22 +-
 .../AccessibilityInfo.ios.js                  |  38 +-
 .../ActivityIndicator/ActivityIndicator.js    |  10 +-
 .../Components/AppleTV/TVEventHandler.js      |  18 +-
 .../Components/AppleTV/TVViewPropTypes.js     | 103 ++--
 Libraries/Components/Button.js                |  16 +-
 Libraries/Components/Clipboard/Clipboard.js   |   4 +-
 .../DatePicker/DatePickerIOS.android.js       |   7 +-
 .../DatePicker/DatePickerIOS.ios.js           |  26 +-
 .../DatePickerAndroid.android.js              |  10 +-
 .../DatePickerAndroid.ios.js                  |   4 +-
 .../DrawerLayoutAndroid.android.js            |  98 ++--
 .../DrawerAndroid/DrawerLayoutAndroid.ios.js  |   2 +
 Libraries/Components/Keyboard/Keyboard.js     |   2 +
 .../Keyboard/KeyboardAvoidingView.js          |  50 +-
 Libraries/Components/LazyRenderer.js          |   6 +-
 .../MaskedView/MaskedViewIOS.android.js       |   2 +
 .../MaskedView/MaskedViewIOS.ios.js           |   7 +-
 .../Navigation/NavigatorIOS.android.js        |   2 +
 .../Components/Navigation/NavigatorIOS.ios.js |  65 ++-
 Libraries/Components/Picker/Picker.js         | 209 ++++----
 .../Picker/PickerAndroid.android.js           |  50 +-
 .../Components/Picker/PickerAndroid.ios.js    |   2 +
 .../Components/Picker/PickerIOS.android.js    |   3 +
 Libraries/Components/Picker/PickerIOS.ios.js  |  41 +-
 .../ProgressBarAndroid.ios.js                 |   2 +
 .../ProgressViewIOS.android.js                |   4 +-
 .../ProgressViewIOS/ProgressViewIOS.ios.js    |   6 +-
 .../RefreshControl/RefreshControl.js          |  19 +-
 .../__mocks__/RefreshControlMock.js           |   2 +
 .../SafeAreaView/SafeAreaView.android.js      |   2 +
 Libraries/Components/ScrollResponder.js       | 165 +++++--
 Libraries/Components/ScrollView/ScrollView.js | 270 ++++++-----
 .../ScrollView/__mocks__/ScrollViewMock.js    |   5 +-
 .../ScrollView/processDecelerationRate.js     |   2 +
 .../SegmentedControlIOS.android.js            |   4 +-
 .../SegmentedControlIOS.ios.js                |  13 +-
 Libraries/Components/Slider/Slider.js         |  58 ++-
 Libraries/Components/StaticContainer.react.js |   6 +-
 Libraries/Components/StaticRenderer.js        |   4 +-
 Libraries/Components/StatusBar/StatusBar.js   |  26 +-
 .../StatusBar/StatusBarIOS.android.js         |   2 +
 .../Components/StatusBar/StatusBarIOS.ios.js  |   4 +-
 Libraries/Components/Subscribable.js          |  16 +-
 Libraries/Components/Switch/Switch.js         |  27 +-
 .../Components/TabBarIOS/TabBarIOS.android.js |   3 +-
 .../Components/TabBarIOS/TabBarIOS.ios.js     |  28 +-
 .../TabBarIOS/TabBarItemIOS.android.js        |   7 +-
 .../Components/TabBarIOS/TabBarItemIOS.ios.js |  20 +-
 .../Components/TextInput/TextInputState.js    |  11 +-
 .../TimePickerAndroid.android.js              |  11 +-
 .../TimePickerAndroid.ios.js                  |   4 +-
 .../ToastAndroid/ToastAndroid.android.js      |  19 +-
 .../ToastAndroid/ToastAndroid.ios.js          |   9 +-
 .../ToolbarAndroid/ToolbarAndroid.android.js  |  20 +-
 .../ToolbarAndroid/ToolbarAndroid.ios.js      |   2 +
 .../Touchable/BoundingDimensions.js           |   3 +-
 Libraries/Components/Touchable/PooledClass.js |   1 +
 Libraries/Components/Touchable/Position.js    |   1 +
 Libraries/Components/Touchable/Touchable.js   | 179 ++++---
 .../TouchableNativeFeedback.android.js        |  59 ++-
 .../Touchable/TouchableNativeFeedback.ios.js  |   7 +-
 .../Components/Touchable/TouchableOpacity.js  |  42 +-
 .../Touchable/TouchableWithoutFeedback.js     |  50 +-
 .../__mocks__/ensureComponentIsNative.js      |   3 +
 .../__tests__/TouchableHighlight-test.js      |   4 +-
 .../Touchable/ensureComponentIsNative.js      |   4 +-
 .../Touchable/ensurePositiveDelayProps.js     |  11 +-
 .../Components/View/PlatformViewPropTypes.js  |   1 +
 .../View/ReactNativeStyleAttributes.js        |   7 +-
 .../View/ReactNativeViewAttributes.js         |   2 +
 .../Components/View/ViewAccessibility.js      |  44 +-
 Libraries/Components/View/ViewPropTypes.js    |  42 +-
 .../Components/View/ViewStylePropTypes.js     |   2 +
 .../ViewPager/ViewPagerAndroid.android.js     |  51 +-
 .../ViewPager/ViewPagerAndroid.ios.js         |   2 +
 .../Components/WebView/WebView.android.js     | 115 +++--
 Libraries/Components/WebView/WebView.ios.js   | 126 ++---
 Libraries/Components/WebView/WebViewShared.js |   2 +
 .../WebView/__tests__/WebViewShared-test.js   |  43 +-
 .../__tests__/parseErrorStack-test.js         |   5 +-
 Libraries/Core/Devtools/getDevServer.js       |   7 +-
 Libraries/Core/Devtools/openFileInEditor.js   |   2 +
 Libraries/Core/Devtools/parseErrorStack.js    |   6 +-
 Libraries/Core/Devtools/setupDevtools.js      |   4 +-
 .../Core/Devtools/symbolicateStackTrace.js    |   6 +-
 Libraries/Core/ExceptionsManager.js           |  38 +-
 Libraries/Core/InitializeCore.js              |  53 ++-
 Libraries/Core/ReactNativeVersion.js          |   4 +-
 Libraries/Core/__mocks__/ErrorUtils.js        |   2 +
 .../MissingNativeEventEmitterShim.js          |  10 +-
 Libraries/EventEmitter/NativeEventEmitter.js  |   2 +
 .../EventEmitter/RCTDeviceEventEmitter.js     |  28 +-
 Libraries/EventEmitter/RCTEventEmitter.js     |   9 +-
 .../EventEmitter/RCTNativeAppEventEmitter.js  |   2 +
 .../__mocks__/NativeEventEmitter.js           |   2 +
 Libraries/Experimental/Incremental.js         |  68 +--
 Libraries/Experimental/IncrementalExample.js  |  60 ++-
 Libraries/Experimental/IncrementalGroup.js    |  11 +-
 .../Experimental/IncrementalPresenter.js      |  24 +-
 .../SwipeableRow/SwipeableListView.js         |  61 ++-
 .../SwipeableListViewDataSource.js            |  20 +-
 .../SwipeableQuickActionButton.js             |   6 +-
 .../SwipeableRow/SwipeableQuickActions.js     |  14 +-
 .../Experimental/SwipeableRow/SwipeableRow.js |  71 +--
 Libraries/Experimental/WindowedListView.js    | 262 ++++++----
 Libraries/Geolocation/Geolocation.js          |  47 +-
 Libraries/Image/AssetSourceResolver.js        |   5 +-
 Libraries/Image/RelativeImageStub.js          |   2 +
 .../__tests__/assetRelativePathInSnapshot.js  |  16 +-
 .../__tests__/resolveAssetSource-test.js      | 329 +++++++------
 Libraries/Image/resolveAssetSource.js         |  13 +-
 Libraries/Inspector/BorderBox.js              |   9 +-
 Libraries/Inspector/BoxInspector.js           |  16 +-
 Libraries/Inspector/ElementBox.js             |   3 +-
 Libraries/Inspector/ElementProperties.js      |  15 +-
 Libraries/Inspector/Inspector.js              |  92 ++--
 Libraries/Inspector/InspectorOverlay.js       |  19 +-
 Libraries/Inspector/InspectorPanel.js         |  36 +-
 Libraries/Inspector/NetworkOverlay.js         | 133 +++---
 Libraries/Inspector/PerformanceOverlay.js     |  12 +-
 Libraries/Inspector/StyleInspector.js         |  22 +-
 Libraries/Inspector/resolveBoxStyle.js        |   3 +-
 Libraries/Interaction/Batchinator.js          |   2 +
 .../Interaction/BridgeSpyStallHandler.js      |  16 +-
 Libraries/Interaction/FrameRateLogger.js      |  13 +-
 Libraries/Interaction/InteractionManager.js   |  34 +-
 Libraries/Interaction/InteractionMixin.js     |   6 +-
 .../Interaction/InteractionStallDebugger.js   |   2 +
 Libraries/Interaction/JSEventLoopWatchdog.js  |   9 +-
 Libraries/Interaction/PanResponder.js         | 147 ++++--
 .../Interaction/ReactPerfStallHandler.js      |   2 +
 Libraries/Interaction/TaskQueue.js            |  53 ++-
 Libraries/Interaction/TouchHistoryMath.js     |   2 +
 .../Interaction/__tests__/Batchinator-test.js |   5 +-
 .../__tests__/InteractionManager-test.js      |  24 +-
 .../__tests__/InteractionMixin-test.js        |   2 +
 .../Interaction/__tests__/TaskQueue-test.js   |   2 +-
 Libraries/JSInspector/InspectorAgent.js       |   2 +
 Libraries/JSInspector/JSInspector.js          |   6 +-
 Libraries/JSInspector/NetworkAgent.js         |  92 ++--
 Libraries/Linking/Linking.js                  |  18 +-
 Libraries/Lists/VirtualizedList.js            |   8 +-
 Libraries/Modal/Modal.js                      |  67 ++-
 Libraries/Network/FormData.js                 |  22 +-
 Libraries/Network/NetInfo.js                  |  63 ++-
 Libraries/Network/RCTNetworking.android.js    |   9 +-
 Libraries/Network/RCTNetworking.ios.js        |  30 +-
 Libraries/Network/XHRInterceptor.js           |  75 +--
 Libraries/Network/XMLHttpRequest.js           | 200 ++++----
 Libraries/Network/__tests__/FormData-test.js  |  11 +-
 .../Network/__tests__/XMLHttpRequest-test.js  |  41 +-
 Libraries/Network/fetch.js                    |   4 +-
 .../Performance/QuickPerformanceLogger.js     |   2 +-
 Libraries/Performance/SamplingProfiler.js     |   7 +-
 .../PermissionsAndroid/PermissionsAndroid.js  |  49 +-
 Libraries/Promise.js                          |   4 +-
 .../PushNotificationIOS.js                    |  84 ++--
 Libraries/RCTTest/SnapshotViewIOS.android.js  |   2 +
 Libraries/RCTTest/SnapshotViewIOS.ios.js      |  14 +-
 Libraries/ReactNative/UIManager.js            |  21 +-
 Libraries/Sample/Sample.android.js            |   4 +-
 Libraries/Sample/Sample.ios.js                |   4 +-
 Libraries/Settings/Settings.android.js        |   2 +
 Libraries/Settings/Settings.ios.js            |  10 +-
 Libraries/Share/Share.js                      |  41 +-
 Libraries/Storage/AsyncStorage.js             |  41 +-
 Libraries/StyleSheet/ColorPropType.js         |  36 +-
 Libraries/StyleSheet/EdgeInsetsPropType.js    |   2 +
 Libraries/StyleSheet/LayoutPropTypes.js       |  50 +-
 Libraries/StyleSheet/PointPropType.js         |   2 +
 Libraries/StyleSheet/StyleSheetPropType.js    |   8 +-
 Libraries/StyleSheet/StyleSheetValidation.js  |  19 +-
 Libraries/StyleSheet/TransformPropTypes.js    |  51 +-
 .../StyleSheet/__tests__/flattenStyle-test.js |   2 +
 .../__tests__/normalizeColor-test.js          |   4 +-
 .../StyleSheet/__tests__/processColor-test.js |  38 +-
 .../__tests__/processTransform-test.js        |  62 ++-
 .../__tests__/setNormalizedColorAlpha-test.js |   4 +-
 Libraries/StyleSheet/processColor.js          |   4 +-
 Libraries/StyleSheet/processTransform.js      |  60 ++-
 .../StyleSheet/setNormalizedColorAlpha.js     |   2 +
 Libraries/Text/TextStylePropTypes.js          |  78 ++-
 Libraries/Text/TextUpdateTest.js              |  17 +-
 Libraries/Utilities/BackAndroid.js            |  24 +-
 Libraries/Utilities/BackHandler.android.js    |   9 +-
 Libraries/Utilities/BackHandler.ios.js        |  15 +-
 Libraries/Utilities/DeviceInfo.js             |   2 +
 Libraries/Utilities/Dimensions.js             |  32 +-
 Libraries/Utilities/HMRLoadingView.android.js |   1 +
 Libraries/Utilities/HMRLoadingView.ios.js     |   3 +-
 Libraries/Utilities/HeapCapture.js            |   4 +-
 Libraries/Utilities/JSDevSupportModule.js     |  12 +-
 Libraries/Utilities/MatrixMath.js             | 447 ++++++++++++------
 Libraries/Utilities/PixelRatio.js             |   2 +
 Libraries/Utilities/Platform.android.js       |   3 +-
 Libraries/Utilities/Platform.ios.js           |   3 +-
 Libraries/Utilities/PlatformOS.android.js     |   3 +-
 Libraries/Utilities/PlatformOS.ios.js         |   3 +-
 Libraries/Utilities/RCTLog.js                 |   8 +-
 Libraries/Utilities/SceneTracker.js           |   9 +-
 Libraries/Utilities/__mocks__/BackHandler.js  |   8 +-
 Libraries/Utilities/__mocks__/PixelRatio.js   |   6 +-
 .../Utilities/__tests__/MatrixMath-test.js    | 182 ++++---
 .../Utilities/__tests__/Platform-test.js      |   6 +-
 .../Utilities/__tests__/SceneTracker-test.js  |   7 +-
 .../__tests__/buildStyleInterpolator-test.js  |  37 +-
 .../deepFreezeAndThrowOnMutationInDev-test.js |  49 +-
 .../Utilities/__tests__/groupByEveryN-test.js |  53 ++-
 .../__tests__/mapWithSeparator-test.js        |   8 +-
 .../Utilities/__tests__/truncate-test.js      |  54 +--
 Libraries/Utilities/binaryToBase64.js         |   2 +
 Libraries/Utilities/buildStyleInterpolator.js |  68 ++-
 Libraries/Utilities/clamp.js                  |   2 +
 .../Utilities/createStrictShapeTypeChecker.js |  30 +-
 .../deepFreezeAndThrowOnMutationInDev.js      |  20 +-
 .../Utilities/defineLazyObjectProperty.js     |   1 +
 Libraries/Utilities/deprecatedPropType.js     |  15 +-
 .../differ/__tests__/deepDiffer-test.js       |  88 ++--
 Libraries/Utilities/differ/deepDiffer.js      |  14 +-
 Libraries/Utilities/differ/insetsDiffer.js    |  28 +-
 Libraries/Utilities/differ/matricesDiffer.js  |   9 +-
 Libraries/Utilities/differ/pointsDiffer.js    |  11 +-
 Libraries/Utilities/differ/sizesDiffer.js     |   7 +-
 Libraries/Utilities/dismissKeyboard.js        |   3 +
 Libraries/Utilities/groupByEveryN.js          |   1 +
 Libraries/Utilities/infoLog.js                |   2 +
 Libraries/Utilities/logError.js               |   2 +
 Libraries/Utilities/mapWithSeparator.js       |   2 +
 Libraries/Utilities/mergeIntoFast.js          |   2 +
 Libraries/Utilities/stringifySafe.js          |   2 +
 Libraries/Utilities/truncate.js               |  18 +-
 Libraries/Vibration/Vibration.js              |  21 +-
 Libraries/Vibration/VibrationIOS.android.js   |   4 +-
 Libraries/Vibration/VibrationIOS.ios.js       |   9 +-
 Libraries/WebSocket/WebSocket.js              |  86 ++--
 Libraries/WebSocket/WebSocketEvent.js         |   1 +
 Libraries/WebSocket/WebSocketInterceptor.js   |  21 +-
 .../WebSocket/__mocks__/event-target-shim.js  |   2 +
 .../WebSocket/__tests__/WebSocket-test.js     |   8 +-
 Libraries/polyfills/Array.es6.js              |  14 +-
 Libraries/polyfills/Array.prototype.es6.js    |  21 +-
 Libraries/polyfills/Number.es6.js             |   1 +
 Libraries/polyfills/Object.es6.js             |  14 +-
 Libraries/polyfills/Object.es7.js             |   2 +-
 Libraries/polyfills/String.prototype.es6.js   |   7 +-
 .../polyfills/__tests__/Object.es7-test.js    |  63 ++-
 Libraries/polyfills/babelHelpers.js           | 157 +++---
 Libraries/polyfills/error-guard.js            |  15 +-
 Libraries/promiseRejectionIsError.js          |   2 +
 Libraries/react-native/React.js               |   1 +
 .../react-native-implementation.js            | 398 ++++++++++++----
 .../react-native/react-native-interface.js    |   2 +
 Libraries/vendor/core/ErrorUtils.js           |   1 +
 Libraries/vendor/core/Map.js                  |  36 +-
 Libraries/vendor/core/Set.js                  |   8 +-
 .../core/_shouldPolyfillES6Collection.js      |  36 +-
 Libraries/vendor/core/getObjectValues.js      |   2 +
 Libraries/vendor/core/guid.js                 |   1 +
 Libraries/vendor/core/isEmpty.js              |   2 +
 Libraries/vendor/core/mergeHelpers.js         |  14 +-
 Libraries/vendor/core/toIterator.js           |  18 +-
 .../selection/DocumentSelectionState.js       |  24 +-
 .../vendor/emitter/EmitterSubscription.js     |   5 +-
 Libraries/vendor/emitter/EventEmitter.js      |  42 +-
 .../vendor/emitter/EventEmitterWithHolding.js |  14 +-
 Libraries/vendor/emitter/EventHolder.js       |  11 +-
 Libraries/vendor/emitter/EventSubscription.js |   3 +-
 .../vendor/emitter/EventSubscriptionVendor.js |  12 +-
 Libraries/vendor/emitter/EventValidator.js    |  35 +-
 Libraries/vendor/emitter/mixInEventEmitter.js |   8 +-
 301 files changed, 6287 insertions(+), 3809 deletions(-)

diff --git a/Libraries/ART/ARTSerializablePath.js b/Libraries/ART/ARTSerializablePath.js
index de02f9498d06..9c2d98e033fc 100644
--- a/Libraries/ART/ARTSerializablePath.js
+++ b/Libraries/ART/ARTSerializablePath.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 // TODO: Move this into an ART mode called "serialized" or something
@@ -19,7 +21,6 @@ const CURVE_TO = 3;
 const ARC = 4;
 
 const SerializablePath = Class(Path, {
-
   initialize: function(path) {
     this.reset();
     if (path instanceof SerializablePath) {
@@ -54,7 +55,18 @@ const SerializablePath = Class(Path, {
   onArc: function(sx, sy, ex, ey, cx, cy, rx, ry, sa, ea, ccw, rotation) {
     if (rx !== ry || rotation) {
       return this._arcToBezier(
-        sx, sy, ex, ey, cx, cy, rx, ry, sa, ea, ccw, rotation
+        sx,
+        sy,
+        ex,
+        ey,
+        cx,
+        cy,
+        rx,
+        ry,
+        sa,
+        ea,
+        ccw,
+        rotation,
       );
     }
     this.path.push(ARC, cx, cy, rx, sa, ea, ccw ? 0 : 1);
@@ -66,8 +78,7 @@ const SerializablePath = Class(Path, {
 
   toJSON: function() {
     return this.path;
-  }
-
+  },
 });
 
 module.exports = SerializablePath;
diff --git a/Libraries/ART/ReactNativeART.js b/Libraries/ART/ReactNativeART.js
index 0f32fa2dae2a..465ddc6b13f2 100644
--- a/Libraries/ART/ReactNativeART.js
+++ b/Libraries/ART/ReactNativeART.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const Color = require('art/core/color');
@@ -69,58 +71,57 @@ const SurfaceViewAttributes = merge(ReactNativeViewAttributes.UIView, {
 });
 
 const NodeAttributes = {
-  transform: { diff: arrayDiffer },
+  transform: {diff: arrayDiffer},
   opacity: true,
 };
 
 const GroupAttributes = merge(NodeAttributes, {
-  clipping: { diff: arrayDiffer }
+  clipping: {diff: arrayDiffer},
 });
 
 const RenderableAttributes = merge(NodeAttributes, {
-  fill: { diff: arrayDiffer },
-  stroke: { diff: arrayDiffer },
+  fill: {diff: arrayDiffer},
+  stroke: {diff: arrayDiffer},
   strokeWidth: true,
   strokeCap: true,
   strokeJoin: true,
-  strokeDash: { diff: arrayDiffer },
+  strokeDash: {diff: arrayDiffer},
 });
 
 const ShapeAttributes = merge(RenderableAttributes, {
-  d: { diff: arrayDiffer },
+  d: {diff: arrayDiffer},
 });
 
 const TextAttributes = merge(RenderableAttributes, {
   alignment: true,
-  frame: { diff: fontAndLinesDiffer },
-  path: { diff: arrayDiffer }
+  frame: {diff: fontAndLinesDiffer},
+  path: {diff: arrayDiffer},
 });
 
 // Native Components
 
-const NativeSurfaceView = createReactNativeComponentClass('ARTSurfaceView',
+const NativeSurfaceView = createReactNativeComponentClass(
+  'ARTSurfaceView',
   () => ({
     validAttributes: SurfaceViewAttributes,
     uiViewClassName: 'ARTSurfaceView',
-  }));
+  }),
+);
 
-const NativeGroup = createReactNativeComponentClass('ARTGroup',
-  () => ({
-    validAttributes: GroupAttributes,
-    uiViewClassName: 'ARTGroup',
-  }));
+const NativeGroup = createReactNativeComponentClass('ARTGroup', () => ({
+  validAttributes: GroupAttributes,
+  uiViewClassName: 'ARTGroup',
+}));
 
-const NativeShape = createReactNativeComponentClass('ARTShape',
-  () => ({
-    validAttributes: ShapeAttributes,
-    uiViewClassName: 'ARTShape',
-  }));
+const NativeShape = createReactNativeComponentClass('ARTShape', () => ({
+  validAttributes: ShapeAttributes,
+  uiViewClassName: 'ARTShape',
+}));
 
-const NativeText = createReactNativeComponentClass('ARTText',
-  () => ({
-    validAttributes: TextAttributes,
-    uiViewClassName: 'ARTText',
-  }));
+const NativeText = createReactNativeComponentClass('ARTText', () => ({
+  validAttributes: TextAttributes,
+  uiViewClassName: 'ARTText',
+}));
 
 // Utilities
 
@@ -145,7 +146,7 @@ class Surface extends React.Component {
   };
 
   getChildContext() {
-    return { isInSurface: true };
+    return {isInSurface: true};
   }
 
   render() {
@@ -153,7 +154,7 @@ class Surface extends React.Component {
     const w = extractNumber(props.width, 0);
     const h = extractNumber(props.height, 0);
     return (
-      <NativeSurfaceView style={[props.style, { width: w, height: h }]}>
+      <NativeSurfaceView style={[props.style, {width: w, height: h}]}>
         {this.props.children}
       </NativeSurfaceView>
     );
@@ -175,10 +176,10 @@ function extractNumber(value, defaultValue) {
 const pooledTransform = new Transform();
 
 function extractTransform(props) {
-  const scaleX = props.scaleX != null ? props.scaleX :
-               props.scale != null ? props.scale : 1;
-  const scaleY = props.scaleY != null ? props.scaleY :
-               props.scale != null ? props.scale : 1;
+  const scaleX =
+    props.scaleX != null ? props.scaleX : props.scale != null ? props.scale : 1;
+  const scaleY =
+    props.scaleY != null ? props.scaleY : props.scale != null ? props.scale : 1;
 
   pooledTransform
     .transformTo(1, 0, 0, 1, 0, 0)
@@ -191,9 +192,12 @@ function extractTransform(props) {
   }
 
   return [
-    pooledTransform.xx, pooledTransform.yx,
-    pooledTransform.xy, pooledTransform.yy,
-    pooledTransform.x,  pooledTransform.y,
+    pooledTransform.xx,
+    pooledTransform.yx,
+    pooledTransform.xy,
+    pooledTransform.yy,
+    pooledTransform.x,
+    pooledTransform.y,
   ];
 }
 
@@ -222,7 +226,7 @@ class Group extends React.Component {
     const props = this.props;
     invariant(
       this.context.isInSurface,
-      'ART: <Group /> must be a child of a <Surface />'
+      'ART: <Group /> must be a child of a <Surface />',
     );
     return (
       <NativeGroup
@@ -299,7 +303,7 @@ function insertOffsetsIntoArray(stops, targetArray, atIndex, multi, reverse) {
     }
   } else {
     for (const offsetString in stops) {
-      offsetNumber = (+offsetString) * multi;
+      offsetNumber = +offsetString * multi;
       targetArray[atIndex + i] = reverse ? 1 - offsetNumber : offsetNumber;
       i++;
     }
@@ -370,17 +374,23 @@ function extractColor(color) {
 
 function extractStrokeCap(strokeCap) {
   switch (strokeCap) {
-    case 'butt': return 0;
-    case 'square': return 2;
-    default: return 1; // round
+    case 'butt':
+      return 0;
+    case 'square':
+      return 2;
+    default:
+      return 1; // round
   }
 }
 
 function extractStrokeJoin(strokeJoin) {
   switch (strokeJoin) {
-    case 'miter': return 0;
-    case 'bevel': return 2;
-    default: return 1; // round
+    case 'miter':
+      return 0;
+    case 'bevel':
+      return 2;
+    default:
+      return 1; // round
   }
 }
 
@@ -404,7 +414,6 @@ class Shape extends React.Component {
         strokeJoin={extractStrokeJoin(props.strokeJoin)}
         strokeWidth={extractNumber(props.strokeWidth, 1)}
         transform={extractTransform(props)}
-
         d={d}
       />
     );
@@ -422,9 +431,10 @@ function extractSingleFontFamily(fontFamilyString) {
   // ART on the web allows for multiple font-families to be specified.
   // For compatibility, we extract the first font-family, hoping
   // we'll get a match.
-  return fontFamilyString.split(',')[0]
-         .replace(fontFamilyPrefix, '')
-         .replace(fontFamilySuffix, '');
+  return fontFamilyString
+    .split(',')[0]
+    .replace(fontFamilyPrefix, '')
+    .replace(fontFamilySuffix, '');
 }
 
 function parseFontString(font) {
@@ -458,7 +468,8 @@ function extractFont(font) {
   }
   const fontFamily = extractSingleFontFamily(font.fontFamily);
   const fontSize = +font.fontSize || 12;
-  const fontWeight = font.fontWeight != null ? font.fontWeight.toString() : '400';
+  const fontWeight =
+    font.fontWeight != null ? font.fontWeight.toString() : '400';
   return {
     // Normalize
     fontFamily: fontFamily,
@@ -470,7 +481,7 @@ function extractFont(font) {
 
 const newLine = /\n/g;
 function extractFontAndLines(font, text) {
-  return { font: extractFont(font), lines: text.split(newLine) };
+  return {font: extractFont(font), lines: text.split(newLine)};
 }
 
 function extractAlignment(alignment) {
@@ -488,10 +499,12 @@ class Text extends React.Component {
   render() {
     const props = this.props;
     const path = props.path;
-    const textPath = path ? (path instanceof Path ? path : new Path(path)).toJSON() : null;
+    const textPath = path
+      ? (path instanceof Path ? path : new Path(path)).toJSON()
+      : null;
     const textFrame = extractFontAndLines(
       props.font,
-      childrenAsString(props.children)
+      childrenAsString(props.children),
     );
     return (
       <NativeText
@@ -503,7 +516,6 @@ class Text extends React.Component {
         strokeJoin={extractStrokeJoin(props.strokeJoin)}
         strokeWidth={extractNumber(props.strokeWidth, 1)}
         transform={extractTransform(props)}
-
         alignment={extractAlignment(props.alignment)}
         frame={textFrame}
         path={textPath}
@@ -518,13 +530,14 @@ function LinearGradient(stops, x1, y1, x2, y2) {
   const type = LINEAR_GRADIENT;
 
   if (arguments.length < 5) {
-    const angle = ((x1 == null) ? 270 : x1) * Math.PI / 180;
+    const angle = (x1 == null ? 270 : x1) * Math.PI / 180;
 
     let x = Math.cos(angle);
     let y = -Math.sin(angle);
     const l = (Math.abs(x) + Math.abs(y)) / 2;
 
-    x *= l; y *= l;
+    x *= l;
+    y *= l;
 
     x1 = 0.5 - x;
     x2 = 0.5 + x;
diff --git a/Libraries/Alert/Alert.js b/Libraries/Alert/Alert.js
index 76c1f516db72..a424f5026d5a 100644
--- a/Libraries/Alert/Alert.js
+++ b/Libraries/Alert/Alert.js
@@ -4,15 +4,17 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const AlertIOS = require('AlertIOS');
 const NativeModules = require('NativeModules');
 const Platform = require('Platform');
 
-import type { AlertType, AlertButtonStyle } from 'AlertIOS';
+import type {AlertType, AlertButtonStyle} from 'AlertIOS';
 
 export type Buttons = Array<{
   text?: string,
@@ -31,7 +33,6 @@ type Options = {
  * See http://facebook.github.io/react-native/docs/alert.html
  */
 class Alert {
-
   /**
    * Launches an alert dialog with the specified title and message.
    *
@@ -46,7 +47,9 @@ class Alert {
   ): void {
     if (Platform.OS === 'ios') {
       if (typeof type !== 'undefined') {
-        console.warn('Alert.alert() with a 5th "type" parameter is deprecated and will be removed. Use AlertIOS.prompt() instead.');
+        console.warn(
+          'Alert.alert() with a 5th "type" parameter is deprecated and will be removed. Use AlertIOS.prompt() instead.',
+        );
         AlertIOS.alert(title, message, buttons, type);
         return;
       }
@@ -61,7 +64,6 @@ class Alert {
  * Wrapper around the Android native module.
  */
 class AlertAndroid {
-
   static alert(
     title: ?string,
     message?: ?string,
@@ -78,35 +80,41 @@ class AlertAndroid {
     }
     // At most three buttons (neutral, negative, positive). Ignore rest.
     // The text 'OK' should be probably localized. iOS Alert does that in native.
-    const validButtons: Buttons = buttons ? buttons.slice(0, 3) : [{text: 'OK'}];
+    const validButtons: Buttons = buttons
+      ? buttons.slice(0, 3)
+      : [{text: 'OK'}];
     const buttonPositive = validButtons.pop();
     const buttonNegative = validButtons.pop();
     const buttonNeutral = validButtons.pop();
     if (buttonNeutral) {
-      config = {...config, buttonNeutral: buttonNeutral.text || '' };
+      config = {...config, buttonNeutral: buttonNeutral.text || ''};
     }
     if (buttonNegative) {
-      config = {...config, buttonNegative: buttonNegative.text || '' };
+      config = {...config, buttonNegative: buttonNegative.text || ''};
     }
     if (buttonPositive) {
-      config = {...config, buttonPositive: buttonPositive.text || '' };
+      config = {...config, buttonPositive: buttonPositive.text || ''};
     }
     NativeModules.DialogManagerAndroid.showAlert(
       config,
-      (errorMessage) => console.warn(errorMessage),
+      errorMessage => console.warn(errorMessage),
       (action, buttonKey) => {
         if (action === NativeModules.DialogManagerAndroid.buttonClicked) {
           if (buttonKey === NativeModules.DialogManagerAndroid.buttonNeutral) {
             buttonNeutral.onPress && buttonNeutral.onPress();
-          } else if (buttonKey === NativeModules.DialogManagerAndroid.buttonNegative) {
+          } else if (
+            buttonKey === NativeModules.DialogManagerAndroid.buttonNegative
+          ) {
             buttonNegative.onPress && buttonNegative.onPress();
-          } else if (buttonKey === NativeModules.DialogManagerAndroid.buttonPositive) {
+          } else if (
+            buttonKey === NativeModules.DialogManagerAndroid.buttonPositive
+          ) {
             buttonPositive.onPress && buttonPositive.onPress();
           }
         } else if (action === NativeModules.DialogManagerAndroid.dismissed) {
           options && options.onDismiss && options.onDismiss();
         }
-      }
+      },
     );
   }
 }
diff --git a/Libraries/Alert/AlertIOS.js b/Libraries/Alert/AlertIOS.js
index 082e3779da88..1998865b2d59 100644
--- a/Libraries/Alert/AlertIOS.js
+++ b/Libraries/Alert/AlertIOS.js
@@ -4,9 +4,11 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  * @jsdoc
  */
+
 'use strict';
 
 const RCTAlertManager = require('NativeModules').AlertManager;
@@ -18,7 +20,7 @@ export type AlertType = $Enum<{
   /**
    * Default alert with no inputs
    */
-  'default': string,
+  default: string,
   /**
    * Plain text input alert
    */
@@ -40,15 +42,15 @@ export type AlertButtonStyle = $Enum<{
   /**
    * Default button style
    */
-  'default': string,
+  default: string,
   /**
    * Cancel button style
    */
-  'cancel': string,
+  cancel: string,
   /**
    * Destructive button style
    */
-  'destructive': string,
+  destructive: string,
 }>;
 
 /**
@@ -87,11 +89,13 @@ class AlertIOS {
   static alert(
     title: ?string,
     message?: ?string,
-    callbackOrButtons?: ?(() => void) | ButtonsArray,
+    callbackOrButtons?: ?((() => void) | ButtonsArray),
     type?: AlertType,
   ): void {
     if (typeof type !== 'undefined') {
-      console.warn('AlertIOS.alert() with a 4th "type" parameter is deprecated and will be removed. Use AlertIOS.prompt() instead.');
+      console.warn(
+        'AlertIOS.alert() with a 4th "type" parameter is deprecated and will be removed. Use AlertIOS.prompt() instead.',
+      );
       this.prompt(title, message, callbackOrButtons, type);
       return;
     }
@@ -106,26 +110,30 @@ class AlertIOS {
   static prompt(
     title: ?string,
     message?: ?string,
-    callbackOrButtons?: ?((text: string) => void) | ButtonsArray,
+    callbackOrButtons?: ?(((text: string) => void) | ButtonsArray),
     type?: ?AlertType = 'plain-text',
     defaultValue?: string,
-    keyboardType?: string
+    keyboardType?: string,
   ): void {
     if (typeof type === 'function') {
       console.warn(
         'You passed a callback function as the "type" argument to AlertIOS.prompt(). React Native is ' +
-        'assuming  you want to use the deprecated AlertIOS.prompt(title, defaultValue, buttons, callback) ' +
-        'signature. The current signature is AlertIOS.prompt(title, message, callbackOrButtons, type, defaultValue, ' +
-        'keyboardType) and the old syntax will be removed in a future version.');
+          'assuming  you want to use the deprecated AlertIOS.prompt(title, defaultValue, buttons, callback) ' +
+          'signature. The current signature is AlertIOS.prompt(title, message, callbackOrButtons, type, defaultValue, ' +
+          'keyboardType) and the old syntax will be removed in a future version.',
+      );
 
       const callback = type;
-      RCTAlertManager.alertWithArgs({
-        title: title || '',
-        type: 'plain-text',
-        defaultValue: message,
-      }, (id, value) => {
-        callback(value);
-      });
+      RCTAlertManager.alertWithArgs(
+        {
+          title: title || '',
+          type: 'plain-text',
+          defaultValue: message,
+        },
+        (id, value) => {
+          callback(value);
+        },
+      );
       return;
     }
 
@@ -135,8 +143,7 @@ class AlertIOS {
     let destructiveButtonKey;
     if (typeof callbackOrButtons === 'function') {
       callbacks = [callbackOrButtons];
-    }
-    else if (callbackOrButtons instanceof Array) {
+    } else if (callbackOrButtons instanceof Array) {
       callbackOrButtons.forEach((btn, index) => {
         callbacks[index] = btn.onPress;
         if (btn.style === 'cancel') {
@@ -152,19 +159,22 @@ class AlertIOS {
       });
     }
 
-    RCTAlertManager.alertWithArgs({
-      title: title || '',
-      message: message || undefined,
-      buttons,
-      type: type || undefined,
-      defaultValue,
-      cancelButtonKey,
-      destructiveButtonKey,
-      keyboardType,
-    }, (id, value) => {
-      const cb = callbacks[id];
-      cb && cb(value);
-    });
+    RCTAlertManager.alertWithArgs(
+      {
+        title: title || '',
+        message: message || undefined,
+        buttons,
+        type: type || undefined,
+        defaultValue,
+        cancelButtonKey,
+        destructiveButtonKey,
+        keyboardType,
+      },
+      (id, value) => {
+        const cb = callbacks[id];
+        cb && cb(value);
+      },
+    );
   }
 }
 
diff --git a/Libraries/Alert/RCTAlertManager.android.js b/Libraries/Alert/RCTAlertManager.android.js
index 57bd4740e8fc..2e510add8dda 100644
--- a/Libraries/Alert/RCTAlertManager.android.js
+++ b/Libraries/Alert/RCTAlertManager.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
-*/
+ * @format
+ */
+
 'use strict';
 
 const NativeModules = require('NativeModules');
@@ -15,8 +17,9 @@ module.exports = {
   alertWithArgs: function(args, callback) {
     // TODO(5998984): Polyfill it correctly with DialogManagerAndroid
     NativeModules.DialogManagerAndroid.showAlert(
-        args,
-        emptyCallback,
-        callback || emptyCallback);
+      args,
+      emptyCallback,
+      callback || emptyCallback,
+    );
   },
 };
diff --git a/Libraries/Alert/RCTAlertManager.ios.js b/Libraries/Alert/RCTAlertManager.ios.js
index d64bce5b4f12..529bb5da0e55 100644
--- a/Libraries/Alert/RCTAlertManager.ios.js
+++ b/Libraries/Alert/RCTAlertManager.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const RCTAlertManager = require('NativeModules').AlertManager;
diff --git a/Libraries/Animated/release/gulpfile.js b/Libraries/Animated/release/gulpfile.js
index f5e87b4c9987..b5599e9365fe 100644
--- a/Libraries/Animated/release/gulpfile.js
+++ b/Libraries/Animated/release/gulpfile.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -20,58 +22,52 @@ var objectAssign = require('object-assign');
 var runSequence = require('run-sequence');
 var webpackStream = require('webpack-stream');
 
-var DEVELOPMENT_HEADER = [
-  '/**',
-  ' * Animated v<%= version %>',
-  ' */'
-].join('\n') + '\n';
-var PRODUCTION_HEADER = [
-  '/**',
-  ' * Animated v<%= version %>',
-  ' *',
-  ' * Copyright (c) 2013-present, Facebook, Inc.',
-  ' *',
-  ' * This source code is licensed under the MIT license found in the',
-  ' * LICENSE file in the root directory of this source tree.',
-  ' */'
-].join('\n') + '\n';
+var DEVELOPMENT_HEADER =
+  ['/**', ' * Animated v<%= version %>', ' */'].join('\n') + '\n';
+var PRODUCTION_HEADER =
+  [
+    '/**',
+    ' * Animated v<%= version %>',
+    ' *',
+    ' * Copyright (c) 2013-present, Facebook, Inc.',
+    ' *',
+    ' * This source code is licensed under the MIT license found in the',
+    ' * LICENSE file in the root directory of this source tree.',
+    ' */',
+  ].join('\n') + '\n';
 
 var babelOpts = {
   nonStandard: true,
-  loose: [
-    'es6.classes'
-  ],
+  loose: ['es6.classes'],
   stage: 1,
   plugins: [babelPluginDEV, babelPluginModules],
   _moduleMap: objectAssign({}, require('fbjs/module-map'), {
-    'React': 'react',
-  })
+    React: 'react',
+  }),
 };
 
 var buildDist = function(opts) {
   var webpackOpts = {
     debug: opts.debug,
     externals: {
-      'react': 'React',
+      react: 'React',
     },
     module: {
-      loaders: [
-        {test: /\.js$/, loader: 'babel'}
-      ],
+      loaders: [{test: /\.js$/, loader: 'babel'}],
     },
     output: {
       filename: opts.output,
-      library: 'Animated'
+      library: 'Animated',
     },
     plugins: [
       new webpackStream.webpack.DefinePlugin({
         'process.env.NODE_ENV': JSON.stringify(
-          opts.debug ? 'development' : 'production'
+          opts.debug ? 'development' : 'production',
         ),
       }),
       new webpackStream.webpack.optimize.OccurenceOrderPlugin(),
-      new webpackStream.webpack.optimize.DedupePlugin()
-    ]
+      new webpackStream.webpack.optimize.DedupePlugin(),
+    ],
   };
   if (!opts.debug) {
     webpackOpts.plugins.push(
@@ -79,9 +75,9 @@ var buildDist = function(opts) {
         compress: {
           hoist_vars: true,
           screw_ie8: true,
-          warnings: false
-        }
-      })
+          warnings: false,
+        },
+      }),
     );
   }
   return webpackStream(webpackOpts, null, function(err, stats) {
@@ -101,7 +97,7 @@ var paths = {
   src: [
     '*src/**/*.js',
     '!src/**/__tests__/**/*.js',
-    '!src/**/__mocks__/**/*.js'
+    '!src/**/__mocks__/**/*.js',
   ],
 };
 
@@ -117,32 +113,36 @@ gulp.task('modules', function() {
     .pipe(gulp.dest(paths.lib));
 });
 
-gulp.task('dist', ['modules'], function () {
+gulp.task('dist', ['modules'], function() {
   var distOpts = {
     debug: true,
-    output: 'animated.js'
+    output: 'animated.js',
   };
   return gulp
     .src(paths.entry)
     .pipe(buildDist(distOpts))
     .pipe(derequire())
-    .pipe(header(DEVELOPMENT_HEADER, {
-      version: process.env.npm_package_version
-    }))
+    .pipe(
+      header(DEVELOPMENT_HEADER, {
+        version: process.env.npm_package_version,
+      }),
+    )
     .pipe(gulp.dest(paths.dist));
 });
 
-gulp.task('dist:min', ['modules'], function () {
+gulp.task('dist:min', ['modules'], function() {
   var distOpts = {
     debug: false,
-    output: 'animated.min.js'
+    output: 'animated.min.js',
   };
   return gulp
     .src(paths.entry)
     .pipe(buildDist(distOpts))
-    .pipe(header(PRODUCTION_HEADER, {
-      version: process.env.npm_package_version
-    }))
+    .pipe(
+      header(PRODUCTION_HEADER, {
+        version: process.env.npm_package_version,
+      }),
+    )
     .pipe(gulp.dest(paths.dist));
 });
 
diff --git a/Libraries/Animated/src/AnimatedWeb.js b/Libraries/Animated/src/AnimatedWeb.js
index 5538eb9b64c3..e80023d73687 100644
--- a/Libraries/Animated/src/AnimatedWeb.js
+++ b/Libraries/Animated/src/AnimatedWeb.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const AnimatedImplementation = require('AnimatedImplementation');
diff --git a/Libraries/Animated/src/Easing.js b/Libraries/Animated/src/Easing.js
index 5fb4478eef63..c5e54b24723e 100644
--- a/Libraries/Animated/src/Easing.js
+++ b/Libraries/Animated/src/Easing.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 let ease;
@@ -162,7 +164,7 @@ class Easing {
    */
   static elastic(bounciness: number = 1): (t: number) => number {
     const p = bounciness * Math.PI;
-    return (t) => 1 - Math.pow(Math.cos(t * Math.PI / 2), 3) * Math.cos(t * p);
+    return t => 1 - Math.pow(Math.cos(t * Math.PI / 2), 3) * Math.cos(t * p);
   }
 
   /**
@@ -177,7 +179,7 @@ class Easing {
     if (s === undefined) {
       s = 1.70158;
     }
-    return (t) => t * t * ((s + 1) * t - s);
+    return t => t * t * ((s + 1) * t - s);
   }
 
   /**
@@ -215,7 +217,7 @@ class Easing {
     x1: number,
     y1: number,
     x2: number,
-    y2: number
+    y2: number,
   ): (t: number) => number {
     const _bezier = require('bezier');
     return _bezier(x1, y1, x2, y2);
@@ -224,19 +226,15 @@ class Easing {
   /**
    * Runs an easing function forwards.
    */
-  static in(
-    easing: (t: number) => number,
-  ): (t: number) => number {
+  static in(easing: (t: number) => number): (t: number) => number {
     return easing;
   }
 
   /**
    * Runs an easing function backwards.
    */
-  static out(
-    easing: (t: number) => number,
-  ): (t: number) => number {
-    return (t) => 1 - easing(1 - t);
+  static out(easing: (t: number) => number): (t: number) => number {
+    return t => 1 - easing(1 - t);
   }
 
   /**
@@ -244,10 +242,8 @@ class Easing {
    * forwards for half of the duration, then backwards for the rest of the
    * duration.
    */
-  static inOut(
-    easing: (t: number) => number,
-  ): (t: number) => number {
-    return (t) => {
+  static inOut(easing: (t: number) => number): (t: number) => number {
+    return t => {
       if (t < 0.5) {
         return easing(t * 2) / 2;
       }
diff --git a/Libraries/Animated/src/SpringConfig.js b/Libraries/Animated/src/SpringConfig.js
index b71fda2eacce..ca25a115cb09 100644
--- a/Libraries/Animated/src/SpringConfig.js
+++ b/Libraries/Animated/src/SpringConfig.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -41,7 +42,7 @@ function fromBouncinessAndSpeed(
   }
 
   function projectNormal(n, start, end) {
-    return start + (n * (end - start));
+    return start + n * (end - start);
   }
 
   function linearInterpolation(t, start, end) {
@@ -53,18 +54,20 @@ function fromBouncinessAndSpeed(
   }
 
   function b3Friction1(x) {
-    return (0.0007 * Math.pow(x, 3)) -
-      (0.031 * Math.pow(x, 2)) + 0.64 * x + 1.28;
+    return 0.0007 * Math.pow(x, 3) - 0.031 * Math.pow(x, 2) + 0.64 * x + 1.28;
   }
 
   function b3Friction2(x) {
-    return (0.000044 * Math.pow(x, 3)) -
-      (0.006 * Math.pow(x, 2)) + 0.36 * x + 2;
+    return 0.000044 * Math.pow(x, 3) - 0.006 * Math.pow(x, 2) + 0.36 * x + 2;
   }
 
   function b3Friction3(x) {
-    return (0.00000045 * Math.pow(x, 3)) -
-      (0.000332 * Math.pow(x, 2)) + 0.1078 * x + 5.84;
+    return (
+      0.00000045 * Math.pow(x, 3) -
+      0.000332 * Math.pow(x, 2) +
+      0.1078 * x +
+      5.84
+    );
   }
 
   function b3Nobounce(tension) {
@@ -84,7 +87,7 @@ function fromBouncinessAndSpeed(
   const bouncyFriction = quadraticOutInterpolation(
     b,
     b3Nobounce(bouncyTension),
-    0.01
+    0.01,
   );
 
   return {
diff --git a/Libraries/Animated/src/__tests__/Animated-test.js b/Libraries/Animated/src/__tests__/Animated-test.js
index 36b4d2a40a50..1c2066bfdc5e 100644
--- a/Libraries/Animated/src/__tests__/Animated-test.js
+++ b/Libraries/Animated/src/__tests__/Animated-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 let Animated = require('Animated');
@@ -15,29 +17,33 @@ describe('Animated tests', () => {
   });
 
   describe('Animated', () => {
-
     it('works end to end', () => {
       const anim = new Animated.Value(0);
 
       const callback = jest.fn();
 
-      const node = new Animated.__PropsOnlyForTests({
-        style: {
-          backgroundColor: 'red',
-          opacity: anim,
-          transform: [
-            {translateX: anim.interpolate({
-              inputRange: [0, 1],
-              outputRange: [100, 200],
-            })},
-            {scale: anim},
-          ],
-          shadowOffset: {
-            width: anim,
-            height: anim,
+      const node = new Animated.__PropsOnlyForTests(
+        {
+          style: {
+            backgroundColor: 'red',
+            opacity: anim,
+            transform: [
+              {
+                translateX: anim.interpolate({
+                  inputRange: [0, 1],
+                  outputRange: [100, 200],
+                }),
+              },
+              {scale: anim},
+            ],
+            shadowOffset: {
+              width: anim,
+              height: anim,
+            },
           },
-        }
-      }, callback);
+        },
+        callback,
+      );
 
       expect(anim.__getChildren().length).toBe(3);
 
@@ -45,10 +51,7 @@ describe('Animated tests', () => {
         style: {
           backgroundColor: 'red',
           opacity: 0,
-          transform: [
-            {translateX: 100},
-            {scale: 0},
-          ],
+          transform: [{translateX: 100}, {scale: 0}],
           shadowOffset: {
             width: 0,
             height: 0,
@@ -64,10 +67,7 @@ describe('Animated tests', () => {
         style: {
           backgroundColor: 'red',
           opacity: 0.5,
-          transform: [
-            {translateX: 150},
-            {scale: 0.5},
-          ],
+          transform: [{translateX: 150}, {scale: 0.5}],
           shadowOffset: {
             width: 0.5,
             height: 0.5,
@@ -107,7 +107,6 @@ describe('Animated tests', () => {
       expect(anim.__detach).toBeCalled();
     });
 
-
     it('stops animation when detached', () => {
       const anim = new Animated.Value(0);
       const callback = jest.fn();
@@ -141,7 +140,8 @@ describe('Animated tests', () => {
       anim.addListener(listener);
       Animated.spring(anim, {toValue: 15}).start();
       jest.runAllTimers();
-      const lastValue = listener.mock.calls[listener.mock.calls.length - 2][0].value;
+      const lastValue =
+        listener.mock.calls[listener.mock.calls.length - 2][0].value;
       expect(lastValue).not.toBe(15);
       expect(lastValue).toBeCloseTo(15);
       expect(anim.__getValue()).toBe(15);
@@ -151,9 +151,14 @@ describe('Animated tests', () => {
       const anim = new Animated.Value(0);
       const listener = jest.fn();
       anim.addListener(listener);
-      Animated.spring(anim, {stiffness: 8000, damping: 2000, toValue: 15}).start();
+      Animated.spring(anim, {
+        stiffness: 8000,
+        damping: 2000,
+        toValue: 15,
+      }).start();
       jest.runAllTimers();
-      const lastValue = listener.mock.calls[listener.mock.calls.length - 2][0].value;
+      const lastValue =
+        listener.mock.calls[listener.mock.calls.length - 2][0].value;
       expect(lastValue).not.toBe(15);
       expect(lastValue).toBeCloseTo(15);
       expect(anim.__getValue()).toBe(15);
@@ -164,9 +169,7 @@ describe('Animated tests', () => {
     });
   });
 
-
   describe('Animated Sequence', () => {
-
     it('works with an empty sequence', () => {
       const cb = jest.fn();
       Animated.sequence([]).start(cb);
@@ -232,9 +235,12 @@ describe('Animated tests', () => {
   });
 
   describe('Animated Loop', () => {
-
     it('loops indefinitely if config not specified', () => {
-      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const animation = {
+        start: jest.fn(),
+        reset: jest.fn(),
+        _isUsingNativeDriver: () => false,
+      };
       const cb = jest.fn();
 
       const loop = Animated.loop(animation);
@@ -261,10 +267,14 @@ describe('Animated tests', () => {
     });
 
     it('loops indefinitely if iterations is -1', () => {
-      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const animation = {
+        start: jest.fn(),
+        reset: jest.fn(),
+        _isUsingNativeDriver: () => false,
+      };
       const cb = jest.fn();
 
-      const loop = Animated.loop(animation, { iterations: -1 });
+      const loop = Animated.loop(animation, {iterations: -1});
 
       expect(animation.start).not.toBeCalled();
 
@@ -288,10 +298,14 @@ describe('Animated tests', () => {
     });
 
     it('loops indefinitely if iterations not specified', () => {
-      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const animation = {
+        start: jest.fn(),
+        reset: jest.fn(),
+        _isUsingNativeDriver: () => false,
+      };
       const cb = jest.fn();
 
-      const loop = Animated.loop(animation, { anotherKey: 'value' });
+      const loop = Animated.loop(animation, {anotherKey: 'value'});
 
       expect(animation.start).not.toBeCalled();
 
@@ -315,10 +329,14 @@ describe('Animated tests', () => {
     });
 
     it('loops three times if iterations is 3', () => {
-      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const animation = {
+        start: jest.fn(),
+        reset: jest.fn(),
+        _isUsingNativeDriver: () => false,
+      };
       const cb = jest.fn();
 
-      const loop = Animated.loop(animation, { iterations: 3 });
+      const loop = Animated.loop(animation, {iterations: 3});
 
       expect(animation.start).not.toBeCalled();
 
@@ -342,10 +360,14 @@ describe('Animated tests', () => {
     });
 
     it('does not loop if iterations is 1', () => {
-      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const animation = {
+        start: jest.fn(),
+        reset: jest.fn(),
+        _isUsingNativeDriver: () => false,
+      };
       const cb = jest.fn();
 
-      const loop = Animated.loop(animation, { iterations: 1 });
+      const loop = Animated.loop(animation, {iterations: 1});
 
       expect(animation.start).not.toBeCalled();
 
@@ -359,10 +381,14 @@ describe('Animated tests', () => {
     });
 
     it('does not animate if iterations is 0', () => {
-      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const animation = {
+        start: jest.fn(),
+        reset: jest.fn(),
+        _isUsingNativeDriver: () => false,
+      };
       const cb = jest.fn();
 
-      const loop = Animated.loop(animation, { iterations: 0 });
+      const loop = Animated.loop(animation, {iterations: 0});
 
       expect(animation.start).not.toBeCalled();
 
@@ -373,7 +399,11 @@ describe('Animated tests', () => {
     });
 
     it('supports interrupting an indefinite loop', () => {
-      const animation = {start: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const animation = {
+        start: jest.fn(),
+        reset: jest.fn(),
+        _isUsingNativeDriver: () => false,
+      };
       const cb = jest.fn();
 
       Animated.loop(animation).start(cb);
@@ -391,7 +421,12 @@ describe('Animated tests', () => {
     });
 
     it('supports stopping loop', () => {
-      const animation = {start: jest.fn(), stop: jest.fn(), reset: jest.fn(), _isUsingNativeDriver: () => false};
+      const animation = {
+        start: jest.fn(),
+        stop: jest.fn(),
+        reset: jest.fn(),
+        _isUsingNativeDriver: () => false,
+      };
       const cb = jest.fn();
 
       const loop = Animated.loop(animation);
@@ -409,7 +444,6 @@ describe('Animated tests', () => {
   });
 
   describe('Animated Parallel', () => {
-
     it('works with an empty parallel', () => {
       const cb = jest.fn();
       Animated.parallel([]).start(cb);
@@ -470,7 +504,6 @@ describe('Animated tests', () => {
       expect(cb).toBeCalledWith({finished: false});
     });
 
-
     it('does not call stop more than once when stopping', () => {
       const anim1 = {start: jest.fn(), stop: jest.fn()};
       const anim2 = {start: jest.fn(), stop: jest.fn()};
@@ -504,10 +537,7 @@ describe('Animated tests', () => {
     it('should call anim after delay in sequence', () => {
       const anim = {start: jest.fn(), stop: jest.fn()};
       const cb = jest.fn();
-      Animated.sequence([
-        Animated.delay(1000),
-        anim,
-      ]).start(cb);
+      Animated.sequence([Animated.delay(1000), anim]).start(cb);
       jest.runAllTimers();
       expect(anim.start.mock.calls.length).toBe(1);
       expect(cb).not.toBeCalled();
@@ -529,19 +559,14 @@ describe('Animated tests', () => {
   describe('Animated Events', () => {
     it('should map events', () => {
       const value = new Animated.Value(0);
-      const handler = Animated.event(
-        [null, {state: {foo: value}}],
-      );
+      const handler = Animated.event([null, {state: {foo: value}}]);
       handler({bar: 'ignoreBar'}, {state: {baz: 'ignoreBaz', foo: 42}});
       expect(value.__getValue()).toBe(42);
     });
     it('should call listeners', () => {
       const value = new Animated.Value(0);
       const listener = jest.fn();
-      const handler = Animated.event(
-        [{foo: value}],
-        {listener},
-      );
+      const handler = Animated.event([{foo: value}], {listener});
       handler({foo: 42});
       expect(value.__getValue()).toBe(42);
       expect(listener.mock.calls.length).toBe(1);
@@ -550,10 +575,7 @@ describe('Animated tests', () => {
     it('should call forked event listeners', () => {
       const value = new Animated.Value(0);
       const listener = jest.fn();
-      const handler = Animated.event(
-        [{foo: value}],
-        {listener},
-      );
+      const handler = Animated.event([{foo: value}], {listener});
       const listener2 = jest.fn();
       const forkedHandler = Animated.forkEvent(handler, listener2);
       forkedHandler({foo: 42});
@@ -577,7 +599,7 @@ describe('Animated tests', () => {
       InteractionManager = require('InteractionManager');
     });
 
-    afterEach(()=> {
+    afterEach(() => {
       jest.unmock('InteractionManager');
     });
 
@@ -633,7 +655,7 @@ describe('Animated tests', () => {
       Animated.timing(value2, {
         toValue: value1.interpolate({
           inputRange: [0, 2],
-          outputRange: [0, 1]
+          outputRange: [0, 1],
         }),
         duration: 0,
       }).start();
@@ -665,24 +687,24 @@ describe('Animated tests', () => {
 
       const callback = jest.fn();
 
-      const node = new Animated.__PropsOnlyForTests({
-        style: {
-          opacity: vec.x.interpolate({
-            inputRange: [0, 42],
-            outputRange: [0.2, 0.8],
-          }),
-          transform: vec.getTranslateTransform(),
-          ...vec.getLayout(),
-        }
-      }, callback);
+      const node = new Animated.__PropsOnlyForTests(
+        {
+          style: {
+            opacity: vec.x.interpolate({
+              inputRange: [0, 42],
+              outputRange: [0.2, 0.8],
+            }),
+            transform: vec.getTranslateTransform(),
+            ...vec.getLayout(),
+          },
+        },
+        callback,
+      );
 
       expect(node.__getValue()).toEqual({
         style: {
           opacity: 0.2,
-          transform: [
-            {translateX: 0},
-            {translateY: 0},
-          ],
+          transform: [{translateX: 0}, {translateY: 0}],
           left: 0,
           top: 0,
         },
@@ -695,10 +717,7 @@ describe('Animated tests', () => {
       expect(node.__getValue()).toEqual({
         style: {
           opacity: 0.8,
-          transform: [
-            {translateX: 42},
-            {translateY: 1492},
-          ],
+          transform: [{translateX: 42}, {translateY: 1492}],
           left: 42,
           top: 1492,
         },
@@ -767,7 +786,7 @@ describe('Animated tests', () => {
     it('should removeAll', () => {
       const value1 = new Animated.Value(0);
       const listener = jest.fn();
-      [1,2,3,4].forEach(() => value1.addListener(listener));
+      [1, 2, 3, 4].forEach(() => value1.addListener(listener));
       value1.setValue(42);
       expect(listener.mock.calls.length).toBe(4);
       expect(listener).toBeCalledWith({value: 42});
diff --git a/Libraries/Animated/src/__tests__/AnimatedNative-test.js b/Libraries/Animated/src/__tests__/AnimatedNative-test.js
index f04d5afb1429..8f59d33c57cb 100644
--- a/Libraries/Animated/src/__tests__/AnimatedNative-test.js
+++ b/Libraries/Animated/src/__tests__/AnimatedNative-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const ClassComponentMock = class {};
@@ -39,7 +41,6 @@ function createAndMountComponent(ComponentClass, props) {
 }
 
 describe('Native Animated', () => {
-
   const nativeAnimatedModule = require('NativeModules').NativeAnimatedModule;
 
   beforeEach(() => {
@@ -64,7 +65,11 @@ describe('Native Animated', () => {
   describe('Animated Value', () => {
     it('proxies `setValue` correctly', () => {
       const anim = new Animated.Value(0);
-      Animated.timing(anim, {toValue: 10, duration: 1000, useNativeDriver: true}).start();
+      Animated.timing(anim, {
+        toValue: 10,
+        duration: 1000,
+        useNativeDriver: true,
+      }).start();
 
       const c = createAndMountComponent(Animated.View, {
         style: {
@@ -82,7 +87,10 @@ describe('Native Animated', () => {
 
       anim.setValue(0.5);
 
-      expect(nativeAnimatedModule.setAnimatedNodeValue).toBeCalledWith(expect.any(Number), 0.5);
+      expect(nativeAnimatedModule.setAnimatedNodeValue).toBeCalledWith(
+        expect.any(Number),
+        0.5,
+      );
       expect(c.refs.node.setNativeProps).not.toHaveBeenCalled();
     });
 
@@ -101,8 +109,10 @@ describe('Native Animated', () => {
         {type: 'value', value: 0, offset: 10},
       );
       anim.setOffset(20);
-      expect(nativeAnimatedModule.setAnimatedNodeOffset)
-        .toBeCalledWith(expect.any(Number), 20);
+      expect(nativeAnimatedModule.setAnimatedNodeOffset).toBeCalledWith(
+        expect.any(Number),
+        20,
+      );
     });
 
     it('should flatten offset', () => {
@@ -119,8 +129,9 @@ describe('Native Animated', () => {
         {type: 'value', value: 0, offset: 0},
       );
       anim.flattenOffset();
-      expect(nativeAnimatedModule.flattenAnimatedNodeOffset)
-        .toBeCalledWith(expect.any(Number));
+      expect(nativeAnimatedModule.flattenAnimatedNodeOffset).toBeCalledWith(
+        expect.any(Number),
+      );
     });
 
     it('should extract offset', () => {
@@ -137,8 +148,9 @@ describe('Native Animated', () => {
         {type: 'value', value: 0, offset: 0},
       );
       anim.extractOffset();
-      expect(nativeAnimatedModule.extractAnimatedNodeOffset)
-        .toBeCalledWith(expect.any(Number));
+      expect(nativeAnimatedModule.extractAnimatedNodeOffset).toBeCalledWith(
+        expect.any(Number),
+      );
     });
   });
 
@@ -148,33 +160,35 @@ describe('Native Animated', () => {
       value1.__makeNative();
       const listener = jest.fn();
       const id = value1.addListener(listener);
-      expect(nativeAnimatedModule.startListeningToAnimatedNodeValue)
-        .toHaveBeenCalledWith(value1.__getNativeTag());
+      expect(
+        nativeAnimatedModule.startListeningToAnimatedNodeValue,
+      ).toHaveBeenCalledWith(value1.__getNativeTag());
 
-      NativeAnimatedHelper.nativeEventEmitter.emit(
-        'onAnimatedValueUpdate',
-        {value: 42, tag: value1.__getNativeTag()},
-      );
+      NativeAnimatedHelper.nativeEventEmitter.emit('onAnimatedValueUpdate', {
+        value: 42,
+        tag: value1.__getNativeTag(),
+      });
       expect(listener).toHaveBeenCalledTimes(1);
       expect(listener).toBeCalledWith({value: 42});
       expect(value1.__getValue()).toBe(42);
 
-      NativeAnimatedHelper.nativeEventEmitter.emit(
-        'onAnimatedValueUpdate',
-        {value: 7, tag: value1.__getNativeTag()},
-      );
+      NativeAnimatedHelper.nativeEventEmitter.emit('onAnimatedValueUpdate', {
+        value: 7,
+        tag: value1.__getNativeTag(),
+      });
       expect(listener).toHaveBeenCalledTimes(2);
       expect(listener).toBeCalledWith({value: 7});
       expect(value1.__getValue()).toBe(7);
 
       value1.removeListener(id);
-      expect(nativeAnimatedModule.stopListeningToAnimatedNodeValue)
-        .toHaveBeenCalledWith(value1.__getNativeTag());
+      expect(
+        nativeAnimatedModule.stopListeningToAnimatedNodeValue,
+      ).toHaveBeenCalledWith(value1.__getNativeTag());
 
-      NativeAnimatedHelper.nativeEventEmitter.emit(
-        'onAnimatedValueUpdate',
-        {value: 1492, tag: value1.__getNativeTag()},
-      );
+      NativeAnimatedHelper.nativeEventEmitter.emit('onAnimatedValueUpdate', {
+        value: 1492,
+        tag: value1.__getNativeTag(),
+      });
       expect(listener).toHaveBeenCalledTimes(2);
       expect(value1.__getValue()).toBe(7);
     });
@@ -183,25 +197,27 @@ describe('Native Animated', () => {
       const value1 = new Animated.Value(0);
       value1.__makeNative();
       const listener = jest.fn();
-      [1,2,3,4].forEach(() => value1.addListener(listener));
-      expect(nativeAnimatedModule.startListeningToAnimatedNodeValue)
-        .toHaveBeenCalledWith(value1.__getNativeTag());
-
-      NativeAnimatedHelper.nativeEventEmitter.emit(
-        'onAnimatedValueUpdate',
-        {value: 42, tag: value1.__getNativeTag()},
-      );
+      [1, 2, 3, 4].forEach(() => value1.addListener(listener));
+      expect(
+        nativeAnimatedModule.startListeningToAnimatedNodeValue,
+      ).toHaveBeenCalledWith(value1.__getNativeTag());
+
+      NativeAnimatedHelper.nativeEventEmitter.emit('onAnimatedValueUpdate', {
+        value: 42,
+        tag: value1.__getNativeTag(),
+      });
       expect(listener).toHaveBeenCalledTimes(4);
       expect(listener).toBeCalledWith({value: 42});
 
       value1.removeAllListeners();
-      expect(nativeAnimatedModule.stopListeningToAnimatedNodeValue)
-        .toHaveBeenCalledWith(value1.__getNativeTag());
+      expect(
+        nativeAnimatedModule.stopListeningToAnimatedNodeValue,
+      ).toHaveBeenCalledWith(value1.__getNativeTag());
 
-      NativeAnimatedHelper.nativeEventEmitter.emit(
-        'onAnimatedValueUpdate',
-        {value: 7, tag: value1.__getNativeTag()},
-      );
+      NativeAnimatedHelper.nativeEventEmitter.emit('onAnimatedValueUpdate', {
+        value: 7,
+        tag: value1.__getNativeTag(),
+      });
       expect(listener).toHaveBeenCalledTimes(4);
     });
   });
@@ -210,15 +226,17 @@ describe('Native Animated', () => {
     it('should map events', () => {
       const value = new Animated.Value(0);
       value.__makeNative();
-      const event = Animated.event(
-        [{nativeEvent: {state: {foo: value}}}],
-        {useNativeDriver: true},
-      );
+      const event = Animated.event([{nativeEvent: {state: {foo: value}}}], {
+        useNativeDriver: true,
+      });
       const c = createAndMountComponent(Animated.View, {onTouchMove: event});
       expect(nativeAnimatedModule.addAnimatedEventToView).toBeCalledWith(
         expect.any(Number),
         'onTouchMove',
-        {nativeEventPath: ['state', 'foo'], animatedValueTag: value.__getNativeTag()},
+        {
+          nativeEventPath: ['state', 'foo'],
+          animatedValueTag: value.__getNativeTag(),
+        },
       );
 
       c.componentWillUnmount();
@@ -232,12 +250,12 @@ describe('Native Animated', () => {
     it('should throw on invalid event path', () => {
       const value = new Animated.Value(0);
       value.__makeNative();
-      const event = Animated.event(
-        [{notNativeEvent: {foo: value}}],
-        {useNativeDriver: true},
-      );
-      expect(() => createAndMountComponent(Animated.View, {onTouchMove: event}))
-        .toThrowError(/nativeEvent/);
+      const event = Animated.event([{notNativeEvent: {foo: value}}], {
+        useNativeDriver: true,
+      });
+      expect(() =>
+        createAndMountComponent(Animated.View, {onTouchMove: event}),
+      ).toThrowError(/nativeEvent/);
       expect(nativeAnimatedModule.addAnimatedEventToView).not.toBeCalled();
     });
 
@@ -245,10 +263,10 @@ describe('Native Animated', () => {
       const value = new Animated.Value(0);
       value.__makeNative();
       const listener = jest.fn();
-      const event = Animated.event(
-        [{nativeEvent: {foo: value}}],
-        {useNativeDriver: true, listener},
-      );
+      const event = Animated.event([{nativeEvent: {foo: value}}], {
+        useNativeDriver: true,
+        listener,
+      });
       const handler = event.__getHandler();
       handler({foo: 42});
       expect(listener).toHaveBeenCalledTimes(1);
@@ -265,21 +283,34 @@ describe('Native Animated', () => {
         },
       });
 
-      Animated.timing(anim, {toValue: 10, duration: 1000, useNativeDriver: true}).start();
+      Animated.timing(anim, {
+        toValue: 10,
+        duration: 1000,
+        useNativeDriver: true,
+      }).start();
 
       c.componentWillUnmount();
 
       expect(nativeAnimatedModule.createAnimatedNode).toHaveBeenCalledTimes(3);
-      expect(nativeAnimatedModule.connectAnimatedNodes).toHaveBeenCalledTimes(2);
+      expect(nativeAnimatedModule.connectAnimatedNodes).toHaveBeenCalledTimes(
+        2,
+      );
 
       expect(nativeAnimatedModule.startAnimatingNode).toBeCalledWith(
         expect.any(Number),
         expect.any(Number),
-        {type: 'frames', frames: expect.any(Array), toValue: expect.any(Number), iterations: 1},
-        expect.any(Function)
+        {
+          type: 'frames',
+          frames: expect.any(Array),
+          toValue: expect.any(Number),
+          iterations: 1,
+        },
+        expect.any(Function),
       );
 
-      expect(nativeAnimatedModule.disconnectAnimatedNodes).toHaveBeenCalledTimes(2);
+      expect(
+        nativeAnimatedModule.disconnectAnimatedNodes,
+      ).toHaveBeenCalledTimes(2);
       expect(nativeAnimatedModule.dropAnimatedNode).toHaveBeenCalledTimes(3);
     });
 
@@ -291,14 +322,24 @@ describe('Native Animated', () => {
         },
       });
 
-      Animated.timing(anim, {toValue: 10, duration: 1000, useNativeDriver: true}).start();
+      Animated.timing(anim, {
+        toValue: 10,
+        duration: 1000,
+        useNativeDriver: true,
+      }).start();
 
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(expect.any(Number), {type: 'value', value: 0, offset: 0});
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(expect.any(Number), {type: 'style', style: {opacity: expect.any(Number)}});
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(expect.any(Number), {type: 'props', props: {style: expect.any(Number)}});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        expect.any(Number),
+        {type: 'value', value: 0, offset: 0},
+      );
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        expect.any(Number),
+        {type: 'style', style: {opacity: expect.any(Number)}},
+      );
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        expect.any(Number),
+        {type: 'props', props: {style: expect.any(Number)}},
+      );
     });
 
     it('sends a valid graph description for Animated.add nodes', () => {
@@ -318,19 +359,23 @@ describe('Native Animated', () => {
         {type: 'addition', input: expect.any(Array)},
       );
       const additionCalls = nativeAnimatedModule.createAnimatedNode.mock.calls.filter(
-        (call) => call[1].type === 'addition'
+        call => call[1].type === 'addition',
       );
       expect(additionCalls.length).toBe(1);
       const additionCall = additionCalls[0];
       const additionNodeTag = additionCall[0];
       const additionConnectionCalls = nativeAnimatedModule.connectAnimatedNodes.mock.calls.filter(
-        (call) => call[1] === additionNodeTag
+        call => call[1] === additionNodeTag,
       );
       expect(additionConnectionCalls.length).toBe(2);
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(additionCall[1].input[0], {type: 'value', value: 1, offset: 0});
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(additionCall[1].input[1], {type: 'value', value: 2, offset: 0});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        additionCall[1].input[0],
+        {type: 'value', value: 1, offset: 0},
+      );
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        additionCall[1].input[1],
+        {type: 'value', value: 2, offset: 0},
+      );
     });
 
     it('sends a valid graph description for Animated.subtract nodes', () => {
@@ -350,19 +395,23 @@ describe('Native Animated', () => {
         {type: 'subtraction', input: expect.any(Array)},
       );
       const subtractionCalls = nativeAnimatedModule.createAnimatedNode.mock.calls.filter(
-        (call) => call[1].type === 'subtraction'
+        call => call[1].type === 'subtraction',
       );
       expect(subtractionCalls.length).toBe(1);
       const subtractionCall = subtractionCalls[0];
       const subtractionNodeTag = subtractionCall[0];
       const subtractionConnectionCalls = nativeAnimatedModule.connectAnimatedNodes.mock.calls.filter(
-        (call) => call[1] === subtractionNodeTag
+        call => call[1] === subtractionNodeTag,
       );
       expect(subtractionConnectionCalls.length).toBe(2);
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(subtractionCall[1].input[0], {type: 'value', value: 2, offset: 0});
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(subtractionCall[1].input[1], {type: 'value', value: 1, offset: 0});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        subtractionCall[1].input[0],
+        {type: 'value', value: 2, offset: 0},
+      );
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        subtractionCall[1].input[1],
+        {type: 'value', value: 1, offset: 0},
+      );
     });
 
     it('sends a valid graph description for Animated.multiply nodes', () => {
@@ -382,19 +431,23 @@ describe('Native Animated', () => {
         {type: 'multiplication', input: expect.any(Array)},
       );
       const multiplicationCalls = nativeAnimatedModule.createAnimatedNode.mock.calls.filter(
-        (call) => call[1].type === 'multiplication'
+        call => call[1].type === 'multiplication',
       );
       expect(multiplicationCalls.length).toBe(1);
       const multiplicationCall = multiplicationCalls[0];
       const multiplicationNodeTag = multiplicationCall[0];
       const multiplicationConnectionCalls = nativeAnimatedModule.connectAnimatedNodes.mock.calls.filter(
-        (call) => call[1] === multiplicationNodeTag
+        call => call[1] === multiplicationNodeTag,
       );
       expect(multiplicationConnectionCalls.length).toBe(2);
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(multiplicationCall[1].input[0], {type: 'value', value: 2, offset: 0});
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(multiplicationCall[1].input[1], {type: 'value', value: 1, offset: 0});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        multiplicationCall[1].input[0],
+        {type: 'value', value: 2, offset: 0},
+      );
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        multiplicationCall[1].input[1],
+        {type: 'value', value: 1, offset: 0},
+      );
     });
 
     it('sends a valid graph description for Animated.divide nodes', () => {
@@ -409,22 +462,28 @@ describe('Native Animated', () => {
         },
       });
 
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(expect.any(Number), {type: 'division', input: expect.any(Array)});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        expect.any(Number),
+        {type: 'division', input: expect.any(Array)},
+      );
       const divisionCalls = nativeAnimatedModule.createAnimatedNode.mock.calls.filter(
-        (call) => call[1].type === 'division'
+        call => call[1].type === 'division',
       );
       expect(divisionCalls.length).toBe(1);
       const divisionCall = divisionCalls[0];
       const divisionNodeTag = divisionCall[0];
       const divisionConnectionCalls = nativeAnimatedModule.connectAnimatedNodes.mock.calls.filter(
-        (call) => call[1] === divisionNodeTag
+        call => call[1] === divisionNodeTag,
       );
       expect(divisionConnectionCalls.length).toBe(2);
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(divisionCall[1].input[0], {type: 'value', value: 4, offset: 0});
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(divisionCall[1].input[1], {type: 'value', value: 2, offset: 0});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        divisionCall[1].input[0],
+        {type: 'value', value: 4, offset: 0},
+      );
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        divisionCall[1].input[1],
+        {type: 'value', value: 2, offset: 0},
+      );
     });
 
     it('sends a valid graph description for Animated.modulo nodes', () => {
@@ -442,17 +501,19 @@ describe('Native Animated', () => {
         {type: 'modulus', modulus: 4, input: expect.any(Number)},
       );
       const moduloCalls = nativeAnimatedModule.createAnimatedNode.mock.calls.filter(
-        (call) => call[1].type === 'modulus'
+        call => call[1].type === 'modulus',
       );
       expect(moduloCalls.length).toBe(1);
       const moduloCall = moduloCalls[0];
       const moduloNodeTag = moduloCall[0];
       const moduloConnectionCalls = nativeAnimatedModule.connectAnimatedNodes.mock.calls.filter(
-        (call) => call[1] === moduloNodeTag
+        call => call[1] === moduloNodeTag,
       );
       expect(moduloConnectionCalls.length).toBe(1);
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(moduloCall[1].input, {type: 'value', value: 4, offset: 0});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        moduloCall[1].input,
+        {type: 'value', value: 4, offset: 0},
+      );
     });
 
     it('sends a valid graph description for interpolate() nodes', () => {
@@ -470,23 +531,28 @@ describe('Native Animated', () => {
 
       expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
         expect.any(Number),
-        {type: 'value', value: 10, offset: 0}
+        {type: 'value', value: 10, offset: 0},
       );
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(expect.any(Number), {
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        expect.any(Number),
+        {
           type: 'interpolation',
           inputRange: [10, 20],
           outputRange: [0, 1],
           extrapolateLeft: 'extend',
           extrapolateRight: 'extend',
-        });
+        },
+      );
       const interpolationNodeTag = nativeAnimatedModule.createAnimatedNode.mock.calls.find(
-        (call) => call[1].type === 'interpolation'
+        call => call[1].type === 'interpolation',
       )[0];
       const valueNodeTag = nativeAnimatedModule.createAnimatedNode.mock.calls.find(
-        (call) => call[1].type === 'value'
+        call => call[1].type === 'value',
       )[0];
-      expect(nativeAnimatedModule.connectAnimatedNodes).toBeCalledWith(valueNodeTag, interpolationNodeTag);
+      expect(nativeAnimatedModule.connectAnimatedNodes).toBeCalledWith(
+        valueNodeTag,
+        interpolationNodeTag,
+      );
     });
 
     it('sends a valid graph description for transform nodes', () => {
@@ -503,15 +569,18 @@ describe('Native Animated', () => {
         expect.any(Number),
         {
           type: 'transform',
-          transforms: [{
-            nodeTag: expect.any(Number),
-            property: 'translateX',
-            type: 'animated',
-          }, {
-            value: 2,
-            property: 'scale',
-            type: 'static',
-          }],
+          transforms: [
+            {
+              nodeTag: expect.any(Number),
+              property: 'translateX',
+              type: 'animated',
+            },
+            {
+              value: 2,
+              property: 'scale',
+              type: 'static',
+            },
+          ],
         },
       );
     });
@@ -531,20 +600,22 @@ describe('Native Animated', () => {
         {type: 'diffclamp', input: expect.any(Number), max: 20, min: 0},
       );
       const diffClampCalls = nativeAnimatedModule.createAnimatedNode.mock.calls.filter(
-        (call) => call[1].type === 'diffclamp'
+        call => call[1].type === 'diffclamp',
       );
       expect(diffClampCalls.length).toBe(1);
       const diffClampCall = diffClampCalls[0];
       const diffClampNodeTag = diffClampCall[0];
       const diffClampConnectionCalls = nativeAnimatedModule.connectAnimatedNodes.mock.calls.filter(
-        (call) => call[1] === diffClampNodeTag
+        call => call[1] === diffClampNodeTag,
       );
       expect(diffClampConnectionCalls.length).toBe(1);
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(diffClampCall[1].input, {type: 'value', value: 2, offset: 0});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        diffClampCall[1].input,
+        {type: 'value', value: 2, offset: 0},
+      );
     });
 
-    it('doesn\'t call into native API if useNativeDriver is set to false', () => {
+    it("doesn't call into native API if useNativeDriver is set to false", () => {
       const anim = new Animated.Value(0);
 
       const c = createAndMountComponent(Animated.View, {
@@ -553,7 +624,11 @@ describe('Native Animated', () => {
         },
       });
 
-      Animated.timing(anim, {toValue: 10, duration: 1000, useNativeDriver: false}).start();
+      Animated.timing(anim, {
+        toValue: 10,
+        duration: 1000,
+        useNativeDriver: false,
+      }).start();
 
       c.componentWillUnmount();
 
@@ -569,10 +644,18 @@ describe('Native Animated', () => {
         },
       });
 
-      Animated.timing(anim, {toValue: 10, duration: 50, useNativeDriver: true}).start();
+      Animated.timing(anim, {
+        toValue: 10,
+        duration: 50,
+        useNativeDriver: true,
+      }).start();
       jest.runAllTimers();
 
-      Animated.timing(anim, {toValue: 4, duration: 500, useNativeDriver: false}).start();
+      Animated.timing(anim, {
+        toValue: 4,
+        duration: 500,
+        useNativeDriver: false,
+      }).start();
       expect(jest.runAllTimers).toThrow();
     });
 
@@ -585,7 +668,11 @@ describe('Native Animated', () => {
         },
       });
 
-      const animation = Animated.timing(anim, {toValue: 10, duration: 50, useNativeDriver: true});
+      const animation = Animated.timing(anim, {
+        toValue: 10,
+        duration: 50,
+        useNativeDriver: true,
+      });
       expect(animation.start).toThrowError(/left/);
     });
 
@@ -603,29 +690,47 @@ describe('Native Animated', () => {
         removeClippedSubviews: true,
       });
 
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(expect.any(Number), { type: 'style', style: { opacity: expect.any(Number) }});
-      expect(nativeAnimatedModule.createAnimatedNode)
-        .toBeCalledWith(expect.any(Number), { type: 'props', props: { style: expect.any(Number) }});
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        expect.any(Number),
+        {type: 'style', style: {opacity: expect.any(Number)}},
+      );
+      expect(nativeAnimatedModule.createAnimatedNode).toBeCalledWith(
+        expect.any(Number),
+        {type: 'props', props: {style: expect.any(Number)}},
+      );
     });
   });
 
   describe('Animations', () => {
     it('sends a valid timing animation description', () => {
       const anim = new Animated.Value(0);
-      Animated.timing(anim, {toValue: 10, duration: 1000, useNativeDriver: true}).start();
+      Animated.timing(anim, {
+        toValue: 10,
+        duration: 1000,
+        useNativeDriver: true,
+      }).start();
 
       expect(nativeAnimatedModule.startAnimatingNode).toBeCalledWith(
         expect.any(Number),
         expect.any(Number),
-        {type: 'frames', frames: expect.any(Array), toValue: expect.any(Number), iterations: 1},
-        expect.any(Function)
+        {
+          type: 'frames',
+          frames: expect.any(Array),
+          toValue: expect.any(Number),
+          iterations: 1,
+        },
+        expect.any(Function),
       );
     });
 
     it('sends a valid spring animation description', () => {
       const anim = new Animated.Value(0);
-      Animated.spring(anim, {toValue: 10, friction: 5, tension: 164, useNativeDriver: true}).start();
+      Animated.spring(anim, {
+        toValue: 10,
+        friction: 5,
+        tension: 164,
+        useNativeDriver: true,
+      }).start();
       expect(nativeAnimatedModule.startAnimatingNode).toBeCalledWith(
         expect.any(Number),
         expect.any(Number),
@@ -641,7 +746,7 @@ describe('Native Animated', () => {
           toValue: 10,
           iterations: 1,
         },
-        expect.any(Function)
+        expect.any(Function),
       );
 
       Animated.spring(anim, {
@@ -649,7 +754,7 @@ describe('Native Animated', () => {
         stiffness: 1000,
         damping: 500,
         mass: 3,
-        useNativeDriver: true
+        useNativeDriver: true,
       }).start();
       expect(nativeAnimatedModule.startAnimatingNode).toBeCalledWith(
         expect.any(Number),
@@ -666,10 +771,15 @@ describe('Native Animated', () => {
           toValue: 10,
           iterations: 1,
         },
-        expect.any(Function)
+        expect.any(Function),
       );
 
-      Animated.spring(anim, {toValue: 10, bounciness: 8, speed: 10, useNativeDriver: true}).start();
+      Animated.spring(anim, {
+        toValue: 10,
+        bounciness: 8,
+        speed: 10,
+        useNativeDriver: true,
+      }).start();
       expect(nativeAnimatedModule.startAnimatingNode).toBeCalledWith(
         expect.any(Number),
         expect.any(Number),
@@ -685,49 +795,67 @@ describe('Native Animated', () => {
           toValue: 10,
           iterations: 1,
         },
-        expect.any(Function)
+        expect.any(Function),
       );
     });
 
     it('sends a valid decay animation description', () => {
       const anim = new Animated.Value(0);
-      Animated.decay(anim, {velocity: 10, deceleration: 0.1, useNativeDriver: true}).start();
+      Animated.decay(anim, {
+        velocity: 10,
+        deceleration: 0.1,
+        useNativeDriver: true,
+      }).start();
 
       expect(nativeAnimatedModule.startAnimatingNode).toBeCalledWith(
         expect.any(Number),
         expect.any(Number),
         {type: 'decay', deceleration: 0.1, velocity: 10, iterations: 1},
-        expect.any(Function)
+        expect.any(Function),
       );
     });
 
     it('works with Animated.loop', () => {
       const anim = new Animated.Value(0);
       Animated.loop(
-        Animated.decay(anim, {velocity: 10, deceleration: 0.1, useNativeDriver: true}),
-        { iterations: 10 },
+        Animated.decay(anim, {
+          velocity: 10,
+          deceleration: 0.1,
+          useNativeDriver: true,
+        }),
+        {iterations: 10},
       ).start();
 
       expect(nativeAnimatedModule.startAnimatingNode).toBeCalledWith(
         expect.any(Number),
         expect.any(Number),
         {type: 'decay', deceleration: 0.1, velocity: 10, iterations: 10},
-        expect.any(Function)
+        expect.any(Function),
       );
     });
 
     it('sends stopAnimation command to native', () => {
       const value = new Animated.Value(0);
-      const animation = Animated.timing(value, {toValue: 10, duration: 50, useNativeDriver: true});
+      const animation = Animated.timing(value, {
+        toValue: 10,
+        duration: 50,
+        useNativeDriver: true,
+      });
 
       animation.start();
       expect(nativeAnimatedModule.startAnimatingNode).toBeCalledWith(
         expect.any(Number),
         expect.any(Number),
-        {type: 'frames', frames: expect.any(Array), toValue: expect.any(Number), iterations: 1},
-        expect.any(Function)
+        {
+          type: 'frames',
+          frames: expect.any(Array),
+          toValue: expect.any(Number),
+          iterations: 1,
+        },
+        expect.any(Function),
       );
-      const animationId = nativeAnimatedModule.startAnimatingNode.mock.calls[0][0];
+      const animationId =
+        nativeAnimatedModule.startAnimatingNode.mock.calls[0][0];
 
       animation.stop();
       expect(nativeAnimatedModule.stopAnimation).toBeCalledWith(animationId);
diff --git a/Libraries/Animated/src/__tests__/Easing-test.js b/Libraries/Animated/src/__tests__/Easing-test.js
index ae6cd3368682..1e2a3a2f4a7c 100644
--- a/Libraries/Animated/src/__tests__/Easing-test.js
+++ b/Libraries/Animated/src/__tests__/Easing-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const Easing = require('Easing');
@@ -88,23 +90,363 @@ describe('Easing', () => {
   }
 
   const Samples = {
-    in_quad: [0,0.0030864197530864196,0.012345679012345678,0.027777777777777776,0.04938271604938271,0.0771604938271605,0.1111111111111111,0.15123456790123457,0.19753086419753085,0.25,0.308641975308642,0.37345679012345684,0.4444444444444444,0.5216049382716049,0.6049382716049383,0.6944444444444445,0.7901234567901234,0.8919753086419753,1],
-    out_quad: [0,0.10802469135802469,0.20987654320987653,0.3055555555555555,0.3950617283950617,0.47839506172839513,0.5555555555555556,0.6265432098765432,0.691358024691358,0.75,0.8024691358024691,0.8487654320987654,0.888888888888889,0.9228395061728394,0.9506172839506174,0.9722222222222221,0.9876543209876543,0.9969135802469136,1],
-    inOut_quad: [0,0.006172839506172839,0.024691358024691357,0.05555555555555555,0.09876543209876543,0.154320987654321,0.2222222222222222,0.30246913580246915,0.3950617283950617,0.5,0.6049382716049383,0.697530864197531,0.7777777777777777,0.845679012345679,0.9012345679012346,0.9444444444444444,0.9753086419753086,0.9938271604938271,1],
-    in_cubic: [0,0.00017146776406035664,0.0013717421124828531,0.004629629629629629,0.010973936899862825,0.021433470507544586,0.037037037037037035,0.05881344307270234,0.0877914951989026,0.125,0.1714677640603567,0.22822359396433475,0.2962962962962963,0.37671467764060357,0.4705075445816187,0.5787037037037038,0.7023319615912208,0.8424211248285322,1],
-    out_cubic: [0,0.15757887517146785,0.2976680384087792,0.42129629629629617,0.5294924554183813,0.6232853223593964,0.7037037037037036,0.7717764060356652,0.8285322359396433,0.875,0.9122085048010974,0.9411865569272977,0.9629629629629629,0.9785665294924554,0.9890260631001372,0.9953703703703703,0.9986282578875172,0.9998285322359396,1],
-    inOut_cubic: [0,0.0006858710562414266,0.0054869684499314125,0.018518518518518517,0.0438957475994513,0.08573388203017834,0.14814814814814814,0.23525377229080935,0.3511659807956104,0.5,0.6488340192043895,0.7647462277091908,0.8518518518518519,0.9142661179698217,0.9561042524005487,0.9814814814814815,0.9945130315500685,0.9993141289437586,1],
-    in_sin: [0,0.003805301908254455,0.01519224698779198,0.03407417371093169,0.06030737921409157,0.09369221296335006,0.1339745962155613,0.1808479557110082,0.233955556881022,0.2928932188134524,0.35721239031346064,0.42642356364895384,0.4999999999999999,0.5773817382593005,0.6579798566743311,0.7411809548974793,0.8263518223330696,0.9128442572523416,0.9999999999999999],
-    out_sin: [0,0.08715574274765817,0.17364817766693033,0.25881904510252074,0.3420201433256687,0.42261826174069944,0.49999999999999994,0.573576436351046,0.6427876096865393,0.7071067811865475,0.766044443118978,0.8191520442889918,0.8660254037844386,0.9063077870366499,0.9396926207859083,0.9659258262890683,0.984807753012208,0.9961946980917455,1],
-    inOut_sin: [0,0.00759612349389599,0.030153689607045786,0.06698729810778065,0.116977778440511,0.17860619515673032,0.24999999999999994,0.32898992833716556,0.4131759111665348,0.49999999999999994,0.5868240888334652,0.6710100716628343,0.7499999999999999,0.8213938048432696,0.883022221559489,0.9330127018922194,0.9698463103929542,0.9924038765061041,1],
-    in_exp: [0,0.0014352875901128893,0.002109491677524035,0.0031003926796253885,0.004556754060844206,0.006697218616039631,0.009843133202303688,0.014466792379488908,0.021262343752724643,0.03125,0.045929202883612456,0.06750373368076916,0.09921256574801243,0.1458161299470146,0.2143109957132682,0.31498026247371835,0.46293735614364506,0.6803950000871883,1],
-    out_exp: [0,0.31960499991281155,0.5370626438563548,0.6850197375262816,0.7856890042867318,0.8541838700529854,0.9007874342519875,0.9324962663192309,0.9540707971163875,0.96875,0.9787376562472754,0.9855332076205111,0.9901568667976963,0.9933027813839603,0.9954432459391558,0.9968996073203746,0.9978905083224759,0.9985647124098871,1],
-    inOut_exp: [0,0.0010547458387620175,0.002278377030422103,0.004921566601151844,0.010631171876362321,0.022964601441806228,0.049606282874006216,0.1071554978566341,0.23146867807182253,0.5,0.7685313219281775,0.892844502143366,0.9503937171259937,0.9770353985581938,0.9893688281236377,0.9950784333988482,0.9977216229695779,0.998945254161238,1],
-    in_circle: [0,0.0015444024660317135,0.006192010000093506,0.013986702816730645,0.025003956956430873,0.03935464078941209,0.057190958417936644,0.07871533601238889,0.10419358352238339,0.1339745962155614,0.1685205807169019,0.20845517506805522,0.2546440075000701,0.3083389112228482,0.37146063894529113,0.4472292016074334,0.5418771527091488,0.6713289009389102,1],
-    out_circle: [0,0.3286710990610898,0.45812284729085123,0.5527707983925666,0.6285393610547089,0.6916610887771518,0.7453559924999298,0.7915448249319448,0.8314794192830981,0.8660254037844386,0.8958064164776166,0.9212846639876111,0.9428090415820634,0.9606453592105879,0.9749960430435691,0.9860132971832694,0.9938079899999065,0.9984555975339683,1],
-    inOut_circle: [0,0.003096005000046753,0.012501978478215436,0.028595479208968322,0.052096791761191696,0.08426029035845095,0.12732200375003505,0.18573031947264557,0.2709385763545744,0.5,0.7290614236454256,0.8142696805273546,0.8726779962499649,0.915739709641549,0.9479032082388084,0.9714045207910317,0.9874980215217846,0.9969039949999532,1],
-    in_back_: [0,-0.004788556241426612,-0.017301289437585736,-0.0347587962962963,-0.05438167352537723,-0.07339051783264748,-0.08900592592592595,-0.09844849451303156,-0.0989388203017833,-0.08769750000000004,-0.06194513031550073,-0.018902307956104283,0.044210370370370254,0.13017230795610413,0.2417629080932785,0.3817615740740742,0.5529477091906719,0.7581007167352535,0.9999999999999998],
-    out_back_: [2.220446049250313e-16,0.24189928326474652,0.44705229080932807,0.6182384259259258,0.7582370919067215,0.8698276920438959,0.9557896296296297,1.0189023079561044,1.0619451303155008,1.0876975,1.0989388203017834,1.0984484945130315,1.089005925925926,1.0733905178326475,1.0543816735253773,1.0347587962962963,1.0173012894375857,1.0047885562414267,1],
+    in_quad: [
+      0,
+      0.0030864197530864196,
+      0.012345679012345678,
+      0.027777777777777776,
+      0.04938271604938271,
+      0.0771604938271605,
+      0.1111111111111111,
+      0.15123456790123457,
+      0.19753086419753085,
+      0.25,
+      0.308641975308642,
+      0.37345679012345684,
+      0.4444444444444444,
+      0.5216049382716049,
+      0.6049382716049383,
+      0.6944444444444445,
+      0.7901234567901234,
+      0.8919753086419753,
+      1,
+    ],
+    out_quad: [
+      0,
+      0.10802469135802469,
+      0.20987654320987653,
+      0.3055555555555555,
+      0.3950617283950617,
+      0.47839506172839513,
+      0.5555555555555556,
+      0.6265432098765432,
+      0.691358024691358,
+      0.75,
+      0.8024691358024691,
+      0.8487654320987654,
+      0.888888888888889,
+      0.9228395061728394,
+      0.9506172839506174,
+      0.9722222222222221,
+      0.9876543209876543,
+      0.9969135802469136,
+      1,
+    ],
+    inOut_quad: [
+      0,
+      0.006172839506172839,
+      0.024691358024691357,
+      0.05555555555555555,
+      0.09876543209876543,
+      0.154320987654321,
+      0.2222222222222222,
+      0.30246913580246915,
+      0.3950617283950617,
+      0.5,
+      0.6049382716049383,
+      0.697530864197531,
+      0.7777777777777777,
+      0.845679012345679,
+      0.9012345679012346,
+      0.9444444444444444,
+      0.9753086419753086,
+      0.9938271604938271,
+      1,
+    ],
+    in_cubic: [
+      0,
+      0.00017146776406035664,
+      0.0013717421124828531,
+      0.004629629629629629,
+      0.010973936899862825,
+      0.021433470507544586,
+      0.037037037037037035,
+      0.05881344307270234,
+      0.0877914951989026,
+      0.125,
+      0.1714677640603567,
+      0.22822359396433475,
+      0.2962962962962963,
+      0.37671467764060357,
+      0.4705075445816187,
+      0.5787037037037038,
+      0.7023319615912208,
+      0.8424211248285322,
+      1,
+    ],
+    out_cubic: [
+      0,
+      0.15757887517146785,
+      0.2976680384087792,
+      0.42129629629629617,
+      0.5294924554183813,
+      0.6232853223593964,
+      0.7037037037037036,
+      0.7717764060356652,
+      0.8285322359396433,
+      0.875,
+      0.9122085048010974,
+      0.9411865569272977,
+      0.9629629629629629,
+      0.9785665294924554,
+      0.9890260631001372,
+      0.9953703703703703,
+      0.9986282578875172,
+      0.9998285322359396,
+      1,
+    ],
+    inOut_cubic: [
+      0,
+      0.0006858710562414266,
+      0.0054869684499314125,
+      0.018518518518518517,
+      0.0438957475994513,
+      0.08573388203017834,
+      0.14814814814814814,
+      0.23525377229080935,
+      0.3511659807956104,
+      0.5,
+      0.6488340192043895,
+      0.7647462277091908,
+      0.8518518518518519,
+      0.9142661179698217,
+      0.9561042524005487,
+      0.9814814814814815,
+      0.9945130315500685,
+      0.9993141289437586,
+      1,
+    ],
+    in_sin: [
+      0,
+      0.003805301908254455,
+      0.01519224698779198,
+      0.03407417371093169,
+      0.06030737921409157,
+      0.09369221296335006,
+      0.1339745962155613,
+      0.1808479557110082,
+      0.233955556881022,
+      0.2928932188134524,
+      0.35721239031346064,
+      0.42642356364895384,
+      0.4999999999999999,
+      0.5773817382593005,
+      0.6579798566743311,
+      0.7411809548974793,
+      0.8263518223330696,
+      0.9128442572523416,
+      0.9999999999999999,
+    ],
+    out_sin: [
+      0,
+      0.08715574274765817,
+      0.17364817766693033,
+      0.25881904510252074,
+      0.3420201433256687,
+      0.42261826174069944,
+      0.49999999999999994,
+      0.573576436351046,
+      0.6427876096865393,
+      0.7071067811865475,
+      0.766044443118978,
+      0.8191520442889918,
+      0.8660254037844386,
+      0.9063077870366499,
+      0.9396926207859083,
+      0.9659258262890683,
+      0.984807753012208,
+      0.9961946980917455,
+      1,
+    ],
+    inOut_sin: [
+      0,
+      0.00759612349389599,
+      0.030153689607045786,
+      0.06698729810778065,
+      0.116977778440511,
+      0.17860619515673032,
+      0.24999999999999994,
+      0.32898992833716556,
+      0.4131759111665348,
+      0.49999999999999994,
+      0.5868240888334652,
+      0.6710100716628343,
+      0.7499999999999999,
+      0.8213938048432696,
+      0.883022221559489,
+      0.9330127018922194,
+      0.9698463103929542,
+      0.9924038765061041,
+      1,
+    ],
+    in_exp: [
+      0,
+      0.0014352875901128893,
+      0.002109491677524035,
+      0.0031003926796253885,
+      0.004556754060844206,
+      0.006697218616039631,
+      0.009843133202303688,
+      0.014466792379488908,
+      0.021262343752724643,
+      0.03125,
+      0.045929202883612456,
+      0.06750373368076916,
+      0.09921256574801243,
+      0.1458161299470146,
+      0.2143109957132682,
+      0.31498026247371835,
+      0.46293735614364506,
+      0.6803950000871883,
+      1,
+    ],
+    out_exp: [
+      0,
+      0.31960499991281155,
+      0.5370626438563548,
+      0.6850197375262816,
+      0.7856890042867318,
+      0.8541838700529854,
+      0.9007874342519875,
+      0.9324962663192309,
+      0.9540707971163875,
+      0.96875,
+      0.9787376562472754,
+      0.9855332076205111,
+      0.9901568667976963,
+      0.9933027813839603,
+      0.9954432459391558,
+      0.9968996073203746,
+      0.9978905083224759,
+      0.9985647124098871,
+      1,
+    ],
+    inOut_exp: [
+      0,
+      0.0010547458387620175,
+      0.002278377030422103,
+      0.004921566601151844,
+      0.010631171876362321,
+      0.022964601441806228,
+      0.049606282874006216,
+      0.1071554978566341,
+      0.23146867807182253,
+      0.5,
+      0.7685313219281775,
+      0.892844502143366,
+      0.9503937171259937,
+      0.9770353985581938,
+      0.9893688281236377,
+      0.9950784333988482,
+      0.9977216229695779,
+      0.998945254161238,
+      1,
+    ],
+    in_circle: [
+      0,
+      0.0015444024660317135,
+      0.006192010000093506,
+      0.013986702816730645,
+      0.025003956956430873,
+      0.03935464078941209,
+      0.057190958417936644,
+      0.07871533601238889,
+      0.10419358352238339,
+      0.1339745962155614,
+      0.1685205807169019,
+      0.20845517506805522,
+      0.2546440075000701,
+      0.3083389112228482,
+      0.37146063894529113,
+      0.4472292016074334,
+      0.5418771527091488,
+      0.6713289009389102,
+      1,
+    ],
+    out_circle: [
+      0,
+      0.3286710990610898,
+      0.45812284729085123,
+      0.5527707983925666,
+      0.6285393610547089,
+      0.6916610887771518,
+      0.7453559924999298,
+      0.7915448249319448,
+      0.8314794192830981,
+      0.8660254037844386,
+      0.8958064164776166,
+      0.9212846639876111,
+      0.9428090415820634,
+      0.9606453592105879,
+      0.9749960430435691,
+      0.9860132971832694,
+      0.9938079899999065,
+      0.9984555975339683,
+      1,
+    ],
+    inOut_circle: [
+      0,
+      0.003096005000046753,
+      0.012501978478215436,
+      0.028595479208968322,
+      0.052096791761191696,
+      0.08426029035845095,
+      0.12732200375003505,
+      0.18573031947264557,
+      0.2709385763545744,
+      0.5,
+      0.7290614236454256,
+      0.8142696805273546,
+      0.8726779962499649,
+      0.915739709641549,
+      0.9479032082388084,
+      0.9714045207910317,
+      0.9874980215217846,
+      0.9969039949999532,
+      1,
+    ],
+    in_back_: [
+      0,
+      -0.004788556241426612,
+      -0.017301289437585736,
+      -0.0347587962962963,
+      -0.05438167352537723,
+      -0.07339051783264748,
+      -0.08900592592592595,
+      -0.09844849451303156,
+      -0.0989388203017833,
+      -0.08769750000000004,
+      -0.06194513031550073,
+      -0.018902307956104283,
+      0.044210370370370254,
+      0.13017230795610413,
+      0.2417629080932785,
+      0.3817615740740742,
+      0.5529477091906719,
+      0.7581007167352535,
+      0.9999999999999998,
+    ],
+    out_back_: [
+      2.220446049250313e-16,
+      0.24189928326474652,
+      0.44705229080932807,
+      0.6182384259259258,
+      0.7582370919067215,
+      0.8698276920438959,
+      0.9557896296296297,
+      1.0189023079561044,
+      1.0619451303155008,
+      1.0876975,
+      1.0989388203017834,
+      1.0984484945130315,
+      1.089005925925926,
+      1.0733905178326475,
+      1.0543816735253773,
+      1.0347587962962963,
+      1.0173012894375857,
+      1.0047885562414267,
+      1,
+    ],
   };
 
   Object.keys(Samples).forEach(function(type) {
diff --git a/Libraries/Animated/src/__tests__/Interpolation-test.js b/Libraries/Animated/src/__tests__/Interpolation-test.js
index c2b832bcf5cf..5515f09bacd0 100644
--- a/Libraries/Animated/src/__tests__/Interpolation-test.js
+++ b/Libraries/Animated/src/__tests__/Interpolation-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const AnimatedInterpolation = require('../nodes/AnimatedInterpolation');
diff --git a/Libraries/Animated/src/__tests__/bezier-test.js b/Libraries/Animated/src/__tests__/bezier-test.js
index 16b7acc0f193..46c7f043b331 100644
--- a/Libraries/Animated/src/__tests__/bezier-test.js
+++ b/Libraries/Animated/src/__tests__/bezier-test.js
@@ -74,7 +74,10 @@ describe('bezier', function() {
   describe('common properties', function() {
     it('should be the right value at extremes', function() {
       repeat(10)(function() {
-        const a = Math.random(), b = 2 * Math.random() - 0.5, c = Math.random(), d = 2 * Math.random() - 0.5;
+        const a = Math.random(),
+          b = 2 * Math.random() - 0.5,
+          c = Math.random(),
+          d = 2 * Math.random() - 0.5;
         const easing = bezier(a, b, c, d);
         expect(easing(0)).toBe(0);
         expect(easing(1)).toBe(1);
@@ -83,7 +86,10 @@ describe('bezier', function() {
 
     it('should approach the projected value of its x=y projected curve', function() {
       repeat(10)(function() {
-        const a = Math.random(), b = Math.random(), c = Math.random(), d = Math.random();
+        const a = Math.random(),
+          b = Math.random(),
+          c = Math.random(),
+          d = Math.random();
         const easing = bezier(a, b, c, d);
         const projected = bezier(b, a, d, c);
         const composed = function(x) {
@@ -96,7 +102,10 @@ describe('bezier', function() {
   describe('two same instances', function() {
     it('should be strictly equals', function() {
       repeat(10)(function() {
-        const a = Math.random(), b = 2 * Math.random() - 0.5, c = Math.random(), d = 2 * Math.random() - 0.5;
+        const a = Math.random(),
+          b = 2 * Math.random() - 0.5,
+          c = Math.random(),
+          d = 2 * Math.random() - 0.5;
         allEquals(bezier(a, b, c, d), bezier(a, b, c, d), 100, 0);
       });
     });
@@ -104,14 +113,20 @@ describe('bezier', function() {
   describe('symetric curves', function() {
     it('should have a central value y~=0.5 at x=0.5', function() {
       repeat(10)(function() {
-        const a = Math.random(), b = 2 * Math.random() - 0.5, c = 1 - a, d = 1 - b;
+        const a = Math.random(),
+          b = 2 * Math.random() - 0.5,
+          c = 1 - a,
+          d = 1 - b;
         const easing = bezier(a, b, c, d);
         assertClose(easing(0.5), 0.5, 2);
       });
     });
     it('should be symmetrical', function() {
       repeat(10)(function() {
-        const a = Math.random(), b = 2 * Math.random() - 0.5, c = 1 - a, d = 1 - b;
+        const a = Math.random(),
+          b = 2 * Math.random() - 0.5,
+          c = 1 - a,
+          d = 1 - b;
         const easing = bezier(a, b, c, d);
         const sym = function(x) {
           return 1 - easing(1 - x);
diff --git a/Libraries/Animated/src/bezier.js b/Libraries/Animated/src/bezier.js
index f38ecef8c451..41a83b545f72 100644
--- a/Libraries/Animated/src/bezier.js
+++ b/Libraries/Animated/src/bezier.js
@@ -2,47 +2,64 @@
  * BezierEasing - use bezier curve for transition easing function
  * https://github.com/gre/bezier-easing
  *
+ * @format
  * @copyright 2014-2015 Gaëtan Renaudeau. MIT License.
  * @noflow
  */
+
 'use strict';
 
- // These values are established by empiricism with tests (tradeoff: performance VS precision)
- const NEWTON_ITERATIONS = 4;
- const NEWTON_MIN_SLOPE = 0.001;
- const SUBDIVISION_PRECISION = 0.0000001;
- const SUBDIVISION_MAX_ITERATIONS = 10;
-
- const kSplineTableSize = 11;
- const kSampleStepSize = 1.0 / (kSplineTableSize - 1.0);
-
- const float32ArraySupported = typeof Float32Array === 'function';
-
- function A (aA1, aA2) { return 1.0 - 3.0 * aA2 + 3.0 * aA1; }
- function B (aA1, aA2) { return 3.0 * aA2 - 6.0 * aA1; }
- function C (aA1)      { return 3.0 * aA1; }
-
- // Returns x(t) given t, x1, and x2, or y(t) given t, y1, and y2.
- function calcBezier (aT, aA1, aA2) { return ((A(aA1, aA2) * aT + B(aA1, aA2)) * aT + C(aA1)) * aT; }
-
- // Returns dx/dt given t, x1, and x2, or dy/dt given t, y1, and y2.
- function getSlope (aT, aA1, aA2) { return 3.0 * A(aA1, aA2) * aT * aT + 2.0 * B(aA1, aA2) * aT + C(aA1); }
-
- function binarySubdivide (aX, aA, aB, mX1, mX2) {
-   let currentX, currentT, i = 0;
-   do {
-     currentT = aA + (aB - aA) / 2.0;
-     currentX = calcBezier(currentT, mX1, mX2) - aX;
-     if (currentX > 0.0) {
-       aB = currentT;
-     } else {
-       aA = currentT;
-     }
-   } while (Math.abs(currentX) > SUBDIVISION_PRECISION && ++i < SUBDIVISION_MAX_ITERATIONS);
-   return currentT;
- }
-
- function newtonRaphsonIterate (aX, aGuessT, mX1, mX2) {
+// These values are established by empiricism with tests (tradeoff: performance VS precision)
+const NEWTON_ITERATIONS = 4;
+const NEWTON_MIN_SLOPE = 0.001;
+const SUBDIVISION_PRECISION = 0.0000001;
+const SUBDIVISION_MAX_ITERATIONS = 10;
+
+const kSplineTableSize = 11;
+const kSampleStepSize = 1.0 / (kSplineTableSize - 1.0);
+
+const float32ArraySupported = typeof Float32Array === 'function';
+
+function A(aA1, aA2) {
+  return 1.0 - 3.0 * aA2 + 3.0 * aA1;
+}
+function B(aA1, aA2) {
+  return 3.0 * aA2 - 6.0 * aA1;
+}
+function C(aA1) {
+  return 3.0 * aA1;
+}
+
+// Returns x(t) given t, x1, and x2, or y(t) given t, y1, and y2.
+function calcBezier(aT, aA1, aA2) {
+  return ((A(aA1, aA2) * aT + B(aA1, aA2)) * aT + C(aA1)) * aT;
+}
+
+// Returns dx/dt given t, x1, and x2, or dy/dt given t, y1, and y2.
+function getSlope(aT, aA1, aA2) {
+  return 3.0 * A(aA1, aA2) * aT * aT + 2.0 * B(aA1, aA2) * aT + C(aA1);
+}
+
+function binarySubdivide(aX, aA, aB, mX1, mX2) {
+  let currentX,
+    currentT,
+    i = 0;
+  do {
+    currentT = aA + (aB - aA) / 2.0;
+    currentX = calcBezier(currentT, mX1, mX2) - aX;
+    if (currentX > 0.0) {
+      aB = currentT;
+    } else {
+      aA = currentT;
+    }
+  } while (
+    Math.abs(currentX) > SUBDIVISION_PRECISION &&
+    ++i < SUBDIVISION_MAX_ITERATIONS
+  );
+  return currentT;
+}
+
+function newtonRaphsonIterate(aX, aGuessT, mX1, mX2) {
   for (let i = 0; i < NEWTON_ITERATIONS; ++i) {
     const currentSlope = getSlope(aGuessT, mX1, mX2);
     if (currentSlope === 0.0) {
@@ -52,56 +69,71 @@
     aGuessT -= currentX / currentSlope;
   }
   return aGuessT;
- }
-
- module.exports = function bezier (mX1, mY1, mX2, mY2) {
-   if (!(0 <= mX1 && mX1 <= 1 && 0 <= mX2 && mX2 <= 1)) { // eslint-disable-line yoda
-     throw new Error('bezier x values must be in [0, 1] range');
-   }
-
-   // Precompute samples table
-   const sampleValues = float32ArraySupported ? new Float32Array(kSplineTableSize) : new Array(kSplineTableSize);
-   if (mX1 !== mY1 || mX2 !== mY2) {
-     for (let i = 0; i < kSplineTableSize; ++i) {
-       sampleValues[i] = calcBezier(i * kSampleStepSize, mX1, mX2);
-     }
-   }
-
-   function getTForX (aX) {
-     let intervalStart = 0.0;
-     let currentSample = 1;
-     const lastSample = kSplineTableSize - 1;
-
-     for (; currentSample !== lastSample && sampleValues[currentSample] <= aX; ++currentSample) {
-       intervalStart += kSampleStepSize;
-     }
-     --currentSample;
-
-     // Interpolate to provide an initial guess for t
-     const dist = (aX - sampleValues[currentSample]) / (sampleValues[currentSample + 1] - sampleValues[currentSample]);
-     const guessForT = intervalStart + dist * kSampleStepSize;
-
-     const initialSlope = getSlope(guessForT, mX1, mX2);
-     if (initialSlope >= NEWTON_MIN_SLOPE) {
-       return newtonRaphsonIterate(aX, guessForT, mX1, mX2);
-     } else if (initialSlope === 0.0) {
-       return guessForT;
-     } else {
-       return binarySubdivide(aX, intervalStart, intervalStart + kSampleStepSize, mX1, mX2);
-     }
-   }
-
-   return function BezierEasing (x) {
-     if (mX1 === mY1 && mX2 === mY2) {
-       return x; // linear
-     }
-     // Because JavaScript number are imprecise, we should guarantee the extremes are right.
-     if (x === 0) {
-       return 0;
-     }
-     if (x === 1) {
-       return 1;
-     }
-     return calcBezier(getTForX(x), mY1, mY2);
-   };
- };
+}
+
+module.exports = function bezier(mX1, mY1, mX2, mY2) {
+  if (!(0 <= mX1 && mX1 <= 1 && 0 <= mX2 && mX2 <= 1)) {
+    // eslint-disable-line yoda
+    throw new Error('bezier x values must be in [0, 1] range');
+  }
+
+  // Precompute samples table
+  const sampleValues = float32ArraySupported
+    ? new Float32Array(kSplineTableSize)
+    : new Array(kSplineTableSize);
+  if (mX1 !== mY1 || mX2 !== mY2) {
+    for (let i = 0; i < kSplineTableSize; ++i) {
+      sampleValues[i] = calcBezier(i * kSampleStepSize, mX1, mX2);
+    }
+  }
+
+  function getTForX(aX) {
+    let intervalStart = 0.0;
+    let currentSample = 1;
+    const lastSample = kSplineTableSize - 1;
+
+    for (
+      ;
+      currentSample !== lastSample && sampleValues[currentSample] <= aX;
+      ++currentSample
+    ) {
+      intervalStart += kSampleStepSize;
+    }
+    --currentSample;
+
+    // Interpolate to provide an initial guess for t
+    const dist =
+      (aX - sampleValues[currentSample]) /
+      (sampleValues[currentSample + 1] - sampleValues[currentSample]);
+    const guessForT = intervalStart + dist * kSampleStepSize;
+
+    const initialSlope = getSlope(guessForT, mX1, mX2);
+    if (initialSlope >= NEWTON_MIN_SLOPE) {
+      return newtonRaphsonIterate(aX, guessForT, mX1, mX2);
+    } else if (initialSlope === 0.0) {
+      return guessForT;
+    } else {
+      return binarySubdivide(
+        aX,
+        intervalStart,
+        intervalStart + kSampleStepSize,
+        mX1,
+        mX2,
+      );
+    }
+  }
+
+  return function BezierEasing(x) {
+    if (mX1 === mY1 && mX2 === mY2) {
+      return x; // linear
+    }
+    // Because JavaScript number are imprecise, we should guarantee the extremes are right.
+    if (x === 0) {
+      return 0;
+    }
+    if (x === 1) {
+      return 1;
+    }
+    return calcBezier(getTForX(x), mY1, mY2);
+  };
+};
diff --git a/Libraries/Animated/src/polyfills/InteractionManager.js b/Libraries/Animated/src/polyfills/InteractionManager.js
index c063e9234b3d..5e82aaaa544c 100644
--- a/Libraries/Animated/src/polyfills/InteractionManager.js
+++ b/Libraries/Animated/src/polyfills/InteractionManager.js
@@ -3,11 +3,13 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
 
 module.exports = {
   createInteractionHandle: function() {},
-  clearInteractionHandle: function() {}
+  clearInteractionHandle: function() {},
 };
diff --git a/Libraries/Animated/src/polyfills/Set.js b/Libraries/Animated/src/polyfills/Set.js
index fd071410d423..c88278bda1cb 100644
--- a/Libraries/Animated/src/polyfills/Set.js
+++ b/Libraries/Animated/src/polyfills/Set.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
diff --git a/Libraries/Animated/src/polyfills/flattenStyle.js b/Libraries/Animated/src/polyfills/flattenStyle.js
index 2e4c8a1d36b4..21907b235f97 100644
--- a/Libraries/Animated/src/polyfills/flattenStyle.js
+++ b/Libraries/Animated/src/polyfills/flattenStyle.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 module.exports = function(style) {
   return style;
diff --git a/Libraries/AppState/AppState.js b/Libraries/AppState/AppState.js
index 904bf2b0e658..554689f11ad6 100644
--- a/Libraries/AppState/AppState.js
+++ b/Libraries/AppState/AppState.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const MissingNativeEventEmitterShim = require('MissingNativeEventEmitterShim');
@@ -23,7 +25,6 @@ const invariant = require('fbjs/lib/invariant');
  * See http://facebook.github.io/react-native/docs/appstate.html
  */
 class AppState extends NativeEventEmitter {
-
   _eventHandlers: Object;
   currentState: ?string;
   isAvailable: boolean = true;
@@ -47,27 +48,21 @@ class AppState extends NativeEventEmitter {
     // prop is up to date, we have to register an observer that updates it
     // whenever the state changes, even if nobody cares. We should just
     // deprecate the `currentState` property and get rid of this.
-    this.addListener(
-      'appStateDidChange',
-      (appStateData) => {
-        eventUpdated = true;
-        this.currentState = appStateData.app_state;
-      }
-    );
+    this.addListener('appStateDidChange', appStateData => {
+      eventUpdated = true;
+      this.currentState = appStateData.app_state;
+    });
 
     // TODO: see above - this request just populates the value of `currentState`
     // when the module is first initialized. Would be better to get rid of the
     // prop and expose `getCurrentAppState` method directly.
-    RCTAppState.getCurrentAppState(
-      (appStateData) => {
-        // It's possible that the state will have changed here & listeners need to be notified
-        if (!eventUpdated && this.currentState !== appStateData.app_state) {
-          this.currentState = appStateData.app_state;
-          this.emit('appStateDidChange', appStateData);
-        }
-      },
-      logError
-    );
+    RCTAppState.getCurrentAppState(appStateData => {
+      // It's possible that the state will have changed here & listeners need to be notified
+      if (!eventUpdated && this.currentState !== appStateData.app_state) {
+        this.currentState = appStateData.app_state;
+        this.emit('appStateDidChange', appStateData);
+      }
+    }, logError);
   }
 
   // TODO: now that AppState is a subclass of NativeEventEmitter, we could
@@ -75,32 +70,30 @@ class AppState extends NativeEventEmitter {
   // addListener` and `listener.remove()` directly. That will be a breaking
   // change though, as both the method and event names are different
   // (addListener events are currently required to be globally unique).
-   /**
+  /**
    * Add a handler to AppState changes by listening to the `change` event type
    * and providing the handler.
    *
    * See http://facebook.github.io/react-native/docs/appstate.html#addeventlistener
    */
-  addEventListener(
-    type: string,
-    handler: Function
-  ) {
+  addEventListener(type: string, handler: Function) {
     invariant(
       ['change', 'memoryWarning'].indexOf(type) !== -1,
-      'Trying to subscribe to unknown event: "%s"', type
+      'Trying to subscribe to unknown event: "%s"',
+      type,
     );
     if (type === 'change') {
-      this._eventHandlers[type].set(handler, this.addListener(
-        'appStateDidChange',
-        (appStateData) => {
+      this._eventHandlers[type].set(
+        handler,
+        this.addListener('appStateDidChange', appStateData => {
           handler(appStateData.app_state);
-        }
-      ));
+        }),
+      );
     } else if (type === 'memoryWarning') {
-      this._eventHandlers[type].set(handler, this.addListener(
-        'memoryWarning',
-        handler
-      ));
+      this._eventHandlers[type].set(
+        handler,
+        this.addListener('memoryWarning', handler),
+      );
     }
   }
 
@@ -109,13 +102,11 @@ class AppState extends NativeEventEmitter {
    *
    * See http://facebook.github.io/react-native/docs/appstate.html#removeeventlistener
    */
-  removeEventListener(
-    type: string,
-    handler: Function
-  ) {
+  removeEventListener(type: string, handler: Function) {
     invariant(
       ['change', 'memoryWarning'].indexOf(type) !== -1,
-      'Trying to remove listener for unknown event: "%s"', type
+      'Trying to remove listener for unknown event: "%s"',
+      type,
     );
     if (!this._eventHandlers[type].has(handler)) {
       return;
diff --git a/Libraries/BatchedBridge/BatchedBridge.js b/Libraries/BatchedBridge/BatchedBridge.js
index bc66ae32f9f4..0b1aae766493 100644
--- a/Libraries/BatchedBridge/BatchedBridge.js
+++ b/Libraries/BatchedBridge/BatchedBridge.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const MessageQueue = require('MessageQueue');
diff --git a/Libraries/BatchedBridge/NativeModules.js b/Libraries/BatchedBridge/NativeModules.js
index a5f991149995..bfee59abb4b7 100644
--- a/Libraries/BatchedBridge/NativeModules.js
+++ b/Libraries/BatchedBridge/NativeModules.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const BatchedBridge = require('BatchedBridge');
@@ -15,53 +17,66 @@ const invariant = require('fbjs/lib/invariant');
 import type {ExtendedError} from 'parseErrorStack';
 
 type ModuleConfig = [
-  string, /* name */
-  ?Object, /* constants */
-  Array<string>, /* functions */
-  Array<number>, /* promise method IDs */
-  Array<number>, /* sync method IDs */
+  string /* name */,
+  ?Object /* constants */,
+  Array<string> /* functions */,
+  Array<number> /* promise method IDs */,
+  Array<number> /* sync method IDs */,
 ];
 
 export type MethodType = 'async' | 'promise' | 'sync';
 
-function genModule(config: ?ModuleConfig, moduleID: number): ?{name: string, module?: Object} {
+function genModule(
+  config: ?ModuleConfig,
+  moduleID: number,
+): ?{name: string, module?: Object} {
   if (!config) {
     return null;
   }
 
   const [moduleName, constants, methods, promiseMethods, syncMethods] = config;
-  invariant(!moduleName.startsWith('RCT') && !moduleName.startsWith('RK'),
-    'Module name prefixes should\'ve been stripped by the native side ' +
-    'but wasn\'t for ' + moduleName);
+  invariant(
+    !moduleName.startsWith('RCT') && !moduleName.startsWith('RK'),
+    "Module name prefixes should've been stripped by the native side " +
+      "but wasn't for " +
+      moduleName,
+  );
 
   if (!constants && !methods) {
     // Module contents will be filled in lazily later
-    return { name: moduleName };
+    return {name: moduleName};
   }
 
   const module = {};
-  methods && methods.forEach((methodName, methodID) => {
-    const isPromise = promiseMethods && arrayContains(promiseMethods, methodID);
-    const isSync = syncMethods && arrayContains(syncMethods, methodID);
-    invariant(!isPromise || !isSync, 'Cannot have a method that is both async and a sync hook');
-    const methodType = isPromise ? 'promise' : isSync ? 'sync' : 'async';
-    module[methodName] = genMethod(moduleID, methodID, methodType);
-  });
+  methods &&
+    methods.forEach((methodName, methodID) => {
+      const isPromise =
+        promiseMethods && arrayContains(promiseMethods, methodID);
+      const isSync = syncMethods && arrayContains(syncMethods, methodID);
+      invariant(
+        !isPromise || !isSync,
+        'Cannot have a method that is both async and a sync hook',
+      );
+      const methodType = isPromise ? 'promise' : isSync ? 'sync' : 'async';
+      module[methodName] = genMethod(moduleID, methodID, methodType);
+    });
   Object.assign(module, constants);
 
   if (__DEV__) {
     BatchedBridge.createDebugLookup(moduleID, moduleName, methods);
   }
 
-  return { name: moduleName, module };
+  return {name: moduleName, module};
 }
 
 // export this method as a global so we can call it from native
 global.__fbGenNativeModule = genModule;
 
 function loadModule(name: string, moduleID: number): ?Object {
-  invariant(global.nativeRequireModuleConfig,
-    'Can\'t lazily create module without nativeRequireModuleConfig');
+  invariant(
+    global.nativeRequireModuleConfig,
+    "Can't lazily create module without nativeRequireModuleConfig",
+  );
   const config = global.nativeRequireModuleConfig(name);
   const info = genModule(config, moduleID);
   return info && info.module;
@@ -72,18 +87,25 @@ function genMethod(moduleID: number, methodID: number, type: MethodType) {
   if (type === 'promise') {
     fn = function(...args: Array<any>) {
       return new Promise((resolve, reject) => {
-        BatchedBridge.enqueueNativeCall(moduleID, methodID, args,
-          (data) => resolve(data),
-          (errorData) => reject(createErrorFromErrorData(errorData)));
+        BatchedBridge.enqueueNativeCall(
+          moduleID,
+          methodID,
+          args,
+          data => resolve(data),
+          errorData => reject(createErrorFromErrorData(errorData)),
+        );
       });
     };
   } else if (type === 'sync') {
     fn = function(...args: Array<any>) {
       if (__DEV__) {
-        invariant(global.nativeCallSyncHook, 'Calling synchronous methods on native ' +
-          'modules is not supported in Chrome.\n\n Consider providing alternative ' +
-          'methods to expose this method in debug mode, e.g. by exposing constants ' +
-          'ahead-of-time.');
+        invariant(
+          global.nativeCallSyncHook,
+          'Calling synchronous methods on native ' +
+            'modules is not supported in Chrome.\n\n Consider providing alternative ' +
+            'methods to expose this method in debug mode, e.g. by exposing constants ' +
+            'ahead-of-time.',
+        );
       }
       return global.nativeCallSyncHook(moduleID, methodID, args);
     };
@@ -93,15 +115,22 @@ function genMethod(moduleID: number, methodID: number, type: MethodType) {
       const secondLastArg = args.length > 1 ? args[args.length - 2] : null;
       const hasSuccessCallback = typeof lastArg === 'function';
       const hasErrorCallback = typeof secondLastArg === 'function';
-      hasErrorCallback && invariant(
-        hasSuccessCallback,
-        'Cannot have a non-function arg after a function arg.'
-      );
+      hasErrorCallback &&
+        invariant(
+          hasSuccessCallback,
+          'Cannot have a non-function arg after a function arg.',
+        );
       const onSuccess = hasSuccessCallback ? lastArg : null;
       const onFail = hasErrorCallback ? secondLastArg : null;
       const callbackCount = hasSuccessCallback + hasErrorCallback;
       args = args.slice(0, args.length - callbackCount);
-      BatchedBridge.enqueueNativeCall(moduleID, methodID, args, onFail, onSuccess);
+      BatchedBridge.enqueueNativeCall(
+        moduleID,
+        methodID,
+        args,
+        onFail,
+        onSuccess,
+      );
     };
   }
   fn.type = type;
@@ -113,41 +142,43 @@ function arrayContains<T>(array: Array<T>, value: T): boolean {
 }
 
 function createErrorFromErrorData(errorData: {message: string}): ExtendedError {
-  const {
-    message,
-    ...extraErrorInfo
-  } = errorData || {};
-  const error : ExtendedError = new Error(message);
+  const {message, ...extraErrorInfo} = errorData || {};
+  const error: ExtendedError = new Error(message);
   error.framesToPop = 1;
   return Object.assign(error, extraErrorInfo);
 }
 
-let NativeModules : {[moduleName: string]: Object} = {};
+let NativeModules: {[moduleName: string]: Object} = {};
 if (global.nativeModuleProxy) {
   NativeModules = global.nativeModuleProxy;
 } else {
   const bridgeConfig = global.__fbBatchedBridgeConfig;
-  invariant(bridgeConfig, '__fbBatchedBridgeConfig is not set, cannot invoke native modules');
+  invariant(
+    bridgeConfig,
+    '__fbBatchedBridgeConfig is not set, cannot invoke native modules',
+  );
 
   const defineLazyObjectProperty = require('defineLazyObjectProperty');
-  (bridgeConfig.remoteModuleConfig || []).forEach((config: ModuleConfig, moduleID: number) => {
-    // Initially this config will only contain the module name when running in JSC. The actual
-    // configuration of the module will be lazily loaded.
-    const info = genModule(config, moduleID);
-    if (!info) {
-      return;
-    }
-
-    if (info.module) {
-      NativeModules[info.name] = info.module;
-    }
-    // If there's no module config, define a lazy getter
-    else {
-      defineLazyObjectProperty(NativeModules, info.name, {
-        get: () => loadModule(info.name, moduleID)
-      });
-    }
-  });
+  (bridgeConfig.remoteModuleConfig || []).forEach(
+    (config: ModuleConfig, moduleID: number) => {
+      // Initially this config will only contain the module name when running in JSC. The actual
+      // configuration of the module will be lazily loaded.
+      const info = genModule(config, moduleID);
+      if (!info) {
+        return;
+      }
+
+      if (info.module) {
+        NativeModules[info.name] = info.module;
+      }
+      // If there's no module config, define a lazy getter
+      else {
+        defineLazyObjectProperty(NativeModules, info.name, {
+          get: () => loadModule(info.name, moduleID),
+        });
+      }
+    },
+  );
 }
 
 module.exports = NativeModules;
diff --git a/Libraries/BatchedBridge/__mocks__/MessageQueueTestConfig.js b/Libraries/BatchedBridge/__mocks__/MessageQueueTestConfig.js
index 2fa722fb39e8..3f9ae5f0a485 100644
--- a/Libraries/BatchedBridge/__mocks__/MessageQueueTestConfig.js
+++ b/Libraries/BatchedBridge/__mocks__/MessageQueueTestConfig.js
@@ -5,11 +5,14 @@
  * LICENSE file in the root directory of this source tree.
  *
  * These don't actually exist anywhere in the code.
+ *
+ * @format
  */
+
 'use strict';
 const remoteModulesConfig = [
-  ['RemoteModule1',null,['remoteMethod','promiseMethod'],[]],
-  ['RemoteModule2',null,['remoteMethod','promiseMethod'],[]],
+  ['RemoteModule1', null, ['remoteMethod', 'promiseMethod'], []],
+  ['RemoteModule2', null, ['remoteMethod', 'promiseMethod'], []],
 ];
 
 const MessageQueueTestConfig = {
diff --git a/Libraries/BatchedBridge/__mocks__/MessageQueueTestModule.js b/Libraries/BatchedBridge/__mocks__/MessageQueueTestModule.js
index 7d4f5f1a565a..05168a6b5700 100644
--- a/Libraries/BatchedBridge/__mocks__/MessageQueueTestModule.js
+++ b/Libraries/BatchedBridge/__mocks__/MessageQueueTestModule.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 /**
@@ -13,10 +15,8 @@
  * cases.
  */
 const MessageQueueTestModule = {
-  testHook1: function() {
-  },
-  testHook2: function() {
-  }
+  testHook1: function() {},
+  testHook2: function() {},
 };
 
 module.exports = MessageQueueTestModule;
diff --git a/Libraries/BatchedBridge/__tests__/NativeModules-test.js b/Libraries/BatchedBridge/__tests__/NativeModules-test.js
index b9cc2411d295..9702146b7190 100644
--- a/Libraries/BatchedBridge/__tests__/NativeModules-test.js
+++ b/Libraries/BatchedBridge/__tests__/NativeModules-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 jest
@@ -59,7 +61,12 @@ describe('MessageQueue', function() {
     const onSucc = jest.fn();
 
     // Perform communication
-    NativeModules.RemoteModule1.promiseMethod('paloAlto', 'menloPark', onFail, onSucc);
+    NativeModules.RemoteModule1.promiseMethod(
+      'paloAlto',
+      'menloPark',
+      onFail,
+      onSucc,
+    );
     NativeModules.RemoteModule2.promiseMethod('mac', 'windows', onFail, onSucc);
 
     const resultingRemoteInvocations = BatchedBridge.flushedQueue();
@@ -73,9 +80,10 @@ describe('MessageQueue', function() {
 
     expect(resultingRemoteInvocations[0][0]).toBe(0); // `RemoteModule1`
     expect(resultingRemoteInvocations[1][0]).toBe(1); // `promiseMethod`
-    expect([                                          // the arguments
+    expect([
+      // the arguments
       resultingRemoteInvocations[2][0][0],
-      resultingRemoteInvocations[2][0][1]
+      resultingRemoteInvocations[2][0][1],
     ]).toEqual(['paloAlto', 'menloPark']);
     // Callbacks ids are tacked onto the end of the remote arguments.
     const firstFailCBID = resultingRemoteInvocations[2][0][2];
@@ -83,9 +91,10 @@ describe('MessageQueue', function() {
 
     expect(resultingRemoteInvocations[0][1]).toBe(1); // `RemoteModule2`
     expect(resultingRemoteInvocations[1][1]).toBe(1); // `promiseMethod`
-    expect([                                          // the arguments
+    expect([
+      // the arguments
       resultingRemoteInvocations[2][1][0],
-      resultingRemoteInvocations[2][1][1]
+      resultingRemoteInvocations[2][1][1],
     ]).toEqual(['mac', 'windows']);
     const secondFailCBID = resultingRemoteInvocations[2][1][2];
     const secondSuccCBID = resultingRemoteInvocations[2][1][3];
diff --git a/Libraries/BugReporting/BugReporting.js b/Libraries/BugReporting/BugReporting.js
index f196276c36fa..6c63b6a1eebf 100644
--- a/Libraries/BugReporting/BugReporting.js
+++ b/Libraries/BugReporting/BugReporting.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
@@ -14,12 +16,14 @@ const infoLog = require('infoLog');
 
 import type EmitterSubscription from 'EmitterSubscription';
 
-type ExtraData = { [key: string]: string };
+type ExtraData = {[key: string]: string};
 type SourceCallback = () => string;
-type DebugData = { extras: ExtraData, files: ExtraData };
+type DebugData = {extras: ExtraData, files: ExtraData};
 
 function defaultExtras() {
-  BugReporting.addFileSource('react_hierarchy.txt', () => require('dumpReactTree')());
+  BugReporting.addFileSource('react_hierarchy.txt', () =>
+    require('dumpReactTree')(),
+  );
 }
 
 /**
@@ -36,14 +40,20 @@ class BugReporting {
 
   static _maybeInit() {
     if (!BugReporting._subscription) {
-      BugReporting._subscription = RCTDeviceEventEmitter
-          .addListener('collectBugExtraData', BugReporting.collectExtraData, null);
+      BugReporting._subscription = RCTDeviceEventEmitter.addListener(
+        'collectBugExtraData',
+        BugReporting.collectExtraData,
+        null,
+      );
       defaultExtras();
     }
 
     if (!BugReporting._redboxSubscription) {
-      BugReporting._redboxSubscription = RCTDeviceEventEmitter
-          .addListener('collectRedBoxExtraData', BugReporting.collectExtraData, null);
+      BugReporting._redboxSubscription = RCTDeviceEventEmitter.addListener(
+        'collectRedBoxExtraData',
+        BugReporting.collectExtraData,
+        null,
+      );
     }
   }
 
@@ -55,7 +65,10 @@ class BugReporting {
    *
    * Conflicts trample with a warning.
    */
-  static addSource(key: string, callback: SourceCallback): {remove: () => void} {
+  static addSource(
+    key: string,
+    callback: SourceCallback,
+  ): {remove: () => void} {
     return this._addSource(key, callback, BugReporting._extraSources);
   }
 
@@ -67,17 +80,30 @@ class BugReporting {
    *
    * Conflicts trample with a warning.
    */
-  static addFileSource(key: string, callback: SourceCallback): {remove: () => void} {
+  static addFileSource(
+    key: string,
+    callback: SourceCallback,
+  ): {remove: () => void} {
     return this._addSource(key, callback, BugReporting._fileSources);
   }
 
-  static _addSource(key: string, callback: SourceCallback, source: Map<string, SourceCallback>): {remove: () => void} {
+  static _addSource(
+    key: string,
+    callback: SourceCallback,
+    source: Map<string, SourceCallback>,
+  ): {remove: () => void} {
     BugReporting._maybeInit();
     if (source.has(key)) {
-      console.warn(`BugReporting.add* called multiple times for same key '${key}'`);
+      console.warn(
+        `BugReporting.add* called multiple times for same key '${key}'`,
+      );
     }
     source.set(key, callback);
-    return {remove: () => { source.delete(key); }};
+    return {
+      remove: () => {
+        source.delete(key);
+      },
+    };
   }
 
   /**
@@ -106,7 +132,7 @@ class BugReporting {
       RedBoxNativeModule.setExtraData &&
       RedBoxNativeModule.setExtraData(extraData, 'From BugReporting.js');
 
-    return { extras: extraData, files: fileData };
+    return {extras: extraData, files: fileData};
   }
 }
 
diff --git a/Libraries/BugReporting/dumpReactTree.js b/Libraries/BugReporting/dumpReactTree.js
index 6ffe64244e50..844585714703 100644
--- a/Libraries/BugReporting/dumpReactTree.js
+++ b/Libraries/BugReporting/dumpReactTree.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /*
@@ -35,7 +37,7 @@ function getReactTree() {
     'React tree dumps have been temporarily disabled while React is ' +
     'upgraded to Fiber.'
   );
-/*
+  /*
   let output = '';
   const rootIds = Object.getOwnPropertyNames(ReactNativeMount._instancesByContainerID);
   for (const rootId of rootIds) {
diff --git a/Libraries/BugReporting/getReactData.js b/Libraries/BugReporting/getReactData.js
index f995e8f41967..b4d1c4a32fd5 100644
--- a/Libraries/BugReporting/getReactData.js
+++ b/Libraries/BugReporting/getReactData.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /**
@@ -31,7 +33,10 @@ function getData(element: Object): Object {
   if (typeof element !== 'object') {
     nodeType = 'Text';
     text = element + '';
-  } else if (element._currentElement === null || element._currentElement === false) {
+  } else if (
+    element._currentElement === null ||
+    element._currentElement === false
+  ) {
     nodeType = 'Empty';
   } else if (element._renderedComponent) {
     nodeType = 'NativeWrapper';
@@ -65,7 +70,11 @@ function getData(element: Object): Object {
       name = element.getName();
       // 0.14 top-level wrapper
       // TODO(jared): The backend should just act as if these don't exist.
-      if (element._renderedComponent && element._currentElement.props === element._renderedComponent._currentElement) {
+      if (
+        element._renderedComponent &&
+        element._currentElement.props ===
+          element._renderedComponent._currentElement
+      ) {
         nodeType = 'Wrapper';
       }
       if (name === null) {
@@ -133,7 +142,7 @@ function setInContext(inst, path: Array<string | number>, value: any) {
 
 function setIn(obj: Object, path: Array<string | number>, value: any) {
   const last = path.pop();
-  const parent = path.reduce((obj_, attr) => obj_ ? obj_[attr] : null, obj);
+  const parent = path.reduce((obj_, attr) => (obj_ ? obj_[attr] : null), obj);
   if (parent) {
     parent[last] = value;
   }
@@ -158,7 +167,11 @@ function copyWithSetImpl(obj, path, idx, value) {
   return updated;
 }
 
-function copyWithSet(obj: Object | Array<any>, path: Array<string | number>, value: any): Object | Array<any> {
+function copyWithSet(
+  obj: Object | Array<any>,
+  path: Array<string | number>,
+  value: any,
+): Object | Array<any> {
   return copyWithSetImpl(obj, path, 0, value);
 }
 
diff --git a/Libraries/CameraRoll/ImagePickerIOS.js b/Libraries/CameraRoll/ImagePickerIOS.js
index b653c11090e2..785f4b57cb6b 100644
--- a/Libraries/CameraRoll/ImagePickerIOS.js
+++ b/Libraries/CameraRoll/ImagePickerIOS.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const RCTImagePicker = require('NativeModules').ImagePickerIOS;
@@ -17,20 +19,36 @@ const ImagePickerIOS = {
   canUseCamera: function(callback: Function) {
     return RCTImagePicker.canUseCamera(callback);
   },
-  openCameraDialog: function(config: Object, successCallback: Function, cancelCallback: Function) {
+  openCameraDialog: function(
+    config: Object,
+    successCallback: Function,
+    cancelCallback: Function,
+  ) {
     config = {
       videoMode: false,
       ...config,
     };
-    return RCTImagePicker.openCameraDialog(config, successCallback, cancelCallback);
+    return RCTImagePicker.openCameraDialog(
+      config,
+      successCallback,
+      cancelCallback,
+    );
   },
-  openSelectDialog: function(config: Object, successCallback: Function, cancelCallback: Function) {
+  openSelectDialog: function(
+    config: Object,
+    successCallback: Function,
+    cancelCallback: Function,
+  ) {
     config = {
       showImages: true,
       showVideos: false,
       ...config,
     };
-    return RCTImagePicker.openSelectDialog(config, successCallback, cancelCallback);
+    return RCTImagePicker.openSelectDialog(
+      config,
+      successCallback,
+      cancelCallback,
+    );
   },
 };
 
diff --git a/Libraries/Color/normalizeColor.js b/Libraries/Color/normalizeColor.js
index 59b3eb33ba5d..7b4ca253107d 100755
--- a/Libraries/Color/normalizeColor.js
+++ b/Libraries/Color/normalizeColor.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 /* eslint no-bitwise: 0 */
 'use strict';
 
@@ -30,30 +32,39 @@ function normalizeColor(color: string | number): ?number {
 
   if ((match = matchers.rgb.exec(color))) {
     return (
-      (// b
-      (parse255(match[1]) << 24 | // r
-      parse255(match[2]) << 16 | // g
-      parse255(match[3]) << 8 | 0x000000ff)) // a
-    ) >>> 0;
+      // b
+      ((parse255(match[1]) << 24) | // r
+      (parse255(match[2]) << 16) | // g
+        (parse255(match[3]) << 8) |
+        0x000000ff) >>> // a
+      0
+    );
   }
 
   if ((match = matchers.rgba.exec(color))) {
     return (
-      (// b
-      (parse255(match[1]) << 24 | // r
-      parse255(match[2]) << 16 | // g
-      parse255(match[3]) << 8 | parse1(match[4]))) // a
-    ) >>> 0;
+      // b
+      ((parse255(match[1]) << 24) | // r
+      (parse255(match[2]) << 16) | // g
+        (parse255(match[3]) << 8) |
+        parse1(match[4])) >>> // a
+      0
+    );
   }
 
   if ((match = matchers.hex3.exec(color))) {
-    return parseInt(
-      match[1] + match[1] + // r
-      match[2] + match[2] + // g
-      match[3] + match[3] + // b
-      'ff', // a
-      16
-    ) >>> 0;
+    return (
+      parseInt(
+        match[1] +
+        match[1] + // r
+        match[2] +
+        match[2] + // g
+        match[3] +
+        match[3] + // b
+          'ff', // a
+        16,
+      ) >>> 0
+    );
   }
 
   // https://drafts.csswg.org/css-color-4/#hex-notation
@@ -62,13 +73,19 @@ function normalizeColor(color: string | number): ?number {
   }
 
   if ((match = matchers.hex4.exec(color))) {
-    return parseInt(
-      match[1] + match[1] + // r
-      match[2] + match[2] + // g
-      match[3] + match[3] + // b
-      match[4] + match[4], // a
-      16
-    ) >>> 0;
+    return (
+      parseInt(
+        match[1] +
+        match[1] + // r
+        match[2] +
+        match[2] + // g
+        match[3] +
+        match[3] + // b
+          match[4] +
+          match[4], // a
+        16,
+      ) >>> 0
+    );
   }
 
   if ((match = matchers.hsl.exec(color))) {
@@ -76,9 +93,11 @@ function normalizeColor(color: string | number): ?number {
       (hslToRgb(
         parse360(match[1]), // h
         parsePercentage(match[2]), // s
-        parsePercentage(match[3]) // l
-      ) | 0x000000ff) // a
-    ) >>> 0;
+        parsePercentage(match[3]), // l
+      ) |
+        0x000000ff) >>> // a
+      0
+    );
   }
 
   if ((match = matchers.hsla.exec(color))) {
@@ -86,9 +105,11 @@ function normalizeColor(color: string | number): ?number {
       (hslToRgb(
         parse360(match[1]), // h
         parsePercentage(match[2]), // s
-        parsePercentage(match[3]) // l
-      ) | parse1(match[4])) // a
-    ) >>> 0;
+        parsePercentage(match[3]), // l
+      ) |
+        parse1(match[4])) >>> // a
+      0
+    );
   }
 
   return null;
@@ -121,9 +142,9 @@ function hslToRgb(h: number, s: number, l: number): number {
   const b = hue2rgb(p, q, h - 1 / 3);
 
   return (
-    Math.round(r * 255) << 24 |
-    Math.round(g * 255) << 16 |
-    Math.round(b * 255) << 8
+    (Math.round(r * 255) << 24) |
+    (Math.round(g * 255) << 16) |
+    (Math.round(b * 255) << 8)
   );
 }
 
@@ -159,7 +180,7 @@ function parse255(str: string): number {
 
 function parse360(str: string): number {
   const int = parseFloat(str);
-  return (((int % 360) + 360) % 360) / 360;
+  return ((int % 360 + 360) % 360) / 360;
 }
 
 function parse1(str: string): number {
diff --git a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
index 232370b5cbf8..dfa09b53a466 100644
--- a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
+++ b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeModules = require('NativeModules');
@@ -32,33 +34,30 @@ const _subscriptions = new Map();
  */
 
 const AccessibilityInfo = {
-
   fetch: function(): Promise {
     return new Promise((resolve, reject) => {
-      RCTAccessibilityInfo.isTouchExplorationEnabled(
-        function(resp) {
-          resolve(resp);
-        }
-      );
+      RCTAccessibilityInfo.isTouchExplorationEnabled(function(resp) {
+        resolve(resp);
+      });
     });
   },
 
-  addEventListener: function (
+  addEventListener: function(
     eventName: ChangeEventName,
-    handler: Function
+    handler: Function,
   ): void {
     const listener = RCTDeviceEventEmitter.addListener(
       TOUCH_EXPLORATION_EVENT,
-      (enabled) => {
+      enabled => {
         handler(enabled);
-      }
+      },
     );
     _subscriptions.set(handler, listener);
   },
 
   removeEventListener: function(
     eventName: ChangeEventName,
-    handler: Function
+    handler: Function,
   ): void {
     const listener = _subscriptions.get(handler);
     if (!listener) {
@@ -67,7 +66,6 @@ const AccessibilityInfo = {
     listener.remove();
     _subscriptions.delete(handler);
   },
-
 };
 
 module.exports = AccessibilityInfo;
diff --git a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
index d1b36494e99a..8f2b0aa78dc0 100644
--- a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
+++ b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeModules = require('NativeModules');
@@ -19,7 +21,7 @@ const ANNOUNCEMENT_DID_FINISH_EVENT = 'announcementDidFinish';
 
 type ChangeEventName = $Enum<{
   change: string,
-  announcementFinished: string
+  announcementFinished: string,
 }>;
 
 const _subscriptions = new Map();
@@ -34,7 +36,6 @@ const _subscriptions = new Map();
  * See http://facebook.github.io/react-native/docs/accessibilityinfo.html
  */
 const AccessibilityInfo = {
-
   /**
    * Query whether a screen reader is currently enabled.
    *
@@ -45,10 +46,7 @@ const AccessibilityInfo = {
    */
   fetch: function(): Promise {
     return new Promise((resolve, reject) => {
-      AccessibilityManager.getCurrentVoiceOverState(
-        resolve,
-        reject
-      );
+      AccessibilityManager.getCurrentVoiceOverState(resolve, reject);
     });
   },
 
@@ -67,27 +65,28 @@ const AccessibilityInfo = {
    *
    * See http://facebook.github.io/react-native/docs/accessibilityinfo.html#addeventlistener
    */
-  addEventListener: function (
+  addEventListener: function(
     eventName: ChangeEventName,
-    handler: Function
+    handler: Function,
   ): Object {
     let listener;
 
     if (eventName === 'change') {
-      listener = RCTDeviceEventEmitter.addListener(
-        VOICE_OVER_EVENT,
-        handler
-      );
+      listener = RCTDeviceEventEmitter.addListener(VOICE_OVER_EVENT, handler);
     } else if (eventName === 'announcementFinished') {
       listener = RCTDeviceEventEmitter.addListener(
         ANNOUNCEMENT_DID_FINISH_EVENT,
-        handler
+        handler,
       );
     }
 
     _subscriptions.set(handler, listener);
     return {
-      remove: AccessibilityInfo.removeEventListener.bind(null, eventName, handler),
+      remove: AccessibilityInfo.removeEventListener.bind(
+        null,
+        eventName,
+        handler,
+      ),
     };
   },
 
@@ -98,9 +97,7 @@ const AccessibilityInfo = {
    *
    * See http://facebook.github.io/react-native/docs/accessibilityinfo.html#setaccessibilityfocus
    */
-  setAccessibilityFocus: function(
-    reactTag: number
-  ): void {
+  setAccessibilityFocus: function(reactTag: number): void {
     AccessibilityManager.setAccessibilityFocus(reactTag);
   },
 
@@ -111,9 +108,7 @@ const AccessibilityInfo = {
    *
    * See http://facebook.github.io/react-native/docs/accessibilityinfo.html#announceforaccessibility
    */
-  announceForAccessibility: function(
-    announcement: string
-  ): void {
+  announceForAccessibility: function(announcement: string): void {
     AccessibilityManager.announceForAccessibility(announcement);
   },
 
@@ -124,7 +119,7 @@ const AccessibilityInfo = {
    */
   removeEventListener: function(
     eventName: ChangeEventName,
-    handler: Function
+    handler: Function,
   ): void {
     const listener = _subscriptions.get(handler);
     if (!listener) {
@@ -133,7 +128,6 @@ const AccessibilityInfo = {
     listener.remove();
     _subscriptions.delete(handler);
   },
-
 };
 
 module.exports = AccessibilityInfo;
diff --git a/Libraries/Components/ActivityIndicator/ActivityIndicator.js b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
index 9692cbf8073e..a3bf769f77c7 100644
--- a/Libraries/Components/ActivityIndicator/ActivityIndicator.js
+++ b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -31,7 +33,7 @@ type DefaultProps = {
   color: any,
   hidesWhenStopped: boolean,
   size: IndicatorSize,
-}
+};
 
 /**
  * Displays a circular loading indicator.
@@ -63,7 +65,7 @@ const ActivityIndicator = createReactClass({
      * See http://facebook.github.io/react-native/docs/activityindicator.html#size
      */
     size: PropTypes.oneOfType([
-      PropTypes.oneOf([ 'small', 'large' ]),
+      PropTypes.oneOf(['small', 'large']),
       PropTypes.number,
     ]),
     /**
@@ -117,14 +119,14 @@ const ActivityIndicator = createReactClass({
         )}
       </View>
     );
-  }
+  },
 });
 
 if (Platform.OS === 'ios') {
   RCTActivityIndicator = requireNativeComponent(
     'RCTActivityIndicatorView',
     ActivityIndicator,
-    { nativeOnly: { activityIndicatorViewStyle: true } }
+    {nativeOnly: {activityIndicatorViewStyle: true}},
   );
 }
 
diff --git a/Libraries/Components/AppleTV/TVEventHandler.js b/Libraries/Components/AppleTV/TVEventHandler.js
index 303e07617f98..567776b5d9bf 100644
--- a/Libraries/Components/AppleTV/TVEventHandler.js
+++ b/Libraries/Components/AppleTV/TVEventHandler.js
@@ -4,12 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Platform = require('Platform');
-const TVNavigationEventEmitter = require('NativeModules').TVNavigationEventEmitter;
+const TVNavigationEventEmitter = require('NativeModules')
+  .TVNavigationEventEmitter;
 const NativeEventEmitter = require('NativeEventEmitter');
 
 function TVEventHandler() {
@@ -17,19 +20,24 @@ function TVEventHandler() {
   this.__nativeTVNavigationEventEmitter = null;
 }
 
-TVEventHandler.prototype.enable = function(component: ?any, callback: Function) {
+TVEventHandler.prototype.enable = function(
+  component: ?any,
+  callback: Function,
+) {
   if (Platform.OS === 'ios' && !TVNavigationEventEmitter) {
     return;
   }
 
-  this.__nativeTVNavigationEventEmitter = new NativeEventEmitter(TVNavigationEventEmitter);
+  this.__nativeTVNavigationEventEmitter = new NativeEventEmitter(
+    TVNavigationEventEmitter,
+  );
   this.__nativeTVNavigationEventListener = this.__nativeTVNavigationEventEmitter.addListener(
     'onHWKeyEvent',
-    (data) => {
+    data => {
       if (callback) {
         callback(component, data);
       }
-    }
+    },
   );
 };
 
diff --git a/Libraries/Components/AppleTV/TVViewPropTypes.js b/Libraries/Components/AppleTV/TVViewPropTypes.js
index 831d5c3992d7..656450df247a 100644
--- a/Libraries/Components/AppleTV/TVViewPropTypes.js
+++ b/Libraries/Components/AppleTV/TVViewPropTypes.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 const PropTypes = require('prop-types');
 
@@ -13,66 +15,65 @@ const PropTypes = require('prop-types');
  * Additional View properties for Apple TV
  */
 const TVViewPropTypes = {
-    /**
-     * When set to true, this view will be focusable
-     * and navigable using the TV remote.
-     */
-    isTVSelectable: PropTypes.bool,
-
-    /**
-     * May be set to true to force the TV focus engine to move focus to this view.
-     */
-    hasTVPreferredFocus: PropTypes.bool,
+  /**
+   * When set to true, this view will be focusable
+   * and navigable using the TV remote.
+   */
+  isTVSelectable: PropTypes.bool,
 
-    /**
-     * *(Apple TV only)* Object with properties to control Apple TV parallax effects.
-     *
-     * enabled: If true, parallax effects are enabled.  Defaults to true.
-     * shiftDistanceX: Defaults to 2.0.
-     * shiftDistanceY: Defaults to 2.0.
-     * tiltAngle: Defaults to 0.05.
-     * magnification: Defaults to 1.0.
-     * pressMagnification: Defaults to 1.0.
-     * pressDuration: Defaults to 0.3.
-     * pressDelay: Defaults to 0.0.
-     *
-     * @platform ios
-     */
-    tvParallaxProperties: PropTypes.object,
+  /**
+   * May be set to true to force the TV focus engine to move focus to this view.
+   */
+  hasTVPreferredFocus: PropTypes.bool,
 
-    /**
-     * *(Apple TV only)* May be used to change the appearance of the Apple TV parallax effect when this view goes in or out of focus.  Defaults to 2.0.
-     *
-     * @platform ios
-     */
-    tvParallaxShiftDistanceX: PropTypes.number,
+  /**
+   * *(Apple TV only)* Object with properties to control Apple TV parallax effects.
+   *
+   * enabled: If true, parallax effects are enabled.  Defaults to true.
+   * shiftDistanceX: Defaults to 2.0.
+   * shiftDistanceY: Defaults to 2.0.
+   * tiltAngle: Defaults to 0.05.
+   * magnification: Defaults to 1.0.
+   * pressMagnification: Defaults to 1.0.
+   * pressDuration: Defaults to 0.3.
+   * pressDelay: Defaults to 0.0.
+   *
+   * @platform ios
+   */
+  tvParallaxProperties: PropTypes.object,
 
-    /**
-     * *(Apple TV only)* May be used to change the appearance of the Apple TV parallax effect when this view goes in or out of focus.  Defaults to 2.0.
-     *
-     * @platform ios
-     */
-    tvParallaxShiftDistanceY: PropTypes.number,
+  /**
+   * *(Apple TV only)* May be used to change the appearance of the Apple TV parallax effect when this view goes in or out of focus.  Defaults to 2.0.
+   *
+   * @platform ios
+   */
+  tvParallaxShiftDistanceX: PropTypes.number,
 
-    /**
-     * *(Apple TV only)* May be used to change the appearance of the Apple TV parallax effect when this view goes in or out of focus.  Defaults to 0.05.
-     *
-     * @platform ios
-     */
-    tvParallaxTiltAngle: PropTypes.number,
+  /**
+   * *(Apple TV only)* May be used to change the appearance of the Apple TV parallax effect when this view goes in or out of focus.  Defaults to 2.0.
+   *
+   * @platform ios
+   */
+  tvParallaxShiftDistanceY: PropTypes.number,
 
-    /**
-     * *(Apple TV only)* May be used to change the appearance of the Apple TV parallax effect when this view goes in or out of focus.  Defaults to 1.0.
-     *
-     * @platform ios
-     */
-    tvParallaxMagnification: PropTypes.number,
+  /**
+   * *(Apple TV only)* May be used to change the appearance of the Apple TV parallax effect when this view goes in or out of focus.  Defaults to 0.05.
+   *
+   * @platform ios
+   */
+  tvParallaxTiltAngle: PropTypes.number,
 
+  /**
+   * *(Apple TV only)* May be used to change the appearance of the Apple TV parallax effect when this view goes in or out of focus.  Defaults to 1.0.
+   *
+   * @platform ios
+   */
+  tvParallaxMagnification: PropTypes.number,
 };
 
 export type TVViewProps = {
-  isTVSelectable?: bool,
-  hasTVPreferredFocus?: bool,
+  isTVSelectable?: boolean,
+  hasTVPreferredFocus?: boolean,
   tvParallaxProperties?: Object,
   tvParallaxShiftDistanceX?: number,
   tvParallaxShiftDistanceY?: number,
diff --git a/Libraries/Components/Button.js b/Libraries/Components/Button.js
index 2956b1a1245b..22c376467ea9 100644
--- a/Libraries/Components/Button.js
+++ b/Libraries/Components/Button.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -117,8 +119,10 @@ class Button extends React.Component<{
       typeof title === 'string',
       'The title prop of a Button must be a string',
     );
-    const formattedTitle = Platform.OS === 'android' ? title.toUpperCase() : title;
-    const Touchable = Platform.OS === 'android' ? TouchableNativeFeedback : TouchableOpacity;
+    const formattedTitle =
+      Platform.OS === 'android' ? title.toUpperCase() : title;
+    const Touchable =
+      Platform.OS === 'android' ? TouchableNativeFeedback : TouchableOpacity;
     return (
       <Touchable
         accessibilityComponentType="button"
@@ -129,7 +133,9 @@ class Button extends React.Component<{
         disabled={disabled}
         onPress={onPress}>
         <View style={buttonStyles}>
-          <Text style={textStyles} disabled={disabled}>{formattedTitle}</Text>
+          <Text style={textStyles} disabled={disabled}>
+            {formattedTitle}
+          </Text>
         </View>
       </Touchable>
     );
@@ -166,7 +172,7 @@ const styles = StyleSheet.create({
     android: {
       elevation: 0,
       backgroundColor: '#dfdfdf',
-    }
+    },
   }),
   textDisabled: Platform.select({
     ios: {
@@ -174,7 +180,7 @@ const styles = StyleSheet.create({
     },
     android: {
       color: '#a1a1a1',
-    }
+    },
   }),
 });
 
diff --git a/Libraries/Components/Clipboard/Clipboard.js b/Libraries/Components/Clipboard/Clipboard.js
index 0bf3b470774c..706bc0fba8c9 100644
--- a/Libraries/Components/Clipboard/Clipboard.js
+++ b/Libraries/Components/Clipboard/Clipboard.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Clipboard = require('NativeModules').Clipboard;
@@ -36,5 +38,5 @@ module.exports = {
    */
   setString(content: string) {
     Clipboard.setString(content);
-  }
+  },
 };
diff --git a/Libraries/Components/DatePicker/DatePickerIOS.android.js b/Libraries/Components/DatePicker/DatePickerIOS.android.js
index d2053808699c..585be6e29767 100644
--- a/Libraries/Components/DatePicker/DatePickerIOS.android.js
+++ b/Libraries/Components/DatePicker/DatePickerIOS.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -17,7 +18,9 @@ class DummyDatePickerIOS extends React.Component {
   render() {
     return (
       <View style={[styles.dummyDatePickerIOS, this.props.style]}>
-        <Text style={styles.datePickerText}>DatePickerIOS is not supported on this platform!</Text>
+        <Text style={styles.datePickerText}>
+          DatePickerIOS is not supported on this platform!
+        </Text>
       </View>
     );
   }
@@ -37,7 +40,7 @@ const styles = StyleSheet.create({
   datePickerText: {
     color: '#333333',
     margin: 20,
-  }
+  },
 });
 
 module.exports = DummyDatePickerIOS;
diff --git a/Libraries/Components/DatePicker/DatePickerIOS.ios.js b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
index 41b0a88969ab..7a5455e60537 100644
--- a/Libraries/Components/DatePicker/DatePickerIOS.ios.js
+++ b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
@@ -4,10 +4,13 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
  *
  * This is a controlled component version of RCTDatePickerIOS
+ *
+ * @format
+ * @flow
  */
+
 'use strict';
 
 const NativeMethodsMixin = require('NativeMethodsMixin');
@@ -125,9 +128,8 @@ const DatePickerIOS = createReactClass({
 
   _onChange: function(event: Event) {
     const nativeTimeStamp = event.nativeEvent.timestamp;
-    this.props.onDateChange && this.props.onDateChange(
-      new Date(nativeTimeStamp)
-    );
+    this.props.onDateChange &&
+      this.props.onDateChange(new Date(nativeTimeStamp));
     // $FlowFixMe(>=0.41.0)
     this.props.onChange && this.props.onChange(event);
   },
@@ -141,9 +143,17 @@ const DatePickerIOS = createReactClass({
     return (
       <View style={props.style}>
         <RCTDatePickerIOS
-          ref={ picker => { this._picker = picker; } }
+          ref={picker => {
+            this._picker = picker;
+          }}
           style={styles.datePickerIOS}
-          date={props.date ? props.date.getTime() : props.initialDate ? props.initialDate.getTime() : undefined}
+          date={
+            props.date
+              ? props.date.getTime()
+              : props.initialDate
+                ? props.initialDate.getTime()
+                : undefined
+          }
           locale={props.locale ? props.locale : undefined}
           maximumDate={
             props.maximumDate ? props.maximumDate.getTime() : undefined
@@ -160,7 +170,7 @@ const DatePickerIOS = createReactClass({
         />
       </View>
     );
-  }
+  },
 });
 
 const styles = StyleSheet.create({
@@ -178,7 +188,7 @@ const RCTDatePickerIOS = requireNativeComponent('RCTDatePicker', {
     maximumDate: PropTypes.number,
     onDateChange: () => null,
     onChange: PropTypes.func,
-  }
+  },
 });
 
 module.exports = DatePickerIOS;
diff --git a/Libraries/Components/DatePickerAndroid/DatePickerAndroid.android.js b/Libraries/Components/DatePickerAndroid/DatePickerAndroid.android.js
index 23691ce10882..bd91263a8f9b 100644
--- a/Libraries/Components/DatePickerAndroid/DatePickerAndroid.android.js
+++ b/Libraries/Components/DatePickerAndroid/DatePickerAndroid.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const DatePickerModule = require('NativeModules').DatePickerAndroid;
@@ -76,11 +78,15 @@ class DatePickerAndroid {
   /**
    * A date has been selected.
    */
-  static get dateSetAction() { return 'dateSetAction'; }
+  static get dateSetAction() {
+    return 'dateSetAction';
+  }
   /**
    * The dialog has been dismissed.
    */
-  static get dismissedAction() { return 'dismissedAction'; }
+  static get dismissedAction() {
+    return 'dismissedAction';
+  }
 }
 
 module.exports = DatePickerAndroid;
diff --git a/Libraries/Components/DatePickerAndroid/DatePickerAndroid.ios.js b/Libraries/Components/DatePickerAndroid/DatePickerAndroid.ios.js
index 4895dfd8286d..a158f035c303 100644
--- a/Libraries/Components/DatePickerAndroid/DatePickerAndroid.ios.js
+++ b/Libraries/Components/DatePickerAndroid/DatePickerAndroid.ios.js
@@ -4,14 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const DatePickerAndroid = {
   async open(options: Object): Promise<Object> {
     return Promise.reject({
-      message: 'DatePickerAndroid is not supported on this platform.'
+      message: 'DatePickerAndroid is not supported on this platform.',
     });
   },
 };
diff --git a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
index f9d84442448b..6b983cb2ad27 100644
--- a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
+++ b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -28,11 +30,7 @@ const requireNativeComponent = require('requireNativeComponent');
 const RK_DRAWER_REF = 'drawerlayout';
 const INNERVIEW_REF = 'innerView';
 
-const DRAWER_STATES = [
-  'Idle',
-  'Dragging',
-  'Settling',
-];
+const DRAWER_STATES = ['Idle', 'Dragging', 'Settling'];
 
 /**
  * React component that wraps the platform `DrawerLayout` (Android only). The
@@ -99,7 +97,7 @@ const DrawerLayoutAndroid = createReactClass({
      */
     drawerPosition: PropTypes.oneOf([
       DrawerConsts.DrawerPosition.Left,
-      DrawerConsts.DrawerPosition.Right
+      DrawerConsts.DrawerPosition.Right,
     ]),
     /**
      * Specifies the width of the drawer, more precisely the width of the view that be pulled in
@@ -116,7 +114,7 @@ const DrawerLayoutAndroid = createReactClass({
     drawerLockMode: PropTypes.oneOf([
       'unlocked',
       'locked-closed',
-      'locked-open'
+      'locked-open',
     ]),
     /**
      * Function called whenever there is an interaction with the navigation view.
@@ -168,31 +166,41 @@ const DrawerLayoutAndroid = createReactClass({
   },
 
   render: function() {
-    const drawStatusBar = Platform.Version >= 21 && this.props.statusBarBackgroundColor;
-    const drawerViewWrapper =
+    const drawStatusBar =
+      Platform.Version >= 21 && this.props.statusBarBackgroundColor;
+    const drawerViewWrapper = (
       <View
         style={[
           styles.drawerSubview,
-          {width: this.props.drawerWidth, backgroundColor: this.props.drawerBackgroundColor}
+          {
+            width: this.props.drawerWidth,
+            backgroundColor: this.props.drawerBackgroundColor,
+          },
         ]}
         collapsable={false}>
         {this.props.renderNavigationView()}
         {drawStatusBar && <View style={styles.drawerStatusBar} />}
-      </View>;
-    const childrenWrapper =
+      </View>
+    );
+    const childrenWrapper = (
       <View ref={INNERVIEW_REF} style={styles.mainSubview} collapsable={false}>
-        {drawStatusBar &&
-        <StatusBar
-          translucent
-          backgroundColor={this.props.statusBarBackgroundColor}
-        />}
-        {drawStatusBar &&
-        <View style={[
-          styles.statusBar,
-          {backgroundColor: this.props.statusBarBackgroundColor}
-        ]} />}
+        {drawStatusBar && (
+          <StatusBar
+            translucent
+            backgroundColor={this.props.statusBarBackgroundColor}
+          />
+        )}
+        {drawStatusBar && (
+          <View
+            style={[
+              styles.statusBar,
+              {backgroundColor: this.props.statusBarBackgroundColor},
+            ]}
+          />
+        )}
         {this.props.children}
-      </View>;
+      </View>
+    );
     return (
       <AndroidDrawerLayout
         {...this.props}
@@ -234,7 +242,9 @@ const DrawerLayoutAndroid = createReactClass({
 
   _onDrawerStateChanged: function(event) {
     if (this.props.onDrawerStateChanged) {
-      this.props.onDrawerStateChanged(DRAWER_STATES[event.nativeEvent.drawerState]);
+      this.props.onDrawerStateChanged(
+        DRAWER_STATES[event.nativeEvent.drawerState],
+      );
     }
   },
 
@@ -245,7 +255,7 @@ const DrawerLayoutAndroid = createReactClass({
     UIManager.dispatchViewManagerCommand(
       this._getDrawerLayoutHandle(),
       UIManager.AndroidDrawerLayout.Commands.openDrawer,
-      null
+      null,
     );
   },
 
@@ -256,29 +266,28 @@ const DrawerLayoutAndroid = createReactClass({
     UIManager.dispatchViewManagerCommand(
       this._getDrawerLayoutHandle(),
       UIManager.AndroidDrawerLayout.Commands.closeDrawer,
-      null
+      null,
     );
   },
   /**
-  * Closing and opening example
-  * Note: To access the drawer you have to give it a ref. Refs do not work on stateless components
-  * render () {
-  *   this.openDrawer = () => {
-  *     this.refs.DRAWER.openDrawer()
-  *   }
-  *   this.closeDrawer = () => {
-  *     this.refs.DRAWER.closeDrawer()
-  *   }
-  *   return (
-  *     <DrawerLayoutAndroid ref={'DRAWER'}>
-  *     </DrawerLayoutAndroid>
-  *   )
-  * }
-  */
+   * Closing and opening example
+   * Note: To access the drawer you have to give it a ref. Refs do not work on stateless components
+   * render () {
+   *   this.openDrawer = () => {
+   *     this.refs.DRAWER.openDrawer()
+   *   }
+   *   this.closeDrawer = () => {
+   *     this.refs.DRAWER.closeDrawer()
+   *   }
+   *   return (
+   *     <DrawerLayoutAndroid ref={'DRAWER'}>
+   *     </DrawerLayoutAndroid>
+   *   )
+   * }
+   */
   _getDrawerLayoutHandle: function() {
     return ReactNative.findNodeHandle(this.refs[RK_DRAWER_REF]);
   },
-
 });
 
 const styles = StyleSheet.create({
@@ -312,6 +321,9 @@ const styles = StyleSheet.create({
 });
 
 // The View that contains both the actual drawer and the main view
-const AndroidDrawerLayout = requireNativeComponent('AndroidDrawerLayout', DrawerLayoutAndroid);
+const AndroidDrawerLayout = requireNativeComponent(
+  'AndroidDrawerLayout',
+  DrawerLayoutAndroid,
+);
 
 module.exports = DrawerLayoutAndroid;
diff --git a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.ios.js b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.ios.js
index ebd42dd5b18b..260d55992979 100644
--- a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.ios.js
+++ b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.ios.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/Components/Keyboard/Keyboard.js b/Libraries/Components/Keyboard/Keyboard.js
index d61b07a88670..da76db76eee3 100644
--- a/Libraries/Components/Keyboard/Keyboard.js
+++ b/Libraries/Components/Keyboard/Keyboard.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const LayoutAnimation = require('LayoutAnimation');
diff --git a/Libraries/Components/Keyboard/KeyboardAvoidingView.js b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
index 87a0172f2091..c559608d34c6 100644
--- a/Libraries/Components/Keyboard/KeyboardAvoidingView.js
+++ b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const createReactClass = require('create-react-class');
@@ -66,9 +68,9 @@ const KeyboardAvoidingView = createReactClass({
      */
     keyboardVerticalOffset: PropTypes.number.isRequired,
     /**
-    * This is to allow us to manually control which KAV shuld take effect when
-    * having more than one KAV at the same screen
-    */
+     * This is to allow us to manually control which KAV shuld take effect when
+     * having more than one KAV at the same screen
+     */
     enabled: PropTypes.bool.isRequired,
   },
 
@@ -130,10 +132,16 @@ const KeyboardAvoidingView = createReactClass({
     this.frame = event.nativeEvent.layout;
   },
 
-  UNSAFE_componentWillUpdate(nextProps: Object, nextState: Object, nextContext?: Object): void {
-    if (nextState.bottom === this.state.bottom &&
-        this.props.behavior === 'height' &&
-        nextProps.behavior === 'height') {
+  UNSAFE_componentWillUpdate(
+    nextProps: Object,
+    nextState: Object,
+    nextContext?: Object,
+  ): void {
+    if (
+      nextState.bottom === this.state.bottom &&
+      this.props.behavior === 'height' &&
+      nextProps.behavior === 'height'
+    ) {
       // If the component rerenders without an internal state change, e.g.
       // triggered by parent component re-rendering, no need for bottom to change.
       nextState.bottom = 0;
@@ -154,7 +162,7 @@ const KeyboardAvoidingView = createReactClass({
   },
 
   componentWillUnmount() {
-    this.subscriptions.forEach((sub) => sub.remove());
+    this.subscriptions.forEach(sub => sub.remove());
   },
 
   render(): React.Element<any> {
@@ -172,17 +180,25 @@ const KeyboardAvoidingView = createReactClass({
           heightStyle = {height: this.frame.height - bottomHeight, flex: 0};
         }
         return (
-          <View ref={viewRef} style={[style, heightStyle]} onLayout={this._onLayout} {...props}>
+          <View
+            ref={viewRef}
+            style={[style, heightStyle]}
+            onLayout={this._onLayout}
+            {...props}>
             {children}
           </View>
         );
 
       case 'position':
         const positionStyle = {bottom: bottomHeight};
-        const { contentContainerStyle } = this.props;
+        const {contentContainerStyle} = this.props;
 
         return (
-          <View ref={viewRef} style={style} onLayout={this._onLayout} {...props}>
+          <View
+            ref={viewRef}
+            style={style}
+            onLayout={this._onLayout}
+            {...props}>
             <View style={[contentContainerStyle, positionStyle]}>
               {children}
             </View>
@@ -192,14 +208,22 @@ const KeyboardAvoidingView = createReactClass({
       case 'padding':
         const paddingStyle = {paddingBottom: bottomHeight};
         return (
-          <View ref={viewRef} style={[style, paddingStyle]} onLayout={this._onLayout} {...props}>
+          <View
+            ref={viewRef}
+            style={[style, paddingStyle]}
+            onLayout={this._onLayout}
+            {...props}>
             {children}
           </View>
         );
 
       default:
         return (
-          <View ref={viewRef} onLayout={this._onLayout} style={style} {...props}>
+          <View
+            ref={viewRef}
+            onLayout={this._onLayout}
+            style={style}
+            {...props}>
             {children}
           </View>
         );
diff --git a/Libraries/Components/LazyRenderer.js b/Libraries/Components/LazyRenderer.js
index b1217aa1f3a2..23164141a3ed 100644
--- a/Libraries/Components/LazyRenderer.js
+++ b/Libraries/Components/LazyRenderer.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const React = require('React');
@@ -22,14 +24,14 @@ const LazyRenderer = createReactClass({
 
   UNSAFE_componentWillMount: function(): void {
     this.setState({
-      _lazyRender : true,
+      _lazyRender: true,
     });
   },
 
   componentDidMount: function(): void {
     requestAnimationFrame(() => {
       this.setState({
-        _lazyRender : false,
+        _lazyRender: false,
       });
     });
   },
diff --git a/Libraries/Components/MaskedView/MaskedViewIOS.android.js b/Libraries/Components/MaskedView/MaskedViewIOS.android.js
index 9684447d0fea..49d44e1541dc 100644
--- a/Libraries/Components/MaskedView/MaskedViewIOS.android.js
+++ b/Libraries/Components/MaskedView/MaskedViewIOS.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/Components/MaskedView/MaskedViewIOS.ios.js b/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
index 0407d3be089f..9f24f4edcf8c 100644
--- a/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
+++ b/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -14,7 +15,7 @@ const View = require('View');
 const ViewPropTypes = require('ViewPropTypes');
 const requireNativeComponent = require('requireNativeComponent');
 
-import type { ViewProps } from 'ViewPropTypes';
+import type {ViewProps} from 'ViewPropTypes';
 
 type Props = ViewProps & {
   children: any,
@@ -70,13 +71,13 @@ class MaskedViewIOS extends React.Component<Props> {
   _hasWarnedInvalidRenderMask = false;
 
   render() {
-    const { maskElement, children, ...otherViewProps } = this.props;
+    const {maskElement, children, ...otherViewProps} = this.props;
 
     if (!React.isValidElement(maskElement)) {
       if (!this._hasWarnedInvalidRenderMask) {
         console.warn(
           'MaskedView: Invalid `maskElement` prop was passed to MaskedView. ' +
-            'Expected a React Element. No mask will render.'
+            'Expected a React Element. No mask will render.',
         );
         this._hasWarnedInvalidRenderMask = true;
       }
diff --git a/Libraries/Components/Navigation/NavigatorIOS.android.js b/Libraries/Components/Navigation/NavigatorIOS.android.js
index ebd42dd5b18b..260d55992979 100644
--- a/Libraries/Components/Navigation/NavigatorIOS.android.js
+++ b/Libraries/Components/Navigation/NavigatorIOS.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/Components/Navigation/NavigatorIOS.ios.js b/Libraries/Components/Navigation/NavigatorIOS.ios.js
index 36223bfadca3..8f28d79147fe 100644
--- a/Libraries/Components/Navigation/NavigatorIOS.ios.js
+++ b/Libraries/Components/Navigation/NavigatorIOS.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EventEmitter = require('EventEmitter');
@@ -40,14 +42,12 @@ class NavigatorTransitionerIOS extends React.Component<$FlowFixMeProps> {
   requestSchedulingNavigation(cb) {
     RCTNavigatorManager.requestSchedulingJavaScriptNavigation(
       ReactNative.findNodeHandle(this),
-      cb
+      cb,
     );
   }
 
   render() {
-    return (
-      <RCTNavigator {...this.props}/>
-    );
+    return <RCTNavigator {...this.props} />;
   }
 }
 
@@ -107,7 +107,7 @@ type State = {
   toIndex: number,
   makingNavigatorRequest: boolean,
   updatingAllIndicesAtOrBeyond: ?number,
-}
+};
 
 type Event = Object;
 
@@ -308,7 +308,6 @@ const NavigatorIOS = createReactClass({
   displayName: 'NavigatorIOS',
 
   propTypes: {
-
     /**
      * NavigatorIOS uses `route` objects to identify child views, their props,
      * and navigation bar configuration. Navigation operations such as push
@@ -436,17 +435,16 @@ const NavigatorIOS = createReactClass({
        */
       barStyle: PropTypes.oneOf(['default', 'black']),
 
-       /**
+      /**
        * The text color of the navigation bar title.
        */
       titleTextColor: PropTypes.string,
 
-       /**
+      /**
        * Boolean value that indicates whether the navigation bar is
        * translucent.
        */
       translucent: PropTypes.bool,
-
     }).isRequired,
 
     /**
@@ -507,7 +505,6 @@ const NavigatorIOS = createReactClass({
      * behavior.
      */
     interactivePopGestureEnabled: PropTypes.bool,
-
   },
 
   navigator: (undefined: ?Object),
@@ -608,7 +605,7 @@ const NavigatorIOS = createReactClass({
 
   _tryLockNavigator: function(cb: () => void) {
     this.refs[TRANSITIONER_REF].requestSchedulingNavigation(
-      (acquiredLock) => acquiredLock && cb()
+      acquiredLock => acquiredLock && cb(),
     );
   },
 
@@ -617,7 +614,9 @@ const NavigatorIOS = createReactClass({
 
     invariant(
       newObservedTopOfStack <= this.state.requestedTopOfStack,
-      'No navigator item should be pushed without JS knowing about it %s %s', newObservedTopOfStack, this.state.requestedTopOfStack
+      'No navigator item should be pushed without JS knowing about it %s %s',
+      newObservedTopOfStack,
+      this.state.requestedTopOfStack,
     );
     const wasWaitingForConfirmation =
       this.state.requestedTopOfStack !== this.state.observedTopOfStack;
@@ -625,7 +624,7 @@ const NavigatorIOS = createReactClass({
       invariant(
         newObservedTopOfStack === this.state.requestedTopOfStack,
         'If waiting for observedTopOfStack to reach requestedTopOfStack, ' +
-        'the only valid observedTopOfStack should be requestedTopOfStack.'
+          'the only valid observedTopOfStack should be requestedTopOfStack.',
       );
     }
     // Mark the most recent observation regardless of if we can lock the
@@ -653,12 +652,15 @@ const NavigatorIOS = createReactClass({
     // even uses the indices in this case, but let's make this describe the
     // truth anyways).
     const updatingAllIndicesAtOrBeyond =
-      this.state.routeStack.length > this.state.observedTopOfStack + 1 ?
-      this.state.observedTopOfStack + 1 :
-      null;
+      this.state.routeStack.length > this.state.observedTopOfStack + 1
+        ? this.state.observedTopOfStack + 1
+        : null;
     this.setState({
       idStack: this.state.idStack.slice(0, this.state.observedTopOfStack + 1),
-      routeStack: this.state.routeStack.slice(0, this.state.observedTopOfStack + 1),
+      routeStack: this.state.routeStack.slice(
+        0,
+        this.state.observedTopOfStack + 1,
+      ),
       // Now we rerequest the top of stack that we observed.
       requestedTopOfStack: this.state.observedTopOfStack,
       makingNavigatorRequest: true,
@@ -675,7 +677,6 @@ const NavigatorIOS = createReactClass({
     // Make sure all previous requests are caught up first. Otherwise reject.
     if (this.state.requestedTopOfStack === this.state.observedTopOfStack) {
       this._tryLockNavigator(() => {
-
         const nextStack = this.state.routeStack.concat([route]);
         const nextIDStack = this.state.idStack.concat([getuid()]);
         this.setState({
@@ -752,7 +753,6 @@ const NavigatorIOS = createReactClass({
       makingNavigatorRequest: false,
       updatingAllIndicesAtOrBeyond: index,
     });
-
   },
 
   /**
@@ -787,7 +787,7 @@ const NavigatorIOS = createReactClass({
     const indexOfRoute = this.state.routeStack.indexOf(route);
     invariant(
       indexOfRoute !== -1,
-      'Calling pop to route for a route that doesn\'t exist!'
+      "Calling pop to route for a route that doesn't exist!",
     );
     const numToPop = this.state.routeStack.length - indexOfRoute - 1;
     this.popN(numToPop);
@@ -851,16 +851,8 @@ const NavigatorIOS = createReactClass({
         <RCTNavigatorItem
           {...props}
           {...route}
-          style={[
-            styles.stackItem,
-            itemWrapperStyle,
-            wrapperStyle
-          ]}>
-          <Component
-            navigator={this.navigator}
-            route={route}
-            {...passProps}
-          />
+          style={[styles.stackItem, itemWrapperStyle, wrapperStyle]}>
+          <Component navigator={this.navigator} route={route} {...passProps} />
         </RCTNavigatorItem>
       </StaticContainer>
     );
@@ -872,8 +864,9 @@ const NavigatorIOS = createReactClass({
       this.state.updatingAllIndicesAtOrBeyond !== null;
     // If not recursing update to navigator at all, may as well avoid
     // computation of navigator children.
-    const items = shouldRecurseToNavigator ?
-      this.state.routeStack.map(this._routeToStackItem) : null;
+    const items = shouldRecurseToNavigator
+      ? this.state.routeStack.map(this._routeToStackItem)
+      : null;
     return (
       <StaticContainer shouldUpdate={shouldRecurseToNavigator}>
         <NavigatorTransitionerIOS
@@ -883,7 +876,9 @@ const NavigatorIOS = createReactClass({
           vertical={this.props.vertical}
           requestedTopOfStack={this.state.requestedTopOfStack}
           onNavigationComplete={this._handleNavigationComplete}
-          interactivePopGestureEnabled={this.props.interactivePopGestureEnabled}>
+          interactivePopGestureEnabled={
+            this.props.interactivePopGestureEnabled
+          }>
           {items}
         </NavigatorTransitionerIOS>
       </StaticContainer>
@@ -911,9 +906,7 @@ const NavigatorIOS = createReactClass({
   render: function() {
     return (
       // $FlowFixMe(>=0.41.0)
-      <View style={this.props.style}>
-        {this._renderNavigationStackItems()}
-      </View>
+      <View style={this.props.style}>{this._renderNavigationStackItems()}</View>
     );
   },
 });
diff --git a/Libraries/Components/Picker/Picker.js b/Libraries/Components/Picker/Picker.js
index 121299319106..1e3e96579e21 100644
--- a/Libraries/Components/Picker/Picker.js
+++ b/Libraries/Components/Picker/Picker.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -35,36 +36,36 @@ const MODE_DROPDOWN = 'dropdown';
  * Individual selectable item in a Picker.
  */
 class PickerItem extends React.Component<{
- label: string,
- value?: any,
- color?: ColorPropType,
- testID?: string,
+  label: string,
+  value?: any,
+  color?: ColorPropType,
+  testID?: string,
 }> {
- static propTypes = {
-   /**
-    * Text to display for this item.
-    */
-   label: PropTypes.string.isRequired,
-   /**
-    * The value to be passed to picker's `onValueChange` callback when
-    * this item is selected. Can be a string or an integer.
-    */
-   value: PropTypes.any,
-   /**
-    * Color of this item's text.
-    * @platform android
-    */
-   color: ColorPropType,
-   /**
-    * Used to locate the item in end-to-end tests.
-    */
-   testID: PropTypes.string,
- };
+  static propTypes = {
+    /**
+     * Text to display for this item.
+     */
+    label: PropTypes.string.isRequired,
+    /**
+     * The value to be passed to picker's `onValueChange` callback when
+     * this item is selected. Can be a string or an integer.
+     */
+    value: PropTypes.any,
+    /**
+     * Color of this item's text.
+     * @platform android
+     */
+    color: ColorPropType,
+    /**
+     * Used to locate the item in end-to-end tests.
+     */
+    testID: PropTypes.string,
+  };
 
- render() {
-   // The items are not rendered directly
-   throw null;
- }
+  render() {
+    // The items are not rendered directly
+    throw null;
+  }
 }
 
 /**
@@ -78,87 +79,89 @@ class PickerItem extends React.Component<{
  *     </Picker>
  */
 class Picker extends React.Component<{
- style?: $FlowFixMe,
- selectedValue?: any,
- onValueChange?: Function,
- enabled?: boolean,
- mode?: 'dialog' | 'dropdown',
- itemStyle?: $FlowFixMe,
- prompt?: string,
- testID?: string,
+  style?: $FlowFixMe,
+  selectedValue?: any,
+  onValueChange?: Function,
+  enabled?: boolean,
+  mode?: 'dialog' | 'dropdown',
+  itemStyle?: $FlowFixMe,
+  prompt?: string,
+  testID?: string,
 }> {
- /**
-  * On Android, display the options in a dialog.
-  */
- static MODE_DIALOG = MODE_DIALOG;
+  /**
+   * On Android, display the options in a dialog.
+   */
+  static MODE_DIALOG = MODE_DIALOG;
 
- /**
-  * On Android, display the options in a dropdown (this is the default).
-  */
- static MODE_DROPDOWN = MODE_DROPDOWN;
+  /**
+   * On Android, display the options in a dropdown (this is the default).
+   */
+  static MODE_DROPDOWN = MODE_DROPDOWN;
 
- static Item = PickerItem;
+  static Item = PickerItem;
 
- static defaultProps = {
-   mode: MODE_DIALOG,
- };
+  static defaultProps = {
+    mode: MODE_DIALOG,
+  };
 
- // $FlowFixMe(>=0.41.0)
- static propTypes = {
-   ...ViewPropTypes,
-   style: pickerStyleType,
-   /**
-    * Value matching value of one of the items. Can be a string or an integer.
-    */
-   selectedValue: PropTypes.any,
-   /**
-    * Callback for when an item is selected. This is called with the following parameters:
-    *   - `itemValue`: the `value` prop of the item that was selected
-    *   - `itemPosition`: the index of the selected item in this picker
-    */
-   onValueChange: PropTypes.func,
-   /**
-    * If set to false, the picker will be disabled, i.e. the user will not be able to make a
-    * selection.
-    * @platform android
-    */
-   enabled: PropTypes.bool,
-   /**
-    * On Android, specifies how to display the selection items when the user taps on the picker:
-    *
-    *   - 'dialog': Show a modal dialog. This is the default.
-    *   - 'dropdown': Shows a dropdown anchored to the picker view
-    *
-    * @platform android
-    */
-   mode: PropTypes.oneOf(['dialog', 'dropdown']),
-   /**
-    * Style to apply to each of the item labels.
-    * @platform ios
-    */
-   itemStyle: itemStylePropType,
-   /**
-    * Prompt string for this picker, used on Android in dialog mode as the title of the dialog.
-    * @platform android
-    */
-   prompt: PropTypes.string,
-   /**
-    * Used to locate this view in end-to-end tests.
-    */
-   testID: PropTypes.string,
- };
+  // $FlowFixMe(>=0.41.0)
+  static propTypes = {
+    ...ViewPropTypes,
+    style: pickerStyleType,
+    /**
+     * Value matching value of one of the items. Can be a string or an integer.
+     */
+    selectedValue: PropTypes.any,
+    /**
+     * Callback for when an item is selected. This is called with the following parameters:
+     *   - `itemValue`: the `value` prop of the item that was selected
+     *   - `itemPosition`: the index of the selected item in this picker
+     */
+    onValueChange: PropTypes.func,
+    /**
+     * If set to false, the picker will be disabled, i.e. the user will not be able to make a
+     * selection.
+     * @platform android
+     */
+    enabled: PropTypes.bool,
+    /**
+     * On Android, specifies how to display the selection items when the user taps on the picker:
+     *
+     *   - 'dialog': Show a modal dialog. This is the default.
+     *   - 'dropdown': Shows a dropdown anchored to the picker view
+     *
+     * @platform android
+     */
+    mode: PropTypes.oneOf(['dialog', 'dropdown']),
+    /**
+     * Style to apply to each of the item labels.
+     * @platform ios
+     */
+    itemStyle: itemStylePropType,
+    /**
+     * Prompt string for this picker, used on Android in dialog mode as the title of the dialog.
+     * @platform android
+     */
+    prompt: PropTypes.string,
+    /**
+     * Used to locate this view in end-to-end tests.
+     */
+    testID: PropTypes.string,
+  };
 
- render() {
-     if (Platform.OS === 'ios') {
-       // $FlowFixMe found when converting React.createClass to ES6
-       return <PickerIOS {...this.props}>{this.props.children}</PickerIOS>;
-     } else if (Platform.OS === 'android') {
-       // $FlowFixMe found when converting React.createClass to ES6
-       return <PickerAndroid {...this.props}>{this.props.children}</PickerAndroid>;
-     } else {
-       return <UnimplementedView />;
-     }
- }
+  render() {
+    if (Platform.OS === 'ios') {
+      // $FlowFixMe found when converting React.createClass to ES6
+      return <PickerIOS {...this.props}>{this.props.children}</PickerIOS>;
+    } else if (Platform.OS === 'android') {
+      return (
+        // $FlowFixMe found when converting React.createClass to ES6
+        <PickerAndroid {...this.props}>{this.props.children}</PickerAndroid>
+      );
+    } else {
+      return <UnimplementedView />;
+    }
+  }
 }
 
 module.exports = Picker;
diff --git a/Libraries/Components/Picker/PickerAndroid.android.js b/Libraries/Components/Picker/PickerAndroid.android.js
index 6bc912bd6d33..c0ce723e479a 100644
--- a/Libraries/Components/Picker/PickerAndroid.android.js
+++ b/Libraries/Components/Picker/PickerAndroid.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -33,15 +34,18 @@ type Event = Object;
 /**
  * Not exposed as a public API - use <Picker> instead.
  */
-class PickerAndroid extends React.Component<{
-  style?: $FlowFixMe,
-  selectedValue?: any,
-  enabled?: boolean,
-  mode?: 'dialog' | 'dropdown',
-  onValueChange?: Function,
-  prompt?: string,
-  testID?: string,
-}, *> {
+class PickerAndroid extends React.Component<
+  {
+    style?: $FlowFixMe,
+    selectedValue?: any,
+    enabled?: boolean,
+    mode?: 'dialog' | 'dropdown',
+    onValueChange?: Function,
+    prompt?: string,
+    testID?: string,
+  },
+  *,
+> {
   static propTypes = {
     ...ViewPropTypes,
     style: pickerStyleType,
@@ -68,7 +72,7 @@ class PickerAndroid extends React.Component<{
   }
 
   // Translate prop and children into stuff that the native picker understands.
-  _stateFromProps = (props) => {
+  _stateFromProps = props => {
     let selectedIndex = 0;
     const items = React.Children.map(props.children, (child, index) => {
       if (child.props.value === props.selectedValue) {
@@ -87,7 +91,8 @@ class PickerAndroid extends React.Component<{
   };
 
   render() {
-    const Picker = this.props.mode === MODE_DROPDOWN ? DropdownPicker : DialogPicker;
+    const Picker =
+      this.props.mode === MODE_DROPDOWN ? DropdownPicker : DialogPicker;
 
     const nativeProps = {
       enabled: this.props.enabled,
@@ -130,8 +135,13 @@ class PickerAndroid extends React.Component<{
     // disallow/undo/mutate the selection of certain values. In other
     // words, the embedder of this component should be the source of
     // truth, not the native component.
-    if (this.refs[REF_PICKER] && this.state.selectedIndex !== this._lastNativePosition) {
-      this.refs[REF_PICKER].setNativeProps({selected: this.state.selectedIndex});
+    if (
+      this.refs[REF_PICKER] &&
+      this.state.selectedIndex !== this._lastNativePosition
+    ) {
+      this.refs[REF_PICKER].setNativeProps({
+        selected: this.state.selectedIndex,
+      });
       this._lastNativePosition = this.state.selectedIndex;
     }
   }
@@ -152,10 +162,18 @@ const cfg = {
   nativeOnly: {
     items: true,
     selected: true,
-  }
+  },
 };
 
-const DropdownPicker = requireNativeComponent('AndroidDropdownPicker', PickerAndroid, cfg);
-const DialogPicker = requireNativeComponent('AndroidDialogPicker', PickerAndroid, cfg);
+const DropdownPicker = requireNativeComponent(
+  'AndroidDropdownPicker',
+  PickerAndroid,
+  cfg,
+);
+const DialogPicker = requireNativeComponent(
+  'AndroidDialogPicker',
+  PickerAndroid,
+  cfg,
+);
 
 module.exports = PickerAndroid;
diff --git a/Libraries/Components/Picker/PickerAndroid.ios.js b/Libraries/Components/Picker/PickerAndroid.ios.js
index ebd42dd5b18b..260d55992979 100644
--- a/Libraries/Components/Picker/PickerAndroid.ios.js
+++ b/Libraries/Components/Picker/PickerAndroid.ios.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/Components/Picker/PickerIOS.android.js b/Libraries/Components/Picker/PickerIOS.android.js
index 2977696844b0..36acfe18342b 100644
--- a/Libraries/Components/Picker/PickerIOS.android.js
+++ b/Libraries/Components/Picker/PickerIOS.android.js
@@ -6,7 +6,10 @@
  *
  *
  * This is a controlled component version of RCTPickerIOS
+ *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/Components/Picker/PickerIOS.ios.js b/Libraries/Components/Picker/PickerIOS.ios.js
index fcd5b12c1633..881c33ce038e 100644
--- a/Libraries/Components/Picker/PickerIOS.ios.js
+++ b/Libraries/Components/Picker/PickerIOS.ios.js
@@ -6,7 +6,10 @@
  *
  *
  * This is a controlled component version of RCTPickerIOS
+ *
+ * @format
  */
+
 'use strict';
 
 const NativeMethodsMixin = require('NativeMethodsMixin');
@@ -46,7 +49,7 @@ const PickerIOS = createReactClass({
   _stateFromProps: function(props) {
     let selectedIndex = 0;
     const items = [];
-    React.Children.toArray(props.children).forEach(function (child, index) {
+    React.Children.toArray(props.children).forEach(function(child, index) {
       if (child.props.value === props.selectedValue) {
         selectedIndex = index;
       }
@@ -63,7 +66,7 @@ const PickerIOS = createReactClass({
     return (
       <View style={this.props.style}>
         <RCTPickerIOS
-          ref={picker => this._picker = picker}
+          ref={picker => (this._picker = picker)}
           style={[styles.pickerIOS, this.props.itemStyle]}
           items={this.state.items}
           selectedIndex={this.state.selectedIndex}
@@ -80,7 +83,10 @@ const PickerIOS = createReactClass({
       this.props.onChange(event);
     }
     if (this.props.onValueChange) {
-      this.props.onValueChange(event.nativeEvent.newValue, event.nativeEvent.newIndex);
+      this.props.onValueChange(
+        event.nativeEvent.newValue,
+        event.nativeEvent.newIndex,
+      );
     }
 
     // The picker is a controlled component. This means we expect the
@@ -89,9 +95,12 @@ const PickerIOS = createReactClass({
     // disallow/undo/mutate the selection of certain values. In other
     // words, the embedder of this component should be the source of
     // truth, not the native component.
-    if (this._picker && this.state.selectedIndex !== event.nativeEvent.newIndex) {
+    if (
+      this._picker &&
+      this.state.selectedIndex !== event.nativeEvent.newIndex
+    ) {
       this._picker.setNativeProps({
-        selectedIndex: this.state.selectedIndex
+        selectedIndex: this.state.selectedIndex,
       });
     }
   },
@@ -119,16 +128,20 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTPickerIOS = requireNativeComponent('RCTPicker', {
-  propTypes: {
-    style: itemStylePropType,
+const RCTPickerIOS = requireNativeComponent(
+  'RCTPicker',
+  {
+    propTypes: {
+      style: itemStylePropType,
+    },
   },
-}, {
-  nativeOnly: {
-    items: true,
-    onChange: true,
-    selectedIndex: true,
+  {
+    nativeOnly: {
+      items: true,
+      onChange: true,
+      selectedIndex: true,
+    },
   },
-});
+);
 
 module.exports = PickerIOS;
diff --git a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.ios.js b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.ios.js
index ebd42dd5b18b..260d55992979 100644
--- a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.ios.js
+++ b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.ios.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.android.js b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.android.js
index dcc8c3fc7489..8caa73db33e4 100644
--- a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.android.js
+++ b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.android.js
@@ -1,10 +1,10 @@
-
 /**
  * Copyright (c) 2015-present, Facebook, Inc.
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -40,7 +40,7 @@ const styles = StyleSheet.create({
     color: '#333333',
     margin: 5,
     fontSize: 10,
-  }
+  },
 });
 
 module.exports = DummyProgressViewIOS;
diff --git a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
index 2c14b4cddff7..dde9f399fdef 100644
--- a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
+++ b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Image = require('Image');
@@ -65,7 +67,7 @@ const ProgressViewIOS = createReactClass({
         style={[styles.progressView, this.props.style]}
       />
     );
-  }
+  },
 });
 
 const styles = StyleSheet.create({
@@ -76,7 +78,7 @@ const styles = StyleSheet.create({
 
 const RCTProgressView = requireNativeComponent(
   'RCTProgressView',
-  ProgressViewIOS
+  ProgressViewIOS,
 );
 
 module.exports = ProgressViewIOS;
diff --git a/Libraries/Components/RefreshControl/RefreshControl.js b/Libraries/Components/RefreshControl/RefreshControl.js
index 07415276261a..e9389c1a400f 100644
--- a/Libraries/Components/RefreshControl/RefreshControl.js
+++ b/Libraries/Components/RefreshControl/RefreshControl.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -19,8 +21,8 @@ const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
 if (Platform.OS === 'android') {
-  const AndroidSwipeRefreshLayout =
-    require('UIManager').AndroidSwipeRefreshLayout;
+  const AndroidSwipeRefreshLayout = require('UIManager')
+    .AndroidSwipeRefreshLayout;
   var RefreshLayoutConsts = AndroidSwipeRefreshLayout
     ? AndroidSwipeRefreshLayout.Constants
     : {SIZE: {}};
@@ -125,7 +127,10 @@ const RefreshControl = createReactClass({
      * Size of the refresh indicator, see RefreshControl.SIZE.
      * @platform android
      */
-    size: PropTypes.oneOf([RefreshLayoutConsts.SIZE.DEFAULT, RefreshLayoutConsts.SIZE.LARGE]),
+    size: PropTypes.oneOf([
+      RefreshLayoutConsts.SIZE.DEFAULT,
+      RefreshLayoutConsts.SIZE.LARGE,
+    ]),
     /**
      * Progress view top offset
      * @platform android
@@ -156,7 +161,9 @@ const RefreshControl = createReactClass({
     return (
       <NativeRefreshControl
         {...this.props}
-        ref={ref => {this._nativeRef = ref;}}
+        ref={ref => {
+          this._nativeRef = ref;
+        }}
         onRefresh={this._onRefresh}
       />
     );
@@ -176,12 +183,12 @@ const RefreshControl = createReactClass({
 if (Platform.OS === 'ios') {
   var NativeRefreshControl = requireNativeComponent(
     'RCTRefreshControl',
-    RefreshControl
+    RefreshControl,
   );
 } else if (Platform.OS === 'android') {
   var NativeRefreshControl = requireNativeComponent(
     'AndroidSwipeRefreshLayout',
-    RefreshControl
+    RefreshControl,
   );
 }
 
diff --git a/Libraries/Components/RefreshControl/__mocks__/RefreshControlMock.js b/Libraries/Components/RefreshControl/__mocks__/RefreshControlMock.js
index 04312d5d4c5d..bc03b7afa878 100644
--- a/Libraries/Components/RefreshControl/__mocks__/RefreshControlMock.js
+++ b/Libraries/Components/RefreshControl/__mocks__/RefreshControlMock.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
diff --git a/Libraries/Components/SafeAreaView/SafeAreaView.android.js b/Libraries/Components/SafeAreaView/SafeAreaView.android.js
index fbc940205383..a581258a5783 100644
--- a/Libraries/Components/SafeAreaView/SafeAreaView.android.js
+++ b/Libraries/Components/SafeAreaView/SafeAreaView.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 module.exports = require('View');
diff --git a/Libraries/Components/ScrollResponder.js b/Libraries/Components/ScrollResponder.js
index 6a38cc7523dd..ab388a31083f 100644
--- a/Libraries/Components/ScrollResponder.js
+++ b/Libraries/Components/ScrollResponder.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Dimensions = require('Dimensions');
@@ -21,7 +23,7 @@ const nullthrows = require('fbjs/lib/nullthrows');
 const performanceNow = require('fbjs/lib/performanceNow');
 const warning = require('fbjs/lib/warning');
 
-const { ScrollViewManager } = require('NativeModules');
+const {ScrollViewManager} = require('NativeModules');
 
 /**
  * Mixin that can be integrated in order to handle scrolling that plays well
@@ -104,11 +106,11 @@ const { ScrollViewManager } = require('NativeModules');
 const IS_ANIMATING_TOUCH_START_THRESHOLD_MS = 16;
 
 type State = {
-    isTouching: boolean,
-    lastMomentumScrollBeginTime: number,
-    lastMomentumScrollEndTime: number,
-    observedScrollSinceBecomingResponder: boolean,
-    becameResponderWhileAnimating: boolean,
+  isTouching: boolean,
+  lastMomentumScrollBeginTime: number,
+  lastMomentumScrollEndTime: number,
+  observedScrollSinceBecomingResponder: boolean,
+  becameResponderWhileAnimating: boolean,
 };
 type Event = Object;
 
@@ -165,9 +167,11 @@ const ScrollResponderMixin = {
   scrollResponderHandleStartShouldSetResponder: function(e: Event): boolean {
     const currentlyFocusedTextInput = TextInputState.currentlyFocusedField();
 
-    if (this.props.keyboardShouldPersistTaps === 'handled' &&
+    if (
+      this.props.keyboardShouldPersistTaps === 'handled' &&
       currentlyFocusedTextInput != null &&
-      e.target !== currentlyFocusedTextInput) {
+      e.target !== currentlyFocusedTextInput
+    ) {
       return true;
     }
     return false;
@@ -184,7 +188,9 @@ const ScrollResponderMixin = {
    *
    * Invoke this from an `onStartShouldSetResponderCapture` event.
    */
-  scrollResponderHandleStartShouldSetResponderCapture: function(e: Event): boolean {
+  scrollResponderHandleStartShouldSetResponderCapture: function(
+    e: Event,
+  ): boolean {
     // The scroll view should receive taps instead of its descendants if:
     // * it is already animating/decelerating
     if (this.scrollResponderIsAnimating()) {
@@ -197,11 +203,13 @@ const ScrollResponderMixin = {
     // then the second tap goes to the actual interior view)
     const currentlyFocusedTextInput = TextInputState.currentlyFocusedField();
     const {keyboardShouldPersistTaps} = this.props;
-    const keyboardNeverPersistTaps = !keyboardShouldPersistTaps ||
-                                    keyboardShouldPersistTaps === 'never';
-    if (keyboardNeverPersistTaps &&
+    const keyboardNeverPersistTaps =
+      !keyboardShouldPersistTaps || keyboardShouldPersistTaps === 'never';
+    if (
+      keyboardNeverPersistTaps &&
       currentlyFocusedTextInput != null
-      /* && !TextInputState.isTextInput(e.target) */) {
+      /* && !TextInputState.isTextInput(e.target) */
+    ) {
       return true;
     }
 
@@ -218,8 +226,7 @@ const ScrollResponderMixin = {
    * altogether. To improve this, find a way to disable the `UIScrollView` after
    * a touch has already started.
    */
-  scrollResponderHandleResponderReject: function() {
-  },
+  scrollResponderHandleResponderReject: function() {},
 
   /**
    * We will allow the scroll view to give up its lock iff it acquired the lock
@@ -270,12 +277,14 @@ const ScrollResponderMixin = {
     // By default scroll views will unfocus a textField
     // if another touch occurs outside of it
     const currentlyFocusedTextInput = TextInputState.currentlyFocusedField();
-    if (this.props.keyboardShouldPersistTaps !== true &&
+    if (
+      this.props.keyboardShouldPersistTaps !== true &&
       this.props.keyboardShouldPersistTaps !== 'always' &&
       currentlyFocusedTextInput != null &&
-      e.target !== currentlyFocusedTextInput  &&
+      e.target !== currentlyFocusedTextInput &&
       !this.state.observedScrollSinceBecomingResponder &&
-      !this.state.becameResponderWhileAnimating) {
+      !this.state.becameResponderWhileAnimating
+    ) {
       this.props.onScrollResponderKeyboardDismissed &&
         this.props.onScrollResponderKeyboardDismissed(e);
       TextInputState.blurTextInput(currentlyFocusedTextInput);
@@ -318,8 +327,10 @@ const ScrollResponderMixin = {
     // - If velocity is non-zero, then the interaction will stop when momentum scroll ends or
     //   another drag starts and ends.
     // - If we don't get velocity, better to stop the interaction twice than not stop it.
-    if (!this.scrollResponderIsAnimating() &&
-        (!velocity || velocity.x === 0 && velocity.y === 0)) {
+    if (
+      !this.scrollResponderIsAnimating() &&
+      (!velocity || (velocity.x === 0 && velocity.y === 0))
+    ) {
       FrameRateLogger.endScroll();
     }
     this.props.onScrollEndDrag && this.props.onScrollEndDrag(e);
@@ -380,9 +391,12 @@ const ScrollResponderMixin = {
    */
   scrollResponderIsAnimating: function(): boolean {
     const now = performanceNow();
-    const timeSinceLastMomentumScrollEnd = now - this.state.lastMomentumScrollEndTime;
-    const isAnimating = timeSinceLastMomentumScrollEnd < IS_ANIMATING_TOUCH_START_THRESHOLD_MS ||
-      this.state.lastMomentumScrollEndTime < this.state.lastMomentumScrollBeginTime;
+    const timeSinceLastMomentumScrollEnd =
+      now - this.state.lastMomentumScrollEndTime;
+    const isAnimating =
+      timeSinceLastMomentumScrollEnd < IS_ANIMATING_TOUCH_START_THRESHOLD_MS ||
+      this.state.lastMomentumScrollEndTime <
+        this.state.lastMomentumScrollBeginTime;
     return isAnimating;
   },
 
@@ -392,9 +406,9 @@ const ScrollResponderMixin = {
    * function otherwise `this` is used.
    */
   scrollResponderGetScrollableNode: function(): any {
-    return this.getScrollableNode ?
-      this.getScrollableNode() :
-      ReactNative.findNodeHandle(this);
+    return this.getScrollableNode
+      ? this.getScrollableNode()
+      : ReactNative.findNodeHandle(this);
   },
 
   /**
@@ -409,12 +423,14 @@ const ScrollResponderMixin = {
    * This is deprecated due to ambiguity (y before x), and SHOULD NOT BE USED.
    */
   scrollResponderScrollTo: function(
-    x?: number | { x?: number, y?: number, animated?: boolean },
+    x?: number | {x?: number, y?: number, animated?: boolean},
     y?: number,
-    animated?: boolean
+    animated?: boolean,
   ) {
     if (typeof x === 'number') {
-      console.warn('`scrollResponderScrollTo(x, y, animated)` is deprecated. Use `scrollResponderScrollTo({x: 5, y: 5, animated: true})` instead.');
+      console.warn(
+        '`scrollResponderScrollTo(x, y, animated)` is deprecated. Use `scrollResponderScrollTo({x: 5, y: 5, animated: true})` instead.',
+      );
     } else {
       ({x, y, animated} = x || {});
     }
@@ -433,9 +449,7 @@ const ScrollResponderMixin = {
    *
    * `scrollResponderScrollToEnd({animated: true})`
    */
-  scrollResponderScrollToEnd: function(
-    options?: { animated?: boolean },
-  ) {
+  scrollResponderScrollToEnd: function(options?: {animated?: boolean}) {
     // Default to true
     const animated = (options && options.animated) !== false;
     UIManager.dispatchViewManagerCommand(
@@ -448,8 +462,13 @@ const ScrollResponderMixin = {
   /**
    * Deprecated, do not use.
    */
-  scrollResponderScrollWithoutAnimationTo: function(offsetX: number, offsetY: number) {
-    console.warn('`scrollResponderScrollWithoutAnimationTo` is deprecated. Use `scrollResponderScrollTo` instead');
+  scrollResponderScrollWithoutAnimationTo: function(
+    offsetX: number,
+    offsetY: number,
+  ) {
+    console.warn(
+      '`scrollResponderScrollWithoutAnimationTo` is deprecated. Use `scrollResponderScrollTo` instead',
+    );
     this.scrollResponderScrollTo({x: offsetX, y: offsetY, animated: false});
   },
 
@@ -460,17 +479,32 @@ const ScrollResponderMixin = {
    * @platform ios
    */
   scrollResponderZoomTo: function(
-    rect: {| x: number, y: number, width: number, height: number, animated?: boolean |},
-    animated?: boolean // deprecated, put this inside the rect argument instead
+    rect: {|
+      x: number,
+      y: number,
+      width: number,
+      height: number,
+      animated?: boolean,
+    |},
+    animated?: boolean, // deprecated, put this inside the rect argument instead
   ) {
-    invariant(ScrollViewManager && ScrollViewManager.zoomToRect, 'zoomToRect is not implemented');
+    invariant(
+      ScrollViewManager && ScrollViewManager.zoomToRect,
+      'zoomToRect is not implemented',
+    );
     if ('animated' in rect) {
       animated = rect.animated;
       delete rect.animated;
     } else if (typeof animated !== 'undefined') {
-      console.warn('`scrollResponderZoomTo` `animated` argument is deprecated. Use `options.animated` instead');
+      console.warn(
+        '`scrollResponderZoomTo` `animated` argument is deprecated. Use `options.animated` instead',
+      );
     }
-    ScrollViewManager.zoomToRect(this.scrollResponderGetScrollableNode(), rect, animated !== false);
+    ScrollViewManager.zoomToRect(
+      this.scrollResponderGetScrollableNode(),
+      rect,
+      animated !== false,
+    );
   },
 
   /**
@@ -480,7 +514,7 @@ const ScrollResponderMixin = {
     UIManager.dispatchViewManagerCommand(
       this.scrollResponderGetScrollableNode(),
       UIManager.RCTScrollView.Commands.flashScrollIndicators,
-      []
+      [],
     );
   },
 
@@ -494,14 +528,18 @@ const ScrollResponderMixin = {
    * @param {bool} preventNegativeScrolling Whether to allow pulling the content
    *        down to make it meet the keyboard's top. Default is false.
    */
-  scrollResponderScrollNativeHandleToKeyboard: function(nodeHandle: any, additionalOffset?: number, preventNegativeScrollOffset?: bool) {
+  scrollResponderScrollNativeHandleToKeyboard: function(
+    nodeHandle: any,
+    additionalOffset?: number,
+    preventNegativeScrollOffset?: boolean,
+  ) {
     this.additionalScrollOffset = additionalOffset || 0;
     this.preventNegativeScrollOffset = !!preventNegativeScrollOffset;
     UIManager.measureLayout(
       nodeHandle,
       ReactNative.findNodeHandle(this.getInnerViewNode()),
       this.scrollResponderTextInputFocusError,
-      this.scrollResponderInputMeasureAndScrollToKeyboard
+      this.scrollResponderInputMeasureAndScrollToKeyboard,
     );
   },
 
@@ -515,12 +553,18 @@ const ScrollResponderMixin = {
    * @param {number} width Width of the text input.
    * @param {number} height Height of the text input.
    */
-  scrollResponderInputMeasureAndScrollToKeyboard: function(left: number, top: number, width: number, height: number) {
+  scrollResponderInputMeasureAndScrollToKeyboard: function(
+    left: number,
+    top: number,
+    width: number,
+    height: number,
+  ) {
     let keyboardScreenY = Dimensions.get('window').height;
     if (this.keyboardWillOpenTo) {
       keyboardScreenY = this.keyboardWillOpenTo.endCoordinates.screenY;
     }
-    let scrollOffsetY = top - keyboardScreenY + height + this.additionalScrollOffset;
+    let scrollOffsetY =
+      top - keyboardScreenY + height + this.additionalScrollOffset;
 
     // By default, this can scroll with negative offset, pulling the content
     // down so that the target component's bottom meets the keyboard's top.
@@ -549,16 +593,34 @@ const ScrollResponderMixin = {
     const {keyboardShouldPersistTaps} = this.props;
     warning(
       typeof keyboardShouldPersistTaps !== 'boolean',
-      `'keyboardShouldPersistTaps={${keyboardShouldPersistTaps}}' is deprecated. `
-      + `Use 'keyboardShouldPersistTaps="${keyboardShouldPersistTaps ? 'always' : 'never'}"' instead`
+      `'keyboardShouldPersistTaps={${keyboardShouldPersistTaps}}' is deprecated. ` +
+        `Use 'keyboardShouldPersistTaps="${
+          keyboardShouldPersistTaps ? 'always' : 'never'
+        }"' instead`,
     );
 
     this.keyboardWillOpenTo = null;
     this.additionalScrollOffset = 0;
-    this.addListenerOn(Keyboard, 'keyboardWillShow', this.scrollResponderKeyboardWillShow);
-    this.addListenerOn(Keyboard, 'keyboardWillHide', this.scrollResponderKeyboardWillHide);
-    this.addListenerOn(Keyboard, 'keyboardDidShow', this.scrollResponderKeyboardDidShow);
-    this.addListenerOn(Keyboard, 'keyboardDidHide', this.scrollResponderKeyboardDidHide);
+    this.addListenerOn(
+      Keyboard,
+      'keyboardWillShow',
+      this.scrollResponderKeyboardWillShow,
+    );
+    this.addListenerOn(
+      Keyboard,
+      'keyboardWillHide',
+      this.scrollResponderKeyboardWillHide,
+    );
+    this.addListenerOn(
+      Keyboard,
+      'keyboardDidShow',
+      this.scrollResponderKeyboardDidShow,
+    );
+    this.addListenerOn(
+      Keyboard,
+      'keyboardDidHide',
+      this.scrollResponderKeyboardDidHide,
+    );
   },
 
   /**
@@ -611,8 +673,7 @@ const ScrollResponderMixin = {
   scrollResponderKeyboardDidHide: function(e: Event) {
     this.keyboardWillOpenTo = null;
     this.props.onKeyboardDidHide && this.props.onKeyboardDidHide(e);
-  }
-
+  },
 };
 
 const ScrollResponder = {
diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 0ec0f188abd8..4b9aa3cff4f5 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const AnimatedImplementation = require('AnimatedImplementation');
@@ -235,7 +237,13 @@ const ScrollView = createReactClass({
      *   - `false`, deprecated, use 'never' instead
      *   - `true`, deprecated, use 'always' instead
      */
-    keyboardShouldPersistTaps: PropTypes.oneOf(['always', 'never', 'handled', false, true]),
+    keyboardShouldPersistTaps: PropTypes.oneOf([
+      'always',
+      'never',
+      'handled',
+      false,
+      true,
+    ]),
     /**
      * When set, the scroll view will adjust the scroll position so that the first child that is
      * currently visible and at or beyond `minIndexForVisible` will not change position. This is
@@ -274,7 +282,7 @@ const ScrollView = createReactClass({
      * @platform ios
      */
     minimumZoomScale: PropTypes.number,
-     /**
+    /**
      * Enables nested scrolling for Android API level 21+.
      * Nested scrolling is supported by default on iOS
      * @platform android
@@ -321,10 +329,10 @@ const ScrollView = createReactClass({
      */
     pagingEnabled: PropTypes.bool,
     /**
-    * When true, ScrollView allows use of pinch gestures to zoom in and out.
-    * The default value is true.
-    * @platform ios
-    */
+     * When true, ScrollView allows use of pinch gestures to zoom in and out.
+     * The default value is true.
+     * @platform ios
+     */
     pinchGestureEnabled: PropTypes.bool,
     /**
      * When false, the view cannot be scrolled via touch interaction.
@@ -453,7 +461,7 @@ const ScrollView = createReactClass({
      */
     scrollPerfTag: PropTypes.string,
 
-     /**
+    /**
      * Used to override default value of overScroll mode.
      *
      * Possible values:
@@ -465,11 +473,7 @@ const ScrollView = createReactClass({
      *
      * @platform android
      */
-    overScrollMode: PropTypes.oneOf([
-      'auto',
-      'always',
-      'never',
-    ]),
+    overScrollMode: PropTypes.oneOf(['auto', 'always', 'never']),
     /**
      * When true, ScrollView will emit updateChildFrames data in scroll events,
      * otherwise will not compute or emit child frame data.  This only exists
@@ -491,18 +495,20 @@ const ScrollView = createReactClass({
      * `import IMAGE from './image.jpg'`.
      * @platform vr
      */
-     scrollBarThumbImage: PropTypes.oneOfType([
-       PropTypes.shape({
-         uri: PropTypes.string,
-       }),
-       // Opaque type returned by import IMAGE from './image.jpg'
-       PropTypes.number,
-     ]),
+    scrollBarThumbImage: PropTypes.oneOfType([
+      PropTypes.shape({
+        uri: PropTypes.string,
+      }),
+      // Opaque type returned by import IMAGE from './image.jpg'
+      PropTypes.number,
+    ]),
   },
 
   mixins: [ScrollResponder.Mixin],
 
-  _scrollAnimatedValue: (new AnimatedImplementation.Value(0): AnimatedImplementation.Value),
+  _scrollAnimatedValue: (new AnimatedImplementation.Value(
+    0,
+  ): AnimatedImplementation.Value),
   _scrollAnimatedValueAttachment: (null: ?{detach: () => void}),
   _stickyHeaderRefs: (new Map(): Map<number, ScrollViewStickyHeader>),
   _headerLayoutYs: (new Map(): Map<string, number>),
@@ -514,8 +520,12 @@ const ScrollView = createReactClass({
   },
 
   UNSAFE_componentWillMount: function() {
-    this._scrollAnimatedValue = new AnimatedImplementation.Value(this.props.contentOffset ? this.props.contentOffset.y : 0);
-    this._scrollAnimatedValue.setOffset(this.props.contentInset ? this.props.contentInset.top : 0);
+    this._scrollAnimatedValue = new AnimatedImplementation.Value(
+      this.props.contentOffset ? this.props.contentOffset.y : 0,
+    );
+    this._scrollAnimatedValue.setOffset(
+      this.props.contentInset ? this.props.contentInset.top : 0,
+    );
     this._stickyHeaderRefs = new Map();
     this._headerLayoutYs = new Map();
   },
@@ -568,19 +578,23 @@ const ScrollView = createReactClass({
    * This is deprecated due to ambiguity (y before x), and SHOULD NOT BE USED.
    */
   scrollTo: function(
-    y?: number | { x?: number, y?: number, animated?: boolean },
+    y?: number | {x?: number, y?: number, animated?: boolean},
     x?: number,
-    animated?: boolean
+    animated?: boolean,
   ) {
     if (typeof y === 'number') {
-      console.warn('`scrollTo(y, x, animated)` is deprecated. Use `scrollTo({x: 5, y: 5, ' +
-        'animated: true})` instead.');
+      console.warn(
+        '`scrollTo(y, x, animated)` is deprecated. Use `scrollTo({x: 5, y: 5, ' +
+          'animated: true})` instead.',
+      );
     } else {
       ({x, y, animated} = y || {});
     }
-    this.getScrollResponder().scrollResponderScrollTo(
-      {x: x || 0, y: y || 0, animated: animated !== false}
-    );
+    this.getScrollResponder().scrollResponderScrollTo({
+      x: x || 0,
+      y: y || 0,
+      animated: animated !== false,
+    });
   },
 
   /**
@@ -591,9 +605,7 @@ const ScrollView = createReactClass({
    * `scrollToEnd({animated: false})` for immediate scrolling.
    * If no options are passed, `animated` defaults to true.
    */
-  scrollToEnd: function(
-    options?: { animated?: boolean },
-  ) {
+  scrollToEnd: function(options?: {animated?: boolean}) {
     // Default to true
     const animated = (options && options.animated) !== false;
     this.getScrollResponder().scrollResponderScrollToEnd({
@@ -605,7 +617,9 @@ const ScrollView = createReactClass({
    * Deprecated, use `scrollTo` instead.
    */
   scrollWithoutAnimationTo: function(y: number = 0, x: number = 0) {
-    console.warn('`scrollWithoutAnimationTo` is deprecated. Use `scrollTo` instead');
+    console.warn(
+      '`scrollWithoutAnimationTo` is deprecated. Use `scrollTo` instead',
+    );
     this.scrollTo({x, y, animated: false});
   },
 
@@ -627,11 +641,14 @@ const ScrollView = createReactClass({
     if (this._scrollAnimatedValueAttachment) {
       this._scrollAnimatedValueAttachment.detach();
     }
-    if (this.props.stickyHeaderIndices && this.props.stickyHeaderIndices.length > 0) {
+    if (
+      this.props.stickyHeaderIndices &&
+      this.props.stickyHeaderIndices.length > 0
+    ) {
       this._scrollAnimatedValueAttachment = AnimatedImplementation.attachNativeEvent(
         this._scrollViewRef,
         'onScroll',
-        [{nativeEvent: {contentOffset: {y: this._scrollAnimatedValue}}}]
+        [{nativeEvent: {contentOffset: {y: this._scrollAnimatedValue}}}],
       );
     }
   },
@@ -658,10 +675,12 @@ const ScrollView = createReactClass({
     this._headerLayoutYs.set(key, layoutY);
 
     const indexOfIndex = this.props.stickyHeaderIndices.indexOf(index);
-    const previousHeaderIndex = this.props.stickyHeaderIndices[indexOfIndex - 1];
+    const previousHeaderIndex = this.props.stickyHeaderIndices[
+      indexOfIndex - 1
+    ];
     if (previousHeaderIndex != null) {
       const previousHeader = this._stickyHeaderRefs.get(
-        this._getKeyForIndex(previousHeaderIndex, childArray)
+        this._getKeyForIndex(previousHeaderIndex, childArray),
       );
       previousHeader && previousHeader.setNextHeaderY(layoutY);
     }
@@ -669,18 +688,25 @@ const ScrollView = createReactClass({
 
   _handleScroll: function(e: Object) {
     if (__DEV__) {
-      if (this.props.onScroll && this.props.scrollEventThrottle == null && Platform.OS === 'ios') {
+      if (
+        this.props.onScroll &&
+        this.props.scrollEventThrottle == null &&
+        Platform.OS === 'ios'
+      ) {
         console.log(
           'You specified `onScroll` on a <ScrollView> but not ' +
-          '`scrollEventThrottle`. You will only receive one event. ' +
-          'Using `16` you get all the events but be aware that it may ' +
-          'cause frame drops, use a bigger number if you don\'t need as ' +
-          'much precision.'
+            '`scrollEventThrottle`. You will only receive one event. ' +
+            'Using `16` you get all the events but be aware that it may ' +
+            "cause frame drops, use a bigger number if you don't need as " +
+            'much precision.',
         );
       }
     }
     if (Platform.OS === 'android') {
-      if (this.props.keyboardDismissMode === 'on-drag' && this.state.isTouching) {
+      if (
+        this.props.keyboardDismissMode === 'on-drag' &&
+        this.state.isTouching
+      ) {
         dismissKeyboard();
       }
     }
@@ -689,7 +715,7 @@ const ScrollView = createReactClass({
 
   _handleLayout: function(e: Object) {
     if (this.props.invertStickyHeaders) {
-      this.setState({ layoutHeight: e.nativeEvent.layout.height });
+      this.setState({layoutHeight: e.nativeEvent.layout.height});
     }
     if (this.props.onLayout) {
       this.props.onLayout(e);
@@ -698,7 +724,8 @@ const ScrollView = createReactClass({
 
   _handleContentOnLayout: function(e: Object) {
     const {width, height} = e.nativeEvent.layout;
-    this.props.onContentSizeChange && this.props.onContentSizeChange(width, height);
+    this.props.onContentSizeChange &&
+      this.props.onContentSizeChange(width, height);
   },
 
   _scrollViewRef: (null: ?ScrollView),
@@ -727,18 +754,18 @@ const ScrollView = createReactClass({
       ScrollContentContainerViewClass = RCTScrollContentView;
       warning(
         !this.props.snapToInterval || !this.props.pagingEnabled,
-        'snapToInterval is currently ignored when pagingEnabled is true.'
+        'snapToInterval is currently ignored when pagingEnabled is true.',
       );
     }
 
     invariant(
       ScrollViewClass !== undefined,
-      'ScrollViewClass must not be undefined'
+      'ScrollViewClass must not be undefined',
     );
 
     invariant(
       ScrollContentContainerViewClass !== undefined,
-      'ScrollContentContainerViewClass must not be undefined'
+      'ScrollContentContainerViewClass must not be undefined',
     );
 
     const contentContainerStyle = [
@@ -747,12 +774,14 @@ const ScrollView = createReactClass({
     ];
     if (__DEV__ && this.props.style) {
       const style = flattenStyle(this.props.style);
-      const childLayoutProps = ['alignItems', 'justifyContent']
-        .filter((prop) => style && style[prop] !== undefined);
+      const childLayoutProps = ['alignItems', 'justifyContent'].filter(
+        prop => style && style[prop] !== undefined,
+      );
       invariant(
         childLayoutProps.length === 0,
-        'ScrollView child layout (' + JSON.stringify(childLayoutProps) +
-          ') must be applied through the contentContainerStyle prop.'
+        'ScrollView child layout (' +
+          JSON.stringify(childLayoutProps) +
+          ') must be applied through the contentContainerStyle prop.',
       );
     }
 
@@ -764,34 +793,38 @@ const ScrollView = createReactClass({
     }
 
     const {stickyHeaderIndices} = this.props;
-    const hasStickyHeaders = stickyHeaderIndices && stickyHeaderIndices.length > 0;
-    const childArray = hasStickyHeaders && React.Children.toArray(this.props.children);
-    const children = hasStickyHeaders ?
-      childArray.map((child, index) => {
-        const indexOfIndex = child ? stickyHeaderIndices.indexOf(index) : -1;
-        if (indexOfIndex > -1) {
-          const key = child.key;
-          const nextIndex = stickyHeaderIndices[indexOfIndex + 1];
-          return (
-            <ScrollViewStickyHeader
-              key={key}
-              ref={(ref) => this._setStickyHeaderRef(key, ref)}
-              nextHeaderLayoutY={
-                this._headerLayoutYs.get(this._getKeyForIndex(nextIndex, childArray))
-              }
-              onLayout={(event) => this._onStickyHeaderLayout(index, event, key)}
-              scrollAnimatedValue={this._scrollAnimatedValue}
-              inverted={this.props.invertStickyHeaders}
-              scrollViewHeight={this.state.layoutHeight}>
-              {child}
-            </ScrollViewStickyHeader>
-          );
-        } else {
-          return child;
-        }
-      }) :
-      this.props.children;
-    const contentContainer =
+    const hasStickyHeaders =
+      stickyHeaderIndices && stickyHeaderIndices.length > 0;
+    const childArray =
+      hasStickyHeaders && React.Children.toArray(this.props.children);
+    const children = hasStickyHeaders
+      ? childArray.map((child, index) => {
+          const indexOfIndex = child ? stickyHeaderIndices.indexOf(index) : -1;
+          if (indexOfIndex > -1) {
+            const key = child.key;
+            const nextIndex = stickyHeaderIndices[indexOfIndex + 1];
+            return (
+              <ScrollViewStickyHeader
+                key={key}
+                ref={ref => this._setStickyHeaderRef(key, ref)}
+                nextHeaderLayoutY={this._headerLayoutYs.get(
+                  this._getKeyForIndex(nextIndex, childArray),
+                )}
+                onLayout={event =>
+                  this._onStickyHeaderLayout(index, event, key)
+                }
+                scrollAnimatedValue={this._scrollAnimatedValue}
+                inverted={this.props.invertStickyHeaders}
+                scrollViewHeight={this.state.layoutHeight}>
+                {child}
+              </ScrollViewStickyHeader>
+            );
+          } else {
+            return child;
+          }
+        })
+      : this.props.children;
+    const contentContainer = (
       <ScrollContentContainerViewClass
         {...contentSizeChangeProps}
         ref={this._setInnerViewRef}
@@ -799,28 +832,31 @@ const ScrollView = createReactClass({
         removeClippedSubviews={
           // Subview clipping causes issues with sticky headers on Android and
           // would be hard to fix properly in a performant way.
-          Platform.OS === 'android' && hasStickyHeaders ?
-            false :
-            this.props.removeClippedSubviews
+          Platform.OS === 'android' && hasStickyHeaders
+            ? false
+            : this.props.removeClippedSubviews
         }
         collapsable={false}>
         {children}
-      </ScrollContentContainerViewClass>;
+      </ScrollContentContainerViewClass>
+    );
 
     const alwaysBounceHorizontal =
-      this.props.alwaysBounceHorizontal !== undefined ?
-        this.props.alwaysBounceHorizontal :
-        this.props.horizontal;
+      this.props.alwaysBounceHorizontal !== undefined
+        ? this.props.alwaysBounceHorizontal
+        : this.props.horizontal;
 
     const alwaysBounceVertical =
-      this.props.alwaysBounceVertical !== undefined ?
-        this.props.alwaysBounceVertical :
-        !this.props.horizontal;
+      this.props.alwaysBounceVertical !== undefined
+        ? this.props.alwaysBounceVertical
+        : !this.props.horizontal;
 
-    const DEPRECATED_sendUpdatedChildFrames =
-      !!this.props.DEPRECATED_sendUpdatedChildFrames;
+    const DEPRECATED_sendUpdatedChildFrames = !!this.props
+      .DEPRECATED_sendUpdatedChildFrames;
 
-    const baseStyle = this.props.horizontal ? styles.baseHorizontal : styles.baseVertical;
+    const baseStyle = this.props.horizontal
+      ? styles.baseHorizontal
+      : styles.baseVertical;
     const props = {
       ...this.props,
       alwaysBounceHorizontal,
@@ -836,25 +872,33 @@ const ScrollView = createReactClass({
       onResponderReject: this.scrollResponderHandleResponderReject,
       onResponderRelease: this.scrollResponderHandleResponderRelease,
       onResponderTerminate: this.scrollResponderHandleTerminate,
-      onResponderTerminationRequest: this.scrollResponderHandleTerminationRequest,
+      onResponderTerminationRequest: this
+        .scrollResponderHandleTerminationRequest,
       onScroll: this._handleScroll,
       onScrollBeginDrag: this.scrollResponderHandleScrollBeginDrag,
       onScrollEndDrag: this.scrollResponderHandleScrollEndDrag,
-      onScrollShouldSetResponder: this.scrollResponderHandleScrollShouldSetResponder,
-      onStartShouldSetResponder: this.scrollResponderHandleStartShouldSetResponder,
-      onStartShouldSetResponderCapture: this.scrollResponderHandleStartShouldSetResponderCapture,
+      onScrollShouldSetResponder: this
+        .scrollResponderHandleScrollShouldSetResponder,
+      onStartShouldSetResponder: this
+        .scrollResponderHandleStartShouldSetResponder,
+      onStartShouldSetResponderCapture: this
+        .scrollResponderHandleStartShouldSetResponderCapture,
       onTouchEnd: this.scrollResponderHandleTouchEnd,
       onTouchMove: this.scrollResponderHandleTouchMove,
       onTouchStart: this.scrollResponderHandleTouchStart,
       onTouchCancel: this.scrollResponderHandleTouchCancel,
       scrollBarThumbImage: resolveAssetSource(this.props.scrollBarThumbImage),
-      scrollEventThrottle: hasStickyHeaders ? 1 : this.props.scrollEventThrottle,
-      sendMomentumEvents: (this.props.onMomentumScrollBegin || this.props.onMomentumScrollEnd) ?
-        true : false,
+      scrollEventThrottle: hasStickyHeaders
+        ? 1
+        : this.props.scrollEventThrottle,
+      sendMomentumEvents:
+        this.props.onMomentumScrollBegin || this.props.onMomentumScrollEnd
+          ? true
+          : false,
       DEPRECATED_sendUpdatedChildFrames,
     };
 
-    const { decelerationRate } = this.props;
+    const {decelerationRate} = this.props;
     if (decelerationRate) {
       props.decelerationRate = processDecelerationRate(decelerationRate);
     }
@@ -881,9 +925,12 @@ const ScrollView = createReactClass({
         return React.cloneElement(
           refreshControl,
           {style: props.style},
-          <ScrollViewClass {...props} style={baseStyle} ref={this._setScrollViewRef}>
+          <ScrollViewClass
+            {...props}
+            style={baseStyle}
+            ref={this._setScrollViewRef}>
             {contentContainer}
-          </ScrollViewClass>
+          </ScrollViewClass>,
         );
       }
     }
@@ -892,7 +939,7 @@ const ScrollView = createReactClass({
         {contentContainer}
       </ScrollViewClass>
     );
-  }
+  },
 });
 
 const styles = StyleSheet.create({
@@ -923,29 +970,29 @@ if (Platform.OS === 'android') {
   nativeOnlyProps = {
     nativeOnly: {
       sendMomentumEvents: true,
-    }
+    },
   };
   AndroidScrollView = requireNativeComponent(
     'RCTScrollView',
     (ScrollView: React.ComponentType<any>),
-    nativeOnlyProps
+    nativeOnlyProps,
   );
   AndroidHorizontalScrollView = requireNativeComponent(
     'AndroidHorizontalScrollView',
     (ScrollView: React.ComponentType<any>),
-    nativeOnlyProps
+    nativeOnlyProps,
   );
   AndroidHorizontalScrollContentView = requireNativeComponent(
-    'AndroidHorizontalScrollContentView'
+    'AndroidHorizontalScrollContentView',
   );
 } else if (Platform.OS === 'ios') {
   nativeOnlyProps = {
     nativeOnly: {
       onMomentumScrollBegin: true,
-      onMomentumScrollEnd : true,
+      onMomentumScrollEnd: true,
       onScrollBeginDrag: true,
       onScrollEndDrag: true,
-    }
+    },
   };
   RCTScrollView = requireNativeComponent(
     'RCTScrollView',
@@ -955,8 +1002,7 @@ if (Platform.OS === 'android') {
   RCTScrollContentView = requireNativeComponent('RCTScrollContentView', View);
 } else {
   nativeOnlyProps = {
-    nativeOnly: {
-    }
+    nativeOnly: {},
   };
   RCTScrollView = requireNativeComponent(
     'RCTScrollView',
diff --git a/Libraries/Components/ScrollView/__mocks__/ScrollViewMock.js b/Libraries/Components/ScrollView/__mocks__/ScrollViewMock.js
index eaa8bb7385e3..46f691382d2f 100644
--- a/Libraries/Components/ScrollView/__mocks__/ScrollViewMock.js
+++ b/Libraries/Components/ScrollView/__mocks__/ScrollViewMock.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -27,9 +28,7 @@ class ScrollViewMock extends ScrollViewComponent {
     return (
       <RCTScrollView {...this.props}>
         {this.props.refreshControl}
-        <View>
-          {this.props.children}
-        </View>
+        <View>{this.props.children}</View>
       </RCTScrollView>
     );
   }
diff --git a/Libraries/Components/ScrollView/processDecelerationRate.js b/Libraries/Components/ScrollView/processDecelerationRate.js
index f46755fda278..18b903ffa383 100644
--- a/Libraries/Components/ScrollView/processDecelerationRate.js
+++ b/Libraries/Components/ScrollView/processDecelerationRate.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 function processDecelerationRate(decelerationRate) {
diff --git a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.android.js b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.android.js
index a8b791e2f6ef..7a988960ceca 100644
--- a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.android.js
+++ b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.android.js
@@ -1,10 +1,10 @@
-
 /**
  * Copyright (c) 2015-present, Facebook, Inc.
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -40,7 +40,7 @@ const styles = StyleSheet.create({
     color: '#333333',
     margin: 5,
     fontSize: 10,
-  }
+  },
 });
 
 module.exports = DummySegmentedControlIOS;
diff --git a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
index 620a8a3ec5c0..7324e4d88533 100644
--- a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
+++ b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeMethodsMixin = require('NativeMethodsMixin');
@@ -89,19 +91,20 @@ const SegmentedControlIOS = createReactClass({
      * If true, then selecting a segment won't persist visually.
      * The `onValueChange` callback will still work as expected.
      */
-    momentary: PropTypes.bool
+    momentary: PropTypes.bool,
   },
 
   getDefaultProps: function(): DefaultProps {
     return {
       values: [],
-      enabled: true
+      enabled: true,
     };
   },
 
   _onChange: function(event: Event) {
     this.props.onChange && this.props.onChange(event);
-    this.props.onValueChange && this.props.onValueChange(event.nativeEvent.value);
+    this.props.onValueChange &&
+      this.props.onValueChange(event.nativeEvent.value);
   },
 
   render: function() {
@@ -113,7 +116,7 @@ const SegmentedControlIOS = createReactClass({
         onChange={this._onChange}
       />
     );
-  }
+  },
 });
 
 const styles = StyleSheet.create({
@@ -124,7 +127,7 @@ const styles = StyleSheet.create({
 
 const RCTSegmentedControl = requireNativeComponent(
   'RCTSegmentedControl',
-  SegmentedControlIOS
+  SegmentedControlIOS,
 );
 
 module.exports = SegmentedControlIOS;
diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index c0f3d015badb..8e9eabd43618 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Image = require('Image');
@@ -192,13 +194,13 @@ const Slider = createReactClass({
     testID: PropTypes.string,
   },
 
-  getDefaultProps: function() : any {
+  getDefaultProps: function(): any {
     return {
       disabled: false,
       value: 0,
       minimumValue: 0,
       maximumValue: 1,
-      step: 0
+      step: 0,
     };
   },
 
@@ -206,8 +208,8 @@ const Slider = createReactClass({
     uiViewClassName: 'RCTSlider',
     validAttributes: {
       ...ReactNativeViewAttributes.RCTView,
-      value: true
-    }
+      value: true,
+    },
   },
 
   render: function() {
@@ -220,15 +222,17 @@ const Slider = createReactClass({
     /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
      * suppresses an error found when Flow v0.54 was deployed. To see the error
      * delete this comment and run Flow. */
-    props.onValueChange = onValueChange && ((event: Event) => {
-      let userEvent = true;
-      if (Platform.OS === 'android') {
-        // On Android there's a special flag telling us the user is
-        // dragging the slider.
-        userEvent = event.nativeEvent.fromUser;
-      }
-      onValueChange && userEvent && onValueChange(event.nativeEvent.value);
-    });
+    props.onValueChange =
+      onValueChange &&
+      ((event: Event) => {
+        let userEvent = true;
+        if (Platform.OS === 'android') {
+          // On Android there's a special flag telling us the user is
+          // dragging the slider.
+          userEvent = event.nativeEvent.fromUser;
+        }
+        onValueChange && userEvent && onValueChange(event.nativeEvent.value);
+      });
 
     /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
      * suppresses an error found when Flow v0.54 was deployed. To see the error
@@ -238,17 +242,21 @@ const Slider = createReactClass({
     /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
      * suppresses an error found when Flow v0.54 was deployed. To see the error
      * delete this comment and run Flow. */
-    props.onSlidingComplete = onSlidingComplete && ((event: Event) => {
-      onSlidingComplete && onSlidingComplete(event.nativeEvent.value);
-    });
-
-    return <RCTSlider
-      {...props}
-      enabled={!this.props.disabled}
-      onStartShouldSetResponder={() => true}
-      onResponderTerminationRequest={() => false}
-    />;
-  }
+    props.onSlidingComplete =
+      onSlidingComplete &&
+      ((event: Event) => {
+        onSlidingComplete && onSlidingComplete(event.nativeEvent.value);
+      });
+
+    return (
+      <RCTSlider
+        {...props}
+        enabled={!this.props.disabled}
+        onStartShouldSetResponder={() => true}
+        onResponderTerminationRequest={() => false}
+      />
+    );
+  },
 });
 
 let styles;
@@ -269,7 +277,7 @@ if (Platform.OS === 'android') {
   options = {
     nativeOnly: {
       enabled: true,
-    }
+    },
   };
 }
 const RCTSlider = requireNativeComponent('RCTSlider', Slider, options);
diff --git a/Libraries/Components/StaticContainer.react.js b/Libraries/Components/StaticContainer.react.js
index a6a4454c8118..ffba809a46ab 100644
--- a/Libraries/Components/StaticContainer.react.js
+++ b/Libraries/Components/StaticContainer.react.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -26,18 +28,16 @@ const React = require('React');
  * React reconciliation.
  */
 class StaticContainer extends React.Component<Object> {
-
   shouldComponentUpdate(nextProps: Object): boolean {
     return !!nextProps.shouldUpdate;
   }
 
   render() {
     const child = this.props.children;
-    return (child === null || child === false)
+    return child === null || child === false
       ? null
       : React.Children.only(child);
   }
-
 }
 
 module.exports = StaticContainer;
diff --git a/Libraries/Components/StaticRenderer.js b/Libraries/Components/StaticRenderer.js
index 5bb9cb99f484..4f8cfbd0989f 100644
--- a/Libraries/Components/StaticRenderer.js
+++ b/Libraries/Components/StaticRenderer.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -21,7 +23,7 @@ class StaticRenderer extends React.Component<{
     render: PropTypes.func.isRequired,
   };
 
-  shouldComponentUpdate(nextProps: { shouldUpdate: boolean }): boolean {
+  shouldComponentUpdate(nextProps: {shouldUpdate: boolean}): boolean {
     return nextProps.shouldUpdate;
   }
 
diff --git a/Libraries/Components/StatusBar/StatusBar.js b/Libraries/Components/StatusBar/StatusBar.js
index 05bd9177ccd4..97db49fdd102 100644
--- a/Libraries/Components/StatusBar/StatusBar.js
+++ b/Libraries/Components/StatusBar/StatusBar.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -24,7 +26,7 @@ export type StatusBarStyle = $Enum<{
   /**
    * Default status bar style (dark for iOS, light for Android)
    */
-  'default': string,
+  default: string,
   /**
    * Dark background, white texts and icons
    */
@@ -42,15 +44,15 @@ export type StatusBarAnimation = $Enum<{
   /**
    * No animation
    */
-  'none': string,
+  none: string,
   /**
    * Fade animation
    */
-  'fade': string,
+  fade: string,
   /**
    * Slide animation
    */
-  'slide': string,
+  slide: string,
 }>;
 
 type DefaultProps = {
@@ -62,7 +64,7 @@ type DefaultProps = {
  */
 function mergePropsStack(
   propsStack: Array<Object>,
-  defaultValues: Object
+  defaultValues: Object,
 ): Object {
   return propsStack.reduce((prev, cur) => {
     for (const prop in cur) {
@@ -223,7 +225,7 @@ class StatusBar extends React.Component<{
   static setNetworkActivityIndicatorVisible(visible: boolean) {
     if (Platform.OS !== 'ios') {
       console.warn(
-        '`setNetworkActivityIndicatorVisible` is only available on iOS'
+        '`setNetworkActivityIndicatorVisible` is only available on iOS',
       );
       return;
     }
@@ -345,7 +347,7 @@ class StatusBar extends React.Component<{
       const oldProps = StatusBar._currentValues;
       const mergedProps = mergePropsStack(
         StatusBar._propsStack,
-        StatusBar._defaultProps
+        StatusBar._defaultProps,
       );
 
       // Update the props that have changed using the merged values from the props stack.
@@ -356,13 +358,15 @@ class StatusBar extends React.Component<{
         ) {
           StatusBarManager.setStyle(
             mergedProps.barStyle.value,
-            mergedProps.barStyle.animated
+            mergedProps.barStyle.animated,
           );
         }
         if (!oldProps || oldProps.hidden.value !== mergedProps.hidden.value) {
           StatusBarManager.setHidden(
             mergedProps.hidden.value,
-            mergedProps.hidden.animated ? mergedProps.hidden.transition : 'none'
+            mergedProps.hidden.animated
+              ? mergedProps.hidden.transition
+              : 'none',
           );
         }
 
@@ -372,7 +376,7 @@ class StatusBar extends React.Component<{
             mergedProps.networkActivityIndicatorVisible
         ) {
           StatusBarManager.setNetworkActivityIndicatorVisible(
-            mergedProps.networkActivityIndicatorVisible
+            mergedProps.networkActivityIndicatorVisible,
           );
         }
       } else if (Platform.OS === 'android') {
@@ -388,7 +392,7 @@ class StatusBar extends React.Component<{
         ) {
           StatusBarManager.setColor(
             processColor(mergedProps.backgroundColor.value),
-            mergedProps.backgroundColor.animated
+            mergedProps.backgroundColor.animated,
           );
         }
         if (!oldProps || oldProps.hidden.value !== mergedProps.hidden.value) {
diff --git a/Libraries/Components/StatusBar/StatusBarIOS.android.js b/Libraries/Components/StatusBar/StatusBarIOS.android.js
index 28ad139b8969..96f77d7868fb 100644
--- a/Libraries/Components/StatusBar/StatusBarIOS.android.js
+++ b/Libraries/Components/StatusBar/StatusBarIOS.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeEventEmitter = require('NativeEventEmitter');
diff --git a/Libraries/Components/StatusBar/StatusBarIOS.ios.js b/Libraries/Components/StatusBar/StatusBarIOS.ios.js
index 3ccab44da625..529e01b308fd 100644
--- a/Libraries/Components/StatusBar/StatusBarIOS.ios.js
+++ b/Libraries/Components/StatusBar/StatusBarIOS.ios.js
@@ -4,12 +4,14 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeEventEmitter = require('NativeEventEmitter');
-const { StatusBarManager } = require('NativeModules');
+const {StatusBarManager} = require('NativeModules');
 
 /**
  * Use `StatusBar` for mutating the status bar.
diff --git a/Libraries/Components/Subscribable.js b/Libraries/Components/Subscribable.js
index a4fc660b5b9f..a56d42ed864c 100644
--- a/Libraries/Components/Subscribable.js
+++ b/Libraries/Components/Subscribable.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 import type EventEmitter from 'EventEmitter';
@@ -21,7 +23,6 @@ import type EventEmitter from 'EventEmitter';
 const Subscribable = {};
 
 Subscribable.Mixin = {
-
   UNSAFE_componentWillMount: function() {
     this._subscribableSubscriptions = [];
   },
@@ -29,9 +30,10 @@ Subscribable.Mixin = {
   componentWillUnmount: function() {
     // This null check is a fix for a broken version of uglify-es. Should be deleted eventually
     // https://github.com/facebook/react-native/issues/17348
-    this._subscribableSubscriptions && this._subscribableSubscriptions.forEach(
-      (subscription) => subscription.remove()
-    );
+    this._subscribableSubscriptions &&
+      this._subscribableSubscriptions.forEach(subscription =>
+        subscription.remove(),
+      );
     this._subscribableSubscriptions = null;
   },
 
@@ -52,12 +54,12 @@ Subscribable.Mixin = {
     eventEmitter: EventEmitter,
     eventType: string,
     listener: Function,
-    context: Object
+    context: Object,
   ) {
     this._subscribableSubscriptions.push(
-      eventEmitter.addListener(eventType, listener, context)
+      eventEmitter.addListener(eventType, listener, context),
     );
-  }
+  },
 };
 
 module.exports = Subscribable;
diff --git a/Libraries/Components/Switch/Switch.js b/Libraries/Components/Switch/Switch.js
index ad613e2c85d4..88f916cf2040 100644
--- a/Libraries/Components/Switch/Switch.js
+++ b/Libraries/Components/Switch/Switch.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -93,7 +95,8 @@ const Switch = createReactClass({
      * suppresses an error when upgrading Flow's support for React. To see the
      * error delete this comment and run Flow. */
     this.props.onChange && this.props.onChange(event);
-    this.props.onValueChange && this.props.onValueChange(event.nativeEvent.value);
+    this.props.onValueChange &&
+      this.props.onValueChange(event.nativeEvent.value);
   },
 
   render: function() {
@@ -113,17 +116,21 @@ const Switch = createReactClass({
       /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
        * error found when Flow v0.70 was deployed. To see the error delete
        * this comment and run Flow. */
-      props.trackTintColor = this.props.value ? this.props.onTintColor : this.props.tintColor;
+      props.trackTintColor = this.props.value
+        ? this.props.onTintColor
+        : this.props.tintColor;
     } else if (Platform.OS === 'ios') {
       props.style = [styles.rctSwitchIOS, this.props.style];
     }
     return (
       <RCTSwitch
         {...props}
-        /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-         * comment suppresses an error when upgrading Flow's support for React.
-         * To see the error delete this comment and run Flow. */
-        ref={(ref) => { this._rctSwitch = ref; }}
+        ref={ref => {
+          /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
+          * comment suppresses an error when upgrading Flow's support for React.
+          * To see the error delete this comment and run Flow. */
+          this._rctSwitch = ref;
+        }}
         onChange={this._onChange}
       />
     );
@@ -134,7 +141,7 @@ const styles = StyleSheet.create({
   rctSwitchIOS: {
     height: 31,
     width: 51,
-  }
+  },
 });
 
 if (Platform.OS === 'android') {
@@ -144,13 +151,13 @@ if (Platform.OS === 'android') {
       on: true,
       enabled: true,
       trackTintColor: true,
-    }
+    },
   });
 } else {
   var RCTSwitch = requireNativeComponent('RCTSwitch', Switch, {
     nativeOnly: {
-      onChange: true
-    }
+      onChange: true,
+    },
   });
 }
 
diff --git a/Libraries/Components/TabBarIOS/TabBarIOS.android.js b/Libraries/Components/TabBarIOS/TabBarIOS.android.js
index 62a6bbac8fb9..e8e376f8a9eb 100644
--- a/Libraries/Components/TabBarIOS/TabBarIOS.android.js
+++ b/Libraries/Components/TabBarIOS/TabBarIOS.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -29,7 +30,7 @@ class DummyTabBarIOS extends React.Component<$FlowFixMeProps> {
 const styles = StyleSheet.create({
   tabGroup: {
     flex: 1,
-  }
+  },
 });
 
 module.exports = DummyTabBarIOS;
diff --git a/Libraries/Components/TabBarIOS/TabBarIOS.ios.js b/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
index 57e32df01e5b..686483f3b232 100644
--- a/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
+++ b/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -20,17 +22,19 @@ const requireNativeComponent = require('requireNativeComponent');
 import type {DangerouslyImpreciseStyleProp} from 'StyleSheet';
 import type {ViewProps} from 'ViewPropTypes';
 
-class TabBarIOS extends React.Component<ViewProps & {
-  style?: DangerouslyImpreciseStyleProp,
-  unselectedTintColor?: string,
-  tintColor?: string,
-  unselectedItemTintColor?: string,
-  barTintColor?: string,
-  barStyle?: 'default' | 'black',
-  translucent?: boolean,
-  itemPositioning?: 'fill' | 'center' | 'auto',
-  children: React.Node,
-}> {
+class TabBarIOS extends React.Component<
+  ViewProps & {
+    style?: DangerouslyImpreciseStyleProp,
+    unselectedTintColor?: string,
+    tintColor?: string,
+    unselectedItemTintColor?: string,
+    barTintColor?: string,
+    barStyle?: 'default' | 'black',
+    translucent?: boolean,
+    itemPositioning?: 'fill' | 'center' | 'auto',
+    children: React.Node,
+  },
+> {
   static Item = TabBarItemIOS;
 
   static propTypes = {
@@ -94,7 +98,7 @@ class TabBarIOS extends React.Component<ViewProps & {
 const styles = StyleSheet.create({
   tabGroup: {
     flex: 1,
-  }
+  },
 });
 
 const RCTTabBar = requireNativeComponent('RCTTabBar', TabBarIOS);
diff --git a/Libraries/Components/TabBarIOS/TabBarItemIOS.android.js b/Libraries/Components/TabBarIOS/TabBarItemIOS.android.js
index 6f6ff5618923..37dc72f4d41f 100644
--- a/Libraries/Components/TabBarIOS/TabBarItemIOS.android.js
+++ b/Libraries/Components/TabBarIOS/TabBarItemIOS.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -18,9 +19,7 @@ class DummyTab extends React.Component {
       return <View />;
     }
     return (
-      <View style={[this.props.style, styles.tab]}>
-        {this.props.children}
-      </View>
+      <View style={[this.props.style, styles.tab]}>{this.props.children}</View>
     );
   }
 }
@@ -35,7 +34,7 @@ const styles = StyleSheet.create({
     left: 0,
     borderColor: 'red',
     borderWidth: 1,
-  }
+  },
 });
 
 module.exports = DummyTab;
diff --git a/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js b/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
index 3f0b85a0c501..44fb44da4486 100644
--- a/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
+++ b/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @noflow
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -26,10 +28,7 @@ class TabBarItemIOS extends React.Component {
     /**
      * Little red bubble that sits at the top right of the icon.
      */
-    badge: PropTypes.oneOfType([
-      PropTypes.string,
-      PropTypes.number,
-    ]),
+    badge: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
     /**
      * Background color for the badge. Available since iOS 10.
      */
@@ -105,7 +104,7 @@ class TabBarItemIOS extends React.Component {
     }
   }
 
-  UNSAFE_componentWillReceiveProps(nextProps: { selected?: boolean }) {
+  UNSAFE_componentWillReceiveProps(nextProps: {selected?: boolean}) {
     if (this.state.hasBeenSelected || nextProps.selected) {
       this.setState({hasBeenSelected: true});
     }
@@ -117,18 +116,17 @@ class TabBarItemIOS extends React.Component {
     // if the tab has already been shown once, always continue to show it so we
     // preserve state between tab transitions
     if (this.state.hasBeenSelected) {
-      var tabContents =
+      var tabContents = (
         <StaticContainer shouldUpdate={this.props.selected}>
           {children}
-        </StaticContainer>;
+        </StaticContainer>
+      );
     } else {
       var tabContents = <View />;
     }
 
     return (
-      <RCTTabBarItem
-        {...props}
-        style={[styles.tab, style]}>
+      <RCTTabBarItem {...props} style={[styles.tab, style]}>
         {tabContents}
       </RCTTabBarItem>
     );
@@ -142,7 +140,7 @@ const styles = StyleSheet.create({
     right: 0,
     bottom: 0,
     left: 0,
-  }
+  },
 });
 
 const RCTTabBarItem = requireNativeComponent('RCTTabBarItem', TabBarItemIOS);
diff --git a/Libraries/Components/TextInput/TextInputState.js b/Libraries/Components/TextInput/TextInputState.js
index 47eeddf12189..95cd24fbe8d2 100644
--- a/Libraries/Components/TextInput/TextInputState.js
+++ b/Libraries/Components/TextInput/TextInputState.js
@@ -4,12 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
  *
  * This class is responsible for coordinating the "focused"
  * state for TextInputs. All calls relating to the keyboard
  * should be funneled through here
+ *
+ * @format
+ * @flow
  */
+
 'use strict';
 
 const Platform = require('Platform');
@@ -18,7 +21,7 @@ const UIManager = require('UIManager');
 const inputs = new Set();
 
 const TextInputState = {
-   /**
+  /**
    * Internal state
    */
   _currentlyFocusedID: (null: ?number),
@@ -45,7 +48,7 @@ const TextInputState = {
         UIManager.dispatchViewManagerCommand(
           textFieldID,
           UIManager.AndroidTextInput.Commands.focusTextInput,
-          null
+          null,
         );
       }
     }
@@ -65,7 +68,7 @@ const TextInputState = {
         UIManager.dispatchViewManagerCommand(
           textFieldID,
           UIManager.AndroidTextInput.Commands.blurTextInput,
-          null
+          null,
         );
       }
     }
diff --git a/Libraries/Components/TimePickerAndroid/TimePickerAndroid.android.js b/Libraries/Components/TimePickerAndroid/TimePickerAndroid.android.js
index b2b8c759e595..6cdd964cc8ce 100644
--- a/Libraries/Components/TimePickerAndroid/TimePickerAndroid.android.js
+++ b/Libraries/Components/TimePickerAndroid/TimePickerAndroid.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const TimePickerModule = require('NativeModules').TimePickerAndroid;
@@ -31,7 +33,6 @@ const TimePickerModule = require('NativeModules').TimePickerAndroid;
  * ```
  */
 class TimePickerAndroid {
-
   /**
    * Opens the standard Android time picker dialog.
    *
@@ -58,11 +59,15 @@ class TimePickerAndroid {
   /**
    * A time has been selected.
    */
-  static get timeSetAction() { return 'timeSetAction'; }
+  static get timeSetAction() {
+    return 'timeSetAction';
+  }
   /**
    * The dialog has been dismissed.
    */
-  static get dismissedAction() { return 'dismissedAction'; }
+  static get dismissedAction() {
+    return 'dismissedAction';
+  }
 }
 
 module.exports = TimePickerAndroid;
diff --git a/Libraries/Components/TimePickerAndroid/TimePickerAndroid.ios.js b/Libraries/Components/TimePickerAndroid/TimePickerAndroid.ios.js
index 3813b6522b00..6a0ecfa65631 100644
--- a/Libraries/Components/TimePickerAndroid/TimePickerAndroid.ios.js
+++ b/Libraries/Components/TimePickerAndroid/TimePickerAndroid.ios.js
@@ -4,14 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const TimePickerAndroid = {
   async open(options: Object): Promise<Object> {
     return Promise.reject({
-      message: 'TimePickerAndroid is not supported on this platform.'
+      message: 'TimePickerAndroid is not supported on this platform.',
     });
   },
 };
diff --git a/Libraries/Components/ToastAndroid/ToastAndroid.android.js b/Libraries/Components/ToastAndroid/ToastAndroid.android.js
index b0a242ed5ffe..c661adf50356 100644
--- a/Libraries/Components/ToastAndroid/ToastAndroid.android.js
+++ b/Libraries/Components/ToastAndroid/ToastAndroid.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -33,7 +34,6 @@ const RCTToastAndroid = require('NativeModules').ToastAndroid;
  */
 
 const ToastAndroid = {
-
   // Toast duration constants
   SHORT: RCTToastAndroid.SHORT,
   LONG: RCTToastAndroid.LONG,
@@ -43,14 +43,11 @@ const ToastAndroid = {
   BOTTOM: RCTToastAndroid.BOTTOM,
   CENTER: RCTToastAndroid.CENTER,
 
-  show: function (
-    message: string,
-    duration: number
-  ): void {
+  show: function(message: string, duration: number): void {
     RCTToastAndroid.show(message, duration);
   },
 
-  showWithGravity: function (
+  showWithGravity: function(
     message: string,
     duration: number,
     gravity: number,
@@ -58,14 +55,20 @@ const ToastAndroid = {
     RCTToastAndroid.showWithGravity(message, duration, gravity);
   },
 
-  showWithGravityAndOffset: function (
+  showWithGravityAndOffset: function(
     message: string,
     duration: number,
     gravity: number,
     xOffset: number,
     yOffset: number,
   ): void {
-    RCTToastAndroid.showWithGravityAndOffset(message, duration, gravity, xOffset, yOffset);
+    RCTToastAndroid.showWithGravityAndOffset(
+      message,
+      duration,
+      gravity,
+      xOffset,
+      yOffset,
+    );
   },
 };
 
diff --git a/Libraries/Components/ToastAndroid/ToastAndroid.ios.js b/Libraries/Components/ToastAndroid/ToastAndroid.ios.js
index 94d0487647ac..adb6032ef673 100644
--- a/Libraries/Components/ToastAndroid/ToastAndroid.ios.js
+++ b/Libraries/Components/ToastAndroid/ToastAndroid.ios.js
@@ -4,21 +4,18 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @noflow
  */
+
 'use strict';
 
 const warning = require('fbjs/lib/warning');
 
 const ToastAndroid = {
-
-  show: function (
-    message: string,
-    duration: number
-  ): void {
+  show: function(message: string, duration: number): void {
     warning(false, 'ToastAndroid is not supported on this platform.');
   },
-
 };
 
 module.exports = ToastAndroid;
diff --git a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
index de6fd5aad12b..5fc04a425301 100644
--- a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
+++ b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -82,12 +83,14 @@ const ToolbarAndroid = createReactClass({
      * `ifRoom` or `never`
      * * `showWithText`: boolean, whether to show text alongside the icon or not
      */
-    actions: PropTypes.arrayOf(PropTypes.shape({
-      title: PropTypes.string.isRequired,
-      icon: optionalImageSource,
-      show: PropTypes.oneOf(['always', 'ifRoom', 'never']),
-      showWithText: PropTypes.bool
-    })),
+    actions: PropTypes.arrayOf(
+      PropTypes.shape({
+        title: PropTypes.string.isRequired,
+        icon: optionalImageSource,
+        show: PropTypes.oneOf(['always', 'ifRoom', 'never']),
+        showWithText: PropTypes.bool,
+      }),
+    ),
     /**
      * Sets the toolbar logo.
      */
@@ -183,7 +186,8 @@ const ToolbarAndroid = createReactClass({
           action.icon = resolveAssetSource(action.icon);
         }
         if (action.show) {
-          action.show = UIManager.ToolbarAndroid.Constants.ShowAsAction[action.show];
+          action.show =
+            UIManager.ToolbarAndroid.Constants.ShowAsAction[action.show];
         }
         nativeActions.push(action);
       }
@@ -206,7 +210,7 @@ const ToolbarAndroid = createReactClass({
 const NativeToolbar = requireNativeComponent('ToolbarAndroid', ToolbarAndroid, {
   nativeOnly: {
     nativeActions: true,
-  }
+  },
 });
 
 module.exports = ToolbarAndroid;
diff --git a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.ios.js b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.ios.js
index ebd42dd5b18b..260d55992979 100644
--- a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.ios.js
+++ b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.ios.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/Components/Touchable/BoundingDimensions.js b/Libraries/Components/Touchable/BoundingDimensions.js
index 898244979d28..755da5ab8937 100644
--- a/Libraries/Components/Touchable/BoundingDimensions.js
+++ b/Libraries/Components/Touchable/BoundingDimensions.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -36,7 +37,7 @@ BoundingDimensions.prototype.destructor = function() {
 BoundingDimensions.getPooledFromElement = function(element) {
   return BoundingDimensions.getPooled(
     element.offsetWidth,
-    element.offsetHeight
+    element.offsetHeight,
   );
 };
 
diff --git a/Libraries/Components/Touchable/PooledClass.js b/Libraries/Components/Touchable/PooledClass.js
index 42cb503d07b7..a6934facae70 100644
--- a/Libraries/Components/Touchable/PooledClass.js
+++ b/Libraries/Components/Touchable/PooledClass.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/Libraries/Components/Touchable/Position.js b/Libraries/Components/Touchable/Position.js
index ce09d00a8e36..19899d74c498 100644
--- a/Libraries/Components/Touchable/Position.js
+++ b/Libraries/Components/Touchable/Position.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
diff --git a/Libraries/Components/Touchable/Touchable.js b/Libraries/Components/Touchable/Touchable.js
index 208315332716..ce449d6d99f8 100644
--- a/Libraries/Components/Touchable/Touchable.js
+++ b/Libraries/Components/Touchable/Touchable.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -110,14 +111,14 @@ const normalizeColor = require('normalizeColor');
  * Touchable states.
  */
 const States = keyMirror({
-  NOT_RESPONDER: null,                   // Not the responder
-  RESPONDER_INACTIVE_PRESS_IN: null,     // Responder, inactive, in the `PressRect`
-  RESPONDER_INACTIVE_PRESS_OUT: null,    // Responder, inactive, out of `PressRect`
-  RESPONDER_ACTIVE_PRESS_IN: null,       // Responder, active, in the `PressRect`
-  RESPONDER_ACTIVE_PRESS_OUT: null,      // Responder, active, out of `PressRect`
-  RESPONDER_ACTIVE_LONG_PRESS_IN: null,  // Responder, active, in the `PressRect`, after long press threshold
+  NOT_RESPONDER: null, // Not the responder
+  RESPONDER_INACTIVE_PRESS_IN: null, // Responder, inactive, in the `PressRect`
+  RESPONDER_INACTIVE_PRESS_OUT: null, // Responder, inactive, out of `PressRect`
+  RESPONDER_ACTIVE_PRESS_IN: null, // Responder, active, in the `PressRect`
+  RESPONDER_ACTIVE_PRESS_OUT: null, // Responder, active, out of `PressRect`
+  RESPONDER_ACTIVE_LONG_PRESS_IN: null, // Responder, active, in the `PressRect`, after long press threshold
   RESPONDER_ACTIVE_LONG_PRESS_OUT: null, // Responder, active, out of `PressRect`, after long press threshold
-  ERROR: null
+  ERROR: null,
 });
 
 /**
@@ -125,7 +126,7 @@ const States = keyMirror({
  */
 const IsActive = {
   RESPONDER_ACTIVE_PRESS_OUT: true,
-  RESPONDER_ACTIVE_PRESS_IN: true
+  RESPONDER_ACTIVE_PRESS_IN: true,
 };
 
 /**
@@ -230,7 +231,7 @@ const Transitions = {
     ENTER_PRESS_RECT: States.NOT_RESPONDER,
     LEAVE_PRESS_RECT: States.NOT_RESPONDER,
     LONG_PRESS_DETECTED: States.NOT_RESPONDER,
-  }
+  },
 };
 
 // ==== Typical Constants for integrating into UI components ====
@@ -324,11 +325,15 @@ const TouchableMixin = {
       evt.dispatchConfig = {};
       if (myTag === evt.tag) {
         if (evt.eventType === 'focus') {
-          cmp.touchableHandleActivePressIn && cmp.touchableHandleActivePressIn(evt);
+          cmp.touchableHandleActivePressIn &&
+            cmp.touchableHandleActivePressIn(evt);
         } else if (evt.eventType === 'blur') {
-          cmp.touchableHandleActivePressOut && cmp.touchableHandleActivePressOut(evt);
+          cmp.touchableHandleActivePressOut &&
+            cmp.touchableHandleActivePressOut(evt);
         } else if (evt.eventType === 'select') {
-          cmp.touchableHandlePress && !cmp.props.disabled && cmp.touchableHandlePress(evt);
+          cmp.touchableHandlePress &&
+            !cmp.props.disabled &&
+            cmp.touchableHandlePress(evt);
         }
       }
     });
@@ -356,7 +361,7 @@ const TouchableMixin = {
    */
   touchableGetInitialState: function() {
     return {
-      touchable: {touchState: undefined, responderID: null}
+      touchable: {touchState: undefined, responderID: null},
     };
   },
 
@@ -378,7 +383,7 @@ const TouchableMixin = {
   /**
    * Return true to cancel press on long press.
    */
-  touchableLongPressCancelsPress: function () {
+  touchableLongPressCancelsPress: function() {
     return true;
   },
 
@@ -401,25 +406,27 @@ const TouchableMixin = {
     this.state.touchable.responderID = dispatchID;
     this._receiveSignal(Signals.RESPONDER_GRANT, e);
     let delayMS =
-      this.touchableGetHighlightDelayMS !== undefined ?
-      Math.max(this.touchableGetHighlightDelayMS(), 0) : HIGHLIGHT_DELAY_MS;
+      this.touchableGetHighlightDelayMS !== undefined
+        ? Math.max(this.touchableGetHighlightDelayMS(), 0)
+        : HIGHLIGHT_DELAY_MS;
     delayMS = isNaN(delayMS) ? HIGHLIGHT_DELAY_MS : delayMS;
     if (delayMS !== 0) {
       this.touchableDelayTimeout = setTimeout(
         this._handleDelay.bind(this, e),
-        delayMS
+        delayMS,
       );
     } else {
       this._handleDelay(e);
     }
 
     let longDelayMS =
-      this.touchableGetLongPressDelayMS !== undefined ?
-      Math.max(this.touchableGetLongPressDelayMS(), 10) : LONG_PRESS_DELAY_MS;
+      this.touchableGetLongPressDelayMS !== undefined
+        ? Math.max(this.touchableGetLongPressDelayMS(), 10)
+        : LONG_PRESS_DELAY_MS;
     longDelayMS = isNaN(longDelayMS) ? LONG_PRESS_DELAY_MS : longDelayMS;
     this.longPressDelayTimeout = setTimeout(
       this._handleLongDelay.bind(this, e),
-      longDelayMS + delayMS
+      longDelayMS + delayMS,
     );
   },
 
@@ -443,7 +450,9 @@ const TouchableMixin = {
   touchableHandleResponderMove: function(e) {
     // Not enough time elapsed yet, wait for highlight -
     // this is just a perf optimization.
-    if (this.state.touchable.touchState === States.RESPONDER_INACTIVE_PRESS_IN) {
+    if (
+      this.state.touchable.touchState === States.RESPONDER_INACTIVE_PRESS_IN
+    ) {
       return;
     }
 
@@ -454,21 +463,23 @@ const TouchableMixin = {
 
     const positionOnActivate = this.state.touchable.positionOnActivate;
     const dimensionsOnActivate = this.state.touchable.dimensionsOnActivate;
-    const pressRectOffset = this.touchableGetPressRectOffset ?
-      this.touchableGetPressRectOffset() : {
-        left: PRESS_EXPAND_PX,
-        right: PRESS_EXPAND_PX,
-        top: PRESS_EXPAND_PX,
-        bottom: PRESS_EXPAND_PX
-      };
+    const pressRectOffset = this.touchableGetPressRectOffset
+      ? this.touchableGetPressRectOffset()
+      : {
+          left: PRESS_EXPAND_PX,
+          right: PRESS_EXPAND_PX,
+          top: PRESS_EXPAND_PX,
+          bottom: PRESS_EXPAND_PX,
+        };
 
     let pressExpandLeft = pressRectOffset.left;
     let pressExpandTop = pressRectOffset.top;
     let pressExpandRight = pressRectOffset.right;
     let pressExpandBottom = pressRectOffset.bottom;
 
-    const hitSlop = this.touchableGetHitSlop ?
-      this.touchableGetHitSlop() : null;
+    const hitSlop = this.touchableGetHitSlop
+      ? this.touchableGetHitSlop()
+      : null;
 
     if (hitSlop) {
       pressExpandLeft += hitSlop.left;
@@ -482,21 +493,26 @@ const TouchableMixin = {
     const pageY = touch && touch.pageY;
 
     if (this.pressInLocation) {
-      const movedDistance = this._getDistanceBetweenPoints(pageX, pageY, this.pressInLocation.pageX, this.pressInLocation.pageY);
+      const movedDistance = this._getDistanceBetweenPoints(
+        pageX,
+        pageY,
+        this.pressInLocation.pageX,
+        this.pressInLocation.pageY,
+      );
       if (movedDistance > LONG_PRESS_ALLOWED_MOVEMENT) {
         this._cancelLongPressDelayTimeout();
       }
     }
 
     const isTouchWithinActive =
-        pageX > positionOnActivate.left - pressExpandLeft &&
-        pageY > positionOnActivate.top - pressExpandTop &&
-        pageX <
-          positionOnActivate.left +
+      pageX > positionOnActivate.left - pressExpandLeft &&
+      pageY > positionOnActivate.top - pressExpandTop &&
+      pageX <
+        positionOnActivate.left +
           dimensionsOnActivate.width +
           pressExpandRight &&
-        pageY <
-          positionOnActivate.top +
+      pageY <
+        positionOnActivate.top +
           dimensionsOnActivate.height +
           pressExpandBottom;
     if (isTouchWithinActive) {
@@ -574,8 +590,6 @@ const TouchableMixin = {
    * touchableGetPressRectOffset: function
    */
 
-
-
   // ==== Internal Logic ====
 
   /**
@@ -608,8 +622,14 @@ const TouchableMixin = {
       Position.release(this.state.touchable.positionOnActivate);
     this.state.touchable.dimensionsOnActivate &&
       BoundingDimensions.release(this.state.touchable.dimensionsOnActivate);
-    this.state.touchable.positionOnActivate = Position.getPooled(globalX, globalY);
-    this.state.touchable.dimensionsOnActivate = BoundingDimensions.getPooled(w, h);
+    this.state.touchable.positionOnActivate = Position.getPooled(
+      globalX,
+      globalY,
+    );
+    this.state.touchable.dimensionsOnActivate = BoundingDimensions.getPooled(
+      w,
+      h,
+    );
   },
 
   _handleDelay: function(e) {
@@ -620,11 +640,18 @@ const TouchableMixin = {
   _handleLongDelay: function(e) {
     this.longPressDelayTimeout = null;
     const curState = this.state.touchable.touchState;
-    if (curState !== States.RESPONDER_ACTIVE_PRESS_IN &&
-        curState !== States.RESPONDER_ACTIVE_LONG_PRESS_IN) {
-      console.error('Attempted to transition from state `' + curState + '` to `' +
-        States.RESPONDER_ACTIVE_LONG_PRESS_IN + '`, which is not supported. This is ' +
-        'most likely due to `Touchable.longPressDelayTimeout` not being cancelled.');
+    if (
+      curState !== States.RESPONDER_ACTIVE_PRESS_IN &&
+      curState !== States.RESPONDER_ACTIVE_LONG_PRESS_IN
+    ) {
+      console.error(
+        'Attempted to transition from state `' +
+          curState +
+          '` to `' +
+          States.RESPONDER_ACTIVE_LONG_PRESS_IN +
+          '`, which is not supported. This is ' +
+          'most likely due to `Touchable.longPressDelayTimeout` not being cancelled.',
+      );
     } else {
       this._receiveSignal(Signals.LONG_PRESS_DETECTED, e);
     }
@@ -647,14 +674,24 @@ const TouchableMixin = {
     }
     if (!nextState) {
       throw new Error(
-        'Unrecognized signal `' + signal + '` or state `' + curState +
-        '` for Touchable responder `' + responderID + '`'
+        'Unrecognized signal `' +
+          signal +
+          '` or state `' +
+          curState +
+          '` for Touchable responder `' +
+          responderID +
+          '`',
       );
     }
     if (nextState === States.ERROR) {
       throw new Error(
-        'Touchable cannot transition from `' + curState + '` to `' + signal +
-        '` for responder `' + responderID + '`'
+        'Touchable cannot transition from `' +
+          curState +
+          '` to `' +
+          signal +
+          '` for responder `' +
+          responderID +
+          '`',
       );
     }
     if (curState !== nextState) {
@@ -663,14 +700,16 @@ const TouchableMixin = {
     }
   },
 
-  _cancelLongPressDelayTimeout: function () {
+  _cancelLongPressDelayTimeout: function() {
     this.longPressDelayTimeout && clearTimeout(this.longPressDelayTimeout);
     this.longPressDelayTimeout = null;
   },
 
-  _isHighlight: function (state) {
-    return state === States.RESPONDER_ACTIVE_PRESS_IN ||
-           state === States.RESPONDER_ACTIVE_LONG_PRESS_IN;
+  _isHighlight: function(state) {
+    return (
+      state === States.RESPONDER_ACTIVE_PRESS_IN ||
+      state === States.RESPONDER_ACTIVE_LONG_PRESS_IN
+    );
   },
 
   _savePressInLocation: function(e) {
@@ -682,7 +721,7 @@ const TouchableMixin = {
     this.pressInLocation = {pageX, pageY, locationX, locationY};
   },
 
-  _getDistanceBetweenPoints: function (aX, aY, bX, bY) {
+  _getDistanceBetweenPoints: function(aX, aY, bX, bY) {
     const deltaX = aX - bX;
     const deltaY = aY - bY;
     return Math.sqrt(deltaX * deltaX + deltaY * deltaY);
@@ -728,12 +767,11 @@ const TouchableMixin = {
     if (IsPressingIn[curState] && signal === Signals.RESPONDER_RELEASE) {
       const hasLongPressHandler = !!this.props.onLongPress;
       const pressIsLongButStillCallOnPress =
-        IsLongPressingIn[curState] && (    // We *are* long pressing..
-          (// But either has no long handler
-          !hasLongPressHandler || !this.touchableLongPressCancelsPress()) // or we're told to ignore it.
-        );
+        IsLongPressingIn[curState] && // We *are* long pressing.. // But either has no long handler
+        (!hasLongPressHandler || !this.touchableLongPressCancelsPress()); // or we're told to ignore it.
 
-      const shouldInvokePress =  !IsLongPressingIn[curState] || pressIsLongButStillCallOnPress;
+      const shouldInvokePress =
+        !IsLongPressingIn[curState] || pressIsLongButStillCallOnPress;
       if (shouldInvokePress && this.touchableHandlePress) {
         if (!newIsHighlight && !curIsHighlight) {
           // we never highlighted because of delay, but we should highlight now
@@ -750,11 +788,11 @@ const TouchableMixin = {
     this.touchableDelayTimeout && clearTimeout(this.touchableDelayTimeout);
     this.touchableDelayTimeout = null;
   },
-  
+
   _playTouchSound: function() {
     UIManager.playTouchSound();
   },
-  
+
   _startHighlight: function(e) {
     this._savePressInLocation(e);
     this.touchableHandleActivePressIn && this.touchableHandleActivePressIn(e);
@@ -762,7 +800,10 @@ const TouchableMixin = {
 
   _endHighlight: function(e) {
     if (this.touchableHandleActivePressOut) {
-      if (this.touchableGetPressOutDelayMS && this.touchableGetPressOutDelayMS()) {
+      if (
+        this.touchableGetPressOutDelayMS &&
+        this.touchableGetPressOutDelayMS()
+      ) {
         this.pressOutDelayTimeout = setTimeout(() => {
           this.touchableHandleActivePressOut(e);
         }, this.touchableGetPressOutDelayMS());
@@ -771,7 +812,6 @@ const TouchableMixin = {
       }
     }
   },
-
 };
 
 const Touchable = {
@@ -785,14 +825,17 @@ const Touchable = {
       return null;
     }
     if (!__DEV__) {
-      throw Error('Touchable.TOUCH_TARGET_DEBUG should not be enabled in prod!');
+      throw Error(
+        'Touchable.TOUCH_TARGET_DEBUG should not be enabled in prod!',
+      );
     }
     const debugHitSlopStyle = {};
     hitSlop = hitSlop || {top: 0, bottom: 0, left: 0, right: 0};
     for (const key in hitSlop) {
       debugHitSlopStyle[key] = -hitSlop[key];
     }
-    const hexColor = '#' + ('00000000' + normalizeColor(color).toString(16)).substr(-8);
+    const hexColor =
+      '#' + ('00000000' + normalizeColor(color).toString(16)).substr(-8);
     return (
       <View
         pointerEvents="none"
@@ -802,11 +845,11 @@ const Touchable = {
           borderWidth: 1,
           borderStyle: 'dashed',
           backgroundColor: hexColor.slice(0, -2) + '0F', // Less opaque
-          ...debugHitSlopStyle
+          ...debugHitSlopStyle,
         }}
       />
     );
-  }
+  },
 };
 
 module.exports = Touchable;
diff --git a/Libraries/Components/Touchable/TouchableNativeFeedback.android.js b/Libraries/Components/Touchable/TouchableNativeFeedback.android.js
index 00f67818bf45..f727d5d8a2b6 100644
--- a/Libraries/Components/Touchable/TouchableNativeFeedback.android.js
+++ b/Libraries/Components/Touchable/TouchableNativeFeedback.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const Platform = require('Platform');
@@ -112,7 +114,10 @@ const TouchableNativeFeedback = createReactClass({
      * Available on android API level 21+.
      */
     SelectableBackgroundBorderless: function() {
-      return {type: 'ThemeAttrAndroid', attribute: 'selectableItemBackgroundBorderless'};
+      return {
+        type: 'ThemeAttrAndroid',
+        attribute: 'selectableItemBackgroundBorderless',
+      };
     },
     /**
      * Creates an object that represents ripple drawable with specified color (as a
@@ -125,12 +130,16 @@ const TouchableNativeFeedback = createReactClass({
      * @param borderless If the ripple can render outside it's bounds
      */
     Ripple: function(color: string, borderless: boolean) {
-      return {type: 'RippleAndroid', color: processColor(color), borderless: borderless};
+      return {
+        type: 'RippleAndroid',
+        color: processColor(color),
+        borderless: borderless,
+      };
     },
 
     canUseNativeForeground: function() {
       return Platform.OS === 'android' && Platform.Version >= 23;
-    }
+    },
   },
 
   mixins: [Touchable.Mixin],
@@ -161,7 +170,10 @@ const TouchableNativeFeedback = createReactClass({
     this.props.onPressIn && this.props.onPressIn(e);
     this._dispatchPressedStateChange(true);
     if (this.pressInLocation) {
-      this._dispatchHotspotUpdate(this.pressInLocation.locationX, this.pressInLocation.locationY);
+      this._dispatchHotspotUpdate(
+        this.pressInLocation.locationX,
+        this.pressInLocation.locationY,
+      );
     }
   },
 
@@ -201,14 +213,17 @@ const TouchableNativeFeedback = createReactClass({
 
   _handleResponderMove: function(e) {
     this.touchableHandleResponderMove(e);
-    this._dispatchHotspotUpdate(e.nativeEvent.locationX, e.nativeEvent.locationY);
+    this._dispatchHotspotUpdate(
+      e.nativeEvent.locationX,
+      e.nativeEvent.locationY,
+    );
   },
 
   _dispatchHotspotUpdate: function(destX, destY) {
     UIManager.dispatchViewManagerCommand(
       ReactNative.findNodeHandle(this),
       UIManager.RCTView.Commands.hotspotUpdate,
-      [destX || 0, destY || 0]
+      [destX || 0, destY || 0],
     );
   },
 
@@ -216,7 +231,7 @@ const TouchableNativeFeedback = createReactClass({
     UIManager.dispatchViewManagerCommand(
       ReactNative.findNodeHandle(this),
       UIManager.RCTView.Commands.setPressed,
-      [pressed]
+      [pressed],
     );
   },
 
@@ -227,16 +242,26 @@ const TouchableNativeFeedback = createReactClass({
       if (!Array.isArray(children)) {
         children = [children];
       }
-      children.push(Touchable.renderDebugView({color: 'brown', hitSlop: this.props.hitSlop}));
+      children.push(
+        Touchable.renderDebugView({
+          color: 'brown',
+          hitSlop: this.props.hitSlop,
+        }),
+      );
     }
-    if (this.props.useForeground && !TouchableNativeFeedback.canUseNativeForeground()) {
+    if (
+      this.props.useForeground &&
+      !TouchableNativeFeedback.canUseNativeForeground()
+    ) {
       console.warn(
         'Requested foreground ripple, but it is not available on this version of Android. ' +
-        'Consider calling TouchableNativeFeedback.canUseNativeForeground() and using a different ' +
-        'Touchable if the result is false.');
+          'Consider calling TouchableNativeFeedback.canUseNativeForeground() and using a different ' +
+          'Touchable if the result is false.',
+      );
     }
     const drawableProp =
-      this.props.useForeground && TouchableNativeFeedback.canUseNativeForeground()
+      this.props.useForeground &&
+      TouchableNativeFeedback.canUseNativeForeground()
         ? 'nativeForegroundAndroid'
         : 'nativeBackgroundAndroid';
     const childProps = {
@@ -253,7 +278,8 @@ const TouchableNativeFeedback = createReactClass({
       isTVSelectable: true,
       hasTVPreferredFocus: this.props.hasTVPreferredFocus,
       onStartShouldSetResponder: this.touchableHandleStartShouldSetResponder,
-      onResponderTerminationRequest: this.touchableHandleResponderTerminationRequest,
+      onResponderTerminationRequest: this
+        .touchableHandleResponderTerminationRequest,
       onResponderGrant: this.touchableHandleResponderGrant,
       onResponderMove: this._handleResponderMove,
       onResponderRelease: this.touchableHandleResponderRelease,
@@ -263,11 +289,8 @@ const TouchableNativeFeedback = createReactClass({
     // We need to clone the actual element so that the ripple background drawable
     // can be applied directly to the background of this element rather than to
     // a wrapper view as done in other Touchable*
-    return React.cloneElement(
-      child,
-      childProps
-    );
-  }
+    return React.cloneElement(child, childProps);
+  },
 });
 
 module.exports = TouchableNativeFeedback;
diff --git a/Libraries/Components/Touchable/TouchableNativeFeedback.ios.js b/Libraries/Components/Touchable/TouchableNativeFeedback.ios.js
index 8c195b9549bd..b0770047bbee 100644
--- a/Libraries/Components/Touchable/TouchableNativeFeedback.ios.js
+++ b/Libraries/Components/Touchable/TouchableNativeFeedback.ios.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -22,7 +23,9 @@ class DummyTouchableNativeFeedback extends React.Component {
   render() {
     return (
       <View style={[styles.container, this.props.style]}>
-        <Text style={styles.info}>TouchableNativeFeedback is not supported on this platform!</Text>
+        <Text style={styles.info}>
+          TouchableNativeFeedback is not supported on this platform!
+        </Text>
       </View>
     );
   }
@@ -42,7 +45,7 @@ const styles = StyleSheet.create({
   info: {
     color: '#333333',
     margin: 20,
-  }
+  },
 });
 
 module.exports = DummyTouchableNativeFeedback;
diff --git a/Libraries/Components/Touchable/TouchableOpacity.js b/Libraries/Components/Touchable/TouchableOpacity.js
index 4ae20db8fb28..afb01b079af9 100644
--- a/Libraries/Components/Touchable/TouchableOpacity.js
+++ b/Libraries/Components/Touchable/TouchableOpacity.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @noflow
  */
+
 'use strict';
 
 // Note (avik): add @flow when Flow supports spread properties in propTypes
@@ -167,15 +169,12 @@ const TouchableOpacity = createReactClass({
    * Animate the touchable to a new opacity.
    */
   setOpacityTo: function(value: number, duration: number) {
-    Animated.timing(
-      this.state.anim,
-      {
-        toValue: value,
-        duration: duration,
-        easing: Easing.inOut(Easing.quad),
-        useNativeDriver: true,
-      }
-    ).start();
+    Animated.timing(this.state.anim, {
+      toValue: value,
+      duration: duration,
+      easing: Easing.inOut(Easing.quad),
+      useNativeDriver: true,
+    }).start();
   },
 
   /**
@@ -217,8 +216,9 @@ const TouchableOpacity = createReactClass({
   },
 
   touchableGetLongPressDelayMS: function() {
-    return this.props.delayLongPress === 0 ? 0 :
-      this.props.delayLongPress || 500;
+    return this.props.delayLongPress === 0
+      ? 0
+      : this.props.delayLongPress || 500;
   },
 
   touchableGetPressOutDelayMS: function() {
@@ -230,16 +230,13 @@ const TouchableOpacity = createReactClass({
   },
 
   _opacityInactive: function(duration: number) {
-    this.setOpacityTo(
-      this._getChildStyleOpacityWithDefault(),
-      duration
-    );
+    this.setOpacityTo(this._getChildStyleOpacityWithDefault(), duration);
   },
 
   _getChildStyleOpacityWithDefault: function() {
-   const childStyle = flattenStyle(this.props.style) || {};
-   return childStyle.opacity == undefined ? 1 : childStyle.opacity;
- },
+    const childStyle = flattenStyle(this.props.style) || {};
+    return childStyle.opacity == undefined ? 1 : childStyle.opacity;
+  },
 
   render: function() {
     return (
@@ -257,13 +254,18 @@ const TouchableOpacity = createReactClass({
         tvParallaxProperties={this.props.tvParallaxProperties}
         hitSlop={this.props.hitSlop}
         onStartShouldSetResponder={this.touchableHandleStartShouldSetResponder}
-        onResponderTerminationRequest={this.touchableHandleResponderTerminationRequest}
+        onResponderTerminationRequest={
+          this.touchableHandleResponderTerminationRequest
+        }
         onResponderGrant={this.touchableHandleResponderGrant}
         onResponderMove={this.touchableHandleResponderMove}
         onResponderRelease={this.touchableHandleResponderRelease}
         onResponderTerminate={this.touchableHandleResponderTerminate}>
         {this.props.children}
-        {Touchable.renderDebugView({color: 'cyan', hitSlop: this.props.hitSlop})}
+        {Touchable.renderDebugView({
+          color: 'cyan',
+          hitSlop: this.props.hitSlop,
+        })}
       </Animated.View>
     );
   },
diff --git a/Libraries/Components/Touchable/TouchableWithoutFeedback.js b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
index d59d04cf4e6c..2c6530733aa5 100755
--- a/Libraries/Components/Touchable/TouchableWithoutFeedback.js
+++ b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EdgeInsetsPropType = require('EdgeInsetsPropType');
@@ -46,9 +48,7 @@ const TouchableWithoutFeedback = createReactClass({
 
   propTypes: {
     accessible: PropTypes.bool,
-    accessibilityComponentType: PropTypes.oneOf(
-      AccessibilityComponentTypes
-    ),
+    accessibilityComponentType: PropTypes.oneOf(AccessibilityComponentTypes),
     accessibilityTraits: PropTypes.oneOfType([
       PropTypes.oneOf(AccessibilityTraits),
       PropTypes.arrayOf(PropTypes.oneOf(AccessibilityTraits)),
@@ -63,14 +63,14 @@ const TouchableWithoutFeedback = createReactClass({
      */
     onPress: PropTypes.func,
     /**
-    * Called as soon as the touchable element is pressed and invoked even before onPress.
-    * This can be useful when making network requests.
-    */
+     * Called as soon as the touchable element is pressed and invoked even before onPress.
+     * This can be useful when making network requests.
+     */
     onPressIn: PropTypes.func,
     /**
-    * Called as soon as the touch is released even before onPress.
-    */
-     onPressOut: PropTypes.func,
+     * Called as soon as the touch is released even before onPress.
+     */
+    onPressOut: PropTypes.func,
     /**
      * Invoked on mount and layout changes with
      *
@@ -156,8 +156,9 @@ const TouchableWithoutFeedback = createReactClass({
   },
 
   touchableGetLongPressDelayMS: function(): number {
-    return this.props.delayLongPress === 0 ? 0 :
-      this.props.delayLongPress || 500;
+    return this.props.delayLongPress === 0
+      ? 0
+      : this.props.delayLongPress || 500;
   },
 
   touchableGetPressOutDelayMS: function(): number {
@@ -172,15 +173,25 @@ const TouchableWithoutFeedback = createReactClass({
     warning(
       !child.type || child.type.displayName !== 'Text',
       'TouchableWithoutFeedback does not work well with Text children. Wrap children in a View instead. See ' +
-        ((child._owner && child._owner.getName && child._owner.getName()) || '<unknown>')
+        ((child._owner && child._owner.getName && child._owner.getName()) ||
+          '<unknown>'),
     );
-    if (Touchable.TOUCH_TARGET_DEBUG && child.type && child.type.displayName === 'View') {
+    if (
+      Touchable.TOUCH_TARGET_DEBUG &&
+      child.type &&
+      child.type.displayName === 'View'
+    ) {
       children = React.Children.toArray(children);
-      children.push(Touchable.renderDebugView({color: 'red', hitSlop: this.props.hitSlop}));
+      children.push(
+        Touchable.renderDebugView({color: 'red', hitSlop: this.props.hitSlop}),
+      );
     }
-    const style = (Touchable.TOUCH_TARGET_DEBUG && child.type && child.type.displayName === 'Text') ?
-      [child.props.style, {color: 'red'}] :
-      child.props.style;
+    const style =
+      Touchable.TOUCH_TARGET_DEBUG &&
+      child.type &&
+      child.type.displayName === 'Text'
+        ? [child.props.style, {color: 'red'}]
+        : child.props.style;
     return (React: any).cloneElement(child, {
       accessible: this.props.accessible !== false,
       accessibilityLabel: this.props.accessibilityLabel,
@@ -191,7 +202,8 @@ const TouchableWithoutFeedback = createReactClass({
       onLayout: this.props.onLayout,
       hitSlop: this.props.hitSlop,
       onStartShouldSetResponder: this.touchableHandleStartShouldSetResponder,
-      onResponderTerminationRequest: this.touchableHandleResponderTerminationRequest,
+      onResponderTerminationRequest: this
+        .touchableHandleResponderTerminationRequest,
       onResponderGrant: this.touchableHandleResponderGrant,
       onResponderMove: this.touchableHandleResponderMove,
       onResponderRelease: this.touchableHandleResponderRelease,
@@ -199,7 +211,7 @@ const TouchableWithoutFeedback = createReactClass({
       style,
       children,
     });
-  }
+  },
 });
 
 module.exports = TouchableWithoutFeedback;
diff --git a/Libraries/Components/Touchable/__mocks__/ensureComponentIsNative.js b/Libraries/Components/Touchable/__mocks__/ensureComponentIsNative.js
index 8f036c71e8cd..f152b68bba74 100644
--- a/Libraries/Components/Touchable/__mocks__/ensureComponentIsNative.js
+++ b/Libraries/Components/Touchable/__mocks__/ensureComponentIsNative.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 module.exports = () => true;
diff --git a/Libraries/Components/Touchable/__tests__/TouchableHighlight-test.js b/Libraries/Components/Touchable/__tests__/TouchableHighlight-test.js
index 396b7387b218..f40cc0b7ad1b 100644
--- a/Libraries/Components/Touchable/__tests__/TouchableHighlight-test.js
+++ b/Libraries/Components/Touchable/__tests__/TouchableHighlight-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const React = require('React');
@@ -18,7 +20,7 @@ describe('TouchableHighlight', () => {
     const instance = ReactTestRenderer.create(
       <TouchableHighlight style={{}}>
         <Text>Touchable</Text>
-      </TouchableHighlight>
+      </TouchableHighlight>,
     );
 
     expect(instance.toJSON()).toMatchSnapshot();
diff --git a/Libraries/Components/Touchable/ensureComponentIsNative.js b/Libraries/Components/Touchable/ensureComponentIsNative.js
index 9b82aeb45ec6..5ce5a39d9baa 100644
--- a/Libraries/Components/Touchable/ensureComponentIsNative.js
+++ b/Libraries/Components/Touchable/ensureComponentIsNative.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const invariant = require('fbjs/lib/invariant');
@@ -14,7 +16,7 @@ const ensureComponentIsNative = function(component: any) {
   invariant(
     component && typeof component.setNativeProps === 'function',
     'Touchable child must either be native or forward setNativeProps to a ' +
-    'native component'
+      'native component',
   );
 };
 
diff --git a/Libraries/Components/Touchable/ensurePositiveDelayProps.js b/Libraries/Components/Touchable/ensurePositiveDelayProps.js
index 9d0be5ccdc5e..01c001ad4b6a 100644
--- a/Libraries/Components/Touchable/ensurePositiveDelayProps.js
+++ b/Libraries/Components/Touchable/ensurePositiveDelayProps.js
@@ -4,17 +4,22 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const invariant = require('fbjs/lib/invariant');
 
 const ensurePositiveDelayProps = function(props: any) {
   invariant(
-    !(props.delayPressIn < 0 || props.delayPressOut < 0 ||
-      props.delayLongPress < 0),
-    'Touchable components cannot have negative delay properties'
+    !(
+      props.delayPressIn < 0 ||
+      props.delayPressOut < 0 ||
+      props.delayLongPress < 0
+    ),
+    'Touchable components cannot have negative delay properties',
   );
 };
 
diff --git a/Libraries/Components/View/PlatformViewPropTypes.js b/Libraries/Components/View/PlatformViewPropTypes.js
index 70ab6694192f..4c6105893cc6 100644
--- a/Libraries/Components/View/PlatformViewPropTypes.js
+++ b/Libraries/Components/View/PlatformViewPropTypes.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/Libraries/Components/View/ReactNativeStyleAttributes.js b/Libraries/Components/View/ReactNativeStyleAttributes.js
index 7c8422413579..7a75dda8b7f4 100644
--- a/Libraries/Components/View/ReactNativeStyleAttributes.js
+++ b/Libraries/Components/View/ReactNativeStyleAttributes.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -27,10 +28,10 @@ const ReactNativeStyleAttributes = {
   ...keyMirror(ImageStylePropTypes),
 };
 
-ReactNativeStyleAttributes.transform = { process: processTransform };
-ReactNativeStyleAttributes.shadowOffset = { diff: sizesDiffer };
+ReactNativeStyleAttributes.transform = {process: processTransform};
+ReactNativeStyleAttributes.shadowOffset = {diff: sizesDiffer};
 
-const colorAttributes = { process: processColor };
+const colorAttributes = {process: processColor};
 ReactNativeStyleAttributes.backgroundColor = colorAttributes;
 ReactNativeStyleAttributes.borderBottomColor = colorAttributes;
 ReactNativeStyleAttributes.borderColor = colorAttributes;
diff --git a/Libraries/Components/View/ReactNativeViewAttributes.js b/Libraries/Components/View/ReactNativeViewAttributes.js
index f18b70281935..7bf8117710ef 100644
--- a/Libraries/Components/View/ReactNativeViewAttributes.js
+++ b/Libraries/Components/View/ReactNativeViewAttributes.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index edab2a569511..c5e44e289d08 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -4,34 +4,36 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 export type AccessibilityTrait =
-  'none' |
-  'button' |
-  'link' |
-  'header' |
-  'search' |
-  'image' |
-  'selected' |
-  'plays' |
-  'key' |
-  'text' |
-  'summary' |
-  'disabled' |
-  'frequentUpdates' |
-  'startsMedia' |
-  'adjustable' |
-  'allowsDirectInteraction' |
-  'pageTurn';
+  | 'none'
+  | 'button'
+  | 'link'
+  | 'header'
+  | 'search'
+  | 'image'
+  | 'selected'
+  | 'plays'
+  | 'key'
+  | 'text'
+  | 'summary'
+  | 'disabled'
+  | 'frequentUpdates'
+  | 'startsMedia'
+  | 'adjustable'
+  | 'allowsDirectInteraction'
+  | 'pageTurn';
 
 export type AccessibilityComponentType =
-  'none' |
-  'button' |
-  'radiobutton_checked' |
-  'radiobutton_unchecked';
+  | 'none'
+  | 'button'
+  | 'radiobutton_checked'
+  | 'radiobutton_unchecked';
 
 module.exports = {
   AccessibilityTraits: [
diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 332059ab0a22..946368f267de 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -36,15 +38,20 @@ export type ViewLayoutEvent = LayoutEvent;
 // There's no easy way to create a different type if (Platform.isTVOS):
 // so we must include TVViewProps
 export type ViewProps = {
-  accessible?: bool,
-  accessibilityLabel?: null | React$PropType$Primitive<any> | string | Array<any> | any,
+  accessible?: boolean,
+  accessibilityLabel?:
+    | null
+    | React$PropType$Primitive<any>
+    | string
+    | Array<any>
+    | any,
   accessibilityActions?: Array<string>,
   accessibilityComponentType?: AccessibilityComponentType,
   accessibilityLiveRegion?: 'none' | 'polite' | 'assertive',
-  importantForAccessibility?: 'auto'| 'yes'| 'no'| 'no-hide-descendants',
+  importantForAccessibility?: 'auto' | 'yes' | 'no' | 'no-hide-descendants',
   accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
-  accessibilityViewIsModal?: bool,
-  accessibilityElementsHidden?: bool,
+  accessibilityViewIsModal?: boolean,
+  accessibilityElementsHidden?: boolean,
   children?: ?React.Node,
   onAccessibilityAction?: Function,
   onAccessibilityTap?: Function,
@@ -63,13 +70,13 @@ export type ViewProps = {
   onMoveShouldSetResponder?: ?Function,
   onMoveShouldSetResponderCapture?: ?Function,
   hitSlop?: ?EdgeInsetsProp,
-  pointerEvents?: null | 'box-none'| 'none'| 'box-only'| 'auto',
+  pointerEvents?: null | 'box-none' | 'none' | 'box-only' | 'auto',
   style?: stylePropType,
-  removeClippedSubviews?: bool,
-  renderToHardwareTextureAndroid?: bool,
-  shouldRasterizeIOS?: bool,
-  collapsable?: bool,
-  needsOffscreenAlphaCompositing?: bool,
+  removeClippedSubviews?: boolean,
+  renderToHardwareTextureAndroid?: boolean,
+  shouldRasterizeIOS?: boolean,
+  collapsable?: boolean,
+  needsOffscreenAlphaCompositing?: boolean,
 } & TVViewProps;
 
 module.exports = {
@@ -115,11 +122,7 @@ module.exports = {
    *
    * See http://facebook.github.io/react-native/docs/view.html#accessibilityliveregion
    */
-  accessibilityLiveRegion: PropTypes.oneOf([
-    'none',
-    'polite',
-    'assertive',
-  ]),
+  accessibilityLiveRegion: PropTypes.oneOf(['none', 'polite', 'assertive']),
 
   /**
    * Controls how view is important for accessibility which is if it
@@ -361,12 +364,7 @@ module.exports = {
    *
    * See http://facebook.github.io/react-native/docs/view.html#pointerevents
    */
-  pointerEvents: PropTypes.oneOf([
-    'box-none',
-    'none',
-    'box-only',
-    'auto',
-  ]),
+  pointerEvents: PropTypes.oneOf(['box-none', 'none', 'box-only', 'auto']),
 
   /**
    * See http://facebook.github.io/react-native/docs/style.html
diff --git a/Libraries/Components/View/ViewStylePropTypes.js b/Libraries/Components/View/ViewStylePropTypes.js
index e252cf5d2c78..8f690fb32f68 100644
--- a/Libraries/Components/View/ViewStylePropTypes.js
+++ b/Libraries/Components/View/ViewStylePropTypes.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
diff --git a/Libraries/Components/ViewPager/ViewPagerAndroid.android.js b/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
index 19421ccc6436..4b75cfb42d52 100644
--- a/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
+++ b/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -132,16 +134,16 @@ class ViewPagerAndroid extends React.Component<{
     ]),
 
     /**
-    * When false, the content does not scroll.
-    * The default value is true.
-    */
+     * When false, the content does not scroll.
+     * The default value is true.
+     */
     scrollEnabled: PropTypes.bool,
 
     /**
      * Whether enable showing peekFraction or not. If this is true, the preview of
      * last and next page will show in current screen. Defaults to false.
      */
-     peekEnabled: PropTypes.bool,
+    peekEnabled: PropTypes.bool,
   };
 
   componentDidMount() {
@@ -164,22 +166,30 @@ class ViewPagerAndroid extends React.Component<{
       }
       const newProps = {
         ...child.props,
-        style: [child.props.style, {
-          position: 'absolute',
-          left: 0,
-          top: 0,
-          right: 0,
-          bottom: 0,
-          width: undefined,
-          height: undefined,
-        }],
+        style: [
+          child.props.style,
+          {
+            position: 'absolute',
+            left: 0,
+            top: 0,
+            right: 0,
+            bottom: 0,
+            width: undefined,
+            height: undefined,
+          },
+        ],
         collapsable: false,
       };
-      if (child.type &&
-          child.type.displayName &&
-          (child.type.displayName !== 'RCTView') &&
-          (child.type.displayName !== 'View')) {
-        console.warn('Each ViewPager child must be a <View>. Was ' + child.type.displayName);
+      if (
+        child.type &&
+        child.type.displayName &&
+        child.type.displayName !== 'RCTView' &&
+        child.type.displayName !== 'View'
+      ) {
+        console.warn(
+          'Each ViewPager child must be a <View>. Was ' +
+            child.type.displayName,
+        );
       }
       return React.createElement(child.type, newProps);
     });
@@ -245,6 +255,9 @@ class ViewPagerAndroid extends React.Component<{
   }
 }
 
-const NativeAndroidViewPager = requireNativeComponent('AndroidViewPager', ViewPagerAndroid);
+const NativeAndroidViewPager = requireNativeComponent(
+  'AndroidViewPager',
+  ViewPagerAndroid,
+);
 
 module.exports = ViewPagerAndroid;
diff --git a/Libraries/Components/ViewPager/ViewPagerAndroid.ios.js b/Libraries/Components/ViewPager/ViewPagerAndroid.ios.js
index ebd42dd5b18b..260d55992979 100644
--- a/Libraries/Components/ViewPager/ViewPagerAndroid.ios.js
+++ b/Libraries/Components/ViewPager/ViewPagerAndroid.ios.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/Components/WebView/WebView.android.js b/Libraries/Components/WebView/WebView.android.js
index b6995458e590..afc69bfcb912 100644
--- a/Libraries/Components/WebView/WebView.android.js
+++ b/Libraries/Components/WebView/WebView.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const EdgeInsetsPropType = require('EdgeInsetsPropType');
@@ -33,9 +35,7 @@ const WebViewState = keyMirror({
 
 const defaultRenderLoading = () => (
   <View style={styles.loadingView}>
-    <ActivityIndicator
-      style={styles.loadingProgressBar}
-    />
+    <ActivityIndicator style={styles.loadingProgressBar} />
   </View>
 );
 
@@ -69,13 +69,10 @@ class WebView extends React.Component {
 
     html: deprecatedPropType(
       PropTypes.string,
-      'Use the `source` prop instead.'
+      'Use the `source` prop instead.',
     ),
 
-    url: deprecatedPropType(
-      PropTypes.string,
-      'Use the `source` prop instead.'
-    ),
+    url: deprecatedPropType(PropTypes.string, 'Use the `source` prop instead.'),
 
     /**
      * Loads static html or a uri (with optional headers) in the WebView.
@@ -205,11 +202,7 @@ class WebView extends React.Component {
      * - `'compatibility'` -  WebView will attempt to be compatible with the approach of a modern web browser with regard to mixed content.
      * @platform android
      */
-    mixedContentMode: PropTypes.oneOf([
-      'never',
-      'always',
-      'compatibility'
-    ]),
+    mixedContentMode: PropTypes.oneOf(['never', 'always', 'compatibility']),
 
     /**
      * Used on Android only, controls whether form autocomplete data should be saved
@@ -248,7 +241,7 @@ class WebView extends React.Component {
   };
 
   static defaultProps = {
-    javaScriptEnabled : true,
+    javaScriptEnabled: true,
     thirdPartyCookiesEnabled: true,
     scalesPageToFit: true,
     saveFormDataDisabled: false,
@@ -270,21 +263,28 @@ class WebView extends React.Component {
   render() {
     let otherView = null;
 
-   if (this.state.viewState === WebViewState.LOADING) {
+    if (this.state.viewState === WebViewState.LOADING) {
       otherView = (this.props.renderLoading || defaultRenderLoading)();
     } else if (this.state.viewState === WebViewState.ERROR) {
       const errorEvent = this.state.lastErrorEvent;
-      otherView = this.props.renderError && this.props.renderError(
-        errorEvent.domain,
-        errorEvent.code,
-        errorEvent.description);
+      otherView =
+        this.props.renderError &&
+        this.props.renderError(
+          errorEvent.domain,
+          errorEvent.code,
+          errorEvent.description,
+        );
     } else if (this.state.viewState !== WebViewState.IDLE) {
-      console.error('RCTWebView invalid state encountered: ' + this.state.loading);
+      console.error(
+        'RCTWebView invalid state encountered: ' + this.state.loading,
+      );
     }
 
     const webViewStyles = [styles.container, this.props.style];
-    if (this.state.viewState === WebViewState.LOADING ||
-      this.state.viewState === WebViewState.ERROR) {
+    if (
+      this.state.viewState === WebViewState.LOADING ||
+      this.state.viewState === WebViewState.ERROR
+    ) {
       // if we're in either LOADING or ERROR states, don't show the webView
       webViewStyles.push(styles.hidden);
     }
@@ -297,18 +297,22 @@ class WebView extends React.Component {
     }
 
     if (source.method === 'POST' && source.headers) {
-      console.warn('WebView: `source.headers` is not supported when using POST.');
+      console.warn(
+        'WebView: `source.headers` is not supported when using POST.',
+      );
     } else if (source.method === 'GET' && source.body) {
       console.warn('WebView: `source.body` is not supported when using GET.');
     }
 
     const nativeConfig = this.props.nativeConfig || {};
 
-    const originWhitelist = (this.props.originWhitelist || []).map(WebViewShared.originWhitelistToRegex);
+    const originWhitelist = (this.props.originWhitelist || []).map(
+      WebViewShared.originWhitelistToRegex,
+    );
 
     let NativeWebView = nativeConfig.component || RCTWebView;
 
-    const webView =
+    const webView = (
       <NativeWebView
         ref={RCT_WEBVIEW_REF}
         key="webViewKey"
@@ -323,21 +327,28 @@ class WebView extends React.Component {
         messagingEnabled={typeof this.props.onMessage === 'function'}
         onMessage={this.onMessage}
         contentInset={this.props.contentInset}
-        automaticallyAdjustContentInsets={this.props.automaticallyAdjustContentInsets}
+        automaticallyAdjustContentInsets={
+          this.props.automaticallyAdjustContentInsets
+        }
         onContentSizeChange={this.props.onContentSizeChange}
         onLoadingStart={this.onLoadingStart}
         onLoadingFinish={this.onLoadingFinish}
         onLoadingError={this.onLoadingError}
         testID={this.props.testID}
         geolocationEnabled={this.props.geolocationEnabled}
-        mediaPlaybackRequiresUserAction={this.props.mediaPlaybackRequiresUserAction}
-        allowUniversalAccessFromFileURLs={this.props.allowUniversalAccessFromFileURLs}
+        mediaPlaybackRequiresUserAction={
+          this.props.mediaPlaybackRequiresUserAction
+        }
+        allowUniversalAccessFromFileURLs={
+          this.props.allowUniversalAccessFromFileURLs
+        }
         originWhitelist={originWhitelist}
         mixedContentMode={this.props.mixedContentMode}
         saveFormDataDisabled={this.props.saveFormDataDisabled}
         urlPrefixesForDefaultIntent={this.props.urlPrefixesForDefaultIntent}
         {...nativeConfig.props}
-      />;
+      />
+    );
 
     return (
       <View style={styles.container}>
@@ -351,7 +362,7 @@ class WebView extends React.Component {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.goForward,
-      null
+      null,
     );
   };
 
@@ -359,18 +370,18 @@ class WebView extends React.Component {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.goBack,
-      null
+      null,
     );
   };
 
   reload = () => {
     this.setState({
-      viewState: WebViewState.LOADING
+      viewState: WebViewState.LOADING,
     });
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.reload,
-      null
+      null,
     );
   };
 
@@ -378,29 +389,29 @@ class WebView extends React.Component {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.stopLoading,
-      null
+      null,
     );
   };
 
-  postMessage = (data) => {
+  postMessage = data => {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.postMessage,
-      [String(data)]
+      [String(data)],
     );
   };
 
   /**
-  * Injects a javascript string into the referenced WebView. Deliberately does not
-  * return a response because using eval() to return a response breaks this method
-  * on pages with a Content Security Policy that disallows eval(). If you need that
-  * functionality, look into postMessage/onMessage.
-  */
-  injectJavaScript = (data) => {
+   * Injects a javascript string into the referenced WebView. Deliberately does not
+   * return a response because using eval() to return a response breaks this method
+   * on pages with a Content Security Policy that disallows eval(). If you need that
+   * functionality, look into postMessage/onMessage.
+   */
+  injectJavaScript = data => {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.injectJavaScript,
-      [data]
+      [data],
     );
   };
 
@@ -408,7 +419,7 @@ class WebView extends React.Component {
    * We return an event with a bunch of fields including:
    *  url, title, loading, canGoBack, canGoForward
    */
-  updateNavigationState = (event) => {
+  updateNavigationState = event => {
     if (this.props.onNavigationStateChange) {
       this.props.onNavigationStateChange(event.nativeEvent);
     }
@@ -418,13 +429,13 @@ class WebView extends React.Component {
     return ReactNative.findNodeHandle(this.refs[RCT_WEBVIEW_REF]);
   };
 
-  onLoadingStart = (event) => {
+  onLoadingStart = event => {
     const onLoadStart = this.props.onLoadStart;
     onLoadStart && onLoadStart(event);
     this.updateNavigationState(event);
   };
 
-  onLoadingError = (event) => {
+  onLoadingError = event => {
     event.persist(); // persist this event because we need to store it
     const {onError, onLoadEnd} = this.props;
     onError && onError(event);
@@ -433,11 +444,11 @@ class WebView extends React.Component {
 
     this.setState({
       lastErrorEvent: event.nativeEvent,
-      viewState: WebViewState.ERROR
+      viewState: WebViewState.ERROR,
     });
   };
 
-  onLoadingFinish = (event) => {
+  onLoadingFinish = event => {
     const {onLoad, onLoadEnd} = this.props;
     onLoad && onLoad(event);
     onLoadEnd && onLoadEnd(event);
@@ -450,10 +461,14 @@ class WebView extends React.Component {
   onMessage = (event: Event) => {
     const {onMessage} = this.props;
     onMessage && onMessage(event);
-  }
+  };
 }
 
-const RCTWebView = requireNativeComponent('RCTWebView', WebView, WebView.extraNativeComponentConfig);
+const RCTWebView = requireNativeComponent(
+  'RCTWebView',
+  WebView,
+  WebView.extraNativeComponentConfig,
+);
 
 const styles = StyleSheet.create({
   container: {
diff --git a/Libraries/Components/WebView/WebView.ios.js b/Libraries/Components/WebView/WebView.ios.js
index 1d54f663f01b..8c0630c2c0e7 100644
--- a/Libraries/Components/WebView/WebView.ios.js
+++ b/Libraries/Components/WebView/WebView.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @noflow
  */
+
 'use strict';
 
 const ActivityIndicator = require('ActivityIndicator');
@@ -55,7 +57,7 @@ type ErrorEvent = {
   domain: any,
   code: any,
   description: any,
-}
+};
 
 type Event = Object;
 
@@ -75,18 +77,10 @@ const defaultRenderLoading = () => (
 );
 const defaultRenderError = (errorDomain, errorCode, errorDesc) => (
   <View style={styles.errorContainer}>
-    <Text style={styles.errorTextTitle}>
-      Error loading page
-    </Text>
-    <Text style={styles.errorText}>
-      {'Domain: ' + errorDomain}
-    </Text>
-    <Text style={styles.errorText}>
-      {'Error Code: ' + errorCode}
-    </Text>
-    <Text style={styles.errorText}>
-      {'Description: ' + errorDesc}
-    </Text>
+    <Text style={styles.errorTextTitle}>Error loading page</Text>
+    <Text style={styles.errorText}>{'Domain: ' + errorDomain}</Text>
+    <Text style={styles.errorText}>{'Error Code: ' + errorCode}</Text>
+    <Text style={styles.errorText}>{'Description: ' + errorDesc}</Text>
   </View>
 );
 
@@ -132,13 +126,10 @@ class WebView extends React.Component {
 
     html: deprecatedPropType(
       PropTypes.string,
-      'Use the `source` prop instead.'
+      'Use the `source` prop instead.',
     ),
 
-    url: deprecatedPropType(
-      PropTypes.string,
-      'Use the `source` prop instead.'
-    ),
+    url: deprecatedPropType(PropTypes.string, 'Use the `source` prop instead.'),
 
     /**
      * Loads static html or a uri (with optional headers) in the WebView.
@@ -380,11 +371,7 @@ class WebView extends React.Component {
      * - `'compatibility'` -  WebView will attempt to be compatible with the approach of a modern web browser with regard to mixed content.
      * @platform android
      */
-    mixedContentMode: PropTypes.oneOf([
-      'never',
-      'always',
-      'compatibility'
-    ]),
+    mixedContentMode: PropTypes.oneOf(['never', 'always', 'compatibility']),
 
     /**
      * Override the native component used to render the WebView. Enables a custom native
@@ -432,24 +419,23 @@ class WebView extends React.Component {
       otherView = (this.props.renderLoading || defaultRenderLoading)();
     } else if (this.state.viewState === WebViewState.ERROR) {
       const errorEvent = this.state.lastErrorEvent;
-      invariant(
-        errorEvent != null,
-        'lastErrorEvent expected to be non-null'
-      );
+      invariant(errorEvent != null, 'lastErrorEvent expected to be non-null');
       otherView = (this.props.renderError || defaultRenderError)(
         errorEvent.domain,
         errorEvent.code,
-        errorEvent.description
+        errorEvent.description,
       );
     } else if (this.state.viewState !== WebViewState.IDLE) {
       console.error(
-        'RCTWebView invalid state encountered: ' + this.state.loading
+        'RCTWebView invalid state encountered: ' + this.state.loading,
       );
     }
 
     const webViewStyles = [styles.container, styles.webView, this.props.style];
-    if (this.state.viewState === WebViewState.LOADING ||
-      this.state.viewState === WebViewState.ERROR) {
+    if (
+      this.state.viewState === WebViewState.LOADING ||
+      this.state.viewState === WebViewState.ERROR
+    ) {
       // if we're in either LOADING or ERROR states, don't show the webView
       webViewStyles.push(styles.hidden);
     }
@@ -458,23 +444,34 @@ class WebView extends React.Component {
 
     const viewManager = nativeConfig.viewManager || RCTWebViewManager;
 
-    const compiledWhitelist = (this.props.originWhitelist || []).map(WebViewShared.originWhitelistToRegex);
-    const onShouldStartLoadWithRequest = ((event: Event) => {
+    const compiledWhitelist = (this.props.originWhitelist || []).map(
+      WebViewShared.originWhitelistToRegex,
+    );
+    const onShouldStartLoadWithRequest = (event: Event) => {
       let shouldStart = true;
       const {url} = event.nativeEvent;
       const origin = WebViewShared.extractOrigin(url);
-      const passesWhitelist = compiledWhitelist.some(x => new RegExp(x).test(origin));
+      const passesWhitelist = compiledWhitelist.some(x =>
+        new RegExp(x).test(origin),
+      );
       shouldStart = shouldStart && passesWhitelist;
       if (!passesWhitelist) {
         Linking.openURL(url);
       }
       if (this.props.onShouldStartLoadWithRequest) {
-        shouldStart = shouldStart && this.props.onShouldStartLoadWithRequest(event.nativeEvent);
+        shouldStart =
+          shouldStart &&
+          this.props.onShouldStartLoadWithRequest(event.nativeEvent);
       }
-      viewManager.startLoadWithResult(!!shouldStart, event.nativeEvent.lockIdentifier);
-    });
+      viewManager.startLoadWithResult(
+        !!shouldStart,
+        event.nativeEvent.lockIdentifier,
+      );
+    };
 
-    const decelerationRate = processDecelerationRate(this.props.decelerationRate);
+    const decelerationRate = processDecelerationRate(
+      this.props.decelerationRate,
+    );
 
     const source = this.props.source || {};
     if (this.props.html) {
@@ -485,9 +482,9 @@ class WebView extends React.Component {
 
     const messagingEnabled = typeof this.props.onMessage === 'function';
 
-    const NativeWebView = nativeConfig.component || RCTWebView;
+    const NativeWebView = nativeConfig.component || RCTWebView;
 
-    const webView =
+    const webView = (
       <NativeWebView
         ref={RCT_WEBVIEW_REF}
         key="webViewKey"
@@ -498,7 +495,9 @@ class WebView extends React.Component {
         scrollEnabled={this.props.scrollEnabled}
         decelerationRate={decelerationRate}
         contentInset={this.props.contentInset}
-        automaticallyAdjustContentInsets={this.props.automaticallyAdjustContentInsets}
+        automaticallyAdjustContentInsets={
+          this.props.automaticallyAdjustContentInsets
+        }
         onLoadingStart={this._onLoadingStart}
         onLoadingFinish={this._onLoadingFinish}
         onLoadingError={this._onLoadingError}
@@ -507,10 +506,13 @@ class WebView extends React.Component {
         onShouldStartLoadWithRequest={onShouldStartLoadWithRequest}
         scalesPageToFit={this.props.scalesPageToFit}
         allowsInlineMediaPlayback={this.props.allowsInlineMediaPlayback}
-        mediaPlaybackRequiresUserAction={this.props.mediaPlaybackRequiresUserAction}
+        mediaPlaybackRequiresUserAction={
+          this.props.mediaPlaybackRequiresUserAction
+        }
         dataDetectorTypes={this.props.dataDetectorTypes}
         {...nativeConfig.props}
-      />;
+      />
+    );
 
     return (
       <View style={styles.container}>
@@ -527,7 +529,7 @@ class WebView extends React.Component {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.goForward,
-      null
+      null,
     );
   };
 
@@ -538,7 +540,7 @@ class WebView extends React.Component {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.goBack,
-      null
+      null,
     );
   };
 
@@ -550,7 +552,7 @@ class WebView extends React.Component {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.reload,
-      null
+      null,
     );
   };
 
@@ -561,7 +563,7 @@ class WebView extends React.Component {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.stopLoading,
-      null
+      null,
     );
   };
 
@@ -575,25 +577,25 @@ class WebView extends React.Component {
    * document.addEventListener('message', e => { document.title = e.data; });
    * ```
    */
-  postMessage = (data) => {
+  postMessage = data => {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.postMessage,
-      [String(data)]
+      [String(data)],
     );
   };
 
   /**
-  * Injects a javascript string into the referenced WebView. Deliberately does not
-  * return a response because using eval() to return a response breaks this method
-  * on pages with a Content Security Policy that disallows eval(). If you need that
-  * functionality, look into postMessage/onMessage.
-  */
-  injectJavaScript = (data) => {
+   * Injects a javascript string into the referenced WebView. Deliberately does not
+   * return a response because using eval() to return a response breaks this method
+   * on pages with a Content Security Policy that disallows eval(). If you need that
+   * functionality, look into postMessage/onMessage.
+   */
+  injectJavaScript = data => {
     UIManager.dispatchViewManagerCommand(
       this.getWebViewHandle(),
       UIManager.RCTWebView.Commands.injectJavaScript,
-      [data]
+      [data],
     );
   };
 
@@ -629,7 +631,7 @@ class WebView extends React.Component {
 
     this.setState({
       lastErrorEvent: event.nativeEvent,
-      viewState: WebViewState.ERROR
+      viewState: WebViewState.ERROR,
     });
   };
 
@@ -646,10 +648,14 @@ class WebView extends React.Component {
   _onMessage = (event: Event) => {
     const {onMessage} = this.props;
     onMessage && onMessage(event);
-  }
+  };
 }
 
-const RCTWebView = requireNativeComponent('RCTWebView', WebView, WebView.extraNativeComponentConfig);
+const RCTWebView = requireNativeComponent(
+  'RCTWebView',
+  WebView,
+  WebView.extraNativeComponentConfig,
+);
 
 const styles = StyleSheet.create({
   container: {
@@ -684,7 +690,7 @@ const styles = StyleSheet.create({
   },
   webView: {
     backgroundColor: '#ffffff',
-  }
+  },
 });
 
 module.exports = WebView;
diff --git a/Libraries/Components/WebView/WebViewShared.js b/Libraries/Components/WebView/WebViewShared.js
index 744ea201f467..5a3006e845b0 100644
--- a/Libraries/Components/WebView/WebViewShared.js
+++ b/Libraries/Components/WebView/WebViewShared.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const escapeStringRegexp = require('escape-string-regexp');
diff --git a/Libraries/Components/WebView/__tests__/WebViewShared-test.js b/Libraries/Components/WebView/__tests__/WebViewShared-test.js
index 37f52064c431..b7456638fedb 100644
--- a/Libraries/Components/WebView/__tests__/WebViewShared-test.js
+++ b/Libraries/Components/WebView/__tests__/WebViewShared-test.js
@@ -4,25 +4,46 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
 
- 'use strict';
+'use strict';
 
 const WebViewShared = require('WebViewShared');
 
 describe('WebViewShared', () => {
   it('extracts the origin correctly', () => {
-    expect(WebViewShared.extractOrigin('http://facebook.com')).toBe('http://facebook.com');
-    expect(WebViewShared.extractOrigin('https://facebook.com')).toBe('https://facebook.com');
-    expect(WebViewShared.extractOrigin('http://facebook.com:8081')).toBe('http://facebook.com:8081');
-    expect(WebViewShared.extractOrigin('ftp://facebook.com')).toBe('ftp://facebook.com');
-    expect(WebViewShared.extractOrigin('myweirdscheme://')).toBe('myweirdscheme://');
-    expect(WebViewShared.extractOrigin('http://facebook.com/')).toBe('http://facebook.com');
-    expect(WebViewShared.extractOrigin('http://facebook.com/longerurl')).toBe('http://facebook.com');
-    expect(WebViewShared.extractOrigin('http://facebook.com/http://facebook.com')).toBe('http://facebook.com');
-    expect(WebViewShared.extractOrigin('http://facebook.com//http://facebook.com')).toBe('http://facebook.com');
-    expect(WebViewShared.extractOrigin('http://facebook.com//http://facebook.com//')).toBe('http://facebook.com');
+    expect(WebViewShared.extractOrigin('http://facebook.com')).toBe(
+      'http://facebook.com',
+    );
+    expect(WebViewShared.extractOrigin('https://facebook.com')).toBe(
+      'https://facebook.com',
+    );
+    expect(WebViewShared.extractOrigin('http://facebook.com:8081')).toBe(
+      'http://facebook.com:8081',
+    );
+    expect(WebViewShared.extractOrigin('ftp://facebook.com')).toBe(
+      'ftp://facebook.com',
+    );
+    expect(WebViewShared.extractOrigin('myweirdscheme://')).toBe(
+      'myweirdscheme://',
+    );
+    expect(WebViewShared.extractOrigin('http://facebook.com/')).toBe(
+      'http://facebook.com',
+    );
+    expect(WebViewShared.extractOrigin('http://facebook.com/longerurl')).toBe(
+      'http://facebook.com',
+    );
+    expect(
+      WebViewShared.extractOrigin('http://facebook.com/http://facebook.com'),
+    ).toBe('http://facebook.com');
+    expect(
+      WebViewShared.extractOrigin('http://facebook.com//http://facebook.com'),
+    ).toBe('http://facebook.com');
+    expect(
+      WebViewShared.extractOrigin('http://facebook.com//http://facebook.com//'),
+    ).toBe('http://facebook.com');
     expect(WebViewShared.extractOrigin('about:blank')).toBe('about:blank');
   });
 
diff --git a/Libraries/Core/Devtools/__tests__/parseErrorStack-test.js b/Libraries/Core/Devtools/__tests__/parseErrorStack-test.js
index 7726a6117b9b..79d677e217e7 100644
--- a/Libraries/Core/Devtools/__tests__/parseErrorStack-test.js
+++ b/Libraries/Core/Devtools/__tests__/parseErrorStack-test.js
@@ -4,10 +4,11 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
-'use strict';
 
+'use strict';
 
 const parseErrorStack = require('parseErrorStack');
 
@@ -16,7 +17,6 @@ function getFakeError() {
 }
 
 describe('parseErrorStack', function() {
-
   it('parses error stack', function() {
     const stack = parseErrorStack(getFakeError());
     expect(stack.length).toBeGreaterThan(0);
@@ -43,5 +43,4 @@ describe('parseErrorStack', function() {
     expect(parseErrorStack({})).toEqual([]);
     expect(parseErrorStack(null)).toEqual([]);
   });
-
 });
diff --git a/Libraries/Core/Devtools/getDevServer.js b/Libraries/Core/Devtools/getDevServer.js
index 1087f6ead2b7..adcc28c2d067 100644
--- a/Libraries/Core/Devtools/getDevServer.js
+++ b/Libraries/Core/Devtools/getDevServer.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const {SourceCode} = require('NativeModules');
@@ -24,7 +26,10 @@ type DevServerInfo = {
  */
 function getDevServer(): DevServerInfo {
   if (_cachedDevServerURL === undefined) {
-    const match = SourceCode && SourceCode.scriptURL && SourceCode.scriptURL.match(/^https?:\/\/.*?\//);
+    const match =
+      SourceCode &&
+      SourceCode.scriptURL &&
+      SourceCode.scriptURL.match(/^https?:\/\/.*?\//);
     _cachedDevServerURL = match ? match[0] : null;
   }
 
diff --git a/Libraries/Core/Devtools/openFileInEditor.js b/Libraries/Core/Devtools/openFileInEditor.js
index 1f4437a5ef8c..c085883920ae 100644
--- a/Libraries/Core/Devtools/openFileInEditor.js
+++ b/Libraries/Core/Devtools/openFileInEditor.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const getDevServer = require('getDevServer');
diff --git a/Libraries/Core/Devtools/parseErrorStack.js b/Libraries/Core/Devtools/parseErrorStack.js
index efcad10191d4..ec85260d7eaa 100644
--- a/Libraries/Core/Devtools/parseErrorStack.js
+++ b/Libraries/Core/Devtools/parseErrorStack.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 export type StackFrame = {
@@ -28,7 +30,9 @@ function parseErrorStack(e: ExtendedError): Array<StackFrame> {
    * error found when Flow v0.54 was deployed. To see the error delete this
    * comment and run Flow. */
   const stacktraceParser = require('stacktrace-parser');
-  const stack = Array.isArray(e.stack) ? e.stack : stacktraceParser.parse(e.stack);
+  const stack = Array.isArray(e.stack)
+    ? e.stack
+    : stacktraceParser.parse(e.stack);
 
   let framesToPop = typeof e.framesToPop === 'number' ? e.framesToPop : 0;
   while (framesToPop--) {
diff --git a/Libraries/Core/Devtools/setupDevtools.js b/Libraries/Core/Devtools/setupDevtools.js
index fec7ea6160cc..ddca7d040030 100644
--- a/Libraries/Core/Devtools/setupDevtools.js
+++ b/Libraries/Core/Devtools/setupDevtools.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 type DevToolsPluginConnection = {
@@ -18,7 +20,7 @@ type DevToolsPlugin = {
   connectToDevTools: (connection: DevToolsPluginConnection) => void,
 };
 
-let register = function () {
+let register = function() {
   // noop
 };
 
diff --git a/Libraries/Core/Devtools/symbolicateStackTrace.js b/Libraries/Core/Devtools/symbolicateStackTrace.js
index 8933394ba92d..b5d7d4e9754f 100644
--- a/Libraries/Core/Devtools/symbolicateStackTrace.js
+++ b/Libraries/Core/Devtools/symbolicateStackTrace.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const getDevServer = require('getDevServer');
@@ -21,7 +23,9 @@ function isSourcedFromDisk(sourcePath: string): boolean {
   return !/^http/.test(sourcePath) && /[\\/]/.test(sourcePath);
 }
 
-async function symbolicateStackTrace(stack: Array<StackFrame>): Promise<Array<StackFrame>> {
+async function symbolicateStackTrace(
+  stack: Array<StackFrame>,
+): Promise<Array<StackFrame>> {
   // RN currently lazy loads whatwg-fetch using a custom fetch module, which,
   // when called for the first time, requires and re-exports 'whatwg-fetch'.
   // However, when a dependency of the project tries to require whatwg-fetch
diff --git a/Libraries/Core/ExceptionsManager.js b/Libraries/Core/ExceptionsManager.js
index 6a0ba132dc81..bc32f5d0d238 100644
--- a/Libraries/Core/ExceptionsManager.js
+++ b/Libraries/Core/ExceptionsManager.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 import type {ExtendedError} from 'parseErrorStack';
@@ -14,30 +16,42 @@ import type {ExtendedError} from 'parseErrorStack';
  * Handles the developer-visible aspect of errors and exceptions
  */
 let exceptionID = 0;
-function reportException(e: ExtendedError, isFatal: bool) {
+function reportException(e: ExtendedError, isFatal: boolean) {
   const {ExceptionsManager} = require('NativeModules');
   if (ExceptionsManager) {
     const parseErrorStack = require('parseErrorStack');
     const stack = parseErrorStack(e);
     const currentExceptionID = ++exceptionID;
     if (isFatal) {
-      ExceptionsManager.reportFatalException(e.message, stack, currentExceptionID);
+      ExceptionsManager.reportFatalException(
+        e.message,
+        stack,
+        currentExceptionID,
+      );
     } else {
-      ExceptionsManager.reportSoftException(e.message, stack, currentExceptionID);
+      ExceptionsManager.reportSoftException(
+        e.message,
+        stack,
+        currentExceptionID,
+      );
     }
     if (__DEV__) {
       const symbolicateStackTrace = require('symbolicateStackTrace');
-      symbolicateStackTrace(stack).then(
-        (prettyStack) => {
+      symbolicateStackTrace(stack)
+        .then(prettyStack => {
           if (prettyStack) {
-            ExceptionsManager.updateExceptionMessage(e.message, prettyStack, currentExceptionID);
+            ExceptionsManager.updateExceptionMessage(
+              e.message,
+              prettyStack,
+              currentExceptionID,
+            );
           } else {
             throw new Error('The stack is null');
           }
-        }
-      ).catch(
-        (error) => console.warn('Unable to symbolicate stack trace: ' + error.message)
-      );
+        })
+        .catch(error =>
+          console.warn('Unable to symbolicate stack trace: ' + error.message),
+        );
     }
   }
 }
@@ -83,7 +97,7 @@ function reactConsoleErrorHandler() {
       // (Note: Logic duplicated in polyfills/console.js.)
       return;
     }
-    const error : ExtendedError = new Error('console.error: ' + str);
+    const error: ExtendedError = new Error('console.error: ' + str);
     error.framesToPop = 1;
     reportException(error, /* isFatal */ false);
   }
@@ -108,4 +122,4 @@ function installConsoleErrorReporter() {
   }
 }
 
-module.exports = { handleException, installConsoleErrorReporter };
+module.exports = {handleException, installConsoleErrorReporter};
diff --git a/Libraries/Core/InitializeCore.js b/Libraries/Core/InitializeCore.js
index 2f10d5fc0e05..119deb92b2b0 100644
--- a/Libraries/Core/InitializeCore.js
+++ b/Libraries/Core/InitializeCore.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -152,13 +153,25 @@ polyfillObjectProperty(navigator, 'geolocation', () => require('Geolocation'));
 const BatchedBridge = require('BatchedBridge');
 BatchedBridge.registerLazyCallableModule('Systrace', () => require('Systrace'));
 BatchedBridge.registerLazyCallableModule('JSTimers', () => require('JSTimers'));
-BatchedBridge.registerLazyCallableModule('HeapCapture', () => require('HeapCapture'));
-BatchedBridge.registerLazyCallableModule('SamplingProfiler', () => require('SamplingProfiler'));
+BatchedBridge.registerLazyCallableModule('HeapCapture', () =>
+  require('HeapCapture'),
+);
+BatchedBridge.registerLazyCallableModule('SamplingProfiler', () =>
+  require('SamplingProfiler'),
+);
 BatchedBridge.registerLazyCallableModule('RCTLog', () => require('RCTLog'));
-BatchedBridge.registerLazyCallableModule('RCTDeviceEventEmitter', () => require('RCTDeviceEventEmitter'));
-BatchedBridge.registerLazyCallableModule('RCTNativeAppEventEmitter', () => require('RCTNativeAppEventEmitter'));
-BatchedBridge.registerLazyCallableModule('PerformanceLogger', () => require('PerformanceLogger'));
-BatchedBridge.registerLazyCallableModule('JSDevSupportModule', () => require('JSDevSupportModule'));
+BatchedBridge.registerLazyCallableModule('RCTDeviceEventEmitter', () =>
+  require('RCTDeviceEventEmitter'),
+);
+BatchedBridge.registerLazyCallableModule('RCTNativeAppEventEmitter', () =>
+  require('RCTNativeAppEventEmitter'),
+);
+BatchedBridge.registerLazyCallableModule('PerformanceLogger', () =>
+  require('PerformanceLogger'),
+);
+BatchedBridge.registerLazyCallableModule('JSDevSupportModule', () =>
+  require('JSDevSupportModule'),
+);
 
 global.__fetchSegment = function(
   segmentId: number,
@@ -167,19 +180,25 @@ global.__fetchSegment = function(
 ) {
   const {SegmentFetcher} = require('NativeModules');
   if (!SegmentFetcher) {
-    throw new Error('SegmentFetcher is missing. Please ensure that it is ' +
-      'included as a NativeModule.');
+    throw new Error(
+      'SegmentFetcher is missing. Please ensure that it is ' +
+        'included as a NativeModule.',
+    );
   }
 
-  SegmentFetcher.fetchSegment(segmentId, options, (errorObject: ?{message: string, code: string}) => {
-    if (errorObject) {
-      const error = new Error(errorObject.message);
-      (error: any).code = errorObject.code;
-      callback(error);
-    }
-
-    callback(null);
-  });
+  SegmentFetcher.fetchSegment(
+    segmentId,
+    options,
+    (errorObject: ?{message: string, code: string}) => {
+      if (errorObject) {
+        const error = new Error(errorObject.message);
+        (error: any).code = errorObject.code;
+        callback(error);
+      }
+
+      callback(null);
+    },
+  );
 };
 
 // Set up devtools
diff --git a/Libraries/Core/ReactNativeVersion.js b/Libraries/Core/ReactNativeVersion.js
index 1b2b2155f551..320b26ac84db 100644
--- a/Libraries/Core/ReactNativeVersion.js
+++ b/Libraries/Core/ReactNativeVersion.js
@@ -1,11 +1,11 @@
 /**
- * @generated by scripts/bump-oss-version.js
- *
  * Copyright (c) 2015-present, Facebook, Inc.
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
+ * @generated by scripts/bump-oss-version.js
  * @flow
  */
 
diff --git a/Libraries/Core/__mocks__/ErrorUtils.js b/Libraries/Core/__mocks__/ErrorUtils.js
index 6b2282672de4..2719c138c454 100644
--- a/Libraries/Core/__mocks__/ErrorUtils.js
+++ b/Libraries/Core/__mocks__/ErrorUtils.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 // This mock only provides short-circuited methods of applyWithGuard and guard.
diff --git a/Libraries/EventEmitter/MissingNativeEventEmitterShim.js b/Libraries/EventEmitter/MissingNativeEventEmitterShim.js
index e9c11b925c8e..562964b85f4c 100644
--- a/Libraries/EventEmitter/MissingNativeEventEmitterShim.js
+++ b/Libraries/EventEmitter/MissingNativeEventEmitterShim.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EmitterSubscription = require('EmitterSubscription');
@@ -28,9 +30,11 @@ class MissingNativeEventEmitterShim extends EventEmitter {
     invariant(
       false,
       `Cannot use '${this._nativeEventEmitterName}' module when ` +
-      `native '${this._nativeModuleName}' is not included in the build. ` +
-      `Either include it, or check '${this._nativeEventEmitterName}'.isAvailable ` +
-      'before calling any methods.'
+        `native '${this._nativeModuleName}' is not included in the build. ` +
+        `Either include it, or check '${
+          this._nativeEventEmitterName
+        }'.isAvailable ` +
+        'before calling any methods.',
     );
   }
 
diff --git a/Libraries/EventEmitter/NativeEventEmitter.js b/Libraries/EventEmitter/NativeEventEmitter.js
index 582cf9561f16..2220670fc769 100644
--- a/Libraries/EventEmitter/NativeEventEmitter.js
+++ b/Libraries/EventEmitter/NativeEventEmitter.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EventEmitter = require('EventEmitter');
diff --git a/Libraries/EventEmitter/RCTDeviceEventEmitter.js b/Libraries/EventEmitter/RCTDeviceEventEmitter.js
index 9378a5f5310b..b0977f219abc 100644
--- a/Libraries/EventEmitter/RCTDeviceEventEmitter.js
+++ b/Libraries/EventEmitter/RCTDeviceEventEmitter.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EventEmitter = require('EventEmitter');
@@ -16,13 +18,25 @@ import type EmitterSubscription from 'EmitterSubscription';
 function checkNativeEventModule(eventType: ?string) {
   if (eventType) {
     if (eventType.lastIndexOf('statusBar', 0) === 0) {
-      throw new Error('`' + eventType + '` event should be registered via the StatusBarIOS module');
+      throw new Error(
+        '`' +
+          eventType +
+          '` event should be registered via the StatusBarIOS module',
+      );
     }
     if (eventType.lastIndexOf('keyboard', 0) === 0) {
-      throw new Error('`' + eventType + '` event should be registered via the Keyboard module');
+      throw new Error(
+        '`' +
+          eventType +
+          '` event should be registered via the Keyboard module',
+      );
     }
     if (eventType === 'appStateDidChange' || eventType === 'memoryWarning') {
-      throw new Error('`' + eventType + '` event should be registered via the AppState module');
+      throw new Error(
+        '`' +
+          eventType +
+          '` event should be registered via the AppState module',
+      );
     }
   }
 }
@@ -32,7 +46,6 @@ function checkNativeEventModule(eventType: ?string) {
  * adding all event listeners directly to RCTDeviceEventEmitter.
  */
 class RCTDeviceEventEmitter extends EventEmitter {
-
   sharedSubscriber: EventSubscriptionVendor;
 
   constructor() {
@@ -41,8 +54,11 @@ class RCTDeviceEventEmitter extends EventEmitter {
     this.sharedSubscriber = sharedSubscriber;
   }
 
-
-  addListener(eventType: string, listener: Function, context: ?Object): EmitterSubscription {
+  addListener(
+    eventType: string,
+    listener: Function,
+    context: ?Object,
+  ): EmitterSubscription {
     if (__DEV__) {
       checkNativeEventModule(eventType);
     }
diff --git a/Libraries/EventEmitter/RCTEventEmitter.js b/Libraries/EventEmitter/RCTEventEmitter.js
index 976356b7aa07..1a51905ba20d 100644
--- a/Libraries/EventEmitter/RCTEventEmitter.js
+++ b/Libraries/EventEmitter/RCTEventEmitter.js
@@ -4,19 +4,18 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const BatchedBridge = require('BatchedBridge');
 
 const RCTEventEmitter = {
   register(eventEmitter: any) {
-    BatchedBridge.registerCallableModule(
-      'RCTEventEmitter',
-      eventEmitter
-    );
-  }
+    BatchedBridge.registerCallableModule('RCTEventEmitter', eventEmitter);
+  },
 };
 
 module.exports = RCTEventEmitter;
diff --git a/Libraries/EventEmitter/RCTNativeAppEventEmitter.js b/Libraries/EventEmitter/RCTNativeAppEventEmitter.js
index 43245aba558e..a32cfcef7cf9 100644
--- a/Libraries/EventEmitter/RCTNativeAppEventEmitter.js
+++ b/Libraries/EventEmitter/RCTNativeAppEventEmitter.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
diff --git a/Libraries/EventEmitter/__mocks__/NativeEventEmitter.js b/Libraries/EventEmitter/__mocks__/NativeEventEmitter.js
index d65243424b4a..e822b72c73c1 100644
--- a/Libraries/EventEmitter/__mocks__/NativeEventEmitter.js
+++ b/Libraries/EventEmitter/__mocks__/NativeEventEmitter.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EventEmitter = require('EventEmitter');
diff --git a/Libraries/Experimental/Incremental.js b/Libraries/Experimental/Incremental.js
index 237e5dbc32e7..cfd0c69fd03c 100644
--- a/Libraries/Experimental/Incremental.js
+++ b/Libraries/Experimental/Incremental.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const InteractionManager = require('InteractionManager');
@@ -79,16 +81,16 @@ const DEBUG = false;
  * component, saving us from ever doing the remaining rendering work.
  */
 export type Props = {
- /**
-  * Called when all the descendants have finished rendering and mounting
-  * recursively.
-  */
- onDone?: () => void,
- /**
-  * Tags instances and associated tasks for easier debugging.
-  */
- name: string,
- children?: any,
+  /**
+   * Called when all the descendants have finished rendering and mounting
+   * recursively.
+   */
+  onDone?: () => void,
+  /**
+   * Tags instances and associated tasks for easier debugging.
+   */
+  name: string,
+  children?: any,
 };
 type DefaultProps = {
   name: string,
@@ -131,30 +133,38 @@ class Incremental extends React.Component<Props, State> {
     if (!ctx) {
       return;
     }
-    this._incrementId = ++(ctx.incrementalCount);
+    this._incrementId = ++ctx.incrementalCount;
     InteractionManager.runAfterInteractions({
       name: 'Incremental:' + this.getName(),
-      gen: () => new Promise(resolve => {
-        if (!this._mounted || this._rendered) {
-          resolve();
-          return;
-        }
-        DEBUG && infoLog('set doIncrementalRender for ' + this.getName());
-        this.setState({doIncrementalRender: true}, resolve);
-      }),
-    }).then(() => {
-      DEBUG && infoLog('call onDone for ' + this.getName());
-      this._mounted && this.props.onDone && this.props.onDone();
-    }).catch((ex) => {
-      ex.message = `Incremental render failed for ${this.getName()}: ${ex.message}`;
-      throw ex;
-    }).done();
+      gen: () =>
+        new Promise(resolve => {
+          if (!this._mounted || this._rendered) {
+            resolve();
+            return;
+          }
+          DEBUG && infoLog('set doIncrementalRender for ' + this.getName());
+          this.setState({doIncrementalRender: true}, resolve);
+        }),
+    })
+      .then(() => {
+        DEBUG && infoLog('call onDone for ' + this.getName());
+        this._mounted && this.props.onDone && this.props.onDone();
+      })
+      .catch(ex => {
+        ex.message = `Incremental render failed for ${this.getName()}: ${
+          ex.message
+        }`;
+        throw ex;
+      })
+      .done();
   }
 
   render(): React.Node {
-    if (this._rendered || // Make sure that once we render once, we stay rendered even if incrementalGroupEnabled gets flipped.
-        !this.context.incrementalGroupEnabled ||
-        this.state.doIncrementalRender) {
+    if (
+      this._rendered || // Make sure that once we render once, we stay rendered even if incrementalGroupEnabled gets flipped.
+      !this.context.incrementalGroupEnabled ||
+      this.state.doIncrementalRender
+    ) {
       DEBUG && infoLog('render ' + this.getName());
       this._rendered = true;
       return this.props.children;
diff --git a/Libraries/Experimental/IncrementalExample.js b/Libraries/Experimental/IncrementalExample.js
index 7f006d38b6a7..3cc441fff385 100644
--- a/Libraries/Experimental/IncrementalExample.js
+++ b/Libraries/Experimental/IncrementalExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -35,7 +37,10 @@ JSEventLoopWatchdog.install({thresholdMS: 200});
 
 let totalWidgets = 0;
 
-class SlowWidget extends React.Component<$FlowFixMeProps, {ctorTimestamp: number, timeToMount: number}> {
+class SlowWidget extends React.Component<
+  $FlowFixMeProps,
+  {ctorTimestamp: number, timeToMount: number},
+> {
   constructor(props, context) {
     super(props, context);
     this.state = {
@@ -69,7 +74,9 @@ function stopInteraction() {
 }
 
 function Block(props: Object) {
-  const IncrementalContainer = props.stream ? IncrementalGroup : IncrementalPresenter;
+  const IncrementalContainer = props.stream
+    ? IncrementalGroup
+    : IncrementalPresenter;
   return (
     <IncrementalContainer name={'b_' + props.idx}>
       <TouchableOpacity
@@ -116,32 +123,37 @@ class IncrementalExample extends React.Component<mixed, {stats: ?Object}> {
   }
   render(): React.Node {
     return (
-      <IncrementalGroup
-        disabled={false}
-        name="root"
-        onDone={this._onDone}>
+      <IncrementalGroup disabled={false} name="root" onDone={this._onDone}>
         <ScrollView style={styles.scrollView}>
           <Text style={styles.headerText}>
             Press and hold on a row to pause rendering.
           </Text>
-          {this.state.stats && <Text>
-            Finished: {JSON.stringify(this.state.stats, null, 2)}
-          </Text>}
-          {Array(8).fill().map((_, blockIdx) => {
-            return (
-              <Block key={blockIdx} idx={blockIdx} stream={blockIdx < 2}>
-                {Array(4).fill().map((_b, rowIdx) => (
-                  <Row key={rowIdx}>
-                    {Array(14).fill().map((_c, widgetIdx) => (
-                      <Incremental key={widgetIdx} name={'w_' + widgetIdx}>
-                        <SlowWidget idx={widgetIdx} />
-                      </Incremental>
+          {this.state.stats && (
+            <Text>Finished: {JSON.stringify(this.state.stats, null, 2)}</Text>
+          )}
+          {Array(8)
+            .fill()
+            .map((_, blockIdx) => {
+              return (
+                <Block key={blockIdx} idx={blockIdx} stream={blockIdx < 2}>
+                  {Array(4)
+                    .fill()
+                    .map((_b, rowIdx) => (
+                      <Row key={rowIdx}>
+                        {Array(14)
+                          .fill()
+                          .map((_c, widgetIdx) => (
+                            <Incremental
+                              key={widgetIdx}
+                              name={'w_' + widgetIdx}>
+                              <SlowWidget idx={widgetIdx} />
+                            </Incremental>
+                          ))}
+                      </Row>
                     ))}
-                  </Row>
-                ))}
-              </Block>
-            );
-          })}
+                </Block>
+              );
+            })}
         </ScrollView>
       </IncrementalGroup>
     );
@@ -150,7 +162,7 @@ class IncrementalExample extends React.Component<mixed, {stats: ?Object}> {
 
 function burnCPU(milliseconds) {
   const start = performanceNow();
-  while (performanceNow() < (start + milliseconds)) {}
+  while (performanceNow() < start + milliseconds) {}
 }
 
 const styles = StyleSheet.create({
diff --git a/Libraries/Experimental/IncrementalGroup.js b/Libraries/Experimental/IncrementalGroup.js
index f630ba66c8c5..af1a7ad63ddb 100644
--- a/Libraries/Experimental/IncrementalGroup.js
+++ b/Libraries/Experimental/IncrementalGroup.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Incremental = require('Incremental');
@@ -36,9 +38,7 @@ class IncrementalGroup extends React.Component<Props & {disabled?: boolean}> {
   _groupInc: string;
   UNSAFE_componentWillMount() {
     this._groupInc = `g${++_groupCounter}-`;
-    DEBUG && infoLog(
-      'create IncrementalGroup with id ' + this.getGroupId()
-    );
+    DEBUG && infoLog('create IncrementalGroup with id ' + this.getGroupId());
   }
 
   getGroupId(): string {
@@ -65,10 +65,7 @@ class IncrementalGroup extends React.Component<Props & {disabled?: boolean}> {
 
   render(): React.Node {
     return (
-      <Incremental
-        onDone={this.props.onDone}
-        children={this.props.children}
-      />
+      <Incremental onDone={this.props.onDone} children={this.props.children} />
     );
   }
 }
diff --git a/Libraries/Experimental/IncrementalPresenter.js b/Libraries/Experimental/IncrementalPresenter.js
index 05520a3ec487..9927179d1739 100644
--- a/Libraries/Experimental/IncrementalPresenter.js
+++ b/Libraries/Experimental/IncrementalPresenter.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const IncrementalGroup = require('IncrementalGroup');
@@ -36,7 +38,7 @@ type Props = {
   onLayout?: (event: Object) => void,
   style?: mixed,
   children?: any,
-}
+};
 class IncrementalPresenter extends React.Component<Props> {
   context: Context;
   _isDone: boolean;
@@ -60,19 +62,23 @@ class IncrementalPresenter extends React.Component<Props> {
   }
   onDone() {
     this._isDone = true;
-    if (this.props.disabled !== true &&
-        this.context.incrementalGroupEnabled !== false) {
+    if (
+      this.props.disabled !== true &&
+      this.context.incrementalGroupEnabled !== false
+    ) {
       // Avoid expensive re-renders and use setNativeProps
-      this.refs.view.setNativeProps(
-        {style: [this.props.style, {opacity: 1, position: 'relative'}]}
-      );
+      this.refs.view.setNativeProps({
+        style: [this.props.style, {opacity: 1, position: 'relative'}],
+      });
     }
     this.props.onDone && this.props.onDone();
   }
   render() {
-    if (this.props.disabled !== true &&
-        this.context.incrementalGroupEnabled !== false &&
-        !this._isDone) {
+    if (
+      this.props.disabled !== true &&
+      this.context.incrementalGroupEnabled !== false &&
+      !this._isDone
+    ) {
       var style = [this.props.style, {opacity: 0, position: 'absolute'}];
     } else {
       var style = this.props.style;
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableListView.js b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
index 4187684ddb67..e449501c7183 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableListView.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ListView = require('ListView');
@@ -22,7 +24,9 @@ type DefaultProps = {
 type Props = {
   bounceFirstRowOnMount: boolean,
   dataSource: SwipeableListViewDataSource,
-  maxSwipeDistance: number | (rowData: any, sectionID: string, rowID: string) => number,
+  maxSwipeDistance:
+    | number
+    | ((rowData: any, sectionID: string, rowID: string) => number),
   onScroll?: ?Function,
   renderRow: Function,
   renderQuickActions: Function,
@@ -78,10 +82,8 @@ class SwipeableListView extends React.Component<Props, State> {
      */
     dataSource: PropTypes.instanceOf(SwipeableListViewDataSource).isRequired,
     // Maximum distance to open to after a swipe
-    maxSwipeDistance: PropTypes.oneOfType([
-      PropTypes.number,
-      PropTypes.func,
-    ]).isRequired,
+    maxSwipeDistance: PropTypes.oneOfType([PropTypes.number, PropTypes.func])
+      .isRequired,
     // Callback method to render the swipeable view
     renderRow: PropTypes.func.isRequired,
     // Callback method to render the view that will be unveiled on swipe
@@ -103,7 +105,10 @@ class SwipeableListView extends React.Component<Props, State> {
   }
 
   UNSAFE_componentWillReceiveProps(nextProps: Props): void {
-    if (this.state.dataSource.getDataSource() !== nextProps.dataSource.getDataSource()) {
+    if (
+      this.state.dataSource.getDataSource() !==
+      nextProps.dataSource.getDataSource()
+    ) {
       this.setState({
         dataSource: nextProps.dataSource,
       });
@@ -114,7 +119,7 @@ class SwipeableListView extends React.Component<Props, State> {
     return (
       <ListView
         {...this.props}
-        ref={(ref) => {
+        ref={ref => {
           this._listViewRef = ref;
         }}
         dataSource={this.state.dataSource.getDataSource()}
@@ -132,7 +137,7 @@ class SwipeableListView extends React.Component<Props, State> {
       });
     }
     this.props.onScroll && this.props.onScroll(e);
-  }
+  };
 
   /**
    * This is a work-around to lock vertical `ListView` scrolling on iOS and
@@ -141,10 +146,13 @@ class SwipeableListView extends React.Component<Props, State> {
    * (from high 20s to almost consistently 60 fps)
    */
   _setListViewScrollable(value: boolean): void {
-    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
-     * error found when Flow v0.68 was deployed. To see the error delete this
-     * comment and run Flow. */
-    if (this._listViewRef && typeof this._listViewRef.setNativeProps === 'function') {
+    if (
+      this._listViewRef &&
+      /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+      * error found when Flow v0.68 was deployed. To see the error delete this
+      * comment and run Flow. */
+      typeof this._listViewRef.setNativeProps === 'function'
+    ) {
       this._listViewRef.setNativeProps({
         scrollEnabled: value,
       });
@@ -153,16 +161,23 @@ class SwipeableListView extends React.Component<Props, State> {
 
   // Passing through ListView's getScrollResponder() function
   getScrollResponder(): ?Object {
-    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
-     * error found when Flow v0.68 was deployed. To see the error delete this
-     * comment and run Flow. */
-    if (this._listViewRef && typeof this._listViewRef.getScrollResponder === 'function') {
+    if (
+      this._listViewRef &&
+      /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
+      * error found when Flow v0.68 was deployed. To see the error delete this
+      * comment and run Flow. */
+      typeof this._listViewRef.getScrollResponder === 'function'
+    ) {
       return this._listViewRef.getScrollResponder();
     }
   }
 
   // This enables rows having variable width slideoutView.
-  _getMaxSwipeDistance(rowData: Object, sectionID: string, rowID: string): number {
+  _getMaxSwipeDistance(
+    rowData: Object,
+    sectionID: string,
+    rowID: string,
+  ): number {
     if (typeof this.props.maxSwipeDistance === 'function') {
       return this.props.maxSwipeDistance(rowData, sectionID, rowID);
     }
@@ -170,8 +185,16 @@ class SwipeableListView extends React.Component<Props, State> {
     return this.props.maxSwipeDistance;
   }
 
-  _renderRow = (rowData: Object, sectionID: string, rowID: string): React.Element<any> => {
-    const slideoutView = this.props.renderQuickActions(rowData, sectionID, rowID);
+  _renderRow = (
+    rowData: Object,
+    sectionID: string,
+    rowID: string,
+  ): React.Element<any> => {
+    const slideoutView = this.props.renderQuickActions(
+      rowData,
+      sectionID,
+      rowID,
+    );
 
     // If renderQuickActions is unspecified or returns falsey, don't allow swipe
     if (!slideoutView) {
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableListViewDataSource.js b/Libraries/Experimental/SwipeableRow/SwipeableListViewDataSource.js
index da4377acad8f..6c409a9acad1 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableListViewDataSource.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableListViewDataSource.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const ListViewDataSource = require('ListViewDataSource');
@@ -37,8 +39,10 @@ class SwipeableListViewDataSource {
          * changed, or its data blob changed.
          */
         return (
-          (row1.id !== this._previousOpenRowID && row2.id === this._openRowID) ||
-          (row1.id === this._previousOpenRowID && row2.id !== this._openRowID) ||
+          (row1.id !== this._previousOpenRowID &&
+            row2.id === this._openRowID) ||
+          (row1.id === this._previousOpenRowID &&
+            row2.id !== this._openRowID) ||
           params.rowHasChanged(row1, row2)
         );
       },
@@ -49,12 +53,12 @@ class SwipeableListViewDataSource {
   cloneWithRowsAndSections(
     dataBlob: any,
     sectionIdentities: ?Array<string>,
-    rowIdentities: ?Array<Array<string>>
+    rowIdentities: ?Array<Array<string>>,
   ): SwipeableListViewDataSource {
     this._dataSource = this._dataSource.cloneWithRowsAndSections(
       dataBlob,
       sectionIdentities,
-      rowIdentities
+      rowIdentities,
     );
 
     this._dataBlob = dataBlob;
@@ -89,10 +93,10 @@ class SwipeableListViewDataSource {
     if (this.rowIdentities && this.rowIdentities.length) {
       const lastSection = this.rowIdentities[this.rowIdentities.length - 1];
       if (lastSection && lastSection.length) {
-       return lastSection[lastSection.length - 1];
-     }
+        return lastSection[lastSection.length - 1];
+      }
     }
-   return Object.keys(this._dataBlob)[this._dataBlob.length - 1];
+    return Object.keys(this._dataBlob)[this._dataBlob.length - 1];
   }
 
   setOpenRowID(rowID: string): SwipeableListViewDataSource {
@@ -102,7 +106,7 @@ class SwipeableListViewDataSource {
     this._dataSource = this._dataSource.cloneWithRowsAndSections(
       this._dataBlob,
       this.sectionIdentities,
-      this.rowIdentities
+      this.rowIdentities,
     );
 
     return this;
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js b/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
index 704f315961ce..dd002fe25974 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Image = require('Image');
@@ -60,9 +62,7 @@ class SwipeableQuickActionButton extends React.Component<{
             source={this.props.imageSource}
             style={this.props.imageStyle}
           />
-          <Text style={this.props.textStyle}>
-            {this.props.text}
-          </Text>
+          <Text style={this.props.textStyle}>{this.props.text}</Text>
         </View>
       </TouchableHighlight>
     );
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableQuickActions.js b/Libraries/Experimental/SwipeableRow/SwipeableQuickActions.js
index 42d2f2cc060b..3642b135d431 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableQuickActions.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableQuickActions.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -40,19 +42,17 @@ class SwipeableQuickActions extends React.Component<{style?: $FlowFixMe}> {
         buttons.push(children[i]);
 
         // $FlowFixMe found when converting React.createClass to ES6
-        if (i < this.props.children.length - 1) { // Not last button
+        if (i < this.props.children.length - 1) {
+          // Not last button
           buttons.push(<View key={i} style={styles.divider} />);
         }
       }
-    } else { // 1 child
+    } else {
+      // 1 child
       buttons = children;
     }
 
-    return (
-      <View style={[styles.background, this.props.style]}>
-        {buttons}
-      </View>
-    );
+    return <View style={[styles.background, this.props.style]}>{buttons}</View>;
   }
 }
 
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableRow.js b/Libraries/Experimental/SwipeableRow/SwipeableRow.js
index 0c072611aaca..26361625c5fc 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableRow.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableRow.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Animated = require('Animated');
@@ -52,7 +54,7 @@ const RIGHT_SWIPE_BOUNCE_BACK_DURATION = 300;
  * Max distance of right swipe to allow (right swipes do functionally nothing).
  * Must be multiplied by SLOW_SPEED_SWIPE_FACTOR because gestureState.dx tracks
  * how far the finger swipes, and not the actual animation distance.
-*/
+ */
 const RIGHT_SWIPE_THRESHOLD = 30 * SLOW_SPEED_SWIPE_FACTOR;
 
 /**
@@ -121,7 +123,8 @@ const SwipeableRow = createReactClass({
 
   UNSAFE_componentWillMount(): void {
     this._panResponder = PanResponder.create({
-      onMoveShouldSetPanResponderCapture: this._handleMoveShouldSetPanResponderCapture,
+      onMoveShouldSetPanResponderCapture: this
+        ._handleMoveShouldSetPanResponderCapture,
       onPanResponderGrant: this._handlePanResponderGrant,
       onPanResponderMove: this._handlePanResponderMove,
       onPanResponderRelease: this._handlePanResponderEnd,
@@ -158,10 +161,8 @@ const SwipeableRow = createReactClass({
     let slideOutView;
     if (this.state.isSwipeableViewRendered && this.state.rowHeight) {
       slideOutView = (
-        <View style={[
-          styles.slideOutContainer,
-          {height: this.state.rowHeight},
-          ]}>
+        <View
+          style={[styles.slideOutContainer, {height: this.state.rowHeight}]}>
           {this.props.slideoutView}
         </View>
       );
@@ -177,8 +178,7 @@ const SwipeableRow = createReactClass({
     );
 
     return (
-      <View
-        {...this._panResponder.panHandlers}>
+      <View {...this._panResponder.panHandlers}>
         {slideOutView}
         {swipeableView}
       </View>
@@ -205,9 +205,7 @@ const SwipeableRow = createReactClass({
     return gestureState.dy < 10 && this._isValidSwipe(gestureState);
   },
 
-  _handlePanResponderGrant(event: Object, gestureState: Object): void {
-
-  },
+  _handlePanResponderGrant(event: Object, gestureState: Object): void {},
 
   _handlePanResponderMove(event: Object, gestureState: Object): void {
     if (this._isSwipingExcessivelyRightFromClosedPosition(gestureState)) {
@@ -263,43 +261,42 @@ const SwipeableRow = createReactClass({
     duration: number = SWIPE_DURATION,
     callback: Function = emptyFunction,
   ): void {
-    Animated.timing(
-      this.state.currentLeft,
-      {
-        duration,
-        toValue,
-        useNativeDriver: true,
-      },
-    ).start(() => {
+    Animated.timing(this.state.currentLeft, {
+      duration,
+      toValue,
+      useNativeDriver: true,
+    }).start(() => {
       this._previousLeft = toValue;
       callback();
     });
   },
 
   _animateToOpenPosition(): void {
-    const maxSwipeDistance = IS_RTL ? -this.props.maxSwipeDistance : this.props.maxSwipeDistance;
+    const maxSwipeDistance = IS_RTL
+      ? -this.props.maxSwipeDistance
+      : this.props.maxSwipeDistance;
     this._animateTo(-maxSwipeDistance);
   },
 
-  _animateToOpenPositionWith(
-    speed: number,
-    distMoved: number,
-  ): void {
+  _animateToOpenPositionWith(speed: number, distMoved: number): void {
     /**
      * Ensure the speed is at least the set speed threshold to prevent a slow
      * swiping animation
      */
-    speed = (
-      speed > HORIZONTAL_FULL_SWIPE_SPEED_THRESHOLD ?
-      speed :
-      HORIZONTAL_FULL_SWIPE_SPEED_THRESHOLD
-    );
+    speed =
+      speed > HORIZONTAL_FULL_SWIPE_SPEED_THRESHOLD
+        ? speed
+        : HORIZONTAL_FULL_SWIPE_SPEED_THRESHOLD;
     /**
      * Calculate the duration the row should take to swipe the remaining distance
      * at the same speed the user swiped (or the speed threshold)
      */
-    const duration = Math.abs((this.props.maxSwipeDistance - Math.abs(distMoved)) / speed);
-    const maxSwipeDistance = IS_RTL ? -this.props.maxSwipeDistance : this.props.maxSwipeDistance;
+    const duration = Math.abs(
+      (this.props.maxSwipeDistance - Math.abs(distMoved)) / speed,
+    );
+    const maxSwipeDistance = IS_RTL
+      ? -this.props.maxSwipeDistance
+      : this.props.maxSwipeDistance;
     this._animateTo(-maxSwipeDistance, duration);
   },
 
@@ -316,9 +313,9 @@ const SwipeableRow = createReactClass({
      * When swiping right, we want to bounce back past closed position on release
      * so users know they should swipe right to get content.
      */
-    const swipeBounceBackDistance = IS_RTL ?
-      -RIGHT_SWIPE_BOUNCE_BACK_DISTANCE :
-      RIGHT_SWIPE_BOUNCE_BACK_DISTANCE;
+    const swipeBounceBackDistance = IS_RTL
+      ? -RIGHT_SWIPE_BOUNCE_BACK_DISTANCE
+      : RIGHT_SWIPE_BOUNCE_BACK_DISTANCE;
     this._animateTo(
       -swipeBounceBackDistance,
       duration,
@@ -328,7 +325,11 @@ const SwipeableRow = createReactClass({
 
   // Ignore swipes due to user's finger moving slightly when tapping
   _isValidSwipe(gestureState: Object): boolean {
-    if (this.props.preventSwipeRight && this._previousLeft === CLOSED_LEFT_POSITION && gestureState.dx > 0) {
+    if (
+      this.props.preventSwipeRight &&
+      this._previousLeft === CLOSED_LEFT_POSITION &&
+      gestureState.dx > 0
+    ) {
       return false;
     }
 
diff --git a/Libraries/Experimental/WindowedListView.js b/Libraries/Experimental/WindowedListView.js
index bf7ef3324b81..15f1d0b4a875 100644
--- a/Libraries/Experimental/WindowedListView.js
+++ b/Libraries/Experimental/WindowedListView.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Batchinator = require('Batchinator');
@@ -67,7 +69,10 @@ type Props = {
    * return a row.
    */
   renderRow: (
-    rowData: any, sectionIdx: number, rowIdx: number, rowKey: string
+    rowData: any,
+    sectionIdx: number,
+    rowIdx: number,
+    rowKey: string,
   ) => ?React.Element<any>,
   /**
    * Rendered when the list is scrolled faster than rows can be rendered.
@@ -78,9 +83,7 @@ type Props = {
   /**
    * Always rendered at the bottom of all the rows.
    */
-  renderFooter?: (
-    showFooter: boolean,
-  ) => ?React.Element<any>,
+  renderFooter?: (showFooter: boolean) => ?React.Element<any>,
   /**
    * Pipes through normal onScroll events from the underlying `ScrollView`.
    */
@@ -178,7 +181,7 @@ class WindowedListView extends React.Component<Props, State> {
      * error is because an exported function parameter is missing an
      * annotation. Without an annotation, these parameters are uncovered by
      * Flow. */
-    renderScrollComponent: (props) => <ScrollView {...props} />,
+    renderScrollComponent: props => <ScrollView {...props} />,
     disableIncrementalRendering: false,
     recomputeRowsBatchingPeriod: 10, // This should capture most events that happen within a frame
   };
@@ -187,7 +190,7 @@ class WindowedListView extends React.Component<Props, State> {
     super(props);
     invariant(
       this.props.numToRenderAhead < this.props.maxNumToRender,
-      'WindowedListView: numToRenderAhead must be less than maxNumToRender'
+      'WindowedListView: numToRenderAhead must be less than maxNumToRender',
     );
     this._computeRowsToRenderBatcher = new Batchinator(
       () => this._computeRowsToRender(this.props),
@@ -198,13 +201,16 @@ class WindowedListView extends React.Component<Props, State> {
     });
     this.state = {
       firstRow: 0,
-      lastRow: Math.min(this.props.data.length, this.props.initialNumToRender) - 1,
+      lastRow:
+        Math.min(this.props.data.length, this.props.initialNumToRender) - 1,
     };
   }
   getScrollResponder(): ?ScrollView {
-    return this._scrollRef &&
+    return (
+      this._scrollRef &&
       this._scrollRef.getScrollResponder &&
-      this._scrollRef.getScrollResponder();
+      this._scrollRef.getScrollResponder()
+    );
   }
   shouldComponentUpdate(newProps: Props, newState: State): boolean {
     DEBUG && infoLog('WLV: shouldComponentUpdate...');
@@ -218,22 +224,33 @@ class WindowedListView extends React.Component<Props, State> {
         return true;
       }
     }
-    const newDataSubset = newProps.data.slice(newState.firstRow, newState.lastRow + 1);
-    const prevDataSubset = this.props.data.slice(this.state.firstRow, this.state.lastRow + 1);
+    const newDataSubset = newProps.data.slice(
+      newState.firstRow,
+      newState.lastRow + 1,
+    );
+    const prevDataSubset = this.props.data.slice(
+      this.state.firstRow,
+      this.state.lastRow + 1,
+    );
     if (newDataSubset.length !== prevDataSubset.length) {
-      DEBUG && infoLog(
-        '  yes, subset length: ',
-        {newLen: newDataSubset.length, oldLen: prevDataSubset.length}
-      );
+      DEBUG &&
+        infoLog('  yes, subset length: ', {
+          newLen: newDataSubset.length,
+          oldLen: prevDataSubset.length,
+        });
       return true;
     }
     for (let idx = 0; idx < newDataSubset.length; idx++) {
-      if (newDataSubset[idx].rowData !== prevDataSubset[idx].rowData ||
-          newDataSubset[idx].rowKey !== prevDataSubset[idx].rowKey) {
-        DEBUG && infoLog(
-          '  yes, data change: ',
-          {idx, new: newDataSubset[idx], old: prevDataSubset[idx]}
-        );
+      if (
+        newDataSubset[idx].rowData !== prevDataSubset[idx].rowData ||
+        newDataSubset[idx].rowKey !== prevDataSubset[idx].rowKey
+      ) {
+        DEBUG &&
+          infoLog('  yes, data change: ', {
+            idx,
+            new: newDataSubset[idx],
+            old: prevDataSubset[idx],
+          });
         return true;
       }
     }
@@ -249,7 +266,7 @@ class WindowedListView extends React.Component<Props, State> {
   _getFrameMetrics = (index: number): ?{length: number, offset: number} => {
     const frame = this._rowFrames[this.props.data[index].rowKey];
     return frame && {length: frame.height, offset: frame.y};
-  }
+  };
   _onScroll = (e: Object) => {
     const newScrollY = e.nativeEvent.contentOffset.y;
     this._isScrolling = this._scrollOffsetY !== newScrollY;
@@ -260,7 +277,10 @@ class WindowedListView extends React.Component<Props, State> {
     if (this._cellsInProgress.size === 0) {
       this._computeRowsToRenderBatcher.schedule();
     }
-    if (this.props.onViewableRowsChanged && Object.keys(this._rowFrames).length) {
+    if (
+      this.props.onViewableRowsChanged &&
+      Object.keys(this._rowFrames).length
+    ) {
       const viewableRows = this._viewabilityHelper.computeViewableItems(
         this.props.data.length,
         e.nativeEvent.contentOffset.y,
@@ -279,19 +299,26 @@ class WindowedListView extends React.Component<Props, State> {
     const {rowKey, layout} = params;
     if (DEBUG) {
       const prev = this._rowFrames[rowKey] || {};
-      infoLog(
-        'record layout for row: ',
-        {k: rowKey, h: layout.height, y: layout.y, x: layout.x, hp: prev.height, yp: prev.y}
-      );
+      infoLog('record layout for row: ', {
+        k: rowKey,
+        h: layout.height,
+        y: layout.y,
+        x: layout.x,
+        hp: prev.height,
+        yp: prev.y,
+      });
       if (this._rowFrames[rowKey]) {
         const deltaY = Math.abs(this._rowFrames[rowKey].y - layout.y);
         const deltaH = Math.abs(this._rowFrames[rowKey].height - layout.height);
         if (deltaY > 2 || deltaH > 2) {
-          const dataEntry = this.props.data.find((datum) => datum.rowKey === rowKey);
-          console.warn(
-            'layout jump: ',
-            {dataEntry, prevLayout: this._rowFrames[rowKey], newLayout: layout}
+          const dataEntry = this.props.data.find(
+            datum => datum.rowKey === rowKey,
           );
+          console.warn('layout jump: ', {
+            dataEntry,
+            prevLayout: this._rowFrames[rowKey],
+            newLayout: layout,
+          });
         }
       }
     }
@@ -311,7 +338,13 @@ class WindowedListView extends React.Component<Props, State> {
    * This is used to keep track of cells that are in the process of rendering. If any cells are in
    * progress, then other updates are skipped because they will just be wasted work.
    */
-  _onProgressChange = ({rowKey, inProgress}: {rowKey: string, inProgress: boolean}) => {
+  _onProgressChange = ({
+    rowKey,
+    inProgress,
+  }: {
+    rowKey: string,
+    inProgress: boolean,
+  }) => {
     if (inProgress) {
       this._cellsInProgress.add(rowKey);
     } else {
@@ -343,7 +376,7 @@ class WindowedListView extends React.Component<Props, State> {
         // No frame - sometimes happens when they come out of order, so just wait for the rest.
         return;
       }
-      if (((frame.y + frame.height) > top) && (firstVisible < 0)) {
+      if (frame.y + frame.height > top && firstVisible < 0) {
         firstVisible = idx;
       }
       if (frame.y < bottom) {
@@ -390,7 +423,7 @@ class WindowedListView extends React.Component<Props, State> {
     if (props.onEndReached) {
       // Make sure we call onEndReached exactly once every time we reach the
       // end.  Resets if scroll back up and down again.
-      const willBeAtTheEnd = lastRow === (totalRows - 1);
+      const willBeAtTheEnd = lastRow === totalRows - 1;
       if (willBeAtTheEnd && !this._hasCalledOnEndReached) {
         props.onEndReached();
         this._hasCalledOnEndReached = true;
@@ -399,15 +432,18 @@ class WindowedListView extends React.Component<Props, State> {
         this._hasCalledOnEndReached = this.state.lastRow === lastRow;
       }
     }
-    const rowsShouldChange = firstRow !== this.state.firstRow || lastRow !== this.state.lastRow;
+    const rowsShouldChange =
+      firstRow !== this.state.firstRow || lastRow !== this.state.lastRow;
     if (this._rowFramesDirty || rowsShouldChange) {
       if (rowsShouldChange) {
         props.onMountedRowsWillChange &&
           props.onMountedRowsWillChange(firstRow, lastRow - firstRow + 1);
-        infoLog(
-          'WLV: row render range will change:',
-          {firstRow, firstVis: this._firstVisible, lastVis: this._lastVisible, lastRow},
-        );
+        infoLog('WLV: row render range will change:', {
+          firstRow,
+          firstVis: this._firstVisible,
+          lastVis: this._lastVisible,
+          lastRow,
+        });
       }
       this._rowFramesDirty = false;
       this.setState({firstRow, lastRow});
@@ -415,9 +451,14 @@ class WindowedListView extends React.Component<Props, State> {
   }
   _updateVisibleRows(newFirstVisible: number, newLastVisible: number) {
     if (this.props.onVisibleRowsChanged) {
-      if (this._firstVisible !== newFirstVisible ||
-          this._lastVisible !== newLastVisible) {
-        this.props.onVisibleRowsChanged(newFirstVisible, newLastVisible - newFirstVisible + 1);
+      if (
+        this._firstVisible !== newFirstVisible ||
+        this._lastVisible !== newLastVisible
+      ) {
+        this.props.onVisibleRowsChanged(
+          newFirstVisible,
+          newLastVisible - newFirstVisible + 1,
+        );
       }
     }
     this._firstVisible = newFirstVisible;
@@ -435,14 +476,17 @@ class WindowedListView extends React.Component<Props, State> {
     // catch up as fast as possible. In the middle, we only disable incremental while scrolling
     // since it's unlikely the user will try to press a button while scrolling. We also ignore the
     // "buffer" size when we are bumped up against the edge of the available data.
-    const firstBuffer = firstRow === 0 ? Infinity : this._firstVisible - firstRow;
-    const lastBuffer = lastRow === this.props.data.length - 1
-      ? Infinity
-      : lastRow - this._lastVisible;
+    const firstBuffer =
+      firstRow === 0 ? Infinity : this._firstVisible - firstRow;
+    const lastBuffer =
+      lastRow === this.props.data.length - 1
+        ? Infinity
+        : lastRow - this._lastVisible;
     const minBuffer = Math.min(firstBuffer, lastBuffer);
-    const disableIncrementalRendering = this.props.disableIncrementalRendering ||
+    const disableIncrementalRendering =
+      this.props.disableIncrementalRendering ||
       (this._isScrolling && minBuffer < this.props.numToRenderAhead * 0.5) ||
-      (minBuffer < this.props.numToRenderAhead * 0.25);
+      minBuffer < this.props.numToRenderAhead * 0.25;
     // Render mode is sticky while the component is mounted.
     for (let ii = firstRow; ii <= lastRow; ii++) {
       const rowKey = this.props.data[ii].rowKey;
@@ -463,7 +507,10 @@ class WindowedListView extends React.Component<Props, State> {
       // Look for the first row where offscreen layout is done (only true for mounted rows) or it
       // will be rendered synchronously and set the spacer height such that it will offset all the
       // unmounted rows before that one using the saved frame data.
-      if (rowFrames[rowKey].offscreenLayoutDone || this._rowRenderMode[rowKey] === 'sync') {
+      if (
+        rowFrames[rowKey].offscreenLayoutDone ||
+        this._rowRenderMode[rowKey] === 'sync'
+      ) {
         if (ii > 0) {
           const prevRowKey = this.props.data[ii - 1].rowKey;
           const frame = rowFrames[prevRowKey];
@@ -490,20 +537,22 @@ class WindowedListView extends React.Component<Props, State> {
         <View
           style={!showIndicator && styles.remove}
           key="ind-top"
-          onLayout={(e) => {
+          onLayout={e => {
             const layout = e.nativeEvent.layout;
             if (layout.height !== this.state.boundaryIndicatorHeight) {
               this.setState({boundaryIndicatorHeight: layout.height});
             }
           }}>
           {this.props.renderWindowBoundaryIndicator(showIndicator)}
-        </View>
+        </View>,
       );
     }
     for (let idx = firstRow; idx <= lastRow; idx++) {
       const rowKey = this.props.data[idx].rowKey;
-      const includeInLayout = this._rowRenderMode[rowKey] === 'sync' ||
-        (this._rowFrames[rowKey] && this._rowFrames[rowKey].offscreenLayoutDone);
+      const includeInLayout =
+        this._rowRenderMode[rowKey] === 'sync' ||
+        (this._rowFrames[rowKey] &&
+          this._rowFrames[rowKey].offscreenLayoutDone);
       rows.push(
         <CellRenderer
           key={rowKey}
@@ -516,20 +565,21 @@ class WindowedListView extends React.Component<Props, State> {
           asyncRowPerfEventName={this.props.asyncRowPerfEventName}
           rowData={this.props.data[idx].rowData}
           renderRow={this.props.renderRow}
-        />
+        />,
       );
     }
     const lastRowKey = this.props.data[lastRow].rowKey;
-    const showFooter = this._rowFrames[lastRowKey] &&
-        this._rowFrames[lastRowKey].offscreenLayoutDone &&
-        lastRow === this.props.data.length - 1;
+    const showFooter =
+      this._rowFrames[lastRowKey] &&
+      this._rowFrames[lastRowKey].offscreenLayoutDone &&
+      lastRow === this.props.data.length - 1;
     if (this.props.renderFooter) {
       rows.push(
         <View
           key="ind-footer"
           style={showFooter ? styles.include : styles.remove}>
           {this.props.renderFooter(showFooter)}
-        </View>
+        </View>,
       );
     }
     if (this.props.renderWindowBoundaryIndicator) {
@@ -537,30 +587,30 @@ class WindowedListView extends React.Component<Props, State> {
         <View
           key="ind-bot"
           style={showFooter ? styles.remove : styles.include}
-          onLayout={(e) => {
+          onLayout={e => {
             const layout = e.nativeEvent.layout;
             if (layout.height !== this.state.boundaryIndicatorHeight) {
               this.setState({boundaryIndicatorHeight: layout.height});
             }
           }}>
           {this.props.renderWindowBoundaryIndicator(!showFooter)}
-        </View>
+        </View>,
       );
     }
     // Prevent user from scrolling into empty space of unmounted rows.
     const contentInset = {top: firstRow === 0 ? 0 : -spacerHeight};
-    return (
-      this.props.renderScrollComponent({
-        scrollEventThrottle: 50,
-        removeClippedSubviews: true,
-        ...this.props,
-        contentInset,
-        ref: (ref) => { this._scrollRef = ref; },
-        onScroll: this._onScroll,
-        onMomentumScrollEnd: this._onMomentumScrollEnd,
-        children: rows,
-      })
-    );
+    return this.props.renderScrollComponent({
+      scrollEventThrottle: 50,
+      removeClippedSubviews: true,
+      ...this.props,
+      contentInset,
+      ref: ref => {
+        this._scrollRef = ref;
+      },
+      onScroll: this._onScroll,
+      onMomentumScrollEnd: this._onMomentumScrollEnd,
+      children: rows,
+    });
   }
 }
 
@@ -576,9 +626,12 @@ type CellProps = {
   /**
    * Renders the actual row contents.
    */
-   renderRow: (
-      rowData: mixed, sectionIdx: number, rowIdx: number, rowKey: string
-   ) => ?React.Element<any>,
+  renderRow: (
+    rowData: mixed,
+    sectionIdx: number,
+    rowIdx: number,
+    rowKey: string,
+  ) => ?React.Element<any>,
   /**
    * Index of the row, passed through to other callbacks.
    */
@@ -625,18 +678,21 @@ class CellRenderer extends React.Component<CellProps> {
     if (this.props.asyncRowPerfEventName) {
       this._perfUpdateID = g_perf_update_id++;
       this._asyncCookie = Systrace.beginAsyncEvent(
-        this.props.asyncRowPerfEventName + this._perfUpdateID
+        this.props.asyncRowPerfEventName + this._perfUpdateID,
+      );
+      infoLog(
+        // $FlowFixMe(>=0.28.0)
+        `perf_asynctest_${this.props.asyncRowPerfEventName}_start ${
+          this._perfUpdateID
+        } ` + `${Date.now()}`,
       );
-      // $FlowFixMe(>=0.28.0)
-      infoLog(`perf_asynctest_${this.props.asyncRowPerfEventName}_start ${this._perfUpdateID} ` +
-        `${Date.now()}`);
     }
     if (this.props.includeInLayout) {
       this._includeInLayoutLatch = true;
     }
     this.props.onProgressChange({rowKey: this.props.rowKey, inProgress: true});
   }
-  _onLayout = (e) => {
+  _onLayout = e => {
     const layout = e.nativeEvent.layout;
     const layoutChanged = deepDiffer(this._lastLayout, layout);
     this._lastLayout = layout;
@@ -660,19 +716,26 @@ class CellRenderer extends React.Component<CellProps> {
     // This happens when Incremental is disabled and _onOffscreenRenderDone is called faster than
     // layout can happen.
     this._lastLayout &&
-      this.props.onNewLayout({rowKey: this.props.rowKey, layout: this._lastLayout});
+      this.props.onNewLayout({
+        rowKey: this.props.rowKey,
+        layout: this._lastLayout,
+      });
 
-    DEBUG && infoLog('\n   >>>>>  display row ' + this.props.rowIndex + '\n\n\n');
+    DEBUG &&
+      infoLog('\n   >>>>>  display row ' + this.props.rowIndex + '\n\n\n');
     if (this.props.asyncRowPerfEventName) {
       // Note this doesn't include the native render time but is more accurate than also including
       // the JS render time of anything that has been queued up.
       Systrace.endAsyncEvent(
         this.props.asyncRowPerfEventName + this._perfUpdateID,
-        this._asyncCookie
+        this._asyncCookie,
+      );
+      infoLog(
+        // $FlowFixMe(>=0.28.0)
+        `perf_asynctest_${this.props.asyncRowPerfEventName}_end ${
+          this._perfUpdateID
+        } ` + `${Date.now()}`,
       );
-      // $FlowFixMe(>=0.28.0)
-      infoLog(`perf_asynctest_${this.props.asyncRowPerfEventName}_end ${this._perfUpdateID} ` +
-        `${Date.now()}`);
     }
   }
   _onOffscreenRenderDone = () => {
@@ -693,7 +756,10 @@ class CellRenderer extends React.Component<CellProps> {
   }
   UNSAFE_componentWillReceiveProps(newProps) {
     if (newProps.includeInLayout && !this.props.includeInLayout) {
-      invariant(this._offscreenRenderDone, 'Should never try to add to layout before render done');
+      invariant(
+        this._offscreenRenderDone,
+        'Should never try to add to layout before render done',
+      );
       this._includeInLayoutLatch = true; // Once we render in layout, make sure it sticks.
       this._containerRef.setNativeProps({style: styles.include});
     }
@@ -701,7 +767,7 @@ class CellRenderer extends React.Component<CellProps> {
   shouldComponentUpdate(newProps: CellProps) {
     return newProps.rowData !== this.props.rowData;
   }
-  _setRef = (ref) => {
+  _setRef = ref => {
     /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This comment
      * suppresses an error when upgrading Flow's support for React. To see the
      * error delete this comment and run Flow. */
@@ -712,9 +778,11 @@ class CellRenderer extends React.Component<CellProps> {
     if (DEBUG) {
       infoLog('render cell ' + this.props.rowIndex);
       const Text = require('Text');
-      debug = <Text style={{backgroundColor: 'lightblue'}}>
-        Row: {this.props.rowIndex}
-      </Text>;
+      debug = (
+        <Text style={{backgroundColor: 'lightblue'}}>
+          Row: {this.props.rowIndex}
+        </Text>
+      );
     }
     const style = this._includeInLayoutLatch ? styles.include : styles.remove;
     return (
@@ -722,12 +790,14 @@ class CellRenderer extends React.Component<CellProps> {
         disabled={this._includeInLayoutLatch}
         onDone={this._onOffscreenRenderDone}
         name={`WLVCell_${this.props.rowIndex}`}>
-        <View
-          ref={this._setRef}
-          style={style}
-          onLayout={this._onLayout}>
+        <View ref={this._setRef} style={style} onLayout={this._onLayout}>
           {debug}
-          {this.props.renderRow(this.props.rowData, 0, this.props.rowIndex, this.props.rowKey)}
+          {this.props.renderRow(
+            this.props.rowData,
+            0,
+            this.props.rowIndex,
+            this.props.rowKey,
+          )}
           {debug}
         </View>
       </IncrementalGroup>
diff --git a/Libraries/Geolocation/Geolocation.js b/Libraries/Geolocation/Geolocation.js
index 8bdc212636be..d252da95bca5 100644
--- a/Libraries/Geolocation/Geolocation.js
+++ b/Libraries/Geolocation/Geolocation.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeEventEmitter = require('NativeEventEmitter');
@@ -27,16 +29,16 @@ let subscriptions = [];
 let updatesEnabled = false;
 
 type GeoConfiguration = {
-  skipPermissionRequests: bool;
-}
+  skipPermissionRequests: boolean,
+};
 
 type GeoOptions = {
   timeout?: number,
   maximumAge?: number,
-  enableHighAccuracy?: bool,
+  enableHighAccuracy?: boolean,
   distanceFilter: number,
-  useSignificantChanges?: bool,
-}
+  useSignificantChanges?: boolean,
+};
 
 /**
  * The Geolocation API extends the web spec:
@@ -45,16 +47,13 @@ type GeoOptions = {
  * See https://facebook.github.io/react-native/docs/geolocation.html
  */
 const Geolocation = {
-
   /*
     * Sets configuration options that will be used in all location requests.
     *
     * See https://facebook.github.io/react-native/docs/geolocation.html#setrnconfiguration
     *
     */
-  setRNConfiguration: function(
-    config: GeoConfiguration
-  ) {
+  setRNConfiguration: function(config: GeoConfiguration) {
     if (RCTLocationObserver.setConfiguration) {
       RCTLocationObserver.setConfiguration(config);
     }
@@ -77,11 +76,11 @@ const Geolocation = {
   getCurrentPosition: async function(
     geo_success: Function,
     geo_error?: Function,
-    geo_options?: GeoOptions
+    geo_options?: GeoOptions,
   ) {
     invariant(
       typeof geo_success === 'function',
-      'Must provide a valid geo_success callback.'
+      'Must provide a valid geo_success callback.',
     );
     let hasPermission = true;
     // Supports Android's new permission model. For Android older devices,
@@ -111,21 +110,21 @@ const Geolocation = {
    *
    * See https://facebook.github.io/react-native/docs/geolocation.html#watchposition
    */
-  watchPosition: function(success: Function, error?: Function, options?: GeoOptions): number {
+  watchPosition: function(
+    success: Function,
+    error?: Function,
+    options?: GeoOptions,
+  ): number {
     if (!updatesEnabled) {
       RCTLocationObserver.startObserving(options || {});
       updatesEnabled = true;
     }
     const watchID = subscriptions.length;
     subscriptions.push([
-      LocationEventEmitter.addListener(
-        'geolocationDidChange',
-        success
-      ),
-      error ? LocationEventEmitter.addListener(
-        'geolocationError',
-        error
-      ) : null,
+      LocationEventEmitter.addListener('geolocationDidChange', success),
+      error
+        ? LocationEventEmitter.addListener('geolocationError', error)
+        : null,
     ]);
     return watchID;
   },
@@ -140,7 +139,8 @@ const Geolocation = {
 
     sub[0].remove();
     // array element refinements not yet enabled in Flow
-    const sub1 = sub[1]; sub1 && sub1.remove();
+    const sub1 = sub[1];
+    sub1 && sub1.remove();
     subscriptions[watchID] = undefined;
     let noWatchers = true;
     for (let ii = 0; ii < subscriptions.length; ii++) {
@@ -163,12 +163,13 @@ const Geolocation = {
           warning(false, 'Called stopObserving with existing subscriptions.');
           sub[0].remove();
           // array element refinements not yet enabled in Flow
-          const sub1 = sub[1]; sub1 && sub1.remove();
+          const sub1 = sub[1];
+          sub1 && sub1.remove();
         }
       }
       subscriptions = [];
     }
-  }
+  },
 };
 
 module.exports = Geolocation;
diff --git a/Libraries/Image/AssetSourceResolver.js b/Libraries/Image/AssetSourceResolver.js
index 6ae1a7801d09..a870a3252428 100644
--- a/Libraries/Image/AssetSourceResolver.js
+++ b/Libraries/Image/AssetSourceResolver.js
@@ -40,7 +40,10 @@ function getScaledAssetPath(asset): string {
  */
 function getAssetPathInDrawableFolder(asset): string {
   const scale = AssetSourceResolver.pickScale(asset.scales, PixelRatio.get());
-  const drawbleFolder = assetPathUtils.getAndroidResourceFolderName(asset, scale);
+  const drawbleFolder = assetPathUtils.getAndroidResourceFolderName(
+    asset,
+    scale,
+  );
   const fileName = assetPathUtils.getAndroidResourceIdentifier(asset);
   return drawbleFolder + '/' + fileName + '.' + asset.type;
 }
diff --git a/Libraries/Image/RelativeImageStub.js b/Libraries/Image/RelativeImageStub.js
index 1a74c36cb1bd..ab845a274d27 100644
--- a/Libraries/Image/RelativeImageStub.js
+++ b/Libraries/Image/RelativeImageStub.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a stub for flow to make it understand require('./icon.png')
diff --git a/Libraries/Image/__tests__/assetRelativePathInSnapshot.js b/Libraries/Image/__tests__/assetRelativePathInSnapshot.js
index 262e636b4710..973d7171c0cd 100644
--- a/Libraries/Image/__tests__/assetRelativePathInSnapshot.js
+++ b/Libraries/Image/__tests__/assetRelativePathInSnapshot.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 jest.disableAutomock();
@@ -16,10 +18,12 @@ const Image = require('Image');
 const View = require('View');
 
 it('renders assets based on relative path', () => {
-  expect(ReactTestRenderer.create(
-  <View>
-    <Image source={require('./img/img1.png')} />
-    <Image source={require('./img/img2.png')} />
-  </View>
-  )).toMatchSnapshot();
+  expect(
+    ReactTestRenderer.create(
+      <View>
+        <Image source={require('./img/img1.png')} />
+        <Image source={require('./img/img2.png')} />
+      </View>,
+    ),
+  ).toMatchSnapshot();
 });
diff --git a/Libraries/Image/__tests__/resolveAssetSource-test.js b/Libraries/Image/__tests__/resolveAssetSource-test.js
index db1a0a853d99..c22f32a65204 100644
--- a/Libraries/Image/__tests__/resolveAssetSource-test.js
+++ b/Libraries/Image/__tests__/resolveAssetSource-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const AssetRegistry = require('AssetRegistry');
@@ -32,12 +34,14 @@ describe('resolveAssetSource', () => {
   });
 
   it('does not change deprecated assets', () => {
-    expect(resolveAssetSource({
-      deprecated: true,
-      width: 100,
-      height: 200,
-      uri: 'logo',
-    })).toEqual({
+    expect(
+      resolveAssetSource({
+        deprecated: true,
+        width: 100,
+        height: 200,
+        uri: 'logo',
+      }),
+    ).toEqual({
       deprecated: true,
       width: 100,
       height: 200,
@@ -53,51 +57,57 @@ describe('resolveAssetSource', () => {
 
   describe('bundle was loaded from network (DEV)', () => {
     beforeEach(() => {
-      NativeModules.SourceCode.scriptURL =
-        'http://10.0.0.1:8081/main.bundle';
+      NativeModules.SourceCode.scriptURL = 'http://10.0.0.1:8081/main.bundle';
       Platform.OS = 'ios';
     });
 
     it('uses network image', () => {
-      expectResolvesAsset({
-        __packager_asset: true,
-        fileSystemLocation: '/root/app/module/a',
-        httpServerLocation: '/assets/module/a',
-        width: 100,
-        height: 200,
-        scales: [1],
-        hash: '5b6f00f',
-        name: 'logo',
-        type: 'png',
-      }, {
-        __packager_asset: true,
-        width: 100,
-        height: 200,
-        uri: 'http://10.0.0.1:8081/assets/module/a/logo.png?platform=ios&hash=5b6f00f',
-        scale: 1,
-      });
+      expectResolvesAsset(
+        {
+          __packager_asset: true,
+          fileSystemLocation: '/root/app/module/a',
+          httpServerLocation: '/assets/module/a',
+          width: 100,
+          height: 200,
+          scales: [1],
+          hash: '5b6f00f',
+          name: 'logo',
+          type: 'png',
+        },
+        {
+          __packager_asset: true,
+          width: 100,
+          height: 200,
+          uri:
+            'http://10.0.0.1:8081/assets/module/a/logo.png?platform=ios&hash=5b6f00f',
+          scale: 1,
+        },
+      );
     });
 
     it('picks matching scale', () => {
-      expectResolvesAsset({
-        __packager_asset: true,
-        fileSystemLocation: '/root/app/module/a',
-        httpServerLocation: '/assets/module/a',
-        width: 100,
-        height: 200,
-        scales: [1, 2, 3],
-        hash: '5b6f00f',
-        name: 'logo',
-        type: 'png',
-      }, {
-        __packager_asset: true,
-        width: 100,
-        height: 200,
-        uri: 'http://10.0.0.1:8081/assets/module/a/logo@2x.png?platform=ios&hash=5b6f00f',
-        scale: 2,
-      });
+      expectResolvesAsset(
+        {
+          __packager_asset: true,
+          fileSystemLocation: '/root/app/module/a',
+          httpServerLocation: '/assets/module/a',
+          width: 100,
+          height: 200,
+          scales: [1, 2, 3],
+          hash: '5b6f00f',
+          name: 'logo',
+          type: 'png',
+        },
+        {
+          __packager_asset: true,
+          width: 100,
+          height: 200,
+          uri:
+            'http://10.0.0.1:8081/assets/module/a/logo@2x.png?platform=ios&hash=5b6f00f',
+          scale: 2,
+        },
+      );
     });
-
   });
 
   describe('bundle was loaded from file on iOS', () => {
@@ -108,23 +118,26 @@ describe('resolveAssetSource', () => {
     });
 
     it('uses pre-packed image', () => {
-      expectResolvesAsset({
-        __packager_asset: true,
-        fileSystemLocation: '/root/app/module/a',
-        httpServerLocation: '/assets/module/a',
-        width: 100,
-        height: 200,
-        scales: [1],
-        hash: '5b6f00f',
-        name: 'logo',
-        type: 'png',
-      }, {
-        __packager_asset: true,
-        width: 100,
-        height: 200,
-        uri: 'file:///Path/To/Sample.app/assets/module/a/logo.png',
-        scale: 1,
-      });
+      expectResolvesAsset(
+        {
+          __packager_asset: true,
+          fileSystemLocation: '/root/app/module/a',
+          httpServerLocation: '/assets/module/a',
+          width: 100,
+          height: 200,
+          scales: [1],
+          hash: '5b6f00f',
+          name: 'logo',
+          type: 'png',
+        },
+        {
+          __packager_asset: true,
+          width: 100,
+          height: 200,
+          uri: 'file:///Path/To/Sample.app/assets/module/a/logo.png',
+          scale: 1,
+        },
+      );
     });
   });
 
@@ -136,23 +149,26 @@ describe('resolveAssetSource', () => {
     });
 
     it('uses pre-packed image', () => {
-      expectResolvesAsset({
-        __packager_asset: true,
-        fileSystemLocation: '/root/app/module/a',
-        httpServerLocation: '/assets/AwesomeModule/Subdir',
-        width: 100,
-        height: 200,
-        scales: [1],
-        hash: '5b6f00f',
-        name: '!@Logo#1_\u20ac', // Invalid chars shouldn't get passed to native
-        type: 'png',
-      }, {
-        __packager_asset: true,
-        width: 100,
-        height: 200,
-        uri: 'awesomemodule_subdir_logo1_',
-        scale: 1,
-      });
+      expectResolvesAsset(
+        {
+          __packager_asset: true,
+          fileSystemLocation: '/root/app/module/a',
+          httpServerLocation: '/assets/AwesomeModule/Subdir',
+          width: 100,
+          height: 200,
+          scales: [1],
+          hash: '5b6f00f',
+          name: '!@Logo#1_\u20ac', // Invalid chars shouldn't get passed to native
+          type: 'png',
+        },
+        {
+          __packager_asset: true,
+          width: 100,
+          height: 200,
+          uri: 'awesomemodule_subdir_logo1_',
+          scale: 1,
+        },
+      );
     });
   });
 
@@ -164,23 +180,27 @@ describe('resolveAssetSource', () => {
     });
 
     it('uses pre-packed image', () => {
-      expectResolvesAsset({
-        __packager_asset: true,
-        fileSystemLocation: '/root/app/module/a',
-        httpServerLocation: '/assets/AwesomeModule/Subdir',
-        width: 100,
-        height: 200,
-        scales: [1],
-        hash: '5b6f00f',
-        name: '!@Logo#1_\u20ac',
-        type: 'png',
-      }, {
-        __packager_asset: true,
-        width: 100,
-        height: 200,
-        uri: 'file:///sdcard/Path/To/Simulator/drawable-mdpi/awesomemodule_subdir_logo1_.png',
-        scale: 1,
-      });
+      expectResolvesAsset(
+        {
+          __packager_asset: true,
+          fileSystemLocation: '/root/app/module/a',
+          httpServerLocation: '/assets/AwesomeModule/Subdir',
+          width: 100,
+          height: 200,
+          scales: [1],
+          hash: '5b6f00f',
+          name: '!@Logo#1_\u20ac',
+          type: 'png',
+        },
+        {
+          __packager_asset: true,
+          width: 100,
+          height: 200,
+          uri:
+            'file:///sdcard/Path/To/Simulator/drawable-mdpi/awesomemodule_subdir_logo1_.png',
+          scale: 1,
+        },
+      );
     });
   });
 
@@ -192,23 +212,27 @@ describe('resolveAssetSource', () => {
     });
 
     it('uses sideloaded image', () => {
-      expectResolvesAsset({
-        __packager_asset: true,
-        fileSystemLocation: '/root/app/module/a',
-        httpServerLocation: '/assets/AwesomeModule/Subdir',
-        width: 100,
-        height: 200,
-        scales: [1],
-        hash: '5b6f00f',
-        name: '!@Logo#1_\u20ac',
-        type: 'png',
-      }, {
-        __packager_asset: true,
-        width: 100,
-        height: 200,
-        uri: 'file:///sdcard/Path/To/Simulator/drawable-mdpi/awesomemodule_subdir_logo1_.png',
-        scale: 1,
-      });
+      expectResolvesAsset(
+        {
+          __packager_asset: true,
+          fileSystemLocation: '/root/app/module/a',
+          httpServerLocation: '/assets/AwesomeModule/Subdir',
+          width: 100,
+          height: 200,
+          scales: [1],
+          hash: '5b6f00f',
+          name: '!@Logo#1_\u20ac',
+          type: 'png',
+        },
+        {
+          __packager_asset: true,
+          width: 100,
+          height: 200,
+          uri:
+            'file:///sdcard/Path/To/Simulator/drawable-mdpi/awesomemodule_subdir_logo1_.png',
+          scale: 1,
+        },
+      );
     });
   });
 
@@ -220,52 +244,57 @@ describe('resolveAssetSource', () => {
     });
 
     it('uses bundled source, event when js is sideloaded', () => {
-      resolveAssetSource.setCustomSourceTransformer(
-        (resolver) => resolver.resourceIdentifierWithoutScale(),
+      resolveAssetSource.setCustomSourceTransformer(resolver =>
+        resolver.resourceIdentifierWithoutScale(),
+      );
+      expectResolvesAsset(
+        {
+          __packager_asset: true,
+          fileSystemLocation: '/root/app/module/a',
+          httpServerLocation: '/assets/AwesomeModule/Subdir',
+          width: 100,
+          height: 200,
+          scales: [1],
+          hash: '5b6f00f',
+          name: '!@Logo#1_\u20ac',
+          type: 'png',
+        },
+        {
+          __packager_asset: true,
+          width: 100,
+          height: 200,
+          uri: 'awesomemodule_subdir_logo1_',
+          scale: 1,
+        },
       );
-      expectResolvesAsset({
-        __packager_asset: true,
-        fileSystemLocation: '/root/app/module/a',
-        httpServerLocation: '/assets/AwesomeModule/Subdir',
-        width: 100,
-        height: 200,
-        scales: [1],
-        hash: '5b6f00f',
-        name: '!@Logo#1_\u20ac',
-        type: 'png',
-      }, {
-        __packager_asset: true,
-        width: 100,
-        height: 200,
-        uri: 'awesomemodule_subdir_logo1_',
-        scale: 1,
-      });
     });
 
     it('allows any customization', () => {
-      resolveAssetSource.setCustomSourceTransformer(
-        (resolver) => resolver.fromSource('TEST')
+      resolveAssetSource.setCustomSourceTransformer(resolver =>
+        resolver.fromSource('TEST'),
+      );
+      expectResolvesAsset(
+        {
+          __packager_asset: true,
+          fileSystemLocation: '/root/app/module/a',
+          httpServerLocation: '/assets/AwesomeModule/Subdir',
+          width: 100,
+          height: 200,
+          scales: [1],
+          hash: '5b6f00f',
+          name: '!@Logo#1_\u20ac',
+          type: 'png',
+        },
+        {
+          __packager_asset: true,
+          width: 100,
+          height: 200,
+          uri: 'TEST',
+          scale: 1,
+        },
       );
-      expectResolvesAsset({
-        __packager_asset: true,
-        fileSystemLocation: '/root/app/module/a',
-        httpServerLocation: '/assets/AwesomeModule/Subdir',
-        width: 100,
-        height: 200,
-        scales: [1],
-        hash: '5b6f00f',
-        name: '!@Logo#1_\u20ac',
-        type: 'png',
-      }, {
-        __packager_asset: true,
-        width: 100,
-        height: 200,
-        uri: 'TEST',
-        scale: 1,
-      });
     });
   });
-
 });
 
 describe('resolveAssetSource.pickScale', () => {
diff --git a/Libraries/Image/resolveAssetSource.js b/Libraries/Image/resolveAssetSource.js
index fe483beff594..9c811e574400 100644
--- a/Libraries/Image/resolveAssetSource.js
+++ b/Libraries/Image/resolveAssetSource.js
@@ -4,16 +4,19 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
  *
  * Resolves an asset into a `source` for `Image`.
+ *
+ * @format
+ * @flow
  */
+
 'use strict';
 
 const AssetRegistry = require('AssetRegistry');
 const AssetSourceResolver = require('AssetSourceResolver');
 
-import type { ResolvedAssetSource } from 'AssetSourceResolver';
+import type {ResolvedAssetSource} from 'AssetSourceResolver';
 
 let _customSourceTransformer, _serverURL, _scriptURL;
 
@@ -23,7 +26,8 @@ function getSourceCodeScriptURL(): ?string {
     return _sourceCodeScriptURL;
   }
 
-  let sourceCode = global.nativeExtensions && global.nativeExtensions.SourceCode;
+  let sourceCode =
+    global.nativeExtensions && global.nativeExtensions.SourceCode;
   if (!sourceCode) {
     const NativeModules = require('NativeModules');
     sourceCode = NativeModules && NativeModules.SourceCode;
@@ -35,7 +39,8 @@ function getSourceCodeScriptURL(): ?string {
 function getDevServerURL(): ?string {
   if (_serverURL === undefined) {
     const sourceCodeScriptURL = getSourceCodeScriptURL();
-    const match = sourceCodeScriptURL && sourceCodeScriptURL.match(/^https?:\/\/.*?\//);
+    const match =
+      sourceCodeScriptURL && sourceCodeScriptURL.match(/^https?:\/\/.*?\//);
     if (match) {
       // jsBundle was loaded from network
       _serverURL = match[0];
diff --git a/Libraries/Inspector/BorderBox.js b/Libraries/Inspector/BorderBox.js
index 21ace69d9c90..b172871df8e2 100644
--- a/Libraries/Inspector/BorderBox.js
+++ b/Libraries/Inspector/BorderBox.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -23,13 +25,8 @@ class BorderBox extends React.Component<$FlowFixMeProps> {
       borderLeftWidth: box.left,
       borderRightWidth: box.right,
     };
-    return (
-      <View style={[style, this.props.style]}>
-        {this.props.children}
-      </View>
-    );
+    return <View style={[style, this.props.style]}>{this.props.children}</View>;
   }
 }
 
 module.exports = BorderBox;
-
diff --git a/Libraries/Inspector/BoxInspector.js b/Libraries/Inspector/BoxInspector.js
index 11fe9c8c9807..af3734600536 100644
--- a/Libraries/Inspector/BoxInspector.js
+++ b/Libraries/Inspector/BoxInspector.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -25,8 +27,8 @@ class BoxInspector extends React.Component<$FlowFixMeProps> {
   render() {
     const frame = this.props.frame;
     const style = this.props.style;
-    const margin = style && resolveBoxStyle('margin', style) || blank;
-    const padding = style && resolveBoxStyle('padding', style) || blank;
+    const margin = (style && resolveBoxStyle('margin', style)) || blank;
+    const padding = (style && resolveBoxStyle('padding', style)) || blank;
     return (
       <BoxContainer title="margin" titleStyle={styles.marginLabel} box={margin}>
         <BoxContainer title="padding" box={padding}>
@@ -35,7 +37,8 @@ class BoxInspector extends React.Component<$FlowFixMeProps> {
               ({(frame.left || 0).toFixed(1)}, {(frame.top || 0).toFixed(1)})
             </Text>
             <Text style={styles.innerText}>
-              {(frame.width || 0).toFixed(1)} &times; {(frame.height || 0).toFixed(1)}
+              {(frame.width || 0).toFixed(1)} &times;{' '}
+              {(frame.height || 0).toFixed(1)}
             </Text>
           </View>
         </BoxContainer>
@@ -50,9 +53,10 @@ class BoxContainer extends React.Component<$FlowFixMeProps> {
     return (
       <View style={styles.box}>
         <View style={styles.row}>
-          {
-            }
-          <Text style={[this.props.titleStyle, styles.label]}>{this.props.title}</Text>
+          {}
+          <Text style={[this.props.titleStyle, styles.label]}>
+            {this.props.title}
+          </Text>
           <Text style={styles.boxText}>{box.top}</Text>
         </View>
         <View style={styles.row}>
diff --git a/Libraries/Inspector/ElementBox.js b/Libraries/Inspector/ElementBox.js
index 17b2c8920e8e..e43233fb0dce 100644
--- a/Libraries/Inspector/ElementBox.js
+++ b/Libraries/Inspector/ElementBox.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -68,4 +70,3 @@ const styles = StyleSheet.create({
 });
 
 module.exports = ElementBox;
-
diff --git a/Libraries/Inspector/ElementProperties.js b/Libraries/Inspector/ElementProperties.js
index 75beaf93e233..1e360944716f 100644
--- a/Libraries/Inspector/ElementProperties.js
+++ b/Libraries/Inspector/ElementProperties.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const BoxInspector = require('BoxInspector');
@@ -79,16 +81,14 @@ class ElementProperties extends React.Component<{
                   style={[styles.breadItem, i === selection && styles.selected]}
                   // $FlowFixMe found when converting React.createClass to ES6
                   onPress={() => this.props.setSelection(i)}>
-                  <Text style={styles.breadItemText}>
-                    {hierarchyItem.name}
-                  </Text>
+                  <Text style={styles.breadItemText}>{hierarchyItem.name}</Text>
                 </TouchableHighlight>
               ),
-              (i) => (
+              i => (
                 <Text key={'sep-' + i} style={styles.breadSep}>
                   &#9656;
                 </Text>
-              )
+              ),
             )}
           </View>
           <View style={styles.row}>
@@ -98,7 +98,8 @@ class ElementProperties extends React.Component<{
             </View>
             {
               // $FlowFixMe found when converting React.createClass to ES6
-            <BoxInspector style={style} frame={this.props.frame} />}
+              <BoxInspector style={style} frame={this.props.frame} />
+            }
           </View>
         </View>
       </TouchableWithoutFeedback>
@@ -152,7 +153,7 @@ const styles = StyleSheet.create({
   openButtonTitle: {
     color: 'white',
     fontSize: 8,
-  }
+  },
 });
 
 module.exports = ElementProperties;
diff --git a/Libraries/Inspector/Inspector.js b/Libraries/Inspector/Inspector.js
index 73ce0719b36d..a5ab122b0cde 100644
--- a/Libraries/Inspector/Inspector.js
+++ b/Libraries/Inspector/Inspector.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -37,8 +38,13 @@ const renderers = findRenderers();
 hook.resolveRNStyle = require('flattenStyle');
 
 function findRenderers(): $ReadOnlyArray<ReactRenderer> {
-  const allRenderers = Object.keys(hook._renderers).map(key => hook._renderers[key]);
-  invariant(allRenderers.length >= 1, 'Expected to find at least one React Native renderer on DevTools hook.');
+  const allRenderers = Object.keys(hook._renderers).map(
+    key => hook._renderers[key],
+  );
+  invariant(
+    allRenderers.length >= 1,
+    'Expected to find at least one React Native renderer on DevTools hook.',
+  );
   return allRenderers;
 }
 
@@ -53,20 +59,23 @@ function getInspectorDataForViewTag(touchedViewTag: number) {
   throw new Error('Expected to find at least one React renderer.');
 }
 
-class Inspector extends React.Component<{
-  inspectedViewTag: ?number,
-  onRequestRerenderApp: (callback: (tag: ?number) => void) => void
-}, {
-  devtoolsAgent: ?Object,
-  hierarchy: any,
-  panelPos: string,
-  inspecting: bool,
-  selection: ?number,
-  perfing: bool,
-  inspected: any,
-  inspectedViewTag: any,
-  networking: bool,
-}> {
+class Inspector extends React.Component<
+  {
+    inspectedViewTag: ?number,
+    onRequestRerenderApp: (callback: (tag: ?number) => void) => void,
+  },
+  {
+    devtoolsAgent: ?Object,
+    hierarchy: any,
+    panelPos: string,
+    inspecting: boolean,
+    selection: ?number,
+    perfing: boolean,
+    inspected: any,
+    inspectedViewTag: any,
+    networking: boolean,
+  },
+> {
   _subs: ?Array<() => void>;
 
   constructor(props: Object) {
@@ -149,15 +158,12 @@ class Inspector extends React.Component<{
     });
   };
 
-
   setSelection(i: number) {
     const hierarchyItem = this.state.hierarchy[i];
     // we pass in ReactNative.findNodeHandle as the method is injected
-    const {
-      measure,
-      props,
-      source,
-    } = hierarchyItem.getInspectorData(ReactNative.findNodeHandle);
+    const {measure, props, source} = hierarchyItem.getInspectorData(
+      ReactNative.findNodeHandle,
+    );
 
     measure((x, y, width, height, left, top) => {
       this.setState({
@@ -175,21 +181,23 @@ class Inspector extends React.Component<{
     // Most likely the touched instance is a native wrapper (like RCTView)
     // which is not very interesting. Most likely user wants a composite
     // instance that contains it (like View)
-    const {
-      hierarchy,
-      props,
-      selection,
-      source,
-    } = getInspectorDataForViewTag(touchedViewTag);
+    const {hierarchy, props, selection, source} = getInspectorDataForViewTag(
+      touchedViewTag,
+    );
 
     if (this.state.devtoolsAgent) {
       // Skip host leafs
       const offsetFromLeaf = hierarchy.length - 1 - selection;
-      this.state.devtoolsAgent.selectFromDOMNode(touchedViewTag, true, offsetFromLeaf);
+      this.state.devtoolsAgent.selectFromDOMNode(
+        touchedViewTag,
+        true,
+        offsetFromLeaf,
+      );
     }
 
     this.setState({
-      panelPos: pointerY > Dimensions.get('window').height / 2 ? 'top' : 'bottom',
+      panelPos:
+        pointerY > Dimensions.get('window').height / 2 ? 'top' : 'bottom',
       selection,
       hierarchy,
       inspected: {
@@ -200,7 +208,7 @@ class Inspector extends React.Component<{
     });
   }
 
-  setPerfing(val: bool) {
+  setPerfing(val: boolean) {
     this.setState({
       perfing: val,
       inspecting: false,
@@ -209,21 +217,21 @@ class Inspector extends React.Component<{
     });
   }
 
-  setInspecting(val: bool) {
+  setInspecting(val: boolean) {
     this.setState({
       inspecting: val,
-      inspected: null
+      inspected: null,
     });
   }
 
-  setTouchTargeting(val: bool) {
+  setTouchTargeting(val: boolean) {
     Touchable.TOUCH_TARGET_DEBUG = val;
-    this.props.onRequestRerenderApp((inspectedViewTag) => {
+    this.props.onRequestRerenderApp(inspectedViewTag => {
       this.setState({inspectedViewTag});
     });
   }
 
-  setNetworking(val: bool) {
+  setNetworking(val: boolean) {
     this.setState({
       networking: val,
       perfing: false,
@@ -233,17 +241,19 @@ class Inspector extends React.Component<{
   }
 
   render() {
-    const panelContainerStyle = (this.state.panelPos === 'bottom') ?
-      {bottom: 0} :
-      {top: Platform.OS === 'ios' ? 20 : 0};
+    const panelContainerStyle =
+      this.state.panelPos === 'bottom'
+        ? {bottom: 0}
+        : {top: Platform.OS === 'ios' ? 20 : 0};
     return (
       <View style={styles.container} pointerEvents="box-none">
-        {this.state.inspecting &&
+        {this.state.inspecting && (
           <InspectorOverlay
             inspected={this.state.inspected}
             inspectedViewTag={this.state.inspectedViewTag}
             onTouchViewTag={this.onTouchViewTag.bind(this)}
-          />}
+          />
+        )}
         <View style={[styles.panelContainer, panelContainerStyle]}>
           <InspectorPanel
             devtoolsIsOpen={!!this.state.devtoolsAgent}
diff --git a/Libraries/Inspector/InspectorOverlay.js b/Libraries/Inspector/InspectorOverlay.js
index a2dda0b316c2..4de9cb2ab818 100644
--- a/Libraries/Inspector/InspectorOverlay.js
+++ b/Libraries/Inspector/InspectorOverlay.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Dimensions = require('Dimensions');
@@ -43,12 +45,16 @@ class InspectorOverlay extends React.Component<{
       this.props.inspectedViewTag,
       [locationX, locationY],
       (nativeViewTag, left, top, width, height) => {
-        this.props.onTouchViewTag(nativeViewTag, {left, top, width, height}, locationY);
-      }
+        this.props.onTouchViewTag(
+          nativeViewTag,
+          {left, top, width, height},
+          locationY,
+        );
+      },
     );
   };
 
-  shouldSetResponser = (e: EventLike): bool => {
+  shouldSetResponser = (e: EventLike): boolean => {
     this.findViewForTouchEvent(e);
     return true;
   };
@@ -56,7 +62,12 @@ class InspectorOverlay extends React.Component<{
   render() {
     let content = null;
     if (this.props.inspected) {
-      content = <ElementBox frame={this.props.inspected.frame} style={this.props.inspected.style} />;
+      content = (
+        <ElementBox
+          frame={this.props.inspected.frame}
+          style={this.props.inspected.style}
+        />
+      );
     }
 
     return (
diff --git a/Libraries/Inspector/InspectorPanel.js b/Libraries/Inspector/InspectorPanel.js
index b2dd639c4a89..2793452d90e5 100644
--- a/Libraries/Inspector/InspectorPanel.js
+++ b/Libraries/Inspector/InspectorPanel.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ElementProperties = require('ElementProperties');
@@ -23,9 +25,7 @@ class InspectorPanel extends React.Component<$FlowFixMeProps> {
   renderWaiting() {
     if (this.props.inspecting) {
       return (
-        <Text style={styles.waitingText}>
-          Tap something to inspect it
-        </Text>
+        <Text style={styles.waitingText}>Tap something to inspect it</Text>
       );
     }
     return <Text style={styles.waitingText}>Nothing is inspected</Text>;
@@ -47,19 +47,11 @@ class InspectorPanel extends React.Component<$FlowFixMeProps> {
         </ScrollView>
       );
     } else if (this.props.perfing) {
-      contents = (
-        <PerformanceOverlay />
-      );
+      contents = <PerformanceOverlay />;
     } else if (this.props.networking) {
-      contents = (
-        <NetworkOverlay />
-      );
+      contents = <NetworkOverlay />;
     } else {
-      contents = (
-        <View style={styles.waiting}>
-          {this.renderWaiting()}
-        </View>
-      );
+      contents = <View style={styles.waiting}>{this.renderWaiting()}</View>;
     }
     return (
       <View style={styles.container}>
@@ -70,15 +62,18 @@ class InspectorPanel extends React.Component<$FlowFixMeProps> {
             pressed={this.props.inspecting}
             onClick={this.props.setInspecting}
           />
-          <Button title={'Perf'}
+          <Button
+            title={'Perf'}
             pressed={this.props.perfing}
             onClick={this.props.setPerfing}
           />
-          <Button title={'Network'}
+          <Button
+            title={'Network'}
             pressed={this.props.networking}
             onClick={this.props.setNetworking}
           />
-          <Button title={'Touchables'}
+          <Button
+            title={'Touchables'}
             pressed={this.props.touchTargeting}
             onClick={this.props.setTouchTargeting}
           />
@@ -104,10 +99,9 @@ InspectorPanel.propTypes = {
 class Button extends React.Component<$FlowFixMeProps> {
   render() {
     return (
-      <TouchableHighlight onPress={() => this.props.onClick(!this.props.pressed)} style={[
-        styles.button,
-        this.props.pressed && styles.buttonPressed
-      ]}>
+      <TouchableHighlight
+        onPress={() => this.props.onClick(!this.props.pressed)}
+        style={[styles.button, this.props.pressed && styles.buttonPressed]}>
         <Text style={styles.buttonText}>{this.props.title}</Text>
       </TouchableHighlight>
     );
diff --git a/Libraries/Inspector/NetworkOverlay.js b/Libraries/Inspector/NetworkOverlay.js
index 3651aa351189..46628eccca71 100644
--- a/Libraries/Inspector/NetworkOverlay.js
+++ b/Libraries/Inspector/NetworkOverlay.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ListView = require('ListView');
@@ -47,15 +49,18 @@ type NetworkRequestInfo = {
 /**
  * Show all the intercepted network requests over the InspectorPanel.
  */
-class NetworkOverlay extends React.Component<Object, {
-  dataSource: ListView.DataSource,
-  newDetailInfo: bool,
-  detailRowID: ?number,
-}> {
+class NetworkOverlay extends React.Component<
+  Object,
+  {
+    dataSource: ListView.DataSource,
+    newDetailInfo: boolean,
+    detailRowID: ?number,
+  },
+> {
   _requests: Array<NetworkRequestInfo>;
   _listViewDataSource: ListView.DataSource;
   _listView: ?ListView;
-  _listViewHighlighted: bool;
+  _listViewHighlighted: boolean;
   _listViewHeight: number;
   _scrollView: ?ScrollView;
   _detailViewItems: Array<Array<React.Element<any>>>;
@@ -78,8 +83,9 @@ class NetworkOverlay extends React.Component<Object, {
     super(props);
     this._requests = [];
     this._detailViewItems = [];
-    this._listViewDataSource =
-      new ListView.DataSource({rowHasChanged: (r1, r2) => r1 !== r2});
+    this._listViewDataSource = new ListView.DataSource({
+      rowHasChanged: (r1, r2) => r1 !== r2,
+    });
     this.state = {
       dataSource: this._listViewDataSource.cloneWithRows([]),
       newDetailInfo: false,
@@ -110,9 +116,9 @@ class NetworkOverlay extends React.Component<Object, {
       this._xhrIdMap[xhr._index] = xhrIndex;
 
       const _xhr: NetworkRequestInfo = {
-        'type': 'XMLHttpRequest',
-        'method': method,
-        'url': url
+        type: 'XMLHttpRequest',
+        method: method,
+        url: url,
       };
       this._requests.push(_xhr);
       this._detailViewItems.push([]);
@@ -156,17 +162,11 @@ class NetworkOverlay extends React.Component<Object, {
         networkInfo.responseSize = size;
         networkInfo.responseHeaders = responseHeaders;
         this._genDetailViewItem(xhrIndex);
-      }
+      },
     );
 
-    XHRInterceptor.setResponseCallback((
-        status,
-        timeout,
-        response,
-        responseURL,
-        responseType,
-        xhr,
-      ) => {
+    XHRInterceptor.setResponseCallback(
+      (status, timeout, response, responseURL, responseType, xhr) => {
         const xhrIndex = this._getRequestIndexByXHRID(xhr._index);
         if (xhrIndex === -1) {
           return;
@@ -178,7 +178,7 @@ class NetworkOverlay extends React.Component<Object, {
         networkInfo.responseURL = responseURL;
         networkInfo.responseType = responseType;
         this._genDetailViewItem(xhrIndex);
-      }
+      },
     );
 
     // Fire above callbacks.
@@ -195,9 +195,9 @@ class NetworkOverlay extends React.Component<Object, {
         const socketIndex = this._requests.length;
         this._socketIdMap[socketId] = socketIndex;
         const _webSocket: NetworkRequestInfo = {
-          'type': 'WebSocket',
-          'url': url,
-          'protocols': protocols,
+          type: 'WebSocket',
+          url: url,
+          protocols: protocols,
         };
         this._requests.push(_webSocket);
         this._detailViewItems.push([]);
@@ -206,7 +206,7 @@ class NetworkOverlay extends React.Component<Object, {
           {dataSource: this._listViewDataSource.cloneWithRows(this._requests)},
           this._scrollToBottom(),
         );
-      }
+      },
     );
 
     WebSocketInterceptor.setCloseCallback(
@@ -220,7 +220,7 @@ class NetworkOverlay extends React.Component<Object, {
           this._requests[socketIndex].closeReason = closeReason;
         }
         this._genDetailViewItem(socketIndex);
-      }
+      },
     );
 
     WebSocketInterceptor.setSendCallback((data, socketId) => {
@@ -294,7 +294,8 @@ class NetworkOverlay extends React.Component<Object, {
       methodCellViewStyle = styles.methodOddCellView;
     }
     return (
-      <TouchableHighlight onPress={() => {
+      <TouchableHighlight
+        onPress={() => {
           this._pressRow(rowID);
           highlightRow(sectionID, rowID);
         }}>
@@ -319,7 +320,8 @@ class NetworkOverlay extends React.Component<Object, {
   _renderSeperator(
     sectionID: number,
     rowID: number,
-    adjacentRowHighlighted: bool): React.Element<any> {
+    adjacentRowHighlighted: boolean,
+  ): React.Element<any> {
     return (
       <View
         key={`${sectionID}-${rowID}`}
@@ -337,14 +339,14 @@ class NetworkOverlay extends React.Component<Object, {
       if (scrollResponder) {
         const scrollY = Math.max(
           this._requests.length * LISTVIEW_CELL_HEIGHT +
-          (this._listViewHighlighted ? 2 * SEPARATOR_THICKNESS : 0) -
-          this._listViewHeight,
+            (this._listViewHighlighted ? 2 * SEPARATOR_THICKNESS : 0) -
+            this._listViewHeight,
           0,
         );
         scrollResponder.scrollResponderScrollTo({
           x: 0,
           y: scrollY,
-          animated: true
+          animated: true,
         });
       }
     }
@@ -365,10 +367,7 @@ class NetworkOverlay extends React.Component<Object, {
    */
   _pressRow(rowID: number): void {
     this._listViewHighlighted = true;
-    this.setState(
-      {detailRowID: rowID},
-      this._scrollToTop(),
-    );
+    this.setState({detailRowID: rowID}, this._scrollToTop());
   }
 
   _scrollToTop(): void {
@@ -396,8 +395,9 @@ class NetworkOverlay extends React.Component<Object, {
       return JSON.stringify(value);
     }
     if (typeof value === 'string' && value.length > 500) {
-      return String(value).substr(0, 500).concat(
-        '\n***TRUNCATED TO 500 CHARACTERS***');
+      return String(value)
+        .substr(0, 500)
+        .concat('\n***TRUNCATED TO 500 CHARACTERS***');
     }
     return value;
   }
@@ -443,12 +443,14 @@ class NetworkOverlay extends React.Component<Object, {
           <Text style={[styles.detailViewText, styles.detailValueCellView]}>
             {this._getStringByValue(requestItem[key])}
           </Text>
-        </View>
+        </View>,
       );
     }
     // Re-render if this network request is showing in the detail view.
-    if (this.state.detailRowID != null &&
-        Number(this.state.detailRowID) === index) {
+    if (
+      this.state.detailRowID != null &&
+      Number(this.state.detailRowID) === index
+    ) {
       this.setState({newDetailInfo: true});
     }
   }
@@ -456,30 +458,37 @@ class NetworkOverlay extends React.Component<Object, {
   render() {
     return (
       <View style={styles.container}>
-        {this.state.detailRowID != null &&
-        <TouchableHighlight
-          style={styles.closeButton}
-          onPress={this._closeButtonClicked}>
-          <View>
-            <Text style={styles.clostButtonText}>v</Text>
-          </View>
-        </TouchableHighlight>}
-        {this.state.detailRowID != null &&
-        <ScrollView
-          style={styles.detailScrollView}
-          ref={this._captureDetailScrollView}>
-          {this._detailViewItems[this.state.detailRowID]}
-        </ScrollView>}
-        <View style={styles.listViewTitle}>
-          {this._requests.length > 0 &&
-          <View style={styles.tableRow}>
-            <View style={styles.urlTitleCellView}>
-              <Text style={styles.cellText} numberOfLines={1}>URL</Text>
+        {this.state.detailRowID != null && (
+          <TouchableHighlight
+            style={styles.closeButton}
+            onPress={this._closeButtonClicked}>
+            <View>
+              <Text style={styles.clostButtonText}>v</Text>
             </View>
-            <View style={styles.methodTitleCellView}>
-              <Text style={styles.cellText} numberOfLines={1}>Type</Text>
+          </TouchableHighlight>
+        )}
+        {this.state.detailRowID != null && (
+          <ScrollView
+            style={styles.detailScrollView}
+            ref={this._captureDetailScrollView}>
+            {this._detailViewItems[this.state.detailRowID]}
+          </ScrollView>
+        )}
+        <View style={styles.listViewTitle}>
+          {this._requests.length > 0 && (
+            <View style={styles.tableRow}>
+              <View style={styles.urlTitleCellView}>
+                <Text style={styles.cellText} numberOfLines={1}>
+                  URL
+                </Text>
+              </View>
+              <View style={styles.methodTitleCellView}>
+                <Text style={styles.cellText} numberOfLines={1}>
+                  Type
+                </Text>
+              </View>
             </View>
-          </View>}
+          )}
         </View>
         <ListView
           style={styles.listView}
diff --git a/Libraries/Inspector/PerformanceOverlay.js b/Libraries/Inspector/PerformanceOverlay.js
index b75c8f1b38bc..3e2936621a20 100644
--- a/Libraries/Inspector/PerformanceOverlay.js
+++ b/Libraries/Inspector/PerformanceOverlay.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const PerformanceLogger = require('PerformanceLogger');
@@ -21,23 +23,19 @@ class PerformanceOverlay extends React.Component<{}> {
 
     for (const key in perfLogs) {
       if (perfLogs[key].totalTime) {
-        const unit = (key === 'BundleSize') ? 'b' : 'ms';
+        const unit = key === 'BundleSize' ? 'b' : 'ms';
         items.push(
           <View style={styles.row} key={key}>
             <Text style={[styles.text, styles.label]}>{key}</Text>
             <Text style={[styles.text, styles.totalTime]}>
               {perfLogs[key].totalTime + unit}
             </Text>
-          </View>
+          </View>,
         );
       }
     }
 
-    return (
-      <View style={styles.container}>
-        {items}
-      </View>
-    );
+    return <View style={styles.container}>{items}</View>;
   }
 }
 
diff --git a/Libraries/Inspector/StyleInspector.js b/Libraries/Inspector/StyleInspector.js
index df32a6688de4..0f06cd40f6b6 100644
--- a/Libraries/Inspector/StyleInspector.js
+++ b/Libraries/Inspector/StyleInspector.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -22,14 +24,25 @@ class StyleInspector extends React.Component<$FlowFixMeProps> {
     return (
       <View style={styles.container}>
         <View>
-          {names.map(name => <Text key={name} style={styles.attr}>{name}:</Text>)}
+          {names.map(name => (
+            <Text key={name} style={styles.attr}>
+              {name}:
+            </Text>
+          ))}
         </View>
 
         <View>
           {names.map(name => {
-            const value = typeof this.props.style[name] === 'object' ? JSON.stringify(this.props.style[name]) : this.props.style[name];
-            return <Text key={name} style={styles.value}>{value}</Text>;
-          } ) }
+            const value =
+              typeof this.props.style[name] === 'object'
+                ? JSON.stringify(this.props.style[name])
+                : this.props.style[name];
+            return (
+              <Text key={name} style={styles.value}>
+                {value}
+              </Text>
+            );
+          })}
         </View>
       </View>
     );
@@ -61,4 +74,3 @@ const styles = StyleSheet.create({
 });
 
 module.exports = StyleInspector;
-
diff --git a/Libraries/Inspector/resolveBoxStyle.js b/Libraries/Inspector/resolveBoxStyle.js
index 27c89de9b6d8..0a0e58e120f6 100644
--- a/Libraries/Inspector/resolveBoxStyle.js
+++ b/Libraries/Inspector/resolveBoxStyle.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /**
@@ -53,4 +55,3 @@ function capFirst(text) {
 }
 
 module.exports = resolveBoxStyle;
-
diff --git a/Libraries/Interaction/Batchinator.js b/Libraries/Interaction/Batchinator.js
index 84097514ba64..eea02e45ed3f 100644
--- a/Libraries/Interaction/Batchinator.js
+++ b/Libraries/Interaction/Batchinator.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const InteractionManager = require('InteractionManager');
diff --git a/Libraries/Interaction/BridgeSpyStallHandler.js b/Libraries/Interaction/BridgeSpyStallHandler.js
index 88f892442d09..d2933584a32f 100644
--- a/Libraries/Interaction/BridgeSpyStallHandler.js
+++ b/Libraries/Interaction/BridgeSpyStallHandler.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const JSEventLoopWatchdog = require('JSEventLoopWatchdog');
@@ -16,7 +18,7 @@ const infoLog = require('infoLog');
 const BridgeSpyStallHandler = {
   register: function() {
     let spyBuffer = [];
-    MessageQueue.spy((data) => {
+    MessageQueue.spy(data => {
       spyBuffer.push(data);
     });
     const TO_JS = 0;
@@ -24,13 +26,13 @@ const BridgeSpyStallHandler = {
       onStall: () => {
         infoLog(
           spyBuffer.length + ' bridge messages during stall: ',
-          spyBuffer.map((info) => {
+          spyBuffer.map(info => {
             let args = '<args>';
             try {
               args = JSON.stringify(info.args);
             } catch (e1) {
               if (Array.isArray(info.args)) {
-                args = info.args.map((arg) => {
+                args = info.args.map(arg => {
                   try {
                     return JSON.stringify(arg);
                   } catch (e2) {
@@ -41,8 +43,12 @@ const BridgeSpyStallHandler = {
                 args = 'keys:' + JSON.stringify(Object.keys(info.args));
               }
             }
-            return `${info.type === TO_JS ? 'N->JS' : 'JS->N'} : ` +
-              `${info.module ? (info.module + '.') : ''}${info.method}(${JSON.stringify(args)})`;
+            return (
+              `${info.type === TO_JS ? 'N->JS' : 'JS->N'} : ` +
+              `${info.module ? info.module + '.' : ''}${
+                info.method
+              }(${JSON.stringify(args)})`
+            );
           }),
         );
       },
diff --git a/Libraries/Interaction/FrameRateLogger.js b/Libraries/Interaction/FrameRateLogger.js
index 1653b85915a2..b9d872e80ff9 100644
--- a/Libraries/Interaction/FrameRateLogger.js
+++ b/Libraries/Interaction/FrameRateLogger.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeModules = require('NativeModules');
@@ -33,7 +35,10 @@ const FrameRateLogger = {
    * Enable `debug` to see local logs of what's going on. `reportStackTraces` will grab stack traces
    * during UI thread stalls and upload them if the native module supports it.
    */
-  setGlobalOptions: function(options: {debug?: boolean, reportStackTraces?: boolean}) {
+  setGlobalOptions: function(options: {
+    debug?: boolean,
+    reportStackTraces?: boolean,
+  }) {
     if (options.debug !== undefined) {
       invariant(
         NativeModules.FrameRateLogger,
@@ -59,7 +64,8 @@ const FrameRateLogger = {
    * in `AppRegistry`, but navigation is also a common place to hook in.
    */
   setContext: function(context: string) {
-    NativeModules.FrameRateLogger && NativeModules.FrameRateLogger.setContext(context);
+    NativeModules.FrameRateLogger &&
+      NativeModules.FrameRateLogger.setContext(context);
   },
 
   /**
@@ -67,7 +73,8 @@ const FrameRateLogger = {
    * automatically.
    */
   beginScroll() {
-    NativeModules.FrameRateLogger && NativeModules.FrameRateLogger.beginScroll();
+    NativeModules.FrameRateLogger &&
+      NativeModules.FrameRateLogger.beginScroll();
   },
 
   /**
diff --git a/Libraries/Interaction/InteractionManager.js b/Libraries/Interaction/InteractionManager.js
index 3d2f2fa46e0b..d8b57d0a9b99 100644
--- a/Libraries/Interaction/InteractionManager.js
+++ b/Libraries/Interaction/InteractionManager.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const BatchedBridge = require('BatchedBridge');
@@ -87,14 +89,19 @@ const InteractionManager = {
    * Schedule a function to run after all interactions have completed. Returns a cancellable
    * "promise".
    */
-  runAfterInteractions(task: ?Task): {then: Function, done: Function, cancel: Function} {
+  runAfterInteractions(
+    task: ?Task,
+  ): {then: Function, done: Function, cancel: Function} {
     const tasks = [];
     const promise = new Promise(resolve => {
       _scheduleUpdate();
       if (task) {
         tasks.push(task);
       }
-      tasks.push({run: resolve, name: 'resolve ' + (task && task.name || '?')});
+      tasks.push({
+        run: resolve,
+        name: 'resolve ' + ((task && task.name) || '?'),
+      });
       _taskQueue.enqueueTasks(tasks);
     });
     return {
@@ -103,7 +110,9 @@ const InteractionManager = {
         if (promise.done) {
           return promise.done(...args);
         } else {
-          console.warn('Tried to call done when not supported by current Promise implementation.');
+          console.warn(
+            'Tried to call done when not supported by current Promise implementation.',
+          );
         }
       },
       cancel: function() {
@@ -128,10 +137,7 @@ const InteractionManager = {
    */
   clearInteractionHandle(handle: Handle) {
     DEBUG && infoLog('clear interaction handle');
-    invariant(
-      !!handle,
-      'Must provide a handle to clear.'
-    );
+    invariant(!!handle, 'Must provide a handle to clear.');
     _scheduleUpdate();
     _addInteractionSet.delete(handle);
     _deleteInteractionSet.add(handle);
@@ -182,12 +188,8 @@ function _processUpdate() {
   _nextUpdateHandle = 0;
 
   const interactionCount = _interactionSet.size;
-  _addInteractionSet.forEach(handle =>
-    _interactionSet.add(handle)
-  );
-  _deleteInteractionSet.forEach(handle =>
-    _interactionSet.delete(handle)
-  );
+  _addInteractionSet.forEach(handle => _interactionSet.add(handle));
+  _deleteInteractionSet.forEach(handle => _interactionSet.delete(handle));
   const nextInteractionCount = _interactionSet.size;
 
   if (interactionCount !== 0 && nextInteractionCount === 0) {
@@ -202,8 +204,10 @@ function _processUpdate() {
   if (nextInteractionCount === 0) {
     while (_taskQueue.hasTasksToProcess()) {
       _taskQueue.processNext();
-      if (_deadline > 0 &&
-          BatchedBridge.getEventLoopRunningTime() >= _deadline) {
+      if (
+        _deadline > 0 &&
+        BatchedBridge.getEventLoopRunningTime() >= _deadline
+      ) {
         // Hit deadline before processing all tasks, so process more later.
         _scheduleUpdate();
         break;
diff --git a/Libraries/Interaction/InteractionMixin.js b/Libraries/Interaction/InteractionMixin.js
index 018ca1bd16d6..78b81f295cdc 100644
--- a/Libraries/Interaction/InteractionMixin.js
+++ b/Libraries/Interaction/InteractionMixin.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const InteractionManager = require('InteractionManager');
@@ -19,7 +21,7 @@ const InteractionMixin = {
   componentWillUnmount: function() {
     while (this._interactionMixinHandles.length) {
       InteractionManager.clearInteractionHandle(
-        this._interactionMixinHandles.pop()
+        this._interactionMixinHandles.pop(),
       );
     }
   },
@@ -35,7 +37,7 @@ const InteractionMixin = {
   clearInteractionHandle: function(clearHandle: number) {
     InteractionManager.clearInteractionHandle(clearHandle);
     this._interactionMixinHandles = this._interactionMixinHandles.filter(
-      handle => handle !== clearHandle
+      handle => handle !== clearHandle,
     );
   },
 
diff --git a/Libraries/Interaction/InteractionStallDebugger.js b/Libraries/Interaction/InteractionStallDebugger.js
index f62e8d244444..192d1eeed83e 100644
--- a/Libraries/Interaction/InteractionStallDebugger.js
+++ b/Libraries/Interaction/InteractionStallDebugger.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const BridgeSpyStallHandler = require('BridgeSpyStallHandler');
diff --git a/Libraries/Interaction/JSEventLoopWatchdog.js b/Libraries/Interaction/JSEventLoopWatchdog.js
index 8e2f00eef41d..5d5328325c18 100644
--- a/Libraries/Interaction/JSEventLoopWatchdog.js
+++ b/Libraries/Interaction/JSEventLoopWatchdog.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const infoLog = require('infoLog');
@@ -60,14 +62,15 @@ const JSEventLoopWatchdog = {
         stallCount++;
         totalStallTime += stallTime;
         longestStall = Math.max(longestStall, stallTime);
-        let msg = `JSEventLoopWatchdog: JS thread busy for ${busyTime}ms. ` +
+        let msg =
+          `JSEventLoopWatchdog: JS thread busy for ${busyTime}ms. ` +
           `${totalStallTime}ms in ${stallCount} stalls so far. `;
-        handlers.forEach((handler) => {
+        handlers.forEach(handler => {
           msg += handler.onStall({lastInterval, busyTime}) || '';
         });
         infoLog(msg);
       }
-      handlers.forEach((handler) => {
+      handlers.forEach(handler => {
         handler.onIterate && handler.onIterate();
       });
       lastInterval = now;
diff --git a/Libraries/Interaction/PanResponder.js b/Libraries/Interaction/PanResponder.js
index 92438d904656..fb974c9931e0 100644
--- a/Libraries/Interaction/PanResponder.js
+++ b/Libraries/Interaction/PanResponder.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -11,10 +12,14 @@
 const InteractionManager = require('./InteractionManager');
 const TouchHistoryMath = require('./TouchHistoryMath');
 
-const currentCentroidXOfTouchesChangedAfter = TouchHistoryMath.currentCentroidXOfTouchesChangedAfter;
-const currentCentroidYOfTouchesChangedAfter = TouchHistoryMath.currentCentroidYOfTouchesChangedAfter;
-const previousCentroidXOfTouchesChangedAfter = TouchHistoryMath.previousCentroidXOfTouchesChangedAfter;
-const previousCentroidYOfTouchesChangedAfter = TouchHistoryMath.previousCentroidYOfTouchesChangedAfter;
+const currentCentroidXOfTouchesChangedAfter =
+  TouchHistoryMath.currentCentroidXOfTouchesChangedAfter;
+const currentCentroidYOfTouchesChangedAfter =
+  TouchHistoryMath.currentCentroidYOfTouchesChangedAfter;
+const previousCentroidXOfTouchesChangedAfter =
+  TouchHistoryMath.previousCentroidXOfTouchesChangedAfter;
+const previousCentroidYOfTouchesChangedAfter =
+  TouchHistoryMath.previousCentroidYOfTouchesChangedAfter;
 const currentCentroidX = TouchHistoryMath.currentCentroidX;
 const currentCentroidY = TouchHistoryMath.currentCentroidY;
 
@@ -117,7 +122,6 @@ const currentCentroidY = TouchHistoryMath.currentCentroidY;
  */
 
 const PanResponder = {
-
   /**
    *
    * A graphical explanation of the touch data flow:
@@ -181,7 +185,7 @@ const PanResponder = {
    * - vx/vy: Velocity.
    */
 
-  _initializeGestureState: function (gestureState) {
+  _initializeGestureState: function(gestureState) {
     gestureState.moveX = 0;
     gestureState.moveY = 0;
     gestureState.x0 = 0;
@@ -219,20 +223,33 @@ const PanResponder = {
    * typical responder callback pattern (without using `PanResponder`), but
    * avoids more dispatches than necessary.
    */
-  _updateGestureStateOnMove: function (gestureState, touchHistory) {
+  _updateGestureStateOnMove: function(gestureState, touchHistory) {
     gestureState.numberActiveTouches = touchHistory.numberActiveTouches;
-    gestureState.moveX = currentCentroidXOfTouchesChangedAfter(touchHistory, gestureState._accountsForMovesUpTo);
-    gestureState.moveY = currentCentroidYOfTouchesChangedAfter(touchHistory, gestureState._accountsForMovesUpTo);
+    gestureState.moveX = currentCentroidXOfTouchesChangedAfter(
+      touchHistory,
+      gestureState._accountsForMovesUpTo,
+    );
+    gestureState.moveY = currentCentroidYOfTouchesChangedAfter(
+      touchHistory,
+      gestureState._accountsForMovesUpTo,
+    );
     const movedAfter = gestureState._accountsForMovesUpTo;
-    const prevX = previousCentroidXOfTouchesChangedAfter(touchHistory, movedAfter);
+    const prevX = previousCentroidXOfTouchesChangedAfter(
+      touchHistory,
+      movedAfter,
+    );
     const x = currentCentroidXOfTouchesChangedAfter(touchHistory, movedAfter);
-    const prevY = previousCentroidYOfTouchesChangedAfter(touchHistory, movedAfter);
+    const prevY = previousCentroidYOfTouchesChangedAfter(
+      touchHistory,
+      movedAfter,
+    );
     const y = currentCentroidYOfTouchesChangedAfter(touchHistory, movedAfter);
     const nextDX = gestureState.dx + (x - prevX);
     const nextDY = gestureState.dy + (y - prevY);
 
     // TODO: This must be filtered intelligently.
-    const dt = touchHistory.mostRecentTimeStamp - gestureState._accountsForMovesUpTo;
+    const dt =
+      touchHistory.mostRecentTimeStamp - gestureState._accountsForMovesUpTo;
     gestureState.vx = (nextDX - gestureState.dx) / dt;
     gestureState.vy = (nextDY - gestureState.dy) / dt;
 
@@ -273,7 +290,7 @@ const PanResponder = {
    *  accordingly. (numberActiveTouches) may not be totally accurate unless you
    *  are the responder.
    */
-  create: function (config) {
+  create: function(config) {
     const interactionState = {
       handle: (null: ?number),
     };
@@ -283,43 +300,46 @@ const PanResponder = {
     };
     PanResponder._initializeGestureState(gestureState);
     const panHandlers = {
-      onStartShouldSetResponder: function (e) {
-        return config.onStartShouldSetPanResponder === undefined ?
-          false :
-          config.onStartShouldSetPanResponder(e, gestureState);
+      onStartShouldSetResponder: function(e) {
+        return config.onStartShouldSetPanResponder === undefined
+          ? false
+          : config.onStartShouldSetPanResponder(e, gestureState);
       },
-      onMoveShouldSetResponder: function (e) {
-        return config.onMoveShouldSetPanResponder === undefined ?
-          false :
-          config.onMoveShouldSetPanResponder(e, gestureState);
+      onMoveShouldSetResponder: function(e) {
+        return config.onMoveShouldSetPanResponder === undefined
+          ? false
+          : config.onMoveShouldSetPanResponder(e, gestureState);
       },
-      onStartShouldSetResponderCapture: function (e) {
+      onStartShouldSetResponderCapture: function(e) {
         // TODO: Actually, we should reinitialize the state any time
         // touches.length increases from 0 active to > 0 active.
         if (e.nativeEvent.touches.length === 1) {
           PanResponder._initializeGestureState(gestureState);
         }
         gestureState.numberActiveTouches = e.touchHistory.numberActiveTouches;
-        return config.onStartShouldSetPanResponderCapture !== undefined ?
-          config.onStartShouldSetPanResponderCapture(e, gestureState) :
-          false;
+        return config.onStartShouldSetPanResponderCapture !== undefined
+          ? config.onStartShouldSetPanResponderCapture(e, gestureState)
+          : false;
       },
 
-      onMoveShouldSetResponderCapture: function (e) {
+      onMoveShouldSetResponderCapture: function(e) {
         const touchHistory = e.touchHistory;
         // Responder system incorrectly dispatches should* to current responder
         // Filter out any touch moves past the first one - we would have
         // already processed multi-touch geometry during the first event.
-        if (gestureState._accountsForMovesUpTo === touchHistory.mostRecentTimeStamp) {
+        if (
+          gestureState._accountsForMovesUpTo ===
+          touchHistory.mostRecentTimeStamp
+        ) {
           return false;
         }
         PanResponder._updateGestureStateOnMove(gestureState, touchHistory);
-        return config.onMoveShouldSetPanResponderCapture ?
-          config.onMoveShouldSetPanResponderCapture(e, gestureState) :
-          false;
+        return config.onMoveShouldSetPanResponderCapture
+          ? config.onMoveShouldSetPanResponderCapture(e, gestureState)
+          : false;
       },
 
-      onResponderGrant: function (e) {
+      onResponderGrant: function(e) {
         if (!interactionState.handle) {
           interactionState.handle = InteractionManager.createInteractionHandle();
         }
@@ -331,21 +351,31 @@ const PanResponder = {
           config.onPanResponderGrant(e, gestureState);
         }
         // TODO: t7467124 investigate if this can be removed
-        return config.onShouldBlockNativeResponder === undefined ?
-          true :
-          config.onShouldBlockNativeResponder();
+        return config.onShouldBlockNativeResponder === undefined
+          ? true
+          : config.onShouldBlockNativeResponder();
       },
 
-      onResponderReject: function (e) {
-        clearInteractionHandle(interactionState, config.onPanResponderReject, e, gestureState);
+      onResponderReject: function(e) {
+        clearInteractionHandle(
+          interactionState,
+          config.onPanResponderReject,
+          e,
+          gestureState,
+        );
       },
 
-      onResponderRelease: function (e) {
-        clearInteractionHandle(interactionState, config.onPanResponderRelease, e, gestureState);
+      onResponderRelease: function(e) {
+        clearInteractionHandle(
+          interactionState,
+          config.onPanResponderRelease,
+          e,
+          gestureState,
+        );
         PanResponder._initializeGestureState(gestureState);
       },
 
-      onResponderStart: function (e) {
+      onResponderStart: function(e) {
         const touchHistory = e.touchHistory;
         gestureState.numberActiveTouches = touchHistory.numberActiveTouches;
         if (config.onPanResponderStart) {
@@ -353,11 +383,14 @@ const PanResponder = {
         }
       },
 
-      onResponderMove: function (e) {
+      onResponderMove: function(e) {
         const touchHistory = e.touchHistory;
         // Guard against the dispatch of two touch moves when there are two
         // simultaneously changed touches.
-        if (gestureState._accountsForMovesUpTo === touchHistory.mostRecentTimeStamp) {
+        if (
+          gestureState._accountsForMovesUpTo ===
+          touchHistory.mostRecentTimeStamp
+        ) {
           return;
         }
         // Filter out any touch moves past the first one - we would have
@@ -368,22 +401,32 @@ const PanResponder = {
         }
       },
 
-      onResponderEnd: function (e) {
+      onResponderEnd: function(e) {
         const touchHistory = e.touchHistory;
         gestureState.numberActiveTouches = touchHistory.numberActiveTouches;
-        clearInteractionHandle(interactionState, config.onPanResponderEnd, e, gestureState);
+        clearInteractionHandle(
+          interactionState,
+          config.onPanResponderEnd,
+          e,
+          gestureState,
+        );
       },
 
-      onResponderTerminate: function (e) {
-        clearInteractionHandle(interactionState, config.onPanResponderTerminate, e, gestureState);
+      onResponderTerminate: function(e) {
+        clearInteractionHandle(
+          interactionState,
+          config.onPanResponderTerminate,
+          e,
+          gestureState,
+        );
         PanResponder._initializeGestureState(gestureState);
       },
 
-      onResponderTerminationRequest: function (e) {
-        return config.onPanResponderTerminationRequest === undefined ?
-          true :
-          config.onPanResponderTerminationRequest(e, gestureState);
-      }
+      onResponderTerminationRequest: function(e) {
+        return config.onPanResponderTerminationRequest === undefined
+          ? true
+          : config.onPanResponderTerminationRequest(e, gestureState);
+      },
     };
     return {
       panHandlers,
@@ -391,14 +434,14 @@ const PanResponder = {
         return interactionState.handle;
       },
     };
-  }
+  },
 };
 
 function clearInteractionHandle(
   interactionState: {handle: ?number},
   callback: Function,
   event: Object,
-  gestureState: Object
+  gestureState: Object,
 ) {
   if (interactionState.handle) {
     InteractionManager.clearInteractionHandle(interactionState.handle);
diff --git a/Libraries/Interaction/ReactPerfStallHandler.js b/Libraries/Interaction/ReactPerfStallHandler.js
index 09c57dabc5f4..bdeaed21d0e4 100644
--- a/Libraries/Interaction/ReactPerfStallHandler.js
+++ b/Libraries/Interaction/ReactPerfStallHandler.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const JSEventLoopWatchdog = require('JSEventLoopWatchdog');
diff --git a/Libraries/Interaction/TaskQueue.js b/Libraries/Interaction/TaskQueue.js
index 6660d84f4719..90f49a8e84d3 100644
--- a/Libraries/Interaction/TaskQueue.js
+++ b/Libraries/Interaction/TaskQueue.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const infoLog = require('infoLog');
@@ -62,17 +64,17 @@ class TaskQueue {
   }
 
   enqueueTasks(tasks: Array<Task>): void {
-    tasks.forEach((task) => this.enqueue(task));
+    tasks.forEach(task => this.enqueue(task));
   }
 
   cancelTasks(tasksToCancel: Array<Task>): void {
     // search through all tasks and remove them.
     this._queueStack = this._queueStack
-      .map((queue) => ({
+      .map(queue => ({
         ...queue,
-        tasks: queue.tasks.filter((task) => tasksToCancel.indexOf(task) === -1),
+        tasks: queue.tasks.filter(task => tasksToCancel.indexOf(task) === -1),
       }))
-      .filter((queue, idx) => (queue.tasks.length > 0 || idx === 0));
+      .filter((queue, idx) => queue.tasks.length > 0 || idx === 0);
   }
 
   /**
@@ -85,7 +87,7 @@ class TaskQueue {
    * `onMoreTasks` will be called after each `PromiseTask` resolves if there are
    * tasks ready to run at that point.
    */
-  hasTasksToProcess(): bool {
+  hasTasksToProcess(): boolean {
     return this._getCurrentQueue().length > 0;
   }
 
@@ -107,30 +109,36 @@ class TaskQueue {
           invariant(
             typeof task === 'function',
             'Expected Function, SimpleTask, or PromiseTask, but got:\n' +
-              JSON.stringify(task, null, 2)
+              JSON.stringify(task, null, 2),
           );
           DEBUG && infoLog('run anonymous task');
           task();
         }
       } catch (e) {
-        e.message = 'TaskQueue: Error with task ' + (task.name || '') + ': ' +
-          e.message;
+        e.message =
+          'TaskQueue: Error with task ' + (task.name || '') + ': ' + e.message;
         throw e;
       }
     }
   }
 
-  _queueStack: Array<{tasks: Array<Task>, popable: bool}>;
+  _queueStack: Array<{tasks: Array<Task>, popable: boolean}>;
   _onMoreTasks: () => void;
 
   _getCurrentQueue(): Array<Task> {
     const stackIdx = this._queueStack.length - 1;
     const queue = this._queueStack[stackIdx];
-    if (queue.popable &&
-        queue.tasks.length === 0 &&
-        this._queueStack.length > 1) {
+    if (
+      queue.popable &&
+      queue.tasks.length === 0 &&
+      this._queueStack.length > 1
+    ) {
       this._queueStack.pop();
-      DEBUG && infoLog('popped queue: ', {stackIdx, queueStackSize: this._queueStack.length});
+      DEBUG &&
+        infoLog('popped queue: ', {
+          stackIdx,
+          queueStackSize: this._queueStack.length,
+        });
       return this._getCurrentQueue();
     } else {
       return queue.tasks;
@@ -146,22 +154,25 @@ class TaskQueue {
     const stackIdx = this._queueStack.length - 1;
     DEBUG && infoLog('push new queue: ', {stackIdx});
     DEBUG && infoLog('exec gen task ' + task.name);
-    task.gen()
+    task
+      .gen()
       .then(() => {
-        DEBUG && infoLog(
-          'onThen for gen task ' + task.name,
-          {stackIdx, queueStackSize: this._queueStack.length},
-        );
+        DEBUG &&
+          infoLog('onThen for gen task ' + task.name, {
+            stackIdx,
+            queueStackSize: this._queueStack.length,
+          });
         this._queueStack[stackIdx].popable = true;
         this.hasTasksToProcess() && this._onMoreTasks();
       })
-      .catch((ex) => {
-        ex.message = `TaskQueue: Error resolving Promise in task ${task.name}: ${ex.message}`;
+      .catch(ex => {
+        ex.message = `TaskQueue: Error resolving Promise in task ${
+          task.name
+        }: ${ex.message}`;
         throw ex;
       })
       .done();
   }
 }
 
-
 module.exports = TaskQueue;
diff --git a/Libraries/Interaction/TouchHistoryMath.js b/Libraries/Interaction/TouchHistoryMath.js
index be5aa707653c..8d6d8253390f 100644
--- a/Libraries/Interaction/TouchHistoryMath.js
+++ b/Libraries/Interaction/TouchHistoryMath.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const TouchHistoryMath = {
diff --git a/Libraries/Interaction/__tests__/Batchinator-test.js b/Libraries/Interaction/__tests__/Batchinator-test.js
index a0afacd4e0d0..4cd4668fb27e 100644
--- a/Libraries/Interaction/__tests__/Batchinator-test.js
+++ b/Libraries/Interaction/__tests__/Batchinator-test.js
@@ -4,14 +4,13 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
 
 'use strict';
 
-jest
-  .mock('ErrorUtils')
-  .mock('BatchedBridge');
+jest.mock('ErrorUtils').mock('BatchedBridge');
 
 function expectToBeCalledOnce(fn) {
   expect(fn.mock.calls.length).toBe(1);
diff --git a/Libraries/Interaction/__tests__/InteractionManager-test.js b/Libraries/Interaction/__tests__/InteractionManager-test.js
index 0a74b7cc7664..edbdb50fb527 100644
--- a/Libraries/Interaction/__tests__/InteractionManager-test.js
+++ b/Libraries/Interaction/__tests__/InteractionManager-test.js
@@ -4,14 +4,13 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
 
 'use strict';
 
-jest
-  .mock('ErrorUtils')
-  .mock('BatchedBridge');
+jest.mock('ErrorUtils').mock('BatchedBridge');
 
 function expectToBeCalledOnce(fn) {
   expect(fn.mock.calls.length).toBe(1);
@@ -31,11 +30,11 @@ describe('InteractionManager', () => {
 
     InteractionManager.addListener(
       InteractionManager.Events.interactionStart,
-      interactionStart
+      interactionStart,
     );
     InteractionManager.addListener(
       InteractionManager.Events.interactionComplete,
-      interactionComplete
+      interactionComplete,
     );
   });
 
@@ -168,7 +167,6 @@ describe('promise tasks', () => {
     sequenceId = 0;
   });
 
-
   it('should run a basic promise task', () => {
     const task1 = jest.fn(() => {
       expect(++sequenceId).toBe(1);
@@ -183,8 +181,10 @@ describe('promise tasks', () => {
     const task1 = jest.fn(() => {
       expect(++sequenceId).toBe(1);
       return new Promise(resolve => {
-        InteractionManager.runAfterInteractions({gen: task2, name: 'gen2'})
-          .then(resolve);
+        InteractionManager.runAfterInteractions({
+          gen: task2,
+          name: 'gen2',
+        }).then(resolve);
       });
     });
     const task2 = jest.fn(() => {
@@ -255,7 +255,7 @@ describe('promise tasks', () => {
     expectToBeCalledOnce(task2);
   });
 
-  const bigAsyncTest = (resolve) => {
+  const bigAsyncTest = resolve => {
     jest.useRealTimers();
 
     const task1 = createSequenceTask(1);
@@ -264,8 +264,10 @@ describe('promise tasks', () => {
       return new Promise(resolve => {
         InteractionManager.runAfterInteractions(task3);
         setTimeout(() => {
-          InteractionManager.runAfterInteractions({gen: task4, name: 'gen4'})
-            .then(resolve);
+          InteractionManager.runAfterInteractions({
+            gen: task4,
+            name: 'gen4',
+          }).then(resolve);
         }, 1);
       });
     });
diff --git a/Libraries/Interaction/__tests__/InteractionMixin-test.js b/Libraries/Interaction/__tests__/InteractionMixin-test.js
index 7a3675b13f0b..77c75c1e9ca5 100644
--- a/Libraries/Interaction/__tests__/InteractionMixin-test.js
+++ b/Libraries/Interaction/__tests__/InteractionMixin-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 jest.enableAutomock().unmock('InteractionMixin');
diff --git a/Libraries/Interaction/__tests__/TaskQueue-test.js b/Libraries/Interaction/__tests__/TaskQueue-test.js
index 407e8fa435cd..ce00415fefd7 100644
--- a/Libraries/Interaction/__tests__/TaskQueue-test.js
+++ b/Libraries/Interaction/__tests__/TaskQueue-test.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
 
@@ -40,7 +41,6 @@ describe('TaskQueue', () => {
     sequenceId = 0;
   });
 
-
   it('should run a basic task', () => {
     const task1 = createSequenceTask(1);
     taskQueue.enqueue({run: task1, name: 'run1'});
diff --git a/Libraries/JSInspector/InspectorAgent.js b/Libraries/JSInspector/InspectorAgent.js
index b419a6c2aadf..2afe86fbe4e0 100644
--- a/Libraries/JSInspector/InspectorAgent.js
+++ b/Libraries/JSInspector/InspectorAgent.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 export type EventSender = (name: string, params: Object) => void;
diff --git a/Libraries/JSInspector/JSInspector.js b/Libraries/JSInspector/JSInspector.js
index e62669aee6a3..21ccf7fbc151 100644
--- a/Libraries/JSInspector/JSInspector.js
+++ b/Libraries/JSInspector/JSInspector.js
@@ -4,18 +4,20 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 import type EventSender from 'InspectorAgent';
 
 interface Agent {
-  constructor(eventSender: EventSender): void
+  constructor(eventSender: EventSender): void;
 }
 
 // Flow doesn't support static declarations in interface
-type AgentClass = Class<Agent> & { DOMAIN: string };
+type AgentClass = Class<Agent> & {DOMAIN: string};
 
 declare function __registerInspectorAgent(type: AgentClass): void;
 declare function __inspectorTimestamp(): number;
diff --git a/Libraries/JSInspector/NetworkAgent.js b/Libraries/JSInspector/NetworkAgent.js
index bf1de686ae91..2b25be3da54c 100644
--- a/Libraries/JSInspector/NetworkAgent.js
+++ b/Libraries/JSInspector/NetworkAgent.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const InspectorAgent = require('InspectorAgent');
@@ -27,34 +29,34 @@ type Headers = Object;
 type ResourceTiming = null;
 
 type ResourceType =
-  'Document' |
-  'Stylesheet' |
-  'Image' |
-  'Media' |
-  'Font' |
-  'Script' |
-  'TextTrack' |
-  'XHR' |
-  'Fetch' |
-  'EventSource' |
-  'WebSocket' |
-  'Manifest' |
-  'Other';
+  | 'Document'
+  | 'Stylesheet'
+  | 'Image'
+  | 'Media'
+  | 'Font'
+  | 'Script'
+  | 'TextTrack'
+  | 'XHR'
+  | 'Fetch'
+  | 'EventSource'
+  | 'WebSocket'
+  | 'Manifest'
+  | 'Other';
 
 type SecurityState =
-  'unknown' |
-  'neutral' |
-  'insecure' |
-  'warning' |
-  'secure' |
-  'info';
+  | 'unknown'
+  | 'neutral'
+  | 'insecure'
+  | 'warning'
+  | 'secure'
+  | 'info';
 type BlockedReason =
-  'csp' |
-  'mixed-content' |
-  'origin' |
-  'inspector' |
-  'subresource-filter' |
-  'other';
+  | 'csp'
+  | 'mixed-content'
+  | 'origin'
+  | 'inspector'
+  | 'subresource-filter'
+  | 'other';
 
 type StackTrace = null;
 
@@ -62,8 +64,8 @@ type Initiator = {
   type: 'script' | 'other',
   stackTrace?: StackTrace,
   url?: string,
-  lineNumber?: number
-}
+  lineNumber?: number,
+};
 
 type ResourcePriority = 'VeryLow' | 'Low' | 'Medium' | 'High' | 'VeryHigh';
 
@@ -151,11 +153,7 @@ class Interceptor {
     return this._requests.get(requestId);
   }
 
-  requestSent(
-    id: number,
-    url: string,
-    method: string,
-    headers: Object) {
+  requestSent(id: number, url: string, method: string, headers: Object) {
     const requestId = String(id);
     this._requests.set(requestId, '');
 
@@ -183,11 +181,7 @@ class Interceptor {
     this._agent.sendEvent('requestWillBeSent', event);
   }
 
-  responseReceived(
-    id: number,
-    url: string,
-    status: number,
-    headers: Object) {
+  responseReceived(id: number, url: string, status: number, headers: Object) {
     const requestId = String(id);
     const response: Response = {
       url,
@@ -214,9 +208,7 @@ class Interceptor {
     this._agent.sendEvent('responseReceived', event);
   }
 
-  dataReceived(
-    id: number,
-    data: string) {
+  dataReceived(id: number, data: string) {
     const requestId = String(id);
     const existingData = this._requests.get(requestId) || '';
     this._requests.set(requestId, existingData.concat(data));
@@ -229,9 +221,7 @@ class Interceptor {
     this._agent.sendEvent('dataReceived', event);
   }
 
-  loadingFinished(
-    id: number,
-    encodedDataLength: number) {
+  loadingFinished(id: number, encodedDataLength: number) {
     const event: LoadingFinishedEvent = {
       requestId: String(id),
       timestamp: JSInspector.getTimestamp(),
@@ -240,9 +230,7 @@ class Interceptor {
     this._agent.sendEvent('loadingFinished', event);
   }
 
-  loadingFailed(
-      id: number,
-      error: string) {
+  loadingFailed(id: number, error: string) {
     const event: LoadingFailedEvent = {
       requestId: String(id),
       timestamp: JSInspector.getTimestamp(),
@@ -260,7 +248,7 @@ class Interceptor {
 
 type EnableArgs = {
   maxResourceBufferSize?: number,
-  maxTotalBufferSize?: number
+  maxTotalBufferSize?: number,
 };
 
 class NetworkAgent extends InspectorAgent {
@@ -269,7 +257,7 @@ class NetworkAgent extends InspectorAgent {
   _sendEvent: EventSender;
   _interceptor: ?Interceptor;
 
-  enable({ maxResourceBufferSize, maxTotalBufferSize }: EnableArgs) {
+  enable({maxResourceBufferSize, maxTotalBufferSize}: EnableArgs) {
     this._interceptor = new Interceptor(this);
     XMLHttpRequest.setInterceptor(this._interceptor);
   }
@@ -279,8 +267,11 @@ class NetworkAgent extends InspectorAgent {
     this._interceptor = null;
   }
 
-  getResponseBody({requestId}: {requestId: RequestId})
-      : {body: ?string, base64Encoded: boolean} {
+  getResponseBody({
+    requestId,
+  }: {
+    requestId: RequestId,
+  }): {body: ?string, base64Encoded: boolean} {
     return {body: this.interceptor().getData(requestId), base64Encoded: false};
   }
 
@@ -290,7 +281,6 @@ class NetworkAgent extends InspectorAgent {
     } else {
       throw Error('_interceptor can not be null');
     }
-
   }
 }
 
diff --git a/Libraries/Linking/Linking.js b/Libraries/Linking/Linking.js
index a4ad9b3b5932..fec44f634fab 100644
--- a/Libraries/Linking/Linking.js
+++ b/Libraries/Linking/Linking.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeEventEmitter = require('NativeEventEmitter');
@@ -14,8 +16,10 @@ const Platform = require('Platform');
 
 const invariant = require('fbjs/lib/invariant');
 
-const LinkingManager = Platform.OS === 'android' ?
-  NativeModules.IntentAndroid : NativeModules.LinkingManager;
+const LinkingManager =
+  Platform.OS === 'android'
+    ? NativeModules.IntentAndroid
+    : NativeModules.LinkingManager;
 
 /**
  * `Linking` gives you a general interface to interact with both incoming
@@ -24,7 +28,6 @@ const LinkingManager = Platform.OS === 'android' ?
  * See https://facebook.github.io/react-native/docs/linking.html
  */
 class Linking extends NativeEventEmitter {
-
   constructor() {
     super(LinkingManager);
   }
@@ -44,7 +47,7 @@ class Linking extends NativeEventEmitter {
    *
    * See https://facebook.github.io/react-native/docs/linking.html#removeeventlistener
    */
-  removeEventListener(type: string, handler: Function ) {
+  removeEventListener(type: string, handler: Function) {
     this.removeListener(type, handler);
   }
 
@@ -81,12 +84,9 @@ class Linking extends NativeEventEmitter {
   _validateURL(url: string) {
     invariant(
       typeof url === 'string',
-      'Invalid URL: should be a string. Was: ' + url
-    );
-    invariant(
-      url,
-      'Invalid URL: cannot be empty'
+      'Invalid URL: should be a string. Was: ' + url,
     );
+    invariant(url, 'Invalid URL: cannot be empty');
   }
 }
 
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 7c54eba55c39..e0a0fbb651fc 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -1353,14 +1353,18 @@ class VirtualizedList extends React.PureComponent<Props, State> {
     // But only if there are items before the first rendered item
     if (first > 0) {
       const distTop = offset - this._getFrameMetricsApprox(first).offset;
-      hiPri = hiPri || distTop < 0 || (velocity < -2 && distTop < scrollingThreshold);
+      hiPri =
+        hiPri || distTop < 0 || (velocity < -2 && distTop < scrollingThreshold);
     }
     // Mark as high priority if we're close to the end of the last item
     // But only if there are items after the last rendered item
     if (last < itemCount - 1) {
       const distBottom =
         this._getFrameMetricsApprox(last).offset - (offset + visibleLength);
-      hiPri = hiPri || distBottom < 0 || (velocity > 2 && distBottom < scrollingThreshold);
+      hiPri =
+        hiPri ||
+        distBottom < 0 ||
+        (velocity > 2 && distBottom < scrollingThreshold);
     }
     // Only trigger high-priority updates if we've actually rendered cells,
     // and with that size estimate, accurately compute how many cells we should render.
diff --git a/Libraries/Modal/Modal.js b/Libraries/Modal/Modal.js
index 77f50cf273d7..d414a288fee3 100644
--- a/Libraries/Modal/Modal.js
+++ b/Libraries/Modal/Modal.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const AppContainer = require('AppContainer');
@@ -21,8 +23,10 @@ const View = require('View');
 const deprecatedPropType = require('deprecatedPropType');
 const requireNativeComponent = require('requireNativeComponent');
 const RCTModalHostView = requireNativeComponent('RCTModalHostView', null);
-const ModalEventEmitter = Platform.OS === 'ios' && NativeModules.ModalManager ?
-  new NativeEventEmitter(NativeModules.ModalManager) : null;
+const ModalEventEmitter =
+  Platform.OS === 'ios' && NativeModules.ModalManager
+    ? new NativeEventEmitter(NativeModules.ModalManager)
+    : null;
 
 import type EmitterSubscription from 'EmitterSubscription';
 
@@ -51,7 +55,12 @@ class Modal extends React.Component<Object> {
      *
      * See https://facebook.github.io/react-native/docs/modal.html#presentationstyle
      */
-    presentationStyle: PropTypes.oneOf(['fullScreen', 'pageSheet', 'formSheet', 'overFullScreen']),
+    presentationStyle: PropTypes.oneOf([
+      'fullScreen',
+      'pageSheet',
+      'formSheet',
+      'overFullScreen',
+    ]),
     /**
      * The `transparent` prop determines whether your modal will fill the
      * entire view.
@@ -78,7 +87,10 @@ class Modal extends React.Component<Object> {
      *
      * See https://facebook.github.io/react-native/docs/modal.html#onrequestclose
      */
-    onRequestClose: (Platform.isTVOS || Platform.OS === 'android') ? PropTypes.func.isRequired : PropTypes.func,
+    onRequestClose:
+      Platform.isTVOS || Platform.OS === 'android'
+        ? PropTypes.func.isRequired
+        : PropTypes.func,
     /**
      * The `onShow` prop allows passing a function that will be called once the
      * modal has been shown.
@@ -95,14 +107,22 @@ class Modal extends React.Component<Object> {
     onDismiss: PropTypes.func,
     animated: deprecatedPropType(
       PropTypes.bool,
-      'Use the `animationType` prop instead.'
+      'Use the `animationType` prop instead.',
     ),
     /**
      * The `supportedOrientations` prop allows the modal to be rotated to any of the specified orientations.
      *
      * See https://facebook.github.io/react-native/docs/modal.html#supportedorientations
      */
-    supportedOrientations: PropTypes.arrayOf(PropTypes.oneOf(['portrait', 'portrait-upside-down', 'landscape', 'landscape-left', 'landscape-right'])),
+    supportedOrientations: PropTypes.arrayOf(
+      PropTypes.oneOf([
+        'portrait',
+        'portrait-upside-down',
+        'landscape',
+        'landscape-left',
+        'landscape-right',
+      ]),
+    ),
     /**
      * The `onOrientationChange` callback is called when the orientation changes while the modal is being displayed.
      *
@@ -165,8 +185,16 @@ class Modal extends React.Component<Object> {
   }
 
   static _confirmProps(props: Object) {
-    if (props.presentationStyle && props.presentationStyle !== 'overFullScreen' && props.transparent) {
-      console.warn(`Modal with '${props.presentationStyle}' presentation style and 'transparent' value is not supported.`);
+    if (
+      props.presentationStyle &&
+      props.presentationStyle !== 'overFullScreen' &&
+      props.transparent
+    ) {
+      console.warn(
+        `Modal with '${
+          props.presentationStyle
+        }' presentation style and 'transparent' value is not supported.`,
+      );
     }
   }
 
@@ -196,11 +224,13 @@ class Modal extends React.Component<Object> {
       }
     }
 
-    const innerChildren = __DEV__ ?
-      ( <AppContainer rootTag={this.context.rootTag}>
-          {this.props.children}
-        </AppContainer>) :
-      this.props.children;
+    const innerChildren = __DEV__ ? (
+      <AppContainer rootTag={this.context.rootTag}>
+        {this.props.children}
+      </AppContainer>
+    ) : (
+      this.props.children
+    );
 
     return (
       <RCTModalHostView
@@ -214,11 +244,8 @@ class Modal extends React.Component<Object> {
         style={styles.modal}
         onStartShouldSetResponder={this._shouldSetResponder}
         supportedOrientations={this.props.supportedOrientations}
-        onOrientationChange={this.props.onOrientationChange}
-        >
-        <View style={[styles.container, containerStyles]}>
-          {innerChildren}
-        </View>
+        onOrientationChange={this.props.onOrientationChange}>
+        <View style={[styles.container, containerStyles]}>{innerChildren}</View>
       </RCTModalHostView>
     );
   }
@@ -236,9 +263,9 @@ const styles = StyleSheet.create({
   },
   container: {
     position: 'absolute',
-    [side] : 0,
+    [side]: 0,
     top: 0,
-  }
+  },
 });
 
 module.exports = Modal;
diff --git a/Libraries/Network/FormData.js b/Libraries/Network/FormData.js
index 40f351c5a5ee..a9de18c067c8 100644
--- a/Libraries/Network/FormData.js
+++ b/Libraries/Network/FormData.js
@@ -4,23 +4,27 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 type FormDataValue = any;
 type FormDataNameValuePair = [string, FormDataValue];
 
 type Headers = {[name: string]: string};
-type FormDataPart = {
-  string: string,
-  headers: Headers,
-} | {
-  uri: string,
-  headers: Headers,
-  name?: string,
-  type?: string,
-};
+type FormDataPart =
+  | {
+      string: string,
+      headers: Headers,
+    }
+  | {
+      uri: string,
+      headers: Headers,
+      name?: string,
+      type?: string,
+    };
 
 /**
  * Polyfill for XMLHttpRequest2 FormData API, allowing multipart POST requests
diff --git a/Libraries/Network/NetInfo.js b/Libraries/Network/NetInfo.js
index 474ce79144e0..6d2363967f3a 100644
--- a/Libraries/Network/NetInfo.js
+++ b/Libraries/Network/NetInfo.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Map = require('Map');
@@ -53,20 +55,19 @@ type ConnectivityStateAndroid = $Enum<{
   UNKNOWN: string,
 }>;
 
-
 const _subscriptions = new Map();
 
 let _isConnectedDeprecated;
 if (Platform.OS === 'ios') {
   _isConnectedDeprecated = function(
     reachability: ReachabilityStateIOS,
-  ): bool {
+  ): boolean {
     return reachability !== 'none' && reachability !== 'unknown';
   };
 } else if (Platform.OS === 'android') {
   _isConnectedDeprecated = function(
-      connectionType: ConnectivityStateAndroid,
-    ): bool {
+    connectionType: ConnectivityStateAndroid,
+  ): boolean {
     return connectionType !== 'NONE' && connectionType !== 'UNKNOWN';
   };
 }
@@ -90,38 +91,40 @@ const NetInfo = {
    */
   addEventListener(
     eventName: ChangeEventName,
-    handler: Function
+    handler: Function,
   ): {remove: () => void} {
     let listener;
     if (eventName === 'connectionChange') {
       listener = NetInfoEventEmitter.addListener(
         DEVICE_CONNECTIVITY_EVENT,
-        (appStateData) => {
+        appStateData => {
           handler({
             type: appStateData.connectionType,
-            effectiveType: appStateData.effectiveConnectionType
+            effectiveType: appStateData.effectiveConnectionType,
           });
-        }
+        },
       );
     } else if (eventName === 'change') {
-      console.warn('NetInfo\'s "change" event is deprecated. Listen to the "connectionChange" event instead.');
+      console.warn(
+        'NetInfo\'s "change" event is deprecated. Listen to the "connectionChange" event instead.',
+      );
 
       listener = NetInfoEventEmitter.addListener(
         DEVICE_CONNECTIVITY_EVENT,
-        (appStateData) => {
+        appStateData => {
           handler(appStateData.network_info);
-        }
+        },
       );
     } else {
       console.warn('Trying to subscribe to unknown event: "' + eventName + '"');
       return {
-        remove: () => {}
+        remove: () => {},
       };
     }
 
     _subscriptions.set(handler, listener);
     return {
-      remove: () => NetInfo.removeEventListener(eventName, handler)
+      remove: () => NetInfo.removeEventListener(eventName, handler),
     };
   },
 
@@ -130,10 +133,7 @@ const NetInfo = {
    *
    * See https://facebook.github.io/react-native/docs/netinfo.html#removeeventlistener
    */
-  removeEventListener(
-    eventName: ChangeEventName,
-    handler: Function
-  ): void {
+  removeEventListener(eventName: ChangeEventName, handler: Function): void {
     const listener = _subscriptions.get(handler);
     if (!listener) {
       return;
@@ -176,7 +176,9 @@ const NetInfo = {
    * be used if necessary.
    */
   fetch(): Promise<any> {
-    console.warn('NetInfo.fetch() is deprecated. Use NetInfo.getConnectionInfo() instead.');
+    console.warn(
+      'NetInfo.fetch() is deprecated. Use NetInfo.getConnectionInfo() instead.',
+    );
     return RCTNetInfo.getCurrentConnectivity().then(resp => resp.network_info);
   },
 
@@ -201,9 +203,9 @@ const NetInfo = {
   isConnected: {
     addEventListener(
       eventName: ChangeEventName,
-      handler: Function
+      handler: Function,
     ): {remove: () => void} {
-      const listener = (connection) => {
+      const listener = connection => {
         if (eventName === 'change') {
           handler(_isConnectedDeprecated(connection));
         } else if (eventName === 'connectionChange') {
@@ -211,26 +213,21 @@ const NetInfo = {
         }
       };
       _isConnectedSubscriptions.set(handler, listener);
-      NetInfo.addEventListener(
-        eventName,
-        listener
-      );
+      NetInfo.addEventListener(eventName, listener);
       return {
-        remove: () => NetInfo.isConnected.removeEventListener(eventName, handler)
+        remove: () =>
+          NetInfo.isConnected.removeEventListener(eventName, handler),
       };
     },
 
-    removeEventListener(
-      eventName: ChangeEventName,
-      handler: Function
-    ): void {
+    removeEventListener(eventName: ChangeEventName, handler: Function): void {
       const listener = _isConnectedSubscriptions.get(handler);
       NetInfo.removeEventListener(
         eventName,
         /* $FlowFixMe(>=0.36.0 site=react_native_fb,react_native_oss) Flow error
          * detected during the deploy of Flow v0.36.0. To see the error, remove
          * this comment and run Flow */
-        listener
+        listener,
       );
       _isConnectedSubscriptions.delete(handler);
     },
@@ -241,9 +238,9 @@ const NetInfo = {
   },
 
   isConnectionExpensive(): Promise<boolean> {
-    return (
-      Platform.OS === 'android' ? RCTNetInfo.isConnectionMetered() : Promise.reject(new Error('Currently not supported on iOS'))
-    );
+    return Platform.OS === 'android'
+      ? RCTNetInfo.isConnectionMetered()
+      : Promise.reject(new Error('Currently not supported on iOS'));
   },
 };
 
diff --git a/Libraries/Network/RCTNetworking.android.js b/Libraries/Network/RCTNetworking.android.js
index 30162a0e88c8..85db7ed6f465 100644
--- a/Libraries/Network/RCTNetworking.android.js
+++ b/Libraries/Network/RCTNetworking.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // Do not require the native RCTNetworking module directly! Use this wrapper module instead.
@@ -39,7 +41,6 @@ function generateRequestId(): number {
  * requestId to each network request that can be used to abort that request later on.
  */
 class RCTNetworking extends NativeEventEmitter {
-
   isAvailable: boolean = true;
 
   constructor() {
@@ -56,11 +57,11 @@ class RCTNetworking extends NativeEventEmitter {
     incrementalUpdates: boolean,
     timeout: number,
     callback: (requestId: number) => any,
-    withCredentials: boolean
+    withCredentials: boolean,
   ) {
     const body = convertRequestBody(data);
     if (body && body.formData) {
-      body.formData = body.formData.map((part) => ({
+      body.formData = body.formData.map(part => ({
         ...part,
         headers: convertHeadersMapToArray(part.headers),
       }));
@@ -75,7 +76,7 @@ class RCTNetworking extends NativeEventEmitter {
       responseType,
       incrementalUpdates,
       timeout,
-      withCredentials
+      withCredentials,
     );
     callback(requestId);
   }
diff --git a/Libraries/Network/RCTNetworking.ios.js b/Libraries/Network/RCTNetworking.ios.js
index 2b834577809e..83f8339ed64a 100644
--- a/Libraries/Network/RCTNetworking.ios.js
+++ b/Libraries/Network/RCTNetworking.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const MissingNativeEventEmitterShim = require('MissingNativeEventEmitterShim');
@@ -15,10 +17,9 @@ const convertRequestBody = require('convertRequestBody');
 
 import type {RequestBody} from 'convertRequestBody';
 
-import type { NativeResponseType } from './XMLHttpRequest';
+import type {NativeResponseType} from './XMLHttpRequest';
 
 class RCTNetworking extends NativeEventEmitter {
-
   isAvailable: boolean = true;
 
   constructor() {
@@ -35,19 +36,22 @@ class RCTNetworking extends NativeEventEmitter {
     incrementalUpdates: boolean,
     timeout: number,
     callback: (requestId: number) => any,
-    withCredentials: boolean
+    withCredentials: boolean,
   ) {
     const body = convertRequestBody(data);
-    RCTNetworkingNative.sendRequest({
-      method,
-      url,
-      data: {...body, trackingName},
-      headers,
-      responseType,
-      incrementalUpdates,
-      timeout,
-      withCredentials
-    }, callback);
+    RCTNetworkingNative.sendRequest(
+      {
+        method,
+        url,
+        data: {...body, trackingName},
+        headers,
+        responseType,
+        incrementalUpdates,
+        timeout,
+        withCredentials,
+      },
+      callback,
+    );
   }
 
   abortRequest(requestId: number) {
diff --git a/Libraries/Network/XHRInterceptor.js b/Libraries/Network/XHRInterceptor.js
index f3dd1e03e084..ced48d391005 100644
--- a/Libraries/Network/XHRInterceptor.js
+++ b/Libraries/Network/XHRInterceptor.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
- 'use strict';
+
+'use strict';
 
 const XMLHttpRequest = require('XMLHttpRequest');
 const originalXHROpen = XMLHttpRequest.prototype.open;
@@ -96,43 +98,48 @@ const XHRInterceptor = {
         sendCallback(data, this);
       }
       if (this.addEventListener) {
-        this.addEventListener('readystatechange', () => {
-          if (!isInterceptorEnabled) {
-            return;
-          }
-          if (this.readyState === this.HEADERS_RECEIVED) {
-            const contentTypeString = this.getResponseHeader('Content-Type');
-            const contentLengthString =
-              this.getResponseHeader('Content-Length');
-            let responseContentType, responseSize;
-            if (contentTypeString) {
-              responseContentType = contentTypeString.split(';')[0];
-            }
-            if (contentLengthString) {
-              responseSize = parseInt(contentLengthString, 10);
+        this.addEventListener(
+          'readystatechange',
+          () => {
+            if (!isInterceptorEnabled) {
+              return;
             }
-            if (headerReceivedCallback) {
-              headerReceivedCallback(
-                responseContentType,
-                responseSize,
-                this.getAllResponseHeaders(),
-                this,
+            if (this.readyState === this.HEADERS_RECEIVED) {
+              const contentTypeString = this.getResponseHeader('Content-Type');
+              const contentLengthString = this.getResponseHeader(
+                'Content-Length',
               );
+              let responseContentType, responseSize;
+              if (contentTypeString) {
+                responseContentType = contentTypeString.split(';')[0];
+              }
+              if (contentLengthString) {
+                responseSize = parseInt(contentLengthString, 10);
+              }
+              if (headerReceivedCallback) {
+                headerReceivedCallback(
+                  responseContentType,
+                  responseSize,
+                  this.getAllResponseHeaders(),
+                  this,
+                );
+              }
             }
-          }
-          if (this.readyState === this.DONE) {
-            if (responseCallback) {
-              responseCallback(
-                this.status,
-                this.timeout,
-                this.response,
-                this.responseURL,
-                this.responseType,
-                this,
-              );
+            if (this.readyState === this.DONE) {
+              if (responseCallback) {
+                responseCallback(
+                  this.status,
+                  this.timeout,
+                  this.response,
+                  this.responseURL,
+                  this.responseType,
+                  this,
+                );
+              }
             }
-          }
-        }, false);
+          },
+          false,
+        );
       }
       originalXHRSend.apply(this, arguments);
     };
diff --git a/Libraries/Network/XMLHttpRequest.js b/Libraries/Network/XMLHttpRequest.js
index afbfc7db68df..e8be40a0ac65 100644
--- a/Libraries/Network/XMLHttpRequest.js
+++ b/Libraries/Network/XMLHttpRequest.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EventTarget = require('event-target-shim');
@@ -23,34 +25,26 @@ const warning = require('fbjs/lib/warning');
 const BlobManager = require('BlobManager');
 
 export type NativeResponseType = 'base64' | 'blob' | 'text';
-export type ResponseType = '' | 'arraybuffer' | 'blob' | 'document' | 'json' | 'text';
+export type ResponseType =
+  | ''
+  | 'arraybuffer'
+  | 'blob'
+  | 'document'
+  | 'json'
+  | 'text';
 export type Response = ?Object | string;
 
 type XHRInterceptor = {
-  requestSent(
-    id: number,
-    url: string,
-    method: string,
-    headers: Object
-  ): void,
+  requestSent(id: number, url: string, method: string, headers: Object): void,
   responseReceived(
     id: number,
     url: string,
     status: number,
-    headers: Object
-  ): void,
-  dataReceived(
-    id: number,
-    data: string
-  ): void,
-  loadingFinished(
-    id: number,
-    encodedDataLength: number
-  ): void,
-  loadingFailed(
-    id: number,
-    error: string
+    headers: Object,
   ): void,
+  dataReceived(id: number, data: string): void,
+  loadingFinished(id: number, encodedDataLength: number): void,
+  loadingFailed(id: number, error: string): void,
 };
 
 // The native blob module is optional so inject it here if available.
@@ -99,7 +93,6 @@ class XMLHttpRequestEventTarget extends EventTarget(...REQUEST_EVENTS) {
  * Shared base for platform-specific XMLHttpRequest implementations.
  */
 class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
-
   static UNSENT: number = UNSENT;
   static OPENED: number = OPENED;
   static HEADERS_RECEIVED: number = HEADERS_RECEIVED;
@@ -129,7 +122,7 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
   status: number = 0;
   timeout: number = 0;
   responseURL: ?string;
-  withCredentials: boolean = true
+  withCredentials: boolean = true;
 
   upload: XMLHttpRequestEventTarget = new XMLHttpRequestEventTarget();
 
@@ -187,14 +180,14 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
   set responseType(responseType: ResponseType): void {
     if (this._sent) {
       throw new Error(
-        'Failed to set the \'responseType\' property on \'XMLHttpRequest\': The ' +
-        'response type cannot be set after the request has been sent.'
+        "Failed to set the 'responseType' property on 'XMLHttpRequest': The " +
+          'response type cannot be set after the request has been sent.',
       );
     }
     if (!SUPPORTED_RESPONSE_TYPES.hasOwnProperty(responseType)) {
       warning(
         false,
-        `The provided value '${responseType}' is not a valid 'responseType'.`
+        `The provided value '${responseType}' is not a valid 'responseType'.`,
       );
       return;
     }
@@ -202,11 +195,14 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
     // redboxes early, e.g. for 'arraybuffer' on ios 7
     invariant(
       SUPPORTED_RESPONSE_TYPES[responseType] || responseType === 'document',
-      `The provided value '${responseType}' is unsupported in this environment.`
+      `The provided value '${responseType}' is unsupported in this environment.`,
     );
 
     if (responseType === 'blob') {
-      invariant(BlobManager.isAvailable, 'Native module BlobModule is required for blob support');
+      invariant(
+        BlobManager.isAvailable,
+        'Native module BlobModule is required for blob support',
+      );
     }
     this._responseType = responseType;
   }
@@ -215,7 +211,7 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
     if (this._responseType !== '' && this._responseType !== 'text') {
       throw new Error(
         "The 'responseText' property is only available if 'responseType' " +
-        `is set to '' or 'text', but it is '${this._responseType}'.`
+          `is set to '' or 'text', but it is '${this._responseType}'.`,
       );
     }
     if (this.readyState < LOADING) {
@@ -227,9 +223,7 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
   get response(): Response {
     const {responseType} = this;
     if (responseType === '' || responseType === 'text') {
-      return this.readyState < LOADING || this._hasError
-        ? ''
-        : this._response;
+      return this.readyState < LOADING || this._hasError ? '' : this._response;
     }
 
     if (this.readyState !== DONE) {
@@ -276,18 +270,20 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
   __didCreateRequest(requestId: number): void {
     this._requestId = requestId;
 
-    XMLHttpRequest._interceptor && XMLHttpRequest._interceptor.requestSent(
-      requestId,
-      this._url || '',
-      this._method || 'GET',
-      this._headers);
+    XMLHttpRequest._interceptor &&
+      XMLHttpRequest._interceptor.requestSent(
+        requestId,
+        this._url || '',
+        this._method || 'GET',
+        this._headers,
+      );
   }
 
   // exposed for testing
   __didUploadProgress(
     requestId: number,
     progress: number,
-    total: number
+    total: number,
   ): void {
     if (requestId === this._requestId) {
       this.upload.dispatchEvent({
@@ -303,7 +299,7 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
     requestId: number,
     status: number,
     responseHeaders: ?Object,
-    responseURL: ?string
+    responseURL: ?string,
   ): void {
     if (requestId === this._requestId) {
       this.status = status;
@@ -315,11 +311,13 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
         delete this.responseURL;
       }
 
-      XMLHttpRequest._interceptor && XMLHttpRequest._interceptor.responseReceived(
-        requestId,
-        responseURL || this._url || '',
-        status,
-        responseHeaders || {});
+      XMLHttpRequest._interceptor &&
+        XMLHttpRequest._interceptor.responseReceived(
+          requestId,
+          responseURL || this._url || '',
+          status,
+          responseHeaders || {},
+        );
     }
   }
 
@@ -331,16 +329,15 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
     this._cachedResponse = undefined; // force lazy recomputation
     this.setReadyState(this.LOADING);
 
-    XMLHttpRequest._interceptor && XMLHttpRequest._interceptor.dataReceived(
-      requestId,
-      response);
+    XMLHttpRequest._interceptor &&
+      XMLHttpRequest._interceptor.dataReceived(requestId, response);
   }
 
   __didReceiveIncrementalData(
     requestId: number,
     responseText: string,
     progress: number,
-    total: number
+    total: number,
   ) {
     if (requestId !== this._requestId) {
       return;
@@ -351,9 +348,8 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
       this._response += responseText;
     }
 
-    XMLHttpRequest._interceptor && XMLHttpRequest._interceptor.dataReceived(
-      requestId,
-      responseText);
+    XMLHttpRequest._interceptor &&
+      XMLHttpRequest._interceptor.dataReceived(requestId, responseText);
 
     this.setReadyState(this.LOADING);
     this.__didReceiveDataProgress(requestId, progress, total);
@@ -362,7 +358,7 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
   __didReceiveDataProgress(
     requestId: number,
     loaded: number,
-    total: number
+    total: number,
   ): void {
     if (requestId !== this._requestId) {
       return;
@@ -379,7 +375,7 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
   __didCompleteResponse(
     requestId: number,
     error: string,
-    timeOutError: boolean
+    timeOutError: boolean,
   ): void {
     if (requestId === this._requestId) {
       if (error) {
@@ -396,13 +392,14 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
       this.setReadyState(this.DONE);
 
       if (error) {
-        XMLHttpRequest._interceptor && XMLHttpRequest._interceptor.loadingFailed(
-          requestId,
-          error);
+        XMLHttpRequest._interceptor &&
+          XMLHttpRequest._interceptor.loadingFailed(requestId, error);
       } else {
-        XMLHttpRequest._interceptor && XMLHttpRequest._interceptor.loadingFinished(
-          requestId,
-          this._response.length);
+        XMLHttpRequest._interceptor &&
+          XMLHttpRequest._interceptor.loadingFinished(
+            requestId,
+            this._response.length,
+          );
       }
     }
   }
@@ -422,9 +419,11 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
       return null;
     }
     const headers = this.responseHeaders || {};
-    return Object.keys(headers).map((headerName) => {
-      return headerName + ': ' + headers[headerName];
-    }).join('\r\n');
+    return Object.keys(headers)
+      .map(headerName => {
+        return headerName + ': ' + headers[headerName];
+      })
+      .join('\r\n');
   }
 
   getResponseHeader(header: string): ?string {
@@ -473,34 +472,39 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
       throw new Error('Request has already been sent');
     }
     this._sent = true;
-    const incrementalEvents = this._incrementalEvents ||
-      !!this.onreadystatechange ||
-      !!this.onprogress;
-
-    this._subscriptions.push(RCTNetworking.addListener(
-      'didSendNetworkData',
-      (args) => this.__didUploadProgress(...args)
-    ));
-    this._subscriptions.push(RCTNetworking.addListener(
-      'didReceiveNetworkResponse',
-      (args) => this.__didReceiveResponse(...args)
-    ));
-    this._subscriptions.push(RCTNetworking.addListener(
-      'didReceiveNetworkData',
-      (args) => this.__didReceiveData(...args)
-    ));
-    this._subscriptions.push(RCTNetworking.addListener(
-      'didReceiveNetworkIncrementalData',
-      (args) => this.__didReceiveIncrementalData(...args)
-    ));
-    this._subscriptions.push(RCTNetworking.addListener(
-      'didReceiveNetworkDataProgress',
-      (args) => this.__didReceiveDataProgress(...args)
-    ));
-    this._subscriptions.push(RCTNetworking.addListener(
-      'didCompleteNetworkResponse',
-      (args) => this.__didCompleteResponse(...args)
-    ));
+    const incrementalEvents =
+      this._incrementalEvents || !!this.onreadystatechange || !!this.onprogress;
+
+    this._subscriptions.push(
+      RCTNetworking.addListener('didSendNetworkData', args =>
+        this.__didUploadProgress(...args),
+      ),
+    );
+    this._subscriptions.push(
+      RCTNetworking.addListener('didReceiveNetworkResponse', args =>
+        this.__didReceiveResponse(...args),
+      ),
+    );
+    this._subscriptions.push(
+      RCTNetworking.addListener('didReceiveNetworkData', args =>
+        this.__didReceiveData(...args),
+      ),
+    );
+    this._subscriptions.push(
+      RCTNetworking.addListener('didReceiveNetworkIncrementalData', args =>
+        this.__didReceiveIncrementalData(...args),
+      ),
+    );
+    this._subscriptions.push(
+      RCTNetworking.addListener('didReceiveNetworkDataProgress', args =>
+        this.__didReceiveDataProgress(...args),
+      ),
+    );
+    this._subscriptions.push(
+      RCTNetworking.addListener('didCompleteNetworkResponse', args =>
+        this.__didCompleteResponse(...args),
+      ),
+    );
 
     let nativeResponseType: NativeResponseType = 'text';
     if (this._responseType === 'arraybuffer') {
@@ -522,7 +526,7 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
       incrementalEvents,
       this.timeout,
       this.__didCreateRequest.bind(this),
-      this.withCredentials
+      this.withCredentials,
     );
   }
 
@@ -533,9 +537,13 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
     }
     // only call onreadystatechange if there is something to abort,
     // below logic is per spec
-    if (!(this.readyState === this.UNSENT ||
+    if (
+      !(
+        this.readyState === this.UNSENT ||
         (this.readyState === this.OPENED && !this._sent) ||
-        this.readyState === this.DONE)) {
+        this.readyState === this.DONE
+      )
+    ) {
       this._reset();
       this.setReadyState(this.DONE);
     }
@@ -546,11 +554,13 @@ class XMLHttpRequest extends EventTarget(...XHR_EVENTS) {
   setResponseHeaders(responseHeaders: ?Object): void {
     this.responseHeaders = responseHeaders || null;
     const headers = responseHeaders || {};
-    this._lowerCaseResponseHeaders =
-      Object.keys(headers).reduce((lcaseHeaders, headerName) => {
+    this._lowerCaseResponseHeaders = Object.keys(headers).reduce(
+      (lcaseHeaders, headerName) => {
         lcaseHeaders[headerName.toLowerCase()] = headers[headerName];
         return lcaseHeaders;
-      }, {});
+      },
+      {},
+    );
   }
 
   setReadyState(newState: number): void {
diff --git a/Libraries/Network/__tests__/FormData-test.js b/Libraries/Network/__tests__/FormData-test.js
index a2b8eb0e7a4f..7831a1220c66 100644
--- a/Libraries/Network/__tests__/FormData-test.js
+++ b/Libraries/Network/__tests__/FormData-test.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
 
@@ -28,9 +29,9 @@ describe('FormData', function() {
     const expectedPart = {
       string: 'null',
       headers: {
-        'content-disposition': 'form-data; name="null"'
+        'content-disposition': 'form-data; name="null"',
       },
-      fieldName: 'null'
+      fieldName: 'null',
     };
     expect(formData.getParts()[0]).toMatchObject(expectedPart);
   });
@@ -39,7 +40,7 @@ describe('FormData', function() {
     formData.append('photo', {
       uri: 'arbitrary/path',
       type: 'image/jpeg',
-      name: 'photo.jpg'
+      name: 'photo.jpg',
     });
 
     const expectedPart = {
@@ -48,9 +49,9 @@ describe('FormData', function() {
       name: 'photo.jpg',
       headers: {
         'content-disposition': 'form-data; name="photo"; filename="photo.jpg"',
-        'content-type': 'image/jpeg'
+        'content-type': 'image/jpeg',
       },
-      fieldName: 'photo'
+      fieldName: 'photo',
     };
     expect(formData.getParts()[0]).toMatchObject(expectedPart);
   });
diff --git a/Libraries/Network/__tests__/XMLHttpRequest-test.js b/Libraries/Network/__tests__/XMLHttpRequest-test.js
index e4a4ed066494..369fdcb3c63a 100644
--- a/Libraries/Network/__tests__/XMLHttpRequest-test.js
+++ b/Libraries/Network/__tests__/XMLHttpRequest-test.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
 
@@ -12,27 +13,26 @@ jest.unmock('Platform');
 const Platform = require('Platform');
 let requestId = 1;
 
-function setRequestId(id){
+function setRequestId(id) {
   if (Platform.OS === 'ios') {
     return;
   }
   requestId = id;
 }
 
-jest
-  .dontMock('event-target-shim')
-  .setMock('NativeModules', {
-    Networking: {
-      addListener: function() {},
-      removeListeners: function() {},
-      sendRequest(options, callback) {
-        if (typeof callback === 'function') { // android does not pass a callback
-          callback(requestId);
-        }
-      },
-      abortRequest: function() {},
+jest.dontMock('event-target-shim').setMock('NativeModules', {
+  Networking: {
+    addListener: function() {},
+    removeListeners: function() {},
+    sendRequest(options, callback) {
+      if (typeof callback === 'function') {
+        // android does not pass a callback
+        callback(requestId);
+      }
     },
-  });
+    abortRequest: function() {},
+  },
+});
 
 const XMLHttpRequest = require('XMLHttpRequest');
 
@@ -98,7 +98,9 @@ describe('XMLHttpRequest', function() {
     // Can't change responseType after first data has been received.
     xhr.open('GET', 'blabla');
     xhr.send();
-    expect(() => { xhr.responseType = 'text'; }).toThrow();
+    expect(() => {
+      xhr.responseType = 'text';
+    }).toThrow();
   });
 
   it('should expose responseText correctly', function() {
@@ -115,7 +117,9 @@ describe('XMLHttpRequest', function() {
     expect(xhr.response).toBe('');
 
     // responseText is read-only.
-    expect(() => { xhr.responseText = 'hi'; }).toThrow();
+    expect(() => {
+      xhr.responseText = 'hi';
+    }).toThrow();
     expect(xhr.responseText).toBe('');
     expect(xhr.response).toBe('');
 
@@ -217,8 +221,7 @@ describe('XMLHttpRequest', function() {
     });
 
     expect(xhr.getAllResponseHeaders()).toBe(
-      'Content-Type: text/plain; charset=utf-8\r\n' +
-      'Content-Length: 32');
+      'Content-Type: text/plain; charset=utf-8\r\n' + 'Content-Length: 32',
+    );
   });
-
 });
diff --git a/Libraries/Network/fetch.js b/Libraries/Network/fetch.js
index 10be3631d26b..db029ae09987 100644
--- a/Libraries/Network/fetch.js
+++ b/Libraries/Network/fetch.js
@@ -4,10 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- *
+ * @format
  */
 
- /* globals Headers, Request, Response */
+/* globals Headers, Request, Response */
 
 'use strict';
 
diff --git a/Libraries/Performance/QuickPerformanceLogger.js b/Libraries/Performance/QuickPerformanceLogger.js
index bdf6d952e1e8..360d5b96a8a5 100644
--- a/Libraries/Performance/QuickPerformanceLogger.js
+++ b/Libraries/Performance/QuickPerformanceLogger.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -86,7 +87,6 @@ const QuickPerformanceLogger = {
     }
     return 0;
   },
-
 };
 
 module.exports = QuickPerformanceLogger;
diff --git a/Libraries/Performance/SamplingProfiler.js b/Libraries/Performance/SamplingProfiler.js
index ec4323e12575..6dcda029c550 100644
--- a/Libraries/Performance/SamplingProfiler.js
+++ b/Libraries/Performance/SamplingProfiler.js
@@ -4,12 +4,14 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const SamplingProfiler = {
-  poke: function (token: number): void {
+  poke: function(token: number): void {
     let error = null;
     let result = null;
     try {
@@ -21,7 +23,8 @@ const SamplingProfiler = {
       }
     } catch (e) {
       console.log(
-        'Error occurred when restarting Sampling Profiler: ' + e.toString());
+        'Error occurred when restarting Sampling Profiler: ' + e.toString(),
+      );
       error = e.toString();
     }
 
diff --git a/Libraries/PermissionsAndroid/PermissionsAndroid.js b/Libraries/PermissionsAndroid/PermissionsAndroid.js
index 6febce80ffd1..123e6bfdd091 100644
--- a/Libraries/PermissionsAndroid/PermissionsAndroid.js
+++ b/Libraries/PermissionsAndroid/PermissionsAndroid.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeModules = require('NativeModules');
@@ -13,7 +15,7 @@ const NativeModules = require('NativeModules');
 type Rationale = {
   title: string,
   message: string,
-}
+};
 
 type PermissionStatus = 'granted' | 'denied' | 'never_ask_again';
 /**
@@ -36,7 +38,7 @@ class PermissionsAndroid {
       CAMERA: 'android.permission.CAMERA',
       READ_CONTACTS: 'android.permission.READ_CONTACTS',
       WRITE_CONTACTS: 'android.permission.WRITE_CONTACTS',
-      GET_ACCOUNTS:  'android.permission.GET_ACCOUNTS',
+      GET_ACCOUNTS: 'android.permission.GET_ACCOUNTS',
       ACCESS_FINE_LOCATION: 'android.permission.ACCESS_FINE_LOCATION',
       ACCESS_COARSE_LOCATION: 'android.permission.ACCESS_COARSE_LOCATION',
       RECORD_AUDIO: 'android.permission.RECORD_AUDIO',
@@ -47,7 +49,7 @@ class PermissionsAndroid {
       ADD_VOICEMAIL: 'com.android.voicemail.permission.ADD_VOICEMAIL',
       USE_SIP: 'android.permission.USE_SIP',
       PROCESS_OUTGOING_CALLS: 'android.permission.PROCESS_OUTGOING_CALLS',
-      BODY_SENSORS:  'android.permission.BODY_SENSORS',
+      BODY_SENSORS: 'android.permission.BODY_SENSORS',
       SEND_SMS: 'android.permission.SEND_SMS',
       RECEIVE_SMS: 'android.permission.RECEIVE_SMS',
       READ_SMS: 'android.permission.READ_SMS',
@@ -72,8 +74,10 @@ class PermissionsAndroid {
    *
    * @deprecated
    */
-  checkPermission(permission: string) : Promise<boolean> {
-    console.warn('"PermissionsAndroid.checkPermission" is deprecated. Use "PermissionsAndroid.check" instead');
+  checkPermission(permission: string): Promise<boolean> {
+    console.warn(
+      '"PermissionsAndroid.checkPermission" is deprecated. Use "PermissionsAndroid.check" instead',
+    );
     return NativeModules.PermissionsAndroid.checkPermission(permission);
   }
 
@@ -83,7 +87,7 @@ class PermissionsAndroid {
    *
    * See https://facebook.github.io/react-native/docs/permissionsandroid.html#check
    */
-  check(permission: string) : Promise<boolean> {
+  check(permission: string): Promise<boolean> {
     return NativeModules.PermissionsAndroid.checkPermission(permission);
   }
 
@@ -101,10 +105,15 @@ class PermissionsAndroid {
    *
    * @deprecated
    */
-  async requestPermission(permission: string, rationale?: Rationale) : Promise<boolean> {
-    console.warn('"PermissionsAndroid.requestPermission" is deprecated. Use "PermissionsAndroid.request" instead');
+  async requestPermission(
+    permission: string,
+    rationale?: Rationale,
+  ): Promise<boolean> {
+    console.warn(
+      '"PermissionsAndroid.requestPermission" is deprecated. Use "PermissionsAndroid.request" instead',
+    );
     const response = await this.request(permission, rationale);
-    return (response === this.RESULTS.GRANTED);
+    return response === this.RESULTS.GRANTED;
   }
 
   /**
@@ -113,16 +122,24 @@ class PermissionsAndroid {
    *
    * See https://facebook.github.io/react-native/docs/permissionsandroid.html#request
    */
-  async request(permission: string, rationale?: Rationale) : Promise<PermissionStatus> {
+  async request(
+    permission: string,
+    rationale?: Rationale,
+  ): Promise<PermissionStatus> {
     if (rationale) {
-      const shouldShowRationale = await NativeModules.PermissionsAndroid.shouldShowRequestPermissionRationale(permission);
+      const shouldShowRationale = await NativeModules.PermissionsAndroid.shouldShowRequestPermissionRationale(
+        permission,
+      );
 
       if (shouldShowRationale) {
         return new Promise((resolve, reject) => {
           NativeModules.DialogManagerAndroid.showAlert(
             rationale,
             () => reject(new Error('Error showing rationale')),
-            () => resolve(NativeModules.PermissionsAndroid.requestPermission(permission))
+            () =>
+              resolve(
+                NativeModules.PermissionsAndroid.requestPermission(permission),
+              ),
           );
         });
       }
@@ -137,8 +154,12 @@ class PermissionsAndroid {
    *
    * See https://facebook.github.io/react-native/docs/permissionsandroid.html#requestmultiple
    */
-  requestMultiple(permissions: Array<string>) : Promise<{[permission: string]: PermissionStatus}> {
-    return NativeModules.PermissionsAndroid.requestMultiplePermissions(permissions);
+  requestMultiple(
+    permissions: Array<string>,
+  ): Promise<{[permission: string]: PermissionStatus}> {
+    return NativeModules.PermissionsAndroid.requestMultiplePermissions(
+      permissions,
+    );
   }
 }
 
diff --git a/Libraries/Promise.js b/Libraries/Promise.js
index aee5ad7e7d0c..2581435a6194 100644
--- a/Libraries/Promise.js
+++ b/Libraries/Promise.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
@@ -40,7 +42,7 @@ if (__DEV__) {
         (stack == null ? '' : stack);
       console.warn(warning);
     },
-    onHandled: (id) => {
+    onHandled: id => {
       const warning =
         `Promise Rejection Handled (id: ${id})\n` +
         'This means you can ignore any previous messages of the form ' +
diff --git a/Libraries/PushNotificationIOS/PushNotificationIOS.js b/Libraries/PushNotificationIOS/PushNotificationIOS.js
index fc3db58f2974..0b66fe4d9b64 100644
--- a/Libraries/PushNotificationIOS/PushNotificationIOS.js
+++ b/Libraries/PushNotificationIOS/PushNotificationIOS.js
@@ -4,15 +4,20 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeEventEmitter = require('NativeEventEmitter');
-const RCTPushNotificationManager = require('NativeModules').PushNotificationManager;
+const RCTPushNotificationManager = require('NativeModules')
+  .PushNotificationManager;
 const invariant = require('fbjs/lib/invariant');
 
-const PushNotificationEmitter = new NativeEventEmitter(RCTPushNotificationManager);
+const PushNotificationEmitter = new NativeEventEmitter(
+  RCTPushNotificationManager,
+);
 
 const _notifHandlers = new Map();
 
@@ -122,7 +127,9 @@ class PushNotificationIOS {
    *
    * See https://facebook.github.io/react-native/docs/pushnotificationios.html#getdeliverednotifications
    */
-  static getDeliveredNotifications(callback: (notifications: Array<Object>) => void): void {
+  static getDeliveredNotifications(
+    callback: (notifications: Array<Object>) => void,
+  ): void {
     RCTPushNotificationManager.getDeliveredNotifications(callback);
   }
 
@@ -179,37 +186,40 @@ class PushNotificationIOS {
    */
   static addEventListener(type: PushNotificationEventName, handler: Function) {
     invariant(
-      type === 'notification' || type === 'register' || type === 'registrationError' || type === 'localNotification',
-      'PushNotificationIOS only supports `notification`, `register`, `registrationError`, and `localNotification` events'
+      type === 'notification' ||
+        type === 'register' ||
+        type === 'registrationError' ||
+        type === 'localNotification',
+      'PushNotificationIOS only supports `notification`, `register`, `registrationError`, and `localNotification` events',
     );
     let listener;
     if (type === 'notification') {
-      listener =  PushNotificationEmitter.addListener(
+      listener = PushNotificationEmitter.addListener(
         DEVICE_NOTIF_EVENT,
-        (notifData) => {
+        notifData => {
           handler(new PushNotificationIOS(notifData));
-        }
+        },
       );
     } else if (type === 'localNotification') {
       listener = PushNotificationEmitter.addListener(
         DEVICE_LOCAL_NOTIF_EVENT,
-        (notifData) => {
+        notifData => {
           handler(new PushNotificationIOS(notifData));
-        }
+        },
       );
     } else if (type === 'register') {
       listener = PushNotificationEmitter.addListener(
         NOTIF_REGISTER_EVENT,
-        (registrationInfo) => {
+        registrationInfo => {
           handler(registrationInfo.deviceToken);
-        }
+        },
       );
     } else if (type === 'registrationError') {
       listener = PushNotificationEmitter.addListener(
         NOTIF_REGISTRATION_ERROR_EVENT,
-        (errorInfo) => {
+        errorInfo => {
           handler(errorInfo);
-        }
+        },
       );
     }
     _notifHandlers.set(type, listener);
@@ -221,10 +231,16 @@ class PushNotificationIOS {
    *
    * See https://facebook.github.io/react-native/docs/pushnotificationios.html#removeeventlistener
    */
-  static removeEventListener(type: PushNotificationEventName, handler: Function) {
+  static removeEventListener(
+    type: PushNotificationEventName,
+    handler: Function,
+  ) {
     invariant(
-      type === 'notification' || type === 'register' || type === 'registrationError' || type === 'localNotification',
-      'PushNotificationIOS only supports `notification`, `register`, `registrationError`, and `localNotification` events'
+      type === 'notification' ||
+        type === 'register' ||
+        type === 'registrationError' ||
+        type === 'localNotification',
+      'PushNotificationIOS only supports `notification`, `register`, `registrationError`, and `localNotification` events',
     );
     const listener = _notifHandlers.get(type);
     if (!listener) {
@@ -245,24 +261,24 @@ class PushNotificationIOS {
   static requestPermissions(permissions?: {
     alert?: boolean,
     badge?: boolean,
-    sound?: boolean
+    sound?: boolean,
   }): Promise<{
     alert: boolean,
     badge: boolean,
-    sound: boolean
+    sound: boolean,
   }> {
     let requestedPermissions = {};
     if (permissions) {
       requestedPermissions = {
         alert: !!permissions.alert,
         badge: !!permissions.badge,
-        sound: !!permissions.sound
+        sound: !!permissions.sound,
       };
     } else {
       requestedPermissions = {
         alert: true,
         badge: true,
-        sound: true
+        sound: true,
       };
     }
     return RCTPushNotificationManager.requestPermissions(requestedPermissions);
@@ -284,10 +300,7 @@ class PushNotificationIOS {
    * See https://facebook.github.io/react-native/docs/pushnotificationios.html#checkpermissions
    */
   static checkPermissions(callback: Function) {
-    invariant(
-      typeof callback === 'function',
-      'Must provide a valid callback'
-    );
+    invariant(typeof callback === 'function', 'Must provide a valid callback');
     RCTPushNotificationManager.checkPermissions(callback);
   }
 
@@ -298,9 +311,11 @@ class PushNotificationIOS {
    * See https://facebook.github.io/react-native/docs/pushnotificationios.html#getinitialnotification
    */
   static getInitialNotification(): Promise<?PushNotificationIOS> {
-    return RCTPushNotificationManager.getInitialNotification().then(notification => {
-      return notification && new PushNotificationIOS(notification);
-    });
+    return RCTPushNotificationManager.getInitialNotification().then(
+      notification => {
+        return notification && new PushNotificationIOS(notification);
+      },
+    );
   }
 
   /**
@@ -320,7 +335,7 @@ class PushNotificationIOS {
     if (nativeNotif.remote) {
       // Extract data from Apple's `aps` dict as defined:
       // https://developer.apple.com/library/ios/documentation/NetworkingInternet/Conceptual/RemoteNotificationsPG/Chapters/ApplePushService.html
-      Object.keys(nativeNotif).forEach((notifKey) => {
+      Object.keys(nativeNotif).forEach(notifKey => {
         const notifVal = nativeNotif[notifKey];
         if (notifKey === 'aps') {
           this._alert = notifVal.alert;
@@ -350,12 +365,19 @@ class PushNotificationIOS {
    * See https://facebook.github.io/react-native/docs/pushnotificationios.html#finish
    */
   finish(fetchResult: string) {
-    if (!this._isRemote || !this._notificationId || this._remoteNotificationCompleteCallbackCalled) {
+    if (
+      !this._isRemote ||
+      !this._notificationId ||
+      this._remoteNotificationCompleteCallbackCalled
+    ) {
       return;
     }
     this._remoteNotificationCompleteCallbackCalled = true;
 
-    RCTPushNotificationManager.onFinishRemoteNotification(this._notificationId, fetchResult);
+    RCTPushNotificationManager.onFinishRemoteNotification(
+      this._notificationId,
+      fetchResult,
+    );
   }
 
   /**
diff --git a/Libraries/RCTTest/SnapshotViewIOS.android.js b/Libraries/RCTTest/SnapshotViewIOS.android.js
index ebd42dd5b18b..260d55992979 100644
--- a/Libraries/RCTTest/SnapshotViewIOS.android.js
+++ b/Libraries/RCTTest/SnapshotViewIOS.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('UnimplementedView');
diff --git a/Libraries/RCTTest/SnapshotViewIOS.ios.js b/Libraries/RCTTest/SnapshotViewIOS.ios.js
index 0a2877a9d642..55cc78424ecc 100644
--- a/Libraries/RCTTest/SnapshotViewIOS.ios.js
+++ b/Libraries/RCTTest/SnapshotViewIOS.ios.js
@@ -4,14 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
 const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
-const { TestModule } = require('NativeModules');
+const {TestModule} = require('NativeModules');
 const UIManager = require('UIManager');
 const View = require('View');
 
@@ -27,9 +29,9 @@ class SnapshotViewIOS extends React.Component<{
   static propTypes = {
     ...ViewPropTypes,
     // A callback when the Snapshot view is ready to be compared
-    onSnapshotReady : PropTypes.func,
+    onSnapshotReady: PropTypes.func,
     // A name to identify the individual instance to the SnapshotView
-    testIdentifier : PropTypes.string,
+    testIdentifier: PropTypes.string,
   };
 
   onDefaultAction = (event: Object) => {
@@ -59,8 +61,8 @@ const style = StyleSheet.create({
 // Verify that RCTSnapshot is part of the UIManager since it is only loaded
 // if you have linked against RCTTest like in tests, otherwise we will have
 // a warning printed out
-const RCTSnapshot = UIManager.RCTSnapshot ?
-  requireNativeComponent('RCTSnapshot', SnapshotViewIOS) :
-  View;
+const RCTSnapshot = UIManager.RCTSnapshot
+  ? requireNativeComponent('RCTSnapshot', SnapshotViewIOS)
+  : View;
 
 module.exports = SnapshotViewIOS;
diff --git a/Libraries/ReactNative/UIManager.js b/Libraries/ReactNative/UIManager.js
index 5f6c61619d9b..d137f757b326 100644
--- a/Libraries/ReactNative/UIManager.js
+++ b/Libraries/ReactNative/UIManager.js
@@ -81,14 +81,21 @@ if (Platform.OS === 'ios') {
   // However, the way things are set up, the list of view managers is not known at compile time.
   // As Prepack runs at compile it, it cannot process this loop.
   // So we wrap it in a special __residual call, which basically tells Prepack to ignore it.
-  let residual = global.__residual ? global.__residual : (_, f, ...args) => f.apply(undefined, args);
-  residual("void", (UIManager, defineLazyObjectProperty) => {
-    UIManager.ViewManagerNames.forEach(viewManagerName => {
-      defineLazyObjectProperty(UIManager, viewManagerName, {
-        get: () => UIManager.getConstantsForViewManager(viewManagerName),
+  let residual = global.__residual
+    ? global.__residual
+    : (_, f, ...args) => f.apply(undefined, args);
+  residual(
+    'void',
+    (UIManager, defineLazyObjectProperty) => {
+      UIManager.ViewManagerNames.forEach(viewManagerName => {
+        defineLazyObjectProperty(UIManager, viewManagerName, {
+          get: () => UIManager.getConstantsForViewManager(viewManagerName),
+        });
       });
-    });
-  }, UIManager, defineLazyObjectProperty);
+    },
+    UIManager,
+    defineLazyObjectProperty,
+  );
 
   // As Prepack now no longer knows which properties exactly the UIManager has,
   // we also tell Prepack that it has only partial knowledge of the UIManager,
diff --git a/Libraries/Sample/Sample.android.js b/Libraries/Sample/Sample.android.js
index 61b3948415b8..d74ef832ae4a 100644
--- a/Libraries/Sample/Sample.android.js
+++ b/Libraries/Sample/Sample.android.js
@@ -1,8 +1,10 @@
 /**
  * Stub of Sample for Android.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const warning = require('fbjs/lib/warning');
@@ -10,7 +12,7 @@ const warning = require('fbjs/lib/warning');
 const Sample = {
   test: function() {
     warning('Not yet implemented for Android.');
-  }
+  },
 };
 
 module.exports = Sample;
diff --git a/Libraries/Sample/Sample.ios.js b/Libraries/Sample/Sample.ios.js
index 0e459eb90ae3..061c4262236f 100644
--- a/Libraries/Sample/Sample.ios.js
+++ b/Libraries/Sample/Sample.ios.js
@@ -1,6 +1,8 @@
 /**
+ * @format
  * @flow
  */
+
 'use strict';
 
 const NativeSample = require('NativeModules').Sample;
@@ -12,7 +14,7 @@ const NativeSample = require('NativeModules').Sample;
 const Sample = {
   test: function() {
     NativeSample.test();
-  }
+  },
 };
 
 module.exports = Sample;
diff --git a/Libraries/Settings/Settings.android.js b/Libraries/Settings/Settings.android.js
index c87accba5834..1e6708a182a5 100644
--- a/Libraries/Settings/Settings.android.js
+++ b/Libraries/Settings/Settings.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Settings = {
diff --git a/Libraries/Settings/Settings.ios.js b/Libraries/Settings/Settings.ios.js
index d0c893ddfb6d..439f8850dd08 100644
--- a/Libraries/Settings/Settings.ios.js
+++ b/Libraries/Settings/Settings.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
@@ -34,7 +36,7 @@ const Settings = {
 
     invariant(
       Array.isArray(keys),
-      'keys should be a string or array of strings'
+      'keys should be a string or array of strings',
     );
 
     const sid = subscriptions.length;
@@ -49,13 +51,13 @@ const Settings = {
   },
 
   _sendObservations(body: Object) {
-    Object.keys(body).forEach((key) => {
+    Object.keys(body).forEach(key => {
       const newValue = body[key];
       const didChange = this._settings[key] !== newValue;
       this._settings[key] = newValue;
 
       if (didChange) {
-        subscriptions.forEach((sub) => {
+        subscriptions.forEach(sub => {
           if (sub.keys.indexOf(key) !== -1 && sub.callback) {
             sub.callback();
           }
@@ -67,7 +69,7 @@ const Settings = {
 
 RCTDeviceEventEmitter.addListener(
   'settingsUpdated',
-  Settings._sendObservations.bind(Settings)
+  Settings._sendObservations.bind(Settings),
 );
 
 module.exports = Settings;
diff --git a/Libraries/Share/Share.js b/Libraries/Share/Share.js
index b6066c11da54..5018170e6ac2 100644
--- a/Libraries/Share/Share.js
+++ b/Libraries/Share/Share.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Platform = require('Platform');
@@ -13,21 +15,19 @@ const Platform = require('Platform');
 const invariant = require('fbjs/lib/invariant');
 const processColor = require('processColor');
 
-const {
-  ActionSheetManager,
-  ShareModule
-} = require('NativeModules');
+const {ActionSheetManager, ShareModule} = require('NativeModules');
 
-type Content = { title?: string, message: string } | { title?: string, url: string };
+type Content =
+  | {title?: string, message: string}
+  | {title?: string, url: string};
 type Options = {
   dialogTitle?: string,
   excludedActivityTypes?: Array<string>,
   tintColor?: string,
-  subject?: string
+  subject?: string,
 };
 
 class Share {
-
   /**
    * Open a dialog to share text content.
    *
@@ -64,40 +64,40 @@ class Share {
   static share(content: Content, options: Options = {}): Promise<Object> {
     invariant(
       typeof content === 'object' && content !== null,
-      'Content to share must be a valid object'
+      'Content to share must be a valid object',
     );
     invariant(
       typeof content.url === 'string' || typeof content.message === 'string',
-      'At least one of URL and message is required'
+      'At least one of URL and message is required',
     );
     invariant(
       typeof options === 'object' && options !== null,
-      'Options must be a valid object'
+      'Options must be a valid object',
     );
 
     if (Platform.OS === 'android') {
       invariant(
         !content.title || typeof content.title === 'string',
-        'Invalid title: title should be a string.'
+        'Invalid title: title should be a string.',
       );
       return ShareModule.share(content, options.dialogTitle);
     } else if (Platform.OS === 'ios') {
       return new Promise((resolve, reject) => {
         ActionSheetManager.showShareActionSheetWithOptions(
           {...content, ...options, tintColor: processColor(options.tintColor)},
-          (error) => reject(error),
+          error => reject(error),
           (success, activityType) => {
             if (success) {
               resolve({
-                'action': 'sharedAction',
-                'activityType': activityType
+                action: 'sharedAction',
+                activityType: activityType,
               });
             } else {
               resolve({
-                'action': 'dismissedAction'
+                action: 'dismissedAction',
               });
             }
-          }
+          },
         );
       });
     } else {
@@ -108,14 +108,17 @@ class Share {
   /**
    * The content was successfully shared.
    */
-  static get sharedAction(): string { return 'sharedAction'; }
+  static get sharedAction(): string {
+    return 'sharedAction';
+  }
 
   /**
    * The dialog has been dismissed.
    * @platform ios
    */
-  static get dismissedAction(): string { return 'dismissedAction'; }
-
+  static get dismissedAction(): string {
+    return 'dismissedAction';
+  }
 }
 
 module.exports = Share;
diff --git a/Libraries/Storage/AsyncStorage.js b/Libraries/Storage/AsyncStorage.js
index ed5042edd934..0877e9b099f3 100644
--- a/Libraries/Storage/AsyncStorage.js
+++ b/Libraries/Storage/AsyncStorage.js
@@ -4,16 +4,19 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @noflow
  * @flow-weak
  * @jsdoc
  */
+
 'use strict';
 
 const NativeModules = require('NativeModules');
 
 // Use RocksDB if available, then SQLite, then file storage.
-const RCTAsyncStorage = NativeModules.AsyncRocksDBStorage ||
+const RCTAsyncStorage =
+  NativeModules.AsyncRocksDBStorage ||
   NativeModules.AsyncSQLiteDBStorage ||
   NativeModules.AsyncLocalStorage;
 
@@ -36,12 +39,12 @@ const AsyncStorage = {
    */
   getItem: function(
     key: string,
-    callback?: ?(error: ?Error, result: ?string) => void
+    callback?: ?(error: ?Error, result: ?string) => void,
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiGet([key], function(errors, result) {
         // Unpack result to get value from [[key,value]]
-        const value = (result && result[0] && result[0][1]) ? result[0][1] : null;
+        const value = result && result[0] && result[0][1] ? result[0][1] : null;
         const errs = convertErrors(errors);
         callback && callback(errs && errs[0], value);
         if (errs) {
@@ -61,10 +64,10 @@ const AsyncStorage = {
   setItem: function(
     key: string,
     value: string,
-    callback?: ?(error: ?Error) => void
+    callback?: ?(error: ?Error) => void,
   ): Promise {
     return new Promise((resolve, reject) => {
-      RCTAsyncStorage.multiSet([[key,value]], function(errors) {
+      RCTAsyncStorage.multiSet([[key, value]], function(errors) {
         const errs = convertErrors(errors);
         callback && callback(errs && errs[0]);
         if (errs) {
@@ -83,7 +86,7 @@ const AsyncStorage = {
    */
   removeItem: function(
     key: string,
-    callback?: ?(error: ?Error) => void
+    callback?: ?(error: ?Error) => void,
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiRemove([key], function(errors) {
@@ -109,10 +112,10 @@ const AsyncStorage = {
   mergeItem: function(
     key: string,
     value: string,
-    callback?: ?(error: ?Error) => void
+    callback?: ?(error: ?Error) => void,
   ): Promise {
     return new Promise((resolve, reject) => {
-      RCTAsyncStorage.multiMerge([[key,value]], function(errors) {
+      RCTAsyncStorage.multiMerge([[key, value]], function(errors) {
         const errs = convertErrors(errors);
         callback && callback(errs && errs[0]);
         if (errs) {
@@ -135,7 +138,7 @@ const AsyncStorage = {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.clear(function(error) {
         callback && callback(convertError(error));
-        if (error && convertError(error)){
+        if (error && convertError(error)) {
           reject(convertError(error));
         } else {
           resolve(null);
@@ -149,7 +152,9 @@ const AsyncStorage = {
    *
    * See http://facebook.github.io/react-native/docs/asyncstorage.html#getallkeys
    */
-  getAllKeys: function(callback?: ?(error: ?Error, keys: ?Array<string>) => void): Promise {
+  getAllKeys: function(
+    callback?: ?(error: ?Error, keys: ?Array<string>) => void,
+  ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.getAllKeys(function(error, keys) {
         callback && callback(convertError(error), keys);
@@ -192,7 +197,11 @@ const AsyncStorage = {
       // Is there a way to avoid using the map but fix the bug in this breaking test?
       // https://github.com/facebook/react-native/commit/8dd8ad76579d7feef34c014d387bf02065692264
       const map = {};
-      result && result.forEach(([key, value]) => { map[key] = value; return value; });
+      result &&
+        result.forEach(([key, value]) => {
+          map[key] = value;
+          return value;
+        });
       const reqLength = getRequests.length;
       for (let i = 0; i < reqLength; i++) {
         const request = getRequests[i];
@@ -213,7 +222,7 @@ const AsyncStorage = {
    */
   multiGet: function(
     keys: Array<string>,
-    callback?: ?(errors: ?Array<Error>, result: ?Array<Array<string>>) => void
+    callback?: ?(errors: ?Array<Error>, result: ?Array<Array<string>>) => void,
   ): Promise {
     if (!this._immediate) {
       this._immediate = setImmediate(() => {
@@ -255,7 +264,7 @@ const AsyncStorage = {
    */
   multiSet: function(
     keyValuePairs: Array<Array<string>>,
-    callback?: ?(errors: ?Array<Error>) => void
+    callback?: ?(errors: ?Array<Error>) => void,
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiSet(keyValuePairs, function(errors) {
@@ -277,7 +286,7 @@ const AsyncStorage = {
    */
   multiRemove: function(
     keys: Array<string>,
-    callback?: ?(errors: ?Array<Error>) => void
+    callback?: ?(errors: ?Array<Error>) => void,
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiRemove(keys, function(errors) {
@@ -302,7 +311,7 @@ const AsyncStorage = {
    */
   multiMerge: function(
     keyValuePairs: Array<Array<string>>,
-    callback?: ?(errors: ?Array<Error>) => void
+    callback?: ?(errors: ?Array<Error>) => void,
   ): Promise {
     return new Promise((resolve, reject) => {
       RCTAsyncStorage.multiMerge(keyValuePairs, function(errors) {
@@ -328,7 +337,7 @@ function convertErrors(errs) {
   if (!errs) {
     return null;
   }
-  return (Array.isArray(errs) ? errs : [errs]).map((e) => convertError(e));
+  return (Array.isArray(errs) ? errs : [errs]).map(e => convertError(e));
 }
 
 function convertError(error) {
diff --git a/Libraries/StyleSheet/ColorPropType.js b/Libraries/StyleSheet/ColorPropType.js
index 562d3ad89ff8..93474c47ae23 100644
--- a/Libraries/StyleSheet/ColorPropType.js
+++ b/Libraries/StyleSheet/ColorPropType.js
@@ -4,18 +4,32 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const normalizeColor = require('normalizeColor');
 
-const colorPropType = function(isRequired, props, propName, componentName, location, propFullName) {
+const colorPropType = function(
+  isRequired,
+  props,
+  propName,
+  componentName,
+  location,
+  propFullName,
+) {
   const color = props[propName];
   if (color === undefined || color === null) {
     if (isRequired) {
       return new Error(
-        'Required ' + location + ' `' + (propFullName || propName) +
-        '` was not specified in `' + componentName + '`.'
+        'Required ' +
+          location +
+          ' `' +
+          (propFullName || propName) +
+          '` was not specified in `' +
+          componentName +
+          '`.',
       );
     }
     return;
@@ -30,9 +44,16 @@ const colorPropType = function(isRequired, props, propName, componentName, locat
 
   if (normalizeColor(color) === null) {
     return new Error(
-      'Invalid ' + location + ' `' + (propFullName || propName) +
-      '` supplied to `' + componentName + '`: ' + color + '\n' +
-`Valid color formats are
+      'Invalid ' +
+        location +
+        ' `' +
+        (propFullName || propName) +
+        '` supplied to `' +
+        componentName +
+        '`: ' +
+        color +
+        '\n' +
+        `Valid color formats are
   - '#f0f' (#rgb)
   - '#f0fc' (#rgba)
   - '#ff00ff' (#rrggbb)
@@ -44,7 +65,8 @@ const colorPropType = function(isRequired, props, propName, componentName, locat
   - 'transparent'
   - 'red'
   - 0xff00ff00 (0xrrggbbaa)
-`);
+`,
+    );
   }
 };
 
diff --git a/Libraries/StyleSheet/EdgeInsetsPropType.js b/Libraries/StyleSheet/EdgeInsetsPropType.js
index 0bab3a58e65a..01e8919e6c26 100644
--- a/Libraries/StyleSheet/EdgeInsetsPropType.js
+++ b/Libraries/StyleSheet/EdgeInsetsPropType.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const PropTypes = require('prop-types');
diff --git a/Libraries/StyleSheet/LayoutPropTypes.js b/Libraries/StyleSheet/LayoutPropTypes.js
index aa755aa4473d..4a12e827dde7 100644
--- a/Libraries/StyleSheet/LayoutPropTypes.js
+++ b/Libraries/StyleSheet/LayoutPropTypes.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ReactPropTypes = require('prop-types');
@@ -29,10 +31,7 @@ const LayoutPropTypes = {
    *  It works similarly to `display` in CSS, but only support 'flex' and 'none'.
    *  'flex' is the default.
    */
-  display: ReactPropTypes.oneOf([
-    'none',
-    'flex',
-  ]),
+  display: ReactPropTypes.oneOf(['none', 'flex']),
 
   /** `width` sets the width of this component.
    *
@@ -73,10 +72,7 @@ const LayoutPropTypes = {
    *
    * This style takes precedence over the `left` and `right` styles.
    */
-  end: ReactPropTypes.oneOfType([
-    ReactPropTypes.number,
-    ReactPropTypes.string,
-  ]),
+  end: ReactPropTypes.oneOfType([ReactPropTypes.number, ReactPropTypes.string]),
 
   /** `top` is the number of logical pixels to offset the top edge of
    *  this component.
@@ -87,10 +83,7 @@ const LayoutPropTypes = {
    *  See https://developer.mozilla.org/en-US/docs/Web/CSS/top
    *  for more details of how `top` affects layout.
    */
-  top: ReactPropTypes.oneOfType([
-    ReactPropTypes.number,
-    ReactPropTypes.string,
-  ]),
+  top: ReactPropTypes.oneOfType([ReactPropTypes.number, ReactPropTypes.string]),
 
   /** `left` is the number of logical pixels to offset the left edge of
    *  this component.
@@ -404,10 +397,7 @@ const LayoutPropTypes = {
    *  for more details on how `position` differs between React Native
    *  and CSS.
    */
-  position: ReactPropTypes.oneOf([
-    'absolute',
-    'relative'
-  ]),
+  position: ReactPropTypes.oneOf(['absolute', 'relative']),
 
   /** `flexDirection` controls which directions children of a container go.
    *  `row` goes left to right, `column` goes top to bottom, and you may
@@ -420,7 +410,7 @@ const LayoutPropTypes = {
     'row',
     'row-reverse',
     'column',
-    'column-reverse'
+    'column-reverse',
   ]),
 
   /** `flexWrap` controls whether children can wrap around after they
@@ -429,11 +419,7 @@ const LayoutPropTypes = {
    *  See https://developer.mozilla.org/en-US/docs/Web/CSS/flex-wrap
    *  for more details.
    */
-  flexWrap: ReactPropTypes.oneOf([
-    'wrap',
-    'nowrap',
-    'wrap-reverse'
-  ]),
+  flexWrap: ReactPropTypes.oneOf(['wrap', 'nowrap', 'wrap-reverse']),
 
   /** `justifyContent` aligns children in the main direction.
    *  For example, if children are flowing vertically, `justifyContent`
@@ -448,7 +434,7 @@ const LayoutPropTypes = {
     'center',
     'space-between',
     'space-around',
-    'space-evenly'
+    'space-evenly',
   ]),
 
   /** `alignItems` aligns children in the cross direction.
@@ -463,7 +449,7 @@ const LayoutPropTypes = {
     'flex-end',
     'center',
     'stretch',
-    'baseline'
+    'baseline',
   ]),
 
   /** `alignSelf` controls how a child aligns in the cross direction,
@@ -478,7 +464,7 @@ const LayoutPropTypes = {
     'flex-end',
     'center',
     'stretch',
-    'baseline'
+    'baseline',
   ]),
 
   /** `alignContent` controls how rows align in the cross direction,
@@ -492,7 +478,7 @@ const LayoutPropTypes = {
     'center',
     'stretch',
     'space-between',
-    'space-around'
+    'space-around',
   ]),
 
   /** `overflow` controls how children are measured and displayed.
@@ -504,11 +490,7 @@ const LayoutPropTypes = {
    *  `overflow: visible` only works on iOS. On Android, all views will clip
    *  their children.
    */
-  overflow: ReactPropTypes.oneOf([
-    'visible',
-    'hidden',
-    'scroll',
-  ]),
+  overflow: ReactPropTypes.oneOf(['visible', 'hidden', 'scroll']),
 
   /** In React Native `flex` does not work the same way that it does in CSS.
    *  `flex` is a number rather than a string, and it works
@@ -573,11 +555,7 @@ const LayoutPropTypes = {
    *  for more details.
    *  @platform ios
    */
-  direction: ReactPropTypes.oneOf([
-    'inherit',
-    'ltr',
-    'rtl',
-  ]),
+  direction: ReactPropTypes.oneOf(['inherit', 'ltr', 'rtl']),
 };
 
 module.exports = LayoutPropTypes;
diff --git a/Libraries/StyleSheet/PointPropType.js b/Libraries/StyleSheet/PointPropType.js
index 8a93b6c54642..362f9185cf9e 100644
--- a/Libraries/StyleSheet/PointPropType.js
+++ b/Libraries/StyleSheet/PointPropType.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const PropTypes = require('prop-types');
diff --git a/Libraries/StyleSheet/StyleSheetPropType.js b/Libraries/StyleSheet/StyleSheetPropType.js
index e024c9374fea..964c91b5d4d3 100644
--- a/Libraries/StyleSheet/StyleSheetPropType.js
+++ b/Libraries/StyleSheet/StyleSheetPropType.js
@@ -4,16 +4,18 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const createStrictShapeTypeChecker = require('createStrictShapeTypeChecker');
 const flattenStyle = require('flattenStyle');
 
-function StyleSheetPropType(
-  shape: {[key: string]: ReactPropsCheckType}
-): ReactPropsCheckType {
+function StyleSheetPropType(shape: {
+  [key: string]: ReactPropsCheckType,
+}): ReactPropsCheckType {
   const shapePropType = createStrictShapeTypeChecker(shape);
   return function(props, propName, componentName, location?, ...rest) {
     let newProps = props;
diff --git a/Libraries/StyleSheet/StyleSheetValidation.js b/Libraries/StyleSheet/StyleSheetValidation.js
index c7686dcb9e93..a645c1e36b3b 100644
--- a/Libraries/StyleSheet/StyleSheetValidation.js
+++ b/Libraries/StyleSheet/StyleSheetValidation.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ImageStylePropTypes = require('ImageStylePropTypes');
@@ -27,7 +29,8 @@ class StyleSheetValidation {
     }
     if (allStylePropTypes[prop] === undefined) {
       const message1 = '"' + prop + '" is not a valid style property.';
-      const message2 = '\nValid style props: ' +
+      const message2 =
+        '\nValid style props: ' +
         JSON.stringify(Object.keys(allStylePropTypes).sort(), null, '  ');
       styleError(message1, style, caller, message2);
     }
@@ -49,7 +52,11 @@ class StyleSheetValidation {
       return;
     }
     for (const prop in styles[name]) {
-      StyleSheetValidation.validateStyleProp(prop, styles[name], 'StyleSheet ' + name);
+      StyleSheetValidation.validateStyleProp(
+        prop,
+        styles[name],
+        'StyleSheet ' + name,
+      );
     }
   }
 
@@ -63,8 +70,12 @@ class StyleSheetValidation {
 const styleError = function(message1, style, caller?, message2?) {
   invariant(
     false,
-    message1 + '\n' + (caller || '<<unknown>>') + ': ' +
-    JSON.stringify(style, null, '  ') + (message2 || '')
+    message1 +
+      '\n' +
+      (caller || '<<unknown>>') +
+      ': ' +
+      JSON.stringify(style, null, '  ') +
+      (message2 || ''),
   );
 };
 
diff --git a/Libraries/StyleSheet/TransformPropTypes.js b/Libraries/StyleSheet/TransformPropTypes.js
index 2f9037abf0ad..105df3f073b9 100644
--- a/Libraries/StyleSheet/TransformPropTypes.js
+++ b/Libraries/StyleSheet/TransformPropTypes.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ReactPropTypes = require('prop-types');
@@ -13,27 +15,27 @@ const ReactPropTypes = require('prop-types');
 const deprecatedPropType = require('deprecatedPropType');
 
 const TransformMatrixPropType = function(
-  props : Object,
-  propName : string,
-  componentName : string
-) : ?Error {
+  props: Object,
+  propName: string,
+  componentName: string,
+): ?Error {
   if (props[propName]) {
     return new Error(
       'The transformMatrix style property is deprecated. ' +
-      'Use `transform: [{ matrix: ... }]` instead.'
+        'Use `transform: [{ matrix: ... }]` instead.',
     );
   }
 };
 
 const DecomposedMatrixPropType = function(
-  props : Object,
-  propName : string,
-  componentName : string
-) : ?Error {
+  props: Object,
+  propName: string,
+  componentName: string,
+): ?Error {
   if (props[propName]) {
     return new Error(
       'The decomposedMatrix style property is deprecated. ' +
-      'Use `transform: [...]` instead.'
+        'Use `transform: [...]` instead.',
     );
   }
 };
@@ -68,8 +70,8 @@ const TransformPropTypes = {
       ReactPropTypes.shape({translateX: ReactPropTypes.number}),
       ReactPropTypes.shape({translateY: ReactPropTypes.number}),
       ReactPropTypes.shape({skewX: ReactPropTypes.string}),
-      ReactPropTypes.shape({skewY: ReactPropTypes.string})
-    ])
+      ReactPropTypes.shape({skewY: ReactPropTypes.string}),
+    ]),
   ),
 
   /**
@@ -82,11 +84,26 @@ const TransformPropTypes = {
   decomposedMatrix: DecomposedMatrixPropType,
 
   /* Deprecated transform props used on Android only */
-  scaleX: deprecatedPropType(ReactPropTypes.number, 'Use the transform prop instead.'),
-  scaleY: deprecatedPropType(ReactPropTypes.number, 'Use the transform prop instead.'),
-  rotation: deprecatedPropType(ReactPropTypes.number, 'Use the transform prop instead.'),
-  translateX: deprecatedPropType(ReactPropTypes.number, 'Use the transform prop instead.'),
-  translateY: deprecatedPropType(ReactPropTypes.number, 'Use the transform prop instead.'),
+  scaleX: deprecatedPropType(
+    ReactPropTypes.number,
+    'Use the transform prop instead.',
+  ),
+  scaleY: deprecatedPropType(
+    ReactPropTypes.number,
+    'Use the transform prop instead.',
+  ),
+  rotation: deprecatedPropType(
+    ReactPropTypes.number,
+    'Use the transform prop instead.',
+  ),
+  translateX: deprecatedPropType(
+    ReactPropTypes.number,
+    'Use the transform prop instead.',
+  ),
+  translateY: deprecatedPropType(
+    ReactPropTypes.number,
+    'Use the transform prop instead.',
+  ),
 };
 
 module.exports = TransformPropTypes;
diff --git a/Libraries/StyleSheet/__tests__/flattenStyle-test.js b/Libraries/StyleSheet/__tests__/flattenStyle-test.js
index 0db505ff29b0..fed9be2b5aad 100644
--- a/Libraries/StyleSheet/__tests__/flattenStyle-test.js
+++ b/Libraries/StyleSheet/__tests__/flattenStyle-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const StyleSheet = require('StyleSheet');
diff --git a/Libraries/StyleSheet/__tests__/normalizeColor-test.js b/Libraries/StyleSheet/__tests__/normalizeColor-test.js
index 7edfdb4ac905..65b398ee222d 100644
--- a/Libraries/StyleSheet/__tests__/normalizeColor-test.js
+++ b/Libraries/StyleSheet/__tests__/normalizeColor-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const normalizeColor = require('normalizeColor');
@@ -122,7 +124,7 @@ describe('normalizeColor', function() {
     expect(normalizeColor(0x01234567)).toBe(0x01234567);
   });
 
-  it('should return the same color when it\'s already normalized', function() {
+  it("should return the same color when it's already normalized", function() {
     const normalizedColor = normalizeColor('red') || 0;
     expect(normalizeColor(normalizedColor)).toBe(normalizedColor);
   });
diff --git a/Libraries/StyleSheet/__tests__/processColor-test.js b/Libraries/StyleSheet/__tests__/processColor-test.js
index a353a52a6be9..1d717bf47268 100644
--- a/Libraries/StyleSheet/__tests__/processColor-test.js
+++ b/Libraries/StyleSheet/__tests__/processColor-test.js
@@ -4,36 +4,37 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const {OS} = require('Platform');
 const processColor = require('processColor');
 
-const platformSpecific = OS === 'android'
-  ? unsigned => unsigned | 0 //eslint-disable-line no-bitwise
-  : x => x;
+const platformSpecific =
+  OS === 'android'
+    ? unsigned => unsigned | 0 //eslint-disable-line no-bitwise
+    : x => x;
 
 describe('processColor', () => {
-
   describe('predefined color names', () => {
-
     it('should convert red', () => {
       const colorFromString = processColor('red');
-      const expectedInt = 0xFFFF0000;
+      const expectedInt = 0xffff0000;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
     it('should convert white', () => {
       const colorFromString = processColor('white');
-      const expectedInt = 0xFFFFFFFF;
+      const expectedInt = 0xffffffff;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
     it('should convert black', () => {
       const colorFromString = processColor('black');
-      const expectedInt = 0xFF000000;
+      const expectedInt = 0xff000000;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
 
@@ -45,53 +46,42 @@ describe('processColor', () => {
   });
 
   describe('RGB strings', () => {
-
     it('should convert rgb(x, y, z)', () => {
       const colorFromString = processColor('rgb(10, 20, 30)');
-      const expectedInt = 0xFF0A141E;
+      const expectedInt = 0xff0a141e;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
-
   });
 
   describe('RGBA strings', () => {
-
     it('should convert rgba(x, y, z, a)', () => {
       const colorFromString = processColor('rgba(10, 20, 30, 0.4)');
-      const expectedInt = 0x660A141E;
+      const expectedInt = 0x660a141e;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
-
   });
 
   describe('HSL strings', () => {
-
     it('should convert hsl(x, y%, z%)', () => {
       const colorFromString = processColor('hsl(318, 69%, 55%)');
-      const expectedInt = 0xFFDB3DAC;
+      const expectedInt = 0xffdb3dac;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
-
   });
 
   describe('HSLA strings', () => {
-
     it('should convert hsla(x, y%, z%, a)', () => {
       const colorFromString = processColor('hsla(318, 69%, 55%, 0.25)');
-      const expectedInt = 0x40DB3DAC;
+      const expectedInt = 0x40db3dac;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
-
   });
 
   describe('hex strings', () => {
-
     it('should convert #xxxxxx', () => {
       const colorFromString = processColor('#1e83c9');
-      const expectedInt = 0xFF1E83C9;
+      const expectedInt = 0xff1e83c9;
       expect(colorFromString).toEqual(platformSpecific(expectedInt));
     });
-
   });
-
 });
diff --git a/Libraries/StyleSheet/__tests__/processTransform-test.js b/Libraries/StyleSheet/__tests__/processTransform-test.js
index 2a5c9380a370..08809e94fccc 100644
--- a/Libraries/StyleSheet/__tests__/processTransform-test.js
+++ b/Libraries/StyleSheet/__tests__/processTransform-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const processTransform = require('processTransform');
@@ -26,25 +28,37 @@ describe('processTransform', () => {
     });
 
     it('should throw on object with multiple properties', () => {
-      expect(() => processTransform([{scale: 0.5, translateY: 10}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{scale: 0.5, translateY: 10}]),
+      ).toThrowErrorMatchingSnapshot();
     });
 
     it('should throw on invalid transform property', () => {
-      expect(() => processTransform([{translateW: 10}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{translateW: 10}]),
+      ).toThrowErrorMatchingSnapshot();
     });
 
     it('should throw when not passing an array to an array prop', () => {
-      expect(() => processTransform([{matrix: 'not-a-matrix'}])).toThrowErrorMatchingSnapshot();
-      expect(() => processTransform([{translate: 10}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{matrix: 'not-a-matrix'}]),
+      ).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{translate: 10}]),
+      ).toThrowErrorMatchingSnapshot();
     });
 
     it('should accept a valid matrix', () => {
       processTransform([{matrix: [1, 1, 1, 1, 1, 1, 1, 1, 1]}]);
-      processTransform([{matrix: [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]}]);
+      processTransform([
+        {matrix: [1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]},
+      ]);
     });
 
     it('should throw when passing a matrix of the wrong size', () => {
-      expect(() => processTransform([{matrix: [1, 1, 1, 1]}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{matrix: [1, 1, 1, 1]}]),
+      ).toThrowErrorMatchingSnapshot();
     });
 
     it('should accept a valid translate', () => {
@@ -53,18 +67,30 @@ describe('processTransform', () => {
     });
 
     it('should throw when passing a translate of the wrong size', () => {
-      expect(() => processTransform([{translate: [1]}])).toThrowErrorMatchingSnapshot();
-      expect(() => processTransform([{translate: [1, 1, 1, 1]}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{translate: [1]}]),
+      ).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{translate: [1, 1, 1, 1]}]),
+      ).toThrowErrorMatchingSnapshot();
     });
 
     it('should throw when passing an invalid value to a number prop', () => {
-      expect(() => processTransform([{translateY: '20deg'}])).toThrowErrorMatchingSnapshot();
-      expect(() => processTransform([{scale: {x: 10, y: 10}}])).toThrowErrorMatchingSnapshot();
-      expect(() => processTransform([{perspective: []}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{translateY: '20deg'}]),
+      ).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{scale: {x: 10, y: 10}}]),
+      ).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{perspective: []}]),
+      ).toThrowErrorMatchingSnapshot();
     });
 
     it('should throw when passing a perspective of 0', () => {
-      expect(() => processTransform([{perspective: 0}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{perspective: 0}]),
+      ).toThrowErrorMatchingSnapshot();
     });
 
     it('should accept an angle in degrees or radians', () => {
@@ -73,12 +99,18 @@ describe('processTransform', () => {
     });
 
     it('should throw when passing an invalid angle prop', () => {
-      expect(() => processTransform([{rotate: 10}])).toThrowErrorMatchingSnapshot();
-      expect(() => processTransform([{skewX: '10drg'}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{rotate: 10}]),
+      ).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{skewX: '10drg'}]),
+      ).toThrowErrorMatchingSnapshot();
     });
 
     it('should throw when passing an Animated.Value', () => {
-      expect(() => processTransform([{rotate: {getValue: () => {}}}])).toThrowErrorMatchingSnapshot();
+      expect(() =>
+        processTransform([{rotate: {getValue: () => {}}}]),
+      ).toThrowErrorMatchingSnapshot();
     });
   });
 });
diff --git a/Libraries/StyleSheet/__tests__/setNormalizedColorAlpha-test.js b/Libraries/StyleSheet/__tests__/setNormalizedColorAlpha-test.js
index 5fd4a9f735e2..f2d09ecb4e18 100644
--- a/Libraries/StyleSheet/__tests__/setNormalizedColorAlpha-test.js
+++ b/Libraries/StyleSheet/__tests__/setNormalizedColorAlpha-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const setNormalizedColorAlpha = require('setNormalizedColorAlpha');
@@ -22,7 +24,7 @@ describe('setNormalizedColorAlpha', function() {
     expect(setNormalizedColorAlpha(0xffffffff, -1)).toBe(0xffffff00);
   });
 
-  it('should ignore the color\'s original alpha', function() {
+  it("should ignore the color's original alpha", function() {
     expect(setNormalizedColorAlpha(0x204080aa, 0.8)).toBe(0x204080cc);
   });
 
diff --git a/Libraries/StyleSheet/processColor.js b/Libraries/StyleSheet/processColor.js
index dba665255110..99b5ecf468cb 100644
--- a/Libraries/StyleSheet/processColor.js
+++ b/Libraries/StyleSheet/processColor.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Platform = require('Platform');
@@ -24,7 +26,7 @@ function processColor(color?: string | number): ?number {
   }
 
   // Converts 0xrrggbbaa into 0xaarrggbb
-  int32Color = (int32Color << 24 | int32Color >>> 8) >>> 0;
+  int32Color = ((int32Color << 24) | (int32Color >>> 8)) >>> 0;
 
   if (Platform.OS === 'android') {
     // Android use 32 bit *signed* integer to represent the color
diff --git a/Libraries/StyleSheet/processTransform.js b/Libraries/StyleSheet/processTransform.js
index fb4ed3445e8c..9bcfd4f4b65e 100644
--- a/Libraries/StyleSheet/processTransform.js
+++ b/Libraries/StyleSheet/processTransform.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const MatrixMath = require('MatrixMath');
@@ -22,7 +24,9 @@ const stringifySafe = require('stringifySafe');
  * be applied in an arbitrary order, and yet have a universal, singular
  * interface to native code.
  */
-function processTransform(transform: Array<Object>): Array<Object> | Array<number> {
+function processTransform(
+  transform: Array<Object>,
+): Array<Object> | Array<number> {
   if (__DEV__) {
     _validateTransforms(transform);
   }
@@ -48,14 +52,20 @@ function processTransform(transform: Array<Object>): Array<Object> | Array<numbe
         _multiplyTransform(result, MatrixMath.reusePerspectiveCommand, [value]);
         break;
       case 'rotateX':
-        _multiplyTransform(result, MatrixMath.reuseRotateXCommand, [_convertToRadians(value)]);
+        _multiplyTransform(result, MatrixMath.reuseRotateXCommand, [
+          _convertToRadians(value),
+        ]);
         break;
       case 'rotateY':
-        _multiplyTransform(result, MatrixMath.reuseRotateYCommand, [_convertToRadians(value)]);
+        _multiplyTransform(result, MatrixMath.reuseRotateYCommand, [
+          _convertToRadians(value),
+        ]);
         break;
       case 'rotate':
       case 'rotateZ':
-        _multiplyTransform(result, MatrixMath.reuseRotateZCommand, [_convertToRadians(value)]);
+        _multiplyTransform(result, MatrixMath.reuseRotateZCommand, [
+          _convertToRadians(value),
+        ]);
         break;
       case 'scale':
         _multiplyTransform(result, MatrixMath.reuseScaleCommand, [value]);
@@ -67,19 +77,33 @@ function processTransform(transform: Array<Object>): Array<Object> | Array<numbe
         _multiplyTransform(result, MatrixMath.reuseScaleYCommand, [value]);
         break;
       case 'translate':
-        _multiplyTransform(result, MatrixMath.reuseTranslate3dCommand, [value[0], value[1], value[2] || 0]);
+        _multiplyTransform(result, MatrixMath.reuseTranslate3dCommand, [
+          value[0],
+          value[1],
+          value[2] || 0,
+        ]);
         break;
       case 'translateX':
-        _multiplyTransform(result, MatrixMath.reuseTranslate2dCommand, [value, 0]);
+        _multiplyTransform(result, MatrixMath.reuseTranslate2dCommand, [
+          value,
+          0,
+        ]);
         break;
       case 'translateY':
-        _multiplyTransform(result, MatrixMath.reuseTranslate2dCommand, [0, value]);
+        _multiplyTransform(result, MatrixMath.reuseTranslate2dCommand, [
+          0,
+          value,
+        ]);
         break;
       case 'skewX':
-        _multiplyTransform(result, MatrixMath.reuseSkewXCommand, [_convertToRadians(value)]);
+        _multiplyTransform(result, MatrixMath.reuseSkewXCommand, [
+          _convertToRadians(value),
+        ]);
         break;
       case 'skewY':
-        _multiplyTransform(result, MatrixMath.reuseSkewYCommand, [_convertToRadians(value)]);
+        _multiplyTransform(result, MatrixMath.reuseSkewYCommand, [
+          _convertToRadians(value),
+        ]);
         break;
       default:
         throw new Error('Invalid transform name: ' + key);
@@ -95,7 +119,7 @@ function processTransform(transform: Array<Object>): Array<Object> | Array<numbe
 function _multiplyTransform(
   result: Array<number>,
   matrixMathFunction: Function,
-  args: Array<number>
+  args: Array<number>,
 ): void {
   const matrixToApply = MatrixMath.createIdentityMatrix();
   const argsWithIdentity = [matrixToApply].concat(args);
@@ -130,14 +154,11 @@ function _validateTransform(key, value, transformation) {
   invariant(
     !value.getValue,
     'You passed an Animated.Value to a normal component. ' +
-    'You need to wrap that component in an Animated. For example, ' +
-    'replace <View /> by <Animated.View />.'
+      'You need to wrap that component in an Animated. For example, ' +
+      'replace <View /> by <Animated.View />.',
   );
 
-  const multivalueTransforms = [
-    'matrix',
-    'translate',
-  ];
+  const multivalueTransforms = ['matrix', 'translate'];
   if (multivalueTransforms.indexOf(key) !== -1) {
     invariant(
       Array.isArray(value),
@@ -210,7 +231,12 @@ function _validateTransform(key, value, transformation) {
       );
       break;
     default:
-      invariant(false, 'Invalid transform %s: %s', key, stringifySafe(transformation));
+      invariant(
+        false,
+        'Invalid transform %s: %s',
+        key,
+        stringifySafe(transformation),
+      );
   }
 }
 
diff --git a/Libraries/StyleSheet/setNormalizedColorAlpha.js b/Libraries/StyleSheet/setNormalizedColorAlpha.js
index 83a0873e577f..52fe783fd602 100644
--- a/Libraries/StyleSheet/setNormalizedColorAlpha.js
+++ b/Libraries/StyleSheet/setNormalizedColorAlpha.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 /* eslint no-bitwise: 0 */
 'use strict';
 
diff --git a/Libraries/Text/TextStylePropTypes.js b/Libraries/Text/TextStylePropTypes.js
index 532f2e3d3ede..28f63c01d7d3 100644
--- a/Libraries/Text/TextStylePropTypes.js
+++ b/Libraries/Text/TextStylePropTypes.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ColorPropType = require('ColorPropType');
@@ -24,10 +26,19 @@ const TextStylePropTypes = {
    * most fonts. Not all fonts have a variant for each of the numeric values,
    * in that case the closest one is chosen.
    */
-  fontWeight: ReactPropTypes.oneOf(
-    ['normal' /*default*/, 'bold',
-     '100', '200', '300', '400', '500', '600', '700', '800', '900']
-  ),
+  fontWeight: ReactPropTypes.oneOf([
+    'normal' /*default*/,
+    'bold',
+    '100',
+    '200',
+    '300',
+    '400',
+    '500',
+    '600',
+    '700',
+    '800',
+    '900',
+  ]),
   /**
    * @platform ios
    */
@@ -38,11 +49,12 @@ const TextStylePropTypes = {
       'lining-nums',
       'tabular-nums',
       'proportional-nums',
-    ])
-  ),
-  textShadowOffset: ReactPropTypes.shape(
-    {width: ReactPropTypes.number, height: ReactPropTypes.number}
+    ]),
   ),
+  textShadowOffset: ReactPropTypes.shape({
+    width: ReactPropTypes.number,
+    height: ReactPropTypes.number,
+  }),
   textShadowRadius: ReactPropTypes.number,
   textShadowColor: ColorPropType,
   /**
@@ -54,15 +66,22 @@ const TextStylePropTypes = {
    * Specifies text alignment. The value 'justify' is only supported on iOS and
    * fallbacks to `left` on Android.
    */
-  textAlign: ReactPropTypes.oneOf(
-    ['auto' /*default*/, 'left', 'right', 'center', 'justify']
-  ),
+  textAlign: ReactPropTypes.oneOf([
+    'auto' /*default*/,
+    'left',
+    'right',
+    'center',
+    'justify',
+  ]),
   /**
    * @platform android
    */
-  textAlignVertical: ReactPropTypes.oneOf(
-    ['auto' /*default*/, 'top', 'bottom', 'center']
-  ),
+  textAlignVertical: ReactPropTypes.oneOf([
+    'auto' /*default*/,
+    'top',
+    'bottom',
+    'center',
+  ]),
   /**
    * Set to `false` to remove extra font padding intended to make space for certain ascenders / descenders.
    * With some fonts, this padding can make text look slightly misaligned when centered vertically.
@@ -70,15 +89,21 @@ const TextStylePropTypes = {
    * @platform android
    */
   includeFontPadding: ReactPropTypes.bool,
-  textDecorationLine: ReactPropTypes.oneOf(
-    ['none' /*default*/, 'underline', 'line-through', 'underline line-through']
-  ),
+  textDecorationLine: ReactPropTypes.oneOf([
+    'none' /*default*/,
+    'underline',
+    'line-through',
+    'underline line-through',
+  ]),
   /**
    * @platform ios
    */
-  textDecorationStyle: ReactPropTypes.oneOf(
-    ['solid' /*default*/, 'double', 'dotted','dashed']
-  ),
+  textDecorationStyle: ReactPropTypes.oneOf([
+    'solid' /*default*/,
+    'double',
+    'dotted',
+    'dashed',
+  ]),
   /**
    * @platform ios
    */
@@ -86,15 +111,16 @@ const TextStylePropTypes = {
   /**
    * @platform ios
    */
-  textTransform: ReactPropTypes.oneOf(
-    ['none' /*default*/, 'capitalize', 'uppercase', 'lowercase']
-  ),
+  textTransform: ReactPropTypes.oneOf([
+    'none' /*default*/,
+    'capitalize',
+    'uppercase',
+    'lowercase',
+  ]),
   /**
    * @platform ios
    */
-  writingDirection: ReactPropTypes.oneOf(
-    ['auto' /*default*/, 'ltr', 'rtl']
-  ),
+  writingDirection: ReactPropTypes.oneOf(['auto' /*default*/, 'ltr', 'rtl']),
 };
 
 module.exports = TextStylePropTypes;
diff --git a/Libraries/Text/TextUpdateTest.js b/Libraries/Text/TextUpdateTest.js
index b3dc0949aeed..5415790979b1 100644
--- a/Libraries/Text/TextUpdateTest.js
+++ b/Libraries/Text/TextUpdateTest.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -15,13 +17,10 @@ const ReactNative = require('react-native');
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
 const TimerMixin = require('react-timer-mixin');
-const {
-  NativeModules,
-  StyleSheet,
-  Text,
-} = ReactNative;
+const {NativeModules, StyleSheet, Text} = ReactNative;
 
-const TestManager = NativeModules.TestManager || NativeModules.SnapshotTestManager;
+const TestManager =
+  NativeModules.TestManager || NativeModules.SnapshotTestManager;
 
 const TextUpdateTest = createReactClass({
   displayName: 'TextUpdateTest',
@@ -30,10 +29,10 @@ const TextUpdateTest = createReactClass({
     return {seeMore: true};
   },
   componentDidMount: function() {
-    this.requestAnimationFrame(
-      () => this.setState({seeMore: false}, () => {
+    this.requestAnimationFrame(() =>
+      this.setState({seeMore: false}, () => {
         TestManager.markTestCompleted();
-      })
+      }),
     );
   },
   render: function() {
diff --git a/Libraries/Utilities/BackAndroid.js b/Libraries/Utilities/BackAndroid.js
index 57e2d8d77a3a..9484ace24119 100644
--- a/Libraries/Utilities/BackAndroid.js
+++ b/Libraries/Utilities/BackAndroid.js
@@ -7,6 +7,7 @@
  * BackAndroid has been moved to BackHandler.  This stub calls BackHandler methods
  * after generating a warning to remind users to move to the new BackHandler module.
  *
+ * @format
  */
 
 'use strict';
@@ -19,28 +20,35 @@ const warning = require('fbjs/lib/warning');
  * Deprecated.  Use BackHandler instead.
  */
 const BackAndroid = {
-
   exitApp: function() {
-    warning(false, 'BackAndroid is deprecated.  Please use BackHandler instead.');
+    warning(
+      false,
+      'BackAndroid is deprecated.  Please use BackHandler instead.',
+    );
     BackHandler.exitApp();
   },
 
-  addEventListener: function (
+  addEventListener: function(
     eventName: BackPressEventName,
-    handler: Function
+    handler: Function,
   ): {remove: () => void} {
-    warning(false, 'BackAndroid is deprecated.  Please use BackHandler instead.');
+    warning(
+      false,
+      'BackAndroid is deprecated.  Please use BackHandler instead.',
+    );
     return BackHandler.addEventListener(eventName, handler);
   },
 
   removeEventListener: function(
     eventName: BackPressEventName,
-    handler: Function
+    handler: Function,
   ): void {
-    warning(false, 'BackAndroid is deprecated.  Please use BackHandler instead.');
+    warning(
+      false,
+      'BackAndroid is deprecated.  Please use BackHandler instead.',
+    );
     BackHandler.removeEventListener(eventName, handler);
   },
-
 };
 
 module.exports = BackAndroid;
diff --git a/Libraries/Utilities/BackHandler.android.js b/Libraries/Utilities/BackHandler.android.js
index 0db35d872098..35c60a155b12 100644
--- a/Libraries/Utilities/BackHandler.android.js
+++ b/Libraries/Utilities/BackHandler.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -66,7 +67,6 @@ RCTDeviceEventEmitter.addListener(DEVICE_BACK_EVENT, function() {
  * ```
  */
 const BackHandler = {
-
   exitApp: function() {
     DeviceEventManager.invokeDefaultBackPressHandler();
   },
@@ -77,9 +77,9 @@ const BackHandler = {
    * - `hardwareBackPress`: Fires when the Android hardware back button is pressed or when the
    * tvOS menu button is pressed.
    */
-  addEventListener: function (
+  addEventListener: function(
     eventName: BackPressEventName,
-    handler: Function
+    handler: Function,
   ): {remove: () => void} {
     _backPressSubscriptions.add(handler);
     return {
@@ -92,11 +92,10 @@ const BackHandler = {
    */
   removeEventListener: function(
     eventName: BackPressEventName,
-    handler: Function
+    handler: Function,
   ): void {
     _backPressSubscriptions.delete(handler);
   },
-
 };
 
 module.exports = BackHandler;
diff --git a/Libraries/Utilities/BackHandler.ios.js b/Libraries/Utilities/BackHandler.ios.js
index 4112d6197f07..968b707d690f 100644
--- a/Libraries/Utilities/BackHandler.ios.js
+++ b/Libraries/Utilities/BackHandler.ios.js
@@ -7,6 +7,7 @@
  * On Apple TV, this implements back navigation using the TV remote's menu button.
  * On iOS, this just implements a stub.
  *
+ * @format
  */
 
 'use strict';
@@ -59,7 +60,9 @@ if (Platform.isTVOS) {
   _tvEventHandler.enable(this, function(cmp, evt) {
     if (evt && evt.eventType === 'menu') {
       let invokeDefault = true;
-      const subscriptions = Array.from(_backPressSubscriptions.values()).reverse();
+      const subscriptions = Array.from(
+        _backPressSubscriptions.values(),
+      ).reverse();
 
       for (let i = 0; i < subscriptions.length; ++i) {
         if (subscriptions[i]()) {
@@ -77,9 +80,9 @@ if (Platform.isTVOS) {
   BackHandler = {
     exitApp: emptyFunction,
 
-    addEventListener: function (
+    addEventListener: function(
       eventName: BackPressEventName,
-      handler: Function
+      handler: Function,
     ): {remove: () => void} {
       _backPressSubscriptions.add(handler);
       return {
@@ -89,15 +92,12 @@ if (Platform.isTVOS) {
 
     removeEventListener: function(
       eventName: BackPressEventName,
-      handler: Function
+      handler: Function,
     ): void {
       _backPressSubscriptions.delete(handler);
     },
-
   };
-
 } else {
-
   BackHandler = {
     exitApp: emptyFunction,
     addEventListener() {
@@ -107,7 +107,6 @@ if (Platform.isTVOS) {
     },
     removeEventListener: emptyFunction,
   };
-
 }
 
 module.exports = BackHandler;
diff --git a/Libraries/Utilities/DeviceInfo.js b/Libraries/Utilities/DeviceInfo.js
index 427ed495232d..88b2a896167f 100644
--- a/Libraries/Utilities/DeviceInfo.js
+++ b/Libraries/Utilities/DeviceInfo.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const DeviceInfo = require('NativeModules').DeviceInfo;
diff --git a/Libraries/Utilities/Dimensions.js b/Libraries/Utilities/Dimensions.js
index 76bde024355c..bd4e60f0ef5b 100644
--- a/Libraries/Utilities/Dimensions.js
+++ b/Libraries/Utilities/Dimensions.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EventEmitter = require('EventEmitter');
@@ -24,7 +26,7 @@ class Dimensions {
    *
    * @param {object} dims Simple string-keyed object of dimensions to set
    */
-  static set(dims: {[key:string]: any}): void {
+  static set(dims: {[key: string]: any}): void {
     // We calculate the window dimensions in JS so that we don't encounter loss of
     // precision in transferring the dimensions (which could be non-integers) over
     // the bridge.
@@ -63,7 +65,7 @@ class Dimensions {
       // Don't fire 'change' the first time the dimensions are set.
       eventEmitter.emit('change', {
         window: dimensions.window,
-        screen: dimensions.screen
+        screen: dimensions.screen,
       });
     } else {
       dimensionsInitialized = true;
@@ -98,13 +100,11 @@ class Dimensions {
    *   are the same as the return values of `Dimensions.get('window')` and
    *   `Dimensions.get('screen')`, respectively.
    */
-  static addEventListener(
-    type: string,
-    handler: Function
-  ) {
+  static addEventListener(type: string, handler: Function) {
     invariant(
       type === 'change',
-      'Trying to subscribe to unknown event: "%s"', type
+      'Trying to subscribe to unknown event: "%s"',
+      type,
     );
     eventEmitter.addListener(type, handler);
   }
@@ -112,19 +112,20 @@ class Dimensions {
   /**
    * Remove an event handler.
    */
-  static removeEventListener(
-    type: string,
-    handler: Function
-  ) {
+  static removeEventListener(type: string, handler: Function) {
     invariant(
       type === 'change',
-      'Trying to remove listener for unknown event: "%s"', type
+      'Trying to remove listener for unknown event: "%s"',
+      type,
     );
     eventEmitter.removeListener(type, handler);
   }
 }
 
-let dims: ?{[key: string]: any} = global.nativeExtensions && global.nativeExtensions.DeviceInfo && global.nativeExtensions.DeviceInfo.Dimensions;
+let dims: ?{[key: string]: any} =
+  global.nativeExtensions &&
+  global.nativeExtensions.DeviceInfo &&
+  global.nativeExtensions.DeviceInfo.Dimensions;
 let nativeExtensionsEnabled = true;
 if (!dims) {
   const DeviceInfo = require('DeviceInfo');
@@ -132,7 +133,10 @@ if (!dims) {
   nativeExtensionsEnabled = false;
 }
 
-invariant(dims, 'Either DeviceInfo native extension or DeviceInfo Native Module must be registered');
+invariant(
+  dims,
+  'Either DeviceInfo native extension or DeviceInfo Native Module must be registered',
+);
 Dimensions.set(dims);
 if (!nativeExtensionsEnabled) {
   RCTDeviceEventEmitter.addListener('didUpdateDimensions', function(update) {
diff --git a/Libraries/Utilities/HMRLoadingView.android.js b/Libraries/Utilities/HMRLoadingView.android.js
index 61bc75c7e517..ae17636537a2 100644
--- a/Libraries/Utilities/HMRLoadingView.android.js
+++ b/Libraries/Utilities/HMRLoadingView.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/Libraries/Utilities/HMRLoadingView.ios.js b/Libraries/Utilities/HMRLoadingView.ios.js
index 4e9ad8fbf93f..631df2c2f819 100644
--- a/Libraries/Utilities/HMRLoadingView.ios.js
+++ b/Libraries/Utilities/HMRLoadingView.ios.js
@@ -4,13 +4,14 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
 'use strict';
 
 const processColor = require('processColor');
-const { DevLoadingView } = require('NativeModules');
+const {DevLoadingView} = require('NativeModules');
 
 class HMRLoadingView {
   static showMessage(message: string) {
diff --git a/Libraries/Utilities/HeapCapture.js b/Libraries/Utilities/HeapCapture.js
index 91df130ed934..999cb869b30d 100644
--- a/Libraries/Utilities/HeapCapture.js
+++ b/Libraries/Utilities/HeapCapture.js
@@ -4,12 +4,14 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const HeapCapture = {
-  captureHeap: function (path: string) {
+  captureHeap: function(path: string) {
     let error = null;
     try {
       global.nativeCaptureHeap(path);
diff --git a/Libraries/Utilities/JSDevSupportModule.js b/Libraries/Utilities/JSDevSupportModule.js
index c25123284613..074ebef6b19f 100644
--- a/Libraries/Utilities/JSDevSupportModule.js
+++ b/Libraries/Utilities/JSDevSupportModule.js
@@ -4,23 +4,27 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const JSDevSupport = require('NativeModules').JSDevSupport;
 const ReactNative = require('ReactNative');
 
 const JSDevSupportModule = {
-  getJSHierarchy: function (tag: number) {
+  getJSHierarchy: function(tag: number) {
     try {
-      const {computeComponentStackForErrorReporting} =
-          ReactNative.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+      const {
+        computeComponentStackForErrorReporting,
+      } = ReactNative.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
       const componentStack = computeComponentStackForErrorReporting(tag);
       if (!componentStack) {
         JSDevSupport.onFailure(
           JSDevSupport.ERROR_CODE_VIEW_NOT_FOUND,
-          'Component stack doesn\'t exist for tag ' + tag);
+          "Component stack doesn't exist for tag " + tag,
+        );
       } else {
         JSDevSupport.onSuccess(componentStack);
       }
diff --git a/Libraries/Utilities/MatrixMath.js b/Libraries/Utilities/MatrixMath.js
index 40f934cc88ac..6a523fa4a4a4 100755
--- a/Libraries/Utilities/MatrixMath.js
+++ b/Libraries/Utilities/MatrixMath.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @noflow
  */
+
 /* eslint-disable space-infix-ops */
 'use strict';
 
@@ -17,20 +19,27 @@ const invariant = require('fbjs/lib/invariant');
  */
 const MatrixMath = {
   createIdentityMatrix: function() {
-    return [
-      1,0,0,0,
-      0,1,0,0,
-      0,0,1,0,
-      0,0,0,1
-    ];
+    return [1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1];
   },
 
   createCopy: function(m) {
     return [
-      m[0],  m[1],  m[2],  m[3],
-      m[4],  m[5],  m[6],  m[7],
-      m[8],  m[9],  m[10], m[11],
-      m[12], m[13], m[14], m[15],
+      m[0],
+      m[1],
+      m[2],
+      m[3],
+      m[4],
+      m[5],
+      m[6],
+      m[7],
+      m[8],
+      m[9],
+      m[10],
+      m[11],
+      m[12],
+      m[13],
+      m[14],
+      m[15],
     ];
   },
 
@@ -43,30 +52,20 @@ const MatrixMath = {
     const ty = -(top + bottom) / (top - bottom);
     const tz = -(far + near) / (far - near);
 
-    return [
-        a,  0,  0,  0,
-        0,  b,  0,  0,
-        0,  0,  c,  0,
-        tx, ty, tz, 1
-    ];
+    return [a, 0, 0, 0, 0, b, 0, 0, 0, 0, c, 0, tx, ty, tz, 1];
   },
 
   createFrustum: function(left, right, bottom, top, near, far) {
-    const r_width  = 1 / (right - left);
+    const r_width = 1 / (right - left);
     const r_height = 1 / (top - bottom);
-    const r_depth  = 1 / (near - far);
+    const r_depth = 1 / (near - far);
     const x = 2 * (near * r_width);
     const y = 2 * (near * r_height);
     const A = (right + left) * r_width;
     const B = (top + bottom) * r_height;
     const C = (far + near) * r_depth;
     const D = 2 * (far * near * r_depth);
-    return [
-      x, 0, 0, 0,
-      0, y, 0, 0,
-      A, B, C,-1,
-      0, 0, D, 0,
-    ];
+    return [x, 0, 0, 0, 0, y, 0, 0, A, B, C, -1, 0, 0, D, 0];
   },
 
   /**
@@ -77,15 +76,10 @@ const MatrixMath = {
    */
   createPerspective: function(fovInRadians, aspect, near, far) {
     const h = 1 / Math.tan(fovInRadians / 2);
-    const r_depth  = 1 / (near - far);
+    const r_depth = 1 / (near - far);
     const C = (far + near) * r_depth;
     const D = 2 * (far * near * r_depth);
-    return [
-      h/aspect, 0, 0, 0,
-      0, h, 0, 0,
-      0, 0, C,-1,
-      0, 0, D, 0,
-    ];
+    return [h / aspect, 0, 0, 0, 0, h, 0, 0, 0, 0, C, -1, 0, 0, D, 0];
   },
 
   createTranslate2d: function(x, y) {
@@ -175,53 +169,104 @@ const MatrixMath = {
   },
 
   multiplyInto: function(out, a, b) {
-    const a00 = a[0], a01 = a[1], a02 = a[2], a03 = a[3], a10 = a[4], a11 = a[5], a12 = a[6], a13 = a[7], a20 = a[8], a21 = a[9], a22 = a[10], a23 = a[11], a30 = a[12], a31 = a[13], a32 = a[14], a33 = a[15];
-
-    let b0  = b[0], b1 = b[1], b2 = b[2], b3 = b[3];
-    out[0] = b0*a00 + b1*a10 + b2*a20 + b3*a30;
-    out[1] = b0*a01 + b1*a11 + b2*a21 + b3*a31;
-    out[2] = b0*a02 + b1*a12 + b2*a22 + b3*a32;
-    out[3] = b0*a03 + b1*a13 + b2*a23 + b3*a33;
-
-    b0 = b[4]; b1 = b[5]; b2 = b[6]; b3 = b[7];
-    out[4] = b0*a00 + b1*a10 + b2*a20 + b3*a30;
-    out[5] = b0*a01 + b1*a11 + b2*a21 + b3*a31;
-    out[6] = b0*a02 + b1*a12 + b2*a22 + b3*a32;
-    out[7] = b0*a03 + b1*a13 + b2*a23 + b3*a33;
-
-    b0 = b[8]; b1 = b[9]; b2 = b[10]; b3 = b[11];
-    out[8] = b0*a00 + b1*a10 + b2*a20 + b3*a30;
-    out[9] = b0*a01 + b1*a11 + b2*a21 + b3*a31;
-    out[10] = b0*a02 + b1*a12 + b2*a22 + b3*a32;
-    out[11] = b0*a03 + b1*a13 + b2*a23 + b3*a33;
-
-    b0 = b[12]; b1 = b[13]; b2 = b[14]; b3 = b[15];
-    out[12] = b0*a00 + b1*a10 + b2*a20 + b3*a30;
-    out[13] = b0*a01 + b1*a11 + b2*a21 + b3*a31;
-    out[14] = b0*a02 + b1*a12 + b2*a22 + b3*a32;
-    out[15] = b0*a03 + b1*a13 + b2*a23 + b3*a33;
+    const a00 = a[0],
+      a01 = a[1],
+      a02 = a[2],
+      a03 = a[3],
+      a10 = a[4],
+      a11 = a[5],
+      a12 = a[6],
+      a13 = a[7],
+      a20 = a[8],
+      a21 = a[9],
+      a22 = a[10],
+      a23 = a[11],
+      a30 = a[12],
+      a31 = a[13],
+      a32 = a[14],
+      a33 = a[15];
+
+    let b0 = b[0],
+      b1 = b[1],
+      b2 = b[2],
+      b3 = b[3];
+    out[0] = b0 * a00 + b1 * a10 + b2 * a20 + b3 * a30;
+    out[1] = b0 * a01 + b1 * a11 + b2 * a21 + b3 * a31;
+    out[2] = b0 * a02 + b1 * a12 + b2 * a22 + b3 * a32;
+    out[3] = b0 * a03 + b1 * a13 + b2 * a23 + b3 * a33;
+
+    b0 = b[4];
+    b1 = b[5];
+    b2 = b[6];
+    b3 = b[7];
+    out[4] = b0 * a00 + b1 * a10 + b2 * a20 + b3 * a30;
+    out[5] = b0 * a01 + b1 * a11 + b2 * a21 + b3 * a31;
+    out[6] = b0 * a02 + b1 * a12 + b2 * a22 + b3 * a32;
+    out[7] = b0 * a03 + b1 * a13 + b2 * a23 + b3 * a33;
+
+    b0 = b[8];
+    b1 = b[9];
+    b2 = b[10];
+    b3 = b[11];
+    out[8] = b0 * a00 + b1 * a10 + b2 * a20 + b3 * a30;
+    out[9] = b0 * a01 + b1 * a11 + b2 * a21 + b3 * a31;
+    out[10] = b0 * a02 + b1 * a12 + b2 * a22 + b3 * a32;
+    out[11] = b0 * a03 + b1 * a13 + b2 * a23 + b3 * a33;
+
+    b0 = b[12];
+    b1 = b[13];
+    b2 = b[14];
+    b3 = b[15];
+    out[12] = b0 * a00 + b1 * a10 + b2 * a20 + b3 * a30;
+    out[13] = b0 * a01 + b1 * a11 + b2 * a21 + b3 * a31;
+    out[14] = b0 * a02 + b1 * a12 + b2 * a22 + b3 * a32;
+    out[15] = b0 * a03 + b1 * a13 + b2 * a23 + b3 * a33;
   },
 
   determinant(matrix: Array<number>): number {
     const [
-      m00, m01, m02, m03,
-      m10, m11, m12, m13,
-      m20, m21, m22, m23,
-      m30, m31, m32, m33
+      m00,
+      m01,
+      m02,
+      m03,
+      m10,
+      m11,
+      m12,
+      m13,
+      m20,
+      m21,
+      m22,
+      m23,
+      m30,
+      m31,
+      m32,
+      m33,
     ] = matrix;
     return (
-      m03 * m12 * m21 * m30 - m02 * m13 * m21 * m30 -
-      m03 * m11 * m22 * m30 + m01 * m13 * m22 * m30 +
-      m02 * m11 * m23 * m30 - m01 * m12 * m23 * m30 -
-      m03 * m12 * m20 * m31 + m02 * m13 * m20 * m31 +
-      m03 * m10 * m22 * m31 - m00 * m13 * m22 * m31 -
-      m02 * m10 * m23 * m31 + m00 * m12 * m23 * m31 +
-      m03 * m11 * m20 * m32 - m01 * m13 * m20 * m32 -
-      m03 * m10 * m21 * m32 + m00 * m13 * m21 * m32 +
-      m01 * m10 * m23 * m32 - m00 * m11 * m23 * m32 -
-      m02 * m11 * m20 * m33 + m01 * m12 * m20 * m33 +
-      m02 * m10 * m21 * m33 - m00 * m12 * m21 * m33 -
-      m01 * m10 * m22 * m33 + m00 * m11 * m22 * m33
+      m03 * m12 * m21 * m30 -
+      m02 * m13 * m21 * m30 -
+      m03 * m11 * m22 * m30 +
+      m01 * m13 * m22 * m30 +
+      m02 * m11 * m23 * m30 -
+      m01 * m12 * m23 * m30 -
+      m03 * m12 * m20 * m31 +
+      m02 * m13 * m20 * m31 +
+      m03 * m10 * m22 * m31 -
+      m00 * m13 * m22 * m31 -
+      m02 * m10 * m23 * m31 +
+      m00 * m12 * m23 * m31 +
+      m03 * m11 * m20 * m32 -
+      m01 * m13 * m20 * m32 -
+      m03 * m10 * m21 * m32 +
+      m00 * m13 * m21 * m32 +
+      m01 * m10 * m23 * m32 -
+      m00 * m11 * m23 * m32 -
+      m02 * m11 * m20 * m33 +
+      m01 * m12 * m20 * m33 +
+      m02 * m10 * m21 * m33 -
+      m00 * m12 * m21 * m33 -
+      m01 * m10 * m22 * m33 +
+      m00 * m11 * m22 * m33
     );
   },
 
@@ -238,56 +283,173 @@ const MatrixMath = {
       return matrix;
     }
     const [
-      m00, m01, m02, m03,
-      m10, m11, m12, m13,
-      m20, m21, m22, m23,
-      m30, m31, m32, m33
+      m00,
+      m01,
+      m02,
+      m03,
+      m10,
+      m11,
+      m12,
+      m13,
+      m20,
+      m21,
+      m22,
+      m23,
+      m30,
+      m31,
+      m32,
+      m33,
     ] = matrix;
     return [
-      (m12*m23*m31 - m13*m22*m31 + m13*m21*m32 - m11*m23*m32 - m12*m21*m33 + m11*m22*m33) / det,
-      (m03*m22*m31 - m02*m23*m31 - m03*m21*m32 + m01*m23*m32 + m02*m21*m33 - m01*m22*m33) / det,
-      (m02*m13*m31 - m03*m12*m31 + m03*m11*m32 - m01*m13*m32 - m02*m11*m33 + m01*m12*m33) / det,
-      (m03*m12*m21 - m02*m13*m21 - m03*m11*m22 + m01*m13*m22 + m02*m11*m23 - m01*m12*m23) / det,
-      (m13*m22*m30 - m12*m23*m30 - m13*m20*m32 + m10*m23*m32 + m12*m20*m33 - m10*m22*m33) / det,
-      (m02*m23*m30 - m03*m22*m30 + m03*m20*m32 - m00*m23*m32 - m02*m20*m33 + m00*m22*m33) / det,
-      (m03*m12*m30 - m02*m13*m30 - m03*m10*m32 + m00*m13*m32 + m02*m10*m33 - m00*m12*m33) / det,
-      (m02*m13*m20 - m03*m12*m20 + m03*m10*m22 - m00*m13*m22 - m02*m10*m23 + m00*m12*m23) / det,
-      (m11*m23*m30 - m13*m21*m30 + m13*m20*m31 - m10*m23*m31 - m11*m20*m33 + m10*m21*m33) / det,
-      (m03*m21*m30 - m01*m23*m30 - m03*m20*m31 + m00*m23*m31 + m01*m20*m33 - m00*m21*m33) / det,
-      (m01*m13*m30 - m03*m11*m30 + m03*m10*m31 - m00*m13*m31 - m01*m10*m33 + m00*m11*m33) / det,
-      (m03*m11*m20 - m01*m13*m20 - m03*m10*m21 + m00*m13*m21 + m01*m10*m23 - m00*m11*m23) / det,
-      (m12*m21*m30 - m11*m22*m30 - m12*m20*m31 + m10*m22*m31 + m11*m20*m32 - m10*m21*m32) / det,
-      (m01*m22*m30 - m02*m21*m30 + m02*m20*m31 - m00*m22*m31 - m01*m20*m32 + m00*m21*m32) / det,
-      (m02*m11*m30 - m01*m12*m30 - m02*m10*m31 + m00*m12*m31 + m01*m10*m32 - m00*m11*m32) / det,
-      (m01*m12*m20 - m02*m11*m20 + m02*m10*m21 - m00*m12*m21 - m01*m10*m22 + m00*m11*m22) / det
+      (m12 * m23 * m31 -
+        m13 * m22 * m31 +
+        m13 * m21 * m32 -
+        m11 * m23 * m32 -
+        m12 * m21 * m33 +
+        m11 * m22 * m33) /
+        det,
+      (m03 * m22 * m31 -
+        m02 * m23 * m31 -
+        m03 * m21 * m32 +
+        m01 * m23 * m32 +
+        m02 * m21 * m33 -
+        m01 * m22 * m33) /
+        det,
+      (m02 * m13 * m31 -
+        m03 * m12 * m31 +
+        m03 * m11 * m32 -
+        m01 * m13 * m32 -
+        m02 * m11 * m33 +
+        m01 * m12 * m33) /
+        det,
+      (m03 * m12 * m21 -
+        m02 * m13 * m21 -
+        m03 * m11 * m22 +
+        m01 * m13 * m22 +
+        m02 * m11 * m23 -
+        m01 * m12 * m23) /
+        det,
+      (m13 * m22 * m30 -
+        m12 * m23 * m30 -
+        m13 * m20 * m32 +
+        m10 * m23 * m32 +
+        m12 * m20 * m33 -
+        m10 * m22 * m33) /
+        det,
+      (m02 * m23 * m30 -
+        m03 * m22 * m30 +
+        m03 * m20 * m32 -
+        m00 * m23 * m32 -
+        m02 * m20 * m33 +
+        m00 * m22 * m33) /
+        det,
+      (m03 * m12 * m30 -
+        m02 * m13 * m30 -
+        m03 * m10 * m32 +
+        m00 * m13 * m32 +
+        m02 * m10 * m33 -
+        m00 * m12 * m33) /
+        det,
+      (m02 * m13 * m20 -
+        m03 * m12 * m20 +
+        m03 * m10 * m22 -
+        m00 * m13 * m22 -
+        m02 * m10 * m23 +
+        m00 * m12 * m23) /
+        det,
+      (m11 * m23 * m30 -
+        m13 * m21 * m30 +
+        m13 * m20 * m31 -
+        m10 * m23 * m31 -
+        m11 * m20 * m33 +
+        m10 * m21 * m33) /
+        det,
+      (m03 * m21 * m30 -
+        m01 * m23 * m30 -
+        m03 * m20 * m31 +
+        m00 * m23 * m31 +
+        m01 * m20 * m33 -
+        m00 * m21 * m33) /
+        det,
+      (m01 * m13 * m30 -
+        m03 * m11 * m30 +
+        m03 * m10 * m31 -
+        m00 * m13 * m31 -
+        m01 * m10 * m33 +
+        m00 * m11 * m33) /
+        det,
+      (m03 * m11 * m20 -
+        m01 * m13 * m20 -
+        m03 * m10 * m21 +
+        m00 * m13 * m21 +
+        m01 * m10 * m23 -
+        m00 * m11 * m23) /
+        det,
+      (m12 * m21 * m30 -
+        m11 * m22 * m30 -
+        m12 * m20 * m31 +
+        m10 * m22 * m31 +
+        m11 * m20 * m32 -
+        m10 * m21 * m32) /
+        det,
+      (m01 * m22 * m30 -
+        m02 * m21 * m30 +
+        m02 * m20 * m31 -
+        m00 * m22 * m31 -
+        m01 * m20 * m32 +
+        m00 * m21 * m32) /
+        det,
+      (m02 * m11 * m30 -
+        m01 * m12 * m30 -
+        m02 * m10 * m31 +
+        m00 * m12 * m31 +
+        m01 * m10 * m32 -
+        m00 * m11 * m32) /
+        det,
+      (m01 * m12 * m20 -
+        m02 * m11 * m20 +
+        m02 * m10 * m21 -
+        m00 * m12 * m21 -
+        m01 * m10 * m22 +
+        m00 * m11 * m22) /
+        det,
     ];
   },
 
   /**
    * Turns columns into rows and rows into columns.
    */
-   transpose(m: Array<number>): Array<number> {
+  transpose(m: Array<number>): Array<number> {
     return [
-      m[0], m[4], m[8],  m[12],
-      m[1], m[5], m[9],  m[13],
-      m[2], m[6], m[10], m[14],
-      m[3], m[7], m[11], m[15]
+      m[0],
+      m[4],
+      m[8],
+      m[12],
+      m[1],
+      m[5],
+      m[9],
+      m[13],
+      m[2],
+      m[6],
+      m[10],
+      m[14],
+      m[3],
+      m[7],
+      m[11],
+      m[15],
     ];
   },
 
   /**
    * Based on: http://tog.acm.org/resources/GraphicsGems/gemsii/unmatrix.c
    */
-  multiplyVectorByMatrix(
-    v: Array<number>,
-    m: Array<number>
-  ): Array<number> {
+  multiplyVectorByMatrix(v: Array<number>, m: Array<number>): Array<number> {
     const [vx, vy, vz, vw] = v;
     return [
-      vx * m[0] + vy * m[4] + vz * m[8]  + vw * m[12],
-      vx * m[1] + vy * m[5] + vz * m[9]  + vw * m[13],
+      vx * m[0] + vy * m[4] + vz * m[8] + vw * m[12],
+      vx * m[1] + vy * m[5] + vz * m[9] + vw * m[13],
       vx * m[2] + vy * m[6] + vz * m[10] + vw * m[14],
-      vx * m[3] + vy * m[7] + vz * m[11] + vw * m[15]
+      vx * m[3] + vy * m[7] + vz * m[11] + vw * m[15],
     ];
   },
 
@@ -295,22 +457,15 @@ const MatrixMath = {
    * From: https://code.google.com/p/webgl-mjs/source/browse/mjs.js
    */
   v3Length(a: Array<number>): number {
-    return Math.sqrt(a[0]*a[0] + a[1]*a[1] + a[2]*a[2]);
+    return Math.sqrt(a[0] * a[0] + a[1] * a[1] + a[2] * a[2]);
   },
 
   /**
    * Based on: https://code.google.com/p/webgl-mjs/source/browse/mjs.js
    */
-   v3Normalize(
-     vector: Array<number>,
-     v3Length: number
-    ): Array<number> {
+  v3Normalize(vector: Array<number>, v3Length: number): Array<number> {
     const im = 1 / (v3Length || MatrixMath.v3Length(vector));
-    return [
-      vector[0] * im,
-      vector[1] * im,
-      vector[2] * im
-    ];
+    return [vector[0] * im, vector[1] * im, vector[2] * im];
   },
 
   /**
@@ -318,9 +473,7 @@ const MatrixMath = {
    * From: https://code.google.com/p/webgl-mjs/source/browse/mjs.js
    */
   v3Dot(a, b) {
-    return a[0] * b[0] +
-           a[1] * b[1] +
-           a[2] * b[2];
+    return a[0] * b[0] + a[1] * b[1] + a[2] * b[2];
   },
 
   /**
@@ -331,12 +484,12 @@ const MatrixMath = {
     a: Array<number>,
     b: Array<number>,
     aScale: number,
-    bScale: number
+    bScale: number,
   ): Array<number> {
     return [
       aScale * a[0] + bScale * b[0],
       aScale * a[1] + bScale * b[1],
-      aScale * a[2] + bScale * b[2]
+      aScale * a[2] + bScale * b[2],
     ];
   },
 
@@ -348,7 +501,7 @@ const MatrixMath = {
     return [
       a[1] * b[2] - a[2] * b[1],
       a[2] * b[0] - a[0] * b[2],
-      a[0] * b[1] - a[1] * b[0]
+      a[0] * b[1] - a[1] * b[0],
     ];
   },
 
@@ -387,14 +540,12 @@ const MatrixMath = {
 
     return [
       MatrixMath.roundTo3Places(
-        Math.atan2(2*qx*qw-2*qy*qz,1-2*qx2-2*qz2) * conv
+        Math.atan2(2 * qx * qw - 2 * qy * qz, 1 - 2 * qx2 - 2 * qz2) * conv,
       ),
       MatrixMath.roundTo3Places(
-        Math.atan2(2*qy*qw-2*qx*qz,1-2*qy2-2*qz2) * conv
+        Math.atan2(2 * qy * qw - 2 * qx * qz, 1 - 2 * qy2 - 2 * qz2) * conv,
       ),
-      MatrixMath.roundTo3Places(
-        Math.asin(2*qx*qy+2*qz*qw) * conv
-      )
+      MatrixMath.roundTo3Places(Math.asin(2 * qx * qy + 2 * qz * qw) * conv),
     ];
   },
 
@@ -404,7 +555,7 @@ const MatrixMath = {
    */
   roundTo3Places(n: number): number {
     const arr = n.toString().split('e');
-    return Math.round(arr[0] + 'e' + (arr[1] ? (+arr[1] - 3) : 3)) * 0.001;
+    return Math.round(arr[0] + 'e' + (arr[1] ? +arr[1] - 3 : 3)) * 0.001;
   },
 
   /**
@@ -419,11 +570,10 @@ const MatrixMath = {
    * http://tog.acm.org/resources/GraphicsGems/gemsii/unmatrix.c
    */
   decomposeMatrix(transformMatrix: Array<number>): ?Object {
-
     invariant(
       transformMatrix.length === 16,
       'Matrix decomposition needs a list of 3d matrix values, received %s',
-      transformMatrix
+      transformMatrix,
     );
 
     // output values
@@ -443,7 +593,7 @@ const MatrixMath = {
     for (var i = 0; i < 4; i++) {
       matrix.push([]);
       for (let j = 0; j < 4; j++) {
-        const value = transformMatrix[(i * 4) + j] / transformMatrix[15];
+        const value = transformMatrix[i * 4 + j] / transformMatrix[15];
         matrix[i].push(value);
         perspectiveMatrix.push(j === 3 ? 0 : value);
       }
@@ -463,20 +613,18 @@ const MatrixMath = {
         matrix[0][3],
         matrix[1][3],
         matrix[2][3],
-        matrix[3][3]
+        matrix[3][3],
       ];
 
       // Solve the equation by inverting perspectiveMatrix and multiplying
       // rightHandSide by the inverse.
-      const inversePerspectiveMatrix = MatrixMath.inverse(
-        perspectiveMatrix
-      );
+      const inversePerspectiveMatrix = MatrixMath.inverse(perspectiveMatrix);
       const transposedInversePerspectiveMatrix = MatrixMath.transpose(
-        inversePerspectiveMatrix
+        inversePerspectiveMatrix,
       );
       var perspective = MatrixMath.multiplyVectorByMatrix(
         rightHandSide,
-        transposedInversePerspectiveMatrix
+        transposedInversePerspectiveMatrix,
       );
     } else {
       // no perspective
@@ -493,11 +641,7 @@ const MatrixMath = {
     // 'row' is a 3 element array of 3 component vectors
     const row = [];
     for (i = 0; i < 3; i++) {
-      row[i] = [
-        matrix[i][0],
-        matrix[i][1],
-        matrix[i][2]
-      ];
+      row[i] = [matrix[i][0], matrix[i][1], matrix[i][2]];
     }
 
     // Compute X scale factor and normalize first row.
@@ -565,15 +709,25 @@ const MatrixMath = {
     // correct for occasional, weird Euler synonyms for 2d rotation
     let rotationDegrees;
     if (
-      quaternion[0] < 0.001 && quaternion[0] >= 0 &&
-      quaternion[1] < 0.001 && quaternion[1] >= 0
+      quaternion[0] < 0.001 &&
+      quaternion[0] >= 0 &&
+      quaternion[1] < 0.001 &&
+      quaternion[1] >= 0
     ) {
       // this is a 2d rotation on the z-axis
-      rotationDegrees = [0, 0, MatrixMath.roundTo3Places(
-        Math.atan2(row[0][1], row[0][0]) * 180 / Math.PI
-      )];
+      rotationDegrees = [
+        0,
+        0,
+        MatrixMath.roundTo3Places(
+          Math.atan2(row[0][1], row[0][0]) * 180 / Math.PI,
+        ),
+      ];
     } else {
-      rotationDegrees = MatrixMath.quaternionToDegreesXYZ(quaternion, matrix, row);
+      rotationDegrees = MatrixMath.quaternionToDegreesXYZ(
+        quaternion,
+        matrix,
+        row,
+      );
     }
 
     // expose both base data and convenience names
@@ -594,7 +748,6 @@ const MatrixMath = {
       translateY: translation[1],
     };
   },
-
 };
 
 module.exports = MatrixMath;
diff --git a/Libraries/Utilities/PixelRatio.js b/Libraries/Utilities/PixelRatio.js
index 58b2b02241fe..0c6386e31a2c 100644
--- a/Libraries/Utilities/PixelRatio.js
+++ b/Libraries/Utilities/PixelRatio.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Dimensions = require('Dimensions');
diff --git a/Libraries/Utilities/Platform.android.js b/Libraries/Utilities/Platform.android.js
index 56b0d2494478..92edba18299b 100644
--- a/Libraries/Utilities/Platform.android.js
+++ b/Libraries/Utilities/Platform.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -25,7 +26,7 @@ const Platform = {
     const constants = NativeModules.PlatformConstants;
     return constants && constants.uiMode === 'tv';
   },
-  select: (obj: Object) => 'android' in obj ? obj.android : obj.default,
+  select: (obj: Object) => ('android' in obj ? obj.android : obj.default),
 };
 
 module.exports = Platform;
diff --git a/Libraries/Utilities/Platform.ios.js b/Libraries/Utilities/Platform.ios.js
index 9780ec75d274..df3a15be20f2 100644
--- a/Libraries/Utilities/Platform.ios.js
+++ b/Libraries/Utilities/Platform.ios.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -35,7 +36,7 @@ const Platform = {
     const constants = NativeModules.PlatformConstants;
     return constants && constants.isTesting;
   },
-  select: (obj: Object) => 'ios' in obj ? obj.ios : obj.default,
+  select: (obj: Object) => ('ios' in obj ? obj.ios : obj.default),
 };
 
 module.exports = Platform;
diff --git a/Libraries/Utilities/PlatformOS.android.js b/Libraries/Utilities/PlatformOS.android.js
index d2183c41682c..5ddf8d81e6e7 100644
--- a/Libraries/Utilities/PlatformOS.android.js
+++ b/Libraries/Utilities/PlatformOS.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -16,7 +17,7 @@ export type PlatformSelectSpec<A, I> = {|
 
 const PlatformOS = {
   OS: 'android',
-  select: <A, I> (spec: PlatformSelectSpec<A, I>): A | I => spec.android,
+  select: <A, I>(spec: PlatformSelectSpec<A, I>): A | I => spec.android,
 };
 
 module.exports = PlatformOS;
diff --git a/Libraries/Utilities/PlatformOS.ios.js b/Libraries/Utilities/PlatformOS.ios.js
index 95b275712a08..90917af1e34e 100644
--- a/Libraries/Utilities/PlatformOS.ios.js
+++ b/Libraries/Utilities/PlatformOS.ios.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -16,7 +17,7 @@ export type PlatformSelectSpec<A, I> = {|
 
 const PlatformOS = {
   OS: 'ios',
-  select: <A, I> (spec: PlatformSelectSpec<A, I>): A | I => spec.ios,
+  select: <A, I>(spec: PlatformSelectSpec<A, I>): A | I => spec.ios,
 };
 
 module.exports = PlatformOS;
diff --git a/Libraries/Utilities/RCTLog.js b/Libraries/Utilities/RCTLog.js
index 7259b79761f7..ab29cd5ce6ee 100644
--- a/Libraries/Utilities/RCTLog.js
+++ b/Libraries/Utilities/RCTLog.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const invariant = require('fbjs/lib/invariant');
@@ -18,7 +20,7 @@ const levelsMap = {
   fatal: 'error',
 };
 
-let warningHandler: ?(Array<any> => void) = null;
+let warningHandler: ?(Array<any>) => void = null;
 
 const RCTLog = {
   // level one of log, info, warn, error, mustfix
@@ -39,7 +41,7 @@ const RCTLog = {
     const logFn = levelsMap[level];
     invariant(
       logFn,
-      'Level "' + level + '" not one of ' + Object.keys(levelsMap).toString()
+      'Level "' + level + '" not one of ' + Object.keys(levelsMap).toString(),
     );
 
     console[logFn](...args);
@@ -47,7 +49,7 @@ const RCTLog = {
 
   setWarningHandler(handler: typeof warningHandler): void {
     warningHandler = handler;
-  }
+  },
 };
 
 module.exports = RCTLog;
diff --git a/Libraries/Utilities/SceneTracker.js b/Libraries/Utilities/SceneTracker.js
index ae41ec03e08b..5d719d8f7b20 100644
--- a/Libraries/Utilities/SceneTracker.js
+++ b/Libraries/Utilities/SceneTracker.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -18,18 +19,20 @@ let _activeScene = {name: 'default'};
 const SceneTracker = {
   setActiveScene(scene: Scene) {
     _activeScene = scene;
-    _listeners.forEach((listener) => listener(_activeScene));
+    _listeners.forEach(listener => listener(_activeScene));
   },
 
   getActiveScene(): Scene {
     return _activeScene;
   },
 
-  addActiveSceneChangedListener(callback: (scene: Scene) => void): {remove: () => void} {
+  addActiveSceneChangedListener(
+    callback: (scene: Scene) => void,
+  ): {remove: () => void} {
     _listeners.push(callback);
     return {
       remove: () => {
-        _listeners = _listeners.filter((listener) => callback !== listener);
+        _listeners = _listeners.filter(listener => callback !== listener);
       },
     };
   },
diff --git a/Libraries/Utilities/__mocks__/BackHandler.js b/Libraries/Utilities/__mocks__/BackHandler.js
index e6319f8974ac..ec1d60bec3b8 100644
--- a/Libraries/Utilities/__mocks__/BackHandler.js
+++ b/Libraries/Utilities/__mocks__/BackHandler.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -13,9 +14,9 @@ const _backPressSubscriptions = new Set();
 const BackHandler = {
   exitApp: jest.fn(),
 
-  addEventListener: function (
+  addEventListener: function(
     eventName: BackPressEventName,
-    handler: Function
+    handler: Function,
   ): {remove: () => void} {
     _backPressSubscriptions.add(handler);
     return {
@@ -25,12 +26,11 @@ const BackHandler = {
 
   removeEventListener: function(
     eventName: BackPressEventName,
-    handler: Function
+    handler: Function,
   ): void {
     _backPressSubscriptions.delete(handler);
   },
 
-
   mockPressBack: function() {
     let invokeDefault = true;
     const subscriptions = [..._backPressSubscriptions].reverse();
diff --git a/Libraries/Utilities/__mocks__/PixelRatio.js b/Libraries/Utilities/__mocks__/PixelRatio.js
index 242d4773380e..efe64953563e 100644
--- a/Libraries/Utilities/__mocks__/PixelRatio.js
+++ b/Libraries/Utilities/__mocks__/PixelRatio.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -10,7 +12,9 @@
 const PixelRatio = {
   get: jest.fn().mockReturnValue(2),
   getFontScale: jest.fn(() => PixelRatio.get()),
-  getPixelSizeForLayoutSize: jest.fn(layoutSize => Math.round(layoutSize * PixelRatio.get())),
+  getPixelSizeForLayoutSize: jest.fn(layoutSize =>
+    Math.round(layoutSize * PixelRatio.get()),
+  ),
   roundToNearestPixel: jest.fn(layoutSize => {
     const ratio = PixelRatio.get();
     return Math.round(layoutSize * ratio) / ratio;
diff --git a/Libraries/Utilities/__tests__/MatrixMath-test.js b/Libraries/Utilities/__tests__/MatrixMath-test.js
index f8491cec0fd7..8a779d3676bf 100644
--- a/Libraries/Utilities/__tests__/MatrixMath-test.js
+++ b/Libraries/Utilities/__tests__/MatrixMath-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const MatrixMath = require('MatrixMath');
@@ -15,68 +17,106 @@ function degreesToRadians(degrees) {
 }
 
 function convertZeroes(degrees) {
-  return degrees.map(value => value === -0 ? 0 : value);
+  return degrees.map(value => (value === -0 ? 0 : value));
 }
 
 describe('MatrixMath', () => {
-
   it('decomposes a 4x4 matrix to produce accurate Z-axis angles', () => {
-    expect(MatrixMath.decomposeMatrix([
-      1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1
-    ]).rotationDegrees).toEqual([0, 0, 0]);
+    expect(
+      MatrixMath.decomposeMatrix([
+        1,
+        0,
+        0,
+        0,
+        0,
+        1,
+        0,
+        0,
+        0,
+        0,
+        1,
+        0,
+        0,
+        0,
+        0,
+        1,
+      ]).rotationDegrees,
+    ).toEqual([0, 0, 0]);
 
     [30, 45, 60, 75, 90, 100, 115, 120, 133, 167].forEach(angle => {
       let mat = MatrixMath.createRotateZ(degreesToRadians(angle));
-      expect(convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees))
-        .toEqual([0, 0, angle]);
+      expect(
+        convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees),
+      ).toEqual([0, 0, angle]);
 
       mat = MatrixMath.createRotateZ(degreesToRadians(-angle));
-      expect(convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees))
-        .toEqual([0, 0, -angle]);
+      expect(
+        convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees),
+      ).toEqual([0, 0, -angle]);
     });
 
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(180))
-    ).rotationDegrees).toEqual([0, 0, 180]);
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(180)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, 180]);
 
     // all values are between 0 and 180;
     // change of sign and direction in the third and fourth quadrant
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(222))
-    ).rotationDegrees).toEqual([0, 0, -138]);
-
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(270))
-    ).rotationDegrees).toEqual([0, 0, -90]);
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(222)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, -138]);
+
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(270)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, -90]);
 
     // 360 is expressed as 0
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(360))
-    ).rotationDegrees).toEqual([0, 0, -0]);
-
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(33.33333333))
-    ).rotationDegrees).toEqual([0, 0, 33.333]);
-
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(86.75309))
-    ).rotationDegrees).toEqual([0, 0, 86.753]);
-
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(42.00000000001))
-    ).rotationDegrees).toEqual([0, 0, 42]);
-
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(42.99999999999))
-    ).rotationDegrees).toEqual([0, 0, 43]);
-
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(42.49999999999))
-    ).rotationDegrees).toEqual([0, 0, 42.5]);
-
-    expect(MatrixMath.decomposeMatrix(
-      MatrixMath.createRotateZ(degreesToRadians(42.55555555555))
-    ).rotationDegrees).toEqual([0, 0, 42.556]);
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(360)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, -0]);
+
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(33.33333333)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, 33.333]);
+
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(86.75309)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, 86.753]);
+
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(42.00000000001)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, 42]);
+
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(42.99999999999)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, 43]);
+
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(42.49999999999)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, 42.5]);
+
+    expect(
+      MatrixMath.decomposeMatrix(
+        MatrixMath.createRotateZ(degreesToRadians(42.55555555555)),
+      ).rotationDegrees,
+    ).toEqual([0, 0, 42.556]);
   });
 
   it('decomposes a 4x4 matrix to produce accurate Y-axis angles', () => {
@@ -84,31 +124,38 @@ describe('MatrixMath', () => {
     [30, 45, 60, 75, 90, 100, 110, 120, 133, 167].forEach(angle => {
       mat = MatrixMath.createIdentityMatrix();
       MatrixMath.reuseRotateYCommand(mat, degreesToRadians(angle));
-      expect(convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees))
-        .toEqual([0, angle, 0]);
+      expect(
+        convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees),
+      ).toEqual([0, angle, 0]);
 
       mat = MatrixMath.createIdentityMatrix();
       MatrixMath.reuseRotateYCommand(mat, degreesToRadians(-angle));
-      expect(convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees))
-        .toEqual([0, -angle, 0]);
+      expect(
+        convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees),
+      ).toEqual([0, -angle, 0]);
     });
 
     // all values are between 0 and 180;
     // change of sign and direction in the third and fourth quadrant
     mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseRotateYCommand(mat, degreesToRadians(222));
-    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees)
-      .toEqual([0, -138, 0]);
+    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees).toEqual([
+      0,
+      -138,
+      0,
+    ]);
 
     mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseRotateYCommand(mat, degreesToRadians(270));
-    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees)
-      .toEqual([0, -90, 0]);
+    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees).toEqual([
+      0,
+      -90,
+      0,
+    ]);
 
     mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseRotateYCommand(mat, degreesToRadians(360));
-    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees)
-      .toEqual([0, 0, 0]);
+    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees).toEqual([0, 0, 0]);
   });
 
   it('decomposes a 4x4 matrix to produce accurate X-axis angles', () => {
@@ -116,26 +163,31 @@ describe('MatrixMath', () => {
     [30, 45, 60, 75, 90, 100, 110, 120, 133, 167].forEach(angle => {
       mat = MatrixMath.createIdentityMatrix();
       MatrixMath.reuseRotateXCommand(mat, degreesToRadians(angle));
-      expect(convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees))
-        .toEqual([angle, 0, 0]);
+      expect(
+        convertZeroes(MatrixMath.decomposeMatrix(mat).rotationDegrees),
+      ).toEqual([angle, 0, 0]);
     });
 
     // all values are between 0 and 180;
     // change of sign and direction in the third and fourth quadrant
     mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseRotateXCommand(mat, degreesToRadians(222));
-    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees)
-      .toEqual([-138, 0, 0]);
+    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees).toEqual([
+      -138,
+      0,
+      0,
+    ]);
 
     mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseRotateXCommand(mat, degreesToRadians(270));
-    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees)
-      .toEqual([-90, 0, 0]);
+    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees).toEqual([
+      -90,
+      0,
+      0,
+    ]);
 
     mat = MatrixMath.createIdentityMatrix();
     MatrixMath.reuseRotateXCommand(mat, degreesToRadians(360));
-    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees)
-      .toEqual([0, 0, 0]);
+    expect(MatrixMath.decomposeMatrix(mat).rotationDegrees).toEqual([0, 0, 0]);
   });
-
 });
diff --git a/Libraries/Utilities/__tests__/Platform-test.js b/Libraries/Utilities/__tests__/Platform-test.js
index 72dafb4329c7..823ed7e56882 100644
--- a/Libraries/Utilities/__tests__/Platform-test.js
+++ b/Libraries/Utilities/__tests__/Platform-test.js
@@ -4,15 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const PlatformIOS = require('../Platform.ios');
 const PlatformAndroid = require('../Platform.android');
 
 describe('Platform', () => {
-
   describe('OS', () => {
     it('should have correct value', () => {
       expect(PlatformIOS.OS).toEqual('ios');
@@ -22,10 +23,9 @@ describe('Platform', () => {
 
   describe('select', () => {
     it('should return platform specific value', () => {
-      const obj = { ios: 'ios', android: 'android' };
+      const obj = {ios: 'ios', android: 'android'};
       expect(PlatformIOS.select(obj)).toEqual(obj.ios);
       expect(PlatformAndroid.select(obj)).toEqual(obj.android);
     });
   });
-
 });
diff --git a/Libraries/Utilities/__tests__/SceneTracker-test.js b/Libraries/Utilities/__tests__/SceneTracker-test.js
index 22dd9cadba85..2e95b87cb3ad 100644
--- a/Libraries/Utilities/__tests__/SceneTracker-test.js
+++ b/Libraries/Utilities/__tests__/SceneTracker-test.js
@@ -4,18 +4,19 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const SceneTracker = require('SceneTracker');
 
 describe('setActiveScene', function() {
-
   it('can handle multiple listeners and unsubscribe', function() {
     const listeners = [jest.fn(), jest.fn(), jest.fn()];
-    const subscriptions = listeners.map(
-      (listener) => SceneTracker.addActiveSceneChangedListener(listener)
+    const subscriptions = listeners.map(listener =>
+      SceneTracker.addActiveSceneChangedListener(listener),
     );
     subscriptions[1].remove();
     const newScene = {name: 'scene1'};
diff --git a/Libraries/Utilities/__tests__/buildStyleInterpolator-test.js b/Libraries/Utilities/__tests__/buildStyleInterpolator-test.js
index 78440b640010..321f541e91b4 100644
--- a/Libraries/Utilities/__tests__/buildStyleInterpolator-test.js
+++ b/Libraries/Utilities/__tests__/buildStyleInterpolator-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const buildStyleInterpolator = require('buildStyleInterpolator');
@@ -87,7 +89,7 @@ describe('buildStyleInterpolator', function() {
         min: 0,
         max: 1,
         type: 'linear',
-        round: 1,  // To make testing easier
+        round: 1, // To make testing easier
         extrapolate: true,
       },
       left: {
@@ -96,7 +98,7 @@ describe('buildStyleInterpolator', function() {
         min: 0,
         max: 1,
         type: 'linear',
-        round: 1,  // To make testing easier
+        round: 1, // To make testing easier
         extrapolate: true,
       },
       top: {
@@ -149,7 +151,7 @@ describe('buildStyleInterpolator', function() {
         min: 0,
         max: 1,
         type: 'linear',
-        round: 2,  // As in one over two
+        round: 2, // As in one over two
         extrapolate: true,
       },
     };
@@ -193,7 +195,7 @@ describe('buildStyleInterpolator', function() {
         min: 0,
         max: 1,
         type: 'linear',
-        round: 2,  // As in one over two
+        round: 2, // As in one over two
         extrapolate: false,
       },
     };
@@ -261,10 +263,11 @@ describe('buildStyleInterpolator', function() {
     const obj = {};
     const res = interpolator(obj, 1);
     expect(obj).toEqual({
-      transform: [{matrix: [1, 0, 0, 0,
-                            0, 1, 0, 0,
-                            0, 0, 1, 0,
-                            2, 20, 200, 1]}]
+      transform: [
+        {
+          matrix: [1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 2, 20, 200, 1],
+        },
+      ],
     });
     expect(res).toBe(true);
   });
@@ -282,10 +285,11 @@ describe('buildStyleInterpolator', function() {
     const obj = {};
     const res = interpolator(obj, 1);
     expect(obj).toEqual({
-      transform: [{matrix: [2, 0, 0, 0,
-                            0, 20, 0, 0,
-                            0, 0, 200, 0,
-                            0, 0, 0, 1]}]
+      transform: [
+        {
+          matrix: [2, 0, 0, 0, 0, 20, 0, 0, 0, 0, 200, 0, 0, 0, 0, 1],
+        },
+      ],
     });
     expect(res).toBe(true);
   });
@@ -310,10 +314,11 @@ describe('buildStyleInterpolator', function() {
     const obj = {};
     const res = interpolator(obj, 1);
     expect(obj).toEqual({
-      transform: [{matrix: [2, 0, 0, 0,
-                            0, 20, 0, 0,
-                            0, 0, 200, 0,
-                            4, 400, 40000, 1]}]
+      transform: [
+        {
+          matrix: [2, 0, 0, 0, 0, 20, 0, 0, 0, 0, 200, 0, 4, 400, 40000, 1],
+        },
+      ],
     });
     expect(res).toBe(true);
   });
diff --git a/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js b/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
index f00b974d95e9..3ec7c7bab78b 100644
--- a/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
+++ b/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
@@ -4,12 +4,13 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 const deepFreezeAndThrowOnMutationInDev = require('deepFreezeAndThrowOnMutationInDev');
 
 describe('deepFreezeAndThrowOnMutationInDev', function() {
-
   it('should be a noop on non object values', () => {
     __DEV__ = true;
     expect(() => deepFreezeAndThrowOnMutationInDev('')).not.toThrow();
@@ -30,9 +31,11 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     __DEV__ = true;
     const o = {key: 'oldValue'};
     deepFreezeAndThrowOnMutationInDev(o);
-    expect(() => { o.key = 'newValue'; }).toThrowError(
+    expect(() => {
+      o.key = 'newValue';
+    }).toThrowError(
       'You attempted to set the key `key` with the value `"newValue"` ' +
-      'on an object that is meant to be immutable and has been frozen.'
+        'on an object that is meant to be immutable and has been frozen.',
     );
     expect(o.key).toBe('oldValue');
   });
@@ -41,9 +44,11 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     __DEV__ = true;
     const o = {key: 'oldValue'};
     deepFreezeAndThrowOnMutationInDev(o);
-    expect(() => { o.key = 'newValue'; }).toThrowError(
+    expect(() => {
+      o.key = 'newValue';
+    }).toThrowError(
       'You attempted to set the key `key` with the value `"newValue"` ' +
-      'on an object that is meant to be immutable and has been frozen.'
+        'on an object that is meant to be immutable and has been frozen.',
     );
     expect(o.key).toBe('oldValue');
   });
@@ -53,9 +58,11 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     __DEV__ = true;
     const o = {key1: {key2: {key3: 'oldValue'}}};
     deepFreezeAndThrowOnMutationInDev(o);
-    expect(() => { o.key1.key2.key3 = 'newValue'; }).toThrowError(
+    expect(() => {
+      o.key1.key2.key3 = 'newValue';
+    }).toThrowError(
       'You attempted to set the key `key3` with the value `"newValue"` ' +
-      'on an object that is meant to be immutable and has been frozen.'
+        'on an object that is meant to be immutable and has been frozen.',
     );
     expect(o.key1.key2.key3).toBe('oldValue');
   });
@@ -64,9 +71,11 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     __DEV__ = true;
     const o = {key1: {key2: {key3: 'oldValue'}}};
     deepFreezeAndThrowOnMutationInDev(o);
-    expect(() => { o.key1.key2.key3 = 'newValue'; }).toThrowError(
+    expect(() => {
+      o.key1.key2.key3 = 'newValue';
+    }).toThrowError(
       'You attempted to set the key `key3` with the value `"newValue"` ' +
-      'on an object that is meant to be immutable and has been frozen.'
+        'on an object that is meant to be immutable and has been frozen.',
     );
     expect(o.key1.key2.key3).toBe('oldValue');
   });
@@ -76,10 +85,11 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     __DEV__ = true;
     const o = {oldKey: 'value'};
     deepFreezeAndThrowOnMutationInDev(o);
-    expect(() => { o.newKey = 'value'; })
-      .toThrowError(
-        /(Cannot|Can't) add property newKey, object is not extensible/
-      );
+    expect(() => {
+      o.newKey = 'value';
+    }).toThrowError(
+      /(Cannot|Can't) add property newKey, object is not extensible/,
+    );
     expect(o.newKey).toBe(undefined);
   });
 
@@ -87,7 +97,9 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     __DEV__ = true;
     const o = {oldKey: 'value'};
     deepFreezeAndThrowOnMutationInDev(o);
-    expect(() => { o.newKey = 'value'; }).not.toThrow();
+    expect(() => {
+      o.newKey = 'value';
+    }).not.toThrow();
     expect(o.newKey).toBe(undefined);
   });
 
@@ -96,7 +108,9 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     __DEV__ = false;
     const o = {key: 'oldValue'};
     deepFreezeAndThrowOnMutationInDev(o);
-    expect(() => { o.key = 'newValue'; }).not.toThrow();
+    expect(() => {
+      o.key = 'newValue';
+    }).not.toThrow();
     expect(o.key).toBe('newValue');
   });
 
@@ -107,7 +121,9 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     const o = {key1: {key2: 'oldValue'}};
     Object.freeze(o);
     deepFreezeAndThrowOnMutationInDev(o);
-    expect(() => { o.key1.key2 = 'newValue'; }).not.toThrow();
+    expect(() => {
+      o.key1.key2 = 'newValue';
+    }).not.toThrow();
     expect(o.key1.key2).toBe('newValue');
   });
 
@@ -117,5 +133,4 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     o.circular = o;
     deepFreezeAndThrowOnMutationInDev(o);
   });
-
 });
diff --git a/Libraries/Utilities/__tests__/groupByEveryN-test.js b/Libraries/Utilities/__tests__/groupByEveryN-test.js
index 56baa9b0ac62..a084cf225ec5 100644
--- a/Libraries/Utilities/__tests__/groupByEveryN-test.js
+++ b/Libraries/Utilities/__tests__/groupByEveryN-test.js
@@ -4,34 +4,51 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 describe('groupByEveryN', () => {
   const groupByEveryN = require('groupByEveryN');
 
   it('should group by with different n', () => {
-    expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 1))
-      .toEqual([[1], [2], [3], [4], [5], [6], [7], [8], [9]]);
-    expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 2))
-      .toEqual([[1, 2], [3, 4], [5, 6], [7, 8], [9, null]]);
-    expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 3))
-      .toEqual([[1, 2, 3], [4, 5, 6], [7, 8, 9]]);
-    expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 4))
-      .toEqual([[1, 2, 3, 4], [5, 6, 7, 8], [9, null, null, null]]);
+    expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 1)).toEqual([
+      [1],
+      [2],
+      [3],
+      [4],
+      [5],
+      [6],
+      [7],
+      [8],
+      [9],
+    ]);
+    expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 2)).toEqual([
+      [1, 2],
+      [3, 4],
+      [5, 6],
+      [7, 8],
+      [9, null],
+    ]);
+    expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 3)).toEqual([
+      [1, 2, 3],
+      [4, 5, 6],
+      [7, 8, 9],
+    ]);
+    expect(groupByEveryN([1, 2, 3, 4, 5, 6, 7, 8, 9], 4)).toEqual([
+      [1, 2, 3, 4],
+      [5, 6, 7, 8],
+      [9, null, null, null],
+    ]);
   });
 
   it('should fill with null', () => {
-    expect(groupByEveryN([], 4))
-      .toEqual([]);
-    expect(groupByEveryN([1], 4))
-      .toEqual([[1, null, null, null]]);
-    expect(groupByEveryN([1, 2], 4))
-      .toEqual([[1, 2, null, null]]);
-    expect(groupByEveryN([1, 2, 3], 4))
-      .toEqual([[1, 2, 3, null]]);
-    expect(groupByEveryN([1, 2, 3, 4], 4))
-      .toEqual([[1, 2, 3, 4]]);
+    expect(groupByEveryN([], 4)).toEqual([]);
+    expect(groupByEveryN([1], 4)).toEqual([[1, null, null, null]]);
+    expect(groupByEveryN([1, 2], 4)).toEqual([[1, 2, null, null]]);
+    expect(groupByEveryN([1, 2, 3], 4)).toEqual([[1, 2, 3, null]]);
+    expect(groupByEveryN([1, 2, 3, 4], 4)).toEqual([[1, 2, 3, 4]]);
   });
 });
diff --git a/Libraries/Utilities/__tests__/mapWithSeparator-test.js b/Libraries/Utilities/__tests__/mapWithSeparator-test.js
index 8f64e0dfa17d..96de9fa889aa 100644
--- a/Libraries/Utilities/__tests__/mapWithSeparator-test.js
+++ b/Libraries/Utilities/__tests__/mapWithSeparator-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 describe('mapWithSeparator', () => {
@@ -20,7 +22,7 @@ describe('mapWithSeparator', () => {
       },
       function() {
         return 0;
-      }
+      },
     );
     expect(result).toEqual([2, 0, 4, 0, 6]);
   });
@@ -34,7 +36,7 @@ describe('mapWithSeparator', () => {
       },
       function(index) {
         return index;
-      }
+      },
     );
     expect(result).toEqual([0, 0, 1, 1, 2]);
   });
@@ -48,7 +50,7 @@ describe('mapWithSeparator', () => {
       },
       function(index) {
         return index;
-      }
+      },
     );
     expect(result).toEqual([3, 0, 2, 1, 1]);
   });
diff --git a/Libraries/Utilities/__tests__/truncate-test.js b/Libraries/Utilities/__tests__/truncate-test.js
index 47b2a3ae9803..b9eb0eef5faf 100644
--- a/Libraries/Utilities/__tests__/truncate-test.js
+++ b/Libraries/Utilities/__tests__/truncate-test.js
@@ -4,52 +4,50 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 describe('truncate', () => {
-
   const truncate = require('truncate');
 
   it('should truncate', () => {
-    expect(truncate('Hello, world.', 5))
-      .toBe('He...');
+    expect(truncate('Hello, world.', 5)).toBe('He...');
   });
   it('should not truncate', () => {
-    expect(truncate('Hello, world.', 50))
-      .toBe('Hello, world.');
+    expect(truncate('Hello, world.', 50)).toBe('Hello, world.');
   });
   it('should not truncate more than minDelta chars.', () => {
-    expect(truncate('Hello, world.', 7, {minDelta: 10}))
-      .toBe('Hello, world.');
-    expect(truncate('Hello, world.', 7, {minDelta: 9}))
-      .toBe('Hell...');
+    expect(truncate('Hello, world.', 7, {minDelta: 10})).toBe('Hello, world.');
+    expect(truncate('Hello, world.', 7, {minDelta: 9})).toBe('Hell...');
   });
   it('should break in the middle of words', () => {
-    expect(truncate('Hello, world.  How are you?', 18, {breakOnWords: false}))
-      .toBe('Hello, world.  H...');
-    expect(truncate('Hello, world.\nHow are you?', 18, {breakOnWords: false}))
-      .toBe('Hello, world.\nHo...');
+    expect(
+      truncate('Hello, world.  How are you?', 18, {breakOnWords: false}),
+    ).toBe('Hello, world.  H...');
+    expect(
+      truncate('Hello, world.\nHow are you?', 18, {breakOnWords: false}),
+    ).toBe('Hello, world.\nHo...');
   });
   it('should break at word boundaries', () => {
-    expect(truncate('Hello, world.  How are you?', 18, {breakOnWords: true}))
-      .toBe('Hello, world....');
-    expect(truncate('Hello, world.\nHow are you?', 18, {breakOnWords: true}))
-      .toBe('Hello, world....');
+    expect(
+      truncate('Hello, world.  How are you?', 18, {breakOnWords: true}),
+    ).toBe('Hello, world....');
+    expect(
+      truncate('Hello, world.\nHow are you?', 18, {breakOnWords: true}),
+    ).toBe('Hello, world....');
   });
   it('should uses custom elipses', () => {
-    expect(truncate('Hello, world.', 9, {elipsis: '&middot'}))
-      .toBe('He&middot');
+    expect(truncate('Hello, world.', 9, {elipsis: '&middot'})).toBe(
+      'He&middot',
+    );
   });
-  it('shouldn\'t barf with weird input', () => {
-    expect(truncate('Hello, world.', 0))
-      .toBe('Hello,...');
-    expect(truncate('Hello, world.', -132))
-      .toBe('...');
-    expect(truncate('', 0))
-      .toBe('');
-    expect(truncate(null, 0))
-      .toBe(null);
+  it("shouldn't barf with weird input", () => {
+    expect(truncate('Hello, world.', 0)).toBe('Hello,...');
+    expect(truncate('Hello, world.', -132)).toBe('...');
+    expect(truncate('', 0)).toBe('');
+    expect(truncate(null, 0)).toBe(null);
   });
 });
diff --git a/Libraries/Utilities/binaryToBase64.js b/Libraries/Utilities/binaryToBase64.js
index 74a01a0bcad4..78e6ae97bc60 100644
--- a/Libraries/Utilities/binaryToBase64.js
+++ b/Libraries/Utilities/binaryToBase64.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
diff --git a/Libraries/Utilities/buildStyleInterpolator.js b/Libraries/Utilities/buildStyleInterpolator.js
index 2ffed265f1df..c316409876c2 100644
--- a/Libraries/Utilities/buildStyleInterpolator.js
+++ b/Libraries/Utilities/buildStyleInterpolator.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -39,7 +40,7 @@ const InterpolateMatrix = {
     mat[13] = mat[1] * x + mat[5] * y + mat[9] * z + mat[13];
     mat[14] = mat[2] * x + mat[6] * y + mat[10] * z + mat[14];
     mat[15] = mat[3] * x + mat[7] * y + mat[11] * z + mat[15];
-  }
+  },
 };
 
 const computeNextValLinear = function(anim, from, to, value) {
@@ -47,7 +48,7 @@ const computeNextValLinear = function(anim, from, to, value) {
   const roundRatio = anim.round;
   let ratio = (value - anim.min) / (anim.max - anim.min);
   if (!anim.extrapolate) {
-    ratio = ratio > 1 ? 1 : (ratio < 0 ? 0 : ratio);
+    ratio = ratio > 1 ? 1 : ratio < 0 ? 0 : ratio;
   }
   let nextVal = from * (1 - ratio) + to * ratio;
   if (hasRoundRatio) {
@@ -64,7 +65,7 @@ const setNextValAndDetectChange = function(result, name, nextVal, didChange) {
   if (!didChange) {
     const prevVal = result[name];
     result[name] = nextVal;
-    didChange = didChange  || (nextVal !== prevVal);
+    didChange = didChange || nextVal !== prevVal;
   } else {
     result[name] = nextVal;
   }
@@ -90,7 +91,13 @@ const initIdentity = function(mat) {
   mat[15] = 1;
 };
 
-const computeNextMatrixOperationField = function(anim, name, dim, index, value) {
+const computeNextMatrixOperationField = function(
+  anim,
+  name,
+  dim,
+  index,
+  value,
+) {
   if (anim.from[dim] !== undefined && anim.to[dim] !== undefined) {
     return computeNextValLinear(anim, anim.from[dim], anim.to[dim], value);
   } else {
@@ -98,10 +105,18 @@ const computeNextMatrixOperationField = function(anim, name, dim, index, value)
   }
 };
 
-const computeTransform = function(anim, name, value, result,
-                                didChange, didMatrix) {
-  const transform = result.transform !== undefined ?
-        result.transform : (result.transform = [{ matrix: [] }]);
+const computeTransform = function(
+  anim,
+  name,
+  value,
+  result,
+  didChange,
+  didMatrix,
+) {
+  const transform =
+    result.transform !== undefined
+      ? result.transform
+      : (result.transform = [{matrix: []}]);
   const mat = transform[0].matrix;
   const m0 = mat[0];
   const m1 = mat[1];
@@ -120,21 +135,30 @@ const computeTransform = function(anim, name, value, result,
   const m14 = mat[14];
   const m15 = mat[15];
   if (!didMatrix) {
-    initIdentity(mat);  // This will be the first transform.
+    initIdentity(mat); // This will be the first transform.
   }
   const x = computeNextMatrixOperationField(anim, name, X_DIM, 0, value);
   const y = computeNextMatrixOperationField(anim, name, Y_DIM, 1, value);
   const z = computeNextMatrixOperationField(anim, name, Z_DIM, 2, value);
   InterpolateMatrix[name](mat, x, y, z);
   if (!didChange) {
-    didChange = m0 !== mat[0] || m1 !== mat[1] ||
-                m2 !== mat[2] || m3 !== mat[3] ||
-                m4 !== mat[4] || m5 !== mat[5] ||
-                m6 !== mat[6] || m7 !== mat[7] ||
-                m8 !== mat[8] || m9 !== mat[9] ||
-                m10 !== mat[10] || m11 !== mat[11] ||
-                m12 !== mat[12] || m13 !== mat[13] ||
-                m14 !== mat[14] || m15 !== mat[15];
+    didChange =
+      m0 !== mat[0] ||
+      m1 !== mat[1] ||
+      m2 !== mat[2] ||
+      m3 !== mat[3] ||
+      m4 !== mat[4] ||
+      m5 !== mat[5] ||
+      m6 !== mat[6] ||
+      m7 !== mat[7] ||
+      m8 !== mat[8] ||
+      m9 !== mat[9] ||
+      m10 !== mat[10] ||
+      m11 !== mat[11] ||
+      m12 !== mat[12] ||
+      m13 !== mat[13] ||
+      m14 !== mat[14] ||
+      m15 !== mat[15];
   }
   return didChange;
 };
@@ -152,8 +176,14 @@ const buildStyleInterpolator = function(anims) {
       const anim = anims[name];
       if (anim.type === 'linear') {
         if (name in InterpolateMatrix) {
-          didChange = computeTransform(anim, name, value, result,
-                                       didChange, didMatrix);
+          didChange = computeTransform(
+            anim,
+            name,
+            value,
+            result,
+            didChange,
+            didMatrix,
+          );
           didMatrix = true;
         } else {
           var next = computeNextValLinearScalar(anim, value);
diff --git a/Libraries/Utilities/clamp.js b/Libraries/Utilities/clamp.js
index dcfc93d855dd..50f60f17c8ce 100644
--- a/Libraries/Utilities/clamp.js
+++ b/Libraries/Utilities/clamp.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @typechecks
  */
+
 'use strict';
 
 /**
diff --git a/Libraries/Utilities/createStrictShapeTypeChecker.js b/Libraries/Utilities/createStrictShapeTypeChecker.js
index 558119f6ae04..ad097e968234 100644
--- a/Libraries/Utilities/createStrictShapeTypeChecker.js
+++ b/Libraries/Utilities/createStrictShapeTypeChecker.js
@@ -4,23 +4,32 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const invariant = require('fbjs/lib/invariant');
 const merge = require('merge');
 
-function createStrictShapeTypeChecker(
-  shapeTypes: {[key: string]: ReactPropsCheckType}
-): ReactPropsChainableTypeChecker {
-  function checkType(isRequired, props, propName, componentName, location?, ...rest) {
+function createStrictShapeTypeChecker(shapeTypes: {
+  [key: string]: ReactPropsCheckType,
+}): ReactPropsChainableTypeChecker {
+  function checkType(
+    isRequired,
+    props,
+    propName,
+    componentName,
+    location?,
+    ...rest
+  ) {
     if (!props[propName]) {
       if (isRequired) {
         invariant(
           false,
           `Required object \`${propName}\` was not specified in ` +
-          `\`${componentName}\`.`
+            `\`${componentName}\`.`,
         );
       }
       return;
@@ -32,7 +41,7 @@ function createStrictShapeTypeChecker(
       invariant(
         false,
         `Invalid ${locationName} \`${propName}\` of type \`${propType}\` ` +
-          `supplied to \`${componentName}\`, expected \`object\`.`
+          `supplied to \`${componentName}\`, expected \`object\`.`,
       );
     }
     // We need to check all keys in case some are required but missing from
@@ -44,8 +53,10 @@ function createStrictShapeTypeChecker(
         invariant(
           false,
           `Invalid props.${propName} key \`${key}\` supplied to \`${componentName}\`.` +
-            '\nBad object: ' + JSON.stringify(props[propName], null, '  ') +
-            '\nValid keys: ' + JSON.stringify(Object.keys(shapeTypes), null, '  ')
+            '\nBad object: ' +
+            JSON.stringify(props[propName], null, '  ') +
+            '\nValid keys: ' +
+            JSON.stringify(Object.keys(shapeTypes), null, '  '),
         );
       }
       const error = checker(propValue, key, componentName, location, ...rest);
@@ -53,7 +64,8 @@ function createStrictShapeTypeChecker(
         invariant(
           false,
           error.message +
-            '\nBad object: ' + JSON.stringify(props[propName], null, '  ')
+            '\nBad object: ' +
+            JSON.stringify(props[propName], null, '  '),
         );
       }
     }
diff --git a/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js b/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
index 9e21a2aae63c..71a29584a358 100644
--- a/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
+++ b/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -28,10 +29,12 @@
  */
 function deepFreezeAndThrowOnMutationInDev<T: Object>(object: T): T {
   if (__DEV__) {
-    if (typeof object !== 'object' ||
-        object === null ||
-        Object.isFrozen(object) ||
-        Object.isSealed(object)) {
+    if (
+      typeof object !== 'object' ||
+      object === null ||
+      Object.isFrozen(object) ||
+      Object.isSealed(object)
+    ) {
       return object;
     }
 
@@ -60,9 +63,12 @@ function deepFreezeAndThrowOnMutationInDev<T: Object>(object: T): T {
 
 function throwOnImmutableMutation(key, value) {
   throw Error(
-    'You attempted to set the key `' + key + '` with the value `' +
-    JSON.stringify(value) + '` on an object that is meant to be immutable ' +
-    'and has been frozen.'
+    'You attempted to set the key `' +
+      key +
+      '` with the value `' +
+      JSON.stringify(value) +
+      '` on an object that is meant to be immutable ' +
+      'and has been frozen.',
   );
 }
 
diff --git a/Libraries/Utilities/defineLazyObjectProperty.js b/Libraries/Utilities/defineLazyObjectProperty.js
index cd01de5c2709..53091c4dff27 100644
--- a/Libraries/Utilities/defineLazyObjectProperty.js
+++ b/Libraries/Utilities/defineLazyObjectProperty.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/Libraries/Utilities/deprecatedPropType.js b/Libraries/Utilities/deprecatedPropType.js
index 398410545ed8..7421b44e9504 100644
--- a/Libraries/Utilities/deprecatedPropType.js
+++ b/Libraries/Utilities/deprecatedPropType.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const UIManager = require('UIManager');
@@ -15,20 +17,17 @@ const UIManager = require('UIManager');
  */
 function deprecatedPropType(
   propType: ReactPropsCheckType,
-  explanation: string
+  explanation: string,
 ): ReactPropsCheckType {
   return function validate(props, propName, componentName, ...rest) {
     // Don't warn for native components.
     if (!UIManager[componentName] && props[propName] !== undefined) {
-      console.warn(`\`${propName}\` supplied to \`${componentName}\` has been deprecated. ${explanation}`);
+      console.warn(
+        `\`${propName}\` supplied to \`${componentName}\` has been deprecated. ${explanation}`,
+      );
     }
 
-    return propType(
-      props,
-      propName,
-      componentName,
-      ...rest
-    );
+    return propType(props, propName, componentName, ...rest);
   };
 }
 
diff --git a/Libraries/Utilities/differ/__tests__/deepDiffer-test.js b/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
index cb39370dc5c4..fd27aa8b1b41 100644
--- a/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
+++ b/Libraries/Utilities/differ/__tests__/deepDiffer-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 const deepDiffer = require('deepDiffer');
@@ -47,14 +49,18 @@ describe('deepDiffer', function() {
     expect(deepDiffer({a: 1, b: 1}, {a: 1})).toBe(true);
     expect(deepDiffer({a: {A: 1}, b: 1}, {a: {A: 1}, b: 1})).toBe(false);
     expect(deepDiffer({a: {A: 1}, b: 1}, {a: {A: 2}, b: 1})).toBe(true);
-    expect(deepDiffer(
-      {a: {A: {aA: 1, bB: 1}}, b: 1},
-      {a: {A: {aA: 1, bB: 1}}, b: 1}
-    )).toBe(false);
-    expect(deepDiffer(
-      {a: {A: {aA: 1, bB: 1}}, b: 1},
-      {a: {A: {aA: 1, cC: 1}}, b: 1}
-    )).toBe(true);
+    expect(
+      deepDiffer(
+        {a: {A: {aA: 1, bB: 1}}, b: 1},
+        {a: {A: {aA: 1, bB: 1}}, b: 1},
+      ),
+    ).toBe(false);
+    expect(
+      deepDiffer(
+        {a: {A: {aA: 1, bB: 1}}, b: 1},
+        {a: {A: {aA: 1, cC: 1}}, b: 1},
+      ),
+    ).toBe(true);
   });
   it('should diff Arrays', () => {
     expect(deepDiffer([], [])).toBe(false);
@@ -73,41 +79,53 @@ describe('deepDiffer', function() {
   it('should diff mixed types', () => {
     expect(deepDiffer({}, [])).toBe(true);
     expect(deepDiffer([], {})).toBe(true);
-    expect(deepDiffer(
-      {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
-      {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]}
-    )).toBe(false);
-    expect(deepDiffer(
-      {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
-      {a: [{A: {aA: 1, bB: 2}}, 'bar'], c: [1, [false]]}
-    )).toBe(true);
-    expect(deepDiffer(
-      {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
-      {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false], null]}
-    )).toBe(true);
-    expect(deepDiffer(
-      {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
-      {a: [{A: {aA: 1, bB: 1}}, ['bar']], c: [1, [false]]}
-    )).toBe(true);
+    expect(
+      deepDiffer(
+        {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
+        {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
+      ),
+    ).toBe(false);
+    expect(
+      deepDiffer(
+        {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
+        {a: [{A: {aA: 1, bB: 2}}, 'bar'], c: [1, [false]]},
+      ),
+    ).toBe(true);
+    expect(
+      deepDiffer(
+        {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
+        {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false], null]},
+      ),
+    ).toBe(true);
+    expect(
+      deepDiffer(
+        {a: [{A: {aA: 1, bB: 1}}, 'bar'], c: [1, [false]]},
+        {a: [{A: {aA: 1, bB: 1}}, ['bar']], c: [1, [false]]},
+      ),
+    ).toBe(true);
   });
   it('should distinguish between proper Array and Object', () => {
     expect(deepDiffer(['a', 'b'], {0: 'a', 1: 'b', length: 2})).toBe(true);
     expect(deepDiffer(['a', 'b'], {length: 2, 0: 'a', 1: 'b'})).toBe(true);
   });
   it('should diff same object', () => {
-    const obj = [1,[2,3]];
+    const obj = [1, [2, 3]];
     expect(deepDiffer(obj, obj)).toBe(false);
   });
   it('should respect maxDepth arg', () => {
-    expect(deepDiffer(
-      {a: {A: {aA: 1, bB: 1}}, b: 1},
-      {a: {A: {aA: 1, bB: 1}}, b: 1},
-      3
-    )).toBe(true);
-    expect(deepDiffer(
-      {a: {A: {aA: 1, bB: 1}}, b: 1},
-      {a: {A: {aA: 1, bB: 1}}, b: 1},
-      4
-    )).toBe(false);
+    expect(
+      deepDiffer(
+        {a: {A: {aA: 1, bB: 1}}, b: 1},
+        {a: {A: {aA: 1, bB: 1}}, b: 1},
+        3,
+      ),
+    ).toBe(true);
+    expect(
+      deepDiffer(
+        {a: {A: {aA: 1, bB: 1}}, b: 1},
+        {a: {A: {aA: 1, bB: 1}}, b: 1},
+        4,
+      ),
+    ).toBe(false);
   });
 });
diff --git a/Libraries/Utilities/differ/deepDiffer.js b/Libraries/Utilities/differ/deepDiffer.js
index 94dc0cd71dc2..8c51cf2117c7 100644
--- a/Libraries/Utilities/differ/deepDiffer.js
+++ b/Libraries/Utilities/differ/deepDiffer.js
@@ -4,14 +4,20 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /*
  * @returns {bool} true if different, false if equal
  */
-const deepDiffer = function(one: any, two: any, maxDepth: number = -1): bool {
+const deepDiffer = function(
+  one: any,
+  two: any,
+  maxDepth: number = -1,
+): boolean {
   if (maxDepth === 0) {
     return true;
   }
@@ -19,15 +25,15 @@ const deepDiffer = function(one: any, two: any, maxDepth: number = -1): bool {
     // Short circuit on identical object references instead of traversing them.
     return false;
   }
-  if ((typeof one === 'function') && (typeof two === 'function')) {
+  if (typeof one === 'function' && typeof two === 'function') {
     // We consider all functions equal
     return false;
   }
-  if ((typeof one !== 'object') || (one === null)) {
+  if (typeof one !== 'object' || one === null) {
     // Primitives can be directly compared
     return one !== two;
   }
-  if ((typeof two !== 'object') || (two === null)) {
+  if (typeof two !== 'object' || two === null) {
     // We know they are different because the previous case would have triggered
     // otherwise.
     return true;
diff --git a/Libraries/Utilities/differ/insetsDiffer.js b/Libraries/Utilities/differ/insetsDiffer.js
index c86f6d17b4e1..c0031775fc2e 100644
--- a/Libraries/Utilities/differ/insetsDiffer.js
+++ b/Libraries/Utilities/differ/insetsDiffer.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 type Inset = {
@@ -13,26 +15,24 @@ type Inset = {
   left: ?number,
   right: ?number,
   bottom: ?number,
-}
+};
 
 const dummyInsets = {
-	top: undefined,
-	left: undefined,
-	right: undefined,
-	bottom: undefined,
+  top: undefined,
+  left: undefined,
+  right: undefined,
+  bottom: undefined,
 };
 
-const insetsDiffer = function(
-  one: ?Inset,
-  two: ?Inset
-): bool {
+const insetsDiffer = function(one: ?Inset, two: ?Inset): boolean {
   one = one || dummyInsets;
   two = two || dummyInsets;
-  return one !== two && (
-    one.top !== two.top ||
-    one.left !== two.left ||
-    one.right !== two.right ||
-    one.bottom !== two.bottom
+  return (
+    one !== two &&
+    (one.top !== two.top ||
+      one.left !== two.left ||
+      one.right !== two.right ||
+      one.bottom !== two.bottom)
   );
 };
 
diff --git a/Libraries/Utilities/differ/matricesDiffer.js b/Libraries/Utilities/differ/matricesDiffer.js
index 883081fa0ab8..0b2d2005f84a 100644
--- a/Libraries/Utilities/differ/matricesDiffer.js
+++ b/Libraries/Utilities/differ/matricesDiffer.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 /**
@@ -20,7 +22,9 @@ const matricesDiffer = function(one, two) {
   if (one === two) {
     return false;
   }
-  return !one || !two ||
+  return (
+    !one ||
+    !two ||
     one[12] !== two[12] ||
     one[13] !== two[13] ||
     one[14] !== two[14] ||
@@ -35,7 +39,8 @@ const matricesDiffer = function(one, two) {
     one[8] !== two[8] ||
     one[9] !== two[9] ||
     one[11] !== two[11] ||
-    one[15] !== two[15];
+    one[15] !== two[15]
+  );
 };
 
 module.exports = matricesDiffer;
diff --git a/Libraries/Utilities/differ/pointsDiffer.js b/Libraries/Utilities/differ/pointsDiffer.js
index b9d239c7907f..ebaa014da2ed 100644
--- a/Libraries/Utilities/differ/pointsDiffer.js
+++ b/Libraries/Utilities/differ/pointsDiffer.js
@@ -4,24 +4,23 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 type Point = {
   x: ?number,
   y: ?number,
-}
+};
 
 const dummyPoint = {x: undefined, y: undefined};
 
-const pointsDiffer = function(one: ?Point, two: ?Point): bool {
+const pointsDiffer = function(one: ?Point, two: ?Point): boolean {
   one = one || dummyPoint;
   two = two || dummyPoint;
-  return one !== two && (
-    one.x !== two.x ||
-    one.y !== two.y
-  );
+  return one !== two && (one.x !== two.x || one.y !== two.y);
 };
 
 module.exports = pointsDiffer;
diff --git a/Libraries/Utilities/differ/sizesDiffer.js b/Libraries/Utilities/differ/sizesDiffer.js
index ad2939cc71ef..9bf477572b23 100644
--- a/Libraries/Utilities/differ/sizesDiffer.js
+++ b/Libraries/Utilities/differ/sizesDiffer.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const dummySize = {width: undefined, height: undefined};
@@ -12,10 +14,7 @@ const dummySize = {width: undefined, height: undefined};
 const sizesDiffer = function(one, two) {
   one = one || dummySize;
   two = two || dummySize;
-  return one !== two && (
-    one.width !== two.width ||
-    one.height !== two.height
-  );
+  return one !== two && (one.width !== two.width || one.height !== two.height);
 };
 
 module.exports = sizesDiffer;
diff --git a/Libraries/Utilities/dismissKeyboard.js b/Libraries/Utilities/dismissKeyboard.js
index 64f7368a35da..ba212f2f9376 100644
--- a/Libraries/Utilities/dismissKeyboard.js
+++ b/Libraries/Utilities/dismissKeyboard.js
@@ -6,7 +6,10 @@
  *
  *
  * This function dismisses the currently-open keyboard, if any
+ *
+ * @format
  */
+
 'use strict';
 
 const TextInputState = require('TextInputState');
diff --git a/Libraries/Utilities/groupByEveryN.js b/Libraries/Utilities/groupByEveryN.js
index bdf13b226936..eb7dbb8eb24c 100644
--- a/Libraries/Utilities/groupByEveryN.js
+++ b/Libraries/Utilities/groupByEveryN.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/Libraries/Utilities/infoLog.js b/Libraries/Utilities/infoLog.js
index 9437179b163d..34b032fe7df5 100644
--- a/Libraries/Utilities/infoLog.js
+++ b/Libraries/Utilities/infoLog.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 /**
diff --git a/Libraries/Utilities/logError.js b/Libraries/Utilities/logError.js
index e79b340563ce..f0ed0b63a0c0 100644
--- a/Libraries/Utilities/logError.js
+++ b/Libraries/Utilities/logError.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /**
diff --git a/Libraries/Utilities/mapWithSeparator.js b/Libraries/Utilities/mapWithSeparator.js
index 09fe19cec897..f94459404a8c 100644
--- a/Libraries/Utilities/mapWithSeparator.js
+++ b/Libraries/Utilities/mapWithSeparator.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 function mapWithSeparator<TFrom, TTo>(
diff --git a/Libraries/Utilities/mergeIntoFast.js b/Libraries/Utilities/mergeIntoFast.js
index cfbc87923987..a1716a324f2b 100644
--- a/Libraries/Utilities/mergeIntoFast.js
+++ b/Libraries/Utilities/mergeIntoFast.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /**
diff --git a/Libraries/Utilities/stringifySafe.js b/Libraries/Utilities/stringifySafe.js
index 4536b8f668be..bfc6dc343f41 100644
--- a/Libraries/Utilities/stringifySafe.js
+++ b/Libraries/Utilities/stringifySafe.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /**
diff --git a/Libraries/Utilities/truncate.js b/Libraries/Utilities/truncate.js
index 017a524912c0..736ae6b452c7 100644
--- a/Libraries/Utilities/truncate.js
+++ b/Libraries/Utilities/truncate.js
@@ -4,15 +4,17 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 type truncateOptions = {
   breakOnWords: boolean,
   minDelta: number,
   elipsis: string,
-}
+};
 
 const defaultOptions = {
   breakOnWords: true,
@@ -24,15 +26,17 @@ const defaultOptions = {
 const truncate = function(
   str: ?string,
   maxChars: number,
-  options?: truncateOptions
+  options?: truncateOptions,
 ): ?string {
   options = Object.assign({}, defaultOptions, options);
-  if (str && str.length &&
-      str.length - options.minDelta + options.elipsis.length >= maxChars) {
+  if (
+    str &&
+    str.length &&
+    str.length - options.minDelta + options.elipsis.length >= maxChars
+  ) {
     // If the slice is happening in the middle of a wide char, add one more char
-    const extraChar = str.charCodeAt(maxChars - options.elipsis.length) > 255
-      ? 1
-      : 0;
+    const extraChar =
+      str.charCodeAt(maxChars - options.elipsis.length) > 255 ? 1 : 0;
     str = str.slice(0, maxChars - options.elipsis.length + 1 + extraChar);
     if (options.breakOnWords) {
       const ii = Math.max(str.lastIndexOf(' '), str.lastIndexOf('\n'));
diff --git a/Libraries/Vibration/Vibration.js b/Libraries/Vibration/Vibration.js
index 182ca26d9c50..39625ac3aa83 100644
--- a/Libraries/Vibration/Vibration.js
+++ b/Libraries/Vibration/Vibration.js
@@ -4,9 +4,11 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  * @jsdoc
  */
+
 'use strict';
 
 const RCTVibration = require('NativeModules').Vibration;
@@ -37,7 +39,12 @@ function vibrateByPattern(pattern: Array<number>, repeat: boolean = false) {
   setTimeout(() => vibrateScheduler(++_id, pattern, repeat, 1), pattern[0]);
 }
 
-function vibrateScheduler(id, pattern: Array<number>, repeat: boolean, nextIndex: number) {
+function vibrateScheduler(
+  id,
+  pattern: Array<number>,
+  repeat: boolean,
+  nextIndex: number,
+) {
   if (!_vibrating || id !== _id) {
     return;
   }
@@ -50,7 +57,10 @@ function vibrateScheduler(id, pattern: Array<number>, repeat: boolean, nextIndex
       return;
     }
   }
-  setTimeout(() => vibrateScheduler(id, pattern, repeat, nextIndex + 1), pattern[nextIndex]);
+  setTimeout(
+    () => vibrateScheduler(id, pattern, repeat, nextIndex + 1),
+    pattern[nextIndex],
+  );
 }
 
 const Vibration = {
@@ -59,7 +69,10 @@ const Vibration = {
    *
    * See https://facebook.github.io/react-native/docs/vibration.html#vibrate
    */
-  vibrate: function(pattern: number | Array<number> = 400, repeat: boolean = false) {
+  vibrate: function(
+    pattern: number | Array<number> = 400,
+    repeat: boolean = false,
+  ) {
     if (Platform.OS === 'android') {
       if (typeof pattern === 'number') {
         RCTVibration.vibrate(pattern);
@@ -92,7 +105,7 @@ const Vibration = {
     } else {
       RCTVibration.cancel();
     }
-  }
+  },
 };
 
 module.exports = Vibration;
diff --git a/Libraries/Vibration/VibrationIOS.android.js b/Libraries/Vibration/VibrationIOS.android.js
index 93a1aab1af83..59cbab19c273 100644
--- a/Libraries/Vibration/VibrationIOS.android.js
+++ b/Libraries/Vibration/VibrationIOS.android.js
@@ -6,7 +6,9 @@
  *
  * Stub of VibrationIOS for Android.
  *
+ * @format
  */
+
 'use strict';
 
 const warning = require('fbjs/lib/warning');
@@ -14,7 +16,7 @@ const warning = require('fbjs/lib/warning');
 const VibrationIOS = {
   vibrate: function() {
     warning('VibrationIOS is not supported on this platform!');
-  }
+  },
 };
 
 module.exports = VibrationIOS;
diff --git a/Libraries/Vibration/VibrationIOS.ios.js b/Libraries/Vibration/VibrationIOS.ios.js
index 29cc3eee02a4..6f1c95c9a294 100644
--- a/Libraries/Vibration/VibrationIOS.ios.js
+++ b/Libraries/Vibration/VibrationIOS.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const RCTVibration = require('NativeModules').Vibration;
@@ -30,12 +32,9 @@ const VibrationIOS = {
    * @deprecated
    */
   vibrate: function() {
-    invariant(
-      arguments[0] === undefined,
-      'Vibration patterns not supported.'
-    );
+    invariant(arguments[0] === undefined, 'Vibration patterns not supported.');
     RCTVibration.vibrate();
-  }
+  },
 };
 
 module.exports = VibrationIOS;
diff --git a/Libraries/WebSocket/WebSocket.js b/Libraries/WebSocket/WebSocket.js
index ef28c6ce464d..578d55e55d9c 100644
--- a/Libraries/WebSocket/WebSocket.js
+++ b/Libraries/WebSocket/WebSocket.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Blob = require('Blob');
@@ -37,9 +39,9 @@ type ArrayBufferView =
   | Uint32Array
   | Float32Array
   | Float64Array
-  | DataView
+  | DataView;
 
-type BinaryType = 'blob' | 'arraybuffer'
+type BinaryType = 'blob' | 'arraybuffer';
 
 const CONNECTING = 0;
 const OPEN = 1;
@@ -48,12 +50,7 @@ const CLOSED = 3;
 
 const CLOSE_NORMAL = 1000;
 
-const WEBSOCKET_EVENTS = [
-  'close',
-  'error',
-  'message',
-  'open',
-];
+const WEBSOCKET_EVENTS = ['close', 'error', 'message', 'open'];
 
 let nextWebSocketId = 0;
 
@@ -94,7 +91,11 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
   // `WebSocket.isAvailable` will return `false`, and WebSocket constructor will throw an error
   static isAvailable: boolean = !!WebSocketModule;
 
-  constructor(url: string, protocols: ?string | ?Array<string>, options: ?{headers?: {origin?: string}}) {
+  constructor(
+    url: string,
+    protocols: ?string | ?Array<string>,
+    options: ?{headers?: {origin?: string}},
+  ) {
     super();
     if (typeof protocols === 'string') {
       protocols = [protocols];
@@ -107,7 +108,9 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
      * error found when Flow v0.68 was deployed. To see the error delete this
      * comment and run Flow. */
     if (unrecognized && typeof unrecognized.origin === 'string') {
-      console.warn('Specifying `origin` as a WebSocket connection option is deprecated. Include it under `headers` instead.');
+      console.warn(
+        'Specifying `origin` as a WebSocket connection option is deprecated. Include it under `headers` instead.',
+      );
       /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This
        * comment suppresses an error found when Flow v0.54 was deployed. To see
        * the error delete this comment and run Flow. */
@@ -120,8 +123,12 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
 
     // Warn about and discard anything else
     if (Object.keys(unrecognized).length > 0) {
-      console.warn('Unrecognized WebSocket connection option(s) `' + Object.keys(unrecognized).join('`, `') + '`. '
-        + 'Did you mean to put these under `headers`?');
+      console.warn(
+        'Unrecognized WebSocket connection option(s) `' +
+          Object.keys(unrecognized).join('`, `') +
+          '`. ' +
+          'Did you mean to put these under `headers`?',
+      );
     }
 
     if (!Array.isArray(protocols)) {
@@ -129,14 +136,16 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
     }
 
     if (!WebSocket.isAvailable) {
-      throw new Error('Cannot initialize WebSocket module. ' +
-      'Native module WebSocketModule is missing.');
+      throw new Error(
+        'Cannot initialize WebSocket module. ' +
+          'Native module WebSocketModule is missing.',
+      );
     }
 
     this._eventEmitter = new NativeEventEmitter(WebSocketModule);
     this._socketId = nextWebSocketId++;
     this._registerEvents();
-    WebSocketModule.connect(url, protocols, { headers }, this._socketId);
+    WebSocketModule.connect(url, protocols, {headers}, this._socketId);
   }
 
   get binaryType(): ?BinaryType {
@@ -145,10 +154,13 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
 
   set binaryType(binaryType: BinaryType): void {
     if (binaryType !== 'blob' && binaryType !== 'arraybuffer') {
-      throw new Error('binaryType must be either \'blob\' or \'arraybuffer\'');
+      throw new Error("binaryType must be either 'blob' or 'arraybuffer'");
     }
     if (this._binaryType === 'blob' || binaryType === 'blob') {
-      invariant(BlobManager.isAvailable, 'Native module BlobModule is required for blob support');
+      invariant(
+        BlobManager.isAvailable,
+        'Native module BlobModule is required for blob support',
+      );
       if (binaryType === 'blob') {
         BlobManager.addWebSocketHandler(this._socketId);
       } else {
@@ -163,8 +175,7 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
   }
 
   close(code?: number, reason?: string): void {
-    if (this.readyState === this.CLOSING ||
-        this.readyState === this.CLOSED) {
+    if (this.readyState === this.CLOSING || this.readyState === this.CLOSED) {
       return;
     }
 
@@ -178,7 +189,10 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
     }
 
     if (data instanceof Blob) {
-      invariant(BlobManager.isAvailable, 'Native module BlobModule is required for blob support');
+      invariant(
+        BlobManager.isAvailable,
+        'Native module BlobModule is required for blob support',
+      );
       BlobManager.sendOverSocket(data, this._socketId);
       return;
     }
@@ -198,7 +212,7 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
 
   ping(): void {
     if (this.readyState === this.CONNECTING) {
-        throw new Error('INVALID_STATE_ERR');
+      throw new Error('INVALID_STATE_ERR');
     }
 
     WebSocketModule.ping(this._socketId);
@@ -239,7 +253,7 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
             data = BlobManager.createFromOptions(ev.data);
             break;
         }
-        this.dispatchEvent(new WebSocketEvent('message', { data }));
+        this.dispatchEvent(new WebSocketEvent('message', {data}));
       }),
       this._eventEmitter.addListener('websocketOpen', ev => {
         if (ev.id !== this._socketId) {
@@ -253,10 +267,12 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
           return;
         }
         this.readyState = this.CLOSED;
-        this.dispatchEvent(new WebSocketEvent('close', {
-          code: ev.code,
-          reason: ev.reason,
-        }));
+        this.dispatchEvent(
+          new WebSocketEvent('close', {
+            code: ev.code,
+            reason: ev.reason,
+          }),
+        );
         this._unregisterEvents();
         this.close();
       }),
@@ -265,15 +281,19 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
           return;
         }
         this.readyState = this.CLOSED;
-        this.dispatchEvent(new WebSocketEvent('error', {
-          message: ev.message,
-        }));
-        this.dispatchEvent(new WebSocketEvent('close', {
-          message: ev.message,
-        }));
+        this.dispatchEvent(
+          new WebSocketEvent('error', {
+            message: ev.message,
+          }),
+        );
+        this.dispatchEvent(
+          new WebSocketEvent('close', {
+            message: ev.message,
+          }),
+        );
         this._unregisterEvents();
         this.close();
-      })
+      }),
     ];
   }
 }
diff --git a/Libraries/WebSocket/WebSocketEvent.js b/Libraries/WebSocket/WebSocketEvent.js
index b72188d34b8c..0fa075b25a27 100644
--- a/Libraries/WebSocket/WebSocketEvent.js
+++ b/Libraries/WebSocket/WebSocketEvent.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
diff --git a/Libraries/WebSocket/WebSocketInterceptor.js b/Libraries/WebSocket/WebSocketInterceptor.js
index 0ab63cf662a9..186dfc253f8c 100644
--- a/Libraries/WebSocket/WebSocketInterceptor.js
+++ b/Libraries/WebSocket/WebSocketInterceptor.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
- 'use strict';
+
+'use strict';
 
 const RCTWebSocketModule = require('NativeModules').WebSocketModule;
 const NativeEventEmitter = require('NativeEventEmitter');
@@ -104,8 +106,9 @@ const WebSocketInterceptor = {
         if (onMessageCallback) {
           onMessageCallback(
             ev.id,
-            (ev.type === 'binary') ?
-            WebSocketInterceptor._arrayBufferToString(ev.data) : ev.data,
+            ev.type === 'binary'
+              ? WebSocketInterceptor._arrayBufferToString(ev.data)
+              : ev.data,
           );
         }
       }),
@@ -123,7 +126,7 @@ const WebSocketInterceptor = {
         if (onErrorCallback) {
           onErrorCallback(ev.id, {message: ev.message});
         }
-      })
+      }),
     ];
   },
 
@@ -178,14 +181,16 @@ const WebSocketInterceptor = {
     isInterceptorEnabled = true;
   },
 
-   _arrayBufferToString(data) {
+  _arrayBufferToString(data) {
     const value = base64.toByteArray(data).buffer;
     if (value === undefined || value === null) {
       return '(no value)';
     }
-    if (typeof ArrayBuffer !== 'undefined' &&
-        typeof Uint8Array !== 'undefined' &&
-        value instanceof ArrayBuffer) {
+    if (
+      typeof ArrayBuffer !== 'undefined' &&
+      typeof Uint8Array !== 'undefined' &&
+      value instanceof ArrayBuffer
+    ) {
       return `ArrayBuffer {${String(Array.from(new Uint8Array(value)))}}`;
     }
     return value;
diff --git a/Libraries/WebSocket/__mocks__/event-target-shim.js b/Libraries/WebSocket/__mocks__/event-target-shim.js
index e6cf0571fe65..348227a374d3 100644
--- a/Libraries/WebSocket/__mocks__/event-target-shim.js
+++ b/Libraries/WebSocket/__mocks__/event-target-shim.js
@@ -1,3 +1,5 @@
+/** @format */
+
 // Jest fatals for the following statement (minimal repro case)
 //
 //   exports.something = Symbol;
diff --git a/Libraries/WebSocket/__tests__/WebSocket-test.js b/Libraries/WebSocket/__tests__/WebSocket-test.js
index a263caf3ee22..d3db6493e295 100644
--- a/Libraries/WebSocket/__tests__/WebSocket-test.js
+++ b/Libraries/WebSocket/__tests__/WebSocket-test.js
@@ -4,21 +4,22 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+react_native
  */
+
 'use strict';
 
 jest.enableAutomock().unmock('WebSocket');
 jest.setMock('NativeModules', {
   WebSocketModule: {
-    connect: () => {}
-  }
+    connect: () => {},
+  },
 });
 
 const WebSocket = require('WebSocket');
 
 describe('WebSocket', function() {
-
   it('should have connection lifecycle constants defined on the class', () => {
     expect(WebSocket.CONNECTING).toEqual(0);
   });
@@ -26,5 +27,4 @@ describe('WebSocket', function() {
   it('should have connection lifecycle constants defined on the instance', () => {
     expect(new WebSocket('wss://echo.websocket.org').CONNECTING).toEqual(0);
   });
-
 });
diff --git a/Libraries/polyfills/Array.es6.js b/Libraries/polyfills/Array.es6.js
index 252d996b919f..a4378d65df98 100644
--- a/Libraries/polyfills/Array.es6.js
+++ b/Libraries/polyfills/Array.es6.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @polyfill
  * @nolint
  */
@@ -27,9 +28,8 @@ if (!Array.from) {
 
     var C = this;
     var items = Object(arrayLike);
-    var symbolIterator = typeof Symbol === 'function'
-      ? Symbol.iterator
-      : '@@iterator';
+    var symbolIterator =
+      typeof Symbol === 'function' ? Symbol.iterator : '@@iterator';
     var mapping = typeof mapFn === 'function';
     var usingIterator = typeof items[symbolIterator] === 'function';
     var key = 0;
@@ -37,9 +37,7 @@ if (!Array.from) {
     var value;
 
     if (usingIterator) {
-      ret = typeof C === 'function'
-        ? new C()
-        : [];
+      ret = typeof C === 'function' ? new C() : [];
       var it = items[symbolIterator]();
       var next;
 
@@ -63,9 +61,7 @@ if (!Array.from) {
       len = 0;
     }
 
-    ret = typeof C === 'function'
-      ? new C(len)
-      : new Array(len);
+    ret = typeof C === 'function' ? new C(len) : new Array(len);
 
     while (key < len) {
       value = items[key];
diff --git a/Libraries/polyfills/Array.prototype.es6.js b/Libraries/polyfills/Array.prototype.es6.js
index a3c8da5415fa..d6b737522999 100644
--- a/Libraries/polyfills/Array.prototype.es6.js
+++ b/Libraries/polyfills/Array.prototype.es6.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @polyfill
  * @nolint
  */
@@ -14,7 +15,7 @@
 function findIndex(predicate, context) {
   if (this == null) {
     throw new TypeError(
-      'Array.prototype.findIndex called on null or undefined'
+      'Array.prototype.findIndex called on null or undefined',
     );
   }
   if (typeof predicate !== 'function') {
@@ -35,7 +36,7 @@ if (!Array.prototype.findIndex) {
     enumerable: false,
     writable: true,
     configurable: true,
-    value: findIndex
+    value: findIndex,
   });
 }
 
@@ -47,13 +48,11 @@ if (!Array.prototype.find) {
     configurable: true,
     value: function(predicate, context) {
       if (this == null) {
-        throw new TypeError(
-          'Array.prototype.find called on null or undefined'
-        );
+        throw new TypeError('Array.prototype.find called on null or undefined');
       }
       var index = findIndex.call(this, predicate, context);
       return index === -1 ? undefined : this[index];
-    }
+    },
   });
 }
 
@@ -63,7 +62,7 @@ if (!Array.prototype.includes) {
     enumerable: false,
     writable: true,
     configurable: true,
-    value: function (searchElement) {
+    value: function(searchElement) {
       var O = Object(this);
       var len = parseInt(O.length) || 0;
       if (len === 0) {
@@ -82,13 +81,15 @@ if (!Array.prototype.includes) {
       var currentElement;
       while (k < len) {
         currentElement = O[k];
-        if (searchElement === currentElement ||
-          (searchElement !== searchElement && currentElement !== currentElement)) {
+        if (
+          searchElement === currentElement ||
+          (searchElement !== searchElement && currentElement !== currentElement)
+        ) {
           return true;
         }
         k++;
       }
       return false;
-    }
+    },
   });
 }
diff --git a/Libraries/polyfills/Number.es6.js b/Libraries/polyfills/Number.es6.js
index b95166205be6..27987677e939 100644
--- a/Libraries/polyfills/Number.es6.js
+++ b/Libraries/polyfills/Number.es6.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @polyfill
  * @nolint
  */
diff --git a/Libraries/polyfills/Object.es6.js b/Libraries/polyfills/Object.es6.js
index 3d521e0a630d..9c45b4c24f6e 100644
--- a/Libraries/polyfills/Object.es6.js
+++ b/Libraries/polyfills/Object.es6.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @polyfill
  * @nolint
  */
@@ -20,7 +21,7 @@ Object.assign = function(target, sources) {
     if (typeof target !== 'object' && typeof target !== 'function') {
       throw new TypeError(
         'In this environment the target of assign MUST be an object. ' +
-        'This error is a performance optimization and not spec compliant.'
+          'This error is a performance optimization and not spec compliant.',
       );
     }
   }
@@ -32,11 +33,10 @@ Object.assign = function(target, sources) {
     }
 
     if (__DEV__) {
-      if (typeof nextSource !== 'object' &&
-          typeof nextSource !== 'function') {
+      if (typeof nextSource !== 'object' && typeof nextSource !== 'function') {
         throw new TypeError(
           'In this environment the sources for assign MUST be an object. ' +
-          'This error is a performance optimization and not spec compliant.'
+            'This error is a performance optimization and not spec compliant.',
         );
       }
     }
@@ -51,9 +51,9 @@ Object.assign = function(target, sources) {
         if (!hasOwnProperty.call(nextSource, key)) {
           throw new TypeError(
             'One of the sources for assign has an enumerable key on the ' +
-            'prototype chain. Are you trying to assign a prototype property? ' +
-            'We don\'t allow it, as this is an edge case that we do not support. ' +
-            'This error is a performance optimization and not spec compliant.'
+              'prototype chain. Are you trying to assign a prototype property? ' +
+              "We don't allow it, as this is an edge case that we do not support. " +
+              'This error is a performance optimization and not spec compliant.',
           );
         }
       }
diff --git a/Libraries/polyfills/Object.es7.js b/Libraries/polyfills/Object.es7.js
index a891057b9e7b..16513b3cc7bb 100644
--- a/Libraries/polyfills/Object.es7.js
+++ b/Libraries/polyfills/Object.es7.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @polyfill
  * @nolint
  */
@@ -54,5 +55,4 @@
       return values;
     };
   }
-
 })();
diff --git a/Libraries/polyfills/String.prototype.es6.js b/Libraries/polyfills/String.prototype.es6.js
index 02b33dd1e199..ac46fc873d26 100644
--- a/Libraries/polyfills/String.prototype.es6.js
+++ b/Libraries/polyfills/String.prototype.es6.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @polyfill
  * @nolint
  */
@@ -21,8 +22,7 @@ if (!String.prototype.startsWith) {
       throw TypeError();
     }
     var string = String(this);
-    var pos = arguments.length > 1 ?
-      (Number(arguments[1]) || 0) : 0;
+    var pos = arguments.length > 1 ? Number(arguments[1]) || 0 : 0;
     var start = Math.min(Math.max(pos, 0), string.length);
     return string.indexOf(String(search), pos) === start;
   };
@@ -37,8 +37,7 @@ if (!String.prototype.endsWith) {
     var string = String(this);
     var stringLength = string.length;
     var searchString = String(search);
-    var pos = arguments.length > 1 ?
-      (Number(arguments[1]) || 0) : stringLength;
+    var pos = arguments.length > 1 ? Number(arguments[1]) || 0 : stringLength;
     var end = Math.min(Math.max(pos, 0), stringLength);
     var start = end - searchString.length;
     if (start < 0) {
diff --git a/Libraries/polyfills/__tests__/Object.es7-test.js b/Libraries/polyfills/__tests__/Object.es7-test.js
index 528a479f3b6b..9fcb9e0b1704 100644
--- a/Libraries/polyfills/__tests__/Object.es7-test.js
+++ b/Libraries/polyfills/__tests__/Object.es7-test.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+jsinfra
  */
 
@@ -23,12 +24,12 @@ describe('Object (ES7)', () => {
     });
 
     it('should check for type', () => {
-      expect(Object.entries.bind(null, null)).toThrow(TypeError(
-        'Object.entries called on non-object'
-      ));
-      expect(Object.entries.bind(null, undefined)).toThrow(TypeError(
-        'Object.entries called on non-object'
-      ));
+      expect(Object.entries.bind(null, null)).toThrow(
+        TypeError('Object.entries called on non-object'),
+      );
+      expect(Object.entries.bind(null, undefined)).toThrow(
+        TypeError('Object.entries called on non-object'),
+      );
       expect(Object.entries.bind(null, [])).not.toThrow();
       expect(Object.entries.bind(null, () => {})).not.toThrow();
       expect(Object.entries.bind(null, {})).not.toThrow();
@@ -36,10 +37,13 @@ describe('Object (ES7)', () => {
     });
 
     it('should return enumerable entries', () => {
-      const foo = Object.defineProperties({}, {
-        x: {value: 10, enumerable: true},
-        y: {value: 20},
-      });
+      const foo = Object.defineProperties(
+        {},
+        {
+          x: {value: 10, enumerable: true},
+          y: {value: 20},
+        },
+      );
 
       expect(Object.entries(foo)).toEqual([['x', 10]]);
 
@@ -57,10 +61,13 @@ describe('Object (ES7)', () => {
     });
 
     it('should return only own entries', () => {
-      const foo = Object.create({z: 30}, {
-        x: {value: 10, enumerable: true},
-        y: {value: 20},
-      });
+      const foo = Object.create(
+        {z: 30},
+        {
+          x: {value: 10, enumerable: true},
+          y: {value: 20},
+        },
+      );
 
       expect(Object.entries(foo)).toEqual([['x', 10]]);
     });
@@ -76,19 +83,22 @@ describe('Object (ES7)', () => {
     });
 
     it('should check for type', () => {
-      expect(Object.values.bind(null, null)).toThrow(TypeError(
-        'Object.values called on non-object'
-      ));
+      expect(Object.values.bind(null, null)).toThrow(
+        TypeError('Object.values called on non-object'),
+      );
       expect(Object.values.bind(null, [])).not.toThrow();
       expect(Object.values.bind(null, () => {})).not.toThrow();
       expect(Object.values.bind(null, {})).not.toThrow();
     });
 
     it('should return enumerable values', () => {
-      const foo = Object.defineProperties({}, {
-        x: {value: 10, enumerable: true},
-        y: {value: 20},
-      });
+      const foo = Object.defineProperties(
+        {},
+        {
+          x: {value: 10, enumerable: true},
+          y: {value: 20},
+        },
+      );
 
       expect(Object.values(foo)).toEqual([10]);
 
@@ -106,10 +116,13 @@ describe('Object (ES7)', () => {
     });
 
     it('should return only own values', () => {
-      const foo = Object.create({z: 30}, {
-        x: {value: 10, enumerable: true},
-        y: {value: 20},
-      });
+      const foo = Object.create(
+        {z: 30},
+        {
+          x: {value: 10, enumerable: true},
+          y: {value: 20},
+        },
+      );
 
       expect(Object.values(foo)).toEqual([10]);
     });
diff --git a/Libraries/polyfills/babelHelpers.js b/Libraries/polyfills/babelHelpers.js
index 11123e0f3bc0..28c007f7633a 100644
--- a/Libraries/polyfills/babelHelpers.js
+++ b/Libraries/polyfills/babelHelpers.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @polyfill
  * @nolint
  */
@@ -18,10 +19,14 @@
 // You may need to clear wrapNativeSuper while the bug hasn't been fixed yet.
 // Do try to keep diffs to a minimum.
 
-var babelHelpers = global.babelHelpers = {};
+var babelHelpers = (global.babelHelpers = {});
 
-babelHelpers.createRawReactElement = (function () {
-  var REACT_ELEMENT_TYPE = typeof Symbol === "function" && Symbol.for && Symbol.for("react.element") || 0xeac7;
+babelHelpers.createRawReactElement = (function() {
+  var REACT_ELEMENT_TYPE =
+    (typeof Symbol === 'function' &&
+      Symbol.for &&
+      Symbol.for('react.element')) ||
+    0xeac7;
   return function createRawReactElement(type, key, props) {
     return {
       $$typeof: REACT_ELEMENT_TYPE,
@@ -29,14 +34,14 @@ babelHelpers.createRawReactElement = (function () {
       key: key,
       ref: null,
       props: props,
-      _owner: null
+      _owner: null,
     };
   };
 })();
 
-babelHelpers.classCallCheck = function (instance, Constructor) {
+babelHelpers.classCallCheck = function(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
+    throw new TypeError('Cannot call a class as a function');
   }
 };
 
@@ -45,7 +50,7 @@ function _defineProperties(target, props) {
     var descriptor = props[i];
     descriptor.enumerable = descriptor.enumerable || false;
     descriptor.configurable = true;
-    if ("value" in descriptor) descriptor.writable = true;
+    if ('value' in descriptor) descriptor.writable = true;
     Object.defineProperty(target, descriptor.key, descriptor);
   }
 }
@@ -56,13 +61,13 @@ babelHelpers.createClass = function(Constructor, protoProps, staticProps) {
   return Constructor;
 };
 
-babelHelpers.defineProperty = function (obj, key, value) {
+babelHelpers.defineProperty = function(obj, key, value) {
   if (key in obj) {
     Object.defineProperty(obj, key, {
       value: value,
       enumerable: true,
       configurable: true,
-      writable: true
+      writable: true,
     });
   } else {
     obj[key] = value;
@@ -71,19 +76,21 @@ babelHelpers.defineProperty = function (obj, key, value) {
   return obj;
 };
 
-babelHelpers._extends = babelHelpers.extends = Object.assign || function (target) {
-  for (var i = 1; i < arguments.length; i++) {
-    var source = arguments[i];
+babelHelpers._extends = babelHelpers.extends =
+  Object.assign ||
+  function(target) {
+    for (var i = 1; i < arguments.length; i++) {
+      var source = arguments[i];
 
-    for (var key in source) {
-      if (Object.prototype.hasOwnProperty.call(source, key)) {
-        target[key] = source[key];
+      for (var key in source) {
+        if (Object.prototype.hasOwnProperty.call(source, key)) {
+          target[key] = source[key];
+        }
       }
     }
-  }
 
-  return target;
-};
+    return target;
+  };
 
 babelHelpers.get = function get(object, property, receiver) {
   if (object === null) object = Function.prototype;
@@ -97,7 +104,7 @@ babelHelpers.get = function get(object, property, receiver) {
     } else {
       return get(parent, property, receiver);
     }
-  } else if ("value" in desc) {
+  } else if ('value' in desc) {
     return desc.value;
   } else {
     var getter = desc.get;
@@ -110,42 +117,55 @@ babelHelpers.get = function get(object, property, receiver) {
   }
 };
 
-babelHelpers.inherits = function (subClass, superClass) {
-  if (typeof superClass !== "function" && superClass !== null) {
-    throw new TypeError("Super expression must either be null or a function");
+babelHelpers.inherits = function(subClass, superClass) {
+  if (typeof superClass !== 'function' && superClass !== null) {
+    throw new TypeError('Super expression must either be null or a function');
   }
   subClass.prototype = Object.create(superClass && superClass.prototype, {
     constructor: {
       value: subClass,
       enumerable: false,
       writable: true,
-      configurable: true
-    }
+      configurable: true,
+    },
   });
-  if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass;
+  if (superClass)
+    Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass);
 };
 
-var _gPO = Object.getPrototypeOf || function _gPO(o) { return o.__proto__ };
-var _sPO = Object.setPrototypeOf || function _sPO(o, p) { o.__proto__ = p; return o };
+var _gPO =
+  Object.getPrototypeOf ||
+  function _gPO(o) {
+    return o.__proto__;
+  };
+var _sPO =
+  Object.setPrototypeOf ||
+  function _sPO(o, p) {
+    o.__proto__ = p;
+    return o;
+  };
 var _construct =
-// TODO: prepack does not like this line (and we can use the fallback just fine)
-// (typeof Reflect === "object" && Reflect.construct) ||
+  // TODO: prepack does not like this line (and we can use the fallback just fine)
+  // (typeof Reflect === "object" && Reflect.construct) ||
   function _construct(Parent, args, Class) {
-    var Constructor, a = [null];
+    var Constructor,
+      a = [null];
     a.push.apply(a, args);
     Constructor = Parent.bind.apply(Parent, a);
-    return _sPO(new Constructor, Class.prototype);
+    return _sPO(new Constructor(), Class.prototype);
   };
-var _cache = typeof Map === "function" && new Map();
+var _cache = typeof Map === 'function' && new Map();
 babelHelpers.wrapNativeSuper = function(Class) {
   // FB:
   // Note: while extending native classes is pretty meh we do have cases, for
   // example; Error. There is also a false positive, for example; Blob.
 
-  if (typeof Class !== "function") {
-    throw new TypeError("Super expression must either be null or a function");
+  if (typeof Class !== 'function') {
+    throw new TypeError('Super expression must either be null or a function');
   }
-  if (typeof _cache !== "undefined") {
+  if (typeof _cache !== 'undefined') {
     if (_cache.has(Class)) return _cache.get(Class);
     _cache.set(Class, Wrapper);
   }
@@ -160,26 +180,25 @@ babelHelpers.wrapNativeSuper = function(Class) {
       enumerable: false,
       writeable: true,
       configurable: true,
-    }
+    },
   });
   return _sPO(
     Wrapper,
-    _sPO(
-      function Super() {
-        return _construct(Class, arguments, _gPO(this).constructor);
-      },
-      Class
-    )
+    _sPO(function Super() {
+      return _construct(Class, arguments, _gPO(this).constructor);
+    }, Class),
   );
 };
 
-babelHelpers.interopRequireDefault = function (obj) {
-  return obj && obj.__esModule ? obj : {
-    default: obj
-  };
+babelHelpers.interopRequireDefault = function(obj) {
+  return obj && obj.__esModule
+    ? obj
+    : {
+        default: obj,
+      };
 };
 
-babelHelpers.interopRequireWildcard = function (obj) {
+babelHelpers.interopRequireWildcard = function(obj) {
   if (obj && obj.__esModule) {
     return obj;
   } else {
@@ -188,7 +207,10 @@ babelHelpers.interopRequireWildcard = function (obj) {
     if (obj != null) {
       for (var key in obj) {
         if (Object.prototype.hasOwnProperty.call(obj, key)) {
-          var desc = Object.defineProperty && Object.getOwnPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : {};
+          var desc =
+            Object.defineProperty && Object.getOwnPropertyDescriptor
+              ? Object.getOwnPropertyDescriptor(obj, key)
+              : {};
 
           if (desc.get || desc.set) {
             Object.defineProperty(newObj, key, desc);
@@ -230,13 +252,15 @@ babelHelpers.objectWithoutProperties = function(source, excluded) {
   return target;
 };
 
-babelHelpers.possibleConstructorReturn = function (self, call) {
-  if (call && (typeof call === "object" || typeof call === "function")) {
+babelHelpers.possibleConstructorReturn = function(self, call) {
+  if (call && (typeof call === 'object' || typeof call === 'function')) {
     return call;
   }
 
   if (self === void 0) {
-    throw new ReferenceError("this hasn't been initialised - super() hasn't been called");
+    throw new ReferenceError(
+      "this hasn't been initialised - super() hasn't been called",
+    );
   }
 
   return self;
@@ -249,7 +273,11 @@ function _sliceIterator(arr, i) {
   var _e = undefined;
 
   try {
-    for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
+    for (
+      var _i = arr[Symbol.iterator](), _s;
+      !(_n = (_s = _i.next()).done);
+      _n = true
+    ) {
       _arr.push(_s.value);
 
       if (i && _arr.length === i) break;
@@ -259,7 +287,7 @@ function _sliceIterator(arr, i) {
     _e = err;
   } finally {
     try {
-      if (!_n && _i["return"] != null) _i["return"]();
+      if (!_n && _i['return'] != null) _i['return']();
     } finally {
       if (_d) throw _e;
     }
@@ -274,25 +302,28 @@ babelHelpers.slicedToArray = function(arr, i) {
   } else if (Symbol.iterator in Object(arr)) {
     return _sliceIterator(arr, i);
   } else {
-    throw new TypeError("Invalid attempt to destructure non-iterable instance");
+    throw new TypeError('Invalid attempt to destructure non-iterable instance');
   }
 };
 
-babelHelpers.taggedTemplateLiteral = function (strings, raw) {
-  return Object.freeze(Object.defineProperties(strings, {
-    raw: {
-      value: Object.freeze(raw)
-    }
-  }));
+babelHelpers.taggedTemplateLiteral = function(strings, raw) {
+  return Object.freeze(
+    Object.defineProperties(strings, {
+      raw: {
+        value: Object.freeze(raw),
+      },
+    }),
+  );
 };
 
-babelHelpers.toArray = function (arr) {
+babelHelpers.toArray = function(arr) {
   return Array.isArray(arr) ? arr : Array.from(arr);
 };
 
-babelHelpers.toConsumableArray = function (arr) {
+babelHelpers.toConsumableArray = function(arr) {
   if (Array.isArray(arr)) {
-    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) arr2[i] = arr[i];
+    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++)
+      arr2[i] = arr[i];
 
     return arr2;
   } else {
diff --git a/Libraries/polyfills/error-guard.js b/Libraries/polyfills/error-guard.js
index 17181d102192..6a23071f2afc 100644
--- a/Libraries/polyfills/error-guard.js
+++ b/Libraries/polyfills/error-guard.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @polyfill
  * @nolint
  */
@@ -69,14 +70,12 @@ const ErrorUtils = {
     }
     name = name || fun.name || '<generated guard>';
     function guarded() {
-      return (
-        ErrorUtils.applyWithGuard(
-          fun,
-          context || this,
-          arguments,
-          null,
-          name
-        )
+      return ErrorUtils.applyWithGuard(
+        fun,
+        context || this,
+        arguments,
+        null,
+        name,
       );
     }
 
diff --git a/Libraries/promiseRejectionIsError.js b/Libraries/promiseRejectionIsError.js
index 672949116911..1ee0320a214e 100644
--- a/Libraries/promiseRejectionIsError.js
+++ b/Libraries/promiseRejectionIsError.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 require('Promise'); // make sure the default rejection handler is installed
diff --git a/Libraries/react-native/React.js b/Libraries/react-native/React.js
index ff4c2454459f..37ee103b456a 100644
--- a/Libraries/react-native/React.js
+++ b/Libraries/react-native/React.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
diff --git a/Libraries/react-native/react-native-implementation.js b/Libraries/react-native/react-native-implementation.js
index 5a6f9759e8ce..3ff7b9ed3b49 100644
--- a/Libraries/react-native/react-native-implementation.js
+++ b/Libraries/react-native/react-native-implementation.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const invariant = require('fbjs/lib/invariant');
@@ -13,118 +15,314 @@ const invariant = require('fbjs/lib/invariant');
 // Export React, plus some native additions.
 const ReactNative = {
   // Components
-  get AccessibilityInfo() { return require('AccessibilityInfo'); },
-  get ActivityIndicator() { return require('ActivityIndicator'); },
-  get ART() { return require('ReactNativeART'); },
-  get Button() { return require('Button'); },
-  get CheckBox() { return require('CheckBox'); },
-  get DatePickerIOS() { return require('DatePickerIOS'); },
-  get DrawerLayoutAndroid() { return require('DrawerLayoutAndroid'); },
-  get FlatList() { return require('FlatList'); },
-  get Image() { return require('Image'); },
-  get ImageBackground() { return require('ImageBackground'); },
-  get ImageEditor() { return require('ImageEditor'); },
-  get ImageStore() { return require('ImageStore'); },
-  get InputAccessoryView() { return require('InputAccessoryView') },
-  get KeyboardAvoidingView() { return require('KeyboardAvoidingView'); },
-  get ListView() { return require('ListView'); },
-  get MaskedViewIOS() { return require('MaskedViewIOS'); },
-  get Modal() { return require('Modal'); },
-  get NavigatorIOS() { return require('NavigatorIOS'); },
-  get Picker() { return require('Picker'); },
-  get PickerIOS() { return require('PickerIOS'); },
-  get ProgressBarAndroid() { return require('ProgressBarAndroid'); },
-  get ProgressViewIOS() { return require('ProgressViewIOS'); },
-  get SafeAreaView() { return require('SafeAreaView'); },
-  get ScrollView() { return require('ScrollView'); },
-  get SectionList() { return require('SectionList'); },
-  get SegmentedControlIOS() { return require('SegmentedControlIOS'); },
-  get Slider() { return require('Slider'); },
-  get SnapshotViewIOS() { return require('SnapshotViewIOS'); },
-  get Switch() { return require('Switch'); },
-  get RefreshControl() { return require('RefreshControl'); },
-  get StatusBar() { return require('StatusBar'); },
-  get SwipeableFlatList() { return require('SwipeableFlatList'); },
-  get SwipeableListView() { return require('SwipeableListView'); },
-  get TabBarIOS() { return require('TabBarIOS'); },
-  get Text() { return require('Text'); },
-  get TextInput() { return require('TextInput'); },
-  get ToastAndroid() { return require('ToastAndroid'); },
-  get ToolbarAndroid() { return require('ToolbarAndroid'); },
-  get Touchable() { return require('Touchable'); },
-  get TouchableHighlight() { return require('TouchableHighlight'); },
-  get TouchableNativeFeedback() { return require('TouchableNativeFeedback'); },
-  get TouchableOpacity() { return require('TouchableOpacity'); },
-  get TouchableWithoutFeedback() { return require('TouchableWithoutFeedback'); },
-  get View() { return require('View'); },
-  get ViewPagerAndroid() { return require('ViewPagerAndroid'); },
-  get VirtualizedList() { return require('VirtualizedList'); },
-  get WebView() { return require('WebView'); },
+  get AccessibilityInfo() {
+    return require('AccessibilityInfo');
+  },
+  get ActivityIndicator() {
+    return require('ActivityIndicator');
+  },
+  get ART() {
+    return require('ReactNativeART');
+  },
+  get Button() {
+    return require('Button');
+  },
+  get CheckBox() {
+    return require('CheckBox');
+  },
+  get DatePickerIOS() {
+    return require('DatePickerIOS');
+  },
+  get DrawerLayoutAndroid() {
+    return require('DrawerLayoutAndroid');
+  },
+  get FlatList() {
+    return require('FlatList');
+  },
+  get Image() {
+    return require('Image');
+  },
+  get ImageBackground() {
+    return require('ImageBackground');
+  },
+  get ImageEditor() {
+    return require('ImageEditor');
+  },
+  get ImageStore() {
+    return require('ImageStore');
+  },
+  get InputAccessoryView() {
+    return require('InputAccessoryView');
+  },
+  get KeyboardAvoidingView() {
+    return require('KeyboardAvoidingView');
+  },
+  get ListView() {
+    return require('ListView');
+  },
+  get MaskedViewIOS() {
+    return require('MaskedViewIOS');
+  },
+  get Modal() {
+    return require('Modal');
+  },
+  get NavigatorIOS() {
+    return require('NavigatorIOS');
+  },
+  get Picker() {
+    return require('Picker');
+  },
+  get PickerIOS() {
+    return require('PickerIOS');
+  },
+  get ProgressBarAndroid() {
+    return require('ProgressBarAndroid');
+  },
+  get ProgressViewIOS() {
+    return require('ProgressViewIOS');
+  },
+  get SafeAreaView() {
+    return require('SafeAreaView');
+  },
+  get ScrollView() {
+    return require('ScrollView');
+  },
+  get SectionList() {
+    return require('SectionList');
+  },
+  get SegmentedControlIOS() {
+    return require('SegmentedControlIOS');
+  },
+  get Slider() {
+    return require('Slider');
+  },
+  get SnapshotViewIOS() {
+    return require('SnapshotViewIOS');
+  },
+  get Switch() {
+    return require('Switch');
+  },
+  get RefreshControl() {
+    return require('RefreshControl');
+  },
+  get StatusBar() {
+    return require('StatusBar');
+  },
+  get SwipeableFlatList() {
+    return require('SwipeableFlatList');
+  },
+  get SwipeableListView() {
+    return require('SwipeableListView');
+  },
+  get TabBarIOS() {
+    return require('TabBarIOS');
+  },
+  get Text() {
+    return require('Text');
+  },
+  get TextInput() {
+    return require('TextInput');
+  },
+  get ToastAndroid() {
+    return require('ToastAndroid');
+  },
+  get ToolbarAndroid() {
+    return require('ToolbarAndroid');
+  },
+  get Touchable() {
+    return require('Touchable');
+  },
+  get TouchableHighlight() {
+    return require('TouchableHighlight');
+  },
+  get TouchableNativeFeedback() {
+    return require('TouchableNativeFeedback');
+  },
+  get TouchableOpacity() {
+    return require('TouchableOpacity');
+  },
+  get TouchableWithoutFeedback() {
+    return require('TouchableWithoutFeedback');
+  },
+  get View() {
+    return require('View');
+  },
+  get ViewPagerAndroid() {
+    return require('ViewPagerAndroid');
+  },
+  get VirtualizedList() {
+    return require('VirtualizedList');
+  },
+  get WebView() {
+    return require('WebView');
+  },
 
   // APIs
-  get ActionSheetIOS() { return require('ActionSheetIOS'); },
-  get Alert() { return require('Alert'); },
-  get AlertIOS() { return require('AlertIOS'); },
-  get Animated() { return require('Animated'); },
-  get AppRegistry() { return require('AppRegistry'); },
-  get AppState() { return require('AppState'); },
-  get AsyncStorage() { return require('AsyncStorage'); },
-  get BackAndroid() { return require('BackAndroid'); }, // deprecated: use BackHandler instead
-  get BackHandler() { return require('BackHandler'); },
-  get CameraRoll() { return require('CameraRoll'); },
-  get Clipboard() { return require('Clipboard'); },
-  get DatePickerAndroid() { return require('DatePickerAndroid'); },
-  get DeviceInfo() { return require('DeviceInfo'); },
-  get Dimensions() { return require('Dimensions'); },
-  get Easing() { return require('Easing'); },
-  get findNodeHandle() { return require('ReactNative').findNodeHandle; },
-  get I18nManager() { return require('I18nManager'); },
-  get ImagePickerIOS() { return require('ImagePickerIOS'); },
-  get InteractionManager() { return require('InteractionManager'); },
-  get Keyboard() { return require('Keyboard'); },
-  get LayoutAnimation() { return require('LayoutAnimation'); },
-  get Linking() { return require('Linking'); },
-  get NativeEventEmitter() { return require('NativeEventEmitter'); },
-  get NetInfo() { return require('NetInfo'); },
-  get PanResponder() { return require('PanResponder'); },
-  get PermissionsAndroid() { return require('PermissionsAndroid'); },
-  get PixelRatio() { return require('PixelRatio'); },
-  get PushNotificationIOS() { return require('PushNotificationIOS'); },
-  get Settings() { return require('Settings'); },
-  get Share() { return require('Share'); },
-  get StatusBarIOS() { return require('StatusBarIOS'); },
-  get StyleSheet() { return require('StyleSheet'); },
-  get Systrace() { return require('Systrace'); },
-  get TimePickerAndroid() { return require('TimePickerAndroid'); },
-  get TVEventHandler() { return require('TVEventHandler'); },
-  get UIManager() { return require('UIManager'); },
-  get unstable_batchedUpdates() { return require('ReactNative').unstable_batchedUpdates; },
-  get Vibration() { return require('Vibration'); },
-  get VibrationIOS() { return require('VibrationIOS'); },
-  get YellowBox() { return require('YellowBox'); },
+  get ActionSheetIOS() {
+    return require('ActionSheetIOS');
+  },
+  get Alert() {
+    return require('Alert');
+  },
+  get AlertIOS() {
+    return require('AlertIOS');
+  },
+  get Animated() {
+    return require('Animated');
+  },
+  get AppRegistry() {
+    return require('AppRegistry');
+  },
+  get AppState() {
+    return require('AppState');
+  },
+  get AsyncStorage() {
+    return require('AsyncStorage');
+  },
+  get BackAndroid() {
+    return require('BackAndroid');
+  }, // deprecated: use BackHandler instead
+  get BackHandler() {
+    return require('BackHandler');
+  },
+  get CameraRoll() {
+    return require('CameraRoll');
+  },
+  get Clipboard() {
+    return require('Clipboard');
+  },
+  get DatePickerAndroid() {
+    return require('DatePickerAndroid');
+  },
+  get DeviceInfo() {
+    return require('DeviceInfo');
+  },
+  get Dimensions() {
+    return require('Dimensions');
+  },
+  get Easing() {
+    return require('Easing');
+  },
+  get findNodeHandle() {
+    return require('ReactNative').findNodeHandle;
+  },
+  get I18nManager() {
+    return require('I18nManager');
+  },
+  get ImagePickerIOS() {
+    return require('ImagePickerIOS');
+  },
+  get InteractionManager() {
+    return require('InteractionManager');
+  },
+  get Keyboard() {
+    return require('Keyboard');
+  },
+  get LayoutAnimation() {
+    return require('LayoutAnimation');
+  },
+  get Linking() {
+    return require('Linking');
+  },
+  get NativeEventEmitter() {
+    return require('NativeEventEmitter');
+  },
+  get NetInfo() {
+    return require('NetInfo');
+  },
+  get PanResponder() {
+    return require('PanResponder');
+  },
+  get PermissionsAndroid() {
+    return require('PermissionsAndroid');
+  },
+  get PixelRatio() {
+    return require('PixelRatio');
+  },
+  get PushNotificationIOS() {
+    return require('PushNotificationIOS');
+  },
+  get Settings() {
+    return require('Settings');
+  },
+  get Share() {
+    return require('Share');
+  },
+  get StatusBarIOS() {
+    return require('StatusBarIOS');
+  },
+  get StyleSheet() {
+    return require('StyleSheet');
+  },
+  get Systrace() {
+    return require('Systrace');
+  },
+  get TimePickerAndroid() {
+    return require('TimePickerAndroid');
+  },
+  get TVEventHandler() {
+    return require('TVEventHandler');
+  },
+  get UIManager() {
+    return require('UIManager');
+  },
+  get unstable_batchedUpdates() {
+    return require('ReactNative').unstable_batchedUpdates;
+  },
+  get Vibration() {
+    return require('Vibration');
+  },
+  get VibrationIOS() {
+    return require('VibrationIOS');
+  },
+  get YellowBox() {
+    return require('YellowBox');
+  },
 
   // Plugins
-  get DeviceEventEmitter() { return require('RCTDeviceEventEmitter'); },
-  get NativeAppEventEmitter() { return require('RCTNativeAppEventEmitter'); },
-  get NativeModules() { return require('NativeModules'); },
-  get Platform() { return require('Platform'); },
-  get processColor() { return require('processColor'); },
-  get requireNativeComponent() { return require('requireNativeComponent'); },
-  get takeSnapshot() { return require('takeSnapshot'); },
+  get DeviceEventEmitter() {
+    return require('RCTDeviceEventEmitter');
+  },
+  get NativeAppEventEmitter() {
+    return require('RCTNativeAppEventEmitter');
+  },
+  get NativeModules() {
+    return require('NativeModules');
+  },
+  get Platform() {
+    return require('Platform');
+  },
+  get processColor() {
+    return require('processColor');
+  },
+  get requireNativeComponent() {
+    return require('requireNativeComponent');
+  },
+  get takeSnapshot() {
+    return require('takeSnapshot');
+  },
 
   // Prop Types
-  get ColorPropType() { return require('ColorPropType'); },
-  get EdgeInsetsPropType() { return require('EdgeInsetsPropType'); },
-  get PointPropType() { return require('PointPropType'); },
-  get ViewPropTypes() { return require('ViewPropTypes'); },
+  get ColorPropType() {
+    return require('ColorPropType');
+  },
+  get EdgeInsetsPropType() {
+    return require('EdgeInsetsPropType');
+  },
+  get PointPropType() {
+    return require('PointPropType');
+  },
+  get ViewPropTypes() {
+    return require('ViewPropTypes');
+  },
 
   // Deprecated
   get Navigator() {
     invariant(
       false,
       'Navigator is deprecated and has been removed from this package. It can now be installed ' +
-      'and imported from `react-native-deprecated-custom-components` instead of `react-native`. ' +
-      'Learn about alternative navigation solutions at http://facebook.github.io/react-native/docs/navigation.html'
+        'and imported from `react-native-deprecated-custom-components` instead of `react-native`. ' +
+        'Learn about alternative navigation solutions at http://facebook.github.io/react-native/docs/navigation.html',
     );
   },
 };
diff --git a/Libraries/react-native/react-native-interface.js b/Libraries/react-native/react-native-interface.js
index 5f2cdf2c1cf6..23fa37cdab9e 100644
--- a/Libraries/react-native/react-native-interface.js
+++ b/Libraries/react-native/react-native-interface.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // see also react-native.js
diff --git a/Libraries/vendor/core/ErrorUtils.js b/Libraries/vendor/core/ErrorUtils.js
index 2fb0272d347a..f64b7fdb17f5 100644
--- a/Libraries/vendor/core/ErrorUtils.js
+++ b/Libraries/vendor/core/ErrorUtils.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/Libraries/vendor/core/Map.js b/Libraries/vendor/core/Map.js
index 575a6b1d57c0..163508349688 100644
--- a/Libraries/vendor/core/Map.js
+++ b/Libraries/vendor/core/Map.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @preventMunge
  * @typechecks
  */
@@ -100,7 +101,6 @@ module.exports = (function(global, undefined) {
   const OLD_IE_HASH_PREFIX = 'IE_HASH_';
 
   class Map {
-
     /**
      * 23.1.1.1
      * Takes an `iterable` which is basically any object that implements a
@@ -163,10 +163,7 @@ module.exports = (function(global, undefined) {
       if (index != null && this._mapData[index]) {
         this._mapData[index][1] = value;
       } else {
-        index = this._mapData.push([
-          key,
-          value
-        ]) - 1;
+        index = this._mapData.push([key, value]) - 1;
         setIndex(this, key, index);
         if (__DEV__) {
           this[SECRET_SIZE_PROP] += 1;
@@ -194,7 +191,6 @@ module.exports = (function(global, undefined) {
       }
     }
 
-
     /**
      * 23.1.3.3
      * Delete a key/value from the collection.
@@ -282,7 +278,6 @@ module.exports = (function(global, undefined) {
   Map.prototype[toIterator.ITERATOR_SYMBOL] = Map.prototype.entries;
 
   class MapIterator {
-
     /**
      * 23.1.5.1
      * Create a `MapIterator` for a given `map`. While this class is private it
@@ -459,17 +454,17 @@ module.exports = (function(global, undefined) {
         } else {
           Object.defineProperty(map, SECRET_SIZE_PROP, {
             value: 0,
-            writable: true
+            writable: true,
           });
           Object.defineProperty(map, 'size', {
-            set: (v) => {
+            set: v => {
               console.error(
                 'PLEASE FIX ME: You are changing the map size property which ' +
-                'should not be writable and will break in production.'
+                  'should not be writable and will break in production.',
               );
               throw new Error('The map size property is not writable.');
             },
-            get: () => map[SECRET_SIZE_PROP]
+            get: () => map[SECRET_SIZE_PROP],
           });
         }
 
@@ -550,7 +545,7 @@ module.exports = (function(global, undefined) {
     }
 
     if (uniqueID) {
-      return  OLD_IE_HASH_PREFIX + uniqueID;
+      return OLD_IE_HASH_PREFIX + uniqueID;
     } else {
       return null;
     }
@@ -567,16 +562,17 @@ module.exports = (function(global, undefined) {
      * @param {object|array|function|regexp} o
      * @return {number}
      */
-    return function getHash(o) { // eslint-disable-line no-shadow
+    return function getHash(o) {
+      // eslint-disable-line no-shadow
       if (o[hashProperty]) {
         return o[hashProperty];
-      } else if (!isES5 &&
-                  o.propertyIsEnumerable &&
-                  o.propertyIsEnumerable[hashProperty]) {
+      } else if (
+        !isES5 &&
+        o.propertyIsEnumerable &&
+        o.propertyIsEnumerable[hashProperty]
+      ) {
         return o.propertyIsEnumerable[hashProperty];
-      } else if (!isES5 &&
-                  isNode(o) &&
-                  getIENodeHash(o)) {
+      } else if (!isES5 && isNode(o) && getIENodeHash(o)) {
         return getIENodeHash(o);
       } else if (!isES5 && o[hashProperty]) {
         return o[hashProperty];
@@ -589,7 +585,7 @@ module.exports = (function(global, undefined) {
             enumerable: false,
             writable: false,
             configurable: false,
-            value: hashCounter
+            value: hashCounter,
           });
         } else if (o.propertyIsEnumerable) {
           // Since we can't define a non-enumerable property on the object
diff --git a/Libraries/vendor/core/Set.js b/Libraries/vendor/core/Set.js
index 3ba61c26a993..d811240a3ac6 100644
--- a/Libraries/vendor/core/Set.js
+++ b/Libraries/vendor/core/Set.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @preventMunge
  * @typechecks
  */
@@ -69,7 +70,6 @@ module.exports = (function(global) {
    */
 
   class Set {
-
     /**
      * 23.2.1.1
      *
@@ -80,8 +80,10 @@ module.exports = (function(global) {
      * @param {*} iterable
      */
     constructor(iterable) {
-      if (this == null ||
-          (typeof this !== 'object' && typeof this !== 'function')) {
+      if (
+        this == null ||
+        (typeof this !== 'object' && typeof this !== 'function')
+      ) {
         throw new TypeError('Wrong set object type.');
       }
 
diff --git a/Libraries/vendor/core/_shouldPolyfillES6Collection.js b/Libraries/vendor/core/_shouldPolyfillES6Collection.js
index 576d1eb67103..4993fa38b435 100644
--- a/Libraries/vendor/core/_shouldPolyfillES6Collection.js
+++ b/Libraries/vendor/core/_shouldPolyfillES6Collection.js
@@ -4,9 +4,11 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @preventMunge
  * @flow
  */
+
 'use strict';
 
 /**
@@ -32,31 +34,33 @@ function _shouldActuallyPolyfillES6Collection(collectionName: string): boolean {
   // These checks are adapted from es6-shim: https://fburl.com/34437854
   // NOTE: `isCallableWithoutNew` and `!supportsSubclassing` are not checked
   // because they make debugging with "break on exceptions" difficult.
-  return Collection == null ||
+  return (
+    Collection == null ||
     typeof Collection !== 'function' ||
     typeof proto.clear !== 'function' ||
     new Collection().size !== 0 ||
     typeof proto.keys !== 'function' ||
-    typeof proto.forEach !== 'function';
+    typeof proto.forEach !== 'function'
+  );
 }
 
-const cache: { [name: string]: bool } = {};
+const cache: {[name: string]: boolean} = {};
 
-  /**
-   * Checks whether a collection name (e.g. "Map" or "Set") has a native polyfill
-   * that is safe to be used and caches this result.
-   * Make sure to make a first call to this function before a corresponding
-   * property on global was overriden in any way.
-   */
+/**
+ * Checks whether a collection name (e.g. "Map" or "Set") has a native polyfill
+ * that is safe to be used and caches this result.
+ * Make sure to make a first call to this function before a corresponding
+ * property on global was overriden in any way.
+ */
 function _shouldPolyfillES6Collection(collectionName: string) {
-    let result = cache[collectionName];
-    if (result !== undefined) {
-      return result;
-    }
-
-    result = _shouldActuallyPolyfillES6Collection(collectionName);
-    cache[collectionName] = result;
+  let result = cache[collectionName];
+  if (result !== undefined) {
     return result;
+  }
+
+  result = _shouldActuallyPolyfillES6Collection(collectionName);
+  cache[collectionName] = result;
+  return result;
 }
 
 module.exports = _shouldPolyfillES6Collection;
diff --git a/Libraries/vendor/core/getObjectValues.js b/Libraries/vendor/core/getObjectValues.js
index 0a020af5169c..79f61f8aa041 100644
--- a/Libraries/vendor/core/getObjectValues.js
+++ b/Libraries/vendor/core/getObjectValues.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @typechecks
  */
+
 'use strict';
 
 /**
diff --git a/Libraries/vendor/core/guid.js b/Libraries/vendor/core/guid.js
index b6195ef6b691..f2946e397357 100644
--- a/Libraries/vendor/core/guid.js
+++ b/Libraries/vendor/core/guid.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 /* eslint-disable no-bitwise */
diff --git a/Libraries/vendor/core/isEmpty.js b/Libraries/vendor/core/isEmpty.js
index c7747c980a56..f8b4eb2c96b0 100644
--- a/Libraries/vendor/core/isEmpty.js
+++ b/Libraries/vendor/core/isEmpty.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 /**
diff --git a/Libraries/vendor/core/mergeHelpers.js b/Libraries/vendor/core/mergeHelpers.js
index 10072ed46335..4382cd771aa9 100644
--- a/Libraries/vendor/core/mergeHelpers.js
+++ b/Libraries/vendor/core/mergeHelpers.js
@@ -6,6 +6,8 @@
  *
  *
  * requiresPolyfills: Array.isArray
+ *
+ * @format
  */
 
 'use strict';
@@ -29,7 +31,6 @@ const isTerminal = function(o) {
 };
 
 const mergeHelpers = {
-
   MAX_MERGE_DEPTH: MAX_MERGE_DEPTH,
 
   isTerminal: isTerminal,
@@ -57,7 +58,7 @@ const mergeHelpers = {
       Array.isArray(one) && Array.isArray(two),
       'Tried to merge arrays, instead got %s and %s.',
       one,
-      two
+      two,
     );
   },
 
@@ -77,7 +78,7 @@ const mergeHelpers = {
     invariant(
       !isTerminal(arg) && !Array.isArray(arg),
       'Tried to merge an object, instead got %s.',
-      arg
+      arg,
     );
   },
 
@@ -88,7 +89,7 @@ const mergeHelpers = {
     invariant(
       (!isTerminal(arg) || typeof arg === 'function') && !Array.isArray(arg),
       'Tried to merge into an object, instead got %s.',
-      arg
+      arg,
     );
   },
 
@@ -102,7 +103,7 @@ const mergeHelpers = {
     invariant(
       level < MAX_MERGE_DEPTH,
       'Maximum deep merge depth exceeded. You may be attempting to merge ' +
-      'circular structures in an unsupported way.'
+        'circular structures in an unsupported way.',
     );
   },
 
@@ -115,7 +116,7 @@ const mergeHelpers = {
     invariant(
       strategy === undefined || strategy in mergeHelpers.ArrayStrategies,
       'You must provide an array strategy to deep merge functions to ' +
-      'instruct the deep merge how to resolve merging two arrays.'
+        'instruct the deep merge how to resolve merging two arrays.',
     );
   },
 
@@ -131,7 +132,6 @@ const mergeHelpers = {
     Concat: 'Concat',
     IndexByIndex: 'IndexByIndex',
   },
-
 };
 
 module.exports = mergeHelpers;
diff --git a/Libraries/vendor/core/toIterator.js b/Libraries/vendor/core/toIterator.js
index 728b68c7bda9..eee68d4706e9 100644
--- a/Libraries/vendor/core/toIterator.js
+++ b/Libraries/vendor/core/toIterator.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 /**
@@ -21,13 +23,13 @@ const KIND_KEY = 'key';
 const KIND_VALUE = 'value';
 const KIND_KEY_VAL = 'key+value';
 /*global Symbol: true*/
-const ITERATOR_SYMBOL = (typeof Symbol === 'function')
-    ? Symbol.iterator
-    : '@@iterator';
+const ITERATOR_SYMBOL =
+  typeof Symbol === 'function' ? Symbol.iterator : '@@iterator';
 
 const toIterator = (function() {
-  if (!(Array.prototype[ITERATOR_SYMBOL] &&
-        String.prototype[ITERATOR_SYMBOL])) {
+  if (
+    !(Array.prototype[ITERATOR_SYMBOL] && String.prototype[ITERATOR_SYMBOL])
+  ) {
     // IIFE to avoid creating classes for no reason because of hoisting.
     return (function() {
       class ArrayIterator {
@@ -110,11 +112,11 @@ const toIterator = (function() {
           let ret;
           const first = s.charCodeAt(index);
 
-          if (first < 0xD800 || first > 0xDBFF || index + 1 === len) {
+          if (first < 0xd800 || first > 0xdbff || index + 1 === len) {
             ret = s[index];
           } else {
             const second = s.charCodeAt(index + 1);
-            if (second < 0xDC00 || second > 0xDFFF) {
+            if (second < 0xdc00 || second > 0xdfff) {
               ret = s[index];
             } else {
               ret = s[index] + s[index + 1];
@@ -162,7 +164,7 @@ Object.assign(toIterator, {
   KIND_KEY,
   KIND_VALUE,
   KIND_KEY_VAL,
-  ITERATOR_SYMBOL
+  ITERATOR_SYMBOL,
 });
 
 module.exports = toIterator;
diff --git a/Libraries/vendor/document/selection/DocumentSelectionState.js b/Libraries/vendor/document/selection/DocumentSelectionState.js
index 350732776f72..8ac05f6a1b17 100644
--- a/Libraries/vendor/document/selection/DocumentSelectionState.js
+++ b/Libraries/vendor/document/selection/DocumentSelectionState.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @typechecks
  */
 
@@ -55,7 +56,7 @@ class DocumentSelectionState {
   constrainLength(maxLength) {
     this.update(
       Math.min(this._anchorOffset, maxLength),
-      Math.min(this._focusOffset, maxLength)
+      Math.min(this._focusOffset, maxLength),
     );
   }
 
@@ -112,18 +113,18 @@ class DocumentSelectionState {
    * @return {?number}
    */
   getStartOffset() {
-    return (
-      this._hasFocus ? Math.min(this._anchorOffset, this._focusOffset) : null
-    );
+    return this._hasFocus
+      ? Math.min(this._anchorOffset, this._focusOffset)
+      : null;
   }
 
   /**
    * @return {?number}
    */
   getEndOffset() {
-    return (
-      this._hasFocus ? Math.max(this._anchorOffset, this._focusOffset) : null
-    );
+    return this._hasFocus
+      ? Math.max(this._anchorOffset, this._focusOffset)
+      : null;
   }
 
   /**
@@ -134,15 +135,16 @@ class DocumentSelectionState {
   overlaps(start, end) {
     return (
       this.hasFocus() &&
-      this.getStartOffset() <= end && start <= this.getEndOffset()
+      this.getStartOffset() <= end &&
+      start <= this.getEndOffset()
     );
   }
 }
 
 mixInEventEmitter(DocumentSelectionState, {
-  'blur': true,
-  'focus': true,
-  'update': true
+  blur: true,
+  focus: true,
+  update: true,
 });
 
 module.exports = DocumentSelectionState;
diff --git a/Libraries/vendor/emitter/EmitterSubscription.js b/Libraries/vendor/emitter/EmitterSubscription.js
index 844c28e386c8..cb372a956bee 100644
--- a/Libraries/vendor/emitter/EmitterSubscription.js
+++ b/Libraries/vendor/emitter/EmitterSubscription.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EventSubscription = require('EventSubscription');
@@ -17,7 +19,6 @@ import type EventSubscriptionVendor from 'EventSubscriptionVendor';
  * EmitterSubscription represents a subscription with listener and context data.
  */
 class EmitterSubscription extends EventSubscription {
-
   emitter: EventEmitter;
   listener: Function;
   context: ?Object;
@@ -36,7 +37,7 @@ class EmitterSubscription extends EventSubscription {
     emitter: EventEmitter,
     subscriber: EventSubscriptionVendor,
     listener: Function,
-    context: ?Object
+    context: ?Object,
   ) {
     super(subscriber);
     this.emitter = emitter;
diff --git a/Libraries/vendor/emitter/EventEmitter.js b/Libraries/vendor/emitter/EventEmitter.js
index 4b9307e49292..7cb35611f358 100644
--- a/Libraries/vendor/emitter/EventEmitter.js
+++ b/Libraries/vendor/emitter/EventEmitter.js
@@ -4,9 +4,11 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @noflow
  * @typecheck
  */
+
 'use strict';
 
 const EmitterSubscription = require('EmitterSubscription');
@@ -29,7 +31,6 @@ const invariant = require('fbjs/lib/invariant');
  * more advanced emitter may use an EventHolder and EventFactory.
  */
 class EventEmitter {
-
   _subscriber: EventSubscriptionVendor;
   _currentSubscription: ?EmitterSubscription;
 
@@ -58,12 +59,14 @@ class EventEmitter {
    *   listener
    */
   addListener(
-    eventType: string, listener: Function, context: ?Object): EmitterSubscription {
-
+    eventType: string,
+    listener: Function,
+    context: ?Object,
+  ): EmitterSubscription {
     return (this._subscriber.addSubscription(
       eventType,
-      new EmitterSubscription(this, this._subscriber, listener, context)
-    ) : any);
+      new EmitterSubscription(this, this._subscriber, listener, context),
+    ): any);
   }
 
   /**
@@ -76,7 +79,11 @@ class EventEmitter {
    * @param {*} context - Optional context object to use when invoking the
    *   listener
    */
-  once(eventType: string, listener: Function, context: ?Object): EmitterSubscription {
+  once(
+    eventType: string,
+    listener: Function,
+    context: ?Object,
+  ): EmitterSubscription {
     return this.addListener(eventType, (...args) => {
       this.removeCurrentListener();
       listener.apply(context, args);
@@ -118,7 +125,7 @@ class EventEmitter {
   removeCurrentListener() {
     invariant(
       !!this._currentSubscription,
-      'Not in an emitting cycle; there is no current subscription'
+      'Not in an emitting cycle; there is no current subscription',
     );
     this.removeSubscription(this._currentSubscription);
   }
@@ -130,7 +137,7 @@ class EventEmitter {
   removeSubscription(subscription: EmitterSubscription) {
     invariant(
       subscription.emitter === this,
-      'Subscription does not belong to this emitter.'
+      'Subscription does not belong to this emitter.',
     );
     this._subscriber.removeSubscription(subscription);
   }
@@ -143,10 +150,13 @@ class EventEmitter {
    * @returns {array}
    */
   listeners(eventType: string): [EmitterSubscription] {
-    const subscriptions: ?[EmitterSubscription] = (this._subscriber.getSubscriptionsForType(eventType): any);
+    const subscriptions: ?[
+      EmitterSubscription,
+    ] = (this._subscriber.getSubscriptionsForType(eventType): any);
     return subscriptions
-      ? subscriptions.filter(emptyFunction.thatReturnsTrue).map(
-          function(subscription) {
+      ? subscriptions
+          .filter(emptyFunction.thatReturnsTrue)
+          .map(function(subscription) {
             return subscription.listener;
           })
       : [];
@@ -167,7 +177,9 @@ class EventEmitter {
    *   emitter.emit('someEvent', 'abc'); // logs 'abc'
    */
   emit(eventType: string) {
-    const subscriptions: ?[EmitterSubscription] = (this._subscriber.getSubscriptionsForType(eventType): any);
+    const subscriptions: ?[
+      EmitterSubscription,
+    ] = (this._subscriber.getSubscriptionsForType(eventType): any);
     if (subscriptions) {
       for (let i = 0, l = subscriptions.length; i < l; i++) {
         const subscription = subscriptions[i];
@@ -177,7 +189,7 @@ class EventEmitter {
           this._currentSubscription = subscription;
           subscription.listener.apply(
             subscription.context,
-            Array.prototype.slice.call(arguments, 1)
+            Array.prototype.slice.call(arguments, 1),
           );
         }
       }
@@ -199,7 +211,9 @@ class EventEmitter {
    *
    */
   removeListener(eventType: String, listener) {
-    const subscriptions: ?[EmitterSubscription] = (this._subscriber.getSubscriptionsForType(eventType): any);
+    const subscriptions: ?[
+      EmitterSubscription,
+    ] = (this._subscriber.getSubscriptionsForType(eventType): any);
     if (subscriptions) {
       for (let i = 0, l = subscriptions.length; i < l; i++) {
         const subscription = subscriptions[i];
diff --git a/Libraries/vendor/emitter/EventEmitterWithHolding.js b/Libraries/vendor/emitter/EventEmitterWithHolding.js
index a9f232a567a8..582fe03c2be3 100644
--- a/Libraries/vendor/emitter/EventEmitterWithHolding.js
+++ b/Libraries/vendor/emitter/EventEmitterWithHolding.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 import type EmitterSubscription from 'EmitterSubscription';
@@ -25,7 +27,6 @@ import type EventHolder from 'EventHolder';
  * that uses an emitter.
  */
 class EventEmitterWithHolding {
-
   _emitter: EventEmitter;
   _eventHolder: EventHolder;
   _currentEventToken: ?Object;
@@ -80,8 +81,15 @@ class EventEmitterWithHolding {
    *   }); // logs 'abc'
    */
   addRetroactiveListener(
-    eventType: string, listener: Function, context: ?Object): EmitterSubscription {
-    const subscription = this._emitter.addListener(eventType, listener, context);
+    eventType: string,
+    listener: Function,
+    context: ?Object,
+  ): EmitterSubscription {
+    const subscription = this._emitter.addListener(
+      eventType,
+      listener,
+      context,
+    );
 
     this._emittingHeldEvents = true;
     this._eventHolder.emitToListener(eventType, listener, context);
diff --git a/Libraries/vendor/emitter/EventHolder.js b/Libraries/vendor/emitter/EventHolder.js
index 2faa43eb19a8..a8c9a1a102ac 100644
--- a/Libraries/vendor/emitter/EventHolder.js
+++ b/Libraries/vendor/emitter/EventHolder.js
@@ -4,14 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const invariant = require('fbjs/lib/invariant');
 
 class EventHolder {
-
   _heldEvents: Object;
   _currentEventKey: ?Object;
 
@@ -46,7 +47,7 @@ class EventHolder {
     const eventsOfType = this._heldEvents[eventType];
     const key = {
       eventType: eventType,
-      index: eventsOfType.length
+      index: eventsOfType.length,
     };
     eventsOfType.push(args);
     return key;
@@ -60,7 +61,7 @@ class EventHolder {
    * @param {?object} context - Optional context object to use when invoking
    *   the listener
    */
-  emitToListener(eventType: ?string , listener: Function, context: ?Object) {
+  emitToListener(eventType: ?string, listener: Function, context: ?Object) {
     const eventsOfType = this._heldEvents[eventType];
     if (!eventsOfType) {
       return;
@@ -72,7 +73,7 @@ class EventHolder {
       }
       this._currentEventKey = {
         eventType: eventType,
-        index: index
+        index: index,
       };
       listener.apply(context, eventHeld);
     });
@@ -90,7 +91,7 @@ class EventHolder {
   releaseCurrentEvent() {
     invariant(
       this._currentEventKey !== null,
-      'Not in an emitting cycle; there is no current event'
+      'Not in an emitting cycle; there is no current event',
     );
     this._currentEventKey && this.releaseEvent(this._currentEventKey);
   }
diff --git a/Libraries/vendor/emitter/EventSubscription.js b/Libraries/vendor/emitter/EventSubscription.js
index 1d809c371d14..3b1052ab403b 100644
--- a/Libraries/vendor/emitter/EventSubscription.js
+++ b/Libraries/vendor/emitter/EventSubscription.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 import type EventSubscriptionVendor from 'EventSubscriptionVendor';
@@ -15,7 +17,6 @@ import type EventSubscriptionVendor from 'EventSubscriptionVendor';
  * remove its own subscription.
  */
 class EventSubscription {
-
   eventType: string;
   key: number;
   subscriber: EventSubscriptionVendor;
diff --git a/Libraries/vendor/emitter/EventSubscriptionVendor.js b/Libraries/vendor/emitter/EventSubscriptionVendor.js
index 779952898c8b..a2602512cdc5 100644
--- a/Libraries/vendor/emitter/EventSubscriptionVendor.js
+++ b/Libraries/vendor/emitter/EventSubscriptionVendor.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const invariant = require('fbjs/lib/invariant');
@@ -17,7 +19,6 @@ import type EventSubscription from 'EventSubscription';
  * subscribed to a particular event type.
  */
 class EventSubscriptionVendor {
-
   _subscriptionsForType: Object;
   _currentSubscription: ?EventSubscription;
 
@@ -33,10 +34,13 @@ class EventSubscriptionVendor {
    * @param {EventSubscription} subscription
    */
   addSubscription(
-    eventType: string, subscription: EventSubscription): EventSubscription {
+    eventType: string,
+    subscription: EventSubscription,
+  ): EventSubscription {
     invariant(
       subscription.subscriber === this,
-      'The subscriber of the subscription is incorrectly set.');
+      'The subscriber of the subscription is incorrectly set.',
+    );
     if (!this._subscriptionsForType[eventType]) {
       this._subscriptionsForType[eventType] = [];
     }
@@ -90,7 +94,7 @@ class EventSubscriptionVendor {
    * @returns {?array}
    */
   getSubscriptionsForType(eventType: string): ?[EventSubscription] {
-   return this._subscriptionsForType[eventType];
+    return this._subscriptionsForType[eventType];
   }
 }
 
diff --git a/Libraries/vendor/emitter/EventValidator.js b/Libraries/vendor/emitter/EventValidator.js
index 16b469791037..400197f65268 100644
--- a/Libraries/vendor/emitter/EventValidator.js
+++ b/Libraries/vendor/emitter/EventValidator.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /**
@@ -36,11 +38,11 @@ const EventValidator = {
       emit: function emit(type, a, b, c, d, e, _) {
         assertAllowsEventType(type, eventTypes);
         return emitter.emit.call(this, type, a, b, c, d, e, _);
-      }
+      },
     });
 
     return emitterWithValidation;
-  }
+  },
 };
 
 function assertAllowsEventType(type, allowedTypes) {
@@ -60,7 +62,7 @@ function errorMessageFor(type, allowedTypes) {
 
 // Allow for good error messages
 if (__DEV__) {
-  var recommendationFor = function (type, allowedTypes) {
+  var recommendationFor = function(type, allowedTypes) {
     const closestTypeRecommendation = closestTypeFor(type, allowedTypes);
     if (isCloseEnough(closestTypeRecommendation, type)) {
       return 'Did you mean "' + closestTypeRecommendation.type + '"? ';
@@ -69,21 +71,21 @@ if (__DEV__) {
     }
   };
 
-  var closestTypeFor = function (type, allowedTypes) {
+  var closestTypeFor = function(type, allowedTypes) {
     const typeRecommendations = allowedTypes.map(
-      typeRecommendationFor.bind(this, type)
+      typeRecommendationFor.bind(this, type),
     );
     return typeRecommendations.sort(recommendationSort)[0];
   };
 
-  var typeRecommendationFor = function (type, recommendedType) {
+  var typeRecommendationFor = function(type, recommendedType) {
     return {
       type: recommendedType,
-      distance: damerauLevenshteinDistance(type, recommendedType)
+      distance: damerauLevenshteinDistance(type, recommendedType),
     };
   };
 
-  var recommendationSort = function (recommendationA, recommendationB) {
+  var recommendationSort = function(recommendationA, recommendationB) {
     if (recommendationA.distance < recommendationB.distance) {
       return -1;
     } else if (recommendationA.distance > recommendationB.distance) {
@@ -93,11 +95,11 @@ if (__DEV__) {
     }
   };
 
-  var isCloseEnough = function (closestType, actualType) {
-    return (closestType.distance / actualType.length) < 0.334;
+  var isCloseEnough = function(closestType, actualType) {
+    return closestType.distance / actualType.length < 0.334;
   };
 
-  var damerauLevenshteinDistance = function (a, b) {
+  var damerauLevenshteinDistance = function(a, b) {
     let i, j;
     const d = [];
 
@@ -116,12 +118,15 @@ if (__DEV__) {
         d[i][j] = Math.min(
           d[i - 1][j] + 1,
           d[i][j - 1] + 1,
-          d[i - 1][j - 1] + cost
+          d[i - 1][j - 1] + cost,
         );
 
-        if (i > 1 && j > 1 &&
-            a.charAt(i - 1) === b.charAt(j - 2) &&
-            a.charAt(i - 2) === b.charAt(j - 1)) {
+        if (
+          i > 1 &&
+          j > 1 &&
+          a.charAt(i - 1) === b.charAt(j - 2) &&
+          a.charAt(i - 2) === b.charAt(j - 1)
+        ) {
           d[i][j] = Math.min(d[i][j], d[i - 2][j - 2] + cost);
         }
       }
diff --git a/Libraries/vendor/emitter/mixInEventEmitter.js b/Libraries/vendor/emitter/mixInEventEmitter.js
index 5b23f891d883..a53ce08d691c 100644
--- a/Libraries/vendor/emitter/mixInEventEmitter.js
+++ b/Libraries/vendor/emitter/mixInEventEmitter.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const EventEmitter = require('EventEmitter');
@@ -56,7 +58,7 @@ function mixInEventEmitter(cls: Function | Object, types: Object) {
   if (ctor) {
     invariant(
       ctor === Object || ctor === Function,
-      'Mix EventEmitter into a class, not an instance'
+      'Mix EventEmitter into a class, not an instance',
     );
   }
 
@@ -93,7 +95,7 @@ const EventEmitterMixin = {
     return this.__getEventEmitter().addRetroactiveListener(
       eventType,
       listener,
-      context
+      context,
     );
   },
 
@@ -129,7 +131,7 @@ const EventEmitterMixin = {
       this.__eventEmitter = new EventEmitterWithHolding(emitter, holder);
     }
     return this.__eventEmitter;
-  }
+  },
 };
 
 module.exports = mixInEventEmitter;

From a93e281428f47ba355ba79cda3e98ca7da677636 Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Fri, 11 May 2018 10:54:22 -0700
Subject: [PATCH 0506/1109] Detach RN Bridge and CS

Reviewed By: danzimm

Differential Revision: D7833851

fbshipit-source-id: 14533c519f08bd39d69f5203040ad54415228f9f
---
 Libraries/BatchedBridge/NativeModules.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/BatchedBridge/NativeModules.js b/Libraries/BatchedBridge/NativeModules.js
index bfee59abb4b7..61dd5bff1e61 100644
--- a/Libraries/BatchedBridge/NativeModules.js
+++ b/Libraries/BatchedBridge/NativeModules.js
@@ -151,7 +151,7 @@ function createErrorFromErrorData(errorData: {message: string}): ExtendedError {
 let NativeModules: {[moduleName: string]: Object} = {};
 if (global.nativeModuleProxy) {
   NativeModules = global.nativeModuleProxy;
-} else {
+} else if (!global.nativeExtensions) {
   const bridgeConfig = global.__fbBatchedBridgeConfig;
   invariant(
     bridgeConfig,

From 194bd88052a62ee0f0bb4827b95e39e1bc0e7a7a Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Fri, 11 May 2018 10:57:29 -0700
Subject: [PATCH 0507/1109] Fix RootViewTest

Reviewed By: fkgozali

Differential Revision: D7944946

fbshipit-source-id: a8dbceba060b22ac4bc4728fb342372c437a0733
---
 ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java | 1 +
 1 file changed, 1 insertion(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 4c4a7952990d..6fbe25e82eb4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -527,6 +527,7 @@ private void defaultJSEntryPoint() {
   @VisibleForTesting
   /* package */ void simulateAttachForTesting() {
     mIsAttachedToInstance = true;
+    mJSTouchDispatcher = new JSTouchDispatcher(this);
   }
 
   private CustomGlobalLayoutListener getCustomGlobalLayoutListener() {

From 166264d63b28582e31d083fab96ef46bc02ea469 Mon Sep 17 00:00:00 2001
From: Irene Feng <irenelfeng@fb.com>
Date: Fri, 11 May 2018 12:09:48 -0700
Subject: [PATCH 0508/1109] Back out "React sync for revisions
 0887c7d...25dda90"

Reviewed By: acdlite

Differential Revision: D7973856

fbshipit-source-id: c9c687651ca752541b80693e2af2f07b31bbabad
---
 Libraries/Renderer/REVISION                   |    2 +-
 Libraries/Renderer/oss/ReactFabric-dev.js     | 2164 ++++++++---------
 Libraries/Renderer/oss/ReactFabric-prod.js    | 1757 +++++++------
 .../Renderer/oss/ReactNativeRenderer-dev.js   | 2164 ++++++++---------
 .../Renderer/oss/ReactNativeRenderer-prod.js  | 1797 +++++++-------
 .../Renderer/shims/NativeMethodsMixin.js      |    1 -
 Libraries/Renderer/shims/ReactDebugTool.js    |    1 -
 Libraries/Renderer/shims/ReactFabric.js       |    1 -
 Libraries/Renderer/shims/ReactNative.js       |    1 -
 .../shims/ReactNativeComponentTree.js         |    1 -
 Libraries/Renderer/shims/ReactNativeTypes.js  |    1 -
 .../shims/ReactNativeViewConfigRegistry.js    |    1 -
 Libraries/Renderer/shims/ReactPerf.js         |    1 -
 Libraries/Renderer/shims/ReactTypes.js        |    1 -
 .../shims/createReactNativeComponentClass.js  |    1 -
 15 files changed, 3762 insertions(+), 4132 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index 1899fb635260..ba0ce2996c48 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-25dda90c1ecb0c662ab06e2c80c1ee31e0ae9d36
\ No newline at end of file
+0887c7d56cb9b83f36dcb490b4245d7bc33bda1f
\ No newline at end of file
diff --git a/Libraries/Renderer/oss/ReactFabric-dev.js b/Libraries/Renderer/oss/ReactFabric-dev.js
index 3b52fb146ce8..0424315c8ed6 100644
--- a/Libraries/Renderer/oss/ReactFabric-dev.js
+++ b/Libraries/Renderer/oss/ReactFabric-dev.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactFabric-dev
  * @preventMunge
  */
 
@@ -26,8 +25,8 @@ var deepDiffer = require("deepDiffer");
 var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
-var checkPropTypes = require("prop-types/checkPropTypes");
 var shallowEqual = require("fbjs/lib/shallowEqual");
+var checkPropTypes = require("prop-types/checkPropTypes");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
 var FabricUIManager = require("FabricUIManager");
 
@@ -816,7 +815,7 @@ var ForwardRef = 14;
 
 function getParent(inst) {
   do {
-    inst = inst.return;
+    inst = inst["return"];
     // TODO: If this is a HostRoot we might want to bail out.
     // That is depending on if we want nested subtrees (layers) to bubble
     // events to their parent. We could also go through parentNode on the
@@ -2313,21 +2312,23 @@ injection.injectEventPluginsByName({
 
 // The Symbol used to tag the ReactElement-like types. If there is no native Symbol
 // nor polyfill, then a plain number is used for performance.
-var hasSymbol = typeof Symbol === "function" && Symbol.for;
+var hasSymbol = typeof Symbol === "function" && Symbol["for"];
 
-var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 0xeac9;
-var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 0xeaca;
-var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
+var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
+var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
-  ? Symbol.for("react.strict_mode")
+  ? Symbol["for"]("react.strict_mode")
   : 0xeacc;
-var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 0xeacd;
-var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 0xeace;
-var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 0xeacf;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
+var REACT_ASYNC_MODE_TYPE = hasSymbol
+  ? Symbol["for"]("react.async_mode")
+  : 0xeacf;
 var REACT_FORWARD_REF_TYPE = hasSymbol
-  ? Symbol.for("react.forward_ref")
+  ? Symbol["for"]("react.forward_ref")
   : 0xead0;
 
 var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
@@ -3410,10 +3411,11 @@ var ContentReset = /*          */ 16;
 var Callback = /*              */ 32;
 var DidCapture = /*            */ 64;
 var Ref = /*                   */ 128;
-var Snapshot = /*              */ 256;
+var ErrLog = /*                */ 256;
+var Snapshot = /*              */ 2048;
 
 // Union of all host effects
-var HostEffectMask = /*        */ 511;
+var HostEffectMask = /*        */ 2559;
 
 var Incomplete = /*            */ 512;
 var ShouldCapture = /*         */ 1024;
@@ -3430,15 +3432,15 @@ function isFiberMountedImpl(fiber) {
     if ((node.effectTag & Placement) !== NoEffect) {
       return MOUNTING;
     }
-    while (node.return) {
-      node = node.return;
+    while (node["return"]) {
+      node = node["return"];
       if ((node.effectTag & Placement) !== NoEffect) {
         return MOUNTING;
       }
     }
   } else {
-    while (node.return) {
-      node = node.return;
+    while (node["return"]) {
+      node = node["return"];
     }
   }
   if (node.tag === HostRoot) {
@@ -3510,7 +3512,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
   var a = fiber;
   var b = alternate;
   while (true) {
-    var parentA = a.return;
+    var parentA = a["return"];
     var parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) {
       // We're at the root.
@@ -3540,7 +3542,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       invariant(false, "Unable to find node on an unmounted component.");
     }
 
-    if (a.return !== b.return) {
+    if (a["return"] !== b["return"]) {
       // The return pointer of A and the return pointer of B point to different
       // fibers. We assume that return pointers never criss-cross, so A must
       // belong to the child set of A.return, and B must belong to the child
@@ -3628,7 +3630,7 @@ function findCurrentHostFiber(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child) {
-      node.child.return = node;
+      node.child["return"] = node;
       node = node.child;
       continue;
     }
@@ -3636,12 +3638,12 @@ function findCurrentHostFiber(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node.return || node.return === currentParent) {
+      if (!node["return"] || node["return"] === currentParent) {
         return null;
       }
-      node = node.return;
+      node = node["return"];
     }
-    node.sibling.return = node.return;
+    node.sibling["return"] = node["return"];
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -3661,7 +3663,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child && node.tag !== HostPortal) {
-      node.child.return = node;
+      node.child["return"] = node;
       node = node.child;
       continue;
     }
@@ -3669,12 +3671,12 @@ function findCurrentHostFiberWithNoPortals(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node.return || node.return === currentParent) {
+      if (!node["return"] || node["return"] === currentParent) {
         return null;
       }
-      node = node.return;
+      node = node["return"];
     }
-    node.sibling.return = node.return;
+    node.sibling["return"] = node["return"];
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -3757,7 +3759,7 @@ function FiberNode(tag, pendingProps, key, mode) {
   this.stateNode = null;
 
   // Fiber
-  this.return = null;
+  this["return"] = null;
   this.child = null;
   this.sibling = null;
   this.index = 0;
@@ -4042,7 +4044,7 @@ function assignFiberPropertiesInDEV(target, source) {
   target.key = source.key;
   target.type = source.type;
   target.stateNode = source.stateNode;
-  target.return = source.return;
+  target["return"] = source["return"];
   target.child = source.child;
   target.sibling = source.sibling;
   target.index = source.index;
@@ -4202,7 +4204,7 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
   do {
     info += describeFiber(node);
     // Otherwise this return pointer might point to the wrong tree:
-    node = node.return;
+    node = node["return"];
   } while (node);
   return info;
 }
@@ -4372,7 +4374,7 @@ var ReactStrictModeWarnings = {
         maybeStrictRoot = fiber;
       }
 
-      fiber = fiber.return;
+      fiber = fiber["return"];
     }
 
     return maybeStrictRoot;
@@ -4493,6 +4495,16 @@ var ReactStrictModeWarnings = {
       return;
     }
 
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    // Note that it is sufficient to check for the presence of a
+    // single lifecycle, componentWillMount, with the polyfill flag.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning === true
+    ) {
+      return;
+    }
+
     var warningsForRoot = void 0;
     if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
       warningsForRoot = {
@@ -4508,23 +4520,19 @@ var ReactStrictModeWarnings = {
 
     var unsafeLifecycles = [];
     if (
-      (typeof instance.componentWillMount === "function" &&
-        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
+      typeof instance.componentWillMount === "function" ||
       typeof instance.UNSAFE_componentWillMount === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillMount");
     }
     if (
-      (typeof instance.componentWillReceiveProps === "function" &&
-        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-          true) ||
+      typeof instance.componentWillReceiveProps === "function" ||
       typeof instance.UNSAFE_componentWillReceiveProps === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
     }
     if (
-      (typeof instance.componentWillUpdate === "function" &&
-        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
+      typeof instance.componentWillUpdate === "function" ||
       typeof instance.UNSAFE_componentWillUpdate === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillUpdate");
@@ -4566,7 +4574,7 @@ function getCurrentFiberOwnerName() {
   return null;
 }
 
-function getCurrentFiberStackAddendum$1() {
+function getCurrentFiberStackAddendum() {
   {
     var fiber = ReactDebugCurrentFiber.current;
     if (fiber === null) {
@@ -4586,7 +4594,7 @@ function resetCurrentFiber() {
 }
 
 function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum$1;
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
   ReactDebugCurrentFiber.current = fiber;
   ReactDebugCurrentFiber.phase = null;
 }
@@ -4602,7 +4610,7 @@ var ReactDebugCurrentFiber = {
   setCurrentFiber: setCurrentFiber,
   setCurrentPhase: setCurrentPhase,
   getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum$1
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
 };
 
 // Prefix measurements so that it's possible to filter them.
@@ -4759,13 +4767,13 @@ var pauseTimers = function() {
     if (fiber._debugIsCurrentlyTiming) {
       endFiberMark(fiber, null, null);
     }
-    fiber = fiber.return;
+    fiber = fiber["return"];
   }
 };
 
 var resumeTimersRecursively = function(fiber) {
-  if (fiber.return !== null) {
-    resumeTimersRecursively(fiber.return);
+  if (fiber["return"] !== null) {
+    resumeTimersRecursively(fiber["return"]);
   }
   if (fiber._debugIsCurrentlyTiming) {
     beginFiberMark(fiber, null);
@@ -4857,7 +4865,7 @@ function stopWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber.return;
+    currentFiber = fiber["return"];
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -4872,7 +4880,7 @@ function stopFailedWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber.return;
+    currentFiber = fiber["return"];
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -5062,232 +5070,100 @@ function stopCommitLifeCyclesTimer() {
   }
 }
 
-// UpdateQueue is a linked list of prioritized updates.
-//
-// Like fibers, update queues come in pairs: a current queue, which represents
-// the visible state of the screen, and a work-in-progress queue, which is
-// can be mutated and processed asynchronously before it is committed — a form
-// of double buffering. If a work-in-progress render is discarded before
-// finishing, we create a new work-in-progress by cloning the current queue.
-//
-// Both queues share a persistent, singly-linked list structure. To schedule an
-// update, we append it to the end of both queues. Each queue maintains a
-// pointer to first update in the persistent list that hasn't been processed.
-// The work-in-progress pointer always has a position equal to or greater than
-// the current queue, since we always work on that one. The current queue's
-// pointer is only updated during the commit phase, when we swap in the
-// work-in-progress.
-//
-// For example:
-//
-//   Current pointer:           A - B - C - D - E - F
-//   Work-in-progress pointer:              D - E - F
-//                                          ^
-//                                          The work-in-progress queue has
-//                                          processed more updates than current.
-//
-// The reason we append to both queues is because otherwise we might drop
-// updates without ever processing them. For example, if we only add updates to
-// the work-in-progress queue, some updates could be lost whenever a work-in
-// -progress render restarts by cloning from current. Similarly, if we only add
-// updates to the current queue, the updates will be lost whenever an already
-// in-progress queue commits and swaps with the current queue. However, by
-// adding to both queues, we guarantee that the update will be part of the next
-// work-in-progress. (And because the work-in-progress queue becomes the
-// current queue once it commits, there's no danger of applying the same
-// update twice.)
-//
-// Prioritization
-// --------------
-//
-// Updates are not sorted by priority, but by insertion; new updates are always
-// appended to the end of the list.
-//
-// The priority is still important, though. When processing the update queue
-// during the render phase, only the updates with sufficient priority are
-// included in the result. If we skip an update because it has insufficient
-// priority, it remains in the queue to be processed later, during a lower
-// priority render. Crucially, all updates subsequent to a skipped update also
-// remain in the queue *regardless of their priority*. That means high priority
-// updates are sometimes processed twice, at two separate priorities. We also
-// keep track of a base state, that represents the state before the first
-// update in the queue is applied.
-//
-// For example:
-//
-//   Given a base state of '', and the following queue of updates
-//
-//     A1 - B2 - C1 - D2
-//
-//   where the number indicates the priority, and the update is applied to the
-//   previous state by appending a letter, React will process these updates as
-//   two separate renders, one per distinct priority level:
-//
-//   First render, at priority 1:
-//     Base state: ''
-//     Updates: [A1, C1]
-//     Result state: 'AC'
-//
-//   Second render, at priority 2:
-//     Base state: 'A'            <-  The base state does not include C1,
-//                                    because B2 was skipped.
-//     Updates: [B2, C1, D2]      <-  C1 was rebased on top of B2
-//     Result state: 'ABCD'
-//
-// Because we process updates in insertion order, and rebase high priority
-// updates when preceding updates are skipped, the final result is deterministic
-// regardless of priority. Intermediate state may vary according to system
-// resources, but the final state is always the same.
-
-var UpdateState = 0;
-var ReplaceState = 1;
-var ForceUpdate = 2;
-var CaptureUpdate = 3;
-
 var didWarnUpdateInsideUpdate = void 0;
-var currentlyProcessingQueue = void 0;
-var resetCurrentlyProcessingQueue = void 0;
+
 {
   didWarnUpdateInsideUpdate = false;
-  currentlyProcessingQueue = null;
-  resetCurrentlyProcessingQueue = function() {
-    currentlyProcessingQueue = null;
-  };
 }
 
+// Callbacks are not validated until invocation
+
+// Singly linked-list of updates. When an update is scheduled, it is added to
+// the queue of the current fiber and the work-in-progress fiber. The two queues
+// are separate but they share a persistent structure.
+//
+// During reconciliation, updates are removed from the work-in-progress fiber,
+// but they remain on the current fiber. That ensures that if a work-in-progress
+// is aborted, the aborted updates are recovered by cloning from current.
+//
+// The work-in-progress queue is always a subset of the current queue.
+//
+// When the tree is committed, the work-in-progress becomes the current.
+
 function createUpdateQueue(baseState) {
   var queue = {
-    expirationTime: NoWork,
     baseState: baseState,
-    firstUpdate: null,
-    lastUpdate: null,
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
-    firstEffect: null,
-    lastEffect: null,
-    firstCapturedEffect: null,
-    lastCapturedEffect: null,
-    hasForceUpdate: false
-  };
-  return queue;
-}
-
-function cloneUpdateQueue(currentQueue) {
-  var queue = {
-    expirationTime: currentQueue.expirationTime,
-    baseState: currentQueue.baseState,
-    firstUpdate: currentQueue.firstUpdate,
-    lastUpdate: currentQueue.lastUpdate,
-
-    // TODO: With resuming, if we bail out and resuse the child tree, we should
-    // keep these effects.
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
-
+    expirationTime: NoWork,
+    first: null,
+    last: null,
+    callbackList: null,
     hasForceUpdate: false,
-
-    firstEffect: null,
-    lastEffect: null,
-
-    firstCapturedEffect: null,
-    lastCapturedEffect: null
+    isInitialized: false,
+    capturedValues: null
   };
+  {
+    queue.isProcessing = false;
+  }
   return queue;
 }
 
-function createUpdate(expirationTime) {
-  return {
-    expirationTime: expirationTime,
-
-    tag: UpdateState,
-    payload: null,
-    callback: null,
-
-    next: null,
-    nextEffect: null
-  };
-}
-
-function appendUpdateToQueue(queue, update, expirationTime) {
+function insertUpdateIntoQueue(queue, update) {
   // Append the update to the end of the list.
-  if (queue.lastUpdate === null) {
+  if (queue.last === null) {
     // Queue is empty
-    queue.firstUpdate = queue.lastUpdate = update;
+    queue.first = queue.last = update;
   } else {
-    queue.lastUpdate.next = update;
-    queue.lastUpdate = update;
+    queue.last.next = update;
+    queue.last = update;
   }
   if (
     queue.expirationTime === NoWork ||
-    queue.expirationTime > expirationTime
+    queue.expirationTime > update.expirationTime
   ) {
-    // The incoming update has the earliest expiration of any update in the
-    // queue. Update the queue's expiration time.
-    queue.expirationTime = expirationTime;
+    queue.expirationTime = update.expirationTime;
   }
 }
 
-function enqueueUpdate(fiber, update, expirationTime) {
-  // Update queues are created lazily.
-  var alternate = fiber.alternate;
-  var queue1 = void 0;
+var q1 = void 0;
+var q2 = void 0;
+function ensureUpdateQueues(fiber) {
+  q1 = q2 = null;
+  // We'll have at least one and at most two distinct update queues.
+  var alternateFiber = fiber.alternate;
+  var queue1 = fiber.updateQueue;
+  if (queue1 === null) {
+    // TODO: We don't know what the base state will be until we begin work.
+    // It depends on which fiber is the next current. Initialize with an empty
+    // base state, then set to the memoizedState when rendering. Not super
+    // happy with this approach.
+    queue1 = fiber.updateQueue = createUpdateQueue(null);
+  }
+
   var queue2 = void 0;
-  if (alternate === null) {
-    // There's only one fiber.
-    queue1 = fiber.updateQueue;
-    queue2 = null;
-    if (queue1 === null) {
-      queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
-    }
-  } else {
-    // There are two owners.
-    queue1 = fiber.updateQueue;
-    queue2 = alternate.updateQueue;
-    if (queue1 === null) {
-      if (queue2 === null) {
-        // Neither fiber has an update queue. Create new ones.
-        queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
-        queue2 = alternate.updateQueue = createUpdateQueue(
-          alternate.memoizedState
-        );
-      } else {
-        // Only one fiber has an update queue. Clone to create a new one.
-        queue1 = fiber.updateQueue = cloneUpdateQueue(queue2);
-      }
-    } else {
-      if (queue2 === null) {
-        // Only one fiber has an update queue. Clone to create a new one.
-        queue2 = alternate.updateQueue = cloneUpdateQueue(queue1);
-      } else {
-        // Both owners have an update queue.
-      }
+  if (alternateFiber !== null) {
+    queue2 = alternateFiber.updateQueue;
+    if (queue2 === null) {
+      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
     }
-  }
-  if (queue2 === null || queue1 === queue2) {
-    // There's only a single queue.
-    appendUpdateToQueue(queue1, update, expirationTime);
   } else {
-    // There are two queues. We need to append the update to both queues,
-    // while accounting for the persistent structure of the list — we don't
-    // want the same update to be added multiple times.
-    if (queue1.lastUpdate === null || queue2.lastUpdate === null) {
-      // One of the queues is not empty. We must add the update to both queues.
-      appendUpdateToQueue(queue1, update, expirationTime);
-      appendUpdateToQueue(queue2, update, expirationTime);
-    } else {
-      // Both queues are non-empty. The last update is the same in both lists,
-      // because of structural sharing. So, only append to one of the lists.
-      appendUpdateToQueue(queue1, update, expirationTime);
-      // But we still need to update the `lastUpdate` pointer of queue2.
-      queue2.lastUpdate = update;
-    }
+    queue2 = null;
   }
+  queue2 = queue2 !== queue1 ? queue2 : null;
 
+  // Use module variables instead of returning a tuple
+  q1 = queue1;
+  q2 = queue2;
+}
+
+function insertUpdateIntoFiber(fiber, update) {
+  ensureUpdateQueues(fiber);
+  var queue1 = q1;
+  var queue2 = q2;
+
+  // Warn if an update is scheduled from inside an updater function.
   {
     if (
-      fiber.tag === ClassComponent &&
-      (currentlyProcessingQueue === queue1 ||
-        (queue2 !== null && currentlyProcessingQueue === queue2)) &&
+      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
       !didWarnUpdateInsideUpdate
     ) {
       warning(
@@ -5300,328 +5176,225 @@ function enqueueUpdate(fiber, update, expirationTime) {
       didWarnUpdateInsideUpdate = true;
     }
   }
-}
 
-function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
-  // Captured updates go into a separate list, and only on the work-in-
-  // progress queue.
-  var workInProgressQueue = workInProgress.updateQueue;
-  if (workInProgressQueue === null) {
-    workInProgressQueue = workInProgress.updateQueue = createUpdateQueue(
-      workInProgress.memoizedState
-    );
-  } else {
-    // TODO: I put this here rather than createWorkInProgress so that we don't
-    // clone the queue unnecessarily. There's probably a better way to
-    // structure this.
-    workInProgressQueue = ensureWorkInProgressQueueIsAClone(
-      workInProgress,
-      workInProgressQueue
-    );
+  // If there's only one queue, add the update to that queue and exit.
+  if (queue2 === null) {
+    insertUpdateIntoQueue(queue1, update);
+    return;
   }
 
-  // Append the update to the end of the list.
-  if (workInProgressQueue.lastCapturedUpdate === null) {
-    // This is the first render phase update
-    workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update;
-  } else {
-    workInProgressQueue.lastCapturedUpdate.next = update;
-    workInProgressQueue.lastCapturedUpdate = update;
-  }
-  if (
-    workInProgressQueue.expirationTime === NoWork ||
-    workInProgressQueue.expirationTime > renderExpirationTime
-  ) {
-    // The incoming update has the earliest expiration of any update in the
-    // queue. Update the queue's expiration time.
-    workInProgressQueue.expirationTime = renderExpirationTime;
+  // If either queue is empty, we need to add to both queues.
+  if (queue1.last === null || queue2.last === null) {
+    insertUpdateIntoQueue(queue1, update);
+    insertUpdateIntoQueue(queue2, update);
+    return;
   }
+
+  // If both lists are not empty, the last update is the same for both lists
+  // because of structural sharing. So, we should only append to one of
+  // the lists.
+  insertUpdateIntoQueue(queue1, update);
+  // But we still need to update the `last` pointer of queue2.
+  queue2.last = update;
 }
 
-function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
-  var current = workInProgress.alternate;
-  if (current !== null) {
-    // If the work-in-progress queue is equal to the current queue,
-    // we need to clone it first.
-    if (queue === current.updateQueue) {
-      queue = workInProgress.updateQueue = cloneUpdateQueue(queue);
-    }
+function getUpdateExpirationTime(fiber) {
+  switch (fiber.tag) {
+    case HostRoot:
+    case ClassComponent:
+      var updateQueue = fiber.updateQueue;
+      if (updateQueue === null) {
+        return NoWork;
+      }
+      return updateQueue.expirationTime;
+    default:
+      return NoWork;
   }
-  return queue;
 }
 
-function getStateFromUpdate(
-  workInProgress,
-  queue,
-  update,
-  prevState,
-  nextProps,
-  instance
-) {
-  switch (update.tag) {
-    case ReplaceState: {
-      var _payload = update.payload;
-      if (typeof _payload === "function") {
-        // Updater function
-        {
-          if (
-            debugRenderPhaseSideEffects ||
-            (debugRenderPhaseSideEffectsForStrictMode &&
-              workInProgress.mode & StrictMode)
-          ) {
-            _payload.call(instance, prevState, nextProps);
-          }
-        }
-        return _payload.call(instance, prevState, nextProps);
-      }
-      // State object
-      return _payload;
-    }
-    case CaptureUpdate: {
-      workInProgress.effectTag =
-        (workInProgress.effectTag & ~ShouldCapture) | DidCapture;
-    }
-    // Intentional fallthrough
-    case UpdateState: {
-      var _payload2 = update.payload;
-      var partialState = void 0;
-      if (typeof _payload2 === "function") {
-        // Updater function
-        {
-          if (
-            debugRenderPhaseSideEffects ||
-            (debugRenderPhaseSideEffectsForStrictMode &&
-              workInProgress.mode & StrictMode)
-          ) {
-            _payload2.call(instance, prevState, nextProps);
-          }
-        }
-        partialState = _payload2.call(instance, prevState, nextProps);
-      } else {
-        // Partial state object
-        partialState = _payload2;
-      }
-      if (partialState === null || partialState === undefined) {
-        // Null and undefined are treated as no-ops.
-        return prevState;
-      }
-      // Merge the partial state and the previous state.
-      return Object.assign({}, prevState, partialState);
-    }
-    case ForceUpdate: {
-      queue.hasForceUpdate = true;
-      return prevState;
-    }
+function getStateFromUpdate(update, instance, prevState, props) {
+  var partialState = update.partialState;
+  if (typeof partialState === "function") {
+    return partialState.call(instance, prevState, props);
+  } else {
+    return partialState;
   }
-  return prevState;
 }
 
 function processUpdateQueue(
+  current,
   workInProgress,
   queue,
-  props,
   instance,
+  props,
   renderExpirationTime
 ) {
-  if (
-    queue.expirationTime === NoWork ||
-    queue.expirationTime > renderExpirationTime
-  ) {
-    // Insufficient priority. Bailout.
-    return;
+  if (current !== null && current.updateQueue === queue) {
+    // We need to create a work-in-progress queue, by cloning the current queue.
+    var currentQueue = queue;
+    queue = workInProgress.updateQueue = {
+      baseState: currentQueue.baseState,
+      expirationTime: currentQueue.expirationTime,
+      first: currentQueue.first,
+      last: currentQueue.last,
+      isInitialized: currentQueue.isInitialized,
+      capturedValues: currentQueue.capturedValues,
+      // These fields are no longer valid because they were already committed.
+      // Reset them.
+      callbackList: null,
+      hasForceUpdate: false
+    };
   }
 
-  queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
-
   {
-    currentlyProcessingQueue = queue;
+    // Set this flag so we can warn if setState is called inside the update
+    // function of another setState.
+    queue.isProcessing = true;
+  }
+
+  // Reset the remaining expiration time. If we skip over any updates, we'll
+  // increase this accordingly.
+  queue.expirationTime = NoWork;
+
+  // TODO: We don't know what the base state will be until we begin work.
+  // It depends on which fiber is the next current. Initialize with an empty
+  // base state, then set to the memoizedState when rendering. Not super
+  // happy with this approach.
+  var state = void 0;
+  if (queue.isInitialized) {
+    state = queue.baseState;
+  } else {
+    state = queue.baseState = workInProgress.memoizedState;
+    queue.isInitialized = true;
   }
-
-  // These values may change as we process the queue.
-  var newBaseState = queue.baseState;
-  var newFirstUpdate = null;
-  var newExpirationTime = NoWork;
-
-  // Iterate through the list of updates to compute the result.
-  var update = queue.firstUpdate;
-  var resultState = newBaseState;
+  var dontMutatePrevState = true;
+  var update = queue.first;
+  var didSkip = false;
   while (update !== null) {
     var updateExpirationTime = update.expirationTime;
     if (updateExpirationTime > renderExpirationTime) {
       // This update does not have sufficient priority. Skip it.
-      if (newFirstUpdate === null) {
-        // This is the first skipped update. It will be the first update in
-        // the new list.
-        newFirstUpdate = update;
-        // Since this is the first update that was skipped, the current result
-        // is the new base state.
-        newBaseState = resultState;
-      }
-      // Since this update will remain in the list, update the remaining
-      // expiration time.
+      var remainingExpirationTime = queue.expirationTime;
       if (
-        newExpirationTime === NoWork ||
-        newExpirationTime > updateExpirationTime
+        remainingExpirationTime === NoWork ||
+        remainingExpirationTime > updateExpirationTime
       ) {
-        newExpirationTime = updateExpirationTime;
+        // Update the remaining expiration time.
+        queue.expirationTime = updateExpirationTime;
       }
-    } else {
-      // This update does have sufficient priority. Process it and compute
-      // a new result.
-      resultState = getStateFromUpdate(
-        workInProgress,
-        queue,
-        update,
-        resultState,
-        props,
-        instance
-      );
-      var _callback = update.callback;
-      if (_callback !== null) {
-        workInProgress.effectTag |= Callback;
-        // Set this to null, in case it was mutated during an aborted render.
-        update.nextEffect = null;
-        if (queue.lastEffect === null) {
-          queue.firstEffect = queue.lastEffect = update;
-        } else {
-          queue.lastEffect.nextEffect = update;
-          queue.lastEffect = update;
-        }
+      if (!didSkip) {
+        didSkip = true;
+        queue.baseState = state;
       }
+      // Continue to the next update.
+      update = update.next;
+      continue;
     }
-    // Continue to the next update.
-    update = update.next;
-  }
 
-  // Separately, iterate though the list of captured updates.
-  var newFirstCapturedUpdate = null;
-  update = queue.firstCapturedUpdate;
-  while (update !== null) {
-    var _updateExpirationTime = update.expirationTime;
-    if (_updateExpirationTime > renderExpirationTime) {
-      // This update does not have sufficient priority. Skip it.
-      if (newFirstCapturedUpdate === null) {
-        // This is the first skipped captured update. It will be the first
-        // update in the new list.
-        newFirstCapturedUpdate = update;
-        // If this is the first update that was skipped, the current result is
-        // the new base state.
-        if (newFirstUpdate === null) {
-          newBaseState = resultState;
-        }
-      }
-      // Since this update will remain in the list, update the remaining
-      // expiration time.
-      if (
-        newExpirationTime === NoWork ||
-        newExpirationTime > _updateExpirationTime
-      ) {
-        newExpirationTime = _updateExpirationTime;
+    // This update does have sufficient priority.
+
+    // If no previous updates were skipped, drop this update from the queue by
+    // advancing the head of the list.
+    if (!didSkip) {
+      queue.first = update.next;
+      if (queue.first === null) {
+        queue.last = null;
       }
+    }
+
+    // Invoke setState callback an extra time to help detect side-effects.
+    // Ignore the return value in this case.
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      getStateFromUpdate(update, instance, state, props);
+    }
+
+    // Process the update
+    var _partialState = void 0;
+    if (update.isReplace) {
+      state = getStateFromUpdate(update, instance, state, props);
+      dontMutatePrevState = true;
     } else {
-      // This update does have sufficient priority. Process it and compute
-      // a new result.
-      resultState = getStateFromUpdate(
-        workInProgress,
-        queue,
-        update,
-        resultState,
-        props,
-        instance
-      );
-      var _callback2 = update.callback;
-      if (_callback2 !== null) {
-        workInProgress.effectTag |= Callback;
-        // Set this to null, in case it was mutated during an aborted render.
-        update.nextEffect = null;
-        if (queue.lastCapturedEffect === null) {
-          queue.firstCapturedEffect = queue.lastCapturedEffect = update;
+      _partialState = getStateFromUpdate(update, instance, state, props);
+      if (_partialState) {
+        if (dontMutatePrevState) {
+          // $FlowFixMe: Idk how to type this properly.
+          state = Object.assign({}, state, _partialState);
         } else {
-          queue.lastCapturedEffect.nextEffect = update;
-          queue.lastCapturedEffect = update;
+          state = Object.assign(state, _partialState);
         }
+        dontMutatePrevState = false;
+      }
+    }
+    if (update.isForced) {
+      queue.hasForceUpdate = true;
+    }
+    if (update.callback !== null) {
+      // Append to list of callbacks.
+      var _callbackList = queue.callbackList;
+      if (_callbackList === null) {
+        _callbackList = queue.callbackList = [];
+      }
+      _callbackList.push(update);
+    }
+    if (update.capturedValue !== null) {
+      var _capturedValues = queue.capturedValues;
+      if (_capturedValues === null) {
+        queue.capturedValues = [update.capturedValue];
+      } else {
+        _capturedValues.push(update.capturedValue);
       }
     }
     update = update.next;
   }
 
-  if (newFirstUpdate === null) {
-    queue.lastUpdate = null;
-  }
-  if (newFirstCapturedUpdate === null) {
-    queue.lastCapturedUpdate = null;
-  } else {
+  if (queue.callbackList !== null) {
     workInProgress.effectTag |= Callback;
+  } else if (
+    queue.first === null &&
+    !queue.hasForceUpdate &&
+    queue.capturedValues === null
+  ) {
+    // The queue is empty. We can reset it.
+    workInProgress.updateQueue = null;
   }
-  if (newFirstUpdate === null && newFirstCapturedUpdate === null) {
-    // We processed every update, without skipping. That means the new base
-    // state is the same as the result state.
-    newBaseState = resultState;
-  }
-
-  queue.baseState = newBaseState;
-  queue.firstUpdate = newFirstUpdate;
-  queue.firstCapturedUpdate = newFirstCapturedUpdate;
-  queue.expirationTime = newExpirationTime;
 
-  workInProgress.memoizedState = resultState;
+  if (!didSkip) {
+    didSkip = true;
+    queue.baseState = state;
+  }
 
   {
-    currentlyProcessingQueue = null;
+    // No longer processing.
+    queue.isProcessing = false;
   }
-}
 
-function callCallback(callback, context) {
-  invariant(
-    typeof callback === "function",
-    "Invalid argument passed as callback. Expected a function. Instead " +
-      "received: %s",
-    callback
-  );
-  callback.call(context);
+  return state;
 }
 
-function commitUpdateQueue(
-  finishedWork,
-  finishedQueue,
-  instance,
-  renderExpirationTime
-) {
-  // If the finished render included captured updates, and there are still
-  // lower priority updates left over, we need to keep the captured updates
-  // in the queue so that they are rebased and not dropped once we process the
-  // queue again at the lower priority.
-  if (finishedQueue.firstCapturedUpdate !== null) {
-    // Join the captured update list to the end of the normal list.
-    if (finishedQueue.lastUpdate !== null) {
-      finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate;
-      finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate;
-    }
-    // Clear the list of captured updates.
-    finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null;
-  }
-
-  // Commit the effects
-  var effect = finishedQueue.firstEffect;
-  finishedQueue.firstEffect = finishedQueue.lastEffect = null;
-  while (effect !== null) {
-    var _callback3 = effect.callback;
-    if (_callback3 !== null) {
-      effect.callback = null;
-      callCallback(_callback3, instance);
-    }
-    effect = effect.nextEffect;
+function commitCallbacks(queue, context) {
+  var callbackList = queue.callbackList;
+  if (callbackList === null) {
+    return;
   }
-
-  effect = finishedQueue.firstCapturedEffect;
-  finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
-  while (effect !== null) {
-    var _callback4 = effect.callback;
-    if (_callback4 !== null) {
-      effect.callback = null;
-      callCallback(_callback4, instance);
-    }
-    effect = effect.nextEffect;
+  // Set the list to null to make sure they don't get called more than once.
+  queue.callbackList = null;
+  for (var i = 0; i < callbackList.length; i++) {
+    var update = callbackList[i];
+    var _callback = update.callback;
+    // This update might be processed again. Clear the callback so it's only
+    // called once.
+    update.callback = null;
+    invariant(
+      typeof _callback === "function",
+      "Invalid argument passed as callback. Expected a function. Instead " +
+        "received: %s",
+      _callback
+    );
+    _callback.call(context);
   }
 }
 
@@ -5629,19 +5402,18 @@ var fakeInternalInstance = {};
 var isArray = Array.isArray;
 
 var didWarnAboutStateAssignmentForComponent = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
 var didWarnAboutUninitializedState = void 0;
 var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
 var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
-var warnOnUndefinedDerivedState = void 0;
 var warnOnInvalidCallback = void 0;
 
 {
   didWarnAboutStateAssignmentForComponent = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
   didWarnAboutUninitializedState = new Set();
   didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
   didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
 
   var didWarnOnInvalidCallback = new Set();
 
@@ -5662,21 +5434,6 @@ var warnOnInvalidCallback = void 0;
     }
   };
 
-  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
-    if (partialState === undefined) {
-      var componentName = getComponentName(workInProgress) || "Component";
-      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-        didWarnAboutUndefinedDerivedState.add(componentName);
-        warning(
-          false,
-          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-            "You have returned undefined.",
-          componentName
-        );
-      }
-    }
-  };
-
   // This is so gross but it's at least non-critical and can be removed if
   // it causes problems. This is meant to give a nicer error message for
   // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
@@ -5698,43 +5455,17 @@ var warnOnInvalidCallback = void 0;
   });
   Object.freeze(fakeInternalInstance);
 }
-
-function applyDerivedStateFromProps(
-  workInProgress,
-  getDerivedStateFromProps,
-  nextProps
-) {
-  var prevState = workInProgress.memoizedState;
-
-  {
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      // Invoke the function an extra time to help detect side-effects.
-      getDerivedStateFromProps(nextProps, prevState);
+function callGetDerivedStateFromCatch(ctor, capturedValues) {
+  var resultState = {};
+  for (var i = 0; i < capturedValues.length; i++) {
+    var capturedValue = capturedValues[i];
+    var error = capturedValue.value;
+    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
+    if (partialState !== null && partialState !== undefined) {
+      Object.assign(resultState, partialState);
     }
   }
-
-  var partialState = getDerivedStateFromProps(nextProps, prevState);
-
-  {
-    warnOnUndefinedDerivedState(workInProgress, partialState);
-  }
-  // Merge the partial state and the previous state.
-  var memoizedState =
-    partialState === null || partialState === undefined
-      ? prevState
-      : Object.assign({}, prevState, partialState);
-  workInProgress.memoizedState = memoizedState;
-
-  // Once the update queue is empty, persist the derived state onto the
-  // base state.
-  var updateQueue = workInProgress.updateQueue;
-  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
-    updateQueue.baseState = memoizedState;
-  }
+  return resultState;
 }
 
 var ReactFiberClassComponent = function(
@@ -5750,57 +5481,65 @@ var ReactFiberClassComponent = function(
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged;
 
-  var classComponentUpdater = {
-    isMounted: isMounted,
-    enqueueSetState: function(inst, payload, callback) {
-      var fiber = get$1(inst);
-      var expirationTime = computeExpirationForFiber(fiber);
+  // Class component state updater
 
-      var update = createUpdate(expirationTime);
-      update.payload = payload;
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "setState");
-        }
-        update.callback = callback;
+  var updater = {
+    isMounted: isMounted,
+    enqueueSetState: function(instance, partialState, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "setState");
       }
-
-      enqueueUpdate(fiber, update, expirationTime);
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: partialState,
+        callback: callback,
+        isReplace: false,
+        isForced: false,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueReplaceState: function(inst, payload, callback) {
-      var fiber = get$1(inst);
-      var expirationTime = computeExpirationForFiber(fiber);
-
-      var update = createUpdate(expirationTime);
-      update.tag = ReplaceState;
-      update.payload = payload;
-
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "replaceState");
-        }
-        update.callback = callback;
+    enqueueReplaceState: function(instance, state, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "replaceState");
       }
-
-      enqueueUpdate(fiber, update, expirationTime);
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: state,
+        callback: callback,
+        isReplace: true,
+        isForced: false,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueForceUpdate: function(inst, callback) {
-      var fiber = get$1(inst);
-      var expirationTime = computeExpirationForFiber(fiber);
-
-      var update = createUpdate(expirationTime);
-      update.tag = ForceUpdate;
-
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "forceUpdate");
-        }
-        update.callback = callback;
+    enqueueForceUpdate: function(instance, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "forceUpdate");
       }
-
-      enqueueUpdate(fiber, update, expirationTime);
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: null,
+        callback: callback,
+        isReplace: false,
+        isForced: true,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
       scheduleWork(fiber, expirationTime);
     }
   };
@@ -5814,10 +5553,11 @@ var ReactFiberClassComponent = function(
     newContext
   ) {
     if (
-      workInProgress.updateQueue !== null &&
-      workInProgress.updateQueue.hasForceUpdate
+      oldProps === null ||
+      (workInProgress.updateQueue !== null &&
+        workInProgress.updateQueue.hasForceUpdate)
     ) {
-      // If forceUpdate was called, disregard sCU.
+      // If the workInProgress already has an Update effect, return true
       return true;
     }
 
@@ -6074,8 +5814,13 @@ var ReactFiberClassComponent = function(
     }
   }
 
+  function resetInputPointers(workInProgress, instance) {
+    instance.props = workInProgress.memoizedProps;
+    instance.state = workInProgress.memoizedState;
+  }
+
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = classComponentUpdater;
+    instance.updater = updater;
     workInProgress.stateNode = instance;
     // The instance needs access to the fiber so that it can schedule updates
     set(instance, workInProgress);
@@ -6084,7 +5829,7 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function constructClassInstance(workInProgress, props, renderExpirationTime) {
+  function constructClassInstance(workInProgress, props) {
     var ctor = workInProgress.type;
     var unmaskedContext = getUnmaskedContext(workInProgress);
     var needsContext = isContextConsumer(workInProgress);
@@ -6093,21 +5838,19 @@ var ReactFiberClassComponent = function(
       : emptyObject;
 
     // Instantiate twice to help detect side-effects.
-    {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        new ctor(props, context); // eslint-disable-line no-new
-      }
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      new ctor(props, context); // eslint-disable-line no-new
     }
 
     var instance = new ctor(props, context);
-    var state = (workInProgress.memoizedState =
+    var state =
       instance.state !== null && instance.state !== undefined
         ? instance.state
-        : null);
+        : null;
     adoptClassInstance(workInProgress, instance);
 
     {
@@ -6198,7 +5941,27 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    workInProgress.memoizedState = state;
+
+    var partialState = callGetDerivedStateFromProps(
+      workInProgress,
+      instance,
+      props,
+      state
+    );
+
+    if (partialState !== null && partialState !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      workInProgress.memoizedState = Object.assign(
+        {},
+        workInProgress.memoizedState,
+        partialState
+      );
+    }
+
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
     // ReactFiberContext usually updates this cache but can't for newly-created instances.
     if (needsContext) {
       cacheContext(workInProgress, unmaskedContext, context);
@@ -6230,7 +5993,7 @@ var ReactFiberClassComponent = function(
           getComponentName(workInProgress) || "Component"
         );
       }
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+      updater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
@@ -6264,13 +6027,57 @@ var ReactFiberClassComponent = function(
           );
         }
       }
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+      updater.enqueueReplaceState(instance, instance.state, null);
+    }
+  }
+
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    var type = workInProgress.type;
+
+    if (typeof type.getDerivedStateFromProps === "function") {
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        // Invoke method an extra time to help detect side-effects.
+        type.getDerivedStateFromProps.call(null, nextProps, prevState);
+      }
+
+      var partialState = type.getDerivedStateFromProps.call(
+        null,
+        nextProps,
+        prevState
+      );
+
+      {
+        if (partialState === undefined) {
+          var componentName = getComponentName(workInProgress) || "Component";
+          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+            didWarnAboutUndefinedDerivedState.add(componentName);
+            warning(
+              false,
+              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+                "You have returned undefined.",
+              componentName
+            );
+          }
+        }
+      }
+
+      return partialState;
     }
   }
 
   // Invokes the mount life-cycles on a previously never rendered instance.
   function mountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
+    var current = workInProgress.alternate;
 
     {
       checkClassInstance(workInProgress);
@@ -6301,28 +6108,6 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        props,
-        instance,
-        renderExpirationTime
-      );
-      instance.state = workInProgress.memoizedState;
-    }
-
-    var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
-        workInProgress,
-        getDerivedStateFromProps,
-        props
-      );
-      instance.state = workInProgress.memoizedState;
-    }
-
     // In order to support react-lifecycles-compat polyfilled components,
     // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
@@ -6334,19 +6119,18 @@ var ReactFiberClassComponent = function(
       callComponentWillMount(workInProgress, instance);
       // If we had additional state updates during this life-cycle, let's
       // process them now.
-      updateQueue = workInProgress.updateQueue;
+      var updateQueue = workInProgress.updateQueue;
       if (updateQueue !== null) {
-        processUpdateQueue(
+        instance.state = processUpdateQueue(
+          current,
           workInProgress,
           updateQueue,
-          props,
           instance,
+          props,
           renderExpirationTime
         );
-        instance.state = workInProgress.memoizedState;
       }
     }
-
     if (typeof instance.componentDidMount === "function") {
       workInProgress.effectTag |= Update;
     }
@@ -6355,18 +6139,16 @@ var ReactFiberClassComponent = function(
   function resumeMountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
+    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
-    instance.props = oldProps;
-
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
-    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof getDerivedStateFromProps === "function" ||
+      typeof ctor.getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6390,27 +6172,93 @@ var ReactFiberClassComponent = function(
       }
     }
 
+    // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
-    var newState = (instance.state = oldState);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
+    // TODO: Previous state can be null.
+    var newState = void 0;
+    var derivedStateFromCatch = void 0;
+    if (workInProgress.updateQueue !== null) {
+      newState = processUpdateQueue(
+        null,
         workInProgress,
-        updateQueue,
-        newProps,
+        workInProgress.updateQueue,
         instance,
+        newProps,
         renderExpirationTime
       );
-      newState = workInProgress.memoizedState;
+
+      var updateQueue = workInProgress.updateQueue;
+      if (
+        updateQueue !== null &&
+        updateQueue.capturedValues !== null &&
+        enableGetDerivedStateFromCatch &&
+        typeof ctor.getDerivedStateFromCatch === "function"
+      ) {
+        var capturedValues = updateQueue.capturedValues;
+        // Don't remove these from the update queue yet. We need them in
+        // finishClassComponent. Do the reset there.
+        // TODO: This is awkward. Refactor class components.
+        // updateQueue.capturedValues = null;
+        derivedStateFromCatch = callGetDerivedStateFromCatch(
+          ctor,
+          capturedValues
+        );
+      }
+    } else {
+      newState = oldState;
     }
 
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
         workInProgress,
-        getDerivedStateFromProps,
-        newProps
+        instance,
+        newProps,
+        newState
       );
-      newState = workInProgress.memoizedState;
+    }
+
+    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromProps
+          : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue = workInProgress.updateQueue;
+      if (_updateQueue !== null) {
+        _updateQueue.baseState = Object.assign(
+          {},
+          _updateQueue.baseState,
+          derivedStateFromProps
+        );
+      }
+    }
+    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromCatch
+          : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue2 = workInProgress.updateQueue;
+      if (_updateQueue2 !== null) {
+        _updateQueue2.baseState = Object.assign(
+          {},
+          _updateQueue2.baseState,
+          derivedStateFromCatch
+        );
+      }
     }
 
     if (
@@ -6467,9 +6315,9 @@ var ReactFiberClassComponent = function(
       }
 
       // If shouldComponentUpdate returned false, we should still update the
-      // memoized state to indicate that this work can be reused.
-      workInProgress.memoizedProps = newProps;
-      workInProgress.memoizedState = newState;
+      // memoized props/state to indicate that this work can be reused.
+      memoizeProps(workInProgress, newProps);
+      memoizeState(workInProgress, newState);
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6485,18 +6333,16 @@ var ReactFiberClassComponent = function(
   function updateClassInstance(current, workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
+    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
-    instance.props = oldProps;
-
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
-    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof getDerivedStateFromProps === "function" ||
+      typeof ctor.getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6520,27 +6366,94 @@ var ReactFiberClassComponent = function(
       }
     }
 
+    // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
-    var newState = (instance.state = oldState);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
+    // TODO: Previous state can be null.
+    var newState = void 0;
+    var derivedStateFromCatch = void 0;
+
+    if (workInProgress.updateQueue !== null) {
+      newState = processUpdateQueue(
+        current,
         workInProgress,
-        updateQueue,
-        newProps,
+        workInProgress.updateQueue,
         instance,
+        newProps,
         renderExpirationTime
       );
-      newState = workInProgress.memoizedState;
+
+      var updateQueue = workInProgress.updateQueue;
+      if (
+        updateQueue !== null &&
+        updateQueue.capturedValues !== null &&
+        enableGetDerivedStateFromCatch &&
+        typeof ctor.getDerivedStateFromCatch === "function"
+      ) {
+        var capturedValues = updateQueue.capturedValues;
+        // Don't remove these from the update queue yet. We need them in
+        // finishClassComponent. Do the reset there.
+        // TODO: This is awkward. Refactor class components.
+        // updateQueue.capturedValues = null;
+        derivedStateFromCatch = callGetDerivedStateFromCatch(
+          ctor,
+          capturedValues
+        );
+      }
+    } else {
+      newState = oldState;
     }
 
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
         workInProgress,
-        getDerivedStateFromProps,
-        newProps
+        instance,
+        newProps,
+        newState
       );
-      newState = workInProgress.memoizedState;
+    }
+
+    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromProps
+          : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue3 = workInProgress.updateQueue;
+      if (_updateQueue3 !== null) {
+        _updateQueue3.baseState = Object.assign(
+          {},
+          _updateQueue3.baseState,
+          derivedStateFromProps
+        );
+      }
+    }
+    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromCatch
+          : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue4 = workInProgress.updateQueue;
+      if (_updateQueue4 !== null) {
+        _updateQueue4.baseState = Object.assign(
+          {},
+          _updateQueue4.baseState,
+          derivedStateFromCatch
+        );
+      }
     }
 
     if (
@@ -6627,8 +6540,8 @@ var ReactFiberClassComponent = function(
 
       // If shouldComponentUpdate returned false, we should still update the
       // memoized props/state to indicate that this work can be reused.
-      workInProgress.memoizedProps = newProps;
-      workInProgress.memoizedState = newState;
+      memoizeProps(workInProgress, newProps);
+      memoizeState(workInProgress, newState);
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6642,6 +6555,7 @@ var ReactFiberClassComponent = function(
 
   return {
     adoptClassInstance: adoptClassInstance,
+    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: constructClassInstance,
     mountClassInstance: mountClassInstance,
     resumeMountClassInstance: resumeMountClassInstance,
@@ -6649,7 +6563,7 @@ var ReactFiberClassComponent = function(
   };
 };
 
-var getCurrentFiberStackAddendum$2 =
+var getCurrentFiberStackAddendum$1 =
   ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
 
 var didWarnAboutMaps = void 0;
@@ -6688,7 +6602,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
       '"key" prop. See https://fb.me/react-warning-keys for ' +
       "more information." +
-      (getCurrentFiberStackAddendum$2() || "");
+      (getCurrentFiberStackAddendum$1() || "");
     if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
       return;
     }
@@ -6699,7 +6613,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
         '"key" prop. See https://fb.me/react-warning-keys for ' +
         "more information.%s",
-      getCurrentFiberStackAddendum$2()
+      getCurrentFiberStackAddendum$1()
     );
   };
 }
@@ -6796,7 +6710,7 @@ function throwOnInvalidObjectType(returnFiber, newChild) {
       addendum =
         " If you meant to render a collection of children, use an array " +
         "instead." +
-        (getCurrentFiberStackAddendum$2() || "");
+        (getCurrentFiberStackAddendum$1() || "");
     }
     invariant(
       false,
@@ -6814,7 +6728,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
     "you return a Component instead of <Component /> from render. " +
     "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$2() || "");
+    (getCurrentFiberStackAddendum$1() || "");
 
   if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
     return;
@@ -6826,7 +6740,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
       "you return a Component instead of <Component /> from render. " +
       "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$2() || ""
+    getCurrentFiberStackAddendum$1() || ""
   );
 }
 
@@ -6939,12 +6853,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, textContent, expirationTime);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       return existing;
     }
   }
@@ -6954,7 +6868,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // Move based on index
       var existing = useFiber(current, element.props, expirationTime);
       existing.ref = coerceRef(returnFiber, current, element);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       {
         existing._debugSource = element._source;
         existing._debugOwner = element._owner;
@@ -6968,7 +6882,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       created.ref = coerceRef(returnFiber, current, element);
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     }
   }
@@ -6986,12 +6900,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, portal.children || [], expirationTime);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       return existing;
     }
   }
@@ -7005,12 +6919,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         key
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, fragment, expirationTime);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       return existing;
     }
   }
@@ -7025,7 +6939,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     }
 
@@ -7038,7 +6952,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           _created.ref = coerceRef(returnFiber, null, newChild);
-          _created.return = returnFiber;
+          _created["return"] = returnFiber;
           return _created;
         }
         case REACT_PORTAL_TYPE: {
@@ -7047,7 +6961,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             returnFiber.mode,
             expirationTime
           );
-          _created2.return = returnFiber;
+          _created2["return"] = returnFiber;
           return _created2;
         }
       }
@@ -7059,7 +6973,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           null
         );
-        _created3.return = returnFiber;
+        _created3["return"] = returnFiber;
         return _created3;
       }
 
@@ -7270,7 +7184,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               "duplicated and/or omitted — the behavior is unsupported and " +
               "could change in a future version.%s",
             key,
-            getCurrentFiberStackAddendum$2()
+            getCurrentFiberStackAddendum$1()
           );
           break;
         default:
@@ -7415,7 +7329,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren.delete(
+            existingChildren["delete"](
               _newFiber2.key === null ? newIdx : _newFiber2.key
             );
           }
@@ -7468,7 +7382,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                 "Using Maps as children is unsupported and will likely yield " +
                   "unexpected results. Convert it to a sequence/iterable of keyed " +
                   "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$2()
+                getCurrentFiberStackAddendum$1()
               )
             : void 0;
           didWarnAboutMaps = true;
@@ -7594,7 +7508,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren.delete(
+            existingChildren["delete"](
               _newFiber4.key === null ? newIdx : _newFiber4.key
             );
           }
@@ -7633,7 +7547,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // the rest.
       deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
       var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       return existing;
     }
     // The existing first child is not a text node so we need to create one
@@ -7644,7 +7558,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created.return = returnFiber;
+    created["return"] = returnFiber;
     return created;
   }
 
@@ -7674,7 +7588,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           existing.ref = coerceRef(returnFiber, child, element);
-          existing.return = returnFiber;
+          existing["return"] = returnFiber;
           {
             existing._debugSource = element._source;
             existing._debugOwner = element._owner;
@@ -7697,7 +7611,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         element.key
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     } else {
       var _created4 = createFiberFromElement(
@@ -7706,7 +7620,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4.return = returnFiber;
+      _created4["return"] = returnFiber;
       return _created4;
     }
   }
@@ -7730,7 +7644,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         ) {
           deleteRemainingChildren(returnFiber, child.sibling);
           var existing = useFiber(child, portal.children || [], expirationTime);
-          existing.return = returnFiber;
+          existing["return"] = returnFiber;
           return existing;
         } else {
           deleteRemainingChildren(returnFiber, child);
@@ -7747,7 +7661,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created.return = returnFiber;
+    created["return"] = returnFiber;
     return created;
   }
 
@@ -7899,7 +7813,7 @@ function cloneChildFibers(current, workInProgress) {
   );
   workInProgress.child = newChild;
 
-  newChild.return = workInProgress;
+  newChild["return"] = workInProgress;
   while (currentChild.sibling !== null) {
     currentChild = currentChild.sibling;
     newChild = newChild.sibling = createWorkInProgress(
@@ -7907,14 +7821,11 @@ function cloneChildFibers(current, workInProgress) {
       currentChild.pendingProps,
       currentChild.expirationTime
     );
-    newChild.return = workInProgress;
+    newChild["return"] = workInProgress;
   }
   newChild.sibling = null;
 }
 
-var getCurrentFiberStackAddendum =
-  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
-
 var didWarnAboutBadClass = void 0;
 var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
 var didWarnAboutStatelessRefs = void 0;
@@ -7958,6 +7869,8 @@ var ReactFiberBeginWork = function(
       memoizeState
     ),
     adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
+    callGetDerivedStateFromProps =
+      _ReactFiberClassCompo.callGetDerivedStateFromProps,
     constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
     mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
     resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
@@ -8009,20 +7922,9 @@ var ReactFiberBeginWork = function(
 
   function updateForwardRef(current, workInProgress) {
     var render = workInProgress.type.render;
-    var nextProps = workInProgress.pendingProps;
-    var ref = workInProgress.ref;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextProps) {
-      var currentRef = current !== null ? current.ref : null;
-      if (ref === currentRef) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-    }
-    var nextChildren = render(nextProps, ref);
+    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
     reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
+    memoizeProps(workInProgress, nextChildren);
     return workInProgress.child;
   }
 
@@ -8108,11 +8010,7 @@ var ReactFiberBeginWork = function(
     if (current === null) {
       if (workInProgress.stateNode === null) {
         // In the initial pass we might need to construct the instance.
-        constructClassInstance(
-          workInProgress,
-          workInProgress.pendingProps,
-          renderExpirationTime
-        );
+        constructClassInstance(workInProgress, workInProgress.pendingProps);
         mountClassInstance(workInProgress, renderExpirationTime);
 
         shouldUpdate = true;
@@ -8130,11 +8028,22 @@ var ReactFiberBeginWork = function(
         renderExpirationTime
       );
     }
+
+    // We processed the update queue inside updateClassInstance. It may have
+    // included some errors that were dispatched during the commit phase.
+    // TODO: Refactor class components so this is less awkward.
+    var didCaptureError = false;
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null && updateQueue.capturedValues !== null) {
+      shouldUpdate = true;
+      didCaptureError = true;
+    }
     return finishClassComponent(
       current,
       workInProgress,
       shouldUpdate,
       hasContext,
+      didCaptureError,
       renderExpirationTime
     );
   }
@@ -8144,13 +8053,12 @@ var ReactFiberBeginWork = function(
     workInProgress,
     shouldUpdate,
     hasContext,
+    didCaptureError,
     renderExpirationTime
   ) {
     // Refs should update even if shouldComponentUpdate returns false
     markRef(current, workInProgress);
 
-    var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
-
     if (!shouldUpdate && !didCaptureError) {
       // Context providers should defer to sCU for rendering
       if (hasContext) {
@@ -8246,26 +8154,29 @@ var ReactFiberBeginWork = function(
     pushHostRootContext(workInProgress);
     var updateQueue = workInProgress.updateQueue;
     if (updateQueue !== null) {
-      var nextProps = workInProgress.pendingProps;
       var prevState = workInProgress.memoizedState;
-      var prevChildren = prevState !== null ? prevState.element : null;
-      processUpdateQueue(
+      var state = processUpdateQueue(
+        current,
         workInProgress,
         updateQueue,
-        nextProps,
+        null,
         null,
         renderExpirationTime
       );
-      var nextState = workInProgress.memoizedState;
-      // Caution: React DevTools currently depends on this property
-      // being called "element".
-      var nextChildren = nextState.element;
+      memoizeState(workInProgress, state);
+      updateQueue = workInProgress.updateQueue;
 
-      if (nextChildren === prevChildren) {
+      var element = void 0;
+      if (updateQueue !== null && updateQueue.capturedValues !== null) {
+        // There's an uncaught error. Unmount the whole root.
+        element = null;
+      } else if (prevState === state) {
         // If the state is the same as before, that's a bailout because we had
         // no work that expires at this time.
         resetHydrationState();
         return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      } else {
+        element = state.element;
       }
       var root = workInProgress.stateNode;
       if (
@@ -8290,15 +8201,16 @@ var ReactFiberBeginWork = function(
         workInProgress.child = mountChildFibers(
           workInProgress,
           null,
-          nextChildren,
+          element,
           renderExpirationTime
         );
       } else {
         // Otherwise reset hydration state in case we aborted and resumed another
         // root.
         resetHydrationState();
-        reconcileChildren(current, workInProgress, nextChildren);
+        reconcileChildren(current, workInProgress, element);
       }
+      memoizeState(workInProgress, state);
       return workInProgress.child;
     }
     resetHydrationState();
@@ -8434,13 +8346,21 @@ var ReactFiberBeginWork = function(
       workInProgress.memoizedState =
         value.state !== null && value.state !== undefined ? value.state : null;
 
-      var getDerivedStateFromProps = Component.getDerivedStateFromProps;
-      if (typeof getDerivedStateFromProps === "function") {
-        applyDerivedStateFromProps(
+      if (typeof Component.getDerivedStateFromProps === "function") {
+        var partialState = callGetDerivedStateFromProps(
           workInProgress,
-          getDerivedStateFromProps,
-          props
+          value,
+          props,
+          workInProgress.memoizedState
         );
+
+        if (partialState !== null && partialState !== undefined) {
+          workInProgress.memoizedState = Object.assign(
+            {},
+            workInProgress.memoizedState,
+            partialState
+          );
+        }
       }
 
       // Push context providers early to prevent context stack mismatches.
@@ -8454,6 +8374,7 @@ var ReactFiberBeginWork = function(
         workInProgress,
         true,
         hasContext,
+        false,
         renderExpirationTime
       );
     } else {
@@ -8599,7 +8520,7 @@ var ReactFiberBeginWork = function(
     var fiber = workInProgress.child;
     if (fiber !== null) {
       // Set the return pointer of the child to the work-in-progress fiber.
-      fiber.return = workInProgress;
+      fiber["return"] = workInProgress;
     }
     while (fiber !== null) {
       var nextFiber = void 0;
@@ -8637,7 +8558,7 @@ var ReactFiberBeginWork = function(
                 // ancestor path already has sufficient priority.
                 break;
               }
-              node = node.return;
+              node = node["return"];
             }
             // Don't scan deeper than a matching consumer. When we render the
             // consumer, we'll continue scanning from that point. This way the
@@ -8659,7 +8580,7 @@ var ReactFiberBeginWork = function(
       }
       if (nextFiber !== null) {
         // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber.return = fiber;
+        nextFiber["return"] = fiber;
       } else {
         // No child. Traverse to next sibling.
         nextFiber = fiber;
@@ -8671,13 +8592,11 @@ var ReactFiberBeginWork = function(
           }
           var sibling = nextFiber.sibling;
           if (sibling !== null) {
-            // Set the return pointer of the sibling to the work-in-progress fiber.
-            sibling.return = nextFiber.return;
             nextFiber = sibling;
             break;
           }
           // No more siblings. Traverse up.
-          nextFiber = nextFiber.return;
+          nextFiber = nextFiber["return"];
         }
       }
       fiber = nextFiber;
@@ -8694,10 +8613,8 @@ var ReactFiberBeginWork = function(
 
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
-    var canBailOnProps = true;
 
     if (hasLegacyContextChanged()) {
-      canBailOnProps = false;
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (oldProps === newProps) {
@@ -8709,20 +8626,6 @@ var ReactFiberBeginWork = function(
     var newValue = newProps.value;
     workInProgress.memoizedProps = newProps;
 
-    {
-      var providerPropTypes = workInProgress.type.propTypes;
-
-      if (providerPropTypes) {
-        checkPropTypes(
-          providerPropTypes,
-          newProps,
-          "prop",
-          "Context.Provider",
-          getCurrentFiberStackAddendum
-        );
-      }
-    }
-
     var changedBits = void 0;
     if (oldProps === null) {
       // Initial render
@@ -8730,7 +8633,7 @@ var ReactFiberBeginWork = function(
     } else {
       if (oldProps.value === newProps.value) {
         // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children && canBailOnProps) {
+        if (oldProps.children === newProps.children) {
           workInProgress.stateNode = 0;
           pushProvider(workInProgress);
           return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8747,7 +8650,7 @@ var ReactFiberBeginWork = function(
           (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
         ) {
           // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children && canBailOnProps) {
+          if (oldProps.children === newProps.children) {
             workInProgress.stateNode = 0;
             pushProvider(workInProgress);
             return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8772,7 +8675,7 @@ var ReactFiberBeginWork = function(
 
           if (changedBits === 0) {
             // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children && canBailOnProps) {
+            if (oldProps.children === newProps.children) {
               workInProgress.stateNode = 0;
               pushProvider(workInProgress);
               return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8858,8 +8761,6 @@ var ReactFiberBeginWork = function(
     }
 
     var newChildren = render(newValue);
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
     reconcileChildren(current, workInProgress, newChildren);
     return workInProgress.child;
   }
@@ -9067,7 +8968,7 @@ var ReactFiberCompleteWork = function(
   function appendAllReturns(returns, workInProgress) {
     var node = workInProgress.stateNode;
     if (node) {
-      node.return = workInProgress;
+      node["return"] = workInProgress;
     }
     while (node !== null) {
       if (
@@ -9079,17 +8980,17 @@ var ReactFiberCompleteWork = function(
       } else if (node.tag === ReturnComponent) {
         returns.push(node.pendingProps.value);
       } else if (node.child !== null) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === workInProgress) {
+        if (node["return"] === null || node["return"] === workInProgress) {
           return;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -9145,7 +9046,7 @@ var ReactFiberCompleteWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
@@ -9153,12 +9054,12 @@ var ReactFiberCompleteWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === workInProgress) {
+        if (node["return"] === null || node["return"] === workInProgress) {
           return;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -9225,7 +9126,7 @@ var ReactFiberCompleteWork = function(
             // down its children. Instead, we'll get insertions from each child in
             // the portal directly.
           } else if (node.child !== null) {
-            node.child.return = node;
+            node.child["return"] = node;
             node = node.child;
             continue;
           }
@@ -9233,12 +9134,12 @@ var ReactFiberCompleteWork = function(
             return;
           }
           while (node.sibling === null) {
-            if (node.return === null || node.return === workInProgress) {
+            if (node["return"] === null || node["return"] === workInProgress) {
               return;
             }
-            node = node.return;
+            node = node["return"];
           }
-          node.sibling.return = node.return;
+          node.sibling["return"] = node["return"];
           node = node.sibling;
         }
       };
@@ -9364,6 +9265,20 @@ var ReactFiberCompleteWork = function(
       case ClassComponent: {
         // We are leaving this subtree, so pop context if any.
         popLegacyContextProvider(workInProgress);
+
+        // If this component caught an error, schedule an error log effect.
+        var instance = workInProgress.stateNode;
+        var updateQueue = workInProgress.updateQueue;
+        if (updateQueue !== null && updateQueue.capturedValues !== null) {
+          workInProgress.effectTag &= ~DidCapture;
+          if (typeof instance.componentDidCatch === "function") {
+            workInProgress.effectTag |= ErrLog;
+          } else {
+            // Normally we clear this in the commit phase, but since we did not
+            // schedule an effect, we need to reset it here.
+            updateQueue.capturedValues = null;
+          }
+        }
         return null;
       }
       case HostRoot: {
@@ -9383,6 +9298,11 @@ var ReactFiberCompleteWork = function(
           workInProgress.effectTag &= ~Placement;
         }
         updateHostContainer(workInProgress);
+
+        var _updateQueue = workInProgress.updateQueue;
+        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
+          workInProgress.effectTag |= ErrLog;
+        }
         return null;
       }
       case HostComponent: {
@@ -9397,13 +9317,13 @@ var ReactFiberCompleteWork = function(
           // have newProps so we'll have to reuse them.
           // TODO: Split the update API as separate for the props vs. children.
           // Even better would be if children weren't special cased at all tho.
-          var instance = workInProgress.stateNode;
+          var _instance = workInProgress.stateNode;
           var currentHostContext = getHostContext();
           // TODO: Experiencing an error where oldProps is null. Suggests a host
           // component is hitting the resume path. Figure out why. Possibly
           // related to `hidden`.
           var updatePayload = prepareUpdate(
-            instance,
+            _instance,
             type,
             oldProps,
             newProps,
@@ -9457,7 +9377,7 @@ var ReactFiberCompleteWork = function(
               markUpdate(workInProgress);
             }
           } else {
-            var _instance = createInstance(
+            var _instance2 = createInstance(
               type,
               newProps,
               rootContainerInstance,
@@ -9465,14 +9385,14 @@ var ReactFiberCompleteWork = function(
               workInProgress
             );
 
-            appendAllChildren(_instance, workInProgress);
+            appendAllChildren(_instance2, workInProgress);
 
             // Certain renderers require commit-time effects for initial mount.
             // (eg DOM renderer supports auto-focus for certain elements).
             // Make sure such renderers get scheduled for later work.
             if (
               finalizeInitialChildren(
-                _instance,
+                _instance2,
                 type,
                 newProps,
                 rootContainerInstance,
@@ -9481,7 +9401,7 @@ var ReactFiberCompleteWork = function(
             ) {
               markUpdate(workInProgress);
             }
-            workInProgress.stateNode = _instance;
+            workInProgress.stateNode = _instance2;
           }
 
           if (workInProgress.ref !== null) {
@@ -9588,6 +9508,139 @@ function createCapturedValue(value, source) {
   };
 }
 
+var ReactFiberUnwindWork = function(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  isAlreadyFailedLegacyErrorBoundary
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+
+  function throwException(returnFiber, sourceFiber, rawValue) {
+    // The source fiber did not complete.
+    sourceFiber.effectTag |= Incomplete;
+    // Its effect list is no longer valid.
+    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+
+    var value = createCapturedValue(rawValue, sourceFiber);
+
+    var workInProgress = returnFiber;
+    do {
+      switch (workInProgress.tag) {
+        case HostRoot: {
+          // Uncaught error
+          var errorInfo = value;
+          ensureUpdateQueues(workInProgress);
+          var updateQueue = workInProgress.updateQueue;
+          updateQueue.capturedValues = [errorInfo];
+          workInProgress.effectTag |= ShouldCapture;
+          return;
+        }
+        case ClassComponent:
+          // Capture and retry
+          var ctor = workInProgress.type;
+          var _instance = workInProgress.stateNode;
+          if (
+            (workInProgress.effectTag & DidCapture) === NoEffect &&
+            ((typeof ctor.getDerivedStateFromCatch === "function" &&
+              enableGetDerivedStateFromCatch) ||
+              (_instance !== null &&
+                typeof _instance.componentDidCatch === "function" &&
+                !isAlreadyFailedLegacyErrorBoundary(_instance)))
+          ) {
+            ensureUpdateQueues(workInProgress);
+            var _updateQueue = workInProgress.updateQueue;
+            var capturedValues = _updateQueue.capturedValues;
+            if (capturedValues === null) {
+              _updateQueue.capturedValues = [value];
+            } else {
+              capturedValues.push(value);
+            }
+            workInProgress.effectTag |= ShouldCapture;
+            return;
+          }
+          break;
+        default:
+          break;
+      }
+      workInProgress = workInProgress["return"];
+    } while (workInProgress !== null);
+  }
+
+  function unwindWork(workInProgress) {
+    switch (workInProgress.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(workInProgress);
+        var effectTag = workInProgress.effectTag;
+        if (effectTag & ShouldCapture) {
+          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var _effectTag = workInProgress.effectTag;
+        if (_effectTag & ShouldCapture) {
+          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        return null;
+      }
+      case HostPortal:
+        popHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        popProvider(workInProgress);
+        return null;
+      default:
+        return null;
+    }
+  }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      default:
+        break;
+    }
+  }
+
+  return {
+    throwException: throwException,
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork
+  };
+};
+
 // This module is forked in different environments.
 // By default, return `true` to log errors to the console.
 // Forks can return `false` if this isn't desirable.
@@ -9839,14 +9892,7 @@ var ReactFiberCommitWork = function(
         }
         var updateQueue = finishedWork.updateQueue;
         if (updateQueue !== null) {
-          _instance2.props = finishedWork.memoizedProps;
-          _instance2.state = finishedWork.memoizedState;
-          commitUpdateQueue(
-            finishedWork,
-            updateQueue,
-            _instance2,
-            committedExpirationTime
-          );
+          commitCallbacks(updateQueue, _instance2);
         }
         return;
       }
@@ -9864,12 +9910,7 @@ var ReactFiberCommitWork = function(
                 break;
             }
           }
-          commitUpdateQueue(
-            finishedWork,
-            _updateQueue,
-            _instance3,
-            committedExpirationTime
-          );
+          commitCallbacks(_updateQueue, _instance3);
         }
         return;
       }
@@ -9906,17 +9947,81 @@ var ReactFiberCommitWork = function(
     }
   }
 
+  function commitErrorLogging(finishedWork, onUncaughtError) {
+    switch (finishedWork.tag) {
+      case ClassComponent:
+        {
+          var ctor = finishedWork.type;
+          var _instance5 = finishedWork.stateNode;
+          var updateQueue = finishedWork.updateQueue;
+          invariant(
+            updateQueue !== null && updateQueue.capturedValues !== null,
+            "An error logging effect should not have been scheduled if no errors " +
+              "were captured. This error is likely caused by a bug in React. " +
+              "Please file an issue."
+          );
+          var capturedErrors = updateQueue.capturedValues;
+          updateQueue.capturedValues = null;
+
+          if (typeof ctor.getDerivedStateFromCatch !== "function") {
+            // To preserve the preexisting retry behavior of error boundaries,
+            // we keep track of which ones already failed during this batch.
+            // This gets reset before we yield back to the browser.
+            // TODO: Warn in strict mode if getDerivedStateFromCatch is
+            // not defined.
+            markLegacyErrorBoundaryAsFailed(_instance5);
+          }
+
+          _instance5.props = finishedWork.memoizedProps;
+          _instance5.state = finishedWork.memoizedState;
+          for (var i = 0; i < capturedErrors.length; i++) {
+            var errorInfo = capturedErrors[i];
+            var _error = errorInfo.value;
+            var stack = errorInfo.stack;
+            logError(finishedWork, errorInfo);
+            _instance5.componentDidCatch(_error, {
+              componentStack: stack !== null ? stack : ""
+            });
+          }
+        }
+        break;
+      case HostRoot: {
+        var _updateQueue2 = finishedWork.updateQueue;
+        invariant(
+          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
+          "An error logging effect should not have been scheduled if no errors " +
+            "were captured. This error is likely caused by a bug in React. " +
+            "Please file an issue."
+        );
+        var _capturedErrors = _updateQueue2.capturedValues;
+        _updateQueue2.capturedValues = null;
+        for (var _i = 0; _i < _capturedErrors.length; _i++) {
+          var _errorInfo = _capturedErrors[_i];
+          logError(finishedWork, _errorInfo);
+          onUncaughtError(_errorInfo.value);
+        }
+        break;
+      }
+      default:
+        invariant(
+          false,
+          "This unit of work tag cannot capture errors.  This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
+
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (ref !== null) {
-      var _instance5 = finishedWork.stateNode;
+      var _instance6 = finishedWork.stateNode;
       var instanceToUse = void 0;
       switch (finishedWork.tag) {
         case HostComponent:
-          instanceToUse = getPublicInstance(_instance5);
+          instanceToUse = getPublicInstance(_instance6);
           break;
         default:
-          instanceToUse = _instance5;
+          instanceToUse = _instance6;
       }
       if (typeof ref === "function") {
         ref(instanceToUse);
@@ -9960,9 +10065,9 @@ var ReactFiberCommitWork = function(
     switch (current.tag) {
       case ClassComponent: {
         safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if (typeof _instance6.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance6);
+        var _instance7 = current.stateNode;
+        if (typeof _instance7.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance7);
         }
         return;
       }
@@ -10004,7 +10109,7 @@ var ReactFiberCommitWork = function(
         // If we don't use mutation we drill down into portals here instead.
         (!mutation || node.tag !== HostPortal)
       ) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
@@ -10012,12 +10117,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === root) {
+        if (node["return"] === null || node["return"] === root) {
           return;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -10028,11 +10133,11 @@ var ReactFiberCommitWork = function(
     // get GC:ed but we don't know which for sure which parent is the current
     // one so we'll settle for GC:ing the subtree of this child. This child
     // itself will be GC:ed when the parent updates the next time.
-    current.return = null;
+    current["return"] = null;
     current.child = null;
     if (current.alternate) {
       current.alternate.child = null;
-      current.alternate.return = null;
+      current.alternate["return"] = null;
     }
   }
 
@@ -10100,6 +10205,7 @@ var ReactFiberCommitWork = function(
 
         commitLifeCycles: commitLifeCycles,
         commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+        commitErrorLogging: commitErrorLogging,
         commitAttachRef: commitAttachRef,
         commitDetachRef: commitDetachRef
       };
@@ -10121,12 +10227,12 @@ var ReactFiberCommitWork = function(
     removeChildFromContainer = mutation.removeChildFromContainer;
 
   function getHostParentFiber(fiber) {
-    var parent = fiber.return;
+    var parent = fiber["return"];
     while (parent !== null) {
       if (isHostParent(parent)) {
         return parent;
       }
-      parent = parent.return;
+      parent = parent["return"];
     }
     invariant(
       false,
@@ -10151,14 +10257,14 @@ var ReactFiberCommitWork = function(
     siblings: while (true) {
       // If we didn't find anything, let's try the next sibling.
       while (node.sibling === null) {
-        if (node.return === null || isHostParent(node.return)) {
+        if (node["return"] === null || isHostParent(node["return"])) {
           // If we pop out of the root or hit the parent the fiber we are the
           // last sibling.
           return null;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
       while (node.tag !== HostComponent && node.tag !== HostText) {
         // If it is not host node and, we might have a host node inside it.
@@ -10172,7 +10278,7 @@ var ReactFiberCommitWork = function(
         if (node.child === null || node.tag === HostPortal) {
           continue siblings;
         } else {
-          node.child.return = node;
+          node.child["return"] = node;
           node = node.child;
         }
       }
@@ -10240,7 +10346,7 @@ var ReactFiberCommitWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
@@ -10248,12 +10354,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === finishedWork) {
+        if (node["return"] === null || node["return"] === finishedWork) {
           return;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -10270,7 +10376,7 @@ var ReactFiberCommitWork = function(
 
     while (true) {
       if (!currentParentIsValid) {
-        var parent = node.return;
+        var parent = node["return"];
         findParent: while (true) {
           invariant(
             parent !== null,
@@ -10291,7 +10397,7 @@ var ReactFiberCommitWork = function(
               currentParentIsContainer = true;
               break findParent;
           }
-          parent = parent.return;
+          parent = parent["return"];
         }
         currentParentIsValid = true;
       }
@@ -10312,7 +10418,7 @@ var ReactFiberCommitWork = function(
         currentParent = node.stateNode.containerInfo;
         // Visit children because portals might contain host components.
         if (node.child !== null) {
-          node.child.return = node;
+          node.child["return"] = node;
           node = node.child;
           continue;
         }
@@ -10320,7 +10426,7 @@ var ReactFiberCommitWork = function(
         commitUnmount(node);
         // Visit children because we may find more host components below.
         if (node.child !== null) {
-          node.child.return = node;
+          node.child["return"] = node;
           node = node.child;
           continue;
         }
@@ -10329,17 +10435,17 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === current) {
+        if (node["return"] === null || node["return"] === current) {
           return;
         }
-        node = node.return;
+        node = node["return"];
         if (node.tag === HostPortal) {
           // When we go out of the portal, we need to restore the parent.
           // Since we don't keep a stack of them, we will search for it.
           currentParentIsValid = false;
         }
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -10357,8 +10463,8 @@ var ReactFiberCommitWork = function(
         return;
       }
       case HostComponent: {
-        var _instance7 = finishedWork.stateNode;
-        if (_instance7 != null) {
+        var _instance8 = finishedWork.stateNode;
+        if (_instance8 != null) {
           // Commit the work prepared earlier.
           var newProps = finishedWork.memoizedProps;
           // For hydration we reuse the update path but we treat the oldProps
@@ -10371,7 +10477,7 @@ var ReactFiberCommitWork = function(
           finishedWork.updateQueue = null;
           if (updatePayload !== null) {
             commitUpdate(
-              _instance7,
+              _instance8,
               updatePayload,
               type,
               oldProps,
@@ -10422,6 +10528,7 @@ var ReactFiberCommitWork = function(
       commitDeletion: commitDeletion,
       commitWork: commitWork,
       commitLifeCycles: commitLifeCycles,
+      commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
     };
@@ -10430,208 +10537,6 @@ var ReactFiberCommitWork = function(
   }
 };
 
-var ReactFiberUnwindWork = function(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  markLegacyErrorBoundaryAsFailed,
-  isAlreadyFailedLegacyErrorBoundary,
-  onUncaughtError
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-
-  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
-    var update = createUpdate(expirationTime);
-    // Unmount the root by rendering null.
-    update.tag = CaptureUpdate;
-    // Caution: React DevTools currently depends on this property
-    // being called "element".
-    update.payload = { element: null };
-    var error = errorInfo.value;
-    update.callback = function() {
-      onUncaughtError(error);
-      logError(fiber, errorInfo);
-    };
-    return update;
-  }
-
-  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
-    var update = createUpdate(expirationTime);
-    update.tag = CaptureUpdate;
-    var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
-    if (
-      enableGetDerivedStateFromCatch &&
-      typeof getDerivedStateFromCatch === "function"
-    ) {
-      var _error = errorInfo.value;
-      update.payload = function() {
-        return getDerivedStateFromCatch(_error);
-      };
-    }
-
-    var inst = fiber.stateNode;
-    if (inst !== null && typeof inst.componentDidCatch === "function") {
-      update.callback = function callback() {
-        if (
-          !enableGetDerivedStateFromCatch ||
-          getDerivedStateFromCatch !== "function"
-        ) {
-          // To preserve the preexisting retry behavior of error boundaries,
-          // we keep track of which ones already failed during this batch.
-          // This gets reset before we yield back to the browser.
-          // TODO: Warn in strict mode if getDerivedStateFromCatch is
-          // not defined.
-          markLegacyErrorBoundaryAsFailed(this);
-        }
-        var error = errorInfo.value;
-        var stack = errorInfo.stack;
-        logError(fiber, errorInfo);
-        this.componentDidCatch(error, {
-          componentStack: stack !== null ? stack : ""
-        });
-      };
-    }
-    return update;
-  }
-
-  function throwException(
-    returnFiber,
-    sourceFiber,
-    rawValue,
-    renderExpirationTime
-  ) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-
-    var value = createCapturedValue(rawValue, sourceFiber);
-
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          var _errorInfo = value;
-          workInProgress.effectTag |= ShouldCapture;
-          var update = createRootErrorUpdate(
-            workInProgress,
-            _errorInfo,
-            renderExpirationTime
-          );
-          enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
-          return;
-        }
-        case ClassComponent:
-          // Capture and retry
-          var errorInfo = value;
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
-          if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            workInProgress.effectTag |= ShouldCapture;
-            // Schedule the error boundary to re-render using updated state
-            var _update = createClassErrorUpdate(
-              workInProgress,
-              errorInfo,
-              renderExpirationTime
-            );
-            enqueueCapturedUpdate(
-              workInProgress,
-              _update,
-              renderExpirationTime
-            );
-            return;
-          }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress.return;
-    } while (workInProgress !== null);
-  }
-
-  function unwindWork(workInProgress) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
-    }
-  }
-
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      default:
-        break;
-    }
-  }
-
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork,
-    createRootErrorUpdate: createRootErrorUpdate,
-    createClassErrorUpdate: createClassErrorUpdate
-  };
-};
-
 var NO_CONTEXT = {};
 
 var ReactFiberHostContext = function(config, stack) {
@@ -10816,7 +10721,7 @@ var ReactFiberHydrationContext = function(config) {
 
     var childToDelete = createFiberFromHostInstanceForDeletion();
     childToDelete.stateNode = instance;
-    childToDelete.return = returnFiber;
+    childToDelete["return"] = returnFiber;
     childToDelete.effectTag = Deletion;
 
     // This might seem like it belongs on progressedFirstDeletion. However,
@@ -11014,13 +10919,13 @@ var ReactFiberHydrationContext = function(config) {
   }
 
   function popToNextHostParent(fiber) {
-    var parent = fiber.return;
+    var parent = fiber["return"];
     while (
       parent !== null &&
       parent.tag !== HostComponent &&
       parent.tag !== HostRoot
     ) {
-      parent = parent.return;
+      parent = parent["return"];
     }
     hydrationParentFiber = parent;
   }
@@ -11342,7 +11247,7 @@ var ReactFiberLegacyContext = function(stack) {
       if (isContextProvider(node)) {
         return node.stateNode.__reactInternalMemoizedMergedChildContext;
       }
-      var parent = node.return;
+      var parent = node["return"];
       invariant(
         parent,
         "Found unexpected detached subtree parent. " +
@@ -11615,15 +11520,11 @@ var ReactFiberScheduler = function(config) {
       legacyContext,
       newContext,
       scheduleWork,
-      markLegacyErrorBoundaryAsFailed,
-      isAlreadyFailedLegacyErrorBoundary,
-      onUncaughtError
+      isAlreadyFailedLegacyErrorBoundary
     ),
     throwException = _ReactFiberUnwindWork.throwException,
     unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork,
-    createRootErrorUpdate = _ReactFiberUnwindWork.createRootErrorUpdate,
-    createClassErrorUpdate = _ReactFiberUnwindWork.createClassErrorUpdate;
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
 
   var _ReactFiberCommitWork = ReactFiberCommitWork(
       config,
@@ -11640,6 +11541,7 @@ var ReactFiberScheduler = function(config) {
     commitDeletion = _ReactFiberCommitWork.commitDeletion,
     commitWork = _ReactFiberCommitWork.commitWork,
     commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
+    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
     commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
     commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
 
@@ -11737,10 +11639,10 @@ var ReactFiberScheduler = function(config) {
 
   function resetStack() {
     if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork.return;
+      var interruptedWork = nextUnitOfWork["return"];
       while (interruptedWork !== null) {
         unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork.return;
+        interruptedWork = interruptedWork["return"];
       }
     }
 
@@ -11865,6 +11767,10 @@ var ReactFiberScheduler = function(config) {
         );
       }
 
+      if (effectTag & ErrLog) {
+        commitErrorLogging(nextEffect, onUncaughtError);
+      }
+
       if (effectTag & Ref) {
         recordEffect();
         commitAttachRef(nextEffect);
@@ -12071,16 +11977,7 @@ var ReactFiberScheduler = function(config) {
     }
 
     // Check for pending updates.
-    var newExpirationTime = NoWork;
-    switch (workInProgress.tag) {
-      case HostRoot:
-      case ClassComponent: {
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null) {
-          newExpirationTime = updateQueue.expirationTime;
-        }
-      }
-    }
+    var newExpirationTime = getUpdateExpirationTime(workInProgress);
 
     // TODO: Calls need to visit stateNode
 
@@ -12113,7 +12010,7 @@ var ReactFiberScheduler = function(config) {
         ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
       }
 
-      var returnFiber = workInProgress.return;
+      var returnFiber = workInProgress["return"];
       var siblingFiber = workInProgress.sibling;
 
       if ((workInProgress.effectTag & Incomplete) === NoEffect) {
@@ -12355,19 +12252,13 @@ var ReactFiberScheduler = function(config) {
           break;
         }
 
-        {
-          // Reset global debug state
-          // We assume this is defined in DEV
-          resetCurrentlyProcessingQueue();
-        }
-
         if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
           replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
         }
 
         var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber.return;
+        var returnFiber = sourceFiber["return"];
         if (returnFiber === null) {
           // This is the root. The root could capture its own errors. However,
           // we don't know if it errors before or after we pushed the host
@@ -12379,12 +12270,7 @@ var ReactFiberScheduler = function(config) {
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(
-          returnFiber,
-          sourceFiber,
-          thrownValue,
-          nextRenderExpirationTime
-        );
+        throwException(returnFiber, sourceFiber, thrownValue);
         nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
       break;
@@ -12432,13 +12318,31 @@ var ReactFiberScheduler = function(config) {
     }
   }
 
+  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
+    // TODO: We only support dispatching errors.
+    var capturedValue = createCapturedValue(value, sourceFiber);
+    var update = {
+      expirationTime: expirationTime,
+      partialState: null,
+      callback: null,
+      isReplace: false,
+      isForced: false,
+      capturedValue: capturedValue,
+      next: null
+    };
+    insertUpdateIntoFiber(boundaryFiber, update);
+    scheduleWork(boundaryFiber, expirationTime);
+  }
+
   function dispatch(sourceFiber, value, expirationTime) {
     invariant(
       !isWorking || isCommitting,
       "dispatch: Cannot dispatch during the render phase."
     );
 
-    var fiber = sourceFiber.return;
+    // TODO: Handle arrays
+
+    var fiber = sourceFiber["return"];
     while (fiber !== null) {
       switch (fiber.tag) {
         case ClassComponent:
@@ -12449,44 +12353,22 @@ var ReactFiberScheduler = function(config) {
             (typeof instance.componentDidCatch === "function" &&
               !isAlreadyFailedLegacyErrorBoundary(instance))
           ) {
-            var errorInfo = createCapturedValue(value, sourceFiber);
-            var update = createClassErrorUpdate(
-              fiber,
-              errorInfo,
-              expirationTime
-            );
-            enqueueUpdate(fiber, update, expirationTime);
-            scheduleWork(fiber, expirationTime);
+            scheduleCapture(sourceFiber, fiber, value, expirationTime);
             return;
           }
           break;
-        case HostRoot: {
-          var _errorInfo = createCapturedValue(value, sourceFiber);
-          var _update = createRootErrorUpdate(
-            fiber,
-            _errorInfo,
-            expirationTime
-          );
-          enqueueUpdate(fiber, _update, expirationTime);
-          scheduleWork(fiber, expirationTime);
+        // TODO: Handle async boundaries
+        case HostRoot:
+          scheduleCapture(sourceFiber, fiber, value, expirationTime);
           return;
-        }
       }
-      fiber = fiber.return;
+      fiber = fiber["return"];
     }
 
     if (sourceFiber.tag === HostRoot) {
       // Error was thrown at the root. There is no parent, so the root
       // itself should capture it.
-      var rootFiber = sourceFiber;
-      var _errorInfo2 = createCapturedValue(value, rootFiber);
-      var _update2 = createRootErrorUpdate(
-        rootFiber,
-        _errorInfo2,
-        expirationTime
-      );
-      enqueueUpdate(rootFiber, _update2, expirationTime);
-      scheduleWork(rootFiber, expirationTime);
+      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
     }
   }
 
@@ -12614,7 +12496,7 @@ var ReactFiberScheduler = function(config) {
           node.alternate.expirationTime = expirationTime;
         }
       }
-      if (node.return === null) {
+      if (node["return"] === null) {
         if (node.tag === HostRoot) {
           var root = node.stateNode;
           if (
@@ -12655,7 +12537,7 @@ var ReactFiberScheduler = function(config) {
           return;
         }
       }
-      node = node.return;
+      node = node["return"];
     }
   }
 
@@ -13284,14 +13166,9 @@ var ReactFiberReconciler$1 = function(config) {
       }
     }
 
-    var update = createUpdate(expirationTime);
-    // Caution: React DevTools currently depends on this property
-    // being called "element".
-    update.payload = { element: element };
-
     callback = callback === undefined ? null : callback;
-    if (callback !== null) {
-      !(typeof callback === "function")
+    {
+      !(callback === null || typeof callback === "function")
         ? warning(
             false,
             "render(...): Expected the last optional `callback` argument to be a " +
@@ -13299,11 +13176,20 @@ var ReactFiberReconciler$1 = function(config) {
             callback
           )
         : void 0;
-      update.callback = callback;
     }
-    enqueueUpdate(current, update, expirationTime);
 
+    var update = {
+      expirationTime: expirationTime,
+      partialState: { element: element },
+      callback: callback,
+      isReplace: false,
+      isForced: false,
+      capturedValue: null,
+      next: null
+    };
+    insertUpdateIntoFiber(current, update);
     scheduleWork(current, expirationTime);
+
     return expirationTime;
   }
 
@@ -13481,8 +13367,8 @@ var ReactFiberReconciler$3 =
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3.default
-  ? ReactFiberReconciler$3.default
+var reactReconciler = ReactFiberReconciler$3["default"]
+  ? ReactFiberReconciler$3["default"]
   : ReactFiberReconciler$3;
 
 function _classCallCheck$1(instance, Constructor) {
@@ -13909,7 +13795,7 @@ var ReactFabric = {
     if (root) {
       // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
       ReactFabricRenderer.updateContainer(null, root, null, function() {
-        roots.delete(containerTag);
+        roots["delete"](containerTag);
       });
     }
   },
@@ -13966,7 +13852,9 @@ var ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var fabric = ReactFabric$3.default ? ReactFabric$3.default : ReactFabric$3;
+var fabric = ReactFabric$3["default"]
+  ? ReactFabric$3["default"]
+  : ReactFabric$3;
 
 module.exports = fabric;
 
diff --git a/Libraries/Renderer/oss/ReactFabric-prod.js b/Libraries/Renderer/oss/ReactFabric-prod.js
index 32b02cc83875..19ca0dde9e33 100644
--- a/Libraries/Renderer/oss/ReactFabric-prod.js
+++ b/Libraries/Renderer/oss/ReactFabric-prod.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactFabric-prod
  * @preventMunge
  */
 
@@ -211,7 +210,7 @@ function getListener(inst, registrationName) {
   return listener;
 }
 function getParent(inst) {
-  do inst = inst.return;
+  do inst = inst["return"];
   while (inst && 5 !== inst.tag);
   return inst ? inst : null;
 }
@@ -918,17 +917,21 @@ injection.injectEventPluginsByName({
   ResponderEventPlugin: ResponderEventPlugin,
   ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
 });
-var hasSymbol = "function" === typeof Symbol && Symbol.for,
-  REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 60105,
-  REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
-  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
-  REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
-  REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
-  REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
-  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
-  REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for("react.forward_ref") : 60112,
+var hasSymbol = "function" === typeof Symbol && Symbol["for"],
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
+  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
+  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol
+    ? Symbol["for"]("react.strict_mode")
+    : 60108,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol
+    ? Symbol["for"]("react.forward_ref")
+    : 60112,
   MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
 function getIteratorFn(maybeIterable) {
   if (null === maybeIterable || "undefined" === typeof maybeIterable)
@@ -1250,11 +1253,11 @@ function getComponentName(fiber) {
 }
 function isFiberMountedImpl(fiber) {
   var node = fiber;
-  if (fiber.alternate) for (; node.return; ) node = node.return;
+  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
   else {
     if (0 !== (node.effectTag & 2)) return 1;
-    for (; node.return; )
-      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
+    for (; node["return"]; )
+      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
   }
   return 3 === node.tag ? 2 : 3;
 }
@@ -1281,7 +1284,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       1 === alternate ? null : fiber
     );
   for (var a = fiber, b = alternate; ; ) {
-    var parentA = a.return,
+    var parentA = a["return"],
       parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) break;
     if (parentA.child === parentB.child) {
@@ -1292,7 +1295,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       }
       invariant(!1, "Unable to find node on an unmounted component.");
     }
-    if (a.return !== b.return) (a = parentA), (b = parentB);
+    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
     else {
       child = !1;
       for (var _child = parentA.child; _child; ) {
@@ -1345,14 +1348,14 @@ function findCurrentHostFiber(parent) {
   if (!parent) return null;
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child.return = node), (node = node.child);
+    if (node.child) (node.child["return"] = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node.return || node.return === parent) return null;
-        node = node.return;
+        if (!node["return"] || node["return"] === parent) return null;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -1364,14 +1367,14 @@ function findCurrentHostFiberWithNoPortals(parent) {
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
     if (node.child && 4 !== node.tag)
-      (node.child.return = node), (node = node.child);
+      (node.child["return"] = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node.return || node.return === parent) return null;
-        node = node.return;
+        if (!node["return"] || node["return"] === parent) return null;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -1380,7 +1383,8 @@ function findCurrentHostFiberWithNoPortals(parent) {
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
   this.key = key;
-  this.sibling = this.child = this.return = this.stateNode = this.type = null;
+  this.stateNode = this.type = null;
+  this.sibling = this.child = this["return"] = null;
   this.index = 0;
   this.ref = null;
   this.pendingProps = pendingProps;
@@ -1571,289 +1575,171 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
         JSCompiler_inline_result = "";
     }
     info += JSCompiler_inline_result;
-    workInProgress = workInProgress.return;
+    workInProgress = workInProgress["return"];
   } while (workInProgress);
   return info;
 }
 new Set();
 function createUpdateQueue(baseState) {
   return {
-    expirationTime: 0,
     baseState: baseState,
-    firstUpdate: null,
-    lastUpdate: null,
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
-    firstEffect: null,
-    lastEffect: null,
-    firstCapturedEffect: null,
-    lastCapturedEffect: null,
-    hasForceUpdate: !1
-  };
-}
-function cloneUpdateQueue(currentQueue) {
-  return {
-    expirationTime: currentQueue.expirationTime,
-    baseState: currentQueue.baseState,
-    firstUpdate: currentQueue.firstUpdate,
-    lastUpdate: currentQueue.lastUpdate,
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
+    expirationTime: 0,
+    first: null,
+    last: null,
+    callbackList: null,
     hasForceUpdate: !1,
-    firstEffect: null,
-    lastEffect: null,
-    firstCapturedEffect: null,
-    lastCapturedEffect: null
-  };
-}
-function createUpdate(expirationTime) {
-  return {
-    expirationTime: expirationTime,
-    tag: 0,
-    payload: null,
-    callback: null,
-    next: null,
-    nextEffect: null
+    isInitialized: !1,
+    capturedValues: null
   };
 }
-function appendUpdateToQueue(queue, update, expirationTime) {
-  null === queue.lastUpdate
-    ? (queue.firstUpdate = queue.lastUpdate = update)
-    : ((queue.lastUpdate.next = update), (queue.lastUpdate = update));
-  if (0 === queue.expirationTime || queue.expirationTime > expirationTime)
-    queue.expirationTime = expirationTime;
-}
-function enqueueUpdate(fiber, update, expirationTime) {
-  var alternate = fiber.alternate;
-  if (null === alternate) {
-    var queue1 = fiber.updateQueue;
-    var queue2 = null;
-    null === queue1 &&
-      (queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState));
-  } else
-    (queue1 = fiber.updateQueue),
-      (queue2 = alternate.updateQueue),
-      null === queue1
-        ? null === queue2
-          ? ((queue1 = fiber.updateQueue = createUpdateQueue(
-              fiber.memoizedState
-            )),
-            (queue2 = alternate.updateQueue = createUpdateQueue(
-              alternate.memoizedState
-            )))
-          : (queue1 = fiber.updateQueue = cloneUpdateQueue(queue2))
-        : null === queue2 &&
-          (queue2 = alternate.updateQueue = cloneUpdateQueue(queue1));
-  null === queue2 || queue1 === queue2
-    ? appendUpdateToQueue(queue1, update, expirationTime)
-    : null === queue1.lastUpdate || null === queue2.lastUpdate
-      ? (appendUpdateToQueue(queue1, update, expirationTime),
-        appendUpdateToQueue(queue2, update, expirationTime))
-      : (appendUpdateToQueue(queue1, update, expirationTime),
-        (queue2.lastUpdate = update));
-}
-function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
-  var workInProgressQueue = workInProgress.updateQueue;
-  workInProgressQueue =
-    null === workInProgressQueue
-      ? (workInProgress.updateQueue = createUpdateQueue(
-          workInProgress.memoizedState
-        ))
-      : ensureWorkInProgressQueueIsAClone(workInProgress, workInProgressQueue);
-  null === workInProgressQueue.lastCapturedUpdate
-    ? (workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update)
-    : ((workInProgressQueue.lastCapturedUpdate.next = update),
-      (workInProgressQueue.lastCapturedUpdate = update));
+function insertUpdateIntoQueue(queue, update) {
+  null === queue.last
+    ? (queue.first = queue.last = update)
+    : ((queue.last.next = update), (queue.last = update));
   if (
-    0 === workInProgressQueue.expirationTime ||
-    workInProgressQueue.expirationTime > renderExpirationTime
+    0 === queue.expirationTime ||
+    queue.expirationTime > update.expirationTime
   )
-    workInProgressQueue.expirationTime = renderExpirationTime;
+    queue.expirationTime = update.expirationTime;
 }
-function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
-  var current = workInProgress.alternate;
-  null !== current &&
-    queue === current.updateQueue &&
-    (queue = workInProgress.updateQueue = cloneUpdateQueue(queue));
-  return queue;
+var q1 = void 0,
+  q2 = void 0;
+function ensureUpdateQueues(fiber) {
+  q1 = q2 = null;
+  var alternateFiber = fiber.alternate,
+    queue1 = fiber.updateQueue;
+  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
+  null !== alternateFiber
+    ? ((fiber = alternateFiber.updateQueue),
+      null === fiber &&
+        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
+    : (fiber = null);
+  q1 = queue1;
+  q2 = fiber !== queue1 ? fiber : null;
 }
-function getStateFromUpdate(
-  workInProgress,
-  queue,
-  update,
-  prevState,
-  nextProps,
-  instance
-) {
-  switch (update.tag) {
-    case 1:
-      return (
-        (workInProgress = update.payload),
-        "function" === typeof workInProgress
-          ? workInProgress.call(instance, prevState, nextProps)
-          : workInProgress
-      );
-    case 3:
-      workInProgress.effectTag = (workInProgress.effectTag & -1025) | 64;
-    case 0:
-      workInProgress = update.payload;
-      nextProps =
-        "function" === typeof workInProgress
-          ? workInProgress.call(instance, prevState, nextProps)
-          : workInProgress;
-      if (null === nextProps || void 0 === nextProps) break;
-      return Object.assign({}, prevState, nextProps);
-    case 2:
-      queue.hasForceUpdate = !0;
-  }
-  return prevState;
+function insertUpdateIntoFiber(fiber, update) {
+  ensureUpdateQueues(fiber);
+  fiber = q1;
+  var queue2 = q2;
+  null === queue2
+    ? insertUpdateIntoQueue(fiber, update)
+    : null === fiber.last || null === queue2.last
+      ? (insertUpdateIntoQueue(fiber, update),
+        insertUpdateIntoQueue(queue2, update))
+      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
+}
+function getStateFromUpdate(update, instance, prevState, props) {
+  update = update.partialState;
+  return "function" === typeof update
+    ? update.call(instance, prevState, props)
+    : update;
 }
 function processUpdateQueue(
+  current,
   workInProgress,
   queue,
-  props,
   instance,
+  props,
   renderExpirationTime
 ) {
-  if (
-    !(0 === queue.expirationTime || queue.expirationTime > renderExpirationTime)
-  ) {
-    queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
-    for (
-      var newBaseState = queue.baseState,
-        newFirstUpdate = null,
-        newExpirationTime = 0,
-        update = queue.firstUpdate,
-        resultState = newBaseState;
-      null !== update;
-
-    ) {
-      var updateExpirationTime = update.expirationTime;
-      if (updateExpirationTime > renderExpirationTime) {
-        if (
-          (null === newFirstUpdate &&
-            ((newFirstUpdate = update), (newBaseState = resultState)),
-          0 === newExpirationTime || newExpirationTime > updateExpirationTime)
-        )
-          newExpirationTime = updateExpirationTime;
-      } else
-        (resultState = getStateFromUpdate(
-          workInProgress,
-          queue,
-          update,
-          resultState,
-          props,
-          instance
-        )),
-          null !== update.callback &&
-            ((workInProgress.effectTag |= 32),
-            (update.nextEffect = null),
-            null === queue.lastEffect
-              ? (queue.firstEffect = queue.lastEffect = update)
-              : ((queue.lastEffect.nextEffect = update),
-                (queue.lastEffect = update)));
-      update = update.next;
-    }
-    updateExpirationTime = null;
-    for (update = queue.firstCapturedUpdate; null !== update; ) {
-      var _updateExpirationTime = update.expirationTime;
-      if (_updateExpirationTime > renderExpirationTime) {
-        if (
-          (null === updateExpirationTime &&
-            ((updateExpirationTime = update),
-            null === newFirstUpdate && (newBaseState = resultState)),
-          0 === newExpirationTime || newExpirationTime > _updateExpirationTime)
-        )
-          newExpirationTime = _updateExpirationTime;
-      } else
-        (resultState = getStateFromUpdate(
-          workInProgress,
-          queue,
-          update,
-          resultState,
-          props,
-          instance
-        )),
-          null !== update.callback &&
-            ((workInProgress.effectTag |= 32),
-            (update.nextEffect = null),
-            null === queue.lastCapturedEffect
-              ? (queue.firstCapturedEffect = queue.lastCapturedEffect = update)
-              : ((queue.lastCapturedEffect.nextEffect = update),
-                (queue.lastCapturedEffect = update)));
-      update = update.next;
-    }
-    null === newFirstUpdate && (queue.lastUpdate = null);
-    null === updateExpirationTime
-      ? (queue.lastCapturedUpdate = null)
-      : (workInProgress.effectTag |= 32);
-    null === newFirstUpdate &&
-      null === updateExpirationTime &&
-      (newBaseState = resultState);
-    queue.baseState = newBaseState;
-    queue.firstUpdate = newFirstUpdate;
-    queue.firstCapturedUpdate = updateExpirationTime;
-    queue.expirationTime = newExpirationTime;
-    workInProgress.memoizedState = resultState;
-  }
-}
-function callCallback(callback, context) {
-  invariant(
-    "function" === typeof callback,
-    "Invalid argument passed as callback. Expected a function. Instead received: %s",
-    callback
-  );
-  callback.call(context);
-}
-function commitUpdateQueue(finishedWork, finishedQueue, instance) {
-  null !== finishedQueue.firstCapturedUpdate &&
-    (null !== finishedQueue.lastUpdate &&
-      ((finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate),
-      (finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate)),
-    (finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null));
-  finishedWork = finishedQueue.firstEffect;
+  null !== current &&
+    current.updateQueue === queue &&
+    (queue = workInProgress.updateQueue = {
+      baseState: queue.baseState,
+      expirationTime: queue.expirationTime,
+      first: queue.first,
+      last: queue.last,
+      isInitialized: queue.isInitialized,
+      capturedValues: queue.capturedValues,
+      callbackList: null,
+      hasForceUpdate: !1
+    });
+  queue.expirationTime = 0;
+  queue.isInitialized
+    ? (current = queue.baseState)
+    : ((current = queue.baseState = workInProgress.memoizedState),
+      (queue.isInitialized = !0));
   for (
-    finishedQueue.firstEffect = finishedQueue.lastEffect = null;
-    null !== finishedWork;
+    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
+    null !== update;
 
   ) {
-    var _callback3 = finishedWork.callback;
-    null !== _callback3 &&
-      ((finishedWork.callback = null), callCallback(_callback3, instance));
-    finishedWork = finishedWork.nextEffect;
+    var updateExpirationTime = update.expirationTime;
+    if (updateExpirationTime > renderExpirationTime) {
+      var remainingExpirationTime = queue.expirationTime;
+      if (
+        0 === remainingExpirationTime ||
+        remainingExpirationTime > updateExpirationTime
+      )
+        queue.expirationTime = updateExpirationTime;
+      didSkip || ((didSkip = !0), (queue.baseState = current));
+    } else {
+      didSkip ||
+        ((queue.first = update.next),
+        null === queue.first && (queue.last = null));
+      if (update.isReplace)
+        (current = getStateFromUpdate(update, instance, current, props)),
+          (dontMutatePrevState = !0);
+      else if (
+        (updateExpirationTime = getStateFromUpdate(
+          update,
+          instance,
+          current,
+          props
+        ))
+      )
+        (current = dontMutatePrevState
+          ? Object.assign({}, current, updateExpirationTime)
+          : Object.assign(current, updateExpirationTime)),
+          (dontMutatePrevState = !1);
+      update.isForced && (queue.hasForceUpdate = !0);
+      null !== update.callback &&
+        ((updateExpirationTime = queue.callbackList),
+        null === updateExpirationTime &&
+          (updateExpirationTime = queue.callbackList = []),
+        updateExpirationTime.push(update));
+      null !== update.capturedValue &&
+        ((updateExpirationTime = queue.capturedValues),
+        null === updateExpirationTime
+          ? (queue.capturedValues = [update.capturedValue])
+          : updateExpirationTime.push(update.capturedValue));
+    }
+    update = update.next;
   }
-  finishedWork = finishedQueue.firstCapturedEffect;
-  for (
-    finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
-    null !== finishedWork;
-
-  )
-    (finishedQueue = finishedWork.callback),
-      null !== finishedQueue &&
-        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
-      (finishedWork = finishedWork.nextEffect);
+  null !== queue.callbackList
+    ? (workInProgress.effectTag |= 32)
+    : null !== queue.first ||
+      queue.hasForceUpdate ||
+      null !== queue.capturedValues ||
+      (workInProgress.updateQueue = null);
+  didSkip || (queue.baseState = current);
+  return current;
 }
-function applyDerivedStateFromProps(
-  workInProgress,
-  getDerivedStateFromProps,
-  nextProps
-) {
-  var prevState = workInProgress.memoizedState;
-  getDerivedStateFromProps = getDerivedStateFromProps(nextProps, prevState);
-  prevState =
-    null === getDerivedStateFromProps || void 0 === getDerivedStateFromProps
-      ? prevState
-      : Object.assign({}, prevState, getDerivedStateFromProps);
-  workInProgress.memoizedState = prevState;
-  workInProgress = workInProgress.updateQueue;
-  null !== workInProgress &&
-    0 === workInProgress.expirationTime &&
-    (workInProgress.baseState = prevState);
+function commitCallbacks(queue, context) {
+  var callbackList = queue.callbackList;
+  if (null !== callbackList)
+    for (
+      queue.callbackList = null, queue = 0;
+      queue < callbackList.length;
+      queue++
+    ) {
+      var update = callbackList[queue],
+        _callback = update.callback;
+      update.callback = null;
+      invariant(
+        "function" === typeof _callback,
+        "Invalid argument passed as callback. Expected a function. Instead received: %s",
+        _callback
+      );
+      _callback.call(context);
+    }
 }
 function ReactFiberClassComponent(
   legacyContext,
   scheduleWork,
-  computeExpirationForFiber
+  computeExpirationForFiber,
+  memoizeProps,
+  memoizeState
 ) {
   function checkShouldComponentUpdate(
     workInProgress,
@@ -1864,8 +1750,9 @@ function ReactFiberClassComponent(
     newContext
   ) {
     if (
-      null !== workInProgress.updateQueue &&
-      workInProgress.updateQueue.hasForceUpdate
+      null === oldProps ||
+      (null !== workInProgress.updateQueue &&
+        workInProgress.updateQueue.hasForceUpdate)
     )
       return !0;
     var instance = workInProgress.stateNode;
@@ -1878,7 +1765,7 @@ function ReactFiberClassComponent(
         : !0;
   }
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = classComponentUpdater;
+    instance.updater = updater;
     workInProgress.stateNode = instance;
     instance._reactInternalFiber = workInProgress;
   }
@@ -1894,52 +1781,78 @@ function ReactFiberClassComponent(
     "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
       instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
     instance.state !== workInProgress &&
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+      updater.enqueueReplaceState(instance, instance.state, null);
+  }
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    workInProgress = workInProgress.type;
+    if ("function" === typeof workInProgress.getDerivedStateFromProps)
+      return workInProgress.getDerivedStateFromProps.call(
+        null,
+        nextProps,
+        prevState
+      );
   }
   var cacheContext = legacyContext.cacheContext,
     getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged,
-    classComponentUpdater = {
+    updater = {
       isMounted: isMounted,
-      enqueueSetState: function(inst, payload, callback) {
-        inst = inst._reactInternalFiber;
-        var expirationTime = computeExpirationForFiber(inst),
-          update = createUpdate(expirationTime);
-        update.payload = payload;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, expirationTime);
-        scheduleWork(inst, expirationTime);
+      enqueueSetState: function(instance, partialState, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: partialState,
+          callback: callback,
+          isReplace: !1,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
       },
-      enqueueReplaceState: function(inst, payload, callback) {
-        inst = inst._reactInternalFiber;
-        var expirationTime = computeExpirationForFiber(inst),
-          update = createUpdate(expirationTime);
-        update.tag = 1;
-        update.payload = payload;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, expirationTime);
-        scheduleWork(inst, expirationTime);
+      enqueueReplaceState: function(instance, state, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: state,
+          callback: callback,
+          isReplace: !0,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
       },
-      enqueueForceUpdate: function(inst, callback) {
-        inst = inst._reactInternalFiber;
-        var expirationTime = computeExpirationForFiber(inst),
-          update = createUpdate(expirationTime);
-        update.tag = 2;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, expirationTime);
-        scheduleWork(inst, expirationTime);
+      enqueueForceUpdate: function(instance, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: null,
+          callback: callback,
+          isReplace: !1,
+          isForced: !0,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
       }
     };
   return {
     adoptClassInstance: adoptClassInstance,
+    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: function(workInProgress, props) {
       var ctor = workInProgress.type,
         unmaskedContext = getUnmaskedContext(workInProgress),
@@ -1947,15 +1860,25 @@ function ReactFiberClassComponent(
         context = needsContext
           ? getMaskedContext(workInProgress, unmaskedContext)
           : emptyObject;
-      props = new ctor(props, context);
-      workInProgress.memoizedState =
-        null !== props.state && void 0 !== props.state ? props.state : null;
-      adoptClassInstance(workInProgress, props);
+      ctor = new ctor(props, context);
+      var state =
+        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
+      adoptClassInstance(workInProgress, ctor);
+      workInProgress.memoizedState = state;
+      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
+      null !== props &&
+        void 0 !== props &&
+        (workInProgress.memoizedState = Object.assign(
+          {},
+          workInProgress.memoizedState,
+          props
+        ));
       needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return props;
+      return ctor;
     },
     mountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
+        current = workInProgress.alternate,
         instance = workInProgress.stateNode,
         props = workInProgress.pendingProps,
         unmaskedContext = getUnmaskedContext(workInProgress);
@@ -1963,20 +1886,6 @@ function ReactFiberClassComponent(
       instance.state = workInProgress.memoizedState;
       instance.refs = emptyObject;
       instance.context = getMaskedContext(workInProgress, unmaskedContext);
-      unmaskedContext = workInProgress.updateQueue;
-      null !== unmaskedContext &&
-        (processUpdateQueue(
-          workInProgress,
-          unmaskedContext,
-          props,
-          instance,
-          renderExpirationTime
-        ),
-        (instance.state = workInProgress.memoizedState));
-      unmaskedContext = workInProgress.type.getDerivedStateFromProps;
-      "function" === typeof unmaskedContext &&
-        (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
-        (instance.state = workInProgress.memoizedState));
       "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate ||
         ("function" !== typeof instance.UNSAFE_componentWillMount &&
@@ -1987,36 +1896,32 @@ function ReactFiberClassComponent(
         "function" === typeof instance.UNSAFE_componentWillMount &&
           instance.UNSAFE_componentWillMount(),
         ctor !== instance.state &&
-          classComponentUpdater.enqueueReplaceState(
-            instance,
-            instance.state,
-            null
-          ),
-        (unmaskedContext = workInProgress.updateQueue),
-        null !== unmaskedContext &&
-          (processUpdateQueue(
+          updater.enqueueReplaceState(instance, instance.state, null),
+        (ctor = workInProgress.updateQueue),
+        null !== ctor &&
+          (instance.state = processUpdateQueue(
+            current,
             workInProgress,
-            unmaskedContext,
-            props,
+            ctor,
             instance,
+            props,
             renderExpirationTime
-          ),
-          (instance.state = workInProgress.memoizedState)));
+          )));
       "function" === typeof instance.componentDidMount &&
         (workInProgress.effectTag |= 4);
     },
     resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps;
-      instance.props = oldProps;
-      var oldContext = instance.context,
+        instance = workInProgress.stateNode;
+      instance.props = workInProgress.memoizedProps;
+      instance.state = workInProgress.memoizedState;
+      var oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps,
+        oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof getDerivedStateFromProps ||
+        "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2027,29 +1932,43 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      var oldState = workInProgress.memoizedState;
-      oldContext = instance.state = oldState;
-      var updateQueue = workInProgress.updateQueue;
-      null !== updateQueue &&
-        (processUpdateQueue(
+      oldContext = workInProgress.memoizedState;
+      renderExpirationTime =
+        null !== workInProgress.updateQueue
+          ? processUpdateQueue(
+              null,
+              workInProgress,
+              workInProgress.updateQueue,
+              instance,
+              newProps,
+              renderExpirationTime
+            )
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
           workInProgress,
-          updateQueue,
-          newProps,
           instance,
+          newProps,
           renderExpirationTime
-        ),
-        (oldContext = workInProgress.memoizedState));
-      "function" === typeof getDerivedStateFromProps &&
-        (applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        ),
-        (oldContext = workInProgress.memoizedState));
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
+          null === renderExpirationTime || void 0 === renderExpirationTime
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue = workInProgress.updateQueue;
+        null !== _updateQueue &&
+          (_updateQueue.baseState = Object.assign(
+            {},
+            _updateQueue.baseState,
+            derivedStateFromProps
+          ));
+      }
       if (
         !(
           oldProps !== newProps ||
-          oldState !== oldContext ||
+          oldContext !== renderExpirationTime ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2060,12 +1979,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4),
           !1
         );
-      (renderExpirationTime = checkShouldComponentUpdate(
+      (oldProps = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
-        oldState,
         oldContext,
+        renderExpirationTime,
         newUnmaskedContext
       ))
         ? (ctor ||
@@ -2079,12 +1998,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4))
         : ("function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
-          (workInProgress.memoizedProps = newProps),
-          (workInProgress.memoizedState = oldContext));
+          memoizeProps(workInProgress, newProps),
+          memoizeState(workInProgress, renderExpirationTime));
       instance.props = newProps;
-      instance.state = oldContext;
+      instance.state = renderExpirationTime;
       instance.context = newUnmaskedContext;
-      return renderExpirationTime;
+      return oldProps;
     },
     updateClassInstance: function(
       current,
@@ -2092,16 +2011,16 @@ function ReactFiberClassComponent(
       renderExpirationTime
     ) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps;
-      instance.props = oldProps;
-      var oldContext = instance.context,
+        instance = workInProgress.stateNode;
+      instance.props = workInProgress.memoizedProps;
+      instance.state = workInProgress.memoizedState;
+      var oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps,
+        oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof getDerivedStateFromProps ||
+        "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2113,28 +2032,42 @@ function ReactFiberClassComponent(
             newUnmaskedContext
           ));
       oldContext = workInProgress.memoizedState;
-      var newState = (instance.state = oldContext),
-        updateQueue = workInProgress.updateQueue;
-      null !== updateQueue &&
-        (processUpdateQueue(
+      renderExpirationTime =
+        null !== workInProgress.updateQueue
+          ? processUpdateQueue(
+              current,
+              workInProgress,
+              workInProgress.updateQueue,
+              instance,
+              newProps,
+              renderExpirationTime
+            )
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
           workInProgress,
-          updateQueue,
-          newProps,
           instance,
+          newProps,
           renderExpirationTime
-        ),
-        (newState = workInProgress.memoizedState));
-      "function" === typeof getDerivedStateFromProps &&
-        (applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        ),
-        (newState = workInProgress.memoizedState));
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
+          null === renderExpirationTime || void 0 === renderExpirationTime
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue3 = workInProgress.updateQueue;
+        null !== _updateQueue3 &&
+          (_updateQueue3.baseState = Object.assign(
+            {},
+            _updateQueue3.baseState,
+            derivedStateFromProps
+          ));
+      }
       if (
         !(
           oldProps !== newProps ||
-          oldContext !== newState ||
+          oldContext !== renderExpirationTime ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2148,15 +2081,15 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 256),
+            (workInProgress.effectTag |= 2048),
           !1
         );
-      (renderExpirationTime = checkShouldComponentUpdate(
+      (derivedStateFromProps = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
         oldContext,
-        newState,
+        renderExpirationTime,
         newUnmaskedContext
       ))
         ? (ctor ||
@@ -2165,19 +2098,19 @@ function ReactFiberClassComponent(
             ("function" === typeof instance.componentWillUpdate &&
               instance.componentWillUpdate(
                 newProps,
-                newState,
+                renderExpirationTime,
                 newUnmaskedContext
               ),
             "function" === typeof instance.UNSAFE_componentWillUpdate &&
               instance.UNSAFE_componentWillUpdate(
                 newProps,
-                newState,
+                renderExpirationTime,
                 newUnmaskedContext
               )),
           "function" === typeof instance.componentDidUpdate &&
             (workInProgress.effectTag |= 4),
           "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 256))
+            (workInProgress.effectTag |= 2048))
         : ("function" !== typeof instance.componentDidUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
@@ -2185,13 +2118,13 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 256),
-          (workInProgress.memoizedProps = newProps),
-          (workInProgress.memoizedState = newState));
+            (workInProgress.effectTag |= 2048),
+          memoizeProps(workInProgress, newProps),
+          memoizeState(workInProgress, renderExpirationTime));
       instance.props = newProps;
-      instance.state = newState;
+      instance.state = renderExpirationTime;
       instance.context = newUnmaskedContext;
-      return renderExpirationTime;
+      return derivedStateFromProps;
     }
   };
 }
@@ -2315,11 +2248,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current.return = returnFiber),
+        (current["return"] = returnFiber),
         current
       );
     current = useFiber(current, textContent, expirationTime);
-    current.return = returnFiber;
+    current["return"] = returnFiber;
     return current;
   }
   function updateElement(returnFiber, current, element, expirationTime) {
@@ -2327,7 +2260,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       return (
         (expirationTime = useFiber(current, element.props, expirationTime)),
         (expirationTime.ref = coerceRef(returnFiber, current, element)),
-        (expirationTime.return = returnFiber),
+        (expirationTime["return"] = returnFiber),
         expirationTime
       );
     expirationTime = createFiberFromElement(
@@ -2336,7 +2269,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       expirationTime
     );
     expirationTime.ref = coerceRef(returnFiber, current, element);
-    expirationTime.return = returnFiber;
+    expirationTime["return"] = returnFiber;
     return expirationTime;
   }
   function updatePortal(returnFiber, current, portal, expirationTime) {
@@ -2352,11 +2285,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current.return = returnFiber),
+        (current["return"] = returnFiber),
         current
       );
     current = useFiber(current, portal.children || [], expirationTime);
-    current.return = returnFiber;
+    current["return"] = returnFiber;
     return current;
   }
   function updateFragment(returnFiber, current, fragment, expirationTime, key) {
@@ -2368,11 +2301,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           key
         )),
-        (current.return = returnFiber),
+        (current["return"] = returnFiber),
         current
       );
     current = useFiber(current, fragment, expirationTime);
-    current.return = returnFiber;
+    current["return"] = returnFiber;
     return current;
   }
   function createChild(returnFiber, newChild, expirationTime) {
@@ -2383,7 +2316,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (newChild.return = returnFiber),
+        (newChild["return"] = returnFiber),
         newChild
       );
     if ("object" === typeof newChild && null !== newChild) {
@@ -2396,7 +2329,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               expirationTime
             )),
             (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
-            (expirationTime.return = returnFiber),
+            (expirationTime["return"] = returnFiber),
             expirationTime
           );
         case REACT_PORTAL_TYPE:
@@ -2406,7 +2339,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (newChild.return = returnFiber),
+            (newChild["return"] = returnFiber),
             newChild
           );
       }
@@ -2418,7 +2351,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime,
             null
           )),
-          (newChild.return = returnFiber),
+          (newChild["return"] = returnFiber),
           newChild
         );
       throwOnInvalidObjectType(returnFiber, newChild);
@@ -2605,21 +2538,17 @@ function ChildReconciler(shouldTrackSideEffects) {
           newChildren[newIdx],
           expirationTime
         ))
-      )
-        shouldTrackSideEffects &&
-          null !== nextOldFiber.alternate &&
-          oldFiber.delete(
+      ) {
+        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
+          oldFiber["delete"](
             null === nextOldFiber.key ? newIdx : nextOldFiber.key
-          ),
-          (currentFirstChild = placeChild(
-            nextOldFiber,
-            currentFirstChild,
-            newIdx
-          )),
-          null === previousNewFiber
-            ? (resultingFirstChild = nextOldFiber)
-            : (previousNewFiber.sibling = nextOldFiber),
-          (previousNewFiber = nextOldFiber);
+          );
+        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
+        null === previousNewFiber
+          ? (resultingFirstChild = nextOldFiber)
+          : (previousNewFiber.sibling = nextOldFiber);
+        previousNewFiber = nextOldFiber;
+      }
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2693,22 +2622,24 @@ function ChildReconciler(shouldTrackSideEffects) {
       !step.done;
       newIdx++, step = newChildrenIterable.next()
     )
-      (step = updateFromMap(
-        oldFiber,
-        returnFiber,
-        newIdx,
-        step.value,
-        expirationTime
-      )),
-        null !== step &&
-          (shouldTrackSideEffects &&
-            null !== step.alternate &&
-            oldFiber.delete(null === step.key ? newIdx : step.key),
-          (currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
-          null === previousNewFiber
-            ? (iteratorFn = step)
-            : (previousNewFiber.sibling = step),
-          (previousNewFiber = step));
+      if (
+        ((step = updateFromMap(
+          oldFiber,
+          returnFiber,
+          newIdx,
+          step.value,
+          expirationTime
+        )),
+        null !== step)
+      ) {
+        if (shouldTrackSideEffects && null !== step.alternate)
+          oldFiber["delete"](null === step.key ? newIdx : step.key);
+        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
+        null === previousNewFiber
+          ? (iteratorFn = step)
+          : (previousNewFiber.sibling = step);
+        previousNewFiber = step;
+      }
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2747,7 +2678,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     isObject,
                     newChild
                   );
-                  currentFirstChild.return = returnFiber;
+                  currentFirstChild["return"] = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2764,7 +2695,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   expirationTime,
                   newChild.key
                 )),
-                (currentFirstChild.return = returnFiber),
+                (currentFirstChild["return"] = returnFiber),
                 (returnFiber = currentFirstChild))
               : ((expirationTime = createFiberFromElement(
                   newChild,
@@ -2776,7 +2707,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   currentFirstChild,
                   newChild
                 )),
-                (expirationTime.return = returnFiber),
+                (expirationTime["return"] = returnFiber),
                 (returnFiber = expirationTime));
           }
           return placeSingleChild(returnFiber);
@@ -2800,7 +2731,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     newChild.children || [],
                     expirationTime
                   );
-                  currentFirstChild.return = returnFiber;
+                  currentFirstChild["return"] = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2815,7 +2746,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             );
-            currentFirstChild.return = returnFiber;
+            currentFirstChild["return"] = returnFiber;
             returnFiber = currentFirstChild;
           }
           return placeSingleChild(returnFiber);
@@ -2830,7 +2761,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               newChild,
               expirationTime
             )),
-            (currentFirstChild.return = returnFiber),
+            (currentFirstChild["return"] = returnFiber),
             (returnFiber = currentFirstChild))
           : (deleteRemainingChildren(returnFiber, currentFirstChild),
             (currentFirstChild = createFiberFromText(
@@ -2838,7 +2769,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (currentFirstChild.return = returnFiber),
+            (currentFirstChild["return"] = returnFiber),
             (returnFiber = currentFirstChild)),
         placeSingleChild(returnFiber)
       );
@@ -2924,10 +2855,10 @@ function ReactFiberBeginWork(
     workInProgress,
     shouldUpdate,
     hasContext,
+    didCaptureError,
     renderExpirationTime
   ) {
     markRef(current, workInProgress);
-    var didCaptureError = 0 !== (workInProgress.effectTag & 64);
     if (!shouldUpdate && !didCaptureError)
       return (
         hasContext && invalidateContextProvider(workInProgress, !1),
@@ -2975,8 +2906,11 @@ function ReactFiberBeginWork(
     renderExpirationTime
   ) {
     var fiber = workInProgress.child;
-    null !== fiber && (fiber.return = workInProgress);
-    for (; null !== fiber; ) {
+    for (
+      null !== fiber && (fiber["return"] = workInProgress);
+      null !== fiber;
+
+    ) {
       switch (fiber.tag) {
         case 12:
           var nextFiber = fiber.stateNode | 0;
@@ -2999,7 +2933,7 @@ function ReactFiberBeginWork(
               )
                 alternate.expirationTime = renderExpirationTime;
               else break;
-              nextFiber = nextFiber.return;
+              nextFiber = nextFiber["return"];
             }
             nextFiber = null;
           } else nextFiber = fiber.child;
@@ -3010,7 +2944,7 @@ function ReactFiberBeginWork(
         default:
           nextFiber = fiber.child;
       }
-      if (null !== nextFiber) nextFiber.return = fiber;
+      if (null !== nextFiber) nextFiber["return"] = fiber;
       else
         for (nextFiber = fiber; null !== nextFiber; ) {
           if (nextFiber === workInProgress) {
@@ -3019,11 +2953,10 @@ function ReactFiberBeginWork(
           }
           fiber = nextFiber.sibling;
           if (null !== fiber) {
-            fiber.return = nextFiber.return;
             nextFiber = fiber;
             break;
           }
-          nextFiber = nextFiber.return;
+          nextFiber = nextFiber["return"];
         }
       fiber = nextFiber;
     }
@@ -3035,10 +2968,8 @@ function ReactFiberBeginWork(
   ) {
     var context = workInProgress.type._context,
       newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps,
-      canBailOnProps = !0;
-    if (hasLegacyContextChanged()) canBailOnProps = !1;
-    else if (oldProps === newProps)
+      oldProps = workInProgress.memoizedProps;
+    if (!hasLegacyContextChanged() && oldProps === newProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
@@ -3048,7 +2979,7 @@ function ReactFiberBeginWork(
     workInProgress.memoizedProps = newProps;
     if (null === oldProps) newValue = 1073741823;
     else if (oldProps.value === newProps.value) {
-      if (oldProps.children === newProps.children && canBailOnProps)
+      if (oldProps.children === newProps.children)
         return (
           (workInProgress.stateNode = 0),
           pushProvider(workInProgress),
@@ -3062,7 +2993,7 @@ function ReactFiberBeginWork(
           (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
         (oldValue !== oldValue && newValue !== newValue)
       ) {
-        if (oldProps.children === newProps.children && canBailOnProps)
+        if (oldProps.children === newProps.children)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3077,7 +3008,7 @@ function ReactFiberBeginWork(
         (newValue |= 0),
         0 === newValue)
       ) {
-        if (oldProps.children === newProps.children && canBailOnProps)
+        if (oldProps.children === newProps.children)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3109,14 +3040,14 @@ function ReactFiberBeginWork(
         current.expirationTime
       );
       workInProgress.child = newChild;
-      for (newChild.return = workInProgress; null !== current.sibling; )
+      for (newChild["return"] = workInProgress; null !== current.sibling; )
         (current = current.sibling),
           (newChild = newChild.sibling = createWorkInProgress(
             current,
             current.pendingProps,
             current.expirationTime
           )),
-          (newChild.return = workInProgress);
+          (newChild["return"] = workInProgress);
       newChild.sibling = null;
     }
     return workInProgress.child;
@@ -3148,6 +3079,7 @@ function ReactFiberBeginWork(
     }
   );
   var adoptClassInstance = config.adoptClassInstance,
+    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
     constructClassInstance = config.constructClassInstance,
     mountClassInstance = config.mountClassInstance,
     resumeMountClassInstance = config.resumeMountClassInstance,
@@ -3196,13 +3128,20 @@ function ReactFiberBeginWork(
               (workInProgress.tag = 2),
               (workInProgress.memoizedState =
                 null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
-              "function" === typeof unmaskedContext &&
-                applyDerivedStateFromProps(
+              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
+                ((props = callGetDerivedStateFromProps(
                   workInProgress,
-                  unmaskedContext,
-                  props
-                ),
+                  fn,
+                  props,
+                  workInProgress.memoizedState
+                )),
+                null !== props &&
+                  void 0 !== props &&
+                  (workInProgress.memoizedState = Object.assign(
+                    {},
+                    workInProgress.memoizedState,
+                    props
+                  ))),
               (props = pushLegacyContextProvider(workInProgress)),
               adoptClassInstance(workInProgress, fn),
               mountClassInstance(workInProgress, renderExpirationTime),
@@ -3211,6 +3150,7 @@ function ReactFiberBeginWork(
                 workInProgress,
                 !0,
                 props,
+                !1,
                 renderExpirationTime
               )))
             : ((workInProgress.tag = 1),
@@ -3238,100 +3178,103 @@ function ReactFiberBeginWork(
             current
           );
         case 2:
-          return (
-            (props = pushLegacyContextProvider(workInProgress)),
-            null === current
-              ? null === workInProgress.stateNode
-                ? (constructClassInstance(
-                    workInProgress,
-                    workInProgress.pendingProps,
-                    renderExpirationTime
-                  ),
-                  mountClassInstance(workInProgress, renderExpirationTime),
-                  (fn = !0))
-                : (fn = resumeMountClassInstance(
-                    workInProgress,
-                    renderExpirationTime
-                  ))
-              : (fn = updateClassInstance(
-                  current,
+          props = pushLegacyContextProvider(workInProgress);
+          null === current
+            ? null === workInProgress.stateNode
+              ? (constructClassInstance(
+                  workInProgress,
+                  workInProgress.pendingProps
+                ),
+                mountClassInstance(workInProgress, renderExpirationTime),
+                (fn = !0))
+              : (fn = resumeMountClassInstance(
                   workInProgress,
                   renderExpirationTime
-                )),
-            finishClassComponent(
+                ))
+            : (fn = updateClassInstance(
+                current,
+                workInProgress,
+                renderExpirationTime
+              ));
+          unmaskedContext = !1;
+          var updateQueue = workInProgress.updateQueue;
+          null !== updateQueue &&
+            null !== updateQueue.capturedValues &&
+            (unmaskedContext = fn = !0);
+          return finishClassComponent(
+            current,
+            workInProgress,
+            fn,
+            props,
+            unmaskedContext,
+            renderExpirationTime
+          );
+        case 3:
+          a: if (
+            (pushHostRootContext(workInProgress),
+            (fn = workInProgress.updateQueue),
+            null !== fn)
+          ) {
+            unmaskedContext = workInProgress.memoizedState;
+            props = processUpdateQueue(
               current,
               workInProgress,
               fn,
-              props,
+              null,
+              null,
               renderExpirationTime
-            )
-          );
-        case 3:
-          return (
-            pushHostRootContext(workInProgress),
-            (props = workInProgress.updateQueue),
-            null !== props
-              ? ((fn = workInProgress.memoizedState),
-                (fn = null !== fn ? fn.element : null),
-                processUpdateQueue(
+            );
+            workInProgress.memoizedState = props;
+            fn = workInProgress.updateQueue;
+            if (null !== fn && null !== fn.capturedValues) fn = null;
+            else if (unmaskedContext === props) {
+              resetHydrationState();
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+              break a;
+            } else fn = props.element;
+            unmaskedContext = workInProgress.stateNode;
+            (null === current || null === current.child) &&
+            unmaskedContext.hydrate &&
+            enterHydrationState(workInProgress)
+              ? ((workInProgress.effectTag |= 2),
+                (workInProgress.child = mountChildFibers(
                   workInProgress,
-                  props,
-                  workInProgress.pendingProps,
                   null,
+                  fn,
                   renderExpirationTime
-                ),
-                (props = workInProgress.memoizedState.element),
-                props === fn
-                  ? (resetHydrationState(),
-                    (current = bailoutOnAlreadyFinishedWork(
-                      current,
-                      workInProgress
-                    )))
-                  : ((fn = workInProgress.stateNode),
-                    (null === current || null === current.child) &&
-                    fn.hydrate &&
-                    enterHydrationState(workInProgress)
-                      ? ((workInProgress.effectTag |= 2),
-                        (workInProgress.child = mountChildFibers(
-                          workInProgress,
-                          null,
-                          props,
-                          renderExpirationTime
-                        )))
-                      : (resetHydrationState(),
-                        reconcileChildren(current, workInProgress, props)),
-                    (current = workInProgress.child)))
+                )))
               : (resetHydrationState(),
-                (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                ))),
-            current
-          );
+                reconcileChildren(current, workInProgress, fn));
+            workInProgress.memoizedState = props;
+            current = workInProgress.child;
+          } else
+            resetHydrationState(),
+              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
+          return current;
         case 5:
           a: {
             pushHostContext(workInProgress);
             null === current &&
               tryToClaimNextHydratableInstance(workInProgress);
             props = workInProgress.type;
-            var memoizedProps = workInProgress.memoizedProps;
+            updateQueue = workInProgress.memoizedProps;
             fn = workInProgress.pendingProps;
             unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && memoizedProps === fn) {
+            if (!hasLegacyContextChanged() && updateQueue === fn) {
               if (
-                (memoizedProps =
+                (updateQueue =
                   workInProgress.mode & 1 &&
                   shouldDeprioritizeSubtree(props, fn))
               )
                 workInProgress.expirationTime = 1073741823;
-              if (!memoizedProps || 1073741823 !== renderExpirationTime) {
+              if (!updateQueue || 1073741823 !== renderExpirationTime) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
             }
-            memoizedProps = fn.children;
+            updateQueue = fn.children;
             shouldSetTextContent(props, fn)
-              ? (memoizedProps = null)
+              ? (updateQueue = null)
               : unmaskedContext &&
                 shouldSetTextContent(props, unmaskedContext) &&
                 (workInProgress.effectTag |= 16);
@@ -3342,7 +3285,7 @@ function ReactFiberBeginWork(
               ? ((workInProgress.expirationTime = 1073741823),
                 (workInProgress.memoizedProps = fn),
                 (current = null))
-              : (reconcileChildren(current, workInProgress, memoizedProps),
+              : (reconcileChildren(current, workInProgress, updateQueue),
                 (workInProgress.memoizedProps = fn),
                 (current = workInProgress.child));
           }
@@ -3408,21 +3351,14 @@ function ReactFiberBeginWork(
           );
         case 14:
           return (
-            (props = workInProgress.type.render),
-            (renderExpirationTime = workInProgress.pendingProps),
-            (fn = workInProgress.ref),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime ||
-            fn !== (null !== current ? current.ref : null)
-              ? ((props = props(renderExpirationTime, fn)),
-                reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
+            (renderExpirationTime = workInProgress.type.render),
+            (renderExpirationTime = renderExpirationTime(
+              workInProgress.pendingProps,
+              workInProgress.ref
+            )),
+            reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            workInProgress.child
           );
         case 10:
           return (
@@ -3471,13 +3407,13 @@ function ReactFiberBeginWork(
           a: {
             fn = workInProgress.type;
             unmaskedContext = workInProgress.pendingProps;
-            memoizedProps = workInProgress.memoizedProps;
+            updateQueue = workInProgress.memoizedProps;
             props = fn._currentValue;
             var changedBits = fn._changedBits;
             if (
               hasLegacyContextChanged() ||
               0 !== changedBits ||
-              memoizedProps !== unmaskedContext
+              updateQueue !== unmaskedContext
             ) {
               workInProgress.memoizedProps = unmaskedContext;
               var observedBits = unmaskedContext.unstable_observedBits;
@@ -3491,13 +3427,12 @@ function ReactFiberBeginWork(
                   changedBits,
                   renderExpirationTime
                 );
-              else if (memoizedProps === unmaskedContext) {
+              else if (updateQueue === unmaskedContext) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
               renderExpirationTime = unmaskedContext.children;
               renderExpirationTime = renderExpirationTime(props);
-              workInProgress.effectTag |= 1;
               reconcileChildren(current, workInProgress, renderExpirationTime);
               current = workInProgress.child;
             } else
@@ -3528,16 +3463,17 @@ function ReactFiberCompleteWork(
       if (5 === node.tag || 6 === node.tag)
         appendInitialChild(parent, node.stateNode);
       else if (4 !== node.tag && null !== node.child) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
       if (node === workInProgress) break;
       for (; null === node.sibling; ) {
-        if (null === node.return || node.return === workInProgress) return;
-        node = node.return;
+        if (null === node["return"] || node["return"] === workInProgress)
+          return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -3578,16 +3514,17 @@ function ReactFiberCompleteWork(
           if (5 === node.tag || 6 === node.tag)
             appendChildToContainerChildSet(newChildSet, node.stateNode);
           else if (4 !== node.tag && null !== node.child) {
-            node.child.return = node;
+            node.child["return"] = node;
             node = node.child;
             continue;
           }
           if (node === workInProgress) break a;
           for (; null === node.sibling; ) {
-            if (null === node.return || node.return === workInProgress) break a;
-            node = node.return;
+            if (null === node["return"] || node["return"] === workInProgress)
+              break a;
+            node = node["return"];
           }
-          node.sibling.return = node.return;
+          node.sibling["return"] = node["return"];
           node = node.sibling;
         }
         portalOrRoot.pendingChildren = newChildSet;
@@ -3651,7 +3588,18 @@ function ReactFiberCompleteWork(
         case 1:
           return null;
         case 2:
-          return popLegacyContextProvider(workInProgress), null;
+          return (
+            popLegacyContextProvider(workInProgress),
+            (current = workInProgress.stateNode),
+            (newProps = workInProgress.updateQueue),
+            null !== newProps &&
+              null !== newProps.capturedValues &&
+              ((workInProgress.effectTag &= -65),
+              "function" === typeof current.componentDidCatch
+                ? (workInProgress.effectTag |= 256)
+                : (newProps.capturedValues = null)),
+            null
+          );
         case 3:
           popHostContainer(workInProgress);
           popTopLevelLegacyContextObject(workInProgress);
@@ -3662,6 +3610,10 @@ function ReactFiberCompleteWork(
           if (null === current || null === current.child)
             popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
           updateHostContainer(workInProgress);
+          current = workInProgress.updateQueue;
+          null !== current &&
+            null !== current.capturedValues &&
+            (workInProgress.effectTag |= 256);
           return null;
         case 5:
           popHostContext(workInProgress);
@@ -3669,10 +3621,10 @@ function ReactFiberCompleteWork(
           var type = workInProgress.type;
           if (null !== current && null != workInProgress.stateNode) {
             var oldProps = current.memoizedProps,
-              instance = workInProgress.stateNode,
+              _instance = workInProgress.stateNode,
               currentHostContext = getHostContext();
-            instance = prepareUpdate(
-              instance,
+            _instance = prepareUpdate(
+              _instance,
               type,
               oldProps,
               newProps,
@@ -3682,7 +3634,7 @@ function ReactFiberCompleteWork(
             updateHostComponent(
               current,
               workInProgress,
-              instance,
+              _instance,
               type,
               oldProps,
               newProps,
@@ -3764,34 +3716,30 @@ function ReactFiberCompleteWork(
           );
           workInProgress.tag = 8;
           type = [];
-          a: {
-            if ((oldProps = workInProgress.stateNode))
-              oldProps.return = workInProgress;
-            for (; null !== oldProps; ) {
+          a: for (
+            (oldProps = workInProgress.stateNode) &&
+            (oldProps["return"] = workInProgress);
+            null !== oldProps;
+
+          ) {
+            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
+              invariant(!1, "A call cannot have host component children.");
+            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
+            else if (null !== oldProps.child) {
+              oldProps.child["return"] = oldProps;
+              oldProps = oldProps.child;
+              continue;
+            }
+            for (; null === oldProps.sibling; ) {
               if (
-                5 === oldProps.tag ||
-                6 === oldProps.tag ||
-                4 === oldProps.tag
+                null === oldProps["return"] ||
+                oldProps["return"] === workInProgress
               )
-                invariant(!1, "A call cannot have host component children.");
-              else if (9 === oldProps.tag)
-                type.push(oldProps.pendingProps.value);
-              else if (null !== oldProps.child) {
-                oldProps.child.return = oldProps;
-                oldProps = oldProps.child;
-                continue;
-              }
-              for (; null === oldProps.sibling; ) {
-                if (
-                  null === oldProps.return ||
-                  oldProps.return === workInProgress
-                )
-                  break a;
-                oldProps = oldProps.return;
-              }
-              oldProps.sibling.return = oldProps.return;
-              oldProps = oldProps.sibling;
+                break a;
+              oldProps = oldProps["return"];
             }
+            oldProps.sibling["return"] = oldProps["return"];
+            oldProps = oldProps.sibling;
           }
           oldProps = newProps.handler;
           newProps = oldProps(newProps.props, type);
@@ -3836,11 +3784,103 @@ function ReactFiberCompleteWork(
     }
   };
 }
-function createCapturedValue(value, source) {
+function ReactFiberUnwindWork(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  isAlreadyFailedLegacyErrorBoundary
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
   return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
+    throwException: function(returnFiber, sourceFiber, rawValue) {
+      sourceFiber.effectTag |= 512;
+      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+      sourceFiber = {
+        value: rawValue,
+        source: sourceFiber,
+        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
+      };
+      do {
+        switch (returnFiber.tag) {
+          case 3:
+            ensureUpdateQueues(returnFiber);
+            returnFiber.updateQueue.capturedValues = [sourceFiber];
+            returnFiber.effectTag |= 1024;
+            return;
+          case 2:
+            if (
+              ((rawValue = returnFiber.stateNode),
+              0 === (returnFiber.effectTag & 64) &&
+                null !== rawValue &&
+                "function" === typeof rawValue.componentDidCatch &&
+                !isAlreadyFailedLegacyErrorBoundary(rawValue))
+            ) {
+              ensureUpdateQueues(returnFiber);
+              rawValue = returnFiber.updateQueue;
+              var capturedValues = rawValue.capturedValues;
+              null === capturedValues
+                ? (rawValue.capturedValues = [sourceFiber])
+                : capturedValues.push(sourceFiber);
+              returnFiber.effectTag |= 1024;
+              return;
+            }
+        }
+        returnFiber = returnFiber["return"];
+      } while (null !== returnFiber);
+    },
+    unwindWork: function(workInProgress) {
+      switch (workInProgress.tag) {
+        case 2:
+          popLegacyContextProvider(workInProgress);
+          var effectTag = workInProgress.effectTag;
+          return effectTag & 1024
+            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+              workInProgress)
+            : null;
+        case 3:
+          return (
+            popHostContainer(workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 5:
+          return popHostContext(workInProgress), null;
+        case 4:
+          return popHostContainer(workInProgress), null;
+        case 13:
+          return popProvider(workInProgress), null;
+        default:
+          return null;
+      }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
+    }
   };
 }
 function logError(boundary, errorInfo) {
@@ -3856,7 +3896,13 @@ function logError(boundary, errorInfo) {
     (e && e.suppressReactErrorLogging) || console.error(e);
   }
 }
-function ReactFiberCommitWork(config, captureError) {
+function ReactFiberCommitWork(
+  config,
+  captureError,
+  scheduleWork,
+  computeExpirationForFiber,
+  markLegacyErrorBoundaryAsFailed
+) {
   function safelyDetachRef(current) {
     var ref = current.ref;
     if (null !== ref)
@@ -3871,7 +3917,7 @@ function ReactFiberCommitWork(config, captureError) {
   function commitBeforeMutationLifeCycles(current, finishedWork) {
     switch (finishedWork.tag) {
       case 2:
-        if (finishedWork.effectTag & 256 && null !== current) {
+        if (finishedWork.effectTag & 2048 && null !== current) {
           var prevProps = current.memoizedProps,
             prevState = current.memoizedState;
           current = finishedWork.stateNode;
@@ -3893,40 +3939,28 @@ function ReactFiberCommitWork(config, captureError) {
         );
     }
   }
-  function commitLifeCycles(
-    finishedRoot,
-    current,
-    finishedWork,
-    currentTime,
-    committedExpirationTime
-  ) {
+  function commitLifeCycles(finishedRoot, current, finishedWork) {
     switch (finishedWork.tag) {
       case 2:
         finishedRoot = finishedWork.stateNode;
-        finishedWork.effectTag & 4 &&
-          (null === current
-            ? ((finishedRoot.props = finishedWork.memoizedProps),
-              (finishedRoot.state = finishedWork.memoizedState),
-              finishedRoot.componentDidMount())
-            : ((currentTime = current.memoizedProps),
-              (current = current.memoizedState),
-              (finishedRoot.props = finishedWork.memoizedProps),
+        if (finishedWork.effectTag & 4)
+          if (null === current)
+            (finishedRoot.props = finishedWork.memoizedProps),
               (finishedRoot.state = finishedWork.memoizedState),
-              finishedRoot.componentDidUpdate(
-                currentTime,
-                current,
-                finishedRoot.__reactInternalSnapshotBeforeUpdate
-              )));
-        current = finishedWork.updateQueue;
-        null !== current &&
-          ((finishedRoot.props = finishedWork.memoizedProps),
-          (finishedRoot.state = finishedWork.memoizedState),
-          commitUpdateQueue(
-            finishedWork,
-            current,
-            finishedRoot,
-            committedExpirationTime
-          ));
+              finishedRoot.componentDidMount();
+          else {
+            var prevProps = current.memoizedProps;
+            current = current.memoizedState;
+            finishedRoot.props = finishedWork.memoizedProps;
+            finishedRoot.state = finishedWork.memoizedState;
+            finishedRoot.componentDidUpdate(
+              prevProps,
+              current,
+              finishedRoot.__reactInternalSnapshotBeforeUpdate
+            );
+          }
+        finishedWork = finishedWork.updateQueue;
+        null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
         break;
       case 3:
         current = finishedWork.updateQueue;
@@ -3940,20 +3974,15 @@ function ReactFiberCommitWork(config, captureError) {
               case 2:
                 finishedRoot = finishedWork.child.stateNode;
             }
-          commitUpdateQueue(
-            finishedWork,
-            current,
-            finishedRoot,
-            committedExpirationTime
-          );
+          commitCallbacks(current, finishedRoot);
         }
         break;
       case 5:
-        committedExpirationTime = finishedWork.stateNode;
+        finishedRoot = finishedWork.stateNode;
         null === current &&
           finishedWork.effectTag & 4 &&
           commitMount(
-            committedExpirationTime,
+            finishedRoot,
             finishedWork.type,
             finishedWork.memoizedProps,
             finishedWork
@@ -3970,16 +3999,62 @@ function ReactFiberCommitWork(config, captureError) {
         );
     }
   }
+  function commitErrorLogging(finishedWork, onUncaughtError) {
+    switch (finishedWork.tag) {
+      case 2:
+        var ctor = finishedWork.type;
+        onUncaughtError = finishedWork.stateNode;
+        var updateQueue = finishedWork.updateQueue;
+        invariant(
+          null !== updateQueue && null !== updateQueue.capturedValues,
+          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
+        );
+        var capturedErrors = updateQueue.capturedValues;
+        updateQueue.capturedValues = null;
+        "function" !== typeof ctor.getDerivedStateFromCatch &&
+          markLegacyErrorBoundaryAsFailed(onUncaughtError);
+        onUncaughtError.props = finishedWork.memoizedProps;
+        onUncaughtError.state = finishedWork.memoizedState;
+        for (ctor = 0; ctor < capturedErrors.length; ctor++) {
+          updateQueue = capturedErrors[ctor];
+          var _error = updateQueue.value,
+            stack = updateQueue.stack;
+          logError(finishedWork, updateQueue);
+          onUncaughtError.componentDidCatch(_error, {
+            componentStack: null !== stack ? stack : ""
+          });
+        }
+        break;
+      case 3:
+        ctor = finishedWork.updateQueue;
+        invariant(
+          null !== ctor && null !== ctor.capturedValues,
+          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
+        );
+        capturedErrors = ctor.capturedValues;
+        ctor.capturedValues = null;
+        for (ctor = 0; ctor < capturedErrors.length; ctor++)
+          (updateQueue = capturedErrors[ctor]),
+            logError(finishedWork, updateQueue),
+            onUncaughtError(updateQueue.value);
+        break;
+      default:
+        invariant(
+          !1,
+          "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (null !== ref) {
-      var _instance5 = finishedWork.stateNode;
+      var _instance6 = finishedWork.stateNode;
       switch (finishedWork.tag) {
         case 5:
-          finishedWork = getPublicInstance(_instance5);
+          finishedWork = getPublicInstance(_instance6);
           break;
         default:
-          finishedWork = _instance5;
+          finishedWork = _instance6;
       }
       "function" === typeof ref
         ? ref(finishedWork)
@@ -4000,12 +4075,12 @@ function ReactFiberCommitWork(config, captureError) {
       switch (current.tag) {
         case 2:
           safelyDetachRef(current);
-          var _instance6 = current.stateNode;
-          if ("function" === typeof _instance6.componentWillUnmount)
+          var _instance7 = current.stateNode;
+          if ("function" === typeof _instance7.componentWillUnmount)
             try {
-              (_instance6.props = current.memoizedProps),
-                (_instance6.state = current.memoizedState),
-                _instance6.componentWillUnmount();
+              (_instance7.props = current.memoizedProps),
+                (_instance7.state = current.memoizedState),
+                _instance7.componentWillUnmount();
             } catch (unmountError) {
               captureError(current, unmountError);
             }
@@ -4022,12 +4097,12 @@ function ReactFiberCommitWork(config, captureError) {
       if (null === node.child || (mutation && 4 === node.tag)) {
         if (node === root) break;
         for (; null === node.sibling; ) {
-          if (null === node.return || node.return === root) return;
-          node = node.return;
+          if (null === node["return"] || node["return"] === root) return;
+          node = node["return"];
         }
-        node.sibling.return = node.return;
+        node.sibling["return"] = node["return"];
         node = node.sibling;
-      } else (node.child.return = node), (node = node.child);
+      } else (node.child["return"] = node), (node = node.child);
     }
   }
   var getPublicInstance = config.getPublicInstance,
@@ -4073,16 +4148,18 @@ function ReactFiberCommitWork(config, captureError) {
       commitPlacement: function() {},
       commitDeletion: function(current) {
         commitNestedUnmounts(current);
-        current.return = null;
+        current["return"] = null;
         current.child = null;
         current.alternate &&
-          ((current.alternate.child = null), (current.alternate.return = null));
+          ((current.alternate.child = null),
+          (current.alternate["return"] = null));
       },
       commitWork: function(current, finishedWork) {
         commitContainer(finishedWork);
       },
       commitLifeCycles: commitLifeCycles,
       commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+      commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
     };
@@ -4090,151 +4167,6 @@ function ReactFiberCommitWork(config, captureError) {
   var commitMount = mutation.commitMount;
   invariant(!1, "Mutating reconciler is disabled.");
 }
-function ReactFiberUnwindWork(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  markLegacyErrorBoundaryAsFailed,
-  isAlreadyFailedLegacyErrorBoundary,
-  onUncaughtError
-) {
-  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
-    expirationTime = createUpdate(expirationTime);
-    expirationTime.tag = 3;
-    expirationTime.payload = { element: null };
-    var error = errorInfo.value;
-    expirationTime.callback = function() {
-      onUncaughtError(error);
-      logError(fiber, errorInfo);
-    };
-    return expirationTime;
-  }
-  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
-    expirationTime = createUpdate(expirationTime);
-    expirationTime.tag = 3;
-    var inst = fiber.stateNode;
-    null !== inst &&
-      "function" === typeof inst.componentDidCatch &&
-      (expirationTime.callback = function() {
-        markLegacyErrorBoundaryAsFailed(this);
-        var error = errorInfo.value,
-          stack = errorInfo.stack;
-        logError(fiber, errorInfo);
-        this.componentDidCatch(error, {
-          componentStack: null !== stack ? stack : ""
-        });
-      });
-    return expirationTime;
-  }
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
-  return {
-    throwException: function(
-      returnFiber,
-      sourceFiber,
-      rawValue,
-      renderExpirationTime
-    ) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      sourceFiber = createCapturedValue(rawValue, sourceFiber);
-      do {
-        switch (returnFiber.tag) {
-          case 3:
-            returnFiber.effectTag |= 1024;
-            sourceFiber = createRootErrorUpdate(
-              returnFiber,
-              sourceFiber,
-              renderExpirationTime
-            );
-            enqueueCapturedUpdate(
-              returnFiber,
-              sourceFiber,
-              renderExpirationTime
-            );
-            return;
-          case 2:
-            rawValue = sourceFiber;
-            var _instance = returnFiber.stateNode;
-            if (
-              0 === (returnFiber.effectTag & 64) &&
-              null !== _instance &&
-              "function" === typeof _instance.componentDidCatch &&
-              !isAlreadyFailedLegacyErrorBoundary(_instance)
-            ) {
-              returnFiber.effectTag |= 1024;
-              sourceFiber = createClassErrorUpdate(
-                returnFiber,
-                rawValue,
-                renderExpirationTime
-              );
-              enqueueCapturedUpdate(
-                returnFiber,
-                sourceFiber,
-                renderExpirationTime
-              );
-              return;
-            }
-        }
-        returnFiber = returnFiber.return;
-      } while (null !== returnFiber);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
-      }
-    },
-    createRootErrorUpdate: createRootErrorUpdate,
-    createClassErrorUpdate: createClassErrorUpdate
-  };
-}
 var NO_CONTEXT = {};
 function ReactFiberHostContext(config, stack) {
   function requiredContext(c) {
@@ -4291,7 +4223,7 @@ function ReactFiberHydrationContext(config) {
     var fiber = new FiberNode(5, null, null, 0);
     fiber.type = "DELETED";
     fiber.stateNode = instance;
-    fiber.return = returnFiber;
+    fiber["return"] = returnFiber;
     fiber.effectTag = 8;
     null !== returnFiber.lastEffect
       ? ((returnFiber.lastEffect.nextEffect = fiber),
@@ -4323,11 +4255,11 @@ function ReactFiberHydrationContext(config) {
   }
   function popToNextHostParent(fiber) {
     for (
-      fiber = fiber.return;
+      fiber = fiber["return"];
       null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
 
     )
-      fiber = fiber.return;
+      fiber = fiber["return"];
     hydrationParentFiber = fiber;
   }
   var shouldSetTextContent = config.shouldSetTextContent;
@@ -4561,7 +4493,7 @@ function ReactFiberLegacyContext(stack) {
       ) {
         if (isContextProvider(fiber))
           return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber.return;
+        fiber = fiber["return"];
         invariant(
           fiber,
           "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
@@ -4628,12 +4560,12 @@ function ReactFiberScheduler(config) {
   function resetStack() {
     if (null !== nextUnitOfWork)
       for (
-        var interruptedWork = nextUnitOfWork.return;
+        var interruptedWork = nextUnitOfWork["return"];
         null !== interruptedWork;
 
       )
         unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork.return);
+          (interruptedWork = interruptedWork["return"]);
     nextRoot = null;
     nextRenderExpirationTime = 0;
     nextUnitOfWork = null;
@@ -4645,71 +4577,74 @@ function ReactFiberScheduler(config) {
       legacyErrorBoundariesThatAlreadyFailed.has(instance)
     );
   }
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    null === legacyErrorBoundariesThatAlreadyFailed
-      ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-      : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-  }
-  function completeUnitOfWork(workInProgress) {
+  function completeUnitOfWork(workInProgress$jscomp$0) {
     for (;;) {
-      var current = workInProgress.alternate,
-        returnFiber = workInProgress.return,
-        siblingFiber = workInProgress.sibling;
-      if (0 === (workInProgress.effectTag & 512)) {
+      var current = workInProgress$jscomp$0.alternate,
+        returnFiber = workInProgress$jscomp$0["return"],
+        siblingFiber = workInProgress$jscomp$0.sibling;
+      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
         current = completeWork(
           current,
-          workInProgress,
+          workInProgress$jscomp$0,
           nextRenderExpirationTime
         );
+        var workInProgress = workInProgress$jscomp$0;
         if (
           1073741823 === nextRenderExpirationTime ||
           1073741823 !== workInProgress.expirationTime
         ) {
-          var newExpirationTime = 0;
-          switch (workInProgress.tag) {
+          b: switch (workInProgress.tag) {
             case 3:
             case 2:
-              var updateQueue = workInProgress.updateQueue;
-              null !== updateQueue &&
-                (newExpirationTime = updateQueue.expirationTime);
+              var newExpirationTime = workInProgress.updateQueue;
+              newExpirationTime =
+                null === newExpirationTime
+                  ? 0
+                  : newExpirationTime.expirationTime;
+              break b;
+            default:
+              newExpirationTime = 0;
           }
-          for (updateQueue = workInProgress.child; null !== updateQueue; )
-            0 !== updateQueue.expirationTime &&
+          for (var child = workInProgress.child; null !== child; )
+            0 !== child.expirationTime &&
               (0 === newExpirationTime ||
-                newExpirationTime > updateQueue.expirationTime) &&
-              (newExpirationTime = updateQueue.expirationTime),
-              (updateQueue = updateQueue.sibling);
+                newExpirationTime > child.expirationTime) &&
+              (newExpirationTime = child.expirationTime),
+              (child = child.sibling);
           workInProgress.expirationTime = newExpirationTime;
         }
         if (null !== current) return current;
         null !== returnFiber &&
           0 === (returnFiber.effectTag & 512) &&
           (null === returnFiber.firstEffect &&
-            (returnFiber.firstEffect = workInProgress.firstEffect),
-          null !== workInProgress.lastEffect &&
+            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
+          null !== workInProgress$jscomp$0.lastEffect &&
             (null !== returnFiber.lastEffect &&
-              (returnFiber.lastEffect.nextEffect = workInProgress.firstEffect),
-            (returnFiber.lastEffect = workInProgress.lastEffect)),
-          1 < workInProgress.effectTag &&
+              (returnFiber.lastEffect.nextEffect =
+                workInProgress$jscomp$0.firstEffect),
+            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
+          1 < workInProgress$jscomp$0.effectTag &&
             (null !== returnFiber.lastEffect
-              ? (returnFiber.lastEffect.nextEffect = workInProgress)
-              : (returnFiber.firstEffect = workInProgress),
-            (returnFiber.lastEffect = workInProgress)));
+              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
+              : (returnFiber.firstEffect = workInProgress$jscomp$0),
+            (returnFiber.lastEffect = workInProgress$jscomp$0)));
         if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress = returnFiber;
+        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
         else {
           isRootReadyForCommit = !0;
           break;
         }
       } else {
-        workInProgress = unwindWork(workInProgress);
-        if (null !== workInProgress)
-          return (workInProgress.effectTag &= 511), workInProgress;
+        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
+        if (null !== workInProgress$jscomp$0)
+          return (
+            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
+          );
         null !== returnFiber &&
           ((returnFiber.firstEffect = returnFiber.lastEffect = null),
           (returnFiber.effectTag |= 512));
         if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress = returnFiber;
+        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
         else break;
       }
     }
@@ -4761,18 +4696,13 @@ function ReactFiberScheduler(config) {
           break;
         }
         isAsync = nextUnitOfWork;
-        var returnFiber = isAsync.return;
+        var returnFiber = isAsync["return"];
         if (null === returnFiber) {
           didFatal = !0;
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(
-          returnFiber,
-          isAsync,
-          thrownValue,
-          nextRenderExpirationTime
-        );
+        throwException(returnFiber, isAsync, thrownValue);
         nextUnitOfWork = completeUnitOfWork(isAsync);
       }
       break;
@@ -4789,61 +4719,55 @@ function ReactFiberScheduler(config) {
       "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
     );
   }
-  function onCommitPhaseError(fiber, error) {
-    var JSCompiler_inline_result;
+  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
+    sourceFiber = {
+      value: value,
+      source: sourceFiber,
+      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
+    };
+    insertUpdateIntoFiber(boundaryFiber, {
+      expirationTime: expirationTime,
+      partialState: null,
+      callback: null,
+      isReplace: !1,
+      isForced: !1,
+      capturedValue: sourceFiber,
+      next: null
+    });
+    scheduleWork(boundaryFiber, expirationTime);
+  }
+  function onCommitPhaseError(fiber$jscomp$0, error) {
     a: {
       invariant(
         !isWorking || isCommitting,
         "dispatch: Cannot dispatch during the render phase."
       );
-      for (
-        JSCompiler_inline_result = fiber.return;
-        null !== JSCompiler_inline_result;
-
-      ) {
-        switch (JSCompiler_inline_result.tag) {
+      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
+        switch (fiber.tag) {
           case 2:
-            var instance = JSCompiler_inline_result.stateNode;
+            var instance = fiber.stateNode;
             if (
-              "function" ===
-                typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
+              "function" === typeof fiber.type.getDerivedStateFromCatch ||
               ("function" === typeof instance.componentDidCatch &&
                 !isAlreadyFailedLegacyErrorBoundary(instance))
             ) {
-              fiber = createCapturedValue(error, fiber);
-              fiber = createClassErrorUpdate(
-                JSCompiler_inline_result,
-                fiber,
-                1
-              );
-              enqueueUpdate(JSCompiler_inline_result, fiber, 1);
-              scheduleWork(JSCompiler_inline_result, 1);
-              JSCompiler_inline_result = void 0;
+              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
+              fiber$jscomp$0 = void 0;
               break a;
             }
             break;
           case 3:
-            fiber = createCapturedValue(error, fiber);
-            fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
-            enqueueUpdate(JSCompiler_inline_result, fiber, 1);
-            scheduleWork(JSCompiler_inline_result, 1);
-            JSCompiler_inline_result = void 0;
+            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
+            fiber$jscomp$0 = void 0;
             break a;
         }
-        JSCompiler_inline_result = JSCompiler_inline_result.return;
+        fiber = fiber["return"];
       }
-      3 === fiber.tag &&
-        ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
-        (JSCompiler_inline_result = createRootErrorUpdate(
-          fiber,
-          JSCompiler_inline_result,
-          1
-        )),
-        enqueueUpdate(fiber, JSCompiler_inline_result, 1),
-        scheduleWork(fiber, 1));
-      JSCompiler_inline_result = void 0;
+      3 === fiber$jscomp$0.tag &&
+        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
+      fiber$jscomp$0 = void 0;
     }
-    return JSCompiler_inline_result;
+    return fiber$jscomp$0;
   }
   function computeExpirationForFiber(fiber) {
     fiber =
@@ -4871,7 +4795,7 @@ function ReactFiberScheduler(config) {
           (0 === fiber.alternate.expirationTime ||
             fiber.alternate.expirationTime > expirationTime) &&
           (fiber.alternate.expirationTime = expirationTime);
-        if (null === fiber.return)
+        if (null === fiber["return"])
           if (3 === fiber.tag) {
             var root = fiber.stateNode;
             !isWorking &&
@@ -4889,7 +4813,7 @@ function ReactFiberScheduler(config) {
             expirationTime = void 0;
             break a;
           }
-        fiber = fiber.return;
+        fiber = fiber["return"];
       }
       expirationTime = void 0;
     }
@@ -5129,7 +5053,7 @@ function ReactFiberScheduler(config) {
         error = void 0;
       try {
         for (; null !== nextEffect; )
-          nextEffect.effectTag & 256 &&
+          nextEffect.effectTag & 2048 &&
             commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
             (nextEffect = nextEffect.nextEffect);
       } catch (e) {
@@ -5205,6 +5129,8 @@ function ReactFiberScheduler(config) {
               didError,
               error
             );
+          effectTag$jscomp$0 & 256 &&
+            commitErrorLogging(nextEffect, onUncaughtError);
           effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
           var next = nextEffect.nextEffect;
           nextEffect.nextEffect = null;
@@ -5267,21 +5193,21 @@ function ReactFiberScheduler(config) {
     legacyContext,
     stack,
     scheduleWork,
-    markLegacyErrorBoundaryAsFailed,
-    isAlreadyFailedLegacyErrorBoundary,
-    onUncaughtError
+    isAlreadyFailedLegacyErrorBoundary
   );
   var throwException = hostContext.throwException,
     unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork,
-    createRootErrorUpdate = hostContext.createRootErrorUpdate,
-    createClassErrorUpdate = hostContext.createClassErrorUpdate;
+    unwindInterruptedWork = hostContext.unwindInterruptedWork;
   hostContext = ReactFiberCommitWork(
     config,
     onCommitPhaseError,
     scheduleWork,
     computeExpirationForFiber,
-    markLegacyErrorBoundaryAsFailed,
+    function(instance) {
+      null === legacyErrorBoundariesThatAlreadyFailed
+        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
+        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+    },
     recalculateCurrentTime
   );
   var commitBeforeMutationLifeCycles =
@@ -5291,6 +5217,7 @@ function ReactFiberScheduler(config) {
     commitDeletion = hostContext.commitDeletion,
     commitWork = hostContext.commitWork,
     commitLifeCycles = hostContext.commitLifeCycles,
+    commitErrorLogging = hostContext.commitErrorLogging,
     commitAttachRef = hostContext.commitAttachRef,
     commitDetachRef = hostContext.commitDetachRef,
     now = config.now,
@@ -5458,11 +5385,15 @@ function ReactFiberReconciler$1(config) {
       ? (container.context = parentComponent)
       : (container.pendingContext = parentComponent);
     container = callback;
-    callback = createUpdate(expirationTime);
-    callback.payload = { element: element };
-    container = void 0 === container ? null : container;
-    null !== container && (callback.callback = container);
-    enqueueUpdate(currentTime, callback, expirationTime);
+    insertUpdateIntoFiber(currentTime, {
+      expirationTime: expirationTime,
+      partialState: { element: element },
+      callback: void 0 === container ? null : container,
+      isReplace: !1,
+      isForced: !1,
+      capturedValue: null,
+      next: null
+    });
     scheduleWork(currentTime, expirationTime);
     return expirationTime;
   }
@@ -5583,8 +5514,8 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
   ReactFiberReconciler$3 =
     (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
     ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3.default
-    ? ReactFiberReconciler$3.default
+  reactReconciler = ReactFiberReconciler$3["default"]
+    ? ReactFiberReconciler$3["default"]
     : ReactFiberReconciler$3,
   nextReactTag = 2,
   ReactFabricHostComponent = (function() {
@@ -5864,7 +5795,7 @@ var roots = new Map(),
       var root = roots.get(containerTag);
       root &&
         ReactFabricRenderer.updateContainer(null, root, null, function() {
-          roots.delete(containerTag);
+          roots["delete"](containerTag);
         });
     },
     createPortal: function(children, containerTag) {
@@ -5939,4 +5870,6 @@ ReactFabricRenderer.injectIntoDevTools({
 });
 var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
   ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
-module.exports = ReactFabric$3.default ? ReactFabric$3.default : ReactFabric$3;
+module.exports = ReactFabric$3["default"]
+  ? ReactFabric$3["default"]
+  : ReactFabric$3;
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
index 6c6430d3eff1..21d9a6c1d543 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactNativeRenderer-dev
  * @preventMunge
  */
 
@@ -27,9 +26,9 @@ var deepDiffer = require("deepDiffer");
 var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
-var checkPropTypes = require("prop-types/checkPropTypes");
 var shallowEqual = require("fbjs/lib/shallowEqual");
 var ExceptionsManager = require("ExceptionsManager");
+var checkPropTypes = require("prop-types/checkPropTypes");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
 
 var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
@@ -971,7 +970,7 @@ var ForwardRef = 14;
 
 function getParent(inst) {
   do {
-    inst = inst.return;
+    inst = inst["return"];
     // TODO: If this is a HostRoot we might want to bail out.
     // That is depending on if we want nested subtrees (layers) to bubble
     // events to their parent. We could also go through parentNode on the
@@ -2717,21 +2716,23 @@ RCTEventEmitter.register(ReactNativeEventEmitter);
 
 // The Symbol used to tag the ReactElement-like types. If there is no native Symbol
 // nor polyfill, then a plain number is used for performance.
-var hasSymbol = typeof Symbol === "function" && Symbol.for;
+var hasSymbol = typeof Symbol === "function" && Symbol["for"];
 
-var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 0xeac9;
-var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 0xeaca;
-var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
+var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
+var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
-  ? Symbol.for("react.strict_mode")
+  ? Symbol["for"]("react.strict_mode")
   : 0xeacc;
-var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 0xeacd;
-var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 0xeace;
-var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 0xeacf;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
+var REACT_ASYNC_MODE_TYPE = hasSymbol
+  ? Symbol["for"]("react.async_mode")
+  : 0xeacf;
 var REACT_FORWARD_REF_TYPE = hasSymbol
-  ? Symbol.for("react.forward_ref")
+  ? Symbol["for"]("react.forward_ref")
   : 0xead0;
 
 var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
@@ -2846,7 +2847,7 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
   do {
     info += describeFiber(node);
     // Otherwise this return pointer might point to the wrong tree:
-    node = node.return;
+    node = node["return"];
   } while (node);
   return info;
 }
@@ -3789,10 +3790,11 @@ var ContentReset = /*          */ 16;
 var Callback = /*              */ 32;
 var DidCapture = /*            */ 64;
 var Ref = /*                   */ 128;
-var Snapshot = /*              */ 256;
+var ErrLog = /*                */ 256;
+var Snapshot = /*              */ 2048;
 
 // Union of all host effects
-var HostEffectMask = /*        */ 511;
+var HostEffectMask = /*        */ 2559;
 
 var Incomplete = /*            */ 512;
 var ShouldCapture = /*         */ 1024;
@@ -3809,15 +3811,15 @@ function isFiberMountedImpl(fiber) {
     if ((node.effectTag & Placement) !== NoEffect) {
       return MOUNTING;
     }
-    while (node.return) {
-      node = node.return;
+    while (node["return"]) {
+      node = node["return"];
       if ((node.effectTag & Placement) !== NoEffect) {
         return MOUNTING;
       }
     }
   } else {
-    while (node.return) {
-      node = node.return;
+    while (node["return"]) {
+      node = node["return"];
     }
   }
   if (node.tag === HostRoot) {
@@ -3889,7 +3891,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
   var a = fiber;
   var b = alternate;
   while (true) {
-    var parentA = a.return;
+    var parentA = a["return"];
     var parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) {
       // We're at the root.
@@ -3919,7 +3921,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       invariant(false, "Unable to find node on an unmounted component.");
     }
 
-    if (a.return !== b.return) {
+    if (a["return"] !== b["return"]) {
       // The return pointer of A and the return pointer of B point to different
       // fibers. We assume that return pointers never criss-cross, so A must
       // belong to the child set of A.return, and B must belong to the child
@@ -4007,7 +4009,7 @@ function findCurrentHostFiber(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child) {
-      node.child.return = node;
+      node.child["return"] = node;
       node = node.child;
       continue;
     }
@@ -4015,12 +4017,12 @@ function findCurrentHostFiber(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node.return || node.return === currentParent) {
+      if (!node["return"] || node["return"] === currentParent) {
         return null;
       }
-      node = node.return;
+      node = node["return"];
     }
-    node.sibling.return = node.return;
+    node.sibling["return"] = node["return"];
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -4040,7 +4042,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child && node.tag !== HostPortal) {
-      node.child.return = node;
+      node.child["return"] = node;
       node = node.child;
       continue;
     }
@@ -4048,12 +4050,12 @@ function findCurrentHostFiberWithNoPortals(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node.return || node.return === currentParent) {
+      if (!node["return"] || node["return"] === currentParent) {
         return null;
       }
-      node = node.return;
+      node = node["return"];
     }
-    node.sibling.return = node.return;
+    node.sibling["return"] = node["return"];
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -4136,7 +4138,7 @@ function FiberNode(tag, pendingProps, key, mode) {
   this.stateNode = null;
 
   // Fiber
-  this.return = null;
+  this["return"] = null;
   this.child = null;
   this.sibling = null;
   this.index = 0;
@@ -4421,7 +4423,7 @@ function assignFiberPropertiesInDEV(target, source) {
   target.key = source.key;
   target.type = source.type;
   target.stateNode = source.stateNode;
-  target.return = source.return;
+  target["return"] = source["return"];
   target.child = source.child;
   target.sibling = source.sibling;
   target.index = source.index;
@@ -4704,7 +4706,7 @@ var ReactStrictModeWarnings = {
         maybeStrictRoot = fiber;
       }
 
-      fiber = fiber.return;
+      fiber = fiber["return"];
     }
 
     return maybeStrictRoot;
@@ -4825,6 +4827,16 @@ var ReactStrictModeWarnings = {
       return;
     }
 
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    // Note that it is sufficient to check for the presence of a
+    // single lifecycle, componentWillMount, with the polyfill flag.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning === true
+    ) {
+      return;
+    }
+
     var warningsForRoot = void 0;
     if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
       warningsForRoot = {
@@ -4840,23 +4852,19 @@ var ReactStrictModeWarnings = {
 
     var unsafeLifecycles = [];
     if (
-      (typeof instance.componentWillMount === "function" &&
-        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
+      typeof instance.componentWillMount === "function" ||
       typeof instance.UNSAFE_componentWillMount === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillMount");
     }
     if (
-      (typeof instance.componentWillReceiveProps === "function" &&
-        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-          true) ||
+      typeof instance.componentWillReceiveProps === "function" ||
       typeof instance.UNSAFE_componentWillReceiveProps === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
     }
     if (
-      (typeof instance.componentWillUpdate === "function" &&
-        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
+      typeof instance.componentWillUpdate === "function" ||
       typeof instance.UNSAFE_componentWillUpdate === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillUpdate");
@@ -4896,7 +4904,7 @@ function getCurrentFiberOwnerName() {
   return null;
 }
 
-function getCurrentFiberStackAddendum$1() {
+function getCurrentFiberStackAddendum() {
   {
     var fiber = ReactDebugCurrentFiber.current;
     if (fiber === null) {
@@ -4916,7 +4924,7 @@ function resetCurrentFiber() {
 }
 
 function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum$1;
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
   ReactDebugCurrentFiber.current = fiber;
   ReactDebugCurrentFiber.phase = null;
 }
@@ -4932,7 +4940,7 @@ var ReactDebugCurrentFiber = {
   setCurrentFiber: setCurrentFiber,
   setCurrentPhase: setCurrentPhase,
   getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum$1
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
 };
 
 // Prefix measurements so that it's possible to filter them.
@@ -5089,13 +5097,13 @@ var pauseTimers = function() {
     if (fiber._debugIsCurrentlyTiming) {
       endFiberMark(fiber, null, null);
     }
-    fiber = fiber.return;
+    fiber = fiber["return"];
   }
 };
 
 var resumeTimersRecursively = function(fiber) {
-  if (fiber.return !== null) {
-    resumeTimersRecursively(fiber.return);
+  if (fiber["return"] !== null) {
+    resumeTimersRecursively(fiber["return"]);
   }
   if (fiber._debugIsCurrentlyTiming) {
     beginFiberMark(fiber, null);
@@ -5187,7 +5195,7 @@ function stopWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber.return;
+    currentFiber = fiber["return"];
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -5202,7 +5210,7 @@ function stopFailedWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber.return;
+    currentFiber = fiber["return"];
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -5392,232 +5400,100 @@ function stopCommitLifeCyclesTimer() {
   }
 }
 
-// UpdateQueue is a linked list of prioritized updates.
-//
-// Like fibers, update queues come in pairs: a current queue, which represents
-// the visible state of the screen, and a work-in-progress queue, which is
-// can be mutated and processed asynchronously before it is committed — a form
-// of double buffering. If a work-in-progress render is discarded before
-// finishing, we create a new work-in-progress by cloning the current queue.
-//
-// Both queues share a persistent, singly-linked list structure. To schedule an
-// update, we append it to the end of both queues. Each queue maintains a
-// pointer to first update in the persistent list that hasn't been processed.
-// The work-in-progress pointer always has a position equal to or greater than
-// the current queue, since we always work on that one. The current queue's
-// pointer is only updated during the commit phase, when we swap in the
-// work-in-progress.
-//
-// For example:
-//
-//   Current pointer:           A - B - C - D - E - F
-//   Work-in-progress pointer:              D - E - F
-//                                          ^
-//                                          The work-in-progress queue has
-//                                          processed more updates than current.
-//
-// The reason we append to both queues is because otherwise we might drop
-// updates without ever processing them. For example, if we only add updates to
-// the work-in-progress queue, some updates could be lost whenever a work-in
-// -progress render restarts by cloning from current. Similarly, if we only add
-// updates to the current queue, the updates will be lost whenever an already
-// in-progress queue commits and swaps with the current queue. However, by
-// adding to both queues, we guarantee that the update will be part of the next
-// work-in-progress. (And because the work-in-progress queue becomes the
-// current queue once it commits, there's no danger of applying the same
-// update twice.)
-//
-// Prioritization
-// --------------
-//
-// Updates are not sorted by priority, but by insertion; new updates are always
-// appended to the end of the list.
-//
-// The priority is still important, though. When processing the update queue
-// during the render phase, only the updates with sufficient priority are
-// included in the result. If we skip an update because it has insufficient
-// priority, it remains in the queue to be processed later, during a lower
-// priority render. Crucially, all updates subsequent to a skipped update also
-// remain in the queue *regardless of their priority*. That means high priority
-// updates are sometimes processed twice, at two separate priorities. We also
-// keep track of a base state, that represents the state before the first
-// update in the queue is applied.
-//
-// For example:
-//
-//   Given a base state of '', and the following queue of updates
-//
-//     A1 - B2 - C1 - D2
-//
-//   where the number indicates the priority, and the update is applied to the
-//   previous state by appending a letter, React will process these updates as
-//   two separate renders, one per distinct priority level:
-//
-//   First render, at priority 1:
-//     Base state: ''
-//     Updates: [A1, C1]
-//     Result state: 'AC'
-//
-//   Second render, at priority 2:
-//     Base state: 'A'            <-  The base state does not include C1,
-//                                    because B2 was skipped.
-//     Updates: [B2, C1, D2]      <-  C1 was rebased on top of B2
-//     Result state: 'ABCD'
-//
-// Because we process updates in insertion order, and rebase high priority
-// updates when preceding updates are skipped, the final result is deterministic
-// regardless of priority. Intermediate state may vary according to system
-// resources, but the final state is always the same.
-
-var UpdateState = 0;
-var ReplaceState = 1;
-var ForceUpdate = 2;
-var CaptureUpdate = 3;
-
 var didWarnUpdateInsideUpdate = void 0;
-var currentlyProcessingQueue = void 0;
-var resetCurrentlyProcessingQueue = void 0;
+
 {
   didWarnUpdateInsideUpdate = false;
-  currentlyProcessingQueue = null;
-  resetCurrentlyProcessingQueue = function() {
-    currentlyProcessingQueue = null;
-  };
 }
 
+// Callbacks are not validated until invocation
+
+// Singly linked-list of updates. When an update is scheduled, it is added to
+// the queue of the current fiber and the work-in-progress fiber. The two queues
+// are separate but they share a persistent structure.
+//
+// During reconciliation, updates are removed from the work-in-progress fiber,
+// but they remain on the current fiber. That ensures that if a work-in-progress
+// is aborted, the aborted updates are recovered by cloning from current.
+//
+// The work-in-progress queue is always a subset of the current queue.
+//
+// When the tree is committed, the work-in-progress becomes the current.
+
 function createUpdateQueue(baseState) {
   var queue = {
-    expirationTime: NoWork,
     baseState: baseState,
-    firstUpdate: null,
-    lastUpdate: null,
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
-    firstEffect: null,
-    lastEffect: null,
-    firstCapturedEffect: null,
-    lastCapturedEffect: null,
-    hasForceUpdate: false
-  };
-  return queue;
-}
-
-function cloneUpdateQueue(currentQueue) {
-  var queue = {
-    expirationTime: currentQueue.expirationTime,
-    baseState: currentQueue.baseState,
-    firstUpdate: currentQueue.firstUpdate,
-    lastUpdate: currentQueue.lastUpdate,
-
-    // TODO: With resuming, if we bail out and resuse the child tree, we should
-    // keep these effects.
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
-
+    expirationTime: NoWork,
+    first: null,
+    last: null,
+    callbackList: null,
     hasForceUpdate: false,
-
-    firstEffect: null,
-    lastEffect: null,
-
-    firstCapturedEffect: null,
-    lastCapturedEffect: null
+    isInitialized: false,
+    capturedValues: null
   };
+  {
+    queue.isProcessing = false;
+  }
   return queue;
 }
 
-function createUpdate(expirationTime) {
-  return {
-    expirationTime: expirationTime,
-
-    tag: UpdateState,
-    payload: null,
-    callback: null,
-
-    next: null,
-    nextEffect: null
-  };
-}
-
-function appendUpdateToQueue(queue, update, expirationTime) {
+function insertUpdateIntoQueue(queue, update) {
   // Append the update to the end of the list.
-  if (queue.lastUpdate === null) {
+  if (queue.last === null) {
     // Queue is empty
-    queue.firstUpdate = queue.lastUpdate = update;
+    queue.first = queue.last = update;
   } else {
-    queue.lastUpdate.next = update;
-    queue.lastUpdate = update;
+    queue.last.next = update;
+    queue.last = update;
   }
   if (
     queue.expirationTime === NoWork ||
-    queue.expirationTime > expirationTime
+    queue.expirationTime > update.expirationTime
   ) {
-    // The incoming update has the earliest expiration of any update in the
-    // queue. Update the queue's expiration time.
-    queue.expirationTime = expirationTime;
+    queue.expirationTime = update.expirationTime;
   }
 }
 
-function enqueueUpdate(fiber, update, expirationTime) {
-  // Update queues are created lazily.
-  var alternate = fiber.alternate;
-  var queue1 = void 0;
+var q1 = void 0;
+var q2 = void 0;
+function ensureUpdateQueues(fiber) {
+  q1 = q2 = null;
+  // We'll have at least one and at most two distinct update queues.
+  var alternateFiber = fiber.alternate;
+  var queue1 = fiber.updateQueue;
+  if (queue1 === null) {
+    // TODO: We don't know what the base state will be until we begin work.
+    // It depends on which fiber is the next current. Initialize with an empty
+    // base state, then set to the memoizedState when rendering. Not super
+    // happy with this approach.
+    queue1 = fiber.updateQueue = createUpdateQueue(null);
+  }
+
   var queue2 = void 0;
-  if (alternate === null) {
-    // There's only one fiber.
-    queue1 = fiber.updateQueue;
-    queue2 = null;
-    if (queue1 === null) {
-      queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
-    }
-  } else {
-    // There are two owners.
-    queue1 = fiber.updateQueue;
-    queue2 = alternate.updateQueue;
-    if (queue1 === null) {
-      if (queue2 === null) {
-        // Neither fiber has an update queue. Create new ones.
-        queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
-        queue2 = alternate.updateQueue = createUpdateQueue(
-          alternate.memoizedState
-        );
-      } else {
-        // Only one fiber has an update queue. Clone to create a new one.
-        queue1 = fiber.updateQueue = cloneUpdateQueue(queue2);
-      }
-    } else {
-      if (queue2 === null) {
-        // Only one fiber has an update queue. Clone to create a new one.
-        queue2 = alternate.updateQueue = cloneUpdateQueue(queue1);
-      } else {
-        // Both owners have an update queue.
-      }
+  if (alternateFiber !== null) {
+    queue2 = alternateFiber.updateQueue;
+    if (queue2 === null) {
+      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
     }
-  }
-  if (queue2 === null || queue1 === queue2) {
-    // There's only a single queue.
-    appendUpdateToQueue(queue1, update, expirationTime);
   } else {
-    // There are two queues. We need to append the update to both queues,
-    // while accounting for the persistent structure of the list — we don't
-    // want the same update to be added multiple times.
-    if (queue1.lastUpdate === null || queue2.lastUpdate === null) {
-      // One of the queues is not empty. We must add the update to both queues.
-      appendUpdateToQueue(queue1, update, expirationTime);
-      appendUpdateToQueue(queue2, update, expirationTime);
-    } else {
-      // Both queues are non-empty. The last update is the same in both lists,
-      // because of structural sharing. So, only append to one of the lists.
-      appendUpdateToQueue(queue1, update, expirationTime);
-      // But we still need to update the `lastUpdate` pointer of queue2.
-      queue2.lastUpdate = update;
-    }
+    queue2 = null;
   }
+  queue2 = queue2 !== queue1 ? queue2 : null;
 
+  // Use module variables instead of returning a tuple
+  q1 = queue1;
+  q2 = queue2;
+}
+
+function insertUpdateIntoFiber(fiber, update) {
+  ensureUpdateQueues(fiber);
+  var queue1 = q1;
+  var queue2 = q2;
+
+  // Warn if an update is scheduled from inside an updater function.
   {
     if (
-      fiber.tag === ClassComponent &&
-      (currentlyProcessingQueue === queue1 ||
-        (queue2 !== null && currentlyProcessingQueue === queue2)) &&
+      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
       !didWarnUpdateInsideUpdate
     ) {
       warning(
@@ -5630,328 +5506,225 @@ function enqueueUpdate(fiber, update, expirationTime) {
       didWarnUpdateInsideUpdate = true;
     }
   }
-}
 
-function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
-  // Captured updates go into a separate list, and only on the work-in-
-  // progress queue.
-  var workInProgressQueue = workInProgress.updateQueue;
-  if (workInProgressQueue === null) {
-    workInProgressQueue = workInProgress.updateQueue = createUpdateQueue(
-      workInProgress.memoizedState
-    );
-  } else {
-    // TODO: I put this here rather than createWorkInProgress so that we don't
-    // clone the queue unnecessarily. There's probably a better way to
-    // structure this.
-    workInProgressQueue = ensureWorkInProgressQueueIsAClone(
-      workInProgress,
-      workInProgressQueue
-    );
+  // If there's only one queue, add the update to that queue and exit.
+  if (queue2 === null) {
+    insertUpdateIntoQueue(queue1, update);
+    return;
   }
 
-  // Append the update to the end of the list.
-  if (workInProgressQueue.lastCapturedUpdate === null) {
-    // This is the first render phase update
-    workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update;
-  } else {
-    workInProgressQueue.lastCapturedUpdate.next = update;
-    workInProgressQueue.lastCapturedUpdate = update;
-  }
-  if (
-    workInProgressQueue.expirationTime === NoWork ||
-    workInProgressQueue.expirationTime > renderExpirationTime
-  ) {
-    // The incoming update has the earliest expiration of any update in the
-    // queue. Update the queue's expiration time.
-    workInProgressQueue.expirationTime = renderExpirationTime;
+  // If either queue is empty, we need to add to both queues.
+  if (queue1.last === null || queue2.last === null) {
+    insertUpdateIntoQueue(queue1, update);
+    insertUpdateIntoQueue(queue2, update);
+    return;
   }
+
+  // If both lists are not empty, the last update is the same for both lists
+  // because of structural sharing. So, we should only append to one of
+  // the lists.
+  insertUpdateIntoQueue(queue1, update);
+  // But we still need to update the `last` pointer of queue2.
+  queue2.last = update;
 }
 
-function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
-  var current = workInProgress.alternate;
-  if (current !== null) {
-    // If the work-in-progress queue is equal to the current queue,
-    // we need to clone it first.
-    if (queue === current.updateQueue) {
-      queue = workInProgress.updateQueue = cloneUpdateQueue(queue);
-    }
+function getUpdateExpirationTime(fiber) {
+  switch (fiber.tag) {
+    case HostRoot:
+    case ClassComponent:
+      var updateQueue = fiber.updateQueue;
+      if (updateQueue === null) {
+        return NoWork;
+      }
+      return updateQueue.expirationTime;
+    default:
+      return NoWork;
   }
-  return queue;
 }
 
-function getStateFromUpdate(
-  workInProgress,
-  queue,
-  update,
-  prevState,
-  nextProps,
-  instance
-) {
-  switch (update.tag) {
-    case ReplaceState: {
-      var _payload = update.payload;
-      if (typeof _payload === "function") {
-        // Updater function
-        {
-          if (
-            debugRenderPhaseSideEffects ||
-            (debugRenderPhaseSideEffectsForStrictMode &&
-              workInProgress.mode & StrictMode)
-          ) {
-            _payload.call(instance, prevState, nextProps);
-          }
-        }
-        return _payload.call(instance, prevState, nextProps);
-      }
-      // State object
-      return _payload;
-    }
-    case CaptureUpdate: {
-      workInProgress.effectTag =
-        (workInProgress.effectTag & ~ShouldCapture) | DidCapture;
-    }
-    // Intentional fallthrough
-    case UpdateState: {
-      var _payload2 = update.payload;
-      var partialState = void 0;
-      if (typeof _payload2 === "function") {
-        // Updater function
-        {
-          if (
-            debugRenderPhaseSideEffects ||
-            (debugRenderPhaseSideEffectsForStrictMode &&
-              workInProgress.mode & StrictMode)
-          ) {
-            _payload2.call(instance, prevState, nextProps);
-          }
-        }
-        partialState = _payload2.call(instance, prevState, nextProps);
-      } else {
-        // Partial state object
-        partialState = _payload2;
-      }
-      if (partialState === null || partialState === undefined) {
-        // Null and undefined are treated as no-ops.
-        return prevState;
-      }
-      // Merge the partial state and the previous state.
-      return Object.assign({}, prevState, partialState);
-    }
-    case ForceUpdate: {
-      queue.hasForceUpdate = true;
-      return prevState;
-    }
+function getStateFromUpdate(update, instance, prevState, props) {
+  var partialState = update.partialState;
+  if (typeof partialState === "function") {
+    return partialState.call(instance, prevState, props);
+  } else {
+    return partialState;
   }
-  return prevState;
 }
 
 function processUpdateQueue(
+  current,
   workInProgress,
   queue,
-  props,
   instance,
+  props,
   renderExpirationTime
 ) {
-  if (
-    queue.expirationTime === NoWork ||
-    queue.expirationTime > renderExpirationTime
-  ) {
-    // Insufficient priority. Bailout.
-    return;
+  if (current !== null && current.updateQueue === queue) {
+    // We need to create a work-in-progress queue, by cloning the current queue.
+    var currentQueue = queue;
+    queue = workInProgress.updateQueue = {
+      baseState: currentQueue.baseState,
+      expirationTime: currentQueue.expirationTime,
+      first: currentQueue.first,
+      last: currentQueue.last,
+      isInitialized: currentQueue.isInitialized,
+      capturedValues: currentQueue.capturedValues,
+      // These fields are no longer valid because they were already committed.
+      // Reset them.
+      callbackList: null,
+      hasForceUpdate: false
+    };
   }
 
-  queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
-
   {
-    currentlyProcessingQueue = queue;
+    // Set this flag so we can warn if setState is called inside the update
+    // function of another setState.
+    queue.isProcessing = true;
+  }
+
+  // Reset the remaining expiration time. If we skip over any updates, we'll
+  // increase this accordingly.
+  queue.expirationTime = NoWork;
+
+  // TODO: We don't know what the base state will be until we begin work.
+  // It depends on which fiber is the next current. Initialize with an empty
+  // base state, then set to the memoizedState when rendering. Not super
+  // happy with this approach.
+  var state = void 0;
+  if (queue.isInitialized) {
+    state = queue.baseState;
+  } else {
+    state = queue.baseState = workInProgress.memoizedState;
+    queue.isInitialized = true;
   }
-
-  // These values may change as we process the queue.
-  var newBaseState = queue.baseState;
-  var newFirstUpdate = null;
-  var newExpirationTime = NoWork;
-
-  // Iterate through the list of updates to compute the result.
-  var update = queue.firstUpdate;
-  var resultState = newBaseState;
+  var dontMutatePrevState = true;
+  var update = queue.first;
+  var didSkip = false;
   while (update !== null) {
     var updateExpirationTime = update.expirationTime;
     if (updateExpirationTime > renderExpirationTime) {
       // This update does not have sufficient priority. Skip it.
-      if (newFirstUpdate === null) {
-        // This is the first skipped update. It will be the first update in
-        // the new list.
-        newFirstUpdate = update;
-        // Since this is the first update that was skipped, the current result
-        // is the new base state.
-        newBaseState = resultState;
-      }
-      // Since this update will remain in the list, update the remaining
-      // expiration time.
+      var remainingExpirationTime = queue.expirationTime;
       if (
-        newExpirationTime === NoWork ||
-        newExpirationTime > updateExpirationTime
+        remainingExpirationTime === NoWork ||
+        remainingExpirationTime > updateExpirationTime
       ) {
-        newExpirationTime = updateExpirationTime;
+        // Update the remaining expiration time.
+        queue.expirationTime = updateExpirationTime;
       }
-    } else {
-      // This update does have sufficient priority. Process it and compute
-      // a new result.
-      resultState = getStateFromUpdate(
-        workInProgress,
-        queue,
-        update,
-        resultState,
-        props,
-        instance
-      );
-      var _callback = update.callback;
-      if (_callback !== null) {
-        workInProgress.effectTag |= Callback;
-        // Set this to null, in case it was mutated during an aborted render.
-        update.nextEffect = null;
-        if (queue.lastEffect === null) {
-          queue.firstEffect = queue.lastEffect = update;
-        } else {
-          queue.lastEffect.nextEffect = update;
-          queue.lastEffect = update;
-        }
+      if (!didSkip) {
+        didSkip = true;
+        queue.baseState = state;
       }
+      // Continue to the next update.
+      update = update.next;
+      continue;
     }
-    // Continue to the next update.
-    update = update.next;
-  }
 
-  // Separately, iterate though the list of captured updates.
-  var newFirstCapturedUpdate = null;
-  update = queue.firstCapturedUpdate;
-  while (update !== null) {
-    var _updateExpirationTime = update.expirationTime;
-    if (_updateExpirationTime > renderExpirationTime) {
-      // This update does not have sufficient priority. Skip it.
-      if (newFirstCapturedUpdate === null) {
-        // This is the first skipped captured update. It will be the first
-        // update in the new list.
-        newFirstCapturedUpdate = update;
-        // If this is the first update that was skipped, the current result is
-        // the new base state.
-        if (newFirstUpdate === null) {
-          newBaseState = resultState;
-        }
-      }
-      // Since this update will remain in the list, update the remaining
-      // expiration time.
-      if (
-        newExpirationTime === NoWork ||
-        newExpirationTime > _updateExpirationTime
-      ) {
-        newExpirationTime = _updateExpirationTime;
+    // This update does have sufficient priority.
+
+    // If no previous updates were skipped, drop this update from the queue by
+    // advancing the head of the list.
+    if (!didSkip) {
+      queue.first = update.next;
+      if (queue.first === null) {
+        queue.last = null;
       }
+    }
+
+    // Invoke setState callback an extra time to help detect side-effects.
+    // Ignore the return value in this case.
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      getStateFromUpdate(update, instance, state, props);
+    }
+
+    // Process the update
+    var _partialState = void 0;
+    if (update.isReplace) {
+      state = getStateFromUpdate(update, instance, state, props);
+      dontMutatePrevState = true;
     } else {
-      // This update does have sufficient priority. Process it and compute
-      // a new result.
-      resultState = getStateFromUpdate(
-        workInProgress,
-        queue,
-        update,
-        resultState,
-        props,
-        instance
-      );
-      var _callback2 = update.callback;
-      if (_callback2 !== null) {
-        workInProgress.effectTag |= Callback;
-        // Set this to null, in case it was mutated during an aborted render.
-        update.nextEffect = null;
-        if (queue.lastCapturedEffect === null) {
-          queue.firstCapturedEffect = queue.lastCapturedEffect = update;
+      _partialState = getStateFromUpdate(update, instance, state, props);
+      if (_partialState) {
+        if (dontMutatePrevState) {
+          // $FlowFixMe: Idk how to type this properly.
+          state = Object.assign({}, state, _partialState);
         } else {
-          queue.lastCapturedEffect.nextEffect = update;
-          queue.lastCapturedEffect = update;
+          state = Object.assign(state, _partialState);
         }
+        dontMutatePrevState = false;
+      }
+    }
+    if (update.isForced) {
+      queue.hasForceUpdate = true;
+    }
+    if (update.callback !== null) {
+      // Append to list of callbacks.
+      var _callbackList = queue.callbackList;
+      if (_callbackList === null) {
+        _callbackList = queue.callbackList = [];
+      }
+      _callbackList.push(update);
+    }
+    if (update.capturedValue !== null) {
+      var _capturedValues = queue.capturedValues;
+      if (_capturedValues === null) {
+        queue.capturedValues = [update.capturedValue];
+      } else {
+        _capturedValues.push(update.capturedValue);
       }
     }
     update = update.next;
   }
 
-  if (newFirstUpdate === null) {
-    queue.lastUpdate = null;
-  }
-  if (newFirstCapturedUpdate === null) {
-    queue.lastCapturedUpdate = null;
-  } else {
+  if (queue.callbackList !== null) {
     workInProgress.effectTag |= Callback;
+  } else if (
+    queue.first === null &&
+    !queue.hasForceUpdate &&
+    queue.capturedValues === null
+  ) {
+    // The queue is empty. We can reset it.
+    workInProgress.updateQueue = null;
   }
-  if (newFirstUpdate === null && newFirstCapturedUpdate === null) {
-    // We processed every update, without skipping. That means the new base
-    // state is the same as the result state.
-    newBaseState = resultState;
-  }
-
-  queue.baseState = newBaseState;
-  queue.firstUpdate = newFirstUpdate;
-  queue.firstCapturedUpdate = newFirstCapturedUpdate;
-  queue.expirationTime = newExpirationTime;
 
-  workInProgress.memoizedState = resultState;
+  if (!didSkip) {
+    didSkip = true;
+    queue.baseState = state;
+  }
 
   {
-    currentlyProcessingQueue = null;
+    // No longer processing.
+    queue.isProcessing = false;
   }
-}
 
-function callCallback(callback, context) {
-  invariant(
-    typeof callback === "function",
-    "Invalid argument passed as callback. Expected a function. Instead " +
-      "received: %s",
-    callback
-  );
-  callback.call(context);
+  return state;
 }
 
-function commitUpdateQueue(
-  finishedWork,
-  finishedQueue,
-  instance,
-  renderExpirationTime
-) {
-  // If the finished render included captured updates, and there are still
-  // lower priority updates left over, we need to keep the captured updates
-  // in the queue so that they are rebased and not dropped once we process the
-  // queue again at the lower priority.
-  if (finishedQueue.firstCapturedUpdate !== null) {
-    // Join the captured update list to the end of the normal list.
-    if (finishedQueue.lastUpdate !== null) {
-      finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate;
-      finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate;
-    }
-    // Clear the list of captured updates.
-    finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null;
-  }
-
-  // Commit the effects
-  var effect = finishedQueue.firstEffect;
-  finishedQueue.firstEffect = finishedQueue.lastEffect = null;
-  while (effect !== null) {
-    var _callback3 = effect.callback;
-    if (_callback3 !== null) {
-      effect.callback = null;
-      callCallback(_callback3, instance);
-    }
-    effect = effect.nextEffect;
+function commitCallbacks(queue, context) {
+  var callbackList = queue.callbackList;
+  if (callbackList === null) {
+    return;
   }
-
-  effect = finishedQueue.firstCapturedEffect;
-  finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
-  while (effect !== null) {
-    var _callback4 = effect.callback;
-    if (_callback4 !== null) {
-      effect.callback = null;
-      callCallback(_callback4, instance);
-    }
-    effect = effect.nextEffect;
+  // Set the list to null to make sure they don't get called more than once.
+  queue.callbackList = null;
+  for (var i = 0; i < callbackList.length; i++) {
+    var update = callbackList[i];
+    var _callback = update.callback;
+    // This update might be processed again. Clear the callback so it's only
+    // called once.
+    update.callback = null;
+    invariant(
+      typeof _callback === "function",
+      "Invalid argument passed as callback. Expected a function. Instead " +
+        "received: %s",
+      _callback
+    );
+    _callback.call(context);
   }
 }
 
@@ -5959,19 +5732,18 @@ var fakeInternalInstance = {};
 var isArray = Array.isArray;
 
 var didWarnAboutStateAssignmentForComponent = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
 var didWarnAboutUninitializedState = void 0;
 var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
 var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
-var warnOnUndefinedDerivedState = void 0;
 var warnOnInvalidCallback = void 0;
 
 {
   didWarnAboutStateAssignmentForComponent = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
   didWarnAboutUninitializedState = new Set();
   didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
   didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
 
   var didWarnOnInvalidCallback = new Set();
 
@@ -5992,21 +5764,6 @@ var warnOnInvalidCallback = void 0;
     }
   };
 
-  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
-    if (partialState === undefined) {
-      var componentName = getComponentName(workInProgress) || "Component";
-      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-        didWarnAboutUndefinedDerivedState.add(componentName);
-        warning(
-          false,
-          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-            "You have returned undefined.",
-          componentName
-        );
-      }
-    }
-  };
-
   // This is so gross but it's at least non-critical and can be removed if
   // it causes problems. This is meant to give a nicer error message for
   // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
@@ -6028,43 +5785,17 @@ var warnOnInvalidCallback = void 0;
   });
   Object.freeze(fakeInternalInstance);
 }
-
-function applyDerivedStateFromProps(
-  workInProgress,
-  getDerivedStateFromProps,
-  nextProps
-) {
-  var prevState = workInProgress.memoizedState;
-
-  {
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      // Invoke the function an extra time to help detect side-effects.
-      getDerivedStateFromProps(nextProps, prevState);
+function callGetDerivedStateFromCatch(ctor, capturedValues) {
+  var resultState = {};
+  for (var i = 0; i < capturedValues.length; i++) {
+    var capturedValue = capturedValues[i];
+    var error = capturedValue.value;
+    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
+    if (partialState !== null && partialState !== undefined) {
+      Object.assign(resultState, partialState);
     }
   }
-
-  var partialState = getDerivedStateFromProps(nextProps, prevState);
-
-  {
-    warnOnUndefinedDerivedState(workInProgress, partialState);
-  }
-  // Merge the partial state and the previous state.
-  var memoizedState =
-    partialState === null || partialState === undefined
-      ? prevState
-      : Object.assign({}, prevState, partialState);
-  workInProgress.memoizedState = memoizedState;
-
-  // Once the update queue is empty, persist the derived state onto the
-  // base state.
-  var updateQueue = workInProgress.updateQueue;
-  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
-    updateQueue.baseState = memoizedState;
-  }
+  return resultState;
 }
 
 var ReactFiberClassComponent = function(
@@ -6080,57 +5811,65 @@ var ReactFiberClassComponent = function(
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged;
 
-  var classComponentUpdater = {
-    isMounted: isMounted,
-    enqueueSetState: function(inst, payload, callback) {
-      var fiber = get$1(inst);
-      var expirationTime = computeExpirationForFiber(fiber);
+  // Class component state updater
 
-      var update = createUpdate(expirationTime);
-      update.payload = payload;
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "setState");
-        }
-        update.callback = callback;
+  var updater = {
+    isMounted: isMounted,
+    enqueueSetState: function(instance, partialState, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "setState");
       }
-
-      enqueueUpdate(fiber, update, expirationTime);
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: partialState,
+        callback: callback,
+        isReplace: false,
+        isForced: false,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueReplaceState: function(inst, payload, callback) {
-      var fiber = get$1(inst);
-      var expirationTime = computeExpirationForFiber(fiber);
-
-      var update = createUpdate(expirationTime);
-      update.tag = ReplaceState;
-      update.payload = payload;
-
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "replaceState");
-        }
-        update.callback = callback;
+    enqueueReplaceState: function(instance, state, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "replaceState");
       }
-
-      enqueueUpdate(fiber, update, expirationTime);
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: state,
+        callback: callback,
+        isReplace: true,
+        isForced: false,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueForceUpdate: function(inst, callback) {
-      var fiber = get$1(inst);
-      var expirationTime = computeExpirationForFiber(fiber);
-
-      var update = createUpdate(expirationTime);
-      update.tag = ForceUpdate;
-
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "forceUpdate");
-        }
-        update.callback = callback;
+    enqueueForceUpdate: function(instance, callback) {
+      var fiber = get$1(instance);
+      callback = callback === undefined ? null : callback;
+      {
+        warnOnInvalidCallback(callback, "forceUpdate");
       }
-
-      enqueueUpdate(fiber, update, expirationTime);
+      var expirationTime = computeExpirationForFiber(fiber);
+      var update = {
+        expirationTime: expirationTime,
+        partialState: null,
+        callback: callback,
+        isReplace: false,
+        isForced: true,
+        capturedValue: null,
+        next: null
+      };
+      insertUpdateIntoFiber(fiber, update);
       scheduleWork(fiber, expirationTime);
     }
   };
@@ -6144,10 +5883,11 @@ var ReactFiberClassComponent = function(
     newContext
   ) {
     if (
-      workInProgress.updateQueue !== null &&
-      workInProgress.updateQueue.hasForceUpdate
+      oldProps === null ||
+      (workInProgress.updateQueue !== null &&
+        workInProgress.updateQueue.hasForceUpdate)
     ) {
-      // If forceUpdate was called, disregard sCU.
+      // If the workInProgress already has an Update effect, return true
       return true;
     }
 
@@ -6404,8 +6144,13 @@ var ReactFiberClassComponent = function(
     }
   }
 
+  function resetInputPointers(workInProgress, instance) {
+    instance.props = workInProgress.memoizedProps;
+    instance.state = workInProgress.memoizedState;
+  }
+
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = classComponentUpdater;
+    instance.updater = updater;
     workInProgress.stateNode = instance;
     // The instance needs access to the fiber so that it can schedule updates
     set(instance, workInProgress);
@@ -6414,7 +6159,7 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function constructClassInstance(workInProgress, props, renderExpirationTime) {
+  function constructClassInstance(workInProgress, props) {
     var ctor = workInProgress.type;
     var unmaskedContext = getUnmaskedContext(workInProgress);
     var needsContext = isContextConsumer(workInProgress);
@@ -6423,21 +6168,19 @@ var ReactFiberClassComponent = function(
       : emptyObject;
 
     // Instantiate twice to help detect side-effects.
-    {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        new ctor(props, context); // eslint-disable-line no-new
-      }
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      new ctor(props, context); // eslint-disable-line no-new
     }
 
     var instance = new ctor(props, context);
-    var state = (workInProgress.memoizedState =
+    var state =
       instance.state !== null && instance.state !== undefined
         ? instance.state
-        : null);
+        : null;
     adoptClassInstance(workInProgress, instance);
 
     {
@@ -6528,7 +6271,27 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    workInProgress.memoizedState = state;
+
+    var partialState = callGetDerivedStateFromProps(
+      workInProgress,
+      instance,
+      props,
+      state
+    );
+
+    if (partialState !== null && partialState !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      workInProgress.memoizedState = Object.assign(
+        {},
+        workInProgress.memoizedState,
+        partialState
+      );
+    }
+
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
     // ReactFiberContext usually updates this cache but can't for newly-created instances.
     if (needsContext) {
       cacheContext(workInProgress, unmaskedContext, context);
@@ -6560,7 +6323,7 @@ var ReactFiberClassComponent = function(
           getComponentName(workInProgress) || "Component"
         );
       }
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+      updater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
@@ -6594,13 +6357,57 @@ var ReactFiberClassComponent = function(
           );
         }
       }
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+      updater.enqueueReplaceState(instance, instance.state, null);
+    }
+  }
+
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    var type = workInProgress.type;
+
+    if (typeof type.getDerivedStateFromProps === "function") {
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        // Invoke method an extra time to help detect side-effects.
+        type.getDerivedStateFromProps.call(null, nextProps, prevState);
+      }
+
+      var partialState = type.getDerivedStateFromProps.call(
+        null,
+        nextProps,
+        prevState
+      );
+
+      {
+        if (partialState === undefined) {
+          var componentName = getComponentName(workInProgress) || "Component";
+          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+            didWarnAboutUndefinedDerivedState.add(componentName);
+            warning(
+              false,
+              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+                "You have returned undefined.",
+              componentName
+            );
+          }
+        }
+      }
+
+      return partialState;
     }
   }
 
   // Invokes the mount life-cycles on a previously never rendered instance.
   function mountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
+    var current = workInProgress.alternate;
 
     {
       checkClassInstance(workInProgress);
@@ -6631,28 +6438,6 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        props,
-        instance,
-        renderExpirationTime
-      );
-      instance.state = workInProgress.memoizedState;
-    }
-
-    var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
-        workInProgress,
-        getDerivedStateFromProps,
-        props
-      );
-      instance.state = workInProgress.memoizedState;
-    }
-
     // In order to support react-lifecycles-compat polyfilled components,
     // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
@@ -6664,19 +6449,18 @@ var ReactFiberClassComponent = function(
       callComponentWillMount(workInProgress, instance);
       // If we had additional state updates during this life-cycle, let's
       // process them now.
-      updateQueue = workInProgress.updateQueue;
+      var updateQueue = workInProgress.updateQueue;
       if (updateQueue !== null) {
-        processUpdateQueue(
+        instance.state = processUpdateQueue(
+          current,
           workInProgress,
           updateQueue,
-          props,
           instance,
+          props,
           renderExpirationTime
         );
-        instance.state = workInProgress.memoizedState;
       }
     }
-
     if (typeof instance.componentDidMount === "function") {
       workInProgress.effectTag |= Update;
     }
@@ -6685,18 +6469,16 @@ var ReactFiberClassComponent = function(
   function resumeMountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
+    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
-    instance.props = oldProps;
-
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
-    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof getDerivedStateFromProps === "function" ||
+      typeof ctor.getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6720,27 +6502,93 @@ var ReactFiberClassComponent = function(
       }
     }
 
+    // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
-    var newState = (instance.state = oldState);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
+    // TODO: Previous state can be null.
+    var newState = void 0;
+    var derivedStateFromCatch = void 0;
+    if (workInProgress.updateQueue !== null) {
+      newState = processUpdateQueue(
+        null,
         workInProgress,
-        updateQueue,
-        newProps,
+        workInProgress.updateQueue,
         instance,
+        newProps,
         renderExpirationTime
       );
-      newState = workInProgress.memoizedState;
+
+      var updateQueue = workInProgress.updateQueue;
+      if (
+        updateQueue !== null &&
+        updateQueue.capturedValues !== null &&
+        enableGetDerivedStateFromCatch &&
+        typeof ctor.getDerivedStateFromCatch === "function"
+      ) {
+        var capturedValues = updateQueue.capturedValues;
+        // Don't remove these from the update queue yet. We need them in
+        // finishClassComponent. Do the reset there.
+        // TODO: This is awkward. Refactor class components.
+        // updateQueue.capturedValues = null;
+        derivedStateFromCatch = callGetDerivedStateFromCatch(
+          ctor,
+          capturedValues
+        );
+      }
+    } else {
+      newState = oldState;
     }
 
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
         workInProgress,
-        getDerivedStateFromProps,
-        newProps
+        instance,
+        newProps,
+        newState
       );
-      newState = workInProgress.memoizedState;
+    }
+
+    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromProps
+          : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue = workInProgress.updateQueue;
+      if (_updateQueue !== null) {
+        _updateQueue.baseState = Object.assign(
+          {},
+          _updateQueue.baseState,
+          derivedStateFromProps
+        );
+      }
+    }
+    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromCatch
+          : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue2 = workInProgress.updateQueue;
+      if (_updateQueue2 !== null) {
+        _updateQueue2.baseState = Object.assign(
+          {},
+          _updateQueue2.baseState,
+          derivedStateFromCatch
+        );
+      }
     }
 
     if (
@@ -6797,9 +6645,9 @@ var ReactFiberClassComponent = function(
       }
 
       // If shouldComponentUpdate returned false, we should still update the
-      // memoized state to indicate that this work can be reused.
-      workInProgress.memoizedProps = newProps;
-      workInProgress.memoizedState = newState;
+      // memoized props/state to indicate that this work can be reused.
+      memoizeProps(workInProgress, newProps);
+      memoizeState(workInProgress, newState);
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6815,18 +6663,16 @@ var ReactFiberClassComponent = function(
   function updateClassInstance(current, workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
+    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
-    instance.props = oldProps;
-
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
-    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof getDerivedStateFromProps === "function" ||
+      typeof ctor.getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6850,27 +6696,94 @@ var ReactFiberClassComponent = function(
       }
     }
 
+    // Compute the next state using the memoized state and the update queue.
     var oldState = workInProgress.memoizedState;
-    var newState = (instance.state = oldState);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
+    // TODO: Previous state can be null.
+    var newState = void 0;
+    var derivedStateFromCatch = void 0;
+
+    if (workInProgress.updateQueue !== null) {
+      newState = processUpdateQueue(
+        current,
         workInProgress,
-        updateQueue,
-        newProps,
+        workInProgress.updateQueue,
         instance,
+        newProps,
         renderExpirationTime
       );
-      newState = workInProgress.memoizedState;
+
+      var updateQueue = workInProgress.updateQueue;
+      if (
+        updateQueue !== null &&
+        updateQueue.capturedValues !== null &&
+        enableGetDerivedStateFromCatch &&
+        typeof ctor.getDerivedStateFromCatch === "function"
+      ) {
+        var capturedValues = updateQueue.capturedValues;
+        // Don't remove these from the update queue yet. We need them in
+        // finishClassComponent. Do the reset there.
+        // TODO: This is awkward. Refactor class components.
+        // updateQueue.capturedValues = null;
+        derivedStateFromCatch = callGetDerivedStateFromCatch(
+          ctor,
+          capturedValues
+        );
+      }
+    } else {
+      newState = oldState;
     }
 
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
+    var derivedStateFromProps = void 0;
+    if (oldProps !== newProps) {
+      // The prevState parameter should be the partially updated state.
+      // Otherwise, spreading state in return values could override updates.
+      derivedStateFromProps = callGetDerivedStateFromProps(
         workInProgress,
-        getDerivedStateFromProps,
-        newProps
+        instance,
+        newProps,
+        newState
       );
-      newState = workInProgress.memoizedState;
+    }
+
+    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromProps
+          : Object.assign({}, newState, derivedStateFromProps);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue3 = workInProgress.updateQueue;
+      if (_updateQueue3 !== null) {
+        _updateQueue3.baseState = Object.assign(
+          {},
+          _updateQueue3.baseState,
+          derivedStateFromProps
+        );
+      }
+    }
+    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
+      // Render-phase updates (like this) should not be added to the update queue,
+      // So that multiple render passes do not enqueue multiple updates.
+      // Instead, just synchronously merge the returned state into the instance.
+      newState =
+        newState === null || newState === undefined
+          ? derivedStateFromCatch
+          : Object.assign({}, newState, derivedStateFromCatch);
+
+      // Update the base state of the update queue.
+      // FIXME: This is getting ridiculous. Refactor plz!
+      var _updateQueue4 = workInProgress.updateQueue;
+      if (_updateQueue4 !== null) {
+        _updateQueue4.baseState = Object.assign(
+          {},
+          _updateQueue4.baseState,
+          derivedStateFromCatch
+        );
+      }
     }
 
     if (
@@ -6957,8 +6870,8 @@ var ReactFiberClassComponent = function(
 
       // If shouldComponentUpdate returned false, we should still update the
       // memoized props/state to indicate that this work can be reused.
-      workInProgress.memoizedProps = newProps;
-      workInProgress.memoizedState = newState;
+      memoizeProps(workInProgress, newProps);
+      memoizeState(workInProgress, newState);
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6972,6 +6885,7 @@ var ReactFiberClassComponent = function(
 
   return {
     adoptClassInstance: adoptClassInstance,
+    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: constructClassInstance,
     mountClassInstance: mountClassInstance,
     resumeMountClassInstance: resumeMountClassInstance,
@@ -6979,7 +6893,7 @@ var ReactFiberClassComponent = function(
   };
 };
 
-var getCurrentFiberStackAddendum$2 =
+var getCurrentFiberStackAddendum$1 =
   ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
 
 var didWarnAboutMaps = void 0;
@@ -7018,7 +6932,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
       '"key" prop. See https://fb.me/react-warning-keys for ' +
       "more information." +
-      (getCurrentFiberStackAddendum$2() || "");
+      (getCurrentFiberStackAddendum$1() || "");
     if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
       return;
     }
@@ -7029,7 +6943,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
         '"key" prop. See https://fb.me/react-warning-keys for ' +
         "more information.%s",
-      getCurrentFiberStackAddendum$2()
+      getCurrentFiberStackAddendum$1()
     );
   };
 }
@@ -7126,7 +7040,7 @@ function throwOnInvalidObjectType(returnFiber, newChild) {
       addendum =
         " If you meant to render a collection of children, use an array " +
         "instead." +
-        (getCurrentFiberStackAddendum$2() || "");
+        (getCurrentFiberStackAddendum$1() || "");
     }
     invariant(
       false,
@@ -7144,7 +7058,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
     "you return a Component instead of <Component /> from render. " +
     "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$2() || "");
+    (getCurrentFiberStackAddendum$1() || "");
 
   if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
     return;
@@ -7156,7 +7070,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
       "you return a Component instead of <Component /> from render. " +
       "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$2() || ""
+    getCurrentFiberStackAddendum$1() || ""
   );
 }
 
@@ -7269,12 +7183,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, textContent, expirationTime);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       return existing;
     }
   }
@@ -7284,7 +7198,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // Move based on index
       var existing = useFiber(current, element.props, expirationTime);
       existing.ref = coerceRef(returnFiber, current, element);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       {
         existing._debugSource = element._source;
         existing._debugOwner = element._owner;
@@ -7298,7 +7212,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       created.ref = coerceRef(returnFiber, current, element);
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     }
   }
@@ -7316,12 +7230,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, portal.children || [], expirationTime);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       return existing;
     }
   }
@@ -7335,12 +7249,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         key
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, fragment, expirationTime);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       return existing;
     }
   }
@@ -7355,7 +7269,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     }
 
@@ -7368,7 +7282,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           _created.ref = coerceRef(returnFiber, null, newChild);
-          _created.return = returnFiber;
+          _created["return"] = returnFiber;
           return _created;
         }
         case REACT_PORTAL_TYPE: {
@@ -7377,7 +7291,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             returnFiber.mode,
             expirationTime
           );
-          _created2.return = returnFiber;
+          _created2["return"] = returnFiber;
           return _created2;
         }
       }
@@ -7389,7 +7303,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           null
         );
-        _created3.return = returnFiber;
+        _created3["return"] = returnFiber;
         return _created3;
       }
 
@@ -7600,7 +7514,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               "duplicated and/or omitted — the behavior is unsupported and " +
               "could change in a future version.%s",
             key,
-            getCurrentFiberStackAddendum$2()
+            getCurrentFiberStackAddendum$1()
           );
           break;
         default:
@@ -7745,7 +7659,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren.delete(
+            existingChildren["delete"](
               _newFiber2.key === null ? newIdx : _newFiber2.key
             );
           }
@@ -7798,7 +7712,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                 "Using Maps as children is unsupported and will likely yield " +
                   "unexpected results. Convert it to a sequence/iterable of keyed " +
                   "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$2()
+                getCurrentFiberStackAddendum$1()
               )
             : void 0;
           didWarnAboutMaps = true;
@@ -7924,7 +7838,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren.delete(
+            existingChildren["delete"](
               _newFiber4.key === null ? newIdx : _newFiber4.key
             );
           }
@@ -7963,7 +7877,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // the rest.
       deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
       var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing.return = returnFiber;
+      existing["return"] = returnFiber;
       return existing;
     }
     // The existing first child is not a text node so we need to create one
@@ -7974,7 +7888,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created.return = returnFiber;
+    created["return"] = returnFiber;
     return created;
   }
 
@@ -8004,7 +7918,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           existing.ref = coerceRef(returnFiber, child, element);
-          existing.return = returnFiber;
+          existing["return"] = returnFiber;
           {
             existing._debugSource = element._source;
             existing._debugOwner = element._owner;
@@ -8027,7 +7941,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         element.key
       );
-      created.return = returnFiber;
+      created["return"] = returnFiber;
       return created;
     } else {
       var _created4 = createFiberFromElement(
@@ -8036,7 +7950,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4.return = returnFiber;
+      _created4["return"] = returnFiber;
       return _created4;
     }
   }
@@ -8060,7 +7974,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         ) {
           deleteRemainingChildren(returnFiber, child.sibling);
           var existing = useFiber(child, portal.children || [], expirationTime);
-          existing.return = returnFiber;
+          existing["return"] = returnFiber;
           return existing;
         } else {
           deleteRemainingChildren(returnFiber, child);
@@ -8077,7 +7991,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created.return = returnFiber;
+    created["return"] = returnFiber;
     return created;
   }
 
@@ -8229,7 +8143,7 @@ function cloneChildFibers(current, workInProgress) {
   );
   workInProgress.child = newChild;
 
-  newChild.return = workInProgress;
+  newChild["return"] = workInProgress;
   while (currentChild.sibling !== null) {
     currentChild = currentChild.sibling;
     newChild = newChild.sibling = createWorkInProgress(
@@ -8237,14 +8151,11 @@ function cloneChildFibers(current, workInProgress) {
       currentChild.pendingProps,
       currentChild.expirationTime
     );
-    newChild.return = workInProgress;
+    newChild["return"] = workInProgress;
   }
   newChild.sibling = null;
 }
 
-var getCurrentFiberStackAddendum =
-  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
-
 var didWarnAboutBadClass = void 0;
 var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
 var didWarnAboutStatelessRefs = void 0;
@@ -8288,6 +8199,8 @@ var ReactFiberBeginWork = function(
       memoizeState
     ),
     adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
+    callGetDerivedStateFromProps =
+      _ReactFiberClassCompo.callGetDerivedStateFromProps,
     constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
     mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
     resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
@@ -8339,20 +8252,9 @@ var ReactFiberBeginWork = function(
 
   function updateForwardRef(current, workInProgress) {
     var render = workInProgress.type.render;
-    var nextProps = workInProgress.pendingProps;
-    var ref = workInProgress.ref;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextProps) {
-      var currentRef = current !== null ? current.ref : null;
-      if (ref === currentRef) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-    }
-    var nextChildren = render(nextProps, ref);
+    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
     reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
+    memoizeProps(workInProgress, nextChildren);
     return workInProgress.child;
   }
 
@@ -8438,11 +8340,7 @@ var ReactFiberBeginWork = function(
     if (current === null) {
       if (workInProgress.stateNode === null) {
         // In the initial pass we might need to construct the instance.
-        constructClassInstance(
-          workInProgress,
-          workInProgress.pendingProps,
-          renderExpirationTime
-        );
+        constructClassInstance(workInProgress, workInProgress.pendingProps);
         mountClassInstance(workInProgress, renderExpirationTime);
 
         shouldUpdate = true;
@@ -8460,11 +8358,22 @@ var ReactFiberBeginWork = function(
         renderExpirationTime
       );
     }
+
+    // We processed the update queue inside updateClassInstance. It may have
+    // included some errors that were dispatched during the commit phase.
+    // TODO: Refactor class components so this is less awkward.
+    var didCaptureError = false;
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null && updateQueue.capturedValues !== null) {
+      shouldUpdate = true;
+      didCaptureError = true;
+    }
     return finishClassComponent(
       current,
       workInProgress,
       shouldUpdate,
       hasContext,
+      didCaptureError,
       renderExpirationTime
     );
   }
@@ -8474,13 +8383,12 @@ var ReactFiberBeginWork = function(
     workInProgress,
     shouldUpdate,
     hasContext,
+    didCaptureError,
     renderExpirationTime
   ) {
     // Refs should update even if shouldComponentUpdate returns false
     markRef(current, workInProgress);
 
-    var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
-
     if (!shouldUpdate && !didCaptureError) {
       // Context providers should defer to sCU for rendering
       if (hasContext) {
@@ -8576,26 +8484,29 @@ var ReactFiberBeginWork = function(
     pushHostRootContext(workInProgress);
     var updateQueue = workInProgress.updateQueue;
     if (updateQueue !== null) {
-      var nextProps = workInProgress.pendingProps;
       var prevState = workInProgress.memoizedState;
-      var prevChildren = prevState !== null ? prevState.element : null;
-      processUpdateQueue(
+      var state = processUpdateQueue(
+        current,
         workInProgress,
         updateQueue,
-        nextProps,
+        null,
         null,
         renderExpirationTime
       );
-      var nextState = workInProgress.memoizedState;
-      // Caution: React DevTools currently depends on this property
-      // being called "element".
-      var nextChildren = nextState.element;
+      memoizeState(workInProgress, state);
+      updateQueue = workInProgress.updateQueue;
 
-      if (nextChildren === prevChildren) {
+      var element = void 0;
+      if (updateQueue !== null && updateQueue.capturedValues !== null) {
+        // There's an uncaught error. Unmount the whole root.
+        element = null;
+      } else if (prevState === state) {
         // If the state is the same as before, that's a bailout because we had
         // no work that expires at this time.
         resetHydrationState();
         return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      } else {
+        element = state.element;
       }
       var root = workInProgress.stateNode;
       if (
@@ -8620,15 +8531,16 @@ var ReactFiberBeginWork = function(
         workInProgress.child = mountChildFibers(
           workInProgress,
           null,
-          nextChildren,
+          element,
           renderExpirationTime
         );
       } else {
         // Otherwise reset hydration state in case we aborted and resumed another
         // root.
         resetHydrationState();
-        reconcileChildren(current, workInProgress, nextChildren);
+        reconcileChildren(current, workInProgress, element);
       }
+      memoizeState(workInProgress, state);
       return workInProgress.child;
     }
     resetHydrationState();
@@ -8764,13 +8676,21 @@ var ReactFiberBeginWork = function(
       workInProgress.memoizedState =
         value.state !== null && value.state !== undefined ? value.state : null;
 
-      var getDerivedStateFromProps = Component.getDerivedStateFromProps;
-      if (typeof getDerivedStateFromProps === "function") {
-        applyDerivedStateFromProps(
+      if (typeof Component.getDerivedStateFromProps === "function") {
+        var partialState = callGetDerivedStateFromProps(
           workInProgress,
-          getDerivedStateFromProps,
-          props
+          value,
+          props,
+          workInProgress.memoizedState
         );
+
+        if (partialState !== null && partialState !== undefined) {
+          workInProgress.memoizedState = Object.assign(
+            {},
+            workInProgress.memoizedState,
+            partialState
+          );
+        }
       }
 
       // Push context providers early to prevent context stack mismatches.
@@ -8784,6 +8704,7 @@ var ReactFiberBeginWork = function(
         workInProgress,
         true,
         hasContext,
+        false,
         renderExpirationTime
       );
     } else {
@@ -8929,7 +8850,7 @@ var ReactFiberBeginWork = function(
     var fiber = workInProgress.child;
     if (fiber !== null) {
       // Set the return pointer of the child to the work-in-progress fiber.
-      fiber.return = workInProgress;
+      fiber["return"] = workInProgress;
     }
     while (fiber !== null) {
       var nextFiber = void 0;
@@ -8967,7 +8888,7 @@ var ReactFiberBeginWork = function(
                 // ancestor path already has sufficient priority.
                 break;
               }
-              node = node.return;
+              node = node["return"];
             }
             // Don't scan deeper than a matching consumer. When we render the
             // consumer, we'll continue scanning from that point. This way the
@@ -8989,7 +8910,7 @@ var ReactFiberBeginWork = function(
       }
       if (nextFiber !== null) {
         // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber.return = fiber;
+        nextFiber["return"] = fiber;
       } else {
         // No child. Traverse to next sibling.
         nextFiber = fiber;
@@ -9001,13 +8922,11 @@ var ReactFiberBeginWork = function(
           }
           var sibling = nextFiber.sibling;
           if (sibling !== null) {
-            // Set the return pointer of the sibling to the work-in-progress fiber.
-            sibling.return = nextFiber.return;
             nextFiber = sibling;
             break;
           }
           // No more siblings. Traverse up.
-          nextFiber = nextFiber.return;
+          nextFiber = nextFiber["return"];
         }
       }
       fiber = nextFiber;
@@ -9024,10 +8943,8 @@ var ReactFiberBeginWork = function(
 
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
-    var canBailOnProps = true;
 
     if (hasLegacyContextChanged()) {
-      canBailOnProps = false;
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (oldProps === newProps) {
@@ -9039,20 +8956,6 @@ var ReactFiberBeginWork = function(
     var newValue = newProps.value;
     workInProgress.memoizedProps = newProps;
 
-    {
-      var providerPropTypes = workInProgress.type.propTypes;
-
-      if (providerPropTypes) {
-        checkPropTypes(
-          providerPropTypes,
-          newProps,
-          "prop",
-          "Context.Provider",
-          getCurrentFiberStackAddendum
-        );
-      }
-    }
-
     var changedBits = void 0;
     if (oldProps === null) {
       // Initial render
@@ -9060,7 +8963,7 @@ var ReactFiberBeginWork = function(
     } else {
       if (oldProps.value === newProps.value) {
         // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children && canBailOnProps) {
+        if (oldProps.children === newProps.children) {
           workInProgress.stateNode = 0;
           pushProvider(workInProgress);
           return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -9077,7 +8980,7 @@ var ReactFiberBeginWork = function(
           (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
         ) {
           // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children && canBailOnProps) {
+          if (oldProps.children === newProps.children) {
             workInProgress.stateNode = 0;
             pushProvider(workInProgress);
             return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -9102,7 +9005,7 @@ var ReactFiberBeginWork = function(
 
           if (changedBits === 0) {
             // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children && canBailOnProps) {
+            if (oldProps.children === newProps.children) {
               workInProgress.stateNode = 0;
               pushProvider(workInProgress);
               return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -9188,8 +9091,6 @@ var ReactFiberBeginWork = function(
     }
 
     var newChildren = render(newValue);
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
     reconcileChildren(current, workInProgress, newChildren);
     return workInProgress.child;
   }
@@ -9397,7 +9298,7 @@ var ReactFiberCompleteWork = function(
   function appendAllReturns(returns, workInProgress) {
     var node = workInProgress.stateNode;
     if (node) {
-      node.return = workInProgress;
+      node["return"] = workInProgress;
     }
     while (node !== null) {
       if (
@@ -9409,17 +9310,17 @@ var ReactFiberCompleteWork = function(
       } else if (node.tag === ReturnComponent) {
         returns.push(node.pendingProps.value);
       } else if (node.child !== null) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === workInProgress) {
+        if (node["return"] === null || node["return"] === workInProgress) {
           return;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -9475,7 +9376,7 @@ var ReactFiberCompleteWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
@@ -9483,12 +9384,12 @@ var ReactFiberCompleteWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === workInProgress) {
+        if (node["return"] === null || node["return"] === workInProgress) {
           return;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -9555,7 +9456,7 @@ var ReactFiberCompleteWork = function(
             // down its children. Instead, we'll get insertions from each child in
             // the portal directly.
           } else if (node.child !== null) {
-            node.child.return = node;
+            node.child["return"] = node;
             node = node.child;
             continue;
           }
@@ -9563,12 +9464,12 @@ var ReactFiberCompleteWork = function(
             return;
           }
           while (node.sibling === null) {
-            if (node.return === null || node.return === workInProgress) {
+            if (node["return"] === null || node["return"] === workInProgress) {
               return;
             }
-            node = node.return;
+            node = node["return"];
           }
-          node.sibling.return = node.return;
+          node.sibling["return"] = node["return"];
           node = node.sibling;
         }
       };
@@ -9694,6 +9595,20 @@ var ReactFiberCompleteWork = function(
       case ClassComponent: {
         // We are leaving this subtree, so pop context if any.
         popLegacyContextProvider(workInProgress);
+
+        // If this component caught an error, schedule an error log effect.
+        var instance = workInProgress.stateNode;
+        var updateQueue = workInProgress.updateQueue;
+        if (updateQueue !== null && updateQueue.capturedValues !== null) {
+          workInProgress.effectTag &= ~DidCapture;
+          if (typeof instance.componentDidCatch === "function") {
+            workInProgress.effectTag |= ErrLog;
+          } else {
+            // Normally we clear this in the commit phase, but since we did not
+            // schedule an effect, we need to reset it here.
+            updateQueue.capturedValues = null;
+          }
+        }
         return null;
       }
       case HostRoot: {
@@ -9713,6 +9628,11 @@ var ReactFiberCompleteWork = function(
           workInProgress.effectTag &= ~Placement;
         }
         updateHostContainer(workInProgress);
+
+        var _updateQueue = workInProgress.updateQueue;
+        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
+          workInProgress.effectTag |= ErrLog;
+        }
         return null;
       }
       case HostComponent: {
@@ -9727,13 +9647,13 @@ var ReactFiberCompleteWork = function(
           // have newProps so we'll have to reuse them.
           // TODO: Split the update API as separate for the props vs. children.
           // Even better would be if children weren't special cased at all tho.
-          var instance = workInProgress.stateNode;
+          var _instance = workInProgress.stateNode;
           var currentHostContext = getHostContext();
           // TODO: Experiencing an error where oldProps is null. Suggests a host
           // component is hitting the resume path. Figure out why. Possibly
           // related to `hidden`.
           var updatePayload = prepareUpdate(
-            instance,
+            _instance,
             type,
             oldProps,
             newProps,
@@ -9787,7 +9707,7 @@ var ReactFiberCompleteWork = function(
               markUpdate(workInProgress);
             }
           } else {
-            var _instance = createInstance(
+            var _instance2 = createInstance(
               type,
               newProps,
               rootContainerInstance,
@@ -9795,14 +9715,14 @@ var ReactFiberCompleteWork = function(
               workInProgress
             );
 
-            appendAllChildren(_instance, workInProgress);
+            appendAllChildren(_instance2, workInProgress);
 
             // Certain renderers require commit-time effects for initial mount.
             // (eg DOM renderer supports auto-focus for certain elements).
             // Make sure such renderers get scheduled for later work.
             if (
               finalizeInitialChildren(
-                _instance,
+                _instance2,
                 type,
                 newProps,
                 rootContainerInstance,
@@ -9811,7 +9731,7 @@ var ReactFiberCompleteWork = function(
             ) {
               markUpdate(workInProgress);
             }
-            workInProgress.stateNode = _instance;
+            workInProgress.stateNode = _instance2;
           }
 
           if (workInProgress.ref !== null) {
@@ -9918,6 +9838,139 @@ function createCapturedValue(value, source) {
   };
 }
 
+var ReactFiberUnwindWork = function(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  isAlreadyFailedLegacyErrorBoundary
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+
+  function throwException(returnFiber, sourceFiber, rawValue) {
+    // The source fiber did not complete.
+    sourceFiber.effectTag |= Incomplete;
+    // Its effect list is no longer valid.
+    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+
+    var value = createCapturedValue(rawValue, sourceFiber);
+
+    var workInProgress = returnFiber;
+    do {
+      switch (workInProgress.tag) {
+        case HostRoot: {
+          // Uncaught error
+          var errorInfo = value;
+          ensureUpdateQueues(workInProgress);
+          var updateQueue = workInProgress.updateQueue;
+          updateQueue.capturedValues = [errorInfo];
+          workInProgress.effectTag |= ShouldCapture;
+          return;
+        }
+        case ClassComponent:
+          // Capture and retry
+          var ctor = workInProgress.type;
+          var _instance = workInProgress.stateNode;
+          if (
+            (workInProgress.effectTag & DidCapture) === NoEffect &&
+            ((typeof ctor.getDerivedStateFromCatch === "function" &&
+              enableGetDerivedStateFromCatch) ||
+              (_instance !== null &&
+                typeof _instance.componentDidCatch === "function" &&
+                !isAlreadyFailedLegacyErrorBoundary(_instance)))
+          ) {
+            ensureUpdateQueues(workInProgress);
+            var _updateQueue = workInProgress.updateQueue;
+            var capturedValues = _updateQueue.capturedValues;
+            if (capturedValues === null) {
+              _updateQueue.capturedValues = [value];
+            } else {
+              capturedValues.push(value);
+            }
+            workInProgress.effectTag |= ShouldCapture;
+            return;
+          }
+          break;
+        default:
+          break;
+      }
+      workInProgress = workInProgress["return"];
+    } while (workInProgress !== null);
+  }
+
+  function unwindWork(workInProgress) {
+    switch (workInProgress.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(workInProgress);
+        var effectTag = workInProgress.effectTag;
+        if (effectTag & ShouldCapture) {
+          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var _effectTag = workInProgress.effectTag;
+        if (_effectTag & ShouldCapture) {
+          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        return null;
+      }
+      case HostPortal:
+        popHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        popProvider(workInProgress);
+        return null;
+      default:
+        return null;
+    }
+  }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      default:
+        break;
+    }
+  }
+
+  return {
+    throwException: throwException,
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork
+  };
+};
+
 // Module provided by RN:
 /**
  * Intercept lifecycle errors and ensure they are shown with the correct stack
@@ -10203,14 +10256,7 @@ var ReactFiberCommitWork = function(
         }
         var updateQueue = finishedWork.updateQueue;
         if (updateQueue !== null) {
-          _instance2.props = finishedWork.memoizedProps;
-          _instance2.state = finishedWork.memoizedState;
-          commitUpdateQueue(
-            finishedWork,
-            updateQueue,
-            _instance2,
-            committedExpirationTime
-          );
+          commitCallbacks(updateQueue, _instance2);
         }
         return;
       }
@@ -10228,12 +10274,7 @@ var ReactFiberCommitWork = function(
                 break;
             }
           }
-          commitUpdateQueue(
-            finishedWork,
-            _updateQueue,
-            _instance3,
-            committedExpirationTime
-          );
+          commitCallbacks(_updateQueue, _instance3);
         }
         return;
       }
@@ -10270,17 +10311,81 @@ var ReactFiberCommitWork = function(
     }
   }
 
+  function commitErrorLogging(finishedWork, onUncaughtError) {
+    switch (finishedWork.tag) {
+      case ClassComponent:
+        {
+          var ctor = finishedWork.type;
+          var _instance5 = finishedWork.stateNode;
+          var updateQueue = finishedWork.updateQueue;
+          invariant(
+            updateQueue !== null && updateQueue.capturedValues !== null,
+            "An error logging effect should not have been scheduled if no errors " +
+              "were captured. This error is likely caused by a bug in React. " +
+              "Please file an issue."
+          );
+          var capturedErrors = updateQueue.capturedValues;
+          updateQueue.capturedValues = null;
+
+          if (typeof ctor.getDerivedStateFromCatch !== "function") {
+            // To preserve the preexisting retry behavior of error boundaries,
+            // we keep track of which ones already failed during this batch.
+            // This gets reset before we yield back to the browser.
+            // TODO: Warn in strict mode if getDerivedStateFromCatch is
+            // not defined.
+            markLegacyErrorBoundaryAsFailed(_instance5);
+          }
+
+          _instance5.props = finishedWork.memoizedProps;
+          _instance5.state = finishedWork.memoizedState;
+          for (var i = 0; i < capturedErrors.length; i++) {
+            var errorInfo = capturedErrors[i];
+            var _error = errorInfo.value;
+            var stack = errorInfo.stack;
+            logError(finishedWork, errorInfo);
+            _instance5.componentDidCatch(_error, {
+              componentStack: stack !== null ? stack : ""
+            });
+          }
+        }
+        break;
+      case HostRoot: {
+        var _updateQueue2 = finishedWork.updateQueue;
+        invariant(
+          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
+          "An error logging effect should not have been scheduled if no errors " +
+            "were captured. This error is likely caused by a bug in React. " +
+            "Please file an issue."
+        );
+        var _capturedErrors = _updateQueue2.capturedValues;
+        _updateQueue2.capturedValues = null;
+        for (var _i = 0; _i < _capturedErrors.length; _i++) {
+          var _errorInfo = _capturedErrors[_i];
+          logError(finishedWork, _errorInfo);
+          onUncaughtError(_errorInfo.value);
+        }
+        break;
+      }
+      default:
+        invariant(
+          false,
+          "This unit of work tag cannot capture errors.  This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+    }
+  }
+
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (ref !== null) {
-      var _instance5 = finishedWork.stateNode;
+      var _instance6 = finishedWork.stateNode;
       var instanceToUse = void 0;
       switch (finishedWork.tag) {
         case HostComponent:
-          instanceToUse = getPublicInstance(_instance5);
+          instanceToUse = getPublicInstance(_instance6);
           break;
         default:
-          instanceToUse = _instance5;
+          instanceToUse = _instance6;
       }
       if (typeof ref === "function") {
         ref(instanceToUse);
@@ -10324,9 +10429,9 @@ var ReactFiberCommitWork = function(
     switch (current.tag) {
       case ClassComponent: {
         safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if (typeof _instance6.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance6);
+        var _instance7 = current.stateNode;
+        if (typeof _instance7.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance7);
         }
         return;
       }
@@ -10368,7 +10473,7 @@ var ReactFiberCommitWork = function(
         // If we don't use mutation we drill down into portals here instead.
         (!mutation || node.tag !== HostPortal)
       ) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
@@ -10376,12 +10481,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === root) {
+        if (node["return"] === null || node["return"] === root) {
           return;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -10392,11 +10497,11 @@ var ReactFiberCommitWork = function(
     // get GC:ed but we don't know which for sure which parent is the current
     // one so we'll settle for GC:ing the subtree of this child. This child
     // itself will be GC:ed when the parent updates the next time.
-    current.return = null;
+    current["return"] = null;
     current.child = null;
     if (current.alternate) {
       current.alternate.child = null;
-      current.alternate.return = null;
+      current.alternate["return"] = null;
     }
   }
 
@@ -10464,6 +10569,7 @@ var ReactFiberCommitWork = function(
 
         commitLifeCycles: commitLifeCycles,
         commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+        commitErrorLogging: commitErrorLogging,
         commitAttachRef: commitAttachRef,
         commitDetachRef: commitDetachRef
       };
@@ -10485,12 +10591,12 @@ var ReactFiberCommitWork = function(
     removeChildFromContainer = mutation.removeChildFromContainer;
 
   function getHostParentFiber(fiber) {
-    var parent = fiber.return;
+    var parent = fiber["return"];
     while (parent !== null) {
       if (isHostParent(parent)) {
         return parent;
       }
-      parent = parent.return;
+      parent = parent["return"];
     }
     invariant(
       false,
@@ -10515,14 +10621,14 @@ var ReactFiberCommitWork = function(
     siblings: while (true) {
       // If we didn't find anything, let's try the next sibling.
       while (node.sibling === null) {
-        if (node.return === null || isHostParent(node.return)) {
+        if (node["return"] === null || isHostParent(node["return"])) {
           // If we pop out of the root or hit the parent the fiber we are the
           // last sibling.
           return null;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
       while (node.tag !== HostComponent && node.tag !== HostText) {
         // If it is not host node and, we might have a host node inside it.
@@ -10536,7 +10642,7 @@ var ReactFiberCommitWork = function(
         if (node.child === null || node.tag === HostPortal) {
           continue siblings;
         } else {
-          node.child.return = node;
+          node.child["return"] = node;
           node = node.child;
         }
       }
@@ -10604,7 +10710,7 @@ var ReactFiberCommitWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
@@ -10612,12 +10718,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === finishedWork) {
+        if (node["return"] === null || node["return"] === finishedWork) {
           return;
         }
-        node = node.return;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -10634,7 +10740,7 @@ var ReactFiberCommitWork = function(
 
     while (true) {
       if (!currentParentIsValid) {
-        var parent = node.return;
+        var parent = node["return"];
         findParent: while (true) {
           invariant(
             parent !== null,
@@ -10655,7 +10761,7 @@ var ReactFiberCommitWork = function(
               currentParentIsContainer = true;
               break findParent;
           }
-          parent = parent.return;
+          parent = parent["return"];
         }
         currentParentIsValid = true;
       }
@@ -10676,7 +10782,7 @@ var ReactFiberCommitWork = function(
         currentParent = node.stateNode.containerInfo;
         // Visit children because portals might contain host components.
         if (node.child !== null) {
-          node.child.return = node;
+          node.child["return"] = node;
           node = node.child;
           continue;
         }
@@ -10684,7 +10790,7 @@ var ReactFiberCommitWork = function(
         commitUnmount(node);
         // Visit children because we may find more host components below.
         if (node.child !== null) {
-          node.child.return = node;
+          node.child["return"] = node;
           node = node.child;
           continue;
         }
@@ -10693,17 +10799,17 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === current) {
+        if (node["return"] === null || node["return"] === current) {
           return;
         }
-        node = node.return;
+        node = node["return"];
         if (node.tag === HostPortal) {
           // When we go out of the portal, we need to restore the parent.
           // Since we don't keep a stack of them, we will search for it.
           currentParentIsValid = false;
         }
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -10721,8 +10827,8 @@ var ReactFiberCommitWork = function(
         return;
       }
       case HostComponent: {
-        var _instance7 = finishedWork.stateNode;
-        if (_instance7 != null) {
+        var _instance8 = finishedWork.stateNode;
+        if (_instance8 != null) {
           // Commit the work prepared earlier.
           var newProps = finishedWork.memoizedProps;
           // For hydration we reuse the update path but we treat the oldProps
@@ -10735,7 +10841,7 @@ var ReactFiberCommitWork = function(
           finishedWork.updateQueue = null;
           if (updatePayload !== null) {
             commitUpdate(
-              _instance7,
+              _instance8,
               updatePayload,
               type,
               oldProps,
@@ -10786,6 +10892,7 @@ var ReactFiberCommitWork = function(
       commitDeletion: commitDeletion,
       commitWork: commitWork,
       commitLifeCycles: commitLifeCycles,
+      commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
     };
@@ -10794,208 +10901,6 @@ var ReactFiberCommitWork = function(
   }
 };
 
-var ReactFiberUnwindWork = function(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  markLegacyErrorBoundaryAsFailed,
-  isAlreadyFailedLegacyErrorBoundary,
-  onUncaughtError
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-
-  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
-    var update = createUpdate(expirationTime);
-    // Unmount the root by rendering null.
-    update.tag = CaptureUpdate;
-    // Caution: React DevTools currently depends on this property
-    // being called "element".
-    update.payload = { element: null };
-    var error = errorInfo.value;
-    update.callback = function() {
-      onUncaughtError(error);
-      logError(fiber, errorInfo);
-    };
-    return update;
-  }
-
-  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
-    var update = createUpdate(expirationTime);
-    update.tag = CaptureUpdate;
-    var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
-    if (
-      enableGetDerivedStateFromCatch &&
-      typeof getDerivedStateFromCatch === "function"
-    ) {
-      var _error = errorInfo.value;
-      update.payload = function() {
-        return getDerivedStateFromCatch(_error);
-      };
-    }
-
-    var inst = fiber.stateNode;
-    if (inst !== null && typeof inst.componentDidCatch === "function") {
-      update.callback = function callback() {
-        if (
-          !enableGetDerivedStateFromCatch ||
-          getDerivedStateFromCatch !== "function"
-        ) {
-          // To preserve the preexisting retry behavior of error boundaries,
-          // we keep track of which ones already failed during this batch.
-          // This gets reset before we yield back to the browser.
-          // TODO: Warn in strict mode if getDerivedStateFromCatch is
-          // not defined.
-          markLegacyErrorBoundaryAsFailed(this);
-        }
-        var error = errorInfo.value;
-        var stack = errorInfo.stack;
-        logError(fiber, errorInfo);
-        this.componentDidCatch(error, {
-          componentStack: stack !== null ? stack : ""
-        });
-      };
-    }
-    return update;
-  }
-
-  function throwException(
-    returnFiber,
-    sourceFiber,
-    rawValue,
-    renderExpirationTime
-  ) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-
-    var value = createCapturedValue(rawValue, sourceFiber);
-
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          var _errorInfo = value;
-          workInProgress.effectTag |= ShouldCapture;
-          var update = createRootErrorUpdate(
-            workInProgress,
-            _errorInfo,
-            renderExpirationTime
-          );
-          enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
-          return;
-        }
-        case ClassComponent:
-          // Capture and retry
-          var errorInfo = value;
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
-          if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            workInProgress.effectTag |= ShouldCapture;
-            // Schedule the error boundary to re-render using updated state
-            var _update = createClassErrorUpdate(
-              workInProgress,
-              errorInfo,
-              renderExpirationTime
-            );
-            enqueueCapturedUpdate(
-              workInProgress,
-              _update,
-              renderExpirationTime
-            );
-            return;
-          }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress.return;
-    } while (workInProgress !== null);
-  }
-
-  function unwindWork(workInProgress) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
-    }
-  }
-
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      default:
-        break;
-    }
-  }
-
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork,
-    createRootErrorUpdate: createRootErrorUpdate,
-    createClassErrorUpdate: createClassErrorUpdate
-  };
-};
-
 var NO_CONTEXT = {};
 
 var ReactFiberHostContext = function(config, stack) {
@@ -11180,7 +11085,7 @@ var ReactFiberHydrationContext = function(config) {
 
     var childToDelete = createFiberFromHostInstanceForDeletion();
     childToDelete.stateNode = instance;
-    childToDelete.return = returnFiber;
+    childToDelete["return"] = returnFiber;
     childToDelete.effectTag = Deletion;
 
     // This might seem like it belongs on progressedFirstDeletion. However,
@@ -11378,13 +11283,13 @@ var ReactFiberHydrationContext = function(config) {
   }
 
   function popToNextHostParent(fiber) {
-    var parent = fiber.return;
+    var parent = fiber["return"];
     while (
       parent !== null &&
       parent.tag !== HostComponent &&
       parent.tag !== HostRoot
     ) {
-      parent = parent.return;
+      parent = parent["return"];
     }
     hydrationParentFiber = parent;
   }
@@ -11706,7 +11611,7 @@ var ReactFiberLegacyContext = function(stack) {
       if (isContextProvider(node)) {
         return node.stateNode.__reactInternalMemoizedMergedChildContext;
       }
-      var parent = node.return;
+      var parent = node["return"];
       invariant(
         parent,
         "Found unexpected detached subtree parent. " +
@@ -11979,15 +11884,11 @@ var ReactFiberScheduler = function(config) {
       legacyContext,
       newContext,
       scheduleWork,
-      markLegacyErrorBoundaryAsFailed,
-      isAlreadyFailedLegacyErrorBoundary,
-      onUncaughtError
+      isAlreadyFailedLegacyErrorBoundary
     ),
     throwException = _ReactFiberUnwindWork.throwException,
     unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork,
-    createRootErrorUpdate = _ReactFiberUnwindWork.createRootErrorUpdate,
-    createClassErrorUpdate = _ReactFiberUnwindWork.createClassErrorUpdate;
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
 
   var _ReactFiberCommitWork = ReactFiberCommitWork(
       config,
@@ -12004,6 +11905,7 @@ var ReactFiberScheduler = function(config) {
     commitDeletion = _ReactFiberCommitWork.commitDeletion,
     commitWork = _ReactFiberCommitWork.commitWork,
     commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
+    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
     commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
     commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
 
@@ -12101,10 +12003,10 @@ var ReactFiberScheduler = function(config) {
 
   function resetStack() {
     if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork.return;
+      var interruptedWork = nextUnitOfWork["return"];
       while (interruptedWork !== null) {
         unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork.return;
+        interruptedWork = interruptedWork["return"];
       }
     }
 
@@ -12229,6 +12131,10 @@ var ReactFiberScheduler = function(config) {
         );
       }
 
+      if (effectTag & ErrLog) {
+        commitErrorLogging(nextEffect, onUncaughtError);
+      }
+
       if (effectTag & Ref) {
         recordEffect();
         commitAttachRef(nextEffect);
@@ -12435,16 +12341,7 @@ var ReactFiberScheduler = function(config) {
     }
 
     // Check for pending updates.
-    var newExpirationTime = NoWork;
-    switch (workInProgress.tag) {
-      case HostRoot:
-      case ClassComponent: {
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null) {
-          newExpirationTime = updateQueue.expirationTime;
-        }
-      }
-    }
+    var newExpirationTime = getUpdateExpirationTime(workInProgress);
 
     // TODO: Calls need to visit stateNode
 
@@ -12477,7 +12374,7 @@ var ReactFiberScheduler = function(config) {
         ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
       }
 
-      var returnFiber = workInProgress.return;
+      var returnFiber = workInProgress["return"];
       var siblingFiber = workInProgress.sibling;
 
       if ((workInProgress.effectTag & Incomplete) === NoEffect) {
@@ -12719,19 +12616,13 @@ var ReactFiberScheduler = function(config) {
           break;
         }
 
-        {
-          // Reset global debug state
-          // We assume this is defined in DEV
-          resetCurrentlyProcessingQueue();
-        }
-
         if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
           replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
         }
 
         var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber.return;
+        var returnFiber = sourceFiber["return"];
         if (returnFiber === null) {
           // This is the root. The root could capture its own errors. However,
           // we don't know if it errors before or after we pushed the host
@@ -12743,12 +12634,7 @@ var ReactFiberScheduler = function(config) {
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(
-          returnFiber,
-          sourceFiber,
-          thrownValue,
-          nextRenderExpirationTime
-        );
+        throwException(returnFiber, sourceFiber, thrownValue);
         nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
       break;
@@ -12796,13 +12682,31 @@ var ReactFiberScheduler = function(config) {
     }
   }
 
+  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
+    // TODO: We only support dispatching errors.
+    var capturedValue = createCapturedValue(value, sourceFiber);
+    var update = {
+      expirationTime: expirationTime,
+      partialState: null,
+      callback: null,
+      isReplace: false,
+      isForced: false,
+      capturedValue: capturedValue,
+      next: null
+    };
+    insertUpdateIntoFiber(boundaryFiber, update);
+    scheduleWork(boundaryFiber, expirationTime);
+  }
+
   function dispatch(sourceFiber, value, expirationTime) {
     invariant(
       !isWorking || isCommitting,
       "dispatch: Cannot dispatch during the render phase."
     );
 
-    var fiber = sourceFiber.return;
+    // TODO: Handle arrays
+
+    var fiber = sourceFiber["return"];
     while (fiber !== null) {
       switch (fiber.tag) {
         case ClassComponent:
@@ -12813,44 +12717,22 @@ var ReactFiberScheduler = function(config) {
             (typeof instance.componentDidCatch === "function" &&
               !isAlreadyFailedLegacyErrorBoundary(instance))
           ) {
-            var errorInfo = createCapturedValue(value, sourceFiber);
-            var update = createClassErrorUpdate(
-              fiber,
-              errorInfo,
-              expirationTime
-            );
-            enqueueUpdate(fiber, update, expirationTime);
-            scheduleWork(fiber, expirationTime);
+            scheduleCapture(sourceFiber, fiber, value, expirationTime);
             return;
           }
           break;
-        case HostRoot: {
-          var _errorInfo = createCapturedValue(value, sourceFiber);
-          var _update = createRootErrorUpdate(
-            fiber,
-            _errorInfo,
-            expirationTime
-          );
-          enqueueUpdate(fiber, _update, expirationTime);
-          scheduleWork(fiber, expirationTime);
+        // TODO: Handle async boundaries
+        case HostRoot:
+          scheduleCapture(sourceFiber, fiber, value, expirationTime);
           return;
-        }
       }
-      fiber = fiber.return;
+      fiber = fiber["return"];
     }
 
     if (sourceFiber.tag === HostRoot) {
       // Error was thrown at the root. There is no parent, so the root
       // itself should capture it.
-      var rootFiber = sourceFiber;
-      var _errorInfo2 = createCapturedValue(value, rootFiber);
-      var _update2 = createRootErrorUpdate(
-        rootFiber,
-        _errorInfo2,
-        expirationTime
-      );
-      enqueueUpdate(rootFiber, _update2, expirationTime);
-      scheduleWork(rootFiber, expirationTime);
+      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
     }
   }
 
@@ -12978,7 +12860,7 @@ var ReactFiberScheduler = function(config) {
           node.alternate.expirationTime = expirationTime;
         }
       }
-      if (node.return === null) {
+      if (node["return"] === null) {
         if (node.tag === HostRoot) {
           var root = node.stateNode;
           if (
@@ -13019,7 +12901,7 @@ var ReactFiberScheduler = function(config) {
           return;
         }
       }
-      node = node.return;
+      node = node["return"];
     }
   }
 
@@ -13648,14 +13530,9 @@ var ReactFiberReconciler$1 = function(config) {
       }
     }
 
-    var update = createUpdate(expirationTime);
-    // Caution: React DevTools currently depends on this property
-    // being called "element".
-    update.payload = { element: element };
-
     callback = callback === undefined ? null : callback;
-    if (callback !== null) {
-      !(typeof callback === "function")
+    {
+      !(callback === null || typeof callback === "function")
         ? warning(
             false,
             "render(...): Expected the last optional `callback` argument to be a " +
@@ -13663,11 +13540,20 @@ var ReactFiberReconciler$1 = function(config) {
             callback
           )
         : void 0;
-      update.callback = callback;
     }
-    enqueueUpdate(current, update, expirationTime);
 
+    var update = {
+      expirationTime: expirationTime,
+      partialState: { element: element },
+      callback: callback,
+      isReplace: false,
+      isForced: false,
+      capturedValue: null,
+      next: null
+    };
+    insertUpdateIntoFiber(current, update);
     scheduleWork(current, expirationTime);
+
     return expirationTime;
   }
 
@@ -13845,8 +13731,8 @@ var ReactFiberReconciler$3 =
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3.default
-  ? ReactFiberReconciler$3.default
+var reactReconciler = ReactFiberReconciler$3["default"]
+  ? ReactFiberReconciler$3["default"]
   : ReactFiberReconciler$3;
 
 function _classCallCheck$1(instance, Constructor) {
@@ -14468,7 +14354,7 @@ var ReactNativeRenderer = {
     if (root) {
       // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
       NativeRenderer.updateContainer(null, root, null, function() {
-        roots.delete(containerTag);
+        roots["delete"](containerTag);
       });
     }
   },
@@ -14535,8 +14421,8 @@ var ReactNativeRenderer$3 =
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var reactNativeRenderer = ReactNativeRenderer$3.default
-  ? ReactNativeRenderer$3.default
+var reactNativeRenderer = ReactNativeRenderer$3["default"]
+  ? ReactNativeRenderer$3["default"]
   : ReactNativeRenderer$3;
 
 module.exports = reactNativeRenderer;
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
index 09031ec3a6c9..f7eb9e09f0dc 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
- * @providesModule ReactNativeRenderer-prod
  * @preventMunge
  */
 
@@ -307,7 +306,7 @@ function getListener(inst, registrationName) {
   return listener;
 }
 function getParent(inst) {
-  do inst = inst.return;
+  do inst = inst["return"];
   while (inst && 5 !== inst.tag);
   return inst ? inst : null;
 }
@@ -1123,17 +1122,21 @@ var ReactNativeEventEmitter = Object.freeze({
   }
 });
 RCTEventEmitter.register(ReactNativeEventEmitter);
-var hasSymbol = "function" === typeof Symbol && Symbol.for,
-  REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 60105,
-  REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
-  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
-  REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
-  REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
-  REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
-  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
-  REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for("react.forward_ref") : 60112,
+var hasSymbol = "function" === typeof Symbol && Symbol["for"],
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
+  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
+  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol
+    ? Symbol["for"]("react.strict_mode")
+    : 60108,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol
+    ? Symbol["for"]("react.forward_ref")
+    : 60112,
   MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
 function getIteratorFn(maybeIterable) {
   if (null === maybeIterable || "undefined" === typeof maybeIterable)
@@ -1207,7 +1210,7 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
         JSCompiler_inline_result = "";
     }
     info += JSCompiler_inline_result;
-    workInProgress = workInProgress.return;
+    workInProgress = workInProgress["return"];
   } while (workInProgress);
   return info;
 }
@@ -1466,11 +1469,11 @@ var ReactCurrentOwner =
   React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
 function isFiberMountedImpl(fiber) {
   var node = fiber;
-  if (fiber.alternate) for (; node.return; ) node = node.return;
+  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
   else {
     if (0 !== (node.effectTag & 2)) return 1;
-    for (; node.return; )
-      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
+    for (; node["return"]; )
+      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
   }
   return 3 === node.tag ? 2 : 3;
 }
@@ -1497,7 +1500,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       1 === alternate ? null : fiber
     );
   for (var a = fiber, b = alternate; ; ) {
-    var parentA = a.return,
+    var parentA = a["return"],
       parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) break;
     if (parentA.child === parentB.child) {
@@ -1508,7 +1511,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       }
       invariant(!1, "Unable to find node on an unmounted component.");
     }
-    if (a.return !== b.return) (a = parentA), (b = parentB);
+    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
     else {
       child = !1;
       for (var _child = parentA.child; _child; ) {
@@ -1561,14 +1564,14 @@ function findCurrentHostFiber(parent) {
   if (!parent) return null;
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child.return = node), (node = node.child);
+    if (node.child) (node.child["return"] = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node.return || node.return === parent) return null;
-        node = node.return;
+        if (!node["return"] || node["return"] === parent) return null;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -1580,14 +1583,14 @@ function findCurrentHostFiberWithNoPortals(parent) {
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
     if (node.child && 4 !== node.tag)
-      (node.child.return = node), (node = node.child);
+      (node.child["return"] = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node.return || node.return === parent) return null;
-        node = node.return;
+        if (!node["return"] || node["return"] === parent) return null;
+        node = node["return"];
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -1596,7 +1599,8 @@ function findCurrentHostFiberWithNoPortals(parent) {
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
   this.key = key;
-  this.sibling = this.child = this.return = this.stateNode = this.type = null;
+  this.stateNode = this.type = null;
+  this.sibling = this.child = this["return"] = null;
   this.index = 0;
   this.ref = null;
   this.pendingProps = pendingProps;
@@ -1761,282 +1765,164 @@ function onCommitUnmount(fiber) {
 new Set();
 function createUpdateQueue(baseState) {
   return {
-    expirationTime: 0,
     baseState: baseState,
-    firstUpdate: null,
-    lastUpdate: null,
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
-    firstEffect: null,
-    lastEffect: null,
-    firstCapturedEffect: null,
-    lastCapturedEffect: null,
-    hasForceUpdate: !1
-  };
-}
-function cloneUpdateQueue(currentQueue) {
-  return {
-    expirationTime: currentQueue.expirationTime,
-    baseState: currentQueue.baseState,
-    firstUpdate: currentQueue.firstUpdate,
-    lastUpdate: currentQueue.lastUpdate,
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
+    expirationTime: 0,
+    first: null,
+    last: null,
+    callbackList: null,
     hasForceUpdate: !1,
-    firstEffect: null,
-    lastEffect: null,
-    firstCapturedEffect: null,
-    lastCapturedEffect: null
-  };
-}
-function createUpdate(expirationTime) {
-  return {
-    expirationTime: expirationTime,
-    tag: 0,
-    payload: null,
-    callback: null,
-    next: null,
-    nextEffect: null
+    isInitialized: !1,
+    capturedValues: null
   };
 }
-function appendUpdateToQueue(queue, update, expirationTime) {
-  null === queue.lastUpdate
-    ? (queue.firstUpdate = queue.lastUpdate = update)
-    : ((queue.lastUpdate.next = update), (queue.lastUpdate = update));
-  if (0 === queue.expirationTime || queue.expirationTime > expirationTime)
-    queue.expirationTime = expirationTime;
-}
-function enqueueUpdate(fiber, update, expirationTime) {
-  var alternate = fiber.alternate;
-  if (null === alternate) {
-    var queue1 = fiber.updateQueue;
-    var queue2 = null;
-    null === queue1 &&
-      (queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState));
-  } else
-    (queue1 = fiber.updateQueue),
-      (queue2 = alternate.updateQueue),
-      null === queue1
-        ? null === queue2
-          ? ((queue1 = fiber.updateQueue = createUpdateQueue(
-              fiber.memoizedState
-            )),
-            (queue2 = alternate.updateQueue = createUpdateQueue(
-              alternate.memoizedState
-            )))
-          : (queue1 = fiber.updateQueue = cloneUpdateQueue(queue2))
-        : null === queue2 &&
-          (queue2 = alternate.updateQueue = cloneUpdateQueue(queue1));
-  null === queue2 || queue1 === queue2
-    ? appendUpdateToQueue(queue1, update, expirationTime)
-    : null === queue1.lastUpdate || null === queue2.lastUpdate
-      ? (appendUpdateToQueue(queue1, update, expirationTime),
-        appendUpdateToQueue(queue2, update, expirationTime))
-      : (appendUpdateToQueue(queue1, update, expirationTime),
-        (queue2.lastUpdate = update));
-}
-function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
-  var workInProgressQueue = workInProgress.updateQueue;
-  workInProgressQueue =
-    null === workInProgressQueue
-      ? (workInProgress.updateQueue = createUpdateQueue(
-          workInProgress.memoizedState
-        ))
-      : ensureWorkInProgressQueueIsAClone(workInProgress, workInProgressQueue);
-  null === workInProgressQueue.lastCapturedUpdate
-    ? (workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update)
-    : ((workInProgressQueue.lastCapturedUpdate.next = update),
-      (workInProgressQueue.lastCapturedUpdate = update));
+function insertUpdateIntoQueue(queue, update) {
+  null === queue.last
+    ? (queue.first = queue.last = update)
+    : ((queue.last.next = update), (queue.last = update));
   if (
-    0 === workInProgressQueue.expirationTime ||
-    workInProgressQueue.expirationTime > renderExpirationTime
+    0 === queue.expirationTime ||
+    queue.expirationTime > update.expirationTime
   )
-    workInProgressQueue.expirationTime = renderExpirationTime;
+    queue.expirationTime = update.expirationTime;
 }
-function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
-  var current = workInProgress.alternate;
-  null !== current &&
-    queue === current.updateQueue &&
-    (queue = workInProgress.updateQueue = cloneUpdateQueue(queue));
-  return queue;
+var q1 = void 0,
+  q2 = void 0;
+function ensureUpdateQueues(fiber) {
+  q1 = q2 = null;
+  var alternateFiber = fiber.alternate,
+    queue1 = fiber.updateQueue;
+  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
+  null !== alternateFiber
+    ? ((fiber = alternateFiber.updateQueue),
+      null === fiber &&
+        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
+    : (fiber = null);
+  q1 = queue1;
+  q2 = fiber !== queue1 ? fiber : null;
 }
-function getStateFromUpdate(
-  workInProgress,
-  queue,
-  update,
-  prevState,
-  nextProps,
-  instance
-) {
-  switch (update.tag) {
-    case 1:
-      return (
-        (workInProgress = update.payload),
-        "function" === typeof workInProgress
-          ? workInProgress.call(instance, prevState, nextProps)
-          : workInProgress
-      );
-    case 3:
-      workInProgress.effectTag = (workInProgress.effectTag & -1025) | 64;
-    case 0:
-      workInProgress = update.payload;
-      nextProps =
-        "function" === typeof workInProgress
-          ? workInProgress.call(instance, prevState, nextProps)
-          : workInProgress;
-      if (null === nextProps || void 0 === nextProps) break;
-      return Object.assign({}, prevState, nextProps);
-    case 2:
-      queue.hasForceUpdate = !0;
-  }
-  return prevState;
+function insertUpdateIntoFiber(fiber, update) {
+  ensureUpdateQueues(fiber);
+  fiber = q1;
+  var queue2 = q2;
+  null === queue2
+    ? insertUpdateIntoQueue(fiber, update)
+    : null === fiber.last || null === queue2.last
+      ? (insertUpdateIntoQueue(fiber, update),
+        insertUpdateIntoQueue(queue2, update))
+      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
+}
+function getStateFromUpdate(update, instance, prevState, props) {
+  update = update.partialState;
+  return "function" === typeof update
+    ? update.call(instance, prevState, props)
+    : update;
 }
 function processUpdateQueue(
+  current,
   workInProgress,
   queue,
-  props,
   instance,
+  props,
   renderExpirationTime
 ) {
-  if (
-    !(0 === queue.expirationTime || queue.expirationTime > renderExpirationTime)
-  ) {
-    queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
-    for (
-      var newBaseState = queue.baseState,
-        newFirstUpdate = null,
-        newExpirationTime = 0,
-        update = queue.firstUpdate,
-        resultState = newBaseState;
-      null !== update;
-
-    ) {
-      var updateExpirationTime = update.expirationTime;
-      if (updateExpirationTime > renderExpirationTime) {
-        if (
-          (null === newFirstUpdate &&
-            ((newFirstUpdate = update), (newBaseState = resultState)),
-          0 === newExpirationTime || newExpirationTime > updateExpirationTime)
-        )
-          newExpirationTime = updateExpirationTime;
-      } else
-        (resultState = getStateFromUpdate(
-          workInProgress,
-          queue,
-          update,
-          resultState,
-          props,
-          instance
-        )),
-          null !== update.callback &&
-            ((workInProgress.effectTag |= 32),
-            (update.nextEffect = null),
-            null === queue.lastEffect
-              ? (queue.firstEffect = queue.lastEffect = update)
-              : ((queue.lastEffect.nextEffect = update),
-                (queue.lastEffect = update)));
-      update = update.next;
-    }
-    updateExpirationTime = null;
-    for (update = queue.firstCapturedUpdate; null !== update; ) {
-      var _updateExpirationTime = update.expirationTime;
-      if (_updateExpirationTime > renderExpirationTime) {
-        if (
-          (null === updateExpirationTime &&
-            ((updateExpirationTime = update),
-            null === newFirstUpdate && (newBaseState = resultState)),
-          0 === newExpirationTime || newExpirationTime > _updateExpirationTime)
-        )
-          newExpirationTime = _updateExpirationTime;
-      } else
-        (resultState = getStateFromUpdate(
-          workInProgress,
-          queue,
-          update,
-          resultState,
-          props,
-          instance
-        )),
-          null !== update.callback &&
-            ((workInProgress.effectTag |= 32),
-            (update.nextEffect = null),
-            null === queue.lastCapturedEffect
-              ? (queue.firstCapturedEffect = queue.lastCapturedEffect = update)
-              : ((queue.lastCapturedEffect.nextEffect = update),
-                (queue.lastCapturedEffect = update)));
-      update = update.next;
-    }
-    null === newFirstUpdate && (queue.lastUpdate = null);
-    null === updateExpirationTime
-      ? (queue.lastCapturedUpdate = null)
-      : (workInProgress.effectTag |= 32);
-    null === newFirstUpdate &&
-      null === updateExpirationTime &&
-      (newBaseState = resultState);
-    queue.baseState = newBaseState;
-    queue.firstUpdate = newFirstUpdate;
-    queue.firstCapturedUpdate = updateExpirationTime;
-    queue.expirationTime = newExpirationTime;
-    workInProgress.memoizedState = resultState;
-  }
-}
-function callCallback(callback, context) {
-  invariant(
-    "function" === typeof callback,
-    "Invalid argument passed as callback. Expected a function. Instead received: %s",
-    callback
-  );
-  callback.call(context);
-}
-function commitUpdateQueue(finishedWork, finishedQueue, instance) {
-  null !== finishedQueue.firstCapturedUpdate &&
-    (null !== finishedQueue.lastUpdate &&
-      ((finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate),
-      (finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate)),
-    (finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null));
-  finishedWork = finishedQueue.firstEffect;
+  null !== current &&
+    current.updateQueue === queue &&
+    (queue = workInProgress.updateQueue = {
+      baseState: queue.baseState,
+      expirationTime: queue.expirationTime,
+      first: queue.first,
+      last: queue.last,
+      isInitialized: queue.isInitialized,
+      capturedValues: queue.capturedValues,
+      callbackList: null,
+      hasForceUpdate: !1
+    });
+  queue.expirationTime = 0;
+  queue.isInitialized
+    ? (current = queue.baseState)
+    : ((current = queue.baseState = workInProgress.memoizedState),
+      (queue.isInitialized = !0));
   for (
-    finishedQueue.firstEffect = finishedQueue.lastEffect = null;
-    null !== finishedWork;
+    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
+    null !== update;
 
   ) {
-    var _callback3 = finishedWork.callback;
-    null !== _callback3 &&
-      ((finishedWork.callback = null), callCallback(_callback3, instance));
-    finishedWork = finishedWork.nextEffect;
+    var updateExpirationTime = update.expirationTime;
+    if (updateExpirationTime > renderExpirationTime) {
+      var remainingExpirationTime = queue.expirationTime;
+      if (
+        0 === remainingExpirationTime ||
+        remainingExpirationTime > updateExpirationTime
+      )
+        queue.expirationTime = updateExpirationTime;
+      didSkip || ((didSkip = !0), (queue.baseState = current));
+    } else {
+      didSkip ||
+        ((queue.first = update.next),
+        null === queue.first && (queue.last = null));
+      if (update.isReplace)
+        (current = getStateFromUpdate(update, instance, current, props)),
+          (dontMutatePrevState = !0);
+      else if (
+        (updateExpirationTime = getStateFromUpdate(
+          update,
+          instance,
+          current,
+          props
+        ))
+      )
+        (current = dontMutatePrevState
+          ? Object.assign({}, current, updateExpirationTime)
+          : Object.assign(current, updateExpirationTime)),
+          (dontMutatePrevState = !1);
+      update.isForced && (queue.hasForceUpdate = !0);
+      null !== update.callback &&
+        ((updateExpirationTime = queue.callbackList),
+        null === updateExpirationTime &&
+          (updateExpirationTime = queue.callbackList = []),
+        updateExpirationTime.push(update));
+      null !== update.capturedValue &&
+        ((updateExpirationTime = queue.capturedValues),
+        null === updateExpirationTime
+          ? (queue.capturedValues = [update.capturedValue])
+          : updateExpirationTime.push(update.capturedValue));
+    }
+    update = update.next;
   }
-  finishedWork = finishedQueue.firstCapturedEffect;
-  for (
-    finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
-    null !== finishedWork;
-
-  )
-    (finishedQueue = finishedWork.callback),
-      null !== finishedQueue &&
-        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
-      (finishedWork = finishedWork.nextEffect);
+  null !== queue.callbackList
+    ? (workInProgress.effectTag |= 32)
+    : null !== queue.first ||
+      queue.hasForceUpdate ||
+      null !== queue.capturedValues ||
+      (workInProgress.updateQueue = null);
+  didSkip || (queue.baseState = current);
+  return current;
 }
-function applyDerivedStateFromProps(
-  workInProgress,
-  getDerivedStateFromProps,
-  nextProps
-) {
-  var prevState = workInProgress.memoizedState;
-  getDerivedStateFromProps = getDerivedStateFromProps(nextProps, prevState);
-  prevState =
-    null === getDerivedStateFromProps || void 0 === getDerivedStateFromProps
-      ? prevState
-      : Object.assign({}, prevState, getDerivedStateFromProps);
-  workInProgress.memoizedState = prevState;
-  workInProgress = workInProgress.updateQueue;
-  null !== workInProgress &&
-    0 === workInProgress.expirationTime &&
-    (workInProgress.baseState = prevState);
+function commitCallbacks(queue, context) {
+  var callbackList = queue.callbackList;
+  if (null !== callbackList)
+    for (
+      queue.callbackList = null, queue = 0;
+      queue < callbackList.length;
+      queue++
+    ) {
+      var update = callbackList[queue],
+        _callback = update.callback;
+      update.callback = null;
+      invariant(
+        "function" === typeof _callback,
+        "Invalid argument passed as callback. Expected a function. Instead received: %s",
+        _callback
+      );
+      _callback.call(context);
+    }
 }
 function ReactFiberClassComponent(
   legacyContext,
   scheduleWork,
-  computeExpirationForFiber
+  computeExpirationForFiber,
+  memoizeProps,
+  memoizeState
 ) {
   function checkShouldComponentUpdate(
     workInProgress,
@@ -2047,8 +1933,9 @@ function ReactFiberClassComponent(
     newContext
   ) {
     if (
-      null !== workInProgress.updateQueue &&
-      workInProgress.updateQueue.hasForceUpdate
+      null === oldProps ||
+      (null !== workInProgress.updateQueue &&
+        workInProgress.updateQueue.hasForceUpdate)
     )
       return !0;
     var instance = workInProgress.stateNode;
@@ -2061,7 +1948,7 @@ function ReactFiberClassComponent(
         : !0;
   }
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = classComponentUpdater;
+    instance.updater = updater;
     workInProgress.stateNode = instance;
     instance._reactInternalFiber = workInProgress;
   }
@@ -2077,52 +1964,78 @@ function ReactFiberClassComponent(
     "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
       instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
     instance.state !== workInProgress &&
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+      updater.enqueueReplaceState(instance, instance.state, null);
+  }
+  function callGetDerivedStateFromProps(
+    workInProgress,
+    instance,
+    nextProps,
+    prevState
+  ) {
+    workInProgress = workInProgress.type;
+    if ("function" === typeof workInProgress.getDerivedStateFromProps)
+      return workInProgress.getDerivedStateFromProps.call(
+        null,
+        nextProps,
+        prevState
+      );
   }
   var cacheContext = legacyContext.cacheContext,
     getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged,
-    classComponentUpdater = {
+    updater = {
       isMounted: isMounted,
-      enqueueSetState: function(inst, payload, callback) {
-        inst = inst._reactInternalFiber;
-        var expirationTime = computeExpirationForFiber(inst),
-          update = createUpdate(expirationTime);
-        update.payload = payload;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, expirationTime);
-        scheduleWork(inst, expirationTime);
+      enqueueSetState: function(instance, partialState, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: partialState,
+          callback: callback,
+          isReplace: !1,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
       },
-      enqueueReplaceState: function(inst, payload, callback) {
-        inst = inst._reactInternalFiber;
-        var expirationTime = computeExpirationForFiber(inst),
-          update = createUpdate(expirationTime);
-        update.tag = 1;
-        update.payload = payload;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, expirationTime);
-        scheduleWork(inst, expirationTime);
+      enqueueReplaceState: function(instance, state, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: state,
+          callback: callback,
+          isReplace: !0,
+          isForced: !1,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
       },
-      enqueueForceUpdate: function(inst, callback) {
-        inst = inst._reactInternalFiber;
-        var expirationTime = computeExpirationForFiber(inst),
-          update = createUpdate(expirationTime);
-        update.tag = 2;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, expirationTime);
-        scheduleWork(inst, expirationTime);
+      enqueueForceUpdate: function(instance, callback) {
+        instance = instance._reactInternalFiber;
+        callback = void 0 === callback ? null : callback;
+        var expirationTime = computeExpirationForFiber(instance);
+        insertUpdateIntoFiber(instance, {
+          expirationTime: expirationTime,
+          partialState: null,
+          callback: callback,
+          isReplace: !1,
+          isForced: !0,
+          capturedValue: null,
+          next: null
+        });
+        scheduleWork(instance, expirationTime);
       }
     };
   return {
     adoptClassInstance: adoptClassInstance,
+    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: function(workInProgress, props) {
       var ctor = workInProgress.type,
         unmaskedContext = getUnmaskedContext(workInProgress),
@@ -2130,15 +2043,25 @@ function ReactFiberClassComponent(
         context = needsContext
           ? getMaskedContext(workInProgress, unmaskedContext)
           : emptyObject;
-      props = new ctor(props, context);
-      workInProgress.memoizedState =
-        null !== props.state && void 0 !== props.state ? props.state : null;
-      adoptClassInstance(workInProgress, props);
+      ctor = new ctor(props, context);
+      var state =
+        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
+      adoptClassInstance(workInProgress, ctor);
+      workInProgress.memoizedState = state;
+      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
+      null !== props &&
+        void 0 !== props &&
+        (workInProgress.memoizedState = Object.assign(
+          {},
+          workInProgress.memoizedState,
+          props
+        ));
       needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return props;
+      return ctor;
     },
     mountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
+        current = workInProgress.alternate,
         instance = workInProgress.stateNode,
         props = workInProgress.pendingProps,
         unmaskedContext = getUnmaskedContext(workInProgress);
@@ -2146,20 +2069,6 @@ function ReactFiberClassComponent(
       instance.state = workInProgress.memoizedState;
       instance.refs = emptyObject;
       instance.context = getMaskedContext(workInProgress, unmaskedContext);
-      unmaskedContext = workInProgress.updateQueue;
-      null !== unmaskedContext &&
-        (processUpdateQueue(
-          workInProgress,
-          unmaskedContext,
-          props,
-          instance,
-          renderExpirationTime
-        ),
-        (instance.state = workInProgress.memoizedState));
-      unmaskedContext = workInProgress.type.getDerivedStateFromProps;
-      "function" === typeof unmaskedContext &&
-        (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
-        (instance.state = workInProgress.memoizedState));
       "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate ||
         ("function" !== typeof instance.UNSAFE_componentWillMount &&
@@ -2170,36 +2079,32 @@ function ReactFiberClassComponent(
         "function" === typeof instance.UNSAFE_componentWillMount &&
           instance.UNSAFE_componentWillMount(),
         ctor !== instance.state &&
-          classComponentUpdater.enqueueReplaceState(
-            instance,
-            instance.state,
-            null
-          ),
-        (unmaskedContext = workInProgress.updateQueue),
-        null !== unmaskedContext &&
-          (processUpdateQueue(
+          updater.enqueueReplaceState(instance, instance.state, null),
+        (ctor = workInProgress.updateQueue),
+        null !== ctor &&
+          (instance.state = processUpdateQueue(
+            current,
             workInProgress,
-            unmaskedContext,
-            props,
+            ctor,
             instance,
+            props,
             renderExpirationTime
-          ),
-          (instance.state = workInProgress.memoizedState)));
+          )));
       "function" === typeof instance.componentDidMount &&
         (workInProgress.effectTag |= 4);
     },
     resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps;
-      instance.props = oldProps;
-      var oldContext = instance.context,
+        instance = workInProgress.stateNode;
+      instance.props = workInProgress.memoizedProps;
+      instance.state = workInProgress.memoizedState;
+      var oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps,
+        oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof getDerivedStateFromProps ||
+        "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2210,29 +2115,43 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      var oldState = workInProgress.memoizedState;
-      oldContext = instance.state = oldState;
-      var updateQueue = workInProgress.updateQueue;
-      null !== updateQueue &&
-        (processUpdateQueue(
+      oldContext = workInProgress.memoizedState;
+      renderExpirationTime =
+        null !== workInProgress.updateQueue
+          ? processUpdateQueue(
+              null,
+              workInProgress,
+              workInProgress.updateQueue,
+              instance,
+              newProps,
+              renderExpirationTime
+            )
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
           workInProgress,
-          updateQueue,
-          newProps,
           instance,
+          newProps,
           renderExpirationTime
-        ),
-        (oldContext = workInProgress.memoizedState));
-      "function" === typeof getDerivedStateFromProps &&
-        (applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        ),
-        (oldContext = workInProgress.memoizedState));
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
+          null === renderExpirationTime || void 0 === renderExpirationTime
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue = workInProgress.updateQueue;
+        null !== _updateQueue &&
+          (_updateQueue.baseState = Object.assign(
+            {},
+            _updateQueue.baseState,
+            derivedStateFromProps
+          ));
+      }
       if (
         !(
           oldProps !== newProps ||
-          oldState !== oldContext ||
+          oldContext !== renderExpirationTime ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2243,12 +2162,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4),
           !1
         );
-      (renderExpirationTime = checkShouldComponentUpdate(
+      (oldProps = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
-        oldState,
         oldContext,
+        renderExpirationTime,
         newUnmaskedContext
       ))
         ? (ctor ||
@@ -2262,12 +2181,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4))
         : ("function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
-          (workInProgress.memoizedProps = newProps),
-          (workInProgress.memoizedState = oldContext));
+          memoizeProps(workInProgress, newProps),
+          memoizeState(workInProgress, renderExpirationTime));
       instance.props = newProps;
-      instance.state = oldContext;
+      instance.state = renderExpirationTime;
       instance.context = newUnmaskedContext;
-      return renderExpirationTime;
+      return oldProps;
     },
     updateClassInstance: function(
       current,
@@ -2275,16 +2194,16 @@ function ReactFiberClassComponent(
       renderExpirationTime
     ) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps;
-      instance.props = oldProps;
-      var oldContext = instance.context,
+        instance = workInProgress.stateNode;
+      instance.props = workInProgress.memoizedProps;
+      instance.state = workInProgress.memoizedState;
+      var oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps,
+        oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof getDerivedStateFromProps ||
+        "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2296,28 +2215,42 @@ function ReactFiberClassComponent(
             newUnmaskedContext
           ));
       oldContext = workInProgress.memoizedState;
-      var newState = (instance.state = oldContext),
-        updateQueue = workInProgress.updateQueue;
-      null !== updateQueue &&
-        (processUpdateQueue(
+      renderExpirationTime =
+        null !== workInProgress.updateQueue
+          ? processUpdateQueue(
+              current,
+              workInProgress,
+              workInProgress.updateQueue,
+              instance,
+              newProps,
+              renderExpirationTime
+            )
+          : oldContext;
+      var derivedStateFromProps = void 0;
+      oldProps !== newProps &&
+        (derivedStateFromProps = callGetDerivedStateFromProps(
           workInProgress,
-          updateQueue,
-          newProps,
           instance,
+          newProps,
           renderExpirationTime
-        ),
-        (newState = workInProgress.memoizedState));
-      "function" === typeof getDerivedStateFromProps &&
-        (applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        ),
-        (newState = workInProgress.memoizedState));
+        ));
+      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
+        renderExpirationTime =
+          null === renderExpirationTime || void 0 === renderExpirationTime
+            ? derivedStateFromProps
+            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
+        var _updateQueue3 = workInProgress.updateQueue;
+        null !== _updateQueue3 &&
+          (_updateQueue3.baseState = Object.assign(
+            {},
+            _updateQueue3.baseState,
+            derivedStateFromProps
+          ));
+      }
       if (
         !(
           oldProps !== newProps ||
-          oldContext !== newState ||
+          oldContext !== renderExpirationTime ||
           hasContextChanged() ||
           (null !== workInProgress.updateQueue &&
             workInProgress.updateQueue.hasForceUpdate)
@@ -2331,15 +2264,15 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 256),
+            (workInProgress.effectTag |= 2048),
           !1
         );
-      (renderExpirationTime = checkShouldComponentUpdate(
+      (derivedStateFromProps = checkShouldComponentUpdate(
         workInProgress,
         oldProps,
         newProps,
         oldContext,
-        newState,
+        renderExpirationTime,
         newUnmaskedContext
       ))
         ? (ctor ||
@@ -2348,19 +2281,19 @@ function ReactFiberClassComponent(
             ("function" === typeof instance.componentWillUpdate &&
               instance.componentWillUpdate(
                 newProps,
-                newState,
+                renderExpirationTime,
                 newUnmaskedContext
               ),
             "function" === typeof instance.UNSAFE_componentWillUpdate &&
               instance.UNSAFE_componentWillUpdate(
                 newProps,
-                newState,
+                renderExpirationTime,
                 newUnmaskedContext
               )),
           "function" === typeof instance.componentDidUpdate &&
             (workInProgress.effectTag |= 4),
           "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 256))
+            (workInProgress.effectTag |= 2048))
         : ("function" !== typeof instance.componentDidUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
@@ -2368,13 +2301,13 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 256),
-          (workInProgress.memoizedProps = newProps),
-          (workInProgress.memoizedState = newState));
+            (workInProgress.effectTag |= 2048),
+          memoizeProps(workInProgress, newProps),
+          memoizeState(workInProgress, renderExpirationTime));
       instance.props = newProps;
-      instance.state = newState;
+      instance.state = renderExpirationTime;
       instance.context = newUnmaskedContext;
-      return renderExpirationTime;
+      return derivedStateFromProps;
     }
   };
 }
@@ -2498,11 +2431,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current.return = returnFiber),
+        (current["return"] = returnFiber),
         current
       );
     current = useFiber(current, textContent, expirationTime);
-    current.return = returnFiber;
+    current["return"] = returnFiber;
     return current;
   }
   function updateElement(returnFiber, current, element, expirationTime) {
@@ -2510,7 +2443,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       return (
         (expirationTime = useFiber(current, element.props, expirationTime)),
         (expirationTime.ref = coerceRef(returnFiber, current, element)),
-        (expirationTime.return = returnFiber),
+        (expirationTime["return"] = returnFiber),
         expirationTime
       );
     expirationTime = createFiberFromElement(
@@ -2519,7 +2452,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       expirationTime
     );
     expirationTime.ref = coerceRef(returnFiber, current, element);
-    expirationTime.return = returnFiber;
+    expirationTime["return"] = returnFiber;
     return expirationTime;
   }
   function updatePortal(returnFiber, current, portal, expirationTime) {
@@ -2535,11 +2468,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current.return = returnFiber),
+        (current["return"] = returnFiber),
         current
       );
     current = useFiber(current, portal.children || [], expirationTime);
-    current.return = returnFiber;
+    current["return"] = returnFiber;
     return current;
   }
   function updateFragment(returnFiber, current, fragment, expirationTime, key) {
@@ -2551,11 +2484,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           key
         )),
-        (current.return = returnFiber),
+        (current["return"] = returnFiber),
         current
       );
     current = useFiber(current, fragment, expirationTime);
-    current.return = returnFiber;
+    current["return"] = returnFiber;
     return current;
   }
   function createChild(returnFiber, newChild, expirationTime) {
@@ -2566,7 +2499,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (newChild.return = returnFiber),
+        (newChild["return"] = returnFiber),
         newChild
       );
     if ("object" === typeof newChild && null !== newChild) {
@@ -2579,7 +2512,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               expirationTime
             )),
             (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
-            (expirationTime.return = returnFiber),
+            (expirationTime["return"] = returnFiber),
             expirationTime
           );
         case REACT_PORTAL_TYPE:
@@ -2589,7 +2522,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (newChild.return = returnFiber),
+            (newChild["return"] = returnFiber),
             newChild
           );
       }
@@ -2601,7 +2534,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime,
             null
           )),
-          (newChild.return = returnFiber),
+          (newChild["return"] = returnFiber),
           newChild
         );
       throwOnInvalidObjectType(returnFiber, newChild);
@@ -2788,21 +2721,17 @@ function ChildReconciler(shouldTrackSideEffects) {
           newChildren[newIdx],
           expirationTime
         ))
-      )
-        shouldTrackSideEffects &&
-          null !== nextOldFiber.alternate &&
-          oldFiber.delete(
+      ) {
+        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
+          oldFiber["delete"](
             null === nextOldFiber.key ? newIdx : nextOldFiber.key
-          ),
-          (currentFirstChild = placeChild(
-            nextOldFiber,
-            currentFirstChild,
-            newIdx
-          )),
-          null === previousNewFiber
-            ? (resultingFirstChild = nextOldFiber)
-            : (previousNewFiber.sibling = nextOldFiber),
-          (previousNewFiber = nextOldFiber);
+          );
+        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
+        null === previousNewFiber
+          ? (resultingFirstChild = nextOldFiber)
+          : (previousNewFiber.sibling = nextOldFiber);
+        previousNewFiber = nextOldFiber;
+      }
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2876,22 +2805,24 @@ function ChildReconciler(shouldTrackSideEffects) {
       !step.done;
       newIdx++, step = newChildrenIterable.next()
     )
-      (step = updateFromMap(
-        oldFiber,
-        returnFiber,
-        newIdx,
-        step.value,
-        expirationTime
-      )),
-        null !== step &&
-          (shouldTrackSideEffects &&
-            null !== step.alternate &&
-            oldFiber.delete(null === step.key ? newIdx : step.key),
-          (currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
-          null === previousNewFiber
-            ? (iteratorFn = step)
-            : (previousNewFiber.sibling = step),
-          (previousNewFiber = step));
+      if (
+        ((step = updateFromMap(
+          oldFiber,
+          returnFiber,
+          newIdx,
+          step.value,
+          expirationTime
+        )),
+        null !== step)
+      ) {
+        if (shouldTrackSideEffects && null !== step.alternate)
+          oldFiber["delete"](null === step.key ? newIdx : step.key);
+        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
+        null === previousNewFiber
+          ? (iteratorFn = step)
+          : (previousNewFiber.sibling = step);
+        previousNewFiber = step;
+      }
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2930,7 +2861,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     isObject,
                     newChild
                   );
-                  currentFirstChild.return = returnFiber;
+                  currentFirstChild["return"] = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2947,7 +2878,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   expirationTime,
                   newChild.key
                 )),
-                (currentFirstChild.return = returnFiber),
+                (currentFirstChild["return"] = returnFiber),
                 (returnFiber = currentFirstChild))
               : ((expirationTime = createFiberFromElement(
                   newChild,
@@ -2959,7 +2890,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   currentFirstChild,
                   newChild
                 )),
-                (expirationTime.return = returnFiber),
+                (expirationTime["return"] = returnFiber),
                 (returnFiber = expirationTime));
           }
           return placeSingleChild(returnFiber);
@@ -2983,7 +2914,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     newChild.children || [],
                     expirationTime
                   );
-                  currentFirstChild.return = returnFiber;
+                  currentFirstChild["return"] = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2998,7 +2929,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             );
-            currentFirstChild.return = returnFiber;
+            currentFirstChild["return"] = returnFiber;
             returnFiber = currentFirstChild;
           }
           return placeSingleChild(returnFiber);
@@ -3013,7 +2944,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               newChild,
               expirationTime
             )),
-            (currentFirstChild.return = returnFiber),
+            (currentFirstChild["return"] = returnFiber),
             (returnFiber = currentFirstChild))
           : (deleteRemainingChildren(returnFiber, currentFirstChild),
             (currentFirstChild = createFiberFromText(
@@ -3021,7 +2952,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (currentFirstChild.return = returnFiber),
+            (currentFirstChild["return"] = returnFiber),
             (returnFiber = currentFirstChild)),
         placeSingleChild(returnFiber)
       );
@@ -3107,10 +3038,10 @@ function ReactFiberBeginWork(
     workInProgress,
     shouldUpdate,
     hasContext,
+    didCaptureError,
     renderExpirationTime
   ) {
     markRef(current, workInProgress);
-    var didCaptureError = 0 !== (workInProgress.effectTag & 64);
     if (!shouldUpdate && !didCaptureError)
       return (
         hasContext && invalidateContextProvider(workInProgress, !1),
@@ -3158,8 +3089,11 @@ function ReactFiberBeginWork(
     renderExpirationTime
   ) {
     var fiber = workInProgress.child;
-    null !== fiber && (fiber.return = workInProgress);
-    for (; null !== fiber; ) {
+    for (
+      null !== fiber && (fiber["return"] = workInProgress);
+      null !== fiber;
+
+    ) {
       switch (fiber.tag) {
         case 12:
           var nextFiber = fiber.stateNode | 0;
@@ -3182,7 +3116,7 @@ function ReactFiberBeginWork(
               )
                 alternate.expirationTime = renderExpirationTime;
               else break;
-              nextFiber = nextFiber.return;
+              nextFiber = nextFiber["return"];
             }
             nextFiber = null;
           } else nextFiber = fiber.child;
@@ -3193,7 +3127,7 @@ function ReactFiberBeginWork(
         default:
           nextFiber = fiber.child;
       }
-      if (null !== nextFiber) nextFiber.return = fiber;
+      if (null !== nextFiber) nextFiber["return"] = fiber;
       else
         for (nextFiber = fiber; null !== nextFiber; ) {
           if (nextFiber === workInProgress) {
@@ -3202,11 +3136,10 @@ function ReactFiberBeginWork(
           }
           fiber = nextFiber.sibling;
           if (null !== fiber) {
-            fiber.return = nextFiber.return;
             nextFiber = fiber;
             break;
           }
-          nextFiber = nextFiber.return;
+          nextFiber = nextFiber["return"];
         }
       fiber = nextFiber;
     }
@@ -3218,10 +3151,8 @@ function ReactFiberBeginWork(
   ) {
     var context = workInProgress.type._context,
       newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps,
-      canBailOnProps = !0;
-    if (hasLegacyContextChanged()) canBailOnProps = !1;
-    else if (oldProps === newProps)
+      oldProps = workInProgress.memoizedProps;
+    if (!hasLegacyContextChanged() && oldProps === newProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
@@ -3231,7 +3162,7 @@ function ReactFiberBeginWork(
     workInProgress.memoizedProps = newProps;
     if (null === oldProps) newValue = 1073741823;
     else if (oldProps.value === newProps.value) {
-      if (oldProps.children === newProps.children && canBailOnProps)
+      if (oldProps.children === newProps.children)
         return (
           (workInProgress.stateNode = 0),
           pushProvider(workInProgress),
@@ -3245,7 +3176,7 @@ function ReactFiberBeginWork(
           (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
         (oldValue !== oldValue && newValue !== newValue)
       ) {
-        if (oldProps.children === newProps.children && canBailOnProps)
+        if (oldProps.children === newProps.children)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3260,7 +3191,7 @@ function ReactFiberBeginWork(
         (newValue |= 0),
         0 === newValue)
       ) {
-        if (oldProps.children === newProps.children && canBailOnProps)
+        if (oldProps.children === newProps.children)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3292,14 +3223,14 @@ function ReactFiberBeginWork(
         current.expirationTime
       );
       workInProgress.child = newChild;
-      for (newChild.return = workInProgress; null !== current.sibling; )
+      for (newChild["return"] = workInProgress; null !== current.sibling; )
         (current = current.sibling),
           (newChild = newChild.sibling = createWorkInProgress(
             current,
             current.pendingProps,
             current.expirationTime
           )),
-          (newChild.return = workInProgress);
+          (newChild["return"] = workInProgress);
       newChild.sibling = null;
     }
     return workInProgress.child;
@@ -3331,6 +3262,7 @@ function ReactFiberBeginWork(
     }
   );
   var adoptClassInstance = config.adoptClassInstance,
+    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
     constructClassInstance = config.constructClassInstance,
     mountClassInstance = config.mountClassInstance,
     resumeMountClassInstance = config.resumeMountClassInstance,
@@ -3379,13 +3311,20 @@ function ReactFiberBeginWork(
               (workInProgress.tag = 2),
               (workInProgress.memoizedState =
                 null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
-              "function" === typeof unmaskedContext &&
-                applyDerivedStateFromProps(
+              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
+                ((props = callGetDerivedStateFromProps(
                   workInProgress,
-                  unmaskedContext,
-                  props
-                ),
+                  fn,
+                  props,
+                  workInProgress.memoizedState
+                )),
+                null !== props &&
+                  void 0 !== props &&
+                  (workInProgress.memoizedState = Object.assign(
+                    {},
+                    workInProgress.memoizedState,
+                    props
+                  ))),
               (props = pushLegacyContextProvider(workInProgress)),
               adoptClassInstance(workInProgress, fn),
               mountClassInstance(workInProgress, renderExpirationTime),
@@ -3394,6 +3333,7 @@ function ReactFiberBeginWork(
                 workInProgress,
                 !0,
                 props,
+                !1,
                 renderExpirationTime
               )))
             : ((workInProgress.tag = 1),
@@ -3421,100 +3361,103 @@ function ReactFiberBeginWork(
             current
           );
         case 2:
-          return (
-            (props = pushLegacyContextProvider(workInProgress)),
-            null === current
-              ? null === workInProgress.stateNode
-                ? (constructClassInstance(
-                    workInProgress,
-                    workInProgress.pendingProps,
-                    renderExpirationTime
-                  ),
-                  mountClassInstance(workInProgress, renderExpirationTime),
-                  (fn = !0))
-                : (fn = resumeMountClassInstance(
-                    workInProgress,
-                    renderExpirationTime
-                  ))
-              : (fn = updateClassInstance(
-                  current,
+          props = pushLegacyContextProvider(workInProgress);
+          null === current
+            ? null === workInProgress.stateNode
+              ? (constructClassInstance(
+                  workInProgress,
+                  workInProgress.pendingProps
+                ),
+                mountClassInstance(workInProgress, renderExpirationTime),
+                (fn = !0))
+              : (fn = resumeMountClassInstance(
                   workInProgress,
                   renderExpirationTime
-                )),
-            finishClassComponent(
+                ))
+            : (fn = updateClassInstance(
+                current,
+                workInProgress,
+                renderExpirationTime
+              ));
+          unmaskedContext = !1;
+          var updateQueue = workInProgress.updateQueue;
+          null !== updateQueue &&
+            null !== updateQueue.capturedValues &&
+            (unmaskedContext = fn = !0);
+          return finishClassComponent(
+            current,
+            workInProgress,
+            fn,
+            props,
+            unmaskedContext,
+            renderExpirationTime
+          );
+        case 3:
+          a: if (
+            (pushHostRootContext(workInProgress),
+            (fn = workInProgress.updateQueue),
+            null !== fn)
+          ) {
+            unmaskedContext = workInProgress.memoizedState;
+            props = processUpdateQueue(
               current,
               workInProgress,
               fn,
-              props,
+              null,
+              null,
               renderExpirationTime
-            )
-          );
-        case 3:
-          return (
-            pushHostRootContext(workInProgress),
-            (props = workInProgress.updateQueue),
-            null !== props
-              ? ((fn = workInProgress.memoizedState),
-                (fn = null !== fn ? fn.element : null),
-                processUpdateQueue(
+            );
+            workInProgress.memoizedState = props;
+            fn = workInProgress.updateQueue;
+            if (null !== fn && null !== fn.capturedValues) fn = null;
+            else if (unmaskedContext === props) {
+              resetHydrationState();
+              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+              break a;
+            } else fn = props.element;
+            unmaskedContext = workInProgress.stateNode;
+            (null === current || null === current.child) &&
+            unmaskedContext.hydrate &&
+            enterHydrationState(workInProgress)
+              ? ((workInProgress.effectTag |= 2),
+                (workInProgress.child = mountChildFibers(
                   workInProgress,
-                  props,
-                  workInProgress.pendingProps,
                   null,
+                  fn,
                   renderExpirationTime
-                ),
-                (props = workInProgress.memoizedState.element),
-                props === fn
-                  ? (resetHydrationState(),
-                    (current = bailoutOnAlreadyFinishedWork(
-                      current,
-                      workInProgress
-                    )))
-                  : ((fn = workInProgress.stateNode),
-                    (null === current || null === current.child) &&
-                    fn.hydrate &&
-                    enterHydrationState(workInProgress)
-                      ? ((workInProgress.effectTag |= 2),
-                        (workInProgress.child = mountChildFibers(
-                          workInProgress,
-                          null,
-                          props,
-                          renderExpirationTime
-                        )))
-                      : (resetHydrationState(),
-                        reconcileChildren(current, workInProgress, props)),
-                    (current = workInProgress.child)))
+                )))
               : (resetHydrationState(),
-                (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                ))),
-            current
-          );
+                reconcileChildren(current, workInProgress, fn));
+            workInProgress.memoizedState = props;
+            current = workInProgress.child;
+          } else
+            resetHydrationState(),
+              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
+          return current;
         case 5:
           a: {
             pushHostContext(workInProgress);
             null === current &&
               tryToClaimNextHydratableInstance(workInProgress);
             props = workInProgress.type;
-            var memoizedProps = workInProgress.memoizedProps;
+            updateQueue = workInProgress.memoizedProps;
             fn = workInProgress.pendingProps;
             unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && memoizedProps === fn) {
+            if (!hasLegacyContextChanged() && updateQueue === fn) {
               if (
-                (memoizedProps =
+                (updateQueue =
                   workInProgress.mode & 1 &&
                   shouldDeprioritizeSubtree(props, fn))
               )
                 workInProgress.expirationTime = 1073741823;
-              if (!memoizedProps || 1073741823 !== renderExpirationTime) {
+              if (!updateQueue || 1073741823 !== renderExpirationTime) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
             }
-            memoizedProps = fn.children;
+            updateQueue = fn.children;
             shouldSetTextContent(props, fn)
-              ? (memoizedProps = null)
+              ? (updateQueue = null)
               : unmaskedContext &&
                 shouldSetTextContent(props, unmaskedContext) &&
                 (workInProgress.effectTag |= 16);
@@ -3525,7 +3468,7 @@ function ReactFiberBeginWork(
               ? ((workInProgress.expirationTime = 1073741823),
                 (workInProgress.memoizedProps = fn),
                 (current = null))
-              : (reconcileChildren(current, workInProgress, memoizedProps),
+              : (reconcileChildren(current, workInProgress, updateQueue),
                 (workInProgress.memoizedProps = fn),
                 (current = workInProgress.child));
           }
@@ -3591,21 +3534,14 @@ function ReactFiberBeginWork(
           );
         case 14:
           return (
-            (props = workInProgress.type.render),
-            (renderExpirationTime = workInProgress.pendingProps),
-            (fn = workInProgress.ref),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime ||
-            fn !== (null !== current ? current.ref : null)
-              ? ((props = props(renderExpirationTime, fn)),
-                reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
+            (renderExpirationTime = workInProgress.type.render),
+            (renderExpirationTime = renderExpirationTime(
+              workInProgress.pendingProps,
+              workInProgress.ref
+            )),
+            reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            workInProgress.child
           );
         case 10:
           return (
@@ -3654,13 +3590,13 @@ function ReactFiberBeginWork(
           a: {
             fn = workInProgress.type;
             unmaskedContext = workInProgress.pendingProps;
-            memoizedProps = workInProgress.memoizedProps;
+            updateQueue = workInProgress.memoizedProps;
             props = fn._currentValue;
             var changedBits = fn._changedBits;
             if (
               hasLegacyContextChanged() ||
               0 !== changedBits ||
-              memoizedProps !== unmaskedContext
+              updateQueue !== unmaskedContext
             ) {
               workInProgress.memoizedProps = unmaskedContext;
               var observedBits = unmaskedContext.unstable_observedBits;
@@ -3674,13 +3610,12 @@ function ReactFiberBeginWork(
                   changedBits,
                   renderExpirationTime
                 );
-              else if (memoizedProps === unmaskedContext) {
+              else if (updateQueue === unmaskedContext) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
               renderExpirationTime = unmaskedContext.children;
               renderExpirationTime = renderExpirationTime(props);
-              workInProgress.effectTag |= 1;
               reconcileChildren(current, workInProgress, renderExpirationTime);
               current = workInProgress.child;
             } else
@@ -3746,7 +3681,18 @@ function ReactFiberCompleteWork(
         case 1:
           return null;
         case 2:
-          return popLegacyContextProvider(workInProgress), null;
+          return (
+            popLegacyContextProvider(workInProgress),
+            (current = workInProgress.stateNode),
+            (newProps = workInProgress.updateQueue),
+            null !== newProps &&
+              null !== newProps.capturedValues &&
+              ((workInProgress.effectTag &= -65),
+              "function" === typeof current.componentDidCatch
+                ? (workInProgress.effectTag |= 256)
+                : (newProps.capturedValues = null)),
+            null
+          );
         case 3:
           popHostContainer(workInProgress);
           popTopLevelLegacyContextObject(workInProgress);
@@ -3757,6 +3703,10 @@ function ReactFiberCompleteWork(
           if (null === current || null === current.child)
             popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
           updateHostContainer(workInProgress);
+          current = workInProgress.updateQueue;
+          null !== current &&
+            null !== current.capturedValues &&
+            (workInProgress.effectTag |= 256);
           return null;
         case 5:
           popHostContext(workInProgress);
@@ -3764,10 +3714,10 @@ function ReactFiberCompleteWork(
           var type = workInProgress.type;
           if (null !== current && null != workInProgress.stateNode) {
             var oldProps = current.memoizedProps,
-              instance = workInProgress.stateNode,
+              _instance = workInProgress.stateNode,
               currentHostContext = getHostContext();
-            instance = prepareUpdate(
-              instance,
+            _instance = prepareUpdate(
+              _instance,
               type,
               oldProps,
               newProps,
@@ -3777,7 +3727,7 @@ function ReactFiberCompleteWork(
             updateHostComponent(
               current,
               workInProgress,
-              instance,
+              _instance,
               type,
               oldProps,
               newProps,
@@ -3824,20 +3774,21 @@ function ReactFiberCompleteWork(
                   4 !== currentHostContext.tag &&
                   null !== currentHostContext.child
                 ) {
-                  currentHostContext.child.return = currentHostContext;
+                  currentHostContext.child["return"] = currentHostContext;
                   currentHostContext = currentHostContext.child;
                   continue;
                 }
                 if (currentHostContext === workInProgress) break;
                 for (; null === currentHostContext.sibling; ) {
                   if (
-                    null === currentHostContext.return ||
-                    currentHostContext.return === workInProgress
+                    null === currentHostContext["return"] ||
+                    currentHostContext["return"] === workInProgress
                   )
                     break a;
-                  currentHostContext = currentHostContext.return;
+                  currentHostContext = currentHostContext["return"];
                 }
-                currentHostContext.sibling.return = currentHostContext.return;
+                currentHostContext.sibling["return"] =
+                  currentHostContext["return"];
                 currentHostContext = currentHostContext.sibling;
               }
               finalizeInitialChildren(
@@ -3890,34 +3841,30 @@ function ReactFiberCompleteWork(
           );
           workInProgress.tag = 8;
           type = [];
-          a: {
-            if ((oldProps = workInProgress.stateNode))
-              oldProps.return = workInProgress;
-            for (; null !== oldProps; ) {
+          a: for (
+            (oldProps = workInProgress.stateNode) &&
+            (oldProps["return"] = workInProgress);
+            null !== oldProps;
+
+          ) {
+            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
+              invariant(!1, "A call cannot have host component children.");
+            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
+            else if (null !== oldProps.child) {
+              oldProps.child["return"] = oldProps;
+              oldProps = oldProps.child;
+              continue;
+            }
+            for (; null === oldProps.sibling; ) {
               if (
-                5 === oldProps.tag ||
-                6 === oldProps.tag ||
-                4 === oldProps.tag
+                null === oldProps["return"] ||
+                oldProps["return"] === workInProgress
               )
-                invariant(!1, "A call cannot have host component children.");
-              else if (9 === oldProps.tag)
-                type.push(oldProps.pendingProps.value);
-              else if (null !== oldProps.child) {
-                oldProps.child.return = oldProps;
-                oldProps = oldProps.child;
-                continue;
-              }
-              for (; null === oldProps.sibling; ) {
-                if (
-                  null === oldProps.return ||
-                  oldProps.return === workInProgress
-                )
-                  break a;
-                oldProps = oldProps.return;
-              }
-              oldProps.sibling.return = oldProps.return;
-              oldProps = oldProps.sibling;
+                break a;
+              oldProps = oldProps["return"];
             }
+            oldProps.sibling["return"] = oldProps["return"];
+            oldProps = oldProps.sibling;
           }
           oldProps = newProps.handler;
           newProps = oldProps(newProps.props, type);
@@ -3962,11 +3909,103 @@ function ReactFiberCompleteWork(
     }
   };
 }
-function createCapturedValue(value, source) {
+function ReactFiberUnwindWork(
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  isAlreadyFailedLegacyErrorBoundary
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
   return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
+    throwException: function(returnFiber, sourceFiber, rawValue) {
+      sourceFiber.effectTag |= 512;
+      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+      sourceFiber = {
+        value: rawValue,
+        source: sourceFiber,
+        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
+      };
+      do {
+        switch (returnFiber.tag) {
+          case 3:
+            ensureUpdateQueues(returnFiber);
+            returnFiber.updateQueue.capturedValues = [sourceFiber];
+            returnFiber.effectTag |= 1024;
+            return;
+          case 2:
+            if (
+              ((rawValue = returnFiber.stateNode),
+              0 === (returnFiber.effectTag & 64) &&
+                null !== rawValue &&
+                "function" === typeof rawValue.componentDidCatch &&
+                !isAlreadyFailedLegacyErrorBoundary(rawValue))
+            ) {
+              ensureUpdateQueues(returnFiber);
+              rawValue = returnFiber.updateQueue;
+              var capturedValues = rawValue.capturedValues;
+              null === capturedValues
+                ? (rawValue.capturedValues = [sourceFiber])
+                : capturedValues.push(sourceFiber);
+              returnFiber.effectTag |= 1024;
+              return;
+            }
+        }
+        returnFiber = returnFiber["return"];
+      } while (null !== returnFiber);
+    },
+    unwindWork: function(workInProgress) {
+      switch (workInProgress.tag) {
+        case 2:
+          popLegacyContextProvider(workInProgress);
+          var effectTag = workInProgress.effectTag;
+          return effectTag & 1024
+            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+              workInProgress)
+            : null;
+        case 3:
+          return (
+            popHostContainer(workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 5:
+          return popHostContext(workInProgress), null;
+        case 4:
+          return popHostContainer(workInProgress), null;
+        case 13:
+          return popProvider(workInProgress), null;
+        default:
+          return null;
+      }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
+    }
   };
 }
 function logError(boundary, errorInfo) {
@@ -3998,7 +4037,13 @@ function logError(boundary, errorInfo) {
     (e && e.suppressReactErrorLogging) || console.error(e);
   }
 }
-function ReactFiberCommitWork(config, captureError) {
+function ReactFiberCommitWork(
+  config,
+  captureError,
+  scheduleWork,
+  computeExpirationForFiber,
+  markLegacyErrorBoundaryAsFailed
+) {
   function safelyDetachRef(current) {
     var ref = current.ref;
     if (null !== ref)
@@ -4015,12 +4060,12 @@ function ReactFiberCommitWork(config, captureError) {
     switch (current.tag) {
       case 2:
         safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if ("function" === typeof _instance6.componentWillUnmount)
+        var _instance7 = current.stateNode;
+        if ("function" === typeof _instance7.componentWillUnmount)
           try {
-            (_instance6.props = current.memoizedProps),
-              (_instance6.state = current.memoizedState),
-              _instance6.componentWillUnmount();
+            (_instance7.props = current.memoizedProps),
+              (_instance7.state = current.memoizedState),
+              _instance7.componentWillUnmount();
           } catch (unmountError) {
             captureError(current, unmountError);
           }
@@ -4043,12 +4088,12 @@ function ReactFiberCommitWork(config, captureError) {
       ) {
         if (node === root) break;
         for (; null === node.sibling; ) {
-          if (null === node.return || node.return === root) return;
-          node = node.return;
+          if (null === node["return"] || node["return"] === root) return;
+          node = node["return"];
         }
-        node.sibling.return = node.return;
+        node.sibling["return"] = node["return"];
         node = node.sibling;
-      } else (node.child.return = node), (node = node.child);
+      } else (node.child["return"] = node), (node = node.child);
   }
   function isHostParent(fiber) {
     return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
@@ -4063,7 +4108,7 @@ function ReactFiberCommitWork(config, captureError) {
 
     ) {
       if (!currentParentIsValid) {
-        currentParentIsValid = node.return;
+        currentParentIsValid = node["return"];
         a: for (;;) {
           invariant(
             null !== currentParentIsValid,
@@ -4083,7 +4128,7 @@ function ReactFiberCommitWork(config, captureError) {
               currentParentIsContainer = !0;
               break a;
           }
-          currentParentIsValid = currentParentIsValid.return;
+          currentParentIsValid = currentParentIsValid["return"];
         }
         currentParentIsValid = !0;
       }
@@ -4098,17 +4143,17 @@ function ReactFiberCommitWork(config, captureError) {
           : commitUnmount(node),
         null !== node.child)
       ) {
-        node.child.return = node;
+        node.child["return"] = node;
         node = node.child;
         continue;
       }
       if (node === current) break;
       for (; null === node.sibling; ) {
-        if (null === node.return || node.return === current) return;
-        node = node.return;
+        if (null === node["return"] || node["return"] === current) return;
+        node = node["return"];
         4 === node.tag && (currentParentIsValid = !1);
       }
-      node.sibling.return = node.return;
+      node.sibling["return"] = node["return"];
       node = node.sibling;
     }
   }
@@ -4133,7 +4178,7 @@ function ReactFiberCommitWork(config, captureError) {
     commitBeforeMutationLifeCycles: function(current, finishedWork) {
       switch (finishedWork.tag) {
         case 2:
-          if (finishedWork.effectTag & 256 && null !== current) {
+          if (finishedWork.effectTag & 2048 && null !== current) {
             var prevProps = current.memoizedProps,
               prevState = current.memoizedState;
             current = finishedWork.stateNode;
@@ -4163,12 +4208,12 @@ function ReactFiberCommitWork(config, captureError) {
     },
     commitPlacement: function(finishedWork) {
       a: {
-        for (var parent = finishedWork.return; null !== parent; ) {
+        for (var parent = finishedWork["return"]; null !== parent; ) {
           if (isHostParent(parent)) {
             var parentFiber = parent;
             break a;
           }
-          parent = parent.return;
+          parent = parent["return"];
         }
         invariant(
           !1,
@@ -4200,13 +4245,16 @@ function ReactFiberCommitWork(config, captureError) {
         (resetTextContent(parent), (parentFiber.effectTag &= -17));
       a: b: for (parentFiber = finishedWork; ; ) {
         for (; null === parentFiber.sibling; ) {
-          if (null === parentFiber.return || isHostParent(parentFiber.return)) {
+          if (
+            null === parentFiber["return"] ||
+            isHostParent(parentFiber["return"])
+          ) {
             parentFiber = null;
             break a;
           }
-          parentFiber = parentFiber.return;
+          parentFiber = parentFiber["return"];
         }
-        parentFiber.sibling.return = parentFiber.return;
+        parentFiber.sibling["return"] = parentFiber["return"];
         for (
           parentFiber = parentFiber.sibling;
           5 !== parentFiber.tag && 6 !== parentFiber.tag;
@@ -4215,7 +4263,7 @@ function ReactFiberCommitWork(config, captureError) {
           if (parentFiber.effectTag & 2) continue b;
           if (null === parentFiber.child || 4 === parentFiber.tag) continue b;
           else
-            (parentFiber.child.return = parentFiber),
+            (parentFiber.child["return"] = parentFiber),
               (parentFiber = parentFiber.child);
         }
         if (!(parentFiber.effectTag & 2)) {
@@ -4233,33 +4281,35 @@ function ReactFiberCommitWork(config, captureError) {
               ? appendChildToContainer(parent, node.stateNode)
               : appendChild(parent, node.stateNode);
         else if (4 !== node.tag && null !== node.child) {
-          node.child.return = node;
+          node.child["return"] = node;
           node = node.child;
           continue;
         }
         if (node === finishedWork) break;
         for (; null === node.sibling; ) {
-          if (null === node.return || node.return === finishedWork) return;
-          node = node.return;
+          if (null === node["return"] || node["return"] === finishedWork)
+            return;
+          node = node["return"];
         }
-        node.sibling.return = node.return;
+        node.sibling["return"] = node["return"];
         node = node.sibling;
       }
     },
     commitDeletion: function(current) {
       unmountHostComponents(current);
-      current.return = null;
+      current["return"] = null;
       current.child = null;
       current.alternate &&
-        ((current.alternate.child = null), (current.alternate.return = null));
+        ((current.alternate.child = null),
+        (current.alternate["return"] = null));
     },
     commitWork: function(current, finishedWork) {
       switch (finishedWork.tag) {
         case 2:
           break;
         case 5:
-          var _instance7 = finishedWork.stateNode;
-          if (null != _instance7) {
+          var _instance8 = finishedWork.stateNode;
+          if (null != _instance8) {
             var newProps = finishedWork.memoizedProps;
             current = null !== current ? current.memoizedProps : newProps;
             var type = finishedWork.type,
@@ -4267,7 +4317,7 @@ function ReactFiberCommitWork(config, captureError) {
             finishedWork.updateQueue = null;
             null !== updatePayload &&
               commitUpdate(
-                _instance7,
+                _instance8,
                 updatePayload,
                 type,
                 current,
@@ -4281,11 +4331,11 @@ function ReactFiberCommitWork(config, captureError) {
             null !== finishedWork.stateNode,
             "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
           );
-          _instance7 = finishedWork.memoizedProps;
+          _instance8 = finishedWork.memoizedProps;
           commitTextUpdate(
             finishedWork.stateNode,
-            null !== current ? current.memoizedProps : _instance7,
-            _instance7
+            null !== current ? current.memoizedProps : _instance8,
+            _instance8
           );
           break;
         case 3:
@@ -4297,40 +4347,28 @@ function ReactFiberCommitWork(config, captureError) {
           );
       }
     },
-    commitLifeCycles: function(
-      finishedRoot,
-      current,
-      finishedWork,
-      currentTime,
-      committedExpirationTime
-    ) {
+    commitLifeCycles: function(finishedRoot, current, finishedWork) {
       switch (finishedWork.tag) {
         case 2:
           finishedRoot = finishedWork.stateNode;
-          finishedWork.effectTag & 4 &&
-            (null === current
-              ? ((finishedRoot.props = finishedWork.memoizedProps),
-                (finishedRoot.state = finishedWork.memoizedState),
-                finishedRoot.componentDidMount())
-              : ((currentTime = current.memoizedProps),
-                (current = current.memoizedState),
-                (finishedRoot.props = finishedWork.memoizedProps),
+          if (finishedWork.effectTag & 4)
+            if (null === current)
+              (finishedRoot.props = finishedWork.memoizedProps),
                 (finishedRoot.state = finishedWork.memoizedState),
-                finishedRoot.componentDidUpdate(
-                  currentTime,
-                  current,
-                  finishedRoot.__reactInternalSnapshotBeforeUpdate
-                )));
-          current = finishedWork.updateQueue;
-          null !== current &&
-            ((finishedRoot.props = finishedWork.memoizedProps),
-            (finishedRoot.state = finishedWork.memoizedState),
-            commitUpdateQueue(
-              finishedWork,
-              current,
-              finishedRoot,
-              committedExpirationTime
-            ));
+                finishedRoot.componentDidMount();
+            else {
+              var prevProps = current.memoizedProps;
+              current = current.memoizedState;
+              finishedRoot.props = finishedWork.memoizedProps;
+              finishedRoot.state = finishedWork.memoizedState;
+              finishedRoot.componentDidUpdate(
+                prevProps,
+                current,
+                finishedRoot.__reactInternalSnapshotBeforeUpdate
+              );
+            }
+          finishedWork = finishedWork.updateQueue;
+          null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
           break;
         case 3:
           current = finishedWork.updateQueue;
@@ -4346,20 +4384,15 @@ function ReactFiberCommitWork(config, captureError) {
                 case 2:
                   finishedRoot = finishedWork.child.stateNode;
               }
-            commitUpdateQueue(
-              finishedWork,
-              current,
-              finishedRoot,
-              committedExpirationTime
-            );
+            commitCallbacks(current, finishedRoot);
           }
           break;
         case 5:
-          committedExpirationTime = finishedWork.stateNode;
+          finishedRoot = finishedWork.stateNode;
           null === current &&
             finishedWork.effectTag & 4 &&
             commitMount(
-              committedExpirationTime,
+              finishedRoot,
               finishedWork.type,
               finishedWork.memoizedProps,
               finishedWork
@@ -4376,16 +4409,62 @@ function ReactFiberCommitWork(config, captureError) {
           );
       }
     },
+    commitErrorLogging: function(finishedWork, onUncaughtError) {
+      switch (finishedWork.tag) {
+        case 2:
+          var ctor = finishedWork.type;
+          onUncaughtError = finishedWork.stateNode;
+          var updateQueue = finishedWork.updateQueue;
+          invariant(
+            null !== updateQueue && null !== updateQueue.capturedValues,
+            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
+          );
+          var capturedErrors = updateQueue.capturedValues;
+          updateQueue.capturedValues = null;
+          "function" !== typeof ctor.getDerivedStateFromCatch &&
+            markLegacyErrorBoundaryAsFailed(onUncaughtError);
+          onUncaughtError.props = finishedWork.memoizedProps;
+          onUncaughtError.state = finishedWork.memoizedState;
+          for (ctor = 0; ctor < capturedErrors.length; ctor++) {
+            updateQueue = capturedErrors[ctor];
+            var _error = updateQueue.value,
+              stack = updateQueue.stack;
+            logError(finishedWork, updateQueue);
+            onUncaughtError.componentDidCatch(_error, {
+              componentStack: null !== stack ? stack : ""
+            });
+          }
+          break;
+        case 3:
+          ctor = finishedWork.updateQueue;
+          invariant(
+            null !== ctor && null !== ctor.capturedValues,
+            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
+          );
+          capturedErrors = ctor.capturedValues;
+          ctor.capturedValues = null;
+          for (ctor = 0; ctor < capturedErrors.length; ctor++)
+            (updateQueue = capturedErrors[ctor]),
+              logError(finishedWork, updateQueue),
+              onUncaughtError(updateQueue.value);
+          break;
+        default:
+          invariant(
+            !1,
+            "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
+          );
+      }
+    },
     commitAttachRef: function(finishedWork) {
       var ref = finishedWork.ref;
       if (null !== ref) {
-        var _instance5 = finishedWork.stateNode;
+        var _instance6 = finishedWork.stateNode;
         switch (finishedWork.tag) {
           case 5:
-            finishedWork = getPublicInstance(_instance5);
+            finishedWork = getPublicInstance(_instance6);
             break;
           default:
-            finishedWork = _instance5;
+            finishedWork = _instance6;
         }
         "function" === typeof ref
           ? ref(finishedWork)
@@ -4401,151 +4480,6 @@ function ReactFiberCommitWork(config, captureError) {
     }
   };
 }
-function ReactFiberUnwindWork(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  markLegacyErrorBoundaryAsFailed,
-  isAlreadyFailedLegacyErrorBoundary,
-  onUncaughtError
-) {
-  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
-    expirationTime = createUpdate(expirationTime);
-    expirationTime.tag = 3;
-    expirationTime.payload = { element: null };
-    var error = errorInfo.value;
-    expirationTime.callback = function() {
-      onUncaughtError(error);
-      logError(fiber, errorInfo);
-    };
-    return expirationTime;
-  }
-  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
-    expirationTime = createUpdate(expirationTime);
-    expirationTime.tag = 3;
-    var inst = fiber.stateNode;
-    null !== inst &&
-      "function" === typeof inst.componentDidCatch &&
-      (expirationTime.callback = function() {
-        markLegacyErrorBoundaryAsFailed(this);
-        var error = errorInfo.value,
-          stack = errorInfo.stack;
-        logError(fiber, errorInfo);
-        this.componentDidCatch(error, {
-          componentStack: null !== stack ? stack : ""
-        });
-      });
-    return expirationTime;
-  }
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
-  return {
-    throwException: function(
-      returnFiber,
-      sourceFiber,
-      rawValue,
-      renderExpirationTime
-    ) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      sourceFiber = createCapturedValue(rawValue, sourceFiber);
-      do {
-        switch (returnFiber.tag) {
-          case 3:
-            returnFiber.effectTag |= 1024;
-            sourceFiber = createRootErrorUpdate(
-              returnFiber,
-              sourceFiber,
-              renderExpirationTime
-            );
-            enqueueCapturedUpdate(
-              returnFiber,
-              sourceFiber,
-              renderExpirationTime
-            );
-            return;
-          case 2:
-            rawValue = sourceFiber;
-            var _instance = returnFiber.stateNode;
-            if (
-              0 === (returnFiber.effectTag & 64) &&
-              null !== _instance &&
-              "function" === typeof _instance.componentDidCatch &&
-              !isAlreadyFailedLegacyErrorBoundary(_instance)
-            ) {
-              returnFiber.effectTag |= 1024;
-              sourceFiber = createClassErrorUpdate(
-                returnFiber,
-                rawValue,
-                renderExpirationTime
-              );
-              enqueueCapturedUpdate(
-                returnFiber,
-                sourceFiber,
-                renderExpirationTime
-              );
-              return;
-            }
-        }
-        returnFiber = returnFiber.return;
-      } while (null !== returnFiber);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
-      }
-    },
-    createRootErrorUpdate: createRootErrorUpdate,
-    createClassErrorUpdate: createClassErrorUpdate
-  };
-}
 var NO_CONTEXT = {};
 function ReactFiberHostContext(config, stack) {
   function requiredContext(c) {
@@ -4602,7 +4536,7 @@ function ReactFiberHydrationContext(config) {
     var fiber = new FiberNode(5, null, null, 0);
     fiber.type = "DELETED";
     fiber.stateNode = instance;
-    fiber.return = returnFiber;
+    fiber["return"] = returnFiber;
     fiber.effectTag = 8;
     null !== returnFiber.lastEffect
       ? ((returnFiber.lastEffect.nextEffect = fiber),
@@ -4634,11 +4568,11 @@ function ReactFiberHydrationContext(config) {
   }
   function popToNextHostParent(fiber) {
     for (
-      fiber = fiber.return;
+      fiber = fiber["return"];
       null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
 
     )
-      fiber = fiber.return;
+      fiber = fiber["return"];
     hydrationParentFiber = fiber;
   }
   var shouldSetTextContent = config.shouldSetTextContent;
@@ -4872,7 +4806,7 @@ function ReactFiberLegacyContext(stack) {
       ) {
         if (isContextProvider(fiber))
           return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber.return;
+        fiber = fiber["return"];
         invariant(
           fiber,
           "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
@@ -4939,12 +4873,12 @@ function ReactFiberScheduler(config) {
   function resetStack() {
     if (null !== nextUnitOfWork)
       for (
-        var interruptedWork = nextUnitOfWork.return;
+        var interruptedWork = nextUnitOfWork["return"];
         null !== interruptedWork;
 
       )
         unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork.return);
+          (interruptedWork = interruptedWork["return"]);
     nextRoot = null;
     nextRenderExpirationTime = 0;
     nextUnitOfWork = null;
@@ -4956,71 +4890,74 @@ function ReactFiberScheduler(config) {
       legacyErrorBoundariesThatAlreadyFailed.has(instance)
     );
   }
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    null === legacyErrorBoundariesThatAlreadyFailed
-      ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-      : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-  }
-  function completeUnitOfWork(workInProgress) {
+  function completeUnitOfWork(workInProgress$jscomp$0) {
     for (;;) {
-      var current = workInProgress.alternate,
-        returnFiber = workInProgress.return,
-        siblingFiber = workInProgress.sibling;
-      if (0 === (workInProgress.effectTag & 512)) {
+      var current = workInProgress$jscomp$0.alternate,
+        returnFiber = workInProgress$jscomp$0["return"],
+        siblingFiber = workInProgress$jscomp$0.sibling;
+      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
         current = completeWork(
           current,
-          workInProgress,
+          workInProgress$jscomp$0,
           nextRenderExpirationTime
         );
+        var workInProgress = workInProgress$jscomp$0;
         if (
           1073741823 === nextRenderExpirationTime ||
           1073741823 !== workInProgress.expirationTime
         ) {
-          var newExpirationTime = 0;
-          switch (workInProgress.tag) {
+          b: switch (workInProgress.tag) {
             case 3:
             case 2:
-              var updateQueue = workInProgress.updateQueue;
-              null !== updateQueue &&
-                (newExpirationTime = updateQueue.expirationTime);
+              var newExpirationTime = workInProgress.updateQueue;
+              newExpirationTime =
+                null === newExpirationTime
+                  ? 0
+                  : newExpirationTime.expirationTime;
+              break b;
+            default:
+              newExpirationTime = 0;
           }
-          for (updateQueue = workInProgress.child; null !== updateQueue; )
-            0 !== updateQueue.expirationTime &&
+          for (var child = workInProgress.child; null !== child; )
+            0 !== child.expirationTime &&
               (0 === newExpirationTime ||
-                newExpirationTime > updateQueue.expirationTime) &&
-              (newExpirationTime = updateQueue.expirationTime),
-              (updateQueue = updateQueue.sibling);
+                newExpirationTime > child.expirationTime) &&
+              (newExpirationTime = child.expirationTime),
+              (child = child.sibling);
           workInProgress.expirationTime = newExpirationTime;
         }
         if (null !== current) return current;
         null !== returnFiber &&
           0 === (returnFiber.effectTag & 512) &&
           (null === returnFiber.firstEffect &&
-            (returnFiber.firstEffect = workInProgress.firstEffect),
-          null !== workInProgress.lastEffect &&
+            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
+          null !== workInProgress$jscomp$0.lastEffect &&
             (null !== returnFiber.lastEffect &&
-              (returnFiber.lastEffect.nextEffect = workInProgress.firstEffect),
-            (returnFiber.lastEffect = workInProgress.lastEffect)),
-          1 < workInProgress.effectTag &&
+              (returnFiber.lastEffect.nextEffect =
+                workInProgress$jscomp$0.firstEffect),
+            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
+          1 < workInProgress$jscomp$0.effectTag &&
             (null !== returnFiber.lastEffect
-              ? (returnFiber.lastEffect.nextEffect = workInProgress)
-              : (returnFiber.firstEffect = workInProgress),
-            (returnFiber.lastEffect = workInProgress)));
+              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
+              : (returnFiber.firstEffect = workInProgress$jscomp$0),
+            (returnFiber.lastEffect = workInProgress$jscomp$0)));
         if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress = returnFiber;
+        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
         else {
           isRootReadyForCommit = !0;
           break;
         }
       } else {
-        workInProgress = unwindWork(workInProgress);
-        if (null !== workInProgress)
-          return (workInProgress.effectTag &= 511), workInProgress;
+        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
+        if (null !== workInProgress$jscomp$0)
+          return (
+            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
+          );
         null !== returnFiber &&
           ((returnFiber.firstEffect = returnFiber.lastEffect = null),
           (returnFiber.effectTag |= 512));
         if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress = returnFiber;
+        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
         else break;
       }
     }
@@ -5072,18 +5009,13 @@ function ReactFiberScheduler(config) {
           break;
         }
         isAsync = nextUnitOfWork;
-        var returnFiber = isAsync.return;
+        var returnFiber = isAsync["return"];
         if (null === returnFiber) {
           didFatal = !0;
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(
-          returnFiber,
-          isAsync,
-          thrownValue,
-          nextRenderExpirationTime
-        );
+        throwException(returnFiber, isAsync, thrownValue);
         nextUnitOfWork = completeUnitOfWork(isAsync);
       }
       break;
@@ -5100,61 +5032,55 @@ function ReactFiberScheduler(config) {
       "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
     );
   }
-  function onCommitPhaseError(fiber, error) {
-    var JSCompiler_inline_result;
+  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
+    sourceFiber = {
+      value: value,
+      source: sourceFiber,
+      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
+    };
+    insertUpdateIntoFiber(boundaryFiber, {
+      expirationTime: expirationTime,
+      partialState: null,
+      callback: null,
+      isReplace: !1,
+      isForced: !1,
+      capturedValue: sourceFiber,
+      next: null
+    });
+    scheduleWork(boundaryFiber, expirationTime);
+  }
+  function onCommitPhaseError(fiber$jscomp$0, error) {
     a: {
       invariant(
         !isWorking || isCommitting,
         "dispatch: Cannot dispatch during the render phase."
       );
-      for (
-        JSCompiler_inline_result = fiber.return;
-        null !== JSCompiler_inline_result;
-
-      ) {
-        switch (JSCompiler_inline_result.tag) {
+      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
+        switch (fiber.tag) {
           case 2:
-            var instance = JSCompiler_inline_result.stateNode;
+            var instance = fiber.stateNode;
             if (
-              "function" ===
-                typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
+              "function" === typeof fiber.type.getDerivedStateFromCatch ||
               ("function" === typeof instance.componentDidCatch &&
                 !isAlreadyFailedLegacyErrorBoundary(instance))
             ) {
-              fiber = createCapturedValue(error, fiber);
-              fiber = createClassErrorUpdate(
-                JSCompiler_inline_result,
-                fiber,
-                1
-              );
-              enqueueUpdate(JSCompiler_inline_result, fiber, 1);
-              scheduleWork(JSCompiler_inline_result, 1);
-              JSCompiler_inline_result = void 0;
+              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
+              fiber$jscomp$0 = void 0;
               break a;
             }
             break;
           case 3:
-            fiber = createCapturedValue(error, fiber);
-            fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
-            enqueueUpdate(JSCompiler_inline_result, fiber, 1);
-            scheduleWork(JSCompiler_inline_result, 1);
-            JSCompiler_inline_result = void 0;
+            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
+            fiber$jscomp$0 = void 0;
             break a;
         }
-        JSCompiler_inline_result = JSCompiler_inline_result.return;
+        fiber = fiber["return"];
       }
-      3 === fiber.tag &&
-        ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
-        (JSCompiler_inline_result = createRootErrorUpdate(
-          fiber,
-          JSCompiler_inline_result,
-          1
-        )),
-        enqueueUpdate(fiber, JSCompiler_inline_result, 1),
-        scheduleWork(fiber, 1));
-      JSCompiler_inline_result = void 0;
+      3 === fiber$jscomp$0.tag &&
+        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
+      fiber$jscomp$0 = void 0;
     }
-    return JSCompiler_inline_result;
+    return fiber$jscomp$0;
   }
   function computeExpirationForFiber(fiber) {
     fiber =
@@ -5182,7 +5108,7 @@ function ReactFiberScheduler(config) {
           (0 === fiber.alternate.expirationTime ||
             fiber.alternate.expirationTime > expirationTime) &&
           (fiber.alternate.expirationTime = expirationTime);
-        if (null === fiber.return)
+        if (null === fiber["return"])
           if (3 === fiber.tag) {
             var root = fiber.stateNode;
             !isWorking &&
@@ -5200,7 +5126,7 @@ function ReactFiberScheduler(config) {
             expirationTime = void 0;
             break a;
           }
-        fiber = fiber.return;
+        fiber = fiber["return"];
       }
       expirationTime = void 0;
     }
@@ -5440,7 +5366,7 @@ function ReactFiberScheduler(config) {
         error = void 0;
       try {
         for (; null !== nextEffect; )
-          nextEffect.effectTag & 256 &&
+          nextEffect.effectTag & 2048 &&
             commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
             (nextEffect = nextEffect.nextEffect);
       } catch (e) {
@@ -5516,6 +5442,8 @@ function ReactFiberScheduler(config) {
               didError,
               error
             );
+          effectTag$jscomp$0 & 256 &&
+            commitErrorLogging(nextEffect, onUncaughtError);
           effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
           var next = nextEffect.nextEffect;
           nextEffect.nextEffect = null;
@@ -5578,21 +5506,21 @@ function ReactFiberScheduler(config) {
     legacyContext,
     stack,
     scheduleWork,
-    markLegacyErrorBoundaryAsFailed,
-    isAlreadyFailedLegacyErrorBoundary,
-    onUncaughtError
+    isAlreadyFailedLegacyErrorBoundary
   );
   var throwException = hostContext.throwException,
     unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork,
-    createRootErrorUpdate = hostContext.createRootErrorUpdate,
-    createClassErrorUpdate = hostContext.createClassErrorUpdate;
+    unwindInterruptedWork = hostContext.unwindInterruptedWork;
   hostContext = ReactFiberCommitWork(
     config,
     onCommitPhaseError,
     scheduleWork,
     computeExpirationForFiber,
-    markLegacyErrorBoundaryAsFailed,
+    function(instance) {
+      null === legacyErrorBoundariesThatAlreadyFailed
+        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
+        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+    },
     recalculateCurrentTime
   );
   var commitBeforeMutationLifeCycles =
@@ -5602,6 +5530,7 @@ function ReactFiberScheduler(config) {
     commitDeletion = hostContext.commitDeletion,
     commitWork = hostContext.commitWork,
     commitLifeCycles = hostContext.commitLifeCycles,
+    commitErrorLogging = hostContext.commitErrorLogging,
     commitAttachRef = hostContext.commitAttachRef,
     commitDetachRef = hostContext.commitDetachRef,
     now = config.now,
@@ -5769,11 +5698,15 @@ function ReactFiberReconciler$1(config) {
       ? (container.context = parentComponent)
       : (container.pendingContext = parentComponent);
     container = callback;
-    callback = createUpdate(expirationTime);
-    callback.payload = { element: element };
-    container = void 0 === container ? null : container;
-    null !== container && (callback.callback = container);
-    enqueueUpdate(currentTime, callback, expirationTime);
+    insertUpdateIntoFiber(currentTime, {
+      expirationTime: expirationTime,
+      partialState: { element: element },
+      callback: void 0 === container ? null : container,
+      isReplace: !1,
+      isForced: !1,
+      capturedValue: null,
+      next: null
+    });
     scheduleWork(currentTime, expirationTime);
     return expirationTime;
   }
@@ -5894,8 +5827,8 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
   ReactFiberReconciler$3 =
     (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
     ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3.default
-    ? ReactFiberReconciler$3.default
+  reactReconciler = ReactFiberReconciler$3["default"]
+    ? ReactFiberReconciler$3["default"]
     : ReactFiberReconciler$3,
   ReactNativeFiberHostComponent = (function() {
     function ReactNativeFiberHostComponent(tag, viewConfig) {
@@ -6286,7 +6219,7 @@ var roots = new Map(),
       var root = roots.get(containerTag);
       root &&
         NativeRenderer.updateContainer(null, root, null, function() {
-          roots.delete(containerTag);
+          roots["delete"](containerTag);
         });
     },
     unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
@@ -6372,6 +6305,6 @@ NativeRenderer.injectIntoDevTools({
 var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
   ReactNativeRenderer$3 =
     (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
-module.exports = ReactNativeRenderer$3.default
-  ? ReactNativeRenderer$3.default
+module.exports = ReactNativeRenderer$3["default"]
+  ? ReactNativeRenderer$3["default"]
   : ReactNativeRenderer$3;
diff --git a/Libraries/Renderer/shims/NativeMethodsMixin.js b/Libraries/Renderer/shims/NativeMethodsMixin.js
index cd0e673b3bff..7acdf99bbd39 100644
--- a/Libraries/Renderer/shims/NativeMethodsMixin.js
+++ b/Libraries/Renderer/shims/NativeMethodsMixin.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule NativeMethodsMixin
  * @flow
  */
 
diff --git a/Libraries/Renderer/shims/ReactDebugTool.js b/Libraries/Renderer/shims/ReactDebugTool.js
index e45af4fb0994..8ea7ba5c1433 100644
--- a/Libraries/Renderer/shims/ReactDebugTool.js
+++ b/Libraries/Renderer/shims/ReactDebugTool.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactDebugTool
  */
 
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactFabric.js b/Libraries/Renderer/shims/ReactFabric.js
index 4162ca62fef7..8dce288d28a7 100644
--- a/Libraries/Renderer/shims/ReactFabric.js
+++ b/Libraries/Renderer/shims/ReactFabric.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactFabric
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactNative.js b/Libraries/Renderer/shims/ReactNative.js
index a648cafbc30c..43c5002e05f5 100644
--- a/Libraries/Renderer/shims/ReactNative.js
+++ b/Libraries/Renderer/shims/ReactNative.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNative
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactNativeComponentTree.js b/Libraries/Renderer/shims/ReactNativeComponentTree.js
index 30ec5257f424..8e8ce6ae06c1 100644
--- a/Libraries/Renderer/shims/ReactNativeComponentTree.js
+++ b/Libraries/Renderer/shims/ReactNativeComponentTree.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNativeComponentTree
  * @flow
  */
 
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index bf9411973933..485ce162ecc6 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ReactNativeTypes
  */
 
 export type MeasureOnSuccessCallback = (
diff --git a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
index ffb0fa213f3b..c8ed940a8609 100644
--- a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
+++ b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactNativeViewConfigRegistry
  * @flow
  */
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactPerf.js b/Libraries/Renderer/shims/ReactPerf.js
index bb6777fff0b9..e94c87501c7d 100644
--- a/Libraries/Renderer/shims/ReactPerf.js
+++ b/Libraries/Renderer/shims/ReactPerf.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule ReactPerf
  */
 
 'use strict';
diff --git a/Libraries/Renderer/shims/ReactTypes.js b/Libraries/Renderer/shims/ReactTypes.js
index 689ed18bf952..747a6c07b6f3 100644
--- a/Libraries/Renderer/shims/ReactTypes.js
+++ b/Libraries/Renderer/shims/ReactTypes.js
@@ -5,7 +5,6 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
- * @providesModule ReactTypes
  */
 
 export type ReactNode =
diff --git a/Libraries/Renderer/shims/createReactNativeComponentClass.js b/Libraries/Renderer/shims/createReactNativeComponentClass.js
index 1a050e8b3cf0..cacaedab88f2 100644
--- a/Libraries/Renderer/shims/createReactNativeComponentClass.js
+++ b/Libraries/Renderer/shims/createReactNativeComponentClass.js
@@ -4,7 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @providesModule createReactNativeComponentClass
  * @flow
  */
 

From a5a4facac38ca4099ec82db8593823add4e08134 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Fri, 11 May 2018 12:23:13 -0700
Subject: [PATCH 0509/1109] Fix ReactShadowNodeTest

Reviewed By: mdvacca

Differential Revision: D7944803

fbshipit-source-id: 6d3b10004d478ad75942af96603c899f44a2e711
---
 .../java/com/facebook/react/fabric/FabricReconcilerTest.java | 5 +----
 .../java/com/facebook/react/fabric/ReactShadowNodeTest.java  | 4 ++--
 2 files changed, 3 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
index 36dfa8267a7e..2cb680067c55 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
@@ -3,19 +3,16 @@
 
 import static org.fest.assertions.api.Assertions.assertThat;
 import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
 
 import com.facebook.react.bridge.CatalystInstance;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReactTestHelper;
-import com.facebook.react.fabric.FabricReconciler;
-import com.facebook.react.fabric.FabricUIManager;
 import com.facebook.react.uimanager.NativeViewHierarchyManager;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
+import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.UIViewOperationQueue;
 import com.facebook.react.uimanager.ViewAtIndex;
-import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
 import java.util.ArrayList;
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
index 1b14c9fc9c42..12f4ddb58fcc 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
@@ -2,12 +2,12 @@
 package com.facebook.react.fabric;
 
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import com.facebook.testing.robolectric.v3.WithTestDefaultsRunner;
 import org.junit.Test;
 import org.junit.runner.RunWith;
+import org.robolectric.RobolectricTestRunner;
 
 /** Tests {@link ReactShadowNode} */
-@RunWith(WithTestDefaultsRunner.class)
+@RunWith(RobolectricTestRunner.class)
 public class ReactShadowNodeTest {
 
   @Test(expected = AssertionError.class)

From 680fb50040bb065f8fc9549540451c338019fea3 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 11 May 2018 12:43:48 -0700
Subject: [PATCH 0510/1109] Add missing copyright headers

Reviewed By: hramos, yungsters

Differential Revision: D7962391

fbshipit-source-id: 958a24e1cb190fc7c4ee0ba058ba88f03cc1a13b
---
 Libraries/Sample/Sample.android.js                 | 5 +++++
 Libraries/Sample/Sample.ios.js                     | 7 +++++++
 Libraries/WebSocket/__mocks__/event-target-shim.js | 9 ++++++++-
 3 files changed, 20 insertions(+), 1 deletion(-)

diff --git a/Libraries/Sample/Sample.android.js b/Libraries/Sample/Sample.android.js
index d74ef832ae4a..2755a884bb31 100644
--- a/Libraries/Sample/Sample.android.js
+++ b/Libraries/Sample/Sample.android.js
@@ -1,4 +1,9 @@
 /**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
  * Stub of Sample for Android.
  *
  * @format
diff --git a/Libraries/Sample/Sample.ios.js b/Libraries/Sample/Sample.ios.js
index 061c4262236f..6c7443201667 100644
--- a/Libraries/Sample/Sample.ios.js
+++ b/Libraries/Sample/Sample.ios.js
@@ -1,4 +1,11 @@
 /**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * Stub of Sample for Android.
+ *
  * @format
  * @flow
  */
diff --git a/Libraries/WebSocket/__mocks__/event-target-shim.js b/Libraries/WebSocket/__mocks__/event-target-shim.js
index 348227a374d3..5b099ea724bd 100644
--- a/Libraries/WebSocket/__mocks__/event-target-shim.js
+++ b/Libraries/WebSocket/__mocks__/event-target-shim.js
@@ -1,4 +1,11 @@
-/** @format */
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @format
+ */
 
 // Jest fatals for the following statement (minimal repro case)
 //

From aba4ec0c0984caf3bec75a803080bd95722b35db Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 11 May 2018 12:43:49 -0700
Subject: [PATCH 0511/1109] Prettier RN local-cli

Reviewed By: yungsters

Differential Revision: D7962462

fbshipit-source-id: 0afe2092af8703895de91a6d1400315c3173aa6d
---
 local-cli/__mocks__/beeper.js                 |   7 +-
 local-cli/bundle/__mocks__/sign.js            |   3 +
 .../filterPlatformAssetScales-test.js         |  19 +-
 .../__tests__/getAssetDestPathAndroid-test.js |  20 +-
 .../__tests__/getAssetDestPathIOS-test.js     |   2 +
 local-cli/bundle/assetPathUtils.js            |  31 +-
 local-cli/bundle/buildBundle.js               |   7 +-
 local-cli/bundle/bundle.js                    |   3 +
 local-cli/bundle/bundleCommandLineArgs.js     |  76 +-
 local-cli/bundle/getAssetDestPathAndroid.js   |   8 +-
 local-cli/bundle/getAssetDestPathIOS.js       |   1 +
 local-cli/bundle/saveAssets.js                |  42 +-
 local-cli/bundle/types.flow.js                |   2 +
 local-cli/bundle/unbundle.js                  |   6 +-
 local-cli/cli.js                              |   3 +
 local-cli/cliEntry.js                         |  61 +-
 local-cli/commands.js                         |  16 +-
 local-cli/core/__fixtures__/android.js        |  22 +-
 local-cli/core/__fixtures__/commands.js       |  23 +-
 local-cli/core/__fixtures__/dependencies.js   |   2 +
 local-cli/core/__fixtures__/ios.js            |  14 +-
 local-cli/core/__fixtures__/projects.js       |   8 +-
 .../__tests__/ios/findPodfilePath.spec.js     |   1 +
 .../__tests__/ios/findPodspecName.spec.js     |  13 +-
 .../core/android/findAndroidAppFolder.js      |   3 +
 local-cli/core/android/findManifest.js        |   3 +
 .../core/android/findPackageClassName.js      |   5 +-
 local-cli/core/android/index.js               |  34 +-
 local-cli/core/android/readManifest.js        |   3 +
 local-cli/core/findAssets.js                  |  14 +-
 local-cli/core/findPlugins.js                 |  22 +-
 local-cli/core/index.js                       |  51 +-
 local-cli/core/ios/findPodfilePath.js         |   2 +
 local-cli/core/ios/findPodspecName.js         |  13 +-
 local-cli/core/ios/findProject.js             |   3 +
 local-cli/core/ios/index.js                   |   5 +-
 local-cli/core/makeCommand.js                 |   9 +-
 local-cli/core/wrapCommands.js                |   5 +-
 local-cli/dependencies/dependencies.js        |  69 +-
 local-cli/eject/eject.js                      |  41 +-
 .../copyProjectTemplateAndReplace.js          |  83 +-
 local-cli/generator/printRunInstructions.js   |  15 +-
 local-cli/generator/promptSync.js             |  61 +-
 local-cli/generator/templates.js              | 127 ++-
 local-cli/info/info.js                        |  15 +-
 local-cli/init/init.js                        |  36 +-
 local-cli/install/install.js                  |   3 +
 local-cli/install/uninstall.js                |   3 +
 local-cli/library/library.js                  |  52 +-
 .../link/__tests__/android/applyPatch.spec.js |  11 +-
 .../__tests__/android/isInstalled.spec.js     |   9 +-
 .../__tests__/android/makeBuildPatch.spec.js  |   7 +-
 .../__tests__/android/makeImportPatch.spec.js |   6 +-
 .../android/makePackagePatch.spec.js          |   6 +-
 .../android/makeSettingsPatch.spec.js         |  45 +-
 .../android/makeStringsPatch.spec.js          |   6 +-
 .../android/normalizeProjectName.spec.js      |  11 +-
 .../__tests__/getDependencyConfig.spec.js     |   3 +-
 .../__tests__/getProjectDependencies.spec.js  |   8 +-
 .../link/__tests__/groupFilesByType.spec.js   |  13 +-
 .../__tests__/ios/addFileToProject.spec.js    |   8 +-
 .../ios/addProjectToLibraries.spec.js         |   3 +-
 .../__tests__/ios/addSharedLibraries.spec.js  |   5 +-
 .../link/__tests__/ios/createGroup.spec.js    |  16 +-
 .../__tests__/ios/getBuildProperty.spec.js    |   3 +-
 local-cli/link/__tests__/ios/getGroup.spec.js |   3 +-
 .../__tests__/ios/getHeaderSearchPath.spec.js |  62 +-
 .../__tests__/ios/getHeadersInFolder.spec.js  |   1 +
 local-cli/link/__tests__/ios/getPlist.spec.js |   3 +-
 .../link/__tests__/ios/getPlistPath.spec.js   |   3 +-
 .../link/__tests__/ios/getProducts.spec.js    |   3 +-
 .../link/__tests__/ios/getTargets.spec.js     |   3 +-
 .../__tests__/ios/hasLibraryImported.spec.js  |   3 +-
 .../link/__tests__/ios/isInstalled.spec.js    |  11 +-
 .../ios/mapHeaderSearchPaths.spec.js          |   3 +-
 .../ios/removeProjectFromLibraries.js         |   5 +-
 .../ios/removeProjectFromProject.spec.js      |   8 +-
 .../__tests__/ios/removeSharedLibrary.spec.js |   5 +-
 .../link/__tests__/ios/writePlist.spec.js     |   7 +-
 local-cli/link/__tests__/link.spec.js         | 187 ++--
 .../__tests__/pods/findLineToAddPod.spec.js   |  21 +-
 .../pods/findMarkedLinesInPodfile.spec.js     |  14 +-
 .../__tests__/pods/findPodTargetLine.spec.js  |   1 +
 .../link/__tests__/pods/isInstalled.spec.js   |  17 +-
 .../__tests__/pods/removePodEntry.spec.js     |  16 +-
 .../link/__tests__/promiseWaterfall.spec.js   |   9 +-
 local-cli/link/android/copyAssets.js          |   7 +-
 local-cli/link/android/fs.js                  |  12 +-
 local-cli/link/android/index.js               |   4 +-
 local-cli/link/android/isInstalled.js         |   2 +
 local-cli/link/android/patches/applyParams.js |  15 +-
 local-cli/link/android/patches/applyPatch.js  |  10 +-
 .../link/android/patches/makeBuildPatch.js    |   6 +-
 .../link/android/patches/makeImportPatch.js   |   2 +
 .../link/android/patches/makePackagePatch.js  |   2 +
 .../link/android/patches/makeSettingsPatch.js |  14 +-
 .../link/android/patches/makeStringsPatch.js  |  19 +-
 .../android/patches/normalizeProjectName.js   |   1 +
 local-cli/link/android/patches/revokePatch.js |   8 +-
 .../link/android/registerNativeModule.js      |  10 +-
 local-cli/link/android/unlinkAssets.js        |  10 +-
 .../link/android/unregisterNativeModule.js    |  12 +-
 local-cli/link/commandStub.js                 |   4 +-
 local-cli/link/getDependencyConfig.js         |   2 +
 local-cli/link/getProjectDependencies.js      |   6 +-
 local-cli/link/groupFilesByType.js            |   2 +
 local-cli/link/ios/addFileToProject.js        |   2 +
 local-cli/link/ios/addProjectToLibraries.js   |   2 +
 local-cli/link/ios/addSharedLibraries.js      |   4 +-
 local-cli/link/ios/addToHeaderSearchPaths.js  |   2 +
 local-cli/link/ios/common/isInstalled.js      |   7 +-
 .../link/ios/common/registerNativeModule.js   |   7 +-
 .../link/ios/common/unregisterNativeModule.js |   7 +-
 local-cli/link/ios/copyAssets.js              |  18 +-
 local-cli/link/ios/createGroup.js             |  28 +-
 local-cli/link/ios/createGroupWithMessage.js  |   4 +-
 local-cli/link/ios/getBuildProperty.js        |  10 +-
 local-cli/link/ios/getGroup.js                |   7 +-
 local-cli/link/ios/getHeaderSearchPath.js     |  23 +-
 local-cli/link/ios/getHeadersInFolder.js      |   9 +-
 local-cli/link/ios/getPlist.js                |   6 +-
 local-cli/link/ios/getPlistPath.js            |   4 +-
 local-cli/link/ios/getProducts.js             |   5 +-
 local-cli/link/ios/getTargets.js              |  20 +-
 local-cli/link/ios/hasLibraryImported.js      |   9 +-
 local-cli/link/ios/index.js                   |   4 +-
 local-cli/link/ios/isInstalled.js             |   2 +
 local-cli/link/ios/mapHeaderSearchPaths.js    |  22 +-
 local-cli/link/ios/registerNativeModule.js    |  29 +-
 .../link/ios/removeFromHeaderSearchPaths.js   |   6 +-
 .../removeFromPbxItemContainerProxySection.js |   7 +-
 .../ios/removeFromPbxReferenceProxySection.js |   2 +
 .../link/ios/removeFromProjectReferences.js   |   8 +-
 .../link/ios/removeFromStaticLibraries.js     |   2 +
 local-cli/link/ios/removeProductGroup.js      |   2 +
 .../link/ios/removeProjectFromLibraries.js    |   6 +-
 .../link/ios/removeProjectFromProject.js      |   2 +
 local-cli/link/ios/removeSharedLibraries.js   |   4 +-
 local-cli/link/ios/unlinkAssets.js            |  17 +-
 local-cli/link/ios/unregisterNativeModule.js  |  25 +-
 local-cli/link/ios/writePlist.js              |   4 +-
 local-cli/link/link.js                        | 130 +--
 local-cli/link/pods/addPodEntry.js            |  15 +-
 local-cli/link/pods/findLineToAddPod.js       |   7 +-
 .../link/pods/findMarkedLinesInPodfile.js     |   4 +-
 local-cli/link/pods/findPodTargetLine.js      |   7 +-
 local-cli/link/pods/isInstalled.js            |   7 +-
 local-cli/link/pods/readPodfile.js            |   2 +
 local-cli/link/pods/registerNativeModule.js   |  10 +-
 local-cli/link/pods/removePodEntry.js         |   9 +-
 local-cli/link/pods/savePodFile.js            |   2 +
 local-cli/link/pods/unregisterNativeModule.js |   8 +-
 local-cli/link/pollParams.js                  |  15 +-
 local-cli/link/promiseWaterfall.js            |   4 +-
 local-cli/link/promisify.js                   |   9 +-
 local-cli/link/unlink.js                      | 117 ++-
 local-cli/logAndroid/logAndroid.js            |  16 +-
 local-cli/logIOS/logIOS.js                    |  32 +-
 local-cli/runAndroid/adb.js                   |   7 +-
 local-cli/runAndroid/runAndroid.js            | 384 +++++---
 .../__tests__/findMatchingSimulator-test.js   | 871 +++++++++---------
 .../runIOS/__tests__/findXcodeProject-test.js |  62 +-
 .../__tests__/parseIOSDevicesList-test.js     |  39 +-
 local-cli/runIOS/findMatchingSimulator.js     |   9 +-
 local-cli/runIOS/findXcodeProject.js          |   8 +-
 local-cli/runIOS/parseIOSDevicesList.js       |  14 +-
 local-cli/runIOS/runIOS.js                    | 364 +++++---
 local-cli/server/checkNodeVersion.js          |  29 +-
 .../middleware/copyToClipBoardMiddleware.js   |   3 +
 local-cli/server/middleware/indexPage.js      |   3 +
 .../middleware/loadRawBodyMiddleware.js       |   3 +
 .../openStackFrameInEditorMiddleware.js       |   3 +
 .../server/middleware/statusPageMiddleware.js |   3 +
 .../middleware/systraceProfileMiddleware.js   |   7 +-
 local-cli/server/middleware/unless.js         |   5 +-
 local-cli/server/server.js                    | 179 ++--
 local-cli/server/util/copyToClipBoard.js      |  33 +-
 .../server/util/debugger-ui/debuggerWorker.js |  15 +-
 local-cli/server/util/jsPackagerClient.js     |  93 +-
 local-cli/server/util/launchChrome.js         |  41 +-
 local-cli/server/util/launchEditor.js         |  48 +-
 local-cli/server/util/messageSocket.js        | 111 ++-
 local-cli/server/util/webSocketProxy.js       |  16 +-
 local-cli/templates/HelloNavigation/App.js    |   6 +-
 .../components/KeyboardSpacer.js              |  36 +-
 .../HelloNavigation/components/ListItem.js    |   6 +-
 .../templates/HelloNavigation/lib/Backend.js  |  16 +-
 .../views/HomeScreenTabNavigator.js           |   4 +-
 .../views/chat/ChatListScreen.js              |  15 +-
 .../HelloNavigation/views/chat/ChatScreen.js  |  49 +-
 .../views/welcome/WelcomeScreen.js            |  19 +-
 .../views/welcome/WelcomeText.android.js      |  22 +-
 .../views/welcome/WelcomeText.ios.js          |  23 +-
 local-cli/templates/HelloWorld/App.js         |  29 +-
 .../templates/HelloWorld/__tests__/App.js     |   6 +-
 local-cli/templates/HelloWorld/index.js       |   6 +-
 local-cli/upgrade/upgrade.js                  |  82 +-
 local-cli/util/PackageManager.js              |  10 +-
 local-cli/util/__mocks__/log.js               |   3 +
 local-cli/util/assertRequiredOptions.js       |   7 +-
 local-cli/util/copyAndReplace.js              |  26 +-
 local-cli/util/findReactNativeScripts.js      |   4 +-
 local-cli/util/findSymlinksPaths.js           |  15 +-
 local-cli/util/isPackagerRunning.js           |  17 +-
 local-cli/util/isValidPackageName.js          |   3 +
 local-cli/util/log.js                         |   3 +
 local-cli/util/parseCommandLine.js            |   3 +
 local-cli/util/walk.js                        |   3 +
 local-cli/util/yarn.js                        |  11 +-
 209 files changed, 3170 insertions(+), 2074 deletions(-)

diff --git a/local-cli/__mocks__/beeper.js b/local-cli/__mocks__/beeper.js
index 2bbac3717fbc..6628a2edc06a 100644
--- a/local-cli/__mocks__/beeper.js
+++ b/local-cli/__mocks__/beeper.js
@@ -3,10 +3,13 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
- 'use strict';
+
+'use strict';
 
 // beeper@1.1.0 has a return statement outside of a function
 // and therefore doesn't parse. Let's mock it so that we can
 // run the tests.
-module.exports = function () {};
+module.exports = function() {};
diff --git a/local-cli/bundle/__mocks__/sign.js b/local-cli/bundle/__mocks__/sign.js
index a7f2bdb6fc8a..f8f9174f9b61 100644
--- a/local-cli/bundle/__mocks__/sign.js
+++ b/local-cli/bundle/__mocks__/sign.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 function sign(source) {
diff --git a/local-cli/bundle/__tests__/filterPlatformAssetScales-test.js b/local-cli/bundle/__tests__/filterPlatformAssetScales-test.js
index d39058dc6ba0..3b6f3b355e06 100644
--- a/local-cli/bundle/__tests__/filterPlatformAssetScales-test.js
+++ b/local-cli/bundle/__tests__/filterPlatformAssetScales-test.js
@@ -4,19 +4,23 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
+
 'use strict';
 
-jest
-  .dontMock('../filterPlatformAssetScales')
-  .dontMock('../assetPathUtils');
+jest.dontMock('../filterPlatformAssetScales').dontMock('../assetPathUtils');
 
 const filterPlatformAssetScales = require('../filterPlatformAssetScales');
 
 describe('filterPlatformAssetScales', () => {
   it('removes everything but 2x and 3x for iOS', () => {
-    expect(filterPlatformAssetScales('ios', [1, 1.5, 2, 3, 4])).toEqual([1, 2, 3]);
+    expect(filterPlatformAssetScales('ios', [1, 1.5, 2, 3, 4])).toEqual([
+      1,
+      2,
+      3,
+    ]);
     expect(filterPlatformAssetScales('ios', [3, 4])).toEqual([3]);
   });
 
@@ -28,6 +32,11 @@ describe('filterPlatformAssetScales', () => {
   });
 
   it('keeps all scales for unknown platform', () => {
-    expect(filterPlatformAssetScales('freebsd', [1, 1.5, 2, 3.7])).toEqual([1, 1.5, 2, 3.7]);
+    expect(filterPlatformAssetScales('freebsd', [1, 1.5, 2, 3.7])).toEqual([
+      1,
+      1.5,
+      2,
+      3.7,
+    ]);
   });
 });
diff --git a/local-cli/bundle/__tests__/getAssetDestPathAndroid-test.js b/local-cli/bundle/__tests__/getAssetDestPathAndroid-test.js
index bd8e78d18d06..cca0ce2af61b 100644
--- a/local-cli/bundle/__tests__/getAssetDestPathAndroid-test.js
+++ b/local-cli/bundle/__tests__/getAssetDestPathAndroid-test.js
@@ -4,13 +4,13 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
+
 'use strict';
 
-jest
-  .dontMock('../getAssetDestPathAndroid')
-  .dontMock('../assetPathUtils');
+jest.dontMock('../getAssetDestPathAndroid').dontMock('../assetPathUtils');
 
 const getAssetDestPathAndroid = require('../getAssetDestPathAndroid');
 
@@ -24,7 +24,9 @@ describe('getAssetDestPathAndroid', () => {
 
     const expectDestPathForScaleToStartWith = (scale, path) => {
       if (!getAssetDestPathAndroid(asset, scale).startsWith(path)) {
-        throw new Error(`asset for scale ${scale} should start with path '${path}'`);
+        throw new Error(
+          `asset for scale ${scale} should start with path '${path}'`,
+        );
       }
     };
 
@@ -43,7 +45,7 @@ describe('getAssetDestPathAndroid', () => {
     };
 
     expect(getAssetDestPathAndroid(asset, 1)).toBe(
-      'drawable-mdpi/app_test_icon.png'
+      'drawable-mdpi/app_test_icon.png',
     );
   });
 
@@ -54,9 +56,7 @@ describe('getAssetDestPathAndroid', () => {
       httpServerLocation: '/assets/RKJSModules/Apps/AndroidSample/Assets',
     };
 
-    expect(
-      getAssetDestPathAndroid(asset, 1).startsWith('assets_')
-    ).toBeFalsy();
+    expect(getAssetDestPathAndroid(asset, 1).startsWith('assets_')).toBeFalsy();
   });
 
   it('should put non-drawable resources to `raw/`', () => {
@@ -66,8 +66,6 @@ describe('getAssetDestPathAndroid', () => {
       httpServerLocation: '/assets/app/test',
     };
 
-    expect(getAssetDestPathAndroid(asset, 1)).toBe(
-      'raw/app_test_video.mp4'
-    );
+    expect(getAssetDestPathAndroid(asset, 1)).toBe('raw/app_test_video.mp4');
   });
 });
diff --git a/local-cli/bundle/__tests__/getAssetDestPathIOS-test.js b/local-cli/bundle/__tests__/getAssetDestPathIOS-test.js
index 52e54530ba7f..620c01571c75 100644
--- a/local-cli/bundle/__tests__/getAssetDestPathIOS-test.js
+++ b/local-cli/bundle/__tests__/getAssetDestPathIOS-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
+
 'use strict';
 
 jest.dontMock('../getAssetDestPathIOS');
diff --git a/local-cli/bundle/assetPathUtils.js b/local-cli/bundle/assetPathUtils.js
index 891908eb480f..95d2f6c6939e 100644
--- a/local-cli/bundle/assetPathUtils.js
+++ b/local-cli/bundle/assetPathUtils.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -17,12 +18,18 @@ import type {PackagerAsset} from '../../Libraries/Image/AssetRegistry';
  */
 function getAndroidAssetSuffix(scale: number): string {
   switch (scale) {
-    case 0.75: return 'ldpi';
-    case 1: return 'mdpi';
-    case 1.5: return 'hdpi';
-    case 2: return 'xhdpi';
-    case 3: return 'xxhdpi';
-    case 4: return 'xxxhdpi';
+    case 0.75:
+      return 'ldpi';
+    case 1:
+      return 'mdpi';
+    case 1.5:
+      return 'hdpi';
+    case 2:
+      return 'xhdpi';
+    case 3:
+      return 'xxhdpi';
+    case 4:
+      return 'xxxhdpi';
   }
   throw new Error('no such scale');
 }
@@ -45,8 +52,8 @@ function getAndroidResourceFolderName(asset: PackagerAsset, scale: number) {
   var suffix = getAndroidAssetSuffix(scale);
   if (!suffix) {
     throw new Error(
-      'Don\'t know which android drawable suffix to use for asset: ' +
-      JSON.stringify(asset)
+      "Don't know which android drawable suffix to use for asset: " +
+        JSON.stringify(asset),
     );
   }
   const androidFolder = 'drawable-' + suffix;
@@ -57,9 +64,9 @@ function getAndroidResourceIdentifier(asset: PackagerAsset) {
   var folderPath = getBasePath(asset);
   return (folderPath + '/' + asset.name)
     .toLowerCase()
-    .replace(/\//g, '_')           // Encode folder structure in file name
-    .replace(/([^a-z0-9_])/g, '')  // Remove illegal chars
-    .replace(/^assets_/, '');      // Remove "assets_" prefix
+    .replace(/\//g, '_') // Encode folder structure in file name
+    .replace(/([^a-z0-9_])/g, '') // Remove illegal chars
+    .replace(/^assets_/, ''); // Remove "assets_" prefix
 }
 
 function getBasePath(asset: PackagerAsset) {
@@ -74,5 +81,5 @@ module.exports = {
   getAndroidAssetSuffix: getAndroidAssetSuffix,
   getAndroidResourceFolderName: getAndroidResourceFolderName,
   getAndroidResourceIdentifier: getAndroidResourceIdentifier,
-  getBasePath: getBasePath
+  getBasePath: getBasePath,
 };
diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index 66872a9c8162..b6ad5a551053 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -117,11 +118,7 @@ async function buildBundle(
   });
 
   // When we're done saving bundle output and the assets, we're done.
-  const assets = await saveAssets(
-    outputAssets,
-    args.platform,
-    args.assetsDest,
-  );
+  const assets = await saveAssets(outputAssets, args.platform, args.assetsDest);
 
   server.end();
 
diff --git a/local-cli/bundle/bundle.js b/local-cli/bundle/bundle.js
index 7bc7099b58fb..96d995db46cd 100644
--- a/local-cli/bundle/bundle.js
+++ b/local-cli/bundle/bundle.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const buildBundle = require('./buildBundle');
diff --git a/local-cli/bundle/bundleCommandLineArgs.js b/local-cli/bundle/bundleCommandLineArgs.js
index cc63e32505a2..4853f877ab7d 100644
--- a/local-cli/bundle/bundleCommandLineArgs.js
+++ b/local-cli/bundle/bundleCommandLineArgs.js
@@ -3,68 +3,94 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 module.exports = [
   {
     command: '--entry-file <path>',
-    description: 'Path to the root JS file, either absolute or relative to JS root',
-  }, {
+    description:
+      'Path to the root JS file, either absolute or relative to JS root',
+  },
+  {
     command: '--platform [string]',
     description: 'Either "ios" or "android"',
     default: 'ios',
-  }, {
+  },
+  {
     command: '--transformer [string]',
     description: 'Specify a custom transformer to be used',
-  }, {
+  },
+  {
     command: '--dev [boolean]',
     description: 'If false, warnings are disabled and the bundle is minified',
-    parse: (val) => val === 'false' ? false : true,
+    parse: val => (val === 'false' ? false : true),
     default: true,
-  }, {
+  },
+  {
     command: '--minify [boolean]',
-    description: 'Allows overriding whether bundle is minified. This defaults to ' +
+    description:
+      'Allows overriding whether bundle is minified. This defaults to ' +
       'false if dev is true, and true if dev is false. Disabling minification ' +
       'can be useful for speeding up production builds for testing purposes.',
-    parse: (val) => val === 'false' ? false : true,
-  }, {
+    parse: val => (val === 'false' ? false : true),
+  },
+  {
     command: '--bundle-output <string>',
-    description: 'File name where to store the resulting bundle, ex. /tmp/groups.bundle',
-  }, {
+    description:
+      'File name where to store the resulting bundle, ex. /tmp/groups.bundle',
+  },
+  {
     command: '--bundle-encoding [string]',
-    description: 'Encoding the bundle should be written in (https://nodejs.org/api/buffer.html#buffer_buffer).',
+    description:
+      'Encoding the bundle should be written in (https://nodejs.org/api/buffer.html#buffer_buffer).',
     default: 'utf8',
-  }, {
+  },
+  {
     command: '--max-workers [number]',
-    description: 'Specifies the maximum number of workers the worker-pool ' +
+    description:
+      'Specifies the maximum number of workers the worker-pool ' +
       'will spawn for transforming files. This defaults to the number of the ' +
       'cores available on your machine.',
     parse: (workers: string) => Number(workers),
-  }, {
+  },
+  {
     command: '--sourcemap-output [string]',
-    description: 'File name where to store the sourcemap file for resulting bundle, ex. /tmp/groups.map',
-  }, {
+    description:
+      'File name where to store the sourcemap file for resulting bundle, ex. /tmp/groups.map',
+  },
+  {
     command: '--sourcemap-sources-root [string]',
-    description: 'Path to make sourcemap\'s sources entries relative to, ex. /root/dir',
-  }, {
+    description:
+      "Path to make sourcemap's sources entries relative to, ex. /root/dir",
+  },
+  {
     command: '--sourcemap-use-absolute-path',
     description: 'Report SourceMapURL using its full path',
     default: false,
-  }, {
+  },
+  {
     command: '--assets-dest [string]',
-    description: 'Directory name where to store assets referenced in the bundle',
-  }, {
+    description:
+      'Directory name where to store assets referenced in the bundle',
+  },
+  {
     command: '--verbose',
     description: 'Enables logging',
     default: false,
-  }, {
+  },
+  {
     command: '--reset-cache',
     description: 'Removes cached files',
     default: false,
-  }, {
+  },
+  {
     command: '--read-global-cache',
-    description: 'Try to fetch transformed JS code from the global cache, if configured.',
+    description:
+      'Try to fetch transformed JS code from the global cache, if configured.',
     default: false,
   },
 ];
diff --git a/local-cli/bundle/getAssetDestPathAndroid.js b/local-cli/bundle/getAssetDestPathAndroid.js
index bdd3c49e32e4..f827e3ed9e52 100644
--- a/local-cli/bundle/getAssetDestPathAndroid.js
+++ b/local-cli/bundle/getAssetDestPathAndroid.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -15,8 +16,11 @@ const path = require('path');
 import type {PackagerAsset} from '../../Libraries/Image/AssetRegistry';
 
 function getAssetDestPathAndroid(asset: PackagerAsset, scale: number): string {
-  const androidFolder = assetPathUtils.getAndroidResourceFolderName(asset, scale);
-  const fileName =  assetPathUtils.getAndroidResourceIdentifier(asset);
+  const androidFolder = assetPathUtils.getAndroidResourceFolderName(
+    asset,
+    scale,
+  );
+  const fileName = assetPathUtils.getAndroidResourceIdentifier(asset);
   return path.join(androidFolder, fileName + '.' + asset.type);
 }
 
diff --git a/local-cli/bundle/getAssetDestPathIOS.js b/local-cli/bundle/getAssetDestPathIOS.js
index 61b935a1703a..cca4a87d773c 100644
--- a/local-cli/bundle/getAssetDestPathIOS.js
+++ b/local-cli/bundle/getAssetDestPathIOS.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/local-cli/bundle/saveAssets.js b/local-cli/bundle/saveAssets.js
index 94fe559a2b49..b069c332b48d 100644
--- a/local-cli/bundle/saveAssets.js
+++ b/local-cli/bundle/saveAssets.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const filterPlatformAssetScales = require('./filterPlatformAssetScales');
@@ -14,33 +17,29 @@ const log = require('../util/log').out('bundle');
 const mkdirp = require('mkdirp');
 const path = require('path');
 
-function saveAssets(
-  assets,
-  platform,
-  assetsDest
-) {
+function saveAssets(assets, platform, assetsDest) {
   if (!assetsDest) {
     console.warn('Assets destination folder is not set, skipping...');
     return Promise.resolve();
   }
 
-  const getAssetDestPath = platform === 'android'
-    ? getAssetDestPathAndroid
-    : getAssetDestPathIOS;
+  const getAssetDestPath =
+    platform === 'android' ? getAssetDestPathAndroid : getAssetDestPathIOS;
 
   const filesToCopy = Object.create(null); // Map src -> dest
-  assets
-    .forEach(asset => {
-      const validScales = new Set(filterPlatformAssetScales(platform, asset.scales));
-      asset.scales.forEach((scale, idx) => {
-        if (!validScales.has(scale)) {
-          return;
-        }
-        const src = asset.files[idx];
-        const dest = path.join(assetsDest, getAssetDestPath(asset, scale));
-        filesToCopy[src] = dest;
-      });
+  assets.forEach(asset => {
+    const validScales = new Set(
+      filterPlatformAssetScales(platform, asset.scales),
+    );
+    asset.scales.forEach((scale, idx) => {
+      if (!validScales.has(scale)) {
+        return;
+      }
+      const src = asset.files[idx];
+      const dest = path.join(assetsDest, getAssetDestPath(asset, scale));
+      filesToCopy[src] = dest;
     });
+  });
 
   return copyAll(filesToCopy);
 }
@@ -53,7 +52,7 @@ function copyAll(filesToCopy) {
 
   log('Copying ' + queue.length + ' asset files');
   return new Promise((resolve, reject) => {
-    const copyNext = (error) => {
+    const copyNext = error => {
       if (error) {
         return reject(error);
       }
@@ -76,7 +75,8 @@ function copy(src, dest, callback) {
     if (err) {
       return callback(err);
     }
-    fs.createReadStream(src)
+    fs
+      .createReadStream(src)
       .pipe(fs.createWriteStream(dest))
       .on('finish', callback);
   });
diff --git a/local-cli/bundle/types.flow.js b/local-cli/bundle/types.flow.js
index ecf86af407ee..3fb3d930ee1b 100644
--- a/local-cli/bundle/types.flow.js
+++ b/local-cli/bundle/types.flow.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /* $FlowFixMe(site=react_native_oss) */
diff --git a/local-cli/bundle/unbundle.js b/local-cli/bundle/unbundle.js
index bc7785fd0ee8..da4a4f70d6a8 100644
--- a/local-cli/bundle/unbundle.js
+++ b/local-cli/bundle/unbundle.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const bundleWithOutput = require('./bundle').withOutput;
@@ -23,7 +26,8 @@ module.exports = {
   func: unbundle,
   options: bundleCommandLineArgs.concat({
     command: '--indexed-unbundle',
-    description: 'Force indexed unbundle file format, even when building for android',
+    description:
+      'Force indexed unbundle file format, even when building for android',
     default: false,
   }),
 };
diff --git a/local-cli/cli.js b/local-cli/cli.js
index 3f31cbad4770..04f0950052b2 100644
--- a/local-cli/cli.js
+++ b/local-cli/cli.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 // gracefulify() has to be called before anything else runs
diff --git a/local-cli/cliEntry.js b/local-cli/cliEntry.js
index 018dd8459a5f..952ccd29bcf7 100644
--- a/local-cli/cliEntry.js
+++ b/local-cli/cliEntry.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const config = require('./core');
@@ -30,9 +32,9 @@ import type {RNConfig} from './core';
 
 commander.version(pkg.version);
 
-const defaultOptParser = (val) => val;
+const defaultOptParser = val => val;
 
-const handleError = (err) => {
+const handleError = err => {
   console.error();
   console.error(err.message || err);
   console.error();
@@ -48,15 +50,12 @@ function printHelpInformation() {
   }
 
   const sourceInformation = this.pkg
-    ? [
-      `  ${chalk.bold('Source:')} ${this.pkg.name}@${this.pkg.version}`,
-      '',
-    ]
+    ? [`  ${chalk.bold('Source:')} ${this.pkg.name}@${this.pkg.version}`, '']
     : [];
 
   let output = [
     '',
-    chalk.bold(chalk.cyan((`  react-native ${cmdName} ${this.usage()}`))),
+    chalk.bold(chalk.cyan(`  react-native ${cmdName} ${this.usage()}`)),
     `  ${this._description}`,
     '',
     ...sourceInformation,
@@ -67,9 +66,9 @@ function printHelpInformation() {
   ];
 
   if (this.examples && this.examples.length > 0) {
-    const formattedUsage = this.examples.map(
-      example => `    ${example.desc}: \n    ${chalk.cyan(example.cmd)}`,
-    ).join('\n\n');
+    const formattedUsage = this.examples
+      .map(example => `    ${example.desc}: \n    ${chalk.cyan(example.cmd)}`)
+      .join('\n\n');
 
     output = output.concat([
       chalk.bold('  Example usage:'),
@@ -78,21 +77,22 @@ function printHelpInformation() {
     ]);
   }
 
-  return output.concat([
-    '',
-    '',
-  ]).join('\n');
+  return output.concat(['', '']).join('\n');
 }
 
 function printUnknownCommand(cmdName) {
-  console.log([
-    '',
-    cmdName
-      ? chalk.red(`  Unrecognized command '${cmdName}'`)
-      : chalk.red('  You didn\'t pass any command'),
-    `  Run ${chalk.cyan('react-native --help')} to see list of all available commands`,
-    '',
-  ].join('\n'));
+  console.log(
+    [
+      '',
+      cmdName
+        ? chalk.red(`  Unrecognized command '${cmdName}'`)
+        : chalk.red("  You didn't pass any command"),
+      `  Run ${chalk.cyan(
+        'react-native --help',
+      )} to see list of all available commands`,
+      '',
+    ].join('\n'),
+  );
 }
 
 const addCommand = (command: CommandT, cfg: RNConfig) => {
@@ -115,17 +115,18 @@ const addCommand = (command: CommandT, cfg: RNConfig) => {
         .catch(handleError);
     });
 
-    cmd.helpInformation = printHelpInformation.bind(cmd);
-    cmd.examples = command.examples;
-    cmd.pkg = command.pkg;
+  cmd.helpInformation = printHelpInformation.bind(cmd);
+  cmd.examples = command.examples;
+  cmd.pkg = command.pkg;
 
-  options
-    .forEach(opt => cmd.option(
+  options.forEach(opt =>
+    cmd.option(
       opt.command,
       opt.description,
       opt.parse || defaultOptParser,
       typeof opt.default === 'function' ? opt.default(cfg) : opt.default,
-    ));
+    ),
+  );
 
   // Placeholder option for --config, which is parsed before any other option,
   // but needs to be here to avoid "unknown option" errors when specified
@@ -143,7 +144,9 @@ function run() {
 
   commander.parse(process.argv);
 
-  const isValidCommand = commands.find(cmd => cmd.name.split(' ')[0] === process.argv[2]);
+  const isValidCommand = commands.find(
+    cmd => cmd.name.split(' ')[0] === process.argv[2],
+  );
 
   if (!isValidCommand) {
     printUnknownCommand(process.argv[2]);
diff --git a/local-cli/commands.js b/local-cli/commands.js
index 1e1a20547384..f75207bd3bc5 100644
--- a/local-cli/commands.js
+++ b/local-cli/commands.js
@@ -4,13 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
-const { getProjectCommands } = require('./core');
+const {getProjectCommands} = require('./core');
 
-import type { RNConfig } from './core';
+import type {RNConfig} from './core';
 
 export type CommandT = {
   name: string,
@@ -58,10 +60,12 @@ const undocumentedCommands = [
   {
     name: 'init',
     func: () => {
-      console.log([
-        'Looks like React Native project already exists in the current',
-        'folder. Run this command from a different folder or remove node_modules/react-native',
-      ].join('\n'));
+      console.log(
+        [
+          'Looks like React Native project already exists in the current',
+          'folder. Run this command from a different folder or remove node_modules/react-native',
+        ].join('\n'),
+      );
     },
   },
 ];
diff --git a/local-cli/core/__fixtures__/android.js b/local-cli/core/__fixtures__/android.js
index 6e8c9c20d311..2d6447b87565 100644
--- a/local-cli/core/__fixtures__/android.js
+++ b/local-cli/core/__fixtures__/android.js
@@ -1,8 +1,14 @@
+/** @format */
+
 const fs = require.requireActual('fs');
 const path = require('path');
 
-const manifest = fs.readFileSync(path.join(__dirname, './files/AndroidManifest.xml'));
-const mainJavaClass = fs.readFileSync(path.join(__dirname, './files/Main.java'));
+const manifest = fs.readFileSync(
+  path.join(__dirname, './files/AndroidManifest.xml'),
+);
+const mainJavaClass = fs.readFileSync(
+  path.join(__dirname, './files/Main.java'),
+);
 
 function generateValidFileStructure(classFileName) {
   return {
@@ -13,7 +19,9 @@ function generateValidFileStructure(classFileName) {
           some: {
             example: {
               'Main.java': mainJavaClass,
-              [classFileName]: fs.readFileSync(path.join(__dirname, `./files/${classFileName}`)),
+              [classFileName]: fs.readFileSync(
+                path.join(__dirname, `./files/${classFileName}`),
+              ),
             },
           },
         },
@@ -34,13 +42,17 @@ exports.userConfigManifest = {
         some: {
           example: {
             'Main.java': mainJavaClass,
-            'ReactPackage.java': fs.readFileSync(path.join(__dirname, './files/ReactPackage.java')),
+            'ReactPackage.java': fs.readFileSync(
+              path.join(__dirname, './files/ReactPackage.java'),
+            ),
           },
         },
       },
     },
     debug: {
-      'AndroidManifest.xml': fs.readFileSync(path.join(__dirname, './files/AndroidManifest-debug.xml')),
+      'AndroidManifest.xml': fs.readFileSync(
+        path.join(__dirname, './files/AndroidManifest-debug.xml'),
+      ),
     },
   },
 };
diff --git a/local-cli/core/__fixtures__/commands.js b/local-cli/core/__fixtures__/commands.js
index cbe4193be29e..2f98b7ef505f 100644
--- a/local-cli/core/__fixtures__/commands.js
+++ b/local-cli/core/__fixtures__/commands.js
@@ -1,15 +1,20 @@
+/** @format */
+
 exports.single = {
   func: () => {},
   description: 'Test action',
   name: 'test',
 };
 
-exports.multiple = [{
-  func: () => {},
-  description: 'Test action #1',
-  name: 'test1',
-}, {
-  func: () => {},
-  description: 'Test action #2',
-  name: 'test2',
-}];
+exports.multiple = [
+  {
+    func: () => {},
+    description: 'Test action #1',
+    name: 'test1',
+  },
+  {
+    func: () => {},
+    description: 'Test action #2',
+    name: 'test2',
+  },
+];
diff --git a/local-cli/core/__fixtures__/dependencies.js b/local-cli/core/__fixtures__/dependencies.js
index 286064e8fe7d..decb08a161c2 100644
--- a/local-cli/core/__fixtures__/dependencies.js
+++ b/local-cli/core/__fixtures__/dependencies.js
@@ -1,3 +1,5 @@
+/** @format */
+
 const fs = require.requireActual('fs');
 const path = require('path');
 const android = require('./android');
diff --git a/local-cli/core/__fixtures__/ios.js b/local-cli/core/__fixtures__/ios.js
index 92256edcd618..99e84080fbac 100644
--- a/local-cli/core/__fixtures__/ios.js
+++ b/local-cli/core/__fixtures__/ios.js
@@ -1,19 +1,25 @@
+/** @format */
+
 const fs = require.requireActual('fs');
 const path = require('path');
 
 exports.valid = {
   'demoProject.xcodeproj': {
-    'project.pbxproj': fs.readFileSync(path.join(__dirname, './files/project.pbxproj')),
+    'project.pbxproj': fs.readFileSync(
+      path.join(__dirname, './files/project.pbxproj'),
+    ),
   },
-  'TestPod.podspec': 'empty'
+  'TestPod.podspec': 'empty',
 };
 
 exports.validTestName = {
   'MyTestProject.xcodeproj': {
-    'project.pbxproj': fs.readFileSync(path.join(__dirname, './files/project.pbxproj')),
+    'project.pbxproj': fs.readFileSync(
+      path.join(__dirname, './files/project.pbxproj'),
+    ),
   },
 };
 
 exports.pod = {
-  'TestPod.podspec': 'empty'
+  'TestPod.podspec': 'empty',
 };
diff --git a/local-cli/core/__fixtures__/projects.js b/local-cli/core/__fixtures__/projects.js
index a9a74e06e02e..28414b3d95a3 100644
--- a/local-cli/core/__fixtures__/projects.js
+++ b/local-cli/core/__fixtures__/projects.js
@@ -1,10 +1,12 @@
+/** @format */
+
 const android = require('./android');
 const ios = require('./ios');
 
 const flat = {
   android: android.valid,
   ios: ios.valid,
-  Podfile: 'empty'
+  Podfile: 'empty',
 };
 
 const nested = {
@@ -22,7 +24,7 @@ const withExamples = {
 
 const withPods = {
   Podfile: 'content',
-  ios: ios.pod
+  ios: ios.pod,
 };
 
-module.exports = { flat, nested, withExamples, withPods };
+module.exports = {flat, nested, withExamples, withPods};
diff --git a/local-cli/core/__tests__/ios/findPodfilePath.spec.js b/local-cli/core/__tests__/ios/findPodfilePath.spec.js
index a5e97030574e..1ada4b658ed6 100644
--- a/local-cli/core/__tests__/ios/findPodfilePath.spec.js
+++ b/local-cli/core/__tests__/ios/findPodfilePath.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
diff --git a/local-cli/core/__tests__/ios/findPodspecName.spec.js b/local-cli/core/__tests__/ios/findPodspecName.spec.js
index 91873779022a..7829ab6e34eb 100644
--- a/local-cli/core/__tests__/ios/findPodspecName.spec.js
+++ b/local-cli/core/__tests__/ios/findPodspecName.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -32,9 +33,9 @@ describe('ios::findPodspecName', () => {
       user: {
         PacketName: {
           'Another.podspec': 'empty',
-          'PacketName.podspec': 'empty'
-        }
-      }
+          'PacketName.podspec': 'empty',
+        },
+      },
     });
     expect(findPodspecName('/user/PacketName')).toBe('PacketName');
   });
@@ -44,9 +45,9 @@ describe('ios::findPodspecName', () => {
       user: {
         packet: {
           'Another.podspec': 'empty',
-          'PacketName.podspec': 'empty'
-        }
-      }
+          'PacketName.podspec': 'empty',
+        },
+      },
     });
     expect(findPodspecName('/user/packet')).toBe('Another');
   });
diff --git a/local-cli/core/android/findAndroidAppFolder.js b/local-cli/core/android/findAndroidAppFolder.js
index 6eac1dea16c2..4eb3416d9533 100644
--- a/local-cli/core/android/findAndroidAppFolder.js
+++ b/local-cli/core/android/findAndroidAppFolder.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fs = require('fs');
diff --git a/local-cli/core/android/findManifest.js b/local-cli/core/android/findManifest.js
index 481a8a474525..9bacbee4742d 100644
--- a/local-cli/core/android/findManifest.js
+++ b/local-cli/core/android/findManifest.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const glob = require('glob');
diff --git a/local-cli/core/android/findPackageClassName.js b/local-cli/core/android/findPackageClassName.js
index 45e2706a4d29..6fe1d3c359ff 100644
--- a/local-cli/core/android/findPackageClassName.js
+++ b/local-cli/core/android/findPackageClassName.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fs = require('fs');
@@ -17,7 +20,7 @@ const path = require('path');
  * @param {String} folder Folder to find java/kt files
  */
 module.exports = function getPackageClassName(folder) {
-  const files = glob.sync('**/+(*.java|*.kt)', { cwd: folder });
+  const files = glob.sync('**/+(*.java|*.kt)', {cwd: folder});
 
   const packages = files
     .map(filePath => fs.readFileSync(path.join(folder, filePath), 'utf8'))
diff --git a/local-cli/core/android/index.js b/local-cli/core/android/index.js
index c21ca60d8f7e..914341a12234 100644
--- a/local-cli/core/android/index.js
+++ b/local-cli/core/android/index.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const findAndroidAppFolder = require('./findAndroidAppFolder');
@@ -12,7 +15,7 @@ const findPackageClassName = require('./findPackageClassName');
 const path = require('path');
 const readManifest = require('./readManifest');
 
-const getPackageName = (manifest) => manifest.attr.package;
+const getPackageName = manifest => manifest.attr.package;
 
 /**
  * Gets android project config by analyzing given folder and taking some
@@ -43,33 +46,34 @@ exports.projectConfig = function projectConfigAndroid(folder, userConfig) {
     throw new Error(`Package name not found in ${manifestPath}`);
   }
 
-  const packageFolder = userConfig.packageFolder ||
-    packageName.replace(/\./g, path.sep);
+  const packageFolder =
+    userConfig.packageFolder || packageName.replace(/\./g, path.sep);
 
   const mainFilePath = path.join(
     sourceDir,
-    userConfig.mainFilePath || `src/main/java/${packageFolder}/MainApplication.java`
+    userConfig.mainFilePath ||
+      `src/main/java/${packageFolder}/MainApplication.java`,
   );
 
   const stringsPath = path.join(
     sourceDir,
-    userConfig.stringsPath || 'src/main/res/values/strings.xml'
+    userConfig.stringsPath || 'src/main/res/values/strings.xml',
   );
 
   const settingsGradlePath = path.join(
     folder,
     'android',
-    userConfig.settingsGradlePath || 'settings.gradle'
+    userConfig.settingsGradlePath || 'settings.gradle',
   );
 
   const assetsPath = path.join(
     sourceDir,
-    userConfig.assetsPath || 'src/main/assets'
+    userConfig.assetsPath || 'src/main/assets',
   );
 
   const buildGradlePath = path.join(
     sourceDir,
-    userConfig.buildGradlePath || 'build.gradle'
+    userConfig.buildGradlePath || 'build.gradle',
   );
 
   return {
@@ -89,7 +93,10 @@ exports.projectConfig = function projectConfigAndroid(folder, userConfig) {
  * Same as projectConfigAndroid except it returns
  * different config that applies to packages only
  */
-exports.dependencyConfig = function dependencyConfigAndroid(folder, userConfig) {
+exports.dependencyConfig = function dependencyConfigAndroid(
+  folder,
+  userConfig,
+) {
   const src = userConfig.sourceDir || findAndroidAppFolder(folder);
 
   if (!src) {
@@ -116,13 +123,14 @@ exports.dependencyConfig = function dependencyConfigAndroid(folder, userConfig)
     return null;
   }
 
-  const packageImportPath = userConfig.packageImportPath ||
+  const packageImportPath =
+    userConfig.packageImportPath ||
     `import ${packageName}.${packageClassName};`;
 
-  const packageInstance = userConfig.packageInstance ||
-    `new ${packageClassName}()`;
+  const packageInstance =
+    userConfig.packageInstance || `new ${packageClassName}()`;
 
-  return { sourceDir, folder, manifest, packageImportPath, packageInstance };
+  return {sourceDir, folder, manifest, packageImportPath, packageInstance};
 };
 
 exports.linkConfig = require('../../link/android');
diff --git a/local-cli/core/android/readManifest.js b/local-cli/core/android/readManifest.js
index 7215c67b18e5..7d61883ca21c 100644
--- a/local-cli/core/android/readManifest.js
+++ b/local-cli/core/android/readManifest.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fs = require('fs');
diff --git a/local-cli/core/findAssets.js b/local-cli/core/findAssets.js
index 1240f25e7ebc..db8b2360031f 100644
--- a/local-cli/core/findAssets.js
+++ b/local-cli/core/findAssets.js
@@ -3,14 +3,17 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const glob = require('glob');
 const path = require('path');
 
-const findAssetsInFolder = (folder) =>
-  glob.sync(path.join(folder, '**'), { nodir: true });
+const findAssetsInFolder = folder =>
+  glob.sync(path.join(folder, '**'), {nodir: true});
 
 /**
  * Given an array of assets folders, e.g. ['Fonts', 'Images'],
@@ -21,8 +24,9 @@ const findAssetsInFolder = (folder) =>
 module.exports = function findAssets(folder, assets) {
   return (assets || [])
     .map(assetsFolder => path.join(folder, assetsFolder))
-    .reduce((_assets, assetsFolder) =>
-      _assets.concat(findAssetsInFolder(assetsFolder)),
-      []
+    .reduce(
+      (_assets, assetsFolder) =>
+        _assets.concat(findAssetsInFolder(assetsFolder)),
+      [],
     );
 };
diff --git a/local-cli/core/findPlugins.js b/local-cli/core/findPlugins.js
index fbf3f064f703..595577ba8e87 100644
--- a/local-cli/core/findPlugins.js
+++ b/local-cli/core/findPlugins.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const path = require('path');
@@ -16,10 +19,11 @@ const flatten = require('lodash').flatten;
  * @param  {String} dependency Name of the dependency
  * @return {Boolean}           If dependency is a rnpm plugin
  */
-const isRNPMPlugin = (dependency) => dependency.indexOf('rnpm-plugin-') === 0;
-const isReactNativePlugin = (dependency) => dependency.indexOf('react-native-') === 0;
+const isRNPMPlugin = dependency => dependency.indexOf('rnpm-plugin-') === 0;
+const isReactNativePlugin = dependency =>
+  dependency.indexOf('react-native-') === 0;
 
-const readPackage = (folder) => {
+const readPackage = folder => {
   try {
     return require(path.join(folder, 'package.json'));
   } catch (e) {
@@ -27,7 +31,7 @@ const readPackage = (folder) => {
   }
 };
 
-const findPluginsInReactNativePackage = (pjson) => {
+const findPluginsInReactNativePackage = pjson => {
   if (!pjson.rnpm || !pjson.rnpm.plugin) {
     return [];
   }
@@ -35,7 +39,7 @@ const findPluginsInReactNativePackage = (pjson) => {
   return path.join(pjson.name, pjson.rnpm.plugin);
 };
 
-const findPlatformsInPackage = (pjson) => {
+const findPlatformsInPackage = pjson => {
   if (!pjson.rnpm || !pjson.rnpm.platform) {
     return [];
   }
@@ -43,7 +47,7 @@ const findPlatformsInPackage = (pjson) => {
   return path.join(pjson.name, pjson.rnpm.platform);
 };
 
-const findPluginInFolder = (folder) => {
+const findPluginInFolder = folder => {
   const pjson = readPackage(folder);
 
   if (!pjson) {
@@ -52,7 +56,7 @@ const findPluginInFolder = (folder) => {
 
   const deps = union(
     Object.keys(pjson.dependencies || {}),
-    Object.keys(pjson.devDependencies || {})
+    Object.keys(pjson.devDependencies || {}),
   );
 
   return deps.reduce(
@@ -71,7 +75,7 @@ const findPluginInFolder = (folder) => {
       }
       return {commands: commands, platforms: platforms};
     },
-    {commands: [], platforms: []}
+    {commands: [], platforms: []},
   );
 };
 
@@ -84,6 +88,6 @@ module.exports = function findPlugins(folders) {
   const plugins = folders.map(findPluginInFolder);
   return {
     commands: uniq(flatten(plugins.map(p => p.commands))),
-    platforms: uniq(flatten(plugins.map(p => p.platforms)))
+    platforms: uniq(flatten(plugins.map(p => p.platforms))),
   };
 };
diff --git a/local-cli/core/index.js b/local-cli/core/index.js
index 3bb0481421b8..d2b3399d177b 100644
--- a/local-cli/core/index.js
+++ b/local-cli/core/index.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const android = require('./android');
@@ -48,39 +50,37 @@ export type RNConfig = {
   getDependencyConfig(pkgName: string): Object,
 };
 
-const getRNPMConfig = (folder) =>
+const getRNPMConfig = folder =>
   // $FlowFixMe non-literal require
   require(path.join(folder, './package.json')).rnpm || {};
 
-const attachPackage = (command, pkg) => Array.isArray(command)
-  ? command.map(cmd => attachPackage(cmd, pkg))
-  : { ...command, pkg };
+const attachPackage = (command, pkg) =>
+  Array.isArray(command)
+    ? command.map(cmd => attachPackage(cmd, pkg))
+    : {...command, pkg};
 
 const appRoot = process.cwd();
 const plugins = findPlugins([appRoot]);
-const pluginPlatforms = plugins
-  .platforms
-  .reduce((acc, pathToPlatforms) => {
+const pluginPlatforms = plugins.platforms.reduce((acc, pathToPlatforms) => {
+  return Object.assign(
+    acc,
     // $FlowFixMe non-literal require
-    return Object.assign(acc, require(path.join(appRoot, 'node_modules', pathToPlatforms)));
-  },
-  {});
+    require(path.join(appRoot, 'node_modules', pathToPlatforms)),
+  );
+}, {});
 
 const defaultRNConfig = {
-
   hasteImplModulePath: require.resolve('../../jest/hasteImpl'),
 
   getProjectCommands(): Array<CommandT> {
-    const commands = plugins
-      .commands
-      .map(pathToCommands => {
-        const name = pathToCommands.split(path.sep)[0];
+    const commands = plugins.commands.map(pathToCommands => {
+      const name = pathToCommands.split(path.sep)[0];
 
-        return attachPackage(
-          require(path.join(appRoot, 'node_modules', pathToCommands)),
-          require(path.join(appRoot, 'node_modules', name, 'package.json'))
-        );
-      });
+      return attachPackage(
+        require(path.join(appRoot, 'node_modules', pathToCommands)),
+        require(path.join(appRoot, 'node_modules', name, 'package.json')),
+      );
+    });
 
     return flatten(commands);
   },
@@ -89,7 +89,7 @@ const defaultRNConfig = {
     return {
       ios,
       android,
-      ...pluginPlatforms
+      ...pluginPlatforms,
     };
   },
 
@@ -113,7 +113,7 @@ const defaultRNConfig = {
     const platforms = this.getPlatformConfig();
     const folder = path.join(process.cwd(), 'node_modules', packageName);
     const rnpm = getRNPMConfig(
-      path.join(process.cwd(), 'node_modules', packageName)
+      path.join(process.cwd(), 'node_modules', packageName),
     );
 
     let config = Object.assign({}, rnpm, {
@@ -135,9 +135,10 @@ const defaultRNConfig = {
  */
 function getCliConfig(): RNConfig {
   const cliArgs = minimist(process.argv.slice(2));
-  const config = cliArgs.config != null
-    ? Config.load(path.resolve(__dirname, cliArgs.config))
-    : Config.findOptional(__dirname);
+  const config =
+    cliArgs.config != null
+      ? Config.load(path.resolve(__dirname, cliArgs.config))
+      : Config.findOptional(__dirname);
 
   return {...defaultRNConfig, ...config};
 }
diff --git a/local-cli/core/ios/findPodfilePath.js b/local-cli/core/ios/findPodfilePath.js
index 6964a8d1ac79..91efb191d635 100644
--- a/local-cli/core/ios/findPodfilePath.js
+++ b/local-cli/core/ios/findPodfilePath.js
@@ -1,3 +1,5 @@
+/** @format */
+
 'use strict';
 
 const fs = require('fs');
diff --git a/local-cli/core/ios/findPodspecName.js b/local-cli/core/ios/findPodspecName.js
index 53a7ca5c3f11..8f43d4360538 100644
--- a/local-cli/core/ios/findPodspecName.js
+++ b/local-cli/core/ios/findPodspecName.js
@@ -1,25 +1,24 @@
+/** @format */
+
 'use strict';
 
 const glob = require('glob');
 const path = require('path');
 
 module.exports = function findPodspecName(folder) {
-  const podspecs = glob.sync('*.podspec', { cwd: folder });
+  const podspecs = glob.sync('*.podspec', {cwd: folder});
   let podspecFile = null;
   if (podspecs.length === 0) {
     return null;
-  }
-  else if (podspecs.length === 1) {
+  } else if (podspecs.length === 1) {
     podspecFile = podspecs[0];
-  }
-  else {
+  } else {
     const folderParts = folder.split(path.sep);
     const currentFolder = folderParts[folderParts.length - 1];
     const toSelect = podspecs.indexOf(currentFolder + '.podspec');
     if (toSelect === -1) {
       podspecFile = podspecs[0];
-    }
-    else {
+    } else {
       podspecFile = podspecs[toSelect];
     }
   }
diff --git a/local-cli/core/ios/findProject.js b/local-cli/core/ios/findProject.js
index 05b9e20b9b7a..3a6547015af2 100644
--- a/local-cli/core/ios/findProject.js
+++ b/local-cli/core/ios/findProject.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const glob = require('glob');
diff --git a/local-cli/core/ios/index.js b/local-cli/core/ios/index.js
index bb306f47846b..f99a270fbc7e 100644
--- a/local-cli/core/ios/index.js
+++ b/local-cli/core/ios/index.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const findProject = require('./findProject');
@@ -15,7 +18,7 @@ const path = require('path');
  * For libraries specified without an extension, add '.tbd' for those that
  * start with 'lib' and '.framework' to the rest.
  */
-const mapSharedLibaries = (libraries) => {
+const mapSharedLibaries = libraries => {
   return libraries.map(name => {
     if (path.extname(name)) {
       return name;
diff --git a/local-cli/core/makeCommand.js b/local-cli/core/makeCommand.js
index a386a0fba376..07fe346918ea 100644
--- a/local-cli/core/makeCommand.js
+++ b/local-cli/core/makeCommand.js
@@ -3,15 +3,20 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const spawn = require('child_process').spawn;
 
 module.exports = function makeCommand(command) {
-  return (cb) => {
+  return cb => {
     if (!cb) {
-      throw new Error(`You missed a callback function for the ${command} command`);
+      throw new Error(
+        `You missed a callback function for the ${command} command`,
+      );
     }
 
     const args = command.split(' ');
diff --git a/local-cli/core/wrapCommands.js b/local-cli/core/wrapCommands.js
index f47cec265406..b5876a69977b 100644
--- a/local-cli/core/wrapCommands.js
+++ b/local-cli/core/wrapCommands.js
@@ -3,14 +3,17 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const makeCommand = require('./makeCommand');
 
 module.exports = function wrapCommands(commands) {
   const mappedCommands = {};
-  Object.keys(commands || []).forEach((k) => {
+  Object.keys(commands || []).forEach(k => {
     mappedCommands[k] = makeCommand(commands[k]);
   });
   return mappedCommands;
diff --git a/local-cli/dependencies/dependencies.js b/local-cli/dependencies/dependencies.js
index b80f68249de6..543e15e21d9e 100644
--- a/local-cli/dependencies/dependencies.js
+++ b/local-cli/dependencies/dependencies.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const Metro = require('metro');
@@ -17,14 +20,16 @@ const {ASSET_REGISTRY_PATH} = require('../core/Constants');
 function dependencies(argv, config, args, packagerInstance) {
   const rootModuleAbsolutePath = args.entryFile;
   if (!fs.existsSync(rootModuleAbsolutePath)) {
-    return Promise.reject(new Error(`File ${rootModuleAbsolutePath} does not exist`));
+    return Promise.reject(
+      new Error(`File ${rootModuleAbsolutePath} does not exist`),
+    );
   }
 
-  const transformModulePath =
-      args.transformer ? path.resolve(args.transformer) :
-      typeof config.getTransformModulePath === 'function' ? config.getTransformModulePath() :
-      undefined;
-
+  const transformModulePath = args.transformer
+    ? path.resolve(args.transformer)
+    : typeof config.getTransformModulePath === 'function'
+      ? config.getTransformModulePath()
+      : undefined;
 
   const packageOpts = {
     assetRegistryPath: ASSET_REGISTRY_PATH,
@@ -43,10 +48,7 @@ function dependencies(argv, config, args, packagerInstance) {
   };
 
   const relativePath = packageOpts.projectRoots.map(root =>
-    path.relative(
-      root,
-      rootModuleAbsolutePath
-    )
+    path.relative(root, rootModuleAbsolutePath),
   )[0];
 
   const options = {
@@ -62,18 +64,19 @@ function dependencies(argv, config, args, packagerInstance) {
     ? fs.createWriteStream(args.output)
     : process.stdout;
 
-  return Promise.resolve((packagerInstance ?
-    packagerInstance.getOrderedDependencyPaths(options) :
-    Metro.getOrderedDependencyPaths(packageOpts, options)).then(
-    deps => {
+  return Promise.resolve(
+    (packagerInstance
+      ? packagerInstance.getOrderedDependencyPaths(options)
+      : Metro.getOrderedDependencyPaths(packageOpts, options)
+    ).then(deps => {
       deps.forEach(modulePath => {
         // Temporary hack to disable listing dependencies not under this directory.
         // Long term, we need either
         // (a) JS code to not depend on anything outside this directory, or
         // (b) Come up with a way to declare this dependency in Buck.
-        const isInsideProjectRoots = packageOpts.projectRoots.filter(
-          root => modulePath.startsWith(root)
-        ).length > 0;
+        const isInsideProjectRoots =
+          packageOpts.projectRoots.filter(root => modulePath.startsWith(root))
+            .length > 0;
 
         if (isInsideProjectRoots) {
           outStream.write(modulePath + '\n');
@@ -82,8 +85,8 @@ function dependencies(argv, config, args, packagerInstance) {
       return writeToFile
         ? denodeify(outStream.end).bind(outStream)()
         : Promise.resolve();
-    }
-  ));
+    }),
+  );
 }
 
 module.exports = {
@@ -94,27 +97,35 @@ module.exports = {
     {
       command: '--entry-file <path>',
       description: 'Absolute path to the root JS file',
-    }, {
+    },
+    {
       command: '--output [path]',
-      description: 'File name where to store the output, ex. /tmp/dependencies.txt',
-    }, {
+      description:
+        'File name where to store the output, ex. /tmp/dependencies.txt',
+    },
+    {
       command: '--platform [extension]',
       description: 'The platform extension used for selecting modules',
-    }, {
+    },
+    {
       command: '--transformer [path]',
-      description: 'Specify a custom transformer to be used'
-    }, {
+      description: 'Specify a custom transformer to be used',
+    },
+    {
       command: '--max-workers [number]',
-      description: 'Specifies the maximum number of workers the worker-pool ' +
+      description:
+        'Specifies the maximum number of workers the worker-pool ' +
         'will spawn for transforming files. This defaults to the number of the ' +
         'cores available on your machine.',
       parse: (workers: string) => Number(workers),
-    }, {
+    },
+    {
       command: '--dev [boolean]',
       description: 'If false, skip all dev-only code path',
-      parse: (val) => val === 'false' ? false : true,
+      parse: val => (val === 'false' ? false : true),
       default: true,
-    }, {
+    },
+    {
       command: '--verbose',
       description: 'Enables logging',
       default: false,
diff --git a/local-cli/eject/eject.js b/local-cli/eject/eject.js
index 569299018d3a..6c18a91fb9b2 100644
--- a/local-cli/eject/eject.js
+++ b/local-cli/eject/eject.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const copyProjectTemplateAndReplace = require('../generator/copyProjectTemplateAndReplace');
@@ -22,13 +25,12 @@ const fs = require('fs');
  */
 
 function eject() {
-
   const doesIOSExist = fs.existsSync(path.resolve('ios'));
   const doesAndroidExist = fs.existsSync(path.resolve('android'));
   if (doesIOSExist && doesAndroidExist) {
     console.error(
       'Both the iOS and Android folders already exist! Please delete `ios` and/or `android` ' +
-      'before ejecting.'
+        'before ejecting.',
     );
     process.exit(1);
   }
@@ -39,8 +41,10 @@ function eject() {
   } catch (e) {
     console.error(
       'Eject requires an `app.json` config file to be located at ' +
-      `${path.resolve('app.json')}, and it must at least specify a \`name\` for the project ` +
-      'name, and a `displayName` for the app\'s home screen label.'
+        `${path.resolve(
+          'app.json',
+        )}, and it must at least specify a \`name\` for the project ` +
+        "name, and a `displayName` for the app's home screen label.",
     );
     process.exit(1);
   }
@@ -49,7 +53,7 @@ function eject() {
   if (!appName) {
     console.error(
       'App `name` must be defined in the `app.json` config file to define the project name. ' +
-      'It must not contain any spaces or dashes.'
+        'It must not contain any spaces or dashes.',
     );
     process.exit(1);
   }
@@ -57,33 +61,46 @@ function eject() {
   if (!displayName) {
     console.error(
       'App `displayName` must be defined in the `app.json` config file, to define the label ' +
-      'of the app on the home screen.'
+        'of the app on the home screen.',
     );
     process.exit(1);
   }
 
-  const templateOptions = { displayName };
+  const templateOptions = {displayName};
 
   if (!doesIOSExist) {
     console.log('Generating the iOS folder.');
     copyProjectTemplateAndReplace(
-      path.resolve('node_modules', 'react-native', 'local-cli', 'templates', 'HelloWorld', 'ios'),
+      path.resolve(
+        'node_modules',
+        'react-native',
+        'local-cli',
+        'templates',
+        'HelloWorld',
+        'ios',
+      ),
       path.resolve('ios'),
       appName,
-      templateOptions
+      templateOptions,
     );
   }
 
   if (!doesAndroidExist) {
     console.log('Generating the Android folder.');
     copyProjectTemplateAndReplace(
-      path.resolve('node_modules', 'react-native', 'local-cli', 'templates', 'HelloWorld', 'android'),
+      path.resolve(
+        'node_modules',
+        'react-native',
+        'local-cli',
+        'templates',
+        'HelloWorld',
+        'android',
+      ),
       path.resolve('android'),
       appName,
-      templateOptions
+      templateOptions,
     );
   }
-
 }
 
 module.exports = {
diff --git a/local-cli/generator/copyProjectTemplateAndReplace.js b/local-cli/generator/copyProjectTemplateAndReplace.js
index 5840e587e7ef..607b3b8ed265 100644
--- a/local-cli/generator/copyProjectTemplateAndReplace.js
+++ b/local-cli/generator/copyProjectTemplateAndReplace.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const chalk = require('chalk');
@@ -26,24 +29,42 @@ const walk = require('../util/walk');
  *          ignorePaths: ['template/file/to/ignore.md'],
  *        }
  */
-function copyProjectTemplateAndReplace(srcPath, destPath, newProjectName, options) {
-  if (!srcPath) { throw new Error('Need a path to copy from'); }
-  if (!destPath) { throw new Error('Need a path to copy to'); }
-  if (!newProjectName) { throw new Error('Need a project name'); }
+function copyProjectTemplateAndReplace(
+  srcPath,
+  destPath,
+  newProjectName,
+  options,
+) {
+  if (!srcPath) {
+    throw new Error('Need a path to copy from');
+  }
+  if (!destPath) {
+    throw new Error('Need a path to copy to');
+  }
+  if (!newProjectName) {
+    throw new Error('Need a project name');
+  }
 
   options = options || {};
 
   walk(srcPath).forEach(absoluteSrcFilePath => {
-
     // 'react-native upgrade'
     if (options.upgrade) {
       // Don't upgrade these files
       const fileName = path.basename(absoluteSrcFilePath);
       // This also includes __tests__/index.*.js
-      if (fileName === 'index.ios.js') { return; }
-      if (fileName === 'index.android.js') { return; }
-      if (fileName === 'index.js') { return; }
-      if (fileName === 'App.js') { return; }
+      if (fileName === 'index.ios.js') {
+        return;
+      }
+      if (fileName === 'index.android.js') {
+        return;
+      }
+      if (fileName === 'index.js') {
+        return;
+      }
+      if (fileName === 'App.js') {
+        return;
+      }
     }
 
     const relativeFilePath = path.relative(srcPath, absoluteSrcFilePath);
@@ -59,14 +80,16 @@ function copyProjectTemplateAndReplace(srcPath, destPath, newProjectName, option
       if (!Array.isArray(options.ignorePaths)) {
         throw new Error('options.ignorePaths must be an array');
       }
-      if (options.ignorePaths.some(ignorePath => ignorePath === relativeFilePath)) {
+      if (
+        options.ignorePaths.some(ignorePath => ignorePath === relativeFilePath)
+      ) {
         // Skip copying this file
         return;
       }
     }
 
     let contentChangedCallback = null;
-    if (options.upgrade && (!options.force)) {
+    if (options.upgrade && !options.force) {
       contentChangedCallback = (_, contentChanged) => {
         return upgradeFileContentChangedCallback(
           absoluteSrcFilePath,
@@ -80,8 +103,8 @@ function copyProjectTemplateAndReplace(srcPath, destPath, newProjectName, option
       path.resolve(destPath, relativeRenamedPath),
       {
         'Hello App Display Name': options.displayName || newProjectName,
-        'HelloWorld': newProjectName,
-        'helloworld': newProjectName.toLowerCase(),
+        HelloWorld: newProjectName,
+        helloworld: newProjectName.toLowerCase(),
       },
       contentChangedCallback,
     );
@@ -97,7 +120,9 @@ function copyProjectTemplateAndReplace(srcPath, destPath, newProjectName, option
  * behavior of automatically renaming .gitignore to .npmignore.
  */
 function dotFilePath(path) {
-  if (!path) {return path;}
+  if (!path) {
+    return path;
+  }
   return path
     .replace('_gitignore', '.gitignore')
     .replace('_gitattributes', '.gitattributes')
@@ -110,20 +135,28 @@ function dotFilePath(path) {
 function upgradeFileContentChangedCallback(
   absoluteSrcFilePath,
   relativeDestPath,
-  contentChanged
+  contentChanged,
 ) {
   if (contentChanged === 'new') {
     console.log(chalk.bold('new') + ' ' + relativeDestPath);
     return 'overwrite';
   } else if (contentChanged === 'changed') {
-    console.log(chalk.bold(relativeDestPath) + ' ' +
-      'has changed in the new version.\nDo you want to keep your ' +
-      relativeDestPath + ' or replace it with the ' +
-      'latest version?\nIf you ever made any changes ' +
-      'to this file, you\'ll probably want to keep it.\n' +
-      'You can see the new version here: ' + absoluteSrcFilePath + '\n' +
-      'Do you want to replace ' + relativeDestPath + '? ' +
-      'Answer y to replace, n to keep your version: ');
+    console.log(
+      chalk.bold(relativeDestPath) +
+        ' ' +
+        'has changed in the new version.\nDo you want to keep your ' +
+        relativeDestPath +
+        ' or replace it with the ' +
+        'latest version?\nIf you ever made any changes ' +
+        "to this file, you'll probably want to keep it.\n" +
+        'You can see the new version here: ' +
+        absoluteSrcFilePath +
+        '\n' +
+        'Do you want to replace ' +
+        relativeDestPath +
+        '? ' +
+        'Answer y to replace, n to keep your version: ',
+    );
     const answer = prompt();
     if (answer === 'y') {
       console.log('Replacing ' + relativeDestPath);
@@ -135,7 +168,9 @@ function upgradeFileContentChangedCallback(
   } else if (contentChanged === 'identical') {
     return 'keep';
   } else {
-    throw new Error(`Unknown file changed state: ${relativeDestPath}, ${contentChanged}`);
+    throw new Error(
+      `Unknown file changed state: ${relativeDestPath}, ${contentChanged}`,
+    );
   }
 }
 
diff --git a/local-cli/generator/printRunInstructions.js b/local-cli/generator/printRunInstructions.js
index cc39a61fd3e6..eaa8e5cd8b0b 100644
--- a/local-cli/generator/printRunInstructions.js
+++ b/local-cli/generator/printRunInstructions.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 var chalk = require('chalk');
@@ -12,8 +15,12 @@ var path = require('path');
 function printRunInstructions(projectDir, projectName) {
   const absoluteProjectDir = path.resolve(projectDir);
   // iOS
-  const xcodeProjectPath = path.resolve(projectDir, 'ios', projectName) + '.xcodeproj';
-  const relativeXcodeProjectPath = path.relative(process.cwd(), xcodeProjectPath);
+  const xcodeProjectPath =
+    path.resolve(projectDir, 'ios', projectName) + '.xcodeproj';
+  const relativeXcodeProjectPath = path.relative(
+    process.cwd(),
+    xcodeProjectPath,
+  );
   console.log(chalk.white.bold('To run your app on iOS:'));
   console.log('   cd ' + absoluteProjectDir);
   console.log('   react-native run-ios');
@@ -23,7 +30,9 @@ function printRunInstructions(projectDir, projectName) {
   // Android
   console.log(chalk.white.bold('To run your app on Android:'));
   console.log('   cd ' + absoluteProjectDir);
-  console.log('   Have an Android emulator running (quickest way to get started), or a device connected');
+  console.log(
+    '   Have an Android emulator running (quickest way to get started), or a device connected',
+  );
   console.log('   react-native run-android');
 }
 
diff --git a/local-cli/generator/promptSync.js b/local-cli/generator/promptSync.js
index 841af5054b87..636138abf257 100644
--- a/local-cli/generator/promptSync.js
+++ b/local-cli/generator/promptSync.js
@@ -1,3 +1,5 @@
+/** @format */
+
 // Simplified version of:
 // https://github.com/0x00A/prompt-sync/blob/master/index.js
 
@@ -7,11 +9,14 @@ var fs = require('fs');
 var term = 13; // carriage return
 
 function create() {
-
   return prompt;
 
   function prompt(ask, value, opts) {
-    var insert = 0, savedinsert = 0, res, i, savedstr;
+    var insert = 0,
+      savedinsert = 0,
+      res,
+      i,
+      savedstr;
     opts = opts || {};
 
     if (Object(ask) === ask) {
@@ -25,15 +30,20 @@ function create() {
     var echo = opts.echo;
     var masked = 'echo' in opts;
 
-    var fd = (process.platform === 'win32') ?
-      process.stdin.fd :
-      fs.openSync('/dev/tty', 'rs');
+    var fd =
+      process.platform === 'win32'
+        ? process.stdin.fd
+        : fs.openSync('/dev/tty', 'rs');
 
     var wasRaw = process.stdin.isRaw;
-    if (!wasRaw) { process.stdin.setRawMode(true); }
+    if (!wasRaw) {
+      process.stdin.setRawMode(true);
+    }
 
     var buf = new Buffer(3);
-    var str = '', character, read;
+    var str = '',
+      character,
+      read;
 
     savedstr = '';
 
@@ -46,7 +56,8 @@ function create() {
 
     while (true) {
       read = fs.readSync(fd, buf, 0, 3);
-      if (read > 1) { // received a control sequence
+      if (read > 1) {
+        // received a control sequence
         if (buf.toString()) {
           str = str + buf.toString();
           str = str.replace(/\0/g, '');
@@ -62,7 +73,7 @@ function create() {
       character = buf[read - 1];
 
       // catch a ^C and return null
-      if (character == 3){
+      if (character == 3) {
         process.stdout.write('^C\n');
         fs.closeSync(fd);
         process.exit(130);
@@ -76,35 +87,49 @@ function create() {
         break;
       }
 
-      if (character == 127 || (process.platform == 'win32' && character == 8)) { //backspace
-        if (!insert) {continue;}
+      if (character == 127 || (process.platform == 'win32' && character == 8)) {
+        //backspace
+        if (!insert) {
+          continue;
+        }
         str = str.slice(0, insert - 1) + str.slice(insert);
         insert--;
         process.stdout.write('\u001b[2D');
       } else {
-        if ((character < 32 ) || (character > 126))
-            {continue;}
-        str = str.slice(0, insert) + String.fromCharCode(character) + str.slice(insert);
+        if (character < 32 || character > 126) {
+          continue;
+        }
+        str =
+          str.slice(0, insert) +
+          String.fromCharCode(character) +
+          str.slice(insert);
         insert++;
       }
 
       if (masked) {
-          process.stdout.write('\u001b[2K\u001b[0G' + ask + Array(str.length + 1).join(echo));
+        process.stdout.write(
+          '\u001b[2K\u001b[0G' + ask + Array(str.length + 1).join(echo),
+        );
       } else {
         process.stdout.write('\u001b[s');
         if (insert == str.length) {
-            process.stdout.write('\u001b[2K\u001b[0G' + ask + str);
+          process.stdout.write('\u001b[2K\u001b[0G' + ask + str);
         } else {
           if (ask) {
             process.stdout.write('\u001b[2K\u001b[0G' + ask + str);
           } else {
-            process.stdout.write('\u001b[2K\u001b[0G' + str + '\u001b[' + (str.length - insert) + 'D');
+            process.stdout.write(
+              '\u001b[2K\u001b[0G' +
+                str +
+                '\u001b[' +
+                (str.length - insert) +
+                'D',
+            );
           }
         }
         process.stdout.write('\u001b[u');
         process.stdout.write('\u001b[1C');
       }
-
     }
 
     process.stdout.write('\n');
diff --git a/local-cli/generator/templates.js b/local-cli/generator/templates.js
index 99e63ec2e99c..17e4379a72b3 100644
--- a/local-cli/generator/templates.js
+++ b/local-cli/generator/templates.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const copyProjectTemplateAndReplace = require('./copyProjectTemplateAndReplace');
@@ -29,15 +32,18 @@ function listTemplatesAndExit(newProjectName, options) {
       // above is defined correctly :)
       console.log(
         'There are no templates available besides ' +
-        'the default "Hello World" one.'
+          'the default "Hello World" one.',
       );
     } else {
       console.log(
         'The available templates are:\n' +
-        templateKeys.join('\n') +
-        '\nYou can use these to create an app based on a template, for example: ' +
-        'you could run: ' +
-        'react-native init ' + newProjectName + ' --template ' + templateKeys[0]
+          templateKeys.join('\n') +
+          '\nYou can use these to create an app based on a template, for example: ' +
+          'you could run: ' +
+          'react-native init ' +
+          newProjectName +
+          ' --template ' +
+          templateKeys[0],
       );
     }
     // Exit 'react-native init'
@@ -54,12 +60,23 @@ function listTemplatesAndExit(newProjectName, options) {
  * @param yarnVersion Version of yarn available on the system, or null if
  *                    yarn is not available. For example '0.18.1'.
  */
-function createProjectFromTemplate(destPath, newProjectName, template, yarnVersion) {
+function createProjectFromTemplate(
+  destPath,
+  newProjectName,
+  template,
+  yarnVersion,
+) {
   // Expand the basic 'HelloWorld' template
   copyProjectTemplateAndReplace(
-    path.resolve('node_modules', 'react-native', 'local-cli', 'templates', 'HelloWorld'),
+    path.resolve(
+      'node_modules',
+      'react-native',
+      'local-cli',
+      'templates',
+      'HelloWorld',
+    ),
     destPath,
-    newProjectName
+    newProjectName,
   );
 
   if (template === undefined) {
@@ -79,7 +96,12 @@ function createProjectFromTemplate(destPath, newProjectName, template, yarnVersi
   if (builtInTemplateName) {
     // template is e.g. 'navigation',
     // use the built-in local-cli/templates/HelloNavigation folder
-    createFromBuiltInTemplate(builtInTemplateName, destPath, newProjectName, yarnVersion);
+    createFromBuiltInTemplate(
+      builtInTemplateName,
+      destPath,
+      newProjectName,
+      yarnVersion,
+    );
   } else {
     // template is e.g. 'ignite',
     // use the template react-native-template-ignite from npm
@@ -89,15 +111,20 @@ function createProjectFromTemplate(destPath, newProjectName, template, yarnVersi
 
 // (We might want to get rid of built-in templates in the future -
 // publish them to npm and install from there.)
-function createFromBuiltInTemplate(templateName, destPath, newProjectName, yarnVersion) {
+function createFromBuiltInTemplate(
+  templateName,
+  destPath,
+  newProjectName,
+  yarnVersion,
+) {
   const templatePath = path.resolve(
-    'node_modules', 'react-native', 'local-cli', 'templates', templateName
-  );
-  copyProjectTemplateAndReplace(
-    templatePath,
-    destPath,
-    newProjectName,
+    'node_modules',
+    'react-native',
+    'local-cli',
+    'templates',
+    templateName,
   );
+  copyProjectTemplateAndReplace(templatePath, destPath, newProjectName);
   installTemplateDependencies(templatePath, yarnVersion);
   installTemplateDevDependencies(templatePath, yarnVersion);
 }
@@ -107,13 +134,18 @@ function createFromBuiltInTemplate(templateName, destPath, newProjectName, yarnV
  * - 'demo' -> Fetch the package react-native-template-demo from npm
  * - git://..., http://..., file://... or any other URL supported by npm
  */
-function createFromRemoteTemplate(template, destPath, newProjectName, yarnVersion) {
+function createFromRemoteTemplate(
+  template,
+  destPath,
+  newProjectName,
+  yarnVersion,
+) {
   let installPackage;
   let templateName;
   if (template.includes('://')) {
-     // URL, e.g. git://, file://
-     installPackage = template;
-     templateName = template.substr(template.lastIndexOf('/') + 1);
+    // URL, e.g. git://, file://
+    installPackage = template;
+    templateName = template.substr(template.lastIndexOf('/') + 1);
   } else {
     // e.g 'demo'
     installPackage = 'react-native-template-' + template;
@@ -124,25 +156,23 @@ function createFromRemoteTemplate(template, destPath, newProjectName, yarnVersio
   console.log(`Fetching template ${installPackage}...`);
   try {
     if (yarnVersion) {
-      execSync(`yarn add ${installPackage} --ignore-scripts`, {stdio: 'inherit'});
+      execSync(`yarn add ${installPackage} --ignore-scripts`, {
+        stdio: 'inherit',
+      });
     } else {
-      execSync(`npm install ${installPackage} --save --save-exact --ignore-scripts`, {stdio: 'inherit'});
+      execSync(
+        `npm install ${installPackage} --save --save-exact --ignore-scripts`,
+        {stdio: 'inherit'},
+      );
     }
-    const templatePath = path.resolve(
-      'node_modules', templateName
-    );
-    copyProjectTemplateAndReplace(
-      templatePath,
-      destPath,
-      newProjectName,
-      {
-        // Every template contains a dummy package.json file included
-        // only for publishing the template to npm.
-        // We want to ignore this dummy file, otherwise it would overwrite
-        // our project's package.json file.
-        ignorePaths: ['package.json', 'dependencies.json'],
-      }
-    );
+    const templatePath = path.resolve('node_modules', templateName);
+    copyProjectTemplateAndReplace(templatePath, destPath, newProjectName, {
+      // Every template contains a dummy package.json file included
+      // only for publishing the template to npm.
+      // We want to ignore this dummy file, otherwise it would overwrite
+      // our project's package.json file.
+      ignorePaths: ['package.json', 'dependencies.json'],
+    });
     installTemplateDependencies(templatePath, yarnVersion);
     installTemplateDevDependencies(templatePath, yarnVersion);
   } finally {
@@ -158,7 +188,7 @@ function createFromRemoteTemplate(template, destPath, newProjectName, yarnVersio
       // if this the clean up fails.
       console.warn(
         `Failed to clean up template temp files in node_modules/${templateName}. ` +
-        'This is not a critical error, you can work on your app.'
+          'This is not a critical error, you can work on your app.',
       );
     }
   }
@@ -167,9 +197,7 @@ function createFromRemoteTemplate(template, destPath, newProjectName, yarnVersio
 function installTemplateDependencies(templatePath, yarnVersion) {
   // dependencies.json is a special file that lists additional dependencies
   // that are required by this template
-  const dependenciesJsonPath = path.resolve(
-    templatePath, 'dependencies.json'
-  );
+  const dependenciesJsonPath = path.resolve(templatePath, 'dependencies.json');
   console.log('Adding dependencies for the project...');
   if (!fs.existsSync(dependenciesJsonPath)) {
     console.log('No additional dependencies.');
@@ -181,7 +209,7 @@ function installTemplateDependencies(templatePath, yarnVersion) {
     dependencies = JSON.parse(fs.readFileSync(dependenciesJsonPath));
   } catch (err) {
     throw new Error(
-      'Could not parse the template\'s dependencies.json: ' + err.message
+      "Could not parse the template's dependencies.json: " + err.message,
     );
   }
   for (let depName in dependencies) {
@@ -191,10 +219,12 @@ function installTemplateDependencies(templatePath, yarnVersion) {
     if (yarnVersion) {
       execSync(`yarn add ${depToInstall}`, {stdio: 'inherit'});
     } else {
-      execSync(`npm install ${depToInstall} --save --save-exact`, {stdio: 'inherit'});
+      execSync(`npm install ${depToInstall} --save --save-exact`, {
+        stdio: 'inherit',
+      });
     }
   }
-  console.log('Linking native dependencies into the project\'s build files...');
+  console.log("Linking native dependencies into the project's build files...");
   execSync('react-native link', {stdio: 'inherit'});
 }
 
@@ -202,7 +232,8 @@ function installTemplateDevDependencies(templatePath, yarnVersion) {
   // devDependencies.json is a special file that lists additional develop dependencies
   // that are required by this template
   const devDependenciesJsonPath = path.resolve(
-    templatePath, 'devDependencies.json'
+    templatePath,
+    'devDependencies.json',
   );
   console.log('Adding develop dependencies for the project...');
   if (!fs.existsSync(devDependenciesJsonPath)) {
@@ -215,7 +246,7 @@ function installTemplateDevDependencies(templatePath, yarnVersion) {
     dependencies = JSON.parse(fs.readFileSync(devDependenciesJsonPath));
   } catch (err) {
     throw new Error(
-      'Could not parse the template\'s devDependencies.json: ' + err.message
+      "Could not parse the template's devDependencies.json: " + err.message,
     );
   }
   for (let depName in dependencies) {
@@ -225,7 +256,9 @@ function installTemplateDevDependencies(templatePath, yarnVersion) {
     if (yarnVersion) {
       execSync(`yarn add ${depToInstall} -D`, {stdio: 'inherit'});
     } else {
-      execSync(`npm install ${depToInstall} --save-dev --save-exact`, {stdio: 'inherit'});
+      execSync(`npm install ${depToInstall} --save-dev --save-exact`, {
+        stdio: 'inherit',
+      });
     }
   }
 }
diff --git a/local-cli/info/info.js b/local-cli/info/info.js
index d5e4284fe0b6..0164c0acde54 100644
--- a/local-cli/info/info.js
+++ b/local-cli/info/info.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const envinfo = require('envinfo');
@@ -13,7 +16,10 @@ const info = function() {
 
   try {
     envinfo.print({
-      packages: typeof args.packages === 'string' ? ['react', 'react-native'].concat(args.packages.split(',')) : args.packages
+      packages:
+        typeof args.packages === 'string'
+          ? ['react', 'react-native'].concat(args.packages.split(','))
+          : args.packages,
     });
   } catch (error) {
     console.log('Error: unable to print environment info');
@@ -27,8 +33,9 @@ module.exports = {
   options: [
     {
       command: '--packages [string]',
-      description: 'Which packages from your package.json to include, in addition to the default React Native and React versions.',
-      default: ['react', 'react-native']
+      description:
+        'Which packages from your package.json to include, in addition to the default React Native and React versions.',
+      default: ['react', 'react-native'],
     },
   ],
   examples: [
@@ -39,7 +46,7 @@ module.exports = {
     {
       desc: 'Get standard version info & specified package versions',
       cmd: 'react-native info --packages jest,eslint,babel-polyfill',
-    }
+    },
   ],
   func: info,
 };
diff --git a/local-cli/init/init.js b/local-cli/init/init.js
index d0233b1ab810..17273f9881d8 100644
--- a/local-cli/init/init.js
+++ b/local-cli/init/init.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const {
@@ -58,42 +61,53 @@ function init(projectDir, argsOrName) {
  */
 function generateProject(destinationRoot, newProjectName, options) {
   var reactNativePackageJson = require('../../package.json');
-  var { peerDependencies } = reactNativePackageJson;
+  var {peerDependencies} = reactNativePackageJson;
   if (!peerDependencies) {
-    console.error('Missing React peer dependency in React Native\'s package.json. Aborting.');
+    console.error(
+      "Missing React peer dependency in React Native's package.json. Aborting.",
+    );
     return;
   }
 
   var reactVersion = peerDependencies.react;
   if (!reactVersion) {
-    console.error('Missing React peer dependency in React Native\'s package.json. Aborting.');
+    console.error(
+      "Missing React peer dependency in React Native's package.json. Aborting.",
+    );
     return;
   }
 
   const yarnVersion =
-    (!options.npm) &&
+    !options.npm &&
     yarn.getYarnVersionIfAvailable() &&
     yarn.isGlobalCliUsingYarn(destinationRoot);
 
-  createProjectFromTemplate(destinationRoot, newProjectName, options.template, yarnVersion);
+  createProjectFromTemplate(
+    destinationRoot,
+    newProjectName,
+    options.template,
+    yarnVersion,
+  );
 
   if (yarnVersion) {
     console.log('Adding React...');
     execSync(`yarn add react@${reactVersion}`, {stdio: 'inherit'});
   } else {
     console.log('Installing React...');
-    execSync(`npm install react@${reactVersion} --save --save-exact`, {stdio: 'inherit'});
+    execSync(`npm install react@${reactVersion} --save --save-exact`, {
+      stdio: 'inherit',
+    });
   }
   if (!options['skip-jest']) {
-    const jestDeps = (
-      `jest babel-jest babel-preset-react-native react-test-renderer@${reactVersion}`
-    );
+    const jestDeps = `jest babel-jest babel-preset-react-native react-test-renderer@${reactVersion}`;
     if (yarnVersion) {
       console.log('Adding Jest...');
       execSync(`yarn add ${jestDeps} --dev --exact`, {stdio: 'inherit'});
     } else {
       console.log('Installing Jest...');
-      execSync(`npm install ${jestDeps} --save-dev --save-exact`, {stdio: 'inherit'});
+      execSync(`npm install ${jestDeps} --save-dev --save-exact`, {
+        stdio: 'inherit',
+      });
     }
     addJestToPackageJson(destinationRoot);
   }
@@ -109,7 +123,7 @@ function addJestToPackageJson(destinationRoot) {
 
   packageJSON.scripts.test = 'jest';
   packageJSON.jest = {
-    preset: 'react-native'
+    preset: 'react-native',
   };
   fs.writeFileSync(packageJSONPath, JSON.stringify(packageJSON, null, 2));
 }
diff --git a/local-cli/install/install.js b/local-cli/install/install.js
index 2efc64978d05..5a0a7afc67ed 100644
--- a/local-cli/install/install.js
+++ b/local-cli/install/install.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const spawnSync = require('child_process').spawnSync;
diff --git a/local-cli/install/uninstall.js b/local-cli/install/uninstall.js
index 0d6fc5ed755b..6a71100677db 100644
--- a/local-cli/install/uninstall.js
+++ b/local-cli/install/uninstall.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const spawnSync = require('child_process').spawnSync;
diff --git a/local-cli/library/library.js b/local-cli/library/library.js
index 14afd6a4059b..4dcc81cbfcd9 100644
--- a/local-cli/library/library.js
+++ b/local-cli/library/library.js
@@ -1,9 +1,12 @@
- /**
+/**
  * Copyright (c) 2015-present, Facebook, Inc.
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const copyAndReplace = require('../util/copyAndReplace');
@@ -18,36 +21,47 @@ const walk = require('../util/walk');
 function library(argv, config, args) {
   if (!isValidPackageName(args.name)) {
     return Promise.reject(
-      args.name + ' is not a valid name for a project. Please use a valid ' +
-      'identifier name (alphanumeric).'
+      args.name +
+        ' is not a valid name for a project. Please use a valid ' +
+        'identifier name (alphanumeric).',
     );
   }
 
   const root = process.cwd();
   const libraries = path.resolve(root, 'Libraries');
   const libraryDest = path.resolve(libraries, args.name);
-  const source = path.resolve('node_modules', 'react-native', 'Libraries', 'Sample');
+  const source = path.resolve(
+    'node_modules',
+    'react-native',
+    'Libraries',
+    'Sample',
+  );
 
   if (!fs.existsSync(libraries)) {
     fs.mkdirSync(libraries);
   }
 
   if (fs.existsSync(libraryDest)) {
-    return Promise.reject(new Error(`Library already exists in ${libraryDest}`));
+    return Promise.reject(
+      new Error(`Library already exists in ${libraryDest}`),
+    );
   }
 
   walk(source).forEach(f => {
-    if (f.indexOf('project.xcworkspace') !== -1 ||
-        f.indexOf('.xcodeproj/xcuserdata') !== -1) {
+    if (
+      f.indexOf('project.xcworkspace') !== -1 ||
+      f.indexOf('.xcodeproj/xcuserdata') !== -1
+    ) {
       return;
     }
 
-    const dest = path.relative(source, f.replace(/Sample/g, args.name).replace(/^_/, '.'));
-    copyAndReplace(
-      path.resolve(source, f),
-      path.resolve(libraryDest, dest),
-      {'Sample': args.name}
+    const dest = path.relative(
+      source,
+      f.replace(/Sample/g, args.name).replace(/^_/, '.'),
     );
+    copyAndReplace(path.resolve(source, f), path.resolve(libraryDest, dest), {
+      Sample: args.name,
+    });
   });
 
   console.log('Created library in', libraryDest);
@@ -55,7 +69,7 @@ function library(argv, config, args) {
   console.log('   Link your library in Xcode:');
   console.log(
     '   https://facebook.github.io/react-native/docs/' +
-    'linking-libraries-ios.html#content\n'
+      'linking-libraries-ios.html#content\n',
   );
 }
 
@@ -63,9 +77,11 @@ module.exports = {
   name: 'new-library',
   func: library,
   description: 'generates a native library bridge',
-  options: [{
-    command: '--name <string>',
-    description: 'name of the library to generate',
-    default: null,
-  }],
+  options: [
+    {
+      command: '--name <string>',
+      description: 'name of the library to generate',
+      default: null,
+    },
+  ],
 };
diff --git a/local-cli/link/__tests__/android/applyPatch.spec.js b/local-cli/link/__tests__/android/applyPatch.spec.js
index b1213dbf315f..79b67f68974e 100644
--- a/local-cli/link/__tests__/android/applyPatch.spec.js
+++ b/local-cli/link/__tests__/android/applyPatch.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -13,14 +14,12 @@ const applyParams = require('../../android/patches/applyParams');
 
 describe('applyParams', () => {
   it('apply params to the string', () => {
-    expect(
-      applyParams('${foo}', {foo: 'foo'}, 'react-native')
-    ).toEqual('getResources().getString(R.string.reactNative_foo)');
+    expect(applyParams('${foo}', {foo: 'foo'}, 'react-native')).toEqual(
+      'getResources().getString(R.string.reactNative_foo)',
+    );
   });
 
   it('use null if no params provided', () => {
-    expect(
-      applyParams('${foo}', {}, 'react-native')
-    ).toEqual('null');
+    expect(applyParams('${foo}', {}, 'react-native')).toEqual('null');
   });
 });
diff --git a/local-cli/link/__tests__/android/isInstalled.spec.js b/local-cli/link/__tests__/android/isInstalled.spec.js
index 131d753731af..a90649f0339f 100644
--- a/local-cli/link/__tests__/android/isInstalled.spec.js
+++ b/local-cli/link/__tests__/android/isInstalled.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -13,7 +14,10 @@ const path = require('path');
 const isInstalled = require('../../android/isInstalled');
 
 const projectConfig = {
-  buildGradlePath: path.join(__dirname, '../../__fixtures__/android/patchedBuild.gradle'),
+  buildGradlePath: path.join(
+    __dirname,
+    '../../__fixtures__/android/patchedBuild.gradle',
+  ),
 };
 
 describe('android::isInstalled', () => {
@@ -23,6 +27,5 @@ describe('android::isInstalled', () => {
   });
 
   it('should return false when project is not in build.gradle', () =>
-    expect(isInstalled(projectConfig, 'test3')).toBeFalsy()
-  );
+    expect(isInstalled(projectConfig, 'test3')).toBeFalsy());
 });
diff --git a/local-cli/link/__tests__/android/makeBuildPatch.spec.js b/local-cli/link/__tests__/android/makeBuildPatch.spec.js
index fdcdad0453b1..51873daf1d02 100644
--- a/local-cli/link/__tests__/android/makeBuildPatch.spec.js
+++ b/local-cli/link/__tests__/android/makeBuildPatch.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -18,8 +19,9 @@ const normalizedScopedName = normalizeProjectName('@scoped/test');
 
 describe('makeBuildPatch', () => {
   it('should build a patch function', () => {
-    expect(Object.prototype.toString(makeBuildPatch(name)))
-      .toBe('[object Object]');
+    expect(Object.prototype.toString(makeBuildPatch(name))).toBe(
+      '[object Object]',
+    );
   });
 
   it('should make a correct patch', () => {
@@ -34,7 +36,6 @@ describe('makeBuildPatch', () => {
   });
 });
 
-
 describe('makeBuildPatchWithScopedPackage', () => {
   it('should make a correct patch', () => {
     const {patch} = makeBuildPatch(scopedName);
diff --git a/local-cli/link/__tests__/android/makeImportPatch.spec.js b/local-cli/link/__tests__/android/makeImportPatch.spec.js
index d02eb6689855..e00977a09617 100644
--- a/local-cli/link/__tests__/android/makeImportPatch.spec.js
+++ b/local-cli/link/__tests__/android/makeImportPatch.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -15,8 +16,9 @@ const packageImportPath = 'import some.example.project';
 
 describe('makeImportPatch', () => {
   it('should build a patch', () => {
-    expect(Object.prototype.toString(makeImportPatch(packageImportPath)))
-      .toBe('[object Object]');
+    expect(Object.prototype.toString(makeImportPatch(packageImportPath))).toBe(
+      '[object Object]',
+    );
   });
 
   it('MainActivity contains a correct import patch', () => {
diff --git a/local-cli/link/__tests__/android/makePackagePatch.spec.js b/local-cli/link/__tests__/android/makePackagePatch.spec.js
index c7e55c7e90f2..48e7a3c30f56 100644
--- a/local-cli/link/__tests__/android/makePackagePatch.spec.js
+++ b/local-cli/link/__tests__/android/makePackagePatch.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -12,7 +13,7 @@
 const makePackagePatch = require('../../android/patches/makePackagePatch');
 const applyParams = require('../../android/patches/applyParams');
 
-const packageInstance = 'new SomeLibrary(${foo}, ${bar}, \'something\')';
+const packageInstance = "new SomeLibrary(${foo}, ${bar}, 'something')";
 const name = 'some-library';
 const params = {
   foo: 'foo',
@@ -22,8 +23,7 @@ const params = {
 describe('makePackagePatch@0.20', () => {
   it('should build a patch', () => {
     const packagePatch = makePackagePatch(packageInstance, params, name);
-    expect(Object.prototype.toString(packagePatch))
-      .toBe('[object Object]');
+    expect(Object.prototype.toString(packagePatch)).toBe('[object Object]');
   });
 
   it('MainActivity contains a correct 0.20 import patch', () => {
diff --git a/local-cli/link/__tests__/android/makeSettingsPatch.spec.js b/local-cli/link/__tests__/android/makeSettingsPatch.spec.js
index 63954af8155f..80b2be703435 100644
--- a/local-cli/link/__tests__/android/makeSettingsPatch.spec.js
+++ b/local-cli/link/__tests__/android/makeSettingsPatch.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -29,48 +30,54 @@ const scopedDependencyConfig = {
 
 describe('makeSettingsPatch', () => {
   it('should build a patch function', () => {
-    expect(Object.prototype.toString(
-      makeSettingsPatch(name, dependencyConfig, projectConfig)
-    )).toBe('[object Object]');
+    expect(
+      Object.prototype.toString(
+        makeSettingsPatch(name, dependencyConfig, projectConfig),
+      ),
+    ).toBe('[object Object]');
   });
 
   it('should make a correct patch', () => {
     const projectDir = path.relative(
       path.dirname(projectConfig.settingsGradlePath),
-      dependencyConfig.sourceDir
+      dependencyConfig.sourceDir,
     );
 
     const {patch} = makeSettingsPatch(name, dependencyConfig, projectConfig);
 
-    expect(patch)
-      .toBe(
-        `include ':${name}'\n` +
+    expect(patch).toBe(
+      `include ':${name}'\n` +
         `project(':${name}').projectDir = ` +
-        `new File(rootProject.projectDir, '${projectDir}')\n`
-      );
+        `new File(rootProject.projectDir, '${projectDir}')\n`,
+    );
   });
 });
 
 describe('makeSettingsPatchWithScopedPackage', () => {
   it('should build a patch function', () => {
-    expect(Object.prototype.toString(
-      makeSettingsPatch(scopedName, scopedDependencyConfig, projectConfig)
-    )).toBe('[object Object]');
+    expect(
+      Object.prototype.toString(
+        makeSettingsPatch(scopedName, scopedDependencyConfig, projectConfig),
+      ),
+    ).toBe('[object Object]');
   });
 
   it('should make a correct patch', () => {
     const projectDir = path.relative(
       path.dirname(projectConfig.settingsGradlePath),
-      scopedDependencyConfig.sourceDir
+      scopedDependencyConfig.sourceDir,
     );
 
-    const {patch} = makeSettingsPatch(scopedName, scopedDependencyConfig, projectConfig);
+    const {patch} = makeSettingsPatch(
+      scopedName,
+      scopedDependencyConfig,
+      projectConfig,
+    );
 
-    expect(patch)
-      .toBe(
-        `include ':${normalizedScopedName}'\n` +
+    expect(patch).toBe(
+      `include ':${normalizedScopedName}'\n` +
         `project(':${normalizedScopedName}').projectDir = ` +
-        `new File(rootProject.projectDir, '${projectDir}')\n`
-      );
+        `new File(rootProject.projectDir, '${projectDir}')\n`,
+    );
   });
 });
diff --git a/local-cli/link/__tests__/android/makeStringsPatch.spec.js b/local-cli/link/__tests__/android/makeStringsPatch.spec.js
index 3015f15b340b..f8b6c07ed946 100644
--- a/local-cli/link/__tests__/android/makeStringsPatch.spec.js
+++ b/local-cli/link/__tests__/android/makeStringsPatch.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -17,8 +18,9 @@ describe('makeStringsPatch', () => {
       keyA: 'valueA',
     };
 
-    expect(makeStringsPatch(params, 'module').patch)
-      .toContain('<string moduleConfig="true" name="module_keyA">valueA</string>');
+    expect(makeStringsPatch(params, 'module').patch).toContain(
+      '<string moduleConfig="true" name="module_keyA">valueA</string>',
+    );
   });
 
   it('should export an empty patch if no params given', () => {
diff --git a/local-cli/link/__tests__/android/normalizeProjectName.spec.js b/local-cli/link/__tests__/android/normalizeProjectName.spec.js
index e4e236aca42f..2a69e2e09844 100644
--- a/local-cli/link/__tests__/android/normalizeProjectName.spec.js
+++ b/local-cli/link/__tests__/android/normalizeProjectName.spec.js
@@ -6,21 +6,20 @@
  *
  * All rights reserved.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
- 'use strict';
+'use strict';
 
 const normalizeProjectName = require('../../android/patches/normalizeProjectName');
 
 const name = 'test';
 const scopedName = '@scoped/test';
 
- describe('normalizeProjectName', () => {
+describe('normalizeProjectName', () => {
   it('should replace slashes with underscores', () => {
-    expect(normalizeProjectName(name))
-      .toBe('test');
-    expect(normalizeProjectName(scopedName))
-      .toBe('@scoped_test');
+    expect(normalizeProjectName(name)).toBe('test');
+    expect(normalizeProjectName(scopedName)).toBe('@scoped_test');
   });
 });
diff --git a/local-cli/link/__tests__/getDependencyConfig.spec.js b/local-cli/link/__tests__/getDependencyConfig.spec.js
index 30db06d537fc..dda764853ee6 100644
--- a/local-cli/link/__tests__/getDependencyConfig.spec.js
+++ b/local-cli/link/__tests__/getDependencyConfig.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -13,7 +14,7 @@ const getDependencyConfig = require('../getDependencyConfig');
 const sinon = require('sinon');
 
 describe('getDependencyConfig', () => {
-  it('should return an array of dependencies\' rnpm config', () => {
+  it("should return an array of dependencies' rnpm config", () => {
     const config = {
       getDependencyConfig: sinon.stub(),
     };
diff --git a/local-cli/link/__tests__/getProjectDependencies.spec.js b/local-cli/link/__tests__/getProjectDependencies.spec.js
index fc7dd3cd91dd..974f128191e4 100644
--- a/local-cli/link/__tests__/getProjectDependencies.spec.js
+++ b/local-cli/link/__tests__/getProjectDependencies.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -17,10 +18,9 @@ describe('getProjectDependencies', () => {
     jest.resetModules();
   });
   it('should return an array of project dependencies', () => {
-    jest.setMock(
-      path.join(process.cwd(), './package.json'),
-      { dependencies: { lodash: '^6.0.0', 'react-native': '^16.0.0' }}
-    );
+    jest.setMock(path.join(process.cwd(), './package.json'), {
+      dependencies: {lodash: '^6.0.0', 'react-native': '^16.0.0'},
+    });
 
     expect(getProjectDependencies()).toEqual(['lodash']);
   });
diff --git a/local-cli/link/__tests__/groupFilesByType.spec.js b/local-cli/link/__tests__/groupFilesByType.spec.js
index a96ff6e24d38..d4c4e9598860 100644
--- a/local-cli/link/__tests__/groupFilesByType.spec.js
+++ b/local-cli/link/__tests__/groupFilesByType.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -12,21 +13,13 @@
 const groupFilesByType = require('../groupFilesByType');
 
 describe('groupFilesByType', () => {
-
   it('should group files by its type', () => {
-    const fonts = [
-      'fonts/a.ttf',
-      'fonts/b.ttf',
-    ];
-    const images = [
-      'images/a.jpg',
-      'images/c.jpeg',
-    ];
+    const fonts = ['fonts/a.ttf', 'fonts/b.ttf'];
+    const images = ['images/a.jpg', 'images/c.jpeg'];
 
     const groupedFiles = groupFilesByType(fonts.concat(images));
 
     expect(groupedFiles.font).toEqual(fonts);
     expect(groupedFiles.image).toEqual(images);
   });
-
 });
diff --git a/local-cli/link/__tests__/ios/addFileToProject.spec.js b/local-cli/link/__tests__/ios/addFileToProject.spec.js
index ca32c867090c..1b6d3ab69540 100644
--- a/local-cli/link/__tests__/ios/addFileToProject.spec.js
+++ b/local-cli/link/__tests__/ios/addFileToProject.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -15,7 +16,7 @@ const addFileToProject = require('../../ios/addFileToProject');
 const _ = require('lodash');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::addFileToProject', () => {
@@ -27,8 +28,9 @@ describe('ios::addFileToProject', () => {
     expect(
       _.includes(
         Object.keys(project.pbxFileReferenceSection()),
-        addFileToProject(project, '../../__fixtures__/linearGradient.pbxproj').fileRef
-      )
+        addFileToProject(project, '../../__fixtures__/linearGradient.pbxproj')
+          .fileRef,
+      ),
     ).toBeTruthy();
   });
 });
diff --git a/local-cli/link/__tests__/ios/addProjectToLibraries.spec.js b/local-cli/link/__tests__/ios/addProjectToLibraries.spec.js
index 4d20621e0afd..6caac1636a60 100644
--- a/local-cli/link/__tests__/ios/addProjectToLibraries.spec.js
+++ b/local-cli/link/__tests__/ios/addProjectToLibraries.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -16,7 +17,7 @@ const addProjectToLibraries = require('../../ios/addProjectToLibraries');
 const last = require('lodash').last;
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::addProjectToLibraries', () => {
diff --git a/local-cli/link/__tests__/ios/addSharedLibraries.spec.js b/local-cli/link/__tests__/ios/addSharedLibraries.spec.js
index 36343a89ce64..4a645bc3fe32 100644
--- a/local-cli/link/__tests__/ios/addSharedLibraries.spec.js
+++ b/local-cli/link/__tests__/ios/addSharedLibraries.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -15,11 +16,10 @@ const addSharedLibraries = require('../../ios/addSharedLibraries');
 const getGroup = require('../../ios/getGroup');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::addSharedLibraries', () => {
-
   beforeEach(() => {
     project.parseSync();
   });
@@ -48,5 +48,4 @@ describe('ios::addSharedLibraries', () => {
     const frameworksGroup = getGroup(project, 'Frameworks');
     expect(frameworksGroup.children.length).toEqual(1);
   });
-
 });
diff --git a/local-cli/link/__tests__/ios/createGroup.spec.js b/local-cli/link/__tests__/ios/createGroup.spec.js
index b3fbf67a1a1f..cee24213f62d 100644
--- a/local-cli/link/__tests__/ios/createGroup.spec.js
+++ b/local-cli/link/__tests__/ios/createGroup.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -16,7 +17,7 @@ const getGroup = require('../../ios/getGroup');
 const last = require('lodash').last;
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::createGroup', () => {
@@ -33,18 +34,14 @@ describe('ios::createGroup', () => {
     const createdGroup = createGroup(project, 'Resources');
     const mainGroup = getGroup(project);
 
-    expect(
-      last(mainGroup.children).comment
-    ).toBe(createdGroup.name);
+    expect(last(mainGroup.children).comment).toBe(createdGroup.name);
   });
 
   it('should create a nested group with given path', () => {
     const createdGroup = createGroup(project, 'NewGroup/NewNestedGroup');
     const outerGroup = getGroup(project, 'NewGroup');
 
-    expect(
-      last(outerGroup.children).comment
-    ).toBe(createdGroup.name);
+    expect(last(outerGroup.children).comment).toBe(createdGroup.name);
   });
 
   it('should-not create already created groups', () => {
@@ -53,10 +50,7 @@ describe('ios::createGroup', () => {
     const mainGroup = getGroup(project);
 
     expect(
-      mainGroup
-        .children
-        .filter(group => group.comment === 'Libraries')
-        .length
+      mainGroup.children.filter(group => group.comment === 'Libraries').length,
     ).toBe(1);
     expect(last(outerGroup.children).comment).toBe(createdGroup.name);
   });
diff --git a/local-cli/link/__tests__/ios/getBuildProperty.spec.js b/local-cli/link/__tests__/ios/getBuildProperty.spec.js
index 831944bbb94d..991c43dfe8ff 100644
--- a/local-cli/link/__tests__/ios/getBuildProperty.spec.js
+++ b/local-cli/link/__tests__/ios/getBuildProperty.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ const path = require('path');
 const getBuildProperty = require('../../ios/getBuildProperty');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::getBuildProperty', () => {
diff --git a/local-cli/link/__tests__/ios/getGroup.spec.js b/local-cli/link/__tests__/ios/getGroup.spec.js
index f46cc31ebd7c..eb6716af7d43 100644
--- a/local-cli/link/__tests__/ios/getGroup.spec.js
+++ b/local-cli/link/__tests__/ios/getGroup.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ const getGroup = require('../../ios/getGroup');
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::getGroup', () => {
diff --git a/local-cli/link/__tests__/ios/getHeaderSearchPath.spec.js b/local-cli/link/__tests__/ios/getHeaderSearchPath.spec.js
index 7e96a20b0edc..bc1669e59d84 100644
--- a/local-cli/link/__tests__/ios/getHeaderSearchPath.spec.js
+++ b/local-cli/link/__tests__/ios/getHeaderSearchPath.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -20,14 +21,19 @@ describe('ios::getHeaderSearchPath', () => {
    */
   it('should return correct path when all headers are in root folder', () => {
     const files = [
-      path.join('react-native-project', 'node_modules', 'package', 'Gradient.h'),
+      path.join(
+        'react-native-project',
+        'node_modules',
+        'package',
+        'Gradient.h',
+      ),
       path.join('react-native-project', 'node_modules', 'package', 'Manager.h'),
     ];
 
     const searchPath = getHeaderSearchPath(SRC_DIR, files);
 
     expect(searchPath).toBe(
-      `"${['$(SRCROOT)', '..', 'node_modules', 'package'].join(path.sep)}"`
+      `"${['$(SRCROOT)', '..', 'node_modules', 'package'].join(path.sep)}"`,
     );
   });
 
@@ -36,14 +42,30 @@ describe('ios::getHeaderSearchPath', () => {
    */
   it('should return correct path when headers are in multiple folders', () => {
     const files = [
-      path.join('react-native-project', 'node_modules', 'package', 'src', 'folderA', 'Gradient.h'),
-      path.join('react-native-project', 'node_modules', 'package', 'src', 'folderB', 'Manager.h'),
+      path.join(
+        'react-native-project',
+        'node_modules',
+        'package',
+        'src',
+        'folderA',
+        'Gradient.h',
+      ),
+      path.join(
+        'react-native-project',
+        'node_modules',
+        'package',
+        'src',
+        'folderB',
+        'Manager.h',
+      ),
     ];
 
     const searchPath = getHeaderSearchPath(SRC_DIR, files);
 
     expect(searchPath).toBe(
-      `"${['$(SRCROOT)', '..', 'node_modules', 'package', 'src'].join(path.sep)}/**"`
+      `"${['$(SRCROOT)', '..', 'node_modules', 'package', 'src'].join(
+        path.sep,
+      )}/**"`,
     );
   });
 
@@ -52,15 +74,37 @@ describe('ios::getHeaderSearchPath', () => {
    */
   it('should return correct path when headers are in root and nested folders', () => {
     const files = [
-      path.join('react-native-project', 'node_modules', 'package', 'src', 'folderA', 'Gradient.h'),
-      path.join('react-native-project', 'node_modules', 'package', 'src', 'folderB', 'Manager.h'),
-      path.join('react-native-project', 'node_modules', 'package', 'src', 'Manager.h'),
+      path.join(
+        'react-native-project',
+        'node_modules',
+        'package',
+        'src',
+        'folderA',
+        'Gradient.h',
+      ),
+      path.join(
+        'react-native-project',
+        'node_modules',
+        'package',
+        'src',
+        'folderB',
+        'Manager.h',
+      ),
+      path.join(
+        'react-native-project',
+        'node_modules',
+        'package',
+        'src',
+        'Manager.h',
+      ),
     ];
 
     const searchPath = getHeaderSearchPath(SRC_DIR, files);
 
     expect(searchPath).toBe(
-      `"${['$(SRCROOT)', '..', 'node_modules', 'package', 'src'].join(path.sep)}/**"`
+      `"${['$(SRCROOT)', '..', 'node_modules', 'package', 'src'].join(
+        path.sep,
+      )}/**"`,
     );
   });
 });
diff --git a/local-cli/link/__tests__/ios/getHeadersInFolder.spec.js b/local-cli/link/__tests__/ios/getHeadersInFolder.spec.js
index ff1068657914..1793755d979e 100644
--- a/local-cli/link/__tests__/ios/getHeadersInFolder.spec.js
+++ b/local-cli/link/__tests__/ios/getHeadersInFolder.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
diff --git a/local-cli/link/__tests__/ios/getPlist.spec.js b/local-cli/link/__tests__/ios/getPlist.spec.js
index 156320079b8a..10e1315dd98f 100644
--- a/local-cli/link/__tests__/ios/getPlist.spec.js
+++ b/local-cli/link/__tests__/ios/getPlist.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ const getPlist = require('../../ios/getPlist');
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::getPlist', () => {
diff --git a/local-cli/link/__tests__/ios/getPlistPath.spec.js b/local-cli/link/__tests__/ios/getPlistPath.spec.js
index bf7c922edc89..9cbce096ea13 100644
--- a/local-cli/link/__tests__/ios/getPlistPath.spec.js
+++ b/local-cli/link/__tests__/ios/getPlistPath.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ const getPlistPath = require('../../ios/getPlistPath');
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::getPlistPath', () => {
diff --git a/local-cli/link/__tests__/ios/getProducts.spec.js b/local-cli/link/__tests__/ios/getProducts.spec.js
index 26bee69fca00..88c7515d7678 100644
--- a/local-cli/link/__tests__/ios/getProducts.spec.js
+++ b/local-cli/link/__tests__/ios/getProducts.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ const getProducts = require('../../ios/getProducts');
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::getProducts', () => {
diff --git a/local-cli/link/__tests__/ios/getTargets.spec.js b/local-cli/link/__tests__/ios/getTargets.spec.js
index 99f3f370215e..7acf9df43ed6 100644
--- a/local-cli/link/__tests__/ios/getTargets.spec.js
+++ b/local-cli/link/__tests__/ios/getTargets.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ const getTargets = require('../../ios/getTargets');
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::getTargets', () => {
diff --git a/local-cli/link/__tests__/ios/hasLibraryImported.spec.js b/local-cli/link/__tests__/ios/hasLibraryImported.spec.js
index 6d9d1723f903..a74e7b59388c 100644
--- a/local-cli/link/__tests__/ios/hasLibraryImported.spec.js
+++ b/local-cli/link/__tests__/ios/hasLibraryImported.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ const hasLibraryImported = require('../../ios/hasLibraryImported');
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::hasLibraryImported', () => {
diff --git a/local-cli/link/__tests__/ios/isInstalled.spec.js b/local-cli/link/__tests__/ios/isInstalled.spec.js
index bc291d79df34..3946677c3538 100644
--- a/local-cli/link/__tests__/ios/isInstalled.spec.js
+++ b/local-cli/link/__tests__/ios/isInstalled.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -19,18 +20,20 @@ const baseProjectConfig = {
 
 describe('ios::isInstalled', () => {
   it('should return true when .xcodeproj in Libraries', () => {
-    const dependencyConfig = { projectName: 'React.xcodeproj' };
+    const dependencyConfig = {projectName: 'React.xcodeproj'};
     expect(isInstalled(baseProjectConfig, dependencyConfig)).toBeTruthy();
   });
 
   it('should return false when .xcodeproj not in Libraries', () => {
-    const dependencyConfig = { projectName: 'Missing.xcodeproj' };
+    const dependencyConfig = {projectName: 'Missing.xcodeproj'};
     expect(isInstalled(baseProjectConfig, dependencyConfig)).toBeFalsy();
   });
 
   it('should return false when `LibraryFolder` is missing', () => {
-    const dependencyConfig = { projectName: 'React.xcodeproj' };
-    const projectConfig = Object.assign({}, baseProjectConfig, { libraryFolder: 'Missing' });
+    const dependencyConfig = {projectName: 'React.xcodeproj'};
+    const projectConfig = Object.assign({}, baseProjectConfig, {
+      libraryFolder: 'Missing',
+    });
     expect(isInstalled(projectConfig, dependencyConfig)).toBeFalsy();
   });
 });
diff --git a/local-cli/link/__tests__/ios/mapHeaderSearchPaths.spec.js b/local-cli/link/__tests__/ios/mapHeaderSearchPaths.spec.js
index e834b32da8cb..785e6bdd73f3 100644
--- a/local-cli/link/__tests__/ios/mapHeaderSearchPaths.spec.js
+++ b/local-cli/link/__tests__/ios/mapHeaderSearchPaths.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ const mapHeaderSearchPaths = require('../../ios/mapHeaderSearchPaths');
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::mapHeaderSearchPaths', () => {
diff --git a/local-cli/link/__tests__/ios/removeProjectFromLibraries.js b/local-cli/link/__tests__/ios/removeProjectFromLibraries.js
index 262d61b11e8e..2c882be27d57 100644
--- a/local-cli/link/__tests__/ios/removeProjectFromLibraries.js
+++ b/local-cli/link/__tests__/ios/removeProjectFromLibraries.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -17,7 +18,7 @@ const last = require('lodash').last;
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::removeProjectFromLibraries', () => {
@@ -26,7 +27,7 @@ describe('ios::removeProjectFromLibraries', () => {
 
     addProjectToLibraries(
       project.pbxGroupByName('Libraries'),
-      new PbxFile('fakePath')
+      new PbxFile('fakePath'),
     );
   });
 
diff --git a/local-cli/link/__tests__/ios/removeProjectFromProject.spec.js b/local-cli/link/__tests__/ios/removeProjectFromProject.spec.js
index 54a3e07cd7aa..16dc3b374e49 100644
--- a/local-cli/link/__tests__/ios/removeProjectFromProject.spec.js
+++ b/local-cli/link/__tests__/ios/removeProjectFromProject.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -16,7 +17,7 @@ const removeProjectFromProject = require('../../ios/removeProjectFromProject');
 const path = require('path');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 const filePath = '../../__fixtures__/linearGradient.pbxproj';
 
@@ -27,8 +28,9 @@ describe('ios::addFileToProject', () => {
   });
 
   it('should return removed file', () => {
-    expect(removeProjectFromProject(project, filePath) instanceof pbxFile)
-      .toBeTruthy();
+    expect(
+      removeProjectFromProject(project, filePath) instanceof pbxFile,
+    ).toBeTruthy();
   });
 
   it('should remove file from a project', () => {
diff --git a/local-cli/link/__tests__/ios/removeSharedLibrary.spec.js b/local-cli/link/__tests__/ios/removeSharedLibrary.spec.js
index 601f0f7aa575..ee69b5c6adfc 100644
--- a/local-cli/link/__tests__/ios/removeSharedLibrary.spec.js
+++ b/local-cli/link/__tests__/ios/removeSharedLibrary.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -16,11 +17,10 @@ const removeSharedLibraries = require('../../ios/removeSharedLibraries');
 const getGroup = require('../../ios/getGroup');
 
 const project = xcode.project(
-  path.join(__dirname, '../../__fixtures__/project.pbxproj')
+  path.join(__dirname, '../../__fixtures__/project.pbxproj'),
 );
 
 describe('ios::removeSharedLibraries', () => {
-
   beforeEach(() => {
     project.parseSync();
     addSharedLibraries(project, ['libc++.tbd', 'libz.tbd']);
@@ -40,5 +40,4 @@ describe('ios::removeSharedLibraries', () => {
     const frameworksGroup = getGroup(project, 'Frameworks');
     expect(frameworksGroup.children.length).toEqual(2);
   });
-
 });
diff --git a/local-cli/link/__tests__/ios/writePlist.spec.js b/local-cli/link/__tests__/ios/writePlist.spec.js
index 7e32b72aacc8..40a7e549255b 100644
--- a/local-cli/link/__tests__/ios/writePlist.spec.js
+++ b/local-cli/link/__tests__/ios/writePlist.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,7 +15,7 @@ jest.mock('fs');
 let plistPath = null;
 jest.mock('../../ios/getPlistPath', () => () => plistPath);
 
-const { readFileSync } = require.requireActual('fs');
+const {readFileSync} = require.requireActual('fs');
 const fs = require('fs');
 
 const xcode = require('xcode');
@@ -33,9 +34,7 @@ const project = xcode.project('/Basic/project.pbxproj');
 
 const plist = {
   CFBundleDevelopmentRegion: 'en',
-  UISupportedInterfaceOrientations: [
-    'UIInterfaceOrientationPortrait'
-  ]
+  UISupportedInterfaceOrientations: ['UIInterfaceOrientationPortrait'],
 };
 
 describe('ios::writePlist', () => {
diff --git a/local-cli/link/__tests__/link.spec.js b/local-cli/link/__tests__/link.spec.js
index 5ff3ab73a19e..7e658eb7d202 100644
--- a/local-cli/link/__tests__/link.spec.js
+++ b/local-cli/link/__tests__/link.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -12,10 +13,7 @@
 const sinon = require('sinon');
 const log = require('npmlog');
 const path = require('path');
-jest.setMock(
-  'chalk',
-  { grey: (str) => str, }
-);
+jest.setMock('chalk', {grey: str => str});
 
 describe('link', () => {
   beforeEach(() => {
@@ -24,7 +22,7 @@ describe('link', () => {
     log.level = 'silent';
   });
 
-  it('should reject when run in a folder without package.json', (done) => {
+  it('should reject when run in a folder without package.json', done => {
     const config = {
       getProjectConfig: () => {
         throw new Error('No package.json found');
@@ -35,77 +33,65 @@ describe('link', () => {
     link([], config).catch(() => done());
   });
 
-  it('should accept a name of a dependency to link', (done) => {
+  it('should accept a name of a dependency to link', done => {
     const config = {
       getPlatformConfig: () => ({ios: {}, android: {}}),
-      getProjectConfig: () => ({ assets: [] }),
-      getDependencyConfig: sinon.stub().returns({ assets: [], commands: {} }),
+      getProjectConfig: () => ({assets: []}),
+      getDependencyConfig: sinon.stub().returns({assets: [], commands: {}}),
     };
 
     const link = require('../link').func;
     link(['react-native-gradient'], config).then(() => {
       expect(
-        config.getDependencyConfig.calledWith('react-native-gradient')
+        config.getDependencyConfig.calledWith('react-native-gradient'),
       ).toBeTruthy();
       done();
     });
   });
 
-  it('should read dependencies from package.json when name not provided', (done) => {
+  it('should read dependencies from package.json when name not provided', done => {
     const config = {
       getPlatformConfig: () => ({ios: {}, android: {}}),
-      getProjectConfig: () => ({ assets: [] }),
-      getDependencyConfig: sinon.stub().returns({ assets: [], commands: {} }),
+      getProjectConfig: () => ({assets: []}),
+      getDependencyConfig: sinon.stub().returns({assets: [], commands: {}}),
     };
 
-    jest.setMock(
-      path.join(process.cwd(), 'package.json'),
-      {
-        dependencies: {
-          'react-native-test': '*',
-        },
-      }
-    );
+    jest.setMock(path.join(process.cwd(), 'package.json'), {
+      dependencies: {
+        'react-native-test': '*',
+      },
+    });
 
     const link = require('../link').func;
     link([], config).then(() => {
       expect(
-        config.getDependencyConfig.calledWith('react-native-test')
+        config.getDependencyConfig.calledWith('react-native-test'),
       ).toBeTruthy();
       done();
     });
   });
 
-  it('should register native module when android/ios projects are present', (done) => {
+  it('should register native module when android/ios projects are present', done => {
     const registerNativeModule = sinon.stub();
     const dependencyConfig = {android: {}, ios: {}, assets: [], commands: {}};
     const androidLinkConfig = require('../android');
     const iosLinkConfig = require('../ios');
     const config = {
-      getPlatformConfig: () => ({ios: { linkConfig: iosLinkConfig }, android: { linkConfig: androidLinkConfig }}),
+      getPlatformConfig: () => ({
+        ios: {linkConfig: iosLinkConfig},
+        android: {linkConfig: androidLinkConfig},
+      }),
       getProjectConfig: () => ({android: {}, ios: {}, assets: []}),
       getDependencyConfig: sinon.stub().returns(dependencyConfig),
     };
 
-    jest.setMock(
-      '../android/isInstalled.js',
-      sinon.stub().returns(false)
-    );
+    jest.setMock('../android/isInstalled.js', sinon.stub().returns(false));
 
-    jest.setMock(
-      '../android/registerNativeModule.js',
-      registerNativeModule
-    );
+    jest.setMock('../android/registerNativeModule.js', registerNativeModule);
 
-    jest.setMock(
-      '../ios/isInstalled.js',
-      sinon.stub().returns(false)
-    );
+    jest.setMock('../ios/isInstalled.js', sinon.stub().returns(false));
 
-    jest.setMock(
-      '../ios/registerNativeModule.js',
-      registerNativeModule
-    );
+    jest.setMock('../ios/registerNativeModule.js', registerNativeModule);
 
     const link = require('../link').func;
 
@@ -115,34 +101,22 @@ describe('link', () => {
     });
   });
 
-  it('should not register modules when they are already installed', (done) => {
+  it('should not register modules when they are already installed', done => {
     const registerNativeModule = sinon.stub();
     const dependencyConfig = {ios: {}, android: {}, assets: [], commands: {}};
     const config = {
       getPlatformConfig: () => ({ios: {}, android: {}}),
-      getProjectConfig: () => ({ ios: {}, android: {}, assets: [] }),
+      getProjectConfig: () => ({ios: {}, android: {}, assets: []}),
       getDependencyConfig: sinon.stub().returns(dependencyConfig),
     };
 
-    jest.setMock(
-      '../ios/isInstalled.js',
-      sinon.stub().returns(true)
-    );
+    jest.setMock('../ios/isInstalled.js', sinon.stub().returns(true));
 
-    jest.setMock(
-      '../android/isInstalled.js',
-      sinon.stub().returns(true)
-    );
+    jest.setMock('../android/isInstalled.js', sinon.stub().returns(true));
 
-    jest.setMock(
-      '../ios/registerNativeModule.js',
-      registerNativeModule
-    );
+    jest.setMock('../ios/registerNativeModule.js', registerNativeModule);
 
-    jest.setMock(
-      '../android/registerNativeModule.js',
-      registerNativeModule
-    );
+    jest.setMock('../android/registerNativeModule.js', registerNativeModule);
 
     const link = require('../link').func;
 
@@ -152,25 +126,32 @@ describe('link', () => {
     });
   });
 
-  it('should register native modules for plugins', (done) => {
+  it('should register native modules for plugins', done => {
     const registerNativeModule = sinon.stub();
-    const dependencyConfig = {ios: {}, android: {}, test: {}, assets: [], commands: {}};
-    const linkPluginConfig = { isInstalled: () => false, register: registerNativeModule };
+    const dependencyConfig = {
+      ios: {},
+      android: {},
+      test: {},
+      assets: [],
+      commands: {},
+    };
+    const linkPluginConfig = {
+      isInstalled: () => false,
+      register: registerNativeModule,
+    };
     const config = {
-      getPlatformConfig: () => ({ ios: {}, android: {}, test: { linkConfig: () => linkPluginConfig }}),
-      getProjectConfig: () => ({ ios: {}, android: {}, test: {}, assets: [] }),
+      getPlatformConfig: () => ({
+        ios: {},
+        android: {},
+        test: {linkConfig: () => linkPluginConfig},
+      }),
+      getProjectConfig: () => ({ios: {}, android: {}, test: {}, assets: []}),
       getDependencyConfig: sinon.stub().returns(dependencyConfig),
     };
 
-    jest.setMock(
-      '../ios/isInstalled.js',
-      sinon.stub().returns(true)
-    );
+    jest.setMock('../ios/isInstalled.js', sinon.stub().returns(true));
 
-    jest.setMock(
-      '../android/isInstalled.js',
-      sinon.stub().returns(true)
-    );
+    jest.setMock('../android/isInstalled.js', sinon.stub().returns(true));
 
     const link = require('../link').func;
 
@@ -180,25 +161,32 @@ describe('link', () => {
     });
   });
 
-  it('should not register native modules for plugins when already installed', (done) => {
+  it('should not register native modules for plugins when already installed', done => {
     const registerNativeModule = sinon.stub();
-    const dependencyConfig = {ios: {}, android: {}, test: {}, assets: [], commands: {}};
-    const linkPluginConfig = { isInstalled: () => true, register: registerNativeModule};
+    const dependencyConfig = {
+      ios: {},
+      android: {},
+      test: {},
+      assets: [],
+      commands: {},
+    };
+    const linkPluginConfig = {
+      isInstalled: () => true,
+      register: registerNativeModule,
+    };
     const config = {
-      getPlatformConfig: () => ({ ios: {}, android: {}, test: { linkConfig: () => linkPluginConfig }}),
-      getProjectConfig: () => ({ ios: {}, android: {}, test: {}, assets: [] }),
+      getPlatformConfig: () => ({
+        ios: {},
+        android: {},
+        test: {linkConfig: () => linkPluginConfig},
+      }),
+      getProjectConfig: () => ({ios: {}, android: {}, test: {}, assets: []}),
       getDependencyConfig: sinon.stub().returns(dependencyConfig),
     };
 
-    jest.setMock(
-      '../ios/isInstalled.js',
-      sinon.stub().returns(true)
-    );
+    jest.setMock('../ios/isInstalled.js', sinon.stub().returns(true));
 
-    jest.setMock(
-      '../android/isInstalled.js',
-      sinon.stub().returns(true)
-    );
+    jest.setMock('../android/isInstalled.js', sinon.stub().returns(true));
 
     const link = require('../link').func;
 
@@ -208,27 +196,23 @@ describe('link', () => {
     });
   });
 
-  it('should run prelink and postlink commands at the appropriate times', (done) => {
+  it('should run prelink and postlink commands at the appropriate times', done => {
     const registerNativeModule = sinon.stub();
     const prelink = sinon.stub().yieldsAsync();
     const postlink = sinon.stub().yieldsAsync();
 
-    jest.setMock(
-      '../ios/registerNativeModule.js',
-      registerNativeModule
-    );
+    jest.setMock('../ios/registerNativeModule.js', registerNativeModule);
 
-    jest.setMock(
-      '../ios/isInstalled.js',
-      sinon.stub().returns(false)
-    );
+    jest.setMock('../ios/isInstalled.js', sinon.stub().returns(false));
 
     const linkConfig = require('../ios');
     const config = {
-      getPlatformConfig: () => ({ ios: { linkConfig: linkConfig }}),
-      getProjectConfig: () => ({ ios: {}, assets: [] }),
+      getPlatformConfig: () => ({ios: {linkConfig: linkConfig}}),
+      getProjectConfig: () => ({ios: {}, assets: []}),
       getDependencyConfig: sinon.stub().returns({
-        ios: {}, assets: [], commands: { prelink, postlink },
+        ios: {},
+        assets: [],
+        commands: {prelink, postlink},
       }),
     };
 
@@ -241,21 +225,18 @@ describe('link', () => {
     });
   });
 
-  it('should copy assets from both project and dependencies projects', (done) => {
+  it('should copy assets from both project and dependencies projects', done => {
     const dependencyAssets = ['Fonts/Font.ttf'];
     const dependencyConfig = {assets: dependencyAssets, ios: {}, commands: {}};
     const projectAssets = ['Fonts/FontC.ttf'];
     const copyAssets = sinon.stub();
 
-    jest.setMock(
-      '../ios/copyAssets.js',
-      copyAssets
-    );
+    jest.setMock('../ios/copyAssets.js', copyAssets);
 
     const linkConfig = require('../ios');
     const config = {
-      getPlatformConfig: () => ({ ios: { linkConfig: linkConfig } }),
-      getProjectConfig: () => ({ ios: {}, assets: projectAssets }),
+      getPlatformConfig: () => ({ios: {linkConfig: linkConfig}}),
+      getProjectConfig: () => ({ios: {}, assets: projectAssets}),
       getDependencyConfig: sinon.stub().returns(dependencyConfig),
     };
 
@@ -264,7 +245,7 @@ describe('link', () => {
     link(['react-native-blur'], config).then(() => {
       expect(copyAssets.calledOnce).toBeTruthy();
       expect(copyAssets.getCall(0).args[0]).toEqual(
-        projectAssets.concat(dependencyAssets)
+        projectAssets.concat(dependencyAssets),
       );
       done();
     });
diff --git a/local-cli/link/__tests__/pods/findLineToAddPod.spec.js b/local-cli/link/__tests__/pods/findLineToAddPod.spec.js
index e065fd406ffe..e0b179a8f943 100644
--- a/local-cli/link/__tests__/pods/findLineToAddPod.spec.js
+++ b/local-cli/link/__tests__/pods/findLineToAddPod.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -19,21 +20,31 @@ const LINE_AFTER_TARGET_IN_TEST_PODFILE = 4;
 describe('pods::findLineToAddPod', () => {
   it('returns null if file is not Podfile', () => {
     const podfile = readPodfile(path.join(PODFILES_PATH, '../Info.plist'));
-    expect(findLineToAddPod(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE)).toBeNull();
+    expect(
+      findLineToAddPod(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE),
+    ).toBeNull();
   });
 
   it('returns correct line number for Simple Podfile', () => {
     const podfile = readPodfile(path.join(PODFILES_PATH, 'PodfileSimple'));
-    expect(findLineToAddPod(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE)).toEqual({ line: 7, indentation: 2 });
+    expect(
+      findLineToAddPod(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE),
+    ).toEqual({line: 7, indentation: 2});
   });
 
   it('returns correct line number for Podfile with target', () => {
     const podfile = readPodfile(path.join(PODFILES_PATH, 'PodfileWithTarget'));
-    expect(findLineToAddPod(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE)).toEqual({ line: 21, indentation: 2 });
+    expect(
+      findLineToAddPod(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE),
+    ).toEqual({line: 21, indentation: 2});
   });
 
   it('returns correct line number for Podfile with function', () => {
-    const podfile = readPodfile(path.join(PODFILES_PATH, 'PodfileWithFunction'));
-    expect(findLineToAddPod(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE)).toEqual({ line: 26, indentation: 2 });
+    const podfile = readPodfile(
+      path.join(PODFILES_PATH, 'PodfileWithFunction'),
+    );
+    expect(
+      findLineToAddPod(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE),
+    ).toEqual({line: 26, indentation: 2});
   });
 });
diff --git a/local-cli/link/__tests__/pods/findMarkedLinesInPodfile.spec.js b/local-cli/link/__tests__/pods/findMarkedLinesInPodfile.spec.js
index f3b6880949f4..7dd2b77af939 100644
--- a/local-cli/link/__tests__/pods/findMarkedLinesInPodfile.spec.js
+++ b/local-cli/link/__tests__/pods/findMarkedLinesInPodfile.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -24,12 +25,19 @@ describe('pods::findMarkedLinesInPodfile', () => {
 
   it('returns empty array for Simple Podfile', () => {
     const podfile = readPodfile(path.join(PODFILES_PATH, 'PodfileSimple'));
-    expect(findMarkedLinesInPodfile(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE)).toEqual([]);
+    expect(
+      findMarkedLinesInPodfile(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE),
+    ).toEqual([]);
   });
 
   it('returns correct line numbers for Podfile with marker', () => {
     const podfile = readPodfile(path.join(PODFILES_PATH, 'PodfileWithMarkers'));
-    const expectedObject = [{ line: 18, indentation: 2 }, { line: 31, indentation: 4 }];
-    expect(findMarkedLinesInPodfile(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE)).toEqual(expectedObject);
+    const expectedObject = [
+      {line: 18, indentation: 2},
+      {line: 31, indentation: 4},
+    ];
+    expect(
+      findMarkedLinesInPodfile(podfile, LINE_AFTER_TARGET_IN_TEST_PODFILE),
+    ).toEqual(expectedObject);
   });
 });
diff --git a/local-cli/link/__tests__/pods/findPodTargetLine.spec.js b/local-cli/link/__tests__/pods/findPodTargetLine.spec.js
index d64a2513c7cc..04b142856f82 100644
--- a/local-cli/link/__tests__/pods/findPodTargetLine.spec.js
+++ b/local-cli/link/__tests__/pods/findPodTargetLine.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
diff --git a/local-cli/link/__tests__/pods/isInstalled.spec.js b/local-cli/link/__tests__/pods/isInstalled.spec.js
index abda0fbe32d6..ba9b3f037538 100644
--- a/local-cli/link/__tests__/pods/isInstalled.spec.js
+++ b/local-cli/link/__tests__/pods/isInstalled.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -16,26 +17,26 @@ const PODFILES_PATH = path.join(__dirname, '../../__fixtures__/pods');
 
 describe('pods::isInstalled', () => {
   it('returns false if pod is missing', () => {
-    const project = { podfile: path.join(PODFILES_PATH, 'PodfileSimple') };
-    const podspecName = { podspec: 'NotExisting' };
+    const project = {podfile: path.join(PODFILES_PATH, 'PodfileSimple')};
+    const podspecName = {podspec: 'NotExisting'};
     expect(isInstalled(project, podspecName)).toBe(false);
   });
 
   it('returns true for existing pod with version number', () => {
-    const project = { podfile: path.join(PODFILES_PATH, 'PodfileSimple') };
-    const podspecName = { podspec: 'TestPod' };
+    const project = {podfile: path.join(PODFILES_PATH, 'PodfileSimple')};
+    const podspecName = {podspec: 'TestPod'};
     expect(isInstalled(project, podspecName)).toBe(true);
   });
 
   it('returns true for existing pod with path', () => {
-    const project = { podfile: path.join(PODFILES_PATH, 'PodfileWithTarget') };
-    const podspecName = { podspec: 'Yoga' };
+    const project = {podfile: path.join(PODFILES_PATH, 'PodfileWithTarget')};
+    const podspecName = {podspec: 'Yoga'};
     expect(isInstalled(project, podspecName)).toBe(true);
   });
 
   it('returns true for existing pod with multiline definition', () => {
-    const project = { podfile: path.join(PODFILES_PATH, 'PodfileWithFunction') };
-    const podspecName = { podspec: 'React' };
+    const project = {podfile: path.join(PODFILES_PATH, 'PodfileWithFunction')};
+    const podspecName = {podspec: 'React'};
     expect(isInstalled(project, podspecName)).toBe(true);
   });
 });
diff --git a/local-cli/link/__tests__/pods/removePodEntry.spec.js b/local-cli/link/__tests__/pods/removePodEntry.spec.js
index 5c2f4a951f02..576664970ba3 100644
--- a/local-cli/link/__tests__/pods/removePodEntry.spec.js
+++ b/local-cli/link/__tests__/pods/removePodEntry.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -17,21 +18,25 @@ const PODFILES_PATH = path.join(__dirname, '../../__fixtures__/pods');
 
 describe('pods::removePodEntry', () => {
   it('should remove one line from Podfile with TestPod', () => {
-    const { podfileContent, podLinesCount } = readTestPodFile('PodfileSimple');
+    const {podfileContent, podLinesCount} = readTestPodFile('PodfileSimple');
     const podFileWithRemoved = removePodEntry(podfileContent, 'TestPod');
     const newLineCount = podFileWithRemoved.split('\n').length;
     expect(newLineCount).toBe(podLinesCount - 1);
   });
 
   it('should remove one line from Podfile with Yoga', () => {
-    const { podfileContent, podLinesCount } = readTestPodFile('PodfileWithTarget');
+    const {podfileContent, podLinesCount} = readTestPodFile(
+      'PodfileWithTarget',
+    );
     const podFileWithRemoved = removePodEntry(podfileContent, 'Yoga');
     const newLineCount = podFileWithRemoved.split('\n').length;
     expect(newLineCount).toBe(podLinesCount - 1);
   });
 
   it('should remove whole reference to React pod from Podfile', () => {
-    const { podfileContent, podLinesCount } = readTestPodFile('PodfileWithTarget');
+    const {podfileContent, podLinesCount} = readTestPodFile(
+      'PodfileWithTarget',
+    );
     const podFileWithRemoved = removePodEntry(podfileContent, 'React');
     const newLineCount = podFileWithRemoved.split('\n').length;
     expect(newLineCount).toBe(podLinesCount - 9);
@@ -40,5 +45,8 @@ describe('pods::removePodEntry', () => {
 
 function readTestPodFile(fileName) {
   const podfileLines = readPodfile(path.join(PODFILES_PATH, fileName));
-  return { podfileContent: podfileLines.join('\n'), podLinesCount: podfileLines.length };
+  return {
+    podfileContent: podfileLines.join('\n'),
+    podLinesCount: podfileLines.length,
+  };
 }
diff --git a/local-cli/link/__tests__/promiseWaterfall.spec.js b/local-cli/link/__tests__/promiseWaterfall.spec.js
index d34aa6502177..3f9adc55a2c9 100644
--- a/local-cli/link/__tests__/promiseWaterfall.spec.js
+++ b/local-cli/link/__tests__/promiseWaterfall.spec.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -13,8 +14,7 @@ const sinon = require('sinon');
 const promiseWaterfall = require('../promiseWaterfall');
 
 describe('promiseWaterfall', () => {
-
-  it('should run promises in a sequence', (done) => {
+  it('should run promises in a sequence', done => {
     const tasks = [sinon.stub(), sinon.stub()];
 
     promiseWaterfall(tasks).then(() => {
@@ -23,7 +23,7 @@ describe('promiseWaterfall', () => {
     });
   });
 
-  it('should resolve with last promise value', (done) => {
+  it('should resolve with last promise value', done => {
     const tasks = [sinon.stub().returns(1), sinon.stub().returns(2)];
 
     promiseWaterfall(tasks).then(value => {
@@ -32,7 +32,7 @@ describe('promiseWaterfall', () => {
     });
   });
 
-  it('should stop the sequence when one of promises is rejected', (done) => {
+  it('should stop the sequence when one of promises is rejected', done => {
     const error = new Error();
     const tasks = [sinon.stub().throws(error), sinon.stub().returns(2)];
 
@@ -42,5 +42,4 @@ describe('promiseWaterfall', () => {
       done();
     });
   });
-
 });
diff --git a/local-cli/link/android/copyAssets.js b/local-cli/link/android/copyAssets.js
index f4bd67ff6a1e..dbaeaa24e93e 100644
--- a/local-cli/link/android/copyAssets.js
+++ b/local-cli/link/android/copyAssets.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs-extra');
@@ -19,6 +21,9 @@ module.exports = function copyAssetsAndroid(files, project) {
   const assets = groupFilesByType(files);
 
   (assets.font || []).forEach(asset =>
-    fs.copySync(asset, path.join(project.assetsPath, 'fonts', path.basename(asset)))
+    fs.copySync(
+      asset,
+      path.join(project.assetsPath, 'fonts', path.basename(asset)),
+    ),
   );
 };
diff --git a/local-cli/link/android/fs.js b/local-cli/link/android/fs.js
index 9ace2aba924f..51ee62136b42 100644
--- a/local-cli/link/android/fs.js
+++ b/local-cli/link/android/fs.js
@@ -3,13 +3,15 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs-extra');
 
-exports.readFile = (file) =>
-  () => fs.readFileSync(file, 'utf8');
+exports.readFile = file => () => fs.readFileSync(file, 'utf8');
 
-exports.writeFile = (file, content) => content ?
-  fs.writeFileSync(file, content, 'utf8') :
-  (c) => fs.writeFileSync(file, c, 'utf8');
+exports.writeFile = (file, content) =>
+  content
+    ? fs.writeFileSync(file, content, 'utf8')
+    : c => fs.writeFileSync(file, c, 'utf8');
diff --git a/local-cli/link/android/index.js b/local-cli/link/android/index.js
index 986ec59450b8..3eacc4175022 100644
--- a/local-cli/link/android/index.js
+++ b/local-cli/link/android/index.js
@@ -1,9 +1,11 @@
+/** @format */
+
 module.exports = function() {
   return {
     isInstalled: require('./isInstalled'),
     register: require('./registerNativeModule'),
     unregister: require('./unregisterNativeModule'),
     copyAssets: require('./copyAssets'),
-    unlinkAssets: require('./unlinkAssets')
+    unlinkAssets: require('./unlinkAssets'),
   };
 };
diff --git a/local-cli/link/android/isInstalled.js b/local-cli/link/android/isInstalled.js
index 2accb2a0160d..43a53396e922 100644
--- a/local-cli/link/android/isInstalled.js
+++ b/local-cli/link/android/isInstalled.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs');
diff --git a/local-cli/link/android/patches/applyParams.js b/local-cli/link/android/patches/applyParams.js
index 5f57f3cb8fa8..2fd193ad6852 100644
--- a/local-cli/link/android/patches/applyParams.js
+++ b/local-cli/link/android/patches/applyParams.js
@@ -3,19 +3,16 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const toCamelCase = require('lodash').camelCase;
 
 module.exports = function applyParams(str, params, prefix) {
-  return str.replace(
-    /\$\{(\w+)\}/g,
-    (pattern, param) => {
-      const name = toCamelCase(prefix) + '_' + param;
+  return str.replace(/\$\{(\w+)\}/g, (pattern, param) => {
+    const name = toCamelCase(prefix) + '_' + param;
 
-      return params[param]
-        ? `getResources().getString(R.string.${name})`
-        : null;
-    }
-  );
+    return params[param] ? `getResources().getString(R.string.${name})` : null;
+  });
 };
diff --git a/local-cli/link/android/patches/applyPatch.js b/local-cli/link/android/patches/applyPatch.js
index df9680c50723..05393a894722 100644
--- a/local-cli/link/android/patches/applyPatch.js
+++ b/local-cli/link/android/patches/applyPatch.js
@@ -3,13 +3,17 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs');
 
 module.exports = function applyPatch(file, patch) {
-  fs.writeFileSync(file, fs
-    .readFileSync(file, 'utf8')
-    .replace(patch.pattern, match => `${match}${patch.patch}`)
+  fs.writeFileSync(
+    file,
+    fs
+      .readFileSync(file, 'utf8')
+      .replace(patch.pattern, match => `${match}${patch.patch}`),
   );
 };
diff --git a/local-cli/link/android/patches/makeBuildPatch.js b/local-cli/link/android/patches/makeBuildPatch.js
index 3c4969af22d8..58512183fb16 100644
--- a/local-cli/link/android/patches/makeBuildPatch.js
+++ b/local-cli/link/android/patches/makeBuildPatch.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const normalizeProjectName = require('./normalizeProjectName');
@@ -10,12 +12,12 @@ const normalizeProjectName = require('./normalizeProjectName');
 module.exports = function makeBuildPatch(name) {
   const normalizedProjectName = normalizeProjectName(name);
   const installPattern = new RegExp(
-    `\\s{4}(compile)(\\(|\\s)(project)\\(\\\':${normalizedProjectName}\\\'\\)(\\)|\\s)`
+    `\\s{4}(compile)(\\(|\\s)(project)\\(\\\':${normalizedProjectName}\\\'\\)(\\)|\\s)`,
   );
 
   return {
     installPattern,
     pattern: /[^ \t]dependencies {\n/,
-    patch: `    compile project(':${normalizedProjectName}')\n`
+    patch: `    compile project(':${normalizedProjectName}')\n`,
   };
 };
diff --git a/local-cli/link/android/patches/makeImportPatch.js b/local-cli/link/android/patches/makeImportPatch.js
index 9cb9aaddc995..90bd0f50326b 100644
--- a/local-cli/link/android/patches/makeImportPatch.js
+++ b/local-cli/link/android/patches/makeImportPatch.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 module.exports = function makeImportPatch(packageImportPath) {
diff --git a/local-cli/link/android/patches/makePackagePatch.js b/local-cli/link/android/patches/makePackagePatch.js
index 054c2ac5649b..29c01b76bb84 100644
--- a/local-cli/link/android/patches/makePackagePatch.js
+++ b/local-cli/link/android/patches/makePackagePatch.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const applyParams = require('./applyParams');
diff --git a/local-cli/link/android/patches/makeSettingsPatch.js b/local-cli/link/android/patches/makeSettingsPatch.js
index a39de2be17dc..76885f706606 100644
--- a/local-cli/link/android/patches/makeSettingsPatch.js
+++ b/local-cli/link/android/patches/makeSettingsPatch.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const path = require('path');
@@ -10,14 +12,17 @@ const normalizeProjectName = require('./normalizeProjectName');
 
 const isWin = process.platform === 'win32';
 
-module.exports = function makeSettingsPatch(name, androidConfig, projectConfig) {
+module.exports = function makeSettingsPatch(
+  name,
+  androidConfig,
+  projectConfig,
+) {
   var projectDir = path.relative(
     path.dirname(projectConfig.settingsGradlePath),
-    androidConfig.sourceDir
+    androidConfig.sourceDir,
   );
   const normalizedProjectName = normalizeProjectName(name);
 
-
   /*
    * Fix for Windows
    * Backslashes is the escape character and will result in
@@ -30,7 +35,8 @@ module.exports = function makeSettingsPatch(name, androidConfig, projectConfig)
 
   return {
     pattern: '\n',
-    patch: `include ':${normalizedProjectName}'\n` +
+    patch:
+      `include ':${normalizedProjectName}'\n` +
       `project(':${normalizedProjectName}').projectDir = ` +
       `new File(rootProject.projectDir, '${projectDir}')\n`,
   };
diff --git a/local-cli/link/android/patches/makeStringsPatch.js b/local-cli/link/android/patches/makeStringsPatch.js
index 281582afb971..a6b40e46f2ca 100644
--- a/local-cli/link/android/patches/makeStringsPatch.js
+++ b/local-cli/link/android/patches/makeStringsPatch.js
@@ -3,21 +3,22 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const toCamelCase = require('lodash').camelCase;
 
 module.exports = function makeStringsPatch(params, prefix) {
-  const values = Object.keys(params)
-    .map(param => {
-      const name = toCamelCase(prefix) + '_' + param;
-      return '    ' +
-        `<string moduleConfig="true" name="${name}">${params[param]}</string>`;
-    });
+  const values = Object.keys(params).map(param => {
+    const name = toCamelCase(prefix) + '_' + param;
+    return (
+      '    ' +
+      `<string moduleConfig="true" name="${name}">${params[param]}</string>`
+    );
+  });
 
-  const patch = values.length > 0
-    ? values.join('\n') + '\n'
-    : '';
+  const patch = values.length > 0 ? values.join('\n') + '\n' : '';
 
   return {
     pattern: '<resources>\n',
diff --git a/local-cli/link/android/patches/normalizeProjectName.js b/local-cli/link/android/patches/normalizeProjectName.js
index fd52d1bb108b..97dae55ededc 100644
--- a/local-cli/link/android/patches/normalizeProjectName.js
+++ b/local-cli/link/android/patches/normalizeProjectName.js
@@ -1,3 +1,4 @@
+/** @format */
 
 module.exports = function normalizeProjectName(name) {
   return name.replace(/\//g, '_');
diff --git a/local-cli/link/android/patches/revokePatch.js b/local-cli/link/android/patches/revokePatch.js
index 9437e56cb088..14972e46ed96 100644
--- a/local-cli/link/android/patches/revokePatch.js
+++ b/local-cli/link/android/patches/revokePatch.js
@@ -3,13 +3,15 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs');
 
 module.exports = function revokePatch(file, patch) {
-  fs.writeFileSync(file, fs
-    .readFileSync(file, 'utf8')
-    .replace(patch.patch, '')
+  fs.writeFileSync(
+    file,
+    fs.readFileSync(file, 'utf8').replace(patch.patch, ''),
   );
 };
diff --git a/local-cli/link/android/registerNativeModule.js b/local-cli/link/android/registerNativeModule.js
index 0ce77c4e6ed4..f73932c02354 100644
--- a/local-cli/link/android/registerNativeModule.js
+++ b/local-cli/link/android/registerNativeModule.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const applyPatch = require('./patches/applyPatch');
@@ -16,13 +18,13 @@ module.exports = function registerNativeAndroidModule(
   name,
   androidConfig,
   params,
-  projectConfig
+  projectConfig,
 ) {
   const buildPatch = makeBuildPatch(name);
 
   applyPatch(
     projectConfig.settingsGradlePath,
-    makeSettingsPatch(name, androidConfig, projectConfig)
+    makeSettingsPatch(name, androidConfig, projectConfig),
   );
 
   applyPatch(projectConfig.buildGradlePath, buildPatch);
@@ -30,11 +32,11 @@ module.exports = function registerNativeAndroidModule(
 
   applyPatch(
     projectConfig.mainFilePath,
-    makePackagePatch(androidConfig.packageInstance, params, name)
+    makePackagePatch(androidConfig.packageInstance, params, name),
   );
 
   applyPatch(
     projectConfig.mainFilePath,
-    makeImportPatch(androidConfig.packageImportPath)
+    makeImportPatch(androidConfig.packageImportPath),
   );
 };
diff --git a/local-cli/link/android/unlinkAssets.js b/local-cli/link/android/unlinkAssets.js
index b0eeefed93c3..81e90c5e71ae 100644
--- a/local-cli/link/android/unlinkAssets.js
+++ b/local-cli/link/android/unlinkAssets.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs-extra');
@@ -18,8 +20,12 @@ const groupFilesByType = require('../groupFilesByType');
 module.exports = function unlinkAssetsAndroid(files, project) {
   const assets = groupFilesByType(files);
 
-  (assets.font || []).forEach((file) => {
-    const filePath = path.join(project.assetsPath, 'fonts', path.basename(file));
+  (assets.font || []).forEach(file => {
+    const filePath = path.join(
+      project.assetsPath,
+      'fonts',
+      path.basename(file),
+    );
     if (fs.existsSync(filePath)) {
       fs.unlinkSync(filePath);
     }
diff --git a/local-cli/link/android/unregisterNativeModule.js b/local-cli/link/android/unregisterNativeModule.js
index b6b8d1665318..880070afa503 100644
--- a/local-cli/link/android/unregisterNativeModule.js
+++ b/local-cli/link/android/unregisterNativeModule.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs');
@@ -18,7 +20,7 @@ const makePackagePatch = require('./patches/makePackagePatch');
 module.exports = function unregisterNativeAndroidModule(
   name,
   androidConfig,
-  projectConfig
+  projectConfig,
 ) {
   const buildPatch = makeBuildPatch(name);
   const strings = fs.readFileSync(projectConfig.stringsPath, 'utf8');
@@ -28,12 +30,12 @@ module.exports = function unregisterNativeAndroidModule(
     /moduleConfig="true" name="(\w+)">(.*)</g,
     (_, param, value) => {
       params[param.slice(toCamelCase(name).length + 1)] = value;
-    }
+    },
   );
 
   revokePatch(
     projectConfig.settingsGradlePath,
-    makeSettingsPatch(name, androidConfig, projectConfig)
+    makeSettingsPatch(name, androidConfig, projectConfig),
   );
 
   revokePatch(projectConfig.buildGradlePath, buildPatch);
@@ -41,11 +43,11 @@ module.exports = function unregisterNativeAndroidModule(
 
   revokePatch(
     projectConfig.mainFilePath,
-    makePackagePatch(androidConfig.packageInstance, params, name)
+    makePackagePatch(androidConfig.packageInstance, params, name),
   );
 
   revokePatch(
     projectConfig.mainFilePath,
-    makeImportPatch(androidConfig.packageImportPath)
+    makeImportPatch(androidConfig.packageImportPath),
   );
 };
diff --git a/local-cli/link/commandStub.js b/local-cli/link/commandStub.js
index 13078bd3404f..768a94f98d32 100644
--- a/local-cli/link/commandStub.js
+++ b/local-cli/link/commandStub.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
-module.exports = (cb) => cb();
+module.exports = cb => cb();
diff --git a/local-cli/link/getDependencyConfig.js b/local-cli/link/getDependencyConfig.js
index 71ce26590906..19c54324e77d 100644
--- a/local-cli/link/getDependencyConfig.js
+++ b/local-cli/link/getDependencyConfig.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
diff --git a/local-cli/link/getProjectDependencies.js b/local-cli/link/getProjectDependencies.js
index 1d5b0781a9b8..c078aab1a372 100644
--- a/local-cli/link/getProjectDependencies.js
+++ b/local-cli/link/getProjectDependencies.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const path = require('path');
@@ -12,5 +14,7 @@ const path = require('path');
  */
 module.exports = function getProjectDependencies() {
   const pjson = require(path.join(process.cwd(), './package.json'));
-  return Object.keys(pjson.dependencies || {}).filter(name => name !== 'react-native');
+  return Object.keys(pjson.dependencies || {}).filter(
+    name => name !== 'react-native',
+  );
 };
diff --git a/local-cli/link/groupFilesByType.js b/local-cli/link/groupFilesByType.js
index 786c71532e9f..47aa7f6b52ed 100644
--- a/local-cli/link/groupFilesByType.js
+++ b/local-cli/link/groupFilesByType.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const groupBy = require('lodash').groupBy;
diff --git a/local-cli/link/ios/addFileToProject.js b/local-cli/link/ios/addFileToProject.js
index 168220f80381..d3a560529c04 100644
--- a/local-cli/link/ios/addFileToProject.js
+++ b/local-cli/link/ios/addFileToProject.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const PbxFile = require('xcode/lib/pbxFile');
diff --git a/local-cli/link/ios/addProjectToLibraries.js b/local-cli/link/ios/addProjectToLibraries.js
index 045697dec1f7..e15c8baf410e 100644
--- a/local-cli/link/ios/addProjectToLibraries.js
+++ b/local-cli/link/ios/addProjectToLibraries.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
diff --git a/local-cli/link/ios/addSharedLibraries.js b/local-cli/link/ios/addSharedLibraries.js
index a0c6f16e649d..e12d913ba236 100644
--- a/local-cli/link/ios/addSharedLibraries.js
+++ b/local-cli/link/ios/addSharedLibraries.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const createGroupWithMessage = require('./createGroupWithMessage');
@@ -18,6 +20,6 @@ module.exports = function addSharedLibraries(project, libraries) {
   const target = project.getFirstTarget().uuid;
 
   for (var name of libraries) {
-    project.addFramework(name, { target });
+    project.addFramework(name, {target});
   }
 };
diff --git a/local-cli/link/ios/addToHeaderSearchPaths.js b/local-cli/link/ios/addToHeaderSearchPaths.js
index 579007ecf81c..dd3923451b34 100644
--- a/local-cli/link/ios/addToHeaderSearchPaths.js
+++ b/local-cli/link/ios/addToHeaderSearchPaths.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const mapHeaderSearchPaths = require('./mapHeaderSearchPaths');
diff --git a/local-cli/link/ios/common/isInstalled.js b/local-cli/link/ios/common/isInstalled.js
index 69bcd8bdf32d..71af956bdcff 100644
--- a/local-cli/link/ios/common/isInstalled.js
+++ b/local-cli/link/ios/common/isInstalled.js
@@ -1,6 +1,11 @@
+/** @format */
+
 const isInstalledIOS = require('../isInstalled');
 const isInstalledPods = require('../../pods/isInstalled');
 
 module.exports = function isInstalled(projectConfig, name, dependencyConfig) {
-  return isInstalledIOS(projectConfig, dependencyConfig) || isInstalledPods(projectConfig, dependencyConfig);
+  return (
+    isInstalledIOS(projectConfig, dependencyConfig) ||
+    isInstalledPods(projectConfig, dependencyConfig)
+  );
 };
diff --git a/local-cli/link/ios/common/registerNativeModule.js b/local-cli/link/ios/common/registerNativeModule.js
index 38ce59606982..72057712fe0e 100644
--- a/local-cli/link/ios/common/registerNativeModule.js
+++ b/local-cli/link/ios/common/registerNativeModule.js
@@ -1,3 +1,5 @@
+/** @format */
+
 const registerDependencyIOS = require('../registerNativeModule');
 const registerDependencyPods = require('../../pods/registerNativeModule');
 
@@ -5,12 +7,11 @@ module.exports = function registerNativeModule(
   name,
   dependencyConfig,
   params,
-  projectConfig
+  projectConfig,
 ) {
   if (projectConfig.podfile && dependencyConfig.podspec) {
     registerDependencyPods(name, dependencyConfig, projectConfig);
-  }
-  else {
+  } else {
     registerDependencyIOS(dependencyConfig, projectConfig);
   }
 };
diff --git a/local-cli/link/ios/common/unregisterNativeModule.js b/local-cli/link/ios/common/unregisterNativeModule.js
index e6d34ada4cce..dbf7bc4147db 100644
--- a/local-cli/link/ios/common/unregisterNativeModule.js
+++ b/local-cli/link/ios/common/unregisterNativeModule.js
@@ -1,3 +1,5 @@
+/** @format */
+
 const compact = require('lodash').compact;
 const isInstalledIOS = require('../isInstalled');
 const isInstalledPods = require('../../pods/isInstalled');
@@ -8,15 +10,14 @@ module.exports = function unregisterNativeModule(
   name,
   dependencyConfig,
   projectConfig,
-  otherDependencies
+  otherDependencies,
 ) {
   const isIosInstalled = isInstalledIOS(projectConfig, dependencyConfig);
   const isPodInstalled = isInstalledPods(projectConfig, dependencyConfig);
   if (isIosInstalled) {
     const iOSDependencies = compact(otherDependencies.map(d => d.config.ios));
     unregisterDependencyIOS(dependencyConfig, projectConfig, iOSDependencies);
-  }
-  else if (isPodInstalled) {
+  } else if (isPodInstalled) {
     unregisterDependencyPods(dependencyConfig, projectConfig);
   }
 };
diff --git a/local-cli/link/ios/copyAssets.js b/local-cli/link/ios/copyAssets.js
index 8f6d2b86eb13..0510569900e0 100644
--- a/local-cli/link/ios/copyAssets.js
+++ b/local-cli/link/ios/copyAssets.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs-extra');
@@ -28,12 +30,11 @@ module.exports = function linkAssetsIOS(files, projectConfig) {
   function addResourceFile(f) {
     return (f || [])
       .map(asset =>
-        project.addResourceFile(
-          path.relative(projectConfig.sourceDir, asset),
-          { target: project.getFirstTarget().uuid }
-        )
+        project.addResourceFile(path.relative(projectConfig.sourceDir, asset), {
+          target: project.getFirstTarget().uuid,
+        }),
       )
-      .filter(file => file)   // xcode returns false if file is already there
+      .filter(file => file) // xcode returns false if file is already there
       .map(file => file.basename);
   }
 
@@ -41,14 +42,11 @@ module.exports = function linkAssetsIOS(files, projectConfig) {
 
   const fonts = addResourceFile(assets.font);
 
-  const existingFonts = (plist.UIAppFonts || []);
+  const existingFonts = plist.UIAppFonts || [];
   const allFonts = [...existingFonts, ...fonts];
   plist.UIAppFonts = Array.from(new Set(allFonts)); // use Set to dedupe w/existing
 
-  fs.writeFileSync(
-    projectConfig.pbxprojPath,
-    project.writeSync()
-  );
+  fs.writeFileSync(projectConfig.pbxprojPath, project.writeSync());
 
   writePlist(project, projectConfig.sourceDir, plist);
 };
diff --git a/local-cli/link/ios/createGroup.js b/local-cli/link/ios/createGroup.js
index 62f79e1c9742..4e9cbccc4188 100644
--- a/local-cli/link/ios/createGroup.js
+++ b/local-cli/link/ios/createGroup.js
@@ -3,11 +3,14 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const getGroup = require('./getGroup');
 
-const hasGroup = (pbxGroup, name) => pbxGroup.children.find(group => group.comment === name);
+const hasGroup = (pbxGroup, name) =>
+  pbxGroup.children.find(group => group.comment === name);
 
 /**
  * Given project and path of the group, it deeply creates a given group
@@ -16,19 +19,16 @@ const hasGroup = (pbxGroup, name) => pbxGroup.children.find(group => group.comme
  * Returns newly created group
  */
 module.exports = function createGroup(project, path) {
-  return path.split('/').reduce(
-    (group, name) => {
-      if (!hasGroup(group, name)) {
-        const uuid = project.pbxCreateGroup(name, '""');
+  return path.split('/').reduce((group, name) => {
+    if (!hasGroup(group, name)) {
+      const uuid = project.pbxCreateGroup(name, '""');
 
-        group.children.push({
-          value: uuid,
-          comment: name,
-        });
-      }
+      group.children.push({
+        value: uuid,
+        comment: name,
+      });
+    }
 
-      return project.pbxGroupByName(name);
-    },
-    getGroup(project)
-  );
+    return project.pbxGroupByName(name);
+  }, getGroup(project));
 };
diff --git a/local-cli/link/ios/createGroupWithMessage.js b/local-cli/link/ios/createGroupWithMessage.js
index 4b598940da95..7d9f1aaa05dd 100644
--- a/local-cli/link/ios/createGroupWithMessage.js
+++ b/local-cli/link/ios/createGroupWithMessage.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const log = require('npmlog');
@@ -24,7 +26,7 @@ module.exports = function createGroupWithMessage(project, path) {
 
     log.warn(
       'ERRGROUP',
-      `Group '${path}' does not exist in your Xcode project. We have created it automatically for you.`
+      `Group '${path}' does not exist in your Xcode project. We have created it automatically for you.`,
     );
   }
 
diff --git a/local-cli/link/ios/getBuildProperty.js b/local-cli/link/ios/getBuildProperty.js
index bb1c7b78b88f..074e37816e92 100644
--- a/local-cli/link/ios/getBuildProperty.js
+++ b/local-cli/link/ios/getBuildProperty.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -18,8 +20,12 @@
  */
 module.exports = function getBuildProperty(project, prop) {
   const target = project.getFirstTarget().firstTarget;
-  const config = project.pbxXCConfigurationList()[target.buildConfigurationList];
-  const buildSection = project.pbxXCBuildConfigurationSection()[config.buildConfigurations[0].value];
+  const config = project.pbxXCConfigurationList()[
+    target.buildConfigurationList
+  ];
+  const buildSection = project.pbxXCBuildConfigurationSection()[
+    config.buildConfigurations[0].value
+  ];
 
   return buildSection.buildSettings[prop];
 };
diff --git a/local-cli/link/ios/getGroup.js b/local-cli/link/ios/getGroup.js
index c66205be0117..fcbfbf16da83 100644
--- a/local-cli/link/ios/getGroup.js
+++ b/local-cli/link/ios/getGroup.js
@@ -3,11 +3,14 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
-const getFirstProject = (project) => project.getFirstProject().firstProject;
+const getFirstProject = project => project.getFirstProject().firstProject;
 
-const findGroup = (group, name) => group.children.find(group => group.comment === name);
+const findGroup = (group, name) =>
+  group.children.find(group => group.comment === name);
 
 /**
  * Returns group from .xcodeproj if one exists, null otherwise
diff --git a/local-cli/link/ios/getHeaderSearchPath.js b/local-cli/link/ios/getHeaderSearchPath.js
index c5f2572c6221..74246abafb60 100644
--- a/local-cli/link/ios/getHeaderSearchPath.js
+++ b/local-cli/link/ios/getHeaderSearchPath.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const path = require('path');
@@ -19,19 +21,19 @@ const last = require('lodash').last;
  *
  * Check `getHeaderSearchPath.spec.js` for more use-cases.
  */
-const getOuterDirectory = (directories) =>
+const getOuterDirectory = directories =>
   directories.reduce((topDir, currentDir) => {
     const currentFolders = currentDir.split(path.sep);
     const topMostFolders = topDir.split(path.sep);
 
-    if (currentFolders.length === topMostFolders.length
-      && last(currentFolders) !== last(topMostFolders)) {
+    if (
+      currentFolders.length === topMostFolders.length &&
+      last(currentFolders) !== last(topMostFolders)
+    ) {
       return currentFolders.slice(0, -1).join(path.sep);
     }
 
-    return currentFolders.length < topMostFolders.length
-      ? currentDir
-      : topDir;
+    return currentFolders.length < topMostFolders.length ? currentDir : topDir;
   });
 
 /**
@@ -49,11 +51,12 @@ const getOuterDirectory = (directories) =>
  * every folder of it to locate correct headers.
  */
 module.exports = function getHeaderSearchPath(sourceDir, headers) {
-  const directories = union(
-    headers.map(path.dirname)
-  );
+  const directories = union(headers.map(path.dirname));
 
   return directories.length === 1
     ? `"$(SRCROOT)${path.sep}${path.relative(sourceDir, directories[0])}"`
-    : `"$(SRCROOT)${path.sep}${path.relative(sourceDir, getOuterDirectory(directories))}/**"`;
+    : `"$(SRCROOT)${path.sep}${path.relative(
+        sourceDir,
+        getOuterDirectory(directories),
+      )}/**"`;
 };
diff --git a/local-cli/link/ios/getHeadersInFolder.js b/local-cli/link/ios/getHeadersInFolder.js
index a4c2250ab47c..c63c450c767f 100644
--- a/local-cli/link/ios/getHeadersInFolder.js
+++ b/local-cli/link/ios/getHeadersInFolder.js
@@ -3,12 +3,19 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const glob = require('glob');
 const path = require('path');
 
-const GLOB_EXCLUDE_PATTERN = ['node_modules/**', 'Pods/**', 'Examples/**', 'examples/**'];
+const GLOB_EXCLUDE_PATTERN = [
+  'node_modules/**',
+  'Pods/**',
+  'Examples/**',
+  'examples/**',
+];
 
 /**
  * Given folder, it returns an array of all header files
diff --git a/local-cli/link/ios/getPlist.js b/local-cli/link/ios/getPlist.js
index 61c877258e90..3948e8d5ec79 100644
--- a/local-cli/link/ios/getPlist.js
+++ b/local-cli/link/ios/getPlist.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const plistParser = require('plist');
@@ -21,7 +23,5 @@ module.exports = function getPlist(project, sourceDir) {
     return null;
   }
 
-  return plistParser.parse(
-    fs.readFileSync(plistPath, 'utf-8')
-  );
+  return plistParser.parse(fs.readFileSync(plistPath, 'utf-8'));
 };
diff --git a/local-cli/link/ios/getPlistPath.js b/local-cli/link/ios/getPlistPath.js
index 0609f5f581f9..72c6be75d176 100644
--- a/local-cli/link/ios/getPlistPath.js
+++ b/local-cli/link/ios/getPlistPath.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const path = require('path');
@@ -17,6 +19,6 @@ module.exports = function getPlistPath(project, sourceDir) {
 
   return path.join(
     sourceDir,
-    plistFile.replace(/"/g, '').replace('$(SRCROOT)', '')
+    plistFile.replace(/"/g, '').replace('$(SRCROOT)', ''),
   );
 };
diff --git a/local-cli/link/ios/getProducts.js b/local-cli/link/ios/getProducts.js
index 7e24f15826be..dd0b0431938e 100644
--- a/local-cli/link/ios/getProducts.js
+++ b/local-cli/link/ios/getProducts.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -13,7 +15,6 @@
 module.exports = function getProducts(project) {
   return project
     .pbxGroupByName('Products')
-    .children
-    .map(c => c.comment)
+    .children.map(c => c.comment)
     .filter(c => c.indexOf('.a') > -1);
 };
diff --git a/local-cli/link/ios/getTargets.js b/local-cli/link/ios/getTargets.js
index 784eed2177f3..b81145a5e987 100644
--- a/local-cli/link/ios/getTargets.js
+++ b/local-cli/link/ios/getTargets.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -13,15 +15,23 @@ module.exports = function getTargets(project) {
   let nativeTargetSection = project.pbxNativeTargetSection();
   return targets.map(function(target) {
     let key = target.value;
-    let configurationListId = project.pbxNativeTargetSection()[key].buildConfigurationList;
-    let configurationList = project.pbxXCConfigurationList()[configurationListId];
+    let configurationListId = project.pbxNativeTargetSection()[key]
+      .buildConfigurationList;
+    let configurationList = project.pbxXCConfigurationList()[
+      configurationListId
+    ];
     let buildConfigurationId = configurationList.buildConfigurations[0].value;
-    let buildConfiguration = project.pbxXCBuildConfigurationSection()[buildConfigurationId];
+    let buildConfiguration = project.pbxXCBuildConfigurationSection()[
+      buildConfigurationId
+    ];
     return {
       uuid: key,
       target: nativeTargetSection[key],
-        name: nativeTargetSection[key].productReference_comment,
-      isTVOS: (buildConfiguration.buildSettings.SDKROOT && (buildConfiguration.buildSettings.SDKROOT.indexOf('appletv') !== -1)) || false
+      name: nativeTargetSection[key].productReference_comment,
+      isTVOS:
+        (buildConfiguration.buildSettings.SDKROOT &&
+          buildConfiguration.buildSettings.SDKROOT.indexOf('appletv') !== -1) ||
+        false,
     };
   });
 };
diff --git a/local-cli/link/ios/hasLibraryImported.js b/local-cli/link/ios/hasLibraryImported.js
index 0372f0b4b920..eed9c6e1cb2a 100644
--- a/local-cli/link/ios/hasLibraryImported.js
+++ b/local-cli/link/ios/hasLibraryImported.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -11,7 +13,8 @@
  * or not
  */
 module.exports = function hasLibraryImported(libraries, packageName) {
-  return libraries.children
-    .filter(library => library.comment === packageName)
-    .length > 0;
+  return (
+    libraries.children.filter(library => library.comment === packageName)
+      .length > 0
+  );
 };
diff --git a/local-cli/link/ios/index.js b/local-cli/link/ios/index.js
index 9653b3be80a1..bf6b57b26186 100644
--- a/local-cli/link/ios/index.js
+++ b/local-cli/link/ios/index.js
@@ -1,9 +1,11 @@
+/** @format */
+
 module.exports = function() {
   return {
     isInstalled: require('./common/isInstalled'),
     register: require('./common/registerNativeModule'),
     unregister: require('./common/unregisterNativeModule'),
     copyAssets: require('./copyAssets'),
-    unlinkAssets: require('./unlinkAssets')
+    unlinkAssets: require('./unlinkAssets'),
   };
 };
diff --git a/local-cli/link/ios/isInstalled.js b/local-cli/link/ios/isInstalled.js
index 7b0e4a94672a..084c8addda6f 100644
--- a/local-cli/link/ios/isInstalled.js
+++ b/local-cli/link/ios/isInstalled.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const xcode = require('xcode');
diff --git a/local-cli/link/ios/mapHeaderSearchPaths.js b/local-cli/link/ios/mapHeaderSearchPaths.js
index cb2a583f25f4..64a8f6560cac 100644
--- a/local-cli/link/ios/mapHeaderSearchPaths.js
+++ b/local-cli/link/ios/mapHeaderSearchPaths.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -25,22 +27,20 @@ const defaultHeaderPaths = ['"$(inherited)"'];
 module.exports = function headerSearchPathIter(project, func) {
   const config = project.pbxXCBuildConfigurationSection();
 
-  Object
-    .keys(config)
+  Object.keys(config)
     .filter(ref => ref.indexOf('_comment') === -1)
     .forEach(ref => {
       const buildSettings = config[ref].buildSettings;
-      const shouldVisitBuildSettings = (
-          Array.isArray(buildSettings.OTHER_LDFLAGS) ?
-            buildSettings.OTHER_LDFLAGS :
-            []
-        )
-        .indexOf('"-lc++"') >= 0;
+      const shouldVisitBuildSettings =
+        (Array.isArray(buildSettings.OTHER_LDFLAGS)
+          ? buildSettings.OTHER_LDFLAGS
+          : []
+        ).indexOf('"-lc++"') >= 0;
 
       if (shouldVisitBuildSettings) {
-        const searchPaths = buildSettings.HEADER_SEARCH_PATHS ?
-          [].concat(buildSettings.HEADER_SEARCH_PATHS) :
-          defaultHeaderPaths;
+        const searchPaths = buildSettings.HEADER_SEARCH_PATHS
+          ? [].concat(buildSettings.HEADER_SEARCH_PATHS)
+          : defaultHeaderPaths;
 
         buildSettings.HEADER_SEARCH_PATHS = func(searchPaths);
       }
diff --git a/local-cli/link/ios/registerNativeModule.js b/local-cli/link/ios/registerNativeModule.js
index fed2b0bb2cfc..41cca896709f 100644
--- a/local-cli/link/ios/registerNativeModule.js
+++ b/local-cli/link/ios/registerNativeModule.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const xcode = require('xcode');
@@ -29,14 +31,22 @@ const getGroup = require('./getGroup');
  *
  * If library is already linked, this action is a no-op.
  */
-module.exports = function registerNativeModuleIOS(dependencyConfig, projectConfig) {
+module.exports = function registerNativeModuleIOS(
+  dependencyConfig,
+  projectConfig,
+) {
   const project = xcode.project(projectConfig.pbxprojPath).parseSync();
-  const dependencyProject = xcode.project(dependencyConfig.pbxprojPath).parseSync();
+  const dependencyProject = xcode
+    .project(dependencyConfig.pbxprojPath)
+    .parseSync();
 
-  const libraries = createGroupWithMessage(project, projectConfig.libraryFolder);
+  const libraries = createGroupWithMessage(
+    project,
+    projectConfig.libraryFolder,
+  );
   const file = addFileToProject(
     project,
-    path.relative(projectConfig.sourceDir, dependencyConfig.projectPath)
+    path.relative(projectConfig.sourceDir, dependencyConfig.projectPath),
   );
 
   const targets = getTargets(project);
@@ -49,7 +59,7 @@ module.exports = function registerNativeModuleIOS(dependencyConfig, projectConfi
       for (i = 0; i < targets.length; i++) {
         if (!targets[i].isTVOS) {
           project.addStaticLibrary(product.name, {
-            target: targets[i].uuid
+            target: targets[i].uuid,
           });
         }
       }
@@ -59,7 +69,7 @@ module.exports = function registerNativeModuleIOS(dependencyConfig, projectConfi
       for (i = 0; i < targets.length; i++) {
         if (targets[i].isTVOS) {
           project.addStaticLibrary(product.name, {
-            target: targets[i].uuid
+            target: targets[i].uuid,
           });
         }
       }
@@ -72,12 +82,9 @@ module.exports = function registerNativeModuleIOS(dependencyConfig, projectConfi
   if (!isEmpty(headers)) {
     addToHeaderSearchPaths(
       project,
-      getHeaderSearchPath(projectConfig.sourceDir, headers)
+      getHeaderSearchPath(projectConfig.sourceDir, headers),
     );
   }
 
-  fs.writeFileSync(
-    projectConfig.pbxprojPath,
-    project.writeSync()
-  );
+  fs.writeFileSync(projectConfig.pbxprojPath, project.writeSync());
 };
diff --git a/local-cli/link/ios/removeFromHeaderSearchPaths.js b/local-cli/link/ios/removeFromHeaderSearchPaths.js
index f662991210c2..ac9ead94c65a 100644
--- a/local-cli/link/ios/removeFromHeaderSearchPaths.js
+++ b/local-cli/link/ios/removeFromHeaderSearchPaths.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const mapHeaderSearchPaths = require('./mapHeaderSearchPaths');
@@ -11,7 +13,7 @@ const mapHeaderSearchPaths = require('./mapHeaderSearchPaths');
  * Given Xcode project and absolute path, it makes sure there are no headers referring to it
  */
 module.exports = function addToHeaderSearchPaths(project, path) {
-  mapHeaderSearchPaths(project,
-    searchPaths => searchPaths.filter(searchPath => searchPath !== path)
+  mapHeaderSearchPaths(project, searchPaths =>
+    searchPaths.filter(searchPath => searchPath !== path),
   );
 };
diff --git a/local-cli/link/ios/removeFromPbxItemContainerProxySection.js b/local-cli/link/ios/removeFromPbxItemContainerProxySection.js
index 44a3fb2db83f..d7e8f05f1661 100644
--- a/local-cli/link/ios/removeFromPbxItemContainerProxySection.js
+++ b/local-cli/link/ios/removeFromPbxItemContainerProxySection.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -10,7 +12,10 @@
  * a new PBXItemContainerProxy is created that contains `containerPortal` value
  * which equals to xcodeproj file.uuid from PBXFileReference section.
  */
-module.exports = function removeFromPbxItemContainerProxySection(project, file) {
+module.exports = function removeFromPbxItemContainerProxySection(
+  project,
+  file,
+) {
   const section = project.hash.project.objects.PBXContainerItemProxy;
 
   for (var key of Object.keys(section)) {
diff --git a/local-cli/link/ios/removeFromPbxReferenceProxySection.js b/local-cli/link/ios/removeFromPbxReferenceProxySection.js
index ba3626b796cb..05346ccabff9 100644
--- a/local-cli/link/ios/removeFromPbxReferenceProxySection.js
+++ b/local-cli/link/ios/removeFromPbxReferenceProxySection.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
diff --git a/local-cli/link/ios/removeFromProjectReferences.js b/local-cli/link/ios/removeFromProjectReferences.js
index 5edc858807f9..4eafe81e8413 100644
--- a/local-cli/link/ios/removeFromProjectReferences.js
+++ b/local-cli/link/ios/removeFromProjectReferences.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -18,7 +20,9 @@
 module.exports = function removeFromProjectReferences(project, file) {
   const firstProject = project.getFirstProject().firstProject;
 
-  const projectRef = firstProject.projectReferences.find(item => item.ProjectRef === file.uuid);
+  const projectRef = firstProject.projectReferences.find(
+    item => item.ProjectRef === file.uuid,
+  );
 
   if (!projectRef) {
     return null;
@@ -26,7 +30,7 @@ module.exports = function removeFromProjectReferences(project, file) {
 
   firstProject.projectReferences.splice(
     firstProject.projectReferences.indexOf(projectRef),
-    1
+    1,
   );
 
   return projectRef;
diff --git a/local-cli/link/ios/removeFromStaticLibraries.js b/local-cli/link/ios/removeFromStaticLibraries.js
index 391088c15702..1fa674331a84 100644
--- a/local-cli/link/ios/removeFromStaticLibraries.js
+++ b/local-cli/link/ios/removeFromStaticLibraries.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const PbxFile = require('xcode/lib/pbxFile');
diff --git a/local-cli/link/ios/removeProductGroup.js b/local-cli/link/ios/removeProductGroup.js
index 888f2a442006..a15fd9d750f4 100644
--- a/local-cli/link/ios/removeProductGroup.js
+++ b/local-cli/link/ios/removeProductGroup.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 module.exports = function removeProductGroup(project, productGroupId) {
diff --git a/local-cli/link/ios/removeProjectFromLibraries.js b/local-cli/link/ios/removeProjectFromLibraries.js
index 9eaee4758bf8..5dc572b9ef50 100644
--- a/local-cli/link/ios/removeProjectFromLibraries.js
+++ b/local-cli/link/ios/removeProjectFromLibraries.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -13,7 +15,7 @@
  * It's mainly due to limitations of `xcode` library.
  */
 module.exports = function removeProjectFromLibraries(libraries, file) {
-  libraries.children = libraries.children.filter(library =>
-    library.comment !== file.basename
+  libraries.children = libraries.children.filter(
+    library => library.comment !== file.basename,
   );
 };
diff --git a/local-cli/link/ios/removeProjectFromProject.js b/local-cli/link/ios/removeProjectFromProject.js
index cb7c17114974..76e9348184e1 100644
--- a/local-cli/link/ios/removeProjectFromProject.js
+++ b/local-cli/link/ios/removeProjectFromProject.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const PbxFile = require('xcode/lib/pbxFile');
diff --git a/local-cli/link/ios/removeSharedLibraries.js b/local-cli/link/ios/removeSharedLibraries.js
index dd2629ebb03c..e0306d28b0ce 100644
--- a/local-cli/link/ios/removeSharedLibraries.js
+++ b/local-cli/link/ios/removeSharedLibraries.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 module.exports = function removeSharedLibraries(project, libraries) {
@@ -13,6 +15,6 @@ module.exports = function removeSharedLibraries(project, libraries) {
   const target = project.getFirstTarget().uuid;
 
   for (var name of libraries) {
-    project.removeFramework(name, { target });
+    project.removeFramework(name, {target});
   }
 };
diff --git a/local-cli/link/ios/unlinkAssets.js b/local-cli/link/ios/unlinkAssets.js
index a7c38446f4ce..67f91cf6c610 100644
--- a/local-cli/link/ios/unlinkAssets.js
+++ b/local-cli/link/ios/unlinkAssets.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const fs = require('fs-extra');
@@ -26,24 +28,24 @@ module.exports = function unlinkAssetsIOS(files, projectConfig) {
   if (!plist) {
     return log.error(
       'ERRPLIST',
-      'Could not locate Info.plist file. Check if your project has \'INFOPLIST_FILE\' set properly'
+      "Could not locate Info.plist file. Check if your project has 'INFOPLIST_FILE' set properly",
     );
   }
 
   if (!project.pbxGroupByName('Resources')) {
     return log.error(
       'ERRGROUP',
-      'Group \'Resources\' does not exist in your Xcode project. There is nothing to unlink.'
+      "Group 'Resources' does not exist in your Xcode project. There is nothing to unlink.",
     );
   }
 
-  const removeResourceFile = function (f) {
+  const removeResourceFile = function(f) {
     (f || [])
       .map(asset =>
         project.removeResourceFile(
           path.relative(projectConfig.sourceDir, asset),
-          { target: project.getFirstTarget().uuid }
-        )
+          {target: project.getFirstTarget().uuid},
+        ),
       )
       .map(file => file.basename);
   };
@@ -54,10 +56,7 @@ module.exports = function unlinkAssetsIOS(files, projectConfig) {
 
   plist.UIAppFonts = difference(plist.UIAppFonts || [], fonts);
 
-  fs.writeFileSync(
-    projectConfig.pbxprojPath,
-    project.writeSync()
-  );
+  fs.writeFileSync(projectConfig.pbxprojPath, project.writeSync());
 
   writePlist(project, projectConfig.sourceDir, plist);
 };
diff --git a/local-cli/link/ios/unregisterNativeModule.js b/local-cli/link/ios/unregisterNativeModule.js
index b35a6c31aefa..c686b8c4969f 100644
--- a/local-cli/link/ios/unregisterNativeModule.js
+++ b/local-cli/link/ios/unregisterNativeModule.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const xcode = require('xcode');
@@ -27,15 +29,21 @@ const removeSharedLibraries = require('./removeSharedLibraries');
  *
  * If library is already unlinked, this action is a no-op.
  */
-module.exports = function unregisterNativeModule(dependencyConfig, projectConfig, iOSDependencies) {
+module.exports = function unregisterNativeModule(
+  dependencyConfig,
+  projectConfig,
+  iOSDependencies,
+) {
   const project = xcode.project(projectConfig.pbxprojPath).parseSync();
-  const dependencyProject = xcode.project(dependencyConfig.pbxprojPath).parseSync();
+  const dependencyProject = xcode
+    .project(dependencyConfig.pbxprojPath)
+    .parseSync();
 
   const libraries = getGroup(project, projectConfig.libraryFolder);
 
   const file = removeProjectFromProject(
     project,
-    path.relative(projectConfig.sourceDir, dependencyConfig.projectPath)
+    path.relative(projectConfig.sourceDir, dependencyConfig.projectPath),
   );
 
   removeProjectFromLibraries(libraries, file);
@@ -50,8 +58,8 @@ module.exports = function unregisterNativeModule(dependencyConfig, projectConfig
     dependencyConfig.sharedLibraries,
     iOSDependencies.reduce(
       (libs, dependency) => libs.concat(dependency.sharedLibraries),
-      projectConfig.sharedLibraries
-    )
+      projectConfig.sharedLibraries,
+    ),
   );
 
   removeSharedLibraries(project, sharedLibraries);
@@ -60,12 +68,9 @@ module.exports = function unregisterNativeModule(dependencyConfig, projectConfig
   if (!isEmpty(headers)) {
     removeFromHeaderSearchPaths(
       project,
-      getHeaderSearchPath(projectConfig.sourceDir, headers)
+      getHeaderSearchPath(projectConfig.sourceDir, headers),
     );
   }
 
-  fs.writeFileSync(
-    projectConfig.pbxprojPath,
-    project.writeSync()
-  );
+  fs.writeFileSync(projectConfig.pbxprojPath, project.writeSync());
 };
diff --git a/local-cli/link/ios/writePlist.js b/local-cli/link/ios/writePlist.js
index 0c025d2e9d22..b2ea1ae1efc8 100644
--- a/local-cli/link/ios/writePlist.js
+++ b/local-cli/link/ios/writePlist.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const plistParser = require('plist');
@@ -26,6 +28,6 @@ module.exports = function writePlist(project, sourceDir, plist) {
   // Ref: https://github.com/facebook/react-native/issues/11668
   return fs.writeFileSync(
     plistPath,
-    plistParser.build(plist, { indent: '\t', offset: -1 }) + '\n'
+    plistParser.build(plist, {indent: '\t', offset: -1}) + '\n',
   );
 };
diff --git a/local-cli/link/link.js b/local-cli/link/link.js
index 66e9efbf563c..892e4f71063b 100644
--- a/local-cli/link/link.js
+++ b/local-cli/link/link.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -35,40 +36,54 @@ import type {RNConfig} from '../core';
 
 log.heading = 'rnpm-link';
 
-const dedupeAssets = (assets) => uniqBy(assets, asset => path.basename(asset));
+const dedupeAssets = assets => uniqBy(assets, asset => path.basename(asset));
 
 const linkDependency = async (platforms, project, dependency) => {
   const params = await pollParams(dependency.config.params);
 
-  Object.keys(platforms || {})
-    .forEach(platform => {
-      if (!project[platform] || !dependency.config[platform]) {
-        return null;
-      }
-
-      const linkConfig = platforms[platform] && platforms[platform].linkConfig && platforms[platform].linkConfig();
-      if (!linkConfig || !linkConfig.isInstalled || !linkConfig.register) {
-        return null;
-      }
-
-      const isInstalled = linkConfig.isInstalled(project[platform], dependency.name, dependency.config[platform]);
+  Object.keys(platforms || {}).forEach(platform => {
+    if (!project[platform] || !dependency.config[platform]) {
+      return null;
+    }
+
+    const linkConfig =
+      platforms[platform] &&
+      platforms[platform].linkConfig &&
+      platforms[platform].linkConfig();
+    if (!linkConfig || !linkConfig.isInstalled || !linkConfig.register) {
+      return null;
+    }
+
+    const isInstalled = linkConfig.isInstalled(
+      project[platform],
+      dependency.name,
+      dependency.config[platform],
+    );
 
-      if (isInstalled) {
-        log.info(chalk.grey(`Platform '${platform}' module ${dependency.name} is already linked`));
-        return null;
-      }
+    if (isInstalled) {
+      log.info(
+        chalk.grey(
+          `Platform '${platform}' module ${dependency.name} is already linked`,
+        ),
+      );
+      return null;
+    }
 
-      log.info(`Linking ${dependency.name} ${platform} dependency`);
+    log.info(`Linking ${dependency.name} ${platform} dependency`);
 
-      linkConfig.register(
-        dependency.name,
-        dependency.config[platform],
-        params,
-        project[platform]
-      );
+    linkConfig.register(
+      dependency.name,
+      dependency.config[platform],
+      params,
+      project[platform],
+    );
 
-      log.info(`Platform '${platform}' module ${dependency.name} has been successfully linked`);
-    });
+    log.info(
+      `Platform '${platform}' module ${
+        dependency.name
+      } has been successfully linked`,
+    );
+  });
 };
 
 const linkAssets = (platforms, project, assets) => {
@@ -76,16 +91,18 @@ const linkAssets = (platforms, project, assets) => {
     return;
   }
 
-  Object.keys(platforms || {})
-    .forEach(platform => {
-      const linkConfig = platforms[platform] && platforms[platform].linkConfig && platforms[platform].linkConfig();
-      if (!linkConfig || !linkConfig.copyAssets) {
-        return;
-      }
-
-      log.info(`Linking assets to ${platform} project`);
-      linkConfig.copyAssets(assets, project[platform]);
-    });
+  Object.keys(platforms || {}).forEach(platform => {
+    const linkConfig =
+      platforms[platform] &&
+      platforms[platform].linkConfig &&
+      platforms[platform].linkConfig();
+    if (!linkConfig || !linkConfig.copyAssets) {
+      return;
+    }
+
+    log.info(`Linking assets to ${platform} project`);
+    linkConfig.copyAssets(assets, project[platform]);
+  });
 
   log.info('Assets have been successfully linked to your project');
 };
@@ -106,19 +123,22 @@ function link(args: Array<string>, config: RNConfig) {
   } catch (err) {
     log.error(
       'ERRPACKAGEJSON',
-      'No package found. Are you sure this is a React Native project?'
+      'No package found. Are you sure this is a React Native project?',
     );
     return Promise.reject(err);
   }
 
-  const hasProjectConfig = Object.keys(platforms).reduce((acc, key) => acc || key in project, false);
+  const hasProjectConfig = Object.keys(platforms).reduce(
+    (acc, key) => acc || key in project,
+    false,
+  );
   if (!hasProjectConfig && findReactNativeScripts()) {
     throw new Error(
       '`react-native link` can not be used in Create React Native App projects. ' +
-      'If you need to include a library that relies on custom native code, ' +
-      'you might have to eject first. ' +
-      'See https://github.com/react-community/create-react-native-app/blob/master/EJECTING.md ' +
-      'for more information.'
+        'If you need to include a library that relies on custom native code, ' +
+        'you might have to eject first. ' +
+        'See https://github.com/react-community/create-react-native-app/blob/master/EJECTING.md ' +
+        'for more information.',
     );
   }
 
@@ -130,26 +150,30 @@ function link(args: Array<string>, config: RNConfig) {
 
   const dependencies = getDependencyConfig(
     config,
-    packageName ? [packageName] : getProjectDependencies()
+    packageName ? [packageName] : getProjectDependencies(),
   );
 
-  const assets = dedupeAssets(dependencies.reduce(
-    (acc, dependency) => acc.concat(dependency.config.assets),
-    project.assets
-  ));
+  const assets = dedupeAssets(
+    dependencies.reduce(
+      (acc, dependency) => acc.concat(dependency.config.assets),
+      project.assets,
+    ),
+  );
 
-  const tasks = flatten(dependencies.map(dependency => [
-    () => promisify(dependency.config.commands.prelink || commandStub),
-    () => linkDependency(platforms, project, dependency),
-    () => promisify(dependency.config.commands.postlink || commandStub),
-  ]));
+  const tasks = flatten(
+    dependencies.map(dependency => [
+      () => promisify(dependency.config.commands.prelink || commandStub),
+      () => linkDependency(platforms, project, dependency),
+      () => promisify(dependency.config.commands.postlink || commandStub),
+    ]),
+  );
 
   tasks.push(() => linkAssets(platforms, project, assets));
 
   return promiseWaterfall(tasks).catch(err => {
     log.error(
       `Something went wrong while linking. Error: ${err.message} \n` +
-      'Please file an issue here: https://github.com/facebook/react-native/issues'
+        'Please file an issue here: https://github.com/facebook/react-native/issues',
     );
     throw err;
   });
diff --git a/local-cli/link/pods/addPodEntry.js b/local-cli/link/pods/addPodEntry.js
index ea9218623678..8ce5654ea4aa 100644
--- a/local-cli/link/pods/addPodEntry.js
+++ b/local-cli/link/pods/addPodEntry.js
@@ -3,21 +3,28 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
 
-module.exports = function addPodEntry(podLines, linesToAddEntry, podName, nodePath) {
+module.exports = function addPodEntry(
+  podLines,
+  linesToAddEntry,
+  podName,
+  nodePath,
+) {
   const newEntry = `pod '${podName}', :path => '../node_modules/${nodePath}'\n`;
 
   if (!linesToAddEntry) {
     return;
   } else if (Array.isArray(linesToAddEntry)) {
-    linesToAddEntry.map(({ line, indentation }, idx) =>
-      podLines.splice(line + idx, 0, getLineToAdd(newEntry, indentation))
+    linesToAddEntry.map(({line, indentation}, idx) =>
+      podLines.splice(line + idx, 0, getLineToAdd(newEntry, indentation)),
     );
   } else {
-    const { line, indentation } = linesToAddEntry;
+    const {line, indentation} = linesToAddEntry;
     podLines.splice(line, 0, getLineToAdd(newEntry, indentation));
   }
 };
diff --git a/local-cli/link/pods/findLineToAddPod.js b/local-cli/link/pods/findLineToAddPod.js
index dca2e391cc48..629296e9f662 100644
--- a/local-cli/link/pods/findLineToAddPod.js
+++ b/local-cli/link/pods/findLineToAddPod.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -16,14 +18,15 @@ module.exports = function findLineToAddPod(podLines, firstTargetLine) {
   const functionDefinition = /^\s*[a-z_]+\s+do(\s+\|[a-z]+\|)?/g;
 
   for (let i = firstTargetLine, len = podLines.length; i < len; i++) {
-    const matchNextConstruct = podLines[i].match(nextTarget) || podLines[i].match(functionDefinition);
+    const matchNextConstruct =
+      podLines[i].match(nextTarget) || podLines[i].match(functionDefinition);
     const matchEnd = podLines[i].match(endOfCurrentTarget);
 
     if (matchNextConstruct || matchEnd) {
       const firstNonSpaceCharacter = podLines[i].search(/\S/);
       return {
         indentation: firstNonSpaceCharacter + (matchEnd ? 2 : 0),
-        line: i
+        line: i,
       };
     }
   }
diff --git a/local-cli/link/pods/findMarkedLinesInPodfile.js b/local-cli/link/pods/findMarkedLinesInPodfile.js
index 42ef7c8bedd4..b58a0d48679d 100644
--- a/local-cli/link/pods/findMarkedLinesInPodfile.js
+++ b/local-cli/link/pods/findMarkedLinesInPodfile.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -12,7 +14,7 @@ module.exports = function findMarkedLinesInPodfile(podLines) {
   const result = [];
   for (let i = 0, len = podLines.length; i < len; i++) {
     if (podLines[i].includes(MARKER_TEXT)) {
-      result.push({ line: i + 1, indentation: podLines[i].indexOf('#') });
+      result.push({line: i + 1, indentation: podLines[i].indexOf('#')});
     }
   }
   return result;
diff --git a/local-cli/link/pods/findPodTargetLine.js b/local-cli/link/pods/findPodTargetLine.js
index d5a8c97fb2b3..10617584affc 100644
--- a/local-cli/link/pods/findPodTargetLine.js
+++ b/local-cli/link/pods/findPodTargetLine.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -10,7 +12,10 @@
 module.exports = function findPodTargetLine(podLines, projectName) {
   const targetName = projectName.replace('.xcodeproj', '');
   //match first target definition in file: target 'target_name' do
-  const targetRegex = new RegExp('target (\'|\")' + targetName + '(\'|\") do', 'g');
+  const targetRegex = new RegExp(
+    'target (\'|")' + targetName + '(\'|") do',
+    'g',
+  );
   for (let i = 0, len = podLines.length; i < len; i++) {
     const match = podLines[i].match(targetRegex);
     if (match) {
diff --git a/local-cli/link/pods/isInstalled.js b/local-cli/link/pods/isInstalled.js
index 251376541d14..7f5d773d8a80 100644
--- a/local-cli/link/pods/isInstalled.js
+++ b/local-cli/link/pods/isInstalled.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -14,7 +16,10 @@ module.exports = function isInstalled(iOSProject, dependencyConfig) {
     return false;
   }
   // match line with pod declaration: pod 'dependencyPodName' (other possible parameters of pod are ignored)
-  const dependencyRegExp = new RegExp('pod\\s+(\'|\")' + dependencyConfig.podspec + '(\'|\")', 'g');
+  const dependencyRegExp = new RegExp(
+    'pod\\s+(\'|")' + dependencyConfig.podspec + '(\'|")',
+    'g',
+  );
   const podLines = readPodfile(iOSProject.podfile);
   for (let i = 0, len = podLines.length; i < len; i++) {
     const match = podLines[i].match(dependencyRegExp);
diff --git a/local-cli/link/pods/readPodfile.js b/local-cli/link/pods/readPodfile.js
index 85ac7ed9bf3d..f70609628f27 100644
--- a/local-cli/link/pods/readPodfile.js
+++ b/local-cli/link/pods/readPodfile.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
diff --git a/local-cli/link/pods/registerNativeModule.js b/local-cli/link/pods/registerNativeModule.js
index b00d93c6f2d6..8ae16a305988 100644
--- a/local-cli/link/pods/registerNativeModule.js
+++ b/local-cli/link/pods/registerNativeModule.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -14,14 +16,18 @@ const findMarkedLinesInPodfile = require('./findMarkedLinesInPodfile');
 const addPodEntry = require('./addPodEntry');
 const savePodFile = require('./savePodFile');
 
-module.exports = function registerNativeModulePods(name, dependencyConfig, iOSProject) {
+module.exports = function registerNativeModulePods(
+  name,
+  dependencyConfig,
+  iOSProject,
+) {
   const podLines = readPodfile(iOSProject.podfile);
   const linesToAddEntry = getLinesToAddEntry(podLines, iOSProject);
   addPodEntry(podLines, linesToAddEntry, dependencyConfig.podspec, name);
   savePodFile(iOSProject.podfile, podLines);
 };
 
-function getLinesToAddEntry(podLines, { projectName }) {
+function getLinesToAddEntry(podLines, {projectName}) {
   const linesToAddPodWithMarker = findMarkedLinesInPodfile(podLines);
   if (linesToAddPodWithMarker.length > 0) {
     return linesToAddPodWithMarker;
diff --git a/local-cli/link/pods/removePodEntry.js b/local-cli/link/pods/removePodEntry.js
index 8af044734d31..83f063ad289c 100644
--- a/local-cli/link/pods/removePodEntry.js
+++ b/local-cli/link/pods/removePodEntry.js
@@ -3,12 +3,19 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
 
 module.exports = function removePodEntry(podfileContent, podName) {
   // this regex should catch line(s) with full pod definition, like: pod 'podname', :path => '../node_modules/podname', :subspecs => ['Sub2', 'Sub1']
-  const podRegex = new RegExp("\\n( |\\t)*pod\\s+(\"|')" + podName + "(\"|')(,\\s*(:[a-z]+\\s*=>)?\\s*((\"|').*?(\"|')|\\[[\\s\\S]*?\\]))*\\n", 'g');
+  const podRegex = new RegExp(
+    '\\n( |\\t)*pod\\s+("|\')' +
+      podName +
+      '("|\')(,\\s*(:[a-z]+\\s*=>)?\\s*(("|\').*?("|\')|\\[[\\s\\S]*?\\]))*\\n',
+    'g',
+  );
   return podfileContent.replace(podRegex, '\n');
 };
diff --git a/local-cli/link/pods/savePodFile.js b/local-cli/link/pods/savePodFile.js
index 5572311105d5..e050c822c057 100644
--- a/local-cli/link/pods/savePodFile.js
+++ b/local-cli/link/pods/savePodFile.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
diff --git a/local-cli/link/pods/unregisterNativeModule.js b/local-cli/link/pods/unregisterNativeModule.js
index 3b2408bf992c..539e0389a5df 100644
--- a/local-cli/link/pods/unregisterNativeModule.js
+++ b/local-cli/link/pods/unregisterNativeModule.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -14,7 +16,7 @@ const removePodEntry = require('./removePodEntry');
  * Unregister native module IOS with CocoaPods
  */
 module.exports = function unregisterNativeModule(dependencyConfig, iOSProject) {
-	const podContent = fs.readFileSync(iOSProject.podfile, 'utf8');
-	const removed = removePodEntry(podContent, dependencyConfig.podspec);
-	fs.writeFileSync(iOSProject.podfile, removed);
+  const podContent = fs.readFileSync(iOSProject.podfile, 'utf8');
+  const removed = removePodEntry(podContent, dependencyConfig.podspec);
+  fs.writeFileSync(iOSProject.podfile, removed);
 };
diff --git a/local-cli/link/pollParams.js b/local-cli/link/pollParams.js
index 4c084a6d3ffe..66aa53e96825 100644
--- a/local-cli/link/pollParams.js
+++ b/local-cli/link/pollParams.js
@@ -3,14 +3,17 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 var inquirer = require('inquirer');
 
-module.exports = (questions) => new Promise((resolve, reject) => {
-  if (!questions) {
-    return resolve({});
-  }
+module.exports = questions =>
+  new Promise((resolve, reject) => {
+    if (!questions) {
+      return resolve({});
+    }
 
-  inquirer.prompt(questions).then(resolve, reject);
-});
+    inquirer.prompt(questions).then(resolve, reject);
+  });
diff --git a/local-cli/link/promiseWaterfall.js b/local-cli/link/promiseWaterfall.js
index fa8b621a9f5a..9b6177d69032 100644
--- a/local-cli/link/promiseWaterfall.js
+++ b/local-cli/link/promiseWaterfall.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /**
@@ -16,6 +18,6 @@
 module.exports = function promiseWaterfall(tasks) {
   return tasks.reduce(
     (prevTaskPromise, task) => prevTaskPromise.then(task),
-    Promise.resolve()
+    Promise.resolve(),
   );
 };
diff --git a/local-cli/link/promisify.js b/local-cli/link/promisify.js
index 665b640f216f..b99f2f43a0f7 100644
--- a/local-cli/link/promisify.js
+++ b/local-cli/link/promisify.js
@@ -3,8 +3,11 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
-module.exports = (func) => new Promise((resolve, reject) =>
-  func((err, res) => err ? reject(err) : resolve(res))
-);
+module.exports = func =>
+  new Promise((resolve, reject) =>
+    func((err, res) => (err ? reject(err) : resolve(res))),
+  );
diff --git a/local-cli/link/unlink.js b/local-cli/link/unlink.js
index 91c89ab7ec08..c886c4f46b7d 100644
--- a/local-cli/link/unlink.js
+++ b/local-cli/link/unlink.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const log = require('npmlog');
@@ -19,37 +21,52 @@ const promisify = require('./promisify');
 
 log.heading = 'rnpm-link';
 
-const unlinkDependency = (platforms, project, dependency, packageName, otherDependencies) => {
-
-  Object.keys(platforms || {})
-    .forEach(platform => {
-      if (!project[platform] || !dependency[platform]) {
-        return;
-      }
-
-      const linkConfig = platforms[platform] && platforms[platform].linkConfig && platforms[platform].linkConfig();
-      if (!linkConfig || !linkConfig.isInstalled || !linkConfig.unregister) {
-        return;
-      }
-
-      const isInstalled = linkConfig.isInstalled(project[platform], packageName, dependency[platform]);
+const unlinkDependency = (
+  platforms,
+  project,
+  dependency,
+  packageName,
+  otherDependencies,
+) => {
+  Object.keys(platforms || {}).forEach(platform => {
+    if (!project[platform] || !dependency[platform]) {
+      return;
+    }
+
+    const linkConfig =
+      platforms[platform] &&
+      platforms[platform].linkConfig &&
+      platforms[platform].linkConfig();
+    if (!linkConfig || !linkConfig.isInstalled || !linkConfig.unregister) {
+      return;
+    }
+
+    const isInstalled = linkConfig.isInstalled(
+      project[platform],
+      packageName,
+      dependency[platform],
+    );
 
-      if (!isInstalled) {
-        log.info(`Platform '${platform}' module ${packageName} is not installed`);
-        return;
-      }
+    if (!isInstalled) {
+      log.info(`Platform '${platform}' module ${packageName} is not installed`);
+      return;
+    }
 
-      log.info(`Unlinking ${packageName} ${platform} dependency`);
+    log.info(`Unlinking ${packageName} ${platform} dependency`);
 
-      linkConfig.unregister(
-        packageName,
-        dependency[platform],
-        project[platform],
-        otherDependencies
-      );
+    linkConfig.unregister(
+      packageName,
+      dependency[platform],
+      project[platform],
+      otherDependencies,
+    );
 
-      log.info(`Platform '${platform}' module ${dependency.name} has been successfully unlinked`);
-    });
+    log.info(
+      `Platform '${platform}' module ${
+        dependency.name
+      } has been successfully unlinked`,
+    );
+  });
 };
 
 /**
@@ -71,7 +88,7 @@ function unlink(args, config) {
   } catch (err) {
     log.error(
       'ERRPACKAGEJSON',
-      'No package found. Are you sure it\'s a React Native project?'
+      "No package found. Are you sure it's a React Native project?",
     );
     return Promise.reject(err);
   }
@@ -81,18 +98,28 @@ function unlink(args, config) {
   } catch (err) {
     log.warn(
       'ERRINVALIDPROJ',
-      `Project ${packageName} is not a react-native library`
+      `Project ${packageName} is not a react-native library`,
     );
     return Promise.reject(err);
   }
 
   const allDependencies = getDependencyConfig(config, getProjectDependencies());
-  const otherDependencies = filter(allDependencies, d => d.name !== packageName);
+  const otherDependencies = filter(
+    allDependencies,
+    d => d.name !== packageName,
+  );
 
   const tasks = [
     () => promisify(dependency.commands.preunlink || commandStub),
-    () => unlinkDependency(platforms, project, dependency, packageName, otherDependencies),
-    () => promisify(dependency.commands.postunlink || commandStub)
+    () =>
+      unlinkDependency(
+        platforms,
+        project,
+        dependency,
+        packageName,
+        otherDependencies,
+      ),
+    () => promisify(dependency.commands.postunlink || commandStub),
   ];
 
   return promiseWaterfall(tasks)
@@ -101,31 +128,33 @@ function unlink(args, config) {
       // link
       const assets = difference(
         dependency.assets,
-        flatten(allDependencies, d => d.assets)
+        flatten(allDependencies, d => d.assets),
       );
 
       if (isEmpty(assets)) {
         return Promise.resolve();
       }
 
-      Object.keys(platforms || {})
-        .forEach(platform => {
-          const linkConfig = platforms[platform] && platforms[platform].linkConfig && platforms[platform].linkConfig();
-          if (!linkConfig || !linkConfig.unlinkAssets) {
-            return;
-          }
+      Object.keys(platforms || {}).forEach(platform => {
+        const linkConfig =
+          platforms[platform] &&
+          platforms[platform].linkConfig &&
+          platforms[platform].linkConfig();
+        if (!linkConfig || !linkConfig.unlinkAssets) {
+          return;
+        }
 
-          log.info(`Unlinking assets from ${platform} project`);
-          linkConfig.unlinkAssets(assets, project[platform]);
-        });
+        log.info(`Unlinking assets from ${platform} project`);
+        linkConfig.unlinkAssets(assets, project[platform]);
+      });
 
       log.info(
-        `${packageName} assets has been successfully unlinked from your project`
+        `${packageName} assets has been successfully unlinked from your project`,
       );
     })
     .catch(err => {
       log.error(
-        `It seems something went wrong while unlinking. Error: ${err.message}`
+        `It seems something went wrong while unlinking. Error: ${err.message}`,
       );
       throw err;
     });
diff --git a/local-cli/logAndroid/logAndroid.js b/local-cli/logAndroid/logAndroid.js
index 7a1aace4bf78..b8608e96e408 100644
--- a/local-cli/logAndroid/logAndroid.js
+++ b/local-cli/logAndroid/logAndroid.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const chalk = require('chalk');
@@ -26,20 +29,19 @@ function _logAndroid() {
 
     const adbArgs = ['logcat', '*:S', 'ReactNative:V', 'ReactNativeJS:V'];
 
-    console.log(chalk.bold(
-      `Starting the logger (${adbPath} ${adbArgs.join(' ')})...`
-    ));
+    console.log(
+      chalk.bold(`Starting the logger (${adbPath} ${adbArgs.join(' ')})...`),
+    );
 
     const log = child_process.spawnSync(adbPath, adbArgs, {stdio: 'inherit'});
 
     if (log.error !== null) {
       throw log.error;
     }
-
   } catch (e) {
-    console.log(chalk.red(
-      'adb invocation failed. Do you have adb in your PATH?'
-    ));
+    console.log(
+      chalk.red('adb invocation failed. Do you have adb in your PATH?'),
+    );
     return Promise.reject();
   }
 }
diff --git a/local-cli/logIOS/logIOS.js b/local-cli/logIOS/logIOS.js
index 3e7b1ffb7c25..272dc0382602 100644
--- a/local-cli/logIOS/logIOS.js
+++ b/local-cli/logIOS/logIOS.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const chalk = require('chalk');
@@ -25,22 +28,24 @@ function _logIOS() {
 
   try {
     rawDevices = child_process.execFileSync(
-      'xcrun', ['simctl', 'list', 'devices', '--json'], {encoding: 'utf8'}
+      'xcrun',
+      ['simctl', 'list', 'devices', '--json'],
+      {encoding: 'utf8'},
     );
   } catch (e) {
-    console.log(chalk.red(
-      'xcrun invocation failed. Please check that Xcode is installed.'
-    ));
+    console.log(
+      chalk.red(
+        'xcrun invocation failed. Please check that Xcode is installed.',
+      ),
+    );
     return Promise.reject(e);
   }
 
-  const { devices } = JSON.parse(rawDevices);
+  const {devices} = JSON.parse(rawDevices);
 
   const device = _findAvailableDevice(devices);
   if (device === undefined) {
-    console.log(chalk.red(
-      'No active iOS device found'
-    ));
+    console.log(chalk.red('No active iOS device found'));
     return Promise.reject();
   }
 
@@ -67,13 +72,14 @@ function tailDeviceLogs(udid) {
     'asl',
   );
 
-  const log =
-    child_process.spawnSync('syslog', ['-w', '-F', 'std', '-d', logDir], {stdio: 'inherit'});
+  const log = child_process.spawnSync(
+    'syslog',
+    ['-w', '-F', 'std', '-d', logDir],
+    {stdio: 'inherit'},
+  );
 
   if (log.error !== null) {
-    console.log(chalk.red(
-      'syslog invocation failed.'
-    ));
+    console.log(chalk.red('syslog invocation failed.'));
     return Promise.reject(log.error);
   }
 }
diff --git a/local-cli/runAndroid/adb.js b/local-cli/runAndroid/adb.js
index 8206093e3fa8..3c6b980d2103 100644
--- a/local-cli/runAndroid/adb.js
+++ b/local-cli/runAndroid/adb.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -21,7 +22,7 @@ function parseDevicesResult(result: string): Array<string> {
   const lines = result.trim().split(/\r?\n/);
 
   for (let i = 0; i < lines.length; i++) {
-    let words = lines[i].split(/[ ,\t]+/).filter((w) => w !== '');
+    let words = lines[i].split(/[ ,\t]+/).filter(w => w !== '');
 
     if (words[1] === 'device') {
       devices.push(words[0]);
@@ -40,11 +41,9 @@ function getDevices(): Array<string> {
   } catch (e) {
     return [];
   }
-
-
 }
 
 module.exports = {
   parseDevicesResult: parseDevicesResult,
-  getDevices: getDevices
+  getDevices: getDevices,
 };
diff --git a/local-cli/runAndroid/runAndroid.js b/local-cli/runAndroid/runAndroid.js
index eb17d38210eb..234530c10415 100644
--- a/local-cli/runAndroid/runAndroid.js
+++ b/local-cli/runAndroid/runAndroid.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const adb = require('./adb');
@@ -31,10 +34,14 @@ function runAndroid(argv, config, args) {
       child_process.spawnSync(
         reactNativeScriptsPath,
         ['android'].concat(process.argv.slice(1)),
-        {stdio: 'inherit'}
+        {stdio: 'inherit'},
       );
     } else {
-      console.log(chalk.red('Android project not found. Maybe run react-native android first?'));
+      console.log(
+        chalk.red(
+          'Android project not found. Maybe run react-native android first?',
+        ),
+      );
     }
     return;
   }
@@ -47,7 +54,9 @@ function runAndroid(argv, config, args) {
     if (result === 'running') {
       console.log(chalk.bold('JS server already running.'));
     } else if (result === 'unrecognized') {
-      console.warn(chalk.yellow('JS server not recognized, continuing with build...'));
+      console.warn(
+        chalk.yellow('JS server not recognized, continuing with build...'),
+      );
     } else {
       // result == 'not_running'
       console.log(chalk.bold('Starting JS server...'));
@@ -74,9 +83,7 @@ function tryRunAdbReverse(packagerPort, device) {
       adbArgs.unshift('-s', device);
     }
 
-    console.log(chalk.bold(
-      `Running ${adbPath} ${adbArgs.join(' ')}`
-    ));
+    console.log(chalk.bold(`Running ${adbPath} ${adbArgs.join(' ')}`));
 
     child_process.execFileSync(adbPath, adbArgs, {
       stdio: [process.stdin, process.stdout, process.stderr],
@@ -99,21 +106,28 @@ function getPackageNameWithSuffix(appId, appIdSuffix, packageName) {
 // Builds the app and runs it on a connected emulator / device.
 function buildAndRun(args) {
   process.chdir(path.join(args.root, 'android'));
-  const cmd = process.platform.startsWith('win')
-    ? 'gradlew.bat'
-    : './gradlew';
+  const cmd = process.platform.startsWith('win') ? 'gradlew.bat' : './gradlew';
 
-  const packageName = fs.readFileSync(
-      `${args.appFolder}/src/main/AndroidManifest.xml`,
-      'utf8'
-    ).match(/package="(.+?)"/)[1];
+  const packageName = fs
+    .readFileSync(`${args.appFolder}/src/main/AndroidManifest.xml`, 'utf8')
+    .match(/package="(.+?)"/)[1];
 
-  const packageNameWithSuffix = getPackageNameWithSuffix(args.appId, args.appIdSuffix, packageName);
+  const packageNameWithSuffix = getPackageNameWithSuffix(
+    args.appId,
+    args.appIdSuffix,
+    packageName,
+  );
 
   const adbPath = getAdbPath();
   if (args.deviceId) {
     if (isString(args.deviceId)) {
-        runOnSpecificDevice(args, cmd, packageNameWithSuffix, packageName, adbPath);
+      runOnSpecificDevice(
+        args,
+        cmd,
+        packageNameWithSuffix,
+        packageName,
+        adbPath,
+      );
     } else {
       console.log(chalk.red('Argument missing for parameter --deviceId'));
     }
@@ -122,14 +136,28 @@ function buildAndRun(args) {
   }
 }
 
-function runOnSpecificDevice(args, gradlew, packageNameWithSuffix, packageName, adbPath) {
+function runOnSpecificDevice(
+  args,
+  gradlew,
+  packageNameWithSuffix,
+  packageName,
+  adbPath,
+) {
   let devices = adb.getDevices();
   if (devices && devices.length > 0) {
     if (devices.indexOf(args.deviceId) !== -1) {
       buildApk(gradlew);
-      installAndLaunchOnDevice(args, args.deviceId, packageNameWithSuffix, packageName, adbPath);
+      installAndLaunchOnDevice(
+        args,
+        args.deviceId,
+        packageNameWithSuffix,
+        packageName,
+        adbPath,
+      );
     } else {
-      console.log('Could not find device with the id: "' + args.deviceId + '".');
+      console.log(
+        'Could not find device with the id: "' + args.deviceId + '".',
+      );
       console.log('Choose one of the following:');
       console.log(devices);
     }
@@ -147,62 +175,104 @@ function buildApk(gradlew) {
       stdio: [process.stdin, process.stdout, process.stderr],
     });
   } catch (e) {
-    console.log(chalk.red('Could not build the app, read the error above for details.\n'));
+    console.log(
+      chalk.red('Could not build the app, read the error above for details.\n'),
+    );
   }
 }
 
 function tryInstallAppOnDevice(args, device) {
   try {
-    const pathToApk = `${args.appFolder}/build/outputs/apk/${args.appFolder}-debug.apk`;
+    const pathToApk = `${args.appFolder}/build/outputs/apk/${
+      args.appFolder
+    }-debug.apk`;
     const adbPath = getAdbPath();
     const adbArgs = ['-s', device, 'install', pathToApk];
-    console.log(chalk.bold(
-      `Installing the app on the device (cd android && adb -s ${device} install ${pathToApk}`
-    ));
+    console.log(
+      chalk.bold(
+        `Installing the app on the device (cd android && adb -s ${device} install ${pathToApk}`,
+      ),
+    );
     child_process.execFileSync(adbPath, adbArgs, {
       stdio: [process.stdin, process.stdout, process.stderr],
     });
   } catch (e) {
     console.log(e.message);
-    console.log(chalk.red(
-      'Could not install the app on the device, read the error above for details.\n'
-    ));
+    console.log(
+      chalk.red(
+        'Could not install the app on the device, read the error above for details.\n',
+      ),
+    );
   }
 }
 
-function tryLaunchAppOnDevice(device, packageNameWithSuffix, packageName, adbPath, mainActivity) {
+function tryLaunchAppOnDevice(
+  device,
+  packageNameWithSuffix,
+  packageName,
+  adbPath,
+  mainActivity,
+) {
   try {
-    const adbArgs = ['-s', device, 'shell', 'am', 'start', '-n', packageNameWithSuffix + '/' + packageName + '.' + mainActivity];
-    console.log(chalk.bold(
-      `Starting the app on ${device} (${adbPath} ${adbArgs.join(' ')})...`
-    ));
+    const adbArgs = [
+      '-s',
+      device,
+      'shell',
+      'am',
+      'start',
+      '-n',
+      packageNameWithSuffix + '/' + packageName + '.' + mainActivity,
+    ];
+    console.log(
+      chalk.bold(
+        `Starting the app on ${device} (${adbPath} ${adbArgs.join(' ')})...`,
+      ),
+    );
     child_process.spawnSync(adbPath, adbArgs, {stdio: 'inherit'});
   } catch (e) {
-    console.log(chalk.red(
-      'adb invocation failed. Do you have adb in your PATH?'
-    ));
+    console.log(
+      chalk.red('adb invocation failed. Do you have adb in your PATH?'),
+    );
   }
 }
 
-function installAndLaunchOnDevice(args, selectedDevice, packageNameWithSuffix, packageName, adbPath) {
+function installAndLaunchOnDevice(
+  args,
+  selectedDevice,
+  packageNameWithSuffix,
+  packageName,
+  adbPath,
+) {
   tryRunAdbReverse(args.port, selectedDevice);
   tryInstallAppOnDevice(args, selectedDevice);
-  tryLaunchAppOnDevice(selectedDevice, packageNameWithSuffix, packageName, adbPath, args.mainActivity);
+  tryLaunchAppOnDevice(
+    selectedDevice,
+    packageNameWithSuffix,
+    packageName,
+    adbPath,
+    args.mainActivity,
+  );
 }
 
-function runOnAllDevices(args, cmd, packageNameWithSuffix, packageName, adbPath){
+function runOnAllDevices(
+  args,
+  cmd,
+  packageNameWithSuffix,
+  packageName,
+  adbPath,
+) {
   try {
     const gradleArgs = [];
     if (args.variant) {
-      gradleArgs.push('install' +
-        args.variant[0].toUpperCase() + args.variant.slice(1)
+      gradleArgs.push(
+        'install' + args.variant[0].toUpperCase() + args.variant.slice(1),
       );
     } else if (args.flavor) {
-      console.warn(chalk.yellow(
-        '--flavor has been deprecated. Use --variant instead'
-      ));
-      gradleArgs.push('install' +
-        args.flavor[0].toUpperCase() + args.flavor.slice(1)
+      console.warn(
+        chalk.yellow('--flavor has been deprecated. Use --variant instead'),
+      );
+      gradleArgs.push(
+        'install' + args.flavor[0].toUpperCase() + args.flavor.slice(1),
       );
     } else {
       gradleArgs.push('installDebug');
@@ -212,132 +282,186 @@ function runOnAllDevices(args, cmd, packageNameWithSuffix, packageName, adbPath)
       gradleArgs.push(args.installDebug);
     }
 
-    console.log(chalk.bold(
-      `Building and installing the app on the device (cd android && ${cmd} ${gradleArgs.join(' ')})...`
-    ));
+    console.log(
+      chalk.bold(
+        `Building and installing the app on the device (cd android && ${cmd} ${gradleArgs.join(
+          ' ',
+        )})...`,
+      ),
+    );
 
     child_process.execFileSync(cmd, gradleArgs, {
       stdio: [process.stdin, process.stdout, process.stderr],
     });
   } catch (e) {
-    console.log(chalk.red(
-      'Could not install the app on the device, read the error above for details.\n' +
-      'Make sure you have an Android emulator running or a device connected and have\n' +
-      'set up your Android development environment:\n' +
-      'https://facebook.github.io/react-native/docs/getting-started.html'
-    ));
+    console.log(
+      chalk.red(
+        'Could not install the app on the device, read the error above for details.\n' +
+          'Make sure you have an Android emulator running or a device connected and have\n' +
+          'set up your Android development environment:\n' +
+          'https://facebook.github.io/react-native/docs/getting-started.html',
+      ),
+    );
     // stderr is automatically piped from the gradle process, so the user
     // should see the error already, there is no need to do
     // `console.log(e.stderr)`
     return Promise.reject();
   }
-    const devices = adb.getDevices();
-    if (devices && devices.length > 0) {
-      devices.forEach((device) => {
-        tryRunAdbReverse(args.port, device);
-        tryLaunchAppOnDevice(device, packageNameWithSuffix, packageName, adbPath, args.mainActivity);
-      });
-    } else {
-      try {
-        // If we cannot execute based on adb devices output, fall back to
-        // shell am start
-        const fallbackAdbArgs = [
-          'shell', 'am', 'start', '-n', packageNameWithSuffix + '/' + packageName + '.MainActivity'
-        ];
-        console.log(chalk.bold(
-          `Starting the app (${adbPath} ${fallbackAdbArgs.join(' ')}...`
-        ));
-        child_process.spawnSync(adbPath, fallbackAdbArgs, {stdio: 'inherit'});
-      } catch (e) {
-        console.log(chalk.red(
-          'adb invocation failed. Do you have adb in your PATH?'
-        ));
-        // stderr is automatically piped from the gradle process, so the user
-        // should see the error already, there is no need to do
-        // `console.log(e.stderr)`
-        return Promise.reject();
-      }
+  const devices = adb.getDevices();
+  if (devices && devices.length > 0) {
+    devices.forEach(device => {
+      tryRunAdbReverse(args.port, device);
+      tryLaunchAppOnDevice(
+        device,
+        packageNameWithSuffix,
+        packageName,
+        adbPath,
+        args.mainActivity,
+      );
+    });
+  } else {
+    try {
+      // If we cannot execute based on adb devices output, fall back to
+      // shell am start
+      const fallbackAdbArgs = [
+        'shell',
+        'am',
+        'start',
+        '-n',
+        packageNameWithSuffix + '/' + packageName + '.MainActivity',
+      ];
+      console.log(
+        chalk.bold(
+          `Starting the app (${adbPath} ${fallbackAdbArgs.join(' ')}...`,
+        ),
+      );
+      child_process.spawnSync(adbPath, fallbackAdbArgs, {stdio: 'inherit'});
+    } catch (e) {
+      console.log(
+        chalk.red('adb invocation failed. Do you have adb in your PATH?'),
+      );
+      // stderr is automatically piped from the gradle process, so the user
+      // should see the error already, there is no need to do
+      // `console.log(e.stderr)`
+      return Promise.reject();
     }
+  }
 }
 
 function startServerInNewWindow(port) {
-  const scriptFile = /^win/.test(process.platform) ?
-    'launchPackager.bat' :
-    'launchPackager.command';
+  const scriptFile = /^win/.test(process.platform)
+    ? 'launchPackager.bat'
+    : 'launchPackager.command';
   const scriptsDir = path.resolve(__dirname, '..', '..', 'scripts');
   const launchPackagerScript = path.resolve(scriptsDir, scriptFile);
   const procConfig = {cwd: scriptsDir};
   const terminal = process.env.REACT_TERMINAL;
 
   // setup the .packager.env file to ensure the packager starts on the right port
-  const packagerEnvFile = path.join(__dirname, '..', '..', 'scripts', '.packager.env');
+  const packagerEnvFile = path.join(
+    __dirname,
+    '..',
+    '..',
+    'scripts',
+    '.packager.env',
+  );
   const content = `export RCT_METRO_PORT=${port}`;
   // ensure we overwrite file by passing the 'w' flag
   fs.writeFileSync(packagerEnvFile, content, {encoding: 'utf8', flag: 'w'});
 
   if (process.platform === 'darwin') {
     if (terminal) {
-      return child_process.spawnSync('open', ['-a', terminal, launchPackagerScript], procConfig);
+      return child_process.spawnSync(
+        'open',
+        ['-a', terminal, launchPackagerScript],
+        procConfig,
+      );
     }
     return child_process.spawnSync('open', [launchPackagerScript], procConfig);
-
   } else if (process.platform === 'linux') {
     procConfig.detached = true;
-    if (terminal){
-      return child_process.spawn(terminal, ['-e', 'sh ' + launchPackagerScript], procConfig);
+    if (terminal) {
+      return child_process.spawn(
+        terminal,
+        ['-e', 'sh ' + launchPackagerScript],
+        procConfig,
+      );
     }
     return child_process.spawn('sh', [launchPackagerScript], procConfig);
-
   } else if (/^win/.test(process.platform)) {
     procConfig.detached = true;
     procConfig.stdio = 'ignore';
-    return child_process.spawn('cmd.exe', ['/C', launchPackagerScript], procConfig);
+    return child_process.spawn(
+      'cmd.exe',
+      ['/C', launchPackagerScript],
+      procConfig,
+    );
   } else {
-    console.log(chalk.red(`Cannot start the packager. Unknown platform ${process.platform}`));
+    console.log(
+      chalk.red(
+        `Cannot start the packager. Unknown platform ${process.platform}`,
+      ),
+    );
   }
 }
 
 module.exports = {
   name: 'run-android',
-  description: 'builds your app and starts it on a connected Android emulator or device',
+  description:
+    'builds your app and starts it on a connected Android emulator or device',
   func: runAndroid,
-  options: [{
-    command: '--install-debug',
-  }, {
-    command: '--root [string]',
-    description: 'Override the root directory for the android build (which contains the android directory)',
-    default: '',
-  }, {
-    command: '--flavor [string]',
-    description: '--flavor has been deprecated. Use --variant instead',
-  }, {
-    command: '--variant [string]',
-  }, {
-    command: '--appFolder [string]',
-    description: 'Specify a different application folder name for the android source.',
-    default: 'app',
-  }, {
-    command: '--appId [string]',
-    description: 'Specify an applicationId to launch after build.',
-    default: '',
-  }, {
-    command: '--appIdSuffix [string]',
-    description: 'Specify an applicationIdSuffix to launch after build.',
-    default: '',
-  }, {
-    command: '--main-activity [string]',
-    description: 'Name of the activity to start',
-    default: 'MainActivity',
-  }, {
-    command: '--deviceId [string]',
-    description: 'builds your app and starts it on a specific device/simulator with the ' +
-      'given device id (listed by running "adb devices" on the command line).',
-  }, {
-    command: '--no-packager',
-    description: 'Do not launch packager while building',
-  }, {
-    command: '--port [number]',
-    default: process.env.RCT_METRO_PORT || 8081,
-    parse: (val: string) => Number(val),
-  }],
+  options: [
+    {
+      command: '--install-debug',
+    },
+    {
+      command: '--root [string]',
+      description:
+        'Override the root directory for the android build (which contains the android directory)',
+      default: '',
+    },
+    {
+      command: '--flavor [string]',
+      description: '--flavor has been deprecated. Use --variant instead',
+    },
+    {
+      command: '--variant [string]',
+    },
+    {
+      command: '--appFolder [string]',
+      description:
+        'Specify a different application folder name for the android source.',
+      default: 'app',
+    },
+    {
+      command: '--appId [string]',
+      description: 'Specify an applicationId to launch after build.',
+      default: '',
+    },
+    {
+      command: '--appIdSuffix [string]',
+      description: 'Specify an applicationIdSuffix to launch after build.',
+      default: '',
+    },
+    {
+      command: '--main-activity [string]',
+      description: 'Name of the activity to start',
+      default: 'MainActivity',
+    },
+    {
+      command: '--deviceId [string]',
+      description:
+        'builds your app and starts it on a specific device/simulator with the ' +
+        'given device id (listed by running "adb devices" on the command line).',
+    },
+    {
+      command: '--no-packager',
+      description: 'Do not launch packager while building',
+    },
+    {
+      command: '--port [number]',
+      default: process.env.RCT_METRO_PORT || 8081,
+      parse: (val: string) => Number(val),
+    },
+  ],
 };
diff --git a/local-cli/runIOS/__tests__/findMatchingSimulator-test.js b/local-cli/runIOS/__tests__/findMatchingSimulator-test.js
index fb3ffddcbe8d..3c59b06839a2 100644
--- a/local-cli/runIOS/__tests__/findMatchingSimulator-test.js
+++ b/local-cli/runIOS/__tests__/findMatchingSimulator-test.js
@@ -5,8 +5,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
+
 'use strict';
 
 jest.dontMock('../findMatchingSimulator');
@@ -15,481 +17,510 @@ const findMatchingSimulator = require('../findMatchingSimulator');
 
 describe('findMatchingSimulator', () => {
   it('should find simulator', () => {
-    expect(findMatchingSimulator({
-        'devices': {
-          'iOS 9.2': [
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 4s',
-              'udid': 'B9B5E161-416B-43C4-A78F-729CB96CC8C6'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 5',
-              'udid': '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': 'BA0D93BD-07E6-4182-9B0A-F60A2474139C'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '9564ABEE-9EC2-4B4A-B443-D3710929A45A'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6s',
-              'udid': 'D0F29BE7-CC3C-4976-888D-C739B4F50508'
-            }
-          ]
-        }
-      },
-      'iPhone 6'
-    )).toEqual({
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'iOS 9.2': [
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 4s',
+                udid: 'B9B5E161-416B-43C4-A78F-729CB96CC8C6',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 5',
+                udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '9564ABEE-9EC2-4B4A-B443-D3710929A45A',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6s',
+                udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
+              },
+            ],
+          },
+        },
+        'iPhone 6',
+      ),
+    ).toEqual({
       udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
       name: 'iPhone 6',
       booted: false,
-      version: 'iOS 9.2'
+      version: 'iOS 9.2',
     });
   });
 
   it('should return null if no simulators available', () => {
-    expect(findMatchingSimulator({
-        'devices': {
-          'iOS 9.2': [
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 4s',
-              'udid': 'B9B5E161-416B-43C4-A78F-729CB96CC8C6'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 5',
-              'udid': '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 6',
-              'udid': 'BA0D93BD-07E6-4182-9B0A-F60A2474139C'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '9564ABEE-9EC2-4B4A-B443-D3710929A45A'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 6s',
-              'udid': 'D0F29BE7-CC3C-4976-888D-C739B4F50508'
-            }
-          ]
-        }
-      },
-      'iPhone 6'
-    )).toEqual(null);
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'iOS 9.2': [
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 4s',
+                udid: 'B9B5E161-416B-43C4-A78F-729CB96CC8C6',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 5',
+                udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 6',
+                udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 6 (Plus)',
+                udid: '9564ABEE-9EC2-4B4A-B443-D3710929A45A',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 6s',
+                udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
+              },
+            ],
+          },
+        },
+        'iPhone 6',
+      ),
+    ).toEqual(null);
   });
 
   it('should return null if an odd input', () => {
-    expect(findMatchingSimulator('random string input', 'iPhone 6')).toEqual(null);
+    expect(findMatchingSimulator('random string input', 'iPhone 6')).toEqual(
+      null,
+    );
   });
 
   it('should return the first simulator in list if none is defined', () => {
-    expect(findMatchingSimulator({
-        'devices': {
-          'iOS 9.2': [
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 4s',
-              'udid': 'B9B5E161-416B-43C4-A78F-729CB96CC8C6'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 5',
-              'udid': '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': 'BA0D93BD-07E6-4182-9B0A-F60A2474139C'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '9564ABEE-9EC2-4B4A-B443-D3710929A45A'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 6s',
-              'udid': 'D0F29BE7-CC3C-4976-888D-C739B4F50508'
-            }
-          ]
-        }
-      },
-      null
-    )).toEqual({
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'iOS 9.2': [
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 4s',
+                udid: 'B9B5E161-416B-43C4-A78F-729CB96CC8C6',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 5',
+                udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '9564ABEE-9EC2-4B4A-B443-D3710929A45A',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 6s',
+                udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
+              },
+            ],
+          },
+        },
+        null,
+      ),
+    ).toEqual({
       udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
       name: 'iPhone 5',
       booted: false,
-      version: 'iOS 9.2'
+      version: 'iOS 9.2',
     });
   });
 
   it('should return the first simulator in list if none is defined', () => {
-    expect(findMatchingSimulator({
-        'devices': {
-          'iOS 9.2': [
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 4s',
-              'udid': 'B9B5E161-416B-43C4-A78F-729CB96CC8C6'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 5',
-              'udid': '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': 'BA0D93BD-07E6-4182-9B0A-F60A2474139C'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '9564ABEE-9EC2-4B4A-B443-D3710929A45A'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 6s',
-              'udid': 'D0F29BE7-CC3C-4976-888D-C739B4F50508'
-            }
-          ],
-          'iOS 10.0': [
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': '2FF48AE5-CC3B-4C80-8D25-48966A6BE2C0'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '841E33FE-E8A1-4B65-9FF8-6EAA6442A3FC'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6s',
-              'udid': 'CBBB8FB8-77AB-49A9-8297-4CCFE3189C22'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 7',
-              'udid': '3A409DC5-5188-42A6-8598-3AA6F34607A5'
-            }
-          ]
-        }
-      },
-      null
-    )).toEqual({
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'iOS 9.2': [
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 4s',
+                udid: 'B9B5E161-416B-43C4-A78F-729CB96CC8C6',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 5',
+                udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '9564ABEE-9EC2-4B4A-B443-D3710929A45A',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 6s',
+                udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
+              },
+            ],
+            'iOS 10.0': [
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: '2FF48AE5-CC3B-4C80-8D25-48966A6BE2C0',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '841E33FE-E8A1-4B65-9FF8-6EAA6442A3FC',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6s',
+                udid: 'CBBB8FB8-77AB-49A9-8297-4CCFE3189C22',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 7',
+                udid: '3A409DC5-5188-42A6-8598-3AA6F34607A5',
+              },
+            ],
+          },
+        },
+        null,
+      ),
+    ).toEqual({
       udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
       name: 'iPhone 5',
       booted: false,
-      version: 'iOS 9.2'
+      version: 'iOS 9.2',
     });
   });
 
   it('should return the booted simulator in list if none is defined', () => {
-    expect(findMatchingSimulator({
-        'devices': {
-          'iOS 9.2': [
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 4s',
-              'udid': 'B9B5E161-416B-43C4-A78F-729CB96CC8C6'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 5',
-              'udid': '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': 'BA0D93BD-07E6-4182-9B0A-F60A2474139C'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '9564ABEE-9EC2-4B4A-B443-D3710929A45A'
-            },
-            {
-              'state': 'Booted',
-              'availability': '(available)',
-              'name': 'iPhone 6s',
-              'udid': 'D0F29BE7-CC3C-4976-888D-C739B4F50508'
-            }
-          ]
-        }
-      },
-      null
-    )).toEqual({
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'iOS 9.2': [
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 4s',
+                udid: 'B9B5E161-416B-43C4-A78F-729CB96CC8C6',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 5',
+                udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '9564ABEE-9EC2-4B4A-B443-D3710929A45A',
+              },
+              {
+                state: 'Booted',
+                availability: '(available)',
+                name: 'iPhone 6s',
+                udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
+              },
+            ],
+          },
+        },
+        null,
+      ),
+    ).toEqual({
       udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
       name: 'iPhone 6s',
       booted: true,
-      version: 'iOS 9.2'
+      version: 'iOS 9.2',
     });
   });
 
   it('should return the defined simulator in list even if another device is booted', () => {
-    expect(findMatchingSimulator({
-        'devices': {
-          'iOS 9.2': [
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 4s',
-              'udid': 'B9B5E161-416B-43C4-A78F-729CB96CC8C6'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 5',
-              'udid': '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': 'BA0D93BD-07E6-4182-9B0A-F60A2474139C'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '9564ABEE-9EC2-4B4A-B443-D3710929A45A'
-            },
-            {
-              'state': 'Booted',
-              'availability': '(available)',
-              'name': 'iPhone 6s',
-              'udid': 'D0F29BE7-CC3C-4976-888D-C739B4F50508'
-            }
-          ]
-        }
-      },
-      'iPhone 6'
-    )).toEqual({
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'iOS 9.2': [
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 4s',
+                udid: 'B9B5E161-416B-43C4-A78F-729CB96CC8C6',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 5',
+                udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '9564ABEE-9EC2-4B4A-B443-D3710929A45A',
+              },
+              {
+                state: 'Booted',
+                availability: '(available)',
+                name: 'iPhone 6s',
+                udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
+              },
+            ],
+          },
+        },
+        'iPhone 6',
+      ),
+    ).toEqual({
       udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
       name: 'iPhone 6',
       booted: false,
-      version: 'iOS 9.2'
+      version: 'iOS 9.2',
     });
   });
 
   it('should return the booted simulator in list if none is defined (multi ios versions)', () => {
-    expect(findMatchingSimulator({
-        'devices': {
-          'iOS 9.2': [
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 4s',
-              'udid': 'B9B5E161-416B-43C4-A78F-729CB96CC8C6'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 5',
-              'udid': '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': 'BA0D93BD-07E6-4182-9B0A-F60A2474139C'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '9564ABEE-9EC2-4B4A-B443-D3710929A45A'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6s',
-              'udid': 'D0F29BE7-CC3C-4976-888D-C739B4F50508'
-            }
-          ],
-          'iOS 10.0': [
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': '2FF48AE5-CC3B-4C80-8D25-48966A6BE2C0'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '841E33FE-E8A1-4B65-9FF8-6EAA6442A3FC'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6s',
-              'udid': 'CBBB8FB8-77AB-49A9-8297-4CCFE3189C22'
-            },
-            {
-              'state': 'Booted',
-              'availability': '(available)',
-              'name': 'iPhone 7',
-              'udid': '3A409DC5-5188-42A6-8598-3AA6F34607A5'
-            }
-          ]
-        }
-      },
-      null
-    )).toEqual({
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'iOS 9.2': [
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 4s',
+                udid: 'B9B5E161-416B-43C4-A78F-729CB96CC8C6',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 5',
+                udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '9564ABEE-9EC2-4B4A-B443-D3710929A45A',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6s',
+                udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
+              },
+            ],
+            'iOS 10.0': [
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: '2FF48AE5-CC3B-4C80-8D25-48966A6BE2C0',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '841E33FE-E8A1-4B65-9FF8-6EAA6442A3FC',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6s',
+                udid: 'CBBB8FB8-77AB-49A9-8297-4CCFE3189C22',
+              },
+              {
+                state: 'Booted',
+                availability: '(available)',
+                name: 'iPhone 7',
+                udid: '3A409DC5-5188-42A6-8598-3AA6F34607A5',
+              },
+            ],
+          },
+        },
+        null,
+      ),
+    ).toEqual({
       udid: '3A409DC5-5188-42A6-8598-3AA6F34607A5',
       name: 'iPhone 7',
       booted: true,
-      version: 'iOS 10.0'
+      version: 'iOS 10.0',
     });
   });
 
   it('should return the defined simulator in list even if another device is booted (multi ios versions)', () => {
-    expect(findMatchingSimulator({
-        'devices': {
-          'iOS 9.2': [
-            {
-              'state': 'Shutdown',
-              'availability': '(unavailable, runtime profile not found)',
-              'name': 'iPhone 4s',
-              'udid': 'B9B5E161-416B-43C4-A78F-729CB96CC8C6'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 5',
-              'udid': '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': 'BA0D93BD-07E6-4182-9B0A-F60A2474139C'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '9564ABEE-9EC2-4B4A-B443-D3710929A45A'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6s',
-              'udid': 'D0F29BE7-CC3C-4976-888D-C739B4F50508'
-            }
-          ],
-          'iOS 10.0': [
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6',
-              'udid': '2FF48AE5-CC3B-4C80-8D25-48966A6BE2C0'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6 (Plus)',
-              'udid': '841E33FE-E8A1-4B65-9FF8-6EAA6442A3FC'
-            },
-            {
-              'state': 'Shutdown',
-              'availability': '(available)',
-              'name': 'iPhone 6s',
-              'udid': 'CBBB8FB8-77AB-49A9-8297-4CCFE3189C22'
-            },
-            {
-              'state': 'Booted',
-              'availability': '(available)',
-              'name': 'iPhone 7',
-              'udid': '3A409DC5-5188-42A6-8598-3AA6F34607A5'
-            }
-          ]
-        }
-      },
-      'iPhone 6s'
-    )).toEqual({
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'iOS 9.2': [
+              {
+                state: 'Shutdown',
+                availability: '(unavailable, runtime profile not found)',
+                name: 'iPhone 4s',
+                udid: 'B9B5E161-416B-43C4-A78F-729CB96CC8C6',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 5',
+                udid: '1CCBBF8B-5773-4EA6-BD6F-C308C87A1ADB',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: 'BA0D93BD-07E6-4182-9B0A-F60A2474139C',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '9564ABEE-9EC2-4B4A-B443-D3710929A45A',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6s',
+                udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
+              },
+            ],
+            'iOS 10.0': [
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6',
+                udid: '2FF48AE5-CC3B-4C80-8D25-48966A6BE2C0',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6 (Plus)',
+                udid: '841E33FE-E8A1-4B65-9FF8-6EAA6442A3FC',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'iPhone 6s',
+                udid: 'CBBB8FB8-77AB-49A9-8297-4CCFE3189C22',
+              },
+              {
+                state: 'Booted',
+                availability: '(available)',
+                name: 'iPhone 7',
+                udid: '3A409DC5-5188-42A6-8598-3AA6F34607A5',
+              },
+            ],
+          },
+        },
+        'iPhone 6s',
+      ),
+    ).toEqual({
       udid: 'D0F29BE7-CC3C-4976-888D-C739B4F50508',
       name: 'iPhone 6s',
       booted: false,
-      version: 'iOS 9.2'
+      version: 'iOS 9.2',
     });
   });
 
   it('should return AppleTV devices if in the list', () => {
-    expect(findMatchingSimulator({
-      'devices': {
-        'tvOS 11.2' : [
-          {
-            'state' : 'Booted',
-            'availability' : '(available)',
-            'name' : 'Apple TV',
-            'udid' : '816C30EA-38EA-41AC-BFDA-96FB632D522E'
-          },
-          {
-            'state' : 'Shutdown',
-            'availability' : '(available)',
-            'name' : 'Apple TV 4K',
-            'udid' : 'BCBB7E4B-D872-4D61-BC61-7C9805551075'
+    expect(
+      findMatchingSimulator(
+        {
+          devices: {
+            'tvOS 11.2': [
+              {
+                state: 'Booted',
+                availability: '(available)',
+                name: 'Apple TV',
+                udid: '816C30EA-38EA-41AC-BFDA-96FB632D522E',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'Apple TV 4K',
+                udid: 'BCBB7E4B-D872-4D61-BC61-7C9805551075',
+              },
+              {
+                state: 'Shutdown',
+                availability: '(available)',
+                name: 'Apple TV 4K (at 1080p)',
+                udid: '1DE12308-1C14-4F0F-991E-A3ADC41BDFFC',
+              },
+            ],
           },
-          {
-            'state' : 'Shutdown',
-            'availability' : '(available)',
-            'name' : 'Apple TV 4K (at 1080p)',
-            'udid' : '1DE12308-1C14-4F0F-991E-A3ADC41BDFFC'
-          }
-        ]
-      }
-    },
-    'Apple TV'
-  )).toEqual({
-    udid: '816C30EA-38EA-41AC-BFDA-96FB632D522E',
-    name: 'Apple TV',
-    booted: true,
-    version: 'tvOS 11.2'
-  });
+        },
+        'Apple TV',
+      ),
+    ).toEqual({
+      udid: '816C30EA-38EA-41AC-BFDA-96FB632D522E',
+      name: 'Apple TV',
+      booted: true,
+      version: 'tvOS 11.2',
+    });
   });
 });
diff --git a/local-cli/runIOS/__tests__/findXcodeProject-test.js b/local-cli/runIOS/__tests__/findXcodeProject-test.js
index 305605feab23..7e63560b2b2e 100644
--- a/local-cli/runIOS/__tests__/findXcodeProject-test.js
+++ b/local-cli/runIOS/__tests__/findXcodeProject-test.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
+
 'use strict';
 
 jest.dontMock('../findXcodeProject');
@@ -14,44 +16,50 @@ const findXcodeProject = require('../findXcodeProject');
 
 describe('findXcodeProject', () => {
   it('should find *.xcodeproj file', () => {
-    expect(findXcodeProject([
-      '.DS_Store',
-      'AwesomeApp',
-      'AwesomeApp.xcodeproj',
-      'AwesomeAppTests',
-      'PodFile',
-      'Podfile.lock',
-      'Pods'
-    ])).toEqual({
+    expect(
+      findXcodeProject([
+        '.DS_Store',
+        'AwesomeApp',
+        'AwesomeApp.xcodeproj',
+        'AwesomeAppTests',
+        'PodFile',
+        'Podfile.lock',
+        'Pods',
+      ]),
+    ).toEqual({
       name: 'AwesomeApp.xcodeproj',
       isWorkspace: false,
     });
   });
 
   it('should prefer *.xcworkspace', () => {
-    expect(findXcodeProject([
-      '.DS_Store',
-      'AwesomeApp',
-      'AwesomeApp.xcodeproj',
-      'AwesomeApp.xcworkspace',
-      'AwesomeAppTests',
-      'PodFile',
-      'Podfile.lock',
-      'Pods'
-    ])).toEqual({
+    expect(
+      findXcodeProject([
+        '.DS_Store',
+        'AwesomeApp',
+        'AwesomeApp.xcodeproj',
+        'AwesomeApp.xcworkspace',
+        'AwesomeAppTests',
+        'PodFile',
+        'Podfile.lock',
+        'Pods',
+      ]),
+    ).toEqual({
       name: 'AwesomeApp.xcworkspace',
       isWorkspace: true,
     });
   });
 
   it('should return null if nothing found', () => {
-    expect(findXcodeProject([
-      '.DS_Store',
-      'AwesomeApp',
-      'AwesomeAppTests',
-      'PodFile',
-      'Podfile.lock',
-      'Pods'
-    ])).toEqual(null);
+    expect(
+      findXcodeProject([
+        '.DS_Store',
+        'AwesomeApp',
+        'AwesomeAppTests',
+        'PodFile',
+        'Podfile.lock',
+        'Pods',
+      ]),
+    ).toEqual(null);
   });
 });
diff --git a/local-cli/runIOS/__tests__/parseIOSDevicesList-test.js b/local-cli/runIOS/__tests__/parseIOSDevicesList-test.js
index aea241c8fe37..89fca8364ac7 100644
--- a/local-cli/runIOS/__tests__/parseIOSDevicesList-test.js
+++ b/local-cli/runIOS/__tests__/parseIOSDevicesList-test.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @emails oncall+javascript_foundation
  */
 
@@ -14,26 +15,34 @@ var parseIOSDevicesList = require('../parseIOSDevicesList');
 
 describe('parseIOSDevicesList', () => {
   it('parses typical output', () => {
-    var devices = parseIOSDevicesList([
-      'Known Devices:',
-      'Maxs MacBook Pro [11111111-1111-1111-1111-111111111111]',
-      "Max's iPhone (9.2) [11111111111111111111aaaaaaaaaaaaaaaaaaaa]",
-      'iPad 2 (9.3) [07538CE4-675B-4EDA-90F2-3DD3CD93309D] (Simulator)',
-      'iPad Air (9.3) [0745F6D1-6DC5-4427-B9A6-6FBA327ED65A] (Simulator)',
-      'iPhone 6s (9.3) [3DBE4ECF-9A86-469E-921B-EE0F9C9AB8F4] (Simulator)',
-      'Known Templates:',
-      'Activity Monitor',
-      'Blank',
-      'System Usage',
-      'Zombies'
-    ].join('\n'));
+    var devices = parseIOSDevicesList(
+      [
+        'Known Devices:',
+        'Maxs MacBook Pro [11111111-1111-1111-1111-111111111111]',
+        "Max's iPhone (9.2) [11111111111111111111aaaaaaaaaaaaaaaaaaaa]",
+        'iPad 2 (9.3) [07538CE4-675B-4EDA-90F2-3DD3CD93309D] (Simulator)',
+        'iPad Air (9.3) [0745F6D1-6DC5-4427-B9A6-6FBA327ED65A] (Simulator)',
+        'iPhone 6s (9.3) [3DBE4ECF-9A86-469E-921B-EE0F9C9AB8F4] (Simulator)',
+        'Known Templates:',
+        'Activity Monitor',
+        'Blank',
+        'System Usage',
+        'Zombies',
+      ].join('\n'),
+    );
 
     expect(devices).toEqual([
-      {name: "Max's iPhone", udid: '11111111111111111111aaaaaaaaaaaaaaaaaaaa', version: '9.2'},
+      {
+        name: "Max's iPhone",
+        udid: '11111111111111111111aaaaaaaaaaaaaaaaaaaa',
+        version: '9.2',
+      },
     ]);
   });
 
   it('ignores garbage', () => {
-    expect(parseIOSDevicesList('Something went terribly wrong (-42)')).toEqual([]);
+    expect(parseIOSDevicesList('Something went terribly wrong (-42)')).toEqual(
+      [],
+    );
   });
 });
diff --git a/local-cli/runIOS/findMatchingSimulator.js b/local-cli/runIOS/findMatchingSimulator.js
index 8b964ec7dba6..f4794c389f1f 100644
--- a/local-cli/runIOS/findMatchingSimulator.js
+++ b/local-cli/runIOS/findMatchingSimulator.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 /**
@@ -40,7 +43,7 @@ function findMatchingSimulator(simulators, simulatorName) {
           udid: simulator.udid,
           name: simulator.name,
           booted,
-          version
+          version,
         };
       }
       if (simulator.name === simulatorName && !match) {
@@ -48,7 +51,7 @@ function findMatchingSimulator(simulators, simulatorName) {
           udid: simulator.udid,
           name: simulator.name,
           booted,
-          version
+          version,
         };
       }
       // Keeps track of the first available simulator for use if we can't find one above.
@@ -57,7 +60,7 @@ function findMatchingSimulator(simulators, simulatorName) {
           udid: simulator.udid,
           name: simulator.name,
           booted,
-          version
+          version,
         };
       }
     }
diff --git a/local-cli/runIOS/findXcodeProject.js b/local-cli/runIOS/findXcodeProject.js
index ecb80b3d3da1..c154221b86cc 100644
--- a/local-cli/runIOS/findXcodeProject.js
+++ b/local-cli/runIOS/findXcodeProject.js
@@ -4,16 +4,18 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const path = require('path');
 
 type ProjectInfo = {
-  name: string;
-  isWorkspace: boolean;
-}
+  name: string,
+  isWorkspace: boolean,
+};
 
 function findXcodeProject(files: Array<string>): ?ProjectInfo {
   const sortedFiles = files.sort();
diff --git a/local-cli/runIOS/parseIOSDevicesList.js b/local-cli/runIOS/parseIOSDevicesList.js
index d0c10a3a5ea8..a85ea352f88a 100644
--- a/local-cli/runIOS/parseIOSDevicesList.js
+++ b/local-cli/runIOS/parseIOSDevicesList.js
@@ -4,25 +4,27 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 type IOSDeviceInfo = {
-  name: string;
-  udid: string;
-  version: string;
-}
+  name: string,
+  udid: string,
+  version: string,
+};
 
 /**
  * Parses the output of `xcrun simctl list devices` command
  */
 function parseIOSDevicesList(text: string): Array<IOSDeviceInfo> {
   const devices = [];
-  text.split('\n').forEach((line) => {
+  text.split('\n').forEach(line => {
     const device = line.match(/(.*?) \((.*?)\) \[(.*?)\]/);
     const noSimulator = line.match(/(.*?) \((.*?)\) \[(.*?)\] \((.*?)\)/);
-    if (device != null && noSimulator == null){
+    if (device != null && noSimulator == null) {
       var name = device[1];
       var version = device[2];
       var udid = device[3];
diff --git a/local-cli/runIOS/runIOS.js b/local-cli/runIOS/runIOS.js
index 61b6795d5ab5..f78700fffbc1 100644
--- a/local-cli/runIOS/runIOS.js
+++ b/local-cli/runIOS/runIOS.js
@@ -1,9 +1,12 @@
 /**
-* Copyright (c) 2015-present, Facebook, Inc.
-*
-* This source code is licensed under the MIT license found in the
-* LICENSE file in the root directory of this source tree.
-*/
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @format
+ */
+
 'use strict';
 
 const child_process = require('child_process');
@@ -13,7 +16,7 @@ const findXcodeProject = require('./findXcodeProject');
 const findReactNativeScripts = require('../util/findReactNativeScripts');
 const parseIOSDevicesList = require('./parseIOSDevicesList');
 const findMatchingSimulator = require('./findMatchingSimulator');
-const getBuildPath = function (configuration = 'Debug', appName, isDevice) {
+const getBuildPath = function(configuration = 'Debug', appName, isDevice) {
   let device;
 
   if (isDevice) {
@@ -29,7 +32,7 @@ const getBuildPath = function (configuration = 'Debug', appName, isDevice) {
 const xcprettyAvailable = function() {
   try {
     child_process.execSync('xcpretty --version', {
-      stdio: [ 0, 'pipe', 'ignore', ]
+      stdio: [0, 'pipe', 'ignore'],
     });
   } catch (error) {
     return false;
@@ -44,11 +47,13 @@ function runIOS(argv, config, args) {
       child_process.spawnSync(
         reactNativeScriptsPath,
         ['ios'].concat(process.argv.slice(1)),
-        {stdio: 'inherit'}
+        {stdio: 'inherit'},
       );
       return;
     } else {
-      throw new Error('iOS project folder not found. Are you sure this is a React Native project?');
+      throw new Error(
+        'iOS project folder not found. Are you sure this is a React Native project?',
+      );
     }
   }
   process.chdir(args.projectPath);
@@ -57,19 +62,38 @@ function runIOS(argv, config, args) {
     throw new Error('Could not find Xcode project files in ios folder');
   }
 
-  const inferredSchemeName = path.basename(xcodeProject.name, path.extname(xcodeProject.name));
+  const inferredSchemeName = path.basename(
+    xcodeProject.name,
+    path.extname(xcodeProject.name),
+  );
   const scheme = args.scheme || inferredSchemeName;
-  console.log(`Found Xcode ${xcodeProject.isWorkspace ? 'workspace' : 'project'} ${xcodeProject.name}`);
+  console.log(
+    `Found Xcode ${xcodeProject.isWorkspace ? 'workspace' : 'project'} ${
+      xcodeProject.name
+    }`,
+  );
   const devices = parseIOSDevicesList(
-    child_process.execFileSync('xcrun', ['instruments', '-s'], {encoding: 'utf8'})
+    child_process.execFileSync('xcrun', ['instruments', '-s'], {
+      encoding: 'utf8',
+    }),
   );
   if (args.device) {
     const selectedDevice = matchingDevice(devices, args.device);
     if (selectedDevice) {
-      return runOnDevice(selectedDevice, scheme, xcodeProject, args.configuration, args.packager, args.verbose, args.port);
+      return runOnDevice(
+        selectedDevice,
+        scheme,
+        xcodeProject,
+        args.configuration,
+        args.packager,
+        args.verbose,
+        args.port,
+      );
     } else {
       if (devices && devices.length > 0) {
-        console.log('Could not find device with the name: "' + args.device + '".');
+        console.log(
+          'Could not find device with the name: "' + args.device + '".',
+        );
         console.log('Choose one of the following:');
         printFoundDevices(devices);
       } else {
@@ -86,7 +110,15 @@ function runIOS(argv, config, args) {
 function runOnDeviceByUdid(args, scheme, xcodeProject, devices) {
   const selectedDevice = matchingDeviceByUdid(devices, args.udid);
   if (selectedDevice) {
-    return runOnDevice(selectedDevice, scheme, xcodeProject, args.configuration, args.packager, args.verbose, args.port);
+    return runOnDevice(
+      selectedDevice,
+      scheme,
+      xcodeProject,
+      args.configuration,
+      args.packager,
+      args.verbose,
+      args.port,
+    );
   } else {
     if (devices && devices.length > 0) {
       console.log('Could not find device with the udid: "' + args.udid + '".');
@@ -99,10 +131,14 @@ function runOnDeviceByUdid(args, scheme, xcodeProject, devices) {
 }
 
 function runOnSimulator(xcodeProject, args, scheme) {
-  return new Promise((resolve) => {
+  return new Promise(resolve => {
     try {
       var simulators = JSON.parse(
-      child_process.execFileSync('xcrun', ['simctl', 'list', '--json', 'devices'], {encoding: 'utf8'})
+        child_process.execFileSync(
+          'xcrun',
+          ['simctl', 'list', '--json', 'devices'],
+          {encoding: 'utf8'},
+        ),
       );
     } catch (e) {
       throw new Error('Could not parse the simulator list output');
@@ -112,71 +148,110 @@ function runOnSimulator(xcodeProject, args, scheme) {
     if (!selectedSimulator) {
       throw new Error(`Could not find ${args.simulator} simulator`);
     }
-    
+
     /**
-		 * Booting simulator through `xcrun simctl boot` will boot it in the `headless` mode
-		 * (running in the background).
-		 *
-		 * In order for user to see the app and the simulator itself, we have to make sure
-		 * that the Simulator.app is running.
-		 *
-		 * We also pass it `-CurrentDeviceUDID` so that when we launch it for the first time,
-		 * it will not boot the "default" device, but the one we set. If the app is already running,
-		 * this flag has no effect.
-		 */
-		child_process.execFileSync('open', [
-			'/Applications/Xcode.app/Contents/Developer/Applications/Simulator.app',
-			'--args',
-			'-CurrentDeviceUDID',
-			selectedSimulator.udid
-		]);
+     * Booting simulator through `xcrun simctl boot` will boot it in the `headless` mode
+     * (running in the background).
+     *
+     * In order for user to see the app and the simulator itself, we have to make sure
+     * that the Simulator.app is running.
+     *
+     * We also pass it `-CurrentDeviceUDID` so that when we launch it for the first time,
+     * it will not boot the "default" device, but the one we set. If the app is already running,
+     * this flag has no effect.
+     */
+    child_process.execFileSync('open', [
+      '/Applications/Xcode.app/Contents/Developer/Applications/Simulator.app',
+      '--args',
+      '-CurrentDeviceUDID',
+      selectedSimulator.udid,
+    ]);
 
     if (!selectedSimulator.booted) {
       const simulatorFullName = formattedDeviceName(selectedSimulator);
       console.log(`Launching ${simulatorFullName}...`);
       try {
-        child_process.spawnSync('xcrun', ['instruments', '-w', selectedSimulator.udid]);
+        child_process.spawnSync('xcrun', [
+          'instruments',
+          '-w',
+          selectedSimulator.udid,
+        ]);
       } catch (e) {
         // instruments always fail with 255 because it expects more arguments,
         // but we want it to only launch the simulator
       }
     }
 
-    buildProject(xcodeProject, selectedSimulator.udid, scheme, args.configuration, args.packager, args.verbose, args.port)
-      .then((appName) => resolve({ udid: selectedSimulator.udid, appName }));
-  })
-  .then(({udid, appName}) => {
+    buildProject(
+      xcodeProject,
+      selectedSimulator.udid,
+      scheme,
+      args.configuration,
+      args.packager,
+      args.verbose,
+      args.port,
+    ).then(appName => resolve({udid: selectedSimulator.udid, appName}));
+  }).then(({udid, appName}) => {
     if (!appName) {
       appName = scheme;
     }
     let appPath = getBuildPath(args.configuration, appName);
     console.log(`Installing ${appPath}`);
-    child_process.spawnSync('xcrun', ['simctl', 'install', udid, appPath], {stdio: 'inherit'});
+    child_process.spawnSync('xcrun', ['simctl', 'install', udid, appPath], {
+      stdio: 'inherit',
+    });
 
-    const bundleID = child_process.execFileSync(
-      '/usr/libexec/PlistBuddy',
-      ['-c', 'Print:CFBundleIdentifier', path.join(appPath, 'Info.plist')],
-      {encoding: 'utf8'}
-    ).trim();
+    const bundleID = child_process
+      .execFileSync(
+        '/usr/libexec/PlistBuddy',
+        ['-c', 'Print:CFBundleIdentifier', path.join(appPath, 'Info.plist')],
+        {encoding: 'utf8'},
+      )
+      .trim();
 
     console.log(`Launching ${bundleID}`);
-    child_process.spawnSync('xcrun', ['simctl', 'launch', udid, bundleID], {stdio: 'inherit'});
+    child_process.spawnSync('xcrun', ['simctl', 'launch', udid, bundleID], {
+      stdio: 'inherit',
+    });
   });
 }
 
-function runOnDevice(selectedDevice, scheme, xcodeProject, configuration, launchPackager, verbose, port) {
-  return buildProject(xcodeProject, selectedDevice.udid, scheme, configuration, launchPackager, verbose, port)
-  .then((appName) => {
+function runOnDevice(
+  selectedDevice,
+  scheme,
+  xcodeProject,
+  configuration,
+  launchPackager,
+  verbose,
+  port,
+) {
+  return buildProject(
+    xcodeProject,
+    selectedDevice.udid,
+    scheme,
+    configuration,
+    launchPackager,
+    verbose,
+    port,
+  ).then(appName => {
     if (!appName) {
       appName = scheme;
     }
     const iosDeployInstallArgs = [
-      '--bundle', getBuildPath(configuration, appName, true),
-      '--id' , selectedDevice.udid,
-      '--justlaunch'
+      '--bundle',
+      getBuildPath(configuration, appName, true),
+      '--id',
+      selectedDevice.udid,
+      '--justlaunch',
     ];
-    console.log(`installing and launching your app on ${selectedDevice.name}...`);
-    const iosDeployOutput = child_process.spawnSync('ios-deploy', iosDeployInstallArgs, {encoding: 'utf8'});
+    console.log(
+      `installing and launching your app on ${selectedDevice.name}...`,
+    );
+    const iosDeployOutput = child_process.spawnSync(
+      'ios-deploy',
+      iosDeployInstallArgs,
+      {encoding: 'utf8'},
+    );
     if (iosDeployOutput.error) {
       console.log('');
       console.log('** INSTALLATION FAILED **');
@@ -188,22 +263,42 @@ function runOnDevice(selectedDevice, scheme, xcodeProject, configuration, launch
   });
 }
 
-function buildProject(xcodeProject, udid, scheme, configuration = 'Debug', launchPackager = false, verbose, port) {
-  return new Promise((resolve,reject) =>
-  {
-     var xcodebuildArgs = [
-      xcodeProject.isWorkspace ? '-workspace' : '-project', xcodeProject.name,
-      '-configuration', configuration,
-      '-scheme', scheme,
-      '-destination', `id=${udid}`,
-      '-derivedDataPath', 'build',
+function buildProject(
+  xcodeProject,
+  udid,
+  scheme,
+  configuration = 'Debug',
+  launchPackager = false,
+  verbose,
+  port,
+) {
+  return new Promise((resolve, reject) => {
+    var xcodebuildArgs = [
+      xcodeProject.isWorkspace ? '-workspace' : '-project',
+      xcodeProject.name,
+      '-configuration',
+      configuration,
+      '-scheme',
+      scheme,
+      '-destination',
+      `id=${udid}`,
+      '-derivedDataPath',
+      'build',
     ];
     console.log(`Building using "xcodebuild ${xcodebuildArgs.join(' ')}"`);
     let xcpretty;
     if (!verbose) {
-      xcpretty = xcprettyAvailable() && child_process.spawn('xcpretty', [], { stdio: ['pipe', process.stdout, process.stderr] });
+      xcpretty =
+        xcprettyAvailable() &&
+        child_process.spawn('xcpretty', [], {
+          stdio: ['pipe', process.stdout, process.stderr],
+        });
     }
-    const buildProcess = child_process.spawn('xcodebuild', xcodebuildArgs, getProcessOptions(launchPackager, port));
+    const buildProcess = child_process.spawn(
+      'xcodebuild',
+      xcodebuildArgs,
+      getProcessOptions(launchPackager, port),
+    );
     let buildOutput = '';
     buildProcess.stdout.on('data', function(data) {
       buildOutput += data.toString();
@@ -221,9 +316,15 @@ function buildProject(xcodeProject, udid, scheme, configuration = 'Debug', launc
         xcpretty.stdin.end();
       }
       //FULL_PRODUCT_NAME is the actual file name of the app, which actually comes from the Product Name in the build config, which does not necessary match a scheme name,  example output line: export FULL_PRODUCT_NAME="Super App Dev.app"
-      let productNameMatch = /export FULL_PRODUCT_NAME="?(.+).app"?$/m.exec(buildOutput);
-      if (productNameMatch && productNameMatch.length && productNameMatch.length > 1) {
-        return resolve(productNameMatch[1]);//0 is the full match, 1 is the app name
+      let productNameMatch = /export FULL_PRODUCT_NAME="?(.+).app"?$/m.exec(
+        buildOutput,
+      );
+      if (
+        productNameMatch &&
+        productNameMatch.length &&
+        productNameMatch.length > 1
+      ) {
+        return resolve(productNameMatch[1]); //0 is the full match, 1 is the app name
       }
       return buildProcess.error ? reject(buildProcess.error) : resolve();
     });
@@ -231,13 +332,19 @@ function buildProject(xcodeProject, udid, scheme, configuration = 'Debug', launc
 }
 
 function matchingDevice(devices, deviceName) {
-  if (deviceName === true && devices.length === 1)
-  {
-    console.log(`Using first available device ${devices[0].name} due to lack of name supplied.`);
+  if (deviceName === true && devices.length === 1) {
+    console.log(
+      `Using first available device ${
+        devices[0].name
+      } due to lack of name supplied.`,
+    );
     return devices[0];
   }
   for (let i = devices.length - 1; i >= 0; i--) {
-    if (devices[i].name === deviceName || formattedDeviceName(devices[i]) === deviceName) {
+    if (
+      devices[i].name === deviceName ||
+      formattedDeviceName(devices[i]) === deviceName
+    ) {
       return devices[i];
     }
   }
@@ -264,12 +371,12 @@ function printFoundDevices(devices) {
 function getProcessOptions(launchPackager, port) {
   if (launchPackager) {
     return {
-      env: { ...process.env, RCT_METRO_PORT: port }
+      env: {...process.env, RCT_METRO_PORT: port},
     };
   }
 
   return {
-    env: { ...process.env, RCT_NO_LAUNCH_PACKAGER: true },
+    env: {...process.env, RCT_NO_LAUNCH_PACKAGER: true},
   };
 }
 
@@ -278,53 +385,66 @@ module.exports = {
   description: 'builds your app and starts it on iOS simulator',
   func: runIOS,
   examples: [
-  {
-    desc: 'Run on a different simulator, e.g. iPhone 5',
-    cmd: 'react-native run-ios --simulator "iPhone 5"',
-  },
-  {
-    desc: 'Pass a non-standard location of iOS directory',
-    cmd: 'react-native run-ios --project-path "./app/ios"',
-  },
-  {
-    desc: "Run on a connected device, e.g. Max's iPhone",
-    cmd: 'react-native run-ios --device "Max\'s iPhone"',
-  },
-  {
-    desc: 'Run on the AppleTV simulator',
-    cmd: 'react-native run-ios --simulator "Apple TV"  --scheme "helloworld-tvOS"',
-  }
+    {
+      desc: 'Run on a different simulator, e.g. iPhone 5',
+      cmd: 'react-native run-ios --simulator "iPhone 5"',
+    },
+    {
+      desc: 'Pass a non-standard location of iOS directory',
+      cmd: 'react-native run-ios --project-path "./app/ios"',
+    },
+    {
+      desc: "Run on a connected device, e.g. Max's iPhone",
+      cmd: 'react-native run-ios --device "Max\'s iPhone"',
+    },
+    {
+      desc: 'Run on the AppleTV simulator',
+      cmd:
+        'react-native run-ios --simulator "Apple TV"  --scheme "helloworld-tvOS"',
+    },
+  ],
+  options: [
+    {
+      command: '--simulator [string]',
+      description: 'Explicitly set simulator to use',
+      default: 'iPhone 6',
+    },
+    {
+      command: '--configuration [string]',
+      description: 'Explicitly set the scheme configuration to use',
+    },
+    {
+      command: '--scheme [string]',
+      description: 'Explicitly set Xcode scheme to use',
+    },
+    {
+      command: '--project-path [string]',
+      description:
+        'Path relative to project root where the Xcode project ' +
+        "(.xcodeproj) lives. The default is 'ios'.",
+      default: 'ios',
+    },
+    {
+      command: '--device [string]',
+      description:
+        'Explicitly set device to use by name.  The value is not required if you have a single device connected.',
+    },
+    {
+      command: '--udid [string]',
+      description: 'Explicitly set device to use by udid',
+    },
+    {
+      command: '--no-packager',
+      description: 'Do not launch packager while building',
+    },
+    {
+      command: '--verbose',
+      description: 'Do not use xcpretty even if installed',
+    },
+    {
+      command: '--port [number]',
+      default: process.env.RCT_METRO_PORT || 8081,
+      parse: (val: string) => Number(val),
+    },
   ],
-  options: [{
-    command: '--simulator [string]',
-    description: 'Explicitly set simulator to use',
-    default: 'iPhone 6',
-  } , {
-    command: '--configuration [string]',
-    description: 'Explicitly set the scheme configuration to use',
-  } , {
-    command: '--scheme [string]',
-    description: 'Explicitly set Xcode scheme to use',
-  }, {
-    command: '--project-path [string]',
-    description: 'Path relative to project root where the Xcode project '
-      + '(.xcodeproj) lives. The default is \'ios\'.',
-    default: 'ios',
-  }, {
-    command: '--device [string]',
-    description: 'Explicitly set device to use by name.  The value is not required if you have a single device connected.',
-  }, {
-    command: '--udid [string]',
-    description: 'Explicitly set device to use by udid',
-  }, {
-    command: '--no-packager',
-    description: 'Do not launch packager while building',
-  }, {
-    command: '--verbose',
-    description: 'Do not use xcpretty even if installed',
-  },{
-    command: '--port [number]',
-    default: process.env.RCT_METRO_PORT || 8081,
-    parse: (val: string) => Number(val),
-  }],
 };
diff --git a/local-cli/server/checkNodeVersion.js b/local-cli/server/checkNodeVersion.js
index 46ec6cdc2f78..8917be55c65c 100644
--- a/local-cli/server/checkNodeVersion.js
+++ b/local-cli/server/checkNodeVersion.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 var chalk = require('chalk');
@@ -12,12 +15,14 @@ var semver = require('semver');
 
 module.exports = function() {
   if (!semver.satisfies(process.version, '>=4')) {
-    var engine = semver.satisfies(process.version, '<1')
-      ? 'Node'
-      : 'io.js';
+    var engine = semver.satisfies(process.version, '<1') ? 'Node' : 'io.js';
 
-    var message = 'You are currently running ' + engine + ' ' +
-      process.version + '.\n' +
+    var message =
+      'You are currently running ' +
+      engine +
+      ' ' +
+      process.version +
+      '.\n' +
       '\n' +
       'React Native runs on Node 4.0 or newer. There are several ways to ' +
       'upgrade Node.js depending on your preference.\n' +
@@ -28,12 +33,14 @@ module.exports = function() {
       '\n' +
       'About Node.js:   https://nodejs.org\n' +
       'Follow along at: https://github.com/facebook/react-native/issues/2545';
-    console.log(formatBanner(message, {
-      chalkFunction: chalk.green,
-      marginLeft: 1,
-      marginRight: 1,
-      paddingBottom: 1,
-    }));
+    console.log(
+      formatBanner(message, {
+        chalkFunction: chalk.green,
+        marginLeft: 1,
+        marginRight: 1,
+        paddingBottom: 1,
+      }),
+    );
     process.exit(1);
   }
 };
diff --git a/local-cli/server/middleware/copyToClipBoardMiddleware.js b/local-cli/server/middleware/copyToClipBoardMiddleware.js
index 723fbd30c881..3f04c69a1584 100644
--- a/local-cli/server/middleware/copyToClipBoardMiddleware.js
+++ b/local-cli/server/middleware/copyToClipBoardMiddleware.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const copyToClipBoard = require('../util/copyToClipBoard');
diff --git a/local-cli/server/middleware/indexPage.js b/local-cli/server/middleware/indexPage.js
index dee12456db2a..55b55c0f7922 100644
--- a/local-cli/server/middleware/indexPage.js
+++ b/local-cli/server/middleware/indexPage.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fs = require('fs');
diff --git a/local-cli/server/middleware/loadRawBodyMiddleware.js b/local-cli/server/middleware/loadRawBodyMiddleware.js
index 924275009ebe..1530c28fa84c 100644
--- a/local-cli/server/middleware/loadRawBodyMiddleware.js
+++ b/local-cli/server/middleware/loadRawBodyMiddleware.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 module.exports = function(req, res, next) {
diff --git a/local-cli/server/middleware/openStackFrameInEditorMiddleware.js b/local-cli/server/middleware/openStackFrameInEditorMiddleware.js
index 471c8ed8bbef..290969ac6f40 100644
--- a/local-cli/server/middleware/openStackFrameInEditorMiddleware.js
+++ b/local-cli/server/middleware/openStackFrameInEditorMiddleware.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const launchEditor = require('../util/launchEditor');
diff --git a/local-cli/server/middleware/statusPageMiddleware.js b/local-cli/server/middleware/statusPageMiddleware.js
index cd8fb80200c1..bbc189223ff9 100644
--- a/local-cli/server/middleware/statusPageMiddleware.js
+++ b/local-cli/server/middleware/statusPageMiddleware.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 /**
diff --git a/local-cli/server/middleware/systraceProfileMiddleware.js b/local-cli/server/middleware/systraceProfileMiddleware.js
index fc1669468f80..dbf71d41d8cb 100644
--- a/local-cli/server/middleware/systraceProfileMiddleware.js
+++ b/local-cli/server/middleware/systraceProfileMiddleware.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fs = require('fs');
@@ -18,7 +21,9 @@ module.exports = function(req, res, next) {
   var dumpName = '/tmp/dump_' + Date.now() + '.json';
   fs.writeFileSync(dumpName, req.rawBody);
   var response =
-    'Your profile was saved at:\n' + dumpName + '\n\n' +
+    'Your profile was saved at:\n' +
+    dumpName +
+    '\n\n' +
     'On Google Chrome navigate to chrome://tracing and then click on "load" ' +
     'to load and visualise your profile.\n\n' +
     'This message is also printed to your console by the packager so you can copy it :)';
diff --git a/local-cli/server/middleware/unless.js b/local-cli/server/middleware/unless.js
index acf0643cf3a0..016adfa7f22a 100644
--- a/local-cli/server/middleware/unless.js
+++ b/local-cli/server/middleware/unless.js
@@ -3,11 +3,14 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 module.exports = (url, middleware) => {
-  return (req, res, next) =>  {
+  return (req, res, next) => {
     if (req.url === url || req.url.startsWith(url + '/')) {
       middleware(req, res, next);
     } else {
diff --git a/local-cli/server/server.js b/local-cli/server/server.js
index 7711e8590afc..b1b3851b3ff7 100644
--- a/local-cli/server/server.js
+++ b/local-cli/server/server.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -56,80 +57,106 @@ module.exports = {
   name: 'start',
   func: server,
   description: 'starts the webserver',
-  options: [{
-    command: '--port [number]',
-    default: process.env.RCT_METRO_PORT || 8081,
-    parse: (val: string) => Number(val),
-  }, {
-    command: '--host [string]',
-    default: '',
-  }, {
-    command: '--root [list]',
-    description: 'add another root(s) to be used by the packager in this project',
-    parse: (val: string) => val.split(',').map(root => path.resolve(root)),
-    default: [],
-  }, {
-    command: '--projectRoots [list]',
-    description: 'override the root(s) to be used by the packager',
-    parse: (val: string) => val.split(','),
-    default: (config: ConfigT) => config.getProjectRoots(),
-  }, {
-    command: '--assetExts [list]',
-    description: 'Specify any additional asset extensions to be used by the packager',
-    parse: (val: string) => val.split(','),
-    default: (config: ConfigT) => config.getAssetExts(),
-  }, {
-    command: '--sourceExts [list]',
-    description: 'Specify any additional source extensions to be used by the packager',
-    parse: (val: string) => val.split(','),
-    default: (config: ConfigT) => config.getSourceExts(),
-  }, {
-    command: '--platforms [list]',
-    description: 'Specify any additional platforms to be used by the packager',
-    parse: (val: string) => val.split(','),
-    default: (config: ConfigT) => config.getPlatforms(),
-  }, {
-    command: '--providesModuleNodeModules [list]',
-    description: 'Specify any npm packages that import dependencies with providesModule',
-    parse: (val: string) => val.split(','),
-    default: (config: RNConfig) => {
-      if (typeof config.getProvidesModuleNodeModules === 'function') {
-        return config.getProvidesModuleNodeModules();
-      }
-      return null;
-    },
-  }, {
-    command: '--max-workers [number]',
-    description: 'Specifies the maximum number of workers the worker-pool ' +
-      'will spawn for transforming files. This defaults to the number of the ' +
-      'cores available on your machine.',
-    parse: (workers: string) => Number(workers),
-  }, {
-    command: '--skipflow',
-    description: 'Disable flow checks'
-  }, {
-    command: '--nonPersistent',
-    description: 'Disable file watcher'
-  }, {
-    command: '--transformer [string]',
-    description: 'Specify a custom transformer to be used'
-  }, {
-    command: '--reset-cache, --resetCache',
-    description: 'Removes cached files',
-  }, {
-    command: '--custom-log-reporter-path, --customLogReporterPath [string]',
-    description: 'Path to a JavaScript file that exports a log reporter as a replacement for TerminalReporter',
-  }, {
-    command: '--verbose',
-    description: 'Enables logging',
-  }, {
-    command: '--https',
-    description: 'Enables https connections to the server',
-  }, {
-    command: '--key [path]',
-    description: 'Path to custom SSL key',
-  }, {
-    command: '--cert [path]',
-    description: 'Path to custom SSL cert',
-  }],
+  options: [
+    {
+      command: '--port [number]',
+      default: process.env.RCT_METRO_PORT || 8081,
+      parse: (val: string) => Number(val),
+    },
+    {
+      command: '--host [string]',
+      default: '',
+    },
+    {
+      command: '--root [list]',
+      description:
+        'add another root(s) to be used by the packager in this project',
+      parse: (val: string) => val.split(',').map(root => path.resolve(root)),
+      default: [],
+    },
+    {
+      command: '--projectRoots [list]',
+      description: 'override the root(s) to be used by the packager',
+      parse: (val: string) => val.split(','),
+      default: (config: ConfigT) => config.getProjectRoots(),
+    },
+    {
+      command: '--assetExts [list]',
+      description:
+        'Specify any additional asset extensions to be used by the packager',
+      parse: (val: string) => val.split(','),
+      default: (config: ConfigT) => config.getAssetExts(),
+    },
+    {
+      command: '--sourceExts [list]',
+      description:
+        'Specify any additional source extensions to be used by the packager',
+      parse: (val: string) => val.split(','),
+      default: (config: ConfigT) => config.getSourceExts(),
+    },
+    {
+      command: '--platforms [list]',
+      description:
+        'Specify any additional platforms to be used by the packager',
+      parse: (val: string) => val.split(','),
+      default: (config: ConfigT) => config.getPlatforms(),
+    },
+    {
+      command: '--providesModuleNodeModules [list]',
+      description:
+        'Specify any npm packages that import dependencies with providesModule',
+      parse: (val: string) => val.split(','),
+      default: (config: RNConfig) => {
+        if (typeof config.getProvidesModuleNodeModules === 'function') {
+          return config.getProvidesModuleNodeModules();
+        }
+        return null;
+      },
+    },
+    {
+      command: '--max-workers [number]',
+      description:
+        'Specifies the maximum number of workers the worker-pool ' +
+        'will spawn for transforming files. This defaults to the number of the ' +
+        'cores available on your machine.',
+      parse: (workers: string) => Number(workers),
+    },
+    {
+      command: '--skipflow',
+      description: 'Disable flow checks',
+    },
+    {
+      command: '--nonPersistent',
+      description: 'Disable file watcher',
+    },
+    {
+      command: '--transformer [string]',
+      description: 'Specify a custom transformer to be used',
+    },
+    {
+      command: '--reset-cache, --resetCache',
+      description: 'Removes cached files',
+    },
+    {
+      command: '--custom-log-reporter-path, --customLogReporterPath [string]',
+      description:
+        'Path to a JavaScript file that exports a log reporter as a replacement for TerminalReporter',
+    },
+    {
+      command: '--verbose',
+      description: 'Enables logging',
+    },
+    {
+      command: '--https',
+      description: 'Enables https connections to the server',
+    },
+    {
+      command: '--key [path]',
+      description: 'Path to custom SSL key',
+    },
+    {
+      command: '--cert [path]',
+      description: 'Path to custom SSL cert',
+    },
+  ],
 };
diff --git a/local-cli/server/util/copyToClipBoard.js b/local-cli/server/util/copyToClipBoard.js
index bb2259e81503..0dbf3a786835 100644
--- a/local-cli/server/util/copyToClipBoard.js
+++ b/local-cli/server/util/copyToClipBoard.js
@@ -3,13 +3,16 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 var child_process = require('child_process');
 var spawn = child_process.spawn;
 var path = require('path');
-var fs  = require('fs');
+var fs = require('fs');
 
 const xsel = path.join(__dirname, 'external/xsel');
 fs.chmodSync(xsel, '0755');
@@ -18,20 +21,20 @@ fs.chmodSync(xsel, '0755');
  */
 function copyToClipBoard(content) {
   switch (process.platform) {
-  case 'darwin':
-    var child = spawn('pbcopy', []);
-    child.stdin.end(new Buffer(content, 'utf8'));
-    return true;
-  case 'win32':
-    var child = spawn('clip', []);
-    child.stdin.end(new Buffer(content, 'utf8'));
-    return true;
-  case 'linux':
-    var child = spawn(xsel, ['--clipboard', '--input']);
-    child.stdin.end(new Buffer(content, 'utf8'));
-    return true;
-  default:
-    return false;
+    case 'darwin':
+      var child = spawn('pbcopy', []);
+      child.stdin.end(new Buffer(content, 'utf8'));
+      return true;
+    case 'win32':
+      var child = spawn('clip', []);
+      child.stdin.end(new Buffer(content, 'utf8'));
+      return true;
+    case 'linux':
+      var child = spawn(xsel, ['--clipboard', '--input']);
+      child.stdin.end(new Buffer(content, 'utf8'));
+      return true;
+    default:
+      return false;
   }
 }
 
diff --git a/local-cli/server/util/debugger-ui/debuggerWorker.js b/local-cli/server/util/debugger-ui/debuggerWorker.js
index e70ca0ec9735..ad820c16fc02 100644
--- a/local-cli/server/util/debugger-ui/debuggerWorker.js
+++ b/local-cli/server/util/debugger-ui/debuggerWorker.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /* global __fbBatchedBridge, self, importScripts, postMessage, onmessage: true */
@@ -22,14 +24,14 @@ onmessage = (function() {
       hasWarned = true;
       console.warn(
         'Remote debugger is in a background tab which may cause apps to ' +
-        'perform slowly. Fix this by foregrounding the tab (or opening it in ' +
-        'a separate window).'
+          'perform slowly. Fix this by foregrounding the tab (or opening it in ' +
+          'a separate window).',
       );
     };
   })();
 
   var messageHandlers = {
-    'executeApplicationScript': function(message, sendReply) {
+    executeApplicationScript: function(message, sendReply) {
       for (var key in message.inject) {
         self[key] = JSON.parse(message.inject[key]);
       }
@@ -41,7 +43,7 @@ onmessage = (function() {
       }
       sendReply(null /* result */, error);
     },
-    'setDebuggerVisibility': function(message) {
+    setDebuggerVisibility: function(message) {
       visibilityState = message.visibilityState;
     },
   };
@@ -67,7 +69,10 @@ onmessage = (function() {
       var error;
       try {
         if (typeof __fbBatchedBridge === 'object') {
-          returnValue = __fbBatchedBridge[object.method].apply(null, object.arguments);
+          returnValue = __fbBatchedBridge[object.method].apply(
+            null,
+            object.arguments,
+          );
         } else {
           error = 'Failed to call function, __fbBatchedBridge is undefined';
         }
diff --git a/local-cli/server/util/jsPackagerClient.js b/local-cli/server/util/jsPackagerClient.js
index 3b449db160e4..0052198228dd 100644
--- a/local-cli/server/util/jsPackagerClient.js
+++ b/local-cli/server/util/jsPackagerClient.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -47,43 +48,51 @@ class JsPackagerClient {
   }
 
   sendRequest(method, target, params) {
-    return this.openPromise.then(() => new Promise((resolve, reject) => {
-      const messageId = getMessageId();
-      this.msgCallbacks.set(messageId, {resolve: resolve, reject: reject});
-      this.ws.send(
-        JSON.stringify({
-          version: PROTOCOL_VERSION,
-          target: target,
-          method: method,
-          id: messageId,
-          params: params,
+    return this.openPromise.then(
+      () =>
+        new Promise((resolve, reject) => {
+          const messageId = getMessageId();
+          this.msgCallbacks.set(messageId, {resolve: resolve, reject: reject});
+          this.ws.send(
+            JSON.stringify({
+              version: PROTOCOL_VERSION,
+              target: target,
+              method: method,
+              id: messageId,
+              params: params,
+            }),
+            error => {
+              if (error !== undefined) {
+                this.msgCallbacks.delete(messageId);
+                reject(error);
+              }
+            },
+          );
         }),
-        error => {
-          if (error !== undefined) {
-            this.msgCallbacks.delete(messageId);
-            reject(error);
-          }
-        });
-    }));
+    );
   }
 
   sendNotification(method, target, params) {
-    return this.openPromise.then(() => new Promise((resolve, reject) => {
-      this.ws.send(
-        JSON.stringify({
-          version: PROTOCOL_VERSION,
-          target: target,
-          method: method,
-          params: params,
+    return this.openPromise.then(
+      () =>
+        new Promise((resolve, reject) => {
+          this.ws.send(
+            JSON.stringify({
+              version: PROTOCOL_VERSION,
+              target: target,
+              method: method,
+              params: params,
+            }),
+            error => {
+              if (error !== undefined) {
+                reject(error);
+              } else {
+                resolve();
+              }
+            },
+          );
         }),
-        error => {
-          if (error !== undefined) {
-            reject(error);
-          } else {
-            resolve();
-          }
-        });
-    }));
+    );
   }
 
   sendBroadcast(method, params) {
@@ -92,16 +101,16 @@ class JsPackagerClient {
 
   getPeers() {
     return new Promise((resolve, reject) => {
-      this.sendRequest('getpeers', TARGET_SERVER, undefined).then(
-        response => {
-          if (!response instanceof Map) {
-            reject('Results received from server are of wrong format:\n' +
-                   JSON.stringify(response));
-          } else {
-            resolve(response);
-          }
-        },
-        reject);
+      this.sendRequest('getpeers', TARGET_SERVER, undefined).then(response => {
+        if (!response instanceof Map) {
+          reject(
+            'Results received from server are of wrong format:\n' +
+              JSON.stringify(response),
+          );
+        } else {
+          resolve(response);
+        }
+      }, reject);
     });
   }
 
diff --git a/local-cli/server/util/launchChrome.js b/local-cli/server/util/launchChrome.js
index 6999a3d0bdd0..f37f06b088c0 100644
--- a/local-cli/server/util/launchChrome.js
+++ b/local-cli/server/util/launchChrome.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
@@ -14,11 +16,16 @@
 const opn = require('opn');
 const execSync = require('child_process').execSync;
 
-function commandExistsUnixSync (commandName, callback) {
+function commandExistsUnixSync(commandName, callback) {
   try {
-    var stdout = execSync('command -v ' + commandName +
-          ' 2>/dev/null' +
-          ' && { echo >&1 \'' + commandName + ' found\'; exit 0; }');
+    var stdout = execSync(
+      'command -v ' +
+        commandName +
+        ' 2>/dev/null' +
+        " && { echo >&1 '" +
+        commandName +
+        " found'; exit 0; }",
+    );
     return !!stdout;
   } catch (error) {
     return false;
@@ -27,20 +34,20 @@ function commandExistsUnixSync (commandName, callback) {
 
 function getChromeAppName(): string {
   switch (process.platform) {
-  case 'darwin':
-    return 'google chrome';
-  case 'win32':
-    return 'chrome';
-  case 'linux':
-    if (commandExistsUnixSync('google-chrome')) {
+    case 'darwin':
+      return 'google chrome';
+    case 'win32':
+      return 'chrome';
+    case 'linux':
+      if (commandExistsUnixSync('google-chrome')) {
+        return 'google-chrome';
+      } else if (commandExistsUnixSync('chromium-browser')) {
+        return 'chromium-browser';
+      } else {
+        return 'chromium';
+      }
+    default:
       return 'google-chrome';
-    } else if (commandExistsUnixSync('chromium-browser')) {
-      return 'chromium-browser';
-    } else {
-      return 'chromium';
-    }
-  default:
-    return 'google-chrome';
   }
 }
 
diff --git a/local-cli/server/util/launchEditor.js b/local-cli/server/util/launchEditor.js
index f78927d82d6e..8b9f1729e10f 100644
--- a/local-cli/server/util/launchEditor.js
+++ b/local-cli/server/util/launchEditor.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 var chalk = require('chalk');
@@ -71,7 +74,10 @@ function getArgumentsForLineNumber(editor, fileName, lineNumber, workspace) {
     case 'mine':
       return ['--line', lineNumber, fileName];
     case 'code':
-      return addWorkspaceToArgumentsIfExists(['-g', fileName + ':' + lineNumber], workspace);
+      return addWorkspaceToArgumentsIfExists(
+        ['-g', fileName + ':' + lineNumber],
+        workspace,
+      );
   }
 
   // For all others, drop the lineNumber until we have
@@ -114,17 +120,19 @@ function guessEditor() {
 }
 
 function printInstructions(title) {
-  console.log([
-    '',
-    chalk.bgBlue.white.bold(' ' + title + ' '),
-    '  When you see Red Box with stack trace, you can click any ',
-    '  stack frame to jump to the source file. The packager will launch your ',
-    '  editor of choice. It will first look at REACT_EDITOR environment ',
-    '  variable, then at EDITOR. To set it up, you can add something like ',
-    '  export REACT_EDITOR=atom to your ~/.bashrc or ~/.zshrc depending on ',
-    '  which shell you use.',
-    ''
-  ].join('\n'));
+  console.log(
+    [
+      '',
+      chalk.bgBlue.white.bold(' ' + title + ' '),
+      '  When you see Red Box with stack trace, you can click any ',
+      '  stack frame to jump to the source file. The packager will launch your ',
+      '  editor of choice. It will first look at REACT_EDITOR environment ',
+      '  variable, then at EDITOR. To set it up, you can add something like ',
+      '  export REACT_EDITOR=atom to your ~/.bashrc or ~/.zshrc depending on ',
+      '  which shell you use.',
+      '',
+    ].join('\n'),
+  );
 }
 
 function transformToAbsolutePathIfNeeded(pathName) {
@@ -136,7 +144,7 @@ function transformToAbsolutePathIfNeeded(pathName) {
 
 function findRootForFile(projectRoots, fileName) {
   fileName = transformToAbsolutePathIfNeeded(fileName);
-  return projectRoots.find((root) => {
+  return projectRoots.find(root => {
     root = transformToAbsolutePathIfNeeded(root);
     return fileName.startsWith(root + path.sep);
   });
@@ -162,11 +170,15 @@ function launchEditor(fileName, lineNumber, projectRoots) {
 
   var workspace = findRootForFile(projectRoots, fileName);
   if (lineNumber) {
-    args = args.concat(getArgumentsForLineNumber(editor, fileName, lineNumber, workspace));
+    args = args.concat(
+      getArgumentsForLineNumber(editor, fileName, lineNumber, workspace),
+    );
   } else {
     args.push(fileName);
   }
-  console.log('Opening ' + chalk.underline(fileName) + ' with ' + chalk.bold(editor));
+  console.log(
+    'Opening ' + chalk.underline(fileName) + ' with ' + chalk.bold(editor),
+  );
 
   if (_childProcess && isTerminalEditor(editor)) {
     // There's an existing editor process already and it's attached
@@ -178,7 +190,11 @@ function launchEditor(fileName, lineNumber, projectRoots) {
   if (process.platform === 'win32') {
     // On Windows, launch the editor in a shell because spawn can only
     // launch .exe files.
-    _childProcess = child_process.spawn('cmd.exe', ['/C', editor].concat(args), {stdio: 'inherit'});
+    _childProcess = child_process.spawn(
+      'cmd.exe',
+      ['/C', editor].concat(args),
+      {stdio: 'inherit'},
+    );
   } else {
     _childProcess = child_process.spawn(editor, args, {stdio: 'inherit'});
   }
diff --git a/local-cli/server/util/messageSocket.js b/local-cli/server/util/messageSocket.js
index bceb72fab01c..87772789a348 100644
--- a/local-cli/server/util/messageSocket.js
+++ b/local-cli/server/util/messageSocket.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const url = require('url');
@@ -21,8 +24,9 @@ function parseMessage(data, binary) {
     if (message.version === PROTOCOL_VERSION) {
       return message;
     }
-    console.error('Received message had wrong protocol version: '
-                  + message.version);
+    console.error(
+      'Received message had wrong protocol version: ' + message.version,
+    );
   } catch (e) {
     console.error('Failed to parse the message as JSON:\n' + data);
   }
@@ -39,24 +43,23 @@ function isBroadcast(message) {
 
 function isRequest(message) {
   return (
-    typeof message.method === 'string' &&
-    typeof message.target === 'string');
+    typeof message.method === 'string' && typeof message.target === 'string'
+  );
 }
 
 function isResponse(message) {
   return (
     typeof message.id === 'object' &&
     typeof message.id.requestId !== undefined &&
-    typeof message.id.clientId === 'string' && (
-      message.result !== undefined ||
-      message.error !== undefined
-  ));
+    typeof message.id.clientId === 'string' &&
+    (message.result !== undefined || message.error !== undefined)
+  );
 }
 
 function attachToServer(server, path) {
   const wss = new WebSocketServer({
     server: server,
-    path: path
+    path: path,
   });
   const clients = new Map();
   let nextClientId = 0;
@@ -77,10 +80,11 @@ function attachToServer(server, path) {
     };
     if (clients.size === 0) {
       notifier.notify({
-        'title': 'React Native: No apps connected',
-        'message': `Sending '${message.method}' to all React Native apps ` +
-                  'failed. Make sure your app is running in the simulator ' +
-                  'or on a phone connected via USB.'
+        title: 'React Native: No apps connected',
+        message:
+          `Sending '${message.method}' to all React Native apps ` +
+          'failed. Make sure your app is running in the simulator ' +
+          'or on a phone connected via USB.',
       });
     }
     for (const [otherId, otherWs] of clients) {
@@ -88,8 +92,10 @@ function attachToServer(server, path) {
         try {
           otherWs.send(JSON.stringify(forwarded));
         } catch (e) {
-          console.error(`Failed to send broadcast to client: '${otherId}' ` +
-                        `due to:\n ${e.toString()}`);
+          console.error(
+            `Failed to send broadcast to client: '${otherId}' ` +
+              `due to:\n ${e.toString()}`,
+          );
         }
       }
     }
@@ -111,18 +117,23 @@ function attachToServer(server, path) {
       if (message.id === undefined) {
         console.error(
           `Handling message from ${clientId} failed with:\n${error}\n` +
-          `message:\n${JSON.stringify(errorMessage)}`);
+            `message:\n${JSON.stringify(errorMessage)}`,
+        );
       } else {
         try {
-          clientWs.send(JSON.stringify({
-            version: PROTOCOL_VERSION,
-            error: error,
-            id: message.id,
-          }));
+          clientWs.send(
+            JSON.stringify({
+              version: PROTOCOL_VERSION,
+              error: error,
+              id: message.id,
+            }),
+          );
         } catch (e) {
-          console.error(`Failed to reply to ${clientId} with error:\n${error}` +
-                        `\nmessage:\n${JSON.stringify(errorMessage)}` +
-                        `\ndue to error: ${e.toString()}`);
+          console.error(
+            `Failed to reply to ${clientId} with error:\n${error}` +
+              `\nmessage:\n${JSON.stringify(errorMessage)}` +
+              `\ndue to error: ${e.toString()}`,
+          );
         }
       }
     }
@@ -145,40 +156,46 @@ function attachToServer(server, path) {
           throw `unknown method: ${message.method}`;
       }
 
-      clientWs.send(JSON.stringify({
-        version: PROTOCOL_VERSION,
-        result: result,
-        id: message.id
-      }));
+      clientWs.send(
+        JSON.stringify({
+          version: PROTOCOL_VERSION,
+          result: result,
+          id: message.id,
+        }),
+      );
     }
 
     function forwardRequest(message) {
-      getClientWs(message.target).send(JSON.stringify({
-        version: PROTOCOL_VERSION,
-        method: message.method,
-        params: message.params,
-        id: (message.id === undefined
-          ? undefined
-          : {requestId: message.id, clientId: clientId}),
-      }));
+      getClientWs(message.target).send(
+        JSON.stringify({
+          version: PROTOCOL_VERSION,
+          method: message.method,
+          params: message.params,
+          id:
+            message.id === undefined
+              ? undefined
+              : {requestId: message.id, clientId: clientId},
+        }),
+      );
     }
 
     function forwardResponse(message) {
-      getClientWs(message.id.clientId).send(JSON.stringify({
-        version: PROTOCOL_VERSION,
-        result: message.result,
-        error: message.error,
-        id: message.id.requestId,
-      }));
+      getClientWs(message.id.clientId).send(
+        JSON.stringify({
+          version: PROTOCOL_VERSION,
+          result: message.result,
+          error: message.error,
+          id: message.id.requestId,
+        }),
+      );
     }
 
     clients.set(clientId, clientWs);
-    clientWs.onclose =
-    clientWs.onerror = () => {
+    clientWs.onclose = clientWs.onerror = () => {
       clientWs.onmessage = null;
       clients.delete(clientId);
     };
-    clientWs.onmessage = (event) => {
+    clientWs.onmessage = event => {
       const message = parseMessage(event.data, event.binary);
       if (message === undefined) {
         console.error('Received message not matching protocol');
@@ -208,7 +225,7 @@ function attachToServer(server, path) {
   return {
     broadcast: (method, params) => {
       handleSendBroadcast(null, {method: method, params: params});
-    }
+    },
   };
 }
 
diff --git a/local-cli/server/util/webSocketProxy.js b/local-cli/server/util/webSocketProxy.js
index 2a854c6d81d5..d419e5158976 100644
--- a/local-cli/server/util/webSocketProxy.js
+++ b/local-cli/server/util/webSocketProxy.js
@@ -3,15 +3,17 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
-'use strict';
 
+'use strict';
 
 function attachToServer(server, path) {
   var WebSocketServer = require('ws').Server;
   var wss = new WebSocketServer({
     server: server,
-    path: path
+    path: path,
   });
   var debuggerSocket, clientSocket;
 
@@ -37,8 +39,7 @@ function attachToServer(server, path) {
         return;
       }
       debuggerSocket = ws;
-      debuggerSocket.onerror =
-      debuggerSocket.onclose = () => {
+      debuggerSocket.onerror = debuggerSocket.onclose = () => {
         debuggerSocket = null;
         if (clientSocket) {
           clientSocket.close(1011, 'Debugger was disconnected');
@@ -51,8 +52,7 @@ function attachToServer(server, path) {
         clientSocket.close(1011, 'Another client connected');
       }
       clientSocket = ws;
-      clientSocket.onerror =
-      clientSocket.onclose = () => {
+      clientSocket.onerror = clientSocket.onclose = () => {
         clientSocket = null;
         send(debuggerSocket, JSON.stringify({method: '$disconnected'}));
       };
@@ -66,10 +66,10 @@ function attachToServer(server, path) {
     server: wss,
     isChromeConnected: function() {
       return !!debuggerSocket;
-    }
+    },
   };
 }
 
 module.exports = {
-  attachToServer: attachToServer
+  attachToServer: attachToServer,
 };
diff --git a/local-cli/templates/HelloNavigation/App.js b/local-cli/templates/HelloNavigation/App.js
index 8b422a767b8b..4ccc87f17910 100644
--- a/local-cli/templates/HelloNavigation/App.js
+++ b/local-cli/templates/HelloNavigation/App.js
@@ -2,10 +2,12 @@
  * This is an example React Native app demonstrates ListViews, text input and
  * navigation between a few screens.
  * https://github.com/facebook/react-native
+ *
+ * @format
  */
 
-import React, { Component } from 'react';
-import { StackNavigator } from 'react-navigation';
+import React, {Component} from 'react';
+import {StackNavigator} from 'react-navigation';
 
 import HomeScreenTabNavigator from './views/HomeScreenTabNavigator';
 import ChatScreen from './views/chat/ChatScreen';
diff --git a/local-cli/templates/HelloNavigation/components/KeyboardSpacer.js b/local-cli/templates/HelloNavigation/components/KeyboardSpacer.js
index 72e10391757c..9b73a41bab2d 100644
--- a/local-cli/templates/HelloNavigation/components/KeyboardSpacer.js
+++ b/local-cli/templates/HelloNavigation/components/KeyboardSpacer.js
@@ -3,28 +3,25 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
 
 /* @flow */
 
-import React, { Component } from 'react';
+import React, {Component} from 'react';
 import PropTypes from 'prop-types';
-import {
-  Platform,
-  View,
-  Keyboard,
-  LayoutAnimation,
-} from 'react-native';
+import {Platform, View, Keyboard, LayoutAnimation} from 'react-native';
 
 type Props = {
   offset?: number,
-}
+};
 
 type State = {
-  keyboardHeight: number
-}
+  keyboardHeight: number,
+};
 
 // Consider contributing this to the popular library:
 // https://github.com/Andr3wHur5t/react-native-keyboard-spacer
@@ -48,9 +45,8 @@ type State = {
  * The KeyboardAvoidingView doesn't work when used together with
  * a ScrollView/ListView.
  */
-const KeyboardSpacer = () => (
-  Platform.OS === 'ios' ? <KeyboardSpacerIOS /> : null
-);
+const KeyboardSpacer = () =>
+  Platform.OS === 'ios' ? <KeyboardSpacerIOS /> : null;
 
 class KeyboardSpacerIOS extends Component<Props, State> {
   static propTypes = {
@@ -73,17 +69,17 @@ class KeyboardSpacerIOS extends Component<Props, State> {
     this._unRegisterEvents();
   }
 
-  _keyboardWillShowSubscription: { +remove: Function };
-  _keyboardWillHideSubscription: { +remove: Function };
+  _keyboardWillShowSubscription: {+remove: Function};
+  _keyboardWillHideSubscription: {+remove: Function};
 
   _registerEvents = () => {
     this._keyboardWillShowSubscription = Keyboard.addListener(
       'keyboardWillShow',
-      this._keyboardWillShow
+      this._keyboardWillShow,
     );
     this._keyboardWillHideSubscription = Keyboard.addListener(
       'keyboardWillHide',
-      this._keyboardWillHide
+      this._keyboardWillHide,
     );
   };
 
@@ -98,9 +94,9 @@ class KeyboardSpacerIOS extends Component<Props, State> {
       duration: 100,
       update: {
         type: 'keyboard',
-      }
+      },
     });
-  }
+  };
 
   _keyboardWillShow = (e: any) => {
     this._configureLayoutAnimation();
@@ -117,7 +113,7 @@ class KeyboardSpacerIOS extends Component<Props, State> {
   };
 
   render() {
-    return <View style={{ height: this.state.keyboardHeight }} />;
+    return <View style={{height: this.state.keyboardHeight}} />;
   }
 }
 
diff --git a/local-cli/templates/HelloNavigation/components/ListItem.js b/local-cli/templates/HelloNavigation/components/ListItem.js
index 4e953214ea01..c93e819b5c14 100644
--- a/local-cli/templates/HelloNavigation/components/ListItem.js
+++ b/local-cli/templates/HelloNavigation/components/ListItem.js
@@ -1,6 +1,8 @@
+/** @format */
+
 'use strict';
 
-import React, { Component } from 'react';
+import React, {Component} from 'react';
 import {
   Platform,
   StyleSheet,
@@ -48,7 +50,7 @@ const styles = StyleSheet.create({
   },
   label: {
     fontSize: 16,
-  }
+  },
 });
 
 export default ListItem;
diff --git a/local-cli/templates/HelloNavigation/lib/Backend.js b/local-cli/templates/HelloNavigation/lib/Backend.js
index 22cde143b63f..a85f0ae753fe 100644
--- a/local-cli/templates/HelloNavigation/lib/Backend.js
+++ b/local-cli/templates/HelloNavigation/lib/Backend.js
@@ -1,3 +1,5 @@
+/** @format */
+
 'use strict';
 
 // This file just a dummy example of a HTTP API to talk to the backend.
@@ -23,7 +25,7 @@ const backendStateForLoggedInPerson = {
           text: 'I ❤️ React Native!',
         },
       ],
-    }
+    },
   ],
 };
 
@@ -33,7 +35,7 @@ const backendStateForLoggedInPerson = {
  * in real-world conditions.
  */
 function isNetworkFailure() {
-  const chanceOfFailure = 0;  // 0..1
+  const chanceOfFailure = 0; // 0..1
   return Math.random() < chanceOfFailure;
 }
 
@@ -45,8 +47,8 @@ function isNetworkFailure() {
  */
 function _makeSimulatedNetworkRequest(getValue) {
   const durationMs = 400;
-  return new Promise(function (resolve, reject) {
-    setTimeout(function () {
+  return new Promise(function(resolve, reject) {
+    setTimeout(function() {
       if (isNetworkFailure()) {
         reject(new Error('Network failure'));
       } else {
@@ -71,9 +73,7 @@ async function fetchChatList() {
 async function fetchChat(name) {
   return _makeSimulatedNetworkRequest((resolve, reject) => {
     resolve(
-      backendStateForLoggedInPerson.chats.find(
-        chat => chat.name === name
-      )
+      backendStateForLoggedInPerson.chats.find(chat => chat.name === name),
     );
   });
 }
@@ -84,7 +84,7 @@ async function fetchChat(name) {
 async function sendMessage({name, message}) {
   return _makeSimulatedNetworkRequest((resolve, reject) => {
     const chatForName = backendStateForLoggedInPerson.chats.find(
-      chat => chat.name === name
+      chat => chat.name === name,
     );
     if (chatForName) {
       chatForName.messages.push({
diff --git a/local-cli/templates/HelloNavigation/views/HomeScreenTabNavigator.js b/local-cli/templates/HelloNavigation/views/HomeScreenTabNavigator.js
index 36ca5af70fe2..09e411a471a9 100644
--- a/local-cli/templates/HelloNavigation/views/HomeScreenTabNavigator.js
+++ b/local-cli/templates/HelloNavigation/views/HomeScreenTabNavigator.js
@@ -1,4 +1,6 @@
-import { TabNavigator } from 'react-navigation';
+/** @format */
+
+import {TabNavigator} from 'react-navigation';
 
 import ChatListScreen from './chat/ChatListScreen';
 import WelcomeScreen from './welcome/WelcomeScreen';
diff --git a/local-cli/templates/HelloNavigation/views/chat/ChatListScreen.js b/local-cli/templates/HelloNavigation/views/chat/ChatListScreen.js
index 4d4fcc093e9c..121deb36d337 100644
--- a/local-cli/templates/HelloNavigation/views/chat/ChatListScreen.js
+++ b/local-cli/templates/HelloNavigation/views/chat/ChatListScreen.js
@@ -1,4 +1,6 @@
-import React, { Component } from 'react';
+/** @format */
+
+import React, {Component} from 'react';
 import {
   ActivityIndicator,
   Image,
@@ -11,18 +13,17 @@ import ListItem from '../../components/ListItem';
 import Backend from '../../lib/Backend';
 
 export default class ChatListScreen extends Component {
-
   static navigationOptions = {
     title: 'Chats',
     header: Platform.OS === 'ios' ? undefined : null,
-    tabBarIcon: ({ tintColor }) => (
+    tabBarIcon: ({tintColor}) => (
       <Image
         // Using react-native-vector-icons works here too
         source={require('./chat-icon.png')}
         style={[styles.icon, {tintColor: tintColor}]}
       />
     ),
-  }
+  };
 
   constructor(props) {
     super(props);
@@ -33,7 +34,7 @@ export default class ChatListScreen extends Component {
 
   async componentDidMount() {
     const chatList = await Backend.fetchChatList();
-    this.setState((prevState) => ({
+    this.setState(prevState => ({
       chatList,
       isLoading: false,
     }));
@@ -41,7 +42,7 @@ export default class ChatListScreen extends Component {
 
   // Binding the function so it can be passed to FlatList below
   // and 'this' works properly inside renderItem
-  renderItem = ({ item }) => {
+  renderItem = ({item}) => {
     return (
       <ListItem
         label={item}
@@ -53,7 +54,7 @@ export default class ChatListScreen extends Component {
         }}
       />
     );
-  }
+  };
 
   render() {
     if (this.state.isLoading) {
diff --git a/local-cli/templates/HelloNavigation/views/chat/ChatScreen.js b/local-cli/templates/HelloNavigation/views/chat/ChatScreen.js
index 6f1dfff32131..0d1e322d151c 100644
--- a/local-cli/templates/HelloNavigation/views/chat/ChatScreen.js
+++ b/local-cli/templates/HelloNavigation/views/chat/ChatScreen.js
@@ -1,4 +1,6 @@
-import React, { Component } from 'react';
+/** @format */
+
+import React, {Component} from 'react';
 import {
   ActivityIndicator,
   Button,
@@ -12,8 +14,7 @@ import KeyboardSpacer from '../../components/KeyboardSpacer';
 import Backend from '../../lib/Backend';
 
 export default class ChatScreen extends Component {
-
-  static navigationOptions = ({ navigation }) => ({
+  static navigationOptions = ({navigation}) => ({
     title: `Chat with ${navigation.state.params.name}`,
   });
   constructor(props) {
@@ -40,7 +41,7 @@ export default class ChatScreen extends Component {
       });
       return;
     }
-    this.setState((prevState) => ({
+    this.setState(prevState => ({
       messages: chat.messages,
       isLoading: false,
     }));
@@ -61,18 +62,19 @@ export default class ChatScreen extends Component {
       // Here we would handle the request failure, e.g. call setState
       // to display a visual hint showing the message could not be sent.
     }
-  }
+  };
 
   addMessageLocal = () => {
-    this.setState((prevState) => {
+    this.setState(prevState => {
       if (!prevState.myMessage) {
         return prevState;
       }
       const messages = [
-        ...prevState.messages, {
+        ...prevState.messages,
+        {
           name: 'Me',
           text: prevState.myMessage,
-        }
+        },
       ];
       return {
         messages: messages,
@@ -80,18 +82,18 @@ export default class ChatScreen extends Component {
       };
     });
     this.textInput.clear();
-  }
+  };
 
-  onMyMessageChange = (event) => {
+  onMyMessageChange = event => {
     this.setState({myMessage: event.nativeEvent.text});
-  }
+  };
 
-  renderItem = ({ item }) => (
+  renderItem = ({item}) => (
     <View style={styles.bubble}>
       <Text style={styles.name}>{item.name}</Text>
       <Text>{item.text}</Text>
     </View>
-  )
+  );
 
   render() {
     if (this.state.isLoading) {
@@ -104,15 +106,17 @@ export default class ChatScreen extends Component {
     return (
       <View style={styles.container}>
         <FlatList
-           data={this.state.messages}
-           renderItem={this.renderItem}
-           keyExtractor={(item, index) => index}
-           style={styles.listView}
-         />
+          data={this.state.messages}
+          renderItem={this.renderItem}
+          keyExtractor={(item, index) => index}
+          style={styles.listView}
+        />
 
         <View style={styles.composer}>
           <TextInput
-            ref={(textInput) => { this.textInput = textInput; }}
+            ref={textInput => {
+              this.textInput = textInput;
+            }}
             style={styles.textInput}
             placeholder="Type a message..."
             text={this.state.myMessage}
@@ -120,10 +124,7 @@ export default class ChatScreen extends Component {
             onChange={this.onMyMessageChange}
           />
           {this.state.myMessage !== '' && (
-            <Button
-              title="Send"
-              onPress={this.onAddMessage}
-            />
+            <Button title="Send" onPress={this.onAddMessage} />
           )}
         </View>
         <KeyboardSpacer />
@@ -165,5 +166,5 @@ const styles = StyleSheet.create({
     height: 30,
     fontSize: 13,
     marginRight: 8,
-  }
+  },
 });
diff --git a/local-cli/templates/HelloNavigation/views/welcome/WelcomeScreen.js b/local-cli/templates/HelloNavigation/views/welcome/WelcomeScreen.js
index 62b7fba55c5b..942a8fbae42d 100644
--- a/local-cli/templates/HelloNavigation/views/welcome/WelcomeScreen.js
+++ b/local-cli/templates/HelloNavigation/views/welcome/WelcomeScreen.js
@@ -1,32 +1,27 @@
-import React, { Component } from 'react';
-import {
-  Image,
-  Platform,
-  StyleSheet,
-} from 'react-native';
+/** @format */
+
+import React, {Component} from 'react';
+import {Image, Platform, StyleSheet} from 'react-native';
 
 import ListItem from '../../components/ListItem';
 import WelcomeText from './WelcomeText';
 
 export default class WelcomeScreen extends Component {
-
   static navigationOptions = {
     title: 'Welcome',
     // You can now set header: null on any component to hide the header
     header: Platform.OS === 'ios' ? undefined : null,
-    tabBarIcon: ({ tintColor }) => (
+    tabBarIcon: ({tintColor}) => (
       <Image
         // Using react-native-vector-icons works here too
         source={require('./welcome-icon.png')}
         style={[styles.icon, {tintColor: tintColor}]}
       />
     ),
-  }
+  };
 
   render() {
-    return (
-      <WelcomeText />
-    );
+    return <WelcomeText />;
   }
 }
 
diff --git a/local-cli/templates/HelloNavigation/views/welcome/WelcomeText.android.js b/local-cli/templates/HelloNavigation/views/welcome/WelcomeText.android.js
index bf77b5101c7a..9f185d56cc6c 100644
--- a/local-cli/templates/HelloNavigation/views/welcome/WelcomeText.android.js
+++ b/local-cli/templates/HelloNavigation/views/welcome/WelcomeText.android.js
@@ -1,24 +1,20 @@
-import React, { Component } from 'react';
-import {
-  StyleSheet,
-  Text,
-  View,
-} from 'react-native';
+/** @format */
+
+import React, {Component} from 'react';
+import {StyleSheet, Text, View} from 'react-native';
 
 export default class WelcomeText extends Component {
   render() {
     return (
       <View style={styles.container}>
-        <Text style={styles.welcome}>
-          Welcome to React Native!
-        </Text>
+        <Text style={styles.welcome}>Welcome to React Native!</Text>
         <Text style={styles.instructions}>
-          This app shows the basics of navigating between a few screens,
-          working with ListView and handling text input.
+          This app shows the basics of navigating between a few screens, working
+          with ListView and handling text input.
         </Text>
         <Text style={styles.instructions}>
-          Modify any files to get started. For example try changing the
-          file views/welcome/WelcomeText.android.js.
+          Modify any files to get started. For example try changing the file
+          views/welcome/WelcomeText.android.js.
         </Text>
         <Text style={styles.instructions}>
           Double tap R on your keyboard to reload,{'\n'}
diff --git a/local-cli/templates/HelloNavigation/views/welcome/WelcomeText.ios.js b/local-cli/templates/HelloNavigation/views/welcome/WelcomeText.ios.js
index 8e040208abbf..673e6889bbba 100644
--- a/local-cli/templates/HelloNavigation/views/welcome/WelcomeText.ios.js
+++ b/local-cli/templates/HelloNavigation/views/welcome/WelcomeText.ios.js
@@ -1,24 +1,21 @@
-import React, { Component } from 'react';
-import {
-  StyleSheet,
-  Text,
-  View,
-} from 'react-native';
+/** @format */
+
+import React, {Component} from 'react';
+import {StyleSheet, Text, View} from 'react-native';
 
 export default class WelcomeText extends Component {
   render() {
     return (
       <View style={styles.container}>
-        <Text style={styles.welcome}>
-          Welcome to React Native!
-        </Text>
+        <Text style={styles.welcome}>Welcome to React Native!</Text>
         <Text style={styles.instructions}>
-          This app shows the basics of navigating between a few screens,
-          working with ListView and handling text input.
+          This app shows the basics of navigating between a few screens, working
+          with ListView and handling text input.
         </Text>
         <Text style={styles.instructions}>
-          Modify any files to get started. For example try changing the
-          file{'\n'}views/welcome/WelcomeText.ios.js.
+          Modify any files to get started. For example try changing the file{
+            '\n'
+          }views/welcome/WelcomeText.ios.js.
         </Text>
         <Text style={styles.instructions}>
           Press Cmd+R to reload,{'\n'}
diff --git a/local-cli/templates/HelloWorld/App.js b/local-cli/templates/HelloWorld/App.js
index dd1d45ab3967..171d0f0f4a85 100644
--- a/local-cli/templates/HelloWorld/App.js
+++ b/local-cli/templates/HelloWorld/App.js
@@ -1,21 +1,18 @@
 /**
  * Sample React Native App
  * https://github.com/facebook/react-native
+ *
+ * @format
  * @flow
  */
 
-import React, { Component } from 'react';
-import {
-  Platform,
-  StyleSheet,
-  Text,
-  View
-} from 'react-native';
+import React, {Component} from 'react';
+import {Platform, StyleSheet, Text, View} from 'react-native';
 
 const instructions = Platform.select({
-  ios: 'Press Cmd+R to reload,\n' +
-    'Cmd+D or shake for dev menu',
-  android: 'Double tap R on your keyboard to reload,\n' +
+  ios: 'Press Cmd+R to reload,\n' + 'Cmd+D or shake for dev menu',
+  android:
+    'Double tap R on your keyboard to reload,\n' +
     'Shake or press menu button for dev menu',
 });
 
@@ -24,15 +21,9 @@ export default class App extends Component<Props> {
   render() {
     return (
       <View style={styles.container}>
-        <Text style={styles.welcome}>
-          Welcome to React Native!
-        </Text>
-        <Text style={styles.instructions}>
-          To get started, edit App.js
-        </Text>
-        <Text style={styles.instructions}>
-          {instructions}
-        </Text>
+        <Text style={styles.welcome}>Welcome to React Native!</Text>
+        <Text style={styles.instructions}>To get started, edit App.js</Text>
+        <Text style={styles.instructions}>{instructions}</Text>
       </View>
     );
   }
diff --git a/local-cli/templates/HelloWorld/__tests__/App.js b/local-cli/templates/HelloWorld/__tests__/App.js
index d0b9ee3165c8..2d5bbce8a44a 100644
--- a/local-cli/templates/HelloWorld/__tests__/App.js
+++ b/local-cli/templates/HelloWorld/__tests__/App.js
@@ -1,3 +1,5 @@
+/** @format */
+
 import 'react-native';
 import React from 'react';
 import App from '../App';
@@ -6,7 +8,5 @@ import App from '../App';
 import renderer from 'react-test-renderer';
 
 it('renders correctly', () => {
-  const tree = renderer.create(
-    <App />
-  );
+  const tree = renderer.create(<App />);
 });
diff --git a/local-cli/templates/HelloWorld/index.js b/local-cli/templates/HelloWorld/index.js
index ab0ecbf4f878..802b4350d6f3 100644
--- a/local-cli/templates/HelloWorld/index.js
+++ b/local-cli/templates/HelloWorld/index.js
@@ -1,5 +1,7 @@
-import { AppRegistry } from 'react-native';
+/** @format */
+
+import {AppRegistry} from 'react-native';
 import App from './App';
-import { name as appName } from './app.json';
+import {name as appName} from './app.json';
 
 AppRegistry.registerComponent(appName, () => App);
diff --git a/local-cli/upgrade/upgrade.js b/local-cli/upgrade/upgrade.js
index 93e3a7815d1f..f433961ebe59 100644
--- a/local-cli/upgrade/upgrade.js
+++ b/local-cli/upgrade/upgrade.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const chalk = require('chalk');
@@ -27,24 +30,24 @@ function validateAndUpgrade() {
   const projectDir = process.cwd();
 
   const packageJSON = JSON.parse(
-      fs.readFileSync(path.resolve(projectDir, 'package.json'), 'utf8')
+    fs.readFileSync(path.resolve(projectDir, 'package.json'), 'utf8'),
   );
 
   warn(
     'You should consider using the new upgrade tool based on Git. It ' +
-    'makes upgrades easier by resolving most conflicts automatically.\n' +
-    'To use it:\n' +
-    '- Go back to the old version of React Native\n' +
-    '- Run "npm install -g react-native-git-upgrade"\n' +
-    '- Run "react-native-git-upgrade"\n' +
-    'See https://facebook.github.io/react-native/docs/upgrading.html'
+      'makes upgrades easier by resolving most conflicts automatically.\n' +
+      'To use it:\n' +
+      '- Go back to the old version of React Native\n' +
+      '- Run "npm install -g react-native-git-upgrade"\n' +
+      '- Run "react-native-git-upgrade"\n' +
+      'See https://facebook.github.io/react-native/docs/upgrading.html',
   );
 
   const projectName = packageJSON.name;
   if (!projectName) {
     warn(
       'Your project needs to have a name, declared in package.json, ' +
-      'such as "name": "AwesomeApp". Please add a project name. Aborting.'
+        'such as "name": "AwesomeApp". Please add a project name. Aborting.',
     );
     return;
   }
@@ -53,7 +56,7 @@ function validateAndUpgrade() {
   if (!version) {
     warn(
       'Your "package.json" file doesn\'t seem to declare "react-native" as ' +
-      'a dependency. Nothing to upgrade. Aborting.'
+        'a dependency. Nothing to upgrade. Aborting.',
     );
     return;
   }
@@ -61,8 +64,8 @@ function validateAndUpgrade() {
   if (version === 'latest' || version === '*') {
     warn(
       'Some major releases introduce breaking changes.\n' +
-      'Please use a caret version number in your "package.json" file \n' +
-      'to avoid breakage. Use e.g. react-native: ^0.38.0. Aborting.'
+        'Please use a caret version number in your "package.json" file \n' +
+        'to avoid breakage. Use e.g. react-native: ^0.38.0. Aborting.',
     );
     return;
   }
@@ -70,15 +73,15 @@ function validateAndUpgrade() {
   const installed = JSON.parse(
     fs.readFileSync(
       path.resolve(projectDir, 'node_modules/react-native/package.json'),
-      'utf8'
-    )
+      'utf8',
+    ),
   );
 
   if (!semver.satisfies(installed.version, version)) {
     warn(
       'react-native version in "package.json" doesn\'t match ' +
-      'the installed version in "node_modules".\n' +
-      'Try running "npm install" to fix this. Aborting.'
+        'the installed version in "node_modules".\n' +
+        'Try running "npm install" to fix this. Aborting.',
     );
     return;
   }
@@ -88,25 +91,30 @@ function validateAndUpgrade() {
   if (!semver.valid(v)) {
     warn(
       "A valid version number for 'react-native' is not specified in your " +
-      "'package.json' file. Aborting."
+        "'package.json' file. Aborting.",
     );
     return;
   }
 
   console.log(
-    'Upgrading project to react-native v' + installed.version + '\n' +
-    'Check out the release notes and breaking changes: ' +
-    'https://github.com/facebook/react-native/releases/tag/v' +
-    semver.major(v) + '.' + semver.minor(v) + '.0'
+    'Upgrading project to react-native v' +
+      installed.version +
+      '\n' +
+      'Check out the release notes and breaking changes: ' +
+      'https://github.com/facebook/react-native/releases/tag/v' +
+      semver.major(v) +
+      '.' +
+      semver.minor(v) +
+      '.0',
   );
 
   // >= v0.21.0, we require react to be a peer dependency
   if (semver.gte(v, '0.21.0') && !packageJSON.dependencies.react) {
     warn(
       'Your "package.json" file doesn\'t seem to have "react" as a dependency.\n' +
-      '"react" was changed from a dependency to a peer dependency in react-native v0.21.0.\n' +
-      'Therefore, it\'s necessary to include "react" in your project\'s dependencies.\n' +
-      'Please run "npm install --save react", then re-run "react-native upgrade".\n'
+        '"react" was changed from a dependency to a peer dependency in react-native v0.21.0.\n' +
+        'Therefore, it\'s necessary to include "react" in your project\'s dependencies.\n' +
+        'Please run "npm install --save react", then re-run "react-native upgrade".\n',
     );
     return;
   }
@@ -114,18 +122,19 @@ function validateAndUpgrade() {
   if (semver.satisfies(v, '~0.26.0')) {
     warn(
       'React Native 0.26 introduced some breaking changes to the native files on iOS. You can\n' +
-      'perform them manually by checking the release notes or use "rnpm" ' +
-      'to do it automatically.\n' +
-      'Just run:\n' +
-      '"npm install -g rnpm && npm install rnpm-plugin-upgrade@0.26 --save-dev", ' +
-      'then run "rnpm upgrade".'
+        'perform them manually by checking the release notes or use "rnpm" ' +
+        'to do it automatically.\n' +
+        'Just run:\n' +
+        '"npm install -g rnpm && npm install rnpm-plugin-upgrade@0.26 --save-dev", ' +
+        'then run "rnpm upgrade".',
     );
   }
 
-  return new Promise((resolve) => {
+  return new Promise(resolve => {
     upgradeProjectFiles(projectDir, projectName);
     console.log(
-      'Successfully upgraded this project to react-native v' + installed.version
+      'Successfully upgraded this project to react-native v' +
+        installed.version,
     );
     resolve();
   });
@@ -137,10 +146,16 @@ function validateAndUpgrade() {
 function upgradeProjectFiles(projectDir, projectName) {
   // Just owerwrite
   copyProjectTemplateAndReplace(
-    path.resolve('node_modules', 'react-native', 'local-cli', 'templates', 'HelloWorld'),
+    path.resolve(
+      'node_modules',
+      'react-native',
+      'local-cli',
+      'templates',
+      'HelloWorld',
+    ),
     projectDir,
     projectName,
-    {upgrade: true}
+    {upgrade: true},
   );
 }
 
@@ -150,7 +165,8 @@ function warn(message) {
 
 const upgradeCommand = {
   name: 'upgrade',
-  description: 'upgrade your app\'s template files to the latest version; run this after ' +
+  description:
+    "upgrade your app's template files to the latest version; run this after " +
     'updating the react-native version in your package.json and running npm install',
   func: validateAndUpgrade,
 };
diff --git a/local-cli/util/PackageManager.js b/local-cli/util/PackageManager.js
index 89024ff2712b..5493ebf56a34 100644
--- a/local-cli/util/PackageManager.js
+++ b/local-cli/util/PackageManager.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const spawnSync = require('child_process').spawnSync;
@@ -25,8 +28,7 @@ function callYarnOrNpm(yarnCommand, npmCommand) {
 
   const projectDir = process.cwd();
   const isYarnAvailable =
-    yarn.getYarnVersionIfAvailable() &&
-    yarn.isGlobalCliUsingYarn(projectDir);
+    yarn.getYarnVersionIfAvailable() && yarn.isGlobalCliUsingYarn(projectDir);
 
   if (isYarnAvailable) {
     command = yarnCommand;
@@ -50,7 +52,7 @@ function callYarnOrNpm(yarnCommand, npmCommand) {
 function add(packageName) {
   return callYarnOrNpm(
     `yarn add ${packageName}`,
-    `npm install ${packageName} --save`
+    `npm install ${packageName} --save`,
   );
 }
 
@@ -62,7 +64,7 @@ function add(packageName) {
 function remove(packageName) {
   return callYarnOrNpm(
     `yarn remove ${packageName}`,
-    `npm uninstall --save ${packageName}`
+    `npm uninstall --save ${packageName}`,
   );
 }
 
diff --git a/local-cli/util/__mocks__/log.js b/local-cli/util/__mocks__/log.js
index 742b2c03701e..12d8627ba478 100644
--- a/local-cli/util/__mocks__/log.js
+++ b/local-cli/util/__mocks__/log.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 module.exports.out = () => jest.genMockFn();
diff --git a/local-cli/util/assertRequiredOptions.js b/local-cli/util/assertRequiredOptions.js
index 877caf0583b9..4974d072876d 100644
--- a/local-cli/util/assertRequiredOptions.js
+++ b/local-cli/util/assertRequiredOptions.js
@@ -3,11 +3,14 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
-const { Option } = require('commander');
-const { camelCase } = require('lodash');
+const {Option} = require('commander');
+const {camelCase} = require('lodash');
 
 // Commander.js has a 2 years old open issue to support <...> syntax
 // for options. Until that gets merged, we run the checks manually
diff --git a/local-cli/util/copyAndReplace.js b/local-cli/util/copyAndReplace.js
index 543bc6ecf012..9d42fad51f6c 100644
--- a/local-cli/util/copyAndReplace.js
+++ b/local-cli/util/copyAndReplace.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fs = require('fs');
@@ -24,7 +27,12 @@ const binaryExtensions = ['.png', '.jar'];
  *        If null, files will be overwritten.
  *        Function(path, 'identical' | 'changed' | 'new') => 'keep' | 'overwrite'
  */
-function copyAndReplace(srcPath, destPath, replacements, contentChangedCallback) {
+function copyAndReplace(
+  srcPath,
+  destPath,
+  replacements,
+  contentChangedCallback,
+) {
   if (fs.lstatSync(srcPath).isDirectory()) {
     if (!fs.existsSync(destPath)) {
       fs.mkdirSync(destPath);
@@ -55,16 +63,22 @@ function copyAndReplace(srcPath, destPath, replacements, contentChangedCallback)
       shouldOverwrite = contentChangedCallback(destPath, contentChanged);
     }
     if (shouldOverwrite === 'overwrite') {
-      copyBinaryFile(srcPath, destPath, (err) => {
-        if (err) { throw err; }
+      copyBinaryFile(srcPath, destPath, err => {
+        if (err) {
+          throw err;
+        }
       });
     }
   } else {
     // Text file
     const srcPermissions = fs.statSync(srcPath).mode;
     let content = fs.readFileSync(srcPath, 'utf8');
-    Object.keys(replacements).forEach(regex =>
-      content = content.replace(new RegExp(regex, 'g'), replacements[regex])
+    Object.keys(replacements).forEach(
+      regex =>
+        (content = content.replace(
+          new RegExp(regex, 'g'),
+          replacements[regex],
+        )),
     );
 
     let shouldOverwrite = 'overwrite';
@@ -106,7 +120,7 @@ function copyBinaryFile(srcPath, destPath, cb) {
     done(err);
   });
   const writeStream = fs.createWriteStream(destPath, {
-    mode: srcPermissions
+    mode: srcPermissions,
   });
   writeStream.on('error', function(err) {
     done(err);
diff --git a/local-cli/util/findReactNativeScripts.js b/local-cli/util/findReactNativeScripts.js
index 28317cd60f2f..6b5d1520623a 100644
--- a/local-cli/util/findReactNativeScripts.js
+++ b/local-cli/util/findReactNativeScripts.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const path = require('path');
@@ -15,7 +17,7 @@ function findReactNativeScripts(): ?string {
   const executablePath = path.resolve(
     'node_modules',
     '.bin',
-    'react-native-scripts'
+    'react-native-scripts',
   );
   if (fs.existsSync(executablePath)) {
     return executablePath;
diff --git a/local-cli/util/findSymlinksPaths.js b/local-cli/util/findSymlinksPaths.js
index e9d2d5670bfd..8fc275fe5a7f 100644
--- a/local-cli/util/findSymlinksPaths.js
+++ b/local-cli/util/findSymlinksPaths.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const path = require('path');
@@ -26,15 +28,12 @@ module.exports = function findSymlinksPaths(lookupFolder, ignoredRoots) {
       if (index !== -1) {
         throw Error(
           'Infinite symlink recursion detected:\n  ' +
-            visited.slice(index).join('\n  ')
+            visited.slice(index).join('\n  '),
         );
       }
 
       visited.push(symlink);
-      symlink = path.resolve(
-        path.dirname(symlink),
-        fs.readlinkSync(symlink)
-      );
+      symlink = path.resolve(path.dirname(symlink), fs.readlinkSync(symlink));
     }
 
     if (visited.length && !rootExists(ignoredRoots, symlink)) {
@@ -43,7 +42,11 @@ module.exports = function findSymlinksPaths(lookupFolder, ignoredRoots) {
   });
 
   const timeEnd = Date.now();
-  console.log(`Scanning ${folders.length} folders for symlinks in ${lookupFolder} (${timeEnd - timeStart}ms)`);
+  console.log(
+    `Scanning ${
+      folders.length
+    } folders for symlinks in ${lookupFolder} (${timeEnd - timeStart}ms)`,
+  );
 
   return resolvedSymlinks;
 };
diff --git a/local-cli/util/isPackagerRunning.js b/local-cli/util/isPackagerRunning.js
index 1384e6be9535..faae20676eea 100644
--- a/local-cli/util/isPackagerRunning.js
+++ b/local-cli/util/isPackagerRunning.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fetch = require('node-fetch');
@@ -17,12 +20,16 @@ const fetch = require('node-fetch');
  *   - `unrecognized`: one other process is running on the port we expect the
  *                     packager to be running.
  */
-function isPackagerRunning(packagerPort = (process.env.RCT_METRO_PORT || 8081)) {
+function isPackagerRunning(packagerPort = process.env.RCT_METRO_PORT || 8081) {
   return fetch(`http://localhost:${packagerPort}/status`).then(
-    res => res.text().then(body =>
-      body === 'packager-status:running' ? 'running' : 'unrecognized'
-    ),
-    () => 'not_running'
+    res =>
+      res
+        .text()
+        .then(
+          body =>
+            body === 'packager-status:running' ? 'running' : 'unrecognized',
+        ),
+    () => 'not_running',
   );
 }
 
diff --git a/local-cli/util/isValidPackageName.js b/local-cli/util/isValidPackageName.js
index 6bf1fdf91671..c0f5d1c93bce 100644
--- a/local-cli/util/isValidPackageName.js
+++ b/local-cli/util/isValidPackageName.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 function isValidPackageName(name) {
diff --git a/local-cli/util/log.js b/local-cli/util/log.js
index 6215de5e76e8..345d68905533 100644
--- a/local-cli/util/log.js
+++ b/local-cli/util/log.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 var _enabled = true;
diff --git a/local-cli/util/parseCommandLine.js b/local-cli/util/parseCommandLine.js
index d216959d68c9..f26c4acf73be 100644
--- a/local-cli/util/parseCommandLine.js
+++ b/local-cli/util/parseCommandLine.js
@@ -16,7 +16,10 @@
  *
  * NOTE: This file is used internally at Facebook and not in `local-cli` itself.
  * No changes should be made to this file without prior discussion with FB team.
+ *
+ * @format
  */
+
 'use strict';
 
 var optimistModule = require('optimist');
diff --git a/local-cli/util/walk.js b/local-cli/util/walk.js
index 5ca1c8d52f32..3f97405812a7 100644
--- a/local-cli/util/walk.js
+++ b/local-cli/util/walk.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fs = require('fs');
diff --git a/local-cli/util/yarn.js b/local-cli/util/yarn.js
index f2edb1c382df..ed3a74a498de 100644
--- a/local-cli/util/yarn.js
+++ b/local-cli/util/yarn.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const execSync = require('child_process').execSync;
@@ -19,9 +22,11 @@ function getYarnVersionIfAvailable() {
   let yarnVersion;
   try {
     // execSync returns a Buffer -> convert to string
-    yarnVersion = (execSync('yarn --version', {
-      stdio: [ 0, 'pipe', 'ignore', ]
-    }).toString() || '').trim();
+    yarnVersion = (
+      execSync('yarn --version', {
+        stdio: [0, 'pipe', 'ignore'],
+      }).toString() || ''
+    ).trim();
   } catch (error) {
     return null;
   }

From 36fcbaa56dbd4d88c176110d659ef7cf5a76f140 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 11 May 2018 13:32:37 -0700
Subject: [PATCH 0512/1109] Prettier the rest of ReactNative

Reviewed By: yungsters

Differential Revision: D7974340

fbshipit-source-id: 5fe457a8a9be4bd360fc3af9acb5c1136b2be0d7
---
 .../RNTesterUnitTestsBundle.js                |   7 +-
 RNTester/js/ARTExample.js                     | 126 ++---
 .../js/AccessibilityAndroidExample.android.js | 106 +++--
 RNTester/js/AccessibilityIOSExample.js        |  70 ++-
 RNTester/js/ActionSheetIOSExample.js          | 179 ++++---
 RNTester/js/ActivityIndicatorExample.js       |  63 +--
 RNTester/js/AlertExample.js                   | 118 +++--
 RNTester/js/AlertIOSExample.js                | 196 ++++----
 RNTester/js/AnimatedExample.js                | 240 +++++-----
 RNTester/js/AnimatedGratuitousApp/AnExApp.js  | 163 ++++---
 .../js/AnimatedGratuitousApp/AnExBobble.js    |  57 +--
 .../js/AnimatedGratuitousApp/AnExChained.js   |  53 ++-
 .../js/AnimatedGratuitousApp/AnExScroll.js    |  81 ++--
 RNTester/js/AnimatedGratuitousApp/AnExSet.js  |  67 ++-
 RNTester/js/AnimatedGratuitousApp/AnExTilt.js |  75 +--
 RNTester/js/AppStateExample.js                |  37 +-
 RNTester/js/AssetScaledImageExample.js        |  31 +-
 RNTester/js/AsyncStorageExample.js            |  41 +-
 RNTester/js/BorderExample.js                  |  46 +-
 RNTester/js/BoxShadowExample.js               |  64 ++-
 RNTester/js/ButtonExample.js                  |  18 +-
 RNTester/js/CameraRollView.js                 |  44 +-
 RNTester/js/ClipboardExample.js               |  22 +-
 RNTester/js/DatePickerAndroidExample.js       |  27 +-
 RNTester/js/DatePickerIOSExample.js           |  50 +-
 RNTester/js/DimensionsExample.js              |  23 +-
 RNTester/js/ExampleTypes.js                   |   2 +
 RNTester/js/FlatListExample.js                |  68 ++-
 RNTester/js/GeolocationExample.js             |  19 +-
 RNTester/js/ImageCapInsetsExample.js          |  23 +-
 RNTester/js/ImageEditingExample.js            |   1 +
 RNTester/js/ImageExample.js                   | 437 ++++++++++--------
 RNTester/js/KeyboardAvoidingViewExample.js    |  15 +-
 RNTester/js/LayoutAnimationExample.js         |  76 ++-
 RNTester/js/LayoutEventsExample.js            |  56 +--
 RNTester/js/LayoutExample.js                  |  89 ++--
 RNTester/js/LinkingExample.js                 |  15 +-
 RNTester/js/ListExampleShared.js              |  68 ++-
 RNTester/js/ListViewExample.js                |  46 +-
 RNTester/js/ListViewGridLayoutExample.js      |  39 +-
 RNTester/js/ListViewPagingExample.js          |  63 ++-
 RNTester/js/MaskedViewExample.js              |  56 +--
 RNTester/js/ModalExample.js                   |  79 +++-
 RNTester/js/MultiColumnExample.js             |  50 +-
 RNTester/js/NativeAnimationsExample.js        |  49 +-
 RNTester/js/NavigatorIOSBarStyleExample.js    |  13 +-
 RNTester/js/NavigatorIOSColorsExample.js      |  17 +-
 RNTester/js/NavigatorIOSExample.js            |  44 +-
 RNTester/js/NetInfoExample.js                 | 122 +++--
 RNTester/js/OrientationChangeExample.js       |  17 +-
 RNTester/js/PanResponderExample.js            |  30 +-
 .../js/PermissionsExampleAndroid.android.js   |  57 ++-
 RNTester/js/PickerExample.js                  |  18 +-
 RNTester/js/PickerIOSExample.js               | 115 +++--
 RNTester/js/PointerEventsExample.js           |  66 ++-
 .../js/ProgressBarAndroidExample.android.js   |  20 +-
 RNTester/js/ProgressViewIOSExample.js         |  57 ++-
 RNTester/js/PushNotificationIOSExample.js     | 150 +++---
 RNTester/js/RCTRootViewIOSExample.js          |  55 +--
 RNTester/js/RNTesterActions.js                |  12 +-
 RNTester/js/RNTesterApp.android.js            |  40 +-
 RNTester/js/RNTesterApp.ios.js                |  90 ++--
 RNTester/js/RNTesterBlock.js                  |  35 +-
 RNTester/js/RNTesterButton.js                 |  11 +-
 RNTester/js/RNTesterExampleContainer.js       |  11 +-
 RNTester/js/RNTesterExampleList.js            |  44 +-
 RNTester/js/RNTesterList.android.js           |   6 +-
 RNTester/js/RNTesterList.ios.js               |   4 +-
 RNTester/js/RNTesterNavigationReducer.js      |   8 +-
 RNTester/js/RNTesterPage.js                   |  27 +-
 RNTester/js/RNTesterSettingSwitchRow.js       |  20 +-
 RNTester/js/RNTesterStatePersister.js         |  16 +-
 RNTester/js/RNTesterTitle.js                  |  12 +-
 RNTester/js/RefreshControlExample.js          |  24 +-
 .../js/RootViewSizeFlexibilityExampleApp.js   |  28 +-
 RNTester/js/ScrollViewSimpleExample.js        |  35 +-
 RNTester/js/SectionListExample.js             |  91 ++--
 RNTester/js/SegmentedControlIOSExample.js     |  79 ++--
 RNTester/js/SetPropertiesExampleApp.js        |  15 +-
 RNTester/js/ShareExample.js                   |  73 ++-
 RNTester/js/SliderExample.js                  |  61 ++-
 RNTester/js/StatusBarExample.js               | 168 ++++---
 RNTester/js/SwipeableListViewExample.js       |  58 ++-
 RNTester/js/SwitchExample.js                  |  86 ++--
 RNTester/js/TVEventHandlerExample.js          |  44 +-
 RNTester/js/TabBarIOSBarStyleExample.js       |  16 +-
 RNTester/js/TabBarIOSExample.js               |  18 +-
 RNTester/js/TextExample.android.js            | 282 ++++++-----
 RNTester/js/TextExample.ios.js                |  94 ++--
 RNTester/js/TextInputExample.android.js       | 265 ++++++-----
 RNTester/js/TextInputExample.ios.js           | 285 ++++++------
 RNTester/js/TimePickerAndroidExample.js       |   3 +-
 RNTester/js/TimerExample.js                   |  76 +--
 RNTester/js/ToastAndroidExample.android.js    |  20 +-
 RNTester/js/ToolbarAndroidExample.android.js  |  81 ++--
 RNTester/js/ToolbarAndroidExample.ios.js      |   2 +
 RNTester/js/TouchableExample.js               | 282 +++++------
 RNTester/js/TransformExample.js               | 123 +++--
 RNTester/js/TransparentHitTestExample.js      |  32 +-
 RNTester/js/URIActionMap.js                   |   8 +-
 RNTester/js/VibrationExample.js               |   2 +
 RNTester/js/VibrationIOSExample.js            |  38 +-
 RNTester/js/ViewExample.js                    | 169 ++++---
 .../js/ViewPagerAndroidExample.android.js     |  89 ++--
 RNTester/js/WebViewExample.js                 | 126 +++--
 RNTester/js/XHRExample.js                     |  85 ++--
 RNTester/js/XHRExampleBinaryUpload.js         |  21 +-
 RNTester/js/XHRExampleCookies.js              |  30 +-
 RNTester/js/XHRExampleDownload.js             |  62 ++-
 RNTester/js/XHRExampleFetch.js                |  38 +-
 RNTester/js/XHRExampleFormData.js             |  65 ++-
 RNTester/js/XHRExampleHeaders.js              |  52 ++-
 RNTester/js/XHRExampleOnTimeOut.js            |  17 +-
 RNTester/js/createExamplePage.js              |  11 +-
 ReactAndroid/src/androidTest/js/Asserts.js    |  11 +-
 .../js/CatalystRootViewTestModule.js          |   1 +
 .../js/DatePickerDialogTestModule.js          |   7 +-
 .../src/androidTest/js/InitialPropsTestApp.js |   1 +
 .../src/androidTest/js/JSResponderTestApp.js  |   4 +-
 .../src/androidTest/js/LayoutEventsTestApp.js |  36 +-
 .../androidTest/js/MeasureLayoutTestModule.js | 129 +++---
 .../js/MultitouchHandlingTestAppModule.js     |   9 +-
 .../src/androidTest/js/NativeIdTestModule.js  |  19 +-
 .../androidTest/js/PickerAndroidTestModule.js |   5 +-
 .../androidTest/js/ProgressBarTestModule.js   |  19 +-
 .../androidTest/js/ScrollViewTestModule.js    |  36 +-
 .../src/androidTest/js/ShareTestModule.js     |  10 +-
 .../js/SubviewsClippingTestModule.js          | 127 +++--
 .../js/SwipeRefreshLayoutTestModule.js        |  12 +-
 ReactAndroid/src/androidTest/js/TestBundle.js | 154 +++---
 .../src/androidTest/js/TestIdTestModule.js    |  13 +-
 .../src/androidTest/js/TestJSLocaleModule.js  |   6 +-
 .../js/TestJSToJavaParametersModule.js        |  18 +-
 .../js/TestJavaToJSArgumentsModule.js         |  13 +-
 .../js/TestJavaToJSReturnValuesModule.js      |   5 +-
 .../src/androidTest/js/TextInputTestModule.js |  20 +-
 .../js/TimePickerDialogTestModule.js          |   5 +-
 .../js/TouchBubblingTestAppModule.js          |  17 +-
 .../src/androidTest/js/UIManagerTestModule.js |  70 ++-
 .../androidTest/js/ViewRenderingTestModule.js |  27 +-
 babel-preset/index.js                         |   3 +
 .../transforms/transform-symbol-member.js     |  20 +-
 bots/code-analysis-bot.js                     |  40 +-
 bots/dangerfile.js                            |  42 +-
 cli.js                                        |   3 +
 flow/create-react-class.js                    |   1 +
 jest/assetFileTransformer.js                  |   3 +
 jest/hasteImpl.js                             |  17 +-
 jest/preprocessor.js                          |  40 +-
 jest/setup.js                                 | 111 ++---
 lib/InitializeJavaScriptAppEngine.js          |   2 +
 lib/RCTEventEmitter.js                        |   2 +
 lib/TextInputState.js                         |   2 +
 lib/UIManager.js                              |   2 +
 lib/UIManagerStatTracker.js                   |   2 +
 lib/View.js                                   |   2 +
 lib/deepDiffer.js                             |   2 +
 lib/deepFreezeAndThrowOnMutationInDev.js      |   2 +
 lib/flattenStyle.js                           |   2 +
 react-native-git-upgrade/checks.js            |  29 +-
 react-native-git-upgrade/cli.js               |   7 +-
 react-native-git-upgrade/cliEntry.js          | 139 ++++--
 react-native-git-upgrade/yarn.js              |   7 +-
 rn-get-polyfills.js                           |   1 +
 scripts/android-e2e-test.js                   | 112 +++--
 scripts/publish-npm.js                        |  29 +-
 .../run-android-ci-instrumentation-tests.js   |  51 +-
 scripts/run-ci-e2e-tests.js                   | 142 +++---
 scripts/try-n-times.js                        |   2 +
 setupBabel.js                                 |   6 +-
 170 files changed, 5130 insertions(+), 3993 deletions(-)

diff --git a/RNTester/RNTesterUnitTests/RNTesterUnitTestsBundle.js b/RNTester/RNTesterUnitTests/RNTesterUnitTestsBundle.js
index e6ff98a10ac1..9e387e5ee842 100644
--- a/RNTester/RNTesterUnitTests/RNTesterUnitTestsBundle.js
+++ b/RNTester/RNTesterUnitTests/RNTesterUnitTestsBundle.js
@@ -4,11 +4,14 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
-const __fbBatchedBridge = { // eslint-disable-line no-unused-vars
+const __fbBatchedBridge = {
+  // eslint-disable-line no-unused-vars
   flushedQueue: function() {
     return null;
-  }
+  },
 };
diff --git a/RNTester/js/ARTExample.js b/RNTester/js/ARTExample.js
index fb8d0378c862..15ae6de031ee 100644
--- a/RNTester/js/ARTExample.js
+++ b/RNTester/js/ARTExample.js
@@ -4,76 +4,92 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  ART,
-  Platform,
-  View,
-} = ReactNative;
-
-const {
-  Surface,
-  Path,
-  Group,
-  Transform,
-  Shape,
-} = ART;
+var {ART, Platform, View} = ReactNative;
 
+const {Surface, Path, Group, Transform, Shape} = ART;
 
 var scale = Platform.isTVOS ? 4 : 1;
 
 class ARTExample extends React.Component<{}> {
-    render(){
-        const pathRect = new Path()
-            .moveTo(scale * 0,scale * 0)
-            .lineTo(scale * 0,scale * 110)
-            .lineTo(scale * 110,scale * 110)
-            .lineTo(scale * 110,scale * 0)
-            .close();
+  render() {
+    const pathRect = new Path()
+      .moveTo(scale * 0, scale * 0)
+      .lineTo(scale * 0, scale * 110)
+      .lineTo(scale * 110, scale * 110)
+      .lineTo(scale * 110, scale * 0)
+      .close();
 
-        const pathCircle0 = new Path()
-            .moveTo(scale * 30,scale * 5)
-            .arc(scale * 0,scale * 50,scale * 25)
-            .arc(scale * 0,-scale * 50,scale * 25)
-            .close();
+    const pathCircle0 = new Path()
+      .moveTo(scale * 30, scale * 5)
+      .arc(scale * 0, scale * 50, scale * 25)
+      .arc(scale * 0, -scale * 50, scale * 25)
+      .close();
 
-        const pathCircle1 = new Path()
-            .moveTo(scale * 30,scale * 55)
-            .arc(scale * 0,scale * 50,scale * 25)
-            .arc(scale * 0,-scale * 50,scale * 25)
-            .close();
+    const pathCircle1 = new Path()
+      .moveTo(scale * 30, scale * 55)
+      .arc(scale * 0, scale * 50, scale * 25)
+      .arc(scale * 0, -scale * 50, scale * 25)
+      .close();
 
-        const pathCircle2 = new Path()
-            .moveTo(scale * 55,scale * 30)
-            .arc(scale * 50,scale * 0,scale * 25)
-            .arc(-scale * 50,scale * 0,scale * 25)
-            .close();
+    const pathCircle2 = new Path()
+      .moveTo(scale * 55, scale * 30)
+      .arc(scale * 50, scale * 0, scale * 25)
+      .arc(-scale * 50, scale * 0, scale * 25)
+      .close();
 
-        const pathCircle3 = new Path()
-            .moveTo(scale * 55,scale * 80)
-            .arc(scale * 50,scale * 0,scale * 25)
-            .arc(-scale * 50,scale * 0,scale * 25)
-            .close();
+    const pathCircle3 = new Path()
+      .moveTo(scale * 55, scale * 80)
+      .arc(scale * 50, scale * 0, scale * 25)
+      .arc(-scale * 50, scale * 0, scale * 25)
+      .close();
 
-        return (
-            <View>
-                <Surface width={scale * 200} height={scale * 200}>
-                    <Group>
-                        <Shape d={pathRect} stroke="#000080" fill="#000080" strokeWidth={scale}/>
-                        <Shape d={pathCircle0} stroke="#FF0000" fill="#FF0000" strokeWidth={scale}/>
-                        <Shape d={pathCircle1} stroke="#00FF00" fill="#00FF00" strokeWidth={scale}/>
-                        <Shape d={pathCircle2} stroke="#00FFFF" fill="#00FFFF" strokeWidth={scale}/>
-                        <Shape d={pathCircle3} stroke="#FFFFFF" fill="#FFFFFF" strokeWidth={scale}/>
-                    </Group>
-                </Surface>
-            </View>
-        );
-    }
+    return (
+      <View>
+        <Surface width={scale * 200} height={scale * 200}>
+          <Group>
+            <Shape
+              d={pathRect}
+              stroke="#000080"
+              fill="#000080"
+              strokeWidth={scale}
+            />
+            <Shape
+              d={pathCircle0}
+              stroke="#FF0000"
+              fill="#FF0000"
+              strokeWidth={scale}
+            />
+            <Shape
+              d={pathCircle1}
+              stroke="#00FF00"
+              fill="#00FF00"
+              strokeWidth={scale}
+            />
+            <Shape
+              d={pathCircle2}
+              stroke="#00FFFF"
+              fill="#00FFFF"
+              strokeWidth={scale}
+            />
+            <Shape
+              d={pathCircle3}
+              stroke="#FFFFFF"
+              fill="#FFFFFF"
+              strokeWidth={scale}
+            />
+          </Group>
+        </Surface>
+      </View>
+    );
+  }
 }
 
 exports.title = '<ART>';
@@ -84,6 +100,6 @@ exports.examples = [
     title: 'ART Example',
     render(): React.Element<any> {
       return <ARTExample />;
-    }
+    },
   },
 ];
diff --git a/RNTester/js/AccessibilityAndroidExample.android.js b/RNTester/js/AccessibilityAndroidExample.android.js
index 6c6a80d416c0..e193d339347b 100644
--- a/RNTester/js/AccessibilityAndroidExample.android.js
+++ b/RNTester/js/AccessibilityAndroidExample.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
@@ -21,7 +23,12 @@ var {
 var RNTesterBlock = require('./RNTesterBlock');
 var RNTesterPage = require('./RNTesterPage');
 
-var importantForAccessibilityValues = ['auto', 'yes', 'no', 'no-hide-descendants'];
+var importantForAccessibilityValues = [
+  'auto',
+  'yes',
+  'no',
+  'no-hide-descendants',
+];
 
 class AccessibilityAndroidExample extends React.Component {
   static title = 'Accessibility';
@@ -37,11 +44,11 @@ class AccessibilityAndroidExample extends React.Component {
   componentDidMount() {
     AccessibilityInfo.addEventListener(
       'change',
-      this._handleScreenReaderToggled
+      this._handleScreenReaderToggled,
     );
-    AccessibilityInfo.fetch().done((isEnabled) => {
+    AccessibilityInfo.fetch().done(isEnabled => {
       this.setState({
-        screenReaderEnabled: isEnabled
+        screenReaderEnabled: isEnabled,
       });
     });
   }
@@ -49,15 +56,15 @@ class AccessibilityAndroidExample extends React.Component {
   componentWillUnmount() {
     AccessibilityInfo.removeEventListener(
       'change',
-      this._handleScreenReaderToggled
+      this._handleScreenReaderToggled,
     );
   }
 
-  _handleScreenReaderToggled = (isEnabled) => {
+  _handleScreenReaderToggled = isEnabled => {
     this.setState({
       screenReaderEnabled: isEnabled,
     });
-  }
+  };
 
   _addOne = () => {
     this.setState({
@@ -80,23 +87,16 @@ class AccessibilityAndroidExample extends React.Component {
   render() {
     return (
       <RNTesterPage title={'Accessibility'}>
-
         <RNTesterBlock title="Nonaccessible view with TextViews">
           <View>
-            <Text style={{color: 'green',}}>
-              This is
-            </Text>
-            <Text style={{color: 'blue'}}>
-              nontouchable normal view.
-            </Text>
+            <Text style={{color: 'green'}}>This is</Text>
+            <Text style={{color: 'blue'}}>nontouchable normal view.</Text>
           </View>
         </RNTesterBlock>
 
         <RNTesterBlock title="Accessible view with TextViews wihout label">
           <View accessible={true}>
-            <Text style={{color: 'green',}}>
-              This is
-            </Text>
+            <Text style={{color: 'green'}}>This is</Text>
             <Text style={{color: 'blue'}}>
               nontouchable accessible view without label.
             </Text>
@@ -104,11 +104,10 @@ class AccessibilityAndroidExample extends React.Component {
         </RNTesterBlock>
 
         <RNTesterBlock title="Accessible view with TextViews with label">
-          <View accessible={true}
+          <View
+            accessible={true}
             accessibilityLabel="I have label, so I read it instead of embedded text.">
-            <Text style={{color: 'green',}}>
-              This is
-            </Text>
+            <Text style={{color: 'green'}}>This is</Text>
             <Text style={{color: 'blue'}}>
               nontouchable accessible view with label.
             </Text>
@@ -117,7 +116,9 @@ class AccessibilityAndroidExample extends React.Component {
 
         <RNTesterBlock title="Touchable with component type = button">
           <TouchableWithoutFeedback
-            onPress={() => ToastAndroid.show('Toasts work by default', ToastAndroid.SHORT)}
+            onPress={() =>
+              ToastAndroid.show('Toasts work by default', ToastAndroid.SHORT)
+            }
             accessibilityComponentType="button">
             <View style={styles.embedded}>
               <Text>Click me</Text>
@@ -139,7 +140,8 @@ class AccessibilityAndroidExample extends React.Component {
 
         <RNTesterBlock title="Check if the screen reader is enabled">
           <Text>
-            The screen reader is {this.state.screenReaderEnabled ? 'enabled' : 'disabled'}.
+            The screen reader is{' '}
+            {this.state.screenReaderEnabled ? 'enabled' : 'disabled'}.
           </Text>
         </RNTesterBlock>
 
@@ -152,15 +154,17 @@ class AccessibilityAndroidExample extends React.Component {
                 top: 10,
                 right: 10,
                 height: 100,
-                backgroundColor: 'green'}}
+                backgroundColor: 'green',
+              }}
               accessible={true}
               accessibilityLabel="First layout"
               importantForAccessibility={
-                importantForAccessibilityValues[this.state.backgroundImportantForAcc]}>
+                importantForAccessibilityValues[
+                  this.state.backgroundImportantForAcc
+                ]
+              }>
               <View accessible={true}>
-                <Text style={{fontSize: 25}}>
-                  Hello
-                </Text>
+                <Text style={{fontSize: 25}}>Hello</Text>
               </View>
             </View>
             <View
@@ -170,19 +174,23 @@ class AccessibilityAndroidExample extends React.Component {
                 top: 25,
                 right: 10,
                 height: 110,
-                backgroundColor: 'yellow', opacity: 0.5}}
+                backgroundColor: 'yellow',
+                opacity: 0.5,
+              }}
               accessible={true}
               accessibilityLabel="Second layout"
               importantForAccessibility={
-                importantForAccessibilityValues[this.state.forgroundImportantForAcc]}>
+                importantForAccessibilityValues[
+                  this.state.forgroundImportantForAcc
+                ]
+              }>
               <View accessible={true}>
-                <Text style={{fontSize: 20}}>
-                  world
-                </Text>
+                <Text style={{fontSize: 20}}>world</Text>
               </View>
             </View>
           </View>
-          <TouchableWithoutFeedback onPress={this._changeBackgroundImportantForAcc}>
+          <TouchableWithoutFeedback
+            onPress={this._changeBackgroundImportantForAcc}>
             <View style={styles.embedded}>
               <Text>
                 Change importantForAccessibility for background layout.
@@ -190,14 +198,17 @@ class AccessibilityAndroidExample extends React.Component {
             </View>
           </TouchableWithoutFeedback>
           <View accessible={true}>
+            <Text>Background layout importantForAccessibility</Text>
             <Text>
-              Background layout importantForAccessibility
-            </Text>
-            <Text>
-              {importantForAccessibilityValues[this.state.backgroundImportantForAcc]}
+              {
+                importantForAccessibilityValues[
+                  this.state.backgroundImportantForAcc
+                ]
+              }
             </Text>
           </View>
-          <TouchableWithoutFeedback onPress={this._changeForgroundImportantForAcc}>
+          <TouchableWithoutFeedback
+            onPress={this._changeForgroundImportantForAcc}>
             <View style={styles.embedded}>
               <Text>
                 Change importantForAccessibility for forground layout.
@@ -205,30 +216,31 @@ class AccessibilityAndroidExample extends React.Component {
             </View>
           </TouchableWithoutFeedback>
           <View accessible={true}>
+            <Text>Forground layout importantForAccessibility</Text>
             <Text>
-              Forground layout importantForAccessibility
-            </Text>
-            <Text>
-              {importantForAccessibilityValues[this.state.forgroundImportantForAcc]}
+              {
+                importantForAccessibilityValues[
+                  this.state.forgroundImportantForAcc
+                ]
+              }
             </Text>
           </View>
         </RNTesterBlock>
-
       </RNTesterPage>
     );
   }
 }
 
 var styles = StyleSheet.create({
-   embedded: {
+  embedded: {
     backgroundColor: 'yellow',
-    padding:10,
+    padding: 10,
   },
   container: {
     flex: 1,
     backgroundColor: 'white',
     padding: 10,
-    height:150,
+    height: 150,
   },
 });
 
diff --git a/RNTester/js/AccessibilityIOSExample.js b/RNTester/js/AccessibilityIOSExample.js
index dabce101ce1e..60d9ceeeddcb 100644
--- a/RNTester/js/AccessibilityIOSExample.js
+++ b/RNTester/js/AccessibilityIOSExample.js
@@ -4,17 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  AccessibilityInfo,
-  Text,
-  View,
-} = ReactNative;
+var {AccessibilityInfo, Text, View} = ReactNative;
 
 class AccessibilityIOSExample extends React.Component<{}> {
   render() {
@@ -23,37 +21,28 @@ class AccessibilityIOSExample extends React.Component<{}> {
         <View
           onAccessibilityTap={() => alert('onAccessibilityTap success')}
           accessible={true}>
-          <Text>
-            Accessibility normal tap example
-          </Text>
+          <Text>Accessibility normal tap example</Text>
         </View>
-        <View onMagicTap={() => alert('onMagicTap success')}
-              accessible={true}>
-          <Text>
-            Accessibility magic tap example
-          </Text>
+        <View onMagicTap={() => alert('onMagicTap success')} accessible={true}>
+          <Text>Accessibility magic tap example</Text>
         </View>
-        <View accessibilityLabel="Some announcement"
-              accessible={true}>
-          <Text>
-            Accessibility label example
-          </Text>
+        <View accessibilityLabel="Some announcement" accessible={true}>
+          <Text>Accessibility label example</Text>
         </View>
-        <View accessibilityTraits={['button', 'selected']}
-              accessible={true}>
-          <Text>
-            Accessibility traits example
-          </Text>
+        <View accessibilityTraits={['button', 'selected']} accessible={true}>
+          <Text>Accessibility traits example</Text>
         </View>
         <Text>
-          Text's accessibilityLabel is the raw text itself unless it is set explicitly.
+          Text's accessibilityLabel is the raw text itself unless it is set
+          explicitly.
         </Text>
-        <Text accessibilityLabel="Test of accessibilityLabel"
-          accessible={true}>
+        <Text accessibilityLabel="Test of accessibilityLabel" accessible={true}>
           This text component's accessibilityLabel is set explicitly.
         </Text>
         <View accessibilityElementsHidden={true}>
-          <Text>This view's children are hidden from the accessibility tree</Text>
+          <Text>
+            This view's children are hidden from the accessibility tree
+          </Text>
         </View>
       </View>
     );
@@ -63,16 +52,16 @@ class AccessibilityIOSExample extends React.Component<{}> {
 class ScreenReaderStatusExample extends React.Component<{}, $FlowFixMeState> {
   state = {
     screenReaderEnabled: false,
-  }
+  };
 
   componentDidMount() {
     AccessibilityInfo.addEventListener(
       'change',
-      this._handleScreenReaderToggled
+      this._handleScreenReaderToggled,
     );
-    AccessibilityInfo.fetch().done((isEnabled) => {
+    AccessibilityInfo.fetch().done(isEnabled => {
       this.setState({
-        screenReaderEnabled: isEnabled
+        screenReaderEnabled: isEnabled,
       });
     });
   }
@@ -80,21 +69,22 @@ class ScreenReaderStatusExample extends React.Component<{}, $FlowFixMeState> {
   componentWillUnmount() {
     AccessibilityInfo.removeEventListener(
       'change',
-      this._handleScreenReaderToggled
+      this._handleScreenReaderToggled,
     );
   }
 
-  _handleScreenReaderToggled = (isEnabled) => {
+  _handleScreenReaderToggled = isEnabled => {
     this.setState({
       screenReaderEnabled: isEnabled,
     });
-  }
+  };
 
   render() {
     return (
       <View>
         <Text>
-          The screen reader is {this.state.screenReaderEnabled ? 'enabled' : 'disabled'}.
+          The screen reader is{' '}
+          {this.state.screenReaderEnabled ? 'enabled' : 'disabled'}.
         </Text>
       </View>
     );
@@ -102,14 +92,18 @@ class ScreenReaderStatusExample extends React.Component<{}, $FlowFixMeState> {
 }
 
 exports.title = 'AccessibilityIOS';
-exports.description = 'Interface to show iOS\' accessibility samples';
+exports.description = "Interface to show iOS' accessibility samples";
 exports.examples = [
   {
     title: 'Accessibility elements',
-    render(): React.Element<any> { return <AccessibilityIOSExample />; }
+    render(): React.Element<any> {
+      return <AccessibilityIOSExample />;
+    },
   },
   {
     title: 'Check if the screen reader is enabled',
-    render(): React.Element<any> { return <ScreenReaderStatusExample />; }
+    render(): React.Element<any> {
+      return <ScreenReaderStatusExample />;
+    },
   },
 ];
diff --git a/RNTester/js/ActionSheetIOSExample.js b/RNTester/js/ActionSheetIOSExample.js
index 1b04190b253a..2c1788864c94 100644
--- a/RNTester/js/ActionSheetIOSExample.js
+++ b/RNTester/js/ActionSheetIOSExample.js
@@ -4,27 +4,17 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  ActionSheetIOS,
-  StyleSheet,
-  takeSnapshot,
-  Text,
-  View,
-} = ReactNative;
-
-var BUTTONS = [
-  'Option 0',
-  'Option 1',
-  'Option 2',
-  'Delete',
-  'Cancel',
-];
+var {ActionSheetIOS, StyleSheet, takeSnapshot, Text, View} = ReactNative;
+
+var BUTTONS = ['Option 0', 'Option 1', 'Option 2', 'Delete', 'Cancel'];
 var DESTRUCTIVE_INDEX = 3;
 var CANCEL_INDEX = 4;
 
@@ -39,22 +29,22 @@ class ActionSheetExample extends React.Component<{}, $FlowFixMeState> {
         <Text onPress={this.showActionSheet} style={style.button}>
           Click to show the ActionSheet
         </Text>
-        <Text>
-          Clicked button: {this.state.clicked}
-        </Text>
+        <Text>Clicked button: {this.state.clicked}</Text>
       </View>
     );
   }
 
   showActionSheet = () => {
-    ActionSheetIOS.showActionSheetWithOptions({
-      options: BUTTONS,
-      cancelButtonIndex: CANCEL_INDEX,
-      destructiveButtonIndex: DESTRUCTIVE_INDEX,
-    },
-    (buttonIndex) => {
-      this.setState({ clicked: BUTTONS[buttonIndex] });
-    });
+    ActionSheetIOS.showActionSheetWithOptions(
+      {
+        options: BUTTONS,
+        cancelButtonIndex: CANCEL_INDEX,
+        destructiveButtonIndex: DESTRUCTIVE_INDEX,
+      },
+      buttonIndex => {
+        this.setState({clicked: BUTTONS[buttonIndex]});
+      },
+    );
   };
 }
 
@@ -69,29 +59,32 @@ class ActionSheetTintExample extends React.Component<{}, $FlowFixMeState> {
         <Text onPress={this.showActionSheet} style={style.button}>
           Click to show the ActionSheet
         </Text>
-        <Text>
-          Clicked button: {this.state.clicked}
-        </Text>
+        <Text>Clicked button: {this.state.clicked}</Text>
       </View>
     );
   }
 
   showActionSheet = () => {
-    ActionSheetIOS.showActionSheetWithOptions({
-      options: BUTTONS,
-      cancelButtonIndex: CANCEL_INDEX,
-      destructiveButtonIndex: DESTRUCTIVE_INDEX,
-      tintColor: 'green',
-    },
-    (buttonIndex) => {
-      this.setState({ clicked: BUTTONS[buttonIndex] });
-    });
+    ActionSheetIOS.showActionSheetWithOptions(
+      {
+        options: BUTTONS,
+        cancelButtonIndex: CANCEL_INDEX,
+        destructiveButtonIndex: DESTRUCTIVE_INDEX,
+        tintColor: 'green',
+      },
+      buttonIndex => {
+        this.setState({clicked: BUTTONS[buttonIndex]});
+      },
+    );
   };
 }
 
-class ShareActionSheetExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class ShareActionSheetExample extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   state = {
-    text: ''
+    text: '',
   };
 
   render() {
@@ -100,38 +93,36 @@ class ShareActionSheetExample extends React.Component<$FlowFixMeProps, $FlowFixM
         <Text onPress={this.showShareActionSheet} style={style.button}>
           Click to show the Share ActionSheet
         </Text>
-        <Text>
-          {this.state.text}
-        </Text>
+        <Text>{this.state.text}</Text>
       </View>
     );
   }
 
   showShareActionSheet = () => {
-    ActionSheetIOS.showShareActionSheetWithOptions({
-      url: this.props.url,
-      message: 'message to go with the shared url',
-      subject: 'a subject to go in the email heading',
-      excludedActivityTypes: [
-        'com.apple.UIKit.activity.PostToTwitter'
-      ]
-    },
-    (error) => alert(error),
-    (completed, method) => {
-      var text;
-      if (completed) {
-        text = `Shared via ${method}`;
-      } else {
-        text = 'You didn\'t share';
-      }
-      this.setState({text});
-    });
+    ActionSheetIOS.showShareActionSheetWithOptions(
+      {
+        url: this.props.url,
+        message: 'message to go with the shared url',
+        subject: 'a subject to go in the email heading',
+        excludedActivityTypes: ['com.apple.UIKit.activity.PostToTwitter'],
+      },
+      error => alert(error),
+      (completed, method) => {
+        var text;
+        if (completed) {
+          text = `Shared via ${method}`;
+        } else {
+          text = "You didn't share";
+        }
+        this.setState({text});
+      },
+    );
   };
 }
 
 class ShareScreenshotExample extends React.Component<{}, $FlowFixMeState> {
   state = {
-    text: ''
+    text: '',
   };
 
   render() {
@@ -140,34 +131,34 @@ class ShareScreenshotExample extends React.Component<{}, $FlowFixMeState> {
         <Text onPress={this.showShareActionSheet} style={style.button}>
           Click to show the Share ActionSheet
         </Text>
-        <Text>
-          {this.state.text}
-        </Text>
+        <Text>{this.state.text}</Text>
       </View>
     );
   }
 
   showShareActionSheet = () => {
     // Take the snapshot (returns a temp file uri)
-    takeSnapshot('window').then((uri) => {
-      // Share image data
-      ActionSheetIOS.showShareActionSheetWithOptions({
-        url: uri,
-        excludedActivityTypes: [
-          'com.apple.UIKit.activity.PostToTwitter'
-        ]
-      },
-      (error) => alert(error),
-      (completed, method) => {
-        var text;
-        if (completed) {
-          text = `Shared via ${method}`;
-        } else {
-          text = 'You didn\'t share';
-        }
-        this.setState({text});
-      });
-    }).catch((error) => alert(error));
+    takeSnapshot('window')
+      .then(uri => {
+        // Share image data
+        ActionSheetIOS.showShareActionSheetWithOptions(
+          {
+            url: uri,
+            excludedActivityTypes: ['com.apple.UIKit.activity.PostToTwitter'],
+          },
+          error => alert(error),
+          (completed, method) => {
+            var text;
+            if (completed) {
+              text = `Shared via ${method}`;
+            } else {
+              text = "You didn't share";
+            }
+            this.setState({text});
+          },
+        );
+      })
+      .catch(error => alert(error));
   };
 }
 
@@ -175,36 +166,40 @@ var style = StyleSheet.create({
   button: {
     marginBottom: 10,
     fontWeight: '500',
-  }
+  },
 });
 
 exports.title = 'ActionSheetIOS';
-exports.description = 'Interface to show iOS\' action sheets';
+exports.description = "Interface to show iOS' action sheets";
 exports.examples = [
   {
     title: 'Show Action Sheet',
-    render(): React.Element<any> { return <ActionSheetExample />; }
+    render(): React.Element<any> {
+      return <ActionSheetExample />;
+    },
   },
   {
     title: 'Show Action Sheet with tinted buttons',
-    render(): React.Element<any> { return <ActionSheetTintExample />; }
+    render(): React.Element<any> {
+      return <ActionSheetTintExample />;
+    },
   },
   {
     title: 'Show Share Action Sheet',
     render(): React.Element<any> {
       return <ShareActionSheetExample url="https://code.facebook.com" />;
-    }
+    },
   },
   {
     title: 'Share Local Image',
     render(): React.Element<any> {
       return <ShareActionSheetExample url="bunny.png" />;
-    }
+    },
   },
   {
     title: 'Share Screenshot',
     render(): React.Element<any> {
       return <ShareScreenshotExample />;
-    }
-  }
+    },
+  },
 ];
diff --git a/RNTester/js/ActivityIndicatorExample.js b/RNTester/js/ActivityIndicatorExample.js
index 05c9e06d4060..2f81857cfcfd 100644
--- a/RNTester/js/ActivityIndicatorExample.js
+++ b/RNTester/js/ActivityIndicatorExample.js
@@ -4,20 +4,25 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
-import React, { Component } from 'react';
-import { ActivityIndicator, StyleSheet, View } from 'react-native';
+import React, {Component} from 'react';
+import {ActivityIndicator, StyleSheet, View} from 'react-native';
 
 /**
  * Optional Flowtype state and timer types definition
  */
-type State = { animating: boolean; };
+type State = {animating: boolean};
 type Timer = number;
 
-class ToggleAnimatingActivityIndicator extends Component<$FlowFixMeProps, State> {
+class ToggleAnimatingActivityIndicator extends Component<
+  $FlowFixMeProps,
+  State,
+> {
   _timer: Timer;
 
   constructor(props) {
@@ -59,8 +64,6 @@ class ToggleAnimatingActivityIndicator extends Component<$FlowFixMeProps, State>
   }
 }
 
-
-
 exports.displayName = (undefined: ?string);
 exports.framework = 'React';
 exports.title = '<ActivityIndicator>';
@@ -76,22 +79,20 @@ exports.examples = [
           color="white"
         />
       );
-    }
+    },
   },
   {
     title: 'Gray',
     render() {
       return (
         <View>
-          <ActivityIndicator
-            style={[styles.centering]}
-          />
+          <ActivityIndicator style={[styles.centering]} />
           <ActivityIndicator
             style={[styles.centering, {backgroundColor: '#eeeeee'}]}
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Custom colors',
@@ -104,7 +105,7 @@ exports.examples = [
           <ActivityIndicator color="#00aa00" />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Large',
@@ -116,38 +117,26 @@ exports.examples = [
           color="white"
         />
       );
-    }
+    },
   },
   {
     title: 'Large, custom colors',
     render() {
       return (
         <View style={styles.horizontal}>
-          <ActivityIndicator
-            size="large"
-            color="#0000ff"
-          />
-          <ActivityIndicator
-            size="large"
-            color="#aa00aa"
-          />
-          <ActivityIndicator
-            size="large"
-            color="#aa3300"
-          />
-          <ActivityIndicator
-            size="large"
-            color="#00aa00"
-          />
+          <ActivityIndicator size="large" color="#0000ff" />
+          <ActivityIndicator size="large" color="#aa00aa" />
+          <ActivityIndicator size="large" color="#aa3300" />
+          <ActivityIndicator size="large" color="#00aa00" />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Start/stop',
     render() {
       return <ToggleAnimatingActivityIndicator />;
-    }
+    },
   },
   {
     title: 'Custom size',
@@ -158,23 +147,17 @@ exports.examples = [
           size="large"
         />
       );
-    }
+    },
   },
   {
     platform: 'android',
     title: 'Custom size (size: 75)',
     render() {
-      return (
-        <ActivityIndicator
-          style={styles.centering}
-          size={75}
-        />
-      );
-    }
+      return <ActivityIndicator style={styles.centering} size={75} />;
+    },
   },
 ];
 
-
 const styles = StyleSheet.create({
   centering: {
     alignItems: 'center',
diff --git a/RNTester/js/AlertExample.js b/RNTester/js/AlertExample.js
index dee922a66abf..02382e769ebb 100644
--- a/RNTester/js/AlertExample.js
+++ b/RNTester/js/AlertExample.js
@@ -4,25 +4,21 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Alert,
-  StyleSheet,
-  Text,
-  TouchableHighlight,
-  View,
-} = ReactNative;
+var {Alert, StyleSheet, Text, TouchableHighlight, View} = ReactNative;
 
 var RNTesterBlock = require('./RNTesterBlock');
 
 // corporate ipsum > lorem ipsum
-var alertMessage = 'Credibly reintermediate next-generation potentialities after goal-oriented ' +
-                   'catalysts for change. Dynamically revolutionize.';
+var alertMessage =
+  'Credibly reintermediate next-generation potentialities after goal-oriented ' +
+  'catalysts for change. Dynamically revolutionize.';
 
 /**
  * Simple alert examples.
@@ -31,90 +27,88 @@ class SimpleAlertExampleBlock extends React.Component {
   render() {
     return (
       <View>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={() => Alert.alert(
-            'Alert Title',
-            alertMessage,
-          )}>
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={() => Alert.alert('Alert Title', alertMessage)}>
           <View style={styles.button}>
             <Text>Alert with message and default button</Text>
           </View>
         </TouchableHighlight>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={() => Alert.alert(
-            'Alert Title',
-            alertMessage,
-            [
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={() =>
+            Alert.alert('Alert Title', alertMessage, [
               {text: 'OK', onPress: () => console.log('OK Pressed!')},
-            ]
-          )}>
+            ])
+          }>
           <View style={styles.button}>
             <Text>Alert with one button</Text>
           </View>
         </TouchableHighlight>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={() => Alert.alert(
-            'Alert Title',
-            alertMessage,
-            [
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={() =>
+            Alert.alert('Alert Title', alertMessage, [
               {text: 'Cancel', onPress: () => console.log('Cancel Pressed!')},
               {text: 'OK', onPress: () => console.log('OK Pressed!')},
-            ]
-          )}>
+            ])
+          }>
           <View style={styles.button}>
             <Text>Alert with two buttons</Text>
           </View>
         </TouchableHighlight>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={() => Alert.alert(
-            'Alert Title',
-            null,
-            [
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={() =>
+            Alert.alert('Alert Title', null, [
               {text: 'Foo', onPress: () => console.log('Foo Pressed!')},
               {text: 'Bar', onPress: () => console.log('Bar Pressed!')},
               {text: 'Baz', onPress: () => console.log('Baz Pressed!')},
-            ]
-          )}>
+            ])
+          }>
           <View style={styles.button}>
             <Text>Alert with three buttons</Text>
           </View>
         </TouchableHighlight>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={() => Alert.alert(
-            'Foo Title',
-            alertMessage,
-            '..............'.split('').map((dot, index) => ({
-              text: 'Button ' + index,
-              onPress: () => console.log('Pressed ' + index)
-            }))
-          )}>
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={() =>
+            Alert.alert(
+              'Foo Title',
+              alertMessage,
+              '..............'.split('').map((dot, index) => ({
+                text: 'Button ' + index,
+                onPress: () => console.log('Pressed ' + index),
+              })),
+            )
+          }>
           <View style={styles.button}>
             <Text>Alert with too many buttons</Text>
           </View>
         </TouchableHighlight>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={() => Alert.alert(
-            'Alert Title',
-            null,
-            [
-              {text: 'OK', onPress: () => console.log('OK Pressed!')},
-            ],
-            {
-              cancelable: false
-            }
-          )}>
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={() =>
+            Alert.alert(
+              'Alert Title',
+              null,
+              [{text: 'OK', onPress: () => console.log('OK Pressed!')}],
+              {
+                cancelable: false,
+              },
+            )
+          }>
           <View style={styles.button}>
             <Text>Alert that cannot be dismissed</Text>
           </View>
         </TouchableHighlight>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={() => Alert.alert(
-            '',
-            alertMessage,
-            [
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={() =>
+            Alert.alert('', alertMessage, [
               {text: 'OK', onPress: () => console.log('OK Pressed!')},
-            ]
-          )}>
+            ])
+          }>
           <View style={styles.button}>
             <Text>Alert without title</Text>
           </View>
diff --git a/RNTester/js/AlertIOSExample.js b/RNTester/js/AlertIOSExample.js
index 8f4a898a5726..4f58c00ada4d 100644
--- a/RNTester/js/AlertIOSExample.js
+++ b/RNTester/js/AlertIOSExample.js
@@ -4,79 +4,69 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  View,
-  Text,
-  TouchableHighlight,
-  AlertIOS,
-} = ReactNative;
+var {StyleSheet, View, Text, TouchableHighlight, AlertIOS} = ReactNative;
 
-var { SimpleAlertExampleBlock } = require('./AlertExample');
+var {SimpleAlertExampleBlock} = require('./AlertExample');
 
 exports.framework = 'React';
 exports.title = 'AlertIOS';
 exports.description = 'iOS alerts and action sheets';
-exports.examples = [{
-  title: 'Alerts',
-  render() {
-    return <SimpleAlertExampleBlock />;
-  }
-},
-{
-  title: 'Prompt Options',
-  render(): React.Element<any> {
-    return <PromptOptions />;
-  }
-},
-{
-  title: 'Prompt Types',
-  render() {
-    return (
-      <View>
-        <TouchableHighlight
-          style={styles.wrapper}
-          onPress={() => AlertIOS.prompt('Plain Text Entry')}>
-
-          <View style={styles.button}>
-            <Text>
-              plain-text
-            </Text>
-          </View>
-
-        </TouchableHighlight>
-        <TouchableHighlight
-          style={styles.wrapper}
-          onPress={() => AlertIOS.prompt('Secure Text', null, null, 'secure-text')}>
-
-          <View style={styles.button}>
-            <Text>
-              secure-text
-            </Text>
-          </View>
-
-        </TouchableHighlight>
-        <TouchableHighlight
-          style={styles.wrapper}
-          onPress={() => AlertIOS.prompt('Login & Password', null, null, 'login-password')}>
-
-          <View style={styles.button}>
-            <Text>
-              login-password
-            </Text>
-          </View>
-
-        </TouchableHighlight>
-      </View>
-    );
-  }
-}];
+exports.examples = [
+  {
+    title: 'Alerts',
+    render() {
+      return <SimpleAlertExampleBlock />;
+    },
+  },
+  {
+    title: 'Prompt Options',
+    render(): React.Element<any> {
+      return <PromptOptions />;
+    },
+  },
+  {
+    title: 'Prompt Types',
+    render() {
+      return (
+        <View>
+          <TouchableHighlight
+            style={styles.wrapper}
+            onPress={() => AlertIOS.prompt('Plain Text Entry')}>
+            <View style={styles.button}>
+              <Text>plain-text</Text>
+            </View>
+          </TouchableHighlight>
+          <TouchableHighlight
+            style={styles.wrapper}
+            onPress={() =>
+              AlertIOS.prompt('Secure Text', null, null, 'secure-text')
+            }>
+            <View style={styles.button}>
+              <Text>secure-text</Text>
+            </View>
+          </TouchableHighlight>
+          <TouchableHighlight
+            style={styles.wrapper}
+            onPress={() =>
+              AlertIOS.prompt('Login & Password', null, null, 'login-password')
+            }>
+            <View style={styles.button}>
+              <Text>login-password</Text>
+            </View>
+          </TouchableHighlight>
+        </View>
+      );
+    },
+  },
+];
 
 class PromptOptions extends React.Component<$FlowFixMeProps, any> {
   customButtons: Array<Object>;
@@ -87,13 +77,16 @@ class PromptOptions extends React.Component<$FlowFixMeProps, any> {
     // $FlowFixMe this seems to be a Flow bug, `saveResponse` is defined below
     this.saveResponse = this.saveResponse.bind(this);
 
-    this.customButtons = [{
-      text: 'Custom OK',
-      onPress: this.saveResponse
-    }, {
-      text: 'Custom Cancel',
-      style: 'cancel',
-    }];
+    this.customButtons = [
+      {
+        text: 'Custom OK',
+        onPress: this.saveResponse,
+      },
+      {
+        text: 'Custom Cancel',
+        style: 'cancel',
+      },
+    ];
 
     this.state = {
       promptValue: undefined,
@@ -104,57 +97,74 @@ class PromptOptions extends React.Component<$FlowFixMeProps, any> {
     return (
       <View>
         <Text style={{marginBottom: 10}}>
-          <Text style={{fontWeight: 'bold'}}>Prompt value:</Text> {this.state.promptValue}
+          <Text style={{fontWeight: 'bold'}}>Prompt value:</Text>{' '}
+          {this.state.promptValue}
         </Text>
 
         <TouchableHighlight
           style={styles.wrapper}
-          onPress={() => AlertIOS.prompt('Type a value', null, this.saveResponse)}>
-
+          onPress={() =>
+            AlertIOS.prompt('Type a value', null, this.saveResponse)
+          }>
           <View style={styles.button}>
-            <Text>
-              prompt with title & callback
-            </Text>
+            <Text>prompt with title & callback</Text>
           </View>
         </TouchableHighlight>
 
         <TouchableHighlight
           style={styles.wrapper}
-          onPress={() => AlertIOS.prompt('Type a value', null, this.customButtons)}>
-
+          onPress={() =>
+            AlertIOS.prompt('Type a value', null, this.customButtons)
+          }>
           <View style={styles.button}>
-            <Text>
-              prompt with title & custom buttons
-            </Text>
+            <Text>prompt with title & custom buttons</Text>
           </View>
         </TouchableHighlight>
 
         <TouchableHighlight
           style={styles.wrapper}
-          onPress={() => AlertIOS.prompt('Type a phone number', null, null, 'plain-text', undefined, 'phone-pad')}>
-
+          onPress={() =>
+            AlertIOS.prompt(
+              'Type a phone number',
+              null,
+              null,
+              'plain-text',
+              undefined,
+              'phone-pad',
+            )
+          }>
           <View style={styles.button}>
-            <Text>
-              prompt with title & custom keyboard
-            </Text>
+            <Text>prompt with title & custom keyboard</Text>
           </View>
         </TouchableHighlight>
 
         <TouchableHighlight
           style={styles.wrapper}
-          onPress={() => AlertIOS.prompt('Type a value', null, this.saveResponse, undefined, 'Default value')}>
-
+          onPress={() =>
+            AlertIOS.prompt(
+              'Type a value',
+              null,
+              this.saveResponse,
+              undefined,
+              'Default value',
+            )
+          }>
           <View style={styles.button}>
-            <Text>
-              prompt with title, callback & default value
-            </Text>
+            <Text>prompt with title, callback & default value</Text>
           </View>
         </TouchableHighlight>
 
         <TouchableHighlight
           style={styles.wrapper}
-          onPress={() => AlertIOS.prompt('Type a value', null, this.customButtons, 'login-password', 'admin@site.com')}>
-
+          onPress={() =>
+            AlertIOS.prompt(
+              'Type a value',
+              null,
+              this.customButtons,
+              'login-password',
+              'admin@site.com',
+            )
+          }>
           <View style={styles.button}>
             <Text>
               prompt with title, custom buttons, login/password & default value
@@ -166,7 +176,7 @@ class PromptOptions extends React.Component<$FlowFixMeProps, any> {
   }
 
   saveResponse(promptValue) {
-    this.setState({ promptValue: JSON.stringify(promptValue) });
+    this.setState({promptValue: JSON.stringify(promptValue)});
   }
 }
 
diff --git a/RNTester/js/AnimatedExample.js b/RNTester/js/AnimatedExample.js
index 9e60a81cb105..d11cbef527b0 100644
--- a/RNTester/js/AnimatedExample.js
+++ b/RNTester/js/AnimatedExample.js
@@ -4,31 +4,29 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Animated,
-  Easing,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Animated, Easing, StyleSheet, Text, View} = ReactNative;
 var RNTesterButton = require('./RNTesterButton');
 
 exports.framework = 'React';
 exports.title = 'Animated - Examples';
-exports.description = 'Animated provides a powerful ' +
+exports.description =
+  'Animated provides a powerful ' +
   'and easy-to-use API for building modern, ' +
   'interactive user experiences.';
 
 exports.examples = [
   {
     title: 'FadeInView',
-    description: 'Uses a simple timing animation to ' +
+    description:
+      'Uses a simple timing animation to ' +
       'bring opacity from 0 to 1 when the component ' +
       'mounts.',
     render: function() {
@@ -40,19 +38,20 @@ exports.examples = [
           };
         }
         componentDidMount() {
-          Animated.timing(       // Uses easing functions
+          Animated.timing(
+            // Uses easing functions
             this.state.fadeAnim, // The value to drive
             {
-              toValue: 1,        // Target
-              duration: 2000,    // Configuration
+              toValue: 1, // Target
+              duration: 2000, // Configuration
             },
-          ).start();             // Don't forget start!
+          ).start(); // Don't forget start!
         }
         render() {
           return (
-            <Animated.View   // Special animatable View
+            <Animated.View // Special animatable View
               style={{
-                opacity: this.state.fadeAnim,  // Binds
+                opacity: this.state.fadeAnim, // Binds
               }}>
               {this.props.children}
             </Animated.View>
@@ -69,19 +68,19 @@ exports.examples = [
         render() {
           return (
             <View>
-              <RNTesterButton onPress={() => {
-                  this.setState((state) => (
-                    {show: !state.show}
-                  ));
+              <RNTesterButton
+                onPress={() => {
+                  this.setState(state => ({show: !state.show}));
                 }}>
-                Press to {this.state.show ?
-                  'Hide' : 'Show'}
+                Press to {this.state.show ? 'Hide' : 'Show'}
               </RNTesterButton>
-              {this.state.show && <FadeInView>
-                <View style={styles.content}>
-                  <Text>FadeInView</Text>
-                </View>
-              </FadeInView>}
+              {this.state.show && (
+                <FadeInView>
+                  <View style={styles.content}>
+                    <Text>FadeInView</Text>
+                  </View>
+                </FadeInView>
+              )}
             </View>
           );
         }
@@ -91,7 +90,8 @@ exports.examples = [
   },
   {
     title: 'Transform Bounce',
-    description: 'One `Animated.Value` is driven by a ' +
+    description:
+      'One `Animated.Value` is driven by a ' +
       'spring with custom constants and mapped to an ' +
       'ordered set of transforms.  Each transform has ' +
       'an interpolation to convert the value into the ' +
@@ -100,33 +100,46 @@ exports.examples = [
       this.anim = this.anim || new Animated.Value(0);
       return (
         <View>
-          <RNTesterButton onPress={() => {
-            Animated.spring(this.anim, {
-              toValue: 0,   // Returns to the start
-              velocity: 3,  // Velocity makes it move
-              tension: -10, // Slow
-              friction: 1,  // Oscillate a lot
-            }).start(); }}>
+          <RNTesterButton
+            onPress={() => {
+              Animated.spring(this.anim, {
+                toValue: 0, // Returns to the start
+                velocity: 3, // Velocity makes it move
+                tension: -10, // Slow
+                friction: 1, // Oscillate a lot
+              }).start();
+            }}>
             Press to Fling it!
           </RNTesterButton>
           <Animated.View
-            style={[styles.content, {
-              transform: [   // Array order matters
-                {scale: this.anim.interpolate({
-                  inputRange: [0, 1],
-                  outputRange: [1, 4],
-                })},
-                {translateX: this.anim.interpolate({
-                  inputRange: [0, 1],
-                  outputRange: [0, 500],
-                })},
-                {rotate: this.anim.interpolate({
-                  inputRange: [0, 1],
-                  outputRange: [
-                    '0deg', '360deg' // 'deg' or 'rad'
-                  ],
-                })},
-              ]}
+            style={[
+              styles.content,
+              {
+                transform: [
+                  // Array order matters
+                  {
+                    scale: this.anim.interpolate({
+                      inputRange: [0, 1],
+                      outputRange: [1, 4],
+                    }),
+                  },
+                  {
+                    translateX: this.anim.interpolate({
+                      inputRange: [0, 1],
+                      outputRange: [0, 500],
+                    }),
+                  },
+                  {
+                    rotate: this.anim.interpolate({
+                      inputRange: [0, 1],
+                      outputRange: [
+                        '0deg',
+                        '360deg', // 'deg' or 'rad'
+                      ],
+                    }),
+                  },
+                ],
+              },
             ]}>
             <Text>Transforms!</Text>
           </Animated.View>
@@ -136,80 +149,87 @@ exports.examples = [
   },
   {
     title: 'Composite Animations with Easing',
-    description: 'Sequence, parallel, delay, and ' +
+    description:
+      'Sequence, parallel, delay, and ' +
       'stagger with different easing functions.',
     render: function() {
-      this.anims = this.anims || [1,2,3].map(
-        () => new Animated.Value(0)
-      );
+      this.anims = this.anims || [1, 2, 3].map(() => new Animated.Value(0));
       return (
         <View>
-          <RNTesterButton onPress={() => {
-            var timing = Animated.timing;
-            Animated.sequence([ // One after the other
-              timing(this.anims[0], {
-                toValue: 200,
-                easing: Easing.linear,
-              }),
-              Animated.delay(400), // Use with sequence
-              timing(this.anims[0], {
-                toValue: 0,
-                easing: Easing.elastic(2), // Springy
-              }),
-              Animated.delay(400),
-              Animated.stagger(200,
-                this.anims.map((anim) => timing(
-                  anim, {toValue: 200}
-                )).concat(
-                this.anims.map((anim) => timing(
-                  anim, {toValue: 0}
-                ))),
-              ),
-              Animated.delay(400),
-              Animated.parallel([
-                Easing.inOut(Easing.quad), // Symmetric
-                Easing.back(1.5),  // Goes backwards first
-                Easing.ease        // Default bezier
-              ].map((easing, ii) => (
-                timing(this.anims[ii], {
-                  toValue: 320, easing, duration: 3000,
-                })
-              ))),
-              Animated.delay(400),
-              Animated.stagger(200,
-                this.anims.map((anim) => timing(anim, {
+          <RNTesterButton
+            onPress={() => {
+              var timing = Animated.timing;
+              Animated.sequence([
+                // One after the other
+                timing(this.anims[0], {
+                  toValue: 200,
+                  easing: Easing.linear,
+                }),
+                Animated.delay(400), // Use with sequence
+                timing(this.anims[0], {
                   toValue: 0,
-                  easing: Easing.bounce, // Like a ball
-                  duration: 2000,
-                })),
-              ),
-            ]).start(); }}>
+                  easing: Easing.elastic(2), // Springy
+                }),
+                Animated.delay(400),
+                Animated.stagger(
+                  200,
+                  this.anims
+                    .map(anim => timing(anim, {toValue: 200}))
+                    .concat(this.anims.map(anim => timing(anim, {toValue: 0}))),
+                ),
+                Animated.delay(400),
+                Animated.parallel(
+                  [
+                    Easing.inOut(Easing.quad), // Symmetric
+                    Easing.back(1.5), // Goes backwards first
+                    Easing.ease, // Default bezier
+                  ].map((easing, ii) =>
+                    timing(this.anims[ii], {
+                      toValue: 320,
+                      easing,
+                      duration: 3000,
+                    }),
+                  ),
+                ),
+                Animated.delay(400),
+                Animated.stagger(
+                  200,
+                  this.anims.map(anim =>
+                    timing(anim, {
+                      toValue: 0,
+                      easing: Easing.bounce, // Like a ball
+                      duration: 2000,
+                    }),
+                  ),
+                ),
+              ]).start();
+            }}>
             Press to Animate
           </RNTesterButton>
-          {['Composite', 'Easing', 'Animations!'].map(
-            (text, ii) => (
-              <Animated.View
-                key={text}
-                style={[styles.content, {
-                  left: this.anims[ii]
-                }]}>
-                <Text>{text}</Text>
-              </Animated.View>
-            )
-          )}
+          {['Composite', 'Easing', 'Animations!'].map((text, ii) => (
+            <Animated.View
+              key={text}
+              style={[
+                styles.content,
+                {
+                  left: this.anims[ii],
+                },
+              ]}>
+              <Text>{text}</Text>
+            </Animated.View>
+          ))}
         </View>
       );
     },
   },
   {
     title: 'Continuous Interactions',
-    description: 'Gesture events, chaining, 2D ' +
+    description:
+      'Gesture events, chaining, 2D ' +
       'values, interrupting and transitioning ' +
       'animations, etc.',
-    render: () => (
-      <Text>Checkout the Gratuitous Animation App!</Text>
-    ),
-  }
+    render: () => <Text>Checkout the Gratuitous Animation App!</Text>,
+  },
 ];
 
 var styles = StyleSheet.create({
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExApp.js b/RNTester/js/AnimatedGratuitousApp/AnExApp.js
index c723f40f7e11..1ade55e2ffc8 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExApp.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExApp.js
@@ -4,19 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Animated,
-  LayoutAnimation,
-  PanResponder,
-  StyleSheet,
-  View,
-} = ReactNative;
+var {Animated, LayoutAnimation, PanResponder, StyleSheet, View} = ReactNative;
 
 var AnExSet = require('AnExSet');
 
@@ -36,55 +32,63 @@ class Circle extends React.Component<any, any> {
     this.state = {
       isActive: false,
       pan: new Animated.ValueXY(), // Vectors reduce boilerplate.  (step1: uncomment)
-      pop: new Animated.Value(0),  // Initial value.               (step2a: uncomment)
+      pop: new Animated.Value(0), // Initial value.               (step2a: uncomment)
     };
   }
 
   _onLongPress(): void {
     var config = {tension: 40, friction: 3};
-    this.state.pan.addListener((value) => {  // Async listener for state changes  (step1: uncomment)
+    this.state.pan.addListener(value => {
+      // Async listener for state changes  (step1: uncomment)
       this.props.onMove && this.props.onMove(value);
     });
     Animated.spring(this.state.pop, {
-      toValue: 1,                  //  Pop to larger size.                      (step2b: uncomment)
-      ...config,                   //  Reuse config for convenient consistency  (step2b: uncomment)
+      toValue: 1, //  Pop to larger size.                      (step2b: uncomment)
+      ...config, //  Reuse config for convenient consistency  (step2b: uncomment)
     }).start();
-    this.setState({panResponder: PanResponder.create({
-      onPanResponderMove: Animated.event([
-        null,                                         // native event - ignore      (step1: uncomment)
-        {dx: this.state.pan.x, dy: this.state.pan.y}, // links pan to gestureState  (step1: uncomment)
-      ]),
-      onPanResponderRelease: (e, gestureState) => {
-        LayoutAnimation.easeInEaseOut();  // @flowfixme animates layout update as one batch (step3: uncomment)
-        Animated.spring(this.state.pop, {
-          toValue: 0,                     // Pop back to 0                       (step2c: uncomment)
-          ...config,
-        }).start();
-        this.setState({panResponder: undefined});
-        this.props.onMove && this.props.onMove({
-          x: gestureState.dx + this.props.restLayout.x,
-          y: gestureState.dy + this.props.restLayout.y,
-        });
-        this.props.onDeactivate();
-        this.state.pan.removeAllListeners();
+    this.setState(
+      {
+        panResponder: PanResponder.create({
+          onPanResponderMove: Animated.event([
+            null, // native event - ignore      (step1: uncomment)
+            {dx: this.state.pan.x, dy: this.state.pan.y}, // links pan to gestureState  (step1: uncomment)
+          ]),
+          onPanResponderRelease: (e, gestureState) => {
+            LayoutAnimation.easeInEaseOut(); // @flowfixme animates layout update as one batch (step3: uncomment)
+            Animated.spring(this.state.pop, {
+              toValue: 0, // Pop back to 0                       (step2c: uncomment)
+              ...config,
+            }).start();
+            this.setState({panResponder: undefined});
+            this.props.onMove &&
+              this.props.onMove({
+                x: gestureState.dx + this.props.restLayout.x,
+                y: gestureState.dy + this.props.restLayout.y,
+              });
+            this.props.onDeactivate();
+            this.state.pan.removeAllListeners();
+          },
+        }),
       },
-    })}, () => {
-      this.props.onActivate();
-    });
+      () => {
+        this.props.onActivate();
+      },
+    );
   }
 
   render(): React.Node {
     if (this.state.panResponder) {
       var handlers = this.state.panResponder.panHandlers;
-      var dragStyle = {                 //  Used to position while dragging
-        position: 'absolute',           //  Hoist out of layout                    (step1: uncomment)
-        ...this.state.pan.getLayout(),  //  Convenience converter                  (step1: uncomment)
+      var dragStyle = {
+        //  Used to position while dragging
+        position: 'absolute', //  Hoist out of layout                    (step1: uncomment)
+        ...this.state.pan.getLayout(), //  Convenience converter                  (step1: uncomment)
       };
     } else {
       handlers = {
         onStartShouldSetResponder: () => !this.state.isActive,
         onResponderGrant: () => {
-          this.state.pan.setValue({x: 0, y: 0});           // reset                (step1: uncomment)
+          this.state.pan.setValue({x: 0, y: 0}); // reset                (step1: uncomment)
           this.state.pan.setOffset(this.props.restLayout); // offset from onLayout (step1: uncomment)
           /* $FlowFixMe(>=0.63.0 site=react_native_fb) This comment suppresses
            * an error found when Flow v0.63 was deployed. To see the error
@@ -99,35 +103,64 @@ class Circle extends React.Component<any, any> {
             clearTimeout(this.longTimer);
             this._toggleIsActive();
           }
-        }
+        },
       };
     }
     var animatedStyle: Object = {
-      shadowOpacity: this.state.pop,    // no need for interpolation            (step2d: uncomment)
+      shadowOpacity: this.state.pop, // no need for interpolation            (step2d: uncomment)
       transform: [
-        {scale: this.state.pop.interpolate({
-          inputRange: [0, 1],
-          outputRange: [1, 1.3]         // scale up from 1 to 1.3               (step2d: uncomment)
-        })},
+        {
+          scale: this.state.pop.interpolate({
+            inputRange: [0, 1],
+            outputRange: [1, 1.3], // scale up from 1 to 1.3               (step2d: uncomment)
+          }),
+        },
       ],
     };
     var openVal = this.props.openVal;
     if (this.props.dummy) {
       animatedStyle.opacity = 0;
     } else if (this.state.isActive) {
-      var innerOpenStyle = [styles.open, {                                 // (step4: uncomment)
-        left: openVal.interpolate({inputRange: [0, 1], outputRange: [this.props.restLayout.x, 0]}),
-        top: openVal.interpolate({inputRange: [0, 1], outputRange: [this.props.restLayout.y, 0]}),
-        width: openVal.interpolate({inputRange: [0, 1], outputRange: [CIRCLE_SIZE, this.props.containerLayout.width]}),
-        height: openVal.interpolate({inputRange: [0, 1], outputRange: [CIRCLE_SIZE, this.props.containerLayout.height]}),
-        margin: openVal.interpolate({inputRange: [0, 1], outputRange: [CIRCLE_MARGIN, 0]}),
-        borderRadius: openVal.interpolate({inputRange: [-0.15, 0, 0.5, 1], outputRange: [0, CIRCLE_SIZE / 2, CIRCLE_SIZE * 1.3, 0]}),
-      }];
+      var innerOpenStyle = [
+        styles.open,
+        {
+          // (step4: uncomment)
+          left: openVal.interpolate({
+            inputRange: [0, 1],
+            outputRange: [this.props.restLayout.x, 0],
+          }),
+          top: openVal.interpolate({
+            inputRange: [0, 1],
+            outputRange: [this.props.restLayout.y, 0],
+          }),
+          width: openVal.interpolate({
+            inputRange: [0, 1],
+            outputRange: [CIRCLE_SIZE, this.props.containerLayout.width],
+          }),
+          height: openVal.interpolate({
+            inputRange: [0, 1],
+            outputRange: [CIRCLE_SIZE, this.props.containerLayout.height],
+          }),
+          margin: openVal.interpolate({
+            inputRange: [0, 1],
+            outputRange: [CIRCLE_MARGIN, 0],
+          }),
+          borderRadius: openVal.interpolate({
+            inputRange: [-0.15, 0, 0.5, 1],
+            outputRange: [0, CIRCLE_SIZE / 2, CIRCLE_SIZE * 1.3, 0],
+          }),
+        },
+      ];
     }
     return (
       <Animated.View
         onLayout={this.props.onLayout}
-        style={[styles.dragView, dragStyle, animatedStyle, this.state.isActive ? styles.open : null]}
+        style={[
+          styles.dragView,
+          dragStyle,
+          animatedStyle,
+          this.state.isActive ? styles.open : null,
+        ]}
         {...handlers}>
         <Animated.View style={[styles.circle, innerOpenStyle]}>
           <AnExSet
@@ -144,14 +177,15 @@ class Circle extends React.Component<any, any> {
   _toggleIsActive(velocity) {
     var config = {tension: 30, friction: 7};
     if (this.state.isActive) {
-      Animated.spring(this.props.openVal, {toValue: 0, ...config}).start(() => { // (step4: uncomment)
+      Animated.spring(this.props.openVal, {toValue: 0, ...config}).start(() => {
+        // (step4: uncomment)
         this.setState({isActive: false}, this.props.onDeactivate);
-      });                                                                        // (step4: uncomment)
+      }); // (step4: uncomment)
     } else {
       this.props.onActivate();
       this.setState({isActive: true, panResponder: undefined}, () => {
         // this.props.openVal.setValue(1);                                             // (step4: comment)
-        Animated.spring(this.props.openVal, {toValue: 1, ...config}).start();    // (step4: uncomment)
+        Animated.spring(this.props.openVal, {toValue: 1, ...config}).start(); // (step4: uncomment)
       });
     }
   }
@@ -160,7 +194,7 @@ class Circle extends React.Component<any, any> {
 class AnExApp extends React.Component<any, any> {
   static title = 'Animated - Gratuitous App';
   static description = 'Bunch of Animations - tap a circle to ' +
-    'open a view with more animations, or longPress and drag to reorder circles.';
+  'open a view with more animations, or longPress and drag to reorder circles.';
 
   _onMove: (position: Point) => void;
   constructor(props: any): void {
@@ -185,7 +219,7 @@ class AnExApp extends React.Component<any, any> {
         if (!this.state.restLayouts[idx]) {
           var onLayout = function(index, e) {
             var layout = e.nativeEvent.layout;
-            this.setState((state) => {
+            this.setState(state => {
               state.restLayouts[index] = layout;
               return state;
             });
@@ -208,7 +242,10 @@ class AnExApp extends React.Component<any, any> {
     });
     if (this.state.activeKey) {
       circles.push(
-        <Animated.View key="dark" style={[styles.darkening, {opacity: this.state.openVal}]} />
+        <Animated.View
+          key="dark"
+          style={[styles.darkening, {opacity: this.state.openVal}]}
+        />,
       );
       circles.push(
         <Circle
@@ -218,13 +255,17 @@ class AnExApp extends React.Component<any, any> {
           restLayout={this.state.activeInitialLayout}
           containerLayout={this.state.layout}
           onMove={this._onMove}
-          onDeactivate={() => { this.setState({activeKey: undefined}); }}
-        />
+          onDeactivate={() => {
+            this.setState({activeKey: undefined});
+          }}
+        />,
       );
     }
     return (
       <View style={styles.container}>
-        <View style={styles.grid} onLayout={(e) => this.setState({layout: e.nativeEvent.layout})}>
+        <View
+          style={styles.grid}
+          onLayout={e => this.setState({layout: e.nativeEvent.layout})}>
           {circles}
         </View>
       </View>
@@ -234,7 +275,7 @@ class AnExApp extends React.Component<any, any> {
   _onMove(position: Point): void {
     var newKeys = moveToClosest(this.state, position);
     if (newKeys !== this.state.keys) {
-      LayoutAnimation.easeInEaseOut();  // animates layout update as one batch (step3: uncomment)
+      LayoutAnimation.easeInEaseOut(); // animates layout update as one batch (step3: uncomment)
       this.setState({keys: newKeys});
     }
   }
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExBobble.js b/RNTester/js/AnimatedGratuitousApp/AnExBobble.js
index 7f56bbe68e97..14d4c839abe7 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExBobble.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExBobble.js
@@ -4,27 +4,28 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Animated,
-  PanResponder,
-  StyleSheet,
-  View,
-} = ReactNative;
+var {Animated, PanResponder, StyleSheet, View} = ReactNative;
 
 var NUM_BOBBLES = 5;
 var RAD_EACH = Math.PI / 2 / (NUM_BOBBLES - 2);
 var RADIUS = 160;
-var BOBBLE_SPOTS = [...Array(NUM_BOBBLES)].map((_, i) => {  // static positions
-  return i === 0 ? {x: 0, y: 0} : {                         // first bobble is the selector
-    x: -Math.cos(RAD_EACH * (i - 1)) * RADIUS,
-    y: -Math.sin(RAD_EACH * (i - 1)) * RADIUS,
-  };
+var BOBBLE_SPOTS = [...Array(NUM_BOBBLES)].map((_, i) => {
+  // static positions
+  return i === 0
+    ? {x: 0, y: 0}
+    : {
+        // first bobble is the selector
+        x: -Math.cos(RAD_EACH * (i - 1)) * RADIUS,
+        y: -Math.sin(RAD_EACH * (i - 1)) * RADIUS,
+      };
 });
 
 class AnExBobble extends React.Component<Object, any> {
@@ -35,18 +36,19 @@ class AnExBobble extends React.Component<Object, any> {
       return new Animated.ValueXY();
     });
     this.state.selectedBobble = null;
-    var bobblePanListener = (e, gestureState) => {     // async events => change selection
+    var bobblePanListener = (e, gestureState) => {
+      // async events => change selection
       var newSelected = computeNewSelected(gestureState);
       if (this.state.selectedBobble !== newSelected) {
         if (this.state.selectedBobble !== null) {
           var restSpot = BOBBLE_SPOTS[this.state.selectedBobble];
           Animated.spring(this.state.bobbles[this.state.selectedBobble], {
-            toValue: restSpot,       // return previously selected bobble to rest position
+            toValue: restSpot, // return previously selected bobble to rest position
           }).start();
         }
         if (newSelected !== null && newSelected !== 0) {
           Animated.spring(this.state.bobbles[newSelected], {
-            toValue: this.state.bobbles[0],    // newly selected should track the selector
+            toValue: this.state.bobbles[0], // newly selected should track the selector
           }).start();
         }
         this.state.selectedBobble = newSelected;
@@ -55,7 +57,7 @@ class AnExBobble extends React.Component<Object, any> {
     var releaseBobble = () => {
       this.state.bobbles.forEach((bobble, i) => {
         Animated.spring(bobble, {
-          toValue: {x: 0, y: 0}           // all bobbles return to zero
+          toValue: {x: 0, y: 0}, // all bobbles return to zero
         }).start();
       });
     };
@@ -64,14 +66,14 @@ class AnExBobble extends React.Component<Object, any> {
       onPanResponderGrant: () => {
         BOBBLE_SPOTS.forEach((spot, idx) => {
           Animated.spring(this.state.bobbles[idx], {
-            toValue: spot,                // spring each bobble to its spot
-            friction: 3,                  // less friction => bouncier
+            toValue: spot, // spring each bobble to its spot
+            friction: 3, // less friction => bouncier
           }).start();
         });
       },
       onPanResponderMove: Animated.event(
-        [ null, {dx: this.state.bobbles[0].x, dy: this.state.bobbles[0].y} ],
-        {listener: bobblePanListener}     // async state changes with arbitrary logic
+        [null, {dx: this.state.bobbles[0].x, dy: this.state.bobbles[0].y}],
+        {listener: bobblePanListener}, // async state changes with arbitrary logic
       ),
       onPanResponderRelease: releaseBobble,
       onPanResponderTerminate: releaseBobble,
@@ -89,10 +91,13 @@ class AnExBobble extends React.Component<Object, any> {
               {...handlers}
               key={i}
               source={{uri: BOBBLE_IMGS[j]}}
-              style={[styles.circle, {
-                backgroundColor: randColor(),                             // re-renders are obvious
-                transform: this.state.bobbles[j].getTranslateTransform(), // simple conversion
-              }]}
+              style={[
+                styles.circle,
+                {
+                  backgroundColor: randColor(), // re-renders are obvious
+                  transform: this.state.bobbles[j].getTranslateTransform(), // simple conversion
+                },
+              ]}
             />
           );
         })}
@@ -119,9 +124,7 @@ var styles = StyleSheet.create({
   },
 });
 
-function computeNewSelected(
-  gestureState: Object,
-): ?number {
+function computeNewSelected(gestureState: Object): ?number {
   var {dx, dy} = gestureState;
   var minDist = Infinity;
   var newSelected = null;
@@ -140,7 +143,7 @@ function computeNewSelected(
 }
 
 function randColor(): string {
-  var colors = [0,1,2].map(() => Math.floor(Math.random() * 150 + 100));
+  var colors = [0, 1, 2].map(() => Math.floor(Math.random() * 150 + 100));
   return 'rgb(' + colors.join(',') + ')';
 }
 
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExChained.js b/RNTester/js/AnimatedGratuitousApp/AnExChained.js
index 00d72dafb12a..b3c09570362a 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExChained.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExChained.js
@@ -4,56 +4,56 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Animated,
-  PanResponder,
-  StyleSheet,
-  View,
-} = ReactNative;
+var {Animated, PanResponder, StyleSheet, View} = ReactNative;
 
 class AnExChained extends React.Component<Object, any> {
   constructor(props: Object) {
     super(props);
     this.state = {
-      stickers: [new Animated.ValueXY()],                    // 1 leader
+      stickers: [new Animated.ValueXY()], // 1 leader
     };
-    var stickerConfig = {tension: 2, friction: 3};           // soft spring
-    for (var i = 0; i < 4; i++) {                            // 4 followers
+    var stickerConfig = {tension: 2, friction: 3}; // soft spring
+    for (var i = 0; i < 4; i++) {
+      // 4 followers
       var sticker = new Animated.ValueXY();
       Animated.spring(sticker, {
         ...stickerConfig,
-        toValue: this.state.stickers[i],               // Animated toValue's are tracked
+        toValue: this.state.stickers[i], // Animated toValue's are tracked
       }).start();
-      this.state.stickers.push(sticker);               // push on the followers
+      this.state.stickers.push(sticker); // push on the followers
     }
     var releaseChain = (e, gestureState) => {
-      this.state.stickers[0].flattenOffset();          // merges offset into value and resets
-      Animated.sequence([                              // spring to start after decay finishes
-        Animated.decay(this.state.stickers[0], {       // coast to a stop
+      this.state.stickers[0].flattenOffset(); // merges offset into value and resets
+      Animated.sequence([
+        // spring to start after decay finishes
+        Animated.decay(this.state.stickers[0], {
+          // coast to a stop
           velocity: {x: gestureState.vx, y: gestureState.vy},
           deceleration: 0.997,
         }),
         Animated.spring(this.state.stickers[0], {
-          toValue: {x: 0, y: 0}                        // return to start
+          toValue: {x: 0, y: 0}, // return to start
         }),
       ]).start();
     };
     this.state.chainResponder = PanResponder.create({
       onStartShouldSetPanResponder: () => true,
       onPanResponderGrant: () => {
-        this.state.stickers[0].stopAnimation((value) => {
-          this.state.stickers[0].setOffset(value);           // start where sticker animated to
-          this.state.stickers[0].setValue({x: 0, y: 0});     // avoid flicker before next event
+        this.state.stickers[0].stopAnimation(value => {
+          this.state.stickers[0].setOffset(value); // start where sticker animated to
+          this.state.stickers[0].setValue({x: 0, y: 0}); // avoid flicker before next event
         });
       },
       onPanResponderMove: Animated.event(
-        [null, {dx: this.state.stickers[0].x, dy: this.state.stickers[0].y}] // map gesture to leader
+        [null, {dx: this.state.stickers[0].x, dy: this.state.stickers[0].y}], // map gesture to leader
       ),
       onPanResponderRelease: releaseChain,
       onPanResponderTerminate: releaseChain,
@@ -65,15 +65,18 @@ class AnExChained extends React.Component<Object, any> {
       <View style={styles.chained}>
         {this.state.stickers.map((_, i) => {
           var j = this.state.stickers.length - i - 1; // reverse so leader is on top
-          var handlers = (j === 0) ? this.state.chainResponder.panHandlers : {};
+          var handlers = j === 0 ? this.state.chainResponder.panHandlers : {};
           return (
             <Animated.Image
               {...handlers}
               key={i}
               source={CHAIN_IMGS[j]}
-              style={[styles.sticker, {
-                transform: this.state.stickers[j].getTranslateTransform(), // simple conversion
-              }]}
+              style={[
+                styles.sticker,
+                {
+                  transform: this.state.stickers[j].getTranslateTransform(), // simple conversion
+                },
+              ]}
             />
           );
         })}
@@ -86,7 +89,7 @@ var styles = StyleSheet.create({
   chained: {
     alignSelf: 'flex-end',
     top: -160,
-    right: 126
+    right: 126,
   },
   sticker: {
     position: 'absolute',
@@ -101,7 +104,7 @@ var CHAIN_IMGS = [
   require('../bunny.png'),
   require('../relay.png'),
   require('../hawk.png'),
-  require('../bunny.png')
+  require('../bunny.png'),
 ];
 
 module.exports = AnExChained;
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExScroll.js b/RNTester/js/AnimatedGratuitousApp/AnExScroll.js
index c0f7495e4baa..0dde543196d7 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExScroll.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExScroll.js
@@ -4,23 +4,18 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Animated,
-  Image,
-  ScrollView,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Animated, Image, ScrollView, StyleSheet, Text, View} = ReactNative;
 
 class AnExScroll extends React.Component<$FlowFixMeProps, any> {
-  state: any = { scrollX: new Animated.Value(0) };
+  state: any = {scrollX: new Animated.Value(0)};
 
   render() {
     var width = this.props.panelWidth;
@@ -28,20 +23,17 @@ class AnExScroll extends React.Component<$FlowFixMeProps, any> {
       <View style={styles.container}>
         <ScrollView
           automaticallyAdjustContentInsets={false}
-          scrollEventThrottle={16 /* get all events */ }
+          scrollEventThrottle={16 /* get all events */}
           onScroll={Animated.event(
-            [{nativeEvent: {contentOffset: {x: this.state.scrollX}}}]  // nested event mapping
+            [{nativeEvent: {contentOffset: {x: this.state.scrollX}}}], // nested event mapping
           )}
           contentContainerStyle={{flex: 1, padding: 10}}
           pagingEnabled={true}
           horizontal={true}>
           <View style={[styles.page, {width}]}>
-            <Image
-              style={{width: 180, height: 180}}
-              source={HAWK_PIC}
-            />
+            <Image style={{width: 180, height: 180}} source={HAWK_PIC} />
             <Text style={styles.text}>
-              {'I\'ll find something to put here.'}
+              {"I'll find something to put here."}
             </Text>
           </View>
           <View style={[styles.page, {width}]}>
@@ -53,29 +45,34 @@ class AnExScroll extends React.Component<$FlowFixMeProps, any> {
         </ScrollView>
         <Animated.Image
           pointerEvents="none"
-          style={[styles.bunny, {transform: [
-            {
-              translateX: this.state.scrollX.interpolate({
-                inputRange: [0, width, 2 * width],
-                outputRange: [0, 0, width / 3],
-                extrapolate: 'clamp',
-              }),
-            },
-            {
-              translateY: this.state.scrollX.interpolate({
-                inputRange: [0, width, 2 * width],
-                outputRange: [0, -200, -260],
-                extrapolate: 'clamp',
-              }),
-            },
+          style={[
+            styles.bunny,
             {
-              scale: this.state.scrollX.interpolate({
-                inputRange: [0, width, 2 * width],
-                outputRange: [0.5, 0.5, 2],
-                extrapolate: 'clamp',
-              }),
+              transform: [
+                {
+                  translateX: this.state.scrollX.interpolate({
+                    inputRange: [0, width, 2 * width],
+                    outputRange: [0, 0, width / 3],
+                    extrapolate: 'clamp',
+                  }),
+                },
+                {
+                  translateY: this.state.scrollX.interpolate({
+                    inputRange: [0, width, 2 * width],
+                    outputRange: [0, -200, -260],
+                    extrapolate: 'clamp',
+                  }),
+                },
+                {
+                  scale: this.state.scrollX.interpolate({
+                    inputRange: [0, width, 2 * width],
+                    outputRange: [0.5, 0.5, 2],
+                    extrapolate: 'clamp',
+                  }),
+                },
+              ],
             },
-          ]}]}
+          ]}
           source={BUNNY_PIC}
         />
       </View>
@@ -107,7 +104,13 @@ var styles = StyleSheet.create({
   },
 });
 
-var HAWK_PIC = {uri: 'https://scontent-sea1-1.xx.fbcdn.net/hphotos-xfa1/t39.1997-6/10734304_1562225620659674_837511701_n.png'};
-var BUNNY_PIC = {uri: 'https://scontent-sea1-1.xx.fbcdn.net/hphotos-xaf1/t39.1997-6/851564_531111380292237_1898871086_n.png'};
+var HAWK_PIC = {
+  uri:
+    'https://scontent-sea1-1.xx.fbcdn.net/hphotos-xfa1/t39.1997-6/10734304_1562225620659674_837511701_n.png',
+};
+var BUNNY_PIC = {
+  uri:
+    'https://scontent-sea1-1.xx.fbcdn.net/hphotos-xaf1/t39.1997-6/851564_531111380292237_1898871086_n.png',
+};
 
 module.exports = AnExScroll;
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExSet.js b/RNTester/js/AnimatedGratuitousApp/AnExSet.js
index 873d5251c2eb..83bc5bfdb5f3 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExSet.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExSet.js
@@ -4,19 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Animated,
-  PanResponder,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Animated, PanResponder, StyleSheet, Text, View} = ReactNative;
 
 var AnExBobble = require('./AnExBobble');
 var AnExChained = require('./AnExChained');
@@ -27,7 +23,7 @@ class AnExSet extends React.Component<Object, any> {
   constructor(props: Object) {
     super(props);
     function randColor() {
-      var colors = [0,1,2].map(() => Math.floor(Math.random() * 150 + 100));
+      var colors = [0, 1, 2].map(() => Math.floor(Math.random() * 150 + 100));
       return 'rgb(' + colors.join(',') + ')';
     }
     this.state = {
@@ -36,38 +32,35 @@ class AnExSet extends React.Component<Object, any> {
     };
   }
   render(): React.Node {
-    var backgroundColor = this.props.openVal ?
-      this.props.openVal.interpolate({
-        inputRange: [0, 1],
-        outputRange: [
-          this.state.closeColor,  // interpolates color strings
-          this.state.openColor
-        ],
-      }) :
-      this.state.closeColor;
-    var panelWidth = this.props.containerLayout && this.props.containerLayout.width || 320;
+    var backgroundColor = this.props.openVal
+      ? this.props.openVal.interpolate({
+          inputRange: [0, 1],
+          outputRange: [
+            this.state.closeColor, // interpolates color strings
+            this.state.openColor,
+          ],
+        })
+      : this.state.closeColor;
+    var panelWidth =
+      (this.props.containerLayout && this.props.containerLayout.width) || 320;
     return (
       <View style={styles.container}>
         <Animated.View
-          style={[styles.header, { backgroundColor }]}
+          style={[styles.header, {backgroundColor}]}
           {...this.state.dismissResponder.panHandlers}>
-          <Text style={[styles.text, styles.headerText]}>
-            {this.props.id}
-          </Text>
+          <Text style={[styles.text, styles.headerText]}>{this.props.id}</Text>
         </Animated.View>
-        {this.props.isActive &&
+        {this.props.isActive && (
           <View style={styles.stream}>
             <View style={styles.card}>
-              <Text style={styles.text}>
-                July 2nd
-              </Text>
+              <Text style={styles.text}>July 2nd</Text>
               <AnExTilt isActive={this.props.isActive} />
               <AnExBobble />
             </View>
-            <AnExScroll panelWidth={panelWidth}/>
+            <AnExScroll panelWidth={panelWidth} />
             <AnExChained />
           </View>
-        }
+        )}
       </View>
     );
   }
@@ -77,24 +70,26 @@ class AnExSet extends React.Component<Object, any> {
     this.state.dismissResponder = PanResponder.create({
       onStartShouldSetPanResponder: () => this.props.isActive,
       onPanResponderGrant: () => {
-        Animated.spring(this.props.openVal, {          // Animated value passed in.
-          toValue: this.state.dismissY.interpolate({   // Track dismiss gesture
-            inputRange: [0, 300],                      // and interpolate pixel distance
-            outputRange: [1, 0],                       // to a fraction.
+        Animated.spring(this.props.openVal, {
+          // Animated value passed in.
+          toValue: this.state.dismissY.interpolate({
+            // Track dismiss gesture
+            inputRange: [0, 300], // and interpolate pixel distance
+            outputRange: [1, 0], // to a fraction.
           }),
           useNativeDriver: true,
         }).start();
       },
       onPanResponderMove: Animated.event(
-        [null, {dy: this.state.dismissY}],             // track pan gesture
-        {useNativeDriver: true}
+        [null, {dy: this.state.dismissY}], // track pan gesture
+        {useNativeDriver: true},
       ),
       onPanResponderRelease: (e, gestureState) => {
         if (gestureState.dy > 100) {
-          this.props.onDismiss(gestureState.vy);  // delegates dismiss action to parent
+          this.props.onDismiss(gestureState.vy); // delegates dismiss action to parent
         } else {
           Animated.spring(this.props.openVal, {
-            toValue: 1,                           // animate back open if released early
+            toValue: 1, // animate back open if released early
             useNativeDriver: true,
           }).start();
         }
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExTilt.js b/RNTester/js/AnimatedGratuitousApp/AnExTilt.js
index c7540de730eb..dbd823843486 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExTilt.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExTilt.js
@@ -4,17 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Animated,
-  PanResponder,
-  StyleSheet,
-} = ReactNative;
+var {Animated, PanResponder, StyleSheet} = ReactNative;
 
 class AnExTilt extends React.Component<Object, any> {
   constructor(props: Object) {
@@ -29,14 +27,14 @@ class AnExTilt extends React.Component<Object, any> {
       onPanResponderGrant: () => {
         Animated.timing(this.state.opacity, {
           toValue: this.state.panX.interpolate({
-            inputRange: [-300, 0, 300],            // pan is in pixels
-            outputRange: [0, 1, 0],                // goes to zero at both edges
+            inputRange: [-300, 0, 300], // pan is in pixels
+            outputRange: [0, 1, 0], // goes to zero at both edges
           }),
-          duration: 0,                             // direct tracking
+          duration: 0, // direct tracking
         }).start();
       },
       onPanResponderMove: Animated.event(
-        [null, {dx: this.state.panX}]              // panX is linked to the gesture
+        [null, {dx: this.state.panX}], // panX is linked to the gesture
       ),
       onPanResponderRelease: (e, gestureState) => {
         var toValue = 0;
@@ -46,19 +44,20 @@ class AnExTilt extends React.Component<Object, any> {
           toValue = -500;
         }
         Animated.spring(this.state.panX, {
-          toValue,                         // animate back to center or off screen
-          velocity: gestureState.vx,       // maintain gesture velocity
+          toValue, // animate back to center or off screen
+          velocity: gestureState.vx, // maintain gesture velocity
           tension: 10,
           friction: 3,
         }).start();
         this.state.panX.removeAllListeners();
-        var id = this.state.panX.addListener(({value}) => { // listen until offscreen
+        var id = this.state.panX.addListener(({value}) => {
+          // listen until offscreen
           if (Math.abs(value) > 400) {
-            this.state.panX.removeListener(id);             // offscreen, so stop listening
+            this.state.panX.removeListener(id); // offscreen, so stop listening
             Animated.timing(this.state.opacity, {
-              toValue: 1,   // Fade back in.  This unlinks it from tracking this.state.panX
+              toValue: 1, // Fade back in.  This unlinks it from tracking this.state.panX
             }).start();
-            this.state.panX.setValue(0);                    // Note: stops the spring animation
+            this.state.panX.setValue(0); // Note: stops the spring animation
             toValue !== 0 && this._startBurnsZoom();
           }
         });
@@ -67,10 +66,10 @@ class AnExTilt extends React.Component<Object, any> {
   }
 
   _startBurnsZoom() {
-    this.state.burns.setValue(1);     // reset to beginning
+    this.state.burns.setValue(1); // reset to beginning
     Animated.decay(this.state.burns, {
-      velocity: 1,                    // sublte zoom
-      deceleration: 0.9999,           // slow decay
+      velocity: 1, // sublte zoom
+      deceleration: 0.9999, // slow decay
     }).start();
   }
 
@@ -82,27 +81,37 @@ class AnExTilt extends React.Component<Object, any> {
     return (
       <Animated.View
         {...this.state.tiltPanResponder.panHandlers}
-        style={[styles.tilt, {
-          opacity: this.state.opacity,
-          transform: [
-            {rotate: this.state.panX.interpolate({
-              inputRange: [-320, 320],
-              outputRange: ['-15deg', '15deg']})},  // interpolate string "shapes"
-            {translateX: this.state.panX},
-          ],
-        }]}>
+        style={[
+          styles.tilt,
+          {
+            opacity: this.state.opacity,
+            transform: [
+              {
+                rotate: this.state.panX.interpolate({
+                  inputRange: [-320, 320],
+                  outputRange: ['-15deg', '15deg'],
+                }),
+              }, // interpolate string "shapes"
+              {translateX: this.state.panX},
+            ],
+          },
+        ]}>
         <Animated.Image
           pointerEvents="none"
           style={{
             flex: 1,
             transform: [
-              {translateX: this.state.panX.interpolate({
-                inputRange: [-3, 3],     // small range is extended by default
-                outputRange: [2, -2]})   // parallax
+              {
+                translateX: this.state.panX.interpolate({
+                  inputRange: [-3, 3], // small range is extended by default
+                  outputRange: [2, -2],
+                }), // parallax
               },
-              {scale: this.state.burns.interpolate({
-                inputRange: [1, 3000],
-                outputRange: [1, 1.25]}) // simple multiplier
+              {
+                scale: this.state.burns.interpolate({
+                  inputRange: [1, 3000],
+                  outputRange: [1, 1.25],
+                }), // simple multiplier
               },
             ],
           }}
diff --git a/RNTester/js/AppStateExample.js b/RNTester/js/AppStateExample.js
index f6b4265c84c3..b4ed67c27ba9 100644
--- a/RNTester/js/AppStateExample.js
+++ b/RNTester/js/AppStateExample.js
@@ -4,19 +4,20 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  AppState,
-  Text,
-  View
-} = ReactNative;
+const {AppState, Text, View} = ReactNative;
 
-class AppStateSubscription extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class AppStateSubscription extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   state = {
     appState: AppState.currentState,
     previousAppStates: [],
@@ -37,7 +38,7 @@ class AppStateSubscription extends React.Component<$FlowFixMeProps, $FlowFixMeSt
     this.setState({memoryWarnings: this.state.memoryWarnings + 1});
   };
 
-  _handleAppStateChange = (appState) => {
+  _handleAppStateChange = appState => {
     var previousAppStates = this.state.previousAppStates.slice();
     previousAppStates.push(this.state.appState);
     this.setState({
@@ -75,21 +76,31 @@ exports.examples = [
   {
     title: 'AppState.currentState',
     description: 'Can be null on app initialization',
-    render() { return <Text>{AppState.currentState}</Text>; }
+    render() {
+      return <Text>{AppState.currentState}</Text>;
+    },
   },
   {
     title: 'Subscribed AppState:',
-    description: 'This changes according to the current state, so you can only ever see it rendered as "active"',
-    render(): React.Element<any> { return <AppStateSubscription showCurrentOnly={true} />; }
+    description:
+      'This changes according to the current state, so you can only ever see it rendered as "active"',
+    render(): React.Element<any> {
+      return <AppStateSubscription showCurrentOnly={true} />;
+    },
   },
   {
     title: 'Previous states:',
-    render(): React.Element<any> { return <AppStateSubscription showCurrentOnly={false} />; }
+    render(): React.Element<any> {
+      return <AppStateSubscription showCurrentOnly={false} />;
+    },
   },
   {
     platform: 'ios',
     title: 'Memory Warnings',
-    description: 'In the IOS simulator, hit Shift+Command+M to simulate a memory warning.',
-    render(): React.Element<any> { return <AppStateSubscription showMemoryWarnings={true} />; }
+    description:
+      'In the IOS simulator, hit Shift+Command+M to simulate a memory warning.',
+    render(): React.Element<any> {
+      return <AppStateSubscription showMemoryWarnings={true} />;
+    },
   },
 ];
diff --git a/RNTester/js/AssetScaledImageExample.js b/RNTester/js/AssetScaledImageExample.js
index 51e97a8aee92..d3a295a27e82 100644
--- a/RNTester/js/AssetScaledImageExample.js
+++ b/RNTester/js/AssetScaledImageExample.js
@@ -4,22 +4,22 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Image,
-  StyleSheet,
-  View,
-  ScrollView
-} = ReactNative;
+var {Image, StyleSheet, View, ScrollView} = ReactNative;
 
-class AssetScaledImageExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class AssetScaledImageExample extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   state = {
-    asset: this.props.asset
+    asset: this.props.asset,
   };
 
   render() {
@@ -27,16 +27,16 @@ class AssetScaledImageExample extends React.Component<$FlowFixMeProps, $FlowFixM
     return (
       <ScrollView>
         <View style={styles.row}>
-          <Image source={image} style={styles.imageWide}/>
+          <Image source={image} style={styles.imageWide} />
         </View>
         <View style={styles.row}>
-          <Image source={image} style={styles.imageThumb}/>
-          <Image source={image} style={styles.imageThumb}/>
-          <Image source={image} style={styles.imageThumb}/>
+          <Image source={image} style={styles.imageThumb} />
+          <Image source={image} style={styles.imageThumb} />
+          <Image source={image} style={styles.imageThumb} />
         </View>
         <View style={styles.row}>
-          <Image source={image} style={styles.imageT1}/>
-          <Image source={image} style={styles.imageT2}/>
+          <Image source={image} style={styles.imageT1} />
+          <Image source={image} style={styles.imageT2} />
         </View>
       </ScrollView>
     );
@@ -85,5 +85,6 @@ var styles = StyleSheet.create({
 });
 
 exports.title = '<AssetScaledImageExample>';
-exports.description = 'Example component that displays the automatic scaling capabilities of the <Image /> tag';
+exports.description =
+  'Example component that displays the automatic scaling capabilities of the <Image /> tag';
 module.exports = AssetScaledImageExample;
diff --git a/RNTester/js/AsyncStorageExample.js b/RNTester/js/AsyncStorageExample.js
index eb354b2db633..14b778022046 100644
--- a/RNTester/js/AsyncStorageExample.js
+++ b/RNTester/js/AsyncStorageExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  AsyncStorage,
-  PickerIOS,
-  Text,
-  View
-} = ReactNative;
+var {AsyncStorage, PickerIOS, Text, View} = ReactNative;
 var PickerItemIOS = PickerIOS.Item;
 
 var STORAGE_KEY = '@AsyncStorageExample:key';
@@ -34,7 +31,7 @@ class BasicStorageExample extends React.Component<{}, $FlowFixMeState> {
   _loadInitialState = async () => {
     try {
       var value = await AsyncStorage.getItem(STORAGE_KEY);
-      if (value !== null){
+      if (value !== null) {
         this.setState({selectedValue: value});
         this._appendMessage('Recovered selection from disk: ' + value);
       } else {
@@ -49,35 +46,27 @@ class BasicStorageExample extends React.Component<{}, $FlowFixMeState> {
     var color = this.state.selectedValue;
     return (
       <View>
-        <PickerIOS
-          selectedValue={color}
-          onValueChange={this._onValueChange}>
-          {COLORS.map((value) => (
-            <PickerItemIOS
-              key={value}
-              value={value}
-              label={value}
-            />
+        <PickerIOS selectedValue={color} onValueChange={this._onValueChange}>
+          {COLORS.map(value => (
+            <PickerItemIOS key={value} value={value} label={value} />
           ))}
         </PickerIOS>
         <Text>
           {'Selected: '}
-          <Text style={{color}}>
-            {this.state.selectedValue}
-          </Text>
+          <Text style={{color}}>{this.state.selectedValue}</Text>
         </Text>
-        <Text>{' '}</Text>
+        <Text> </Text>
         <Text onPress={this._removeStorage}>
           Press here to remove from storage.
         </Text>
-        <Text>{' '}</Text>
+        <Text> </Text>
         <Text>Messages:</Text>
-        {this.state.messages.map((m) => <Text key={m}>{m}</Text>)}
+        {this.state.messages.map(m => <Text key={m}>{m}</Text>)}
       </View>
     );
   }
 
-  _onValueChange = async (selectedValue) => {
+  _onValueChange = async selectedValue => {
     this.setState({selectedValue});
     try {
       await AsyncStorage.setItem(STORAGE_KEY, selectedValue);
@@ -96,7 +85,7 @@ class BasicStorageExample extends React.Component<{}, $FlowFixMeState> {
     }
   };
 
-  _appendMessage = (message) => {
+  _appendMessage = message => {
     this.setState({messages: this.state.messages.concat(message)});
   };
 }
@@ -106,6 +95,8 @@ exports.description = 'Asynchronous local disk storage.';
 exports.examples = [
   {
     title: 'Basics - getItem, setItem, removeItem',
-    render(): React.Element<any> { return <BasicStorageExample />; }
+    render(): React.Element<any> {
+      return <BasicStorageExample />;
+    },
   },
 ];
diff --git a/RNTester/js/BorderExample.js b/RNTester/js/BorderExample.js
index 6f64581dfbda..388fc68fef49 100644
--- a/RNTester/js/BorderExample.js
+++ b/RNTester/js/BorderExample.js
@@ -4,15 +4,14 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  View
-} = ReactNative;
+var {StyleSheet, View} = ReactNative;
 
 var styles = StyleSheet.create({
   box: {
@@ -84,7 +83,7 @@ var styles = StyleSheet.create({
   border7_inner: {
     backgroundColor: 'blue',
     width: 100,
-    height: 100
+    height: 100,
   },
   border8: {
     width: 60,
@@ -158,46 +157,47 @@ var styles = StyleSheet.create({
     borderTopRightRadius: 40,
     borderBottomRightRadius: 30,
     borderBottomLeftRadius: 40,
-  }
+  },
 });
 
 exports.title = 'Border';
-exports.description = 'Demonstrates some of the border styles available to Views.';
+exports.description =
+  'Demonstrates some of the border styles available to Views.';
 exports.examples = [
   {
     title: 'Equal-Width / Same-Color',
     description: 'borderWidth & borderColor',
     render() {
       return <View style={[styles.box, styles.border1]} />;
-    }
+    },
   },
   {
     title: 'Equal-Width / Same-Color',
     description: 'borderWidth & borderColor & borderRadius',
     render() {
       return <View style={[styles.box, styles.borderRadius]} />;
-    }
+    },
   },
   {
     title: 'Equal-Width Borders',
     description: 'borderWidth & border*Color',
     render() {
       return <View style={[styles.box, styles.border2]} />;
-    }
+    },
   },
   {
     title: 'Same-Color Borders',
     description: 'border*Width & borderColor',
     render() {
       return <View style={[styles.box, styles.border3]} />;
-    }
+    },
   },
   {
     title: 'Custom Borders',
     description: 'border*Width & border*Color',
     render() {
       return <View style={[styles.box, styles.border4]} />;
-    }
+    },
   },
   {
     title: 'Custom Borders',
@@ -205,7 +205,7 @@ exports.examples = [
     platform: 'ios',
     render() {
       return <View style={[styles.box, styles.border5]} />;
-    }
+    },
   },
   {
     title: 'Custom Borders',
@@ -213,7 +213,7 @@ exports.examples = [
     platform: 'ios',
     render() {
       return <View style={[styles.box, styles.border6]} />;
-    }
+    },
   },
   {
     title: 'Custom Borders',
@@ -225,7 +225,7 @@ exports.examples = [
           <View style={styles.border7_inner} />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Single Borders',
@@ -239,14 +239,14 @@ exports.examples = [
           <View style={[styles.box, styles.border8, {borderRightWidth: 5}]} />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Corner Radii',
     description: 'borderTopLeftRadius & borderBottomRightRadius',
     render() {
       return <View style={[styles.box, styles.border9]} />;
-    }
+    },
   },
   {
     title: 'Corner Radii / Elevation',
@@ -254,34 +254,34 @@ exports.examples = [
     platform: 'android',
     render() {
       return <View style={[styles.box, styles.border10]} />;
-    }
+    },
   },
   {
     title: 'CSS Trick - Triangle',
     description: 'create a triangle by manipulating border colors and widths',
     render() {
       return <View style={[styles.border11]} />;
-    }
+    },
   },
   {
     title: 'Curved border(Left|Right|Bottom|Top)Width',
     description: 'Make a non-uniform width curved border',
     render() {
       return <View style={[styles.box, styles.border12]} />;
-    }
+    },
   },
   {
     title: 'Curved border(Left|Right|Bottom|Top)Color',
     description: 'Make a non-uniform color curved border',
     render() {
       return <View style={[styles.box, styles.border13]} />;
-    }
+    },
   },
   {
     title: 'Curved border(Top|Bottom)(Left|Right)Radius',
     description: 'Make a non-uniform radius curved border',
     render() {
       return <View style={[styles.box, styles.border14]} />;
-    }
-  }
+    },
+  },
 ];
diff --git a/RNTester/js/BoxShadowExample.js b/RNTester/js/BoxShadowExample.js
index 056b61aee33a..42fe0aaad5ae 100644
--- a/RNTester/js/BoxShadowExample.js
+++ b/RNTester/js/BoxShadowExample.js
@@ -4,16 +4,14 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Image,
-  StyleSheet,
-  View
-} = ReactNative;
+var {Image, StyleSheet, View} = ReactNative;
 
 var styles = StyleSheet.create({
   box: {
@@ -35,46 +33,72 @@ var styles = StyleSheet.create({
 });
 
 exports.title = 'Box Shadow';
-exports.description = 'Demonstrates some of the shadow styles available to Views.';
+exports.description =
+  'Demonstrates some of the shadow styles available to Views.';
 exports.examples = [
   {
     title: 'Basic shadow',
     description: 'shadowOpacity: 0.5, shadowOffset: {2, 2}',
     render() {
       return <View style={[styles.box, styles.shadow1]} />;
-    }
+    },
   },
   {
     title: 'Colored shadow',
-    description: 'shadowColor: \'red\', shadowRadius: 0',
+    description: "shadowColor: 'red', shadowRadius: 0",
     render() {
       return <View style={[styles.box, styles.shadow2]} />;
-    }
+    },
   },
   {
     title: 'Shaped shadow',
     description: 'borderRadius: 50',
     render() {
       return <View style={[styles.box, styles.shadow1, {borderRadius: 50}]} />;
-    }
+    },
   },
   {
     title: 'Image shadow',
     description: 'Image shadows are derived exactly from the pixels.',
     render() {
-      return <Image
-        source={require('./hawk.png')}
-        style={[styles.box, styles.shadow1, {borderWidth: 0, overflow: 'visible'}]}
-      />;
-    }
+      return (
+        <Image
+          source={require('./hawk.png')}
+          style={[
+            styles.box,
+            styles.shadow1,
+            {borderWidth: 0, overflow: 'visible'},
+          ]}
+        />
+      );
+    },
   },
   {
     title: 'Child shadow',
-    description: 'For views without an opaque background color, shadow will be derived from the subviews.',
+    description:
+      'For views without an opaque background color, shadow will be derived from the subviews.',
     render() {
-      return <View style={[styles.box, styles.shadow1, {backgroundColor: 'transparent'}]}>
-        <View style={[styles.box, {width: 80, height: 80, borderRadius: 40, margin: 8, backgroundColor: 'red'}]}/>
-      </View>;
-    }
+      return (
+        <View
+          style={[
+            styles.box,
+            styles.shadow1,
+            {backgroundColor: 'transparent'},
+          ]}>
+          <View
+            style={[
+              styles.box,
+              {
+                width: 80,
+                height: 80,
+                borderRadius: 40,
+                margin: 8,
+                backgroundColor: 'red',
+              },
+            ]}
+          />
+        </View>
+      );
+    },
   },
 ];
diff --git a/RNTester/js/ButtonExample.js b/RNTester/js/ButtonExample.js
index 8ba4876ed74e..1d7251986972 100644
--- a/RNTester/js/ButtonExample.js
+++ b/RNTester/js/ButtonExample.js
@@ -4,17 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  Alert,
-  Button,
-  View,
-} = ReactNative;
+const {Alert, Button, View} = ReactNative;
 
 const onButtonPress = () => {
   Alert.alert('Button has been pressed!');
@@ -28,7 +26,8 @@ exports.description = 'Simple React Native button component.';
 exports.examples = [
   {
     title: 'Simple Button',
-    description: 'The title and onPress handler are required. It is ' +
+    description:
+      'The title and onPress handler are required. It is ' +
       'recommended to set accessibilityLabel to help make your app usable by ' +
       'everyone.',
     render: function() {
@@ -43,7 +42,8 @@ exports.examples = [
   },
   {
     title: 'Adjusted color',
-    description: 'Adjusts the color in a way that looks standard on each ' +
+    description:
+      'Adjusts the color in a way that looks standard on each ' +
       'platform. On iOS, the color prop controls the color of the text. On ' +
       'Android, the color adjusts the background color of the button.',
     render: function() {
@@ -59,8 +59,8 @@ exports.examples = [
   },
   {
     title: 'Fit to text layout',
-    description: 'This layout strategy lets the title define the width of ' +
-      'the button',
+    description:
+      'This layout strategy lets the title define the width of ' + 'the button',
     render: function() {
       return (
         <View style={{flexDirection: 'row', justifyContent: 'space-between'}}>
diff --git a/RNTester/js/CameraRollView.js b/RNTester/js/CameraRollView.js
index 29eb070223a9..1568585ea89c 100644
--- a/RNTester/js/CameraRollView.js
+++ b/RNTester/js/CameraRollView.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -58,15 +60,10 @@ var propTypes = {
    */
   imagesPerRow: PropTypes.number,
 
-   /**
+  /**
    * The asset type, one of 'Photos', 'Videos' or 'All'
    */
-  assetType: PropTypes.oneOf([
-    'Photos',
-    'Videos',
-    'All',
-  ]),
-
+  assetType: PropTypes.oneOf(['Photos', 'Videos', 'All']),
 };
 
 var CameraRollView = createReactClass({
@@ -82,12 +79,7 @@ var CameraRollView = createReactClass({
       renderImage: function(asset) {
         var imageSize = 150;
         var imageStyle = [styles.image, {width: imageSize, height: imageSize}];
-        return (
-          <Image
-            source={asset.node.image}
-            style={imageStyle}
-          />
-        );
+        return <Image source={asset.node.image} style={imageStyle} />;
       },
     };
   },
@@ -98,7 +90,7 @@ var CameraRollView = createReactClass({
     return {
       assets: ([]: Array<Image>),
       groupTypes: this.props.groupTypes,
-      lastCursor: (null : ?string),
+      lastCursor: (null: ?string),
       assetType: this.props.assetType,
       noMore: false,
       loadingMore: false,
@@ -114,7 +106,7 @@ var CameraRollView = createReactClass({
     var ds = new ListView.DataSource({rowHasChanged: this._rowHasChanged});
     this.state.dataSource = ds.cloneWithRows(
       // $FlowFixMe(>=0.41.0)
-      groupByEveryN(this.state.assets, this.props.imagesPerRow)
+      groupByEveryN(this.state.assets, this.props.imagesPerRow),
     );
   },
 
@@ -178,7 +170,9 @@ var CameraRollView = createReactClass({
    */
   fetch: function(clear?: boolean) {
     if (!this.state.loadingMore) {
-      this.setState({loadingMore: true}, () => { this._fetch(clear); });
+      this.setState({loadingMore: true}, () => {
+        this._fetch(clear);
+      });
     }
   },
 
@@ -217,8 +211,12 @@ var CameraRollView = createReactClass({
   },
 
   // rowData is an array of images
-  _renderRow: function(rowData: Array<Image>, sectionID: string, rowID: string)  {
-    var images = rowData.map((image) => {
+  _renderRow: function(
+    rowData: Array<Image>,
+    sectionID: string,
+    rowID: string,
+  ) {
+    var images = rowData.map(image => {
       if (image === null) {
         return null;
       }
@@ -226,16 +224,12 @@ var CameraRollView = createReactClass({
       return this.props.renderImage(image);
     });
 
-    return (
-      <View style={styles.row}>
-        {images}
-      </View>
-    );
+    return <View style={styles.row}>{images}</View>;
   },
 
   _appendAssets: function(data: Object) {
     var assets = data.edges;
-    var newState: Object = { loadingMore: false };
+    var newState: Object = {loadingMore: false};
 
     if (!data.page_info.has_next_page) {
       newState.noMore = true;
@@ -246,7 +240,7 @@ var CameraRollView = createReactClass({
       newState.assets = this.state.assets.concat(assets);
       newState.dataSource = this.state.dataSource.cloneWithRows(
         // $FlowFixMe(>=0.41.0)
-        groupByEveryN(newState.assets, this.props.imagesPerRow)
+        groupByEveryN(newState.assets, this.props.imagesPerRow),
       );
     }
 
diff --git a/RNTester/js/ClipboardExample.js b/RNTester/js/ClipboardExample.js
index 57ee1e172e73..13309df37493 100644
--- a/RNTester/js/ClipboardExample.js
+++ b/RNTester/js/ClipboardExample.js
@@ -4,21 +4,19 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Clipboard,
-  View,
-  Text,
-} = ReactNative;
+var {Clipboard, View, Text} = ReactNative;
 
 class ClipboardExample extends React.Component<{}, $FlowFixMeState> {
   state = {
-    content: 'Content will appear here'
+    content: 'Content will appear here',
   };
 
   _setClipboardContent = async () => {
@@ -27,7 +25,7 @@ class ClipboardExample extends React.Component<{}, $FlowFixMeState> {
       var content = await Clipboard.getString();
       this.setState({content});
     } catch (e) {
-      this.setState({content:e.message});
+      this.setState({content: e.message});
     }
   };
 
@@ -37,9 +35,7 @@ class ClipboardExample extends React.Component<{}, $FlowFixMeState> {
         <Text onPress={this._setClipboardContent} style={{color: 'blue'}}>
           Tap to put "Hello World" in the clipboard
         </Text>
-        <Text style={{color: 'red', marginTop: 20}}>
-          {this.state.content}
-        </Text>
+        <Text style={{color: 'red', marginTop: 20}}>{this.state.content}</Text>
       </View>
     );
   }
@@ -51,7 +47,7 @@ exports.examples = [
   {
     title: 'Clipboard.setString() and getString()',
     render() {
-      return <ClipboardExample/>;
-    }
-  }
+      return <ClipboardExample />;
+    },
+  },
 ];
diff --git a/RNTester/js/DatePickerAndroidExample.js b/RNTester/js/DatePickerAndroidExample.js
index 2b6706e06be5..fc63ca20e6b1 100644
--- a/RNTester/js/DatePickerAndroidExample.js
+++ b/RNTester/js/DatePickerAndroidExample.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
@@ -62,31 +64,44 @@ class DatePickerAndroidExample extends React.Component {
       <RNTesterPage title="DatePickerAndroid">
         <RNTesterBlock title="Simple date picker">
           <TouchableWithoutFeedback
-            onPress={this.showPicker.bind(this, 'simple', {date: this.state.simpleDate})}>
+            onPress={this.showPicker.bind(this, 'simple', {
+              date: this.state.simpleDate,
+            })}>
             <Text style={styles.text}>{this.state.simpleText}</Text>
           </TouchableWithoutFeedback>
         </RNTesterBlock>
         <RNTesterBlock title="Simple spinner date picker">
           <TouchableWithoutFeedback
-            onPress={this.showPicker.bind(this, 'spinner', {date: this.state.spinnerDate, mode: 'spinner'})}>
+            onPress={this.showPicker.bind(this, 'spinner', {
+              date: this.state.spinnerDate,
+              mode: 'spinner',
+            })}>
             <Text style={styles.text}>{this.state.spinnerText}</Text>
           </TouchableWithoutFeedback>
         </RNTesterBlock>
         <RNTesterBlock title="Simple calendar date picker">
           <TouchableWithoutFeedback
-            onPress={this.showPicker.bind(this, 'calendar', {date: this.state.calendarDate, mode: 'calendar'})}>
+            onPress={this.showPicker.bind(this, 'calendar', {
+              date: this.state.calendarDate,
+              mode: 'calendar',
+            })}>
             <Text style={styles.text}>{this.state.calendarText}</Text>
           </TouchableWithoutFeedback>
         </RNTesterBlock>
         <RNTesterBlock title="Simple default date picker">
           <TouchableWithoutFeedback
-            onPress={this.showPicker.bind(this, 'default', {date: this.state.defaultDate, mode: 'default'})}>
+            onPress={this.showPicker.bind(this, 'default', {
+              date: this.state.defaultDate,
+              mode: 'default',
+            })}>
             <Text style={styles.text}>{this.state.defaultText}</Text>
           </TouchableWithoutFeedback>
         </RNTesterBlock>
         <RNTesterBlock title="Date picker with pre-set date">
           <TouchableWithoutFeedback
-            onPress={this.showPicker.bind(this, 'preset', {date: this.state.presetDate})}>
+            onPress={this.showPicker.bind(this, 'preset', {
+              date: this.state.presetDate,
+            })}>
             <Text style={styles.text}>{this.state.presetText}</Text>
           </TouchableWithoutFeedback>
         </RNTesterBlock>
@@ -117,7 +132,7 @@ class DatePickerAndroidExample extends React.Component {
             })}>
             <Text style={styles.text}>{this.state.allText}</Text>
           </TouchableWithoutFeedback>
-          </RNTesterBlock>
+        </RNTesterBlock>
       </RNTesterPage>
     );
   }
diff --git a/RNTester/js/DatePickerIOSExample.js b/RNTester/js/DatePickerIOSExample.js
index a0b6234e8225..5bd76259742e 100644
--- a/RNTester/js/DatePickerIOSExample.js
+++ b/RNTester/js/DatePickerIOSExample.js
@@ -4,24 +4,23 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  DatePickerIOS,
-  StyleSheet,
-  Text,
-  TextInput,
-  View,
-} = ReactNative;
+var {DatePickerIOS, StyleSheet, Text, TextInput, View} = ReactNative;
 
-class DatePickerExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class DatePickerExample extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   static defaultProps = {
     date: new Date(),
-    timeZoneOffsetInHours: (-1) * (new Date()).getTimezoneOffset() / 60,
+    timeZoneOffsetInHours: -1 * new Date().getTimezoneOffset() / 60,
   };
 
   state = {
@@ -29,11 +28,11 @@ class DatePickerExample extends React.Component<$FlowFixMeProps, $FlowFixMeState
     timeZoneOffsetInHours: this.props.timeZoneOffsetInHours,
   };
 
-  onDateChange = (date) => {
+  onDateChange = date => {
     this.setState({date: date});
   };
 
-  onTimezoneChange = (event) => {
+  onTimezoneChange = event => {
     var offset = parseInt(event.nativeEvent.text, 10);
     if (isNaN(offset)) {
       return;
@@ -47,11 +46,11 @@ class DatePickerExample extends React.Component<$FlowFixMeProps, $FlowFixMeState
     return (
       <View>
         <WithLabel label="Value:">
-          <Text>{
-            this.state.date.toLocaleDateString() +
-            ' ' +
-            this.state.date.toLocaleTimeString()
-          }</Text>
+          <Text>
+            {this.state.date.toLocaleDateString() +
+              ' ' +
+              this.state.date.toLocaleTimeString()}
+          </Text>
         </WithLabel>
         <WithLabel label="Timezone:">
           <TextInput
@@ -93,9 +92,7 @@ class WithLabel extends React.Component<$FlowFixMeProps> {
     return (
       <View style={styles.labelContainer}>
         <View style={styles.labelView}>
-          <Text style={styles.label}>
-            {this.props.label}
-          </Text>
+          <Text style={styles.label}>{this.props.label}</Text>
         </View>
         {this.props.children}
       </View>
@@ -107,9 +104,7 @@ class Heading extends React.Component<$FlowFixMeProps> {
   render() {
     return (
       <View style={styles.headingContainer}>
-        <Text style={styles.heading}>
-          {this.props.label}
-        </Text>
+        <Text style={styles.heading}>{this.props.label}</Text>
       </View>
     );
   }
@@ -119,12 +114,13 @@ exports.displayName = (undefined: ?string);
 exports.title = '<DatePickerIOS>';
 exports.description = 'Select dates and times using the native UIDatePicker.';
 exports.examples = [
-{
-  title: '<DatePickerIOS>',
-  render: function(): React.Element<any> {
-    return <DatePickerExample />;
+  {
+    title: '<DatePickerIOS>',
+    render: function(): React.Element<any> {
+      return <DatePickerExample />;
+    },
   },
-}];
+];
 
 var styles = StyleSheet.create({
   textinput: {
diff --git a/RNTester/js/DimensionsExample.js b/RNTester/js/DimensionsExample.js
index d0274f15a185..436968c3b34a 100644
--- a/RNTester/js/DimensionsExample.js
+++ b/RNTester/js/DimensionsExample.js
@@ -4,19 +4,20 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  Dimensions,
-  Text,
-  View
-} = ReactNative;
+const {Dimensions, Text, View} = ReactNative;
 
-class DimensionsSubscription extends React.Component<{dim: string}, {dims: Object}> {
+class DimensionsSubscription extends React.Component<
+  {dim: string},
+  {dims: Object},
+> {
   state = {
     dims: Dimensions.get(this.props.dim),
   };
@@ -29,7 +30,7 @@ class DimensionsSubscription extends React.Component<{dim: string}, {dims: Objec
     Dimensions.removeEventListener('change', this._handleDimensionsChange);
   }
 
-  _handleDimensionsChange = (dimensions) => {
+  _handleDimensionsChange = dimensions => {
     this.setState({
       dims: dimensions[this.props.dim],
     });
@@ -49,10 +50,14 @@ exports.description = 'Dimensions of the viewport';
 exports.examples = [
   {
     title: 'window',
-    render(): React.Element<any> { return <DimensionsSubscription dim="window" />; }
+    render(): React.Element<any> {
+      return <DimensionsSubscription dim="window" />;
+    },
   },
   {
     title: 'screen',
-    render(): React.Element<any> { return <DimensionsSubscription dim="screen" />; }
+    render(): React.Element<any> {
+      return <DimensionsSubscription dim="screen" />;
+    },
   },
 ];
diff --git a/RNTester/js/ExampleTypes.js b/RNTester/js/ExampleTypes.js
index 4e42bf4cf3da..5d7e2a55795a 100644
--- a/RNTester/js/ExampleTypes.js
+++ b/RNTester/js/ExampleTypes.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This comment
diff --git a/RNTester/js/FlatListExample.js b/RNTester/js/FlatListExample.js
index 0c47ebc69f68..4098934dc0b6 100644
--- a/RNTester/js/FlatListExample.js
+++ b/RNTester/js/FlatListExample.js
@@ -4,19 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Alert = require('Alert');
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  Animated,
-  FlatList,
-  StyleSheet,
-  View,
-} = ReactNative;
+const {Animated, FlatList, StyleSheet, View} = ReactNative;
 
 const RNTesterPage = require('./RNTesterPage');
 
@@ -61,21 +58,23 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
     empty: false,
   };
 
-  _onChangeFilterText = (filterText) => {
+  _onChangeFilterText = filterText => {
     this.setState({filterText});
   };
 
-  _onChangeScrollToIndex = (text) => {
-    this._listRef.getNode().scrollToIndex({viewPosition: 0.5, index: Number(text)});
+  _onChangeScrollToIndex = text => {
+    this._listRef
+      .getNode()
+      .scrollToIndex({viewPosition: 0.5, index: Number(text)});
   };
 
   _scrollPos = new Animated.Value(0);
   _scrollSinkX = Animated.event(
-    [{nativeEvent: { contentOffset: { x: this._scrollPos } }}],
+    [{nativeEvent: {contentOffset: {x: this._scrollPos}}}],
     {useNativeDriver: true},
   );
   _scrollSinkY = Animated.event(
-    [{nativeEvent: { contentOffset: { y: this._scrollPos } }}],
+    [{nativeEvent: {contentOffset: {y: this._scrollPos}}}],
     {useNativeDriver: true},
   );
 
@@ -85,14 +84,11 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
 
   render() {
     const filterRegex = new RegExp(String(this.state.filterText), 'i');
-    const filter = (item) => (
-      filterRegex.test(item.text) || filterRegex.test(item.title)
-    );
+    const filter = item =>
+      filterRegex.test(item.text) || filterRegex.test(item.title);
     const filteredData = this.state.data.filter(filter);
     return (
-      <RNTesterPage
-        noSpacer={true}
-        noScroll={true}>
+      <RNTesterPage noSpacer={true} noScroll={true}>
         <View style={styles.container}>
           <View style={styles.searchRow}>
             <View style={styles.options}>
@@ -126,13 +122,13 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
             data={this.state.empty ? [] : filteredData}
             debug={this.state.debug}
             disableVirtualization={!this.state.virtualized}
-            getItemLayout={this.state.fixedHeight ?
-              this._getItemLayout :
-              undefined
+            getItemLayout={
+              this.state.fixedHeight ? this._getItemLayout : undefined
             }
             horizontal={this.state.horizontal}
             inverted={this.state.inverted}
-            key={(this.state.horizontal ? 'h' : 'v') +
+            key={
+              (this.state.horizontal ? 'h' : 'v') +
               (this.state.fixedHeight ? 'f' : 'd')
             }
             keyboardShouldPersistTaps="always"
@@ -141,7 +137,9 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
             numColumns={1}
             onEndReached={this._onEndReached}
             onRefresh={this._onRefresh}
-            onScroll={this.state.horizontal ? this._scrollSinkX : this._scrollSinkY}
+            onScroll={
+              this.state.horizontal ? this._scrollSinkX : this._scrollSinkY
+            }
             onViewableItemsChanged={this._onViewableItemsChanged}
             ref={this._captureRef}
             refreshing={false}
@@ -153,7 +151,9 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
       </RNTesterPage>
     );
   }
-  _captureRef = (ref) => { this._listRef = ref; };
+  _captureRef = ref => {
+    this._listRef = ref;
+  };
   _getItemLayout = (data: any, index: number) => {
     return getItemLayout(data, index, this.state.horizontal);
   };
@@ -161,7 +161,7 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
     if (this.state.data.length >= 1000) {
       return;
     }
-    this.setState((state) => ({
+    this.setState(state => ({
       data: state.data.concat(genItemData(100, state.data.length)),
     }));
   };
@@ -181,20 +181,19 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
   // This is called when items change viewability by scrolling into or out of
   // the viewable area.
   _onViewableItemsChanged = (info: {
-      changed: Array<{
-        key: string,
-        isViewable: boolean,
-        item: any,
-        index: ?number,
-        section?: any,
-      }>
-    }
-  ) => {
+    changed: Array<{
+      key: string,
+      isViewable: boolean,
+      item: any,
+      index: ?number,
+      section?: any,
+    }>,
+  }) => {
     // Impressions can be logged here
     if (this.state.logViewable) {
       infoLog(
         'onViewableItemsChanged: ',
-        info.changed.map((v) => ({...v, item: '...'})),
+        info.changed.map(v => ({...v, item: '...'})),
       );
     }
   };
@@ -205,7 +204,6 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
   _listRef: AnimatedFlatList;
 }
 
-
 const styles = StyleSheet.create({
   container: {
     backgroundColor: 'rgb(239, 239, 244)',
diff --git a/RNTester/js/GeolocationExample.js b/RNTester/js/GeolocationExample.js
index 2cbd091f50f5..73b5deeed929 100644
--- a/RNTester/js/GeolocationExample.js
+++ b/RNTester/js/GeolocationExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
-'use strict';
 
+'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, View} = ReactNative;
 
 exports.framework = 'React';
 exports.title = 'Geolocation';
@@ -27,7 +24,7 @@ exports.examples = [
     render: function(): React.Element<any> {
       return <GeolocationExample />;
     },
-  }
+  },
 ];
 
 class GeolocationExample extends React.Component<{}, $FlowFixMeState> {
@@ -40,14 +37,14 @@ class GeolocationExample extends React.Component<{}, $FlowFixMeState> {
 
   componentDidMount() {
     navigator.geolocation.getCurrentPosition(
-      (position) => {
+      position => {
         var initialPosition = JSON.stringify(position);
         this.setState({initialPosition});
       },
-      (error) => alert(JSON.stringify(error)),
-      {enableHighAccuracy: true, timeout: 20000, maximumAge: 1000}
+      error => alert(JSON.stringify(error)),
+      {enableHighAccuracy: true, timeout: 20000, maximumAge: 1000},
     );
-    this.watchID = navigator.geolocation.watchPosition((position) => {
+    this.watchID = navigator.geolocation.watchPosition(position => {
       var lastPosition = JSON.stringify(position);
       this.setState({lastPosition});
     });
diff --git a/RNTester/js/ImageCapInsetsExample.js b/RNTester/js/ImageCapInsetsExample.js
index 97b407f08e11..8f84d77358cf 100644
--- a/RNTester/js/ImageCapInsetsExample.js
+++ b/RNTester/js/ImageCapInsetsExample.js
@@ -4,34 +4,29 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
 
 var nativeImageSource = require('nativeImageSource');
-var {
-  Image,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Image, StyleSheet, Text, View} = ReactNative;
 
 class ImageCapInsetsExample extends React.Component<{}> {
   render() {
     return (
       <View>
         <View style={styles.background}>
-          <Text>
-            capInsets: none
-          </Text>
+          <Text>capInsets: none</Text>
           <Image
             source={nativeImageSource({
               ios: 'story-background',
               width: 60,
-              height: 60
+              height: 60,
             })}
             style={styles.storyBackground}
             resizeMode={Image.resizeMode.stretch}
@@ -39,14 +34,12 @@ class ImageCapInsetsExample extends React.Component<{}> {
           />
         </View>
         <View style={[styles.background, {paddingTop: 10}]}>
-          <Text>
-            capInsets: 15
-          </Text>
+          <Text>capInsets: 15</Text>
           <Image
             source={nativeImageSource({
               ios: 'story-background',
               width: 60,
-              height: 60
+              height: 60,
             })}
             style={styles.storyBackground}
             resizeMode={Image.resizeMode.stretch}
@@ -74,7 +67,7 @@ var styles = StyleSheet.create({
   },
   text: {
     fontSize: 13.5,
-  }
+  },
 });
 
 module.exports = ImageCapInsetsExample;
diff --git a/RNTester/js/ImageEditingExample.js b/RNTester/js/ImageEditingExample.js
index 76bf871273a4..048869c26861 100644
--- a/RNTester/js/ImageEditingExample.js
+++ b/RNTester/js/ImageEditingExample.js
@@ -4,5 +4,6 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
diff --git a/RNTester/js/ImageExample.js b/RNTester/js/ImageExample.js
index 65c6380509b2..280146395432 100644
--- a/RNTester/js/ImageExample.js
+++ b/RNTester/js/ImageExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -21,10 +23,12 @@ var {
   ImageBackground,
 } = ReactNative;
 
-var base64Icon = 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEsAAABLCAQAAACSR7JhAAADtUlEQVR4Ac3YA2Bj6QLH0XPT1Fzbtm29tW3btm3bfLZtv7e2ObZnms7d8Uw098tuetPzrxv8wiISrtVudrG2JXQZ4VOv+qUfmqCGGl1mqLhoA52oZlb0mrjsnhKpgeUNEs91Z0pd1kvihA3ULGVHiQO2narKSHKkEMulm9VgUyE60s1aWoMQUbpZOWE+kaqs4eLEjdIlZTcFZB0ndc1+lhB1lZrIuk5P2aib1NBpZaL+JaOGIt0ls47SKzLC7CqrlGF6RZ09HGoNy1lYl2aRSWL5GuzqWU1KafRdoRp0iOQEiDzgZPnG6DbldcomadViflnl/cL93tOoVbsOLVM2jylvdWjXolWX1hmfZbGR/wjypDjFLSZIRov09BgYmtUqPQPlQrPapecLgTIy0jMgPKtTeob2zWtrGH3xvjUkPCtNg/tm1rjwrMa+mdUkPd3hWbH0jArPGiU9ufCsNNWFZ40wpwn+62/66R2RUtoso1OB34tnLOcy7YB1fUdc9e0q3yru8PGM773vXsuZ5YIZX+5xmHwHGVvlrGPN6ZSiP1smOsMMde40wKv2VmwPPVXNut4sVpUreZiLBHi0qln/VQeI/LTMYXpsJtFiclUN+5HVZazim+Ky+7sAvxWnvjXrJFneVtLWLyPJu9K3cXLWeOlbMTlrIelbMDlrLenrjEQOtIF+fuI9xRp9ZBFp6+b6WT8RrxEpdK64BuvHgDk+vUy+b5hYk6zfyfs051gRoNO1usU12WWRWL73/MMEy9pMi9qIrR4ZpV16Rrvduxazmy1FSvuFXRkqTnE7m2kdb5U8xGjLw/spRr1uTov4uOgQE+0N/DvFrG/Jt7i/FzwxbA9kDanhf2w+t4V97G8lrT7wc08aA2QNUkuTfW/KimT01wdlfK4yEw030VfT0RtZbzjeMprNq8m8tnSTASrTLti64oBNdpmMQm0eEwvfPwRbUBywG5TzjPCsdwk3IeAXjQblLCoXnDVeoAz6SfJNk5TTzytCNZk/POtTSV40NwOFWzw86wNJRpubpXsn60NJFlHeqlYRbslqZm2jnEZ3qcSKgm0kTli3zZVS7y/iivZTweYXJ26Y+RTbV1zh3hYkgyFGSTKPfRVbRqWWVReaxYeSLarYv1Qqsmh1s95S7G+eEWK0f3jYKTbV6bOwepjfhtafsvUsqrQvrGC8YhmnO9cSCk3yuY984F1vesdHYhWJ5FvASlacshUsajFt2mUM9pqzvKGcyNJW0arTKN1GGGzQlH0tXwLDgQTurS8eIQAAAABJRU5ErkJggg==';
+var base64Icon =
+  'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEsAAABLCAQAAACSR7JhAAADtUlEQVR4Ac3YA2Bj6QLH0XPT1Fzbtm29tW3btm3bfLZtv7e2ObZnms7d8Uw098tuetPzrxv8wiISrtVudrG2JXQZ4VOv+qUfmqCGGl1mqLhoA52oZlb0mrjsnhKpgeUNEs91Z0pd1kvihA3ULGVHiQO2narKSHKkEMulm9VgUyE60s1aWoMQUbpZOWE+kaqs4eLEjdIlZTcFZB0ndc1+lhB1lZrIuk5P2aib1NBpZaL+JaOGIt0ls47SKzLC7CqrlGF6RZ09HGoNy1lYl2aRSWL5GuzqWU1KafRdoRp0iOQEiDzgZPnG6DbldcomadViflnl/cL93tOoVbsOLVM2jylvdWjXolWX1hmfZbGR/wjypDjFLSZIRov09BgYmtUqPQPlQrPapecLgTIy0jMgPKtTeob2zWtrGH3xvjUkPCtNg/tm1rjwrMa+mdUkPd3hWbH0jArPGiU9ufCsNNWFZ40wpwn+62/66R2RUtoso1OB34tnLOcy7YB1fUdc9e0q3yru8PGM773vXsuZ5YIZX+5xmHwHGVvlrGPN6ZSiP1smOsMMde40wKv2VmwPPVXNut4sVpUreZiLBHi0qln/VQeI/LTMYXpsJtFiclUN+5HVZazim+Ky+7sAvxWnvjXrJFneVtLWLyPJu9K3cXLWeOlbMTlrIelbMDlrLenrjEQOtIF+fuI9xRp9ZBFp6+b6WT8RrxEpdK64BuvHgDk+vUy+b5hYk6zfyfs051gRoNO1usU12WWRWL73/MMEy9pMi9qIrR4ZpV16Rrvduxazmy1FSvuFXRkqTnE7m2kdb5U8xGjLw/spRr1uTov4uOgQE+0N/DvFrG/Jt7i/FzwxbA9kDanhf2w+t4V97G8lrT7wc08aA2QNUkuTfW/KimT01wdlfK4yEw030VfT0RtZbzjeMprNq8m8tnSTASrTLti64oBNdpmMQm0eEwvfPwRbUBywG5TzjPCsdwk3IeAXjQblLCoXnDVeoAz6SfJNk5TTzytCNZk/POtTSV40NwOFWzw86wNJRpubpXsn60NJFlHeqlYRbslqZm2jnEZ3qcSKgm0kTli3zZVS7y/iivZTweYXJ26Y+RTbV1zh3hYkgyFGSTKPfRVbRqWWVReaxYeSLarYv1Qqsmh1s95S7G+eEWK0f3jYKTbV6bOwepjfhtafsvUsqrQvrGC8YhmnO9cSCk3yuY984F1vesdHYhWJ5FvASlacshUsajFt2mUM9pqzvKGcyNJW0arTKN1GGGzQlH0tXwLDgQTurS8eIQAAAABJRU5ErkJggg==';
 
 var ImageCapInsetsExample = require('./ImageCapInsetsExample');
-const IMAGE_PREFETCH_URL = 'http://origami.design/public/images/bird-logo.png?r=1&t=' + Date.now();
+const IMAGE_PREFETCH_URL =
+  'http://origami.design/public/images/bird-logo.png?r=1&t=' + Date.now();
 var prefetchTask = Image.prefetch(IMAGE_PREFETCH_URL);
 
 /* $FlowFixMe(>=0.63.0 site=react_native_fb) This comment suppresses an error
@@ -45,19 +49,23 @@ var NetworkImageCallbackExample = createReactClass({
   },
 
   render: function() {
-    var { mountTime } = this.state;
+    var {mountTime} = this.state;
 
     return (
       <View>
         <Image
           source={this.props.source}
           style={[styles.base, {overflow: 'visible'}]}
-          onLoadStart={() => this._loadEventFired(`✔ onLoadStart (+${new Date() - mountTime}ms)`)}
-          onLoad={(event) => {
+          onLoadStart={() =>
+            this._loadEventFired(`✔ onLoadStart (+${new Date() - mountTime}ms)`)
+          }
+          onLoad={event => {
             // Currently this image source feature is only available on iOS.
             if (event.nativeEvent.source) {
               const url = event.nativeEvent.source.url;
-              this._loadEventFired(`✔ onLoad (+${new Date() - mountTime}ms) for URL ${url}`);
+              this._loadEventFired(
+                `✔ onLoad (+${new Date() - mountTime}ms) for URL ${url}`,
+              );
             } else {
               this._loadEventFired(`✔ onLoad (+${new Date() - mountTime}ms)`);
             }
@@ -65,43 +73,61 @@ var NetworkImageCallbackExample = createReactClass({
           onLoadEnd={() => {
             this._loadEventFired(`✔ onLoadEnd (+${new Date() - mountTime}ms)`);
             this.setState({startLoadPrefetched: true}, () => {
-              prefetchTask.then(() => {
-                this._loadEventFired(`✔ Prefetch OK (+${new Date() - mountTime}ms)`);
-              }, error => {
-                this._loadEventFired(`✘ Prefetch failed (+${new Date() - mountTime}ms)`);
-              });
+              prefetchTask.then(
+                () => {
+                  this._loadEventFired(
+                    `✔ Prefetch OK (+${new Date() - mountTime}ms)`,
+                  );
+                },
+                error => {
+                  this._loadEventFired(
+                    `✘ Prefetch failed (+${new Date() - mountTime}ms)`,
+                  );
+                },
+              );
             });
           }}
         />
-        {this.state.startLoadPrefetched ?
+        {this.state.startLoadPrefetched ? (
           <Image
             source={this.props.prefetchedSource}
             style={[styles.base, {overflow: 'visible'}]}
-            onLoadStart={() => this._loadEventFired(`✔ (prefetched) onLoadStart (+${new Date() - mountTime}ms)`)}
-            onLoad={(event) => {
+            onLoadStart={() =>
+              this._loadEventFired(
+                `✔ (prefetched) onLoadStart (+${new Date() - mountTime}ms)`,
+              )
+            }
+            onLoad={event => {
               // Currently this image source feature is only available on iOS.
               if (event.nativeEvent.source) {
                 const url = event.nativeEvent.source.url;
-                this._loadEventFired(`✔ (prefetched) onLoad (+${new Date() - mountTime}ms) for URL ${url}`);
+                this._loadEventFired(
+                  `✔ (prefetched) onLoad (+${new Date() -
+                    mountTime}ms) for URL ${url}`,
+                );
               } else {
-                this._loadEventFired(`✔ (prefetched) onLoad (+${new Date() - mountTime}ms)`);
+                this._loadEventFired(
+                  `✔ (prefetched) onLoad (+${new Date() - mountTime}ms)`,
+                );
               }
             }}
-            onLoadEnd={() => this._loadEventFired(`✔ (prefetched) onLoadEnd (+${new Date() - mountTime}ms)`)}
+            onLoadEnd={() =>
+              this._loadEventFired(
+                `✔ (prefetched) onLoadEnd (+${new Date() - mountTime}ms)`,
+              )
+            }
           />
-          : null}
-        <Text style={{marginTop: 20}}>
-          {this.state.events.join('\n')}
-        </Text>
+        ) : null}
+        <Text style={{marginTop: 20}}>{this.state.events.join('\n')}</Text>
       </View>
     );
   },
 
   _loadEventFired(event) {
-    this.setState((state) => {
-      return state.events = [...state.events, event];
+    this.setState(state => {
+      return (state.events = [...state.events, event]);
     });
-  }
+  },
 });
 
 var NetworkImageExample = createReactClass({
@@ -109,27 +135,38 @@ var NetworkImageExample = createReactClass({
     return {
       error: false,
       loading: false,
-      progress: 0
+      progress: 0,
     };
   },
   render: function() {
-    var loader = this.state.loading ?
+    var loader = this.state.loading ? (
       <View style={styles.progress}>
         <Text>{this.state.progress}%</Text>
-        <ActivityIndicator style={{marginLeft:5}} />
-      </View> : null;
-    return this.state.error ?
-      <Text>{this.state.error}</Text> :
+        <ActivityIndicator style={{marginLeft: 5}} />
+      </View>
+    ) : null;
+    return this.state.error ? (
+      <Text>{this.state.error}</Text>
+    ) : (
       <ImageBackground
         source={this.props.source}
         style={[styles.base, {overflow: 'visible'}]}
-        onLoadStart={(e) => this.setState({loading: true})}
-        onError={(e) => this.setState({error: e.nativeEvent.error, loading: false})}
-        onProgress={(e) => this.setState({progress: Math.round(100 * e.nativeEvent.loaded / e.nativeEvent.total)})}
+        onLoadStart={e => this.setState({loading: true})}
+        onError={e =>
+          this.setState({error: e.nativeEvent.error, loading: false})
+        }
+        onProgress={e =>
+          this.setState({
+            progress: Math.round(
+              100 * e.nativeEvent.loaded / e.nativeEvent.total,
+            ),
+          })
+        }
         onLoad={() => this.setState({loading: false, error: false})}>
         {loader}
-      </ImageBackground>;
-  }
+      </ImageBackground>
+    );
+  },
 });
 
 var ImageSizeExample = createReactClass({
@@ -154,7 +191,8 @@ var ImageSizeExample = createReactClass({
             backgroundColor: 'transparent',
             marginRight: 10,
           }}
-          source={this.props.source} />
+          source={this.props.source}
+        />
         <Text>
           Actual dimensions:{'\n'}
           Width: {this.state.width}, Height: {this.state.height}
@@ -175,26 +213,36 @@ var MultipleSourcesExample = createReactClass({
     return (
       <View>
         <View style={{flexDirection: 'row', justifyContent: 'space-between'}}>
-          <Text
-            style={styles.touchableText}
-            onPress={this.decreaseImageSize} >
+          <Text style={styles.touchableText} onPress={this.decreaseImageSize}>
             Decrease image size
           </Text>
-          <Text
-            style={styles.touchableText}
-            onPress={this.increaseImageSize} >
+          <Text style={styles.touchableText} onPress={this.increaseImageSize}>
             Increase image size
           </Text>
         </View>
-        <Text>Container image size: {this.state.width}x{this.state.height} </Text>
-        <View
-          style={{height: this.state.height, width: this.state.width}} >
+        <Text>
+          Container image size: {this.state.width}x{this.state.height}{' '}
+        </Text>
+        <View style={{height: this.state.height, width: this.state.width}}>
           <Image
             style={{flex: 1}}
             source={[
-              {uri: 'https://facebook.github.io/react-native/img/favicon.png', width: 38, height: 38},
-              {uri: 'https://facebook.github.io/react-native/img/favicon.png', width: 76, height: 76},
-              {uri: 'https://facebook.github.io/react-native/img/opengraph.png', width: 400, height: 400}
+              {
+                uri: 'https://facebook.github.io/react-native/img/favicon.png',
+                width: 38,
+                height: 38,
+              },
+              {
+                uri: 'https://facebook.github.io/react-native/img/favicon.png',
+                width: 76,
+                height: 76,
+              },
+              {
+                uri:
+                  'https://facebook.github.io/react-native/img/opengraph.png',
+                width: 400,
+                height: 400,
+              },
             ]}
           />
         </View>
@@ -224,33 +272,43 @@ var MultipleSourcesExample = createReactClass({
 exports.displayName = (undefined: ?string);
 exports.framework = 'React';
 exports.title = '<Image>';
-exports.description = 'Base component for displaying different types of images.';
+exports.description =
+  'Base component for displaying different types of images.';
 
 exports.examples = [
   {
     title: 'Plain Network Image',
-    description: 'If the `source` prop `uri` property is prefixed with ' +
-    '"http", then it will be downloaded from the network.',
+    description:
+      'If the `source` prop `uri` property is prefixed with ' +
+      '"http", then it will be downloaded from the network.',
     render: function() {
-      return (
-        <Image
-          source={fullImage}
-          style={styles.base}
-        />
-      );
+      return <Image source={fullImage} style={styles.base} />;
     },
   },
   {
     title: 'Plain Static Image',
-    description: 'Static assets should be placed in the source code tree, and ' +
-    'required in the same way as JavaScript modules.',
+    description:
+      'Static assets should be placed in the source code tree, and ' +
+      'required in the same way as JavaScript modules.',
     render: function() {
       return (
         <View style={styles.horizontal}>
-          <Image source={require('./uie_thumb_normal.png')} style={styles.icon} />
-          <Image source={require('./uie_thumb_selected.png')} style={styles.icon} />
-          <Image source={require('./uie_comment_normal.png')} style={styles.icon} />
-          <Image source={require('./uie_comment_highlighted.png')} style={styles.icon} />
+          <Image
+            source={require('./uie_thumb_normal.png')}
+            style={styles.icon}
+          />
+          <Image
+            source={require('./uie_thumb_selected.png')}
+            style={styles.icon}
+          />
+          <Image
+            source={require('./uie_comment_normal.png')}
+            style={styles.icon}
+          />
+          <Image
+            source={require('./uie_comment_highlighted.png')}
+            style={styles.icon}
+          />
         </View>
       );
     },
@@ -259,8 +317,14 @@ exports.examples = [
     title: 'Image Loading Events',
     render: function() {
       return (
-        <NetworkImageCallbackExample source={{uri: 'http://origami.design/public/images/bird-logo.png?r=1&t=' + Date.now()}}
-          prefetchedSource={{uri: IMAGE_PREFETCH_URL}}/>
+        <NetworkImageCallbackExample
+          source={{
+            uri:
+              'http://origami.design/public/images/bird-logo.png?r=1&t=' +
+              Date.now(),
+          }}
+          prefetchedSource={{uri: IMAGE_PREFETCH_URL}}
+        />
       );
     },
   },
@@ -268,7 +332,11 @@ exports.examples = [
     title: 'Error Handler',
     render: function() {
       return (
-        <NetworkImageExample source={{uri: 'https://TYPO_ERROR_facebook.github.io/react/logo-og.png'}} />
+        <NetworkImageExample
+          source={{
+            uri: 'https://TYPO_ERROR_facebook.github.io/react/logo-og.png',
+          }}
+        />
       );
     },
     platform: 'ios',
@@ -277,7 +345,11 @@ exports.examples = [
     title: 'Image Download Progress',
     render: function() {
       return (
-        <NetworkImageExample source={{uri: 'http://origami.design/public/images/bird-logo.png?r=1'}}/>
+        <NetworkImageExample
+          source={{
+            uri: 'http://origami.design/public/images/bird-logo.png?r=1',
+          }}
+        />
       );
     },
     platform: 'ios',
@@ -289,7 +361,9 @@ exports.examples = [
       return (
         <Image
           defaultSource={require('./bunny.png')}
-          source={{uri: 'https://facebook.github.io/origami/public/images/birds.jpg'}}
+          source={{
+            uri: 'https://facebook.github.io/origami/public/images/birds.jpg',
+          }}
           style={styles.base}
         />
       );
@@ -298,17 +372,18 @@ exports.examples = [
   },
   {
     title: 'Cache Policy',
-    description: 'First image has never been loaded before and is instructed not to load unless in cache.' +
-    'Placeholder image from above will stay. Second image is the same but forced to load regardless of' +
-    ' local cache state.',
-    render: function () {
+    description:
+      'First image has never been loaded before and is instructed not to load unless in cache.' +
+      'Placeholder image from above will stay. Second image is the same but forced to load regardless of' +
+      ' local cache state.',
+    render: function() {
       return (
         <View style={styles.horizontal}>
           <Image
             defaultSource={require('./bunny.png')}
             source={{
               uri: smallImage.uri + '?cacheBust=notinCache' + Date.now(),
-              cache: 'only-if-cached'
+              cache: 'only-if-cached',
             }}
             style={styles.base}
           />
@@ -316,7 +391,7 @@ exports.examples = [
             defaultSource={require('./bunny.png')}
             source={{
               uri: smallImage.uri + '?cacheBust=notinCache' + Date.now(),
-              cache: 'reload'
+              cache: 'reload',
             }}
             style={styles.base}
           />
@@ -335,7 +410,7 @@ exports.examples = [
             style={[
               styles.base,
               styles.background,
-              {borderWidth: 3, borderColor: '#f099f0'}
+              {borderWidth: 3, borderColor: '#f099f0'},
             ]}
           />
         </View>
@@ -352,7 +427,7 @@ exports.examples = [
             style={[
               styles.base,
               styles.background,
-              {borderWidth: 5, borderColor: '#f099f0'}
+              {borderWidth: 5, borderColor: '#f099f0'},
             ]}
           />
         </View>
@@ -364,10 +439,7 @@ exports.examples = [
     render: function() {
       return (
         <View style={styles.horizontal}>
-          <Image
-            style={[styles.base, {borderRadius: 5}]}
-            source={fullImage}
-          />
+          <Image style={[styles.base, {borderRadius: 5}]} source={fullImage} />
           <Image
             style={[styles.base, styles.leftMargin, {borderRadius: 19}]}
             source={fullImage}
@@ -386,7 +458,7 @@ exports.examples = [
             style={[
               styles.base,
               styles.leftMargin,
-              {backgroundColor: 'rgba(0, 0, 100, 0.25)'}
+              {backgroundColor: 'rgba(0, 0, 100, 0.25)'},
             ]}
             source={smallImage}
           />
@@ -407,10 +479,7 @@ exports.examples = [
     render: function() {
       return (
         <View style={styles.horizontal}>
-          <Image
-            style={[styles.base, {opacity: 1}]}
-            source={fullImage}
-          />
+          <Image style={[styles.base, {opacity: 1}]} source={fullImage} />
           <Image
             style={[styles.base, styles.leftMargin, {opacity: 0.8}]}
             source={fullImage}
@@ -442,10 +511,9 @@ exports.examples = [
         <View style={{width: 60, height: 60}}>
           <Image
             style={{...StyleSheet.absoluteFillObject}}
-            source={fullImage}/>
-          <Text style={styles.nestedText}>
-            React
-          </Text>
+            source={fullImage}
+          />
+          <Text style={styles.nestedText}>React</Text>
         </View>
       );
     },
@@ -457,16 +525,15 @@ exports.examples = [
         <ImageBackground
           style={{width: 60, height: 60, backgroundColor: 'transparent'}}
           source={fullImage}>
-          <Text style={styles.nestedText}>
-            React
-          </Text>
+          <Text style={styles.nestedText}>React</Text>
         </ImageBackground>
       );
     },
   },
   {
     title: 'Tint Color',
-    description: 'The `tintColor` style prop changes all the non-alpha ' +
+    description:
+      'The `tintColor` style prop changes all the non-alpha ' +
       'pixels to the tint color.',
     render: function() {
       return (
@@ -474,19 +541,31 @@ exports.examples = [
           <View style={styles.horizontal}>
             <Image
               source={require('./uie_thumb_normal.png')}
-              style={[styles.icon, {borderRadius: 5, tintColor: '#5ac8fa' }]}
+              style={[styles.icon, {borderRadius: 5, tintColor: '#5ac8fa'}]}
             />
             <Image
               source={require('./uie_thumb_normal.png')}
-              style={[styles.icon, styles.leftMargin, {borderRadius: 5, tintColor: '#4cd964' }]}
+              style={[
+                styles.icon,
+                styles.leftMargin,
+                {borderRadius: 5, tintColor: '#4cd964'},
+              ]}
             />
             <Image
               source={require('./uie_thumb_normal.png')}
-              style={[styles.icon, styles.leftMargin, {borderRadius: 5, tintColor: '#ff2d55' }]}
+              style={[
+                styles.icon,
+                styles.leftMargin,
+                {borderRadius: 5, tintColor: '#ff2d55'},
+              ]}
             />
             <Image
               source={require('./uie_thumb_normal.png')}
-              style={[styles.icon, styles.leftMargin, {borderRadius: 5, tintColor: '#8e8e93' }]}
+              style={[
+                styles.icon,
+                styles.leftMargin,
+                {borderRadius: 5, tintColor: '#8e8e93'},
+              ]}
             />
           </View>
           <Text style={styles.sectionText}>
@@ -495,19 +574,31 @@ exports.examples = [
           <View style={styles.horizontal}>
             <Image
               source={smallImage}
-              style={[styles.base, {borderRadius: 5, tintColor: '#5ac8fa' }]}
+              style={[styles.base, {borderRadius: 5, tintColor: '#5ac8fa'}]}
             />
             <Image
               source={smallImage}
-              style={[styles.base, styles.leftMargin, {borderRadius: 5, tintColor: '#4cd964' }]}
+              style={[
+                styles.base,
+                styles.leftMargin,
+                {borderRadius: 5, tintColor: '#4cd964'},
+              ]}
             />
             <Image
               source={smallImage}
-              style={[styles.base, styles.leftMargin, {borderRadius: 5, tintColor: '#ff2d55' }]}
+              style={[
+                styles.base,
+                styles.leftMargin,
+                {borderRadius: 5, tintColor: '#ff2d55'},
+              ]}
             />
             <Image
               source={smallImage}
-              style={[styles.base, styles.leftMargin, {borderRadius: 5, tintColor: '#8e8e93' }]}
+              style={[
+                styles.base,
+                styles.leftMargin,
+                {borderRadius: 5, tintColor: '#8e8e93'},
+              ]}
             />
           </View>
         </View>
@@ -516,71 +607,62 @@ exports.examples = [
   },
   {
     title: 'Resize Mode',
-    description: 'The `resizeMode` style prop controls how the image is ' +
+    description:
+      'The `resizeMode` style prop controls how the image is ' +
       'rendered within the frame.',
     render: function() {
       return (
         <View>
           {[smallImage, fullImage].map((image, index) => {
             return (
-            <View key={index}>
-              <View style={styles.horizontal}>
-                <View>
-                  <Text style={[styles.resizeModeText]}>
-                    Contain
-                  </Text>
-                  <Image
-                    style={styles.resizeMode}
-                    resizeMode={Image.resizeMode.contain}
-                    source={image}
-                  />
+              <View key={index}>
+                <View style={styles.horizontal}>
+                  <View>
+                    <Text style={[styles.resizeModeText]}>Contain</Text>
+                    <Image
+                      style={styles.resizeMode}
+                      resizeMode={Image.resizeMode.contain}
+                      source={image}
+                    />
+                  </View>
+                  <View style={styles.leftMargin}>
+                    <Text style={[styles.resizeModeText]}>Cover</Text>
+                    <Image
+                      style={styles.resizeMode}
+                      resizeMode={Image.resizeMode.cover}
+                      source={image}
+                    />
+                  </View>
                 </View>
-                <View style={styles.leftMargin}>
-                  <Text style={[styles.resizeModeText]}>
-                    Cover
-                  </Text>
-                  <Image
-                    style={styles.resizeMode}
-                    resizeMode={Image.resizeMode.cover}
-                    source={image}
-                  />
+                <View style={styles.horizontal}>
+                  <View>
+                    <Text style={[styles.resizeModeText]}>Stretch</Text>
+                    <Image
+                      style={styles.resizeMode}
+                      resizeMode={Image.resizeMode.stretch}
+                      source={image}
+                    />
+                  </View>
+                  <View style={styles.leftMargin}>
+                    <Text style={[styles.resizeModeText]}>Repeat</Text>
+                    <Image
+                      style={styles.resizeMode}
+                      resizeMode={Image.resizeMode.repeat}
+                      source={image}
+                    />
+                  </View>
+                  <View style={styles.leftMargin}>
+                    <Text style={[styles.resizeModeText]}>Center</Text>
+                    <Image
+                      style={styles.resizeMode}
+                      resizeMode={Image.resizeMode.center}
+                      source={image}
+                    />
+                  </View>
                 </View>
               </View>
-              <View style={styles.horizontal}>
-                <View>
-                  <Text style={[styles.resizeModeText]}>
-                    Stretch
-                  </Text>
-                  <Image
-                    style={styles.resizeMode}
-                    resizeMode={Image.resizeMode.stretch}
-                    source={image}
-                  />
-                </View>
-                <View style={styles.leftMargin}>
-                  <Text style={[styles.resizeModeText]}>
-                    Repeat
-                  </Text>
-                  <Image
-                    style={styles.resizeMode}
-                    resizeMode={Image.resizeMode.repeat}
-                    source={image}
-                  />
-                </View>
-                <View style={styles.leftMargin}>
-                  <Text style={[styles.resizeModeText]}>
-                    Center
-                  </Text>
-                  <Image
-                    style={styles.resizeMode}
-                    resizeMode={Image.resizeMode.center}
-                    source={image}
-                  />
-                </View>
-              </View>
-            </View>
-          );
-        })}
+            );
+          })}
         </View>
       );
     },
@@ -591,7 +673,10 @@ exports.examples = [
       return (
         <Image
           style={styles.gif}
-          source={{uri: 'https://38.media.tumblr.com/9e9bd08c6e2d10561dd1fb4197df4c4e/tumblr_mfqekpMktw1rn90umo1_500.gif'}}
+          source={{
+            uri:
+              'https://38.media.tumblr.com/9e9bd08c6e2d10561dd1fb4197df4c4e/tumblr_mfqekpMktw1rn90umo1_500.gif',
+          }}
         />
       );
     },
@@ -601,10 +686,7 @@ exports.examples = [
     title: 'Base64 image',
     render: function() {
       return (
-        <Image
-          style={styles.base64}
-          source={{uri: base64Icon, scale: 3}}
-        />
+        <Image style={styles.base64} source={{uri: base64Icon, scale: 3}} />
       );
     },
     platform: 'ios',
@@ -642,17 +724,12 @@ exports.examples = [
       'Images shipped with the native bundle, but not managed ' +
       'by the JS packager',
     render: function() {
-      return (
-        <Image
-          source={{uri: 'legacy_image', width: 120, height: 120}}
-        />
-      );
+      return <Image source={{uri: 'legacy_image', width: 120, height: 120}} />;
     },
   },
   {
     title: 'Bundled images',
-    description:
-      'Images shipped in a separate native bundle',
+    description: 'Images shipped in a separate native bundle',
     render: function() {
       return (
         <View style={{flexDirection: 'row'}}>
@@ -684,11 +761,7 @@ exports.examples = [
     render: function() {
       return (
         <View style={styles.horizontal}>
-          <Image
-            style={[styles.base,]}
-            source={fullImage}
-            blurRadius={0}
-          />
+          <Image style={[styles.base]} source={fullImage} blurRadius={0} />
           <Image
             style={[styles.base, styles.leftMargin]}
             source={fullImage}
@@ -720,8 +793,12 @@ exports.examples = [
   },
 ];
 
-var fullImage = {uri: 'https://facebook.github.io/react-native/img/opengraph.png'};
-var smallImage = {uri: 'https://facebook.github.io/react-native/img/favicon.png'};
+var fullImage = {
+  uri: 'https://facebook.github.io/react-native/img/opengraph.png',
+};
+var smallImage = {
+  uri: 'https://facebook.github.io/react-native/img/favicon.png',
+};
 
 var styles = StyleSheet.create({
   base: {
@@ -732,13 +809,13 @@ var styles = StyleSheet.create({
     flex: 1,
     alignItems: 'center',
     flexDirection: 'row',
-    width: 100
+    width: 100,
   },
   leftMargin: {
     marginLeft: 10,
   },
   background: {
-    backgroundColor: '#222222'
+    backgroundColor: '#222222',
   },
   sectionText: {
     marginVertical: 6,
@@ -747,13 +824,13 @@ var styles = StyleSheet.create({
     marginLeft: 12,
     marginTop: 20,
     backgroundColor: 'transparent',
-    color: 'white'
+    color: 'white',
   },
   resizeMode: {
     width: 90,
     height: 60,
     borderWidth: 0.5,
-    borderColor: 'black'
+    borderColor: 'black',
   },
   resizeModeText: {
     fontSize: 11,
diff --git a/RNTester/js/KeyboardAvoidingViewExample.js b/RNTester/js/KeyboardAvoidingViewExample.js
index 3c84590822d6..2e51ed842016 100644
--- a/RNTester/js/KeyboardAvoidingViewExample.js
+++ b/RNTester/js/KeyboardAvoidingViewExample.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const React = require('React');
@@ -40,15 +42,16 @@ class KeyboardAvoidingViewExample extends React.Component {
     return (
       <View style={styles.outerContainer}>
         <Modal animationType="fade" visible={this.state.modalOpen}>
-          <KeyboardAvoidingView behavior={this.state.behavior} style={styles.container}>
+          <KeyboardAvoidingView
+            behavior={this.state.behavior}
+            style={styles.container}>
             <SegmentedControlIOS
               onValueChange={this.onSegmentChange}
               selectedIndex={this.state.behavior === 'padding' ? 0 : 1}
               style={styles.segment}
-              values={['Padding', 'Position']} />
-            <TextInput
-              placeholder="<TextInput />"
-              style={styles.textInput} />
+              values={['Padding', 'Position']}
+            />
+            <TextInput placeholder="<TextInput />" style={styles.textInput} />
           </KeyboardAvoidingView>
           <TouchableHighlight
             onPress={() => this.setState({modalOpen: false})}
@@ -98,7 +101,7 @@ const styles = StyleSheet.create({
     position: 'absolute',
     top: 30,
     left: 10,
-  }
+  },
 });
 
 module.exports = KeyboardAvoidingViewExample;
diff --git a/RNTester/js/LayoutAnimationExample.js b/RNTester/js/LayoutAnimationExample.js
index a62143d2b04a..47f5889834bd 100644
--- a/RNTester/js/LayoutAnimationExample.js
+++ b/RNTester/js/LayoutAnimationExample.js
@@ -4,19 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  LayoutAnimation,
-  StyleSheet,
-  Text,
-  View,
-  TouchableOpacity,
-} = ReactNative;
+const {LayoutAnimation, StyleSheet, Text, View, TouchableOpacity} = ReactNative;
 
 class AddRemoveExample extends React.Component<{}, $FlowFixMeState> {
   state = {
@@ -28,19 +24,19 @@ class AddRemoveExample extends React.Component<{}, $FlowFixMeState> {
   }
 
   _onPressAddView = () => {
-    this.setState((state) => ({views: [...state.views, {}]}));
+    this.setState(state => ({views: [...state.views, {}]}));
   };
 
   _onPressRemoveView = () => {
-    this.setState((state) => ({views: state.views.slice(0, -1)}));
+    this.setState(state => ({views: state.views.slice(0, -1)}));
   };
 
   render() {
-    const views = this.state.views.map((view, i) =>
+    const views = this.state.views.map((view, i) => (
       <View key={i} style={styles.view}>
         <Text>{i}</Text>
       </View>
-    );
+    ));
     return (
       <View style={styles.container}>
         <TouchableOpacity onPress={this._onPressAddView}>
@@ -53,23 +49,23 @@ class AddRemoveExample extends React.Component<{}, $FlowFixMeState> {
             <Text>Remove view</Text>
           </View>
         </TouchableOpacity>
-        <View style={styles.viewContainer}>
-          {views}
-        </View>
+        <View style={styles.viewContainer}>{views}</View>
       </View>
     );
   }
 }
 
-const GreenSquare = () =>
+const GreenSquare = () => (
   <View style={styles.greenSquare}>
     <Text>Green square</Text>
-  </View>;
+  </View>
+);
 
-const BlueSquare = () =>
+const BlueSquare = () => (
   <View style={styles.blueSquare}>
     <Text>Blue square</Text>
-  </View>;
+  </View>
+);
 
 class CrossFadeExample extends React.Component<{}, $FlowFixMeState> {
   state = {
@@ -78,7 +74,7 @@ class CrossFadeExample extends React.Component<{}, $FlowFixMeState> {
 
   _onPressToggle = () => {
     LayoutAnimation.easeInEaseOut();
-    this.setState((state) => ({toggled: !state.toggled}));
+    this.setState(state => ({toggled: !state.toggled}));
   };
 
   render() {
@@ -90,11 +86,7 @@ class CrossFadeExample extends React.Component<{}, $FlowFixMeState> {
           </View>
         </TouchableOpacity>
         <View style={styles.viewContainer}>
-          {
-            this.state.toggled ?
-            <GreenSquare /> :
-            <BlueSquare />
-          }
+          {this.state.toggled ? <GreenSquare /> : <BlueSquare />}
         </View>
       </View>
     );
@@ -118,7 +110,7 @@ class LayoutUpdateExample extends React.Component<{}, $FlowFixMeState> {
       clearTimeout(this.timeout);
       this.timeout = null;
     }
-  }
+  };
 
   _onPressToggle = () => {
     this._clearTimeout();
@@ -145,7 +137,9 @@ class LayoutUpdateExample extends React.Component<{}, $FlowFixMeState> {
           </View>
         </TouchableOpacity>
         <View style={[styles.view, {width, height}]}>
-          <Text>{width}x{height}</Text>
+          <Text>
+            {width}x{height}
+          </Text>
         </View>
       </View>
     );
@@ -196,19 +190,23 @@ const styles = StyleSheet.create({
 
 exports.title = 'Layout Animation';
 exports.description = 'Layout animation';
-exports.examples = [{
-  title: 'Add and remove views',
-  render(): React.Element<any> {
-    return <AddRemoveExample />;
+exports.examples = [
+  {
+    title: 'Add and remove views',
+    render(): React.Element<any> {
+      return <AddRemoveExample />;
+    },
   },
-}, {
-  title: 'Cross fade views',
-  render(): React.Element<any> {
-    return <CrossFadeExample />;
+  {
+    title: 'Cross fade views',
+    render(): React.Element<any> {
+      return <CrossFadeExample />;
+    },
   },
-}, {
-  title: 'Layout update during animation',
-  render(): React.Element<any> {
-    return <LayoutUpdateExample />;
+  {
+    title: 'Layout update during animation',
+    render(): React.Element<any> {
+      return <LayoutUpdateExample />;
+    },
   },
-}];
+];
diff --git a/RNTester/js/LayoutEventsExample.js b/RNTester/js/LayoutEventsExample.js
index b90bc27fd5ca..f5556a868175 100644
--- a/RNTester/js/LayoutEventsExample.js
+++ b/RNTester/js/LayoutEventsExample.js
@@ -4,29 +4,25 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Image,
-  LayoutAnimation,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Image, LayoutAnimation, StyleSheet, Text, View} = ReactNative;
 
 import type {ViewLayout, ViewLayoutEvent} from 'ViewPropTypes';
 
 type State = {
-  containerStyle?: { width: number },
+  containerStyle?: {width: number},
   extraText?: string,
   imageLayout?: ViewLayout,
   textLayout?: ViewLayout,
   viewLayout?: ViewLayout,
-  viewStyle: { margin: number },
+  viewStyle: {margin: number},
 };
 
 class LayoutEventExample extends React.Component<{}, State> {
@@ -37,24 +33,21 @@ class LayoutEventExample extends React.Component<{}, State> {
   };
 
   animateViewLayout = () => {
-    LayoutAnimation.configureNext(
-      LayoutAnimation.Presets.spring,
-      () => {
-        console.log('layout animation done.');
-        this.addWrapText();
-      }
-    );
+    LayoutAnimation.configureNext(LayoutAnimation.Presets.spring, () => {
+      console.log('layout animation done.');
+      this.addWrapText();
+    });
     this.setState({
       viewStyle: {
         margin: this.state.viewStyle.margin > 20 ? 20 : 60,
-      }
+      },
     });
   };
 
   addWrapText = () => {
     this.setState(
       {extraText: '  And a bunch more text to wrap around a few lines.'},
-      this.changeContainer
+      this.changeContainer,
     );
   };
 
@@ -84,7 +77,10 @@ class LayoutEventExample extends React.Component<{}, State> {
     return (
       <View style={this.state.containerStyle}>
         <Text>
-          layout events are called on mount and whenever layout is recalculated. Note that the layout event will typically be received <Text style={styles.italicText}>before</Text> the layout has updated on screen, especially when using layout animations.{'  '}
+          layout events are called on mount and whenever layout is recalculated.
+          Note that the layout event will typically be received{' '}
+          <Text style={styles.italicText}>before</Text> the layout has updated
+          on screen, especially when using layout animations.{'  '}
           <Text style={styles.pressText} onPress={this.animateViewLayout}>
             Press here to change layout.
           </Text>
@@ -94,10 +90,14 @@ class LayoutEventExample extends React.Component<{}, State> {
             ref="img"
             onLayout={this.onImageLayout}
             style={styles.image}
-            source={{uri: 'https://fbcdn-dragon-a.akamaihd.net/hphotos-ak-prn1/t39.1997/p128x128/851561_767334496626293_1958532586_n.png'}}
+            source={{
+              uri:
+                'https://fbcdn-dragon-a.akamaihd.net/hphotos-ak-prn1/t39.1997/p128x128/851561_767334496626293_1958532586_n.png',
+            }}
           />
           <Text>
-            ViewLayout: {JSON.stringify(this.state.viewLayout, null, '  ') + '\n\n'}
+            ViewLayout:{' '}
+            {JSON.stringify(this.state.viewLayout, null, '  ') + '\n\n'}
           </Text>
           <Text ref="txt" onLayout={this.onTextLayout} style={styles.text}>
             A simple piece of text.{this.state.extraText}
@@ -140,12 +140,14 @@ var styles = StyleSheet.create({
 });
 
 exports.title = 'Layout Events';
-exports.description = 'Examples that show how Layout events can be used to ' +
+exports.description =
+  'Examples that show how Layout events can be used to ' +
   'measure view size and position.';
 exports.examples = [
-{
-  title: 'LayoutEventExample',
-  render: function(): React.Element<any> {
-    return <LayoutEventExample />;
+  {
+    title: 'LayoutEventExample',
+    render: function(): React.Element<any> {
+      return <LayoutEventExample />;
+    },
   },
-}];
+];
diff --git a/RNTester/js/LayoutExample.js b/RNTester/js/LayoutExample.js
index b6edcaef7297..3803fcf90028 100644
--- a/RNTester/js/LayoutExample.js
+++ b/RNTester/js/LayoutExample.js
@@ -4,17 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, View} = ReactNative;
 
 var RNTesterBlock = require('./RNTesterBlock');
 var RNTesterPage = require('./RNTesterPage');
@@ -47,9 +45,7 @@ class CircleBlock extends React.Component<$FlowFixMeProps> {
       marginBottom: 2,
     };
     return (
-      <View style={[circleStyle, this.props.style]}>
-        {this.props.children}
-      </View>
+      <View style={[circleStyle, this.props.style]}>{this.props.children}</View>
     );
   }
 }
@@ -65,7 +61,7 @@ class LayoutExample extends React.Component<$FlowFixMeProps> {
       <Circle bgColor="#D443E3" key="violet" />,
       <Circle bgColor="#FF9049" key="orange" />,
       <Circle bgColor="#FFE649" key="yellow" />,
-      <Circle bgColor="#7FE040" key="green" />
+      <Circle bgColor="#7FE040" key="green" />,
     ];
 
     return (
@@ -87,7 +83,11 @@ class LayoutExample extends React.Component<$FlowFixMeProps> {
           <CircleBlock style={{flexDirection: 'column-reverse'}}>
             {fiveColoredCircles}
           </CircleBlock>
-          <View style={[styles.overlay, {position: 'absolute', top: 15, left: 160}]}>
+          <View
+            style={[
+              styles.overlay,
+              {position: 'absolute', top: 15, left: 160},
+            ]}>
             <Text>{'top: 15, left: 160'}</Text>
           </View>
         </RNTesterBlock>
@@ -117,30 +117,63 @@ class LayoutExample extends React.Component<$FlowFixMeProps> {
         <RNTesterBlock title="Align Items - Other Direction">
           <Text>flex-start</Text>
           <CircleBlock style={{alignItems: 'flex-start', height: 30}}>
-            <Circle size={15} /><Circle size={10} /><Circle size={20} />
-            <Circle size={17} /><Circle size={12} /><Circle size={15} />
-            <Circle size={10} /><Circle size={20} /><Circle size={17} />
-            <Circle size={12} /><Circle size={15} /><Circle size={10} />
-            <Circle size={20} /><Circle size={17} /><Circle size={12} />
-            <Circle size={15} /><Circle size={8} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={8} />
           </CircleBlock>
           <Text>center</Text>
           <CircleBlock style={{alignItems: 'center', height: 30}}>
-            <Circle size={15} /><Circle size={10} /><Circle size={20} />
-            <Circle size={17} /><Circle size={12} /><Circle size={15} />
-            <Circle size={10} /><Circle size={20} /><Circle size={17} />
-            <Circle size={12} /><Circle size={15} /><Circle size={10} />
-            <Circle size={20} /><Circle size={17} /><Circle size={12} />
-            <Circle size={15} /><Circle size={8} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={8} />
           </CircleBlock>
           <Text>flex-end</Text>
           <CircleBlock style={{alignItems: 'flex-end', height: 30}}>
-            <Circle size={15} /><Circle size={10} /><Circle size={20} />
-            <Circle size={17} /><Circle size={12} /><Circle size={15} />
-            <Circle size={10} /><Circle size={20} /><Circle size={17} />
-            <Circle size={12} /><Circle size={15} /><Circle size={10} />
-            <Circle size={20} /><Circle size={17} /><Circle size={12} />
-            <Circle size={15} /><Circle size={8} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={10} />
+            <Circle size={20} />
+            <Circle size={17} />
+            <Circle size={12} />
+            <Circle size={15} />
+            <Circle size={8} />
           </CircleBlock>
         </RNTesterBlock>
         <RNTesterBlock title="Flex Wrap">
diff --git a/RNTester/js/LinkingExample.js b/RNTester/js/LinkingExample.js
index 4ee6a27421b6..5f6724f95bb1 100644
--- a/RNTester/js/LinkingExample.js
+++ b/RNTester/js/LinkingExample.js
@@ -4,19 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
 var PropTypes = require('prop-types');
 var ReactNative = require('react-native');
-var {
-  Linking,
-  StyleSheet,
-  Text,
-  TouchableOpacity,
-  View,
-} = ReactNative;
+var {Linking, StyleSheet, Text, TouchableOpacity, View} = ReactNative;
 var RNTesterBlock = require('./RNTesterBlock');
 
 class OpenURLButton extends React.Component {
@@ -29,15 +25,14 @@ class OpenURLButton extends React.Component {
       if (supported) {
         Linking.openURL(this.props.url);
       } else {
-        console.log('Don\'t know how to open URI: ' + this.props.url);
+        console.log("Don't know how to open URI: " + this.props.url);
       }
     });
   };
 
   render() {
     return (
-      <TouchableOpacity
-        onPress={this.handleClick}>
+      <TouchableOpacity onPress={this.handleClick}>
         <View style={styles.button}>
           <Text style={styles.text}>Open {this.props.url}</Text>
         </View>
diff --git a/RNTester/js/ListExampleShared.js b/RNTester/js/ListExampleShared.js
index 2aab97161657..0edb7fe181ad 100644
--- a/RNTester/js/ListExampleShared.js
+++ b/RNTester/js/ListExampleShared.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -22,7 +24,13 @@ const {
   View,
 } = ReactNative;
 
-type Item = {title: string, text: string, key: string, pressed: boolean, noImage?: ?boolean};
+type Item = {
+  title: string,
+  text: string,
+  key: string,
+  pressed: boolean,
+  noImage?: ?boolean,
+};
 
 function genItemData(count: number, start: number = 0): Array<Item> {
   const dataBlob = [];
@@ -65,12 +73,16 @@ class ItemComponent extends React.PureComponent<{
           pressMagnification: 1.1,
         }}
         style={horizontal ? styles.horizItem : styles.item}>
-        <View style={[
-          styles.row, horizontal && {width: HORIZ_WIDTH}, fixedHeight && {height: ITEM_HEIGHT}]}>
+        <View
+          style={[
+            styles.row,
+            horizontal && {width: HORIZ_WIDTH},
+            fixedHeight && {height: ITEM_HEIGHT},
+          ]}>
           {!item.noImage && <Image style={styles.thumb} source={imgSource} />}
           <Text
             style={styles.text}
-            numberOfLines={(horizontal || fixedHeight) ? 3 : undefined}>
+            numberOfLines={horizontal || fixedHeight ? 3 : undefined}>
             {item.title} - {item.text}
           </Text>
         </View>
@@ -84,7 +96,9 @@ const renderStackedItem = ({item}: {item: Item}) => {
   const imgSource = THUMB_URLS[itemHash % THUMB_URLS.length];
   return (
     <View style={styles.stacked}>
-      <Text style={styles.stackedText}>{item.title} - {item.text}</Text>
+      <Text style={styles.stackedText}>
+        {item.title} - {item.text}
+      </Text>
       <Image style={styles.thumb} source={imgSource} />
     </View>
   );
@@ -135,7 +149,10 @@ class SeparatorComponent extends React.PureComponent<{}> {
 class ItemSeparatorComponent extends React.PureComponent<$FlowFixMeProps> {
   render() {
     const style = this.props.highlighted
-      ? [styles.itemSeparator, {marginLeft: 0, backgroundColor: 'rgb(217, 217, 217)'}]
+      ? [
+          styles.itemSeparator,
+          {marginLeft: 0, backgroundColor: 'rgb(217, 217, 217)'},
+        ]
       : styles.itemSeparator;
     return <View style={style} />;
   }
@@ -144,15 +161,22 @@ class ItemSeparatorComponent extends React.PureComponent<$FlowFixMeProps> {
 class Spindicator extends React.PureComponent<$FlowFixMeProps> {
   render() {
     return (
-      <Animated.View style={[styles.spindicator, {
-        transform: [
-          {rotate: this.props.value.interpolate({
-            inputRange: [0, 5000],
-            outputRange: ['0deg', '360deg'],
-            extrapolate: 'extend',
-          })}
-        ]
-      }]} />
+      <Animated.View
+        style={[
+          styles.spindicator,
+          {
+            transform: [
+              {
+                rotate: this.props.value.interpolate({
+                  inputRange: [0, 5000],
+                  outputRange: ['0deg', '360deg'],
+                  extrapolate: 'extend',
+                }),
+              },
+            ],
+          },
+        ]}
+      />
     );
   }
 }
@@ -172,7 +196,8 @@ const THUMB_URLS = [
   require('./Thumbnails/victory.png'),
 ];
 
-const LOREM_IPSUM = 'Lorem ipsum dolor sit amet, ius ad pertinax oportere accommodare, an vix \
+const LOREM_IPSUM =
+  'Lorem ipsum dolor sit amet, ius ad pertinax oportere accommodare, an vix \
 civibus corrumpit referrentur. Te nam case ludus inciderint, te mea facilisi adipiscing. Sea id \
 integre luptatum. In tota sale consequuntur nec. Erat ocurreret mei ei. Eu paulo sapientem \
 vulputate est, vel an accusam intellegam interesset. Nam eu stet pericula reprimique, ea vim illud \
@@ -182,7 +207,7 @@ modus, putant invidunt reprehendunt ne qui.';
 function hashCode(str: string): number {
   let hash = 15;
   for (let ii = str.length - 1; ii >= 0; ii--) {
-    hash = ((hash << 5) - hash) + str.charCodeAt(ii);
+    hash = (hash << 5) - hash + str.charCodeAt(ii);
   }
   return hash;
 }
@@ -191,15 +216,16 @@ const HEADER = {height: 30, width: 100};
 const SEPARATOR_HEIGHT = StyleSheet.hairlineWidth;
 
 function getItemLayout(data: any, index: number, horizontal?: boolean) {
-  const [length, separator, header] = horizontal ?
-    [HORIZ_WIDTH, 0, HEADER.width] : [ITEM_HEIGHT, SEPARATOR_HEIGHT, HEADER.height];
+  const [length, separator, header] = horizontal
+    ? [HORIZ_WIDTH, 0, HEADER.width]
+    : [ITEM_HEIGHT, SEPARATOR_HEIGHT, HEADER.height];
   return {length, offset: (length + separator) * index + header, index};
 }
 
 function pressItem(context: Object, key: string) {
   const index = Number(key);
   const pressed = !context.state.data[index].pressed;
-  context.setState((state) => {
+  context.setState(state => {
     const newData = [...state.data];
     newData[index] = {
       ...state.data[index],
@@ -220,7 +246,7 @@ function renderSmallSwitchOption(context: Object, key: string) {
       <Switch
         style={styles.smallSwitch}
         value={context.state[key]}
-        onValueChange={(value) => context.setState({[key]: value})}
+        onValueChange={value => context.setState({[key]: value})}
       />
     </View>
   );
diff --git a/RNTester/js/ListViewExample.js b/RNTester/js/ListViewExample.js
index ea1e07bafe5e..9e008dd400b7 100644
--- a/RNTester/js/ListViewExample.js
+++ b/RNTester/js/ListViewExample.js
@@ -4,21 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var createReactClass = require('create-react-class');
 var ReactNative = require('react-native');
-var {
-  Image,
-  ListView,
-  TouchableHighlight,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Image, ListView, TouchableHighlight, StyleSheet, Text, View} = ReactNative;
 
 var RNTesterPage = require('./RNTesterPage');
 
@@ -26,7 +21,7 @@ var ListViewSimpleExample = createReactClass({
   displayName: 'ListViewSimpleExample',
   statics: {
     title: '<ListView>',
-    description: 'Performant, scrollable list of data.'
+    description: 'Performant, scrollable list of data.',
   },
 
   getInitialState: function() {
@@ -57,11 +52,17 @@ var ListViewSimpleExample = createReactClass({
     );
   },
 
-  _renderRow: function(rowData: string, sectionID: number, rowID: number, highlightRow: (sectionID: number, rowID: number) => void) {
+  _renderRow: function(
+    rowData: string,
+    sectionID: number,
+    rowID: number,
+    highlightRow: (sectionID: number, rowID: number) => void,
+  ) {
     var rowHash = Math.abs(hashCode(rowData));
     var imgSource = THUMB_URLS[rowHash % THUMB_URLS.length];
     return (
-      <TouchableHighlight onPress={() => {
+      <TouchableHighlight
+        onPress={() => {
           this._pressRow(rowID);
           highlightRow(sectionID, rowID);
         }}>
@@ -88,12 +89,18 @@ var ListViewSimpleExample = createReactClass({
 
   _pressRow: function(rowID: number) {
     this._pressData[rowID] = !this._pressData[rowID];
-    this.setState({dataSource: this.state.dataSource.cloneWithRows(
-      this._genRows(this._pressData)
-    )});
+    this.setState({
+      dataSource: this.state.dataSource.cloneWithRows(
+        this._genRows(this._pressData),
+      ),
+    });
   },
 
-  _renderSeparator: function(sectionID: number, rowID: number, adjacentRowHighlighted: bool) {
+  _renderSeparator: function(
+    sectionID: number,
+    rowID: number,
+    adjacentRowHighlighted: boolean,
+  ) {
     return (
       <View
         key={`${sectionID}-${rowID}`}
@@ -103,7 +110,7 @@ var ListViewSimpleExample = createReactClass({
         }}
       />
     );
-  }
+  },
 });
 
 var THUMB_URLS = [
@@ -119,14 +126,15 @@ var THUMB_URLS = [
   require('./Thumbnails/poke.png'),
   require('./Thumbnails/superlike.png'),
   require('./Thumbnails/victory.png'),
-  ];
-var LOREM_IPSUM = 'Lorem ipsum dolor sit amet, ius ad pertinax oportere accommodare, an vix civibus corrumpit referrentur. Te nam case ludus inciderint, te mea facilisi adipiscing. Sea id integre luptatum. In tota sale consequuntur nec. Erat ocurreret mei ei. Eu paulo sapientem vulputate est, vel an accusam intellegam interesset. Nam eu stet pericula reprimique, ea vim illud modus, putant invidunt reprehendunt ne qui.';
+];
+var LOREM_IPSUM =
+  'Lorem ipsum dolor sit amet, ius ad pertinax oportere accommodare, an vix civibus corrumpit referrentur. Te nam case ludus inciderint, te mea facilisi adipiscing. Sea id integre luptatum. In tota sale consequuntur nec. Erat ocurreret mei ei. Eu paulo sapientem vulputate est, vel an accusam intellegam interesset. Nam eu stet pericula reprimique, ea vim illud modus, putant invidunt reprehendunt ne qui.';
 
 /* eslint no-bitwise: 0 */
 var hashCode = function(str) {
   var hash = 15;
   for (var ii = str.length - 1; ii >= 0; ii--) {
-    hash = ((hash << 5) - hash) + str.charCodeAt(ii);
+    hash = (hash << 5) - hash + str.charCodeAt(ii);
   }
   return hash;
 };
diff --git a/RNTester/js/ListViewGridLayoutExample.js b/RNTester/js/ListViewGridLayoutExample.js
index 5f389596ea86..65a407f4d19e 100644
--- a/RNTester/js/ListViewGridLayoutExample.js
+++ b/RNTester/js/ListViewGridLayoutExample.js
@@ -4,21 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var createReactClass = require('create-react-class');
 var ReactNative = require('react-native');
-var {
-  Image,
-  ListView,
-  TouchableHighlight,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Image, ListView, TouchableHighlight, StyleSheet, Text, View} = ReactNative;
 
 var THUMB_URLS = [
   require('./Thumbnails/like.png'),
@@ -40,7 +35,7 @@ var ListViewGridLayoutExample = createReactClass({
 
   statics: {
     title: '<ListView> - Grid Layout',
-    description: 'Flexbox grid layout.'
+    description: 'Flexbox grid layout.',
   },
 
   getInitialState: function() {
@@ -75,13 +70,13 @@ var ListViewGridLayoutExample = createReactClass({
     var rowHash = Math.abs(hashCode(rowData));
     var imgSource = THUMB_URLS[rowHash % THUMB_URLS.length];
     return (
-      <TouchableHighlight onPress={() => this._pressRow(rowID)} underlayColor="transparent">
+      <TouchableHighlight
+        onPress={() => this._pressRow(rowID)}
+        underlayColor="transparent">
         <View>
           <View style={styles.row}>
             <Image style={styles.thumb} source={imgSource} />
-            <Text style={styles.text}>
-              {rowData}
-            </Text>
+            <Text style={styles.text}>{rowData}</Text>
           </View>
         </View>
       </TouchableHighlight>
@@ -99,9 +94,11 @@ var ListViewGridLayoutExample = createReactClass({
 
   _pressRow: function(rowID: number) {
     this._pressData[rowID] = !this._pressData[rowID];
-    this.setState({dataSource: this.state.dataSource.cloneWithRows(
-      this._genRows(this._pressData)
-    )});
+    this.setState({
+      dataSource: this.state.dataSource.cloneWithRows(
+        this._genRows(this._pressData),
+      ),
+    });
   },
 });
 
@@ -109,7 +106,7 @@ var ListViewGridLayoutExample = createReactClass({
 var hashCode = function(str) {
   var hash = 15;
   for (var ii = str.length - 1; ii >= 0; ii--) {
-    hash = ((hash << 5) - hash) + str.charCodeAt(ii);
+    hash = (hash << 5) - hash + str.charCodeAt(ii);
   }
   return hash;
 };
@@ -119,7 +116,7 @@ var styles = StyleSheet.create({
     justifyContent: 'space-around',
     flexDirection: 'row',
     flexWrap: 'wrap',
-    alignItems: 'flex-start'
+    alignItems: 'flex-start',
   },
   row: {
     justifyContent: 'center',
@@ -131,16 +128,16 @@ var styles = StyleSheet.create({
     alignItems: 'center',
     borderWidth: 1,
     borderRadius: 5,
-    borderColor: '#CCC'
+    borderColor: '#CCC',
   },
   thumb: {
     width: 64,
-    height: 64
+    height: 64,
   },
   text: {
     flex: 1,
     marginTop: 5,
-    fontWeight: 'bold'
+    fontWeight: 'bold',
   },
 });
 
diff --git a/RNTester/js/ListViewPagingExample.js b/RNTester/js/ListViewPagingExample.js
index 88548ec0b985..5ff64ec6c136 100644
--- a/RNTester/js/ListViewPagingExample.js
+++ b/RNTester/js/ListViewPagingExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -21,9 +23,7 @@ var {
 } = ReactNative;
 
 var NativeModules = require('NativeModules');
-var {
-  UIManager,
-} = NativeModules;
+var {UIManager} = NativeModules;
 
 var THUMB_URLS = [
   require('./Thumbnails/like.png'),
@@ -53,7 +53,10 @@ class Thumb extends React.Component<{}, $FlowFixMeState> {
   };
 
   _onPressThumb = () => {
-    var config = layoutAnimationConfigs[this.state.thumbIndex % layoutAnimationConfigs.length];
+    var config =
+      layoutAnimationConfigs[
+        this.state.thumbIndex % layoutAnimationConfigs.length
+      ];
     LayoutAnimation.configureNext(config);
     this.setState({
       thumbIndex: this._getThumbIdx(),
@@ -71,13 +74,14 @@ class Thumb extends React.Component<{}, $FlowFixMeState> {
         <Image style={styles.img} source={THUMB_URLS[this.state.thumbIndex]} />
         <Image style={styles.img} source={THUMB_URLS[this.state.thumbIndex]} />
         <Image style={styles.img} source={THUMB_URLS[this.state.thumbIndex]} />
-        {this.state.dir === 'column' ?
+        {this.state.dir === 'column' ? (
           <Text>
-            Oooo, look at this new text!  So awesome it may just be crazy.
-            Let me keep typing here so it wraps at least one line.
-          </Text> :
+            Oooo, look at this new text! So awesome it may just be crazy. Let me
+            keep typing here so it wraps at least one line.
+          </Text>
+        ) : (
           <Text />
-        }
+        )}
       </TouchableOpacity>
     );
   }
@@ -121,36 +125,43 @@ class ListViewPagingExample extends React.Component<$FlowFixMeProps, *> {
     }
 
     this.state = {
-      dataSource: dataSource.cloneWithRowsAndSections(dataBlob, sectionIDs, rowIDs),
+      dataSource: dataSource.cloneWithRowsAndSections(
+        dataBlob,
+        sectionIDs,
+        rowIDs,
+      ),
       headerPressCount: 0,
     };
   }
 
-  renderRow = (rowData: string, sectionID: string, rowID: string): React.Element<any> => {
-    return (<Thumb text={rowData}/>);
+  renderRow = (
+    rowData: string,
+    sectionID: string,
+    rowID: string,
+  ): React.Element<any> => {
+    return <Thumb text={rowData} />;
   };
 
   renderSectionHeader = (sectionData: string, sectionID: string) => {
     return (
       <View style={styles.section}>
-        <Text style={styles.text}>
-          {sectionData}
-        </Text>
+        <Text style={styles.text}>{sectionData}</Text>
       </View>
     );
   };
 
   renderHeader = () => {
-    var headerLikeText = this.state.headerPressCount % 2 ?
-      <View><Text style={styles.text}>1 Like</Text></View> :
-      null;
+    var headerLikeText =
+      this.state.headerPressCount % 2 ? (
+        <View>
+          <Text style={styles.text}>1 Like</Text>
+        </View>
+      ) : null;
     return (
       <TouchableOpacity onPress={this._onPressHeader} style={styles.header}>
         {headerLikeText}
         <View>
-          <Text style={styles.text}>
-            Table Header (click me)
-          </Text>
+          <Text style={styles.text}>Table Header (click me)</Text>
         </View>
       </TouchableOpacity>
     );
@@ -171,7 +182,9 @@ class ListViewPagingExample extends React.Component<$FlowFixMeProps, *> {
       <ListView
         style={styles.listview}
         dataSource={this.state.dataSource}
-        onChangeVisibleRows={(visibleRows, changedRows) => console.log({visibleRows, changedRows})}
+        onChangeVisibleRows={(visibleRows, changedRows) =>
+          console.log({visibleRows, changedRows})
+        }
         renderHeader={this.renderHeader}
         renderFooter={this.renderFooter}
         renderSectionHeader={this.renderSectionHeader}
@@ -185,7 +198,11 @@ class ListViewPagingExample extends React.Component<$FlowFixMeProps, *> {
   }
 
   _onPressHeader = () => {
-    var config = layoutAnimationConfigs[Math.floor(this.state.headerPressCount / 2) % layoutAnimationConfigs.length];
+    var config =
+      layoutAnimationConfigs[
+        Math.floor(this.state.headerPressCount / 2) %
+          layoutAnimationConfigs.length
+      ];
     LayoutAnimation.configureNext(config);
     this.setState({headerPressCount: this.state.headerPressCount + 1});
   };
diff --git a/RNTester/js/MaskedViewExample.js b/RNTester/js/MaskedViewExample.js
index 6548b7e49570..081496b6f1b6 100644
--- a/RNTester/js/MaskedViewExample.js
+++ b/RNTester/js/MaskedViewExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -50,7 +52,7 @@ class MaskedViewExample extends React.Component<{}, $FlowFixMeState> {
           timing: 750,
           useNativeDriver: true,
         }),
-      ])
+      ]),
     ).start();
 
     Animated.loop(
@@ -58,7 +60,7 @@ class MaskedViewExample extends React.Component<{}, $FlowFixMeState> {
         toValue: 360,
         timing: 2000,
         useNativeDriver: true,
-      })
+      }),
     ).start();
   }
 
@@ -66,18 +68,16 @@ class MaskedViewExample extends React.Component<{}, $FlowFixMeState> {
     return (
       <RNTesterPage title="<MaskedViewIOS>">
         <RNTesterBlock title="Basic Mask">
-          <View style={{ width: 300, height: 300, alignSelf: 'center' }}>
+          <View style={{width: 300, height: 300, alignSelf: 'center'}}>
             <MaskedViewIOS
-              style={{ flex: 1 }}
+              style={{flex: 1}}
               maskElement={
                 <View style={styles.maskContainerStyle}>
-                  <Text style={styles.maskTextStyle}>
-                    Basic Mask
-                  </Text>
+                  <Text style={styles.maskTextStyle}>Basic Mask</Text>
                 </View>
               }>
-              <View style={{ flex: 1, backgroundColor: 'blue' }} />
-              <View style={{ flex: 1, backgroundColor: 'red' }} />
+              <View style={{flex: 1, backgroundColor: 'blue'}} />
+              <View style={{flex: 1, backgroundColor: 'red'}} />
             </MaskedViewIOS>
           </View>
         </RNTesterBlock>
@@ -90,11 +90,11 @@ class MaskedViewExample extends React.Component<{}, $FlowFixMeState> {
               backgroundColor: '#eeeeee',
             }}>
             <MaskedViewIOS
-              style={{ flex: 1 }}
+              style={{flex: 1}}
               maskElement={
                 <View style={styles.maskContainerStyle}>
                   <Image
-                    style={{ height: 200, width: 200 }}
+                    style={{height: 200, width: 200}}
                     source={require('./imageMask.png')}
                   />
                 </View>
@@ -102,7 +102,7 @@ class MaskedViewExample extends React.Component<{}, $FlowFixMeState> {
               <View style={styles.maskContainerStyle}>
                 <Image
                   resizeMode="cover"
-                  style={{ width: 200, height: 200 }}
+                  style={{width: 200, height: 200}}
                   source={{
                     uri:
                       'https://38.media.tumblr.com/9e9bd08c6e2d10561dd1fb4197df4c4e/tumblr_mfqekpMktw1rn90umo1_500.gif',
@@ -113,18 +113,16 @@ class MaskedViewExample extends React.Component<{}, $FlowFixMeState> {
           </View>
         </RNTesterBlock>
         <RNTesterBlock title="Animated Mask">
-          <View style={{ width: 300, height: 300, alignSelf: 'center' }}>
+          <View style={{width: 300, height: 300, alignSelf: 'center'}}>
             <MaskedViewIOS
-              style={{ flex: 1 }}
+              style={{flex: 1}}
               maskElement={
                 <Animated.View
                   style={[
                     styles.maskContainerStyle,
-                    { transform: [{ scale: this._maskScaleAnimatedValue }] },
+                    {transform: [{scale: this._maskScaleAnimatedValue}]},
                   ]}>
-                  <Text style={styles.maskTextStyle}>
-                    Basic Mask
-                  </Text>
+                  <Text style={styles.maskTextStyle}>Basic Mask</Text>
                 </Animated.View>
               }>
               <Animated.View
@@ -139,33 +137,25 @@ class MaskedViewExample extends React.Component<{}, $FlowFixMeState> {
                     },
                   ],
                 }}>
-                <View style={{ flex: 1, backgroundColor: 'blue' }} />
-                <View style={{ flex: 1, backgroundColor: 'red' }} />
+                <View style={{flex: 1, backgroundColor: 'blue'}} />
+                <View style={{flex: 1, backgroundColor: 'red'}} />
               </Animated.View>
             </MaskedViewIOS>
           </View>
         </RNTesterBlock>
         <RNTesterBlock title="Mask w/ Changing Children">
-          <View style={{ width: 300, height: 300, alignSelf: 'center' }}>
+          <View style={{width: 300, height: 300, alignSelf: 'center'}}>
             <MaskedViewIOS
-              style={{ flex: 1 }}
+              style={{flex: 1}}
               maskElement={
                 <View style={styles.maskContainerStyle}>
-                  <Text style={styles.maskTextStyle}>
-                    Basic Mask
-                  </Text>
+                  <Text style={styles.maskTextStyle}>Basic Mask</Text>
                 </View>
               }>
               {this.state.alternateChildren
                 ? [
-                    <View
-                      key={1}
-                      style={{ flex: 1, backgroundColor: 'blue' }}
-                    />,
-                    <View
-                      key={2}
-                      style={{ flex: 1, backgroundColor: 'red' }}
-                    />,
+                    <View key={1} style={{flex: 1, backgroundColor: 'blue'}} />,
+                    <View key={2} style={{flex: 1, backgroundColor: 'red'}} />,
                   ]
                 : null}
             </MaskedViewIOS>
diff --git a/RNTester/js/ModalExample.js b/RNTester/js/ModalExample.js
index eba8a646cfc9..cfb51abe6297 100644
--- a/RNTester/js/ModalExample.js
+++ b/RNTester/js/ModalExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -52,7 +54,9 @@ class Button extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
         onShowUnderlay={this._onHighlight}
         style={[styles.button, this.props.style]}
         underlayColor="#a9d9d4">
-          <Text style={[styles.buttonText, colorStyle]}>{this.props.children}</Text>
+        <Text style={[styles.buttonText, colorStyle]}>
+          {this.props.children}
+        </Text>
       </TouchableHighlight>
     );
   }
@@ -77,11 +81,11 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
     currentOrientation: 'unknown',
   };
 
-  _setModalVisible = (visible) => {
+  _setModalVisible = visible => {
     this.setState({modalVisible: visible});
   };
 
-  _setAnimationType = (type) => {
+  _setAnimationType = type => {
     this.setState({animationType: type});
   };
 
@@ -94,19 +98,24 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
       return null;
     }
     return (
-      <Switch value={this.state.transparent} onValueChange={this._toggleTransparent} />
+      <Switch
+        value={this.state.transparent}
+        onValueChange={this._toggleTransparent}
+      />
     );
   }
 
   render() {
     var modalBackgroundStyle = {
-      backgroundColor: this.state.transparent ? 'rgba(0, 0, 0, 0.5)' : '#f5fcff',
+      backgroundColor: this.state.transparent
+        ? 'rgba(0, 0, 0, 0.5)'
+        : '#f5fcff',
     };
     var innerContainerTransparentStyle = this.state.transparent
       ? {backgroundColor: '#fff', padding: 20}
       : null;
     var activeButtonStyle = {
-      backgroundColor: '#ddd'
+      backgroundColor: '#ddd',
     };
 
     return (
@@ -117,13 +126,26 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
           transparent={this.state.transparent}
           visible={this.state.modalVisible}
           onRequestClose={() => this._setModalVisible(false)}
-          supportedOrientations={supportedOrientationsPickerValues[this.state.selectedSupportedOrientation]}
-          onOrientationChange={evt => this.setState({currentOrientation: evt.nativeEvent.orientation})}
-          >
+          supportedOrientations={
+            supportedOrientationsPickerValues[
+              this.state.selectedSupportedOrientation
+            ]
+          }
+          onOrientationChange={evt =>
+            this.setState({currentOrientation: evt.nativeEvent.orientation})
+          }>
           <View style={[styles.container, modalBackgroundStyle]}>
-            <View style={[styles.innerContainer, innerContainerTransparentStyle]}>
-              <Text>This modal was presented {this.state.animationType === 'none' ? 'without' : 'with'} animation.</Text>
-              <Text>It is currently displayed in {this.state.currentOrientation} mode.</Text>
+            <View
+              style={[styles.innerContainer, innerContainerTransparentStyle]}>
+              <Text>
+                This modal was presented{' '}
+                {this.state.animationType === 'none' ? 'without' : 'with'}{' '}
+                animation.
+              </Text>
+              <Text>
+                It is currently displayed in {this.state.currentOrientation}{' '}
+                mode.
+              </Text>
               <Button
                 onPress={this._setModalVisible.bind(this, false)}
                 style={styles.modalButton}>
@@ -134,13 +156,25 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
         </Modal>
         <View style={styles.row}>
           <Text style={styles.rowTitle}>Animation Type</Text>
-          <Button onPress={this._setAnimationType.bind(this, 'none')} style={this.state.animationType === 'none' ? activeButtonStyle : {}}>
+          <Button
+            onPress={this._setAnimationType.bind(this, 'none')}
+            style={
+              this.state.animationType === 'none' ? activeButtonStyle : {}
+            }>
             none
           </Button>
-          <Button onPress={this._setAnimationType.bind(this, 'slide')} style={this.state.animationType === 'slide' ? activeButtonStyle : {}}>
+          <Button
+            onPress={this._setAnimationType.bind(this, 'slide')}
+            style={
+              this.state.animationType === 'slide' ? activeButtonStyle : {}
+            }>
             slide
           </Button>
-          <Button onPress={this._setAnimationType.bind(this, 'fade')} style={this.state.animationType === 'fade' ? activeButtonStyle : {}}>
+          <Button
+            onPress={this._setAnimationType.bind(this, 'fade')}
+            style={
+              this.state.animationType === 'fade' ? activeButtonStyle : {}
+            }>
             fade
           </Button>
         </View>
@@ -166,9 +200,10 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
           <Text style={styles.rowTitle}>Presentation style</Text>
           <Picker
             selectedValue={this.state.presentationStyle}
-            onValueChange={(presentationStyle) => this.setState({presentationStyle})}
-            itemStyle={styles.pickerItem}
-          >
+            onValueChange={presentationStyle =>
+              this.setState({presentationStyle})
+            }
+            itemStyle={styles.pickerItem}>
             <Item label="Full Screen" value="fullScreen" />
             <Item label="Page Sheet" value="pageSheet" />
             <Item label="Form Sheet" value="formSheet" />
@@ -181,9 +216,10 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
           <Text style={styles.rowTitle}>Supported orientations</Text>
           <Picker
             selectedValue={this.state.selectedSupportedOrientation}
-            onValueChange={(_, i) => this.setState({selectedSupportedOrientation: i})}
-            itemStyle={styles.pickerItem}
-            >
+            onValueChange={(_, i) =>
+              this.setState({selectedSupportedOrientation: i})
+            }
+            itemStyle={styles.pickerItem}>
             <Item label="Portrait" value={0} />
             <Item label="Landscape" value={1} />
             <Item label="Landscape left" value={2} />
@@ -197,7 +233,6 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
   }
 }
 
-
 exports.examples = [
   {
     title: 'Modal Presentation',
diff --git a/RNTester/js/MultiColumnExample.js b/RNTester/js/MultiColumnExample.js
index 52fdaa2721d4..468bc7440655 100644
--- a/RNTester/js/MultiColumnExample.js
+++ b/RNTester/js/MultiColumnExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  FlatList,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+const {FlatList, StyleSheet, Text, View} = ReactNative;
 
 const RNTesterPage = require('./RNTesterPage');
 
@@ -33,7 +30,10 @@ const {
   renderSmallSwitchOption,
 } = require('./ListExampleShared');
 
-class MultiColumnExample extends React.PureComponent<$FlowFixMeProps, $FlowFixMeState> {
+class MultiColumnExample extends React.PureComponent<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   static title = '<FlatList> - MultiColumn';
   static description = 'Performant, scrollable grid of data.';
 
@@ -45,15 +45,16 @@ class MultiColumnExample extends React.PureComponent<$FlowFixMeProps, $FlowFixMe
     numColumns: 2,
     virtualized: true,
   };
-  _onChangeFilterText = (filterText) => {
+  _onChangeFilterText = filterText => {
     this.setState(() => ({filterText}));
   };
-  _onChangeNumColumns = (numColumns) => {
+  _onChangeNumColumns = numColumns => {
     this.setState(() => ({numColumns: Number(numColumns)}));
   };
   render() {
     const filterRegex = new RegExp(String(this.state.filterText), 'i');
-    const filter = (item) => (filterRegex.test(item.text) || filterRegex.test(item.title));
+    const filter = item =>
+      filterRegex.test(item.text) || filterRegex.test(item.title);
     const filteredData = this.state.data.filter(filter);
     return (
       <RNTesterPage
@@ -67,7 +68,7 @@ class MultiColumnExample extends React.PureComponent<$FlowFixMeProps, $FlowFixMe
               placeholder="Search..."
               value={this.state.filterText}
             />
-            <Text>   numColumns: </Text>
+            <Text> numColumns: </Text>
             <PlainInput
               clearButtonMode="never"
               onChangeText={this._onChangeNumColumns}
@@ -84,7 +85,9 @@ class MultiColumnExample extends React.PureComponent<$FlowFixMeProps, $FlowFixMe
         <FlatList
           ListFooterComponent={FooterComponent}
           ListHeaderComponent={HeaderComponent}
-          getItemLayout={this.state.fixedHeight ? this._getItemLayout : undefined}
+          getItemLayout={
+            this.state.fixedHeight ? this._getItemLayout : undefined
+          }
           data={filteredData}
           key={this.state.numColumns + (this.state.fixedHeight ? 'f' : 'v')}
           numColumns={this.state.numColumns || 1}
@@ -98,8 +101,12 @@ class MultiColumnExample extends React.PureComponent<$FlowFixMeProps, $FlowFixMe
       </RNTesterPage>
     );
   }
-  _getItemLayout(data: any, index: number): {length: number, offset: number, index: number} {
-    const length = getItemLayout(data, index).length + 2 * (CARD_MARGIN + BORDER_WIDTH);
+  _getItemLayout(
+    data: any,
+    index: number,
+  ): {length: number, offset: number, index: number} {
+    const length =
+      getItemLayout(data, index).length + 2 * (CARD_MARGIN + BORDER_WIDTH);
     return {length, offset: length * index, index};
   }
   _renderItemComponent = ({item}) => {
@@ -116,12 +123,19 @@ class MultiColumnExample extends React.PureComponent<$FlowFixMeProps, $FlowFixMe
   // This is called when items change viewability by scrolling into or out of the viewable area.
   _onViewableItemsChanged = (info: {
     changed: Array<{
-      key: string, isViewable: boolean, item: {columns: Array<*>}, index: ?number, section?: any
-    }>},
-  ) => {
+      key: string,
+      isViewable: boolean,
+      item: {columns: Array<*>},
+      index: ?number,
+      section?: any,
+    }>,
+  }) => {
     // Impressions can be logged here
     if (this.state.logViewable) {
-      infoLog('onViewableItemsChanged: ', info.changed.map((v) => ({...v, item: '...'})));
+      infoLog(
+        'onViewableItemsChanged: ',
+        info.changed.map(v => ({...v, item: '...'})),
+      );
     }
   };
   _pressItem = (key: string) => {
diff --git a/RNTester/js/NativeAnimationsExample.js b/RNTester/js/NativeAnimationsExample.js
index 52cb766c8aec..44d5416c4a3e 100644
--- a/RNTester/js/NativeAnimationsExample.js
+++ b/RNTester/js/NativeAnimationsExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -30,9 +32,10 @@ class Tester extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
   current = 0;
 
   onPress = () => {
-    const animConfig = this.current && this.props.reverseConfig
-      ? this.props.reverseConfig
-      : this.props.config;
+    const animConfig =
+      this.current && this.props.reverseConfig
+        ? this.props.reverseConfig
+        : this.props.config;
     this.current = this.current ? 0 : 1;
     const config: Object = {
       ...animConfig,
@@ -62,9 +65,7 @@ class Tester extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
           <View>
             <Text>JavaScript:</Text>
           </View>
-          <View style={styles.row}>
-            {this.props.children(this.state.js)}
-          </View>
+          <View style={styles.row}>{this.props.children(this.state.js)}</View>
         </View>
       </TouchableWithoutFeedback>
     );
@@ -155,7 +156,10 @@ class LoopExample extends React.Component<{}, $FlowFixMeState> {
 }
 
 const RNTesterSettingSwitchRow = require('RNTesterSettingSwitchRow');
-class InternalSettings extends React.Component<{}, {busyTime: number | string, filteredStall: number}> {
+class InternalSettings extends React.Component<
+  {},
+  {busyTime: number | string, filteredStall: number},
+> {
   _stallInterval: ?number;
   render() {
     return (
@@ -170,8 +174,7 @@ class InternalSettings extends React.Component<{}, {busyTime: number | string, f
             this._stallInterval = setInterval(() => {
               const start = Date.now();
               console.warn('burn CPU');
-              while (Date.now() - start < 100) {
-              }
+              while (Date.now() - start < 100) {}
             }, 300);
           }}
           onDisable={() => {
@@ -191,8 +194,8 @@ class InternalSettings extends React.Component<{}, {busyTime: number | string, f
               onStall: ({busyTime}) =>
                 this.setState(state => ({
                   busyTime,
-                  filteredStall: (state.filteredStall || 0) * 0.97 +
-                    busyTime * 0.03,
+                  filteredStall:
+                    (state.filteredStall || 0) * 0.97 + busyTime * 0.03,
                 })),
             });
           }}
@@ -200,11 +203,12 @@ class InternalSettings extends React.Component<{}, {busyTime: number | string, f
             console.warn('Cannot disable yet....');
           }}
         />
-        {this.state &&
+        {this.state && (
           <Text>
             {`JS Stall filtered: ${Math.round(this.state.filteredStall)}, `}
             {`last: ${this.state.busyTime}`}
-          </Text>}
+          </Text>
+        )}
       </View>
     );
   }
@@ -252,7 +256,10 @@ class EventExample extends React.Component<{}, $FlowFixMeState> {
   }
 }
 
-class TrackingExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class TrackingExample extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   state = {
     native: new Animated.Value(0),
     toNative: new Animated.Value(0),
@@ -287,9 +294,15 @@ class TrackingExample extends React.Component<$FlowFixMeProps, $FlowFixMeState>
   };
 
   renderBlock = (anim, dest) => [
-    <Animated.View key="line" style={[styles.line, { transform: [{ translateX: dest }]}]}/>,
-    <Animated.View key="block" style={[styles.block, { transform: [{ translateX: anim }]}]}/>,
-  ]
+    <Animated.View
+      key="line"
+      style={[styles.line, {transform: [{translateX: dest}]}]}
+    />,
+    <Animated.View
+      key="block"
+      style={[styles.block, {transform: [{translateX: anim}]}]}
+    />,
+  ];
 
   render() {
     return (
@@ -572,7 +585,7 @@ exports.examples = [
     title: 'translateX => Animated.spring (stiffness/damping/mass)',
     render: function() {
       return (
-        <Tester type="spring" config={{stiffness: 1000, damping: 500, mass: 3 }}>
+        <Tester type="spring" config={{stiffness: 1000, damping: 500, mass: 3}}>
           {anim => (
             <Animated.View
               style={[
diff --git a/RNTester/js/NavigatorIOSBarStyleExample.js b/RNTester/js/NavigatorIOSBarStyleExample.js
index 62e331e22f5a..07ca90edc05c 100644
--- a/RNTester/js/NavigatorIOSBarStyleExample.js
+++ b/RNTester/js/NavigatorIOSBarStyleExample.js
@@ -16,19 +16,14 @@
  * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  *
+ * @format
  */
 
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  NavigatorIOS,
-  StatusBar,
-  StyleSheet,
-  Text,
-  View
-} = ReactNative;
+var {NavigatorIOS, StatusBar, StyleSheet, Text, View} = ReactNative;
 
 class EmptyPage extends React.Component<{
   text: string,
@@ -36,9 +31,7 @@ class EmptyPage extends React.Component<{
   render() {
     return (
       <View style={styles.emptyPage}>
-        <Text style={styles.emptyPageText}>
-          {this.props.text}
-        </Text>
+        <Text style={styles.emptyPageText}>{this.props.text}</Text>
       </View>
     );
   }
diff --git a/RNTester/js/NavigatorIOSColorsExample.js b/RNTester/js/NavigatorIOSColorsExample.js
index cdcf6edb7bbd..d9a7cbb29e0c 100644
--- a/RNTester/js/NavigatorIOSColorsExample.js
+++ b/RNTester/js/NavigatorIOSColorsExample.js
@@ -4,26 +4,20 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  NavigatorIOS,
-  StatusBar,
-  StyleSheet,
-  Text,
-  View
-} = ReactNative;
+var {NavigatorIOS, StatusBar, StyleSheet, Text, View} = ReactNative;
 
 class EmptyPage extends React.Component {
   render() {
     return (
       <View style={styles.emptyPage}>
-        <Text style={styles.emptyPageText}>
-          {this.props.text}
-        </Text>
+        <Text style={styles.emptyPageText}>{this.props.text}</Text>
       </View>
     );
   }
@@ -49,7 +43,8 @@ class NavigatorIOSColors extends React.Component {
             this.props.onExampleExit();
           },
           passProps: {
-            text: 'The nav bar has custom colors with tintColor, ' +
+            text:
+              'The nav bar has custom colors with tintColor, ' +
               'barTintColor and titleTextColor props.',
           },
         }}
diff --git a/RNTester/js/NavigatorIOSExample.js b/RNTester/js/NavigatorIOSExample.js
index 3712b7c4dba8..252bf0e9e965 100644
--- a/RNTester/js/NavigatorIOSExample.js
+++ b/RNTester/js/NavigatorIOSExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -28,9 +30,7 @@ class EmptyPage extends React.Component<$FlowFixMeProps> {
   render() {
     return (
       <View style={styles.emptyPage}>
-        <Text style={styles.emptyPageText}>
-          {this.props.text}
-        </Text>
+        <Text style={styles.emptyPageText}>{this.props.text}</Text>
       </View>
     );
   }
@@ -44,7 +44,7 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
     }
     return (
       <ScrollView style={styles.list}>
-        <View style={styles.line}/>
+        <View style={styles.line} />
         <View style={styles.group}>
           {this._renderRow(recurseTitle, () => {
             this.props.navigator.push({
@@ -75,7 +75,7 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
               onRightButtonPress: () => this.props.navigator.pop(),
               passProps: {
                 text: 'This page has a right button in the nav bar',
-              }
+              },
             });
           })}
           {this._renderRow('Custom Right System Button', () => {
@@ -86,7 +86,7 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
               onRightButtonPress: () => this.props.navigator.pop(),
               passProps: {
                 text: 'This page has a right system button in the nav bar',
-              }
+              },
             });
           })}
           {this._renderRow('Custom Left & Right Icons', () => {
@@ -98,7 +98,7 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
               rightButtonIcon: nativeImageSource({
                 ios: 'NavBarButtonPlus',
                 width: 17,
-                height: 17
+                height: 17,
               }),
               onRightButtonPress: () => {
                 AlertIOS.alert(
@@ -109,12 +109,13 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
                       text: 'OK',
                       onPress: () => console.log('Tapped OK'),
                     },
-                  ]
+                  ],
                 );
               },
               passProps: {
-                text: 'This page has an icon for the right button in the nav bar',
-              }
+                text:
+                  'This page has an icon for the right button in the nav bar',
+              },
             });
           })}
           {this._renderRow('Custom Left & Right System Icons', () => {
@@ -133,12 +134,13 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
                       text: 'OK',
                       onPress: () => console.log('Tapped OK'),
                     },
-                  ]
+                  ],
                 );
               },
               passProps: {
-                text: 'This page has an icon for the right button in the nav bar',
-              }
+                text:
+                  'This page has an icon for the right button in the nav bar',
+              },
             });
           })}
           {this._renderRow('Pop', () => {
@@ -150,9 +152,12 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
           {this._renderReplace()}
           {this._renderReplacePrevious()}
           {this._renderReplacePreviousAndPop()}
-          {this._renderRow('Exit NavigatorIOS Example', this.props.onExampleExit)}
+          {this._renderRow(
+            'Exit NavigatorIOS Example',
+            this.props.onExampleExit,
+          )}
         </View>
-        <View style={styles.line}/>
+        <View style={styles.line} />
       </ScrollView>
     );
   }
@@ -170,9 +175,10 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
         rightButtonTitle: 'Undo',
         onRightButtonPress: () => this.props.navigator.replace(prevRoute),
         passProps: {
-          text: 'The component is replaced, but there is currently no ' +
+          text:
+            'The component is replaced, but there is currently no ' +
             'way to change the right button or title of the current route',
-        }
+        },
       });
     });
   };
@@ -216,9 +222,7 @@ class NavigatorIOSExamplePage extends React.Component<$FlowFixMeProps> {
       <View>
         <TouchableHighlight onPress={onPress}>
           <View style={styles.row}>
-            <Text style={styles.rowText}>
-              {title}
-            </Text>
+            <Text style={styles.rowText}>{title}</Text>
           </View>
         </TouchableHighlight>
         <View style={styles.separator} />
diff --git a/RNTester/js/NetInfoExample.js b/RNTester/js/NetInfoExample.js
index b81251949dad..c3b62afdfdbe 100644
--- a/RNTester/js/NetInfoExample.js
+++ b/RNTester/js/NetInfoExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  NetInfo,
-  Text,
-  View,
-  TouchableWithoutFeedback,
-} = ReactNative;
+const {NetInfo, Text, View, TouchableWithoutFeedback} = ReactNative;
 
 class ConnectionInfoSubscription extends React.Component<{}, $FlowFixMeState> {
   state = {
@@ -23,20 +20,14 @@ class ConnectionInfoSubscription extends React.Component<{}, $FlowFixMeState> {
   };
 
   componentDidMount() {
-    NetInfo.addEventListener(
-        'change',
-        this._handleConnectionInfoChange
-    );
+    NetInfo.addEventListener('change', this._handleConnectionInfoChange);
   }
 
   componentWillUnmount() {
-    NetInfo.removeEventListener(
-        'change',
-        this._handleConnectionInfoChange
-    );
+    NetInfo.removeEventListener('change', this._handleConnectionInfoChange);
   }
 
-  _handleConnectionInfoChange = (connectionInfo) => {
+  _handleConnectionInfoChange = connectionInfo => {
     const connectionInfoHistory = this.state.connectionInfoHistory.slice();
     connectionInfoHistory.push(connectionInfo);
     this.setState({
@@ -46,9 +37,9 @@ class ConnectionInfoSubscription extends React.Component<{}, $FlowFixMeState> {
 
   render() {
     return (
-        <View>
-          <Text>{JSON.stringify(this.state.connectionInfoHistory)}</Text>
-        </View>
+      <View>
+        <Text>{JSON.stringify(this.state.connectionInfoHistory)}</Text>
+      </View>
     );
   }
 }
@@ -59,23 +50,17 @@ class ConnectionInfoCurrent extends React.Component<{}, $FlowFixMeState> {
   };
 
   componentDidMount() {
-    NetInfo.addEventListener(
-        'change',
-        this._handleConnectionInfoChange
-    );
-    NetInfo.fetch().done(
-        (connectionInfo) => { this.setState({connectionInfo}); }
-    );
+    NetInfo.addEventListener('change', this._handleConnectionInfoChange);
+    NetInfo.fetch().done(connectionInfo => {
+      this.setState({connectionInfo});
+    });
   }
 
   componentWillUnmount() {
-    NetInfo.removeEventListener(
-        'change',
-        this._handleConnectionInfoChange
-    );
+    NetInfo.removeEventListener('change', this._handleConnectionInfoChange);
   }
 
-  _handleConnectionInfoChange = (connectionInfo) => {
+  _handleConnectionInfoChange = connectionInfo => {
     this.setState({
       connectionInfo,
     });
@@ -83,9 +68,9 @@ class ConnectionInfoCurrent extends React.Component<{}, $FlowFixMeState> {
 
   render() {
     return (
-        <View>
-          <Text>{this.state.connectionInfo}</Text>
-        </View>
+      <View>
+        <Text>{this.state.connectionInfo}</Text>
+      </View>
     );
   }
 }
@@ -97,22 +82,22 @@ class IsConnected extends React.Component<{}, $FlowFixMeState> {
 
   componentDidMount() {
     NetInfo.isConnected.addEventListener(
-        'change',
-        this._handleConnectivityChange
-    );
-    NetInfo.isConnected.fetch().done(
-        (isConnected) => { this.setState({isConnected}); }
+      'change',
+      this._handleConnectivityChange,
     );
+    NetInfo.isConnected.fetch().done(isConnected => {
+      this.setState({isConnected});
+    });
   }
 
   componentWillUnmount() {
     NetInfo.isConnected.removeEventListener(
-        'change',
-        this._handleConnectivityChange
+      'change',
+      this._handleConnectivityChange,
     );
   }
 
-  _handleConnectivityChange = (isConnected) => {
+  _handleConnectivityChange = isConnected => {
     this.setState({
       isConnected,
     });
@@ -120,37 +105,40 @@ class IsConnected extends React.Component<{}, $FlowFixMeState> {
 
   render() {
     return (
-        <View>
-          <Text>{this.state.isConnected ? 'Online' : 'Offline'}</Text>
-        </View>
+      <View>
+        <Text>{this.state.isConnected ? 'Online' : 'Offline'}</Text>
+      </View>
     );
   }
 }
 
 class IsConnectionExpensive extends React.Component<{}, $FlowFixMeState> {
   state = {
-    isConnectionExpensive: (null : ?boolean),
+    isConnectionExpensive: (null: ?boolean),
   };
 
   _checkIfExpensive = () => {
-    NetInfo.isConnectionExpensive().then(
-        isConnectionExpensive => { this.setState({isConnectionExpensive}); }
-    );
+    NetInfo.isConnectionExpensive().then(isConnectionExpensive => {
+      this.setState({isConnectionExpensive});
+    });
   };
 
   render() {
     return (
-        <View>
-          <TouchableWithoutFeedback onPress={this._checkIfExpensive}>
-            <View>
-              <Text>Click to see if connection is expensive:
-                {this.state.isConnectionExpensive === true ? 'Expensive' :
-                this.state.isConnectionExpensive === false ? 'Not expensive'
-                : 'Unknown'}
-              </Text>
-            </View>
-          </TouchableWithoutFeedback>
-        </View>
+      <View>
+        <TouchableWithoutFeedback onPress={this._checkIfExpensive}>
+          <View>
+            <Text>
+              Click to see if connection is expensive:
+              {this.state.isConnectionExpensive === true
+                ? 'Expensive'
+                : this.state.isConnectionExpensive === false
+                  ? 'Not expensive'
+                  : 'Unknown'}
+            </Text>
+          </View>
+        </TouchableWithoutFeedback>
+      </View>
     );
   }
 }
@@ -161,22 +149,30 @@ exports.examples = [
   {
     title: 'NetInfo.isConnected',
     description: 'Asynchronously load and observe connectivity',
-    render(): React.Element<any> { return <IsConnected />; }
+    render(): React.Element<any> {
+      return <IsConnected />;
+    },
   },
   {
     title: 'NetInfo.update',
     description: 'Asynchronously load and observe connectionInfo',
-    render(): React.Element<any> { return <ConnectionInfoCurrent />; }
+    render(): React.Element<any> {
+      return <ConnectionInfoCurrent />;
+    },
   },
   {
     title: 'NetInfo.updateHistory',
     description: 'Observed updates to connectionInfo',
-    render(): React.Element<any> { return <ConnectionInfoSubscription />; }
+    render(): React.Element<any> {
+      return <ConnectionInfoSubscription />;
+    },
   },
   {
     platform: 'android',
     title: 'NetInfo.isConnectionExpensive (Android)',
     description: 'Asynchronously check isConnectionExpensive',
-    render(): React.Element<any> { return <IsConnectionExpensive />; }
+    render(): React.Element<any> {
+      return <IsConnectionExpensive />;
+    },
   },
 ];
diff --git a/RNTester/js/OrientationChangeExample.js b/RNTester/js/OrientationChangeExample.js
index 0c07d21a02b3..cb2bee02c33d 100644
--- a/RNTester/js/OrientationChangeExample.js
+++ b/RNTester/js/OrientationChangeExample.js
@@ -4,17 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  DeviceEventEmitter,
-  Text,
-  View,
-} = ReactNative;
+const {DeviceEventEmitter, Text, View} = ReactNative;
 
 import type EmitterSubscription from 'EmitterSubscription';
 
@@ -29,7 +27,8 @@ class OrientationChangeExample extends React.Component<{}, $FlowFixMeState> {
 
   componentDidMount() {
     this._orientationSubscription = DeviceEventEmitter.addListener(
-      'namedOrientationDidChange', this._onOrientationChange,
+      'namedOrientationDidChange',
+      this._onOrientationChange,
     );
   }
 
@@ -43,7 +42,7 @@ class OrientationChangeExample extends React.Component<{}, $FlowFixMeState> {
       orientationDegrees: orientation.rotationDegrees,
       isLandscape: orientation.isLandscape,
     });
-  }
+  };
 
   render() {
     return (
@@ -60,6 +59,8 @@ exports.examples = [
   {
     title: 'OrientationChangeExample',
     description: 'listening to device orientation changes',
-    render() { return <OrientationChangeExample />; },
+    render() {
+      return <OrientationChangeExample />;
+    },
   },
 ];
diff --git a/RNTester/js/PanResponderExample.js b/RNTester/js/PanResponderExample.js
index 598de1eac80c..8e0d44a35f2d 100644
--- a/RNTester/js/PanResponderExample.js
+++ b/RNTester/js/PanResponderExample.js
@@ -4,18 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow weak
  */
+
 'use strict';
 
 var React = require('react');
 var createReactClass = require('create-react-class');
 var ReactNative = require('react-native');
-var {
-  PanResponder,
-  StyleSheet,
-  View,
-} = ReactNative;
+var {PanResponder, StyleSheet, View} = ReactNative;
 
 var CIRCLE_SIZE = 80;
 
@@ -24,14 +22,15 @@ var PanResponderExample = createReactClass({
 
   statics: {
     title: 'PanResponder Sample',
-    description: 'Shows the use of PanResponder to provide basic gesture handling.',
+    description:
+      'Shows the use of PanResponder to provide basic gesture handling.',
   },
 
   _panResponder: {},
   _previousLeft: 0,
   _previousTop: 0,
   _circleStyles: {},
-  circle: (null : ?{ setNativeProps(props: Object): void }),
+  circle: (null: ?{setNativeProps(props: Object): void}),
 
   UNSAFE_componentWillMount: function() {
     this._panResponder = PanResponder.create({
@@ -49,7 +48,7 @@ var PanResponderExample = createReactClass({
         left: this._previousLeft,
         top: this._previousTop,
         backgroundColor: 'green',
-      }
+      },
     };
   },
 
@@ -59,10 +58,9 @@ var PanResponderExample = createReactClass({
 
   render: function() {
     return (
-      <View
-        style={styles.container}>
+      <View style={styles.container}>
         <View
-          ref={(circle) => {
+          ref={circle => {
             this.circle = circle;
           }}
           style={styles.circle}
@@ -86,12 +84,18 @@ var PanResponderExample = createReactClass({
     this.circle && this.circle.setNativeProps(this._circleStyles);
   },
 
-  _handleStartShouldSetPanResponder: function(e: Object, gestureState: Object): boolean {
+  _handleStartShouldSetPanResponder: function(
+    e: Object,
+    gestureState: Object,
+  ): boolean {
     // Should we become active when the user presses down on the circle?
     return true;
   },
 
-  _handleMoveShouldSetPanResponder: function(e: Object, gestureState: Object): boolean {
+  _handleMoveShouldSetPanResponder: function(
+    e: Object,
+    gestureState: Object,
+  ): boolean {
     // Should we become active when the user moves a touch over the circle?
     return true;
   },
diff --git a/RNTester/js/PermissionsExampleAndroid.android.js b/RNTester/js/PermissionsExampleAndroid.android.js
index 322307f32706..81a7ec5b1a6d 100644
--- a/RNTester/js/PermissionsExampleAndroid.android.js
+++ b/RNTester/js/PermissionsExampleAndroid.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -40,19 +42,34 @@ class PermissionsExample extends React.Component<{}, $FlowFixMeState> {
           style={styles.picker}
           selectedValue={this.state.permission}
           onValueChange={this._onSelectPermission.bind(this)}>
-          <Item label={PermissionsAndroid.PERMISSIONS.CAMERA} value={PermissionsAndroid.PERMISSIONS.CAMERA} />
-          <Item label={PermissionsAndroid.PERMISSIONS.READ_CALENDAR} value={PermissionsAndroid.PERMISSIONS.READ_CALENDAR} />
-          <Item label={PermissionsAndroid.PERMISSIONS.ACCESS_FINE_LOCATION} value={PermissionsAndroid.PERMISSIONS.ACCESS_FINE_LOCATION} />
+          <Item
+            label={PermissionsAndroid.PERMISSIONS.CAMERA}
+            value={PermissionsAndroid.PERMISSIONS.CAMERA}
+          />
+          <Item
+            label={PermissionsAndroid.PERMISSIONS.READ_CALENDAR}
+            value={PermissionsAndroid.PERMISSIONS.READ_CALENDAR}
+          />
+          <Item
+            label={PermissionsAndroid.PERMISSIONS.ACCESS_FINE_LOCATION}
+            value={PermissionsAndroid.PERMISSIONS.ACCESS_FINE_LOCATION}
+          />
         </Picker>
         <TouchableWithoutFeedback onPress={this._checkPermission}>
           <View>
-            <Text style={[styles.touchable, styles.text]}>Check Permission</Text>
+            <Text style={[styles.touchable, styles.text]}>
+              Check Permission
+            </Text>
           </View>
         </TouchableWithoutFeedback>
-        <Text style={styles.text}>Permission Status: {this.state.hasPermission}</Text>
+        <Text style={styles.text}>
+          Permission Status: {this.state.hasPermission}
+        </Text>
         <TouchableWithoutFeedback onPress={this._requestPermission}>
           <View>
-            <Text style={[styles.touchable, styles.text]}>Request Permission</Text>
+            <Text style={[styles.touchable, styles.text]}>
+              Request Permission
+            </Text>
           </View>
         </TouchableWithoutFeedback>
       </View>
@@ -68,25 +85,22 @@ class PermissionsExample extends React.Component<{}, $FlowFixMeState> {
   _checkPermission = async () => {
     let result = await PermissionsAndroid.check(this.state.permission);
     this.setState({
-      hasPermission: (result ? 'Granted' : 'Revoked') + ' for ' +
-        this.state.permission,
+      hasPermission:
+        (result ? 'Granted' : 'Revoked') + ' for ' + this.state.permission,
     });
   };
 
   _requestPermission = async () => {
-    let result = await PermissionsAndroid.request(
-      this.state.permission,
-      {
-        title: 'Permission Explanation',
-        message:
-          'The app needs the following permission ' + this.state.permission +
-          ' because of reasons. Please approve.'
-      },
-    );
+    let result = await PermissionsAndroid.request(this.state.permission, {
+      title: 'Permission Explanation',
+      message:
+        'The app needs the following permission ' +
+        this.state.permission +
+        ' because of reasons. Please approve.',
+    });
 
     this.setState({
-      hasPermission: result + ' for ' +
-        this.state.permission,
+      hasPermission: result + ' for ' + this.state.permission,
     });
   };
 }
@@ -94,7 +108,8 @@ class PermissionsExample extends React.Component<{}, $FlowFixMeState> {
 exports.examples = [
   {
     title: 'Permissions Example',
-    description: 'Short example of how to use the runtime permissions API introduced in Android M.',
+    description:
+      'Short example of how to use the runtime permissions API introduced in Android M.',
     render: () => <PermissionsExample />,
   },
 ];
@@ -116,5 +131,5 @@ var styles = StyleSheet.create({
   },
   picker: {
     flex: 1,
-  }
+  },
 });
diff --git a/RNTester/js/PickerExample.js b/RNTester/js/PickerExample.js
index 4bd2fd2c3622..6026ac74eb4d 100644
--- a/RNTester/js/PickerExample.js
+++ b/RNTester/js/PickerExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -14,10 +16,7 @@ const StyleSheet = require('StyleSheet');
 const RNTesterBlock = require('RNTesterBlock');
 const RNTesterPage = require('RNTesterPage');
 
-const {
-  Picker,
-  Text,
-} = ReactNative;
+const {Picker, Text} = ReactNative;
 
 const Item = Picker.Item;
 
@@ -46,7 +45,10 @@ class PickerExample extends React.Component<{}, $FlowFixMeState> {
           </Picker>
         </RNTesterBlock>
         <RNTesterBlock title="Disabled picker">
-          <Picker style={styles.picker} enabled={false} selectedValue={this.state.selected1}>
+          <Picker
+            style={styles.picker}
+            enabled={false}
+            selectedValue={this.state.selected1}>
             <Item label="hello" value="key0" />
             <Item label="world" value="key1" />
           </Picker>
@@ -77,7 +79,8 @@ class PickerExample extends React.Component<{}, $FlowFixMeState> {
             <Item label="world" value="key1" />
           </Picker>
           <Text>
-            Cannot change the value of this picker because it doesn't update selectedValue.
+            Cannot change the value of this picker because it doesn't update
+            selectedValue.
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Colorful pickers">
@@ -105,7 +108,8 @@ class PickerExample extends React.Component<{}, $FlowFixMeState> {
   }
 
   changeMode = () => {
-    const newMode = this.state.mode === Picker.MODE_DIALOG
+    const newMode =
+      this.state.mode === Picker.MODE_DIALOG
         ? Picker.MODE_DROPDOWN
         : Picker.MODE_DIALOG;
     this.setState({mode: newMode});
diff --git a/RNTester/js/PickerIOSExample.js b/RNTester/js/PickerIOSExample.js
index 4202fd517e50..0ca1f61452a9 100644
--- a/RNTester/js/PickerIOSExample.js
+++ b/RNTester/js/PickerIOSExample.js
@@ -4,17 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  PickerIOS,
-  Text,
-  View,
-} = ReactNative;
+var {PickerIOS, Text, View} = ReactNative;
 
 var PickerItemIOS = PickerIOS.Item;
 
@@ -25,7 +23,16 @@ var CAR_MAKES_AND_MODELS = {
   },
   alfa: {
     name: 'Alfa-Romeo',
-    models: ['159', '4C', 'Alfasud', 'Brera', 'GTV6', 'Giulia', 'MiTo', 'Spider'],
+    models: [
+      '159',
+      '4C',
+      'Alfasud',
+      'Brera',
+      'GTV6',
+      'Giulia',
+      'MiTo',
+      'Spider',
+    ],
   },
   aston: {
     name: 'Aston Martin',
@@ -33,7 +40,19 @@ var CAR_MAKES_AND_MODELS = {
   },
   audi: {
     name: 'Audi',
-    models: ['90', '4000', '5000', 'A3', 'A4', 'A5', 'A6', 'A7', 'A8', 'Q5', 'Q7'],
+    models: [
+      '90',
+      '4000',
+      '5000',
+      'A3',
+      'A4',
+      'A5',
+      'A6',
+      'A7',
+      'A8',
+      'Q5',
+      'Q7',
+    ],
   },
   austin: {
     name: 'Austin',
@@ -45,8 +64,15 @@ var CAR_MAKES_AND_MODELS = {
   },
   buick: {
     name: 'Buick',
-    models: ['Electra', 'LaCrosse', 'LeSabre', 'Park Avenue', 'Regal',
-             'Roadmaster', 'Skylark'],
+    models: [
+      'Electra',
+      'LaCrosse',
+      'LeSabre',
+      'Park Avenue',
+      'Regal',
+      'Roadmaster',
+      'Skylark',
+    ],
   },
   cadillac: {
     name: 'Cadillac',
@@ -54,8 +80,21 @@ var CAR_MAKES_AND_MODELS = {
   },
   chevrolet: {
     name: 'Chevrolet',
-    models: ['Astro', 'Aveo', 'Bel Air', 'Captiva', 'Cavalier', 'Chevelle',
-             'Corvair', 'Corvette', 'Cruze', 'Nova', 'SS', 'Vega', 'Volt'],
+    models: [
+      'Astro',
+      'Aveo',
+      'Bel Air',
+      'Captiva',
+      'Cavalier',
+      'Chevelle',
+      'Corvair',
+      'Corvette',
+      'Cruze',
+      'Nova',
+      'SS',
+      'Vega',
+      'Volt',
+    ],
   },
 };
 
@@ -73,8 +112,8 @@ class PickerExample extends React.Component<{}, $FlowFixMeState> {
         <Text>Please choose a make for your car:</Text>
         <PickerIOS
           selectedValue={this.state.carMake}
-          onValueChange={(carMake) => this.setState({carMake, modelIndex: 0})}>
-          {Object.keys(CAR_MAKES_AND_MODELS).map((carMake) => (
+          onValueChange={carMake => this.setState({carMake, modelIndex: 0})}>
+          {Object.keys(CAR_MAKES_AND_MODELS).map(carMake => (
             <PickerItemIOS
               key={carMake}
               value={carMake}
@@ -86,14 +125,16 @@ class PickerExample extends React.Component<{}, $FlowFixMeState> {
         <PickerIOS
           selectedValue={this.state.modelIndex}
           key={this.state.carMake}
-          onValueChange={(modelIndex) => this.setState({modelIndex})}>
-          {CAR_MAKES_AND_MODELS[this.state.carMake].models.map((modelName, modelIndex) => (
-            <PickerItemIOS
-              key={this.state.carMake + '_' + modelIndex}
-              value={modelIndex}
-              label={modelName}
-            />
-          ))}
+          onValueChange={modelIndex => this.setState({modelIndex})}>
+          {CAR_MAKES_AND_MODELS[this.state.carMake].models.map(
+            (modelName, modelIndex) => (
+              <PickerItemIOS
+                key={this.state.carMake + '_' + modelIndex}
+                value={modelIndex}
+                label={modelName}
+              />
+            ),
+          )}
         </PickerIOS>
         <Text>You selected: {selectionString}</Text>
       </View>
@@ -110,10 +151,15 @@ class PickerStyleExample extends React.Component<{}, $FlowFixMeState> {
   render() {
     return (
       <PickerIOS
-        itemStyle={{fontSize: 25, color: 'red', textAlign: 'left', fontWeight: 'bold'}}
+        itemStyle={{
+          fontSize: 25,
+          color: 'red',
+          textAlign: 'left',
+          fontWeight: 'bold',
+        }}
         selectedValue={this.state.carMake}
-        onValueChange={(carMake) => this.setState({carMake, modelIndex: 0})}>
-        {Object.keys(CAR_MAKES_AND_MODELS).map((carMake) => (
+        onValueChange={carMake => this.setState({carMake, modelIndex: 0})}>
+        {Object.keys(CAR_MAKES_AND_MODELS).map(carMake => (
           <PickerItemIOS
             key={carMake}
             value={carMake}
@@ -129,15 +175,16 @@ exports.displayName = (undefined: ?string);
 exports.title = '<PickerIOS>';
 exports.description = 'Render lists of selectable options with UIPickerView.';
 exports.examples = [
-{
-  title: '<PickerIOS>',
-  render: function(): React.Element<any> {
-    return <PickerExample />;
+  {
+    title: '<PickerIOS>',
+    render: function(): React.Element<any> {
+      return <PickerExample />;
+    },
   },
-},
-{
-  title: '<PickerIOS> with custom styling',
-  render: function(): React.Element<any> {
-    return <PickerStyleExample />;
+  {
+    title: '<PickerIOS> with custom styling',
+    render: function(): React.Element<any> {
+      return <PickerStyleExample />;
+    },
   },
-}];
+];
diff --git a/RNTester/js/PointerEventsExample.js b/RNTester/js/PointerEventsExample.js
index 1fc85702a38d..b22fb8b3324a 100644
--- a/RNTester/js/PointerEventsExample.js
+++ b/RNTester/js/PointerEventsExample.js
@@ -4,24 +4,22 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, View} = ReactNative;
 
 class ExampleBox extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
   state = {
     log: [],
   };
 
-  handleLog = (msg) => {
+  handleLog = msg => {
     this.state.log = this.state.log.concat([msg]);
   };
 
@@ -48,8 +46,7 @@ class ExampleBox extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
             * React. To see the error delete this comment and run Flow. */}
           <this.props.Component onLog={this.handleLog} />
         </View>
-        <View
-          style={styles.logBox}>
+        <View style={styles.logBox}>
           <DemoText style={styles.logText}>
             {this.state.log.join('\n')}
           </DemoText>
@@ -65,9 +62,7 @@ class NoneExample extends React.Component<$FlowFixMeProps> {
       <View
         onTouchStart={() => this.props.onLog('A unspecified touched')}
         style={styles.box}>
-        <DemoText style={styles.text}>
-          A: unspecified
-        </DemoText>
+        <DemoText style={styles.text}>A: unspecified</DemoText>
         <View
           pointerEvents="none"
           onTouchStart={() => this.props.onLog('B none touched')}
@@ -96,10 +91,7 @@ class DemoText extends React.Component<$FlowFixMeProps> {
   render() {
     return (
       <View pointerEvents="none">
-        <Text
-          style={this.props.style}>
-          {this.props.children}
-        </Text>
+        <Text style={this.props.style}>{this.props.children}</Text>
       </View>
     );
   }
@@ -111,9 +103,7 @@ class BoxNoneExample extends React.Component<$FlowFixMeProps> {
       <View
         onTouchStart={() => this.props.onLog('A unspecified touched')}
         style={styles.box}>
-        <DemoText style={styles.text}>
-          A: unspecified
-        </DemoText>
+        <DemoText style={styles.text}>A: unspecified</DemoText>
         <View
           pointerEvents="box-none"
           onTouchStart={() => this.props.onLog('B box-none touched')}
@@ -124,17 +114,15 @@ class BoxNoneExample extends React.Component<$FlowFixMeProps> {
           <View
             onTouchStart={() => this.props.onLog('C unspecified touched')}
             style={styles.box}>
-            <DemoText style={styles.text}>
-              C: unspecified
-            </DemoText>
+            <DemoText style={styles.text}>C: unspecified</DemoText>
           </View>
           <View
             pointerEvents="auto"
-            onTouchStart={() => this.props.onLog('C explicitly unspecified touched')}
+            onTouchStart={() =>
+              this.props.onLog('C explicitly unspecified touched')
+            }
             style={[styles.box]}>
-            <DemoText style={[styles.text]}>
-              C: explicitly unspecified
-            </DemoText>
+            <DemoText style={[styles.text]}>C: explicitly unspecified</DemoText>
           </View>
         </View>
       </View>
@@ -148,16 +136,12 @@ class BoxOnlyExample extends React.Component<$FlowFixMeProps> {
       <View
         onTouchStart={() => this.props.onLog('A unspecified touched')}
         style={styles.box}>
-        <DemoText style={styles.text}>
-          A: unspecified
-        </DemoText>
+        <DemoText style={styles.text}>A: unspecified</DemoText>
         <View
           pointerEvents="box-only"
           onTouchStart={() => this.props.onLog('B box-only touched')}
           style={styles.box}>
-          <DemoText style={styles.text}>
-            B: box-only
-          </DemoText>
+          <DemoText style={styles.text}>B: box-only</DemoText>
           <View
             onTouchStart={() => this.props.onLog('C unspecified touched')}
             style={[styles.box, styles.boxPassedThrough]}>
@@ -167,7 +151,9 @@ class BoxOnlyExample extends React.Component<$FlowFixMeProps> {
           </View>
           <View
             pointerEvents="auto"
-            onTouchStart={() => this.props.onLog('C explicitly unspecified touched')}
+            onTouchStart={() =>
+              this.props.onLog('C explicitly unspecified touched')
+            }
             style={[styles.box, styles.boxPassedThrough]}>
             <DemoText style={[styles.text, styles.textPassedThrough]}>
               C: explicitly unspecified
@@ -189,21 +175,24 @@ var exampleClasses: Array<ExampleClass> = [
   {
     Component: NoneExample,
     title: '`none`',
-    description: '`none` causes touch events on the container and its child components to pass through to the parent container.',
+    description:
+      '`none` causes touch events on the container and its child components to pass through to the parent container.',
   },
   {
     Component: BoxNoneExample,
     title: '`box-none`',
-    description: '`box-none` causes touch events on the container to pass through and will only detect touch events on its child components.',
+    description:
+      '`box-none` causes touch events on the container to pass through and will only detect touch events on its child components.',
   },
   {
     Component: BoxOnlyExample,
     title: '`box-only`',
-    description: '`box-only` causes touch events on the container\'s child components to pass through and will only detect touch events on the container itself.',
-  }
+    description:
+      "`box-only` causes touch events on the container's child components to pass through and will only detect touch events on the container itself.",
+  },
 ];
 
-var infoToExample = (info) => {
+var infoToExample = info => {
   return {
     title: info.title,
     description: info.description,
@@ -248,7 +237,8 @@ var styles = StyleSheet.create({
 
 exports.framework = 'React';
 exports.title = 'Pointer Events';
-exports.description = 'Demonstrates the use of the pointerEvents prop of a ' +
+exports.description =
+  'Demonstrates the use of the pointerEvents prop of a ' +
   'View to control how touches should be handled.';
 /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an error
  * found when Flow v0.70 was deployed. To see the error delete this comment
diff --git a/RNTester/js/ProgressBarAndroidExample.android.js b/RNTester/js/ProgressBarAndroidExample.android.js
index 1d55779d5780..2b3d7feeafcc 100644
--- a/RNTester/js/ProgressBarAndroidExample.android.js
+++ b/RNTester/js/ProgressBarAndroidExample.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var ProgressBar = require('ProgressBarAndroid');
@@ -22,17 +24,15 @@ var MovingBar = createReactClass({
 
   getInitialState: function() {
     return {
-      progress: 0
+      progress: 0,
     };
   },
 
   componentDidMount: function() {
-    this.setInterval(
-      () => {
-        var progress = (this.state.progress + 0.02) % 1;
-        this.setState({progress: progress});
-      }, 50
-    );
+    this.setInterval(() => {
+      var progress = (this.state.progress + 0.02) % 1;
+      this.setState({progress: progress});
+    }, 50);
   },
 
   render: function() {
@@ -60,7 +60,11 @@ class ProgressBarAndroidExample extends React.Component<{}> {
         </RNTesterBlock>
 
         <RNTesterBlock title="Horizontal Blue ProgressBar">
-          <MovingBar styleAttr="Horizontal" indeterminate={false} color="blue" />
+          <MovingBar
+            styleAttr="Horizontal"
+            indeterminate={false}
+            color="blue"
+          />
         </RNTesterBlock>
       </RNTesterPage>
     );
diff --git a/RNTester/js/ProgressViewIOSExample.js b/RNTester/js/ProgressViewIOSExample.js
index 821fe2e2520e..f691d9d3f98e 100644
--- a/RNTester/js/ProgressViewIOSExample.js
+++ b/RNTester/js/ProgressViewIOSExample.js
@@ -4,18 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var createReactClass = require('create-react-class');
 var ReactNative = require('react-native');
-var {
-  ProgressViewIOS,
-  StyleSheet,
-  View,
-} = ReactNative;
+var {ProgressViewIOS, StyleSheet, View} = ReactNative;
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
@@ -37,7 +35,7 @@ var ProgressViewExample = createReactClass({
 
   updateProgress() {
     var progress = this.state.progress + 0.01;
-    this.setState({ progress });
+    this.setState({progress});
     this.requestAnimationFrame(() => this.updateProgress());
   },
 
@@ -49,11 +47,30 @@ var ProgressViewExample = createReactClass({
   render() {
     return (
       <View style={styles.container}>
-        <ProgressViewIOS style={styles.progressView} progress={this.getProgress(0)}/>
-        <ProgressViewIOS style={styles.progressView} progressTintColor="purple" progress={this.getProgress(0.2)}/>
-        <ProgressViewIOS style={styles.progressView} progressTintColor="red" progress={this.getProgress(0.4)}/>
-        <ProgressViewIOS style={styles.progressView} progressTintColor="orange" progress={this.getProgress(0.6)}/>
-        <ProgressViewIOS style={styles.progressView} progressTintColor="yellow" progress={this.getProgress(0.8)}/>
+        <ProgressViewIOS
+          style={styles.progressView}
+          progress={this.getProgress(0)}
+        />
+        <ProgressViewIOS
+          style={styles.progressView}
+          progressTintColor="purple"
+          progress={this.getProgress(0.2)}
+        />
+        <ProgressViewIOS
+          style={styles.progressView}
+          progressTintColor="red"
+          progress={this.getProgress(0.4)}
+        />
+        <ProgressViewIOS
+          style={styles.progressView}
+          progressTintColor="orange"
+          progress={this.getProgress(0.6)}
+        />
+        <ProgressViewIOS
+          style={styles.progressView}
+          progressTintColor="yellow"
+          progress={this.getProgress(0.8)}
+        />
       </View>
     );
   },
@@ -63,14 +80,14 @@ exports.displayName = (undefined: ?string);
 exports.framework = 'React';
 exports.title = 'ProgressViewIOS';
 exports.description = 'ProgressViewIOS';
-exports.examples = [{
-  title: 'ProgressViewIOS',
-  render() {
-    return (
-      <ProgressViewExample/>
-    );
-  }
-}];
+exports.examples = [
+  {
+    title: 'ProgressViewIOS',
+    render() {
+      return <ProgressViewExample />;
+    },
+  },
+];
 
 var styles = StyleSheet.create({
   container: {
@@ -79,5 +96,5 @@ var styles = StyleSheet.create({
   },
   progressView: {
     marginTop: 20,
-  }
+  },
 });
diff --git a/RNTester/js/PushNotificationIOSExample.js b/RNTester/js/PushNotificationIOSExample.js
index b2c54165a1c5..f4e86ef5dddd 100644
--- a/RNTester/js/PushNotificationIOSExample.js
+++ b/RNTester/js/PushNotificationIOSExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -26,9 +28,7 @@ class Button extends React.Component<$FlowFixMeProps> {
         underlayColor={'white'}
         style={styles.button}
         onPress={this.props.onPress}>
-        <Text style={styles.buttonLabel}>
-          {this.props.label}
-        </Text>
+        <Text style={styles.buttonLabel}>{this.props.label}</Text>
       </TouchableHighlight>
     );
   }
@@ -37,18 +37,36 @@ class Button extends React.Component<$FlowFixMeProps> {
 class NotificationExample extends React.Component<{}> {
   UNSAFE_componentWillMount() {
     PushNotificationIOS.addEventListener('register', this._onRegistered);
-    PushNotificationIOS.addEventListener('registrationError', this._onRegistrationError);
-    PushNotificationIOS.addEventListener('notification', this._onRemoteNotification);
-    PushNotificationIOS.addEventListener('localNotification', this._onLocalNotification);
+    PushNotificationIOS.addEventListener(
+      'registrationError',
+      this._onRegistrationError,
+    );
+    PushNotificationIOS.addEventListener(
+      'notification',
+      this._onRemoteNotification,
+    );
+    PushNotificationIOS.addEventListener(
+      'localNotification',
+      this._onLocalNotification,
+    );
 
     PushNotificationIOS.requestPermissions();
   }
 
   componentWillUnmount() {
     PushNotificationIOS.removeEventListener('register', this._onRegistered);
-    PushNotificationIOS.removeEventListener('registrationError', this._onRegistrationError);
-    PushNotificationIOS.removeEventListener('notification', this._onRemoteNotification);
-    PushNotificationIOS.removeEventListener('localNotification', this._onLocalNotification);
+    PushNotificationIOS.removeEventListener(
+      'registrationError',
+      this._onRegistrationError,
+    );
+    PushNotificationIOS.removeEventListener(
+      'notification',
+      this._onRemoteNotification,
+    );
+    PushNotificationIOS.removeEventListener(
+      'localNotification',
+      this._onLocalNotification,
+    );
   }
 
   render() {
@@ -86,7 +104,7 @@ class NotificationExample extends React.Component<{}> {
         alert: 'Sample local notification',
         badge: '+1',
         sound: 'default',
-        category: 'REACT_NATIVE'
+        category: 'REACT_NATIVE',
       },
     });
   }
@@ -95,10 +113,12 @@ class NotificationExample extends React.Component<{}> {
     AlertIOS.alert(
       'Registered For Remote Push',
       `Device Token: ${deviceToken}`,
-      [{
-        text: 'Dismiss',
-        onPress: null,
-      }]
+      [
+        {
+          text: 'Dismiss',
+          onPress: null,
+        },
+      ],
     );
   }
 
@@ -106,10 +126,12 @@ class NotificationExample extends React.Component<{}> {
     AlertIOS.alert(
       'Failed To Register For Remote Push',
       `Error (${error.code}): ${error.message}`,
-      [{
-        text: 'Dismiss',
-        onPress: null,
-      }]
+      [
+        {
+          text: 'Dismiss',
+          onPress: null,
+        },
+      ],
     );
   }
 
@@ -120,29 +142,32 @@ class NotificationExample extends React.Component<{}> {
       category: ${notification.getCategory()};\n
       content-available: ${notification.getContentAvailable()}.`;
 
-    AlertIOS.alert(
-      'Push Notification Received',
-      result,
-      [{
+    AlertIOS.alert('Push Notification Received', result, [
+      {
         text: 'Dismiss',
         onPress: null,
-      }]
-    );
+      },
+    ]);
   }
 
-  _onLocalNotification(notification){
+  _onLocalNotification(notification) {
     AlertIOS.alert(
       'Local Notification Received',
       'Alert message: ' + notification.getMessage(),
-      [{
-        text: 'Dismiss',
-        onPress: null,
-      }]
+      [
+        {
+          text: 'Dismiss',
+          onPress: null,
+        },
+      ],
     );
   }
 }
 
-class NotificationPermissionExample extends React.Component<$FlowFixMeProps, any> {
+class NotificationPermissionExample extends React.Component<
+  $FlowFixMeProps,
+  any,
+> {
   constructor(props) {
     super(props);
     this.state = {permissions: null};
@@ -155,15 +180,13 @@ class NotificationPermissionExample extends React.Component<$FlowFixMeProps, any
           onPress={this._showPermissions.bind(this)}
           label="Show enabled permissions"
         />
-        <Text>
-          {JSON.stringify(this.state.permissions)}
-        </Text>
+        <Text>{JSON.stringify(this.state.permissions)}</Text>
       </View>
     );
   }
 
   _showPermissions() {
-    PushNotificationIOS.checkPermissions((permissions) => {
+    PushNotificationIOS.checkPermissions(permissions => {
       this.setState({permissions});
     });
   }
@@ -183,32 +206,35 @@ var styles = StyleSheet.create({
 exports.title = 'PushNotificationIOS';
 exports.description = 'Apple PushNotification and badge value';
 exports.examples = [
-{
-  title: 'Badge Number',
-  render(): React.Element<any> {
-    return (
-      <View>
-        <Button
-          onPress={() => PushNotificationIOS.setApplicationIconBadgeNumber(42)}
-          label="Set app's icon badge to 42"
-        />
-        <Button
-          onPress={() => PushNotificationIOS.setApplicationIconBadgeNumber(0)}
-          label="Clear app's icon badge"
-        />
-      </View>
-    );
+  {
+    title: 'Badge Number',
+    render(): React.Element<any> {
+      return (
+        <View>
+          <Button
+            onPress={() =>
+              PushNotificationIOS.setApplicationIconBadgeNumber(42)
+            }
+            label="Set app's icon badge to 42"
+          />
+          <Button
+            onPress={() => PushNotificationIOS.setApplicationIconBadgeNumber(0)}
+            label="Clear app's icon badge"
+          />
+        </View>
+      );
+    },
   },
-},
-{
-  title: 'Push Notifications',
-  render(): React.Element<any> {
-    return <NotificationExample />;
-  }
-},
-{
-  title: 'Notifications Permissions',
-  render(): React.Element<any> {
-    return <NotificationPermissionExample />;
-  }
-}];
+  {
+    title: 'Push Notifications',
+    render(): React.Element<any> {
+      return <NotificationExample />;
+    },
+  },
+  {
+    title: 'Notifications Permissions',
+    render(): React.Element<any> {
+      return <NotificationPermissionExample />;
+    },
+  },
+];
diff --git a/RNTester/js/RCTRootViewIOSExample.js b/RNTester/js/RCTRootViewIOSExample.js
index 5eba0e8cae70..0314507bc5b5 100644
--- a/RNTester/js/RCTRootViewIOSExample.js
+++ b/RNTester/js/RCTRootViewIOSExample.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -11,22 +12,21 @@
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+const {StyleSheet, Text, View} = ReactNative;
 
 const requireNativeComponent = require('requireNativeComponent');
 
 class AppPropertiesUpdateExample extends React.Component<{}> {
   render() {
     // Do not require this unless we are actually rendering.
-    const UpdatePropertiesExampleView = requireNativeComponent('UpdatePropertiesExampleView');
+    const UpdatePropertiesExampleView = requireNativeComponent(
+      'UpdatePropertiesExampleView',
+    );
     return (
       <View style={styles.container}>
         <Text style={styles.text}>
-          Press the button to update the field below by passing new properties to the RN app.
+          Press the button to update the field below by passing new properties
+          to the RN app.
         </Text>
         <UpdatePropertiesExampleView style={styles.nativeView}>
           <Text style={styles.text}>
@@ -41,11 +41,14 @@ class AppPropertiesUpdateExample extends React.Component<{}> {
 class RootViewSizeFlexibilityExample extends React.Component<{}> {
   render() {
     // Do not require this unless we are actually rendering.
-    const FlexibleSizeExampleView = requireNativeComponent('FlexibleSizeExampleView');
+    const FlexibleSizeExampleView = requireNativeComponent(
+      'FlexibleSizeExampleView',
+    );
     return (
       <View style={styles.container}>
         <Text style={styles.text}>
-          Press the button to resize it. On resize, RCTRootViewDelegate is notified. You can use it to handle content size updates.
+          Press the button to resize it. On resize, RCTRootViewDelegate is
+          notified. You can use it to handle content size updates.
         </Text>
         <FlexibleSizeExampleView style={styles.nativeView}>
           <Text style={styles.text}>
@@ -63,30 +66,28 @@ const styles = StyleSheet.create({
     backgroundColor: '#F5FCFF',
   },
   text: {
-    marginBottom: 20
+    marginBottom: 20,
   },
   nativeView: {
     height: 140,
-    width: 280
-  }
+    width: 280,
+  },
 });
 
 exports.title = 'RCTRootView';
-exports.description = 'Examples that show useful methods when embedding React Native in a native application';
+exports.description =
+  'Examples that show useful methods when embedding React Native in a native application';
 exports.examples = [
-{
-  title: 'Updating app properties in runtime',
-  render(): React.Element<any> {
-    return (
-      <AppPropertiesUpdateExample/>
-    );
+  {
+    title: 'Updating app properties in runtime',
+    render(): React.Element<any> {
+      return <AppPropertiesUpdateExample />;
+    },
   },
-},
-{
-  title: 'RCTRootView\'s size flexibility',
-  render(): React.Element<any> {
-    return (
-      <RootViewSizeFlexibilityExample/>
-    );
+  {
+    title: "RCTRootView's size flexibility",
+    render(): React.Element<any> {
+      return <RootViewSizeFlexibilityExample />;
+    },
   },
-}];
+];
diff --git a/RNTester/js/RNTesterActions.js b/RNTester/js/RNTesterActions.js
index cc89277dcf9c..69fc8b9ea5cc 100644
--- a/RNTester/js/RNTesterActions.js
+++ b/RNTester/js/RNTesterActions.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 export type RNTesterBackAction = {
@@ -21,12 +23,10 @@ export type RNTesterExampleAction = {
   openExample: string,
 };
 
-export type RNTesterAction = (
-  RNTesterBackAction |
-  RNTesterListAction |
-  RNTesterExampleAction
-);
-
+export type RNTesterAction =
+  | RNTesterBackAction
+  | RNTesterListAction
+  | RNTesterExampleAction;
 
 function Back(): RNTesterBackAction {
   return {
diff --git a/RNTester/js/RNTesterApp.android.js b/RNTester/js/RNTesterApp.android.js
index ad377b85a54f..42c43b81aa8c 100644
--- a/RNTester/js/RNTesterApp.android.js
+++ b/RNTester/js/RNTesterApp.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const AppRegistry = require('AppRegistry');
@@ -29,7 +31,7 @@ const View = require('View');
 
 const nativeImageSource = require('nativeImageSource');
 
-import type { RNTesterNavigationState } from './RNTesterNavigationReducer';
+import type {RNTesterNavigationState} from './RNTesterNavigationReducer';
 
 UIManager.setLayoutAnimationEnabledExperimental(true);
 
@@ -44,24 +46,29 @@ const APP_STATE_KEY = 'RNTesterAppState.v2';
 const HEADER_LOGO_ICON = nativeImageSource({
   android: 'launcher_icon',
   width: 132,
-  height: 144
+  height: 144,
 });
 
 const HEADER_NAV_ICON = nativeImageSource({
   android: 'ic_menu_black_24dp',
   width: 48,
-  height: 48
+  height: 48,
 });
 
 class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
   UNSAFE_componentWillMount() {
-    BackHandler.addEventListener('hardwareBackPress', this._handleBackButtonPress);
+    BackHandler.addEventListener(
+      'hardwareBackPress',
+      this._handleBackButtonPress,
+    );
   }
 
   componentDidMount() {
-    Linking.getInitialURL().then((url) => {
+    Linking.getInitialURL().then(url => {
       AsyncStorage.getItem(APP_STATE_KEY, (err, storedString) => {
-        const exampleAction = URIActionMap(this.props.exampleFromAppetizeParams);
+        const exampleAction = URIActionMap(
+          this.props.exampleFromAppetizeParams,
+        );
         const urlAction = URIActionMap(url);
         const launchAction = exampleAction || urlAction;
         if (err || !storedString) {
@@ -94,7 +101,9 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
         onDrawerClose={() => {
           this._overrideBackPressForDrawerLayout = false;
         }}
-        ref={(drawer) => { this.drawer = drawer; }}
+        ref={drawer => {
+          this.drawer = drawer;
+        }}
         renderNavigationView={this._renderDrawerContent}
         statusBarBackgroundColor="#589c90">
         {this._renderApp()}
@@ -116,9 +125,7 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
   };
 
   _renderApp() {
-    const {
-      openExample,
-    } = this.state;
+    const {openExample} = this.state;
 
     if (openExample) {
       const ExampleModule = RNTesterList.Modules[openExample];
@@ -128,7 +135,9 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
             onExampleExit={() => {
               this._handleAction(RNTesterActions.Back());
             }}
-            ref={(example) => { this._exampleRef = example; }}
+            ref={example => {
+              this._exampleRef = example;
+            }}
           />
         );
       } else if (ExampleModule) {
@@ -143,7 +152,9 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
             />
             <RNTesterExampleContainer
               module={ExampleModule}
-              ref={(example) => { this._exampleRef = example; }}
+              ref={example => {
+                this._exampleRef = example;
+              }}
             />
           </View>
         );
@@ -171,9 +182,8 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
     this.drawer && this.drawer.closeDrawer();
     const newState = RNTesterNavigationReducer(this.state, action);
     if (this.state !== newState) {
-      this.setState(
-        newState,
-        () => AsyncStorage.setItem(APP_STATE_KEY, JSON.stringify(this.state))
+      this.setState(newState, () =>
+        AsyncStorage.setItem(APP_STATE_KEY, JSON.stringify(this.state)),
       );
       return true;
     }
diff --git a/RNTester/js/RNTesterApp.ios.js b/RNTester/js/RNTesterApp.ios.js
index a72ebb724edb..7d5b1a1b2391 100644
--- a/RNTester/js/RNTesterApp.ios.js
+++ b/RNTester/js/RNTesterApp.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const AsyncStorage = require('AsyncStorage');
@@ -27,12 +29,12 @@ const {
   StyleSheet,
   Text,
   View,
-  SafeAreaView
+  SafeAreaView,
 } = ReactNative;
 
-import type { RNTesterExample } from './RNTesterList.ios';
-import type { RNTesterAction } from './RNTesterActions';
-import type { RNTesterNavigationState } from './RNTesterNavigationReducer';
+import type {RNTesterExample} from './RNTesterList.ios';
+import type {RNTesterAction} from './RNTesterActions';
+import type {RNTesterNavigationState} from './RNTesterNavigationReducer';
 
 type Props = {
   exampleFromAppetizeParams: string,
@@ -40,15 +42,17 @@ type Props = {
 
 const APP_STATE_KEY = 'RNTesterAppState.v2';
 
-const Header = ({ onBack, title }: { onBack?: () => mixed, title: string }) => (
+const Header = ({onBack, title}: {onBack?: () => mixed, title: string}) => (
   <SafeAreaView style={styles.headerContainer}>
     <View style={styles.header}>
       <View style={styles.headerCenter}>
         <Text style={styles.title}>{title}</Text>
       </View>
-      {onBack && <View style={styles.headerLeft}>
-        <Button title="Back" onPress={onBack} />
-      </View>}
+      {onBack && (
+        <View style={styles.headerLeft}>
+          <Button title="Back" onPress={onBack} />
+        </View>
+      )}
     </View>
   </SafeAreaView>
 );
@@ -59,9 +63,11 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
   }
 
   componentDidMount() {
-    Linking.getInitialURL().then((url) => {
+    Linking.getInitialURL().then(url => {
       AsyncStorage.getItem(APP_STATE_KEY, (err, storedString) => {
-        const exampleAction = URIActionMap(this.props.exampleFromAppetizeParams);
+        const exampleAction = URIActionMap(
+          this.props.exampleFromAppetizeParams,
+        );
         const urlAction = URIActionMap(url);
         const launchAction = exampleAction || urlAction;
         if (err || !storedString) {
@@ -78,14 +84,14 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
       });
     });
 
-    Linking.addEventListener('url', (url) => {
+    Linking.addEventListener('url', url => {
       this._handleAction(URIActionMap(url));
     });
   }
 
   _handleBack = () => {
     this._handleAction(RNTesterActions.Back());
-  }
+  };
 
   _handleAction = (action: ?RNTesterAction) => {
     if (!action) {
@@ -93,12 +99,11 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
     }
     const newState = RNTesterNavigationReducer(this.state, action);
     if (this.state !== newState) {
-      this.setState(
-        newState,
-        () => AsyncStorage.setItem(APP_STATE_KEY, JSON.stringify(this.state))
+      this.setState(newState, () =>
+        AsyncStorage.setItem(APP_STATE_KEY, JSON.stringify(this.state)),
       );
     }
-  }
+  };
 
   render() {
     if (!this.state) {
@@ -107,11 +112,7 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
     if (this.state.openExample) {
       const Component = RNTesterList.Modules[this.state.openExample];
       if (Component.external) {
-        return (
-          <Component
-            onExampleExit={this._handleBack}
-          />
-        );
+        return <Component onExampleExit={this._handleBack} />;
       } else {
         return (
           <View style={styles.exampleContainer}>
@@ -120,7 +121,6 @@ class RNTesterApp extends React.Component<Props, RNTesterNavigationState> {
           </View>
         );
       }
-
     }
     return (
       <View style={styles.exampleContainer}>
@@ -145,10 +145,9 @@ const styles = StyleSheet.create({
   },
   header: {
     height: 40,
-    flexDirection: 'row'
-  },
-  headerLeft: {
+    flexDirection: 'row',
   },
+  headerLeft: {},
   headerCenter: {
     flex: 1,
     position: 'absolute',
@@ -166,26 +165,35 @@ const styles = StyleSheet.create({
   },
 });
 
-AppRegistry.registerComponent('SetPropertiesExampleApp', () => require('./SetPropertiesExampleApp'));
-AppRegistry.registerComponent('RootViewSizeFlexibilityExampleApp', () => require('./RootViewSizeFlexibilityExampleApp'));
+AppRegistry.registerComponent('SetPropertiesExampleApp', () =>
+  require('./SetPropertiesExampleApp'),
+);
+AppRegistry.registerComponent('RootViewSizeFlexibilityExampleApp', () =>
+  require('./RootViewSizeFlexibilityExampleApp'),
+);
 AppRegistry.registerComponent('RNTesterApp', () => RNTesterApp);
 
 // Register suitable examples for snapshot tests
-RNTesterList.ComponentExamples.concat(RNTesterList.APIExamples).forEach((Example: RNTesterExample) => {
-  const ExampleModule = Example.module;
-  if (ExampleModule.displayName) {
-    class Snapshotter extends React.Component<{}> {
-      render() {
-        return (
-          <SnapshotViewIOS>
-            <RNTesterExampleContainer module={ExampleModule} />
-          </SnapshotViewIOS>
-        );
+RNTesterList.ComponentExamples.concat(RNTesterList.APIExamples).forEach(
+  (Example: RNTesterExample) => {
+    const ExampleModule = Example.module;
+    if (ExampleModule.displayName) {
+      class Snapshotter extends React.Component<{}> {
+        render() {
+          return (
+            <SnapshotViewIOS>
+              <RNTesterExampleContainer module={ExampleModule} />
+            </SnapshotViewIOS>
+          );
+        }
       }
-    }
 
-    AppRegistry.registerComponent(ExampleModule.displayName, () => Snapshotter);
-  }
-});
+      AppRegistry.registerComponent(
+        ExampleModule.displayName,
+        () => Snapshotter,
+      );
+    }
+  },
+);
 
 module.exports = RNTesterApp;
diff --git a/RNTester/js/RNTesterBlock.js b/RNTester/js/RNTesterBlock.js
index fa3c44f7873b..591b26b68a67 100644
--- a/RNTester/js/RNTesterBlock.js
+++ b/RNTester/js/RNTesterBlock.js
@@ -4,23 +4,24 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var PropTypes = require('prop-types');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, View} = ReactNative;
 
-class RNTesterBlock extends React.Component<{
-  title?: string,
-  description?: string,
-}, $FlowFixMeState> {
+class RNTesterBlock extends React.Component<
+  {
+    title?: string,
+    description?: string,
+  },
+  $FlowFixMeState,
+> {
   static propTypes = {
     title: PropTypes.string,
     description: PropTypes.string,
@@ -31,24 +32,22 @@ class RNTesterBlock extends React.Component<{
   render() {
     var description;
     if (this.props.description) {
-      description =
-        <Text style={styles.descriptionText}>
-          {this.props.description}
-        </Text>;
+      description = (
+        <Text style={styles.descriptionText}>{this.props.description}</Text>
+      );
     }
 
     return (
       <View style={styles.container}>
         <View style={styles.titleContainer}>
-          <Text style={styles.titleText}>
-            {this.props.title}
-          </Text>
+          <Text style={styles.titleText}>{this.props.title}</Text>
           {description}
         </View>
         <View style={styles.children}>
           {
             // $FlowFixMe found when converting React.createClass to ES6
-            this.props.children}
+            this.props.children
+          }
         </View>
       </View>
     );
@@ -93,7 +92,7 @@ var styles = StyleSheet.create({
   },
   children: {
     margin: 10,
-  }
+  },
 });
 
 module.exports = RNTesterBlock;
diff --git a/RNTester/js/RNTesterButton.js b/RNTester/js/RNTesterButton.js
index 9ac5f6e8e818..57ac204b2242 100644
--- a/RNTester/js/RNTesterButton.js
+++ b/RNTester/js/RNTesterButton.js
@@ -4,18 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var PropTypes = require('prop-types');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  TouchableHighlight,
-} = ReactNative;
+var {StyleSheet, Text, TouchableHighlight} = ReactNative;
 
 class RNTesterButton extends React.Component<{onPress?: Function}> {
   static propTypes = {
@@ -31,7 +29,8 @@ class RNTesterButton extends React.Component<{onPress?: Function}> {
         <Text>
           {
             // $FlowFixMe found when converting React.createClass to ES6
-            this.props.children}
+            this.props.children
+          }
         </Text>
       </TouchableHighlight>
     );
diff --git a/RNTester/js/RNTesterExampleContainer.js b/RNTester/js/RNTesterExampleContainer.js
index 02e010771f45..0b3e3d2331b9 100644
--- a/RNTester/js/RNTesterExampleContainer.js
+++ b/RNTester/js/RNTesterExampleContainer.js
@@ -4,13 +4,13 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const React = require('react');
-const {
-  Platform,
-} = require('react-native');
+const {Platform} = require('react-native');
 const RNTesterBlock = require('./RNTesterBlock');
 const RNTesterPage = require('./RNTesterPage');
 
@@ -25,10 +25,7 @@ class RNTesterExampleContainer extends React.Component {
       title += ' (' + platform + ' only)';
     }
     return (
-      <RNTesterBlock
-        key={i}
-        title={title}
-        description={description}>
+      <RNTesterBlock key={i} title={title} description={description}>
         {example.render()}
       </RNTesterBlock>
     );
diff --git a/RNTester/js/RNTesterExampleList.js b/RNTester/js/RNTesterExampleList.js
index c7d974c48409..d031caef4524 100644
--- a/RNTester/js/RNTesterExampleList.js
+++ b/RNTester/js/RNTesterExampleList.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Platform = require('Platform');
@@ -53,34 +55,29 @@ class RowComponent extends React.PureComponent<{
     return (
       <TouchableHighlight {...this.props} onPress={this._onPress}>
         <View style={styles.row}>
-          <Text style={styles.rowTitleText}>
-            {item.module.title}
-          </Text>
-          <Text style={styles.rowDetailText}>
-            {item.module.description}
-          </Text>
+          <Text style={styles.rowTitleText}>{item.module.title}</Text>
+          <Text style={styles.rowDetailText}>{item.module.description}</Text>
         </View>
       </TouchableHighlight>
     );
   }
 }
 
-const renderSectionHeader = ({section}) =>
-  <Text style={styles.sectionHeader}>
-    {section.title}
-  </Text>;
+const renderSectionHeader = ({section}) => (
+  <Text style={styles.sectionHeader}>{section.title}</Text>
+);
 
 class RNTesterExampleList extends React.Component<Props, $FlowFixMeState> {
   render() {
     const filterText = this.props.persister.state.filter;
     const filterRegex = new RegExp(String(filterText), 'i');
-    const filter = (example) =>
+    const filter = example =>
       /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
        * error found when Flow v0.68 was deployed. To see the error delete this
        * comment and run Flow. */
       this.props.disableSearch ||
-        filterRegex.test(example.module.title) &&
-        (!Platform.isTVOS || example.supportsTVOS);
+      (filterRegex.test(example.module.title) &&
+        (!Platform.isTVOS || example.supportsTVOS));
 
     const sections = [
       {
@@ -138,10 +135,12 @@ class RNTesterExampleList extends React.Component<Props, $FlowFixMeState> {
     }
     return (
       <RowComponent
-        item={{module: {
-          title: 'RNTester',
-          description: 'React Native Examples',
-        }}}
+        item={{
+          module: {
+            title: 'RNTester',
+            description: 'React Native Examples',
+          },
+        }}
         onNavigate={this.props.onNavigate}
         onPress={() => {
           this.props.onNavigate(RNTesterActions.ExampleList());
@@ -185,10 +184,13 @@ const ItemSeparator = ({highlighted}) => (
   <View style={highlighted ? styles.separatorHighlighted : styles.separator} />
 );
 
-RNTesterExampleList = RNTesterStatePersister.createContainer(RNTesterExampleList, {
-  cacheKeySuffix: () => 'mainList',
-  getInitialState: () => ({filter: ''}),
-});
+RNTesterExampleList = RNTesterStatePersister.createContainer(
+  RNTesterExampleList,
+  {
+    cacheKeySuffix: () => 'mainList',
+    getInitialState: () => ({filter: ''}),
+  },
+);
 
 const styles = StyleSheet.create({
   listContainer: {
diff --git a/RNTester/js/RNTesterList.android.js b/RNTester/js/RNTesterList.android.js
index d038354b25c7..8e8f6b791b8f 100644
--- a/RNTester/js/RNTesterList.android.js
+++ b/RNTester/js/RNTesterList.android.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 export type RNTesterExample = {
@@ -84,11 +86,11 @@ const ComponentExamples: Array<RNTesterExample> = [
   },
   {
     key: 'SwipeableFlatListExample',
-    module: require('./SwipeableFlatListExample')
+    module: require('./SwipeableFlatListExample'),
   },
   {
     key: 'SwipeableListViewExample',
-    module: require('./SwipeableListViewExample')
+    module: require('./SwipeableListViewExample'),
   },
   {
     key: 'SwitchExample',
diff --git a/RNTester/js/RNTesterList.ios.js b/RNTester/js/RNTesterList.ios.js
index 812abde4fe71..f7a62efaa05f 100644
--- a/RNTester/js/RNTesterList.ios.js
+++ b/RNTester/js/RNTesterList.ios.js
@@ -4,14 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 export type RNTesterExample = {
   key: string,
   module: Object,
-  supportsTVOS: boolean
+  supportsTVOS: boolean,
 };
 
 const ComponentExamples: Array<RNTesterExample> = [
diff --git a/RNTester/js/RNTesterNavigationReducer.js b/RNTester/js/RNTesterNavigationReducer.js
index 60c21a7106a2..7dc222eee179 100644
--- a/RNTester/js/RNTesterNavigationReducer.js
+++ b/RNTester/js/RNTesterNavigationReducer.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // $FlowFixMe : This is a platform-forked component, and flow seems to only run on iOS?
@@ -17,16 +19,13 @@ export type RNTesterNavigationState = {
 
 function RNTesterNavigationReducer(
   state: ?RNTesterNavigationState,
-  action: any
+  action: any,
 ): RNTesterNavigationState {
-
   if (
     // Default value is to see example list
     !state ||
-
     // Handle the explicit list action
     action.type === 'RNTesterListAction' ||
-
     // Handle requests to go back to the list when an example is open
     (state.openExample && action.type === 'RNTesterBackAction')
   ) {
@@ -37,7 +36,6 @@ function RNTesterNavigationReducer(
   }
 
   if (action.type === 'RNTesterExampleAction') {
-
     // Make sure we see the module before returning the new state
     const ExampleModule = RNTesterList.Modules[action.openExample];
 
diff --git a/RNTester/js/RNTesterPage.js b/RNTester/js/RNTesterPage.js
index 4af103ea8166..580bd959800d 100644
--- a/RNTester/js/RNTesterPage.js
+++ b/RNTester/js/RNTesterPage.js
@@ -4,18 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var PropTypes = require('prop-types');
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  ScrollView,
-  StyleSheet,
-  View,
-} = ReactNative;
+var {ScrollView, StyleSheet, View} = ReactNative;
 
 var RNTesterTitle = require('./RNTesterTitle');
 
@@ -43,20 +41,19 @@ class RNTesterPage extends React.Component<{
     /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
      * error found when Flow v0.68 was deployed. To see the error delete this
      * comment and run Flow. */
-    var title = this.props.title ?
-      <RNTesterTitle title={this.props.title} /> :
-      null;
+    var title = this.props.title ? (
+      <RNTesterTitle title={this.props.title} />
+    ) : null;
     var spacer = this.props.noSpacer ? null : <View style={styles.spacer} />;
     return (
       <View style={styles.container}>
         {title}
-        <ContentWrapper
-          style={styles.wrapper}
-          {...wrapperProps}>
-            {
-              // $FlowFixMe found when converting React.createClass to ES6
-              this.props.children}
-            {spacer}
+        <ContentWrapper style={styles.wrapper} {...wrapperProps}>
+          {
+            // $FlowFixMe found when converting React.createClass to ES6
+            this.props.children
+          }
+          {spacer}
         </ContentWrapper>
       </View>
     );
diff --git a/RNTester/js/RNTesterSettingSwitchRow.js b/RNTester/js/RNTesterSettingSwitchRow.js
index 01cca6336c9e..423ccf23b242 100644
--- a/RNTester/js/RNTesterSettingSwitchRow.js
+++ b/RNTester/js/RNTesterSettingSwitchRow.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('React');
@@ -15,7 +17,10 @@ const Text = require('Text');
 const RNTesterStatePersister = require('./RNTesterStatePersister');
 const View = require('View');
 
-class RNTesterSettingSwitchRow extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class RNTesterSettingSwitchRow extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   UNSAFE_componentWillReceiveProps(newProps) {
     const {onEnable, onDisable, persister} = this.props;
     if (newProps.persister.state !== persister.state) {
@@ -29,7 +34,7 @@ class RNTesterSettingSwitchRow extends React.Component<$FlowFixMeProps, $FlowFix
         <Text>{label}</Text>
         <Switch
           value={persister.state}
-          onValueChange={(value) => {
+          onValueChange={value => {
             persister.setState(() => value);
           }}
         />
@@ -44,8 +49,11 @@ const styles = StyleSheet.create({
     justifyContent: 'space-between',
   },
 });
-RNTesterSettingSwitchRow = RNTesterStatePersister.createContainer(RNTesterSettingSwitchRow, {
-  cacheKeySuffix: ({label}) => 'Switch:' + label,
-  getInitialState: ({initialValue}) => initialValue,
-});
+RNTesterSettingSwitchRow = RNTesterStatePersister.createContainer(
+  RNTesterSettingSwitchRow,
+  {
+    cacheKeySuffix: ({label}) => 'Switch:' + label,
+    getInitialState: ({initialValue}) => initialValue,
+  },
+);
 module.exports = RNTesterSettingSwitchRow;
diff --git a/RNTester/js/RNTesterStatePersister.js b/RNTester/js/RNTesterStatePersister.js
index 455f429225a7..fb697e7d77ee 100644
--- a/RNTester/js/RNTesterStatePersister.js
+++ b/RNTester/js/RNTesterStatePersister.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const AsyncStorage = require('AsyncStorage');
@@ -34,13 +36,19 @@ function createContainer<Props: Object, State>(
     version?: string,
   },
 ): React.ComponentType<Props> {
-  return class ComponentWithPersistedState extends React.Component<Props, $FlowFixMeState> {
+  return class ComponentWithPersistedState extends React.Component<
+    Props,
+    $FlowFixMeState,
+  > {
     /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This comment
      * suppresses an error when upgrading Flow's support for React. To see the
      * error delete this comment and run Flow. */
-    static displayName = `RNTesterStatePersister(${Component.displayName || Component.name})`;
+    static displayName = `RNTesterStatePersister(${Component.displayName ||
+      Component.name})`;
     state = {value: spec.getInitialState(this.props)};
-    _cacheKey = `RNTester:${spec.version || 'v1'}:${spec.cacheKeySuffix(this.props)}`;
+    _cacheKey = `RNTester:${spec.version || 'v1'}:${spec.cacheKeySuffix(
+      this.props,
+    )}`;
     componentDidMount() {
       AsyncStorage.getItem(this._cacheKey, (err, value) => {
         if (!err && value) {
@@ -49,7 +57,7 @@ function createContainer<Props: Object, State>(
       });
     }
     _passSetState = (stateLamda: (state: State) => State): void => {
-      this.setState((state) => {
+      this.setState(state => {
         const value = stateLamda(state.value);
         AsyncStorage.setItem(this._cacheKey, JSON.stringify(value));
         return {value};
diff --git a/RNTester/js/RNTesterTitle.js b/RNTester/js/RNTesterTitle.js
index 17687d98bd8f..39d36a3a029f 100644
--- a/RNTester/js/RNTesterTitle.js
+++ b/RNTester/js/RNTesterTitle.js
@@ -4,25 +4,21 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, View} = ReactNative;
 
 class RNTesterTitle extends React.Component<$FlowFixMeProps> {
   render() {
     return (
       <View style={styles.container}>
-        <Text style={styles.text}>
-          {this.props.title}
-        </Text>
+        <Text style={styles.text}>{this.props.title}</Text>
       </View>
     );
   }
diff --git a/RNTester/js/RefreshControlExample.js b/RNTester/js/RefreshControlExample.js
index 055a85c5f644..bb69fff63a85 100644
--- a/RNTester/js/RefreshControlExample.js
+++ b/RNTester/js/RefreshControlExample.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 const React = require('react');
@@ -42,7 +44,7 @@ class Row extends React.Component {
 
   render() {
     return (
-     <TouchableWithoutFeedback onPress={this._onClick} >
+      <TouchableWithoutFeedback onPress={this._onClick}>
         <View style={styles.row}>
           <Text style={styles.text}>
             {this.props.data.text + ' (' + this.props.data.clicks + ' clicks)'}
@@ -60,11 +62,13 @@ class RefreshControlExample extends React.Component {
   state = {
     isRefreshing: false,
     loaded: 0,
-    rowData: Array.from(new Array(20)).map(
-      (val, i) => ({text: 'Initial row ' + i, clicks: 0})),
+    rowData: Array.from(new Array(20)).map((val, i) => ({
+      text: 'Initial row ' + i,
+      clicks: 0,
+    })),
   };
 
-  _onClick = (row) => {
+  _onClick = row => {
     row.clicks++;
     this.setState({
       rowData: this.state.rowData,
@@ -73,7 +77,7 @@ class RefreshControlExample extends React.Component {
 
   render() {
     const rows = this.state.rowData.map((row, ii) => {
-      return <Row key={ii} data={row} onClick={this._onClick}/>;
+      return <Row key={ii} data={row} onClick={this._onClick} />;
     });
     return (
       <ScrollView
@@ -99,11 +103,11 @@ class RefreshControlExample extends React.Component {
     setTimeout(() => {
       // prepend 10 items
       const rowData = Array.from(new Array(10))
-      .map((val, i) => ({
-        text: 'Loaded row ' + (+this.state.loaded + i),
-        clicks: 0,
-      }))
-      .concat(this.state.rowData);
+        .map((val, i) => ({
+          text: 'Loaded row ' + (+this.state.loaded + i),
+          clicks: 0,
+        }))
+        .concat(this.state.rowData);
 
       this.setState({
         loaded: this.state.loaded + 10,
diff --git a/RNTester/js/RootViewSizeFlexibilityExampleApp.js b/RNTester/js/RootViewSizeFlexibilityExampleApp.js
index c08a2ec578d5..bfcce23e6b8f 100644
--- a/RNTester/js/RootViewSizeFlexibilityExampleApp.js
+++ b/RNTester/js/RootViewSizeFlexibilityExampleApp.js
@@ -4,39 +4,39 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  StyleSheet,
-  Text,
-  TouchableHighlight,
-  View,
-} = ReactNative;
+const {StyleSheet, Text, TouchableHighlight, View} = ReactNative;
 
-class RootViewSizeFlexibilityExampleApp extends React.Component<{toggled: boolean}, any> {
+class RootViewSizeFlexibilityExampleApp extends React.Component<
+  {toggled: boolean},
+  any,
+> {
   constructor(props: {toggled: boolean}) {
     super(props);
-    this.state = { toggled: false };
+    this.state = {toggled: false};
   }
 
   _onPressButton() {
-    this.setState({ toggled: !this.state.toggled });
+    this.setState({toggled: !this.state.toggled});
   }
 
   render() {
-    const viewStyle = this.state.toggled ? styles.bigContainer : styles.smallContainer;
+    const viewStyle = this.state.toggled
+      ? styles.bigContainer
+      : styles.smallContainer;
 
     return (
       <TouchableHighlight onPress={this._onPressButton.bind(this)}>
         <View style={viewStyle}>
           <View style={styles.center}>
-            <Text style={styles.whiteText}>
-              React Native Button
-            </Text>
+            <Text style={styles.whiteText}>React Native Button</Text>
           </View>
         </View>
       </TouchableHighlight>
@@ -62,7 +62,7 @@ const styles = StyleSheet.create({
   },
   whiteText: {
     color: 'white',
-  }
+  },
 });
 
 module.exports = RootViewSizeFlexibilityExampleApp;
diff --git a/RNTester/js/ScrollViewSimpleExample.js b/RNTester/js/ScrollViewSimpleExample.js
index a4fc25fe14e2..85c4147470d2 100644
--- a/RNTester/js/ScrollViewSimpleExample.js
+++ b/RNTester/js/ScrollViewSimpleExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  ScrollView,
-  StyleSheet,
-  Text,
-  TouchableOpacity
-} = ReactNative;
+var {ScrollView, StyleSheet, Text, TouchableOpacity} = ReactNative;
 
 var NUM_ITEMS = 20;
 
@@ -26,11 +23,11 @@ class ScrollViewSimpleExample extends React.Component<{}> {
   makeItems = (nItems: number, styles): Array<any> => {
     var items = [];
     for (var i = 0; i < nItems; i++) {
-       items[i] = (
-         <TouchableOpacity key={i} style={styles}>
-           <Text>{'Item ' + i}</Text>
-         </TouchableOpacity>
-       );
+      items[i] = (
+        <TouchableOpacity key={i} style={styles}>
+          <Text>{'Item ' + i}</Text>
+        </TouchableOpacity>
+      );
     }
     return items;
   };
@@ -40,7 +37,10 @@ class ScrollViewSimpleExample extends React.Component<{}> {
     var items = this.makeItems(NUM_ITEMS, styles.itemWrapper);
     items[4] = (
       <ScrollView key={'scrollView'} horizontal={true}>
-        {this.makeItems(NUM_ITEMS, [styles.itemWrapper, styles.horizontalItemWrapper])}
+        {this.makeItems(NUM_ITEMS, [
+          styles.itemWrapper,
+          styles.horizontalItemWrapper,
+        ])}
       </ScrollView>
     );
     items.push(
@@ -48,20 +48,17 @@ class ScrollViewSimpleExample extends React.Component<{}> {
         key={'scrollViewSnap'}
         horizontal
         snapToInterval={210.0}
-        pagingEnabled
-      >
+        pagingEnabled>
         {this.makeItems(NUM_ITEMS, [
           styles.itemWrapper,
           styles.horizontalItemWrapper,
           styles.horizontalPagingItemWrapper,
         ])}
-      </ScrollView>
+      </ScrollView>,
     );
 
     var verticalScrollView = (
-      <ScrollView style={styles.verticalScrollView}>
-        {items}
-      </ScrollView>
+      <ScrollView style={styles.verticalScrollView}>{items}</ScrollView>
     );
 
     return verticalScrollView;
@@ -82,7 +79,7 @@ var styles = StyleSheet.create({
     margin: 5,
   },
   horizontalItemWrapper: {
-    padding: 50
+    padding: 50,
   },
   horizontalPagingItemWrapper: {
     width: 200,
diff --git a/RNTester/js/SectionListExample.js b/RNTester/js/SectionListExample.js
index 5410251853ed..5d3f73f70c2b 100644
--- a/RNTester/js/SectionListExample.js
+++ b/RNTester/js/SectionListExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -60,7 +62,11 @@ const renderSectionFooter = ({section}) => (
 );
 
 const CustomSeparatorComponent = ({highlighted, text}) => (
-  <View style={[styles.customSeparator, highlighted && {backgroundColor: 'rgb(217, 217, 217)'}]}>
+  <View
+    style={[
+      styles.customSeparator,
+      highlighted && {backgroundColor: 'rgb(217, 217, 217)'},
+    ]}>
     <Text style={styles.separatorText}>{text}</Text>
   </View>
 );
@@ -80,39 +86,38 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
 
   _scrollPos = new Animated.Value(0);
   _scrollSinkY = Animated.event(
-    [{nativeEvent: { contentOffset: { y: this._scrollPos } }}],
+    [{nativeEvent: {contentOffset: {y: this._scrollPos}}}],
     {useNativeDriver: true},
   );
 
   _sectionListRef: any;
-  _captureRef = (ref) => { this._sectionListRef = ref; };
+  _captureRef = ref => {
+    this._sectionListRef = ref;
+  };
 
   _scrollToLocation(sectionIndex: number, itemIndex: number) {
-    this._sectionListRef
-      .getNode()
-      .scrollToLocation({ sectionIndex, itemIndex });
+    this._sectionListRef.getNode().scrollToLocation({sectionIndex, itemIndex});
   }
 
   render() {
     const filterRegex = new RegExp(String(this.state.filterText), 'i');
-    const filter = (item) => (
-      filterRegex.test(item.text) || filterRegex.test(item.title)
-    );
+    const filter = item =>
+      filterRegex.test(item.text) || filterRegex.test(item.title);
     const filteredData = this.state.data.filter(filter);
     const filteredSectionData = [];
     let startIndex = 0;
     const endIndex = filteredData.length - 1;
     for (let ii = 10; ii <= endIndex + 10; ii += 10) {
       filteredSectionData.push({
-        key: `${filteredData[startIndex].key} - ${filteredData[Math.min(ii - 1, endIndex)].key}`,
+        key: `${filteredData[startIndex].key} - ${
+          filteredData[Math.min(ii - 1, endIndex)].key
+        }`,
         data: filteredData.slice(startIndex, ii),
       });
       startIndex = ii;
     }
     return (
-      <RNTesterPage
-        noSpacer={true}
-        noScroll={true}>
+      <RNTesterPage noSpacer={true} noScroll={true}>
         <View style={styles.searchRow}>
           <PlainInput
             onChangeText={filterText => {
@@ -130,9 +135,18 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
           </View>
           <View style={styles.scrollToRow}>
             <Text>scroll to:</Text>
-            <Button title="Item A" onPress={() => this._scrollToLocation(2, 1)}/>
-            <Button title="Item B" onPress={() => this._scrollToLocation(3, 6)}/>
-            <Button title="Item C" onPress={() => this._scrollToLocation(6, 3)}/>
+            <Button
+              title="Item A"
+              onPress={() => this._scrollToLocation(2, 1)}
+            />
+            <Button
+              title="Item B"
+              onPress={() => this._scrollToLocation(3, 6)}
+            />
+            <Button
+              title="Item C"
+              onPress={() => this._scrollToLocation(6, 3)}
+            />
           </View>
         </View>
         <SeparatorComponent />
@@ -140,12 +154,12 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
           ref={this._captureRef}
           ListHeaderComponent={HeaderComponent}
           ListFooterComponent={FooterComponent}
-          SectionSeparatorComponent={(info) =>
+          SectionSeparatorComponent={info => (
             <CustomSeparatorComponent {...info} text="SECTION SEPARATOR" />
-          }
-          ItemSeparatorComponent={(info) =>
+          )}
+          ItemSeparatorComponent={info => (
             <CustomSeparatorComponent {...info} text="ITEM SEPARATOR" />
-          }
+          )}
           debug={this.state.debug}
           inverted={this.state.inverted}
           enableVirtualization={this.state.virtualized}
@@ -166,14 +180,28 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
               renderItem: renderStackedItem,
               key: 's1',
               data: [
-                {title: 'Item In Header Section', text: 'Section s1', key: 'header item'},
+                {
+                  title: 'Item In Header Section',
+                  text: 'Section s1',
+                  key: 'header item',
+                },
               ],
             },
             {
               key: 's2',
               data: [
-                {noImage: true, title: '1st item', text: 'Section s2', key: 'noimage0'},
-                {noImage: true, title: '2nd item', text: 'Section s2', key: 'noimage1'},
+                {
+                  noImage: true,
+                  title: '1st item',
+                  text: 'Section s2',
+                  key: 'noimage0',
+                },
+                {
+                  noImage: true,
+                  title: '2nd item',
+                  text: 'Section s2',
+                  key: 'noimage1',
+                },
               ],
             },
             ...filteredSectionData,
@@ -202,14 +230,19 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
       isViewable: boolean,
       item: {columns: Array<*>},
       index: ?number,
-      section?: any
-    }>},
-  ) => {
+      section?: any,
+    }>,
+  }) => {
     // Impressions can be logged here
     if (this.state.logViewable) {
-      infoLog('onViewableItemsChanged: ', info.changed.map((v: Object) => (
-        {...v, item: '...', section: v.section.key}
-      )));
+      infoLog(
+        'onViewableItemsChanged: ',
+        info.changed.map((v: Object) => ({
+          ...v,
+          item: '...',
+          section: v.section.key,
+        })),
+      );
     }
   };
 
diff --git a/RNTester/js/SegmentedControlIOSExample.js b/RNTester/js/SegmentedControlIOSExample.js
index c0098b5fafd4..6dd003769565 100644
--- a/RNTester/js/SegmentedControlIOSExample.js
+++ b/RNTester/js/SegmentedControlIOSExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  SegmentedControlIOS,
-  Text,
-  View,
-  StyleSheet
-} = ReactNative;
+var {SegmentedControlIOS, Text, View, StyleSheet} = ReactNative;
 
 class BasicSegmentedControlExample extends React.Component<{}> {
   render() {
@@ -25,7 +22,9 @@ class BasicSegmentedControlExample extends React.Component<{}> {
           <SegmentedControlIOS values={['One', 'Two']} />
         </View>
         <View>
-          <SegmentedControlIOS values={['One', 'Two', 'Three', 'Four', 'Five']} />
+          <SegmentedControlIOS
+            values={['One', 'Two', 'Three', 'Four', 'Five']}
+          />
         </View>
       </View>
     );
@@ -61,7 +60,11 @@ class DisabledSegmentedControlExample extends React.Component<{}> {
     return (
       <View>
         <View>
-          <SegmentedControlIOS enabled={false} values={['One', 'Two']} selectedIndex={1} />
+          <SegmentedControlIOS
+            enabled={false}
+            values={['One', 'Two']}
+            selectedIndex={1}
+          />
         </View>
       </View>
     );
@@ -73,48 +76,56 @@ class ColorSegmentedControlExample extends React.Component<{}> {
     return (
       <View>
         <View style={{marginBottom: 10}}>
-          <SegmentedControlIOS tintColor="#ff0000" values={['One', 'Two', 'Three', 'Four']} selectedIndex={0} />
+          <SegmentedControlIOS
+            tintColor="#ff0000"
+            values={['One', 'Two', 'Three', 'Four']}
+            selectedIndex={0}
+          />
         </View>
         <View>
-          <SegmentedControlIOS tintColor="#00ff00" values={['One', 'Two', 'Three']} selectedIndex={1} />
+          <SegmentedControlIOS
+            tintColor="#00ff00"
+            values={['One', 'Two', 'Three']}
+            selectedIndex={1}
+          />
         </View>
       </View>
     );
   }
 }
 
-class EventSegmentedControlExample extends React.Component<{}, $FlowFixMeState> {
+class EventSegmentedControlExample extends React.Component<
+  {},
+  $FlowFixMeState,
+> {
   state = {
     values: ['One', 'Two', 'Three'],
     value: 'Not selected',
-    selectedIndex: undefined
+    selectedIndex: undefined,
   };
 
   render() {
     return (
       <View>
-        <Text style={styles.text} >
-          Value: {this.state.value}
-        </Text>
-        <Text style={styles.text} >
-          Index: {this.state.selectedIndex}
-        </Text>
+        <Text style={styles.text}>Value: {this.state.value}</Text>
+        <Text style={styles.text}>Index: {this.state.selectedIndex}</Text>
         <SegmentedControlIOS
           values={this.state.values}
           selectedIndex={this.state.selectedIndex}
           onChange={this._onChange}
-          onValueChange={this._onValueChange} />
+          onValueChange={this._onValueChange}
+        />
       </View>
     );
   }
 
-  _onChange = (event) => {
+  _onChange = event => {
     this.setState({
       selectedIndex: event.nativeEvent.selectedSegmentIndex,
     });
   };
 
-  _onValueChange = (value) => {
+  _onValueChange = value => {
     this.setState({
       value: value,
     });
@@ -136,26 +147,38 @@ exports.description = 'Native segmented control';
 exports.examples = [
   {
     title: 'Segmented controls can have values',
-    render(): React.Element<any> { return <BasicSegmentedControlExample />; }
+    render(): React.Element<any> {
+      return <BasicSegmentedControlExample />;
+    },
   },
   {
     title: 'Segmented controls can have a pre-selected value',
-    render(): React.Element<any> { return <PreSelectedSegmentedControlExample />; }
+    render(): React.Element<any> {
+      return <PreSelectedSegmentedControlExample />;
+    },
   },
   {
     title: 'Segmented controls can be momentary',
-    render(): React.Element<any> { return <MomentarySegmentedControlExample />; }
+    render(): React.Element<any> {
+      return <MomentarySegmentedControlExample />;
+    },
   },
   {
     title: 'Segmented controls can be disabled',
-    render(): React.Element<any> { return <DisabledSegmentedControlExample />; }
+    render(): React.Element<any> {
+      return <DisabledSegmentedControlExample />;
+    },
   },
   {
     title: 'Custom colors can be provided',
-    render(): React.Element<any> { return <ColorSegmentedControlExample />; }
+    render(): React.Element<any> {
+      return <ColorSegmentedControlExample />;
+    },
   },
   {
     title: 'Change events can be detected',
-    render(): React.Element<any> { return <EventSegmentedControlExample />; }
-  }
+    render(): React.Element<any> {
+      return <EventSegmentedControlExample />;
+    },
+  },
 ];
diff --git a/RNTester/js/SetPropertiesExampleApp.js b/RNTester/js/SetPropertiesExampleApp.js
index 95034438b0a1..2b8e3fe5bf26 100644
--- a/RNTester/js/SetPropertiesExampleApp.js
+++ b/RNTester/js/SetPropertiesExampleApp.js
@@ -4,36 +4,31 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  Text,
-  View,
-} = ReactNative;
+const {Text, View} = ReactNative;
 
 class SetPropertiesExampleApp extends React.Component<$FlowFixMeProps> {
-
   render() {
     const wrapperStyle = {
       backgroundColor: this.props.color,
       flex: 1,
       alignItems: 'center',
-      justifyContent: 'center'
+      justifyContent: 'center',
     };
 
     return (
       <View style={wrapperStyle}>
-        <Text>
-          Embedded React Native view
-        </Text>
+        <Text>Embedded React Native view</Text>
       </View>
     );
   }
-
 }
 
 module.exports = SetPropertiesExampleApp;
diff --git a/RNTester/js/ShareExample.js b/RNTester/js/ShareExample.js
index 7df3edd360f7..ac3aa22ee2f4 100644
--- a/RNTester/js/ShareExample.js
+++ b/RNTester/js/ShareExample.js
@@ -4,29 +4,27 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  View,
-  Text,
-  TouchableHighlight,
-  Share,
-} = ReactNative;
+var {StyleSheet, View, Text, TouchableHighlight, Share} = ReactNative;
 
 exports.framework = 'React';
 exports.title = 'Share';
 exports.description = 'Share data with other Apps.';
-exports.examples = [{
-  title: 'Share Text Content',
-  render() {
-    return <ShareMessageExample />;
-  }
-}];
+exports.examples = [
+  {
+    title: 'Share Text Content',
+    render() {
+      return <ShareMessageExample />;
+    },
+  },
+];
 
 class ShareMessageExample extends React.Component<$FlowFixMeProps, any> {
   _shareMessage: Function;
@@ -41,21 +39,19 @@ class ShareMessageExample extends React.Component<$FlowFixMeProps, any> {
     this._showResult = this._showResult.bind(this);
 
     this.state = {
-      result: ''
+      result: '',
     };
   }
 
   render() {
     return (
       <View>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={this._shareMessage}>
+        <TouchableHighlight style={styles.wrapper} onPress={this._shareMessage}>
           <View style={styles.button}>
             <Text>Click to share message</Text>
           </View>
         </TouchableHighlight>
-        <TouchableHighlight style={styles.wrapper}
-          onPress={this._shareText}>
+        <TouchableHighlight style={styles.wrapper} onPress={this._shareText}>
           <View style={styles.button}>
             <Text>Click to share message, URL and title</Text>
           </View>
@@ -67,33 +63,37 @@ class ShareMessageExample extends React.Component<$FlowFixMeProps, any> {
 
   _shareMessage() {
     Share.share({
-      message: 'React Native | A framework for building native apps using React'
+      message:
+        'React Native | A framework for building native apps using React',
     })
-    .then(this._showResult)
-    .catch((error) => this.setState({result: 'error: ' + error.message}));
+      .then(this._showResult)
+      .catch(error => this.setState({result: 'error: ' + error.message}));
   }
 
   _shareText() {
-    Share.share({
-      message: 'A framework for building native apps using React',
-      url: 'http://facebook.github.io/react-native/',
-      title: 'React Native'
-    }, {
-      subject: 'A subject to go in the email heading',
-      dialogTitle: 'Share React Native website',
-      excludedActivityTypes: [
-        'com.apple.UIKit.activity.PostToTwitter'
-      ],
-      tintColor: 'green'
-    })
-    .then(this._showResult)
-    .catch((error) => this.setState({result: 'error: ' + error.message}));
+    Share.share(
+      {
+        message: 'A framework for building native apps using React',
+        url: 'http://facebook.github.io/react-native/',
+        title: 'React Native',
+      },
+      {
+        subject: 'A subject to go in the email heading',
+        dialogTitle: 'Share React Native website',
+        excludedActivityTypes: ['com.apple.UIKit.activity.PostToTwitter'],
+        tintColor: 'green',
+      },
+    )
+      .then(this._showResult)
+      .catch(error => this.setState({result: 'error: ' + error.message}));
   }
 
   _showResult(result) {
     if (result.action === Share.sharedAction) {
       if (result.activityType) {
-        this.setState({result: 'shared with an activityType: ' + result.activityType});
+        this.setState({
+          result: 'shared with an activityType: ' + result.activityType,
+        });
       } else {
         this.setState({result: 'shared'});
       }
@@ -103,7 +103,6 @@ class ShareMessageExample extends React.Component<$FlowFixMeProps, any> {
   }
 }
 
-
 var styles = StyleSheet.create({
   wrapper: {
     borderRadius: 5,
diff --git a/RNTester/js/SliderExample.js b/RNTester/js/SliderExample.js
index b05877572e70..a6d951033636 100644
--- a/RNTester/js/SliderExample.js
+++ b/RNTester/js/SliderExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Slider,
-  Text,
-  StyleSheet,
-  View,
-} = ReactNative;
+var {Slider, Text, StyleSheet, View} = ReactNative;
 
 class SliderExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
   static defaultProps = {
@@ -29,18 +26,22 @@ class SliderExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
   render() {
     return (
       <View>
-        <Text style={styles.text} >
+        <Text style={styles.text}>
           {this.state.value && +this.state.value.toFixed(3)}
         </Text>
         <Slider
           {...this.props}
-          onValueChange={(value) => this.setState({value: value})} />
+          onValueChange={value => this.setState({value: value})}
+        />
       </View>
     );
   }
 }
 
-class SlidingCompleteExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class SlidingCompleteExample extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   state = {
     slideCompletionValue: 0,
     slideCompletionCount: 0,
@@ -51,11 +52,16 @@ class SlidingCompleteExample extends React.Component<$FlowFixMeProps, $FlowFixMe
       <View>
         <SliderExample
           {...this.props}
-          onSlidingComplete={(value) => this.setState({
+          onSlidingComplete={value =>
+            this.setState({
               slideCompletionValue: value,
-              slideCompletionCount: this.state.slideCompletionCount + 1})} />
+              slideCompletionCount: this.state.slideCompletionCount + 1,
+            })
+          }
+        />
         <Text>
-          Completions: {this.state.slideCompletionCount} Value: {this.state.slideCompletionValue}
+          Completions: {this.state.slideCompletionCount} Value:{' '}
+          {this.state.slideCompletionValue}
         </Text>
       </View>
     );
@@ -83,38 +89,31 @@ exports.examples = [
     title: 'Default settings',
     render(): React.Element<any> {
       return <SliderExample />;
-    }
+    },
   },
   {
     title: 'Initial value: 0.5',
     render(): React.Element<any> {
       return <SliderExample value={0.5} />;
-    }
+    },
   },
   {
     title: 'minimumValue: -1, maximumValue: 2',
     render(): React.Element<any> {
-      return (
-        <SliderExample
-          minimumValue={-1}
-          maximumValue={2}
-        />
-      );
-    }
+      return <SliderExample minimumValue={-1} maximumValue={2} />;
+    },
   },
   {
     title: 'step: 0.25',
     render(): React.Element<any> {
       return <SliderExample step={0.25} />;
-    }
+    },
   },
   {
     title: 'onSlidingComplete',
     render(): React.Element<any> {
-      return (
-        <SlidingCompleteExample />
-      );
-    }
+      return <SlidingCompleteExample />;
+    },
   },
   {
     title: 'Custom min/max track tint color',
@@ -126,28 +125,28 @@ exports.examples = [
           value={0.5}
         />
       );
-    }
+    },
   },
   {
     title: 'Custom thumb color',
     platform: 'android',
     render(): React.Element<any> {
       return <SliderExample thumbTintColor={'blue'} />;
-    }
+    },
   },
   {
     title: 'Custom thumb image',
     platform: 'ios',
     render(): React.Element<any> {
       return <SliderExample thumbImage={require('./uie_thumb_big.png')} />;
-    }
+    },
   },
   {
     title: 'Custom track image',
     platform: 'ios',
     render(): React.Element<any> {
       return <SliderExample trackImage={require('./slider.png')} />;
-    }
+    },
   },
   {
     title: 'Custom min/max track image',
@@ -159,6 +158,6 @@ exports.examples = [
           maximumTrackImage={require('./slider-right.png')}
         />
       );
-    }
+    },
   },
 ];
diff --git a/RNTester/js/StatusBarExample.js b/RNTester/js/StatusBarExample.js
index b9949c17cce1..3247567111c9 100644
--- a/RNTester/js/StatusBarExample.js
+++ b/RNTester/js/StatusBarExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -23,22 +25,11 @@ exports.framework = 'React';
 exports.title = '<StatusBar>';
 exports.description = 'Component for controlling the status bar';
 
-const colors = [
-  '#ff0000',
-  '#00ff00',
-  '#0000ff',
-  'rgba(0, 0, 0, 0.4)',
-];
+const colors = ['#ff0000', '#00ff00', '#0000ff', 'rgba(0, 0, 0, 0.4)'];
 
-const barStyles = [
-  'default',
-  'light-content',
-];
+const barStyles = ['default', 'light-content'];
 
-const showHideTransitions = [
-  'fade',
-  'slide',
-];
+const showHideTransitions = ['fade', 'slide'];
 
 function getValue<T>(values: Array<T>, index: number): T {
   return values[index % values.length];
@@ -64,7 +55,10 @@ class StatusBarHiddenExample extends React.Component<{}, $FlowFixMeState> {
   _onChangeTransition = () => {
     this._showHideTransitionIndex++;
     this.setState({
-      showHideTransition: getValue(showHideTransitions, this._showHideTransitionIndex),
+      showHideTransition: getValue(
+        showHideTransitions,
+        this._showHideTransitionIndex,
+      ),
     });
   };
 
@@ -87,7 +81,9 @@ class StatusBarHiddenExample extends React.Component<{}, $FlowFixMeState> {
           style={styles.wrapper}
           onPress={this._onChangeAnimated}>
           <View style={styles.button}>
-            <Text>animated (ios only): {this.state.animated ? 'true' : 'false'}</Text>
+            <Text>
+              animated (ios only): {this.state.animated ? 'true' : 'false'}
+            </Text>
           </View>
         </TouchableHighlight>
         <TouchableHighlight
@@ -95,8 +91,10 @@ class StatusBarHiddenExample extends React.Component<{}, $FlowFixMeState> {
           onPress={this._onChangeTransition}>
           <View style={styles.button}>
             <Text>
-              showHideTransition (ios only):
-              '{getValue(showHideTransitions, this._showHideTransitionIndex)}'
+              showHideTransition (ios only): '{getValue(
+                showHideTransitions,
+                this._showHideTransitionIndex,
+              )}'
             </Text>
           </View>
         </TouchableHighlight>
@@ -149,14 +147,18 @@ class StatusBarStyleExample extends React.Component<{}, $FlowFixMeState> {
   }
 }
 
-class StatusBarNetworkActivityExample extends React.Component<{}, $FlowFixMeState> {
+class StatusBarNetworkActivityExample extends React.Component<
+  {},
+  $FlowFixMeState,
+> {
   state = {
     networkActivityIndicatorVisible: false,
   };
 
   _onChangeNetworkIndicatorVisible = () => {
     this.setState({
-      networkActivityIndicatorVisible: !this.state.networkActivityIndicatorVisible,
+      networkActivityIndicatorVisible: !this.state
+        .networkActivityIndicatorVisible,
     });
   };
 
@@ -164,7 +166,9 @@ class StatusBarNetworkActivityExample extends React.Component<{}, $FlowFixMeStat
     return (
       <View>
         <StatusBar
-          networkActivityIndicatorVisible={this.state.networkActivityIndicatorVisible}
+          networkActivityIndicatorVisible={
+            this.state.networkActivityIndicatorVisible
+          }
         />
         <TouchableHighlight
           style={styles.wrapper}
@@ -181,7 +185,10 @@ class StatusBarNetworkActivityExample extends React.Component<{}, $FlowFixMeStat
   }
 }
 
-class StatusBarBackgroundColorExample extends React.Component<{}, $FlowFixMeState> {
+class StatusBarBackgroundColorExample extends React.Component<
+  {},
+  $FlowFixMeState,
+> {
   state = {
     animated: true,
     backgroundColor: getValue(colors, 0),
@@ -238,14 +245,14 @@ class StatusBarTranslucentExample extends React.Component<{}, $FlowFixMeState> {
   render() {
     return (
       <View>
-        <StatusBar
-          translucent={this.state.translucent}
-        />
+        <StatusBar translucent={this.state.translucent} />
         <TouchableHighlight
           style={styles.wrapper}
           onPress={this._onChangeTranslucent}>
           <View style={styles.button}>
-            <Text>translucent: {this.state.translucent ? 'true' : 'false'}</Text>
+            <Text>
+              translucent: {this.state.translucent ? 'true' : 'false'}
+            </Text>
           </View>
         </TouchableHighlight>
       </View>
@@ -363,7 +370,10 @@ class StatusBarStaticAndroidExample extends React.Component<{}> {
             StatusBar.setBackgroundColor('rgba(0, 0, 0, 0.4)', true);
           }}>
           <View style={styles.button}>
-            <Text>setTranslucent(true) and setBackgroundColor('rgba(0, 0, 0, 0.4)', true)</Text>
+            <Text>
+              setTranslucent(true) and setBackgroundColor('rgba(0, 0, 0, 0.4)',
+              true)
+            </Text>
           </View>
         </TouchableHighlight>
         <TouchableHighlight
@@ -373,7 +383,9 @@ class StatusBarStaticAndroidExample extends React.Component<{}> {
             StatusBar.setBackgroundColor('black', true);
           }}>
           <View style={styles.button}>
-            <Text>setTranslucent(false) and setBackgroundColor('black', true)</Text>
+            <Text>
+              setTranslucent(false) and setBackgroundColor('black', true)
+            </Text>
           </View>
         </TouchableHighlight>
       </View>
@@ -381,7 +393,6 @@ class StatusBarStaticAndroidExample extends React.Component<{}> {
   }
 }
 
-
 class ModalExample extends React.Component<{}, $FlowFixMeState> {
   state = {
     modalVisible: false,
@@ -423,58 +434,67 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
   }
 }
 
-const examples = [{
-  title: 'StatusBar hidden',
-  render() {
-    return <StatusBarHiddenExample />;
+const examples = [
+  {
+    title: 'StatusBar hidden',
+    render() {
+      return <StatusBarHiddenExample />;
+    },
   },
-}, {
-  title: 'StatusBar style',
-  render() {
-    return <StatusBarStyleExample />;
+  {
+    title: 'StatusBar style',
+    render() {
+      return <StatusBarStyleExample />;
+    },
+    platform: 'ios',
   },
-  platform: 'ios',
-}, {
-  title: 'StatusBar network activity indicator',
-  render() {
-    return <StatusBarNetworkActivityExample />;
+  {
+    title: 'StatusBar network activity indicator',
+    render() {
+      return <StatusBarNetworkActivityExample />;
+    },
+    platform: 'ios',
   },
-  platform: 'ios',
-}, {
-  title: 'StatusBar background color',
-  render() {
-    return <StatusBarBackgroundColorExample />;
+  {
+    title: 'StatusBar background color',
+    render() {
+      return <StatusBarBackgroundColorExample />;
+    },
+    platform: 'android',
   },
-  platform: 'android',
-}, {
-  title: 'StatusBar translucent',
-  render() {
-    return <StatusBarTranslucentExample />;
+  {
+    title: 'StatusBar translucent',
+    render() {
+      return <StatusBarTranslucentExample />;
+    },
+    platform: 'android',
   },
-  platform: 'android',
-}, {
-  title: 'StatusBar static API',
-  render() {
-    return <StatusBarStaticIOSExample />;
+  {
+    title: 'StatusBar static API',
+    render() {
+      return <StatusBarStaticIOSExample />;
+    },
+    platform: 'ios',
   },
-  platform: 'ios',
-}, {
-  title: 'StatusBar static API',
-  render() {
-    return <StatusBarStaticAndroidExample />;
+  {
+    title: 'StatusBar static API',
+    render() {
+      return <StatusBarStaticAndroidExample />;
+    },
+    platform: 'android',
   },
-  platform: 'android',
-}, {
-  title: 'StatusBar dimensions',
-  render() {
-    return (
-      <View>
-        <Text>Height (Android only): {StatusBar.currentHeight} pts</Text>
-      </View>
-    );
+  {
+    title: 'StatusBar dimensions',
+    render() {
+      return (
+        <View>
+          <Text>Height (Android only): {StatusBar.currentHeight} pts</Text>
+        </View>
+      );
+    },
+    platform: 'android',
   },
-  platform: 'android',
-}];
+];
 
 exports.examples = examples;
 
@@ -483,7 +503,7 @@ var styles = StyleSheet.create({
     flex: 1,
     justifyContent: 'center',
     padding: 20,
-    backgroundColor: '#f5fcff'
+    backgroundColor: '#f5fcff',
   },
   innerContainer: {
     borderRadius: 10,
diff --git a/RNTester/js/SwipeableListViewExample.js b/RNTester/js/SwipeableListViewExample.js
index db91633962cf..1fec55d93e43 100644
--- a/RNTester/js/SwipeableListViewExample.js
+++ b/RNTester/js/SwipeableListViewExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -27,7 +29,7 @@ var SwipeableListViewSimpleExample = createReactClass({
   displayName: 'SwipeableListViewSimpleExample',
   statics: {
     title: '<SwipeableListView>',
-    description: 'Performant, scrollable, swipeable list of data.'
+    description: 'Performant, scrollable, swipeable list of data.',
   },
 
   getInitialState: function() {
@@ -52,15 +54,24 @@ var SwipeableListViewSimpleExample = createReactClass({
         <SwipeableListView
           dataSource={this.state.dataSource}
           maxSwipeDistance={100}
-          renderQuickActions={
-            (rowData: Object, sectionID: string, rowID: string) => {
-            return (<View style={styles.actionsContainer}>
-              <TouchableHighlight onPress={() => {
-                Alert.alert('Tips', 'You could do something with this row: ' + rowData.text);
-              }}>
-                <Text>Remove</Text>
-              </TouchableHighlight>
-            </View>);
+          renderQuickActions={(
+            rowData: Object,
+            sectionID: string,
+            rowID: string,
+          ) => {
+            return (
+              <View style={styles.actionsContainer}>
+                <TouchableHighlight
+                  onPress={() => {
+                    Alert.alert(
+                      'Tips',
+                      'You could do something with this row: ' + rowData.text,
+                    );
+                  }}>
+                  <Text>Remove</Text>
+                </TouchableHighlight>
+              </View>
+            );
           }}
           renderRow={this._renderRow}
           renderSeparator={this._renderSeperator}
@@ -69,7 +80,12 @@ var SwipeableListViewSimpleExample = createReactClass({
     );
   },
 
-  _renderRow: function(rowData: Object, sectionID: number, rowID: number, highlightRow: (sectionID: number, rowID: number) => void) {
+  _renderRow: function(
+    rowData: Object,
+    sectionID: number,
+    rowID: number,
+    highlightRow: (sectionID: number, rowID: number) => void,
+  ) {
     var rowHash = Math.abs(hashCode(rowData.id));
     var imgSource = THUMB_URLS[rowHash % THUMB_URLS.length];
     return (
@@ -109,13 +125,20 @@ var SwipeableListViewSimpleExample = createReactClass({
     dataBlob['Section 0'] = {};
     for (var ii = 0; ii < 100; ii++) {
       var pressedText = pressData[ii] ? ' (pressed)' : '';
-      dataBlob[sectionIDs[0]]['Row ' + ii] = {id: 'Row ' + ii, text: 'Row ' + ii + pressedText};
+      dataBlob[sectionIDs[0]]['Row ' + ii] = {
+        id: 'Row ' + ii,
+        text: 'Row ' + ii + pressedText,
+      };
       rowIDs[0].push('Row ' + ii);
     }
     return [dataBlob, sectionIDs, rowIDs];
   },
 
-  _renderSeperator: function(sectionID: number, rowID: number, adjacentRowHighlighted: bool) {
+  _renderSeperator: function(
+    sectionID: number,
+    rowID: number,
+    adjacentRowHighlighted: boolean,
+  ) {
     return (
       <View
         key={`${sectionID}-${rowID}`}
@@ -125,7 +148,7 @@ var SwipeableListViewSimpleExample = createReactClass({
         }}
       />
     );
-  }
+  },
 });
 
 var THUMB_URLS = [
@@ -141,14 +164,15 @@ var THUMB_URLS = [
   require('./Thumbnails/poke.png'),
   require('./Thumbnails/superlike.png'),
   require('./Thumbnails/victory.png'),
-  ];
-var LOREM_IPSUM = 'Lorem ipsum dolor sit amet, ius ad pertinax oportere accommodare, an vix civibus corrumpit referrentur. Te nam case ludus inciderint, te mea facilisi adipiscing. Sea id integre luptatum. In tota sale consequuntur nec. Erat ocurreret mei ei. Eu paulo sapientem vulputate est, vel an accusam intellegam interesset. Nam eu stet pericula reprimique, ea vim illud modus, putant invidunt reprehendunt ne qui.';
+];
+var LOREM_IPSUM =
+  'Lorem ipsum dolor sit amet, ius ad pertinax oportere accommodare, an vix civibus corrumpit referrentur. Te nam case ludus inciderint, te mea facilisi adipiscing. Sea id integre luptatum. In tota sale consequuntur nec. Erat ocurreret mei ei. Eu paulo sapientem vulputate est, vel an accusam intellegam interesset. Nam eu stet pericula reprimique, ea vim illud modus, putant invidunt reprehendunt ne qui.';
 
 /* eslint no-bitwise: 0 */
 var hashCode = function(str) {
   var hash = 15;
   for (var ii = str.length - 1; ii >= 0; ii--) {
-    hash = ((hash << 5) - hash) + str.charCodeAt(ii);
+    hash = (hash << 5) - hash + str.charCodeAt(ii);
   }
   return hash;
 };
diff --git a/RNTester/js/SwitchExample.js b/RNTester/js/SwitchExample.js
index e040c76a1c79..a8116ff243cf 100644
--- a/RNTester/js/SwitchExample.js
+++ b/RNTester/js/SwitchExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Platform,
-  Switch,
-  Text,
-  View
-} = ReactNative;
+var {Platform, Switch, Text, View} = ReactNative;
 
 class BasicSwitchExample extends React.Component<{}, $FlowFixMeState> {
   state = {
@@ -27,12 +24,14 @@ class BasicSwitchExample extends React.Component<{}, $FlowFixMeState> {
     return (
       <View>
         <Switch
-          onValueChange={(value) => this.setState({falseSwitchIsOn: value})}
+          onValueChange={value => this.setState({falseSwitchIsOn: value})}
           style={{marginBottom: 10}}
-          value={this.state.falseSwitchIsOn} />
+          value={this.state.falseSwitchIsOn}
+        />
         <Switch
-          onValueChange={(value) => this.setState({trueSwitchIsOn: value})}
-          value={this.state.trueSwitchIsOn} />
+          onValueChange={value => this.setState({trueSwitchIsOn: value})}
+          value={this.state.trueSwitchIsOn}
+        />
       </View>
     );
   }
@@ -42,13 +41,8 @@ class DisabledSwitchExample extends React.Component<{}> {
   render() {
     return (
       <View>
-        <Switch
-          disabled={true}
-          style={{marginBottom: 10}}
-          value={true} />
-        <Switch
-          disabled={true}
-          value={false} />
+        <Switch disabled={true} style={{marginBottom: 10}} value={true} />
+        <Switch disabled={true} value={false} />
       </View>
     );
   }
@@ -64,18 +58,20 @@ class ColorSwitchExample extends React.Component<{}, $FlowFixMeState> {
     return (
       <View>
         <Switch
-          onValueChange={(value) => this.setState({colorFalseSwitchIsOn: value})}
+          onValueChange={value => this.setState({colorFalseSwitchIsOn: value})}
           onTintColor="#00ff00"
           style={{marginBottom: 10}}
           thumbTintColor="#0000ff"
           tintColor="#ff0000"
-          value={this.state.colorFalseSwitchIsOn} />
+          value={this.state.colorFalseSwitchIsOn}
+        />
         <Switch
-          onValueChange={(value) => this.setState({colorTrueSwitchIsOn: value})}
+          onValueChange={value => this.setState({colorTrueSwitchIsOn: value})}
           onTintColor="#00ff00"
           thumbTintColor="#0000ff"
           tintColor="#ff0000"
-          value={this.state.colorTrueSwitchIsOn} />
+          value={this.state.colorTrueSwitchIsOn}
+        />
       </View>
     );
   }
@@ -89,27 +85,35 @@ class EventSwitchExample extends React.Component<{}, $FlowFixMeState> {
 
   render() {
     return (
-      <View style={{ flexDirection: 'row', justifyContent: 'space-around' }}>
+      <View style={{flexDirection: 'row', justifyContent: 'space-around'}}>
         <View>
           <Switch
-            onValueChange={(value) => this.setState({eventSwitchIsOn: value})}
+            onValueChange={value => this.setState({eventSwitchIsOn: value})}
             style={{marginBottom: 10}}
-            value={this.state.eventSwitchIsOn} />
+            value={this.state.eventSwitchIsOn}
+          />
           <Switch
-            onValueChange={(value) => this.setState({eventSwitchIsOn: value})}
+            onValueChange={value => this.setState({eventSwitchIsOn: value})}
             style={{marginBottom: 10}}
-            value={this.state.eventSwitchIsOn} />
+            value={this.state.eventSwitchIsOn}
+          />
           <Text>{this.state.eventSwitchIsOn ? 'On' : 'Off'}</Text>
         </View>
         <View>
           <Switch
-            onValueChange={(value) => this.setState({eventSwitchRegressionIsOn: value})}
+            onValueChange={value =>
+              this.setState({eventSwitchRegressionIsOn: value})
+            }
             style={{marginBottom: 10}}
-            value={this.state.eventSwitchRegressionIsOn} />
+            value={this.state.eventSwitchRegressionIsOn}
+          />
           <Switch
-            onValueChange={(value) => this.setState({eventSwitchRegressionIsOn: value})}
+            onValueChange={value =>
+              this.setState({eventSwitchRegressionIsOn: value})
+            }
             style={{marginBottom: 10}}
-            value={this.state.eventSwitchRegressionIsOn} />
+            value={this.state.eventSwitchRegressionIsOn}
+          />
           <Text>{this.state.eventSwitchRegressionIsOn ? 'On' : 'Off'}</Text>
         </View>
       </View>
@@ -120,24 +124,34 @@ class EventSwitchExample extends React.Component<{}, $FlowFixMeState> {
 var examples = [
   {
     title: 'Switches can be set to true or false',
-    render(): React.Element<any> { return <BasicSwitchExample />; }
+    render(): React.Element<any> {
+      return <BasicSwitchExample />;
+    },
   },
   {
     title: 'Switches can be disabled',
-    render(): React.Element<any> { return <DisabledSwitchExample />; }
+    render(): React.Element<any> {
+      return <DisabledSwitchExample />;
+    },
   },
   {
     title: 'Change events can be detected',
-    render(): React.Element<any> { return <EventSwitchExample />; }
+    render(): React.Element<any> {
+      return <EventSwitchExample />;
+    },
   },
   {
     title: 'Switches are controlled components',
-    render(): React.Element<any> { return <Switch />; }
+    render(): React.Element<any> {
+      return <Switch />;
+    },
   },
   {
     title: 'Custom colors can be provided',
-    render(): React.Element<any> { return <ColorSwitchExample />; }
-  }
+    render(): React.Element<any> {
+      return <ColorSwitchExample />;
+    },
+  },
 ];
 
 exports.title = '<Switch>';
diff --git a/RNTester/js/TVEventHandlerExample.js b/RNTester/js/TVEventHandlerExample.js
index 84067863268c..177614e7cf67 100644
--- a/RNTester/js/TVEventHandlerExample.js
+++ b/RNTester/js/TVEventHandlerExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -23,18 +25,25 @@ var {
 exports.framework = 'React';
 exports.title = 'TVEventHandler example';
 exports.description = 'iOS alerts and action sheets';
-exports.examples = [{
-  title: 'TVEventHandler',
-  render() {return <TVEventHandlerView/>;}
-}];
+exports.examples = [
+  {
+    title: 'TVEventHandler',
+    render() {
+      return <TVEventHandlerView />;
+    },
+  },
+];
 
-class TVEventHandlerView extends React.Component<$FlowFixMeProps, {
-  lastEventType: string
-}> {
+class TVEventHandlerView extends React.Component<
+  $FlowFixMeProps,
+  {
+    lastEventType: string,
+  },
+> {
   constructor(props) {
     super(props);
     this.state = {
-      lastEventType: ''
+      lastEventType: '',
     };
   }
 
@@ -44,7 +53,7 @@ class TVEventHandlerView extends React.Component<$FlowFixMeProps, {
     this._tvEventHandler = new TVEventHandler();
     this._tvEventHandler.enable(this, function(cmp, evt) {
       cmp.setState({
-        lastEventType: evt.eventType
+        lastEventType: evt.eventType,
       });
     });
   }
@@ -65,26 +74,23 @@ class TVEventHandlerView extends React.Component<$FlowFixMeProps, {
   }
 
   render() {
-
     if (Platform.isTVOS) {
       return (
         <View>
           <TouchableOpacity onPress={() => {}}>
-          <Text>
-            This example enables an instance of TVEventHandler to show the last event detected from the Apple TV Siri remote or from a keyboard.
-          </Text>
+            <Text>
+              This example enables an instance of TVEventHandler to show the
+              last event detected from the Apple TV Siri remote or from a
+              keyboard.
+            </Text>
           </TouchableOpacity>
-          <Text style={{color: 'blue'}}>
-            {this.state.lastEventType}
-          </Text>
+          <Text style={{color: 'blue'}}>{this.state.lastEventType}</Text>
         </View>
       );
     } else {
       return (
         <View>
-          <Text>
-            This example is intended to be run on Apple TV.
-          </Text>
+          <Text>This example is intended to be run on Apple TV.</Text>
         </View>
       );
     }
diff --git a/RNTester/js/TabBarIOSBarStyleExample.js b/RNTester/js/TabBarIOSBarStyleExample.js
index 972235698133..d6a035aed3e1 100644
--- a/RNTester/js/TabBarIOSBarStyleExample.js
+++ b/RNTester/js/TabBarIOSBarStyleExample.js
@@ -16,6 +16,7 @@
  * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  *
+ * @format
  * @flow
  */
 
@@ -23,14 +24,10 @@
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  TabBarIOS,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, TabBarIOS, Text, View} = ReactNative;
 
-var base64Icon = 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEsAAABLCAQAAACSR7JhAAADtUlEQVR4Ac3YA2Bj6QLH0XPT1Fzbtm29tW3btm3bfLZtv7e2ObZnms7d8Uw098tuetPzrxv8wiISrtVudrG2JXQZ4VOv+qUfmqCGGl1mqLhoA52oZlb0mrjsnhKpgeUNEs91Z0pd1kvihA3ULGVHiQO2narKSHKkEMulm9VgUyE60s1aWoMQUbpZOWE+kaqs4eLEjdIlZTcFZB0ndc1+lhB1lZrIuk5P2aib1NBpZaL+JaOGIt0ls47SKzLC7CqrlGF6RZ09HGoNy1lYl2aRSWL5GuzqWU1KafRdoRp0iOQEiDzgZPnG6DbldcomadViflnl/cL93tOoVbsOLVM2jylvdWjXolWX1hmfZbGR/wjypDjFLSZIRov09BgYmtUqPQPlQrPapecLgTIy0jMgPKtTeob2zWtrGH3xvjUkPCtNg/tm1rjwrMa+mdUkPd3hWbH0jArPGiU9ufCsNNWFZ40wpwn+62/66R2RUtoso1OB34tnLOcy7YB1fUdc9e0q3yru8PGM773vXsuZ5YIZX+5xmHwHGVvlrGPN6ZSiP1smOsMMde40wKv2VmwPPVXNut4sVpUreZiLBHi0qln/VQeI/LTMYXpsJtFiclUN+5HVZazim+Ky+7sAvxWnvjXrJFneVtLWLyPJu9K3cXLWeOlbMTlrIelbMDlrLenrjEQOtIF+fuI9xRp9ZBFp6+b6WT8RrxEpdK64BuvHgDk+vUy+b5hYk6zfyfs051gRoNO1usU12WWRWL73/MMEy9pMi9qIrR4ZpV16Rrvduxazmy1FSvuFXRkqTnE7m2kdb5U8xGjLw/spRr1uTov4uOgQE+0N/DvFrG/Jt7i/FzwxbA9kDanhf2w+t4V97G8lrT7wc08aA2QNUkuTfW/KimT01wdlfK4yEw030VfT0RtZbzjeMprNq8m8tnSTASrTLti64oBNdpmMQm0eEwvfPwRbUBywG5TzjPCsdwk3IeAXjQblLCoXnDVeoAz6SfJNk5TTzytCNZk/POtTSV40NwOFWzw86wNJRpubpXsn60NJFlHeqlYRbslqZm2jnEZ3qcSKgm0kTli3zZVS7y/iivZTweYXJ26Y+RTbV1zh3hYkgyFGSTKPfRVbRqWWVReaxYeSLarYv1Qqsmh1s95S7G+eEWK0f3jYKTbV6bOwepjfhtafsvUsqrQvrGC8YhmnO9cSCk3yuY984F1vesdHYhWJ5FvASlacshUsajFt2mUM9pqzvKGcyNJW0arTKN1GGGzQlH0tXwLDgQTurS8eIQAAAABJRU5ErkJggg==';
+var base64Icon =
+  'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEsAAABLCAQAAACSR7JhAAADtUlEQVR4Ac3YA2Bj6QLH0XPT1Fzbtm29tW3btm3bfLZtv7e2ObZnms7d8Uw098tuetPzrxv8wiISrtVudrG2JXQZ4VOv+qUfmqCGGl1mqLhoA52oZlb0mrjsnhKpgeUNEs91Z0pd1kvihA3ULGVHiQO2narKSHKkEMulm9VgUyE60s1aWoMQUbpZOWE+kaqs4eLEjdIlZTcFZB0ndc1+lhB1lZrIuk5P2aib1NBpZaL+JaOGIt0ls47SKzLC7CqrlGF6RZ09HGoNy1lYl2aRSWL5GuzqWU1KafRdoRp0iOQEiDzgZPnG6DbldcomadViflnl/cL93tOoVbsOLVM2jylvdWjXolWX1hmfZbGR/wjypDjFLSZIRov09BgYmtUqPQPlQrPapecLgTIy0jMgPKtTeob2zWtrGH3xvjUkPCtNg/tm1rjwrMa+mdUkPd3hWbH0jArPGiU9ufCsNNWFZ40wpwn+62/66R2RUtoso1OB34tnLOcy7YB1fUdc9e0q3yru8PGM773vXsuZ5YIZX+5xmHwHGVvlrGPN6ZSiP1smOsMMde40wKv2VmwPPVXNut4sVpUreZiLBHi0qln/VQeI/LTMYXpsJtFiclUN+5HVZazim+Ky+7sAvxWnvjXrJFneVtLWLyPJu9K3cXLWeOlbMTlrIelbMDlrLenrjEQOtIF+fuI9xRp9ZBFp6+b6WT8RrxEpdK64BuvHgDk+vUy+b5hYk6zfyfs051gRoNO1usU12WWRWL73/MMEy9pMi9qIrR4ZpV16Rrvduxazmy1FSvuFXRkqTnE7m2kdb5U8xGjLw/spRr1uTov4uOgQE+0N/DvFrG/Jt7i/FzwxbA9kDanhf2w+t4V97G8lrT7wc08aA2QNUkuTfW/KimT01wdlfK4yEw030VfT0RtZbzjeMprNq8m8tnSTASrTLti64oBNdpmMQm0eEwvfPwRbUBywG5TzjPCsdwk3IeAXjQblLCoXnDVeoAz6SfJNk5TTzytCNZk/POtTSV40NwOFWzw86wNJRpubpXsn60NJFlHeqlYRbslqZm2jnEZ3qcSKgm0kTli3zZVS7y/iivZTweYXJ26Y+RTbV1zh3hYkgyFGSTKPfRVbRqWWVReaxYeSLarYv1Qqsmh1s95S7G+eEWK0f3jYKTbV6bOwepjfhtafsvUsqrQvrGC8YhmnO9cSCk3yuY984F1vesdHYhWJ5FvASlacshUsajFt2mUM9pqzvKGcyNJW0arTKN1GGGzQlH0tXwLDgQTurS8eIQAAAABJRU5ErkJggg==';
 
 class TabBarIOSBarStyleExample extends React.Component<{}> {
   static title = '<TabBarIOS> - Custom Bar Style';
@@ -40,10 +37,7 @@ class TabBarIOSBarStyleExample extends React.Component<{}> {
   render() {
     return (
       <TabBarIOS barStyle="black">
-        <TabBarIOS.Item
-          title="Tab"
-          icon={{uri: base64Icon, scale: 3}}
-          selected>
+        <TabBarIOS.Item title="Tab" icon={{uri: base64Icon, scale: 3}} selected>
           <View style={styles.tabContent}>
             <Text style={styles.tabText}>Single page</Text>
           </View>
diff --git a/RNTester/js/TabBarIOSExample.js b/RNTester/js/TabBarIOSExample.js
index 12906b0e176e..38fcbc64f815 100644
--- a/RNTester/js/TabBarIOSExample.js
+++ b/RNTester/js/TabBarIOSExample.js
@@ -4,20 +4,18 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  TabBarIOS,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, TabBarIOS, Text, View} = ReactNative;
 
-var base64Icon = 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEsAAABLCAQAAACSR7JhAAADtUlEQVR4Ac3YA2Bj6QLH0XPT1Fzbtm29tW3btm3bfLZtv7e2ObZnms7d8Uw098tuetPzrxv8wiISrtVudrG2JXQZ4VOv+qUfmqCGGl1mqLhoA52oZlb0mrjsnhKpgeUNEs91Z0pd1kvihA3ULGVHiQO2narKSHKkEMulm9VgUyE60s1aWoMQUbpZOWE+kaqs4eLEjdIlZTcFZB0ndc1+lhB1lZrIuk5P2aib1NBpZaL+JaOGIt0ls47SKzLC7CqrlGF6RZ09HGoNy1lYl2aRSWL5GuzqWU1KafRdoRp0iOQEiDzgZPnG6DbldcomadViflnl/cL93tOoVbsOLVM2jylvdWjXolWX1hmfZbGR/wjypDjFLSZIRov09BgYmtUqPQPlQrPapecLgTIy0jMgPKtTeob2zWtrGH3xvjUkPCtNg/tm1rjwrMa+mdUkPd3hWbH0jArPGiU9ufCsNNWFZ40wpwn+62/66R2RUtoso1OB34tnLOcy7YB1fUdc9e0q3yru8PGM773vXsuZ5YIZX+5xmHwHGVvlrGPN6ZSiP1smOsMMde40wKv2VmwPPVXNut4sVpUreZiLBHi0qln/VQeI/LTMYXpsJtFiclUN+5HVZazim+Ky+7sAvxWnvjXrJFneVtLWLyPJu9K3cXLWeOlbMTlrIelbMDlrLenrjEQOtIF+fuI9xRp9ZBFp6+b6WT8RrxEpdK64BuvHgDk+vUy+b5hYk6zfyfs051gRoNO1usU12WWRWL73/MMEy9pMi9qIrR4ZpV16Rrvduxazmy1FSvuFXRkqTnE7m2kdb5U8xGjLw/spRr1uTov4uOgQE+0N/DvFrG/Jt7i/FzwxbA9kDanhf2w+t4V97G8lrT7wc08aA2QNUkuTfW/KimT01wdlfK4yEw030VfT0RtZbzjeMprNq8m8tnSTASrTLti64oBNdpmMQm0eEwvfPwRbUBywG5TzjPCsdwk3IeAXjQblLCoXnDVeoAz6SfJNk5TTzytCNZk/POtTSV40NwOFWzw86wNJRpubpXsn60NJFlHeqlYRbslqZm2jnEZ3qcSKgm0kTli3zZVS7y/iivZTweYXJ26Y+RTbV1zh3hYkgyFGSTKPfRVbRqWWVReaxYeSLarYv1Qqsmh1s95S7G+eEWK0f3jYKTbV6bOwepjfhtafsvUsqrQvrGC8YhmnO9cSCk3yuY984F1vesdHYhWJ5FvASlacshUsajFt2mUM9pqzvKGcyNJW0arTKN1GGGzQlH0tXwLDgQTurS8eIQAAAABJRU5ErkJggg==';
+var base64Icon =
+  'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAEsAAABLCAQAAACSR7JhAAADtUlEQVR4Ac3YA2Bj6QLH0XPT1Fzbtm29tW3btm3bfLZtv7e2ObZnms7d8Uw098tuetPzrxv8wiISrtVudrG2JXQZ4VOv+qUfmqCGGl1mqLhoA52oZlb0mrjsnhKpgeUNEs91Z0pd1kvihA3ULGVHiQO2narKSHKkEMulm9VgUyE60s1aWoMQUbpZOWE+kaqs4eLEjdIlZTcFZB0ndc1+lhB1lZrIuk5P2aib1NBpZaL+JaOGIt0ls47SKzLC7CqrlGF6RZ09HGoNy1lYl2aRSWL5GuzqWU1KafRdoRp0iOQEiDzgZPnG6DbldcomadViflnl/cL93tOoVbsOLVM2jylvdWjXolWX1hmfZbGR/wjypDjFLSZIRov09BgYmtUqPQPlQrPapecLgTIy0jMgPKtTeob2zWtrGH3xvjUkPCtNg/tm1rjwrMa+mdUkPd3hWbH0jArPGiU9ufCsNNWFZ40wpwn+62/66R2RUtoso1OB34tnLOcy7YB1fUdc9e0q3yru8PGM773vXsuZ5YIZX+5xmHwHGVvlrGPN6ZSiP1smOsMMde40wKv2VmwPPVXNut4sVpUreZiLBHi0qln/VQeI/LTMYXpsJtFiclUN+5HVZazim+Ky+7sAvxWnvjXrJFneVtLWLyPJu9K3cXLWeOlbMTlrIelbMDlrLenrjEQOtIF+fuI9xRp9ZBFp6+b6WT8RrxEpdK64BuvHgDk+vUy+b5hYk6zfyfs051gRoNO1usU12WWRWL73/MMEy9pMi9qIrR4ZpV16Rrvduxazmy1FSvuFXRkqTnE7m2kdb5U8xGjLw/spRr1uTov4uOgQE+0N/DvFrG/Jt7i/FzwxbA9kDanhf2w+t4V97G8lrT7wc08aA2QNUkuTfW/KimT01wdlfK4yEw030VfT0RtZbzjeMprNq8m8tnSTASrTLti64oBNdpmMQm0eEwvfPwRbUBywG5TzjPCsdwk3IeAXjQblLCoXnDVeoAz6SfJNk5TTzytCNZk/POtTSV40NwOFWzw86wNJRpubpXsn60NJFlHeqlYRbslqZm2jnEZ3qcSKgm0kTli3zZVS7y/iivZTweYXJ26Y+RTbV1zh3hYkgyFGSTKPfRVbRqWWVReaxYeSLarYv1Qqsmh1s95S7G+eEWK0f3jYKTbV6bOwepjfhtafsvUsqrQvrGC8YhmnO9cSCk3yuY984F1vesdHYhWJ5FvASlacshUsajFt2mUM9pqzvKGcyNJW0arTKN1GGGzQlH0tXwLDgQTurS8eIQAAAABJRU5ErkJggg==';
 
 class TabBarExample extends React.Component<{}, $FlowFixMeState> {
   static title = '<TabBarIOS>';
@@ -34,7 +32,9 @@ class TabBarExample extends React.Component<{}, $FlowFixMeState> {
     return (
       <View style={[styles.tabContent, {backgroundColor: color}]}>
         <Text style={styles.tabText}>{pageText}</Text>
-        <Text style={styles.tabText}>{num} re-renders of the {pageText}</Text>
+        <Text style={styles.tabText}>
+          {num} re-renders of the {pageText}
+        </Text>
       </View>
     );
   };
@@ -79,7 +79,7 @@ class TabBarExample extends React.Component<{}, $FlowFixMeState> {
           onPress={() => {
             this.setState({
               selectedTab: 'greenTab',
-              presses: this.state.presses + 1
+              presses: this.state.presses + 1,
             });
           }}>
           {this._renderContent('#21551C', 'Green Tab', this.state.presses)}
diff --git a/RNTester/js/TextExample.android.js b/RNTester/js/TextExample.android.js
index 6f824e01132e..e38a92702193 100644
--- a/RNTester/js/TextExample.android.js
+++ b/RNTester/js/TextExample.android.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Image,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Image, StyleSheet, Text, View} = ReactNative;
 var RNTesterBlock = require('./RNTesterBlock');
 var RNTesterPage = require('./RNTesterPage');
 
@@ -34,25 +31,31 @@ class AttributeToggler extends React.Component<{}, $FlowFixMeState> {
 
   toggleWeight = () => {
     this.setState({
-      fontWeight: this.state.fontWeight === 'bold' ? 'normal' : 'bold'
+      fontWeight: this.state.fontWeight === 'bold' ? 'normal' : 'bold',
     });
   };
 
   increaseSize = () => {
     this.setState({
-      fontSize: this.state.fontSize + 1
+      fontSize: this.state.fontSize + 1,
     });
   };
 
   render() {
-    var curStyle = {fontWeight: this.state.fontWeight, fontSize: this.state.fontSize};
+    var curStyle = {
+      fontWeight: this.state.fontWeight,
+      fontSize: this.state.fontSize,
+    };
     return (
       <View>
         <Text style={curStyle}>
           Tap the controls below to change attributes.
         </Text>
         <Text>
-          <Text>See how it will even work on <Text style={curStyle}>this nested text</Text></Text>
+          <Text>
+            See how it will even work on{' '}
+            <Text style={curStyle}>this nested text</Text>
+          </Text>
         </Text>
         <Text>
           <Text onPress={this.toggleWeight}>Toggle Weight</Text>
@@ -75,8 +78,8 @@ class TextExample extends React.Component<{}> {
       <RNTesterPage title="<Text>">
         <RNTesterBlock title="Wrap">
           <Text>
-            The text should wrap if it goes on multiple lines.
-            See, this is going to the next line.
+            The text should wrap if it goes on multiple lines. See, this is
+            going to the next line.
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Padding">
@@ -85,21 +88,15 @@ class TextExample extends React.Component<{}> {
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Font Family">
-          <Text style={{fontFamily: 'sans-serif'}}>
-            Sans-Serif
-          </Text>
+          <Text style={{fontFamily: 'sans-serif'}}>Sans-Serif</Text>
           <Text style={{fontFamily: 'sans-serif', fontWeight: 'bold'}}>
             Sans-Serif Bold
           </Text>
-          <Text style={{fontFamily: 'serif'}}>
-            Serif
-          </Text>
+          <Text style={{fontFamily: 'serif'}}>Serif</Text>
           <Text style={{fontFamily: 'serif', fontWeight: 'bold'}}>
             Serif Bold
           </Text>
-          <Text style={{fontFamily: 'monospace'}}>
-            Monospace
-          </Text>
+          <Text style={{fontFamily: 'monospace'}}>Monospace</Text>
           <Text style={{fontFamily: 'monospace', fontWeight: 'bold'}}>
             Monospace Bold (After 5.0)
           </Text>
@@ -107,49 +104,63 @@ class TextExample extends React.Component<{}> {
         <RNTesterBlock title="Android Material Design fonts">
           <View style={{flexDirection: 'row', alignItems: 'flex-start'}}>
             <View style={{flex: 1}}>
-              <Text style={{fontFamily: 'sans-serif'}}>
-                Roboto Regular
-              </Text>
+              <Text style={{fontFamily: 'sans-serif'}}>Roboto Regular</Text>
               <Text style={{fontFamily: 'sans-serif', fontStyle: 'italic'}}>
                 Roboto Italic
               </Text>
               <Text style={{fontFamily: 'sans-serif', fontWeight: 'bold'}}>
                 Roboto Bold
               </Text>
-              <Text style={{fontFamily: 'sans-serif', fontStyle: 'italic', fontWeight: 'bold'}}>
+              <Text
+                style={{
+                  fontFamily: 'sans-serif',
+                  fontStyle: 'italic',
+                  fontWeight: 'bold',
+                }}>
                 Roboto Bold Italic
               </Text>
-              <Text style={{fontFamily: 'sans-serif-light'}}>
-                Roboto Light
-              </Text>
-              <Text style={{fontFamily: 'sans-serif-light', fontStyle: 'italic'}}>
+              <Text style={{fontFamily: 'sans-serif-light'}}>Roboto Light</Text>
+              <Text
+                style={{fontFamily: 'sans-serif-light', fontStyle: 'italic'}}>
                 Roboto Light Italic
               </Text>
               <Text style={{fontFamily: 'sans-serif-thin'}}>
                 Roboto Thin (After 4.2)
               </Text>
-              <Text style={{fontFamily: 'sans-serif-thin', fontStyle: 'italic'}}>
+              <Text
+                style={{fontFamily: 'sans-serif-thin', fontStyle: 'italic'}}>
                 Roboto Thin Italic (After 4.2)
               </Text>
               <Text style={{fontFamily: 'sans-serif-condensed'}}>
                 Roboto Condensed
               </Text>
-              <Text style={{fontFamily: 'sans-serif-condensed', fontStyle: 'italic'}}>
+              <Text
+                style={{
+                  fontFamily: 'sans-serif-condensed',
+                  fontStyle: 'italic',
+                }}>
                 Roboto Condensed Italic
               </Text>
-              <Text style={{fontFamily: 'sans-serif-condensed', fontWeight: 'bold'}}>
+              <Text
+                style={{
+                  fontFamily: 'sans-serif-condensed',
+                  fontWeight: 'bold',
+                }}>
                 Roboto Condensed Bold
               </Text>
-              <Text style={{
+              <Text
+                style={{
                   fontFamily: 'sans-serif-condensed',
                   fontStyle: 'italic',
-                  fontWeight: 'bold'}}>
+                  fontWeight: 'bold',
+                }}>
                 Roboto Condensed Bold Italic
               </Text>
               <Text style={{fontFamily: 'sans-serif-medium'}}>
                 Roboto Medium (After 5.0)
               </Text>
-              <Text style={{fontFamily: 'sans-serif-medium', fontStyle: 'italic'}}>
+              <Text
+                style={{fontFamily: 'sans-serif-medium', fontStyle: 'italic'}}>
                 Roboto Medium Italic (After 5.0)
               </Text>
             </View>
@@ -158,10 +169,13 @@ class TextExample extends React.Component<{}> {
         <RNTesterBlock title="Custom Fonts">
           <View style={{flexDirection: 'row', alignItems: 'flex-start'}}>
             <View style={{flex: 1}}>
-              <Text style={{fontFamily: 'notoserif'}}>
-                NotoSerif Regular
-              </Text>
-              <Text style={{fontFamily: 'notoserif', fontStyle: 'italic', fontWeight: 'bold'}}>
+              <Text style={{fontFamily: 'notoserif'}}>NotoSerif Regular</Text>
+              <Text
+                style={{
+                  fontFamily: 'notoserif',
+                  fontStyle: 'italic',
+                  fontWeight: 'bold',
+                }}>
                 NotoSerif Bold Italic
               </Text>
               <Text style={{fontFamily: 'notoserif', fontStyle: 'italic'}}>
@@ -172,36 +186,20 @@ class TextExample extends React.Component<{}> {
         </RNTesterBlock>
 
         <RNTesterBlock title="Font Size">
-          <Text style={{fontSize: 23}}>
-            Size 23
-          </Text>
-          <Text style={{fontSize: 8}}>
-            Size 8
-          </Text>
+          <Text style={{fontSize: 23}}>Size 23</Text>
+          <Text style={{fontSize: 8}}>Size 8</Text>
         </RNTesterBlock>
         <RNTesterBlock title="Color">
-          <Text style={{color: 'red'}}>
-            Red color
-          </Text>
-          <Text style={{color: 'blue'}}>
-            Blue color
-          </Text>
+          <Text style={{color: 'red'}}>Red color</Text>
+          <Text style={{color: 'blue'}}>Blue color</Text>
         </RNTesterBlock>
         <RNTesterBlock title="Font Weight">
-          <Text style={{fontWeight: 'bold'}}>
-            Move fast and be bold
-          </Text>
-          <Text style={{fontWeight: 'normal'}}>
-            Move fast and be bold
-          </Text>
+          <Text style={{fontWeight: 'bold'}}>Move fast and be bold</Text>
+          <Text style={{fontWeight: 'normal'}}>Move fast and be bold</Text>
         </RNTesterBlock>
         <RNTesterBlock title="Font Style">
-          <Text style={{fontStyle: 'italic'}}>
-            Move fast and be bold
-          </Text>
-          <Text style={{fontStyle: 'normal'}}>
-            Move fast and be bold
-          </Text>
+          <Text style={{fontStyle: 'italic'}}>Move fast and be bold</Text>
+          <Text style={{fontStyle: 'normal'}}>Move fast and be bold</Text>
         </RNTesterBlock>
         <RNTesterBlock title="Font Style and Weight">
           <Text style={{fontStyle: 'italic', fontWeight: 'bold'}}>
@@ -209,20 +207,25 @@ class TextExample extends React.Component<{}> {
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Text Decoration">
-          <Text style={{textDecorationLine: 'underline'}}>
-            Solid underline
-          </Text>
-          <Text style={{textDecorationLine: 'none'}}>
-            None textDecoration
-          </Text>
-          <Text style={{textDecorationLine: 'line-through', textDecorationStyle: 'solid'}}>
+          <Text style={{textDecorationLine: 'underline'}}>Solid underline</Text>
+          <Text style={{textDecorationLine: 'none'}}>None textDecoration</Text>
+          <Text
+            style={{
+              textDecorationLine: 'line-through',
+              textDecorationStyle: 'solid',
+            }}>
             Solid line-through
           </Text>
           <Text style={{textDecorationLine: 'underline line-through'}}>
             Both underline and line-through
           </Text>
           <Text>
-            Mixed text with <Text style={{textDecorationLine: 'underline'}}>underline</Text> and <Text style={{textDecorationLine: 'line-through'}}>line-through</Text> text nodes
+            Mixed text with{' '}
+            <Text style={{textDecorationLine: 'underline'}}>underline</Text> and{' '}
+            <Text style={{textDecorationLine: 'line-through'}}>
+              line-through
+            </Text>{' '}
+            text nodes
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Nested">
@@ -249,11 +252,17 @@ class TextExample extends React.Component<{}> {
                 </Text>
               </Text>
             </Text>
-            <Text style={{fontWeight: 'bold'}} onPress={() => console.log('2nd')}>
+            <Text
+              style={{fontWeight: 'bold'}}
+              onPress={() => console.log('2nd')}>
               (and bold
-              <Text style={{fontStyle: 'italic', fontSize: 11, color: '#527fe4'}} onPress={() => console.log('3rd')}>
+              <Text
+                style={{fontStyle: 'italic', fontSize: 11, color: '#527fe4'}}
+                onPress={() => console.log('3rd')}>
                 (and tiny bold italic blue
-                <Text style={{fontWeight: 'normal', fontStyle: 'normal'}} onPress={() => console.log('4th')}>
+                <Text
+                  style={{fontWeight: 'normal', fontStyle: 'normal'}}
+                  onPress={() => console.log('4th')}>
                   (and tiny normal blue)
                 </Text>
                 )
@@ -262,19 +271,29 @@ class TextExample extends React.Component<{}> {
             </Text>
             )
           </Text>
-          <Text style={{fontFamily: 'serif'}} onPress={() => console.log('1st')}>
+          <Text
+            style={{fontFamily: 'serif'}}
+            onPress={() => console.log('1st')}>
             (Serif
-            <Text style={{fontStyle: 'italic', fontWeight: 'bold'}} onPress={() => console.log('2nd')}>
+            <Text
+              style={{fontStyle: 'italic', fontWeight: 'bold'}}
+              onPress={() => console.log('2nd')}>
               (Serif Bold Italic
               <Text
-                style={{fontFamily: 'monospace', fontStyle: 'normal', fontWeight: 'normal'}}
+                style={{
+                  fontFamily: 'monospace',
+                  fontStyle: 'normal',
+                  fontWeight: 'normal',
+                }}
                 onPress={() => console.log('3rd')}>
                 (Monospace Normal
                 <Text
                   style={{fontFamily: 'sans-serif', fontWeight: 'bold'}}
                   onPress={() => console.log('4th')}>
                   (Sans-Serif Bold
-                  <Text style={{fontWeight: 'normal'}} onPress={() => console.log('5th')}>
+                  <Text
+                    style={{fontWeight: 'normal'}}
+                    onPress={() => console.log('5th')}>
                     (and Sans-Serif Normal)
                   </Text>
                   )
@@ -290,20 +309,19 @@ class TextExample extends React.Component<{}> {
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Text Align">
-          <Text>
-            auto (default) - english LTR
-          </Text>
-          <Text>
-            أحب اللغة العربية auto (default) - arabic RTL
-          </Text>
+          <Text>auto (default) - english LTR</Text>
+          <Text>أحب اللغة العربية auto (default) - arabic RTL</Text>
           <Text style={{textAlign: 'left'}}>
-            left left left left left left left left left left left left left left left
+            left left left left left left left left left left left left left
+            left left
           </Text>
           <Text style={{textAlign: 'center'}}>
-            center center center center center center center center center center center
+            center center center center center center center center center
+            center center
           </Text>
           <Text style={{textAlign: 'right'}}>
-            right right right right right right right right right right right right right
+            right right right right right right right right right right right
+            right right
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Unicode">
@@ -332,19 +350,19 @@ class TextExample extends React.Component<{}> {
         </RNTesterBlock>
         <RNTesterBlock title="Spaces">
           <Text>
-            A {'generated'} {' '} {'string'} and    some &nbsp;&nbsp;&nbsp; spaces
+            A {'generated'} {'string'} and some &nbsp;&nbsp;&nbsp; spaces
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Line Height">
           <Text style={{lineHeight: 35}}>
-            Holisticly formulate inexpensive ideas before best-of-breed benefits. <Text style={{fontSize: 20}}>Continually</Text> expedite magnetic potentialities rather than client-focused interfaces.
+            Holisticly formulate inexpensive ideas before best-of-breed
+            benefits. <Text style={{fontSize: 20}}>Continually</Text> expedite
+            magnetic potentialities rather than client-focused interfaces.
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Letter Spacing">
           <View>
-            <Text style={{letterSpacing: 0}}>
-              letterSpacing = 0
-            </Text>
+            <Text style={{letterSpacing: 0}}>letterSpacing = 0</Text>
             <Text style={{letterSpacing: 2, marginTop: 5}}>
               letterSpacing = 2
             </Text>
@@ -352,14 +370,25 @@ class TextExample extends React.Component<{}> {
               letterSpacing = 9
             </Text>
             <View style={{flexDirection: 'row'}}>
-              <Text style={{fontSize: 12, letterSpacing: 2, backgroundColor: 'fuchsia', marginTop: 5}}>
+              <Text
+                style={{
+                  fontSize: 12,
+                  letterSpacing: 2,
+                  backgroundColor: 'fuchsia',
+                  marginTop: 5,
+                }}>
                 With size and background color
               </Text>
             </View>
             <Text style={{letterSpacing: -1, marginTop: 5}}>
               letterSpacing = -1
             </Text>
-            <Text style={{letterSpacing: 3, backgroundColor: '#dddddd', marginTop: 5}}>
+            <Text
+              style={{
+                letterSpacing: 3,
+                backgroundColor: '#dddddd',
+                marginTop: 5,
+              }}>
               [letterSpacing = 3]
               <Text style={{letterSpacing: 0, backgroundColor: '#bbbbbb'}}>
                 [Nested letterSpacing = 0]
@@ -380,11 +409,14 @@ class TextExample extends React.Component<{}> {
           <Text style={{backgroundColor: '#ffaaaa'}}>
             Red background,
             <Text style={{backgroundColor: '#aaaaff'}}>
-              {' '}blue background,
+              {' '}
+              blue background,
               <Text>
-                {' '}inherited blue background,
+                {' '}
+                inherited blue background,
                 <Text style={{backgroundColor: '#aaffaa'}}>
-                  {' '}nested green background.
+                  {' '}
+                  nested green background.
                 </Text>
               </Text>
             </Text>
@@ -407,24 +439,32 @@ class TextExample extends React.Component<{}> {
           <Text style={[styles.backgroundColorText, {top: -80}]}>
             Default containerBackgroundColor (inherited) + backgroundColor wash
           </Text>
-          <Text style={[styles.backgroundColorText, {top: -70, backgroundColor: 'transparent'}]}>
+          <Text
+            style={[
+              styles.backgroundColorText,
+              {top: -70, backgroundColor: 'transparent'},
+            ]}>
             {"containerBackgroundColor: 'transparent' + backgroundColor wash"}
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="numberOfLines attribute">
           <Text numberOfLines={1}>
-            Maximum of one line no matter now much I write here. If I keep writing it{"'"}ll just truncate after one line
+            Maximum of one line no matter now much I write here. If I keep
+            writing it{"'"}ll just truncate after one line
           </Text>
           <Text numberOfLines={2} style={{marginTop: 20}}>
-            Maximum of two lines no matter now much I write here. If I keep writing it{"'"}ll just truncate after two lines
+            Maximum of two lines no matter now much I write here. If I keep
+            writing it{"'"}ll just truncate after two lines
           </Text>
           <Text style={{marginTop: 20}}>
-            No maximum lines specified no matter now much I write here. If I keep writing it{"'"}ll just keep going and going
+            No maximum lines specified no matter now much I write here. If I
+            keep writing it{"'"}ll just keep going and going
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="selectable attribute">
           <Text selectable>
-            This text is selectable if you click-and-hold, and will offer the native Android selection menus.
+            This text is selectable if you click-and-hold, and will offer the
+            native Android selection menus.
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="selectionColor attribute">
@@ -434,11 +474,18 @@ class TextExample extends React.Component<{}> {
         </RNTesterBlock>
         <RNTesterBlock title="Inline images">
           <Text>
-            This text contains an inline image <Image source={require('./flux.png')}/>. Neat, huh?
+            This text contains an inline image{' '}
+            <Image source={require('./flux.png')} />. Neat, huh?
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Text shadow">
-          <Text style={{fontSize: 20, textShadowOffset: {width: 2, height: 2}, textShadowRadius: 1, textShadowColor: '#00cccc'}}>
+          <Text
+            style={{
+              fontSize: 20,
+              textShadowOffset: {width: 2, height: 2},
+              textShadowRadius: 1,
+              textShadowColor: '#00cccc',
+            }}>
             Demo text shadow
           </Text>
         </RNTesterBlock>
@@ -457,21 +504,32 @@ class TextExample extends React.Component<{}> {
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Include Font Padding">
-          <View style={{flexDirection: 'row', justifyContent: 'space-around', marginBottom: 10}}>
+          <View
+            style={{
+              flexDirection: 'row',
+              justifyContent: 'space-around',
+              marginBottom: 10,
+            }}>
             <View style={{alignItems: 'center'}}>
-              <Text style={styles.includeFontPaddingText}>
-                Ey
-              </Text>
+              <Text style={styles.includeFontPaddingText}>Ey</Text>
               <Text>Default</Text>
             </View>
             <View style={{alignItems: 'center'}}>
-              <Text style={[styles.includeFontPaddingText, {includeFontPadding: false, marginLeft: 10}]}>
+              <Text
+                style={[
+                  styles.includeFontPaddingText,
+                  {includeFontPadding: false, marginLeft: 10},
+                ]}>
                 Ey
               </Text>
               <Text>includeFontPadding: false</Text>
             </View>
           </View>
-          <Text>By default Android will put extra space above text to allow for upper-case accents or other ascenders. With some fonts, this can make text look slightly misaligned when centered vertically.</Text>
+          <Text>
+            By default Android will put extra space above text to allow for
+            upper-case accents or other ascenders. With some fonts, this can
+            make text look slightly misaligned when centered vertically.
+          </Text>
         </RNTesterBlock>
       </RNTesterPage>
     );
@@ -481,7 +539,7 @@ class TextExample extends React.Component<{}> {
 var styles = StyleSheet.create({
   backgroundColorText: {
     left: 5,
-    backgroundColor: 'rgba(100, 100, 100, 0.3)'
+    backgroundColor: 'rgba(100, 100, 100, 0.3)',
   },
   includeFontPaddingText: {
     fontSize: 120,
@@ -490,7 +548,7 @@ var styles = StyleSheet.create({
     color: '#000000',
     textAlignVertical: 'center',
     alignSelf: 'center',
-  }
+  },
 });
 
 module.exports = TextExample;
diff --git a/RNTester/js/TextExample.ios.js b/RNTester/js/TextExample.ios.js
index 968e0a42c8f8..6fdd942d4b84 100644
--- a/RNTester/js/TextExample.ios.js
+++ b/RNTester/js/TextExample.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Platform = require('Platform');
@@ -225,10 +227,16 @@ class TextBaseLineLayoutExample extends React.Component<*, *> {
   render() {
     var texts = [];
     for (var i = 9; i >= 0; i--) {
-      texts.push(<Text key={i} style={{fontSize: 8 + i * 5, backgroundColor: '#eee'}}>{i}</Text>);
+      texts.push(
+        <Text key={i} style={{fontSize: 8 + i * 5, backgroundColor: '#eee'}}>
+          {i}
+        </Text>,
+      );
     }
 
-    const marker = <View style={{width: 20, height: 20, backgroundColor: 'gray'}} />;
+    const marker = (
+      <View style={{width: 20, height: 20, backgroundColor: 'gray'}} />
+    );
     const subtitleStyle = {fontSize: 16, marginTop: 8, fontWeight: 'bold'};
 
     return (
@@ -236,9 +244,7 @@ class TextBaseLineLayoutExample extends React.Component<*, *> {
         <Text style={subtitleStyle}>{'Nested <Text/>s:'}</Text>
         <View style={{flexDirection: 'row', alignItems: 'baseline'}}>
           {marker}
-          <Text>
-            {texts}
-          </Text>
+          <Text>{texts}</Text>
           {marker}
         </View>
 
@@ -254,7 +260,12 @@ class TextBaseLineLayoutExample extends React.Component<*, *> {
           {marker}
           <Text selectable={true}>
             Some text.
-            <View style={{flexDirection: 'row', alignItems: 'baseline', backgroundColor: '#eee'}}>
+            <View
+              style={{
+                flexDirection: 'row',
+                alignItems: 'baseline',
+                backgroundColor: '#eee',
+              }}>
               {marker}
               <Text>Text inside View.</Text>
               {marker}
@@ -266,9 +277,7 @@ class TextBaseLineLayoutExample extends React.Component<*, *> {
         <Text style={subtitleStyle}>{'<TextInput/>:'}</Text>
         <View style={{flexDirection: 'row', alignItems: 'baseline'}}>
           {marker}
-          <TextInput style={{margin: 0, padding: 0}}>
-            {texts}
-          </TextInput>
+          <TextInput style={{margin: 0, padding: 0}}>{texts}</TextInput>
           {marker}
         </View>
 
@@ -575,14 +584,25 @@ exports.examples = [
             letterSpacing = 9
           </Text>
           <View style={{flexDirection: 'row'}}>
-            <Text style={{fontSize: 12, letterSpacing: 2, backgroundColor: 'fuchsia', marginTop: 5}}>
+            <Text
+              style={{
+                fontSize: 12,
+                letterSpacing: 2,
+                backgroundColor: 'fuchsia',
+                marginTop: 5,
+              }}>
               With size and background color
             </Text>
           </View>
           <Text style={{letterSpacing: -1, marginTop: 5}}>
             letterSpacing = -1
           </Text>
-          <Text style={{letterSpacing: 3, backgroundColor: '#dddddd', marginTop: 5}}>
+          <Text
+            style={{
+              letterSpacing: 3,
+              backgroundColor: '#dddddd',
+              marginTop: 5,
+            }}>
             [letterSpacing = 3]
             <Text style={{letterSpacing: 0, backgroundColor: '#bbbbbb'}}>
               [Nested letterSpacing = 0]
@@ -600,7 +620,7 @@ exports.examples = [
     render: function() {
       return (
         <Text>
-          A {'generated'} {' '} {'string'} and    some &nbsp;&nbsp;&nbsp; spaces
+          A {'generated'} {'string'} and some &nbsp;&nbsp;&nbsp; spaces
         </Text>
       );
     },
@@ -719,8 +739,9 @@ exports.examples = [
             </Text>
           </Text>
           <Text style={{marginTop: 10}}>
-            You can disable scaling for your Text component by passing {'"'}allowFontScaling={'{'}false{'}"'}{' '}
-            prop.
+            You can disable scaling for your Text component by passing {'"'}allowFontScaling={
+              '{'
+            }false{'}"'} prop.
           </Text>
           <Text allowFontScaling={false} style={{marginTop: 20}}>
             This text will not scale.
@@ -830,11 +851,15 @@ exports.examples = [
           This text has a view
           <View style={{borderColor: 'red', borderWidth: 1}}>
             <Text style={{borderColor: 'blue', borderWidth: 1}}>which has</Text>
-            <Text style={{borderColor: 'green', borderWidth: 1}}>another text inside.</Text>
+            <Text style={{borderColor: 'green', borderWidth: 1}}>
+              another text inside.
+            </Text>
             <Text style={{borderColor: 'yellow', borderWidth: 1}}>
               And moreover, it has another view
               <View style={{borderColor: 'red', borderWidth: 1}}>
-                <Text style={{borderColor: 'blue', borderWidth: 1}}>with another text inside!</Text>
+                <Text style={{borderColor: 'blue', borderWidth: 1}}>
+                  with another text inside!
+                </Text>
               </View>
             </Text>
           </View>
@@ -856,42 +881,43 @@ exports.examples = [
     },
   },
   {
-    title: 'Text `alignItems: \'baseline\'` style',
+    title: "Text `alignItems: 'baseline'` style",
     render: function() {
       return <TextBaseLineLayoutExample />;
-    }
+    },
   },
   {
     title: 'Transform',
     render: function() {
       return (
         <View>
-          <Text style={{ textTransform: 'uppercase'}}>
+          <Text style={{textTransform: 'uppercase'}}>
             This text should be uppercased.
           </Text>
-          <Text style={{ textTransform: 'lowercase'}}>
+          <Text style={{textTransform: 'lowercase'}}>
             This TEXT SHOULD be lowercased.
           </Text>
-          <Text style={{ textTransform: 'capitalize'}}>
+          <Text style={{textTransform: 'capitalize'}}>
             This text should be CAPITALIZED.
           </Text>
-          <Text style={{ textTransform: 'capitalize'}}>
-            Mixed:{' '}
-            <Text style={{ textTransform: 'uppercase'}}>
-              uppercase{' '}
-            </Text>
-            <Text style={{ textTransform: 'lowercase'}}>
-              LoWeRcAsE{' '}
-            </Text>
-            <Text style={{ textTransform: 'capitalize'}}>
+          <Text style={{textTransform: 'capitalize'}}>
+            Mixed: <Text style={{textTransform: 'uppercase'}}>uppercase </Text>
+            <Text style={{textTransform: 'lowercase'}}>LoWeRcAsE </Text>
+            <Text style={{textTransform: 'capitalize'}}>
               capitalize each word
             </Text>
           </Text>
-          <Text>Should be "ABC":
-            <Text style={{ textTransform: 'uppercase' }}>a<Text>b</Text>c</Text>
+          <Text>
+            Should be "ABC":
+            <Text style={{textTransform: 'uppercase'}}>
+              a<Text>b</Text>c
+            </Text>
           </Text>
-          <Text>Should be "AbC":
-            <Text style={{ textTransform: 'uppercase' }}>a<Text style={{ textTransform: 'none' }}>b</Text>c</Text>
+          <Text>
+            Should be "AbC":
+            <Text style={{textTransform: 'uppercase'}}>
+              a<Text style={{textTransform: 'none'}}>b</Text>c
+            </Text>
           </Text>
         </View>
       );
diff --git a/RNTester/js/TextInputExample.android.js b/RNTester/js/TextInputExample.android.js
index f0b3403d618f..30cee2eb29ac 100644
--- a/RNTester/js/TextInputExample.android.js
+++ b/RNTester/js/TextInputExample.android.js
@@ -4,20 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Text,
-  TextInput,
-  View,
-  StyleSheet,
-  Slider,
-  Switch,
-} = ReactNative;
+var {Text, TextInput, View, StyleSheet, Slider, Switch} = ReactNative;
 
 class TextEventsExample extends React.Component<{}, $FlowFixMeState> {
   state = {
@@ -27,8 +22,8 @@ class TextEventsExample extends React.Component<{}, $FlowFixMeState> {
     prev3Text: '<No Event>',
   };
 
-  updateText = (text) => {
-    this.setState((state) => {
+  updateText = text => {
+    this.setState(state => {
       return {
         curText: text,
         prevText: state.curText,
@@ -48,25 +43,28 @@ class TextEventsExample extends React.Component<{}, $FlowFixMeState> {
           multiline
           onFocus={() => this.updateText('onFocus')}
           onBlur={() => this.updateText('onBlur')}
-          onChange={(event) => this.updateText(
-            'onChange text: ' + event.nativeEvent.text
-          )}
-          onContentSizeChange={(event) => this.updateText(
-            'onContentSizeChange size: ' + event.nativeEvent.contentSize
-          )}
-          onEndEditing={(event) => this.updateText(
-            'onEndEditing text: ' + event.nativeEvent.text
-          )}
-          onSubmitEditing={(event) => this.updateText(
-            'onSubmitEditing text: ' + event.nativeEvent.text
-          )}
-          onKeyPress={(event) => this.updateText(
-            'onKeyPress key: ' + event.nativeEvent.key
-          )}
+          onChange={event =>
+            this.updateText('onChange text: ' + event.nativeEvent.text)
+          }
+          onContentSizeChange={event =>
+            this.updateText(
+              'onContentSizeChange size: ' + event.nativeEvent.contentSize,
+            )
+          }
+          onEndEditing={event =>
+            this.updateText('onEndEditing text: ' + event.nativeEvent.text)
+          }
+          onSubmitEditing={event =>
+            this.updateText('onSubmitEditing text: ' + event.nativeEvent.text)
+          }
+          onKeyPress={event =>
+            this.updateText('onKeyPress key: ' + event.nativeEvent.key)
+          }
           style={styles.singleLine}
         />
         <Text style={styles.eventLabel}>
-          {this.state.curText}{'\n'}
+          {this.state.curText}
+          {'\n'}
           (prev: {this.state.prevText}){'\n'}
           (prev2: {this.state.prev2Text}){'\n'}
           (prev3: {this.state.prev3Text})
@@ -90,7 +88,7 @@ class RewriteExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
         <TextInput
           multiline={false}
           maxLength={limit}
-          onChangeText={(text) => {
+          onChangeText={text => {
             text = text.replace(/ /g, '_');
             this.setState({text});
           }}
@@ -105,19 +103,23 @@ class RewriteExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
   }
 }
 
-class TokenizedTextExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class TokenizedTextExample extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   constructor(props) {
     super(props);
     this.state = {text: 'Hello #World'};
   }
   render() {
-
     //define delimiter
     let delimiter = /\s+/;
 
     //split string
     let _text = this.state.text;
-    let token, index, parts = [];
+    let token,
+      index,
+      parts = [];
     while (_text) {
       delimiter.lastIndex = 0;
       token = delimiter.exec(_text);
@@ -136,9 +138,13 @@ class TokenizedTextExample extends React.Component<$FlowFixMeProps, $FlowFixMeSt
     parts.push(_text);
 
     //highlight hashtags
-    parts = parts.map((text) => {
+    parts = parts.map(text => {
       if (/^#/.test(text)) {
-        return <Text key={text} style={styles.hashtag}>{text}</Text>;
+        return (
+          <Text key={text} style={styles.hashtag}>
+            {text}
+          </Text>
+        );
       } else {
         return text;
       }
@@ -149,7 +155,7 @@ class TokenizedTextExample extends React.Component<$FlowFixMeProps, $FlowFixMeSt
         <TextInput
           multiline={true}
           style={styles.multiline}
-          onChangeText={(text) => {
+          onChangeText={text => {
             this.setState({text});
           }}>
           <Text>{parts}</Text>
@@ -160,7 +166,7 @@ class TokenizedTextExample extends React.Component<$FlowFixMeProps, $FlowFixMeSt
 }
 
 class BlurOnSubmitExample extends React.Component<{}> {
-  focusNextField = (nextField) => {
+  focusNextField = nextField => {
     this.refs[nextField].focus();
   };
 
@@ -213,7 +219,10 @@ class BlurOnSubmitExample extends React.Component<{}> {
   }
 }
 
-class ToggleDefaultPaddingExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class ToggleDefaultPaddingExample extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   constructor(props) {
     super(props);
     this.state = {hasPadding: false};
@@ -221,8 +230,9 @@ class ToggleDefaultPaddingExample extends React.Component<$FlowFixMeProps, $Flow
   render() {
     return (
       <View>
-        <TextInput style={this.state.hasPadding ? { padding: 0 } : null}/>
-        <Text onPress={() => this.setState({hasPadding: !this.state.hasPadding})}>
+        <TextInput style={this.state.hasPadding ? {padding: 0} : null} />
+        <Text
+          onPress={() => this.setState({hasPadding: !this.state.hasPadding})}>
           Toggle padding
         </Text>
       </View>
@@ -232,20 +242,23 @@ class ToggleDefaultPaddingExample extends React.Component<$FlowFixMeProps, $Flow
 
 type SelectionExampleState = {
   selection: {
-    start: number;
-    end: number;
-  };
-  value: string;
+    start: number,
+    end: number,
+  },
+  value: string,
 };
 
-class SelectionExample extends React.Component<$FlowFixMeProps, SelectionExampleState> {
+class SelectionExample extends React.Component<
+  $FlowFixMeProps,
+  SelectionExampleState,
+> {
   _textInput: any;
 
   constructor(props) {
     super(props);
     this.state = {
       selection: {start: 0, end: 0},
-      value: props.value
+      value: props.value,
     };
   }
 
@@ -283,7 +296,7 @@ class SelectionExample extends React.Component<$FlowFixMeProps, SelectionExample
       <View>
         <TextInput
           multiline={this.props.multiline}
-          onChangeText={(value) => this.setState({value})}
+          onChangeText={value => this.setState({value})}
           onSelectionChange={this.onSelectionChange.bind(this)}
           ref={textInput => (this._textInput = textInput)}
           selection={this.state.selection}
@@ -291,24 +304,16 @@ class SelectionExample extends React.Component<$FlowFixMeProps, SelectionExample
           value={this.state.value}
         />
         <View>
-          <Text>
-            selection = {JSON.stringify(this.state.selection)}
-          </Text>
+          <Text>selection = {JSON.stringify(this.state.selection)}</Text>
           <Text onPress={this.placeAt.bind(this, 0)}>
             Place at Start (0, 0)
           </Text>
           <Text onPress={this.placeAt.bind(this, length)}>
             Place at End ({length}, {length})
           </Text>
-          <Text onPress={this.placeAtRandom.bind(this)}>
-            Place at Random
-          </Text>
-          <Text onPress={this.select.bind(this, 0, length)}>
-            Select All
-          </Text>
-          <Text onPress={this.selectRandom.bind(this)}>
-            Select Random
-          </Text>
+          <Text onPress={this.placeAtRandom.bind(this)}>Place at Random</Text>
+          <Text onPress={this.select.bind(this, 0, length)}>Select All</Text>
+          <Text onPress={this.selectRandom.bind(this)}>Select Random</Text>
         </View>
       </View>
     );
@@ -316,7 +321,6 @@ class SelectionExample extends React.Component<$FlowFixMeProps, SelectionExample
 }
 
 class AutogrowingTextInputExample extends React.Component<{}> {
-
   constructor(props) {
     super(props);
 
@@ -347,19 +351,21 @@ class AutogrowingTextInputExample extends React.Component<{}> {
           minimumValue={0}
           maximumValue={100}
           step={10}
-          onValueChange={(value) => this.setState({width: value})}
+          onValueChange={value => this.setState({width: value})}
         />
         <Text>Multiline:</Text>
         <Switch
           value={this.state.multiline}
-          onValueChange={(value) => this.setState({multiline: value})}
+          onValueChange={value => this.setState({multiline: value})}
         />
         <Text>TextInput:</Text>
         <TextInput
           multiline={this.state.multiline}
           style={[style, {width: this.state.width + '%'}]}
-          onChangeText={(value) => this.setState({text: value})}
-          onContentSizeChange={(event) => this.setState({contentSize: event.nativeEvent.contentSize})}
+          onChangeText={value => this.setState({text: value})}
+          onContentSizeChange={event =>
+            this.setState({contentSize: event.nativeEvent.contentSize})
+          }
           {...props}
         />
         <Text>Plain text value representation:</Text>
@@ -405,24 +411,19 @@ exports.examples = [
           accessibilityLabel="I am the accessibility label for text input"
         />
       );
-    }
+    },
   },
   {
     title: "Live Re-Write (<sp>  ->  '_')",
     render: function() {
       return <RewriteExample />;
-    }
+    },
   },
   {
     title: 'Auto-capitalize',
     render: function() {
-      var autoCapitalizeTypes = [
-        'none',
-        'sentences',
-        'words',
-        'characters',
-      ];
-      var examples = autoCapitalizeTypes.map((type) => {
+      var autoCapitalizeTypes = ['none', 'sentences', 'words', 'characters'];
+      var examples = autoCapitalizeTypes.map(type => {
         return (
           <TextInput
             key={type}
@@ -433,7 +434,7 @@ exports.examples = [
         );
       });
       return <View>{examples}</View>;
-    }
+    },
   },
   {
     title: 'Auto-correct',
@@ -452,18 +453,13 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Keyboard types',
     render: function() {
-      var keyboardTypes = [
-        'default',
-        'email-address',
-        'numeric',
-        'phone-pad',
-      ];
-      var examples = keyboardTypes.map((type) => {
+      var keyboardTypes = ['default', 'email-address', 'numeric', 'phone-pad'];
+      var examples = keyboardTypes.map(type => {
         return (
           <TextInput
             key={type}
@@ -474,15 +470,19 @@ exports.examples = [
         );
       });
       return <View>{examples}</View>;
-    }
+    },
   },
   {
     title: 'Blur on submit',
-    render: function(): React.Element<any> { return <BlurOnSubmitExample />; },
+    render: function(): React.Element<any> {
+      return <BlurOnSubmitExample />;
+    },
   },
   {
     title: 'Event handling',
-    render: function(): React.Element<any> { return <TextEventsExample />; },
+    render: function(): React.Element<any> {
+      return <TextEventsExample />;
+    },
   },
   {
     title: 'Colors and text inputs',
@@ -517,7 +517,10 @@ exports.examples = [
           />
           <TextInput
             defaultValue="Same BackgroundColor as View "
-            style={[styles.singleLine, {backgroundColor: 'rgba(100, 100, 100, 0.3)'}]}>
+            style={[
+              styles.singleLine,
+              {backgroundColor: 'rgba(100, 100, 100, 0.3)'},
+            ]}>
             <Text style={{backgroundColor: 'rgba(100, 100, 100, 0.3)'}}>
               Darker backgroundColor
             </Text>
@@ -525,10 +528,11 @@ exports.examples = [
           <TextInput
             defaultValue="Highlight Color is red"
             selectionColor={'red'}
-            style={styles.singleLine} />
+            style={styles.singleLine}
+          />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Text input, themes and heights',
@@ -539,7 +543,7 @@ exports.examples = [
           style={[styles.singleLineWithHeightTextInput]}
         />
       );
-    }
+    },
   },
   {
     title: 'fontFamily, fontWeight and fontStyle',
@@ -551,11 +555,17 @@ exports.examples = [
             placeholder="Custom fonts like Sans-Serif are supported"
           />
           <TextInput
-            style={[styles.singleLine, {fontFamily: 'sans-serif', fontWeight: 'bold'}]}
+            style={[
+              styles.singleLine,
+              {fontFamily: 'sans-serif', fontWeight: 'bold'},
+            ]}
             placeholder="Sans-Serif bold"
           />
           <TextInput
-            style={[styles.singleLine, {fontFamily: 'sans-serif', fontStyle: 'italic'}]}
+            style={[
+              styles.singleLine,
+              {fontFamily: 'sans-serif', fontStyle: 'italic'},
+            ]}
             placeholder="Sans-Serif italic"
           />
           <TextInput
@@ -564,7 +574,7 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'letterSpacing',
@@ -589,7 +599,7 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Passwords',
@@ -609,19 +619,19 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Editable',
     render: function() {
       return (
         <TextInput
-           defaultValue="Can't touch this! (>'-')> ^(' - ')^ <('-'<) (>'-')> ^(' - ')^"
-           editable={false}
-           style={styles.singleLine}
-         />
+          defaultValue="Can't touch this! (>'-')> ^(' - ')^ <('-'<) (>'-')> ^(' - ')^"
+          editable={false}
+          style={styles.singleLine}
+        />
       );
-    }
+    },
   },
   {
     title: 'Multiline',
@@ -633,24 +643,36 @@ exports.examples = [
             placeholder="multiline, aligned top-left"
             placeholderTextColor="red"
             multiline={true}
-            style={[styles.multiline, {textAlign: 'left', textAlignVertical: 'top'}]}
+            style={[
+              styles.multiline,
+              {textAlign: 'left', textAlignVertical: 'top'},
+            ]}
           />
           <TextInput
             autoCorrect={true}
             placeholder="multiline, aligned center"
             placeholderTextColor="green"
             multiline={true}
-            style={[styles.multiline, {textAlign: 'center', textAlignVertical: 'center'}]}
+            style={[
+              styles.multiline,
+              {textAlign: 'center', textAlignVertical: 'center'},
+            ]}
           />
           <TextInput
             autoCorrect={true}
             multiline={true}
-            style={[styles.multiline, {color: 'blue'}, {textAlign: 'right', textAlignVertical: 'bottom'}]}>
-            <Text style={styles.multiline}>multiline with children, aligned bottom-right</Text>
+            style={[
+              styles.multiline,
+              {color: 'blue'},
+              {textAlign: 'right', textAlignVertical: 'bottom'},
+            ]}>
+            <Text style={styles.multiline}>
+              multiline with children, aligned bottom-right
+            </Text>
           </TextInput>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Fixed number of lines',
@@ -658,17 +680,19 @@ exports.examples = [
     render: function() {
       return (
         <View>
-          <TextInput numberOfLines={2}
+          <TextInput
+            numberOfLines={2}
             multiline={true}
             placeholder="Two line input"
           />
-          <TextInput numberOfLines={5}
+          <TextInput
+            numberOfLines={5}
             multiline={true}
             placeholder="Five line input"
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Auto-expanding',
@@ -679,8 +703,7 @@ exports.examples = [
             enablesReturnKeyAutomatically={true}
             returnKeyType="done"
             multiline={true}
-            style={{maxHeight: 400, minHeight: 20, backgroundColor: '#eeeeee'}}
-          >
+            style={{maxHeight: 400, minHeight: 20, backgroundColor: '#eeeeee'}}>
             generic generic generic
             <Text style={{fontSize: 6, color: 'red'}}>
               small small small small small small
@@ -693,13 +716,13 @@ exports.examples = [
           </AutogrowingTextInputExample>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Attributed text',
     render: function() {
       return <TokenizedTextExample />;
-    }
+    },
   },
   {
     title: 'Return key',
@@ -713,11 +736,8 @@ exports.examples = [
         'previous',
         'next',
       ];
-      var returnKeyLabels = [
-        'Compile',
-        'React Native',
-      ];
-      var examples = returnKeyTypes.map((type) => {
+      var returnKeyLabels = ['Compile', 'React Native'];
+      var examples = returnKeyTypes.map(type => {
         return (
           <TextInput
             key={type}
@@ -727,7 +747,7 @@ exports.examples = [
           />
         );
       });
-      var types = returnKeyLabels.map((type) => {
+      var types = returnKeyLabels.map(type => {
         return (
           <TextInput
             key={type}
@@ -737,8 +757,13 @@ exports.examples = [
           />
         );
       });
-      return <View>{examples}{types}</View>;
-    }
+      return (
+        <View>
+          {examples}
+          {types}
+        </View>
+      );
+    },
   },
   {
     title: 'Inline Images',
@@ -762,11 +787,13 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Toggle Default Padding',
-    render: function(): React.Element<any> { return <ToggleDefaultPaddingExample />; },
+    render: function(): React.Element<any> {
+      return <ToggleDefaultPaddingExample />;
+    },
   },
   {
     title: 'Text selection & cursor placement',
@@ -784,6 +811,6 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
 ];
diff --git a/RNTester/js/TextInputExample.ios.js b/RNTester/js/TextInputExample.ios.js
index 704278796f06..0d53264772e3 100644
--- a/RNTester/js/TextInputExample.ios.js
+++ b/RNTester/js/TextInputExample.ios.js
@@ -4,22 +4,17 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const Button = require('Button');
 const InputAccessoryView = require('InputAccessoryView');
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Text,
-  TextInput,
-  View,
-  StyleSheet,
-  Slider,
-  Switch,
-} = ReactNative;
+var {Text, TextInput, View, StyleSheet, Slider, Switch} = ReactNative;
 
 class WithLabel extends React.Component<$FlowFixMeProps> {
   render() {
@@ -42,8 +37,8 @@ class TextEventsExample extends React.Component<{}, $FlowFixMeState> {
     prev3Text: '<No Event>',
   };
 
-  updateText = (text) => {
-    this.setState((state) => {
+  updateText = text => {
+    this.setState(state => {
       return {
         curText: text,
         prevText: state.curText,
@@ -62,27 +57,31 @@ class TextEventsExample extends React.Component<{}, $FlowFixMeState> {
           autoCorrect={false}
           onFocus={() => this.updateText('onFocus')}
           onBlur={() => this.updateText('onBlur')}
-          onChange={(event) => this.updateText(
-            'onChange text: ' + event.nativeEvent.text
-          )}
-          onEndEditing={(event) => this.updateText(
-            'onEndEditing text: ' + event.nativeEvent.text
-          )}
-          onSubmitEditing={(event) => this.updateText(
-            'onSubmitEditing text: ' + event.nativeEvent.text
-          )}
-          onSelectionChange={(event) => this.updateText(
-            'onSelectionChange range: ' +
-              event.nativeEvent.selection.start + ',' +
-              event.nativeEvent.selection.end
-          )}
-          onKeyPress={(event) => {
+          onChange={event =>
+            this.updateText('onChange text: ' + event.nativeEvent.text)
+          }
+          onEndEditing={event =>
+            this.updateText('onEndEditing text: ' + event.nativeEvent.text)
+          }
+          onSubmitEditing={event =>
+            this.updateText('onSubmitEditing text: ' + event.nativeEvent.text)
+          }
+          onSelectionChange={event =>
+            this.updateText(
+              'onSelectionChange range: ' +
+                event.nativeEvent.selection.start +
+                ',' +
+                event.nativeEvent.selection.end,
+            )
+          }
+          onKeyPress={event => {
             this.updateText('onKeyPress key: ' + event.nativeEvent.key);
           }}
           style={styles.default}
         />
         <Text style={styles.eventLabel}>
-          {this.state.curText}{'\n'}
+          {this.state.curText}
+          {'\n'}
           (prev: {this.state.prevText}){'\n'}
           (prev2: {this.state.prev2Text}){'\n'}
           (prev3: {this.state.prev3Text})
@@ -135,7 +134,7 @@ class RewriteExample extends React.Component<$FlowFixMeProps, any> {
         <TextInput
           multiline={false}
           maxLength={limit}
-          onChangeText={(text) => {
+          onChangeText={text => {
             text = text.replace(/ /g, '_');
             this.setState({text});
           }}
@@ -150,7 +149,10 @@ class RewriteExample extends React.Component<$FlowFixMeProps, any> {
   }
 }
 
-class RewriteExampleInvalidCharacters extends React.Component<$FlowFixMeProps, any> {
+class RewriteExampleInvalidCharacters extends React.Component<
+  $FlowFixMeProps,
+  any,
+> {
   constructor(props) {
     super(props);
     this.state = {text: ''};
@@ -160,7 +162,7 @@ class RewriteExampleInvalidCharacters extends React.Component<$FlowFixMeProps, a
       <View style={styles.rewriteContainer}>
         <TextInput
           multiline={false}
-          onChangeText={(text) => {
+          onChangeText={text => {
             this.setState({text: text.replace(/\s/g, '')});
           }}
           style={styles.default}
@@ -177,13 +179,14 @@ class TokenizedTextExample extends React.Component<$FlowFixMeProps, any> {
     this.state = {text: 'Hello #World'};
   }
   render() {
-
     //define delimiter
     let delimiter = /\s+/;
 
     //split string
     let _text = this.state.text;
-    let token, index, parts = [];
+    let token,
+      index,
+      parts = [];
     while (_text) {
       delimiter.lastIndex = 0;
       token = delimiter.exec(_text);
@@ -202,9 +205,13 @@ class TokenizedTextExample extends React.Component<$FlowFixMeProps, any> {
     parts.push(_text);
 
     //highlight hashtags
-    parts = parts.map((text) => {
+    parts = parts.map(text => {
       if (/^#/.test(text)) {
-        return <Text key={text} style={styles.hashtag}>{text}</Text>;
+        return (
+          <Text key={text} style={styles.hashtag}>
+            {text}
+          </Text>
+        );
       } else {
         return text;
       }
@@ -215,7 +222,7 @@ class TokenizedTextExample extends React.Component<$FlowFixMeProps, any> {
         <TextInput
           multiline={true}
           style={styles.multiline}
-          onChangeText={(text) => {
+          onChangeText={text => {
             this.setState({text});
           }}>
           <Text>{parts}</Text>
@@ -226,7 +233,7 @@ class TokenizedTextExample extends React.Component<$FlowFixMeProps, any> {
 }
 
 class BlurOnSubmitExample extends React.Component<{}> {
-  focusNextField = (nextField) => {
+  focusNextField = nextField => {
     this.refs[nextField].focus();
   };
 
@@ -282,20 +289,23 @@ class BlurOnSubmitExample extends React.Component<{}> {
 
 type SelectionExampleState = {
   selection: {
-    start: number;
-    end?: number;
-  };
-  value: string;
+    start: number,
+    end?: number,
+  },
+  value: string,
 };
 
-class SelectionExample extends React.Component<$FlowFixMeProps, SelectionExampleState> {
+class SelectionExample extends React.Component<
+  $FlowFixMeProps,
+  SelectionExampleState,
+> {
   _textInput: any;
 
   constructor(props) {
     super(props);
     this.state = {
       selection: {start: 0, end: 0},
-      value: props.value
+      value: props.value,
     };
   }
 
@@ -314,7 +324,9 @@ class SelectionExample extends React.Component<$FlowFixMeProps, SelectionExample
   }
 
   selectRandom() {
-    var positions = [this.getRandomPosition(), this.getRandomPosition()].sort((a, b) => a - b);
+    var positions = [this.getRandomPosition(), this.getRandomPosition()].sort(
+      (a, b) => a - b,
+    );
     this.select(...positions);
   }
 
@@ -333,7 +345,7 @@ class SelectionExample extends React.Component<$FlowFixMeProps, SelectionExample
       <View>
         <TextInput
           multiline={this.props.multiline}
-          onChangeText={(value) => this.setState({value})}
+          onChangeText={value => this.setState({value})}
           onSelectionChange={this.onSelectionChange.bind(this)}
           ref={textInput => (this._textInput = textInput)}
           selection={this.state.selection}
@@ -341,31 +353,26 @@ class SelectionExample extends React.Component<$FlowFixMeProps, SelectionExample
           value={this.state.value}
         />
         <View>
-          <Text>
-            selection = {JSON.stringify(this.state.selection)}
-          </Text>
+          <Text>selection = {JSON.stringify(this.state.selection)}</Text>
           <Text onPress={this.placeAt.bind(this, 0)}>
             Place at Start (0, 0)
           </Text>
           <Text onPress={this.placeAt.bind(this, length)}>
             Place at End ({length}, {length})
           </Text>
-          <Text onPress={this.placeAtRandom.bind(this)}>
-            Place at Random
-          </Text>
-          <Text onPress={this.select.bind(this, 0, length)}>
-            Select All
-          </Text>
-          <Text onPress={this.selectRandom.bind(this)}>
-            Select Random
-          </Text>
+          <Text onPress={this.placeAtRandom.bind(this)}>Place at Random</Text>
+          <Text onPress={this.select.bind(this, 0, length)}>Select All</Text>
+          <Text onPress={this.selectRandom.bind(this)}>Select Random</Text>
         </View>
       </View>
     );
   }
 }
 
-class AutogrowingTextInputExample extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+class AutogrowingTextInputExample extends React.Component<
+  $FlowFixMeProps,
+  $FlowFixMeState,
+> {
   constructor(props) {
     super(props);
 
@@ -396,20 +403,22 @@ class AutogrowingTextInputExample extends React.Component<$FlowFixMeProps, $Flow
           minimumValue={0}
           maximumValue={100}
           step={10}
-          onValueChange={(value) => this.setState({width: value})}
+          onValueChange={value => this.setState({width: value})}
         />
         <Text>Multiline:</Text>
         <Switch
           value={this.state.multiline}
-          onValueChange={(value) => this.setState({multiline: value})}
+          onValueChange={value => this.setState({multiline: value})}
         />
         <Text>TextInput:</Text>
         <TextInput
           value="prop"
           multiline={this.state.multiline}
           style={[style, {width: this.state.width + '%'}]}
-          onChangeText={(value) => this.setState({text: value})}
-          onContentSizeChange={(event) => this.setState({contentSize: event.nativeEvent.contentSize})}
+          onChangeText={value => this.setState({text: value})}
+          onContentSizeChange={event =>
+            this.setState({contentSize: event.nativeEvent.contentSize})
+          }
           {...props}
         />
         <Text>Plain text value representation:</Text>
@@ -501,25 +510,25 @@ exports.examples = [
           accessibilityLabel="I am the accessibility label for text input"
         />
       );
-    }
+    },
   },
   {
     title: "Live Re-Write (<sp>  ->  '_') + maxLength",
     render: function() {
       return <RewriteExample />;
-    }
+    },
   },
   {
     title: 'Live Re-Write (no spaces allowed)',
     render: function() {
       return <RewriteExampleInvalidCharacters />;
-    }
+    },
   },
   {
     title: 'Keyboard Accessory View',
     render: function() {
       return <TextInputAccessoryViewExample />;
-    }
+    },
   },
   {
     title: 'Auto-capitalize',
@@ -527,32 +536,20 @@ exports.examples = [
       return (
         <View>
           <WithLabel label="none">
-            <TextInput
-              autoCapitalize="none"
-              style={styles.default}
-            />
+            <TextInput autoCapitalize="none" style={styles.default} />
           </WithLabel>
           <WithLabel label="sentences">
-            <TextInput
-              autoCapitalize="sentences"
-              style={styles.default}
-            />
+            <TextInput autoCapitalize="sentences" style={styles.default} />
           </WithLabel>
           <WithLabel label="words">
-            <TextInput
-              autoCapitalize="words"
-              style={styles.default}
-            />
+            <TextInput autoCapitalize="words" style={styles.default} />
           </WithLabel>
           <WithLabel label="characters">
-            <TextInput
-              autoCapitalize="characters"
-              style={styles.default}
-            />
+            <TextInput autoCapitalize="characters" style={styles.default} />
           </WithLabel>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Auto-correct',
@@ -567,7 +564,7 @@ exports.examples = [
           </WithLabel>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Nested content and `value` property',
@@ -582,7 +579,10 @@ exports.examples = [
             </TextInput>
           </WithLabel>
           <WithLabel label="multiline">
-            <TextInput style={styles.default} multiline={true} value="(value property)">
+            <TextInput
+              style={styles.default}
+              multiline={true}
+              value="(value property)">
               (first raw text node)
               <Text color="red">(internal raw text node)</Text>
               (last raw text node)
@@ -590,7 +590,7 @@ exports.examples = [
           </WithLabel>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Keyboard types',
@@ -609,39 +609,29 @@ exports.examples = [
         'web-search',
         'numeric',
       ];
-      var examples = keyboardTypes.map((type) => {
+      var examples = keyboardTypes.map(type => {
         return (
           <WithLabel key={type} label={type}>
-            <TextInput
-              keyboardType={type}
-              style={styles.default}
-            />
+            <TextInput keyboardType={type} style={styles.default} />
           </WithLabel>
         );
       });
       return <View>{examples}</View>;
-    }
+    },
   },
   {
     title: 'Keyboard appearance',
     render: function() {
-      var keyboardAppearance = [
-        'default',
-        'light',
-        'dark',
-      ];
-      var examples = keyboardAppearance.map((type) => {
+      var keyboardAppearance = ['default', 'light', 'dark'];
+      var examples = keyboardAppearance.map(type => {
         return (
           <WithLabel key={type} label={type}>
-            <TextInput
-              keyboardAppearance={type}
-              style={styles.default}
-            />
+            <TextInput keyboardAppearance={type} style={styles.default} />
           </WithLabel>
         );
       });
       return <View>{examples}</View>;
-    }
+    },
   },
   {
     title: 'Return key types',
@@ -659,18 +649,15 @@ exports.examples = [
         'done',
         'emergency-call',
       ];
-      var examples = returnKeyTypes.map((type) => {
+      var examples = returnKeyTypes.map(type => {
         return (
           <WithLabel key={type} label={type}>
-            <TextInput
-              returnKeyType={type}
-              style={styles.default}
-            />
+            <TextInput returnKeyType={type} style={styles.default} />
           </WithLabel>
         );
       });
       return <View>{examples}</View>;
-    }
+    },
   },
   {
     title: 'Enable return key automatically',
@@ -678,11 +665,14 @@ exports.examples = [
       return (
         <View>
           <WithLabel label="true">
-            <TextInput enablesReturnKeyAutomatically={true} style={styles.default} />
+            <TextInput
+              enablesReturnKeyAutomatically={true}
+              style={styles.default}
+            />
           </WithLabel>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Secure text entry',
@@ -690,15 +680,21 @@ exports.examples = [
       return (
         <View>
           <WithLabel label="true">
-            <TextInput secureTextEntry={true} style={styles.default} defaultValue="abc" />
+            <TextInput
+              secureTextEntry={true}
+              style={styles.default}
+              defaultValue="abc"
+            />
           </WithLabel>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Event handling',
-    render: function(): React.Element<any> { return <TextEventsExample />; },
+    render: function(): React.Element<any> {
+      return <TextEventsExample />;
+    },
   },
   {
     title: 'Colored input text',
@@ -715,7 +711,7 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Colored highlight/cursor for text input',
@@ -734,24 +730,18 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Clear button mode',
-    render: function () {
+    render: function() {
       return (
         <View>
           <WithLabel label="never">
-            <TextInput
-              style={styles.default}
-              clearButtonMode="never"
-            />
+            <TextInput style={styles.default} clearButtonMode="never" />
           </WithLabel>
           <WithLabel label="while editing">
-            <TextInput
-              style={styles.default}
-              clearButtonMode="while-editing"
-            />
+            <TextInput style={styles.default} clearButtonMode="while-editing" />
           </WithLabel>
           <WithLabel label="unless editing">
             <TextInput
@@ -760,14 +750,11 @@ exports.examples = [
             />
           </WithLabel>
           <WithLabel label="always">
-            <TextInput
-              style={styles.default}
-              clearButtonMode="always"
-            />
+            <TextInput style={styles.default} clearButtonMode="always" />
           </WithLabel>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Clear and select',
@@ -810,11 +797,13 @@ exports.examples = [
           </WithLabel>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Blur on submit',
-    render: function(): React.Element<any> { return <BlurOnSubmitExample />; },
+    render: function(): React.Element<any> {
+      return <BlurOnSubmitExample />;
+    },
   },
   {
     title: 'Multiline blur on submit',
@@ -831,7 +820,7 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Multiline',
@@ -874,7 +863,7 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'TextInput Intrinsic Size',
@@ -914,7 +903,7 @@ exports.examples = [
                 borderBottomRightRadius: 20,
                 padding: 10,
                 paddingTop: 20,
-                maxHeight: 100
+                maxHeight: 100,
               }}
               testID="multiline_textinput"
               multiline={true}
@@ -941,7 +930,7 @@ exports.examples = [
           </View>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Auto-expanding',
@@ -958,7 +947,7 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Auto-expanding',
@@ -969,11 +958,14 @@ exports.examples = [
             enablesReturnKeyAutomatically={true}
             returnKeyType="done"
             multiline={true}
-            style={{maxHeight: 400, minHeight: 20, paddingTop: 0, backgroundColor: '#eeeeee', color: 'blue'}}
-          >
-            <Text style={{fontSize: 30, color: 'green'}}>
-              huge
-            </Text>
+            style={{
+              maxHeight: 400,
+              minHeight: 20,
+              paddingTop: 0,
+              backgroundColor: '#eeeeee',
+              color: 'blue',
+            }}>
+            <Text style={{fontSize: 30, color: 'green'}}>huge</Text>
             generic generic generic
             <Text style={{fontSize: 6, color: 'red'}}>
               small small small small small small
@@ -986,13 +978,13 @@ exports.examples = [
           </AutogrowingTextInputExample>
         </View>
       );
-    }
+    },
   },
   {
     title: 'Attributed text',
     render: function() {
       return <TokenizedTextExample />;
-    }
+    },
   },
   {
     title: 'Text selection & cursor placement',
@@ -1010,7 +1002,7 @@ exports.examples = [
           />
         </View>
       );
-    }
+    },
   },
   {
     title: 'TextInput maxLength',
@@ -1018,10 +1010,7 @@ exports.examples = [
       return (
         <View>
           <WithLabel label="maxLength: 5">
-            <TextInput
-              maxLength={5}
-              style={styles.default}
-            />
+            <TextInput maxLength={5} style={styles.default} />
           </WithLabel>
           <WithLabel label="maxLength: 5 with placeholder">
             <TextInput
@@ -1046,6 +1035,6 @@ exports.examples = [
           </WithLabel>
         </View>
       );
-    }
+    },
   },
 ];
diff --git a/RNTester/js/TimePickerAndroidExample.js b/RNTester/js/TimePickerAndroidExample.js
index 517f674665ac..a72bcdafbff0 100644
--- a/RNTester/js/TimePickerAndroidExample.js
+++ b/RNTester/js/TimePickerAndroidExample.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
@@ -116,4 +118,3 @@ var styles = StyleSheet.create({
 });
 
 module.exports = TimePickerAndroidExample;
-
diff --git a/RNTester/js/TimerExample.js b/RNTester/js/TimerExample.js
index a56fd5ad3fe0..3b930c800f65 100644
--- a/RNTester/js/TimerExample.js
+++ b/RNTester/js/TimerExample.js
@@ -4,20 +4,16 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var createReactClass = require('create-react-class');
 var ReactNative = require('react-native');
-var {
-  AlertIOS,
-  Platform,
-  ToastAndroid,
-  Text,
-  View,
-} = ReactNative;
+var {AlertIOS, Platform, ToastAndroid, Text, View} = ReactNative;
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
@@ -30,7 +26,7 @@ var performanceNow = require('fbjs/lib/performanceNow');
 
 function burnCPU(milliseconds) {
   const start = performanceNow();
-  while (performanceNow() < (start + milliseconds)) {}
+  while (performanceNow() < start + milliseconds) {}
 }
 
 class RequestIdleCallbackTester extends React.Component<{}, $FlowFixMeState> {
@@ -73,35 +69,45 @@ class RequestIdleCallbackTester extends React.Component<{}, $FlowFixMeState> {
     );
   }
 
-  _run = (shouldBurnCPU) => {
+  _run = shouldBurnCPU => {
     cancelIdleCallback(this._idleTimer);
-    this._idleTimer = requestIdleCallback((deadline) => {
+    this._idleTimer = requestIdleCallback(deadline => {
       let message = '';
 
       if (shouldBurnCPU) {
         burnCPU(10);
         message = 'Burned CPU for 10ms,';
       }
-      this.setState({message: `${message} ${deadline.timeRemaining()}ms remaining in frame`});
+      this.setState({
+        message: `${message} ${deadline.timeRemaining()}ms remaining in frame`,
+      });
     });
   };
 
   _runWithTimeout = () => {
     cancelIdleCallback(this._idleTimer);
-    this._idleTimer = requestIdleCallback((deadline) => {
-      this.setState({
-        message: `${deadline.timeRemaining()}ms remaining in frame, it did timeout: ${deadline.didTimeout ? 'yes' : 'no'}`
-      });
-    }, { timeout: 100 });
+    this._idleTimer = requestIdleCallback(
+      deadline => {
+        this.setState({
+          message: `${deadline.timeRemaining()}ms remaining in frame, it did timeout: ${
+            deadline.didTimeout ? 'yes' : 'no'
+          }`,
+        });
+      },
+      {timeout: 100},
+    );
     burnCPU(100);
   };
 
   _runBackground = () => {
     cancelIdleCallback(this._idleTimer);
-    const handler = (deadline) => {
+    const handler = deadline => {
       while (deadline.timeRemaining() > 5) {
         burnCPU(5);
-        this.setState({message: `Burned CPU for 5ms ${this._iters++} times, ${deadline.timeRemaining()}ms remaining in frame`});
+        this.setState({
+          message: `Burned CPU for 5ms ${this
+            ._iters++} times, ${deadline.timeRemaining()}ms remaining in frame`,
+        });
       }
 
       this._idleTimer = requestIdleCallback(handler);
@@ -122,8 +128,8 @@ var TimerTester = createReactClass({
   _ii: 0,
   _iters: 0,
   _start: 0,
-  _timerFn: (null : ?(() => any)),
-  _handle: (null : any),
+  _timerFn: (null: ?() => any),
+  _handle: (null: any),
 
   render: function() {
     var args = 'fn' + (this.props.dt !== undefined ? ', ' + this.props.dt : '');
@@ -160,9 +166,18 @@ var TimerTester = createReactClass({
     }
     if (this._ii >= this._iters && !this._handle) {
       var d = new Date();
-      var e = (d.getTime() - this._start);
-      var msg = 'Finished ' + this._ii + ' ' + this.props.type + ' calls.\n' +
-        'Elapsed time: ' + e + ' ms\n' + (e / this._ii) + ' ms / iter';
+      var e = d.getTime() - this._start;
+      var msg =
+        'Finished ' +
+        this._ii +
+        ' ' +
+        this.props.type +
+        ' calls.\n' +
+        'Elapsed time: ' +
+        e +
+        ' ms\n' +
+        e / this._ii +
+        ' ms / iter';
       console.log(msg);
       if (Platform.OS === 'ios') {
         AlertIOS.alert(msg);
@@ -170,7 +185,9 @@ var TimerTester = createReactClass({
         ToastAndroid.show(msg, ToastAndroid.SHORT);
       }
       this._start = 0;
-      this.forceUpdate(() => { this._ii = 0; });
+      this.forceUpdate(() => {
+        this._ii = 0;
+      });
       return;
     }
     this._ii++;
@@ -194,13 +211,15 @@ var TimerTester = createReactClass({
 
 exports.framework = 'React';
 exports.title = 'Timers, TimerMixin';
-exports.description = 'The TimerMixin provides timer functions for executing ' +
+exports.description =
+  'The TimerMixin provides timer functions for executing ' +
   'code in the future that are safely cleaned up when the component unmounts.';
 
 exports.examples = [
   {
     title: 'this.setTimeout(fn, t)',
-    description: 'Execute function fn t milliseconds in the future.  If ' +
+    description:
+      'Execute function fn t milliseconds in the future.  If ' +
       't === 0, it will be enqueued immediately in the next event loop.  ' +
       'Larger values will fire on the closest frame.',
     render: function() {
@@ -248,7 +267,8 @@ exports.examples = [
   },
   {
     title: 'this.setInterval(fn, t)',
-    description: 'Execute function fn every t milliseconds until cancelled ' +
+    description:
+      'Execute function fn every t milliseconds until cancelled ' +
       'or component is unmounted.',
     render: function(): React.Element<any> {
       class IntervalExample extends React.Component<{}, $FlowFixMeState> {
@@ -271,7 +291,7 @@ exports.examples = [
           return (
             <View>
               <TimerTester ref="interval" dt={25} type="setInterval" />
-              <RNTesterButton onPress={() => this.refs.interval.clear() }>
+              <RNTesterButton onPress={() => this.refs.interval.clear()}>
                 Clear interval
               </RNTesterButton>
             </View>
diff --git a/RNTester/js/ToastAndroidExample.android.js b/RNTester/js/ToastAndroidExample.android.js
index 6ca7b9c4f8b7..7274fa969cf1 100644
--- a/RNTester/js/ToastAndroidExample.android.js
+++ b/RNTester/js/ToastAndroidExample.android.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -11,12 +12,7 @@
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  ToastAndroid,
-  TouchableWithoutFeedback,
-} = ReactNative;
+var {StyleSheet, Text, ToastAndroid, TouchableWithoutFeedback} = ReactNative;
 
 var RNTesterBlock = require('RNTesterBlock');
 var RNTesterPage = require('RNTesterPage');
@@ -32,14 +28,22 @@ class ToastExample extends React.Component<{}, $FlowFixMeState> {
         <RNTesterBlock title="Simple toast">
           <TouchableWithoutFeedback
             onPress={() =>
-              ToastAndroid.show('This is a toast with short duration', ToastAndroid.SHORT)}>
+              ToastAndroid.show(
+                'This is a toast with short duration',
+                ToastAndroid.SHORT,
+              )
+            }>
             <Text style={styles.text}>Click me.</Text>
           </TouchableWithoutFeedback>
         </RNTesterBlock>
         <RNTesterBlock title="Toast with long duration">
           <TouchableWithoutFeedback
             onPress={() =>
-              ToastAndroid.show('This is a toast with long duration', ToastAndroid.LONG)}>
+              ToastAndroid.show(
+                'This is a toast with long duration',
+                ToastAndroid.LONG,
+              )
+            }>
             <Text style={styles.text}>Click me.</Text>
           </TouchableWithoutFeedback>
         </RNTesterBlock>
diff --git a/RNTester/js/ToolbarAndroidExample.android.js b/RNTester/js/ToolbarAndroidExample.android.js
index 7a17105698c4..4043c054f3fb 100644
--- a/RNTester/js/ToolbarAndroidExample.android.js
+++ b/RNTester/js/ToolbarAndroidExample.android.js
@@ -4,19 +4,17 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
 
 var nativeImageSource = require('nativeImageSource');
-var {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, View} = ReactNative;
 var RNTesterBlock = require('./RNTesterBlock');
 var RNTesterPage = require('./RNTesterPage');
 
@@ -45,13 +43,14 @@ class ToolbarAndroidExample extends React.Component<{}, $FlowFixMeState> {
             navIcon={nativeImageSource({
               android: 'ic_menu_black_24dp',
               width: 48,
-              height: 48
+              height: 48,
             })}
             onActionSelected={this._onActionSelected}
             onIconClicked={() => this.setState({actionText: 'Icon clicked'})}
             style={styles.toolbar}
             subtitle={this.state.actionText}
-            title="Toolbar" />
+            title="Toolbar"
+          />
           <Text>{this.state.actionText}</Text>
         </RNTesterBlock>
         <RNTesterBlock title="Toolbar with logo & custom title view (a View with Switch+Text)">
@@ -59,14 +58,16 @@ class ToolbarAndroidExample extends React.Component<{}, $FlowFixMeState> {
             logo={nativeImageSource({
               android: 'launcher_icon',
               width: 132,
-              height: 144
+              height: 144,
             })}
             style={styles.toolbar}>
-            <View style={{height: 56, flexDirection: 'row', alignItems: 'center'}}>
+            <View
+              style={{height: 56, flexDirection: 'row', alignItems: 'center'}}>
               <Switch
                 value={this.state.toolbarSwitch}
-                onValueChange={(value) => this.setState({'toolbarSwitch': value})} />
-              <Text>{'\'Tis but a switch'}</Text>
+                onValueChange={value => this.setState({toolbarSwitch: value})}
+              />
+              <Text>{"'Tis but a switch"}</Text>
             </View>
           </ToolbarAndroid>
         </RNTesterBlock>
@@ -74,7 +75,8 @@ class ToolbarAndroidExample extends React.Component<{}, $FlowFixMeState> {
           <ToolbarAndroid
             actions={toolbarActions}
             style={styles.toolbar}
-            subtitle="There be no icon here" />
+            subtitle="There be no icon here"
+          />
         </RNTesterBlock>
         <RNTesterBlock title="Toolbar with navIcon & logo, no title">
           <ToolbarAndroid
@@ -82,50 +84,57 @@ class ToolbarAndroidExample extends React.Component<{}, $FlowFixMeState> {
             logo={nativeImageSource({
               android: 'launcher_icon',
               width: 132,
-              height: 144
+              height: 144,
             })}
             navIcon={nativeImageSource({
               android: 'ic_menu_black_24dp',
               width: 48,
-              height: 48
+              height: 48,
             })}
-            style={styles.toolbar} />
+            style={styles.toolbar}
+          />
         </RNTesterBlock>
         <RNTesterBlock title="Toolbar with custom title colors">
           <ToolbarAndroid
             navIcon={nativeImageSource({
               android: 'ic_menu_black_24dp',
               width: 48,
-              height: 48
+              height: 48,
             })}
             onIconClicked={() => this.setState({colorProps: {}})}
             title="Wow, such toolbar"
             style={styles.toolbar}
             subtitle="Much native"
-            {...this.state.colorProps} />
+            {...this.state.colorProps}
+          />
           <Text>
-            Touch the icon to reset the custom colors to the default (theme-provided) ones.
+            Touch the icon to reset the custom colors to the default
+            (theme-provided) ones.
           </Text>
         </RNTesterBlock>
         <RNTesterBlock title="Toolbar with remote logo & navIcon">
           <ToolbarAndroid
-            actions={[{title: 'Bunny', icon: require('./bunny.png'), show: 'always'}]}
+            actions={[
+              {title: 'Bunny', icon: require('./bunny.png'), show: 'always'},
+            ]}
             logo={require('./hawk.png')}
             navIcon={require('./bunny.png')}
             title="Bunny and Hawk"
-            style={styles.toolbar} />
+            style={styles.toolbar}
+          />
         </RNTesterBlock>
         <RNTesterBlock title="Toolbar with custom overflowIcon">
           <ToolbarAndroid
             actions={toolbarActions}
             overflowIcon={require('./bunny.png')}
-            style={styles.toolbar} />
+            style={styles.toolbar}
+          />
         </RNTesterBlock>
       </RNTesterPage>
     );
   }
 
-  _onActionSelected = (position) => {
+  _onActionSelected = position => {
     this.setState({
       actionText: 'Selected ' + toolbarActions[position].title,
     });
@@ -133,17 +142,25 @@ class ToolbarAndroidExample extends React.Component<{}, $FlowFixMeState> {
 }
 
 var toolbarActions = [
-  {title: 'Create', icon: nativeImageSource({
-    android: 'ic_create_black_48dp',
-    width: 96,
-    height: 96
-  }), show: 'always'},
+  {
+    title: 'Create',
+    icon: nativeImageSource({
+      android: 'ic_create_black_48dp',
+      width: 96,
+      height: 96,
+    }),
+    show: 'always',
+  },
   {title: 'Filter'},
-  {title: 'Settings', icon: nativeImageSource({
-    android: 'ic_settings_black_48dp',
-    width: 96,
-    height: 96
-  }), show: 'always'},
+  {
+    title: 'Settings',
+    icon: nativeImageSource({
+      android: 'ic_settings_black_48dp',
+      width: 96,
+      height: 96,
+    }),
+    show: 'always',
+  },
 ];
 
 var styles = StyleSheet.create({
diff --git a/RNTester/js/ToolbarAndroidExample.ios.js b/RNTester/js/ToolbarAndroidExample.ios.js
index 5e8c57f7a81d..25bf7dba0fe7 100644
--- a/RNTester/js/ToolbarAndroidExample.ios.js
+++ b/RNTester/js/ToolbarAndroidExample.ios.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // Not applicable to iOS.
diff --git a/RNTester/js/TouchableExample.js b/RNTester/js/TouchableExample.js
index 069dff9d26c0..3ce3faa45bb0 100644
--- a/RNTester/js/TouchableExample.js
+++ b/RNTester/js/TouchableExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -24,115 +26,130 @@ var {
 
 const NativeModules = require('NativeModules');
 
-const forceTouchAvailable = (NativeModules.PlatformConstants &&
-  NativeModules.PlatformConstants.forceTouchAvailable) || false;
+const forceTouchAvailable =
+  (NativeModules.PlatformConstants &&
+    NativeModules.PlatformConstants.forceTouchAvailable) ||
+  false;
 
 exports.displayName = (undefined: ?string);
 exports.description = 'Touchable and onPress examples.';
 exports.title = '<Touchable*> and onPress';
 exports.examples = [
-{
-  title: '<TouchableHighlight>',
-  description: 'TouchableHighlight works by adding an extra view with a ' +
-    'black background under the single child view.  This works best when the ' +
-    'child view is fully opaque, although it can be made to work as a simple ' +
-    'background color change as well with the activeOpacity and ' +
-    'underlayColor props.',
-  render: function() {
-    return (
-      <View>
-        <View style={styles.row}>
-          <TouchableHighlight
-            style={styles.wrapper}
-            onPress={() => console.log('stock THW image - highlight')}>
-            <Image
-              source={heartImage}
-              style={styles.image}
-            />
-          </TouchableHighlight>
-          <TouchableHighlight
-            style={styles.wrapper}
-            activeOpacity={1}
-            animationVelocity={0}
-            tvParallaxProperties={{pressMagnification: 1.3, pressDuration: 0.6}}
-            underlayColor="rgb(210, 230, 255)"
-            onPress={() => console.log('custom THW text - highlight')}>
-            <View style={styles.wrapperCustom}>
-              <Text style={styles.text}>
-                Tap Here For Custom Highlight!
-              </Text>
-            </View>
-          </TouchableHighlight>
+  {
+    title: '<TouchableHighlight>',
+    description:
+      'TouchableHighlight works by adding an extra view with a ' +
+      'black background under the single child view.  This works best when the ' +
+      'child view is fully opaque, although it can be made to work as a simple ' +
+      'background color change as well with the activeOpacity and ' +
+      'underlayColor props.',
+    render: function() {
+      return (
+        <View>
+          <View style={styles.row}>
+            <TouchableHighlight
+              style={styles.wrapper}
+              onPress={() => console.log('stock THW image - highlight')}>
+              <Image source={heartImage} style={styles.image} />
+            </TouchableHighlight>
+            <TouchableHighlight
+              style={styles.wrapper}
+              activeOpacity={1}
+              animationVelocity={0}
+              tvParallaxProperties={{
+                pressMagnification: 1.3,
+                pressDuration: 0.6,
+              }}
+              underlayColor="rgb(210, 230, 255)"
+              onPress={() => console.log('custom THW text - highlight')}>
+              <View style={styles.wrapperCustom}>
+                <Text style={styles.text}>Tap Here For Custom Highlight!</Text>
+              </View>
+            </TouchableHighlight>
+          </View>
         </View>
-      </View>
-    );
+      );
+    },
   },
- }, {
-  title: 'TouchableNativeFeedback with Animated child',
-  description: 'TouchableNativeFeedback can have an AnimatedComponent as a' +
-    'direct child.',
-  platform: 'android',
-  render: function() {
-    const mScale = new Animated.Value(1);
-    Animated.timing(mScale, {toValue: 0.3, duration: 1000}).start();
-    const style = {
-      backgroundColor: 'rgb(180, 64, 119)',
-      width: 200,
-      height: 100,
-      transform: [{scale: mScale}]
-    };
-    return (
-      <View>
-        <View style={styles.row}>
-          <TouchableNativeFeedback>
-            <Animated.View style={style}/>
-          </TouchableNativeFeedback>
+  {
+    title: 'TouchableNativeFeedback with Animated child',
+    description:
+      'TouchableNativeFeedback can have an AnimatedComponent as a' +
+      'direct child.',
+    platform: 'android',
+    render: function() {
+      const mScale = new Animated.Value(1);
+      Animated.timing(mScale, {toValue: 0.3, duration: 1000}).start();
+      const style = {
+        backgroundColor: 'rgb(180, 64, 119)',
+        width: 200,
+        height: 100,
+        transform: [{scale: mScale}],
+      };
+      return (
+        <View>
+          <View style={styles.row}>
+            <TouchableNativeFeedback>
+              <Animated.View style={style} />
+            </TouchableNativeFeedback>
+          </View>
         </View>
-      </View>
-    );
+      );
+    },
+  },
+  {
+    title: '<Text onPress={fn}> with highlight',
+    render: function(): React.Element<any> {
+      return <TextOnPressBox />;
+    },
   },
-}, {
-  title: '<Text onPress={fn}> with highlight',
-  render: function(): React.Element<any> {
-    return <TextOnPressBox />;
+  {
+    title: 'Touchable feedback events',
+    description:
+      '<Touchable*> components accept onPress, onPressIn, ' +
+      'onPressOut, and onLongPress as props.',
+    render: function(): React.Element<any> {
+      return <TouchableFeedbackEvents />;
+    },
   },
-}, {
-  title: 'Touchable feedback events',
-  description: '<Touchable*> components accept onPress, onPressIn, ' +
-    'onPressOut, and onLongPress as props.',
-  render: function(): React.Element<any> {
-    return <TouchableFeedbackEvents />;
+  {
+    title: 'Touchable delay for events',
+    description:
+      '<Touchable*> components also accept delayPressIn, ' +
+      'delayPressOut, and delayLongPress as props. These props impact the ' +
+      'timing of feedback events.',
+    render: function(): React.Element<any> {
+      return <TouchableDelayEvents />;
+    },
   },
-}, {
-  title: 'Touchable delay for events',
-  description: '<Touchable*> components also accept delayPressIn, ' +
-    'delayPressOut, and delayLongPress as props. These props impact the ' +
-    'timing of feedback events.',
-  render: function(): React.Element<any> {
-    return <TouchableDelayEvents />;
+  {
+    title: '3D Touch / Force Touch',
+    description:
+      'iPhone 6s and 6s plus support 3D touch, which adds a force property to touches',
+    render: function(): React.Element<any> {
+      return <ForceTouchExample />;
+    },
+    platform: 'ios',
   },
-}, {
-  title: '3D Touch / Force Touch',
-  description: 'iPhone 6s and 6s plus support 3D touch, which adds a force property to touches',
-  render: function(): React.Element<any> {
-    return <ForceTouchExample />;
+  {
+    title: 'Touchable Hit Slop',
+    description:
+      '<Touchable*> components accept hitSlop prop which extends the touch area ' +
+      'without changing the view bounds.',
+    render: function(): React.Element<any> {
+      return <TouchableHitSlop />;
+    },
   },
-  platform: 'ios',
-}, {
-   title: 'Touchable Hit Slop',
-   description: '<Touchable*> components accept hitSlop prop which extends the touch area ' +
-     'without changing the view bounds.',
-   render: function(): React.Element<any> {
-     return <TouchableHitSlop />;
-   },
-}, {
-   title: 'Disabled Touchable*',
-   description: '<Touchable*> components accept disabled prop which prevents ' +
-     'any interaction with component',
-   render: function(): React.Element<any> {
-     return <TouchableDisabled />;
-   },
- }];
+  {
+    title: 'Disabled Touchable*',
+    description:
+      '<Touchable*> components accept disabled prop which prevents ' +
+      'any interaction with component',
+    render: function(): React.Element<any> {
+      return <TouchableDisabled />;
+    },
+  },
+];
 
 class TextOnPressBox extends React.Component<{}, $FlowFixMeState> {
   state = {
@@ -155,15 +172,11 @@ class TextOnPressBox extends React.Component<{}, $FlowFixMeState> {
 
     return (
       <View>
-        <Text
-          style={styles.textBlock}
-          onPress={this.textOnPress}>
+        <Text style={styles.textBlock} onPress={this.textOnPress}>
           Text has built-in onPress handling
         </Text>
         <View style={styles.logBox}>
-          <Text>
-            {textLog}
-          </Text>
+          <Text>{textLog}</Text>
         </View>
       </View>
     );
@@ -189,19 +202,19 @@ class TouchableFeedbackEvents extends React.Component<{}, $FlowFixMeState> {
             onPressIn={() => this._appendEvent('pressIn')}
             onPressOut={() => this._appendEvent('pressOut')}
             onLongPress={() => this._appendEvent('longPress')}>
-            <Text style={styles.button}>
-              Press Me
-            </Text>
+            <Text style={styles.button}>Press Me</Text>
           </TouchableOpacity>
         </View>
-        <View testID="touchable_feedback_events_console" style={styles.eventLogBox}>
+        <View
+          testID="touchable_feedback_events_console"
+          style={styles.eventLogBox}>
           {this.state.eventLog.map((e, ii) => <Text key={ii}>{e}</Text>)}
         </View>
       </View>
     );
   }
 
-  _appendEvent = (eventName) => {
+  _appendEvent = eventName => {
     var limit = 6;
     var eventLog = this.state.eventLog.slice(0, limit - 1);
     eventLog.unshift(eventName);
@@ -228,19 +241,19 @@ class TouchableDelayEvents extends React.Component<{}, $FlowFixMeState> {
             onPressOut={() => this._appendEvent('pressOut - 1000ms delay')}
             delayLongPress={800}
             onLongPress={() => this._appendEvent('longPress - 800ms delay')}>
-            <Text style={styles.button}>
-              Press Me
-            </Text>
+            <Text style={styles.button}>Press Me</Text>
           </TouchableOpacity>
         </View>
-        <View style={styles.eventLogBox} testID="touchable_delay_events_console">
+        <View
+          style={styles.eventLogBox}
+          testID="touchable_delay_events_console">
           {this.state.eventLog.map((e, ii) => <Text key={ii}>{e}</Text>)}
         </View>
       </View>
     );
   }
 
-  _appendEvent = (eventName) => {
+  _appendEvent = eventName => {
     var limit = 6;
     var eventLog = this.state.eventLog.slice(0, limit - 1);
     eventLog.unshift(eventName);
@@ -254,9 +267,9 @@ class ForceTouchExample extends React.Component<{}, $FlowFixMeState> {
   };
 
   _renderConsoleText = () => {
-    return forceTouchAvailable ?
-      'Force: ' + this.state.force.toFixed(3) :
-      '3D Touch is not available on this device';
+    return forceTouchAvailable
+      ? 'Force: ' + this.state.force.toFixed(3)
+      : '3D Touch is not available on this device';
   };
 
   render() {
@@ -270,11 +283,11 @@ class ForceTouchExample extends React.Component<{}, $FlowFixMeState> {
             style={styles.wrapper}
             testID="touchable_3dtouch_button"
             onStartShouldSetResponder={() => true}
-            onResponderMove={(event) => this.setState({force: event.nativeEvent.force})}
-            onResponderRelease={(event) => this.setState({force: 0})}>
-            <Text style={styles.button}>
-              Press Me
-            </Text>
+            onResponderMove={event =>
+              this.setState({force: event.nativeEvent.force})
+            }
+            onResponderRelease={event => this.setState({force: 0})}>
+            <Text style={styles.button}>Press Me</Text>
           </View>
         </View>
       </View>
@@ -309,15 +322,11 @@ class TouchableHitSlop extends React.Component<{}, $FlowFixMeState> {
             style={styles.hitSlopWrapper}
             hitSlop={{top: 30, bottom: 30, left: 60, right: 60}}
             testID="touchable_hit_slop_button">
-            <Text style={styles.hitSlopButton}>
-              Press Outside This View
-            </Text>
+            <Text style={styles.hitSlopButton}>Press Outside This View</Text>
           </TouchableOpacity>
-         </View>
+        </View>
         <View style={styles.logBox}>
-          <Text>
-            {log}
-          </Text>
+          <Text>{log}</Text>
         </View>
       </View>
     );
@@ -343,9 +352,7 @@ class TouchableDisabled extends React.Component<{}> {
           underlayColor="rgb(210, 230, 255)"
           style={[styles.row, styles.block]}
           onPress={() => console.log('custom THW text - highlight')}>
-          <Text style={styles.disabledButton}>
-            Disabled TouchableHighlight
-          </Text>
+          <Text style={styles.disabledButton}>Disabled TouchableHighlight</Text>
         </TouchableHighlight>
 
         <TouchableHighlight
@@ -354,12 +361,10 @@ class TouchableDisabled extends React.Component<{}> {
           underlayColor="rgb(210, 230, 255)"
           style={[styles.row, styles.block]}
           onPress={() => console.log('custom THW text - highlight')}>
-          <Text style={styles.button}>
-            Enabled TouchableHighlight
-          </Text>
+          <Text style={styles.button}>Enabled TouchableHighlight</Text>
         </TouchableHighlight>
 
-        {Platform.OS === 'android' &&
+        {Platform.OS === 'android' && (
           <TouchableNativeFeedback
             style={[styles.row, styles.block]}
             onPress={() => console.log('custom TNF has been clicked')}
@@ -370,21 +375,22 @@ class TouchableDisabled extends React.Component<{}> {
               </Text>
             </View>
           </TouchableNativeFeedback>
-        }
+        )}
 
-        {Platform.OS === 'android' &&
+        {Platform.OS === 'android' && (
           <TouchableNativeFeedback
             disabled={true}
             style={[styles.row, styles.block]}
             onPress={() => console.log('custom TNF has been clicked')}
             background={TouchableNativeFeedback.SelectableBackground()}>
             <View>
-              <Text style={[styles.disabledButton, styles.nativeFeedbackButton]}>
+              <Text
+                style={[styles.disabledButton, styles.nativeFeedbackButton]}>
                 Disabled TouchableNativeFeedback
               </Text>
             </View>
           </TouchableNativeFeedback>
-        }
+        )}
       </View>
     );
   }
diff --git a/RNTester/js/TransformExample.js b/RNTester/js/TransformExample.js
index 4271e074a017..8af5fc55d282 100644
--- a/RNTester/js/TransformExample.js
+++ b/RNTester/js/TransformExample.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Animated,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {Animated, StyleSheet, Text, View} = ReactNative;
 
 class Flip extends React.Component<{}, $FlowFixMeState> {
   state = {
@@ -37,33 +34,42 @@ class Flip extends React.Component<{}, $FlowFixMeState> {
   render() {
     return (
       <View style={styles.flipCardContainer}>
-        <Animated.View style={[
-          styles.flipCard,
-          {transform: [
-            {perspective: 850},
-            {rotateX: this.state.theta.interpolate({
-              inputRange: [0, 180],
-              outputRange: ['0deg', '180deg']
-            })},
-          ]}]}>
-          <Text style={styles.flipText}>
-            This text is flipping great.
-          </Text>
+        <Animated.View
+          style={[
+            styles.flipCard,
+            {
+              transform: [
+                {perspective: 850},
+                {
+                  rotateX: this.state.theta.interpolate({
+                    inputRange: [0, 180],
+                    outputRange: ['0deg', '180deg'],
+                  }),
+                },
+              ],
+            },
+          ]}>
+          <Text style={styles.flipText}>This text is flipping great.</Text>
         </Animated.View>
-        <Animated.View style={[styles.flipCard, {
-          position: 'absolute',
-          top: 0,
-          backgroundColor: 'red',
-          transform: [
-            {perspective: 850},
-            {rotateX: this.state.theta.interpolate({
-              inputRange: [0, 180],
-              outputRange: ['180deg', '360deg']
-            })},
-          ]}]}>
-          <Text style={styles.flipText}>
-            On the flip side...
-          </Text>
+        <Animated.View
+          style={[
+            styles.flipCard,
+            {
+              position: 'absolute',
+              top: 0,
+              backgroundColor: 'red',
+              transform: [
+                {perspective: 850},
+                {
+                  rotateX: this.state.theta.interpolate({
+                    inputRange: [0, 180],
+                    outputRange: ['180deg', '360deg'],
+                  }),
+                },
+              ],
+            },
+          ]}>
+          <Text style={styles.flipText}>On the flip side...</Text>
         </Animated.View>
       </View>
     );
@@ -110,9 +116,7 @@ var styles = StyleSheet.create({
     height: 50,
     position: 'absolute',
     top: 0,
-    transform: [
-      {rotate: '30deg'},
-    ],
+    transform: [{rotate: '30deg'}],
     width: 50,
   },
   box3step2: {
@@ -122,11 +126,7 @@ var styles = StyleSheet.create({
     opacity: 0.5,
     position: 'absolute',
     top: 0,
-    transform: [
-      {rotate: '30deg'},
-      {scaleX: 2},
-      {scaleY: 2},
-    ],
+    transform: [{rotate: '30deg'}, {scaleX: 2}, {scaleY: 2}],
     width: 50,
   },
   box3step3: {
@@ -151,11 +151,7 @@ var styles = StyleSheet.create({
     height: 50,
     position: 'absolute',
     top: 0,
-    transform: [
-      {translate: [200, 350]},
-      {scale: 2.5},
-      {rotate: '-0.2rad'},
-    ],
+    transform: [{translate: [200, 350]}, {scale: 2.5}, {rotate: '-0.2rad'}],
     width: 100,
   },
   box5: {
@@ -167,11 +163,7 @@ var styles = StyleSheet.create({
     width: 50,
   },
   box5Transform: {
-    transform: [
-      {translate: [-50, 35]},
-      {rotate: '50deg'},
-      {scale: 2},
-    ],
+    transform: [{translate: [-50, 35]}, {rotate: '50deg'}, {scale: 2}],
   },
   flipCardContainer: {
     marginVertical: 40,
@@ -191,7 +183,7 @@ var styles = StyleSheet.create({
     fontSize: 20,
     color: 'white',
     fontWeight: 'bold',
-  }
+  },
 });
 
 exports.title = 'Transforms';
@@ -200,29 +192,33 @@ exports.examples = [
   {
     title: 'Perspective, Rotate, Animation',
     description: 'perspective: 850, rotateX: Animated.timing(0 -> 360)',
-    render(): React.Element<any> { return <Flip />; }
+    render(): React.Element<any> {
+      return <Flip />;
+    },
   },
   {
     title: 'Translate, Rotate, Scale',
-    description: "translateX: 100, translateY: 50, rotate: '30deg', scaleX: 2, scaleY: 2",
+    description:
+      "translateX: 100, translateY: 50, rotate: '30deg', scaleX: 2, scaleY: 2",
     render() {
       return (
         <View style={styles.container}>
           <View style={styles.box1} />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Scale, Translate, Rotate, ',
-    description: "scaleX: 2, scaleY: 2, translateX: 100, translateY: 50, rotate: '30deg'",
+    description:
+      "scaleX: 2, scaleY: 2, translateX: 100, translateY: 50, rotate: '30deg'",
     render() {
       return (
         <View style={styles.container}>
           <View style={styles.box2} />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Rotate',
@@ -233,7 +229,7 @@ exports.examples = [
           <View style={styles.box3step1} />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Rotate, Scale',
@@ -244,18 +240,19 @@ exports.examples = [
           <View style={styles.box3step2} />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Rotate, Scale, Translate ',
-    description: "rotate: '30deg', scaleX: 2, scaleY: 2, translateX: 100, translateY: 50",
+    description:
+      "rotate: '30deg', scaleX: 2, scaleY: 2, translateX: 100, translateY: 50",
     render() {
       return (
         <View style={styles.container}>
           <View style={styles.box3step3} />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Translate, Scale, Rotate',
@@ -266,7 +263,7 @@ exports.examples = [
           <View style={styles.box4} />
         </View>
       );
-    }
+    },
   },
   {
     title: 'Translate, Rotate, Scale',
@@ -277,6 +274,6 @@ exports.examples = [
           <View style={[styles.box5, styles.box5Transform]} />
         </View>
       );
-    }
-  }
+    },
+  },
 ];
diff --git a/RNTester/js/TransparentHitTestExample.js b/RNTester/js/TransparentHitTestExample.js
index e1baa00964ed..7ba595bee16e 100644
--- a/RNTester/js/TransparentHitTestExample.js
+++ b/RNTester/js/TransparentHitTestExample.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -11,11 +12,7 @@
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  Text,
-  View,
-  TouchableOpacity,
-} = ReactNative;
+var {Text, View, TouchableOpacity} = ReactNative;
 
 class TransparentHitTestExample extends React.Component<{}> {
   render() {
@@ -25,14 +22,17 @@ class TransparentHitTestExample extends React.Component<{}> {
           <Text>HELLO!</Text>
         </TouchableOpacity>
 
-        <View style={{
-          position: 'absolute',
-          backgroundColor: 'green',
-          top: 0,
-          left: 0,
-          bottom: 0,
-          right: 0,
-          opacity: 0.0}} />
+        <View
+          style={{
+            position: 'absolute',
+            backgroundColor: 'green',
+            top: 0,
+            left: 0,
+            bottom: 0,
+            right: 0,
+            opacity: 0.0,
+          }}
+        />
       </View>
     );
   }
@@ -44,6 +44,8 @@ exports.description = 'Transparent view receiving touch events';
 exports.examples = [
   {
     title: 'TransparentHitTestExample',
-    render(): React.Element<any> { return <TransparentHitTestExample />; }
-  }
+    render(): React.Element<any> {
+      return <TransparentHitTestExample />;
+    },
+  },
 ];
diff --git a/RNTester/js/URIActionMap.js b/RNTester/js/URIActionMap.js
index f303fa21a499..cf33d0104346 100644
--- a/RNTester/js/URIActionMap.js
+++ b/RNTester/js/URIActionMap.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const ReactNative = require('react-native');
@@ -13,11 +15,9 @@ const RNTesterActions = require('./RNTesterActions');
 // $FlowFixMe : This is a platform-forked component, and flow seems to only run on iOS?
 const RNTesterList = require('./RNTesterList');
 
-const {
-  Alert,
-} = ReactNative;
+const {Alert} = ReactNative;
 
-import type { RNTesterAction } from './RNTesterActions';
+import type {RNTesterAction} from './RNTesterActions';
 
 function PathActionMap(path: string): ?RNTesterAction {
   // Warning! Hacky parsing for example code. Use a library for this!
diff --git a/RNTester/js/VibrationExample.js b/RNTester/js/VibrationExample.js
index a213799902f8..ed12bd1e5491 100644
--- a/RNTester/js/VibrationExample.js
+++ b/RNTester/js/VibrationExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
diff --git a/RNTester/js/VibrationIOSExample.js b/RNTester/js/VibrationIOSExample.js
index 5f642519da18..59e96b673977 100644
--- a/RNTester/js/VibrationIOSExample.js
+++ b/RNTester/js/VibrationIOSExample.js
@@ -4,37 +4,35 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  View,
-  Text,
-  TouchableHighlight,
-  VibrationIOS
-} = ReactNative;
+var {StyleSheet, View, Text, TouchableHighlight, VibrationIOS} = ReactNative;
 
 exports.framework = 'React';
 exports.title = 'VibrationIOS';
 exports.description = 'Vibration API for iOS';
-exports.examples = [{
-  title: 'VibrationIOS.vibrate()',
-  render() {
-    return (
-      <TouchableHighlight
-        style={styles.wrapper}
-        onPress={() => VibrationIOS.vibrate()}>
-        <View style={styles.button}>
-          <Text>Vibrate</Text>
-        </View>
-      </TouchableHighlight>
-    );
+exports.examples = [
+  {
+    title: 'VibrationIOS.vibrate()',
+    render() {
+      return (
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={() => VibrationIOS.vibrate()}>
+          <View style={styles.button}>
+            <Text>Vibrate</Text>
+          </View>
+        </TouchableHighlight>
+      );
+    },
   },
-}];
+];
 
 var styles = StyleSheet.create({
   wrapper: {
diff --git a/RNTester/js/ViewExample.js b/RNTester/js/ViewExample.js
index 5d643a12fa09..1cc4ad686772 100644
--- a/RNTester/js/ViewExample.js
+++ b/RNTester/js/ViewExample.js
@@ -4,17 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, View} = ReactNative;
 var TouchableWithoutFeedback = require('TouchableWithoutFeedback');
 
 var styles = StyleSheet.create({
@@ -33,32 +31,30 @@ var styles = StyleSheet.create({
 
 class ViewBorderStyleExample extends React.Component<{}, $FlowFixMeState> {
   state = {
-    showBorder: true
+    showBorder: true,
   };
 
   render() {
     return (
       <TouchableWithoutFeedback onPress={this._handlePress}>
         <View>
-          <View style={{
-            borderWidth: 1,
-            borderStyle: this.state.showBorder ? 'dashed' : null,
-            padding: 5
-          }}>
-            <Text style={{fontSize: 11}}>
-              Dashed border style
-            </Text>
-          </View>
-          <View style={{
-            marginTop: 5,
-            borderWidth: 1,
-            borderRadius: 5,
-            borderStyle: this.state.showBorder ? 'dotted' : null,
-            padding: 5
-          }}>
-            <Text style={{fontSize: 11}}>
-              Dotted border style
-            </Text>
+          <View
+            style={{
+              borderWidth: 1,
+              borderStyle: this.state.showBorder ? 'dashed' : null,
+              padding: 5,
+            }}>
+            <Text style={{fontSize: 11}}>Dashed border style</Text>
+          </View>
+          <View
+            style={{
+              marginTop: 5,
+              borderWidth: 1,
+              borderRadius: 5,
+              borderStyle: this.state.showBorder ? 'dotted' : null,
+              padding: 5,
+            }}>
+            <Text style={{fontSize: 11}}>Dotted border style</Text>
           </View>
         </View>
       </TouchableWithoutFeedback>
@@ -72,7 +68,7 @@ class ViewBorderStyleExample extends React.Component<{}, $FlowFixMeState> {
 
 class ZIndexExample extends React.Component<{}, $FlowFixMeState> {
   state = {
-    flipped: false
+    flipped: false,
   };
 
   render() {
@@ -81,28 +77,32 @@ class ZIndexExample extends React.Component<{}, $FlowFixMeState> {
       <TouchableWithoutFeedback onPress={this._handlePress}>
         <View>
           <Text style={{paddingBottom: 10}}>Tap to flip sorting order</Text>
-          <View style={[
-            styles.zIndex,
-            {marginTop: 0, backgroundColor: '#E57373', zIndex: indices[0]}
-          ]}>
+          <View
+            style={[
+              styles.zIndex,
+              {marginTop: 0, backgroundColor: '#E57373', zIndex: indices[0]},
+            ]}>
             <Text>ZIndex {indices[0]}</Text>
           </View>
-          <View style={[
-            styles.zIndex,
-            {marginLeft: 50, backgroundColor: '#FFF176', zIndex: indices[1]}
-          ]}>
+          <View
+            style={[
+              styles.zIndex,
+              {marginLeft: 50, backgroundColor: '#FFF176', zIndex: indices[1]},
+            ]}>
             <Text>ZIndex {indices[1]}</Text>
           </View>
-          <View style={[
-            styles.zIndex,
-            {marginLeft: 100, backgroundColor: '#81C784', zIndex: indices[2]}
-          ]}>
+          <View
+            style={[
+              styles.zIndex,
+              {marginLeft: 100, backgroundColor: '#81C784', zIndex: indices[2]},
+            ]}>
             <Text>ZIndex {indices[2]}</Text>
           </View>
-          <View style={[
-            styles.zIndex,
-            {marginLeft: 150, backgroundColor: '#64B5F6', zIndex: indices[3]}
-          ]}>
+          <View
+            style={[
+              styles.zIndex,
+              {marginLeft: 150, backgroundColor: '#64B5F6', zIndex: indices[3]},
+            ]}>
             <Text>ZIndex {indices[3]}</Text>
           </View>
         </View>
@@ -116,7 +116,8 @@ class ZIndexExample extends React.Component<{}, $FlowFixMeState> {
 }
 
 exports.title = '<View>';
-exports.description = 'Basic building block of all UI, examples that ' +
+exports.description =
+  'Basic building block of all UI, examples that ' +
   'demonstrate some of the many styles available.';
 
 exports.displayName = 'ViewExample';
@@ -126,13 +127,12 @@ exports.examples = [
     render: function() {
       return (
         <View style={{backgroundColor: '#527FE4', padding: 5}}>
-          <Text style={{fontSize: 11}}>
-            Blue background
-          </Text>
+          <Text style={{fontSize: 11}}>Blue background</Text>
         </View>
       );
     },
-  }, {
+  },
+  {
     title: 'Border',
     render: function() {
       return (
@@ -141,7 +141,8 @@ exports.examples = [
         </View>
       );
     },
-  }, {
+  },
+  {
     title: 'Padding/Margin',
     render: function() {
       return (
@@ -152,43 +153,48 @@ exports.examples = [
           <View style={[styles.box, {margin: 5}]}>
             <Text style={{fontSize: 11}}>5px margin</Text>
           </View>
-          <View style={[styles.box, {margin: 5, padding: 5, alignSelf: 'flex-start'}]}>
-            <Text style={{fontSize: 11}}>
-              5px margin and padding,
-            </Text>
-            <Text style={{fontSize: 11}}>
-              widthAutonomous=true
-            </Text>
+          <View
+            style={[
+              styles.box,
+              {margin: 5, padding: 5, alignSelf: 'flex-start'},
+            ]}>
+            <Text style={{fontSize: 11}}>5px margin and padding,</Text>
+            <Text style={{fontSize: 11}}>widthAutonomous=true</Text>
           </View>
         </View>
       );
     },
-  }, {
+  },
+  {
     title: 'Border Radius',
     render: function() {
       return (
         <View style={{borderWidth: 0.5, borderRadius: 5, padding: 5}}>
           <Text style={{fontSize: 11}}>
-            Too much use of `borderRadius` (especially large radii) on
-            anything which is scrolling may result in dropped frames.
-            Use sparingly.
+            Too much use of `borderRadius` (especially large radii) on anything
+            which is scrolling may result in dropped frames. Use sparingly.
           </Text>
         </View>
       );
     },
-  }, {
+  },
+  {
     title: 'Border Style',
     render: function() {
       return <ViewBorderStyleExample />;
     },
-  }, {
+  },
+  {
     title: 'Circle with Border Radius',
     render: function() {
       return (
-        <View style={{borderRadius: 10, borderWidth: 1, width: 20, height: 20}} />
+        <View
+          style={{borderRadius: 10, borderWidth: 1, width: 20, height: 20}}
+        />
       );
     },
-  }, {
+  },
+  {
     title: 'Overflow',
     render: function() {
       return (
@@ -206,7 +212,8 @@ exports.examples = [
               <Text>Overflow hidden</Text>
             </View>
           </View>
-          <View style={{width: 95, height: 10, marginBottom: 5, borderWidth: 0.5}}>
+          <View
+            style={{width: 95, height: 10, marginBottom: 5, borderWidth: 0.5}}>
             <View style={{width: 200, height: 20}}>
               <Text>Overflow visible</Text>
             </View>
@@ -214,22 +221,38 @@ exports.examples = [
         </View>
       );
     },
-  }, {
+  },
+  {
     title: 'Opacity',
     render: function() {
       return (
         <View>
-          <View style={{opacity: 0}}><Text>Opacity 0</Text></View>
-          <View style={{opacity: 0.1}}><Text>Opacity 0.1</Text></View>
-          <View style={{opacity: 0.3}}><Text>Opacity 0.3</Text></View>
-          <View style={{opacity: 0.5}}><Text>Opacity 0.5</Text></View>
-          <View style={{opacity: 0.7}}><Text>Opacity 0.7</Text></View>
-          <View style={{opacity: 0.9}}><Text>Opacity 0.9</Text></View>
-          <View style={{opacity: 1}}><Text>Opacity 1</Text></View>
+          <View style={{opacity: 0}}>
+            <Text>Opacity 0</Text>
+          </View>
+          <View style={{opacity: 0.1}}>
+            <Text>Opacity 0.1</Text>
+          </View>
+          <View style={{opacity: 0.3}}>
+            <Text>Opacity 0.3</Text>
+          </View>
+          <View style={{opacity: 0.5}}>
+            <Text>Opacity 0.5</Text>
+          </View>
+          <View style={{opacity: 0.7}}>
+            <Text>Opacity 0.7</Text>
+          </View>
+          <View style={{opacity: 0.9}}>
+            <Text>Opacity 0.9</Text>
+          </View>
+          <View style={{opacity: 1}}>
+            <Text>Opacity 1</Text>
+          </View>
         </View>
       );
     },
-  }, {
+  },
+  {
     title: 'ZIndex',
     render: function() {
       return <ZIndexExample />;
diff --git a/RNTester/js/ViewPagerAndroidExample.android.js b/RNTester/js/ViewPagerAndroidExample.android.js
index 1c5da99bae64..1eb60ad3d6c6 100644
--- a/RNTester/js/ViewPagerAndroidExample.android.js
+++ b/RNTester/js/ViewPagerAndroidExample.android.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('react');
@@ -19,7 +21,7 @@ var {
   ViewPagerAndroid,
 } = ReactNative;
 
-import type { ViewPagerScrollState } from 'ViewPagerAndroid';
+import type {ViewPagerScrollState} from 'ViewPagerAndroid';
 
 var PAGES = 5;
 var BGCOLOR = ['#fdc08e', '#fff6b9', '#99d1b7', '#dde5fe', '#f79273'];
@@ -45,13 +47,9 @@ class LikeCount extends React.Component {
     return (
       <View style={styles.likeContainer}>
         <TouchableOpacity onPress={this.onClick} style={styles.likeButton}>
-          <Text style={styles.likesText}>
-            {thumbsUp + ' Like'}
-          </Text>
+          <Text style={styles.likesText}>{thumbsUp + ' Like'}</Text>
         </TouchableOpacity>
-        <Text style={styles.likesText}>
-          {this.state.likes + ' likes'}
-        </Text>
+        <Text style={styles.likesText}>{this.state.likes + ' likes'}</Text>
       </View>
     );
   }
@@ -67,7 +65,11 @@ class Button extends React.Component {
   render() {
     return (
       <TouchableWithoutFeedback onPress={this._handlePress}>
-        <View style={[styles.button, this.props.enabled ? {} : styles.buttonDisabled]}>
+        <View
+          style={[
+            styles.button,
+            this.props.enabled ? {} : styles.buttonDisabled,
+          ]}>
           <Text style={styles.buttonText}>{this.props.text}</Text>
         </View>
       </TouchableWithoutFeedback>
@@ -77,11 +79,12 @@ class Button extends React.Component {
 
 class ProgressBar extends React.Component {
   render() {
-    var fractionalPosition = (this.props.progress.position + this.props.progress.offset);
-    var progressBarSize = (fractionalPosition / (PAGES - 1)) * this.props.size;
+    var fractionalPosition =
+      this.props.progress.position + this.props.progress.offset;
+    var progressBarSize = fractionalPosition / (PAGES - 1) * this.props.size;
     return (
       <View style={[styles.progressBarContainer, {width: this.props.size}]}>
-        <View style={[styles.progressBar, {width: progressBarSize}]}/>
+        <View style={[styles.progressBar, {width: progressBarSize}]} />
       </View>
     );
   }
@@ -101,24 +104,24 @@ class ViewPagerAndroidExample extends React.Component {
     },
   };
 
-  onPageSelected = (e) => {
+  onPageSelected = e => {
     this.setState({page: e.nativeEvent.position});
   };
 
-  onPageScroll = (e) => {
+  onPageScroll = e => {
     this.setState({progress: e.nativeEvent});
   };
 
-  onPageScrollStateChanged = (state : ViewPagerScrollState) => {
+  onPageScrollStateChanged = (state: ViewPagerScrollState) => {
     this.setState({scrollState: state});
   };
 
-  move = (delta) => {
+  move = delta => {
     var page = this.state.page + delta;
     this.go(page);
   };
 
-  go = (page) => {
+  go = page => {
     if (this.state.animationsAreEnabled) {
       this.viewPager.setPage(page);
     } else {
@@ -143,10 +146,10 @@ class ViewPagerAndroidExample extends React.Component {
             source={{uri: IMAGE_URIS[i % BGCOLOR.length]}}
           />
           <LikeCount />
-       </View>
+        </View>,
       );
     }
-    var { page, animationsAreEnabled } = this.state;
+    var {page, animationsAreEnabled} = this.state;
     return (
       <View style={styles.container}>
         <ViewPagerAndroid
@@ -157,37 +160,61 @@ class ViewPagerAndroidExample extends React.Component {
           onPageSelected={this.onPageSelected}
           onPageScrollStateChanged={this.onPageScrollStateChanged}
           pageMargin={10}
-          ref={viewPager => { this.viewPager = viewPager; }}>
+          ref={viewPager => {
+            this.viewPager = viewPager;
+          }}>
           {pages}
         </ViewPagerAndroid>
         <View style={styles.buttons}>
           <Button
             enabled={true}
-            text={this.state.scrollEnabled ? 'Scroll Enabled' : 'Scroll Disabled'}
-            onPress={() => this.setState({scrollEnabled: !this.state.scrollEnabled})}
+            text={
+              this.state.scrollEnabled ? 'Scroll Enabled' : 'Scroll Disabled'
+            }
+            onPress={() =>
+              this.setState({scrollEnabled: !this.state.scrollEnabled})
+            }
           />
         </View>
         <View style={styles.buttons}>
-          { animationsAreEnabled ?
+          {animationsAreEnabled ? (
             <Button
               text="Turn off animations"
               enabled={true}
               onPress={() => this.setState({animationsAreEnabled: false})}
-            /> :
+            />
+          ) : (
             <Button
               text="Turn animations back on"
               enabled={true}
               onPress={() => this.setState({animationsAreEnabled: true})}
-            /> }
-          <Text style={styles.scrollStateText}>ScrollState[ {this.state.scrollState} ]</Text>
+            />
+          )}
+          <Text style={styles.scrollStateText}>
+            ScrollState[ {this.state.scrollState} ]
+          </Text>
         </View>
         <View style={styles.buttons}>
-          <Button text="Start" enabled={page > 0} onPress={() => this.go(0)}/>
-          <Button text="Prev" enabled={page > 0} onPress={() => this.move(-1)}/>
-          <Text style={styles.buttonText}>Page {page + 1} / {PAGES}</Text>
-          <ProgressBar size={100} progress={this.state.progress}/>
-          <Button text="Next" enabled={page < PAGES - 1} onPress={() => this.move(1)}/>
-          <Button text="Last" enabled={page < PAGES - 1} onPress={() => this.go(PAGES - 1)}/>
+          <Button text="Start" enabled={page > 0} onPress={() => this.go(0)} />
+          <Button
+            text="Prev"
+            enabled={page > 0}
+            onPress={() => this.move(-1)}
+          />
+          <Text style={styles.buttonText}>
+            Page {page + 1} / {PAGES}
+          </Text>
+          <ProgressBar size={100} progress={this.state.progress} />
+          <Button
+            text="Next"
+            enabled={page < PAGES - 1}
+            onPress={() => this.move(1)}
+          />
+          <Button
+            text="Last"
+            enabled={page < PAGES - 1}
+            onPress={() => this.go(PAGES - 1)}
+          />
         </View>
       </View>
     );
diff --git a/RNTester/js/WebViewExample.js b/RNTester/js/WebViewExample.js
index 84b99001ecf5..fdb0abb61d49 100644
--- a/RNTester/js/WebViewExample.js
+++ b/RNTester/js/WebViewExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -17,7 +19,7 @@ var {
   TouchableWithoutFeedback,
   TouchableOpacity,
   View,
-  WebView
+  WebView,
 } = ReactNative;
 
 var HEADER = '#3b5998';
@@ -41,7 +43,7 @@ class WebViewExample extends React.Component<{}, $FlowFixMeState> {
 
   inputText = '';
 
-  handleTextInputChange = (event) => {
+  handleTextInputChange = event => {
     var url = event.nativeEvent.text;
     if (!/^[a-zA-Z-_]+:/.test(url)) {
       url = 'http://' + url;
@@ -57,17 +59,21 @@ class WebViewExample extends React.Component<{}, $FlowFixMeState> {
         <View style={[styles.addressBarRow]}>
           <TouchableOpacity
             onPress={this.goBack}
-            style={this.state.backButtonEnabled ? styles.navButton : styles.disabledButton}>
-            <Text>
-               {'<'}
-            </Text>
+            style={
+              this.state.backButtonEnabled
+                ? styles.navButton
+                : styles.disabledButton
+            }>
+            <Text>{'<'}</Text>
           </TouchableOpacity>
           <TouchableOpacity
             onPress={this.goForward}
-            style={this.state.forwardButtonEnabled ? styles.navButton : styles.disabledButton}>
-            <Text>
-              {'>'}
-            </Text>
+            style={
+              this.state.forwardButtonEnabled
+                ? styles.navButton
+                : styles.disabledButton
+            }>
+            <Text>{'>'}</Text>
           </TouchableOpacity>
           <TextInput
             ref={TEXT_INPUT_REF}
@@ -80,9 +86,7 @@ class WebViewExample extends React.Component<{}, $FlowFixMeState> {
           />
           <TouchableOpacity onPress={this.pressGoButton}>
             <View style={styles.goButton}>
-              <Text>
-                 Go!
-              </Text>
+              <Text>Go!</Text>
             </View>
           </TouchableOpacity>
         </View>
@@ -118,23 +122,23 @@ class WebViewExample extends React.Component<{}, $FlowFixMeState> {
     this.refs[WEBVIEW_REF].reload();
   };
 
-  onShouldStartLoadWithRequest = (event) => {
+  onShouldStartLoadWithRequest = event => {
     // Implement any custom loading logic here, don't forget to return!
     return true;
   };
 
-  onNavigationStateChange = (navState) => {
+  onNavigationStateChange = navState => {
     this.setState({
       backButtonEnabled: navState.canGoBack,
       forwardButtonEnabled: navState.canGoForward,
       url: navState.url,
       status: navState.title,
       loading: navState.loading,
-      scalesPageToFit: true
+      scalesPageToFit: true,
     });
   };
 
-  onSubmitEditing = (event) => {
+  onSubmitEditing = event => {
     this.pressGoButton();
   };
 
@@ -187,17 +191,19 @@ class ScaledWebView extends React.Component<{}, $FlowFixMeState> {
           scalesPageToFit={this.state.scalingEnabled}
         />
         <View style={styles.buttons}>
-        { this.state.scalingEnabled ?
-          <Button
-            text="Scaling:ON"
-            enabled={true}
-            onPress={() => this.setState({scalingEnabled: false})}
-          /> :
-          <Button
-            text="Scaling:OFF"
-            enabled={true}
-            onPress={() => this.setState({scalingEnabled: true})}
-          /> }
+          {this.state.scalingEnabled ? (
+            <Button
+              text="Scaling:ON"
+              enabled={true}
+              onPress={() => this.setState({scalingEnabled: false})}
+            />
+          ) : (
+            <Button
+              text="Scaling:OFF"
+              enabled={true}
+              onPress={() => this.setState({scalingEnabled: true})}
+            />
+          )}
         </View>
       </View>
     );
@@ -205,39 +211,48 @@ class ScaledWebView extends React.Component<{}, $FlowFixMeState> {
 }
 
 class MessagingTest extends React.Component<{}, $FlowFixMeState> {
-  webview = null
+  webview = null;
 
   state = {
     messagesReceivedFromWebView: 0,
     message: '',
-  }
+  };
 
-  onMessage = e => this.setState({
-    messagesReceivedFromWebView: this.state.messagesReceivedFromWebView + 1,
-    message: e.nativeEvent.data,
-  })
+  onMessage = e =>
+    this.setState({
+      messagesReceivedFromWebView: this.state.messagesReceivedFromWebView + 1,
+      message: e.nativeEvent.data,
+    });
 
   postMessage = () => {
     if (this.webview) {
       this.webview.postMessage('"Hello" from React Native!');
     }
-  }
+  };
 
   render(): React.Node {
     const {messagesReceivedFromWebView, message} = this.state;
 
     return (
-      <View style={[styles.container, { height: 200 }]}>
+      <View style={[styles.container, {height: 200}]}>
         <View style={styles.container}>
-          <Text>Messages received from web view: {messagesReceivedFromWebView}</Text>
+          <Text>
+            Messages received from web view: {messagesReceivedFromWebView}
+          </Text>
           <Text>{message || '(No message)'}</Text>
           <View style={styles.buttons}>
-            <Button text="Send Message to Web View" enabled onPress={this.postMessage} />
+            <Button
+              text="Send Message to Web View"
+              enabled
+              onPress={this.postMessage}
+            />
           </View>
         </View>
         <View style={styles.container}>
           <WebView
-            ref={webview => { this.webview = webview; }}
+            ref={webview => {
+              this.webview = webview;
+            }}
             style={{
               backgroundColor: BGWASH,
               height: 100,
@@ -259,12 +274,14 @@ class InjectJS extends React.Component<{}> {
     if (this.webview) {
       this.webview.injectJavaScript(script);
     }
-  }
+  };
   render() {
     return (
       <View>
         <WebView
-          ref={webview => { this.webview = webview; }}
+          ref={webview => {
+            this.webview = webview;
+          }}
           style={{
             backgroundColor: BGWASH,
             height: 300,
@@ -275,12 +292,11 @@ class InjectJS extends React.Component<{}> {
         <View style={styles.buttons}>
           <Button text="Inject JS" enabled onPress={this.injectJS} />
         </View>
-    </View>
+      </View>
     );
   }
 }
 
-
 var styles = StyleSheet.create({
   container: {
     flex: 1,
@@ -401,11 +417,15 @@ exports.description = 'Base component to display web content';
 exports.examples = [
   {
     title: 'Simple Browser',
-    render(): React.Element<any> { return <WebViewExample />; }
+    render(): React.Element<any> {
+      return <WebViewExample />;
+    },
   },
   {
     title: 'Scale Page to Fit',
-    render(): React.Element<any> { return <ScaledWebView/>; }
+    render(): React.Element<any> {
+      return <ScaledWebView />;
+    },
   },
   {
     title: 'Bundled HTML',
@@ -421,7 +441,7 @@ exports.examples = [
           scalesPageToFit={true}
         />
       );
-    }
+    },
   },
   {
     title: 'Static HTML',
@@ -436,7 +456,7 @@ exports.examples = [
           scalesPageToFit={true}
         />
       );
-    }
+    },
   },
   {
     title: 'POST Test',
@@ -450,19 +470,23 @@ exports.examples = [
           source={{
             uri: 'http://www.posttestserver.com/post.php',
             method: 'POST',
-            body: 'foo=bar&bar=foo'
+            body: 'foo=bar&bar=foo',
           }}
           scalesPageToFit={false}
         />
       );
-    }
+    },
   },
   {
     title: 'Messaging Test',
-    render(): React.Element<any> { return <MessagingTest />; }
+    render(): React.Element<any> {
+      return <MessagingTest />;
+    },
   },
   {
     title: 'Inject JavaScript',
-    render(): React.Element<any> { return <InjectJS />; }
+    render(): React.Element<any> {
+      return <InjectJS />;
+    },
   },
 ];
diff --git a/RNTester/js/XHRExample.js b/RNTester/js/XHRExample.js
index fc7cb8c21376..5cec37c1debc 100644
--- a/RNTester/js/XHRExample.js
+++ b/RNTester/js/XHRExample.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
@@ -20,41 +22,50 @@ var XHRExampleCookies = require('./XHRExampleCookies');
 
 exports.framework = 'React';
 exports.title = 'XMLHttpRequest';
-exports.description = 'Example that demonstrates upload and download ' +
+exports.description =
+  'Example that demonstrates upload and download ' +
   'requests using XMLHttpRequest.';
-exports.examples = [{
-  title: 'File Download',
-  render() {
-    return <XHRExampleDownload/>;
-  }
-}, {
-  title: 'multipart/form-data Upload',
-  render() {
-    return <XHRExampleBinaryUpload/>;
-  }
-}, {
-  title: 'multipart/form-data Upload',
-  render() {
-    return <XHRExampleFormData/>;
-  }
-}, {
-  title: 'Fetch Test',
-  render() {
-    return <XHRExampleFetch/>;
-  }
-}, {
-  title: 'Headers',
-  render() {
-    return <XHRExampleHeaders/>;
-  }
-}, {
-  title: 'Time Out Test',
-  render() {
-    return <XHRExampleOnTimeOut/>;
-  }
-}, {
-  title: 'Cookies',
-  render() {
-    return <XHRExampleCookies/>;
-  }
-}];
+exports.examples = [
+  {
+    title: 'File Download',
+    render() {
+      return <XHRExampleDownload />;
+    },
+  },
+  {
+    title: 'multipart/form-data Upload',
+    render() {
+      return <XHRExampleBinaryUpload />;
+    },
+  },
+  {
+    title: 'multipart/form-data Upload',
+    render() {
+      return <XHRExampleFormData />;
+    },
+  },
+  {
+    title: 'Fetch Test',
+    render() {
+      return <XHRExampleFetch />;
+    },
+  },
+  {
+    title: 'Headers',
+    render() {
+      return <XHRExampleHeaders />;
+    },
+  },
+  {
+    title: 'Time Out Test',
+    render() {
+      return <XHRExampleOnTimeOut />;
+    },
+  },
+  {
+    title: 'Cookies',
+    render() {
+      return <XHRExampleCookies />;
+    },
+  },
+];
diff --git a/RNTester/js/XHRExampleBinaryUpload.js b/RNTester/js/XHRExampleBinaryUpload.js
index efe96dea0f22..1321522ccaf7 100644
--- a/RNTester/js/XHRExampleBinaryUpload.js
+++ b/RNTester/js/XHRExampleBinaryUpload.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -47,30 +49,22 @@ That is my proper element.
 --Faust, JW Goethe
 `;
 
-
 class XHRExampleBinaryUpload extends React.Component<{}, $FlowFixMeState> {
-
   static handlePostTestServerUpload(xhr: XMLHttpRequest) {
     if (xhr.status !== 200) {
       Alert.alert(
         'Upload failed',
-        'Expected HTTP 200 OK response, got ' + xhr.status
+        'Expected HTTP 200 OK response, got ' + xhr.status,
       );
       return;
     }
     if (!xhr.responseText) {
-      Alert.alert(
-        'Upload failed',
-        'No response payload.'
-      );
+      Alert.alert('Upload failed', 'No response payload.');
       return;
     }
     var index = xhr.responseText.indexOf('http://www.posttestserver.com/');
     if (index === -1) {
-      Alert.alert(
-        'Upload failed',
-        'Invalid response payload.'
-      );
+      Alert.alert('Upload failed', 'Invalid response payload.');
       return;
     }
     var url = xhr.responseText.slice(index).split('\n')[0];
@@ -117,8 +111,8 @@ class XHRExampleBinaryUpload extends React.Component<{}, $FlowFixMeState> {
         <Text>Upload 255 bytes as...</Text>
         <Picker
           selectedValue={this.state.type}
-          onValueChange={(type) => this.setState({type})}>
-          {Object.keys(BINARY_TYPES).map((type) => (
+          onValueChange={type => this.setState({type})}>
+          {Object.keys(BINARY_TYPES).map(type => (
             <Picker.Item key={type} label={type} value={type} />
           ))}
         </Picker>
@@ -132,7 +126,6 @@ class XHRExampleBinaryUpload extends React.Component<{}, $FlowFixMeState> {
       </View>
     );
   }
-
 }
 
 const styles = StyleSheet.create({
diff --git a/RNTester/js/XHRExampleCookies.js b/RNTester/js/XHRExampleCookies.js
index 2050f555eb91..6008e7a1a3c2 100644
--- a/RNTester/js/XHRExampleCookies.js
+++ b/RNTester/js/XHRExampleCookies.js
@@ -4,19 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  TouchableHighlight,
-  View,
-  WebView,
-} = ReactNative;
+var {StyleSheet, Text, TouchableHighlight, View, WebView} = ReactNative;
 
 var RCTNetworking = require('RCTNetworking');
 
@@ -36,7 +32,7 @@ class XHRExampleCookies extends React.Component<any, any> {
   setCookie(domain: string) {
     var {a, b} = this.state;
     var url = `https://${domain}/cookies/set?a=${a}&b=${b}`;
-    fetch(url).then((response) => {
+    fetch(url).then(response => {
       this.setStatus(`Cookies a=${a}, b=${b} set`);
       this.refreshWebview();
     });
@@ -49,18 +45,22 @@ class XHRExampleCookies extends React.Component<any, any> {
   }
 
   getCookies(domain: string) {
-    fetch(`https://${domain}/cookies`).then((response) => {
-      return response.json();
-    }).then((data) => {
-      this.setStatus(`Got cookies ${JSON.stringify(data.cookies)} from server`);
-      this.refreshWebview();
-    });
+    fetch(`https://${domain}/cookies`)
+      .then(response => {
+        return response.json();
+      })
+      .then(data => {
+        this.setStatus(
+          `Got cookies ${JSON.stringify(data.cookies)} from server`,
+        );
+        this.refreshWebview();
+      });
 
     this.setStatus('Getting cookies...');
   }
 
   clearCookies() {
-    RCTNetworking.clearCookies((cleared) => {
+    RCTNetworking.clearCookies(cleared => {
       this.setStatus('Cookies cleared, had cookies=' + cleared.toString());
       this.refreshWebview();
     });
diff --git a/RNTester/js/XHRExampleDownload.js b/RNTester/js/XHRExampleDownload.js
index 2ffe801fbcc1..3cc4b34c5bc0 100644
--- a/RNTester/js/XHRExampleDownload.js
+++ b/RNTester/js/XHRExampleDownload.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -40,11 +42,7 @@ class ProgressBar extends React.Component<$FlowFixMeProps> {
         />
       );
     }
-    return (
-      <ProgressViewIOS
-        progress={this.props.progress}
-      />
-    );
+    return <ProgressViewIOS progress={this.props.progress} />;
   }
 }
 
@@ -77,8 +75,10 @@ class XHRExampleDownload extends React.Component<{}, Object> {
 
     const onreadystatechange = () => {
       if (xhr.readyState === xhr.HEADERS_RECEIVED) {
-        const contentLength =
-          parseInt(xhr.getResponseHeader('Content-Length'), 10);
+        const contentLength = parseInt(
+          xhr.getResponseHeader('Content-Length'),
+          10,
+        );
         this.setState({
           contentLength,
           responseLength: 0,
@@ -89,7 +89,7 @@ class XHRExampleDownload extends React.Component<{}, Object> {
         });
       }
     };
-    const onprogress = (event) => {
+    const onprogress = event => {
       this.setState({
         progressTotal: event.total,
         progressLoaded: event.loaded,
@@ -112,17 +112,19 @@ class XHRExampleDownload extends React.Component<{}, Object> {
         return;
       }
       if (xhr.status === 200) {
-        let responseType =
-          `Response is a string, ${xhr.response.length} characters long.`;
+        let responseType = `Response is a string, ${
+          xhr.response.length
+        } characters long.`;
         if (xhr.response instanceof ArrayBuffer) {
-          responseType =
-            `Response is an ArrayBuffer, ${xhr.response.byteLength} bytes long.`;
+          responseType = `Response is an ArrayBuffer, ${
+            xhr.response.byteLength
+          } bytes long.`;
         }
         Alert.alert('Download complete!', responseType);
       } else if (xhr.status !== 0) {
         Alert.alert(
           'Error',
-          `Server returned HTTP status of ${xhr.status}: ${xhr.responseText}`
+          `Server returned HTTP status of ${xhr.status}: ${xhr.responseText}`,
         );
       } else {
         Alert.alert('Error', xhr.responseText);
@@ -134,7 +136,7 @@ class XHRExampleDownload extends React.Component<{}, Object> {
     xhr.send();
 
     this.setState({downloading: true});
-  }
+  };
 
   componentWillUnmount() {
     this.cancelled = true;
@@ -149,9 +151,7 @@ class XHRExampleDownload extends React.Component<{}, Object> {
         </View>
       </View>
     ) : (
-      <TouchableHighlight
-        style={styles.wrapper}
-        onPress={this._download}>
+      <TouchableHighlight style={styles.wrapper} onPress={this._download}>
         <View style={styles.button}>
           <Text>Download 5MB Text File</Text>
         </View>
@@ -161,30 +161,26 @@ class XHRExampleDownload extends React.Component<{}, Object> {
     let readystate = null;
     let progress = null;
     if (this.state.readystateHandler && !this.state.arraybuffer) {
-      const { responseLength, contentLength } = this.state;
+      const {responseLength, contentLength} = this.state;
       readystate = (
         <View>
           <Text style={styles.progressBarLabel}>
-            responseText:{' '}
-            {roundKilo(responseLength)}/{roundKilo(contentLength)}k chars
+            responseText: {roundKilo(responseLength)}/{roundKilo(contentLength)}k
+            chars
           </Text>
-          <ProgressBar
-            progress={(responseLength / contentLength)}
-          />
+          <ProgressBar progress={responseLength / contentLength} />
         </View>
       );
     }
     if (this.state.progressHandler) {
-      const { progressLoaded, progressTotal } = this.state;
+      const {progressLoaded, progressTotal} = this.state;
       progress = (
         <View>
           <Text style={styles.progressBarLabel}>
-            onprogress:{' '}
-            {roundKilo(progressLoaded)}/{roundKilo(progressTotal)} KB
+            onprogress: {roundKilo(progressLoaded)}/{roundKilo(progressTotal)}{' '}
+            KB
           </Text>
-          <ProgressBar
-            progress={(progressLoaded / progressTotal)}
-          />
+          <ProgressBar progress={progressLoaded / progressTotal} />
         </View>
       );
     }
@@ -195,21 +191,23 @@ class XHRExampleDownload extends React.Component<{}, Object> {
           <Text>onreadystatechange handler</Text>
           <Switch
             value={this.state.readystateHandler}
-            onValueChange={(readystateHandler => this.setState({readystateHandler}))}
+            onValueChange={readystateHandler =>
+              this.setState({readystateHandler})
+            }
           />
         </View>
         <View style={styles.configRow}>
           <Text>onprogress handler</Text>
           <Switch
             value={this.state.progressHandler}
-            onValueChange={(progressHandler => this.setState({progressHandler}))}
+            onValueChange={progressHandler => this.setState({progressHandler})}
           />
         </View>
         <View style={styles.configRow}>
           <Text>download as arraybuffer</Text>
           <Switch
             value={this.state.arraybuffer}
-            onValueChange={(arraybuffer => this.setState({arraybuffer}))}
+            onValueChange={arraybuffer => this.setState({arraybuffer})}
           />
         </View>
         {button}
diff --git a/RNTester/js/XHRExampleFetch.js b/RNTester/js/XHRExampleFetch.js
index c4915ce5677a..72f1f7e43b11 100644
--- a/RNTester/js/XHRExampleFetch.js
+++ b/RNTester/js/XHRExampleFetch.js
@@ -4,20 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  TextInput,
-  View,
-  Platform,
-} = ReactNative;
-
+var {StyleSheet, Text, TextInput, View, Platform} = ReactNative;
 
 class XHRExampleFetch extends React.Component<any, any> {
   responseURL: ?string;
@@ -26,20 +21,22 @@ class XHRExampleFetch extends React.Component<any, any> {
   constructor(props: any) {
     super(props);
     this.state = {
-     responseText: null,
+      responseText: null,
     };
     this.responseURL = null;
     this.responseHeaders = null;
   }
 
   submit(uri: String) {
-    fetch(uri).then((response) => {
-      this.responseURL = response.url;
-      this.responseHeaders = response.headers;
-      return response.text();
-    }).then((body) => {
-      this.setState({responseText: body});
-    });
+    fetch(uri)
+      .then(response => {
+        this.responseURL = response.url;
+        this.responseHeaders = response.headers;
+        return response.text();
+      })
+      .then(body => {
+        this.setState({responseText: body});
+      });
   }
 
   _renderHeaders() {
@@ -52,13 +49,16 @@ class XHRExampleFetch extends React.Component<any, any> {
     for (var i = 0; i < keys.length; i++) {
       var key = keys[i];
       var value = this.responseHeaders.get(key);
-      responseHeaders.push(<Text>{key}: {value}</Text>);
+      responseHeaders.push(
+        <Text>
+          {key}: {value}
+        </Text>,
+      );
     }
     return responseHeaders;
   }
 
   render() {
-
     var responseURL = this.responseURL ? (
       <View style={{marginTop: 10}}>
         <Text style={styles.label}>Server response URL:</Text>
@@ -91,7 +91,7 @@ class XHRExampleFetch extends React.Component<any, any> {
         <TextInput
           returnKeyType="go"
           defaultValue="http://www.posttestserver.com/post.php"
-          onSubmitEditing={(event)=> {
+          onSubmitEditing={event => {
             this.submit(event.nativeEvent.text);
           }}
           style={styles.textInput}
diff --git a/RNTester/js/XHRExampleFormData.js b/RNTester/js/XHRExampleFormData.js
index 8c0080ea11b7..bc2e43b07628 100644
--- a/RNTester/js/XHRExampleFormData.js
+++ b/RNTester/js/XHRExampleFormData.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
@@ -48,30 +50,25 @@ class XHRExampleFormData extends React.Component<Object, Object> {
   }
 
   _fetchRandomPhoto = () => {
-    CameraRoll.getPhotos(
-      {first: PAGE_SIZE}
-    ).then(
-      (data) => {
-        if (!this._isMounted) {
-          return;
-        }
-        var edges = data.edges;
-        var edge = edges[Math.floor(Math.random() * edges.length)];
-        var randomPhoto = edge && edge.node && edge.node.image;
-        if (randomPhoto) {
-          let {width, height} = randomPhoto;
-          width *= 0.25;
-          height *= 0.25;
-          ImageEditor.cropImage(
-            randomPhoto.uri,
-            {offset: {x: 0, y: 0}, size: {width, height}},
-            (uri) => this.setState({randomPhoto: {uri}}),
-            (error) => undefined
-          );
-        }
-      },
-      (error) => undefined
-    );
+    CameraRoll.getPhotos({first: PAGE_SIZE}).then(data => {
+      if (!this._isMounted) {
+        return;
+      }
+      var edges = data.edges;
+      var edge = edges[Math.floor(Math.random() * edges.length)];
+      var randomPhoto = edge && edge.node && edge.node.image;
+      if (randomPhoto) {
+        let {width, height} = randomPhoto;
+        width *= 0.25;
+        height *= 0.25;
+        ImageEditor.cropImage(
+          randomPhoto.uri,
+          {offset: {x: 0, y: 0}, size: {width, height}},
+          uri => this.setState({randomPhoto: {uri}}),
+          error => undefined,
+        );
+      }
+    }, error => undefined);
   };
 
   _addTextParam = () => {
@@ -107,10 +104,10 @@ class XHRExampleFormData extends React.Component<Object, Object> {
         name: 'image.jpg',
       });
     }
-    this.state.textParams.forEach(
-      (param) => formdata.append(param.name, param.value)
+    this.state.textParams.forEach(param =>
+      formdata.append(param.name, param.value),
     );
-    xhr.upload.onprogress = (event) => {
+    xhr.upload.onprogress = event => {
       if (event.lengthComputable) {
         this.setState({uploadProgress: event.loaded / event.total});
       }
@@ -124,10 +121,7 @@ class XHRExampleFormData extends React.Component<Object, Object> {
     var image = null;
     if (this.state.randomPhoto) {
       image = (
-        <Image
-          source={this.state.randomPhoto}
-          style={styles.randomPhoto}
-        />
+        <Image source={this.state.randomPhoto} style={styles.randomPhoto} />
       );
     }
     var textItems = this.state.textParams.map((item, index) => (
@@ -170,8 +164,9 @@ class XHRExampleFormData extends React.Component<Object, Object> {
       <View>
         <View style={styles.paramRow}>
           <Text style={styles.photoLabel}>
-            Random photo from your library
-            (<Text style={styles.textButton} onPress={this._fetchRandomPhoto}>
+            Random photo from your library (<Text
+              style={styles.textButton}
+              onPress={this._fetchRandomPhoto}>
               update
             </Text>)
           </Text>
@@ -185,9 +180,7 @@ class XHRExampleFormData extends React.Component<Object, Object> {
             Add a text param
           </Text>
         </View>
-        <View style={styles.uploadButton}>
-          {uploadButton}
-        </View>
+        <View style={styles.uploadButton}>{uploadButton}</View>
       </View>
     );
   }
diff --git a/RNTester/js/XHRExampleHeaders.js b/RNTester/js/XHRExampleHeaders.js
index b3dc69edc21a..6fb4e28dbf03 100644
--- a/RNTester/js/XHRExampleHeaders.js
+++ b/RNTester/js/XHRExampleHeaders.js
@@ -4,21 +4,17 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @noflow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  TouchableHighlight,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, TouchableHighlight, View} = ReactNative;
 
 class XHRExampleHeaders extends React.Component {
-
   xhr: XMLHttpRequest;
   cancelled: boolean;
 
@@ -46,11 +42,15 @@ class XHRExampleHeaders extends React.Component {
         if (xhr.status === 200) {
           this.setState({
             status: 'Download complete!',
-            headers: xhr.getAllResponseHeaders()
+            headers: xhr.getAllResponseHeaders(),
           });
         } else if (xhr.status !== 0) {
           this.setState({
-            status: 'Error: Server returned HTTP status of ' + xhr.status + ' ' + xhr.responseText,
+            status:
+              'Error: Server returned HTTP status of ' +
+              xhr.status +
+              ' ' +
+              xhr.responseText,
           });
         } else {
           this.setState({
@@ -59,7 +59,10 @@ class XHRExampleHeaders extends React.Component {
         }
       }
     };
-    xhr.open('GET', 'https://httpbin.org/response-headers?header1=value&header2=value1&header2=value2');
+    xhr.open(
+      'GET',
+      'https://httpbin.org/response-headers?header1=value&header2=value1&header2=value2',
+    );
     xhr.send();
     this.xhr = xhr;
 
@@ -72,21 +75,22 @@ class XHRExampleHeaders extends React.Component {
   }
 
   render() {
-    var button = this.state.status === 'Downloading...' ? (
-      <View style={styles.wrapper}>
-        <View style={styles.button}>
-          <Text>...</Text>
+    var button =
+      this.state.status === 'Downloading...' ? (
+        <View style={styles.wrapper}>
+          <View style={styles.button}>
+            <Text>...</Text>
+          </View>
         </View>
-      </View>
-    ) : (
-      <TouchableHighlight
-        style={styles.wrapper}
-        onPress={this.download.bind(this)}>
-        <View style={styles.button}>
-         <Text>Get headers</Text>
-        </View>
-      </TouchableHighlight>
-    );
+      ) : (
+        <TouchableHighlight
+          style={styles.wrapper}
+          onPress={this.download.bind(this)}>
+          <View style={styles.button}>
+            <Text>Get headers</Text>
+          </View>
+        </TouchableHighlight>
+      );
 
     return (
       <View>
diff --git a/RNTester/js/XHRExampleOnTimeOut.js b/RNTester/js/XHRExampleOnTimeOut.js
index 1afb39904201..57a918b53c10 100644
--- a/RNTester/js/XHRExampleOnTimeOut.js
+++ b/RNTester/js/XHRExampleOnTimeOut.js
@@ -4,18 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 var React = require('react');
 var ReactNative = require('react-native');
-var {
-  StyleSheet,
-  Text,
-  TouchableHighlight,
-  View,
-} = ReactNative;
+var {StyleSheet, Text, TouchableHighlight, View} = ReactNative;
 
 class XHRExampleOnTimeOut extends React.Component<any, any> {
   xhr: XMLHttpRequest;
@@ -24,7 +21,7 @@ class XHRExampleOnTimeOut extends React.Component<any, any> {
     super(props);
     this.state = {
       status: '',
-      loading: false
+      loading: false,
     };
   }
 
@@ -33,7 +30,7 @@ class XHRExampleOnTimeOut extends React.Component<any, any> {
 
     var xhr = this.xhr || new XMLHttpRequest();
 
-    xhr.onerror = ()=> {
+    xhr.onerror = () => {
       console.log('Status ', xhr.status);
       console.log('Error ', xhr.responseText);
     };
@@ -41,7 +38,7 @@ class XHRExampleOnTimeOut extends React.Component<any, any> {
     xhr.ontimeout = () => {
       this.setState({
         status: xhr.responseText,
-        loading: false
+        loading: false,
       });
     };
 
@@ -74,7 +71,7 @@ class XHRExampleOnTimeOut extends React.Component<any, any> {
         style={styles.wrapper}
         onPress={this.loadTimeOutRequest.bind(this)}>
         <View style={styles.button}>
-         <Text>Make Time Out Request</Text>
+          <Text>Make Time Out Request</Text>
         </View>
       </TouchableHighlight>
     );
diff --git a/RNTester/js/createExamplePage.js b/RNTester/js/createExamplePage.js
index 1ae3733b969a..eba5a495287c 100644
--- a/RNTester/js/createExamplePage.js
+++ b/RNTester/js/createExamplePage.js
@@ -4,19 +4,22 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const React = require('react');
 
 const RNTesterExampleContainer = require('./RNTesterExampleContainer');
 
-import type { ExampleModule } from 'ExampleTypes';
-
-var createExamplePage = function(title: ?string, exampleModule: ExampleModule)
-  : React.ComponentType<any> {
+import type {ExampleModule} from 'ExampleTypes';
 
+var createExamplePage = function(
+  title: ?string,
+  exampleModule: ExampleModule,
+): React.ComponentType<any> {
   class ExamplePage extends React.Component<{}> {
     render() {
       return <RNTesterExampleContainer module={exampleModule} title={title} />;
diff --git a/ReactAndroid/src/androidTest/js/Asserts.js b/ReactAndroid/src/androidTest/js/Asserts.js
index 95fd89f272d1..467065d0e944 100644
--- a/ReactAndroid/src/androidTest/js/Asserts.js
+++ b/ReactAndroid/src/androidTest/js/Asserts.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -15,8 +16,14 @@ var Asserts = {
     if (expected !== actual) {
       Assert.fail(
         msg ||
-        'Expected: ' + expected + ', received: ' + actual + '\n' +
-        'at ' + (new Error()).stack);
+          'Expected: ' +
+            expected +
+            ', received: ' +
+            actual +
+            '\n' +
+            'at ' +
+            new Error().stack,
+      );
     } else {
       Assert.success();
     }
diff --git a/ReactAndroid/src/androidTest/js/CatalystRootViewTestModule.js b/ReactAndroid/src/androidTest/js/CatalystRootViewTestModule.js
index b0e5571b277a..497fc48e3530 100644
--- a/ReactAndroid/src/androidTest/js/CatalystRootViewTestModule.js
+++ b/ReactAndroid/src/androidTest/js/CatalystRootViewTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/DatePickerDialogTestModule.js b/ReactAndroid/src/androidTest/js/DatePickerDialogTestModule.js
index 4ba296cc757a..b15808cde634 100644
--- a/ReactAndroid/src/androidTest/js/DatePickerDialogTestModule.js
+++ b/ReactAndroid/src/androidTest/js/DatePickerDialogTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -16,7 +17,7 @@ var View = require('View');
 
 class DatePickerDialogTestApp extends React.Component {
   render() {
-    return (<View />);
+    return <View />;
   }
 }
 
@@ -31,14 +32,14 @@ var DatePickerDialogTestModule = {
           RecordingModule.recordDismissed();
         }
       },
-      ({code, message}) => RecordingModule.recordError()
+      ({code, message}) => RecordingModule.recordError(),
     );
   },
 };
 
 BatchedBridge.registerCallableModule(
   'DatePickerDialogTestModule',
-  DatePickerDialogTestModule
+  DatePickerDialogTestModule,
 );
 
 module.exports = DatePickerDialogTestModule;
diff --git a/ReactAndroid/src/androidTest/js/InitialPropsTestApp.js b/ReactAndroid/src/androidTest/js/InitialPropsTestApp.js
index 002ebf0cc68b..c031fde6046f 100644
--- a/ReactAndroid/src/androidTest/js/InitialPropsTestApp.js
+++ b/ReactAndroid/src/androidTest/js/InitialPropsTestApp.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
diff --git a/ReactAndroid/src/androidTest/js/JSResponderTestApp.js b/ReactAndroid/src/androidTest/js/JSResponderTestApp.js
index d6e7f878defb..ff5180186540 100644
--- a/ReactAndroid/src/androidTest/js/JSResponderTestApp.js
+++ b/ReactAndroid/src/androidTest/js/JSResponderTestApp.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 var React = require('React');
@@ -56,7 +58,7 @@ var styles = StyleSheet.create({
   },
   row: {
     height: 30,
-  }
+  },
 });
 
 module.exports = JSResponderTestApp;
diff --git a/ReactAndroid/src/androidTest/js/LayoutEventsTestApp.js b/ReactAndroid/src/androidTest/js/LayoutEventsTestApp.js
index 153089437e4c..df25944f1166 100644
--- a/ReactAndroid/src/androidTest/js/LayoutEventsTestApp.js
+++ b/ReactAndroid/src/androidTest/js/LayoutEventsTestApp.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -14,14 +15,13 @@ var View = require('View');
 var RecordingModule = require('NativeModules').Recording;
 
 const LAYOUT_SPECS = [
- [10, 10, 100, 100],
- [10, 10, 50, 50],
- [0, 0, 50, 50],
- [0, 0, 50, 50],
+  [10, 10, 100, 100],
+  [10, 10, 50, 50],
+  [0, 0, 50, 50],
+  [0, 0, 50, 50],
 ];
 
 class LayoutEventsTestApp extends React.Component {
-
   constructor() {
     super();
     this.state = {
@@ -30,9 +30,11 @@ class LayoutEventsTestApp extends React.Component {
     this.numParentLayouts = 0;
   }
 
-  handleOnLayout = (e) => {
+  handleOnLayout = e => {
     var layout = e.nativeEvent.layout;
-    RecordingModule.record(layout.x + ',' + layout.y + '-' + layout.width + 'x' + layout.height);
+    RecordingModule.record(
+      layout.x + ',' + layout.y + '-' + layout.width + 'x' + layout.height,
+    );
 
     if (this.state.specNumber >= LAYOUT_SPECS.length) {
       // This will cause the test to fail
@@ -44,7 +46,7 @@ class LayoutEventsTestApp extends React.Component {
     }
   };
 
-  handleParentOnLayout = (e) => {
+  handleParentOnLayout = e => {
     if (this.numParentLayouts > 0) {
       // This will cause the test to fail - the parent's layout doesn't change
       // so we should only get the event once.
@@ -57,13 +59,19 @@ class LayoutEventsTestApp extends React.Component {
     const layout = LAYOUT_SPECS[this.state.specNumber];
     return (
       <View
-          onLayout={this.handleParentOnLayout}
-          testID="parent"
-          style={{left: 0, top: 0, width: 500, height: 500}}>
+        onLayout={this.handleParentOnLayout}
+        testID="parent"
+        style={{left: 0, top: 0, width: 500, height: 500}}>
         <View
-            onLayout={this.handleOnLayout}
-            testID="container"
-            style={{left: layout[0], top: layout[1], width: layout[2], height: layout[3]}}/>
+          onLayout={this.handleOnLayout}
+          testID="container"
+          style={{
+            left: layout[0],
+            top: layout[1],
+            width: layout[2],
+            height: layout[3],
+          }}
+        />
       </View>
     );
   }
diff --git a/ReactAndroid/src/androidTest/js/MeasureLayoutTestModule.js b/ReactAndroid/src/androidTest/js/MeasureLayoutTestModule.js
index baf4f7bc03ba..03e156b6f4cf 100644
--- a/ReactAndroid/src/androidTest/js/MeasureLayoutTestModule.js
+++ b/ReactAndroid/src/androidTest/js/MeasureLayoutTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -19,29 +20,29 @@ var assertEquals = require('Asserts').assertEquals;
 
 var styles = StyleSheet.create({
   A: {
-    'width': 500,
-    'height': 500,
+    width: 500,
+    height: 500,
   },
   B: {
     backgroundColor: 'rgb(255, 0, 0)',
-    'left': 50,
-    'top': 80,
-    'width': 200,
-    'height': 300,
+    left: 50,
+    top: 80,
+    width: 200,
+    height: 300,
   },
   C: {
     backgroundColor: 'rgb(0, 255, 0)',
-    'left': 100,
-    'top': 70,
-    'width': 50,
-    'height': 150,
+    left: 100,
+    top: 70,
+    width: 50,
+    height: 150,
   },
   D: {
     backgroundColor: 'rgb(0, 0, 255)',
-    'left': 400,
-    'top': 100,
-    'width': 50,
-    'height': 200,
+    left: 400,
+    top: 100,
+    width: 50,
+    height: 200,
   },
 });
 
@@ -90,114 +91,124 @@ var MeasureLayoutTestModule = {
     });
   },
   verifyMeasureLayoutCRelativeToA: function() {
-    UIManager.measureLayout(
-      C,
-      A,
-      shouldNotCallThisCallback,
-      function (x, y, width, height) {
-        assertEquals(50, width);
-        assertEquals(150, height);
-        assertEquals(150, x);
-        assertEquals(150, y);
-      });
+    UIManager.measureLayout(C, A, shouldNotCallThisCallback, function(
+      x,
+      y,
+      width,
+      height,
+    ) {
+      assertEquals(50, width);
+      assertEquals(150, height);
+      assertEquals(150, x);
+      assertEquals(150, y);
+    });
   },
   verifyMeasureLayoutCRelativeToB: function() {
-    UIManager.measureLayout(
-      C,
-      B,
-      shouldNotCallThisCallback,
-      function (x, y, width, height) {
-        assertEquals(50, width);
-        assertEquals(150, height);
-        assertEquals(100, x);
-        assertEquals(70, y);
-      });
+    UIManager.measureLayout(C, B, shouldNotCallThisCallback, function(
+      x,
+      y,
+      width,
+      height,
+    ) {
+      assertEquals(50, width);
+      assertEquals(150, height);
+      assertEquals(100, x);
+      assertEquals(70, y);
+    });
   },
   verifyMeasureLayoutCRelativeToSelf: function() {
-    UIManager.measureLayout(
-      C,
-      C,
-      shouldNotCallThisCallback,
-      function (x, y, width, height) {
-        assertEquals(50, width);
-        assertEquals(150, height);
-        assertEquals(0, x);
-        assertEquals(0, y);
-      });
+    UIManager.measureLayout(C, C, shouldNotCallThisCallback, function(
+      x,
+      y,
+      width,
+      height,
+    ) {
+      assertEquals(50, width);
+      assertEquals(150, height);
+      assertEquals(0, x);
+      assertEquals(0, y);
+    });
   },
   verifyMeasureLayoutRelativeToParentOnViewA: function() {
     UIManager.measureLayoutRelativeToParent(
       A,
       shouldNotCallThisCallback,
-      function (x, y, width, height) {
+      function(x, y, width, height) {
         assertEquals(500, width);
         assertEquals(500, height);
         assertEquals(0, x);
         assertEquals(0, y);
-      });
+      },
+    );
   },
   verifyMeasureLayoutRelativeToParentOnViewB: function() {
     UIManager.measureLayoutRelativeToParent(
       B,
       shouldNotCallThisCallback,
-      function (x, y, width, height) {
+      function(x, y, width, height) {
         assertEquals(200, width);
         assertEquals(300, height);
         assertEquals(50, x);
         assertEquals(80, y);
-      });
+      },
+    );
   },
   verifyMeasureLayoutRelativeToParentOnViewC: function() {
     UIManager.measureLayoutRelativeToParent(
       C,
       shouldNotCallThisCallback,
-      function (x, y, width, height) {
+      function(x, y, width, height) {
         assertEquals(50, width);
         assertEquals(150, height);
         assertEquals(100, x);
         assertEquals(70, y);
-      });
+      },
+    );
   },
   verifyMeasureLayoutDRelativeToB: function() {
     UIManager.measureLayout(
       D,
       B,
-      function () {
+      function() {
         assertEquals(true, true);
       },
-      shouldNotCallThisCallback);
+      shouldNotCallThisCallback,
+    );
   },
   verifyMeasureLayoutNonExistentTag: function() {
     UIManager.measureLayout(
       192,
       A,
-      function () {
+      function() {
         assertEquals(true, true);
       },
-      shouldNotCallThisCallback);
+      shouldNotCallThisCallback,
+    );
   },
   verifyMeasureLayoutNonExistentAncestor: function() {
     UIManager.measureLayout(
       B,
       192,
-      function () {
+      function() {
         assertEquals(true, true);
       },
-      shouldNotCallThisCallback);
+      shouldNotCallThisCallback,
+    );
   },
   verifyMeasureLayoutRelativeToParentNonExistentTag: function() {
     UIManager.measureLayoutRelativeToParent(
       192,
-      function () {
+      function() {
         assertEquals(true, true);
       },
-      shouldNotCallThisCallback);
+      shouldNotCallThisCallback,
+    );
   },
 };
 
 BatchedBridge.registerCallableModule(
   'MeasureLayoutTestModule',
-  MeasureLayoutTestModule
+  MeasureLayoutTestModule,
 );
 
 module.exports = MeasureLayoutTestModule;
diff --git a/ReactAndroid/src/androidTest/js/MultitouchHandlingTestAppModule.js b/ReactAndroid/src/androidTest/js/MultitouchHandlingTestAppModule.js
index 0c591483f6c1..58f6a460501c 100644
--- a/ReactAndroid/src/androidTest/js/MultitouchHandlingTestAppModule.js
+++ b/ReactAndroid/src/androidTest/js/MultitouchHandlingTestAppModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -15,16 +16,16 @@ var TouchEventUtils = require('fbjs/lib/TouchEventUtils');
 var View = require('View');
 
 class TouchTestApp extends React.Component {
-  handleStartShouldSetResponder = (e) => {
+  handleStartShouldSetResponder = e => {
     return true;
   };
 
-  handleOnResponderMove = (e) => {
+  handleOnResponderMove = e => {
     e = TouchEventUtils.extractSingleTouch(e.nativeEvent);
     Recording.record('move;' + e.touches.length);
   };
 
-  handleResponderStart = (e) => {
+  handleResponderStart = e => {
     e = TouchEventUtils.extractSingleTouch(e.nativeEvent);
     if (e.touches) {
       Recording.record('start;' + e.touches.length);
@@ -33,7 +34,7 @@ class TouchTestApp extends React.Component {
     }
   };
 
-  handleResponderEnd = (e) => {
+  handleResponderEnd = e => {
     e = TouchEventUtils.extractSingleTouch(e.nativeEvent);
     if (e.touches) {
       Recording.record('end;' + e.touches.length);
diff --git a/ReactAndroid/src/androidTest/js/NativeIdTestModule.js b/ReactAndroid/src/androidTest/js/NativeIdTestModule.js
index be457b3c5699..eb791c356d12 100644
--- a/ReactAndroid/src/androidTest/js/NativeIdTestModule.js
+++ b/ReactAndroid/src/androidTest/js/NativeIdTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -28,18 +29,16 @@ const View = require('View');
  */
 class NativeIdTestApp extends React.Component<{}> {
   render() {
-    const uri = 'data:image/gif;base64,' +
-        'R0lGODdhMAAwAPAAAAAAAP///ywAAAAAMAAwAAAC8IyPqcvt3wCcDkiLc7C0qwyGHhSWpjQu5yqmCYsapy' +
-        'uvUUlvONmOZtfzgFzByTB10QgxOR0TqBQejhRNzOfkVJ+5YiUqrXF5Y5lKh/DeuNcP5yLWGsEbtLiOSpa/' +
-        'TPg7JpJHxyendzWTBfX0cxOnKPjgBzi4diinWGdkF8kjdfnycQZXZeYGejmJlZeGl9i2icVqaNVailT6F5' +
-        'iJ90m6mvuTS4OK05M0vDk0Q4XUtwvKOzrcd3iq9uisF81M1OIcR7lEewwcLp7tuNNkM3uNna3F2JQFo97V' +
-        'riy/Xl4/f1cf5VWzXyym7PHhhx4dbgYKAAA7';
+    const uri =
+      'data:image/gif;base64,' +
+      'R0lGODdhMAAwAPAAAAAAAP///ywAAAAAMAAwAAAC8IyPqcvt3wCcDkiLc7C0qwyGHhSWpjQu5yqmCYsapy' +
+      'uvUUlvONmOZtfzgFzByTB10QgxOR0TqBQejhRNzOfkVJ+5YiUqrXF5Y5lKh/DeuNcP5yLWGsEbtLiOSpa/' +
+      'TPg7JpJHxyendzWTBfX0cxOnKPjgBzi4diinWGdkF8kjdfnycQZXZeYGejmJlZeGl9i2icVqaNVailT6F5' +
+      'iJ90m6mvuTS4OK05M0vDk0Q4XUtwvKOzrcd3iq9uisF81M1OIcR7lEewwcLp7tuNNkM3uNna3F2JQFo97V' +
+      'riy/Xl4/f1cf5VWzXyym7PHhhx4dbgYKAAA7';
     return (
       <View>
-        <Image
-          nativeID="Image"
-          source={{uri: uri}}
-          style={styles.base} />
+        <Image nativeID="Image" source={{uri: uri}} style={styles.base} />
         <Text nativeID="Text">text</Text>
         <TextInput nativeID="TextInput" value="Text input" />
         <TouchableBounce nativeID="TouchableBounce">
diff --git a/ReactAndroid/src/androidTest/js/PickerAndroidTestModule.js b/ReactAndroid/src/androidTest/js/PickerAndroidTestModule.js
index 237dacba21bf..97210eccb083 100644
--- a/ReactAndroid/src/androidTest/js/PickerAndroidTestModule.js
+++ b/ReactAndroid/src/androidTest/js/PickerAndroidTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -62,7 +63,7 @@ class PickerAndroidTestApp extends React.Component {
     );
   }
 
-  onValueChange = (value) => {
+  onValueChange = value => {
     this.setState({selected: value});
     RecordingModule.recordSelection(value);
   };
@@ -83,7 +84,7 @@ var PickerAndroidTestModule = {
 
 BatchedBridge.registerCallableModule(
   'PickerAndroidTestModule',
-  PickerAndroidTestModule
+  PickerAndroidTestModule,
 );
 
 module.exports = PickerAndroidTestModule;
diff --git a/ReactAndroid/src/androidTest/js/ProgressBarTestModule.js b/ReactAndroid/src/androidTest/js/ProgressBarTestModule.js
index a6e3849e0d23..e9b4b563ba82 100644
--- a/ReactAndroid/src/androidTest/js/ProgressBarTestModule.js
+++ b/ReactAndroid/src/androidTest/js/ProgressBarTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -21,14 +22,14 @@ class ProgressBarSampleApp extends React.Component {
   render() {
     return (
       <View>
-        <ProgressBar styleAttr="Horizontal" testID="Horizontal"/>
-        <ProgressBar styleAttr="Small" testID="Small"/>
-        <ProgressBar styleAttr="Large" testID="Large"/>
-        <ProgressBar styleAttr="Normal" testID="Normal"/>
-        <ProgressBar styleAttr="Inverse" testID="Inverse"/>
-        <ProgressBar styleAttr="SmallInverse" testID="SmallInverse"/>
-        <ProgressBar styleAttr="LargeInverse" testID="LargeInverse"/>
-        <View style={{width:200}}>
+        <ProgressBar styleAttr="Horizontal" testID="Horizontal" />
+        <ProgressBar styleAttr="Small" testID="Small" />
+        <ProgressBar styleAttr="Large" testID="Large" />
+        <ProgressBar styleAttr="Normal" testID="Normal" />
+        <ProgressBar styleAttr="Inverse" testID="Inverse" />
+        <ProgressBar styleAttr="SmallInverse" testID="SmallInverse" />
+        <ProgressBar styleAttr="LargeInverse" testID="LargeInverse" />
+        <View style={{width: 200}}>
           <ProgressBar styleAttr="Horizontal" testID="Horizontal200" />
         </View>
       </View>
@@ -44,7 +45,7 @@ var ProgressBarTestModule = {
 
 BatchedBridge.registerCallableModule(
   'ProgressBarTestModule',
-  ProgressBarTestModule
+  ProgressBarTestModule,
 );
 
 module.exports = ProgressBarTestModule;
diff --git a/ReactAndroid/src/androidTest/js/ScrollViewTestModule.js b/ReactAndroid/src/androidTest/js/ScrollViewTestModule.js
index 7654f106087a..f6f83beee310 100644
--- a/ReactAndroid/src/androidTest/js/ScrollViewTestModule.js
+++ b/ReactAndroid/src/androidTest/js/ScrollViewTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -47,15 +48,24 @@ var getInitialState = function() {
 };
 
 var onScroll = function(e) {
-  ScrollListener.onScroll(e.nativeEvent.contentOffset.x, e.nativeEvent.contentOffset.y);
+  ScrollListener.onScroll(
+    e.nativeEvent.contentOffset.x,
+    e.nativeEvent.contentOffset.y,
+  );
 };
 
 var onScrollBeginDrag = function(e) {
-  ScrollListener.onScrollBeginDrag(e.nativeEvent.contentOffset.x, e.nativeEvent.contentOffset.y);
+  ScrollListener.onScrollBeginDrag(
+    e.nativeEvent.contentOffset.x,
+    e.nativeEvent.contentOffset.y,
+  );
 };
 
 var onScrollEndDrag = function(e) {
-  ScrollListener.onScrollEndDrag(e.nativeEvent.contentOffset.x, e.nativeEvent.contentOffset.y);
+  ScrollListener.onScrollEndDrag(
+    e.nativeEvent.contentOffset.x,
+    e.nativeEvent.contentOffset.y,
+  );
 };
 
 var onItemPress = function(itemNumber) {
@@ -78,11 +88,17 @@ var ScrollViewTestApp = createReactClass({
     scrollViewApp = this;
     var children = this.state.data.map((item, index) => (
       <Item
-        key={index} text={item.text}
-        onPress={this.onItemPress.bind(this, index)} />
+        key={index}
+        text={item.text}
+        onPress={this.onItemPress.bind(this, index)}
+      />
     ));
     return (
-      <ScrollView onScroll={this.onScroll} onScrollBeginDrag={this.onScrollBeginDrag} onScrollEndDrag={this.onScrollEndDrag} ref="scrollView">
+      <ScrollView
+        onScroll={this.onScroll}
+        onScrollBeginDrag={this.onScrollBeginDrag}
+        onScrollEndDrag={this.onScrollEndDrag}
+        ref="scrollView">
         {children}
       </ScrollView>
     );
@@ -103,8 +119,10 @@ var HorizontalScrollViewTestApp = createReactClass({
     scrollViewApp = this;
     var children = this.state.data.map((item, index) => (
       <Item
-        key={index} text={item.text}
-        onPress={this.onItemPress.bind(this, index)} />
+        key={index}
+        text={item.text}
+        onPress={this.onItemPress.bind(this, index)}
+      />
     ));
     return (
       <ScrollView horizontal={true} onScroll={this.onScroll} ref="scrollView">
@@ -136,7 +154,7 @@ var ScrollViewTestModule = {
 
 BatchedBridge.registerCallableModule(
   'ScrollViewTestModule',
-  ScrollViewTestModule
+  ScrollViewTestModule,
 );
 
 module.exports = ScrollViewTestModule;
diff --git a/ReactAndroid/src/androidTest/js/ShareTestModule.js b/ReactAndroid/src/androidTest/js/ShareTestModule.js
index dd0f7fc9646d..3c230a3d0147 100644
--- a/ReactAndroid/src/androidTest/js/ShareTestModule.js
+++ b/ReactAndroid/src/androidTest/js/ShareTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -16,7 +17,7 @@ var View = require('View');
 
 class ShareTestApp extends React.Component {
   render() {
-    return (<View />);
+    return <View />;
   }
 }
 
@@ -25,14 +26,11 @@ var ShareTestModule = {
   showShareDialog: function(content, options) {
     Share.share(content, options).then(
       () => RecordingModule.recordOpened(),
-      ({code, message}) => RecordingModule.recordError()
+      ({code, message}) => RecordingModule.recordError(),
     );
   },
 };
 
-BatchedBridge.registerCallableModule(
-  'ShareTestModule',
-  ShareTestModule
-);
+BatchedBridge.registerCallableModule('ShareTestModule', ShareTestModule);
 
 module.exports = ShareTestModule;
diff --git a/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js b/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
index 859acfc92c6a..9f19e0e39034 100644
--- a/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
+++ b/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -24,12 +25,30 @@ class ClippingSample1 extends React.Component {
     var styles = sample1Styles;
     return (
       <View>
-        <ClippableView clippableViewID="outer" style={styles.outer} removeClippedSubviews={true}>
-          <ClippableView clippableViewID="inner1" style={[styles.inner, styles.inner1]}/>
-          <ClippableView clippableViewID="inner2" style={[styles.inner, styles.inner2]}/>
-          <ClippableView clippableViewID="inner3" style={[styles.inner, styles.inner3]}/>
-          <ClippableView clippableViewID="inner4" style={[styles.inner, styles.inner4]}/>
-          <ClippableView clippableViewID="inner5" style={[styles.inner, styles.inner5]}/>
+        <ClippableView
+          clippableViewID="outer"
+          style={styles.outer}
+          removeClippedSubviews={true}>
+          <ClippableView
+            clippableViewID="inner1"
+            style={[styles.inner, styles.inner1]}
+          />
+          <ClippableView
+            clippableViewID="inner2"
+            style={[styles.inner, styles.inner2]}
+          />
+          <ClippableView
+            clippableViewID="inner3"
+            style={[styles.inner, styles.inner3]}
+          />
+          <ClippableView
+            clippableViewID="inner4"
+            style={[styles.inner, styles.inner4]}
+          />
+          <ClippableView
+            clippableViewID="inner5"
+            style={[styles.inner, styles.inner5]}
+          />
         </ClippableView>
       </View>
     );
@@ -75,15 +94,30 @@ class ClippingSample2 extends React.Component {
     var styles = sample2Styles;
     return (
       <View>
-        <ClippableView clippableViewID="outer" style={styles.outer} removeClippedSubviews={true}>
+        <ClippableView
+          clippableViewID="outer"
+          style={styles.outer}
+          removeClippedSubviews={true}>
           <ClippableView
-              clippableViewID="complexInner"
-              style={styles.complexInner}
-              removeClippedSubviews={true}>
-            <ClippableView clippableViewID="inner1" style={[styles.inner, styles.inner1]}/>
-            <ClippableView clippableViewID="inner2" style={[styles.inner, styles.inner2]}/>
-            <ClippableView clippableViewID="inner3" style={[styles.inner, styles.inner3]}/>
-            <ClippableView clippableViewID="inner4" style={[styles.inner, styles.inner4]}/>
+            clippableViewID="complexInner"
+            style={styles.complexInner}
+            removeClippedSubviews={true}>
+            <ClippableView
+              clippableViewID="inner1"
+              style={[styles.inner, styles.inner1]}
+            />
+            <ClippableView
+              clippableViewID="inner2"
+              style={[styles.inner, styles.inner2]}
+            />
+            <ClippableView
+              clippableViewID="inner3"
+              style={[styles.inner, styles.inner3]}
+            />
+            <ClippableView
+              clippableViewID="inner4"
+              style={[styles.inner, styles.inner4]}
+            />
           </ClippableView>
         </ClippableView>
       </View>
@@ -132,13 +166,19 @@ var sample2Styles = StyleSheet.create({
 class UpdatingSample1 extends React.Component {
   render() {
     var styles = updating1Styles;
-    var inner1Styles = [styles.inner1, {height: this.props.update1 ? 200 : 100}];
+    var inner1Styles = [
+      styles.inner1,
+      {height: this.props.update1 ? 200 : 100},
+    ];
     var inner2Styles = [styles.inner2, {top: this.props.update2 ? 200 : 50}];
     return (
       <View>
-        <ClippableView clippableViewID="outer" style={styles.outer} removeClippedSubviews={true}>
-          <ClippableView clippableViewID="inner1" style={inner1Styles}/>
-          <ClippableView clippableViewID="inner2" style={inner2Styles}/>
+        <ClippableView
+          clippableViewID="outer"
+          style={styles.outer}
+          removeClippedSubviews={true}>
+          <ClippableView clippableViewID="inner1" style={inner1Styles} />
+          <ClippableView clippableViewID="inner2" style={inner2Styles} />
         </ClippableView>
       </View>
     );
@@ -166,7 +206,7 @@ var updating1Styles = StyleSheet.create({
     left: 50,
     top: 50,
     backgroundColor: 'green',
-  }
+  },
 });
 
 class UpdatingSample2 extends React.Component {
@@ -175,8 +215,11 @@ class UpdatingSample2 extends React.Component {
     var outerStyles = [styles.outer, {height: this.props.update ? 200 : 100}];
     return (
       <View>
-        <ClippableView clippableViewID="outer" style={outerStyles} removeClippedSubviews={true}>
-          <ClippableView clippableViewID="inner" style={styles.inner}/>
+        <ClippableView
+          clippableViewID="outer"
+          style={outerStyles}
+          removeClippedSubviews={true}>
+          <ClippableView clippableViewID="inner" style={styles.inner} />
         </ClippableView>
       </View>
     );
@@ -204,25 +247,28 @@ class ScrollViewTest extends React.Component {
     var children = [];
     for (var i = 0; i < 4; i++) {
       children[i] = (
-        <ClippableView key={i} style={styles.row} clippableViewID={'' + i}/>
+        <ClippableView key={i} style={styles.row} clippableViewID={'' + i} />
       );
     }
     for (var i = 4; i < 6; i++) {
       var viewID = 'C' + (i - 4);
       children[i] = (
         <ClippableView
-            key={i}
-            style={styles.complex}
-            clippableViewID={viewID}
-            removeClippedSubviews={true}>
-          <ClippableView style={styles.inner} clippableViewID={viewID + '.1'}/>
-          <ClippableView style={styles.inner} clippableViewID={viewID + '.2'}/>
+          key={i}
+          style={styles.complex}
+          clippableViewID={viewID}
+          removeClippedSubviews={true}>
+          <ClippableView style={styles.inner} clippableViewID={viewID + '.1'} />
+          <ClippableView style={styles.inner} clippableViewID={viewID + '.2'} />
         </ClippableView>
       );
     }
 
     return (
-      <ScrollView removeClippedSubviews={true} style={styles.scrollView} testID="scroll_view">
+      <ScrollView
+        removeClippedSubviews={true}
+        style={styles.scrollView}
+        testID="scroll_view">
         {children}
       </ScrollView>
     );
@@ -258,7 +304,6 @@ var scrollTestStyles = StyleSheet.create({
   },
 });
 
-
 var appInstance = null;
 
 class SubviewsClippingTestApp extends React.Component {
@@ -268,42 +313,40 @@ class SubviewsClippingTestApp extends React.Component {
     appInstance = this;
   }
 
-  setComponent = (component) => {
+  setComponent = component => {
     this.setState({component: component});
   };
 
   render() {
     var component = this.state.component;
-    return (
-      <View>
-        {component}
-      </View>
-    );
+    return <View>{component}</View>;
   }
 }
 
 var SubviewsClippingTestModule = {
   App: SubviewsClippingTestApp,
   renderClippingSample1: function() {
-    appInstance.setComponent(<ClippingSample1/>);
+    appInstance.setComponent(<ClippingSample1 />);
   },
   renderClippingSample2: function() {
-    appInstance.setComponent(<ClippingSample2/>);
+    appInstance.setComponent(<ClippingSample2 />);
   },
   renderUpdatingSample1: function(update1, update2) {
-    appInstance.setComponent(<UpdatingSample1 update1={update1} update2={update2}/>);
+    appInstance.setComponent(
+      <UpdatingSample1 update1={update1} update2={update2} />,
+    );
   },
   renderUpdatingSample2: function(update) {
-    appInstance.setComponent(<UpdatingSample2 update={update}/>);
+    appInstance.setComponent(<UpdatingSample2 update={update} />);
   },
   renderScrollViewTest: function() {
-    appInstance.setComponent(<ScrollViewTest/>);
+    appInstance.setComponent(<ScrollViewTest />);
   },
 };
 
 BatchedBridge.registerCallableModule(
   'SubviewsClippingTestModule',
-  SubviewsClippingTestModule
+  SubviewsClippingTestModule,
 );
 
 module.exports = SubviewsClippingTestModule;
diff --git a/ReactAndroid/src/androidTest/js/SwipeRefreshLayoutTestModule.js b/ReactAndroid/src/androidTest/js/SwipeRefreshLayoutTestModule.js
index 5a126772ef56..0bd3fabf2008 100644
--- a/ReactAndroid/src/androidTest/js/SwipeRefreshLayoutTestModule.js
+++ b/ReactAndroid/src/androidTest/js/SwipeRefreshLayoutTestModule.js
@@ -4,13 +4,15 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
 
 var BatchedBridge = require('BatchedBridge');
 var React = require('React');
-var RecordingModule = require('NativeModules').SwipeRefreshLayoutRecordingModule;
+var RecordingModule = require('NativeModules')
+  .SwipeRefreshLayoutRecordingModule;
 var ScrollView = require('ScrollView');
 var RefreshControl = require('RefreshControl');
 var Text = require('Text');
@@ -26,9 +28,7 @@ class Row extends React.Component {
     return (
       <TouchableWithoutFeedback onPress={this._onPress}>
         <View>
-          <Text>
-            {this.state.clicks + ' clicks'}
-          </Text>
+          <Text>{this.state.clicks + ' clicks'}</Text>
         </View>
       </TouchableWithoutFeedback>
     );
@@ -77,12 +77,12 @@ var SwipeRefreshLayoutTestModule = {
     if (app != null) {
       app.setState({rows});
     }
-  }
+  },
 };
 
 BatchedBridge.registerCallableModule(
   'SwipeRefreshLayoutTestModule',
-  SwipeRefreshLayoutTestModule
+  SwipeRefreshLayoutTestModule,
 );
 
 module.exports = SwipeRefreshLayoutTestModule;
diff --git a/ReactAndroid/src/androidTest/js/TestBundle.js b/ReactAndroid/src/androidTest/js/TestBundle.js
index 64d2c57d26f3..59da7e6695b8 100644
--- a/ReactAndroid/src/androidTest/js/TestBundle.js
+++ b/ReactAndroid/src/androidTest/js/TestBundle.js
@@ -4,7 +4,9 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
+
 'use strict';
 
 // Disable YellowBox so we do not have to mock its dependencies
@@ -29,86 +31,88 @@ require('SwipeRefreshLayoutTestModule');
 require('TextInputTestModule');
 require('TimePickerDialogTestModule');
 
-
 // Define catalyst test apps used in integration tests
 var AppRegistry = require('AppRegistry');
 
 var apps = [
-{
-  appKey: 'CatalystRootViewTestApp',
-  component: () => require('CatalystRootViewTestModule').CatalystRootViewTestApp
-},
-{
-  appKey: 'DatePickerDialogTestApp',
-  component: () => require('DatePickerDialogTestModule').DatePickerDialogTestApp
-},
-{
-  appKey: 'JSResponderTestApp',
-  component: () => require('JSResponderTestApp'),
-},
-{
-  appKey: 'HorizontalScrollViewTestApp',
-  component: () => require('ScrollViewTestModule').HorizontalScrollViewTestApp,
-},
-{
-  appKey: 'InitialPropsTestApp',
-  component: () => require('InitialPropsTestApp'),
-},
-{
-  appKey: 'LayoutEventsTestApp',
-  component: () => require('LayoutEventsTestApp'),
-},
-{
-  appKey: 'MeasureLayoutTestApp',
-  component: () => require('MeasureLayoutTestModule').MeasureLayoutTestApp
-},
-{
-  appKey: 'MultitouchHandlingTestAppModule',
-  component: () => require('MultitouchHandlingTestAppModule')
-},
-{
-  appKey: 'NativeIdTestApp',
-  component: () => require('NativeIdTestModule').NativeIdTestApp
-},
-{
-  appKey: 'PickerAndroidTestApp',
-  component: () => require('PickerAndroidTestModule').PickerAndroidTestApp,
-},
-{
-  appKey: 'ScrollViewTestApp',
-  component: () => require('ScrollViewTestModule').ScrollViewTestApp,
-},
-{
-  appKey: 'ShareTestApp',
-  component: () => require('ShareTestModule').ShareTestApp,
-},
-{
-  appKey: 'SubviewsClippingTestApp',
-  component: () => require('SubviewsClippingTestModule').App,
-},
-{
-  appKey: 'SwipeRefreshLayoutTestApp',
-  component: () => require('SwipeRefreshLayoutTestModule').SwipeRefreshLayoutTestApp
-},
-{
-  appKey: 'TextInputTestApp',
-  component: () => require('TextInputTestModule').TextInputTestApp
-},
-{
-  appKey: 'TestIdTestApp',
-  component: () => require('TestIdTestModule').TestIdTestApp
-},
-{
-  appKey: 'TimePickerDialogTestApp',
-  component: () => require('TimePickerDialogTestModule').TimePickerDialogTestApp
-},
-{
-  appKey: 'TouchBubblingTestAppModule',
-  component: () => require('TouchBubblingTestAppModule')
-},
-
+  {
+    appKey: 'CatalystRootViewTestApp',
+    component: () =>
+      require('CatalystRootViewTestModule').CatalystRootViewTestApp,
+  },
+  {
+    appKey: 'DatePickerDialogTestApp',
+    component: () =>
+      require('DatePickerDialogTestModule').DatePickerDialogTestApp,
+  },
+  {
+    appKey: 'JSResponderTestApp',
+    component: () => require('JSResponderTestApp'),
+  },
+  {
+    appKey: 'HorizontalScrollViewTestApp',
+    component: () =>
+      require('ScrollViewTestModule').HorizontalScrollViewTestApp,
+  },
+  {
+    appKey: 'InitialPropsTestApp',
+    component: () => require('InitialPropsTestApp'),
+  },
+  {
+    appKey: 'LayoutEventsTestApp',
+    component: () => require('LayoutEventsTestApp'),
+  },
+  {
+    appKey: 'MeasureLayoutTestApp',
+    component: () => require('MeasureLayoutTestModule').MeasureLayoutTestApp,
+  },
+  {
+    appKey: 'MultitouchHandlingTestAppModule',
+    component: () => require('MultitouchHandlingTestAppModule'),
+  },
+  {
+    appKey: 'NativeIdTestApp',
+    component: () => require('NativeIdTestModule').NativeIdTestApp,
+  },
+  {
+    appKey: 'PickerAndroidTestApp',
+    component: () => require('PickerAndroidTestModule').PickerAndroidTestApp,
+  },
+  {
+    appKey: 'ScrollViewTestApp',
+    component: () => require('ScrollViewTestModule').ScrollViewTestApp,
+  },
+  {
+    appKey: 'ShareTestApp',
+    component: () => require('ShareTestModule').ShareTestApp,
+  },
+  {
+    appKey: 'SubviewsClippingTestApp',
+    component: () => require('SubviewsClippingTestModule').App,
+  },
+  {
+    appKey: 'SwipeRefreshLayoutTestApp',
+    component: () =>
+      require('SwipeRefreshLayoutTestModule').SwipeRefreshLayoutTestApp,
+  },
+  {
+    appKey: 'TextInputTestApp',
+    component: () => require('TextInputTestModule').TextInputTestApp,
+  },
+  {
+    appKey: 'TestIdTestApp',
+    component: () => require('TestIdTestModule').TestIdTestApp,
+  },
+  {
+    appKey: 'TimePickerDialogTestApp',
+    component: () =>
+      require('TimePickerDialogTestModule').TimePickerDialogTestApp,
+  },
+  {
+    appKey: 'TouchBubblingTestAppModule',
+    component: () => require('TouchBubblingTestAppModule'),
+  },
 ];
 
-
 module.exports = apps;
 AppRegistry.registerConfig(apps);
diff --git a/ReactAndroid/src/androidTest/js/TestIdTestModule.js b/ReactAndroid/src/androidTest/js/TestIdTestModule.js
index 0320f3cf8be7..5b045d38fbaa 100644
--- a/ReactAndroid/src/androidTest/js/TestIdTestModule.js
+++ b/ReactAndroid/src/androidTest/js/TestIdTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -30,16 +31,19 @@ class TestIdTestApp extends React.Component {
   render() {
     return (
       <View>
-
         <Image
           testID="Image"
-          source={{uri: 'data:image/gif;base64,' +
+          source={{
+            uri:
+              'data:image/gif;base64,' +
               'R0lGODdhMAAwAPAAAAAAAP///ywAAAAAMAAwAAAC8IyPqcvt3wCcDkiLc7C0qwyGHhSWpjQu5yqmCYsapy' +
               'uvUUlvONmOZtfzgFzByTB10QgxOR0TqBQejhRNzOfkVJ+5YiUqrXF5Y5lKh/DeuNcP5yLWGsEbtLiOSpa/' +
               'TPg7JpJHxyendzWTBfX0cxOnKPjgBzi4diinWGdkF8kjdfnycQZXZeYGejmJlZeGl9i2icVqaNVailT6F5' +
               'iJ90m6mvuTS4OK05M0vDk0Q4XUtwvKOzrcd3iq9uisF81M1OIcR7lEewwcLp7tuNNkM3uNna3F2JQFo97V' +
-              'riy/Xl4/f1cf5VWzXyym7PHhhx4dbgYKAAA7'}}
-          style={styles.base} />
+              'riy/Xl4/f1cf5VWzXyym7PHhhx4dbgYKAAA7',
+          }}
+          style={styles.base}
+        />
 
         <Text testID="Text">text</Text>
 
@@ -64,7 +68,6 @@ class TestIdTestApp extends React.Component {
         </TouchableWithoutFeedback>
 
         <View testID="View" />
-
       </View>
     );
   }
diff --git a/ReactAndroid/src/androidTest/js/TestJSLocaleModule.js b/ReactAndroid/src/androidTest/js/TestJSLocaleModule.js
index a9aca7983d23..9a5915396d1f 100644
--- a/ReactAndroid/src/androidTest/js/TestJSLocaleModule.js
+++ b/ReactAndroid/src/androidTest/js/TestJSLocaleModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -20,9 +21,6 @@ var TestJSLocaleModule = {
   },
 };
 
-BatchedBridge.registerCallableModule(
-  'TestJSLocaleModule',
-  TestJSLocaleModule
-);
+BatchedBridge.registerCallableModule('TestJSLocaleModule', TestJSLocaleModule);
 
 module.exports = TestJSLocaleModule;
diff --git a/ReactAndroid/src/androidTest/js/TestJSToJavaParametersModule.js b/ReactAndroid/src/androidTest/js/TestJSToJavaParametersModule.js
index 5e5527846ae0..ec31e15cb55f 100644
--- a/ReactAndroid/src/androidTest/js/TestJSToJavaParametersModule.js
+++ b/ReactAndroid/src/androidTest/js/TestJSToJavaParametersModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -49,9 +50,9 @@ var TestJSToJavaParametersModule = {
   },
   returnMapWithArrays: function() {
     Recording.receiveMap({
-      'empty': [],
-      'ints': [43, 44],
-      'mixed': [77, 'string', ['another', 'array']],
+      empty: [],
+      ints: [43, 44],
+      mixed: [77, 'string', ['another', 'array']],
     });
   },
   returnArrayWithStringDoubleIntMapArrayBooleanNull: function() {
@@ -65,7 +66,7 @@ var TestJSToJavaParametersModule = {
       int: -55,
       array: [],
       boolean: true,
-      null: null
+      null: null,
     });
   },
   returnArrayWithLargeInts: function() {
@@ -80,7 +81,7 @@ var TestJSToJavaParametersModule = {
       b: 41,
       c: 'string',
       d: 'other string',
-      e: [1,'foo','bar'],
+      e: [1, 'foo', 'bar'],
       f: null,
     });
   },
@@ -99,7 +100,8 @@ var TestJSToJavaParametersModule = {
       'two-bytes': '\u00A2',
       'three-bytes': '\u20AC',
       'four-bytes': '\uD83D\uDE1C',
-      'mixed': '\u017C\u00F3\u0142\u0107 g\u0119\u015Bl\u0105 \u6211 \uD83D\uDE0E ja\u017A\u0107'
+      mixed:
+        '\u017C\u00F3\u0142\u0107 g\u0119\u015Bl\u0105 \u6211 \uD83D\uDE0E ja\u017A\u0107',
     });
   },
   returnArrayWithMultibyteUTF8CharacterString: function() {
@@ -108,14 +110,14 @@ var TestJSToJavaParametersModule = {
       '\u00A2',
       '\u20AC',
       '\uD83D\uDE1C',
-      '\u017C\u00F3\u0142\u0107 g\u0119\u015Bl\u0105 \u6211 \uD83D\uDE0E ja\u017A\u0107'
+      '\u017C\u00F3\u0142\u0107 g\u0119\u015Bl\u0105 \u6211 \uD83D\uDE0E ja\u017A\u0107',
     ]);
   },
 };
 
 BatchedBridge.registerCallableModule(
   'TestJSToJavaParametersModule',
-  TestJSToJavaParametersModule
+  TestJSToJavaParametersModule,
 );
 
 module.exports = TestJSToJavaParametersModule;
diff --git a/ReactAndroid/src/androidTest/js/TestJavaToJSArgumentsModule.js b/ReactAndroid/src/androidTest/js/TestJavaToJSArgumentsModule.js
index 6e71061666bf..d112ff213d02 100644
--- a/ReactAndroid/src/androidTest/js/TestJavaToJSArgumentsModule.js
+++ b/ReactAndroid/src/androidTest/js/TestJavaToJSArgumentsModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -24,9 +25,7 @@ function strictStringCompare(a, b) {
 }
 
 function assertStrictStringEquals(a, b) {
-  assertTrue(
-    strictStringCompare(a,b),
-    'Expected: ' + a + ', received: ' + b);
+  assertTrue(strictStringCompare(a, b), 'Expected: ' + a + ', received: ' + b);
 }
 
 var TestJavaToJSArgumentsModule = {
@@ -92,7 +91,8 @@ var TestJavaToJSArgumentsModule = {
     assertStrictStringEquals('\uD83D\uDE1C', map['four-bytes']);
     assertStrictStringEquals(
       '\u017C\u00F3\u0142\u0107 g\u0119\u015Bl\u0105 \u6211 \uD83D\uDE0E ja\u017A\u0107',
-      map.mixed);
+      map.mixed,
+    );
   },
   receiveArrayWithMultibyteUTF8CharacterString: function(array) {
     assertTrue(true);
@@ -101,13 +101,14 @@ var TestJavaToJSArgumentsModule = {
     assertStrictStringEquals('\uD83D\uDE1C', array[2]);
     assertStrictStringEquals(
       '\u017C\u00F3\u0142\u0107 g\u0119\u015Bl\u0105 \u6211 \uD83D\uDE0E ja\u017A\u0107',
-      array[3]);
+      array[3],
+    );
   },
 };
 
 BatchedBridge.registerCallableModule(
   'TestJavaToJSArgumentsModule',
-  TestJavaToJSArgumentsModule
+  TestJavaToJSArgumentsModule,
 );
 
 module.exports = TestJavaToJSArgumentsModule;
diff --git a/ReactAndroid/src/androidTest/js/TestJavaToJSReturnValuesModule.js b/ReactAndroid/src/androidTest/js/TestJavaToJSReturnValuesModule.js
index 1aa72f0b8572..e21f8600cbf4 100644
--- a/ReactAndroid/src/androidTest/js/TestJavaToJSReturnValuesModule.js
+++ b/ReactAndroid/src/androidTest/js/TestJavaToJSReturnValuesModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -26,12 +27,12 @@ var TestJavaToJSReturnValuesModule = {
     } catch (ex) {
       assertTrue(ex.message.indexOf('Exception triggered') !== -1);
     }
-  }
+  },
 };
 
 BatchedBridge.registerCallableModule(
   'TestJavaToJSReturnValuesModule',
-  TestJavaToJSReturnValuesModule
+  TestJavaToJSReturnValuesModule,
 );
 
 module.exports = TestJavaToJSReturnValuesModule;
diff --git a/ReactAndroid/src/androidTest/js/TextInputTestModule.js b/ReactAndroid/src/androidTest/js/TextInputTestModule.js
index fff1fc5bca68..48d29344de31 100644
--- a/ReactAndroid/src/androidTest/js/TextInputTestModule.js
+++ b/ReactAndroid/src/androidTest/js/TextInputTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -25,13 +26,14 @@ class TokenizedTextExample extends React.Component {
     this.state = {text: ''};
   }
   render() {
-
     //define delimiter
     let delimiter = /\s+/;
 
     //split string
     let _text = this.state.text;
-    let token, index, parts = [];
+    let token,
+      index,
+      parts = [];
     while (_text) {
       delimiter.lastIndex = 0;
       token = delimiter.exec(_text);
@@ -50,9 +52,13 @@ class TokenizedTextExample extends React.Component {
     parts.push(_text);
 
     //highlight hashtags
-    parts = parts.map((text) => {
+    parts = parts.map(text => {
       if (/^#/.test(text)) {
-        return <Text key={text} style={styles.hashtag}>{text}</Text>;
+        return (
+          <Text key={text} style={styles.hashtag}>
+            {text}
+          </Text>
+        );
       } else {
         return text;
       }
@@ -65,7 +71,7 @@ class TokenizedTextExample extends React.Component {
           testID="tokenizedInput"
           multiline={true}
           style={styles.multiline}
-          onChangeText={(text) => {
+          onChangeText={text => {
             this.setState({text});
           }}>
           <Text>{parts}</Text>
@@ -80,7 +86,7 @@ class TextInputTestApp extends React.Component {
     app = this;
   }
 
-  handleOnSubmitEditing = (record) => {
+  handleOnSubmitEditing = record => {
     Recording.record(record);
   };
 
@@ -173,7 +179,7 @@ var TextInputTestModule = {
 
 BatchedBridge.registerCallableModule(
   'TextInputTestModule',
-  TextInputTestModule
+  TextInputTestModule,
 );
 
 module.exports = TextInputTestModule;
diff --git a/ReactAndroid/src/androidTest/js/TimePickerDialogTestModule.js b/ReactAndroid/src/androidTest/js/TimePickerDialogTestModule.js
index 80e355c951ec..5db19b67e45b 100644
--- a/ReactAndroid/src/androidTest/js/TimePickerDialogTestModule.js
+++ b/ReactAndroid/src/androidTest/js/TimePickerDialogTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -31,14 +32,14 @@ var TimePickerDialogTestModule = {
           RecordingModule.recordDismissed();
         }
       },
-      ({code, message}) => RecordingModule.recordError()
+      ({code, message}) => RecordingModule.recordError(),
     );
   },
 };
 
 BatchedBridge.registerCallableModule(
   'TimePickerDialogTestModule',
-  TimePickerDialogTestModule
+  TimePickerDialogTestModule,
 );
 
 module.exports = TimePickerDialogTestModule;
diff --git a/ReactAndroid/src/androidTest/js/TouchBubblingTestAppModule.js b/ReactAndroid/src/androidTest/js/TouchBubblingTestAppModule.js
index 6f8e6226ad58..4ae71bf70f2c 100644
--- a/ReactAndroid/src/androidTest/js/TouchBubblingTestAppModule.js
+++ b/ReactAndroid/src/androidTest/js/TouchBubblingTestAppModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -16,16 +17,20 @@ var View = require('View');
 var TouchableWithoutFeedback = require('TouchableWithoutFeedback');
 
 class TouchBubblingTestApp extends React.Component {
-  handlePress = (record) => {
+  handlePress = record => {
     Recording.record(record);
   };
 
   render() {
     return (
       <View style={styles.container}>
-        <TouchableWithoutFeedback onPress={this.handlePress.bind(this, 'outer')} testID="D">
+        <TouchableWithoutFeedback
+          onPress={this.handlePress.bind(this, 'outer')}
+          testID="D">
           <View style={styles.outer}>
-            <TouchableWithoutFeedback onPress={this.handlePress.bind(this, 'inner')} testID="B">
+            <TouchableWithoutFeedback
+              onPress={this.handlePress.bind(this, 'inner')}
+              testID="B">
               <View style={styles.inner}>
                 <View style={styles.superinner} testID="A" />
               </View>
@@ -33,7 +38,9 @@ class TouchBubblingTestApp extends React.Component {
             <View style={styles.inner} testID="C" />
           </View>
         </TouchableWithoutFeedback>
-        <TouchableWithoutFeedback onPress={this.handlePress.bind(this, 'outsider')} testID="E">
+        <TouchableWithoutFeedback
+          onPress={this.handlePress.bind(this, 'outsider')}
+          testID="E">
           <View style={styles.element} />
         </TouchableWithoutFeedback>
       </View>
@@ -68,7 +75,7 @@ var styles = StyleSheet.create({
     backgroundColor: '#eeeeee',
     height: 20,
     width: 20,
-  }
+  },
 });
 
 module.exports = TouchBubblingTestApp;
diff --git a/ReactAndroid/src/androidTest/js/UIManagerTestModule.js b/ReactAndroid/src/androidTest/js/UIManagerTestModule.js
index 93f73d44c0d6..33d1d3aca1b0 100644
--- a/ReactAndroid/src/androidTest/js/UIManagerTestModule.js
+++ b/ReactAndroid/src/androidTest/js/UIManagerTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -34,16 +35,25 @@ var FlexTestApp = createReactClass({
       left: 10,
       width: 50,
       height: 60,
-    }
+    },
   }),
   render: function() {
     return (
-      <View style={this._styles.container} testID="container" collapsable={false}>
-        <View style={[this._styles.child, {backgroundColor: '#ff0000'}]} collapsable={false}/>
-        <View style={[this._styles.child, {backgroundColor: '#0000ff'}]} collapsable={false}/>
+      <View
+        style={this._styles.container}
+        testID="container"
+        collapsable={false}>
+        <View
+          style={[this._styles.child, {backgroundColor: '#ff0000'}]}
+          collapsable={false}
+        />
+        <View
+          style={[this._styles.child, {backgroundColor: '#0000ff'}]}
+          collapsable={false}
+        />
       </View>
     );
-  }
+  },
 });
 
 var FlexWithText = createReactClass({
@@ -65,14 +75,17 @@ var FlexWithText = createReactClass({
   }),
   render: function() {
     return (
-      <View style={this._styles.container} testID="container" collapsable={false}>
+      <View
+        style={this._styles.container}
+        testID="container"
+        collapsable={false}>
         <View style={this._styles.row} collapsable={false}>
           <Text style={this._styles.inner}>Hello</Text>
           <Text style={this._styles.inner}>World</Text>
         </View>
       </View>
     );
-  }
+  },
 });
 
 var AbsolutePositionTestApp = createReactClass({
@@ -84,11 +97,17 @@ var AbsolutePositionTestApp = createReactClass({
       left: 10,
       width: 50,
       height: 60,
-    }
+    },
   }),
   render: function() {
-    return <View style={this._styles.absolute} testID="absolute" collapsable={false}/>;
-  }
+    return (
+      <View
+        style={this._styles.absolute}
+        testID="absolute"
+        collapsable={false}
+      />
+    );
+  },
 });
 
 var AbsolutePositionBottomRightTestApp = createReactClass({
@@ -104,15 +123,18 @@ var AbsolutePositionBottomRightTestApp = createReactClass({
       right: 10,
       width: 50,
       height: 60,
-    }
+    },
   }),
   render: function() {
     return (
-      <View style={this._styles.container} testID="container" collapsable={false}>
-        <View style={this._styles.absolute} collapsable={false}/>
+      <View
+        style={this._styles.container}
+        testID="container"
+        collapsable={false}>
+        <View style={this._styles.absolute} collapsable={false} />
       </View>
     );
-  }
+  },
 });
 
 var CenteredTextView = createReactClass({
@@ -134,11 +156,13 @@ var CenteredTextView = createReactClass({
     return (
       <View collapsable={false}>
         <View style={this._styles.parent} collapsable={false}>
-          <Text style={this._styles.text} testID="text">{this.props.text}</Text>
+          <Text style={this._styles.text} testID="text">
+            {this.props.text}
+          </Text>
         </View>
       </View>
     );
-  }
+  },
 });
 
 var flushUpdatePositionInList = null;
@@ -150,11 +174,11 @@ var UpdatePositionInListTestApp = createReactClass({
     },
     active: {
       height: 50,
-    }
+    },
   }),
   getInitialState: function() {
-    flushUpdatePositionInList = () => this.setState({ active: true });
-    return { active: false };
+    flushUpdatePositionInList = () => this.setState({active: true});
+    return {active: false};
   },
   render: function() {
     return (
@@ -167,10 +191,10 @@ var UpdatePositionInListTestApp = createReactClass({
           ]}
           collapsable={false}
         />
-        <View style={this._styles.element} collapsable={false}/>
+        <View style={this._styles.element} collapsable={false} />
       </View>
     );
-  }
+  },
 });
 
 var UIManagerTestModule = {
@@ -194,12 +218,12 @@ var UIManagerTestModule = {
   },
   flushUpdatePositionInList: function() {
     flushUpdatePositionInList();
-  }
+  },
 };
 
 BatchedBridge.registerCallableModule(
   'UIManagerTestModule',
-  UIManagerTestModule
+  UIManagerTestModule,
 );
 
 module.exports = UIManagerTestModule;
diff --git a/ReactAndroid/src/androidTest/js/ViewRenderingTestModule.js b/ReactAndroid/src/androidTest/js/ViewRenderingTestModule.js
index 0ddaa86f07e9..c2215318a52f 100644
--- a/ReactAndroid/src/androidTest/js/ViewRenderingTestModule.js
+++ b/ReactAndroid/src/androidTest/js/ViewRenderingTestModule.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
@@ -26,9 +27,7 @@ class ViewSampleApp extends React.Component {
   state = {};
 
   render() {
-    return (
-      <View style={styles.view} collapsable={false}/>
-    );
+    return <View style={styles.view} collapsable={false} />;
   }
 }
 
@@ -40,7 +39,10 @@ class MarginSampleApp extends React.Component {
   render() {
     updateMargins = this.setState.bind(this, {margin: 15});
     return (
-      <View style={{margin: this.state.margin, marginLeft: 20}} collapsable={false}/>
+      <View
+        style={{margin: this.state.margin, marginLeft: 20}}
+        collapsable={false}
+      />
     );
   }
 }
@@ -48,8 +50,13 @@ class MarginSampleApp extends React.Component {
 class BorderSampleApp extends React.Component {
   render() {
     return (
-      <View style={{borderLeftWidth: 20, borderWidth: 5, backgroundColor: 'blue'}} collapsable={false}>
-        <View style={{backgroundColor: 'red', width: 20, height: 20}} collapsable={false}/>
+      <View
+        style={{borderLeftWidth: 20, borderWidth: 5, backgroundColor: 'blue'}}
+        collapsable={false}>
+        <View
+          style={{backgroundColor: 'red', width: 20, height: 20}}
+          collapsable={false}
+        />
       </View>
     );
   }
@@ -64,11 +71,9 @@ class TransformSampleApp extends React.Component {
         {rotate: '15deg'},
         {scaleX: 5},
         {scaleY: 10},
-      ]
+      ],
     };
-    return (
-      <View style={style} collapsable={false}/>
-    );
+    return <View style={style} collapsable={false} />;
   }
 }
 
@@ -92,7 +97,7 @@ var ViewRenderingTestModule = {
 
 BatchedBridge.registerCallableModule(
   'ViewRenderingTestModule',
-  ViewRenderingTestModule
+  ViewRenderingTestModule,
 );
 
 module.exports = ViewRenderingTestModule;
diff --git a/babel-preset/index.js b/babel-preset/index.js
index aaff5ba9f15c..2209567af269 100644
--- a/babel-preset/index.js
+++ b/babel-preset/index.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('./configs/main');
diff --git a/babel-preset/transforms/transform-symbol-member.js b/babel-preset/transforms/transform-symbol-member.js
index fd5333d1fe54..3cf5f5faf9f7 100644
--- a/babel-preset/transforms/transform-symbol-member.js
+++ b/babel-preset/transforms/transform-symbol-member.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -37,16 +39,12 @@ module.exports = function symbolMember(babel) {
           t.conditionalExpression(
             t.binaryExpression(
               '===',
-              t.unaryExpression(
-                'typeof',
-                t.identifier('Symbol'),
-                true
-              ),
-              t.stringLiteral('function')
+              t.unaryExpression('typeof', t.identifier('Symbol'), true),
+              t.stringLiteral('function'),
             ),
             node,
-            t.stringLiteral(`@@${node.property.name}`)
-          )
+            t.stringLiteral(`@@${node.property.name}`),
+          ),
         );
 
         // We should stop to avoid infinite recursion, since Babel
@@ -60,8 +58,10 @@ module.exports = function symbolMember(babel) {
 function isAppropriateMember(path) {
   let node = path.node;
 
-  return path.parentPath.type !== 'AssignmentExpression' &&
+  return (
+    path.parentPath.type !== 'AssignmentExpression' &&
     node.object.type === 'Identifier' &&
     node.object.name === 'Symbol' &&
-    node.property.type === 'Identifier';
+    node.property.type === 'Identifier'
+  );
 }
diff --git a/bots/code-analysis-bot.js b/bots/code-analysis-bot.js
index 4ab9af077961..d39120e53e06 100644
--- a/bots/code-analysis-bot.js
+++ b/bots/code-analysis-bot.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 if (!process.env.CI_USER) {
@@ -15,7 +18,9 @@ if (!process.env.CI_REPO) {
   process.exit(1);
 }
 if (!process.env.GITHUB_TOKEN) {
-  console.error('Missing GITHUB_TOKEN. Example: 5fd88b964fa214c4be2b144dc5af5d486a2f8c1e');
+  console.error(
+    'Missing GITHUB_TOKEN. Example: 5fd88b964fa214c4be2b144dc5af5d486a2f8c1e',
+  );
   process.exit(1);
 }
 if (!process.env.PULL_REQUEST_NUMBER) {
@@ -90,7 +95,7 @@ var converters = {
         });
       });
     });
-  }
+  },
 };
 
 function getShaFromPullRequest(user, repo, number, callback) {
@@ -118,7 +123,6 @@ function getFilesFromCommit(user, repo, sha, callback) {
   });
 }
 
-
 /**
  * Sadly we can't just give the line number to github, we have to give the
  * line number relative to the patch file which is super annoying. This
@@ -130,7 +134,7 @@ function getLineMapFromPatch(patchString) {
   var fileLineIndex = 0;
   var lineMap = {};
 
-  patchString.split('\n').forEach((line) => {
+  patchString.split('\n').forEach(line => {
     if (line.match(/^@@/)) {
       fileLineIndex = line.match(/\+([0-9]+)/)[1] - 1;
       return;
@@ -179,27 +183,27 @@ function main(messages, user, repo, number) {
     return;
   }
 
-  getShaFromPullRequest(user, repo, number, (sha) => {
-    getFilesFromCommit(user, repo, sha, (files) => {
-      files
-        .filter((file) => messages[file.filename])
-        .forEach((file) => {
-          // github api sometimes does not return a patch on large commits
-          if (!file.patch) {
-            return;
-          }
-          var lineMap = getLineMapFromPatch(file.patch);
-          messages[file.filename].forEach((message) => {
-            sendComment(user, repo, number, sha, file.filename, lineMap, message);
-          });
+  getShaFromPullRequest(user, repo, number, sha => {
+    getFilesFromCommit(user, repo, sha, files => {
+      files.filter(file => messages[file.filename]).forEach(file => {
+        // github api sometimes does not return a patch on large commits
+        if (!file.patch) {
+          return;
+        }
+        var lineMap = getLineMapFromPatch(file.patch);
+        messages[file.filename].forEach(message => {
+          sendComment(user, repo, number, sha, file.filename, lineMap, message);
         });
+      });
     });
   });
 }
 
 var content = '';
 process.stdin.resume();
-process.stdin.on('data', function(buf) { content += buf.toString(); });
+process.stdin.on('data', function(buf) {
+  content += buf.toString();
+});
 process.stdin.on('end', function() {
   var messages = {};
 
diff --git a/bots/dangerfile.js b/bots/dangerfile.js
index 3380e718fb34..de7c07416344 100644
--- a/bots/dangerfile.js
+++ b/bots/dangerfile.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -11,7 +13,7 @@ const fs = require('fs');
 const includes = require('lodash.includes');
 const minimatch = require('minimatch');
 
-const { danger, fail, markdown, message, warn } = require('danger');
+const {danger, fail, markdown, message, warn} = require('danger');
 
 // Fails if the description is too short.
 if (!danger.github.pr.body || danger.github.pr.body.length < 10) {
@@ -22,13 +24,16 @@ if (!danger.github.pr.body || danger.github.pr.body.length < 10) {
 const packageChanged = includes(danger.git.modified_files, 'package.json');
 if (packageChanged) {
   const title = ':lock: package.json';
-  const idea = 'Changes were made to package.json. ' +
+  const idea =
+    'Changes were made to package.json. ' +
     'This will require a manual import by a Facebook employee.';
   warn(`${title} - <i>${idea}</i>`);
 }
 
 // Warns if a test plan is missing.
-const includesTestPlan = danger.github.pr.body && danger.github.pr.body.toLowerCase().includes('test plan');
+const includesTestPlan =
+  danger.github.pr.body &&
+  danger.github.pr.body.toLowerCase().includes('test plan');
 if (!includesTestPlan) {
   const title = ':clipboard: Test Plan';
   const idea = 'This PR appears to be missing a Test Plan.';
@@ -36,9 +41,13 @@ if (!includesTestPlan) {
 }
 
 // Regex looks for given categories, types, a file/framework/component, and a message - broken into 4 capture groups
-const releaseNotesRegex = /\[\s?(ANDROID|CLI|DOCS|GENERAL|INTERNAL|IOS|TVOS|WINDOWS)\s?\]\s*?\[\s?(BREAKING|BUGFIX|ENHANCEMENT|FEATURE|MINOR)\s?\]\s*?\[(.*)\]\s*?\-\s*?(.*)/ig;
-const includesReleaseNotes = danger.github.pr.body && danger.github.pr.body.toLowerCase().includes('release notes');
-const correctlyFormattedReleaseNotes = releaseNotesRegex.test(danger.github.pr.body);
+const releaseNotesRegex = /\[\s?(ANDROID|CLI|DOCS|GENERAL|INTERNAL|IOS|TVOS|WINDOWS)\s?\]\s*?\[\s?(BREAKING|BUGFIX|ENHANCEMENT|FEATURE|MINOR)\s?\]\s*?\[(.*)\]\s*?\-\s*?(.*)/gi;
+const includesReleaseNotes =
+  danger.github.pr.body &&
+  danger.github.pr.body.toLowerCase().includes('release notes');
+const correctlyFormattedReleaseNotes = releaseNotesRegex.test(
+  danger.github.pr.body,
+);
 
 if (!includesReleaseNotes) {
   const title = ':clipboard: Release Notes';
@@ -54,11 +63,20 @@ if (!includesReleaseNotes) {
 var bigPRThreshold = 600;
 if (danger.github.pr.additions + danger.github.pr.deletions > bigPRThreshold) {
   const title = ':exclamation: Big PR';
-  const idea = `This PR is extremely unlikely to get reviewed because it touches ${danger.github.pr.additions + danger.github.pr.deletions} lines.`;
+  const idea = `This PR is extremely unlikely to get reviewed because it touches ${danger
+    .github.pr.additions + danger.github.pr.deletions} lines.`;
   warn(`${title} - <i>${idea}</i>`);
-} else if (danger.git.modified_files + danger.git.added_files + danger.git.deleted_files > bigPRThreshold) {
+} else if (
+  danger.git.modified_files +
+    danger.git.added_files +
+    danger.git.deleted_files >
+  bigPRThreshold
+) {
   const title = ':exclamation: Big PR';
-  const idea = `This PR is extremely unlikely to get reviewed because it touches ${danger.git.modified_files + danger.git.added_files + danger.git.deleted_files} files.`;
+  const idea = `This PR is extremely unlikely to get reviewed because it touches ${danger
+    .git.modified_files +
+    danger.git.added_files +
+    danger.git.deleted_files} files.`;
   warn(`${title} - <i>${idea}</i>`);
 }
 
@@ -68,10 +86,12 @@ const isMergeRefMaster = danger.github.pr.base.ref === 'master';
 const isMergeRefStable = danger.github.pr.base.ref.indexOf('-stable') !== -1;
 if (!isMergeRefMaster && isMergeRefStable) {
   const title = ':grey_question: Base Branch';
-  const idea = 'The base branch for this PR is something other than `master`. Are you sure you want to merge these changes into a stable release? If you are interested in backporting updates to an older release, the suggested approach is to land those changes on `master` first and then cherry-pick the commits into the branch for that release. The [Releases Guide](https://github.com/facebook/react-native/blob/master/Releases.md) has more information.';
+  const idea =
+    'The base branch for this PR is something other than `master`. Are you sure you want to merge these changes into a stable release? If you are interested in backporting updates to an older release, the suggested approach is to land those changes on `master` first and then cherry-pick the commits into the branch for that release. The [Releases Guide](https://github.com/facebook/react-native/blob/master/Releases.md) has more information.';
   warn(`${title} - <i>${idea}</i>`);
 } else if (!isMergeRefMaster && !isMergeRefStable) {
   const title = ':exclamation: Base Branch';
-  const idea = 'The base branch for this PR is something other than `master`. [Are you sure you want to target something other than the `master` branch?](http://facebook.github.io/react-native/docs/contributing.html#pull-requests)';
+  const idea =
+    'The base branch for this PR is something other than `master`. [Are you sure you want to target something other than the `master` branch?](http://facebook.github.io/react-native/docs/contributing.html#pull-requests)';
   fail(`${title} - <i>${idea}</i>`);
 }
diff --git a/cli.js b/cli.js
index 272a78dfcdcf..a57a0a686284 100644
--- a/cli.js
+++ b/cli.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 module.exports = require('./local-cli/cli.js');
diff --git a/flow/create-react-class.js b/flow/create-react-class.js
index 571653b18de8..dc3fea97e964 100644
--- a/flow/create-react-class.js
+++ b/flow/create-react-class.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  * @nolint
  */
diff --git a/jest/assetFileTransformer.js b/jest/assetFileTransformer.js
index e3a318aed3c1..da6cf34a0da5 100644
--- a/jest/assetFileTransformer.js
+++ b/jest/assetFileTransformer.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 /* eslint-env node */
diff --git a/jest/hasteImpl.js b/jest/hasteImpl.js
index ec838a1d47d0..568f7e8df0d0 100644
--- a/jest/hasteImpl.js
+++ b/jest/hasteImpl.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -13,20 +14,20 @@ const path = require('path');
 
 const ROOT = path.join(__dirname, '..');
 
-const BLACKLISTED_PATTERNS/*: Array<RegExp>*/ = [
+const BLACKLISTED_PATTERNS /*: Array<RegExp> */ = [
   /.*\/__(mocks|tests)__\/.*/,
   /^Libraries\/Animated\/src\/polyfills\/.*/,
   /^Libraries\/Renderer\/fb\/.*/,
 ];
 
-const WHITELISTED_PREFIXES/*: Array<string>*/ = [
+const WHITELISTED_PREFIXES /*: Array<string> */ = [
   'IntegrationTests',
   'Libraries',
   'ReactAndroid',
   'RNTester',
 ];
 
-const NAME_REDUCERS/*: Array<[RegExp, string]>*/ = [
+const NAME_REDUCERS /*: Array<[RegExp, string]> */ = [
   // extract basename
   [/^(?:.*\/)?([a-zA-Z0-9$_.-]+)$/, '$1'],
   // strip .js/.js.flow suffix
@@ -41,23 +42,23 @@ const haste = {
    *                       filePath is not a haste module
    */
   getHasteName(
-    filePath/*: string*/,
-    sourceCode/* : ?string*/
-  )/*: (string | void)*/ {
+    filePath /*: string */,
+    sourceCode /*: ?string */,
+  ) /*: string | void */ {
     if (!isHastePath(filePath)) {
       return undefined;
     }
 
     const hasteName = NAME_REDUCERS.reduce(
       (name, [pattern, replacement]) => name.replace(pattern, replacement),
-      filePath
+      filePath,
     );
 
     return hasteName;
   },
 };
 
-function isHastePath(filePath/*: string*/)/*: bool*/ {
+function isHastePath(filePath /*: string */) /*: boolean */ {
   if (!filePath.endsWith('.js') && !filePath.endsWith('.js.flow')) {
     return false;
   }
diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index 6d9e60de675f..a2854943d952 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
@@ -22,10 +23,12 @@ const babelRegisterOnly = require('metro-babel-register');
 const createCacheKeyFunction = require('fbjs-scripts/jest/createCacheKeyFunction');
 const generate = require('@babel/generator').default;
 
-const nodeFiles = RegExp([
-  '/local-cli/',
-  '/metro(?:-[^\/]*)?/', // metro, metro-core, metro-source-map, metro-etc
-].join('|'));
+const nodeFiles = RegExp(
+  [
+    '/local-cli/',
+    '/metro(?:-[^/]*)?/', // metro, metro-core, metro-source-map, metro-etc
+  ].join('|'),
+);
 const nodeOptions = babelRegisterOnly.config([nodeFiles]);
 
 babelRegisterOnly([]);
@@ -33,11 +36,12 @@ babelRegisterOnly([]);
 /* $FlowFixMe(site=react_native_oss) */
 const transformer = require('metro/src/transformer.js');
 module.exports = {
-  process(src/*: string*/, file/*: string*/) {
-    if (nodeFiles.test(file)) { // node specific transforms only
+  process(src /*: string */, file /*: string */) {
+    if (nodeFiles.test(file)) {
+      // node specific transforms only
       return babelTransformSync(
         src,
-        Object.assign({filename: file}, nodeOptions)
+        Object.assign({filename: file}, nodeOptions),
       ).code;
     }
 
@@ -96,15 +100,19 @@ module.exports = {
       ],
     });
 
-    return generate(ast, {
-      code: true,
-      comments: false,
-      compact: false,
-      filename: file,
-      retainLines: true,
-      sourceFileName: file,
-      sourceMaps: true,
-    }, src).code;
+    return generate(
+      ast,
+      {
+        code: true,
+        comments: false,
+        compact: false,
+        filename: file,
+        retainLines: true,
+        sourceFileName: file,
+        sourceMaps: true,
+      },
+      src,
+    ).code;
   },
 
   getCacheKey: createCacheKeyFunction([
diff --git a/jest/setup.js b/jest/setup.js
index 18cb7dfbddd7..1cb1eddfa9cd 100644
--- a/jest/setup.js
+++ b/jest/setup.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const MockNativeMethods = require.requireActual('./MockNativeMethods');
@@ -16,7 +19,9 @@ require.requireActual('../Libraries/polyfills/error-guard');
 global.__DEV__ = true;
 
 global.Promise = require.requireActual('promise');
-global.regeneratorRuntime = require.requireActual('regenerator-runtime/runtime');
+global.regeneratorRuntime = require.requireActual(
+  'regenerator-runtime/runtime',
+);
 
 global.requestAnimationFrame = function(callback) {
   return setTimeout(callback, 0);
@@ -25,9 +30,7 @@ global.cancelAnimationFrame = function(id) {
   clearTimeout(id);
 };
 
-jest
-  .mock('setupDevtools')
-  .mock('npmlog');
+jest.mock('setupDevtools').mock('npmlog');
 
 // there's a __mock__ for it.
 jest.setMock('ErrorUtils', require('ErrorUtils'));
@@ -41,10 +44,7 @@ jest
   .mock('View', () => mockComponent('View', MockNativeMethods))
   .mock('RefreshControl', () => require.requireMock('RefreshControlMock'))
   .mock('ScrollView', () => require.requireMock('ScrollViewMock'))
-  .mock(
-    'ActivityIndicator',
-    () => mockComponent('ActivityIndicator'),
-  )
+  .mock('ActivityIndicator', () => mockComponent('ActivityIndicator'))
   .mock('ListView', () => require.requireMock('ListViewMock'))
   .mock('ListViewDataSource', () => {
     const DataSource = require.requireActual('ListViewDataSource');
@@ -54,9 +54,9 @@ jest
         // Ensure this doesn't throw.
         try {
           Object.keys(dataBlob).forEach(key => {
-            this.items += dataBlob[key] && (
-              dataBlob[key].length || dataBlob[key].size || 0
-            );
+            this.items +=
+              dataBlob[key] &&
+              (dataBlob[key].length || dataBlob[key].size || 0);
           });
         } catch (e) {
           this.items = 'unknown';
@@ -68,7 +68,9 @@ jest
     return DataSource;
   })
   .mock('AnimatedImplementation', () => {
-    const AnimatedImplementation = require.requireActual('AnimatedImplementation');
+    const AnimatedImplementation = require.requireActual(
+      'AnimatedImplementation',
+    );
     const oldCreate = AnimatedImplementation.createAnimatedComponent;
     AnimatedImplementation.createAnimatedComponent = function(Component) {
       const Wrapped = oldCreate(Component);
@@ -80,7 +82,8 @@ jest
   .mock('ReactNative', () => {
     const ReactNative = require.requireActual('ReactNative');
     const NativeMethodsMixin =
-      ReactNative.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.NativeMethodsMixin;
+      ReactNative.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED
+        .NativeMethodsMixin;
 
     Object.assign(NativeMethodsMixin, MockNativeMethods);
     Object.assign(ReactNative.NativeComponent.prototype, MockNativeMethods);
@@ -99,10 +102,18 @@ const mockNativeModules = {
     removeEventListener: jest.fn(),
   },
   AsyncLocalStorage: {
-    multiGet: jest.fn((keys, callback) => process.nextTick(() => callback(null, []))),
-    multiSet: jest.fn((entries, callback) => process.nextTick(() => callback(null))),
-    multiRemove: jest.fn((keys, callback) => process.nextTick(() => callback(null))),
-    multiMerge: jest.fn((entries, callback) => process.nextTick(() => callback(null))),
+    multiGet: jest.fn((keys, callback) =>
+      process.nextTick(() => callback(null, [])),
+    ),
+    multiSet: jest.fn((entries, callback) =>
+      process.nextTick(() => callback(null)),
+    ),
+    multiRemove: jest.fn((keys, callback) =>
+      process.nextTick(() => callback(null)),
+    ),
+    multiMerge: jest.fn((entries, callback) =>
+      process.nextTick(() => callback(null)),
+    ),
     clear: jest.fn(callback => process.nextTick(() => callback(null))),
     getAllKeys: jest.fn(callback => process.nextTick(() => callback(null, []))),
   },
@@ -149,14 +160,12 @@ const mockNativeModules = {
     }),
   },
   ImageLoader: {
-    getSize: jest.fn(
-      (url) => Promise.resolve({width: 320, height: 240})
-    ),
+    getSize: jest.fn(url => Promise.resolve({width: 320, height: 240})),
     prefetchImage: jest.fn(),
   },
   ImageViewManager: {
-    getSize: jest.fn(
-      (uri, success) => process.nextTick(() => success(320, 240))
+    getSize: jest.fn((uri, success) =>
+      process.nextTick(() => success(320, 240)),
     ),
     prefetchImage: jest.fn(),
   },
@@ -166,13 +175,9 @@ const mockNativeModules = {
   },
   Linking: {
     openURL: jest.fn(),
-    canOpenURL: jest.fn(
-      () => Promise.resolve(true)
-    ),
+    canOpenURL: jest.fn(() => Promise.resolve(true)),
     addEventListener: jest.fn(),
-    getInitialURL: jest.fn(
-      () => Promise.resolve()
-    ),
+    getInitialURL: jest.fn(() => Promise.resolve()),
     removeEventListener: jest.fn(),
   },
   LocationObserver: {
@@ -182,24 +187,16 @@ const mockNativeModules = {
   },
   ModalFullscreenViewManager: {},
   NetInfo: {
-    fetch: jest.fn(
-      () => Promise.resolve()
-    ),
-    getConnectionInfo: jest.fn(
-      () => Promise.resolve()
-    ),
+    fetch: jest.fn(() => Promise.resolve()),
+    getConnectionInfo: jest.fn(() => Promise.resolve()),
     addEventListener: jest.fn(),
     removeEventListener: jest.fn(),
     isConnected: {
-      fetch: jest.fn(
-        () => Promise.resolve()
-      ),
+      fetch: jest.fn(() => Promise.resolve()),
       addEventListener: jest.fn(),
       removeEventListener: jest.fn(),
     },
-    isConnectionExpensive: jest.fn(
-      () => Promise.resolve()
-    ),
+    isConnectionExpensive: jest.fn(() => Promise.resolve()),
   },
   Networking: {
     sendRequest: jest.fn(),
@@ -215,12 +212,20 @@ const mockNativeModules = {
     getDeliveredNotifications: jest.fn(callback => process.nextTick(() => [])),
     removeDeliveredNotifications: jest.fn(),
     setApplicationIconBadgeNumber: jest.fn(),
-    getApplicationIconBadgeNumber: jest.fn(callback => process.nextTick(() => callback(0))),
+    getApplicationIconBadgeNumber: jest.fn(callback =>
+      process.nextTick(() => callback(0)),
+    ),
     cancelLocalNotifications: jest.fn(),
-    getScheduledLocalNotifications: jest.fn(callback => process.nextTick(() => callback())),
-    requestPermissions: jest.fn(() => Promise.resolve({alert: true, badge: true, sound: true})),
+    getScheduledLocalNotifications: jest.fn(callback =>
+      process.nextTick(() => callback()),
+    ),
+    requestPermissions: jest.fn(() =>
+      Promise.resolve({alert: true, badge: true, sound: true}),
+    ),
     abandonPermissions: jest.fn(),
-    checkPermissions: jest.fn(callback => process.nextTick(() => callback({alert: true, badge: true, sound: true}))),
+    checkPermissions: jest.fn(callback =>
+      process.nextTick(() => callback({alert: true, badge: true, sound: true})),
+    ),
     getInitialNotification: jest.fn(() => Promise.resolve(null)),
     addListener: jest.fn(),
     removeListeners: jest.fn(),
@@ -300,19 +305,15 @@ Object.keys(mockNativeModules).forEach(module => {
   }
 });
 
-jest
-  .doMock('NativeModules', () => mockNativeModules);
+jest.doMock('NativeModules', () => mockNativeModules);
 
 jest.doMock('requireNativeComponent', () => {
   const React = require('react');
 
-  return viewName => class extends React.Component {
-    render() {
-      return React.createElement(
-        viewName,
-        this.props,
-        this.props.children,
-      );
-    }
-  };
+  return viewName =>
+    class extends React.Component {
+      render() {
+        return React.createElement(viewName, this.props, this.props.children);
+      }
+    };
 });
diff --git a/lib/InitializeJavaScriptAppEngine.js b/lib/InitializeJavaScriptAppEngine.js
index 6709e0a27109..5048f860e41d 100644
--- a/lib/InitializeJavaScriptAppEngine.js
+++ b/lib/InitializeJavaScriptAppEngine.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/lib/RCTEventEmitter.js b/lib/RCTEventEmitter.js
index 8968fb8641df..c225257d105c 100644
--- a/lib/RCTEventEmitter.js
+++ b/lib/RCTEventEmitter.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/lib/TextInputState.js b/lib/TextInputState.js
index 37738ceb670a..5345311a518d 100644
--- a/lib/TextInputState.js
+++ b/lib/TextInputState.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/lib/UIManager.js b/lib/UIManager.js
index 6bd741903fb3..b846967b626f 100644
--- a/lib/UIManager.js
+++ b/lib/UIManager.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/lib/UIManagerStatTracker.js b/lib/UIManagerStatTracker.js
index 9300a7c6f7ea..c62aebdf0aee 100644
--- a/lib/UIManagerStatTracker.js
+++ b/lib/UIManagerStatTracker.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/lib/View.js b/lib/View.js
index 6e3f20a85855..852e741251bd 100644
--- a/lib/View.js
+++ b/lib/View.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/lib/deepDiffer.js b/lib/deepDiffer.js
index ad3d3cb05329..6254047d4726 100644
--- a/lib/deepDiffer.js
+++ b/lib/deepDiffer.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/lib/deepFreezeAndThrowOnMutationInDev.js b/lib/deepFreezeAndThrowOnMutationInDev.js
index 92d9f8f40e0b..6691d2a648b1 100644
--- a/lib/deepFreezeAndThrowOnMutationInDev.js
+++ b/lib/deepFreezeAndThrowOnMutationInDev.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/lib/flattenStyle.js b/lib/flattenStyle.js
index 3c5651fdc602..1c7256c7fca7 100644
--- a/lib/flattenStyle.js
+++ b/lib/flattenStyle.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 // This is a forwarding module to allow React to require React Native internals
diff --git a/react-native-git-upgrade/checks.js b/react-native-git-upgrade/checks.js
index 1660addd00e2..88be3ac07853 100644
--- a/react-native-git-upgrade/checks.js
+++ b/react-native-git-upgrade/checks.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const {execSync} = require('child_process');
@@ -12,7 +15,7 @@ const semver = require('semver');
 function checkDeclaredVersion(declaredVersion) {
   if (!declaredVersion) {
     throw new Error(
-      'Your "package.json" file doesn\'t seem to have "react-native" as a dependency.'
+      'Your "package.json" file doesn\'t seem to have "react-native" as a dependency.',
     );
   }
 }
@@ -20,11 +23,15 @@ function checkDeclaredVersion(declaredVersion) {
 function checkMatchingVersions(currentVersion, declaredVersion, useYarn) {
   if (!semver.satisfies(currentVersion, declaredVersion)) {
     throw new Error(
-      'react-native version in "package.json" (' + declaredVersion + ') doesn\'t match ' +
-      'the installed version in "node_modules" (' + currentVersion + ').\n' +
-      (useYarn ?
-        'Try running "yarn" to fix this.' :
-        'Try running "npm install" to fix this.')
+      'react-native version in "package.json" (' +
+        declaredVersion +
+        ") doesn't match " +
+        'the installed version in "node_modules" (' +
+        currentVersion +
+        ').\n' +
+        (useYarn
+          ? 'Try running "yarn" to fix this.'
+          : 'Try running "npm install" to fix this.'),
     );
   }
 }
@@ -33,10 +40,10 @@ function checkReactPeerDependency(currentVersion, declaredReactVersion) {
   if (semver.lt(currentVersion, '0.21.0') && !declaredReactVersion) {
     throw new Error(
       'Your "package.json" file doesn\'t seem to have "react" as a dependency.\n' +
-      '"react" was changed from a dependency to a peer dependency in react-native v0.21.0.\n' +
-      'Therefore, it\'s necessary to include "react" in your project\'s dependencies.\n' +
-      'Please run "npm install --save react", then re-run ' +
-      '"react-native upgrade".'
+        '"react" was changed from a dependency to a peer dependency in react-native v0.21.0.\n' +
+        'Therefore, it\'s necessary to include "react" in your project\'s dependencies.\n' +
+        'Please run "npm install --save react", then re-run ' +
+        '"react-native upgrade".',
     );
   }
 }
@@ -47,7 +54,7 @@ function checkGitAvailable() {
   } catch (error) {
     throw new Error(
       '"react-native-git-upgrade" requires "git" to be available in path. ' +
-      'Please install Git (https://git-scm.com)"'
+        'Please install Git (https://git-scm.com)"',
     );
   }
 }
diff --git a/react-native-git-upgrade/cli.js b/react-native-git-upgrade/cli.js
index 94647fd16c48..19103c9fefb9 100644
--- a/react-native-git-upgrade/cli.js
+++ b/react-native-git-upgrade/cli.js
@@ -3,16 +3,19 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 require('babel-register')({
   presets: [
     require('babel-preset-es2015-node'),
-    require('babel-preset-stage-3')
+    require('babel-preset-stage-3'),
   ],
   // Enable transpiling for react-native-git-upgrade AND the generator, just like the upgrade CLI command does
-  only: /(react-native-git-upgrade\/(?!(node_modules)))|(local-cli\/generator)/
+  only: /(react-native-git-upgrade\/(?!(node_modules)))|(local-cli\/generator)/,
 });
 
 var cliEntry = require('./cliEntry');
diff --git a/react-native-git-upgrade/cliEntry.js b/react-native-git-upgrade/cliEntry.js
index 49f9d53b4807..bb3afc61e6f6 100644
--- a/react-native-git-upgrade/cliEntry.js
+++ b/react-native-git-upgrade/cliEntry.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const fs = require('fs');
@@ -36,7 +39,8 @@ log.heading = 'git-upgrade';
  */
 function exec(command, logOutput, logger = null) {
   return new Promise((resolve, reject) => {
-    let stderr, stdout = '';
+    let stderr,
+      stdout = '';
     const child = shell.exec(command, {async: true, silent: true});
 
     child.stdout.on('data', data => {
@@ -63,22 +67,26 @@ function exec(command, logOutput, logger = null) {
       if (code === 0) {
         resolve(stdout);
       } else if (code) {
-        reject(new Error(`Command '${command}' exited with code ${code}:
+        reject(
+          new Error(`Command '${command}' exited with code ${code}:
 stderr: ${stderr}
-stdout: ${stdout}`));
+stdout: ${stdout}`),
+        );
       } else {
-        reject(new Error(`Command '${command}' terminated with signal '${signal}':
+        reject(
+          new Error(`Command '${command}' terminated with signal '${signal}':
 stderr: ${stderr}
-stdout: ${stdout}`));
+stdout: ${stdout}`),
+        );
       }
     });
   });
 }
 
 function parseJsonFile(path, useYarn) {
-  const installHint = useYarn ?
-    'Make sure you ran "yarn" and that you are inside a React Native project.' :
-    'Make sure you ran "npm install" and that you are inside a React Native project.';
+  const installHint = useYarn
+    ? 'Make sure you ran "yarn" and that you are inside a React Native project.'
+    : 'Make sure you ran "npm install" and that you are inside a React Native project.';
   let fileContents;
   try {
     fileContents = fs.readFileSync(path, 'utf8');
@@ -94,18 +102,22 @@ function parseJsonFile(path, useYarn) {
 
 function readPackageFiles(useYarn) {
   const reactNativeNodeModulesPakPath = path.resolve(
-    process.cwd(), 'node_modules', 'react-native', 'package.json'
+    process.cwd(),
+    'node_modules',
+    'react-native',
+    'package.json',
   );
   const reactNodeModulesPakPath = path.resolve(
-    process.cwd(), 'node_modules', 'react', 'package.json'
-  );
-  const pakPath = path.resolve(
-    process.cwd(), 'package.json'
+    process.cwd(),
+    'node_modules',
+    'react',
+    'package.json',
   );
+  const pakPath = path.resolve(process.cwd(), 'package.json');
   return {
     reactNativeNodeModulesPak: parseJsonFile(reactNativeNodeModulesPakPath),
     reactNodeModulesPak: parseJsonFile(reactNodeModulesPakPath),
-    pak: parseJsonFile(pakPath)
+    pak: parseJsonFile(pakPath),
   };
 }
 
@@ -121,15 +133,16 @@ function parseInformationJsonOutput(jsonOutput, requestedVersion) {
     return {newVersion, newReactVersionRange};
   } catch (err) {
     throw new Error(
-      'The specified version of React Native ' + requestedVersion + ' doesn\'t exist.\n' +
-      'Re-run the react-native-git-upgrade command with an existing version,\n' +
-      'for example: "react-native-git-upgrade 0.38.0",\n' +
-      'or without arguments to upgrade to the latest: "react-native-git-upgrade".'
+      'The specified version of React Native ' +
+        requestedVersion +
+        " doesn't exist.\n" +
+        'Re-run the react-native-git-upgrade command with an existing version,\n' +
+        'for example: "react-native-git-upgrade 0.38.0",\n' +
+        'or without arguments to upgrade to the latest: "react-native-git-upgrade".',
     );
   }
 }
 
-
 function setupWorkingDir(tmpDir) {
   return new Promise((resolve, reject) => {
     rimraf(tmpDir, err => {
@@ -163,7 +176,11 @@ function copyCurrentGitIgnoreFile(tmpDir) {
    */
   try {
     const gitignorePath = path.resolve(process.cwd(), '.gitignore');
-    const repoExcludePath = path.resolve(tmpDir, process.env.GIT_DIR, 'info/exclude');
+    const repoExcludePath = path.resolve(
+      tmpDir,
+      process.env.GIT_DIR,
+      'info/exclude',
+    );
     const content = fs.readFileSync(gitignorePath, 'utf8');
     fs.appendFileSync(repoExcludePath, content);
   } catch (err) {
@@ -188,7 +205,10 @@ function generateTemplates(generatorDir, appName, verbose) {
 }
 
 function runCopyAndReplace(generatorDir, appName) {
-  const copyProjectTemplateAndReplacePath = path.resolve(generatorDir, 'copyProjectTemplateAndReplace');
+  const copyProjectTemplateAndReplacePath = path.resolve(
+    generatorDir,
+    'copyProjectTemplateAndReplace',
+  );
   /*
    * This module is required twice during the process: for both old and new version
    * of React Native.
@@ -201,7 +221,7 @@ function runCopyAndReplace(generatorDir, appName) {
     path.resolve(generatorDir, '..', 'templates', 'HelloWorld'),
     process.cwd(),
     appName,
-    {upgrade: true, force: true}
+    {upgrade: true, force: true},
   );
 }
 
@@ -216,7 +236,9 @@ function runYeomanGenerators(generatorDir, appName, verbose) {
   const env = yeoman.createEnv();
   env.register(generatorDir, 'react:app');
   const generatorArgs = ['react:app', appName];
-  return new Promise((resolve) => env.run(generatorArgs, {upgrade: true, force: true}, resolve));
+  return new Promise(resolve =>
+    env.run(generatorArgs, {upgrade: true, force: true}, resolve),
+  );
 }
 
 /**
@@ -225,15 +247,17 @@ function runYeomanGenerators(generatorDir, appName, verbose) {
 async function checkForUpdates() {
   try {
     log.info('Check for updates');
-    const lastGitUpgradeVersion = await exec('npm view react-native-git-upgrade@latest version');
+    const lastGitUpgradeVersion = await exec(
+      'npm view react-native-git-upgrade@latest version',
+    );
     const current = require('./package').version;
     const latest = semver.clean(lastGitUpgradeVersion);
     if (semver.gt(latest, current)) {
       log.warn(
         'A more recent version of "react-native-git-upgrade" has been found.\n' +
-        `Current: ${current}\n` +
-        `Latest: ${latest}\n` +
-        'Please run "npm install -g react-native-git-upgrade"'
+          `Current: ${current}\n` +
+          `Latest: ${latest}\n` +
+          'Please run "npm install -g react-native-git-upgrade"',
       );
     }
   } catch (err) {
@@ -263,7 +287,13 @@ function shouldUseYarn(cliArgs, projectDir) {
  */
 async function run(requestedVersion, cliArgs) {
   const tmpDir = path.resolve(os.tmpdir(), 'react-native-git-upgrade');
-  const generatorDir = path.resolve(process.cwd(), 'node_modules', 'react-native', 'local-cli', 'generator');
+  const generatorDir = path.resolve(
+    process.cwd(),
+    'node_modules',
+    'react-native',
+    'local-cli',
+    'generator',
+  );
   let projectBackupCreated = false;
 
   try {
@@ -272,7 +302,11 @@ async function run(requestedVersion, cliArgs) {
     const useYarn = shouldUseYarn(cliArgs, path.resolve(process.cwd()));
 
     log.info('Read package.json files');
-    const {reactNativeNodeModulesPak, reactNodeModulesPak, pak} = readPackageFiles(useYarn);
+    const {
+      reactNativeNodeModulesPak,
+      reactNodeModulesPak,
+      pak,
+    } = readPackageFiles(useYarn);
     const appName = pak.name;
     const currentVersion = reactNativeNodeModulesPak.version;
     const currentReactVersion = reactNodeModulesPak.version;
@@ -294,11 +328,19 @@ async function run(requestedVersion, cliArgs) {
     checkGitAvailable();
 
     log.info('Get information from NPM registry');
-    const viewCommand = 'npm view react-native@' + (requestedVersion || 'latest') + ' --json';
+    const viewCommand =
+      'npm view react-native@' + (requestedVersion || 'latest') + ' --json';
     const jsonOutput = await exec(viewCommand, verbose);
-    const {newVersion, newReactVersionRange} = parseInformationJsonOutput(jsonOutput, requestedVersion);
+    const {newVersion, newReactVersionRange} = parseInformationJsonOutput(
+      jsonOutput,
+      requestedVersion,
+    );
     // Print which versions we're upgrading to
-    log.info('Upgrading to React Native ' + newVersion + (newReactVersionRange ? ', React ' + newReactVersionRange : ''));
+    log.info(
+      'Upgrading to React Native ' +
+        newVersion +
+        (newReactVersionRange ? ', React ' + newReactVersionRange : ''),
+    );
 
     log.info('Setup temporary working directory');
     await setupWorkingDir(tmpDir);
@@ -329,7 +371,10 @@ async function run(requestedVersion, cliArgs) {
     await exec('git add .', verbose);
 
     log.info('Commit old version template');
-    await exec('git commit -m "Old version" --allow-empty --no-verify', verbose);
+    await exec(
+      'git commit -m "Old version" --allow-empty --no-verify',
+      verbose,
+    );
 
     log.info('Install the new version');
     let installCommand;
@@ -339,7 +384,10 @@ async function run(requestedVersion, cliArgs) {
       installCommand = 'npm install --save --color=always';
     }
     installCommand += ' react-native@' + newVersion;
-    if (newReactVersionRange && !semver.satisfies(currentReactVersion, newReactVersionRange)) {
+    if (
+      newReactVersionRange &&
+      !semver.satisfies(currentReactVersion, newReactVersionRange)
+    ) {
       // Install React as well to avoid unmet peer dependency
       installCommand += ' react@' + newReactVersionRange;
     }
@@ -352,13 +400,22 @@ async function run(requestedVersion, cliArgs) {
     await exec('git add .', verbose);
 
     log.info('Commit new version template');
-    await exec('git commit -m "New version" --allow-empty --no-verify', verbose);
+    await exec(
+      'git commit -m "New version" --allow-empty --no-verify',
+      verbose,
+    );
 
     log.info('Generate the patch between the 2 versions');
-    const diffOutput = await exec('git diff --binary --no-color HEAD~1 HEAD', verbose);
+    const diffOutput = await exec(
+      'git diff --binary --no-color HEAD~1 HEAD',
+      verbose,
+    );
 
     log.info('Save the patch in temp directory');
-    const patchPath = path.resolve(tmpDir, `upgrade_${currentVersion}_${newVersion}.patch`);
+    const patchPath = path.resolve(
+      tmpDir,
+      `upgrade_${currentVersion}_${newVersion}.patch`,
+    );
     fs.writeFileSync(patchPath, diffOutput);
 
     log.info('Reset the 2 temporary commits');
@@ -376,16 +433,16 @@ async function run(requestedVersion, cliArgs) {
     } catch (err) {
       log.warn(
         'The upgrade process succeeded but there might be conflicts to be resolved. ' +
-        'See above for the list of files that have merge conflicts. ' +
-        'If you don’t see the expected changes, try running:\n' +
-        `git apply --reject ${patchPath}`);
+          'See above for the list of files that have merge conflicts. ' +
+          'If you don’t see the expected changes, try running:\n' +
+          `git apply --reject ${patchPath}`,
+      );
     } finally {
       log.info('Upgrade done');
       if (cliArgs.verbose) {
         log.info(`Temporary working directory: ${tmpDir}`);
       }
     }
-
   } catch (err) {
     log.error('An error occurred during upgrade:');
     log.error(err.stack);
diff --git a/react-native-git-upgrade/yarn.js b/react-native-git-upgrade/yarn.js
index 9e461190e458..b215cfa4a4ac 100644
--- a/react-native-git-upgrade/yarn.js
+++ b/react-native-git-upgrade/yarn.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 const execSync = require('child_process').execSync;
@@ -22,7 +25,9 @@ function getYarnVersionIfAvailable() {
     if (process.platform.startsWith('win')) {
       yarnVersion = (execSync('yarn --version').toString() || '').trim();
     } else {
-      yarnVersion = (execSync('yarn --version 2>/dev/null').toString() || '').trim();
+      yarnVersion = (
+        execSync('yarn --version 2>/dev/null').toString() || ''
+      ).trim();
     }
   } catch (error) {
     return null;
diff --git a/rn-get-polyfills.js b/rn-get-polyfills.js
index e7dd869c6f4e..db65ff2245b7 100644
--- a/rn-get-polyfills.js
+++ b/rn-get-polyfills.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  */
 
 'use strict';
diff --git a/scripts/android-e2e-test.js b/scripts/android-e2e-test.js
index bb0e109607de..f23371b106c2 100644
--- a/scripts/android-e2e-test.js
+++ b/scripts/android-e2e-test.js
@@ -21,9 +21,11 @@
  * - (cd android && ./gradlew :app:copyDownloadableDepsToLibs)
  * - buck build android/app
  * - node ../node_modules/.bin/_mocha ../android-e2e-test.js
+ *
+ * @format
  */
 
- /* eslint-env mocha */
+/* eslint-env mocha */
 
 'use strict';
 
@@ -35,27 +37,32 @@ require('colors');
 // value in ms to print out screen contents, set this value in CI to debug if tests are failing
 const appiumDebugInterval = process.env.APPIUM_DEBUG_INTERVAL;
 
-describe('Android Test App', function () {
+describe('Android Test App', function() {
   this.timeout(600000);
   let driver;
   let debugIntervalId;
 
-  before(function () {
+  before(function() {
     driver = wd.promiseChainRemote({
       host: 'localhost',
-      port: 4723
+      port: 4723,
     });
-    driver.on('status', function (info) {
+    driver.on('status', function(info) {
       console.log(info.cyan);
     });
-    driver.on('command', function (method, path, data) {
+    driver.on('command', function(method, path, data) {
       if (path === 'source()' && data) {
-        console.log(' > ' + method.yellow, 'Screen contents'.grey, '\n', pd.xml(data).yellow);
+        console.log(
+          ' > ' + method.yellow,
+          'Screen contents'.grey,
+          '\n',
+          pd.xml(data).yellow,
+        );
       } else {
         console.log(' > ' + method.yellow, path.grey, data || '');
       }
     });
-    driver.on('http', function (method, path, data) {
+    driver.on('http', function(method, path, data) {
       console.log(' > ' + method.magenta, path, (data || '').grey);
     });
 
@@ -70,7 +77,7 @@ describe('Android Test App', function () {
     const desired = {
       platformName: 'Android',
       deviceName: 'Android Emulator',
-      app: path.resolve('buck-out/gen/android/app/app.apk')
+      app: path.resolve('buck-out/gen/android/app/app.apk'),
     };
 
     // React Native in dev mode often starts with Red Box "Can't fibd variable __fbBatchedBridge..."
@@ -78,56 +85,79 @@ describe('Android Test App', function () {
     return driver
       .init(desired)
       .setImplicitWaitTimeout(5000)
-      .waitForElementByXPath('//android.widget.Button[@text="Reload JS"]').
-      then((elem) => {
-        elem.click();
-      }, (err) => {
-        // ignoring if Reload JS button can't be located
-      })
+      .waitForElementByXPath('//android.widget.Button[@text="Reload JS"]')
+      .then(
+        elem => {
+          elem.click();
+        },
+        err => {
+          // ignoring if Reload JS button can't be located
+        },
+      )
       .setImplicitWaitTimeout(150000);
   });
 
-  after(function () {
+  after(function() {
     if (debugIntervalId) {
       clearInterval(debugIntervalId);
     }
     return driver.quit();
   });
 
-  it('should have Hot Module Reloading working', function () {
+  it('should have Hot Module Reloading working', function() {
     const androidAppCode = fs.readFileSync('index.js', 'utf-8');
     let intervalToUpdate;
-    return driver
-      .waitForElementByXPath('//android.widget.TextView[starts-with(@text, "Welcome to React Native!")]')
-      // http://developer.android.com/reference/android/view/KeyEvent.html#KEYCODE_MENU
-      .pressDeviceKey(82)
-      .elementByXPath('//android.widget.TextView[starts-with(@text, "Enable Hot Reloading")]')
-      .click()
-      .waitForElementByXPath('//android.widget.TextView[starts-with(@text, "Welcome to React Native!")]')
-      .then(() => {
-        let iteration = 0;
-        // CI environment can be quite slow and we can't guarantee that it can consistently motice a file change
-        // so we change the file every few seconds just in case
-        intervalToUpdate = setInterval(() => {
-          fs.writeFileSync('index.js', androidAppCode.replace('Welcome to React Native!', 'Welcome to React Native with HMR!' + iteration), 'utf-8');
-        }, 3000);
-      })
-      .waitForElementByXPath('//android.widget.TextView[starts-with(@text, "Welcome to React Native with HMR!")]')
-      .finally(() => {
-        clearInterval(intervalToUpdate);
-        fs.writeFileSync('index.js', androidAppCode, 'utf-8');
-      });
+    return (
+      driver
+        .waitForElementByXPath(
+          '//android.widget.TextView[starts-with(@text, "Welcome to React Native!")]',
+        )
+        // http://developer.android.com/reference/android/view/KeyEvent.html#KEYCODE_MENU
+        .pressDeviceKey(82)
+        .elementByXPath(
+          '//android.widget.TextView[starts-with(@text, "Enable Hot Reloading")]',
+        )
+        .click()
+        .waitForElementByXPath(
+          '//android.widget.TextView[starts-with(@text, "Welcome to React Native!")]',
+        )
+        .then(() => {
+          let iteration = 0;
+          // CI environment can be quite slow and we can't guarantee that it can consistently motice a file change
+          // so we change the file every few seconds just in case
+          intervalToUpdate = setInterval(() => {
+            fs.writeFileSync(
+              'index.js',
+              androidAppCode.replace(
+                'Welcome to React Native!',
+                'Welcome to React Native with HMR!' + iteration,
+              ),
+              'utf-8',
+            );
+          }, 3000);
+        })
+        .waitForElementByXPath(
+          '//android.widget.TextView[starts-with(@text, "Welcome to React Native with HMR!")]',
+        )
+        .finally(() => {
+          clearInterval(intervalToUpdate);
+          fs.writeFileSync('index.js', androidAppCode, 'utf-8');
+        })
+    );
   });
 
-
-  it('should have Debug In Chrome working', function () {
+  it('should have Debug In Chrome working', function() {
     const androidAppCode = fs.readFileSync('index.js', 'utf-8');
     // http://developer.android.com/reference/android/view/KeyEvent.html#KEYCODE_MENU
     return driver
-      .waitForElementByXPath('//android.widget.TextView[starts-with(@text, "Welcome to React Native!")]')
+      .waitForElementByXPath(
+        '//android.widget.TextView[starts-with(@text, "Welcome to React Native!")]',
+      )
       .pressDeviceKey(82)
       .elementByXPath('//android.widget.TextView[starts-with(@text, "Debug")]')
       .click()
-      .waitForElementByXPath('//android.widget.TextView[starts-with(@text, "Welcome to React Native!")]');
+      .waitForElementByXPath(
+        '//android.widget.TextView[starts-with(@text, "Welcome to React Native!")]',
+      );
   });
 });
diff --git a/scripts/publish-npm.js b/scripts/publish-npm.js
index 269fc7014dd3..f9492a935776 100644
--- a/scripts/publish-npm.js
+++ b/scripts/publish-npm.js
@@ -3,7 +3,10 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
+
 'use strict';
 
 /**
@@ -60,17 +63,24 @@ if (buildBranch.indexOf('-stable') !== -1) {
 // 34c034298dc9cad5a4553964a5a324450fda0385
 const currentCommit = exec('git rev-parse HEAD', {silent: true}).stdout.trim();
 // [34c034298dc9cad5a4553964a5a324450fda0385, refs/heads/0.33-stable, refs/tags/latest, refs/tags/v0.33.1, refs/tags/v0.34.1-rc]
-const tagsWithVersion = exec(`git ls-remote origin | grep ${currentCommit}`, {silent: true})
+const tagsWithVersion = exec(`git ls-remote origin | grep ${currentCommit}`, {
+  silent: true,
+})
   .stdout.split(/\s/)
   // ['refs/tags/v0.33.0', 'refs/tags/v0.33.0-rc', 'refs/tags/v0.33.0-rc1', 'refs/tags/v0.33.0-rc2', 'refs/tags/v0.34.0']
-  .filter(version => !!version && version.indexOf(`refs/tags/v${branchVersion}`) === 0)
+  .filter(
+    version =>
+      !!version && version.indexOf(`refs/tags/v${branchVersion}`) === 0,
+  )
   // ['refs/tags/v0.33.0', 'refs/tags/v0.33.0-rc', 'refs/tags/v0.33.0-rc1', 'refs/tags/v0.33.0-rc2']
   .filter(version => version.indexOf(branchVersion) !== -1)
   // ['v0.33.0', 'v0.33.0-rc', 'v0.33.0-rc1', 'v0.33.0-rc2']
   .map(version => version.slice('refs/tags/'.length));
 
 if (tagsWithVersion.length === 0) {
-  echo('Error: Can\'t find version tag in current commit. To deploy to NPM you must add tag v0.XY.Z[-rc] to your commit');
+  echo(
+    "Error: Can't find version tag in current commit. To deploy to NPM you must add tag v0.XY.Z[-rc] to your commit",
+  );
   exit(1);
 }
 let releaseVersion;
@@ -86,7 +96,7 @@ if (tagsWithVersion[0].indexOf('-rc') === -1) {
 
 // -------- Generating Android Artifacts with JavaDoc
 if (exec('./gradlew :ReactAndroid:installArchives').code) {
-  echo('Couldn\'t generate artifacts');
+  echo("Couldn't generate artifacts");
   exit(1);
 }
 
@@ -95,12 +105,17 @@ exec('git checkout ReactAndroid/gradle.properties');
 
 echo('Generated artifacts for Maven');
 
-let artifacts = ['-javadoc.jar', '-sources.jar', '.aar', '.pom'].map((suffix) => {
+let artifacts = ['-javadoc.jar', '-sources.jar', '.aar', '.pom'].map(suffix => {
   return `react-native-${releaseVersion}${suffix}`;
 });
 
-artifacts.forEach((name) => {
-  if (!test('-e', `./android/com/facebook/react/react-native/${releaseVersion}/${name}`)) {
+artifacts.forEach(name => {
+  if (
+    !test(
+      '-e',
+      `./android/com/facebook/react/react-native/${releaseVersion}/${name}`,
+    )
+  ) {
     echo(`file ${name} was not generated`);
     exit(1);
   }
diff --git a/scripts/run-android-ci-instrumentation-tests.js b/scripts/run-android-ci-instrumentation-tests.js
index 17d382a32e15..9a87de4f83ab 100644
--- a/scripts/run-android-ci-instrumentation-tests.js
+++ b/scripts/run-android-ci-instrumentation-tests.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -19,12 +21,7 @@
  * --retries [num] - how many times to retry possible flaky commands: npm install and running tests, default 1
  */
 
-const {
-   echo,
-   exec,
-   exit,
-   ls,
-} = require('shelljs');
+const {echo, exec, exit, ls} = require('shelljs');
 
 const argv = require('yargs').argv;
 const numberOfRetries = argv.retries || 1;
@@ -34,33 +31,39 @@ const path = require('path');
 // Flaky tests ignored on Circle CI. They still run internally at fb.
 const ignoredTests = [
   'ReactScrollViewTestCase',
-  'ReactHorizontalScrollViewTestCase'
+  'ReactHorizontalScrollViewTestCase',
 ];
 
 // ReactAndroid/src/androidTest/java/com/facebook/react/tests/ReactHorizontalScrollViewTestCase.java
 const testClasses = ls(`${argv.path}/*.java`)
-.map(javaFile => {
-  // ReactHorizontalScrollViewTestCase
-  return path.basename(javaFile, '.java');
-}).filter(className => {
-  return ignoredTests.indexOf(className) === -1;
-}).map(className => {
-  // com.facebook.react.tests.ReactHorizontalScrollViewTestCase
-  return argv.package + '.' + className;
-});
+  .map(javaFile => {
+    // ReactHorizontalScrollViewTestCase
+    return path.basename(javaFile, '.java');
+  })
+  .filter(className => {
+    return ignoredTests.indexOf(className) === -1;
+  })
+  .map(className => {
+    // com.facebook.react.tests.ReactHorizontalScrollViewTestCase
+    return argv.package + '.' + className;
+  });
 
 let exitCode = 0;
-testClasses.forEach((testClass) => {
-  if (tryExecNTimes(
-    () => {
+testClasses.forEach(testClass => {
+  if (
+    tryExecNTimes(() => {
       echo(`Starting ${testClass}`);
       // any faster means Circle CI crashes
       exec('sleep 10s');
-      return exec(`./scripts/run-instrumentation-tests-via-adb-shell.sh ${argv.package} ${testClass}`).code;
-    },
-    numberOfRetries)) {
-      echo(`${testClass} failed ${numberOfRetries} times`);
-      exitCode = 1;
+      return exec(
+        `./scripts/run-instrumentation-tests-via-adb-shell.sh ${
+          argv.package
+        } ${testClass}`,
+      ).code;
+    }, numberOfRetries)
+  ) {
+    echo(`${testClass} failed ${numberOfRetries} times`);
+    exitCode = 1;
   }
 });
 
diff --git a/scripts/run-ci-e2e-tests.js b/scripts/run-ci-e2e-tests.js
index cd1163f0ba24..f3096c083a28 100644
--- a/scripts/run-ci-e2e-tests.js
+++ b/scripts/run-ci-e2e-tests.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -32,8 +34,12 @@ const TEMP = exec('mktemp -d /tmp/react-native-XXXXXXXX').stdout.trim();
 // To make sure we actually installed the local version
 // of react-native, we will create a temp file inside the template
 // and check that it exists after `react-native init
-const MARKER_IOS = exec(`mktemp ${ROOT}/local-cli/templates/HelloWorld/ios/HelloWorld/XXXXXXXX`).stdout.trim();
-const MARKER_ANDROID = exec(`mktemp ${ROOT}/local-cli/templates/HelloWorld/android/XXXXXXXX`).stdout.trim();
+const MARKER_IOS = exec(
+  `mktemp ${ROOT}/local-cli/templates/HelloWorld/ios/HelloWorld/XXXXXXXX`,
+).stdout.trim();
+const MARKER_ANDROID = exec(
+  `mktemp ${ROOT}/local-cli/templates/HelloWorld/android/XXXXXXXX`,
+).stdout.trim();
 const numberOfRetries = argv.retries || 1;
 let SERVER_PID;
 let APPIUM_PID;
@@ -43,7 +49,11 @@ try {
   // install CLI
   cd('react-native-cli');
   exec('yarn pack');
-  const CLI_PACKAGE = path.join(ROOT, 'react-native-cli', 'react-native-cli-*.tgz');
+  const CLI_PACKAGE = path.join(
+    ROOT,
+    'react-native-cli',
+    'react-native-cli-*.tgz',
+  );
   cd('..');
 
   if (!argv['skip-cli-install']) {
@@ -56,7 +66,11 @@ try {
   }
 
   if (argv.android) {
-    if (exec('./gradlew :ReactAndroid:installArchives -Pjobs=1 -Dorg.gradle.jvmargs="-Xmx512m -XX:+HeapDumpOnOutOfMemoryError"').code) {
+    if (
+      exec(
+        './gradlew :ReactAndroid:installArchives -Pjobs=1 -Dorg.gradle.jvmargs="-Xmx512m -XX:+HeapDumpOnOutOfMemoryError"',
+      ).code
+    ) {
       echo('Failed to compile Android binaries');
       exitCode = 1;
       throw Error(exitCode);
@@ -71,17 +85,20 @@ try {
 
   const PACKAGE = path.join(ROOT, 'react-native-*.tgz');
   cd(TEMP);
-  if (tryExecNTimes(
-    () => {
-      exec('sleep 10s');
-      return exec(`react-native init EndToEndTest --version ${PACKAGE}`).code;
-    },
-    numberOfRetries,
-    () => rm('-rf', 'EndToEndTest'))) {
-      echo('Failed to execute react-native init');
-      echo('Most common reason is npm registry connectivity, try again');
-      exitCode = 1;
-      throw Error(exitCode);
+  if (
+    tryExecNTimes(
+      () => {
+        exec('sleep 10s');
+        return exec(`react-native init EndToEndTest --version ${PACKAGE}`).code;
+      },
+      numberOfRetries,
+      () => rm('-rf', 'EndToEndTest'),
+    )
+  ) {
+    echo('Failed to execute react-native init');
+    echo('Most common reason is npm registry connectivity, try again');
+    exitCode = 1;
+    throw Error(exitCode);
   }
 
   cd('EndToEndTest');
@@ -89,13 +106,20 @@ try {
   if (argv.android) {
     echo('Running an Android e2e test');
     echo('Installing e2e framework');
-    if (tryExecNTimes(
-      () => exec('yarn add --dev appium@1.5.1 mocha@2.4.5 wd@0.3.11 colors@1.0.3 pretty-data2@0.40.1', { silent: true }).code,
-      numberOfRetries)) {
-        echo('Failed to install appium');
-        echo('Most common reason is npm registry connectivity, try again');
-        exitCode = 1;
-        throw Error(exitCode);
+    if (
+      tryExecNTimes(
+        () =>
+          exec(
+            'yarn add --dev appium@1.5.1 mocha@2.4.5 wd@0.3.11 colors@1.0.3 pretty-data2@0.40.1',
+            {silent: true},
+          ).code,
+        numberOfRetries,
+      )
+    ) {
+      echo('Failed to install appium');
+      echo('Most common reason is npm registry connectivity, try again');
+      exitCode = 1;
+      throw Error(exitCode);
     }
     cp(`${SCRIPTS}/android-e2e-test.js`, 'android-e2e-test.js');
     cd('android');
@@ -108,7 +132,9 @@ try {
       throw Error(exitCode);
     }
     cd('..');
-    exec('keytool -genkey -v -keystore android/keystores/debug.keystore -storepass android -alias androiddebugkey -keypass android -dname "CN=Android Debug,O=Android,C=US"');
+    exec(
+      'keytool -genkey -v -keystore android/keystores/debug.keystore -storepass android -alias androiddebugkey -keypass android -dname "CN=Android Debug,O=Android,C=US"',
+    );
 
     echo(`Starting appium server, ${APPIUM_PID}`);
     const appiumProcess = spawn('node', ['./node_modules/.bin/appium']);
@@ -124,27 +150,27 @@ try {
     echo(`Starting packager server, ${SERVER_PID}`);
     // shelljs exec('', {async: true}) does not emit stdout events, so we rely on good old spawn
     const packagerProcess = spawn('yarn', ['start', '--max-workers 1'], {
-      env: process.env
+      env: process.env,
     });
     SERVER_PID = packagerProcess.pid;
     // wait a bit to allow packager to startup
     exec('sleep 15s');
     echo('Executing android e2e test');
-    if (tryExecNTimes(
-      () => {
+    if (
+      tryExecNTimes(() => {
         exec('sleep 10s');
         return exec('node node_modules/.bin/_mocha android-e2e-test.js').code;
-      },
-      numberOfRetries)) {
-        echo('Failed to run Android e2e tests');
-        echo('Most likely the code is broken');
-        exitCode = 1;
-        throw Error(exitCode);
+      }, numberOfRetries)
+    ) {
+      echo('Failed to run Android e2e tests');
+      echo('Most likely the code is broken');
+      exitCode = 1;
+      throw Error(exitCode);
     }
   }
 
   if (argv.ios || argv.tvos) {
-    var iosTestType = (argv.tvos ? 'tvOS' : 'iOS');
+    var iosTestType = argv.tvos ? 'tvOS' : 'iOS';
     echo('Running the ' + iosTestType + 'app');
     cd('ios');
     // Make sure we installed local version of react-native
@@ -156,43 +182,56 @@ try {
     // shelljs exec('', {async: true}) does not emit stdout events, so we rely on good old spawn
     const packagerEnv = Object.create(process.env);
     packagerEnv.REACT_NATIVE_MAX_WORKERS = 1;
-    const packagerProcess = spawn('yarn', ['start', '--nonPersistent'],
-      {
-        stdio: 'inherit',
-        env: packagerEnv
-      });
+    const packagerProcess = spawn('yarn', ['start', '--nonPersistent'], {
+      stdio: 'inherit',
+      env: packagerEnv,
+    });
     SERVER_PID = packagerProcess.pid;
     exec('sleep 15s');
     // prepare cache to reduce chances of possible red screen "Can't fibd variable __fbBatchedBridge..."
-    exec('response=$(curl --write-out %{http_code} --silent --output /dev/null localhost:8081/index.bundle?platform=ios&dev=true)');
+    exec(
+      'response=$(curl --write-out %{http_code} --silent --output /dev/null localhost:8081/index.bundle?platform=ios&dev=true)',
+    );
     echo(`Starting packager server, ${SERVER_PID}`);
     echo('Executing ' + iosTestType + ' e2e test');
-    if (tryExecNTimes(
-      () => {
+    if (
+      tryExecNTimes(() => {
         exec('sleep 10s');
         if (argv.tvos) {
-          return exec('xcodebuild -destination "platform=tvOS Simulator,name=Apple TV 1080p,OS=10.0" -scheme EndToEndTest-tvOS -sdk appletvsimulator test | xcpretty && exit ${PIPESTATUS[0]}').code;
+          return exec(
+            'xcodebuild -destination "platform=tvOS Simulator,name=Apple TV 1080p,OS=10.0" -scheme EndToEndTest-tvOS -sdk appletvsimulator test | xcpretty && exit ${PIPESTATUS[0]}',
+          ).code;
         } else {
-          return exec('xcodebuild -destination "platform=iOS Simulator,name=iPhone 5s,OS=10.3.1" -scheme EndToEndTest -sdk iphonesimulator test | xcpretty && exit ${PIPESTATUS[0]}').code;
+          return exec(
+            'xcodebuild -destination "platform=iOS Simulator,name=iPhone 5s,OS=10.3.1" -scheme EndToEndTest -sdk iphonesimulator test | xcpretty && exit ${PIPESTATUS[0]}',
+          ).code;
         }
-      },
-      numberOfRetries)) {
-        echo('Failed to run ' + iosTestType + ' e2e tests');
-        echo('Most likely the code is broken');
-        exitCode = 1;
-        throw Error(exitCode);
+      }, numberOfRetries)
+    ) {
+      echo('Failed to run ' + iosTestType + ' e2e tests');
+      echo('Most likely the code is broken');
+      exitCode = 1;
+      throw Error(exitCode);
     }
     cd('..');
   }
 
   if (argv.js) {
     // Check the packager produces a bundle (doesn't throw an error)
-    if (exec('react-native bundle --max-workers 1 --platform android --dev true --entry-file index.js --bundle-output android-bundle.js').code) {
+    if (
+      exec(
+        'react-native bundle --max-workers 1 --platform android --dev true --entry-file index.js --bundle-output android-bundle.js',
+      ).code
+    ) {
       echo('Could not build Android bundle');
       exitCode = 1;
       throw Error(exitCode);
     }
-    if (exec('react-native --max-workers 1 bundle --platform ios --dev true --entry-file index.js --bundle-output ios-bundle.js').code) {
+    if (
+      exec(
+        'react-native --max-workers 1 bundle --platform ios --dev true --entry-file index.js --bundle-output ios-bundle.js',
+      ).code
+    ) {
       echo('Could not build iOS bundle');
       exitCode = 1;
       throw Error(exitCode);
@@ -209,7 +248,6 @@ try {
     }
   }
   exitCode = 0;
-
 } finally {
   cd(ROOT);
   rm(MARKER_IOS);
diff --git a/scripts/try-n-times.js b/scripts/try-n-times.js
index 59abeca17317..1be7209360b6 100644
--- a/scripts/try-n-times.js
+++ b/scripts/try-n-times.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 /* globals echo:false */
diff --git a/setupBabel.js b/setupBabel.js
index 96b54429d7cf..7c6784f79018 100644
--- a/setupBabel.js
+++ b/setupBabel.js
@@ -3,6 +3,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 'use strict';
@@ -17,7 +19,9 @@ const BABEL_ENABLED_PATHS = ['local-cli'];
  * support Flow type annotations.
  */
 function setupBabel() {
-  babelRegisterOnly(babelRegisterOnly.buildRegExps(__dirname, BABEL_ENABLED_PATHS));
+  babelRegisterOnly(
+    babelRegisterOnly.buildRegExps(__dirname, BABEL_ENABLED_PATHS),
+  );
 }
 
 module.exports = setupBabel;

From 0e5c2633ee261d27c57e180494a2662a9f00dbc8 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 11 May 2018 13:32:39 -0700
Subject: [PATCH 0513/1109] Prettier files with shebang

Reviewed By: yungsters

Differential Revision: D7974564

fbshipit-source-id: 00db563ce24868c0fde117e981936b83cec30e48
---
 .../websocket_integration_test_server.js      |   5 +-
 RNTester/js/http_test_server.js               |   1 +
 RNTester/js/websocket_test_server.js          |   5 +-
 local-cli/wrong-react-native.js               |  23 ++--
 react-native-cli/index.js                     | 119 ++++++++++--------
 react-native-git-upgrade/index.js             |  43 ++++---
 scripts/bump-oss-version.js                   |  68 ++++++----
 7 files changed, 155 insertions(+), 109 deletions(-)

diff --git a/IntegrationTests/websocket_integration_test_server.js b/IntegrationTests/websocket_integration_test_server.js
index 763668f3275d..50a6568710a2 100755
--- a/IntegrationTests/websocket_integration_test_server.js
+++ b/IntegrationTests/websocket_integration_test_server.js
@@ -7,6 +7,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @format
  */
 'use strict';
 
@@ -26,8 +27,8 @@ An incoming message of 'exit' will shut down the server.
 `);
 
 const server = new WebSocket.Server({port: 5555});
-server.on('connection', (ws) => {
-  ws.on('message', (message) => {
+server.on('connection', ws => {
+  ws.on('message', message => {
     console.log('Received message:', message);
     if (message === 'exit') {
       console.log('WebSocket integration test server exit');
diff --git a/RNTester/js/http_test_server.js b/RNTester/js/http_test_server.js
index 998d73dbf194..c9a4be575394 100755
--- a/RNTester/js/http_test_server.js
+++ b/RNTester/js/http_test_server.js
@@ -6,6 +6,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @format
  */
 'use strict';
 
diff --git a/RNTester/js/websocket_test_server.js b/RNTester/js/websocket_test_server.js
index 3f3a23cfa04c..eacab9e21977 100755
--- a/RNTester/js/websocket_test_server.js
+++ b/RNTester/js/websocket_test_server.js
@@ -6,6 +6,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @flow
+ * @format
  */
 'use strict';
 
@@ -29,8 +30,8 @@ ArrayBuffer instead of a string.
 
 const respondWithBinary = process.argv.indexOf('--binary') !== -1;
 const server = new WebSocket.Server({port: 5555});
-server.on('connection', (ws) => {
-  ws.on('message', (message) => {
+server.on('connection', ws => {
+  ws.on('message', message => {
     console.log('Received message:', message);
     console.log('Cookie:', ws.upgradeReq.headers.cookie);
     if (respondWithBinary) {
diff --git a/local-cli/wrong-react-native.js b/local-cli/wrong-react-native.js
index 57f04feadc39..3b949818a05c 100755
--- a/local-cli/wrong-react-native.js
+++ b/local-cli/wrong-react-native.js
@@ -5,6 +5,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 const isWindows = process.platform === 'win32';
@@ -14,23 +16,28 @@ if (isWindows) {
   const fs = require('fs');
   const path = require('path');
   // On Windows, assume we are installed globally if we can't find a package.json above node_modules.
-  installedGlobally = !(fs.existsSync(path.join(__dirname, '../../../package.json')));
+  installedGlobally = !fs.existsSync(
+    path.join(__dirname, '../../../package.json'),
+  );
 } else {
   // On non-windows, assume we are installed globally if we are called from outside of the node_mobules/.bin/react-native executable.
   var script = process.argv[1];
   installedGlobally = script.indexOf('node_modules/.bin/react-native') === -1;
 }
 
-
 if (installedGlobally) {
   const chalk = require('chalk');
 
-  console.error([
-    chalk.red('Looks like you installed react-native globally, maybe you meant react-native-cli?'),
-    chalk.red('To fix the issue, run:'),
-    'npm uninstall -g react-native',
-    'npm install -g react-native-cli'
-  ].join('\n'));
+  console.error(
+    [
+      chalk.red(
+        'Looks like you installed react-native globally, maybe you meant react-native-cli?',
+      ),
+      chalk.red('To fix the issue, run:'),
+      'npm uninstall -g react-native',
+      'npm install -g react-native-cli',
+    ].join('\n'),
+  );
   process.exit(1);
 } else {
   require('./cli').run();
diff --git a/react-native-cli/index.js b/react-native-cli/index.js
index 5cde164967a7..fa83050700ce 100755
--- a/react-native-cli/index.js
+++ b/react-native-cli/index.js
@@ -5,6 +5,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
@@ -60,12 +62,7 @@ var semver = require('semver');
 var options = require('minimist')(process.argv.slice(2));
 
 var CLI_MODULE_PATH = function() {
-  return path.resolve(
-    process.cwd(),
-    'node_modules',
-    'react-native',
-    'cli.js'
-  );
+  return path.resolve(process.cwd(), 'node_modules', 'react-native', 'cli.js');
 };
 
 var REACT_NATIVE_PACKAGE_JSON_PATH = function() {
@@ -73,7 +70,7 @@ var REACT_NATIVE_PACKAGE_JSON_PATH = function() {
     process.cwd(),
     'node_modules',
     'react-native',
-    'package.json'
+    'package.json',
   );
 };
 
@@ -90,7 +87,9 @@ function getYarnVersionIfAvailable() {
     if (process.platform.startsWith('win')) {
       yarnVersion = (execSync('yarn --version 2> NUL').toString() || '').trim();
     } else {
-      yarnVersion = (execSync('yarn --version 2>/dev/null').toString() || '').trim();
+      yarnVersion = (
+        execSync('yarn --version 2>/dev/null').toString() || ''
+      ).trim();
     }
   } catch (error) {
     return null;
@@ -119,51 +118,51 @@ if (cli) {
   cli.run();
 } else {
   if (options._.length === 0 && (options.h || options.help)) {
-    console.log([
-      '',
-      '  Usage: react-native [command] [options]',
-      '',
-      '',
-      '  Commands:',
-      '',
-      '    init <ProjectName> [options]  generates a new project and installs its dependencies',
-      '',
-      '  Options:',
-      '',
-      '    -h, --help    output usage information',
-      '    -v, --version use a specific version of React Native',
-      '    --template use an app template. Use --template to see available templates.',
-      '',
-    ].join('\n'));
+    console.log(
+      [
+        '',
+        '  Usage: react-native [command] [options]',
+        '',
+        '',
+        '  Commands:',
+        '',
+        '    init <ProjectName> [options]  generates a new project and installs its dependencies',
+        '',
+        '  Options:',
+        '',
+        '    -h, --help    output usage information',
+        '    -v, --version use a specific version of React Native',
+        '    --template use an app template. Use --template to see available templates.',
+        '',
+      ].join('\n'),
+    );
     process.exit(0);
   }
 
   if (commands.length === 0) {
     console.error(
-      'You did not pass any commands, run `react-native --help` to see a list of all available commands.'
+      'You did not pass any commands, run `react-native --help` to see a list of all available commands.',
     );
     process.exit(1);
   }
 
   switch (commands[0]) {
-  case 'init':
-    if (!commands[1]) {
+    case 'init':
+      if (!commands[1]) {
+        console.error('Usage: react-native init <ProjectName> [--verbose]');
+        process.exit(1);
+      } else {
+        init(commands[1], options);
+      }
+      break;
+    default:
       console.error(
-        'Usage: react-native init <ProjectName> [--verbose]'
+        'Command `%s` unrecognized. ' +
+          'Make sure that you have run `npm install` and that you are inside a react-native project.',
+        commands[0],
       );
       process.exit(1);
-    } else {
-      init(commands[1], options);
-    }
-    break;
-  default:
-    console.error(
-      'Command `%s` unrecognized. ' +
-      'Make sure that you have run `npm install` and that you are inside a react-native project.',
-      commands[0]
-    );
-    process.exit(1);
-    break;
+      break;
   }
 }
 
@@ -172,7 +171,7 @@ function validateProjectName(name) {
     console.error(
       '"%s" is not a valid name for a project. Please use a valid identifier ' +
         'name (alphanumeric).',
-      name
+      name,
     );
     process.exit(1);
   }
@@ -181,7 +180,7 @@ function validateProjectName(name) {
     console.error(
       '"%s" is not a valid name for a project. Please do not use the ' +
         'reserved word "React".',
-      name
+      name,
     );
     process.exit(1);
   }
@@ -212,10 +211,10 @@ function createAfterConfirmation(name, options) {
     message: 'Directory ' + name + ' already exists. Continue?',
     validator: /y[es]*|n[o]?/,
     warning: 'Must respond yes or no',
-    default: 'no'
+    default: 'no',
   };
 
-  prompt.get(property, function (err, result) {
+  prompt.get(property, function(err, result) {
     if (result.yesno[0] === 'y') {
       createProject(name, options);
     } else {
@@ -231,7 +230,7 @@ function createProject(name, options) {
 
   console.log(
     'This will walk you through creating a new React Native project in',
-    root
+    root,
   );
 
   if (!fs.existsSync(root)) {
@@ -246,9 +245,12 @@ function createProject(name, options) {
       start: 'node node_modules/react-native/local-cli/cli.js start',
       ios: 'react-native run-ios',
       android: 'react-native run-android',
-    }
+    },
   };
-  fs.writeFileSync(path.join(root, 'package.json'), JSON.stringify(packageJson));
+  fs.writeFileSync(
+    path.join(root, 'package.json'),
+    JSON.stringify(packageJson),
+  );
   process.chdir(root);
 
   run(root, projectName, options);
@@ -269,7 +271,7 @@ function getInstallPackage(rnPackage) {
 function run(root, projectName, options) {
   var rnPackage = options.version; // e.g. '0.38' or '/path/to/archive.tgz'
   var forceNpmClient = options.npm;
-  var yarnVersion = (!forceNpmClient) && getYarnVersionIfAvailable();
+  var yarnVersion = !forceNpmClient && getYarnVersionIfAvailable();
   var installCommand;
   if (options.installCommand) {
     // In CI environments it can be useful to provide a custom command,
@@ -286,9 +288,12 @@ function run(root, projectName, options) {
     } else {
       console.log('Installing ' + getInstallPackage(rnPackage) + '...');
       if (!forceNpmClient) {
-        console.log('Consider installing yarn to make this faster: https://yarnpkg.com');
+        console.log(
+          'Consider installing yarn to make this faster: https://yarnpkg.com',
+        );
       }
-      installCommand = 'npm install --save --save-exact ' + getInstallPackage(rnPackage);
+      installCommand =
+        'npm install --save --save-exact ' + getInstallPackage(rnPackage);
       if (options.verbose) {
         installCommand += ' --verbose';
       }
@@ -312,13 +317,15 @@ function checkNodeVersion() {
     return;
   }
   if (!semver.satisfies(process.version, packageJson.engines.node)) {
-    console.error(chalk.red(
+    console.error(
+      chalk.red(
         'You are currently running Node %s but React Native requires %s. ' +
-        'Please use a supported version of Node.\n' +
-        'See https://facebook.github.io/react-native/docs/getting-started.html'
+          'Please use a supported version of Node.\n' +
+          'See https://facebook.github.io/react-native/docs/getting-started.html',
       ),
       process.version,
-      packageJson.engines.node);
+      packageJson.engines.node,
+    );
   }
 }
 
@@ -327,7 +334,9 @@ function printVersionsAndExit(reactNativePackageJsonPath) {
   try {
     console.log('react-native: ' + require(reactNativePackageJsonPath).version);
   } catch (e) {
-    console.log('react-native: n/a - not inside a React Native project directory');
+    console.log(
+      'react-native: n/a - not inside a React Native project directory',
+    );
   }
   process.exit();
 }
diff --git a/react-native-git-upgrade/index.js b/react-native-git-upgrade/index.js
index dea50c344e9a..c5e927312507 100644
--- a/react-native-git-upgrade/index.js
+++ b/react-native-git-upgrade/index.js
@@ -5,30 +5,34 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 
 var argv = require('minimist')(process.argv.slice(2));
 var cli = require('./cli');
 
 if (argv._.length === 0 && (argv.h || argv.help)) {
-  console.log([
-    '',
-    '  Usage: react-native-git-upgrade [version] [options]',
-    '',
-    '',
-    '  Commands:',
-    '',
-    '    [Version]     upgrades React Native and app templates to the desired version',
-    '                  (latest, if not specified)',
-    '',
-    '  Options:',
-    '',
-    '    -h, --help    output usage information',
-    '    -v, --version output the version number',
-    '    --verbose output debugging info',
-    '    --npm force using the npm client even if your project uses yarn',
-    '',
-  ].join('\n'));
+  console.log(
+    [
+      '',
+      '  Usage: react-native-git-upgrade [version] [options]',
+      '',
+      '',
+      '  Commands:',
+      '',
+      '    [Version]     upgrades React Native and app templates to the desired version',
+      '                  (latest, if not specified)',
+      '',
+      '  Options:',
+      '',
+      '    -h, --help    output usage information',
+      '    -v, --version output the version number',
+      '    --verbose output debugging info',
+      '    --npm force using the npm client even if your project uses yarn',
+      '',
+    ].join('\n'),
+  );
   process.exit(0);
 }
 
@@ -37,5 +41,4 @@ if (argv._.length === 0 && (argv.v || argv.version)) {
   process.exit(0);
 }
 
-cli.run(argv._[0], argv)
-  .catch(console.error);
+cli.run(argv._[0], argv).catch(console.error);
diff --git a/scripts/bump-oss-version.js b/scripts/bump-oss-version.js
index 11ac0f940e0f..6af9eb22706e 100755
--- a/scripts/bump-oss-version.js
+++ b/scripts/bump-oss-version.js
@@ -4,6 +4,8 @@
  *
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
+ *
+ * @format
  */
 'use strict';
 
@@ -14,13 +16,7 @@
  * All you have to do is push changes to remote and CI will make a new build.
  */
 const fs = require('fs');
-const {
-  cat,
-  echo,
-  exec,
-  exit,
-  sed,
-} = require('shelljs');
+const {cat, echo, exec, exit, sed} = require('shelljs');
 
 const minimist = require('minimist');
 
@@ -30,7 +26,9 @@ let argv = minimist(process.argv.slice(2), {
 });
 
 // - check we are in release branch, e.g. 0.33-stable
-let branch = exec('git symbolic-ref --short HEAD', {silent: true}).stdout.trim();
+let branch = exec('git symbolic-ref --short HEAD', {
+  silent: true,
+}).stdout.trim();
 
 if (branch.indexOf('-stable') === -1) {
   echo('You must be in 0.XX-stable branch to bump a version');
@@ -44,14 +42,18 @@ let versionMajor = branch.slice(0, branch.indexOf('-stable'));
 // e.g. 0.33.1 or 0.33.0-rc4
 let version = argv._[0];
 if (!version || version.indexOf(versionMajor) !== 0) {
-  echo(`You must pass a tag like 0.${versionMajor}.[X]-rc[Y] to bump a version`);
+  echo(
+    `You must pass a tag like 0.${versionMajor}.[X]-rc[Y] to bump a version`,
+  );
   exit(1);
 }
 
 // Generate version files to detect mismatches between JS and native.
 let match = version.match(/^(\d+)\.(\d+)\.(\d+)(?:-(.+))?$/);
 if (!match) {
-  echo(`You must pass a correctly formatted version; couldn't parse ${version}`);
+  echo(
+    `You must pass a correctly formatted version; couldn't parse ${version}`,
+  );
   exit(1);
 }
 let [, major, minor, patch, prerelease] = match;
@@ -62,8 +64,11 @@ fs.writeFileSync(
     .replace('${major}', major)
     .replace('${minor}', minor)
     .replace('${patch}', patch)
-    .replace('${prerelease}', prerelease !== undefined ? `"${prerelease}"` : 'null'),
-  'utf-8'
+    .replace(
+      '${prerelease}',
+      prerelease !== undefined ? `"${prerelease}"` : 'null',
+    ),
+  'utf-8',
 );
 
 fs.writeFileSync(
@@ -72,8 +77,11 @@ fs.writeFileSync(
     .replace('${major}', `@(${major})`)
     .replace('${minor}', `@(${minor})`)
     .replace('${patch}', `@(${patch})`)
-    .replace('${prerelease}', prerelease !== undefined ? `@"${prerelease}"` : '[NSNull null]'),
-  'utf-8'
+    .replace(
+      '${prerelease}',
+      prerelease !== undefined ? `@"${prerelease}"` : '[NSNull null]',
+    ),
+  'utf-8',
 );
 
 fs.writeFileSync(
@@ -82,8 +90,11 @@ fs.writeFileSync(
     .replace('${major}', major)
     .replace('${minor}', minor)
     .replace('${patch}', patch)
-    .replace('${prerelease}', prerelease !== undefined ? `'${prerelease}'` : 'null'),
-  'utf-8'
+    .replace(
+      '${prerelease}',
+      prerelease !== undefined ? `'${prerelease}'` : 'null',
+    ),
+  'utf-8',
 );
 
 let packageJson = JSON.parse(cat('package.json'));
@@ -91,16 +102,27 @@ packageJson.version = version;
 fs.writeFileSync('package.json', JSON.stringify(packageJson, null, 2), 'utf-8');
 
 // - change ReactAndroid/gradle.properties
-if (sed('-i', /^VERSION_NAME=.*/, `VERSION_NAME=${version}`, 'ReactAndroid/gradle.properties').code) {
-  echo('Couldn\'t update version for Gradle');
+if (
+  sed(
+    '-i',
+    /^VERSION_NAME=.*/,
+    `VERSION_NAME=${version}`,
+    'ReactAndroid/gradle.properties',
+  ).code
+) {
+  echo("Couldn't update version for Gradle");
   exit(1);
 }
 
 // verify that files changed, we just do a git diff and check how many times version is added across files
-let numberOfChangedLinesWithNewVersion = exec(`git diff -U0 | grep '^[+]' | grep -c ${version} `, {silent: true})
-  .stdout.trim();
+let numberOfChangedLinesWithNewVersion = exec(
+  `git diff -U0 | grep '^[+]' | grep -c ${version} `,
+  {silent: true},
+).stdout.trim();
 if (+numberOfChangedLinesWithNewVersion !== 2) {
-  echo('Failed to update all the files. package.json and gradle.properties must have versions in them');
+  echo(
+    'Failed to update all the files. package.json and gradle.properties must have versions in them',
+  );
   echo('Fix the issue, revert and try again');
   exec('git diff');
   exit(1);
@@ -114,7 +136,9 @@ if (exec(`git commit -a -m "[${version}] Bump version numbers"`).code) {
 
 // - add tag v0.21.0-rc
 if (exec(`git tag v${version}`).code) {
-  echo(`failed to tag the commit with v${version}, are you sure this release wasn't made earlier?`);
+  echo(
+    `failed to tag the commit with v${version}, are you sure this release wasn't made earlier?`,
+  );
   echo('You may want to rollback the last commit');
   echo('git reset --hard HEAD~1');
   exit(1);

From 8125be942bd5fd8fe851bad04ae6b9bcb0af4727 Mon Sep 17 00:00:00 2001
From: Mehdi Mulani <mehdi@fb.com>
Date: Fri, 11 May 2018 14:13:24 -0700
Subject: [PATCH 0514/1109] Reland prevent console logging on iOS 11.3+ within
 WebSocket

Reviewed By: shergin

Differential Revision: D7953765

fbshipit-source-id: 6b259d10c719e9ad6b2cfdbf1ebb883dacf08353
---
 .../WebSocket/RCTReconnectingWebSocket.m      | 32 +++++++++++++++++--
 1 file changed, 30 insertions(+), 2 deletions(-)

diff --git a/Libraries/WebSocket/RCTReconnectingWebSocket.m b/Libraries/WebSocket/RCTReconnectingWebSocket.m
index 04e5dee57b67..c0f0988cf72e 100644
--- a/Libraries/WebSocket/RCTReconnectingWebSocket.m
+++ b/Libraries/WebSocket/RCTReconnectingWebSocket.m
@@ -11,14 +11,37 @@
 #import <React/RCTDefines.h>
 #import <fishhook/fishhook.h>
 
-#if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
+#if __has_include(<os/log.h>) && defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 100300 /* __IPHONE_10_3 */
 #import <os/log.h>
-#endif /* __IPHONE_11_0 */
+#endif /* __IPHONE_10_3 */
 
 #import "RCTSRWebSocket.h"
 
 #if RCT_DEV // Only supported in dev mode
 
+#if __has_include(<os/log.h>) && defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 100300 /* __IPHONE_10_3 */
+
+// From https://github.com/apple/swift/blob/ad40c770bfe372f879b530443a3d94761fe258a6/stdlib/public/SDK/os/os_log.m
+typedef struct os_log_pack_s {
+  uint64_t olp_continuous_time;
+  struct timespec olp_wall_time;
+  const void *olp_mh;
+  const void *olp_pc;
+  const char *olp_format;
+  uint8_t olp_data[0];
+} os_log_pack_s, *os_log_pack_t;
+
+static void (*orig__nwlog_pack)(os_log_pack_t pack, os_log_type_t logType);
+
+static void my__nwlog_pack(os_log_pack_t pack, os_log_type_t logType)
+{
+  if (logType == OS_LOG_TYPE_ERROR && strstr(pack->olp_format, "Connection has no connected handler") == NULL) {
+    orig__nwlog_pack(pack, logType);
+  }
+}
+
+#endif /* __IPHONE_10_3 */
+
 static void (*orig_nwlog_legacy_v)(int, char*, va_list);
 
 static void my_nwlog_legacy_v(int level, char *format, va_list args) {
@@ -63,6 +86,11 @@ + (void)load
     rebind_symbols((struct rebinding[1]){
       {"nwlog_legacy_v", my_nwlog_legacy_v, (void *)&orig_nwlog_legacy_v}
     }, 1);
+#if __has_include(<os/log.h>) && defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 100300 /* __IPHONE_10_3 */
+    rebind_symbols((struct rebinding[1]){
+      {"__nwlog_pack", my__nwlog_pack, (void *)&orig__nwlog_pack}
+    }, 1);
+#endif /* __IPHONE_10_3 */
 #if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
     rebind_symbols((struct rebinding[1]){
       {"_os_log_error_impl", my_os_log_error_impl, (void *)&orig_os_log_error_impl}

From b762f5293ede2d92161b61a087e7671dc6233cde Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 11 May 2018 15:05:15 -0700
Subject: [PATCH 0515/1109] Decouple the Worker options from the Babel
 Transformer options

Reviewed By: jeanlauliac

Differential Revision: D7894079

fbshipit-source-id: 40cbd991690f25f8c0f045c42a0105d74d516803
---
 jest/preprocessor.js | 2 --
 1 file changed, 2 deletions(-)

diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index a2854943d952..e2796fcf5f61 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -49,11 +49,9 @@ module.exports = {
       filename: file,
       localPath: file,
       options: {
-        assetDataPlugins: [],
         ast: true, // needed for open source (?) https://github.com/facebook/react-native/commit/f8d6b97140cffe8d18b2558f94570c8d1b410d5c#r28647044
         dev: true,
         inlineRequires: true,
-        minify: false,
         platform: '',
         projectRoot: '',
         retainLines: true,

From 75ff136f036fd4ded267b0262db1defff1542a97 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 11 May 2018 17:09:14 -0700
Subject: [PATCH 0516/1109] Load 'ReactFabric' only when it is required to
 render a Fabric component

Reviewed By: yungsters

Differential Revision: D7970603

fbshipit-source-id: 34676b9e174bc1e1141f4f435aa2c8e2b62cd5b9
---
 Libraries/ReactNative/renderApplication.js | 6 ++----
 1 file changed, 2 insertions(+), 4 deletions(-)

diff --git a/Libraries/ReactNative/renderApplication.js b/Libraries/ReactNative/renderApplication.js
index 42e9673dbc48..7d699f754651 100644
--- a/Libraries/ReactNative/renderApplication.js
+++ b/Libraries/ReactNative/renderApplication.js
@@ -12,8 +12,6 @@
 
 const AppContainer = require('AppContainer');
 const React = require('React');
-const ReactFabric = require('ReactFabric');
-const ReactNative = require('ReactNative');
 
 const invariant = require('fbjs/lib/invariant');
 
@@ -51,9 +49,9 @@ function renderApplication<Props: Object>(
   }
 
   if (fabric) {
-    ReactFabric.render(renderable, rootTag);
+    require('ReactFabric').render(renderable, rootTag);
   } else {
-    ReactNative.render(renderable, rootTag);
+    require('ReactNative').render(renderable, rootTag);
   }
 }
 

From c1e6f278237e84c8ed26d3d2eb45035f250e2d40 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Fri, 11 May 2018 17:24:00 -0700
Subject: [PATCH 0517/1109] Bump to Node 8

Summary:
Moving to Node 8 in React Native will allow us to be consistent with Facebook, e.g. trailing commas.

As of April 30, Node 4.x is end of life, and Node 6.x entered maintenance mode (see https://medium.com/the-node-js-collection/april-2018-release-updates-from-the-node-js-project-71687e1f7742).

This will require our docs to be updated to require Node 8 as a minimum. This should be done as part of the following PR: https://github.com/facebook/react-native-website/pull/355

Circle CI already runs all JS tests using Node 8, and it has an extra compatibility check that uses Node 6. This workflow is dropped as we no longer need to check for failures when Node 6 is used.

See https://github.com/facebook/react-native/issues/19226

[GENERAL] [BREAKING] [Node] - Bump minimum req. Node version to 8
Closes https://github.com/facebook/react-native/pull/19230

Differential Revision: D7979478

Pulled By: hramos

fbshipit-source-id: c91ec118f0a59c4daae5fcdbfc822ccead591304
---
 .circleci/config.yml                 | 22 ----------------------
 local-cli/server/checkNodeVersion.js |  6 +++---
 package.json                         |  2 +-
 3 files changed, 4 insertions(+), 26 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 23c9472731c6..52bb45540cd1 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -365,24 +365,6 @@ jobs:
       - store_test_results:
           path: ~/react-native/reports/junit
 
-  # Runs JavaScript tests on Node 6
-  test_javascript_node6_compatibility:
-    <<: *defaults
-    docker:
-      - image: circleci/node:6
-    steps:
-      - checkout
-      - run: *setup-artifacts
-
-      - restore-cache: *restore-cache-yarn
-      - run: *yarn
-      - save-cache: *save-cache-yarn
-
-      - run: *run-js-tests
-
-      - store_test_results:
-          path: ~/react-native/reports/junit
-
   # Runs unit tests on iOS devices
   test_ios:
     <<: *macos_defaults
@@ -624,10 +606,6 @@ workflows:
           requires:
             - checkout_code
 
-      # Test JavaScript using Node 6, the minimum supported version
-      - test_javascript_node6_compatibility:
-          filters: *filter-ignore-gh-pages
-
       # Test Android
       - test_android:
           filters: *filter-ignore-gh-pages
diff --git a/local-cli/server/checkNodeVersion.js b/local-cli/server/checkNodeVersion.js
index 8917be55c65c..7eb55a6d87d7 100644
--- a/local-cli/server/checkNodeVersion.js
+++ b/local-cli/server/checkNodeVersion.js
@@ -14,7 +14,7 @@ var formatBanner = require('metro-core/src/formatBanner');
 var semver = require('semver');
 
 module.exports = function() {
-  if (!semver.satisfies(process.version, '>=4')) {
+  if (!semver.satisfies(process.version, '>=8')) {
     var engine = semver.satisfies(process.version, '<1') ? 'Node' : 'io.js';
 
     var message =
@@ -24,7 +24,7 @@ module.exports = function() {
       process.version +
       '.\n' +
       '\n' +
-      'React Native runs on Node 4.0 or newer. There are several ways to ' +
+      'React Native runs on Node 8.0 or newer. There are several ways to ' +
       'upgrade Node.js depending on your preference.\n' +
       '\n' +
       'nvm:       nvm install node && nvm alias default node\n' +
@@ -32,7 +32,7 @@ module.exports = function() {
       'Installer: download the Mac .pkg from https://nodejs.org/\n' +
       '\n' +
       'About Node.js:   https://nodejs.org\n' +
-      'Follow along at: https://github.com/facebook/react-native/issues/2545';
+      'Follow along at: https://github.com/facebook/react-native/issues/19226';
     console.log(
       formatBanner(message, {
         chalkFunction: chalk.green,
diff --git a/package.json b/package.json
index f345d3909531..c37b2724d34c 100644
--- a/package.json
+++ b/package.json
@@ -8,7 +8,7 @@
     "url": "git@github.com:facebook/react-native.git"
   },
   "engines": {
-    "node": ">=4"
+    "node": ">=8"
   },
   "prettier": {
     "requirePragma": true,

From 4767f9be455cc32f89fb7ccf9030f007e7462014 Mon Sep 17 00:00:00 2001
From: Panagiotis Vekris <pvekris@fb.com>
Date: Fri, 11 May 2018 17:44:27 -0700
Subject: [PATCH 0518/1109] v0.72.0 in xplat/js

Reviewed By: gabelevi

Differential Revision: D7956747

fbshipit-source-id: b1993de405c273b3cc1ed74f994e8e75bda0a985
---
 .flowconfig                                | 2 +-
 Libraries/ReactNative/AppContainer.js      | 3 ---
 local-cli/templates/HelloWorld/_flowconfig | 2 +-
 package.json                               | 2 +-
 4 files changed, 3 insertions(+), 6 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index aea408653180..e5367e543cda 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -69,4 +69,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.71.0
+^0.72.0
diff --git a/Libraries/ReactNative/AppContainer.js b/Libraries/ReactNative/AppContainer.js
index 8cdbd6dec15c..fde991045d69 100644
--- a/Libraries/ReactNative/AppContainer.js
+++ b/Libraries/ReactNative/AppContainer.js
@@ -102,9 +102,6 @@ class AppContainer extends React.Component<Props, State> {
         pointerEvents="box-none"
         style={styles.appContainer}
         ref={ref => {
-          /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-           * comment suppresses an error when upgrading Flow's support for
-           * React. To see the error delete this comment and run Flow. */
           this._mainRef = ref;
         }}>
         {this.props.children}
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 187b25e48158..83ff2c6bd64f 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -51,4 +51,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.71.0
+^0.72.0
diff --git a/package.json b/package.json
index c37b2724d34c..412789dba0e4 100644
--- a/package.json
+++ b/package.json
@@ -213,7 +213,7 @@
     "eslint-plugin-jest": "21.8.0",
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
-    "flow-bin": "^0.71.0",
+    "flow-bin": "^0.72.0",
     "jest": "23.0.0-charlie.1",
     "jest-junit": "3.7.0",
     "prettier": "1.12.1",

From dbc9364b2142c4ad908d7d30a15361f113bb429b Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 11 May 2018 19:12:18 -0700
Subject: [PATCH 0519/1109] Fabric FB4A integration

Reviewed By: fkgozali

Differential Revision: D7953706

fbshipit-source-id: 406f8340eb3706dc07dcd32dcfaa5bdc06981aa1
---
 .../react/testing/ReactAppTestActivity.java   |  2 +-
 .../facebook/react/ReactInstanceManager.java  |  1 -
 .../react/ReactInstanceManagerBuilder.java    |  2 +-
 .../react/bridge/JSIModuleRegistry.java       | 20 ++++++++++++++++---
 4 files changed, 19 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index de18fad93e27..307caf3c0170 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -262,7 +262,7 @@ public Class<? extends JSIModule> getJSIModuleClass() {
                       @Override
                       public FabricUIManager getJSIModule() {
                         List<ViewManager> viewManagers =
-                            getReactInstanceManager().getOrCreateViewManagers(reactApplicationContext);
+                          getReactInstanceManager().getOrCreateViewManagers(reactApplicationContext);
                         FabricUIManager fabricUIManager =
                             new FabricUIManager(
                                 reactApplicationContext, new ViewManagerRegistry(viewManagers));
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 24a57c759b15..9687065e2501 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -85,7 +85,6 @@
 import com.facebook.soloader.SoLoader;
 import com.facebook.systrace.Systrace;
 import com.facebook.systrace.SystraceMessage;
-
 import java.util.ArrayList;
 import java.util.Collection;
 import java.util.Collections;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
index a0f4438330e6..0b6454086ace 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
@@ -281,6 +281,6 @@ public ReactInstanceManager build() {
         mDevBundleDownloadListener,
         mMinNumShakes,
         mMinTimeLeftInFrameForNonBatchedOperationMs,
-      mJSIModulesProvider);
+        mJSIModulesProvider);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
index 913aae68bcbf..7d4e1141bcad 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
@@ -1,23 +1,37 @@
 package com.facebook.react.bridge;
 
+import com.facebook.infer.annotation.Assertions;
+import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
-import com.facebook.infer.annotation.Assertions;
 
 public class JSIModuleRegistry {
 
+  private final List<JSIModuleHolder> mModuleList = new ArrayList<>();
   private final Map<Class, JSIModule> mModules = new HashMap<>();
+  private volatile boolean mIsInitialized = false;
 
   public JSIModuleRegistry() { }
 
   public <T extends JSIModule> T getModule(Class<T> moduleClass) {
+    JSIModule jsiModule = mModules.get(moduleClass);
+    if (jsiModule == null) {
+      initModules();
+    }
     return (T) Assertions.assertNotNull(mModules.get(moduleClass));
   }
 
   public void registerModules(List<JSIModuleHolder> jsiModules) {
-    for (JSIModuleHolder holder : jsiModules) {
-      mModules.put(holder.getJSIModuleClass(), holder.getJSIModule());
+    mModuleList.addAll(jsiModules);
+  }
+
+  public synchronized void initModules() {
+    if (!mIsInitialized) {
+      for (JSIModuleHolder holder : mModuleList) {
+        mModules.put(holder.getJSIModuleClass(), holder.getJSIModule());
+      }
+      mIsInitialized = true;
     }
   }
 }

From bc658d3c4405676643d952a126295dbc7fc26217 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:01 -0700
Subject: [PATCH 0520/1109] Spread TVViewProps into ViewProps instead of
 intersection

Reviewed By: yungsters

Differential Revision: D7976556

fbshipit-source-id: ca2f6bcac249a937523c4b50add8960085a8be49
---
 Libraries/Components/AppleTV/TVViewPropTypes.js | 4 ++--
 Libraries/Components/View/ViewPropTypes.js      | 8 +++++---
 2 files changed, 7 insertions(+), 5 deletions(-)

diff --git a/Libraries/Components/AppleTV/TVViewPropTypes.js b/Libraries/Components/AppleTV/TVViewPropTypes.js
index 656450df247a..5bda1f618c54 100644
--- a/Libraries/Components/AppleTV/TVViewPropTypes.js
+++ b/Libraries/Components/AppleTV/TVViewPropTypes.js
@@ -71,7 +71,7 @@ const TVViewPropTypes = {
   tvParallaxMagnification: PropTypes.number,
 };
 
-export type TVViewProps = {
+export type TVViewProps = $ReadOnly<{|
   isTVSelectable?: boolean,
   hasTVPreferredFocus?: boolean,
   tvParallaxProperties?: Object,
@@ -79,6 +79,6 @@ export type TVViewProps = {
   tvParallaxShiftDistanceY?: number,
   tvParallaxTiltAngle?: number,
   tvParallaxMagnification?: number,
-};
+|}>;
 
 module.exports = TVViewPropTypes;
diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 946368f267de..61406b2ca4f6 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -35,9 +35,11 @@ const stylePropType = StyleSheetPropType(ViewStylePropTypes);
 export type ViewLayout = Layout;
 export type ViewLayoutEvent = LayoutEvent;
 
-// There's no easy way to create a different type if (Platform.isTVOS):
-// so we must include TVViewProps
 export type ViewProps = {
+  // There's no easy way to create a different type if (Platform.isTVOS):
+  // so we must include TVViewProps
+  ...TVViewProps,
+
   accessible?: boolean,
   accessibilityLabel?:
     | null
@@ -77,7 +79,7 @@ export type ViewProps = {
   shouldRasterizeIOS?: boolean,
   collapsable?: boolean,
   needsOffscreenAlphaCompositing?: boolean,
-} & TVViewProps;
+};
 
 module.exports = {
   /**

From 65c336f38f4afd43c8b5f81745abf38bd9b8ddbf Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:03 -0700
Subject: [PATCH 0521/1109] Make ViewProps Exact

Reviewed By: yungsters

Differential Revision: D7976755

fbshipit-source-id: f6a0da1023a9235763c7ecb3ca7a9238887d0471
---
 .../MaskedView/MaskedViewIOS.ios.js           |  4 ++-
 .../Components/TabBarIOS/TabBarIOS.ios.js     | 27 ++++++++++---------
 Libraries/Components/View/ViewPropTypes.js    |  4 +--
 3 files changed, 19 insertions(+), 16 deletions(-)

diff --git a/Libraries/Components/MaskedView/MaskedViewIOS.ios.js b/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
index 9f24f4edcf8c..b0d1ab490a98 100644
--- a/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
+++ b/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
@@ -17,7 +17,9 @@ const requireNativeComponent = require('requireNativeComponent');
 
 import type {ViewProps} from 'ViewPropTypes';
 
-type Props = ViewProps & {
+type Props = {
+  ...ViewProps,
+
   children: any,
   /**
    * Should be a React element to be rendered and applied as the
diff --git a/Libraries/Components/TabBarIOS/TabBarIOS.ios.js b/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
index 686483f3b232..42d6cb238e90 100644
--- a/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
+++ b/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
@@ -22,19 +22,20 @@ const requireNativeComponent = require('requireNativeComponent');
 import type {DangerouslyImpreciseStyleProp} from 'StyleSheet';
 import type {ViewProps} from 'ViewPropTypes';
 
-class TabBarIOS extends React.Component<
-  ViewProps & {
-    style?: DangerouslyImpreciseStyleProp,
-    unselectedTintColor?: string,
-    tintColor?: string,
-    unselectedItemTintColor?: string,
-    barTintColor?: string,
-    barStyle?: 'default' | 'black',
-    translucent?: boolean,
-    itemPositioning?: 'fill' | 'center' | 'auto',
-    children: React.Node,
-  },
-> {
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  style?: DangerouslyImpreciseStyleProp,
+  unselectedTintColor?: string,
+  tintColor?: string,
+  unselectedItemTintColor?: string,
+  barTintColor?: string,
+  barStyle?: 'default' | 'black',
+  translucent?: boolean,
+  itemPositioning?: 'fill' | 'center' | 'auto',
+  children: React.Node,
+|}>;
+
+class TabBarIOS extends React.Component<Props> {
   static Item = TabBarItemIOS;
 
   static propTypes = {
diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 61406b2ca4f6..1d5f193c62de 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -35,7 +35,7 @@ const stylePropType = StyleSheetPropType(ViewStylePropTypes);
 export type ViewLayout = Layout;
 export type ViewLayoutEvent = LayoutEvent;
 
-export type ViewProps = {
+export type ViewProps = $ReadOnly<{|
   // There's no easy way to create a different type if (Platform.isTVOS):
   // so we must include TVViewProps
   ...TVViewProps,
@@ -79,7 +79,7 @@ export type ViewProps = {
   shouldRasterizeIOS?: boolean,
   collapsable?: boolean,
   needsOffscreenAlphaCompositing?: boolean,
-};
+|}>;
 
 module.exports = {
   /**

From 7ba7acdee73cc0e8a490c38e4d8afe63de590368 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:05 -0700
Subject: [PATCH 0522/1109] Surfacing Flow issues around invalid props

Reviewed By: yungsters

Differential Revision: D7977386

fbshipit-source-id: a6df2d75e0caa55a84f9c9c6860f622942955dfc
---
 Libraries/Components/ScrollView/ScrollView.js | 3 +++
 Libraries/Lists/MetroListView.js              | 2 +-
 Libraries/StyleSheet/EdgeInsetsPropType.js    | 6 ++----
 Libraries/StyleSheet/PointPropType.js         | 4 +---
 RNTester/js/ScrollViewExample.js              | 2 +-
 5 files changed, 8 insertions(+), 9 deletions(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 4b9aa3cff4f5..0154932f243a 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -237,6 +237,7 @@ const ScrollView = createReactClass({
      *   - `false`, deprecated, use 'never' instead
      *   - `true`, deprecated, use 'always' instead
      */
+    // $FlowFixMe
     keyboardShouldPersistTaps: PropTypes.oneOf([
       'always',
       'never',
@@ -521,9 +522,11 @@ const ScrollView = createReactClass({
 
   UNSAFE_componentWillMount: function() {
     this._scrollAnimatedValue = new AnimatedImplementation.Value(
+      // $FlowFixMe
       this.props.contentOffset ? this.props.contentOffset.y : 0,
     );
     this._scrollAnimatedValue.setOffset(
+      // $FlowFixMe
       this.props.contentInset ? this.props.contentInset.top : 0,
     );
     this._stickyHeaderRefs = new Map();
diff --git a/Libraries/Lists/MetroListView.js b/Libraries/Lists/MetroListView.js
index f2447760f9ee..fbf6b5554f72 100644
--- a/Libraries/Lists/MetroListView.js
+++ b/Libraries/Lists/MetroListView.js
@@ -146,7 +146,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
       />
     );
   }
-  _listRef: ListView;
+  _listRef: ?ListView;
   _captureRef = ref => {
     this._listRef = ref;
   };
diff --git a/Libraries/StyleSheet/EdgeInsetsPropType.js b/Libraries/StyleSheet/EdgeInsetsPropType.js
index 01e8919e6c26..8f6a594c368b 100644
--- a/Libraries/StyleSheet/EdgeInsetsPropType.js
+++ b/Libraries/StyleSheet/EdgeInsetsPropType.js
@@ -12,14 +12,12 @@
 
 const PropTypes = require('prop-types');
 
-const createStrictShapeTypeChecker = require('createStrictShapeTypeChecker');
-
-const EdgeInsetsPropType = (createStrictShapeTypeChecker({
+const EdgeInsetsPropType = PropTypes.shape({
   top: PropTypes.number,
   left: PropTypes.number,
   bottom: PropTypes.number,
   right: PropTypes.number,
-}): ReactPropsCheckType & ReactPropsChainableTypeChecker);
+});
 
 export type EdgeInsetsProp = {|
   +top: number,
diff --git a/Libraries/StyleSheet/PointPropType.js b/Libraries/StyleSheet/PointPropType.js
index 362f9185cf9e..3be09b110061 100644
--- a/Libraries/StyleSheet/PointPropType.js
+++ b/Libraries/StyleSheet/PointPropType.js
@@ -12,9 +12,7 @@
 
 const PropTypes = require('prop-types');
 
-const createStrictShapeTypeChecker = require('createStrictShapeTypeChecker');
-
-const PointPropType = createStrictShapeTypeChecker({
+const PointPropType = PropTypes.shape({
   x: PropTypes.number,
   y: PropTypes.number,
 });
diff --git a/RNTester/js/ScrollViewExample.js b/RNTester/js/ScrollViewExample.js
index c1d634b8ebf5..201eb93f46eb 100644
--- a/RNTester/js/ScrollViewExample.js
+++ b/RNTester/js/ScrollViewExample.js
@@ -80,7 +80,7 @@ exports.examples = [
         title: string,
         additionalStyles: typeof StyleSheet,
       ) {
-        let _scrollView: ScrollView;
+        let _scrollView: ?ScrollView;
         return (
           <View style={additionalStyles}>
             <Text style={styles.text}>{title}</Text>

From f19ee28e7d896aaacf26c6f850230019bdef0d3d Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:08 -0700
Subject: [PATCH 0523/1109] Adding $FlowFixMe to invalid prop accesses

Reviewed By: yungsters

Differential Revision: D7977387

fbshipit-source-id: 442e7445be62f78bdf166a2b97ef031e39877355
---
 Libraries/Components/ScrollView/ScrollView.js       | 13 +++++++++++++
 Libraries/Components/TextInput/TextInput.js         |  1 +
 Libraries/Components/Touchable/TouchableBounce.js   |  1 +
 .../Components/Touchable/TouchableHighlight.js      | 12 ++++++++++++
 .../Touchable/TouchableWithoutFeedback.js           |  4 ++++
 .../Experimental/SwipeableRow/SwipeableListView.js  |  2 ++
 Libraries/Lists/FlatList.js                         |  1 +
 Libraries/Lists/ListView/ListView.js                |  2 ++
 Libraries/Lists/MetroListView.js                    |  7 +++++++
 Libraries/Lists/SectionList.js                      |  5 +++++
 Libraries/Lists/VirtualizedList.js                  |  3 +++
 RNTester/js/ScrollViewExample.js                    |  4 ++++
 12 files changed, 55 insertions(+)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 0154932f243a..682809a1ad46 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -636,6 +636,7 @@ const ScrollView = createReactClass({
   },
 
   _getKeyForIndex: function(index, childArray) {
+    // $FlowFixMe Invalid prop usage
     const child = childArray[index];
     return child && child.key;
   },
@@ -668,6 +669,7 @@ const ScrollView = createReactClass({
     if (!this.props.stickyHeaderIndices) {
       return;
     }
+    // $FlowFixMe Invalid prop usage
     const childArray = React.Children.toArray(this.props.children);
     if (key !== this._getKeyForIndex(index, childArray)) {
       // ignore stale layout update
@@ -677,8 +679,10 @@ const ScrollView = createReactClass({
     const layoutY = event.nativeEvent.layout.y;
     this._headerLayoutYs.set(key, layoutY);
 
+    // $FlowFixMe Invalid prop usage
     const indexOfIndex = this.props.stickyHeaderIndices.indexOf(index);
     const previousHeaderIndex = this.props.stickyHeaderIndices[
+      // $FlowFixMe Invalid prop usage
       indexOfIndex - 1
     ];
     if (previousHeaderIndex != null) {
@@ -799,12 +803,16 @@ const ScrollView = createReactClass({
     const hasStickyHeaders =
       stickyHeaderIndices && stickyHeaderIndices.length > 0;
     const childArray =
+      // $FlowFixMe Invalid prop usage
       hasStickyHeaders && React.Children.toArray(this.props.children);
     const children = hasStickyHeaders
+      // $FlowFixMe Invalid prop usage
       ? childArray.map((child, index) => {
+          // $FlowFixMe Invalid prop usage
           const indexOfIndex = child ? stickyHeaderIndices.indexOf(index) : -1;
           if (indexOfIndex > -1) {
             const key = child.key;
+            // $FlowFixMe Invalid prop usage
             const nextIndex = stickyHeaderIndices[indexOfIndex + 1];
             return (
               <ScrollViewStickyHeader
@@ -826,10 +834,12 @@ const ScrollView = createReactClass({
             return child;
           }
         })
+      // $FlowFixMe Invalid prop usage
       : this.props.children;
     const contentContainer = (
       <ScrollContentContainerViewClass
         {...contentSizeChangeProps}
+        // $FlowFixMe Invalid prop usage
         ref={this._setInnerViewRef}
         style={contentContainerStyle}
         removeClippedSubviews={
@@ -913,6 +923,7 @@ const ScrollView = createReactClass({
         // On iOS the RefreshControl is a child of the ScrollView.
         // tvOS lacks native support for RefreshControl, so don't include it in that case
         return (
+          // $FlowFixMe Invalid prop usage
           <ScrollViewClass {...props} ref={this._setScrollViewRef}>
             {Platform.isTVOS ? null : refreshControl}
             {contentContainer}
@@ -931,6 +942,7 @@ const ScrollView = createReactClass({
           <ScrollViewClass
             {...props}
             style={baseStyle}
+            // $FlowFixMe Invalid prop usage
             ref={this._setScrollViewRef}>
             {contentContainer}
           </ScrollViewClass>,
@@ -938,6 +950,7 @@ const ScrollView = createReactClass({
       }
     }
     return (
+      // $FlowFixMe Invalid prop usage
       <ScrollViewClass {...props} ref={this._setScrollViewRef}>
         {contentContainer}
       </ScrollViewClass>
diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index 754af17e1bcb..0cdfdd43994f 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -1040,6 +1040,7 @@ const TextInput = createReactClass({
   },
 
   _onTextInput: function(event: Event) {
+    // $FlowFixMe Invalid prop usage
     this.props.onTextInput && this.props.onTextInput(event);
   },
 
diff --git a/Libraries/Components/Touchable/TouchableBounce.js b/Libraries/Components/Touchable/TouchableBounce.js
index 1ebb1a877415..1942140d3825 100644
--- a/Libraries/Components/Touchable/TouchableBounce.js
+++ b/Libraries/Components/Touchable/TouchableBounce.js
@@ -138,6 +138,7 @@ const TouchableBounce = createReactClass({
   },
 
   touchableGetPressRectOffset: function(): typeof PRESS_RETENTION_OFFSET {
+    // $FlowFixMe Invalid prop usage
     return this.props.pressRetentionOffset || PRESS_RETENTION_OFFSET;
   },
 
diff --git a/Libraries/Components/Touchable/TouchableHighlight.js b/Libraries/Components/Touchable/TouchableHighlight.js
index 4d8f63eecdd0..670fda7a4d94 100644
--- a/Libraries/Components/Touchable/TouchableHighlight.js
+++ b/Libraries/Components/Touchable/TouchableHighlight.js
@@ -190,6 +190,7 @@ const TouchableHighlight = createReactClass({
   getDefaultProps: () => DEFAULT_PROPS,
 
   getInitialState: function() {
+    // $FlowFixMe Invalid prop usage
     this._isMounted = false;
     if (this.props.testOnly_pressed) {
       return {
@@ -211,11 +212,13 @@ const TouchableHighlight = createReactClass({
   },
 
   componentDidMount: function() {
+    // $FlowFixMe Invalid prop usage
     this._isMounted = true;
     ensurePositiveDelayProps(this.props);
   },
 
   componentWillUnmount: function() {
+    // $FlowFixMe Invalid prop usage
     this._isMounted = false;
     clearTimeout(this._hideTimeout);
   },
@@ -235,12 +238,14 @@ const TouchableHighlight = createReactClass({
    */
   touchableHandleActivePressIn: function(e: PressEvent) {
     clearTimeout(this._hideTimeout);
+    // $FlowFixMe Invalid prop usage
     this._hideTimeout = null;
     this._showUnderlay();
     this.props.onPressIn && this.props.onPressIn(e);
   },
 
   touchableHandleActivePressOut: function(e: PressEvent) {
+    // $FlowFixMe Invalid prop usage
     if (!this._hideTimeout) {
       this._hideUnderlay();
     }
@@ -251,6 +256,7 @@ const TouchableHighlight = createReactClass({
     clearTimeout(this._hideTimeout);
     if (!Platform.isTVOS) {
       this._showUnderlay();
+      // $FlowFixMe Invalid prop usage
       this._hideTimeout = setTimeout(
         this._hideUnderlay,
         this.props.delayPressOut,
@@ -284,6 +290,7 @@ const TouchableHighlight = createReactClass({
   },
 
   _showUnderlay: function() {
+    // $FlowFixMe Invalid prop usage
     if (!this._isMounted || !this._hasPressHandler()) {
       return;
     }
@@ -300,6 +307,7 @@ const TouchableHighlight = createReactClass({
 
   _hideUnderlay: function() {
     clearTimeout(this._hideTimeout);
+    // $FlowFixMe Invalid prop usage
     this._hideTimeout = null;
     if (this.props.testOnly_pressed) {
       return;
@@ -323,10 +331,12 @@ const TouchableHighlight = createReactClass({
   },
 
   render: function() {
+    // $FlowFixMe Invalid prop usage
     const child = React.Children.only(this.props.children);
     return (
       <View
         accessible={this.props.accessible !== false}
+        // $FlowFixMe Invalid prop usage
         accessibilityLabel={this.props.accessibilityLabel}
         accessibilityComponentType={this.props.accessibilityComponentType}
         accessibilityTraits={this.props.accessibilityTraits}
@@ -347,7 +357,9 @@ const TouchableHighlight = createReactClass({
         onResponderMove={this.touchableHandleResponderMove}
         onResponderRelease={this.touchableHandleResponderRelease}
         onResponderTerminate={this.touchableHandleResponderTerminate}
+        // $FlowFixMe Invalid prop usage
         nativeID={this.props.nativeID}
+        // $FlowFixMe Invalid prop usage
         testID={this.props.testID}>
         {React.cloneElement(child, {
           style: StyleSheet.compose(
diff --git a/Libraries/Components/Touchable/TouchableWithoutFeedback.js b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
index 2c6530733aa5..8594846b3de9 100755
--- a/Libraries/Components/Touchable/TouchableWithoutFeedback.js
+++ b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
@@ -144,6 +144,7 @@ const TouchableWithoutFeedback = createReactClass({
   },
 
   touchableGetPressRectOffset: function(): typeof PRESS_RETENTION_OFFSET {
+    // $FlowFixMe Invalid prop usage
     return this.props.pressRetentionOffset || PRESS_RETENTION_OFFSET;
   },
 
@@ -194,10 +195,13 @@ const TouchableWithoutFeedback = createReactClass({
         : child.props.style;
     return (React: any).cloneElement(child, {
       accessible: this.props.accessible !== false,
+      // $FlowFixMe Invalid prop usage
       accessibilityLabel: this.props.accessibilityLabel,
       accessibilityComponentType: this.props.accessibilityComponentType,
       accessibilityTraits: this.props.accessibilityTraits,
+      // $FlowFixMe Invalid prop usage
       nativeID: this.props.nativeID,
+      // $FlowFixMe Invalid prop usage
       testID: this.props.testID,
       onLayout: this.props.onLayout,
       hitSlop: this.props.hitSlop,
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableListView.js b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
index e449501c7183..11afd75e3c6b 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableListView.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
@@ -117,9 +117,11 @@ class SwipeableListView extends React.Component<Props, State> {
 
   render(): React.Node {
     return (
+      // $FlowFixMe Invalid prop usage
       <ListView
         {...this.props}
         ref={ref => {
+          // $FlowFixMe Invalid prop usage
           this._listViewRef = ref;
         }}
         dataSource={this.state.dataSource.getDataSource()}
diff --git a/Libraries/Lists/FlatList.js b/Libraries/Lists/FlatList.js
index 5a0827be1df8..0e693a39649d 100644
--- a/Libraries/Lists/FlatList.js
+++ b/Libraries/Lists/FlatList.js
@@ -476,6 +476,7 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
   _virtualizedListPairs: Array<ViewabilityConfigCallbackPair> = [];
 
   _captureRef = ref => {
+    // $FlowFixMe Invalid prop usage
     this._listRef = ref;
   };
 
diff --git a/Libraries/Lists/ListView/ListView.js b/Libraries/Lists/ListView/ListView.js
index cd168bc656cd..402b053fdf27 100644
--- a/Libraries/Lists/ListView/ListView.js
+++ b/Libraries/Lists/ListView/ListView.js
@@ -516,8 +516,10 @@ const ListView = createReactClass({
     if (props.removeClippedSubviews === undefined) {
       props.removeClippedSubviews = true;
     }
+    // $FlowFixMe Invalid prop usage
     Object.assign(props, {
       onScroll: this._onScroll,
+      // $FlowFixMe Invalid prop usage
       stickyHeaderIndices: this.props.stickyHeaderIndices.concat(
         stickySectionHeaderIndices,
       ),
diff --git a/Libraries/Lists/MetroListView.js b/Libraries/Lists/MetroListView.js
index fbf6b5554f72..a072bb931152 100644
--- a/Libraries/Lists/MetroListView.js
+++ b/Libraries/Lists/MetroListView.js
@@ -85,6 +85,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
   }
   scrollToOffset(params: {animated?: ?boolean, offset: number}) {
     const {animated, offset} = params;
+    // $FlowFixMe Invalid prop usage
     this._listRef.scrollTo(
       this.props.horizontal ? {x: offset, animated} : {y: offset, animated},
     );
@@ -94,6 +95,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
   }
   setNativeProps(props: Object) {
     if (this._listRef) {
+      // $FlowFixMe Invalid prop usage
       this._listRef.setNativeProps(props);
     }
   }
@@ -102,6 +104,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
     renderScrollComponent: (props: Props) => {
       if (props.onRefresh) {
         return (
+          // $FlowFixMe Invalid prop usage
           <ScrollView
             {...props}
             refreshControl={
@@ -117,6 +120,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
           />
         );
       } else {
+        // $FlowFixMe Invalid prop usage
         return <ScrollView {...props} />;
       }
     },
@@ -135,6 +139,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
   }
   render() {
     return (
+      // $FlowFixMe Invalid prop usage
       <ListView
         {...this.props}
         dataSource={this.state.ds}
@@ -142,6 +147,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
         renderRow={this._renderRow}
         renderFooter={this.props.FooterComponent && this._renderFooter}
         renderSectionHeader={this.props.sections && this._renderSectionHeader}
+        // $FlowFixMe Invalid prop usage
         renderSeparator={this.props.SeparatorComponent && this._renderSeparator}
       />
     );
@@ -167,6 +173,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
     } else {
       invariant(!props.sections, 'Cannot have both sections and items props.');
       return {
+        // $FlowFixMe Invalid prop usage
         ds: state.ds.cloneWithRows(props.items),
         sectionHeaderData,
       };
diff --git a/Libraries/Lists/SectionList.js b/Libraries/Lists/SectionList.js
index 17a4f84711e0..2590e28aadbd 100644
--- a/Libraries/Lists/SectionList.js
+++ b/Libraries/Lists/SectionList.js
@@ -284,6 +284,7 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
    */
   recordInteraction() {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
+    // $FlowFixMe Invalid prop usage
     listRef && listRef.recordInteraction();
   }
 
@@ -294,6 +295,7 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
    */
   flashScrollIndicators() {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
+    // $FlowFixMe Invalid prop usage
     listRef && listRef.flashScrollIndicators();
   }
 
@@ -303,6 +305,7 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
   getScrollResponder(): ?ScrollView {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
     if (listRef) {
+      // $FlowFixMe Invalid prop usage
       return listRef.getScrollResponder();
     }
   }
@@ -310,6 +313,7 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
   getScrollableNode() {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
     if (listRef) {
+      // $FlowFixMe Invalid prop usage
       return listRef.getScrollableNode();
     }
   }
@@ -317,6 +321,7 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
   setNativeProps(props: Object) {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
     if (listRef) {
+      // $FlowFixMe Invalid prop usage
       listRef.setNativeProps(props);
     }
   }
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index e0a0fbb651fc..034b3a6e2df6 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -924,6 +924,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
       (this.props.renderScrollComponent || this._defaultRenderScrollComponent)(
         scrollProps,
       ),
+      // $FlowFixMe Invalid prop usage
       {
         ref: this._captureScrollRef,
       },
@@ -1016,6 +1017,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
           '`',
       );
       return (
+        // $FlowFixMe Invalid prop usage
         <ScrollView
           {...props}
           refreshControl={
@@ -1032,6 +1034,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
         />
       );
     } else {
+      // $FlowFixMe Invalid prop usage
       return <ScrollView {...props} />;
     }
   };
diff --git a/RNTester/js/ScrollViewExample.js b/RNTester/js/ScrollViewExample.js
index 201eb93f46eb..6d70a62624a2 100644
--- a/RNTester/js/ScrollViewExample.js
+++ b/RNTester/js/ScrollViewExample.js
@@ -39,6 +39,7 @@ exports.examples = [
         <View>
           <ScrollView
             ref={scrollView => {
+              // $FlowFixMe Invalid prop usage
               _scrollView = scrollView;
             }}
             automaticallyAdjustContentInsets={false}
@@ -96,18 +97,21 @@ exports.examples = [
             <Button
               label="Scroll to start"
               onPress={() => {
+                // $FlowFixMe Invalid prop usage
                 _scrollView.scrollTo({x: 0});
               }}
             />
             <Button
               label="Scroll to end"
               onPress={() => {
+                // $FlowFixMe Invalid prop usage
                 _scrollView.scrollToEnd({animated: true});
               }}
             />
             <Button
               label="Flash scroll indicators"
               onPress={() => {
+                // $FlowFixMe Invalid prop usage
                 _scrollView.flashScrollIndicators();
               }}
             />

From 0b71d1ddb03c036ed118574c105b0af505da19fc Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:12 -0700
Subject: [PATCH 0524/1109] Flow Typing ActivityIndicator

Reviewed By: yungsters

Differential Revision: D7977834

fbshipit-source-id: 62e54f98ee8f9e7d5189fc19c803a95f5c4c43aa
---
 .../ActivityIndicator/ActivityIndicator.js    | 20 +++++++++++++++----
 1 file changed, 16 insertions(+), 4 deletions(-)

diff --git a/Libraries/Components/ActivityIndicator/ActivityIndicator.js b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
index a3bf769f77c7..7438d1e35f12 100644
--- a/Libraries/Components/ActivityIndicator/ActivityIndicator.js
+++ b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
@@ -22,15 +22,27 @@ const ViewPropTypes = require('ViewPropTypes');
 
 const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
+
+import type {ViewProps} from 'ViewPropTypes';
+
 let RCTActivityIndicator;
 
 const GRAY = '#999999';
 
 type IndicatorSize = number | 'small' | 'large';
 
+type Props = $ReadOnly<{|
+  ...ViewProps,
+
+  animating?: ?boolean,
+  color?: ?string,
+  hidesWhenStopped?: ?boolean,
+  size?: ?IndicatorSize,
+|}>;
+
 type DefaultProps = {
   animating: boolean,
-  color: any,
+  color: ?string,
   hidesWhenStopped: boolean,
   size: IndicatorSize,
 };
@@ -40,7 +52,7 @@ type DefaultProps = {
  *
  * See http://facebook.github.io/react-native/docs/activityindicator.html
  */
-const ActivityIndicator = createReactClass({
+const ActivityIndicator = ((createReactClass({
   displayName: 'ActivityIndicator',
   mixins: [NativeMethodsMixin],
 
@@ -81,7 +93,7 @@ const ActivityIndicator = createReactClass({
   getDefaultProps(): DefaultProps {
     return {
       animating: true,
-      color: Platform.OS === 'ios' ? GRAY : undefined,
+      color: Platform.OS === 'ios' ? GRAY : null,
       hidesWhenStopped: true,
       size: 'small',
     };
@@ -120,7 +132,7 @@ const ActivityIndicator = createReactClass({
       </View>
     );
   },
-});
+}): any): React.ComponentType<Props>);
 
 if (Platform.OS === 'ios') {
   RCTActivityIndicator = requireNativeComponent(

From 97e572ea6d7b1fd829ca20f5d5c8ff970d88e68b Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:14 -0700
Subject: [PATCH 0525/1109] Flow Type DatePickerIOS.ios.js

Reviewed By: yungsters

Differential Revision: D7978090

fbshipit-source-id: 65da360f34f4b6d9240a8343c89be66404767474
---
 .../Components/DatePicker/DatePickerIOS.ios.js | 18 ++++++++++++++++--
 1 file changed, 16 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/DatePicker/DatePickerIOS.ios.js b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
index 7a5455e60537..c089d9ea8a5a 100644
--- a/Libraries/Components/DatePicker/DatePickerIOS.ios.js
+++ b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
@@ -24,12 +24,26 @@ const ViewPropTypes = require('ViewPropTypes');
 const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {ViewProps} from 'ViewPropTypes';
 type DefaultProps = {
   mode: 'date' | 'time' | 'datetime',
 };
 
 type Event = Object;
 
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  date?: ?Date,
+  initialDate?: ?Date,
+  locale?: ?string,
+  maximumDate?: ?Date,
+  minimumDate?: ?Date,
+  minuteInterval?: ?(1 | 2 | 3 | 4 | 5 | 6 | 10 | 12 | 15 | 20 | 30),
+  mode?: ?('date' | 'time' | 'datetime'),
+  onDateChange: (date: Date) => void,
+  timeZoneOffsetInMinutes?: ?number,
+|}>;
+
 /**
  * Use `DatePickerIOS` to render a date/time picker (selector) on iOS.  This is
  * a controlled component, so you must hook in to the `onDateChange` callback
@@ -37,7 +51,7 @@ type Event = Object;
  * the user's change will be reverted immediately to reflect `props.date` as the
  * source of truth.
  */
-const DatePickerIOS = createReactClass({
+const DatePickerIOS = ((createReactClass({
   displayName: 'DatePickerIOS',
   // TOOD: Put a better type for _picker
   _picker: (undefined: ?$FlowFixMe),
@@ -171,7 +185,7 @@ const DatePickerIOS = createReactClass({
       </View>
     );
   },
-});
+}): any): React.ComponentType<Props>);
 
 const styles = StyleSheet.create({
   datePickerIOS: {

From 188b118b6075be1614c553596b85d430767f2dbc Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:16 -0700
Subject: [PATCH 0526/1109] Flow Type KeyboardAvoidingView

Reviewed By: yungsters

Differential Revision: D7978494

fbshipit-source-id: e21b4910470d3dc3fd35027f2f975b6842baa6ab
---
 .../Components/Keyboard/KeyboardAvoidingView.js   | 15 ++++++++++++---
 1 file changed, 12 insertions(+), 3 deletions(-)

diff --git a/Libraries/Components/Keyboard/KeyboardAvoidingView.js b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
index c559608d34c6..64ab0551f7c9 100644
--- a/Libraries/Components/Keyboard/KeyboardAvoidingView.js
+++ b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
@@ -24,7 +24,8 @@ const View = require('View');
 const ViewPropTypes = require('ViewPropTypes');
 
 import type EmitterSubscription from 'EmitterSubscription';
-import type {ViewLayout, ViewLayoutEvent} from 'ViewPropTypes';
+import type {ViewStyleProp} from 'StyleSheet';
+import type {ViewProps, ViewLayout, ViewLayoutEvent} from 'ViewPropTypes';
 
 type ScreenRect = {
   screenX: number,
@@ -39,13 +40,21 @@ type KeyboardChangeEvent = {
   easing?: string,
 };
 
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  behavior?: ?('height' | 'position' | 'padding'),
+  contentContainerStyle?: ?ViewStyleProp,
+  enabled?: ?boolean,
+  keyboardVerticalOffset?: ?number,
+|}>;
+
 const viewRef = 'VIEW';
 
 /**
  * This is a component to solve the common problem of views that need to move out of the way of the virtual keyboard.
  * It can automatically adjust either its height, position or bottom padding based on the position of the keyboard.
  */
-const KeyboardAvoidingView = createReactClass({
+const KeyboardAvoidingView = ((createReactClass({
   displayName: 'KeyboardAvoidingView',
   mixins: [TimerMixin],
 
@@ -229,6 +238,6 @@ const KeyboardAvoidingView = createReactClass({
         );
     }
   },
-});
+}): any): React.ComponentType<Props>);
 
 module.exports = KeyboardAvoidingView;

From b1276622791d5dbe4199bb075f473908c3e62b31 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:18 -0700
Subject: [PATCH 0527/1109] Flow Type ScrollView

Reviewed By: yungsters

Differential Revision: D7981073

fbshipit-source-id: 38c100f37e46683da1e34b335d476e706baae238
---
 .../ScrollView/InternalScrollViewType.js      |  46 +++++++
 Libraries/Components/ScrollView/ScrollView.js | 114 +++++++++++++++++-
 Libraries/StyleSheet/EdgeInsetsPropType.js    |  12 +-
 Libraries/StyleSheet/PointPropType.js         |   5 +
 4 files changed, 165 insertions(+), 12 deletions(-)
 create mode 100644 Libraries/Components/ScrollView/InternalScrollViewType.js

diff --git a/Libraries/Components/ScrollView/InternalScrollViewType.js b/Libraries/Components/ScrollView/InternalScrollViewType.js
new file mode 100644
index 000000000000..a97ca9f43641
--- /dev/null
+++ b/Libraries/Components/ScrollView/InternalScrollViewType.js
@@ -0,0 +1,46 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @format
+ * @flow
+ */
+
+const React = require('React');
+
+// This class is purely a facsimile of ScrollView so that we can
+// properly type it with Flow before migrating ScrollView off of
+// createReactClass. If there are things missing here that are in
+// ScrollView, that is unintentional.
+class InternalScrollViewType<Props> extends React.Component<Props> {
+  scrollTo(
+    y?: number | {x?: number, y?: number, animated?: boolean},
+    x?: number,
+    animated?: boolean,
+  ) {}
+
+  flashScrollIndicators() {}
+  scrollToEnd(options?: {animated?: boolean}) {}
+  scrollWithoutAnimationTo(y: number = 0, x: number = 0) {}
+  setNativeProps(props: Object) {}
+
+  getScrollResponder(): any {}
+  getScrollableNode(): any {}
+  getInnerViewNode(): any {}
+
+  scrollResponderScrollNativeHandleToKeyboard(
+    nodeHandle: any,
+    additionalOffset?: number,
+    preventNegativeScrollOffset?: boolean,
+  ) {}
+
+  scrollResponderScrollTo(
+    x?: number | {x?: number, y?: number, animated?: boolean},
+    y?: number,
+    animated?: boolean,
+  ) {}
+}
+
+module.exports = InternalScrollViewType;
diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 682809a1ad46..3038f4cfff03 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -25,6 +25,7 @@ const StyleSheetPropType = require('StyleSheetPropType');
 const View = require('View');
 const ViewPropTypes = require('ViewPropTypes');
 const ViewStylePropTypes = require('ViewStylePropTypes');
+const InternalScrollViewType = require('InternalScrollViewType');
 
 const createReactClass = require('create-react-class');
 const dismissKeyboard = require('dismissKeyboard');
@@ -38,7 +39,104 @@ const requireNativeComponent = require('requireNativeComponent');
 const warning = require('fbjs/lib/warning');
 const resolveAssetSource = require('resolveAssetSource');
 
+import type {PressEvent} from 'CoreEventTypes';
+import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
 import type {NativeMethodsMixinType} from 'ReactNativeTypes';
+import type {ViewStyleProp} from 'StyleSheet';
+import type {ViewProps} from 'ViewPropTypes';
+import type {PointProp} from 'PointPropType';
+
+import type {ColorValue} from 'StyleSheetTypes';
+
+type TouchableProps = $ReadOnly<{|
+  onTouchStart?: (event: PressEvent) => void,
+  onTouchMove?: (event: PressEvent) => void,
+  onTouchEnd?: (event: PressEvent) => void,
+  onTouchCancel?: (event: PressEvent) => void,
+  onTouchEndCapture?: (event: PressEvent) => void,
+|}>;
+
+type IOSProps = $ReadOnly<{|
+  automaticallyAdjustContentInsets?: ?boolean,
+  contentInset?: ?EdgeInsetsProp,
+  contentOffset?: ?PointProp,
+  bounces?: ?boolean,
+  bouncesZoom?: ?boolean,
+  alwaysBounceHorizontal?: ?boolean,
+  alwaysBounceVertical?: ?boolean,
+  centerContent?: ?boolean,
+  decelerationRate?: ?('fast' | 'normal' | number),
+  indicatorStyle?: ?('default' | 'black' | 'white'),
+  directionalLockEnabled?: ?boolean,
+  canCancelContentTouches?: ?boolean,
+  maintainVisibleContentPosition?: ?$ReadOnly<{|
+    minIndexForVisible: number,
+    autoscrollToTopThreshold?: ?number,
+  |}>,
+  maximumZoomScale?: ?number,
+  minimumZoomScale?: ?number,
+  pinchGestureEnabled?: ?boolean,
+  scrollEventThrottle?: ?number,
+  scrollIndicatorInsets?: ?EdgeInsetsProp,
+  scrollsToTop?: ?boolean,
+  showsHorizontalScrollIndicator?: ?boolean,
+  snapToAlignment?: ?('start' | 'center' | 'end'),
+  zoomScale?: ?number,
+  contentInsetAdjustmentBehavior?: ?(
+    | 'automatic'
+    | 'scrollableAxes'
+    | 'never'
+    | 'always'
+  ),
+  DEPRECATED_sendUpdatedChildFrames?: ?boolean,
+|}>;
+
+type AndroidProps = $ReadOnly<{|
+  nestedScrollEnabled?: ?boolean,
+  endFillColor?: ?ColorValue,
+  scrollPerfTag?: ?string,
+  overScrollMode?: ?('auto' | 'always' | 'never'),
+|}>;
+
+type VRProps = $ReadOnly<{|
+  scrollBarThumbImage?: ?($ReadOnly<{||}> | number),
+|}>;
+
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  ...TouchableProps,
+  ...IOSProps,
+  ...AndroidProps,
+  ...VRProps,
+
+  contentContainerStyle?: ?ViewStyleProp,
+  horizontal?: ?boolean,
+  invertStickyHeaders?: ?boolean,
+  keyboardDismissMode?: ?(
+    | 'none' // default
+    | 'on-drag' // cross-platform
+    | 'interactive'
+  ), // ios only
+  // $FlowFixMe Issues found when typing ScrollView
+  keyboardShouldPersistTaps?: ?('always' | 'never' | 'handled' | false | true),
+  onMomentumScrollBegin?: ?Function,
+  onMomentumScrollEnd?: ?Function,
+
+  onScroll?: ?Function,
+  onScrollBeginDrag?: ?Function,
+  onScrollEndDrag?: ?Function,
+  onContentSizeChange?: ?Function,
+  onKeyboardDidShow?: (event: PressEvent) => void,
+  pagingEnabled?: ?boolean,
+  scrollEnabled?: ?boolean,
+  showsVerticalScrollIndicator?: ?boolean,
+  stickyHeaderIndices?: ?$ReadOnlyArray<number>,
+  snapToInterval?: ?number,
+  removeClippedSubviews?: ?boolean,
+  refreshControl?: ?React.Element<any>,
+  style?: ?ViewStyleProp,
+  children?: React.Node,
+|}>;
 
 /**
  * Component that wraps platform ScrollView while providing
@@ -75,7 +173,6 @@ import type {NativeMethodsMixinType} from 'ReactNativeTypes';
  * multiple columns, infinite scroll loading, or any number of other features it
  * supports out of the box.
  */
-// $FlowFixMe(>=0.41.0)
 const ScrollView = createReactClass({
   displayName: 'ScrollView',
   propTypes: {
@@ -806,8 +903,8 @@ const ScrollView = createReactClass({
       // $FlowFixMe Invalid prop usage
       hasStickyHeaders && React.Children.toArray(this.props.children);
     const children = hasStickyHeaders
-      // $FlowFixMe Invalid prop usage
-      ? childArray.map((child, index) => {
+      ? // $FlowFixMe Invalid prop usage
+        childArray.map((child, index) => {
           // $FlowFixMe Invalid prop usage
           const indexOfIndex = child ? stickyHeaderIndices.indexOf(index) : -1;
           if (indexOfIndex > -1) {
@@ -834,8 +931,8 @@ const ScrollView = createReactClass({
             return child;
           }
         })
-      // $FlowFixMe Invalid prop usage
-      : this.props.children;
+      : // $FlowFixMe Invalid prop usage
+        this.props.children;
     const contentContainer = (
       <ScrollContentContainerViewClass
         {...contentSizeChangeProps}
@@ -884,6 +981,7 @@ const ScrollView = createReactClass({
       onResponderGrant: this.scrollResponderHandleResponderGrant,
       onResponderReject: this.scrollResponderHandleResponderReject,
       onResponderRelease: this.scrollResponderHandleResponderRelease,
+      // $FlowFixMe
       onResponderTerminate: this.scrollResponderHandleTerminate,
       onResponderTerminationRequest: this
         .scrollResponderHandleTerminationRequest,
@@ -958,6 +1056,10 @@ const ScrollView = createReactClass({
   },
 });
 
+const TypedScrollView = ((ScrollView: any): Class<
+  InternalScrollViewType<Props>,
+>);
+
 const styles = StyleSheet.create({
   baseVertical: {
     flexGrow: 1,
@@ -1028,4 +1130,4 @@ if (Platform.OS === 'android') {
   RCTScrollContentView = requireNativeComponent('RCTScrollContentView', View);
 }
 
-module.exports = ScrollView;
+module.exports = TypedScrollView;
diff --git a/Libraries/StyleSheet/EdgeInsetsPropType.js b/Libraries/StyleSheet/EdgeInsetsPropType.js
index 8f6a594c368b..10a6bf6104eb 100644
--- a/Libraries/StyleSheet/EdgeInsetsPropType.js
+++ b/Libraries/StyleSheet/EdgeInsetsPropType.js
@@ -19,11 +19,11 @@ const EdgeInsetsPropType = PropTypes.shape({
   right: PropTypes.number,
 });
 
-export type EdgeInsetsProp = {|
-  +top: number,
-  +left: number,
-  +bottom: number,
-  +right: number,
-|};
+export type EdgeInsetsProp = $ReadOnly<{|
+  top?: ?number,
+  left?: ?number,
+  bottom?: ?number,
+  right?: ?number,
+|}>;
 
 module.exports = EdgeInsetsPropType;
diff --git a/Libraries/StyleSheet/PointPropType.js b/Libraries/StyleSheet/PointPropType.js
index 3be09b110061..008c675048da 100644
--- a/Libraries/StyleSheet/PointPropType.js
+++ b/Libraries/StyleSheet/PointPropType.js
@@ -17,4 +17,9 @@ const PointPropType = PropTypes.shape({
   y: PropTypes.number,
 });
 
+export type PointProp = $ReadOnly<{
+  x: number,
+  y: number,
+}>;
+
 module.exports = PointPropType;

From 91c4b0357a1e83419095ed5ae9c9f50602f86ce6 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 10:25:21 -0700
Subject: [PATCH 0528/1109] Remove unused suppressions

Reviewed By: yungsters

Differential Revision: D7982027

fbshipit-source-id: 00e538dc678275495e097d9cd14a0a2643ebaefd
---
 Libraries/Components/ScrollView/ScrollView.js            | 1 -
 Libraries/Experimental/SwipeableRow/SwipeableListView.js | 2 --
 Libraries/Lists/FlatList.js                              | 1 -
 Libraries/Lists/ListView/ListView.js                     | 2 --
 Libraries/Lists/MetroListView.js                         | 4 ----
 Libraries/Lists/SectionList.js                           | 5 -----
 6 files changed, 15 deletions(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 3038f4cfff03..0822ba140d4e 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -334,7 +334,6 @@ const ScrollView = createReactClass({
      *   - `false`, deprecated, use 'never' instead
      *   - `true`, deprecated, use 'always' instead
      */
-    // $FlowFixMe
     keyboardShouldPersistTaps: PropTypes.oneOf([
       'always',
       'never',
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableListView.js b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
index 11afd75e3c6b..e449501c7183 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableListView.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
@@ -117,11 +117,9 @@ class SwipeableListView extends React.Component<Props, State> {
 
   render(): React.Node {
     return (
-      // $FlowFixMe Invalid prop usage
       <ListView
         {...this.props}
         ref={ref => {
-          // $FlowFixMe Invalid prop usage
           this._listViewRef = ref;
         }}
         dataSource={this.state.dataSource.getDataSource()}
diff --git a/Libraries/Lists/FlatList.js b/Libraries/Lists/FlatList.js
index 0e693a39649d..5a0827be1df8 100644
--- a/Libraries/Lists/FlatList.js
+++ b/Libraries/Lists/FlatList.js
@@ -476,7 +476,6 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
   _virtualizedListPairs: Array<ViewabilityConfigCallbackPair> = [];
 
   _captureRef = ref => {
-    // $FlowFixMe Invalid prop usage
     this._listRef = ref;
   };
 
diff --git a/Libraries/Lists/ListView/ListView.js b/Libraries/Lists/ListView/ListView.js
index 402b053fdf27..cd168bc656cd 100644
--- a/Libraries/Lists/ListView/ListView.js
+++ b/Libraries/Lists/ListView/ListView.js
@@ -516,10 +516,8 @@ const ListView = createReactClass({
     if (props.removeClippedSubviews === undefined) {
       props.removeClippedSubviews = true;
     }
-    // $FlowFixMe Invalid prop usage
     Object.assign(props, {
       onScroll: this._onScroll,
-      // $FlowFixMe Invalid prop usage
       stickyHeaderIndices: this.props.stickyHeaderIndices.concat(
         stickySectionHeaderIndices,
       ),
diff --git a/Libraries/Lists/MetroListView.js b/Libraries/Lists/MetroListView.js
index a072bb931152..c8d7a45a662a 100644
--- a/Libraries/Lists/MetroListView.js
+++ b/Libraries/Lists/MetroListView.js
@@ -95,7 +95,6 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
   }
   setNativeProps(props: Object) {
     if (this._listRef) {
-      // $FlowFixMe Invalid prop usage
       this._listRef.setNativeProps(props);
     }
   }
@@ -139,7 +138,6 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
   }
   render() {
     return (
-      // $FlowFixMe Invalid prop usage
       <ListView
         {...this.props}
         dataSource={this.state.ds}
@@ -147,7 +145,6 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
         renderRow={this._renderRow}
         renderFooter={this.props.FooterComponent && this._renderFooter}
         renderSectionHeader={this.props.sections && this._renderSectionHeader}
-        // $FlowFixMe Invalid prop usage
         renderSeparator={this.props.SeparatorComponent && this._renderSeparator}
       />
     );
@@ -173,7 +170,6 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
     } else {
       invariant(!props.sections, 'Cannot have both sections and items props.');
       return {
-        // $FlowFixMe Invalid prop usage
         ds: state.ds.cloneWithRows(props.items),
         sectionHeaderData,
       };
diff --git a/Libraries/Lists/SectionList.js b/Libraries/Lists/SectionList.js
index 2590e28aadbd..17a4f84711e0 100644
--- a/Libraries/Lists/SectionList.js
+++ b/Libraries/Lists/SectionList.js
@@ -284,7 +284,6 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
    */
   recordInteraction() {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
-    // $FlowFixMe Invalid prop usage
     listRef && listRef.recordInteraction();
   }
 
@@ -295,7 +294,6 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
    */
   flashScrollIndicators() {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
-    // $FlowFixMe Invalid prop usage
     listRef && listRef.flashScrollIndicators();
   }
 
@@ -305,7 +303,6 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
   getScrollResponder(): ?ScrollView {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
     if (listRef) {
-      // $FlowFixMe Invalid prop usage
       return listRef.getScrollResponder();
     }
   }
@@ -313,7 +310,6 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
   getScrollableNode() {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
     if (listRef) {
-      // $FlowFixMe Invalid prop usage
       return listRef.getScrollableNode();
     }
   }
@@ -321,7 +317,6 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
   setNativeProps(props: Object) {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
     if (listRef) {
-      // $FlowFixMe Invalid prop usage
       listRef.setNativeProps(props);
     }
   }

From 0b79d1faa21eb3c29aeeba08ee0fb2ed62e6cc54 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 23:10:42 -0700
Subject: [PATCH 0529/1109] Type TouchableWithoutFeedback

Reviewed By: yungsters

Differential Revision: D7982348

fbshipit-source-id: 409ce4a5ea8c09e58c42caf9db60117253503c4c
---
 .../Touchable/TouchableWithoutFeedback.js     | 43 ++++++++++++++++---
 1 file changed, 38 insertions(+), 5 deletions(-)

diff --git a/Libraries/Components/Touchable/TouchableWithoutFeedback.js b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
index 8594846b3de9..f80fd9a07cd7 100755
--- a/Libraries/Components/Touchable/TouchableWithoutFeedback.js
+++ b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
@@ -32,9 +32,41 @@ const {
 } = require('ViewAccessibility');
 
 import type {PressEvent} from 'CoreEventTypes';
+import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
+import type {
+  AccessibilityComponentType,
+  AccessibilityTrait,
+} from 'ViewAccessibility';
 
 const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
 
+type Props = $ReadOnly<{|
+  accessible?: boolean,
+  accessibilityComponentType?: AccessibilityComponentType,
+  accessibilityLabel?:
+    | null
+    | React$PropType$Primitive<any>
+    | string
+    | Array<any>
+    | any,
+  accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
+  children?: ?React.Node,
+  delayLongPress?: ?number,
+  delayPressIn?: ?number,
+  delayPressOut?: ?number,
+  disabled?: ?boolean,
+  hitSlop?: ?EdgeInsetsProp,
+  nativeID?: ?string,
+  onLayout?: ?Function,
+  onLongPress?: ?Function,
+  onPress?: ?Function,
+  onPressIn?: ?Function,
+  onPressOut?: ?Function,
+  pressRetentionOffset?: ?EdgeInsetsProp,
+  rejectResponderTermination?: ?boolean,
+  testID?: ?string,
+|}>;
+
 /**
  * Do not use unless you have a very good reason. All elements that
  * respond to press should have a visual feedback when touched.
@@ -42,12 +74,13 @@ const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
  * TouchableWithoutFeedback supports only one child.
  * If you wish to have several child components, wrap them in a View.
  */
-const TouchableWithoutFeedback = createReactClass({
+const TouchableWithoutFeedback = ((createReactClass({
   displayName: 'TouchableWithoutFeedback',
   mixins: [TimerMixin, Touchable.Mixin],
 
   propTypes: {
     accessible: PropTypes.bool,
+    accessibilityLabel: PropTypes.node,
     accessibilityComponentType: PropTypes.oneOf(AccessibilityComponentTypes),
     accessibilityTraits: PropTypes.oneOfType([
       PropTypes.oneOf(AccessibilityTraits),
@@ -80,6 +113,9 @@ const TouchableWithoutFeedback = createReactClass({
 
     onLongPress: PropTypes.func,
 
+    nativeID: PropTypes.string,
+    testID: PropTypes.string,
+
     /**
      * Delay in ms, from the start of the touch, before onPressIn is called.
      */
@@ -195,13 +231,10 @@ const TouchableWithoutFeedback = createReactClass({
         : child.props.style;
     return (React: any).cloneElement(child, {
       accessible: this.props.accessible !== false,
-      // $FlowFixMe Invalid prop usage
       accessibilityLabel: this.props.accessibilityLabel,
       accessibilityComponentType: this.props.accessibilityComponentType,
       accessibilityTraits: this.props.accessibilityTraits,
-      // $FlowFixMe Invalid prop usage
       nativeID: this.props.nativeID,
-      // $FlowFixMe Invalid prop usage
       testID: this.props.testID,
       onLayout: this.props.onLayout,
       hitSlop: this.props.hitSlop,
@@ -216,6 +249,6 @@ const TouchableWithoutFeedback = createReactClass({
       children,
     });
   },
-});
+}): any): React.ComponentType<Props>);
 
 module.exports = TouchableWithoutFeedback;

From 6b3aad31f67e3543e4b52774dfb7369e99329d52 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 23:10:44 -0700
Subject: [PATCH 0530/1109] Remove unused suppressions

Reviewed By: yungsters

Differential Revision: D7983271

fbshipit-source-id: ee64e2dacbc8a1b75915b825f7bf0621a121422d
---
 Libraries/Components/Touchable/TouchableHighlight.js | 12 ------------
 1 file changed, 12 deletions(-)

diff --git a/Libraries/Components/Touchable/TouchableHighlight.js b/Libraries/Components/Touchable/TouchableHighlight.js
index 670fda7a4d94..4d8f63eecdd0 100644
--- a/Libraries/Components/Touchable/TouchableHighlight.js
+++ b/Libraries/Components/Touchable/TouchableHighlight.js
@@ -190,7 +190,6 @@ const TouchableHighlight = createReactClass({
   getDefaultProps: () => DEFAULT_PROPS,
 
   getInitialState: function() {
-    // $FlowFixMe Invalid prop usage
     this._isMounted = false;
     if (this.props.testOnly_pressed) {
       return {
@@ -212,13 +211,11 @@ const TouchableHighlight = createReactClass({
   },
 
   componentDidMount: function() {
-    // $FlowFixMe Invalid prop usage
     this._isMounted = true;
     ensurePositiveDelayProps(this.props);
   },
 
   componentWillUnmount: function() {
-    // $FlowFixMe Invalid prop usage
     this._isMounted = false;
     clearTimeout(this._hideTimeout);
   },
@@ -238,14 +235,12 @@ const TouchableHighlight = createReactClass({
    */
   touchableHandleActivePressIn: function(e: PressEvent) {
     clearTimeout(this._hideTimeout);
-    // $FlowFixMe Invalid prop usage
     this._hideTimeout = null;
     this._showUnderlay();
     this.props.onPressIn && this.props.onPressIn(e);
   },
 
   touchableHandleActivePressOut: function(e: PressEvent) {
-    // $FlowFixMe Invalid prop usage
     if (!this._hideTimeout) {
       this._hideUnderlay();
     }
@@ -256,7 +251,6 @@ const TouchableHighlight = createReactClass({
     clearTimeout(this._hideTimeout);
     if (!Platform.isTVOS) {
       this._showUnderlay();
-      // $FlowFixMe Invalid prop usage
       this._hideTimeout = setTimeout(
         this._hideUnderlay,
         this.props.delayPressOut,
@@ -290,7 +284,6 @@ const TouchableHighlight = createReactClass({
   },
 
   _showUnderlay: function() {
-    // $FlowFixMe Invalid prop usage
     if (!this._isMounted || !this._hasPressHandler()) {
       return;
     }
@@ -307,7 +300,6 @@ const TouchableHighlight = createReactClass({
 
   _hideUnderlay: function() {
     clearTimeout(this._hideTimeout);
-    // $FlowFixMe Invalid prop usage
     this._hideTimeout = null;
     if (this.props.testOnly_pressed) {
       return;
@@ -331,12 +323,10 @@ const TouchableHighlight = createReactClass({
   },
 
   render: function() {
-    // $FlowFixMe Invalid prop usage
     const child = React.Children.only(this.props.children);
     return (
       <View
         accessible={this.props.accessible !== false}
-        // $FlowFixMe Invalid prop usage
         accessibilityLabel={this.props.accessibilityLabel}
         accessibilityComponentType={this.props.accessibilityComponentType}
         accessibilityTraits={this.props.accessibilityTraits}
@@ -357,9 +347,7 @@ const TouchableHighlight = createReactClass({
         onResponderMove={this.touchableHandleResponderMove}
         onResponderRelease={this.touchableHandleResponderRelease}
         onResponderTerminate={this.touchableHandleResponderTerminate}
-        // $FlowFixMe Invalid prop usage
         nativeID={this.props.nativeID}
-        // $FlowFixMe Invalid prop usage
         testID={this.props.testID}>
         {React.cloneElement(child, {
           style: StyleSheet.compose(

From f0c18dc820537892dcc33d5aebbf4f52cf299b95 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 23:10:46 -0700
Subject: [PATCH 0531/1109] Flow type TouchableHighlight

Reviewed By: yungsters

Differential Revision: D7983631

fbshipit-source-id: 98b3708b26e2bf96426d5acaa5c7e2311a3a34f6
---
 .../Touchable/TouchableHighlight.js           | 24 +++++++++++++++++--
 .../Touchable/TouchableWithoutFeedback.js     | 16 ++++---------
 .../Components/View/ViewAccessibility.js      |  4 ++++
 RNTester/js/RNTesterExampleList.js            |  5 +++-
 RNTester/js/TouchableExample.js               |  3 ---
 5 files changed, 35 insertions(+), 17 deletions(-)

diff --git a/Libraries/Components/Touchable/TouchableHighlight.js b/Libraries/Components/Touchable/TouchableHighlight.js
index 4d8f63eecdd0..117884faf864 100644
--- a/Libraries/Components/Touchable/TouchableHighlight.js
+++ b/Libraries/Components/Touchable/TouchableHighlight.js
@@ -25,6 +25,9 @@ const createReactClass = require('create-react-class');
 const ensurePositiveDelayProps = require('ensurePositiveDelayProps');
 
 import type {PressEvent} from 'CoreEventTypes';
+import type {Props as TouchableWithoutFeedbackProps} from 'TouchableWithoutFeedback';
+import type {ViewStyleProp} from 'StyleSheet';
+import type {ColorValue} from 'StyleSheetTypes';
 
 const DEFAULT_PROPS = {
   activeOpacity: 0.85,
@@ -34,6 +37,23 @@ const DEFAULT_PROPS = {
 
 const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
 
+type IOSProps = $ReadOnly<{|
+  hasTVPreferredFocus?: ?boolean,
+  tvParallaxProperties?: ?Object,
+|}>;
+
+type Props = $ReadOnly<{|
+  ...TouchableWithoutFeedbackProps,
+  ...IOSProps,
+
+  activeOpacity?: ?number,
+  underlayColor?: ?ColorValue,
+  style?: ?ViewStyleProp,
+  onShowUnderlay?: ?Function,
+  onHideUnderlay?: ?Function,
+  testOnly_pressed?: ?boolean,
+|}>;
+
 /**
  * A wrapper for making views respond properly to touches.
  * On press down, the opacity of the wrapped view is decreased, which allows
@@ -131,7 +151,7 @@ const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
  *
  */
 
-const TouchableHighlight = createReactClass({
+const TouchableHighlight = ((createReactClass({
   displayName: 'TouchableHighlight',
   propTypes: {
     ...TouchableWithoutFeedback.propTypes,
@@ -362,6 +382,6 @@ const TouchableHighlight = createReactClass({
       </View>
     );
   },
-});
+}): any): React.ComponentType<Props>);
 
 module.exports = TouchableHighlight;
diff --git a/Libraries/Components/Touchable/TouchableWithoutFeedback.js b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
index f80fd9a07cd7..2cd249cb5be6 100755
--- a/Libraries/Components/Touchable/TouchableWithoutFeedback.js
+++ b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
@@ -13,17 +13,11 @@
 const EdgeInsetsPropType = require('EdgeInsetsPropType');
 const React = require('React');
 const PropTypes = require('prop-types');
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
 const TimerMixin = require('react-timer-mixin');
 const Touchable = require('Touchable');
 
 const createReactClass = require('create-react-class');
 const ensurePositiveDelayProps = require('ensurePositiveDelayProps');
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
 const warning = require('fbjs/lib/warning');
 
 const {
@@ -35,21 +29,21 @@ import type {PressEvent} from 'CoreEventTypes';
 import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
 import type {
   AccessibilityComponentType,
-  AccessibilityTrait,
+  AccessibilityTraits as AccessibilityTraitsFlow,
 } from 'ViewAccessibility';
 
 const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
 
-type Props = $ReadOnly<{|
-  accessible?: boolean,
-  accessibilityComponentType?: AccessibilityComponentType,
+export type Props = $ReadOnly<{|
+  accessible?: ?boolean,
+  accessibilityComponentType?: ?AccessibilityComponentType,
   accessibilityLabel?:
     | null
     | React$PropType$Primitive<any>
     | string
     | Array<any>
     | any,
-  accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
+  accessibilityTraits?: ?AccessibilityTraitsFlow,
   children?: ?React.Node,
   delayLongPress?: ?number,
   delayPressIn?: ?number,
diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index c5e44e289d08..b6e46f5b65a9 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -29,6 +29,10 @@ export type AccessibilityTrait =
   | 'allowsDirectInteraction'
   | 'pageTurn';
 
+export type AccessibilityTraits =
+  | AccessibilityTrait
+  | $ReadOnlyArray<AccessibilityTrait>;
+
 export type AccessibilityComponentType =
   | 'none'
   | 'button'
diff --git a/RNTester/js/RNTesterExampleList.js b/RNTester/js/RNTesterExampleList.js
index d031caef4524..c9ccce1a88a0 100644
--- a/RNTester/js/RNTesterExampleList.js
+++ b/RNTester/js/RNTesterExampleList.js
@@ -53,7 +53,10 @@ class RowComponent extends React.PureComponent<{
   render() {
     const {item} = this.props;
     return (
-      <TouchableHighlight {...this.props} onPress={this._onPress}>
+      <TouchableHighlight
+        onShowUnderlay={this.props.onShowUnderlay}
+        onHideUnderlay={this.props.onHideUnderlay}
+        onPress={this._onPress}>
         <View style={styles.row}>
           <Text style={styles.rowTitleText}>{item.module.title}</Text>
           <Text style={styles.rowDetailText}>{item.module.description}</Text>
diff --git a/RNTester/js/TouchableExample.js b/RNTester/js/TouchableExample.js
index 3ce3faa45bb0..711bd8bc1dae 100644
--- a/RNTester/js/TouchableExample.js
+++ b/RNTester/js/TouchableExample.js
@@ -55,7 +55,6 @@ exports.examples = [
             <TouchableHighlight
               style={styles.wrapper}
               activeOpacity={1}
-              animationVelocity={0}
               tvParallaxProperties={{
                 pressMagnification: 1.3,
                 pressDuration: 0.6,
@@ -348,7 +347,6 @@ class TouchableDisabled extends React.Component<{}> {
         <TouchableHighlight
           activeOpacity={1}
           disabled={true}
-          animationVelocity={0}
           underlayColor="rgb(210, 230, 255)"
           style={[styles.row, styles.block]}
           onPress={() => console.log('custom THW text - highlight')}>
@@ -357,7 +355,6 @@ class TouchableDisabled extends React.Component<{}> {
 
         <TouchableHighlight
           activeOpacity={1}
-          animationVelocity={0}
           underlayColor="rgb(210, 230, 255)"
           style={[styles.row, styles.block]}
           onPress={() => console.log('custom THW text - highlight')}>

From 6cfa4a360d307e744c1d233adad7a7edae513218 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 23:10:49 -0700
Subject: [PATCH 0532/1109] TouchableOpacity @noflow -> @flow

Reviewed By: yungsters

Differential Revision: D7983644

fbshipit-source-id: bf4a0ba600ac51ef07ac12927eed29eeb92ffb2a
---
 Libraries/Components/Touchable/TouchableOpacity.js | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/Libraries/Components/Touchable/TouchableOpacity.js b/Libraries/Components/Touchable/TouchableOpacity.js
index afb01b079af9..3ecce7234593 100644
--- a/Libraries/Components/Touchable/TouchableOpacity.js
+++ b/Libraries/Components/Touchable/TouchableOpacity.js
@@ -5,13 +5,11 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @noflow
+ * @flow
  */
 
 'use strict';
 
-// Note (avik): add @flow when Flow supports spread properties in propTypes
-
 const Animated = require('Animated');
 const Easing = require('Easing');
 const NativeMethodsMixin = require('NativeMethodsMixin');

From 44743c07ad672e39668f92a801578906ec92996a Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 23:10:51 -0700
Subject: [PATCH 0533/1109] Flow Type TouchableOpacity

Reviewed By: yungsters

Differential Revision: D7983709

fbshipit-source-id: 0f664c831b754277e344aa53b2dbed6b4f720cd5
---
 .../Components/Touchable/TouchableOpacity.js  | 19 +++++++++++++++++--
 1 file changed, 17 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/Touchable/TouchableOpacity.js b/Libraries/Components/Touchable/TouchableOpacity.js
index 3ecce7234593..f860337e0d65 100644
--- a/Libraries/Components/Touchable/TouchableOpacity.js
+++ b/Libraries/Components/Touchable/TouchableOpacity.js
@@ -23,10 +23,25 @@ const createReactClass = require('create-react-class');
 const ensurePositiveDelayProps = require('ensurePositiveDelayProps');
 const flattenStyle = require('flattenStyle');
 
+import type {Props as TouchableWithoutFeedbackProps} from 'TouchableWithoutFeedback';
+import type {ViewStyleProp} from 'StyleSheet';
+
 type Event = Object;
 
 const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
 
+type TVProps = $ReadOnly<{|
+  hasTVPreferredFocus?: ?boolean,
+  tvParallaxProperties?: ?Object,
+|}>;
+
+type Props = $ReadOnly<{|
+  ...TouchableWithoutFeedbackProps,
+  ...TVProps,
+  activeOpacity?: ?number,
+  style?: ?ViewStyleProp,
+|}>;
+
 /**
  * A wrapper for making views respond properly to touches.
  * On press down, the opacity of the wrapped view is decreased, dimming it.
@@ -115,7 +130,7 @@ const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
  * ```
  *
  */
-const TouchableOpacity = createReactClass({
+const TouchableOpacity = ((createReactClass({
   displayName: 'TouchableOpacity',
   mixins: [TimerMixin, Touchable.Mixin, NativeMethodsMixin],
 
@@ -267,6 +282,6 @@ const TouchableOpacity = createReactClass({
       </Animated.View>
     );
   },
-});
+}): any): React.ComponentType<Props>);
 
 module.exports = TouchableOpacity;

From 0fe72579be3488f988b1647170146a70bb0dc48b Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 23:10:53 -0700
Subject: [PATCH 0534/1109] Image cleanup

Reviewed By: yungsters

Differential Revision: D7983744

fbshipit-source-id: c6c1c78fd93b40553688f1444b57074802520f7e
---
 Libraries/Image/Image.ios.js  | 5 -----
 Libraries/Image/ImageProps.js | 6 +++---
 2 files changed, 3 insertions(+), 8 deletions(-)

diff --git a/Libraries/Image/Image.ios.js b/Libraries/Image/Image.ios.js
index eb0d0241af52..4989f62d39a6 100644
--- a/Libraries/Image/Image.ios.js
+++ b/Libraries/Image/Image.ios.js
@@ -9,18 +9,13 @@
  */
 'use strict';
 
-const EdgeInsetsPropType = require('EdgeInsetsPropType');
 const ImageProps = require('ImageProps');
 const ImageResizeMode = require('ImageResizeMode');
-const ImageSourcePropType = require('ImageSourcePropType');
-const ImageStylePropTypes = require('ImageStylePropTypes');
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const NativeModules = require('NativeModules');
 const React = require('React');
-const PropTypes = require('prop-types');
 const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const StyleSheet = require('StyleSheet');
-const StyleSheetPropType = require('StyleSheetPropType');
 
 const createReactClass = require('create-react-class');
 const flattenStyle = require('flattenStyle');
diff --git a/Libraries/Image/ImageProps.js b/Libraries/Image/ImageProps.js
index 63015586296d..46d367fccf8c 100644
--- a/Libraries/Image/ImageProps.js
+++ b/Libraries/Image/ImageProps.js
@@ -18,8 +18,8 @@ const StyleSheetPropType = require('StyleSheetPropType');
 
 import type {ImageSource} from 'ImageSource';
 import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
-import type {LayoutEvent} from 'CoreEventTypes';
-import type {SyntheticEvent} from 'CoreEventTypes';
+import type {LayoutEvent, SyntheticEvent} from 'CoreEventTypes';
+import type {ImageStyleProp} from 'StyleSheet';
 
 export type ImageProps = {
   accessible?: boolean,
@@ -35,7 +35,7 @@ export type ImageProps = {
   resizeMethod?: ?('auto' | 'resize' | 'scale'),
   resizeMode?: ?('cover' | 'contain' | 'stretch' | 'repeat' | 'center'),
   source?: ?ImageSource,
-  style?: typeof ImageStylePropTypes,
+  style?: ImageStyleProp,
   testID?: ?string,
 
   // ios

From a9a612bfb6c4804f7898431180bb74c3711b0254 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 23:10:55 -0700
Subject: [PATCH 0535/1109] Making ImageURISource exact

Reviewed By: yungsters

Differential Revision: D7984204

fbshipit-source-id: ccd2627b72da5c97f046c895652fdf7cc0b3db40
---
 Libraries/Image/ImageSource.js | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/Image/ImageSource.js b/Libraries/Image/ImageSource.js
index b729863234ff..4fdd7f270a53 100644
--- a/Libraries/Image/ImageSource.js
+++ b/Libraries/Image/ImageSource.js
@@ -11,7 +11,7 @@
 
 // This is to sync with ImageSourcePropTypes.js.
 
-type ImageURISource = {
+type ImageURISource = $ReadOnly<{|
   uri?: string,
   bundle?: string,
   method?: string,
@@ -21,6 +21,6 @@ type ImageURISource = {
   width?: number,
   height?: number,
   scale?: number,
-};
+|}>;
 
 export type ImageSource = ImageURISource | number | Array<ImageURISource>;

From 870775ee738e9405c6545500f9a637df9b513a02 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 12 May 2018 23:10:57 -0700
Subject: [PATCH 0536/1109] Stop expose Image.resizeMode

Summary:
Exposing this enum is essentially useless and at worst is a runtime cost that isn't necessary by just using the string.

The value of this enum, as far as I understand it, is to enforce that only valid options are used. We can enforce this at build time with Flow.

I was able to migrate our codebase with a few Find and Replace for things like

```
resizeMode={Image.resizeMode.contain}
```

Reviewed By: yungsters

Differential Revision: D7983982

fbshipit-source-id: ddd7024023f8d2f01aad1fff6c8103983a1bec1a
---
 Libraries/Image/Image.android.js     |  3 ---
 Libraries/Image/Image.ios.js         |  2 --
 RNTester/js/ImageCapInsetsExample.js |  4 ++--
 RNTester/js/ImageExample.js          | 10 +++++-----
 4 files changed, 7 insertions(+), 12 deletions(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index b54d624118b1..cf87d4bc782e 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -10,7 +10,6 @@
 
 'use strict';
 
-const ImageResizeMode = require('ImageResizeMode');
 const ImageStylePropTypes = require('ImageStylePropTypes');
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const NativeModules = require('NativeModules');
@@ -132,8 +131,6 @@ const Image = createReactClass({
   },
 
   statics: {
-    resizeMode: ImageResizeMode,
-
     getSize(
       url: string,
       success: (width: number, height: number) => void,
diff --git a/Libraries/Image/Image.ios.js b/Libraries/Image/Image.ios.js
index 4989f62d39a6..86a5525374fe 100644
--- a/Libraries/Image/Image.ios.js
+++ b/Libraries/Image/Image.ios.js
@@ -10,7 +10,6 @@
 'use strict';
 
 const ImageProps = require('ImageProps');
-const ImageResizeMode = require('ImageResizeMode');
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const NativeModules = require('NativeModules');
 const React = require('React');
@@ -36,7 +35,6 @@ const Image = createReactClass({
   propTypes: ImageProps,
 
   statics: {
-    resizeMode: ImageResizeMode,
     /**
      * Retrieve the width and height (in pixels) of an image prior to displaying it.
      *
diff --git a/RNTester/js/ImageCapInsetsExample.js b/RNTester/js/ImageCapInsetsExample.js
index 8f84d77358cf..76705f4d7e60 100644
--- a/RNTester/js/ImageCapInsetsExample.js
+++ b/RNTester/js/ImageCapInsetsExample.js
@@ -29,7 +29,7 @@ class ImageCapInsetsExample extends React.Component<{}> {
               height: 60,
             })}
             style={styles.storyBackground}
-            resizeMode={Image.resizeMode.stretch}
+            resizeMode="stretch"
             capInsets={{left: 0, right: 0, bottom: 0, top: 0}}
           />
         </View>
@@ -42,7 +42,7 @@ class ImageCapInsetsExample extends React.Component<{}> {
               height: 60,
             })}
             style={styles.storyBackground}
-            resizeMode={Image.resizeMode.stretch}
+            resizeMode="stretch"
             capInsets={{left: 15, right: 15, bottom: 15, top: 15}}
           />
         </View>
diff --git a/RNTester/js/ImageExample.js b/RNTester/js/ImageExample.js
index 280146395432..2125e2669e72 100644
--- a/RNTester/js/ImageExample.js
+++ b/RNTester/js/ImageExample.js
@@ -621,7 +621,7 @@ exports.examples = [
                     <Text style={[styles.resizeModeText]}>Contain</Text>
                     <Image
                       style={styles.resizeMode}
-                      resizeMode={Image.resizeMode.contain}
+                      resizeMode="contain"
                       source={image}
                     />
                   </View>
@@ -629,7 +629,7 @@ exports.examples = [
                     <Text style={[styles.resizeModeText]}>Cover</Text>
                     <Image
                       style={styles.resizeMode}
-                      resizeMode={Image.resizeMode.cover}
+                      resizeMode="cover"
                       source={image}
                     />
                   </View>
@@ -639,7 +639,7 @@ exports.examples = [
                     <Text style={[styles.resizeModeText]}>Stretch</Text>
                     <Image
                       style={styles.resizeMode}
-                      resizeMode={Image.resizeMode.stretch}
+                      resizeMode="stretch"
                       source={image}
                     />
                   </View>
@@ -647,7 +647,7 @@ exports.examples = [
                     <Text style={[styles.resizeModeText]}>Repeat</Text>
                     <Image
                       style={styles.resizeMode}
-                      resizeMode={Image.resizeMode.repeat}
+                      resizeMode="repeat"
                       source={image}
                     />
                   </View>
@@ -655,7 +655,7 @@ exports.examples = [
                     <Text style={[styles.resizeModeText]}>Center</Text>
                     <Image
                       style={styles.resizeMode}
-                      resizeMode={Image.resizeMode.center}
+                      resizeMode="center"
                       source={image}
                     />
                   </View>

From 3d3edfc3da0e92dc5c6c6c3d1ed63a75733a8c5e Mon Sep 17 00:00:00 2001
From: Federico Trimboli <federicotrimboli@gmail.com>
Date: Sat, 12 May 2018 23:19:27 -0700
Subject: [PATCH 0537/1109] Replace magic numbers with `safeAreaInsets` in
 `RCTDevLoadingView`

Summary:
This PR replaces magic numbers used for offsetting `RCTDevLoadingView` when running on iPhone X, in favour of `safeAreaInsets`.

Tested on iPhone X and iPhone 8. Here is a screenshot showing how it looks on iPhone X.
![nansi](https://user-images.githubusercontent.com/3900360/39599961-b4239d90-4ef3-11e8-97f4-269d571a6c8d.png)
Closes https://github.com/facebook/react-native/pull/19119

Differential Revision: D7984823

Pulled By: hramos

fbshipit-source-id: 0c7c3ba0fa258a64f6c4a1e0620f87bf0620984c
---
 React/DevSupport/RCTDevLoadingView.m | 8 +++++---
 1 file changed, 5 insertions(+), 3 deletions(-)

diff --git a/React/DevSupport/RCTDevLoadingView.m b/React/DevSupport/RCTDevLoadingView.m
index 9382c91caa6e..6d67c9d80a6e 100644
--- a/React/DevSupport/RCTDevLoadingView.m
+++ b/React/DevSupport/RCTDevLoadingView.m
@@ -72,9 +72,11 @@ - (void)setBridge:(RCTBridge *)bridge
     self->_showDate = [NSDate date];
     if (!self->_window && !RCTRunningInTestEnvironment()) {
       CGSize screenSize = [UIScreen mainScreen].bounds.size;
-      if (screenSize.height == 812 /* iPhone X */) {
-        self->_window = [[UIWindow alloc] initWithFrame:CGRectMake(0, 0, screenSize.width, 60)];
-        self->_label = [[UILabel alloc] initWithFrame:CGRectMake(0, 30, self->_window.bounds.size.width, 30)];
+      
+      if (@available(iOS 11.0, *)) {
+        UIWindow *window = UIApplication.sharedApplication.keyWindow;
+        self->_window = [[UIWindow alloc] initWithFrame:CGRectMake(0, 0, screenSize.width, window.safeAreaInsets.top + 30)];
+        self->_label = [[UILabel alloc] initWithFrame:CGRectMake(0, window.safeAreaInsets.top, screenSize.width, 30)];
       } else {
         self->_window = [[UIWindow alloc] initWithFrame:CGRectMake(0, 0, screenSize.width, 22)];
         self->_label = [[UILabel alloc] initWithFrame:self->_window.bounds];

From 41a940392cea497bc5eb627b24083d0211d1eb89 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Sun, 13 May 2018 00:48:47 -0700
Subject: [PATCH 0538/1109] RN: Add Missing Events to ViewPropTypes

Reviewed By: TheSavior

Differential Revision: D7984937

fbshipit-source-id: fc2703e3382a7515b71f8a634aca5b6d7a5b25b4
---
 Libraries/Components/View/ViewPropTypes.js | 50 ++++++++++++++++------
 1 file changed, 36 insertions(+), 14 deletions(-)

diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 1d5f193c62de..addbc6e7e81d 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -35,7 +35,43 @@ const stylePropType = StyleSheetPropType(ViewStylePropTypes);
 export type ViewLayout = Layout;
 export type ViewLayoutEvent = LayoutEvent;
 
+type DirectEventProps = $ReadOnly<{|
+  onAccessibilityAction?: Function,
+  onAccessibilityTap?: Function,
+  onLayout?: ?(event: LayoutEvent) => void,
+  onMagicTap?: Function,
+|}>;
+
+type TouchEventProps = $ReadOnly<{|
+  onTouchCancel?: ?Function,
+  onTouchCancelCapture?: ?Function,
+  onTouchEnd?: ?Function,
+  onTouchEndCapture?: ?Function,
+  onTouchMove?: ?Function,
+  onTouchMoveCapture?: ?Function,
+  onTouchStart?: ?Function,
+  onTouchStartCapture?: ?Function,
+|}>;
+
+type GestureResponderEventProps = $ReadOnly<{|
+  onMoveShouldSetResponder?: ?Function,
+  onMoveShouldSetResponderCapture?: ?Function,
+  onResponderGrant?: ?Function,
+  onResponderMove?: ?Function,
+  onResponderReject?: ?Function,
+  onResponderRelease?: ?Function,
+  onResponderStart?: ?Function,
+  onResponderTerminate?: ?Function,
+  onResponderTerminationRequest?: ?Function,
+  onStartShouldSetResponder?: ?Function,
+  onStartShouldSetResponderCapture?: ?Function,
+|}>;
+
 export type ViewProps = $ReadOnly<{|
+  ...DirectEventProps,
+  ...GestureResponderEventProps,
+  ...TouchEventProps,
+
   // There's no easy way to create a different type if (Platform.isTVOS):
   // so we must include TVViewProps
   ...TVViewProps,
@@ -55,22 +91,8 @@ export type ViewProps = $ReadOnly<{|
   accessibilityViewIsModal?: boolean,
   accessibilityElementsHidden?: boolean,
   children?: ?React.Node,
-  onAccessibilityAction?: Function,
-  onAccessibilityTap?: Function,
-  onMagicTap?: Function,
   testID?: ?string,
   nativeID?: string,
-  onLayout?: ?(event: LayoutEvent) => void,
-  onResponderGrant?: ?Function,
-  onResponderMove?: ?Function,
-  onResponderReject?: ?Function,
-  onResponderRelease?: ?Function,
-  onResponderTerminate?: ?Function,
-  onResponderTerminationRequest?: ?Function,
-  onStartShouldSetResponder?: ?Function,
-  onStartShouldSetResponderCapture?: ?Function,
-  onMoveShouldSetResponder?: ?Function,
-  onMoveShouldSetResponderCapture?: ?Function,
   hitSlop?: ?EdgeInsetsProp,
   pointerEvents?: null | 'box-none' | 'none' | 'box-only' | 'auto',
   style?: stylePropType,

From de11ba2a5ee90929dbc67d914de59bdd2ebc29ca Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Sun, 13 May 2018 00:48:49 -0700
Subject: [PATCH 0539/1109] RN: Fix Type for ReactNative.NativeComponent (1/2)

Reviewed By: TheSavior

Differential Revision: D7984814

fbshipit-source-id: 0097819128b7f82267bceeb9d5e1b5057c5129ec
---
 Libraries/Components/View/View.js            |  2 +-
 Libraries/Renderer/shims/ReactNativeTypes.js | 23 ++++++++++++++++++--
 Libraries/Text/Text.js                       |  4 ++--
 3 files changed, 24 insertions(+), 5 deletions(-)

diff --git a/Libraries/Components/View/View.js b/Libraries/Components/View/View.js
index 9694a2fb39a2..5e1b6bdb57ab 100644
--- a/Libraries/Components/View/View.js
+++ b/Libraries/Components/View/View.js
@@ -74,4 +74,4 @@ if (__DEV__) {
   ViewToExport.displayName = 'View';
 }
 
-module.exports = ((ViewToExport: any): Class<NativeComponent<ViewProps, any>>);
+module.exports = ((ViewToExport: any): Class<NativeComponent<ViewProps>>);
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index 485ce162ecc6..1f0d1dce0b09 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -4,9 +4,12 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
+import * as React from 'react';
+
 export type MeasureOnSuccessCallback = (
   x: number,
   y: number,
@@ -51,6 +54,22 @@ export type ReactNativeBaseComponentViewConfig = {
 
 export type ViewConfigGetter = () => ReactNativeBaseComponentViewConfig;
 
+/**
+ * Class only exists for its Flow type.
+ */
+class ReactNativeComponent<Props> extends React.Component<Props> {
+  blur(): void {}
+  focus(): void {}
+  measure(callback: MeasureOnSuccessCallback): void {}
+  measureInWindow(callback: MeasureInWindowOnSuccessCallback): void {}
+  measureLayout(
+    relativeToNativeNode: number,
+    onSuccess: MeasureLayoutOnSuccessCallback,
+    onFail?: () => void,
+  ): void {}
+  setNativeProps(nativeProps: Object): void {}
+}
+
 /**
  * This type keeps ReactNativeFiberHostComponent and NativeMethodsMixin in sync.
  * It can also provide types for ReactNative applications that use NMM or refs.
@@ -86,7 +105,7 @@ type SecretInternalsFabricType = {
  * Provide minimal Flow typing for the high-level RN API and call it a day.
  */
 export type ReactNativeType = {
-  NativeComponent: any,
+  NativeComponent: typeof ReactNativeComponent,
   findNodeHandle(componentOrHandle: any): ?number,
   render(
     element: React$Element<any>,
@@ -101,7 +120,7 @@ export type ReactNativeType = {
 };
 
 export type ReactFabricType = {
-  NativeComponent: any,
+  NativeComponent: typeof ReactNativeComponent,
   findNodeHandle(componentOrHandle: any): ?number,
   render(
     element: React$Element<any>,
diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index 1dcac7c1a759..a1f9db79398e 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -36,7 +36,7 @@ type ResponseHandlers = $ReadOnly<{|
 
 type Props = $ReadOnly<{
   ...TextProps,
-  forwardedRef: ?React.Ref<NativeComponent<TextProps, any>>,
+  forwardedRef: ?React.Ref<NativeComponent<TextProps>>,
 }>;
 
 type State = {|
@@ -270,4 +270,4 @@ Text.displayName = 'Text';
 // TODO: Deprecate this.
 Text.propTypes = TextPropTypes;
 
-module.exports = ((Text: any): NativeComponent<TextProps, any>);
+module.exports = ((Text: any): Class<NativeComponent<TextProps>>);

From 752863629d63bca6d96a101bfeccc4e7ad3e953e Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Sun, 13 May 2018 00:48:51 -0700
Subject: [PATCH 0540/1109] RN: Fix Type for ReactNative.NativeComponent (2/2)

Reviewed By: TheSavior

Differential Revision: D7984936

fbshipit-source-id: d0477c54420b49220e9529fa70c2b2babce0b409
---
 Libraries/Components/Keyboard/KeyboardAvoidingView.js | 4 ++++
 Libraries/Lists/VirtualizedList.js                    | 9 +++++++--
 Libraries/RCTTest/SnapshotViewIOS.ios.js              | 1 +
 Libraries/ReactNative/AppContainer.js                 | 1 +
 Libraries/Text/Text.js                                | 2 ++
 RNTester/js/RTLExample.js                             | 1 +
 6 files changed, 16 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/Keyboard/KeyboardAvoidingView.js b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
index 64ab0551f7c9..790c5a3acf8f 100644
--- a/Libraries/Components/Keyboard/KeyboardAvoidingView.js
+++ b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
@@ -189,6 +189,7 @@ const KeyboardAvoidingView = ((createReactClass({
           heightStyle = {height: this.frame.height - bottomHeight, flex: 0};
         }
         return (
+          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           <View
             ref={viewRef}
             style={[style, heightStyle]}
@@ -203,6 +204,7 @@ const KeyboardAvoidingView = ((createReactClass({
         const {contentContainerStyle} = this.props;
 
         return (
+          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           <View
             ref={viewRef}
             style={style}
@@ -217,6 +219,7 @@ const KeyboardAvoidingView = ((createReactClass({
       case 'padding':
         const paddingStyle = {paddingBottom: bottomHeight};
         return (
+          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           <View
             ref={viewRef}
             style={[style, paddingStyle]}
@@ -228,6 +231,7 @@ const KeyboardAvoidingView = ((createReactClass({
 
       default:
         return (
+          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           <View
             ref={viewRef}
             onLayout={this._onLayout}
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 034b3a6e2df6..37819aaeef9a 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -757,7 +757,9 @@ class VirtualizedList extends React.PureComponent<Props, State> {
           cellKey={this._getCellKey() + '-header'}
           key="$header">
           <View onLayout={this._onLayoutHeader} style={inversionStyle}>
-            {element}
+            {
+              // $FlowFixMe - Typing ReactNativeComponent revealed errors
+              element}
           </View>
         </VirtualizedCellWrapper>,
       );
@@ -890,7 +892,9 @@ class VirtualizedList extends React.PureComponent<Props, State> {
           cellKey={this._getCellKey() + '-footer'}
           key="$footer">
           <View onLayout={this._onLayoutFooter} style={inversionStyle}>
-            {element}
+            {
+              // $FlowFixMe - Typing ReactNativeComponent revealed errors
+              element}
           </View>
         </VirtualizedCellWrapper>,
       );
@@ -1008,6 +1012,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
   _defaultRenderScrollComponent = props => {
     const onRefresh = props.onRefresh;
     if (this._isNestedWithSameOrientation()) {
+      // $FlowFixMe - Typing ReactNativeComponent revealed errors
       return <View {...props} />;
     } else if (onRefresh) {
       invariant(
diff --git a/Libraries/RCTTest/SnapshotViewIOS.ios.js b/Libraries/RCTTest/SnapshotViewIOS.ios.js
index 55cc78424ecc..f2a53511bc1b 100644
--- a/Libraries/RCTTest/SnapshotViewIOS.ios.js
+++ b/Libraries/RCTTest/SnapshotViewIOS.ios.js
@@ -42,6 +42,7 @@ class SnapshotViewIOS extends React.Component<{
     const testIdentifier = this.props.testIdentifier || 'test';
     const onSnapshotReady = this.props.onSnapshotReady || this.onDefaultAction;
     return (
+      // $FlowFixMe - Typing ReactNativeComponent revealed errors
       <RCTSnapshot
         style={style.snapshot}
         {...this.props}
diff --git a/Libraries/ReactNative/AppContainer.js b/Libraries/ReactNative/AppContainer.js
index fde991045d69..ce4a78043a4f 100644
--- a/Libraries/ReactNative/AppContainer.js
+++ b/Libraries/ReactNative/AppContainer.js
@@ -102,6 +102,7 @@ class AppContainer extends React.Component<Props, State> {
         pointerEvents="box-none"
         style={styles.appContainer}
         ref={ref => {
+          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           this._mainRef = ref;
         }}>
         {this.props.children}
diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index a1f9db79398e..1f1698bc25ed 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -36,6 +36,7 @@ type ResponseHandlers = $ReadOnly<{|
 
 type Props = $ReadOnly<{
   ...TextProps,
+  // $FlowFixMe - Typing ReactNativeComponent revealed errors
   forwardedRef: ?React.Ref<NativeComponent<TextProps>>,
 }>;
 
@@ -139,6 +140,7 @@ class TouchableText extends React.Component<Props, State> {
       <TextAncestor.Consumer>
         {hasTextAncestor =>
           hasTextAncestor ? (
+            // $FlowFixMe - Typing ReactNativeComponent revealed errors
             <RCTVirtualText {...props} ref={props.forwardedRef} />
           ) : (
             <TextAncestor.Provider value={true}>
diff --git a/RNTester/js/RTLExample.js b/RNTester/js/RTLExample.js
index 67120d06bb2d..ac3ec573a7e1 100644
--- a/RNTester/js/RTLExample.js
+++ b/RNTester/js/RTLExample.js
@@ -484,6 +484,7 @@ class RTLExample extends React.Component<any, State> {
           <RNTesterBlock
             title={'Controlling Animation'}
             description={'Animation direction according to layout'}>
+            {/* $FlowFixMe - Typing ReactNativeComponent revealed errors */}
             <View Style={styles.view}>
               <AnimationBlock
                 onPress={this._linearTap}

From 8454a36b0bc54cb1e267bc264657cc693607da71 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sun, 13 May 2018 01:38:35 -0700
Subject: [PATCH 0541/1109] Flow type TouchableBounce

Reviewed By: yungsters

Differential Revision: D7984827

fbshipit-source-id: b0dd67b5c4d57cd9bb0339a5266a16e4565b2d54
---
 .../Components/Touchable/TouchableBounce.js   | 63 ++++++++-----------
 1 file changed, 25 insertions(+), 38 deletions(-)

diff --git a/Libraries/Components/Touchable/TouchableBounce.js b/Libraries/Components/Touchable/TouchableBounce.js
index 1942140d3825..b9fe3d1523a4 100644
--- a/Libraries/Components/Touchable/TouchableBounce.js
+++ b/Libraries/Components/Touchable/TouchableBounce.js
@@ -16,6 +16,12 @@ const React = require('React');
 const createReactClass = require('create-react-class');
 const PropTypes = require('prop-types');
 const Touchable = require('Touchable');
+const TouchableWithoutFeedback = require('TouchableWithoutFeedback');
+const ViewPropTypes = require('ViewPropTypes');
+
+import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
+import type {Props as TouchableWithoutFeedbackProps} from 'TouchableWithoutFeedback';
+import type {ViewStyleProp} from 'StyleSheet';
 
 type Event = Object;
 
@@ -26,6 +32,17 @@ type State = {
 
 const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
 
+type Props = $ReadOnly<{|
+  ...TouchableWithoutFeedbackProps,
+
+  onPressWithCompletion?: ?Function,
+  onPressAnimationComplete?: ?Function,
+  pressRetentionOffset?: ?EdgeInsetsProp,
+  releaseVelocity?: ?number,
+  releaseBounciness?: ?number,
+  style?: ?ViewStyleProp,
+|}>;
+
 /**
  * Example of using the `TouchableMixin` to play well with other responder
  * locking views including `ScrollView`. `TouchableMixin` provides touchable
@@ -33,20 +50,13 @@ const PRESS_RETENTION_OFFSET = {top: 20, left: 20, right: 20, bottom: 30};
  * `TouchableMixin` expects us to implement some abstract methods to handle
  * interesting interactions such as `handleTouchablePress`.
  */
-const TouchableBounce = createReactClass({
+const TouchableBounce = ((createReactClass({
   displayName: 'TouchableBounce',
   mixins: [Touchable.Mixin, NativeMethodsMixin],
 
   propTypes: {
-    /**
-     * When true, indicates that the view is an accessibility element. By default,
-     * all the touchable elements are accessible.
-     */
-    accessible: PropTypes.bool,
+    ...TouchableWithoutFeedback.propTypes,
 
-    onPress: PropTypes.func,
-    onPressIn: PropTypes.func,
-    onPressOut: PropTypes.func,
     // The function passed takes a callback to start the animation which should
     // be run after this onPress handler is done. You can use this (for example)
     // to update UI before starting the animation.
@@ -61,17 +71,13 @@ const TouchableBounce = createReactClass({
      * is disabled. Ensure you pass in a constant to reduce memory allocations.
      */
     pressRetentionOffset: EdgeInsetsPropType,
-    /**
-     * This defines how far your touch can start away from the button. This is
-     * added to `pressRetentionOffset` when moving off of the button.
-     * ** NOTE **
-     * The touch area never extends past the parent view bounds and the Z-index
-     * of sibling views always takes precedence if a touch hits two overlapping
-     * views.
-     */
-    hitSlop: EdgeInsetsPropType,
     releaseVelocity: PropTypes.number.isRequired,
     releaseBounciness: PropTypes.number.isRequired,
+    /**
+     * Style to apply to the container/underlay. Most commonly used to make sure
+     * rounded corners match the wrapped component.
+     */
+    style: ViewPropTypes.style,
   },
 
   getDefaultProps: function() {
@@ -138,7 +144,6 @@ const TouchableBounce = createReactClass({
   },
 
   touchableGetPressRectOffset: function(): typeof PRESS_RETENTION_OFFSET {
-    // $FlowFixMe Invalid prop usage
     return this.props.pressRetentionOffset || PRESS_RETENTION_OFFSET;
   },
 
@@ -153,30 +158,12 @@ const TouchableBounce = createReactClass({
   render: function(): React.Element<any> {
     return (
       <Animated.View
-        /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-         * comment suppresses an error when upgrading Flow's support for React.
-         * To see the error delete this comment and run Flow. */
         style={[{transform: [{scale: this.state.scale}]}, this.props.style]}
         accessible={this.props.accessible !== false}
-        /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-         * comment suppresses an error when upgrading Flow's support for React.
-         * To see the error delete this comment and run Flow. */
         accessibilityLabel={this.props.accessibilityLabel}
-        /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-         * comment suppresses an error when upgrading Flow's support for React.
-         * To see the error delete this comment and run Flow. */
         accessibilityComponentType={this.props.accessibilityComponentType}
-        /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-         * comment suppresses an error when upgrading Flow's support for React.
-         * To see the error delete this comment and run Flow. */
         accessibilityTraits={this.props.accessibilityTraits}
-        /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-         * comment suppresses an error when upgrading Flow's support for React.
-         * To see the error delete this comment and run Flow. */
         nativeID={this.props.nativeID}
-        /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-         * comment suppresses an error when upgrading Flow's support for React.
-         * To see the error delete this comment and run Flow. */
         testID={this.props.testID}
         hitSlop={this.props.hitSlop}
         onStartShouldSetResponder={this.touchableHandleStartShouldSetResponder}
@@ -198,6 +185,6 @@ const TouchableBounce = createReactClass({
       </Animated.View>
     );
   },
-});
+}): any): React.ComponentType<Props>);
 
 module.exports = TouchableBounce;

From 0e707ff8436c93251ce6a831ac1f760e60ffdf1c Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sun, 13 May 2018 01:38:36 -0700
Subject: [PATCH 0542/1109] Clean up TextInput

Reviewed By: yungsters

Differential Revision: D7984843

fbshipit-source-id: 17259ade77f08d37dff9bb85984798f99885ad86
---
 Libraries/Components/TextInput/TextInput.js | 8 +-------
 1 file changed, 1 insertion(+), 7 deletions(-)

diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index 0cdfdd43994f..a79324fbf01b 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -22,9 +22,6 @@ const StyleSheet = require('StyleSheet');
 const Text = require('Text');
 const TextAncestor = require('TextAncestor');
 const TextInputState = require('TextInputState');
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
 const TimerMixin = require('react-timer-mixin');
 const TouchableWithoutFeedback = require('TouchableWithoutFeedback');
 const UIManager = require('UIManager');
@@ -33,9 +30,6 @@ const ViewPropTypes = require('ViewPropTypes');
 const emptyFunction = require('fbjs/lib/emptyFunction');
 const invariant = require('fbjs/lib/invariant');
 const requireNativeComponent = require('requireNativeComponent');
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
 const warning = require('fbjs/lib/warning');
 
 let AndroidTextInput;
@@ -399,6 +393,7 @@ const TextInput = createReactClass({
      * Only called for multiline text inputs.
      */
     onContentSizeChange: PropTypes.func,
+    onTextInput: PropTypes.func,
     /**
      * Callback that is called when text input ends.
      */
@@ -1040,7 +1035,6 @@ const TextInput = createReactClass({
   },
 
   _onTextInput: function(event: Event) {
-    // $FlowFixMe Invalid prop usage
     this.props.onTextInput && this.props.onTextInput(event);
   },
 

From 053c7b2a84d97b0270d5c81d89fe39f18e91687f Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sun, 13 May 2018 01:38:38 -0700
Subject: [PATCH 0543/1109] Adding a Stringish type

Reviewed By: yungsters

Differential Revision: D7984925

fbshipit-source-id: b58bff2fa172f8127d70986accb45af1afca4d68
---
 flow/Stringish.js | 14 ++++++++++++++
 1 file changed, 14 insertions(+)
 create mode 100644 flow/Stringish.js

diff --git a/flow/Stringish.js b/flow/Stringish.js
new file mode 100644
index 000000000000..55d0e3707ac5
--- /dev/null
+++ b/flow/Stringish.js
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ * @format
+ */
+
+// This type allows Facebook to internally Override
+// this type to allow our internationalization type which
+// is a string at runtime but Flow doesn't know that.
+declare type Stringish = string;

From c8bcda8150278fde07331ca6958976b2b3395688 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:08:58 -0700
Subject: [PATCH 0544/1109] FlowType TextInput

Reviewed By: yungsters

Differential Revision: D7985109

fbshipit-source-id: 294919bce64b21cab4f37262a7da9e68cb67207f
---
 Libraries/Components/TextInput/TextInput.js | 153 +++++++++++++++++++-
 RNTester/js/TextInputExample.ios.js         |   4 +-
 2 files changed, 154 insertions(+), 3 deletions(-)

diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index a79324fbf01b..a9f6716a340f 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -32,6 +32,10 @@ const invariant = require('fbjs/lib/invariant');
 const requireNativeComponent = require('requireNativeComponent');
 const warning = require('fbjs/lib/warning');
 
+import type {ColorValue} from 'StyleSheetTypes';
+import type {TextStyleProp} from 'StyleSheet';
+import type {ViewProps} from 'ViewPropTypes';
+
 let AndroidTextInput;
 let RCTMultilineTextInputView;
 let RCTSinglelineTextInputView;
@@ -69,6 +73,144 @@ const DataDetectorTypes = [
   'all',
 ];
 
+type DataDetectorTypesType =
+  | 'phoneNumber'
+  | 'link'
+  | 'address'
+  | 'calendarEvent'
+  | 'none'
+  | 'all';
+
+export type KeyboardType =
+  // Cross Platform
+  | 'default'
+  | 'email-address'
+  | 'numeric'
+  | 'phone-pad'
+  | 'number-pad'
+  // iOS-only
+  | 'ascii-capable'
+  | 'numbers-and-punctuation'
+  | 'url'
+  | 'name-phone-pad'
+  | 'decimal-pad'
+  | 'twitter'
+  | 'web-search'
+  // Android-only
+  | 'visible-password';
+
+export type ReturnKeyType =
+  // Cross Platform
+  | 'done'
+  | 'go'
+  | 'next'
+  | 'search'
+  | 'send'
+  // Android-only
+  | 'none'
+  | 'previous'
+  // iOS-only
+  | 'default'
+  | 'emergency-call'
+  | 'google'
+  | 'join'
+  | 'route'
+  | 'yahoo';
+
+export type AutoCapitalize = 'none' | 'sentences' | 'words' | 'characters';
+
+type IOSProps = $ReadOnly<{|
+  spellCheck?: ?boolean,
+  keyboardAppearance?: ?('default' | 'light' | 'dark'),
+  enablesReturnKeyAutomatically?: ?boolean,
+  selectionState?: ?DocumentSelectionState,
+  clearButtonMode?: ?('never' | 'while-editing' | 'unless-editing' | 'always'),
+  clearTextOnFocus?: ?boolean,
+  dataDetectorTypes?:
+    | ?DataDetectorTypesType
+    | $ReadOnlyArray<DataDetectorTypesType>,
+  inputAccessoryViewID?: ?string,
+  textContentType?: ?(
+    | 'none'
+    | 'URL'
+    | 'addressCity'
+    | 'addressCityAndState'
+    | 'addressState'
+    | 'countryName'
+    | 'creditCardNumber'
+    | 'emailAddress'
+    | 'familyName'
+    | 'fullStreetAddress'
+    | 'givenName'
+    | 'jobTitle'
+    | 'location'
+    | 'middleName'
+    | 'name'
+    | 'namePrefix'
+    | 'nameSuffix'
+    | 'nickname'
+    | 'organizationName'
+    | 'postalCode'
+    | 'streetAddressLine1'
+    | 'streetAddressLine2'
+    | 'sublocality'
+    | 'telephoneNumber'
+    | 'username'
+    | 'password'
+  ),
+|}>;
+
+type AndroidProps = $ReadOnly<{|
+  returnKeyLabel?: ?string,
+  numberOfLines?: ?number,
+  disableFullscreenUI?: ?boolean,
+  textBreakStrategy?: ?('simple' | 'highQuality' | 'balanced'),
+  underlineColorAndroid?: ?ColorValue,
+  inlineImageLeft?: ?string,
+  inlineImagePadding?: ?number,
+|}>;
+
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  ...IOSProps,
+  ...AndroidProps,
+  autoCapitalize?: ?AutoCapitalize,
+  autoCorrect?: ?boolean,
+  autoFocus?: ?boolean,
+  allowFontScaling?: ?boolean,
+  editable?: ?boolean,
+  keyboardType?: ?KeyboardType,
+  returnKeyType?: ?ReturnKeyType,
+  maxLength?: ?number,
+  multiline?: ?boolean,
+  onBlur?: ?Function,
+  onFocus?: ?Function,
+  onChange?: ?Function,
+  onChangeText?: ?Function,
+  onContentSizeChange?: ?Function,
+  onTextInput?: ?Function,
+  onEndEditing?: ?Function,
+  onSelectionChange?: ?Function,
+  onSubmitEditing?: ?Function,
+  onKeyPress?: ?Function,
+  onScroll?: ?Function,
+  placeholder?: ?Stringish,
+  placeholderTextColor?: ?ColorValue,
+  secureTextEntry?: ?boolean,
+  selectionColor?: ?ColorValue,
+  selection?: ?$ReadOnly<{|
+    start: number,
+    end?: ?number,
+  |}>,
+  value?: ?Stringish,
+  defaultValue?: ?Stringish,
+  selectTextOnFocus?: ?boolean,
+  blurOnSubmit?: ?boolean,
+  style?: ?TextStyleProp,
+  caretHidden?: ?boolean,
+  contextMenuHidden?: ?boolean,
+|}>;
+
 /**
  * A foundational component for inputting text into the app via a
  * keyboard. Props provide configurability for several features, such as
@@ -1043,6 +1185,15 @@ const TextInput = createReactClass({
   },
 });
 
+class InternalTextInputType extends ReactNative.NativeComponent<Props> {
+  clear() {}
+
+  // $FlowFixMe
+  isFocused(): boolean {}
+}
+
+const TypedTextInput = ((TextInput: any): Class<InternalTextInputType>);
+
 const styles = StyleSheet.create({
   multilineInput: {
     // This default top inset makes RCTMultilineTextInputView seem as close as possible
@@ -1052,4 +1203,4 @@ const styles = StyleSheet.create({
   },
 });
 
-module.exports = TextInput;
+module.exports = TypedTextInput;
diff --git a/RNTester/js/TextInputExample.ios.js b/RNTester/js/TextInputExample.ios.js
index 0d53264772e3..d536d46d8b23 100644
--- a/RNTester/js/TextInputExample.ios.js
+++ b/RNTester/js/TextInputExample.ios.js
@@ -288,10 +288,10 @@ class BlurOnSubmitExample extends React.Component<{}> {
 }
 
 type SelectionExampleState = {
-  selection: {
+  selection: {|
     start: number,
     end?: number,
-  },
+  |},
   value: string,
 };
 

From ffda0178509ed92396f15db37a41d3d668ade4e6 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:00 -0700
Subject: [PATCH 0545/1109] Removing unnecessary FlowFixMe

Reviewed By: yungsters

Differential Revision: D7985116

fbshipit-source-id: 97a7a37b2ffe7a81669973f9dca6824a4f352a07
---
 Libraries/Components/Touchable/TouchableBounce.js | 5 +----
 1 file changed, 1 insertion(+), 4 deletions(-)

diff --git a/Libraries/Components/Touchable/TouchableBounce.js b/Libraries/Components/Touchable/TouchableBounce.js
index b9fe3d1523a4..4a61ef0bc89d 100644
--- a/Libraries/Components/Touchable/TouchableBounce.js
+++ b/Libraries/Components/Touchable/TouchableBounce.js
@@ -174,10 +174,7 @@ const TouchableBounce = ((createReactClass({
         onResponderMove={this.touchableHandleResponderMove}
         onResponderRelease={this.touchableHandleResponderRelease}
         onResponderTerminate={this.touchableHandleResponderTerminate}>
-        {
-          // $FlowFixMe(>=0.41.0)
-          this.props.children
-        }
+        {this.props.children}
         {Touchable.renderDebugView({
           color: 'orange',
           hitSlop: this.props.hitSlop,

From 1419c7a7fde5b216cd3203bff791d9b1f17f22cd Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:03 -0700
Subject: [PATCH 0546/1109] Migrate ScrollView fake type to
 ReactNative.NativeComponent

Reviewed By: yungsters

Differential Revision: D7985122

fbshipit-source-id: b78fc6ad84485e8aa42657c2b21d70c9f3a271d6
---
 Libraries/Components/ScrollView/InternalScrollViewType.js | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/Libraries/Components/ScrollView/InternalScrollViewType.js b/Libraries/Components/ScrollView/InternalScrollViewType.js
index a97ca9f43641..a1d42bb46a6d 100644
--- a/Libraries/Components/ScrollView/InternalScrollViewType.js
+++ b/Libraries/Components/ScrollView/InternalScrollViewType.js
@@ -8,13 +8,13 @@
  * @flow
  */
 
-const React = require('React');
+const ReactNative = require('ReactNative');
 
 // This class is purely a facsimile of ScrollView so that we can
 // properly type it with Flow before migrating ScrollView off of
 // createReactClass. If there are things missing here that are in
 // ScrollView, that is unintentional.
-class InternalScrollViewType<Props> extends React.Component<Props> {
+class InternalScrollViewType<Props> extends ReactNative.NativeComponent<Props> {
   scrollTo(
     y?: number | {x?: number, y?: number, animated?: boolean},
     x?: number,
@@ -24,7 +24,6 @@ class InternalScrollViewType<Props> extends React.Component<Props> {
   flashScrollIndicators() {}
   scrollToEnd(options?: {animated?: boolean}) {}
   scrollWithoutAnimationTo(y: number = 0, x: number = 0) {}
-  setNativeProps(props: Object) {}
 
   getScrollResponder(): any {}
   getScrollableNode(): any {}

From af6e2eb02d3651f869b5436e68e61ef3ab3405a0 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:06 -0700
Subject: [PATCH 0547/1109] Removing unnecessary FlowFixMe

Reviewed By: yungsters

Differential Revision: D7985749

fbshipit-source-id: ba7e152749c5a5cac134b51e0229dc11870bb3e0
---
 Libraries/Components/ScrollView/ScrollView.js |  3 ---
 Libraries/Lists/ListView/ListView.js          | 10 ----------
 2 files changed, 13 deletions(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 0822ba140d4e..09928bf047d7 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -33,9 +33,6 @@ const flattenStyle = require('flattenStyle');
 const invariant = require('fbjs/lib/invariant');
 const processDecelerationRate = require('processDecelerationRate');
 const requireNativeComponent = require('requireNativeComponent');
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
 const warning = require('fbjs/lib/warning');
 const resolveAssetSource = require('resolveAssetSource');
 
diff --git a/Libraries/Lists/ListView/ListView.js b/Libraries/Lists/ListView/ListView.js
index cd168bc656cd..8a1753d2d60a 100644
--- a/Libraries/Lists/ListView/ListView.js
+++ b/Libraries/Lists/ListView/ListView.js
@@ -18,15 +18,8 @@ const RCTScrollViewManager = require('NativeModules').ScrollViewManager;
 const ScrollView = require('ScrollView');
 const ScrollResponder = require('ScrollResponder');
 const StaticRenderer = require('StaticRenderer');
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
 const TimerMixin = require('react-timer-mixin');
 const View = require('View');
-
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
 const cloneReferencedElement = require('react-clone-referenced-element');
 const createReactClass = require('create-react-class');
 const isEmpty = require('isEmpty');
@@ -423,9 +416,6 @@ const ListView = createReactClass({
       const rowIDs = allRowIDs[sectionIdx];
       if (rowIDs.length === 0) {
         if (this.props.enableEmptySections === undefined) {
-          /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses
-           * an error found when Flow v0.54 was deployed. To see the error
-           * delete this comment and run Flow. */
           const warning = require('fbjs/lib/warning');
           warning(
             false,

From 4b1ecb62045fbb78764d1f51030f2253be705c5c Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:10 -0700
Subject: [PATCH 0548/1109] Flowtype ListView

Reviewed By: yungsters

Differential Revision: D7985836

fbshipit-source-id: 6e0944a8d2fb85aabc34dfd3125a07b208749f21
---
 Libraries/Components/ScrollView/ScrollView.js |  2 +-
 .../SwipeableRow/SwipeableListView.js         |  2 ++
 Libraries/Inspector/NetworkOverlay.js         |  1 +
 Libraries/Lists/FlatList.js                   |  9 +++++-
 .../Lists/ListView/InternalListViewType.js    | 30 ++++++++++++++++++
 Libraries/Lists/ListView/ListView.js          | 31 +++++++++++++++++--
 Libraries/Lists/MetroListView.js              |  2 ++
 Libraries/Lists/SectionList.js                |  1 +
 8 files changed, 73 insertions(+), 5 deletions(-)
 create mode 100644 Libraries/Lists/ListView/InternalListViewType.js

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 09928bf047d7..4b1b76848c7a 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -99,7 +99,7 @@ type VRProps = $ReadOnly<{|
   scrollBarThumbImage?: ?($ReadOnly<{||}> | number),
 |}>;
 
-type Props = $ReadOnly<{|
+export type Props = $ReadOnly<{|
   ...ViewProps,
   ...TouchableProps,
   ...IOSProps,
diff --git a/Libraries/Experimental/SwipeableRow/SwipeableListView.js b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
index e449501c7183..bae4eb5f2ff8 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableListView.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableListView.js
@@ -117,9 +117,11 @@ class SwipeableListView extends React.Component<Props, State> {
 
   render(): React.Node {
     return (
+      // $FlowFixMe Found when typing ListView
       <ListView
         {...this.props}
         ref={ref => {
+          // $FlowFixMe Found when typing ListView
           this._listViewRef = ref;
         }}
         dataSource={this.state.dataSource.getDataSource()}
diff --git a/Libraries/Inspector/NetworkOverlay.js b/Libraries/Inspector/NetworkOverlay.js
index 46628eccca71..ee60a7e00492 100644
--- a/Libraries/Inspector/NetworkOverlay.js
+++ b/Libraries/Inspector/NetworkOverlay.js
@@ -497,6 +497,7 @@ class NetworkOverlay extends React.Component<
           renderRow={this._renderRow}
           enableEmptySections={true}
           renderSeparator={this._renderSeperator}
+          // $FlowFixMe Found when typing ListView
           onLayout={this._listViewOnLayout}
         />
       </View>
diff --git a/Libraries/Lists/FlatList.js b/Libraries/Lists/FlatList.js
index 5a0827be1df8..cb909bbe74c1 100644
--- a/Libraries/Lists/FlatList.js
+++ b/Libraries/Lists/FlatList.js
@@ -346,6 +346,7 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
     viewPosition?: number,
   }) {
     if (this._listRef) {
+      // $FlowFixMe Found when typing ListView
       this._listRef.scrollToIndex(params);
     }
   }
@@ -362,6 +363,7 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
     viewPosition?: number,
   }) {
     if (this._listRef) {
+      // $FlowFixMe Found when typing ListView
       this._listRef.scrollToItem(params);
     }
   }
@@ -373,6 +375,7 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
    */
   scrollToOffset(params: {animated?: ?boolean, offset: number}) {
     if (this._listRef) {
+      // $FlowFixMe Found when typing ListView
       this._listRef.scrollToOffset(params);
     }
   }
@@ -384,6 +387,7 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
    */
   recordInteraction() {
     if (this._listRef) {
+      // $FlowFixMe Found when typing ListView
       this._listRef.recordInteraction();
     }
   }
@@ -395,6 +399,7 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
    */
   flashScrollIndicators() {
     if (this._listRef) {
+      // $FlowFixMe Found when typing ListView
       this._listRef.flashScrollIndicators();
     }
   }
@@ -404,12 +409,14 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
    */
   getScrollResponder() {
     if (this._listRef) {
+      // $FlowFixMe Found when typing ListView
       return this._listRef.getScrollResponder();
     }
   }
 
   getScrollableNode() {
     if (this._listRef) {
+      // $FlowFixMe Found when typing ListView
       return this._listRef.getScrollableNode();
     }
   }
@@ -472,7 +479,7 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
   }
 
   _hasWarnedLegacy = false;
-  _listRef: null | VirtualizedList | ListView;
+  _listRef: null | VirtualizedList | ListView | MetroListView;
   _virtualizedListPairs: Array<ViewabilityConfigCallbackPair> = [];
 
   _captureRef = ref => {
diff --git a/Libraries/Lists/ListView/InternalListViewType.js b/Libraries/Lists/ListView/InternalListViewType.js
new file mode 100644
index 000000000000..1df93fd565d9
--- /dev/null
+++ b/Libraries/Lists/ListView/InternalListViewType.js
@@ -0,0 +1,30 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @format
+ * @flow
+ */
+
+const React = require('React');
+const ListViewDataSource = require('ListViewDataSource');
+
+// This class is purely a facsimile of ListView so that we can
+// properly type it with Flow before migrating ListView off of
+// createReactClass. If there are things missing here that are in
+// ListView, that is unintentional.
+class InternalListViewType<Props> extends React.Component<Props> {
+  static DataSource = ListViewDataSource;
+  setNativeProps(props: Object) {}
+  flashScrollIndicators() {}
+  getScrollResponder(): any {}
+  getScrollableNode(): any {}
+  // $FlowFixMe
+  getMetrics(): Object {}
+  scrollTo(...args: Array<mixed>) {}
+  scrollToEnd(options?: ?{animated?: ?boolean}) {}
+}
+
+module.exports = InternalListViewType;
diff --git a/Libraries/Lists/ListView/ListView.js b/Libraries/Lists/ListView/ListView.js
index 8a1753d2d60a..10ab9aef3101 100644
--- a/Libraries/Lists/ListView/ListView.js
+++ b/Libraries/Lists/ListView/ListView.js
@@ -9,6 +9,7 @@
  */
 'use strict';
 
+const InternalListViewType = require('InternalListViewType');
 const ListViewDataSource = require('ListViewDataSource');
 const Platform = require('Platform');
 const React = require('React');
@@ -25,12 +26,36 @@ const createReactClass = require('create-react-class');
 const isEmpty = require('isEmpty');
 const merge = require('merge');
 
+import type {Props as ScrollViewProps} from 'ScrollView';
+
 const DEFAULT_PAGE_SIZE = 1;
 const DEFAULT_INITIAL_ROWS = 10;
 const DEFAULT_SCROLL_RENDER_AHEAD = 1000;
 const DEFAULT_END_REACHED_THRESHOLD = 1000;
 const DEFAULT_SCROLL_CALLBACK_THROTTLE = 50;
 
+type Props = $ReadOnly<{|
+  ...ScrollViewProps,
+
+  dataSource: ListViewDataSource,
+  renderSeparator?: ?Function,
+  renderRow: Function,
+  initialListSize?: ?number,
+  onEndReached?: ?Function,
+  onEndReachedThreshold?: ?number,
+  pageSize?: ?number,
+  renderFooter?: ?Function,
+  renderHeader?: ?Function,
+  renderSectionHeader?: ?Function,
+  renderScrollComponent?: ?Function,
+  scrollRenderAheadDistance?: ?number,
+  onChangeVisibleRows?: ?Function,
+  removeClippedSubviews?: ?boolean,
+  stickySectionHeadersEnabled?: ?boolean,
+  stickyHeaderIndices?: ?$ReadOnlyArray<number>,
+  enableEmptySections?: ?boolean,
+|}>;
+
 /**
  * DEPRECATED - use one of the new list components, such as [`FlatList`](docs/flatlist.html)
  * or [`SectionList`](docs/sectionlist.html) for bounded memory use, fewer bugs,
@@ -92,7 +117,7 @@ const ListView = createReactClass({
   displayName: 'ListView',
   _childFrames: ([]: Array<Object>),
   _sentEndForContentLength: (null: ?number),
-  _scrollComponent: (null: any),
+  _scrollComponent: (null: ?React.ElementRef<typeof ScrollView>),
   _prevRenderedRowsCount: 0,
   _visibleRows: ({}: Object),
   scrollProperties: ({}: Object),
@@ -555,7 +580,7 @@ const ListView = createReactClass({
       );
   },
 
-  _setScrollComponentRef: function(scrollComponent: Object) {
+  _setScrollComponentRef: function(scrollComponent) {
     this._scrollComponent = scrollComponent;
   },
 
@@ -752,4 +777,4 @@ const ListView = createReactClass({
   },
 });
 
-module.exports = ListView;
+module.exports = ((ListView: any): Class<InternalListViewType<Props>>);
diff --git a/Libraries/Lists/MetroListView.js b/Libraries/Lists/MetroListView.js
index c8d7a45a662a..1d59dba8d165 100644
--- a/Libraries/Lists/MetroListView.js
+++ b/Libraries/Lists/MetroListView.js
@@ -138,6 +138,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
   }
   render() {
     return (
+      // $FlowFixMe Found when typing ListView
       <ListView
         {...this.props}
         dataSource={this.state.ds}
@@ -170,6 +171,7 @@ class MetroListView extends React.Component<Props, $FlowFixMeState> {
     } else {
       invariant(!props.sections, 'Cannot have both sections and items props.');
       return {
+        // $FlowFixMe Found when typing ListView
         ds: state.ds.cloneWithRows(props.items),
         sectionHeaderData,
       };
diff --git a/Libraries/Lists/SectionList.js b/Libraries/Lists/SectionList.js
index 17a4f84711e0..9d7d2eb8195d 100644
--- a/Libraries/Lists/SectionList.js
+++ b/Libraries/Lists/SectionList.js
@@ -284,6 +284,7 @@ class SectionList<SectionT: SectionBase<any>> extends React.PureComponent<
    */
   recordInteraction() {
     const listRef = this._wrapperListRef && this._wrapperListRef.getListRef();
+    // $FlowFixMe Found when typing ListView
     listRef && listRef.recordInteraction();
   }
 

From 891dfc3da4b5825097aedf73ff04e8982c00aeff Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:13 -0700
Subject: [PATCH 0549/1109] Flowtype RefreshControl

Reviewed By: yungsters

Differential Revision: D7985835

fbshipit-source-id: 67a27cb99738d99959b1c795af95d0415a84f1b9
---
 .../RefreshControl/RefreshControl.js          | 35 ++++++++++++++++++-
 1 file changed, 34 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/RefreshControl/RefreshControl.js b/Libraries/Components/RefreshControl/RefreshControl.js
index e9389c1a400f..665a1bd91ea9 100644
--- a/Libraries/Components/RefreshControl/RefreshControl.js
+++ b/Libraries/Components/RefreshControl/RefreshControl.js
@@ -14,12 +14,16 @@ const ColorPropType = require('ColorPropType');
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const Platform = require('Platform');
 const React = require('React');
+const ReactNative = require('ReactNative');
 const PropTypes = require('prop-types');
 const ViewPropTypes = require('ViewPropTypes');
 
 const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {ColorValue} from 'StyleSheetTypes';
+import type {ViewProps} from 'ViewPropTypes';
+
 if (Platform.OS === 'android') {
   const AndroidSwipeRefreshLayout = require('UIManager')
     .AndroidSwipeRefreshLayout;
@@ -30,6 +34,31 @@ if (Platform.OS === 'android') {
   var RefreshLayoutConsts = {SIZE: {}};
 }
 
+type IOSProps = $ReadOnly<{|
+  tintColor?: ?ColorValue,
+  titleColor?: ?ColorValue,
+  title?: ?string,
+|}>;
+
+type AndroidProps = $ReadOnly<{|
+  enabled?: ?boolean,
+  colors?: ?$ReadOnlyArray<ColorValue>,
+  progressBackgroundColor?: ?ColorValue,
+  size?: ?(
+    | typeof RefreshLayoutConsts.SIZE.DEFAULT
+    | typeof RefreshLayoutConsts.SIZE.LARGE
+  ),
+  progressViewOffset?: ?number,
+|}>;
+
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  ...IOSProps,
+  ...AndroidProps,
+  onRefresh?: ?Function,
+  refreshing: boolean,
+|}>;
+
 /**
  * This component is used inside a ScrollView or ListView to add pull to refresh
  * functionality. When the ScrollView is at `scrollY: 0`, swiping down
@@ -180,6 +209,10 @@ const RefreshControl = createReactClass({
   },
 });
 
+class TypedRefreshControl extends ReactNative.NativeComponent<Props> {
+  static SIZE = RefreshLayoutConsts.SIZE;
+}
+
 if (Platform.OS === 'ios') {
   var NativeRefreshControl = requireNativeComponent(
     'RCTRefreshControl',
@@ -192,4 +225,4 @@ if (Platform.OS === 'ios') {
   );
 }
 
-module.exports = RefreshControl;
+module.exports = ((RefreshControl: any): Class<TypedRefreshControl>);

From cbe045a95f1ca53d99ae521742a93299a53d6136 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:16 -0700
Subject: [PATCH 0550/1109] Flowtype Slider

Reviewed By: yungsters

Differential Revision: D7985857

fbshipit-source-id: 8b6b9f58aa89b898fa38d1cfc0564df5f64741a2
---
 Libraries/Components/Slider/Slider.js | 36 ++++++++++++++++++++++++++-
 1 file changed, 35 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index 8e9eabd43618..4c4c0b979028 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -13,6 +13,7 @@
 const Image = require('Image');
 const ColorPropType = require('ColorPropType');
 const NativeMethodsMixin = require('NativeMethodsMixin');
+const ReactNative = require('ReactNative');
 const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const Platform = require('Platform');
 const React = require('React');
@@ -23,8 +24,41 @@ const ViewPropTypes = require('ViewPropTypes');
 const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {ImageSource} from 'ImageSource';
+import type {ViewStyleProp} from 'StyleSheet';
+import type {ColorValue} from 'StyleSheetTypes';
+import type {ViewProps} from 'ViewPropTypes';
+
 type Event = Object;
 
+type IOSProps = $ReadOnly<{|
+  trackImage?: ?ImageSource,
+  minimumTrackImage?: ?ImageSource,
+  maximumTrackImage?: ?ImageSource,
+  thumbImage?: ?ImageSource,
+|}>;
+
+type AndroidProps = $ReadOnly<{|
+  thumbTintColor?: ?ColorValue,
+|}>;
+
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  ...IOSProps,
+  ...AndroidProps,
+  style?: ?ViewStyleProp,
+  value?: ?number,
+  step?: ?number,
+  minimumValue?: ?number,
+  maximumValue?: ?number,
+  minimumTrackTintColor?: ?ColorValue,
+  maximumTrackTintColor?: ?ColorValue,
+  disabled?: ?boolean,
+  onValueChange?: ?Function,
+  onSlidingComplete?: ?Function,
+  testID?: ?string,
+|}>;
+
 /**
  * A component used to select a single value from a range of values.
  *
@@ -282,4 +316,4 @@ if (Platform.OS === 'android') {
 }
 const RCTSlider = requireNativeComponent('RCTSlider', Slider, options);
 
-module.exports = Slider;
+module.exports = ((Slider: any): Class<ReactNative.NativeComponent<Props>>);

From 06052a2330fc9c1dd0d56c6bbe5a17703f80c6b9 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:18 -0700
Subject: [PATCH 0551/1109] Flowtype Switch

Reviewed By: yungsters

Differential Revision: D7985880

fbshipit-source-id: eaaff2188b8257d09e1bf628d19dae6dfb4c2fc6
---
 Libraries/Components/Switch/Switch.js | 20 +++++++++++++++++---
 1 file changed, 17 insertions(+), 3 deletions(-)

diff --git a/Libraries/Components/Switch/Switch.js b/Libraries/Components/Switch/Switch.js
index 88f916cf2040..1730e7cbf019 100644
--- a/Libraries/Components/Switch/Switch.js
+++ b/Libraries/Components/Switch/Switch.js
@@ -14,6 +14,7 @@ const ColorPropType = require('ColorPropType');
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const Platform = require('Platform');
 const React = require('React');
+const ReactNative = require('ReactNative');
 const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
 const ViewPropTypes = require('ViewPropTypes');
@@ -21,11 +22,24 @@ const ViewPropTypes = require('ViewPropTypes');
 const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
-type DefaultProps = {
+import type {ColorValue} from 'StyleSheetTypes';
+import type {ViewProps} from 'ViewPropTypes';
+
+type DefaultProps = $ReadOnly<{|
   value: boolean,
   disabled: boolean,
-};
+|}>;
 
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  value?: ?boolean,
+  disabled?: ?boolean,
+  onValueChange?: ?Function,
+  testID?: ?string,
+  tintColor?: ?ColorValue,
+  onTintColor?: ?ColorValue,
+  thumbTintColor?: ?ColorValue,
+|}>;
 /**
  * Renders a boolean input.
  *
@@ -161,4 +175,4 @@ if (Platform.OS === 'android') {
   });
 }
 
-module.exports = Switch;
+module.exports = ((Switch: any): Class<ReactNative.NativeComponent<Props>>);

From d796129895f2778d32a1f16df40cd105cb4e458b Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:21 -0700
Subject: [PATCH 0552/1109] Delete LazyRenderer

Summary: This isn't used internally at Facebook and we have no public documentation for this component. If people are interested in using it they can easily reproduce this function outside of core.

Reviewed By: yungsters

Differential Revision: D7985955

fbshipit-source-id: 859878a858cbcb42fec7f9bd04e5d7574801e445
---
 Libraries/Components/LazyRenderer.js | 44 ----------------------------
 1 file changed, 44 deletions(-)
 delete mode 100644 Libraries/Components/LazyRenderer.js

diff --git a/Libraries/Components/LazyRenderer.js b/Libraries/Components/LazyRenderer.js
deleted file mode 100644
index 23164141a3ed..000000000000
--- a/Libraries/Components/LazyRenderer.js
+++ /dev/null
@@ -1,44 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- */
-
-'use strict';
-
-const React = require('React');
-const createReactClass = require('create-react-class');
-const PropTypes = require('prop-types');
-const TimerMixin = require('react-timer-mixin');
-
-const LazyRenderer = createReactClass({
-  displayName: 'LazyRenderer',
-  mixin: [TimerMixin],
-
-  propTypes: {
-    render: PropTypes.func.isRequired,
-  },
-
-  UNSAFE_componentWillMount: function(): void {
-    this.setState({
-      _lazyRender: true,
-    });
-  },
-
-  componentDidMount: function(): void {
-    requestAnimationFrame(() => {
-      this.setState({
-        _lazyRender: false,
-      });
-    });
-  },
-
-  render: function(): ?React.Element {
-    return this.state._lazyRender ? null : this.props.render();
-  },
-});
-
-module.exports = LazyRenderer;

From 1c66cdc7e8ce8190dfbef76629601497446b2b0a Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:23 -0700
Subject: [PATCH 0553/1109] Flowtype PickerIOS

Reviewed By: yungsters

Differential Revision: D7985960

fbshipit-source-id: 9fbce5fafe47bee1d2a527c72f3ebef85d26f9f1
---
 Libraries/Components/Picker/PickerIOS.ios.js | 26 ++++++++++++++++++--
 1 file changed, 24 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/Picker/PickerIOS.ios.js b/Libraries/Components/Picker/PickerIOS.ios.js
index 881c33ce038e..6eef251e5b4c 100644
--- a/Libraries/Components/Picker/PickerIOS.ios.js
+++ b/Libraries/Components/Picker/PickerIOS.ios.js
@@ -14,6 +14,7 @@
 
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const React = require('React');
+const ReactNative = require('ReactNative');
 const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
 const StyleSheetPropType = require('StyleSheetPropType');
@@ -26,6 +27,17 @@ const createReactClass = require('create-react-class');
 const itemStylePropType = StyleSheetPropType(TextStylePropTypes);
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {ColorValue} from 'StyleSheetTypes';
+import type {ViewProps} from 'ViewPropTypes';
+
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  color?: ?ColorValue,
+  label: string,
+  testID?: ?string,
+  value?: ?any,
+|}>;
+
 const PickerIOS = createReactClass({
   displayName: 'PickerIOS',
   mixins: [NativeMethodsMixin],
@@ -106,7 +118,13 @@ const PickerIOS = createReactClass({
   },
 });
 
-PickerIOS.Item = class extends React.Component {
+PickerIOS.Item = class extends React.Component<
+  $ReadOnly<{|
+    label: string,
+    value?: ?any,
+    color?: ?ColorValue,
+  |}>,
+> {
   static propTypes = {
     value: PropTypes.any, // string or integer basically
     label: PropTypes.string,
@@ -119,6 +137,10 @@ PickerIOS.Item = class extends React.Component {
   }
 };
 
+class TypedPickerIOS extends ReactNative.NativeComponent<Props> {
+  static Item = PickerIOS.Item;
+}
+
 const styles = StyleSheet.create({
   pickerIOS: {
     // The picker will conform to whatever width is given, but we do
@@ -144,4 +166,4 @@ const RCTPickerIOS = requireNativeComponent(
   },
 );
 
-module.exports = PickerIOS;
+module.exports = ((PickerIOS: any): Class<TypedPickerIOS>);

From c87701ba05a8524756e87c089eb92c8f3c81823e Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:26 -0700
Subject: [PATCH 0554/1109] Flowtype ProgressViewIOS

Reviewed By: yungsters

Differential Revision: D7985969

fbshipit-source-id: d351ebc26e7be2741c93ce462ae59aa13d0c1f27
---
 .../ProgressViewIOS/ProgressViewIOS.ios.js    | 19 ++++++++++++++++++-
 1 file changed, 18 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
index dde9f399fdef..a7d6d61e5b5e 100644
--- a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
+++ b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
@@ -13,6 +13,7 @@
 const Image = require('Image');
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const React = require('React');
+const ReactNative = require('ReactNative');
 const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
 const ViewPropTypes = require('ViewPropTypes');
@@ -20,6 +21,20 @@ const ViewPropTypes = require('ViewPropTypes');
 const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {ImageSource} from 'ImageSource';
+import type {ColorValue} from 'StyleSheetTypes';
+import type {ViewProps} from 'ViewPropTypes';
+
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  progressViewStyle?: ?('default' | 'bar'),
+  progress?: ?number,
+  progressTintColor?: ?ColorValue,
+  trackTintColor?: ?string,
+  progressImage?: ?ImageSource,
+  trackImage?: ?ImageSource,
+|}>;
+
 /**
  * Use `ProgressViewIOS` to render a UIProgressView on iOS.
  */
@@ -81,4 +96,6 @@ const RCTProgressView = requireNativeComponent(
   ProgressViewIOS,
 );
 
-module.exports = ProgressViewIOS;
+module.exports = ((ProgressViewIOS: any): Class<
+  ReactNative.NativeComponent<Props>,
+>);

From 113f009698dbd8f1b4c1048d77ff1eb373021083 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:28 -0700
Subject: [PATCH 0555/1109] Flowtype SegmentedControlIOS

Reviewed By: yungsters

Differential Revision: D7985978

fbshipit-source-id: 6579ad8dd5c5377571fd790149ea5cfc6b33939f
---
 .../SegmentedControlIOS.ios.js                | 20 +++++++++++++++++--
 1 file changed, 18 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
index 7324e4d88533..f0a407245041 100644
--- a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
+++ b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
@@ -12,6 +12,7 @@
 
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const React = require('React');
+const ReactNative = require('ReactNative');
 const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
 const ViewPropTypes = require('ViewPropTypes');
@@ -19,11 +20,24 @@ const ViewPropTypes = require('ViewPropTypes');
 const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {ViewProps} from 'ViewPropTypes';
+
 type DefaultProps = {
-  values: Array<string>,
+  values: $ReadOnlyArray<string>,
   enabled: boolean,
 };
 
+type Props = $ReadOnly<{|
+  ...ViewProps,
+  values?: ?$ReadOnlyArray<string>,
+  selectedIndex?: ?number,
+  onValueChange?: ?Function,
+  onChange?: ?Function,
+  enabled?: ?boolean,
+  tintColor?: ?string,
+  momentary?: ?boolean,
+|}>;
+
 const SEGMENTED_CONTROL_REFERENCE = 'segmentedcontrol';
 
 type Event = Object;
@@ -130,4 +144,6 @@ const RCTSegmentedControl = requireNativeComponent(
   SegmentedControlIOS,
 );
 
-module.exports = SegmentedControlIOS;
+module.exports = ((SegmentedControlIOS: any): Class<
+  ReactNative.NativeComponent<Props>,
+>);

From 5e6c51b19e433078f19e7e423849d648c6d770ac Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:31 -0700
Subject: [PATCH 0556/1109] Flowtype SwipeableRow

Reviewed By: yungsters

Differential Revision: D7985995

fbshipit-source-id: 4fd1085291c47be4a2753dc1252dc6a3c66269d9
---
 .../Experimental/SwipeableRow/SwipeableRow.js | 21 ++++++++++++++++++-
 1 file changed, 20 insertions(+), 1 deletion(-)

diff --git a/Libraries/Experimental/SwipeableRow/SwipeableRow.js b/Libraries/Experimental/SwipeableRow/SwipeableRow.js
index 26361625c5fc..3cbeb3d6ca25 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableRow.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableRow.js
@@ -57,6 +57,20 @@ const RIGHT_SWIPE_BOUNCE_BACK_DURATION = 300;
  */
 const RIGHT_SWIPE_THRESHOLD = 30 * SLOW_SPEED_SWIPE_FACTOR;
 
+type Props = $ReadOnly<{|
+  children?: ?React.Node,
+  isOpen?: ?boolean,
+  maxSwipeDistance?: ?number,
+  onClose?: ?Function,
+  onOpen?: ?Function,
+  onSwipeEnd?: ?Function,
+  onSwipeStart?: ?Function,
+  preventSwipeRight?: ?boolean,
+  shouldBounceOnMount?: ?boolean,
+  slideoutView?: ?React.Node,
+  swipeThreshold?: ?number,
+|}>;
+
 /**
  * Creates a swipable row that allows taps on the main item and a custom View
  * on the item hidden behind the row. Typically this should be used in
@@ -374,6 +388,11 @@ const SwipeableRow = createReactClass({
   },
 });
 
+// TODO: Delete this when `SwipeableRow` uses class syntax.
+class TypedSwipeableRow extends React.Component<Props> {
+  close() {}
+}
+
 const styles = StyleSheet.create({
   slideOutContainer: {
     bottom: 0,
@@ -384,4 +403,4 @@ const styles = StyleSheet.create({
   },
 });
 
-module.exports = SwipeableRow;
+module.exports = ((SwipeableRow: any): Class<TypedSwipeableRow>);

From 75ad71ee2456af9a84f7729e0950420210c927db Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:33 -0700
Subject: [PATCH 0557/1109] Delete TextUpdateTest

Reviewed By: yungsters

Differential Revision: D7985997

fbshipit-source-id: b8c1c95cdd6ead471614b37bc32d6b36280157cc
---
 Libraries/Text/TextUpdateTest.js | 57 --------------------------------
 1 file changed, 57 deletions(-)
 delete mode 100644 Libraries/Text/TextUpdateTest.js

diff --git a/Libraries/Text/TextUpdateTest.js b/Libraries/Text/TextUpdateTest.js
deleted file mode 100644
index 5415790979b1..000000000000
--- a/Libraries/Text/TextUpdateTest.js
+++ /dev/null
@@ -1,57 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- * @flow
- */
-
-'use strict';
-
-const React = require('react');
-const createReactClass = require('create-react-class');
-const ReactNative = require('react-native');
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
-const TimerMixin = require('react-timer-mixin');
-const {NativeModules, StyleSheet, Text} = ReactNative;
-
-const TestManager =
-  NativeModules.TestManager || NativeModules.SnapshotTestManager;
-
-const TextUpdateTest = createReactClass({
-  displayName: 'TextUpdateTest',
-  mixins: [TimerMixin],
-  getInitialState: function() {
-    return {seeMore: true};
-  },
-  componentDidMount: function() {
-    this.requestAnimationFrame(() =>
-      this.setState({seeMore: false}, () => {
-        TestManager.markTestCompleted();
-      }),
-    );
-  },
-  render: function() {
-    return (
-      <Text
-        style={styles.container}
-        onPress={() => this.setState({seeMore: !this.state.seeMore})}>
-        <Text>Tap to see more (bugs)...</Text>
-        {this.state.seeMore && 'raw text'}
-      </Text>
-    );
-  },
-});
-
-const styles = StyleSheet.create({
-  container: {
-    margin: 10,
-    marginTop: 100,
-  },
-});
-
-module.exports = TextUpdateTest;

From 398f1d8dddaa5f5c12909ab479e99c3e83c3b884 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 14 May 2018 00:09:36 -0700
Subject: [PATCH 0558/1109] vars -> let/const react-native IntegrationTests

Reviewed By: yungsters

Differential Revision: D7986752

fbshipit-source-id: 1f9b129ce19e052584a2cd1240686b6099c64416
---
 IntegrationTests/AppEventsTest.js             | 18 +++++-----
 IntegrationTests/AsyncStorageTest.js          | 32 +++++++++---------
 IntegrationTests/ImageCachePolicyTest.js      |  8 ++---
 IntegrationTests/ImageSnapshotTest.js         |  8 ++---
 .../IntegrationTestHarnessTest.js             | 12 +++----
 IntegrationTests/IntegrationTestsApp.js       | 10 +++---
 IntegrationTests/LayoutEventsTest.js          | 24 +++++++-------
 IntegrationTests/LoggingTestModule.js         |  8 ++---
 IntegrationTests/PromiseTest.js               |  8 ++---
 IntegrationTests/PropertiesUpdateTest.js      |  8 ++---
 .../RCTRootViewIntegrationTestApp.js          | 10 +++---
 .../ReactContentSizeUpdateTest.js             | 26 +++++++--------
 IntegrationTests/SimpleSnapshotTest.js        | 12 +++----
 IntegrationTests/SizeFlexibilityUpdateTest.js | 22 ++++++-------
 IntegrationTests/SyncMethodTest.js            |  6 ++--
 IntegrationTests/TimersTest.js                | 33 ++++++++++---------
 IntegrationTests/WebSocketTest.js             | 20 +++++------
 IntegrationTests/WebViewTest.js               | 18 +++++-----
 18 files changed, 143 insertions(+), 140 deletions(-)

diff --git a/IntegrationTests/AppEventsTest.js b/IntegrationTests/AppEventsTest.js
index 9df430fea983..90da0bd87c1a 100644
--- a/IntegrationTests/AppEventsTest.js
+++ b/IntegrationTests/AppEventsTest.js
@@ -10,14 +10,14 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {NativeAppEventEmitter, StyleSheet, Text, View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const React = require('react');
+const ReactNative = require('react-native');
+const {NativeAppEventEmitter, StyleSheet, Text, View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
-var deepDiffer = require('deepDiffer');
+const deepDiffer = require('deepDiffer');
 
-var TEST_PAYLOAD = {foo: 'bar'};
+const TEST_PAYLOAD = {foo: 'bar'};
 
 type AppEvent = {data: Object, ts: number};
 type State = {
@@ -31,7 +31,7 @@ class AppEventsTest extends React.Component<{}, State> {
 
   componentDidMount() {
     NativeAppEventEmitter.addListener('testEvent', this.receiveEvent);
-    var event = {data: TEST_PAYLOAD, ts: Date.now()};
+    const event = {data: TEST_PAYLOAD, ts: Date.now()};
     TestModule.sendAppEvent('testEvent', event);
     this.setState({sent: event});
   }
@@ -40,7 +40,7 @@ class AppEventsTest extends React.Component<{}, State> {
     if (deepDiffer(event.data, TEST_PAYLOAD)) {
       throw new Error('Received wrong event: ' + JSON.stringify(event));
     }
-    var elapsed = Date.now() - event.ts + 'ms';
+    const elapsed = Date.now() - event.ts + 'ms';
     this.setState({received: event, elapsed}, () => {
       TestModule.markTestCompleted();
     });
@@ -57,7 +57,7 @@ class AppEventsTest extends React.Component<{}, State> {
 
 AppEventsTest.displayName = 'AppEventsTest';
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   container: {
     margin: 40,
   },
diff --git a/IntegrationTests/AsyncStorageTest.js b/IntegrationTests/AsyncStorageTest.js
index 9245854e2e01..150aa2aed511 100644
--- a/IntegrationTests/AsyncStorageTest.js
+++ b/IntegrationTests/AsyncStorageTest.js
@@ -10,27 +10,27 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {AsyncStorage, Text, View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const React = require('react');
+const ReactNative = require('react-native');
+const {AsyncStorage, Text, View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
-var deepDiffer = require('deepDiffer');
+const deepDiffer = require('deepDiffer');
 
-var DEBUG = false;
+const DEBUG = false;
 
-var KEY_1 = 'key_1';
-var VAL_1 = 'val_1';
-var KEY_2 = 'key_2';
-var VAL_2 = 'val_2';
-var KEY_MERGE = 'key_merge';
-var VAL_MERGE_1 = {foo: 1, bar: {hoo: 1, boo: 1}, moo: {a: 3}};
-var VAL_MERGE_2 = {bar: {hoo: 2}, baz: 2, moo: {a: 3}};
-var VAL_MERGE_EXPECT = {foo: 1, bar: {hoo: 2, boo: 1}, baz: 2, moo: {a: 3}};
+const KEY_1 = 'key_1';
+const VAL_1 = 'val_1';
+const KEY_2 = 'key_2';
+const VAL_2 = 'val_2';
+const KEY_MERGE = 'key_merge';
+const VAL_MERGE_1 = {foo: 1, bar: {hoo: 1, boo: 1}, moo: {a: 3}};
+const VAL_MERGE_2 = {bar: {hoo: 2}, baz: 2, moo: {a: 3}};
+const VAL_MERGE_EXPECT = {foo: 1, bar: {hoo: 2, boo: 1}, baz: 2, moo: {a: 3}};
 
 // setup in componentDidMount
-var done = (result: ?boolean) => {};
-var updateMessage = (message: string) => {};
+let done = (result: ?boolean) => {};
+let updateMessage = (message: string) => {};
 
 function runTestCase(description: string, fn) {
   updateMessage(description);
diff --git a/IntegrationTests/ImageCachePolicyTest.js b/IntegrationTests/ImageCachePolicyTest.js
index 1c4429389cbb..1dc5d5fb61a9 100644
--- a/IntegrationTests/ImageCachePolicyTest.js
+++ b/IntegrationTests/ImageCachePolicyTest.js
@@ -10,10 +10,10 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {Image, View, Text, StyleSheet} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const React = require('react');
+const ReactNative = require('react-native');
+const {Image, View, Text, StyleSheet} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
 /*
  * The reload and force-cache tests don't actually verify that the complete functionality.
diff --git a/IntegrationTests/ImageSnapshotTest.js b/IntegrationTests/ImageSnapshotTest.js
index 5c74433a9d40..c20406c641ec 100644
--- a/IntegrationTests/ImageSnapshotTest.js
+++ b/IntegrationTests/ImageSnapshotTest.js
@@ -10,10 +10,10 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {Image, View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const React = require('react');
+const ReactNative = require('react-native');
+const {Image, View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
 class ImageSnapshotTest extends React.Component<{}> {
   componentDidMount() {
diff --git a/IntegrationTests/IntegrationTestHarnessTest.js b/IntegrationTests/IntegrationTestHarnessTest.js
index 2a596d068b67..045d2e7e1eae 100644
--- a/IntegrationTests/IntegrationTestHarnessTest.js
+++ b/IntegrationTests/IntegrationTestHarnessTest.js
@@ -13,12 +13,12 @@
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-var requestAnimationFrame = require('fbjs/lib/requestAnimationFrame');
-var React = require('react');
-var PropTypes = require('prop-types');
-var ReactNative = require('react-native');
-var {Text, View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const requestAnimationFrame = require('fbjs/lib/requestAnimationFrame');
+const React = require('react');
+const PropTypes = require('prop-types');
+const ReactNative = require('react-native');
+const {Text, View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
 class IntegrationTestHarnessTest extends React.Component<
   {
diff --git a/IntegrationTests/IntegrationTestsApp.js b/IntegrationTests/IntegrationTestsApp.js
index c59f15b3d73a..421b4f6abe2b 100644
--- a/IntegrationTests/IntegrationTestsApp.js
+++ b/IntegrationTests/IntegrationTestsApp.js
@@ -10,9 +10,9 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {
+const React = require('react');
+const ReactNative = require('react-native');
+const {
   AppRegistry,
   ScrollView,
   StyleSheet,
@@ -22,7 +22,7 @@ var {
 } = ReactNative;
 
 // Keep this list in sync with RNTesterIntegrationTests.m
-var TESTS = [
+const TESTS = [
   require('./IntegrationTestHarnessTest'),
   require('./TimersTest'),
   require('./AsyncStorageTest'),
@@ -89,7 +89,7 @@ class IntegrationTestsApp extends React.Component<{}, $FlowFixMeState> {
   }
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   container: {
     backgroundColor: 'white',
     marginTop: 40,
diff --git a/IntegrationTests/LayoutEventsTest.js b/IntegrationTests/LayoutEventsTest.js
index b9183a34e92e..5d2676bc1550 100644
--- a/IntegrationTests/LayoutEventsTest.js
+++ b/IntegrationTests/LayoutEventsTest.js
@@ -10,13 +10,13 @@
 
 'use strict';
 
-var React = require('react');
-var createReactClass = require('create-react-class');
-var ReactNative = require('react-native');
-var {Image, LayoutAnimation, StyleSheet, Text, View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const React = require('react');
+const createReactClass = require('create-react-class');
+const ReactNative = require('react-native');
+const {Image, LayoutAnimation, StyleSheet, Text, View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
-var deepDiffer = require('deepDiffer');
+const deepDiffer = require('deepDiffer');
 
 function debug(...args) {
   // console.log.apply(null, arguments);
@@ -42,7 +42,7 @@ type State = {
   containerStyle?: Style,
 };
 
-var LayoutEventsTest = createReactClass({
+const LayoutEventsTest = createReactClass({
   displayName: 'LayoutEventsTest',
   getInitialState(): State {
     return {
@@ -93,7 +93,7 @@ var LayoutEventsTest = createReactClass({
   },
   compare: function(node: string, measured: any, onLayout: any): void {
     if (deepDiffer(measured, onLayout)) {
-      var data = {measured, onLayout};
+      const data = {measured, onLayout};
       throw new Error(
         node +
           ' onLayout mismatch with measure ' +
@@ -114,9 +114,9 @@ var LayoutEventsTest = createReactClass({
     this.setState({imageLayout: e.nativeEvent.layout}, this.checkLayout);
   },
   render: function() {
-    var viewStyle = [styles.view, this.state.viewStyle];
-    var textLayout = this.state.textLayout || {width: '?', height: '?'};
-    var imageLayout = this.state.imageLayout || {x: '?', y: '?'};
+    const viewStyle = [styles.view, this.state.viewStyle];
+    const textLayout = this.state.textLayout || {width: '?', height: '?'};
+    const imageLayout = this.state.imageLayout || {x: '?', y: '?'};
     debug('viewLayout', this.state.viewLayout);
     return (
       <View style={[styles.container, this.state.containerStyle]}>
@@ -141,7 +141,7 @@ var LayoutEventsTest = createReactClass({
   },
 });
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   container: {
     margin: 40,
   },
diff --git a/IntegrationTests/LoggingTestModule.js b/IntegrationTests/LoggingTestModule.js
index 76a4fbccd712..905abee40082 100644
--- a/IntegrationTests/LoggingTestModule.js
+++ b/IntegrationTests/LoggingTestModule.js
@@ -9,12 +9,12 @@
 
 'use strict';
 
-var BatchedBridge = require('BatchedBridge');
+const BatchedBridge = require('BatchedBridge');
 
-var warning = require('fbjs/lib/warning');
-var invariant = require('fbjs/lib/invariant');
+const warning = require('fbjs/lib/warning');
+const invariant = require('fbjs/lib/invariant');
 
-var LoggingTestModule = {
+const LoggingTestModule = {
   logToConsole: function(str) {
     console.log(str);
   },
diff --git a/IntegrationTests/PromiseTest.js b/IntegrationTests/PromiseTest.js
index 3e919a86712b..facf8b45cdc7 100644
--- a/IntegrationTests/PromiseTest.js
+++ b/IntegrationTests/PromiseTest.js
@@ -10,10 +10,10 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const React = require('react');
+const ReactNative = require('react-native');
+const {View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
 class PromiseTest extends React.Component<{}> {
   shouldResolve = false;
diff --git a/IntegrationTests/PropertiesUpdateTest.js b/IntegrationTests/PropertiesUpdateTest.js
index e2c16f3a6325..33d17da5e5c4 100644
--- a/IntegrationTests/PropertiesUpdateTest.js
+++ b/IntegrationTests/PropertiesUpdateTest.js
@@ -9,11 +9,11 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {View} = ReactNative;
+const React = require('react');
+const ReactNative = require('react-native');
+const {View} = ReactNative;
 
-var {TestModule} = ReactNative.NativeModules;
+const {TestModule} = ReactNative.NativeModules;
 
 class PropertiesUpdateTest extends React.Component {
   render() {
diff --git a/IntegrationTests/RCTRootViewIntegrationTestApp.js b/IntegrationTests/RCTRootViewIntegrationTestApp.js
index 8cb499f3677f..6afda59cd688 100644
--- a/IntegrationTests/RCTRootViewIntegrationTestApp.js
+++ b/IntegrationTests/RCTRootViewIntegrationTestApp.js
@@ -11,10 +11,10 @@
 
 require('regenerator-runtime/runtime');
 
-var React = require('react');
-var ReactNative = require('react-native');
+const React = require('react');
+const ReactNative = require('react-native');
 
-var {
+const {
   AppRegistry,
   ScrollView,
   StyleSheet,
@@ -24,7 +24,7 @@ var {
 } = ReactNative;
 
 /* Keep this list in sync with RCTRootViewIntegrationTests.m */
-var TESTS = [
+const TESTS = [
   require('./PropertiesUpdateTest'),
   require('./ReactContentSizeUpdateTest'),
   require('./SizeFlexibilityUpdateTest'),
@@ -70,7 +70,7 @@ class RCTRootViewIntegrationTestApp extends React.Component {
   }
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   container: {
     backgroundColor: 'white',
     marginTop: 40,
diff --git a/IntegrationTests/ReactContentSizeUpdateTest.js b/IntegrationTests/ReactContentSizeUpdateTest.js
index 1306f8d7aa98..be0b06b6abf5 100644
--- a/IntegrationTests/ReactContentSizeUpdateTest.js
+++ b/IntegrationTests/ReactContentSizeUpdateTest.js
@@ -9,23 +9,23 @@
 
 'use strict';
 
-var React = require('react');
-var createReactClass = require('create-react-class');
-var ReactNative = require('react-native');
-var RCTNativeAppEventEmitter = require('RCTNativeAppEventEmitter');
-var Subscribable = require('Subscribable');
-var TimerMixin = require('react-timer-mixin');
+const React = require('react');
+const createReactClass = require('create-react-class');
+const ReactNative = require('react-native');
+const RCTNativeAppEventEmitter = require('RCTNativeAppEventEmitter');
+const Subscribable = require('Subscribable');
+const TimerMixin = require('react-timer-mixin');
 
-var {View} = ReactNative;
+const {View} = ReactNative;
 
-var {TestModule} = ReactNative.NativeModules;
+const {TestModule} = ReactNative.NativeModules;
 
-var reactViewWidth = 101;
-var reactViewHeight = 102;
-var newReactViewWidth = 201;
-var newReactViewHeight = 202;
+const reactViewWidth = 101;
+const reactViewHeight = 102;
+const newReactViewWidth = 201;
+const newReactViewHeight = 202;
 
-var ReactContentSizeUpdateTest = createReactClass({
+const ReactContentSizeUpdateTest = createReactClass({
   displayName: 'ReactContentSizeUpdateTest',
   mixins: [Subscribable.Mixin, TimerMixin],
 
diff --git a/IntegrationTests/SimpleSnapshotTest.js b/IntegrationTests/SimpleSnapshotTest.js
index ea32c4a9a912..2857f3f41b49 100644
--- a/IntegrationTests/SimpleSnapshotTest.js
+++ b/IntegrationTests/SimpleSnapshotTest.js
@@ -10,15 +10,15 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
+const React = require('react');
+const ReactNative = require('react-native');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-var requestAnimationFrame = require('fbjs/lib/requestAnimationFrame');
+const requestAnimationFrame = require('fbjs/lib/requestAnimationFrame');
 
-var {StyleSheet, View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const {StyleSheet, View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
 class SimpleSnapshotTest extends React.Component<{}> {
   componentDidMount() {
@@ -42,7 +42,7 @@ class SimpleSnapshotTest extends React.Component<{}> {
   }
 }
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   box1: {
     width: 80,
     height: 50,
diff --git a/IntegrationTests/SizeFlexibilityUpdateTest.js b/IntegrationTests/SizeFlexibilityUpdateTest.js
index 5f885ddb7bd7..0d0ebd4bfc20 100644
--- a/IntegrationTests/SizeFlexibilityUpdateTest.js
+++ b/IntegrationTests/SizeFlexibilityUpdateTest.js
@@ -9,21 +9,21 @@
 
 'use strict';
 
-var React = require('react');
-var createReactClass = require('create-react-class');
-var ReactNative = require('react-native');
-var RCTNativeAppEventEmitter = require('RCTNativeAppEventEmitter');
-var Subscribable = require('Subscribable');
-var {View} = ReactNative;
+const React = require('react');
+const createReactClass = require('create-react-class');
+const ReactNative = require('react-native');
+const RCTNativeAppEventEmitter = require('RCTNativeAppEventEmitter');
+const Subscribable = require('Subscribable');
+const {View} = ReactNative;
 
-var {TestModule} = ReactNative.NativeModules;
+const {TestModule} = ReactNative.NativeModules;
 
-var reactViewWidth = 111;
-var reactViewHeight = 222;
+const reactViewWidth = 111;
+const reactViewHeight = 222;
 
-var finalState = false;
+let finalState = false;
 
-var SizeFlexibilityUpdateTest = createReactClass({
+const SizeFlexibilityUpdateTest = createReactClass({
   displayName: 'SizeFlexibilityUpdateTest',
   mixins: [Subscribable.Mixin],
 
diff --git a/IntegrationTests/SyncMethodTest.js b/IntegrationTests/SyncMethodTest.js
index eca1df986ba3..6efef977d811 100644
--- a/IntegrationTests/SyncMethodTest.js
+++ b/IntegrationTests/SyncMethodTest.js
@@ -10,9 +10,9 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {View} = ReactNative;
+const React = require('react');
+const ReactNative = require('react-native');
+const {View} = ReactNative;
 
 const {TestModule, RNTesterTestModule} = ReactNative.NativeModules;
 
diff --git a/IntegrationTests/TimersTest.js b/IntegrationTests/TimersTest.js
index 86e1a962175c..15d42c4c852a 100644
--- a/IntegrationTests/TimersTest.js
+++ b/IntegrationTests/TimersTest.js
@@ -10,18 +10,18 @@
 
 'use strict';
 
-var React = require('react');
-var createReactClass = require('create-react-class');
-var ReactNative = require('react-native');
+const React = require('react');
+const createReactClass = require('create-react-class');
+const ReactNative = require('react-native');
 /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
  * found when Flow v0.54 was deployed. To see the error delete this comment and
  * run Flow. */
-var TimerMixin = require('react-timer-mixin');
+const TimerMixin = require('react-timer-mixin');
 
-var {StyleSheet, Text, View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const {StyleSheet, Text, View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
-var TimersTest = createReactClass({
+const TimersTest = createReactClass({
   displayName: 'TimersTest',
   mixins: [TimerMixin],
 
@@ -70,22 +70,25 @@ var TimersTest = createReactClass({
   },
 
   testClearTimeout0() {
-    var timeout = this.setTimeout(() => this._fail('testClearTimeout0'), 0);
+    const timeout = this.setTimeout(() => this._fail('testClearTimeout0'), 0);
     this.clearTimeout(timeout);
     this.testClearTimeout30();
   },
 
   testClearTimeout30() {
-    var timeout = this.setTimeout(() => this._fail('testClearTimeout30'), 30);
+    const timeout = this.setTimeout(() => this._fail('testClearTimeout30'), 30);
     this.clearTimeout(timeout);
     this.setTimeout(this.testClearMulti, 50);
   },
 
   testClearMulti() {
-    var fails = [];
+    const fails = [];
     fails.push(this.setTimeout(() => this._fail('testClearMulti-1'), 20));
     fails.push(this.setTimeout(() => this._fail('testClearMulti-2'), 50));
-    var delayClear = this.setTimeout(() => this._fail('testClearMulti-3'), 50);
+    const delayClear = this.setTimeout(
+      () => this._fail('testClearMulti-3'),
+      50,
+    );
     fails.push(this.setTimeout(() => this._fail('testClearMulti-4'), 0));
     fails.push(this.setTimeout(() => this._fail('testClearMulti-5'), 10));
 
@@ -97,7 +100,7 @@ var TimersTest = createReactClass({
 
   testOrdering() {
     // Clear timers are set first because it's more likely to uncover bugs.
-    var fail0;
+    let fail0;
     this.setImmediate(() => this.clearTimeout(fail0));
     fail0 = this.setTimeout(
       () =>
@@ -107,7 +110,7 @@ var TimersTest = createReactClass({
         ),
       0,
     );
-    var failAnim; // This should fail without the t=0 fastpath feature.
+    let failAnim; // This should fail without the t=0 fastpath feature.
     this.setTimeout(() => this.cancelAnimationFrame(failAnim), 0);
     failAnim = this.requestAnimationFrame(() =>
       this._fail(
@@ -115,7 +118,7 @@ var TimersTest = createReactClass({
           'requestAnimationFrame',
       ),
     );
-    var fail25;
+    let fail25;
     this.setTimeout(() => {
       this.clearTimeout(fail25);
     }, 20);
@@ -165,7 +168,7 @@ var TimersTest = createReactClass({
   },
 });
 
-var styles = StyleSheet.create({
+const styles = StyleSheet.create({
   container: {
     backgroundColor: 'white',
     padding: 40,
diff --git a/IntegrationTests/WebSocketTest.js b/IntegrationTests/WebSocketTest.js
index 33d6b2500c5d..f2478cbcb685 100644
--- a/IntegrationTests/WebSocketTest.js
+++ b/IntegrationTests/WebSocketTest.js
@@ -10,10 +10,10 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {View} = ReactNative;
-var {TestModule} = ReactNative.NativeModules;
+const React = require('react');
+const ReactNative = require('react-native');
+const {View} = ReactNative;
+const {TestModule} = ReactNative.NativeModules;
 
 const DEFAULT_WS_URL = 'ws://localhost:5555/';
 
@@ -49,9 +49,9 @@ class WebSocketTest extends React.Component<{}, State> {
   };
 
   _waitFor = (condition: any, timeout: any, callback: any) => {
-    var remaining = timeout;
-    var t;
-    var timeoutFunction = function() {
+    let remaining = timeout;
+    let t;
+    const timeoutFunction = function() {
       if (condition()) {
         callback(true);
         return;
@@ -121,7 +121,7 @@ class WebSocketTest extends React.Component<{}, State> {
   }
 
   testConnect = () => {
-    var component = this;
+    const component = this;
     component._connect();
     component._waitFor(component._socketIsConnected, 5, function(
       connectSucceeded,
@@ -135,7 +135,7 @@ class WebSocketTest extends React.Component<{}, State> {
   };
 
   testSendAndReceive = () => {
-    var component = this;
+    const component = this;
     component._sendTestMessage();
     component._waitFor(component._receivedTestExpectedResponse, 5, function(
       messageReceived,
@@ -149,7 +149,7 @@ class WebSocketTest extends React.Component<{}, State> {
   };
 
   testDisconnect = () => {
-    var component = this;
+    const component = this;
     component._disconnect();
     component._waitFor(component._socketIsDisconnected, 5, function(
       disconnectSucceeded,
diff --git a/IntegrationTests/WebViewTest.js b/IntegrationTests/WebViewTest.js
index 47b4544cda88..74dbeddec6b5 100644
--- a/IntegrationTests/WebViewTest.js
+++ b/IntegrationTests/WebViewTest.js
@@ -9,18 +9,18 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {WebView} = ReactNative;
+const React = require('react');
+const ReactNative = require('react-native');
+const {WebView} = ReactNative;
 
-var {TestModule} = ReactNative.NativeModules;
+const {TestModule} = ReactNative.NativeModules;
 
 class WebViewTest extends React.Component {
   render() {
-    var firstMessageReceived = false;
-    var secondMessageReceived = false;
+    let firstMessageReceived = false;
+    let secondMessageReceived = false;
     function processMessage(e) {
-      var message = e.nativeEvent.data;
+      const message = e.nativeEvent.data;
       if (message === 'First') {
         firstMessageReceived = true;
       }
@@ -41,7 +41,7 @@ class WebViewTest extends React.Component {
         throw new Error('First message got lost');
       }
     }
-    var html =
+    const html =
       'Hello world' +
       '<script>' +
       "window.setTimeout(function(){window.postMessage('First'); window.postMessage('Second')}, 0)" +
@@ -56,7 +56,7 @@ class WebViewTest extends React.Component {
       );
     }, 10000);
 
-    var source = {
+    const source = {
       html: html,
     };
 

From 3ac914478d9636e7fffe29751e916ac16f311652 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 14 May 2018 09:22:13 -0700
Subject: [PATCH 0559/1109] Add support for View Manager commands in Fabric

Reviewed By: achen1

Differential Revision: D7879104

fbshipit-source-id: fd89acb3941bb03364d18ddedf68a081aef934a0
---
 .../facebook/react/ReactInstanceManager.java  |  4 +--
 .../com/facebook/react/ReactRootView.java     |  8 ++---
 .../com/facebook/react/bridge/UIManager.java  | 17 ++++++++++
 .../react/fabric/FabricUIManager.java         | 18 +++++++++++
 .../react/uimanager/UIImplementation.java     |  2 +-
 .../react/uimanager/UIManagerHelper.java      | 32 +++++++++++++++++++
 .../react/uimanager/UIManagerModule.java      | 16 ++++++++--
 .../react/uimanager/UIViewOperationQueue.java |  2 +-
 8 files changed, 89 insertions(+), 10 deletions(-)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 9687065e2501..a50a17b2fd1c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -79,7 +79,7 @@
 import com.facebook.react.modules.fabric.ReactFabric;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
 import com.facebook.react.uimanager.UIImplementationProvider;
-import com.facebook.react.uimanager.UIManagerModule;
+import com.facebook.react.uimanager.UIManagerHelper;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.views.imagehelper.ResourceDrawableIdHelper;
 import com.facebook.soloader.SoLoader;
@@ -1011,7 +1011,7 @@ private void attachRootViewToInstance(
       CatalystInstance catalystInstance) {
     Log.d(ReactConstants.TAG, "ReactInstanceManager.attachRootViewToInstance()");
     Systrace.beginSection(TRACE_TAG_REACT_JAVA_BRIDGE, "attachRootViewToInstance");
-    UIManager uiManagerModule = rootView.isFabric() ? catalystInstance.getJSIModule(UIManager.class) : catalystInstance.getNativeModule(UIManagerModule.class);
+    UIManager uiManagerModule = UIManagerHelper.getUIManager(mCurrentReactContext, rootView.isFabric());
     final int rootTag = uiManagerModule.addRootView(rootView);
     rootView.setRootViewTag(rootTag);
     rootView.invokeJSEntryPoint();
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 6fbe25e82eb4..ddf80d63c046 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -44,6 +44,7 @@
 import com.facebook.react.uimanager.JSTouchDispatcher;
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.RootView;
+import com.facebook.react.uimanager.UIManagerHelper;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
@@ -402,10 +403,9 @@ private void updateRootLayoutSpecs(final int widthMeasureSpec, final int heightM
           new GuardedRunnable(reactApplicationContext) {
             @Override
             public void runGuarded() {
-              reactApplicationContext
-                  .getCatalystInstance()
-                  .getNativeModule(UIManagerModule.class)
-                  .updateRootLayoutSpecs(getRootViewTag(), widthMeasureSpec, heightMeasureSpec);
+              UIManagerHelper
+                .getUIManager(reactApplicationContext, isFabric())
+                .updateRootLayoutSpecs(getRootViewTag(), widthMeasureSpec, heightMeasureSpec);
             }
           });
     }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
index 6cbca5de698f..924f84189771 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
@@ -3,6 +3,8 @@
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 
+import javax.annotation.Nullable;
+
 public interface UIManager extends JSIModule {
 
   /**
@@ -10,4 +12,19 @@ public interface UIManager extends JSIModule {
    */
   <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(final T rootView);
 
+  /**
+   * Updates the layout specs of the RootShadowNode based on the Measure specs received by
+   * parameters.
+   */
+  void updateRootLayoutSpecs(int rootTag, int widthMeasureSpec, int heightMeasureSpec);
+
+  /**
+   * Dispatches the commandId received by parameter to the view associated with the reactTag.
+   * The command will be processed in the UIThread.
+   * 
+   * @param reactTag {@link int} that identifies the view that will receive this command
+   * @param commandId {@link int} command id
+   * @param commandArgs {@link ReadableArray} parameters associated with the command
+   */
+  void dispatchViewManagerCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs);
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index ce8046092b29..31a2a866f6a4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -16,6 +16,7 @@
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.bridge.GuardedRunnable;
 import com.facebook.react.bridge.ReactApplicationContext;
+import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.ReadableNativeMap;
 import com.facebook.react.bridge.UIManager;
@@ -35,8 +36,10 @@
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 import java.util.ArrayList;
+import java.util.HashSet;
 import java.util.LinkedList;
 import java.util.List;
+import java.util.Set;
 import javax.annotation.Nullable;
 
 /**
@@ -280,6 +283,11 @@ public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNod
     }
   }
 
+  @Deprecated
+  public void dispatchViewManagerCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs) {
+    mUIViewOperationQueue.enqueueDispatchCommand(reactTag, commandId, commandArgs);
+  }
+
   private void notifyOnBeforeLayoutRecursive(ReactShadowNode node) {
     if (!node.hasUpdates()) {
       return;
@@ -367,6 +375,16 @@ public void onSizeChanged(final int width, final int height, int oldW, int oldH)
     return rootTag;
   }
 
+  @Override
+  public void updateRootLayoutSpecs(int rootViewTag, int widthMeasureSpec, int heightMeasureSpec) {
+    ReactShadowNode rootNode = mRootShadowNodeRegistry.getNode(rootViewTag);
+    if (rootNode == null) {
+      Log.w(ReactConstants.TAG, "Tried to update non-existent root tag: " + rootViewTag);
+      return;
+    }
+    updateRootView(rootNode, widthMeasureSpec, heightMeasureSpec);
+  }
+
   /**
    * Updates the root view size and re-render the RN surface.
    *
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
index 5f124ab88ab4..c1adee2e6cca 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
@@ -788,7 +788,7 @@ public void clearJSResponder() {
     mOperationsQueue.enqueueClearJSResponder();
   }
 
-  public void dispatchViewManagerCommand(int reactTag, int commandId, ReadableArray commandArgs) {
+  public void dispatchViewManagerCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs) {
     assertViewExists(reactTag, "dispatchViewManagerCommand");
     mOperationsQueue.enqueueDispatchCommand(reactTag, commandId, commandArgs);
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java
new file mode 100644
index 000000000000..1cf7c6fb35fd
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java
@@ -0,0 +1,32 @@
+package com.facebook.react.uimanager;
+
+import static com.facebook.react.uimanager.common.ViewType.FABRIC;
+import static com.facebook.react.uimanager.common.ViewUtil.getViewType;
+
+import com.facebook.react.bridge.CatalystInstance;
+import com.facebook.react.bridge.ReactContext;
+import com.facebook.react.bridge.UIManager;
+
+/**
+ * Helper class for {@link UIManager}.
+ */
+public class UIManagerHelper {
+
+  /**
+   * @return a {@link UIManager} that can handle the react tag received by parameter.
+   */
+  public static UIManager getUIManager(ReactContext context, int reactTag) {
+    return getUIManager(context, getViewType(reactTag) == FABRIC);
+  }
+
+  /**
+   * @return a {@link UIManager} that can handle the react tag received by parameter.
+   */
+  public static UIManager getUIManager(ReactContext context, boolean isFabric) {
+    CatalystInstance catalystInstance = context.getCatalystInstance();
+    return isFabric ?
+      catalystInstance.getJSIModule(UIManager.class) :
+      catalystInstance.getNativeModule(UIManagerModule.class);
+  }
+
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 3ef612874938..630f1d973cdc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -10,6 +10,9 @@
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_END;
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_START;
 
+import static com.facebook.react.uimanager.common.ViewType.FABRIC;
+import static com.facebook.react.uimanager.common.ViewType.PAPER;
+
 import android.content.ComponentCallbacks2;
 import android.content.res.Configuration;
 import android.content.Context;
@@ -37,6 +40,7 @@
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
+import com.facebook.react.uimanager.common.ViewUtil;
 import com.facebook.react.uimanager.debug.NotThreadSafeViewHierarchyUpdateDebugListener;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.systrace.Systrace;
@@ -582,9 +586,17 @@ public void clearJSResponder() {
     mUIImplementation.clearJSResponder();
   }
 
+  @Override
   @ReactMethod
-  public void dispatchViewManagerCommand(int reactTag, int commandId, ReadableArray commandArgs) {
-    mUIImplementation.dispatchViewManagerCommand(reactTag, commandId, commandArgs);
+  public void dispatchViewManagerCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs) {
+    //TODO: this is a temporary approach to support ViewManagerCommands in Fabric until
+    // the dispatchViewManagerCommand() method is supported by Fabric JS API.
+    if (ViewUtil.getViewType(reactTag) == FABRIC) {
+      UIManagerHelper.getUIManager(getReactApplicationContext(), true)
+        .dispatchViewManagerCommand(reactTag, commandId, commandArgs);
+    } else {
+      mUIImplementation.dispatchViewManagerCommand(reactTag, commandId, commandArgs);
+    }
   }
   
   @ReactMethod
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
index 832b94ce2cdc..183fcf436a88 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
@@ -647,7 +647,7 @@ public void enqueueClearJSResponder() {
   public void enqueueDispatchCommand(
       int reactTag,
       int commandId,
-      ReadableArray commandArgs) {
+      @Nullable ReadableArray commandArgs) {
     mOperations.add(new DispatchCommandOperation(reactTag, commandId, commandArgs));
   }
 

From a83cddf037d1226ebe47c122460460546d459c53 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 14 May 2018 09:22:15 -0700
Subject: [PATCH 0560/1109] Refactor isFabric() -> getUIManagerType()

Reviewed By: achen1

Differential Revision: D7897855

fbshipit-source-id: 6b52d989187124c81ab8ee4a732703b46b05dc65
---
 .../facebook/react/ReactInstanceManager.java  |  5 ++--
 .../com/facebook/react/ReactRootView.java     | 15 ++++++-----
 .../com/facebook/react/bridge/UIManager.java  |  2 +-
 .../react/fabric/FabricUIManager.java         |  3 +--
 .../react/uimanager/UIManagerHelper.java      | 27 +++++++++++++------
 .../react/uimanager/UIManagerModule.java      | 19 +++++++------
 .../{ViewType.java => UIManagerType.java}     | 10 +++----
 .../react/uimanager/common/ViewUtil.java      | 11 ++++----
 .../uimanager/events/EventDispatcher.java     |  1 +
 9 files changed, 53 insertions(+), 40 deletions(-)
 rename ReactAndroid/src/main/java/com/facebook/react/uimanager/common/{ViewType.java => UIManagerType.java} (64%)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index a50a17b2fd1c..45d678232124 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -25,6 +25,7 @@
 import static com.facebook.react.bridge.ReactMarkerConstants.REACT_CONTEXT_THREAD_START;
 import static com.facebook.react.bridge.ReactMarkerConstants.SETUP_REACT_CONTEXT_END;
 import static com.facebook.react.bridge.ReactMarkerConstants.SETUP_REACT_CONTEXT_START;
+import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 import static com.facebook.systrace.Systrace.TRACE_TAG_REACT_APPS;
 import static com.facebook.systrace.Systrace.TRACE_TAG_REACT_JAVA_BRIDGE;
 import static com.facebook.systrace.Systrace.TRACE_TAG_REACT_JS_VM_CALLS;
@@ -1011,7 +1012,7 @@ private void attachRootViewToInstance(
       CatalystInstance catalystInstance) {
     Log.d(ReactConstants.TAG, "ReactInstanceManager.attachRootViewToInstance()");
     Systrace.beginSection(TRACE_TAG_REACT_JAVA_BRIDGE, "attachRootViewToInstance");
-    UIManager uiManagerModule = UIManagerHelper.getUIManager(mCurrentReactContext, rootView.isFabric());
+    UIManager uiManagerModule = UIManagerHelper.getUIManager(mCurrentReactContext, rootView.getUIManagerType());
     final int rootTag = uiManagerModule.addRootView(rootView);
     rootView.setRootViewTag(rootTag);
     rootView.invokeJSEntryPoint();
@@ -1037,7 +1038,7 @@ private void detachViewFromInstance(
       CatalystInstance catalystInstance) {
     Log.d(ReactConstants.TAG, "ReactInstanceManager.detachViewFromInstance()");
     UiThreadUtil.assertOnUiThread();
-    if (rootView.isFabric()) {
+    if (rootView.getUIManagerType() == FABRIC) {
       catalystInstance.getJSModule(ReactFabric.class)
         .unmountComponentAtNode(rootView.getId());
     } else {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index ddf80d63c046..9e7c04ba80cd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -8,6 +8,8 @@
 package com.facebook.react;
 
 import static com.facebook.systrace.Systrace.TRACE_TAG_REACT_JAVA_BRIDGE;
+import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
+import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
 
 import android.content.Context;
 import android.graphics.Canvas;
@@ -50,6 +52,7 @@
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.systrace.Systrace;
+import com.facebook.react.uimanager.common.UIManagerType;
 import javax.annotation.Nullable;
 
 /**
@@ -91,7 +94,7 @@ public interface ReactRootViewEventListener {
   private int mWidthMeasureSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED);
   private int mHeightMeasureSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED);
   private @Nullable Runnable mJSEntryPoint;
-  private boolean mIsFabric = false;
+  private @UIManagerType int mUIManagerType = DEFAULT;
 
   public ReactRootView(Context context) {
     super(context);
@@ -404,7 +407,7 @@ private void updateRootLayoutSpecs(final int widthMeasureSpec, final int heightM
             @Override
             public void runGuarded() {
               UIManagerHelper
-                .getUIManager(reactApplicationContext, isFabric())
+                .getUIManager(reactApplicationContext, getUIManagerType())
                 .updateRootLayoutSpecs(getRootViewTag(), widthMeasureSpec, heightMeasureSpec);
             }
           });
@@ -507,7 +510,7 @@ private void defaultJSEntryPoint() {
         if (appProperties != null) {
           appParams.putMap("initialProps", Arguments.fromBundle(appProperties));
         }
-        if (isFabric()) {
+        if (getUIManagerType() == FABRIC) {
           appParams.putBoolean("fabric", true);
         }
 
@@ -584,11 +587,11 @@ public void handleException(final Throwable t) {
   }
 
   public void setIsFabric(boolean isFabric) {
-    mIsFabric = isFabric;
+    mUIManagerType = isFabric ? FABRIC : DEFAULT;
   }
 
-  public boolean isFabric() {
-    return mIsFabric;
+  public @UIManagerType int getUIManagerType() {
+    return mUIManagerType;
   }
 
   @Nullable
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
index 924f84189771..875f42cbf12b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
@@ -26,5 +26,5 @@ public interface UIManager extends JSIModule {
    * @param commandId {@link int} command id
    * @param commandArgs {@link ReadableArray} parameters associated with the command
    */
-  void dispatchViewManagerCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs);
+  void dispatchCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs);
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 31a2a866f6a4..f9d1948ab87e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -283,8 +283,7 @@ public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNod
     }
   }
 
-  @Deprecated
-  public void dispatchViewManagerCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs) {
+  public void dispatchCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs) {
     mUIViewOperationQueue.enqueueDispatchCommand(reactTag, commandId, commandArgs);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java
index 1cf7c6fb35fd..6503ccb067f0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java
@@ -1,11 +1,13 @@
 package com.facebook.react.uimanager;
 
-import static com.facebook.react.uimanager.common.ViewType.FABRIC;
-import static com.facebook.react.uimanager.common.ViewUtil.getViewType;
+import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
+import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
+import static com.facebook.react.uimanager.common.ViewUtil.getUIManagerType;
 
 import com.facebook.react.bridge.CatalystInstance;
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.bridge.UIManager;
+import com.facebook.react.uimanager.common.UIManagerType;
 
 /**
  * Helper class for {@link UIManager}.
@@ -15,18 +17,27 @@ public class UIManagerHelper {
   /**
    * @return a {@link UIManager} that can handle the react tag received by parameter.
    */
-  public static UIManager getUIManager(ReactContext context, int reactTag) {
-    return getUIManager(context, getViewType(reactTag) == FABRIC);
+  public static UIManager getUIManagerForReactTag(ReactContext context, int reactTag) {
+    return getUIManager(context, getUIManagerType(reactTag));
   }
 
   /**
    * @return a {@link UIManager} that can handle the react tag received by parameter.
    */
-  public static UIManager getUIManager(ReactContext context, boolean isFabric) {
+  public static UIManager getUIManager(ReactContext context, @UIManagerType int uiManagerType) {
     CatalystInstance catalystInstance = context.getCatalystInstance();
-    return isFabric ?
-      catalystInstance.getJSIModule(UIManager.class) :
-      catalystInstance.getNativeModule(UIManagerModule.class);
+    UIManager uiManager;
+    switch (uiManagerType) {
+      case FABRIC:
+        uiManager = catalystInstance.getJSIModule(UIManager.class);
+        break;
+      case DEFAULT:
+        uiManager = catalystInstance.getNativeModule(UIManagerModule.class);
+        break;
+      default:
+        throw new IllegalArgumentException("Invalid UIManagerType: " + uiManagerType);
+    }
+    return uiManager;
   }
 
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 630f1d973cdc..3937f13deb9e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -10,8 +10,7 @@
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_END;
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_START;
 
-import static com.facebook.react.uimanager.common.ViewType.FABRIC;
-import static com.facebook.react.uimanager.common.ViewType.PAPER;
+import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
 
 import android.content.ComponentCallbacks2;
 import android.content.res.Configuration;
@@ -586,19 +585,19 @@ public void clearJSResponder() {
     mUIImplementation.clearJSResponder();
   }
 
-  @Override
   @ReactMethod
   public void dispatchViewManagerCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs) {
     //TODO: this is a temporary approach to support ViewManagerCommands in Fabric until
     // the dispatchViewManagerCommand() method is supported by Fabric JS API.
-    if (ViewUtil.getViewType(reactTag) == FABRIC) {
-      UIManagerHelper.getUIManager(getReactApplicationContext(), true)
-        .dispatchViewManagerCommand(reactTag, commandId, commandArgs);
-    } else {
-      mUIImplementation.dispatchViewManagerCommand(reactTag, commandId, commandArgs);
-    }
+    UIManagerHelper.getUIManager(getReactApplicationContext(), ViewUtil.getUIManagerType(reactTag))
+      .dispatchCommand(reactTag, commandId, commandArgs);
+  }
+
+  @Override
+  public void dispatchCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs) {
+    mUIImplementation.dispatchViewManagerCommand(reactTag, commandId, commandArgs);
   }
-  
+
   @ReactMethod
   public void playTouchSound() {
     AudioManager audioManager = (AudioManager) getReactApplicationContext().getSystemService(Context.AUDIO_SERVICE);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewType.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/UIManagerType.java
similarity index 64%
rename from ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewType.java
rename to ReactAndroid/src/main/java/com/facebook/react/uimanager/common/UIManagerType.java
index 66e4fdbecd44..44a2e8b8f62a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewType.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/UIManagerType.java
@@ -6,16 +6,16 @@
  */
 package com.facebook.react.uimanager.common;
 
-import static com.facebook.react.uimanager.common.ViewType.FABRIC;
-import static com.facebook.react.uimanager.common.ViewType.PAPER;
+import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
+import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
 import static java.lang.annotation.RetentionPolicy.SOURCE;
 
 import java.lang.annotation.Retention;
 import android.support.annotation.IntDef;
 
 @Retention(SOURCE)
-@IntDef({PAPER, FABRIC})
-public @interface ViewType {
-  int PAPER = 1;
+@IntDef({DEFAULT, FABRIC})
+public @interface UIManagerType {
+  int DEFAULT = 1;
   int FABRIC = 2;
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewUtil.java
index cc7a3ddcbd04..ef679635efbb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewUtil.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/ViewUtil.java
@@ -7,23 +7,22 @@
 
 package com.facebook.react.uimanager.common;
 
-import static com.facebook.react.uimanager.common.ViewType.FABRIC;
-import static com.facebook.react.uimanager.common.ViewType.PAPER;
+import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
+import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
 
 public class ViewUtil {
 
   /**
    * Counter for uniquely identifying views.
-   * - % 10 === 1 means it is a rootTag.
    * - % 2 === 0 means it is a Fabric tag.
    * See https://github.com/facebook/react/pull/12587
    *
    * @param reactTag {@link }
    */
-  @ViewType
-  public static int getViewType(int reactTag) {
+  @UIManagerType
+  public static int getUIManagerType(int reactTag) {
     if (reactTag % 2 == 0) return FABRIC;
-    return PAPER;
+    return DEFAULT;
   }
 
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
index c53a9f3dec5f..7feddf17b0d4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
@@ -24,6 +24,7 @@
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.modules.core.ChoreographerCompat;
 import com.facebook.react.modules.core.ReactChoreographer;
+import com.facebook.react.uimanager.common.UIManagerType;
 import com.facebook.systrace.Systrace;
 
 /**

From 07df36557c8cbbaee5e870460162aa725a606ff4 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Mon, 14 May 2018 11:08:02 -0700
Subject: [PATCH 0561/1109] remove fresco proguard rules

Summary:
Fresco now maintain proguard rules by itself (https://github.com/facebook/fresco/pull/2075), so it won't be necessary for react native copy its rules.
Run RNTTester Android app in release mode, app build successful and won't crash in ImageModule.

none

 [ANDROID] [BUGFIX] [PROGUARD] - remove fresco proguard rules
Closes https://github.com/facebook/react-native/pull/19040

Differential Revision: D7992146

Pulled By: hramos

fbshipit-source-id: 9ee3dd4c6756472395ec9e36a967b469f0760999
---
 ReactAndroid/proguard-rules.pro | 19 -------------------
 1 file changed, 19 deletions(-)

diff --git a/ReactAndroid/proguard-rules.pro b/ReactAndroid/proguard-rules.pro
index 6e9ff0ac7551..668d5bd472f8 100644
--- a/ReactAndroid/proguard-rules.pro
+++ b/ReactAndroid/proguard-rules.pro
@@ -69,22 +69,3 @@
 -dontwarn java.nio.file.*
 -dontwarn org.codehaus.mojo.animal_sniffer.IgnoreJRERequirement
 -dontwarn okio.**
-
-# Fresco
-# Keep our interfaces so they can be used by other ProGuard rules.
-# See http://sourceforge.net/p/proguard/bugs/466/
--keep,allowobfuscation @interface com.facebook.soloader.DoNotOptimize
-
-# Do not strip any method/class that is annotated with @DoNotOptimize
--keep @com.facebook.soloader.DoNotOptimize class *
--keepclassmembers class * {
-    @com.facebook.soloader.DoNotOptimize *;
-}
-
-# Keep native methods
--keepclassmembers class * {
-    native <methods>;
-}
-
--dontwarn javax.annotation.**
--dontwarn com.facebook.infer.**

From 344c205070d5ad670c97984dd86ec9ac13c73f81 Mon Sep 17 00:00:00 2001
From: fattahmuhyiddeen <fattahmuhyiddeen@gmail.com>
Date: Mon, 14 May 2018 11:40:50 -0700
Subject: [PATCH 0562/1109] Fix crash during Archiving project in IOS

Summary:
Thank you for sending the PR! We appreciate you spending the time to work on these changes.
Help us understand your motivation by explaining why you decided to make this change.

  To fix issue that crash on XCode 9.3

Archive the project in XCode 9.3

This does not change any documentation

 To fix issue that crash on XCode 9.3

 [IOS] [BREAKING] [RCTImageCache.m] - Crash during archiving in XCode 9.3
Closes https://github.com/facebook/react-native/pull/18682

Differential Revision: D7992071

Pulled By: hramos

fbshipit-source-id: 1089e469712b1eb2fcdd3ad59766c187e932f46c
---
 Libraries/Image/RCTImageCache.m | 9 +++++----
 1 file changed, 5 insertions(+), 4 deletions(-)

diff --git a/Libraries/Image/RCTImageCache.m b/Libraries/Image/RCTImageCache.m
index 8caedae7cf81..4d4803c4ab08 100644
--- a/Libraries/Image/RCTImageCache.m
+++ b/Libraries/Image/RCTImageCache.m
@@ -14,6 +14,7 @@
 #import <React/RCTConvert.h>
 #import <React/RCTNetworking.h>
 #import <React/RCTUtils.h>
+#import <React/RCTResizeMode.h>
 
 #import "RCTImageUtils.h"
 
@@ -22,8 +23,8 @@
 static NSString *RCTCacheKeyForImage(NSString *imageTag, CGSize size, CGFloat scale,
                                      RCTResizeMode resizeMode, NSString *responseDate)
 {
-    return [NSString stringWithFormat:@"%@|%g|%g|%g|%lld|%@",
-            imageTag, size.width, size.height, scale, (long long)resizeMode, responseDate];
+  return [NSString stringWithFormat:@"%@|%g|%g|%g|%lld|%@",
+          imageTag, size.width, size.height, scale, (long long)resizeMode, responseDate];
 }
 
 @implementation RCTImageCache
@@ -36,7 +37,7 @@ - (instancetype)init
 {
   _decodedImageCache = [NSCache new];
   _decodedImageCache.totalCostLimit = 5 * 1024 * 1024; // 5MB
-
+  
   [[NSNotificationCenter defaultCenter] addObserver:self
                                            selector:@selector(clearCache)
                                                name:UIApplicationDidReceiveMemoryWarningNotification
@@ -45,7 +46,7 @@ - (instancetype)init
                                            selector:@selector(clearCache)
                                                name:UIApplicationWillResignActiveNotification
                                              object:nil];
-
+  
   return self;
 }
 

From 9fbff62b5ff9b3effb18f135e1cd9bd34a83c985 Mon Sep 17 00:00:00 2001
From: Aaron Abramov <dabramov@fb.com>
Date: Mon, 14 May 2018 13:26:30 -0700
Subject: [PATCH 0563/1109] Use `hg root` for all CWD in test environment

Reviewed By: mjesun

Differential Revision: D7852925

fbshipit-source-id: 4baf8cddc43d388269577a337cfe5f329c86d0f6
---
 .../__tests__/getProjectDependencies.spec.js  | 11 ++++++----
 local-cli/link/__tests__/link.spec.js         | 22 -------------------
 local-cli/link/getProjectDependencies.js      |  4 ++--
 3 files changed, 9 insertions(+), 28 deletions(-)

diff --git a/local-cli/link/__tests__/getProjectDependencies.spec.js b/local-cli/link/__tests__/getProjectDependencies.spec.js
index 974f128191e4..1a2916351a20 100644
--- a/local-cli/link/__tests__/getProjectDependencies.spec.js
+++ b/local-cli/link/__tests__/getProjectDependencies.spec.js
@@ -6,6 +6,7 @@
  *
  * @format
  * @emails oncall+javascript_foundation
+ * @format
  */
 
 'use strict';
@@ -13,20 +14,22 @@
 const getProjectDependencies = require('../getProjectDependencies');
 const path = require('path');
 
+const CWD = path.resolve(__dirname, '../../..');
+
 describe('getProjectDependencies', () => {
   beforeEach(() => {
     jest.resetModules();
   });
   it('should return an array of project dependencies', () => {
-    jest.setMock(path.join(process.cwd(), './package.json'), {
+    jest.setMock(path.join(CWD, './package.json'), {
       dependencies: {lodash: '^6.0.0', 'react-native': '^16.0.0'},
     });
 
-    expect(getProjectDependencies()).toEqual(['lodash']);
+    expect(getProjectDependencies(CWD)).toEqual(['lodash']);
   });
 
   it('should return an empty array when no dependencies set', () => {
-    jest.setMock(path.join(process.cwd(), './package.json'), {});
-    expect(getProjectDependencies()).toEqual([]);
+    jest.setMock(path.join(CWD, './package.json'), {});
+    expect(getProjectDependencies(CWD)).toEqual([]);
   });
 });
diff --git a/local-cli/link/__tests__/link.spec.js b/local-cli/link/__tests__/link.spec.js
index 7e658eb7d202..9cbe601f2fb4 100644
--- a/local-cli/link/__tests__/link.spec.js
+++ b/local-cli/link/__tests__/link.spec.js
@@ -49,28 +49,6 @@ describe('link', () => {
     });
   });
 
-  it('should read dependencies from package.json when name not provided', done => {
-    const config = {
-      getPlatformConfig: () => ({ios: {}, android: {}}),
-      getProjectConfig: () => ({assets: []}),
-      getDependencyConfig: sinon.stub().returns({assets: [], commands: {}}),
-    };
-
-    jest.setMock(path.join(process.cwd(), 'package.json'), {
-      dependencies: {
-        'react-native-test': '*',
-      },
-    });
-
-    const link = require('../link').func;
-    link([], config).then(() => {
-      expect(
-        config.getDependencyConfig.calledWith('react-native-test'),
-      ).toBeTruthy();
-      done();
-    });
-  });
-
   it('should register native module when android/ios projects are present', done => {
     const registerNativeModule = sinon.stub();
     const dependencyConfig = {android: {}, ios: {}, assets: [], commands: {}};
diff --git a/local-cli/link/getProjectDependencies.js b/local-cli/link/getProjectDependencies.js
index c078aab1a372..9b4838ba923f 100644
--- a/local-cli/link/getProjectDependencies.js
+++ b/local-cli/link/getProjectDependencies.js
@@ -12,8 +12,8 @@ const path = require('path');
 /**
  * Returns an array of dependencies that should be linked/checked.
  */
-module.exports = function getProjectDependencies() {
-  const pjson = require(path.join(process.cwd(), './package.json'));
+module.exports = function getProjectDependencies(cwd) {
+  const pjson = require(path.join(cwd || process.cwd(), './package.json'));
   return Object.keys(pjson.dependencies || {}).filter(
     name => name !== 'react-native',
   );

From 37652f26b45dcbec2d49b0e159105dfedceaa5c0 Mon Sep 17 00:00:00 2001
From: Vincent Langlet <vincentlanglet@users.noreply.github.com>
Date: Mon, 14 May 2018 15:06:55 -0700
Subject: [PATCH 0564/1109] Move eslint plugin from dependencies to dev
 dependencies

Summary:
`eslint-plugin-react-native` was a dependencies. I think it should be a dev dependencies like `eslint-plugin-eslint-comments`, `eslint-plugin-flowtype`, `eslint-plugin-jest`, `eslint-plugin-prettier` and `eslint-plugin-react`.

No need

Not needed

[INTERNAL] [ENHANCEMENT] [./package.json] - Move `eslint-plugin-react-native` to devDependencies.
Closes https://github.com/facebook/react-native/pull/18851

Differential Revision: D7991437

Pulled By: hramos

fbshipit-source-id: 5481290423848b9c34df24629086239600d42274
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 412789dba0e4..5ec4680e8f1e 100644
--- a/package.json
+++ b/package.json
@@ -159,7 +159,6 @@
     "envinfo": "^3.0.0",
     "errorhandler": "^1.5.0",
     "escape-string-regexp": "^1.0.5",
-    "eslint-plugin-react-native": "^3.2.1",
     "event-target-shim": "^1.0.5",
     "fbjs": "^0.8.14",
     "fbjs-scripts": "^0.8.1",
@@ -213,6 +212,7 @@
     "eslint-plugin-jest": "21.8.0",
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
+    "eslint-plugin-react-native": "^3.2.1",
     "flow-bin": "^0.72.0",
     "jest": "23.0.0-charlie.1",
     "jest-junit": "3.7.0",

From 582e1bded3a72f70625230afb8dfa8365e34d0e1 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:25 -0700
Subject: [PATCH 0565/1109] Fabric: Text types conversions & better debug
 printing

Summary: Trivial.

Reviewed By: fkgozali

Differential Revision: D7863489

fbshipit-source-id: c7b9852e104ca12eea144473ed8e1f2973a36df7
---
 .../attributedstring/TextAttributes.cpp       | 17 +++---
 .../debugStringConvertibleUtils.h             |  6 ++
 .../attributedstring/textValuesConversions.h  | 61 +++++++++++++++++++
 ReactCommon/fabric/core/BUCK                  |  1 +
 .../fabric/core/debugStringConvertibleUtils.h | 20 ++++++
 .../core/layout/layoutValuesConversions.h     | 32 ++++++++++
 6 files changed, 128 insertions(+), 9 deletions(-)
 create mode 100644 ReactCommon/fabric/core/debugStringConvertibleUtils.h
 create mode 100644 ReactCommon/fabric/core/layout/layoutValuesConversions.h

diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.cpp b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
index 4f85297dc713..0373f5f2a3be 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
@@ -7,6 +7,7 @@
 
 #include "TextAttributes.h"
 
+#include <fabric/core/debugStringConvertibleUtils.h>
 #include <fabric/graphics/debugStringConvertibleUtils.h>
 #include <fabric/graphics/graphicValuesConversions.h>
 #include "debugStringConvertibleUtils.h"
@@ -54,8 +55,6 @@ void TextAttributes::apply(TextAttributes textAttributes) {
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList TextAttributes::getDebugProps() const {
-  // TODO: Implement all fields.
-
   return {
     // Color
     debugStringConvertibleItem("backgroundColor", backgroundColor),
@@ -68,20 +67,20 @@ SharedDebugStringConvertibleList TextAttributes::getDebugProps() const {
     debugStringConvertibleItem("fontSizeMultiplier", fontSizeMultiplier),
     debugStringConvertibleItem("fontWeight", fontWeight),
     debugStringConvertibleItem("fontStyle", fontStyle),
-    //debugStringConvertibleItem("fontVariant", fontVariant),
+    debugStringConvertibleItem("fontVariant", fontVariant),
     debugStringConvertibleItem("allowFontScaling", allowFontScaling),
     debugStringConvertibleItem("letterSpacing", letterSpacing),
 
     // Paragraph Styles
     debugStringConvertibleItem("lineHeight", lineHeight),
-    //debugStringConvertibleItem("alignment", alignment),
-    //debugStringConvertibleItem("baseWritingDirection", baseWritingDirection),
+    debugStringConvertibleItem("alignment", alignment),
+    debugStringConvertibleItem("baseWritingDirection", baseWritingDirection),
 
     // Decoration
     debugStringConvertibleItem("textDecorationColor", textDecorationColor),
-    //debugStringConvertibleItem("textDecorationLineType", textDecorationLineType),
-    //debugStringConvertibleItem("textDecorationLineStyle", textDecorationLineStyle),
-    //debugStringConvertibleItem("textDecorationLinePattern", textDecorationLinePattern),
+    debugStringConvertibleItem("textDecorationLineType", textDecorationLineType),
+    debugStringConvertibleItem("textDecorationLineStyle", textDecorationLineStyle),
+    debugStringConvertibleItem("textDecorationLinePattern", textDecorationLinePattern),
 
     // Shadow
     debugStringConvertibleItem("textShadowOffset", textShadowOffset),
@@ -90,7 +89,7 @@ SharedDebugStringConvertibleList TextAttributes::getDebugProps() const {
 
     // Special
     debugStringConvertibleItem("isHighlighted", isHighlighted),
-    //debugStringConvertibleItem("layoutDirection", layoutDirection),
+    debugStringConvertibleItem("layoutDirection", layoutDirection),
   };
 }
 
diff --git a/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h b/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
index 617efb4c19cd..3f303cd0668b 100644
--- a/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
+++ b/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
@@ -16,6 +16,12 @@ namespace react {
 DEBUG_STRING_CONVERTIBLE_TEMPLATE(EllipsizeMode, stringFromEllipsizeMode)
 DEBUG_STRING_CONVERTIBLE_TEMPLATE(FontWeight, stringFromFontWeight)
 DEBUG_STRING_CONVERTIBLE_TEMPLATE(FontStyle, stringFromFontStyle)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(FontVariant, stringFromFontVariant)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(TextAlignment, stringFromTextAlignment)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(WritingDirection, stringFromWritingDirection)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(TextDecorationLineType, stringFromTextDecorationLineType)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(TextDecorationLineStyle, stringFromTextDecorationLineStyle)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(TextDecorationLinePattern, stringFromTextDecorationLinePattern)
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/attributedstring/textValuesConversions.h b/ReactCommon/fabric/attributedstring/textValuesConversions.h
index deb5660e2f76..bae4eb65be92 100644
--- a/ReactCommon/fabric/attributedstring/textValuesConversions.h
+++ b/ReactCommon/fabric/attributedstring/textValuesConversions.h
@@ -83,6 +83,22 @@ inline FontVariant fontVariantFromDynamic(const folly::dynamic &value) {
   return fontVariant;
 }
 
+inline std::string stringFromFontVariant(const FontVariant &fontVariant) {
+  std::string result;
+  std::string separator = ", ";
+  if ((int)fontVariant & (int)FontVariant::SmallCaps) { result += "small-caps" + separator; }
+  if ((int)fontVariant & (int)FontVariant::OldstyleNums) { result += "oldstyle-nums" + separator; }
+  if ((int)fontVariant & (int)FontVariant::LiningNums) { result += "lining-nums" + separator; }
+  if ((int)fontVariant & (int)FontVariant::TabularNums) { result += "tabular-nums" + separator; }
+  if ((int)fontVariant & (int)FontVariant::ProportionalNums) { result += "proportional-nums" + separator; }
+
+  if (!result.empty()) {
+    result.erase(result.length() - separator.length());
+  }
+
+  return result;
+}
+
 inline TextAlignment textAlignmentFromDynamic(const folly::dynamic &value) {
   auto string = value.asString();
   if (string == "natural") { return TextAlignment::Natural; }
@@ -93,6 +109,16 @@ inline TextAlignment textAlignmentFromDynamic(const folly::dynamic &value) {
   abort();
 }
 
+inline std::string stringFromTextAlignment(const TextAlignment &textAlignment) {
+  switch (textAlignment) {
+    case TextAlignment::Natural: return "natural";
+    case TextAlignment::Left: return "left";
+    case TextAlignment::Center: return "center";
+    case TextAlignment::Right: return "right";
+    case TextAlignment::Justified: return "justified";
+  }
+}
+
 inline WritingDirection writingDirectionFromDynamic(const folly::dynamic &value) {
   auto string = value.asString();
   if (string == "natural") { return WritingDirection::Natural; }
@@ -101,6 +127,14 @@ inline WritingDirection writingDirectionFromDynamic(const folly::dynamic &value)
   abort();
 }
 
+inline std::string stringFromWritingDirection(const WritingDirection &writingDirection) {
+  switch (writingDirection) {
+    case WritingDirection::Natural: return "natural";
+    case WritingDirection::LeftToRight: return "ltr";
+    case WritingDirection::RightToLeft: return "rtl";
+  }
+}
+
 inline TextDecorationLineType textDecorationLineTypeFromDynamic(const folly::dynamic &value) {
   auto string = value.asString();
   if (string == "none") { return TextDecorationLineType::None; }
@@ -110,6 +144,15 @@ inline TextDecorationLineType textDecorationLineTypeFromDynamic(const folly::dyn
   abort();
 }
 
+inline std::string stringFromTextDecorationLineType(const TextDecorationLineType &textDecorationLineType) {
+  switch (textDecorationLineType) {
+    case TextDecorationLineType::None: return "none";
+    case TextDecorationLineType::Underline: return "underline";
+    case TextDecorationLineType::Strikethrough: return "strikethrough";
+    case TextDecorationLineType::UnderlineStrikethrough: return "underline-strikethrough";
+  }
+}
+
 inline TextDecorationLineStyle textDecorationLineStyleFromDynamic(const folly::dynamic &value) {
   auto string = value.asString();
   if (string == "single") { return TextDecorationLineStyle::Single; }
@@ -118,6 +161,14 @@ inline TextDecorationLineStyle textDecorationLineStyleFromDynamic(const folly::d
   abort();
 }
 
+inline std::string stringFromTextDecorationLineStyle(const TextDecorationLineStyle &textDecorationLineStyle) {
+  switch (textDecorationLineStyle) {
+    case TextDecorationLineStyle::Single: return "single";
+    case TextDecorationLineStyle::Thick: return "thick";
+    case TextDecorationLineStyle::Double: return "double";
+  }
+}
+
 inline TextDecorationLinePattern textDecorationLinePatternFromDynamic(const folly::dynamic &value) {
   auto string = value.asString();
   if (string == "solid") { return TextDecorationLinePattern::Solid; }
@@ -128,5 +179,15 @@ inline TextDecorationLinePattern textDecorationLinePatternFromDynamic(const foll
   abort();
 }
 
+inline std::string stringFromTextDecorationLinePattern(const TextDecorationLinePattern &textDecorationLinePattern) {
+  switch (textDecorationLinePattern) {
+    case TextDecorationLinePattern::Solid: return "solid";
+    case TextDecorationLinePattern::Dot: return "dot";
+    case TextDecorationLinePattern::Dash: return "dash";
+    case TextDecorationLinePattern::DashDot: return "dash-dot";
+    case TextDecorationLinePattern::DashDotDot: return "dash-dot-dot";
+  }
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 4c732efc470e..02c39ac75579 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -20,6 +20,7 @@ rn_xplat_cxx_library(
     header_namespace = "",
     exported_headers = subdir_glob(
         [
+            ("", "*.h"),
             ("primitives", "*.h"),
             ("componentdescriptor", "*.h"),
             ("layout", "*.h"),
diff --git a/ReactCommon/fabric/core/debugStringConvertibleUtils.h b/ReactCommon/fabric/core/debugStringConvertibleUtils.h
new file mode 100644
index 000000000000..0dc60ea89b29
--- /dev/null
+++ b/ReactCommon/fabric/core/debugStringConvertibleUtils.h
@@ -0,0 +1,20 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/debug/debugStringConvertibleUtils.h>
+#include <fabric/core/layoutValuesConversions.h>
+
+namespace facebook {
+namespace react {
+
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(LayoutDirection, stringFromLayoutDirection)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(DisplayType, stringFromDisplayType)
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/layout/layoutValuesConversions.h b/ReactCommon/fabric/core/layout/layoutValuesConversions.h
new file mode 100644
index 000000000000..dc821a35fadc
--- /dev/null
+++ b/ReactCommon/fabric/core/layout/layoutValuesConversions.h
@@ -0,0 +1,32 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/LayoutPrimitives.h>
+
+namespace facebook {
+namespace react {
+
+inline std::string stringFromLayoutDirection(const LayoutDirection &layoutDirection) {
+  switch (layoutDirection) {
+    case LayoutDirection::Undefined: return "undefined";
+    case LayoutDirection::LeftToRight: return "ltr";
+    case LayoutDirection::RightToLeft: return "rtl";
+  }
+}
+
+inline std::string stringFromDisplayType(const DisplayType &displayType) {
+  switch (displayType) {
+    case DisplayType::None: return "none";
+    case DisplayType::Flex: return "flex";
+    case DisplayType::Inline: return "inline";
+  }
+}
+
+} // namespace react
+} // namespace facebook

From dd3a6eda7038b22b790f878ebd26d9fa58e7230c Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:28 -0700
Subject: [PATCH 0566/1109] Fabric: Devirtualizing of props parsing infra

Summary:
This diff contains several tight to each other changes (which can/should not be split into several diffs):
 * The props parsing/conversion process was de-virtualized: we don't use virtual `apply` method to parse props anymore. Instead, we use old-fashioned constructors.
 * All fields of Props classes which represent props values were marked as `const` which make impossible to modify them after the objects were created (even if we have non-const value-of/pointer-to the whole Props object). Those fields are also `public` now.
 * All custom handwritten getters were removed (because we don't need them anymore).

So, now we don't need all those custom getters which makes code much more compact, performant and codegen-friendly.

Reviewed By: fkgozali

Differential Revision: D7901245

fbshipit-source-id: 9f4b1fd2da64bf963b63215ed3bd74b9d3c58dd5
---
 .../Mounting/RCTParagraphComponentView.mm     |  2 +-
 React/Fabric/Mounting/RCTViewComponentView.mm |  4 +-
 .../core/shadownode/ConcreteShadowNode.h      | 18 ++----
 ReactCommon/fabric/core/shadownode/Props.cpp  | 11 +---
 ReactCommon/fabric/core/shadownode/Props.h    |  8 +--
 .../fabric/core/shadownode/propsConversions.h | 30 +++++----
 .../core/tests/ComponentDescriptorTest.cpp    |  4 +-
 .../fabric/core/tests/ShadowNodeTest.cpp      |  7 +-
 ReactCommon/fabric/core/tests/TestComponent.h |  9 ++-
 .../fabric/text/basetext/BaseTextProps.cpp    | 59 ++++++++---------
 .../fabric/text/basetext/BaseTextProps.h      | 18 ++----
 .../text/basetext/BaseTextShadowNode.cpp      |  4 +-
 .../fabric/text/paragraph/ParagraphProps.cpp  | 40 ++++++------
 .../fabric/text/paragraph/ParagraphProps.h    | 17 ++---
 .../text/paragraph/ParagraphShadowNode.cpp    |  4 +-
 ReactCommon/fabric/text/propsConversions.h    | 18 +++---
 .../fabric/text/rawtext/RawTextProps.cpp      | 21 ++----
 .../fabric/text/rawtext/RawTextProps.h        | 11 ++--
 ReactCommon/fabric/text/text/TextProps.cpp    |  6 +-
 ReactCommon/fabric/text/text/TextProps.h      |  4 +-
 ReactCommon/fabric/uimanager/ShadowTree.cpp   |  4 +-
 ReactCommon/fabric/view/ViewProps.cpp         | 64 ++++++-------------
 ReactCommon/fabric/view/ViewProps.h           | 26 ++++----
 .../view/accessibility/AccessibilityProps.cpp | 15 +----
 .../view/accessibility/AccessibilityProps.h   | 30 +++++----
 ReactCommon/fabric/view/root/RootProps.cpp    | 36 +++++------
 ReactCommon/fabric/view/root/RootProps.h      | 20 +++---
 .../fabric/view/root/RootShadowNode.cpp       |  2 +-
 .../view/yoga/YogaLayoutableShadowNode.cpp    |  6 +-
 .../fabric/view/yoga/YogaStylableProps.cpp    | 18 ++++--
 .../fabric/view/yoga/YogaStylableProps.h      | 12 ++--
 31 files changed, 224 insertions(+), 304 deletions(-)

diff --git a/React/Fabric/Mounting/RCTParagraphComponentView.mm b/React/Fabric/Mounting/RCTParagraphComponentView.mm
index 29175e9f535e..770913113ec3 100644
--- a/React/Fabric/Mounting/RCTParagraphComponentView.mm
+++ b/React/Fabric/Mounting/RCTParagraphComponentView.mm
@@ -39,7 +39,7 @@ - (void)updateProps:(SharedProps)props oldProps:(SharedProps)oldProps
   [super updateProps:props oldProps:oldProps];
   auto paragraphProps = std::static_pointer_cast<const ParagraphProps>(props);
   assert(paragraphProps);
-  _paragraphAttributes = paragraphProps->getParagraphAttributes();
+  _paragraphAttributes = paragraphProps->paragraphAttributes;
 }
 
 - (void)updateLocalData:(SharedLocalData)localData
diff --git a/React/Fabric/Mounting/RCTViewComponentView.mm b/React/Fabric/Mounting/RCTViewComponentView.mm
index 26fff3a50a62..9183968b5b01 100644
--- a/React/Fabric/Mounting/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/RCTViewComponentView.mm
@@ -24,8 +24,8 @@ - (void)updateProps:(facebook::react::SharedProps)props
   auto oldViewProps = *std::dynamic_pointer_cast<const ViewProps>(oldProps);
   auto newViewProps = *std::dynamic_pointer_cast<const ViewProps>(props);
 
-  if (oldViewProps.getBackgroundColor() != newViewProps.getBackgroundColor()) {
-    self.backgroundColor = [UIColor colorWithCGColor:newViewProps.getBackgroundColor().get()];
+  if (oldViewProps.backgroundColor != newViewProps.backgroundColor) {
+    self.backgroundColor = [UIColor colorWithCGColor:newViewProps.backgroundColor.get()];
   }
 
   // TODO: Implement all sutable non-layout <View> props.
diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index 06a1afa7c989..93663a325a53 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -28,22 +28,12 @@ class ConcreteShadowNode: public ShadowNode {
   using SharedConcreteProps = std::shared_ptr<const PropsT>;
   using SharedConcreteShadowNode = std::shared_ptr<const ConcreteShadowNode>;
 
-  static const SharedConcreteProps Props(const RawProps &rawProps, const SharedProps &baseProps = nullptr) {
-    if (!baseProps) {
-      auto props = std::make_shared<PropsT>();
-      props->apply(rawProps);
-      return props;
-    }
-
-    auto concreteBaseProps = std::dynamic_pointer_cast<const PropsT>(baseProps);
-    assert(concreteBaseProps);
-    auto props = std::make_shared<PropsT>(*concreteBaseProps);
-    props->apply(rawProps);
-    return props;
+  static SharedConcreteProps Props(const RawProps &rawProps, const SharedProps &baseProps = nullptr) {
+    return std::make_shared<const PropsT>(baseProps ? *std::static_pointer_cast<const PropsT>(baseProps) : PropsT(), rawProps);
   }
 
-  static const SharedConcreteProps defaultSharedProps() {
-    static const SharedConcreteProps defaultSharedProps = std::make_shared<PropsT>();
+  static SharedConcreteProps defaultSharedProps() {
+    static const SharedConcreteProps defaultSharedProps = std::make_shared<const PropsT>();
     return defaultSharedProps;
   }
 
diff --git a/ReactCommon/fabric/core/shadownode/Props.cpp b/ReactCommon/fabric/core/shadownode/Props.cpp
index 688b288fd508..f70632d47464 100644
--- a/ReactCommon/fabric/core/shadownode/Props.cpp
+++ b/ReactCommon/fabric/core/shadownode/Props.cpp
@@ -13,15 +13,8 @@
 namespace facebook {
 namespace react {
 
-void Props::apply(const RawProps &rawProps) {
-  ensureUnsealed();
-
-  applyRawProp(rawProps, "nativeID", nativeId_);
-}
-
-const std::string &Props::getNativeId() const {
-  return nativeId_;
-}
+Props::Props(const Props &sourceProps, const RawProps &rawProps):
+  nativeId(convertRawProp(rawProps, "nativeID", sourceProps.nativeId)) {};
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/Props.h b/ReactCommon/fabric/core/shadownode/Props.h
index d7ecea7426c6..1e349020a972 100644
--- a/ReactCommon/fabric/core/shadownode/Props.h
+++ b/ReactCommon/fabric/core/shadownode/Props.h
@@ -28,12 +28,10 @@ class Props:
   public virtual DebugStringConvertible {
 
 public:
-  virtual void apply(const RawProps &rawProps);
+  Props() = default;
+  Props(const Props &sourceProps, const RawProps &rawProps);
 
-  const std::string &getNativeId() const;
-
-private:
-  std::string nativeId_ {""};
+  const std::string nativeId;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/shadownode/propsConversions.h b/ReactCommon/fabric/core/shadownode/propsConversions.h
index 689caf0ed801..89d1808fec22 100644
--- a/ReactCommon/fabric/core/shadownode/propsConversions.h
+++ b/ReactCommon/fabric/core/shadownode/propsConversions.h
@@ -20,33 +20,37 @@ inline int intFromDynamic(const folly::dynamic &value) { return value.getInt();
 inline Float floatFromDynamic(const folly::dynamic &value) { return value.getDouble(); }
 inline std::string stringFromDynamic(const folly::dynamic &value) { return value.getString(); }
 
-#define APPLY_RAW_PROP_TEMPLATE(type, converter) \
-inline static void applyRawProp(const RawProps &rawProps, const std::string &name, type &property) { \
+#define CONVERT_RAW_PROP_TEMPLATE(type, converter) \
+inline static type convertRawProp(const RawProps &rawProps, const std::string &name, const type &defaultValue) { \
   auto &&iterator = rawProps.find(name); \
   if (iterator != rawProps.end()) { \
-    property = converter(iterator->second); \
+    return converter(iterator->second); \
+  } else { \
+    return defaultValue; \
   } \
 } \
 \
-inline static void applyRawProp(const RawProps &rawProps, const std::string &name, folly::Optional<type> &property) { \
+inline static folly::Optional<type> convertRawProp(const RawProps &rawProps, const std::string &name, const folly::Optional<type> &defaultValue) { \
   auto &&iterator = rawProps.find(name); \
   if (iterator != rawProps.end()) { \
     auto &&value = iterator->second; \
     if (value.isNull()) { \
-      property = {}; \
+      return {}; \
     } else { \
-      property = converter(value); \
+      return converter(value); \
     } \
+  } else { \
+    return defaultValue; \
   } \
 }
 
-APPLY_RAW_PROP_TEMPLATE(bool, boolFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(int, intFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(Float, floatFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(std::string, stringFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(SharedColor, colorFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(Point, pointFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(Size, sizeFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(bool, boolFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(int, intFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(Float, floatFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(std::string, stringFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(SharedColor, colorFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(Point, pointFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(Size, sizeFromDynamic)
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
index 460a3124bc3e..f297d3800a84 100644
--- a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
+++ b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
@@ -26,7 +26,7 @@ TEST(ComponentDescriptorTest, createShadowNode) {
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
   ASSERT_EQ(node->getTag(), 9);
   ASSERT_EQ(node->getRootTag(), 1);
-  ASSERT_STREQ(node->getProps()->getNativeId().c_str(), "abc");
+  ASSERT_STREQ(node->getProps()->nativeId.c_str(), "abc");
 }
 
 TEST(ComponentDescriptorTest, cloneShadowNode) {
@@ -42,7 +42,7 @@ TEST(ComponentDescriptorTest, cloneShadowNode) {
   ASSERT_STREQ(cloned->getComponentName().c_str(), "Test");
   ASSERT_EQ(cloned->getTag(), 9);
   ASSERT_EQ(cloned->getRootTag(), 1);
-  ASSERT_STREQ(cloned->getProps()->getNativeId().c_str(), "abc");
+  ASSERT_STREQ(cloned->getProps()->nativeId.c_str(), "abc");
 }
 
 TEST(ComponentDescriptorTest, appendChild) {
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index 7a945bf40fb1..3395763d9e55 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -19,13 +19,12 @@ TEST(ShadowNodeTest, handleProps) {
   RawProps raw;
   raw["nativeID"] = "abc";
 
-  auto props = std::make_shared<Props>();
-  props->apply(raw);
+  auto props = std::make_shared<Props>(Props(), raw);
 
   // Props are not sealed after applying raw props.
   ASSERT_FALSE(props->getSealed());
 
-  ASSERT_STREQ(props->getNativeId().c_str(), "abc");
+  ASSERT_STREQ(props->nativeId.c_str(), "abc");
 }
 
 TEST(ShadowNodeTest, handleShadowNodeCreation) {
@@ -41,7 +40,7 @@ TEST(ShadowNodeTest, handleShadowNodeCreation) {
   ASSERT_EQ(node->getSourceNode(), nullptr);
   ASSERT_EQ(node->getChildren()->size(), 0);
 
-  ASSERT_STREQ(node->getProps()->getNativeId().c_str(), "testNativeID");
+  ASSERT_STREQ(node->getProps()->nativeId.c_str(), "testNativeID");
 
   node->sealRecursive();
   ASSERT_TRUE(node->getSealed());
diff --git a/ReactCommon/fabric/core/tests/TestComponent.h b/ReactCommon/fabric/core/tests/TestComponent.h
index 87372ffea8c2..b7257caabc06 100644
--- a/ReactCommon/fabric/core/tests/TestComponent.h
+++ b/ReactCommon/fabric/core/tests/TestComponent.h
@@ -13,6 +13,7 @@
 #include <fabric/core/ConcreteShadowNode.h>
 #include <fabric/core/LocalData.h>
 #include <fabric/core/ShadowNode.h>
+#include <folly/dynamic.h>
 
 using namespace facebook::react;
 
@@ -37,11 +38,9 @@ class TestLocalData: public LocalData {
 
 class TestProps : public Props {
 public:
-  TestProps() {
-    RawProps raw;
-    raw["nativeID"] = "testNativeID";
-    apply(raw);
-  }
+  using Props::Props;
+  TestProps():
+    Props(Props(), {{"nativeID", "testNativeID"}}) {}
 };
 using SharedTestProps = std::shared_ptr<const TestProps>;
 
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
index 5b03c924d5eb..736474355879 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
+++ b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
@@ -16,52 +16,53 @@
 namespace facebook {
 namespace react {
 
-void BaseTextProps::apply(const RawProps &rawProps) {
+static TextAttributes convertRawProp(const RawProps &rawProps, const TextAttributes defaultTextAttributes) {
+  TextAttributes textAttributes;
+
   // Color
-  applyRawProp(rawProps, "color", textAttributes_.foregroundColor);
-  applyRawProp(rawProps, "backgroundColor", textAttributes_.backgroundColor);
-  applyRawProp(rawProps, "opacity", textAttributes_.opacity);
+  textAttributes.foregroundColor = convertRawProp(rawProps, "color", defaultTextAttributes.foregroundColor);
+  textAttributes.backgroundColor = convertRawProp(rawProps, "backgroundColor", defaultTextAttributes.backgroundColor);
+  textAttributes.opacity = convertRawProp(rawProps, "opacity", defaultTextAttributes.opacity);
 
   // Font
-  applyRawProp(rawProps, "fontFamily", textAttributes_.fontFamily);
-  applyRawProp(rawProps, "fontSize", textAttributes_.fontSize);
-  applyRawProp(rawProps, "fontSizeMultiplier", textAttributes_.fontSizeMultiplier);
-  applyRawProp(rawProps, "fontWeight", textAttributes_.fontWeight);
-  applyRawProp(rawProps, "fontStyle", textAttributes_.fontStyle);
-  applyRawProp(rawProps, "fontVariant", textAttributes_.fontVariant);
-  applyRawProp(rawProps, "allowFontScaling", textAttributes_.allowFontScaling);
-  applyRawProp(rawProps, "letterSpacing", textAttributes_.letterSpacing);
+  textAttributes.fontFamily = convertRawProp(rawProps, "fontFamily", defaultTextAttributes.fontFamily);
+  textAttributes.fontSize = convertRawProp(rawProps, "fontSize", defaultTextAttributes.fontSize);
+  textAttributes.fontSizeMultiplier = convertRawProp(rawProps, "fontSizeMultiplier", defaultTextAttributes.fontSizeMultiplier);
+  textAttributes.fontWeight = convertRawProp(rawProps, "fontWeight", defaultTextAttributes.fontWeight);
+  textAttributes.fontStyle = convertRawProp(rawProps, "fontStyle", defaultTextAttributes.fontStyle);
+  textAttributes.fontVariant = convertRawProp(rawProps, "fontVariant", defaultTextAttributes.fontVariant);
+  textAttributes.allowFontScaling = convertRawProp(rawProps, "allowFontScaling", defaultTextAttributes.allowFontScaling);
+  textAttributes.letterSpacing = convertRawProp(rawProps, "letterSpacing", defaultTextAttributes.letterSpacing);
 
   // Paragraph
-  applyRawProp(rawProps, "lineHeight", textAttributes_.lineHeight);
-  applyRawProp(rawProps, "alignment", textAttributes_.alignment);
-  applyRawProp(rawProps, "baseWritingDirection", textAttributes_.baseWritingDirection);
+  textAttributes.lineHeight = convertRawProp(rawProps, "lineHeight", defaultTextAttributes.lineHeight);
+  textAttributes.alignment = convertRawProp(rawProps, "alignment", defaultTextAttributes.alignment);
+  textAttributes.baseWritingDirection = convertRawProp(rawProps, "baseWritingDirection", defaultTextAttributes.baseWritingDirection);
 
   // Decoration
-  applyRawProp(rawProps, "textDecorationColor", textAttributes_.textDecorationColor);
-  applyRawProp(rawProps, "textDecorationLineType", textAttributes_.textDecorationLineType);
-  applyRawProp(rawProps, "textDecorationLineStyle", textAttributes_.textDecorationLineStyle);
-  applyRawProp(rawProps, "textDecorationLinePattern", textAttributes_.textDecorationLinePattern);
+  textAttributes.textDecorationColor = convertRawProp(rawProps, "textDecorationColor", defaultTextAttributes.textDecorationColor);
+  textAttributes.textDecorationLineType = convertRawProp(rawProps, "textDecorationLineType", defaultTextAttributes.textDecorationLineType);
+  textAttributes.textDecorationLineStyle = convertRawProp(rawProps, "textDecorationLineStyle", defaultTextAttributes.textDecorationLineStyle);
+  textAttributes.textDecorationLinePattern = convertRawProp(rawProps, "textDecorationLinePattern", defaultTextAttributes.textDecorationLinePattern);
 
   // Shadow
-  applyRawProp(rawProps, "textShadowOffset", textAttributes_.textShadowOffset);
-  applyRawProp(rawProps, "textShadowRadius", textAttributes_.textShadowRadius);
-  applyRawProp(rawProps, "textShadowColor", textAttributes_.textShadowColor);
+  textAttributes.textShadowOffset = convertRawProp(rawProps, "textShadowOffset", defaultTextAttributes.textShadowOffset);
+  textAttributes.textShadowRadius = convertRawProp(rawProps, "textShadowRadius", defaultTextAttributes.textShadowRadius);
+  textAttributes.textShadowColor = convertRawProp(rawProps, "textShadowColor", defaultTextAttributes.textShadowColor);
 
   // Special
-  applyRawProp(rawProps, "isHighlighted", textAttributes_.isHighlighted);
-}
+  textAttributes.isHighlighted = convertRawProp(rawProps, "isHighlighted", defaultTextAttributes.isHighlighted);
 
-#pragma mark - Getters
-
-TextAttributes BaseTextProps::getTextAttributes() const {
-  return textAttributes_;
+  return textAttributes;
 }
 
+BaseTextProps::BaseTextProps(const BaseTextProps &sourceProps, const RawProps &rawProps):
+  textAttributes(convertRawProp(rawProps, sourceProps.textAttributes)) {};
+
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList BaseTextProps::getDebugProps() const {
-  return textAttributes_.getDebugProps();
+  return textAttributes.getDebugProps();
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.h b/ReactCommon/fabric/text/basetext/BaseTextProps.h
index 9d3909a3b354..6e5026a594db 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextProps.h
+++ b/ReactCommon/fabric/text/basetext/BaseTextProps.h
@@ -22,27 +22,17 @@ namespace react {
 class BaseTextProps {
 public:
 
-  /*
-   * Same semantic as `Props::apply(...)`.
-   */
-  void apply(const RawProps &rawProps);
+  BaseTextProps() = default;
+  BaseTextProps(const BaseTextProps &sourceProps, const RawProps &rawProps);
 
-#pragma mark - Getters
+#pragma mark - Props
 
-  /*
-   * Returns all props values as `TextAttributes` object.
-   */
-  TextAttributes getTextAttributes() const;
+  const TextAttributes textAttributes {};
 
 #pragma mark - DebugStringConvertible (partially)
 
   SharedDebugStringConvertibleList getDebugProps() const;
-
-private:
-
-  TextAttributes textAttributes_;
 };
 
 } // namespace react
 } // namespace facebook
-
diff --git a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
index f37f534b880d..d812d242c060 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
+++ b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
@@ -30,7 +30,7 @@ AttributedString BaseTextShadowNode::getAttributedString(
     SharedRawTextShadowNode rawTextShadowNode = std::dynamic_pointer_cast<const RawTextShadowNode>(childNode);
     if (rawTextShadowNode) {
       AttributedString::Fragment fragment;
-      fragment.string = rawTextShadowNode->getProps()->getText();
+      fragment.string = rawTextShadowNode->getProps()->text;
       fragment.textAttributes = textAttributes;
       attributedString.appendFragment(fragment);
       continue;
@@ -40,7 +40,7 @@ AttributedString BaseTextShadowNode::getAttributedString(
     SharedTextShadowNode textShadowNode = std::dynamic_pointer_cast<const TextShadowNode>(childNode);
     if (textShadowNode) {
       TextAttributes localTextAttributes = textAttributes;
-      localTextAttributes.apply(textShadowNode->getProps()->getTextAttributes());
+      localTextAttributes.apply(textShadowNode->getProps()->textAttributes);
       attributedString.appendAttributedString(textShadowNode->getAttributedString(localTextAttributes, textShadowNode->getChildren()));
       continue;
     }
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
index a4481e138366..628ee1eff744 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
@@ -15,38 +15,34 @@
 namespace facebook {
 namespace react {
 
-void ParagraphProps::apply(const RawProps &rawProps) {
-  ViewProps::apply(rawProps);
-  BaseTextProps::apply(rawProps);
-
-  // Paragraph Attributes
-  applyRawProp(rawProps, "numberOfLines", paragraphAttributes_.maximumNumberOfLines);
-  applyRawProp(rawProps, "ellipsizeMode", paragraphAttributes_.ellipsizeMode);
-  applyRawProp(rawProps, "adjustsFontSizeToFit", paragraphAttributes_.adjustsFontSizeToFit);
-  applyRawProp(rawProps, "minimumFontSize", paragraphAttributes_.minimumFontSize);
-  applyRawProp(rawProps, "maximumFontSize", paragraphAttributes_.maximumFontSize);
-
-  // Other Props
-  applyRawProp(rawProps, "selectable", isSelectable_);
-}
+static ParagraphAttributes convertRawProp(const RawProps &rawProps, const ParagraphAttributes &defaultParagraphAttributes) {
+  ParagraphAttributes paragraphAttributes;
 
-#pragma mark - Getters
+  paragraphAttributes.maximumNumberOfLines = convertRawProp(rawProps, "numberOfLines", defaultParagraphAttributes.maximumNumberOfLines);
+  paragraphAttributes.ellipsizeMode = convertRawProp(rawProps, "ellipsizeMode", defaultParagraphAttributes.ellipsizeMode);
+  paragraphAttributes.adjustsFontSizeToFit = convertRawProp(rawProps, "adjustsFontSizeToFit", defaultParagraphAttributes.adjustsFontSizeToFit);
+  paragraphAttributes.minimumFontSize = convertRawProp(rawProps, "minimumFontSize", defaultParagraphAttributes.minimumFontSize);
+  paragraphAttributes.maximumFontSize = convertRawProp(rawProps, "maximumFontSize", defaultParagraphAttributes.maximumFontSize);
 
-ParagraphAttributes ParagraphProps::getParagraphAttributes() const {
-  return paragraphAttributes_;
+  return paragraphAttributes;
 }
 
-bool ParagraphProps::getIsSelectable() const {
-  return isSelectable_;
-}
+ParagraphProps::ParagraphProps(const ParagraphProps &sourceProps, const RawProps &rawProps):
+  ViewProps(sourceProps, rawProps),
+  BaseTextProps(sourceProps, rawProps),
+  paragraphAttributes(convertRawProp(rawProps, sourceProps.paragraphAttributes)),
+  isSelectable(convertRawProp(rawProps, "selectable", sourceProps.isSelectable)) {};
 
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList ParagraphProps::getDebugProps() const {
   return
     ViewProps::getDebugProps() +
-    paragraphAttributes_.getDebugProps() +
-    BaseTextProps::getDebugProps();
+    BaseTextProps::getDebugProps() +
+    paragraphAttributes.getDebugProps() +
+    SharedDebugStringConvertibleList {
+      debugStringConvertibleItem("isSelectable", isSelectable)
+    };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.h b/ReactCommon/fabric/text/paragraph/ParagraphProps.h
index 4918f47b9787..a31e1c3585b4 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.h
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.h
@@ -32,30 +32,25 @@ class ParagraphProps:
   public BaseTextProps {
 
 public:
+  ParagraphProps() = default;
+  ParagraphProps(const ParagraphProps &sourceProps, const RawProps &rawProps);
 
-  void apply(const RawProps &rawProps) override;
-
-#pragma mark - Getters
+#pragma mark - Props
 
   /*
-   * Returns `ParagraphAttributes` object which has all prop values that affect
-   * visual representation of the paragraph.
+   * Contains all prop values that affect visual representation of the paragraph.
    */
-  ParagraphAttributes getParagraphAttributes() const;
+  const ParagraphAttributes paragraphAttributes {};
 
   /*
    * Defines can the text be selected (and copied) or not.
    */
-  bool getIsSelectable() const;
+  const bool isSelectable {false};
 
 #pragma mark - DebugStringConvertible
 
   SharedDebugStringConvertibleList getDebugProps() const override;
 
-private:
-
-  ParagraphAttributes paragraphAttributes_ {};
-  bool isSelectable_ {false};
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
index 57d13d7ed66f..e7b6513ba235 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
@@ -19,7 +19,7 @@ ComponentName ParagraphShadowNode::getComponentName() const {
 }
 
 AttributedString ParagraphShadowNode::getAttributedString() const {
-  return BaseTextShadowNode::getAttributedString(getProps()->getTextAttributes(), getChildren());
+  return BaseTextShadowNode::getAttributedString(getProps()->textAttributes, getChildren());
 }
 
 void ParagraphShadowNode::setTextLayoutManager(SharedTextLayoutManager textLayoutManager) {
@@ -41,7 +41,7 @@ void ParagraphShadowNode::updateLocalData() {
 Size ParagraphShadowNode::measure(LayoutConstraints layoutConstraints) const {
   return textLayoutManager_->measure(
     getAttributedString(),
-    getProps()->getParagraphAttributes(),
+    getProps()->paragraphAttributes,
     layoutConstraints
   );
 }
diff --git a/ReactCommon/fabric/text/propsConversions.h b/ReactCommon/fabric/text/propsConversions.h
index 1656e82af44f..b8362947f43f 100644
--- a/ReactCommon/fabric/text/propsConversions.h
+++ b/ReactCommon/fabric/text/propsConversions.h
@@ -15,15 +15,15 @@
 namespace facebook {
 namespace react {
 
-APPLY_RAW_PROP_TEMPLATE(EllipsizeMode, ellipsizeModeFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(FontWeight, fontWeightFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(FontStyle, fontStyleFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(FontVariant, fontVariantFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(WritingDirection, writingDirectionFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(TextAlignment, textAlignmentFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(TextDecorationLineType, textDecorationLineTypeFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(TextDecorationLineStyle, textDecorationLineStyleFromDynamic)
-APPLY_RAW_PROP_TEMPLATE(TextDecorationLinePattern, textDecorationLinePatternFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(EllipsizeMode, ellipsizeModeFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(FontWeight, fontWeightFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(FontStyle, fontStyleFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(FontVariant, fontVariantFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(WritingDirection, writingDirectionFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(TextAlignment, textAlignmentFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(TextDecorationLineType, textDecorationLineTypeFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(TextDecorationLineStyle, textDecorationLineStyleFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(TextDecorationLinePattern, textDecorationLinePatternFromDynamic)
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/text/rawtext/RawTextProps.cpp b/ReactCommon/fabric/text/rawtext/RawTextProps.cpp
index d985188c9dd8..93f64c86f349 100644
--- a/ReactCommon/fabric/text/rawtext/RawTextProps.cpp
+++ b/ReactCommon/fabric/text/rawtext/RawTextProps.cpp
@@ -9,28 +9,21 @@
 
 #include <fabric/core/propsConversions.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
 
 namespace facebook {
 namespace react {
 
-void RawTextProps::apply(const RawProps &rawProps) {
-  Props::apply(rawProps);
-
-  applyRawProp(rawProps, "text", text_);
-}
-
-#pragma mark - Getters
-
-std::string RawTextProps::getText() const {
-  return text_;
-}
+RawTextProps::RawTextProps(const RawTextProps &sourceProps, const RawProps &rawProps):
+  Props(sourceProps, rawProps),
+  text(convertRawProp(rawProps, "text", sourceProps.text)) {};
 
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList RawTextProps::getDebugProps() const {
-  SharedDebugStringConvertibleList list = {};
-  list.push_back(std::make_shared<DebugStringConvertibleItem>("text", text_));
-  return list;
+  return {
+    debugStringConvertibleItem("text", text)
+  };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/text/rawtext/RawTextProps.h b/ReactCommon/fabric/text/rawtext/RawTextProps.h
index 4dd84f8fba5a..37ba902ee219 100644
--- a/ReactCommon/fabric/text/rawtext/RawTextProps.h
+++ b/ReactCommon/fabric/text/rawtext/RawTextProps.h
@@ -24,19 +24,16 @@ class RawTextProps:
 
 public:
 
-  void apply(const RawProps &rawProps) override;
+  RawTextProps() = default;
+  RawTextProps(const RawTextProps &sourceProps, const RawProps &rawProps);
 
-#pragma mark - Getters
+#pragma mark - Props
 
-  std::string getText() const;
+  const std::string text {""};
 
 #pragma mark - DebugStringConvertible
 
   SharedDebugStringConvertibleList getDebugProps() const override;
-
-private:
-
-  std::string text_ {""};
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/text/text/TextProps.cpp b/ReactCommon/fabric/text/text/TextProps.cpp
index c752a5f0ec01..5e8a3e1c669e 100644
--- a/ReactCommon/fabric/text/text/TextProps.cpp
+++ b/ReactCommon/fabric/text/text/TextProps.cpp
@@ -16,10 +16,8 @@
 namespace facebook {
 namespace react {
 
-void TextProps::apply(const RawProps &rawProps) {
-  Props::apply(rawProps);
-  BaseTextProps::apply(rawProps);
-}
+TextProps::TextProps(const TextProps &sourceProps, const RawProps &rawProps):
+  BaseTextProps::BaseTextProps(sourceProps, rawProps) {};
 
 #pragma mark - DebugStringConvertible
 
diff --git a/ReactCommon/fabric/text/text/TextProps.h b/ReactCommon/fabric/text/text/TextProps.h
index 8762642bb02e..b42050731740 100644
--- a/ReactCommon/fabric/text/text/TextProps.h
+++ b/ReactCommon/fabric/text/text/TextProps.h
@@ -25,7 +25,9 @@ class TextProps:
   public BaseTextProps {
 
 public:
-  void apply(const RawProps &rawProps) override;
+
+  TextProps() = default;
+  TextProps(const TextProps &sourceProps, const RawProps &rawProps);
 
 #pragma mark - DebugStringConvertible
 
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 66d2e23068c8..32a7870d96a7 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -44,9 +44,7 @@ void ShadowTree::constraintLayout(const LayoutConstraints &layoutConstraints, co
 
 UnsharedRootShadowNode ShadowTree::cloneRootShadowNode(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const {
   auto oldRootShadowNode = rootShadowNode_;
-  auto &&props = std::make_shared<RootProps>(*oldRootShadowNode->getProps());
-  props->applyLayoutConstraints(layoutConstraints);
-  props->applyLayoutContext(layoutContext);
+  auto &&props = std::make_shared<const RootProps>(*oldRootShadowNode->getProps(), layoutConstraints, layoutContext);
   auto newRootShadowNode = std::make_shared<RootShadowNode>(oldRootShadowNode, props, nullptr);
   return newRootShadowNode;
 }
diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index e49de1a6fe48..ecd11927238d 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -7,59 +7,37 @@
 
 #include "ViewProps.h"
 
-#include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/graphics/graphicValuesConversions.h>
 #include <fabric/core/propsConversions.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
+#include <fabric/graphics/debugStringConvertibleUtils.h>
+#include <fabric/graphics/graphicValuesConversions.h>
 
 namespace facebook {
 namespace react {
 
-void ViewProps::apply(const RawProps &rawProps) {
-  Props::apply(rawProps);
-  YogaStylableProps::apply(rawProps);
-
-  applyRawProp(rawProps, "zIndex", zIndex_);
-  applyRawProp(rawProps, "opacity", opacity_);
-  applyRawProp(rawProps, "color", foregroundColor_);
-  applyRawProp(rawProps, "backgroundColor", backgroundColor_);
-}
-
-#pragma mark - Getters
-
-SharedColor ViewProps::getForegroundColor() const {
-  return foregroundColor_;
-}
+ViewProps::ViewProps(const YGStyle &yogaStyle):
+  YogaStylableProps(yogaStyle) {}
 
-SharedColor ViewProps::getBackgroundColor() const {
-  return backgroundColor_;
-}
+ViewProps::ViewProps(const ViewProps &sourceProps, const RawProps &rawProps):
+  Props(sourceProps, rawProps),
+  YogaStylableProps(sourceProps, rawProps),
+  zIndex(convertRawProp(rawProps, "zIndex", sourceProps.zIndex)),
+  opacity(convertRawProp(rawProps, "opacity", sourceProps.opacity)),
+  foregroundColor(convertRawProp(rawProps, "color", sourceProps.foregroundColor)),
+  backgroundColor(convertRawProp(rawProps, "backgroundColor", sourceProps.backgroundColor)) {};
 
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList ViewProps::getDebugProps() const {
-  ViewProps defaultProps = {};
-
-  SharedDebugStringConvertibleList list = {};
-
-#define VIEW_PROPS_ADD_TO_SET(stringName, propertyName, accessor, convertor) \
-  if (propertyName != defaultProps.propertyName) { \
-    list.push_back(std::make_shared<DebugStringConvertibleItem>(#stringName, convertor(propertyName accessor))); \
-  }
-
-  VIEW_PROPS_ADD_TO_SET(zIndex, zIndex_, , std::to_string)
-  VIEW_PROPS_ADD_TO_SET(opacity, opacity_, , std::to_string)
-
-  VIEW_PROPS_ADD_TO_SET(backgroundColor, backgroundColor_, , colorNameFromColor)
-  VIEW_PROPS_ADD_TO_SET(foregroundColor, foregroundColor_, , colorNameFromColor)
-
-  // Accessibility Props
-  auto accessibilityPropsList = AccessibilityProps::getDebugProps();
-  std::move(accessibilityPropsList.begin(), accessibilityPropsList.end(), std::back_inserter(list));
-
-  // Yoga styles
-  list.push_back(std::make_shared<DebugStringConvertibleItem>("style", "", YogaStylableProps::getDebugProps()));
-
-  return list;
+  return
+    AccessibilityProps::getDebugProps() +
+    YogaStylableProps::getDebugProps() +
+    SharedDebugStringConvertibleList {
+      debugStringConvertibleItem("zIndex", zIndex),
+      debugStringConvertibleItem("opacity", opacity),
+      debugStringConvertibleItem("foregroundColor", foregroundColor),
+      debugStringConvertibleItem("backgroundColor", backgroundColor),
+    };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
index 4aceb7f11748..b0fa20369c3c 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -26,28 +26,26 @@ class ViewProps:
   public AccessibilityProps {
 
 public:
-  void apply(const RawProps &rawProps) override;
 
-#pragma mark - Getters
+  ViewProps() = default;
+  ViewProps(const YGStyle &yogaStyle);
+  ViewProps(const ViewProps &sourceProps, const RawProps &rawProps);
 
-  SharedColor getForegroundColor() const;
-  SharedColor getBackgroundColor() const;
+#pragma mark - Props
 
-#pragma mark - DebugStringConvertible
+  const int zIndex {0};
+  const Float opacity {1};
 
-  SharedDebugStringConvertibleList getDebugProps() const override;
+  const SharedColor foregroundColor {nullptr};
+  const SharedColor backgroundColor {nullptr};
 
-private:
-  int zIndex_ {0};
-  Float opacity_ {1.0};
+  const SharedColor shadowColor {nullptr};
+  const Point shadowOffset {};
 
-  SharedColor foregroundColor_ {nullptr};
-  SharedColor backgroundColor_ {nullptr};
+#pragma mark - DebugStringConvertible
 
-  SharedColor shadowColor_ {nullptr};
-  Point shadowOffset_ {0, 0};
+  SharedDebugStringConvertibleList getDebugProps() const override;
 };
 
 } // namespace react
 } // namespace facebook
-
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp b/ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp
index 373b4d9412c8..f8833ac7d928 100644
--- a/ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp
+++ b/ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp
@@ -12,20 +12,7 @@
 namespace facebook {
 namespace react {
 
-void AccessibilityProps::apply(const RawProps &rawProps) {
-  for (auto const &pair : rawProps) {
-    auto const &name = pair.first;
-    auto const &value = pair.second;
-
-#define ACCESSIBILITY_PROPERTY(stringName, variableName, accessor, convertor) \
-  if (name == #stringName) { \
-    variableName = convertor(value accessor); \
-    continue; \
-  }
-
-    ACCESSIBILITY_PROPERTY(accessibilityLabel, accessibilityLabel_, .asString(),)
-  }
-}
+AccessibilityProps::AccessibilityProps(const AccessibilityProps &sourceProps, const RawProps &rawProps) {}
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h b/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
index 12d1dbaf0a77..f807c5b556bd 100644
--- a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
+++ b/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
@@ -20,22 +20,24 @@ class AccessibilityProps;
 typedef std::shared_ptr<const AccessibilityProps> SharedAccessibilityProps;
 
 class AccessibilityProps:
-  public virtual DebugStringConvertible
-{
+  public virtual DebugStringConvertible {
 
 public:
-  void apply(const RawProps &rawProps);
-
-protected:
-  bool accessible_ {true};
-  std::string accessibilityActions_ {""};
-  std::string accessibilityLabel_ {""};
-  AccessibilityTraits accessibilityTraits_ {AccessibilityTraits::None};
-  bool accessibilityViewIsModal_ {false};
-  bool accessibilityElementsHidden_ {false};
-  SharedDirectEventHandler onAccessibilityAction_ {nullptr};
-  SharedDirectEventHandler onAccessibilityTap_ {nullptr};
-  SharedDirectEventHandler onMagicTap_ {nullptr};
+
+  AccessibilityProps() = default;
+  AccessibilityProps(const AccessibilityProps &sourceProps, const RawProps &rawProps);
+
+#pragma mark - Props
+
+  const bool accessible {true};
+  const std::string accessibilityActions {""};
+  const std::string accessibilityLabel {""};
+  const AccessibilityTraits accessibilityTraits {AccessibilityTraits::None};
+  const bool accessibilityViewIsModal {false};
+  const bool accessibilityElementsHidden {false};
+  const SharedDirectEventHandler onAccessibilityAction {nullptr};
+  const SharedDirectEventHandler onAccessibilityTap {nullptr};
+  const SharedDirectEventHandler onMagicTap {nullptr};
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/root/RootProps.cpp b/ReactCommon/fabric/view/root/RootProps.cpp
index e8f0becede97..4040ed3a7e40 100644
--- a/ReactCommon/fabric/view/root/RootProps.cpp
+++ b/ReactCommon/fabric/view/root/RootProps.cpp
@@ -7,39 +7,35 @@
 
 #include "RootProps.h"
 
+#include "YogaLayoutableShadowNode.h"
 #include "yogaValuesConversions.h"
 
 namespace facebook {
 namespace react {
 
-void RootProps::applyLayoutConstraints(const LayoutConstraints &layoutConstraints) {
-  ensureUnsealed();
-
-  layoutConstraints_ = layoutConstraints;
-
-  yogaStyle_.minDimensions[YGDimensionWidth] =
+static YGStyle yogaStyleFromLayoutConstraints(const LayoutConstraints &layoutConstraints) {
+  YGStyle yogaStyle;
+  yogaStyle.minDimensions[YGDimensionWidth] =
     yogaStyleValueFromFloat(layoutConstraints.minimumSize.width);
-  yogaStyle_.minDimensions[YGDimensionHeight] =
+  yogaStyle.minDimensions[YGDimensionHeight] =
     yogaStyleValueFromFloat(layoutConstraints.minimumSize.height);
 
-  yogaStyle_.maxDimensions[YGDimensionWidth] =
+  yogaStyle.maxDimensions[YGDimensionWidth] =
     yogaStyleValueFromFloat(layoutConstraints.maximumSize.width);
-  yogaStyle_.maxDimensions[YGDimensionHeight] =
+  yogaStyle.maxDimensions[YGDimensionHeight] =
     yogaStyleValueFromFloat(layoutConstraints.maximumSize.height);
-}
 
-void RootProps::applyLayoutContext(const LayoutContext &layoutContext) {
-  ensureUnsealed();
-  layoutContext_ = layoutContext;
+  return yogaStyle;
 }
 
-LayoutConstraints RootProps::getLayoutConstraints() const {
-  return layoutConstraints_;
-}
-
-LayoutContext RootProps::getLayoutContext() const {
-  return layoutContext_;
-}
+RootProps::RootProps(
+  const RootProps &sourceProps,
+  const LayoutConstraints &layoutConstraints,
+  const LayoutContext &layoutContext
+):
+  ViewProps(yogaStyleFromLayoutConstraints(layoutConstraints)),
+  layoutConstraints(layoutConstraints),
+  layoutContext(layoutContext) {};
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/view/root/RootProps.h b/ReactCommon/fabric/view/root/RootProps.h
index f8c40f361914..f26c53c71815 100644
--- a/ReactCommon/fabric/view/root/RootProps.h
+++ b/ReactCommon/fabric/view/root/RootProps.h
@@ -25,19 +25,17 @@ class RootProps final:
 
 public:
 
-  /*
-   * Same semantic as `apply()` but LayoutConstraints & LayoutContext specific.
-   */
-  void applyLayoutConstraints(const LayoutConstraints &layoutConstraints);
-  void applyLayoutContext(const LayoutContext &layoutContext);
+  RootProps() = default;
+  RootProps(
+    const RootProps &sourceProps,
+    const LayoutConstraints &layoutConstraints,
+    const LayoutContext &layoutContext
+  );
 
-  LayoutConstraints getLayoutConstraints() const;
-  LayoutContext getLayoutContext() const;
+#pragma mark - Props
 
-private:
-
-  LayoutConstraints layoutConstraints_;
-  LayoutContext layoutContext_;
+  const LayoutConstraints layoutConstraints {};
+  const LayoutContext layoutContext {};
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/root/RootShadowNode.cpp b/ReactCommon/fabric/view/root/RootShadowNode.cpp
index 97dc7dd011e5..7cefd4b0a476 100644
--- a/ReactCommon/fabric/view/root/RootShadowNode.cpp
+++ b/ReactCommon/fabric/view/root/RootShadowNode.cpp
@@ -16,7 +16,7 @@ ComponentName RootShadowNode::getComponentName() const {
 
 void RootShadowNode::layout() {
   ensureUnsealed();
-  layout(getProps()->getLayoutContext());
+  layout(getProps()->layoutContext);
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index bce88ce68ada..10d1a2aa7945 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -10,10 +10,10 @@
 #include <algorithm>
 #include <memory>
 
-#include <yoga/Yoga.h>
 #include <fabric/core/LayoutContext.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
+#include <yoga/Yoga.h>
 
 #include "yogaValuesConversions.h"
 
@@ -40,7 +40,7 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
 
   auto yogaNode = std::make_shared<YGNode>();
   yogaNode->setConfig(suitableYogaConfig().get());
-  yogaNode->setStyle(props->getYogaStyle());
+  yogaNode->setStyle(props->yogaStyle);
   yogaNode->setContext(this);
   yogaNode->setDirty(true);
   YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(*yogaNode, children);
@@ -59,7 +59,7 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   yogaNode->setDirty(true);
 
   if (props) {
-    yogaNode->setStyle(props->getYogaStyle());
+    yogaNode->setStyle(props->yogaStyle);
   }
 
   if (children) {
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
index c13e3462dfce..2deec512699d 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
@@ -17,18 +17,16 @@
 namespace facebook {
 namespace react {
 
-const YGStyle &YogaStylableProps::getYogaStyle() const {
-  return yogaStyle_;
-}
+static YGStyle convertRawProp(const RawProps &rawProps, const YGStyle &defaultValue) {
+  YGStyle yogaStyle = defaultValue;
 
-void YogaStylableProps::apply(const RawProps &rawProps) {
   for (auto const &pair : rawProps) {
     auto const &name = pair.first;
     auto const &value = pair.second;
 
 #define YOGA_STYLE_PROPERTY(stringName, yogaName, accessor, convertor) \
   if (name == #stringName) { \
-    yogaStyle_.yogaName = convertor(value accessor); \
+    yogaStyle.yogaName = convertor(value accessor); \
     continue; \
   }
 
@@ -97,15 +95,23 @@ void YogaStylableProps::apply(const RawProps &rawProps) {
 
     YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(aspectRatio)
   }
+
+  return yogaStyle;
 }
 
+YogaStylableProps::YogaStylableProps(const YGStyle &yogaStyle):
+  yogaStyle(yogaStyle) {}
+
+YogaStylableProps::YogaStylableProps(const YogaStylableProps &sourceProps, const RawProps &rawProps):
+  yogaStyle(convertRawProp(rawProps, sourceProps.yogaStyle)) {};
+
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList YogaStylableProps::getDebugProps() const {
   SharedDebugStringConvertibleList list = {};
 
   YGStyle defaultYogaStyle = YGStyle();
-  YGStyle currentYogaStyle = yogaStyle_;
+  YGStyle currentYogaStyle = yogaStyle;
 
 #define YOGA_STYLE_PROPS_ADD_TO_SET(stringName, propertyName, accessor, convertor) \
   { \
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.h b/ReactCommon/fabric/view/yoga/YogaStylableProps.h
index 14f721c0594b..3dd023584110 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.h
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.h
@@ -23,16 +23,18 @@ class YogaStylableProps:
   public virtual DebugStringConvertible {
 
 public:
-  const YGStyle &getYogaStyle() const;
 
-  void apply(const RawProps &rawProps);
+  YogaStylableProps() = default;
+  YogaStylableProps(const YGStyle &yogaStyle);
+  YogaStylableProps(const YogaStylableProps &sourceProps, const RawProps &rawProps);
+
+#pragma mark - Props
+
+  const YGStyle yogaStyle {};
 
 #pragma mark - DebugStringConvertible
 
   SharedDebugStringConvertibleList getDebugProps() const override;
-
-protected:
-  YGStyle yogaStyle_ {};
 };
 
 } // namespace react

From f3f378ad3d0c213f8a8e1d2a4d0460cc79cfc33f Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:31 -0700
Subject: [PATCH 0567/1109] Fabric: Using modern props-conversion appraoch for
 YogaStylableProps

Summary:
This a natiral continue of previous/ongoing work towards modernizing props pipeline.
Less defines, less code, more obvious code.

Reviewed By: fkgozali

Differential Revision: D7901246

fbshipit-source-id: 3387b6d13e21e6ec48a38c9e3708762dfe536105
---
 ReactCommon/fabric/view/propsConversions.h    | 87 ++++++++++++++++++
 .../fabric/view/yoga/YogaStylableProps.cpp    | 89 +------------------
 2 files changed, 91 insertions(+), 85 deletions(-)
 create mode 100644 ReactCommon/fabric/view/propsConversions.h

diff --git a/ReactCommon/fabric/view/propsConversions.h b/ReactCommon/fabric/view/propsConversions.h
new file mode 100644
index 000000000000..76d19228a91d
--- /dev/null
+++ b/ReactCommon/fabric/view/propsConversions.h
@@ -0,0 +1,87 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/propsConversions.h>
+#include <fabric/view/yogaValuesConversions.h>
+
+namespace facebook {
+namespace react {
+
+CONVERT_RAW_PROP_TEMPLATE(YGDirection, yogaStyleDirectionFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGFlexDirection, yogaStyleFlexDirectionFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGJustify, yogaStyleJustifyFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGAlign, yogaStyleAlignFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGPositionType, yogaStylePositionTypeFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGWrap, yogaStyleWrapFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGOverflow, yogaStyleOverflowFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGDisplay, yogaStyleDisplayFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGValue, yogaStyleValueFromDynamic)
+CONVERT_RAW_PROP_TEMPLATE(YGFloatOptional, yogaStyleOptionalFloatFromDynamic)
+
+static std::array<YGValue, 2> convertRawProp(const RawProps &rawProps, const std::string &widthName, const std::string &heightName, const std::array<YGValue, 2> &defaultValue) {
+  std::array<YGValue, 2> dimentions;
+  dimentions[YGDimensionWidth] = convertRawProp(rawProps, widthName, defaultValue[YGDimensionWidth]);
+  dimentions[YGDimensionHeight] = convertRawProp(rawProps, heightName, defaultValue[YGDimensionHeight]);
+  return dimentions;
+}
+
+static std::array<YGValue, YGEdgeCount> convertRawProp(const RawProps &rawProps, const std::string &prefix, const std::array<YGValue, YGEdgeCount> &defaultValue) {
+  std::array<YGValue, YGEdgeCount> result = defaultValue;
+  result[YGEdgeLeft] = convertRawProp(rawProps, prefix + "Left", defaultValue[YGEdgeLeft]);
+  result[YGEdgeTop] = convertRawProp(rawProps, prefix + "Top", defaultValue[YGEdgeTop]);
+  result[YGEdgeRight] = convertRawProp(rawProps, prefix + "Right", defaultValue[YGEdgeRight]);
+  result[YGEdgeBottom] = convertRawProp(rawProps, prefix + "Bottom", defaultValue[YGEdgeBottom]);
+  result[YGEdgeStart] = convertRawProp(rawProps, prefix + "Start", defaultValue[YGEdgeStart]);
+  result[YGEdgeEnd] = convertRawProp(rawProps, prefix + "End", defaultValue[YGEdgeEnd]);
+  result[YGEdgeHorizontal] = convertRawProp(rawProps, prefix + "Horizontal", defaultValue[YGEdgeHorizontal]);
+  result[YGEdgeVertical] = convertRawProp(rawProps, prefix + "Vertical", defaultValue[YGEdgeVertical]);
+  result[YGEdgeAll] = convertRawProp(rawProps, prefix, defaultValue[YGEdgeAll]);
+  return result;
+}
+
+static std::array<YGValue, YGEdgeCount> convertRawProp(const RawProps &rawProps, const std::array<YGValue, YGEdgeCount> &defaultValue) {
+  std::array<YGValue, YGEdgeCount> result = defaultValue;
+  result[YGEdgeLeft] = convertRawProp(rawProps, "left", defaultValue[YGEdgeLeft]);
+  result[YGEdgeTop] = convertRawProp(rawProps, "top", defaultValue[YGEdgeTop]);
+  result[YGEdgeRight] = convertRawProp(rawProps, "right", defaultValue[YGEdgeRight]);
+  result[YGEdgeBottom] = convertRawProp(rawProps, "bottom", defaultValue[YGEdgeBottom]);
+  result[YGEdgeStart] = convertRawProp(rawProps, "start", defaultValue[YGEdgeStart]);
+  result[YGEdgeEnd] = convertRawProp(rawProps, "end", defaultValue[YGEdgeEnd]);
+  return result;
+}
+
+static YGStyle convertRawProp(const RawProps &rawProps, const YGStyle &defaultValue) {
+  YGStyle yogaStyle;
+  yogaStyle.direction = convertRawProp(rawProps, "direction", defaultValue.direction);
+  yogaStyle.flexDirection = convertRawProp(rawProps, "flexDirection", defaultValue.flexDirection);
+  yogaStyle.justifyContent = convertRawProp(rawProps, "justifyContent", defaultValue.justifyContent);
+  yogaStyle.alignContent = convertRawProp(rawProps, "alignContent", defaultValue.alignContent);
+  yogaStyle.alignItems = convertRawProp(rawProps, "alignItems", defaultValue.alignItems);
+  yogaStyle.alignSelf = convertRawProp(rawProps, "alignSelf", defaultValue.alignSelf);
+  yogaStyle.positionType = convertRawProp(rawProps, "positionType", defaultValue.positionType);
+  yogaStyle.flexWrap = convertRawProp(rawProps, "flexWrap", defaultValue.flexWrap);
+  yogaStyle.overflow = convertRawProp(rawProps, "overflow", defaultValue.overflow);
+  yogaStyle.display = convertRawProp(rawProps, "display", defaultValue.display);
+  yogaStyle.flex = convertRawProp(rawProps, "flex", defaultValue.flex);
+  yogaStyle.flexGrow = convertRawProp(rawProps, "flexGrow", defaultValue.flexGrow);
+  yogaStyle.flexShrink = convertRawProp(rawProps, "flexShrink", defaultValue.flexShrink);
+  yogaStyle.flexBasis = convertRawProp(rawProps, "flexBasis", defaultValue.flexBasis);
+  yogaStyle.margin = convertRawProp(rawProps, "margin", defaultValue.margin);
+  yogaStyle.position = convertRawProp(rawProps, defaultValue.position);
+  yogaStyle.padding = convertRawProp(rawProps, "padding", defaultValue.padding);
+  yogaStyle.border = convertRawProp(rawProps, "border", defaultValue.border);
+  yogaStyle.dimensions = convertRawProp(rawProps, "width", "height", defaultValue.dimensions);
+  yogaStyle.minDimensions = convertRawProp(rawProps, "minWidth", "minHeight", defaultValue.minDimensions);
+  yogaStyle.maxDimensions = convertRawProp(rawProps, "maxWidth", "maxHeight", defaultValue.maxDimensions);
+  yogaStyle.aspectRatio = convertRawProp(rawProps, "aspectRatio", defaultValue.aspectRatio);
+  return yogaStyle;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
index 2deec512699d..88471868b6d0 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
@@ -7,98 +7,17 @@
 
 #include "YogaStylableProps.h"
 
-#include <yoga/Yoga.h>
-#include <yoga/YGNode.h>
-
+#include <fabric/core/propsConversions.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/view/propsConversions.h>
+#include <yoga/YGNode.h>
+#include <yoga/Yoga.h>
 
 #include "yogaValuesConversions.h"
 
 namespace facebook {
 namespace react {
 
-static YGStyle convertRawProp(const RawProps &rawProps, const YGStyle &defaultValue) {
-  YGStyle yogaStyle = defaultValue;
-
-  for (auto const &pair : rawProps) {
-    auto const &name = pair.first;
-    auto const &value = pair.second;
-
-#define YOGA_STYLE_PROPERTY(stringName, yogaName, accessor, convertor) \
-  if (name == #stringName) { \
-    yogaStyle.yogaName = convertor(value accessor); \
-    continue; \
-  }
-
-#define YOGA_STYLE_SIMPLE_FLOAT_PROPERTY(name) \
-  YOGA_STYLE_PROPERTY(name, name, .asDouble(), )
-
-#define YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(name) \
-  YOGA_STYLE_PROPERTY(name, name, .asDouble(), yogaOptionalFloatFromFabricFloat)
-
-#define YOGA_STYLE_SIMPLE_INTEGER_PROPERTY(name) \
-  YOGA_STYLE_PROPERTY(name, name, .asInt(), )
-
-// Dimension Properties
-#define YOGA_STYLE_DIMENSION_PROPERTY() \
-  YOGA_STYLE_PROPERTY(width, dimensions[YGDimensionWidth], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(height, dimensions[YGDimensionHeight], , yogaStyleValueFromDynamic)
-
-#define YOGA_STYLE_PREFIXED_DIMENSION_PROPERTY(prefix) \
-  YOGA_STYLE_PROPERTY(prefix##Width, prefix##Dimensions[YGDimensionWidth], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix##Height, prefix##Dimensions[YGDimensionHeight], , yogaStyleValueFromDynamic)
-
-// Edge Properties
-#define YOGA_STYLE_POSITION_EDGE_PROPERTY() \
-  YOGA_STYLE_PROPERTY(left, position[YGEdgeLeft], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(top, position[YGEdgeTop], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(right, position[YGEdgeRight], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(bottom, position[YGEdgeBottom], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(start, position[YGEdgeStart], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(end, position[YGEdgeEnd], , yogaStyleValueFromDynamic)
-
-#define YOGA_STYLE_PREFIXED_EDGE_PROPERTY(prefix) \
-  YOGA_STYLE_PROPERTY(prefix##Left, prefix[YGEdgeLeft], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix##Top, prefix[YGEdgeTop], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix##Right, prefix[YGEdgeRight], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix##Bottom, prefix[YGEdgeBottom], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix##Start, prefix[YGEdgeStart], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix##End, prefix[YGEdgeEnd], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix##Horizontal, prefix[YGEdgeHorizontal], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix##Vertical, prefix[YGEdgeVertical], , yogaStyleValueFromDynamic) \
-  YOGA_STYLE_PROPERTY(prefix, prefix[YGEdgeAll], , yogaStyleValueFromDynamic)
-
-    YOGA_STYLE_PROPERTY(direction, direction, , yogaStyleDirectionFromDynamic)
-    YOGA_STYLE_PROPERTY(flexDirection, flexDirection, , yogaStyleFlexDirectionFromDynamic)
-    YOGA_STYLE_PROPERTY(justifyContent, justifyContent, , yogaStyleJustifyFromDynamic)
-    YOGA_STYLE_PROPERTY(alignContent, alignContent, , yogaStyleAlignFromDynamic)
-    YOGA_STYLE_PROPERTY(alignItems, alignItems, , yogaStyleAlignFromDynamic)
-    YOGA_STYLE_PROPERTY(alignSelf, alignSelf, , yogaStyleAlignFromDynamic)
-    YOGA_STYLE_PROPERTY(positionType, positionType, , yogaStylePositionTypeFromDynamic)
-    YOGA_STYLE_PROPERTY(flexWrap, flexWrap, , yogaStyleWrapFromDynamic)
-    YOGA_STYLE_PROPERTY(overflow, overflow, , yogaStyleOverflowFromDynamic)
-    YOGA_STYLE_PROPERTY(display, display, , yogaStyleDisplayFromDynamic)
-
-    YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(flex)
-    YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(flexGrow)
-    YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(flexShrink)
-    YOGA_STYLE_PROPERTY(flexBasis, flexBasis, , yogaStyleValueFromDynamic)
-
-    YOGA_STYLE_DIMENSION_PROPERTY()
-    YOGA_STYLE_PREFIXED_DIMENSION_PROPERTY(min)
-    YOGA_STYLE_PREFIXED_DIMENSION_PROPERTY(max)
-
-    YOGA_STYLE_POSITION_EDGE_PROPERTY()
-    YOGA_STYLE_PREFIXED_EDGE_PROPERTY(margin)
-    YOGA_STYLE_PREFIXED_EDGE_PROPERTY(padding)
-    YOGA_STYLE_PREFIXED_EDGE_PROPERTY(border)
-
-    YOGA_STYLE_OPTIONAL_FLOAT_PROPERTY(aspectRatio)
-  }
-
-  return yogaStyle;
-}
-
 YogaStylableProps::YogaStylableProps(const YGStyle &yogaStyle):
   yogaStyle(yogaStyle) {}
 

From 2b827c9f13409d2d4119c024597d05b5066a5453 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:34 -0700
Subject: [PATCH 0568/1109] Fabric: Modernizing debug printing in View module

Summary: This is continue of the work started in D7797561.

Reviewed By: fkgozali

Differential Revision: D7901244

fbshipit-source-id: 2f7a5cd9fa8c0079787e26e19c7c6c4255e54b42
---
 .../fabric/view/debugStringConvertibleUtils.h | 48 ++++++++++++++
 .../fabric/view/yoga/YogaStylableProps.cpp    | 66 ++++++++-----------
 .../fabric/view/yoga/YogaStylableProps.h      |  7 +-
 .../view/yoga/yogaValuesConversions.cpp       | 15 +++--
 .../fabric/view/yoga/yogaValuesConversions.h  |  8 +--
 5 files changed, 91 insertions(+), 53 deletions(-)
 create mode 100644 ReactCommon/fabric/view/debugStringConvertibleUtils.h

diff --git a/ReactCommon/fabric/view/debugStringConvertibleUtils.h b/ReactCommon/fabric/view/debugStringConvertibleUtils.h
new file mode 100644
index 000000000000..a1a2f9422701
--- /dev/null
+++ b/ReactCommon/fabric/view/debugStringConvertibleUtils.h
@@ -0,0 +1,48 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/debug/debugStringConvertibleUtils.h>
+#include <fabric/view/yogaValuesConversions.h>
+
+// Yoga does not have this as part of the library, so we have to implement it
+// here ouside of `facebook::react::` namespace.
+inline bool operator==(const YGValue &lhs, const YGValue &rhs) {
+  if (
+    (lhs.unit == YGUnitUndefined && rhs.unit == YGUnitUndefined) ||
+    (lhs.unit == YGUnitAuto && rhs.unit == YGUnitAuto)
+  ) {
+    return true;
+  }
+
+  return
+    lhs.unit == rhs.unit &&
+    ((isnan(lhs.value) && isnan(rhs.value)) || (lhs.value == rhs.value));
+}
+
+namespace facebook {
+namespace react {
+
+using YogaDimentionsType = std::array<YGValue, YGDimensionCount>;
+using YogaEdgesType = std::array<YGValue, YGEdgeCount>;
+
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YogaDimentionsType, stringFromYogaStyleDimensions)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YogaEdgesType, stringFromYogaStyleEdges)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGDirection, stringFromYogaStyleDirection)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGFlexDirection, stringFromYogaStyleFlexDirection)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGJustify, stringFromYogaStyleJustify)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGAlign, stringFromYogaStyleAlign)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGPositionType, stringFromYogaStylePositionType)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGWrap, stringFromYogaStyleWrap)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGOverflow, stringFromYogaStyleOverflow)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGDisplay, stringFromYogaStyleDisplay)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGValue, stringFromYogaStyleValue)
+DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(YGFloatOptional, stringFromYogaStyleOptionalFloat, YGFloatOptional(), IS_EQUAL)
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
index 88471868b6d0..4a3553c1ff81 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
@@ -9,6 +9,7 @@
 
 #include <fabric/core/propsConversions.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/view/debugStringConvertibleUtils.h>
 #include <fabric/view/propsConversions.h>
 #include <yoga/YGNode.h>
 #include <yoga/Yoga.h>
@@ -27,46 +28,31 @@ YogaStylableProps::YogaStylableProps(const YogaStylableProps &sourceProps, const
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList YogaStylableProps::getDebugProps() const {
-  SharedDebugStringConvertibleList list = {};
-
-  YGStyle defaultYogaStyle = YGStyle();
-  YGStyle currentYogaStyle = yogaStyle;
-
-#define YOGA_STYLE_PROPS_ADD_TO_SET(stringName, propertyName, accessor, convertor) \
-  { \
-    auto currentValueString = convertor(currentYogaStyle.propertyName accessor); \
-    auto defaultValueString = convertor(defaultYogaStyle.propertyName accessor); \
-    if (currentValueString != defaultValueString) { \
-      list.push_back(std::make_shared<DebugStringConvertibleItem>(#stringName, currentValueString)); \
-    } \
-  }
-
-  YOGA_STYLE_PROPS_ADD_TO_SET(direction, direction, , stringFromYogaStyleDirection)
-
-  YOGA_STYLE_PROPS_ADD_TO_SET(flexDirection, flexDirection, , stringFromYogaStyleFlexDirection)
-  YOGA_STYLE_PROPS_ADD_TO_SET(justifyContent, justifyContent, , stringFromYogaStyleJustify)
-  YOGA_STYLE_PROPS_ADD_TO_SET(alignItems, alignItems, , stringFromYogaStyleAlign)
-  YOGA_STYLE_PROPS_ADD_TO_SET(alignSelf, alignSelf, , stringFromYogaStyleAlign)
-  YOGA_STYLE_PROPS_ADD_TO_SET(positionType, positionType, , stringFromYogaStylePositionType)
-  YOGA_STYLE_PROPS_ADD_TO_SET(flexWrap, flexWrap, , stringFromYogaStyleWrap)
-  YOGA_STYLE_PROPS_ADD_TO_SET(overflow, overflow, , stringFromYogaStyleOverflow)
-
-  YOGA_STYLE_PROPS_ADD_TO_SET(flex, flex, , stringFromYogaStyleOptionalFloat)
-  YOGA_STYLE_PROPS_ADD_TO_SET(flexGrow, flexGrow, , stringFromYogaStyleOptionalFloat)
-  YOGA_STYLE_PROPS_ADD_TO_SET(flexShrink, flexShrink, , stringFromYogaStyleOptionalFloat)
-  YOGA_STYLE_PROPS_ADD_TO_SET(flexBasis, flexBasis, , stringFromYogaStyleValue)
-  YOGA_STYLE_PROPS_ADD_TO_SET(margin, margin, , stringFromYogaStyleEdge)
-  YOGA_STYLE_PROPS_ADD_TO_SET(position, position, , stringFromYogaStyleEdge)
-  YOGA_STYLE_PROPS_ADD_TO_SET(padding, padding, , stringFromYogaStyleEdge)
-  YOGA_STYLE_PROPS_ADD_TO_SET(border, border, , stringFromYogaStyleEdge)
-
-  YOGA_STYLE_PROPS_ADD_TO_SET(size, dimensions, , stringFromYogaStyleDimensions)
-  YOGA_STYLE_PROPS_ADD_TO_SET(minSize, minDimensions, , stringFromYogaStyleDimensions)
-  YOGA_STYLE_PROPS_ADD_TO_SET(maxSize, maxDimensions, , stringFromYogaStyleDimensions)
-
-  YOGA_STYLE_PROPS_ADD_TO_SET(aspectRatio, aspectRatio, , stringFromYogaStyleOptionalFloat)
-
-  return list;
+  YGStyle defaultYogaStyle;
+  return {
+    debugStringConvertibleItem("direction", yogaStyle.direction, defaultYogaStyle.direction),
+    debugStringConvertibleItem("flexDirection", yogaStyle.flexDirection, defaultYogaStyle.flexDirection),
+    debugStringConvertibleItem("justifyContent", yogaStyle.justifyContent, defaultYogaStyle.justifyContent),
+    debugStringConvertibleItem("alignContent", yogaStyle.alignContent, defaultYogaStyle.alignContent),
+    debugStringConvertibleItem("alignItems", yogaStyle.alignItems, defaultYogaStyle.alignItems),
+    debugStringConvertibleItem("alignSelf", yogaStyle.alignSelf, defaultYogaStyle.alignSelf),
+    debugStringConvertibleItem("positionType", yogaStyle.positionType, defaultYogaStyle.positionType),
+    debugStringConvertibleItem("flexWrap", yogaStyle.flexWrap, defaultYogaStyle.flexWrap),
+    debugStringConvertibleItem("overflow", yogaStyle.overflow, defaultYogaStyle.overflow),
+    debugStringConvertibleItem("display", yogaStyle.display, defaultYogaStyle.display),
+    debugStringConvertibleItem("flex", yogaStyle.flex, defaultYogaStyle.flex),
+    debugStringConvertibleItem("flexGrow", yogaStyle.flexGrow, defaultYogaStyle.flexGrow),
+    debugStringConvertibleItem("flexShrink", yogaStyle.flexShrink, defaultYogaStyle.flexShrink),
+    debugStringConvertibleItem("flexBasis", yogaStyle.flexBasis, defaultYogaStyle.flexBasis),
+    debugStringConvertibleItem("margin", yogaStyle.margin, defaultYogaStyle.margin),
+    debugStringConvertibleItem("position", yogaStyle.position, defaultYogaStyle.position),
+    debugStringConvertibleItem("padding", yogaStyle.padding, defaultYogaStyle.padding),
+    debugStringConvertibleItem("border", yogaStyle.border, defaultYogaStyle.border),
+    debugStringConvertibleItem("dimensions", yogaStyle.dimensions, defaultYogaStyle.dimensions),
+    debugStringConvertibleItem("minDimensions", yogaStyle.minDimensions, defaultYogaStyle.minDimensions),
+    debugStringConvertibleItem("maxDimensions", yogaStyle.maxDimensions, defaultYogaStyle.maxDimensions),
+    debugStringConvertibleItem("aspectRatio", yogaStyle.aspectRatio, defaultYogaStyle.aspectRatio),
+  };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.h b/ReactCommon/fabric/view/yoga/YogaStylableProps.h
index 3dd023584110..c62bb03e7094 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.h
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.h
@@ -19,8 +19,7 @@ class YogaStylableProps;
 
 typedef std::shared_ptr<const YogaStylableProps> SharedYogaStylableProps;
 
-class YogaStylableProps:
-  public virtual DebugStringConvertible {
+class YogaStylableProps {
 
 public:
 
@@ -32,9 +31,9 @@ class YogaStylableProps:
 
   const YGStyle yogaStyle {};
 
-#pragma mark - DebugStringConvertible
+#pragma mark - DebugStringConvertible (Partial)
 
-  SharedDebugStringConvertibleList getDebugProps() const override;
+  SharedDebugStringConvertibleList getDebugProps() const;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
index 328ea9f18332..d53f78b2a628 100644
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
@@ -220,7 +220,7 @@ YGFloatOptional yogaStyleOptionalFloatFromDynamic(const folly::dynamic &value) {
   abort();
 }
 
-std::string stringFromYogaDimensions(std::array<float, 2> dimensions) {
+std::string stringFromYogaDimensions(std::array<float, YGDimensionCount> dimensions) {
   return "{" + folly::to<std::string>(dimensions[0]) + ", " + folly::to<std::string>(dimensions[1]) + "}";
 }
 
@@ -228,7 +228,7 @@ std::string stringFromYogaPosition(std::array<float, 4> position) {
   return "{" + folly::to<std::string>(position[0]) + ", " + folly::to<std::string>(position[1]) + "}";
 }
 
-std::string stringFromYogaEdges(std::array<float, 6> edges) {
+std::string stringFromYogaEdges(std::array<float, YGEdgeCount> edges) {
   return "{" +
     folly::to<std::string>(edges[0]) + ", " +
     folly::to<std::string>(edges[1]) + ", " +
@@ -324,18 +324,23 @@ std::string stringFromYogaStyleOptionalFloat(YGFloatOptional value) {
   return folly::to<std::string>(fabricFloatFromYogaFloat(value.getValue()));
 }
 
-std::string stringFromYogaStyleDimensions(std::array<YGValue, 2> value) {
+std::string stringFromYogaStyleDimensions(std::array<YGValue, YGDimensionCount> value) {
   return "{" +
     stringFromYogaStyleValue(value[0]) + ", " +
     stringFromYogaStyleValue(value[1]) + "}";
 }
 
-std::string stringFromYogaStyleEdge(std::array<YGValue, YGEdgeCount> value) {
+std::string stringFromYogaStyleEdges(std::array<YGValue, YGEdgeCount> value) {
   return "{" +
     stringFromYogaStyleValue(value[0]) + ", " +
     stringFromYogaStyleValue(value[1]) + ", " +
     stringFromYogaStyleValue(value[2]) + ", " +
-    stringFromYogaStyleValue(value[3]) + "}";
+    stringFromYogaStyleValue(value[3]) + ", " +
+    stringFromYogaStyleValue(value[4]) + ", " +
+    stringFromYogaStyleValue(value[5]) + ", " +
+    stringFromYogaStyleValue(value[6]) + ", " +
+    stringFromYogaStyleValue(value[7]) + ", " +
+    stringFromYogaStyleValue(value[8]) + "}";
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.h b/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
index 6837f9e10b32..376182933aa8 100644
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
+++ b/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
@@ -39,9 +39,9 @@ YGDisplay yogaStyleDisplayFromDynamic(const folly::dynamic &value);
 YGValue yogaStyleValueFromDynamic(const folly::dynamic &value);
 YGFloatOptional yogaStyleOptionalFloatFromDynamic(const folly::dynamic &value);
 
-std::string stringFromYogaDimensions(std::array<float, 2> dimensions);
+std::string stringFromYogaDimensions(std::array<float, YGDimensionCount> dimensions);
 std::string stringFromYogaPosition(std::array<float, 4> position);
-std::string stringFromYogaEdges(std::array<float, 6> edges);
+std::string stringFromYogaEdges(std::array<float, YGEdgeCount> edges);
 std::string stringFromYogaStyleDirection(YGDirection direction);
 std::string stringFromYogaStyleFlexDirection(YGFlexDirection value);
 std::string stringFromYogaStyleJustify(YGJustify value);
@@ -52,8 +52,8 @@ std::string stringFromYogaStyleOverflow(YGOverflow value);
 std::string stringFromYogaStyleDisplay(YGDisplay value);
 std::string stringFromYogaStyleValue(YGValue value);
 std::string stringFromYogaStyleOptionalFloat(YGFloatOptional value);
-std::string stringFromYogaStyleDimensions(std::array<YGValue, 2> value);
-std::string stringFromYogaStyleEdge(std::array<YGValue, YGEdgeCount> value);
+std::string stringFromYogaStyleDimensions(std::array<YGValue, YGDimensionCount> value);
+std::string stringFromYogaStyleEdges(std::array<YGValue, YGEdgeCount> value);
 
 } // namespace react
 } // namespace facebook

From 03fb77cc95aabbe088a942569cc2ded606454e58 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:40 -0700
Subject: [PATCH 0569/1109] Fabric: Using templates to generate convertRawProp
 and debugStringConvertibleItem functions

Summary:
This diff opens a diffstack where we migrate the generation of all prop conversions (convertRawProp) and pretty-printing (debugStringConvertibleItem) functions to C++ templates (instead of using `#define`s).
So, this diff implements base versions of those functions as templated functions.
For now we still need #define-based version, but eventually, we will get rid of it.

Reviewed By: fkgozali

Differential Revision: D7958247

fbshipit-source-id: 24346297c1bd17e8054758f0eb84698eebfa21e2
---
 .../attributedstring/ParagraphAttributes.h      |  2 +-
 .../fabric/core/shadownode/propsConversions.h   | 17 +++++++++++++++++
 .../fabric/debug/debugStringConvertibleUtils.h  |  9 +++++++++
 .../text/paragraph/ParagraphLocalData.cpp       |  3 ++-
 4 files changed, 29 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/attributedstring/ParagraphAttributes.h b/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
index 42eb1aa0ab06..baa47c0c363b 100644
--- a/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
+++ b/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
@@ -39,7 +39,7 @@ class ParagraphAttributes:
   int maximumNumberOfLines {0};
 
   /*
-   * In case if a text cannot fit given boudaures, defines a place where
+   * In case if a text cannot fit given boundaries, defines a place where
    * an ellipsize should be placed.
    */
   EllipsizeMode ellipsizeMode {EllipsizeMode::Clip};
diff --git a/ReactCommon/fabric/core/shadownode/propsConversions.h b/ReactCommon/fabric/core/shadownode/propsConversions.h
index 89d1808fec22..290a3fa1716b 100644
--- a/ReactCommon/fabric/core/shadownode/propsConversions.h
+++ b/ReactCommon/fabric/core/shadownode/propsConversions.h
@@ -52,5 +52,22 @@ CONVERT_RAW_PROP_TEMPLATE(SharedColor, colorFromDynamic)
 CONVERT_RAW_PROP_TEMPLATE(Point, pointFromDynamic)
 CONVERT_RAW_PROP_TEMPLATE(Size, sizeFromDynamic)
 
+inline void fromDynamic(const folly::dynamic &value, bool &result) { result = value.getBool(); }
+inline void fromDynamic(const folly::dynamic &value, int &result) { result = value.getInt(); }
+inline void fromDynamic(const folly::dynamic &value, Float &result) { result = value.getDouble(); }
+inline void fromDynamic(const folly::dynamic &value, std::string &result) { result = value.getString(); }
+
+template <typename T>
+inline T convertRawProp(const RawProps &rawProps, const std::string &name, const T &defaultValue) {
+  auto &&iterator = rawProps.find(name);
+  if (iterator != rawProps.end()) {
+    T result = defaultValue;
+    fromDynamic(iterator->second, result);
+    return result;
+  } else {
+    return defaultValue;
+  }
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
index d6be81b3c6be..e956208585e5 100644
--- a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
+++ b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
@@ -19,6 +19,15 @@
 namespace facebook {
 namespace react {
 
+template <typename T>
+inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, T value, T defaultValue = {}) {
+  if (value == defaultValue) {
+    return nullptr;
+  }
+
+  return std::make_shared<DebugStringConvertibleItem>(name, toString(value));
+}
+
 SharedDebugStringConvertibleList operator+(const SharedDebugStringConvertibleList &lhs, const SharedDebugStringConvertibleList &rhs);
 SharedDebugStringConvertible debugStringConvertibleItem(std::string name, DebugStringConvertible value, std::string defaultValue = "");
 
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
index 0064ee862e7f..c96098981d64 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
@@ -8,6 +8,7 @@
 #include "ParagraphLocalData.h"
 
 #include <fabric/debug/debugStringConvertibleUtils.h>
+#include <fabric/attributedstring/debugStringConvertibleUtils.h>
 
 namespace facebook {
 namespace react {
@@ -38,7 +39,7 @@ std::string ParagraphLocalData::getDebugName() const {
 
 SharedDebugStringConvertibleList ParagraphLocalData::getDebugProps() const {
   return {
-    debugStringConvertibleItem("attributedString", attributedString_)
+    debugStringConvertibleItem("attributedString", attributedString_, "")
   };
 }
 

From 7048c9134ae18e51c8903a7d476b5e7e7d997d90 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:42 -0700
Subject: [PATCH 0570/1109] Fabric: Support for optionals in `convertRawProp`
 and `debugStringConvertibleItem` templates

Summary:
We have to have automatic treatment for `optional` types. So, if we can process type `T` we can also automatically process `optional<T>.`
Support for optional allows us to not introduce new types (with embedded special "undefined" value) or pollute existing pure types (with special "undefined" value). (A lot of examples of those types can be found in AttributedString module.)

Reviewed By: fkgozali

Differential Revision: D7958249

fbshipit-source-id: 21af526a17dd0329e1262020cab8ecb902316654
---
 .../fabric/core/shadownode/propsConversions.h   | 17 +++++++++++++++++
 .../fabric/debug/debugStringConvertibleUtils.h  |  8 ++++++++
 2 files changed, 25 insertions(+)

diff --git a/ReactCommon/fabric/core/shadownode/propsConversions.h b/ReactCommon/fabric/core/shadownode/propsConversions.h
index 290a3fa1716b..b03bdc1387b7 100644
--- a/ReactCommon/fabric/core/shadownode/propsConversions.h
+++ b/ReactCommon/fabric/core/shadownode/propsConversions.h
@@ -69,5 +69,22 @@ inline T convertRawProp(const RawProps &rawProps, const std::string &name, const
   }
 }
 
+template <typename T>
+inline static folly::Optional<T> convertRawProp(const RawProps &rawProps, const std::string &name, const folly::Optional<T> &defaultValue) {
+  auto &&iterator = rawProps.find(name);
+  if (iterator != rawProps.end()) {
+    auto &&value = iterator->second;
+    if (value.isNull()) {
+      return defaultValue;
+    } else {
+      T result;
+      fromDynamic(value, result);
+      return result;
+    }
+  } else {
+    return defaultValue;
+  }
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
index e956208585e5..22eca9acfa90 100644
--- a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
+++ b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
@@ -28,6 +28,14 @@ inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name,
   return std::make_shared<DebugStringConvertibleItem>(name, toString(value));
 }
 
+template <typename T>
+inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, folly::Optional<T> value, T defaultValue = {}) {
+  if (!value.has_value()) {
+    return nullptr;
+  }
+  return debugStringConvertibleItem(name, value.value_or(defaultValue), defaultValue);
+}
+
 SharedDebugStringConvertibleList operator+(const SharedDebugStringConvertibleList &lhs, const SharedDebugStringConvertibleList &rhs);
 SharedDebugStringConvertible debugStringConvertibleItem(std::string name, DebugStringConvertible value, std::string defaultValue = "");
 

From 9d21e6661ab6af5e37205ccfbadd8b2aa12f8320 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:45 -0700
Subject: [PATCH 0571/1109] Fabric: New props treatment in `attributedstring`
 module

Summary:
Adopting template-generated `convertRawProp` and `debugStringConvertibleItem` functions in `attributedstring` module.
Note, to do so we have to change signatures of some conversions functions to make them more overloading-friendly.

Reviewed By: fkgozali

Differential Revision: D7958245

fbshipit-source-id: 275a58bd3955a6ceb4881bffff86bf1d4501b3d2
---
 .../attributedstring/ParagraphAttributes.cpp  |   6 +-
 .../attributedstring/ParagraphAttributes.h    |   2 +-
 .../attributedstring/TextAttributes.cpp       |   2 +-
 .../fabric/attributedstring/TextAttributes.h  |   2 +-
 .../fabric/attributedstring/conversions.h     | 192 +++++++++++++++++
 .../debugStringConvertibleUtils.h             |  27 ---
 .../{TextPrimitives.h => primitives.h}        |   0
 .../tests/AttributedStringTest.cpp            |   4 -
 .../attributedstring/textValuesConversions.h  | 193 ------------------
 .../fabric/text/basetext/BaseTextProps.cpp    |   3 +-
 .../text/paragraph/ParagraphLocalData.cpp     |   1 -
 .../fabric/text/paragraph/ParagraphProps.cpp  |   3 +-
 ReactCommon/fabric/text/propsConversions.h    |  29 ---
 ReactCommon/fabric/text/text/TextProps.cpp    |   6 -
 14 files changed, 199 insertions(+), 271 deletions(-)
 create mode 100644 ReactCommon/fabric/attributedstring/conversions.h
 delete mode 100644 ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
 rename ReactCommon/fabric/attributedstring/{TextPrimitives.h => primitives.h} (100%)
 delete mode 100644 ReactCommon/fabric/attributedstring/textValuesConversions.h
 delete mode 100644 ReactCommon/fabric/text/propsConversions.h

diff --git a/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp b/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
index 43d895e7608c..f3382a54d4c9 100644
--- a/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
@@ -7,10 +7,8 @@
 
 #include "ParagraphAttributes.h"
 
-#include <fabric/attributedstring/textValuesConversions.h>
-#include <fabric/debug/DebugStringConvertibleItem.h>
-
-#include "debugStringConvertibleUtils.h"
+#include <fabric/attributedstring/conversions.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/attributedstring/ParagraphAttributes.h b/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
index baa47c0c363b..b6271999a2d7 100644
--- a/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
+++ b/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
@@ -9,7 +9,7 @@
 
 #include <limits>
 
-#include <fabric/attributedstring/TextPrimitives.h>
+#include <fabric/attributedstring/primitives.h>
 #include <fabric/debug/DebugStringConvertible.h>
 #include <fabric/graphics/Geometry.h>
 
diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.cpp b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
index 0373f5f2a3be..fe6967749047 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
@@ -7,10 +7,10 @@
 
 #include "TextAttributes.h"
 
+#include <fabric/attributedstring/conversions.h>
 #include <fabric/core/debugStringConvertibleUtils.h>
 #include <fabric/graphics/debugStringConvertibleUtils.h>
 #include <fabric/graphics/graphicValuesConversions.h>
-#include "debugStringConvertibleUtils.h"
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.h b/ReactCommon/fabric/attributedstring/TextAttributes.h
index 30159eb5c8f4..c474e7e2aa6a 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.h
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.h
@@ -9,7 +9,7 @@
 
 #include <limits>
 
-#include <fabric/attributedstring/TextPrimitives.h>
+#include <fabric/attributedstring/primitives.h>
 #include <fabric/core/LayoutPrimitives.h>
 #include <fabric/core/ReactPrimitives.h>
 #include <fabric/debug/DebugStringConvertible.h>
diff --git a/ReactCommon/fabric/attributedstring/conversions.h b/ReactCommon/fabric/attributedstring/conversions.h
new file mode 100644
index 000000000000..478d423517f0
--- /dev/null
+++ b/ReactCommon/fabric/attributedstring/conversions.h
@@ -0,0 +1,192 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/attributedstring/primitives.h>
+#include <fabric/graphics/Geometry.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+inline std::string toString(const EllipsizeMode &ellipsisMode) {
+  switch (ellipsisMode) {
+    case EllipsizeMode::Clip: return "clip";
+    case EllipsizeMode::Head: return "head";
+    case EllipsizeMode::Tail: return "tail";
+    case EllipsizeMode::Middle: return "middle";
+  }
+}
+
+inline void fromDynamic(const folly::dynamic &value, EllipsizeMode &result) {
+  auto string = value.getString();
+  if (string == "clip") { result = EllipsizeMode::Clip; return; }
+  if (string == "head") { result = EllipsizeMode::Head; return; }
+  if (string == "tail") { result = EllipsizeMode::Tail; return; }
+  if (string == "middle") { result = EllipsizeMode::Middle; return; }
+  abort();
+}
+
+inline void fromDynamic(const folly::dynamic &value, FontWeight &result) {
+  auto string = value.asString();
+  if (string == "normal") { result = FontWeight::Regular; return; }
+  if (string == "regular") { result = FontWeight::Regular; return; }
+  if (string == "bold") { result = FontWeight::Bold; return; }
+  if (string == "100") { result = FontWeight::Weight100; return; }
+  if (string == "200") { result = FontWeight::Weight200; return; }
+  if (string == "300") { result = FontWeight::Weight300; return; }
+  if (string == "400") { result = FontWeight::Weight400; return; }
+  if (string == "500") { result = FontWeight::Weight500; return; }
+  if (string == "600") { result = FontWeight::Weight600; return; }
+  if (string == "700") { result = FontWeight::Weight700; return; }
+  if (string == "800") { result = FontWeight::Weight800; return; }
+  if (string == "900") { result = FontWeight::Weight900; return; }
+  abort();
+}
+
+inline std::string toString(const FontWeight &fontWeight) {
+  return std::to_string((int)fontWeight);
+}
+
+inline void fromDynamic(const folly::dynamic &value, FontStyle &result) {
+  auto string = value.asString();
+  if (string == "normal") { result = FontStyle::Normal; return; }
+  if (string == "italic") { result = FontStyle::Italic; return; }
+  if (string == "oblique") { result = FontStyle::Oblique; return; }
+  abort();
+}
+
+inline std::string toString(const FontStyle &fontStyle) {
+  switch (fontStyle) {
+    case FontStyle::Normal: return "normal";
+    case FontStyle::Italic: return "italic";
+    case FontStyle::Oblique: return "oblique";
+  }
+}
+
+inline void fromDynamic(const folly::dynamic &value, FontVariant &result) {
+  assert(value.isArray());
+  result = FontVariant::Default;
+  for (auto &&item : value) {
+    auto string = item.asString();
+    if (string == "small-caps") { result = (FontVariant)((int)result | (int)FontVariant::SmallCaps); continue; }
+    if (string == "oldstyle-nums") { result = (FontVariant)((int)result | (int)FontVariant::OldstyleNums); continue; }
+    if (string == "lining-nums") { result = (FontVariant)((int)result | (int)FontVariant::LiningNums); continue; }
+    if (string == "tabular-nums") { result = (FontVariant)((int)result | (int)FontVariant::TabularNums); continue; }
+    if (string == "proportional-nums") { result = (FontVariant)((int)result | (int)FontVariant::ProportionalNums); continue; }
+  }
+}
+
+inline std::string toString(const FontVariant &fontVariant) {
+  std::string result;
+  std::string separator = ", ";
+  if ((int)fontVariant & (int)FontVariant::SmallCaps) { result += "small-caps" + separator; }
+  if ((int)fontVariant & (int)FontVariant::OldstyleNums) { result += "oldstyle-nums" + separator; }
+  if ((int)fontVariant & (int)FontVariant::LiningNums) { result += "lining-nums" + separator; }
+  if ((int)fontVariant & (int)FontVariant::TabularNums) { result += "tabular-nums" + separator; }
+  if ((int)fontVariant & (int)FontVariant::ProportionalNums) { result += "proportional-nums" + separator; }
+
+  if (!result.empty()) {
+    result.erase(result.length() - separator.length());
+  }
+
+  return result;
+}
+
+inline void fromDynamic(const folly::dynamic &value, TextAlignment &result) {
+  auto string = value.asString();
+  if (string == "natural") { result = TextAlignment::Natural; return; }
+  if (string == "left") { result = TextAlignment::Left; return; }
+  if (string == "center") { result = TextAlignment::Center; return; }
+  if (string == "right") { result = TextAlignment::Right; return; }
+  if (string == "justified") { result = TextAlignment::Justified; return; }
+  abort();
+}
+
+inline std::string toString(const TextAlignment &textAlignment) {
+  switch (textAlignment) {
+    case TextAlignment::Natural: return "natural";
+    case TextAlignment::Left: return "left";
+    case TextAlignment::Center: return "center";
+    case TextAlignment::Right: return "right";
+    case TextAlignment::Justified: return "justified";
+  }
+}
+
+inline void fromDynamic(const folly::dynamic &value, WritingDirection &result) {
+  auto string = value.asString();
+  if (string == "natural") { result = WritingDirection::Natural; return; }
+  if (string == "ltr") { result = WritingDirection::LeftToRight; return; }
+  if (string == "rtl") { result = WritingDirection::RightToLeft; return; }
+  abort();
+}
+
+inline std::string toString(const WritingDirection &writingDirection) {
+  switch (writingDirection) {
+    case WritingDirection::Natural: return "natural";
+    case WritingDirection::LeftToRight: return "ltr";
+    case WritingDirection::RightToLeft: return "rtl";
+  }
+}
+
+inline void fromDynamic(const folly::dynamic &value, TextDecorationLineType &result) {
+  auto string = value.asString();
+  if (string == "none") { result = TextDecorationLineType::None; return; }
+  if (string == "underline") { result = TextDecorationLineType::Underline; return; }
+  if (string == "strikethrough") { result = TextDecorationLineType::Strikethrough; return; }
+  if (string == "underline-strikethrough") { result = TextDecorationLineType::UnderlineStrikethrough; return; }
+  abort();
+}
+
+inline std::string toString(const TextDecorationLineType &textDecorationLineType) {
+  switch (textDecorationLineType) {
+    case TextDecorationLineType::None: return "none";
+    case TextDecorationLineType::Underline: return "underline";
+    case TextDecorationLineType::Strikethrough: return "strikethrough";
+    case TextDecorationLineType::UnderlineStrikethrough: return "underline-strikethrough";
+  }
+}
+
+inline void fromDynamic(const folly::dynamic &value, TextDecorationLineStyle &result) {
+  auto string = value.asString();
+  if (string == "single") { result = TextDecorationLineStyle::Single; return; }
+  if (string == "thick") { result = TextDecorationLineStyle::Thick; return; }
+  if (string == "double") { result = TextDecorationLineStyle::Double; return; }
+  abort();
+}
+
+inline std::string toString(const TextDecorationLineStyle &textDecorationLineStyle) {
+  switch (textDecorationLineStyle) {
+    case TextDecorationLineStyle::Single: return "single";
+    case TextDecorationLineStyle::Thick: return "thick";
+    case TextDecorationLineStyle::Double: return "double";
+  }
+}
+
+inline void fromDynamic(const folly::dynamic &value, TextDecorationLinePattern &result) {
+  auto string = value.asString();
+  if (string == "solid") { result = TextDecorationLinePattern::Solid; return; }
+  if (string == "dot") { result = TextDecorationLinePattern::Dot; return; }
+  if (string == "dash") { result = TextDecorationLinePattern::Dash; return; }
+  if (string == "dash-dot") { result = TextDecorationLinePattern::DashDot; return; }
+  if (string == "dash-dot-dot") { result = TextDecorationLinePattern::DashDotDot; return; }
+  abort();
+}
+
+inline std::string toString(const TextDecorationLinePattern &textDecorationLinePattern) {
+  switch (textDecorationLinePattern) {
+    case TextDecorationLinePattern::Solid: return "solid";
+    case TextDecorationLinePattern::Dot: return "dot";
+    case TextDecorationLinePattern::Dash: return "dash";
+    case TextDecorationLinePattern::DashDot: return "dash-dot";
+    case TextDecorationLinePattern::DashDotDot: return "dash-dot-dot";
+  }
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h b/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
deleted file mode 100644
index 3f303cd0668b..000000000000
--- a/ReactCommon/fabric/attributedstring/debugStringConvertibleUtils.h
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <fabric/debug/debugStringConvertibleUtils.h>
-#include <fabric/attributedstring/textValuesConversions.h>
-
-namespace facebook {
-namespace react {
-
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(EllipsizeMode, stringFromEllipsizeMode)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(FontWeight, stringFromFontWeight)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(FontStyle, stringFromFontStyle)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(FontVariant, stringFromFontVariant)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(TextAlignment, stringFromTextAlignment)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(WritingDirection, stringFromWritingDirection)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(TextDecorationLineType, stringFromTextDecorationLineType)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(TextDecorationLineStyle, stringFromTextDecorationLineStyle)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(TextDecorationLinePattern, stringFromTextDecorationLinePattern)
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/attributedstring/TextPrimitives.h b/ReactCommon/fabric/attributedstring/primitives.h
similarity index 100%
rename from ReactCommon/fabric/attributedstring/TextPrimitives.h
rename to ReactCommon/fabric/attributedstring/primitives.h
diff --git a/ReactCommon/fabric/attributedstring/tests/AttributedStringTest.cpp b/ReactCommon/fabric/attributedstring/tests/AttributedStringTest.cpp
index b3a8eddd343d..a04597a74552 100644
--- a/ReactCommon/fabric/attributedstring/tests/AttributedStringTest.cpp
+++ b/ReactCommon/fabric/attributedstring/tests/AttributedStringTest.cpp
@@ -9,10 +9,6 @@
 
 #include <gtest/gtest.h>
 
-#include <fabric/attributedstring/TextPrimitives.h>
-
-using namespace facebook::react;
-
 TEST(AttributedStringTest, testSomething) {
   // TODO
 }
diff --git a/ReactCommon/fabric/attributedstring/textValuesConversions.h b/ReactCommon/fabric/attributedstring/textValuesConversions.h
deleted file mode 100644
index bae4eb65be92..000000000000
--- a/ReactCommon/fabric/attributedstring/textValuesConversions.h
+++ /dev/null
@@ -1,193 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <fabric/attributedstring/TextPrimitives.h>
-#include <fabric/graphics/Geometry.h>
-#include <folly/dynamic.h>
-
-namespace facebook {
-namespace react {
-
-inline std::string stringFromEllipsizeMode(const EllipsizeMode &ellipsisMode) {
-  switch (ellipsisMode) {
-    case EllipsizeMode::Clip: return "clip";
-    case EllipsizeMode::Head: return "head";
-    case EllipsizeMode::Tail: return "tail";
-    case EllipsizeMode::Middle: return "middle";
-  }
-}
-
-inline EllipsizeMode ellipsizeModeFromDynamic(const folly::dynamic &value) {
-  auto string = value.getString();
-  if (string == "clip") { return EllipsizeMode::Clip; }
-  if (string == "head") { return EllipsizeMode::Head; }
-  if (string == "tail") { return EllipsizeMode::Tail; }
-  if (string == "middle") { return EllipsizeMode::Middle; }
-  abort();
-}
-
-inline FontWeight fontWeightFromDynamic(const folly::dynamic &value) {
-  auto string = value.asString();
-  if (string == "normal") { return FontWeight::Regular; }
-  if (string == "regular") { return FontWeight::Regular; }
-  if (string == "bold") { return FontWeight::Bold; }
-  if (string == "100") { return FontWeight::Weight100; }
-  if (string == "200") { return FontWeight::Weight200; }
-  if (string == "300") { return FontWeight::Weight300; }
-  if (string == "400") { return FontWeight::Weight400; }
-  if (string == "500") { return FontWeight::Weight500; }
-  if (string == "600") { return FontWeight::Weight600; }
-  if (string == "700") { return FontWeight::Weight700; }
-  if (string == "800") { return FontWeight::Weight800; }
-  if (string == "900") { return FontWeight::Weight900; }
-  abort();
-}
-
-inline std::string stringFromFontWeight(const FontWeight &fontWeight) {
-  return std::to_string((int)fontWeight);
-}
-
-inline FontStyle fontStyleFromDynamic(const folly::dynamic &value) {
-  auto string = value.asString();
-  if (string == "normal") { return FontStyle::Normal; }
-  if (string == "italic") { return FontStyle::Italic; }
-  if (string == "oblique") { return FontStyle::Oblique; }
-  abort();
-}
-
-inline std::string stringFromFontStyle(const FontStyle &fontStyle) {
-  switch (fontStyle) {
-    case FontStyle::Normal: return "normal";
-    case FontStyle::Italic: return "italic";
-    case FontStyle::Oblique: return "oblique";
-  }
-}
-
-inline FontVariant fontVariantFromDynamic(const folly::dynamic &value) {
-  assert(value.isArray());
-  FontVariant fontVariant = FontVariant::Default;
-  for (auto &&item : value) {
-    auto string = item.asString();
-    if (string == "small-caps") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::SmallCaps); continue; }
-    if (string == "oldstyle-nums") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::OldstyleNums); continue; }
-    if (string == "lining-nums") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::LiningNums); continue; }
-    if (string == "tabular-nums") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::TabularNums); continue; }
-    if (string == "proportional-nums") { fontVariant = (FontVariant)((int)fontVariant | (int)FontVariant::ProportionalNums); continue; }
-  }
-  return fontVariant;
-}
-
-inline std::string stringFromFontVariant(const FontVariant &fontVariant) {
-  std::string result;
-  std::string separator = ", ";
-  if ((int)fontVariant & (int)FontVariant::SmallCaps) { result += "small-caps" + separator; }
-  if ((int)fontVariant & (int)FontVariant::OldstyleNums) { result += "oldstyle-nums" + separator; }
-  if ((int)fontVariant & (int)FontVariant::LiningNums) { result += "lining-nums" + separator; }
-  if ((int)fontVariant & (int)FontVariant::TabularNums) { result += "tabular-nums" + separator; }
-  if ((int)fontVariant & (int)FontVariant::ProportionalNums) { result += "proportional-nums" + separator; }
-
-  if (!result.empty()) {
-    result.erase(result.length() - separator.length());
-  }
-
-  return result;
-}
-
-inline TextAlignment textAlignmentFromDynamic(const folly::dynamic &value) {
-  auto string = value.asString();
-  if (string == "natural") { return TextAlignment::Natural; }
-  if (string == "left") { return TextAlignment::Left; }
-  if (string == "center") { return TextAlignment::Center; }
-  if (string == "right") { return TextAlignment::Right; }
-  if (string == "justified") { return TextAlignment::Justified; }
-  abort();
-}
-
-inline std::string stringFromTextAlignment(const TextAlignment &textAlignment) {
-  switch (textAlignment) {
-    case TextAlignment::Natural: return "natural";
-    case TextAlignment::Left: return "left";
-    case TextAlignment::Center: return "center";
-    case TextAlignment::Right: return "right";
-    case TextAlignment::Justified: return "justified";
-  }
-}
-
-inline WritingDirection writingDirectionFromDynamic(const folly::dynamic &value) {
-  auto string = value.asString();
-  if (string == "natural") { return WritingDirection::Natural; }
-  if (string == "ltr") { return WritingDirection::LeftToRight; }
-  if (string == "rtl") { return WritingDirection::RightToLeft; }
-  abort();
-}
-
-inline std::string stringFromWritingDirection(const WritingDirection &writingDirection) {
-  switch (writingDirection) {
-    case WritingDirection::Natural: return "natural";
-    case WritingDirection::LeftToRight: return "ltr";
-    case WritingDirection::RightToLeft: return "rtl";
-  }
-}
-
-inline TextDecorationLineType textDecorationLineTypeFromDynamic(const folly::dynamic &value) {
-  auto string = value.asString();
-  if (string == "none") { return TextDecorationLineType::None; }
-  if (string == "underline") { return TextDecorationLineType::Underline; }
-  if (string == "strikethrough") { return TextDecorationLineType::Strikethrough; }
-  if (string == "underline-strikethrough") { return TextDecorationLineType::UnderlineStrikethrough; }
-  abort();
-}
-
-inline std::string stringFromTextDecorationLineType(const TextDecorationLineType &textDecorationLineType) {
-  switch (textDecorationLineType) {
-    case TextDecorationLineType::None: return "none";
-    case TextDecorationLineType::Underline: return "underline";
-    case TextDecorationLineType::Strikethrough: return "strikethrough";
-    case TextDecorationLineType::UnderlineStrikethrough: return "underline-strikethrough";
-  }
-}
-
-inline TextDecorationLineStyle textDecorationLineStyleFromDynamic(const folly::dynamic &value) {
-  auto string = value.asString();
-  if (string == "single") { return TextDecorationLineStyle::Single; }
-  if (string == "thick") { return TextDecorationLineStyle::Thick; }
-  if (string == "double") { return TextDecorationLineStyle::Double; }
-  abort();
-}
-
-inline std::string stringFromTextDecorationLineStyle(const TextDecorationLineStyle &textDecorationLineStyle) {
-  switch (textDecorationLineStyle) {
-    case TextDecorationLineStyle::Single: return "single";
-    case TextDecorationLineStyle::Thick: return "thick";
-    case TextDecorationLineStyle::Double: return "double";
-  }
-}
-
-inline TextDecorationLinePattern textDecorationLinePatternFromDynamic(const folly::dynamic &value) {
-  auto string = value.asString();
-  if (string == "solid") { return TextDecorationLinePattern::Solid; }
-  if (string == "dot") { return TextDecorationLinePattern::Dot; }
-  if (string == "dash") { return TextDecorationLinePattern::Dash; }
-  if (string == "dash-dot") { return TextDecorationLinePattern::DashDot; }
-  if (string == "dash-dot-dot") { return TextDecorationLinePattern::DashDotDot; }
-  abort();
-}
-
-inline std::string stringFromTextDecorationLinePattern(const TextDecorationLinePattern &textDecorationLinePattern) {
-  switch (textDecorationLinePattern) {
-    case TextDecorationLinePattern::Solid: return "solid";
-    case TextDecorationLinePattern::Dot: return "dot";
-    case TextDecorationLinePattern::Dash: return "dash";
-    case TextDecorationLinePattern::DashDot: return "dash-dot";
-    case TextDecorationLinePattern::DashDotDot: return "dash-dot-dot";
-  }
-}
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
index 736474355879..d900d0ab2f5e 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
+++ b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
@@ -7,11 +7,10 @@
 
 #include "BaseTextProps.h"
 
-#include <fabric/attributedstring/textValuesConversions.h>
+#include <fabric/attributedstring/conversions.h>
 #include <fabric/core/propsConversions.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
 #include <fabric/graphics/graphicValuesConversions.h>
-#include <fabric/text/propsConversions.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
index c96098981d64..30fc681fd041 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
@@ -8,7 +8,6 @@
 #include "ParagraphLocalData.h"
 
 #include <fabric/debug/debugStringConvertibleUtils.h>
-#include <fabric/attributedstring/debugStringConvertibleUtils.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
index 628ee1eff744..a6ea79c6e71e 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
@@ -7,10 +7,9 @@
 
 #include "ParagraphProps.h"
 
-#include <fabric/attributedstring/textValuesConversions.h>
+#include <fabric/attributedstring/conversions.h>
 #include <fabric/core/propsConversions.h>
 #include <fabric/debug/debugStringConvertibleUtils.h>
-#include <fabric/text/propsConversions.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/propsConversions.h b/ReactCommon/fabric/text/propsConversions.h
deleted file mode 100644
index b8362947f43f..000000000000
--- a/ReactCommon/fabric/text/propsConversions.h
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <fabric/attributedstring/TextPrimitives.h>
-#include <fabric/attributedstring/textValuesConversions.h>
-#include <fabric/core/propsConversions.h>
-#include <folly/dynamic.h>
-
-namespace facebook {
-namespace react {
-
-CONVERT_RAW_PROP_TEMPLATE(EllipsizeMode, ellipsizeModeFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(FontWeight, fontWeightFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(FontStyle, fontStyleFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(FontVariant, fontVariantFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(WritingDirection, writingDirectionFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(TextAlignment, textAlignmentFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(TextDecorationLineType, textDecorationLineTypeFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(TextDecorationLineStyle, textDecorationLineStyleFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(TextDecorationLinePattern, textDecorationLinePatternFromDynamic)
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/text/text/TextProps.cpp b/ReactCommon/fabric/text/text/TextProps.cpp
index 5e8a3e1c669e..443fe48c0451 100644
--- a/ReactCommon/fabric/text/text/TextProps.cpp
+++ b/ReactCommon/fabric/text/text/TextProps.cpp
@@ -7,12 +7,6 @@
 
 #include "TextProps.h"
 
-#include <fabric/attributedstring/textValuesConversions.h>
-#include <fabric/core/propsConversions.h>
-#include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/graphics/graphicValuesConversions.h>
-#include <fabric/text/propsConversions.h>
-
 namespace facebook {
 namespace react {
 

From 9f85873c9fa010ddb903ef5e15f47b8e1685b1db Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:48 -0700
Subject: [PATCH 0572/1109] Fabric: New props treatment in `graphics` module

Summary:
Same as previous one.
Adopting template-generated `convertRawProp` and `debugStringConvertibleItem` functions in `graphics` module.
Note, to do so we have to change signatures of some conversions functions to make them more overloading-friendly.

Reviewed By: fkgozali

Differential Revision: D7958252

fbshipit-source-id: 0f33a2e6aad60befacee31486acdb9b6114d3e07
---
 .../attributedstring/TextAttributes.cpp       |  3 +-
 .../core/layout/LayoutableShadowNode.cpp      |  8 +--
 .../fabric/core/shadownode/propsConversions.h | 11 +---
 ...hicValuesConversions.cpp => conversions.h} | 64 +++++++++++--------
 .../graphics/debugStringConvertibleUtils.h    | 22 -------
 .../graphics/graphicValuesConversions.h       | 34 ----------
 .../fabric/graphics/tests/GraphicsTest.cpp    |  3 -
 .../fabric/text/basetext/BaseTextProps.cpp    |  2 +-
 .../fabric/text/rawtext/RawTextProps.cpp      |  1 -
 ReactCommon/fabric/view/ViewProps.cpp         |  3 +-
 10 files changed, 44 insertions(+), 107 deletions(-)
 rename ReactCommon/fabric/graphics/{graphicValuesConversions.cpp => conversions.h} (62%)
 delete mode 100644 ReactCommon/fabric/graphics/debugStringConvertibleUtils.h
 delete mode 100644 ReactCommon/fabric/graphics/graphicValuesConversions.h

diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.cpp b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
index fe6967749047..66e1f02b9021 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
@@ -8,9 +8,8 @@
 #include "TextAttributes.h"
 
 #include <fabric/attributedstring/conversions.h>
+#include <fabric/graphics/conversions.h>
 #include <fabric/core/debugStringConvertibleUtils.h>
-#include <fabric/graphics/debugStringConvertibleUtils.h>
-#include <fabric/graphics/graphicValuesConversions.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index a1fd9623fb86..5db399f373f7 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -11,7 +11,7 @@
 #include <fabric/core/LayoutContext.h>
 #include <fabric/core/LayoutMetrics.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/graphics/graphicValuesConversions.h>
+#include <fabric/graphics/conversions.h>
 
 namespace facebook {
 namespace react {
@@ -110,14 +110,14 @@ SharedDebugStringConvertibleList LayoutableShadowNode::getDebugProps() const {
   LayoutMetrics layoutMetrics = getLayoutMetrics();
   LayoutMetrics defaultLayoutMetrics = LayoutMetrics();
 
-  list.push_back(std::make_shared<DebugStringConvertibleItem>("frame", stringFromRect(layoutMetrics.frame)));
+  list.push_back(std::make_shared<DebugStringConvertibleItem>("frame", toString(layoutMetrics.frame)));
 
   if (layoutMetrics.borderWidth != defaultLayoutMetrics.borderWidth) {
-    list.push_back(std::make_shared<DebugStringConvertibleItem>("borderWidth", stringFromEdgeInsets(layoutMetrics.borderWidth)));
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("borderWidth", toString(layoutMetrics.borderWidth)));
   }
 
   if (layoutMetrics.contentInsets != defaultLayoutMetrics.contentInsets) {
-    list.push_back(std::make_shared<DebugStringConvertibleItem>("contentInsets", stringFromEdgeInsets(layoutMetrics.contentInsets)));
+    list.push_back(std::make_shared<DebugStringConvertibleItem>("contentInsets", toString(layoutMetrics.contentInsets)));
   }
 
   if (layoutMetrics.displayType == DisplayType::None) {
diff --git a/ReactCommon/fabric/core/shadownode/propsConversions.h b/ReactCommon/fabric/core/shadownode/propsConversions.h
index b03bdc1387b7..240f70ce1267 100644
--- a/ReactCommon/fabric/core/shadownode/propsConversions.h
+++ b/ReactCommon/fabric/core/shadownode/propsConversions.h
@@ -10,7 +10,7 @@
 #include <folly/dynamic.h>
 #include <fabric/graphics/Color.h>
 #include <fabric/graphics/Geometry.h>
-#include <fabric/graphics/graphicValuesConversions.h>
+#include <fabric/graphics/conversions.h>
 
 namespace facebook {
 namespace react {
@@ -44,17 +44,8 @@ inline static folly::Optional<type> convertRawProp(const RawProps &rawProps, con
   } \
 }
 
-CONVERT_RAW_PROP_TEMPLATE(bool, boolFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(int, intFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(Float, floatFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(std::string, stringFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(SharedColor, colorFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(Point, pointFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(Size, sizeFromDynamic)
-
 inline void fromDynamic(const folly::dynamic &value, bool &result) { result = value.getBool(); }
 inline void fromDynamic(const folly::dynamic &value, int &result) { result = value.getInt(); }
-inline void fromDynamic(const folly::dynamic &value, Float &result) { result = value.getDouble(); }
 inline void fromDynamic(const folly::dynamic &value, std::string &result) { result = value.getString(); }
 
 template <typename T>
diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp b/ReactCommon/fabric/graphics/conversions.h
similarity index 62%
rename from ReactCommon/fabric/graphics/graphicValuesConversions.cpp
rename to ReactCommon/fabric/graphics/conversions.h
index 874c70b69045..7d0cd5b1cef5 100644
--- a/ReactCommon/fabric/graphics/graphicValuesConversions.cpp
+++ b/ReactCommon/fabric/graphics/conversions.h
@@ -5,14 +5,18 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#include "graphicValuesConversions.h"
+#pragma once
 
-#include <folly/Conv.h>
+#include <folly/dynamic.h>
+#include <fabric/graphics/Color.h>
+#include <fabric/graphics/Geometry.h>
 
 namespace facebook {
 namespace react {
 
-SharedColor colorFromDynamic(const folly::dynamic &value) {
+#pragma mark - Color
+
+inline void fromDynamic(const folly::dynamic &value, SharedColor &result) {
   float red;
   float green;
   float blue;
@@ -36,10 +40,10 @@ SharedColor colorFromDynamic(const folly::dynamic &value) {
     abort();
   }
 
-  return colorFromComponents({red, green, blue, alpha});
+  result = colorFromComponents({red, green, blue, alpha});
 }
 
-std::string colorNameFromColor(const SharedColor &value) {
+inline std::string toString(const SharedColor &value) {
   ColorComponents components = colorComponentsFromColor(value);
   const float ratio = 256;
   return "rgba(" +
@@ -49,19 +53,41 @@ std::string colorNameFromColor(const SharedColor &value) {
     folly::to<std::string>(round(components.alpha * ratio)) + ")";
 }
 
-std::string stringFromPoint(const Point &point) {
+#pragma mark - Geometry
+
+inline void fromDynamic(const folly::dynamic &value, Float &result) {
+  result = value.asDouble();
+}
+
+inline void fromDynamic(const folly::dynamic &value, Point &result) {
+  if (value.isArray()) {
+    result = Point {(Float)value[0].asDouble(), (Float)value[1].asDouble()};
+    return;
+  }
+  abort();
+}
+
+inline void fromDynamic(const folly::dynamic &value, Size &result) {
+  if (value.isArray()) {
+    result = Size {(Float)value[0].asDouble(), (Float)value[1].asDouble()};
+    return;
+  }
+  abort();
+}
+
+inline std::string toString(const Point &point) {
   return "{" + folly::to<std::string>(point.x) + ", " + folly::to<std::string>(point.y) + "}";
 }
 
-std::string stringFromSize(const Size &size) {
+inline std::string toString(const Size &size) {
   return "{" + folly::to<std::string>(size.width) + ", " + folly::to<std::string>(size.height) + "}";
 }
 
-std::string stringFromRect(const Rect &rect) {
-  return "{" + stringFromPoint(rect.origin) + ", " + stringFromSize(rect.size) + "}";
+inline std::string toString(const Rect &rect) {
+  return "{" + toString(rect.origin) + ", " + toString(rect.size) + "}";
 }
 
-std::string stringFromEdgeInsets(const EdgeInsets &edgeInsets) {
+inline std::string toString(const EdgeInsets &edgeInsets) {
   return "{" +
     folly::to<std::string>(edgeInsets.left) + ", " +
     folly::to<std::string>(edgeInsets.top) + ", " +
@@ -69,23 +95,5 @@ std::string stringFromEdgeInsets(const EdgeInsets &edgeInsets) {
     folly::to<std::string>(edgeInsets.bottom) + "}";
 }
 
-Float floatFromDynamic(const folly::dynamic &value) {
-  return value.asDouble();
-}
-
-Point pointFromDynamic(const folly::dynamic &value) {
-  if (value.isArray()) {
-    return Point {(Float)value[0].asDouble(), (Float)value[1].asDouble()};
-  }
-  abort();
-}
-
-Size sizeFromDynamic(const folly::dynamic &value) {
-  if (value.isArray()) {
-    return Size {(Float)value[0].asDouble(), (Float)value[1].asDouble()};
-  }
-  abort();
-}
-
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/graphics/debugStringConvertibleUtils.h b/ReactCommon/fabric/graphics/debugStringConvertibleUtils.h
deleted file mode 100644
index d67dd14cce13..000000000000
--- a/ReactCommon/fabric/graphics/debugStringConvertibleUtils.h
+++ /dev/null
@@ -1,22 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <fabric/debug/debugStringConvertibleUtils.h>
-#include <fabric/graphics/graphicValuesConversions.h>
-
-namespace facebook {
-namespace react {
-
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(Point, stringFromPoint)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(Size, stringFromSize)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(Rect, stringFromRect)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(SharedColor, colorNameFromColor)
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/graphicValuesConversions.h b/ReactCommon/fabric/graphics/graphicValuesConversions.h
deleted file mode 100644
index 7d49cdf97058..000000000000
--- a/ReactCommon/fabric/graphics/graphicValuesConversions.h
+++ /dev/null
@@ -1,34 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <folly/dynamic.h>
-#include <fabric/graphics/Color.h>
-#include <fabric/graphics/Geometry.h>
-
-namespace facebook {
-namespace react {
-
-#pragma mark - Color
-
-SharedColor colorFromDynamic(const folly::dynamic &value);
-std::string colorNameFromColor(const SharedColor &value);
-
-#pragma mark - Geometry
-
-std::string stringFromPoint(const Point &point);
-std::string stringFromSize(const Size &size);
-std::string stringFromRect(const Rect &rect);
-std::string stringFromEdgeInsets(const EdgeInsets &edgeInsets);
-
-Float floatFromDynamic(const folly::dynamic &value);
-Point pointFromDynamic(const folly::dynamic &value);
-Size sizeFromDynamic(const folly::dynamic &value);
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/tests/GraphicsTest.cpp b/ReactCommon/fabric/graphics/tests/GraphicsTest.cpp
index 3b88ac8a423d..4684d4c50079 100644
--- a/ReactCommon/fabric/graphics/tests/GraphicsTest.cpp
+++ b/ReactCommon/fabric/graphics/tests/GraphicsTest.cpp
@@ -7,11 +7,8 @@
 
 #include <memory>
 
-#include <fabric/graphics/graphicValuesConversions.h>
 #include <gtest/gtest.h>
 
-using namespace facebook::react;
-
 TEST(GraphicsTest, testSomething) {
   // TODO
 }
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
index d900d0ab2f5e..2b3a1e9c79b1 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
+++ b/ReactCommon/fabric/text/basetext/BaseTextProps.cpp
@@ -10,7 +10,7 @@
 #include <fabric/attributedstring/conversions.h>
 #include <fabric/core/propsConversions.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/graphics/graphicValuesConversions.h>
+#include <fabric/graphics/conversions.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/rawtext/RawTextProps.cpp b/ReactCommon/fabric/text/rawtext/RawTextProps.cpp
index 93f64c86f349..f3945701befc 100644
--- a/ReactCommon/fabric/text/rawtext/RawTextProps.cpp
+++ b/ReactCommon/fabric/text/rawtext/RawTextProps.cpp
@@ -8,7 +8,6 @@
 #include "RawTextProps.h"
 
 #include <fabric/core/propsConversions.h>
-#include <fabric/debug/DebugStringConvertibleItem.h>
 #include <fabric/debug/debugStringConvertibleUtils.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index ecd11927238d..0d0f3efdef41 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -9,8 +9,7 @@
 
 #include <fabric/core/propsConversions.h>
 #include <fabric/debug/debugStringConvertibleUtils.h>
-#include <fabric/graphics/debugStringConvertibleUtils.h>
-#include <fabric/graphics/graphicValuesConversions.h>
+#include <fabric/graphics/conversions.h>
 
 namespace facebook {
 namespace react {

From c19649cc168e1519538c6cbef4437357b67044b7 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:51 -0700
Subject: [PATCH 0573/1109] Fabric: New props treatment in `view` module

Summary:
Same as previous one.
Adopting template-generated `convertRawProp` and `debugStringConvertibleItem` functions in `view` module.
Note, to do so we have to change signatures of some conversions functions to make them more overloading-friendly.

Reviewed By: fkgozali

Differential Revision: D7958242

fbshipit-source-id: 10199d1fbb43329de93604aa383c884f5cc64dc5
---
 ReactCommon/fabric/view/ViewProps.cpp         |  10 +-
 ...ogaValuesConversions.cpp => conversions.h} | 206 +++++++++---------
 .../fabric/view/debugStringConvertibleUtils.h |  48 ----
 ReactCommon/fabric/view/propsConversions.h    |  13 +-
 ReactCommon/fabric/view/root/RootProps.cpp    |   2 +-
 .../view/yoga/YogaLayoutableShadowNode.cpp    |   2 +-
 .../fabric/view/yoga/YogaStylableProps.cpp    |   6 +-
 .../fabric/view/yoga/yogaValuesConversions.h  |  59 -----
 8 files changed, 118 insertions(+), 228 deletions(-)
 rename ReactCommon/fabric/view/{yoga/yogaValuesConversions.cpp => conversions.h} (50%)
 delete mode 100644 ReactCommon/fabric/view/debugStringConvertibleUtils.h
 delete mode 100644 ReactCommon/fabric/view/yoga/yogaValuesConversions.h

diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index 0d0f3efdef41..5f667312c7e9 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -28,14 +28,16 @@ ViewProps::ViewProps(const ViewProps &sourceProps, const RawProps &rawProps):
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList ViewProps::getDebugProps() const {
+  auto &&defaultViewProps = ViewProps();
+
   return
     AccessibilityProps::getDebugProps() +
     YogaStylableProps::getDebugProps() +
     SharedDebugStringConvertibleList {
-      debugStringConvertibleItem("zIndex", zIndex),
-      debugStringConvertibleItem("opacity", opacity),
-      debugStringConvertibleItem("foregroundColor", foregroundColor),
-      debugStringConvertibleItem("backgroundColor", backgroundColor),
+      debugStringConvertibleItem("zIndex", zIndex, defaultViewProps.zIndex),
+      debugStringConvertibleItem("opacity", opacity, defaultViewProps.opacity),
+      debugStringConvertibleItem("foregroundColor", foregroundColor, defaultViewProps.foregroundColor),
+      debugStringConvertibleItem("backgroundColor", backgroundColor, defaultViewProps.backgroundColor),
     };
 }
 
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp b/ReactCommon/fabric/view/conversions.h
similarity index 50%
rename from ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
rename to ReactCommon/fabric/view/conversions.h
index d53f78b2a628..4f129c2a928d 100644
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.cpp
+++ b/ReactCommon/fabric/view/conversions.h
@@ -5,16 +5,34 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#include "yogaValuesConversions.h"
+#pragma once
 
+#include <fabric/core/LayoutMetrics.h>
+#include <fabric/graphics/Geometry.h>
+#include <folly/dynamic.h>
 #include <folly/Conv.h>
+#include <yoga/Yoga.h>
+#include <yoga/YGNode.h>
+
+// Yoga does not have this as part of the library, so we have to implement it
+// here ouside of `facebook::react::` namespace.
+inline bool operator==(const YGValue &lhs, const YGValue &rhs) {
+  if (
+    (lhs.unit == YGUnitUndefined && rhs.unit == YGUnitUndefined) ||
+    (lhs.unit == YGUnitAuto && rhs.unit == YGUnitAuto)
+  ) {
+    return true;
+  }
 
-#include <fabric/core/LayoutMetrics.h>
+  return
+    lhs.unit == rhs.unit &&
+    ((isnan(lhs.value) && isnan(rhs.value)) || (lhs.value == rhs.value));
+}
 
 namespace facebook {
 namespace react {
 
-Float fabricFloatFromYogaFloat(float value) {
+inline Float fabricFloatFromYogaFloat(float value) {
   if (value == YGUndefined) {
     return kFloatUndefined;
   }
@@ -22,7 +40,7 @@ Float fabricFloatFromYogaFloat(float value) {
   return (Float)value;
 }
 
-float yogaFloatFromFabricFloat(Float value) {
+inline float yogaFloatFromFabricFloat(Float value) {
   if (value == kFloatUndefined) {
     return YGUndefined;
   }
@@ -30,7 +48,7 @@ float yogaFloatFromFabricFloat(Float value) {
   return (float)value;
 }
 
-Float fabricFloatFromYogaOptionalFloat(YGFloatOptional value) {
+inline Float fabricFloatFromYogaOptionalFloat(YGFloatOptional value) {
   if (value.isUndefined()) {
     return kFloatUndefined;
   }
@@ -38,7 +56,7 @@ Float fabricFloatFromYogaOptionalFloat(YGFloatOptional value) {
   return fabricFloatFromYogaFloat(value.getValue());
 }
 
-YGFloatOptional yogaOptionalFloatFromFabricFloat(Float value) {
+inline YGFloatOptional yogaOptionalFloatFromFabricFloat(Float value) {
   if (value == kFloatUndefined) {
     return YGFloatOptional();
   }
@@ -46,7 +64,7 @@ YGFloatOptional yogaOptionalFloatFromFabricFloat(Float value) {
   return YGFloatOptional(yogaFloatFromFabricFloat(value));
 }
 
-YGValue yogaStyleValueFromFloat(const Float &value) {
+inline YGValue yogaStyleValueFromFloat(const Float &value) {
   if (isnan(value) || value == kFloatUndefined) {
     return YGValueUndefined;
   }
@@ -54,7 +72,7 @@ YGValue yogaStyleValueFromFloat(const Float &value) {
   return {(float)value, YGUnitPoint};
 }
 
-LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode) {
+inline LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode) {
   LayoutMetrics layoutMetrics;
 
   YGLayout layout = yogaNode.getLayout();
@@ -93,142 +111,130 @@ LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode) {
   return layoutMetrics;
 }
 
-YGDirection yogaStyleDirectionFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGDirection &result) {
   assert(value.isString());
   auto stringValue = value.asString();
-
-  if (stringValue == "inherit") { return YGDirectionInherit; }
-  if (stringValue == "ltr") { return YGDirectionLTR; }
-  if (stringValue == "rtl") { return YGDirectionRTL; }
-
+  if (stringValue == "inherit") { result = YGDirectionInherit; return; }
+  if (stringValue == "ltr") { result = YGDirectionLTR; return; }
+  if (stringValue == "rtl") { result = YGDirectionRTL; return; }
   abort();
 }
 
-YGFlexDirection yogaStyleFlexDirectionFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGFlexDirection &result) {
   assert(value.isString());
   auto stringValue = value.asString();
-
-  if (stringValue == "column") { return YGFlexDirectionColumn; }
-  if (stringValue == "column-reverse") { return YGFlexDirectionColumnReverse; }
-  if (stringValue == "row") { return YGFlexDirectionRow; }
-  if (stringValue == "row-reverse") { return YGFlexDirectionRowReverse; }
-
+  if (stringValue == "column") { result = YGFlexDirectionColumn; return; }
+  if (stringValue == "column-reverse") { result = YGFlexDirectionColumnReverse; return; }
+  if (stringValue == "row") { result = YGFlexDirectionRow; return; }
+  if (stringValue == "row-reverse") { result = YGFlexDirectionRowReverse; return; }
   abort();
 }
 
-YGJustify yogaStyleJustifyFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGJustify &result) {
   assert(value.isString());
   auto stringValue = value.asString();
-
-  if (stringValue == "flex-start") { return YGJustifyFlexStart; }
-  if (stringValue == "center") { return YGJustifyCenter; }
-  if (stringValue == "flex-end") { return YGJustifyFlexEnd; }
-  if (stringValue == "space-between") { return YGJustifySpaceBetween; }
-  if (stringValue == "space-around") { return YGJustifySpaceAround; }
-  if (stringValue == "space-evenly") { return YGJustifySpaceEvenly; }
-
+  if (stringValue == "flex-start") { result = YGJustifyFlexStart; return; }
+  if (stringValue == "center") { result = YGJustifyCenter; return; }
+  if (stringValue == "flex-end") { result = YGJustifyFlexEnd; return; }
+  if (stringValue == "space-between") { result = YGJustifySpaceBetween; return; }
+  if (stringValue == "space-around") { result = YGJustifySpaceAround; return; }
+  if (stringValue == "space-evenly") { result = YGJustifySpaceEvenly; return; }
   abort();
 }
 
-YGAlign yogaStyleAlignFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGAlign &result) {
   assert(value.isString());
   auto stringValue = value.asString();
-
-  if (stringValue == "auto") { return YGAlignAuto; }
-  if (stringValue == "flex-start") { return YGAlignFlexStart; }
-  if (stringValue == "center") { return YGAlignCenter; }
-  if (stringValue == "flex-end") { return YGAlignFlexEnd; }
-  if (stringValue == "stretch") { return YGAlignStretch; }
-  if (stringValue == "baseline") { return YGAlignBaseline; }
-  if (stringValue == "between") { return YGAlignSpaceBetween; }
-  if (stringValue == "space-around") { return YGAlignSpaceAround; }
-
+  if (stringValue == "auto") { result = YGAlignAuto; return; }
+  if (stringValue == "flex-start") { result = YGAlignFlexStart; return; }
+  if (stringValue == "center") { result = YGAlignCenter; return; }
+  if (stringValue == "flex-end") { result = YGAlignFlexEnd; return; }
+  if (stringValue == "stretch") { result = YGAlignStretch; return; }
+  if (stringValue == "baseline") { result = YGAlignBaseline; return; }
+  if (stringValue == "between") { result = YGAlignSpaceBetween; return; }
+  if (stringValue == "space-around") { result = YGAlignSpaceAround; return; }
   abort();
 }
 
-YGPositionType yogaStylePositionTypeFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGPositionType &result) {
   assert(value.isString());
   auto stringValue = value.asString();
-
-  if (stringValue == "relative") { return YGPositionTypeRelative; }
-  if (stringValue == "absolute") { return YGPositionTypeAbsolute; }
-
+  if (stringValue == "relative") { result = YGPositionTypeRelative; return; }
+  if (stringValue == "absolute") { result = YGPositionTypeAbsolute; return; }
   abort();
 }
 
-YGWrap yogaStyleWrapFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGWrap &result) {
   assert(value.isString());
   auto stringValue = value.asString();
-
-  if (stringValue == "no-wrap") { return YGWrapNoWrap; }
-  if (stringValue == "wrap") { return YGWrapWrap; }
-  if (stringValue == "wrap-reverse") { return YGWrapWrapReverse; }
-
+  if (stringValue == "no-wrap") { result = YGWrapNoWrap; return; }
+  if (stringValue == "wrap") { result = YGWrapWrap; return; }
+  if (stringValue == "wrap-reverse") { result = YGWrapWrapReverse; return; }
   abort();
 }
 
-YGOverflow yogaStyleOverflowFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGOverflow &result) {
   assert(value.isString());
   auto stringValue = value.asString();
-
-  if (stringValue == "visible") { return YGOverflowVisible; }
-  if (stringValue == "hidden") { return YGOverflowHidden; }
-  if (stringValue == "scroll") { return YGOverflowScroll; }
-
+  if (stringValue == "visible") { result = YGOverflowVisible; return; }
+  if (stringValue == "hidden") { result = YGOverflowHidden; return; }
+  if (stringValue == "scroll") { result = YGOverflowScroll; return; }
   abort();
 }
 
-YGDisplay yogaStyleDisplayFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGDisplay &result) {
   assert(value.isString());
   auto stringValue = value.asString();
-
-  if (stringValue == "flex") { return YGDisplayFlex; }
-  if (stringValue == "none") { return YGDisplayNone; }
-
+  if (stringValue == "flex") { result = YGDisplayFlex; return; }
+  if (stringValue == "none") { result = YGDisplayNone; return; }
   abort();
 }
 
-YGValue yogaStyleValueFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGValue &result) {
   if (value.isNumber()) {
-    return yogaStyleValueFromFloat(value.asDouble());
+    result = yogaStyleValueFromFloat(value.asDouble());
+    return;
   } else if (value.isString()) {
     const auto stringValue = value.asString();
     if (stringValue == "auto") {
-      return YGValueUndefined;
+      result = YGValueUndefined;
+      return;
     } else {
       if (stringValue.back() == '%') {
-        return { folly::to<float>(stringValue.substr(stringValue.length() - 1)), YGUnitPercent };
+        result = { folly::to<float>(stringValue.substr(stringValue.length() - 1)), YGUnitPercent };
+        return;
       } else {
-        return { folly::to<float>(stringValue), YGUnitPoint };
+        result = { folly::to<float>(stringValue), YGUnitPoint };
+        return;
       }
     }
   }
-
-  return YGValueUndefined;
+  result = YGValueUndefined;
 }
 
-YGFloatOptional yogaStyleOptionalFloatFromDynamic(const folly::dynamic &value) {
+inline void fromDynamic(const folly::dynamic &value, YGFloatOptional &result) {
   if (value.isNumber()) {
-    return YGFloatOptional(value.asDouble());
+    result = YGFloatOptional(value.asDouble());
+    return;
   } else if (value.isString()) {
     const auto stringValue = value.asString();
     if (stringValue == "auto") {
-      return YGFloatOptional();
+      result = YGFloatOptional();
+      return;
     }
   }
-
   abort();
 }
 
-std::string stringFromYogaDimensions(std::array<float, YGDimensionCount> dimensions) {
+inline std::string toString(const std::array<float, YGDimensionCount> &dimensions) {
   return "{" + folly::to<std::string>(dimensions[0]) + ", " + folly::to<std::string>(dimensions[1]) + "}";
 }
 
-std::string stringFromYogaPosition(std::array<float, 4> position) {
+inline std::string toString(const std::array<float, 4> &position) {
   return "{" + folly::to<std::string>(position[0]) + ", " + folly::to<std::string>(position[1]) + "}";
 }
 
-std::string stringFromYogaEdges(std::array<float, YGEdgeCount> edges) {
+inline std::string toString(const std::array<float, YGEdgeCount> &edges) {
   return "{" +
     folly::to<std::string>(edges[0]) + ", " +
     folly::to<std::string>(edges[1]) + ", " +
@@ -236,7 +242,7 @@ std::string stringFromYogaEdges(std::array<float, YGEdgeCount> edges) {
     folly::to<std::string>(edges[3]) + "}";
 }
 
-std::string stringFromYogaStyleDirection(YGDirection value) {
+inline std::string toString(const YGDirection &value) {
   switch (value) {
     case YGDirectionInherit: return "inherit";
     case YGDirectionLTR: return "ltr";
@@ -244,7 +250,7 @@ std::string stringFromYogaStyleDirection(YGDirection value) {
   }
 }
 
-std::string stringFromYogaStyleFlexDirection(YGFlexDirection value) {
+inline std::string toString(const YGFlexDirection &value) {
   switch (value) {
     case YGFlexDirectionColumn: return "column";
     case YGFlexDirectionColumnReverse: return "column-reverse";
@@ -253,7 +259,7 @@ std::string stringFromYogaStyleFlexDirection(YGFlexDirection value) {
   }
 }
 
-std::string stringFromYogaStyleJustify(YGJustify value) {
+inline std::string toString(const YGJustify &value) {
   switch (value) {
     case YGJustifyFlexStart: return "flex-start";
     case YGJustifyCenter: return "center";
@@ -264,7 +270,7 @@ std::string stringFromYogaStyleJustify(YGJustify value) {
   }
 }
 
-std::string stringFromYogaStyleAlign(YGAlign value) {
+inline std::string toString(const YGAlign &value) {
   switch (value) {
     case YGAlignAuto: return "auto";
     case YGAlignFlexStart: return "flex-start";
@@ -277,14 +283,14 @@ std::string stringFromYogaStyleAlign(YGAlign value) {
   }
 }
 
-std::string stringFromYogaStylePositionType(YGPositionType value) {
+inline std::string toString(const YGPositionType &value) {
   switch (value) {
     case YGPositionTypeRelative: return "relative";
     case YGPositionTypeAbsolute: return "absolute";
   }
 }
 
-std::string stringFromYogaStyleWrap(YGWrap value) {
+inline std::string toString(const YGWrap &value) {
   switch (value) {
     case YGWrapNoWrap: return "no-wrap";
     case YGWrapWrap: return "wrap";
@@ -292,7 +298,7 @@ std::string stringFromYogaStyleWrap(YGWrap value) {
   }
 }
 
-std::string stringFromYogaStyleOverflow(YGOverflow value) {
+inline std::string toString(const YGOverflow &value) {
   switch (value) {
     case YGOverflowVisible: return "visible";
     case YGOverflowScroll: return "scroll";
@@ -300,14 +306,14 @@ std::string stringFromYogaStyleOverflow(YGOverflow value) {
   }
 }
 
-std::string stringFromYogaStyleDisplay(YGDisplay value) {
+inline std::string toString(const YGDisplay &value) {
   switch (value) {
     case YGDisplayFlex: return "flex";
     case YGDisplayNone: return "none";
   }
 }
 
-std::string stringFromYogaStyleValue(YGValue value) {
+inline std::string toString(const YGValue &value) {
   switch (value.unit) {
     case YGUnitUndefined: return "undefined";
     case YGUnitPoint: return folly::to<std::string>(value.value);
@@ -316,7 +322,7 @@ std::string stringFromYogaStyleValue(YGValue value) {
   }
 }
 
-std::string stringFromYogaStyleOptionalFloat(YGFloatOptional value) {
+inline std::string toString(const YGFloatOptional &value) {
   if (value.isUndefined()) {
     return "undefined";
   }
@@ -324,23 +330,23 @@ std::string stringFromYogaStyleOptionalFloat(YGFloatOptional value) {
   return folly::to<std::string>(fabricFloatFromYogaFloat(value.getValue()));
 }
 
-std::string stringFromYogaStyleDimensions(std::array<YGValue, YGDimensionCount> value) {
+inline std::string toString(const std::array<YGValue, YGDimensionCount> &value) {
   return "{" +
-    stringFromYogaStyleValue(value[0]) + ", " +
-    stringFromYogaStyleValue(value[1]) + "}";
+    toString(value[0]) + ", " +
+    toString(value[1]) + "}";
 }
 
-std::string stringFromYogaStyleEdges(std::array<YGValue, YGEdgeCount> value) {
+inline std::string toString(const std::array<YGValue, YGEdgeCount> &value) {
   return "{" +
-    stringFromYogaStyleValue(value[0]) + ", " +
-    stringFromYogaStyleValue(value[1]) + ", " +
-    stringFromYogaStyleValue(value[2]) + ", " +
-    stringFromYogaStyleValue(value[3]) + ", " +
-    stringFromYogaStyleValue(value[4]) + ", " +
-    stringFromYogaStyleValue(value[5]) + ", " +
-    stringFromYogaStyleValue(value[6]) + ", " +
-    stringFromYogaStyleValue(value[7]) + ", " +
-    stringFromYogaStyleValue(value[8]) + "}";
+    toString(value[0]) + ", " +
+    toString(value[1]) + ", " +
+    toString(value[2]) + ", " +
+    toString(value[3]) + ", " +
+    toString(value[4]) + ", " +
+    toString(value[5]) + ", " +
+    toString(value[6]) + ", " +
+    toString(value[7]) + ", " +
+    toString(value[8]) + "}";
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/debugStringConvertibleUtils.h b/ReactCommon/fabric/view/debugStringConvertibleUtils.h
deleted file mode 100644
index a1a2f9422701..000000000000
--- a/ReactCommon/fabric/view/debugStringConvertibleUtils.h
+++ /dev/null
@@ -1,48 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <fabric/debug/debugStringConvertibleUtils.h>
-#include <fabric/view/yogaValuesConversions.h>
-
-// Yoga does not have this as part of the library, so we have to implement it
-// here ouside of `facebook::react::` namespace.
-inline bool operator==(const YGValue &lhs, const YGValue &rhs) {
-  if (
-    (lhs.unit == YGUnitUndefined && rhs.unit == YGUnitUndefined) ||
-    (lhs.unit == YGUnitAuto && rhs.unit == YGUnitAuto)
-  ) {
-    return true;
-  }
-
-  return
-    lhs.unit == rhs.unit &&
-    ((isnan(lhs.value) && isnan(rhs.value)) || (lhs.value == rhs.value));
-}
-
-namespace facebook {
-namespace react {
-
-using YogaDimentionsType = std::array<YGValue, YGDimensionCount>;
-using YogaEdgesType = std::array<YGValue, YGEdgeCount>;
-
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YogaDimentionsType, stringFromYogaStyleDimensions)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YogaEdgesType, stringFromYogaStyleEdges)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGDirection, stringFromYogaStyleDirection)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGFlexDirection, stringFromYogaStyleFlexDirection)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGJustify, stringFromYogaStyleJustify)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGAlign, stringFromYogaStyleAlign)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGPositionType, stringFromYogaStylePositionType)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGWrap, stringFromYogaStyleWrap)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGOverflow, stringFromYogaStyleOverflow)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGDisplay, stringFromYogaStyleDisplay)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(YGValue, stringFromYogaStyleValue)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(YGFloatOptional, stringFromYogaStyleOptionalFloat, YGFloatOptional(), IS_EQUAL)
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/view/propsConversions.h b/ReactCommon/fabric/view/propsConversions.h
index 76d19228a91d..b21ccbcae1b6 100644
--- a/ReactCommon/fabric/view/propsConversions.h
+++ b/ReactCommon/fabric/view/propsConversions.h
@@ -8,22 +8,11 @@
 #pragma once
 
 #include <fabric/core/propsConversions.h>
-#include <fabric/view/yogaValuesConversions.h>
+#include <fabric/view/conversions.h>
 
 namespace facebook {
 namespace react {
 
-CONVERT_RAW_PROP_TEMPLATE(YGDirection, yogaStyleDirectionFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGFlexDirection, yogaStyleFlexDirectionFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGJustify, yogaStyleJustifyFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGAlign, yogaStyleAlignFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGPositionType, yogaStylePositionTypeFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGWrap, yogaStyleWrapFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGOverflow, yogaStyleOverflowFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGDisplay, yogaStyleDisplayFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGValue, yogaStyleValueFromDynamic)
-CONVERT_RAW_PROP_TEMPLATE(YGFloatOptional, yogaStyleOptionalFloatFromDynamic)
-
 static std::array<YGValue, 2> convertRawProp(const RawProps &rawProps, const std::string &widthName, const std::string &heightName, const std::array<YGValue, 2> &defaultValue) {
   std::array<YGValue, 2> dimentions;
   dimentions[YGDimensionWidth] = convertRawProp(rawProps, widthName, defaultValue[YGDimensionWidth]);
diff --git a/ReactCommon/fabric/view/root/RootProps.cpp b/ReactCommon/fabric/view/root/RootProps.cpp
index 4040ed3a7e40..70aac488a035 100644
--- a/ReactCommon/fabric/view/root/RootProps.cpp
+++ b/ReactCommon/fabric/view/root/RootProps.cpp
@@ -8,7 +8,7 @@
 #include "RootProps.h"
 
 #include "YogaLayoutableShadowNode.h"
-#include "yogaValuesConversions.h"
+#include "conversions.h"
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 10d1a2aa7945..49d018ecb870 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -15,7 +15,7 @@
 #include <fabric/debug/DebugStringConvertibleItem.h>
 #include <yoga/Yoga.h>
 
-#include "yogaValuesConversions.h"
+#include "conversions.h"
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
index 4a3553c1ff81..d89686b5366e 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
@@ -7,14 +7,14 @@
 
 #include "YogaStylableProps.h"
 
+#include <fabric/view/conversions.h>
 #include <fabric/core/propsConversions.h>
-#include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/view/debugStringConvertibleUtils.h>
 #include <fabric/view/propsConversions.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
 #include <yoga/YGNode.h>
 #include <yoga/Yoga.h>
 
-#include "yogaValuesConversions.h"
+#include "conversions.h"
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/yoga/yogaValuesConversions.h b/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
deleted file mode 100644
index 376182933aa8..000000000000
--- a/ReactCommon/fabric/view/yoga/yogaValuesConversions.h
+++ /dev/null
@@ -1,59 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <folly/dynamic.h>
-#include <yoga/Yoga.h>
-#include <yoga/YGNode.h>
-
-#include <fabric/graphics/Geometry.h>
-
-namespace facebook {
-namespace react {
-
-struct LayoutMetrics;
-
-Float fabricFloatFromYogaFloat(float value);
-float yogaFloatFromFabricFloat(Float value);
-
-Float fabricFloatFromYogaOptionalFloat(YGFloatOptional value);
-YGFloatOptional yogaOptionalFloatFromFabricFloat(Float value);
-
-YGValue yogaStyleValueFromFloat(const Float &value);
-
-LayoutMetrics layoutMetricsFromYogaNode(YGNode &yogaNode);
-
-YGDirection yogaStyleDirectionFromDynamic(const folly::dynamic &value);
-YGFlexDirection yogaStyleFlexDirectionFromDynamic(const folly::dynamic &value);
-YGJustify yogaStyleJustifyFromDynamic(const folly::dynamic &value);
-YGAlign yogaStyleAlignFromDynamic(const folly::dynamic &value);
-YGPositionType yogaStylePositionTypeFromDynamic(const folly::dynamic &value);
-YGWrap yogaStyleWrapFromDynamic(const folly::dynamic &value);
-YGOverflow yogaStyleOverflowFromDynamic(const folly::dynamic &value);
-YGDisplay yogaStyleDisplayFromDynamic(const folly::dynamic &value);
-YGValue yogaStyleValueFromDynamic(const folly::dynamic &value);
-YGFloatOptional yogaStyleOptionalFloatFromDynamic(const folly::dynamic &value);
-
-std::string stringFromYogaDimensions(std::array<float, YGDimensionCount> dimensions);
-std::string stringFromYogaPosition(std::array<float, 4> position);
-std::string stringFromYogaEdges(std::array<float, YGEdgeCount> edges);
-std::string stringFromYogaStyleDirection(YGDirection direction);
-std::string stringFromYogaStyleFlexDirection(YGFlexDirection value);
-std::string stringFromYogaStyleJustify(YGJustify value);
-std::string stringFromYogaStyleAlign(YGAlign value);
-std::string stringFromYogaStylePositionType(YGPositionType value);
-std::string stringFromYogaStyleWrap(YGWrap value);
-std::string stringFromYogaStyleOverflow(YGOverflow value);
-std::string stringFromYogaStyleDisplay(YGDisplay value);
-std::string stringFromYogaStyleValue(YGValue value);
-std::string stringFromYogaStyleOptionalFloat(YGFloatOptional value);
-std::string stringFromYogaStyleDimensions(std::array<YGValue, YGDimensionCount> value);
-std::string stringFromYogaStyleEdges(std::array<YGValue, YGEdgeCount> value);
-
-} // namespace react
-} // namespace facebook

From 120dcec621d6a474594fe8fe16ff15aaa5ea127a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:54 -0700
Subject: [PATCH 0574/1109] Fabric: New props treatment in `core` module

Summary:
Same as previous one.
Adopting template-generated `convertRawProp` and `debugStringConvertibleItem` functions in `core` module.
Note, to do so we have to change signatures of some conversions functions to make them more overloading-friendly.

Reviewed By: fkgozali

Differential Revision: D7958243

fbshipit-source-id: 500ee420d9aa562ee3c5810ef625e06541eda8fb
---
 .../attributedstring/ParagraphAttributes.cpp  |  1 +
 .../attributedstring/TextAttributes.cpp       |  4 +++-
 ...ayoutValuesConversions.h => conversions.h} |  4 ++--
 .../fabric/core/debugStringConvertibleUtils.h | 20 -------------------
 .../core/{shadownode => }/propsConversions.h  |  0
 5 files changed, 6 insertions(+), 23 deletions(-)
 rename ReactCommon/fabric/core/{layout/layoutValuesConversions.h => conversions.h} (80%)
 delete mode 100644 ReactCommon/fabric/core/debugStringConvertibleUtils.h
 rename ReactCommon/fabric/core/{shadownode => }/propsConversions.h (100%)

diff --git a/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp b/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
index f3382a54d4c9..53550b6db4e0 100644
--- a/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/ParagraphAttributes.cpp
@@ -8,6 +8,7 @@
 #include "ParagraphAttributes.h"
 
 #include <fabric/attributedstring/conversions.h>
+#include <fabric/graphics/conversions.h>
 #include <fabric/debug/debugStringConvertibleUtils.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.cpp b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
index 66e1f02b9021..93e316250863 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
@@ -8,8 +8,10 @@
 #include "TextAttributes.h"
 
 #include <fabric/attributedstring/conversions.h>
+#include <fabric/core/conversions.h>
 #include <fabric/graphics/conversions.h>
-#include <fabric/core/debugStringConvertibleUtils.h>
+
+#include <fabric/debug/debugStringConvertibleUtils.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/core/layout/layoutValuesConversions.h b/ReactCommon/fabric/core/conversions.h
similarity index 80%
rename from ReactCommon/fabric/core/layout/layoutValuesConversions.h
rename to ReactCommon/fabric/core/conversions.h
index dc821a35fadc..1d058558dfca 100644
--- a/ReactCommon/fabric/core/layout/layoutValuesConversions.h
+++ b/ReactCommon/fabric/core/conversions.h
@@ -12,7 +12,7 @@
 namespace facebook {
 namespace react {
 
-inline std::string stringFromLayoutDirection(const LayoutDirection &layoutDirection) {
+inline std::string toString(const LayoutDirection &layoutDirection) {
   switch (layoutDirection) {
     case LayoutDirection::Undefined: return "undefined";
     case LayoutDirection::LeftToRight: return "ltr";
@@ -20,7 +20,7 @@ inline std::string stringFromLayoutDirection(const LayoutDirection &layoutDirect
   }
 }
 
-inline std::string stringFromDisplayType(const DisplayType &displayType) {
+inline std::string toString(const DisplayType &displayType) {
   switch (displayType) {
     case DisplayType::None: return "none";
     case DisplayType::Flex: return "flex";
diff --git a/ReactCommon/fabric/core/debugStringConvertibleUtils.h b/ReactCommon/fabric/core/debugStringConvertibleUtils.h
deleted file mode 100644
index 0dc60ea89b29..000000000000
--- a/ReactCommon/fabric/core/debugStringConvertibleUtils.h
+++ /dev/null
@@ -1,20 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <fabric/debug/debugStringConvertibleUtils.h>
-#include <fabric/core/layoutValuesConversions.h>
-
-namespace facebook {
-namespace react {
-
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(LayoutDirection, stringFromLayoutDirection)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(DisplayType, stringFromDisplayType)
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
similarity index 100%
rename from ReactCommon/fabric/core/shadownode/propsConversions.h
rename to ReactCommon/fabric/core/propsConversions.h

From 1f9676a1cb023f149fa7caebdf4135a1137256dd Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:57 -0700
Subject: [PATCH 0575/1109] Fabric: Final cleanup of define-based props
 treatment

Summary: Oh, my! No more `#define`s related to props conversions and debug-printing.

Reviewed By: fkgozali

Differential Revision: D7958250

fbshipit-source-id: 86950070c55f134aa3a575b9fd68fc90d865cf44
---
 ReactCommon/fabric/core/propsConversions.h    | 62 ++++++-------------
 .../debug/debugStringConvertibleUtils.cpp     | 25 --------
 .../debug/debugStringConvertibleUtils.h       | 42 +++++--------
 3 files changed, 33 insertions(+), 96 deletions(-)
 delete mode 100644 ReactCommon/fabric/debug/debugStringConvertibleUtils.cpp

diff --git a/ReactCommon/fabric/core/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
index 240f70ce1267..edca1fe8e0ae 100644
--- a/ReactCommon/fabric/core/propsConversions.h
+++ b/ReactCommon/fabric/core/propsConversions.h
@@ -15,35 +15,6 @@
 namespace facebook {
 namespace react {
 
-inline bool boolFromDynamic(const folly::dynamic &value) { return value.getBool(); }
-inline int intFromDynamic(const folly::dynamic &value) { return value.getInt(); }
-inline Float floatFromDynamic(const folly::dynamic &value) { return value.getDouble(); }
-inline std::string stringFromDynamic(const folly::dynamic &value) { return value.getString(); }
-
-#define CONVERT_RAW_PROP_TEMPLATE(type, converter) \
-inline static type convertRawProp(const RawProps &rawProps, const std::string &name, const type &defaultValue) { \
-  auto &&iterator = rawProps.find(name); \
-  if (iterator != rawProps.end()) { \
-    return converter(iterator->second); \
-  } else { \
-    return defaultValue; \
-  } \
-} \
-\
-inline static folly::Optional<type> convertRawProp(const RawProps &rawProps, const std::string &name, const folly::Optional<type> &defaultValue) { \
-  auto &&iterator = rawProps.find(name); \
-  if (iterator != rawProps.end()) { \
-    auto &&value = iterator->second; \
-    if (value.isNull()) { \
-      return {}; \
-    } else { \
-      return converter(value); \
-    } \
-  } else { \
-    return defaultValue; \
-  } \
-}
-
 inline void fromDynamic(const folly::dynamic &value, bool &result) { result = value.getBool(); }
 inline void fromDynamic(const folly::dynamic &value, int &result) { result = value.getInt(); }
 inline void fromDynamic(const folly::dynamic &value, std::string &result) { result = value.getString(); }
@@ -51,30 +22,33 @@ inline void fromDynamic(const folly::dynamic &value, std::string &result) { resu
 template <typename T>
 inline T convertRawProp(const RawProps &rawProps, const std::string &name, const T &defaultValue) {
   auto &&iterator = rawProps.find(name);
-  if (iterator != rawProps.end()) {
-    T result = defaultValue;
-    fromDynamic(iterator->second, result);
-    return result;
-  } else {
+  if (iterator == rawProps.end()) {
     return defaultValue;
   }
+
+  auto &&value = iterator->second;
+  T result;
+  fromDynamic(value, result);
+  return result;
 }
 
 template <typename T>
 inline static folly::Optional<T> convertRawProp(const RawProps &rawProps, const std::string &name, const folly::Optional<T> &defaultValue) {
   auto &&iterator = rawProps.find(name);
-  if (iterator != rawProps.end()) {
-    auto &&value = iterator->second;
-    if (value.isNull()) {
-      return defaultValue;
-    } else {
-      T result;
-      fromDynamic(value, result);
-      return result;
-    }
-  } else {
+  if (iterator == rawProps.end()) {
     return defaultValue;
   }
+
+  auto &&value = iterator->second;
+  T result;
+
+  // Special case for optionals: `null` always means `no value`.
+  if (value.isNull()) {
+    return {};
+  }
+
+  fromDynamic(value, result);
+  return result;
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/debug/debugStringConvertibleUtils.cpp b/ReactCommon/fabric/debug/debugStringConvertibleUtils.cpp
deleted file mode 100644
index de9817d4999f..000000000000
--- a/ReactCommon/fabric/debug/debugStringConvertibleUtils.cpp
+++ /dev/null
@@ -1,25 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#include "debugStringConvertibleUtils.h"
-
-namespace facebook {
-namespace react {
-
-SharedDebugStringConvertibleList operator+(const SharedDebugStringConvertibleList &lhs, const SharedDebugStringConvertibleList &rhs) {
-  SharedDebugStringConvertibleList result = {};
-  std::move(lhs.begin(), lhs.end(), std::back_inserter(result));
-  std::move(rhs.begin(), rhs.end(), std::back_inserter(result));
-  return result;
-}
-
-SharedDebugStringConvertible debugStringConvertibleItem(std::string name, DebugStringConvertible value, std::string defaultValue) {
-  return debugStringConvertibleItem(name, value.getDebugDescription(), defaultValue);
-}
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
index 22eca9acfa90..836945018b32 100644
--- a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
+++ b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
@@ -19,6 +19,12 @@
 namespace facebook {
 namespace react {
 
+inline std::string toString(const std::string &value) { return value; }
+inline std::string toString(const int &value) { return folly::to<std::string>(value); }
+inline std::string toString(const bool &value) { return folly::to<std::string>(value); }
+inline std::string toString(const float &value) { return folly::to<std::string>(value); }
+inline std::string toString(const double &value) { return folly::to<std::string>(value); }
+
 template <typename T>
 inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, T value, T defaultValue = {}) {
   if (value == defaultValue) {
@@ -33,38 +39,20 @@ inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name,
   if (!value.has_value()) {
     return nullptr;
   }
+
   return debugStringConvertibleItem(name, value.value_or(defaultValue), defaultValue);
 }
 
-SharedDebugStringConvertibleList operator+(const SharedDebugStringConvertibleList &lhs, const SharedDebugStringConvertibleList &rhs);
-SharedDebugStringConvertible debugStringConvertibleItem(std::string name, DebugStringConvertible value, std::string defaultValue = "");
-
-#define IS_EQUAL(a, b) ((a) == (b))
-#define IS_EQUAL_FLOAT(a, b) ((isnan(a) == isnan(b)) || ((a) == (b)))
-
-#define DEBUG_STRING_CONVERTIBLE_TEMPLATE(type, converter) \
-DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(type, converter, {}, IS_EQUAL)
-
-#define DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(type, converter, defaults, comparator) \
-inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, type value, type defaultValue = defaults) { \
-  if (comparator(value, defaultValue)) { \
-    return nullptr; \
-  } \
-  return std::make_shared<DebugStringConvertibleItem>(name, converter(value)); \
-} \
-\
-inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, folly::Optional<type> value, type defaultValue = defaults) { \
-  if (value.has_value()) { \
-    return nullptr; \
-  } \
-  return debugStringConvertibleItem(name, value.value_or(defaultValue), defaultValue); \
+inline SharedDebugStringConvertibleList operator+(const SharedDebugStringConvertibleList &lhs, const SharedDebugStringConvertibleList &rhs) {
+  SharedDebugStringConvertibleList result = {};
+  std::move(lhs.begin(), lhs.end(), std::back_inserter(result));
+  std::move(rhs.begin(), rhs.end(), std::back_inserter(result));
+  return result;
 }
 
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(std::string, )
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(int, folly::to<std::string>)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE(bool, folly::to<std::string>)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(float, folly::to<std::string>, std::numeric_limits<float>::quiet_NaN(), IS_EQUAL_FLOAT)
-DEBUG_STRING_CONVERTIBLE_TEMPLATE_EX(double, folly::to<std::string>, std::numeric_limits<float>::quiet_NaN(), IS_EQUAL_FLOAT)
+inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, DebugStringConvertible value, std::string defaultValue) {
+  return debugStringConvertibleItem(name, value.getDebugDescription(), defaultValue);
+}
 
 } // namespace react
 } // namespace facebook

From 858f7f833100f0601905f274ec5034c663414a42 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 14 May 2018 15:43:59 -0700
Subject: [PATCH 0576/1109] Fabric: Improved printing of Yoga's `Edges` data
 structure

Summary:
Yoga represents concepts like `margin`, `padding` and `position` as `edges` (aka std::array<YGValue, YGEdgeCount>).
This diff improves conversion of this data structure to string (primarily for debugging purposes).

Reviewed By: fkgozali

Differential Revision: D7958241

fbshipit-source-id: 6931c7b5d2395c28821c8daef62f609b13f112c6
---
 ReactCommon/fabric/view/conversions.h | 29 ++++++++++++++++++---------
 1 file changed, 19 insertions(+), 10 deletions(-)

diff --git a/ReactCommon/fabric/view/conversions.h b/ReactCommon/fabric/view/conversions.h
index 4f129c2a928d..cec142a7b949 100644
--- a/ReactCommon/fabric/view/conversions.h
+++ b/ReactCommon/fabric/view/conversions.h
@@ -337,16 +337,25 @@ inline std::string toString(const std::array<YGValue, YGDimensionCount> &value)
 }
 
 inline std::string toString(const std::array<YGValue, YGEdgeCount> &value) {
-  return "{" +
-    toString(value[0]) + ", " +
-    toString(value[1]) + ", " +
-    toString(value[2]) + ", " +
-    toString(value[3]) + ", " +
-    toString(value[4]) + ", " +
-    toString(value[5]) + ", " +
-    toString(value[6]) + ", " +
-    toString(value[7]) + ", " +
-    toString(value[8]) + "}";
+  static std::array<std::string, YGEdgeCount> names = {
+    {"left", "top", "right", "bottom", "start", "end", "horizontal", "vertical", "all"}
+  };
+
+  std::string result;
+  std::string separator = ", ";
+
+  for (int i = 0; i < YGEdgeCount; i++) {
+    if (value[i].unit == YGUnitUndefined) {
+      continue;
+    }
+    result += names[i] + ": " + toString(value[i]) + separator;
+  }
+
+  if (!result.empty()) {
+    result.erase(result.length() - separator.length());
+  }
+
+  return "{" + result + "}";
 }
 
 } // namespace react

From c017dcb0f2903b49b2f21cc150226aeb7f5026ee Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 14 May 2018 17:36:34 -0700
Subject: [PATCH 0577/1109] RN: Switch KeyboardAvoidingView to Class Syntax

Summary:
Refactors `KeyboardAvoidingView` by using class syntax and fixing all Flow errors.

Note that there's still a bunch of sketchy stuff going on in this component with mutated instance variables (that are used in `render`!) and unsafe lifecycle methods. But at least now it's a little bit less painful on the eyes.

Reviewed By: TheSavior

Differential Revision: D7987443

fbshipit-source-id: f5c27a9dd383c430d9a5a9dc0b6e10e2c4fe8dd9
---
 Libraries/Components/Keyboard/Keyboard.js     |  23 +-
 .../Keyboard/KeyboardAvoidingView.js          | 199 ++++++++----------
 2 files changed, 100 insertions(+), 122 deletions(-)

diff --git a/Libraries/Components/Keyboard/Keyboard.js b/Libraries/Components/Keyboard/Keyboard.js
index da76db76eee3..feeb4a4ec2ce 100644
--- a/Libraries/Components/Keyboard/Keyboard.js
+++ b/Libraries/Components/Keyboard/Keyboard.js
@@ -25,16 +25,19 @@ type KeyboardEventName =
   | 'keyboardWillChangeFrame'
   | 'keyboardDidChangeFrame';
 
-export type KeyboardEvent = {|
-  +duration?: number,
-  +easing?: string,
-  +endCoordinates: {|
-    +width: number,
-    +height: number,
-    +screenX: number,
-    +screenY: number,
-  |},
-|};
+type ScreenRect = $ReadOnly<{|
+  screenX: number,
+  screenY: number,
+  width: number,
+  height: number,
+|}>;
+
+export type KeyboardEvent = $ReadOnly<{|
+  duration?: number,
+  easing?: string,
+  endCoordinates: ScreenRect,
+  startCoordinates?: ScreenRect,
+|}>;
 
 type KeyboardEventListener = (e: KeyboardEvent) => void;
 
diff --git a/Libraries/Components/Keyboard/KeyboardAvoidingView.js b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
index 790c5a3acf8f..104fabd0f53a 100644
--- a/Libraries/Components/Keyboard/KeyboardAvoidingView.js
+++ b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
@@ -10,97 +10,69 @@
 
 'use strict';
 
-const createReactClass = require('create-react-class');
 const Keyboard = require('Keyboard');
 const LayoutAnimation = require('LayoutAnimation');
 const Platform = require('Platform');
-const PropTypes = require('prop-types');
 const React = require('React');
-/* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an error
- * found when Flow v0.54 was deployed. To see the error delete this comment and
- * run Flow. */
-const TimerMixin = require('react-timer-mixin');
+const StyleSheet = require('StyleSheet');
 const View = require('View');
-const ViewPropTypes = require('ViewPropTypes');
 
 import type EmitterSubscription from 'EmitterSubscription';
 import type {ViewStyleProp} from 'StyleSheet';
 import type {ViewProps, ViewLayout, ViewLayoutEvent} from 'ViewPropTypes';
-
-type ScreenRect = {
-  screenX: number,
-  screenY: number,
-  width: number,
-  height: number,
-};
-type KeyboardChangeEvent = {
-  startCoordinates?: ScreenRect,
-  endCoordinates: ScreenRect,
-  duration?: number,
-  easing?: string,
-};
+import type {KeyboardEvent} from 'Keyboard';
 
 type Props = $ReadOnly<{|
   ...ViewProps,
+
+  /**
+   * Specify how to react to the presence of the keyboard.
+   */
   behavior?: ?('height' | 'position' | 'padding'),
+
+  /**
+   * Style of the content container when `behavior` is 'position'.
+   */
   contentContainerStyle?: ?ViewStyleProp,
-  enabled?: ?boolean,
-  keyboardVerticalOffset?: ?number,
+
+  /**
+   * Controls whether this `KeyboardAvoidingView` instance should take effect.
+   * This is useful when more than one is on the screen. Defaults to true.
+   */
+  enabled: ?boolean,
+
+  /**
+   * Distance between the top of the user screen and the React Native view. This
+   * may be non-zero in some cases. Defaults to 0.
+   */
+  keyboardVerticalOffset: number,
 |}>;
 
+type State = {|
+  bottom: number,
+|};
+
 const viewRef = 'VIEW';
 
 /**
- * This is a component to solve the common problem of views that need to move out of the way of the virtual keyboard.
- * It can automatically adjust either its height, position or bottom padding based on the position of the keyboard.
+ * View that moves out of the way when the keyboard appears by automatically
+ * adjusting its height, position, or bottom padding.
  */
-const KeyboardAvoidingView = ((createReactClass({
-  displayName: 'KeyboardAvoidingView',
-  mixins: [TimerMixin],
-
-  propTypes: {
-    ...ViewPropTypes,
-    /**
-     * Specify how the `KeyboardAvoidingView` will react to the presence of
-     * the keyboard. It can adjust the height, position or bottom padding of the view
-     */
-    behavior: PropTypes.oneOf(['height', 'position', 'padding']),
-
-    /**
-     * The style of the content container(View) when behavior is 'position'.
-     */
-    contentContainerStyle: ViewPropTypes.style,
-
-    /**
-     * This is the distance between the top of the user screen and the react native view,
-     * may be non-zero in some use cases. The default value is 0.
-     */
-    keyboardVerticalOffset: PropTypes.number.isRequired,
-    /**
-     * This is to allow us to manually control which KAV shuld take effect when
-     * having more than one KAV at the same screen
-     */
-    enabled: PropTypes.bool.isRequired,
-  },
-
-  getDefaultProps() {
-    return {
-      enabled: true,
-      keyboardVerticalOffset: 0,
-    };
-  },
-
-  getInitialState() {
-    return {
-      bottom: 0,
-    };
-  },
-
-  subscriptions: ([]: Array<EmitterSubscription>),
-  frame: (null: ?ViewLayout),
-
-  _relativeKeyboardHeight(keyboardFrame: ScreenRect): number {
-    const frame = this.frame;
+class KeyboardAvoidingView extends React.Component<Props, State> {
+  static defaultProps = {
+    enabled: true,
+    keyboardVerticalOffset: 0,
+  };
+
+  _frame: ?ViewLayout = null;
+  _subscriptions: Array<EmitterSubscription> = [];
+
+  state = {
+    bottom: 0,
+  };
+
+  _relativeKeyboardHeight(keyboardFrame): number {
+    const frame = this._frame;
     if (!frame || !keyboardFrame) {
       return 0;
     }
@@ -110,10 +82,10 @@ const KeyboardAvoidingView = ((createReactClass({
     // Calculate the displacement needed for the view such that it
     // no longer overlaps with the keyboard
     return Math.max(frame.y + frame.height - keyboardY, 0);
-  },
+  }
 
-  _onKeyboardChange(event: ?KeyboardChangeEvent) {
-    if (!event) {
+  _onKeyboardChange = (event: ?KeyboardEvent) => {
+    if (event == null) {
       this.setState({bottom: 0});
       return;
     }
@@ -135,17 +107,13 @@ const KeyboardAvoidingView = ((createReactClass({
       });
     }
     this.setState({bottom: height});
-  },
+  };
 
-  _onLayout(event: ViewLayoutEvent) {
-    this.frame = event.nativeEvent.layout;
-  },
+  _onLayout = (event: ViewLayoutEvent) => {
+    this._frame = event.nativeEvent.layout;
+  };
 
-  UNSAFE_componentWillUpdate(
-    nextProps: Object,
-    nextState: Object,
-    nextContext?: Object,
-  ): void {
+  UNSAFE_componentWillUpdate(nextProps: Props, nextState: State): void {
     if (
       nextState.bottom === this.state.bottom &&
       this.props.behavior === 'height' &&
@@ -155,44 +123,55 @@ const KeyboardAvoidingView = ((createReactClass({
       // triggered by parent component re-rendering, no need for bottom to change.
       nextState.bottom = 0;
     }
-  },
+  }
 
-  UNSAFE_componentWillMount() {
+  componentDidMount(): void {
     if (Platform.OS === 'ios') {
-      this.subscriptions = [
+      this._subscriptions = [
         Keyboard.addListener('keyboardWillChangeFrame', this._onKeyboardChange),
       ];
     } else {
-      this.subscriptions = [
+      this._subscriptions = [
         Keyboard.addListener('keyboardDidHide', this._onKeyboardChange),
         Keyboard.addListener('keyboardDidShow', this._onKeyboardChange),
       ];
     }
-  },
-
-  componentWillUnmount() {
-    this.subscriptions.forEach(sub => sub.remove());
-  },
-
-  render(): React.Element<any> {
-    // $FlowFixMe(>=0.41.0)
-    const {behavior, children, style, ...props} = this.props;
-    const bottomHeight = this.props.enabled ? this.state.bottom : 0;
+  }
+
+  componentWillUnmount(): void {
+    this._subscriptions.forEach(subscription => {
+      subscription.remove();
+    });
+  }
+
+  render(): React.Node {
+    const {
+      behavior,
+      children,
+      contentContainerStyle,
+      enabled,
+      keyboardVerticalOffset, // eslint-disable-line no-unused-vars
+      style,
+      ...props
+    } = this.props;
+    const bottomHeight = enabled ? this.state.bottom : 0;
     switch (behavior) {
       case 'height':
         let heightStyle;
-        if (this.frame) {
+        if (this._frame != null) {
           // Note that we only apply a height change when there is keyboard present,
           // i.e. this.state.bottom is greater than 0. If we remove that condition,
           // this.frame.height will never go back to its original value.
           // When height changes, we need to disable flex.
-          heightStyle = {height: this.frame.height - bottomHeight, flex: 0};
+          heightStyle = {
+            height: this._frame.height - bottomHeight,
+            flex: 0,
+          };
         }
         return (
-          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           <View
             ref={viewRef}
-            style={[style, heightStyle]}
+            style={StyleSheet.compose(style, heightStyle)}
             onLayout={this._onLayout}
             {...props}>
             {children}
@@ -200,29 +179,26 @@ const KeyboardAvoidingView = ((createReactClass({
         );
 
       case 'position':
-        const positionStyle = {bottom: bottomHeight};
-        const {contentContainerStyle} = this.props;
-
         return (
-          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           <View
             ref={viewRef}
             style={style}
             onLayout={this._onLayout}
             {...props}>
-            <View style={[contentContainerStyle, positionStyle]}>
+            <View
+              style={StyleSheet.compose(contentContainerStyle, {
+                bottom: bottomHeight,
+              })}>
               {children}
             </View>
           </View>
         );
 
       case 'padding':
-        const paddingStyle = {paddingBottom: bottomHeight};
         return (
-          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           <View
             ref={viewRef}
-            style={[style, paddingStyle]}
+            style={StyleSheet.compose(style, {paddingBottom: bottomHeight})}
             onLayout={this._onLayout}
             {...props}>
             {children}
@@ -231,7 +207,6 @@ const KeyboardAvoidingView = ((createReactClass({
 
       default:
         return (
-          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           <View
             ref={viewRef}
             onLayout={this._onLayout}
@@ -241,7 +216,7 @@ const KeyboardAvoidingView = ((createReactClass({
           </View>
         );
     }
-  },
-}): any): React.ComponentType<Props>);
+  }
+}
 
 module.exports = KeyboardAvoidingView;

From 6042592cf46787f089e76b661376705380607207 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 14 May 2018 17:36:36 -0700
Subject: [PATCH 0578/1109] RN: Revise $FlowFixMe in Text

Reviewed By: TheSavior

Differential Revision: D7987519

fbshipit-source-id: 01c389ab7c277ec8423c137e61bb94a0d3ba4669
---
 Libraries/Text/Text.js | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index 1f1698bc25ed..884c86a5e964 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -36,8 +36,7 @@ type ResponseHandlers = $ReadOnly<{|
 
 type Props = $ReadOnly<{
   ...TextProps,
-  // $FlowFixMe - Typing ReactNativeComponent revealed errors
-  forwardedRef: ?React.Ref<NativeComponent<TextProps>>,
+  forwardedRef: ?React.Ref<'RCTText' | 'RCTVirtualText'>,
 }>;
 
 type State = {|
@@ -140,7 +139,6 @@ class TouchableText extends React.Component<Props, State> {
       <TextAncestor.Consumer>
         {hasTextAncestor =>
           hasTextAncestor ? (
-            // $FlowFixMe - Typing ReactNativeComponent revealed errors
             <RCTVirtualText {...props} ref={props.forwardedRef} />
           ) : (
             <TextAncestor.Provider value={true}>

From 206ef54aa415e3e2bb0d48111104dfc372b97e0f Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 14 May 2018 17:36:38 -0700
Subject: [PATCH 0579/1109] RN: Fix $FlowFixMe in RTLExample

Summary: Fix the typo in `RTLExample.js` that is now detected by Flow.

Reviewed By: TheSavior

Differential Revision: D7987526

fbshipit-source-id: d30f536b2f41e2127909675ea065a3355e5576ad
---
 RNTester/js/RTLExample.js | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/RNTester/js/RTLExample.js b/RNTester/js/RTLExample.js
index ac3ec573a7e1..b833adfcbe3c 100644
--- a/RNTester/js/RTLExample.js
+++ b/RNTester/js/RTLExample.js
@@ -484,8 +484,7 @@ class RTLExample extends React.Component<any, State> {
           <RNTesterBlock
             title={'Controlling Animation'}
             description={'Animation direction according to layout'}>
-            {/* $FlowFixMe - Typing ReactNativeComponent revealed errors */}
-            <View Style={styles.view}>
+            <View style={styles.view}>
               <AnimationBlock
                 onPress={this._linearTap}
                 imgStyle={{

From a956551af73cf785ee4345e92e71fd5b17c5644e Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 14 May 2018 17:36:40 -0700
Subject: [PATCH 0580/1109] RN: Fix $FlowFixMe in AppContainer

Summary: Fixes the `$FlowFixMe` type errors in `AppContainer`.

Reviewed By: TheSavior

Differential Revision: D7987552

fbshipit-source-id: 5eba319aa2661c2d6d8ed24affc066504096b72c
---
 Libraries/ReactNative/AppContainer.js | 26 ++++++++++++--------------
 1 file changed, 12 insertions(+), 14 deletions(-)

diff --git a/Libraries/ReactNative/AppContainer.js b/Libraries/ReactNative/AppContainer.js
index ce4a78043a4f..ad5f8c06a35f 100644
--- a/Libraries/ReactNative/AppContainer.js
+++ b/Libraries/ReactNative/AppContainer.js
@@ -21,25 +21,24 @@ const View = require('View');
 type Context = {
   rootTag: number,
 };
-type Props = {|
-  /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This comment
-   * suppresses an error when upgrading Flow's support for React. To see the
-   * error delete this comment and run Flow. */
-  children?: React.Children,
+
+type Props = $ReadOnly<{|
+  children?: React.Node,
   rootTag: number,
-  WrapperComponent?: ?React.ComponentType<*>,
-|};
-type State = {
-  inspector: ?React.Element<any>,
+  WrapperComponent?: ?React.ComponentType<any>,
+|}>;
+
+type State = {|
+  inspector: ?React.Node,
   mainKey: number,
-};
+|};
 
 class AppContainer extends React.Component<Props, State> {
   state: State = {
     inspector: null,
     mainKey: 1,
   };
-  _mainRef: ?React.Element<any>;
+  _mainRef: ?React.ElementRef<typeof View>;
   _subscription: ?EmitterSubscription = null;
 
   static childContextTypes = {
@@ -81,7 +80,7 @@ class AppContainer extends React.Component<Props, State> {
   }
 
   componentWillUnmount(): void {
-    if (this._subscription) {
+    if (this._subscription != null) {
       this._subscription.remove();
     }
   }
@@ -102,7 +101,6 @@ class AppContainer extends React.Component<Props, State> {
         pointerEvents="box-none"
         style={styles.appContainer}
         ref={ref => {
-          // $FlowFixMe - Typing ReactNativeComponent revealed errors
           this._mainRef = ref;
         }}>
         {this.props.children}
@@ -110,7 +108,7 @@ class AppContainer extends React.Component<Props, State> {
     );
 
     const Wrapper = this.props.WrapperComponent;
-    if (Wrapper) {
+    if (Wrapper != null) {
       innerView = <Wrapper>{innerView}</Wrapper>;
     }
     return (

From 4ef099679d64032b57edd5f0ac75c233ab7f2956 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Mon, 14 May 2018 18:56:51 -0700
Subject: [PATCH 0581/1109] Expose new methods to Custom/System JSC

Reviewed By: fkgozali

Differential Revision: D7998298

fbshipit-source-id: f20d5b961db1cc31880d383a67d8bba40dd8008f
---
 React/React.xcodeproj/project.pbxproj       | 10 +++++++
 ReactCommon/jschelpers/BUCK                 |  1 +
 ReactCommon/jschelpers/JSCWrapper.h         | 12 ++++++++
 ReactCommon/jschelpers/JSWeak.h             | 32 +++++++++++++++++++++
 ReactCommon/jschelpers/JavaScriptCore.h     | 19 +++++++++---
 ReactCommon/jschelpers/systemJSCWrapper.cpp | 23 +++++++++++++++
 6 files changed, 93 insertions(+), 4 deletions(-)
 create mode 100644 ReactCommon/jschelpers/JSWeak.h

diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index 1f6f9f2eef69..ef3189426c62 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -1200,6 +1200,10 @@
 		A2440AA21DF8D854006E7BFC /* RCTReloadCommand.h in Headers */ = {isa = PBXBuildFile; fileRef = A2440AA01DF8D854006E7BFC /* RCTReloadCommand.h */; };
 		A2440AA31DF8D854006E7BFC /* RCTReloadCommand.m in Sources */ = {isa = PBXBuildFile; fileRef = A2440AA11DF8D854006E7BFC /* RCTReloadCommand.m */; };
 		A2440AA41DF8D865006E7BFC /* RCTReloadCommand.h in Headers */ = {isa = PBXBuildFile; fileRef = A2440AA01DF8D854006E7BFC /* RCTReloadCommand.h */; };
+		A2C986DF208C7DF700C0D579 /* JSWeak.h in Headers */ = {isa = PBXBuildFile; fileRef = A2E0E69F208AA9EC007044C1 /* JSWeak.h */; };
+		A2C986E0208C7DF900C0D579 /* JSWeak.h in Headers */ = {isa = PBXBuildFile; fileRef = A2E0E69F208AA9EC007044C1 /* JSWeak.h */; };
+		A2C986E1208C7E9C00C0D579 /* JSWeak.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = A2E0E69F208AA9EC007044C1 /* JSWeak.h */; };
+		A2C986E2208C7EA800C0D579 /* JSWeak.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = A2E0E69F208AA9EC007044C1 /* JSWeak.h */; };
 		AC70D2E91DE489E4002E6351 /* RCTJavaScriptLoader.mm in Sources */ = {isa = PBXBuildFile; fileRef = AC70D2E81DE489E4002E6351 /* RCTJavaScriptLoader.mm */; };
 		B233E6EA1D2D845D00BC68BA /* RCTI18nManager.m in Sources */ = {isa = PBXBuildFile; fileRef = B233E6E91D2D845D00BC68BA /* RCTI18nManager.m */; };
 		B95154321D1B34B200FE7B80 /* RCTActivityIndicatorView.m in Sources */ = {isa = PBXBuildFile; fileRef = B95154311D1B34B200FE7B80 /* RCTActivityIndicatorView.m */; };
@@ -1571,6 +1575,7 @@
 			dstPath = include/jschelpers;
 			dstSubfolderSpec = 16;
 			files = (
+				A2C986E2208C7EA800C0D579 /* JSWeak.h in Copy Headers */,
 				3DA982601E5B1089004F2374 /* JSCHelpers.h in Copy Headers */,
 				3DA982611E5B1089004F2374 /* noncopyable.h in Copy Headers */,
 				3DA982621E5B1089004F2374 /* Unicode.h in Copy Headers */,
@@ -1799,6 +1804,7 @@
 			dstPath = include/jschelpers;
 			dstSubfolderSpec = 16;
 			files = (
+				A2C986E1208C7E9C00C0D579 /* JSWeak.h in Copy Headers */,
 				3DA9825A1E5B1079004F2374 /* JavaScriptCore.h in Copy Headers */,
 				3DA9825B1E5B1079004F2374 /* JSCHelpers.h in Copy Headers */,
 				3DA9825C1E5B1079004F2374 /* JSCWrapper.h in Copy Headers */,
@@ -2302,6 +2308,7 @@
 		9936F3361F5F2F480010BF04 /* PrivateDataBase.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = PrivateDataBase.h; path = privatedata/PrivateDataBase.h; sourceTree = "<group>"; };
 		A2440AA01DF8D854006E7BFC /* RCTReloadCommand.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTReloadCommand.h; sourceTree = "<group>"; };
 		A2440AA11DF8D854006E7BFC /* RCTReloadCommand.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTReloadCommand.m; sourceTree = "<group>"; };
+		A2E0E69F208AA9EC007044C1 /* JSWeak.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSWeak.h; sourceTree = "<group>"; };
 		AC70D2E81DE489E4002E6351 /* RCTJavaScriptLoader.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = RCTJavaScriptLoader.mm; sourceTree = "<group>"; };
 		AC70D2EB1DE48A22002E6351 /* JSBundleType.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSBundleType.cpp; sourceTree = "<group>"; };
 		ACDD3FDA1BC7430D00E7DE33 /* RCTBorderStyle.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTBorderStyle.h; sourceTree = "<group>"; };
@@ -2760,6 +2767,7 @@
 		3D4A621D1DDD3985001F41B4 /* jschelpers */ = {
 			isa = PBXGroup;
 			children = (
+				A2E0E69F208AA9EC007044C1 /* JSWeak.h */,
 				19DED2281E77E29200F089BB /* systemJSCWrapper.cpp */,
 				3D7A27DC1DE32541002E3F95 /* JavaScriptCore.h */,
 				3D92B1071E0369AD0018521A /* JSCHelpers.cpp */,
@@ -3376,6 +3384,7 @@
 			files = (
 				19F61C041E8495FF00571D81 /* JSCHelpers.h in Headers */,
 				19F61C051E8495FF00571D81 /* noncopyable.h in Headers */,
+				A2C986E0208C7DF900C0D579 /* JSWeak.h in Headers */,
 				19F61C061E8495FF00571D81 /* Unicode.h in Headers */,
 				19F61C071E8495FF00571D81 /* Value.h in Headers */,
 				3D3030251DF8295E00D6DDAE /* JavaScriptCore.h in Headers */,
@@ -3423,6 +3432,7 @@
 			files = (
 				13EBC6821E28733C00880AC5 /* Value.h in Headers */,
 				13EBC6811E28733C00880AC5 /* Unicode.h in Headers */,
+				A2C986DF208C7DF700C0D579 /* JSWeak.h in Headers */,
 				13EBC6801E28733C00880AC5 /* noncopyable.h in Headers */,
 				13EBC67E1E28726000880AC5 /* JSCHelpers.h in Headers */,
 				3D3CD93D1DE5FC1400167DC4 /* JavaScriptCore.h in Headers */,
diff --git a/ReactCommon/jschelpers/BUCK b/ReactCommon/jschelpers/BUCK
index c0bb888ea0c9..76939bba19e6 100644
--- a/ReactCommon/jschelpers/BUCK
+++ b/ReactCommon/jschelpers/BUCK
@@ -4,6 +4,7 @@ EXPORTED_HEADERS = [
     "JavaScriptCore.h",
     "JSCHelpers.h",
     "JSCWrapper.h",
+    "JSWeak.h",
     "noncopyable.h",
     "Unicode.h",
     "Value.h",
diff --git a/ReactCommon/jschelpers/JSCWrapper.h b/ReactCommon/jschelpers/JSCWrapper.h
index d221ea7eb410..15c15ef98e81 100644
--- a/ReactCommon/jschelpers/JSCWrapper.h
+++ b/ReactCommon/jschelpers/JSCWrapper.h
@@ -10,6 +10,7 @@
 #include <functional>
 #include <string>
 #include <JavaScriptCore/JavaScript.h>
+#include <jschelpers/JSWeak.h>
 
 #if defined(JSCINTERNAL) || (!defined(__APPLE__))
 #define JSC_IMPORT extern "C"
@@ -77,6 +78,10 @@ struct JSCWrapper {
   // JSContext
   JSC_WRAPPER_METHOD(JSContextGetGlobalContext);
   JSC_WRAPPER_METHOD(JSContextGetGlobalObject);
+  JSC_WRAPPER_METHOD(JSContextGetGroup);
+  JSC_WRAPPER_METHOD(JSContextGroupRetain);
+  JSC_WRAPPER_METHOD(JSContextGroupRelease);
+
   JSC_WRAPPER_METHOD(FBJSContextStartGCTimers);
 
   // JSEvaluate
@@ -99,6 +104,7 @@ struct JSCWrapper {
 
   // JSClass
   JSC_WRAPPER_METHOD(JSClassCreate);
+  JSC_WRAPPER_METHOD(JSClassRetain);
   JSC_WRAPPER_METHOD(JSClassRelease);
 
   // JSObject
@@ -141,6 +147,12 @@ struct JSCWrapper {
   JSC_WRAPPER_METHOD(JSValueUnprotect);
   JSC_WRAPPER_METHOD(JSValueIsNull);
 
+  // JSWeak
+  JSC_WRAPPER_METHOD(JSWeakCreate);
+  JSC_WRAPPER_METHOD(JSWeakRetain);
+  JSC_WRAPPER_METHOD(JSWeakRelease);
+  JSC_WRAPPER_METHOD(JSWeakGetObject);
+
   // Sampling profiler
   JSC_WRAPPER_METHOD(JSSamplingProfilerEnabled);
   JSC_WRAPPER_METHOD(JSPokeSamplingProfiler);
diff --git a/ReactCommon/jschelpers/JSWeak.h b/ReactCommon/jschelpers/JSWeak.h
new file mode 100644
index 000000000000..9c0704237667
--- /dev/null
+++ b/ReactCommon/jschelpers/JSWeak.h
@@ -0,0 +1,32 @@
+/**
+ * Copyright (c) 2016-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <JavaScriptCore/JSObjectRef.h>
+
+// These Symbols are included in JSC builds but not exported as part of the public headers.
+
+#ifndef JSWeakPrivate_h
+#define JSWeakPrivate_h
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+typedef struct OpaqueJSWeak* JSWeakRef;
+
+JSWeakRef JSWeakCreate(JSContextGroupRef, JSObjectRef);
+
+void JSWeakRetain(JSContextGroupRef, JSWeakRef);
+void JSWeakRelease(JSContextGroupRef, JSWeakRef);
+
+JSObjectRef JSWeakGetObject(JSWeakRef);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // JSWeakPrivate_h
diff --git a/ReactCommon/jschelpers/JavaScriptCore.h b/ReactCommon/jschelpers/JavaScriptCore.h
index ff3dfd3b5dd0..5d7dd3ad891d 100644
--- a/ReactCommon/jschelpers/JavaScriptCore.h
+++ b/ReactCommon/jschelpers/JavaScriptCore.h
@@ -72,16 +72,20 @@
 #define JSC_JSGlobalContextRelease(...) __jsc_wrapper(JSGlobalContextRelease, __VA_ARGS__)
 #define JSC_JSGlobalContextSetName(...) __jsc_wrapper(JSGlobalContextSetName, __VA_ARGS__)
 
-jsc_poison(JSContextGroupCreate JSContextGroupRelease JSContextGroupRetain
-           JSGlobalContextCreate JSGlobalContextCreateInGroup JSGlobalContextCopyName
-           JSGlobalContextRelease JSGlobalContextRetain JSGlobalContextSetName)
+jsc_poison(JSContextGroupCreate JSGlobalContextCreate JSGlobalContextCreateInGroup
+           JSGlobalContextCopyName JSGlobalContextRelease JSGlobalContextRetain
+           JSGlobalContextSetName)
 
 // JSContext
 #define JSC_JSContextGetGlobalContext(...) __jsc_wrapper(JSContextGetGlobalContext, __VA_ARGS__)
 #define JSC_JSContextGetGlobalObject(...) __jsc_wrapper(JSContextGetGlobalObject, __VA_ARGS__)
+#define JSC_JSContextGetGroup(ctx) __jsc_wrapper(JSContextGetGroup, ctx)
+#define JSC_JSContextGroupRetain(...) __jsc_bool_wrapper(JSContextGroupRetain, __VA_ARGS__)
+#define JSC_JSContextGroupRelease(...) __jsc_bool_wrapper(JSContextGroupRelease, __VA_ARGS__)
 #define JSC_FBJSContextStartGCTimers(...) __jsc_wrapper(FBJSContextStartGCTimers, __VA_ARGS__)
 
-jsc_poison(JSContextGetGlobalContext JSContextGetGlobalObject JSContextGetGroup FBJSContextStartGCTimers)
+jsc_poison(JSContextGetGlobalContext JSContextGetGlobalObject JSContextGetGroup
+           JSContextGroupRelease JSContextGroupRetain FBJSContextStartGCTimers)
 
 // JSEvaluate
 #define JSC_JSEvaluateScript(...) __jsc_wrapper(JSEvaluateScript, __VA_ARGS__)
@@ -134,6 +138,7 @@ jsc_poison(JSValueCreateJSONString JSValueGetType JSValueGetTypedArrayType JSVal
 
 // JSClass
 #define JSC_JSClassCreate(...) __jsc_bool_wrapper(JSClassCreate, __VA_ARGS__)
+#define JSC_JSClassRetain(...) __jsc_bool_wrapper(JSClassRetain, __VA_ARGS__)
 #define JSC_JSClassRelease(...) __jsc_bool_wrapper(JSClassRelease, __VA_ARGS__)
 
 jsc_poison(JSClassCreate JSClassRelease JSClassRetain)
@@ -182,6 +187,12 @@ jsc_poison(JSObjectMakeArrayBufferWithBytesNoCopy JSObjectMakeTypedArray
            JSObjectGetTypedArrayBuffer JSObjectGetTypedArrayLength
            JSObjectGetArrayBufferBytesPtr JSObjectGetArrayBufferByteLength)
 
+// JSWeak
+#define JSC_JSWeakCreate(...) __jsc_bool_wrapper(JSWeakCreate, __VA_ARGS__)
+#define JSC_JSWeakRetain(...) __jsc_bool_wrapper(JSWeakRetain, __VA_ARGS__)
+#define JSC_JSWeakRelease(...) __jsc_bool_wrapper(JSWeakRelease, __VA_ARGS__)
+#define JSC_JSWeakGetObject(...) __jsc_drop_ctx_wrapper(JSWeakGetObject, __VA_ARGS__)
+
 // Sampling profiler
 #define JSC_JSSamplingProfilerEnabled(...) __jsc_drop_ctx_wrapper(JSSamplingProfilerEnabled, __VA_ARGS__)
 #define JSC_JSPokeSamplingProfiler(...) __jsc_wrapper(JSPokeSamplingProfiler, __VA_ARGS__)
diff --git a/ReactCommon/jschelpers/systemJSCWrapper.cpp b/ReactCommon/jschelpers/systemJSCWrapper.cpp
index 45e0597efe81..c97180d7cc3e 100644
--- a/ReactCommon/jschelpers/systemJSCWrapper.cpp
+++ b/ReactCommon/jschelpers/systemJSCWrapper.cpp
@@ -34,6 +34,11 @@ UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(configureJSCForIOS)
 
 UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(FBJSContextStartGCTimers)
 
+UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(JSWeakCreate)
+UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(JSWeakRetain)
+UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(JSWeakRelease)
+UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(JSWeakGetObject)
+
 bool JSSamplingProfilerEnabled() {
   return false;
 }
@@ -57,6 +62,10 @@ const JSCWrapper* systemJSCWrapper() {
 
       .JSContextGetGlobalContext = JSContextGetGlobalContext,
       .JSContextGetGlobalObject = JSContextGetGlobalObject,
+      .JSContextGetGroup = JSContextGetGroup,
+      .JSContextGroupRetain = JSContextGroupRetain,
+      .JSContextGroupRelease = JSContextGroupRelease,
+
       .FBJSContextStartGCTimers =
         (decltype(&FBJSContextStartGCTimers))
         Unimplemented_FBJSContextStartGCTimers,
@@ -82,6 +91,7 @@ const JSCWrapper* systemJSCWrapper() {
       .JSStringRetain = JSStringRetain,
 
       .JSClassCreate = JSClassCreate,
+      .JSClassRetain = JSClassRetain,
       .JSClassRelease = JSClassRelease,
 
       .JSObjectCallAsConstructor = JSObjectCallAsConstructor,
@@ -121,6 +131,19 @@ const JSCWrapper* systemJSCWrapper() {
       .JSValueUnprotect = JSValueUnprotect,
       .JSValueIsNull = JSValueIsNull,
 
+      .JSWeakCreate =
+        (decltype(&JSWeakCreate))
+        Unimplemented_JSWeakCreate,
+      .JSWeakRetain =
+        (decltype(&JSWeakRetain))
+        Unimplemented_JSWeakRetain,
+      .JSWeakRelease =
+        (decltype(&JSWeakRelease))
+        Unimplemented_JSWeakRelease,
+      .JSWeakGetObject =
+        (decltype(&JSWeakGetObject))
+        Unimplemented_JSWeakGetObject,
+
       .JSSamplingProfilerEnabled = JSSamplingProfilerEnabled,
       .JSPokeSamplingProfiler =
         (decltype(&JSPokeSamplingProfiler))

From 42fc87eb8d504d9771360d898a907d51a5403b7e Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Mon, 14 May 2018 20:34:35 -0700
Subject: [PATCH 0582/1109] remove unnecessary ExceptionManager abstraction

Reviewed By: sebmarkbage

Differential Revision: D8002124

fbshipit-source-id: 4e0bce9686549d0dd7b59b1323efd11ea168855b
---
 RNTester/Podfile.lock                         | 16 +++--
 React.podspec                                 | 14 ----
 React/Base/RCTLog.h                           |  7 --
 React/Base/RCTLog.mm                          | 65 +++++++++----------
 React/CxxExceptions/RCTCxxExceptionManager.h  | 27 --------
 React/CxxExceptions/RCTCxxExceptionManager.mm | 31 ---------
 React/Fabric/RCTFabricUIManagerWrapper.h      |  2 -
 React/Fabric/RCTFabricUIManagerWrapper.mm     |  8 ---
 React/Fabric/RCTSurfacePresenter.h            |  4 +-
 React/Fabric/RCTSurfacePresenter.mm           | 14 ----
 ReactCommon/exceptions/BUCK                   | 40 ------------
 ReactCommon/exceptions/ExceptionManager.h     | 28 --------
 12 files changed, 40 insertions(+), 216 deletions(-)
 delete mode 100644 React/CxxExceptions/RCTCxxExceptionManager.h
 delete mode 100644 React/CxxExceptions/RCTCxxExceptionManager.mm
 delete mode 100644 ReactCommon/exceptions/BUCK
 delete mode 100644 ReactCommon/exceptions/ExceptionManager.h

diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index 57ad2bcedbe7..a52cf4348062 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -14,9 +14,6 @@ PODS:
     - Folly (= 2016.10.31.00)
     - React/Core
     - React/cxxreact
-  - React/CxxExceptions (1000.0.0):
-    - React/CxxBridge
-    - React/exceptions
   - React/cxxreact (1000.0.0):
     - boost-for-react-native (= 1.63.0)
     - Folly (= 2016.10.31.00)
@@ -25,19 +22,27 @@ PODS:
   - React/DevSupport (1000.0.0):
     - React/Core
     - React/RCTWebSocket
-  - React/exceptions (1000.0.0)
   - React/fabric (1000.0.0):
+    - React/fabric/attributedstring (= 1000.0.0)
     - React/fabric/core (= 1000.0.0)
     - React/fabric/debug (= 1000.0.0)
     - React/fabric/graphics (= 1000.0.0)
+    - React/fabric/text (= 1000.0.0)
+    - React/fabric/textlayoutmanager (= 1000.0.0)
     - React/fabric/uimanager (= 1000.0.0)
     - React/fabric/view (= 1000.0.0)
+  - React/fabric/attributedstring (1000.0.0):
+    - Folly (= 2016.10.31.00)
   - React/fabric/core (1000.0.0):
     - Folly (= 2016.10.31.00)
   - React/fabric/debug (1000.0.0):
     - Folly (= 2016.10.31.00)
   - React/fabric/graphics (1000.0.0):
     - Folly (= 2016.10.31.00)
+  - React/fabric/text (1000.0.0):
+    - Folly (= 2016.10.31.00)
+  - React/fabric/textlayoutmanager (1000.0.0):
+    - Folly (= 2016.10.31.00)
   - React/fabric/uimanager (1000.0.0):
     - Folly (= 2016.10.31.00)
   - React/fabric/view (1000.0.0):
@@ -61,7 +66,6 @@ PODS:
   - React/RCTFabric (1000.0.0):
     - Folly (= 2016.10.31.00)
     - React/Core
-    - React/CxxExceptions
     - React/fabric
   - React/RCTGeolocation (1000.0.0):
     - React/Core
@@ -131,7 +135,7 @@ SPEC CHECKSUMS:
   DoubleConversion: e22e0762848812a87afd67ffda3998d9ef29170c
   Folly: 9a8eea4725a0b6ba3256ebf206c21e352c23abf8
   glog: 1de0bb937dccdc981596d3b5825ebfb765017ded
-  React: e3382e39c51a5e5889248e97c6b9b1b3ca443a08
+  React: 512b17e881b5d04d703cd292caa6f4fe12984688
   yoga: bdd268c5812f00bdb52cc2b58f129797e97935eb
 
 PODFILE CHECKSUM: 1a96172007b66aa74825c234f17139dd9c3d3cd7
diff --git a/React.podspec b/React.podspec
index 9305d94ea484..1c590b4ff530 100644
--- a/React.podspec
+++ b/React.podspec
@@ -74,13 +74,6 @@ Pod::Spec.new do |s|
     ss.compiler_flags       = folly_compiler_flags
     ss.private_header_files = "React/Cxx*/*.h"
     ss.source_files         = "React/Cxx*/*.{h,m,mm}"
-    ss.exclude_files        = "React/CxxExceptions/**/*"
-  end
-
-  s.subspec "CxxExceptions" do |ss|
-    ss.dependency             "React/CxxBridge"
-    ss.dependency             "React/exceptions"
-    ss.source_files         = "React/CxxExceptions/*.{h,m,mm}"
   end
 
   s.subspec "DevSupport" do |ss|
@@ -93,7 +86,6 @@ Pod::Spec.new do |s|
   s.subspec "RCTFabric" do |ss|
     ss.dependency             "Folly", folly_version
     ss.dependency             "React/Core"
-    ss.dependency             "React/CxxExceptions"
     ss.dependency             "React/fabric"
     ss.compiler_flags       = folly_compiler_flags
     ss.source_files         = "React/Fabric/**/*.{c,h,m,mm,S,cpp}"
@@ -142,12 +134,6 @@ Pod::Spec.new do |s|
     ss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/boost-for-react-native\" \"$(PODS_ROOT)/DoubleConversion\" \"$(PODS_ROOT)/Folly\"" }
   end
 
-  s.subspec "exceptions" do |ss|
-    ss.source_files         = "ReactCommon/exceptions/*.{cpp,h}"
-    ss.header_dir           = "cxxreact"
-    ss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\"" }
-  end
-
   s.subspec "fabric" do |ss|
     ss.subspec "attributedstring" do |sss|
       sss.dependency             "Folly", folly_version
diff --git a/React/Base/RCTLog.h b/React/Base/RCTLog.h
index 6ef09d620c55..9f9317da410c 100644
--- a/React/Base/RCTLog.h
+++ b/React/Base/RCTLog.h
@@ -120,13 +120,6 @@ RCT_EXTERN void RCTPerformBlockWithLogFunction(void (^block)(void), RCTLogFuncti
  */
 RCT_EXTERN void RCTPerformBlockWithLogPrefix(void (^block)(void), NSString *prefix);
 
-/**
- * This method computes the current call stack, useful for error reporting.
- */
-RCT_EXTERN NSArray<NSDictionary *> *RCTGetCallStack(const char *fileName, int lineNumber);
-
-#define RCT_CALLSTACK RCTGetCallStack(__FILE__, __LINE__)
-
 /**
  * Private logging function - ignore this.
  */
diff --git a/React/Base/RCTLog.mm b/React/Base/RCTLog.mm
index 4e65fa0cc87b..edb92fe01468 100644
--- a/React/Base/RCTLog.mm
+++ b/React/Base/RCTLog.mm
@@ -197,41 +197,6 @@ void RCTPerformBlockWithLogPrefix(void (^block)(void), NSString *prefix)
   return _regex;
 }
 
-NSArray<NSDictionary *>* RCTGetCallStack(const char *fileName, int lineNumber)
-{
-  NSArray<NSString *> *stackSymbols = [NSThread callStackSymbols];
-  NSMutableArray<NSDictionary *> *stack =
-  [NSMutableArray arrayWithCapacity:(stackSymbols.count - 1)];
-  [stackSymbols enumerateObjectsUsingBlock:^(NSString *frameSymbols, NSUInteger idx, __unused BOOL *stop) {
-    if (idx == 0) {
-      // don't include the current frame
-      return;
-    }
-
-    NSRange range = NSMakeRange(0, frameSymbols.length);
-    NSTextCheckingResult *match = [nativeStackFrameRegex() firstMatchInString:frameSymbols options:0 range:range];
-    if (!match) {
-      return;
-    }
-
-    NSString *methodName = [frameSymbols substringWithRange:[match rangeAtIndex:1]];
-    char *demangledName = abi::__cxa_demangle([methodName UTF8String], NULL, NULL, NULL);
-    if (demangledName) {
-      methodName = @(demangledName);
-      free(demangledName);
-    }
-
-    if (idx == 1 && fileName) {
-      NSString *file = [@(fileName) componentsSeparatedByString:@"/"].lastObject;
-      [stack addObject:@{@"methodName": methodName, @"file": file, @"lineNumber": @(lineNumber)}];
-    } else {
-      [stack addObject:@{@"methodName": methodName}];
-    }
-  }];
-
-  return [stack copy];
-}
-
 void _RCTLogNativeInternal(RCTLogLevel level, const char *fileName, int lineNumber, NSString *format, ...)
 {
   RCTLogFunction logFunction = RCTGetLocalLogFunction();
@@ -252,7 +217,35 @@ void _RCTLogNativeInternal(RCTLogLevel level, const char *fileName, int lineNumb
 
     // Log to red box in debug mode.
     if (RCTSharedApplication() && level >= RCTLOG_REDBOX_LEVEL) {
-      NSArray<NSDictionary *> *stack = RCT_CALLSTACK;
+      NSArray<NSString *> *stackSymbols = [NSThread callStackSymbols];
+      NSMutableArray<NSDictionary *> *stack =
+        [NSMutableArray arrayWithCapacity:(stackSymbols.count - 1)];
+      [stackSymbols enumerateObjectsUsingBlock:^(NSString *frameSymbols, NSUInteger idx, __unused BOOL *stop) {
+        if (idx == 0) {
+          // don't include the current frame
+          return;
+        }
+
+        NSRange range = NSMakeRange(0, frameSymbols.length);
+        NSTextCheckingResult *match = [nativeStackFrameRegex() firstMatchInString:frameSymbols options:0 range:range];
+        if (!match) {
+          return;
+        }
+
+        NSString *methodName = [frameSymbols substringWithRange:[match rangeAtIndex:1]];
+        char *demangledName = abi::__cxa_demangle([methodName UTF8String], NULL, NULL, NULL);
+        if (demangledName) {
+          methodName = @(demangledName);
+          free(demangledName);
+        }
+
+        if (idx == 1 && fileName) {
+          NSString *file = [@(fileName) componentsSeparatedByString:@"/"].lastObject;
+          [stack addObject:@{@"methodName": methodName, @"file": file, @"lineNumber": @(lineNumber)}];
+        } else {
+          [stack addObject:@{@"methodName": methodName}];
+        }
+      }];
 
       dispatch_async(dispatch_get_main_queue(), ^{
         // red box is thread safe, but by deferring to main queue we avoid a startup
diff --git a/React/CxxExceptions/RCTCxxExceptionManager.h b/React/CxxExceptions/RCTCxxExceptionManager.h
deleted file mode 100644
index c8e3de44c40f..000000000000
--- a/React/CxxExceptions/RCTCxxExceptionManager.h
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <cxxreact/ExceptionManager.h>
-
-namespace facebook {
-namespace react {
-
-/**
- * Connector class (from C++ to ObjC++) to allow FabricUIManager to invoke native UI operations/updates.
- * UIKit-related impl doesn't live here, but this class gets passed to the FabricUIManager C++ impl directly.
- */
-class RCTCxxExceptionManager : public ExceptionManager {
-public:
-
-  virtual void handleSoftException(const std::exception& e) const override;
-  virtual void handleFatalException(const std::exception& e) const override;
-};
-
-} // namespace react
-} // namespace facebook
diff --git a/React/CxxExceptions/RCTCxxExceptionManager.mm b/React/CxxExceptions/RCTCxxExceptionManager.mm
deleted file mode 100644
index 61e636378ddd..000000000000
--- a/React/CxxExceptions/RCTCxxExceptionManager.mm
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#import "RCTCxxExceptionManager.h"
-
-#import <Foundation/Foundation.h>
-
-#import <React/RCTBridge.h>
-#import <React/RCTBridge+Private.h>
-#import <React/RCTExceptionsManager.h>
-#import <React/RCTLog.h>
-
-namespace facebook {
-namespace react {
-
-void RCTCxxExceptionManager::handleSoftException(const std::exception& e) const {
-  RCTExceptionsManager *manager = [[RCTBridge currentBridge] moduleForClass:[RCTExceptionsManager class]];
-  [manager reportSoftException:[NSString stringWithUTF8String:e.what()] stack:RCT_CALLSTACK exceptionId:@0];
-}
-
-void RCTCxxExceptionManager::handleFatalException(const std::exception& e) const {
-  RCTExceptionsManager *manager = [[RCTBridge currentBridge] moduleForClass:[RCTExceptionsManager class]];
-  [manager reportFatalException:[NSString stringWithUTF8String:e.what()] stack:RCT_CALLSTACK exceptionId:@0];
-}
-
-} // namespace react
-} // namespace facebook
diff --git a/React/Fabric/RCTFabricUIManagerWrapper.h b/React/Fabric/RCTFabricUIManagerWrapper.h
index 234668bb1b09..d40ef78c359c 100644
--- a/React/Fabric/RCTFabricUIManagerWrapper.h
+++ b/React/Fabric/RCTFabricUIManagerWrapper.h
@@ -17,7 +17,6 @@ namespace facebook {
 namespace react {
 
 class FabricUIManager;
-class ExceptionManager;
 
 } // namespace react
 } // namespace facebook
@@ -30,7 +29,6 @@ using namespace facebook::react;
 @interface RCTFabricUIManagerWrapper : NSObject <RCTInvalidating>
 
 - (std::shared_ptr<FabricUIManager>)manager;
-- (std::shared_ptr<ExceptionManager>)exceptionManager;
 
 @end
 
diff --git a/React/Fabric/RCTFabricUIManagerWrapper.mm b/React/Fabric/RCTFabricUIManagerWrapper.mm
index dff3f263f12d..0d4613b0c28f 100644
--- a/React/Fabric/RCTFabricUIManagerWrapper.mm
+++ b/React/Fabric/RCTFabricUIManagerWrapper.mm
@@ -7,7 +7,6 @@
 
 #import "RCTFabricUIManagerWrapper.h"
 
-#include <React/RCTCxxExceptionManager.h>
 #include <fabric/uimanager/ComponentDescriptorRegistry.h>
 #include <fabric/uimanager/FabricUIManager.h>
 #include <fabric/view/ViewComponentDescriptor.h>
@@ -20,7 +19,6 @@
 @implementation RCTFabricUIManagerWrapper
 {
   std::shared_ptr<FabricUIManager> _manager;
-  std::shared_ptr<ExceptionManager> _exceptionManager;
   std::shared_ptr<IFabricPlatformUIOperationManager> _platformUIOperationManager;
 }
 
@@ -28,7 +26,6 @@ - (instancetype)init
 {
   self = [super init];
   if (self) {
-    _exceptionManager = std::make_shared<RCTCxxExceptionManager>();
     _platformUIOperationManager = std::make_shared<RCTFabricPlatformUIOperationManagerConnector>();
 
     auto componentDescriptorRegistry = std::make_shared<ComponentDescriptorRegistry>();
@@ -45,11 +42,6 @@ - (instancetype)init
   return _manager;
 }
 
-- (std::shared_ptr<ExceptionManager>)exceptionManager
-{
-  return _exceptionManager;
-}
-
 - (void)invalidate
 {
 }
diff --git a/React/Fabric/RCTSurfacePresenter.h b/React/Fabric/RCTSurfacePresenter.h
index 65456cbf53e6..52c44fbda763 100644
--- a/React/Fabric/RCTSurfacePresenter.h
+++ b/React/Fabric/RCTSurfacePresenter.h
@@ -9,7 +9,6 @@
 #import <memory>
 
 #import <React/RCTBridge.h>
-#import <React/RCTCxxExceptionManager.h>
 #import <fabric/uimanager/FabricUIManager.h>
 
 NS_ASSUME_NONNULL_BEGIN
@@ -56,10 +55,9 @@ NS_ASSUME_NONNULL_BEGIN
 @interface RCTSurfacePresenter (Deprecated)
 
 /**
- * We need to expose `exceptionManager` and `uiManager` for registration
+ * We need to expose `uiManager` for registration
  * purposes. Eventually, we will move this down to C++ side.
  */
-- (std::shared_ptr<facebook::react::ExceptionManager>)exceptionManager_DO_NOT_USE;
 - (std::shared_ptr<facebook::react::FabricUIManager>)uiManager_DO_NOT_USE;
 
 @end
diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
index 1e0164f2b9fd..8673a2fc70cc 100644
--- a/React/Fabric/RCTSurfacePresenter.mm
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -8,7 +8,6 @@
 #import "RCTSurfacePresenter.h"
 
 #import <React/RCTAssert.h>
-#import <React/RCTCxxExceptionManager.h>
 #import <React/RCTScheduler.h>
 #import <React/RCTMountingManager.h>
 #import <React/RCTFabricSurface.h>
@@ -30,7 +29,6 @@ @interface RCTSurfacePresenter () <RCTSchedulerDelegate, RCTMountingManagerDeleg
 @end
 
 @implementation RCTSurfacePresenter {
-  std::shared_ptr<ExceptionManager> _exceptionManager;
   RCTScheduler *_scheduler;
   RCTMountingManager *_mountingManager;
   RCTBridge *_bridge;
@@ -44,8 +42,6 @@ - (instancetype)initWithBridge:(RCTBridge *)bridge
     _bridge = bridge;
     _batchedBridge = [_bridge batchedBridge] ?: _bridge;
 
-    _exceptionManager = std::make_shared<RCTCxxExceptionManager>();
-
     _scheduler = [[RCTScheduler alloc] init];
     _scheduler.delegate = self;
 
@@ -57,11 +53,6 @@ - (instancetype)initWithBridge:(RCTBridge *)bridge
   return self;
 }
 
-- (std::shared_ptr<ExceptionManager>)exceptionManager
-{
-  return _exceptionManager;
-}
-
 - (void)schedulerDidComputeMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions rootTag:(ReactTag)rootTag
 {
   [_mountingManager mutateComponentViewTreeWithMutationInstructions:instructions
@@ -167,11 +158,6 @@ @implementation RCTSurfacePresenter (Deprecated)
   return _scheduler.uiManager_DO_NOT_USE;
 }
 
-- (std::shared_ptr<facebook::react::ExceptionManager>)exceptionManager_DO_NOT_USE
-{
-  return _exceptionManager;
-}
-
 @end
 
 @implementation RCTBridge (RCTSurfacePresenter)
diff --git a/ReactCommon/exceptions/BUCK b/ReactCommon/exceptions/BUCK
deleted file mode 100644
index 6f1ef1bb933b..000000000000
--- a/ReactCommon/exceptions/BUCK
+++ /dev/null
@@ -1,40 +0,0 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
-
-rn_xplat_cxx_library(
-    name = "exceptions",
-    srcs = glob(["*.cpp"]),
-    header_namespace = "",
-    exported_headers = subdir_glob(
-        [
-            ("", "*.h"),
-        ],
-        prefix = "cxxreact",
-    ),
-    compiler_flags = [
-        "-fexceptions",
-        "-frtti",
-        "-std=c++14",
-        "-Wall",
-    ],
-    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
-    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
-    force_static = True,
-    preprocessor_flags = [
-        "-DLOG_TAG=\"ReactNative\"",
-        "-DWITH_FBSYSTRACE=1",
-    ],
-    visibility = [
-        "PUBLIC",
-    ],
-    deps = [
-        "xplat//fbsystrace:fbsystrace",
-        "xplat//third-party/glog:glog",
-    ],
-)
diff --git a/ReactCommon/exceptions/ExceptionManager.h b/ReactCommon/exceptions/ExceptionManager.h
deleted file mode 100644
index 278179c67dec..000000000000
--- a/ReactCommon/exceptions/ExceptionManager.h
+++ /dev/null
@@ -1,28 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-#include <exception>
-
-namespace facebook {
-namespace react {
-
-/**
- * An abstract class for C++-based exception handling that differentiates
- * soft exceptions from fatal exceptions.
- */
-class ExceptionManager {
-public:
-  virtual ~ExceptionManager() = default;
-
-  virtual void handleSoftException(const std::exception &e) const = 0;
-  virtual void handleFatalException(const std::exception &e) const = 0;
-};
-
-} // namespace react
-} // namespace facebook

From ffe6c110f7ce33460fe0399ccbda16a6adbe90ca Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Mon, 14 May 2018 23:30:53 -0700
Subject: [PATCH 0583/1109] Fix keyboard handling with
 keyboardShouldPersistTaps: never

Summary:
When `keyboardShouldPersistTaps` is `"never"` it would break when doing the following steps:

- Tap input 1, keyboard goes up
- Tap input 2, keyboard stays down (The bug I expected without the isTextInput check was that it would dismiss instead :o )
- Tap outside, keyboard stays down. It should dismiss here since it should never persist taps (unless tapping another input)

What seems to happen is that RN `currentlyFocusedTextInput` goes out of sync with the focused text input and is null even if there is still a text input focused. I haven't had time to investigate the cause of that (probably some race condition because of trying to focus and blur at the same time) but we should not try to dismiss the keyboard when tapping another TextInput in the first place.

I reproduced the bug mentioned by setting `keyboardShouldPersistTaps` to `"never"` in RNTesterPage.js and then using the steps described above. I made sure that the bug did not happen after this change.

[GENERAL][BUGFIX][ScrollResponder] - Fix keyboard handling with keyboardShouldPersistTaps: never
Closes https://github.com/facebook/react-native/pull/19255

Differential Revision: D8002818

Pulled By: mdvacca

fbshipit-source-id: 6ecb8d2c30eb9338529471a958b5dc04037c7ec6
---
 Libraries/Components/ScrollResponder.js | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/ScrollResponder.js b/Libraries/Components/ScrollResponder.js
index ab388a31083f..548efba80da4 100644
--- a/Libraries/Components/ScrollResponder.js
+++ b/Libraries/Components/ScrollResponder.js
@@ -207,8 +207,8 @@ const ScrollResponderMixin = {
       !keyboardShouldPersistTaps || keyboardShouldPersistTaps === 'never';
     if (
       keyboardNeverPersistTaps &&
-      currentlyFocusedTextInput != null
-      /* && !TextInputState.isTextInput(e.target) */
+      currentlyFocusedTextInput != null &&
+      !TextInputState.isTextInput(e.target)
     ) {
       return true;
     }

From 803afd8430a87aff0f4aa8d66e5a2905db7d8c36 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 15 May 2018 02:40:35 -0700
Subject: [PATCH 0584/1109] Bump metro@0.37.0

Reviewed By: jeanlauliac

Differential Revision: D7988114

fbshipit-source-id: aeaed94cb89a929ab5079af957bfccd9fd7ebd83
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 5ec4680e8f1e..1229456241e8 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.36.1",
-    "metro-babel-register": "^0.36.1",
-    "metro-core": "^0.36.1",
-    "metro-memory-fs": "^0.36.1",
+    "metro": "^0.37.0",
+    "metro-babel-register": "^0.37.0",
+    "metro-core": "^0.37.0",
+    "metro-memory-fs": "^0.37.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From a3931e95317acaff5ceb1d2fb0f26ae67744c8a3 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Tue, 15 May 2018 09:22:31 -0700
Subject: [PATCH 0585/1109] android compileSdkVersion 26, use buildToolsVersion
 26.0.3

Summary:
Starting August 2018, Google Play will require targetSdkVersion 26 for new applications, and November 2018 for application updates.

This PR will use Android build tools 26.0.3 and compilerSdk 26, then support library version 26.0.2 to make targeting 26 easier in the future.

I think this PR will help to people compile and test their applications, thus make transition easier (smoother). Also we'll have opportunity and time to migrate code to target 26.

https://github.com/facebook/react-native/issues/18095

React Native on android must work as usual

Closes https://github.com/facebook/react-native/pull/19257

Differential Revision: D8010354

Pulled By: mdvacca

fbshipit-source-id: 63ba03585e918b38c2a2adb5d2f2e85d7ce46fae
---
 RNTester/android/app/build.gradle                       | 6 +++---
 ReactAndroid/build.gradle                               | 6 +++---
 local-cli/templates/HelloWorld/android/app/build.gradle | 6 +++---
 local-cli/templates/HelloWorld/android/build.gradle     | 8 ++++++++
 4 files changed, 17 insertions(+), 9 deletions(-)

diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index 5e5503b5eb7c..c1149e6a5e6f 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -84,8 +84,8 @@ def enableSeparateBuildPerCPUArchitecture = false
 def enableProguardInReleaseBuilds = false
 
 android {
-    compileSdkVersion 23
-    buildToolsVersion "23.0.1"
+    compileSdkVersion 26
+    buildToolsVersion "26.0.3"
 
     defaultConfig {
         applicationId "com.facebook.react.uiapp"
@@ -137,7 +137,7 @@ android {
 
 dependencies {
     compile fileTree(dir: 'libs', include: ['*.jar'])
-    compile 'com.android.support:appcompat-v7:23.0.1'
+    compile 'com.android.support:appcompat-v7:26.0.2'
 
     // Build React Native from source
     compile project(':ReactAndroid')
diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 503b814f32ac..29fdcd6aae65 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -242,8 +242,8 @@ task packageReactNdkLibsForBuck(dependsOn: packageReactNdkLibs, type: Copy) {
 }
 
 android {
-    compileSdkVersion 23
-    buildToolsVersion "23.0.1"
+    compileSdkVersion 26
+    buildToolsVersion "26.0.3"
 
     defaultConfig {
         minSdkVersion 16
@@ -292,7 +292,7 @@ android {
 dependencies {
     compile fileTree(dir: 'src/main/third-party/java/infer-annotations/', include: ['*.jar'])
     compile 'javax.inject:javax.inject:1'
-    compile 'com.android.support:appcompat-v7:23.0.1'
+    compile 'com.android.support:appcompat-v7:26.0.2'
     compile 'com.facebook.fbui.textlayoutbuilder:textlayoutbuilder:1.0.0'
     compile 'com.facebook.fresco:fresco:1.9.0'
     compile 'com.facebook.fresco:imagepipeline-okhttp3:1.9.0'
diff --git a/local-cli/templates/HelloWorld/android/app/build.gradle b/local-cli/templates/HelloWorld/android/app/build.gradle
index ec6f3022572a..f9f5ebc2bb39 100644
--- a/local-cli/templates/HelloWorld/android/app/build.gradle
+++ b/local-cli/templates/HelloWorld/android/app/build.gradle
@@ -94,8 +94,8 @@ def enableSeparateBuildPerCPUArchitecture = false
 def enableProguardInReleaseBuilds = false
 
 android {
-    compileSdkVersion 23
-    buildToolsVersion "23.0.1"
+    compileSdkVersion 26
+    buildToolsVersion "26.0.3"
 
     defaultConfig {
         applicationId "com.helloworld"
@@ -138,7 +138,7 @@ android {
 
 dependencies {
     compile fileTree(dir: "libs", include: ["*.jar"])
-    compile "com.android.support:appcompat-v7:23.0.1"
+    compile "com.android.support:appcompat-v7:26.0.2"
     compile "com.facebook.react:react-native:+"  // From node_modules
 }
 
diff --git a/local-cli/templates/HelloWorld/android/build.gradle b/local-cli/templates/HelloWorld/android/build.gradle
index eed9972b5c13..8bd0ba32b04f 100644
--- a/local-cli/templates/HelloWorld/android/build.gradle
+++ b/local-cli/templates/HelloWorld/android/build.gradle
@@ -3,6 +3,10 @@
 buildscript {
     repositories {
         jcenter()
+        maven {
+            url 'https://maven.google.com/'
+            name 'Google'
+        }
     }
     dependencies {
         classpath 'com.android.tools.build:gradle:2.2.3'
@@ -16,6 +20,10 @@ allprojects {
     repositories {
         mavenLocal()
         jcenter()
+        maven {
+            url 'https://maven.google.com/'
+            name 'Google'
+        }
         maven {
             // All of React Native (JS, Obj-C sources, Android binaries) is installed from npm
             url "$rootDir/../node_modules/react-native/android"

From 4a0243fcd3ad2b90ccf81ae15666f6323a3b264a Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 15 May 2018 09:25:40 -0700
Subject: [PATCH 0586/1109] iOS: whitelist a few components for testing purpose

Reviewed By: mmmulani

Differential Revision: D7999459

fbshipit-source-id: e56946931997cb51ee66020a97c60f3c85d1d348
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index b9a5cd57fcb7..4c6c1efe2279 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -66,6 +66,14 @@ static const std::string componentNameByReactViewName(std::string viewName) {
     return "View";
   }
 
+  // Other temporary fallback until the native components are implemented.
+  if (
+    viewName == "ActivityIndicatorView" ||
+    viewName == "ShimmeringView"
+  ) {
+    return "View";
+  }
+
   return viewName;
 }
 

From 70066ecd2bbb06fb23de2add5e59c1332c5e33a6 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 15 May 2018 13:08:46 -0700
Subject: [PATCH 0587/1109] RN: Remove ReactPerf References

Reviewed By: fkgozali

Differential Revision: D8002194

fbshipit-source-id: a60073698d0f348d788b5c67e1c1c0010f7ec7f1
---
 .../Interaction/InteractionStallDebugger.js   |  6 +---
 .../Interaction/ReactPerfStallHandler.js      | 34 -------------------
 2 files changed, 1 insertion(+), 39 deletions(-)
 delete mode 100644 Libraries/Interaction/ReactPerfStallHandler.js

diff --git a/Libraries/Interaction/InteractionStallDebugger.js b/Libraries/Interaction/InteractionStallDebugger.js
index 192d1eeed83e..899eee0ec114 100644
--- a/Libraries/Interaction/InteractionStallDebugger.js
+++ b/Libraries/Interaction/InteractionStallDebugger.js
@@ -12,15 +12,11 @@
 
 const BridgeSpyStallHandler = require('BridgeSpyStallHandler');
 const JSEventLoopWatchdog = require('JSEventLoopWatchdog');
-const ReactPerfStallHandler = require('ReactPerfStallHandler');
 
 const InteractionStallDebugger = {
-  install: function(options: {thresholdMS: number}) {
+  install(options: {thresholdMS: number}): void {
     JSEventLoopWatchdog.install(options);
     BridgeSpyStallHandler.register();
-    if (__DEV__) {
-      ReactPerfStallHandler.register();
-    }
   },
 };
 
diff --git a/Libraries/Interaction/ReactPerfStallHandler.js b/Libraries/Interaction/ReactPerfStallHandler.js
deleted file mode 100644
index bdeaed21d0e4..000000000000
--- a/Libraries/Interaction/ReactPerfStallHandler.js
+++ /dev/null
@@ -1,34 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- * @flow
- */
-
-'use strict';
-
-const JSEventLoopWatchdog = require('JSEventLoopWatchdog');
-const ReactPerf = require('ReactPerf');
-
-const ReactPerfStallHandler = {
-  register: function() {
-    ReactPerf.start();
-    JSEventLoopWatchdog.addHandler({
-      onStall: () => {
-        ReactPerf.stop();
-        ReactPerf.printInclusive();
-        ReactPerf.printWasted();
-        ReactPerf.start();
-      },
-      onIterate: () => {
-        ReactPerf.stop();
-        ReactPerf.start();
-      },
-    });
-  },
-};
-
-module.exports = ReactPerfStallHandler;

From 83169c95a3525fcb74e34853022475093b9a1a77 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 15 May 2018 13:08:47 -0700
Subject: [PATCH 0588/1109] React sync for revisions 0887c7d...bde4b16

Reviewed By: fkgozali, acdlite

Differential Revision: D7999962

fbshipit-source-id: 8ef358574244bd76fe5a67a1781d59a70fc9c449
---
 Libraries/Renderer/REVISION                   |     2 +-
 Libraries/Renderer/oss/ReactFabric-dev.js     |  3518 ++--
 Libraries/Renderer/oss/ReactFabric-prod.js    |  2219 +--
 .../Renderer/oss/ReactNativeRenderer-dev.js   | 14477 ++++++++--------
 .../Renderer/oss/ReactNativeRenderer-prod.js  |  3458 ++--
 .../Renderer/shims/NativeMethodsMixin.js      |     1 +
 Libraries/Renderer/shims/ReactDebugTool.js    |    16 -
 Libraries/Renderer/shims/ReactFabric.js       |     2 +
 Libraries/Renderer/shims/ReactNative.js       |     2 +
 .../shims/ReactNativeComponentTree.js         |     1 +
 Libraries/Renderer/shims/ReactNativeTypes.js  |     2 +-
 .../shims/ReactNativeViewConfigRegistry.js    |     2 +
 Libraries/Renderer/shims/ReactPerf.js         |    15 -
 Libraries/Renderer/shims/ReactTypes.js        |     3 +
 .../shims/createReactNativeComponentClass.js  |     1 +
 package.json                                  |     2 +-
 16 files changed, 13052 insertions(+), 10669 deletions(-)
 delete mode 100644 Libraries/Renderer/shims/ReactDebugTool.js
 delete mode 100644 Libraries/Renderer/shims/ReactPerf.js

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index ba0ce2996c48..752ac5912cc5 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-0887c7d56cb9b83f36dcb490b4245d7bc33bda1f
\ No newline at end of file
+bde4b1659fd4aea796482f24d40c2e834fca635f
\ No newline at end of file
diff --git a/Libraries/Renderer/oss/ReactFabric-dev.js b/Libraries/Renderer/oss/ReactFabric-dev.js
index 0424315c8ed6..d4a4d86b2bd4 100644
--- a/Libraries/Renderer/oss/ReactFabric-dev.js
+++ b/Libraries/Renderer/oss/ReactFabric-dev.js
@@ -5,7 +5,9 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
+ * @providesModule ReactFabric-dev
  * @preventMunge
+ * @generated
  */
 
 'use strict';
@@ -25,8 +27,9 @@ var deepDiffer = require("deepDiffer");
 var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
-var shallowEqual = require("fbjs/lib/shallowEqual");
 var checkPropTypes = require("prop-types/checkPropTypes");
+var shallowEqual = require("fbjs/lib/shallowEqual");
+var ExceptionsManager = require("ExceptionsManager");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
 var FabricUIManager = require("FabricUIManager");
 
@@ -812,10 +815,12 @@ var Mode = 11;
 var ContextConsumer = 12;
 var ContextProvider = 13;
 var ForwardRef = 14;
+var Profiler = 15;
+var TimeoutComponent = 16;
 
 function getParent(inst) {
   do {
-    inst = inst["return"];
+    inst = inst.return;
     // TODO: If this is a HostRoot we might want to bail out.
     // That is depending on if we want nested subtrees (layers) to bubble
     // events to their parent. We could also go through parentNode on the
@@ -2312,24 +2317,24 @@ injection.injectEventPluginsByName({
 
 // The Symbol used to tag the ReactElement-like types. If there is no native Symbol
 // nor polyfill, then a plain number is used for performance.
-var hasSymbol = typeof Symbol === "function" && Symbol["for"];
+var hasSymbol = typeof Symbol === "function" && Symbol.for;
 
-var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
-var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
-var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 0xeac7;
+var REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 0xeac8;
+var REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 0xeac9;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.strict_mode")
+  ? Symbol.for("react.strict_mode")
   : 0xeacc;
-var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
-var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
-var REACT_ASYNC_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.async_mode")
-  : 0xeacf;
+var REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profile_root") : 0xeacc;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 0xeace;
+var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 0xeacf;
 var REACT_FORWARD_REF_TYPE = hasSymbol
-  ? Symbol["for"]("react.forward_ref")
+  ? Symbol.for("react.forward_ref")
   : 0xead0;
+var REACT_TIMEOUT_TYPE = hasSymbol ? Symbol.for("react.timeout") : 0xead1;
 
 var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
 var FAUX_ITERATOR_SYMBOL = "@@iterator";
@@ -3289,55 +3294,6 @@ var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
   return ReactNativeComponent;
 };
 
-var hasNativePerformanceNow =
-  typeof performance === "object" && typeof performance.now === "function";
-
-var now = hasNativePerformanceNow
-  ? function() {
-      return performance.now();
-    }
-  : function() {
-      return Date.now();
-    };
-
-var scheduledCallback = null;
-var frameDeadline = 0;
-
-var frameDeadlineObject = {
-  timeRemaining: function() {
-    return frameDeadline - now();
-  },
-  didTimeout: false
-};
-
-function setTimeoutCallback() {
-  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
-  // React API probably changing to boolean rather than time remaining.
-  // Longer-term plan is to rewrite this using shared memory,
-  // And just return the value of the bit as the boolean.
-  frameDeadline = now() + 5;
-
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  if (callback !== null) {
-    callback(frameDeadlineObject);
-  }
-}
-
-// RN has a poor polyfill for requestIdleCallback so we aren't using it.
-// This implementation is only intended for short-term use anyway.
-// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
-function scheduleDeferredCallback(callback) {
-  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
-  scheduledCallback = callback;
-  return setTimeout(setTimeoutCallback, 1);
-}
-
-function cancelDeferredCallback(callbackID) {
-  scheduledCallback = null;
-  clearTimeout(callbackID);
-}
-
 /**
  * `ReactInstanceMap` maintains a mapping from a public facing stateful
  * instance (key) and the internal representation (value). This allows public
@@ -3377,14 +3333,24 @@ function getComponentName(fiber) {
     return type;
   }
   switch (type) {
+    case REACT_ASYNC_MODE_TYPE:
+      return "AsyncMode";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_CONTEXT_TYPE:
+      return "Context.Consumer";
     case REACT_FRAGMENT_TYPE:
       return "ReactFragment";
     case REACT_PORTAL_TYPE:
       return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
+    case REACT_PROFILER_TYPE:
+      return "Profiler(" + fiber.pendingProps.id + ")";
+    case REACT_PROVIDER_TYPE:
+      return "Context.Provider";
     case REACT_RETURN_TYPE:
       return "ReactReturn";
+    case REACT_STRICT_MODE_TYPE:
+      return "StrictMode";
   }
   if (typeof type === "object" && type !== null) {
     switch (type.$$typeof) {
@@ -3411,11 +3377,10 @@ var ContentReset = /*          */ 16;
 var Callback = /*              */ 32;
 var DidCapture = /*            */ 64;
 var Ref = /*                   */ 128;
-var ErrLog = /*                */ 256;
-var Snapshot = /*              */ 2048;
+var Snapshot = /*              */ 256;
 
 // Union of all host effects
-var HostEffectMask = /*        */ 2559;
+var HostEffectMask = /*        */ 511;
 
 var Incomplete = /*            */ 512;
 var ShouldCapture = /*         */ 1024;
@@ -3432,15 +3397,15 @@ function isFiberMountedImpl(fiber) {
     if ((node.effectTag & Placement) !== NoEffect) {
       return MOUNTING;
     }
-    while (node["return"]) {
-      node = node["return"];
+    while (node.return) {
+      node = node.return;
       if ((node.effectTag & Placement) !== NoEffect) {
         return MOUNTING;
       }
     }
   } else {
-    while (node["return"]) {
-      node = node["return"];
+    while (node.return) {
+      node = node.return;
     }
   }
   if (node.tag === HostRoot) {
@@ -3512,7 +3477,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
   var a = fiber;
   var b = alternate;
   while (true) {
-    var parentA = a["return"];
+    var parentA = a.return;
     var parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) {
       // We're at the root.
@@ -3542,7 +3507,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       invariant(false, "Unable to find node on an unmounted component.");
     }
 
-    if (a["return"] !== b["return"]) {
+    if (a.return !== b.return) {
       // The return pointer of A and the return pointer of B point to different
       // fibers. We assume that return pointers never criss-cross, so A must
       // belong to the child set of A.return, and B must belong to the child
@@ -3630,7 +3595,7 @@ function findCurrentHostFiber(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child) {
-      node.child["return"] = node;
+      node.child.return = node;
       node = node.child;
       continue;
     }
@@ -3638,12 +3603,12 @@ function findCurrentHostFiber(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
+      if (!node.return || node.return === currentParent) {
         return null;
       }
-      node = node["return"];
+      node = node.return;
     }
-    node.sibling["return"] = node["return"];
+    node.sibling.return = node.return;
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -3663,7 +3628,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
     if (node.tag === HostComponent || node.tag === HostText) {
       return node;
     } else if (node.child && node.tag !== HostPortal) {
-      node.child["return"] = node;
+      node.child.return = node;
       node = node.child;
       continue;
     }
@@ -3671,12 +3636,12 @@ function findCurrentHostFiberWithNoPortals(parent) {
       return null;
     }
     while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
+      if (!node.return || node.return === currentParent) {
         return null;
       }
-      node = node["return"];
+      node = node.return;
     }
-    node.sibling["return"] = node["return"];
+    node.sibling.return = node.return;
     node = node.sibling;
   }
   // Flow needs the return null here, but ESLint complains about it.
@@ -3684,6 +3649,23 @@ function findCurrentHostFiberWithNoPortals(parent) {
   return null;
 }
 
+var debugRenderPhaseSideEffects = false;
+var debugRenderPhaseSideEffectsForStrictMode = false;
+var enableUserTimingAPI = true;
+var enableGetDerivedStateFromCatch = false;
+var enableSuspense = false;
+var warnAboutDeprecatedLifecycles = false;
+var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
+var enableProfilerTimer = false;
+
+// React Fabric uses persistent reconciler.
+var enableMutatingReconciler = false;
+var enableNoopReconciler = false;
+var enablePersistentReconciler = true;
+var fireGetDerivedStateFromPropsOnStateUpdates = true;
+
+// Only used in www builds.
+
 // Max 31 bit integer. The max integer size in V8 for 32-bit systems.
 // Math.pow(2, 30) - 1
 // 0b111111111111111111111111111111
@@ -3713,15 +3695,19 @@ function ceiling(num, precision) {
 }
 
 function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
-  return ceiling(
-    currentTime + expirationInMs / UNIT_SIZE,
-    bucketSizeMs / UNIT_SIZE
+  return (
+    MAGIC_NUMBER_OFFSET +
+    ceiling(
+      currentTime - MAGIC_NUMBER_OFFSET + expirationInMs / UNIT_SIZE,
+      bucketSizeMs / UNIT_SIZE
+    )
   );
 }
 
 var NoContext = 0;
 var AsyncMode = 1;
 var StrictMode = 2;
+var ProfileMode = 4;
 
 var hasBadMapPolyfill = void 0;
 
@@ -3759,7 +3745,7 @@ function FiberNode(tag, pendingProps, key, mode) {
   this.stateNode = null;
 
   // Fiber
-  this["return"] = null;
+  this.return = null;
   this.child = null;
   this.sibling = null;
   this.index = 0;
@@ -3784,6 +3770,11 @@ function FiberNode(tag, pendingProps, key, mode) {
 
   this.alternate = null;
 
+  if (enableProfilerTimer) {
+    this.selfBaseTime = 0;
+    this.treeBaseTime = 0;
+  }
+
   {
     this._debugID = debugCounter++;
     this._debugSource = null;
@@ -3869,6 +3860,11 @@ function createWorkInProgress(current, pendingProps, expirationTime) {
   workInProgress.index = current.index;
   workInProgress.ref = current.ref;
 
+  if (enableProfilerTimer) {
+    workInProgress.selfBaseTime = current.selfBaseTime;
+    workInProgress.treeBaseTime = current.treeBaseTime;
+  }
+
   return workInProgress;
 }
 
@@ -3910,12 +3906,20 @@ function createFiberFromElement(element, mode, expirationTime) {
         fiberTag = Mode;
         mode |= StrictMode;
         break;
+      case REACT_PROFILER_TYPE:
+        return createFiberFromProfiler(pendingProps, mode, expirationTime, key);
       case REACT_CALL_TYPE:
         fiberTag = CallComponent;
         break;
       case REACT_RETURN_TYPE:
         fiberTag = ReturnComponent;
         break;
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = TimeoutComponent;
+        // Suspense does not require async, but its children should be strict
+        // mode compatible.
+        mode |= StrictMode;
+        break;
       default: {
         if (typeof type === "object" && type !== null) {
           switch (type.$$typeof) {
@@ -4002,6 +4006,30 @@ function createFiberFromFragment(elements, mode, expirationTime, key) {
   return fiber;
 }
 
+function createFiberFromProfiler(pendingProps, mode, expirationTime, key) {
+  {
+    if (
+      typeof pendingProps.id !== "string" ||
+      typeof pendingProps.onRender !== "function"
+    ) {
+      invariant(
+        false,
+        'Profiler must specify an "id" string and "onRender" function as props'
+      );
+    }
+  }
+
+  var fiber = createFiber(Profiler, pendingProps, key, mode | ProfileMode);
+  fiber.type = REACT_PROFILER_TYPE;
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    duration: 0,
+    startTime: 0
+  };
+
+  return fiber;
+}
+
 function createFiberFromText(content, mode, expirationTime) {
   var fiber = createFiber(HostText, content, null, mode);
   fiber.expirationTime = expirationTime;
@@ -4044,7 +4072,7 @@ function assignFiberPropertiesInDEV(target, source) {
   target.key = source.key;
   target.type = source.type;
   target.stateNode = source.stateNode;
-  target["return"] = source["return"];
+  target.return = source.return;
   target.child = source.child;
   target.sibling = source.sibling;
   target.index = source.index;
@@ -4060,6 +4088,10 @@ function assignFiberPropertiesInDEV(target, source) {
   target.lastEffect = source.lastEffect;
   target.expirationTime = source.expirationTime;
   target.alternate = source.alternate;
+  if (enableProfilerTimer) {
+    target.selfBaseTime = source.selfBaseTime;
+    target.treeBaseTime = source.treeBaseTime;
+  }
   target._debugID = source._debugID;
   target._debugSource = source._debugSource;
   target._debugOwner = source._debugOwner;
@@ -4077,6 +4109,13 @@ function createFiberRoot(containerInfo, isAsync, hydrate) {
     current: uninitializedFiber,
     containerInfo: containerInfo,
     pendingChildren: null,
+
+    earliestPendingTime: NoWork,
+    latestPendingTime: NoWork,
+    earliestSuspendedTime: NoWork,
+    latestSuspendedTime: NoWork,
+    latestPingedTime: NoWork,
+
     pendingCommitExpirationTime: NoWork,
     finishedWork: null,
     context: null,
@@ -4204,7 +4243,7 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
   do {
     info += describeFiber(node);
     // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
+    node = node.return;
   } while (node);
   return info;
 }
@@ -4374,7 +4413,7 @@ var ReactStrictModeWarnings = {
         maybeStrictRoot = fiber;
       }
 
-      fiber = fiber["return"];
+      fiber = fiber.return;
     }
 
     return maybeStrictRoot;
@@ -4495,16 +4534,6 @@ var ReactStrictModeWarnings = {
       return;
     }
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    // Note that it is sufficient to check for the presence of a
-    // single lifecycle, componentWillMount, with the polyfill flag.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning === true
-    ) {
-      return;
-    }
-
     var warningsForRoot = void 0;
     if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
       warningsForRoot = {
@@ -4520,19 +4549,23 @@ var ReactStrictModeWarnings = {
 
     var unsafeLifecycles = [];
     if (
-      typeof instance.componentWillMount === "function" ||
+      (typeof instance.componentWillMount === "function" &&
+        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
       typeof instance.UNSAFE_componentWillMount === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillMount");
     }
     if (
-      typeof instance.componentWillReceiveProps === "function" ||
+      (typeof instance.componentWillReceiveProps === "function" &&
+        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+          true) ||
       typeof instance.UNSAFE_componentWillReceiveProps === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
     }
     if (
-      typeof instance.componentWillUpdate === "function" ||
+      (typeof instance.componentWillUpdate === "function" &&
+        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
       typeof instance.UNSAFE_componentWillUpdate === "function"
     ) {
       unsafeLifecycles.push("UNSAFE_componentWillUpdate");
@@ -4546,19 +4579,127 @@ var ReactStrictModeWarnings = {
   };
 }
 
-var debugRenderPhaseSideEffects = false;
-var debugRenderPhaseSideEffectsForStrictMode = false;
-var enableUserTimingAPI = true;
-var enableGetDerivedStateFromCatch = false;
-var warnAboutDeprecatedLifecycles = false;
-var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
+/**
+ * The "actual" render time is total time required to render the descendants of a Profiler component.
+ * This time is stored as a stack, since Profilers can be nested.
+ * This time is started during the "begin" phase and stopped during the "complete" phase.
+ * It is paused (and accumulated) in the event of an interruption or an aborted render.
+ */
 
-// React Fabric uses persistent reconciler.
-var enableMutatingReconciler = false;
-var enableNoopReconciler = false;
-var enablePersistentReconciler = true;
+function createProfilerTimer(now) {
+  var fiberStack = void 0;
 
-// Only used in www builds.
+  {
+    fiberStack = [];
+  }
+
+  var timerPausedAt = 0;
+  var totalElapsedPauseTime = 0;
+
+  function checkActualRenderTimeStackEmpty() {
+    {
+      !(fiberStack.length === 0)
+        ? warning(
+            false,
+            "Expected an empty stack. Something was not reset properly."
+          )
+        : void 0;
+    }
+  }
+
+  function markActualRenderTimeStarted(fiber) {
+    {
+      fiberStack.push(fiber);
+    }
+    fiber.stateNode.startTime = now() - totalElapsedPauseTime;
+  }
+
+  function pauseActualRenderTimerIfRunning() {
+    if (timerPausedAt === 0) {
+      timerPausedAt = now();
+    }
+  }
+
+  function recordElapsedActualRenderTime(fiber) {
+    {
+      !(fiber === fiberStack.pop())
+        ? warning(false, "Unexpected Fiber popped.")
+        : void 0;
+    }
+    fiber.stateNode.duration +=
+      now() - totalElapsedPauseTime - fiber.stateNode.startTime;
+  }
+
+  function resetActualRenderTimer() {
+    totalElapsedPauseTime = 0;
+  }
+
+  function resumeActualRenderTimerIfPaused() {
+    if (timerPausedAt > 0) {
+      totalElapsedPauseTime += now() - timerPausedAt;
+      timerPausedAt = 0;
+    }
+  }
+
+  /**
+   * The "base" render time is the duration of the “begin” phase of work for a particular fiber.
+   * This time is measured and stored on each fiber.
+   * The time for all sibling fibers are accumulated and stored on their parent during the "complete" phase.
+   * If a fiber bails out (sCU false) then its "base" timer is cancelled and the fiber is not updated.
+   */
+
+  var baseStartTime = -1;
+
+  function recordElapsedBaseRenderTimeIfRunning(fiber) {
+    if (baseStartTime !== -1) {
+      fiber.selfBaseTime = now() - baseStartTime;
+    }
+  }
+
+  function startBaseRenderTimer() {
+    {
+      if (baseStartTime !== -1) {
+        warning(
+          false,
+          "Cannot start base timer that is already running. " +
+            "This error is likely caused by a bug in React. " +
+            "Please file an issue."
+        );
+      }
+    }
+    baseStartTime = now();
+  }
+
+  function stopBaseRenderTimerIfRunning() {
+    baseStartTime = -1;
+  }
+
+  if (enableProfilerTimer) {
+    return {
+      checkActualRenderTimeStackEmpty: checkActualRenderTimeStackEmpty,
+      markActualRenderTimeStarted: markActualRenderTimeStarted,
+      pauseActualRenderTimerIfRunning: pauseActualRenderTimerIfRunning,
+      recordElapsedActualRenderTime: recordElapsedActualRenderTime,
+      resetActualRenderTimer: resetActualRenderTimer,
+      resumeActualRenderTimerIfPaused: resumeActualRenderTimerIfPaused,
+      recordElapsedBaseRenderTimeIfRunning: recordElapsedBaseRenderTimeIfRunning,
+      startBaseRenderTimer: startBaseRenderTimer,
+      stopBaseRenderTimerIfRunning: stopBaseRenderTimerIfRunning
+    };
+  } else {
+    return {
+      checkActualRenderTimeStackEmpty: function() {},
+      markActualRenderTimeStarted: function(fiber) {},
+      pauseActualRenderTimerIfRunning: function() {},
+      recordElapsedActualRenderTime: function(fiber) {},
+      resetActualRenderTimer: function() {},
+      resumeActualRenderTimerIfPaused: function() {},
+      recordElapsedBaseRenderTimeIfRunning: function(fiber) {},
+      startBaseRenderTimer: function() {},
+      stopBaseRenderTimerIfRunning: function() {}
+    };
+  }
+}
 
 function getCurrentFiberOwnerName() {
   {
@@ -4574,7 +4715,7 @@ function getCurrentFiberOwnerName() {
   return null;
 }
 
-function getCurrentFiberStackAddendum() {
+function getCurrentFiberStackAddendum$1() {
   {
     var fiber = ReactDebugCurrentFiber.current;
     if (fiber === null) {
@@ -4594,7 +4735,7 @@ function resetCurrentFiber() {
 }
 
 function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum$1;
   ReactDebugCurrentFiber.current = fiber;
   ReactDebugCurrentFiber.phase = null;
 }
@@ -4610,7 +4751,7 @@ var ReactDebugCurrentFiber = {
   setCurrentFiber: setCurrentFiber,
   setCurrentPhase: setCurrentPhase,
   getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum$1
 };
 
 // Prefix measurements so that it's possible to filter them.
@@ -4767,13 +4908,13 @@ var pauseTimers = function() {
     if (fiber._debugIsCurrentlyTiming) {
       endFiberMark(fiber, null, null);
     }
-    fiber = fiber["return"];
+    fiber = fiber.return;
   }
 };
 
 var resumeTimersRecursively = function(fiber) {
-  if (fiber["return"] !== null) {
-    resumeTimersRecursively(fiber["return"]);
+  if (fiber.return !== null) {
+    resumeTimersRecursively(fiber.return);
   }
   if (fiber._debugIsCurrentlyTiming) {
     beginFiberMark(fiber, null);
@@ -4865,7 +5006,7 @@ function stopWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
+    currentFiber = fiber.return;
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -4880,7 +5021,7 @@ function stopFailedWorkTimer(fiber) {
       return;
     }
     // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
+    currentFiber = fiber.return;
     if (!fiber._debugIsCurrentlyTiming) {
       return;
     }
@@ -5070,100 +5211,234 @@ function stopCommitLifeCyclesTimer() {
   }
 }
 
-var didWarnUpdateInsideUpdate = void 0;
+// UpdateQueue is a linked list of prioritized updates.
+//
+// Like fibers, update queues come in pairs: a current queue, which represents
+// the visible state of the screen, and a work-in-progress queue, which is
+// can be mutated and processed asynchronously before it is committed — a form
+// of double buffering. If a work-in-progress render is discarded before
+// finishing, we create a new work-in-progress by cloning the current queue.
+//
+// Both queues share a persistent, singly-linked list structure. To schedule an
+// update, we append it to the end of both queues. Each queue maintains a
+// pointer to first update in the persistent list that hasn't been processed.
+// The work-in-progress pointer always has a position equal to or greater than
+// the current queue, since we always work on that one. The current queue's
+// pointer is only updated during the commit phase, when we swap in the
+// work-in-progress.
+//
+// For example:
+//
+//   Current pointer:           A - B - C - D - E - F
+//   Work-in-progress pointer:              D - E - F
+//                                          ^
+//                                          The work-in-progress queue has
+//                                          processed more updates than current.
+//
+// The reason we append to both queues is because otherwise we might drop
+// updates without ever processing them. For example, if we only add updates to
+// the work-in-progress queue, some updates could be lost whenever a work-in
+// -progress render restarts by cloning from current. Similarly, if we only add
+// updates to the current queue, the updates will be lost whenever an already
+// in-progress queue commits and swaps with the current queue. However, by
+// adding to both queues, we guarantee that the update will be part of the next
+// work-in-progress. (And because the work-in-progress queue becomes the
+// current queue once it commits, there's no danger of applying the same
+// update twice.)
+//
+// Prioritization
+// --------------
+//
+// Updates are not sorted by priority, but by insertion; new updates are always
+// appended to the end of the list.
+//
+// The priority is still important, though. When processing the update queue
+// during the render phase, only the updates with sufficient priority are
+// included in the result. If we skip an update because it has insufficient
+// priority, it remains in the queue to be processed later, during a lower
+// priority render. Crucially, all updates subsequent to a skipped update also
+// remain in the queue *regardless of their priority*. That means high priority
+// updates are sometimes processed twice, at two separate priorities. We also
+// keep track of a base state, that represents the state before the first
+// update in the queue is applied.
+//
+// For example:
+//
+//   Given a base state of '', and the following queue of updates
+//
+//     A1 - B2 - C1 - D2
+//
+//   where the number indicates the priority, and the update is applied to the
+//   previous state by appending a letter, React will process these updates as
+//   two separate renders, one per distinct priority level:
+//
+//   First render, at priority 1:
+//     Base state: ''
+//     Updates: [A1, C1]
+//     Result state: 'AC'
+//
+//   Second render, at priority 2:
+//     Base state: 'A'            <-  The base state does not include C1,
+//                                    because B2 was skipped.
+//     Updates: [B2, C1, D2]      <-  C1 was rebased on top of B2
+//     Result state: 'ABCD'
+//
+// Because we process updates in insertion order, and rebase high priority
+// updates when preceding updates are skipped, the final result is deterministic
+// regardless of priority. Intermediate state may vary according to system
+// resources, but the final state is always the same.
+
+var UpdateState = 0;
+var ReplaceState = 1;
+var ForceUpdate = 2;
+var CaptureUpdate = 3;
 
+// Global state that is reset at the beginning of calling `processUpdateQueue`.
+// It should only be read right after calling `processUpdateQueue`, via
+// `checkHasForceUpdateAfterProcessing`.
+var hasForceUpdate = false;
+
+var didWarnUpdateInsideUpdate = void 0;
+var currentlyProcessingQueue = void 0;
+var resetCurrentlyProcessingQueue = void 0;
 {
   didWarnUpdateInsideUpdate = false;
+  currentlyProcessingQueue = null;
+  resetCurrentlyProcessingQueue = function() {
+    currentlyProcessingQueue = null;
+  };
 }
 
-// Callbacks are not validated until invocation
-
-// Singly linked-list of updates. When an update is scheduled, it is added to
-// the queue of the current fiber and the work-in-progress fiber. The two queues
-// are separate but they share a persistent structure.
-//
-// During reconciliation, updates are removed from the work-in-progress fiber,
-// but they remain on the current fiber. That ensures that if a work-in-progress
-// is aborted, the aborted updates are recovered by cloning from current.
-//
-// The work-in-progress queue is always a subset of the current queue.
-//
-// When the tree is committed, the work-in-progress becomes the current.
-
 function createUpdateQueue(baseState) {
   var queue = {
-    baseState: baseState,
     expirationTime: NoWork,
-    first: null,
-    last: null,
-    callbackList: null,
-    hasForceUpdate: false,
-    isInitialized: false,
-    capturedValues: null
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+  return queue;
+}
+
+function cloneUpdateQueue(currentQueue) {
+  var queue = {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+
+    // TODO: With resuming, if we bail out and resuse the child tree, we should
+    // keep these effects.
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+
+    firstEffect: null,
+    lastEffect: null,
+
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
   };
-  {
-    queue.isProcessing = false;
-  }
   return queue;
 }
 
-function insertUpdateIntoQueue(queue, update) {
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+
+    tag: UpdateState,
+    payload: null,
+    callback: null,
+
+    next: null,
+    nextEffect: null
+  };
+}
+
+function appendUpdateToQueue(queue, update, expirationTime) {
   // Append the update to the end of the list.
-  if (queue.last === null) {
+  if (queue.lastUpdate === null) {
     // Queue is empty
-    queue.first = queue.last = update;
+    queue.firstUpdate = queue.lastUpdate = update;
   } else {
-    queue.last.next = update;
-    queue.last = update;
+    queue.lastUpdate.next = update;
+    queue.lastUpdate = update;
   }
   if (
     queue.expirationTime === NoWork ||
-    queue.expirationTime > update.expirationTime
+    queue.expirationTime > expirationTime
   ) {
-    queue.expirationTime = update.expirationTime;
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    queue.expirationTime = expirationTime;
   }
 }
 
-var q1 = void 0;
-var q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  // We'll have at least one and at most two distinct update queues.
-  var alternateFiber = fiber.alternate;
-  var queue1 = fiber.updateQueue;
-  if (queue1 === null) {
-    // TODO: We don't know what the base state will be until we begin work.
-    // It depends on which fiber is the next current. Initialize with an empty
-    // base state, then set to the memoizedState when rendering. Not super
-    // happy with this approach.
-    queue1 = fiber.updateQueue = createUpdateQueue(null);
-  }
-
+function enqueueUpdate(fiber, update, expirationTime) {
+  // Update queues are created lazily.
+  var alternate = fiber.alternate;
+  var queue1 = void 0;
   var queue2 = void 0;
-  if (alternateFiber !== null) {
-    queue2 = alternateFiber.updateQueue;
-    if (queue2 === null) {
-      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
+  if (alternate === null) {
+    // There's only one fiber.
+    queue1 = fiber.updateQueue;
+    queue2 = null;
+    if (queue1 === null) {
+      queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
     }
   } else {
-    queue2 = null;
+    // There are two owners.
+    queue1 = fiber.updateQueue;
+    queue2 = alternate.updateQueue;
+    if (queue1 === null) {
+      if (queue2 === null) {
+        // Neither fiber has an update queue. Create new ones.
+        queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
+        queue2 = alternate.updateQueue = createUpdateQueue(
+          alternate.memoizedState
+        );
+      } else {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue1 = fiber.updateQueue = cloneUpdateQueue(queue2);
+      }
+    } else {
+      if (queue2 === null) {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue2 = alternate.updateQueue = cloneUpdateQueue(queue1);
+      } else {
+        // Both owners have an update queue.
+      }
+    }
+  }
+  if (queue2 === null || queue1 === queue2) {
+    // There's only a single queue.
+    appendUpdateToQueue(queue1, update, expirationTime);
+  } else {
+    // There are two queues. We need to append the update to both queues,
+    // while accounting for the persistent structure of the list — we don't
+    // want the same update to be added multiple times.
+    if (queue1.lastUpdate === null || queue2.lastUpdate === null) {
+      // One of the queues is not empty. We must add the update to both queues.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      appendUpdateToQueue(queue2, update, expirationTime);
+    } else {
+      // Both queues are non-empty. The last update is the same in both lists,
+      // because of structural sharing. So, only append to one of the lists.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      // But we still need to update the `lastUpdate` pointer of queue2.
+      queue2.lastUpdate = update;
+    }
   }
-  queue2 = queue2 !== queue1 ? queue2 : null;
-
-  // Use module variables instead of returning a tuple
-  q1 = queue1;
-  q2 = queue2;
-}
-
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  var queue1 = q1;
-  var queue2 = q2;
 
-  // Warn if an update is scheduled from inside an updater function.
   {
     if (
-      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
+      fiber.tag === ClassComponent &&
+      (currentlyProcessingQueue === queue1 ||
+        (queue2 !== null && currentlyProcessingQueue === queue2)) &&
       !didWarnUpdateInsideUpdate
     ) {
       warning(
@@ -5176,225 +5451,338 @@ function insertUpdateIntoFiber(fiber, update) {
       didWarnUpdateInsideUpdate = true;
     }
   }
+}
 
-  // If there's only one queue, add the update to that queue and exit.
-  if (queue2 === null) {
-    insertUpdateIntoQueue(queue1, update);
-    return;
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  // Captured updates go into a separate list, and only on the work-in-
+  // progress queue.
+  var workInProgressQueue = workInProgress.updateQueue;
+  if (workInProgressQueue === null) {
+    workInProgressQueue = workInProgress.updateQueue = createUpdateQueue(
+      workInProgress.memoizedState
+    );
+  } else {
+    // TODO: I put this here rather than createWorkInProgress so that we don't
+    // clone the queue unnecessarily. There's probably a better way to
+    // structure this.
+    workInProgressQueue = ensureWorkInProgressQueueIsAClone(
+      workInProgress,
+      workInProgressQueue
+    );
   }
 
-  // If either queue is empty, we need to add to both queues.
-  if (queue1.last === null || queue2.last === null) {
-    insertUpdateIntoQueue(queue1, update);
-    insertUpdateIntoQueue(queue2, update);
-    return;
+  // Append the update to the end of the list.
+  if (workInProgressQueue.lastCapturedUpdate === null) {
+    // This is the first render phase update
+    workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update;
+  } else {
+    workInProgressQueue.lastCapturedUpdate.next = update;
+    workInProgressQueue.lastCapturedUpdate = update;
   }
-
-  // If both lists are not empty, the last update is the same for both lists
-  // because of structural sharing. So, we should only append to one of
-  // the lists.
-  insertUpdateIntoQueue(queue1, update);
-  // But we still need to update the `last` pointer of queue2.
-  queue2.last = update;
-}
-
-function getUpdateExpirationTime(fiber) {
-  switch (fiber.tag) {
-    case HostRoot:
-    case ClassComponent:
-      var updateQueue = fiber.updateQueue;
-      if (updateQueue === null) {
-        return NoWork;
-      }
-      return updateQueue.expirationTime;
-    default:
-      return NoWork;
+  if (
+    workInProgressQueue.expirationTime === NoWork ||
+    workInProgressQueue.expirationTime > renderExpirationTime
+  ) {
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    workInProgressQueue.expirationTime = renderExpirationTime;
   }
 }
 
-function getStateFromUpdate(update, instance, prevState, props) {
-  var partialState = update.partialState;
-  if (typeof partialState === "function") {
-    return partialState.call(instance, prevState, props);
-  } else {
-    return partialState;
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  if (current !== null) {
+    // If the work-in-progress queue is equal to the current queue,
+    // we need to clone it first.
+    if (queue === current.updateQueue) {
+      queue = workInProgress.updateQueue = cloneUpdateQueue(queue);
+    }
   }
+  return queue;
 }
 
-function processUpdateQueue(
-  current,
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case ReplaceState: {
+      var _payload = update.payload;
+      if (typeof _payload === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload.call(instance, prevState, nextProps);
+          }
+        }
+        return _payload.call(instance, prevState, nextProps);
+      }
+      // State object
+      return _payload;
+    }
+    case CaptureUpdate: {
+      workInProgress.effectTag =
+        (workInProgress.effectTag & ~ShouldCapture) | DidCapture;
+    }
+    // Intentional fallthrough
+    case UpdateState: {
+      var _payload2 = update.payload;
+      var partialState = void 0;
+      if (typeof _payload2 === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload2.call(instance, prevState, nextProps);
+          }
+        }
+        partialState = _payload2.call(instance, prevState, nextProps);
+      } else {
+        // Partial state object
+        partialState = _payload2;
+      }
+      if (partialState === null || partialState === undefined) {
+        // Null and undefined are treated as no-ops.
+        return prevState;
+      }
+      // Merge the partial state and the previous state.
+      return Object.assign({}, prevState, partialState);
+    }
+    case ForceUpdate: {
+      hasForceUpdate = true;
+      return prevState;
+    }
+  }
+  return prevState;
+}
+
+function processUpdateQueue(
   workInProgress,
   queue,
-  instance,
   props,
+  instance,
   renderExpirationTime
 ) {
-  if (current !== null && current.updateQueue === queue) {
-    // We need to create a work-in-progress queue, by cloning the current queue.
-    var currentQueue = queue;
-    queue = workInProgress.updateQueue = {
-      baseState: currentQueue.baseState,
-      expirationTime: currentQueue.expirationTime,
-      first: currentQueue.first,
-      last: currentQueue.last,
-      isInitialized: currentQueue.isInitialized,
-      capturedValues: currentQueue.capturedValues,
-      // These fields are no longer valid because they were already committed.
-      // Reset them.
-      callbackList: null,
-      hasForceUpdate: false
-    };
+  hasForceUpdate = false;
+
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > renderExpirationTime
+  ) {
+    // Insufficient priority. Bailout.
+    return;
   }
 
+  queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+
   {
-    // Set this flag so we can warn if setState is called inside the update
-    // function of another setState.
-    queue.isProcessing = true;
-  }
-
-  // Reset the remaining expiration time. If we skip over any updates, we'll
-  // increase this accordingly.
-  queue.expirationTime = NoWork;
-
-  // TODO: We don't know what the base state will be until we begin work.
-  // It depends on which fiber is the next current. Initialize with an empty
-  // base state, then set to the memoizedState when rendering. Not super
-  // happy with this approach.
-  var state = void 0;
-  if (queue.isInitialized) {
-    state = queue.baseState;
-  } else {
-    state = queue.baseState = workInProgress.memoizedState;
-    queue.isInitialized = true;
+    currentlyProcessingQueue = queue;
   }
-  var dontMutatePrevState = true;
-  var update = queue.first;
-  var didSkip = false;
+
+  // These values may change as we process the queue.
+  var newBaseState = queue.baseState;
+  var newFirstUpdate = null;
+  var newExpirationTime = NoWork;
+
+  // Iterate through the list of updates to compute the result.
+  var update = queue.firstUpdate;
+  var resultState = newBaseState;
   while (update !== null) {
     var updateExpirationTime = update.expirationTime;
     if (updateExpirationTime > renderExpirationTime) {
       // This update does not have sufficient priority. Skip it.
-      var remainingExpirationTime = queue.expirationTime;
+      if (newFirstUpdate === null) {
+        // This is the first skipped update. It will be the first update in
+        // the new list.
+        newFirstUpdate = update;
+        // Since this is the first update that was skipped, the current result
+        // is the new base state.
+        newBaseState = resultState;
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
       if (
-        remainingExpirationTime === NoWork ||
-        remainingExpirationTime > updateExpirationTime
+        newExpirationTime === NoWork ||
+        newExpirationTime > updateExpirationTime
       ) {
-        // Update the remaining expiration time.
-        queue.expirationTime = updateExpirationTime;
+        newExpirationTime = updateExpirationTime;
       }
-      if (!didSkip) {
-        didSkip = true;
-        queue.baseState = state;
+    } else {
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback = update.callback;
+      if (_callback !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastEffect === null) {
+          queue.firstEffect = queue.lastEffect = update;
+        } else {
+          queue.lastEffect.nextEffect = update;
+          queue.lastEffect = update;
+        }
       }
-      // Continue to the next update.
-      update = update.next;
-      continue;
     }
+    // Continue to the next update.
+    update = update.next;
+  }
 
-    // This update does have sufficient priority.
-
-    // If no previous updates were skipped, drop this update from the queue by
-    // advancing the head of the list.
-    if (!didSkip) {
-      queue.first = update.next;
-      if (queue.first === null) {
-        queue.last = null;
+  // Separately, iterate though the list of captured updates.
+  var newFirstCapturedUpdate = null;
+  update = queue.firstCapturedUpdate;
+  while (update !== null) {
+    var _updateExpirationTime = update.expirationTime;
+    if (_updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      if (newFirstCapturedUpdate === null) {
+        // This is the first skipped captured update. It will be the first
+        // update in the new list.
+        newFirstCapturedUpdate = update;
+        // If this is the first update that was skipped, the current result is
+        // the new base state.
+        if (newFirstUpdate === null) {
+          newBaseState = resultState;
+        }
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
+      if (
+        newExpirationTime === NoWork ||
+        newExpirationTime > _updateExpirationTime
+      ) {
+        newExpirationTime = _updateExpirationTime;
       }
-    }
-
-    // Invoke setState callback an extra time to help detect side-effects.
-    // Ignore the return value in this case.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      getStateFromUpdate(update, instance, state, props);
-    }
-
-    // Process the update
-    var _partialState = void 0;
-    if (update.isReplace) {
-      state = getStateFromUpdate(update, instance, state, props);
-      dontMutatePrevState = true;
     } else {
-      _partialState = getStateFromUpdate(update, instance, state, props);
-      if (_partialState) {
-        if (dontMutatePrevState) {
-          // $FlowFixMe: Idk how to type this properly.
-          state = Object.assign({}, state, _partialState);
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback2 = update.callback;
+      if (_callback2 !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastCapturedEffect === null) {
+          queue.firstCapturedEffect = queue.lastCapturedEffect = update;
         } else {
-          state = Object.assign(state, _partialState);
+          queue.lastCapturedEffect.nextEffect = update;
+          queue.lastCapturedEffect = update;
         }
-        dontMutatePrevState = false;
-      }
-    }
-    if (update.isForced) {
-      queue.hasForceUpdate = true;
-    }
-    if (update.callback !== null) {
-      // Append to list of callbacks.
-      var _callbackList = queue.callbackList;
-      if (_callbackList === null) {
-        _callbackList = queue.callbackList = [];
-      }
-      _callbackList.push(update);
-    }
-    if (update.capturedValue !== null) {
-      var _capturedValues = queue.capturedValues;
-      if (_capturedValues === null) {
-        queue.capturedValues = [update.capturedValue];
-      } else {
-        _capturedValues.push(update.capturedValue);
       }
     }
     update = update.next;
   }
 
-  if (queue.callbackList !== null) {
+  if (newFirstUpdate === null) {
+    queue.lastUpdate = null;
+  }
+  if (newFirstCapturedUpdate === null) {
+    queue.lastCapturedUpdate = null;
+  } else {
     workInProgress.effectTag |= Callback;
-  } else if (
-    queue.first === null &&
-    !queue.hasForceUpdate &&
-    queue.capturedValues === null
-  ) {
-    // The queue is empty. We can reset it.
-    workInProgress.updateQueue = null;
   }
-
-  if (!didSkip) {
-    didSkip = true;
-    queue.baseState = state;
+  if (newFirstUpdate === null && newFirstCapturedUpdate === null) {
+    // We processed every update, without skipping. That means the new base
+    // state is the same as the result state.
+    newBaseState = resultState;
   }
 
+  queue.baseState = newBaseState;
+  queue.firstUpdate = newFirstUpdate;
+  queue.firstCapturedUpdate = newFirstCapturedUpdate;
+  queue.expirationTime = newExpirationTime;
+
+  workInProgress.memoizedState = resultState;
+
   {
-    // No longer processing.
-    queue.isProcessing = false;
+    currentlyProcessingQueue = null;
   }
+}
 
-  return state;
+function callCallback(callback, context) {
+  invariant(
+    typeof callback === "function",
+    "Invalid argument passed as callback. Expected a function. Instead " +
+      "received: %s",
+    callback
+  );
+  callback.call(context);
 }
 
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (callbackList === null) {
-    return;
+function resetHasForceUpdateBeforeProcessing() {
+  hasForceUpdate = false;
+}
+
+function checkHasForceUpdateAfterProcessing() {
+  return hasForceUpdate;
+}
+
+function commitUpdateQueue(
+  finishedWork,
+  finishedQueue,
+  instance,
+  renderExpirationTime
+) {
+  // If the finished render included captured updates, and there are still
+  // lower priority updates left over, we need to keep the captured updates
+  // in the queue so that they are rebased and not dropped once we process the
+  // queue again at the lower priority.
+  if (finishedQueue.firstCapturedUpdate !== null) {
+    // Join the captured update list to the end of the normal list.
+    if (finishedQueue.lastUpdate !== null) {
+      finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate;
+      finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate;
+    }
+    // Clear the list of captured updates.
+    finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null;
   }
-  // Set the list to null to make sure they don't get called more than once.
-  queue.callbackList = null;
-  for (var i = 0; i < callbackList.length; i++) {
-    var update = callbackList[i];
-    var _callback = update.callback;
-    // This update might be processed again. Clear the callback so it's only
-    // called once.
-    update.callback = null;
-    invariant(
-      typeof _callback === "function",
-      "Invalid argument passed as callback. Expected a function. Instead " +
-        "received: %s",
-      _callback
-    );
-    _callback.call(context);
+
+  // Commit the effects
+  var effect = finishedQueue.firstEffect;
+  finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+  while (effect !== null) {
+    var _callback3 = effect.callback;
+    if (_callback3 !== null) {
+      effect.callback = null;
+      callCallback(_callback3, instance);
+    }
+    effect = effect.nextEffect;
+  }
+
+  effect = finishedQueue.firstCapturedEffect;
+  finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+  while (effect !== null) {
+    var _callback4 = effect.callback;
+    if (_callback4 !== null) {
+      effect.callback = null;
+      callCallback(_callback4, instance);
+    }
+    effect = effect.nextEffect;
   }
 }
 
@@ -5402,18 +5790,19 @@ var fakeInternalInstance = {};
 var isArray = Array.isArray;
 
 var didWarnAboutStateAssignmentForComponent = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
 var didWarnAboutUninitializedState = void 0;
 var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
 var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
+var warnOnUndefinedDerivedState = void 0;
 var warnOnInvalidCallback = void 0;
 
 {
   didWarnAboutStateAssignmentForComponent = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
   didWarnAboutUninitializedState = new Set();
   didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
   didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
 
   var didWarnOnInvalidCallback = new Set();
 
@@ -5434,6 +5823,21 @@ var warnOnInvalidCallback = void 0;
     }
   };
 
+  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
+    if (partialState === undefined) {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+        didWarnAboutUndefinedDerivedState.add(componentName);
+        warning(
+          false,
+          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+            "You have returned undefined.",
+          componentName
+        );
+      }
+    }
+  };
+
   // This is so gross but it's at least non-critical and can be removed if
   // it causes problems. This is meant to give a nicer error message for
   // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
@@ -5455,17 +5859,43 @@ var warnOnInvalidCallback = void 0;
   });
   Object.freeze(fakeInternalInstance);
 }
-function callGetDerivedStateFromCatch(ctor, capturedValues) {
-  var resultState = {};
-  for (var i = 0; i < capturedValues.length; i++) {
-    var capturedValue = capturedValues[i];
-    var error = capturedValue.value;
-    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
-    if (partialState !== null && partialState !== undefined) {
-      Object.assign(resultState, partialState);
+
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+
+  {
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      // Invoke the function an extra time to help detect side-effects.
+      getDerivedStateFromProps(nextProps, prevState);
     }
   }
-  return resultState;
+
+  var partialState = getDerivedStateFromProps(nextProps, prevState);
+
+  {
+    warnOnUndefinedDerivedState(workInProgress, partialState);
+  }
+  // Merge the partial state and the previous state.
+  var memoizedState =
+    partialState === null || partialState === undefined
+      ? prevState
+      : Object.assign({}, prevState, partialState);
+  workInProgress.memoizedState = memoizedState;
+
+  // Once the update queue is empty, persist the derived state onto the
+  // base state.
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
+    updateQueue.baseState = memoizedState;
+  }
 }
 
 var ReactFiberClassComponent = function(
@@ -5473,7 +5903,8 @@ var ReactFiberClassComponent = function(
   scheduleWork,
   computeExpirationForFiber,
   memoizeProps,
-  memoizeState
+  memoizeState,
+  recalculateCurrentTime
 ) {
   var cacheContext = legacyContext.cacheContext,
     getMaskedContext = legacyContext.getMaskedContext,
@@ -5481,65 +5912,60 @@ var ReactFiberClassComponent = function(
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged;
 
-  // Class component state updater
-
-  var updater = {
+  var classComponentUpdater = {
     isMounted: isMounted,
-    enqueueSetState: function(instance, partialState, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "setState");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: partialState,
-        callback: callback,
-        isReplace: false,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+    enqueueSetState: function(inst, payload, callback) {
+      var fiber = get$1(inst);
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(currentTime, fiber);
+
+      var update = createUpdate(expirationTime);
+      update.payload = payload;
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "setState");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueReplaceState: function(instance, state, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "replaceState");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: state,
-        callback: callback,
-        isReplace: true,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+    enqueueReplaceState: function(inst, payload, callback) {
+      var fiber = get$1(inst);
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(currentTime, fiber);
+
+      var update = createUpdate(expirationTime);
+      update.tag = ReplaceState;
+      update.payload = payload;
+
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "replaceState");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueForceUpdate: function(instance, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "forceUpdate");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: null,
-        callback: callback,
-        isReplace: false,
-        isForced: true,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+    enqueueForceUpdate: function(inst, callback) {
+      var fiber = get$1(inst);
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(currentTime, fiber);
+
+      var update = createUpdate(expirationTime);
+      update.tag = ForceUpdate;
+
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "forceUpdate");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     }
   };
@@ -5552,15 +5978,6 @@ var ReactFiberClassComponent = function(
     newState,
     newContext
   ) {
-    if (
-      oldProps === null ||
-      (workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate)
-    ) {
-      // If the workInProgress already has an Update effect, return true
-      return true;
-    }
-
     var instance = workInProgress.stateNode;
     var ctor = workInProgress.type;
     if (typeof instance.shouldComponentUpdate === "function") {
@@ -5814,13 +6231,8 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function resetInputPointers(workInProgress, instance) {
-    instance.props = workInProgress.memoizedProps;
-    instance.state = workInProgress.memoizedState;
-  }
-
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
+    instance.updater = classComponentUpdater;
     workInProgress.stateNode = instance;
     // The instance needs access to the fiber so that it can schedule updates
     set(instance, workInProgress);
@@ -5829,7 +6241,7 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function constructClassInstance(workInProgress, props) {
+  function constructClassInstance(workInProgress, props, renderExpirationTime) {
     var ctor = workInProgress.type;
     var unmaskedContext = getUnmaskedContext(workInProgress);
     var needsContext = isContextConsumer(workInProgress);
@@ -5838,19 +6250,21 @@ var ReactFiberClassComponent = function(
       : emptyObject;
 
     // Instantiate twice to help detect side-effects.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      new ctor(props, context); // eslint-disable-line no-new
+    {
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        new ctor(props, context); // eslint-disable-line no-new
+      }
     }
 
     var instance = new ctor(props, context);
-    var state =
+    var state = (workInProgress.memoizedState =
       instance.state !== null && instance.state !== undefined
         ? instance.state
-        : null;
+        : null);
     adoptClassInstance(workInProgress, instance);
 
     {
@@ -5941,26 +6355,6 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    workInProgress.memoizedState = state;
-
-    var partialState = callGetDerivedStateFromProps(
-      workInProgress,
-      instance,
-      props,
-      state
-    );
-
-    if (partialState !== null && partialState !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      workInProgress.memoizedState = Object.assign(
-        {},
-        workInProgress.memoizedState,
-        partialState
-      );
-    }
-
     // Cache unmasked context so we can avoid recreating masked context unless necessary.
     // ReactFiberContext usually updates this cache but can't for newly-created instances.
     if (needsContext) {
@@ -5993,7 +6387,7 @@ var ReactFiberClassComponent = function(
           getComponentName(workInProgress) || "Component"
         );
       }
-      updater.enqueueReplaceState(instance, instance.state, null);
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
@@ -6027,57 +6421,13 @@ var ReactFiberClassComponent = function(
           );
         }
       }
-      updater.enqueueReplaceState(instance, instance.state, null);
-    }
-  }
-
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    var type = workInProgress.type;
-
-    if (typeof type.getDerivedStateFromProps === "function") {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        // Invoke method an extra time to help detect side-effects.
-        type.getDerivedStateFromProps.call(null, nextProps, prevState);
-      }
-
-      var partialState = type.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
-
-      {
-        if (partialState === undefined) {
-          var componentName = getComponentName(workInProgress) || "Component";
-          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-            didWarnAboutUndefinedDerivedState.add(componentName);
-            warning(
-              false,
-              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-                "You have returned undefined.",
-              componentName
-            );
-          }
-        }
-      }
-
-      return partialState;
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
   // Invokes the mount life-cycles on a previously never rendered instance.
   function mountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
-    var current = workInProgress.alternate;
 
     {
       checkClassInstance(workInProgress);
@@ -6108,6 +6458,28 @@ var ReactFiberClassComponent = function(
       }
     }
 
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
+        workInProgress,
+        updateQueue,
+        props,
+        instance,
+        renderExpirationTime
+      );
+      instance.state = workInProgress.memoizedState;
+    }
+
+    var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
+        workInProgress,
+        getDerivedStateFromProps,
+        props
+      );
+      instance.state = workInProgress.memoizedState;
+    }
+
     // In order to support react-lifecycles-compat polyfilled components,
     // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
@@ -6119,18 +6491,19 @@ var ReactFiberClassComponent = function(
       callComponentWillMount(workInProgress, instance);
       // If we had additional state updates during this life-cycle, let's
       // process them now.
-      var updateQueue = workInProgress.updateQueue;
+      updateQueue = workInProgress.updateQueue;
       if (updateQueue !== null) {
-        instance.state = processUpdateQueue(
-          current,
+        processUpdateQueue(
           workInProgress,
           updateQueue,
-          instance,
           props,
+          instance,
           renderExpirationTime
         );
+        instance.state = workInProgress.memoizedState;
       }
     }
+
     if (typeof instance.componentDidMount === "function") {
       workInProgress.effectTag |= Update;
     }
@@ -6139,16 +6512,18 @@ var ReactFiberClassComponent = function(
   function resumeMountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
+    instance.props = oldProps;
+
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6172,103 +6547,26 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Compute the next state using the memoized state and the update queue.
+    resetHasForceUpdateBeforeProcessing();
+
     var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        null,
+    var newState = (instance.state = oldState);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
         workInProgress,
-        workInProgress.updateQueue,
-        instance,
+        updateQueue,
         newProps,
-        renderExpirationTime
-      );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
-    }
-
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
         instance,
-        newProps,
-        newState
+        renderExpirationTime
       );
+      newState = workInProgress.memoizedState;
     }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue = workInProgress.updateQueue;
-      if (_updateQueue !== null) {
-        _updateQueue.baseState = Object.assign(
-          {},
-          _updateQueue.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue2 = workInProgress.updateQueue;
-      if (_updateQueue2 !== null) {
-        _updateQueue2.baseState = Object.assign(
-          {},
-          _updateQueue2.baseState,
-          derivedStateFromCatch
-        );
-      }
-    }
-
     if (
       oldProps === newProps &&
       oldState === newState &&
       !hasContextChanged() &&
-      !(
-        workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate
-      )
+      !checkHasForceUpdateAfterProcessing()
     ) {
       // If an update was already in progress, we should schedule an Update
       // effect even though we're bailing out, so that cWU/cDU are called.
@@ -6278,14 +6576,25 @@ var ReactFiberClassComponent = function(
       return false;
     }
 
-    var shouldUpdate = checkShouldComponentUpdate(
-      workInProgress,
-      oldProps,
-      newProps,
-      oldState,
-      newState,
-      newContext
-    );
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
+        workInProgress,
+        getDerivedStateFromProps,
+        newProps
+      );
+      newState = workInProgress.memoizedState;
+    }
+
+    var shouldUpdate =
+      checkHasForceUpdateAfterProcessing() ||
+      checkShouldComponentUpdate(
+        workInProgress,
+        oldProps,
+        newProps,
+        oldState,
+        newState,
+        newContext
+      );
 
     if (shouldUpdate) {
       // In order to support react-lifecycles-compat polyfilled components,
@@ -6315,9 +6624,9 @@ var ReactFiberClassComponent = function(
       }
 
       // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
+      // memoized state to indicate that this work can be reused.
+      workInProgress.memoizedProps = newProps;
+      workInProgress.memoizedState = newState;
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6333,16 +6642,18 @@ var ReactFiberClassComponent = function(
   function updateClassInstance(current, workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
+    instance.props = oldProps;
+
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6366,104 +6677,27 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Compute the next state using the memoized state and the update queue.
-    var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
+    resetHasForceUpdateBeforeProcessing();
 
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        current,
+    var oldState = workInProgress.memoizedState;
+    var newState = (instance.state = oldState);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
         workInProgress,
-        workInProgress.updateQueue,
-        instance,
+        updateQueue,
         newProps,
-        renderExpirationTime
-      );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
-    }
-
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
         instance,
-        newProps,
-        newState
+        renderExpirationTime
       );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue3 = workInProgress.updateQueue;
-      if (_updateQueue3 !== null) {
-        _updateQueue3.baseState = Object.assign(
-          {},
-          _updateQueue3.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue4 = workInProgress.updateQueue;
-      if (_updateQueue4 !== null) {
-        _updateQueue4.baseState = Object.assign(
-          {},
-          _updateQueue4.baseState,
-          derivedStateFromCatch
-        );
-      }
+      newState = workInProgress.memoizedState;
     }
 
     if (
       oldProps === newProps &&
       oldState === newState &&
       !hasContextChanged() &&
-      !(
-        workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate
-      )
+      !checkHasForceUpdateAfterProcessing()
     ) {
       // If an update was already in progress, we should schedule an Update
       // effect even though we're bailing out, so that cWU/cDU are called.
@@ -6486,14 +6720,27 @@ var ReactFiberClassComponent = function(
       return false;
     }
 
-    var shouldUpdate = checkShouldComponentUpdate(
-      workInProgress,
-      oldProps,
-      newProps,
-      oldState,
-      newState,
-      newContext
-    );
+    if (typeof getDerivedStateFromProps === "function") {
+      if (fireGetDerivedStateFromPropsOnStateUpdates || oldProps !== newProps) {
+        applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        );
+        newState = workInProgress.memoizedState;
+      }
+    }
+
+    var shouldUpdate =
+      checkHasForceUpdateAfterProcessing() ||
+      checkShouldComponentUpdate(
+        workInProgress,
+        oldProps,
+        newProps,
+        oldState,
+        newState,
+        newContext
+      );
 
     if (shouldUpdate) {
       // In order to support react-lifecycles-compat polyfilled components,
@@ -6540,8 +6787,8 @@ var ReactFiberClassComponent = function(
 
       // If shouldComponentUpdate returned false, we should still update the
       // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
+      workInProgress.memoizedProps = newProps;
+      workInProgress.memoizedState = newState;
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6555,7 +6802,6 @@ var ReactFiberClassComponent = function(
 
   return {
     adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: constructClassInstance,
     mountClassInstance: mountClassInstance,
     resumeMountClassInstance: resumeMountClassInstance,
@@ -6563,7 +6809,7 @@ var ReactFiberClassComponent = function(
   };
 };
 
-var getCurrentFiberStackAddendum$1 =
+var getCurrentFiberStackAddendum$2 =
   ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
 
 var didWarnAboutMaps = void 0;
@@ -6602,7 +6848,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
       '"key" prop. See https://fb.me/react-warning-keys for ' +
       "more information." +
-      (getCurrentFiberStackAddendum$1() || "");
+      (getCurrentFiberStackAddendum$2() || "");
     if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
       return;
     }
@@ -6613,7 +6859,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
         '"key" prop. See https://fb.me/react-warning-keys for ' +
         "more information.%s",
-      getCurrentFiberStackAddendum$1()
+      getCurrentFiberStackAddendum$2()
     );
   };
 }
@@ -6710,7 +6956,7 @@ function throwOnInvalidObjectType(returnFiber, newChild) {
       addendum =
         " If you meant to render a collection of children, use an array " +
         "instead." +
-        (getCurrentFiberStackAddendum$1() || "");
+        (getCurrentFiberStackAddendum$2() || "");
     }
     invariant(
       false,
@@ -6728,7 +6974,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
     "you return a Component instead of <Component /> from render. " +
     "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$1() || "");
+    (getCurrentFiberStackAddendum$2() || "");
 
   if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
     return;
@@ -6740,7 +6986,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
       "you return a Component instead of <Component /> from render. " +
       "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$1() || ""
+    getCurrentFiberStackAddendum$2() || ""
   );
 }
 
@@ -6853,12 +7099,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, textContent, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -6868,7 +7114,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // Move based on index
       var existing = useFiber(current, element.props, expirationTime);
       existing.ref = coerceRef(returnFiber, current, element);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       {
         existing._debugSource = element._source;
         existing._debugOwner = element._owner;
@@ -6882,7 +7128,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       created.ref = coerceRef(returnFiber, current, element);
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     }
   }
@@ -6900,12 +7146,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, portal.children || [], expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -6919,12 +7165,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         key
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, fragment, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -6939,7 +7185,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     }
 
@@ -6952,7 +7198,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           _created.ref = coerceRef(returnFiber, null, newChild);
-          _created["return"] = returnFiber;
+          _created.return = returnFiber;
           return _created;
         }
         case REACT_PORTAL_TYPE: {
@@ -6961,7 +7207,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             returnFiber.mode,
             expirationTime
           );
-          _created2["return"] = returnFiber;
+          _created2.return = returnFiber;
           return _created2;
         }
       }
@@ -6973,7 +7219,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           null
         );
-        _created3["return"] = returnFiber;
+        _created3.return = returnFiber;
         return _created3;
       }
 
@@ -7184,7 +7430,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               "duplicated and/or omitted — the behavior is unsupported and " +
               "could change in a future version.%s",
             key,
-            getCurrentFiberStackAddendum$1()
+            getCurrentFiberStackAddendum$2()
           );
           break;
         default:
@@ -7329,7 +7575,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren["delete"](
+            existingChildren.delete(
               _newFiber2.key === null ? newIdx : _newFiber2.key
             );
           }
@@ -7382,7 +7628,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                 "Using Maps as children is unsupported and will likely yield " +
                   "unexpected results. Convert it to a sequence/iterable of keyed " +
                   "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$1()
+                getCurrentFiberStackAddendum$2()
               )
             : void 0;
           didWarnAboutMaps = true;
@@ -7508,7 +7754,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren["delete"](
+            existingChildren.delete(
               _newFiber4.key === null ? newIdx : _newFiber4.key
             );
           }
@@ -7547,7 +7793,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // the rest.
       deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
       var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
     // The existing first child is not a text node so we need to create one
@@ -7558,7 +7804,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created["return"] = returnFiber;
+    created.return = returnFiber;
     return created;
   }
 
@@ -7588,7 +7834,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           existing.ref = coerceRef(returnFiber, child, element);
-          existing["return"] = returnFiber;
+          existing.return = returnFiber;
           {
             existing._debugSource = element._source;
             existing._debugOwner = element._owner;
@@ -7611,7 +7857,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         element.key
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       var _created4 = createFiberFromElement(
@@ -7620,7 +7866,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4["return"] = returnFiber;
+      _created4.return = returnFiber;
       return _created4;
     }
   }
@@ -7644,7 +7890,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         ) {
           deleteRemainingChildren(returnFiber, child.sibling);
           var existing = useFiber(child, portal.children || [], expirationTime);
-          existing["return"] = returnFiber;
+          existing.return = returnFiber;
           return existing;
         } else {
           deleteRemainingChildren(returnFiber, child);
@@ -7661,7 +7907,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created["return"] = returnFiber;
+    created.return = returnFiber;
     return created;
   }
 
@@ -7813,7 +8059,7 @@ function cloneChildFibers(current, workInProgress) {
   );
   workInProgress.child = newChild;
 
-  newChild["return"] = workInProgress;
+  newChild.return = workInProgress;
   while (currentChild.sibling !== null) {
     currentChild = currentChild.sibling;
     newChild = newChild.sibling = createWorkInProgress(
@@ -7821,11 +8067,14 @@ function cloneChildFibers(current, workInProgress) {
       currentChild.pendingProps,
       currentChild.expirationTime
     );
-    newChild["return"] = workInProgress;
+    newChild.return = workInProgress;
   }
   newChild.sibling = null;
 }
 
+var getCurrentFiberStackAddendum =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+
 var didWarnAboutBadClass = void 0;
 var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
 var didWarnAboutStatelessRefs = void 0;
@@ -7843,13 +8092,19 @@ var ReactFiberBeginWork = function(
   newContext,
   hydrationContext,
   scheduleWork,
-  computeExpirationForFiber
+  computeExpirationForFiber,
+  profilerTimer,
+  recalculateCurrentTime
 ) {
   var shouldSetTextContent = config.shouldSetTextContent,
     shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
   var pushHostContext = hostContext.pushHostContext,
     pushHostContainer = hostContext.pushHostContainer;
-  var pushProvider = newContext.pushProvider;
+  var pushProvider = newContext.pushProvider,
+    getContextCurrentValue = newContext.getContextCurrentValue,
+    getContextChangedBits = newContext.getContextChangedBits;
+  var markActualRenderTimeStarted = profilerTimer.markActualRenderTimeStarted,
+    stopBaseRenderTimerIfRunning = profilerTimer.stopBaseRenderTimerIfRunning;
   var getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     hasLegacyContextChanged = legacyContext.hasContextChanged,
@@ -7866,11 +8121,10 @@ var ReactFiberBeginWork = function(
       scheduleWork,
       computeExpirationForFiber,
       memoizeProps,
-      memoizeState
+      memoizeState,
+      recalculateCurrentTime
     ),
     adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
-    callGetDerivedStateFromProps =
-      _ReactFiberClassCompo.callGetDerivedStateFromProps,
     constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
     mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
     resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
@@ -7922,9 +8176,28 @@ var ReactFiberBeginWork = function(
 
   function updateForwardRef(current, workInProgress) {
     var render = workInProgress.type.render;
-    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
+    var nextProps = workInProgress.pendingProps;
+    var ref = workInProgress.ref;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextProps) {
+      var currentRef = current !== null ? current.ref : null;
+      if (ref === currentRef) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+    }
+
+    var nextChildren = void 0;
+    {
+      ReactCurrentOwner.current = workInProgress;
+      ReactDebugCurrentFiber.setCurrentPhase("render");
+      nextChildren = render(nextProps, ref);
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+
     reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
     return workInProgress.child;
   }
 
@@ -7957,6 +8230,25 @@ var ReactFiberBeginWork = function(
     return workInProgress.child;
   }
 
+  function updateProfiler(current, workInProgress) {
+    var nextProps = workInProgress.pendingProps;
+    if (enableProfilerTimer) {
+      // Start render timer here and push start time onto queue
+      markActualRenderTimeStarted(workInProgress);
+
+      // Let the "complete" phase know to stop the timer,
+      // And the scheduler to record the measured time.
+      workInProgress.effectTag |= Update;
+    }
+    if (workInProgress.memoizedProps === nextProps) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    var nextChildren = nextProps.children;
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
+    return workInProgress.child;
+  }
+
   function markRef(current, workInProgress) {
     var ref = workInProgress.ref;
     if (
@@ -8010,7 +8302,11 @@ var ReactFiberBeginWork = function(
     if (current === null) {
       if (workInProgress.stateNode === null) {
         // In the initial pass we might need to construct the instance.
-        constructClassInstance(workInProgress, workInProgress.pendingProps);
+        constructClassInstance(
+          workInProgress,
+          workInProgress.pendingProps,
+          renderExpirationTime
+        );
         mountClassInstance(workInProgress, renderExpirationTime);
 
         shouldUpdate = true;
@@ -8028,22 +8324,11 @@ var ReactFiberBeginWork = function(
         renderExpirationTime
       );
     }
-
-    // We processed the update queue inside updateClassInstance. It may have
-    // included some errors that were dispatched during the commit phase.
-    // TODO: Refactor class components so this is less awkward.
-    var didCaptureError = false;
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null && updateQueue.capturedValues !== null) {
-      shouldUpdate = true;
-      didCaptureError = true;
-    }
     return finishClassComponent(
       current,
       workInProgress,
       shouldUpdate,
       hasContext,
-      didCaptureError,
       renderExpirationTime
     );
   }
@@ -8053,12 +8338,13 @@ var ReactFiberBeginWork = function(
     workInProgress,
     shouldUpdate,
     hasContext,
-    didCaptureError,
     renderExpirationTime
   ) {
     // Refs should update even if shouldComponentUpdate returns false
     markRef(current, workInProgress);
 
+    var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
+
     if (!shouldUpdate && !didCaptureError) {
       // Context providers should defer to sCU for rendering
       if (hasContext) {
@@ -8085,6 +8371,10 @@ var ReactFiberBeginWork = function(
       // the new API.
       // TODO: Warn in a future release.
       nextChildren = null;
+
+      if (enableProfilerTimer) {
+        stopBaseRenderTimerIfRunning();
+      }
     } else {
       {
         ReactDebugCurrentFiber.setCurrentPhase("render");
@@ -8154,29 +8444,26 @@ var ReactFiberBeginWork = function(
     pushHostRootContext(workInProgress);
     var updateQueue = workInProgress.updateQueue;
     if (updateQueue !== null) {
+      var nextProps = workInProgress.pendingProps;
       var prevState = workInProgress.memoizedState;
-      var state = processUpdateQueue(
-        current,
+      var prevChildren = prevState !== null ? prevState.element : null;
+      processUpdateQueue(
         workInProgress,
         updateQueue,
-        null,
+        nextProps,
         null,
         renderExpirationTime
       );
-      memoizeState(workInProgress, state);
-      updateQueue = workInProgress.updateQueue;
+      var nextState = workInProgress.memoizedState;
+      // Caution: React DevTools currently depends on this property
+      // being called "element".
+      var nextChildren = nextState.element;
 
-      var element = void 0;
-      if (updateQueue !== null && updateQueue.capturedValues !== null) {
-        // There's an uncaught error. Unmount the whole root.
-        element = null;
-      } else if (prevState === state) {
+      if (nextChildren === prevChildren) {
         // If the state is the same as before, that's a bailout because we had
         // no work that expires at this time.
         resetHydrationState();
         return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      } else {
-        element = state.element;
       }
       var root = workInProgress.stateNode;
       if (
@@ -8201,16 +8488,15 @@ var ReactFiberBeginWork = function(
         workInProgress.child = mountChildFibers(
           workInProgress,
           null,
-          element,
+          nextChildren,
           renderExpirationTime
         );
       } else {
         // Otherwise reset hydration state in case we aborted and resumed another
         // root.
         resetHydrationState();
-        reconcileChildren(current, workInProgress, element);
+        reconcileChildren(current, workInProgress, nextChildren);
       }
-      memoizeState(workInProgress, state);
       return workInProgress.child;
     }
     resetHydrationState();
@@ -8346,21 +8632,13 @@ var ReactFiberBeginWork = function(
       workInProgress.memoizedState =
         value.state !== null && value.state !== undefined ? value.state : null;
 
-      if (typeof Component.getDerivedStateFromProps === "function") {
-        var partialState = callGetDerivedStateFromProps(
+      var getDerivedStateFromProps = Component.getDerivedStateFromProps;
+      if (typeof getDerivedStateFromProps === "function") {
+        applyDerivedStateFromProps(
           workInProgress,
-          value,
-          props,
-          workInProgress.memoizedState
+          getDerivedStateFromProps,
+          props
         );
-
-        if (partialState !== null && partialState !== undefined) {
-          workInProgress.memoizedState = Object.assign(
-            {},
-            workInProgress.memoizedState,
-            partialState
-          );
-        }
       }
 
       // Push context providers early to prevent context stack mismatches.
@@ -8374,7 +8652,6 @@ var ReactFiberBeginWork = function(
         workInProgress,
         true,
         hasContext,
-        false,
         renderExpirationTime
       );
     } else {
@@ -8477,6 +8754,41 @@ var ReactFiberBeginWork = function(
     return workInProgress.stateNode;
   }
 
+  function updateTimeoutComponent(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    if (enableSuspense) {
+      var nextProps = workInProgress.pendingProps;
+      var prevProps = workInProgress.memoizedProps;
+
+      var prevDidTimeout = workInProgress.memoizedState;
+
+      // Check if we already attempted to render the normal state. If we did,
+      // and we timed out, render the placeholder state.
+      var alreadyCaptured =
+        (workInProgress.effectTag & DidCapture) === NoEffect;
+      var nextDidTimeout = !alreadyCaptured;
+
+      if (hasLegacyContextChanged()) {
+        // Normally we can bail out on props equality but if context has changed
+        // we don't do the bailout and we have to reuse existing props instead.
+      } else if (nextProps === prevProps && nextDidTimeout === prevDidTimeout) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+
+      var render = nextProps.children;
+      var nextChildren = render(nextDidTimeout);
+      workInProgress.memoizedProps = nextProps;
+      workInProgress.memoizedState = nextDidTimeout;
+      reconcileChildren(current, workInProgress, nextChildren);
+      return workInProgress.child;
+    } else {
+      return null;
+    }
+  }
+
   function updatePortalComponent(
     current,
     workInProgress,
@@ -8520,7 +8832,7 @@ var ReactFiberBeginWork = function(
     var fiber = workInProgress.child;
     if (fiber !== null) {
       // Set the return pointer of the child to the work-in-progress fiber.
-      fiber["return"] = workInProgress;
+      fiber.return = workInProgress;
     }
     while (fiber !== null) {
       var nextFiber = void 0;
@@ -8558,7 +8870,7 @@ var ReactFiberBeginWork = function(
                 // ancestor path already has sufficient priority.
                 break;
               }
-              node = node["return"];
+              node = node.return;
             }
             // Don't scan deeper than a matching consumer. When we render the
             // consumer, we'll continue scanning from that point. This way the
@@ -8580,7 +8892,7 @@ var ReactFiberBeginWork = function(
       }
       if (nextFiber !== null) {
         // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber["return"] = fiber;
+        nextFiber.return = fiber;
       } else {
         // No child. Traverse to next sibling.
         nextFiber = fiber;
@@ -8592,11 +8904,13 @@ var ReactFiberBeginWork = function(
           }
           var sibling = nextFiber.sibling;
           if (sibling !== null) {
+            // Set the return pointer of the sibling to the work-in-progress fiber.
+            sibling.return = nextFiber.return;
             nextFiber = sibling;
             break;
           }
           // No more siblings. Traverse up.
-          nextFiber = nextFiber["return"];
+          nextFiber = nextFiber.return;
         }
       }
       fiber = nextFiber;
@@ -8613,8 +8927,10 @@ var ReactFiberBeginWork = function(
 
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
+    var canBailOnProps = true;
 
     if (hasLegacyContextChanged()) {
+      canBailOnProps = false;
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (oldProps === newProps) {
@@ -8626,6 +8942,20 @@ var ReactFiberBeginWork = function(
     var newValue = newProps.value;
     workInProgress.memoizedProps = newProps;
 
+    {
+      var providerPropTypes = workInProgress.type.propTypes;
+
+      if (providerPropTypes) {
+        checkPropTypes(
+          providerPropTypes,
+          newProps,
+          "prop",
+          "Context.Provider",
+          getCurrentFiberStackAddendum
+        );
+      }
+    }
+
     var changedBits = void 0;
     if (oldProps === null) {
       // Initial render
@@ -8633,7 +8963,7 @@ var ReactFiberBeginWork = function(
     } else {
       if (oldProps.value === newProps.value) {
         // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children) {
+        if (oldProps.children === newProps.children && canBailOnProps) {
           workInProgress.stateNode = 0;
           pushProvider(workInProgress);
           return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8650,7 +8980,7 @@ var ReactFiberBeginWork = function(
           (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
         ) {
           // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children) {
+          if (oldProps.children === newProps.children && canBailOnProps) {
             workInProgress.stateNode = 0;
             pushProvider(workInProgress);
             return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8675,7 +9005,7 @@ var ReactFiberBeginWork = function(
 
           if (changedBits === 0) {
             // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children) {
+            if (oldProps.children === newProps.children && canBailOnProps) {
               workInProgress.stateNode = 0;
               pushProvider(workInProgress);
               return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8709,8 +9039,8 @@ var ReactFiberBeginWork = function(
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
 
-    var newValue = context._currentValue;
-    var changedBits = context._changedBits;
+    var newValue = getContextCurrentValue(context);
+    var changedBits = getContextChangedBits(context);
 
     if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
@@ -8760,7 +9090,16 @@ var ReactFiberBeginWork = function(
         : void 0;
     }
 
-    var newChildren = render(newValue);
+    var newChildren = void 0;
+    {
+      ReactCurrentOwner.current = workInProgress;
+      ReactDebugCurrentFiber.setCurrentPhase("render");
+      newChildren = render(newValue);
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
     reconcileChildren(current, workInProgress, newChildren);
     return workInProgress.child;
   }
@@ -8787,6 +9126,11 @@ var ReactFiberBeginWork = function(
   function bailoutOnAlreadyFinishedWork(current, workInProgress) {
     cancelWorkTimer(workInProgress);
 
+    if (enableProfilerTimer) {
+      // Don't update "base" render times for bailouts.
+      stopBaseRenderTimerIfRunning();
+    }
+
     // TODO: We should ideally be able to bail out early if the children have no
     // more work to do. However, since we don't have a separation of this
     // Fiber's priority and its children yet - we don't know without doing lots
@@ -8808,6 +9152,11 @@ var ReactFiberBeginWork = function(
   function bailoutOnLowPriority(current, workInProgress) {
     cancelWorkTimer(workInProgress);
 
+    if (enableProfilerTimer) {
+      // Don't update "base" render times for bailouts.
+      stopBaseRenderTimerIfRunning();
+    }
+
     // TODO: Handle HostComponent tags here as well and call pushHostContext()?
     // See PR 8590 discussion for context
     switch (workInProgress.tag) {
@@ -8826,6 +9175,11 @@ var ReactFiberBeginWork = function(
       case ContextProvider:
         pushProvider(workInProgress);
         break;
+      case Profiler:
+        if (enableProfilerTimer) {
+          markActualRenderTimeStarted(workInProgress);
+        }
+        break;
     }
     // TODO: What if this is currently in progress?
     // How can that happen? How is this not being cloned?
@@ -8890,6 +9244,12 @@ var ReactFiberBeginWork = function(
         // A return component is just a placeholder, we can just run through the
         // next one immediately.
         return null;
+      case TimeoutComponent:
+        return updateTimeoutComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
       case HostPortal:
         return updatePortalComponent(
           current,
@@ -8902,6 +9262,8 @@ var ReactFiberBeginWork = function(
         return updateFragment(current, workInProgress);
       case Mode:
         return updateMode(current, workInProgress);
+      case Profiler:
+        return updateProfiler(current, workInProgress);
       case ContextProvider:
         return updateContextProvider(
           current,
@@ -8933,7 +9295,8 @@ var ReactFiberCompleteWork = function(
   hostContext,
   legacyContext,
   newContext,
-  hydrationContext
+  hydrationContext,
+  profilerTimer
 ) {
   var createInstance = config.createInstance,
     createTextInstance = config.createTextInstance,
@@ -8946,6 +9309,8 @@ var ReactFiberCompleteWork = function(
     popHostContext = hostContext.popHostContext,
     getHostContext = hostContext.getHostContext,
     popHostContainer = hostContext.popHostContainer;
+  var recordElapsedActualRenderTime =
+    profilerTimer.recordElapsedActualRenderTime;
   var popLegacyContextProvider = legacyContext.popContextProvider,
     popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
   var popProvider = newContext.popProvider;
@@ -8968,7 +9333,7 @@ var ReactFiberCompleteWork = function(
   function appendAllReturns(returns, workInProgress) {
     var node = workInProgress.stateNode;
     if (node) {
-      node["return"] = workInProgress;
+      node.return = workInProgress;
     }
     while (node !== null) {
       if (
@@ -8980,17 +9345,17 @@ var ReactFiberCompleteWork = function(
       } else if (node.tag === ReturnComponent) {
         returns.push(node.pendingProps.value);
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -9046,7 +9411,7 @@ var ReactFiberCompleteWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -9054,12 +9419,12 @@ var ReactFiberCompleteWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -9126,7 +9491,7 @@ var ReactFiberCompleteWork = function(
             // down its children. Instead, we'll get insertions from each child in
             // the portal directly.
           } else if (node.child !== null) {
-            node.child["return"] = node;
+            node.child.return = node;
             node = node.child;
             continue;
           }
@@ -9134,12 +9499,12 @@ var ReactFiberCompleteWork = function(
             return;
           }
           while (node.sibling === null) {
-            if (node["return"] === null || node["return"] === workInProgress) {
+            if (node.return === null || node.return === workInProgress) {
               return;
             }
-            node = node["return"];
+            node = node.return;
           }
-          node.sibling["return"] = node["return"];
+          node.sibling.return = node.return;
           node = node.sibling;
         }
       };
@@ -9265,20 +9630,6 @@ var ReactFiberCompleteWork = function(
       case ClassComponent: {
         // We are leaving this subtree, so pop context if any.
         popLegacyContextProvider(workInProgress);
-
-        // If this component caught an error, schedule an error log effect.
-        var instance = workInProgress.stateNode;
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null && updateQueue.capturedValues !== null) {
-          workInProgress.effectTag &= ~DidCapture;
-          if (typeof instance.componentDidCatch === "function") {
-            workInProgress.effectTag |= ErrLog;
-          } else {
-            // Normally we clear this in the commit phase, but since we did not
-            // schedule an effect, we need to reset it here.
-            updateQueue.capturedValues = null;
-          }
-        }
         return null;
       }
       case HostRoot: {
@@ -9298,11 +9649,6 @@ var ReactFiberCompleteWork = function(
           workInProgress.effectTag &= ~Placement;
         }
         updateHostContainer(workInProgress);
-
-        var _updateQueue = workInProgress.updateQueue;
-        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
-          workInProgress.effectTag |= ErrLog;
-        }
         return null;
       }
       case HostComponent: {
@@ -9317,13 +9663,13 @@ var ReactFiberCompleteWork = function(
           // have newProps so we'll have to reuse them.
           // TODO: Split the update API as separate for the props vs. children.
           // Even better would be if children weren't special cased at all tho.
-          var _instance = workInProgress.stateNode;
+          var instance = workInProgress.stateNode;
           var currentHostContext = getHostContext();
           // TODO: Experiencing an error where oldProps is null. Suggests a host
           // component is hitting the resume path. Figure out why. Possibly
           // related to `hidden`.
           var updatePayload = prepareUpdate(
-            _instance,
+            instance,
             type,
             oldProps,
             newProps,
@@ -9377,7 +9723,7 @@ var ReactFiberCompleteWork = function(
               markUpdate(workInProgress);
             }
           } else {
-            var _instance2 = createInstance(
+            var _instance = createInstance(
               type,
               newProps,
               rootContainerInstance,
@@ -9385,14 +9731,14 @@ var ReactFiberCompleteWork = function(
               workInProgress
             );
 
-            appendAllChildren(_instance2, workInProgress);
+            appendAllChildren(_instance, workInProgress);
 
             // Certain renderers require commit-time effects for initial mount.
             // (eg DOM renderer supports auto-focus for certain elements).
             // Make sure such renderers get scheduled for later work.
             if (
               finalizeInitialChildren(
-                _instance2,
+                _instance,
                 type,
                 newProps,
                 rootContainerInstance,
@@ -9401,7 +9747,7 @@ var ReactFiberCompleteWork = function(
             ) {
               markUpdate(workInProgress);
             }
-            workInProgress.stateNode = _instance2;
+            workInProgress.stateNode = _instance;
           }
 
           if (workInProgress.ref !== null) {
@@ -9461,10 +9807,17 @@ var ReactFiberCompleteWork = function(
         return null;
       case ForwardRef:
         return null;
+      case TimeoutComponent:
+        return null;
       case Fragment:
         return null;
       case Mode:
         return null;
+      case Profiler:
+        if (enableProfilerTimer) {
+          recordElapsedActualRenderTime(workInProgress);
+        }
+        return null;
       case HostPortal:
         popHostContainer(workInProgress);
         updateHostContainer(workInProgress);
@@ -9508,144 +9861,45 @@ function createCapturedValue(value, source) {
   };
 }
 
-var ReactFiberUnwindWork = function(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
+// Module provided by RN:
+/**
+ * Intercept lifecycle errors and ensure they are shown with the correct stack
+ * trace within the native redbox component.
+ */
+function showErrorDialog(capturedError) {
+  var componentStack = capturedError.componentStack,
+    error = capturedError.error;
 
-  function throwException(returnFiber, sourceFiber, rawValue) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+  var errorToHandle = void 0;
 
-    var value = createCapturedValue(rawValue, sourceFiber);
+  // Typically Errors are thrown but eg strings or null can be thrown as well.
+  if (error instanceof Error) {
+    var message = error.message,
+      name = error.name;
 
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          // Uncaught error
-          var errorInfo = value;
-          ensureUpdateQueues(workInProgress);
-          var updateQueue = workInProgress.updateQueue;
-          updateQueue.capturedValues = [errorInfo];
-          workInProgress.effectTag |= ShouldCapture;
-          return;
-        }
-        case ClassComponent:
-          // Capture and retry
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
-          if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            ensureUpdateQueues(workInProgress);
-            var _updateQueue = workInProgress.updateQueue;
-            var capturedValues = _updateQueue.capturedValues;
-            if (capturedValues === null) {
-              _updateQueue.capturedValues = [value];
-            } else {
-              capturedValues.push(value);
-            }
-            workInProgress.effectTag |= ShouldCapture;
-            return;
-          }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress["return"];
-    } while (workInProgress !== null);
-  }
+    var summary = message ? name + ": " + message : name;
 
-  function unwindWork(workInProgress) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
-    }
-  }
+    errorToHandle = error;
 
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      default:
-        break;
-    }
+    try {
+      errorToHandle.message =
+        summary + "\n\nThis error is located at:" + componentStack;
+    } catch (e) {}
+  } else if (typeof error === "string") {
+    errorToHandle = new Error(
+      error + "\n\nThis error is located at:" + componentStack
+    );
+  } else {
+    errorToHandle = new Error("Unspecified error at:" + componentStack);
   }
 
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork
-  };
-};
+  ExceptionsManager.handleException(errorToHandle, false);
 
-// This module is forked in different environments.
-// By default, return `true` to log errors to the console.
-// Forks can return `false` if this isn't desirable.
-function showErrorDialog(capturedError) {
-  return true;
+  // Return false here to prevent ReactFiberErrorLogger default behavior of
+  // logging error details to console.error. Calls to console.error are
+  // automatically routed to the native redbox controller, which we've already
+  // done above by calling ExceptionsManager.
+  return false;
 }
 
 function logCapturedError(capturedError) {
@@ -9892,7 +10146,14 @@ var ReactFiberCommitWork = function(
         }
         var updateQueue = finishedWork.updateQueue;
         if (updateQueue !== null) {
-          commitCallbacks(updateQueue, _instance2);
+          _instance2.props = finishedWork.memoizedProps;
+          _instance2.state = finishedWork.memoizedState;
+          commitUpdateQueue(
+            finishedWork,
+            updateQueue,
+            _instance2,
+            committedExpirationTime
+          );
         }
         return;
       }
@@ -9910,7 +10171,12 @@ var ReactFiberCommitWork = function(
                 break;
             }
           }
-          commitCallbacks(_updateQueue, _instance3);
+          commitUpdateQueue(
+            finishedWork,
+            _updateQueue,
+            _instance3,
+            committedExpirationTime
+          );
         }
         return;
       }
@@ -9935,93 +10201,37 @@ var ReactFiberCommitWork = function(
       }
       case HostPortal: {
         // We have no life-cycles associated with portals.
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
-    }
-  }
-
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case ClassComponent:
-        {
-          var ctor = finishedWork.type;
-          var _instance5 = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            updateQueue !== null && updateQueue.capturedValues !== null,
-            "An error logging effect should not have been scheduled if no errors " +
-              "were captured. This error is likely caused by a bug in React. " +
-              "Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-
-          if (typeof ctor.getDerivedStateFromCatch !== "function") {
-            // To preserve the preexisting retry behavior of error boundaries,
-            // we keep track of which ones already failed during this batch.
-            // This gets reset before we yield back to the browser.
-            // TODO: Warn in strict mode if getDerivedStateFromCatch is
-            // not defined.
-            markLegacyErrorBoundaryAsFailed(_instance5);
-          }
-
-          _instance5.props = finishedWork.memoizedProps;
-          _instance5.state = finishedWork.memoizedState;
-          for (var i = 0; i < capturedErrors.length; i++) {
-            var errorInfo = capturedErrors[i];
-            var _error = errorInfo.value;
-            var stack = errorInfo.stack;
-            logError(finishedWork, errorInfo);
-            _instance5.componentDidCatch(_error, {
-              componentStack: stack !== null ? stack : ""
-            });
-          }
-        }
-        break;
-      case HostRoot: {
-        var _updateQueue2 = finishedWork.updateQueue;
-        invariant(
-          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
-          "An error logging effect should not have been scheduled if no errors " +
-            "were captured. This error is likely caused by a bug in React. " +
-            "Please file an issue."
-        );
-        var _capturedErrors = _updateQueue2.capturedValues;
-        _updateQueue2.capturedValues = null;
-        for (var _i = 0; _i < _capturedErrors.length; _i++) {
-          var _errorInfo = _capturedErrors[_i];
-          logError(finishedWork, _errorInfo);
-          onUncaughtError(_errorInfo.value);
-        }
-        break;
+        return;
       }
-      default:
+      case Profiler: {
+        // We have no life-cycles associated with Profiler.
+        return;
+      }
+      case TimeoutComponent: {
+        // We have no life-cycles associated with Timeouts.
+        return;
+      }
+      default: {
         invariant(
           false,
-          "This unit of work tag cannot capture errors.  This error is " +
+          "This unit of work tag should not have side-effects. This error is " +
             "likely caused by a bug in React. Please file an issue."
         );
+      }
     }
   }
 
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (ref !== null) {
-      var _instance6 = finishedWork.stateNode;
+      var _instance5 = finishedWork.stateNode;
       var instanceToUse = void 0;
       switch (finishedWork.tag) {
         case HostComponent:
-          instanceToUse = getPublicInstance(_instance6);
+          instanceToUse = getPublicInstance(_instance5);
           break;
         default:
-          instanceToUse = _instance6;
+          instanceToUse = _instance5;
       }
       if (typeof ref === "function") {
         ref(instanceToUse);
@@ -10065,9 +10275,9 @@ var ReactFiberCommitWork = function(
     switch (current.tag) {
       case ClassComponent: {
         safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if (typeof _instance7.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance7);
+        var _instance6 = current.stateNode;
+        if (typeof _instance6.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance6);
         }
         return;
       }
@@ -10109,7 +10319,7 @@ var ReactFiberCommitWork = function(
         // If we don't use mutation we drill down into portals here instead.
         (!mutation || node.tag !== HostPortal)
       ) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -10117,12 +10327,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === root) {
+        if (node.return === null || node.return === root) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10133,11 +10343,11 @@ var ReactFiberCommitWork = function(
     // get GC:ed but we don't know which for sure which parent is the current
     // one so we'll settle for GC:ing the subtree of this child. This child
     // itself will be GC:ed when the parent updates the next time.
-    current["return"] = null;
+    current.return = null;
     current.child = null;
     if (current.alternate) {
       current.alternate.child = null;
-      current.alternate["return"] = null;
+      current.alternate.return = null;
     }
   }
 
@@ -10205,7 +10415,6 @@ var ReactFiberCommitWork = function(
 
         commitLifeCycles: commitLifeCycles,
         commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-        commitErrorLogging: commitErrorLogging,
         commitAttachRef: commitAttachRef,
         commitDetachRef: commitDetachRef
       };
@@ -10227,12 +10436,12 @@ var ReactFiberCommitWork = function(
     removeChildFromContainer = mutation.removeChildFromContainer;
 
   function getHostParentFiber(fiber) {
-    var parent = fiber["return"];
+    var parent = fiber.return;
     while (parent !== null) {
       if (isHostParent(parent)) {
         return parent;
       }
-      parent = parent["return"];
+      parent = parent.return;
     }
     invariant(
       false,
@@ -10257,14 +10466,14 @@ var ReactFiberCommitWork = function(
     siblings: while (true) {
       // If we didn't find anything, let's try the next sibling.
       while (node.sibling === null) {
-        if (node["return"] === null || isHostParent(node["return"])) {
+        if (node.return === null || isHostParent(node.return)) {
           // If we pop out of the root or hit the parent the fiber we are the
           // last sibling.
           return null;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
       while (node.tag !== HostComponent && node.tag !== HostText) {
         // If it is not host node and, we might have a host node inside it.
@@ -10278,7 +10487,7 @@ var ReactFiberCommitWork = function(
         if (node.child === null || node.tag === HostPortal) {
           continue siblings;
         } else {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
         }
       }
@@ -10346,7 +10555,7 @@ var ReactFiberCommitWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -10354,12 +10563,12 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === finishedWork) {
+        if (node.return === null || node.return === finishedWork) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10376,7 +10585,7 @@ var ReactFiberCommitWork = function(
 
     while (true) {
       if (!currentParentIsValid) {
-        var parent = node["return"];
+        var parent = node.return;
         findParent: while (true) {
           invariant(
             parent !== null,
@@ -10397,7 +10606,7 @@ var ReactFiberCommitWork = function(
               currentParentIsContainer = true;
               break findParent;
           }
-          parent = parent["return"];
+          parent = parent.return;
         }
         currentParentIsValid = true;
       }
@@ -10418,7 +10627,7 @@ var ReactFiberCommitWork = function(
         currentParent = node.stateNode.containerInfo;
         // Visit children because portals might contain host components.
         if (node.child !== null) {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
           continue;
         }
@@ -10426,7 +10635,7 @@ var ReactFiberCommitWork = function(
         commitUnmount(node);
         // Visit children because we may find more host components below.
         if (node.child !== null) {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
           continue;
         }
@@ -10435,17 +10644,17 @@ var ReactFiberCommitWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === current) {
+        if (node.return === null || node.return === current) {
           return;
         }
-        node = node["return"];
+        node = node.return;
         if (node.tag === HostPortal) {
           // When we go out of the portal, we need to restore the parent.
           // Since we don't keep a stack of them, we will search for it.
           currentParentIsValid = false;
         }
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -10463,8 +10672,8 @@ var ReactFiberCommitWork = function(
         return;
       }
       case HostComponent: {
-        var _instance8 = finishedWork.stateNode;
-        if (_instance8 != null) {
+        var _instance7 = finishedWork.stateNode;
+        if (_instance7 != null) {
           // Commit the work prepared earlier.
           var newProps = finishedWork.memoizedProps;
           // For hydration we reuse the update path but we treat the oldProps
@@ -10477,7 +10686,7 @@ var ReactFiberCommitWork = function(
           finishedWork.updateQueue = null;
           if (updatePayload !== null) {
             commitUpdate(
-              _instance8,
+              _instance7,
               updatePayload,
               type,
               oldProps,
@@ -10506,6 +10715,25 @@ var ReactFiberCommitWork = function(
       case HostRoot: {
         return;
       }
+      case Profiler: {
+        if (enableProfilerTimer) {
+          var onRender = finishedWork.memoizedProps.onRender;
+          onRender(
+            finishedWork.memoizedProps.id,
+            current === null ? "mount" : "update",
+            finishedWork.stateNode.duration,
+            finishedWork.treeBaseTime
+          );
+
+          // Reset actualTime after successful commit.
+          // By default, we append to this time to account for errors and pauses.
+          finishedWork.stateNode.duration = 0;
+        }
+        return;
+      }
+      case TimeoutComponent: {
+        return;
+      }
       default: {
         invariant(
           false,
@@ -10528,7 +10756,6 @@ var ReactFiberCommitWork = function(
       commitDeletion: commitDeletion,
       commitWork: commitWork,
       commitLifeCycles: commitLifeCycles,
-      commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
     };
@@ -10537,6 +10764,347 @@ var ReactFiberCommitWork = function(
   }
 };
 
+var ReactFiberUnwindWork = function(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  computeExpirationForFiber,
+  recalculateCurrentTime,
+  markLegacyErrorBoundaryAsFailed,
+  isAlreadyFailedLegacyErrorBoundary,
+  onUncaughtError,
+  profilerTimer,
+  suspendRoot,
+  retrySuspendedRoot
+) {
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext;
+  var popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
+  var popProvider = newContext.popProvider;
+  var resumeActualRenderTimerIfPaused =
+      profilerTimer.resumeActualRenderTimerIfPaused,
+    recordElapsedActualRenderTime = profilerTimer.recordElapsedActualRenderTime;
+
+  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+    var update = createUpdate(expirationTime);
+    // Unmount the root by rendering null.
+    update.tag = CaptureUpdate;
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    update.payload = { element: null };
+    var error = errorInfo.value;
+    update.callback = function() {
+      onUncaughtError(error);
+      logError(fiber, errorInfo);
+    };
+    return update;
+  }
+
+  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+    var update = createUpdate(expirationTime);
+    update.tag = CaptureUpdate;
+    var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
+    if (
+      enableGetDerivedStateFromCatch &&
+      typeof getDerivedStateFromCatch === "function"
+    ) {
+      var _error = errorInfo.value;
+      update.payload = function() {
+        return getDerivedStateFromCatch(_error);
+      };
+    }
+
+    var inst = fiber.stateNode;
+    if (inst !== null && typeof inst.componentDidCatch === "function") {
+      update.callback = function callback() {
+        if (
+          !enableGetDerivedStateFromCatch ||
+          getDerivedStateFromCatch !== "function"
+        ) {
+          // To preserve the preexisting retry behavior of error boundaries,
+          // we keep track of which ones already failed during this batch.
+          // This gets reset before we yield back to the browser.
+          // TODO: Warn in strict mode if getDerivedStateFromCatch is
+          // not defined.
+          markLegacyErrorBoundaryAsFailed(this);
+        }
+        var error = errorInfo.value;
+        var stack = errorInfo.stack;
+        logError(fiber, errorInfo);
+        this.componentDidCatch(error, {
+          componentStack: stack !== null ? stack : ""
+        });
+      };
+    }
+    return update;
+  }
+
+  function schedulePing(finishedWork) {
+    // Once the promise resolves, we should try rendering the non-
+    // placeholder state again.
+    var currentTime = recalculateCurrentTime();
+    var expirationTime = computeExpirationForFiber(currentTime, finishedWork);
+    var recoveryUpdate = createUpdate(expirationTime);
+    enqueueUpdate(finishedWork, recoveryUpdate, expirationTime);
+    scheduleWork(finishedWork, expirationTime);
+  }
+
+  function throwException(
+    root,
+    returnFiber,
+    sourceFiber,
+    value,
+    renderIsExpired,
+    renderExpirationTime,
+    currentTimeMs
+  ) {
+    // The source fiber did not complete.
+    sourceFiber.effectTag |= Incomplete;
+    // Its effect list is no longer valid.
+    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+
+    if (
+      enableSuspense &&
+      value !== null &&
+      typeof value === "object" &&
+      typeof value.then === "function"
+    ) {
+      // This is a thenable.
+      var _thenable = value;
+
+      var expirationTimeMs = expirationTimeToMs(renderExpirationTime);
+      var startTimeMs = expirationTimeMs - 5000;
+      var elapsedMs = currentTimeMs - startTimeMs;
+      if (elapsedMs < 0) {
+        elapsedMs = 0;
+      }
+      var remainingTimeMs = expirationTimeMs - currentTimeMs;
+
+      // Find the earliest timeout of all the timeouts in the ancestor path.
+      // TODO: Alternatively, we could store the earliest timeout on the context
+      // stack, rather than searching on every suspend.
+      var _workInProgress = returnFiber;
+      var earliestTimeoutMs = -1;
+      searchForEarliestTimeout: do {
+        if (_workInProgress.tag === TimeoutComponent) {
+          var current = _workInProgress.alternate;
+          if (current !== null && current.memoizedState === true) {
+            // A parent Timeout already committed in a placeholder state. We
+            // need to handle this promise immediately. In other words, we
+            // should never suspend inside a tree that already expired.
+            earliestTimeoutMs = 0;
+            break searchForEarliestTimeout;
+          }
+          var timeoutPropMs = _workInProgress.pendingProps.ms;
+          if (typeof timeoutPropMs === "number") {
+            if (timeoutPropMs <= 0) {
+              earliestTimeoutMs = 0;
+              break searchForEarliestTimeout;
+            } else if (
+              earliestTimeoutMs === -1 ||
+              timeoutPropMs < earliestTimeoutMs
+            ) {
+              earliestTimeoutMs = timeoutPropMs;
+            }
+          } else if (earliestTimeoutMs === -1) {
+            earliestTimeoutMs = remainingTimeMs;
+          }
+        }
+        _workInProgress = _workInProgress.return;
+      } while (_workInProgress !== null);
+
+      // Compute the remaining time until the timeout.
+      var msUntilTimeout = earliestTimeoutMs - elapsedMs;
+
+      if (renderExpirationTime === Never || msUntilTimeout > 0) {
+        // There's still time remaining.
+        suspendRoot(root, _thenable, msUntilTimeout, renderExpirationTime);
+        var onResolveOrReject = function() {
+          retrySuspendedRoot(root, renderExpirationTime);
+        };
+        _thenable.then(onResolveOrReject, onResolveOrReject);
+        return;
+      } else {
+        // No time remaining. Need to fallback to placeholder.
+        // Find the nearest timeout that can be retried.
+        _workInProgress = returnFiber;
+        do {
+          switch (_workInProgress.tag) {
+            case HostRoot: {
+              // The root expired, but no fallback was provided. Throw a
+              // helpful error.
+              var message =
+                renderExpirationTime === Sync
+                  ? "A synchronous update was suspended, but no fallback UI " +
+                    "was provided."
+                  : "An update was suspended for longer than the timeout, " +
+                    "but no fallback UI was provided.";
+              value = new Error(message);
+              break;
+            }
+            case TimeoutComponent: {
+              if ((_workInProgress.effectTag & DidCapture) === NoEffect) {
+                _workInProgress.effectTag |= ShouldCapture;
+                var _onResolveOrReject = schedulePing.bind(
+                  null,
+                  _workInProgress
+                );
+                _thenable.then(_onResolveOrReject, _onResolveOrReject);
+                return;
+              }
+              // Already captured during this render. Continue to the next
+              // Timeout ancestor.
+              break;
+            }
+          }
+          _workInProgress = _workInProgress.return;
+        } while (_workInProgress !== null);
+      }
+    }
+
+    // We didn't find a boundary that could handle this type of exception. Start
+    // over and traverse parent path again, this time treating the exception
+    // as an error.
+    value = createCapturedValue(value, sourceFiber);
+    var workInProgress = returnFiber;
+    do {
+      switch (workInProgress.tag) {
+        case HostRoot: {
+          var _errorInfo = value;
+          workInProgress.effectTag |= ShouldCapture;
+          var update = createRootErrorUpdate(
+            workInProgress,
+            _errorInfo,
+            renderExpirationTime
+          );
+          enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
+          return;
+        }
+        case ClassComponent:
+          // Capture and retry
+          var errorInfo = value;
+          var ctor = workInProgress.type;
+          var _instance = workInProgress.stateNode;
+          if (
+            (workInProgress.effectTag & DidCapture) === NoEffect &&
+            ((typeof ctor.getDerivedStateFromCatch === "function" &&
+              enableGetDerivedStateFromCatch) ||
+              (_instance !== null &&
+                typeof _instance.componentDidCatch === "function" &&
+                !isAlreadyFailedLegacyErrorBoundary(_instance)))
+          ) {
+            workInProgress.effectTag |= ShouldCapture;
+            // Schedule the error boundary to re-render using updated state
+            var _update = createClassErrorUpdate(
+              workInProgress,
+              errorInfo,
+              renderExpirationTime
+            );
+            enqueueCapturedUpdate(
+              workInProgress,
+              _update,
+              renderExpirationTime
+            );
+            return;
+          }
+          break;
+        default:
+          break;
+      }
+      workInProgress = workInProgress.return;
+    } while (workInProgress !== null);
+  }
+
+  function unwindWork(workInProgress, renderIsExpired, renderExpirationTime) {
+    switch (workInProgress.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(workInProgress);
+        var effectTag = workInProgress.effectTag;
+        if (effectTag & ShouldCapture) {
+          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostRoot: {
+        popHostContainer(workInProgress);
+        popTopLevelLegacyContextObject(workInProgress);
+        var _effectTag = workInProgress.effectTag;
+        if (_effectTag & ShouldCapture) {
+          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostComponent: {
+        popHostContext(workInProgress);
+        return null;
+      }
+      case TimeoutComponent: {
+        var _effectTag2 = workInProgress.effectTag;
+        if (_effectTag2 & ShouldCapture) {
+          workInProgress.effectTag =
+            (_effectTag2 & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
+      case HostPortal:
+        popHostContainer(workInProgress);
+        return null;
+      case ContextProvider:
+        popProvider(workInProgress);
+        return null;
+      default:
+        return null;
+    }
+  }
+
+  function unwindInterruptedWork(interruptedWork) {
+    switch (interruptedWork.tag) {
+      case ClassComponent: {
+        popLegacyContextProvider(interruptedWork);
+        break;
+      }
+      case HostRoot: {
+        popHostContainer(interruptedWork);
+        popTopLevelLegacyContextObject(interruptedWork);
+        break;
+      }
+      case HostComponent: {
+        popHostContext(interruptedWork);
+        break;
+      }
+      case HostPortal:
+        popHostContainer(interruptedWork);
+        break;
+      case ContextProvider:
+        popProvider(interruptedWork);
+        break;
+      case Profiler:
+        if (enableProfilerTimer) {
+          // Resume in case we're picking up on work that was paused.
+          resumeActualRenderTimerIfPaused();
+          recordElapsedActualRenderTime(interruptedWork);
+        }
+        break;
+      default:
+        break;
+    }
+  }
+
+  return {
+    throwException: throwException,
+    unwindWork: unwindWork,
+    unwindInterruptedWork: unwindInterruptedWork,
+    createRootErrorUpdate: createRootErrorUpdate,
+    createClassErrorUpdate: createClassErrorUpdate
+  };
+};
+
 var NO_CONTEXT = {};
 
 var ReactFiberHostContext = function(config, stack) {
@@ -10721,7 +11289,7 @@ var ReactFiberHydrationContext = function(config) {
 
     var childToDelete = createFiberFromHostInstanceForDeletion();
     childToDelete.stateNode = instance;
-    childToDelete["return"] = returnFiber;
+    childToDelete.return = returnFiber;
     childToDelete.effectTag = Deletion;
 
     // This might seem like it belongs on progressedFirstDeletion. However,
@@ -10919,13 +11487,13 @@ var ReactFiberHydrationContext = function(config) {
   }
 
   function popToNextHostParent(fiber) {
-    var parent = fiber["return"];
+    var parent = fiber.return;
     while (
       parent !== null &&
       parent.tag !== HostComponent &&
       parent.tag !== HostRoot
     ) {
-      parent = parent["return"];
+      parent = parent.return;
     }
     hydrationParentFiber = parent;
   }
@@ -10972,31 +11540,199 @@ var ReactFiberHydrationContext = function(config) {
     return true;
   }
 
-  function resetHydrationState() {
-    hydrationParentFiber = null;
-    nextHydratableInstance = null;
-    isHydrating = false;
+  function resetHydrationState() {
+    hydrationParentFiber = null;
+    nextHydratableInstance = null;
+    isHydrating = false;
+  }
+
+  return {
+    enterHydrationState: enterHydrationState,
+    resetHydrationState: resetHydrationState,
+    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
+    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
+    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
+    popHydrationState: popHydrationState
+  };
+};
+
+// This lets us hook into Fiber to debug what it's doing.
+// See https://github.com/facebook/react/pull/8033.
+// This is not part of the public API, not even for React DevTools.
+// You may only inject a debugTool if you work on React Fiber itself.
+var ReactFiberInstrumentation = {
+  debugTool: null
+};
+
+var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
+
+// TODO: Offscreen updates
+
+function markPendingPriorityLevel(root, expirationTime) {
+  if (enableSuspense) {
+    // Update the latest and earliest pending times
+    var earliestPendingTime = root.earliestPendingTime;
+    if (earliestPendingTime === NoWork) {
+      // No other pending updates.
+      root.earliestPendingTime = root.latestPendingTime = expirationTime;
+    } else {
+      if (earliestPendingTime > expirationTime) {
+        // This is the earliest pending update.
+        root.earliestPendingTime = expirationTime;
+      } else {
+        var latestPendingTime = root.latestPendingTime;
+        if (latestPendingTime < expirationTime) {
+          // This is the latest pending update
+          root.latestPendingTime = expirationTime;
+        }
+      }
+    }
+  }
+}
+
+function markCommittedPriorityLevels(root, currentTime, earliestRemainingTime) {
+  if (enableSuspense) {
+    if (earliestRemainingTime === NoWork) {
+      // Fast path. There's no remaining work. Clear everything.
+      root.earliestPendingTime = NoWork;
+      root.latestPendingTime = NoWork;
+      root.earliestSuspendedTime = NoWork;
+      root.latestSuspendedTime = NoWork;
+      root.latestPingedTime = NoWork;
+      return;
+    }
+
+    // Let's see if the previous latest known pending level was just flushed.
+    var latestPendingTime = root.latestPendingTime;
+    if (latestPendingTime !== NoWork) {
+      if (latestPendingTime < earliestRemainingTime) {
+        // We've flushed all the known pending levels.
+        root.earliestPendingTime = root.latestPendingTime = NoWork;
+      } else {
+        var earliestPendingTime = root.earliestPendingTime;
+        if (earliestPendingTime < earliestRemainingTime) {
+          // We've flushed the earliest known pending level. Set this to the
+          // latest pending time.
+          root.earliestPendingTime = root.latestPendingTime;
+        }
+      }
+    }
+
+    // Now let's handle the earliest remaining level in the whole tree. We need to
+    // decide whether to treat it as a pending level or as suspended. Check
+    // it falls within the range of known suspended levels.
+
+    var earliestSuspendedTime = root.earliestSuspendedTime;
+    if (earliestSuspendedTime === NoWork) {
+      // There's no suspended work. Treat the earliest remaining level as a
+      // pending level.
+      markPendingPriorityLevel(root, earliestRemainingTime);
+      return;
+    }
+
+    var latestSuspendedTime = root.latestSuspendedTime;
+    if (earliestRemainingTime > latestSuspendedTime) {
+      // The earliest remaining level is later than all the suspended work. That
+      // means we've flushed all the suspended work.
+      root.earliestSuspendedTime = NoWork;
+      root.latestSuspendedTime = NoWork;
+      root.latestPingedTime = NoWork;
+
+      // There's no suspended work. Treat the earliest remaining level as a
+      // pending level.
+      markPendingPriorityLevel(root, earliestRemainingTime);
+      return;
+    }
+
+    if (earliestRemainingTime < earliestSuspendedTime) {
+      // The earliest remaining time is earlier than all the suspended work.
+      // Treat it as a pending update.
+      markPendingPriorityLevel(root, earliestRemainingTime);
+      return;
+    }
+
+    // The earliest remaining time falls within the range of known suspended
+    // levels. We should treat this as suspended work.
+  }
+}
+
+function markSuspendedPriorityLevel(root, suspendedTime) {
+  if (enableSuspense) {
+    // First, check the known pending levels and update them if needed.
+    var earliestPendingTime = root.earliestPendingTime;
+    var latestPendingTime = root.latestPendingTime;
+    if (earliestPendingTime === suspendedTime) {
+      if (latestPendingTime === suspendedTime) {
+        // Both known pending levels were suspended. Clear them.
+        root.earliestPendingTime = root.latestPendingTime = NoWork;
+      } else {
+        // The earliest pending level was suspended. Clear by setting it to the
+        // latest pending level.
+        root.earliestPendingTime = latestPendingTime;
+      }
+    } else if (latestPendingTime === suspendedTime) {
+      // The latest pending level was suspended. Clear by setting it to the
+      // latest pending level.
+      root.latestPendingTime = earliestPendingTime;
+    }
+
+    // Next, if we're working on the lowest known suspended level, clear the ping.
+    // TODO: What if a promise suspends and pings before the root completes?
+    var latestSuspendedTime = root.latestSuspendedTime;
+    if (latestSuspendedTime === suspendedTime) {
+      root.latestPingedTime = NoWork;
+    }
+
+    // Finally, update the known suspended levels.
+    var earliestSuspendedTime = root.earliestSuspendedTime;
+    if (earliestSuspendedTime === NoWork) {
+      // No other suspended levels.
+      root.earliestSuspendedTime = root.latestSuspendedTime = suspendedTime;
+    } else {
+      if (earliestSuspendedTime > suspendedTime) {
+        // This is the earliest suspended level.
+        root.earliestSuspendedTime = suspendedTime;
+      } else if (latestSuspendedTime < suspendedTime) {
+        // This is the latest suspended level
+        root.latestSuspendedTime = suspendedTime;
+      }
+    }
+  }
+}
+
+function markPingedPriorityLevel(root, pingedTime) {
+  if (enableSuspense) {
+    var latestSuspendedTime = root.latestSuspendedTime;
+    if (latestSuspendedTime !== NoWork && latestSuspendedTime <= pingedTime) {
+      var latestPingedTime = root.latestPingedTime;
+      if (latestPingedTime === NoWork || latestPingedTime < pingedTime) {
+        root.latestPingedTime = pingedTime;
+      }
+    }
   }
+}
 
-  return {
-    enterHydrationState: enterHydrationState,
-    resetHydrationState: resetHydrationState,
-    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
-    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
-    popHydrationState: popHydrationState
-  };
-};
+function findNextPendingPriorityLevel(root) {
+  if (enableSuspense) {
+    var earliestSuspendedTime = root.earliestSuspendedTime;
+    var earliestPendingTime = root.earliestPendingTime;
+    if (earliestSuspendedTime === NoWork) {
+      // Fast path. There's no suspended work.
+      return earliestPendingTime;
+    }
 
-// This lets us hook into Fiber to debug what it's doing.
-// See https://github.com/facebook/react/pull/8033.
-// This is not part of the public API, not even for React DevTools.
-// You may only inject a debugTool if you work on React Fiber itself.
-var ReactFiberInstrumentation = {
-  debugTool: null
-};
+    // First, check if there's known pending work.
+    if (earliestPendingTime !== NoWork) {
+      return earliestPendingTime;
+    }
 
-var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
+    // Finally, if a suspended level was pinged, work on that. Otherwise there's
+    // nothing to work on.
+    return root.latestPingedTime;
+  } else {
+    return root.current.expirationTime;
+  }
+}
 
 var warnedAboutMissingGetChildContext = void 0;
 
@@ -11247,7 +11983,7 @@ var ReactFiberLegacyContext = function(stack) {
       if (isContextProvider(node)) {
         return node.stateNode.__reactInternalMemoizedMergedChildContext;
       }
-      var parent = node["return"];
+      var parent = node.return;
       invariant(
         parent,
         "Found unexpected detached subtree parent. " +
@@ -11275,7 +12011,7 @@ var ReactFiberLegacyContext = function(stack) {
   };
 };
 
-var ReactFiberNewContext = function(stack) {
+var ReactFiberNewContext = function(stack, isPrimaryRenderer) {
   var createCursor = stack.createCursor,
     push = stack.push,
     pop = stack.pop;
@@ -11293,25 +12029,46 @@ var ReactFiberNewContext = function(stack) {
   function pushProvider(providerFiber) {
     var context = providerFiber.type._context;
 
-    push(changedBitsCursor, context._changedBits, providerFiber);
-    push(valueCursor, context._currentValue, providerFiber);
-    push(providerCursor, providerFiber, providerFiber);
+    if (isPrimaryRenderer) {
+      push(changedBitsCursor, context._changedBits, providerFiber);
+      push(valueCursor, context._currentValue, providerFiber);
+      push(providerCursor, providerFiber, providerFiber);
 
-    context._currentValue = providerFiber.pendingProps.value;
-    context._changedBits = providerFiber.stateNode;
+      context._currentValue = providerFiber.pendingProps.value;
+      context._changedBits = providerFiber.stateNode;
+      {
+        !(
+          context._currentRenderer === null ||
+          context._currentRenderer === rendererSigil
+        )
+          ? warning(
+              false,
+              "Detected multiple renderers concurrently rendering the " +
+                "same context provider. This is currently unsupported."
+            )
+          : void 0;
+        context._currentRenderer = rendererSigil;
+      }
+    } else {
+      push(changedBitsCursor, context._changedBits2, providerFiber);
+      push(valueCursor, context._currentValue2, providerFiber);
+      push(providerCursor, providerFiber, providerFiber);
 
-    {
-      !(
-        context._currentRenderer === null ||
-        context._currentRenderer === rendererSigil
-      )
-        ? warning(
-            false,
-            "Detected multiple renderers concurrently rendering the " +
-              "same context provider. This is currently unsupported."
-          )
-        : void 0;
-      context._currentRenderer = rendererSigil;
+      context._currentValue2 = providerFiber.pendingProps.value;
+      context._changedBits2 = providerFiber.stateNode;
+      {
+        !(
+          context._currentRenderer2 === null ||
+          context._currentRenderer2 === rendererSigil
+        )
+          ? warning(
+              false,
+              "Detected multiple renderers concurrently rendering the " +
+                "same context provider. This is currently unsupported."
+            )
+          : void 0;
+        context._currentRenderer2 = rendererSigil;
+      }
     }
   }
 
@@ -11324,13 +12081,28 @@ var ReactFiberNewContext = function(stack) {
     pop(changedBitsCursor, providerFiber);
 
     var context = providerFiber.type._context;
-    context._currentValue = currentValue;
-    context._changedBits = changedBits;
+    if (isPrimaryRenderer) {
+      context._currentValue = currentValue;
+      context._changedBits = changedBits;
+    } else {
+      context._currentValue2 = currentValue;
+      context._changedBits2 = changedBits;
+    }
+  }
+
+  function getContextCurrentValue(context) {
+    return isPrimaryRenderer ? context._currentValue : context._currentValue2;
+  }
+
+  function getContextChangedBits(context) {
+    return isPrimaryRenderer ? context._changedBits : context._changedBits2;
   }
 
   return {
     pushProvider: pushProvider,
-    popProvider: popProvider
+    popProvider: popProvider,
+    getContextCurrentValue: getContextCurrentValue,
+    getContextChangedBits: getContextChangedBits
   };
 };
 
@@ -11483,10 +12255,17 @@ var warnAboutInvalidUpdates = void 0;
 }
 
 var ReactFiberScheduler = function(config) {
+  var now = config.now,
+    scheduleDeferredCallback = config.scheduleDeferredCallback,
+    cancelDeferredCallback = config.cancelDeferredCallback,
+    prepareForCommit = config.prepareForCommit,
+    resetAfterCommit = config.resetAfterCommit;
+
   var stack = ReactFiberStack();
   var hostContext = ReactFiberHostContext(config, stack);
   var legacyContext = ReactFiberLegacyContext(stack);
-  var newContext = ReactFiberNewContext(stack);
+  var newContext = ReactFiberNewContext(stack, config.isPrimaryRenderer);
+  var profilerTimer = createProfilerTimer(now);
   var popHostContext = hostContext.popHostContext,
     popHostContainer = hostContext.popHostContainer;
   var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
@@ -11502,7 +12281,9 @@ var ReactFiberScheduler = function(config) {
       newContext,
       hydrationContext,
       scheduleWork,
-      computeExpirationForFiber
+      computeExpirationForFiber,
+      profilerTimer,
+      recalculateCurrentTime
     ),
     beginWork = _ReactFiberBeginWork.beginWork;
 
@@ -11511,20 +12292,31 @@ var ReactFiberScheduler = function(config) {
       hostContext,
       legacyContext,
       newContext,
-      hydrationContext
+      hydrationContext,
+      profilerTimer
     ),
     completeWork = _ReactFiberCompleteWo.completeWork;
 
   var _ReactFiberUnwindWork = ReactFiberUnwindWork(
+      config,
       hostContext,
       legacyContext,
       newContext,
       scheduleWork,
-      isAlreadyFailedLegacyErrorBoundary
+      computeExpirationForFiber,
+      recalculateCurrentTime,
+      markLegacyErrorBoundaryAsFailed,
+      isAlreadyFailedLegacyErrorBoundary,
+      onUncaughtError,
+      profilerTimer,
+      suspendRoot,
+      retrySuspendedRoot
     ),
     throwException = _ReactFiberUnwindWork.throwException,
     unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork,
+    createRootErrorUpdate = _ReactFiberUnwindWork.createRootErrorUpdate,
+    createClassErrorUpdate = _ReactFiberUnwindWork.createClassErrorUpdate;
 
   var _ReactFiberCommitWork = ReactFiberCommitWork(
       config,
@@ -11541,15 +12333,20 @@ var ReactFiberScheduler = function(config) {
     commitDeletion = _ReactFiberCommitWork.commitDeletion,
     commitWork = _ReactFiberCommitWork.commitWork,
     commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
-    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
     commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
     commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
 
-  var now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit;
+  var checkActualRenderTimeStackEmpty =
+      profilerTimer.checkActualRenderTimeStackEmpty,
+    pauseActualRenderTimerIfRunning =
+      profilerTimer.pauseActualRenderTimerIfRunning,
+    recordElapsedBaseRenderTimeIfRunning =
+      profilerTimer.recordElapsedBaseRenderTimeIfRunning,
+    resetActualRenderTimer = profilerTimer.resetActualRenderTimer,
+    resumeActualRenderTimerIfPaused =
+      profilerTimer.resumeActualRenderTimerIfPaused,
+    startBaseRenderTimer = profilerTimer.startBaseRenderTimer,
+    stopBaseRenderTimerIfRunning = profilerTimer.stopBaseRenderTimerIfRunning;
 
   // Represents the current time in ms.
 
@@ -11572,6 +12369,8 @@ var ReactFiberScheduler = function(config) {
   var nextRoot = null;
   // The time at which we're currently rendering work.
   var nextRenderExpirationTime = NoWork;
+  var nextLatestTimeoutMs = -1;
+  var nextRenderIsExpired = false;
 
   // The next fiber with an effect that we're currently committing.
   var nextEffect = null;
@@ -11594,7 +12393,18 @@ var ReactFiberScheduler = function(config) {
     stashedWorkInProgressProperties = null;
     isReplayingFailedUnitOfWork = false;
     originalReplayError = null;
-    replayUnitOfWork = function(failedUnitOfWork, error, isAsync) {
+    replayUnitOfWork = function(failedUnitOfWork, thrownValue, isAsync) {
+      if (
+        thrownValue !== null &&
+        typeof thrownValue === "object" &&
+        typeof thrownValue.then === "function"
+      ) {
+        // Don't replay promises. Treat everything else like an error.
+        // TODO: Need to figure out a different strategy if/when we add
+        // support for catching other types.
+        return;
+      }
+
       // Restore the original state of the work-in-progress
       assignFiberPropertiesInDEV(
         failedUnitOfWork,
@@ -11620,12 +12430,17 @@ var ReactFiberScheduler = function(config) {
       }
       // Replay the begin phase.
       isReplayingFailedUnitOfWork = true;
-      originalReplayError = error;
+      originalReplayError = thrownValue;
       invokeGuardedCallback$2(null, workLoop, null, isAsync);
       isReplayingFailedUnitOfWork = false;
       originalReplayError = null;
       if (hasCaughtError()) {
         clearCaughtError();
+
+        if (enableProfilerTimer) {
+          // Stop "base" render timer again (after the re-thrown error).
+          stopBaseRenderTimerIfRunning();
+        }
       } else {
         // If the begin phase did not fail the second time, set this pointer
         // back to the original value.
@@ -11639,10 +12454,10 @@ var ReactFiberScheduler = function(config) {
 
   function resetStack() {
     if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork["return"];
+      var interruptedWork = nextUnitOfWork.return;
       while (interruptedWork !== null) {
         unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork["return"];
+        interruptedWork = interruptedWork.return;
       }
     }
 
@@ -11653,6 +12468,8 @@ var ReactFiberScheduler = function(config) {
 
     nextRoot = null;
     nextRenderExpirationTime = NoWork;
+    nextLatestTimeoutMs = -1;
+    nextRenderIsExpired = false;
     nextUnitOfWork = null;
 
     isRootReadyForCommit = false;
@@ -11767,10 +12584,6 @@ var ReactFiberScheduler = function(config) {
         );
       }
 
-      if (effectTag & ErrLog) {
-        commitErrorLogging(nextEffect, onUncaughtError);
-      }
-
       if (effectTag & Ref) {
         recordEffect();
         commitAttachRef(nextEffect);
@@ -11949,6 +12762,13 @@ var ReactFiberScheduler = function(config) {
       }
     }
 
+    if (enableProfilerTimer) {
+      {
+        checkActualRenderTimeStackEmpty();
+      }
+      resetActualRenderTimer();
+    }
+
     isCommitting = false;
     isWorking = false;
     stopCommitLifeCyclesTimer();
@@ -11960,7 +12780,8 @@ var ReactFiberScheduler = function(config) {
       ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
     }
 
-    var remainingTime = root.current.expirationTime;
+    markCommittedPriorityLevels(root, currentTime, root.current.expirationTime);
+    var remainingTime = findNextPendingPriorityLevel(root);
     if (remainingTime === NoWork) {
       // If there's no remaining work, we can clear the set of already failed
       // error boundaries.
@@ -11977,22 +12798,50 @@ var ReactFiberScheduler = function(config) {
     }
 
     // Check for pending updates.
-    var newExpirationTime = getUpdateExpirationTime(workInProgress);
+    var newExpirationTime = NoWork;
+    switch (workInProgress.tag) {
+      case HostRoot:
+      case ClassComponent: {
+        var updateQueue = workInProgress.updateQueue;
+        if (updateQueue !== null) {
+          newExpirationTime = updateQueue.expirationTime;
+        }
+      }
+    }
 
     // TODO: Calls need to visit stateNode
 
     // Bubble up the earliest expiration time.
-    var child = workInProgress.child;
-    while (child !== null) {
-      if (
-        child.expirationTime !== NoWork &&
-        (newExpirationTime === NoWork ||
-          newExpirationTime > child.expirationTime)
-      ) {
-        newExpirationTime = child.expirationTime;
+    // (And "base" render timers if that feature flag is enabled)
+    if (enableProfilerTimer && workInProgress.mode & ProfileMode) {
+      var treeBaseTime = workInProgress.selfBaseTime;
+      var child = workInProgress.child;
+      while (child !== null) {
+        treeBaseTime += child.treeBaseTime;
+        if (
+          child.expirationTime !== NoWork &&
+          (newExpirationTime === NoWork ||
+            newExpirationTime > child.expirationTime)
+        ) {
+          newExpirationTime = child.expirationTime;
+        }
+        child = child.sibling;
+      }
+      workInProgress.treeBaseTime = treeBaseTime;
+    } else {
+      var _child = workInProgress.child;
+      while (_child !== null) {
+        if (
+          _child.expirationTime !== NoWork &&
+          (newExpirationTime === NoWork ||
+            newExpirationTime > _child.expirationTime)
+        ) {
+          newExpirationTime = _child.expirationTime;
+        }
+        _child = _child.sibling;
       }
-      child = child.sibling;
     }
+
     workInProgress.expirationTime = newExpirationTime;
   }
 
@@ -12010,7 +12859,7 @@ var ReactFiberScheduler = function(config) {
         ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
       }
 
-      var returnFiber = workInProgress["return"];
+      var returnFiber = workInProgress.return;
       var siblingFiber = workInProgress.sibling;
 
       if ((workInProgress.effectTag & Incomplete) === NoEffect) {
@@ -12095,7 +12944,11 @@ var ReactFiberScheduler = function(config) {
         // This fiber did not complete because something threw. Pop values off
         // the stack without entering the complete phase. If this is a boundary,
         // capture values if possible.
-        var _next = unwindWork(workInProgress);
+        var _next = unwindWork(
+          workInProgress,
+          nextRenderIsExpired,
+          nextRenderExpirationTime
+        );
         // Because this fiber did not complete, don't reset its expiration time.
         if (workInProgress.effectTag & DidCapture) {
           // Restarting an error boundary
@@ -12171,7 +13024,19 @@ var ReactFiberScheduler = function(config) {
         workInProgress
       );
     }
-    var next = beginWork(current, workInProgress, nextRenderExpirationTime);
+
+    var next = void 0;
+    if (enableProfilerTimer) {
+      startBaseRenderTimer();
+      next = beginWork(current, workInProgress, nextRenderExpirationTime);
+
+      // Update "base" time if the render wasn't bailed out on.
+      recordElapsedBaseRenderTimeIfRunning(workInProgress);
+      stopBaseRenderTimerIfRunning();
+    } else {
+      next = beginWork(current, workInProgress, nextRenderExpirationTime);
+    }
+
     {
       ReactDebugCurrentFiber.resetCurrentFiber();
       if (isReplayingFailedUnitOfWork) {
@@ -12207,6 +13072,12 @@ var ReactFiberScheduler = function(config) {
       while (nextUnitOfWork !== null && !shouldYield()) {
         nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
       }
+
+      if (enableProfilerTimer) {
+        // If we didn't finish, pause the "actual" render timer.
+        // We'll restart it when we resume work.
+        pauseActualRenderTimerIfRunning();
+      }
     }
   }
 
@@ -12229,6 +13100,7 @@ var ReactFiberScheduler = function(config) {
       resetStack();
       nextRoot = root;
       nextRenderExpirationTime = expirationTime;
+      nextLatestTimeoutMs = -1;
       nextUnitOfWork = createWorkInProgress(
         nextRoot.current,
         null,
@@ -12239,12 +13111,20 @@ var ReactFiberScheduler = function(config) {
 
     var didFatal = false;
 
+    nextRenderIsExpired =
+      !isAsync || nextRenderExpirationTime <= mostRecentCurrentTime;
+
     startWorkLoopTimer(nextUnitOfWork);
 
     do {
       try {
         workLoop(isAsync);
       } catch (thrownValue) {
+        if (enableProfilerTimer) {
+          // Stop "base" render timer in the event of an error.
+          stopBaseRenderTimerIfRunning();
+        }
+
         if (nextUnitOfWork === null) {
           // This is a fatal error.
           didFatal = true;
@@ -12252,13 +13132,19 @@ var ReactFiberScheduler = function(config) {
           break;
         }
 
+        {
+          // Reset global debug state
+          // We assume this is defined in DEV
+          resetCurrentlyProcessingQueue();
+        }
+
         if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
           replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
         }
 
         var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber["return"];
+        var returnFiber = sourceFiber.return;
         if (returnFiber === null) {
           // This is the root. The root could capture its own errors. However,
           // we don't know if it errors before or after we pushed the host
@@ -12270,7 +13156,15 @@ var ReactFiberScheduler = function(config) {
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(returnFiber, sourceFiber, thrownValue);
+        throwException(
+          root,
+          returnFiber,
+          sourceFiber,
+          thrownValue,
+          nextRenderIsExpired,
+          nextRenderExpirationTime,
+          mostRecentCurrentTimeMs
+        );
         nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
       break;
@@ -12304,10 +13198,19 @@ var ReactFiberScheduler = function(config) {
         stopWorkLoopTimer(interruptedBy, didCompleteRoot);
         interruptedBy = null;
         invariant(
-          false,
+          !nextRenderIsExpired,
           "Expired work should have completed. This error is likely caused " +
             "by a bug in React. Please file an issue."
         );
+        markSuspendedPriorityLevel(root, expirationTime);
+        if (nextLatestTimeoutMs >= 0) {
+          setTimeout(function() {
+            retrySuspendedRoot(root, expirationTime);
+          }, nextLatestTimeoutMs);
+        }
+        var firstUnblockedExpirationTime = findNextPendingPriorityLevel(root);
+        onBlock(firstUnblockedExpirationTime);
+        return null;
       }
     } else {
       stopWorkLoopTimer(interruptedBy, didCompleteRoot);
@@ -12318,31 +13221,13 @@ var ReactFiberScheduler = function(config) {
     }
   }
 
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    // TODO: We only support dispatching errors.
-    var capturedValue = createCapturedValue(value, sourceFiber);
-    var update = {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: false,
-      isForced: false,
-      capturedValue: capturedValue,
-      next: null
-    };
-    insertUpdateIntoFiber(boundaryFiber, update);
-    scheduleWork(boundaryFiber, expirationTime);
-  }
-
   function dispatch(sourceFiber, value, expirationTime) {
     invariant(
       !isWorking || isCommitting,
       "dispatch: Cannot dispatch during the render phase."
     );
 
-    // TODO: Handle arrays
-
-    var fiber = sourceFiber["return"];
+    var fiber = sourceFiber.return;
     while (fiber !== null) {
       switch (fiber.tag) {
         case ClassComponent:
@@ -12353,22 +13238,44 @@ var ReactFiberScheduler = function(config) {
             (typeof instance.componentDidCatch === "function" &&
               !isAlreadyFailedLegacyErrorBoundary(instance))
           ) {
-            scheduleCapture(sourceFiber, fiber, value, expirationTime);
+            var errorInfo = createCapturedValue(value, sourceFiber);
+            var update = createClassErrorUpdate(
+              fiber,
+              errorInfo,
+              expirationTime
+            );
+            enqueueUpdate(fiber, update, expirationTime);
+            scheduleWork(fiber, expirationTime);
             return;
           }
           break;
-        // TODO: Handle async boundaries
-        case HostRoot:
-          scheduleCapture(sourceFiber, fiber, value, expirationTime);
+        case HostRoot: {
+          var _errorInfo = createCapturedValue(value, sourceFiber);
+          var _update = createRootErrorUpdate(
+            fiber,
+            _errorInfo,
+            expirationTime
+          );
+          enqueueUpdate(fiber, _update, expirationTime);
+          scheduleWork(fiber, expirationTime);
           return;
+        }
       }
-      fiber = fiber["return"];
+      fiber = fiber.return;
     }
 
     if (sourceFiber.tag === HostRoot) {
       // Error was thrown at the root. There is no parent, so the root
       // itself should capture it.
-      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
+      var rootFiber = sourceFiber;
+      var _errorInfo2 = createCapturedValue(value, rootFiber);
+      var _update2 = createRootErrorUpdate(
+        rootFiber,
+        _errorInfo2,
+        expirationTime
+      );
+      enqueueUpdate(rootFiber, _update2, expirationTime);
+      scheduleWork(rootFiber, expirationTime);
     }
   }
 
@@ -12417,7 +13324,7 @@ var ReactFiberScheduler = function(config) {
     return lastUniqueAsyncExpiration;
   }
 
-  function computeExpirationForFiber(fiber) {
+  function computeExpirationForFiber(currentTime, fiber) {
     var expirationTime = void 0;
     if (expirationContext !== NoWork) {
       // An explicit expiration context was set;
@@ -12438,12 +13345,10 @@ var ReactFiberScheduler = function(config) {
       if (fiber.mode & AsyncMode) {
         if (isBatchingInteractiveUpdates) {
           // This is an interactive update
-          var currentTime = recalculateCurrentTime();
           expirationTime = computeInteractiveExpiration(currentTime);
         } else {
           // This is an async update
-          var _currentTime = recalculateCurrentTime();
-          expirationTime = computeAsyncExpiration(_currentTime);
+          expirationTime = computeAsyncExpiration(currentTime);
         }
       } else {
         // This is a sync update
@@ -12464,15 +13369,27 @@ var ReactFiberScheduler = function(config) {
     return expirationTime;
   }
 
-  function scheduleWork(fiber, expirationTime) {
-    return scheduleWorkImpl(fiber, expirationTime, false);
+  // TODO: Rename this to scheduleTimeout or something
+  function suspendRoot(root, thenable, timeoutMs, suspendedTime) {
+    // Schedule the timeout.
+    if (timeoutMs >= 0 && nextLatestTimeoutMs < timeoutMs) {
+      nextLatestTimeoutMs = timeoutMs;
+    }
+  }
+
+  function retrySuspendedRoot(root, suspendedTime) {
+    markPingedPriorityLevel(root, suspendedTime);
+    var retryTime = findNextPendingPriorityLevel(root);
+    if (retryTime !== NoWork) {
+      requestRetry(root, retryTime);
+    }
   }
 
-  function scheduleWorkImpl(fiber, expirationTime, isErrorRecovery) {
+  function scheduleWork(fiber, expirationTime) {
     recordScheduleUpdate();
 
     {
-      if (!isErrorRecovery && fiber.tag === ClassComponent) {
+      if (fiber.tag === ClassComponent) {
         var instance = fiber.stateNode;
         warnAboutInvalidUpdates(instance);
       }
@@ -12496,7 +13413,7 @@ var ReactFiberScheduler = function(config) {
           node.alternate.expirationTime = expirationTime;
         }
       }
-      if (node["return"] === null) {
+      if (node.return === null) {
         if (node.tag === HostRoot) {
           var root = node.stateNode;
           if (
@@ -12508,6 +13425,8 @@ var ReactFiberScheduler = function(config) {
             interruptedBy = fiber;
             resetStack();
           }
+          markPendingPriorityLevel(root, expirationTime);
+          var nextExpirationTimeToWorkOn = findNextPendingPriorityLevel(root);
           if (
             // If we're in the render phase, we don't need to schedule this root
             // for an update, because we'll do it before we exit...
@@ -12516,8 +13435,7 @@ var ReactFiberScheduler = function(config) {
             // ...unless this is a different root than the one we're rendering.
             nextRoot !== root
           ) {
-            // Add this root to the root schedule.
-            requestWork(root, expirationTime);
+            requestWork(root, nextExpirationTimeToWorkOn);
           }
           if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
             invariant(
@@ -12530,14 +13448,14 @@ var ReactFiberScheduler = function(config) {
           }
         } else {
           {
-            if (!isErrorRecovery && fiber.tag === ClassComponent) {
+            if (fiber.tag === ClassComponent) {
               warnAboutUpdateOnUnmounted(fiber);
             }
           }
           return;
         }
       }
-      node = node["return"];
+      node = node.return;
     }
   }
 
@@ -12625,6 +13543,18 @@ var ReactFiberScheduler = function(config) {
     });
   }
 
+  function requestRetry(root, expirationTime) {
+    if (
+      root.remainingExpirationTime === NoWork ||
+      root.remainingExpirationTime < expirationTime
+    ) {
+      // For a retry, only update the remaining expiration time if it has a
+      // *lower priority* than the existing value. This is because, on a retry,
+      // we should attempt to coalesce as much as possible.
+      requestWork(root, expirationTime);
+    }
+  }
+
   // requestWork is called by the scheduler whenever a root receives an update.
   // It's up to the renderer to call renderRoot at some point in the future.
   function requestWork(root, expirationTime) {
@@ -12774,6 +13704,10 @@ var ReactFiberScheduler = function(config) {
     // the deadline.
     findHighestPriorityRoot();
 
+    if (enableProfilerTimer) {
+      resumeActualRenderTimerIfPaused();
+    }
+
     if (enableUserTimingAPI && deadline !== null) {
       var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
       var timeout = expirationTimeToMs(nextFlushedExpirationTime);
@@ -12789,6 +13723,7 @@ var ReactFiberScheduler = function(config) {
         (!deadlineDidExpire ||
           recalculateCurrentTime() >= nextFlushedExpirationTime)
       ) {
+        recalculateCurrentTime();
         performWorkOnRoot(
           nextFlushedRoot,
           nextFlushedExpirationTime,
@@ -12915,6 +13850,12 @@ var ReactFiberScheduler = function(config) {
             // There's no time left. Mark this root as complete. We'll come
             // back and commit it later.
             root.finishedWork = _finishedWork;
+
+            if (enableProfilerTimer) {
+              // If we didn't finish, pause the "actual" render timer.
+              // We'll restart it when we resume work.
+              pauseActualRenderTimerIfRunning();
+            }
           }
         }
       }
@@ -12976,6 +13917,16 @@ var ReactFiberScheduler = function(config) {
     }
   }
 
+  function onBlock(remainingExpirationTime) {
+    invariant(
+      nextFlushedRoot !== null,
+      "Should be working on a root. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+    // This root was blocked. Unschedule it until there's another update.
+    nextFlushedRoot.remainingExpirationTime = remainingExpirationTime;
+  }
+
   // TODO: Batching should be implemented at the renderer level, not inside
   // the reconciler.
   function batchedUpdates(fn, a) {
@@ -13141,13 +14092,7 @@ var ReactFiberReconciler$1 = function(config) {
       : parentContext;
   }
 
-  function scheduleRootUpdate(
-    current,
-    element,
-    currentTime,
-    expirationTime,
-    callback
-  ) {
+  function scheduleRootUpdate(current, element, expirationTime, callback) {
     {
       if (
         ReactDebugCurrentFiber.phase === "render" &&
@@ -13166,9 +14111,14 @@ var ReactFiberReconciler$1 = function(config) {
       }
     }
 
+    var update = createUpdate(expirationTime);
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    update.payload = { element: element };
+
     callback = callback === undefined ? null : callback;
-    {
-      !(callback === null || typeof callback === "function")
+    if (callback !== null) {
+      !(typeof callback === "function")
         ? warning(
             false,
             "render(...): Expected the last optional `callback` argument to be a " +
@@ -13176,20 +14126,11 @@ var ReactFiberReconciler$1 = function(config) {
             callback
           )
         : void 0;
+      update.callback = callback;
     }
+    enqueueUpdate(current, update, expirationTime);
 
-    var update = {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: callback,
-      isReplace: false,
-      isForced: false,
-      capturedValue: null,
-      next: null
-    };
-    insertUpdateIntoFiber(current, update);
     scheduleWork(current, expirationTime);
-
     return expirationTime;
   }
 
@@ -13197,7 +14138,6 @@ var ReactFiberReconciler$1 = function(config) {
     element,
     container,
     parentComponent,
-    currentTime,
     expirationTime,
     callback
   ) {
@@ -13223,13 +14163,7 @@ var ReactFiberReconciler$1 = function(config) {
       container.pendingContext = context;
     }
 
-    return scheduleRootUpdate(
-      current,
-      element,
-      currentTime,
-      expirationTime,
-      callback
-    );
+    return scheduleRootUpdate(current, element, expirationTime, callback);
   }
 
   function findHostInstance(component) {
@@ -13259,12 +14193,11 @@ var ReactFiberReconciler$1 = function(config) {
     updateContainer: function(element, container, parentComponent, callback) {
       var current = container.current;
       var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(current);
+      var expirationTime = computeExpirationForFiber(currentTime, current);
       return updateContainerAtExpirationTime(
         element,
         container,
         parentComponent,
-        currentTime,
         expirationTime,
         callback
       );
@@ -13276,12 +14209,10 @@ var ReactFiberReconciler$1 = function(config) {
       expirationTime,
       callback
     ) {
-      var currentTime = recalculateCurrentTime();
       return updateContainerAtExpirationTime(
         element,
         container,
         parentComponent,
-        currentTime,
         expirationTime,
         callback
       );
@@ -13367,10 +14298,59 @@ var ReactFiberReconciler$3 =
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3["default"]
-  ? ReactFiberReconciler$3["default"]
+var reactReconciler = ReactFiberReconciler$3.default
+  ? ReactFiberReconciler$3.default
   : ReactFiberReconciler$3;
 
+var hasNativePerformanceNow =
+  typeof performance === "object" && typeof performance.now === "function";
+
+var now = hasNativePerformanceNow
+  ? function() {
+      return performance.now();
+    }
+  : function() {
+      return Date.now();
+    };
+
+var scheduledCallback = null;
+var frameDeadline = 0;
+
+var frameDeadlineObject = {
+  timeRemaining: function() {
+    return frameDeadline - now();
+  },
+  didTimeout: false
+};
+
+function setTimeoutCallback() {
+  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
+  // React API probably changing to boolean rather than time remaining.
+  // Longer-term plan is to rewrite this using shared memory,
+  // And just return the value of the bit as the boolean.
+  frameDeadline = now() + 5;
+
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  if (callback !== null) {
+    callback(frameDeadlineObject);
+  }
+}
+
+// RN has a poor polyfill for requestIdleCallback so we aren't using it.
+// This implementation is only intended for short-term use anyway.
+// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
+function scheduleDeferredCallback(callback) {
+  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
+  scheduledCallback = callback;
+  return setTimeout(setTimeoutCallback, 1);
+}
+
+function cancelDeferredCallback(callbackID) {
+  scheduledCallback = null;
+  clearTimeout(callbackID);
+}
+
 function _classCallCheck$1(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
     throw new TypeError("Cannot call a class as a function");
@@ -13387,7 +14367,6 @@ var nextReactTag = 2;
 /**
  * This is used for refs on host components.
  */
-
 var ReactFabricHostComponent = (function() {
   function ReactFabricHostComponent(tag, viewConfig, props) {
     _classCallCheck$1(this, ReactFabricHostComponent);
@@ -13455,7 +14434,7 @@ var ReactFabricHostComponent = (function() {
   return ReactFabricHostComponent;
 })();
 
-var ReactFabricRenderer = reactReconciler({
+var ReacFabricHostConfig = {
   appendInitialChild: function(parentInstance, child) {
     FabricUIManager.appendChild(parentInstance.node, child.node);
   },
@@ -13479,6 +14458,11 @@ var ReactFabricRenderer = reactReconciler({
       }
     }
 
+    invariant(
+      type !== "RCTView" || !hostContext.isInAParentText,
+      "Nesting of <View> within <Text> is not currently supported."
+    );
+
     var updatePayload = create(props, viewConfig.validAttributes);
 
     var node = FabricUIManager.createNode(
@@ -13502,6 +14486,11 @@ var ReactFabricRenderer = reactReconciler({
     hostContext,
     internalInstanceHandle
   ) {
+    invariant(
+      hostContext.isInAParentText,
+      "Text strings must be rendered within a <Text> component."
+    );
+
     var tag = nextReactTag;
     nextReactTag += 2;
 
@@ -13525,11 +14514,23 @@ var ReactFabricRenderer = reactReconciler({
   ) {
     return false;
   },
-  getRootHostContext: function() {
-    return emptyObject;
+  getRootHostContext: function(rootContainerInstance) {
+    return { isInAParentText: false };
   },
-  getChildHostContext: function() {
-    return emptyObject;
+  getChildHostContext: function(parentHostContext, type) {
+    var prevIsInAParentText = parentHostContext.isInAParentText;
+    var isInAParentText =
+      type === "AndroidTextInput" || // Android
+      type === "RCTMultilineTextInputView" || // iOS
+      type === "RCTSinglelineTextInputView" || // iOS
+      type === "RCTText" ||
+      type === "RCTVirtualText";
+
+    if (prevIsInAParentText !== isInAParentText) {
+      return { isInAParentText: isInAParentText };
+    } else {
+      return parentHostContext;
+    }
   },
   getPublicInstance: function(instance) {
     return instance.canonical;
@@ -13537,6 +14538,9 @@ var ReactFabricRenderer = reactReconciler({
 
   now: now,
 
+  // The Fabric renderer is secondary to the existing React Native renderer.
+  isPrimaryRenderer: false,
+
   prepareForCommit: function() {
     // Noop
   },
@@ -13619,7 +14623,9 @@ var ReactFabricRenderer = reactReconciler({
     },
     replaceContainerChildren: function(container, newChildren) {}
   }
-});
+};
+
+var ReactFabricRenderer = reactReconciler(ReacFabricHostConfig);
 
 // Module provided by RN:
 var getInspectorDataForViewTag = void 0;
@@ -13795,7 +14801,7 @@ var ReactFabric = {
     if (root) {
       // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
       ReactFabricRenderer.updateContainer(null, root, null, function() {
-        roots["delete"](containerTag);
+        roots.delete(containerTag);
       });
     }
   },
@@ -13814,28 +14820,6 @@ var ReactFabric = {
   }
 };
 
-{
-  // $FlowFixMe
-  Object.assign(
-    ReactFabric.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-    {
-      // TODO: none of these work since Fiber. Remove these dependencies.
-      // Used by RCTRenderingPerf, Systrace:
-      ReactDebugTool: {
-        addHook: function() {},
-        removeHook: function() {}
-      },
-      // Used by ReactPerfStallHandler, RCTRenderingPerf:
-      ReactPerf: {
-        start: function() {},
-        stop: function() {},
-        printInclusive: function() {},
-        printWasted: function() {}
-      }
-    }
-  );
-}
-
 ReactFabricRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
@@ -13852,9 +14836,7 @@ var ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var fabric = ReactFabric$3["default"]
-  ? ReactFabric$3["default"]
-  : ReactFabric$3;
+var fabric = ReactFabric$3.default ? ReactFabric$3.default : ReactFabric$3;
 
 module.exports = fabric;
 
diff --git a/Libraries/Renderer/oss/ReactFabric-prod.js b/Libraries/Renderer/oss/ReactFabric-prod.js
index 19ca0dde9e33..dd7e75d707ef 100644
--- a/Libraries/Renderer/oss/ReactFabric-prod.js
+++ b/Libraries/Renderer/oss/ReactFabric-prod.js
@@ -5,7 +5,9 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
+ * @providesModule ReactFabric-prod
  * @preventMunge
+ * @generated
  */
 
 "use strict";
@@ -20,6 +22,7 @@ var invariant = require("fbjs/lib/invariant"),
   React = require("react"),
   emptyObject = require("fbjs/lib/emptyObject"),
   shallowEqual = require("fbjs/lib/shallowEqual"),
+  ExceptionsManager = require("ExceptionsManager"),
   FabricUIManager = require("FabricUIManager"),
   eventPluginOrder = null,
   namesToPlugins = {};
@@ -210,7 +213,7 @@ function getListener(inst, registrationName) {
   return listener;
 }
 function getParent(inst) {
-  do inst = inst["return"];
+  do inst = inst.return;
   while (inst && 5 !== inst.tag);
   return inst ? inst : null;
 }
@@ -917,21 +920,19 @@ injection.injectEventPluginsByName({
   ResponderEventPlugin: ResponderEventPlugin,
   ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
 });
-var hasSymbol = "function" === typeof Symbol && Symbol["for"],
-  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
-  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
-  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
-  REACT_STRICT_MODE_TYPE = hasSymbol
-    ? Symbol["for"]("react.strict_mode")
-    : 60108,
-  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
-  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
-  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
-  REACT_FORWARD_REF_TYPE = hasSymbol
-    ? Symbol["for"]("react.forward_ref")
-    : 60112,
+var hasSymbol = "function" === typeof Symbol && Symbol.for,
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
+  REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 60104,
+  REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 60105,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
+  REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profile_root") : 60108,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for("react.forward_ref") : 60112,
+  REACT_TIMEOUT_TYPE = hasSymbol ? Symbol.for("react.timeout") : 60113,
   MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
 function getIteratorFn(maybeIterable) {
   if (null === maybeIterable || "undefined" === typeof maybeIterable)
@@ -1203,49 +1204,37 @@ function _inherits(subClass, superClass) {
       ? Object.setPrototypeOf(subClass, superClass)
       : (subClass.__proto__ = superClass));
 }
-var now =
-    "object" === typeof performance && "function" === typeof performance.now
-      ? function() {
-          return performance.now();
-        }
-      : function() {
-          return Date.now();
-        },
-  scheduledCallback = null,
-  frameDeadline = 0,
-  frameDeadlineObject = {
-    timeRemaining: function() {
-      return frameDeadline - now();
-    },
-    didTimeout: !1
-  };
-function setTimeoutCallback() {
-  frameDeadline = now() + 5;
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  null !== callback && callback(frameDeadlineObject);
-}
 var ReactCurrentOwner =
   React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
 function getComponentName(fiber) {
-  fiber = fiber.type;
-  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
-  if ("string" === typeof fiber) return fiber;
-  switch (fiber) {
+  var type = fiber.type;
+  if ("function" === typeof type) return type.displayName || type.name;
+  if ("string" === typeof type) return type;
+  switch (type) {
+    case REACT_ASYNC_MODE_TYPE:
+      return "AsyncMode";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_CONTEXT_TYPE:
+      return "Context.Consumer";
     case REACT_FRAGMENT_TYPE:
       return "ReactFragment";
     case REACT_PORTAL_TYPE:
       return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
+    case REACT_PROFILER_TYPE:
+      return "Profiler(" + fiber.pendingProps.id + ")";
+    case REACT_PROVIDER_TYPE:
+      return "Context.Provider";
     case REACT_RETURN_TYPE:
       return "ReactReturn";
+    case REACT_STRICT_MODE_TYPE:
+      return "StrictMode";
   }
-  if ("object" === typeof fiber && null !== fiber)
-    switch (fiber.$$typeof) {
+  if ("object" === typeof type && null !== type)
+    switch (type.$$typeof) {
       case REACT_FORWARD_REF_TYPE:
         return (
-          (fiber = fiber.render.displayName || fiber.render.name || ""),
+          (fiber = type.render.displayName || type.render.name || ""),
           "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
         );
     }
@@ -1253,11 +1242,11 @@ function getComponentName(fiber) {
 }
 function isFiberMountedImpl(fiber) {
   var node = fiber;
-  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
+  if (fiber.alternate) for (; node.return; ) node = node.return;
   else {
     if (0 !== (node.effectTag & 2)) return 1;
-    for (; node["return"]; )
-      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
+    for (; node.return; )
+      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
   }
   return 3 === node.tag ? 2 : 3;
 }
@@ -1284,7 +1273,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       1 === alternate ? null : fiber
     );
   for (var a = fiber, b = alternate; ; ) {
-    var parentA = a["return"],
+    var parentA = a.return,
       parentB = parentA ? parentA.alternate : null;
     if (!parentA || !parentB) break;
     if (parentA.child === parentB.child) {
@@ -1295,7 +1284,7 @@ function findCurrentFiberUsingSlowPath(fiber) {
       }
       invariant(!1, "Unable to find node on an unmounted component.");
     }
-    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
+    if (a.return !== b.return) (a = parentA), (b = parentB);
     else {
       child = !1;
       for (var _child = parentA.child; _child; ) {
@@ -1348,14 +1337,14 @@ function findCurrentHostFiber(parent) {
   if (!parent) return null;
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child["return"] = node), (node = node.child);
+    if (node.child) (node.child.return = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -1367,14 +1356,14 @@ function findCurrentHostFiberWithNoPortals(parent) {
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
     if (node.child && 4 !== node.tag)
-      (node.child["return"] = node), (node = node.child);
+      (node.child.return = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -1383,8 +1372,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
   this.key = key;
-  this.stateNode = this.type = null;
-  this.sibling = this.child = this["return"] = null;
+  this.sibling = this.child = this.return = this.stateNode = this.type = null;
   this.index = 0;
   this.ref = null;
   this.pendingProps = pendingProps;
@@ -1448,12 +1436,24 @@ function createFiberFromElement(element, mode, expirationTime) {
         fiberTag = 11;
         mode |= 2;
         break;
+      case REACT_PROFILER_TYPE:
+        return (
+          (type = new FiberNode(15, element, key, mode | 4)),
+          (type.type = REACT_PROFILER_TYPE),
+          (type.expirationTime = expirationTime),
+          (type.stateNode = { duration: 0, startTime: 0 }),
+          type
+        );
       case REACT_CALL_TYPE:
         fiberTag = 7;
         break;
       case REACT_RETURN_TYPE:
         fiberTag = 9;
         break;
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = 16;
+        mode |= 2;
+        break;
       default:
         if ("object" === typeof type && null !== type)
           switch (type.$$typeof) {
@@ -1575,171 +1575,305 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
         JSCompiler_inline_result = "";
     }
     info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
+    workInProgress = workInProgress.return;
   } while (workInProgress);
   return info;
 }
+function createProfilerTimer() {
+  return {
+    checkActualRenderTimeStackEmpty: function() {},
+    markActualRenderTimeStarted: function() {},
+    pauseActualRenderTimerIfRunning: function() {},
+    recordElapsedActualRenderTime: function() {},
+    resetActualRenderTimer: function() {},
+    resumeActualRenderTimerIfPaused: function() {},
+    recordElapsedBaseRenderTimeIfRunning: function() {},
+    startBaseRenderTimer: function() {},
+    stopBaseRenderTimerIfRunning: function() {}
+  };
+}
 new Set();
+var hasForceUpdate = !1;
 function createUpdateQueue(baseState) {
   return {
-    baseState: baseState,
     expirationTime: 0,
-    first: null,
-    last: null,
-    callbackList: null,
-    hasForceUpdate: !1,
-    isInitialized: !1,
-    capturedValues: null
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function cloneUpdateQueue(currentQueue) {
+  return {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+    tag: 0,
+    payload: null,
+    callback: null,
+    next: null,
+    nextEffect: null
   };
 }
-function insertUpdateIntoQueue(queue, update) {
-  null === queue.last
-    ? (queue.first = queue.last = update)
-    : ((queue.last.next = update), (queue.last = update));
+function appendUpdateToQueue(queue, update, expirationTime) {
+  null === queue.lastUpdate
+    ? (queue.firstUpdate = queue.lastUpdate = update)
+    : ((queue.lastUpdate.next = update), (queue.lastUpdate = update));
+  if (0 === queue.expirationTime || queue.expirationTime > expirationTime)
+    queue.expirationTime = expirationTime;
+}
+function enqueueUpdate(fiber, update, expirationTime) {
+  var alternate = fiber.alternate;
+  if (null === alternate) {
+    var queue1 = fiber.updateQueue;
+    var queue2 = null;
+    null === queue1 &&
+      (queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState));
+  } else
+    (queue1 = fiber.updateQueue),
+      (queue2 = alternate.updateQueue),
+      null === queue1
+        ? null === queue2
+          ? ((queue1 = fiber.updateQueue = createUpdateQueue(
+              fiber.memoizedState
+            )),
+            (queue2 = alternate.updateQueue = createUpdateQueue(
+              alternate.memoizedState
+            )))
+          : (queue1 = fiber.updateQueue = cloneUpdateQueue(queue2))
+        : null === queue2 &&
+          (queue2 = alternate.updateQueue = cloneUpdateQueue(queue1));
+  null === queue2 || queue1 === queue2
+    ? appendUpdateToQueue(queue1, update, expirationTime)
+    : null === queue1.lastUpdate || null === queue2.lastUpdate
+      ? (appendUpdateToQueue(queue1, update, expirationTime),
+        appendUpdateToQueue(queue2, update, expirationTime))
+      : (appendUpdateToQueue(queue1, update, expirationTime),
+        (queue2.lastUpdate = update));
+}
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  var workInProgressQueue = workInProgress.updateQueue;
+  workInProgressQueue =
+    null === workInProgressQueue
+      ? (workInProgress.updateQueue = createUpdateQueue(
+          workInProgress.memoizedState
+        ))
+      : ensureWorkInProgressQueueIsAClone(workInProgress, workInProgressQueue);
+  null === workInProgressQueue.lastCapturedUpdate
+    ? (workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update)
+    : ((workInProgressQueue.lastCapturedUpdate.next = update),
+      (workInProgressQueue.lastCapturedUpdate = update));
   if (
-    0 === queue.expirationTime ||
-    queue.expirationTime > update.expirationTime
+    0 === workInProgressQueue.expirationTime ||
+    workInProgressQueue.expirationTime > renderExpirationTime
   )
-    queue.expirationTime = update.expirationTime;
-}
-var q1 = void 0,
-  q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  var alternateFiber = fiber.alternate,
-    queue1 = fiber.updateQueue;
-  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
-  null !== alternateFiber
-    ? ((fiber = alternateFiber.updateQueue),
-      null === fiber &&
-        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
-    : (fiber = null);
-  q1 = queue1;
-  q2 = fiber !== queue1 ? fiber : null;
+    workInProgressQueue.expirationTime = renderExpirationTime;
 }
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  fiber = q1;
-  var queue2 = q2;
-  null === queue2
-    ? insertUpdateIntoQueue(fiber, update)
-    : null === fiber.last || null === queue2.last
-      ? (insertUpdateIntoQueue(fiber, update),
-        insertUpdateIntoQueue(queue2, update))
-      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  null !== current &&
+    queue === current.updateQueue &&
+    (queue = workInProgress.updateQueue = cloneUpdateQueue(queue));
+  return queue;
 }
-function getStateFromUpdate(update, instance, prevState, props) {
-  update = update.partialState;
-  return "function" === typeof update
-    ? update.call(instance, prevState, props)
-    : update;
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case 1:
+      return (
+        (workInProgress = update.payload),
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress
+      );
+    case 3:
+      workInProgress.effectTag = (workInProgress.effectTag & -1025) | 64;
+    case 0:
+      workInProgress = update.payload;
+      nextProps =
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress;
+      if (null === nextProps || void 0 === nextProps) break;
+      return Object.assign({}, prevState, nextProps);
+    case 2:
+      hasForceUpdate = !0;
+  }
+  return prevState;
 }
 function processUpdateQueue(
-  current,
   workInProgress,
   queue,
-  instance,
   props,
+  instance,
   renderExpirationTime
 ) {
-  null !== current &&
-    current.updateQueue === queue &&
-    (queue = workInProgress.updateQueue = {
-      baseState: queue.baseState,
-      expirationTime: queue.expirationTime,
-      first: queue.first,
-      last: queue.last,
-      isInitialized: queue.isInitialized,
-      capturedValues: queue.capturedValues,
-      callbackList: null,
-      hasForceUpdate: !1
-    });
-  queue.expirationTime = 0;
-  queue.isInitialized
-    ? (current = queue.baseState)
-    : ((current = queue.baseState = workInProgress.memoizedState),
-      (queue.isInitialized = !0));
-  for (
-    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
-    null !== update;
-
+  hasForceUpdate = !1;
+  if (
+    !(0 === queue.expirationTime || queue.expirationTime > renderExpirationTime)
   ) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        remainingExpirationTime > updateExpirationTime
-      )
-        queue.expirationTime = updateExpirationTime;
-      didSkip || ((didSkip = !0), (queue.baseState = current));
-    } else {
-      didSkip ||
-        ((queue.first = update.next),
-        null === queue.first && (queue.last = null));
-      if (update.isReplace)
-        (current = getStateFromUpdate(update, instance, current, props)),
-          (dontMutatePrevState = !0);
-      else if (
-        (updateExpirationTime = getStateFromUpdate(
+    queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+    for (
+      var newBaseState = queue.baseState,
+        newFirstUpdate = null,
+        newExpirationTime = 0,
+        update = queue.firstUpdate,
+        resultState = newBaseState;
+      null !== update;
+
+    ) {
+      var updateExpirationTime = update.expirationTime;
+      if (updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === newFirstUpdate &&
+            ((newFirstUpdate = update), (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > updateExpirationTime)
+        )
+          newExpirationTime = updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
           update,
-          instance,
-          current,
-          props
-        ))
-      )
-        (current = dontMutatePrevState
-          ? Object.assign({}, current, updateExpirationTime)
-          : Object.assign(current, updateExpirationTime)),
-          (dontMutatePrevState = !1);
-      update.isForced && (queue.hasForceUpdate = !0);
-      null !== update.callback &&
-        ((updateExpirationTime = queue.callbackList),
-        null === updateExpirationTime &&
-          (updateExpirationTime = queue.callbackList = []),
-        updateExpirationTime.push(update));
-      null !== update.capturedValue &&
-        ((updateExpirationTime = queue.capturedValues),
-        null === updateExpirationTime
-          ? (queue.capturedValues = [update.capturedValue])
-          : updateExpirationTime.push(update.capturedValue));
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastEffect
+              ? (queue.firstEffect = queue.lastEffect = update)
+              : ((queue.lastEffect.nextEffect = update),
+                (queue.lastEffect = update)));
+      update = update.next;
+    }
+    updateExpirationTime = null;
+    for (update = queue.firstCapturedUpdate; null !== update; ) {
+      var _updateExpirationTime = update.expirationTime;
+      if (_updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === updateExpirationTime &&
+            ((updateExpirationTime = update),
+            null === newFirstUpdate && (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > _updateExpirationTime)
+        )
+          newExpirationTime = _updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
+          update,
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastCapturedEffect
+              ? (queue.firstCapturedEffect = queue.lastCapturedEffect = update)
+              : ((queue.lastCapturedEffect.nextEffect = update),
+                (queue.lastCapturedEffect = update)));
+      update = update.next;
     }
-    update = update.next;
+    null === newFirstUpdate && (queue.lastUpdate = null);
+    null === updateExpirationTime
+      ? (queue.lastCapturedUpdate = null)
+      : (workInProgress.effectTag |= 32);
+    null === newFirstUpdate &&
+      null === updateExpirationTime &&
+      (newBaseState = resultState);
+    queue.baseState = newBaseState;
+    queue.firstUpdate = newFirstUpdate;
+    queue.firstCapturedUpdate = updateExpirationTime;
+    queue.expirationTime = newExpirationTime;
+    workInProgress.memoizedState = resultState;
   }
-  null !== queue.callbackList
-    ? (workInProgress.effectTag |= 32)
-    : null !== queue.first ||
-      queue.hasForceUpdate ||
-      null !== queue.capturedValues ||
-      (workInProgress.updateQueue = null);
-  didSkip || (queue.baseState = current);
-  return current;
 }
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (null !== callbackList)
-    for (
-      queue.callbackList = null, queue = 0;
-      queue < callbackList.length;
-      queue++
-    ) {
-      var update = callbackList[queue],
-        _callback = update.callback;
-      update.callback = null;
-      invariant(
-        "function" === typeof _callback,
-        "Invalid argument passed as callback. Expected a function. Instead received: %s",
-        _callback
-      );
-      _callback.call(context);
-    }
+function callCallback(callback, context) {
+  invariant(
+    "function" === typeof callback,
+    "Invalid argument passed as callback. Expected a function. Instead received: %s",
+    callback
+  );
+  callback.call(context);
+}
+function commitUpdateQueue(finishedWork, finishedQueue, instance) {
+  null !== finishedQueue.firstCapturedUpdate &&
+    (null !== finishedQueue.lastUpdate &&
+      ((finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate),
+      (finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate)),
+    (finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null));
+  finishedWork = finishedQueue.firstEffect;
+  for (
+    finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+    null !== finishedWork;
+
+  ) {
+    var _callback3 = finishedWork.callback;
+    null !== _callback3 &&
+      ((finishedWork.callback = null), callCallback(_callback3, instance));
+    finishedWork = finishedWork.nextEffect;
+  }
+  finishedWork = finishedQueue.firstCapturedEffect;
+  for (
+    finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+    null !== finishedWork;
+
+  )
+    (finishedQueue = finishedWork.callback),
+      null !== finishedQueue &&
+        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
+      (finishedWork = finishedWork.nextEffect);
+}
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+  getDerivedStateFromProps = getDerivedStateFromProps(nextProps, prevState);
+  prevState =
+    null === getDerivedStateFromProps || void 0 === getDerivedStateFromProps
+      ? prevState
+      : Object.assign({}, prevState, getDerivedStateFromProps);
+  workInProgress.memoizedState = prevState;
+  workInProgress = workInProgress.updateQueue;
+  null !== workInProgress &&
+    0 === workInProgress.expirationTime &&
+    (workInProgress.baseState = prevState);
 }
 function ReactFiberClassComponent(
   legacyContext,
   scheduleWork,
   computeExpirationForFiber,
   memoizeProps,
-  memoizeState
+  memoizeState,
+  recalculateCurrentTime
 ) {
   function checkShouldComponentUpdate(
     workInProgress,
@@ -1749,12 +1883,6 @@ function ReactFiberClassComponent(
     newState,
     newContext
   ) {
-    if (
-      null === oldProps ||
-      (null !== workInProgress.updateQueue &&
-        workInProgress.updateQueue.hasForceUpdate)
-    )
-      return !0;
     var instance = workInProgress.stateNode;
     workInProgress = workInProgress.type;
     return "function" === typeof instance.shouldComponentUpdate
@@ -1765,7 +1893,7 @@ function ReactFiberClassComponent(
         : !0;
   }
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
+    instance.updater = classComponentUpdater;
     workInProgress.stateNode = instance;
     instance._reactInternalFiber = workInProgress;
   }
@@ -1781,78 +1909,55 @@ function ReactFiberClassComponent(
     "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
       instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
     instance.state !== workInProgress &&
-      updater.enqueueReplaceState(instance, instance.state, null);
-  }
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    workInProgress = workInProgress.type;
-    if ("function" === typeof workInProgress.getDerivedStateFromProps)
-      return workInProgress.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
   }
   var cacheContext = legacyContext.cacheContext,
     getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged,
-    updater = {
+    classComponentUpdater = {
       isMounted: isMounted,
-      enqueueSetState: function(instance, partialState, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: partialState,
-          callback: callback,
-          isReplace: !1,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueSetState: function(inst, payload, callback) {
+        inst = inst._reactInternalFiber;
+        var currentTime = recalculateCurrentTime();
+        currentTime = computeExpirationForFiber(currentTime, inst);
+        var update = createUpdate(currentTime);
+        update.payload = payload;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, currentTime);
+        scheduleWork(inst, currentTime);
       },
-      enqueueReplaceState: function(instance, state, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: state,
-          callback: callback,
-          isReplace: !0,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueReplaceState: function(inst, payload, callback) {
+        inst = inst._reactInternalFiber;
+        var currentTime = recalculateCurrentTime();
+        currentTime = computeExpirationForFiber(currentTime, inst);
+        var update = createUpdate(currentTime);
+        update.tag = 1;
+        update.payload = payload;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, currentTime);
+        scheduleWork(inst, currentTime);
       },
-      enqueueForceUpdate: function(instance, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: null,
-          callback: callback,
-          isReplace: !1,
-          isForced: !0,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueForceUpdate: function(inst, callback) {
+        inst = inst._reactInternalFiber;
+        var currentTime = recalculateCurrentTime();
+        currentTime = computeExpirationForFiber(currentTime, inst);
+        var update = createUpdate(currentTime);
+        update.tag = 2;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, currentTime);
+        scheduleWork(inst, currentTime);
       }
     };
   return {
     adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: function(workInProgress, props) {
       var ctor = workInProgress.type,
         unmaskedContext = getUnmaskedContext(workInProgress),
@@ -1860,25 +1965,15 @@ function ReactFiberClassComponent(
         context = needsContext
           ? getMaskedContext(workInProgress, unmaskedContext)
           : emptyObject;
-      ctor = new ctor(props, context);
-      var state =
-        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
-      adoptClassInstance(workInProgress, ctor);
-      workInProgress.memoizedState = state;
-      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
-      null !== props &&
-        void 0 !== props &&
-        (workInProgress.memoizedState = Object.assign(
-          {},
-          workInProgress.memoizedState,
-          props
-        ));
+      props = new ctor(props, context);
+      workInProgress.memoizedState =
+        null !== props.state && void 0 !== props.state ? props.state : null;
+      adoptClassInstance(workInProgress, props);
       needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return ctor;
+      return props;
     },
     mountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        current = workInProgress.alternate,
         instance = workInProgress.stateNode,
         props = workInProgress.pendingProps,
         unmaskedContext = getUnmaskedContext(workInProgress);
@@ -1886,6 +1981,20 @@ function ReactFiberClassComponent(
       instance.state = workInProgress.memoizedState;
       instance.refs = emptyObject;
       instance.context = getMaskedContext(workInProgress, unmaskedContext);
+      unmaskedContext = workInProgress.updateQueue;
+      null !== unmaskedContext &&
+        (processUpdateQueue(
+          workInProgress,
+          unmaskedContext,
+          props,
+          instance,
+          renderExpirationTime
+        ),
+        (instance.state = workInProgress.memoizedState));
+      unmaskedContext = workInProgress.type.getDerivedStateFromProps;
+      "function" === typeof unmaskedContext &&
+        (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+        (instance.state = workInProgress.memoizedState));
       "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate ||
         ("function" !== typeof instance.UNSAFE_componentWillMount &&
@@ -1896,32 +2005,36 @@ function ReactFiberClassComponent(
         "function" === typeof instance.UNSAFE_componentWillMount &&
           instance.UNSAFE_componentWillMount(),
         ctor !== instance.state &&
-          updater.enqueueReplaceState(instance, instance.state, null),
-        (ctor = workInProgress.updateQueue),
-        null !== ctor &&
-          (instance.state = processUpdateQueue(
-            current,
-            workInProgress,
-            ctor,
+          classComponentUpdater.enqueueReplaceState(
             instance,
+            instance.state,
+            null
+          ),
+        (unmaskedContext = workInProgress.updateQueue),
+        null !== unmaskedContext &&
+          (processUpdateQueue(
+            workInProgress,
+            unmaskedContext,
             props,
+            instance,
             renderExpirationTime
-          )));
+          ),
+          (instance.state = workInProgress.memoizedState)));
       "function" === typeof instance.componentDidMount &&
         (workInProgress.effectTag |= 4);
     },
     resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
+        instance = workInProgress.stateNode,
+        oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps;
+      instance.props = oldProps;
+      var oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -1932,61 +2045,47 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              null,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
+      hasForceUpdate = !1;
+      var oldState = workInProgress.memoizedState;
+      oldContext = instance.state = oldState;
+      var updateQueue = workInProgress.updateQueue;
+      null !== updateQueue &&
+        (processUpdateQueue(
           workInProgress,
-          instance,
+          updateQueue,
           newProps,
+          instance,
           renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue = workInProgress.updateQueue;
-        null !== _updateQueue &&
-          (_updateQueue.baseState = Object.assign(
-            {},
-            _updateQueue.baseState,
-            derivedStateFromProps
-          ));
-      }
+        ),
+        (oldContext = workInProgress.memoizedState));
       if (
-        !(
-          oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
-          hasContextChanged() ||
-          (null !== workInProgress.updateQueue &&
-            workInProgress.updateQueue.hasForceUpdate)
-        )
+        oldProps === newProps &&
+        oldState === oldContext &&
+        !hasContextChanged() &&
+        !hasForceUpdate
       )
         return (
           "function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
           !1
         );
-      (oldProps = checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldContext,
-        renderExpirationTime,
-        newUnmaskedContext
-      ))
+      "function" === typeof getDerivedStateFromProps &&
+        (applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        ),
+        (oldContext = workInProgress.memoizedState));
+      (renderExpirationTime =
+        hasForceUpdate ||
+        checkShouldComponentUpdate(
+          workInProgress,
+          oldProps,
+          newProps,
+          oldState,
+          oldContext,
+          newUnmaskedContext
+        ))
         ? (ctor ||
             ("function" !== typeof instance.UNSAFE_componentWillMount &&
               "function" !== typeof instance.componentWillMount) ||
@@ -1998,12 +2097,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4))
         : ("function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
+          (workInProgress.memoizedProps = newProps),
+          (workInProgress.memoizedState = oldContext));
       instance.props = newProps;
-      instance.state = renderExpirationTime;
+      instance.state = oldContext;
       instance.context = newUnmaskedContext;
-      return oldProps;
+      return renderExpirationTime;
     },
     updateClassInstance: function(
       current,
@@ -2011,16 +2110,16 @@ function ReactFiberClassComponent(
       renderExpirationTime
     ) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
+        instance = workInProgress.stateNode,
+        oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps;
+      instance.props = oldProps;
+      var oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2031,47 +2130,24 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
+      hasForceUpdate = !1;
       oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              current,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
+      var newState = (instance.state = oldContext),
+        updateQueue = workInProgress.updateQueue;
+      null !== updateQueue &&
+        (processUpdateQueue(
           workInProgress,
-          instance,
+          updateQueue,
           newProps,
+          instance,
           renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue3 = workInProgress.updateQueue;
-        null !== _updateQueue3 &&
-          (_updateQueue3.baseState = Object.assign(
-            {},
-            _updateQueue3.baseState,
-            derivedStateFromProps
-          ));
-      }
+        ),
+        (newState = workInProgress.memoizedState));
       if (
-        !(
-          oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
-          hasContextChanged() ||
-          (null !== workInProgress.updateQueue &&
-            workInProgress.updateQueue.hasForceUpdate)
-        )
+        oldProps === newProps &&
+        oldContext === newState &&
+        !hasContextChanged() &&
+        !hasForceUpdate
       )
         return (
           "function" !== typeof instance.componentDidUpdate ||
@@ -2081,36 +2157,45 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
+            (workInProgress.effectTag |= 256),
           !1
         );
-      (derivedStateFromProps = checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldContext,
-        renderExpirationTime,
-        newUnmaskedContext
-      ))
+      "function" === typeof getDerivedStateFromProps &&
+        (applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        ),
+        (newState = workInProgress.memoizedState));
+      (renderExpirationTime =
+        hasForceUpdate ||
+        checkShouldComponentUpdate(
+          workInProgress,
+          oldProps,
+          newProps,
+          oldContext,
+          newState,
+          newUnmaskedContext
+        ))
         ? (ctor ||
             ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
               "function" !== typeof instance.componentWillUpdate) ||
             ("function" === typeof instance.componentWillUpdate &&
               instance.componentWillUpdate(
                 newProps,
-                renderExpirationTime,
+                newState,
                 newUnmaskedContext
               ),
             "function" === typeof instance.UNSAFE_componentWillUpdate &&
               instance.UNSAFE_componentWillUpdate(
                 newProps,
-                renderExpirationTime,
+                newState,
                 newUnmaskedContext
               )),
           "function" === typeof instance.componentDidUpdate &&
             (workInProgress.effectTag |= 4),
           "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 2048))
+            (workInProgress.effectTag |= 256))
         : ("function" !== typeof instance.componentDidUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
@@ -2118,13 +2203,13 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
+            (workInProgress.effectTag |= 256),
+          (workInProgress.memoizedProps = newProps),
+          (workInProgress.memoizedState = newState));
       instance.props = newProps;
-      instance.state = renderExpirationTime;
+      instance.state = newState;
       instance.context = newUnmaskedContext;
-      return derivedStateFromProps;
+      return renderExpirationTime;
     }
   };
 }
@@ -2248,11 +2333,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, textContent, expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function updateElement(returnFiber, current, element, expirationTime) {
@@ -2260,7 +2345,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       return (
         (expirationTime = useFiber(current, element.props, expirationTime)),
         (expirationTime.ref = coerceRef(returnFiber, current, element)),
-        (expirationTime["return"] = returnFiber),
+        (expirationTime.return = returnFiber),
         expirationTime
       );
     expirationTime = createFiberFromElement(
@@ -2269,7 +2354,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       expirationTime
     );
     expirationTime.ref = coerceRef(returnFiber, current, element);
-    expirationTime["return"] = returnFiber;
+    expirationTime.return = returnFiber;
     return expirationTime;
   }
   function updatePortal(returnFiber, current, portal, expirationTime) {
@@ -2285,11 +2370,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, portal.children || [], expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function updateFragment(returnFiber, current, fragment, expirationTime, key) {
@@ -2301,11 +2386,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           key
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, fragment, expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function createChild(returnFiber, newChild, expirationTime) {
@@ -2316,7 +2401,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (newChild["return"] = returnFiber),
+        (newChild.return = returnFiber),
         newChild
       );
     if ("object" === typeof newChild && null !== newChild) {
@@ -2329,7 +2414,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               expirationTime
             )),
             (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
-            (expirationTime["return"] = returnFiber),
+            (expirationTime.return = returnFiber),
             expirationTime
           );
         case REACT_PORTAL_TYPE:
@@ -2339,7 +2424,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (newChild["return"] = returnFiber),
+            (newChild.return = returnFiber),
             newChild
           );
       }
@@ -2351,7 +2436,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime,
             null
           )),
-          (newChild["return"] = returnFiber),
+          (newChild.return = returnFiber),
           newChild
         );
       throwOnInvalidObjectType(returnFiber, newChild);
@@ -2538,17 +2623,21 @@ function ChildReconciler(shouldTrackSideEffects) {
           newChildren[newIdx],
           expirationTime
         ))
-      ) {
-        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
-          oldFiber["delete"](
+      )
+        shouldTrackSideEffects &&
+          null !== nextOldFiber.alternate &&
+          oldFiber.delete(
             null === nextOldFiber.key ? newIdx : nextOldFiber.key
-          );
-        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (resultingFirstChild = nextOldFiber)
-          : (previousNewFiber.sibling = nextOldFiber);
-        previousNewFiber = nextOldFiber;
-      }
+          ),
+          (currentFirstChild = placeChild(
+            nextOldFiber,
+            currentFirstChild,
+            newIdx
+          )),
+          null === previousNewFiber
+            ? (resultingFirstChild = nextOldFiber)
+            : (previousNewFiber.sibling = nextOldFiber),
+          (previousNewFiber = nextOldFiber);
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2622,24 +2711,22 @@ function ChildReconciler(shouldTrackSideEffects) {
       !step.done;
       newIdx++, step = newChildrenIterable.next()
     )
-      if (
-        ((step = updateFromMap(
-          oldFiber,
-          returnFiber,
-          newIdx,
-          step.value,
-          expirationTime
-        )),
-        null !== step)
-      ) {
-        if (shouldTrackSideEffects && null !== step.alternate)
-          oldFiber["delete"](null === step.key ? newIdx : step.key);
-        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (iteratorFn = step)
-          : (previousNewFiber.sibling = step);
-        previousNewFiber = step;
-      }
+      (step = updateFromMap(
+        oldFiber,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      )),
+        null !== step &&
+          (shouldTrackSideEffects &&
+            null !== step.alternate &&
+            oldFiber.delete(null === step.key ? newIdx : step.key),
+          (currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+          null === previousNewFiber
+            ? (iteratorFn = step)
+            : (previousNewFiber.sibling = step),
+          (previousNewFiber = step));
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2678,7 +2765,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     isObject,
                     newChild
                   );
-                  currentFirstChild["return"] = returnFiber;
+                  currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2695,7 +2782,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   expirationTime,
                   newChild.key
                 )),
-                (currentFirstChild["return"] = returnFiber),
+                (currentFirstChild.return = returnFiber),
                 (returnFiber = currentFirstChild))
               : ((expirationTime = createFiberFromElement(
                   newChild,
@@ -2707,7 +2794,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   currentFirstChild,
                   newChild
                 )),
-                (expirationTime["return"] = returnFiber),
+                (expirationTime.return = returnFiber),
                 (returnFiber = expirationTime));
           }
           return placeSingleChild(returnFiber);
@@ -2731,7 +2818,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     newChild.children || [],
                     expirationTime
                   );
-                  currentFirstChild["return"] = returnFiber;
+                  currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2746,7 +2833,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             );
-            currentFirstChild["return"] = returnFiber;
+            currentFirstChild.return = returnFiber;
             returnFiber = currentFirstChild;
           }
           return placeSingleChild(returnFiber);
@@ -2761,7 +2848,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               newChild,
               expirationTime
             )),
-            (currentFirstChild["return"] = returnFiber),
+            (currentFirstChild.return = returnFiber),
             (returnFiber = currentFirstChild))
           : (deleteRemainingChildren(returnFiber, currentFirstChild),
             (currentFirstChild = createFiberFromText(
@@ -2769,7 +2856,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (currentFirstChild["return"] = returnFiber),
+            (currentFirstChild.return = returnFiber),
             (returnFiber = currentFirstChild)),
         placeSingleChild(returnFiber)
       );
@@ -2811,7 +2898,9 @@ function ReactFiberBeginWork(
   newContext,
   hydrationContext,
   scheduleWork,
-  computeExpirationForFiber
+  computeExpirationForFiber,
+  profilerTimer,
+  recalculateCurrentTime
 ) {
   function reconcileChildren(current, workInProgress, nextChildren) {
     reconcileChildrenAtExpirationTime(
@@ -2855,10 +2944,10 @@ function ReactFiberBeginWork(
     workInProgress,
     shouldUpdate,
     hasContext,
-    didCaptureError,
     renderExpirationTime
   ) {
     markRef(current, workInProgress);
+    var didCaptureError = 0 !== (workInProgress.effectTag & 64);
     if (!shouldUpdate && !didCaptureError)
       return (
         hasContext && invalidateContextProvider(workInProgress, !1),
@@ -2906,11 +2995,8 @@ function ReactFiberBeginWork(
     renderExpirationTime
   ) {
     var fiber = workInProgress.child;
-    for (
-      null !== fiber && (fiber["return"] = workInProgress);
-      null !== fiber;
-
-    ) {
+    null !== fiber && (fiber.return = workInProgress);
+    for (; null !== fiber; ) {
       switch (fiber.tag) {
         case 12:
           var nextFiber = fiber.stateNode | 0;
@@ -2933,7 +3019,7 @@ function ReactFiberBeginWork(
               )
                 alternate.expirationTime = renderExpirationTime;
               else break;
-              nextFiber = nextFiber["return"];
+              nextFiber = nextFiber.return;
             }
             nextFiber = null;
           } else nextFiber = fiber.child;
@@ -2944,7 +3030,7 @@ function ReactFiberBeginWork(
         default:
           nextFiber = fiber.child;
       }
-      if (null !== nextFiber) nextFiber["return"] = fiber;
+      if (null !== nextFiber) nextFiber.return = fiber;
       else
         for (nextFiber = fiber; null !== nextFiber; ) {
           if (nextFiber === workInProgress) {
@@ -2953,10 +3039,11 @@ function ReactFiberBeginWork(
           }
           fiber = nextFiber.sibling;
           if (null !== fiber) {
+            fiber.return = nextFiber.return;
             nextFiber = fiber;
             break;
           }
-          nextFiber = nextFiber["return"];
+          nextFiber = nextFiber.return;
         }
       fiber = nextFiber;
     }
@@ -2968,8 +3055,10 @@ function ReactFiberBeginWork(
   ) {
     var context = workInProgress.type._context,
       newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps;
-    if (!hasLegacyContextChanged() && oldProps === newProps)
+      oldProps = workInProgress.memoizedProps,
+      canBailOnProps = !0;
+    if (hasLegacyContextChanged()) canBailOnProps = !1;
+    else if (oldProps === newProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
@@ -2979,7 +3068,7 @@ function ReactFiberBeginWork(
     workInProgress.memoizedProps = newProps;
     if (null === oldProps) newValue = 1073741823;
     else if (oldProps.value === newProps.value) {
-      if (oldProps.children === newProps.children)
+      if (oldProps.children === newProps.children && canBailOnProps)
         return (
           (workInProgress.stateNode = 0),
           pushProvider(workInProgress),
@@ -2993,7 +3082,7 @@ function ReactFiberBeginWork(
           (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
         (oldValue !== oldValue && newValue !== newValue)
       ) {
-        if (oldProps.children === newProps.children)
+        if (oldProps.children === newProps.children && canBailOnProps)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3008,7 +3097,7 @@ function ReactFiberBeginWork(
         (newValue |= 0),
         0 === newValue)
       ) {
-        if (oldProps.children === newProps.children)
+        if (oldProps.children === newProps.children && canBailOnProps)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3040,14 +3129,14 @@ function ReactFiberBeginWork(
         current.expirationTime
       );
       workInProgress.child = newChild;
-      for (newChild["return"] = workInProgress; null !== current.sibling; )
+      for (newChild.return = workInProgress; null !== current.sibling; )
         (current = current.sibling),
           (newChild = newChild.sibling = createWorkInProgress(
             current,
             current.pendingProps,
             current.expirationTime
           )),
-          (newChild["return"] = workInProgress);
+          (newChild.return = workInProgress);
       newChild.sibling = null;
     }
     return workInProgress.child;
@@ -3057,6 +3146,8 @@ function ReactFiberBeginWork(
     pushHostContext = hostContext.pushHostContext,
     pushHostContainer = hostContext.pushHostContainer,
     pushProvider = newContext.pushProvider,
+    getContextCurrentValue = newContext.getContextCurrentValue,
+    getContextChangedBits = newContext.getContextChangedBits,
     getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     hasLegacyContextChanged = legacyContext.hasContextChanged,
@@ -3076,10 +3167,10 @@ function ReactFiberBeginWork(
     },
     function(workInProgress, nextState) {
       workInProgress.memoizedState = nextState;
-    }
+    },
+    recalculateCurrentTime
   );
   var adoptClassInstance = config.adoptClassInstance,
-    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
     constructClassInstance = config.constructClassInstance,
     mountClassInstance = config.mountClassInstance,
     resumeMountClassInstance = config.resumeMountClassInstance,
@@ -3128,20 +3219,13 @@ function ReactFiberBeginWork(
               (workInProgress.tag = 2),
               (workInProgress.memoizedState =
                 null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
-                ((props = callGetDerivedStateFromProps(
+              (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
+              "function" === typeof unmaskedContext &&
+                applyDerivedStateFromProps(
                   workInProgress,
-                  fn,
-                  props,
-                  workInProgress.memoizedState
-                )),
-                null !== props &&
-                  void 0 !== props &&
-                  (workInProgress.memoizedState = Object.assign(
-                    {},
-                    workInProgress.memoizedState,
-                    props
-                  ))),
+                  unmaskedContext,
+                  props
+                ),
               (props = pushLegacyContextProvider(workInProgress)),
               adoptClassInstance(workInProgress, fn),
               mountClassInstance(workInProgress, renderExpirationTime),
@@ -3150,7 +3234,6 @@ function ReactFiberBeginWork(
                 workInProgress,
                 !0,
                 props,
-                !1,
                 renderExpirationTime
               )))
             : ((workInProgress.tag = 1),
@@ -3178,103 +3261,100 @@ function ReactFiberBeginWork(
             current
           );
         case 2:
-          props = pushLegacyContextProvider(workInProgress);
-          null === current
-            ? null === workInProgress.stateNode
-              ? (constructClassInstance(
-                  workInProgress,
-                  workInProgress.pendingProps
-                ),
-                mountClassInstance(workInProgress, renderExpirationTime),
-                (fn = !0))
-              : (fn = resumeMountClassInstance(
+          return (
+            (props = pushLegacyContextProvider(workInProgress)),
+            null === current
+              ? null === workInProgress.stateNode
+                ? (constructClassInstance(
+                    workInProgress,
+                    workInProgress.pendingProps,
+                    renderExpirationTime
+                  ),
+                  mountClassInstance(workInProgress, renderExpirationTime),
+                  (fn = !0))
+                : (fn = resumeMountClassInstance(
+                    workInProgress,
+                    renderExpirationTime
+                  ))
+              : (fn = updateClassInstance(
+                  current,
                   workInProgress,
                   renderExpirationTime
-                ))
-            : (fn = updateClassInstance(
-                current,
-                workInProgress,
-                renderExpirationTime
-              ));
-          unmaskedContext = !1;
-          var updateQueue = workInProgress.updateQueue;
-          null !== updateQueue &&
-            null !== updateQueue.capturedValues &&
-            (unmaskedContext = fn = !0);
-          return finishClassComponent(
-            current,
-            workInProgress,
-            fn,
-            props,
-            unmaskedContext,
-            renderExpirationTime
-          );
-        case 3:
-          a: if (
-            (pushHostRootContext(workInProgress),
-            (fn = workInProgress.updateQueue),
-            null !== fn)
-          ) {
-            unmaskedContext = workInProgress.memoizedState;
-            props = processUpdateQueue(
+                )),
+            finishClassComponent(
               current,
               workInProgress,
               fn,
-              null,
-              null,
+              props,
               renderExpirationTime
-            );
-            workInProgress.memoizedState = props;
-            fn = workInProgress.updateQueue;
-            if (null !== fn && null !== fn.capturedValues) fn = null;
-            else if (unmaskedContext === props) {
-              resetHydrationState();
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-              break a;
-            } else fn = props.element;
-            unmaskedContext = workInProgress.stateNode;
-            (null === current || null === current.child) &&
-            unmaskedContext.hydrate &&
-            enterHydrationState(workInProgress)
-              ? ((workInProgress.effectTag |= 2),
-                (workInProgress.child = mountChildFibers(
+            )
+          );
+        case 3:
+          return (
+            pushHostRootContext(workInProgress),
+            (props = workInProgress.updateQueue),
+            null !== props
+              ? ((fn = workInProgress.memoizedState),
+                (fn = null !== fn ? fn.element : null),
+                processUpdateQueue(
                   workInProgress,
+                  props,
+                  workInProgress.pendingProps,
                   null,
-                  fn,
                   renderExpirationTime
-                )))
+                ),
+                (props = workInProgress.memoizedState.element),
+                props === fn
+                  ? (resetHydrationState(),
+                    (current = bailoutOnAlreadyFinishedWork(
+                      current,
+                      workInProgress
+                    )))
+                  : ((fn = workInProgress.stateNode),
+                    (null === current || null === current.child) &&
+                    fn.hydrate &&
+                    enterHydrationState(workInProgress)
+                      ? ((workInProgress.effectTag |= 2),
+                        (workInProgress.child = mountChildFibers(
+                          workInProgress,
+                          null,
+                          props,
+                          renderExpirationTime
+                        )))
+                      : (resetHydrationState(),
+                        reconcileChildren(current, workInProgress, props)),
+                    (current = workInProgress.child)))
               : (resetHydrationState(),
-                reconcileChildren(current, workInProgress, fn));
-            workInProgress.memoizedState = props;
-            current = workInProgress.child;
-          } else
-            resetHydrationState(),
-              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
-          return current;
+                (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                ))),
+            current
+          );
         case 5:
           a: {
             pushHostContext(workInProgress);
             null === current &&
               tryToClaimNextHydratableInstance(workInProgress);
             props = workInProgress.type;
-            updateQueue = workInProgress.memoizedProps;
+            var memoizedProps = workInProgress.memoizedProps;
             fn = workInProgress.pendingProps;
             unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && updateQueue === fn) {
+            if (!hasLegacyContextChanged() && memoizedProps === fn) {
               if (
-                (updateQueue =
+                (memoizedProps =
                   workInProgress.mode & 1 &&
                   shouldDeprioritizeSubtree(props, fn))
               )
                 workInProgress.expirationTime = 1073741823;
-              if (!updateQueue || 1073741823 !== renderExpirationTime) {
+              if (!memoizedProps || 1073741823 !== renderExpirationTime) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
             }
-            updateQueue = fn.children;
+            memoizedProps = fn.children;
             shouldSetTextContent(props, fn)
-              ? (updateQueue = null)
+              ? (memoizedProps = null)
               : unmaskedContext &&
                 shouldSetTextContent(props, unmaskedContext) &&
                 (workInProgress.effectTag |= 16);
@@ -3285,7 +3365,7 @@ function ReactFiberBeginWork(
               ? ((workInProgress.expirationTime = 1073741823),
                 (workInProgress.memoizedProps = fn),
                 (current = null))
-              : (reconcileChildren(current, workInProgress, updateQueue),
+              : (reconcileChildren(current, workInProgress, memoizedProps),
                 (workInProgress.memoizedProps = fn),
                 (current = workInProgress.child));
           }
@@ -3325,6 +3405,8 @@ function ReactFiberBeginWork(
           );
         case 9:
           return null;
+        case 16:
+          return null;
         case 4:
           return (
             pushHostContainer(
@@ -3351,14 +3433,21 @@ function ReactFiberBeginWork(
           );
         case 14:
           return (
-            (renderExpirationTime = workInProgress.type.render),
-            (renderExpirationTime = renderExpirationTime(
-              workInProgress.pendingProps,
-              workInProgress.ref
-            )),
-            reconcileChildren(current, workInProgress, renderExpirationTime),
-            (workInProgress.memoizedProps = renderExpirationTime),
-            workInProgress.child
+            (props = workInProgress.type.render),
+            (renderExpirationTime = workInProgress.pendingProps),
+            (fn = workInProgress.ref),
+            hasLegacyContextChanged() ||
+            workInProgress.memoizedProps !== renderExpirationTime ||
+            fn !== (null !== current ? current.ref : null)
+              ? ((props = props(renderExpirationTime, fn)),
+                reconcileChildren(current, workInProgress, props),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
           );
         case 10:
           return (
@@ -3397,9 +3486,26 @@ function ReactFiberBeginWork(
                 )),
             current
           );
-        case 13:
-          return updateContextProvider(
-            current,
+        case 15:
+          return (
+            (renderExpirationTime = workInProgress.pendingProps),
+            workInProgress.memoizedProps === renderExpirationTime
+              ? (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                ))
+              : (reconcileChildren(
+                  current,
+                  workInProgress,
+                  renderExpirationTime.children
+                ),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child)),
+            current
+          );
+        case 13:
+          return updateContextProvider(
+            current,
             workInProgress,
             renderExpirationTime
           );
@@ -3407,13 +3513,13 @@ function ReactFiberBeginWork(
           a: {
             fn = workInProgress.type;
             unmaskedContext = workInProgress.pendingProps;
-            updateQueue = workInProgress.memoizedProps;
-            props = fn._currentValue;
-            var changedBits = fn._changedBits;
+            memoizedProps = workInProgress.memoizedProps;
+            props = getContextCurrentValue(fn);
+            var changedBits = getContextChangedBits(fn);
             if (
               hasLegacyContextChanged() ||
               0 !== changedBits ||
-              updateQueue !== unmaskedContext
+              memoizedProps !== unmaskedContext
             ) {
               workInProgress.memoizedProps = unmaskedContext;
               var observedBits = unmaskedContext.unstable_observedBits;
@@ -3427,12 +3533,13 @@ function ReactFiberBeginWork(
                   changedBits,
                   renderExpirationTime
                 );
-              else if (updateQueue === unmaskedContext) {
+              else if (memoizedProps === unmaskedContext) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
               renderExpirationTime = unmaskedContext.children;
               renderExpirationTime = renderExpirationTime(props);
+              workInProgress.effectTag |= 1;
               reconcileChildren(current, workInProgress, renderExpirationTime);
               current = workInProgress.child;
             } else
@@ -3463,17 +3570,16 @@ function ReactFiberCompleteWork(
       if (5 === node.tag || 6 === node.tag)
         appendInitialChild(parent, node.stateNode);
       else if (4 !== node.tag && null !== node.child) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
       if (node === workInProgress) break;
       for (; null === node.sibling; ) {
-        if (null === node["return"] || node["return"] === workInProgress)
-          return;
-        node = node["return"];
+        if (null === node.return || node.return === workInProgress) return;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -3514,17 +3620,16 @@ function ReactFiberCompleteWork(
           if (5 === node.tag || 6 === node.tag)
             appendChildToContainerChildSet(newChildSet, node.stateNode);
           else if (4 !== node.tag && null !== node.child) {
-            node.child["return"] = node;
+            node.child.return = node;
             node = node.child;
             continue;
           }
           if (node === workInProgress) break a;
           for (; null === node.sibling; ) {
-            if (null === node["return"] || node["return"] === workInProgress)
-              break a;
-            node = node["return"];
+            if (null === node.return || node.return === workInProgress) break a;
+            node = node.return;
           }
-          node.sibling["return"] = node["return"];
+          node.sibling.return = node.return;
           node = node.sibling;
         }
         portalOrRoot.pendingChildren = newChildSet;
@@ -3588,18 +3693,7 @@ function ReactFiberCompleteWork(
         case 1:
           return null;
         case 2:
-          return (
-            popLegacyContextProvider(workInProgress),
-            (current = workInProgress.stateNode),
-            (newProps = workInProgress.updateQueue),
-            null !== newProps &&
-              null !== newProps.capturedValues &&
-              ((workInProgress.effectTag &= -65),
-              "function" === typeof current.componentDidCatch
-                ? (workInProgress.effectTag |= 256)
-                : (newProps.capturedValues = null)),
-            null
-          );
+          return popLegacyContextProvider(workInProgress), null;
         case 3:
           popHostContainer(workInProgress);
           popTopLevelLegacyContextObject(workInProgress);
@@ -3610,10 +3704,6 @@ function ReactFiberCompleteWork(
           if (null === current || null === current.child)
             popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
           updateHostContainer(workInProgress);
-          current = workInProgress.updateQueue;
-          null !== current &&
-            null !== current.capturedValues &&
-            (workInProgress.effectTag |= 256);
           return null;
         case 5:
           popHostContext(workInProgress);
@@ -3621,10 +3711,10 @@ function ReactFiberCompleteWork(
           var type = workInProgress.type;
           if (null !== current && null != workInProgress.stateNode) {
             var oldProps = current.memoizedProps,
-              _instance = workInProgress.stateNode,
+              instance = workInProgress.stateNode,
               currentHostContext = getHostContext();
-            _instance = prepareUpdate(
-              _instance,
+            instance = prepareUpdate(
+              instance,
               type,
               oldProps,
               newProps,
@@ -3634,7 +3724,7 @@ function ReactFiberCompleteWork(
             updateHostComponent(
               current,
               workInProgress,
-              _instance,
+              instance,
               type,
               oldProps,
               newProps,
@@ -3716,30 +3806,34 @@ function ReactFiberCompleteWork(
           );
           workInProgress.tag = 8;
           type = [];
-          a: for (
-            (oldProps = workInProgress.stateNode) &&
-            (oldProps["return"] = workInProgress);
-            null !== oldProps;
-
-          ) {
-            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
-              invariant(!1, "A call cannot have host component children.");
-            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
-            else if (null !== oldProps.child) {
-              oldProps.child["return"] = oldProps;
-              oldProps = oldProps.child;
-              continue;
-            }
-            for (; null === oldProps.sibling; ) {
+          a: {
+            if ((oldProps = workInProgress.stateNode))
+              oldProps.return = workInProgress;
+            for (; null !== oldProps; ) {
               if (
-                null === oldProps["return"] ||
-                oldProps["return"] === workInProgress
+                5 === oldProps.tag ||
+                6 === oldProps.tag ||
+                4 === oldProps.tag
               )
-                break a;
-              oldProps = oldProps["return"];
+                invariant(!1, "A call cannot have host component children.");
+              else if (9 === oldProps.tag)
+                type.push(oldProps.pendingProps.value);
+              else if (null !== oldProps.child) {
+                oldProps.child.return = oldProps;
+                oldProps = oldProps.child;
+                continue;
+              }
+              for (; null === oldProps.sibling; ) {
+                if (
+                  null === oldProps.return ||
+                  oldProps.return === workInProgress
+                )
+                  break a;
+                oldProps = oldProps.return;
+              }
+              oldProps.sibling.return = oldProps.return;
+              oldProps = oldProps.sibling;
             }
-            oldProps.sibling["return"] = oldProps["return"];
-            oldProps = oldProps.sibling;
           }
           oldProps = newProps.handler;
           newProps = oldProps(newProps.props, type);
@@ -3756,10 +3850,14 @@ function ReactFiberCompleteWork(
           return null;
         case 14:
           return null;
+        case 16:
+          return null;
         case 10:
           return null;
         case 11:
           return null;
+        case 15:
+          return null;
         case 4:
           return (
             popHostContainer(workInProgress),
@@ -3784,125 +3882,43 @@ function ReactFiberCompleteWork(
     }
   };
 }
-function ReactFiberUnwindWork(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
+function createCapturedValue(value, source) {
   return {
-    throwException: function(returnFiber, sourceFiber, rawValue) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      sourceFiber = {
-        value: rawValue,
-        source: sourceFiber,
-        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-      };
-      do {
-        switch (returnFiber.tag) {
-          case 3:
-            ensureUpdateQueues(returnFiber);
-            returnFiber.updateQueue.capturedValues = [sourceFiber];
-            returnFiber.effectTag |= 1024;
-            return;
-          case 2:
-            if (
-              ((rawValue = returnFiber.stateNode),
-              0 === (returnFiber.effectTag & 64) &&
-                null !== rawValue &&
-                "function" === typeof rawValue.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(rawValue))
-            ) {
-              ensureUpdateQueues(returnFiber);
-              rawValue = returnFiber.updateQueue;
-              var capturedValues = rawValue.capturedValues;
-              null === capturedValues
-                ? (rawValue.capturedValues = [sourceFiber])
-                : capturedValues.push(sourceFiber);
-              returnFiber.effectTag |= 1024;
-              return;
-            }
-        }
-        returnFiber = returnFiber["return"];
-      } while (null !== returnFiber);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
-      }
-    }
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
   };
 }
 function logError(boundary, errorInfo) {
-  var source = errorInfo.source;
-  null === errorInfo.stack && getStackAddendumByWorkInProgressFiber(source);
+  var source = errorInfo.source,
+    stack = errorInfo.stack;
+  null === stack && (stack = getStackAddendumByWorkInProgressFiber(source));
   null !== source && getComponentName(source);
+  source = null !== stack ? stack : "";
   errorInfo = errorInfo.value;
   null !== boundary && 2 === boundary.tag && getComponentName(boundary);
   try {
-    (errorInfo && errorInfo.suppressReactErrorLogging) ||
-      console.error(errorInfo);
+    if (errorInfo instanceof Error) {
+      var message = errorInfo.message,
+        name = errorInfo.name;
+      var errorToHandle = errorInfo;
+      try {
+        errorToHandle.message =
+          (message ? name + ": " + message : name) +
+          "\n\nThis error is located at:" +
+          source;
+      } catch (e) {}
+    } else
+      errorToHandle =
+        "string" === typeof errorInfo
+          ? Error(errorInfo + "\n\nThis error is located at:" + source)
+          : Error("Unspecified error at:" + source);
+    ExceptionsManager.handleException(errorToHandle, !1);
   } catch (e) {
     (e && e.suppressReactErrorLogging) || console.error(e);
   }
 }
-function ReactFiberCommitWork(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed
-) {
+function ReactFiberCommitWork(config, captureError) {
   function safelyDetachRef(current) {
     var ref = current.ref;
     if (null !== ref)
@@ -3917,7 +3933,7 @@ function ReactFiberCommitWork(
   function commitBeforeMutationLifeCycles(current, finishedWork) {
     switch (finishedWork.tag) {
       case 2:
-        if (finishedWork.effectTag & 2048 && null !== current) {
+        if (finishedWork.effectTag & 256 && null !== current) {
           var prevProps = current.memoizedProps,
             prevState = current.memoizedState;
           current = finishedWork.stateNode;
@@ -3939,28 +3955,40 @@ function ReactFiberCommitWork(
         );
     }
   }
-  function commitLifeCycles(finishedRoot, current, finishedWork) {
+  function commitLifeCycles(
+    finishedRoot,
+    current,
+    finishedWork,
+    currentTime,
+    committedExpirationTime
+  ) {
     switch (finishedWork.tag) {
       case 2:
         finishedRoot = finishedWork.stateNode;
-        if (finishedWork.effectTag & 4)
-          if (null === current)
-            (finishedRoot.props = finishedWork.memoizedProps),
+        finishedWork.effectTag & 4 &&
+          (null === current
+            ? ((finishedRoot.props = finishedWork.memoizedProps),
               (finishedRoot.state = finishedWork.memoizedState),
-              finishedRoot.componentDidMount();
-          else {
-            var prevProps = current.memoizedProps;
-            current = current.memoizedState;
-            finishedRoot.props = finishedWork.memoizedProps;
-            finishedRoot.state = finishedWork.memoizedState;
-            finishedRoot.componentDidUpdate(
-              prevProps,
-              current,
-              finishedRoot.__reactInternalSnapshotBeforeUpdate
-            );
-          }
-        finishedWork = finishedWork.updateQueue;
-        null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
+              finishedRoot.componentDidMount())
+            : ((currentTime = current.memoizedProps),
+              (current = current.memoizedState),
+              (finishedRoot.props = finishedWork.memoizedProps),
+              (finishedRoot.state = finishedWork.memoizedState),
+              finishedRoot.componentDidUpdate(
+                currentTime,
+                current,
+                finishedRoot.__reactInternalSnapshotBeforeUpdate
+              )));
+        current = finishedWork.updateQueue;
+        null !== current &&
+          ((finishedRoot.props = finishedWork.memoizedProps),
+          (finishedRoot.state = finishedWork.memoizedState),
+          commitUpdateQueue(
+            finishedWork,
+            current,
+            finishedRoot,
+            committedExpirationTime
+          ));
         break;
       case 3:
         current = finishedWork.updateQueue;
@@ -3974,15 +4002,20 @@ function ReactFiberCommitWork(
               case 2:
                 finishedRoot = finishedWork.child.stateNode;
             }
-          commitCallbacks(current, finishedRoot);
+          commitUpdateQueue(
+            finishedWork,
+            current,
+            finishedRoot,
+            committedExpirationTime
+          );
         }
         break;
       case 5:
-        finishedRoot = finishedWork.stateNode;
+        committedExpirationTime = finishedWork.stateNode;
         null === current &&
           finishedWork.effectTag & 4 &&
           commitMount(
-            finishedRoot,
+            committedExpirationTime,
             finishedWork.type,
             finishedWork.memoizedProps,
             finishedWork
@@ -3992,69 +4025,27 @@ function ReactFiberCommitWork(
         break;
       case 4:
         break;
-      default:
-        invariant(
-          !1,
-          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case 2:
-        var ctor = finishedWork.type;
-        onUncaughtError = finishedWork.stateNode;
-        var updateQueue = finishedWork.updateQueue;
-        invariant(
-          null !== updateQueue && null !== updateQueue.capturedValues,
-          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-        );
-        var capturedErrors = updateQueue.capturedValues;
-        updateQueue.capturedValues = null;
-        "function" !== typeof ctor.getDerivedStateFromCatch &&
-          markLegacyErrorBoundaryAsFailed(onUncaughtError);
-        onUncaughtError.props = finishedWork.memoizedProps;
-        onUncaughtError.state = finishedWork.memoizedState;
-        for (ctor = 0; ctor < capturedErrors.length; ctor++) {
-          updateQueue = capturedErrors[ctor];
-          var _error = updateQueue.value,
-            stack = updateQueue.stack;
-          logError(finishedWork, updateQueue);
-          onUncaughtError.componentDidCatch(_error, {
-            componentStack: null !== stack ? stack : ""
-          });
-        }
+      case 15:
         break;
-      case 3:
-        ctor = finishedWork.updateQueue;
-        invariant(
-          null !== ctor && null !== ctor.capturedValues,
-          "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-        );
-        capturedErrors = ctor.capturedValues;
-        ctor.capturedValues = null;
-        for (ctor = 0; ctor < capturedErrors.length; ctor++)
-          (updateQueue = capturedErrors[ctor]),
-            logError(finishedWork, updateQueue),
-            onUncaughtError(updateQueue.value);
+      case 16:
         break;
       default:
         invariant(
           !1,
-          "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
+          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
         );
     }
   }
   function commitAttachRef(finishedWork) {
     var ref = finishedWork.ref;
     if (null !== ref) {
-      var _instance6 = finishedWork.stateNode;
+      var _instance5 = finishedWork.stateNode;
       switch (finishedWork.tag) {
         case 5:
-          finishedWork = getPublicInstance(_instance6);
+          finishedWork = getPublicInstance(_instance5);
           break;
         default:
-          finishedWork = _instance6;
+          finishedWork = _instance5;
       }
       "function" === typeof ref
         ? ref(finishedWork)
@@ -4075,12 +4066,12 @@ function ReactFiberCommitWork(
       switch (current.tag) {
         case 2:
           safelyDetachRef(current);
-          var _instance7 = current.stateNode;
-          if ("function" === typeof _instance7.componentWillUnmount)
+          var _instance6 = current.stateNode;
+          if ("function" === typeof _instance6.componentWillUnmount)
             try {
-              (_instance7.props = current.memoizedProps),
-                (_instance7.state = current.memoizedState),
-                _instance7.componentWillUnmount();
+              (_instance6.props = current.memoizedProps),
+                (_instance6.state = current.memoizedState),
+                _instance6.componentWillUnmount();
             } catch (unmountError) {
               captureError(current, unmountError);
             }
@@ -4097,12 +4088,12 @@ function ReactFiberCommitWork(
       if (null === node.child || (mutation && 4 === node.tag)) {
         if (node === root) break;
         for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === root) return;
-          node = node["return"];
+          if (null === node.return || node.return === root) return;
+          node = node.return;
         }
-        node.sibling["return"] = node["return"];
+        node.sibling.return = node.return;
         node = node.sibling;
-      } else (node.child["return"] = node), (node = node.child);
+      } else (node.child.return = node), (node = node.child);
     }
   }
   var getPublicInstance = config.getPublicInstance,
@@ -4148,18 +4139,16 @@ function ReactFiberCommitWork(
       commitPlacement: function() {},
       commitDeletion: function(current) {
         commitNestedUnmounts(current);
-        current["return"] = null;
+        current.return = null;
         current.child = null;
         current.alternate &&
-          ((current.alternate.child = null),
-          (current.alternate["return"] = null));
+          ((current.alternate.child = null), (current.alternate.return = null));
       },
       commitWork: function(current, finishedWork) {
         commitContainer(finishedWork);
       },
       commitLifeCycles: commitLifeCycles,
       commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitErrorLogging: commitErrorLogging,
       commitAttachRef: commitAttachRef,
       commitDetachRef: commitDetachRef
     };
@@ -4167,6 +4156,153 @@ function ReactFiberCommitWork(
   var commitMount = mutation.commitMount;
   invariant(!1, "Mutating reconciler is disabled.");
 }
+function ReactFiberUnwindWork(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  computeExpirationForFiber,
+  recalculateCurrentTime,
+  markLegacyErrorBoundaryAsFailed,
+  isAlreadyFailedLegacyErrorBoundary,
+  onUncaughtError
+) {
+  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+    expirationTime = createUpdate(expirationTime);
+    expirationTime.tag = 3;
+    expirationTime.payload = { element: null };
+    var error = errorInfo.value;
+    expirationTime.callback = function() {
+      onUncaughtError(error);
+      logError(fiber, errorInfo);
+    };
+    return expirationTime;
+  }
+  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+    expirationTime = createUpdate(expirationTime);
+    expirationTime.tag = 3;
+    var inst = fiber.stateNode;
+    null !== inst &&
+      "function" === typeof inst.componentDidCatch &&
+      (expirationTime.callback = function() {
+        markLegacyErrorBoundaryAsFailed(this);
+        var error = errorInfo.value,
+          stack = errorInfo.stack;
+        logError(fiber, errorInfo);
+        this.componentDidCatch(error, {
+          componentStack: null !== stack ? stack : ""
+        });
+      });
+    return expirationTime;
+  }
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
+  return {
+    throwException: function(
+      root,
+      returnFiber,
+      sourceFiber,
+      value,
+      renderIsExpired,
+      renderExpirationTime
+    ) {
+      sourceFiber.effectTag |= 512;
+      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+      value = createCapturedValue(value, sourceFiber);
+      root = returnFiber;
+      do {
+        switch (root.tag) {
+          case 3:
+            root.effectTag |= 1024;
+            value = createRootErrorUpdate(root, value, renderExpirationTime);
+            enqueueCapturedUpdate(root, value, renderExpirationTime);
+            return;
+          case 2:
+            if (
+              ((returnFiber = value),
+              (sourceFiber = root.stateNode),
+              0 === (root.effectTag & 64) &&
+                null !== sourceFiber &&
+                "function" === typeof sourceFiber.componentDidCatch &&
+                !isAlreadyFailedLegacyErrorBoundary(sourceFiber))
+            ) {
+              root.effectTag |= 1024;
+              value = createClassErrorUpdate(
+                root,
+                returnFiber,
+                renderExpirationTime
+              );
+              enqueueCapturedUpdate(root, value, renderExpirationTime);
+              return;
+            }
+        }
+        root = root.return;
+      } while (null !== root);
+    },
+    unwindWork: function(workInProgress) {
+      switch (workInProgress.tag) {
+        case 2:
+          popLegacyContextProvider(workInProgress);
+          var effectTag = workInProgress.effectTag;
+          return effectTag & 1024
+            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+              workInProgress)
+            : null;
+        case 3:
+          return (
+            popHostContainer(workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 5:
+          return popHostContext(workInProgress), null;
+        case 16:
+          return (
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 4:
+          return popHostContainer(workInProgress), null;
+        case 13:
+          return popProvider(workInProgress), null;
+        default:
+          return null;
+      }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
+        case 2:
+          popLegacyContextProvider(interruptedWork);
+          break;
+        case 3:
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
+          break;
+        case 5:
+          popHostContext(interruptedWork);
+          break;
+        case 4:
+          popHostContainer(interruptedWork);
+          break;
+        case 13:
+          popProvider(interruptedWork);
+      }
+    },
+    createRootErrorUpdate: createRootErrorUpdate,
+    createClassErrorUpdate: createClassErrorUpdate
+  };
+}
 var NO_CONTEXT = {};
 function ReactFiberHostContext(config, stack) {
   function requiredContext(c) {
@@ -4223,7 +4359,7 @@ function ReactFiberHydrationContext(config) {
     var fiber = new FiberNode(5, null, null, 0);
     fiber.type = "DELETED";
     fiber.stateNode = instance;
-    fiber["return"] = returnFiber;
+    fiber.return = returnFiber;
     fiber.effectTag = 8;
     null !== returnFiber.lastEffect
       ? ((returnFiber.lastEffect.nextEffect = fiber),
@@ -4255,11 +4391,11 @@ function ReactFiberHydrationContext(config) {
   }
   function popToNextHostParent(fiber) {
     for (
-      fiber = fiber["return"];
+      fiber = fiber.return;
       null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
 
     )
-      fiber = fiber["return"];
+      fiber = fiber.return;
     hydrationParentFiber = fiber;
   }
   var shouldSetTextContent = config.shouldSetTextContent;
@@ -4493,7 +4629,7 @@ function ReactFiberLegacyContext(stack) {
       ) {
         if (isContextProvider(fiber))
           return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber["return"];
+        fiber = fiber.return;
         invariant(
           fiber,
           "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
@@ -4503,7 +4639,7 @@ function ReactFiberLegacyContext(stack) {
     }
   };
 }
-function ReactFiberNewContext(stack) {
+function ReactFiberNewContext(stack, isPrimaryRenderer) {
   var createCursor = stack.createCursor,
     push = stack.push,
     pop = stack.pop,
@@ -4513,11 +4649,17 @@ function ReactFiberNewContext(stack) {
   return {
     pushProvider: function(providerFiber) {
       var context = providerFiber.type._context;
-      push(changedBitsCursor, context._changedBits, providerFiber);
-      push(valueCursor, context._currentValue, providerFiber);
-      push(providerCursor, providerFiber, providerFiber);
-      context._currentValue = providerFiber.pendingProps.value;
-      context._changedBits = providerFiber.stateNode;
+      isPrimaryRenderer
+        ? (push(changedBitsCursor, context._changedBits, providerFiber),
+          push(valueCursor, context._currentValue, providerFiber),
+          push(providerCursor, providerFiber, providerFiber),
+          (context._currentValue = providerFiber.pendingProps.value),
+          (context._changedBits = providerFiber.stateNode))
+        : (push(changedBitsCursor, context._changedBits2, providerFiber),
+          push(valueCursor, context._currentValue2, providerFiber),
+          push(providerCursor, providerFiber, providerFiber),
+          (context._currentValue2 = providerFiber.pendingProps.value),
+          (context._changedBits2 = providerFiber.stateNode));
     },
     popProvider: function(providerFiber) {
       var changedBits = changedBitsCursor.current,
@@ -4526,8 +4668,17 @@ function ReactFiberNewContext(stack) {
       pop(valueCursor, providerFiber);
       pop(changedBitsCursor, providerFiber);
       providerFiber = providerFiber.type._context;
-      providerFiber._currentValue = currentValue;
-      providerFiber._changedBits = changedBits;
+      isPrimaryRenderer
+        ? ((providerFiber._currentValue = currentValue),
+          (providerFiber._changedBits = changedBits))
+        : ((providerFiber._currentValue2 = currentValue),
+          (providerFiber._changedBits2 = changedBits));
+    },
+    getContextCurrentValue: function(context) {
+      return isPrimaryRenderer ? context._currentValue : context._currentValue2;
+    },
+    getContextChangedBits: function(context) {
+      return isPrimaryRenderer ? context._changedBits : context._changedBits2;
     }
   };
 }
@@ -4560,14 +4711,16 @@ function ReactFiberScheduler(config) {
   function resetStack() {
     if (null !== nextUnitOfWork)
       for (
-        var interruptedWork = nextUnitOfWork["return"];
+        var interruptedWork = nextUnitOfWork.return;
         null !== interruptedWork;
 
       )
         unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork["return"]);
+          (interruptedWork = interruptedWork.return);
     nextRoot = null;
     nextRenderExpirationTime = 0;
+    nextLatestTimeoutMs = -1;
+    nextRenderIsExpired = !1;
     nextUnitOfWork = null;
     isRootReadyForCommit = !1;
   }
@@ -4577,10 +4730,15 @@ function ReactFiberScheduler(config) {
       legacyErrorBoundariesThatAlreadyFailed.has(instance)
     );
   }
+  function markLegacyErrorBoundaryAsFailed(instance) {
+    null === legacyErrorBoundariesThatAlreadyFailed
+      ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
+      : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+  }
   function completeUnitOfWork(workInProgress$jscomp$0) {
     for (;;) {
       var current = workInProgress$jscomp$0.alternate,
-        returnFiber = workInProgress$jscomp$0["return"],
+        returnFiber = workInProgress$jscomp$0.return,
         siblingFiber = workInProgress$jscomp$0.sibling;
       if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
         current = completeWork(
@@ -4593,24 +4751,20 @@ function ReactFiberScheduler(config) {
           1073741823 === nextRenderExpirationTime ||
           1073741823 !== workInProgress.expirationTime
         ) {
-          b: switch (workInProgress.tag) {
+          var newExpirationTime = 0;
+          switch (workInProgress.tag) {
             case 3:
             case 2:
-              var newExpirationTime = workInProgress.updateQueue;
-              newExpirationTime =
-                null === newExpirationTime
-                  ? 0
-                  : newExpirationTime.expirationTime;
-              break b;
-            default:
-              newExpirationTime = 0;
+              var updateQueue = workInProgress.updateQueue;
+              null !== updateQueue &&
+                (newExpirationTime = updateQueue.expirationTime);
           }
-          for (var child = workInProgress.child; null !== child; )
-            0 !== child.expirationTime &&
+          for (updateQueue = workInProgress.child; null !== updateQueue; )
+            0 !== updateQueue.expirationTime &&
               (0 === newExpirationTime ||
-                newExpirationTime > child.expirationTime) &&
-              (newExpirationTime = child.expirationTime),
-              (child = child.sibling);
+                newExpirationTime > updateQueue.expirationTime) &&
+              (newExpirationTime = updateQueue.expirationTime),
+              (updateQueue = updateQueue.sibling);
           workInProgress.expirationTime = newExpirationTime;
         }
         if (null !== current) return current;
@@ -4635,10 +4789,14 @@ function ReactFiberScheduler(config) {
           break;
         }
       } else {
-        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
+        workInProgress$jscomp$0 = unwindWork(
+          workInProgress$jscomp$0,
+          nextRenderIsExpired,
+          nextRenderExpirationTime
+        );
         if (null !== workInProgress$jscomp$0)
           return (
-            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
+            (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
           );
         null !== returnFiber &&
           ((returnFiber.firstEffect = returnFiber.lastEffect = null),
@@ -4674,6 +4832,7 @@ function ReactFiberScheduler(config) {
       resetStack(),
         (nextRoot = root),
         (nextRenderExpirationTime = expirationTime),
+        (nextLatestTimeoutMs = -1),
         (nextUnitOfWork = createWorkInProgress(
           nextRoot.current,
           null,
@@ -4681,6 +4840,8 @@ function ReactFiberScheduler(config) {
         )),
         (root.pendingCommitExpirationTime = 0);
     var didFatal = !1;
+    nextRenderIsExpired =
+      !isAsync || nextRenderExpirationTime <= mostRecentCurrentTime;
     do {
       try {
         if (isAsync)
@@ -4696,128 +4857,151 @@ function ReactFiberScheduler(config) {
           break;
         }
         isAsync = nextUnitOfWork;
-        var returnFiber = isAsync["return"];
+        var returnFiber = isAsync.return;
         if (null === returnFiber) {
           didFatal = !0;
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(returnFiber, isAsync, thrownValue);
+        throwException(
+          root,
+          returnFiber,
+          isAsync,
+          thrownValue,
+          nextRenderIsExpired,
+          nextRenderExpirationTime,
+          mostRecentCurrentTimeMs
+        );
         nextUnitOfWork = completeUnitOfWork(isAsync);
       }
       break;
     } while (1);
     isWorking = !1;
-    if (didFatal || null !== nextUnitOfWork) return null;
-    if (isRootReadyForCommit)
-      return (
-        (root.pendingCommitExpirationTime = expirationTime),
-        root.current.alternate
+    if (didFatal) return null;
+    if (null === nextUnitOfWork) {
+      if (isRootReadyForCommit)
+        return (
+          (root.pendingCommitExpirationTime = expirationTime),
+          root.current.alternate
+        );
+      invariant(
+        !nextRenderIsExpired,
+        "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
       );
-    invariant(
-      !1,
-      "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    sourceFiber = {
-      value: value,
-      source: sourceFiber,
-      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-    };
-    insertUpdateIntoFiber(boundaryFiber, {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: sourceFiber,
-      next: null
-    });
-    scheduleWork(boundaryFiber, expirationTime);
+      0 <= nextLatestTimeoutMs &&
+        setTimeout(function() {
+          retrySuspendedRoot(root, expirationTime);
+        }, nextLatestTimeoutMs);
+      onBlock(root.current.expirationTime);
+    }
+    return null;
   }
-  function onCommitPhaseError(fiber$jscomp$0, error) {
+  function onCommitPhaseError(fiber, error) {
+    var JSCompiler_inline_result;
     a: {
       invariant(
         !isWorking || isCommitting,
         "dispatch: Cannot dispatch during the render phase."
       );
-      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
-        switch (fiber.tag) {
+      for (
+        JSCompiler_inline_result = fiber.return;
+        null !== JSCompiler_inline_result;
+
+      ) {
+        switch (JSCompiler_inline_result.tag) {
           case 2:
-            var instance = fiber.stateNode;
+            var instance = JSCompiler_inline_result.stateNode;
             if (
-              "function" === typeof fiber.type.getDerivedStateFromCatch ||
+              "function" ===
+                typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
               ("function" === typeof instance.componentDidCatch &&
                 !isAlreadyFailedLegacyErrorBoundary(instance))
             ) {
-              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-              fiber$jscomp$0 = void 0;
+              fiber = createCapturedValue(error, fiber);
+              fiber = createClassErrorUpdate(
+                JSCompiler_inline_result,
+                fiber,
+                1
+              );
+              enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+              scheduleWork(JSCompiler_inline_result, 1);
+              JSCompiler_inline_result = void 0;
               break a;
             }
             break;
           case 3:
-            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-            fiber$jscomp$0 = void 0;
+            fiber = createCapturedValue(error, fiber);
+            fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+            enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+            scheduleWork(JSCompiler_inline_result, 1);
+            JSCompiler_inline_result = void 0;
             break a;
         }
-        fiber = fiber["return"];
+        JSCompiler_inline_result = JSCompiler_inline_result.return;
       }
-      3 === fiber$jscomp$0.tag &&
-        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
-      fiber$jscomp$0 = void 0;
+      3 === fiber.tag &&
+        ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
+        (JSCompiler_inline_result = createRootErrorUpdate(
+          fiber,
+          JSCompiler_inline_result,
+          1
+        )),
+        enqueueUpdate(fiber, JSCompiler_inline_result, 1),
+        scheduleWork(fiber, 1));
+      JSCompiler_inline_result = void 0;
     }
-    return fiber$jscomp$0;
+    return JSCompiler_inline_result;
   }
-  function computeExpirationForFiber(fiber) {
-    fiber =
+  function computeExpirationForFiber(currentTime, fiber) {
+    currentTime =
       0 !== expirationContext
         ? expirationContext
         : isWorking
           ? isCommitting ? 1 : nextRenderExpirationTime
           : fiber.mode & 1
             ? isBatchingInteractiveUpdates
-              ? 10 * ((((recalculateCurrentTime() + 15) / 10) | 0) + 1)
-              : 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1)
+              ? 2 + 10 * ((((currentTime - 2 + 15) / 10) | 0) + 1)
+              : 2 + 25 * ((((currentTime - 2 + 500) / 25) | 0) + 1)
             : 1;
     isBatchingInteractiveUpdates &&
       (0 === lowestPendingInteractiveExpirationTime ||
-        fiber > lowestPendingInteractiveExpirationTime) &&
-      (lowestPendingInteractiveExpirationTime = fiber);
-    return fiber;
+        currentTime > lowestPendingInteractiveExpirationTime) &&
+      (lowestPendingInteractiveExpirationTime = currentTime);
+    return currentTime;
+  }
+  function retrySuspendedRoot(root) {
+    var retryTime = root.current.expirationTime;
+    0 !== retryTime &&
+      (0 === root.remainingExpirationTime ||
+        root.remainingExpirationTime < retryTime) &&
+      requestWork(root, retryTime);
   }
   function scheduleWork(fiber, expirationTime) {
-    a: {
-      for (; null !== fiber; ) {
-        if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
-          fiber.expirationTime = expirationTime;
-        null !== fiber.alternate &&
-          (0 === fiber.alternate.expirationTime ||
-            fiber.alternate.expirationTime > expirationTime) &&
-          (fiber.alternate.expirationTime = expirationTime);
-        if (null === fiber["return"])
-          if (3 === fiber.tag) {
-            var root = fiber.stateNode;
-            !isWorking &&
-              0 !== nextRenderExpirationTime &&
-              expirationTime < nextRenderExpirationTime &&
-              resetStack();
-            (isWorking && !isCommitting && nextRoot === root) ||
-              requestWork(root, expirationTime);
-            nestedUpdateCount > NESTED_UPDATE_LIMIT &&
-              invariant(
-                !1,
-                "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
-              );
-          } else {
-            expirationTime = void 0;
-            break a;
-          }
-        fiber = fiber["return"];
-      }
-      expirationTime = void 0;
+    for (; null !== fiber; ) {
+      if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
+        fiber.expirationTime = expirationTime;
+      null !== fiber.alternate &&
+        (0 === fiber.alternate.expirationTime ||
+          fiber.alternate.expirationTime > expirationTime) &&
+        (fiber.alternate.expirationTime = expirationTime);
+      if (null === fiber.return)
+        if (3 === fiber.tag) {
+          var root = fiber.stateNode;
+          !isWorking &&
+            0 !== nextRenderExpirationTime &&
+            expirationTime < nextRenderExpirationTime &&
+            resetStack();
+          var nextExpirationTimeToWorkOn = root.current.expirationTime;
+          (isWorking && !isCommitting && nextRoot === root) ||
+            requestWork(root, nextExpirationTimeToWorkOn);
+          nestedUpdateCount > NESTED_UPDATE_LIMIT &&
+            invariant(
+              !1,
+              "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
+            );
+        } else break;
+      fiber = fiber.return;
     }
-    return expirationTime;
   }
   function recalculateCurrentTime() {
     mostRecentCurrentTimeMs = now() - originalStartTimeMs;
@@ -4943,11 +5127,12 @@ function ReactFiberScheduler(config) {
           recalculateCurrentTime() >= nextFlushedExpirationTime);
 
       )
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        ),
+        recalculateCurrentTime(),
+          performWorkOnRoot(
+            nextFlushedRoot,
+            nextFlushedExpirationTime,
+            !deadlineDidExpire
+          ),
           findHighestPriorityRoot();
     else
       for (
@@ -5053,7 +5238,7 @@ function ReactFiberScheduler(config) {
         error = void 0;
       try {
         for (; null !== nextEffect; )
-          nextEffect.effectTag & 2048 &&
+          nextEffect.effectTag & 256 &&
             commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
             (nextEffect = nextEffect.nextEffect);
       } catch (e) {
@@ -5129,8 +5314,6 @@ function ReactFiberScheduler(config) {
               didError,
               error
             );
-          effectTag$jscomp$0 & 256 &&
-            commitErrorLogging(nextEffect, onUncaughtError);
           effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
           var next = nextEffect.nextEffect;
           nextEffect.nextEffect = null;
@@ -5167,11 +5350,24 @@ function ReactFiberScheduler(config) {
     nextFlushedRoot.remainingExpirationTime = 0;
     hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
   }
-  var stack = ReactFiberStack(),
+  function onBlock(remainingExpirationTime) {
+    invariant(
+      null !== nextFlushedRoot,
+      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
+    );
+    nextFlushedRoot.remainingExpirationTime = remainingExpirationTime;
+  }
+  var now = config.now,
+    scheduleDeferredCallback = config.scheduleDeferredCallback,
+    cancelDeferredCallback = config.cancelDeferredCallback,
+    prepareForCommit = config.prepareForCommit,
+    resetAfterCommit = config.resetAfterCommit,
+    stack = ReactFiberStack(),
     hostContext = ReactFiberHostContext(config, stack),
     legacyContext = ReactFiberLegacyContext(stack);
-  stack = ReactFiberNewContext(stack);
-  var hydrationContext = ReactFiberHydrationContext(config),
+  stack = ReactFiberNewContext(stack, config.isPrimaryRenderer);
+  var profilerTimer = createProfilerTimer(now),
+    hydrationContext = ReactFiberHydrationContext(config),
     beginWork = ReactFiberBeginWork(
       config,
       hostContext,
@@ -5179,52 +5375,58 @@ function ReactFiberScheduler(config) {
       stack,
       hydrationContext,
       scheduleWork,
-      computeExpirationForFiber
+      computeExpirationForFiber,
+      profilerTimer,
+      recalculateCurrentTime
     ).beginWork,
     completeWork = ReactFiberCompleteWork(
       config,
       hostContext,
       legacyContext,
       stack,
-      hydrationContext
+      hydrationContext,
+      profilerTimer
     ).completeWork;
   hostContext = ReactFiberUnwindWork(
+    config,
     hostContext,
     legacyContext,
     stack,
     scheduleWork,
-    isAlreadyFailedLegacyErrorBoundary
+    computeExpirationForFiber,
+    recalculateCurrentTime,
+    markLegacyErrorBoundaryAsFailed,
+    isAlreadyFailedLegacyErrorBoundary,
+    onUncaughtError,
+    profilerTimer,
+    function(root, thenable, timeoutMs) {
+      0 <= timeoutMs &&
+        nextLatestTimeoutMs < timeoutMs &&
+        (nextLatestTimeoutMs = timeoutMs);
+    },
+    retrySuspendedRoot
   );
   var throwException = hostContext.throwException,
     unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork;
-  hostContext = ReactFiberCommitWork(
+    unwindInterruptedWork = hostContext.unwindInterruptedWork,
+    createRootErrorUpdate = hostContext.createRootErrorUpdate,
+    createClassErrorUpdate = hostContext.createClassErrorUpdate;
+  config = ReactFiberCommitWork(
     config,
     onCommitPhaseError,
     scheduleWork,
     computeExpirationForFiber,
-    function(instance) {
-      null === legacyErrorBoundariesThatAlreadyFailed
-        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-    },
+    markLegacyErrorBoundaryAsFailed,
     recalculateCurrentTime
   );
-  var commitBeforeMutationLifeCycles =
-      hostContext.commitBeforeMutationLifeCycles,
-    commitResetTextContent = hostContext.commitResetTextContent,
-    commitPlacement = hostContext.commitPlacement,
-    commitDeletion = hostContext.commitDeletion,
-    commitWork = hostContext.commitWork,
-    commitLifeCycles = hostContext.commitLifeCycles,
-    commitErrorLogging = hostContext.commitErrorLogging,
-    commitAttachRef = hostContext.commitAttachRef,
-    commitDetachRef = hostContext.commitDetachRef,
-    now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit,
+  var commitBeforeMutationLifeCycles = config.commitBeforeMutationLifeCycles,
+    commitResetTextContent = config.commitResetTextContent,
+    commitPlacement = config.commitPlacement,
+    commitDeletion = config.commitDeletion,
+    commitWork = config.commitWork,
+    commitLifeCycles = config.commitLifeCycles,
+    commitAttachRef = config.commitAttachRef,
+    commitDetachRef = config.commitDetachRef,
     originalStartTimeMs = now(),
     mostRecentCurrentTime = 2,
     mostRecentCurrentTimeMs = originalStartTimeMs,
@@ -5234,6 +5436,8 @@ function ReactFiberScheduler(config) {
     nextUnitOfWork = null,
     nextRoot = null,
     nextRenderExpirationTime = 0,
+    nextLatestTimeoutMs = -1,
+    nextRenderIsExpired = !1,
     nextEffect = null,
     isCommitting = !1,
     isRootReadyForCommit = !1,
@@ -5322,7 +5526,7 @@ function ReactFiberScheduler(config) {
     deferredUpdates: function(fn) {
       var previousExpirationContext = expirationContext;
       expirationContext =
-        25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
+        2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
       try {
         return fn();
       } finally {
@@ -5356,7 +5560,8 @@ function ReactFiberScheduler(config) {
         (lowestPendingInteractiveExpirationTime = 0));
     },
     computeUniqueAsyncExpiration: function() {
-      var result = 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
+      var result =
+        2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
       result <= lastUniqueAsyncExpiration &&
         (result = lastUniqueAsyncExpiration + 1);
       return (lastUniqueAsyncExpiration = result);
@@ -5369,11 +5574,10 @@ function ReactFiberReconciler$1(config) {
     element,
     container,
     parentComponent,
-    currentTime,
     expirationTime,
     callback
   ) {
-    currentTime = container.current;
+    var current = container.current;
     if (parentComponent) {
       parentComponent = parentComponent._reactInternalFiber;
       var parentContext = findCurrentUnmaskedContext(parentComponent);
@@ -5385,16 +5589,12 @@ function ReactFiberReconciler$1(config) {
       ? (container.context = parentComponent)
       : (container.pendingContext = parentComponent);
     container = callback;
-    insertUpdateIntoFiber(currentTime, {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: void 0 === container ? null : container,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: null,
-      next: null
-    });
-    scheduleWork(currentTime, expirationTime);
+    callback = createUpdate(expirationTime);
+    callback.payload = { element: element };
+    container = void 0 === container ? null : container;
+    null !== container && (callback.callback = container);
+    enqueueUpdate(current, callback, expirationTime);
+    scheduleWork(current, expirationTime);
     return expirationTime;
   }
   var getPublicInstance = config.getPublicInstance;
@@ -5413,6 +5613,11 @@ function ReactFiberReconciler$1(config) {
         current: isAsync,
         containerInfo: containerInfo,
         pendingChildren: null,
+        earliestPendingTime: 0,
+        latestPendingTime: 0,
+        earliestSuspendedTime: 0,
+        latestSuspendedTime: 0,
+        latestPingedTime: 0,
         pendingCommitExpirationTime: 0,
         finishedWork: null,
         context: null,
@@ -5427,12 +5632,11 @@ function ReactFiberReconciler$1(config) {
     updateContainer: function(element, container, parentComponent, callback) {
       var current = container.current,
         currentTime = recalculateCurrentTime();
-      current = computeExpirationForFiber(current);
+      current = computeExpirationForFiber(currentTime, current);
       return updateContainerAtExpirationTime(
         element,
         container,
         parentComponent,
-        currentTime,
         current,
         callback
       );
@@ -5444,12 +5648,10 @@ function ReactFiberReconciler$1(config) {
       expirationTime,
       callback
     ) {
-      var currentTime = recalculateCurrentTime();
       return updateContainerAtExpirationTime(
         element,
         container,
         parentComponent,
-        currentTime,
         expirationTime,
         callback
       );
@@ -5514,10 +5716,32 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
   ReactFiberReconciler$3 =
     (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
     ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3["default"]
-    ? ReactFiberReconciler$3["default"]
+  reactReconciler = ReactFiberReconciler$3.default
+    ? ReactFiberReconciler$3.default
     : ReactFiberReconciler$3,
-  nextReactTag = 2,
+  now =
+    "object" === typeof performance && "function" === typeof performance.now
+      ? function() {
+          return performance.now();
+        }
+      : function() {
+          return Date.now();
+        },
+  scheduledCallback = null,
+  frameDeadline = 0,
+  frameDeadlineObject = {
+    timeRemaining: function() {
+      return frameDeadline - now();
+    },
+    didTimeout: !1
+  };
+function setTimeoutCallback() {
+  frameDeadline = now() + 5;
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  null !== callback && callback(frameDeadlineObject);
+}
+var nextReactTag = 2,
   ReactFabricHostComponent = (function() {
     function ReactFabricHostComponent(tag, viewConfig, props) {
       if (!(this instanceof ReactFabricHostComponent))
@@ -5580,23 +5804,27 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
       hostContext,
       internalInstanceHandle
     ) {
-      hostContext = nextReactTag;
+      var tag = nextReactTag;
       nextReactTag += 2;
-      type = ReactNativeViewConfigRegistry.get(type);
-      var updatePayload = diffProperties(
+      var viewConfig = ReactNativeViewConfigRegistry.get(type);
+      invariant(
+        "RCTView" !== type || !hostContext.isInAParentText,
+        "Nesting of <View> within <Text> is not currently supported."
+      );
+      type = diffProperties(
         null,
         emptyObject$1,
         props,
-        type.validAttributes
+        viewConfig.validAttributes
       );
       rootContainerInstance = FabricUIManager.createNode(
-        hostContext,
-        type.uiViewClassName,
+        tag,
+        viewConfig.uiViewClassName,
         rootContainerInstance,
-        updatePayload,
+        type,
         internalInstanceHandle
       );
-      props = new ReactFabricHostComponent(hostContext, type, props);
+      props = new ReactFabricHostComponent(tag, viewConfig, props);
       return { node: rootContainerInstance, canonical: props };
     },
     createTextInstance: function(
@@ -5605,6 +5833,10 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
       hostContext,
       internalInstanceHandle
     ) {
+      invariant(
+        hostContext.isInAParentText,
+        "Text strings must be rendered within a <Text> component."
+      );
       hostContext = nextReactTag;
       nextReactTag += 2;
       return {
@@ -5621,15 +5853,24 @@ var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
       return !1;
     },
     getRootHostContext: function() {
-      return emptyObject;
+      return { isInAParentText: !1 };
     },
-    getChildHostContext: function() {
-      return emptyObject;
+    getChildHostContext: function(parentHostContext, type) {
+      type =
+        "AndroidTextInput" === type ||
+        "RCTMultilineTextInputView" === type ||
+        "RCTSinglelineTextInputView" === type ||
+        "RCTText" === type ||
+        "RCTVirtualText" === type;
+      return parentHostContext.isInAParentText !== type
+        ? { isInAParentText: type }
+        : parentHostContext;
     },
     getPublicInstance: function(instance) {
       return instance.canonical;
     },
     now: now,
+    isPrimaryRenderer: !1,
     prepareForCommit: function() {},
     prepareUpdate: function(instance, type, oldProps, newProps) {
       return diffProperties(
@@ -5795,7 +6036,7 @@ var roots = new Map(),
       var root = roots.get(containerTag);
       root &&
         ReactFabricRenderer.updateContainer(null, root, null, function() {
-          roots["delete"](containerTag);
+          roots.delete(containerTag);
         });
     },
     createPortal: function(children, containerTag) {
@@ -5870,6 +6111,4 @@ ReactFabricRenderer.injectIntoDevTools({
 });
 var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
   ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
-module.exports = ReactFabric$3["default"]
-  ? ReactFabric$3["default"]
-  : ReactFabric$3;
+module.exports = ReactFabric$3.default ? ReactFabric$3.default : ReactFabric$3;
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
index 21d9a6c1d543..de1791245051 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
@@ -5,7 +5,9 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
+ * @providesModule ReactNativeRenderer-dev
  * @preventMunge
+ * @generated
  */
 
 'use strict';
@@ -21,15 +23,15 @@ var emptyFunction = require("fbjs/lib/emptyFunction");
 var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
 var UIManager = require("UIManager");
 var RCTEventEmitter = require("RCTEventEmitter");
-var TextInputState = require("TextInputState");
-var deepDiffer = require("deepDiffer");
-var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
+var checkPropTypes = require("prop-types/checkPropTypes");
 var shallowEqual = require("fbjs/lib/shallowEqual");
 var ExceptionsManager = require("ExceptionsManager");
-var checkPropTypes = require("prop-types/checkPropTypes");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
+var deepDiffer = require("deepDiffer");
+var flattenStyle = require("flattenStyle");
+var TextInputState = require("TextInputState");
 
 var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
   this._hasCaughtError = false;
@@ -967,10 +969,12 @@ var Mode = 11;
 var ContextConsumer = 12;
 var ContextProvider = 13;
 var ForwardRef = 14;
+var Profiler = 15;
+var TimeoutComponent = 16;
 
 function getParent(inst) {
   do {
-    inst = inst["return"];
+    inst = inst.return;
     // TODO: If this is a HostRoot we might want to bail out.
     // That is depending on if we want nested subtrees (layers) to bubble
     // events to their parent. We could also go through parentNode on the
@@ -2714,26 +2718,55 @@ var ReactNativeEventEmitter = Object.freeze({
  */
 RCTEventEmitter.register(ReactNativeEventEmitter);
 
+/**
+ * `ReactInstanceMap` maintains a mapping from a public facing stateful
+ * instance (key) and the internal representation (value). This allows public
+ * methods to accept the user facing instance as an argument and map them back
+ * to internal methods.
+ *
+ * Note that this module is currently shared and assumed to be stateless.
+ * If this becomes an actual Map, that will break.
+ */
+
+/**
+ * This API should be called `delete` but we'd have to make sure to always
+ * transform these to strings for IE support. When this transform is fully
+ * supported we can rename it.
+ */
+
+function get$1(key) {
+  return key._reactInternalFiber;
+}
+
+function set(key, value) {
+  key._reactInternalFiber = value;
+}
+
+var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
+
+var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
+var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
+
 // The Symbol used to tag the ReactElement-like types. If there is no native Symbol
 // nor polyfill, then a plain number is used for performance.
-var hasSymbol = typeof Symbol === "function" && Symbol["for"];
+var hasSymbol = typeof Symbol === "function" && Symbol.for;
 
-var REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 0xeac9;
-var REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 0xeaca;
-var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 0xeacb;
+var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 0xeac7;
+var REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 0xeac8;
+var REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 0xeac9;
+var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 0xeaca;
+var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.strict_mode")
+  ? Symbol.for("react.strict_mode")
   : 0xeacc;
-var REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 0xeacd;
-var REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 0xeace;
-var REACT_ASYNC_MODE_TYPE = hasSymbol
-  ? Symbol["for"]("react.async_mode")
-  : 0xeacf;
+var REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profile_root") : 0xeacc;
+var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 0xeacd;
+var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 0xeace;
+var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 0xeacf;
 var REACT_FORWARD_REF_TYPE = hasSymbol
-  ? Symbol["for"]("react.forward_ref")
+  ? Symbol.for("react.forward_ref")
   : 0xead0;
+var REACT_TIMEOUT_TYPE = hasSymbol ? Symbol.for("react.timeout") : 0xead1;
 
 var MAYBE_ITERATOR_SYMBOL = typeof Symbol === "function" && Symbol.iterator;
 var FAUX_ITERATOR_SYMBOL = "@@iterator";
@@ -2751,43 +2784,6 @@ function getIteratorFn(maybeIterable) {
   return null;
 }
 
-function createPortal(
-  children,
-  containerInfo,
-  // TODO: figure out the API for cross-renderer implementation.
-  implementation
-) {
-  var key =
-    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
-
-  return {
-    // This tag allow us to uniquely identify this as a React Portal
-    $$typeof: REACT_PORTAL_TYPE,
-    key: key == null ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
-}
-
-// TODO: this is special because it gets imported during build.
-
-var ReactVersion = "16.3.2";
-
-var describeComponentFrame = function(name, source, ownerName) {
-  return (
-    "\n    in " +
-    (name || "Unknown") +
-    (source
-      ? " (at " +
-        source.fileName.replace(/^.*[\\\/]/, "") +
-        ":" +
-        source.lineNumber +
-        ")"
-      : ownerName ? " (created by " + ownerName + ")" : "")
-  );
-};
-
 function getComponentName(fiber) {
   var type = fiber.type;
 
@@ -2798,14 +2794,24 @@ function getComponentName(fiber) {
     return type;
   }
   switch (type) {
+    case REACT_ASYNC_MODE_TYPE:
+      return "AsyncMode";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_CONTEXT_TYPE:
+      return "Context.Consumer";
     case REACT_FRAGMENT_TYPE:
       return "ReactFragment";
     case REACT_PORTAL_TYPE:
       return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
+    case REACT_PROFILER_TYPE:
+      return "Profiler(" + fiber.pendingProps.id + ")";
+    case REACT_PROVIDER_TYPE:
+      return "Context.Provider";
     case REACT_RETURN_TYPE:
       return "ReactReturn";
+    case REACT_STRICT_MODE_TYPE:
+      return "StrictMode";
   }
   if (typeof type === "object" && type !== null) {
     switch (type.$$typeof) {
@@ -2819,2912 +2825,2423 @@ function getComponentName(fiber) {
   return null;
 }
 
-function describeFiber(fiber) {
-  switch (fiber.tag) {
-    case IndeterminateComponent:
-    case FunctionalComponent:
-    case ClassComponent:
-    case HostComponent:
-      var owner = fiber._debugOwner;
-      var source = fiber._debugSource;
-      var name = getComponentName(fiber);
-      var ownerName = null;
-      if (owner) {
-        ownerName = getComponentName(owner);
-      }
-      return describeComponentFrame(name, source, ownerName);
-    default:
-      return "";
-  }
-}
+// Don't change these two values. They're used by React Dev Tools.
+var NoEffect = /*              */ 0;
+var PerformedWork = /*         */ 1;
 
-// This function can only be called with a work-in-progress fiber and
-// only during begin or complete phase. Do not call it under any other
-// circumstances.
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  var node = workInProgress;
-  do {
-    info += describeFiber(node);
-    // Otherwise this return pointer might point to the wrong tree:
-    node = node["return"];
-  } while (node);
-  return info;
-}
+// You can change the rest (and add more).
+var Placement = /*             */ 2;
+var Update = /*                */ 4;
+var PlacementAndUpdate = /*    */ 6;
+var Deletion = /*              */ 8;
+var ContentReset = /*          */ 16;
+var Callback = /*              */ 32;
+var DidCapture = /*            */ 64;
+var Ref = /*                   */ 128;
+var Snapshot = /*              */ 256;
 
-// Modules provided by RN:
-var emptyObject$1 = {};
+// Union of all host effects
+var HostEffectMask = /*        */ 511;
 
-/**
- * Create a payload that contains all the updates between two sets of props.
- *
- * These helpers are all encapsulated into a single module, because they use
- * mutation as a performance optimization which leads to subtle shared
- * dependencies between the code paths. To avoid this mutable state leaking
- * across modules, I've kept them isolated to this module.
- */
+var Incomplete = /*            */ 512;
+var ShouldCapture = /*         */ 1024;
 
-// Tracks removed keys
-var removedKeys = null;
-var removedKeyCount = 0;
+var MOUNTING = 1;
+var MOUNTED = 2;
+var UNMOUNTED = 3;
 
-function defaultDiffer(prevProp, nextProp) {
-  if (typeof nextProp !== "object" || nextProp === null) {
-    // Scalars have already been checked for equality
-    return true;
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (!fiber.alternate) {
+    // If there is no alternate, this might be a new tree that isn't inserted
+    // yet. If it is, then it will have a pending insertion effect on it.
+    if ((node.effectTag & Placement) !== NoEffect) {
+      return MOUNTING;
+    }
+    while (node.return) {
+      node = node.return;
+      if ((node.effectTag & Placement) !== NoEffect) {
+        return MOUNTING;
+      }
+    }
   } else {
-    // For objects and arrays, the default diffing algorithm is a deep compare
-    return deepDiffer(prevProp, nextProp);
+    while (node.return) {
+      node = node.return;
+    }
+  }
+  if (node.tag === HostRoot) {
+    // TODO: Check if this was a nested HostRoot when used with
+    // renderContainerIntoSubtree.
+    return MOUNTED;
   }
+  // If we didn't hit the root, that means that we're in an disconnected tree
+  // that has been unmounted.
+  return UNMOUNTED;
 }
 
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node)) {
-    var i = node.length;
-    while (i-- && removedKeyCount > 0) {
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
-    }
-  } else if (node && removedKeyCount > 0) {
-    var obj = node;
-    for (var propKey in removedKeys) {
-      if (!removedKeys[propKey]) {
-        continue;
-      }
-      var _nextProp = obj[propKey];
-      if (_nextProp === undefined) {
-        continue;
-      }
-
-      var attributeConfig = validAttributes[propKey];
-      if (!attributeConfig) {
-        continue; // not a valid native prop
-      }
-
-      if (typeof _nextProp === "function") {
-        _nextProp = true;
-      }
-      if (typeof _nextProp === "undefined") {
-        _nextProp = null;
-      }
+function isFiberMounted(fiber) {
+  return isFiberMountedImpl(fiber) === MOUNTED;
+}
 
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = _nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(_nextProp)
-            : _nextProp;
-        updatePayload[propKey] = nextValue;
-      }
-      removedKeys[propKey] = false;
-      removedKeyCount--;
+function isMounted(component) {
+  {
+    var owner = ReactCurrentOwner.current;
+    if (owner !== null && owner.tag === ClassComponent) {
+      var ownerFiber = owner;
+      var instance = ownerFiber.stateNode;
+      !instance._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing isMounted inside its render() function. " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(ownerFiber) || "A component"
+          )
+        : void 0;
+      instance._warnedAboutRefsInRender = true;
     }
   }
+
+  var fiber = get$1(component);
+  if (!fiber) {
+    return false;
+  }
+  return isFiberMountedImpl(fiber) === MOUNTED;
 }
 
-function diffNestedArrayProperty(
-  updatePayload,
-  prevArray,
-  nextArray,
-  validAttributes
-) {
-  var minLength =
-    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
-  var i = void 0;
-  for (i = 0; i < minLength; i++) {
-    // Diff any items in the array in the forward direction. Repeated keys
-    // will be overwritten by later values.
-    updatePayload = diffNestedProperty(
-      updatePayload,
-      prevArray[i],
-      nextArray[i],
-      validAttributes
-    );
-  }
-  for (; i < prevArray.length; i++) {
-    // Clear out all remaining properties.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevArray[i],
-      validAttributes
-    );
-  }
-  for (; i < nextArray.length; i++) {
-    // Add all remaining properties.
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextArray[i],
-      validAttributes
-    );
-  }
-  return updatePayload;
+function assertIsMounted(fiber) {
+  invariant(
+    isFiberMountedImpl(fiber) === MOUNTED,
+    "Unable to find node on an unmounted component."
+  );
 }
 
-function diffNestedProperty(
-  updatePayload,
-  prevProp,
-  nextProp,
-  validAttributes
-) {
-  if (!updatePayload && prevProp === nextProp) {
-    // If no properties have been added, then we can bail out quickly on object
-    // equality.
-    return updatePayload;
-  }
-
-  if (!prevProp || !nextProp) {
-    if (nextProp) {
-      return addNestedProperty(updatePayload, nextProp, validAttributes);
-    }
-    if (prevProp) {
-      return clearNestedProperty(updatePayload, prevProp, validAttributes);
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate) {
+    // If there is no alternate, then we only need to check if it is mounted.
+    var state = isFiberMountedImpl(fiber);
+    invariant(
+      state !== UNMOUNTED,
+      "Unable to find node on an unmounted component."
+    );
+    if (state === MOUNTING) {
+      return null;
     }
-    return updatePayload;
+    return fiber;
   }
+  // If we have two possible branches, we'll walk backwards up to the root
+  // to see what path the root points to. On the way we may hit one of the
+  // special cases and we'll deal with them.
+  var a = fiber;
+  var b = alternate;
+  while (true) {
+    var parentA = a.return;
+    var parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) {
+      // We're at the root.
+      break;
+    }
 
-  if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
-    // Both are leaves, we can diff the leaves.
-    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
-  }
+    // If both copies of the parent fiber point to the same child, we can
+    // assume that the child is current. This happens when we bailout on low
+    // priority: the bailed out fiber's child reuses the current child.
+    if (parentA.child === parentB.child) {
+      var child = parentA.child;
+      while (child) {
+        if (child === a) {
+          // We've determined that A is the current branch.
+          assertIsMounted(parentA);
+          return fiber;
+        }
+        if (child === b) {
+          // We've determined that B is the current branch.
+          assertIsMounted(parentA);
+          return alternate;
+        }
+        child = child.sibling;
+      }
+      // We should never have an alternate for any mounting node. So the only
+      // way this could possibly happen is if this was unmounted, if at all.
+      invariant(false, "Unable to find node on an unmounted component.");
+    }
 
-  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
-    // Both are arrays, we can diff the arrays.
-    return diffNestedArrayProperty(
-      updatePayload,
-      prevProp,
-      nextProp,
-      validAttributes
-    );
-  }
+    if (a.return !== b.return) {
+      // The return pointer of A and the return pointer of B point to different
+      // fibers. We assume that return pointers never criss-cross, so A must
+      // belong to the child set of A.return, and B must belong to the child
+      // set of B.return.
+      a = parentA;
+      b = parentB;
+    } else {
+      // The return pointers point to the same fiber. We'll have to use the
+      // default, slow path: scan the child sets of each parent alternate to see
+      // which child belongs to which set.
+      //
+      // Search parent A's child set
+      var didFindChild = false;
+      var _child = parentA.child;
+      while (_child) {
+        if (_child === a) {
+          didFindChild = true;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          didFindChild = true;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!didFindChild) {
+        // Search parent B's child set
+        _child = parentB.child;
+        while (_child) {
+          if (_child === a) {
+            didFindChild = true;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            didFindChild = true;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          didFindChild,
+          "Child was not found in either parent set. This indicates a bug " +
+            "in React related to the return pointer. Please file an issue."
+        );
+      }
+    }
 
-  if (Array.isArray(prevProp)) {
-    return diffProperties(
-      updatePayload,
-      // $FlowFixMe - We know that this is always an object when the input is.
-      flattenStyle(prevProp),
-      // $FlowFixMe - We know that this isn't an array because of above flow.
-      nextProp,
-      validAttributes
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. " +
+        "This error is likely caused by a bug in React. Please file an issue."
     );
   }
-
-  return diffProperties(
-    updatePayload,
-    prevProp,
-    // $FlowFixMe - We know that this is always an object when the input is.
-    flattenStyle(nextProp),
-    validAttributes
+  // If the root is not a host container, we're in a disconnected tree. I.e.
+  // unmounted.
+  invariant(
+    a.tag === HostRoot,
+    "Unable to find node on an unmounted component."
   );
-}
-
-/**
- * addNestedProperty takes a single set of props and valid attribute
- * attribute configurations. It processes each prop and adds it to the
- * updatePayload.
- */
-function addNestedProperty(updatePayload, nextProp, validAttributes) {
-  if (!nextProp) {
-    return updatePayload;
+  if (a.stateNode.current === a) {
+    // We've determined that A is the current branch.
+    return fiber;
   }
+  // Otherwise B has to be current branch.
+  return alternate;
+}
 
-  if (!Array.isArray(nextProp)) {
-    // Add each property of the leaf.
-    return addProperties(updatePayload, nextProp, validAttributes);
+function findCurrentHostFiber(parent) {
+  var currentParent = findCurrentFiberUsingSlowPath(parent);
+  if (!currentParent) {
+    return null;
   }
 
-  for (var i = 0; i < nextProp.length; i++) {
-    // Add all the properties of the array.
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextProp[i],
-      validAttributes
-    );
+  // Next we'll drill down this component to find the first HostComponent/Text.
+  var node = currentParent;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      return node;
+    } else if (node.child) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === currentParent) {
+      return null;
+    }
+    while (!node.sibling) {
+      if (!node.return || node.return === currentParent) {
+        return null;
+      }
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
   }
-
-  return updatePayload;
+  // Flow needs the return null here, but ESLint complains about it.
+  // eslint-disable-next-line no-unreachable
+  return null;
 }
 
-/**
- * clearNestedProperty takes a single set of props and valid attributes. It
- * adds a null sentinel to the updatePayload, for each prop key.
- */
-function clearNestedProperty(updatePayload, prevProp, validAttributes) {
-  if (!prevProp) {
-    return updatePayload;
-  }
-
-  if (!Array.isArray(prevProp)) {
-    // Add each property of the leaf.
-    return clearProperties(updatePayload, prevProp, validAttributes);
+function findCurrentHostFiberWithNoPortals(parent) {
+  var currentParent = findCurrentFiberUsingSlowPath(parent);
+  if (!currentParent) {
+    return null;
   }
 
-  for (var i = 0; i < prevProp.length; i++) {
-    // Add all the properties of the array.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevProp[i],
-      validAttributes
-    );
-  }
-  return updatePayload;
-}
-
-/**
- * diffProperties takes two sets of props and a set of valid attributes
- * and write to updatePayload the values that changed or were deleted.
- * If no updatePayload is provided, a new one is created and returned if
- * anything changed.
- */
-function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
-  var attributeConfig = void 0;
-  var nextProp = void 0;
-  var prevProp = void 0;
-
-  for (var propKey in nextProps) {
-    attributeConfig = validAttributes[propKey];
-    if (!attributeConfig) {
-      continue; // not a valid native prop
+  // Next we'll drill down this component to find the first HostComponent/Text.
+  var node = currentParent;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      return node;
+    } else if (node.child && node.tag !== HostPortal) {
+      node.child.return = node;
+      node = node.child;
+      continue;
     }
-
-    prevProp = prevProps[propKey];
-    nextProp = nextProps[propKey];
-
-    // functions are converted to booleans as markers that the associated
-    // events should be sent from native.
-    if (typeof nextProp === "function") {
-      nextProp = true;
-      // If nextProp is not a function, then don't bother changing prevProp
-      // since nextProp will win and go into the updatePayload regardless.
-      if (typeof prevProp === "function") {
-        prevProp = true;
-      }
+    if (node === currentParent) {
+      return null;
     }
-
-    // An explicit value of undefined is treated as a null because it overrides
-    // any other preceding value.
-    if (typeof nextProp === "undefined") {
-      nextProp = null;
-      if (typeof prevProp === "undefined") {
-        prevProp = null;
+    while (!node.sibling) {
+      if (!node.return || node.return === currentParent) {
+        return null;
       }
+      node = node.return;
     }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+  // Flow needs the return null here, but ESLint complains about it.
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
 
-    if (removedKeys) {
-      removedKeys[propKey] = false;
-    }
-
-    if (updatePayload && updatePayload[propKey] !== undefined) {
-      // Something else already triggered an update to this key because another
-      // value diffed. Since we're now later in the nested arrays our value is
-      // more important so we need to calculate it and override the existing
-      // value. It doesn't matter if nothing changed, we'll set it anyway.
+var debugRenderPhaseSideEffects = false;
+var debugRenderPhaseSideEffectsForStrictMode = false;
+var enableGetDerivedStateFromCatch = false;
+var enableSuspense = false;
+var enableMutatingReconciler = true;
+var enableNoopReconciler = false;
+var enablePersistentReconciler = false;
+var enableUserTimingAPI = true;
+var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
+var warnAboutDeprecatedLifecycles = false;
+var enableProfilerTimer = false;
+var fireGetDerivedStateFromPropsOnStateUpdates = true;
 
-      // Pattern match on: attributeConfig
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(nextProp)
-            : nextProp;
-        updatePayload[propKey] = nextValue;
-      }
-      continue;
-    }
+// Only used in www builds.
 
-    if (prevProp === nextProp) {
-      continue; // nothing changed
-    }
+// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
+// Math.pow(2, 30) - 1
+// 0b111111111111111111111111111111
+var MAX_SIGNED_31_BIT_INT = 1073741823;
 
-    // Pattern match on: attributeConfig
-    if (typeof attributeConfig !== "object") {
-      // case: !Object is the default case
-      if (defaultDiffer(prevProp, nextProp)) {
-        // a normal leaf has changed
-        (updatePayload || (updatePayload = {}))[propKey] = nextProp;
-      }
-    } else if (
-      typeof attributeConfig.diff === "function" ||
-      typeof attributeConfig.process === "function"
-    ) {
-      // case: CustomAttributeConfiguration
-      var shouldUpdate =
-        prevProp === undefined ||
-        (typeof attributeConfig.diff === "function"
-          ? attributeConfig.diff(prevProp, nextProp)
-          : defaultDiffer(prevProp, nextProp));
-      if (shouldUpdate) {
-        var _nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(nextProp)
-            : nextProp;
-        (updatePayload || (updatePayload = {}))[propKey] = _nextValue;
-      }
-    } else {
-      // default: fallthrough case when nested properties are defined
-      removedKeys = null;
-      removedKeyCount = 0;
-      // We think that attributeConfig is not CustomAttributeConfiguration at
-      // this point so we assume it must be AttributeConfiguration.
-      updatePayload = diffNestedProperty(
-        updatePayload,
-        prevProp,
-        nextProp,
-        attributeConfig
-      );
-      if (removedKeyCount > 0 && updatePayload) {
-        restoreDeletedValuesInNestedArray(
-          updatePayload,
-          nextProp,
-          attributeConfig
-        );
-        removedKeys = null;
-      }
-    }
-  }
+// TODO: Use an opaque type once ESLint et al support the syntax
 
-  // Also iterate through all the previous props to catch any that have been
-  // removed and make sure native gets the signal so it can reset them to the
-  // default.
-  for (var _propKey in prevProps) {
-    if (nextProps[_propKey] !== undefined) {
-      continue; // we've already covered this key in the previous pass
-    }
-    attributeConfig = validAttributes[_propKey];
-    if (!attributeConfig) {
-      continue; // not a valid native prop
-    }
+var NoWork = 0;
+var Sync = 1;
+var Never = MAX_SIGNED_31_BIT_INT;
 
-    if (updatePayload && updatePayload[_propKey] !== undefined) {
-      // This was already updated to a diff result earlier.
-      continue;
-    }
+var UNIT_SIZE = 10;
+var MAGIC_NUMBER_OFFSET = 2;
 
-    prevProp = prevProps[_propKey];
-    if (prevProp === undefined) {
-      continue; // was already empty anyway
-    }
-    // Pattern match on: attributeConfig
-    if (
-      typeof attributeConfig !== "object" ||
-      typeof attributeConfig.diff === "function" ||
-      typeof attributeConfig.process === "function"
-    ) {
-      // case: CustomAttributeConfiguration | !Object
-      // Flag the leaf property for removal by sending a sentinel.
-      (updatePayload || (updatePayload = {}))[_propKey] = null;
-      if (!removedKeys) {
-        removedKeys = {};
-      }
-      if (!removedKeys[_propKey]) {
-        removedKeys[_propKey] = true;
-        removedKeyCount++;
-      }
-    } else {
-      // default:
-      // This is a nested attribute configuration where all the properties
-      // were removed so we need to go through and clear out all of them.
-      updatePayload = clearNestedProperty(
-        updatePayload,
-        prevProp,
-        attributeConfig
-      );
-    }
-  }
-  return updatePayload;
+// 1 unit of expiration time represents 10ms.
+function msToExpirationTime(ms) {
+  // Always add an offset so that we don't clash with the magic number for NoWork.
+  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
 }
 
-/**
- * addProperties adds all the valid props to the payload after being processed.
- */
-function addProperties(updatePayload, props, validAttributes) {
-  // TODO: Fast path
-  return diffProperties(updatePayload, emptyObject$1, props, validAttributes);
+function expirationTimeToMs(expirationTime) {
+  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
 }
 
-/**
- * clearProperties clears all the previous props by adding a null sentinel
- * to the payload for each valid key.
- */
-function clearProperties(updatePayload, prevProps, validAttributes) {
-  // TODO: Fast path
-  return diffProperties(
-    updatePayload,
-    prevProps,
-    emptyObject$1,
-    validAttributes
-  );
+function ceiling(num, precision) {
+  return (((num / precision) | 0) + 1) * precision;
 }
 
-function create(props, validAttributes) {
-  return addProperties(
-    null, // updatePayload
-    props,
-    validAttributes
+function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
+  return (
+    MAGIC_NUMBER_OFFSET +
+    ceiling(
+      currentTime - MAGIC_NUMBER_OFFSET + expirationInMs / UNIT_SIZE,
+      bucketSizeMs / UNIT_SIZE
+    )
   );
 }
 
-function diff(prevProps, nextProps, validAttributes) {
-  return diffProperties(
-    null, // updatePayload
-    prevProps,
-    nextProps,
-    validAttributes
-  );
-}
+var NoContext = 0;
+var AsyncMode = 1;
+var StrictMode = 2;
+var ProfileMode = 4;
 
-/**
- * In the future, we should cleanup callbacks by cancelling them instead of
- * using this.
- */
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (!callback) {
-      return undefined;
-    }
-    if (typeof context.__isMounted === "boolean") {
-      // TODO(gaearon): this is gross and should be removed.
-      // It is currently necessary because View uses createClass,
-      // and so any measure() calls on View (which are done by React
-      // DevTools) trigger the isMounted() deprecation warning.
-      if (!context.__isMounted) {
-        return undefined;
-      }
-      // The else branch is important so that we don't
-      // trigger the deprecation warning by calling isMounted.
-    } else if (typeof context.isMounted === "function") {
-      if (!context.isMounted()) {
-        return undefined;
-      }
-    }
-    return callback.apply(context, arguments);
-  };
-}
+var hasBadMapPolyfill = void 0;
 
-function throwOnStylesProp(component, props) {
-  if (props.styles !== undefined) {
-    var owner = component._owner || null;
-    var name = component.constructor.displayName;
-    var msg =
-      "`styles` is not a supported property of `" +
-      name +
-      "`, did " +
-      "you mean `style` (singular)?";
-    if (owner && owner.constructor && owner.constructor.displayName) {
-      msg +=
-        "\n\nCheck the `" +
-        owner.constructor.displayName +
-        "` parent " +
-        " component.";
-    }
-    throw new Error(msg);
+{
+  hasBadMapPolyfill = false;
+  try {
+    var nonExtensibleObject = Object.preventExtensions({});
+    var testMap = new Map([[nonExtensibleObject, null]]);
+    var testSet = new Set([nonExtensibleObject]);
+    // This is necessary for Rollup to not consider these unused.
+    // https://github.com/rollup/rollup/issues/1771
+    // TODO: we can remove these if Rollup fixes the bug.
+    testMap.set(0, 0);
+    testSet.add(0);
+  } catch (e) {
+    // TODO: Consider warning about bad polyfills
+    hasBadMapPolyfill = true;
   }
 }
 
-function warnForStyleProps(props, validAttributes) {
-  for (var key in validAttributes.style) {
-    if (!(validAttributes[key] || props[key] === undefined)) {
-      console.error(
-        "You are setting the style `{ " +
-          key +
-          ": ... }` as a prop. You " +
-          "should nest it in a style object. " +
-          "E.g. `{ style: { " +
-          key +
-          ": ... } }`"
-      );
-    }
-  }
-}
+// A Fiber is work on a Component that needs to be done or was done. There can
+// be more than one per component.
 
-// Modules provided by RN:
-var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
-  /**
-   * `NativeMethodsMixin` provides methods to access the underlying native
-   * component directly. This can be useful in cases when you want to focus
-   * a view or measure its on-screen dimensions, for example.
-   *
-   * The methods described here are available on most of the default components
-   * provided by React Native. Note, however, that they are *not* available on
-   * composite components that aren't directly backed by a native view. This will
-   * generally include most components that you define in your own app. For more
-   * information, see [Direct
-   * Manipulation](docs/direct-manipulation.html).
-   *
-   * Note the Flow $Exact<> syntax is required to support mixins.
-   * React createClass mixins can only be used with exact types.
-   */
-  var NativeMethodsMixin = {
-    /**
-     * Determines the location on screen, width, and height of the given view and
-     * returns the values via an async callback. If successful, the callback will
-     * be called with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *  - pageX
-     *  - pageY
-     *
-     * Note that these measurements are not available until after the rendering
-     * has been completed in native. If you need the measurements as soon as
-     * possible, consider using the [`onLayout`
-     * prop](docs/view.html#onlayout) instead.
-     */
-    measure: function(callback) {
-      UIManager.measure(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    },
+var debugCounter = void 0;
 
-    /**
-     * Determines the location of the given view in the window and returns the
-     * values via an async callback. If the React root view is embedded in
-     * another native view, this will give you the absolute coordinates. If
-     * successful, the callback will be called with the following
-     * arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *
-     * Note that these measurements are not available until after the rendering
-     * has been completed in native.
-     */
-    measureInWindow: function(callback) {
-      UIManager.measureInWindow(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    },
+{
+  debugCounter = 1;
+}
 
-    /**
-     * Like [`measure()`](#measure), but measures the view relative an ancestor,
-     * specified as `relativeToNativeNode`. This means that the returned x, y
-     * are relative to the origin x, y of the ancestor view.
-     *
-     * As always, to obtain a native node handle for a component, you can use
-     * `findNodeHandle(component)`.
-     */
-    measureLayout: function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail /* currently unused */
-    ) {
-      UIManager.measureLayout(
-        findNodeHandle(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    },
+function FiberNode(tag, pendingProps, key, mode) {
+  // Instance
+  this.tag = tag;
+  this.key = key;
+  this.type = null;
+  this.stateNode = null;
 
-    /**
-     * This function sends props straight to native. They will not participate in
-     * future diff process - this means that if you do not include them in the
-     * next render, they will remain active (see [Direct
-     * Manipulation](docs/direct-manipulation.html)).
-     */
-    setNativeProps: function(nativeProps) {
-      // Class components don't have viewConfig -> validateAttributes.
-      // Nor does it make sense to set native props on a non-native component.
-      // Instead, find the nearest host component and set props on it.
-      // Use findNodeHandle() rather than findNodeHandle() because
-      // We want the instance/wrapper (not the native tag).
-      var maybeInstance = void 0;
+  // Fiber
+  this.return = null;
+  this.child = null;
+  this.sibling = null;
+  this.index = 0;
 
-      // Fiber errors if findNodeHandle is called for an umounted component.
-      // Tests using ReactTestRenderer will trigger this case indirectly.
-      // Mimicking stack behavior, we should silently ignore this case.
-      // TODO Fix ReactTestRenderer so we can remove this try/catch.
-      try {
-        maybeInstance = findHostInstance(this);
-      } catch (error) {}
+  this.ref = null;
 
-      // If there is no host component beneath this we should fail silently.
-      // This is not an error; it could mean a class component rendered null.
-      if (maybeInstance == null) {
-        return;
-      }
+  this.pendingProps = pendingProps;
+  this.memoizedProps = null;
+  this.updateQueue = null;
+  this.memoizedState = null;
 
-      var viewConfig = maybeInstance.viewConfig;
+  this.mode = mode;
 
-      {
-        warnForStyleProps(nativeProps, viewConfig.validAttributes);
-      }
+  // Effects
+  this.effectTag = NoEffect;
+  this.nextEffect = null;
 
-      var updatePayload = create(nativeProps, viewConfig.validAttributes);
+  this.firstEffect = null;
+  this.lastEffect = null;
 
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          updatePayload
-        );
-      }
-    },
+  this.expirationTime = NoWork;
 
-    /**
-     * Requests focus for the given input or view. The exact behavior triggered
-     * will depend on the platform and type of view.
-     */
-    focus: function() {
-      TextInputState.focusTextInput(findNodeHandle(this));
-    },
+  this.alternate = null;
 
-    /**
-     * Removes focus from an input or view. This is the opposite of `focus()`.
-     */
-    blur: function() {
-      TextInputState.blurTextInput(findNodeHandle(this));
-    }
-  };
+  if (enableProfilerTimer) {
+    this.selfBaseTime = 0;
+    this.treeBaseTime = 0;
+  }
 
   {
-    // hide this from Flow since we can't define these properties outside of
-    // true without actually implementing them (setting them to undefined
-    // isn't allowed by ReactClass)
-    var NativeMethodsMixin_DEV = NativeMethodsMixin;
-    invariant(
-      !NativeMethodsMixin_DEV.componentWillMount &&
-        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
-        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
-        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
-      "Do not override existing functions."
-    );
-    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
-    // Once these lifecycles have been remove from the reconciler.
-    NativeMethodsMixin_DEV.componentWillMount = function() {
-      throwOnStylesProp(this, this.props);
-    };
-    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
-      throwOnStylesProp(this, newProps);
-    };
-    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
-      throwOnStylesProp(this, this.props);
-    };
-    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
-      newProps
-    ) {
-      throwOnStylesProp(this, newProps);
-    };
-
-    // React may warn about cWM/cWRP/cWU methods being deprecated.
-    // Add a flag to suppress these warnings for this special case.
-    // TODO (bvaughn) Remove this flag once the above methods have been removed.
-    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
-    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
+    this._debugID = debugCounter++;
+    this._debugSource = null;
+    this._debugOwner = null;
+    this._debugIsCurrentlyTiming = false;
+    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
+      Object.preventExtensions(this);
+    }
   }
+}
 
-  return NativeMethodsMixin;
+// This is a constructor function, rather than a POJO constructor, still
+// please ensure we do the following:
+// 1) Nobody should add any instance methods on this. Instance methods can be
+//    more difficult to predict when they get optimized and they are almost
+//    never inlined properly in static compilers.
+// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
+//    always know when it is a fiber.
+// 3) We might want to experiment with using numeric keys since they are easier
+//    to optimize in a non-JIT environment.
+// 4) We can easily go from a constructor to a createFiber object literal if that
+//    is faster.
+// 5) It should be easy to port this to a C struct and keep a C implementation
+//    compatible.
+var createFiber = function(tag, pendingProps, key, mode) {
+  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
+  return new FiberNode(tag, pendingProps, key, mode);
 };
 
-function _classCallCheck(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
-  }
-}
-
-function _possibleConstructorReturn(self, call) {
-  if (!self) {
-    throw new ReferenceError(
-      "this hasn't been initialised - super() hasn't been called"
-    );
-  }
-  return call && (typeof call === "object" || typeof call === "function")
-    ? call
-    : self;
+function shouldConstruct(Component) {
+  return !!(Component.prototype && Component.prototype.isReactComponent);
 }
 
-function _inherits(subClass, superClass) {
-  if (typeof superClass !== "function" && superClass !== null) {
-    throw new TypeError(
-      "Super expression must either be null or a function, not " +
-        typeof superClass
+// This is used to create an alternate fiber to do work on.
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  if (workInProgress === null) {
+    // We use a double buffering pooling technique because we know that we'll
+    // only ever need at most two versions of a tree. We pool the "other" unused
+    // node that we're free to reuse. This is lazily created to avoid allocating
+    // extra objects for things that are never updated. It also allow us to
+    // reclaim the extra memory if needed.
+    workInProgress = createFiber(
+      current.tag,
+      pendingProps,
+      current.key,
+      current.mode
     );
-  }
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: false,
-      writable: true,
-      configurable: true
-    }
-  });
-  if (superClass)
-    Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass);
-}
-
-// Modules provided by RN:
-var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
-  /**
-   * Superclass that provides methods to access the underlying native component.
-   * This can be useful when you want to focus a view or measure its dimensions.
-   *
-   * Methods implemented by this class are available on most default components
-   * provided by React Native. However, they are *not* available on composite
-   * components that are not directly backed by a native view. For more
-   * information, see [Direct Manipulation](docs/direct-manipulation.html).
-   *
-   * @abstract
-   */
-  var ReactNativeComponent = (function(_React$Component) {
-    _inherits(ReactNativeComponent, _React$Component);
-
-    function ReactNativeComponent() {
-      _classCallCheck(this, ReactNativeComponent);
+    workInProgress.type = current.type;
+    workInProgress.stateNode = current.stateNode;
 
-      return _possibleConstructorReturn(
-        this,
-        _React$Component.apply(this, arguments)
-      );
+    {
+      // DEV-only fields
+      workInProgress._debugID = current._debugID;
+      workInProgress._debugSource = current._debugSource;
+      workInProgress._debugOwner = current._debugOwner;
     }
 
-    /**
-     * Removes focus. This is the opposite of `focus()`.
-     */
-
-    /**
-     * Due to bugs in Flow's handling of React.createClass, some fields already
-     * declared in the base class need to be redeclared below.
-     */
-    ReactNativeComponent.prototype.blur = function blur() {
-      TextInputState.blurTextInput(findNodeHandle(this));
-    };
-
-    /**
-     * Requests focus. The exact behavior depends on the platform and view.
-     */
-
-    ReactNativeComponent.prototype.focus = function focus() {
-      TextInputState.focusTextInput(findNodeHandle(this));
-    };
+    workInProgress.alternate = current;
+    current.alternate = workInProgress;
+  } else {
+    workInProgress.pendingProps = pendingProps;
 
-    /**
-     * Measures the on-screen location and dimensions. If successful, the callback
-     * will be called asynchronously with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *  - pageX
-     *  - pageY
-     *
-     * These values are not available until after natives rendering completes. If
-     * you need the measurements as soon as possible, consider using the
-     * [`onLayout` prop](docs/view.html#onlayout) instead.
-     */
+    // We already have an alternate.
+    // Reset the effect tag.
+    workInProgress.effectTag = NoEffect;
 
-    ReactNativeComponent.prototype.measure = function measure(callback) {
-      UIManager.measure(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    };
+    // The effect list is no longer valid.
+    workInProgress.nextEffect = null;
+    workInProgress.firstEffect = null;
+    workInProgress.lastEffect = null;
+  }
 
-    /**
-     * Measures the on-screen location and dimensions. Even if the React Native
-     * root view is embedded within another native view, this method will give you
-     * the absolute coordinates measured from the window. If successful, the
-     * callback will be called asynchronously with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *
-     * These values are not available until after natives rendering completes.
-     */
+  workInProgress.expirationTime = expirationTime;
 
-    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
-      callback
-    ) {
-      UIManager.measureInWindow(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    };
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
 
-    /**
-     * Similar to [`measure()`](#measure), but the resulting location will be
-     * relative to the supplied ancestor's location.
-     *
-     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
-     */
+  // These will be overridden during the parent's reconciliation
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
 
-    ReactNativeComponent.prototype.measureLayout = function measureLayout(
-      relativeToNativeNode,
-      onSuccess,
-      onFail /* currently unused */
-    ) {
-      UIManager.measureLayout(
-        findNodeHandle(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    };
+  if (enableProfilerTimer) {
+    workInProgress.selfBaseTime = current.selfBaseTime;
+    workInProgress.treeBaseTime = current.treeBaseTime;
+  }
 
-    /**
-     * This function sends props straight to native. They will not participate in
-     * future diff process - this means that if you do not include them in the
-     * next render, they will remain active (see [Direct
-     * Manipulation](docs/direct-manipulation.html)).
-     */
+  return workInProgress;
+}
 
-    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
-      nativeProps
-    ) {
-      // Class components don't have viewConfig -> validateAttributes.
-      // Nor does it make sense to set native props on a non-native component.
-      // Instead, find the nearest host component and set props on it.
-      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
-      // We want the instance/wrapper (not the native tag).
-      var maybeInstance = void 0;
+function createHostRootFiber(isAsync) {
+  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
+  return createFiber(HostRoot, null, null, mode);
+}
 
-      // Fiber errors if findNodeHandle is called for an umounted component.
-      // Tests using ReactTestRenderer will trigger this case indirectly.
-      // Mimicking stack behavior, we should silently ignore this case.
-      // TODO Fix ReactTestRenderer so we can remove this try/catch.
-      try {
-        maybeInstance = findHostInstance(this);
-      } catch (error) {}
+function createFiberFromElement(element, mode, expirationTime) {
+  var owner = null;
+  {
+    owner = element._owner;
+  }
 
-      // If there is no host component beneath this we should fail silently.
-      // This is not an error; it could mean a class component rendered null.
-      if (maybeInstance == null) {
-        return;
-      }
+  var fiber = void 0;
+  var type = element.type;
+  var key = element.key;
+  var pendingProps = element.props;
 
-      var viewConfig =
-        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
-
-      var updatePayload = create(nativeProps, viewConfig.validAttributes);
-
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          updatePayload
+  var fiberTag = void 0;
+  if (typeof type === "function") {
+    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
+  } else if (typeof type === "string") {
+    fiberTag = HostComponent;
+  } else {
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          pendingProps.children,
+          mode,
+          expirationTime,
+          key
         );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= AsyncMode | StrictMode;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= StrictMode;
+        break;
+      case REACT_PROFILER_TYPE:
+        return createFiberFromProfiler(pendingProps, mode, expirationTime, key);
+      case REACT_CALL_TYPE:
+        fiberTag = CallComponent;
+        break;
+      case REACT_RETURN_TYPE:
+        fiberTag = ReturnComponent;
+        break;
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = TimeoutComponent;
+        // Suspense does not require async, but its children should be strict
+        // mode compatible.
+        mode |= StrictMode;
+        break;
+      default: {
+        if (typeof type === "object" && type !== null) {
+          switch (type.$$typeof) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = ContextProvider;
+              break;
+            case REACT_CONTEXT_TYPE:
+              // This is a consumer
+              fiberTag = ContextConsumer;
+              break;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = ForwardRef;
+              break;
+            default:
+              if (typeof type.tag === "number") {
+                // Currently assumed to be a continuation and therefore is a
+                // fiber already.
+                // TODO: The yield system is currently broken for updates in
+                // some cases. The reified yield stores a fiber, but we don't
+                // know which fiber that is; the current or a workInProgress?
+                // When the continuation gets rendered here we don't know if we
+                // can reuse that fiber or if we need to clone it. There is
+                // probably a clever way to restructure this.
+                fiber = type;
+                fiber.pendingProps = pendingProps;
+                fiber.expirationTime = expirationTime;
+                return fiber;
+              } else {
+                throwOnInvalidElementType(type, owner);
+              }
+              break;
+          }
+        } else {
+          throwOnInvalidElementType(type, owner);
+        }
       }
-    };
-
-    return ReactNativeComponent;
-  })(React.Component);
-
-  // eslint-disable-next-line no-unused-expressions
-
-  return ReactNativeComponent;
-};
-
-/**
- * `ReactInstanceMap` maintains a mapping from a public facing stateful
- * instance (key) and the internal representation (value). This allows public
- * methods to accept the user facing instance as an argument and map them back
- * to internal methods.
- *
- * Note that this module is currently shared and assumed to be stateless.
- * If this becomes an actual Map, that will break.
- */
+    }
+  }
 
-/**
- * This API should be called `delete` but we'd have to make sure to always
- * transform these to strings for IE support. When this transform is fully
- * supported we can rename it.
- */
+  fiber = createFiber(fiberTag, pendingProps, key, mode);
+  fiber.type = type;
+  fiber.expirationTime = expirationTime;
 
-function get$1(key) {
-  return key._reactInternalFiber;
-}
+  {
+    fiber._debugSource = element._source;
+    fiber._debugOwner = element._owner;
+  }
 
-function set(key, value) {
-  key._reactInternalFiber = value;
+  return fiber;
 }
 
-var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
-
-var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
-var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
-
-// Don't change these two values. They're used by React Dev Tools.
-var NoEffect = /*              */ 0;
-var PerformedWork = /*         */ 1;
-
-// You can change the rest (and add more).
-var Placement = /*             */ 2;
-var Update = /*                */ 4;
-var PlacementAndUpdate = /*    */ 6;
-var Deletion = /*              */ 8;
-var ContentReset = /*          */ 16;
-var Callback = /*              */ 32;
-var DidCapture = /*            */ 64;
-var Ref = /*                   */ 128;
-var ErrLog = /*                */ 256;
-var Snapshot = /*              */ 2048;
-
-// Union of all host effects
-var HostEffectMask = /*        */ 2559;
-
-var Incomplete = /*            */ 512;
-var ShouldCapture = /*         */ 1024;
-
-var MOUNTING = 1;
-var MOUNTED = 2;
-var UNMOUNTED = 3;
-
-function isFiberMountedImpl(fiber) {
-  var node = fiber;
-  if (!fiber.alternate) {
-    // If there is no alternate, this might be a new tree that isn't inserted
-    // yet. If it is, then it will have a pending insertion effect on it.
-    if ((node.effectTag & Placement) !== NoEffect) {
-      return MOUNTING;
-    }
-    while (node["return"]) {
-      node = node["return"];
-      if ((node.effectTag & Placement) !== NoEffect) {
-        return MOUNTING;
-      }
+function throwOnInvalidElementType(type, owner) {
+  var info = "";
+  {
+    if (
+      type === undefined ||
+      (typeof type === "object" &&
+        type !== null &&
+        Object.keys(type).length === 0)
+    ) {
+      info +=
+        " You likely forgot to export your component from the file " +
+        "it's defined in, or you might have mixed up default and " +
+        "named imports.";
     }
-  } else {
-    while (node["return"]) {
-      node = node["return"];
+    var ownerName = owner ? getComponentName(owner) : null;
+    if (ownerName) {
+      info += "\n\nCheck the render method of `" + ownerName + "`.";
     }
   }
-  if (node.tag === HostRoot) {
-    // TODO: Check if this was a nested HostRoot when used with
-    // renderContainerIntoSubtree.
-    return MOUNTED;
-  }
-  // If we didn't hit the root, that means that we're in an disconnected tree
-  // that has been unmounted.
-  return UNMOUNTED;
+  invariant(
+    false,
+    "Element type is invalid: expected a string (for built-in " +
+      "components) or a class/function (for composite components) " +
+      "but got: %s.%s",
+    type == null ? type : typeof type,
+    info
+  );
 }
 
-function isFiberMounted(fiber) {
-  return isFiberMountedImpl(fiber) === MOUNTED;
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  var fiber = createFiber(Fragment, elements, key, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
 }
 
-function isMounted(component) {
+function createFiberFromProfiler(pendingProps, mode, expirationTime, key) {
   {
-    var owner = ReactCurrentOwner.current;
-    if (owner !== null && owner.tag === ClassComponent) {
-      var ownerFiber = owner;
-      var instance = ownerFiber.stateNode;
-      !instance._warnedAboutRefsInRender
-        ? warning(
-            false,
-            "%s is accessing isMounted inside its render() function. " +
-              "render() should be a pure function of props and state. It should " +
-              "never access something that requires stale data from the previous " +
-              "render, such as refs. Move this logic to componentDidMount and " +
-              "componentDidUpdate instead.",
-            getComponentName(ownerFiber) || "A component"
-          )
-        : void 0;
-      instance._warnedAboutRefsInRender = true;
+    if (
+      typeof pendingProps.id !== "string" ||
+      typeof pendingProps.onRender !== "function"
+    ) {
+      invariant(
+        false,
+        'Profiler must specify an "id" string and "onRender" function as props'
+      );
     }
   }
 
-  var fiber = get$1(component);
-  if (!fiber) {
-    return false;
-  }
-  return isFiberMountedImpl(fiber) === MOUNTED;
+  var fiber = createFiber(Profiler, pendingProps, key, mode | ProfileMode);
+  fiber.type = REACT_PROFILER_TYPE;
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    duration: 0,
+    startTime: 0
+  };
+
+  return fiber;
 }
 
-function assertIsMounted(fiber) {
-  invariant(
-    isFiberMountedImpl(fiber) === MOUNTED,
-    "Unable to find node on an unmounted component."
-  );
+function createFiberFromText(content, mode, expirationTime) {
+  var fiber = createFiber(HostText, content, null, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
 }
 
-function findCurrentFiberUsingSlowPath(fiber) {
-  var alternate = fiber.alternate;
-  if (!alternate) {
-    // If there is no alternate, then we only need to check if it is mounted.
-    var state = isFiberMountedImpl(fiber);
-    invariant(
-      state !== UNMOUNTED,
-      "Unable to find node on an unmounted component."
-    );
-    if (state === MOUNTING) {
-      return null;
-    }
-    return fiber;
-  }
-  // If we have two possible branches, we'll walk backwards up to the root
-  // to see what path the root points to. On the way we may hit one of the
-  // special cases and we'll deal with them.
-  var a = fiber;
-  var b = alternate;
-  while (true) {
-    var parentA = a["return"];
-    var parentB = parentA ? parentA.alternate : null;
-    if (!parentA || !parentB) {
-      // We're at the root.
-      break;
-    }
-
-    // If both copies of the parent fiber point to the same child, we can
-    // assume that the child is current. This happens when we bailout on low
-    // priority: the bailed out fiber's child reuses the current child.
-    if (parentA.child === parentB.child) {
-      var child = parentA.child;
-      while (child) {
-        if (child === a) {
-          // We've determined that A is the current branch.
-          assertIsMounted(parentA);
-          return fiber;
-        }
-        if (child === b) {
-          // We've determined that B is the current branch.
-          assertIsMounted(parentA);
-          return alternate;
-        }
-        child = child.sibling;
-      }
-      // We should never have an alternate for any mounting node. So the only
-      // way this could possibly happen is if this was unmounted, if at all.
-      invariant(false, "Unable to find node on an unmounted component.");
-    }
-
-    if (a["return"] !== b["return"]) {
-      // The return pointer of A and the return pointer of B point to different
-      // fibers. We assume that return pointers never criss-cross, so A must
-      // belong to the child set of A.return, and B must belong to the child
-      // set of B.return.
-      a = parentA;
-      b = parentB;
-    } else {
-      // The return pointers point to the same fiber. We'll have to use the
-      // default, slow path: scan the child sets of each parent alternate to see
-      // which child belongs to which set.
-      //
-      // Search parent A's child set
-      var didFindChild = false;
-      var _child = parentA.child;
-      while (_child) {
-        if (_child === a) {
-          didFindChild = true;
-          a = parentA;
-          b = parentB;
-          break;
-        }
-        if (_child === b) {
-          didFindChild = true;
-          b = parentA;
-          a = parentB;
-          break;
-        }
-        _child = _child.sibling;
-      }
-      if (!didFindChild) {
-        // Search parent B's child set
-        _child = parentB.child;
-        while (_child) {
-          if (_child === a) {
-            didFindChild = true;
-            a = parentB;
-            b = parentA;
-            break;
-          }
-          if (_child === b) {
-            didFindChild = true;
-            b = parentB;
-            a = parentA;
-            break;
-          }
-          _child = _child.sibling;
-        }
-        invariant(
-          didFindChild,
-          "Child was not found in either parent set. This indicates a bug " +
-            "in React related to the return pointer. Please file an issue."
-        );
-      }
-    }
-
-    invariant(
-      a.alternate === b,
-      "Return fibers should always be each others' alternates. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  // If the root is not a host container, we're in a disconnected tree. I.e.
-  // unmounted.
-  invariant(
-    a.tag === HostRoot,
-    "Unable to find node on an unmounted component."
-  );
-  if (a.stateNode.current === a) {
-    // We've determined that A is the current branch.
-    return fiber;
-  }
-  // Otherwise B has to be current branch.
-  return alternate;
+function createFiberFromHostInstanceForDeletion() {
+  var fiber = createFiber(HostComponent, null, null, NoContext);
+  fiber.type = "DELETED";
+  return fiber;
 }
 
-function findCurrentHostFiber(parent) {
-  var currentParent = findCurrentFiberUsingSlowPath(parent);
-  if (!currentParent) {
-    return null;
-  }
-
-  // Next we'll drill down this component to find the first HostComponent/Text.
-  var node = currentParent;
-  while (true) {
-    if (node.tag === HostComponent || node.tag === HostText) {
-      return node;
-    } else if (node.child) {
-      node.child["return"] = node;
-      node = node.child;
-      continue;
-    }
-    if (node === currentParent) {
-      return null;
-    }
-    while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
-        return null;
-      }
-      node = node["return"];
-    }
-    node.sibling["return"] = node["return"];
-    node = node.sibling;
-  }
-  // Flow needs the return null here, but ESLint complains about it.
-  // eslint-disable-next-line no-unreachable
-  return null;
+function createFiberFromPortal(portal, mode, expirationTime) {
+  var pendingProps = portal.children !== null ? portal.children : [];
+  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null, // Used by persistent updates
+    implementation: portal.implementation
+  };
+  return fiber;
 }
 
-function findCurrentHostFiberWithNoPortals(parent) {
-  var currentParent = findCurrentFiberUsingSlowPath(parent);
-  if (!currentParent) {
-    return null;
+// Used for stashing WIP properties to replay failed work in DEV.
+function assignFiberPropertiesInDEV(target, source) {
+  if (target === null) {
+    // This Fiber's initial properties will always be overwritten.
+    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
+    target = createFiber(IndeterminateComponent, null, null, NoContext);
   }
 
-  // Next we'll drill down this component to find the first HostComponent/Text.
-  var node = currentParent;
-  while (true) {
-    if (node.tag === HostComponent || node.tag === HostText) {
-      return node;
-    } else if (node.child && node.tag !== HostPortal) {
-      node.child["return"] = node;
-      node = node.child;
-      continue;
-    }
-    if (node === currentParent) {
-      return null;
-    }
-    while (!node.sibling) {
-      if (!node["return"] || node["return"] === currentParent) {
-        return null;
-      }
-      node = node["return"];
-    }
-    node.sibling["return"] = node["return"];
-    node = node.sibling;
+  // This is intentionally written as a list of all properties.
+  // We tried to use Object.assign() instead but this is called in
+  // the hottest path, and Object.assign() was too slow:
+  // https://github.com/facebook/react/issues/12502
+  // This code is DEV-only so size is not a concern.
+
+  target.tag = source.tag;
+  target.key = source.key;
+  target.type = source.type;
+  target.stateNode = source.stateNode;
+  target.return = source.return;
+  target.child = source.child;
+  target.sibling = source.sibling;
+  target.index = source.index;
+  target.ref = source.ref;
+  target.pendingProps = source.pendingProps;
+  target.memoizedProps = source.memoizedProps;
+  target.updateQueue = source.updateQueue;
+  target.memoizedState = source.memoizedState;
+  target.mode = source.mode;
+  target.effectTag = source.effectTag;
+  target.nextEffect = source.nextEffect;
+  target.firstEffect = source.firstEffect;
+  target.lastEffect = source.lastEffect;
+  target.expirationTime = source.expirationTime;
+  target.alternate = source.alternate;
+  if (enableProfilerTimer) {
+    target.selfBaseTime = source.selfBaseTime;
+    target.treeBaseTime = source.treeBaseTime;
   }
-  // Flow needs the return null here, but ESLint complains about it.
-  // eslint-disable-next-line no-unreachable
-  return null;
+  target._debugID = source._debugID;
+  target._debugSource = source._debugSource;
+  target._debugOwner = source._debugOwner;
+  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
+  return target;
 }
 
-// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
-// Math.pow(2, 30) - 1
-// 0b111111111111111111111111111111
-var MAX_SIGNED_31_BIT_INT = 1073741823;
-
-// TODO: Use an opaque type once ESLint et al support the syntax
+// TODO: This should be lifted into the renderer.
 
-var NoWork = 0;
-var Sync = 1;
-var Never = MAX_SIGNED_31_BIT_INT;
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  // Cyclic construction. This cheats the type system right now because
+  // stateNode is any.
+  var uninitializedFiber = createHostRootFiber(isAsync);
+  var root = {
+    current: uninitializedFiber,
+    containerInfo: containerInfo,
+    pendingChildren: null,
 
-var UNIT_SIZE = 10;
-var MAGIC_NUMBER_OFFSET = 2;
+    earliestPendingTime: NoWork,
+    latestPendingTime: NoWork,
+    earliestSuspendedTime: NoWork,
+    latestSuspendedTime: NoWork,
+    latestPingedTime: NoWork,
 
-// 1 unit of expiration time represents 10ms.
-function msToExpirationTime(ms) {
-  // Always add an offset so that we don't clash with the magic number for NoWork.
-  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
+    pendingCommitExpirationTime: NoWork,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    remainingExpirationTime: NoWork,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  uninitializedFiber.stateNode = root;
+  return root;
 }
 
-function expirationTimeToMs(expirationTime) {
-  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
-}
+var onCommitFiberRoot = null;
+var onCommitFiberUnmount = null;
+var hasLoggedError = false;
 
-function ceiling(num, precision) {
-  return (((num / precision) | 0) + 1) * precision;
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {
+      if (true && !hasLoggedError) {
+        hasLoggedError = true;
+        warning(false, "React DevTools encountered an error: %s", err);
+      }
+    }
+  };
 }
 
-function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
-  return ceiling(
-    currentTime + expirationInMs / UNIT_SIZE,
-    bucketSizeMs / UNIT_SIZE
-  );
-}
-
-var NoContext = 0;
-var AsyncMode = 1;
-var StrictMode = 2;
-
-var hasBadMapPolyfill = void 0;
-
-{
-  hasBadMapPolyfill = false;
+function injectInternals(internals) {
+  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
+    // No DevTools
+    return false;
+  }
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled) {
+    // This isn't a real property on the hook, but it can be set to opt out
+    // of DevTools integration and associated warnings and logs.
+    // https://github.com/facebook/react/issues/3877
+    return true;
+  }
+  if (!hook.supportsFiber) {
+    {
+      warning(
+        false,
+        "The installed version of React DevTools is too old and will not work " +
+          "with the current version of React. Please update React DevTools. " +
+          "https://fb.me/react-devtools"
+      );
+    }
+    // DevTools exists, even though it doesn't support Fiber.
+    return true;
+  }
   try {
-    var nonExtensibleObject = Object.preventExtensions({});
-    var testMap = new Map([[nonExtensibleObject, null]]);
-    var testSet = new Set([nonExtensibleObject]);
-    // This is necessary for Rollup to not consider these unused.
-    // https://github.com/rollup/rollup/issues/1771
-    // TODO: we can remove these if Rollup fixes the bug.
-    testMap.set(0, 0);
-    testSet.add(0);
-  } catch (e) {
-    // TODO: Consider warning about bad polyfills
-    hasBadMapPolyfill = true;
+    var rendererID = hook.inject(internals);
+    // We have successfully injected, so now it is safe to set up hooks.
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {
+    // Catch all errors because it is unsafe to throw during initialization.
+    {
+      warning(false, "React DevTools encountered an error: %s.", err);
+    }
   }
+  // DevTools exists
+  return true;
 }
 
-// A Fiber is work on a Component that needs to be done or was done. There can
-// be more than one per component.
-
-var debugCounter = void 0;
-
-{
-  debugCounter = 1;
+function onCommitRoot(root) {
+  if (typeof onCommitFiberRoot === "function") {
+    onCommitFiberRoot(root);
+  }
 }
 
-function FiberNode(tag, pendingProps, key, mode) {
-  // Instance
-  this.tag = tag;
-  this.key = key;
-  this.type = null;
-  this.stateNode = null;
+function onCommitUnmount(fiber) {
+  if (typeof onCommitFiberUnmount === "function") {
+    onCommitFiberUnmount(fiber);
+  }
+}
 
-  // Fiber
-  this["return"] = null;
-  this.child = null;
-  this.sibling = null;
-  this.index = 0;
+var describeComponentFrame = function(name, source, ownerName) {
+  return (
+    "\n    in " +
+    (name || "Unknown") +
+    (source
+      ? " (at " +
+        source.fileName.replace(/^.*[\\\/]/, "") +
+        ":" +
+        source.lineNumber +
+        ")"
+      : ownerName ? " (created by " + ownerName + ")" : "")
+  );
+};
 
-  this.ref = null;
+function describeFiber(fiber) {
+  switch (fiber.tag) {
+    case IndeterminateComponent:
+    case FunctionalComponent:
+    case ClassComponent:
+    case HostComponent:
+      var owner = fiber._debugOwner;
+      var source = fiber._debugSource;
+      var name = getComponentName(fiber);
+      var ownerName = null;
+      if (owner) {
+        ownerName = getComponentName(owner);
+      }
+      return describeComponentFrame(name, source, ownerName);
+    default:
+      return "";
+  }
+}
 
-  this.pendingProps = pendingProps;
-  this.memoizedProps = null;
-  this.updateQueue = null;
-  this.memoizedState = null;
+// This function can only be called with a work-in-progress fiber and
+// only during begin or complete phase. Do not call it under any other
+// circumstances.
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  var node = workInProgress;
+  do {
+    info += describeFiber(node);
+    // Otherwise this return pointer might point to the wrong tree:
+    node = node.return;
+  } while (node);
+  return info;
+}
 
-  this.mode = mode;
+/**
+ * Forked from fbjs/warning:
+ * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
+ *
+ * Only change is we use console.warn instead of console.error,
+ * and do nothing when 'console' is not supported.
+ * This really simplifies the code.
+ * ---
+ * Similar to invariant but only logs a warning if the condition is not met.
+ * This can be used to log issues in development environments in critical
+ * paths. Removing the logging code for production environments will keep the
+ * same logic and follow the same code paths.
+ */
 
-  // Effects
-  this.effectTag = NoEffect;
-  this.nextEffect = null;
+var lowPriorityWarning = function() {};
 
-  this.firstEffect = null;
-  this.lastEffect = null;
+{
+  var printWarning = function(format) {
+    for (
+      var _len = arguments.length,
+        args = Array(_len > 1 ? _len - 1 : 0),
+        _key = 1;
+      _key < _len;
+      _key++
+    ) {
+      args[_key - 1] = arguments[_key];
+    }
 
-  this.expirationTime = NoWork;
+    var argIndex = 0;
+    var message =
+      "Warning: " +
+      format.replace(/%s/g, function() {
+        return args[argIndex++];
+      });
+    if (typeof console !== "undefined") {
+      console.warn(message);
+    }
+    try {
+      // --- Welcome to debugging React ---
+      // This error was thrown as a convenience so that you can use this stack
+      // to find the callsite that caused this warning to fire.
+      throw new Error(message);
+    } catch (x) {}
+  };
 
-  this.alternate = null;
+  lowPriorityWarning = function(condition, format) {
+    if (format === undefined) {
+      throw new Error(
+        "`warning(condition, format, ...args)` requires a warning " +
+          "message argument"
+      );
+    }
+    if (!condition) {
+      for (
+        var _len2 = arguments.length,
+          args = Array(_len2 > 2 ? _len2 - 2 : 0),
+          _key2 = 2;
+        _key2 < _len2;
+        _key2++
+      ) {
+        args[_key2 - 2] = arguments[_key2];
+      }
 
-  {
-    this._debugID = debugCounter++;
-    this._debugSource = null;
-    this._debugOwner = null;
-    this._debugIsCurrentlyTiming = false;
-    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
-      Object.preventExtensions(this);
+      printWarning.apply(undefined, [format].concat(args));
     }
-  }
+  };
 }
 
-// This is a constructor function, rather than a POJO constructor, still
-// please ensure we do the following:
-// 1) Nobody should add any instance methods on this. Instance methods can be
-//    more difficult to predict when they get optimized and they are almost
-//    never inlined properly in static compilers.
-// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
-//    always know when it is a fiber.
-// 3) We might want to experiment with using numeric keys since they are easier
-//    to optimize in a non-JIT environment.
-// 4) We can easily go from a constructor to a createFiber object literal if that
-//    is faster.
-// 5) It should be easy to port this to a C struct and keep a C implementation
-//    compatible.
-var createFiber = function(tag, pendingProps, key, mode) {
-  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
-  return new FiberNode(tag, pendingProps, key, mode);
+var lowPriorityWarning$1 = lowPriorityWarning;
+
+var ReactStrictModeWarnings = {
+  discardPendingWarnings: function() {},
+  flushPendingDeprecationWarnings: function() {},
+  flushPendingUnsafeLifecycleWarnings: function() {},
+  recordDeprecationWarnings: function(fiber, instance) {},
+  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
 };
 
-function shouldConstruct(Component) {
-  return !!(Component.prototype && Component.prototype.isReactComponent);
-}
+{
+  var LIFECYCLE_SUGGESTIONS = {
+    UNSAFE_componentWillMount: "componentDidMount",
+    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
+    UNSAFE_componentWillUpdate: "componentDidUpdate"
+  };
 
-// This is used to create an alternate fiber to do work on.
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  if (workInProgress === null) {
-    // We use a double buffering pooling technique because we know that we'll
-    // only ever need at most two versions of a tree. We pool the "other" unused
-    // node that we're free to reuse. This is lazily created to avoid allocating
-    // extra objects for things that are never updated. It also allow us to
-    // reclaim the extra memory if needed.
-    workInProgress = createFiber(
-      current.tag,
-      pendingProps,
-      current.key,
-      current.mode
-    );
-    workInProgress.type = current.type;
-    workInProgress.stateNode = current.stateNode;
+  var pendingComponentWillMountWarnings = [];
+  var pendingComponentWillReceivePropsWarnings = [];
+  var pendingComponentWillUpdateWarnings = [];
+  var pendingUnsafeLifecycleWarnings = new Map();
 
-    {
-      // DEV-only fields
-      workInProgress._debugID = current._debugID;
-      workInProgress._debugSource = current._debugSource;
-      workInProgress._debugOwner = current._debugOwner;
-    }
+  // Tracks components we have already warned about.
+  var didWarnAboutDeprecatedLifecycles = new Set();
+  var didWarnAboutUnsafeLifecycles = new Set();
 
-    workInProgress.alternate = current;
-    current.alternate = workInProgress;
-  } else {
-    workInProgress.pendingProps = pendingProps;
+  var setToSortedString = function(set) {
+    var array = [];
+    set.forEach(function(value) {
+      array.push(value);
+    });
+    return array.sort().join(", ");
+  };
 
-    // We already have an alternate.
-    // Reset the effect tag.
-    workInProgress.effectTag = NoEffect;
+  ReactStrictModeWarnings.discardPendingWarnings = function() {
+    pendingComponentWillMountWarnings = [];
+    pendingComponentWillReceivePropsWarnings = [];
+    pendingComponentWillUpdateWarnings = [];
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
 
-    // The effect list is no longer valid.
-    workInProgress.nextEffect = null;
-    workInProgress.firstEffect = null;
-    workInProgress.lastEffect = null;
-  }
+  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
+    pendingUnsafeLifecycleWarnings.forEach(function(
+      lifecycleWarningsMap,
+      strictRoot
+    ) {
+      var lifecyclesWarningMesages = [];
 
-  workInProgress.expirationTime = expirationTime;
+      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
+        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
+        if (lifecycleWarnings.length > 0) {
+          var componentNames = new Set();
+          lifecycleWarnings.forEach(function(fiber) {
+            componentNames.add(getComponentName(fiber) || "Component");
+            didWarnAboutUnsafeLifecycles.add(fiber.type);
+          });
 
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
+          var formatted = lifecycle.replace("UNSAFE_", "");
+          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
+          var sortedComponentNames = setToSortedString(componentNames);
 
-  // These will be overridden during the parent's reconciliation
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
+          lifecyclesWarningMesages.push(
+            formatted +
+              ": Please update the following components to use " +
+              (suggestion + " instead: " + sortedComponentNames)
+          );
+        }
+      });
 
-  return workInProgress;
-}
+      if (lifecyclesWarningMesages.length > 0) {
+        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+          strictRoot
+        );
 
-function createHostRootFiber(isAsync) {
-  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
-  return createFiber(HostRoot, null, null, mode);
-}
+        warning(
+          false,
+          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
+            "\n\n%s" +
+            "\n\nLearn more about this warning here:" +
+            "\nhttps://fb.me/react-strict-mode-warnings",
+          strictRootComponentStack,
+          lifecyclesWarningMesages.join("\n\n")
+        );
+      }
+    });
 
-function createFiberFromElement(element, mode, expirationTime) {
-  var owner = null;
-  {
-    owner = element._owner;
-  }
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
 
-  var fiber = void 0;
-  var type = element.type;
-  var key = element.key;
-  var pendingProps = element.props;
+  var getStrictRoot = function(fiber) {
+    var maybeStrictRoot = null;
 
-  var fiberTag = void 0;
-  if (typeof type === "function") {
-    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
-  } else if (typeof type === "string") {
-    fiberTag = HostComponent;
-  } else {
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          pendingProps.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= AsyncMode | StrictMode;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= StrictMode;
-        break;
-      case REACT_CALL_TYPE:
-        fiberTag = CallComponent;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = ReturnComponent;
-        break;
-      default: {
-        if (typeof type === "object" && type !== null) {
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = ContextProvider;
-              break;
-            case REACT_CONTEXT_TYPE:
-              // This is a consumer
-              fiberTag = ContextConsumer;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = ForwardRef;
-              break;
-            default:
-              if (typeof type.tag === "number") {
-                // Currently assumed to be a continuation and therefore is a
-                // fiber already.
-                // TODO: The yield system is currently broken for updates in
-                // some cases. The reified yield stores a fiber, but we don't
-                // know which fiber that is; the current or a workInProgress?
-                // When the continuation gets rendered here we don't know if we
-                // can reuse that fiber or if we need to clone it. There is
-                // probably a clever way to restructure this.
-                fiber = type;
-                fiber.pendingProps = pendingProps;
-                fiber.expirationTime = expirationTime;
-                return fiber;
-              } else {
-                throwOnInvalidElementType(type, owner);
-              }
-              break;
-          }
-        } else {
-          throwOnInvalidElementType(type, owner);
-        }
+    while (fiber !== null) {
+      if (fiber.mode & StrictMode) {
+        maybeStrictRoot = fiber;
       }
+
+      fiber = fiber.return;
     }
-  }
 
-  fiber = createFiber(fiberTag, pendingProps, key, mode);
-  fiber.type = type;
-  fiber.expirationTime = expirationTime;
+    return maybeStrictRoot;
+  };
 
-  {
-    fiber._debugSource = element._source;
-    fiber._debugOwner = element._owner;
-  }
+  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
+    if (pendingComponentWillMountWarnings.length > 0) {
+      var uniqueNames = new Set();
+      pendingComponentWillMountWarnings.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-  return fiber;
-}
+      var sortedNames = setToSortedString(uniqueNames);
 
-function throwOnInvalidElementType(type, owner) {
-  var info = "";
-  {
-    if (
-      type === undefined ||
-      (typeof type === "object" &&
-        type !== null &&
-        Object.keys(type).length === 0)
-    ) {
-      info +=
-        " You likely forgot to export your component from the file " +
-        "it's defined in, or you might have mixed up default and " +
-        "named imports.";
-    }
-    var ownerName = owner ? getComponentName(owner) : null;
-    if (ownerName) {
-      info += "\n\nCheck the render method of `" + ownerName + "`.";
+      lowPriorityWarning$1(
+        false,
+        "componentWillMount is deprecated and will be removed in the next major version. " +
+          "Use componentDidMount instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillMount." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        sortedNames
+      );
+
+      pendingComponentWillMountWarnings = [];
     }
-  }
-  invariant(
-    false,
-    "Element type is invalid: expected a string (for built-in " +
-      "components) or a class/function (for composite components) " +
-      "but got: %s.%s",
-    type == null ? type : typeof type,
-    info
-  );
-}
 
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  var fiber = createFiber(Fragment, elements, key, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
+    if (pendingComponentWillReceivePropsWarnings.length > 0) {
+      var _uniqueNames = new Set();
+      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
+        _uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-function createFiberFromText(content, mode, expirationTime) {
-  var fiber = createFiber(HostText, content, null, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
+      var _sortedNames = setToSortedString(_uniqueNames);
 
-function createFiberFromHostInstanceForDeletion() {
-  var fiber = createFiber(HostComponent, null, null, NoContext);
-  fiber.type = "DELETED";
-  return fiber;
-}
+      lowPriorityWarning$1(
+        false,
+        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
+          "Use static getDerivedStateFromProps instead." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames
+      );
 
-function createFiberFromPortal(portal, mode, expirationTime) {
-  var pendingProps = portal.children !== null ? portal.children : [];
-  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null, // Used by persistent updates
-    implementation: portal.implementation
-  };
-  return fiber;
-}
+      pendingComponentWillReceivePropsWarnings = [];
+    }
 
-// Used for stashing WIP properties to replay failed work in DEV.
-function assignFiberPropertiesInDEV(target, source) {
-  if (target === null) {
-    // This Fiber's initial properties will always be overwritten.
-    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
-    target = createFiber(IndeterminateComponent, null, null, NoContext);
-  }
+    if (pendingComponentWillUpdateWarnings.length > 0) {
+      var _uniqueNames2 = new Set();
+      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
+        _uniqueNames2.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-  // This is intentionally written as a list of all properties.
-  // We tried to use Object.assign() instead but this is called in
-  // the hottest path, and Object.assign() was too slow:
-  // https://github.com/facebook/react/issues/12502
-  // This code is DEV-only so size is not a concern.
+      var _sortedNames2 = setToSortedString(_uniqueNames2);
 
-  target.tag = source.tag;
-  target.key = source.key;
-  target.type = source.type;
-  target.stateNode = source.stateNode;
-  target["return"] = source["return"];
-  target.child = source.child;
-  target.sibling = source.sibling;
-  target.index = source.index;
-  target.ref = source.ref;
-  target.pendingProps = source.pendingProps;
-  target.memoizedProps = source.memoizedProps;
-  target.updateQueue = source.updateQueue;
-  target.memoizedState = source.memoizedState;
-  target.mode = source.mode;
-  target.effectTag = source.effectTag;
-  target.nextEffect = source.nextEffect;
-  target.firstEffect = source.firstEffect;
-  target.lastEffect = source.lastEffect;
-  target.expirationTime = source.expirationTime;
-  target.alternate = source.alternate;
-  target._debugID = source._debugID;
-  target._debugSource = source._debugSource;
-  target._debugOwner = source._debugOwner;
-  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
-  return target;
-}
+      lowPriorityWarning$1(
+        false,
+        "componentWillUpdate is deprecated and will be removed in the next major version. " +
+          "Use componentDidUpdate instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillUpdate." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames2
+      );
 
-// TODO: This should be lifted into the renderer.
+      pendingComponentWillUpdateWarnings = [];
+    }
+  };
 
-function createFiberRoot(containerInfo, isAsync, hydrate) {
-  // Cyclic construction. This cheats the type system right now because
-  // stateNode is any.
-  var uninitializedFiber = createHostRootFiber(isAsync);
-  var root = {
-    current: uninitializedFiber,
-    containerInfo: containerInfo,
-    pendingChildren: null,
-    pendingCommitExpirationTime: NoWork,
-    finishedWork: null,
-    context: null,
-    pendingContext: null,
-    hydrate: hydrate,
-    remainingExpirationTime: NoWork,
-    firstBatch: null,
-    nextScheduledRoot: null
+  ReactStrictModeWarnings.recordDeprecationWarnings = function(
+    fiber,
+    instance
+  ) {
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
+      return;
+    }
+
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillMountWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" &&
+      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillReceivePropsWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillUpdate === "function" &&
+      instance.componentWillUpdate.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillUpdateWarnings.push(fiber);
+    }
   };
-  uninitializedFiber.stateNode = root;
-  return root;
-}
 
-var onCommitFiberRoot = null;
-var onCommitFiberUnmount = null;
-var hasLoggedError = false;
+  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = getStrictRoot(fiber);
 
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {
-      if (true && !hasLoggedError) {
-        hasLoggedError = true;
-        warning(false, "React DevTools encountered an error: %s", err);
-      }
+    // Dedup strategy: Warn once per component.
+    // This is difficult to track any other way since component names
+    // are often vague and are likely to collide between 3rd party libraries.
+    // An expand property is probably okay to use here since it's DEV-only,
+    // and will only be set in the event of serious warnings.
+    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+      return;
+    }
+
+    var warningsForRoot = void 0;
+    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
+      warningsForRoot = {
+        UNSAFE_componentWillMount: [],
+        UNSAFE_componentWillReceiveProps: [],
+        UNSAFE_componentWillUpdate: []
+      };
+
+      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
+    } else {
+      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
+    }
+
+    var unsafeLifecycles = [];
+    if (
+      (typeof instance.componentWillMount === "function" &&
+        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
+      typeof instance.UNSAFE_componentWillMount === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillMount");
+    }
+    if (
+      (typeof instance.componentWillReceiveProps === "function" &&
+        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+          true) ||
+      typeof instance.UNSAFE_componentWillReceiveProps === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    }
+    if (
+      (typeof instance.componentWillUpdate === "function" &&
+        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
+      typeof instance.UNSAFE_componentWillUpdate === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
+    }
+
+    if (unsafeLifecycles.length > 0) {
+      unsafeLifecycles.forEach(function(lifecycle) {
+        warningsForRoot[lifecycle].push(fiber);
+      });
     }
   };
 }
 
-function injectInternals(internals) {
-  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
-    // No DevTools
-    return false;
+/**
+ * The "actual" render time is total time required to render the descendants of a Profiler component.
+ * This time is stored as a stack, since Profilers can be nested.
+ * This time is started during the "begin" phase and stopped during the "complete" phase.
+ * It is paused (and accumulated) in the event of an interruption or an aborted render.
+ */
+
+function createProfilerTimer(now) {
+  var fiberStack = void 0;
+
+  {
+    fiberStack = [];
   }
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled) {
-    // This isn't a real property on the hook, but it can be set to opt out
-    // of DevTools integration and associated warnings and logs.
-    // https://github.com/facebook/react/issues/3877
-    return true;
+
+  var timerPausedAt = 0;
+  var totalElapsedPauseTime = 0;
+
+  function checkActualRenderTimeStackEmpty() {
+    {
+      !(fiberStack.length === 0)
+        ? warning(
+            false,
+            "Expected an empty stack. Something was not reset properly."
+          )
+        : void 0;
+    }
   }
-  if (!hook.supportsFiber) {
+
+  function markActualRenderTimeStarted(fiber) {
     {
-      warning(
-        false,
-        "The installed version of React DevTools is too old and will not work " +
-          "with the current version of React. Please update React DevTools. " +
-          "https://fb.me/react-devtools"
-      );
+      fiberStack.push(fiber);
     }
-    // DevTools exists, even though it doesn't support Fiber.
-    return true;
+    fiber.stateNode.startTime = now() - totalElapsedPauseTime;
   }
-  try {
-    var rendererID = hook.inject(internals);
-    // We have successfully injected, so now it is safe to set up hooks.
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {
-    // Catch all errors because it is unsafe to throw during initialization.
+
+  function pauseActualRenderTimerIfRunning() {
+    if (timerPausedAt === 0) {
+      timerPausedAt = now();
+    }
+  }
+
+  function recordElapsedActualRenderTime(fiber) {
     {
-      warning(false, "React DevTools encountered an error: %s.", err);
+      !(fiber === fiberStack.pop())
+        ? warning(false, "Unexpected Fiber popped.")
+        : void 0;
     }
+    fiber.stateNode.duration +=
+      now() - totalElapsedPauseTime - fiber.stateNode.startTime;
   }
-  // DevTools exists
-  return true;
-}
 
-function onCommitRoot(root) {
-  if (typeof onCommitFiberRoot === "function") {
-    onCommitFiberRoot(root);
+  function resetActualRenderTimer() {
+    totalElapsedPauseTime = 0;
   }
-}
 
-function onCommitUnmount(fiber) {
-  if (typeof onCommitFiberUnmount === "function") {
-    onCommitFiberUnmount(fiber);
+  function resumeActualRenderTimerIfPaused() {
+    if (timerPausedAt > 0) {
+      totalElapsedPauseTime += now() - timerPausedAt;
+      timerPausedAt = 0;
+    }
   }
-}
 
-/**
- * Forked from fbjs/warning:
- * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
- *
- * Only change is we use console.warn instead of console.error,
- * and do nothing when 'console' is not supported.
- * This really simplifies the code.
- * ---
- * Similar to invariant but only logs a warning if the condition is not met.
- * This can be used to log issues in development environments in critical
- * paths. Removing the logging code for production environments will keep the
- * same logic and follow the same code paths.
- */
+  /**
+   * The "base" render time is the duration of the “begin” phase of work for a particular fiber.
+   * This time is measured and stored on each fiber.
+   * The time for all sibling fibers are accumulated and stored on their parent during the "complete" phase.
+   * If a fiber bails out (sCU false) then its "base" timer is cancelled and the fiber is not updated.
+   */
 
-var lowPriorityWarning = function() {};
+  var baseStartTime = -1;
 
-{
-  var printWarning = function(format) {
-    for (
-      var _len = arguments.length,
-        args = Array(_len > 1 ? _len - 1 : 0),
-        _key = 1;
-      _key < _len;
-      _key++
-    ) {
-      args[_key - 1] = arguments[_key];
+  function recordElapsedBaseRenderTimeIfRunning(fiber) {
+    if (baseStartTime !== -1) {
+      fiber.selfBaseTime = now() - baseStartTime;
     }
+  }
 
-    var argIndex = 0;
-    var message =
-      "Warning: " +
-      format.replace(/%s/g, function() {
-        return args[argIndex++];
-      });
-    if (typeof console !== "undefined") {
-      console.warn(message);
+  function startBaseRenderTimer() {
+    {
+      if (baseStartTime !== -1) {
+        warning(
+          false,
+          "Cannot start base timer that is already running. " +
+            "This error is likely caused by a bug in React. " +
+            "Please file an issue."
+        );
+      }
     }
-    try {
-      // --- Welcome to debugging React ---
-      // This error was thrown as a convenience so that you can use this stack
-      // to find the callsite that caused this warning to fire.
-      throw new Error(message);
-    } catch (x) {}
-  };
+    baseStartTime = now();
+  }
 
-  lowPriorityWarning = function(condition, format) {
-    if (format === undefined) {
-      throw new Error(
-        "`warning(condition, format, ...args)` requires a warning " +
-          "message argument"
-      );
-    }
-    if (!condition) {
-      for (
-        var _len2 = arguments.length,
-          args = Array(_len2 > 2 ? _len2 - 2 : 0),
-          _key2 = 2;
-        _key2 < _len2;
-        _key2++
-      ) {
-        args[_key2 - 2] = arguments[_key2];
-      }
+  function stopBaseRenderTimerIfRunning() {
+    baseStartTime = -1;
+  }
 
-      printWarning.apply(undefined, [format].concat(args));
-    }
-  };
+  if (enableProfilerTimer) {
+    return {
+      checkActualRenderTimeStackEmpty: checkActualRenderTimeStackEmpty,
+      markActualRenderTimeStarted: markActualRenderTimeStarted,
+      pauseActualRenderTimerIfRunning: pauseActualRenderTimerIfRunning,
+      recordElapsedActualRenderTime: recordElapsedActualRenderTime,
+      resetActualRenderTimer: resetActualRenderTimer,
+      resumeActualRenderTimerIfPaused: resumeActualRenderTimerIfPaused,
+      recordElapsedBaseRenderTimeIfRunning: recordElapsedBaseRenderTimeIfRunning,
+      startBaseRenderTimer: startBaseRenderTimer,
+      stopBaseRenderTimerIfRunning: stopBaseRenderTimerIfRunning
+    };
+  } else {
+    return {
+      checkActualRenderTimeStackEmpty: function() {},
+      markActualRenderTimeStarted: function(fiber) {},
+      pauseActualRenderTimerIfRunning: function() {},
+      recordElapsedActualRenderTime: function(fiber) {},
+      resetActualRenderTimer: function() {},
+      resumeActualRenderTimerIfPaused: function() {},
+      recordElapsedBaseRenderTimeIfRunning: function(fiber) {},
+      startBaseRenderTimer: function() {},
+      stopBaseRenderTimerIfRunning: function() {}
+    };
+  }
 }
 
-var lowPriorityWarning$1 = lowPriorityWarning;
+function getCurrentFiberOwnerName() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    var owner = fiber._debugOwner;
+    if (owner !== null && typeof owner !== "undefined") {
+      return getComponentName(owner);
+    }
+  }
+  return null;
+}
 
-var ReactStrictModeWarnings = {
-  discardPendingWarnings: function() {},
-  flushPendingDeprecationWarnings: function() {},
-  flushPendingUnsafeLifecycleWarnings: function() {},
-  recordDeprecationWarnings: function(fiber, instance) {},
-  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
-};
+function getCurrentFiberStackAddendum$1() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    // Safe because if current fiber exists, we are reconciling,
+    // and it is guaranteed to be the work-in-progress version.
+    return getStackAddendumByWorkInProgressFiber(fiber);
+  }
+  return null;
+}
 
-{
-  var LIFECYCLE_SUGGESTIONS = {
-    UNSAFE_componentWillMount: "componentDidMount",
-    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
-    UNSAFE_componentWillUpdate: "componentDidUpdate"
-  };
+function resetCurrentFiber() {
+  ReactDebugCurrentFrame.getCurrentStack = null;
+  ReactDebugCurrentFiber.current = null;
+  ReactDebugCurrentFiber.phase = null;
+}
 
-  var pendingComponentWillMountWarnings = [];
-  var pendingComponentWillReceivePropsWarnings = [];
-  var pendingComponentWillUpdateWarnings = [];
-  var pendingUnsafeLifecycleWarnings = new Map();
+function setCurrentFiber(fiber) {
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum$1;
+  ReactDebugCurrentFiber.current = fiber;
+  ReactDebugCurrentFiber.phase = null;
+}
 
-  // Tracks components we have already warned about.
-  var didWarnAboutDeprecatedLifecycles = new Set();
-  var didWarnAboutUnsafeLifecycles = new Set();
+function setCurrentPhase(phase) {
+  ReactDebugCurrentFiber.phase = phase;
+}
 
-  var setToSortedString = function(set) {
-    var array = [];
-    set.forEach(function(value) {
-      array.push(value);
-    });
-    return array.sort().join(", ");
-  };
+var ReactDebugCurrentFiber = {
+  current: null,
+  phase: null,
+  resetCurrentFiber: resetCurrentFiber,
+  setCurrentFiber: setCurrentFiber,
+  setCurrentPhase: setCurrentPhase,
+  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum$1
+};
 
-  ReactStrictModeWarnings.discardPendingWarnings = function() {
-    pendingComponentWillMountWarnings = [];
-    pendingComponentWillReceivePropsWarnings = [];
-    pendingComponentWillUpdateWarnings = [];
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+// Prefix measurements so that it's possible to filter them.
+// Longer prefixes are hard to read in DevTools.
+var reactEmoji = "\u269B";
+var warningEmoji = "\u26D4";
+var supportsUserTiming =
+  typeof performance !== "undefined" &&
+  typeof performance.mark === "function" &&
+  typeof performance.clearMarks === "function" &&
+  typeof performance.measure === "function" &&
+  typeof performance.clearMeasures === "function";
 
-  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
-    pendingUnsafeLifecycleWarnings.forEach(function(
-      lifecycleWarningsMap,
-      strictRoot
-    ) {
-      var lifecyclesWarningMesages = [];
+// Keep track of current fiber so that we know the path to unwind on pause.
+// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
+var currentFiber = null;
+// If we're in the middle of user code, which fiber and method is it?
+// Reusing `currentFiber` would be confusing for this because user code fiber
+// can change during commit phase too, but we don't need to unwind it (since
+// lifecycles in the commit phase don't resemble a tree).
+var currentPhase = null;
+var currentPhaseFiber = null;
+// Did lifecycle hook schedule an update? This is often a performance problem,
+// so we will keep track of it, and include it in the report.
+// Track commits caused by cascading updates.
+var isCommitting = false;
+var hasScheduledUpdateInCurrentCommit = false;
+var hasScheduledUpdateInCurrentPhase = false;
+var commitCountInCurrentWorkLoop = 0;
+var effectCountInCurrentCommit = 0;
+var isWaitingForCallback = false;
+// During commits, we only show a measurement once per method name
+// to avoid stretch the commit phase with measurement overhead.
+var labelsInCurrentCommit = new Set();
 
-      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
-        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
-        if (lifecycleWarnings.length > 0) {
-          var componentNames = new Set();
-          lifecycleWarnings.forEach(function(fiber) {
-            componentNames.add(getComponentName(fiber) || "Component");
-            didWarnAboutUnsafeLifecycles.add(fiber.type);
-          });
+var formatMarkName = function(markName) {
+  return reactEmoji + " " + markName;
+};
 
-          var formatted = lifecycle.replace("UNSAFE_", "");
-          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = setToSortedString(componentNames);
+var formatLabel = function(label, warning$$1) {
+  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
+  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
+  return "" + prefix + label + suffix;
+};
 
-          lifecyclesWarningMesages.push(
-            formatted +
-              ": Please update the following components to use " +
-              (suggestion + " instead: " + sortedComponentNames)
-          );
-        }
-      });
+var beginMark = function(markName) {
+  performance.mark(formatMarkName(markName));
+};
 
-      if (lifecyclesWarningMesages.length > 0) {
-        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
-          strictRoot
-        );
+var clearMark = function(markName) {
+  performance.clearMarks(formatMarkName(markName));
+};
 
-        warning(
-          false,
-          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
-            "\n\n%s" +
-            "\n\nLearn more about this warning here:" +
-            "\nhttps://fb.me/react-strict-mode-warnings",
-          strictRootComponentStack,
-          lifecyclesWarningMesages.join("\n\n")
-        );
-      }
-    });
+var endMark = function(label, markName, warning$$1) {
+  var formattedMarkName = formatMarkName(markName);
+  var formattedLabel = formatLabel(label, warning$$1);
+  try {
+    performance.measure(formattedLabel, formattedMarkName);
+  } catch (err) {}
+  // If previous mark was missing for some reason, this will throw.
+  // This could only happen if React crashed in an unexpected place earlier.
+  // Don't pile on with more errors.
 
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+  // Clear marks immediately to avoid growing buffer.
+  performance.clearMarks(formattedMarkName);
+  performance.clearMeasures(formattedLabel);
+};
 
-  var getStrictRoot = function(fiber) {
-    var maybeStrictRoot = null;
+var getFiberMarkName = function(label, debugID) {
+  return label + " (#" + debugID + ")";
+};
 
-    while (fiber !== null) {
-      if (fiber.mode & StrictMode) {
-        maybeStrictRoot = fiber;
-      }
-
-      fiber = fiber["return"];
-    }
-
-    return maybeStrictRoot;
-  };
+var getFiberLabel = function(componentName, isMounted, phase) {
+  if (phase === null) {
+    // These are composite component total time measurements.
+    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
+  } else {
+    // Composite component methods.
+    return componentName + "." + phase;
+  }
+};
 
-  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
-    if (pendingComponentWillMountWarnings.length > 0) {
-      var uniqueNames = new Set();
-      pendingComponentWillMountWarnings.forEach(function(fiber) {
-        uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+var beginFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
 
-      var sortedNames = setToSortedString(uniqueNames);
+  if (isCommitting && labelsInCurrentCommit.has(label)) {
+    // During the commit phase, we don't show duplicate labels because
+    // there is a fixed overhead for every measurement, and we don't
+    // want to stretch the commit phase beyond necessary.
+    return false;
+  }
+  labelsInCurrentCommit.add(label);
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillMount is deprecated and will be removed in the next major version. " +
-          "Use componentDidMount instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillMount." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        sortedNames
-      );
+  var markName = getFiberMarkName(label, debugID);
+  beginMark(markName);
+  return true;
+};
 
-      pendingComponentWillMountWarnings = [];
-    }
+var clearFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  clearMark(markName);
+};
 
-    if (pendingComponentWillReceivePropsWarnings.length > 0) {
-      var _uniqueNames = new Set();
-      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
-        _uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+var endFiberMark = function(fiber, phase, warning$$1) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  endMark(label, markName, warning$$1);
+};
 
-      var _sortedNames = setToSortedString(_uniqueNames);
+var shouldIgnoreFiber = function(fiber) {
+  // Host components should be skipped in the timeline.
+  // We could check typeof fiber.type, but does this work with RN?
+  switch (fiber.tag) {
+    case HostRoot:
+    case HostComponent:
+    case HostText:
+    case HostPortal:
+    case CallComponent:
+    case ReturnComponent:
+    case Fragment:
+    case ContextProvider:
+    case ContextConsumer:
+    case Mode:
+      return true;
+    default:
+      return false;
+  }
+};
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
-          "Use static getDerivedStateFromProps instead." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames
-      );
+var clearPendingPhaseMeasurement = function() {
+  if (currentPhase !== null && currentPhaseFiber !== null) {
+    clearFiberMark(currentPhaseFiber, currentPhase);
+  }
+  currentPhaseFiber = null;
+  currentPhase = null;
+  hasScheduledUpdateInCurrentPhase = false;
+};
 
-      pendingComponentWillReceivePropsWarnings = [];
+var pauseTimers = function() {
+  // Stops all currently active measurements so that they can be resumed
+  // if we continue in a later deferred loop from the same unit of work.
+  var fiber = currentFiber;
+  while (fiber) {
+    if (fiber._debugIsCurrentlyTiming) {
+      endFiberMark(fiber, null, null);
     }
+    fiber = fiber.return;
+  }
+};
 
-    if (pendingComponentWillUpdateWarnings.length > 0) {
-      var _uniqueNames2 = new Set();
-      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
-        _uniqueNames2.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames2 = setToSortedString(_uniqueNames2);
-
-      lowPriorityWarning$1(
-        false,
-        "componentWillUpdate is deprecated and will be removed in the next major version. " +
-          "Use componentDidUpdate instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillUpdate." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames2
-      );
+var resumeTimersRecursively = function(fiber) {
+  if (fiber.return !== null) {
+    resumeTimersRecursively(fiber.return);
+  }
+  if (fiber._debugIsCurrentlyTiming) {
+    beginFiberMark(fiber, null);
+  }
+};
 
-      pendingComponentWillUpdateWarnings = [];
-    }
-  };
+var resumeTimers = function() {
+  // Resumes all measurements that were active during the last deferred loop.
+  if (currentFiber !== null) {
+    resumeTimersRecursively(currentFiber);
+  }
+};
 
-  ReactStrictModeWarnings.recordDeprecationWarnings = function(
-    fiber,
-    instance
-  ) {
-    // Dedup strategy: Warn once per component.
-    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
-      return;
-    }
+function recordEffect() {
+  if (enableUserTimingAPI) {
+    effectCountInCurrentCommit++;
+  }
+}
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillMountWarnings.push(fiber);
+function recordScheduleUpdate() {
+  if (enableUserTimingAPI) {
+    if (isCommitting) {
+      hasScheduledUpdateInCurrentCommit = true;
     }
     if (
-      typeof instance.componentWillReceiveProps === "function" &&
-      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+      currentPhase !== null &&
+      currentPhase !== "componentWillMount" &&
+      currentPhase !== "componentWillReceiveProps"
     ) {
-      pendingComponentWillReceivePropsWarnings.push(fiber);
+      hasScheduledUpdateInCurrentPhase = true;
     }
-    if (
-      typeof instance.componentWillUpdate === "function" &&
-      instance.componentWillUpdate.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillUpdateWarnings.push(fiber);
+  }
+}
+
+function startRequestCallbackTimer() {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming && !isWaitingForCallback) {
+      isWaitingForCallback = true;
+      beginMark("(Waiting for async callback...)");
     }
-  };
+  }
+}
 
-  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
-    fiber,
-    instance
-  ) {
-    var strictRoot = getStrictRoot(fiber);
+function stopRequestCallbackTimer(didExpire, expirationTime) {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming) {
+      isWaitingForCallback = false;
+      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
+      endMark(
+        "(Waiting for async callback... will force flush in " +
+          expirationTime +
+          " ms)",
+        "(Waiting for async callback...)",
+        warning$$1
+      );
+    }
+  }
+}
 
-    // Dedup strategy: Warn once per component.
-    // This is difficult to track any other way since component names
-    // are often vague and are likely to collide between 3rd party libraries.
-    // An expand property is probably okay to use here since it's DEV-only,
-    // and will only be set in the event of serious warnings.
-    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+function startWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
       return;
     }
+    // If we pause, this is the fiber to unwind from.
+    currentFiber = fiber;
+    if (!beginFiberMark(fiber, null)) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = true;
+  }
+}
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    // Note that it is sufficient to check for the presence of a
-    // single lifecycle, componentWillMount, with the polyfill flag.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning === true
-    ) {
+function cancelWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
       return;
     }
+    // Remember we shouldn't complete measurement for this fiber.
+    // Otherwise flamechart will be deep even for small updates.
+    fiber._debugIsCurrentlyTiming = false;
+    clearFiberMark(fiber, null);
+  }
+}
 
-    var warningsForRoot = void 0;
-    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
-      warningsForRoot = {
-        UNSAFE_componentWillMount: [],
-        UNSAFE_componentWillReceiveProps: [],
-        UNSAFE_componentWillUpdate: []
-      };
+function stopWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber.return;
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = false;
+    endFiberMark(fiber, null, null);
+  }
+}
 
-      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
-    } else {
-      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
+function stopFailedWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
     }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber.return;
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = false;
+    var warning$$1 = "An error was thrown inside this error boundary";
+    endFiberMark(fiber, null, warning$$1);
+  }
+}
 
-    var unsafeLifecycles = [];
-    if (
-      typeof instance.componentWillMount === "function" ||
-      typeof instance.UNSAFE_componentWillMount === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillMount");
+function startPhaseTimer(fiber, phase) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    if (
-      typeof instance.componentWillReceiveProps === "function" ||
-      typeof instance.UNSAFE_componentWillReceiveProps === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    clearPendingPhaseMeasurement();
+    if (!beginFiberMark(fiber, phase)) {
+      return;
     }
-    if (
-      typeof instance.componentWillUpdate === "function" ||
-      typeof instance.UNSAFE_componentWillUpdate === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
+    currentPhaseFiber = fiber;
+    currentPhase = phase;
+  }
+}
+
+function stopPhaseTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    if (currentPhase !== null && currentPhaseFiber !== null) {
+      var warning$$1 = hasScheduledUpdateInCurrentPhase
+        ? "Scheduled a cascading update"
+        : null;
+      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
     }
+    currentPhase = null;
+    currentPhaseFiber = null;
+  }
+}
 
-    if (unsafeLifecycles.length > 0) {
-      unsafeLifecycles.forEach(function(lifecycle) {
-        warningsForRoot[lifecycle].push(fiber);
-      });
+function startWorkLoopTimer(nextUnitOfWork) {
+  if (enableUserTimingAPI) {
+    currentFiber = nextUnitOfWork;
+    if (!supportsUserTiming) {
+      return;
     }
-  };
+    commitCountInCurrentWorkLoop = 0;
+    // This is top level call.
+    // Any other measurements are performed within.
+    beginMark("(React Tree Reconciliation)");
+    // Resume any measurements that were in progress during the last loop.
+    resumeTimers();
+  }
 }
 
-var debugRenderPhaseSideEffects = false;
-var debugRenderPhaseSideEffectsForStrictMode = false;
-var enableGetDerivedStateFromCatch = false;
-var enableMutatingReconciler = true;
-var enableNoopReconciler = false;
-var enablePersistentReconciler = false;
-var enableUserTimingAPI = true;
-var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
-var warnAboutDeprecatedLifecycles = false;
+function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var warning$$1 = null;
+    if (interruptedBy !== null) {
+      if (interruptedBy.tag === HostRoot) {
+        warning$$1 = "A top-level update interrupted the previous render";
+      } else {
+        var componentName = getComponentName(interruptedBy) || "Unknown";
+        warning$$1 =
+          "An update to " + componentName + " interrupted the previous render";
+      }
+    } else if (commitCountInCurrentWorkLoop > 1) {
+      warning$$1 = "There were cascading updates";
+    }
+    commitCountInCurrentWorkLoop = 0;
+    var label = didCompleteRoot
+      ? "(React Tree Reconciliation: Completed Root)"
+      : "(React Tree Reconciliation: Yielded)";
+    // Pause any measurements until the next loop.
+    pauseTimers();
+    endMark(label, "(React Tree Reconciliation)", warning$$1);
+  }
+}
 
-// Only used in www builds.
+function startCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    isCommitting = true;
+    hasScheduledUpdateInCurrentCommit = false;
+    labelsInCurrentCommit.clear();
+    beginMark("(Committing Changes)");
+  }
+}
 
-function getCurrentFiberOwnerName() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
+function stopCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    var owner = fiber._debugOwner;
-    if (owner !== null && typeof owner !== "undefined") {
-      return getComponentName(owner);
+
+    var warning$$1 = null;
+    if (hasScheduledUpdateInCurrentCommit) {
+      warning$$1 = "Lifecycle hook scheduled a cascading update";
+    } else if (commitCountInCurrentWorkLoop > 0) {
+      warning$$1 = "Caused by a cascading update in earlier commit";
     }
+    hasScheduledUpdateInCurrentCommit = false;
+    commitCountInCurrentWorkLoop++;
+    isCommitting = false;
+    labelsInCurrentCommit.clear();
+
+    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
   }
-  return null;
 }
 
-function getCurrentFiberStackAddendum() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
+function startCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
-    // Safe because if current fiber exists, we are reconciling,
-    // and it is guaranteed to be the work-in-progress version.
-    return getStackAddendumByWorkInProgressFiber(fiber);
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Snapshot Effects)");
   }
-  return null;
 }
 
-function resetCurrentFiber() {
-  ReactDebugCurrentFrame.getCurrentStack = null;
-  ReactDebugCurrentFiber.current = null;
-  ReactDebugCurrentFiber.phase = null;
+function stopCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Snapshot Effects: " + count + " Total)",
+      "(Committing Snapshot Effects)",
+      null
+    );
+  }
 }
 
-function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
-  ReactDebugCurrentFiber.current = fiber;
-  ReactDebugCurrentFiber.phase = null;
+function startCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Host Effects)");
+  }
 }
 
-function setCurrentPhase(phase) {
-  ReactDebugCurrentFiber.phase = phase;
+function stopCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Host Effects: " + count + " Total)",
+      "(Committing Host Effects)",
+      null
+    );
+  }
 }
 
-var ReactDebugCurrentFiber = {
-  current: null,
-  phase: null,
-  resetCurrentFiber: resetCurrentFiber,
-  setCurrentFiber: setCurrentFiber,
-  setCurrentPhase: setCurrentPhase,
-  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
-};
-
-// Prefix measurements so that it's possible to filter them.
-// Longer prefixes are hard to read in DevTools.
-var reactEmoji = "\u269B";
-var warningEmoji = "\u26D4";
-var supportsUserTiming =
-  typeof performance !== "undefined" &&
-  typeof performance.mark === "function" &&
-  typeof performance.clearMarks === "function" &&
-  typeof performance.measure === "function" &&
-  typeof performance.clearMeasures === "function";
+function startCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Calling Lifecycle Methods)");
+  }
+}
 
-// Keep track of current fiber so that we know the path to unwind on pause.
-// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
-var currentFiber = null;
-// If we're in the middle of user code, which fiber and method is it?
-// Reusing `currentFiber` would be confusing for this because user code fiber
-// can change during commit phase too, but we don't need to unwind it (since
-// lifecycles in the commit phase don't resemble a tree).
-var currentPhase = null;
-var currentPhaseFiber = null;
-// Did lifecycle hook schedule an update? This is often a performance problem,
-// so we will keep track of it, and include it in the report.
-// Track commits caused by cascading updates.
-var isCommitting = false;
-var hasScheduledUpdateInCurrentCommit = false;
-var hasScheduledUpdateInCurrentPhase = false;
-var commitCountInCurrentWorkLoop = 0;
-var effectCountInCurrentCommit = 0;
-var isWaitingForCallback = false;
-// During commits, we only show a measurement once per method name
-// to avoid stretch the commit phase with measurement overhead.
-var labelsInCurrentCommit = new Set();
-
-var formatMarkName = function(markName) {
-  return reactEmoji + " " + markName;
-};
+function stopCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Calling Lifecycle Methods: " + count + " Total)",
+      "(Calling Lifecycle Methods)",
+      null
+    );
+  }
+}
 
-var formatLabel = function(label, warning$$1) {
-  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
-  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
-  return "" + prefix + label + suffix;
-};
+// UpdateQueue is a linked list of prioritized updates.
+//
+// Like fibers, update queues come in pairs: a current queue, which represents
+// the visible state of the screen, and a work-in-progress queue, which is
+// can be mutated and processed asynchronously before it is committed — a form
+// of double buffering. If a work-in-progress render is discarded before
+// finishing, we create a new work-in-progress by cloning the current queue.
+//
+// Both queues share a persistent, singly-linked list structure. To schedule an
+// update, we append it to the end of both queues. Each queue maintains a
+// pointer to first update in the persistent list that hasn't been processed.
+// The work-in-progress pointer always has a position equal to or greater than
+// the current queue, since we always work on that one. The current queue's
+// pointer is only updated during the commit phase, when we swap in the
+// work-in-progress.
+//
+// For example:
+//
+//   Current pointer:           A - B - C - D - E - F
+//   Work-in-progress pointer:              D - E - F
+//                                          ^
+//                                          The work-in-progress queue has
+//                                          processed more updates than current.
+//
+// The reason we append to both queues is because otherwise we might drop
+// updates without ever processing them. For example, if we only add updates to
+// the work-in-progress queue, some updates could be lost whenever a work-in
+// -progress render restarts by cloning from current. Similarly, if we only add
+// updates to the current queue, the updates will be lost whenever an already
+// in-progress queue commits and swaps with the current queue. However, by
+// adding to both queues, we guarantee that the update will be part of the next
+// work-in-progress. (And because the work-in-progress queue becomes the
+// current queue once it commits, there's no danger of applying the same
+// update twice.)
+//
+// Prioritization
+// --------------
+//
+// Updates are not sorted by priority, but by insertion; new updates are always
+// appended to the end of the list.
+//
+// The priority is still important, though. When processing the update queue
+// during the render phase, only the updates with sufficient priority are
+// included in the result. If we skip an update because it has insufficient
+// priority, it remains in the queue to be processed later, during a lower
+// priority render. Crucially, all updates subsequent to a skipped update also
+// remain in the queue *regardless of their priority*. That means high priority
+// updates are sometimes processed twice, at two separate priorities. We also
+// keep track of a base state, that represents the state before the first
+// update in the queue is applied.
+//
+// For example:
+//
+//   Given a base state of '', and the following queue of updates
+//
+//     A1 - B2 - C1 - D2
+//
+//   where the number indicates the priority, and the update is applied to the
+//   previous state by appending a letter, React will process these updates as
+//   two separate renders, one per distinct priority level:
+//
+//   First render, at priority 1:
+//     Base state: ''
+//     Updates: [A1, C1]
+//     Result state: 'AC'
+//
+//   Second render, at priority 2:
+//     Base state: 'A'            <-  The base state does not include C1,
+//                                    because B2 was skipped.
+//     Updates: [B2, C1, D2]      <-  C1 was rebased on top of B2
+//     Result state: 'ABCD'
+//
+// Because we process updates in insertion order, and rebase high priority
+// updates when preceding updates are skipped, the final result is deterministic
+// regardless of priority. Intermediate state may vary according to system
+// resources, but the final state is always the same.
 
-var beginMark = function(markName) {
-  performance.mark(formatMarkName(markName));
-};
+var UpdateState = 0;
+var ReplaceState = 1;
+var ForceUpdate = 2;
+var CaptureUpdate = 3;
 
-var clearMark = function(markName) {
-  performance.clearMarks(formatMarkName(markName));
-};
+// Global state that is reset at the beginning of calling `processUpdateQueue`.
+// It should only be read right after calling `processUpdateQueue`, via
+// `checkHasForceUpdateAfterProcessing`.
+var hasForceUpdate = false;
 
-var endMark = function(label, markName, warning$$1) {
-  var formattedMarkName = formatMarkName(markName);
-  var formattedLabel = formatLabel(label, warning$$1);
-  try {
-    performance.measure(formattedLabel, formattedMarkName);
-  } catch (err) {}
-  // If previous mark was missing for some reason, this will throw.
-  // This could only happen if React crashed in an unexpected place earlier.
-  // Don't pile on with more errors.
+var didWarnUpdateInsideUpdate = void 0;
+var currentlyProcessingQueue = void 0;
+var resetCurrentlyProcessingQueue = void 0;
+{
+  didWarnUpdateInsideUpdate = false;
+  currentlyProcessingQueue = null;
+  resetCurrentlyProcessingQueue = function() {
+    currentlyProcessingQueue = null;
+  };
+}
 
-  // Clear marks immediately to avoid growing buffer.
-  performance.clearMarks(formattedMarkName);
-  performance.clearMeasures(formattedLabel);
-};
+function createUpdateQueue(baseState) {
+  var queue = {
+    expirationTime: NoWork,
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+  return queue;
+}
 
-var getFiberMarkName = function(label, debugID) {
-  return label + " (#" + debugID + ")";
-};
+function cloneUpdateQueue(currentQueue) {
+  var queue = {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
 
-var getFiberLabel = function(componentName, isMounted, phase) {
-  if (phase === null) {
-    // These are composite component total time measurements.
-    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
-  } else {
-    // Composite component methods.
-    return componentName + "." + phase;
-  }
-};
+    // TODO: With resuming, if we bail out and resuse the child tree, we should
+    // keep these effects.
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
 
-var beginFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
+    firstEffect: null,
+    lastEffect: null,
 
-  if (isCommitting && labelsInCurrentCommit.has(label)) {
-    // During the commit phase, we don't show duplicate labels because
-    // there is a fixed overhead for every measurement, and we don't
-    // want to stretch the commit phase beyond necessary.
-    return false;
-  }
-  labelsInCurrentCommit.add(label);
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+  return queue;
+}
 
-  var markName = getFiberMarkName(label, debugID);
-  beginMark(markName);
-  return true;
-};
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
 
-var clearFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  clearMark(markName);
-};
+    tag: UpdateState,
+    payload: null,
+    callback: null,
 
-var endFiberMark = function(fiber, phase, warning$$1) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  endMark(label, markName, warning$$1);
-};
+    next: null,
+    nextEffect: null
+  };
+}
 
-var shouldIgnoreFiber = function(fiber) {
-  // Host components should be skipped in the timeline.
-  // We could check typeof fiber.type, but does this work with RN?
-  switch (fiber.tag) {
-    case HostRoot:
-    case HostComponent:
-    case HostText:
-    case HostPortal:
-    case CallComponent:
-    case ReturnComponent:
-    case Fragment:
-    case ContextProvider:
-    case ContextConsumer:
-    case Mode:
-      return true;
-    default:
-      return false;
+function appendUpdateToQueue(queue, update, expirationTime) {
+  // Append the update to the end of the list.
+  if (queue.lastUpdate === null) {
+    // Queue is empty
+    queue.firstUpdate = queue.lastUpdate = update;
+  } else {
+    queue.lastUpdate.next = update;
+    queue.lastUpdate = update;
   }
-};
-
-var clearPendingPhaseMeasurement = function() {
-  if (currentPhase !== null && currentPhaseFiber !== null) {
-    clearFiberMark(currentPhaseFiber, currentPhase);
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > expirationTime
+  ) {
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    queue.expirationTime = expirationTime;
   }
-  currentPhaseFiber = null;
-  currentPhase = null;
-  hasScheduledUpdateInCurrentPhase = false;
-};
+}
 
-var pauseTimers = function() {
-  // Stops all currently active measurements so that they can be resumed
-  // if we continue in a later deferred loop from the same unit of work.
-  var fiber = currentFiber;
-  while (fiber) {
-    if (fiber._debugIsCurrentlyTiming) {
-      endFiberMark(fiber, null, null);
+function enqueueUpdate(fiber, update, expirationTime) {
+  // Update queues are created lazily.
+  var alternate = fiber.alternate;
+  var queue1 = void 0;
+  var queue2 = void 0;
+  if (alternate === null) {
+    // There's only one fiber.
+    queue1 = fiber.updateQueue;
+    queue2 = null;
+    if (queue1 === null) {
+      queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
+    }
+  } else {
+    // There are two owners.
+    queue1 = fiber.updateQueue;
+    queue2 = alternate.updateQueue;
+    if (queue1 === null) {
+      if (queue2 === null) {
+        // Neither fiber has an update queue. Create new ones.
+        queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
+        queue2 = alternate.updateQueue = createUpdateQueue(
+          alternate.memoizedState
+        );
+      } else {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue1 = fiber.updateQueue = cloneUpdateQueue(queue2);
+      }
+    } else {
+      if (queue2 === null) {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue2 = alternate.updateQueue = cloneUpdateQueue(queue1);
+      } else {
+        // Both owners have an update queue.
+      }
     }
-    fiber = fiber["return"];
-  }
-};
-
-var resumeTimersRecursively = function(fiber) {
-  if (fiber["return"] !== null) {
-    resumeTimersRecursively(fiber["return"]);
-  }
-  if (fiber._debugIsCurrentlyTiming) {
-    beginFiberMark(fiber, null);
-  }
-};
-
-var resumeTimers = function() {
-  // Resumes all measurements that were active during the last deferred loop.
-  if (currentFiber !== null) {
-    resumeTimersRecursively(currentFiber);
   }
-};
-
-function recordEffect() {
-  if (enableUserTimingAPI) {
-    effectCountInCurrentCommit++;
+  if (queue2 === null || queue1 === queue2) {
+    // There's only a single queue.
+    appendUpdateToQueue(queue1, update, expirationTime);
+  } else {
+    // There are two queues. We need to append the update to both queues,
+    // while accounting for the persistent structure of the list — we don't
+    // want the same update to be added multiple times.
+    if (queue1.lastUpdate === null || queue2.lastUpdate === null) {
+      // One of the queues is not empty. We must add the update to both queues.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      appendUpdateToQueue(queue2, update, expirationTime);
+    } else {
+      // Both queues are non-empty. The last update is the same in both lists,
+      // because of structural sharing. So, only append to one of the lists.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      // But we still need to update the `lastUpdate` pointer of queue2.
+      queue2.lastUpdate = update;
+    }
   }
-}
 
-function recordScheduleUpdate() {
-  if (enableUserTimingAPI) {
-    if (isCommitting) {
-      hasScheduledUpdateInCurrentCommit = true;
-    }
+  {
     if (
-      currentPhase !== null &&
-      currentPhase !== "componentWillMount" &&
-      currentPhase !== "componentWillReceiveProps"
+      fiber.tag === ClassComponent &&
+      (currentlyProcessingQueue === queue1 ||
+        (queue2 !== null && currentlyProcessingQueue === queue2)) &&
+      !didWarnUpdateInsideUpdate
     ) {
-      hasScheduledUpdateInCurrentPhase = true;
+      warning(
+        false,
+        "An update (setState, replaceState, or forceUpdate) was scheduled " +
+          "from inside an update function. Update functions should be pure, " +
+          "with zero side-effects. Consider using componentDidUpdate or a " +
+          "callback."
+      );
+      didWarnUpdateInsideUpdate = true;
     }
   }
 }
 
-function startRequestCallbackTimer() {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming && !isWaitingForCallback) {
-      isWaitingForCallback = true;
-      beginMark("(Waiting for async callback...)");
-    }
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  // Captured updates go into a separate list, and only on the work-in-
+  // progress queue.
+  var workInProgressQueue = workInProgress.updateQueue;
+  if (workInProgressQueue === null) {
+    workInProgressQueue = workInProgress.updateQueue = createUpdateQueue(
+      workInProgress.memoizedState
+    );
+  } else {
+    // TODO: I put this here rather than createWorkInProgress so that we don't
+    // clone the queue unnecessarily. There's probably a better way to
+    // structure this.
+    workInProgressQueue = ensureWorkInProgressQueueIsAClone(
+      workInProgress,
+      workInProgressQueue
+    );
+  }
+
+  // Append the update to the end of the list.
+  if (workInProgressQueue.lastCapturedUpdate === null) {
+    // This is the first render phase update
+    workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update;
+  } else {
+    workInProgressQueue.lastCapturedUpdate.next = update;
+    workInProgressQueue.lastCapturedUpdate = update;
+  }
+  if (
+    workInProgressQueue.expirationTime === NoWork ||
+    workInProgressQueue.expirationTime > renderExpirationTime
+  ) {
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    workInProgressQueue.expirationTime = renderExpirationTime;
   }
 }
 
-function stopRequestCallbackTimer(didExpire, expirationTime) {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming) {
-      isWaitingForCallback = false;
-      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
-      endMark(
-        "(Waiting for async callback... will force flush in " +
-          expirationTime +
-          " ms)",
-        "(Waiting for async callback...)",
-        warning$$1
-      );
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  if (current !== null) {
+    // If the work-in-progress queue is equal to the current queue,
+    // we need to clone it first.
+    if (queue === current.updateQueue) {
+      queue = workInProgress.updateQueue = cloneUpdateQueue(queue);
     }
   }
+  return queue;
 }
 
-function startWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, this is the fiber to unwind from.
-    currentFiber = fiber;
-    if (!beginFiberMark(fiber, null)) {
-      return;
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case ReplaceState: {
+      var _payload = update.payload;
+      if (typeof _payload === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload.call(instance, prevState, nextProps);
+          }
+        }
+        return _payload.call(instance, prevState, nextProps);
+      }
+      // State object
+      return _payload;
     }
-    fiber._debugIsCurrentlyTiming = true;
-  }
-}
-
-function cancelWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
+    case CaptureUpdate: {
+      workInProgress.effectTag =
+        (workInProgress.effectTag & ~ShouldCapture) | DidCapture;
     }
-    // Remember we shouldn't complete measurement for this fiber.
-    // Otherwise flamechart will be deep even for small updates.
-    fiber._debugIsCurrentlyTiming = false;
-    clearFiberMark(fiber, null);
-  }
-}
-
-function stopWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
+    // Intentional fallthrough
+    case UpdateState: {
+      var _payload2 = update.payload;
+      var partialState = void 0;
+      if (typeof _payload2 === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload2.call(instance, prevState, nextProps);
+          }
+        }
+        partialState = _payload2.call(instance, prevState, nextProps);
+      } else {
+        // Partial state object
+        partialState = _payload2;
+      }
+      if (partialState === null || partialState === undefined) {
+        // Null and undefined are treated as no-ops.
+        return prevState;
+      }
+      // Merge the partial state and the previous state.
+      return Object.assign({}, prevState, partialState);
     }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
+    case ForceUpdate: {
+      hasForceUpdate = true;
+      return prevState;
     }
-    fiber._debugIsCurrentlyTiming = false;
-    endFiberMark(fiber, null, null);
   }
+  return prevState;
 }
 
-function stopFailedWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
-    }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber["return"];
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
-    }
-    fiber._debugIsCurrentlyTiming = false;
-    var warning$$1 = "An error was thrown inside this error boundary";
-    endFiberMark(fiber, null, warning$$1);
-  }
-}
+function processUpdateQueue(
+  workInProgress,
+  queue,
+  props,
+  instance,
+  renderExpirationTime
+) {
+  hasForceUpdate = false;
 
-function startPhaseTimer(fiber, phase) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    clearPendingPhaseMeasurement();
-    if (!beginFiberMark(fiber, phase)) {
-      return;
-    }
-    currentPhaseFiber = fiber;
-    currentPhase = phase;
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > renderExpirationTime
+  ) {
+    // Insufficient priority. Bailout.
+    return;
   }
-}
 
-function stopPhaseTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    if (currentPhase !== null && currentPhaseFiber !== null) {
-      var warning$$1 = hasScheduledUpdateInCurrentPhase
-        ? "Scheduled a cascading update"
-        : null;
-      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
-    }
-    currentPhase = null;
-    currentPhaseFiber = null;
+  queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+
+  {
+    currentlyProcessingQueue = queue;
   }
-}
 
-function startWorkLoopTimer(nextUnitOfWork) {
-  if (enableUserTimingAPI) {
-    currentFiber = nextUnitOfWork;
-    if (!supportsUserTiming) {
-      return;
+  // These values may change as we process the queue.
+  var newBaseState = queue.baseState;
+  var newFirstUpdate = null;
+  var newExpirationTime = NoWork;
+
+  // Iterate through the list of updates to compute the result.
+  var update = queue.firstUpdate;
+  var resultState = newBaseState;
+  while (update !== null) {
+    var updateExpirationTime = update.expirationTime;
+    if (updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      if (newFirstUpdate === null) {
+        // This is the first skipped update. It will be the first update in
+        // the new list.
+        newFirstUpdate = update;
+        // Since this is the first update that was skipped, the current result
+        // is the new base state.
+        newBaseState = resultState;
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
+      if (
+        newExpirationTime === NoWork ||
+        newExpirationTime > updateExpirationTime
+      ) {
+        newExpirationTime = updateExpirationTime;
+      }
+    } else {
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback = update.callback;
+      if (_callback !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastEffect === null) {
+          queue.firstEffect = queue.lastEffect = update;
+        } else {
+          queue.lastEffect.nextEffect = update;
+          queue.lastEffect = update;
+        }
+      }
     }
-    commitCountInCurrentWorkLoop = 0;
-    // This is top level call.
-    // Any other measurements are performed within.
-    beginMark("(React Tree Reconciliation)");
-    // Resume any measurements that were in progress during the last loop.
-    resumeTimers();
+    // Continue to the next update.
+    update = update.next;
   }
-}
 
-function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var warning$$1 = null;
-    if (interruptedBy !== null) {
-      if (interruptedBy.tag === HostRoot) {
-        warning$$1 = "A top-level update interrupted the previous render";
-      } else {
-        var componentName = getComponentName(interruptedBy) || "Unknown";
-        warning$$1 =
-          "An update to " + componentName + " interrupted the previous render";
+  // Separately, iterate though the list of captured updates.
+  var newFirstCapturedUpdate = null;
+  update = queue.firstCapturedUpdate;
+  while (update !== null) {
+    var _updateExpirationTime = update.expirationTime;
+    if (_updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      if (newFirstCapturedUpdate === null) {
+        // This is the first skipped captured update. It will be the first
+        // update in the new list.
+        newFirstCapturedUpdate = update;
+        // If this is the first update that was skipped, the current result is
+        // the new base state.
+        if (newFirstUpdate === null) {
+          newBaseState = resultState;
+        }
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
+      if (
+        newExpirationTime === NoWork ||
+        newExpirationTime > _updateExpirationTime
+      ) {
+        newExpirationTime = _updateExpirationTime;
+      }
+    } else {
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback2 = update.callback;
+      if (_callback2 !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastCapturedEffect === null) {
+          queue.firstCapturedEffect = queue.lastCapturedEffect = update;
+        } else {
+          queue.lastCapturedEffect.nextEffect = update;
+          queue.lastCapturedEffect = update;
+        }
       }
-    } else if (commitCountInCurrentWorkLoop > 1) {
-      warning$$1 = "There were cascading updates";
     }
-    commitCountInCurrentWorkLoop = 0;
-    var label = didCompleteRoot
-      ? "(React Tree Reconciliation: Completed Root)"
-      : "(React Tree Reconciliation: Yielded)";
-    // Pause any measurements until the next loop.
-    pauseTimers();
-    endMark(label, "(React Tree Reconciliation)", warning$$1);
+    update = update.next;
   }
-}
 
-function startCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    isCommitting = true;
-    hasScheduledUpdateInCurrentCommit = false;
-    labelsInCurrentCommit.clear();
-    beginMark("(Committing Changes)");
+  if (newFirstUpdate === null) {
+    queue.lastUpdate = null;
+  }
+  if (newFirstCapturedUpdate === null) {
+    queue.lastCapturedUpdate = null;
+  } else {
+    workInProgress.effectTag |= Callback;
+  }
+  if (newFirstUpdate === null && newFirstCapturedUpdate === null) {
+    // We processed every update, without skipping. That means the new base
+    // state is the same as the result state.
+    newBaseState = resultState;
   }
-}
 
-function stopCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
+  queue.baseState = newBaseState;
+  queue.firstUpdate = newFirstUpdate;
+  queue.firstCapturedUpdate = newFirstCapturedUpdate;
+  queue.expirationTime = newExpirationTime;
 
-    var warning$$1 = null;
-    if (hasScheduledUpdateInCurrentCommit) {
-      warning$$1 = "Lifecycle hook scheduled a cascading update";
-    } else if (commitCountInCurrentWorkLoop > 0) {
-      warning$$1 = "Caused by a cascading update in earlier commit";
-    }
-    hasScheduledUpdateInCurrentCommit = false;
-    commitCountInCurrentWorkLoop++;
-    isCommitting = false;
-    labelsInCurrentCommit.clear();
+  workInProgress.memoizedState = resultState;
 
-    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
+  {
+    currentlyProcessingQueue = null;
   }
 }
 
-function startCommitSnapshotEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Snapshot Effects)");
-  }
+function callCallback(callback, context) {
+  invariant(
+    typeof callback === "function",
+    "Invalid argument passed as callback. Expected a function. Instead " +
+      "received: %s",
+    callback
+  );
+  callback.call(context);
 }
 
-function stopCommitSnapshotEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Snapshot Effects: " + count + " Total)",
-      "(Committing Snapshot Effects)",
-      null
-    );
-  }
+function resetHasForceUpdateBeforeProcessing() {
+  hasForceUpdate = false;
 }
 
-function startCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
+function checkHasForceUpdateAfterProcessing() {
+  return hasForceUpdate;
+}
+
+function commitUpdateQueue(
+  finishedWork,
+  finishedQueue,
+  instance,
+  renderExpirationTime
+) {
+  // If the finished render included captured updates, and there are still
+  // lower priority updates left over, we need to keep the captured updates
+  // in the queue so that they are rebased and not dropped once we process the
+  // queue again at the lower priority.
+  if (finishedQueue.firstCapturedUpdate !== null) {
+    // Join the captured update list to the end of the normal list.
+    if (finishedQueue.lastUpdate !== null) {
+      finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate;
+      finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate;
     }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Host Effects)");
+    // Clear the list of captured updates.
+    finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null;
   }
-}
 
-function stopCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
+  // Commit the effects
+  var effect = finishedQueue.firstEffect;
+  finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+  while (effect !== null) {
+    var _callback3 = effect.callback;
+    if (_callback3 !== null) {
+      effect.callback = null;
+      callCallback(_callback3, instance);
     }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Host Effects: " + count + " Total)",
-      "(Committing Host Effects)",
-      null
-    );
+    effect = effect.nextEffect;
   }
-}
 
-function startCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
+  effect = finishedQueue.firstCapturedEffect;
+  finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+  while (effect !== null) {
+    var _callback4 = effect.callback;
+    if (_callback4 !== null) {
+      effect.callback = null;
+      callCallback(_callback4, instance);
     }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Calling Lifecycle Methods)");
-  }
-}
-
-function stopCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Calling Lifecycle Methods: " + count + " Total)",
-      "(Calling Lifecycle Methods)",
-      null
-    );
-  }
-}
-
-var didWarnUpdateInsideUpdate = void 0;
-
-{
-  didWarnUpdateInsideUpdate = false;
-}
-
-// Callbacks are not validated until invocation
-
-// Singly linked-list of updates. When an update is scheduled, it is added to
-// the queue of the current fiber and the work-in-progress fiber. The two queues
-// are separate but they share a persistent structure.
-//
-// During reconciliation, updates are removed from the work-in-progress fiber,
-// but they remain on the current fiber. That ensures that if a work-in-progress
-// is aborted, the aborted updates are recovered by cloning from current.
-//
-// The work-in-progress queue is always a subset of the current queue.
-//
-// When the tree is committed, the work-in-progress becomes the current.
-
-function createUpdateQueue(baseState) {
-  var queue = {
-    baseState: baseState,
-    expirationTime: NoWork,
-    first: null,
-    last: null,
-    callbackList: null,
-    hasForceUpdate: false,
-    isInitialized: false,
-    capturedValues: null
-  };
-  {
-    queue.isProcessing = false;
-  }
-  return queue;
-}
-
-function insertUpdateIntoQueue(queue, update) {
-  // Append the update to the end of the list.
-  if (queue.last === null) {
-    // Queue is empty
-    queue.first = queue.last = update;
-  } else {
-    queue.last.next = update;
-    queue.last = update;
-  }
-  if (
-    queue.expirationTime === NoWork ||
-    queue.expirationTime > update.expirationTime
-  ) {
-    queue.expirationTime = update.expirationTime;
-  }
-}
-
-var q1 = void 0;
-var q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  // We'll have at least one and at most two distinct update queues.
-  var alternateFiber = fiber.alternate;
-  var queue1 = fiber.updateQueue;
-  if (queue1 === null) {
-    // TODO: We don't know what the base state will be until we begin work.
-    // It depends on which fiber is the next current. Initialize with an empty
-    // base state, then set to the memoizedState when rendering. Not super
-    // happy with this approach.
-    queue1 = fiber.updateQueue = createUpdateQueue(null);
-  }
-
-  var queue2 = void 0;
-  if (alternateFiber !== null) {
-    queue2 = alternateFiber.updateQueue;
-    if (queue2 === null) {
-      queue2 = alternateFiber.updateQueue = createUpdateQueue(null);
-    }
-  } else {
-    queue2 = null;
-  }
-  queue2 = queue2 !== queue1 ? queue2 : null;
-
-  // Use module variables instead of returning a tuple
-  q1 = queue1;
-  q2 = queue2;
-}
-
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  var queue1 = q1;
-  var queue2 = q2;
-
-  // Warn if an update is scheduled from inside an updater function.
-  {
-    if (
-      (queue1.isProcessing || (queue2 !== null && queue2.isProcessing)) &&
-      !didWarnUpdateInsideUpdate
-    ) {
-      warning(
-        false,
-        "An update (setState, replaceState, or forceUpdate) was scheduled " +
-          "from inside an update function. Update functions should be pure, " +
-          "with zero side-effects. Consider using componentDidUpdate or a " +
-          "callback."
-      );
-      didWarnUpdateInsideUpdate = true;
-    }
-  }
-
-  // If there's only one queue, add the update to that queue and exit.
-  if (queue2 === null) {
-    insertUpdateIntoQueue(queue1, update);
-    return;
-  }
-
-  // If either queue is empty, we need to add to both queues.
-  if (queue1.last === null || queue2.last === null) {
-    insertUpdateIntoQueue(queue1, update);
-    insertUpdateIntoQueue(queue2, update);
-    return;
-  }
-
-  // If both lists are not empty, the last update is the same for both lists
-  // because of structural sharing. So, we should only append to one of
-  // the lists.
-  insertUpdateIntoQueue(queue1, update);
-  // But we still need to update the `last` pointer of queue2.
-  queue2.last = update;
-}
-
-function getUpdateExpirationTime(fiber) {
-  switch (fiber.tag) {
-    case HostRoot:
-    case ClassComponent:
-      var updateQueue = fiber.updateQueue;
-      if (updateQueue === null) {
-        return NoWork;
-      }
-      return updateQueue.expirationTime;
-    default:
-      return NoWork;
-  }
-}
-
-function getStateFromUpdate(update, instance, prevState, props) {
-  var partialState = update.partialState;
-  if (typeof partialState === "function") {
-    return partialState.call(instance, prevState, props);
-  } else {
-    return partialState;
-  }
-}
-
-function processUpdateQueue(
-  current,
-  workInProgress,
-  queue,
-  instance,
-  props,
-  renderExpirationTime
-) {
-  if (current !== null && current.updateQueue === queue) {
-    // We need to create a work-in-progress queue, by cloning the current queue.
-    var currentQueue = queue;
-    queue = workInProgress.updateQueue = {
-      baseState: currentQueue.baseState,
-      expirationTime: currentQueue.expirationTime,
-      first: currentQueue.first,
-      last: currentQueue.last,
-      isInitialized: currentQueue.isInitialized,
-      capturedValues: currentQueue.capturedValues,
-      // These fields are no longer valid because they were already committed.
-      // Reset them.
-      callbackList: null,
-      hasForceUpdate: false
-    };
-  }
-
-  {
-    // Set this flag so we can warn if setState is called inside the update
-    // function of another setState.
-    queue.isProcessing = true;
-  }
-
-  // Reset the remaining expiration time. If we skip over any updates, we'll
-  // increase this accordingly.
-  queue.expirationTime = NoWork;
-
-  // TODO: We don't know what the base state will be until we begin work.
-  // It depends on which fiber is the next current. Initialize with an empty
-  // base state, then set to the memoizedState when rendering. Not super
-  // happy with this approach.
-  var state = void 0;
-  if (queue.isInitialized) {
-    state = queue.baseState;
-  } else {
-    state = queue.baseState = workInProgress.memoizedState;
-    queue.isInitialized = true;
-  }
-  var dontMutatePrevState = true;
-  var update = queue.first;
-  var didSkip = false;
-  while (update !== null) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      // This update does not have sufficient priority. Skip it.
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        remainingExpirationTime === NoWork ||
-        remainingExpirationTime > updateExpirationTime
-      ) {
-        // Update the remaining expiration time.
-        queue.expirationTime = updateExpirationTime;
-      }
-      if (!didSkip) {
-        didSkip = true;
-        queue.baseState = state;
-      }
-      // Continue to the next update.
-      update = update.next;
-      continue;
-    }
-
-    // This update does have sufficient priority.
-
-    // If no previous updates were skipped, drop this update from the queue by
-    // advancing the head of the list.
-    if (!didSkip) {
-      queue.first = update.next;
-      if (queue.first === null) {
-        queue.last = null;
-      }
-    }
-
-    // Invoke setState callback an extra time to help detect side-effects.
-    // Ignore the return value in this case.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      getStateFromUpdate(update, instance, state, props);
-    }
-
-    // Process the update
-    var _partialState = void 0;
-    if (update.isReplace) {
-      state = getStateFromUpdate(update, instance, state, props);
-      dontMutatePrevState = true;
-    } else {
-      _partialState = getStateFromUpdate(update, instance, state, props);
-      if (_partialState) {
-        if (dontMutatePrevState) {
-          // $FlowFixMe: Idk how to type this properly.
-          state = Object.assign({}, state, _partialState);
-        } else {
-          state = Object.assign(state, _partialState);
-        }
-        dontMutatePrevState = false;
-      }
-    }
-    if (update.isForced) {
-      queue.hasForceUpdate = true;
-    }
-    if (update.callback !== null) {
-      // Append to list of callbacks.
-      var _callbackList = queue.callbackList;
-      if (_callbackList === null) {
-        _callbackList = queue.callbackList = [];
-      }
-      _callbackList.push(update);
-    }
-    if (update.capturedValue !== null) {
-      var _capturedValues = queue.capturedValues;
-      if (_capturedValues === null) {
-        queue.capturedValues = [update.capturedValue];
-      } else {
-        _capturedValues.push(update.capturedValue);
-      }
-    }
-    update = update.next;
-  }
-
-  if (queue.callbackList !== null) {
-    workInProgress.effectTag |= Callback;
-  } else if (
-    queue.first === null &&
-    !queue.hasForceUpdate &&
-    queue.capturedValues === null
-  ) {
-    // The queue is empty. We can reset it.
-    workInProgress.updateQueue = null;
-  }
-
-  if (!didSkip) {
-    didSkip = true;
-    queue.baseState = state;
-  }
-
-  {
-    // No longer processing.
-    queue.isProcessing = false;
-  }
-
-  return state;
-}
-
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (callbackList === null) {
-    return;
-  }
-  // Set the list to null to make sure they don't get called more than once.
-  queue.callbackList = null;
-  for (var i = 0; i < callbackList.length; i++) {
-    var update = callbackList[i];
-    var _callback = update.callback;
-    // This update might be processed again. Clear the callback so it's only
-    // called once.
-    update.callback = null;
-    invariant(
-      typeof _callback === "function",
-      "Invalid argument passed as callback. Expected a function. Instead " +
-        "received: %s",
-      _callback
-    );
-    _callback.call(context);
+    effect = effect.nextEffect;
   }
 }
 
@@ -5732,18 +5249,19 @@ var fakeInternalInstance = {};
 var isArray = Array.isArray;
 
 var didWarnAboutStateAssignmentForComponent = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
 var didWarnAboutUninitializedState = void 0;
 var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
 var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
+var warnOnUndefinedDerivedState = void 0;
 var warnOnInvalidCallback = void 0;
 
 {
   didWarnAboutStateAssignmentForComponent = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
   didWarnAboutUninitializedState = new Set();
   didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
   didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
 
   var didWarnOnInvalidCallback = new Set();
 
@@ -5764,6 +5282,21 @@ var warnOnInvalidCallback = void 0;
     }
   };
 
+  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
+    if (partialState === undefined) {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+        didWarnAboutUndefinedDerivedState.add(componentName);
+        warning(
+          false,
+          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+            "You have returned undefined.",
+          componentName
+        );
+      }
+    }
+  };
+
   // This is so gross but it's at least non-critical and can be removed if
   // it causes problems. This is meant to give a nicer error message for
   // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
@@ -5785,17 +5318,43 @@ var warnOnInvalidCallback = void 0;
   });
   Object.freeze(fakeInternalInstance);
 }
-function callGetDerivedStateFromCatch(ctor, capturedValues) {
-  var resultState = {};
-  for (var i = 0; i < capturedValues.length; i++) {
-    var capturedValue = capturedValues[i];
-    var error = capturedValue.value;
-    var partialState = ctor.getDerivedStateFromCatch.call(null, error);
-    if (partialState !== null && partialState !== undefined) {
-      Object.assign(resultState, partialState);
+
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+
+  {
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      // Invoke the function an extra time to help detect side-effects.
+      getDerivedStateFromProps(nextProps, prevState);
     }
   }
-  return resultState;
+
+  var partialState = getDerivedStateFromProps(nextProps, prevState);
+
+  {
+    warnOnUndefinedDerivedState(workInProgress, partialState);
+  }
+  // Merge the partial state and the previous state.
+  var memoizedState =
+    partialState === null || partialState === undefined
+      ? prevState
+      : Object.assign({}, prevState, partialState);
+  workInProgress.memoizedState = memoizedState;
+
+  // Once the update queue is empty, persist the derived state onto the
+  // base state.
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
+    updateQueue.baseState = memoizedState;
+  }
 }
 
 var ReactFiberClassComponent = function(
@@ -5803,7 +5362,8 @@ var ReactFiberClassComponent = function(
   scheduleWork,
   computeExpirationForFiber,
   memoizeProps,
-  memoizeState
+  memoizeState,
+  recalculateCurrentTime
 ) {
   var cacheContext = legacyContext.cacheContext,
     getMaskedContext = legacyContext.getMaskedContext,
@@ -5811,65 +5371,60 @@ var ReactFiberClassComponent = function(
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged;
 
-  // Class component state updater
-
-  var updater = {
+  var classComponentUpdater = {
     isMounted: isMounted,
-    enqueueSetState: function(instance, partialState, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "setState");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: partialState,
-        callback: callback,
-        isReplace: false,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+    enqueueSetState: function(inst, payload, callback) {
+      var fiber = get$1(inst);
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(currentTime, fiber);
+
+      var update = createUpdate(expirationTime);
+      update.payload = payload;
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "setState");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueReplaceState: function(instance, state, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "replaceState");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: state,
-        callback: callback,
-        isReplace: true,
-        isForced: false,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+    enqueueReplaceState: function(inst, payload, callback) {
+      var fiber = get$1(inst);
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(currentTime, fiber);
+
+      var update = createUpdate(expirationTime);
+      update.tag = ReplaceState;
+      update.payload = payload;
+
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "replaceState");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     },
-    enqueueForceUpdate: function(instance, callback) {
-      var fiber = get$1(instance);
-      callback = callback === undefined ? null : callback;
-      {
-        warnOnInvalidCallback(callback, "forceUpdate");
-      }
-      var expirationTime = computeExpirationForFiber(fiber);
-      var update = {
-        expirationTime: expirationTime,
-        partialState: null,
-        callback: callback,
-        isReplace: false,
-        isForced: true,
-        capturedValue: null,
-        next: null
-      };
-      insertUpdateIntoFiber(fiber, update);
+    enqueueForceUpdate: function(inst, callback) {
+      var fiber = get$1(inst);
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(currentTime, fiber);
+
+      var update = createUpdate(expirationTime);
+      update.tag = ForceUpdate;
+
+      if (callback !== undefined && callback !== null) {
+        {
+          warnOnInvalidCallback(callback, "forceUpdate");
+        }
+        update.callback = callback;
+      }
+
+      enqueueUpdate(fiber, update, expirationTime);
       scheduleWork(fiber, expirationTime);
     }
   };
@@ -5882,15 +5437,6 @@ var ReactFiberClassComponent = function(
     newState,
     newContext
   ) {
-    if (
-      oldProps === null ||
-      (workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate)
-    ) {
-      // If the workInProgress already has an Update effect, return true
-      return true;
-    }
-
     var instance = workInProgress.stateNode;
     var ctor = workInProgress.type;
     if (typeof instance.shouldComponentUpdate === "function") {
@@ -6144,13 +5690,8 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function resetInputPointers(workInProgress, instance) {
-    instance.props = workInProgress.memoizedProps;
-    instance.state = workInProgress.memoizedState;
-  }
-
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
+    instance.updater = classComponentUpdater;
     workInProgress.stateNode = instance;
     // The instance needs access to the fiber so that it can schedule updates
     set(instance, workInProgress);
@@ -6159,7 +5700,7 @@ var ReactFiberClassComponent = function(
     }
   }
 
-  function constructClassInstance(workInProgress, props) {
+  function constructClassInstance(workInProgress, props, renderExpirationTime) {
     var ctor = workInProgress.type;
     var unmaskedContext = getUnmaskedContext(workInProgress);
     var needsContext = isContextConsumer(workInProgress);
@@ -6168,19 +5709,21 @@ var ReactFiberClassComponent = function(
       : emptyObject;
 
     // Instantiate twice to help detect side-effects.
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      new ctor(props, context); // eslint-disable-line no-new
+    {
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        new ctor(props, context); // eslint-disable-line no-new
+      }
     }
 
     var instance = new ctor(props, context);
-    var state =
+    var state = (workInProgress.memoizedState =
       instance.state !== null && instance.state !== undefined
         ? instance.state
-        : null;
+        : null);
     adoptClassInstance(workInProgress, instance);
 
     {
@@ -6271,26 +5814,6 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    workInProgress.memoizedState = state;
-
-    var partialState = callGetDerivedStateFromProps(
-      workInProgress,
-      instance,
-      props,
-      state
-    );
-
-    if (partialState !== null && partialState !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      workInProgress.memoizedState = Object.assign(
-        {},
-        workInProgress.memoizedState,
-        partialState
-      );
-    }
-
     // Cache unmasked context so we can avoid recreating masked context unless necessary.
     // ReactFiberContext usually updates this cache but can't for newly-created instances.
     if (needsContext) {
@@ -6323,7 +5846,7 @@ var ReactFiberClassComponent = function(
           getComponentName(workInProgress) || "Component"
         );
       }
-      updater.enqueueReplaceState(instance, instance.state, null);
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
@@ -6357,57 +5880,13 @@ var ReactFiberClassComponent = function(
           );
         }
       }
-      updater.enqueueReplaceState(instance, instance.state, null);
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
     }
   }
 
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    var type = workInProgress.type;
-
-    if (typeof type.getDerivedStateFromProps === "function") {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        // Invoke method an extra time to help detect side-effects.
-        type.getDerivedStateFromProps.call(null, nextProps, prevState);
-      }
-
-      var partialState = type.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
-
-      {
-        if (partialState === undefined) {
-          var componentName = getComponentName(workInProgress) || "Component";
-          if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-            didWarnAboutUndefinedDerivedState.add(componentName);
-            warning(
-              false,
-              "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-                "You have returned undefined.",
-              componentName
-            );
-          }
-        }
-      }
-
-      return partialState;
-    }
-  }
-
-  // Invokes the mount life-cycles on a previously never rendered instance.
-  function mountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var current = workInProgress.alternate;
+  // Invokes the mount life-cycles on a previously never rendered instance.
+  function mountClassInstance(workInProgress, renderExpirationTime) {
+    var ctor = workInProgress.type;
 
     {
       checkClassInstance(workInProgress);
@@ -6438,6 +5917,28 @@ var ReactFiberClassComponent = function(
       }
     }
 
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
+        workInProgress,
+        updateQueue,
+        props,
+        instance,
+        renderExpirationTime
+      );
+      instance.state = workInProgress.memoizedState;
+    }
+
+    var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
+        workInProgress,
+        getDerivedStateFromProps,
+        props
+      );
+      instance.state = workInProgress.memoizedState;
+    }
+
     // In order to support react-lifecycles-compat polyfilled components,
     // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
@@ -6449,18 +5950,19 @@ var ReactFiberClassComponent = function(
       callComponentWillMount(workInProgress, instance);
       // If we had additional state updates during this life-cycle, let's
       // process them now.
-      var updateQueue = workInProgress.updateQueue;
+      updateQueue = workInProgress.updateQueue;
       if (updateQueue !== null) {
-        instance.state = processUpdateQueue(
-          current,
+        processUpdateQueue(
           workInProgress,
           updateQueue,
-          instance,
           props,
+          instance,
           renderExpirationTime
         );
+        instance.state = workInProgress.memoizedState;
       }
     }
+
     if (typeof instance.componentDidMount === "function") {
       workInProgress.effectTag |= Update;
     }
@@ -6469,16 +5971,18 @@ var ReactFiberClassComponent = function(
   function resumeMountClassInstance(workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
+    instance.props = oldProps;
+
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6502,103 +6006,26 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Compute the next state using the memoized state and the update queue.
+    resetHasForceUpdateBeforeProcessing();
+
     var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        null,
+    var newState = (instance.state = oldState);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
         workInProgress,
-        workInProgress.updateQueue,
-        instance,
+        updateQueue,
         newProps,
-        renderExpirationTime
-      );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
-    }
-
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
         instance,
-        newProps,
-        newState
+        renderExpirationTime
       );
+      newState = workInProgress.memoizedState;
     }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue = workInProgress.updateQueue;
-      if (_updateQueue !== null) {
-        _updateQueue.baseState = Object.assign(
-          {},
-          _updateQueue.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue2 = workInProgress.updateQueue;
-      if (_updateQueue2 !== null) {
-        _updateQueue2.baseState = Object.assign(
-          {},
-          _updateQueue2.baseState,
-          derivedStateFromCatch
-        );
-      }
-    }
-
     if (
       oldProps === newProps &&
       oldState === newState &&
       !hasContextChanged() &&
-      !(
-        workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate
-      )
+      !checkHasForceUpdateAfterProcessing()
     ) {
       // If an update was already in progress, we should schedule an Update
       // effect even though we're bailing out, so that cWU/cDU are called.
@@ -6608,14 +6035,25 @@ var ReactFiberClassComponent = function(
       return false;
     }
 
-    var shouldUpdate = checkShouldComponentUpdate(
-      workInProgress,
-      oldProps,
-      newProps,
-      oldState,
-      newState,
-      newContext
-    );
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
+        workInProgress,
+        getDerivedStateFromProps,
+        newProps
+      );
+      newState = workInProgress.memoizedState;
+    }
+
+    var shouldUpdate =
+      checkHasForceUpdateAfterProcessing() ||
+      checkShouldComponentUpdate(
+        workInProgress,
+        oldProps,
+        newProps,
+        oldState,
+        newState,
+        newContext
+      );
 
     if (shouldUpdate) {
       // In order to support react-lifecycles-compat polyfilled components,
@@ -6645,9 +6083,9 @@ var ReactFiberClassComponent = function(
       }
 
       // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
+      // memoized state to indicate that this work can be reused.
+      workInProgress.memoizedProps = newProps;
+      workInProgress.memoizedState = newState;
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6663,16 +6101,18 @@ var ReactFiberClassComponent = function(
   function updateClassInstance(current, workInProgress, renderExpirationTime) {
     var ctor = workInProgress.type;
     var instance = workInProgress.stateNode;
-    resetInputPointers(workInProgress, instance);
 
     var oldProps = workInProgress.memoizedProps;
     var newProps = workInProgress.pendingProps;
+    instance.props = oldProps;
+
     var oldContext = instance.context;
     var newUnmaskedContext = getUnmaskedContext(workInProgress);
     var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
+    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
     var hasNewLifecycles =
-      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof getDerivedStateFromProps === "function" ||
       typeof instance.getSnapshotBeforeUpdate === "function";
 
     // Note: During these life-cycles, instance.props/instance.state are what
@@ -6696,104 +6136,27 @@ var ReactFiberClassComponent = function(
       }
     }
 
-    // Compute the next state using the memoized state and the update queue.
-    var oldState = workInProgress.memoizedState;
-    // TODO: Previous state can be null.
-    var newState = void 0;
-    var derivedStateFromCatch = void 0;
+    resetHasForceUpdateBeforeProcessing();
 
-    if (workInProgress.updateQueue !== null) {
-      newState = processUpdateQueue(
-        current,
+    var oldState = workInProgress.memoizedState;
+    var newState = (instance.state = oldState);
+    var updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
         workInProgress,
-        workInProgress.updateQueue,
-        instance,
+        updateQueue,
         newProps,
-        renderExpirationTime
-      );
-
-      var updateQueue = workInProgress.updateQueue;
-      if (
-        updateQueue !== null &&
-        updateQueue.capturedValues !== null &&
-        enableGetDerivedStateFromCatch &&
-        typeof ctor.getDerivedStateFromCatch === "function"
-      ) {
-        var capturedValues = updateQueue.capturedValues;
-        // Don't remove these from the update queue yet. We need them in
-        // finishClassComponent. Do the reset there.
-        // TODO: This is awkward. Refactor class components.
-        // updateQueue.capturedValues = null;
-        derivedStateFromCatch = callGetDerivedStateFromCatch(
-          ctor,
-          capturedValues
-        );
-      }
-    } else {
-      newState = oldState;
-    }
-
-    var derivedStateFromProps = void 0;
-    if (oldProps !== newProps) {
-      // The prevState parameter should be the partially updated state.
-      // Otherwise, spreading state in return values could override updates.
-      derivedStateFromProps = callGetDerivedStateFromProps(
-        workInProgress,
         instance,
-        newProps,
-        newState
+        renderExpirationTime
       );
-    }
-
-    if (derivedStateFromProps !== null && derivedStateFromProps !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromProps
-          : Object.assign({}, newState, derivedStateFromProps);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue3 = workInProgress.updateQueue;
-      if (_updateQueue3 !== null) {
-        _updateQueue3.baseState = Object.assign(
-          {},
-          _updateQueue3.baseState,
-          derivedStateFromProps
-        );
-      }
-    }
-    if (derivedStateFromCatch !== null && derivedStateFromCatch !== undefined) {
-      // Render-phase updates (like this) should not be added to the update queue,
-      // So that multiple render passes do not enqueue multiple updates.
-      // Instead, just synchronously merge the returned state into the instance.
-      newState =
-        newState === null || newState === undefined
-          ? derivedStateFromCatch
-          : Object.assign({}, newState, derivedStateFromCatch);
-
-      // Update the base state of the update queue.
-      // FIXME: This is getting ridiculous. Refactor plz!
-      var _updateQueue4 = workInProgress.updateQueue;
-      if (_updateQueue4 !== null) {
-        _updateQueue4.baseState = Object.assign(
-          {},
-          _updateQueue4.baseState,
-          derivedStateFromCatch
-        );
-      }
+      newState = workInProgress.memoizedState;
     }
 
     if (
       oldProps === newProps &&
       oldState === newState &&
       !hasContextChanged() &&
-      !(
-        workInProgress.updateQueue !== null &&
-        workInProgress.updateQueue.hasForceUpdate
-      )
+      !checkHasForceUpdateAfterProcessing()
     ) {
       // If an update was already in progress, we should schedule an Update
       // effect even though we're bailing out, so that cWU/cDU are called.
@@ -6816,14 +6179,27 @@ var ReactFiberClassComponent = function(
       return false;
     }
 
-    var shouldUpdate = checkShouldComponentUpdate(
-      workInProgress,
-      oldProps,
-      newProps,
-      oldState,
-      newState,
-      newContext
-    );
+    if (typeof getDerivedStateFromProps === "function") {
+      if (fireGetDerivedStateFromPropsOnStateUpdates || oldProps !== newProps) {
+        applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        );
+        newState = workInProgress.memoizedState;
+      }
+    }
+
+    var shouldUpdate =
+      checkHasForceUpdateAfterProcessing() ||
+      checkShouldComponentUpdate(
+        workInProgress,
+        oldProps,
+        newProps,
+        oldState,
+        newState,
+        newContext
+      );
 
     if (shouldUpdate) {
       // In order to support react-lifecycles-compat polyfilled components,
@@ -6870,8 +6246,8 @@ var ReactFiberClassComponent = function(
 
       // If shouldComponentUpdate returned false, we should still update the
       // memoized props/state to indicate that this work can be reused.
-      memoizeProps(workInProgress, newProps);
-      memoizeState(workInProgress, newState);
+      workInProgress.memoizedProps = newProps;
+      workInProgress.memoizedState = newState;
     }
 
     // Update the existing instance's state, props, and context pointers even
@@ -6885,7 +6261,6 @@ var ReactFiberClassComponent = function(
 
   return {
     adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: constructClassInstance,
     mountClassInstance: mountClassInstance,
     resumeMountClassInstance: resumeMountClassInstance,
@@ -6893,7 +6268,7 @@ var ReactFiberClassComponent = function(
   };
 };
 
-var getCurrentFiberStackAddendum$1 =
+var getCurrentFiberStackAddendum$2 =
   ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
 
 var didWarnAboutMaps = void 0;
@@ -6932,7 +6307,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
       '"key" prop. See https://fb.me/react-warning-keys for ' +
       "more information." +
-      (getCurrentFiberStackAddendum$1() || "");
+      (getCurrentFiberStackAddendum$2() || "");
     if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
       return;
     }
@@ -6943,7 +6318,7 @@ var warnForMissingKey = function(child) {};
       "Each child in an array or iterator should have a unique " +
         '"key" prop. See https://fb.me/react-warning-keys for ' +
         "more information.%s",
-      getCurrentFiberStackAddendum$1()
+      getCurrentFiberStackAddendum$2()
     );
   };
 }
@@ -7040,7 +6415,7 @@ function throwOnInvalidObjectType(returnFiber, newChild) {
       addendum =
         " If you meant to render a collection of children, use an array " +
         "instead." +
-        (getCurrentFiberStackAddendum$1() || "");
+        (getCurrentFiberStackAddendum$2() || "");
     }
     invariant(
       false,
@@ -7058,7 +6433,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
     "you return a Component instead of <Component /> from render. " +
     "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$1() || "");
+    (getCurrentFiberStackAddendum$2() || "");
 
   if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
     return;
@@ -7070,7 +6445,7 @@ function warnOnFunctionType() {
     "Functions are not valid as a React child. This may happen if " +
       "you return a Component instead of <Component /> from render. " +
       "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$1() || ""
+    getCurrentFiberStackAddendum$2() || ""
   );
 }
 
@@ -7183,12 +6558,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, textContent, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -7198,7 +6573,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // Move based on index
       var existing = useFiber(current, element.props, expirationTime);
       existing.ref = coerceRef(returnFiber, current, element);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       {
         existing._debugSource = element._source;
         existing._debugOwner = element._owner;
@@ -7212,7 +6587,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       created.ref = coerceRef(returnFiber, current, element);
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     }
   }
@@ -7230,12 +6605,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, portal.children || [], expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -7249,12 +6624,12 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         key
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       // Update
       var existing = useFiber(current, fragment, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
   }
@@ -7269,7 +6644,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         returnFiber.mode,
         expirationTime
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     }
 
@@ -7282,7 +6657,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           _created.ref = coerceRef(returnFiber, null, newChild);
-          _created["return"] = returnFiber;
+          _created.return = returnFiber;
           return _created;
         }
         case REACT_PORTAL_TYPE: {
@@ -7291,7 +6666,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             returnFiber.mode,
             expirationTime
           );
-          _created2["return"] = returnFiber;
+          _created2.return = returnFiber;
           return _created2;
         }
       }
@@ -7303,7 +6678,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           null
         );
-        _created3["return"] = returnFiber;
+        _created3.return = returnFiber;
         return _created3;
       }
 
@@ -7514,7 +6889,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               "duplicated and/or omitted — the behavior is unsupported and " +
               "could change in a future version.%s",
             key,
-            getCurrentFiberStackAddendum$1()
+            getCurrentFiberStackAddendum$2()
           );
           break;
         default:
@@ -7659,7 +7034,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren["delete"](
+            existingChildren.delete(
               _newFiber2.key === null ? newIdx : _newFiber2.key
             );
           }
@@ -7712,7 +7087,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                 "Using Maps as children is unsupported and will likely yield " +
                   "unexpected results. Convert it to a sequence/iterable of keyed " +
                   "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$1()
+                getCurrentFiberStackAddendum$2()
               )
             : void 0;
           didWarnAboutMaps = true;
@@ -7838,7 +7213,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             // current, that means that we reused the fiber. We need to delete
             // it from the child list so that we don't add it to the deletion
             // list.
-            existingChildren["delete"](
+            existingChildren.delete(
               _newFiber4.key === null ? newIdx : _newFiber4.key
             );
           }
@@ -7877,7 +7252,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       // the rest.
       deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
       var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing["return"] = returnFiber;
+      existing.return = returnFiber;
       return existing;
     }
     // The existing first child is not a text node so we need to create one
@@ -7888,7 +7263,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created["return"] = returnFiber;
+    created.return = returnFiber;
     return created;
   }
 
@@ -7918,7 +7293,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime
           );
           existing.ref = coerceRef(returnFiber, child, element);
-          existing["return"] = returnFiber;
+          existing.return = returnFiber;
           {
             existing._debugSource = element._source;
             existing._debugOwner = element._owner;
@@ -7941,7 +7316,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime,
         element.key
       );
-      created["return"] = returnFiber;
+      created.return = returnFiber;
       return created;
     } else {
       var _created4 = createFiberFromElement(
@@ -7950,7 +7325,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
       _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4["return"] = returnFiber;
+      _created4.return = returnFiber;
       return _created4;
     }
   }
@@ -7974,7 +7349,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         ) {
           deleteRemainingChildren(returnFiber, child.sibling);
           var existing = useFiber(child, portal.children || [], expirationTime);
-          existing["return"] = returnFiber;
+          existing.return = returnFiber;
           return existing;
         } else {
           deleteRemainingChildren(returnFiber, child);
@@ -7991,7 +7366,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       returnFiber.mode,
       expirationTime
     );
-    created["return"] = returnFiber;
+    created.return = returnFiber;
     return created;
   }
 
@@ -8143,7 +7518,7 @@ function cloneChildFibers(current, workInProgress) {
   );
   workInProgress.child = newChild;
 
-  newChild["return"] = workInProgress;
+  newChild.return = workInProgress;
   while (currentChild.sibling !== null) {
     currentChild = currentChild.sibling;
     newChild = newChild.sibling = createWorkInProgress(
@@ -8151,11 +7526,14 @@ function cloneChildFibers(current, workInProgress) {
       currentChild.pendingProps,
       currentChild.expirationTime
     );
-    newChild["return"] = workInProgress;
+    newChild.return = workInProgress;
   }
   newChild.sibling = null;
 }
 
+var getCurrentFiberStackAddendum =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+
 var didWarnAboutBadClass = void 0;
 var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
 var didWarnAboutStatelessRefs = void 0;
@@ -8173,13 +7551,19 @@ var ReactFiberBeginWork = function(
   newContext,
   hydrationContext,
   scheduleWork,
-  computeExpirationForFiber
+  computeExpirationForFiber,
+  profilerTimer,
+  recalculateCurrentTime
 ) {
   var shouldSetTextContent = config.shouldSetTextContent,
     shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
   var pushHostContext = hostContext.pushHostContext,
     pushHostContainer = hostContext.pushHostContainer;
-  var pushProvider = newContext.pushProvider;
+  var pushProvider = newContext.pushProvider,
+    getContextCurrentValue = newContext.getContextCurrentValue,
+    getContextChangedBits = newContext.getContextChangedBits;
+  var markActualRenderTimeStarted = profilerTimer.markActualRenderTimeStarted,
+    stopBaseRenderTimerIfRunning = profilerTimer.stopBaseRenderTimerIfRunning;
   var getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     hasLegacyContextChanged = legacyContext.hasContextChanged,
@@ -8196,11 +7580,10 @@ var ReactFiberBeginWork = function(
       scheduleWork,
       computeExpirationForFiber,
       memoizeProps,
-      memoizeState
+      memoizeState,
+      recalculateCurrentTime
     ),
     adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
-    callGetDerivedStateFromProps =
-      _ReactFiberClassCompo.callGetDerivedStateFromProps,
     constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
     mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
     resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
@@ -8252,9 +7635,28 @@ var ReactFiberBeginWork = function(
 
   function updateForwardRef(current, workInProgress) {
     var render = workInProgress.type.render;
-    var nextChildren = render(workInProgress.pendingProps, workInProgress.ref);
+    var nextProps = workInProgress.pendingProps;
+    var ref = workInProgress.ref;
+    if (hasLegacyContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (workInProgress.memoizedProps === nextProps) {
+      var currentRef = current !== null ? current.ref : null;
+      if (ref === currentRef) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+    }
+
+    var nextChildren = void 0;
+    {
+      ReactCurrentOwner.current = workInProgress;
+      ReactDebugCurrentFiber.setCurrentPhase("render");
+      nextChildren = render(nextProps, ref);
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+
     reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
     return workInProgress.child;
   }
 
@@ -8287,6 +7689,25 @@ var ReactFiberBeginWork = function(
     return workInProgress.child;
   }
 
+  function updateProfiler(current, workInProgress) {
+    var nextProps = workInProgress.pendingProps;
+    if (enableProfilerTimer) {
+      // Start render timer here and push start time onto queue
+      markActualRenderTimeStarted(workInProgress);
+
+      // Let the "complete" phase know to stop the timer,
+      // And the scheduler to record the measured time.
+      workInProgress.effectTag |= Update;
+    }
+    if (workInProgress.memoizedProps === nextProps) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    var nextChildren = nextProps.children;
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextProps);
+    return workInProgress.child;
+  }
+
   function markRef(current, workInProgress) {
     var ref = workInProgress.ref;
     if (
@@ -8340,7 +7761,11 @@ var ReactFiberBeginWork = function(
     if (current === null) {
       if (workInProgress.stateNode === null) {
         // In the initial pass we might need to construct the instance.
-        constructClassInstance(workInProgress, workInProgress.pendingProps);
+        constructClassInstance(
+          workInProgress,
+          workInProgress.pendingProps,
+          renderExpirationTime
+        );
         mountClassInstance(workInProgress, renderExpirationTime);
 
         shouldUpdate = true;
@@ -8358,22 +7783,11 @@ var ReactFiberBeginWork = function(
         renderExpirationTime
       );
     }
-
-    // We processed the update queue inside updateClassInstance. It may have
-    // included some errors that were dispatched during the commit phase.
-    // TODO: Refactor class components so this is less awkward.
-    var didCaptureError = false;
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null && updateQueue.capturedValues !== null) {
-      shouldUpdate = true;
-      didCaptureError = true;
-    }
     return finishClassComponent(
       current,
       workInProgress,
       shouldUpdate,
       hasContext,
-      didCaptureError,
       renderExpirationTime
     );
   }
@@ -8383,12 +7797,13 @@ var ReactFiberBeginWork = function(
     workInProgress,
     shouldUpdate,
     hasContext,
-    didCaptureError,
     renderExpirationTime
   ) {
     // Refs should update even if shouldComponentUpdate returns false
     markRef(current, workInProgress);
 
+    var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
+
     if (!shouldUpdate && !didCaptureError) {
       // Context providers should defer to sCU for rendering
       if (hasContext) {
@@ -8415,6 +7830,10 @@ var ReactFiberBeginWork = function(
       // the new API.
       // TODO: Warn in a future release.
       nextChildren = null;
+
+      if (enableProfilerTimer) {
+        stopBaseRenderTimerIfRunning();
+      }
     } else {
       {
         ReactDebugCurrentFiber.setCurrentPhase("render");
@@ -8484,29 +7903,26 @@ var ReactFiberBeginWork = function(
     pushHostRootContext(workInProgress);
     var updateQueue = workInProgress.updateQueue;
     if (updateQueue !== null) {
+      var nextProps = workInProgress.pendingProps;
       var prevState = workInProgress.memoizedState;
-      var state = processUpdateQueue(
-        current,
+      var prevChildren = prevState !== null ? prevState.element : null;
+      processUpdateQueue(
         workInProgress,
         updateQueue,
-        null,
+        nextProps,
         null,
         renderExpirationTime
       );
-      memoizeState(workInProgress, state);
-      updateQueue = workInProgress.updateQueue;
+      var nextState = workInProgress.memoizedState;
+      // Caution: React DevTools currently depends on this property
+      // being called "element".
+      var nextChildren = nextState.element;
 
-      var element = void 0;
-      if (updateQueue !== null && updateQueue.capturedValues !== null) {
-        // There's an uncaught error. Unmount the whole root.
-        element = null;
-      } else if (prevState === state) {
+      if (nextChildren === prevChildren) {
         // If the state is the same as before, that's a bailout because we had
         // no work that expires at this time.
         resetHydrationState();
         return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      } else {
-        element = state.element;
       }
       var root = workInProgress.stateNode;
       if (
@@ -8531,16 +7947,15 @@ var ReactFiberBeginWork = function(
         workInProgress.child = mountChildFibers(
           workInProgress,
           null,
-          element,
+          nextChildren,
           renderExpirationTime
         );
       } else {
         // Otherwise reset hydration state in case we aborted and resumed another
         // root.
         resetHydrationState();
-        reconcileChildren(current, workInProgress, element);
+        reconcileChildren(current, workInProgress, nextChildren);
       }
-      memoizeState(workInProgress, state);
       return workInProgress.child;
     }
     resetHydrationState();
@@ -8676,21 +8091,13 @@ var ReactFiberBeginWork = function(
       workInProgress.memoizedState =
         value.state !== null && value.state !== undefined ? value.state : null;
 
-      if (typeof Component.getDerivedStateFromProps === "function") {
-        var partialState = callGetDerivedStateFromProps(
+      var getDerivedStateFromProps = Component.getDerivedStateFromProps;
+      if (typeof getDerivedStateFromProps === "function") {
+        applyDerivedStateFromProps(
           workInProgress,
-          value,
-          props,
-          workInProgress.memoizedState
+          getDerivedStateFromProps,
+          props
         );
-
-        if (partialState !== null && partialState !== undefined) {
-          workInProgress.memoizedState = Object.assign(
-            {},
-            workInProgress.memoizedState,
-            partialState
-          );
-        }
       }
 
       // Push context providers early to prevent context stack mismatches.
@@ -8704,7 +8111,6 @@ var ReactFiberBeginWork = function(
         workInProgress,
         true,
         hasContext,
-        false,
         renderExpirationTime
       );
     } else {
@@ -8807,6 +8213,41 @@ var ReactFiberBeginWork = function(
     return workInProgress.stateNode;
   }
 
+  function updateTimeoutComponent(
+    current,
+    workInProgress,
+    renderExpirationTime
+  ) {
+    if (enableSuspense) {
+      var nextProps = workInProgress.pendingProps;
+      var prevProps = workInProgress.memoizedProps;
+
+      var prevDidTimeout = workInProgress.memoizedState;
+
+      // Check if we already attempted to render the normal state. If we did,
+      // and we timed out, render the placeholder state.
+      var alreadyCaptured =
+        (workInProgress.effectTag & DidCapture) === NoEffect;
+      var nextDidTimeout = !alreadyCaptured;
+
+      if (hasLegacyContextChanged()) {
+        // Normally we can bail out on props equality but if context has changed
+        // we don't do the bailout and we have to reuse existing props instead.
+      } else if (nextProps === prevProps && nextDidTimeout === prevDidTimeout) {
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+
+      var render = nextProps.children;
+      var nextChildren = render(nextDidTimeout);
+      workInProgress.memoizedProps = nextProps;
+      workInProgress.memoizedState = nextDidTimeout;
+      reconcileChildren(current, workInProgress, nextChildren);
+      return workInProgress.child;
+    } else {
+      return null;
+    }
+  }
+
   function updatePortalComponent(
     current,
     workInProgress,
@@ -8850,7 +8291,7 @@ var ReactFiberBeginWork = function(
     var fiber = workInProgress.child;
     if (fiber !== null) {
       // Set the return pointer of the child to the work-in-progress fiber.
-      fiber["return"] = workInProgress;
+      fiber.return = workInProgress;
     }
     while (fiber !== null) {
       var nextFiber = void 0;
@@ -8888,7 +8329,7 @@ var ReactFiberBeginWork = function(
                 // ancestor path already has sufficient priority.
                 break;
               }
-              node = node["return"];
+              node = node.return;
             }
             // Don't scan deeper than a matching consumer. When we render the
             // consumer, we'll continue scanning from that point. This way the
@@ -8910,7 +8351,7 @@ var ReactFiberBeginWork = function(
       }
       if (nextFiber !== null) {
         // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber["return"] = fiber;
+        nextFiber.return = fiber;
       } else {
         // No child. Traverse to next sibling.
         nextFiber = fiber;
@@ -8922,11 +8363,13 @@ var ReactFiberBeginWork = function(
           }
           var sibling = nextFiber.sibling;
           if (sibling !== null) {
+            // Set the return pointer of the sibling to the work-in-progress fiber.
+            sibling.return = nextFiber.return;
             nextFiber = sibling;
             break;
           }
           // No more siblings. Traverse up.
-          nextFiber = nextFiber["return"];
+          nextFiber = nextFiber.return;
         }
       }
       fiber = nextFiber;
@@ -8943,8 +8386,10 @@ var ReactFiberBeginWork = function(
 
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
+    var canBailOnProps = true;
 
     if (hasLegacyContextChanged()) {
+      canBailOnProps = false;
       // Normally we can bail out on props equality but if context has changed
       // we don't do the bailout and we have to reuse existing props instead.
     } else if (oldProps === newProps) {
@@ -8956,6 +8401,20 @@ var ReactFiberBeginWork = function(
     var newValue = newProps.value;
     workInProgress.memoizedProps = newProps;
 
+    {
+      var providerPropTypes = workInProgress.type.propTypes;
+
+      if (providerPropTypes) {
+        checkPropTypes(
+          providerPropTypes,
+          newProps,
+          "prop",
+          "Context.Provider",
+          getCurrentFiberStackAddendum
+        );
+      }
+    }
+
     var changedBits = void 0;
     if (oldProps === null) {
       // Initial render
@@ -8963,7 +8422,7 @@ var ReactFiberBeginWork = function(
     } else {
       if (oldProps.value === newProps.value) {
         // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children) {
+        if (oldProps.children === newProps.children && canBailOnProps) {
           workInProgress.stateNode = 0;
           pushProvider(workInProgress);
           return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -8980,7 +8439,7 @@ var ReactFiberBeginWork = function(
           (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
         ) {
           // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children) {
+          if (oldProps.children === newProps.children && canBailOnProps) {
             workInProgress.stateNode = 0;
             pushProvider(workInProgress);
             return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -9005,7 +8464,7 @@ var ReactFiberBeginWork = function(
 
           if (changedBits === 0) {
             // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children) {
+            if (oldProps.children === newProps.children && canBailOnProps) {
               workInProgress.stateNode = 0;
               pushProvider(workInProgress);
               return bailoutOnAlreadyFinishedWork(current, workInProgress);
@@ -9039,8 +8498,8 @@ var ReactFiberBeginWork = function(
     var newProps = workInProgress.pendingProps;
     var oldProps = workInProgress.memoizedProps;
 
-    var newValue = context._currentValue;
-    var changedBits = context._changedBits;
+    var newValue = getContextCurrentValue(context);
+    var changedBits = getContextChangedBits(context);
 
     if (hasLegacyContextChanged()) {
       // Normally we can bail out on props equality but if context has changed
@@ -9090,7 +8549,16 @@ var ReactFiberBeginWork = function(
         : void 0;
     }
 
-    var newChildren = render(newValue);
+    var newChildren = void 0;
+    {
+      ReactCurrentOwner.current = workInProgress;
+      ReactDebugCurrentFiber.setCurrentPhase("render");
+      newChildren = render(newValue);
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+
+    // React DevTools reads this flag.
+    workInProgress.effectTag |= PerformedWork;
     reconcileChildren(current, workInProgress, newChildren);
     return workInProgress.child;
   }
@@ -9117,6 +8585,11 @@ var ReactFiberBeginWork = function(
   function bailoutOnAlreadyFinishedWork(current, workInProgress) {
     cancelWorkTimer(workInProgress);
 
+    if (enableProfilerTimer) {
+      // Don't update "base" render times for bailouts.
+      stopBaseRenderTimerIfRunning();
+    }
+
     // TODO: We should ideally be able to bail out early if the children have no
     // more work to do. However, since we don't have a separation of this
     // Fiber's priority and its children yet - we don't know without doing lots
@@ -9138,6 +8611,11 @@ var ReactFiberBeginWork = function(
   function bailoutOnLowPriority(current, workInProgress) {
     cancelWorkTimer(workInProgress);
 
+    if (enableProfilerTimer) {
+      // Don't update "base" render times for bailouts.
+      stopBaseRenderTimerIfRunning();
+    }
+
     // TODO: Handle HostComponent tags here as well and call pushHostContext()?
     // See PR 8590 discussion for context
     switch (workInProgress.tag) {
@@ -9156,6 +8634,11 @@ var ReactFiberBeginWork = function(
       case ContextProvider:
         pushProvider(workInProgress);
         break;
+      case Profiler:
+        if (enableProfilerTimer) {
+          markActualRenderTimeStarted(workInProgress);
+        }
+        break;
     }
     // TODO: What if this is currently in progress?
     // How can that happen? How is this not being cloned?
@@ -9220,6 +8703,12 @@ var ReactFiberBeginWork = function(
         // A return component is just a placeholder, we can just run through the
         // next one immediately.
         return null;
+      case TimeoutComponent:
+        return updateTimeoutComponent(
+          current,
+          workInProgress,
+          renderExpirationTime
+        );
       case HostPortal:
         return updatePortalComponent(
           current,
@@ -9232,6 +8721,8 @@ var ReactFiberBeginWork = function(
         return updateFragment(current, workInProgress);
       case Mode:
         return updateMode(current, workInProgress);
+      case Profiler:
+        return updateProfiler(current, workInProgress);
       case ContextProvider:
         return updateContextProvider(
           current,
@@ -9263,7 +8754,8 @@ var ReactFiberCompleteWork = function(
   hostContext,
   legacyContext,
   newContext,
-  hydrationContext
+  hydrationContext,
+  profilerTimer
 ) {
   var createInstance = config.createInstance,
     createTextInstance = config.createTextInstance,
@@ -9276,6 +8768,8 @@ var ReactFiberCompleteWork = function(
     popHostContext = hostContext.popHostContext,
     getHostContext = hostContext.getHostContext,
     popHostContainer = hostContext.popHostContainer;
+  var recordElapsedActualRenderTime =
+    profilerTimer.recordElapsedActualRenderTime;
   var popLegacyContextProvider = legacyContext.popContextProvider,
     popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
   var popProvider = newContext.popProvider;
@@ -9298,7 +8792,7 @@ var ReactFiberCompleteWork = function(
   function appendAllReturns(returns, workInProgress) {
     var node = workInProgress.stateNode;
     if (node) {
-      node["return"] = workInProgress;
+      node.return = workInProgress;
     }
     while (node !== null) {
       if (
@@ -9310,17 +8804,17 @@ var ReactFiberCompleteWork = function(
       } else if (node.tag === ReturnComponent) {
         returns.push(node.pendingProps.value);
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -9376,7 +8870,7 @@ var ReactFiberCompleteWork = function(
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
@@ -9384,12 +8878,12 @@ var ReactFiberCompleteWork = function(
         return;
       }
       while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === workInProgress) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
-        node = node["return"];
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -9456,7 +8950,7 @@ var ReactFiberCompleteWork = function(
             // down its children. Instead, we'll get insertions from each child in
             // the portal directly.
           } else if (node.child !== null) {
-            node.child["return"] = node;
+            node.child.return = node;
             node = node.child;
             continue;
           }
@@ -9464,12 +8958,12 @@ var ReactFiberCompleteWork = function(
             return;
           }
           while (node.sibling === null) {
-            if (node["return"] === null || node["return"] === workInProgress) {
+            if (node.return === null || node.return === workInProgress) {
               return;
             }
-            node = node["return"];
+            node = node.return;
           }
-          node.sibling["return"] = node["return"];
+          node.sibling.return = node.return;
           node = node.sibling;
         }
       };
@@ -9595,20 +9089,6 @@ var ReactFiberCompleteWork = function(
       case ClassComponent: {
         // We are leaving this subtree, so pop context if any.
         popLegacyContextProvider(workInProgress);
-
-        // If this component caught an error, schedule an error log effect.
-        var instance = workInProgress.stateNode;
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null && updateQueue.capturedValues !== null) {
-          workInProgress.effectTag &= ~DidCapture;
-          if (typeof instance.componentDidCatch === "function") {
-            workInProgress.effectTag |= ErrLog;
-          } else {
-            // Normally we clear this in the commit phase, but since we did not
-            // schedule an effect, we need to reset it here.
-            updateQueue.capturedValues = null;
-          }
-        }
         return null;
       }
       case HostRoot: {
@@ -9628,11 +9108,6 @@ var ReactFiberCompleteWork = function(
           workInProgress.effectTag &= ~Placement;
         }
         updateHostContainer(workInProgress);
-
-        var _updateQueue = workInProgress.updateQueue;
-        if (_updateQueue !== null && _updateQueue.capturedValues !== null) {
-          workInProgress.effectTag |= ErrLog;
-        }
         return null;
       }
       case HostComponent: {
@@ -9647,13 +9122,13 @@ var ReactFiberCompleteWork = function(
           // have newProps so we'll have to reuse them.
           // TODO: Split the update API as separate for the props vs. children.
           // Even better would be if children weren't special cased at all tho.
-          var _instance = workInProgress.stateNode;
+          var instance = workInProgress.stateNode;
           var currentHostContext = getHostContext();
           // TODO: Experiencing an error where oldProps is null. Suggests a host
           // component is hitting the resume path. Figure out why. Possibly
           // related to `hidden`.
           var updatePayload = prepareUpdate(
-            _instance,
+            instance,
             type,
             oldProps,
             newProps,
@@ -9707,7 +9182,7 @@ var ReactFiberCompleteWork = function(
               markUpdate(workInProgress);
             }
           } else {
-            var _instance2 = createInstance(
+            var _instance = createInstance(
               type,
               newProps,
               rootContainerInstance,
@@ -9715,14 +9190,14 @@ var ReactFiberCompleteWork = function(
               workInProgress
             );
 
-            appendAllChildren(_instance2, workInProgress);
+            appendAllChildren(_instance, workInProgress);
 
             // Certain renderers require commit-time effects for initial mount.
             // (eg DOM renderer supports auto-focus for certain elements).
             // Make sure such renderers get scheduled for later work.
             if (
               finalizeInitialChildren(
-                _instance2,
+                _instance,
                 type,
                 newProps,
                 rootContainerInstance,
@@ -9731,7 +9206,7 @@ var ReactFiberCompleteWork = function(
             ) {
               markUpdate(workInProgress);
             }
-            workInProgress.stateNode = _instance2;
+            workInProgress.stateNode = _instance;
           }
 
           if (workInProgress.ref !== null) {
@@ -9791,10 +9266,17 @@ var ReactFiberCompleteWork = function(
         return null;
       case ForwardRef:
         return null;
+      case TimeoutComponent:
+        return null;
       case Fragment:
         return null;
       case Mode:
         return null;
+      case Profiler:
+        if (enableProfilerTimer) {
+          recordElapsedActualRenderTime(workInProgress);
+        }
+        return null;
       case HostPortal:
         popHostContainer(workInProgress);
         updateHostContainer(workInProgress);
@@ -9808,71 +9290,1161 @@ var ReactFiberCompleteWork = function(
       // Error cases
       case IndeterminateComponent:
         invariant(
-          false,
-          "An indeterminate component should have become determinate before " +
-            "completing. This error is likely caused by a bug in React. Please " +
-            "file an issue."
+          false,
+          "An indeterminate component should have become determinate before " +
+            "completing. This error is likely caused by a bug in React. Please " +
+            "file an issue."
+        );
+      // eslint-disable-next-line no-fallthrough
+      default:
+        invariant(
+          false,
+          "Unknown unit of work tag. This error is likely caused by a bug in " +
+            "React. Please file an issue."
+        );
+    }
+  }
+
+  return {
+    completeWork: completeWork
+  };
+};
+
+function createCapturedValue(value, source) {
+  // If the value is an error, call this function immediately after it is thrown
+  // so the stack is accurate.
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
+
+// Module provided by RN:
+/**
+ * Intercept lifecycle errors and ensure they are shown with the correct stack
+ * trace within the native redbox component.
+ */
+function showErrorDialog(capturedError) {
+  var componentStack = capturedError.componentStack,
+    error = capturedError.error;
+
+  var errorToHandle = void 0;
+
+  // Typically Errors are thrown but eg strings or null can be thrown as well.
+  if (error instanceof Error) {
+    var message = error.message,
+      name = error.name;
+
+    var summary = message ? name + ": " + message : name;
+
+    errorToHandle = error;
+
+    try {
+      errorToHandle.message =
+        summary + "\n\nThis error is located at:" + componentStack;
+    } catch (e) {}
+  } else if (typeof error === "string") {
+    errorToHandle = new Error(
+      error + "\n\nThis error is located at:" + componentStack
+    );
+  } else {
+    errorToHandle = new Error("Unspecified error at:" + componentStack);
+  }
+
+  ExceptionsManager.handleException(errorToHandle, false);
+
+  // Return false here to prevent ReactFiberErrorLogger default behavior of
+  // logging error details to console.error. Calls to console.error are
+  // automatically routed to the native redbox controller, which we've already
+  // done above by calling ExceptionsManager.
+  return false;
+}
+
+function logCapturedError(capturedError) {
+  var logError = showErrorDialog(capturedError);
+
+  // Allow injected showErrorDialog() to prevent default console.error logging.
+  // This enables renderers like ReactNative to better manage redbox behavior.
+  if (logError === false) {
+    return;
+  }
+
+  var error = capturedError.error;
+  var suppressLogging = error && error.suppressReactErrorLogging;
+  if (suppressLogging) {
+    return;
+  }
+
+  {
+    var componentName = capturedError.componentName,
+      componentStack = capturedError.componentStack,
+      errorBoundaryName = capturedError.errorBoundaryName,
+      errorBoundaryFound = capturedError.errorBoundaryFound,
+      willRetry = capturedError.willRetry;
+
+    var componentNameMessage = componentName
+      ? "The above error occurred in the <" + componentName + "> component:"
+      : "The above error occurred in one of your React components:";
+
+    var errorBoundaryMessage = void 0;
+    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
+    if (errorBoundaryFound && errorBoundaryName) {
+      if (willRetry) {
+        errorBoundaryMessage =
+          "React will try to recreate this component tree from scratch " +
+          ("using the error boundary you provided, " + errorBoundaryName + ".");
+      } else {
+        errorBoundaryMessage =
+          "This error was initially handled by the error boundary " +
+          errorBoundaryName +
+          ".\n" +
+          "Recreating the tree from scratch failed so React will unmount the tree.";
+      }
+    } else {
+      errorBoundaryMessage =
+        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
+        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
+    }
+    var combinedMessage =
+      "" +
+      componentNameMessage +
+      componentStack +
+      "\n\n" +
+      ("" + errorBoundaryMessage);
+
+    // In development, we provide our own message with just the component stack.
+    // We don't include the original error message and JS stack because the browser
+    // has already printed it. Even if the application swallows the error, it is still
+    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
+    console.error(combinedMessage);
+  }
+}
+
+var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
+var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
+
+var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
+{
+  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
+}
+
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source;
+  var stack = errorInfo.stack;
+  if (stack === null) {
+    stack = getStackAddendumByWorkInProgressFiber(source);
+  }
+
+  var capturedError = {
+    componentName: source !== null ? getComponentName(source) : null,
+    componentStack: stack !== null ? stack : "",
+    error: errorInfo.value,
+    errorBoundary: null,
+    errorBoundaryName: null,
+    errorBoundaryFound: false,
+    willRetry: false
+  };
+
+  if (boundary !== null && boundary.tag === ClassComponent) {
+    capturedError.errorBoundary = boundary.stateNode;
+    capturedError.errorBoundaryName = getComponentName(boundary);
+    capturedError.errorBoundaryFound = true;
+    capturedError.willRetry = true;
+  }
+
+  try {
+    logCapturedError(capturedError);
+  } catch (e) {
+    // Prevent cycle if logCapturedError() throws.
+    // A cycle may still occur if logCapturedError renders a component that throws.
+    var suppressLogging = e && e.suppressReactErrorLogging;
+    if (!suppressLogging) {
+      console.error(e);
+    }
+  }
+}
+
+var ReactFiberCommitWork = function(
+  config,
+  captureError,
+  scheduleWork,
+  computeExpirationForFiber,
+  markLegacyErrorBoundaryAsFailed,
+  recalculateCurrentTime
+) {
+  var getPublicInstance = config.getPublicInstance,
+    mutation = config.mutation,
+    persistence = config.persistence;
+
+  var callComponentWillUnmountWithTimer = function(current, instance) {
+    startPhaseTimer(current, "componentWillUnmount");
+    instance.props = current.memoizedProps;
+    instance.state = current.memoizedState;
+    instance.componentWillUnmount();
+    stopPhaseTimer();
+  };
+
+  // Capture errors so they don't interrupt unmounting.
+  function safelyCallComponentWillUnmount(current, instance) {
+    {
+      invokeGuardedCallback$3(
+        null,
+        callComponentWillUnmountWithTimer,
+        null,
+        current,
+        instance
+      );
+      if (hasCaughtError$1()) {
+        var unmountError = clearCaughtError$1();
+        captureError(current, unmountError);
+      }
+    }
+  }
+
+  function safelyDetachRef(current) {
+    var ref = current.ref;
+    if (ref !== null) {
+      if (typeof ref === "function") {
+        {
+          invokeGuardedCallback$3(null, ref, null, null);
+          if (hasCaughtError$1()) {
+            var refError = clearCaughtError$1();
+            captureError(current, refError);
+          }
+        }
+      } else {
+        ref.current = null;
+      }
+    }
+  }
+
+  function commitBeforeMutationLifeCycles(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        if (finishedWork.effectTag & Snapshot) {
+          if (current !== null) {
+            var prevProps = current.memoizedProps;
+            var prevState = current.memoizedState;
+            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
+            var _instance = finishedWork.stateNode;
+            _instance.props = finishedWork.memoizedProps;
+            _instance.state = finishedWork.memoizedState;
+            var snapshot = _instance.getSnapshotBeforeUpdate(
+              prevProps,
+              prevState
+            );
+            {
+              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
+              if (
+                snapshot === undefined &&
+                !didWarnSet.has(finishedWork.type)
+              ) {
+                didWarnSet.add(finishedWork.type);
+                warning(
+                  false,
+                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
+                    "must be returned. You have returned undefined.",
+                  getComponentName(finishedWork)
+                );
+              }
+            }
+            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+            stopPhaseTimer();
+          }
+        }
+        return;
+      }
+      case HostRoot:
+      case HostComponent:
+      case HostText:
+      case HostPortal:
+        // Nothing to do for these component types
+        return;
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
+  function commitLifeCycles(
+    finishedRoot,
+    current,
+    finishedWork,
+    currentTime,
+    committedExpirationTime
+  ) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        var _instance2 = finishedWork.stateNode;
+        if (finishedWork.effectTag & Update) {
+          if (current === null) {
+            startPhaseTimer(finishedWork, "componentDidMount");
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidMount();
+            stopPhaseTimer();
+          } else {
+            var prevProps = current.memoizedProps;
+            var prevState = current.memoizedState;
+            startPhaseTimer(finishedWork, "componentDidUpdate");
+            _instance2.props = finishedWork.memoizedProps;
+            _instance2.state = finishedWork.memoizedState;
+            _instance2.componentDidUpdate(
+              prevProps,
+              prevState,
+              _instance2.__reactInternalSnapshotBeforeUpdate
+            );
+            stopPhaseTimer();
+          }
+        }
+        var updateQueue = finishedWork.updateQueue;
+        if (updateQueue !== null) {
+          _instance2.props = finishedWork.memoizedProps;
+          _instance2.state = finishedWork.memoizedState;
+          commitUpdateQueue(
+            finishedWork,
+            updateQueue,
+            _instance2,
+            committedExpirationTime
+          );
+        }
+        return;
+      }
+      case HostRoot: {
+        var _updateQueue = finishedWork.updateQueue;
+        if (_updateQueue !== null) {
+          var _instance3 = null;
+          if (finishedWork.child !== null) {
+            switch (finishedWork.child.tag) {
+              case HostComponent:
+                _instance3 = getPublicInstance(finishedWork.child.stateNode);
+                break;
+              case ClassComponent:
+                _instance3 = finishedWork.child.stateNode;
+                break;
+            }
+          }
+          commitUpdateQueue(
+            finishedWork,
+            _updateQueue,
+            _instance3,
+            committedExpirationTime
+          );
+        }
+        return;
+      }
+      case HostComponent: {
+        var _instance4 = finishedWork.stateNode;
+
+        // Renderers may schedule work to be done after host components are mounted
+        // (eg DOM renderer may schedule auto-focus for inputs and form controls).
+        // These effects should only be committed when components are first mounted,
+        // aka when there is no current/alternate.
+        if (current === null && finishedWork.effectTag & Update) {
+          var type = finishedWork.type;
+          var props = finishedWork.memoizedProps;
+          commitMount(_instance4, type, props, finishedWork);
+        }
+
+        return;
+      }
+      case HostText: {
+        // We have no life-cycles associated with text.
+        return;
+      }
+      case HostPortal: {
+        // We have no life-cycles associated with portals.
+        return;
+      }
+      case Profiler: {
+        // We have no life-cycles associated with Profiler.
+        return;
+      }
+      case TimeoutComponent: {
+        // We have no life-cycles associated with Timeouts.
+        return;
+      }
+      default: {
+        invariant(
+          false,
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
+        );
+      }
+    }
+  }
+
+  function commitAttachRef(finishedWork) {
+    var ref = finishedWork.ref;
+    if (ref !== null) {
+      var _instance5 = finishedWork.stateNode;
+      var instanceToUse = void 0;
+      switch (finishedWork.tag) {
+        case HostComponent:
+          instanceToUse = getPublicInstance(_instance5);
+          break;
+        default:
+          instanceToUse = _instance5;
+      }
+      if (typeof ref === "function") {
+        ref(instanceToUse);
+      } else {
+        {
+          if (!ref.hasOwnProperty("current")) {
+            warning(
+              false,
+              "Unexpected ref object provided for %s. " +
+                "Use either a ref-setter function or React.createRef().%s",
+              getComponentName(finishedWork),
+              getStackAddendumByWorkInProgressFiber(finishedWork)
+            );
+          }
+        }
+
+        ref.current = instanceToUse;
+      }
+    }
+  }
+
+  function commitDetachRef(current) {
+    var currentRef = current.ref;
+    if (currentRef !== null) {
+      if (typeof currentRef === "function") {
+        currentRef(null);
+      } else {
+        currentRef.current = null;
+      }
+    }
+  }
+
+  // User-originating errors (lifecycles and refs) should not interrupt
+  // deletion, so don't let them throw. Host-originating errors should
+  // interrupt deletion, so it's okay
+  function commitUnmount(current) {
+    if (typeof onCommitUnmount === "function") {
+      onCommitUnmount(current);
+    }
+
+    switch (current.tag) {
+      case ClassComponent: {
+        safelyDetachRef(current);
+        var _instance6 = current.stateNode;
+        if (typeof _instance6.componentWillUnmount === "function") {
+          safelyCallComponentWillUnmount(current, _instance6);
+        }
+        return;
+      }
+      case HostComponent: {
+        safelyDetachRef(current);
+        return;
+      }
+      case CallComponent: {
+        commitNestedUnmounts(current.stateNode);
+        return;
+      }
+      case HostPortal: {
+        // TODO: this is recursive.
+        // We are also not using this parent because
+        // the portal will get pushed immediately.
+        if (enableMutatingReconciler && mutation) {
+          unmountHostComponents(current);
+        } else if (enablePersistentReconciler && persistence) {
+          emptyPortalContainer(current);
+        }
+        return;
+      }
+    }
+  }
+
+  function commitNestedUnmounts(root) {
+    // While we're inside a removed host node we don't want to call
+    // removeChild on the inner nodes because they're removed by the top
+    // call anyway. We also want to call componentWillUnmount on all
+    // composites before this host node is removed from the tree. Therefore
+    var node = root;
+    while (true) {
+      commitUnmount(node);
+      // Visit children because they may contain more composite or host nodes.
+      // Skip portals because commitUnmount() currently visits them recursively.
+      if (
+        node.child !== null &&
+        // If we use mutation we drill down into portals using commitUnmount above.
+        // If we don't use mutation we drill down into portals here instead.
+        (!mutation || node.tag !== HostPortal)
+      ) {
+        node.child.return = node;
+        node = node.child;
+        continue;
+      }
+      if (node === root) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node.return === null || node.return === root) {
+          return;
+        }
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+
+  function detachFiber(current) {
+    // Cut off the return pointers to disconnect it from the tree. Ideally, we
+    // should clear the child pointer of the parent alternate to let this
+    // get GC:ed but we don't know which for sure which parent is the current
+    // one so we'll settle for GC:ing the subtree of this child. This child
+    // itself will be GC:ed when the parent updates the next time.
+    current.return = null;
+    current.child = null;
+    if (current.alternate) {
+      current.alternate.child = null;
+      current.alternate.return = null;
+    }
+  }
+
+  var emptyPortalContainer = void 0;
+
+  if (!mutation) {
+    var commitContainer = void 0;
+    if (persistence) {
+      var replaceContainerChildren = persistence.replaceContainerChildren,
+        createContainerChildSet = persistence.createContainerChildSet;
+
+      emptyPortalContainer = function(current) {
+        var portal = current.stateNode;
+        var containerInfo = portal.containerInfo;
+
+        var emptyChildSet = createContainerChildSet(containerInfo);
+        replaceContainerChildren(containerInfo, emptyChildSet);
+      };
+      commitContainer = function(finishedWork) {
+        switch (finishedWork.tag) {
+          case ClassComponent: {
+            return;
+          }
+          case HostComponent: {
+            return;
+          }
+          case HostText: {
+            return;
+          }
+          case HostRoot:
+          case HostPortal: {
+            var portalOrRoot = finishedWork.stateNode;
+            var containerInfo = portalOrRoot.containerInfo,
+              _pendingChildren = portalOrRoot.pendingChildren;
+
+            replaceContainerChildren(containerInfo, _pendingChildren);
+            return;
+          }
+          default: {
+            invariant(
+              false,
+              "This unit of work tag should not have side-effects. This error is " +
+                "likely caused by a bug in React. Please file an issue."
+            );
+          }
+        }
+      };
+    } else {
+      commitContainer = function(finishedWork) {
+        // Noop
+      };
+    }
+    if (enablePersistentReconciler || enableNoopReconciler) {
+      return {
+        commitResetTextContent: function(finishedWork) {},
+        commitPlacement: function(finishedWork) {},
+        commitDeletion: function(current) {
+          // Detach refs and call componentWillUnmount() on the whole subtree.
+          commitNestedUnmounts(current);
+          detachFiber(current);
+        },
+        commitWork: function(current, finishedWork) {
+          commitContainer(finishedWork);
+        },
+
+        commitLifeCycles: commitLifeCycles,
+        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+        commitAttachRef: commitAttachRef,
+        commitDetachRef: commitDetachRef
+      };
+    } else if (persistence) {
+      invariant(false, "Persistent reconciler is disabled.");
+    } else {
+      invariant(false, "Noop reconciler is disabled.");
+    }
+  }
+  var commitMount = mutation.commitMount,
+    commitUpdate = mutation.commitUpdate,
+    resetTextContent = mutation.resetTextContent,
+    commitTextUpdate = mutation.commitTextUpdate,
+    appendChild = mutation.appendChild,
+    appendChildToContainer = mutation.appendChildToContainer,
+    insertBefore = mutation.insertBefore,
+    insertInContainerBefore = mutation.insertInContainerBefore,
+    removeChild = mutation.removeChild,
+    removeChildFromContainer = mutation.removeChildFromContainer;
+
+  function getHostParentFiber(fiber) {
+    var parent = fiber.return;
+    while (parent !== null) {
+      if (isHostParent(parent)) {
+        return parent;
+      }
+      parent = parent.return;
+    }
+    invariant(
+      false,
+      "Expected to find a host parent. This error is likely caused by a bug " +
+        "in React. Please file an issue."
+    );
+  }
+
+  function isHostParent(fiber) {
+    return (
+      fiber.tag === HostComponent ||
+      fiber.tag === HostRoot ||
+      fiber.tag === HostPortal
+    );
+  }
+
+  function getHostSibling(fiber) {
+    // We're going to search forward into the tree until we find a sibling host
+    // node. Unfortunately, if multiple insertions are done in a row we have to
+    // search past them. This leads to exponential search for the next sibling.
+    var node = fiber;
+    siblings: while (true) {
+      // If we didn't find anything, let's try the next sibling.
+      while (node.sibling === null) {
+        if (node.return === null || isHostParent(node.return)) {
+          // If we pop out of the root or hit the parent the fiber we are the
+          // last sibling.
+          return null;
+        }
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+      while (node.tag !== HostComponent && node.tag !== HostText) {
+        // If it is not host node and, we might have a host node inside it.
+        // Try to search down until we find one.
+        if (node.effectTag & Placement) {
+          // If we don't have a child, try the siblings instead.
+          continue siblings;
+        }
+        // If we don't have a child, try the siblings instead.
+        // We also skip portals because they are not part of this host tree.
+        if (node.child === null || node.tag === HostPortal) {
+          continue siblings;
+        } else {
+          node.child.return = node;
+          node = node.child;
+        }
+      }
+      // Check if this host node is stable or about to be placed.
+      if (!(node.effectTag & Placement)) {
+        // Found it!
+        return node.stateNode;
+      }
+    }
+  }
+
+  function commitPlacement(finishedWork) {
+    // Recursively insert all host nodes into the parent.
+    var parentFiber = getHostParentFiber(finishedWork);
+    var parent = void 0;
+    var isContainer = void 0;
+    switch (parentFiber.tag) {
+      case HostComponent:
+        parent = parentFiber.stateNode;
+        isContainer = false;
+        break;
+      case HostRoot:
+        parent = parentFiber.stateNode.containerInfo;
+        isContainer = true;
+        break;
+      case HostPortal:
+        parent = parentFiber.stateNode.containerInfo;
+        isContainer = true;
+        break;
+      default:
+        invariant(
+          false,
+          "Invalid host parent fiber. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+    }
+    if (parentFiber.effectTag & ContentReset) {
+      // Reset the text content of the parent before doing any insertions
+      resetTextContent(parent);
+      // Clear ContentReset from the effect tag
+      parentFiber.effectTag &= ~ContentReset;
+    }
+
+    var before = getHostSibling(finishedWork);
+    // We only have the top Fiber that was inserted but we need recurse down its
+    // children to find all the terminal nodes.
+    var node = finishedWork;
+    while (true) {
+      if (node.tag === HostComponent || node.tag === HostText) {
+        if (before) {
+          if (isContainer) {
+            insertInContainerBefore(parent, node.stateNode, before);
+          } else {
+            insertBefore(parent, node.stateNode, before);
+          }
+        } else {
+          if (isContainer) {
+            appendChildToContainer(parent, node.stateNode);
+          } else {
+            appendChild(parent, node.stateNode);
+          }
+        }
+      } else if (node.tag === HostPortal) {
+        // If the insertion itself is a portal, then we don't want to traverse
+        // down its children. Instead, we'll get insertions from each child in
+        // the portal directly.
+      } else if (node.child !== null) {
+        node.child.return = node;
+        node = node.child;
+        continue;
+      }
+      if (node === finishedWork) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node.return === null || node.return === finishedWork) {
+          return;
+        }
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+
+  function unmountHostComponents(current) {
+    // We only have the top Fiber that was inserted but we need recurse down its
+    var node = current;
+
+    // Each iteration, currentParent is populated with node's host parent if not
+    // currentParentIsValid.
+    var currentParentIsValid = false;
+    var currentParent = void 0;
+    var currentParentIsContainer = void 0;
+
+    while (true) {
+      if (!currentParentIsValid) {
+        var parent = node.return;
+        findParent: while (true) {
+          invariant(
+            parent !== null,
+            "Expected to find a host parent. This error is likely caused by " +
+              "a bug in React. Please file an issue."
+          );
+          switch (parent.tag) {
+            case HostComponent:
+              currentParent = parent.stateNode;
+              currentParentIsContainer = false;
+              break findParent;
+            case HostRoot:
+              currentParent = parent.stateNode.containerInfo;
+              currentParentIsContainer = true;
+              break findParent;
+            case HostPortal:
+              currentParent = parent.stateNode.containerInfo;
+              currentParentIsContainer = true;
+              break findParent;
+          }
+          parent = parent.return;
+        }
+        currentParentIsValid = true;
+      }
+
+      if (node.tag === HostComponent || node.tag === HostText) {
+        commitNestedUnmounts(node);
+        // After all the children have unmounted, it is now safe to remove the
+        // node from the tree.
+        if (currentParentIsContainer) {
+          removeChildFromContainer(currentParent, node.stateNode);
+        } else {
+          removeChild(currentParent, node.stateNode);
+        }
+        // Don't visit children because we already visited them.
+      } else if (node.tag === HostPortal) {
+        // When we go into a portal, it becomes the parent to remove from.
+        // We will reassign it back when we pop the portal on the way up.
+        currentParent = node.stateNode.containerInfo;
+        // Visit children because portals might contain host components.
+        if (node.child !== null) {
+          node.child.return = node;
+          node = node.child;
+          continue;
+        }
+      } else {
+        commitUnmount(node);
+        // Visit children because we may find more host components below.
+        if (node.child !== null) {
+          node.child.return = node;
+          node = node.child;
+          continue;
+        }
+      }
+      if (node === current) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node.return === null || node.return === current) {
+          return;
+        }
+        node = node.return;
+        if (node.tag === HostPortal) {
+          // When we go out of the portal, we need to restore the parent.
+          // Since we don't keep a stack of them, we will search for it.
+          currentParentIsValid = false;
+        }
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+
+  function commitDeletion(current) {
+    // Recursively delete all host nodes from the parent.
+    // Detach refs and call componentWillUnmount() on the whole subtree.
+    unmountHostComponents(current);
+    detachFiber(current);
+  }
+
+  function commitWork(current, finishedWork) {
+    switch (finishedWork.tag) {
+      case ClassComponent: {
+        return;
+      }
+      case HostComponent: {
+        var _instance7 = finishedWork.stateNode;
+        if (_instance7 != null) {
+          // Commit the work prepared earlier.
+          var newProps = finishedWork.memoizedProps;
+          // For hydration we reuse the update path but we treat the oldProps
+          // as the newProps. The updatePayload will contain the real change in
+          // this case.
+          var oldProps = current !== null ? current.memoizedProps : newProps;
+          var type = finishedWork.type;
+          // TODO: Type the updateQueue to be specific to host components.
+          var updatePayload = finishedWork.updateQueue;
+          finishedWork.updateQueue = null;
+          if (updatePayload !== null) {
+            commitUpdate(
+              _instance7,
+              updatePayload,
+              type,
+              oldProps,
+              newProps,
+              finishedWork
+            );
+          }
+        }
+        return;
+      }
+      case HostText: {
+        invariant(
+          finishedWork.stateNode !== null,
+          "This should have a text node initialized. This error is likely " +
+            "caused by a bug in React. Please file an issue."
         );
-      // eslint-disable-next-line no-fallthrough
-      default:
+        var textInstance = finishedWork.stateNode;
+        var newText = finishedWork.memoizedProps;
+        // For hydration we reuse the update path but we treat the oldProps
+        // as the newProps. The updatePayload will contain the real change in
+        // this case.
+        var oldText = current !== null ? current.memoizedProps : newText;
+        commitTextUpdate(textInstance, oldText, newText);
+        return;
+      }
+      case HostRoot: {
+        return;
+      }
+      case Profiler: {
+        if (enableProfilerTimer) {
+          var onRender = finishedWork.memoizedProps.onRender;
+          onRender(
+            finishedWork.memoizedProps.id,
+            current === null ? "mount" : "update",
+            finishedWork.stateNode.duration,
+            finishedWork.treeBaseTime
+          );
+
+          // Reset actualTime after successful commit.
+          // By default, we append to this time to account for errors and pauses.
+          finishedWork.stateNode.duration = 0;
+        }
+        return;
+      }
+      case TimeoutComponent: {
+        return;
+      }
+      default: {
         invariant(
           false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
+          "This unit of work tag should not have side-effects. This error is " +
+            "likely caused by a bug in React. Please file an issue."
         );
+      }
     }
   }
 
-  return {
-    completeWork: completeWork
-  };
-};
+  function commitResetTextContent(current) {
+    resetTextContent(current.stateNode);
+  }
 
-function createCapturedValue(value, source) {
-  // If the value is an error, call this function immediately after it is thrown
-  // so the stack is accurate.
-  return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
-  };
-}
+  if (enableMutatingReconciler) {
+    return {
+      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
+      commitResetTextContent: commitResetTextContent,
+      commitPlacement: commitPlacement,
+      commitDeletion: commitDeletion,
+      commitWork: commitWork,
+      commitLifeCycles: commitLifeCycles,
+      commitAttachRef: commitAttachRef,
+      commitDetachRef: commitDetachRef
+    };
+  } else {
+    invariant(false, "Mutating reconciler is disabled.");
+  }
+};
 
 var ReactFiberUnwindWork = function(
+  config,
   hostContext,
   legacyContext,
   newContext,
   scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
+  computeExpirationForFiber,
+  recalculateCurrentTime,
+  markLegacyErrorBoundaryAsFailed,
+  isAlreadyFailedLegacyErrorBoundary,
+  onUncaughtError,
+  profilerTimer,
+  suspendRoot,
+  retrySuspendedRoot
 ) {
   var popHostContainer = hostContext.popHostContainer,
     popHostContext = hostContext.popHostContext;
   var popLegacyContextProvider = legacyContext.popContextProvider,
     popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
   var popProvider = newContext.popProvider;
+  var resumeActualRenderTimerIfPaused =
+      profilerTimer.resumeActualRenderTimerIfPaused,
+    recordElapsedActualRenderTime = profilerTimer.recordElapsedActualRenderTime;
+
+  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+    var update = createUpdate(expirationTime);
+    // Unmount the root by rendering null.
+    update.tag = CaptureUpdate;
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    update.payload = { element: null };
+    var error = errorInfo.value;
+    update.callback = function() {
+      onUncaughtError(error);
+      logError(fiber, errorInfo);
+    };
+    return update;
+  }
+
+  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+    var update = createUpdate(expirationTime);
+    update.tag = CaptureUpdate;
+    var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
+    if (
+      enableGetDerivedStateFromCatch &&
+      typeof getDerivedStateFromCatch === "function"
+    ) {
+      var _error = errorInfo.value;
+      update.payload = function() {
+        return getDerivedStateFromCatch(_error);
+      };
+    }
+
+    var inst = fiber.stateNode;
+    if (inst !== null && typeof inst.componentDidCatch === "function") {
+      update.callback = function callback() {
+        if (
+          !enableGetDerivedStateFromCatch ||
+          getDerivedStateFromCatch !== "function"
+        ) {
+          // To preserve the preexisting retry behavior of error boundaries,
+          // we keep track of which ones already failed during this batch.
+          // This gets reset before we yield back to the browser.
+          // TODO: Warn in strict mode if getDerivedStateFromCatch is
+          // not defined.
+          markLegacyErrorBoundaryAsFailed(this);
+        }
+        var error = errorInfo.value;
+        var stack = errorInfo.stack;
+        logError(fiber, errorInfo);
+        this.componentDidCatch(error, {
+          componentStack: stack !== null ? stack : ""
+        });
+      };
+    }
+    return update;
+  }
+
+  function schedulePing(finishedWork) {
+    // Once the promise resolves, we should try rendering the non-
+    // placeholder state again.
+    var currentTime = recalculateCurrentTime();
+    var expirationTime = computeExpirationForFiber(currentTime, finishedWork);
+    var recoveryUpdate = createUpdate(expirationTime);
+    enqueueUpdate(finishedWork, recoveryUpdate, expirationTime);
+    scheduleWork(finishedWork, expirationTime);
+  }
 
-  function throwException(returnFiber, sourceFiber, rawValue) {
+  function throwException(
+    root,
+    returnFiber,
+    sourceFiber,
+    value,
+    renderIsExpired,
+    renderExpirationTime,
+    currentTimeMs
+  ) {
     // The source fiber did not complete.
     sourceFiber.effectTag |= Incomplete;
     // Its effect list is no longer valid.
     sourceFiber.firstEffect = sourceFiber.lastEffect = null;
 
-    var value = createCapturedValue(rawValue, sourceFiber);
+    if (
+      enableSuspense &&
+      value !== null &&
+      typeof value === "object" &&
+      typeof value.then === "function"
+    ) {
+      // This is a thenable.
+      var _thenable = value;
+
+      var expirationTimeMs = expirationTimeToMs(renderExpirationTime);
+      var startTimeMs = expirationTimeMs - 5000;
+      var elapsedMs = currentTimeMs - startTimeMs;
+      if (elapsedMs < 0) {
+        elapsedMs = 0;
+      }
+      var remainingTimeMs = expirationTimeMs - currentTimeMs;
+
+      // Find the earliest timeout of all the timeouts in the ancestor path.
+      // TODO: Alternatively, we could store the earliest timeout on the context
+      // stack, rather than searching on every suspend.
+      var _workInProgress = returnFiber;
+      var earliestTimeoutMs = -1;
+      searchForEarliestTimeout: do {
+        if (_workInProgress.tag === TimeoutComponent) {
+          var current = _workInProgress.alternate;
+          if (current !== null && current.memoizedState === true) {
+            // A parent Timeout already committed in a placeholder state. We
+            // need to handle this promise immediately. In other words, we
+            // should never suspend inside a tree that already expired.
+            earliestTimeoutMs = 0;
+            break searchForEarliestTimeout;
+          }
+          var timeoutPropMs = _workInProgress.pendingProps.ms;
+          if (typeof timeoutPropMs === "number") {
+            if (timeoutPropMs <= 0) {
+              earliestTimeoutMs = 0;
+              break searchForEarliestTimeout;
+            } else if (
+              earliestTimeoutMs === -1 ||
+              timeoutPropMs < earliestTimeoutMs
+            ) {
+              earliestTimeoutMs = timeoutPropMs;
+            }
+          } else if (earliestTimeoutMs === -1) {
+            earliestTimeoutMs = remainingTimeMs;
+          }
+        }
+        _workInProgress = _workInProgress.return;
+      } while (_workInProgress !== null);
+
+      // Compute the remaining time until the timeout.
+      var msUntilTimeout = earliestTimeoutMs - elapsedMs;
+
+      if (renderExpirationTime === Never || msUntilTimeout > 0) {
+        // There's still time remaining.
+        suspendRoot(root, _thenable, msUntilTimeout, renderExpirationTime);
+        var onResolveOrReject = function() {
+          retrySuspendedRoot(root, renderExpirationTime);
+        };
+        _thenable.then(onResolveOrReject, onResolveOrReject);
+        return;
+      } else {
+        // No time remaining. Need to fallback to placeholder.
+        // Find the nearest timeout that can be retried.
+        _workInProgress = returnFiber;
+        do {
+          switch (_workInProgress.tag) {
+            case HostRoot: {
+              // The root expired, but no fallback was provided. Throw a
+              // helpful error.
+              var message =
+                renderExpirationTime === Sync
+                  ? "A synchronous update was suspended, but no fallback UI " +
+                    "was provided."
+                  : "An update was suspended for longer than the timeout, " +
+                    "but no fallback UI was provided.";
+              value = new Error(message);
+              break;
+            }
+            case TimeoutComponent: {
+              if ((_workInProgress.effectTag & DidCapture) === NoEffect) {
+                _workInProgress.effectTag |= ShouldCapture;
+                var _onResolveOrReject = schedulePing.bind(
+                  null,
+                  _workInProgress
+                );
+                _thenable.then(_onResolveOrReject, _onResolveOrReject);
+                return;
+              }
+              // Already captured during this render. Continue to the next
+              // Timeout ancestor.
+              break;
+            }
+          }
+          _workInProgress = _workInProgress.return;
+        } while (_workInProgress !== null);
+      }
+    }
 
+    // We didn't find a boundary that could handle this type of exception. Start
+    // over and traverse parent path again, this time treating the exception
+    // as an error.
+    value = createCapturedValue(value, sourceFiber);
     var workInProgress = returnFiber;
     do {
       switch (workInProgress.tag) {
         case HostRoot: {
-          // Uncaught error
-          var errorInfo = value;
-          ensureUpdateQueues(workInProgress);
-          var updateQueue = workInProgress.updateQueue;
-          updateQueue.capturedValues = [errorInfo];
+          var _errorInfo = value;
           workInProgress.effectTag |= ShouldCapture;
+          var update = createRootErrorUpdate(
+            workInProgress,
+            _errorInfo,
+            renderExpirationTime
+          );
+          enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
           return;
         }
         case ClassComponent:
           // Capture and retry
+          var errorInfo = value;
           var ctor = workInProgress.type;
           var _instance = workInProgress.stateNode;
           if (
@@ -9883,26 +10455,29 @@ var ReactFiberUnwindWork = function(
                 typeof _instance.componentDidCatch === "function" &&
                 !isAlreadyFailedLegacyErrorBoundary(_instance)))
           ) {
-            ensureUpdateQueues(workInProgress);
-            var _updateQueue = workInProgress.updateQueue;
-            var capturedValues = _updateQueue.capturedValues;
-            if (capturedValues === null) {
-              _updateQueue.capturedValues = [value];
-            } else {
-              capturedValues.push(value);
-            }
             workInProgress.effectTag |= ShouldCapture;
+            // Schedule the error boundary to re-render using updated state
+            var _update = createClassErrorUpdate(
+              workInProgress,
+              errorInfo,
+              renderExpirationTime
+            );
+            enqueueCapturedUpdate(
+              workInProgress,
+              _update,
+              renderExpirationTime
+            );
             return;
           }
           break;
         default:
           break;
       }
-      workInProgress = workInProgress["return"];
+      workInProgress = workInProgress.return;
     } while (workInProgress !== null);
   }
 
-  function unwindWork(workInProgress) {
+  function unwindWork(workInProgress, renderIsExpired, renderExpirationTime) {
     switch (workInProgress.tag) {
       case ClassComponent: {
         popLegacyContextProvider(workInProgress);
@@ -9927,6 +10502,15 @@ var ReactFiberUnwindWork = function(
         popHostContext(workInProgress);
         return null;
       }
+      case TimeoutComponent: {
+        var _effectTag2 = workInProgress.effectTag;
+        if (_effectTag2 & ShouldCapture) {
+          workInProgress.effectTag =
+            (_effectTag2 & ~ShouldCapture) | DidCapture;
+          return workInProgress;
+        }
+        return null;
+      }
       case HostPortal:
         popHostContainer(workInProgress);
         return null;
@@ -9959,6 +10543,13 @@ var ReactFiberUnwindWork = function(
       case ContextProvider:
         popProvider(interruptedWork);
         break;
+      case Profiler:
+        if (enableProfilerTimer) {
+          // Resume in case we're picking up on work that was paused.
+          resumeActualRenderTimerIfPaused();
+          recordElapsedActualRenderTime(interruptedWork);
+        }
+        break;
       default:
         break;
     }
@@ -9967,4209 +10558,4587 @@ var ReactFiberUnwindWork = function(
   return {
     throwException: throwException,
     unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork
+    unwindInterruptedWork: unwindInterruptedWork,
+    createRootErrorUpdate: createRootErrorUpdate,
+    createClassErrorUpdate: createClassErrorUpdate
   };
 };
 
-// Module provided by RN:
-/**
- * Intercept lifecycle errors and ensure they are shown with the correct stack
- * trace within the native redbox component.
- */
-function showErrorDialog(capturedError) {
-  var componentStack = capturedError.componentStack,
-    error = capturedError.error;
-
-  var errorToHandle = void 0;
-
-  // Typically Errors are thrown but eg strings or null can be thrown as well.
-  if (error instanceof Error) {
-    var message = error.message,
-      name = error.name;
+var NO_CONTEXT = {};
 
-    var summary = message ? name + ": " + message : name;
+var ReactFiberHostContext = function(config, stack) {
+  var getChildHostContext = config.getChildHostContext,
+    getRootHostContext = config.getRootHostContext;
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
 
-    errorToHandle = error;
+  var contextStackCursor = createCursor(NO_CONTEXT);
+  var contextFiberStackCursor = createCursor(NO_CONTEXT);
+  var rootInstanceStackCursor = createCursor(NO_CONTEXT);
 
-    try {
-      errorToHandle.message =
-        summary + "\n\nThis error is located at:" + componentStack;
-    } catch (e) {}
-  } else if (typeof error === "string") {
-    errorToHandle = new Error(
-      error + "\n\nThis error is located at:" + componentStack
+  function requiredContext(c) {
+    invariant(
+      c !== NO_CONTEXT,
+      "Expected host context to exist. This error is likely caused by a bug " +
+        "in React. Please file an issue."
     );
-  } else {
-    errorToHandle = new Error("Unspecified error at:" + componentStack);
+    return c;
   }
 
-  ExceptionsManager.handleException(errorToHandle, false);
-
-  // Return false here to prevent ReactFiberErrorLogger default behavior of
-  // logging error details to console.error. Calls to console.error are
-  // automatically routed to the native redbox controller, which we've already
-  // done above by calling ExceptionsManager.
-  return false;
-}
+  function getRootHostContainer() {
+    var rootInstance = requiredContext(rootInstanceStackCursor.current);
+    return rootInstance;
+  }
 
-function logCapturedError(capturedError) {
-  var logError = showErrorDialog(capturedError);
+  function pushHostContainer(fiber, nextRootInstance) {
+    // Push current root instance onto the stack;
+    // This allows us to reset root when portals are popped.
+    push(rootInstanceStackCursor, nextRootInstance, fiber);
+    // Track the context and the Fiber that provided it.
+    // This enables us to pop only Fibers that provide unique contexts.
+    push(contextFiberStackCursor, fiber, fiber);
 
-  // Allow injected showErrorDialog() to prevent default console.error logging.
-  // This enables renderers like ReactNative to better manage redbox behavior.
-  if (logError === false) {
-    return;
+    // Finally, we need to push the host context to the stack.
+    // However, we can't just call getRootHostContext() and push it because
+    // we'd have a different number of entries on the stack depending on
+    // whether getRootHostContext() throws somewhere in renderer code or not.
+    // So we push an empty value first. This lets us safely unwind on errors.
+    push(contextStackCursor, NO_CONTEXT, fiber);
+    var nextRootContext = getRootHostContext(nextRootInstance);
+    // Now that we know this function doesn't throw, replace it.
+    pop(contextStackCursor, fiber);
+    push(contextStackCursor, nextRootContext, fiber);
   }
 
-  var error = capturedError.error;
-  var suppressLogging = error && error.suppressReactErrorLogging;
-  if (suppressLogging) {
-    return;
+  function popHostContainer(fiber) {
+    pop(contextStackCursor, fiber);
+    pop(contextFiberStackCursor, fiber);
+    pop(rootInstanceStackCursor, fiber);
   }
 
-  {
-    var componentName = capturedError.componentName,
-      componentStack = capturedError.componentStack,
-      errorBoundaryName = capturedError.errorBoundaryName,
-      errorBoundaryFound = capturedError.errorBoundaryFound,
-      willRetry = capturedError.willRetry;
+  function getHostContext() {
+    var context = requiredContext(contextStackCursor.current);
+    return context;
+  }
 
-    var componentNameMessage = componentName
-      ? "The above error occurred in the <" + componentName + "> component:"
-      : "The above error occurred in one of your React components:";
+  function pushHostContext(fiber) {
+    var rootInstance = requiredContext(rootInstanceStackCursor.current);
+    var context = requiredContext(contextStackCursor.current);
+    var nextContext = getChildHostContext(context, fiber.type, rootInstance);
 
-    var errorBoundaryMessage = void 0;
-    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
-    if (errorBoundaryFound && errorBoundaryName) {
-      if (willRetry) {
-        errorBoundaryMessage =
-          "React will try to recreate this component tree from scratch " +
-          ("using the error boundary you provided, " + errorBoundaryName + ".");
-      } else {
-        errorBoundaryMessage =
-          "This error was initially handled by the error boundary " +
-          errorBoundaryName +
-          ".\n" +
-          "Recreating the tree from scratch failed so React will unmount the tree.";
-      }
-    } else {
-      errorBoundaryMessage =
-        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
-        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
+    // Don't push this Fiber's context unless it's unique.
+    if (context === nextContext) {
+      return;
     }
-    var combinedMessage =
-      "" +
-      componentNameMessage +
-      componentStack +
-      "\n\n" +
-      ("" + errorBoundaryMessage);
 
-    // In development, we provide our own message with just the component stack.
-    // We don't include the original error message and JS stack because the browser
-    // has already printed it. Even if the application swallows the error, it is still
-    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
-    console.error(combinedMessage);
+    // Track the context and the Fiber that provided it.
+    // This enables us to pop only Fibers that provide unique contexts.
+    push(contextFiberStackCursor, fiber, fiber);
+    push(contextStackCursor, nextContext, fiber);
   }
-}
-
-var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
-var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
 
-var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
-{
-  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
-}
+  function popHostContext(fiber) {
+    // Do not pop unless this Fiber provided the current context.
+    // pushHostContext() only pushes Fibers that provide unique contexts.
+    if (contextFiberStackCursor.current !== fiber) {
+      return;
+    }
 
-function logError(boundary, errorInfo) {
-  var source = errorInfo.source;
-  var stack = errorInfo.stack;
-  if (stack === null) {
-    stack = getStackAddendumByWorkInProgressFiber(source);
+    pop(contextStackCursor, fiber);
+    pop(contextFiberStackCursor, fiber);
   }
 
-  var capturedError = {
-    componentName: source !== null ? getComponentName(source) : null,
-    componentStack: stack !== null ? stack : "",
-    error: errorInfo.value,
-    errorBoundary: null,
-    errorBoundaryName: null,
-    errorBoundaryFound: false,
-    willRetry: false
+  return {
+    getHostContext: getHostContext,
+    getRootHostContainer: getRootHostContainer,
+    popHostContainer: popHostContainer,
+    popHostContext: popHostContext,
+    pushHostContainer: pushHostContainer,
+    pushHostContext: pushHostContext
   };
+};
 
-  if (boundary !== null && boundary.tag === ClassComponent) {
-    capturedError.errorBoundary = boundary.stateNode;
-    capturedError.errorBoundaryName = getComponentName(boundary);
-    capturedError.errorBoundaryFound = true;
-    capturedError.willRetry = true;
-  }
+var ReactFiberHydrationContext = function(config) {
+  var shouldSetTextContent = config.shouldSetTextContent,
+    hydration = config.hydration;
 
-  try {
-    logCapturedError(capturedError);
-  } catch (e) {
-    // Prevent cycle if logCapturedError() throws.
-    // A cycle may still occur if logCapturedError renders a component that throws.
-    var suppressLogging = e && e.suppressReactErrorLogging;
-    if (!suppressLogging) {
-      console.error(e);
-    }
+  // If this doesn't have hydration mode.
+
+  if (!hydration) {
+    return {
+      enterHydrationState: function() {
+        return false;
+      },
+      resetHydrationState: function() {},
+      tryToClaimNextHydratableInstance: function() {},
+      prepareToHydrateHostInstance: function() {
+        invariant(
+          false,
+          "Expected prepareToHydrateHostInstance() to never be called. " +
+            "This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      prepareToHydrateHostTextInstance: function() {
+        invariant(
+          false,
+          "Expected prepareToHydrateHostTextInstance() to never be called. " +
+            "This error is likely caused by a bug in React. Please file an issue."
+        );
+      },
+      popHydrationState: function(fiber) {
+        return false;
+      }
+    };
   }
-}
 
-var ReactFiberCommitWork = function(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed,
-  recalculateCurrentTime
-) {
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation,
-    persistence = config.persistence;
+  var canHydrateInstance = hydration.canHydrateInstance,
+    canHydrateTextInstance = hydration.canHydrateTextInstance,
+    getNextHydratableSibling = hydration.getNextHydratableSibling,
+    getFirstHydratableChild = hydration.getFirstHydratableChild,
+    hydrateInstance = hydration.hydrateInstance,
+    hydrateTextInstance = hydration.hydrateTextInstance,
+    didNotMatchHydratedContainerTextInstance =
+      hydration.didNotMatchHydratedContainerTextInstance,
+    didNotMatchHydratedTextInstance = hydration.didNotMatchHydratedTextInstance,
+    didNotHydrateContainerInstance = hydration.didNotHydrateContainerInstance,
+    didNotHydrateInstance = hydration.didNotHydrateInstance,
+    didNotFindHydratableContainerInstance =
+      hydration.didNotFindHydratableContainerInstance,
+    didNotFindHydratableContainerTextInstance =
+      hydration.didNotFindHydratableContainerTextInstance,
+    didNotFindHydratableInstance = hydration.didNotFindHydratableInstance,
+    didNotFindHydratableTextInstance =
+      hydration.didNotFindHydratableTextInstance;
 
-  var callComponentWillUnmountWithTimer = function(current, instance) {
-    startPhaseTimer(current, "componentWillUnmount");
-    instance.props = current.memoizedProps;
-    instance.state = current.memoizedState;
-    instance.componentWillUnmount();
-    stopPhaseTimer();
-  };
+  // The deepest Fiber on the stack involved in a hydration context.
+  // This may have been an insertion or a hydration.
 
-  // Capture errors so they don't interrupt unmounting.
-  function safelyCallComponentWillUnmount(current, instance) {
-    {
-      invokeGuardedCallback$3(
-        null,
-        callComponentWillUnmountWithTimer,
-        null,
-        current,
-        instance
-      );
-      if (hasCaughtError$1()) {
-        var unmountError = clearCaughtError$1();
-        captureError(current, unmountError);
-      }
-    }
+  var hydrationParentFiber = null;
+  var nextHydratableInstance = null;
+  var isHydrating = false;
+
+  function enterHydrationState(fiber) {
+    var parentInstance = fiber.stateNode.containerInfo;
+    nextHydratableInstance = getFirstHydratableChild(parentInstance);
+    hydrationParentFiber = fiber;
+    isHydrating = true;
+    return true;
   }
 
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (ref !== null) {
-      if (typeof ref === "function") {
-        {
-          invokeGuardedCallback$3(null, ref, null, null);
-          if (hasCaughtError$1()) {
-            var refError = clearCaughtError$1();
-            captureError(current, refError);
-          }
-        }
-      } else {
-        ref.current = null;
+  function deleteHydratableInstance(returnFiber, instance) {
+    {
+      switch (returnFiber.tag) {
+        case HostRoot:
+          didNotHydrateContainerInstance(
+            returnFiber.stateNode.containerInfo,
+            instance
+          );
+          break;
+        case HostComponent:
+          didNotHydrateInstance(
+            returnFiber.type,
+            returnFiber.memoizedProps,
+            returnFiber.stateNode,
+            instance
+          );
+          break;
       }
     }
-  }
 
-  function commitBeforeMutationLifeCycles(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        if (finishedWork.effectTag & Snapshot) {
-          if (current !== null) {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
-            var _instance = finishedWork.stateNode;
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            var snapshot = _instance.getSnapshotBeforeUpdate(
-              prevProps,
-              prevState
-            );
-            {
-              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
-              if (
-                snapshot === undefined &&
-                !didWarnSet.has(finishedWork.type)
-              ) {
-                didWarnSet.add(finishedWork.type);
-                warning(
-                  false,
-                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
-                    "must be returned. You have returned undefined.",
-                  getComponentName(finishedWork)
-                );
-              }
-            }
-            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
-            stopPhaseTimer();
-          }
-        }
-        return;
-      }
-      case HostRoot:
-      case HostComponent:
-      case HostText:
-      case HostPortal:
-        // Nothing to do for these component types
-        return;
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
+    var childToDelete = createFiberFromHostInstanceForDeletion();
+    childToDelete.stateNode = instance;
+    childToDelete.return = returnFiber;
+    childToDelete.effectTag = Deletion;
+
+    // This might seem like it belongs on progressedFirstDeletion. However,
+    // these children are not part of the reconciliation list of children.
+    // Even if we abort and rereconcile the children, that will try to hydrate
+    // again and the nodes are still in the host tree so these will be
+    // recreated.
+    if (returnFiber.lastEffect !== null) {
+      returnFiber.lastEffect.nextEffect = childToDelete;
+      returnFiber.lastEffect = childToDelete;
+    } else {
+      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
     }
   }
 
-  function commitLifeCycles(
-    finishedRoot,
-    current,
-    finishedWork,
-    currentTime,
-    committedExpirationTime
-  ) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        var _instance2 = finishedWork.stateNode;
-        if (finishedWork.effectTag & Update) {
-          if (current === null) {
-            startPhaseTimer(finishedWork, "componentDidMount");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidMount();
-            stopPhaseTimer();
-          } else {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "componentDidUpdate");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidUpdate(
-              prevProps,
-              prevState,
-              _instance2.__reactInternalSnapshotBeforeUpdate
-            );
-            stopPhaseTimer();
+  function insertNonHydratedInstance(returnFiber, fiber) {
+    fiber.effectTag |= Placement;
+    {
+      switch (returnFiber.tag) {
+        case HostRoot: {
+          var parentContainer = returnFiber.stateNode.containerInfo;
+          switch (fiber.tag) {
+            case HostComponent:
+              var type = fiber.type;
+              var props = fiber.pendingProps;
+              didNotFindHydratableContainerInstance(
+                parentContainer,
+                type,
+                props
+              );
+              break;
+            case HostText:
+              var text = fiber.pendingProps;
+              didNotFindHydratableContainerTextInstance(parentContainer, text);
+              break;
           }
+          break;
         }
-        var updateQueue = finishedWork.updateQueue;
-        if (updateQueue !== null) {
-          commitCallbacks(updateQueue, _instance2);
-        }
-        return;
-      }
-      case HostRoot: {
-        var _updateQueue = finishedWork.updateQueue;
-        if (_updateQueue !== null) {
-          var _instance3 = null;
-          if (finishedWork.child !== null) {
-            switch (finishedWork.child.tag) {
-              case HostComponent:
-                _instance3 = getPublicInstance(finishedWork.child.stateNode);
-                break;
-              case ClassComponent:
-                _instance3 = finishedWork.child.stateNode;
-                break;
-            }
+        case HostComponent: {
+          var parentType = returnFiber.type;
+          var parentProps = returnFiber.memoizedProps;
+          var parentInstance = returnFiber.stateNode;
+          switch (fiber.tag) {
+            case HostComponent:
+              var _type = fiber.type;
+              var _props = fiber.pendingProps;
+              didNotFindHydratableInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                _type,
+                _props
+              );
+              break;
+            case HostText:
+              var _text = fiber.pendingProps;
+              didNotFindHydratableTextInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                _text
+              );
+              break;
           }
-          commitCallbacks(_updateQueue, _instance3);
+          break;
         }
-        return;
+        default:
+          return;
       }
-      case HostComponent: {
-        var _instance4 = finishedWork.stateNode;
+    }
+  }
 
-        // Renderers may schedule work to be done after host components are mounted
-        // (eg DOM renderer may schedule auto-focus for inputs and form controls).
-        // These effects should only be committed when components are first mounted,
-        // aka when there is no current/alternate.
-        if (current === null && finishedWork.effectTag & Update) {
-          var type = finishedWork.type;
-          var props = finishedWork.memoizedProps;
-          commitMount(_instance4, type, props, finishedWork);
+  function tryHydrate(fiber, nextInstance) {
+    switch (fiber.tag) {
+      case HostComponent: {
+        var type = fiber.type;
+        var props = fiber.pendingProps;
+        var instance = canHydrateInstance(nextInstance, type, props);
+        if (instance !== null) {
+          fiber.stateNode = instance;
+          return true;
         }
-
-        return;
+        return false;
       }
       case HostText: {
-        // We have no life-cycles associated with text.
-        return;
+        var text = fiber.pendingProps;
+        var textInstance = canHydrateTextInstance(nextInstance, text);
+        if (textInstance !== null) {
+          fiber.stateNode = textInstance;
+          return true;
+        }
+        return false;
       }
-      case HostPortal: {
-        // We have no life-cycles associated with portals.
+      default:
+        return false;
+    }
+  }
+
+  function tryToClaimNextHydratableInstance(fiber) {
+    if (!isHydrating) {
+      return;
+    }
+    var nextInstance = nextHydratableInstance;
+    if (!nextInstance) {
+      // Nothing to hydrate. Make it an insertion.
+      insertNonHydratedInstance(hydrationParentFiber, fiber);
+      isHydrating = false;
+      hydrationParentFiber = fiber;
+      return;
+    }
+    if (!tryHydrate(fiber, nextInstance)) {
+      // If we can't hydrate this instance let's try the next one.
+      // We use this as a heuristic. It's based on intuition and not data so it
+      // might be flawed or unnecessary.
+      nextInstance = getNextHydratableSibling(nextInstance);
+      if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
+        // Nothing to hydrate. Make it an insertion.
+        insertNonHydratedInstance(hydrationParentFiber, fiber);
+        isHydrating = false;
+        hydrationParentFiber = fiber;
         return;
       }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
+      // We matched the next one, we'll now assume that the first one was
+      // superfluous and we'll delete it. Since we can't eagerly delete it
+      // we'll have to schedule a deletion. To do that, this node needs a dummy
+      // fiber associated with it.
+      deleteHydratableInstance(hydrationParentFiber, nextHydratableInstance);
     }
+    hydrationParentFiber = fiber;
+    nextHydratableInstance = getFirstHydratableChild(nextInstance);
   }
 
-  function commitErrorLogging(finishedWork, onUncaughtError) {
-    switch (finishedWork.tag) {
-      case ClassComponent:
-        {
-          var ctor = finishedWork.type;
-          var _instance5 = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            updateQueue !== null && updateQueue.capturedValues !== null,
-            "An error logging effect should not have been scheduled if no errors " +
-              "were captured. This error is likely caused by a bug in React. " +
-              "Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-
-          if (typeof ctor.getDerivedStateFromCatch !== "function") {
-            // To preserve the preexisting retry behavior of error boundaries,
-            // we keep track of which ones already failed during this batch.
-            // This gets reset before we yield back to the browser.
-            // TODO: Warn in strict mode if getDerivedStateFromCatch is
-            // not defined.
-            markLegacyErrorBoundaryAsFailed(_instance5);
-          }
-
-          _instance5.props = finishedWork.memoizedProps;
-          _instance5.state = finishedWork.memoizedState;
-          for (var i = 0; i < capturedErrors.length; i++) {
-            var errorInfo = capturedErrors[i];
-            var _error = errorInfo.value;
-            var stack = errorInfo.stack;
-            logError(finishedWork, errorInfo);
-            _instance5.componentDidCatch(_error, {
-              componentStack: stack !== null ? stack : ""
-            });
-          }
-        }
-        break;
-      case HostRoot: {
-        var _updateQueue2 = finishedWork.updateQueue;
-        invariant(
-          _updateQueue2 !== null && _updateQueue2.capturedValues !== null,
-          "An error logging effect should not have been scheduled if no errors " +
-            "were captured. This error is likely caused by a bug in React. " +
-            "Please file an issue."
-        );
-        var _capturedErrors = _updateQueue2.capturedValues;
-        _updateQueue2.capturedValues = null;
-        for (var _i = 0; _i < _capturedErrors.length; _i++) {
-          var _errorInfo = _capturedErrors[_i];
-          logError(finishedWork, _errorInfo);
-          onUncaughtError(_errorInfo.value);
-        }
-        break;
-      }
-      default:
-        invariant(
-          false,
-          "This unit of work tag cannot capture errors.  This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
+  function prepareToHydrateHostInstance(
+    fiber,
+    rootContainerInstance,
+    hostContext
+  ) {
+    var instance = fiber.stateNode;
+    var updatePayload = hydrateInstance(
+      instance,
+      fiber.type,
+      fiber.memoizedProps,
+      rootContainerInstance,
+      hostContext,
+      fiber
+    );
+    // TODO: Type this specific to this type of component.
+    fiber.updateQueue = updatePayload;
+    // If the update payload indicates that there is a change or if there
+    // is a new ref we mark this as an update.
+    if (updatePayload !== null) {
+      return true;
     }
+    return false;
   }
 
-  function commitAttachRef(finishedWork) {
-    var ref = finishedWork.ref;
-    if (ref !== null) {
-      var _instance6 = finishedWork.stateNode;
-      var instanceToUse = void 0;
-      switch (finishedWork.tag) {
-        case HostComponent:
-          instanceToUse = getPublicInstance(_instance6);
-          break;
-        default:
-          instanceToUse = _instance6;
-      }
-      if (typeof ref === "function") {
-        ref(instanceToUse);
-      } else {
-        {
-          if (!ref.hasOwnProperty("current")) {
-            warning(
-              false,
-              "Unexpected ref object provided for %s. " +
-                "Use either a ref-setter function or React.createRef().%s",
-              getComponentName(finishedWork),
-              getStackAddendumByWorkInProgressFiber(finishedWork)
-            );
+  function prepareToHydrateHostTextInstance(fiber) {
+    var textInstance = fiber.stateNode;
+    var textContent = fiber.memoizedProps;
+    var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
+    {
+      if (shouldUpdate) {
+        // We assume that prepareToHydrateHostTextInstance is called in a context where the
+        // hydration parent is the parent host component of this host text.
+        var returnFiber = hydrationParentFiber;
+        if (returnFiber !== null) {
+          switch (returnFiber.tag) {
+            case HostRoot: {
+              var parentContainer = returnFiber.stateNode.containerInfo;
+              didNotMatchHydratedContainerTextInstance(
+                parentContainer,
+                textInstance,
+                textContent
+              );
+              break;
+            }
+            case HostComponent: {
+              var parentType = returnFiber.type;
+              var parentProps = returnFiber.memoizedProps;
+              var parentInstance = returnFiber.stateNode;
+              didNotMatchHydratedTextInstance(
+                parentType,
+                parentProps,
+                parentInstance,
+                textInstance,
+                textContent
+              );
+              break;
+            }
           }
         }
-
-        ref.current = instanceToUse;
       }
     }
+    return shouldUpdate;
   }
 
-  function commitDetachRef(current) {
-    var currentRef = current.ref;
-    if (currentRef !== null) {
-      if (typeof currentRef === "function") {
-        currentRef(null);
-      } else {
-        currentRef.current = null;
-      }
+  function popToNextHostParent(fiber) {
+    var parent = fiber.return;
+    while (
+      parent !== null &&
+      parent.tag !== HostComponent &&
+      parent.tag !== HostRoot
+    ) {
+      parent = parent.return;
     }
+    hydrationParentFiber = parent;
   }
 
-  // User-originating errors (lifecycles and refs) should not interrupt
-  // deletion, so don't let them throw. Host-originating errors should
-  // interrupt deletion, so it's okay
-  function commitUnmount(current) {
-    if (typeof onCommitUnmount === "function") {
-      onCommitUnmount(current);
+  function popHydrationState(fiber) {
+    if (fiber !== hydrationParentFiber) {
+      // We're deeper than the current hydration context, inside an inserted
+      // tree.
+      return false;
     }
-
-    switch (current.tag) {
-      case ClassComponent: {
-        safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if (typeof _instance7.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance7);
-        }
-        return;
-      }
-      case HostComponent: {
-        safelyDetachRef(current);
-        return;
-      }
-      case CallComponent: {
-        commitNestedUnmounts(current.stateNode);
-        return;
-      }
-      case HostPortal: {
-        // TODO: this is recursive.
-        // We are also not using this parent because
-        // the portal will get pushed immediately.
-        if (enableMutatingReconciler && mutation) {
-          unmountHostComponents(current);
-        } else if (enablePersistentReconciler && persistence) {
-          emptyPortalContainer(current);
-        }
-        return;
-      }
+    if (!isHydrating) {
+      // If we're not currently hydrating but we're in a hydration context, then
+      // we were an insertion and now need to pop up reenter hydration of our
+      // siblings.
+      popToNextHostParent(fiber);
+      isHydrating = true;
+      return false;
     }
-  }
 
-  function commitNestedUnmounts(root) {
-    // While we're inside a removed host node we don't want to call
-    // removeChild on the inner nodes because they're removed by the top
-    // call anyway. We also want to call componentWillUnmount on all
-    // composites before this host node is removed from the tree. Therefore
-    var node = root;
-    while (true) {
-      commitUnmount(node);
-      // Visit children because they may contain more composite or host nodes.
-      // Skip portals because commitUnmount() currently visits them recursively.
-      if (
-        node.child !== null &&
-        // If we use mutation we drill down into portals using commitUnmount above.
-        // If we don't use mutation we drill down into portals here instead.
-        (!mutation || node.tag !== HostPortal)
-      ) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === root) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === root) {
-          return;
-        }
-        node = node["return"];
+    var type = fiber.type;
+
+    // If we have any remaining hydratable nodes, we need to delete them now.
+    // We only do this deeper than head and body since they tend to have random
+    // other nodes in them. We also ignore components with pure text content in
+    // side of them.
+    // TODO: Better heuristic.
+    if (
+      fiber.tag !== HostComponent ||
+      (type !== "head" &&
+        type !== "body" &&
+        !shouldSetTextContent(type, fiber.memoizedProps))
+    ) {
+      var nextInstance = nextHydratableInstance;
+      while (nextInstance) {
+        deleteHydratableInstance(fiber, nextInstance);
+        nextInstance = getNextHydratableSibling(nextInstance);
       }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
     }
+
+    popToNextHostParent(fiber);
+    nextHydratableInstance = hydrationParentFiber
+      ? getNextHydratableSibling(fiber.stateNode)
+      : null;
+    return true;
   }
 
-  function detachFiber(current) {
-    // Cut off the return pointers to disconnect it from the tree. Ideally, we
-    // should clear the child pointer of the parent alternate to let this
-    // get GC:ed but we don't know which for sure which parent is the current
-    // one so we'll settle for GC:ing the subtree of this child. This child
-    // itself will be GC:ed when the parent updates the next time.
-    current["return"] = null;
-    current.child = null;
-    if (current.alternate) {
-      current.alternate.child = null;
-      current.alternate["return"] = null;
-    }
+  function resetHydrationState() {
+    hydrationParentFiber = null;
+    nextHydratableInstance = null;
+    isHydrating = false;
   }
 
-  var emptyPortalContainer = void 0;
+  return {
+    enterHydrationState: enterHydrationState,
+    resetHydrationState: resetHydrationState,
+    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
+    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
+    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
+    popHydrationState: popHydrationState
+  };
+};
 
-  if (!mutation) {
-    var commitContainer = void 0;
-    if (persistence) {
-      var replaceContainerChildren = persistence.replaceContainerChildren,
-        createContainerChildSet = persistence.createContainerChildSet;
+// This lets us hook into Fiber to debug what it's doing.
+// See https://github.com/facebook/react/pull/8033.
+// This is not part of the public API, not even for React DevTools.
+// You may only inject a debugTool if you work on React Fiber itself.
+var ReactFiberInstrumentation = {
+  debugTool: null
+};
 
-      emptyPortalContainer = function(current) {
-        var portal = current.stateNode;
-        var containerInfo = portal.containerInfo;
+var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
 
-        var emptyChildSet = createContainerChildSet(containerInfo);
-        replaceContainerChildren(containerInfo, emptyChildSet);
-      };
-      commitContainer = function(finishedWork) {
-        switch (finishedWork.tag) {
-          case ClassComponent: {
-            return;
-          }
-          case HostComponent: {
-            return;
-          }
-          case HostText: {
-            return;
-          }
-          case HostRoot:
-          case HostPortal: {
-            var portalOrRoot = finishedWork.stateNode;
-            var containerInfo = portalOrRoot.containerInfo,
-              _pendingChildren = portalOrRoot.pendingChildren;
+// TODO: Offscreen updates
 
-            replaceContainerChildren(containerInfo, _pendingChildren);
-            return;
-          }
-          default: {
-            invariant(
-              false,
-              "This unit of work tag should not have side-effects. This error is " +
-                "likely caused by a bug in React. Please file an issue."
-            );
-          }
-        }
-      };
+function markPendingPriorityLevel(root, expirationTime) {
+  if (enableSuspense) {
+    // Update the latest and earliest pending times
+    var earliestPendingTime = root.earliestPendingTime;
+    if (earliestPendingTime === NoWork) {
+      // No other pending updates.
+      root.earliestPendingTime = root.latestPendingTime = expirationTime;
     } else {
-      commitContainer = function(finishedWork) {
-        // Noop
-      };
+      if (earliestPendingTime > expirationTime) {
+        // This is the earliest pending update.
+        root.earliestPendingTime = expirationTime;
+      } else {
+        var latestPendingTime = root.latestPendingTime;
+        if (latestPendingTime < expirationTime) {
+          // This is the latest pending update
+          root.latestPendingTime = expirationTime;
+        }
+      }
     }
-    if (enablePersistentReconciler || enableNoopReconciler) {
-      return {
-        commitResetTextContent: function(finishedWork) {},
-        commitPlacement: function(finishedWork) {},
-        commitDeletion: function(current) {
-          // Detach refs and call componentWillUnmount() on the whole subtree.
-          commitNestedUnmounts(current);
-          detachFiber(current);
-        },
-        commitWork: function(current, finishedWork) {
-          commitContainer(finishedWork);
-        },
+  }
+}
 
-        commitLifeCycles: commitLifeCycles,
-        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-        commitErrorLogging: commitErrorLogging,
-        commitAttachRef: commitAttachRef,
-        commitDetachRef: commitDetachRef
-      };
-    } else if (persistence) {
-      invariant(false, "Persistent reconciler is disabled.");
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
+function markCommittedPriorityLevels(root, currentTime, earliestRemainingTime) {
+  if (enableSuspense) {
+    if (earliestRemainingTime === NoWork) {
+      // Fast path. There's no remaining work. Clear everything.
+      root.earliestPendingTime = NoWork;
+      root.latestPendingTime = NoWork;
+      root.earliestSuspendedTime = NoWork;
+      root.latestSuspendedTime = NoWork;
+      root.latestPingedTime = NoWork;
+      return;
     }
-  }
-  var commitMount = mutation.commitMount,
-    commitUpdate = mutation.commitUpdate,
-    resetTextContent = mutation.resetTextContent,
-    commitTextUpdate = mutation.commitTextUpdate,
-    appendChild = mutation.appendChild,
-    appendChildToContainer = mutation.appendChildToContainer,
-    insertBefore = mutation.insertBefore,
-    insertInContainerBefore = mutation.insertInContainerBefore,
-    removeChild = mutation.removeChild,
-    removeChildFromContainer = mutation.removeChildFromContainer;
 
-  function getHostParentFiber(fiber) {
-    var parent = fiber["return"];
-    while (parent !== null) {
-      if (isHostParent(parent)) {
-        return parent;
+    // Let's see if the previous latest known pending level was just flushed.
+    var latestPendingTime = root.latestPendingTime;
+    if (latestPendingTime !== NoWork) {
+      if (latestPendingTime < earliestRemainingTime) {
+        // We've flushed all the known pending levels.
+        root.earliestPendingTime = root.latestPendingTime = NoWork;
+      } else {
+        var earliestPendingTime = root.earliestPendingTime;
+        if (earliestPendingTime < earliestRemainingTime) {
+          // We've flushed the earliest known pending level. Set this to the
+          // latest pending time.
+          root.earliestPendingTime = root.latestPendingTime;
+        }
       }
-      parent = parent["return"];
     }
-    invariant(
-      false,
-      "Expected to find a host parent. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-  }
 
-  function isHostParent(fiber) {
-    return (
-      fiber.tag === HostComponent ||
-      fiber.tag === HostRoot ||
-      fiber.tag === HostPortal
-    );
+    // Now let's handle the earliest remaining level in the whole tree. We need to
+    // decide whether to treat it as a pending level or as suspended. Check
+    // it falls within the range of known suspended levels.
+
+    var earliestSuspendedTime = root.earliestSuspendedTime;
+    if (earliestSuspendedTime === NoWork) {
+      // There's no suspended work. Treat the earliest remaining level as a
+      // pending level.
+      markPendingPriorityLevel(root, earliestRemainingTime);
+      return;
+    }
+
+    var latestSuspendedTime = root.latestSuspendedTime;
+    if (earliestRemainingTime > latestSuspendedTime) {
+      // The earliest remaining level is later than all the suspended work. That
+      // means we've flushed all the suspended work.
+      root.earliestSuspendedTime = NoWork;
+      root.latestSuspendedTime = NoWork;
+      root.latestPingedTime = NoWork;
+
+      // There's no suspended work. Treat the earliest remaining level as a
+      // pending level.
+      markPendingPriorityLevel(root, earliestRemainingTime);
+      return;
+    }
+
+    if (earliestRemainingTime < earliestSuspendedTime) {
+      // The earliest remaining time is earlier than all the suspended work.
+      // Treat it as a pending update.
+      markPendingPriorityLevel(root, earliestRemainingTime);
+      return;
+    }
+
+    // The earliest remaining time falls within the range of known suspended
+    // levels. We should treat this as suspended work.
   }
+}
 
-  function getHostSibling(fiber) {
-    // We're going to search forward into the tree until we find a sibling host
-    // node. Unfortunately, if multiple insertions are done in a row we have to
-    // search past them. This leads to exponential search for the next sibling.
-    var node = fiber;
-    siblings: while (true) {
-      // If we didn't find anything, let's try the next sibling.
-      while (node.sibling === null) {
-        if (node["return"] === null || isHostParent(node["return"])) {
-          // If we pop out of the root or hit the parent the fiber we are the
-          // last sibling.
-          return null;
-        }
-        node = node["return"];
+function markSuspendedPriorityLevel(root, suspendedTime) {
+  if (enableSuspense) {
+    // First, check the known pending levels and update them if needed.
+    var earliestPendingTime = root.earliestPendingTime;
+    var latestPendingTime = root.latestPendingTime;
+    if (earliestPendingTime === suspendedTime) {
+      if (latestPendingTime === suspendedTime) {
+        // Both known pending levels were suspended. Clear them.
+        root.earliestPendingTime = root.latestPendingTime = NoWork;
+      } else {
+        // The earliest pending level was suspended. Clear by setting it to the
+        // latest pending level.
+        root.earliestPendingTime = latestPendingTime;
       }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-      while (node.tag !== HostComponent && node.tag !== HostText) {
-        // If it is not host node and, we might have a host node inside it.
-        // Try to search down until we find one.
-        if (node.effectTag & Placement) {
-          // If we don't have a child, try the siblings instead.
-          continue siblings;
-        }
-        // If we don't have a child, try the siblings instead.
-        // We also skip portals because they are not part of this host tree.
-        if (node.child === null || node.tag === HostPortal) {
-          continue siblings;
-        } else {
-          node.child["return"] = node;
-          node = node.child;
-        }
+    } else if (latestPendingTime === suspendedTime) {
+      // The latest pending level was suspended. Clear by setting it to the
+      // latest pending level.
+      root.latestPendingTime = earliestPendingTime;
+    }
+
+    // Next, if we're working on the lowest known suspended level, clear the ping.
+    // TODO: What if a promise suspends and pings before the root completes?
+    var latestSuspendedTime = root.latestSuspendedTime;
+    if (latestSuspendedTime === suspendedTime) {
+      root.latestPingedTime = NoWork;
+    }
+
+    // Finally, update the known suspended levels.
+    var earliestSuspendedTime = root.earliestSuspendedTime;
+    if (earliestSuspendedTime === NoWork) {
+      // No other suspended levels.
+      root.earliestSuspendedTime = root.latestSuspendedTime = suspendedTime;
+    } else {
+      if (earliestSuspendedTime > suspendedTime) {
+        // This is the earliest suspended level.
+        root.earliestSuspendedTime = suspendedTime;
+      } else if (latestSuspendedTime < suspendedTime) {
+        // This is the latest suspended level
+        root.latestSuspendedTime = suspendedTime;
       }
-      // Check if this host node is stable or about to be placed.
-      if (!(node.effectTag & Placement)) {
-        // Found it!
-        return node.stateNode;
+    }
+  }
+}
+
+function markPingedPriorityLevel(root, pingedTime) {
+  if (enableSuspense) {
+    var latestSuspendedTime = root.latestSuspendedTime;
+    if (latestSuspendedTime !== NoWork && latestSuspendedTime <= pingedTime) {
+      var latestPingedTime = root.latestPingedTime;
+      if (latestPingedTime === NoWork || latestPingedTime < pingedTime) {
+        root.latestPingedTime = pingedTime;
       }
     }
   }
+}
 
-  function commitPlacement(finishedWork) {
-    // Recursively insert all host nodes into the parent.
-    var parentFiber = getHostParentFiber(finishedWork);
-    var parent = void 0;
-    var isContainer = void 0;
-    switch (parentFiber.tag) {
-      case HostComponent:
-        parent = parentFiber.stateNode;
-        isContainer = false;
-        break;
-      case HostRoot:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      case HostPortal:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      default:
-        invariant(
-          false,
-          "Invalid host parent fiber. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
+function findNextPendingPriorityLevel(root) {
+  if (enableSuspense) {
+    var earliestSuspendedTime = root.earliestSuspendedTime;
+    var earliestPendingTime = root.earliestPendingTime;
+    if (earliestSuspendedTime === NoWork) {
+      // Fast path. There's no suspended work.
+      return earliestPendingTime;
     }
-    if (parentFiber.effectTag & ContentReset) {
-      // Reset the text content of the parent before doing any insertions
-      resetTextContent(parent);
-      // Clear ContentReset from the effect tag
-      parentFiber.effectTag &= ~ContentReset;
+
+    // First, check if there's known pending work.
+    if (earliestPendingTime !== NoWork) {
+      return earliestPendingTime;
     }
 
-    var before = getHostSibling(finishedWork);
-    // We only have the top Fiber that was inserted but we need recurse down its
-    // children to find all the terminal nodes.
-    var node = finishedWork;
-    while (true) {
-      if (node.tag === HostComponent || node.tag === HostText) {
-        if (before) {
-          if (isContainer) {
-            insertInContainerBefore(parent, node.stateNode, before);
-          } else {
-            insertBefore(parent, node.stateNode, before);
-          }
-        } else {
-          if (isContainer) {
-            appendChildToContainer(parent, node.stateNode);
-          } else {
-            appendChild(parent, node.stateNode);
-          }
-        }
-      } else if (node.tag === HostPortal) {
-        // If the insertion itself is a portal, then we don't want to traverse
-        // down its children. Instead, we'll get insertions from each child in
-        // the portal directly.
-      } else if (node.child !== null) {
-        node.child["return"] = node;
-        node = node.child;
-        continue;
-      }
-      if (node === finishedWork) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === finishedWork) {
-          return;
-        }
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
+    // Finally, if a suspended level was pinged, work on that. Otherwise there's
+    // nothing to work on.
+    return root.latestPingedTime;
+  } else {
+    return root.current.expirationTime;
+  }
+}
+
+var warnedAboutMissingGetChildContext = void 0;
+
+{
+  warnedAboutMissingGetChildContext = {};
+}
+
+var ReactFiberLegacyContext = function(stack) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
+
+  // A cursor to the current merged context object on the stack.
+
+  var contextStackCursor = createCursor(emptyObject);
+  // A cursor to a boolean indicating whether the context has changed.
+  var didPerformWorkStackCursor = createCursor(false);
+  // Keep track of the previous context object that was on the stack.
+  // We use this to get access to the parent context after we have already
+  // pushed the next context provider, and now need to merge their contexts.
+  var previousContext = emptyObject;
+
+  function getUnmaskedContext(workInProgress) {
+    var hasOwnContext = isContextProvider(workInProgress);
+    if (hasOwnContext) {
+      // If the fiber is a context provider itself, when we read its context
+      // we have already pushed its own child context on the stack. A context
+      // provider should not "see" its own child context. Therefore we read the
+      // previous (parent) context instead for a context provider.
+      return previousContext;
     }
+    return contextStackCursor.current;
   }
 
-  function unmountHostComponents(current) {
-    // We only have the top Fiber that was inserted but we need recurse down its
-    var node = current;
+  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+    var instance = workInProgress.stateNode;
+    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
+  }
 
-    // Each iteration, currentParent is populated with node's host parent if not
-    // currentParentIsValid.
-    var currentParentIsValid = false;
-    var currentParent = void 0;
-    var currentParentIsContainer = void 0;
+  function getMaskedContext(workInProgress, unmaskedContext) {
+    var type = workInProgress.type;
+    var contextTypes = type.contextTypes;
+    if (!contextTypes) {
+      return emptyObject;
+    }
 
-    while (true) {
-      if (!currentParentIsValid) {
-        var parent = node["return"];
-        findParent: while (true) {
-          invariant(
-            parent !== null,
-            "Expected to find a host parent. This error is likely caused by " +
-              "a bug in React. Please file an issue."
-          );
-          switch (parent.tag) {
-            case HostComponent:
-              currentParent = parent.stateNode;
-              currentParentIsContainer = false;
-              break findParent;
-            case HostRoot:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-            case HostPortal:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-          }
-          parent = parent["return"];
-        }
-        currentParentIsValid = true;
-      }
+    // Avoid recreating masked context unless unmasked context has changed.
+    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
+    // This may trigger infinite loops if componentWillReceiveProps calls setState.
+    var instance = workInProgress.stateNode;
+    if (
+      instance &&
+      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+    ) {
+      return instance.__reactInternalMemoizedMaskedChildContext;
+    }
 
-      if (node.tag === HostComponent || node.tag === HostText) {
-        commitNestedUnmounts(node);
-        // After all the children have unmounted, it is now safe to remove the
-        // node from the tree.
-        if (currentParentIsContainer) {
-          removeChildFromContainer(currentParent, node.stateNode);
-        } else {
-          removeChild(currentParent, node.stateNode);
-        }
-        // Don't visit children because we already visited them.
-      } else if (node.tag === HostPortal) {
-        // When we go into a portal, it becomes the parent to remove from.
-        // We will reassign it back when we pop the portal on the way up.
-        currentParent = node.stateNode.containerInfo;
-        // Visit children because portals might contain host components.
-        if (node.child !== null) {
-          node.child["return"] = node;
-          node = node.child;
-          continue;
-        }
-      } else {
-        commitUnmount(node);
-        // Visit children because we may find more host components below.
-        if (node.child !== null) {
-          node.child["return"] = node;
-          node = node.child;
-          continue;
-        }
-      }
-      if (node === current) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node["return"] === null || node["return"] === current) {
-          return;
-        }
-        node = node["return"];
-        if (node.tag === HostPortal) {
-          // When we go out of the portal, we need to restore the parent.
-          // Since we don't keep a stack of them, we will search for it.
-          currentParentIsValid = false;
-        }
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
+    var context = {};
+    for (var key in contextTypes) {
+      context[key] = unmaskedContext[key];
+    }
+
+    {
+      var name = getComponentName(workInProgress) || "Unknown";
+      checkPropTypes(
+        contextTypes,
+        context,
+        "context",
+        name,
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
     }
-  }
 
-  function commitDeletion(current) {
-    // Recursively delete all host nodes from the parent.
-    // Detach refs and call componentWillUnmount() on the whole subtree.
-    unmountHostComponents(current);
-    detachFiber(current);
+    // Cache unmasked context so we can avoid recreating masked context unless necessary.
+    // Context is created before the class component is instantiated so check for instance.
+    if (instance) {
+      cacheContext(workInProgress, unmaskedContext, context);
+    }
+
+    return context;
   }
 
-  function commitWork(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        return;
-      }
-      case HostComponent: {
-        var _instance8 = finishedWork.stateNode;
-        if (_instance8 != null) {
-          // Commit the work prepared earlier.
-          var newProps = finishedWork.memoizedProps;
-          // For hydration we reuse the update path but we treat the oldProps
-          // as the newProps. The updatePayload will contain the real change in
-          // this case.
-          var oldProps = current !== null ? current.memoizedProps : newProps;
-          var type = finishedWork.type;
-          // TODO: Type the updateQueue to be specific to host components.
-          var updatePayload = finishedWork.updateQueue;
-          finishedWork.updateQueue = null;
-          if (updatePayload !== null) {
-            commitUpdate(
-              _instance8,
-              updatePayload,
-              type,
-              oldProps,
-              newProps,
-              finishedWork
-            );
-          }
-        }
-        return;
-      }
-      case HostText: {
-        invariant(
-          finishedWork.stateNode !== null,
-          "This should have a text node initialized. This error is likely " +
-            "caused by a bug in React. Please file an issue."
-        );
-        var textInstance = finishedWork.stateNode;
-        var newText = finishedWork.memoizedProps;
-        // For hydration we reuse the update path but we treat the oldProps
-        // as the newProps. The updatePayload will contain the real change in
-        // this case.
-        var oldText = current !== null ? current.memoizedProps : newText;
-        commitTextUpdate(textInstance, oldText, newText);
-        return;
-      }
-      case HostRoot: {
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
-    }
+  function hasContextChanged() {
+    return didPerformWorkStackCursor.current;
   }
 
-  function commitResetTextContent(current) {
-    resetTextContent(current.stateNode);
+  function isContextConsumer(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
   }
 
-  if (enableMutatingReconciler) {
-    return {
-      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitResetTextContent: commitResetTextContent,
-      commitPlacement: commitPlacement,
-      commitDeletion: commitDeletion,
-      commitWork: commitWork,
-      commitLifeCycles: commitLifeCycles,
-      commitErrorLogging: commitErrorLogging,
-      commitAttachRef: commitAttachRef,
-      commitDetachRef: commitDetachRef
-    };
-  } else {
-    invariant(false, "Mutating reconciler is disabled.");
+  function isContextProvider(fiber) {
+    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
   }
-};
 
-var NO_CONTEXT = {};
+  function popContextProvider(fiber) {
+    if (!isContextProvider(fiber)) {
+      return;
+    }
 
-var ReactFiberHostContext = function(config, stack) {
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
 
-  var contextStackCursor = createCursor(NO_CONTEXT);
-  var contextFiberStackCursor = createCursor(NO_CONTEXT);
-  var rootInstanceStackCursor = createCursor(NO_CONTEXT);
+  function popTopLevelContextObject(fiber) {
+    pop(didPerformWorkStackCursor, fiber);
+    pop(contextStackCursor, fiber);
+  }
 
-  function requiredContext(c) {
+  function pushTopLevelContextObject(fiber, context, didChange) {
     invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug " +
-        "in React. Please file an issue."
+      contextStackCursor.cursor == null,
+      "Unexpected context found on stack. " +
+        "This error is likely caused by a bug in React. Please file an issue."
     );
-    return c;
-  }
 
-  function getRootHostContainer() {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    return rootInstance;
+    push(contextStackCursor, context, fiber);
+    push(didPerformWorkStackCursor, didChange, fiber);
   }
 
-  function pushHostContainer(fiber, nextRootInstance) {
-    // Push current root instance onto the stack;
-    // This allows us to reset root when portals are popped.
-    push(rootInstanceStackCursor, nextRootInstance, fiber);
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
+  function processChildContext(fiber, parentContext) {
+    var instance = fiber.stateNode;
+    var childContextTypes = fiber.type.childContextTypes;
 
-    // Finally, we need to push the host context to the stack.
-    // However, we can't just call getRootHostContext() and push it because
-    // we'd have a different number of entries on the stack depending on
-    // whether getRootHostContext() throws somewhere in renderer code or not.
-    // So we push an empty value first. This lets us safely unwind on errors.
-    push(contextStackCursor, NO_CONTEXT, fiber);
-    var nextRootContext = getRootHostContext(nextRootInstance);
-    // Now that we know this function doesn't throw, replace it.
-    pop(contextStackCursor, fiber);
-    push(contextStackCursor, nextRootContext, fiber);
-  }
+    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
+    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
+    if (typeof instance.getChildContext !== "function") {
+      {
+        var componentName = getComponentName(fiber) || "Unknown";
 
-  function popHostContainer(fiber) {
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
-    pop(rootInstanceStackCursor, fiber);
+        if (!warnedAboutMissingGetChildContext[componentName]) {
+          warnedAboutMissingGetChildContext[componentName] = true;
+          warning(
+            false,
+            "%s.childContextTypes is specified but there is no getChildContext() method " +
+              "on the instance. You can either define getChildContext() on %s or remove " +
+              "childContextTypes from it.",
+            componentName,
+            componentName
+          );
+        }
+      }
+      return parentContext;
+    }
+
+    var childContext = void 0;
+    {
+      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
+    }
+    startPhaseTimer(fiber, "getChildContext");
+    childContext = instance.getChildContext();
+    stopPhaseTimer();
+    {
+      ReactDebugCurrentFiber.setCurrentPhase(null);
+    }
+    for (var contextKey in childContext) {
+      invariant(
+        contextKey in childContextTypes,
+        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+        getComponentName(fiber) || "Unknown",
+        contextKey
+      );
+    }
+    {
+      var name = getComponentName(fiber) || "Unknown";
+      checkPropTypes(
+        childContextTypes,
+        childContext,
+        "child context",
+        name,
+        // In practice, there is one case in which we won't get a stack. It's when
+        // somebody calls unstable_renderSubtreeIntoContainer() and we process
+        // context from the parent component instance. The stack will be missing
+        // because it's outside of the reconciliation, and so the pointer has not
+        // been set. This is rare and doesn't matter. We'll also remove that API.
+        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      );
+    }
+
+    return Object.assign({}, parentContext, childContext);
   }
 
-  function getHostContext() {
-    var context = requiredContext(contextStackCursor.current);
-    return context;
+  function pushContextProvider(workInProgress) {
+    if (!isContextProvider(workInProgress)) {
+      return false;
+    }
+
+    var instance = workInProgress.stateNode;
+    // We push the context as early as possible to ensure stack integrity.
+    // If the instance does not exist yet, we will push null at first,
+    // and replace it on the stack later when invalidating the context.
+    var memoizedMergedChildContext =
+      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+      emptyObject;
+
+    // Remember the parent context so we can merge with it later.
+    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
+    previousContext = contextStackCursor.current;
+    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
+    push(
+      didPerformWorkStackCursor,
+      didPerformWorkStackCursor.current,
+      workInProgress
+    );
+
+    return true;
   }
 
-  function pushHostContext(fiber) {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    var context = requiredContext(contextStackCursor.current);
-    var nextContext = getChildHostContext(context, fiber.type, rootInstance);
+  function invalidateContextProvider(workInProgress, didChange) {
+    var instance = workInProgress.stateNode;
+    invariant(
+      instance,
+      "Expected to have an instance by this point. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+
+    if (didChange) {
+      // Merge parent and own context.
+      // Skip this if we're not updating due to sCU.
+      // This avoids unnecessarily recomputing memoized values.
+      var mergedContext = processChildContext(workInProgress, previousContext);
+      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
 
-    // Don't push this Fiber's context unless it's unique.
-    if (context === nextContext) {
-      return;
+      // Replace the old (or empty) context with the new one.
+      // It is important to unwind the context in the reverse order.
+      pop(didPerformWorkStackCursor, workInProgress);
+      pop(contextStackCursor, workInProgress);
+      // Now push the new context and mark that it has changed.
+      push(contextStackCursor, mergedContext, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
+    } else {
+      pop(didPerformWorkStackCursor, workInProgress);
+      push(didPerformWorkStackCursor, didChange, workInProgress);
     }
-
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
-    push(contextStackCursor, nextContext, fiber);
   }
 
-  function popHostContext(fiber) {
-    // Do not pop unless this Fiber provided the current context.
-    // pushHostContext() only pushes Fibers that provide unique contexts.
-    if (contextFiberStackCursor.current !== fiber) {
-      return;
-    }
+  function findCurrentUnmaskedContext(fiber) {
+    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
+    // makes sense elsewhere
+    invariant(
+      isFiberMounted(fiber) && fiber.tag === ClassComponent,
+      "Expected subtree parent to be a mounted class component. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
 
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
+    var node = fiber;
+    while (node.tag !== HostRoot) {
+      if (isContextProvider(node)) {
+        return node.stateNode.__reactInternalMemoizedMergedChildContext;
+      }
+      var parent = node.return;
+      invariant(
+        parent,
+        "Found unexpected detached subtree parent. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
+      node = parent;
+    }
+    return node.stateNode.context;
   }
 
   return {
-    getHostContext: getHostContext,
-    getRootHostContainer: getRootHostContainer,
-    popHostContainer: popHostContainer,
-    popHostContext: popHostContext,
-    pushHostContainer: pushHostContainer,
-    pushHostContext: pushHostContext
+    getUnmaskedContext: getUnmaskedContext,
+    cacheContext: cacheContext,
+    getMaskedContext: getMaskedContext,
+    hasContextChanged: hasContextChanged,
+    isContextConsumer: isContextConsumer,
+    isContextProvider: isContextProvider,
+    popContextProvider: popContextProvider,
+    popTopLevelContextObject: popTopLevelContextObject,
+    pushTopLevelContextObject: pushTopLevelContextObject,
+    processChildContext: processChildContext,
+    pushContextProvider: pushContextProvider,
+    invalidateContextProvider: invalidateContextProvider,
+    findCurrentUnmaskedContext: findCurrentUnmaskedContext
   };
 };
 
-var ReactFiberHydrationContext = function(config) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    hydration = config.hydration;
+var ReactFiberNewContext = function(stack, isPrimaryRenderer) {
+  var createCursor = stack.createCursor,
+    push = stack.push,
+    pop = stack.pop;
 
-  // If this doesn't have hydration mode.
+  var providerCursor = createCursor(null);
+  var valueCursor = createCursor(null);
+  var changedBitsCursor = createCursor(0);
 
-  if (!hydration) {
-    return {
-      enterHydrationState: function() {
-        return false;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostTextInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      popHydrationState: function(fiber) {
-        return false;
-      }
-    };
+  var rendererSigil = void 0;
+  {
+    // Use this to detect multiple renderers using the same context
+    rendererSigil = {};
   }
 
-  var canHydrateInstance = hydration.canHydrateInstance,
-    canHydrateTextInstance = hydration.canHydrateTextInstance,
-    getNextHydratableSibling = hydration.getNextHydratableSibling,
-    getFirstHydratableChild = hydration.getFirstHydratableChild,
-    hydrateInstance = hydration.hydrateInstance,
-    hydrateTextInstance = hydration.hydrateTextInstance,
-    didNotMatchHydratedContainerTextInstance =
-      hydration.didNotMatchHydratedContainerTextInstance,
-    didNotMatchHydratedTextInstance = hydration.didNotMatchHydratedTextInstance,
-    didNotHydrateContainerInstance = hydration.didNotHydrateContainerInstance,
-    didNotHydrateInstance = hydration.didNotHydrateInstance,
-    didNotFindHydratableContainerInstance =
-      hydration.didNotFindHydratableContainerInstance,
-    didNotFindHydratableContainerTextInstance =
-      hydration.didNotFindHydratableContainerTextInstance,
-    didNotFindHydratableInstance = hydration.didNotFindHydratableInstance,
-    didNotFindHydratableTextInstance =
-      hydration.didNotFindHydratableTextInstance;
-
-  // The deepest Fiber on the stack involved in a hydration context.
-  // This may have been an insertion or a hydration.
+  function pushProvider(providerFiber) {
+    var context = providerFiber.type._context;
 
-  var hydrationParentFiber = null;
-  var nextHydratableInstance = null;
-  var isHydrating = false;
+    if (isPrimaryRenderer) {
+      push(changedBitsCursor, context._changedBits, providerFiber);
+      push(valueCursor, context._currentValue, providerFiber);
+      push(providerCursor, providerFiber, providerFiber);
 
-  function enterHydrationState(fiber) {
-    var parentInstance = fiber.stateNode.containerInfo;
-    nextHydratableInstance = getFirstHydratableChild(parentInstance);
-    hydrationParentFiber = fiber;
-    isHydrating = true;
-    return true;
-  }
+      context._currentValue = providerFiber.pendingProps.value;
+      context._changedBits = providerFiber.stateNode;
+      {
+        !(
+          context._currentRenderer === null ||
+          context._currentRenderer === rendererSigil
+        )
+          ? warning(
+              false,
+              "Detected multiple renderers concurrently rendering the " +
+                "same context provider. This is currently unsupported."
+            )
+          : void 0;
+        context._currentRenderer = rendererSigil;
+      }
+    } else {
+      push(changedBitsCursor, context._changedBits2, providerFiber);
+      push(valueCursor, context._currentValue2, providerFiber);
+      push(providerCursor, providerFiber, providerFiber);
 
-  function deleteHydratableInstance(returnFiber, instance) {
-    {
-      switch (returnFiber.tag) {
-        case HostRoot:
-          didNotHydrateContainerInstance(
-            returnFiber.stateNode.containerInfo,
-            instance
-          );
-          break;
-        case HostComponent:
-          didNotHydrateInstance(
-            returnFiber.type,
-            returnFiber.memoizedProps,
-            returnFiber.stateNode,
-            instance
-          );
-          break;
+      context._currentValue2 = providerFiber.pendingProps.value;
+      context._changedBits2 = providerFiber.stateNode;
+      {
+        !(
+          context._currentRenderer2 === null ||
+          context._currentRenderer2 === rendererSigil
+        )
+          ? warning(
+              false,
+              "Detected multiple renderers concurrently rendering the " +
+                "same context provider. This is currently unsupported."
+            )
+          : void 0;
+        context._currentRenderer2 = rendererSigil;
       }
     }
+  }
 
-    var childToDelete = createFiberFromHostInstanceForDeletion();
-    childToDelete.stateNode = instance;
-    childToDelete["return"] = returnFiber;
-    childToDelete.effectTag = Deletion;
+  function popProvider(providerFiber) {
+    var changedBits = changedBitsCursor.current;
+    var currentValue = valueCursor.current;
 
-    // This might seem like it belongs on progressedFirstDeletion. However,
-    // these children are not part of the reconciliation list of children.
-    // Even if we abort and rereconcile the children, that will try to hydrate
-    // again and the nodes are still in the host tree so these will be
-    // recreated.
-    if (returnFiber.lastEffect !== null) {
-      returnFiber.lastEffect.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
+    pop(providerCursor, providerFiber);
+    pop(valueCursor, providerFiber);
+    pop(changedBitsCursor, providerFiber);
+
+    var context = providerFiber.type._context;
+    if (isPrimaryRenderer) {
+      context._currentValue = currentValue;
+      context._changedBits = changedBits;
     } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+      context._currentValue2 = currentValue;
+      context._changedBits2 = changedBits;
     }
   }
 
-  function insertNonHydratedInstance(returnFiber, fiber) {
-    fiber.effectTag |= Placement;
-    {
-      switch (returnFiber.tag) {
-        case HostRoot: {
-          var parentContainer = returnFiber.stateNode.containerInfo;
-          switch (fiber.tag) {
-            case HostComponent:
-              var type = fiber.type;
-              var props = fiber.pendingProps;
-              didNotFindHydratableContainerInstance(
-                parentContainer,
-                type,
-                props
-              );
-              break;
-            case HostText:
-              var text = fiber.pendingProps;
-              didNotFindHydratableContainerTextInstance(parentContainer, text);
-              break;
-          }
-          break;
-        }
-        case HostComponent: {
-          var parentType = returnFiber.type;
-          var parentProps = returnFiber.memoizedProps;
-          var parentInstance = returnFiber.stateNode;
-          switch (fiber.tag) {
-            case HostComponent:
-              var _type = fiber.type;
-              var _props = fiber.pendingProps;
-              didNotFindHydratableInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _type,
-                _props
-              );
-              break;
-            case HostText:
-              var _text = fiber.pendingProps;
-              didNotFindHydratableTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _text
-              );
-              break;
-          }
-          break;
-        }
-        default:
-          return;
-      }
-    }
+  function getContextCurrentValue(context) {
+    return isPrimaryRenderer ? context._currentValue : context._currentValue2;
+  }
+
+  function getContextChangedBits(context) {
+    return isPrimaryRenderer ? context._changedBits : context._changedBits2;
+  }
+
+  return {
+    pushProvider: pushProvider,
+    popProvider: popProvider,
+    getContextCurrentValue: getContextCurrentValue,
+    getContextChangedBits: getContextChangedBits
+  };
+};
+
+var ReactFiberStack = function() {
+  var valueStack = [];
+
+  var fiberStack = void 0;
+
+  {
+    fiberStack = [];
   }
 
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case HostComponent: {
-        var type = fiber.type;
-        var props = fiber.pendingProps;
-        var instance = canHydrateInstance(nextInstance, type, props);
-        if (instance !== null) {
-          fiber.stateNode = instance;
-          return true;
-        }
-        return false;
-      }
-      case HostText: {
-        var text = fiber.pendingProps;
-        var textInstance = canHydrateTextInstance(nextInstance, text);
-        if (textInstance !== null) {
-          fiber.stateNode = textInstance;
-          return true;
-        }
-        return false;
-      }
-      default:
-        return false;
-    }
+  var index = -1;
+
+  function createCursor(defaultValue) {
+    return {
+      current: defaultValue
+    };
   }
 
-  function tryToClaimNextHydratableInstance(fiber) {
-    if (!isHydrating) {
-      return;
-    }
-    var nextInstance = nextHydratableInstance;
-    if (!nextInstance) {
-      // Nothing to hydrate. Make it an insertion.
-      insertNonHydratedInstance(hydrationParentFiber, fiber);
-      isHydrating = false;
-      hydrationParentFiber = fiber;
+  function isEmpty() {
+    return index === -1;
+  }
+
+  function pop(cursor, fiber) {
+    if (index < 0) {
+      {
+        warning(false, "Unexpected pop.");
+      }
       return;
     }
-    if (!tryHydrate(fiber, nextInstance)) {
-      // If we can't hydrate this instance let's try the next one.
-      // We use this as a heuristic. It's based on intuition and not data so it
-      // might be flawed or unnecessary.
-      nextInstance = getNextHydratableSibling(nextInstance);
-      if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-        // Nothing to hydrate. Make it an insertion.
-        insertNonHydratedInstance(hydrationParentFiber, fiber);
-        isHydrating = false;
-        hydrationParentFiber = fiber;
-        return;
+
+    {
+      if (fiber !== fiberStack[index]) {
+        warning(false, "Unexpected Fiber popped.");
       }
-      // We matched the next one, we'll now assume that the first one was
-      // superfluous and we'll delete it. Since we can't eagerly delete it
-      // we'll have to schedule a deletion. To do that, this node needs a dummy
-      // fiber associated with it.
-      deleteHydratableInstance(hydrationParentFiber, nextHydratableInstance);
     }
-    hydrationParentFiber = fiber;
-    nextHydratableInstance = getFirstHydratableChild(nextInstance);
+
+    cursor.current = valueStack[index];
+
+    valueStack[index] = null;
+
+    {
+      fiberStack[index] = null;
+    }
+
+    index--;
   }
 
-  function prepareToHydrateHostInstance(
-    fiber,
-    rootContainerInstance,
-    hostContext
-  ) {
-    var instance = fiber.stateNode;
-    var updatePayload = hydrateInstance(
-      instance,
-      fiber.type,
-      fiber.memoizedProps,
-      rootContainerInstance,
-      hostContext,
-      fiber
-    );
-    // TODO: Type this specific to this type of component.
-    fiber.updateQueue = updatePayload;
-    // If the update payload indicates that there is a change or if there
-    // is a new ref we mark this as an update.
-    if (updatePayload !== null) {
-      return true;
+  function push(cursor, value, fiber) {
+    index++;
+
+    valueStack[index] = cursor.current;
+
+    {
+      fiberStack[index] = fiber;
     }
-    return false;
+
+    cursor.current = value;
   }
 
-  function prepareToHydrateHostTextInstance(fiber) {
-    var textInstance = fiber.stateNode;
-    var textContent = fiber.memoizedProps;
-    var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
+  function checkThatStackIsEmpty() {
     {
-      if (shouldUpdate) {
-        // We assume that prepareToHydrateHostTextInstance is called in a context where the
-        // hydration parent is the parent host component of this host text.
-        var returnFiber = hydrationParentFiber;
-        if (returnFiber !== null) {
-          switch (returnFiber.tag) {
-            case HostRoot: {
-              var parentContainer = returnFiber.stateNode.containerInfo;
-              didNotMatchHydratedContainerTextInstance(
-                parentContainer,
-                textInstance,
-                textContent
-              );
-              break;
-            }
-            case HostComponent: {
-              var parentType = returnFiber.type;
-              var parentProps = returnFiber.memoizedProps;
-              var parentInstance = returnFiber.stateNode;
-              didNotMatchHydratedTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                textInstance,
-                textContent
-              );
-              break;
-            }
-          }
-        }
+      if (index !== -1) {
+        warning(
+          false,
+          "Expected an empty stack. Something was not reset properly."
+        );
       }
     }
-    return shouldUpdate;
   }
 
-  function popToNextHostParent(fiber) {
-    var parent = fiber["return"];
-    while (
-      parent !== null &&
-      parent.tag !== HostComponent &&
-      parent.tag !== HostRoot
-    ) {
-      parent = parent["return"];
+  function resetStackAfterFatalErrorInDev() {
+    {
+      index = -1;
+      valueStack.length = 0;
+      fiberStack.length = 0;
     }
-    hydrationParentFiber = parent;
   }
 
-  function popHydrationState(fiber) {
-    if (fiber !== hydrationParentFiber) {
-      // We're deeper than the current hydration context, inside an inserted
-      // tree.
-      return false;
-    }
-    if (!isHydrating) {
-      // If we're not currently hydrating but we're in a hydration context, then
-      // we were an insertion and now need to pop up reenter hydration of our
-      // siblings.
-      popToNextHostParent(fiber);
-      isHydrating = true;
-      return false;
-    }
+  return {
+    createCursor: createCursor,
+    isEmpty: isEmpty,
+    pop: pop,
+    push: push,
+    checkThatStackIsEmpty: checkThatStackIsEmpty,
+    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
+  };
+};
 
-    var type = fiber.type;
+var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError = ReactErrorUtils.hasCaughtError;
+var clearCaughtError = ReactErrorUtils.clearCaughtError;
 
-    // If we have any remaining hydratable nodes, we need to delete them now.
-    // We only do this deeper than head and body since they tend to have random
-    // other nodes in them. We also ignore components with pure text content in
-    // side of them.
-    // TODO: Better heuristic.
-    if (
-      fiber.tag !== HostComponent ||
-      (type !== "head" &&
-        type !== "body" &&
-        !shouldSetTextContent(type, fiber.memoizedProps))
-    ) {
-      var nextInstance = nextHydratableInstance;
-      while (nextInstance) {
-        deleteHydratableInstance(fiber, nextInstance);
-        nextInstance = getNextHydratableSibling(nextInstance);
-      }
+var didWarnAboutStateTransition = void 0;
+var didWarnSetStateChildContext = void 0;
+var warnAboutUpdateOnUnmounted = void 0;
+var warnAboutInvalidUpdates = void 0;
+
+{
+  didWarnAboutStateTransition = false;
+  didWarnSetStateChildContext = false;
+  var didWarnStateUpdateForUnmountedComponent = {};
+
+  warnAboutUpdateOnUnmounted = function(fiber) {
+    // We show the whole stack but dedupe on the top component's name because
+    // the problematic code almost always lies inside that component.
+    var componentName = getComponentName(fiber) || "ReactClass";
+    if (didWarnStateUpdateForUnmountedComponent[componentName]) {
+      return;
+    }
+    warning(
+      false,
+      "Can't call setState (or forceUpdate) on an unmounted component. This " +
+        "is a no-op, but it indicates a memory leak in your application. To " +
+        "fix, cancel all subscriptions and asynchronous tasks in the " +
+        "componentWillUnmount method.%s",
+      getStackAddendumByWorkInProgressFiber(fiber)
+    );
+    didWarnStateUpdateForUnmountedComponent[componentName] = true;
+  };
+
+  warnAboutInvalidUpdates = function(instance) {
+    switch (ReactDebugCurrentFiber.phase) {
+      case "getChildContext":
+        if (didWarnSetStateChildContext) {
+          return;
+        }
+        warning(
+          false,
+          "setState(...): Cannot call setState() inside getChildContext()"
+        );
+        didWarnSetStateChildContext = true;
+        break;
+      case "render":
+        if (didWarnAboutStateTransition) {
+          return;
+        }
+        warning(
+          false,
+          "Cannot update during an existing state transition (such as within " +
+            "`render` or another component's constructor). Render methods should " +
+            "be a pure function of props and state; constructor side-effects are " +
+            "an anti-pattern, but can be moved to `componentWillMount`."
+        );
+        didWarnAboutStateTransition = true;
+        break;
     }
+  };
+}
 
-    popToNextHostParent(fiber);
-    nextHydratableInstance = hydrationParentFiber
-      ? getNextHydratableSibling(fiber.stateNode)
-      : null;
-    return true;
-  }
+var ReactFiberScheduler = function(config) {
+  var now = config.now,
+    scheduleDeferredCallback = config.scheduleDeferredCallback,
+    cancelDeferredCallback = config.cancelDeferredCallback,
+    prepareForCommit = config.prepareForCommit,
+    resetAfterCommit = config.resetAfterCommit;
 
-  function resetHydrationState() {
-    hydrationParentFiber = null;
-    nextHydratableInstance = null;
-    isHydrating = false;
-  }
+  var stack = ReactFiberStack();
+  var hostContext = ReactFiberHostContext(config, stack);
+  var legacyContext = ReactFiberLegacyContext(stack);
+  var newContext = ReactFiberNewContext(stack, config.isPrimaryRenderer);
+  var profilerTimer = createProfilerTimer(now);
+  var popHostContext = hostContext.popHostContext,
+    popHostContainer = hostContext.popHostContainer;
+  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popLegacyContextProvider = legacyContext.popContextProvider;
+  var popProvider = newContext.popProvider;
 
-  return {
-    enterHydrationState: enterHydrationState,
-    resetHydrationState: resetHydrationState,
-    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
-    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
-    popHydrationState: popHydrationState
-  };
-};
+  var hydrationContext = ReactFiberHydrationContext(config);
 
-// This lets us hook into Fiber to debug what it's doing.
-// See https://github.com/facebook/react/pull/8033.
-// This is not part of the public API, not even for React DevTools.
-// You may only inject a debugTool if you work on React Fiber itself.
-var ReactFiberInstrumentation = {
-  debugTool: null
-};
+  var _ReactFiberBeginWork = ReactFiberBeginWork(
+      config,
+      hostContext,
+      legacyContext,
+      newContext,
+      hydrationContext,
+      scheduleWork,
+      computeExpirationForFiber,
+      profilerTimer,
+      recalculateCurrentTime
+    ),
+    beginWork = _ReactFiberBeginWork.beginWork;
 
-var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
+  var _ReactFiberCompleteWo = ReactFiberCompleteWork(
+      config,
+      hostContext,
+      legacyContext,
+      newContext,
+      hydrationContext,
+      profilerTimer
+    ),
+    completeWork = _ReactFiberCompleteWo.completeWork;
 
-var warnedAboutMissingGetChildContext = void 0;
+  var _ReactFiberUnwindWork = ReactFiberUnwindWork(
+      config,
+      hostContext,
+      legacyContext,
+      newContext,
+      scheduleWork,
+      computeExpirationForFiber,
+      recalculateCurrentTime,
+      markLegacyErrorBoundaryAsFailed,
+      isAlreadyFailedLegacyErrorBoundary,
+      onUncaughtError,
+      profilerTimer,
+      suspendRoot,
+      retrySuspendedRoot
+    ),
+    throwException = _ReactFiberUnwindWork.throwException,
+    unwindWork = _ReactFiberUnwindWork.unwindWork,
+    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork,
+    createRootErrorUpdate = _ReactFiberUnwindWork.createRootErrorUpdate,
+    createClassErrorUpdate = _ReactFiberUnwindWork.createClassErrorUpdate;
 
-{
-  warnedAboutMissingGetChildContext = {};
-}
+  var _ReactFiberCommitWork = ReactFiberCommitWork(
+      config,
+      onCommitPhaseError,
+      scheduleWork,
+      computeExpirationForFiber,
+      markLegacyErrorBoundaryAsFailed,
+      recalculateCurrentTime
+    ),
+    commitBeforeMutationLifeCycles =
+      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
+    commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
+    commitPlacement = _ReactFiberCommitWork.commitPlacement,
+    commitDeletion = _ReactFiberCommitWork.commitDeletion,
+    commitWork = _ReactFiberCommitWork.commitWork,
+    commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
+    commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
+    commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
 
-var ReactFiberLegacyContext = function(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
+  var checkActualRenderTimeStackEmpty =
+      profilerTimer.checkActualRenderTimeStackEmpty,
+    pauseActualRenderTimerIfRunning =
+      profilerTimer.pauseActualRenderTimerIfRunning,
+    recordElapsedBaseRenderTimeIfRunning =
+      profilerTimer.recordElapsedBaseRenderTimeIfRunning,
+    resetActualRenderTimer = profilerTimer.resetActualRenderTimer,
+    resumeActualRenderTimerIfPaused =
+      profilerTimer.resumeActualRenderTimerIfPaused,
+    startBaseRenderTimer = profilerTimer.startBaseRenderTimer,
+    stopBaseRenderTimerIfRunning = profilerTimer.stopBaseRenderTimerIfRunning;
 
-  // A cursor to the current merged context object on the stack.
+  // Represents the current time in ms.
 
-  var contextStackCursor = createCursor(emptyObject);
-  // A cursor to a boolean indicating whether the context has changed.
-  var didPerformWorkStackCursor = createCursor(false);
-  // Keep track of the previous context object that was on the stack.
-  // We use this to get access to the parent context after we have already
-  // pushed the next context provider, and now need to merge their contexts.
-  var previousContext = emptyObject;
+  var originalStartTimeMs = now();
+  var mostRecentCurrentTime = msToExpirationTime(0);
+  var mostRecentCurrentTimeMs = originalStartTimeMs;
 
-  function getUnmaskedContext(workInProgress) {
-    var hasOwnContext = isContextProvider(workInProgress);
-    if (hasOwnContext) {
-      // If the fiber is a context provider itself, when we read its context
-      // we have already pushed its own child context on the stack. A context
-      // provider should not "see" its own child context. Therefore we read the
-      // previous (parent) context instead for a context provider.
-      return previousContext;
-    }
-    return contextStackCursor.current;
-  }
+  // Used to ensure computeUniqueAsyncExpiration is monotonically increases.
+  var lastUniqueAsyncExpiration = 0;
 
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    var instance = workInProgress.stateNode;
-    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
-  }
+  // Represents the expiration time that incoming updates should use. (If this
+  // is NoWork, use the default strategy: async updates in async mode, sync
+  // updates in sync mode.)
+  var expirationContext = NoWork;
 
-  function getMaskedContext(workInProgress, unmaskedContext) {
-    var type = workInProgress.type;
-    var contextTypes = type.contextTypes;
-    if (!contextTypes) {
-      return emptyObject;
-    }
+  var isWorking = false;
 
-    // Avoid recreating masked context unless unmasked context has changed.
-    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
-    // This may trigger infinite loops if componentWillReceiveProps calls setState.
-    var instance = workInProgress.stateNode;
-    if (
-      instance &&
-      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-    ) {
-      return instance.__reactInternalMemoizedMaskedChildContext;
-    }
+  // The next work in progress fiber that we're currently working on.
+  var nextUnitOfWork = null;
+  var nextRoot = null;
+  // The time at which we're currently rendering work.
+  var nextRenderExpirationTime = NoWork;
+  var nextLatestTimeoutMs = -1;
+  var nextRenderIsExpired = false;
 
-    var context = {};
-    for (var key in contextTypes) {
-      context[key] = unmaskedContext[key];
-    }
+  // The next fiber with an effect that we're currently committing.
+  var nextEffect = null;
 
-    {
-      var name = getComponentName(workInProgress) || "Unknown";
-      checkPropTypes(
-        contextTypes,
-        context,
-        "context",
-        name,
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-      );
-    }
+  var isCommitting = false;
 
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // Context is created before the class component is instantiated so check for instance.
-    if (instance) {
-      cacheContext(workInProgress, unmaskedContext, context);
-    }
+  var isRootReadyForCommit = false;
 
-    return context;
-  }
+  var legacyErrorBoundariesThatAlreadyFailed = null;
 
-  function hasContextChanged() {
-    return didPerformWorkStackCursor.current;
-  }
+  // Used for performance tracking.
+  var interruptedBy = null;
 
-  function isContextConsumer(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
-  }
+  var stashedWorkInProgressProperties = void 0;
+  var replayUnitOfWork = void 0;
+  var isReplayingFailedUnitOfWork = void 0;
+  var originalReplayError = void 0;
+  var rethrowOriginalError = void 0;
+  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+    stashedWorkInProgressProperties = null;
+    isReplayingFailedUnitOfWork = false;
+    originalReplayError = null;
+    replayUnitOfWork = function(failedUnitOfWork, thrownValue, isAsync) {
+      if (
+        thrownValue !== null &&
+        typeof thrownValue === "object" &&
+        typeof thrownValue.then === "function"
+      ) {
+        // Don't replay promises. Treat everything else like an error.
+        // TODO: Need to figure out a different strategy if/when we add
+        // support for catching other types.
+        return;
+      }
 
-  function isContextProvider(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+      // Restore the original state of the work-in-progress
+      assignFiberPropertiesInDEV(
+        failedUnitOfWork,
+        stashedWorkInProgressProperties
+      );
+      switch (failedUnitOfWork.tag) {
+        case HostRoot:
+          popHostContainer(failedUnitOfWork);
+          popTopLevelLegacyContextObject(failedUnitOfWork);
+          break;
+        case HostComponent:
+          popHostContext(failedUnitOfWork);
+          break;
+        case ClassComponent:
+          popLegacyContextProvider(failedUnitOfWork);
+          break;
+        case HostPortal:
+          popHostContainer(failedUnitOfWork);
+          break;
+        case ContextProvider:
+          popProvider(failedUnitOfWork);
+          break;
+      }
+      // Replay the begin phase.
+      isReplayingFailedUnitOfWork = true;
+      originalReplayError = thrownValue;
+      invokeGuardedCallback$2(null, workLoop, null, isAsync);
+      isReplayingFailedUnitOfWork = false;
+      originalReplayError = null;
+      if (hasCaughtError()) {
+        clearCaughtError();
+
+        if (enableProfilerTimer) {
+          // Stop "base" render timer again (after the re-thrown error).
+          stopBaseRenderTimerIfRunning();
+        }
+      } else {
+        // If the begin phase did not fail the second time, set this pointer
+        // back to the original value.
+        nextUnitOfWork = failedUnitOfWork;
+      }
+    };
+    rethrowOriginalError = function() {
+      throw originalReplayError;
+    };
   }
 
-  function popContextProvider(fiber) {
-    if (!isContextProvider(fiber)) {
-      return;
+  function resetStack() {
+    if (nextUnitOfWork !== null) {
+      var interruptedWork = nextUnitOfWork.return;
+      while (interruptedWork !== null) {
+        unwindInterruptedWork(interruptedWork);
+        interruptedWork = interruptedWork.return;
+      }
     }
 
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
-  }
+    {
+      ReactStrictModeWarnings.discardPendingWarnings();
+      stack.checkThatStackIsEmpty();
+    }
 
-  function popTopLevelContextObject(fiber) {
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
+    nextRoot = null;
+    nextRenderExpirationTime = NoWork;
+    nextLatestTimeoutMs = -1;
+    nextRenderIsExpired = false;
+    nextUnitOfWork = null;
+
+    isRootReadyForCommit = false;
   }
 
-  function pushTopLevelContextObject(fiber, context, didChange) {
-    invariant(
-      contextStackCursor.cursor == null,
-      "Unexpected context found on stack. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
+  function commitAllHostEffects() {
+    while (nextEffect !== null) {
+      {
+        ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
+      }
+      recordEffect();
 
-    push(contextStackCursor, context, fiber);
-    push(didPerformWorkStackCursor, didChange, fiber);
-  }
+      var effectTag = nextEffect.effectTag;
 
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode;
-    var childContextTypes = fiber.type.childContextTypes;
+      if (effectTag & ContentReset) {
+        commitResetTextContent(nextEffect);
+      }
 
-    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
-    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
-    if (typeof instance.getChildContext !== "function") {
-      {
-        var componentName = getComponentName(fiber) || "Unknown";
+      if (effectTag & Ref) {
+        var current = nextEffect.alternate;
+        if (current !== null) {
+          commitDetachRef(current);
+        }
+      }
 
-        if (!warnedAboutMissingGetChildContext[componentName]) {
-          warnedAboutMissingGetChildContext[componentName] = true;
-          warning(
-            false,
-            "%s.childContextTypes is specified but there is no getChildContext() method " +
-              "on the instance. You can either define getChildContext() on %s or remove " +
-              "childContextTypes from it.",
-            componentName,
-            componentName
-          );
+      // The following switch statement is only concerned about placement,
+      // updates, and deletions. To avoid needing to add a case for every
+      // possible bitmap value, we remove the secondary effects from the
+      // effect tag and switch on that value.
+      var primaryEffectTag = effectTag & (Placement | Update | Deletion);
+      switch (primaryEffectTag) {
+        case Placement: {
+          commitPlacement(nextEffect);
+          // Clear the "placement" from effect tag so that we know that this is inserted, before
+          // any life-cycles like componentDidMount gets called.
+          // TODO: findDOMNode doesn't rely on this any more but isMounted
+          // does and isMounted is deprecated anyway so we should be able
+          // to kill this.
+          nextEffect.effectTag &= ~Placement;
+          break;
+        }
+        case PlacementAndUpdate: {
+          // Placement
+          commitPlacement(nextEffect);
+          // Clear the "placement" from effect tag so that we know that this is inserted, before
+          // any life-cycles like componentDidMount gets called.
+          nextEffect.effectTag &= ~Placement;
+
+          // Update
+          var _current = nextEffect.alternate;
+          commitWork(_current, nextEffect);
+          break;
+        }
+        case Update: {
+          var _current2 = nextEffect.alternate;
+          commitWork(_current2, nextEffect);
+          break;
+        }
+        case Deletion: {
+          commitDeletion(nextEffect);
+          break;
         }
       }
-      return parentContext;
+      nextEffect = nextEffect.nextEffect;
     }
 
-    var childContext = void 0;
-    {
-      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
-    }
-    startPhaseTimer(fiber, "getChildContext");
-    childContext = instance.getChildContext();
-    stopPhaseTimer();
-    {
-      ReactDebugCurrentFiber.setCurrentPhase(null);
-    }
-    for (var contextKey in childContext) {
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
-      );
-    }
     {
-      var name = getComponentName(fiber) || "Unknown";
-      checkPropTypes(
-        childContextTypes,
-        childContext,
-        "child context",
-        name,
-        // In practice, there is one case in which we won't get a stack. It's when
-        // somebody calls unstable_renderSubtreeIntoContainer() and we process
-        // context from the parent component instance. The stack will be missing
-        // because it's outside of the reconciliation, and so the pointer has not
-        // been set. This is rare and doesn't matter. We'll also remove that API.
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-      );
-    }
-
-    return Object.assign({}, parentContext, childContext);
-  }
-
-  function pushContextProvider(workInProgress) {
-    if (!isContextProvider(workInProgress)) {
-      return false;
+      ReactDebugCurrentFiber.resetCurrentFiber();
     }
-
-    var instance = workInProgress.stateNode;
-    // We push the context as early as possible to ensure stack integrity.
-    // If the instance does not exist yet, we will push null at first,
-    // and replace it on the stack later when invalidating the context.
-    var memoizedMergedChildContext =
-      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-      emptyObject;
-
-    // Remember the parent context so we can merge with it later.
-    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
-    previousContext = contextStackCursor.current;
-    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
-    push(
-      didPerformWorkStackCursor,
-      didPerformWorkStackCursor.current,
-      workInProgress
-    );
-
-    return true;
   }
 
-  function invalidateContextProvider(workInProgress, didChange) {
-    var instance = workInProgress.stateNode;
-    invariant(
-      instance,
-      "Expected to have an instance by this point. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
+  function commitBeforeMutationLifecycles() {
+    while (nextEffect !== null) {
+      var effectTag = nextEffect.effectTag;
 
-    if (didChange) {
-      // Merge parent and own context.
-      // Skip this if we're not updating due to sCU.
-      // This avoids unnecessarily recomputing memoized values.
-      var mergedContext = processChildContext(workInProgress, previousContext);
-      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+      if (effectTag & Snapshot) {
+        recordEffect();
+        var current = nextEffect.alternate;
+        commitBeforeMutationLifeCycles(current, nextEffect);
+      }
 
-      // Replace the old (or empty) context with the new one.
-      // It is important to unwind the context in the reverse order.
-      pop(didPerformWorkStackCursor, workInProgress);
-      pop(contextStackCursor, workInProgress);
-      // Now push the new context and mark that it has changed.
-      push(contextStackCursor, mergedContext, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    } else {
-      pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
+      // Don't cleanup effects yet;
+      // This will be done by commitAllLifeCycles()
+      nextEffect = nextEffect.nextEffect;
     }
   }
 
-  function findCurrentUnmaskedContext(fiber) {
-    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
-    // makes sense elsewhere
-    invariant(
-      isFiberMounted(fiber) && fiber.tag === ClassComponent,
-      "Expected subtree parent to be a mounted class component. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
+  function commitAllLifeCycles(
+    finishedRoot,
+    currentTime,
+    committedExpirationTime
+  ) {
+    {
+      ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
 
-    var node = fiber;
-    while (node.tag !== HostRoot) {
-      if (isContextProvider(node)) {
-        return node.stateNode.__reactInternalMemoizedMergedChildContext;
+      if (warnAboutDeprecatedLifecycles) {
+        ReactStrictModeWarnings.flushPendingDeprecationWarnings();
       }
-      var parent = node["return"];
-      invariant(
-        parent,
-        "Found unexpected detached subtree parent. " +
-          "This error is likely caused by a bug in React. Please file an issue."
-      );
-      node = parent;
     }
-    return node.stateNode.context;
-  }
+    while (nextEffect !== null) {
+      var effectTag = nextEffect.effectTag;
 
-  return {
-    getUnmaskedContext: getUnmaskedContext,
-    cacheContext: cacheContext,
-    getMaskedContext: getMaskedContext,
-    hasContextChanged: hasContextChanged,
-    isContextConsumer: isContextConsumer,
-    isContextProvider: isContextProvider,
-    popContextProvider: popContextProvider,
-    popTopLevelContextObject: popTopLevelContextObject,
-    pushTopLevelContextObject: pushTopLevelContextObject,
-    processChildContext: processChildContext,
-    pushContextProvider: pushContextProvider,
-    invalidateContextProvider: invalidateContextProvider,
-    findCurrentUnmaskedContext: findCurrentUnmaskedContext
-  };
-};
+      if (effectTag & (Update | Callback)) {
+        recordEffect();
+        var current = nextEffect.alternate;
+        commitLifeCycles(
+          finishedRoot,
+          current,
+          nextEffect,
+          currentTime,
+          committedExpirationTime
+        );
+      }
 
-var ReactFiberNewContext = function(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
+      if (effectTag & Ref) {
+        recordEffect();
+        commitAttachRef(nextEffect);
+      }
 
-  var providerCursor = createCursor(null);
-  var valueCursor = createCursor(null);
-  var changedBitsCursor = createCursor(0);
+      var next = nextEffect.nextEffect;
+      // Ensure that we clean these up so that we don't accidentally keep them.
+      // I'm not actually sure this matters because we can't reset firstEffect
+      // and lastEffect since they're on every node, not just the effectful
+      // ones. So we have to clean everything as we reuse nodes anyway.
+      nextEffect.nextEffect = null;
+      // Ensure that we reset the effectTag here so that we can rely on effect
+      // tags to reason about the current life-cycle.
+      nextEffect = next;
+    }
+  }
 
-  var rendererSigil = void 0;
-  {
-    // Use this to detect multiple renderers using the same context
-    rendererSigil = {};
+  function isAlreadyFailedLegacyErrorBoundary(instance) {
+    return (
+      legacyErrorBoundariesThatAlreadyFailed !== null &&
+      legacyErrorBoundariesThatAlreadyFailed.has(instance)
+    );
   }
 
-  function pushProvider(providerFiber) {
-    var context = providerFiber.type._context;
+  function markLegacyErrorBoundaryAsFailed(instance) {
+    if (legacyErrorBoundariesThatAlreadyFailed === null) {
+      legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
+    } else {
+      legacyErrorBoundariesThatAlreadyFailed.add(instance);
+    }
+  }
+
+  function commitRoot(finishedWork) {
+    isWorking = true;
+    isCommitting = true;
+    startCommitTimer();
 
-    push(changedBitsCursor, context._changedBits, providerFiber);
-    push(valueCursor, context._currentValue, providerFiber);
-    push(providerCursor, providerFiber, providerFiber);
+    var root = finishedWork.stateNode;
+    invariant(
+      root.current !== finishedWork,
+      "Cannot commit the same tree as before. This is probably a bug " +
+        "related to the return field. This error is likely caused by a bug " +
+        "in React. Please file an issue."
+    );
+    var committedExpirationTime = root.pendingCommitExpirationTime;
+    invariant(
+      committedExpirationTime !== NoWork,
+      "Cannot commit an incomplete root. This error is likely caused by a " +
+        "bug in React. Please file an issue."
+    );
+    root.pendingCommitExpirationTime = NoWork;
 
-    context._currentValue = providerFiber.pendingProps.value;
-    context._changedBits = providerFiber.stateNode;
+    var currentTime = recalculateCurrentTime();
 
-    {
-      !(
-        context._currentRenderer === null ||
-        context._currentRenderer === rendererSigil
-      )
-        ? warning(
-            false,
-            "Detected multiple renderers concurrently rendering the " +
-              "same context provider. This is currently unsupported."
-          )
-        : void 0;
-      context._currentRenderer = rendererSigil;
+    // Reset this to null before calling lifecycles
+    ReactCurrentOwner.current = null;
+
+    var firstEffect = void 0;
+    if (finishedWork.effectTag > PerformedWork) {
+      // A fiber's effect list consists only of its children, not itself. So if
+      // the root has an effect, we need to add it to the end of the list. The
+      // resulting list is the set that would belong to the root's parent, if
+      // it had one; that is, all the effects in the tree including the root.
+      if (finishedWork.lastEffect !== null) {
+        finishedWork.lastEffect.nextEffect = finishedWork;
+        firstEffect = finishedWork.firstEffect;
+      } else {
+        firstEffect = finishedWork;
+      }
+    } else {
+      // There is no effect on the root.
+      firstEffect = finishedWork.firstEffect;
     }
-  }
 
-  function popProvider(providerFiber) {
-    var changedBits = changedBitsCursor.current;
-    var currentValue = valueCursor.current;
+    prepareForCommit(root.containerInfo);
 
-    pop(providerCursor, providerFiber);
-    pop(valueCursor, providerFiber);
-    pop(changedBitsCursor, providerFiber);
+    // Invoke instances of getSnapshotBeforeUpdate before mutation.
+    nextEffect = firstEffect;
+    startCommitSnapshotEffectsTimer();
+    while (nextEffect !== null) {
+      var didError = false;
+      var error = void 0;
+      {
+        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
+        if (hasCaughtError()) {
+          didError = true;
+          error = clearCaughtError();
+        }
+      }
+      if (didError) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, error);
+        // Clean-up
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
+    stopCommitSnapshotEffectsTimer();
 
-    var context = providerFiber.type._context;
-    context._currentValue = currentValue;
-    context._changedBits = changedBits;
-  }
+    // Commit all the side-effects within a tree. We'll do this in two passes.
+    // The first pass performs all the host insertions, updates, deletions and
+    // ref unmounts.
+    nextEffect = firstEffect;
+    startCommitHostEffectsTimer();
+    while (nextEffect !== null) {
+      var _didError = false;
+      var _error = void 0;
+      {
+        invokeGuardedCallback$2(null, commitAllHostEffects, null);
+        if (hasCaughtError()) {
+          _didError = true;
+          _error = clearCaughtError();
+        }
+      }
+      if (_didError) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, _error);
+        // Clean-up
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
+    stopCommitHostEffectsTimer();
 
-  return {
-    pushProvider: pushProvider,
-    popProvider: popProvider
-  };
-};
+    resetAfterCommit(root.containerInfo);
 
-var ReactFiberStack = function() {
-  var valueStack = [];
+    // The work-in-progress tree is now the current tree. This must come after
+    // the first pass of the commit phase, so that the previous tree is still
+    // current during componentWillUnmount, but before the second pass, so that
+    // the finished work is current during componentDidMount/Update.
+    root.current = finishedWork;
 
-  var fiberStack = void 0;
+    // In the second pass we'll perform all life-cycles and ref callbacks.
+    // Life-cycles happen as a separate pass so that all placements, updates,
+    // and deletions in the entire tree have already been invoked.
+    // This pass also triggers any renderer-specific initial effects.
+    nextEffect = firstEffect;
+    startCommitLifeCyclesTimer();
+    while (nextEffect !== null) {
+      var _didError2 = false;
+      var _error2 = void 0;
+      {
+        invokeGuardedCallback$2(
+          null,
+          commitAllLifeCycles,
+          null,
+          root,
+          currentTime,
+          committedExpirationTime
+        );
+        if (hasCaughtError()) {
+          _didError2 = true;
+          _error2 = clearCaughtError();
+        }
+      }
+      if (_didError2) {
+        invariant(
+          nextEffect !== null,
+          "Should have next effect. This error is likely caused by a bug " +
+            "in React. Please file an issue."
+        );
+        onCommitPhaseError(nextEffect, _error2);
+        if (nextEffect !== null) {
+          nextEffect = nextEffect.nextEffect;
+        }
+      }
+    }
 
-  {
-    fiberStack = [];
-  }
+    if (enableProfilerTimer) {
+      {
+        checkActualRenderTimeStackEmpty();
+      }
+      resetActualRenderTimer();
+    }
 
-  var index = -1;
+    isCommitting = false;
+    isWorking = false;
+    stopCommitLifeCyclesTimer();
+    stopCommitTimer();
+    if (typeof onCommitRoot === "function") {
+      onCommitRoot(finishedWork.stateNode);
+    }
+    if (true && ReactFiberInstrumentation_1.debugTool) {
+      ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
+    }
 
-  function createCursor(defaultValue) {
-    return {
-      current: defaultValue
-    };
+    markCommittedPriorityLevels(root, currentTime, root.current.expirationTime);
+    var remainingTime = findNextPendingPriorityLevel(root);
+    if (remainingTime === NoWork) {
+      // If there's no remaining work, we can clear the set of already failed
+      // error boundaries.
+      legacyErrorBoundariesThatAlreadyFailed = null;
+    }
+    return remainingTime;
   }
 
-  function isEmpty() {
-    return index === -1;
-  }
+  function resetExpirationTime(workInProgress, renderTime) {
+    if (renderTime !== Never && workInProgress.expirationTime === Never) {
+      // The children of this component are hidden. Don't bubble their
+      // expiration times.
+      return;
+    }
 
-  function pop(cursor, fiber) {
-    if (index < 0) {
-      {
-        warning(false, "Unexpected pop.");
+    // Check for pending updates.
+    var newExpirationTime = NoWork;
+    switch (workInProgress.tag) {
+      case HostRoot:
+      case ClassComponent: {
+        var updateQueue = workInProgress.updateQueue;
+        if (updateQueue !== null) {
+          newExpirationTime = updateQueue.expirationTime;
+        }
       }
-      return;
     }
 
-    {
-      if (fiber !== fiberStack[index]) {
-        warning(false, "Unexpected Fiber popped.");
+    // TODO: Calls need to visit stateNode
+
+    // Bubble up the earliest expiration time.
+    // (And "base" render timers if that feature flag is enabled)
+    if (enableProfilerTimer && workInProgress.mode & ProfileMode) {
+      var treeBaseTime = workInProgress.selfBaseTime;
+      var child = workInProgress.child;
+      while (child !== null) {
+        treeBaseTime += child.treeBaseTime;
+        if (
+          child.expirationTime !== NoWork &&
+          (newExpirationTime === NoWork ||
+            newExpirationTime > child.expirationTime)
+        ) {
+          newExpirationTime = child.expirationTime;
+        }
+        child = child.sibling;
+      }
+      workInProgress.treeBaseTime = treeBaseTime;
+    } else {
+      var _child = workInProgress.child;
+      while (_child !== null) {
+        if (
+          _child.expirationTime !== NoWork &&
+          (newExpirationTime === NoWork ||
+            newExpirationTime > _child.expirationTime)
+        ) {
+          newExpirationTime = _child.expirationTime;
+        }
+        _child = _child.sibling;
       }
     }
 
-    cursor.current = valueStack[index];
+    workInProgress.expirationTime = newExpirationTime;
+  }
 
-    valueStack[index] = null;
+  function completeUnitOfWork(workInProgress) {
+    // Attempt to complete the current unit of work, then move to the
+    // next sibling. If there are no more siblings, return to the
+    // parent fiber.
+    while (true) {
+      // The current, flushed, state of this fiber is the alternate.
+      // Ideally nothing should rely on this, but relying on it here
+      // means that we don't need an additional field on the work in
+      // progress.
+      var current = workInProgress.alternate;
+      {
+        ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+      }
 
-    {
-      fiberStack[index] = null;
-    }
+      var returnFiber = workInProgress.return;
+      var siblingFiber = workInProgress.sibling;
 
-    index--;
-  }
+      if ((workInProgress.effectTag & Incomplete) === NoEffect) {
+        // This fiber completed.
+        var next = completeWork(
+          current,
+          workInProgress,
+          nextRenderExpirationTime
+        );
+        stopWorkTimer(workInProgress);
+        resetExpirationTime(workInProgress, nextRenderExpirationTime);
+        {
+          ReactDebugCurrentFiber.resetCurrentFiber();
+        }
 
-  function push(cursor, value, fiber) {
-    index++;
+        if (next !== null) {
+          stopWorkTimer(workInProgress);
+          if (true && ReactFiberInstrumentation_1.debugTool) {
+            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
+              workInProgress
+            );
+          }
+          // If completing this work spawned new work, do that next. We'll come
+          // back here again.
+          return next;
+        }
 
-    valueStack[index] = cursor.current;
+        if (
+          returnFiber !== null &&
+          // Do not append effects to parents if a sibling failed to complete
+          (returnFiber.effectTag & Incomplete) === NoEffect
+        ) {
+          // Append all the effects of the subtree and this fiber onto the effect
+          // list of the parent. The completion order of the children affects the
+          // side-effect order.
+          if (returnFiber.firstEffect === null) {
+            returnFiber.firstEffect = workInProgress.firstEffect;
+          }
+          if (workInProgress.lastEffect !== null) {
+            if (returnFiber.lastEffect !== null) {
+              returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
+            }
+            returnFiber.lastEffect = workInProgress.lastEffect;
+          }
 
-    {
-      fiberStack[index] = fiber;
-    }
+          // If this fiber had side-effects, we append it AFTER the children's
+          // side-effects. We can perform certain side-effects earlier if
+          // needed, by doing multiple passes over the effect list. We don't want
+          // to schedule our own side-effect on our own list because if end up
+          // reusing children we'll schedule this effect onto itself since we're
+          // at the end.
+          var effectTag = workInProgress.effectTag;
+          // Skip both NoWork and PerformedWork tags when creating the effect list.
+          // PerformedWork effect is read by React DevTools but shouldn't be committed.
+          if (effectTag > PerformedWork) {
+            if (returnFiber.lastEffect !== null) {
+              returnFiber.lastEffect.nextEffect = workInProgress;
+            } else {
+              returnFiber.firstEffect = workInProgress;
+            }
+            returnFiber.lastEffect = workInProgress;
+          }
+        }
 
-    cursor.current = value;
-  }
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+        }
 
-  function checkThatStackIsEmpty() {
-    {
-      if (index !== -1) {
-        warning(
-          false,
-          "Expected an empty stack. Something was not reset properly."
+        if (siblingFiber !== null) {
+          // If there is more work to do in this returnFiber, do that next.
+          return siblingFiber;
+        } else if (returnFiber !== null) {
+          // If there's no more work in this returnFiber. Complete the returnFiber.
+          workInProgress = returnFiber;
+          continue;
+        } else {
+          // We've reached the root.
+          isRootReadyForCommit = true;
+          return null;
+        }
+      } else {
+        // This fiber did not complete because something threw. Pop values off
+        // the stack without entering the complete phase. If this is a boundary,
+        // capture values if possible.
+        var _next = unwindWork(
+          workInProgress,
+          nextRenderIsExpired,
+          nextRenderExpirationTime
         );
-      }
-    }
-  }
+        // Because this fiber did not complete, don't reset its expiration time.
+        if (workInProgress.effectTag & DidCapture) {
+          // Restarting an error boundary
+          stopFailedWorkTimer(workInProgress);
+        } else {
+          stopWorkTimer(workInProgress);
+        }
 
-  function resetStackAfterFatalErrorInDev() {
-    {
-      index = -1;
-      valueStack.length = 0;
-      fiberStack.length = 0;
-    }
-  }
+        {
+          ReactDebugCurrentFiber.resetCurrentFiber();
+        }
 
-  return {
-    createCursor: createCursor,
-    isEmpty: isEmpty,
-    pop: pop,
-    push: push,
-    checkThatStackIsEmpty: checkThatStackIsEmpty,
-    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
-  };
-};
+        if (_next !== null) {
+          stopWorkTimer(workInProgress);
+          if (true && ReactFiberInstrumentation_1.debugTool) {
+            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
+              workInProgress
+            );
+          }
+          // If completing this work spawned new work, do that next. We'll come
+          // back here again.
+          // Since we're restarting, remove anything that is not a host effect
+          // from the effect tag.
+          _next.effectTag &= HostEffectMask;
+          return _next;
+        }
 
-var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError = ReactErrorUtils.hasCaughtError;
-var clearCaughtError = ReactErrorUtils.clearCaughtError;
+        if (returnFiber !== null) {
+          // Mark the parent fiber as incomplete and clear its effect list.
+          returnFiber.firstEffect = returnFiber.lastEffect = null;
+          returnFiber.effectTag |= Incomplete;
+        }
 
-var didWarnAboutStateTransition = void 0;
-var didWarnSetStateChildContext = void 0;
-var warnAboutUpdateOnUnmounted = void 0;
-var warnAboutInvalidUpdates = void 0;
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+        }
 
-{
-  didWarnAboutStateTransition = false;
-  didWarnSetStateChildContext = false;
-  var didWarnStateUpdateForUnmountedComponent = {};
+        if (siblingFiber !== null) {
+          // If there is more work to do in this returnFiber, do that next.
+          return siblingFiber;
+        } else if (returnFiber !== null) {
+          // If there's no more work in this returnFiber. Complete the returnFiber.
+          workInProgress = returnFiber;
+          continue;
+        } else {
+          return null;
+        }
+      }
+    }
 
-  warnAboutUpdateOnUnmounted = function(fiber) {
-    // We show the whole stack but dedupe on the top component's name because
-    // the problematic code almost always lies inside that component.
-    var componentName = getComponentName(fiber) || "ReactClass";
-    if (didWarnStateUpdateForUnmountedComponent[componentName]) {
-      return;
+    // Without this explicit null return Flow complains of invalid return type
+    // TODO Remove the above while(true) loop
+    // eslint-disable-next-line no-unreachable
+    return null;
+  }
+
+  function performUnitOfWork(workInProgress) {
+    // The current, flushed, state of this fiber is the alternate.
+    // Ideally nothing should rely on this, but relying on it here
+    // means that we don't need an additional field on the work in
+    // progress.
+    var current = workInProgress.alternate;
+
+    // See if beginning this work spawns more work.
+    startWorkTimer(workInProgress);
+    {
+      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
     }
-    warning(
-      false,
-      "Can't call setState (or forceUpdate) on an unmounted component. This " +
-        "is a no-op, but it indicates a memory leak in your application. To " +
-        "fix, cancel all subscriptions and asynchronous tasks in the " +
-        "componentWillUnmount method.%s",
-      getStackAddendumByWorkInProgressFiber(fiber)
-    );
-    didWarnStateUpdateForUnmountedComponent[componentName] = true;
-  };
 
-  warnAboutInvalidUpdates = function(instance) {
-    switch (ReactDebugCurrentFiber.phase) {
-      case "getChildContext":
-        if (didWarnSetStateChildContext) {
-          return;
-        }
-        warning(
-          false,
-          "setState(...): Cannot call setState() inside getChildContext()"
-        );
-        didWarnSetStateChildContext = true;
-        break;
-      case "render":
-        if (didWarnAboutStateTransition) {
-          return;
-        }
-        warning(
-          false,
-          "Cannot update during an existing state transition (such as within " +
-            "`render` or another component's constructor). Render methods should " +
-            "be a pure function of props and state; constructor side-effects are " +
-            "an anti-pattern, but can be moved to `componentWillMount`."
-        );
-        didWarnAboutStateTransition = true;
-        break;
+    if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
+        stashedWorkInProgressProperties,
+        workInProgress
+      );
     }
-  };
-}
-
-var ReactFiberScheduler = function(config) {
-  var stack = ReactFiberStack();
-  var hostContext = ReactFiberHostContext(config, stack);
-  var legacyContext = ReactFiberLegacyContext(stack);
-  var newContext = ReactFiberNewContext(stack);
-  var popHostContext = hostContext.popHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popLegacyContextProvider = legacyContext.popContextProvider;
-  var popProvider = newContext.popProvider;
 
-  var hydrationContext = ReactFiberHydrationContext(config);
+    var next = void 0;
+    if (enableProfilerTimer) {
+      startBaseRenderTimer();
+      next = beginWork(current, workInProgress, nextRenderExpirationTime);
 
-  var _ReactFiberBeginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber
-    ),
-    beginWork = _ReactFiberBeginWork.beginWork;
+      // Update "base" time if the render wasn't bailed out on.
+      recordElapsedBaseRenderTimeIfRunning(workInProgress);
+      stopBaseRenderTimerIfRunning();
+    } else {
+      next = beginWork(current, workInProgress, nextRenderExpirationTime);
+    }
 
-  var _ReactFiberCompleteWo = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext
-    ),
-    completeWork = _ReactFiberCompleteWo.completeWork;
+    {
+      ReactDebugCurrentFiber.resetCurrentFiber();
+      if (isReplayingFailedUnitOfWork) {
+        // Currently replaying a failed unit of work. This should be unreachable,
+        // because the render phase is meant to be idempotent, and it should
+        // have thrown again. Since it didn't, rethrow the original error, so
+        // React's internal stack is not misaligned.
+        rethrowOriginalError();
+      }
+    }
+    if (true && ReactFiberInstrumentation_1.debugTool) {
+      ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
+    }
 
-  var _ReactFiberUnwindWork = ReactFiberUnwindWork(
-      hostContext,
-      legacyContext,
-      newContext,
-      scheduleWork,
-      isAlreadyFailedLegacyErrorBoundary
-    ),
-    throwException = _ReactFiberUnwindWork.throwException,
-    unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork;
+    if (next === null) {
+      // If this doesn't spawn new work, complete the current work.
+      next = completeUnitOfWork(workInProgress);
+    }
 
-  var _ReactFiberCommitWork = ReactFiberCommitWork(
-      config,
-      onCommitPhaseError,
-      scheduleWork,
-      computeExpirationForFiber,
-      markLegacyErrorBoundaryAsFailed,
-      recalculateCurrentTime
-    ),
-    commitBeforeMutationLifeCycles =
-      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
-    commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
-    commitPlacement = _ReactFiberCommitWork.commitPlacement,
-    commitDeletion = _ReactFiberCommitWork.commitDeletion,
-    commitWork = _ReactFiberCommitWork.commitWork,
-    commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
-    commitErrorLogging = _ReactFiberCommitWork.commitErrorLogging,
-    commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
-    commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
+    ReactCurrentOwner.current = null;
 
-  var now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit;
+    return next;
+  }
 
-  // Represents the current time in ms.
+  function workLoop(isAsync) {
+    if (!isAsync) {
+      // Flush all expired work.
+      while (nextUnitOfWork !== null) {
+        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      }
+    } else {
+      // Flush asynchronous work until the deadline runs out of time.
+      while (nextUnitOfWork !== null && !shouldYield()) {
+        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      }
 
-  var originalStartTimeMs = now();
-  var mostRecentCurrentTime = msToExpirationTime(0);
-  var mostRecentCurrentTimeMs = originalStartTimeMs;
+      if (enableProfilerTimer) {
+        // If we didn't finish, pause the "actual" render timer.
+        // We'll restart it when we resume work.
+        pauseActualRenderTimerIfRunning();
+      }
+    }
+  }
 
-  // Used to ensure computeUniqueAsyncExpiration is monotonically increases.
-  var lastUniqueAsyncExpiration = 0;
+  function renderRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isWorking,
+      "renderRoot was called recursively. This error is likely caused " +
+        "by a bug in React. Please file an issue."
+    );
+    isWorking = true;
 
-  // Represents the expiration time that incoming updates should use. (If this
-  // is NoWork, use the default strategy: async updates in async mode, sync
-  // updates in sync mode.)
-  var expirationContext = NoWork;
+    // Check if we're starting from a fresh stack, or if we're resuming from
+    // previously yielded work.
+    if (
+      expirationTime !== nextRenderExpirationTime ||
+      root !== nextRoot ||
+      nextUnitOfWork === null
+    ) {
+      // Reset the stack and start working from the root.
+      resetStack();
+      nextRoot = root;
+      nextRenderExpirationTime = expirationTime;
+      nextLatestTimeoutMs = -1;
+      nextUnitOfWork = createWorkInProgress(
+        nextRoot.current,
+        null,
+        nextRenderExpirationTime
+      );
+      root.pendingCommitExpirationTime = NoWork;
+    }
 
-  var isWorking = false;
+    var didFatal = false;
 
-  // The next work in progress fiber that we're currently working on.
-  var nextUnitOfWork = null;
-  var nextRoot = null;
-  // The time at which we're currently rendering work.
-  var nextRenderExpirationTime = NoWork;
+    nextRenderIsExpired =
+      !isAsync || nextRenderExpirationTime <= mostRecentCurrentTime;
 
-  // The next fiber with an effect that we're currently committing.
-  var nextEffect = null;
+    startWorkLoopTimer(nextUnitOfWork);
 
-  var isCommitting = false;
+    do {
+      try {
+        workLoop(isAsync);
+      } catch (thrownValue) {
+        if (enableProfilerTimer) {
+          // Stop "base" render timer in the event of an error.
+          stopBaseRenderTimerIfRunning();
+        }
 
-  var isRootReadyForCommit = false;
+        if (nextUnitOfWork === null) {
+          // This is a fatal error.
+          didFatal = true;
+          onUncaughtError(thrownValue);
+          break;
+        }
 
-  var legacyErrorBoundariesThatAlreadyFailed = null;
+        {
+          // Reset global debug state
+          // We assume this is defined in DEV
+          resetCurrentlyProcessingQueue();
+        }
 
-  // Used for performance tracking.
-  var interruptedBy = null;
+        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+          var failedUnitOfWork = nextUnitOfWork;
+          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
+        }
 
-  var stashedWorkInProgressProperties = void 0;
-  var replayUnitOfWork = void 0;
-  var isReplayingFailedUnitOfWork = void 0;
-  var originalReplayError = void 0;
-  var rethrowOriginalError = void 0;
-  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-    stashedWorkInProgressProperties = null;
-    isReplayingFailedUnitOfWork = false;
-    originalReplayError = null;
-    replayUnitOfWork = function(failedUnitOfWork, error, isAsync) {
-      // Restore the original state of the work-in-progress
-      assignFiberPropertiesInDEV(
-        failedUnitOfWork,
-        stashedWorkInProgressProperties
-      );
-      switch (failedUnitOfWork.tag) {
-        case HostRoot:
-          popHostContainer(failedUnitOfWork);
-          popTopLevelLegacyContextObject(failedUnitOfWork);
-          break;
-        case HostComponent:
-          popHostContext(failedUnitOfWork);
-          break;
-        case ClassComponent:
-          popLegacyContextProvider(failedUnitOfWork);
-          break;
-        case HostPortal:
-          popHostContainer(failedUnitOfWork);
-          break;
-        case ContextProvider:
-          popProvider(failedUnitOfWork);
+        var sourceFiber = nextUnitOfWork;
+        var returnFiber = sourceFiber.return;
+        if (returnFiber === null) {
+          // This is the root. The root could capture its own errors. However,
+          // we don't know if it errors before or after we pushed the host
+          // context. This information is needed to avoid a stack mismatch.
+          // Because we're not sure, treat this as a fatal error. We could track
+          // which phase it fails in, but doesn't seem worth it. At least
+          // for now.
+          didFatal = true;
+          onUncaughtError(thrownValue);
           break;
+        }
+        throwException(
+          root,
+          returnFiber,
+          sourceFiber,
+          thrownValue,
+          nextRenderIsExpired,
+          nextRenderExpirationTime,
+          mostRecentCurrentTimeMs
+        );
+        nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
-      // Replay the begin phase.
-      isReplayingFailedUnitOfWork = true;
-      originalReplayError = error;
-      invokeGuardedCallback$2(null, workLoop, null, isAsync);
-      isReplayingFailedUnitOfWork = false;
-      originalReplayError = null;
-      if (hasCaughtError()) {
-        clearCaughtError();
-      } else {
-        // If the begin phase did not fail the second time, set this pointer
-        // back to the original value.
-        nextUnitOfWork = failedUnitOfWork;
+      break;
+    } while (true);
+
+    // We're done performing work. Time to clean up.
+    var didCompleteRoot = false;
+    isWorking = false;
+
+    // Yield back to main thread.
+    if (didFatal) {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
+      // There was a fatal error.
+      {
+        stack.resetStackAfterFatalErrorInDev();
       }
-    };
-    rethrowOriginalError = function() {
-      throw originalReplayError;
-    };
+      return null;
+    } else if (nextUnitOfWork === null) {
+      // We reached the root.
+      if (isRootReadyForCommit) {
+        didCompleteRoot = true;
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
+        // The root successfully completed. It's ready for commit.
+        root.pendingCommitExpirationTime = expirationTime;
+        var finishedWork = root.current.alternate;
+        return finishedWork;
+      } else {
+        // The root did not complete.
+        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+        interruptedBy = null;
+        invariant(
+          !nextRenderIsExpired,
+          "Expired work should have completed. This error is likely caused " +
+            "by a bug in React. Please file an issue."
+        );
+        markSuspendedPriorityLevel(root, expirationTime);
+        if (nextLatestTimeoutMs >= 0) {
+          setTimeout(function() {
+            retrySuspendedRoot(root, expirationTime);
+          }, nextLatestTimeoutMs);
+        }
+        var firstUnblockedExpirationTime = findNextPendingPriorityLevel(root);
+        onBlock(firstUnblockedExpirationTime);
+        return null;
+      }
+    } else {
+      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      interruptedBy = null;
+      // There's more work to do, but we ran out of time. Yield back to
+      // the renderer.
+      return null;
+    }
   }
 
-  function resetStack() {
-    if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork["return"];
-      while (interruptedWork !== null) {
-        unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork["return"];
+  function dispatch(sourceFiber, value, expirationTime) {
+    invariant(
+      !isWorking || isCommitting,
+      "dispatch: Cannot dispatch during the render phase."
+    );
+
+    var fiber = sourceFiber.return;
+    while (fiber !== null) {
+      switch (fiber.tag) {
+        case ClassComponent:
+          var ctor = fiber.type;
+          var instance = fiber.stateNode;
+          if (
+            typeof ctor.getDerivedStateFromCatch === "function" ||
+            (typeof instance.componentDidCatch === "function" &&
+              !isAlreadyFailedLegacyErrorBoundary(instance))
+          ) {
+            var errorInfo = createCapturedValue(value, sourceFiber);
+            var update = createClassErrorUpdate(
+              fiber,
+              errorInfo,
+              expirationTime
+            );
+            enqueueUpdate(fiber, update, expirationTime);
+            scheduleWork(fiber, expirationTime);
+            return;
+          }
+          break;
+        case HostRoot: {
+          var _errorInfo = createCapturedValue(value, sourceFiber);
+          var _update = createRootErrorUpdate(
+            fiber,
+            _errorInfo,
+            expirationTime
+          );
+          enqueueUpdate(fiber, _update, expirationTime);
+          scheduleWork(fiber, expirationTime);
+          return;
+        }
       }
+      fiber = fiber.return;
     }
 
-    {
-      ReactStrictModeWarnings.discardPendingWarnings();
-      stack.checkThatStackIsEmpty();
+    if (sourceFiber.tag === HostRoot) {
+      // Error was thrown at the root. There is no parent, so the root
+      // itself should capture it.
+      var rootFiber = sourceFiber;
+      var _errorInfo2 = createCapturedValue(value, rootFiber);
+      var _update2 = createRootErrorUpdate(
+        rootFiber,
+        _errorInfo2,
+        expirationTime
+      );
+      enqueueUpdate(rootFiber, _update2, expirationTime);
+      scheduleWork(rootFiber, expirationTime);
     }
+  }
 
-    nextRoot = null;
-    nextRenderExpirationTime = NoWork;
-    nextUnitOfWork = null;
+  function onCommitPhaseError(fiber, error) {
+    return dispatch(fiber, error, Sync);
+  }
 
-    isRootReadyForCommit = false;
+  function computeAsyncExpiration(currentTime) {
+    // Given the current clock time, returns an expiration time. We use rounding
+    // to batch like updates together.
+    // Should complete within ~1000ms. 1200ms max.
+    var expirationMs = 5000;
+    var bucketSizeMs = 250;
+    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
   }
 
-  function commitAllHostEffects() {
-    while (nextEffect !== null) {
-      {
-        ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
-      }
-      recordEffect();
+  function computeInteractiveExpiration(currentTime) {
+    var expirationMs = void 0;
+    // We intentionally set a higher expiration time for interactive updates in
+    // dev than in production.
+    // If the main thread is being blocked so long that you hit the expiration,
+    // it's a problem that could be solved with better scheduling.
+    // People will be more likely to notice this and fix it with the long
+    // expiration time in development.
+    // In production we opt for better UX at the risk of masking scheduling
+    // problems, by expiring fast.
+    {
+      // Should complete within ~500ms. 600ms max.
+      expirationMs = 500;
+    }
+    var bucketSizeMs = 100;
+    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+  }
 
-      var effectTag = nextEffect.effectTag;
+  // Creates a unique async expiration time.
+  function computeUniqueAsyncExpiration() {
+    var currentTime = recalculateCurrentTime();
+    var result = computeAsyncExpiration(currentTime);
+    if (result <= lastUniqueAsyncExpiration) {
+      // Since we assume the current time monotonically increases, we only hit
+      // this branch when computeUniqueAsyncExpiration is fired multiple times
+      // within a 200ms window (or whatever the async bucket size is).
+      result = lastUniqueAsyncExpiration + 1;
+    }
+    lastUniqueAsyncExpiration = result;
+    return lastUniqueAsyncExpiration;
+  }
 
-      if (effectTag & ContentReset) {
-        commitResetTextContent(nextEffect);
+  function computeExpirationForFiber(currentTime, fiber) {
+    var expirationTime = void 0;
+    if (expirationContext !== NoWork) {
+      // An explicit expiration context was set;
+      expirationTime = expirationContext;
+    } else if (isWorking) {
+      if (isCommitting) {
+        // Updates that occur during the commit phase should have sync priority
+        // by default.
+        expirationTime = Sync;
+      } else {
+        // Updates during the render phase should expire at the same time as
+        // the work that is being rendered.
+        expirationTime = nextRenderExpirationTime;
       }
-
-      if (effectTag & Ref) {
-        var current = nextEffect.alternate;
-        if (current !== null) {
-          commitDetachRef(current);
+    } else {
+      // No explicit expiration context was set, and we're not currently
+      // performing work. Calculate a new expiration time.
+      if (fiber.mode & AsyncMode) {
+        if (isBatchingInteractiveUpdates) {
+          // This is an interactive update
+          expirationTime = computeInteractiveExpiration(currentTime);
+        } else {
+          // This is an async update
+          expirationTime = computeAsyncExpiration(currentTime);
         }
+      } else {
+        // This is a sync update
+        expirationTime = Sync;
       }
-
-      // The following switch statement is only concerned about placement,
-      // updates, and deletions. To avoid needing to add a case for every
-      // possible bitmap value, we remove the secondary effects from the
-      // effect tag and switch on that value.
-      var primaryEffectTag = effectTag & (Placement | Update | Deletion);
-      switch (primaryEffectTag) {
-        case Placement: {
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          // TODO: findDOMNode doesn't rely on this any more but isMounted
-          // does and isMounted is deprecated anyway so we should be able
-          // to kill this.
-          nextEffect.effectTag &= ~Placement;
-          break;
-        }
-        case PlacementAndUpdate: {
-          // Placement
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          nextEffect.effectTag &= ~Placement;
-
-          // Update
-          var _current = nextEffect.alternate;
-          commitWork(_current, nextEffect);
-          break;
-        }
-        case Update: {
-          var _current2 = nextEffect.alternate;
-          commitWork(_current2, nextEffect);
-          break;
-        }
-        case Deletion: {
-          commitDeletion(nextEffect);
-          break;
-        }
+    }
+    if (isBatchingInteractiveUpdates) {
+      // This is an interactive update. Keep track of the lowest pending
+      // interactive expiration time. This allows us to synchronously flush
+      // all interactive updates when needed.
+      if (
+        lowestPendingInteractiveExpirationTime === NoWork ||
+        expirationTime > lowestPendingInteractiveExpirationTime
+      ) {
+        lowestPendingInteractiveExpirationTime = expirationTime;
       }
-      nextEffect = nextEffect.nextEffect;
     }
+    return expirationTime;
+  }
 
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
+  // TODO: Rename this to scheduleTimeout or something
+  function suspendRoot(root, thenable, timeoutMs, suspendedTime) {
+    // Schedule the timeout.
+    if (timeoutMs >= 0 && nextLatestTimeoutMs < timeoutMs) {
+      nextLatestTimeoutMs = timeoutMs;
     }
   }
 
-  function commitBeforeMutationLifecycles() {
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & Snapshot) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitBeforeMutationLifeCycles(current, nextEffect);
-      }
-
-      // Don't cleanup effects yet;
-      // This will be done by commitAllLifeCycles()
-      nextEffect = nextEffect.nextEffect;
+  function retrySuspendedRoot(root, suspendedTime) {
+    markPingedPriorityLevel(root, suspendedTime);
+    var retryTime = findNextPendingPriorityLevel(root);
+    if (retryTime !== NoWork) {
+      requestRetry(root, retryTime);
     }
   }
 
-  function commitAllLifeCycles(
-    finishedRoot,
-    currentTime,
-    committedExpirationTime
-  ) {
-    {
-      ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
+  function scheduleWork(fiber, expirationTime) {
+    recordScheduleUpdate();
 
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.flushPendingDeprecationWarnings();
+    {
+      if (fiber.tag === ClassComponent) {
+        var instance = fiber.stateNode;
+        warnAboutInvalidUpdates(instance);
       }
     }
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
 
-      if (effectTag & (Update | Callback)) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitLifeCycles(
-          finishedRoot,
-          current,
-          nextEffect,
-          currentTime,
-          committedExpirationTime
-        );
+    var node = fiber;
+    while (node !== null) {
+      // Walk the parent path to the root and update each node's
+      // expiration time.
+      if (
+        node.expirationTime === NoWork ||
+        node.expirationTime > expirationTime
+      ) {
+        node.expirationTime = expirationTime;
       }
-
-      if (effectTag & ErrLog) {
-        commitErrorLogging(nextEffect, onUncaughtError);
+      if (node.alternate !== null) {
+        if (
+          node.alternate.expirationTime === NoWork ||
+          node.alternate.expirationTime > expirationTime
+        ) {
+          node.alternate.expirationTime = expirationTime;
+        }
       }
-
-      if (effectTag & Ref) {
-        recordEffect();
-        commitAttachRef(nextEffect);
+      if (node.return === null) {
+        if (node.tag === HostRoot) {
+          var root = node.stateNode;
+          if (
+            !isWorking &&
+            nextRenderExpirationTime !== NoWork &&
+            expirationTime < nextRenderExpirationTime
+          ) {
+            // This is an interruption. (Used for performance tracking.)
+            interruptedBy = fiber;
+            resetStack();
+          }
+          markPendingPriorityLevel(root, expirationTime);
+          var nextExpirationTimeToWorkOn = findNextPendingPriorityLevel(root);
+          if (
+            // If we're in the render phase, we don't need to schedule this root
+            // for an update, because we'll do it before we exit...
+            !isWorking ||
+            isCommitting ||
+            // ...unless this is a different root than the one we're rendering.
+            nextRoot !== root
+          ) {
+            requestWork(root, nextExpirationTimeToWorkOn);
+          }
+          if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
+            invariant(
+              false,
+              "Maximum update depth exceeded. This can happen when a " +
+                "component repeatedly calls setState inside " +
+                "componentWillUpdate or componentDidUpdate. React limits " +
+                "the number of nested updates to prevent infinite loops."
+            );
+          }
+        } else {
+          {
+            if (fiber.tag === ClassComponent) {
+              warnAboutUpdateOnUnmounted(fiber);
+            }
+          }
+          return;
+        }
       }
-
-      var next = nextEffect.nextEffect;
-      // Ensure that we clean these up so that we don't accidentally keep them.
-      // I'm not actually sure this matters because we can't reset firstEffect
-      // and lastEffect since they're on every node, not just the effectful
-      // ones. So we have to clean everything as we reuse nodes anyway.
-      nextEffect.nextEffect = null;
-      // Ensure that we reset the effectTag here so that we can rely on effect
-      // tags to reason about the current life-cycle.
-      nextEffect = next;
+      node = node.return;
     }
   }
 
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      legacyErrorBoundariesThatAlreadyFailed !== null &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
+  function recalculateCurrentTime() {
+    // Subtract initial time so it fits inside 32bits
+    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
+    mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
+    return mostRecentCurrentTime;
   }
 
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    if (legacyErrorBoundariesThatAlreadyFailed === null) {
-      legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
-    } else {
-      legacyErrorBoundariesThatAlreadyFailed.add(instance);
+  function deferredUpdates(fn) {
+    var previousExpirationContext = expirationContext;
+    var currentTime = recalculateCurrentTime();
+    expirationContext = computeAsyncExpiration(currentTime);
+    try {
+      return fn();
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  }
+  function syncUpdates(fn, a, b, c, d) {
+    var previousExpirationContext = expirationContext;
+    expirationContext = Sync;
+    try {
+      return fn(a, b, c, d);
+    } finally {
+      expirationContext = previousExpirationContext;
     }
   }
 
-  function commitRoot(finishedWork) {
-    isWorking = true;
-    isCommitting = true;
-    startCommitTimer();
+  // TODO: Everything below this is written as if it has been lifted to the
+  // renderers. I'll do this in a follow-up.
 
-    var root = finishedWork.stateNode;
-    invariant(
-      root.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug " +
-        "related to the return field. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-    var committedExpirationTime = root.pendingCommitExpirationTime;
-    invariant(
-      committedExpirationTime !== NoWork,
-      "Cannot commit an incomplete root. This error is likely caused by a " +
-        "bug in React. Please file an issue."
-    );
-    root.pendingCommitExpirationTime = NoWork;
+  // Linked-list of roots
+  var firstScheduledRoot = null;
+  var lastScheduledRoot = null;
 
-    var currentTime = recalculateCurrentTime();
+  var callbackExpirationTime = NoWork;
+  var callbackID = -1;
+  var isRendering = false;
+  var nextFlushedRoot = null;
+  var nextFlushedExpirationTime = NoWork;
+  var lowestPendingInteractiveExpirationTime = NoWork;
+  var deadlineDidExpire = false;
+  var hasUnhandledError = false;
+  var unhandledError = null;
+  var deadline = null;
 
-    // Reset this to null before calling lifecycles
-    ReactCurrentOwner.current = null;
+  var isBatchingUpdates = false;
+  var isUnbatchingUpdates = false;
+  var isBatchingInteractiveUpdates = false;
 
-    var firstEffect = void 0;
-    if (finishedWork.effectTag > PerformedWork) {
-      // A fiber's effect list consists only of its children, not itself. So if
-      // the root has an effect, we need to add it to the end of the list. The
-      // resulting list is the set that would belong to the root's parent, if
-      // it had one; that is, all the effects in the tree including the root.
-      if (finishedWork.lastEffect !== null) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        firstEffect = finishedWork.firstEffect;
-      } else {
-        firstEffect = finishedWork;
-      }
-    } else {
-      // There is no effect on the root.
-      firstEffect = finishedWork.firstEffect;
-    }
+  var completedBatches = null;
 
-    prepareForCommit(root.containerInfo);
+  // Use these to prevent an infinite loop of nested updates
+  var NESTED_UPDATE_LIMIT = 1000;
+  var nestedUpdateCount = 0;
 
-    // Invoke instances of getSnapshotBeforeUpdate before mutation.
-    nextEffect = firstEffect;
-    startCommitSnapshotEffectsTimer();
-    while (nextEffect !== null) {
-      var didError = false;
-      var error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
-        if (hasCaughtError()) {
-          didError = true;
-          error = clearCaughtError();
-        }
-      }
-      if (didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
-    stopCommitSnapshotEffectsTimer();
+  var timeHeuristicForUnitOfWork = 1;
 
-    // Commit all the side-effects within a tree. We'll do this in two passes.
-    // The first pass performs all the host insertions, updates, deletions and
-    // ref unmounts.
-    nextEffect = firstEffect;
-    startCommitHostEffectsTimer();
-    while (nextEffect !== null) {
-      var _didError = false;
-      var _error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitAllHostEffects, null);
-        if (hasCaughtError()) {
-          _didError = true;
-          _error = clearCaughtError();
-        }
-      }
-      if (_didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
+  function scheduleCallbackWithExpiration(expirationTime) {
+    if (callbackExpirationTime !== NoWork) {
+      // A callback is already scheduled. Check its expiration time (timeout).
+      if (expirationTime > callbackExpirationTime) {
+        // Existing callback has sufficient timeout. Exit.
+        return;
+      } else {
+        // Existing callback has insufficient timeout. Cancel and schedule a
+        // new one.
+        cancelDeferredCallback(callbackID);
       }
+      // The request callback timer is already running. Don't start a new one.
+    } else {
+      startRequestCallbackTimer();
     }
-    stopCommitHostEffectsTimer();
-
-    resetAfterCommit(root.containerInfo);
-
-    // The work-in-progress tree is now the current tree. This must come after
-    // the first pass of the commit phase, so that the previous tree is still
-    // current during componentWillUnmount, but before the second pass, so that
-    // the finished work is current during componentDidMount/Update.
-    root.current = finishedWork;
 
-    // In the second pass we'll perform all life-cycles and ref callbacks.
-    // Life-cycles happen as a separate pass so that all placements, updates,
-    // and deletions in the entire tree have already been invoked.
-    // This pass also triggers any renderer-specific initial effects.
-    nextEffect = firstEffect;
-    startCommitLifeCyclesTimer();
-    while (nextEffect !== null) {
-      var _didError2 = false;
-      var _error2 = void 0;
-      {
-        invokeGuardedCallback$2(
-          null,
-          commitAllLifeCycles,
-          null,
-          root,
-          currentTime,
-          committedExpirationTime
-        );
-        if (hasCaughtError()) {
-          _didError2 = true;
-          _error2 = clearCaughtError();
-        }
-      }
-      if (_didError2) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error2);
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
+    // Compute a timeout for the given expiration time.
+    var currentMs = now() - originalStartTimeMs;
+    var expirationMs = expirationTimeToMs(expirationTime);
+    var timeout = expirationMs - currentMs;
 
-    isCommitting = false;
-    isWorking = false;
-    stopCommitLifeCyclesTimer();
-    stopCommitTimer();
-    if (typeof onCommitRoot === "function") {
-      onCommitRoot(finishedWork.stateNode);
-    }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
-    }
+    callbackExpirationTime = expirationTime;
+    callbackID = scheduleDeferredCallback(performAsyncWork, {
+      timeout: timeout
+    });
+  }
 
-    var remainingTime = root.current.expirationTime;
-    if (remainingTime === NoWork) {
-      // If there's no remaining work, we can clear the set of already failed
-      // error boundaries.
-      legacyErrorBoundariesThatAlreadyFailed = null;
+  function requestRetry(root, expirationTime) {
+    if (
+      root.remainingExpirationTime === NoWork ||
+      root.remainingExpirationTime < expirationTime
+    ) {
+      // For a retry, only update the remaining expiration time if it has a
+      // *lower priority* than the existing value. This is because, on a retry,
+      // we should attempt to coalesce as much as possible.
+      requestWork(root, expirationTime);
     }
-    return remainingTime;
   }
 
-  function resetExpirationTime(workInProgress, renderTime) {
-    if (renderTime !== Never && workInProgress.expirationTime === Never) {
-      // The children of this component are hidden. Don't bubble their
-      // expiration times.
+  // requestWork is called by the scheduler whenever a root receives an update.
+  // It's up to the renderer to call renderRoot at some point in the future.
+  function requestWork(root, expirationTime) {
+    addRootToSchedule(root, expirationTime);
+
+    if (isRendering) {
+      // Prevent reentrancy. Remaining work will be scheduled at the end of
+      // the currently rendering batch.
       return;
     }
 
-    // Check for pending updates.
-    var newExpirationTime = getUpdateExpirationTime(workInProgress);
+    if (isBatchingUpdates) {
+      // Flush work at the end of the batch.
+      if (isUnbatchingUpdates) {
+        // ...unless we're inside unbatchedUpdates, in which case we should
+        // flush it now.
+        nextFlushedRoot = root;
+        nextFlushedExpirationTime = Sync;
+        performWorkOnRoot(root, Sync, false);
+      }
+      return;
+    }
 
-    // TODO: Calls need to visit stateNode
+    // TODO: Get rid of Sync and use current time?
+    if (expirationTime === Sync) {
+      performSyncWork();
+    } else {
+      scheduleCallbackWithExpiration(expirationTime);
+    }
+  }
 
-    // Bubble up the earliest expiration time.
-    var child = workInProgress.child;
-    while (child !== null) {
+  function addRootToSchedule(root, expirationTime) {
+    // Add the root to the schedule.
+    // Check if this root is already part of the schedule.
+    if (root.nextScheduledRoot === null) {
+      // This root is not already scheduled. Add it.
+      root.remainingExpirationTime = expirationTime;
+      if (lastScheduledRoot === null) {
+        firstScheduledRoot = lastScheduledRoot = root;
+        root.nextScheduledRoot = root;
+      } else {
+        lastScheduledRoot.nextScheduledRoot = root;
+        lastScheduledRoot = root;
+        lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+      }
+    } else {
+      // This root is already scheduled, but its priority may have increased.
+      var remainingExpirationTime = root.remainingExpirationTime;
       if (
-        child.expirationTime !== NoWork &&
-        (newExpirationTime === NoWork ||
-          newExpirationTime > child.expirationTime)
+        remainingExpirationTime === NoWork ||
+        expirationTime < remainingExpirationTime
       ) {
-        newExpirationTime = child.expirationTime;
+        // Update the priority.
+        root.remainingExpirationTime = expirationTime;
       }
-      child = child.sibling;
     }
-    workInProgress.expirationTime = newExpirationTime;
   }
 
-  function completeUnitOfWork(workInProgress) {
-    // Attempt to complete the current unit of work, then move to the
-    // next sibling. If there are no more siblings, return to the
-    // parent fiber.
-    while (true) {
-      // The current, flushed, state of this fiber is the alternate.
-      // Ideally nothing should rely on this, but relying on it here
-      // means that we don't need an additional field on the work in
-      // progress.
-      var current = workInProgress.alternate;
-      {
-        ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+  function findHighestPriorityRoot() {
+    var highestPriorityWork = NoWork;
+    var highestPriorityRoot = null;
+    if (lastScheduledRoot !== null) {
+      var previousScheduledRoot = lastScheduledRoot;
+      var root = firstScheduledRoot;
+      while (root !== null) {
+        var remainingExpirationTime = root.remainingExpirationTime;
+        if (remainingExpirationTime === NoWork) {
+          // This root no longer has work. Remove it from the scheduler.
+
+          // TODO: This check is redudant, but Flow is confused by the branch
+          // below where we set lastScheduledRoot to null, even though we break
+          // from the loop right after.
+          invariant(
+            previousScheduledRoot !== null && lastScheduledRoot !== null,
+            "Should have a previous and last root. This error is likely " +
+              "caused by a bug in React. Please file an issue."
+          );
+          if (root === root.nextScheduledRoot) {
+            // This is the only root in the list.
+            root.nextScheduledRoot = null;
+            firstScheduledRoot = lastScheduledRoot = null;
+            break;
+          } else if (root === firstScheduledRoot) {
+            // This is the first root in the list.
+            var next = root.nextScheduledRoot;
+            firstScheduledRoot = next;
+            lastScheduledRoot.nextScheduledRoot = next;
+            root.nextScheduledRoot = null;
+          } else if (root === lastScheduledRoot) {
+            // This is the last root in the list.
+            lastScheduledRoot = previousScheduledRoot;
+            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+            root.nextScheduledRoot = null;
+            break;
+          } else {
+            previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
+            root.nextScheduledRoot = null;
+          }
+          root = previousScheduledRoot.nextScheduledRoot;
+        } else {
+          if (
+            highestPriorityWork === NoWork ||
+            remainingExpirationTime < highestPriorityWork
+          ) {
+            // Update the priority, if it's higher
+            highestPriorityWork = remainingExpirationTime;
+            highestPriorityRoot = root;
+          }
+          if (root === lastScheduledRoot) {
+            break;
+          }
+          previousScheduledRoot = root;
+          root = root.nextScheduledRoot;
+        }
       }
+    }
 
-      var returnFiber = workInProgress["return"];
-      var siblingFiber = workInProgress.sibling;
+    // If the next root is the same as the previous root, this is a nested
+    // update. To prevent an infinite loop, increment the nested update count.
+    var previousFlushedRoot = nextFlushedRoot;
+    if (
+      previousFlushedRoot !== null &&
+      previousFlushedRoot === highestPriorityRoot &&
+      highestPriorityWork === Sync
+    ) {
+      nestedUpdateCount++;
+    } else {
+      // Reset whenever we switch roots.
+      nestedUpdateCount = 0;
+    }
+    nextFlushedRoot = highestPriorityRoot;
+    nextFlushedExpirationTime = highestPriorityWork;
+  }
 
-      if ((workInProgress.effectTag & Incomplete) === NoEffect) {
-        // This fiber completed.
-        var next = completeWork(
-          current,
-          workInProgress,
-          nextRenderExpirationTime
-        );
-        stopWorkTimer(workInProgress);
-        resetExpirationTime(workInProgress, nextRenderExpirationTime);
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
+  function performAsyncWork(dl) {
+    performWork(NoWork, true, dl);
+  }
 
-        if (next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
-          }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          return next;
-        }
+  function performSyncWork() {
+    performWork(Sync, false, null);
+  }
 
-        if (
-          returnFiber !== null &&
-          // Do not append effects to parents if a sibling failed to complete
-          (returnFiber.effectTag & Incomplete) === NoEffect
-        ) {
-          // Append all the effects of the subtree and this fiber onto the effect
-          // list of the parent. The completion order of the children affects the
-          // side-effect order.
-          if (returnFiber.firstEffect === null) {
-            returnFiber.firstEffect = workInProgress.firstEffect;
-          }
-          if (workInProgress.lastEffect !== null) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
-            }
-            returnFiber.lastEffect = workInProgress.lastEffect;
-          }
+  function performWork(minExpirationTime, isAsync, dl) {
+    deadline = dl;
 
-          // If this fiber had side-effects, we append it AFTER the children's
-          // side-effects. We can perform certain side-effects earlier if
-          // needed, by doing multiple passes over the effect list. We don't want
-          // to schedule our own side-effect on our own list because if end up
-          // reusing children we'll schedule this effect onto itself since we're
-          // at the end.
-          var effectTag = workInProgress.effectTag;
-          // Skip both NoWork and PerformedWork tags when creating the effect list.
-          // PerformedWork effect is read by React DevTools but shouldn't be committed.
-          if (effectTag > PerformedWork) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress;
-            } else {
-              returnFiber.firstEffect = workInProgress;
-            }
-            returnFiber.lastEffect = workInProgress;
-          }
-        }
+    // Keep working on roots until there's no more work, or until the we reach
+    // the deadline.
+    findHighestPriorityRoot();
+
+    if (enableProfilerTimer) {
+      resumeActualRenderTimerIfPaused();
+    }
+
+    if (enableUserTimingAPI && deadline !== null) {
+      var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
+      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
+      stopRequestCallbackTimer(didExpire, timeout);
+    }
+
+    if (isAsync) {
+      while (
+        nextFlushedRoot !== null &&
+        nextFlushedExpirationTime !== NoWork &&
+        (minExpirationTime === NoWork ||
+          minExpirationTime >= nextFlushedExpirationTime) &&
+        (!deadlineDidExpire ||
+          recalculateCurrentTime() >= nextFlushedExpirationTime)
+      ) {
+        recalculateCurrentTime();
+        performWorkOnRoot(
+          nextFlushedRoot,
+          nextFlushedExpirationTime,
+          !deadlineDidExpire
+        );
+        findHighestPriorityRoot();
+      }
+    } else {
+      while (
+        nextFlushedRoot !== null &&
+        nextFlushedExpirationTime !== NoWork &&
+        (minExpirationTime === NoWork ||
+          minExpirationTime >= nextFlushedExpirationTime)
+      ) {
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
+        findHighestPriorityRoot();
+      }
+    }
+
+    // We're done flushing work. Either we ran out of time in this callback,
+    // or there's no more work left with sufficient priority.
 
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
-        }
+    // If we're inside a callback, set this to false since we just completed it.
+    if (deadline !== null) {
+      callbackExpirationTime = NoWork;
+      callbackID = -1;
+    }
+    // If there's work left over, schedule a new callback.
+    if (nextFlushedExpirationTime !== NoWork) {
+      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
+    }
 
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
-        } else {
-          // We've reached the root.
-          isRootReadyForCommit = true;
-          return null;
-        }
-      } else {
-        // This fiber did not complete because something threw. Pop values off
-        // the stack without entering the complete phase. If this is a boundary,
-        // capture values if possible.
-        var _next = unwindWork(workInProgress);
-        // Because this fiber did not complete, don't reset its expiration time.
-        if (workInProgress.effectTag & DidCapture) {
-          // Restarting an error boundary
-          stopFailedWorkTimer(workInProgress);
-        } else {
-          stopWorkTimer(workInProgress);
-        }
+    // Clean-up.
+    deadline = null;
+    deadlineDidExpire = false;
 
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
+    finishRendering();
+  }
 
-        if (_next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
+  function flushRoot(root, expirationTime) {
+    invariant(
+      !isRendering,
+      "work.commit(): Cannot commit while already rendering. This likely " +
+        "means you attempted to commit from inside a lifecycle method."
+    );
+    // Perform work on root as if the given expiration time is the current time.
+    // This has the effect of synchronously flushing all work up to and
+    // including the given time.
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
+    performWorkOnRoot(root, expirationTime, false);
+    // Flush any sync work that was scheduled by lifecycles
+    performSyncWork();
+    finishRendering();
+  }
+
+  function finishRendering() {
+    nestedUpdateCount = 0;
+
+    if (completedBatches !== null) {
+      var batches = completedBatches;
+      completedBatches = null;
+      for (var i = 0; i < batches.length; i++) {
+        var batch = batches[i];
+        try {
+          batch._onComplete();
+        } catch (error) {
+          if (!hasUnhandledError) {
+            hasUnhandledError = true;
+            unhandledError = error;
           }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          // Since we're restarting, remove anything that is not a host effect
-          // from the effect tag.
-          _next.effectTag &= HostEffectMask;
-          return _next;
         }
+      }
+    }
 
-        if (returnFiber !== null) {
-          // Mark the parent fiber as incomplete and clear its effect list.
-          returnFiber.firstEffect = returnFiber.lastEffect = null;
-          returnFiber.effectTag |= Incomplete;
-        }
+    if (hasUnhandledError) {
+      var error = unhandledError;
+      unhandledError = null;
+      hasUnhandledError = false;
+      throw error;
+    }
+  }
 
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+  function performWorkOnRoot(root, expirationTime, isAsync) {
+    invariant(
+      !isRendering,
+      "performWorkOnRoot was called recursively. This error is likely caused " +
+        "by a bug in React. Please file an issue."
+    );
+
+    isRendering = true;
+
+    // Check if this is async work or sync/expired work.
+    if (!isAsync) {
+      // Flush sync work.
+      var finishedWork = root.finishedWork;
+      if (finishedWork !== null) {
+        // This root is already complete. We can commit it.
+        completeRoot(root, finishedWork, expirationTime);
+      } else {
+        root.finishedWork = null;
+        finishedWork = renderRoot(root, expirationTime, false);
+        if (finishedWork !== null) {
+          // We've completed the root. Commit it.
+          completeRoot(root, finishedWork, expirationTime);
         }
+      }
+    } else {
+      // Flush async work.
+      var _finishedWork = root.finishedWork;
+      if (_finishedWork !== null) {
+        // This root is already complete. We can commit it.
+        completeRoot(root, _finishedWork, expirationTime);
+      } else {
+        root.finishedWork = null;
+        _finishedWork = renderRoot(root, expirationTime, true);
+        if (_finishedWork !== null) {
+          // We've completed the root. Check the deadline one more time
+          // before committing.
+          if (!shouldYield()) {
+            // Still time left. Commit the root.
+            completeRoot(root, _finishedWork, expirationTime);
+          } else {
+            // There's no time left. Mark this root as complete. We'll come
+            // back and commit it later.
+            root.finishedWork = _finishedWork;
 
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
-        } else {
-          return null;
+            if (enableProfilerTimer) {
+              // If we didn't finish, pause the "actual" render timer.
+              // We'll restart it when we resume work.
+              pauseActualRenderTimerIfRunning();
+            }
+          }
         }
       }
     }
 
-    // Without this explicit null return Flow complains of invalid return type
-    // TODO Remove the above while(true) loop
-    // eslint-disable-next-line no-unreachable
-    return null;
+    isRendering = false;
   }
 
-  function performUnitOfWork(workInProgress) {
-    // The current, flushed, state of this fiber is the alternate.
-    // Ideally nothing should rely on this, but relying on it here
-    // means that we don't need an additional field on the work in
-    // progress.
-    var current = workInProgress.alternate;
-
-    // See if beginning this work spawns more work.
-    startWorkTimer(workInProgress);
-    {
-      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+  function completeRoot(root, finishedWork, expirationTime) {
+    // Check if there's a batch that matches this expiration time.
+    var firstBatch = root.firstBatch;
+    if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
+      if (completedBatches === null) {
+        completedBatches = [firstBatch];
+      } else {
+        completedBatches.push(firstBatch);
+      }
+      if (firstBatch._defer) {
+        // This root is blocked from committing by a batch. Unschedule it until
+        // we receive another update.
+        root.finishedWork = finishedWork;
+        root.remainingExpirationTime = NoWork;
+        return;
+      }
     }
 
-    if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
-        stashedWorkInProgressProperties,
-        workInProgress
-      );
+    // Commit the root.
+    root.finishedWork = null;
+    root.remainingExpirationTime = commitRoot(finishedWork);
+  }
+
+  // When working on async work, the reconciler asks the renderer if it should
+  // yield execution. For DOM, we implement this with requestIdleCallback.
+  function shouldYield() {
+    if (deadline === null) {
+      return false;
     }
-    var next = beginWork(current, workInProgress, nextRenderExpirationTime);
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
-      if (isReplayingFailedUnitOfWork) {
-        // Currently replaying a failed unit of work. This should be unreachable,
-        // because the render phase is meant to be idempotent, and it should
-        // have thrown again. Since it didn't, rethrow the original error, so
-        // React's internal stack is not misaligned.
-        rethrowOriginalError();
-      }
+    if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
+      // Disregard deadline.didTimeout. Only expired work should be flushed
+      // during a timeout. This path is only hit for non-expired work.
+      return false;
     }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
+    deadlineDidExpire = true;
+    return true;
+  }
+
+  function onUncaughtError(error) {
+    invariant(
+      nextFlushedRoot !== null,
+      "Should be working on a root. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+    // Unschedule this root so we don't work on it again until there's
+    // another update.
+    nextFlushedRoot.remainingExpirationTime = NoWork;
+    if (!hasUnhandledError) {
+      hasUnhandledError = true;
+      unhandledError = error;
     }
+  }
 
-    if (next === null) {
-      // If this doesn't spawn new work, complete the current work.
-      next = completeUnitOfWork(workInProgress);
+  function onBlock(remainingExpirationTime) {
+    invariant(
+      nextFlushedRoot !== null,
+      "Should be working on a root. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
+    // This root was blocked. Unschedule it until there's another update.
+    nextFlushedRoot.remainingExpirationTime = remainingExpirationTime;
+  }
+
+  // TODO: Batching should be implemented at the renderer level, not inside
+  // the reconciler.
+  function batchedUpdates(fn, a) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      return fn(a);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performSyncWork();
+      }
     }
-
-    ReactCurrentOwner.current = null;
-
-    return next;
   }
 
-  function workLoop(isAsync) {
-    if (!isAsync) {
-      // Flush all expired work.
-      while (nextUnitOfWork !== null) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      }
-    } else {
-      // Flush asynchronous work until the deadline runs out of time.
-      while (nextUnitOfWork !== null && !shouldYield()) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+  // TODO: Batching should be implemented at the renderer level, not inside
+  // the reconciler.
+  function unbatchedUpdates(fn, a) {
+    if (isBatchingUpdates && !isUnbatchingUpdates) {
+      isUnbatchingUpdates = true;
+      try {
+        return fn(a);
+      } finally {
+        isUnbatchingUpdates = false;
       }
     }
+    return fn(a);
   }
 
-  function renderRoot(root, expirationTime, isAsync) {
+  // TODO: Batching should be implemented at the renderer level, not within
+  // the reconciler.
+  function flushSync(fn, a) {
     invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
+      !isRendering,
+      "flushSync was called from inside a lifecycle method. It cannot be " +
+        "called when React is already rendering."
     );
-    isWorking = true;
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      return syncUpdates(fn, a);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      performSyncWork();
+    }
+  }
 
-    // Check if we're starting from a fresh stack, or if we're resuming from
-    // previously yielded work.
+  function interactiveUpdates(fn, a, b) {
+    if (isBatchingInteractiveUpdates) {
+      return fn(a, b);
+    }
+    // If there are any pending interactive updates, synchronously flush them.
+    // This needs to happen before we read any handlers, because the effect of
+    // the previous event may influence which handlers are called during
+    // this event.
     if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      nextUnitOfWork === null
+      !isBatchingUpdates &&
+      !isRendering &&
+      lowestPendingInteractiveExpirationTime !== NoWork
     ) {
-      // Reset the stack and start working from the root.
-      resetStack();
-      nextRoot = root;
-      nextRenderExpirationTime = expirationTime;
-      nextUnitOfWork = createWorkInProgress(
-        nextRoot.current,
-        null,
-        nextRenderExpirationTime
-      );
-      root.pendingCommitExpirationTime = NoWork;
+      // Synchronously flush pending interactive updates.
+      performWork(lowestPendingInteractiveExpirationTime, false, null);
+      lowestPendingInteractiveExpirationTime = NoWork;
+    }
+    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingInteractiveUpdates = true;
+    isBatchingUpdates = true;
+    try {
+      return fn(a, b);
+    } finally {
+      isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performSyncWork();
+      }
     }
+  }
 
-    var didFatal = false;
+  function flushInteractiveUpdates() {
+    if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
+      // Synchronously flush pending interactive updates.
+      performWork(lowestPendingInteractiveExpirationTime, false, null);
+      lowestPendingInteractiveExpirationTime = NoWork;
+    }
+  }
 
-    startWorkLoopTimer(nextUnitOfWork);
+  function flushControlled(fn) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = true;
+    try {
+      syncUpdates(fn);
+    } finally {
+      isBatchingUpdates = previousIsBatchingUpdates;
+      if (!isBatchingUpdates && !isRendering) {
+        performWork(Sync, false, null);
+      }
+    }
+  }
 
-    do {
-      try {
-        workLoop(isAsync);
-      } catch (thrownValue) {
-        if (nextUnitOfWork === null) {
-          // This is a fatal error.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-          break;
-        }
+  return {
+    recalculateCurrentTime: recalculateCurrentTime,
+    computeExpirationForFiber: computeExpirationForFiber,
+    scheduleWork: scheduleWork,
+    requestWork: requestWork,
+    flushRoot: flushRoot,
+    batchedUpdates: batchedUpdates,
+    unbatchedUpdates: unbatchedUpdates,
+    flushSync: flushSync,
+    flushControlled: flushControlled,
+    deferredUpdates: deferredUpdates,
+    syncUpdates: syncUpdates,
+    interactiveUpdates: interactiveUpdates,
+    flushInteractiveUpdates: flushInteractiveUpdates,
+    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+    legacyContext: legacyContext
+  };
+};
 
-        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-          var failedUnitOfWork = nextUnitOfWork;
-          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
-        }
+var didWarnAboutNestedUpdates = void 0;
 
-        var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber["return"];
-        if (returnFiber === null) {
-          // This is the root. The root could capture its own errors. However,
-          // we don't know if it errors before or after we pushed the host
-          // context. This information is needed to avoid a stack mismatch.
-          // Because we're not sure, treat this as a fatal error. We could track
-          // which phase it fails in, but doesn't seem worth it. At least
-          // for now.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        throwException(returnFiber, sourceFiber, thrownValue);
-        nextUnitOfWork = completeUnitOfWork(sourceFiber);
-      }
-      break;
-    } while (true);
+{
+  didWarnAboutNestedUpdates = false;
+}
 
-    // We're done performing work. Time to clean up.
-    var didCompleteRoot = false;
-    isWorking = false;
+// 0 is PROD, 1 is DEV.
+// Might add PROFILE later.
 
-    // Yield back to main thread.
-    if (didFatal) {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There was a fatal error.
-      {
-        stack.resetStackAfterFatalErrorInDev();
-      }
-      return null;
-    } else if (nextUnitOfWork === null) {
-      // We reached the root.
-      if (isRootReadyForCommit) {
-        didCompleteRoot = true;
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        // The root successfully completed. It's ready for commit.
-        root.pendingCommitExpirationTime = expirationTime;
-        var finishedWork = root.current.alternate;
-        return finishedWork;
-      } else {
-        // The root did not complete.
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        invariant(
-          false,
-          "Expired work should have completed. This error is likely caused " +
-            "by a bug in React. Please file an issue."
-        );
-      }
-    } else {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There's more work to do, but we ran out of time. Yield back to
-      // the renderer.
-      return null;
-    }
-  }
+var ReactFiberReconciler$1 = function(config) {
+  var getPublicInstance = config.getPublicInstance;
 
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    // TODO: We only support dispatching errors.
-    var capturedValue = createCapturedValue(value, sourceFiber);
-    var update = {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: false,
-      isForced: false,
-      capturedValue: capturedValue,
-      next: null
-    };
-    insertUpdateIntoFiber(boundaryFiber, update);
-    scheduleWork(boundaryFiber, expirationTime);
-  }
+  var _ReactFiberScheduler = ReactFiberScheduler(config),
+    computeUniqueAsyncExpiration =
+      _ReactFiberScheduler.computeUniqueAsyncExpiration,
+    recalculateCurrentTime = _ReactFiberScheduler.recalculateCurrentTime,
+    computeExpirationForFiber = _ReactFiberScheduler.computeExpirationForFiber,
+    scheduleWork = _ReactFiberScheduler.scheduleWork,
+    requestWork = _ReactFiberScheduler.requestWork,
+    flushRoot = _ReactFiberScheduler.flushRoot,
+    batchedUpdates = _ReactFiberScheduler.batchedUpdates,
+    unbatchedUpdates = _ReactFiberScheduler.unbatchedUpdates,
+    flushSync = _ReactFiberScheduler.flushSync,
+    flushControlled = _ReactFiberScheduler.flushControlled,
+    deferredUpdates = _ReactFiberScheduler.deferredUpdates,
+    syncUpdates = _ReactFiberScheduler.syncUpdates,
+    interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
+    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
+    legacyContext = _ReactFiberScheduler.legacyContext;
 
-  function dispatch(sourceFiber, value, expirationTime) {
-    invariant(
-      !isWorking || isCommitting,
-      "dispatch: Cannot dispatch during the render phase."
-    );
+  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
+    isContextProvider = legacyContext.isContextProvider,
+    processChildContext = legacyContext.processChildContext;
 
-    // TODO: Handle arrays
+  function getContextForSubtree(parentComponent) {
+    if (!parentComponent) {
+      return emptyObject;
+    }
 
-    var fiber = sourceFiber["return"];
-    while (fiber !== null) {
-      switch (fiber.tag) {
-        case ClassComponent:
-          var ctor = fiber.type;
-          var instance = fiber.stateNode;
-          if (
-            typeof ctor.getDerivedStateFromCatch === "function" ||
-            (typeof instance.componentDidCatch === "function" &&
-              !isAlreadyFailedLegacyErrorBoundary(instance))
-          ) {
-            scheduleCapture(sourceFiber, fiber, value, expirationTime);
-            return;
-          }
-          break;
-        // TODO: Handle async boundaries
-        case HostRoot:
-          scheduleCapture(sourceFiber, fiber, value, expirationTime);
-          return;
+    var fiber = get$1(parentComponent);
+    var parentContext = findCurrentUnmaskedContext(fiber);
+    return isContextProvider(fiber)
+      ? processChildContext(fiber, parentContext)
+      : parentContext;
+  }
+
+  function scheduleRootUpdate(current, element, expirationTime, callback) {
+    {
+      if (
+        ReactDebugCurrentFiber.phase === "render" &&
+        ReactDebugCurrentFiber.current !== null &&
+        !didWarnAboutNestedUpdates
+      ) {
+        didWarnAboutNestedUpdates = true;
+        warning(
+          false,
+          "Render methods should be a pure function of props and state; " +
+            "triggering nested component updates from render is not allowed. " +
+            "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
+            "Check the render method of %s.",
+          getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
+        );
       }
-      fiber = fiber["return"];
     }
 
-    if (sourceFiber.tag === HostRoot) {
-      // Error was thrown at the root. There is no parent, so the root
-      // itself should capture it.
-      scheduleCapture(sourceFiber, sourceFiber, value, expirationTime);
+    var update = createUpdate(expirationTime);
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    update.payload = { element: element };
+
+    callback = callback === undefined ? null : callback;
+    if (callback !== null) {
+      !(typeof callback === "function")
+        ? warning(
+            false,
+            "render(...): Expected the last optional `callback` argument to be a " +
+              "function. Instead received: %s.",
+            callback
+          )
+        : void 0;
+      update.callback = callback;
     }
-  }
+    enqueueUpdate(current, update, expirationTime);
 
-  function onCommitPhaseError(fiber, error) {
-    return dispatch(fiber, error, Sync);
+    scheduleWork(current, expirationTime);
+    return expirationTime;
   }
 
-  function computeAsyncExpiration(currentTime) {
-    // Given the current clock time, returns an expiration time. We use rounding
-    // to batch like updates together.
-    // Should complete within ~1000ms. 1200ms max.
-    var expirationMs = 5000;
-    var bucketSizeMs = 250;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
+  function updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    expirationTime,
+    callback
+  ) {
+    // TODO: If this is a nested container, this won't be the root.
+    var current = container.current;
 
-  function computeInteractiveExpiration(currentTime) {
-    var expirationMs = void 0;
-    // We intentionally set a higher expiration time for interactive updates in
-    // dev than in production.
-    // If the main thread is being blocked so long that you hit the expiration,
-    // it's a problem that could be solved with better scheduling.
-    // People will be more likely to notice this and fix it with the long
-    // expiration time in development.
-    // In production we opt for better UX at the risk of masking scheduling
-    // problems, by expiring fast.
     {
-      // Should complete within ~500ms. 600ms max.
-      expirationMs = 500;
+      if (ReactFiberInstrumentation_1.debugTool) {
+        if (current.alternate === null) {
+          ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
+        } else if (element === null) {
+          ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
+        } else {
+          ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
+        }
+      }
     }
-    var bucketSizeMs = 100;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
 
-  // Creates a unique async expiration time.
-  function computeUniqueAsyncExpiration() {
-    var currentTime = recalculateCurrentTime();
-    var result = computeAsyncExpiration(currentTime);
-    if (result <= lastUniqueAsyncExpiration) {
-      // Since we assume the current time monotonically increases, we only hit
-      // this branch when computeUniqueAsyncExpiration is fired multiple times
-      // within a 200ms window (or whatever the async bucket size is).
-      result = lastUniqueAsyncExpiration + 1;
+    var context = getContextForSubtree(parentComponent);
+    if (container.context === null) {
+      container.context = context;
+    } else {
+      container.pendingContext = context;
     }
-    lastUniqueAsyncExpiration = result;
-    return lastUniqueAsyncExpiration;
+
+    return scheduleRootUpdate(current, element, expirationTime, callback);
   }
 
-  function computeExpirationForFiber(fiber) {
-    var expirationTime = void 0;
-    if (expirationContext !== NoWork) {
-      // An explicit expiration context was set;
-      expirationTime = expirationContext;
-    } else if (isWorking) {
-      if (isCommitting) {
-        // Updates that occur during the commit phase should have sync priority
-        // by default.
-        expirationTime = Sync;
-      } else {
-        // Updates during the render phase should expire at the same time as
-        // the work that is being rendered.
-        expirationTime = nextRenderExpirationTime;
-      }
-    } else {
-      // No explicit expiration context was set, and we're not currently
-      // performing work. Calculate a new expiration time.
-      if (fiber.mode & AsyncMode) {
-        if (isBatchingInteractiveUpdates) {
-          // This is an interactive update
-          var currentTime = recalculateCurrentTime();
-          expirationTime = computeInteractiveExpiration(currentTime);
-        } else {
-          // This is an async update
-          var _currentTime = recalculateCurrentTime();
-          expirationTime = computeAsyncExpiration(_currentTime);
-        }
+  function findHostInstance(component) {
+    var fiber = get$1(component);
+    if (fiber === undefined) {
+      if (typeof component.render === "function") {
+        invariant(false, "Unable to find node on an unmounted component.");
       } else {
-        // This is a sync update
-        expirationTime = Sync;
+        invariant(
+          false,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        );
       }
     }
-    if (isBatchingInteractiveUpdates) {
-      // This is an interactive update. Keep track of the lowest pending
-      // interactive expiration time. This allows us to synchronously flush
-      // all interactive updates when needed.
-      if (
-        lowestPendingInteractiveExpirationTime === NoWork ||
-        expirationTime > lowestPendingInteractiveExpirationTime
-      ) {
-        lowestPendingInteractiveExpirationTime = expirationTime;
-      }
+    var hostFiber = findCurrentHostFiber(fiber);
+    if (hostFiber === null) {
+      return null;
     }
-    return expirationTime;
+    return hostFiber.stateNode;
   }
 
-  function scheduleWork(fiber, expirationTime) {
-    return scheduleWorkImpl(fiber, expirationTime, false);
-  }
+  return {
+    createContainer: function(containerInfo, isAsync, hydrate) {
+      return createFiberRoot(containerInfo, isAsync, hydrate);
+    },
+    updateContainer: function(element, container, parentComponent, callback) {
+      var current = container.current;
+      var currentTime = recalculateCurrentTime();
+      var expirationTime = computeExpirationForFiber(currentTime, current);
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        expirationTime,
+        callback
+      );
+    },
+    updateContainerAtExpirationTime: function(
+      element,
+      container,
+      parentComponent,
+      expirationTime,
+      callback
+    ) {
+      return updateContainerAtExpirationTime(
+        element,
+        container,
+        parentComponent,
+        expirationTime,
+        callback
+      );
+    },
 
-  function scheduleWorkImpl(fiber, expirationTime, isErrorRecovery) {
-    recordScheduleUpdate();
+    flushRoot: flushRoot,
 
-    {
-      if (!isErrorRecovery && fiber.tag === ClassComponent) {
-        var instance = fiber.stateNode;
-        warnAboutInvalidUpdates(instance);
-      }
-    }
+    requestWork: requestWork,
 
-    var node = fiber;
-    while (node !== null) {
-      // Walk the parent path to the root and update each node's
-      // expiration time.
-      if (
-        node.expirationTime === NoWork ||
-        node.expirationTime > expirationTime
-      ) {
-        node.expirationTime = expirationTime;
-      }
-      if (node.alternate !== null) {
-        if (
-          node.alternate.expirationTime === NoWork ||
-          node.alternate.expirationTime > expirationTime
-        ) {
-          node.alternate.expirationTime = expirationTime;
-        }
+    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+
+    batchedUpdates: batchedUpdates,
+
+    unbatchedUpdates: unbatchedUpdates,
+
+    deferredUpdates: deferredUpdates,
+
+    syncUpdates: syncUpdates,
+
+    interactiveUpdates: interactiveUpdates,
+
+    flushInteractiveUpdates: flushInteractiveUpdates,
+
+    flushControlled: flushControlled,
+
+    flushSync: flushSync,
+
+    getPublicRootInstance: function(container) {
+      var containerFiber = container.current;
+      if (!containerFiber.child) {
+        return null;
       }
-      if (node["return"] === null) {
-        if (node.tag === HostRoot) {
-          var root = node.stateNode;
-          if (
-            !isWorking &&
-            nextRenderExpirationTime !== NoWork &&
-            expirationTime < nextRenderExpirationTime
-          ) {
-            // This is an interruption. (Used for performance tracking.)
-            interruptedBy = fiber;
-            resetStack();
-          }
-          if (
-            // If we're in the render phase, we don't need to schedule this root
-            // for an update, because we'll do it before we exit...
-            !isWorking ||
-            isCommitting ||
-            // ...unless this is a different root than the one we're rendering.
-            nextRoot !== root
-          ) {
-            // Add this root to the root schedule.
-            requestWork(root, expirationTime);
-          }
-          if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
-            invariant(
-              false,
-              "Maximum update depth exceeded. This can happen when a " +
-                "component repeatedly calls setState inside " +
-                "componentWillUpdate or componentDidUpdate. React limits " +
-                "the number of nested updates to prevent infinite loops."
-            );
-          }
-        } else {
-          {
-            if (!isErrorRecovery && fiber.tag === ClassComponent) {
-              warnAboutUpdateOnUnmounted(fiber);
+      switch (containerFiber.child.tag) {
+        case HostComponent:
+          return getPublicInstance(containerFiber.child.stateNode);
+        default:
+          return containerFiber.child.stateNode;
+      }
+    },
+
+    findHostInstance: findHostInstance,
+
+    findHostInstanceWithNoPortals: function(fiber) {
+      var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
+      if (hostFiber === null) {
+        return null;
+      }
+      return hostFiber.stateNode;
+    },
+    injectIntoDevTools: function(devToolsConfig) {
+      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+
+      return injectInternals(
+        Object.assign({}, devToolsConfig, {
+          findHostInstanceByFiber: function(fiber) {
+            var hostFiber = findCurrentHostFiber(fiber);
+            if (hostFiber === null) {
+              return null;
+            }
+            return hostFiber.stateNode;
+          },
+          findFiberByHostInstance: function(instance) {
+            if (!findFiberByHostInstance) {
+              // Might not be implemented by the renderer.
+              return null;
             }
+            return findFiberByHostInstance(instance);
           }
-          return;
-        }
-      }
-      node = node["return"];
+        })
+      );
     }
-  }
+  };
+};
 
-  function recalculateCurrentTime() {
-    // Subtract initial time so it fits inside 32bits
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
-    return mostRecentCurrentTime;
-  }
+var ReactFiberReconciler$2 = Object.freeze({
+  default: ReactFiberReconciler$1
+});
 
-  function deferredUpdates(fn) {
-    var previousExpirationContext = expirationContext;
-    var currentTime = recalculateCurrentTime();
-    expirationContext = computeAsyncExpiration(currentTime);
-    try {
-      return fn();
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = Sync;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
+var ReactFiberReconciler$3 =
+  (ReactFiberReconciler$2 && ReactFiberReconciler$1) || ReactFiberReconciler$2;
 
-  // TODO: Everything below this is written as if it has been lifted to the
-  // renderers. I'll do this in a follow-up.
+// TODO: bundle Flow types with the package.
 
-  // Linked-list of roots
-  var firstScheduledRoot = null;
-  var lastScheduledRoot = null;
+// TODO: decide on the top-level export form.
+// This is hacky but makes it work with both Rollup and Jest.
+var reactReconciler = ReactFiberReconciler$3.default
+  ? ReactFiberReconciler$3.default
+  : ReactFiberReconciler$3;
 
-  var callbackExpirationTime = NoWork;
-  var callbackID = -1;
-  var isRendering = false;
-  var nextFlushedRoot = null;
-  var nextFlushedExpirationTime = NoWork;
-  var lowestPendingInteractiveExpirationTime = NoWork;
-  var deadlineDidExpire = false;
-  var hasUnhandledError = false;
-  var unhandledError = null;
-  var deadline = null;
+function createPortal(
+  children,
+  containerInfo,
+  // TODO: figure out the API for cross-renderer implementation.
+  implementation
+) {
+  var key =
+    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
 
-  var isBatchingUpdates = false;
-  var isUnbatchingUpdates = false;
-  var isBatchingInteractiveUpdates = false;
+  return {
+    // This tag allow us to uniquely identify this as a React Portal
+    $$typeof: REACT_PORTAL_TYPE,
+    key: key == null ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
 
-  var completedBatches = null;
+// TODO: this is special because it gets imported during build.
 
-  // Use these to prevent an infinite loop of nested updates
-  var NESTED_UPDATE_LIMIT = 1000;
-  var nestedUpdateCount = 0;
+var ReactVersion = "16.3.2";
 
-  var timeHeuristicForUnitOfWork = 1;
+// Modules provided by RN:
+var emptyObject$1 = {};
 
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (callbackExpirationTime !== NoWork) {
-      // A callback is already scheduled. Check its expiration time (timeout).
-      if (expirationTime > callbackExpirationTime) {
-        // Existing callback has sufficient timeout. Exit.
-        return;
-      } else {
-        // Existing callback has insufficient timeout. Cancel and schedule a
-        // new one.
-        cancelDeferredCallback(callbackID);
+/**
+ * Create a payload that contains all the updates between two sets of props.
+ *
+ * These helpers are all encapsulated into a single module, because they use
+ * mutation as a performance optimization which leads to subtle shared
+ * dependencies between the code paths. To avoid this mutable state leaking
+ * across modules, I've kept them isolated to this module.
+ */
+
+// Tracks removed keys
+var removedKeys = null;
+var removedKeyCount = 0;
+
+function defaultDiffer(prevProp, nextProp) {
+  if (typeof nextProp !== "object" || nextProp === null) {
+    // Scalars have already been checked for equality
+    return true;
+  } else {
+    // For objects and arrays, the default diffing algorithm is a deep compare
+    return deepDiffer(prevProp, nextProp);
+  }
+}
+
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node)) {
+    var i = node.length;
+    while (i-- && removedKeyCount > 0) {
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+    }
+  } else if (node && removedKeyCount > 0) {
+    var obj = node;
+    for (var propKey in removedKeys) {
+      if (!removedKeys[propKey]) {
+        continue;
       }
-      // The request callback timer is already running. Don't start a new one.
-    } else {
-      startRequestCallbackTimer();
+      var _nextProp = obj[propKey];
+      if (_nextProp === undefined) {
+        continue;
+      }
+
+      var attributeConfig = validAttributes[propKey];
+      if (!attributeConfig) {
+        continue; // not a valid native prop
+      }
+
+      if (typeof _nextProp === "function") {
+        _nextProp = true;
+      }
+      if (typeof _nextProp === "undefined") {
+        _nextProp = null;
+      }
+
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = _nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(_nextProp)
+            : _nextProp;
+        updatePayload[propKey] = nextValue;
+      }
+      removedKeys[propKey] = false;
+      removedKeyCount--;
     }
+  }
+}
 
-    // Compute a timeout for the given expiration time.
-    var currentMs = now() - originalStartTimeMs;
-    var expirationMs = expirationTimeToMs(expirationTime);
-    var timeout = expirationMs - currentMs;
+function diffNestedArrayProperty(
+  updatePayload,
+  prevArray,
+  nextArray,
+  validAttributes
+) {
+  var minLength =
+    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
+  var i = void 0;
+  for (i = 0; i < minLength; i++) {
+    // Diff any items in the array in the forward direction. Repeated keys
+    // will be overwritten by later values.
+    updatePayload = diffNestedProperty(
+      updatePayload,
+      prevArray[i],
+      nextArray[i],
+      validAttributes
+    );
+  }
+  for (; i < prevArray.length; i++) {
+    // Clear out all remaining properties.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevArray[i],
+      validAttributes
+    );
+  }
+  for (; i < nextArray.length; i++) {
+    // Add all remaining properties.
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextArray[i],
+      validAttributes
+    );
+  }
+  return updatePayload;
+}
 
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: timeout
-    });
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) {
+    // If no properties have been added, then we can bail out quickly on object
+    // equality.
+    return updatePayload;
   }
 
-  // requestWork is called by the scheduler whenever a root receives an update.
-  // It's up to the renderer to call renderRoot at some point in the future.
-  function requestWork(root, expirationTime) {
-    addRootToSchedule(root, expirationTime);
-
-    if (isRendering) {
-      // Prevent reentrancy. Remaining work will be scheduled at the end of
-      // the currently rendering batch.
-      return;
+  if (!prevProp || !nextProp) {
+    if (nextProp) {
+      return addNestedProperty(updatePayload, nextProp, validAttributes);
     }
-
-    if (isBatchingUpdates) {
-      // Flush work at the end of the batch.
-      if (isUnbatchingUpdates) {
-        // ...unless we're inside unbatchedUpdates, in which case we should
-        // flush it now.
-        nextFlushedRoot = root;
-        nextFlushedExpirationTime = Sync;
-        performWorkOnRoot(root, Sync, false);
-      }
-      return;
+    if (prevProp) {
+      return clearNestedProperty(updatePayload, prevProp, validAttributes);
     }
+    return updatePayload;
+  }
 
-    // TODO: Get rid of Sync and use current time?
-    if (expirationTime === Sync) {
-      performSyncWork();
-    } else {
-      scheduleCallbackWithExpiration(expirationTime);
-    }
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
+    // Both are leaves, we can diff the leaves.
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
   }
 
-  function addRootToSchedule(root, expirationTime) {
-    // Add the root to the schedule.
-    // Check if this root is already part of the schedule.
-    if (root.nextScheduledRoot === null) {
-      // This root is not already scheduled. Add it.
-      root.remainingExpirationTime = expirationTime;
-      if (lastScheduledRoot === null) {
-        firstScheduledRoot = lastScheduledRoot = root;
-        root.nextScheduledRoot = root;
-      } else {
-        lastScheduledRoot.nextScheduledRoot = root;
-        lastScheduledRoot = root;
-        lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-      }
-    } else {
-      // This root is already scheduled, but its priority may have increased.
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        remainingExpirationTime === NoWork ||
-        expirationTime < remainingExpirationTime
-      ) {
-        // Update the priority.
-        root.remainingExpirationTime = expirationTime;
-      }
-    }
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    // Both are arrays, we can diff the arrays.
+    return diffNestedArrayProperty(
+      updatePayload,
+      prevProp,
+      nextProp,
+      validAttributes
+    );
   }
 
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = NoWork;
-    var highestPriorityRoot = null;
-    if (lastScheduledRoot !== null) {
-      var previousScheduledRoot = lastScheduledRoot;
-      var root = firstScheduledRoot;
-      while (root !== null) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (remainingExpirationTime === NoWork) {
-          // This root no longer has work. Remove it from the scheduler.
+  if (Array.isArray(prevProp)) {
+    return diffProperties(
+      updatePayload,
+      // $FlowFixMe - We know that this is always an object when the input is.
+      flattenStyle(prevProp),
+      // $FlowFixMe - We know that this isn't an array because of above flow.
+      nextProp,
+      validAttributes
+    );
+  }
 
-          // TODO: This check is redudant, but Flow is confused by the branch
-          // below where we set lastScheduledRoot to null, even though we break
-          // from the loop right after.
-          invariant(
-            previousScheduledRoot !== null && lastScheduledRoot !== null,
-            "Should have a previous and last root. This error is likely " +
-              "caused by a bug in React. Please file an issue."
-          );
-          if (root === root.nextScheduledRoot) {
-            // This is the only root in the list.
-            root.nextScheduledRoot = null;
-            firstScheduledRoot = lastScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot) {
-            // This is the first root in the list.
-            var next = root.nextScheduledRoot;
-            firstScheduledRoot = next;
-            lastScheduledRoot.nextScheduledRoot = next;
-            root.nextScheduledRoot = null;
-          } else if (root === lastScheduledRoot) {
-            // This is the last root in the list.
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else {
-            previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
-            root.nextScheduledRoot = null;
-          }
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            highestPriorityWork === NoWork ||
-            remainingExpirationTime < highestPriorityWork
-          ) {
-            // Update the priority, if it's higher
-            highestPriorityWork = remainingExpirationTime;
-            highestPriorityRoot = root;
-          }
-          if (root === lastScheduledRoot) {
-            break;
-          }
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
-        }
-      }
-    }
+  return diffProperties(
+    updatePayload,
+    prevProp,
+    // $FlowFixMe - We know that this is always an object when the input is.
+    flattenStyle(nextProp),
+    validAttributes
+  );
+}
 
-    // If the next root is the same as the previous root, this is a nested
-    // update. To prevent an infinite loop, increment the nested update count.
-    var previousFlushedRoot = nextFlushedRoot;
-    if (
-      previousFlushedRoot !== null &&
-      previousFlushedRoot === highestPriorityRoot &&
-      highestPriorityWork === Sync
-    ) {
-      nestedUpdateCount++;
-    } else {
-      // Reset whenever we switch roots.
-      nestedUpdateCount = 0;
-    }
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
+/**
+ * addNestedProperty takes a single set of props and valid attribute
+ * attribute configurations. It processes each prop and adds it to the
+ * updatePayload.
+ */
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) {
+    return updatePayload;
   }
 
-  function performAsyncWork(dl) {
-    performWork(NoWork, true, dl);
+  if (!Array.isArray(nextProp)) {
+    // Add each property of the leaf.
+    return addProperties(updatePayload, nextProp, validAttributes);
   }
 
-  function performSyncWork() {
-    performWork(Sync, false, null);
+  for (var i = 0; i < nextProp.length; i++) {
+    // Add all the properties of the array.
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
   }
 
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
+  return updatePayload;
+}
 
-    // Keep working on roots until there's no more work, or until the we reach
-    // the deadline.
-    findHighestPriorityRoot();
+/**
+ * clearNestedProperty takes a single set of props and valid attributes. It
+ * adds a null sentinel to the updatePayload, for each prop key.
+ */
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) {
+    return updatePayload;
+  }
 
-    if (enableUserTimingAPI && deadline !== null) {
-      var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
-      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
-      stopRequestCallbackTimer(didExpire, timeout);
-    }
+  if (!Array.isArray(prevProp)) {
+    // Add each property of the leaf.
+    return clearProperties(updatePayload, prevProp, validAttributes);
+  }
 
-    if (isAsync) {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime)
-      ) {
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        );
-        findHighestPriorityRoot();
-      }
-    } else {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime)
-      ) {
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
-        findHighestPriorityRoot();
-      }
+  for (var i = 0; i < prevProp.length; i++) {
+    // Add all the properties of the array.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  }
+  return updatePayload;
+}
+
+/**
+ * diffProperties takes two sets of props and a set of valid attributes
+ * and write to updatePayload the values that changed or were deleted.
+ * If no updatePayload is provided, a new one is created and returned if
+ * anything changed.
+ */
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig = void 0;
+  var nextProp = void 0;
+  var prevProp = void 0;
+
+  for (var propKey in nextProps) {
+    attributeConfig = validAttributes[propKey];
+    if (!attributeConfig) {
+      continue; // not a valid native prop
     }
 
-    // We're done flushing work. Either we ran out of time in this callback,
-    // or there's no more work left with sufficient priority.
+    prevProp = prevProps[propKey];
+    nextProp = nextProps[propKey];
 
-    // If we're inside a callback, set this to false since we just completed it.
-    if (deadline !== null) {
-      callbackExpirationTime = NoWork;
-      callbackID = -1;
-    }
-    // If there's work left over, schedule a new callback.
-    if (nextFlushedExpirationTime !== NoWork) {
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
+    // functions are converted to booleans as markers that the associated
+    // events should be sent from native.
+    if (typeof nextProp === "function") {
+      nextProp = true;
+      // If nextProp is not a function, then don't bother changing prevProp
+      // since nextProp will win and go into the updatePayload regardless.
+      if (typeof prevProp === "function") {
+        prevProp = true;
+      }
     }
 
-    // Clean-up.
-    deadline = null;
-    deadlineDidExpire = false;
-
-    finishRendering();
-  }
+    // An explicit value of undefined is treated as a null because it overrides
+    // any other preceding value.
+    if (typeof nextProp === "undefined") {
+      nextProp = null;
+      if (typeof prevProp === "undefined") {
+        prevProp = null;
+      }
+    }
 
-  function flushRoot(root, expirationTime) {
-    invariant(
-      !isRendering,
-      "work.commit(): Cannot commit while already rendering. This likely " +
-        "means you attempted to commit from inside a lifecycle method."
-    );
-    // Perform work on root as if the given expiration time is the current time.
-    // This has the effect of synchronously flushing all work up to and
-    // including the given time.
-    nextFlushedRoot = root;
-    nextFlushedExpirationTime = expirationTime;
-    performWorkOnRoot(root, expirationTime, false);
-    // Flush any sync work that was scheduled by lifecycles
-    performSyncWork();
-    finishRendering();
-  }
+    if (removedKeys) {
+      removedKeys[propKey] = false;
+    }
 
-  function finishRendering() {
-    nestedUpdateCount = 0;
+    if (updatePayload && updatePayload[propKey] !== undefined) {
+      // Something else already triggered an update to this key because another
+      // value diffed. Since we're now later in the nested arrays our value is
+      // more important so we need to calculate it and override the existing
+      // value. It doesn't matter if nothing changed, we'll set it anyway.
 
-    if (completedBatches !== null) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          if (!hasUnhandledError) {
-            hasUnhandledError = true;
-            unhandledError = error;
-          }
-        }
+      // Pattern match on: attributeConfig
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(nextProp)
+            : nextProp;
+        updatePayload[propKey] = nextValue;
       }
+      continue;
     }
 
-    if (hasUnhandledError) {
-      var error = unhandledError;
-      unhandledError = null;
-      hasUnhandledError = false;
-      throw error;
+    if (prevProp === nextProp) {
+      continue; // nothing changed
+    }
+
+    // Pattern match on: attributeConfig
+    if (typeof attributeConfig !== "object") {
+      // case: !Object is the default case
+      if (defaultDiffer(prevProp, nextProp)) {
+        // a normal leaf has changed
+        (updatePayload || (updatePayload = {}))[propKey] = nextProp;
+      }
+    } else if (
+      typeof attributeConfig.diff === "function" ||
+      typeof attributeConfig.process === "function"
+    ) {
+      // case: CustomAttributeConfiguration
+      var shouldUpdate =
+        prevProp === undefined ||
+        (typeof attributeConfig.diff === "function"
+          ? attributeConfig.diff(prevProp, nextProp)
+          : defaultDiffer(prevProp, nextProp));
+      if (shouldUpdate) {
+        var _nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(nextProp)
+            : nextProp;
+        (updatePayload || (updatePayload = {}))[propKey] = _nextValue;
+      }
+    } else {
+      // default: fallthrough case when nested properties are defined
+      removedKeys = null;
+      removedKeyCount = 0;
+      // We think that attributeConfig is not CustomAttributeConfiguration at
+      // this point so we assume it must be AttributeConfiguration.
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp,
+        nextProp,
+        attributeConfig
+      );
+      if (removedKeyCount > 0 && updatePayload) {
+        restoreDeletedValuesInNestedArray(
+          updatePayload,
+          nextProp,
+          attributeConfig
+        );
+        removedKeys = null;
+      }
     }
   }
 
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
-    );
+  // Also iterate through all the previous props to catch any that have been
+  // removed and make sure native gets the signal so it can reset them to the
+  // default.
+  for (var _propKey in prevProps) {
+    if (nextProps[_propKey] !== undefined) {
+      continue; // we've already covered this key in the previous pass
+    }
+    attributeConfig = validAttributes[_propKey];
+    if (!attributeConfig) {
+      continue; // not a valid native prop
+    }
 
-    isRendering = true;
+    if (updatePayload && updatePayload[_propKey] !== undefined) {
+      // This was already updated to a diff result earlier.
+      continue;
+    }
 
-    // Check if this is async work or sync/expired work.
-    if (!isAsync) {
-      // Flush sync work.
-      var finishedWork = root.finishedWork;
-      if (finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot(root, finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        finishedWork = renderRoot(root, expirationTime, false);
-        if (finishedWork !== null) {
-          // We've completed the root. Commit it.
-          completeRoot(root, finishedWork, expirationTime);
-        }
+    prevProp = prevProps[_propKey];
+    if (prevProp === undefined) {
+      continue; // was already empty anyway
+    }
+    // Pattern match on: attributeConfig
+    if (
+      typeof attributeConfig !== "object" ||
+      typeof attributeConfig.diff === "function" ||
+      typeof attributeConfig.process === "function"
+    ) {
+      // case: CustomAttributeConfiguration | !Object
+      // Flag the leaf property for removal by sending a sentinel.
+      (updatePayload || (updatePayload = {}))[_propKey] = null;
+      if (!removedKeys) {
+        removedKeys = {};
       }
-    } else {
-      // Flush async work.
-      var _finishedWork = root.finishedWork;
-      if (_finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot(root, _finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        _finishedWork = renderRoot(root, expirationTime, true);
-        if (_finishedWork !== null) {
-          // We've completed the root. Check the deadline one more time
-          // before committing.
-          if (!shouldYield()) {
-            // Still time left. Commit the root.
-            completeRoot(root, _finishedWork, expirationTime);
-          } else {
-            // There's no time left. Mark this root as complete. We'll come
-            // back and commit it later.
-            root.finishedWork = _finishedWork;
-          }
-        }
+      if (!removedKeys[_propKey]) {
+        removedKeys[_propKey] = true;
+        removedKeyCount++;
       }
+    } else {
+      // default:
+      // This is a nested attribute configuration where all the properties
+      // were removed so we need to go through and clear out all of them.
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp,
+        attributeConfig
+      );
     }
+  }
+  return updatePayload;
+}
+
+/**
+ * addProperties adds all the valid props to the payload after being processed.
+ */
+function addProperties(updatePayload, props, validAttributes) {
+  // TODO: Fast path
+  return diffProperties(updatePayload, emptyObject$1, props, validAttributes);
+}
+
+/**
+ * clearProperties clears all the previous props by adding a null sentinel
+ * to the payload for each valid key.
+ */
+function clearProperties(updatePayload, prevProps, validAttributes) {
+  // TODO: Fast path
+  return diffProperties(
+    updatePayload,
+    prevProps,
+    emptyObject$1,
+    validAttributes
+  );
+}
 
-    isRendering = false;
-  }
+function create(props, validAttributes) {
+  return addProperties(
+    null, // updatePayload
+    props,
+    validAttributes
+  );
+}
 
-  function completeRoot(root, finishedWork, expirationTime) {
-    // Check if there's a batch that matches this expiration time.
-    var firstBatch = root.firstBatch;
-    if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
-      if (completedBatches === null) {
-        completedBatches = [firstBatch];
-      } else {
-        completedBatches.push(firstBatch);
+function diff(prevProps, nextProps, validAttributes) {
+  return diffProperties(
+    null, // updatePayload
+    prevProps,
+    nextProps,
+    validAttributes
+  );
+}
+
+/**
+ * In the future, we should cleanup callbacks by cancelling them instead of
+ * using this.
+ */
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (!callback) {
+      return undefined;
+    }
+    if (typeof context.__isMounted === "boolean") {
+      // TODO(gaearon): this is gross and should be removed.
+      // It is currently necessary because View uses createClass,
+      // and so any measure() calls on View (which are done by React
+      // DevTools) trigger the isMounted() deprecation warning.
+      if (!context.__isMounted) {
+        return undefined;
       }
-      if (firstBatch._defer) {
-        // This root is blocked from committing by a batch. Unschedule it until
-        // we receive another update.
-        root.finishedWork = finishedWork;
-        root.remainingExpirationTime = NoWork;
-        return;
+      // The else branch is important so that we don't
+      // trigger the deprecation warning by calling isMounted.
+    } else if (typeof context.isMounted === "function") {
+      if (!context.isMounted()) {
+        return undefined;
       }
     }
+    return callback.apply(context, arguments);
+  };
+}
 
-    // Commit the root.
-    root.finishedWork = null;
-    root.remainingExpirationTime = commitRoot(finishedWork);
-  }
-
-  // When working on async work, the reconciler asks the renderer if it should
-  // yield execution. For DOM, we implement this with requestIdleCallback.
-  function shouldYield() {
-    if (deadline === null) {
-      return false;
-    }
-    if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
-      // Disregard deadline.didTimeout. Only expired work should be flushed
-      // during a timeout. This path is only hit for non-expired work.
-      return false;
+function throwOnStylesProp(component, props) {
+  if (props.styles !== undefined) {
+    var owner = component._owner || null;
+    var name = component.constructor.displayName;
+    var msg =
+      "`styles` is not a supported property of `" +
+      name +
+      "`, did " +
+      "you mean `style` (singular)?";
+    if (owner && owner.constructor && owner.constructor.displayName) {
+      msg +=
+        "\n\nCheck the `" +
+        owner.constructor.displayName +
+        "` parent " +
+        " component.";
     }
-    deadlineDidExpire = true;
-    return true;
+    throw new Error(msg);
   }
+}
 
-  function onUncaughtError(error) {
-    invariant(
-      nextFlushedRoot !== null,
-      "Should be working on a root. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-    // Unschedule this root so we don't work on it again until there's
-    // another update.
-    nextFlushedRoot.remainingExpirationTime = NoWork;
-    if (!hasUnhandledError) {
-      hasUnhandledError = true;
-      unhandledError = error;
+function warnForStyleProps(props, validAttributes) {
+  for (var key in validAttributes.style) {
+    if (!(validAttributes[key] || props[key] === undefined)) {
+      console.error(
+        "You are setting the style `{ " +
+          key +
+          ": ... }` as a prop. You " +
+          "should nest it in a style object. " +
+          "E.g. `{ style: { " +
+          key +
+          ": ... } }`"
+      );
     }
   }
+}
 
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function batchedUpdates(fn, a) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return fn(a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
-      }
-    }
+function _classCallCheck(instance, Constructor) {
+  if (!(instance instanceof Constructor)) {
+    throw new TypeError("Cannot call a class as a function");
   }
+}
 
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function unbatchedUpdates(fn, a) {
-    if (isBatchingUpdates && !isUnbatchingUpdates) {
-      isUnbatchingUpdates = true;
-      try {
-        return fn(a);
-      } finally {
-        isUnbatchingUpdates = false;
-      }
-    }
-    return fn(a);
+// Modules provided by RN:
+/**
+ * This component defines the same methods as NativeMethodsMixin but without the
+ * findNodeHandle wrapper. This wrapper is unnecessary for HostComponent views
+ * and would also result in a circular require.js dependency (since
+ * ReactNativeFiber depends on this component and NativeMethodsMixin depends on
+ * ReactNativeFiber).
+ */
+
+var ReactNativeFiberHostComponent = (function() {
+  function ReactNativeFiberHostComponent(tag, viewConfig) {
+    _classCallCheck(this, ReactNativeFiberHostComponent);
+
+    this._nativeTag = tag;
+    this._children = [];
+    this.viewConfig = viewConfig;
   }
 
-  // TODO: Batching should be implemented at the renderer level, not within
-  // the reconciler.
-  function flushSync(fn, a) {
-    invariant(
-      !isRendering,
-      "flushSync was called from inside a lifecycle method. It cannot be " +
-        "called when React is already rendering."
+  ReactNativeFiberHostComponent.prototype.blur = function blur() {
+    TextInputState.blurTextInput(this._nativeTag);
+  };
+
+  ReactNativeFiberHostComponent.prototype.focus = function focus() {
+    TextInputState.focusTextInput(this._nativeTag);
+  };
+
+  ReactNativeFiberHostComponent.prototype.measure = function measure(callback) {
+    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+  };
+
+  ReactNativeFiberHostComponent.prototype.measureInWindow = function measureInWindow(
+    callback
+  ) {
+    UIManager.measureInWindow(
+      this._nativeTag,
+      mountSafeCallback(this, callback)
     );
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return syncUpdates(fn, a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      performSyncWork();
-    }
-  }
+  };
 
-  function interactiveUpdates(fn, a, b) {
-    if (isBatchingInteractiveUpdates) {
-      return fn(a, b);
-    }
-    // If there are any pending interactive updates, synchronously flush them.
-    // This needs to happen before we read any handlers, because the effect of
-    // the previous event may influence which handlers are called during
-    // this event.
-    if (
-      !isBatchingUpdates &&
-      !isRendering &&
-      lowestPendingInteractiveExpirationTime !== NoWork
-    ) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
+  ReactNativeFiberHostComponent.prototype.measureLayout = function measureLayout(
+    relativeToNativeNode,
+    onSuccess,
+    onFail /* currently unused */
+  ) {
+    UIManager.measureLayout(
+      this._nativeTag,
+      relativeToNativeNode,
+      mountSafeCallback(this, onFail),
+      mountSafeCallback(this, onSuccess)
+    );
+  };
+
+  ReactNativeFiberHostComponent.prototype.setNativeProps = function setNativeProps(
+    nativeProps
+  ) {
+    {
+      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
     }
-    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingInteractiveUpdates = true;
-    isBatchingUpdates = true;
-    try {
-      return fn(a, b);
-    } finally {
-      isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
-      }
+
+    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
+
+    // Avoid the overhead of bridge calls if there's no update.
+    // This is an expensive no-op for Android, and causes an unnecessary
+    // view invalidation for certain components (eg RCTTextInput) on iOS.
+    if (updatePayload != null) {
+      UIManager.updateView(
+        this._nativeTag,
+        this.viewConfig.uiViewClassName,
+        updatePayload
+      );
     }
-  }
+  };
 
-  function flushInteractiveUpdates() {
-    if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
-    }
-  }
+  return ReactNativeFiberHostComponent;
+})();
 
-  function flushControlled(fn) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      syncUpdates(fn);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performWork(Sync, false, null);
-      }
+var hasNativePerformanceNow =
+  typeof performance === "object" && typeof performance.now === "function";
+
+var now = hasNativePerformanceNow
+  ? function() {
+      return performance.now();
     }
-  }
+  : function() {
+      return Date.now();
+    };
 
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: flushRoot,
-    batchedUpdates: batchedUpdates,
-    unbatchedUpdates: unbatchedUpdates,
-    flushSync: flushSync,
-    flushControlled: flushControlled,
-    deferredUpdates: deferredUpdates,
-    syncUpdates: syncUpdates,
-    interactiveUpdates: interactiveUpdates,
-    flushInteractiveUpdates: flushInteractiveUpdates,
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-    legacyContext: legacyContext
-  };
+var scheduledCallback = null;
+var frameDeadline = 0;
+
+var frameDeadlineObject = {
+  timeRemaining: function() {
+    return frameDeadline - now();
+  },
+  didTimeout: false
 };
 
-var didWarnAboutNestedUpdates = void 0;
+function setTimeoutCallback() {
+  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
+  // React API probably changing to boolean rather than time remaining.
+  // Longer-term plan is to rewrite this using shared memory,
+  // And just return the value of the bit as the boolean.
+  frameDeadline = now() + 5;
 
-{
-  didWarnAboutNestedUpdates = false;
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  if (callback !== null) {
+    callback(frameDeadlineObject);
+  }
 }
 
-// 0 is PROD, 1 is DEV.
-// Might add PROFILE later.
-
-var ReactFiberReconciler$1 = function(config) {
-  var getPublicInstance = config.getPublicInstance;
+// RN has a poor polyfill for requestIdleCallback so we aren't using it.
+// This implementation is only intended for short-term use anyway.
+// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
+function scheduleDeferredCallback(callback) {
+  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
+  scheduledCallback = callback;
+  return setTimeout(setTimeoutCallback, 1);
+}
 
-  var _ReactFiberScheduler = ReactFiberScheduler(config),
-    computeUniqueAsyncExpiration =
-      _ReactFiberScheduler.computeUniqueAsyncExpiration,
-    recalculateCurrentTime = _ReactFiberScheduler.recalculateCurrentTime,
-    computeExpirationForFiber = _ReactFiberScheduler.computeExpirationForFiber,
-    scheduleWork = _ReactFiberScheduler.scheduleWork,
-    requestWork = _ReactFiberScheduler.requestWork,
-    flushRoot = _ReactFiberScheduler.flushRoot,
-    batchedUpdates = _ReactFiberScheduler.batchedUpdates,
-    unbatchedUpdates = _ReactFiberScheduler.unbatchedUpdates,
-    flushSync = _ReactFiberScheduler.flushSync,
-    flushControlled = _ReactFiberScheduler.flushControlled,
-    deferredUpdates = _ReactFiberScheduler.deferredUpdates,
-    syncUpdates = _ReactFiberScheduler.syncUpdates,
-    interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
-    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
-    legacyContext = _ReactFiberScheduler.legacyContext;
+function cancelDeferredCallback(callbackID) {
+  scheduledCallback = null;
+  clearTimeout(callbackID);
+}
 
-  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
+// Modules provided by RN:
+// Counter for uniquely identifying views.
+// % 10 === 1 means it is a rootTag.
+// % 2 === 0 means it is a Fabric tag.
+var nextReactTag = 3;
+function allocateTag() {
+  var tag = nextReactTag;
+  if (tag % 10 === 1) {
+    tag += 2;
+  }
+  nextReactTag = tag + 2;
+  return tag;
+}
 
-  function getContextForSubtree(parentComponent) {
-    if (!parentComponent) {
-      return emptyObject;
-    }
+function recursivelyUncacheFiberNode(node) {
+  if (typeof node === "number") {
+    // Leaf node (eg text)
+    uncacheFiberNode(node);
+  } else {
+    uncacheFiberNode(node._nativeTag);
 
-    var fiber = get$1(parentComponent);
-    var parentContext = findCurrentUnmaskedContext(fiber);
-    return isContextProvider(fiber)
-      ? processChildContext(fiber, parentContext)
-      : parentContext;
+    node._children.forEach(recursivelyUncacheFiberNode);
   }
+}
 
-  function scheduleRootUpdate(
-    current,
-    element,
-    currentTime,
-    expirationTime,
-    callback
+var ReactNativeHostConfig = {
+  appendInitialChild: function(parentInstance, child) {
+    parentInstance._children.push(child);
+  },
+  createInstance: function(
+    type,
+    props,
+    rootContainerInstance,
+    hostContext,
+    internalInstanceHandle
   ) {
+    var tag = allocateTag();
+    var viewConfig = ReactNativeViewConfigRegistry.get(type);
+
     {
-      if (
-        ReactDebugCurrentFiber.phase === "render" &&
-        ReactDebugCurrentFiber.current !== null &&
-        !didWarnAboutNestedUpdates
-      ) {
-        didWarnAboutNestedUpdates = true;
-        warning(
-          false,
-          "Render methods should be a pure function of props and state; " +
-            "triggering nested component updates from render is not allowed. " +
-            "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
-            "Check the render method of %s.",
-          getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
-        );
+      for (var key in viewConfig.validAttributes) {
+        if (props.hasOwnProperty(key)) {
+          deepFreezeAndThrowOnMutationInDev(props[key]);
+        }
       }
     }
 
-    callback = callback === undefined ? null : callback;
-    {
-      !(callback === null || typeof callback === "function")
-        ? warning(
-            false,
-            "render(...): Expected the last optional `callback` argument to be a " +
-              "function. Instead received: %s.",
-            callback
-          )
-        : void 0;
+    invariant(
+      type !== "RCTView" || !hostContext.isInAParentText,
+      "Nesting of <View> within <Text> is not currently supported."
+    );
+
+    var updatePayload = create(props, viewConfig.validAttributes);
+
+    UIManager.createView(
+      tag, // reactTag
+      viewConfig.uiViewClassName, // viewName
+      rootContainerInstance, // rootTag
+      updatePayload
+    );
+
+    var component = new ReactNativeFiberHostComponent(tag, viewConfig);
+
+    precacheFiberNode(internalInstanceHandle, tag);
+    updateFiberProps(tag, props);
+
+    // Not sure how to avoid this cast. Flow is okay if the component is defined
+    // in the same file but if it's external it can't see the types.
+    return component;
+  },
+  createTextInstance: function(
+    text,
+    rootContainerInstance,
+    hostContext,
+    internalInstanceHandle
+  ) {
+    invariant(
+      hostContext.isInAParentText,
+      "Text strings must be rendered within a <Text> component."
+    );
+
+    var tag = allocateTag();
+
+    UIManager.createView(
+      tag, // reactTag
+      "RCTRawText", // viewName
+      rootContainerInstance, // rootTag
+      { text: text }
+    );
+
+    precacheFiberNode(internalInstanceHandle, tag);
+
+    return tag;
+  },
+  finalizeInitialChildren: function(
+    parentInstance,
+    type,
+    props,
+    rootContainerInstance
+  ) {
+    // Don't send a no-op message over the bridge.
+    if (parentInstance._children.length === 0) {
+      return false;
+    }
+
+    // Map from child objects to native tags.
+    // Either way we need to pass a copy of the Array to prevent it from being frozen.
+    var nativeTags = parentInstance._children.map(function(child) {
+      return typeof child === "number"
+        ? child // Leaf node (eg text)
+        : child._nativeTag;
+    });
+
+    UIManager.setChildren(
+      parentInstance._nativeTag, // containerTag
+      nativeTags
+    );
+
+    return false;
+  },
+  getRootHostContext: function(rootContainerInstance) {
+    return { isInAParentText: false };
+  },
+  getChildHostContext: function(parentHostContext, type) {
+    var prevIsInAParentText = parentHostContext.isInAParentText;
+    var isInAParentText =
+      type === "AndroidTextInput" || // Android
+      type === "RCTMultilineTextInputView" || // iOS
+      type === "RCTSinglelineTextInputView" || // iOS
+      type === "RCTText" ||
+      type === "RCTVirtualText";
+
+    if (prevIsInAParentText !== isInAParentText) {
+      return { isInAParentText: isInAParentText };
+    } else {
+      return parentHostContext;
     }
+  },
+  getPublicInstance: function(instance) {
+    return instance;
+  },
 
-    var update = {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: callback,
-      isReplace: false,
-      isForced: false,
-      capturedValue: null,
-      next: null
-    };
-    insertUpdateIntoFiber(current, update);
-    scheduleWork(current, expirationTime);
+  now: now,
 
-    return expirationTime;
-  }
+  isPrimaryRenderer: true,
 
-  function updateContainerAtExpirationTime(
-    element,
-    container,
-    parentComponent,
-    currentTime,
-    expirationTime,
-    callback
+  prepareForCommit: function() {
+    // Noop
+  },
+  prepareUpdate: function(
+    instance,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    hostContext
   ) {
-    // TODO: If this is a nested container, this won't be the root.
-    var current = container.current;
+    return emptyObject;
+  },
+  resetAfterCommit: function() {
+    // Noop
+  },
 
-    {
-      if (ReactFiberInstrumentation_1.debugTool) {
-        if (current.alternate === null) {
-          ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
-        } else if (element === null) {
-          ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
-        } else {
-          ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
-        }
-      }
-    }
+  scheduleDeferredCallback: scheduleDeferredCallback,
+  cancelDeferredCallback: cancelDeferredCallback,
 
-    var context = getContextForSubtree(parentComponent);
-    if (container.context === null) {
-      container.context = context;
-    } else {
-      container.pendingContext = context;
-    }
+  shouldDeprioritizeSubtree: function(type, props) {
+    return false;
+  },
+  shouldSetTextContent: function(type, props) {
+    // TODO (bvaughn) Revisit this decision.
+    // Always returning false simplifies the createInstance() implementation,
+    // But creates an additional child Fiber for raw text children.
+    // No additional native views are created though.
+    // It's not clear to me which is better so I'm deferring for now.
+    // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
+    return false;
+  },
 
-    return scheduleRootUpdate(
-      current,
-      element,
-      currentTime,
-      expirationTime,
-      callback
-    );
-  }
+  mutation: {
+    appendChild: function(parentInstance, child) {
+      var childTag = typeof child === "number" ? child : child._nativeTag;
+      var children = parentInstance._children;
+      var index = children.indexOf(child);
 
-  function findHostInstance(component) {
-    var fiber = get$1(component);
-    if (fiber === undefined) {
-      if (typeof component.render === "function") {
-        invariant(false, "Unable to find node on an unmounted component.");
+      if (index >= 0) {
+        children.splice(index, 1);
+        children.push(child);
+
+        UIManager.manageChildren(
+          parentInstance._nativeTag, // containerTag
+          [index], // moveFromIndices
+          [children.length - 1], // moveToIndices
+          [], // addChildReactTags
+          [], // addAtIndices
+          []
+        );
       } else {
-        invariant(
-          false,
-          "Argument appears to not be a ReactComponent. Keys: %s",
-          Object.keys(component)
+        children.push(child);
+
+        UIManager.manageChildren(
+          parentInstance._nativeTag, // containerTag
+          [], // moveFromIndices
+          [], // moveToIndices
+          [childTag], // addChildReactTags
+          [children.length - 1], // addAtIndices
+          []
         );
       }
-    }
-    var hostFiber = findCurrentHostFiber(fiber);
-    if (hostFiber === null) {
-      return null;
-    }
-    return hostFiber.stateNode;
-  }
-
-  return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      return createFiberRoot(containerInfo, isAsync, hydrate);
     },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current;
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        expirationTime,
-        callback
+    appendChildToContainer: function(parentInstance, child) {
+      var childTag = typeof child === "number" ? child : child._nativeTag;
+      UIManager.setChildren(
+        parentInstance, // containerTag
+        [childTag]
       );
     },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
-    ) {
-      var currentTime = recalculateCurrentTime();
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        currentTime,
-        expirationTime,
-        callback
+    commitTextUpdate: function(textInstance, oldText, newText) {
+      UIManager.updateView(
+        textInstance, // reactTag
+        "RCTRawText", // viewName
+        { text: newText }
       );
     },
+    commitMount: function(instance, type, newProps, internalInstanceHandle) {
+      // Noop
+    },
+    commitUpdate: function(
+      instance,
+      updatePayloadTODO,
+      type,
+      oldProps,
+      newProps,
+      internalInstanceHandle
+    ) {
+      var viewConfig = instance.viewConfig;
 
-    flushRoot: flushRoot,
-
-    requestWork: requestWork,
-
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-
-    batchedUpdates: batchedUpdates,
-
-    unbatchedUpdates: unbatchedUpdates,
-
-    deferredUpdates: deferredUpdates,
-
-    syncUpdates: syncUpdates,
-
-    interactiveUpdates: interactiveUpdates,
-
-    flushInteractiveUpdates: flushInteractiveUpdates,
-
-    flushControlled: flushControlled,
+      updateFiberProps(instance._nativeTag, newProps);
 
-    flushSync: flushSync,
+      var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
 
-    getPublicRootInstance: function(container) {
-      var containerFiber = container.current;
-      if (!containerFiber.child) {
-        return null;
-      }
-      switch (containerFiber.child.tag) {
-        case HostComponent:
-          return getPublicInstance(containerFiber.child.stateNode);
-        default:
-          return containerFiber.child.stateNode;
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          instance._nativeTag, // reactTag
+          viewConfig.uiViewClassName, // viewName
+          updatePayload
+        );
       }
     },
+    insertBefore: function(parentInstance, child, beforeChild) {
+      var children = parentInstance._children;
+      var index = children.indexOf(child);
 
-    findHostInstance: findHostInstance,
+      // Move existing child or add new child?
+      if (index >= 0) {
+        children.splice(index, 1);
+        var beforeChildIndex = children.indexOf(beforeChild);
+        children.splice(beforeChildIndex, 0, child);
 
-    findHostInstanceWithNoPortals: function(fiber) {
-      var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
-      if (hostFiber === null) {
-        return null;
+        UIManager.manageChildren(
+          parentInstance._nativeTag, // containerID
+          [index], // moveFromIndices
+          [beforeChildIndex], // moveToIndices
+          [], // addChildReactTags
+          [], // addAtIndices
+          []
+        );
+      } else {
+        var _beforeChildIndex = children.indexOf(beforeChild);
+        children.splice(_beforeChildIndex, 0, child);
+
+        var childTag = typeof child === "number" ? child : child._nativeTag;
+
+        UIManager.manageChildren(
+          parentInstance._nativeTag, // containerID
+          [], // moveFromIndices
+          [], // moveToIndices
+          [childTag], // addChildReactTags
+          [_beforeChildIndex], // addAtIndices
+          []
+        );
       }
-      return hostFiber.stateNode;
     },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            var hostFiber = findCurrentHostFiber(fiber);
-            if (hostFiber === null) {
-              return null;
-            }
-            return hostFiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            if (!findFiberByHostInstance) {
-              // Might not be implemented by the renderer.
-              return null;
-            }
-            return findFiberByHostInstance(instance);
-          }
-        })
+    insertInContainerBefore: function(parentInstance, child, beforeChild) {
+      // TODO (bvaughn): Remove this check when...
+      // We create a wrapper object for the container in ReactNative render()
+      // Or we refactor to remove wrapper objects entirely.
+      // For more info on pros/cons see PR #8560 description.
+      invariant(
+        typeof parentInstance !== "number",
+        "Container does not support insertBefore operation"
       );
-    }
-  };
-};
-
-var ReactFiberReconciler$2 = Object.freeze({
-  default: ReactFiberReconciler$1
-});
-
-var ReactFiberReconciler$3 =
-  (ReactFiberReconciler$2 && ReactFiberReconciler$1) || ReactFiberReconciler$2;
-
-// TODO: bundle Flow types with the package.
+    },
+    removeChild: function(parentInstance, child) {
+      recursivelyUncacheFiberNode(child);
+      var children = parentInstance._children;
+      var index = children.indexOf(child);
 
-// TODO: decide on the top-level export form.
-// This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3["default"]
-  ? ReactFiberReconciler$3["default"]
-  : ReactFiberReconciler$3;
+      children.splice(index, 1);
 
-function _classCallCheck$1(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
+      UIManager.manageChildren(
+        parentInstance._nativeTag, // containerID
+        [], // moveFromIndices
+        [], // moveToIndices
+        [], // addChildReactTags
+        [], // addAtIndices
+        [index]
+      );
+    },
+    removeChildFromContainer: function(parentInstance, child) {
+      recursivelyUncacheFiberNode(child);
+      UIManager.manageChildren(
+        parentInstance, // containerID
+        [], // moveFromIndices
+        [], // moveToIndices
+        [], // addChildReactTags
+        [], // addAtIndices
+        [0]
+      );
+    },
+    resetTextContent: function(instance) {
+      // Noop
+    }
   }
-}
+};
 
 // Modules provided by RN:
-/**
- * This component defines the same methods as NativeMethodsMixin but without the
- * findNodeHandle wrapper. This wrapper is unnecessary for HostComponent views
- * and would also result in a circular require.js dependency (since
- * ReactNativeFiber depends on this component and NativeMethodsMixin depends on
- * ReactNativeFiber).
- */
-
-var ReactNativeFiberHostComponent = (function() {
-  function ReactNativeFiberHostComponent(tag, viewConfig) {
-    _classCallCheck$1(this, ReactNativeFiberHostComponent);
-
-    this._nativeTag = tag;
-    this._children = [];
-    this.viewConfig = viewConfig;
-  }
+var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
+  /**
+   * `NativeMethodsMixin` provides methods to access the underlying native
+   * component directly. This can be useful in cases when you want to focus
+   * a view or measure its on-screen dimensions, for example.
+   *
+   * The methods described here are available on most of the default components
+   * provided by React Native. Note, however, that they are *not* available on
+   * composite components that aren't directly backed by a native view. This will
+   * generally include most components that you define in your own app. For more
+   * information, see [Direct
+   * Manipulation](docs/direct-manipulation.html).
+   *
+   * Note the Flow $Exact<> syntax is required to support mixins.
+   * React createClass mixins can only be used with exact types.
+   */
+  var NativeMethodsMixin = {
+    /**
+     * Determines the location on screen, width, and height of the given view and
+     * returns the values via an async callback. If successful, the callback will
+     * be called with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native. If you need the measurements as soon as
+     * possible, consider using the [`onLayout`
+     * prop](docs/view.html#onlayout) instead.
+     */
+    measure: function(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
 
-  ReactNativeFiberHostComponent.prototype.blur = function blur() {
-    TextInputState.blurTextInput(this._nativeTag);
-  };
+    /**
+     * Determines the location of the given view in the window and returns the
+     * values via an async callback. If the React root view is embedded in
+     * another native view, this will give you the absolute coordinates. If
+     * successful, the callback will be called with the following
+     * arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native.
+     */
+    measureInWindow: function(callback) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    },
 
-  ReactNativeFiberHostComponent.prototype.focus = function focus() {
-    TextInputState.focusTextInput(this._nativeTag);
-  };
+    /**
+     * Like [`measure()`](#measure), but measures the view relative an ancestor,
+     * specified as `relativeToNativeNode`. This means that the returned x, y
+     * are relative to the origin x, y of the ancestor view.
+     *
+     * As always, to obtain a native node handle for a component, you can use
+     * `findNodeHandle(component)`.
+     */
+    measureLayout: function(
+      relativeToNativeNode,
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    },
 
-  ReactNativeFiberHostComponent.prototype.measure = function measure(callback) {
-    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-  };
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
+    setNativeProps: function(nativeProps) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
 
-  ReactNativeFiberHostComponent.prototype.measureInWindow = function measureInWindow(
-    callback
-  ) {
-    UIManager.measureInWindow(
-      this._nativeTag,
-      mountSafeCallback(this, callback)
-    );
-  };
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
 
-  ReactNativeFiberHostComponent.prototype.measureLayout = function measureLayout(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      this._nativeTag,
-      relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  };
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
 
-  ReactNativeFiberHostComponent.prototype.setNativeProps = function setNativeProps(
-    nativeProps
-  ) {
-    {
-      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
-    }
+      var viewConfig = maybeInstance.viewConfig;
 
-    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
+      {
+        warnForStyleProps(nativeProps, viewConfig.validAttributes);
+      }
 
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        this._nativeTag,
-        this.viewConfig.uiViewClassName,
-        updatePayload
-      );
-    }
-  };
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
 
-  return ReactNativeFiberHostComponent;
-})();
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
+      }
+    },
 
-var hasNativePerformanceNow =
-  typeof performance === "object" && typeof performance.now === "function";
+    /**
+     * Requests focus for the given input or view. The exact behavior triggered
+     * will depend on the platform and type of view.
+     */
+    focus: function() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    },
 
-var now = hasNativePerformanceNow
-  ? function() {
-      return performance.now();
+    /**
+     * Removes focus from an input or view. This is the opposite of `focus()`.
+     */
+    blur: function() {
+      TextInputState.blurTextInput(findNodeHandle(this));
     }
-  : function() {
-      return Date.now();
+  };
+
+  {
+    // hide this from Flow since we can't define these properties outside of
+    // true without actually implementing them (setting them to undefined
+    // isn't allowed by ReactClass)
+    var NativeMethodsMixin_DEV = NativeMethodsMixin;
+    invariant(
+      !NativeMethodsMixin_DEV.componentWillMount &&
+        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
+      "Do not override existing functions."
+    );
+    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
+    // Once these lifecycles have been remove from the reconciler.
+    NativeMethodsMixin_DEV.componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
+      throwOnStylesProp(this, newProps);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
+      newProps
+    ) {
+      throwOnStylesProp(this, newProps);
     };
 
-var scheduledCallback = null;
-var frameDeadline = 0;
+    // React may warn about cWM/cWRP/cWU methods being deprecated.
+    // Add a flag to suppress these warnings for this special case.
+    // TODO (bvaughn) Remove this flag once the above methods have been removed.
+    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
+    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
+  }
 
-var frameDeadlineObject = {
-  timeRemaining: function() {
-    return frameDeadline - now();
-  },
-  didTimeout: false
+  return NativeMethodsMixin;
 };
 
-function setTimeoutCallback() {
-  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
-  // React API probably changing to boolean rather than time remaining.
-  // Longer-term plan is to rewrite this using shared memory,
-  // And just return the value of the bit as the boolean.
-  frameDeadline = now() + 5;
-
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  if (callback !== null) {
-    callback(frameDeadlineObject);
+function _classCallCheck$1(instance, Constructor) {
+  if (!(instance instanceof Constructor)) {
+    throw new TypeError("Cannot call a class as a function");
   }
 }
 
-// RN has a poor polyfill for requestIdleCallback so we aren't using it.
-// This implementation is only intended for short-term use anyway.
-// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
-function scheduleDeferredCallback(callback) {
-  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
-  scheduledCallback = callback;
-  return setTimeout(setTimeoutCallback, 1);
-}
-
-function cancelDeferredCallback(callbackID) {
-  scheduledCallback = null;
-  clearTimeout(callbackID);
-}
-
-// Modules provided by RN:
-// Counter for uniquely identifying views.
-// % 10 === 1 means it is a rootTag.
-// % 2 === 0 means it is a Fabric tag.
-var nextReactTag = 3;
-function allocateTag() {
-  var tag = nextReactTag;
-  if (tag % 10 === 1) {
-    tag += 2;
+function _possibleConstructorReturn(self, call) {
+  if (!self) {
+    throw new ReferenceError(
+      "this hasn't been initialised - super() hasn't been called"
+    );
   }
-  nextReactTag = tag + 2;
-  return tag;
+  return call && (typeof call === "object" || typeof call === "function")
+    ? call
+    : self;
 }
 
-function recursivelyUncacheFiberNode(node) {
-  if (typeof node === "number") {
-    // Leaf node (eg text)
-    uncacheFiberNode(node);
-  } else {
-    uncacheFiberNode(node._nativeTag);
-
-    node._children.forEach(recursivelyUncacheFiberNode);
+function _inherits(subClass, superClass) {
+  if (typeof superClass !== "function" && superClass !== null) {
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
   }
-}
-
-var NativeRenderer = reactReconciler({
-  appendInitialChild: function(parentInstance, child) {
-    parentInstance._children.push(child);
-  },
-  createInstance: function(
-    type,
-    props,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    var tag = allocateTag();
-    var viewConfig = ReactNativeViewConfigRegistry.get(type);
-
-    {
-      for (var key in viewConfig.validAttributes) {
-        if (props.hasOwnProperty(key)) {
-          deepFreezeAndThrowOnMutationInDev(props[key]);
-        }
-      }
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: false,
+      writable: true,
+      configurable: true
     }
+  });
+  if (superClass)
+    Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass);
+}
 
-    var updatePayload = create(props, viewConfig.validAttributes);
-
-    UIManager.createView(
-      tag, // reactTag
-      viewConfig.uiViewClassName, // viewName
-      rootContainerInstance, // rootTag
-      updatePayload
-    );
-
-    var component = new ReactNativeFiberHostComponent(tag, viewConfig);
-
-    precacheFiberNode(internalInstanceHandle, tag);
-    updateFiberProps(tag, props);
+// Modules provided by RN:
+var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
+  /**
+   * Superclass that provides methods to access the underlying native component.
+   * This can be useful when you want to focus a view or measure its dimensions.
+   *
+   * Methods implemented by this class are available on most default components
+   * provided by React Native. However, they are *not* available on composite
+   * components that are not directly backed by a native view. For more
+   * information, see [Direct Manipulation](docs/direct-manipulation.html).
+   *
+   * @abstract
+   */
+  var ReactNativeComponent = (function(_React$Component) {
+    _inherits(ReactNativeComponent, _React$Component);
 
-    // Not sure how to avoid this cast. Flow is okay if the component is defined
-    // in the same file but if it's external it can't see the types.
-    return component;
-  },
-  createTextInstance: function(
-    text,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    var tag = allocateTag();
+    function ReactNativeComponent() {
+      _classCallCheck$1(this, ReactNativeComponent);
 
-    UIManager.createView(
-      tag, // reactTag
-      "RCTRawText", // viewName
-      rootContainerInstance, // rootTag
-      { text: text }
-    );
+      return _possibleConstructorReturn(
+        this,
+        _React$Component.apply(this, arguments)
+      );
+    }
 
-    precacheFiberNode(internalInstanceHandle, tag);
+    /**
+     * Removes focus. This is the opposite of `focus()`.
+     */
 
-    return tag;
-  },
-  finalizeInitialChildren: function(
-    parentInstance,
-    type,
-    props,
-    rootContainerInstance
-  ) {
-    // Don't send a no-op message over the bridge.
-    if (parentInstance._children.length === 0) {
-      return false;
-    }
+    /**
+     * Due to bugs in Flow's handling of React.createClass, some fields already
+     * declared in the base class need to be redeclared below.
+     */
+    ReactNativeComponent.prototype.blur = function blur() {
+      TextInputState.blurTextInput(findNodeHandle(this));
+    };
 
-    // Map from child objects to native tags.
-    // Either way we need to pass a copy of the Array to prevent it from being frozen.
-    var nativeTags = parentInstance._children.map(function(child) {
-      return typeof child === "number"
-        ? child // Leaf node (eg text)
-        : child._nativeTag;
-    });
+    /**
+     * Requests focus. The exact behavior depends on the platform and view.
+     */
 
-    UIManager.setChildren(
-      parentInstance._nativeTag, // containerTag
-      nativeTags
-    );
+    ReactNativeComponent.prototype.focus = function focus() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    };
 
-    return false;
-  },
-  getRootHostContext: function() {
-    return emptyObject;
-  },
-  getChildHostContext: function() {
-    return emptyObject;
-  },
-  getPublicInstance: function(instance) {
-    return instance;
-  },
+    /**
+     * Measures the on-screen location and dimensions. If successful, the callback
+     * will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * These values are not available until after natives rendering completes. If
+     * you need the measurements as soon as possible, consider using the
+     * [`onLayout` prop](docs/view.html#onlayout) instead.
+     */
 
-  now: now,
+    ReactNativeComponent.prototype.measure = function measure(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
 
-  prepareForCommit: function() {
-    // Noop
-  },
-  prepareUpdate: function(
-    instance,
-    type,
-    oldProps,
-    newProps,
-    rootContainerInstance,
-    hostContext
-  ) {
-    return emptyObject;
-  },
-  resetAfterCommit: function() {
-    // Noop
-  },
+    /**
+     * Measures the on-screen location and dimensions. Even if the React Native
+     * root view is embedded within another native view, this method will give you
+     * the absolute coordinates measured from the window. If successful, the
+     * callback will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * These values are not available until after natives rendering completes.
+     */
 
-  scheduleDeferredCallback: scheduleDeferredCallback,
-  cancelDeferredCallback: cancelDeferredCallback,
+    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
 
-  shouldDeprioritizeSubtree: function(type, props) {
-    return false;
-  },
-  shouldSetTextContent: function(type, props) {
-    // TODO (bvaughn) Revisit this decision.
-    // Always returning false simplifies the createInstance() implementation,
-    // But creates an additional child Fiber for raw text children.
-    // No additional native views are created though.
-    // It's not clear to me which is better so I'm deferring for now.
-    // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
-    return false;
-  },
+    /**
+     * Similar to [`measure()`](#measure), but the resulting location will be
+     * relative to the supplied ancestor's location.
+     *
+     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
+     */
 
-  mutation: {
-    appendChild: function(parentInstance, child) {
-      var childTag = typeof child === "number" ? child : child._nativeTag;
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
+    ReactNativeComponent.prototype.measureLayout = function measureLayout(
+      relativeToNativeNode,
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
 
-      if (index >= 0) {
-        children.splice(index, 1);
-        children.push(child);
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
 
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerTag
-          [index], // moveFromIndices
-          [children.length - 1], // moveToIndices
-          [], // addChildReactTags
-          [], // addAtIndices
-          []
-        );
-      } else {
-        children.push(child);
+    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
+      nativeProps
+    ) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
 
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerTag
-          [], // moveFromIndices
-          [], // moveToIndices
-          [childTag], // addChildReactTags
-          [children.length - 1], // addAtIndices
-          []
-        );
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
+
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
       }
-    },
-    appendChildToContainer: function(parentInstance, child) {
-      var childTag = typeof child === "number" ? child : child._nativeTag;
-      UIManager.setChildren(
-        parentInstance, // containerTag
-        [childTag]
-      );
-    },
-    commitTextUpdate: function(textInstance, oldText, newText) {
-      UIManager.updateView(
-        textInstance, // reactTag
-        "RCTRawText", // viewName
-        { text: newText }
-      );
-    },
-    commitMount: function(instance, type, newProps, internalInstanceHandle) {
-      // Noop
-    },
-    commitUpdate: function(
-      instance,
-      updatePayloadTODO,
-      type,
-      oldProps,
-      newProps,
-      internalInstanceHandle
-    ) {
-      var viewConfig = instance.viewConfig;
 
-      updateFiberProps(instance._nativeTag, newProps);
+      var viewConfig =
+        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
 
-      var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
 
       // Avoid the overhead of bridge calls if there's no update.
       // This is an expensive no-op for Android, and causes an unnecessary
       // view invalidation for certain components (eg RCTTextInput) on iOS.
       if (updatePayload != null) {
         UIManager.updateView(
-          instance._nativeTag, // reactTag
-          viewConfig.uiViewClassName, // viewName
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
           updatePayload
         );
       }
-    },
-    insertBefore: function(parentInstance, child, beforeChild) {
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
-
-      // Move existing child or add new child?
-      if (index >= 0) {
-        children.splice(index, 1);
-        var beforeChildIndex = children.indexOf(beforeChild);
-        children.splice(beforeChildIndex, 0, child);
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerID
-          [index], // moveFromIndices
-          [beforeChildIndex], // moveToIndices
-          [], // addChildReactTags
-          [], // addAtIndices
-          []
-        );
-      } else {
-        var _beforeChildIndex = children.indexOf(beforeChild);
-        children.splice(_beforeChildIndex, 0, child);
-
-        var childTag = typeof child === "number" ? child : child._nativeTag;
+    };
 
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerID
-          [], // moveFromIndices
-          [], // moveToIndices
-          [childTag], // addChildReactTags
-          [_beforeChildIndex], // addAtIndices
-          []
-        );
-      }
-    },
-    insertInContainerBefore: function(parentInstance, child, beforeChild) {
-      // TODO (bvaughn): Remove this check when...
-      // We create a wrapper object for the container in ReactNative render()
-      // Or we refactor to remove wrapper objects entirely.
-      // For more info on pros/cons see PR #8560 description.
-      invariant(
-        typeof parentInstance !== "number",
-        "Container does not support insertBefore operation"
-      );
-    },
-    removeChild: function(parentInstance, child) {
-      recursivelyUncacheFiberNode(child);
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
+    return ReactNativeComponent;
+  })(React.Component);
 
-      children.splice(index, 1);
+  // eslint-disable-next-line no-unused-expressions
 
-      UIManager.manageChildren(
-        parentInstance._nativeTag, // containerID
-        [], // moveFromIndices
-        [], // moveToIndices
-        [], // addChildReactTags
-        [], // addAtIndices
-        [index]
-      );
-    },
-    removeChildFromContainer: function(parentInstance, child) {
-      recursivelyUncacheFiberNode(child);
-      UIManager.manageChildren(
-        parentInstance, // containerID
-        [], // moveFromIndices
-        [], // moveToIndices
-        [], // addChildReactTags
-        [], // addAtIndices
-        [0]
-      );
-    },
-    resetTextContent: function(instance) {
-      // Noop
-    }
-  }
-});
+  return ReactNativeComponent;
+};
 
 // Module provided by RN:
 var getInspectorDataForViewTag = void 0;
@@ -14274,7 +15243,9 @@ var getInspectorDataForViewTag = void 0;
 }
 
 // Module provided by RN:
-var findHostInstance = NativeRenderer.findHostInstance;
+var ReactNativeFiberRenderer = reactReconciler(ReactNativeHostConfig);
+
+var findHostInstance = ReactNativeFiberRenderer.findHostInstance;
 
 function findNodeHandle(componentOrHandle) {
   {
@@ -14319,7 +15290,7 @@ function findNodeHandle(componentOrHandle) {
   return hostInstance._nativeTag;
 }
 
-injection$2.injectRenderer(NativeRenderer);
+injection$2.injectRenderer(ReactNativeFiberRenderer);
 
 function computeComponentStackForErrorReporting(reactTag) {
   var fiber = getInstanceFromTag(reactTag);
@@ -14342,19 +15313,23 @@ var ReactNativeRenderer = {
     if (!root) {
       // TODO (bvaughn): If we decide to keep the wrapper component,
       // We could create a wrapper for containerTag as well to reduce special casing.
-      root = NativeRenderer.createContainer(containerTag, false, false);
+      root = ReactNativeFiberRenderer.createContainer(
+        containerTag,
+        false,
+        false
+      );
       roots.set(containerTag, root);
     }
-    NativeRenderer.updateContainer(element, root, null, callback);
+    ReactNativeFiberRenderer.updateContainer(element, root, null, callback);
 
-    return NativeRenderer.getPublicRootInstance(root);
+    return ReactNativeFiberRenderer.getPublicRootInstance(root);
   },
   unmountComponentAtNode: function(containerTag) {
     var root = roots.get(containerTag);
     if (root) {
       // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
-      NativeRenderer.updateContainer(null, root, null, function() {
-        roots["delete"](containerTag);
+      ReactNativeFiberRenderer.updateContainer(null, root, null, function() {
+        roots.delete(containerTag);
       });
     }
   },
@@ -14382,29 +15357,7 @@ var ReactNativeRenderer = {
   }
 };
 
-{
-  // $FlowFixMe
-  Object.assign(
-    ReactNativeRenderer.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-    {
-      // TODO: none of these work since Fiber. Remove these dependencies.
-      // Used by RCTRenderingPerf, Systrace:
-      ReactDebugTool: {
-        addHook: function() {},
-        removeHook: function() {}
-      },
-      // Used by ReactPerfStallHandler, RCTRenderingPerf:
-      ReactPerf: {
-        start: function() {},
-        stop: function() {},
-        printInclusive: function() {},
-        printWasted: function() {}
-      }
-    }
-  );
-}
-
-NativeRenderer.injectIntoDevTools({
+ReactNativeFiberRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 1,
@@ -14421,8 +15374,8 @@ var ReactNativeRenderer$3 =
 
 // TODO: decide on the top-level export form.
 // This is hacky but makes it work with both Rollup and Jest.
-var reactNativeRenderer = ReactNativeRenderer$3["default"]
-  ? ReactNativeRenderer$3["default"]
+var reactNativeRenderer = ReactNativeRenderer$3.default
+  ? ReactNativeRenderer$3.default
   : ReactNativeRenderer$3;
 
 module.exports = reactNativeRenderer;
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
index f7eb9e09f0dc..45cc8fca1ac8 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
@@ -5,7 +5,9 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @noflow
+ * @providesModule ReactNativeRenderer-prod
  * @preventMunge
+ * @generated
  */
 
 "use strict";
@@ -15,13 +17,13 @@ var invariant = require("fbjs/lib/invariant"),
   ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
   UIManager = require("UIManager"),
   RCTEventEmitter = require("RCTEventEmitter"),
-  TextInputState = require("TextInputState"),
-  deepDiffer = require("deepDiffer"),
-  flattenStyle = require("flattenStyle"),
   React = require("react"),
   emptyObject = require("fbjs/lib/emptyObject"),
   shallowEqual = require("fbjs/lib/shallowEqual"),
-  ExceptionsManager = require("ExceptionsManager");
+  ExceptionsManager = require("ExceptionsManager"),
+  deepDiffer = require("deepDiffer"),
+  flattenStyle = require("flattenStyle"),
+  TextInputState = require("TextInputState");
 function invokeGuardedCallback(name, func, context, a, b, c, d, e, f) {
   this._hasCaughtError = !1;
   this._caughtError = null;
@@ -306,7 +308,7 @@ function getListener(inst, registrationName) {
   return listener;
 }
 function getParent(inst) {
-  do inst = inst["return"];
+  do inst = inst.return;
   while (inst && 5 !== inst.tag);
   return inst ? inst : null;
 }
@@ -1122,21 +1124,21 @@ var ReactNativeEventEmitter = Object.freeze({
   }
 });
 RCTEventEmitter.register(ReactNativeEventEmitter);
-var hasSymbol = "function" === typeof Symbol && Symbol["for"],
-  REACT_ELEMENT_TYPE = hasSymbol ? Symbol["for"]("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol["for"]("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol["for"]("react.return") : 60105,
-  REACT_PORTAL_TYPE = hasSymbol ? Symbol["for"]("react.portal") : 60106,
-  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol["for"]("react.fragment") : 60107,
-  REACT_STRICT_MODE_TYPE = hasSymbol
-    ? Symbol["for"]("react.strict_mode")
-    : 60108,
-  REACT_PROVIDER_TYPE = hasSymbol ? Symbol["for"]("react.provider") : 60109,
-  REACT_CONTEXT_TYPE = hasSymbol ? Symbol["for"]("react.context") : 60110,
-  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol["for"]("react.async_mode") : 60111,
-  REACT_FORWARD_REF_TYPE = hasSymbol
-    ? Symbol["for"]("react.forward_ref")
-    : 60112,
+var ReactCurrentOwner =
+    React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner,
+  hasSymbol = "function" === typeof Symbol && Symbol.for,
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
+  REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 60104,
+  REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 60105,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
+  REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profile_root") : 60108,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for("react.forward_ref") : 60112,
+  REACT_TIMEOUT_TYPE = hasSymbol ? Symbol.for("react.timeout") : 60113,
   MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
 function getIteratorFn(maybeIterable) {
   if (null === maybeIterable || "undefined" === typeof maybeIterable)
@@ -1146,436 +1148,149 @@ function getIteratorFn(maybeIterable) {
     maybeIterable["@@iterator"];
   return "function" === typeof maybeIterable ? maybeIterable : null;
 }
-function createPortal(children, containerInfo, implementation) {
-  var key =
-    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
-  return {
-    $$typeof: REACT_PORTAL_TYPE,
-    key: null == key ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
-}
 function getComponentName(fiber) {
-  fiber = fiber.type;
-  if ("function" === typeof fiber) return fiber.displayName || fiber.name;
-  if ("string" === typeof fiber) return fiber;
-  switch (fiber) {
+  var type = fiber.type;
+  if ("function" === typeof type) return type.displayName || type.name;
+  if ("string" === typeof type) return type;
+  switch (type) {
+    case REACT_ASYNC_MODE_TYPE:
+      return "AsyncMode";
+    case REACT_CALL_TYPE:
+      return "ReactCall";
+    case REACT_CONTEXT_TYPE:
+      return "Context.Consumer";
     case REACT_FRAGMENT_TYPE:
       return "ReactFragment";
     case REACT_PORTAL_TYPE:
       return "ReactPortal";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
+    case REACT_PROFILER_TYPE:
+      return "Profiler(" + fiber.pendingProps.id + ")";
+    case REACT_PROVIDER_TYPE:
+      return "Context.Provider";
     case REACT_RETURN_TYPE:
       return "ReactReturn";
+    case REACT_STRICT_MODE_TYPE:
+      return "StrictMode";
   }
-  if ("object" === typeof fiber && null !== fiber)
-    switch (fiber.$$typeof) {
+  if ("object" === typeof type && null !== type)
+    switch (type.$$typeof) {
       case REACT_FORWARD_REF_TYPE:
         return (
-          (fiber = fiber.render.displayName || fiber.render.name || ""),
+          (fiber = type.render.displayName || type.render.name || ""),
           "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
         );
     }
   return null;
 }
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  do {
-    a: switch (workInProgress.tag) {
-      case 0:
-      case 1:
-      case 2:
-      case 5:
-        var owner = workInProgress._debugOwner,
-          source = workInProgress._debugSource;
-        var JSCompiler_inline_result = getComponentName(workInProgress);
-        var ownerName = null;
-        owner && (ownerName = getComponentName(owner));
-        owner = source;
-        JSCompiler_inline_result =
-          "\n    in " +
-          (JSCompiler_inline_result || "Unknown") +
-          (owner
-            ? " (at " +
-              owner.fileName.replace(/^.*[\\\/]/, "") +
-              ":" +
-              owner.lineNumber +
-              ")"
-            : ownerName ? " (created by " + ownerName + ")" : "");
-        break a;
-      default:
-        JSCompiler_inline_result = "";
-    }
-    info += JSCompiler_inline_result;
-    workInProgress = workInProgress["return"];
-  } while (workInProgress);
-  return info;
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (fiber.alternate) for (; node.return; ) node = node.return;
+  else {
+    if (0 !== (node.effectTag & 2)) return 1;
+    for (; node.return; )
+      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
+  }
+  return 3 === node.tag ? 2 : 3;
 }
-var emptyObject$1 = {},
-  removedKeys = null,
-  removedKeyCount = 0;
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node))
-    for (var i = node.length; i-- && 0 < removedKeyCount; )
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
-  else if (node && 0 < removedKeyCount)
-    for (i in removedKeys)
-      if (removedKeys[i]) {
-        var _nextProp = node[i];
-        if (void 0 !== _nextProp) {
-          var attributeConfig = validAttributes[i];
-          if (attributeConfig) {
-            "function" === typeof _nextProp && (_nextProp = !0);
-            "undefined" === typeof _nextProp && (_nextProp = null);
-            if ("object" !== typeof attributeConfig)
-              updatePayload[i] = _nextProp;
-            else if (
-              "function" === typeof attributeConfig.diff ||
-              "function" === typeof attributeConfig.process
-            )
-              (_nextProp =
-                "function" === typeof attributeConfig.process
-                  ? attributeConfig.process(_nextProp)
-                  : _nextProp),
-                (updatePayload[i] = _nextProp);
-            removedKeys[i] = !1;
-            removedKeyCount--;
+function isMounted(component) {
+  return (component = component._reactInternalFiber)
+    ? 2 === isFiberMountedImpl(component)
+    : !1;
+}
+function assertIsMounted(fiber) {
+  invariant(
+    2 === isFiberMountedImpl(fiber),
+    "Unable to find node on an unmounted component."
+  );
+}
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate)
+    return (
+      (alternate = isFiberMountedImpl(fiber)),
+      invariant(
+        3 !== alternate,
+        "Unable to find node on an unmounted component."
+      ),
+      1 === alternate ? null : fiber
+    );
+  for (var a = fiber, b = alternate; ; ) {
+    var parentA = a.return,
+      parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) break;
+    if (parentA.child === parentB.child) {
+      for (var child = parentA.child; child; ) {
+        if (child === a) return assertIsMounted(parentA), fiber;
+        if (child === b) return assertIsMounted(parentA), alternate;
+        child = child.sibling;
+      }
+      invariant(!1, "Unable to find node on an unmounted component.");
+    }
+    if (a.return !== b.return) (a = parentA), (b = parentB);
+    else {
+      child = !1;
+      for (var _child = parentA.child; _child; ) {
+        if (_child === a) {
+          child = !0;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          child = !0;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!child) {
+        for (_child = parentB.child; _child; ) {
+          if (_child === a) {
+            child = !0;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            child = !0;
+            b = parentB;
+            a = parentA;
+            break;
           }
+          _child = _child.sibling;
         }
+        invariant(
+          child,
+          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
+        );
       }
-}
-function diffNestedProperty(
-  updatePayload,
-  prevProp,
-  nextProp,
-  validAttributes
-) {
-  if (!updatePayload && prevProp === nextProp) return updatePayload;
-  if (!prevProp || !nextProp)
-    return nextProp
-      ? addNestedProperty(updatePayload, nextProp, validAttributes)
-      : prevProp
-        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
-        : updatePayload;
-  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
-    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
-  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
-    var minLength =
-        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
-      i;
-    for (i = 0; i < minLength; i++)
-      updatePayload = diffNestedProperty(
-        updatePayload,
-        prevProp[i],
-        nextProp[i],
-        validAttributes
-      );
-    for (; i < prevProp.length; i++)
-      updatePayload = clearNestedProperty(
-        updatePayload,
-        prevProp[i],
-        validAttributes
-      );
-    for (; i < nextProp.length; i++)
-      updatePayload = addNestedProperty(
-        updatePayload,
-        nextProp[i],
-        validAttributes
-      );
-    return updatePayload;
+    }
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
+    );
   }
-  return Array.isArray(prevProp)
-    ? diffProperties(
-        updatePayload,
-        flattenStyle(prevProp),
-        nextProp,
-        validAttributes
-      )
-    : diffProperties(
-        updatePayload,
-        prevProp,
-        flattenStyle(nextProp),
-        validAttributes
-      );
+  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
+  return a.stateNode.current === a ? fiber : alternate;
 }
-function addNestedProperty(updatePayload, nextProp, validAttributes) {
-  if (!nextProp) return updatePayload;
-  if (!Array.isArray(nextProp))
-    return diffProperties(
-      updatePayload,
-      emptyObject$1,
-      nextProp,
-      validAttributes
-    );
-  for (var i = 0; i < nextProp.length; i++)
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextProp[i],
-      validAttributes
-    );
-  return updatePayload;
-}
-function clearNestedProperty(updatePayload, prevProp, validAttributes) {
-  if (!prevProp) return updatePayload;
-  if (!Array.isArray(prevProp))
-    return diffProperties(
-      updatePayload,
-      prevProp,
-      emptyObject$1,
-      validAttributes
-    );
-  for (var i = 0; i < prevProp.length; i++)
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevProp[i],
-      validAttributes
-    );
-  return updatePayload;
-}
-function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
-  var attributeConfig, propKey;
-  for (propKey in nextProps)
-    if ((attributeConfig = validAttributes[propKey])) {
-      var prevProp = prevProps[propKey];
-      var nextProp = nextProps[propKey];
-      "function" === typeof nextProp &&
-        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
-      "undefined" === typeof nextProp &&
-        ((nextProp = null),
-        "undefined" === typeof prevProp && (prevProp = null));
-      removedKeys && (removedKeys[propKey] = !1);
-      if (updatePayload && void 0 !== updatePayload[propKey])
-        if ("object" !== typeof attributeConfig)
-          updatePayload[propKey] = nextProp;
-        else {
-          if (
-            "function" === typeof attributeConfig.diff ||
-            "function" === typeof attributeConfig.process
-          )
-            (attributeConfig =
-              "function" === typeof attributeConfig.process
-                ? attributeConfig.process(nextProp)
-                : nextProp),
-              (updatePayload[propKey] = attributeConfig);
-        }
-      else if (prevProp !== nextProp)
-        if ("object" !== typeof attributeConfig)
-          ("object" !== typeof nextProp ||
-            null === nextProp ||
-            deepDiffer(prevProp, nextProp)) &&
-            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
-        else if (
-          "function" === typeof attributeConfig.diff ||
-          "function" === typeof attributeConfig.process
-        ) {
-          if (
-            void 0 === prevProp ||
-            ("function" === typeof attributeConfig.diff
-              ? attributeConfig.diff(prevProp, nextProp)
-              : "object" !== typeof nextProp ||
-                null === nextProp ||
-                deepDiffer(prevProp, nextProp))
-          )
-            (attributeConfig =
-              "function" === typeof attributeConfig.process
-                ? attributeConfig.process(nextProp)
-                : nextProp),
-              ((updatePayload || (updatePayload = {}))[
-                propKey
-              ] = attributeConfig);
-        } else
-          (removedKeys = null),
-            (removedKeyCount = 0),
-            (updatePayload = diffNestedProperty(
-              updatePayload,
-              prevProp,
-              nextProp,
-              attributeConfig
-            )),
-            0 < removedKeyCount &&
-              updatePayload &&
-              (restoreDeletedValuesInNestedArray(
-                updatePayload,
-                nextProp,
-                attributeConfig
-              ),
-              (removedKeys = null));
-    }
-  for (var _propKey in prevProps)
-    void 0 === nextProps[_propKey] &&
-      (!(attributeConfig = validAttributes[_propKey]) ||
-        (updatePayload && void 0 !== updatePayload[_propKey]) ||
-        ((prevProp = prevProps[_propKey]),
-        void 0 !== prevProp &&
-          ("object" !== typeof attributeConfig ||
-          "function" === typeof attributeConfig.diff ||
-          "function" === typeof attributeConfig.process
-            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
-              removedKeys || (removedKeys = {}),
-              removedKeys[_propKey] ||
-                ((removedKeys[_propKey] = !0), removedKeyCount++))
-            : (updatePayload = clearNestedProperty(
-                updatePayload,
-                prevProp,
-                attributeConfig
-              )))));
-  return updatePayload;
-}
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (callback) {
-      if ("boolean" === typeof context.__isMounted) {
-        if (!context.__isMounted) return;
-      } else if (
-        "function" === typeof context.isMounted &&
-        !context.isMounted()
-      )
-        return;
-      return callback.apply(context, arguments);
-    }
-  };
-}
-function _inherits(subClass, superClass) {
-  if ("function" !== typeof superClass && null !== superClass)
-    throw new TypeError(
-      "Super expression must either be null or a function, not " +
-        typeof superClass
-    );
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: !1,
-      writable: !0,
-      configurable: !0
-    }
-  });
-  superClass &&
-    (Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass));
-}
-var ReactCurrentOwner =
-  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
-function isFiberMountedImpl(fiber) {
-  var node = fiber;
-  if (fiber.alternate) for (; node["return"]; ) node = node["return"];
-  else {
-    if (0 !== (node.effectTag & 2)) return 1;
-    for (; node["return"]; )
-      if (((node = node["return"]), 0 !== (node.effectTag & 2))) return 1;
-  }
-  return 3 === node.tag ? 2 : 3;
-}
-function isMounted(component) {
-  return (component = component._reactInternalFiber)
-    ? 2 === isFiberMountedImpl(component)
-    : !1;
-}
-function assertIsMounted(fiber) {
-  invariant(
-    2 === isFiberMountedImpl(fiber),
-    "Unable to find node on an unmounted component."
-  );
-}
-function findCurrentFiberUsingSlowPath(fiber) {
-  var alternate = fiber.alternate;
-  if (!alternate)
-    return (
-      (alternate = isFiberMountedImpl(fiber)),
-      invariant(
-        3 !== alternate,
-        "Unable to find node on an unmounted component."
-      ),
-      1 === alternate ? null : fiber
-    );
-  for (var a = fiber, b = alternate; ; ) {
-    var parentA = a["return"],
-      parentB = parentA ? parentA.alternate : null;
-    if (!parentA || !parentB) break;
-    if (parentA.child === parentB.child) {
-      for (var child = parentA.child; child; ) {
-        if (child === a) return assertIsMounted(parentA), fiber;
-        if (child === b) return assertIsMounted(parentA), alternate;
-        child = child.sibling;
-      }
-      invariant(!1, "Unable to find node on an unmounted component.");
-    }
-    if (a["return"] !== b["return"]) (a = parentA), (b = parentB);
-    else {
-      child = !1;
-      for (var _child = parentA.child; _child; ) {
-        if (_child === a) {
-          child = !0;
-          a = parentA;
-          b = parentB;
-          break;
-        }
-        if (_child === b) {
-          child = !0;
-          b = parentA;
-          a = parentB;
-          break;
-        }
-        _child = _child.sibling;
-      }
-      if (!child) {
-        for (_child = parentB.child; _child; ) {
-          if (_child === a) {
-            child = !0;
-            a = parentB;
-            b = parentA;
-            break;
-          }
-          if (_child === b) {
-            child = !0;
-            b = parentB;
-            a = parentA;
-            break;
-          }
-          _child = _child.sibling;
-        }
-        invariant(
-          child,
-          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
-        );
-      }
-    }
-    invariant(
-      a.alternate === b,
-      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
-  return a.stateNode.current === a ? fiber : alternate;
-}
-function findCurrentHostFiber(parent) {
-  parent = findCurrentFiberUsingSlowPath(parent);
-  if (!parent) return null;
-  for (var node = parent; ; ) {
-    if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child["return"] = node), (node = node.child);
-    else {
-      if (node === parent) break;
-      for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
-      }
-      node.sibling["return"] = node["return"];
-      node = node.sibling;
-    }
-  }
-  return null;
+function findCurrentHostFiber(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child) (node.child.return = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+  return null;
 }
 function findCurrentHostFiberWithNoPortals(parent) {
   parent = findCurrentFiberUsingSlowPath(parent);
@@ -1583,14 +1298,14 @@ function findCurrentHostFiberWithNoPortals(parent) {
   for (var node = parent; ; ) {
     if (5 === node.tag || 6 === node.tag) return node;
     if (node.child && 4 !== node.tag)
-      (node.child["return"] = node), (node = node.child);
+      (node.child.return = node), (node = node.child);
     else {
       if (node === parent) break;
       for (; !node.sibling; ) {
-        if (!node["return"] || node["return"] === parent) return null;
-        node = node["return"];
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -1599,8 +1314,7 @@ function findCurrentHostFiberWithNoPortals(parent) {
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
   this.key = key;
-  this.stateNode = this.type = null;
-  this.sibling = this.child = this["return"] = null;
+  this.sibling = this.child = this.return = this.stateNode = this.type = null;
   this.index = 0;
   this.ref = null;
   this.pendingProps = pendingProps;
@@ -1664,12 +1378,24 @@ function createFiberFromElement(element, mode, expirationTime) {
         fiberTag = 11;
         mode |= 2;
         break;
+      case REACT_PROFILER_TYPE:
+        return (
+          (type = new FiberNode(15, element, key, mode | 4)),
+          (type.type = REACT_PROFILER_TYPE),
+          (type.expirationTime = expirationTime),
+          (type.stateNode = { duration: 0, startTime: 0 }),
+          type
+        );
       case REACT_CALL_TYPE:
         fiberTag = 7;
         break;
       case REACT_RETURN_TYPE:
         fiberTag = 9;
         break;
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = 16;
+        mode |= 2;
+        break;
       default:
         if ("object" === typeof type && null !== type)
           switch (type.$$typeof) {
@@ -1762,167 +1488,334 @@ function onCommitRoot(root) {
 function onCommitUnmount(fiber) {
   "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
 }
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
+    }
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress.return;
+  } while (workInProgress);
+  return info;
+}
+function createProfilerTimer() {
+  return {
+    checkActualRenderTimeStackEmpty: function() {},
+    markActualRenderTimeStarted: function() {},
+    pauseActualRenderTimerIfRunning: function() {},
+    recordElapsedActualRenderTime: function() {},
+    resetActualRenderTimer: function() {},
+    resumeActualRenderTimerIfPaused: function() {},
+    recordElapsedBaseRenderTimeIfRunning: function() {},
+    startBaseRenderTimer: function() {},
+    stopBaseRenderTimerIfRunning: function() {}
+  };
+}
 new Set();
+var hasForceUpdate = !1;
 function createUpdateQueue(baseState) {
   return {
-    baseState: baseState,
     expirationTime: 0,
-    first: null,
-    last: null,
-    callbackList: null,
-    hasForceUpdate: !1,
-    isInitialized: !1,
-    capturedValues: null
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function cloneUpdateQueue(currentQueue) {
+  return {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
   };
 }
-function insertUpdateIntoQueue(queue, update) {
-  null === queue.last
-    ? (queue.first = queue.last = update)
-    : ((queue.last.next = update), (queue.last = update));
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+    tag: 0,
+    payload: null,
+    callback: null,
+    next: null,
+    nextEffect: null
+  };
+}
+function appendUpdateToQueue(queue, update, expirationTime) {
+  null === queue.lastUpdate
+    ? (queue.firstUpdate = queue.lastUpdate = update)
+    : ((queue.lastUpdate.next = update), (queue.lastUpdate = update));
+  if (0 === queue.expirationTime || queue.expirationTime > expirationTime)
+    queue.expirationTime = expirationTime;
+}
+function enqueueUpdate(fiber, update, expirationTime) {
+  var alternate = fiber.alternate;
+  if (null === alternate) {
+    var queue1 = fiber.updateQueue;
+    var queue2 = null;
+    null === queue1 &&
+      (queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState));
+  } else
+    (queue1 = fiber.updateQueue),
+      (queue2 = alternate.updateQueue),
+      null === queue1
+        ? null === queue2
+          ? ((queue1 = fiber.updateQueue = createUpdateQueue(
+              fiber.memoizedState
+            )),
+            (queue2 = alternate.updateQueue = createUpdateQueue(
+              alternate.memoizedState
+            )))
+          : (queue1 = fiber.updateQueue = cloneUpdateQueue(queue2))
+        : null === queue2 &&
+          (queue2 = alternate.updateQueue = cloneUpdateQueue(queue1));
+  null === queue2 || queue1 === queue2
+    ? appendUpdateToQueue(queue1, update, expirationTime)
+    : null === queue1.lastUpdate || null === queue2.lastUpdate
+      ? (appendUpdateToQueue(queue1, update, expirationTime),
+        appendUpdateToQueue(queue2, update, expirationTime))
+      : (appendUpdateToQueue(queue1, update, expirationTime),
+        (queue2.lastUpdate = update));
+}
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  var workInProgressQueue = workInProgress.updateQueue;
+  workInProgressQueue =
+    null === workInProgressQueue
+      ? (workInProgress.updateQueue = createUpdateQueue(
+          workInProgress.memoizedState
+        ))
+      : ensureWorkInProgressQueueIsAClone(workInProgress, workInProgressQueue);
+  null === workInProgressQueue.lastCapturedUpdate
+    ? (workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update)
+    : ((workInProgressQueue.lastCapturedUpdate.next = update),
+      (workInProgressQueue.lastCapturedUpdate = update));
   if (
-    0 === queue.expirationTime ||
-    queue.expirationTime > update.expirationTime
+    0 === workInProgressQueue.expirationTime ||
+    workInProgressQueue.expirationTime > renderExpirationTime
   )
-    queue.expirationTime = update.expirationTime;
+    workInProgressQueue.expirationTime = renderExpirationTime;
 }
-var q1 = void 0,
-  q2 = void 0;
-function ensureUpdateQueues(fiber) {
-  q1 = q2 = null;
-  var alternateFiber = fiber.alternate,
-    queue1 = fiber.updateQueue;
-  null === queue1 && (queue1 = fiber.updateQueue = createUpdateQueue(null));
-  null !== alternateFiber
-    ? ((fiber = alternateFiber.updateQueue),
-      null === fiber &&
-        (fiber = alternateFiber.updateQueue = createUpdateQueue(null)))
-    : (fiber = null);
-  q1 = queue1;
-  q2 = fiber !== queue1 ? fiber : null;
-}
-function insertUpdateIntoFiber(fiber, update) {
-  ensureUpdateQueues(fiber);
-  fiber = q1;
-  var queue2 = q2;
-  null === queue2
-    ? insertUpdateIntoQueue(fiber, update)
-    : null === fiber.last || null === queue2.last
-      ? (insertUpdateIntoQueue(fiber, update),
-        insertUpdateIntoQueue(queue2, update))
-      : (insertUpdateIntoQueue(fiber, update), (queue2.last = update));
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  null !== current &&
+    queue === current.updateQueue &&
+    (queue = workInProgress.updateQueue = cloneUpdateQueue(queue));
+  return queue;
 }
-function getStateFromUpdate(update, instance, prevState, props) {
-  update = update.partialState;
-  return "function" === typeof update
-    ? update.call(instance, prevState, props)
-    : update;
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case 1:
+      return (
+        (workInProgress = update.payload),
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress
+      );
+    case 3:
+      workInProgress.effectTag = (workInProgress.effectTag & -1025) | 64;
+    case 0:
+      workInProgress = update.payload;
+      nextProps =
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress;
+      if (null === nextProps || void 0 === nextProps) break;
+      return Object.assign({}, prevState, nextProps);
+    case 2:
+      hasForceUpdate = !0;
+  }
+  return prevState;
 }
 function processUpdateQueue(
-  current,
   workInProgress,
   queue,
-  instance,
   props,
+  instance,
   renderExpirationTime
 ) {
-  null !== current &&
-    current.updateQueue === queue &&
-    (queue = workInProgress.updateQueue = {
-      baseState: queue.baseState,
-      expirationTime: queue.expirationTime,
-      first: queue.first,
-      last: queue.last,
-      isInitialized: queue.isInitialized,
-      capturedValues: queue.capturedValues,
-      callbackList: null,
-      hasForceUpdate: !1
-    });
-  queue.expirationTime = 0;
-  queue.isInitialized
-    ? (current = queue.baseState)
-    : ((current = queue.baseState = workInProgress.memoizedState),
-      (queue.isInitialized = !0));
-  for (
-    var dontMutatePrevState = !0, update = queue.first, didSkip = !1;
-    null !== update;
-
+  hasForceUpdate = !1;
+  if (
+    !(0 === queue.expirationTime || queue.expirationTime > renderExpirationTime)
   ) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      var remainingExpirationTime = queue.expirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        remainingExpirationTime > updateExpirationTime
-      )
-        queue.expirationTime = updateExpirationTime;
-      didSkip || ((didSkip = !0), (queue.baseState = current));
-    } else {
-      didSkip ||
-        ((queue.first = update.next),
-        null === queue.first && (queue.last = null));
-      if (update.isReplace)
-        (current = getStateFromUpdate(update, instance, current, props)),
-          (dontMutatePrevState = !0);
-      else if (
-        (updateExpirationTime = getStateFromUpdate(
+    queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+    for (
+      var newBaseState = queue.baseState,
+        newFirstUpdate = null,
+        newExpirationTime = 0,
+        update = queue.firstUpdate,
+        resultState = newBaseState;
+      null !== update;
+
+    ) {
+      var updateExpirationTime = update.expirationTime;
+      if (updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === newFirstUpdate &&
+            ((newFirstUpdate = update), (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > updateExpirationTime)
+        )
+          newExpirationTime = updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
           update,
-          instance,
-          current,
-          props
-        ))
-      )
-        (current = dontMutatePrevState
-          ? Object.assign({}, current, updateExpirationTime)
-          : Object.assign(current, updateExpirationTime)),
-          (dontMutatePrevState = !1);
-      update.isForced && (queue.hasForceUpdate = !0);
-      null !== update.callback &&
-        ((updateExpirationTime = queue.callbackList),
-        null === updateExpirationTime &&
-          (updateExpirationTime = queue.callbackList = []),
-        updateExpirationTime.push(update));
-      null !== update.capturedValue &&
-        ((updateExpirationTime = queue.capturedValues),
-        null === updateExpirationTime
-          ? (queue.capturedValues = [update.capturedValue])
-          : updateExpirationTime.push(update.capturedValue));
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastEffect
+              ? (queue.firstEffect = queue.lastEffect = update)
+              : ((queue.lastEffect.nextEffect = update),
+                (queue.lastEffect = update)));
+      update = update.next;
+    }
+    updateExpirationTime = null;
+    for (update = queue.firstCapturedUpdate; null !== update; ) {
+      var _updateExpirationTime = update.expirationTime;
+      if (_updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === updateExpirationTime &&
+            ((updateExpirationTime = update),
+            null === newFirstUpdate && (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > _updateExpirationTime)
+        )
+          newExpirationTime = _updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
+          update,
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastCapturedEffect
+              ? (queue.firstCapturedEffect = queue.lastCapturedEffect = update)
+              : ((queue.lastCapturedEffect.nextEffect = update),
+                (queue.lastCapturedEffect = update)));
+      update = update.next;
     }
-    update = update.next;
+    null === newFirstUpdate && (queue.lastUpdate = null);
+    null === updateExpirationTime
+      ? (queue.lastCapturedUpdate = null)
+      : (workInProgress.effectTag |= 32);
+    null === newFirstUpdate &&
+      null === updateExpirationTime &&
+      (newBaseState = resultState);
+    queue.baseState = newBaseState;
+    queue.firstUpdate = newFirstUpdate;
+    queue.firstCapturedUpdate = updateExpirationTime;
+    queue.expirationTime = newExpirationTime;
+    workInProgress.memoizedState = resultState;
   }
-  null !== queue.callbackList
-    ? (workInProgress.effectTag |= 32)
-    : null !== queue.first ||
-      queue.hasForceUpdate ||
-      null !== queue.capturedValues ||
-      (workInProgress.updateQueue = null);
-  didSkip || (queue.baseState = current);
-  return current;
 }
-function commitCallbacks(queue, context) {
-  var callbackList = queue.callbackList;
-  if (null !== callbackList)
-    for (
-      queue.callbackList = null, queue = 0;
-      queue < callbackList.length;
-      queue++
-    ) {
-      var update = callbackList[queue],
-        _callback = update.callback;
-      update.callback = null;
-      invariant(
-        "function" === typeof _callback,
-        "Invalid argument passed as callback. Expected a function. Instead received: %s",
-        _callback
-      );
-      _callback.call(context);
-    }
+function callCallback(callback, context) {
+  invariant(
+    "function" === typeof callback,
+    "Invalid argument passed as callback. Expected a function. Instead received: %s",
+    callback
+  );
+  callback.call(context);
+}
+function commitUpdateQueue(finishedWork, finishedQueue, instance) {
+  null !== finishedQueue.firstCapturedUpdate &&
+    (null !== finishedQueue.lastUpdate &&
+      ((finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate),
+      (finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate)),
+    (finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null));
+  finishedWork = finishedQueue.firstEffect;
+  for (
+    finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+    null !== finishedWork;
+
+  ) {
+    var _callback3 = finishedWork.callback;
+    null !== _callback3 &&
+      ((finishedWork.callback = null), callCallback(_callback3, instance));
+    finishedWork = finishedWork.nextEffect;
+  }
+  finishedWork = finishedQueue.firstCapturedEffect;
+  for (
+    finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+    null !== finishedWork;
+
+  )
+    (finishedQueue = finishedWork.callback),
+      null !== finishedQueue &&
+        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
+      (finishedWork = finishedWork.nextEffect);
+}
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+  getDerivedStateFromProps = getDerivedStateFromProps(nextProps, prevState);
+  prevState =
+    null === getDerivedStateFromProps || void 0 === getDerivedStateFromProps
+      ? prevState
+      : Object.assign({}, prevState, getDerivedStateFromProps);
+  workInProgress.memoizedState = prevState;
+  workInProgress = workInProgress.updateQueue;
+  null !== workInProgress &&
+    0 === workInProgress.expirationTime &&
+    (workInProgress.baseState = prevState);
 }
 function ReactFiberClassComponent(
   legacyContext,
   scheduleWork,
   computeExpirationForFiber,
   memoizeProps,
-  memoizeState
+  memoizeState,
+  recalculateCurrentTime
 ) {
   function checkShouldComponentUpdate(
     workInProgress,
@@ -1932,12 +1825,6 @@ function ReactFiberClassComponent(
     newState,
     newContext
   ) {
-    if (
-      null === oldProps ||
-      (null !== workInProgress.updateQueue &&
-        workInProgress.updateQueue.hasForceUpdate)
-    )
-      return !0;
     var instance = workInProgress.stateNode;
     workInProgress = workInProgress.type;
     return "function" === typeof instance.shouldComponentUpdate
@@ -1948,7 +1835,7 @@ function ReactFiberClassComponent(
         : !0;
   }
   function adoptClassInstance(workInProgress, instance) {
-    instance.updater = updater;
+    instance.updater = classComponentUpdater;
     workInProgress.stateNode = instance;
     instance._reactInternalFiber = workInProgress;
   }
@@ -1964,78 +1851,55 @@ function ReactFiberClassComponent(
     "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
       instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
     instance.state !== workInProgress &&
-      updater.enqueueReplaceState(instance, instance.state, null);
-  }
-  function callGetDerivedStateFromProps(
-    workInProgress,
-    instance,
-    nextProps,
-    prevState
-  ) {
-    workInProgress = workInProgress.type;
-    if ("function" === typeof workInProgress.getDerivedStateFromProps)
-      return workInProgress.getDerivedStateFromProps.call(
-        null,
-        nextProps,
-        prevState
-      );
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
   }
   var cacheContext = legacyContext.cacheContext,
     getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     isContextConsumer = legacyContext.isContextConsumer,
     hasContextChanged = legacyContext.hasContextChanged,
-    updater = {
+    classComponentUpdater = {
       isMounted: isMounted,
-      enqueueSetState: function(instance, partialState, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: partialState,
-          callback: callback,
-          isReplace: !1,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueSetState: function(inst, payload, callback) {
+        inst = inst._reactInternalFiber;
+        var currentTime = recalculateCurrentTime();
+        currentTime = computeExpirationForFiber(currentTime, inst);
+        var update = createUpdate(currentTime);
+        update.payload = payload;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, currentTime);
+        scheduleWork(inst, currentTime);
       },
-      enqueueReplaceState: function(instance, state, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: state,
-          callback: callback,
-          isReplace: !0,
-          isForced: !1,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueReplaceState: function(inst, payload, callback) {
+        inst = inst._reactInternalFiber;
+        var currentTime = recalculateCurrentTime();
+        currentTime = computeExpirationForFiber(currentTime, inst);
+        var update = createUpdate(currentTime);
+        update.tag = 1;
+        update.payload = payload;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, currentTime);
+        scheduleWork(inst, currentTime);
       },
-      enqueueForceUpdate: function(instance, callback) {
-        instance = instance._reactInternalFiber;
-        callback = void 0 === callback ? null : callback;
-        var expirationTime = computeExpirationForFiber(instance);
-        insertUpdateIntoFiber(instance, {
-          expirationTime: expirationTime,
-          partialState: null,
-          callback: callback,
-          isReplace: !1,
-          isForced: !0,
-          capturedValue: null,
-          next: null
-        });
-        scheduleWork(instance, expirationTime);
+      enqueueForceUpdate: function(inst, callback) {
+        inst = inst._reactInternalFiber;
+        var currentTime = recalculateCurrentTime();
+        currentTime = computeExpirationForFiber(currentTime, inst);
+        var update = createUpdate(currentTime);
+        update.tag = 2;
+        void 0 !== callback &&
+          null !== callback &&
+          (update.callback = callback);
+        enqueueUpdate(inst, update, currentTime);
+        scheduleWork(inst, currentTime);
       }
     };
   return {
     adoptClassInstance: adoptClassInstance,
-    callGetDerivedStateFromProps: callGetDerivedStateFromProps,
     constructClassInstance: function(workInProgress, props) {
       var ctor = workInProgress.type,
         unmaskedContext = getUnmaskedContext(workInProgress),
@@ -2043,25 +1907,15 @@ function ReactFiberClassComponent(
         context = needsContext
           ? getMaskedContext(workInProgress, unmaskedContext)
           : emptyObject;
-      ctor = new ctor(props, context);
-      var state =
-        null !== ctor.state && void 0 !== ctor.state ? ctor.state : null;
-      adoptClassInstance(workInProgress, ctor);
-      workInProgress.memoizedState = state;
-      props = callGetDerivedStateFromProps(workInProgress, ctor, props, state);
-      null !== props &&
-        void 0 !== props &&
-        (workInProgress.memoizedState = Object.assign(
-          {},
-          workInProgress.memoizedState,
-          props
-        ));
+      props = new ctor(props, context);
+      workInProgress.memoizedState =
+        null !== props.state && void 0 !== props.state ? props.state : null;
+      adoptClassInstance(workInProgress, props);
       needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return ctor;
+      return props;
     },
     mountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        current = workInProgress.alternate,
         instance = workInProgress.stateNode,
         props = workInProgress.pendingProps,
         unmaskedContext = getUnmaskedContext(workInProgress);
@@ -2069,6 +1923,20 @@ function ReactFiberClassComponent(
       instance.state = workInProgress.memoizedState;
       instance.refs = emptyObject;
       instance.context = getMaskedContext(workInProgress, unmaskedContext);
+      unmaskedContext = workInProgress.updateQueue;
+      null !== unmaskedContext &&
+        (processUpdateQueue(
+          workInProgress,
+          unmaskedContext,
+          props,
+          instance,
+          renderExpirationTime
+        ),
+        (instance.state = workInProgress.memoizedState));
+      unmaskedContext = workInProgress.type.getDerivedStateFromProps;
+      "function" === typeof unmaskedContext &&
+        (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+        (instance.state = workInProgress.memoizedState));
       "function" === typeof ctor.getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate ||
         ("function" !== typeof instance.UNSAFE_componentWillMount &&
@@ -2079,32 +1947,36 @@ function ReactFiberClassComponent(
         "function" === typeof instance.UNSAFE_componentWillMount &&
           instance.UNSAFE_componentWillMount(),
         ctor !== instance.state &&
-          updater.enqueueReplaceState(instance, instance.state, null),
-        (ctor = workInProgress.updateQueue),
-        null !== ctor &&
-          (instance.state = processUpdateQueue(
-            current,
-            workInProgress,
-            ctor,
+          classComponentUpdater.enqueueReplaceState(
             instance,
+            instance.state,
+            null
+          ),
+        (unmaskedContext = workInProgress.updateQueue),
+        null !== unmaskedContext &&
+          (processUpdateQueue(
+            workInProgress,
+            unmaskedContext,
             props,
+            instance,
             renderExpirationTime
-          )));
+          ),
+          (instance.state = workInProgress.memoizedState)));
       "function" === typeof instance.componentDidMount &&
         (workInProgress.effectTag |= 4);
     },
     resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
+        instance = workInProgress.stateNode,
+        oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps;
+      instance.props = oldProps;
+      var oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2115,61 +1987,47 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
-      oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              null,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
+      hasForceUpdate = !1;
+      var oldState = workInProgress.memoizedState;
+      oldContext = instance.state = oldState;
+      var updateQueue = workInProgress.updateQueue;
+      null !== updateQueue &&
+        (processUpdateQueue(
           workInProgress,
-          instance,
+          updateQueue,
           newProps,
+          instance,
           renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue = workInProgress.updateQueue;
-        null !== _updateQueue &&
-          (_updateQueue.baseState = Object.assign(
-            {},
-            _updateQueue.baseState,
-            derivedStateFromProps
-          ));
-      }
+        ),
+        (oldContext = workInProgress.memoizedState));
       if (
-        !(
-          oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
-          hasContextChanged() ||
-          (null !== workInProgress.updateQueue &&
-            workInProgress.updateQueue.hasForceUpdate)
-        )
+        oldProps === newProps &&
+        oldState === oldContext &&
+        !hasContextChanged() &&
+        !hasForceUpdate
       )
         return (
           "function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
           !1
         );
-      (oldProps = checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldContext,
-        renderExpirationTime,
-        newUnmaskedContext
-      ))
+      "function" === typeof getDerivedStateFromProps &&
+        (applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        ),
+        (oldContext = workInProgress.memoizedState));
+      (renderExpirationTime =
+        hasForceUpdate ||
+        checkShouldComponentUpdate(
+          workInProgress,
+          oldProps,
+          newProps,
+          oldState,
+          oldContext,
+          newUnmaskedContext
+        ))
         ? (ctor ||
             ("function" !== typeof instance.UNSAFE_componentWillMount &&
               "function" !== typeof instance.componentWillMount) ||
@@ -2181,12 +2039,12 @@ function ReactFiberClassComponent(
             (workInProgress.effectTag |= 4))
         : ("function" === typeof instance.componentDidMount &&
             (workInProgress.effectTag |= 4),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
+          (workInProgress.memoizedProps = newProps),
+          (workInProgress.memoizedState = oldContext));
       instance.props = newProps;
-      instance.state = renderExpirationTime;
+      instance.state = oldContext;
       instance.context = newUnmaskedContext;
-      return oldProps;
+      return renderExpirationTime;
     },
     updateClassInstance: function(
       current,
@@ -2194,16 +2052,16 @@ function ReactFiberClassComponent(
       renderExpirationTime
     ) {
       var ctor = workInProgress.type,
-        instance = workInProgress.stateNode;
-      instance.props = workInProgress.memoizedProps;
-      instance.state = workInProgress.memoizedState;
-      var oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps,
-        oldContext = instance.context,
+        instance = workInProgress.stateNode,
+        oldProps = workInProgress.memoizedProps,
+        newProps = workInProgress.pendingProps;
+      instance.props = oldProps;
+      var oldContext = instance.context,
         newUnmaskedContext = getUnmaskedContext(workInProgress);
       newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
+      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
       (ctor =
-        "function" === typeof ctor.getDerivedStateFromProps ||
+        "function" === typeof getDerivedStateFromProps ||
         "function" === typeof instance.getSnapshotBeforeUpdate) ||
         ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
           "function" !== typeof instance.componentWillReceiveProps) ||
@@ -2214,47 +2072,24 @@ function ReactFiberClassComponent(
             newProps,
             newUnmaskedContext
           ));
+      hasForceUpdate = !1;
       oldContext = workInProgress.memoizedState;
-      renderExpirationTime =
-        null !== workInProgress.updateQueue
-          ? processUpdateQueue(
-              current,
-              workInProgress,
-              workInProgress.updateQueue,
-              instance,
-              newProps,
-              renderExpirationTime
-            )
-          : oldContext;
-      var derivedStateFromProps = void 0;
-      oldProps !== newProps &&
-        (derivedStateFromProps = callGetDerivedStateFromProps(
+      var newState = (instance.state = oldContext),
+        updateQueue = workInProgress.updateQueue;
+      null !== updateQueue &&
+        (processUpdateQueue(
           workInProgress,
-          instance,
+          updateQueue,
           newProps,
+          instance,
           renderExpirationTime
-        ));
-      if (null !== derivedStateFromProps && void 0 !== derivedStateFromProps) {
-        renderExpirationTime =
-          null === renderExpirationTime || void 0 === renderExpirationTime
-            ? derivedStateFromProps
-            : Object.assign({}, renderExpirationTime, derivedStateFromProps);
-        var _updateQueue3 = workInProgress.updateQueue;
-        null !== _updateQueue3 &&
-          (_updateQueue3.baseState = Object.assign(
-            {},
-            _updateQueue3.baseState,
-            derivedStateFromProps
-          ));
-      }
+        ),
+        (newState = workInProgress.memoizedState));
       if (
-        !(
-          oldProps !== newProps ||
-          oldContext !== renderExpirationTime ||
-          hasContextChanged() ||
-          (null !== workInProgress.updateQueue &&
-            workInProgress.updateQueue.hasForceUpdate)
-        )
+        oldProps === newProps &&
+        oldContext === newState &&
+        !hasContextChanged() &&
+        !hasForceUpdate
       )
         return (
           "function" !== typeof instance.componentDidUpdate ||
@@ -2264,36 +2099,45 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
+            (workInProgress.effectTag |= 256),
           !1
         );
-      (derivedStateFromProps = checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldContext,
-        renderExpirationTime,
-        newUnmaskedContext
-      ))
+      "function" === typeof getDerivedStateFromProps &&
+        (applyDerivedStateFromProps(
+          workInProgress,
+          getDerivedStateFromProps,
+          newProps
+        ),
+        (newState = workInProgress.memoizedState));
+      (renderExpirationTime =
+        hasForceUpdate ||
+        checkShouldComponentUpdate(
+          workInProgress,
+          oldProps,
+          newProps,
+          oldContext,
+          newState,
+          newUnmaskedContext
+        ))
         ? (ctor ||
             ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
               "function" !== typeof instance.componentWillUpdate) ||
             ("function" === typeof instance.componentWillUpdate &&
               instance.componentWillUpdate(
                 newProps,
-                renderExpirationTime,
+                newState,
                 newUnmaskedContext
               ),
             "function" === typeof instance.UNSAFE_componentWillUpdate &&
               instance.UNSAFE_componentWillUpdate(
                 newProps,
-                renderExpirationTime,
+                newState,
                 newUnmaskedContext
               )),
           "function" === typeof instance.componentDidUpdate &&
             (workInProgress.effectTag |= 4),
           "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 2048))
+            (workInProgress.effectTag |= 256))
         : ("function" !== typeof instance.componentDidUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
@@ -2301,13 +2145,13 @@ function ReactFiberClassComponent(
           "function" !== typeof instance.getSnapshotBeforeUpdate ||
             (oldProps === current.memoizedProps &&
               oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 2048),
-          memoizeProps(workInProgress, newProps),
-          memoizeState(workInProgress, renderExpirationTime));
+            (workInProgress.effectTag |= 256),
+          (workInProgress.memoizedProps = newProps),
+          (workInProgress.memoizedState = newState));
       instance.props = newProps;
-      instance.state = renderExpirationTime;
+      instance.state = newState;
       instance.context = newUnmaskedContext;
-      return derivedStateFromProps;
+      return renderExpirationTime;
     }
   };
 }
@@ -2431,11 +2275,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, textContent, expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function updateElement(returnFiber, current, element, expirationTime) {
@@ -2443,7 +2287,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       return (
         (expirationTime = useFiber(current, element.props, expirationTime)),
         (expirationTime.ref = coerceRef(returnFiber, current, element)),
-        (expirationTime["return"] = returnFiber),
+        (expirationTime.return = returnFiber),
         expirationTime
       );
     expirationTime = createFiberFromElement(
@@ -2452,7 +2296,7 @@ function ChildReconciler(shouldTrackSideEffects) {
       expirationTime
     );
     expirationTime.ref = coerceRef(returnFiber, current, element);
-    expirationTime["return"] = returnFiber;
+    expirationTime.return = returnFiber;
     return expirationTime;
   }
   function updatePortal(returnFiber, current, portal, expirationTime) {
@@ -2468,11 +2312,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, portal.children || [], expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function updateFragment(returnFiber, current, fragment, expirationTime, key) {
@@ -2484,11 +2328,11 @@ function ChildReconciler(shouldTrackSideEffects) {
           expirationTime,
           key
         )),
-        (current["return"] = returnFiber),
+        (current.return = returnFiber),
         current
       );
     current = useFiber(current, fragment, expirationTime);
-    current["return"] = returnFiber;
+    current.return = returnFiber;
     return current;
   }
   function createChild(returnFiber, newChild, expirationTime) {
@@ -2499,7 +2343,7 @@ function ChildReconciler(shouldTrackSideEffects) {
           returnFiber.mode,
           expirationTime
         )),
-        (newChild["return"] = returnFiber),
+        (newChild.return = returnFiber),
         newChild
       );
     if ("object" === typeof newChild && null !== newChild) {
@@ -2512,7 +2356,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               expirationTime
             )),
             (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
-            (expirationTime["return"] = returnFiber),
+            (expirationTime.return = returnFiber),
             expirationTime
           );
         case REACT_PORTAL_TYPE:
@@ -2522,7 +2366,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (newChild["return"] = returnFiber),
+            (newChild.return = returnFiber),
             newChild
           );
       }
@@ -2534,7 +2378,7 @@ function ChildReconciler(shouldTrackSideEffects) {
             expirationTime,
             null
           )),
-          (newChild["return"] = returnFiber),
+          (newChild.return = returnFiber),
           newChild
         );
       throwOnInvalidObjectType(returnFiber, newChild);
@@ -2721,17 +2565,21 @@ function ChildReconciler(shouldTrackSideEffects) {
           newChildren[newIdx],
           expirationTime
         ))
-      ) {
-        if (shouldTrackSideEffects && null !== nextOldFiber.alternate)
-          oldFiber["delete"](
+      )
+        shouldTrackSideEffects &&
+          null !== nextOldFiber.alternate &&
+          oldFiber.delete(
             null === nextOldFiber.key ? newIdx : nextOldFiber.key
-          );
-        currentFirstChild = placeChild(nextOldFiber, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (resultingFirstChild = nextOldFiber)
-          : (previousNewFiber.sibling = nextOldFiber);
-        previousNewFiber = nextOldFiber;
-      }
+          ),
+          (currentFirstChild = placeChild(
+            nextOldFiber,
+            currentFirstChild,
+            newIdx
+          )),
+          null === previousNewFiber
+            ? (resultingFirstChild = nextOldFiber)
+            : (previousNewFiber.sibling = nextOldFiber),
+          (previousNewFiber = nextOldFiber);
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2805,24 +2653,22 @@ function ChildReconciler(shouldTrackSideEffects) {
       !step.done;
       newIdx++, step = newChildrenIterable.next()
     )
-      if (
-        ((step = updateFromMap(
-          oldFiber,
-          returnFiber,
-          newIdx,
-          step.value,
-          expirationTime
-        )),
-        null !== step)
-      ) {
-        if (shouldTrackSideEffects && null !== step.alternate)
-          oldFiber["delete"](null === step.key ? newIdx : step.key);
-        currentFirstChild = placeChild(step, currentFirstChild, newIdx);
-        null === previousNewFiber
-          ? (iteratorFn = step)
-          : (previousNewFiber.sibling = step);
-        previousNewFiber = step;
-      }
+      (step = updateFromMap(
+        oldFiber,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      )),
+        null !== step &&
+          (shouldTrackSideEffects &&
+            null !== step.alternate &&
+            oldFiber.delete(null === step.key ? newIdx : step.key),
+          (currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+          null === previousNewFiber
+            ? (iteratorFn = step)
+            : (previousNewFiber.sibling = step),
+          (previousNewFiber = step));
     shouldTrackSideEffects &&
       oldFiber.forEach(function(child) {
         return deleteChild(returnFiber, child);
@@ -2861,7 +2707,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     isObject,
                     newChild
                   );
-                  currentFirstChild["return"] = returnFiber;
+                  currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2878,7 +2724,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   expirationTime,
                   newChild.key
                 )),
-                (currentFirstChild["return"] = returnFiber),
+                (currentFirstChild.return = returnFiber),
                 (returnFiber = currentFirstChild))
               : ((expirationTime = createFiberFromElement(
                   newChild,
@@ -2890,7 +2736,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                   currentFirstChild,
                   newChild
                 )),
-                (expirationTime["return"] = returnFiber),
+                (expirationTime.return = returnFiber),
                 (returnFiber = expirationTime));
           }
           return placeSingleChild(returnFiber);
@@ -2914,7 +2760,7 @@ function ChildReconciler(shouldTrackSideEffects) {
                     newChild.children || [],
                     expirationTime
                   );
-                  currentFirstChild["return"] = returnFiber;
+                  currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
@@ -2929,7 +2775,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             );
-            currentFirstChild["return"] = returnFiber;
+            currentFirstChild.return = returnFiber;
             returnFiber = currentFirstChild;
           }
           return placeSingleChild(returnFiber);
@@ -2944,7 +2790,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               newChild,
               expirationTime
             )),
-            (currentFirstChild["return"] = returnFiber),
+            (currentFirstChild.return = returnFiber),
             (returnFiber = currentFirstChild))
           : (deleteRemainingChildren(returnFiber, currentFirstChild),
             (currentFirstChild = createFiberFromText(
@@ -2952,7 +2798,7 @@ function ChildReconciler(shouldTrackSideEffects) {
               returnFiber.mode,
               expirationTime
             )),
-            (currentFirstChild["return"] = returnFiber),
+            (currentFirstChild.return = returnFiber),
             (returnFiber = currentFirstChild)),
         placeSingleChild(returnFiber)
       );
@@ -2994,7 +2840,9 @@ function ReactFiberBeginWork(
   newContext,
   hydrationContext,
   scheduleWork,
-  computeExpirationForFiber
+  computeExpirationForFiber,
+  profilerTimer,
+  recalculateCurrentTime
 ) {
   function reconcileChildren(current, workInProgress, nextChildren) {
     reconcileChildrenAtExpirationTime(
@@ -3038,10 +2886,10 @@ function ReactFiberBeginWork(
     workInProgress,
     shouldUpdate,
     hasContext,
-    didCaptureError,
     renderExpirationTime
   ) {
     markRef(current, workInProgress);
+    var didCaptureError = 0 !== (workInProgress.effectTag & 64);
     if (!shouldUpdate && !didCaptureError)
       return (
         hasContext && invalidateContextProvider(workInProgress, !1),
@@ -3089,11 +2937,8 @@ function ReactFiberBeginWork(
     renderExpirationTime
   ) {
     var fiber = workInProgress.child;
-    for (
-      null !== fiber && (fiber["return"] = workInProgress);
-      null !== fiber;
-
-    ) {
+    null !== fiber && (fiber.return = workInProgress);
+    for (; null !== fiber; ) {
       switch (fiber.tag) {
         case 12:
           var nextFiber = fiber.stateNode | 0;
@@ -3116,7 +2961,7 @@ function ReactFiberBeginWork(
               )
                 alternate.expirationTime = renderExpirationTime;
               else break;
-              nextFiber = nextFiber["return"];
+              nextFiber = nextFiber.return;
             }
             nextFiber = null;
           } else nextFiber = fiber.child;
@@ -3127,7 +2972,7 @@ function ReactFiberBeginWork(
         default:
           nextFiber = fiber.child;
       }
-      if (null !== nextFiber) nextFiber["return"] = fiber;
+      if (null !== nextFiber) nextFiber.return = fiber;
       else
         for (nextFiber = fiber; null !== nextFiber; ) {
           if (nextFiber === workInProgress) {
@@ -3136,10 +2981,11 @@ function ReactFiberBeginWork(
           }
           fiber = nextFiber.sibling;
           if (null !== fiber) {
+            fiber.return = nextFiber.return;
             nextFiber = fiber;
             break;
           }
-          nextFiber = nextFiber["return"];
+          nextFiber = nextFiber.return;
         }
       fiber = nextFiber;
     }
@@ -3151,8 +2997,10 @@ function ReactFiberBeginWork(
   ) {
     var context = workInProgress.type._context,
       newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps;
-    if (!hasLegacyContextChanged() && oldProps === newProps)
+      oldProps = workInProgress.memoizedProps,
+      canBailOnProps = !0;
+    if (hasLegacyContextChanged()) canBailOnProps = !1;
+    else if (oldProps === newProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
@@ -3162,7 +3010,7 @@ function ReactFiberBeginWork(
     workInProgress.memoizedProps = newProps;
     if (null === oldProps) newValue = 1073741823;
     else if (oldProps.value === newProps.value) {
-      if (oldProps.children === newProps.children)
+      if (oldProps.children === newProps.children && canBailOnProps)
         return (
           (workInProgress.stateNode = 0),
           pushProvider(workInProgress),
@@ -3176,7 +3024,7 @@ function ReactFiberBeginWork(
           (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
         (oldValue !== oldValue && newValue !== newValue)
       ) {
-        if (oldProps.children === newProps.children)
+        if (oldProps.children === newProps.children && canBailOnProps)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3191,7 +3039,7 @@ function ReactFiberBeginWork(
         (newValue |= 0),
         0 === newValue)
       ) {
-        if (oldProps.children === newProps.children)
+        if (oldProps.children === newProps.children && canBailOnProps)
           return (
             (workInProgress.stateNode = 0),
             pushProvider(workInProgress),
@@ -3223,14 +3071,14 @@ function ReactFiberBeginWork(
         current.expirationTime
       );
       workInProgress.child = newChild;
-      for (newChild["return"] = workInProgress; null !== current.sibling; )
+      for (newChild.return = workInProgress; null !== current.sibling; )
         (current = current.sibling),
           (newChild = newChild.sibling = createWorkInProgress(
             current,
             current.pendingProps,
             current.expirationTime
           )),
-          (newChild["return"] = workInProgress);
+          (newChild.return = workInProgress);
       newChild.sibling = null;
     }
     return workInProgress.child;
@@ -3240,6 +3088,8 @@ function ReactFiberBeginWork(
     pushHostContext = hostContext.pushHostContext,
     pushHostContainer = hostContext.pushHostContainer,
     pushProvider = newContext.pushProvider,
+    getContextCurrentValue = newContext.getContextCurrentValue,
+    getContextChangedBits = newContext.getContextChangedBits,
     getMaskedContext = legacyContext.getMaskedContext,
     getUnmaskedContext = legacyContext.getUnmaskedContext,
     hasLegacyContextChanged = legacyContext.hasContextChanged,
@@ -3259,10 +3109,10 @@ function ReactFiberBeginWork(
     },
     function(workInProgress, nextState) {
       workInProgress.memoizedState = nextState;
-    }
+    },
+    recalculateCurrentTime
   );
   var adoptClassInstance = config.adoptClassInstance,
-    callGetDerivedStateFromProps = config.callGetDerivedStateFromProps,
     constructClassInstance = config.constructClassInstance,
     mountClassInstance = config.mountClassInstance,
     resumeMountClassInstance = config.resumeMountClassInstance,
@@ -3311,20 +3161,13 @@ function ReactFiberBeginWork(
               (workInProgress.tag = 2),
               (workInProgress.memoizedState =
                 null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              "function" === typeof unmaskedContext.getDerivedStateFromProps &&
-                ((props = callGetDerivedStateFromProps(
+              (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
+              "function" === typeof unmaskedContext &&
+                applyDerivedStateFromProps(
                   workInProgress,
-                  fn,
-                  props,
-                  workInProgress.memoizedState
-                )),
-                null !== props &&
-                  void 0 !== props &&
-                  (workInProgress.memoizedState = Object.assign(
-                    {},
-                    workInProgress.memoizedState,
-                    props
-                  ))),
+                  unmaskedContext,
+                  props
+                ),
               (props = pushLegacyContextProvider(workInProgress)),
               adoptClassInstance(workInProgress, fn),
               mountClassInstance(workInProgress, renderExpirationTime),
@@ -3333,7 +3176,6 @@ function ReactFiberBeginWork(
                 workInProgress,
                 !0,
                 props,
-                !1,
                 renderExpirationTime
               )))
             : ((workInProgress.tag = 1),
@@ -3361,103 +3203,100 @@ function ReactFiberBeginWork(
             current
           );
         case 2:
-          props = pushLegacyContextProvider(workInProgress);
-          null === current
-            ? null === workInProgress.stateNode
-              ? (constructClassInstance(
-                  workInProgress,
-                  workInProgress.pendingProps
-                ),
-                mountClassInstance(workInProgress, renderExpirationTime),
-                (fn = !0))
-              : (fn = resumeMountClassInstance(
+          return (
+            (props = pushLegacyContextProvider(workInProgress)),
+            null === current
+              ? null === workInProgress.stateNode
+                ? (constructClassInstance(
+                    workInProgress,
+                    workInProgress.pendingProps,
+                    renderExpirationTime
+                  ),
+                  mountClassInstance(workInProgress, renderExpirationTime),
+                  (fn = !0))
+                : (fn = resumeMountClassInstance(
+                    workInProgress,
+                    renderExpirationTime
+                  ))
+              : (fn = updateClassInstance(
+                  current,
                   workInProgress,
                   renderExpirationTime
-                ))
-            : (fn = updateClassInstance(
-                current,
-                workInProgress,
-                renderExpirationTime
-              ));
-          unmaskedContext = !1;
-          var updateQueue = workInProgress.updateQueue;
-          null !== updateQueue &&
-            null !== updateQueue.capturedValues &&
-            (unmaskedContext = fn = !0);
-          return finishClassComponent(
-            current,
-            workInProgress,
-            fn,
-            props,
-            unmaskedContext,
-            renderExpirationTime
-          );
-        case 3:
-          a: if (
-            (pushHostRootContext(workInProgress),
-            (fn = workInProgress.updateQueue),
-            null !== fn)
-          ) {
-            unmaskedContext = workInProgress.memoizedState;
-            props = processUpdateQueue(
+                )),
+            finishClassComponent(
               current,
               workInProgress,
               fn,
-              null,
-              null,
+              props,
               renderExpirationTime
-            );
-            workInProgress.memoizedState = props;
-            fn = workInProgress.updateQueue;
-            if (null !== fn && null !== fn.capturedValues) fn = null;
-            else if (unmaskedContext === props) {
-              resetHydrationState();
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-              break a;
-            } else fn = props.element;
-            unmaskedContext = workInProgress.stateNode;
-            (null === current || null === current.child) &&
-            unmaskedContext.hydrate &&
-            enterHydrationState(workInProgress)
-              ? ((workInProgress.effectTag |= 2),
-                (workInProgress.child = mountChildFibers(
+            )
+          );
+        case 3:
+          return (
+            pushHostRootContext(workInProgress),
+            (props = workInProgress.updateQueue),
+            null !== props
+              ? ((fn = workInProgress.memoizedState),
+                (fn = null !== fn ? fn.element : null),
+                processUpdateQueue(
                   workInProgress,
+                  props,
+                  workInProgress.pendingProps,
                   null,
-                  fn,
                   renderExpirationTime
-                )))
+                ),
+                (props = workInProgress.memoizedState.element),
+                props === fn
+                  ? (resetHydrationState(),
+                    (current = bailoutOnAlreadyFinishedWork(
+                      current,
+                      workInProgress
+                    )))
+                  : ((fn = workInProgress.stateNode),
+                    (null === current || null === current.child) &&
+                    fn.hydrate &&
+                    enterHydrationState(workInProgress)
+                      ? ((workInProgress.effectTag |= 2),
+                        (workInProgress.child = mountChildFibers(
+                          workInProgress,
+                          null,
+                          props,
+                          renderExpirationTime
+                        )))
+                      : (resetHydrationState(),
+                        reconcileChildren(current, workInProgress, props)),
+                    (current = workInProgress.child)))
               : (resetHydrationState(),
-                reconcileChildren(current, workInProgress, fn));
-            workInProgress.memoizedState = props;
-            current = workInProgress.child;
-          } else
-            resetHydrationState(),
-              (current = bailoutOnAlreadyFinishedWork(current, workInProgress));
-          return current;
+                (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                ))),
+            current
+          );
         case 5:
           a: {
             pushHostContext(workInProgress);
             null === current &&
               tryToClaimNextHydratableInstance(workInProgress);
             props = workInProgress.type;
-            updateQueue = workInProgress.memoizedProps;
+            var memoizedProps = workInProgress.memoizedProps;
             fn = workInProgress.pendingProps;
             unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && updateQueue === fn) {
+            if (!hasLegacyContextChanged() && memoizedProps === fn) {
               if (
-                (updateQueue =
+                (memoizedProps =
                   workInProgress.mode & 1 &&
                   shouldDeprioritizeSubtree(props, fn))
               )
                 workInProgress.expirationTime = 1073741823;
-              if (!updateQueue || 1073741823 !== renderExpirationTime) {
+              if (!memoizedProps || 1073741823 !== renderExpirationTime) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
             }
-            updateQueue = fn.children;
+            memoizedProps = fn.children;
             shouldSetTextContent(props, fn)
-              ? (updateQueue = null)
+              ? (memoizedProps = null)
               : unmaskedContext &&
                 shouldSetTextContent(props, unmaskedContext) &&
                 (workInProgress.effectTag |= 16);
@@ -3468,7 +3307,7 @@ function ReactFiberBeginWork(
               ? ((workInProgress.expirationTime = 1073741823),
                 (workInProgress.memoizedProps = fn),
                 (current = null))
-              : (reconcileChildren(current, workInProgress, updateQueue),
+              : (reconcileChildren(current, workInProgress, memoizedProps),
                 (workInProgress.memoizedProps = fn),
                 (current = workInProgress.child));
           }
@@ -3508,6 +3347,8 @@ function ReactFiberBeginWork(
           );
         case 9:
           return null;
+        case 16:
+          return null;
         case 4:
           return (
             pushHostContainer(
@@ -3532,17 +3373,24 @@ function ReactFiberBeginWork(
                 )),
             current
           );
-        case 14:
-          return (
-            (renderExpirationTime = workInProgress.type.render),
-            (renderExpirationTime = renderExpirationTime(
-              workInProgress.pendingProps,
-              workInProgress.ref
-            )),
-            reconcileChildren(current, workInProgress, renderExpirationTime),
-            (workInProgress.memoizedProps = renderExpirationTime),
-            workInProgress.child
-          );
+        case 14:
+          return (
+            (props = workInProgress.type.render),
+            (renderExpirationTime = workInProgress.pendingProps),
+            (fn = workInProgress.ref),
+            hasLegacyContextChanged() ||
+            workInProgress.memoizedProps !== renderExpirationTime ||
+            fn !== (null !== current ? current.ref : null)
+              ? ((props = props(renderExpirationTime, fn)),
+                reconcileChildren(current, workInProgress, props),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child))
+              : (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                )),
+            current
+          );
         case 10:
           return (
             (renderExpirationTime = workInProgress.pendingProps),
@@ -3580,6 +3428,23 @@ function ReactFiberBeginWork(
                 )),
             current
           );
+        case 15:
+          return (
+            (renderExpirationTime = workInProgress.pendingProps),
+            workInProgress.memoizedProps === renderExpirationTime
+              ? (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                ))
+              : (reconcileChildren(
+                  current,
+                  workInProgress,
+                  renderExpirationTime.children
+                ),
+                (workInProgress.memoizedProps = renderExpirationTime),
+                (current = workInProgress.child)),
+            current
+          );
         case 13:
           return updateContextProvider(
             current,
@@ -3590,13 +3455,13 @@ function ReactFiberBeginWork(
           a: {
             fn = workInProgress.type;
             unmaskedContext = workInProgress.pendingProps;
-            updateQueue = workInProgress.memoizedProps;
-            props = fn._currentValue;
-            var changedBits = fn._changedBits;
+            memoizedProps = workInProgress.memoizedProps;
+            props = getContextCurrentValue(fn);
+            var changedBits = getContextChangedBits(fn);
             if (
               hasLegacyContextChanged() ||
               0 !== changedBits ||
-              updateQueue !== unmaskedContext
+              memoizedProps !== unmaskedContext
             ) {
               workInProgress.memoizedProps = unmaskedContext;
               var observedBits = unmaskedContext.unstable_observedBits;
@@ -3610,12 +3475,13 @@ function ReactFiberBeginWork(
                   changedBits,
                   renderExpirationTime
                 );
-              else if (updateQueue === unmaskedContext) {
+              else if (memoizedProps === unmaskedContext) {
                 current = bailoutOnAlreadyFinishedWork(current, workInProgress);
                 break a;
               }
               renderExpirationTime = unmaskedContext.children;
               renderExpirationTime = renderExpirationTime(props);
+              workInProgress.effectTag |= 1;
               reconcileChildren(current, workInProgress, renderExpirationTime);
               current = workInProgress.child;
             } else
@@ -3681,18 +3547,7 @@ function ReactFiberCompleteWork(
         case 1:
           return null;
         case 2:
-          return (
-            popLegacyContextProvider(workInProgress),
-            (current = workInProgress.stateNode),
-            (newProps = workInProgress.updateQueue),
-            null !== newProps &&
-              null !== newProps.capturedValues &&
-              ((workInProgress.effectTag &= -65),
-              "function" === typeof current.componentDidCatch
-                ? (workInProgress.effectTag |= 256)
-                : (newProps.capturedValues = null)),
-            null
-          );
+          return popLegacyContextProvider(workInProgress), null;
         case 3:
           popHostContainer(workInProgress);
           popTopLevelLegacyContextObject(workInProgress);
@@ -3703,10 +3558,6 @@ function ReactFiberCompleteWork(
           if (null === current || null === current.child)
             popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
           updateHostContainer(workInProgress);
-          current = workInProgress.updateQueue;
-          null !== current &&
-            null !== current.capturedValues &&
-            (workInProgress.effectTag |= 256);
           return null;
         case 5:
           popHostContext(workInProgress);
@@ -3714,10 +3565,10 @@ function ReactFiberCompleteWork(
           var type = workInProgress.type;
           if (null !== current && null != workInProgress.stateNode) {
             var oldProps = current.memoizedProps,
-              _instance = workInProgress.stateNode,
+              instance = workInProgress.stateNode,
               currentHostContext = getHostContext();
-            _instance = prepareUpdate(
-              _instance,
+            instance = prepareUpdate(
+              instance,
               type,
               oldProps,
               newProps,
@@ -3727,7 +3578,7 @@ function ReactFiberCompleteWork(
             updateHostComponent(
               current,
               workInProgress,
-              _instance,
+              instance,
               type,
               oldProps,
               newProps,
@@ -3774,21 +3625,20 @@ function ReactFiberCompleteWork(
                   4 !== currentHostContext.tag &&
                   null !== currentHostContext.child
                 ) {
-                  currentHostContext.child["return"] = currentHostContext;
+                  currentHostContext.child.return = currentHostContext;
                   currentHostContext = currentHostContext.child;
                   continue;
                 }
                 if (currentHostContext === workInProgress) break;
                 for (; null === currentHostContext.sibling; ) {
                   if (
-                    null === currentHostContext["return"] ||
-                    currentHostContext["return"] === workInProgress
+                    null === currentHostContext.return ||
+                    currentHostContext.return === workInProgress
                   )
                     break a;
-                  currentHostContext = currentHostContext["return"];
+                  currentHostContext = currentHostContext.return;
                 }
-                currentHostContext.sibling["return"] =
-                  currentHostContext["return"];
+                currentHostContext.sibling.return = currentHostContext.return;
                 currentHostContext = currentHostContext.sibling;
               }
               finalizeInitialChildren(
@@ -3841,30 +3691,34 @@ function ReactFiberCompleteWork(
           );
           workInProgress.tag = 8;
           type = [];
-          a: for (
-            (oldProps = workInProgress.stateNode) &&
-            (oldProps["return"] = workInProgress);
-            null !== oldProps;
-
-          ) {
-            if (5 === oldProps.tag || 6 === oldProps.tag || 4 === oldProps.tag)
-              invariant(!1, "A call cannot have host component children.");
-            else if (9 === oldProps.tag) type.push(oldProps.pendingProps.value);
-            else if (null !== oldProps.child) {
-              oldProps.child["return"] = oldProps;
-              oldProps = oldProps.child;
-              continue;
-            }
-            for (; null === oldProps.sibling; ) {
+          a: {
+            if ((oldProps = workInProgress.stateNode))
+              oldProps.return = workInProgress;
+            for (; null !== oldProps; ) {
               if (
-                null === oldProps["return"] ||
-                oldProps["return"] === workInProgress
+                5 === oldProps.tag ||
+                6 === oldProps.tag ||
+                4 === oldProps.tag
               )
-                break a;
-              oldProps = oldProps["return"];
+                invariant(!1, "A call cannot have host component children.");
+              else if (9 === oldProps.tag)
+                type.push(oldProps.pendingProps.value);
+              else if (null !== oldProps.child) {
+                oldProps.child.return = oldProps;
+                oldProps = oldProps.child;
+                continue;
+              }
+              for (; null === oldProps.sibling; ) {
+                if (
+                  null === oldProps.return ||
+                  oldProps.return === workInProgress
+                )
+                  break a;
+                oldProps = oldProps.return;
+              }
+              oldProps.sibling.return = oldProps.return;
+              oldProps = oldProps.sibling;
             }
-            oldProps.sibling["return"] = oldProps["return"];
-            oldProps = oldProps.sibling;
           }
           oldProps = newProps.handler;
           newProps = oldProps(newProps.props, type);
@@ -3881,10 +3735,14 @@ function ReactFiberCompleteWork(
           return null;
         case 14:
           return null;
+        case 16:
+          return null;
         case 10:
           return null;
         case 11:
           return null;
+        case 15:
+          return null;
         case 4:
           return (
             popHostContainer(workInProgress),
@@ -3909,103 +3767,11 @@ function ReactFiberCompleteWork(
     }
   };
 }
-function ReactFiberUnwindWork(
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  isAlreadyFailedLegacyErrorBoundary
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
+function createCapturedValue(value, source) {
   return {
-    throwException: function(returnFiber, sourceFiber, rawValue) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      sourceFiber = {
-        value: rawValue,
-        source: sourceFiber,
-        stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-      };
-      do {
-        switch (returnFiber.tag) {
-          case 3:
-            ensureUpdateQueues(returnFiber);
-            returnFiber.updateQueue.capturedValues = [sourceFiber];
-            returnFiber.effectTag |= 1024;
-            return;
-          case 2:
-            if (
-              ((rawValue = returnFiber.stateNode),
-              0 === (returnFiber.effectTag & 64) &&
-                null !== rawValue &&
-                "function" === typeof rawValue.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(rawValue))
-            ) {
-              ensureUpdateQueues(returnFiber);
-              rawValue = returnFiber.updateQueue;
-              var capturedValues = rawValue.capturedValues;
-              null === capturedValues
-                ? (rawValue.capturedValues = [sourceFiber])
-                : capturedValues.push(sourceFiber);
-              returnFiber.effectTag |= 1024;
-              return;
-            }
-        }
-        returnFiber = returnFiber["return"];
-      } while (null !== returnFiber);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
-      }
-    }
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
   };
 }
 function logError(boundary, errorInfo) {
@@ -4037,13 +3803,7 @@ function logError(boundary, errorInfo) {
     (e && e.suppressReactErrorLogging) || console.error(e);
   }
 }
-function ReactFiberCommitWork(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed
-) {
+function ReactFiberCommitWork(config, captureError) {
   function safelyDetachRef(current) {
     var ref = current.ref;
     if (null !== ref)
@@ -4060,12 +3820,12 @@ function ReactFiberCommitWork(
     switch (current.tag) {
       case 2:
         safelyDetachRef(current);
-        var _instance7 = current.stateNode;
-        if ("function" === typeof _instance7.componentWillUnmount)
+        var _instance6 = current.stateNode;
+        if ("function" === typeof _instance6.componentWillUnmount)
           try {
-            (_instance7.props = current.memoizedProps),
-              (_instance7.state = current.memoizedState),
-              _instance7.componentWillUnmount();
+            (_instance6.props = current.memoizedProps),
+              (_instance6.state = current.memoizedState),
+              _instance6.componentWillUnmount();
           } catch (unmountError) {
             captureError(current, unmountError);
           }
@@ -4088,12 +3848,12 @@ function ReactFiberCommitWork(
       ) {
         if (node === root) break;
         for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === root) return;
-          node = node["return"];
+          if (null === node.return || node.return === root) return;
+          node = node.return;
         }
-        node.sibling["return"] = node["return"];
+        node.sibling.return = node.return;
         node = node.sibling;
-      } else (node.child["return"] = node), (node = node.child);
+      } else (node.child.return = node), (node = node.child);
   }
   function isHostParent(fiber) {
     return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
@@ -4108,7 +3868,7 @@ function ReactFiberCommitWork(
 
     ) {
       if (!currentParentIsValid) {
-        currentParentIsValid = node["return"];
+        currentParentIsValid = node.return;
         a: for (;;) {
           invariant(
             null !== currentParentIsValid,
@@ -4128,7 +3888,7 @@ function ReactFiberCommitWork(
               currentParentIsContainer = !0;
               break a;
           }
-          currentParentIsValid = currentParentIsValid["return"];
+          currentParentIsValid = currentParentIsValid.return;
         }
         currentParentIsValid = !0;
       }
@@ -4143,17 +3903,17 @@ function ReactFiberCommitWork(
           : commitUnmount(node),
         null !== node.child)
       ) {
-        node.child["return"] = node;
+        node.child.return = node;
         node = node.child;
         continue;
       }
       if (node === current) break;
       for (; null === node.sibling; ) {
-        if (null === node["return"] || node["return"] === current) return;
-        node = node["return"];
+        if (null === node.return || node.return === current) return;
+        node = node.return;
         4 === node.tag && (currentParentIsValid = !1);
       }
-      node.sibling["return"] = node["return"];
+      node.sibling.return = node.return;
       node = node.sibling;
     }
   }
@@ -4178,7 +3938,7 @@ function ReactFiberCommitWork(
     commitBeforeMutationLifeCycles: function(current, finishedWork) {
       switch (finishedWork.tag) {
         case 2:
-          if (finishedWork.effectTag & 2048 && null !== current) {
+          if (finishedWork.effectTag & 256 && null !== current) {
             var prevProps = current.memoizedProps,
               prevState = current.memoizedState;
             current = finishedWork.stateNode;
@@ -4208,12 +3968,12 @@ function ReactFiberCommitWork(
     },
     commitPlacement: function(finishedWork) {
       a: {
-        for (var parent = finishedWork["return"]; null !== parent; ) {
+        for (var parent = finishedWork.return; null !== parent; ) {
           if (isHostParent(parent)) {
             var parentFiber = parent;
             break a;
           }
-          parent = parent["return"];
+          parent = parent.return;
         }
         invariant(
           !1,
@@ -4245,16 +4005,13 @@ function ReactFiberCommitWork(
         (resetTextContent(parent), (parentFiber.effectTag &= -17));
       a: b: for (parentFiber = finishedWork; ; ) {
         for (; null === parentFiber.sibling; ) {
-          if (
-            null === parentFiber["return"] ||
-            isHostParent(parentFiber["return"])
-          ) {
+          if (null === parentFiber.return || isHostParent(parentFiber.return)) {
             parentFiber = null;
             break a;
           }
-          parentFiber = parentFiber["return"];
+          parentFiber = parentFiber.return;
         }
-        parentFiber.sibling["return"] = parentFiber["return"];
+        parentFiber.sibling.return = parentFiber.return;
         for (
           parentFiber = parentFiber.sibling;
           5 !== parentFiber.tag && 6 !== parentFiber.tag;
@@ -4263,7 +4020,7 @@ function ReactFiberCommitWork(
           if (parentFiber.effectTag & 2) continue b;
           if (null === parentFiber.child || 4 === parentFiber.tag) continue b;
           else
-            (parentFiber.child["return"] = parentFiber),
+            (parentFiber.child.return = parentFiber),
               (parentFiber = parentFiber.child);
         }
         if (!(parentFiber.effectTag & 2)) {
@@ -4281,35 +4038,33 @@ function ReactFiberCommitWork(
               ? appendChildToContainer(parent, node.stateNode)
               : appendChild(parent, node.stateNode);
         else if (4 !== node.tag && null !== node.child) {
-          node.child["return"] = node;
+          node.child.return = node;
           node = node.child;
           continue;
         }
         if (node === finishedWork) break;
         for (; null === node.sibling; ) {
-          if (null === node["return"] || node["return"] === finishedWork)
-            return;
-          node = node["return"];
+          if (null === node.return || node.return === finishedWork) return;
+          node = node.return;
         }
-        node.sibling["return"] = node["return"];
+        node.sibling.return = node.return;
         node = node.sibling;
       }
     },
     commitDeletion: function(current) {
       unmountHostComponents(current);
-      current["return"] = null;
+      current.return = null;
       current.child = null;
       current.alternate &&
-        ((current.alternate.child = null),
-        (current.alternate["return"] = null));
+        ((current.alternate.child = null), (current.alternate.return = null));
     },
     commitWork: function(current, finishedWork) {
       switch (finishedWork.tag) {
         case 2:
           break;
         case 5:
-          var _instance8 = finishedWork.stateNode;
-          if (null != _instance8) {
+          var _instance7 = finishedWork.stateNode;
+          if (null != _instance7) {
             var newProps = finishedWork.memoizedProps;
             current = null !== current ? current.memoizedProps : newProps;
             var type = finishedWork.type,
@@ -4317,7 +4072,7 @@ function ReactFiberCommitWork(
             finishedWork.updateQueue = null;
             null !== updatePayload &&
               commitUpdate(
-                _instance8,
+                _instance7,
                 updatePayload,
                 type,
                 current,
@@ -4331,14 +4086,101 @@ function ReactFiberCommitWork(
             null !== finishedWork.stateNode,
             "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
           );
-          _instance8 = finishedWork.memoizedProps;
+          _instance7 = finishedWork.memoizedProps;
           commitTextUpdate(
             finishedWork.stateNode,
-            null !== current ? current.memoizedProps : _instance8,
-            _instance8
+            null !== current ? current.memoizedProps : _instance7,
+            _instance7
+          );
+          break;
+        case 3:
+          break;
+        case 15:
+          break;
+        case 16:
+          break;
+        default:
+          invariant(
+            !1,
+            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
           );
+      }
+    },
+    commitLifeCycles: function(
+      finishedRoot,
+      current,
+      finishedWork,
+      currentTime,
+      committedExpirationTime
+    ) {
+      switch (finishedWork.tag) {
+        case 2:
+          finishedRoot = finishedWork.stateNode;
+          finishedWork.effectTag & 4 &&
+            (null === current
+              ? ((finishedRoot.props = finishedWork.memoizedProps),
+                (finishedRoot.state = finishedWork.memoizedState),
+                finishedRoot.componentDidMount())
+              : ((currentTime = current.memoizedProps),
+                (current = current.memoizedState),
+                (finishedRoot.props = finishedWork.memoizedProps),
+                (finishedRoot.state = finishedWork.memoizedState),
+                finishedRoot.componentDidUpdate(
+                  currentTime,
+                  current,
+                  finishedRoot.__reactInternalSnapshotBeforeUpdate
+                )));
+          current = finishedWork.updateQueue;
+          null !== current &&
+            ((finishedRoot.props = finishedWork.memoizedProps),
+            (finishedRoot.state = finishedWork.memoizedState),
+            commitUpdateQueue(
+              finishedWork,
+              current,
+              finishedRoot,
+              committedExpirationTime
+            ));
           break;
         case 3:
+          current = finishedWork.updateQueue;
+          if (null !== current) {
+            finishedRoot = null;
+            if (null !== finishedWork.child)
+              switch (finishedWork.child.tag) {
+                case 5:
+                  finishedRoot = getPublicInstance(
+                    finishedWork.child.stateNode
+                  );
+                  break;
+                case 2:
+                  finishedRoot = finishedWork.child.stateNode;
+              }
+            commitUpdateQueue(
+              finishedWork,
+              current,
+              finishedRoot,
+              committedExpirationTime
+            );
+          }
+          break;
+        case 5:
+          committedExpirationTime = finishedWork.stateNode;
+          null === current &&
+            finishedWork.effectTag & 4 &&
+            commitMount(
+              committedExpirationTime,
+              finishedWork.type,
+              finishedWork.memoizedProps,
+              finishedWork
+            );
+          break;
+        case 6:
+          break;
+        case 4:
+          break;
+        case 15:
+          break;
+        case 16:
           break;
         default:
           invariant(
@@ -4347,137 +4189,176 @@ function ReactFiberCommitWork(
           );
       }
     },
-    commitLifeCycles: function(finishedRoot, current, finishedWork) {
-      switch (finishedWork.tag) {
+    commitAttachRef: function(finishedWork) {
+      var ref = finishedWork.ref;
+      if (null !== ref) {
+        var _instance5 = finishedWork.stateNode;
+        switch (finishedWork.tag) {
+          case 5:
+            finishedWork = getPublicInstance(_instance5);
+            break;
+          default:
+            finishedWork = _instance5;
+        }
+        "function" === typeof ref
+          ? ref(finishedWork)
+          : (ref.current = finishedWork);
+      }
+    },
+    commitDetachRef: function(current) {
+      current = current.ref;
+      null !== current &&
+        ("function" === typeof current
+          ? current(null)
+          : (current.current = null));
+    }
+  };
+}
+function ReactFiberUnwindWork(
+  config,
+  hostContext,
+  legacyContext,
+  newContext,
+  scheduleWork,
+  computeExpirationForFiber,
+  recalculateCurrentTime,
+  markLegacyErrorBoundaryAsFailed,
+  isAlreadyFailedLegacyErrorBoundary,
+  onUncaughtError
+) {
+  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+    expirationTime = createUpdate(expirationTime);
+    expirationTime.tag = 3;
+    expirationTime.payload = { element: null };
+    var error = errorInfo.value;
+    expirationTime.callback = function() {
+      onUncaughtError(error);
+      logError(fiber, errorInfo);
+    };
+    return expirationTime;
+  }
+  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+    expirationTime = createUpdate(expirationTime);
+    expirationTime.tag = 3;
+    var inst = fiber.stateNode;
+    null !== inst &&
+      "function" === typeof inst.componentDidCatch &&
+      (expirationTime.callback = function() {
+        markLegacyErrorBoundaryAsFailed(this);
+        var error = errorInfo.value,
+          stack = errorInfo.stack;
+        logError(fiber, errorInfo);
+        this.componentDidCatch(error, {
+          componentStack: null !== stack ? stack : ""
+        });
+      });
+    return expirationTime;
+  }
+  var popHostContainer = hostContext.popHostContainer,
+    popHostContext = hostContext.popHostContext,
+    popLegacyContextProvider = legacyContext.popContextProvider,
+    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
+    popProvider = newContext.popProvider;
+  return {
+    throwException: function(
+      root,
+      returnFiber,
+      sourceFiber,
+      value,
+      renderIsExpired,
+      renderExpirationTime
+    ) {
+      sourceFiber.effectTag |= 512;
+      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+      value = createCapturedValue(value, sourceFiber);
+      root = returnFiber;
+      do {
+        switch (root.tag) {
+          case 3:
+            root.effectTag |= 1024;
+            value = createRootErrorUpdate(root, value, renderExpirationTime);
+            enqueueCapturedUpdate(root, value, renderExpirationTime);
+            return;
+          case 2:
+            if (
+              ((returnFiber = value),
+              (sourceFiber = root.stateNode),
+              0 === (root.effectTag & 64) &&
+                null !== sourceFiber &&
+                "function" === typeof sourceFiber.componentDidCatch &&
+                !isAlreadyFailedLegacyErrorBoundary(sourceFiber))
+            ) {
+              root.effectTag |= 1024;
+              value = createClassErrorUpdate(
+                root,
+                returnFiber,
+                renderExpirationTime
+              );
+              enqueueCapturedUpdate(root, value, renderExpirationTime);
+              return;
+            }
+        }
+        root = root.return;
+      } while (null !== root);
+    },
+    unwindWork: function(workInProgress) {
+      switch (workInProgress.tag) {
+        case 2:
+          popLegacyContextProvider(workInProgress);
+          var effectTag = workInProgress.effectTag;
+          return effectTag & 1024
+            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+              workInProgress)
+            : null;
+        case 3:
+          return (
+            popHostContainer(workInProgress),
+            popTopLevelLegacyContextObject(workInProgress),
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 5:
+          return popHostContext(workInProgress), null;
+        case 16:
+          return (
+            (effectTag = workInProgress.effectTag),
+            effectTag & 1024
+              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+                workInProgress)
+              : null
+          );
+        case 4:
+          return popHostContainer(workInProgress), null;
+        case 13:
+          return popProvider(workInProgress), null;
+        default:
+          return null;
+      }
+    },
+    unwindInterruptedWork: function(interruptedWork) {
+      switch (interruptedWork.tag) {
         case 2:
-          finishedRoot = finishedWork.stateNode;
-          if (finishedWork.effectTag & 4)
-            if (null === current)
-              (finishedRoot.props = finishedWork.memoizedProps),
-                (finishedRoot.state = finishedWork.memoizedState),
-                finishedRoot.componentDidMount();
-            else {
-              var prevProps = current.memoizedProps;
-              current = current.memoizedState;
-              finishedRoot.props = finishedWork.memoizedProps;
-              finishedRoot.state = finishedWork.memoizedState;
-              finishedRoot.componentDidUpdate(
-                prevProps,
-                current,
-                finishedRoot.__reactInternalSnapshotBeforeUpdate
-              );
-            }
-          finishedWork = finishedWork.updateQueue;
-          null !== finishedWork && commitCallbacks(finishedWork, finishedRoot);
+          popLegacyContextProvider(interruptedWork);
           break;
         case 3:
-          current = finishedWork.updateQueue;
-          if (null !== current) {
-            finishedRoot = null;
-            if (null !== finishedWork.child)
-              switch (finishedWork.child.tag) {
-                case 5:
-                  finishedRoot = getPublicInstance(
-                    finishedWork.child.stateNode
-                  );
-                  break;
-                case 2:
-                  finishedRoot = finishedWork.child.stateNode;
-              }
-            commitCallbacks(current, finishedRoot);
-          }
+          popHostContainer(interruptedWork);
+          popTopLevelLegacyContextObject(interruptedWork);
           break;
         case 5:
-          finishedRoot = finishedWork.stateNode;
-          null === current &&
-            finishedWork.effectTag & 4 &&
-            commitMount(
-              finishedRoot,
-              finishedWork.type,
-              finishedWork.memoizedProps,
-              finishedWork
-            );
-          break;
-        case 6:
+          popHostContext(interruptedWork);
           break;
         case 4:
+          popHostContainer(interruptedWork);
           break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitErrorLogging: function(finishedWork, onUncaughtError) {
-      switch (finishedWork.tag) {
-        case 2:
-          var ctor = finishedWork.type;
-          onUncaughtError = finishedWork.stateNode;
-          var updateQueue = finishedWork.updateQueue;
-          invariant(
-            null !== updateQueue && null !== updateQueue.capturedValues,
-            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-          );
-          var capturedErrors = updateQueue.capturedValues;
-          updateQueue.capturedValues = null;
-          "function" !== typeof ctor.getDerivedStateFromCatch &&
-            markLegacyErrorBoundaryAsFailed(onUncaughtError);
-          onUncaughtError.props = finishedWork.memoizedProps;
-          onUncaughtError.state = finishedWork.memoizedState;
-          for (ctor = 0; ctor < capturedErrors.length; ctor++) {
-            updateQueue = capturedErrors[ctor];
-            var _error = updateQueue.value,
-              stack = updateQueue.stack;
-            logError(finishedWork, updateQueue);
-            onUncaughtError.componentDidCatch(_error, {
-              componentStack: null !== stack ? stack : ""
-            });
-          }
-          break;
-        case 3:
-          ctor = finishedWork.updateQueue;
-          invariant(
-            null !== ctor && null !== ctor.capturedValues,
-            "An error logging effect should not have been scheduled if no errors were captured. This error is likely caused by a bug in React. Please file an issue."
-          );
-          capturedErrors = ctor.capturedValues;
-          ctor.capturedValues = null;
-          for (ctor = 0; ctor < capturedErrors.length; ctor++)
-            (updateQueue = capturedErrors[ctor]),
-              logError(finishedWork, updateQueue),
-              onUncaughtError(updateQueue.value);
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag cannot capture errors.  This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitAttachRef: function(finishedWork) {
-      var ref = finishedWork.ref;
-      if (null !== ref) {
-        var _instance6 = finishedWork.stateNode;
-        switch (finishedWork.tag) {
-          case 5:
-            finishedWork = getPublicInstance(_instance6);
-            break;
-          default:
-            finishedWork = _instance6;
-        }
-        "function" === typeof ref
-          ? ref(finishedWork)
-          : (ref.current = finishedWork);
+        case 13:
+          popProvider(interruptedWork);
       }
     },
-    commitDetachRef: function(current) {
-      current = current.ref;
-      null !== current &&
-        ("function" === typeof current
-          ? current(null)
-          : (current.current = null));
-    }
+    createRootErrorUpdate: createRootErrorUpdate,
+    createClassErrorUpdate: createClassErrorUpdate
   };
 }
 var NO_CONTEXT = {};
@@ -4536,7 +4417,7 @@ function ReactFiberHydrationContext(config) {
     var fiber = new FiberNode(5, null, null, 0);
     fiber.type = "DELETED";
     fiber.stateNode = instance;
-    fiber["return"] = returnFiber;
+    fiber.return = returnFiber;
     fiber.effectTag = 8;
     null !== returnFiber.lastEffect
       ? ((returnFiber.lastEffect.nextEffect = fiber),
@@ -4568,11 +4449,11 @@ function ReactFiberHydrationContext(config) {
   }
   function popToNextHostParent(fiber) {
     for (
-      fiber = fiber["return"];
+      fiber = fiber.return;
       null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
 
     )
-      fiber = fiber["return"];
+      fiber = fiber.return;
     hydrationParentFiber = fiber;
   }
   var shouldSetTextContent = config.shouldSetTextContent;
@@ -4806,7 +4687,7 @@ function ReactFiberLegacyContext(stack) {
       ) {
         if (isContextProvider(fiber))
           return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber["return"];
+        fiber = fiber.return;
         invariant(
           fiber,
           "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
@@ -4816,7 +4697,7 @@ function ReactFiberLegacyContext(stack) {
     }
   };
 }
-function ReactFiberNewContext(stack) {
+function ReactFiberNewContext(stack, isPrimaryRenderer) {
   var createCursor = stack.createCursor,
     push = stack.push,
     pop = stack.pop,
@@ -4826,11 +4707,17 @@ function ReactFiberNewContext(stack) {
   return {
     pushProvider: function(providerFiber) {
       var context = providerFiber.type._context;
-      push(changedBitsCursor, context._changedBits, providerFiber);
-      push(valueCursor, context._currentValue, providerFiber);
-      push(providerCursor, providerFiber, providerFiber);
-      context._currentValue = providerFiber.pendingProps.value;
-      context._changedBits = providerFiber.stateNode;
+      isPrimaryRenderer
+        ? (push(changedBitsCursor, context._changedBits, providerFiber),
+          push(valueCursor, context._currentValue, providerFiber),
+          push(providerCursor, providerFiber, providerFiber),
+          (context._currentValue = providerFiber.pendingProps.value),
+          (context._changedBits = providerFiber.stateNode))
+        : (push(changedBitsCursor, context._changedBits2, providerFiber),
+          push(valueCursor, context._currentValue2, providerFiber),
+          push(providerCursor, providerFiber, providerFiber),
+          (context._currentValue2 = providerFiber.pendingProps.value),
+          (context._changedBits2 = providerFiber.stateNode));
     },
     popProvider: function(providerFiber) {
       var changedBits = changedBitsCursor.current,
@@ -4839,8 +4726,17 @@ function ReactFiberNewContext(stack) {
       pop(valueCursor, providerFiber);
       pop(changedBitsCursor, providerFiber);
       providerFiber = providerFiber.type._context;
-      providerFiber._currentValue = currentValue;
-      providerFiber._changedBits = changedBits;
+      isPrimaryRenderer
+        ? ((providerFiber._currentValue = currentValue),
+          (providerFiber._changedBits = changedBits))
+        : ((providerFiber._currentValue2 = currentValue),
+          (providerFiber._changedBits2 = changedBits));
+    },
+    getContextCurrentValue: function(context) {
+      return isPrimaryRenderer ? context._currentValue : context._currentValue2;
+    },
+    getContextChangedBits: function(context) {
+      return isPrimaryRenderer ? context._changedBits : context._changedBits2;
     }
   };
 }
@@ -4873,14 +4769,16 @@ function ReactFiberScheduler(config) {
   function resetStack() {
     if (null !== nextUnitOfWork)
       for (
-        var interruptedWork = nextUnitOfWork["return"];
+        var interruptedWork = nextUnitOfWork.return;
         null !== interruptedWork;
 
       )
         unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork["return"]);
+          (interruptedWork = interruptedWork.return);
     nextRoot = null;
     nextRenderExpirationTime = 0;
+    nextLatestTimeoutMs = -1;
+    nextRenderIsExpired = !1;
     nextUnitOfWork = null;
     isRootReadyForCommit = !1;
   }
@@ -4890,10 +4788,15 @@ function ReactFiberScheduler(config) {
       legacyErrorBoundariesThatAlreadyFailed.has(instance)
     );
   }
+  function markLegacyErrorBoundaryAsFailed(instance) {
+    null === legacyErrorBoundariesThatAlreadyFailed
+      ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
+      : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+  }
   function completeUnitOfWork(workInProgress$jscomp$0) {
     for (;;) {
       var current = workInProgress$jscomp$0.alternate,
-        returnFiber = workInProgress$jscomp$0["return"],
+        returnFiber = workInProgress$jscomp$0.return,
         siblingFiber = workInProgress$jscomp$0.sibling;
       if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
         current = completeWork(
@@ -4906,24 +4809,20 @@ function ReactFiberScheduler(config) {
           1073741823 === nextRenderExpirationTime ||
           1073741823 !== workInProgress.expirationTime
         ) {
-          b: switch (workInProgress.tag) {
+          var newExpirationTime = 0;
+          switch (workInProgress.tag) {
             case 3:
             case 2:
-              var newExpirationTime = workInProgress.updateQueue;
-              newExpirationTime =
-                null === newExpirationTime
-                  ? 0
-                  : newExpirationTime.expirationTime;
-              break b;
-            default:
-              newExpirationTime = 0;
+              var updateQueue = workInProgress.updateQueue;
+              null !== updateQueue &&
+                (newExpirationTime = updateQueue.expirationTime);
           }
-          for (var child = workInProgress.child; null !== child; )
-            0 !== child.expirationTime &&
+          for (updateQueue = workInProgress.child; null !== updateQueue; )
+            0 !== updateQueue.expirationTime &&
               (0 === newExpirationTime ||
-                newExpirationTime > child.expirationTime) &&
-              (newExpirationTime = child.expirationTime),
-              (child = child.sibling);
+                newExpirationTime > updateQueue.expirationTime) &&
+              (newExpirationTime = updateQueue.expirationTime),
+              (updateQueue = updateQueue.sibling);
           workInProgress.expirationTime = newExpirationTime;
         }
         if (null !== current) return current;
@@ -4948,10 +4847,14 @@ function ReactFiberScheduler(config) {
           break;
         }
       } else {
-        workInProgress$jscomp$0 = unwindWork(workInProgress$jscomp$0);
+        workInProgress$jscomp$0 = unwindWork(
+          workInProgress$jscomp$0,
+          nextRenderIsExpired,
+          nextRenderExpirationTime
+        );
         if (null !== workInProgress$jscomp$0)
           return (
-            (workInProgress$jscomp$0.effectTag &= 2559), workInProgress$jscomp$0
+            (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
           );
         null !== returnFiber &&
           ((returnFiber.firstEffect = returnFiber.lastEffect = null),
@@ -4987,6 +4890,7 @@ function ReactFiberScheduler(config) {
       resetStack(),
         (nextRoot = root),
         (nextRenderExpirationTime = expirationTime),
+        (nextLatestTimeoutMs = -1),
         (nextUnitOfWork = createWorkInProgress(
           nextRoot.current,
           null,
@@ -4994,6 +4898,8 @@ function ReactFiberScheduler(config) {
         )),
         (root.pendingCommitExpirationTime = 0);
     var didFatal = !1;
+    nextRenderIsExpired =
+      !isAsync || nextRenderExpirationTime <= mostRecentCurrentTime;
     do {
       try {
         if (isAsync)
@@ -5009,128 +4915,151 @@ function ReactFiberScheduler(config) {
           break;
         }
         isAsync = nextUnitOfWork;
-        var returnFiber = isAsync["return"];
+        var returnFiber = isAsync.return;
         if (null === returnFiber) {
           didFatal = !0;
           onUncaughtError(thrownValue);
           break;
         }
-        throwException(returnFiber, isAsync, thrownValue);
+        throwException(
+          root,
+          returnFiber,
+          isAsync,
+          thrownValue,
+          nextRenderIsExpired,
+          nextRenderExpirationTime,
+          mostRecentCurrentTimeMs
+        );
         nextUnitOfWork = completeUnitOfWork(isAsync);
       }
       break;
     } while (1);
     isWorking = !1;
-    if (didFatal || null !== nextUnitOfWork) return null;
-    if (isRootReadyForCommit)
-      return (
-        (root.pendingCommitExpirationTime = expirationTime),
-        root.current.alternate
+    if (didFatal) return null;
+    if (null === nextUnitOfWork) {
+      if (isRootReadyForCommit)
+        return (
+          (root.pendingCommitExpirationTime = expirationTime),
+          root.current.alternate
+        );
+      invariant(
+        !nextRenderIsExpired,
+        "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
       );
-    invariant(
-      !1,
-      "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
-    );
-  }
-  function scheduleCapture(sourceFiber, boundaryFiber, value, expirationTime) {
-    sourceFiber = {
-      value: value,
-      source: sourceFiber,
-      stack: getStackAddendumByWorkInProgressFiber(sourceFiber)
-    };
-    insertUpdateIntoFiber(boundaryFiber, {
-      expirationTime: expirationTime,
-      partialState: null,
-      callback: null,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: sourceFiber,
-      next: null
-    });
-    scheduleWork(boundaryFiber, expirationTime);
+      0 <= nextLatestTimeoutMs &&
+        setTimeout(function() {
+          retrySuspendedRoot(root, expirationTime);
+        }, nextLatestTimeoutMs);
+      onBlock(root.current.expirationTime);
+    }
+    return null;
   }
-  function onCommitPhaseError(fiber$jscomp$0, error) {
+  function onCommitPhaseError(fiber, error) {
+    var JSCompiler_inline_result;
     a: {
       invariant(
         !isWorking || isCommitting,
         "dispatch: Cannot dispatch during the render phase."
       );
-      for (var fiber = fiber$jscomp$0["return"]; null !== fiber; ) {
-        switch (fiber.tag) {
+      for (
+        JSCompiler_inline_result = fiber.return;
+        null !== JSCompiler_inline_result;
+
+      ) {
+        switch (JSCompiler_inline_result.tag) {
           case 2:
-            var instance = fiber.stateNode;
+            var instance = JSCompiler_inline_result.stateNode;
             if (
-              "function" === typeof fiber.type.getDerivedStateFromCatch ||
+              "function" ===
+                typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
               ("function" === typeof instance.componentDidCatch &&
                 !isAlreadyFailedLegacyErrorBoundary(instance))
             ) {
-              scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-              fiber$jscomp$0 = void 0;
+              fiber = createCapturedValue(error, fiber);
+              fiber = createClassErrorUpdate(
+                JSCompiler_inline_result,
+                fiber,
+                1
+              );
+              enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+              scheduleWork(JSCompiler_inline_result, 1);
+              JSCompiler_inline_result = void 0;
               break a;
             }
             break;
           case 3:
-            scheduleCapture(fiber$jscomp$0, fiber, error, 1);
-            fiber$jscomp$0 = void 0;
+            fiber = createCapturedValue(error, fiber);
+            fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+            enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+            scheduleWork(JSCompiler_inline_result, 1);
+            JSCompiler_inline_result = void 0;
             break a;
         }
-        fiber = fiber["return"];
+        JSCompiler_inline_result = JSCompiler_inline_result.return;
       }
-      3 === fiber$jscomp$0.tag &&
-        scheduleCapture(fiber$jscomp$0, fiber$jscomp$0, error, 1);
-      fiber$jscomp$0 = void 0;
+      3 === fiber.tag &&
+        ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
+        (JSCompiler_inline_result = createRootErrorUpdate(
+          fiber,
+          JSCompiler_inline_result,
+          1
+        )),
+        enqueueUpdate(fiber, JSCompiler_inline_result, 1),
+        scheduleWork(fiber, 1));
+      JSCompiler_inline_result = void 0;
     }
-    return fiber$jscomp$0;
+    return JSCompiler_inline_result;
   }
-  function computeExpirationForFiber(fiber) {
-    fiber =
+  function computeExpirationForFiber(currentTime, fiber) {
+    currentTime =
       0 !== expirationContext
         ? expirationContext
         : isWorking
           ? isCommitting ? 1 : nextRenderExpirationTime
           : fiber.mode & 1
             ? isBatchingInteractiveUpdates
-              ? 10 * ((((recalculateCurrentTime() + 15) / 10) | 0) + 1)
-              : 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1)
+              ? 2 + 10 * ((((currentTime - 2 + 15) / 10) | 0) + 1)
+              : 2 + 25 * ((((currentTime - 2 + 500) / 25) | 0) + 1)
             : 1;
     isBatchingInteractiveUpdates &&
       (0 === lowestPendingInteractiveExpirationTime ||
-        fiber > lowestPendingInteractiveExpirationTime) &&
-      (lowestPendingInteractiveExpirationTime = fiber);
-    return fiber;
+        currentTime > lowestPendingInteractiveExpirationTime) &&
+      (lowestPendingInteractiveExpirationTime = currentTime);
+    return currentTime;
+  }
+  function retrySuspendedRoot(root) {
+    var retryTime = root.current.expirationTime;
+    0 !== retryTime &&
+      (0 === root.remainingExpirationTime ||
+        root.remainingExpirationTime < retryTime) &&
+      requestWork(root, retryTime);
   }
   function scheduleWork(fiber, expirationTime) {
-    a: {
-      for (; null !== fiber; ) {
-        if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
-          fiber.expirationTime = expirationTime;
-        null !== fiber.alternate &&
-          (0 === fiber.alternate.expirationTime ||
-            fiber.alternate.expirationTime > expirationTime) &&
-          (fiber.alternate.expirationTime = expirationTime);
-        if (null === fiber["return"])
-          if (3 === fiber.tag) {
-            var root = fiber.stateNode;
-            !isWorking &&
-              0 !== nextRenderExpirationTime &&
-              expirationTime < nextRenderExpirationTime &&
-              resetStack();
-            (isWorking && !isCommitting && nextRoot === root) ||
-              requestWork(root, expirationTime);
-            nestedUpdateCount > NESTED_UPDATE_LIMIT &&
-              invariant(
-                !1,
-                "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
-              );
-          } else {
-            expirationTime = void 0;
-            break a;
-          }
-        fiber = fiber["return"];
-      }
-      expirationTime = void 0;
+    for (; null !== fiber; ) {
+      if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
+        fiber.expirationTime = expirationTime;
+      null !== fiber.alternate &&
+        (0 === fiber.alternate.expirationTime ||
+          fiber.alternate.expirationTime > expirationTime) &&
+        (fiber.alternate.expirationTime = expirationTime);
+      if (null === fiber.return)
+        if (3 === fiber.tag) {
+          var root = fiber.stateNode;
+          !isWorking &&
+            0 !== nextRenderExpirationTime &&
+            expirationTime < nextRenderExpirationTime &&
+            resetStack();
+          var nextExpirationTimeToWorkOn = root.current.expirationTime;
+          (isWorking && !isCommitting && nextRoot === root) ||
+            requestWork(root, nextExpirationTimeToWorkOn);
+          nestedUpdateCount > NESTED_UPDATE_LIMIT &&
+            invariant(
+              !1,
+              "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
+            );
+        } else break;
+      fiber = fiber.return;
     }
-    return expirationTime;
   }
   function recalculateCurrentTime() {
     mostRecentCurrentTimeMs = now() - originalStartTimeMs;
@@ -5256,11 +5185,12 @@ function ReactFiberScheduler(config) {
           recalculateCurrentTime() >= nextFlushedExpirationTime);
 
       )
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        ),
+        recalculateCurrentTime(),
+          performWorkOnRoot(
+            nextFlushedRoot,
+            nextFlushedExpirationTime,
+            !deadlineDidExpire
+          ),
           findHighestPriorityRoot();
     else
       for (
@@ -5366,7 +5296,7 @@ function ReactFiberScheduler(config) {
         error = void 0;
       try {
         for (; null !== nextEffect; )
-          nextEffect.effectTag & 2048 &&
+          nextEffect.effectTag & 256 &&
             commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
             (nextEffect = nextEffect.nextEffect);
       } catch (e) {
@@ -5442,8 +5372,6 @@ function ReactFiberScheduler(config) {
               didError,
               error
             );
-          effectTag$jscomp$0 & 256 &&
-            commitErrorLogging(nextEffect, onUncaughtError);
           effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
           var next = nextEffect.nextEffect;
           nextEffect.nextEffect = null;
@@ -5480,11 +5408,24 @@ function ReactFiberScheduler(config) {
     nextFlushedRoot.remainingExpirationTime = 0;
     hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
   }
-  var stack = ReactFiberStack(),
+  function onBlock(remainingExpirationTime) {
+    invariant(
+      null !== nextFlushedRoot,
+      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
+    );
+    nextFlushedRoot.remainingExpirationTime = remainingExpirationTime;
+  }
+  var now = config.now,
+    scheduleDeferredCallback = config.scheduleDeferredCallback,
+    cancelDeferredCallback = config.cancelDeferredCallback,
+    prepareForCommit = config.prepareForCommit,
+    resetAfterCommit = config.resetAfterCommit,
+    stack = ReactFiberStack(),
     hostContext = ReactFiberHostContext(config, stack),
     legacyContext = ReactFiberLegacyContext(stack);
-  stack = ReactFiberNewContext(stack);
-  var hydrationContext = ReactFiberHydrationContext(config),
+  stack = ReactFiberNewContext(stack, config.isPrimaryRenderer);
+  var profilerTimer = createProfilerTimer(now),
+    hydrationContext = ReactFiberHydrationContext(config),
     beginWork = ReactFiberBeginWork(
       config,
       hostContext,
@@ -5492,52 +5433,58 @@ function ReactFiberScheduler(config) {
       stack,
       hydrationContext,
       scheduleWork,
-      computeExpirationForFiber
+      computeExpirationForFiber,
+      profilerTimer,
+      recalculateCurrentTime
     ).beginWork,
     completeWork = ReactFiberCompleteWork(
       config,
       hostContext,
       legacyContext,
       stack,
-      hydrationContext
+      hydrationContext,
+      profilerTimer
     ).completeWork;
   hostContext = ReactFiberUnwindWork(
+    config,
     hostContext,
     legacyContext,
     stack,
     scheduleWork,
-    isAlreadyFailedLegacyErrorBoundary
+    computeExpirationForFiber,
+    recalculateCurrentTime,
+    markLegacyErrorBoundaryAsFailed,
+    isAlreadyFailedLegacyErrorBoundary,
+    onUncaughtError,
+    profilerTimer,
+    function(root, thenable, timeoutMs) {
+      0 <= timeoutMs &&
+        nextLatestTimeoutMs < timeoutMs &&
+        (nextLatestTimeoutMs = timeoutMs);
+    },
+    retrySuspendedRoot
   );
   var throwException = hostContext.throwException,
     unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork;
-  hostContext = ReactFiberCommitWork(
+    unwindInterruptedWork = hostContext.unwindInterruptedWork,
+    createRootErrorUpdate = hostContext.createRootErrorUpdate,
+    createClassErrorUpdate = hostContext.createClassErrorUpdate;
+  config = ReactFiberCommitWork(
     config,
     onCommitPhaseError,
     scheduleWork,
     computeExpirationForFiber,
-    function(instance) {
-      null === legacyErrorBoundariesThatAlreadyFailed
-        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-        : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-    },
+    markLegacyErrorBoundaryAsFailed,
     recalculateCurrentTime
   );
-  var commitBeforeMutationLifeCycles =
-      hostContext.commitBeforeMutationLifeCycles,
-    commitResetTextContent = hostContext.commitResetTextContent,
-    commitPlacement = hostContext.commitPlacement,
-    commitDeletion = hostContext.commitDeletion,
-    commitWork = hostContext.commitWork,
-    commitLifeCycles = hostContext.commitLifeCycles,
-    commitErrorLogging = hostContext.commitErrorLogging,
-    commitAttachRef = hostContext.commitAttachRef,
-    commitDetachRef = hostContext.commitDetachRef,
-    now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit,
+  var commitBeforeMutationLifeCycles = config.commitBeforeMutationLifeCycles,
+    commitResetTextContent = config.commitResetTextContent,
+    commitPlacement = config.commitPlacement,
+    commitDeletion = config.commitDeletion,
+    commitWork = config.commitWork,
+    commitLifeCycles = config.commitLifeCycles,
+    commitAttachRef = config.commitAttachRef,
+    commitDetachRef = config.commitDetachRef,
     originalStartTimeMs = now(),
     mostRecentCurrentTime = 2,
     mostRecentCurrentTimeMs = originalStartTimeMs,
@@ -5547,6 +5494,8 @@ function ReactFiberScheduler(config) {
     nextUnitOfWork = null,
     nextRoot = null,
     nextRenderExpirationTime = 0,
+    nextLatestTimeoutMs = -1,
+    nextRenderIsExpired = !1,
     nextEffect = null,
     isCommitting = !1,
     isRootReadyForCommit = !1,
@@ -5635,7 +5584,7 @@ function ReactFiberScheduler(config) {
     deferredUpdates: function(fn) {
       var previousExpirationContext = expirationContext;
       expirationContext =
-        25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
+        2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
       try {
         return fn();
       } finally {
@@ -5669,7 +5618,8 @@ function ReactFiberScheduler(config) {
         (lowestPendingInteractiveExpirationTime = 0));
     },
     computeUniqueAsyncExpiration: function() {
-      var result = 25 * ((((recalculateCurrentTime() + 500) / 25) | 0) + 1);
+      var result =
+        2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
       result <= lastUniqueAsyncExpiration &&
         (result = lastUniqueAsyncExpiration + 1);
       return (lastUniqueAsyncExpiration = result);
@@ -5682,11 +5632,10 @@ function ReactFiberReconciler$1(config) {
     element,
     container,
     parentComponent,
-    currentTime,
     expirationTime,
     callback
   ) {
-    currentTime = container.current;
+    var current = container.current;
     if (parentComponent) {
       parentComponent = parentComponent._reactInternalFiber;
       var parentContext = findCurrentUnmaskedContext(parentComponent);
@@ -5698,16 +5647,12 @@ function ReactFiberReconciler$1(config) {
       ? (container.context = parentComponent)
       : (container.pendingContext = parentComponent);
     container = callback;
-    insertUpdateIntoFiber(currentTime, {
-      expirationTime: expirationTime,
-      partialState: { element: element },
-      callback: void 0 === container ? null : container,
-      isReplace: !1,
-      isForced: !1,
-      capturedValue: null,
-      next: null
-    });
-    scheduleWork(currentTime, expirationTime);
+    callback = createUpdate(expirationTime);
+    callback.payload = { element: element };
+    container = void 0 === container ? null : container;
+    null !== container && (callback.callback = container);
+    enqueueUpdate(current, callback, expirationTime);
+    scheduleWork(current, expirationTime);
     return expirationTime;
   }
   var getPublicInstance = config.getPublicInstance;
@@ -5726,6 +5671,11 @@ function ReactFiberReconciler$1(config) {
         current: isAsync,
         containerInfo: containerInfo,
         pendingChildren: null,
+        earliestPendingTime: 0,
+        latestPendingTime: 0,
+        earliestSuspendedTime: 0,
+        latestSuspendedTime: 0,
+        latestPingedTime: 0,
         pendingCommitExpirationTime: 0,
         finishedWork: null,
         context: null,
@@ -5740,12 +5690,11 @@ function ReactFiberReconciler$1(config) {
     updateContainer: function(element, container, parentComponent, callback) {
       var current = container.current,
         currentTime = recalculateCurrentTime();
-      current = computeExpirationForFiber(current);
+      current = computeExpirationForFiber(currentTime, current);
       return updateContainerAtExpirationTime(
         element,
         container,
         parentComponent,
-        currentTime,
         current,
         callback
       );
@@ -5757,12 +5706,10 @@ function ReactFiberReconciler$1(config) {
       expirationTime,
       callback
     ) {
-      var currentTime = recalculateCurrentTime();
       return updateContainerAtExpirationTime(
         element,
         container,
         parentComponent,
-        currentTime,
         expirationTime,
         callback
       );
@@ -5823,14 +5770,257 @@ function ReactFiberReconciler$1(config) {
     }
   };
 }
-var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
-  ReactFiberReconciler$3 =
-    (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
-    ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3["default"]
-    ? ReactFiberReconciler$3["default"]
-    : ReactFiberReconciler$3,
-  ReactNativeFiberHostComponent = (function() {
+var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
+  ReactFiberReconciler$3 =
+    (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
+    ReactFiberReconciler$2,
+  reactReconciler = ReactFiberReconciler$3.default
+    ? ReactFiberReconciler$3.default
+    : ReactFiberReconciler$3;
+function createPortal(children, containerInfo, implementation) {
+  var key =
+    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
+  return {
+    $$typeof: REACT_PORTAL_TYPE,
+    key: null == key ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+var emptyObject$1 = {},
+  removedKeys = null,
+  removedKeyCount = 0;
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node))
+    for (var i = node.length; i-- && 0 < removedKeyCount; )
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+  else if (node && 0 < removedKeyCount)
+    for (i in removedKeys)
+      if (removedKeys[i]) {
+        var _nextProp = node[i];
+        if (void 0 !== _nextProp) {
+          var attributeConfig = validAttributes[i];
+          if (attributeConfig) {
+            "function" === typeof _nextProp && (_nextProp = !0);
+            "undefined" === typeof _nextProp && (_nextProp = null);
+            if ("object" !== typeof attributeConfig)
+              updatePayload[i] = _nextProp;
+            else if (
+              "function" === typeof attributeConfig.diff ||
+              "function" === typeof attributeConfig.process
+            )
+              (_nextProp =
+                "function" === typeof attributeConfig.process
+                  ? attributeConfig.process(_nextProp)
+                  : _nextProp),
+                (updatePayload[i] = _nextProp);
+            removedKeys[i] = !1;
+            removedKeyCount--;
+          }
+        }
+      }
+}
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) return updatePayload;
+  if (!prevProp || !nextProp)
+    return nextProp
+      ? addNestedProperty(updatePayload, nextProp, validAttributes)
+      : prevProp
+        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
+        : updatePayload;
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    var minLength =
+        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
+      i;
+    for (i = 0; i < minLength; i++)
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp[i],
+        nextProp[i],
+        validAttributes
+      );
+    for (; i < prevProp.length; i++)
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp[i],
+        validAttributes
+      );
+    for (; i < nextProp.length; i++)
+      updatePayload = addNestedProperty(
+        updatePayload,
+        nextProp[i],
+        validAttributes
+      );
+    return updatePayload;
+  }
+  return Array.isArray(prevProp)
+    ? diffProperties(
+        updatePayload,
+        flattenStyle(prevProp),
+        nextProp,
+        validAttributes
+      )
+    : diffProperties(
+        updatePayload,
+        prevProp,
+        flattenStyle(nextProp),
+        validAttributes
+      );
+}
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) return updatePayload;
+  if (!Array.isArray(nextProp))
+    return diffProperties(
+      updatePayload,
+      emptyObject$1,
+      nextProp,
+      validAttributes
+    );
+  for (var i = 0; i < nextProp.length; i++)
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) return updatePayload;
+  if (!Array.isArray(prevProp))
+    return diffProperties(
+      updatePayload,
+      prevProp,
+      emptyObject$1,
+      validAttributes
+    );
+  for (var i = 0; i < prevProp.length; i++)
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig, propKey;
+  for (propKey in nextProps)
+    if ((attributeConfig = validAttributes[propKey])) {
+      var prevProp = prevProps[propKey];
+      var nextProp = nextProps[propKey];
+      "function" === typeof nextProp &&
+        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
+      "undefined" === typeof nextProp &&
+        ((nextProp = null),
+        "undefined" === typeof prevProp && (prevProp = null));
+      removedKeys && (removedKeys[propKey] = !1);
+      if (updatePayload && void 0 !== updatePayload[propKey])
+        if ("object" !== typeof attributeConfig)
+          updatePayload[propKey] = nextProp;
+        else {
+          if (
+            "function" === typeof attributeConfig.diff ||
+            "function" === typeof attributeConfig.process
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              (updatePayload[propKey] = attributeConfig);
+        }
+      else if (prevProp !== nextProp)
+        if ("object" !== typeof attributeConfig)
+          ("object" !== typeof nextProp ||
+            null === nextProp ||
+            deepDiffer(prevProp, nextProp)) &&
+            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
+        else if (
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+        ) {
+          if (
+            void 0 === prevProp ||
+            ("function" === typeof attributeConfig.diff
+              ? attributeConfig.diff(prevProp, nextProp)
+              : "object" !== typeof nextProp ||
+                null === nextProp ||
+                deepDiffer(prevProp, nextProp))
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              ((updatePayload || (updatePayload = {}))[
+                propKey
+              ] = attributeConfig);
+        } else
+          (removedKeys = null),
+            (removedKeyCount = 0),
+            (updatePayload = diffNestedProperty(
+              updatePayload,
+              prevProp,
+              nextProp,
+              attributeConfig
+            )),
+            0 < removedKeyCount &&
+              updatePayload &&
+              (restoreDeletedValuesInNestedArray(
+                updatePayload,
+                nextProp,
+                attributeConfig
+              ),
+              (removedKeys = null));
+    }
+  for (var _propKey in prevProps)
+    void 0 === nextProps[_propKey] &&
+      (!(attributeConfig = validAttributes[_propKey]) ||
+        (updatePayload && void 0 !== updatePayload[_propKey]) ||
+        ((prevProp = prevProps[_propKey]),
+        void 0 !== prevProp &&
+          ("object" !== typeof attributeConfig ||
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
+              removedKeys || (removedKeys = {}),
+              removedKeys[_propKey] ||
+                ((removedKeys[_propKey] = !0), removedKeyCount++))
+            : (updatePayload = clearNestedProperty(
+                updatePayload,
+                prevProp,
+                attributeConfig
+              )))));
+  return updatePayload;
+}
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (callback) {
+      if ("boolean" === typeof context.__isMounted) {
+        if (!context.__isMounted) return;
+      } else if (
+        "function" === typeof context.isMounted &&
+        !context.isMounted()
+      )
+        return;
+      return callback.apply(context, arguments);
+    }
+  };
+}
+var ReactNativeFiberHostComponent = (function() {
     function ReactNativeFiberHostComponent(tag, viewConfig) {
       if (!(this instanceof ReactNativeFiberHostComponent))
         throw new TypeError("Cannot call a class as a function");
@@ -5920,204 +6110,238 @@ function recursivelyUncacheFiberNode(node) {
     : (uncacheFiberNode(node._nativeTag),
       node._children.forEach(recursivelyUncacheFiberNode));
 }
-var NativeRenderer = reactReconciler({
-    appendInitialChild: function(parentInstance, child) {
-      parentInstance._children.push(child);
-    },
-    createInstance: function(
-      type,
+var ReactNativeHostConfig = {
+  appendInitialChild: function(parentInstance, child) {
+    parentInstance._children.push(child);
+  },
+  createInstance: function(
+    type,
+    props,
+    rootContainerInstance,
+    hostContext,
+    internalInstanceHandle
+  ) {
+    var tag = allocateTag(),
+      viewConfig = ReactNativeViewConfigRegistry.get(type);
+    invariant(
+      "RCTView" !== type || !hostContext.isInAParentText,
+      "Nesting of <View> within <Text> is not currently supported."
+    );
+    type = diffProperties(
+      null,
+      emptyObject$1,
       props,
+      viewConfig.validAttributes
+    );
+    UIManager.createView(
+      tag,
+      viewConfig.uiViewClassName,
       rootContainerInstance,
-      hostContext,
-      internalInstanceHandle
-    ) {
-      hostContext = allocateTag();
-      type = ReactNativeViewConfigRegistry.get(type);
-      var updatePayload = diffProperties(
-        null,
-        emptyObject$1,
-        props,
-        type.validAttributes
-      );
-      UIManager.createView(
-        hostContext,
-        type.uiViewClassName,
-        rootContainerInstance,
-        updatePayload
-      );
-      rootContainerInstance = new ReactNativeFiberHostComponent(
-        hostContext,
-        type
-      );
-      instanceCache[hostContext] = internalInstanceHandle;
-      instanceProps[hostContext] = props;
-      return rootContainerInstance;
-    },
-    createTextInstance: function(
-      text,
-      rootContainerInstance,
-      hostContext,
-      internalInstanceHandle
-    ) {
-      hostContext = allocateTag();
-      UIManager.createView(hostContext, "RCTRawText", rootContainerInstance, {
-        text: text
-      });
-      instanceCache[hostContext] = internalInstanceHandle;
-      return hostContext;
-    },
-    finalizeInitialChildren: function(parentInstance) {
-      if (0 === parentInstance._children.length) return !1;
-      var nativeTags = parentInstance._children.map(function(child) {
-        return "number" === typeof child ? child : child._nativeTag;
-      });
-      UIManager.setChildren(parentInstance._nativeTag, nativeTags);
-      return !1;
-    },
-    getRootHostContext: function() {
-      return emptyObject;
+      type
+    );
+    rootContainerInstance = new ReactNativeFiberHostComponent(tag, viewConfig);
+    instanceCache[tag] = internalInstanceHandle;
+    instanceProps[tag] = props;
+    return rootContainerInstance;
+  },
+  createTextInstance: function(
+    text,
+    rootContainerInstance,
+    hostContext,
+    internalInstanceHandle
+  ) {
+    invariant(
+      hostContext.isInAParentText,
+      "Text strings must be rendered within a <Text> component."
+    );
+    hostContext = allocateTag();
+    UIManager.createView(hostContext, "RCTRawText", rootContainerInstance, {
+      text: text
+    });
+    instanceCache[hostContext] = internalInstanceHandle;
+    return hostContext;
+  },
+  finalizeInitialChildren: function(parentInstance) {
+    if (0 === parentInstance._children.length) return !1;
+    var nativeTags = parentInstance._children.map(function(child) {
+      return "number" === typeof child ? child : child._nativeTag;
+    });
+    UIManager.setChildren(parentInstance._nativeTag, nativeTags);
+    return !1;
+  },
+  getRootHostContext: function() {
+    return { isInAParentText: !1 };
+  },
+  getChildHostContext: function(parentHostContext, type) {
+    type =
+      "AndroidTextInput" === type ||
+      "RCTMultilineTextInputView" === type ||
+      "RCTSinglelineTextInputView" === type ||
+      "RCTText" === type ||
+      "RCTVirtualText" === type;
+    return parentHostContext.isInAParentText !== type
+      ? { isInAParentText: type }
+      : parentHostContext;
+  },
+  getPublicInstance: function(instance) {
+    return instance;
+  },
+  now: now,
+  isPrimaryRenderer: !0,
+  prepareForCommit: function() {},
+  prepareUpdate: function() {
+    return emptyObject;
+  },
+  resetAfterCommit: function() {},
+  scheduleDeferredCallback: function(callback) {
+    scheduledCallback = callback;
+    return setTimeout(setTimeoutCallback, 1);
+  },
+  cancelDeferredCallback: function(callbackID) {
+    scheduledCallback = null;
+    clearTimeout(callbackID);
+  },
+  shouldDeprioritizeSubtree: function() {
+    return !1;
+  },
+  shouldSetTextContent: function() {
+    return !1;
+  },
+  mutation: {
+    appendChild: function(parentInstance, child) {
+      var childTag = "number" === typeof child ? child : child._nativeTag,
+        children = parentInstance._children,
+        index = children.indexOf(child);
+      0 <= index
+        ? (children.splice(index, 1),
+          children.push(child),
+          UIManager.manageChildren(
+            parentInstance._nativeTag,
+            [index],
+            [children.length - 1],
+            [],
+            [],
+            []
+          ))
+        : (children.push(child),
+          UIManager.manageChildren(
+            parentInstance._nativeTag,
+            [],
+            [],
+            [childTag],
+            [children.length - 1],
+            []
+          ));
     },
-    getChildHostContext: function() {
-      return emptyObject;
+    appendChildToContainer: function(parentInstance, child) {
+      UIManager.setChildren(parentInstance, [
+        "number" === typeof child ? child : child._nativeTag
+      ]);
     },
-    getPublicInstance: function(instance) {
-      return instance;
+    commitTextUpdate: function(textInstance, oldText, newText) {
+      UIManager.updateView(textInstance, "RCTRawText", { text: newText });
     },
-    now: now,
-    prepareForCommit: function() {},
-    prepareUpdate: function() {
-      return emptyObject;
+    commitMount: function() {},
+    commitUpdate: function(
+      instance,
+      updatePayloadTODO,
+      type,
+      oldProps,
+      newProps
+    ) {
+      updatePayloadTODO = instance.viewConfig;
+      instanceProps[instance._nativeTag] = newProps;
+      oldProps = diffProperties(
+        null,
+        oldProps,
+        newProps,
+        updatePayloadTODO.validAttributes
+      );
+      null != oldProps &&
+        UIManager.updateView(
+          instance._nativeTag,
+          updatePayloadTODO.uiViewClassName,
+          oldProps
+        );
     },
-    resetAfterCommit: function() {},
-    scheduleDeferredCallback: function(callback) {
-      scheduledCallback = callback;
-      return setTimeout(setTimeoutCallback, 1);
+    insertBefore: function(parentInstance, child, beforeChild) {
+      var children = parentInstance._children,
+        index = children.indexOf(child);
+      0 <= index
+        ? (children.splice(index, 1),
+          (beforeChild = children.indexOf(beforeChild)),
+          children.splice(beforeChild, 0, child),
+          UIManager.manageChildren(
+            parentInstance._nativeTag,
+            [index],
+            [beforeChild],
+            [],
+            [],
+            []
+          ))
+        : ((index = children.indexOf(beforeChild)),
+          children.splice(index, 0, child),
+          UIManager.manageChildren(
+            parentInstance._nativeTag,
+            [],
+            [],
+            ["number" === typeof child ? child : child._nativeTag],
+            [index],
+            []
+          ));
     },
-    cancelDeferredCallback: function(callbackID) {
-      scheduledCallback = null;
-      clearTimeout(callbackID);
+    insertInContainerBefore: function(parentInstance) {
+      invariant(
+        "number" !== typeof parentInstance,
+        "Container does not support insertBefore operation"
+      );
     },
-    shouldDeprioritizeSubtree: function() {
-      return !1;
+    removeChild: function(parentInstance, child) {
+      recursivelyUncacheFiberNode(child);
+      var children = parentInstance._children;
+      child = children.indexOf(child);
+      children.splice(child, 1);
+      UIManager.manageChildren(
+        parentInstance._nativeTag,
+        [],
+        [],
+        [],
+        [],
+        [child]
+      );
     },
-    shouldSetTextContent: function() {
-      return !1;
+    removeChildFromContainer: function(parentInstance, child) {
+      recursivelyUncacheFiberNode(child);
+      UIManager.manageChildren(parentInstance, [], [], [], [], [0]);
     },
-    mutation: {
-      appendChild: function(parentInstance, child) {
-        var childTag = "number" === typeof child ? child : child._nativeTag,
-          children = parentInstance._children,
-          index = children.indexOf(child);
-        0 <= index
-          ? (children.splice(index, 1),
-            children.push(child),
-            UIManager.manageChildren(
-              parentInstance._nativeTag,
-              [index],
-              [children.length - 1],
-              [],
-              [],
-              []
-            ))
-          : (children.push(child),
-            UIManager.manageChildren(
-              parentInstance._nativeTag,
-              [],
-              [],
-              [childTag],
-              [children.length - 1],
-              []
-            ));
-      },
-      appendChildToContainer: function(parentInstance, child) {
-        UIManager.setChildren(parentInstance, [
-          "number" === typeof child ? child : child._nativeTag
-        ]);
-      },
-      commitTextUpdate: function(textInstance, oldText, newText) {
-        UIManager.updateView(textInstance, "RCTRawText", { text: newText });
-      },
-      commitMount: function() {},
-      commitUpdate: function(
-        instance,
-        updatePayloadTODO,
-        type,
-        oldProps,
-        newProps
-      ) {
-        updatePayloadTODO = instance.viewConfig;
-        instanceProps[instance._nativeTag] = newProps;
-        oldProps = diffProperties(
-          null,
-          oldProps,
-          newProps,
-          updatePayloadTODO.validAttributes
-        );
-        null != oldProps &&
-          UIManager.updateView(
-            instance._nativeTag,
-            updatePayloadTODO.uiViewClassName,
-            oldProps
-          );
-      },
-      insertBefore: function(parentInstance, child, beforeChild) {
-        var children = parentInstance._children,
-          index = children.indexOf(child);
-        0 <= index
-          ? (children.splice(index, 1),
-            (beforeChild = children.indexOf(beforeChild)),
-            children.splice(beforeChild, 0, child),
-            UIManager.manageChildren(
-              parentInstance._nativeTag,
-              [index],
-              [beforeChild],
-              [],
-              [],
-              []
-            ))
-          : ((index = children.indexOf(beforeChild)),
-            children.splice(index, 0, child),
-            UIManager.manageChildren(
-              parentInstance._nativeTag,
-              [],
-              [],
-              ["number" === typeof child ? child : child._nativeTag],
-              [index],
-              []
-            ));
-      },
-      insertInContainerBefore: function(parentInstance) {
-        invariant(
-          "number" !== typeof parentInstance,
-          "Container does not support insertBefore operation"
-        );
-      },
-      removeChild: function(parentInstance, child) {
-        recursivelyUncacheFiberNode(child);
-        var children = parentInstance._children;
-        child = children.indexOf(child);
-        children.splice(child, 1);
-        UIManager.manageChildren(
-          parentInstance._nativeTag,
-          [],
-          [],
-          [],
-          [],
-          [child]
-        );
-      },
-      removeChildFromContainer: function(parentInstance, child) {
-        recursivelyUncacheFiberNode(child);
-        UIManager.manageChildren(parentInstance, [], [], [], [], [0]);
-      },
-      resetTextContent: function() {}
+    resetTextContent: function() {}
+  }
+};
+function _inherits(subClass, superClass) {
+  if ("function" !== typeof superClass && null !== superClass)
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: !1,
+      writable: !0,
+      configurable: !0
     }
-  }),
-  getInspectorDataForViewTag = void 0;
+  });
+  superClass &&
+    (Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass));
+}
+var getInspectorDataForViewTag = void 0;
 getInspectorDataForViewTag = function() {
   invariant(!1, "getInspectorDataForViewTag() is not available in production");
 };
-var findHostInstance = NativeRenderer.findHostInstance;
+var ReactNativeFiberRenderer = reactReconciler(ReactNativeHostConfig),
+  findHostInstance = ReactNativeFiberRenderer.findHostInstance;
 function findNodeHandle(componentOrHandle) {
   if (null == componentOrHandle) return null;
   if ("number" === typeof componentOrHandle) return componentOrHandle;
@@ -6131,8 +6355,8 @@ function findNodeHandle(componentOrHandle) {
       ? componentOrHandle.canonical._nativeTag
       : componentOrHandle._nativeTag;
 }
-_batchedUpdates = NativeRenderer.batchedUpdates;
-_flushInteractiveUpdates = NativeRenderer.flushInteractiveUpdates;
+_batchedUpdates = ReactNativeFiberRenderer.batchedUpdates;
+_flushInteractiveUpdates = ReactNativeFiberRenderer.flushInteractiveUpdates;
 var roots = new Map(),
   ReactNativeRenderer = {
     NativeComponent: (function(findNodeHandle, findHostInstance) {
@@ -6210,16 +6434,20 @@ var roots = new Map(),
     render: function(element, containerTag, callback) {
       var root = roots.get(containerTag);
       root ||
-        ((root = NativeRenderer.createContainer(containerTag, !1, !1)),
+        ((root = ReactNativeFiberRenderer.createContainer(
+          containerTag,
+          !1,
+          !1
+        )),
         roots.set(containerTag, root));
-      NativeRenderer.updateContainer(element, root, null, callback);
-      return NativeRenderer.getPublicRootInstance(root);
+      ReactNativeFiberRenderer.updateContainer(element, root, null, callback);
+      return ReactNativeFiberRenderer.getPublicRootInstance(root);
     },
     unmountComponentAtNode: function(containerTag) {
       var root = roots.get(containerTag);
       root &&
-        NativeRenderer.updateContainer(null, root, null, function() {
-          roots["delete"](containerTag);
+        ReactNativeFiberRenderer.updateContainer(null, root, null, function() {
+          roots.delete(containerTag);
         });
     },
     unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
@@ -6295,7 +6523,7 @@ var roots = new Map(),
       }
     }
   };
-NativeRenderer.injectIntoDevTools({
+ReactNativeFiberRenderer.injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
@@ -6305,6 +6533,6 @@ NativeRenderer.injectIntoDevTools({
 var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
   ReactNativeRenderer$3 =
     (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
-module.exports = ReactNativeRenderer$3["default"]
-  ? ReactNativeRenderer$3["default"]
+module.exports = ReactNativeRenderer$3.default
+  ? ReactNativeRenderer$3.default
   : ReactNativeRenderer$3;
diff --git a/Libraries/Renderer/shims/NativeMethodsMixin.js b/Libraries/Renderer/shims/NativeMethodsMixin.js
index 7acdf99bbd39..70e1d9dda540 100644
--- a/Libraries/Renderer/shims/NativeMethodsMixin.js
+++ b/Libraries/Renderer/shims/NativeMethodsMixin.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/Libraries/Renderer/shims/ReactDebugTool.js b/Libraries/Renderer/shims/ReactDebugTool.js
deleted file mode 100644
index 8ea7ba5c1433..000000000000
--- a/Libraries/Renderer/shims/ReactDebugTool.js
+++ /dev/null
@@ -1,16 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- */
-
-'use strict';
-
-const {
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-} = require('ReactNative');
-
-module.exports =
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactDebugTool;
diff --git a/Libraries/Renderer/shims/ReactFabric.js b/Libraries/Renderer/shims/ReactFabric.js
index 8dce288d28a7..a5e317ba4a27 100644
--- a/Libraries/Renderer/shims/ReactFabric.js
+++ b/Libraries/Renderer/shims/ReactFabric.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 const BatchedBridge = require('BatchedBridge');
diff --git a/Libraries/Renderer/shims/ReactNative.js b/Libraries/Renderer/shims/ReactNative.js
index 43c5002e05f5..fd7d3e3dbe25 100644
--- a/Libraries/Renderer/shims/ReactNative.js
+++ b/Libraries/Renderer/shims/ReactNative.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 import type {ReactNativeType} from 'ReactNativeTypes';
diff --git a/Libraries/Renderer/shims/ReactNativeComponentTree.js b/Libraries/Renderer/shims/ReactNativeComponentTree.js
index 8e8ce6ae06c1..702b621a5e46 100644
--- a/Libraries/Renderer/shims/ReactNativeComponentTree.js
+++ b/Libraries/Renderer/shims/ReactNativeComponentTree.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index 1f0d1dce0b09..c38b0b44ebcf 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -8,7 +8,7 @@
  * @flow
  */
 
-import * as React from 'react';
+import React from 'react';
 
 export type MeasureOnSuccessCallback = (
   x: number,
diff --git a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
index c8ed940a8609..44a7f1827da6 100644
--- a/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
+++ b/Libraries/Renderer/shims/ReactNativeViewConfigRegistry.js
@@ -4,8 +4,10 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
+
 'use strict';
 
 import type {
diff --git a/Libraries/Renderer/shims/ReactPerf.js b/Libraries/Renderer/shims/ReactPerf.js
deleted file mode 100644
index e94c87501c7d..000000000000
--- a/Libraries/Renderer/shims/ReactPerf.js
+++ /dev/null
@@ -1,15 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- */
-
-'use strict';
-
-const {
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-} = require('ReactNative');
-
-module.exports = __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactPerf;
diff --git a/Libraries/Renderer/shims/ReactTypes.js b/Libraries/Renderer/shims/ReactTypes.js
index 747a6c07b6f3..ac4eed362d0a 100644
--- a/Libraries/Renderer/shims/ReactTypes.js
+++ b/Libraries/Renderer/shims/ReactTypes.js
@@ -84,10 +84,13 @@ export type ReactContext<T> = {
   _defaultValue: T,
 
   _currentValue: T,
+  _currentValue2: T,
   _changedBits: number,
+  _changedBits2: number,
 
   // DEV only
   _currentRenderer?: Object | null,
+  _currentRenderer2?: Object | null,
 };
 
 export type ReactPortal = {
diff --git a/Libraries/Renderer/shims/createReactNativeComponentClass.js b/Libraries/Renderer/shims/createReactNativeComponentClass.js
index cacaedab88f2..4ea7d2818378 100644
--- a/Libraries/Renderer/shims/createReactNativeComponentClass.js
+++ b/Libraries/Renderer/shims/createReactNativeComponentClass.js
@@ -4,6 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @format
  * @flow
  */
 
diff --git a/package.json b/package.json
index 1229456241e8..ebae261767a7 100644
--- a/package.json
+++ b/package.json
@@ -160,7 +160,7 @@
     "errorhandler": "^1.5.0",
     "escape-string-regexp": "^1.0.5",
     "event-target-shim": "^1.0.5",
-    "fbjs": "^0.8.14",
+    "fbjs": "0.8.16",
     "fbjs-scripts": "^0.8.1",
     "fs-extra": "^1.0.0",
     "glob": "^7.1.1",

From 4a2c560768abb2d8407900fdb2fbe4971ae00a1c Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Tue, 15 May 2018 13:38:30 -0700
Subject: [PATCH 0589/1109] add missing jest mock in StatusBarManager

Summary:
fix issue https://github.com/facebook/react-native/issues/11701.

Pass current ci

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

 [GENERAL] [BUGFIX] [JEST] - add missing jest mock in StatusBarManager

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/19017

Differential Revision: D8014888

Pulled By: hramos

fbshipit-source-id: 1be29f9643cf0faa53ad64f79e11d48b654a97b3
---
 jest/setup.js | 1 +
 1 file changed, 1 insertion(+)

diff --git a/jest/setup.js b/jest/setup.js
index 1cb1eddfa9cd..570c37911175 100644
--- a/jest/setup.js
+++ b/jest/setup.js
@@ -234,6 +234,7 @@ const mockNativeModules = {
     scriptURL: null,
   },
   StatusBarManager: {
+    HEIGHT: 42,
     setColor: jest.fn(),
     setStyle: jest.fn(),
     setHidden: jest.fn(),

From 6c58035ae62bd6546772577b5918dd9c9059ec27 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Tue, 15 May 2018 14:28:30 -0700
Subject: [PATCH 0590/1109] Reuse and clean up JSC class ref bindings

Reviewed By: fkgozali

Differential Revision: D7893634

fbshipit-source-id: de11cb93f9f7e7c935af2da4616671043438363b
---
 .../com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
index 83023f488aa7..27aac53bbb81 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
@@ -33,10 +33,15 @@ typedef struct FabricJSCUIManager {
     : wrapperObjectClassRef(classRef)
     , useCustomJSC(customJSC) {
     fabricUiManager = make_global(module);
+    JSC_JSClassRetain(useCustomJSC, wrapperObjectClassRef);
   }
   global_ref<jobject> fabricUiManager;
   JSClassRef wrapperObjectClassRef;
   bool useCustomJSC;
+
+  ~FabricJSCUIManager() {
+    JSC_JSClassRelease(useCustomJSC, wrapperObjectClassRef);
+  }
 } FabricJSCUIManager;
 
 jobject makePlainGlobalRef(jobject object) {
@@ -283,6 +288,8 @@ void FabricJSCBinding::installFabric(jlong jsContextNativePointer,
   addFabricMethod(context, fabricModule, classRef, module, "appendChildToSet", appendChildToSet);
   addFabricMethod(context, fabricModule, classRef, module, "completeRoot", completeRoot);
 
+  JSC_JSClassRelease(useCustomJSC, classRef);
+
   JSObjectRef globalObject = JSC_JSContextGetGlobalObject(context);
   JSStringRef globalName = JSC_JSStringCreateWithUTF8CString(context, "nativeFabricUIManager");
   JSC_JSObjectSetProperty(context, globalObject, globalName, module, kJSPropertyAttributeNone, NULL);

From 2f4ca831bfd936be9ae71a8a5700003abb65a0f5 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 15 May 2018 16:35:11 -0700
Subject: [PATCH 0591/1109] React sync for revisions bde4b16...de84d5c

Reviewed By: bvaughn

Differential Revision: D8018924

fbshipit-source-id: 1092ad70ebe95aee70ec3ea9a8edfb6ac46a66c4
---
 Libraries/Renderer/REVISION                   |   2 +-
 Libraries/Renderer/oss/ReactFabric-dev.js     | 331 +++++-----------
 Libraries/Renderer/oss/ReactFabric-prod.js    | 354 +++++++-----------
 .../Renderer/oss/ReactNativeRenderer-dev.js   | 317 +++++-----------
 .../Renderer/oss/ReactNativeRenderer-prod.js  | 294 ++++++---------
 5 files changed, 442 insertions(+), 856 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index 752ac5912cc5..617cce49d160 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-bde4b1659fd4aea796482f24d40c2e834fca635f
\ No newline at end of file
+de84d5c1079b12455058ee177fb3ff97cc0fb8d0
\ No newline at end of file
diff --git a/Libraries/Renderer/oss/ReactFabric-dev.js b/Libraries/Renderer/oss/ReactFabric-dev.js
index d4a4d86b2bd4..eb3f3e078b39 100644
--- a/Libraries/Renderer/oss/ReactFabric-dev.js
+++ b/Libraries/Renderer/oss/ReactFabric-dev.js
@@ -523,21 +523,6 @@ var injection$1 = {
   }
 };
 
-function isEndish(topLevelType) {
-  return (
-    topLevelType === "topMouseUp" ||
-    topLevelType === "topTouchEnd" ||
-    topLevelType === "topTouchCancel"
-  );
-}
-
-function isMoveish(topLevelType) {
-  return topLevelType === "topMouseMove" || topLevelType === "topTouchMove";
-}
-function isStartish(topLevelType) {
-  return topLevelType === "topMouseDown" || topLevelType === "topTouchStart";
-}
-
 var validateEventDispatches = void 0;
 {
   validateEventDispatches = function(event) {
@@ -807,9 +792,7 @@ var HostRoot = 3; // Root of a host tree. Could be nested inside another node.
 var HostPortal = 4; // A subtree. Could be an entry point to a different renderer.
 var HostComponent = 5;
 var HostText = 6;
-var CallComponent = 7;
-var CallHandlerPhase = 8;
-var ReturnComponent = 9;
+
 var Fragment = 10;
 var Mode = 11;
 var ContextConsumer = 12;
@@ -1386,6 +1369,29 @@ var ResponderSyntheticEvent = SyntheticEvent$1.extend({
   }
 });
 
+var TOP_TOUCH_START = "topTouchStart";
+var TOP_TOUCH_MOVE = "topTouchMove";
+var TOP_TOUCH_END = "topTouchEnd";
+var TOP_TOUCH_CANCEL = "topTouchCancel";
+var TOP_SCROLL = "topScroll";
+var TOP_SELECTION_CHANGE = "topSelectionChange";
+
+function isStartish(topLevelType) {
+  return topLevelType === TOP_TOUCH_START;
+}
+
+function isMoveish(topLevelType) {
+  return topLevelType === TOP_TOUCH_MOVE;
+}
+
+function isEndish(topLevelType) {
+  return topLevelType === TOP_TOUCH_END || topLevelType === TOP_TOUCH_CANCEL;
+}
+
+var startDependencies = [TOP_TOUCH_START];
+var moveDependencies = [TOP_TOUCH_MOVE];
+var endDependencies = [TOP_TOUCH_CANCEL, TOP_TOUCH_END];
+
 /**
  * Tracks the position and time of each active touch by `touch.identifier`. We
  * should typically only see IDs in the range of 1-20 because IDs get recycled
@@ -1608,11 +1614,6 @@ var responderInst = null;
  */
 var trackedTouchCount = 0;
 
-/**
- * Last reported number of active touches.
- */
-var previousActiveTouches = 0;
-
 var changeResponder = function(nextResponderInst, blockHostResponder) {
   var oldResponderInst = responderInst;
   responderInst = nextResponderInst;
@@ -1634,7 +1635,8 @@ var eventTypes$1 = {
     phasedRegistrationNames: {
       bubbled: "onStartShouldSetResponder",
       captured: "onStartShouldSetResponderCapture"
-    }
+    },
+    dependencies: startDependencies
   },
 
   /**
@@ -1650,7 +1652,8 @@ var eventTypes$1 = {
     phasedRegistrationNames: {
       bubbled: "onScrollShouldSetResponder",
       captured: "onScrollShouldSetResponderCapture"
-    }
+    },
+    dependencies: [TOP_SCROLL]
   },
 
   /**
@@ -1664,7 +1667,8 @@ var eventTypes$1 = {
     phasedRegistrationNames: {
       bubbled: "onSelectionChangeShouldSetResponder",
       captured: "onSelectionChangeShouldSetResponderCapture"
-    }
+    },
+    dependencies: [TOP_SELECTION_CHANGE]
   },
 
   /**
@@ -1675,22 +1679,45 @@ var eventTypes$1 = {
     phasedRegistrationNames: {
       bubbled: "onMoveShouldSetResponder",
       captured: "onMoveShouldSetResponderCapture"
-    }
+    },
+    dependencies: moveDependencies
   },
 
   /**
    * Direct responder events dispatched directly to responder. Do not bubble.
    */
-  responderStart: { registrationName: "onResponderStart" },
-  responderMove: { registrationName: "onResponderMove" },
-  responderEnd: { registrationName: "onResponderEnd" },
-  responderRelease: { registrationName: "onResponderRelease" },
+  responderStart: {
+    registrationName: "onResponderStart",
+    dependencies: startDependencies
+  },
+  responderMove: {
+    registrationName: "onResponderMove",
+    dependencies: moveDependencies
+  },
+  responderEnd: {
+    registrationName: "onResponderEnd",
+    dependencies: endDependencies
+  },
+  responderRelease: {
+    registrationName: "onResponderRelease",
+    dependencies: endDependencies
+  },
   responderTerminationRequest: {
-    registrationName: "onResponderTerminationRequest"
+    registrationName: "onResponderTerminationRequest",
+    dependencies: []
+  },
+  responderGrant: {
+    registrationName: "onResponderGrant",
+    dependencies: []
+  },
+  responderReject: {
+    registrationName: "onResponderReject",
+    dependencies: []
   },
-  responderGrant: { registrationName: "onResponderGrant" },
-  responderReject: { registrationName: "onResponderReject" },
-  responderTerminate: { registrationName: "onResponderTerminate" }
+  responderTerminate: {
+    registrationName: "onResponderTerminate",
+    dependencies: []
+  }
 };
 
 /**
@@ -1893,7 +1920,7 @@ function setResponderAndExtractTransfer(
     ? eventTypes$1.startShouldSetResponder
     : isMoveish(topLevelType)
       ? eventTypes$1.moveShouldSetResponder
-      : topLevelType === "topSelectionChange"
+      : topLevelType === TOP_SELECTION_CHANGE
         ? eventTypes$1.selectionChangeShouldSetResponder
         : eventTypes$1.scrollShouldSetResponder;
 
@@ -1998,8 +2025,8 @@ function canTriggerTransfer(topLevelType, topLevelInst, nativeEvent) {
     // responderIgnoreScroll: We are trying to migrate away from specifically
     // tracking native scroll events here and responderIgnoreScroll indicates we
     // will send topTouchCancel to handle canceling touch events instead
-    ((topLevelType === "topScroll" && !nativeEvent.responderIgnoreScroll) ||
-      (trackedTouchCount > 0 && topLevelType === "topSelectionChange") ||
+    ((topLevelType === TOP_SCROLL && !nativeEvent.responderIgnoreScroll) ||
+      (trackedTouchCount > 0 && topLevelType === TOP_SELECTION_CHANGE) ||
       isStartish(topLevelType) ||
       isMoveish(topLevelType))
   );
@@ -2105,7 +2132,7 @@ var ResponderEventPlugin = {
     }
 
     var isResponderTerminate =
-      responderInst && topLevelType === "topTouchCancel";
+      responderInst && topLevelType === TOP_TOUCH_CANCEL;
     var isResponderRelease =
       responderInst &&
       !isResponderTerminate &&
@@ -2127,23 +2154,10 @@ var ResponderEventPlugin = {
       changeResponder(null);
     }
 
-    var numberActiveTouches =
-      ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
-    if (
-      ResponderEventPlugin.GlobalInteractionHandler &&
-      numberActiveTouches !== previousActiveTouches
-    ) {
-      ResponderEventPlugin.GlobalInteractionHandler.onChange(
-        numberActiveTouches
-      );
-    }
-    previousActiveTouches = numberActiveTouches;
-
     return extracted;
   },
 
   GlobalResponderHandler: null,
-  GlobalInteractionHandler: null,
 
   injection: {
     /**
@@ -2153,14 +2167,6 @@ var ResponderEventPlugin = {
      */
     injectGlobalResponderHandler: function(GlobalResponderHandler) {
       ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
-    },
-
-    /**
-     * @param {{onChange: (numberActiveTouches) => void} GlobalInteractionHandler
-     * Object that handles any change in the number of active touches.
-     */
-    injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
-      ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
     }
   }
 };
@@ -2320,8 +2326,6 @@ injection.injectEventPluginsByName({
 var hasSymbol = typeof Symbol === "function" && Symbol.for;
 
 var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 0xeac9;
 var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 0xeaca;
 var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
@@ -3335,8 +3339,6 @@ function getComponentName(fiber) {
   switch (type) {
     case REACT_ASYNC_MODE_TYPE:
       return "AsyncMode";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
     case REACT_CONTEXT_TYPE:
       return "Context.Consumer";
     case REACT_FRAGMENT_TYPE:
@@ -3347,8 +3349,6 @@ function getComponentName(fiber) {
       return "Profiler(" + fiber.pendingProps.id + ")";
     case REACT_PROVIDER_TYPE:
       return "Context.Provider";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
     case REACT_STRICT_MODE_TYPE:
       return "StrictMode";
   }
@@ -3908,12 +3908,6 @@ function createFiberFromElement(element, mode, expirationTime) {
         break;
       case REACT_PROFILER_TYPE:
         return createFiberFromProfiler(pendingProps, mode, expirationTime, key);
-      case REACT_CALL_TYPE:
-        fiberTag = CallComponent;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = ReturnComponent;
-        break;
       case REACT_TIMEOUT_TYPE:
         fiberTag = TimeoutComponent;
         // Suspense does not require async, but its children should be strict
@@ -4879,8 +4873,6 @@ var shouldIgnoreFiber = function(fiber) {
     case HostComponent:
     case HostText:
     case HostPortal:
-    case CallComponent:
-    case ReturnComponent:
     case Fragment:
     case ContextProvider:
     case ContextConsumer:
@@ -8716,44 +8708,6 @@ var ReactFiberBeginWork = function(
     }
   }
 
-  function updateCallComponent(current, workInProgress, renderExpirationTime) {
-    var nextProps = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextProps) {
-      nextProps = workInProgress.memoizedProps;
-      // TODO: When bailing out, we might need to return the stateNode instead
-      // of the child. To check it for work.
-      // return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var nextChildren = nextProps.children;
-
-    // The following is a fork of reconcileChildrenAtExpirationTime but using
-    // stateNode to store the child.
-    if (current === null) {
-      workInProgress.stateNode = mountChildFibers(
-        workInProgress,
-        workInProgress.stateNode,
-        nextChildren,
-        renderExpirationTime
-      );
-    } else {
-      workInProgress.stateNode = reconcileChildFibers(
-        workInProgress,
-        current.stateNode,
-        nextChildren,
-        renderExpirationTime
-      );
-    }
-
-    memoizeProps(workInProgress, nextProps);
-    // This doesn't take arbitrary time so we could synchronously just begin
-    // eagerly do the work of workInProgress.child as an optimization.
-    return workInProgress.stateNode;
-  }
-
   function updateTimeoutComponent(
     current,
     workInProgress,
@@ -9230,20 +9184,6 @@ var ReactFiberBeginWork = function(
         );
       case HostText:
         return updateHostText(current, workInProgress);
-      case CallHandlerPhase:
-        // This is a restart. Reset the tag to the initial phase.
-        workInProgress.tag = CallComponent;
-      // Intentionally fall through since this is now the same.
-      case CallComponent:
-        return updateCallComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ReturnComponent:
-        // A return component is just a placeholder, we can just run through the
-        // next one immediately.
-        return null;
       case TimeoutComponent:
         return updateTimeoutComponent(
           current,
@@ -9330,75 +9270,6 @@ var ReactFiberCompleteWork = function(
     workInProgress.effectTag |= Ref;
   }
 
-  function appendAllReturns(returns, workInProgress) {
-    var node = workInProgress.stateNode;
-    if (node) {
-      node.return = workInProgress;
-    }
-    while (node !== null) {
-      if (
-        node.tag === HostComponent ||
-        node.tag === HostText ||
-        node.tag === HostPortal
-      ) {
-        invariant(false, "A call cannot have host component children.");
-      } else if (node.tag === ReturnComponent) {
-        returns.push(node.pendingProps.value);
-      } else if (node.child !== null) {
-        node.child.return = node;
-        node = node.child;
-        continue;
-      }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === workInProgress) {
-          return;
-        }
-        node = node.return;
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
-    }
-  }
-
-  function moveCallToHandlerPhase(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var props = workInProgress.memoizedProps;
-    invariant(
-      props,
-      "Should be resolved by now. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-
-    // First step of the call has completed. Now we need to do the second.
-    // TODO: It would be nice to have a multi stage call represented by a
-    // single component, or at least tail call optimize nested ones. Currently
-    // that requires additional fields that we don't want to add to the fiber.
-    // So this requires nested handlers.
-    // Note: This doesn't mutate the alternate node. I don't think it needs to
-    // since this stage is reset for every pass.
-    workInProgress.tag = CallHandlerPhase;
-
-    // Build up the returns.
-    // TODO: Compare this to a generator or opaque helpers like Children.
-    var returns = [];
-    appendAllReturns(returns, workInProgress);
-    var fn = props.handler;
-    var childProps = props.props;
-    var nextChildren = fn(childProps, returns);
-
-    var currentFirstChild = current !== null ? current.child : null;
-    workInProgress.child = reconcileChildFibers(
-      workInProgress,
-      currentFirstChild,
-      nextChildren,
-      renderExpirationTime
-    );
-    return workInProgress.child;
-  }
-
   function appendAllChildren(parent, workInProgress) {
     // We only have the top Fiber that was created but we need recurse down its
     // children to find all the terminal nodes.
@@ -9792,19 +9663,6 @@ var ReactFiberCompleteWork = function(
         }
         return null;
       }
-      case CallComponent:
-        return moveCallToHandlerPhase(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case CallHandlerPhase:
-        // Reset the tag to now be a first phase call.
-        workInProgress.tag = CallComponent;
-        return null;
-      case ReturnComponent:
-        // Does nothing.
-        return null;
       case ForwardRef:
         return null;
       case TimeoutComponent:
@@ -10285,10 +10143,6 @@ var ReactFiberCommitWork = function(
         safelyDetachRef(current);
         return;
       }
-      case CallComponent: {
-        commitNestedUnmounts(current.stateNode);
-        return;
-      }
       case HostPortal: {
         // TODO: this is recursive.
         // We are also not using this parent because
@@ -10428,7 +10282,7 @@ var ReactFiberCommitWork = function(
     commitUpdate = mutation.commitUpdate,
     resetTextContent = mutation.resetTextContent,
     commitTextUpdate = mutation.commitTextUpdate,
-    appendChild = mutation.appendChild,
+    appendChild$$1 = mutation.appendChild,
     appendChildToContainer = mutation.appendChildToContainer,
     insertBefore = mutation.insertBefore,
     insertInContainerBefore = mutation.insertInContainerBefore,
@@ -10547,7 +10401,7 @@ var ReactFiberCommitWork = function(
           if (isContainer) {
             appendChildToContainer(parent, node.stateNode);
           } else {
-            appendChild(parent, node.stateNode);
+            appendChild$$1(parent, node.stateNode);
           }
         }
       } else if (node.tag === HostPortal) {
@@ -13027,12 +12881,17 @@ var ReactFiberScheduler = function(config) {
 
     var next = void 0;
     if (enableProfilerTimer) {
-      startBaseRenderTimer();
+      if (workInProgress.mode & ProfileMode) {
+        startBaseRenderTimer();
+      }
+
       next = beginWork(current, workInProgress, nextRenderExpirationTime);
 
-      // Update "base" time if the render wasn't bailed out on.
-      recordElapsedBaseRenderTimeIfRunning(workInProgress);
-      stopBaseRenderTimerIfRunning();
+      if (workInProgress.mode & ProfileMode) {
+        // Update "base" time if the render wasn't bailed out on.
+        recordElapsedBaseRenderTimeIfRunning(workInProgress);
+        stopBaseRenderTimerIfRunning();
+      }
     } else {
       next = beginWork(current, workInProgress, nextRenderExpirationTime);
     }
@@ -13822,13 +13681,13 @@ var ReactFiberScheduler = function(config) {
       var finishedWork = root.finishedWork;
       if (finishedWork !== null) {
         // This root is already complete. We can commit it.
-        completeRoot(root, finishedWork, expirationTime);
+        completeRoot$$1(root, finishedWork, expirationTime);
       } else {
         root.finishedWork = null;
         finishedWork = renderRoot(root, expirationTime, false);
         if (finishedWork !== null) {
           // We've completed the root. Commit it.
-          completeRoot(root, finishedWork, expirationTime);
+          completeRoot$$1(root, finishedWork, expirationTime);
         }
       }
     } else {
@@ -13836,7 +13695,7 @@ var ReactFiberScheduler = function(config) {
       var _finishedWork = root.finishedWork;
       if (_finishedWork !== null) {
         // This root is already complete. We can commit it.
-        completeRoot(root, _finishedWork, expirationTime);
+        completeRoot$$1(root, _finishedWork, expirationTime);
       } else {
         root.finishedWork = null;
         _finishedWork = renderRoot(root, expirationTime, true);
@@ -13845,7 +13704,7 @@ var ReactFiberScheduler = function(config) {
           // before committing.
           if (!shouldYield()) {
             // Still time left. Commit the root.
-            completeRoot(root, _finishedWork, expirationTime);
+            completeRoot$$1(root, _finishedWork, expirationTime);
           } else {
             // There's no time left. Mark this root as complete. We'll come
             // back and commit it later.
@@ -13864,7 +13723,7 @@ var ReactFiberScheduler = function(config) {
     isRendering = false;
   }
 
-  function completeRoot(root, finishedWork, expirationTime) {
+  function completeRoot$$1(root, finishedWork, expirationTime) {
     // Check if there's a batch that matches this expiration time.
     var firstBatch = root.firstBatch;
     if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
@@ -14434,7 +14293,7 @@ var ReactFabricHostComponent = (function() {
   return ReactFabricHostComponent;
 })();
 
-var ReacFabricHostConfig = {
+var ReactFabricHostConfig = {
   appendInitialChild: function(parentInstance, child) {
     FabricUIManager.appendChild(parentInstance.node, child.node);
   },
@@ -14470,7 +14329,7 @@ var ReacFabricHostConfig = {
       viewConfig.uiViewClassName, // viewName
       rootContainerInstance, // rootTag
       updatePayload, // props
-      internalInstanceHandle
+      internalInstanceHandle // internalInstanceHandle
     );
 
     var component = new ReactFabricHostComponent(tag, viewConfig, props);
@@ -14499,7 +14358,7 @@ var ReacFabricHostConfig = {
       "RCTRawText", // viewName
       rootContainerInstance, // rootTag
       { text: text }, // props
-      internalInstanceHandle
+      internalInstanceHandle // instance handle
     );
 
     return {
@@ -14593,18 +14452,26 @@ var ReacFabricHostConfig = {
       var clone = void 0;
       if (keepChildren) {
         if (updatePayload !== null) {
-          clone = FabricUIManager.cloneNodeWithNewProps(node, updatePayload);
+          clone = FabricUIManager.cloneNodeWithNewProps(
+            node,
+            updatePayload,
+            internalInstanceHandle
+          );
         } else {
-          clone = FabricUIManager.cloneNode(node);
+          clone = FabricUIManager.cloneNode(node, internalInstanceHandle);
         }
       } else {
         if (updatePayload !== null) {
           clone = FabricUIManager.cloneNodeWithNewChildrenAndProps(
             node,
-            updatePayload
+            updatePayload,
+            internalInstanceHandle
           );
         } else {
-          clone = FabricUIManager.cloneNodeWithNewChildren(node);
+          clone = FabricUIManager.cloneNodeWithNewChildren(
+            node,
+            internalInstanceHandle
+          );
         }
       }
       return {
@@ -14625,7 +14492,7 @@ var ReacFabricHostConfig = {
   }
 };
 
-var ReactFabricRenderer = reactReconciler(ReacFabricHostConfig);
+var ReactFabricRenderer = reactReconciler(ReactFabricHostConfig);
 
 // Module provided by RN:
 var getInspectorDataForViewTag = void 0;
@@ -14816,7 +14683,7 @@ var ReactFabric = {
     // Used as a mixin in many createClass-based components
     NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
     // Used by react-native-github/Libraries/ components
-    ReactNativeComponentTree: ReactNativeComponentTree
+    ReactNativeComponentTree: ReactNativeComponentTree // ScrollResponder
   }
 };
 
diff --git a/Libraries/Renderer/oss/ReactFabric-prod.js b/Libraries/Renderer/oss/ReactFabric-prod.js
index dd7e75d707ef..c4ca5aba4beb 100644
--- a/Libraries/Renderer/oss/ReactFabric-prod.js
+++ b/Libraries/Renderer/oss/ReactFabric-prod.js
@@ -100,19 +100,6 @@ var plugins = [],
   getFiberCurrentPropsFromNode = null,
   getInstanceFromNode = null,
   getNodeFromInstance = null;
-function isEndish(topLevelType) {
-  return (
-    "topMouseUp" === topLevelType ||
-    "topTouchEnd" === topLevelType ||
-    "topTouchCancel" === topLevelType
-  );
-}
-function isMoveish(topLevelType) {
-  return "topMouseMove" === topLevelType || "topTouchMove" === topLevelType;
-}
-function isStartish(topLevelType) {
-  return "topMouseDown" === topLevelType || "topTouchStart" === topLevelType;
-}
 function executeDirectDispatch(event) {
   var dispatchListener = event._dispatchListeners,
     dispatchInstance = event._dispatchInstances;
@@ -382,10 +369,19 @@ function addEventPoolingTo(EventConstructor) {
   EventConstructor.release = releasePooledEvent;
 }
 var ResponderSyntheticEvent = SyntheticEvent.extend({
-    touchHistory: function() {
-      return null;
-    }
-  }),
+  touchHistory: function() {
+    return null;
+  }
+});
+function isStartish(topLevelType) {
+  return "topTouchStart" === topLevelType;
+}
+function isMoveish(topLevelType) {
+  return "topTouchMove" === topLevelType;
+}
+var startDependencies = ["topTouchStart"],
+  moveDependencies = ["topTouchMove"],
+  endDependencies = ["topTouchCancel", "topTouchEnd"],
   touchBank = [],
   touchHistory = {
     touchBank: touchBank,
@@ -491,19 +487,22 @@ var ResponderTouchHistoryStore = {
           (touchHistory.indexOfSingleActiveTouch =
             nativeEvent.touches[0].identifier);
     else if (
-      isEndish(topLevelType) &&
-      (nativeEvent.changedTouches.forEach(recordTouchEnd),
-      (touchHistory.numberActiveTouches = nativeEvent.touches.length),
-      1 === touchHistory.numberActiveTouches)
+      "topTouchEnd" === topLevelType ||
+      "topTouchCancel" === topLevelType
     )
-      for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
-        if (
-          ((nativeEvent = touchBank[topLevelType]),
-          null != nativeEvent && nativeEvent.touchActive)
-        ) {
-          touchHistory.indexOfSingleActiveTouch = topLevelType;
-          break;
-        }
+      if (
+        (nativeEvent.changedTouches.forEach(recordTouchEnd),
+        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+        1 === touchHistory.numberActiveTouches)
+      )
+        for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
+          if (
+            ((nativeEvent = touchBank[topLevelType]),
+            null != nativeEvent && nativeEvent.touchActive)
+          ) {
+            touchHistory.indexOfSingleActiveTouch = topLevelType;
+            break;
+          }
   },
   touchHistory: touchHistory
 };
@@ -519,8 +518,7 @@ function accumulate(current, next) {
       : Array.isArray(next) ? [current].concat(next) : [current, next];
 }
 var responderInst = null,
-  trackedTouchCount = 0,
-  previousActiveTouches = 0;
+  trackedTouchCount = 0;
 function changeResponder(nextResponderInst, blockHostResponder) {
   var oldResponderInst = responderInst;
   responderInst = nextResponderInst;
@@ -536,36 +534,59 @@ var eventTypes$1 = {
       phasedRegistrationNames: {
         bubbled: "onStartShouldSetResponder",
         captured: "onStartShouldSetResponderCapture"
-      }
+      },
+      dependencies: startDependencies
     },
     scrollShouldSetResponder: {
       phasedRegistrationNames: {
         bubbled: "onScrollShouldSetResponder",
         captured: "onScrollShouldSetResponderCapture"
-      }
+      },
+      dependencies: ["topScroll"]
     },
     selectionChangeShouldSetResponder: {
       phasedRegistrationNames: {
         bubbled: "onSelectionChangeShouldSetResponder",
         captured: "onSelectionChangeShouldSetResponderCapture"
-      }
+      },
+      dependencies: ["topSelectionChange"]
     },
     moveShouldSetResponder: {
       phasedRegistrationNames: {
         bubbled: "onMoveShouldSetResponder",
         captured: "onMoveShouldSetResponderCapture"
-      }
+      },
+      dependencies: moveDependencies
+    },
+    responderStart: {
+      registrationName: "onResponderStart",
+      dependencies: startDependencies
+    },
+    responderMove: {
+      registrationName: "onResponderMove",
+      dependencies: moveDependencies
+    },
+    responderEnd: {
+      registrationName: "onResponderEnd",
+      dependencies: endDependencies
+    },
+    responderRelease: {
+      registrationName: "onResponderRelease",
+      dependencies: endDependencies
     },
-    responderStart: { registrationName: "onResponderStart" },
-    responderMove: { registrationName: "onResponderMove" },
-    responderEnd: { registrationName: "onResponderEnd" },
-    responderRelease: { registrationName: "onResponderRelease" },
     responderTerminationRequest: {
-      registrationName: "onResponderTerminationRequest"
+      registrationName: "onResponderTerminationRequest",
+      dependencies: []
+    },
+    responderGrant: { registrationName: "onResponderGrant", dependencies: [] },
+    responderReject: {
+      registrationName: "onResponderReject",
+      dependencies: []
     },
-    responderGrant: { registrationName: "onResponderGrant" },
-    responderReject: { registrationName: "onResponderReject" },
-    responderTerminate: { registrationName: "onResponderTerminate" }
+    responderTerminate: {
+      registrationName: "onResponderTerminate",
+      dependencies: []
+    }
   },
   ResponderEventPlugin = {
     _getResponder: function() {
@@ -579,7 +600,10 @@ var eventTypes$1 = {
       nativeEventTarget
     ) {
       if (isStartish(topLevelType)) trackedTouchCount += 1;
-      else if (isEndish(topLevelType))
+      else if (
+        "topTouchEnd" === topLevelType ||
+        "topTouchCancel" === topLevelType
+      )
         if (0 <= trackedTouchCount) --trackedTouchCount;
         else
           return (
@@ -749,7 +773,9 @@ var eventTypes$1 = {
       } else JSCompiler_temp = null;
       JSCompiler_temp$jscomp$0 = responderInst && isStartish(topLevelType);
       targetInst = responderInst && isMoveish(topLevelType);
-      depthA = responderInst && isEndish(topLevelType);
+      depthA =
+        responderInst &&
+        ("topTouchEnd" === topLevelType || "topTouchCancel" === topLevelType);
       if (
         (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
           ? eventTypes$1.responderStart
@@ -777,7 +803,9 @@ var eventTypes$1 = {
         responderInst && "topTouchCancel" === topLevelType;
       if (
         (topLevelType =
-          responderInst && !JSCompiler_temp$jscomp$0 && isEndish(topLevelType))
+          responderInst &&
+          !JSCompiler_temp$jscomp$0 &&
+          ("topTouchEnd" === topLevelType || "topTouchCancel" === topLevelType))
       )
         a: {
           if ((topLevelType = nativeEvent.touches) && 0 !== topLevelType.length)
@@ -819,23 +847,12 @@ var eventTypes$1 = {
           forEachAccumulated(nativeEvent, accumulateDirectDispatchesSingle),
           (JSCompiler_temp = accumulate(JSCompiler_temp, nativeEvent)),
           changeResponder(null);
-      nativeEvent = ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
-      if (
-        ResponderEventPlugin.GlobalInteractionHandler &&
-        nativeEvent !== previousActiveTouches
-      )
-        ResponderEventPlugin.GlobalInteractionHandler.onChange(nativeEvent);
-      previousActiveTouches = nativeEvent;
       return JSCompiler_temp;
     },
     GlobalResponderHandler: null,
-    GlobalInteractionHandler: null,
     injection: {
       injectGlobalResponderHandler: function(GlobalResponderHandler) {
         ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
-      },
-      injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
-        ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
       }
     }
   },
@@ -922,8 +939,6 @@ injection.injectEventPluginsByName({
 });
 var hasSymbol = "function" === typeof Symbol && Symbol.for,
   REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 60105,
   REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
   REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
   REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
@@ -1213,8 +1228,6 @@ function getComponentName(fiber) {
   switch (type) {
     case REACT_ASYNC_MODE_TYPE:
       return "AsyncMode";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
     case REACT_CONTEXT_TYPE:
       return "Context.Consumer";
     case REACT_FRAGMENT_TYPE:
@@ -1225,8 +1238,6 @@ function getComponentName(fiber) {
       return "Profiler(" + fiber.pendingProps.id + ")";
     case REACT_PROVIDER_TYPE:
       return "Context.Provider";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
     case REACT_STRICT_MODE_TYPE:
       return "StrictMode";
   }
@@ -1444,12 +1455,6 @@ function createFiberFromElement(element, mode, expirationTime) {
           (type.stateNode = { duration: 0, startTime: 0 }),
           type
         );
-      case REACT_CALL_TYPE:
-        fiberTag = 7;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = 9;
-        break;
       case REACT_TIMEOUT_TYPE:
         fiberTag = 16;
         mode |= 2;
@@ -3377,34 +3382,6 @@ function ReactFiberBeginWork(
             (workInProgress.memoizedProps = workInProgress.pendingProps),
             null
           );
-        case 8:
-          workInProgress.tag = 7;
-        case 7:
-          return (
-            (props = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-              workInProgress.memoizedProps !== props ||
-              (props = workInProgress.memoizedProps),
-            (fn = props.children),
-            (workInProgress.stateNode =
-              null === current
-                ? mountChildFibers(
-                    workInProgress,
-                    workInProgress.stateNode,
-                    fn,
-                    renderExpirationTime
-                  )
-                : reconcileChildFibers(
-                    workInProgress,
-                    current.stateNode,
-                    fn,
-                    renderExpirationTime
-                  )),
-            (workInProgress.memoizedProps = props),
-            workInProgress.stateNode
-          );
-        case 9:
-          return null;
         case 16:
           return null;
         case 4:
@@ -3687,7 +3664,7 @@ function ReactFiberCompleteWork(
     };
   } else invariant(!1, "Noop reconciler is disabled.");
   return {
-    completeWork: function(current, workInProgress, renderExpirationTime) {
+    completeWork: function(current, workInProgress) {
       var newProps = workInProgress.pendingProps;
       switch (workInProgress.tag) {
         case 1:
@@ -3707,8 +3684,8 @@ function ReactFiberCompleteWork(
           return null;
         case 5:
           popHostContext(workInProgress);
-          renderExpirationTime = getRootHostContainer();
-          var type = workInProgress.type;
+          var rootContainerInstance = getRootHostContainer(),
+            type = workInProgress.type;
           if (null !== current && null != workInProgress.stateNode) {
             var oldProps = current.memoizedProps,
               instance = workInProgress.stateNode,
@@ -3718,7 +3695,7 @@ function ReactFiberCompleteWork(
               type,
               oldProps,
               newProps,
-              renderExpirationTime,
+              rootContainerInstance,
               currentHostContext
             );
             updateHostComponent(
@@ -3728,7 +3705,7 @@ function ReactFiberCompleteWork(
               type,
               oldProps,
               newProps,
-              renderExpirationTime,
+              rootContainerInstance,
               currentHostContext
             );
             current.ref !== workInProgress.ref &&
@@ -3746,13 +3723,13 @@ function ReactFiberCompleteWork(
             popHydrationState(workInProgress)
               ? prepareToHydrateHostInstance(
                   workInProgress,
-                  renderExpirationTime,
+                  rootContainerInstance,
                   current
                 ) && markUpdate(workInProgress)
               : ((oldProps = createInstance(
                   type,
                   newProps,
-                  renderExpirationTime,
+                  rootContainerInstance,
                   current,
                   workInProgress
                 )),
@@ -3761,7 +3738,7 @@ function ReactFiberCompleteWork(
                   oldProps,
                   type,
                   newProps,
-                  renderExpirationTime,
+                  rootContainerInstance,
                   current
                 ) && markUpdate(workInProgress),
                 (workInProgress.stateNode = oldProps));
@@ -3785,69 +3762,19 @@ function ReactFiberCompleteWork(
                 ),
                 null
               );
-            current = getRootHostContainer();
-            renderExpirationTime = getHostContext();
+            rootContainerInstance = getRootHostContainer();
+            type = getHostContext();
             popHydrationState(workInProgress)
               ? prepareToHydrateHostTextInstance(workInProgress) &&
                 markUpdate(workInProgress)
               : (workInProgress.stateNode = createTextInstance(
                   newProps,
-                  current,
-                  renderExpirationTime,
+                  rootContainerInstance,
+                  type,
                   workInProgress
                 ));
           }
           return null;
-        case 7:
-          newProps = workInProgress.memoizedProps;
-          invariant(
-            newProps,
-            "Should be resolved by now. This error is likely caused by a bug in React. Please file an issue."
-          );
-          workInProgress.tag = 8;
-          type = [];
-          a: {
-            if ((oldProps = workInProgress.stateNode))
-              oldProps.return = workInProgress;
-            for (; null !== oldProps; ) {
-              if (
-                5 === oldProps.tag ||
-                6 === oldProps.tag ||
-                4 === oldProps.tag
-              )
-                invariant(!1, "A call cannot have host component children.");
-              else if (9 === oldProps.tag)
-                type.push(oldProps.pendingProps.value);
-              else if (null !== oldProps.child) {
-                oldProps.child.return = oldProps;
-                oldProps = oldProps.child;
-                continue;
-              }
-              for (; null === oldProps.sibling; ) {
-                if (
-                  null === oldProps.return ||
-                  oldProps.return === workInProgress
-                )
-                  break a;
-                oldProps = oldProps.return;
-              }
-              oldProps.sibling.return = oldProps.return;
-              oldProps = oldProps.sibling;
-            }
-          }
-          oldProps = newProps.handler;
-          newProps = oldProps(newProps.props, type);
-          workInProgress.child = reconcileChildFibers(
-            workInProgress,
-            null !== current ? current.child : null,
-            newProps,
-            renderExpirationTime
-          );
-          return workInProgress.child;
-        case 8:
-          return (workInProgress.tag = 7), null;
-        case 9:
-          return null;
         case 14:
           return null;
         case 16:
@@ -4059,43 +3986,6 @@ function ReactFiberCommitWork(config, captureError) {
         ? current(null)
         : (current.current = null));
   }
-  function commitNestedUnmounts(root) {
-    for (var node = root; ; ) {
-      var current = node;
-      "function" === typeof onCommitUnmount && onCommitUnmount(current);
-      switch (current.tag) {
-        case 2:
-          safelyDetachRef(current);
-          var _instance6 = current.stateNode;
-          if ("function" === typeof _instance6.componentWillUnmount)
-            try {
-              (_instance6.props = current.memoizedProps),
-                (_instance6.state = current.memoizedState),
-                _instance6.componentWillUnmount();
-            } catch (unmountError) {
-              captureError(current, unmountError);
-            }
-          break;
-        case 5:
-          safelyDetachRef(current);
-          break;
-        case 7:
-          commitNestedUnmounts(current.stateNode);
-          break;
-        case 4:
-          persistence && emptyPortalContainer(current);
-      }
-      if (null === node.child || (mutation && 4 === node.tag)) {
-        if (node === root) break;
-        for (; null === node.sibling; ) {
-          if (null === node.return || node.return === root) return;
-          node = node.return;
-        }
-        node.sibling.return = node.return;
-        node = node.sibling;
-      } else (node.child.return = node), (node = node.child);
-    }
-  }
   var getPublicInstance = config.getPublicInstance,
     mutation = config.mutation,
     persistence = config.persistence,
@@ -4137,12 +4027,45 @@ function ReactFiberCommitWork(config, captureError) {
     return {
       commitResetTextContent: function() {},
       commitPlacement: function() {},
-      commitDeletion: function(current) {
-        commitNestedUnmounts(current);
-        current.return = null;
-        current.child = null;
-        current.alternate &&
-          ((current.alternate.child = null), (current.alternate.return = null));
+      commitDeletion: function(current$jscomp$0) {
+        a: for (var node = current$jscomp$0; ; ) {
+          var current = node;
+          "function" === typeof onCommitUnmount && onCommitUnmount(current);
+          switch (current.tag) {
+            case 2:
+              safelyDetachRef(current);
+              var _instance6 = current.stateNode;
+              if ("function" === typeof _instance6.componentWillUnmount)
+                try {
+                  (_instance6.props = current.memoizedProps),
+                    (_instance6.state = current.memoizedState),
+                    _instance6.componentWillUnmount();
+                } catch (unmountError) {
+                  captureError(current, unmountError);
+                }
+              break;
+            case 5:
+              safelyDetachRef(current);
+              break;
+            case 4:
+              persistence && emptyPortalContainer(current);
+          }
+          if (null === node.child || (mutation && 4 === node.tag)) {
+            if (node === current$jscomp$0) break;
+            for (; null === node.sibling; ) {
+              if (null === node.return || node.return === current$jscomp$0)
+                break a;
+              node = node.return;
+            }
+            node.sibling.return = node.return;
+            node = node.sibling;
+          } else (node.child.return = node), (node = node.child);
+        }
+        current$jscomp$0.return = null;
+        current$jscomp$0.child = null;
+        current$jscomp$0.alternate &&
+          ((current$jscomp$0.alternate.child = null),
+          (current$jscomp$0.alternate.return = null));
       },
       commitWork: function(current, finishedWork) {
         commitContainer(finishedWork);
@@ -5182,22 +5105,23 @@ function ReactFiberScheduler(config) {
     isAsync
       ? ((isAsync = root.finishedWork),
         null !== isAsync
-          ? completeRoot(root, isAsync, expirationTime)
+          ? completeRoot$$1(root, isAsync, expirationTime)
           : ((root.finishedWork = null),
             (isAsync = renderRoot(root, expirationTime, !0)),
             null !== isAsync &&
               (shouldYield()
                 ? (root.finishedWork = isAsync)
-                : completeRoot(root, isAsync, expirationTime))))
+                : completeRoot$$1(root, isAsync, expirationTime))))
       : ((isAsync = root.finishedWork),
         null !== isAsync
-          ? completeRoot(root, isAsync, expirationTime)
+          ? completeRoot$$1(root, isAsync, expirationTime)
           : ((root.finishedWork = null),
             (isAsync = renderRoot(root, expirationTime, !1)),
-            null !== isAsync && completeRoot(root, isAsync, expirationTime)));
+            null !== isAsync &&
+              completeRoot$$1(root, isAsync, expirationTime)));
     isRendering = !1;
   }
-  function completeRoot(root, finishedWork, expirationTime) {
+  function completeRoot$$1(root, finishedWork, expirationTime) {
     var firstBatch = root.firstBatch;
     if (
       null !== firstBatch &&
@@ -5909,14 +5833,22 @@ var nextReactTag = 2,
         return {
           node: keepChildren
             ? null !== updatePayload
-              ? FabricUIManager.cloneNodeWithNewProps(type, updatePayload)
-              : FabricUIManager.cloneNode(type)
+              ? FabricUIManager.cloneNodeWithNewProps(
+                  type,
+                  updatePayload,
+                  internalInstanceHandle
+                )
+              : FabricUIManager.cloneNode(type, internalInstanceHandle)
             : null !== updatePayload
               ? FabricUIManager.cloneNodeWithNewChildrenAndProps(
                   type,
-                  updatePayload
+                  updatePayload,
+                  internalInstanceHandle
                 )
-              : FabricUIManager.cloneNodeWithNewChildren(type),
+              : FabricUIManager.cloneNodeWithNewChildren(
+                  type,
+                  internalInstanceHandle
+                ),
           canonical: instance.canonical
         };
       },
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
index de1791245051..9b2b430c1466 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
@@ -523,21 +523,6 @@ var injection$1 = {
   }
 };
 
-function isEndish(topLevelType) {
-  return (
-    topLevelType === "topMouseUp" ||
-    topLevelType === "topTouchEnd" ||
-    topLevelType === "topTouchCancel"
-  );
-}
-
-function isMoveish(topLevelType) {
-  return topLevelType === "topMouseMove" || topLevelType === "topTouchMove";
-}
-function isStartish(topLevelType) {
-  return topLevelType === "topMouseDown" || topLevelType === "topTouchStart";
-}
-
 var validateEventDispatches = void 0;
 {
   validateEventDispatches = function(event) {
@@ -961,9 +946,7 @@ var HostRoot = 3; // Root of a host tree. Could be nested inside another node.
 var HostPortal = 4; // A subtree. Could be an entry point to a different renderer.
 var HostComponent = 5;
 var HostText = 6;
-var CallComponent = 7;
-var CallHandlerPhase = 8;
-var ReturnComponent = 9;
+
 var Fragment = 10;
 var Mode = 11;
 var ContextConsumer = 12;
@@ -1540,6 +1523,29 @@ var ResponderSyntheticEvent = SyntheticEvent$1.extend({
   }
 });
 
+var TOP_TOUCH_START = "topTouchStart";
+var TOP_TOUCH_MOVE = "topTouchMove";
+var TOP_TOUCH_END = "topTouchEnd";
+var TOP_TOUCH_CANCEL = "topTouchCancel";
+var TOP_SCROLL = "topScroll";
+var TOP_SELECTION_CHANGE = "topSelectionChange";
+
+function isStartish(topLevelType) {
+  return topLevelType === TOP_TOUCH_START;
+}
+
+function isMoveish(topLevelType) {
+  return topLevelType === TOP_TOUCH_MOVE;
+}
+
+function isEndish(topLevelType) {
+  return topLevelType === TOP_TOUCH_END || topLevelType === TOP_TOUCH_CANCEL;
+}
+
+var startDependencies = [TOP_TOUCH_START];
+var moveDependencies = [TOP_TOUCH_MOVE];
+var endDependencies = [TOP_TOUCH_CANCEL, TOP_TOUCH_END];
+
 /**
  * Tracks the position and time of each active touch by `touch.identifier`. We
  * should typically only see IDs in the range of 1-20 because IDs get recycled
@@ -1762,11 +1768,6 @@ var responderInst = null;
  */
 var trackedTouchCount = 0;
 
-/**
- * Last reported number of active touches.
- */
-var previousActiveTouches = 0;
-
 var changeResponder = function(nextResponderInst, blockHostResponder) {
   var oldResponderInst = responderInst;
   responderInst = nextResponderInst;
@@ -1788,7 +1789,8 @@ var eventTypes$1 = {
     phasedRegistrationNames: {
       bubbled: "onStartShouldSetResponder",
       captured: "onStartShouldSetResponderCapture"
-    }
+    },
+    dependencies: startDependencies
   },
 
   /**
@@ -1804,7 +1806,8 @@ var eventTypes$1 = {
     phasedRegistrationNames: {
       bubbled: "onScrollShouldSetResponder",
       captured: "onScrollShouldSetResponderCapture"
-    }
+    },
+    dependencies: [TOP_SCROLL]
   },
 
   /**
@@ -1818,7 +1821,8 @@ var eventTypes$1 = {
     phasedRegistrationNames: {
       bubbled: "onSelectionChangeShouldSetResponder",
       captured: "onSelectionChangeShouldSetResponderCapture"
-    }
+    },
+    dependencies: [TOP_SELECTION_CHANGE]
   },
 
   /**
@@ -1829,22 +1833,45 @@ var eventTypes$1 = {
     phasedRegistrationNames: {
       bubbled: "onMoveShouldSetResponder",
       captured: "onMoveShouldSetResponderCapture"
-    }
+    },
+    dependencies: moveDependencies
   },
 
   /**
    * Direct responder events dispatched directly to responder. Do not bubble.
    */
-  responderStart: { registrationName: "onResponderStart" },
-  responderMove: { registrationName: "onResponderMove" },
-  responderEnd: { registrationName: "onResponderEnd" },
-  responderRelease: { registrationName: "onResponderRelease" },
+  responderStart: {
+    registrationName: "onResponderStart",
+    dependencies: startDependencies
+  },
+  responderMove: {
+    registrationName: "onResponderMove",
+    dependencies: moveDependencies
+  },
+  responderEnd: {
+    registrationName: "onResponderEnd",
+    dependencies: endDependencies
+  },
+  responderRelease: {
+    registrationName: "onResponderRelease",
+    dependencies: endDependencies
+  },
   responderTerminationRequest: {
-    registrationName: "onResponderTerminationRequest"
+    registrationName: "onResponderTerminationRequest",
+    dependencies: []
   },
-  responderGrant: { registrationName: "onResponderGrant" },
-  responderReject: { registrationName: "onResponderReject" },
-  responderTerminate: { registrationName: "onResponderTerminate" }
+  responderGrant: {
+    registrationName: "onResponderGrant",
+    dependencies: []
+  },
+  responderReject: {
+    registrationName: "onResponderReject",
+    dependencies: []
+  },
+  responderTerminate: {
+    registrationName: "onResponderTerminate",
+    dependencies: []
+  }
 };
 
 /**
@@ -2047,7 +2074,7 @@ function setResponderAndExtractTransfer(
     ? eventTypes$1.startShouldSetResponder
     : isMoveish(topLevelType)
       ? eventTypes$1.moveShouldSetResponder
-      : topLevelType === "topSelectionChange"
+      : topLevelType === TOP_SELECTION_CHANGE
         ? eventTypes$1.selectionChangeShouldSetResponder
         : eventTypes$1.scrollShouldSetResponder;
 
@@ -2152,8 +2179,8 @@ function canTriggerTransfer(topLevelType, topLevelInst, nativeEvent) {
     // responderIgnoreScroll: We are trying to migrate away from specifically
     // tracking native scroll events here and responderIgnoreScroll indicates we
     // will send topTouchCancel to handle canceling touch events instead
-    ((topLevelType === "topScroll" && !nativeEvent.responderIgnoreScroll) ||
-      (trackedTouchCount > 0 && topLevelType === "topSelectionChange") ||
+    ((topLevelType === TOP_SCROLL && !nativeEvent.responderIgnoreScroll) ||
+      (trackedTouchCount > 0 && topLevelType === TOP_SELECTION_CHANGE) ||
       isStartish(topLevelType) ||
       isMoveish(topLevelType))
   );
@@ -2259,7 +2286,7 @@ var ResponderEventPlugin = {
     }
 
     var isResponderTerminate =
-      responderInst && topLevelType === "topTouchCancel";
+      responderInst && topLevelType === TOP_TOUCH_CANCEL;
     var isResponderRelease =
       responderInst &&
       !isResponderTerminate &&
@@ -2281,23 +2308,10 @@ var ResponderEventPlugin = {
       changeResponder(null);
     }
 
-    var numberActiveTouches =
-      ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
-    if (
-      ResponderEventPlugin.GlobalInteractionHandler &&
-      numberActiveTouches !== previousActiveTouches
-    ) {
-      ResponderEventPlugin.GlobalInteractionHandler.onChange(
-        numberActiveTouches
-      );
-    }
-    previousActiveTouches = numberActiveTouches;
-
     return extracted;
   },
 
   GlobalResponderHandler: null,
-  GlobalInteractionHandler: null,
 
   injection: {
     /**
@@ -2307,14 +2321,6 @@ var ResponderEventPlugin = {
      */
     injectGlobalResponderHandler: function(GlobalResponderHandler) {
       ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
-    },
-
-    /**
-     * @param {{onChange: (numberActiveTouches) => void} GlobalInteractionHandler
-     * Object that handles any change in the number of active touches.
-     */
-    injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
-      ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
     }
   }
 };
@@ -2752,8 +2758,6 @@ var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
 var hasSymbol = typeof Symbol === "function" && Symbol.for;
 
 var REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 0xeac7;
-var REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 0xeac8;
-var REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 0xeac9;
 var REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 0xeaca;
 var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
@@ -2796,8 +2800,6 @@ function getComponentName(fiber) {
   switch (type) {
     case REACT_ASYNC_MODE_TYPE:
       return "AsyncMode";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
     case REACT_CONTEXT_TYPE:
       return "Context.Consumer";
     case REACT_FRAGMENT_TYPE:
@@ -2808,8 +2810,6 @@ function getComponentName(fiber) {
       return "Profiler(" + fiber.pendingProps.id + ")";
     case REACT_PROVIDER_TYPE:
       return "Context.Provider";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
     case REACT_STRICT_MODE_TYPE:
       return "StrictMode";
   }
@@ -3120,7 +3120,7 @@ var enablePersistentReconciler = false;
 var enableUserTimingAPI = true;
 var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
 var warnAboutDeprecatedLifecycles = false;
-var enableProfilerTimer = false;
+var enableProfilerTimer = true;
 var fireGetDerivedStateFromPropsOnStateUpdates = true;
 
 // Only used in www builds.
@@ -3367,12 +3367,6 @@ function createFiberFromElement(element, mode, expirationTime) {
         break;
       case REACT_PROFILER_TYPE:
         return createFiberFromProfiler(pendingProps, mode, expirationTime, key);
-      case REACT_CALL_TYPE:
-        fiberTag = CallComponent;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = ReturnComponent;
-        break;
       case REACT_TIMEOUT_TYPE:
         fiberTag = TimeoutComponent;
         // Suspense does not require async, but its children should be strict
@@ -4338,8 +4332,6 @@ var shouldIgnoreFiber = function(fiber) {
     case HostComponent:
     case HostText:
     case HostPortal:
-    case CallComponent:
-    case ReturnComponent:
     case Fragment:
     case ContextProvider:
     case ContextConsumer:
@@ -8175,44 +8167,6 @@ var ReactFiberBeginWork = function(
     }
   }
 
-  function updateCallComponent(current, workInProgress, renderExpirationTime) {
-    var nextProps = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextProps) {
-      nextProps = workInProgress.memoizedProps;
-      // TODO: When bailing out, we might need to return the stateNode instead
-      // of the child. To check it for work.
-      // return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var nextChildren = nextProps.children;
-
-    // The following is a fork of reconcileChildrenAtExpirationTime but using
-    // stateNode to store the child.
-    if (current === null) {
-      workInProgress.stateNode = mountChildFibers(
-        workInProgress,
-        workInProgress.stateNode,
-        nextChildren,
-        renderExpirationTime
-      );
-    } else {
-      workInProgress.stateNode = reconcileChildFibers(
-        workInProgress,
-        current.stateNode,
-        nextChildren,
-        renderExpirationTime
-      );
-    }
-
-    memoizeProps(workInProgress, nextProps);
-    // This doesn't take arbitrary time so we could synchronously just begin
-    // eagerly do the work of workInProgress.child as an optimization.
-    return workInProgress.stateNode;
-  }
-
   function updateTimeoutComponent(
     current,
     workInProgress,
@@ -8689,20 +8643,6 @@ var ReactFiberBeginWork = function(
         );
       case HostText:
         return updateHostText(current, workInProgress);
-      case CallHandlerPhase:
-        // This is a restart. Reset the tag to the initial phase.
-        workInProgress.tag = CallComponent;
-      // Intentionally fall through since this is now the same.
-      case CallComponent:
-        return updateCallComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ReturnComponent:
-        // A return component is just a placeholder, we can just run through the
-        // next one immediately.
-        return null;
       case TimeoutComponent:
         return updateTimeoutComponent(
           current,
@@ -8789,75 +8729,6 @@ var ReactFiberCompleteWork = function(
     workInProgress.effectTag |= Ref;
   }
 
-  function appendAllReturns(returns, workInProgress) {
-    var node = workInProgress.stateNode;
-    if (node) {
-      node.return = workInProgress;
-    }
-    while (node !== null) {
-      if (
-        node.tag === HostComponent ||
-        node.tag === HostText ||
-        node.tag === HostPortal
-      ) {
-        invariant(false, "A call cannot have host component children.");
-      } else if (node.tag === ReturnComponent) {
-        returns.push(node.pendingProps.value);
-      } else if (node.child !== null) {
-        node.child.return = node;
-        node = node.child;
-        continue;
-      }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === workInProgress) {
-          return;
-        }
-        node = node.return;
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
-    }
-  }
-
-  function moveCallToHandlerPhase(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var props = workInProgress.memoizedProps;
-    invariant(
-      props,
-      "Should be resolved by now. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-
-    // First step of the call has completed. Now we need to do the second.
-    // TODO: It would be nice to have a multi stage call represented by a
-    // single component, or at least tail call optimize nested ones. Currently
-    // that requires additional fields that we don't want to add to the fiber.
-    // So this requires nested handlers.
-    // Note: This doesn't mutate the alternate node. I don't think it needs to
-    // since this stage is reset for every pass.
-    workInProgress.tag = CallHandlerPhase;
-
-    // Build up the returns.
-    // TODO: Compare this to a generator or opaque helpers like Children.
-    var returns = [];
-    appendAllReturns(returns, workInProgress);
-    var fn = props.handler;
-    var childProps = props.props;
-    var nextChildren = fn(childProps, returns);
-
-    var currentFirstChild = current !== null ? current.child : null;
-    workInProgress.child = reconcileChildFibers(
-      workInProgress,
-      currentFirstChild,
-      nextChildren,
-      renderExpirationTime
-    );
-    return workInProgress.child;
-  }
-
   function appendAllChildren(parent, workInProgress) {
     // We only have the top Fiber that was created but we need recurse down its
     // children to find all the terminal nodes.
@@ -9251,19 +9122,6 @@ var ReactFiberCompleteWork = function(
         }
         return null;
       }
-      case CallComponent:
-        return moveCallToHandlerPhase(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case CallHandlerPhase:
-        // Reset the tag to now be a first phase call.
-        workInProgress.tag = CallComponent;
-        return null;
-      case ReturnComponent:
-        // Does nothing.
-        return null;
       case ForwardRef:
         return null;
       case TimeoutComponent:
@@ -9744,10 +9602,6 @@ var ReactFiberCommitWork = function(
         safelyDetachRef(current);
         return;
       }
-      case CallComponent: {
-        commitNestedUnmounts(current.stateNode);
-        return;
-      }
       case HostPortal: {
         // TODO: this is recursive.
         // We are also not using this parent because
@@ -12486,12 +12340,17 @@ var ReactFiberScheduler = function(config) {
 
     var next = void 0;
     if (enableProfilerTimer) {
-      startBaseRenderTimer();
+      if (workInProgress.mode & ProfileMode) {
+        startBaseRenderTimer();
+      }
+
       next = beginWork(current, workInProgress, nextRenderExpirationTime);
 
-      // Update "base" time if the render wasn't bailed out on.
-      recordElapsedBaseRenderTimeIfRunning(workInProgress);
-      stopBaseRenderTimerIfRunning();
+      if (workInProgress.mode & ProfileMode) {
+        // Update "base" time if the render wasn't bailed out on.
+        recordElapsedBaseRenderTimeIfRunning(workInProgress);
+        stopBaseRenderTimerIfRunning();
+      }
     } else {
       next = beginWork(current, workInProgress, nextRenderExpirationTime);
     }
@@ -14476,7 +14335,7 @@ var ReactNativeHostConfig = {
       tag, // reactTag
       viewConfig.uiViewClassName, // viewName
       rootContainerInstance, // rootTag
-      updatePayload
+      updatePayload // props
     );
 
     var component = new ReactNativeFiberHostComponent(tag, viewConfig);
@@ -14505,7 +14364,7 @@ var ReactNativeHostConfig = {
       tag, // reactTag
       "RCTRawText", // viewName
       rootContainerInstance, // rootTag
-      { text: text }
+      { text: text } // props
     );
 
     precacheFiberNode(internalInstanceHandle, tag);
@@ -14533,7 +14392,7 @@ var ReactNativeHostConfig = {
 
     UIManager.setChildren(
       parentInstance._nativeTag, // containerTag
-      nativeTags
+      nativeTags // reactTags
     );
 
     return false;
@@ -14613,7 +14472,7 @@ var ReactNativeHostConfig = {
           [children.length - 1], // moveToIndices
           [], // addChildReactTags
           [], // addAtIndices
-          []
+          [] // removeAtIndices
         );
       } else {
         children.push(child);
@@ -14624,7 +14483,7 @@ var ReactNativeHostConfig = {
           [], // moveToIndices
           [childTag], // addChildReactTags
           [children.length - 1], // addAtIndices
-          []
+          [] // removeAtIndices
         );
       }
     },
@@ -14632,14 +14491,14 @@ var ReactNativeHostConfig = {
       var childTag = typeof child === "number" ? child : child._nativeTag;
       UIManager.setChildren(
         parentInstance, // containerTag
-        [childTag]
+        [childTag] // reactTags
       );
     },
     commitTextUpdate: function(textInstance, oldText, newText) {
       UIManager.updateView(
         textInstance, // reactTag
         "RCTRawText", // viewName
-        { text: newText }
+        { text: newText } // props
       );
     },
     commitMount: function(instance, type, newProps, internalInstanceHandle) {
@@ -14666,7 +14525,7 @@ var ReactNativeHostConfig = {
         UIManager.updateView(
           instance._nativeTag, // reactTag
           viewConfig.uiViewClassName, // viewName
-          updatePayload
+          updatePayload // props
         );
       }
     },
@@ -14686,7 +14545,7 @@ var ReactNativeHostConfig = {
           [beforeChildIndex], // moveToIndices
           [], // addChildReactTags
           [], // addAtIndices
-          []
+          [] // removeAtIndices
         );
       } else {
         var _beforeChildIndex = children.indexOf(beforeChild);
@@ -14700,7 +14559,7 @@ var ReactNativeHostConfig = {
           [], // moveToIndices
           [childTag], // addChildReactTags
           [_beforeChildIndex], // addAtIndices
-          []
+          [] // removeAtIndices
         );
       }
     },
@@ -14727,7 +14586,7 @@ var ReactNativeHostConfig = {
         [], // moveToIndices
         [], // addChildReactTags
         [], // addAtIndices
-        [index]
+        [index] // removeAtIndices
       );
     },
     removeChildFromContainer: function(parentInstance, child) {
@@ -14738,7 +14597,7 @@ var ReactNativeHostConfig = {
         [], // moveToIndices
         [], // addChildReactTags
         [], // addAtIndices
-        [0]
+        [0] // removeAtIndices
       );
     },
     resetTextContent: function(instance) {
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
index 45cc8fca1ac8..471d04181673 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
@@ -164,19 +164,6 @@ var plugins = [],
   getFiberCurrentPropsFromNode = null,
   getInstanceFromNode = null,
   getNodeFromInstance = null;
-function isEndish(topLevelType) {
-  return (
-    "topMouseUp" === topLevelType ||
-    "topTouchEnd" === topLevelType ||
-    "topTouchCancel" === topLevelType
-  );
-}
-function isMoveish(topLevelType) {
-  return "topMouseMove" === topLevelType || "topTouchMove" === topLevelType;
-}
-function isStartish(topLevelType) {
-  return "topMouseDown" === topLevelType || "topTouchStart" === topLevelType;
-}
 function executeDispatch(event, simulated, listener, inst) {
   simulated = event.type || "unknown-event";
   event.currentTarget = getNodeFromInstance(inst);
@@ -477,10 +464,19 @@ function addEventPoolingTo(EventConstructor) {
   EventConstructor.release = releasePooledEvent;
 }
 var ResponderSyntheticEvent = SyntheticEvent.extend({
-    touchHistory: function() {
-      return null;
-    }
-  }),
+  touchHistory: function() {
+    return null;
+  }
+});
+function isStartish(topLevelType) {
+  return "topTouchStart" === topLevelType;
+}
+function isMoveish(topLevelType) {
+  return "topTouchMove" === topLevelType;
+}
+var startDependencies = ["topTouchStart"],
+  moveDependencies = ["topTouchMove"],
+  endDependencies = ["topTouchCancel", "topTouchEnd"],
   touchBank = [],
   touchHistory = {
     touchBank: touchBank,
@@ -586,19 +582,22 @@ var ResponderTouchHistoryStore = {
           (touchHistory.indexOfSingleActiveTouch =
             nativeEvent.touches[0].identifier);
     else if (
-      isEndish(topLevelType) &&
-      (nativeEvent.changedTouches.forEach(recordTouchEnd),
-      (touchHistory.numberActiveTouches = nativeEvent.touches.length),
-      1 === touchHistory.numberActiveTouches)
+      "topTouchEnd" === topLevelType ||
+      "topTouchCancel" === topLevelType
     )
-      for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
-        if (
-          ((nativeEvent = touchBank[topLevelType]),
-          null != nativeEvent && nativeEvent.touchActive)
-        ) {
-          touchHistory.indexOfSingleActiveTouch = topLevelType;
-          break;
-        }
+      if (
+        (nativeEvent.changedTouches.forEach(recordTouchEnd),
+        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+        1 === touchHistory.numberActiveTouches)
+      )
+        for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
+          if (
+            ((nativeEvent = touchBank[topLevelType]),
+            null != nativeEvent && nativeEvent.touchActive)
+          ) {
+            touchHistory.indexOfSingleActiveTouch = topLevelType;
+            break;
+          }
   },
   touchHistory: touchHistory
 };
@@ -614,8 +613,7 @@ function accumulate(current, next) {
       : Array.isArray(next) ? [current].concat(next) : [current, next];
 }
 var responderInst = null,
-  trackedTouchCount = 0,
-  previousActiveTouches = 0;
+  trackedTouchCount = 0;
 function changeResponder(nextResponderInst, blockHostResponder) {
   var oldResponderInst = responderInst;
   responderInst = nextResponderInst;
@@ -631,36 +629,59 @@ var eventTypes$1 = {
       phasedRegistrationNames: {
         bubbled: "onStartShouldSetResponder",
         captured: "onStartShouldSetResponderCapture"
-      }
+      },
+      dependencies: startDependencies
     },
     scrollShouldSetResponder: {
       phasedRegistrationNames: {
         bubbled: "onScrollShouldSetResponder",
         captured: "onScrollShouldSetResponderCapture"
-      }
+      },
+      dependencies: ["topScroll"]
     },
     selectionChangeShouldSetResponder: {
       phasedRegistrationNames: {
         bubbled: "onSelectionChangeShouldSetResponder",
         captured: "onSelectionChangeShouldSetResponderCapture"
-      }
+      },
+      dependencies: ["topSelectionChange"]
     },
     moveShouldSetResponder: {
       phasedRegistrationNames: {
         bubbled: "onMoveShouldSetResponder",
         captured: "onMoveShouldSetResponderCapture"
-      }
+      },
+      dependencies: moveDependencies
+    },
+    responderStart: {
+      registrationName: "onResponderStart",
+      dependencies: startDependencies
+    },
+    responderMove: {
+      registrationName: "onResponderMove",
+      dependencies: moveDependencies
+    },
+    responderEnd: {
+      registrationName: "onResponderEnd",
+      dependencies: endDependencies
+    },
+    responderRelease: {
+      registrationName: "onResponderRelease",
+      dependencies: endDependencies
     },
-    responderStart: { registrationName: "onResponderStart" },
-    responderMove: { registrationName: "onResponderMove" },
-    responderEnd: { registrationName: "onResponderEnd" },
-    responderRelease: { registrationName: "onResponderRelease" },
     responderTerminationRequest: {
-      registrationName: "onResponderTerminationRequest"
+      registrationName: "onResponderTerminationRequest",
+      dependencies: []
+    },
+    responderGrant: { registrationName: "onResponderGrant", dependencies: [] },
+    responderReject: {
+      registrationName: "onResponderReject",
+      dependencies: []
     },
-    responderGrant: { registrationName: "onResponderGrant" },
-    responderReject: { registrationName: "onResponderReject" },
-    responderTerminate: { registrationName: "onResponderTerminate" }
+    responderTerminate: {
+      registrationName: "onResponderTerminate",
+      dependencies: []
+    }
   },
   ResponderEventPlugin = {
     _getResponder: function() {
@@ -674,7 +695,10 @@ var eventTypes$1 = {
       nativeEventTarget
     ) {
       if (isStartish(topLevelType)) trackedTouchCount += 1;
-      else if (isEndish(topLevelType))
+      else if (
+        "topTouchEnd" === topLevelType ||
+        "topTouchCancel" === topLevelType
+      )
         if (0 <= trackedTouchCount) --trackedTouchCount;
         else
           return (
@@ -844,7 +868,9 @@ var eventTypes$1 = {
       } else JSCompiler_temp = null;
       JSCompiler_temp$jscomp$0 = responderInst && isStartish(topLevelType);
       targetInst = responderInst && isMoveish(topLevelType);
-      depthA = responderInst && isEndish(topLevelType);
+      depthA =
+        responderInst &&
+        ("topTouchEnd" === topLevelType || "topTouchCancel" === topLevelType);
       if (
         (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
           ? eventTypes$1.responderStart
@@ -872,7 +898,9 @@ var eventTypes$1 = {
         responderInst && "topTouchCancel" === topLevelType;
       if (
         (topLevelType =
-          responderInst && !JSCompiler_temp$jscomp$0 && isEndish(topLevelType))
+          responderInst &&
+          !JSCompiler_temp$jscomp$0 &&
+          ("topTouchEnd" === topLevelType || "topTouchCancel" === topLevelType))
       )
         a: {
           if ((topLevelType = nativeEvent.touches) && 0 !== topLevelType.length)
@@ -914,23 +942,12 @@ var eventTypes$1 = {
           forEachAccumulated(nativeEvent, accumulateDirectDispatchesSingle),
           (JSCompiler_temp = accumulate(JSCompiler_temp, nativeEvent)),
           changeResponder(null);
-      nativeEvent = ResponderTouchHistoryStore.touchHistory.numberActiveTouches;
-      if (
-        ResponderEventPlugin.GlobalInteractionHandler &&
-        nativeEvent !== previousActiveTouches
-      )
-        ResponderEventPlugin.GlobalInteractionHandler.onChange(nativeEvent);
-      previousActiveTouches = nativeEvent;
       return JSCompiler_temp;
     },
     GlobalResponderHandler: null,
-    GlobalInteractionHandler: null,
     injection: {
       injectGlobalResponderHandler: function(GlobalResponderHandler) {
         ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
-      },
-      injectGlobalInteractionHandler: function(GlobalInteractionHandler) {
-        ResponderEventPlugin.GlobalInteractionHandler = GlobalInteractionHandler;
       }
     }
   },
@@ -1128,8 +1145,6 @@ var ReactCurrentOwner =
     React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner,
   hasSymbol = "function" === typeof Symbol && Symbol.for,
   REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
-  REACT_CALL_TYPE = hasSymbol ? Symbol.for("react.call") : 60104,
-  REACT_RETURN_TYPE = hasSymbol ? Symbol.for("react.return") : 60105,
   REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
   REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
   REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
@@ -1155,8 +1170,6 @@ function getComponentName(fiber) {
   switch (type) {
     case REACT_ASYNC_MODE_TYPE:
       return "AsyncMode";
-    case REACT_CALL_TYPE:
-      return "ReactCall";
     case REACT_CONTEXT_TYPE:
       return "Context.Consumer";
     case REACT_FRAGMENT_TYPE:
@@ -1167,8 +1180,6 @@ function getComponentName(fiber) {
       return "Profiler(" + fiber.pendingProps.id + ")";
     case REACT_PROVIDER_TYPE:
       return "Context.Provider";
-    case REACT_RETURN_TYPE:
-      return "ReactReturn";
     case REACT_STRICT_MODE_TYPE:
       return "StrictMode";
   }
@@ -1386,12 +1397,6 @@ function createFiberFromElement(element, mode, expirationTime) {
           (type.stateNode = { duration: 0, startTime: 0 }),
           type
         );
-      case REACT_CALL_TYPE:
-        fiberTag = 7;
-        break;
-      case REACT_RETURN_TYPE:
-        fiberTag = 9;
-        break;
       case REACT_TIMEOUT_TYPE:
         fiberTag = 16;
         mode |= 2;
@@ -3319,34 +3324,6 @@ function ReactFiberBeginWork(
             (workInProgress.memoizedProps = workInProgress.pendingProps),
             null
           );
-        case 8:
-          workInProgress.tag = 7;
-        case 7:
-          return (
-            (props = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-              workInProgress.memoizedProps !== props ||
-              (props = workInProgress.memoizedProps),
-            (fn = props.children),
-            (workInProgress.stateNode =
-              null === current
-                ? mountChildFibers(
-                    workInProgress,
-                    workInProgress.stateNode,
-                    fn,
-                    renderExpirationTime
-                  )
-                : reconcileChildFibers(
-                    workInProgress,
-                    current.stateNode,
-                    fn,
-                    renderExpirationTime
-                  )),
-            (workInProgress.memoizedProps = props),
-            workInProgress.stateNode
-          );
-        case 9:
-          return null;
         case 16:
           return null;
         case 4:
@@ -3541,7 +3518,7 @@ function ReactFiberCompleteWork(
       ? invariant(!1, "Persistent reconciler is disabled.")
       : invariant(!1, "Noop reconciler is disabled.");
   return {
-    completeWork: function(current, workInProgress, renderExpirationTime) {
+    completeWork: function(current, workInProgress) {
       var newProps = workInProgress.pendingProps;
       switch (workInProgress.tag) {
         case 1:
@@ -3561,8 +3538,8 @@ function ReactFiberCompleteWork(
           return null;
         case 5:
           popHostContext(workInProgress);
-          renderExpirationTime = getRootHostContainer();
-          var type = workInProgress.type;
+          var rootContainerInstance = getRootHostContainer(),
+            type = workInProgress.type;
           if (null !== current && null != workInProgress.stateNode) {
             var oldProps = current.memoizedProps,
               instance = workInProgress.stateNode,
@@ -3572,7 +3549,7 @@ function ReactFiberCompleteWork(
               type,
               oldProps,
               newProps,
-              renderExpirationTime,
+              rootContainerInstance,
               currentHostContext
             );
             updateHostComponent(
@@ -3582,7 +3559,7 @@ function ReactFiberCompleteWork(
               type,
               oldProps,
               newProps,
-              renderExpirationTime,
+              rootContainerInstance,
               currentHostContext
             );
             current.ref !== workInProgress.ref &&
@@ -3600,14 +3577,14 @@ function ReactFiberCompleteWork(
             if (popHydrationState(workInProgress))
               prepareToHydrateHostInstance(
                 workInProgress,
-                renderExpirationTime,
+                rootContainerInstance,
                 current
               ) && markUpdate(workInProgress);
             else {
               oldProps = createInstance(
                 type,
                 newProps,
-                renderExpirationTime,
+                rootContainerInstance,
                 current,
                 workInProgress
               );
@@ -3645,7 +3622,7 @@ function ReactFiberCompleteWork(
                 oldProps,
                 type,
                 newProps,
-                renderExpirationTime,
+                rootContainerInstance,
                 current
               ) && markUpdate(workInProgress);
               workInProgress.stateNode = oldProps;
@@ -3670,69 +3647,19 @@ function ReactFiberCompleteWork(
                 ),
                 null
               );
-            current = getRootHostContainer();
-            renderExpirationTime = getHostContext();
+            rootContainerInstance = getRootHostContainer();
+            type = getHostContext();
             popHydrationState(workInProgress)
               ? prepareToHydrateHostTextInstance(workInProgress) &&
                 markUpdate(workInProgress)
               : (workInProgress.stateNode = createTextInstance(
                   newProps,
-                  current,
-                  renderExpirationTime,
+                  rootContainerInstance,
+                  type,
                   workInProgress
                 ));
           }
           return null;
-        case 7:
-          newProps = workInProgress.memoizedProps;
-          invariant(
-            newProps,
-            "Should be resolved by now. This error is likely caused by a bug in React. Please file an issue."
-          );
-          workInProgress.tag = 8;
-          type = [];
-          a: {
-            if ((oldProps = workInProgress.stateNode))
-              oldProps.return = workInProgress;
-            for (; null !== oldProps; ) {
-              if (
-                5 === oldProps.tag ||
-                6 === oldProps.tag ||
-                4 === oldProps.tag
-              )
-                invariant(!1, "A call cannot have host component children.");
-              else if (9 === oldProps.tag)
-                type.push(oldProps.pendingProps.value);
-              else if (null !== oldProps.child) {
-                oldProps.child.return = oldProps;
-                oldProps = oldProps.child;
-                continue;
-              }
-              for (; null === oldProps.sibling; ) {
-                if (
-                  null === oldProps.return ||
-                  oldProps.return === workInProgress
-                )
-                  break a;
-                oldProps = oldProps.return;
-              }
-              oldProps.sibling.return = oldProps.return;
-              oldProps = oldProps.sibling;
-            }
-          }
-          oldProps = newProps.handler;
-          newProps = oldProps(newProps.props, type);
-          workInProgress.child = reconcileChildFibers(
-            workInProgress,
-            null !== current ? current.child : null,
-            newProps,
-            renderExpirationTime
-          );
-          return workInProgress.child;
-        case 8:
-          return (workInProgress.tag = 7), null;
-        case 9:
-          return null;
         case 14:
           return null;
         case 16:
@@ -3833,28 +3760,10 @@ function ReactFiberCommitWork(config, captureError) {
       case 5:
         safelyDetachRef(current);
         break;
-      case 7:
-        commitNestedUnmounts(current.stateNode);
-        break;
       case 4:
         mutation && unmountHostComponents(current);
     }
   }
-  function commitNestedUnmounts(root) {
-    for (var node = root; ; )
-      if (
-        (commitUnmount(node),
-        null === node.child || (mutation && 4 === node.tag))
-      ) {
-        if (node === root) break;
-        for (; null === node.sibling; ) {
-          if (null === node.return || node.return === root) return;
-          node = node.return;
-        }
-        node.sibling.return = node.return;
-        node = node.sibling;
-      } else (node.child.return = node), (node = node.child);
-  }
   function isHostParent(fiber) {
     return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
   }
@@ -3892,12 +3801,31 @@ function ReactFiberCommitWork(config, captureError) {
         }
         currentParentIsValid = !0;
       }
-      if (5 === node.tag || 6 === node.tag)
-        commitNestedUnmounts(node),
-          currentParentIsContainer
-            ? removeChildFromContainer(currentParent, node.stateNode)
-            : removeChild(currentParent, node.stateNode);
-      else if (
+      if (5 === node.tag || 6 === node.tag) {
+        a: for (var root = node, node$jscomp$0 = root; ; )
+          if (
+            (commitUnmount(node$jscomp$0),
+            null === node$jscomp$0.child ||
+              (mutation && 4 === node$jscomp$0.tag))
+          ) {
+            if (node$jscomp$0 === root) break;
+            for (; null === node$jscomp$0.sibling; ) {
+              if (
+                null === node$jscomp$0.return ||
+                node$jscomp$0.return === root
+              )
+                break a;
+              node$jscomp$0 = node$jscomp$0.return;
+            }
+            node$jscomp$0.sibling.return = node$jscomp$0.return;
+            node$jscomp$0 = node$jscomp$0.sibling;
+          } else
+            (node$jscomp$0.child.return = node$jscomp$0),
+              (node$jscomp$0 = node$jscomp$0.child);
+        currentParentIsContainer
+          ? removeChildFromContainer(currentParent, node.stateNode)
+          : removeChild(currentParent, node.stateNode);
+      } else if (
         (4 === node.tag
           ? (currentParent = node.stateNode.containerInfo)
           : commitUnmount(node),

From 499d654eb8d3f0294a3ad0d1e073be48aac7870b Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Tue, 15 May 2018 16:43:43 -0700
Subject: [PATCH 0592/1109] Halve the period of time until an issue is
 considered stale

Summary:
I propose halving the time required to flag and close an issue due to inactivity. The new time period would be 90 days (~3 months), at which point the bot will flag an issue as stale. This starts the second timer, where if the issue sees no further activity within 30 days, it will be closed by the bot.

_Extra: Do not automatically mark as stale issues labeled as regressions or "Help Wanted"_

Currently, an issue must see no activity for 180 days (~six months), at which point it is labeled stale. It will then take a further 60 days of inactivity before the issue is closed.

Take for example issue 9773. It was opened in September 2016, and closed for inactivity in November 2016. It was then resurrected February 2018. Three months later, no activity has occurred. This is, in my opinion, too lenient and the issue should be closed.

Last year, we reached a point where the repo has over 1,500 open issues. After finding some of these issues had no activity for over a year, I enabled a Stale bot on the repository which took care of closing any issue that saw no activity over a two week period. This helped us get to 200 open issues after some time.

After hearing feedback from the community that the bot was too aggressive on new issues, and considering that 200 open issues on such a broad project as React Native is not too high of a number, I dialed down the Stale bot so that it would take up to ~8 months to close a stale issue. In hindsight, I believe this was too big of an over-correction on my part. With open issues now topping 600, I think it's about time the Stale bot starts closing inactive issues again.

My view is that closing an issue does not indicate the issue is invalid. Closing an issue for inactivity is a sign that the issue is not problematic enough to inspire a member of the community to followup and/or propose a fix through a PR. Closing stale issues as soon as possible should help maintainers surface active issues with the greatest impact on users of the library.

None, configuration change.

[INTERNAL] [MINOR] [stale.yml] - Update Stale bot to halve stale closing times.
Closes https://github.com/facebook/react-native/pull/19253

Differential Revision: D8019532

Pulled By: hramos

fbshipit-source-id: 405b87ac3229c5ffb20a2ce2234cdcbec1f01c66
---
 .github/stale.yml | 11 +++++++----
 1 file changed, 7 insertions(+), 4 deletions(-)

diff --git a/.github/stale.yml b/.github/stale.yml
index a738daf37832..538514d64696 100644
--- a/.github/stale.yml
+++ b/.github/stale.yml
@@ -1,12 +1,15 @@
+# Configuration for probot-stale - https://github.com/probot/stale
 # Number of days of inactivity before an issue becomes stale
-daysUntilStale: 180
+daysUntilStale: 90
 # Number of days of inactivity before a stale issue is closed
-daysUntilClose: 60
+daysUntilClose: 30
 # Issues with these labels will never be considered stale
 exemptLabels:
   - Good first issue
   - For Discussion
-  - Core Team 
+  - Core Team
+  - "Help Wanted :octocat:"
+  - ":warning:Regression"
 # Label to use when marking an issue as stale
 staleLabel: Stale 
 # Comment to post when marking an issue as stale. Set to `false` to disable
@@ -17,4 +20,4 @@ markComment: >
 # Comment to post when closing a stale issue. Set to `false` to disable
 closeComment: >
   Closing this issue after a prolonged period of inactivity. If this issue is still present in the latest release, please feel free to create a new issue with up-to-date information.
-only: issues
\ No newline at end of file
+only: issues

From 1ad8351d9b05c56c3e573ed9efbe6098eb220aa9 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 15 May 2018 17:13:41 -0700
Subject: [PATCH 0593/1109] Clear apt cache

Summary:
This will unblock test_android on CI.
Closes https://github.com/facebook/react-native/pull/19275

Differential Revision: D8020049

Pulled By: hramos

fbshipit-source-id: 9d738a636f63138aae918759e879f9e397c11aca
---
 .circleci/config.yml                     | 10 +++++-----
 scripts/circleci/apt-get-android-deps.sh |  2 +-
 2 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 52bb45540cd1..22aaf594a8fd 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -44,15 +44,15 @@ aliases:
 
   - &restore-cache-apt
     keys:
-      - v1-apt-{{ arch }}-{{ .Branch }}-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
-      # Fallback in case checksum fails
-      - v1-apt-{{ arch }}-{{ .Branch }}-
+      - v1-apt-{{ .Branch }}-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
       # Fallback in case this is a first-time run on a fork
-      - v1-apt-{{ arch }}-master-
+      # You always want to match checksum, if it fails,
+      # proceed with a fresh install.
+      - v1-apt-master-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
   - &save-cache-apt
     paths:
       - ~/vendor/apt
-    key: v1-apt-{{ arch }}-{{ .Branch }}-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
+    key: v1-apt-{{ .Branch }}-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
 
   - &restore-cache-ndk
     keys:
diff --git a/scripts/circleci/apt-get-android-deps.sh b/scripts/circleci/apt-get-android-deps.sh
index 6463de83d046..8305f6244ccc 100755
--- a/scripts/circleci/apt-get-android-deps.sh
+++ b/scripts/circleci/apt-get-android-deps.sh
@@ -22,4 +22,4 @@ fi
 
 # Install all packages in the cache
 echo "Installing build dependencies..."
-sudo dpkg -i ~/vendor/apt/archives/*.deb
\ No newline at end of file
+sudo dpkg -i ~/vendor/apt/archives/*.deb

From 2472d915ab94e489f8f3ad9f56ef356860281bf6 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 15 May 2018 17:25:16 -0700
Subject: [PATCH 0594/1109] Consolidate CI/local test scripts

Summary:
Update `scripts/run-android-emulator.sh` to use same settings as Circle CI when creating and launching an AVD. This helps provide a known good configuration, useful for running Android tests locally.

Run `scripts/run-android-emulator.sh` and confirm AVD is created && launched
Run `scripts/run-android-emulator.sh` again and see message about AVD already running
Run `test_android` on CI and observe AVD is launched.

Run `runXcodeTests.sh` and confirm unit tests run.
Run CI and confirm iOS unit tests run.

[GENERAL][MINOR][`scripts`] - Consolidate CI/local test scripts
Closes https://github.com/facebook/react-native/pull/19228

Differential Revision: D8019888

Pulled By: hramos

fbshipit-source-id: 28b12c2e781ee80bcc90c22e691a5acb16232369
---
 .circleci/config.yml                          | 20 +++++-----
 ...un-android-docker-instrumentation-tests.sh |  2 +-
 runXcodeTests.sh                              | 24 ++++++------
 scripts/.tests.env                            | 32 +++++++++++++++
 ...e-ci-android-setup.sh => android-setup.sh} | 39 +++++++++----------
 scripts/run-android-emulator.sh               | 14 +++++--
 scripts/validate-android-device-env.sh        |  0
 7 files changed, 85 insertions(+), 46 deletions(-)
 create mode 100644 scripts/.tests.env
 rename scripts/{circle-ci-android-setup.sh => android-setup.sh} (69%)
 mode change 100644 => 100755 scripts/validate-android-device-env.sh

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 22aaf594a8fd..eb83b1dcc69a 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -22,12 +22,12 @@ aliases:
 
   - &restore-cache-android-packages
     keys:
-      - v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-{{ checksum "scripts/circle-ci-android-setup.sh" }}
+      - v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-{{ checksum "scripts/android-setup.sh" }}
       - v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-
   - &save-cache-android-packages
     paths:
       - /opt/android/sdk
-    key: v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-{{ checksum "scripts/circle-ci-android-setup.sh" }}
+    key: v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-{{ checksum "scripts/android-setup.sh" }}
 
   - &restore-cache-gradle
     keys:
@@ -56,12 +56,12 @@ aliases:
 
   - &restore-cache-ndk
     keys:
-      - v3-android-ndk-{{ arch }}-r10e-{{ checksum "scripts/circle-ci-android-setup.sh" }}
+      - v3-android-ndk-{{ arch }}-r10e-{{ checksum "scripts/android-setup.sh" }}
       - v3-android-ndk-{{ arch }}-r10e-
   - &save-cache-ndk
     paths:
       - /opt/ndk
-    key: v3-android-ndk-{{ arch }}-r10e-{{ checksum "scripts/circle-ci-android-setup.sh" }}
+    key: v3-android-ndk-{{ arch }}-r10e-{{ checksum "scripts/android-setup.sh" }}
 
   - &restore-cache-buck
     keys:
@@ -117,7 +117,7 @@ aliases:
   # Dependency Management
   - &install-ndk
     name: Install Android NDK
-    command: source scripts/circle-ci-android-setup.sh && getAndroidNDK
+    command: source scripts/android-setup.sh && getAndroidNDK
 
   - &yarn
     |
@@ -174,7 +174,7 @@ aliases:
 
   - &install-android-packages
     name: Install Android SDK Packages
-    command: source scripts/circle-ci-android-setup.sh && getAndroidSDK
+    command: source scripts/android-setup.sh && getAndroidPackages
 
   - &install-android-build-dependencies
     name: Install Android Build Dependencies
@@ -223,16 +223,16 @@ aliases:
 
   - &create-avd
     name: Create Android Virtual Device
-    command: source scripts/circle-ci-android-setup.sh && createAVD
+    command: source scripts/android-setup.sh && createAVD
 
   - &launch-avd
     name: Launch Android Virtual Device in Background
-    command: source scripts/circle-ci-android-setup.sh && launchAVD
+    command: source scripts/android-setup.sh && launchAVD
     background: true
 
   - &wait-for-avd
     name: Wait for Android Virtual Device
-    command: source scripts/circle-ci-android-setup.sh && waitForAVD
+    command: source scripts/android-setup.sh && waitForAVD
 
   - &build-js-bundle
     name: Build JavaScript Bundle
@@ -253,7 +253,7 @@ aliases:
       if [[ ! -e ReactAndroid/src/androidTest/assets/AndroidTestBundle.js ]]; then
         echo "JavaScript bundle missing, cannot run instrumentation tests. Verify build-js-bundle step completed successfully."; exit 1;
       fi
-      source scripts/circle-ci-android-setup.sh && NO_BUCKD=1 retry3 timeout 300 buck install ReactAndroid/src/androidTest/buck-runner:instrumentation-tests --config build.threads=$BUILD_THREADS
+      source scripts/android-setup.sh && NO_BUCKD=1 retry3 timeout 300 buck install ReactAndroid/src/androidTest/buck-runner:instrumentation-tests --config build.threads=$BUILD_THREADS
 
   - &collect-android-test-results
     name: Collect Test Results
diff --git a/ContainerShip/scripts/run-android-docker-instrumentation-tests.sh b/ContainerShip/scripts/run-android-docker-instrumentation-tests.sh
index c7806c7f055a..ed7183dec9d5 100644
--- a/ContainerShip/scripts/run-android-docker-instrumentation-tests.sh
+++ b/ContainerShip/scripts/run-android-docker-instrumentation-tests.sh
@@ -28,7 +28,7 @@ watchman shutdown-server
 node local-cli/cli.js bundle --platform android --dev true --entry-file ReactAndroid/src/androidTest/js/TestBundle.js --bundle-output ReactAndroid/src/androidTest/assets/AndroidTestBundle.js
 
 # build test APK
-source ./scripts/circle-ci-android-setup.sh && NO_BUCKD=1 retry3 buck install ReactAndroid/src/androidTest/buck-runner:instrumentation-tests --config build.threads=1
+source ./scripts/android-setup.sh && NO_BUCKD=1 retry3 buck install ReactAndroid/src/androidTest/buck-runner:instrumentation-tests --config build.threads=1
 
 # run installed apk with tests
 node ./ContainerShip/scripts/run-android-ci-instrumentation-tests.js $*
diff --git a/runXcodeTests.sh b/runXcodeTests.sh
index d4524a4a6384..b1b6e7f4fba3 100755
--- a/runXcodeTests.sh
+++ b/runXcodeTests.sh
@@ -1,18 +1,20 @@
 #!/bin/sh
+# This script should be run from the react-native root
 
-# Run from react-native root
+THIS_DIR=$(dirname "$0")
+source "scripts/.tests.env"
 
-set -e
-
-if [ -z "$1" ]
+if [ -n "$1" ]
   then
-    echo "You must supply an OS version as the first arg, e.g. 8.1"
-    exit 255
+    echo "Overriding..."
+    IOS_TARGET_OS="${1}"
+    SDK="iphonesimulator${1}"
+    DESTINATION="platform=iOS Simulator,OS=${IOS_TARGET_OS},name=${IOS_DEVICE}"
 fi
 
-xctool \
-  -project RNTester/RNTester.xcodeproj \
-  -scheme RNTester \
-  -sdk iphonesimulator${1} \
-  -destination "platform=iOS Simulator,OS=${1},name=iPhone 5" \
+xcodebuild \
+  -project "RNTester/RNTester.xcodeproj" \
+  -scheme $SCHEME \
+  -sdk $SDK \
+  -destination "$DESTINATION" \
   build test
diff --git a/scripts/.tests.env b/scripts/.tests.env
new file mode 100644
index 000000000000..e32332722c14
--- /dev/null
+++ b/scripts/.tests.env
@@ -0,0 +1,32 @@
+# These should match the recommended versions listed in
+# https://facebook.github.io/react-native/docs/getting-started.html
+
+
+## ANDROID ##
+# Android SDK Build Tools revision
+export ANDROID_SDK_BUILD_TOOLS_REVISION=23.0.1
+# Android API Level we build with
+export ANDROID_SDK_BUILD_API_LEVEL="23"
+# Minimum Android API Level we target
+export ANDROID_SDK_TARGET_API_LEVEL="19"
+# Android Virtual Device name
+export AVD_NAME="testAVD"
+# ABI to use in Android Virtual Device
+export AVD_ABI=x86
+
+## IOS ##
+export IOS_TARGET_OS="11.3"
+export IOS_DEVICE="iPhone 5s"
+
+export SCHEME="RNTester"
+export SDK="iphonesimulator${IOS_TARGET_OS}"
+export DESTINATION="platform=iOS Simulator,OS=${IOS_TARGET_OS},name=${IOS_DEVICE}"
+
+## CI OVERRIDES ##
+# Values to override when running in CI
+# $CI is set by Circle CI
+if [ $CI ]; then
+  # Use ARM on Circle CI
+  export AVD_ABI=armeabi-v7a
+fi
+
diff --git a/scripts/circle-ci-android-setup.sh b/scripts/android-setup.sh
similarity index 69%
rename from scripts/circle-ci-android-setup.sh
rename to scripts/android-setup.sh
index 35421a598a03..c879a968911b 100644
--- a/scripts/circle-ci-android-setup.sh
+++ b/scripts/android-setup.sh
@@ -1,25 +1,16 @@
 # inspired by https://github.com/Originate/guide/blob/master/android/guide/Continuous%20Integration.md
 
-# SDK Built Tools revision, per http://facebook.github.io/react-native/docs/getting-started.html
-ANDROID_SDK_BUILD_TOOLS_REVISION=23.0.1
-# API Level we build with
-ANDROID_SDK_BUILD_API_LEVEL="23"
-# Minimum API Level we target, used for emulator image
-ANDROID_SDK_TARGET_API_LEVEL="19"
-# Emulator name
-AVD_NAME="testAVD"
+source "scripts/.tests.env"
 
-function getAndroidSDK {
-  export PATH="$ANDROID_HOME/platform-tools:$ANDROID_HOME/tools:$PATH"
+function getAndroidPackages {
+  export PATH="$ANDROID_HOME/platform-tools:$ANDROID_HOME/tools:$ANDROID_HOME/tools.bin:$PATH"
 
   DEPS="$ANDROID_HOME/installed-dependencies"
 
-  if [ ! -e $DEPS ]; then
-    echo "Installing Android API level $ANDROID_SDK_TARGET_API_LEVEL, Google APIs, ARM EABI v7a system image..."
-    sdkmanager "system-images;android-$ANDROID_SDK_TARGET_API_LEVEL;google_apis;armeabi-v7a"
-# x86 image requires hardware acceleration, which is not supported when running within the CircleCI Docker image
-#    echo "Installing Android API level $ANDROID_SDK_TARGET_API_LEVEL, Google APIs, Intel x86 Atom system image..."
-#    sdkmanager "system-images;android-$ANDROID_SDK_TARGET_API_LEVEL;google_apis;x86"
+  # Package names can be obtained using `sdkmanager --list`
+  if [ ! -e $DEPS ] || [ ! $CI ]; then
+    echo "Installing Android API level $ANDROID_SDK_TARGET_API_LEVEL, Google APIs, $AVD_ABI system image..."
+    sdkmanager "system-images;android-$ANDROID_SDK_TARGET_API_LEVEL;google_apis;$AVD_ABI"
     echo "Installing build SDK for Android API level $ANDROID_SDK_BUILD_API_LEVEL..."
     sdkmanager "platforms;android-$ANDROID_SDK_BUILD_API_LEVEL"
     echo "Installing target SDK for Android API level $ANDROID_SDK_TARGET_API_LEVEL..."
@@ -30,7 +21,7 @@ function getAndroidSDK {
     sdkmanager "add-ons;addon-google_apis-google-$ANDROID_SDK_BUILD_API_LEVEL"
     echo "Installing Android Support Repository"
     sdkmanager "extras;android;m2repository"
-    touch $DEPS
+    $CI && touch $DEPS
   fi
 }
 
@@ -50,13 +41,21 @@ function getAndroidNDK {
 }
 
 function createAVD {
-  echo no | avdmanager create avd --name $AVD_NAME --force --package "system-images;android-$ANDROID_SDK_TARGET_API_LEVEL;google_apis;armeabi-v7a" --tag google_apis --abi armeabi-v7a
+  AVD_PACKAGES="system-images;android-$ANDROID_SDK_TARGET_API_LEVEL;google_apis;$AVD_ABI"
+  echo "Creating AVD with packages $AVD_PACKAGES"
+  echo no | avdmanager create avd --name $AVD_NAME --force --package $AVD_PACKAGES --tag google_apis --abi $AVD_ABI
 }
 
 function launchAVD {
+  export PATH="$ANDROID_HOME/emulator:$PATH"
+
   # The AVD name here should match the one created in createAVD
-  # emulator64-arm -avd $AVD_NAME -no-audio -no-window -no-boot-anim -gpu off
-  emulator -avd $AVD_NAME -no-audio -no-window
+  if [ $CI ]
+  then
+    emulator -avd $AVD_NAME -no-audio -no-window
+  else
+    emulator -avd $AVD_NAME
+  fi
 }
 
 function waitForAVD {
diff --git a/scripts/run-android-emulator.sh b/scripts/run-android-emulator.sh
index a705e0a8a026..d7307120b0ed 100755
--- a/scripts/run-android-emulator.sh
+++ b/scripts/run-android-emulator.sh
@@ -5,7 +5,8 @@
 # The only reason to use this config is that it represents a known-good
 # virtual device configuration.
 # This is useful for running integration tests on a local machine.
-# TODO: make continuous integration use the precise same setup
+
+THIS_DIR=$(dirname "$0")
 
 STATE=`adb get-state`
 
@@ -14,6 +15,11 @@ if [ -n "$STATE" ]; then
     exit 1
 fi
 
-echo "Creating virtual device..."
-echo no | android create avd -n testAVD -f -t android-23 --abi default/x86
-emulator -avd testAVD
+echo "Installing packages"
+source "${THIS_DIR}/android-setup.sh" && getAndroidPackages
+
+echo "Creating Android virtual device..."
+source "${THIS_DIR}/android-setup.sh" && createAVD
+
+echo "Launching Android virtual device..."
+source "${THIS_DIR}/android-setup.sh" && launchAVD
diff --git a/scripts/validate-android-device-env.sh b/scripts/validate-android-device-env.sh
old mode 100644
new mode 100755

From 274c1757e67f7d1e9ae8fe724d1f0f7755e00e06 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Tue, 15 May 2018 23:10:39 -0700
Subject: [PATCH 0595/1109] Make Android build tools 26.0.3 available to CI

Summary:
a3931e95317acaff5ceb1d2fb0f26ae67744c8a3 bumped buildToolsVersions to 26.0.3, and `test_android` started failing because that particular build tools version was not getting installed in CircleCI.
Closes https://github.com/facebook/react-native/pull/19276

Differential Revision: D8020664

Pulled By: hramos

fbshipit-source-id: 561aa8186ed165b3652923a9bcaf56134acfd90b
---
 scripts/.tests.env       | 4 ++--
 scripts/android-setup.sh | 2 +-
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/scripts/.tests.env b/scripts/.tests.env
index e32332722c14..9bbc63b24a5d 100644
--- a/scripts/.tests.env
+++ b/scripts/.tests.env
@@ -4,9 +4,9 @@
 
 ## ANDROID ##
 # Android SDK Build Tools revision
-export ANDROID_SDK_BUILD_TOOLS_REVISION=23.0.1
+export ANDROID_SDK_BUILD_TOOLS_REVISION=26.0.3
 # Android API Level we build with
-export ANDROID_SDK_BUILD_API_LEVEL="23"
+export ANDROID_SDK_BUILD_API_LEVEL="26"
 # Minimum Android API Level we target
 export ANDROID_SDK_TARGET_API_LEVEL="19"
 # Android Virtual Device name
diff --git a/scripts/android-setup.sh b/scripts/android-setup.sh
index c879a968911b..87734287448c 100644
--- a/scripts/android-setup.sh
+++ b/scripts/android-setup.sh
@@ -16,7 +16,7 @@ function getAndroidPackages {
     echo "Installing target SDK for Android API level $ANDROID_SDK_TARGET_API_LEVEL..."
     sdkmanager "platforms;android-$ANDROID_SDK_TARGET_API_LEVEL"
     echo "Installing SDK build tools, revision $ANDROID_SDK_BUILD_TOOLS_REVISION..."
-    sdkmanager "build-tools;$ANDROID_SDK_BUILD_TOOLS_REVISION"
+    sdkmanager "build-tools;android-$ANDROID_SDK_BUILD_TOOLS_REVISION"
     echo "Installing Google APIs for Android API level $ANDROID_SDK_BUILD_API_LEVEL..."
     sdkmanager "add-ons;addon-google_apis-google-$ANDROID_SDK_BUILD_API_LEVEL"
     echo "Installing Android Support Repository"

From 10c5368c37d9ae29b155a21caa4d3755f192d911 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 15 May 2018 23:32:33 -0700
Subject: [PATCH 0596/1109] Fabric: Fixed issue where root shadow node does not
 layout itself

Summary: Conceptually, it always must be node owner's responsibility, but for the root node, we have to make an exception because there is no another parent node and there is no another component which has access to YogaNode.

Reviewed By: fkgozali

Differential Revision: D7958251

fbshipit-source-id: 0bdaea87adbd323c758bc3c28f325be615aa90f3
---
 ReactCommon/fabric/view/root/RootShadowNode.cpp         | 6 ++++++
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h | 3 ++-
 2 files changed, 8 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/view/root/RootShadowNode.cpp b/ReactCommon/fabric/view/root/RootShadowNode.cpp
index 7cefd4b0a476..e48b1336cc39 100644
--- a/ReactCommon/fabric/view/root/RootShadowNode.cpp
+++ b/ReactCommon/fabric/view/root/RootShadowNode.cpp
@@ -6,6 +6,7 @@
  */
 
 #include "RootShadowNode.h"
+#include "conversions.h"
 
 namespace facebook {
 namespace react {
@@ -17,6 +18,11 @@ ComponentName RootShadowNode::getComponentName() const {
 void RootShadowNode::layout() {
   ensureUnsealed();
   layout(getProps()->layoutContext);
+
+  // This is the rare place where shadow node must layout (set `layoutMetrics`)
+  // itself because there is no a parent node which usually should do it.
+  YGNode *yogaNode = const_cast<YGNode *>(yogaNode_.get());
+  setLayoutMetrics(layoutMetricsFromYogaNode(*yogaNode));
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index 0d00a3f3690b..7c3a1b2f3d91 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -82,9 +82,10 @@ class YogaLayoutableShadowNode:
   
   void layoutChildren(LayoutContext layoutContext) override;
 
-private:
+protected:
   mutable SharedYogaNode yogaNode_;
 
+private:
   static SharedYogaConfig suitableYogaConfig();
   static void setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children);
   static YGNode *yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex);

From 57d69772b767e76c3306e7328c5a4bd7769864bd Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 15 May 2018 23:32:34 -0700
Subject: [PATCH 0597/1109] Fabric: Improved signature of
 `calculateMutationInstructions`

Summary: Apparently, `calculateMutationInstructions` must also produce mutation instructions for root node as well. To make it possible we have to change the signature of the function and weak some restrictions in TreeMutationInstruction.

Reviewed By: fkgozali

Differential Revision: D7958248

fbshipit-source-id: 4109a6bce3a77f7eb89157201fd0e80f98487dbd
---
 .../fabric/uimanager/Differentiator.cpp       | 30 ++++++++++++++++++-
 ReactCommon/fabric/uimanager/Differentiator.h |  5 ++--
 ReactCommon/fabric/uimanager/ShadowTree.cpp   |  3 +-
 .../uimanager/TreeMutationInstruction.cpp     |  2 --
 4 files changed, 32 insertions(+), 8 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/Differentiator.cpp b/ReactCommon/fabric/uimanager/Differentiator.cpp
index 87f929904503..a689d51d9db6 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.cpp
+++ b/ReactCommon/fabric/uimanager/Differentiator.cpp
@@ -5,7 +5,7 @@
 namespace facebook {
 namespace react {
 
-void calculateMutationInstructions(
+static void calculateMutationInstructions(
   TreeMutationInstructionList &instructions,
   SharedShadowNode parentNode,
   SharedShadowNodeSharedList oldChildNodes,
@@ -154,5 +154,33 @@ void calculateMutationInstructions(
   instructions.insert(instructions.end(), downwardInstructions.begin(), downwardInstructions.end());
 }
 
+
+void calculateMutationInstructions(
+  TreeMutationInstructionList &instructions,
+  SharedShadowNode oldRootShadowNode,
+  SharedShadowNode newRootShadowNode
+) {
+  // Root shadow nodes must have same tag.
+  assert(oldRootShadowNode->getTag() == newRootShadowNode->getTag());
+
+  if (*oldRootShadowNode != *newRootShadowNode) {
+    instructions.push_back(
+      TreeMutationInstruction::Replace(
+        nullptr,
+        oldRootShadowNode,
+        newRootShadowNode,
+        -1
+      )
+    );
+  }
+
+  calculateMutationInstructions(
+    instructions,
+    oldRootShadowNode,
+    oldRootShadowNode->getChildren(),
+    newRootShadowNode->getChildren()
+  );
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/Differentiator.h b/ReactCommon/fabric/uimanager/Differentiator.h
index 7eb9fa332ff6..c1d7a8b1d4e8 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.h
+++ b/ReactCommon/fabric/uimanager/Differentiator.h
@@ -15,9 +15,8 @@ namespace react {
  */
 void calculateMutationInstructions(
   TreeMutationInstructionList &instructions,
-  SharedShadowNode parentNode,
-  SharedShadowNodeSharedList oldChildNodes,
-  SharedShadowNodeSharedList newChildNodes
+  SharedShadowNode oldNode,
+  SharedShadowNode newNode
 );
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 32a7870d96a7..30b246438649 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -69,8 +69,7 @@ void ShadowTree::complete(UnsharedRootShadowNode newRootShadowNode) {
   calculateMutationInstructions(
     instructions,
     oldRootShadowNode,
-    oldRootShadowNode->ShadowNode::getChildren(),
-    newRootShadowNode->ShadowNode::getChildren()
+    newRootShadowNode
   );
 
   if (commit(newRootShadowNode)) {
diff --git a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
index 42882ee6cfc6..fd728dd7a417 100644
--- a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
+++ b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
@@ -82,10 +82,8 @@ const TreeMutationInstruction TreeMutationInstruction::Replace(
   SharedShadowNode newChildNode,
   int index
 ) {
-  assert(parentNode);
   assert(oldChildNode);
   assert(newChildNode);
-  assert(index != -1);
 
   return TreeMutationInstruction(
     Replacement,

From 545f087b46b5e41b7fa12debc289e5eda9d4ef86 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 15 May 2018 23:32:36 -0700
Subject: [PATCH 0598/1109] Fabric: Several helper functions for `react::Rect`

Summary: Trivial. We will need them soon at least for ScrollView.

Reviewed By: fkgozali

Differential Revision: D7958244

fbshipit-source-id: ce92c6e6181181ac17d817292af18ffa46a4d975
---
 ReactCommon/fabric/graphics/Geometry.h | 15 +++++++++++++++
 1 file changed, 15 insertions(+)

diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index 00efbe62f2ac..ec5de4100194 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -2,6 +2,7 @@
 
 #pragma once
 
+#include <algorithm>
 #include <tuple>
 
 #include <CoreGraphics/CGBase.h>
@@ -85,6 +86,20 @@ struct Rect {
   bool operator !=(const Rect& rhs) const {
     return !(*this == rhs);
   }
+
+  Float getMaxX() const { return size.width > 0 ? origin.x + size.width : origin.x; }
+  Float getMaxY() const { return size.height > 0 ? origin.y + size.height : origin.y; }
+  Float getMinX() const { return size.width >= 0 ? origin.x : origin.x + size.width; }
+  Float getMinY() const { return size.height >= 0 ? origin.y : origin.y + size.height; }
+
+  void unionInPlace(const Rect &rect) {
+    Float x1 = std::min(getMinX(), rect.getMinX());
+    Float y1 = std::min(getMinY(), rect.getMinY());
+    Float x2 = std::max(getMaxX(), rect.getMaxX());
+    Float y2 = std::max(getMaxY(), rect.getMaxY());
+    origin = {x1, y1};
+    size = {x2 - x1, y2 - y1};
+  }
 };
 
 /*

From 30d08ea8a47a9ce666e3af94874e9621a17a3cd4 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 15 May 2018 23:32:38 -0700
Subject: [PATCH 0599/1109] Fabric: `EdgeInsets` from `dynamic` conversion

Summary: We will need this for several components, first of all for ScrollView.

Reviewed By: fkgozali

Differential Revision: D7958246

fbshipit-source-id: 364b939abe8f0734376448149bbdc735abd00189
---
 ReactCommon/fabric/graphics/conversions.h | 13 +++++++++++++
 1 file changed, 13 insertions(+)

diff --git a/ReactCommon/fabric/graphics/conversions.h b/ReactCommon/fabric/graphics/conversions.h
index 7d0cd5b1cef5..2ca159c73857 100644
--- a/ReactCommon/fabric/graphics/conversions.h
+++ b/ReactCommon/fabric/graphics/conversions.h
@@ -75,6 +75,19 @@ inline void fromDynamic(const folly::dynamic &value, Size &result) {
   abort();
 }
 
+inline void fromDynamic(const folly::dynamic &value, EdgeInsets &result) {
+  if (value.isArray()) {
+    result = EdgeInsets {
+      (Float)value[0].asDouble(),
+      (Float)value[1].asDouble(),
+      (Float)value[2].asDouble(),
+      (Float)value[3].asDouble()
+    };
+    return;
+  }
+  abort();
+}
+
 inline std::string toString(const Point &point) {
   return "{" + folly::to<std::string>(point.x) + ", " + folly::to<std::string>(point.y) + "}";
 }

From 48dccf18b884f3165c4b179383e4965b0a58d2c7 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 15 May 2018 23:32:42 -0700
Subject: [PATCH 0600/1109] Fabric: Making logging in FabricUIManager optional

Summary: Trivial.

Reviewed By: fkgozali

Differential Revision: D7961186

fbshipit-source-id: 703fa3b336e093c430d32ab08eafc42b1f590f32
---
 .../fabric/uimanager/FabricUIManager.cpp      | 31 ++++++++++---------
 1 file changed, 17 insertions(+), 14 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 4c6c1efe2279..9099374b8fc8 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -20,6 +20,9 @@
 namespace facebook {
 namespace react {
 
+// TODO: Kill this flag and remove debug logging.
+const bool isLoggingEnabled = false;
+
 static const RawProps rawPropsFromDynamic(const folly::dynamic object) {
   // TODO: Convert this to something smarter, probably returning `std::iterator`.
   RawProps result;
@@ -90,7 +93,7 @@ UIManagerDelegate *FabricUIManager::getDelegate() {
 }
 
 SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
-  LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
 
   ComponentName componentName = componentNameByReactViewName(viewName);
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[componentName];
@@ -104,7 +107,7 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
       componentDescriptor->cloneProps(nullptr, rawProps)
     );
 
-  LOG(INFO) << "FabricUIManager::createNode() -> " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode() -> " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
 
   if (delegate_) {
     delegate_->uiManagerDidCreateShadowNode(shadowNode);
@@ -114,18 +117,18 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
 }
 
 SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode) {
-  LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
 
   SharedShadowNode clonedShadowNode =
     componentDescriptor->cloneShadowNode(shadowNode);
 
-  LOG(INFO) << "FabricUIManager::cloneNode() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNode() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode) {
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   // Assuming semantic: Cloning with same props but empty children.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
 
@@ -136,12 +139,12 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with same children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
@@ -153,12 +156,12 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
       nullptr
     );
 
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }
 
 SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with empty children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
@@ -170,12 +173,12 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
-  LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }
 
 void FabricUIManager::appendChild(const SharedShadowNode &parentShadowNode, const SharedShadowNode &childShadowNode) {
-  LOG(INFO) << "FabricUIManager::appendChild(parentShadowNode: " << parentShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", childShadowNode: " << childShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::appendChild(parentShadowNode: " << parentShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", childShadowNode: " << childShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[parentShadowNode];
 
   // TODO: Remove this after we move this to JS side.
@@ -192,17 +195,17 @@ void FabricUIManager::appendChild(const SharedShadowNode &parentShadowNode, cons
 }
 
 SharedShadowNodeUnsharedList FabricUIManager::createChildSet(int rootTag) {
-  LOG(INFO) << "FabricUIManager::createChildSet(rootTag: " << rootTag << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::createChildSet(rootTag: " << rootTag << ")";
   return std::make_shared<SharedShadowNodeList>(SharedShadowNodeList({}));
 }
 
 void FabricUIManager::appendChildToSet(const SharedShadowNodeUnsharedList &shadowNodeList, const SharedShadowNode &shadowNode) {
-  LOG(INFO) << "FabricUIManager::appendChildToSet(shadowNodeList: " << shadowNodeList << ", shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::appendChildToSet(shadowNodeList: " << shadowNodeList << ", shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   shadowNodeList->push_back(shadowNode);
 }
 
 void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedList &children) {
-  LOG(INFO) << "FabricUIManager::completeRoot(rootTag: " << rootTag << ", shadowNodeList: " << children << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::completeRoot(rootTag: " << rootTag << ", shadowNodeList: " << children << ")";
 
   if (delegate_) {
     delegate_->uiManagerDidFinishTransaction(rootTag, children);

From 8c74864d7bff16ccfd5179ea399b0bc4adaef69b Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Wed, 16 May 2018 08:49:57 -0700
Subject: [PATCH 0601/1109] Update Android packages cache key

Summary:
Packages are now defined in `scripts/.tests.env`, so the checksum is updated accordingly.

We also throw away the cache if the checksum fails as not doing so may prevent us from picking up new packages due to the filesystem check in `scripts/android-setup.sh`#getAndroidPackages(), as the presence of the `installed-dependencies` file restored from cache will incorrectly flag all deps as being installed.
Closes https://github.com/facebook/react-native/pull/19298

Differential Revision: D8025918

Pulled By: hramos

fbshipit-source-id: 189492baac2fea39280884ea20e376a368e23c2e
---
 .circleci/config.yml     | 5 ++---
 scripts/.tests.env       | 2 ++
 scripts/android-setup.sh | 7 ++++---
 3 files changed, 8 insertions(+), 6 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index eb83b1dcc69a..4e49f255a4be 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -22,12 +22,11 @@ aliases:
 
   - &restore-cache-android-packages
     keys:
-      - v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-{{ checksum "scripts/android-setup.sh" }}
-      - v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-
+      - v1-android-sdkmanager-packages-api-26-alpha-{{ checksum "scripts/.tests.env" }}
   - &save-cache-android-packages
     paths:
       - /opt/android/sdk
-    key: v1-android-sdkmanager-packages-{{ arch }}-api-26-alpha-{{ checksum "scripts/android-setup.sh" }}
+    key: v1-android-sdkmanager-packages-api-26-alpha-{{ checksum "scripts/.tests.env" }}
 
   - &restore-cache-gradle
     keys:
diff --git a/scripts/.tests.env b/scripts/.tests.env
index 9bbc63b24a5d..ab318809fef5 100644
--- a/scripts/.tests.env
+++ b/scripts/.tests.env
@@ -7,6 +7,8 @@
 export ANDROID_SDK_BUILD_TOOLS_REVISION=26.0.3
 # Android API Level we build with
 export ANDROID_SDK_BUILD_API_LEVEL="26"
+# Google APIs for Android level
+export ANDROID_GOOGLE_API_LEVEL="23"
 # Minimum Android API Level we target
 export ANDROID_SDK_TARGET_API_LEVEL="19"
 # Android Virtual Device name
diff --git a/scripts/android-setup.sh b/scripts/android-setup.sh
index 87734287448c..6492173f3f8d 100644
--- a/scripts/android-setup.sh
+++ b/scripts/android-setup.sh
@@ -16,9 +16,10 @@ function getAndroidPackages {
     echo "Installing target SDK for Android API level $ANDROID_SDK_TARGET_API_LEVEL..."
     sdkmanager "platforms;android-$ANDROID_SDK_TARGET_API_LEVEL"
     echo "Installing SDK build tools, revision $ANDROID_SDK_BUILD_TOOLS_REVISION..."
-    sdkmanager "build-tools;android-$ANDROID_SDK_BUILD_TOOLS_REVISION"
-    echo "Installing Google APIs for Android API level $ANDROID_SDK_BUILD_API_LEVEL..."
-    sdkmanager "add-ons;addon-google_apis-google-$ANDROID_SDK_BUILD_API_LEVEL"
+    sdkmanager "build-tools;$ANDROID_SDK_BUILD_TOOLS_REVISION"
+    # These moved to "system-images;android-$ANDROID_SDK_BUILD_API_LEVEL;google_apis;x86" starting with API level 25, but there is no ARM version.
+    echo "Installing Google APIs $ANDROID_GOOGLE_API_LEVEL..."
+    sdkmanager "add-ons;addon-google_apis-google-$ANDROID_GOOGLE_API_LEVEL"
     echo "Installing Android Support Repository"
     sdkmanager "extras;android;m2repository"
     $CI && touch $DEPS

From 128c9343c464f3e7898d6e245f135f8bdf6caa6a Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Wed, 16 May 2018 13:35:33 -0700
Subject: [PATCH 0602/1109] iOS: fix up RNTesterPods

Summary:
A few fixes:
* missing include: folly/Optional.h
* switch folly::Optional's `has_value()` to `hasValue()` for now until folly is upgraded to newer version
* fix up import for RCTTextAttributes.h
* fix up includes for "conversions.h" to use namespaced includes

Reviewed By: mmmulani

Differential Revision: D8021149

fbshipit-source-id: d3955986d3ab6b1d9b61ac1e385767893ce57e5e
---
 Libraries/Text/RCTConvert+Text.h              |  3 ++-
 Libraries/Text/RCTTextAttributes.h            |  3 ++-
 RNTester/Podfile.lock                         |  6 ++---
 React.podspec                                 |  2 +-
 .../attributedstring/TextAttributes.cpp       | 24 +++++++++----------
 ReactCommon/fabric/core/propsConversions.h    |  1 +
 .../debug/debugStringConvertibleUtils.h       |  3 ++-
 .../RCTAttributedTextUtils.mm                 | 12 +++++-----
 ReactCommon/fabric/view/root/RootProps.cpp    |  3 ++-
 .../fabric/view/root/RootShadowNode.cpp       |  3 ++-
 .../view/yoga/YogaLayoutableShadowNode.cpp    |  3 +--
 11 files changed, 34 insertions(+), 29 deletions(-)

diff --git a/Libraries/Text/RCTConvert+Text.h b/Libraries/Text/RCTConvert+Text.h
index 81a3c7ccfaff..7c43cfca8943 100644
--- a/Libraries/Text/RCTConvert+Text.h
+++ b/Libraries/Text/RCTConvert+Text.h
@@ -6,7 +6,8 @@
  */
 
 #import <React/RCTConvert.h>
-#import <RCTText/RCTTextTransform.h>
+
+#import "RCTTextTransform.h"
 
 NS_ASSUME_NONNULL_BEGIN
 
diff --git a/Libraries/Text/RCTTextAttributes.h b/Libraries/Text/RCTTextAttributes.h
index 802211909a42..7575bb17269f 100644
--- a/Libraries/Text/RCTTextAttributes.h
+++ b/Libraries/Text/RCTTextAttributes.h
@@ -8,7 +8,8 @@
 #import <UIKit/UIKit.h>
 
 #import <React/RCTTextDecorationLineType.h>
-#import <RCTText/RCTTextTransform.h>
+
+#import "RCTTextTransform.h"
 
 NS_ASSUME_NONNULL_BEGIN
 
diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index a52cf4348062..9afe598993e1 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -115,7 +115,7 @@ DEPENDENCIES:
   - yoga (from `../ReactCommon/yoga`)
 
 SPEC REPOS:
-  https://github.com/CocoaPods/Specs.git:
+  https://github.com/cocoapods/specs.git:
     - boost-for-react-native
 
 EXTERNAL SOURCES:
@@ -135,9 +135,9 @@ SPEC CHECKSUMS:
   DoubleConversion: e22e0762848812a87afd67ffda3998d9ef29170c
   Folly: 9a8eea4725a0b6ba3256ebf206c21e352c23abf8
   glog: 1de0bb937dccdc981596d3b5825ebfb765017ded
-  React: 512b17e881b5d04d703cd292caa6f4fe12984688
+  React: 3d56cdd885ecc0f2f3534b2f54a11cf9707229fb
   yoga: bdd268c5812f00bdb52cc2b58f129797e97935eb
 
 PODFILE CHECKSUM: 1a96172007b66aa74825c234f17139dd9c3d3cd7
 
-COCOAPODS: 1.5.0
+COCOAPODS: 1.5.2
diff --git a/React.podspec b/React.podspec
index 1c590b4ff530..e5a5d0ba7980 100644
--- a/React.podspec
+++ b/React.podspec
@@ -183,7 +183,7 @@ Pod::Spec.new do |s|
     ss.subspec "textlayoutmanager" do |sss|
       sss.dependency             "Folly", folly_version
       sss.compiler_flags       = folly_compiler_flags
-      sss.source_files         = "ReactCommon/fabric/textlayoutmanager/**/*.{cpp,h}"
+      sss.source_files         = "ReactCommon/fabric/textlayoutmanager/**/*.{cpp,h,mm}"
       sss.exclude_files        = "**/tests/*"
       sss.header_dir           = "fabric/textlayoutmanager"
       sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.cpp b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
index 93e316250863..1a5528182ec7 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.cpp
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.cpp
@@ -26,31 +26,31 @@ void TextAttributes::apply(TextAttributes textAttributes) {
   fontFamily = !textAttributes.fontFamily.empty() ? textAttributes.fontFamily : fontFamily;
   fontSize = !isnan(textAttributes.fontSize) ? textAttributes.fontSize : fontSize;
   fontSizeMultiplier = !isnan(textAttributes.fontSizeMultiplier) ? textAttributes.fontSizeMultiplier : fontSizeMultiplier;
-  fontWeight = textAttributes.fontWeight.has_value() ? textAttributes.fontWeight : fontWeight;
-  fontStyle = textAttributes.fontStyle.has_value() ? textAttributes.fontStyle : fontStyle;
-  fontVariant = textAttributes.fontVariant.has_value() ? textAttributes.fontVariant : fontVariant;
-  allowFontScaling = textAttributes.allowFontScaling.has_value() ? textAttributes.allowFontScaling : allowFontScaling;
+  fontWeight = textAttributes.fontWeight.hasValue() ? textAttributes.fontWeight : fontWeight;
+  fontStyle = textAttributes.fontStyle.hasValue() ? textAttributes.fontStyle : fontStyle;
+  fontVariant = textAttributes.fontVariant.hasValue() ? textAttributes.fontVariant : fontVariant;
+  allowFontScaling = textAttributes.allowFontScaling.hasValue() ? textAttributes.allowFontScaling : allowFontScaling;
   letterSpacing = !isnan(textAttributes.letterSpacing) ? textAttributes.letterSpacing : letterSpacing;
 
   // Paragraph Styles
   lineHeight = !isnan(textAttributes.lineHeight) ? textAttributes.lineHeight : lineHeight;
-  alignment = textAttributes.alignment.has_value() ? textAttributes.alignment : alignment;
-  baseWritingDirection = textAttributes.baseWritingDirection.has_value() ? textAttributes.baseWritingDirection : baseWritingDirection;
+  alignment = textAttributes.alignment.hasValue() ? textAttributes.alignment : alignment;
+  baseWritingDirection = textAttributes.baseWritingDirection.hasValue() ? textAttributes.baseWritingDirection : baseWritingDirection;
 
   // Decoration
   textDecorationColor = textAttributes.textDecorationColor ? textAttributes.textDecorationColor : textDecorationColor;
-  textDecorationLineType = textAttributes.textDecorationLineType.has_value() ? textAttributes.textDecorationLineType : textDecorationLineType;
-  textDecorationLineStyle = textAttributes.textDecorationLineStyle.has_value() ? textAttributes.textDecorationLineStyle : textDecorationLineStyle;
-  textDecorationLinePattern = textAttributes.textDecorationLinePattern.has_value() ? textAttributes.textDecorationLinePattern : textDecorationLinePattern;
+  textDecorationLineType = textAttributes.textDecorationLineType.hasValue() ? textAttributes.textDecorationLineType : textDecorationLineType;
+  textDecorationLineStyle = textAttributes.textDecorationLineStyle.hasValue() ? textAttributes.textDecorationLineStyle : textDecorationLineStyle;
+  textDecorationLinePattern = textAttributes.textDecorationLinePattern.hasValue() ? textAttributes.textDecorationLinePattern : textDecorationLinePattern;
 
   // Shadow
-  textShadowOffset = textAttributes.textShadowOffset.has_value() ? textAttributes.textShadowOffset.value() : textShadowOffset;
+  textShadowOffset = textAttributes.textShadowOffset.hasValue() ? textAttributes.textShadowOffset.value() : textShadowOffset;
   textShadowRadius = !isnan(textAttributes.textShadowRadius) ? textAttributes.textShadowRadius : textShadowRadius;
   textShadowColor = textAttributes.textShadowColor ? textAttributes.textShadowColor : textShadowColor;
 
   // Special
-  isHighlighted = textAttributes.isHighlighted.has_value() ? textAttributes.isHighlighted : isHighlighted;
-  layoutDirection = textAttributes.layoutDirection.has_value() ? textAttributes.layoutDirection : layoutDirection;
+  isHighlighted = textAttributes.isHighlighted.hasValue() ? textAttributes.isHighlighted : isHighlighted;
+  layoutDirection = textAttributes.layoutDirection.hasValue() ? textAttributes.layoutDirection : layoutDirection;
 }
 
 #pragma mark - DebugStringConvertible
diff --git a/ReactCommon/fabric/core/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
index edca1fe8e0ae..f4a25f8dff9e 100644
--- a/ReactCommon/fabric/core/propsConversions.h
+++ b/ReactCommon/fabric/core/propsConversions.h
@@ -7,6 +7,7 @@
 
 #pragma once
 
+#include <folly/Optional.h>
 #include <folly/dynamic.h>
 #include <fabric/graphics/Color.h>
 #include <fabric/graphics/Geometry.h>
diff --git a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
index 836945018b32..f0a26d0590ce 100644
--- a/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
+++ b/ReactCommon/fabric/debug/debugStringConvertibleUtils.h
@@ -15,6 +15,7 @@
 #include <fabric/debug/DebugStringConvertible.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
 #include <folly/Conv.h>
+#include <folly/Optional.h>
 
 namespace facebook {
 namespace react {
@@ -36,7 +37,7 @@ inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name,
 
 template <typename T>
 inline SharedDebugStringConvertible debugStringConvertibleItem(std::string name, folly::Optional<T> value, T defaultValue = {}) {
-  if (!value.has_value()) {
+  if (!value.hasValue()) {
     return nullptr;
   }
 
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
index da7c70fd0c6e..11d4db50c075 100644
--- a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
+++ b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
@@ -19,9 +19,9 @@
   RCTFontProperties fontProperties;
   fontProperties.family = fontFamily;
   fontProperties.size = textAttributes.fontSize;
-  fontProperties.style = textAttributes.fontStyle.has_value() ? RCTFontStyleFromFontStyle(textAttributes.fontStyle.value()) : RCTFontStyleUndefined;
-  fontProperties.variant = textAttributes.fontVariant.has_value() ? RCTFontVariantFromFontVariant(textAttributes.fontVariant.value()) : RCTFontVariantDefault;
-  fontProperties.weight = textAttributes.fontWeight.has_value() ? CGFloat(textAttributes.fontWeight.value()) : NAN;
+  fontProperties.style = textAttributes.fontStyle.hasValue() ? RCTFontStyleFromFontStyle(textAttributes.fontStyle.value()) : RCTFontStyleUndefined;
+  fontProperties.variant = textAttributes.fontVariant.hasValue() ? RCTFontVariantFromFontVariant(textAttributes.fontVariant.value()) : RCTFontVariantDefault;
+  fontProperties.weight = textAttributes.fontWeight.hasValue() ? CGFloat(textAttributes.fontWeight.value()) : NAN;
   fontProperties.sizeMultiplier = textAttributes.fontSizeMultiplier;
 
   return RCTFontWithFontProperties(fontProperties);
@@ -82,7 +82,7 @@ inline static CGFloat RCTEffectiveFontSizeMultiplierFromTextAttributes(const Tex
   // Paragraph Style
   NSMutableParagraphStyle *paragraphStyle = [NSMutableParagraphStyle new];
   BOOL isParagraphStyleUsed = NO;
-  if (textAttributes.alignment.has_value()) {
+  if (textAttributes.alignment.hasValue()) {
     TextAlignment textAlignment = textAttributes.alignment.value_or(TextAlignment::Natural);
     if (textAttributes.layoutDirection.value_or(LayoutDirection::LeftToRight) == LayoutDirection::RightToLeft) {
       if (textAlignment == TextAlignment::Right) {
@@ -97,7 +97,7 @@ inline static CGFloat RCTEffectiveFontSizeMultiplierFromTextAttributes(const Tex
     isParagraphStyleUsed = YES;
   }
 
-  if (textAttributes.baseWritingDirection.has_value()) {
+  if (textAttributes.baseWritingDirection.hasValue()) {
     paragraphStyle.baseWritingDirection =
       RCTNSWritingDirectionFromWritingDirection(textAttributes.baseWritingDirection.value());
     isParagraphStyleUsed = YES;
@@ -151,7 +151,7 @@ inline static CGFloat RCTEffectiveFontSizeMultiplierFromTextAttributes(const Tex
   }
 
   // Shadow
-  if (textAttributes.textShadowOffset.has_value()) {
+  if (textAttributes.textShadowOffset.hasValue()) {
     auto textShadowOffset = textAttributes.textShadowOffset.value();
     NSShadow *shadow = [NSShadow new];
     shadow.shadowOffset = CGSize {textShadowOffset.x, textShadowOffset.y};
diff --git a/ReactCommon/fabric/view/root/RootProps.cpp b/ReactCommon/fabric/view/root/RootProps.cpp
index 70aac488a035..ec7260b539ef 100644
--- a/ReactCommon/fabric/view/root/RootProps.cpp
+++ b/ReactCommon/fabric/view/root/RootProps.cpp
@@ -7,8 +7,9 @@
 
 #include "RootProps.h"
 
+#include <fabric/view/conversions.h>
+
 #include "YogaLayoutableShadowNode.h"
-#include "conversions.h"
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/root/RootShadowNode.cpp b/ReactCommon/fabric/view/root/RootShadowNode.cpp
index e48b1336cc39..8fdbb50565a8 100644
--- a/ReactCommon/fabric/view/root/RootShadowNode.cpp
+++ b/ReactCommon/fabric/view/root/RootShadowNode.cpp
@@ -6,7 +6,8 @@
  */
 
 #include "RootShadowNode.h"
-#include "conversions.h"
+
+#include <fabric/view/conversions.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 49d018ecb870..9ad1be234f25 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -13,10 +13,9 @@
 #include <fabric/core/LayoutContext.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/view/conversions.h>
 #include <yoga/Yoga.h>
 
-#include "conversions.h"
-
 namespace facebook {
 namespace react {
 

From 86b3865bfef32dae842118c43a4159418abdde58 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Wed, 16 May 2018 17:43:16 -0700
Subject: [PATCH 0603/1109] Omit Fabric Yoga dependency in OSS

Reviewed By: achen1

Differential Revision: D8036707

fbshipit-source-id: 33c02ae28cecd7d470d0cd968589c65485857f6c
---
 .../test/java/com/facebook/react/fabric/BUCK  | 79 ++++++++++---------
 1 file changed, 40 insertions(+), 39 deletions(-)

diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
index faa1e3fa21a8..6cfe34c2e058 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
@@ -1,40 +1,41 @@
-load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_robolectric_test", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target")
 
-rn_robolectric_test(
-    name = "fabric",
-    srcs = glob(["**/*.java"]),
-    contacts = ["oncall+fbandroid_sheriff@xmail.facebook.com"],
-    resources = glob([
-        "**/*.txt",
-        "**/*.json",
-    ]),
-    visibility = [
-        "PUBLIC",
-    ],
-    deps = [
-        "xplat//yoga/java:java",
-        react_native_dep("third-party/java/assertj:assertj-core"),
-        react_native_dep("third-party/java/fest:fest"),
-        react_native_dep("third-party/java/fest:fest_android"),
-        react_native_dep("third-party/java/guava:guava"),
-        react_native_dep("third-party/java/jackson:jackson"),
-        react_native_dep("third-party/java/jsr-305:jsr-305"),
-        react_native_dep("third-party/java/jsr-330:jsr-330"),
-        react_native_dep("third-party/java/junit:junit"),
-        react_native_dep("third-party/java/mockito:mockito"),
-        react_native_dep("third-party/java/robolectric3/robolectric:robolectric"),
-        react_native_dep("libraries/fbcore/src/test/java/com/facebook/powermock:powermock"),
-        react_native_dep("libraries/soloader/java/com/facebook/soloader:soloader"),
-        react_native_dep("third-party/android/support/v4:lib-support-v4"),
-        react_native_target("java/com/facebook/react:react"),
-        react_native_target("java/com/facebook/react/bridge:bridge"),
-        react_native_target("java/com/facebook/react/common:common"),
-        react_native_target("java/com/facebook/react/fabric:fabric"),
-        react_native_target("java/com/facebook/react/modules/core:core"),
-        react_native_target("java/com/facebook/react/uimanager:uimanager"),
-        react_native_target("java/com/facebook/react/views/text:text"),
-        react_native_target("java/com/facebook/react/views/view:view"),
-        react_native_target("java/com/facebook/react/views/progressbar:progressbar"),
-        react_native_tests_target("java/com/facebook/react/bridge:testhelpers"),
-    ],
-)
+if not IS_OSS_BUILD:
+    rn_robolectric_test(
+        name = "fabric",
+        srcs = glob(["**/*.java"]),
+        contacts = ["oncall+fbandroid_sheriff@xmail.facebook.com"],
+        resources = glob([
+            "**/*.txt",
+            "**/*.json",
+        ]),
+        visibility = [
+            "PUBLIC",
+        ],
+        deps = [
+            "xplat//yoga/java:java",
+            react_native_dep("third-party/java/assertj:assertj-core"),
+            react_native_dep("third-party/java/fest:fest"),
+            react_native_dep("third-party/java/fest:fest_android"),
+            react_native_dep("third-party/java/guava:guava"),
+            react_native_dep("third-party/java/jackson:jackson"),
+            react_native_dep("third-party/java/jsr-305:jsr-305"),
+            react_native_dep("third-party/java/jsr-330:jsr-330"),
+            react_native_dep("third-party/java/junit:junit"),
+            react_native_dep("third-party/java/mockito:mockito"),
+            react_native_dep("third-party/java/robolectric3/robolectric:robolectric"),
+            react_native_dep("libraries/fbcore/src/test/java/com/facebook/powermock:powermock"),
+            react_native_dep("libraries/soloader/java/com/facebook/soloader:soloader"),
+            react_native_dep("third-party/android/support/v4:lib-support-v4"),
+            react_native_target("java/com/facebook/react:react"),
+            react_native_target("java/com/facebook/react/bridge:bridge"),
+            react_native_target("java/com/facebook/react/common:common"),
+            react_native_target("java/com/facebook/react/fabric:fabric"),
+            react_native_target("java/com/facebook/react/modules/core:core"),
+            react_native_target("java/com/facebook/react/uimanager:uimanager"),
+            react_native_target("java/com/facebook/react/views/text:text"),
+            react_native_target("java/com/facebook/react/views/view:view"),
+            react_native_target("java/com/facebook/react/views/progressbar:progressbar"),
+            react_native_tests_target("java/com/facebook/react/bridge:testhelpers"),
+        ],
+    )

From b1d646a7cd6757391aa58045990cf3516b77ad50 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 16 May 2018 17:57:27 -0700
Subject: [PATCH 0604/1109] Add extra logging information for ReactShadowNode

Reviewed By: achen1

Differential Revision: D8020040

fbshipit-source-id: c0606eeeb14e89e52f2a0b5537418d88387e4e0a
---
 .../com/facebook/react/uimanager/ReactShadowNodeImpl.java   | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index ff009b5b2c29..a6c152066782 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -110,6 +110,7 @@ public YogaNode cloneNode(YogaNode oldYogaNode,
   private final float[] mPadding = new float[Spacing.ALL + 1];
   private final boolean[] mPaddingIsPercent = new boolean[Spacing.ALL + 1];
   private YogaNode mYogaNode;
+  private int mGenerationDebugInformation = 1;
   private ReactShadowNode mOriginalReactShadowNode = null;
 
   private @Nullable ReactStylesDiffMap mNewProps;
@@ -143,6 +144,7 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     mScreenY = 0;
     mScreenWidth = 0;
     mScreenHeight = 0;
+    mGenerationDebugInformation = original.mGenerationDebugInformation + 1;
     arraycopy(original.mPadding, 0, mPadding, 0, original.mPadding.length);
     arraycopy(original.mPaddingIsPercent, 0, mPaddingIsPercent, 0, original.mPaddingIsPercent.length);
     mNewProps = null;
@@ -1062,8 +1064,8 @@ private void getHierarchyInfoWithIndentation(StringBuilder result, int level) {
       result.append("  ");
     }
 
-    result.append("<").append(getClass().getSimpleName()).append(" tag=").append(getReactTag()).append(" hash=")
-      .append(hashCode());
+    result.append("<").append(getClass().getSimpleName()).append(" tag=").append(getReactTag()).append(" gen=")
+      .append(mGenerationDebugInformation);
     if (mYogaNode != null) {
       result.append(" layout='x:").append(getScreenX())
         .append(" y:").append(getScreenY()).append(" w:").append(getLayoutWidth()).append(" h:")

From 1e8a45f2067766f5c797d9b3d530b7a10ad88e17 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Wed, 16 May 2018 20:12:39 -0700
Subject: [PATCH 0605/1109] Remove checksum fallbacks to ensure clean installs

Summary:
If `package.json` has changed, let's throw away the cache and let yarn install do its thing.

Circle CI.

[INTERNAL][MINOR][CircleCI] - Remove checksum fallbacks
Closes https://github.com/facebook/react-native/pull/19303

Differential Revision: D8029286

Pulled By: hramos

fbshipit-source-id: 528681e4da9f0215bf63f9f8b3920a95036badca
---
 .circleci/config.yml | 34 ++++++++++++++++++++--------------
 1 file changed, 20 insertions(+), 14 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 4e49f255a4be..57d57acdbf42 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -1,19 +1,24 @@
 aliases:
   # Cache Management
-  - &restore-cache-yarn
+  - &restore-yarn-cache
     keys:
-      - v1-yarn-{{ arch }}-{{ checksum "package.json" }}
-      - v1-yarn-{{ arch }}-
-  - &save-cache-yarn
+      - v1-yarn-cache-{{ arch }}
+  - &save-yarn-cache
     paths:
-      - node_modules
       - ~/.cache/yarn
-    key: v1-yarn-{{ arch }}-{{ checksum "package.json" }}
+    key: v1-yarn-cache-{{ arch }}
+
+  - &restore-node-modules
+    keys:
+      - v2-node-modules-{{ arch }}-{{ checksum "package.json" }}
+  - &save-node-modules
+    paths:
+      - node_modules
+    key: v2-node-modules-{{ arch }}-{{ checksum "package.json" }}
 
   - &restore-cache-analysis
     keys:
       - v1-analysis-dependencies-{{ arch }}-{{ checksum "package.json" }}{{ checksum "bots/package.json" }}
-      - v1-analysis-dependencies-{{ arch }}-
   - &save-cache-analysis
     paths:
       - bots/node_modules
@@ -45,8 +50,6 @@ aliases:
     keys:
       - v1-apt-{{ .Branch }}-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
       # Fallback in case this is a first-time run on a fork
-      # You always want to match checksum, if it fails,
-      # proceed with a fresh install.
       - v1-apt-master-{{ checksum "scripts/circleci/apt-get-android-deps.sh" }}
   - &save-cache-apt
     paths:
@@ -56,7 +59,6 @@ aliases:
   - &restore-cache-ndk
     keys:
       - v3-android-ndk-{{ arch }}-r10e-{{ checksum "scripts/android-setup.sh" }}
-      - v3-android-ndk-{{ arch }}-r10e-
   - &save-cache-ndk
     paths:
       - /opt/ndk
@@ -325,9 +327,11 @@ jobs:
       - checkout
       - run: *setup-artifacts
 
-      - restore-cache: *restore-cache-yarn
+      - restore-cache: *restore-yarn-cache
+      - restore-cache: *restore-node-modules
       - run: *yarn
-      - save-cache: *save-cache-yarn
+      - save-cache: *save-yarn-cache
+      - save-cache: *save-node-modules
 
       # Basic checks against the checkout, cache...
       - run: *run-sanity-checks
@@ -454,9 +458,11 @@ jobs:
       - run: *gradle-download-deps
       - save-cache: *save-cache-gradle-downloads
 
-      - restore-cache: *restore-cache-yarn
+      - restore-cache: *restore-yarn-cache
+      - restore-cache: *restore-node-modules
       - run: *yarn
-      - save-cache: *save-cache-yarn
+      - save-cache: *save-yarn-cache
+      - save-cache: *save-node-modules
 
       - run:
           name: Publish React Native Package

From 8dad3e413247cc11ec0fb97485893315ebf77f69 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Wed, 16 May 2018 22:29:13 -0700
Subject: [PATCH 0606/1109] add google maven repo required by appcompat-v7 26

Summary:
add google maven repo required by appcompat-v7 26

CI will download appcompat-v7 version 26.0.2

[GENERAL][MINOR][Android] - add google maven repo required by appcompat-v7 26
Closes https://github.com/facebook/react-native/pull/19316

Differential Revision: D8039324

Pulled By: hramos

fbshipit-source-id: 3e9f4dd20560f4337e81967ee9b5c30ec61016de
---
 build.gradle | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/build.gradle b/build.gradle
index fb60c323a263..e40f43e2799a 100644
--- a/build.gradle
+++ b/build.gradle
@@ -4,6 +4,10 @@ buildscript {
     repositories {
         jcenter()
         mavenLocal()
+        maven {
+            url 'https://maven.google.com/'
+            name 'Google'
+        }
     }
     dependencies {
         classpath 'com.android.tools.build:gradle:2.2.2'
@@ -18,6 +22,10 @@ allprojects {
     repositories {
         jcenter()
         mavenLocal()
+        maven {
+            url 'https://maven.google.com/'
+            name 'Google'
+        }
 
         def androidSdk = System.getenv("ANDROID_SDK")
         maven {

From 4e1453eb01ee4d20d6070ec292ae97f589b5087f Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Thu, 17 May 2018 09:48:47 -0700
Subject: [PATCH 0607/1109] Add RTL support for Fabric android rendering

Reviewed By: fkgozali

Differential Revision: D8035223

fbshipit-source-id: 22d702e487fd2c20cd03e5004d904ddfcfbdb55a
---
 ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK    | 3 ++-
 .../main/java/com/facebook/react/fabric/FabricUIManager.java | 5 ++++-
 2 files changed, 6 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
index da59ddbf2bfc..fc9da7d6b6f9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "YOGA_TARGET", "react_native_target")
 
 rn_android_library(
     name = "fabric",
@@ -11,6 +11,7 @@ rn_android_library(
         "PUBLIC",
     ],
     deps = [
+        YOGA_TARGET,
         react_native_dep("third-party/java/infer-annotations:infer-annotations"),
         react_native_dep("third-party/java/jsr-305:jsr-305"),
         react_native_target("java/com/facebook/react:react"),
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index f9d1948ab87e..c7a539e3ede8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -35,6 +35,7 @@
 import com.facebook.react.uimanager.ViewManagerRegistry;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
+import com.facebook.yoga.YogaDirection;
 import java.util.ArrayList;
 import java.util.HashSet;
 import java.util.LinkedList;
@@ -411,7 +412,9 @@ public void removeRootView(int rootTag) {
   private ReactShadowNode createRootShadowNode(int rootTag, ThemedReactContext themedReactContext) {
     ReactShadowNode rootNode = new ReactShadowNodeImpl();
     I18nUtil sharedI18nUtilInstance = I18nUtil.getInstance();
-    // TODO: setLayoutDirection for the rootNode
+    if (sharedI18nUtilInstance.isRTL(themedReactContext)) {
+      rootNode.setLayoutDirection(YogaDirection.RTL);
+    }
     rootNode.setViewClassName("Root");
     rootNode.setReactTag(rootTag);
     rootNode.setThemedContext(themedReactContext);

From ce3b7b8204dad0fd62a76a0ce66472eca4b25bc8 Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Thu, 17 May 2018 11:18:36 -0700
Subject: [PATCH 0608/1109] Bring back TextInput.State, deprecate
 focusTextInput and blurTextInput

Summary:
a275eac56e21b8f3631bcd03ace86c07a3b0c0ba removed TextInput.State but we should keep it as it was a public-ish API and we don't have any migration plan off it. Also bring back `focusTextInput` and `blurTextInput` with a deprecation warning.

Tested TextInput.State is back

[GENERAL][ENHANCEMENT][TextInput] - Bring back TextInput.State, deprecate focusTextInput and blurTextInput
Closes https://github.com/facebook/react-native/pull/18936

Differential Revision: D8044439

Pulled By: hramos

fbshipit-source-id: fde145f04bb1d46ef58b5954cb7963adf495b21c
---
 Libraries/Components/TextInput/TextInput.js | 18 +++++++++++++++++-
 1 file changed, 17 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index a9f6716a340f..7909b5a8fae5 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -325,7 +325,23 @@ type Props = $ReadOnly<{|
 
 const TextInput = createReactClass({
   displayName: 'TextInput',
-
+  statics: {
+    State: {
+      currentlyFocusedField: TextInputState.currentlyFocusedField,
+      focusTextInput: (textFieldID: ?number) => {
+        console.warn(
+          '`focusTextInput` is deprecated, use the `focus` method of the `TextInput` ref instead.',
+        );
+        TextInputState.focusTextInput(textFieldID);
+      },
+      blurTextInput: (textFieldID: ?number) => {
+        console.warn(
+          '`blurTextInput` is deprecated, use `Keyboard.dismiss` or the `blur` method of the `TextInput` ref.',
+        );
+        TextInputState.blurTextInput(textFieldID);
+      },
+    },
+  },
   propTypes: {
     ...ViewPropTypes,
     /**

From b8051720344f3716e964eaf7cfdd2a91dc703602 Mon Sep 17 00:00:00 2001
From: Jose Pereira <onaips@gmail.com>
Date: Thu, 17 May 2018 18:51:03 -0700
Subject: [PATCH 0609/1109] Clear _handlers on RCTNetworking invalidation

Summary:
This PR fixes a bug where in `RCTNetworking` not all tasks/handlers were not being cleared when invalidating the class.

I came across this issue when writing some unit tests for my native plugins, sometimes a test would finish running (and the bridge invalidated), and only afterwards a callback from RCTNetworking would come, resulting in this exception:

```
2018-05-07 15:23:34.264494-0700 Guardian[73794:10710945] *** Assertion failure in -[RCTEventEmitter sendEventWithName:body:](), /Users/.../app/node_modules/react-native/React/Modules/RCTEventEmitter.m:41
2018-05-07 15:23:34.276505-0700 Guardian[73794:10710945] *** Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Error when sending event: didCompleteNetworkResponse with body: (
    2,
    cancelled,
    0
). Bridge is not set. This is probably because you've explicitly synthesized the bridge in RCTNetworking, even though it's inherited from RCTEventEmitter.'
*** First throw call stack:
(
	0   CoreFoundation                      0x000000010d5b21e6 __exceptionPreprocess + 294
	1   libobjc.A.dylib                     0x000000010be6f031 objc_exception_throw + 48
	2   CoreFoundation                      0x000000010d5b7472 +[NSException raise:format:arguments:] + 98
	3   Foundation                          0x000000010b94864f -[NSAssertionHandler handleFailureInFunction:file:lineNumber:description:] + 165
	4   Guardian                            0x0000000106ff5227 -[RCTEventEmitter sendEventWithName:body:] + 567
	5   Guardian                            0x0000000106e9ebab __76-[RCTNetworking sendRequest:responseType:incrementalUpdates:responseSender:]_block_invoke.423 + 1115
	6   Guardian                            0x0000000106e8f48c __50-[RCTNetworkTask URLRequest:didCompleteWithError:]_block_invoke + 92
	7   Guardian                            0x0000000106e8ded1 -[RCTNetworkTask dispatchCallback:] + 113
	8   Guardian                            0x0000000106e8f37a -[RCTNetworkTask URLRequest:didCompleteWithError:] + 410
	9   Guardian                            0x0000000106ea1aa3 -[RCTHTTPRequestHandler URLSession:task:didCompleteWithError:] + 403
	10  CFNetwork                           0x000000010cf3a437 __51-[NSURLSession delegate_task:didCompleteWithError:]_block_invoke.207 + 80
	11  Foundation                          0x000000010b885363 __NSBLOCKOPERATION_IS_CALLING_OUT_TO_A_BLOCK__ + 7
	12  Foundation                          0x000000010b8851ca -[NSBlockOperation main] + 68
	13  Foundation                          0x000000010b8836b2 -[__NSOperationInternal _start:] + 766
	14  libdispatch.dylib                   0x0000000112457779 _dispatch_client_callout + 8
	15  libdispatch.dylib                   0x000000011245c931 _dispatch_block_invoke_direct + 317
	16  libdispatch.dylib                   0x0000000112457779 _dispatch_client_callout + 8
	17  libdispatch.dylib                   0x000000011245c931 _dispatch_block_invoke_direct + 317
	18  libdispatch.dylib                   0x000000011245c7d4 dispatch_block_perform + 109
	19  Foundation                          0x000000010b87f75b __NSOQSchedule_f + 337
	20  libdispatch.dylib                   0x0000000112457779 _dispatch_client_callout + 8
	21  libdispatch.dylib                   0x000000011245f1b2 _dispatch_queue_serial_drain + 735
	22  libdispatch.dylib                   0x000000011245f9af _dispatch_queue_invoke + 321
	23  libdispatch.dylib                   0x0000000112461cf8 _dispatch_root_queue_drain + 473
	24  libdispatch.dylib                   0x0000000112461ac1 _dispatch_worker_thread3 + 119
	25  libsystem_pthread.dylib             0x000000011297a169 _pthread_wqthread + 1387
	26  libsystem_pthread.dylib             0x0000000112979be9 start_wqthread + 13
)
libc++abi.dylib: terminating with uncaught exception of type NSException
```

Bug can be reproduced by making a `XMLHttpRequest` (uses `RCTNetworking` internally) that takes a couple seconds to perform, and issuing a RCTBridge reload command in the meantime.

You can add the following code to the react-native template project,

```
  componentDidMount() {
    var oReq = new XMLHttpRequest();
    oReq.addEventListener("load", () => console.log('Finished'));
    oReq.open("GET", "https://www.dropbox.com/s/o01hz0chqvjafhv/file.bin?dl=1");
    oReq.send();
    console.log('Request is being performed...')
  }
```
In my case I download a 1MB file.
Run the project and reload the a couple times. Bug is triggered.

 [INTERNAL] [BUGFIX] [RCTNetworking] - Clear handlers and tasks on RCTNetworking invalidation
Closes https://github.com/facebook/react-native/pull/19169

Differential Revision: D8053070

Pulled By: hramos

fbshipit-source-id: d8af54fecd99173905363f962ffc638ef8b85082
---
 Libraries/Network/RCTNetworking.mm | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/Libraries/Network/RCTNetworking.mm b/Libraries/Network/RCTNetworking.mm
index f8de23abf012..e7e5ad88c6a8 100644
--- a/Libraries/Network/RCTNetworking.mm
+++ b/Libraries/Network/RCTNetworking.mm
@@ -139,6 +139,11 @@ @implementation RCTNetworking
 
 - (void)invalidate
 {
+  for (NSNumber *requestID in _tasksByRequestID) {
+    [_tasksByRequestID[requestID] cancel];
+  }
+  [_tasksByRequestID removeAllObjects];
+  _handlers = nil;
   _requestHandlers = nil;
   _responseHandlers = nil;
 }

From e3a3999b75f2e3d716991562e477f76d39652056 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 17 May 2018 20:03:37 -0700
Subject: [PATCH 0610/1109] Fabric: ScrollView: primitives and buck target

Summary: Trivial.

Reviewed By: fkgozali

Differential Revision: D7961870

fbshipit-source-id: 3cfd92bd441dbf516ade777e6428924e9634257a
---
 React.podspec                                 |  9 +++
 ReactCommon/fabric/scrollview/BUCK            | 81 +++++++++++++++++++
 ReactCommon/fabric/scrollview/conversions.h   | 65 +++++++++++++++
 ReactCommon/fabric/scrollview/primitives.h    | 32 ++++++++
 .../scrollview/tests/ScrollViewTest.cpp       | 14 ++++
 5 files changed, 201 insertions(+)
 create mode 100644 ReactCommon/fabric/scrollview/BUCK
 create mode 100644 ReactCommon/fabric/scrollview/conversions.h
 create mode 100644 ReactCommon/fabric/scrollview/primitives.h
 create mode 100644 ReactCommon/fabric/scrollview/tests/ScrollViewTest.cpp

diff --git a/React.podspec b/React.podspec
index e5a5d0ba7980..094b5889aef6 100644
--- a/React.podspec
+++ b/React.podspec
@@ -171,6 +171,15 @@ Pod::Spec.new do |s|
       sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
     end
 
+    ss.subspec "scrollview" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/scrollview/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/scrollview"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
     ss.subspec "text" do |sss|
       sss.dependency             "Folly", folly_version
       sss.compiler_flags       = folly_compiler_flags
diff --git a/ReactCommon/fabric/scrollview/BUCK b/ReactCommon/fabric/scrollview/BUCK
new file mode 100644
index 000000000000..f653943119e2
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/BUCK
@@ -0,0 +1,81 @@
+load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+
+rn_xplat_cxx_library(
+    name = "scrollview",
+    srcs = glob(
+        ["**/*.cpp"],
+        excludes = glob(["tests/**/*.cpp"]),
+    ),
+    headers = glob(
+        ["**/*.h"],
+        excludes = glob(["tests/**/*.h"]),
+    ),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/scrollview",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    force_static = True,
+    macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+        react_native_xplat_target("fabric/view:view"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":scrollview",
+        ],
+    )
diff --git a/ReactCommon/fabric/scrollview/conversions.h b/ReactCommon/fabric/scrollview/conversions.h
new file mode 100644
index 000000000000..e0fc07a6c50b
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/conversions.h
@@ -0,0 +1,65 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/scrollview/primitives.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+inline void fromDynamic(const folly::dynamic &value, ScrollViewSnapToAlignment &result) {
+  auto string = value.asString();
+  if (string == "start") { result = ScrollViewSnapToAlignment::Start; return; }
+  if (string == "center") { result = ScrollViewSnapToAlignment::Center; return; }
+  if (string == "end") { result = ScrollViewSnapToAlignment::End; return; }
+  abort();
+}
+
+inline void fromDynamic(const folly::dynamic &value, ScrollViewIndicatorStyle &result) {
+  auto string = value.asString();
+  if (string == "default") { result = ScrollViewIndicatorStyle::Default; return; }
+  if (string == "black") { result = ScrollViewIndicatorStyle::Black; return; }
+  if (string == "white") { result = ScrollViewIndicatorStyle::White; return; }
+  abort();
+}
+
+inline void fromDynamic(const folly::dynamic &value, ScrollViewKeyboardDismissMode &result) {
+  auto string = value.asString();
+  if (string == "none") { result = ScrollViewKeyboardDismissMode::None; return; }
+  if (string == "on-drag") { result = ScrollViewKeyboardDismissMode::OnDrag; return; }
+  if (string == "interactive") { result = ScrollViewKeyboardDismissMode::Interactive; return; }
+  abort();
+}
+
+inline std::string toString(const ScrollViewSnapToAlignment &value) {
+  switch (value) {
+    case ScrollViewSnapToAlignment::Start: return "start";
+    case ScrollViewSnapToAlignment::Center: return "center";
+    case ScrollViewSnapToAlignment::End: return "end";
+  }
+}
+
+inline std::string toString(const ScrollViewIndicatorStyle &value) {
+  switch (value) {
+    case ScrollViewIndicatorStyle::Default: return "default";
+    case ScrollViewIndicatorStyle::Black: return "black";
+    case ScrollViewIndicatorStyle::White: return "white";
+  }
+}
+
+inline std::string toString(const ScrollViewKeyboardDismissMode &value) {
+  switch (value) {
+    case ScrollViewKeyboardDismissMode::None: return "none";
+    case ScrollViewKeyboardDismissMode::OnDrag: return "on-drag";
+    case ScrollViewKeyboardDismissMode::Interactive: return "interactive";
+  }
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/primitives.h b/ReactCommon/fabric/scrollview/primitives.h
new file mode 100644
index 000000000000..73d1aa210f50
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/primitives.h
@@ -0,0 +1,32 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+namespace facebook {
+namespace react {
+
+enum class ScrollViewSnapToAlignment {
+  Start,
+  Center,
+  End
+};
+
+enum class ScrollViewIndicatorStyle {
+  Default,
+  Black,
+  White
+};
+
+enum class ScrollViewKeyboardDismissMode {
+  None,
+  OnDrag,
+  Interactive
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/tests/ScrollViewTest.cpp b/ReactCommon/fabric/scrollview/tests/ScrollViewTest.cpp
new file mode 100644
index 000000000000..7b7e23fea410
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/tests/ScrollViewTest.cpp
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+TEST(ScrollViewTest, testSomething) {
+  // TODO
+}

From bd99d3a6f4d0b0d06bc529c8d1542c055b1aca58 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 17 May 2018 20:03:39 -0700
Subject: [PATCH 0611/1109] Fabric: ScrollView: xplat part (shadow node, props,
 localdata, descriptor)

Summary:
All the props of a scrollview, and local data.
LocalData part is probably the most interesting: with it we precompute content size which we use inside native scrollview. Previously we rely on some assumptions like "ScrollView must have only one subview" instead, and that was not so efficient and straight-forward.

Reviewed By: fkgozali

Differential Revision: D7961869

fbshipit-source-id: fa070b8423a3e7739aeb62220e51213683e1a223
---
 .../ScrollViewComponentDescriptor.h           | 24 ++++++
 .../fabric/scrollview/ScrollViewLocalData.cpp | 36 ++++++++
 .../fabric/scrollview/ScrollViewLocalData.h   | 46 ++++++++++
 .../fabric/scrollview/ScrollViewProps.cpp     | 84 +++++++++++++++++++
 .../fabric/scrollview/ScrollViewProps.h       | 59 +++++++++++++
 .../scrollview/ScrollViewShadowNode.cpp       | 41 +++++++++
 .../fabric/scrollview/ScrollViewShadowNode.h  | 45 ++++++++++
 ReactCommon/fabric/uimanager/BUCK             |  2 +
 8 files changed, 337 insertions(+)
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewLocalData.cpp
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewLocalData.h
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewProps.cpp
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewProps.h
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewShadowNode.h

diff --git a/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h b/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h
new file mode 100644
index 000000000000..44d61202ebf4
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h
@@ -0,0 +1,24 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/ConcreteComponentDescriptor.h>
+#include <fabric/scrollview/ScrollViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class ScrollViewComponentDescriptor final: public ConcreteComponentDescriptor<ScrollViewShadowNode> {
+public:
+  ComponentName getComponentName() const override {
+    return "ScrollView";
+  }
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/ScrollViewLocalData.cpp b/ReactCommon/fabric/scrollview/ScrollViewLocalData.cpp
new file mode 100644
index 000000000000..a4424f81f97b
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewLocalData.cpp
@@ -0,0 +1,36 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ScrollViewLocalData.h"
+
+#include <fabric/debug/debugStringConvertibleUtils.h>
+#include <fabric/graphics/conversions.h>
+
+namespace facebook {
+namespace react {
+
+ScrollViewLocalData::ScrollViewLocalData(Rect contentBoundingRect):
+  contentBoundingRect(contentBoundingRect) {}
+
+Size ScrollViewLocalData::getContentSize() const {
+  return Size {contentBoundingRect.getMaxX(), contentBoundingRect.getMaxY()};
+}
+
+#pragma mark - DebugStringConvertible
+
+std::string ScrollViewLocalData::getDebugName() const {
+  return "ScrollViewLocalData";
+}
+
+SharedDebugStringConvertibleList ScrollViewLocalData::getDebugProps() const {
+  return {
+    debugStringConvertibleItem("contentBoundingRect", contentBoundingRect)
+  };
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/ScrollViewLocalData.h b/ReactCommon/fabric/scrollview/ScrollViewLocalData.h
new file mode 100644
index 000000000000..8ed967d62328
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewLocalData.h
@@ -0,0 +1,46 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/LocalData.h>
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+class ScrollViewLocalData;
+
+using SharedScrollViewLocalData = std::shared_ptr<const ScrollViewLocalData>;
+
+/*
+ * LocalData for <ScrollView> component.
+ */
+class ScrollViewLocalData:
+  public LocalData {
+
+public:
+  ScrollViewLocalData(Rect contentBoundingRect);
+
+  /*
+   * Compound size of all nested (first level only) components;
+   * is used for computing `contentSize`.
+   */
+  const Rect contentBoundingRect;
+
+#pragma mark - Getters
+
+  Size getContentSize() const;
+
+#pragma mark - DebugStringConvertible
+
+  std::string getDebugName() const override;
+  SharedDebugStringConvertibleList getDebugProps() const override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/ScrollViewProps.cpp b/ReactCommon/fabric/scrollview/ScrollViewProps.cpp
new file mode 100644
index 000000000000..1e4004d06189
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewProps.cpp
@@ -0,0 +1,84 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ScrollViewProps.h"
+
+#include <fabric/graphics/conversions.h>
+#include <fabric/scrollview/conversions.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
+
+#include <fabric/core/propsConversions.h>
+
+namespace facebook {
+namespace react {
+
+ScrollViewProps::ScrollViewProps(const ScrollViewProps &sourceProps, const RawProps &rawProps):
+  ViewProps(sourceProps, rawProps),
+  alwaysBounceHorizontal(convertRawProp(rawProps, "alwaysBounceHorizontal", sourceProps.alwaysBounceHorizontal)),
+  alwaysBounceVertical(convertRawProp(rawProps, "alwaysBounceVertical", sourceProps.alwaysBounceVertical)),
+  bounces(convertRawProp(rawProps, "bounces", sourceProps.bounces)),
+  bouncesZoom(convertRawProp(rawProps, "bouncesZoom", sourceProps.bouncesZoom)),
+  canCancelContentTouches(convertRawProp(rawProps, "canCancelContentTouches", sourceProps.canCancelContentTouches)),
+  centerContent(convertRawProp(rawProps, "centerContent", sourceProps.centerContent)),
+  automaticallyAdjustContentInsets(convertRawProp(rawProps, "automaticallyAdjustContentInsets", sourceProps.automaticallyAdjustContentInsets)),
+  decelerationRate(convertRawProp(rawProps, "decelerationRate", sourceProps.decelerationRate)),
+  directionalLockEnabled(convertRawProp(rawProps, "directionalLockEnabled", sourceProps.directionalLockEnabled)),
+  indicatorStyle(convertRawProp(rawProps, "indicatorStyle", sourceProps.indicatorStyle)),
+  keyboardDismissMode(convertRawProp(rawProps, "keyboardDismissMode", sourceProps.keyboardDismissMode)),
+  maximumZoomScale(convertRawProp(rawProps, "maximumZoomScale", sourceProps.maximumZoomScale)),
+  minimumZoomScale(convertRawProp(rawProps, "minimumZoomScale", sourceProps.minimumZoomScale)),
+  scrollEnabled(convertRawProp(rawProps, "scrollEnabled", sourceProps.scrollEnabled)),
+  pagingEnabled(convertRawProp(rawProps, "pagingEnabled", sourceProps.pagingEnabled)),
+  pinchGestureEnabled(convertRawProp(rawProps, "pinchGestureEnabled", sourceProps.pinchGestureEnabled)),
+  scrollsToTop(convertRawProp(rawProps, "scrollsToTop", sourceProps.scrollsToTop)),
+  showsHorizontalScrollIndicator(convertRawProp(rawProps, "showsHorizontalScrollIndicator", sourceProps.showsHorizontalScrollIndicator)),
+  showsVerticalScrollIndicator(convertRawProp(rawProps, "showsVerticalScrollIndicator", sourceProps.showsVerticalScrollIndicator)),
+  scrollEventThrottle(convertRawProp(rawProps, "scrollEventThrottle", sourceProps.scrollEventThrottle)),
+  zoomScale(convertRawProp(rawProps, "zoomScale", sourceProps.zoomScale)),
+  contentInset(convertRawProp(rawProps, "contentInset", sourceProps.contentInset)),
+  scrollIndicatorInsets(convertRawProp(rawProps, "scrollIndicatorInsets", sourceProps.scrollIndicatorInsets)),
+  snapToInterval(convertRawProp(rawProps, "snapToInterval", sourceProps.snapToInterval)),
+  snapToAlignment(convertRawProp(rawProps, "snapToAlignment", sourceProps.snapToAlignment)) {}
+
+#pragma mark - DebugStringConvertible
+
+SharedDebugStringConvertibleList ScrollViewProps::getDebugProps() const {
+  ScrollViewProps defaultScrollViewProps;
+
+  return
+    ViewProps::getDebugProps() +
+    SharedDebugStringConvertibleList {
+      debugStringConvertibleItem("alwaysBounceHorizontal", alwaysBounceHorizontal, defaultScrollViewProps.alwaysBounceHorizontal),
+      debugStringConvertibleItem("alwaysBounceVertical", alwaysBounceVertical, defaultScrollViewProps.alwaysBounceVertical),
+      debugStringConvertibleItem("bounces", bounces, defaultScrollViewProps.bounces),
+      debugStringConvertibleItem("bouncesZoom", bouncesZoom, defaultScrollViewProps.bouncesZoom),
+      debugStringConvertibleItem("canCancelContentTouches", canCancelContentTouches, defaultScrollViewProps.canCancelContentTouches),
+      debugStringConvertibleItem("centerContent", centerContent, defaultScrollViewProps.centerContent),
+      debugStringConvertibleItem("automaticallyAdjustContentInsets", automaticallyAdjustContentInsets, defaultScrollViewProps.automaticallyAdjustContentInsets),
+      debugStringConvertibleItem("decelerationRate", decelerationRate, defaultScrollViewProps.decelerationRate),
+      debugStringConvertibleItem("directionalLockEnabled", directionalLockEnabled, defaultScrollViewProps.directionalLockEnabled),
+      debugStringConvertibleItem("indicatorStyle", indicatorStyle, defaultScrollViewProps.indicatorStyle),
+      debugStringConvertibleItem("keyboardDismissMode", keyboardDismissMode, defaultScrollViewProps.keyboardDismissMode),
+      debugStringConvertibleItem("maximumZoomScale", maximumZoomScale, defaultScrollViewProps.maximumZoomScale),
+      debugStringConvertibleItem("minimumZoomScale", minimumZoomScale, defaultScrollViewProps.minimumZoomScale),
+      debugStringConvertibleItem("scrollEnabled", scrollEnabled, defaultScrollViewProps.scrollEnabled),
+      debugStringConvertibleItem("pagingEnabled", pagingEnabled, defaultScrollViewProps.pagingEnabled),
+      debugStringConvertibleItem("pinchGestureEnabled", pinchGestureEnabled, defaultScrollViewProps.pinchGestureEnabled),
+      debugStringConvertibleItem("scrollsToTop", scrollsToTop, defaultScrollViewProps.scrollsToTop),
+      debugStringConvertibleItem("showsHorizontalScrollIndicator", showsHorizontalScrollIndicator, defaultScrollViewProps.showsHorizontalScrollIndicator),
+      debugStringConvertibleItem("showsVerticalScrollIndicator", showsVerticalScrollIndicator, defaultScrollViewProps.showsVerticalScrollIndicator),
+      debugStringConvertibleItem("scrollEventThrottle", scrollEventThrottle, defaultScrollViewProps.scrollEventThrottle),
+      debugStringConvertibleItem("zoomScale", zoomScale, defaultScrollViewProps.zoomScale),
+      debugStringConvertibleItem("contentInset", contentInset, defaultScrollViewProps.contentInset),
+      debugStringConvertibleItem("scrollIndicatorInsets", scrollIndicatorInsets, defaultScrollViewProps.scrollIndicatorInsets),
+      debugStringConvertibleItem("snapToInterval", snapToInterval, defaultScrollViewProps.snapToInterval),
+      debugStringConvertibleItem("snapToAlignment", snapToAlignment, defaultScrollViewProps.snapToAlignment),
+    };
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/ScrollViewProps.h b/ReactCommon/fabric/scrollview/ScrollViewProps.h
new file mode 100644
index 000000000000..190332c2fe91
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewProps.h
@@ -0,0 +1,59 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/scrollview/primitives.h>
+#include <fabric/view/ViewProps.h>
+
+namespace facebook {
+namespace react {
+
+// TODO (T28334063): Consider for codegen.
+class ScrollViewProps final:
+  public ViewProps {
+
+public:
+  ScrollViewProps() = default;
+  ScrollViewProps(const ScrollViewProps &sourceProps, const RawProps &rawProps);
+
+#pragma mark - Props
+
+  const bool alwaysBounceHorizontal {true};
+  const bool alwaysBounceVertical {true};
+  const bool bounces {true};
+  const bool bouncesZoom {true};
+  const bool canCancelContentTouches {true};
+  const bool centerContent {false};
+  const bool automaticallyAdjustContentInsets  {false};
+  const Float decelerationRate {0.998};
+  const bool directionalLockEnabled {false};
+  const ScrollViewIndicatorStyle indicatorStyle {ScrollViewIndicatorStyle::Default};
+  const ScrollViewKeyboardDismissMode keyboardDismissMode {ScrollViewKeyboardDismissMode::None};
+  const Float maximumZoomScale {1.0};
+  const Float minimumZoomScale {1.0};
+  const bool scrollEnabled {true};
+  const bool pagingEnabled {false};
+  const bool pinchGestureEnabled {true};
+  const bool scrollsToTop {true};
+  const bool showsHorizontalScrollIndicator {true};
+  const bool showsVerticalScrollIndicator {true};
+  const Float scrollEventThrottle {0};
+  const Float zoomScale {1.0};
+  const EdgeInsets contentInset {};
+  const EdgeInsets scrollIndicatorInsets {};
+  const int snapToInterval {0};
+  const ScrollViewSnapToAlignment snapToAlignment {ScrollViewSnapToAlignment::Start};
+
+#pragma mark - DebugStringConvertible
+
+  SharedDebugStringConvertibleList getDebugProps() const override;
+};
+
+} // namespace react
+} // namespace facebook
+
diff --git a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
new file mode 100644
index 000000000000..96c60b2e3f74
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
@@ -0,0 +1,41 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ScrollViewShadowNode.h"
+
+#include <fabric/core/LayoutMetrics.h>
+
+#include "ScrollViewLocalData.h"
+
+namespace facebook {
+namespace react {
+
+ComponentName ScrollViewShadowNode::getComponentName() const {
+  return ComponentName("ScrollView");
+}
+
+void ScrollViewShadowNode::updateLocalData() {
+  ensureUnsealed();
+
+  Rect contentBoundingRect;
+  for (auto &&childNode : getLayoutableChildNodes()) {
+    contentBoundingRect.unionInPlace(childNode->getLayoutMetrics().frame);
+  }
+
+  auto &&localData = std::make_shared<const ScrollViewLocalData>(contentBoundingRect);
+  setLocalData(localData);
+}
+
+#pragma mark - LayoutableShadowNode
+
+void ScrollViewShadowNode::layout(LayoutContext layoutContext) {
+  ConcreteViewShadowNode<ScrollViewProps>::layout(layoutContext);
+  updateLocalData();
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
new file mode 100644
index 000000000000..e53e93e29ea9
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
@@ -0,0 +1,45 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/LayoutContext.h>
+#include <fabric/scrollview/ScrollViewProps.h>
+#include <fabric/view/ConcreteViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+class ScrollViewShadowNode;
+
+using SharedScrollViewShadowNode = std::shared_ptr<const ScrollViewShadowNode>;
+
+/*
+ * `ShadowNode` for <ScrollView> component.
+ */
+class ScrollViewShadowNode final:
+  public ConcreteViewShadowNode<ScrollViewProps> {
+
+public:
+
+  using ConcreteViewShadowNode::ConcreteViewShadowNode;
+
+  ComponentName getComponentName() const override;
+
+#pragma mark - LayoutableShadowNode
+
+  void layout(LayoutContext layoutContext) override;
+
+private:
+
+  void updateLocalData();
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 39004b1e121d..78a4c7ae1fff 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -54,6 +54,8 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/text:text"),
         react_native_xplat_target("fabric/view:view"),
+        react_native_xplat_target("fabric/scrollview:scrollview"),
+        react_native_xplat_target("fabric/text:text"),
     ],
 )
 

From 15cb6540c1193c1e7125e484b8f8156e218b3f9b Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 17 May 2018 20:03:41 -0700
Subject: [PATCH 0612/1109] Fabric: ScrollView, the native part

Summary: Note: not all scrollview props and features (especially event listeners and imperative calls) are supported yet.

Reviewed By: fkgozali

Differential Revision: D7961868

fbshipit-source-id: 5277674fe976e089fd963066f78e705ad846d78d
---
 .../Root}/RCTRootComponentView.h              |   0
 .../Root}/RCTRootComponentView.mm             |   0
 .../ScrollView/RCTEnhancedScrollView.h        |  25 ++++
 .../ScrollView/RCTEnhancedScrollView.mm       |  12 ++
 .../ScrollView/RCTScrollViewComponentView.h   |  21 +++
 .../ScrollView/RCTScrollViewComponentView.mm  | 122 ++++++++++++++++++
 .../Text}/RCTParagraphComponentView.h         |   0
 .../Text}/RCTParagraphComponentView.mm        |   0
 .../View}/RCTViewComponentView.h              |   0
 .../View}/RCTViewComponentView.mm             |   0
 .../fabric/uimanager/FabricUIManager.cpp      |   3 +-
 ReactCommon/fabric/uimanager/Scheduler.cpp    |   8 +-
 .../fabric/view/ConcreteViewShadowNode.h      |   2 +-
 13 files changed, 187 insertions(+), 6 deletions(-)
 rename React/Fabric/Mounting/{ => ComponentViews/Root}/RCTRootComponentView.h (100%)
 rename React/Fabric/Mounting/{ => ComponentViews/Root}/RCTRootComponentView.mm (100%)
 create mode 100644 React/Fabric/Mounting/ComponentViews/ScrollView/RCTEnhancedScrollView.h
 create mode 100644 React/Fabric/Mounting/ComponentViews/ScrollView/RCTEnhancedScrollView.mm
 create mode 100644 React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.h
 create mode 100644 React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
 rename React/Fabric/Mounting/{ => ComponentViews/Text}/RCTParagraphComponentView.h (100%)
 rename React/Fabric/Mounting/{ => ComponentViews/Text}/RCTParagraphComponentView.mm (100%)
 rename React/Fabric/Mounting/{ => ComponentViews/View}/RCTViewComponentView.h (100%)
 rename React/Fabric/Mounting/{ => ComponentViews/View}/RCTViewComponentView.mm (100%)

diff --git a/React/Fabric/Mounting/RCTRootComponentView.h b/React/Fabric/Mounting/ComponentViews/Root/RCTRootComponentView.h
similarity index 100%
rename from React/Fabric/Mounting/RCTRootComponentView.h
rename to React/Fabric/Mounting/ComponentViews/Root/RCTRootComponentView.h
diff --git a/React/Fabric/Mounting/RCTRootComponentView.mm b/React/Fabric/Mounting/ComponentViews/Root/RCTRootComponentView.mm
similarity index 100%
rename from React/Fabric/Mounting/RCTRootComponentView.mm
rename to React/Fabric/Mounting/ComponentViews/Root/RCTRootComponentView.mm
diff --git a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTEnhancedScrollView.h b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTEnhancedScrollView.h
new file mode 100644
index 000000000000..0795a78991d1
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTEnhancedScrollView.h
@@ -0,0 +1,25 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTViewComponentView.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * `UIScrollView` subclass which has some improvements and tweeks
+ * wich are not directly related to React.
+ */
+@interface RCTEnhancedScrollView : UIScrollView
+
+@property (nonatomic, assign) BOOL pinchGestureEnabled;
+@property (nonatomic, assign) BOOL centerContent;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTEnhancedScrollView.mm b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTEnhancedScrollView.mm
new file mode 100644
index 000000000000..62ecd203d986
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTEnhancedScrollView.mm
@@ -0,0 +1,12 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTEnhancedScrollView.h"
+
+@implementation RCTEnhancedScrollView
+
+@end
diff --git a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.h b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.h
new file mode 100644
index 000000000000..b031d6d760b8
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.h
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTViewComponentView.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * UIView class for <ScrollView> component.
+ */
+@interface RCTScrollViewComponentView : RCTViewComponentView
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
new file mode 100644
index 000000000000..93ee34af86bb
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
@@ -0,0 +1,122 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTScrollViewComponentView.h"
+
+#import <React/RCTAssert.h>
+#import <fabric/graphics/Geometry.h>
+#import <fabric/scrollview/ScrollViewLocalData.h>
+#import <fabric/scrollview/ScrollViewProps.h>
+
+#import "RCTConversions.h"
+#import "RCTEnhancedScrollView.h"
+
+using namespace facebook::react;
+
+@interface RCTScrollViewComponentView () <UIScrollViewDelegate>
+
+@property (nonatomic, assign) CGFloat scrollEventThrottle;
+
+@end
+
+@implementation RCTScrollViewComponentView {
+  RCTEnhancedScrollView *_Nonnull _scrollView;
+  UIView *_Nonnull _contentView;
+  SharedScrollViewLocalData _scrollViewLocalData;
+}
+
+- (instancetype)initWithFrame:(CGRect)frame
+{
+  if (self = [super initWithFrame:frame]) {
+    _scrollView = [[RCTEnhancedScrollView alloc] initWithFrame:self.bounds];
+    _scrollView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
+    _scrollView.delegate = self;
+    _scrollView.delaysContentTouches = NO;
+    _contentView = [[UIView alloc] initWithFrame:_scrollView.bounds];
+    [_scrollView addSubview:_contentView];
+    [self addSubview:_scrollView];
+  }
+
+  return self;
+}
+
+- (void)updateProps:(SharedProps)props oldProps:(SharedProps)oldProps
+{
+  [super updateProps:props oldProps:oldProps];
+
+  if (!oldProps) {
+    oldProps = _props ?: std::make_shared<ScrollViewProps>();
+  }
+  _props = props;
+
+  auto oldScrollViewProps = *std::dynamic_pointer_cast<const ScrollViewProps>(oldProps);
+  auto newScrollViewProps = *std::dynamic_pointer_cast<const ScrollViewProps>(props);
+
+#define REMAP_PROP(reactName, localName, target) \
+  if (oldScrollViewProps.reactName != newScrollViewProps.reactName) { \
+    target.localName = newScrollViewProps.reactName; \
+  }
+
+#define REMAP_VIEW_PROP(reactName, localName) REMAP_PROP(reactName, localName, self)
+#define MAP_VIEW_PROP(name) REMAP_VIEW_PROP(name, name)
+#define REMAP_SCROLL_VIEW_PROP(reactName, localName) REMAP_PROP(reactName, localName, _scrollView)
+#define MAP_SCROLL_VIEW_PROP(name) REMAP_SCROLL_VIEW_PROP(name, name)
+
+  // FIXME: Commented props are not supported yet.
+  MAP_SCROLL_VIEW_PROP(alwaysBounceHorizontal);
+  MAP_SCROLL_VIEW_PROP(alwaysBounceVertical);
+  MAP_SCROLL_VIEW_PROP(bounces);
+  MAP_SCROLL_VIEW_PROP(bouncesZoom);
+  MAP_SCROLL_VIEW_PROP(canCancelContentTouches);
+  MAP_SCROLL_VIEW_PROP(centerContent);
+  //MAP_SCROLL_VIEW_PROP(automaticallyAdjustContentInsets);
+  MAP_SCROLL_VIEW_PROP(decelerationRate);
+  MAP_SCROLL_VIEW_PROP(directionalLockEnabled);
+  //MAP_SCROLL_VIEW_PROP(indicatorStyle);
+  //MAP_SCROLL_VIEW_PROP(keyboardDismissMode);
+  MAP_SCROLL_VIEW_PROP(maximumZoomScale);
+  MAP_SCROLL_VIEW_PROP(minimumZoomScale);
+  MAP_SCROLL_VIEW_PROP(scrollEnabled);
+  MAP_SCROLL_VIEW_PROP(pagingEnabled);
+  MAP_SCROLL_VIEW_PROP(pinchGestureEnabled);
+  MAP_SCROLL_VIEW_PROP(scrollsToTop);
+  MAP_SCROLL_VIEW_PROP(showsHorizontalScrollIndicator);
+  MAP_SCROLL_VIEW_PROP(showsVerticalScrollIndicator);
+  MAP_VIEW_PROP(scrollEventThrottle);
+  MAP_SCROLL_VIEW_PROP(zoomScale);
+  //MAP_SCROLL_VIEW_PROP(contentInset);
+  //MAP_SCROLL_VIEW_PROP(scrollIndicatorInsets);
+  //MAP_SCROLL_VIEW_PROP(snapToInterval);
+  //MAP_SCROLL_VIEW_PROP(snapToAlignment);
+}
+
+- (void)updateLocalData:(SharedLocalData)localData
+           oldLocalData:(SharedLocalData)oldLocalData
+{
+  assert(std::dynamic_pointer_cast<const ScrollViewLocalData>(localData));
+  _scrollViewLocalData = std::static_pointer_cast<const ScrollViewLocalData>(localData);
+  CGSize contentSize = RCTCGSizeFromSize(_scrollViewLocalData->getContentSize());
+  _contentView.frame = CGRect {CGPointZero, contentSize};
+  _scrollView.contentSize = contentSize;
+}
+
+#pragma mark - ComponentViewProtocol
+
+- (void)mountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
+                          index:(NSInteger)index
+{
+  [_contentView insertSubview:childComponentView atIndex:index];
+}
+
+- (void)unmountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
+                            index:(NSInteger)index
+{
+  RCTAssert(childComponentView.superview == _contentView, @"Attempt to unmount improperly mounted component view.");
+  [childComponentView removeFromSuperview];
+}
+
+@end
diff --git a/React/Fabric/Mounting/RCTParagraphComponentView.h b/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.h
similarity index 100%
rename from React/Fabric/Mounting/RCTParagraphComponentView.h
rename to React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.h
diff --git a/React/Fabric/Mounting/RCTParagraphComponentView.mm b/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm
similarity index 100%
rename from React/Fabric/Mounting/RCTParagraphComponentView.mm
rename to React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm
diff --git a/React/Fabric/Mounting/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
similarity index 100%
rename from React/Fabric/Mounting/RCTViewComponentView.h
rename to React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
diff --git a/React/Fabric/Mounting/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
similarity index 100%
rename from React/Fabric/Mounting/RCTViewComponentView.mm
rename to React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 9099374b8fc8..da5af6f7af04 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -63,8 +63,7 @@ static const std::string componentNameByReactViewName(std::string viewName) {
   // We need this temporarly for testing purposes until we have proper
   // implementation of <ScrollView> component.
   if (
-    viewName == "ScrollContentView" ||
-    viewName == "ScrollView"
+    viewName == "ScrollContentView"
   ) {
     return "View";
   }
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index f4ffe53a3b11..5f43929aa74c 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -3,11 +3,12 @@
 #include "Scheduler.h"
 
 #include <fabric/core/LayoutContext.h>
-#include <fabric/uimanager/ComponentDescriptorRegistry.h>
-#include <fabric/uimanager/FabricUIManager.h>
+#include <fabric/scrollview/ScrollViewComponentDescriptor.h>
 #include <fabric/text/ParagraphComponentDescriptor.h>
-#include <fabric/text/TextComponentDescriptor.h>
 #include <fabric/text/RawTextComponentDescriptor.h>
+#include <fabric/text/TextComponentDescriptor.h>
+#include <fabric/uimanager/ComponentDescriptorRegistry.h>
+#include <fabric/uimanager/FabricUIManager.h>
 #include <fabric/view/ViewComponentDescriptor.h>
 #include <fabric/view/ViewProps.h>
 #include <fabric/view/ViewShadowNode.h>
@@ -20,6 +21,7 @@ namespace react {
 Scheduler::Scheduler() {
   auto componentDescriptorRegistry = std::make_shared<ComponentDescriptorRegistry>();
   componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ViewComponentDescriptor>());
+  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ScrollViewComponentDescriptor>());
   componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ParagraphComponentDescriptor>());
   componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<TextComponentDescriptor>());
   componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<RawTextComponentDescriptor>());
diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
index 02ee969427f1..345e3fc4693d 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -143,7 +143,7 @@ class ConcreteViewShadowNode:
     return list;
   }
 
-private:
+protected:
 
 #pragma mark - LayoutableShadowNode
 

From 8f507280acfa09340364c24bd5f445464b0d1b86 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 17 May 2018 20:03:42 -0700
Subject: [PATCH 0613/1109] Fabric: Removing default arguments from
 ShadowNode's constructors

Summary: We don't use them at all; moreover they complicate adding/changing signatures of those methods (because arguments with defaults must be grouped at the end and some arguments cannot have defaults).

Reviewed By: fkgozali

Differential Revision: D7981456

fbshipit-source-id: d7dd098e83630d1ab3342d2ca52ade9c4e27b2c3
---
 .../core/shadownode/ConcreteShadowNode.h      | 11 +++---
 .../fabric/core/shadownode/ShadowNode.h       | 10 +++---
 .../fabric/core/tests/ShadowNodeTest.cpp      | 35 ++++++++++---------
 ReactCommon/fabric/uimanager/ShadowTree.cpp   |  4 ++-
 .../fabric/view/ConcreteViewShadowNode.h      | 10 +++---
 5 files changed, 36 insertions(+), 34 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index 93663a325a53..6cf911ea1328 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -41,9 +41,9 @@ class ConcreteShadowNode: public ShadowNode {
     const Tag &tag,
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
-    const SharedConcreteProps &props = ConcreteShadowNode::defaultSharedProps(),
-    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList(),
-    const ShadowNodeCloneFunction &cloneFunction = nullptr
+    const SharedConcreteProps &props,
+    const SharedShadowNodeSharedList &children,
+    const ShadowNodeCloneFunction &cloneFunction
   ):
     ShadowNode(
       tag,
@@ -56,8 +56,8 @@ class ConcreteShadowNode: public ShadowNode {
 
   ConcreteShadowNode(
     const SharedConcreteShadowNode &shadowNode,
-    const SharedProps &props = nullptr,
-    const SharedShadowNodeSharedList &children = nullptr
+    const SharedProps &props,
+    const SharedShadowNodeSharedList &children
   ):
     ShadowNode(
       shadowNode,
@@ -73,7 +73,6 @@ class ConcreteShadowNode: public ShadowNode {
     assert(std::dynamic_pointer_cast<const PropsT>(props_));
     return std::static_pointer_cast<const PropsT>(props_);
   }
-
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index fec74d3ab9dd..927590b868e4 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -44,15 +44,15 @@ class ShadowNode:
     const Tag &tag,
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
-    const SharedProps &props = SharedProps(),
-    const SharedShadowNodeSharedList &children = SharedShadowNodeSharedList(),
-    const ShadowNodeCloneFunction &cloneFunction = nullptr
+    const SharedProps &props,
+    const SharedShadowNodeSharedList &children,
+    const ShadowNodeCloneFunction &cloneFunction
   );
 
   ShadowNode(
     const SharedShadowNode &shadowNode,
-    const SharedProps &props = nullptr,
-    const SharedShadowNodeSharedList &children = nullptr
+    const SharedProps &props,
+    const SharedShadowNodeSharedList &children
   );
 
   /*
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index 3395763d9e55..dfdf0dec4ae5 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -28,7 +28,7 @@ TEST(ShadowNodeTest, handleProps) {
 }
 
 TEST(ShadowNodeTest, handleShadowNodeCreation) {
-  auto node = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+  auto node = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, std::make_shared<const TestProps>(), ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
 
   ASSERT_FALSE(node->getSealed());
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
@@ -48,8 +48,8 @@ TEST(ShadowNodeTest, handleShadowNodeCreation) {
 }
 
 TEST(ShadowNodeTest, handleShadowNodeSimpleCloning) {
-  auto node = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
-  auto node2 = std::make_shared<TestShadowNode>(node);
+  auto node = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, std::make_shared<const TestProps>(), ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto node2 = std::make_shared<TestShadowNode>(node, nullptr, nullptr);
 
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
   ASSERT_EQ(node->getTag(), 9);
@@ -59,9 +59,10 @@ TEST(ShadowNodeTest, handleShadowNodeSimpleCloning) {
 }
 
 TEST(ShadowNodeTest, handleShadowNodeMutation) {
-  auto node1 = std::make_shared<TestShadowNode>(1, 1, (void *)NULL);
-  auto node2 = std::make_shared<TestShadowNode>(2, 1, (void *)NULL);
-  auto node3 = std::make_shared<TestShadowNode>(3, 1, (void *)NULL);
+  auto props = std::make_shared<const TestProps>();
+  auto node1 = std::make_shared<TestShadowNode>(1, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto node2 = std::make_shared<TestShadowNode>(2, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto node3 = std::make_shared<TestShadowNode>(3, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
 
   node1->appendChild(node2);
   node1->appendChild(node3);
@@ -70,7 +71,7 @@ TEST(ShadowNodeTest, handleShadowNodeMutation) {
   ASSERT_EQ(node1Children->at(0), node2);
   ASSERT_EQ(node1Children->at(1), node3);
 
-  auto node4 = std::make_shared<TestShadowNode>(node2);
+  auto node4 = std::make_shared<TestShadowNode>(node2, nullptr, nullptr);
   node1->replaceChild(node2, node4);
   node1Children = node1->getChildren();
   ASSERT_EQ(node1Children->size(), 2);
@@ -86,16 +87,16 @@ TEST(ShadowNodeTest, handleShadowNodeMutation) {
   // No more mutation after sealing.
   EXPECT_THROW(node4->clearSourceNode(), std::runtime_error);
 
-  auto node5 = std::make_shared<TestShadowNode>(node4);
+  auto node5 = std::make_shared<TestShadowNode>(node4, nullptr, nullptr);
   node5->clearSourceNode();
   ASSERT_EQ(node5->getSourceNode(), nullptr);
 }
 
 TEST(ShadowNodeTest, handleSourceNode) {
-  auto nodeFirstGeneration = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
-  auto nodeSecondGeneration = std::make_shared<TestShadowNode>(nodeFirstGeneration);
-  auto nodeThirdGeneration = std::make_shared<TestShadowNode>(nodeSecondGeneration);
-  auto nodeForthGeneration = std::make_shared<TestShadowNode>(nodeThirdGeneration);
+  auto nodeFirstGeneration = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, std::make_shared<const TestProps>(), ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto nodeSecondGeneration = std::make_shared<TestShadowNode>(nodeFirstGeneration, nullptr, nullptr);
+  auto nodeThirdGeneration = std::make_shared<TestShadowNode>(nodeSecondGeneration, nullptr, nullptr);
+  auto nodeForthGeneration = std::make_shared<TestShadowNode>(nodeThirdGeneration, nullptr, nullptr);
 
   // Ensure established shource nodes structure.
   ASSERT_EQ(nodeForthGeneration->getSourceNode(), nodeThirdGeneration);
@@ -116,7 +117,7 @@ TEST(ShadowNodeTest, handleSourceNode) {
 }
 
 TEST(ShadowNodeTest, handleCloneFunction) {
-  auto firstNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+  auto firstNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, std::make_shared<const TestProps>(), ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
 
   // The shadow node is not clonable if `cloneFunction` is not provided,
   ASSERT_DEATH_IF_SUPPORTED(firstNode->clone(), "cloneFunction_");
@@ -159,10 +160,10 @@ TEST(ShadowNodeTest, handleLocalData) {
 
   auto localDataOver9000 = std::make_shared<TestLocalData>();
   localDataOver9000->setNumber(9001);
-
-  auto firstNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
-  auto secondNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
-  auto thirdNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL);
+  auto props = std::make_shared<const TestProps>();
+  auto firstNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto secondNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto thirdNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
 
   firstNode->setLocalData(localData42);
   secondNode->setLocalData(localData42);
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 30b246438649..c274d2e68520 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -19,7 +19,9 @@ ShadowTree::ShadowTree(Tag rootTag):
     rootTag,
     rootTag,
     nullptr,
-    RootShadowNode::defaultSharedProps()
+    RootShadowNode::defaultSharedProps(),
+    ShadowNode::emptySharedShadowNodeSharedList(),
+    nullptr
   );
 }
 
diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
index 345e3fc4693d..83149be3301a 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -43,9 +43,9 @@ class ConcreteViewShadowNode:
     const Tag &tag,
     const Tag &rootTag,
     const InstanceHandle &instanceHandle,
-    const SharedConcreteViewProps &props = ConcreteViewShadowNode::defaultSharedProps(),
-    const SharedShadowNodeSharedList &children = ShadowNode::emptySharedShadowNodeSharedList(),
-    const ShadowNodeCloneFunction &cloneFunction = nullptr
+    const SharedConcreteViewProps &props,
+    const SharedShadowNodeSharedList &children,
+    const ShadowNodeCloneFunction &cloneFunction
   ):
     ConcreteShadowNode<ViewPropsT>(
       tag,
@@ -65,8 +65,8 @@ class ConcreteViewShadowNode:
 
   ConcreteViewShadowNode(
     const SharedConcreteViewShadowNode &shadowNode,
-    const SharedConcreteViewProps &props = nullptr,
-    const SharedShadowNodeSharedList &children = nullptr
+    const SharedConcreteViewProps &props,
+    const SharedShadowNodeSharedList &children
   ):
     ConcreteShadowNode<ViewPropsT>(
       shadowNode,

From cc09d21e6047df8378ef3a7a209b68f8d63967a1 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 17 May 2018 20:03:46 -0700
Subject: [PATCH 0614/1109] Fabric: Simplifying usage of
 `ConcreteComponentDescriptor`

Summary:
Now ConcreteComponentDescriptor can infer `ComponentName` from `ShadowNodeT` automatically,
so in the most cases we even don't need to create a subclass of that.

Reviewed By: fkgozali

Differential Revision: D8016965

fbshipit-source-id: d910597093c9f4c9f32ca06cb3ef1b12538b9543
---
 .../ConcreteComponentDescriptor.h                 | 15 +++++++++++++++
 .../scrollview/ScrollViewComponentDescriptor.h    |  7 +------
 .../text/paragraph/ParagraphComponentDescriptor.h |  4 ----
 .../text/rawtext/RawTextComponentDescriptor.h     | 10 +---------
 .../fabric/text/text/TextComponentDescriptor.h    |  8 +-------
 ReactCommon/fabric/view/ViewComponentDescriptor.h |  7 +------
 6 files changed, 19 insertions(+), 32 deletions(-)

diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index f690cb652f7b..3d2721f81563 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -35,6 +35,21 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     return typeid(ShadowNodeT).hash_code();
   }
 
+  ComponentName getComponentName() const override {
+    // Even if this looks suboptimal, it is the only way to call
+    // a virtual non-static method of `ShadowNodeT`.
+    // Because it is not a hot path (it is executed once per an app run),
+    // it's fine.
+    return std::make_shared<ShadowNodeT>(
+      0,
+      0,
+      nullptr,
+      std::make_shared<const ConcreteProps>(),
+      ShadowNode::emptySharedShadowNodeSharedList(),
+      nullptr
+    )->ShadowNodeT::getComponentName();
+  }
+
   SharedShadowNode createShadowNode(
     const Tag &tag,
     const Tag &rootTag,
diff --git a/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h b/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h
index 44d61202ebf4..b1c075980ff6 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h
+++ b/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h
@@ -13,12 +13,7 @@
 namespace facebook {
 namespace react {
 
-class ScrollViewComponentDescriptor final: public ConcreteComponentDescriptor<ScrollViewShadowNode> {
-public:
-  ComponentName getComponentName() const override {
-    return "ScrollView";
-  }
-};
+using ScrollViewComponentDescriptor = ConcreteComponentDescriptor<ScrollViewShadowNode>;
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h b/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
index d77676783006..6648ddb5e142 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
+++ b/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
@@ -27,10 +27,6 @@ class ParagraphComponentDescriptor: public ConcreteComponentDescriptor<Paragraph
     textLayoutManager_ = std::make_shared<TextLayoutManager>();
   }
 
-  ComponentName getComponentName() const override {
-    return "Paragraph";
-  }
-
   void adopt(UnsharedShadowNode shadowNode) const override {
     ConcreteComponentDescriptor<ParagraphShadowNode>::adopt(shadowNode);
 
diff --git a/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h b/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h
index 6f615fa3c620..ca2ccdbe1cf9 100644
--- a/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h
+++ b/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h
@@ -13,15 +13,7 @@
 namespace facebook {
 namespace react {
 
-/*
- * Descriptor for <RawText> component.
- */
-class RawTextComponentDescriptor: public ConcreteComponentDescriptor<RawTextShadowNode> {
-public:
-  ComponentName getComponentName() const override {
-    return "RawText";
-  }
-};
+using RawTextComponentDescriptor = ConcreteComponentDescriptor<RawTextShadowNode>;
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/text/text/TextComponentDescriptor.h b/ReactCommon/fabric/text/text/TextComponentDescriptor.h
index 043492f21e91..5abb428e33de 100644
--- a/ReactCommon/fabric/text/text/TextComponentDescriptor.h
+++ b/ReactCommon/fabric/text/text/TextComponentDescriptor.h
@@ -8,18 +8,12 @@
 #pragma once
 
 #include <fabric/core/ConcreteComponentDescriptor.h>
-#include <fabric/text/TextProps.h>
 #include <fabric/text/TextShadowNode.h>
 
 namespace facebook {
 namespace react {
 
-class TextComponentDescriptor: public ConcreteComponentDescriptor<TextShadowNode> {
-public:
-  ComponentName getComponentName() const override {
-    return "Text";
-  }
-};
+using TextComponentDescriptor = ConcreteComponentDescriptor<TextShadowNode>;
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewComponentDescriptor.h b/ReactCommon/fabric/view/ViewComponentDescriptor.h
index 1db26dc3b5b7..4c25d8b943b6 100644
--- a/ReactCommon/fabric/view/ViewComponentDescriptor.h
+++ b/ReactCommon/fabric/view/ViewComponentDescriptor.h
@@ -13,12 +13,7 @@
 namespace facebook {
 namespace react {
 
-class ViewComponentDescriptor: public ConcreteComponentDescriptor<ViewShadowNode> {
-public:
-  ComponentName getComponentName() const override {
-    return "View";
-  }
-};
+using ViewComponentDescriptor = ConcreteComponentDescriptor<ViewShadowNode>;
 
 } // namespace react
 } // namespace facebook

From 129690fad1173e10fa0000942480e8261d0d3978 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Thu, 17 May 2018 20:06:40 -0700
Subject: [PATCH 0615/1109] Migrate to new GitHub issue templates

Summary:
This will allow us to present a user with a different template depending on the type of help they need.

To do:

1. Update the bot so that it auto-closes any issue that contains text from `question.md` (i.e. tried to ask a question through GitHub).
2. In a separate PR: new template to handle feature requests (update the bot to allow these to remain open)
3. Allow multiple other types of issues, such as requesting a cherry pick, or reporting a regression vs. something that does not work as expected.
4. Link to Stack Overflow / Discuss directly if and when GitHub allows the 'Get Started' button to point to a URL.
Closes https://github.com/facebook/react-native/pull/19334

Differential Revision: D8051229

Pulled By: hramos

fbshipit-source-id: 9e8aea232688c53dcbb0c047e92799e68b8b7842
---
 .../bug_report.md}                            | 10 +++++++--
 .github/ISSUE_TEMPLATE/question.md            | 21 +++++++++++++++++++
 2 files changed, 29 insertions(+), 2 deletions(-)
 rename .github/{ISSUE_TEMPLATE.md => ISSUE_TEMPLATE/bug_report.md} (90%)
 create mode 100644 .github/ISSUE_TEMPLATE/question.md

diff --git a/.github/ISSUE_TEMPLATE.md b/.github/ISSUE_TEMPLATE/bug_report.md
similarity index 90%
rename from .github/ISSUE_TEMPLATE.md
rename to .github/ISSUE_TEMPLATE/bug_report.md
index 46d7bb4760de..3c4f6e2f67d8 100644
--- a/.github/ISSUE_TEMPLATE.md
+++ b/.github/ISSUE_TEMPLATE/bug_report.md
@@ -1,3 +1,9 @@
+---
+name: 🐛 Bug Report
+about: Something is not working as expected.
+
+---
+
 <!--
   We use GitHub Issues exclusively for tracking bugs in React Native.
   Questions? Visit http://facebook.github.io/react-native/help.html
@@ -15,8 +21,8 @@
 <!-- Required. Run `react-native info` in your terminal and paste its contents here. -->
 
 ## Steps to Reproduce
-<!-- 
-  Required. Let us know how to reproduce the issue. Include a code sample, share a project, 
+<!--
+  Required. Let us know how to reproduce the issue. Include a code sample, share a project,
   or share an app that reproduces the issue using [Snack](https://snack.expo.io/).
 -->
 
diff --git a/.github/ISSUE_TEMPLATE/question.md b/.github/ISSUE_TEMPLATE/question.md
new file mode 100644
index 000000000000..503775b920d0
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/question.md
@@ -0,0 +1,21 @@
+---
+name: 💬 Question
+about: For questions about using React Native in your app.
+
+---
+
+--------------^ Click "Preview" for a nicer view!
+
+We use GitHub Issues exclusively for tracking bugs in React Native. If you need help with your React Native app, the right place to go depends on the type of help that you need.
+
+### Stack Overflow
+
+Many members of the community use Stack Overflow to ask questions. Read through the [existing questions](http://stackoverflow.com/questions/tagged/react-native?sort=frequent) tagged with **react-native** or [ask your own](http://stackoverflow.com/questions/ask?tags=react-native)!
+
+### Discussion Forum
+
+For longer-form conversations about React Native, we’ve set up a [discussion forum at **discuss.reactjs.org**](https://discuss.reactjs.org/t/welcome-react-native-community-group/10239). This forum is a great place for discussion about best practices and application architecture as well as the future of React Native. If you have an answerable code-level question, please post it to [Stack Overflow](http://stackoverflow.com/questions/ask?tags=react-native) instead.
+
+### Reactiflux Chat
+
+If you need an answer right away, check out the [Reactiflux Discord](https://discord.gg/0ZcbPKXt5bZjGY5n) community. There are usually a number of React Native experts there who can help out or point you to somewhere you might want to look.

From fbd1beaf666be9c09a380784f8c0cd34ba083a6b Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Fri, 18 May 2018 05:57:30 -0700
Subject: [PATCH 0616/1109] Add automated script to update the babelHelpers
 file

Reviewed By: cpojer

Differential Revision: D8025371

fbshipit-source-id: 4811f16d882196bc32be7471b6a3ab4d834651c2
---
 Libraries/polyfills/babelHelpers.js | 278 +++++++++++++++++++---------
 1 file changed, 192 insertions(+), 86 deletions(-)

diff --git a/Libraries/polyfills/babelHelpers.js b/Libraries/polyfills/babelHelpers.js
index 28c007f7633a..9453b150cfb7 100644
--- a/Libraries/polyfills/babelHelpers.js
+++ b/Libraries/polyfills/babelHelpers.js
@@ -4,64 +4,78 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * Regenerate through
+ *    `js1 upgrade babel-helpers` + manual tweaks
+ *
+ * Components used for this file;
+ *   - assertThisInitialized
+ *   - classCallCheck
+ *   - createClass
+ *   - defineProperty
+ *   - extends
+ *   - get
+ *   - inherits
+ *   - interopRequireDefault
+ *   - interopRequireWildcard
+ *   - objectWithoutProperties
+ *   - possibleConstructorReturn
+ *   - slicedToArray
+ *   - taggedTemplateLiteral
+ *   - taggedTemplateLiteralLoose
+ *   - toArray
+ *   - toConsumableArray
+ *   - wrapNativeSuper
+ *
+ * @flow
+ * @generated (with babel 7.0.0-beta.40)
  * @format
- * @polyfill
  * @nolint
+ * @polyfill
  */
 
-/* eslint-disable quotes, curly, no-proto, no-undef-init, dot-notation */
-
-// Created by running:
-// require('fs').writeFileSync('babelExternalHelpers.js', require('@babel/core').buildExternalHelpers('_extends classCallCheck createClass createRawReactElement defineProperty get inherits  interopRequireDefault interopRequireWildcard objectWithoutProperties possibleConstructorReturn slicedToArray taggedTemplateLiteral toArray toConsumableArray wrapNativeSuper assertThisInitialized taggedTemplateLiteralLoose'.split(' ')))// then replacing the `global` reference in the last line to also use `this`.
-//
-// Actually, that's a lie, because babel omits _extends and
-// createRawReactElement. the file is also cleaned up a bit.
-// You may need to clear wrapNativeSuper while the bug hasn't been fixed yet.
-// Do try to keep diffs to a minimum.
+'use strict';
 
 var babelHelpers = (global.babelHelpers = {});
 
-babelHelpers.createRawReactElement = (function() {
-  var REACT_ELEMENT_TYPE =
-    (typeof Symbol === 'function' &&
-      Symbol.for &&
-      Symbol.for('react.element')) ||
-    0xeac7;
-  return function createRawReactElement(type, key, props) {
-    return {
-      $$typeof: REACT_ELEMENT_TYPE,
-      type: type,
-      key: key,
-      ref: null,
-      props: props,
-      _owner: null,
-    };
-  };
-})();
+// ### classCallCheck ###
 
-babelHelpers.classCallCheck = function(instance, Constructor) {
+function _classCallCheck(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
     throw new TypeError('Cannot call a class as a function');
   }
-};
+}
+
+babelHelpers.classCallCheck = _classCallCheck;
+
+// ### createClass ###
 
 function _defineProperties(target, props) {
   for (var i = 0; i < props.length; i++) {
     var descriptor = props[i];
     descriptor.enumerable = descriptor.enumerable || false;
     descriptor.configurable = true;
-    if ('value' in descriptor) descriptor.writable = true;
+    if ('value' in descriptor) {
+      descriptor.writable = true;
+    }
     Object.defineProperty(target, descriptor.key, descriptor);
   }
 }
 
-babelHelpers.createClass = function(Constructor, protoProps, staticProps) {
-  if (protoProps) _defineProperties(Constructor.prototype, protoProps);
-  if (staticProps) _defineProperties(Constructor, staticProps);
+function _createClass(Constructor, protoProps, staticProps) {
+  if (protoProps) {
+    _defineProperties(Constructor.prototype, protoProps);
+  }
+  if (staticProps) {
+    _defineProperties(Constructor, staticProps);
+  }
   return Constructor;
-};
+}
 
-babelHelpers.defineProperty = function(obj, key, value) {
+babelHelpers.createClass = _createClass;
+
+// ### defineProperty ###
+
+function _defineProperty(obj, key, value) {
   if (key in obj) {
     Object.defineProperty(obj, key, {
       value: value,
@@ -74,26 +88,40 @@ babelHelpers.defineProperty = function(obj, key, value) {
   }
 
   return obj;
-};
+}
 
-babelHelpers._extends = babelHelpers.extends =
-  Object.assign ||
-  function(target) {
-    for (var i = 1; i < arguments.length; i++) {
-      var source = arguments[i];
+babelHelpers.defineProperty = _defineProperty;
 
-      for (var key in source) {
-        if (Object.prototype.hasOwnProperty.call(source, key)) {
-          target[key] = source[key];
+// ### extends ###
+
+function _extends() {
+  babelHelpers.extends = _extends =
+    Object.assign ||
+    function(target) {
+      for (var i = 1; i < arguments.length; i++) {
+        var source = arguments[i];
+
+        for (var key in source) {
+          if (Object.prototype.hasOwnProperty.call(source, key)) {
+            target[key] = source[key];
+          }
         }
       }
-    }
 
-    return target;
-  };
+      return target;
+    };
+
+  return _extends.apply(this, arguments);
+}
 
-babelHelpers.get = function get(object, property, receiver) {
-  if (object === null) object = Function.prototype;
+babelHelpers.extends = _extends;
+
+// ### get ###
+
+function _get(object, property, receiver) {
+  if (object === null) {
+    object = Function.prototype;
+  }
   var desc = Object.getOwnPropertyDescriptor(object, property);
 
   if (desc === undefined) {
@@ -102,7 +130,7 @@ babelHelpers.get = function get(object, property, receiver) {
     if (parent === null) {
       return undefined;
     } else {
-      return get(parent, property, receiver);
+      return _get(parent, property, receiver);
     }
   } else if ('value' in desc) {
     return desc.value;
@@ -115,12 +143,17 @@ babelHelpers.get = function get(object, property, receiver) {
 
     return getter.call(receiver);
   }
-};
+}
+
+babelHelpers.get = _get;
+
+// ### inherits ###
 
-babelHelpers.inherits = function(subClass, superClass) {
+function _inherits(subClass, superClass) {
   if (typeof superClass !== 'function' && superClass !== null) {
     throw new TypeError('Super expression must either be null or a function');
   }
+
   subClass.prototype = Object.create(superClass && superClass.prototype, {
     constructor: {
       value: subClass,
@@ -129,24 +162,32 @@ babelHelpers.inherits = function(subClass, superClass) {
       configurable: true,
     },
   });
-  if (superClass)
+  if (superClass) {
     Object.setPrototypeOf
       ? Object.setPrototypeOf(subClass, superClass)
       : (subClass.__proto__ = superClass);
-};
+  }
+}
+
+babelHelpers.inherits = _inherits;
+
+// ### wrapNativeSuper ###
 
 var _gPO =
   Object.getPrototypeOf ||
   function _gPO(o) {
     return o.__proto__;
   };
+
 var _sPO =
   Object.setPrototypeOf ||
   function _sPO(o, p) {
     o.__proto__ = p;
     return o;
   };
+
 var _construct =
+  // FB:
   // TODO: prepack does not like this line (and we can use the fallback just fine)
   // (typeof Reflect === "object" && Reflect.construct) ||
   function _construct(Parent, args, Class) {
@@ -156,24 +197,32 @@ var _construct =
     Constructor = Parent.bind.apply(Parent, a);
     return _sPO(new Constructor(), Class.prototype);
   };
+
 var _cache = typeof Map === 'function' && new Map();
-babelHelpers.wrapNativeSuper = function(Class) {
+
+function _wrapNativeSuper(Class) {
   // FB:
   // Note: while extending native classes is pretty meh we do have cases, for
   // example; Error. There is also a false positive, for example; Blob.
-
   if (typeof Class !== 'function') {
     throw new TypeError('Super expression must either be null or a function');
   }
+
   if (typeof _cache !== 'undefined') {
-    if (_cache.has(Class)) return _cache.get(Class);
+    if (_cache.has(Class)) {
+      return _cache.get(Class);
+    }
+
     _cache.set(Class, Wrapper);
   }
+
   function Wrapper() {
+    // FB:
     // this is a temporary fix for a babel bug (it's invoking the wrong func
     // when you do `super()`)
     return _construct(Class, arguments, _gPO(this).constructor);
   }
+
   Wrapper.prototype = Object.create(Class.prototype, {
     constructor: {
       value: Wrapper,
@@ -188,17 +237,25 @@ babelHelpers.wrapNativeSuper = function(Class) {
       return _construct(Class, arguments, _gPO(this).constructor);
     }, Class),
   );
-};
+}
+
+babelHelpers.wrapNativeSuper = _wrapNativeSuper;
+
+// ### interopRequireDefault ###
 
-babelHelpers.interopRequireDefault = function(obj) {
+function _interopRequireDefault(obj) {
   return obj && obj.__esModule
     ? obj
     : {
         default: obj,
       };
-};
+}
+
+babelHelpers.interopRequireDefault = _interopRequireDefault;
+
+// ### interopRequireWildcard ###
 
-babelHelpers.interopRequireWildcard = function(obj) {
+function _interopRequireWildcard(obj) {
   if (obj && obj.__esModule) {
     return obj;
   } else {
@@ -224,17 +281,25 @@ babelHelpers.interopRequireWildcard = function(obj) {
     newObj.default = obj;
     return newObj;
   }
-};
+}
+
+babelHelpers.interopRequireWildcard = _interopRequireWildcard;
 
-babelHelpers.objectWithoutProperties = function(source, excluded) {
-  if (source == null) return {};
+// ### objectWithoutProperties ###
+
+function _objectWithoutProperties(source, excluded) {
+  if (source == null) {
+    return {};
+  }
   var target = {};
   var sourceKeys = Object.keys(source);
   var key, i;
 
   for (i = 0; i < sourceKeys.length; i++) {
     key = sourceKeys[i];
-    if (excluded.indexOf(key) >= 0) continue;
+    if (excluded.indexOf(key) >= 0) {
+      continue;
+    }
     target[key] = source[key];
   }
 
@@ -243,16 +308,24 @@ babelHelpers.objectWithoutProperties = function(source, excluded) {
 
     for (i = 0; i < sourceSymbolKeys.length; i++) {
       key = sourceSymbolKeys[i];
-      if (excluded.indexOf(key) >= 0) continue;
-      if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue;
+      if (excluded.indexOf(key) >= 0) {
+        continue;
+      }
+      if (!Object.prototype.propertyIsEnumerable.call(source, key)) {
+        continue;
+      }
       target[key] = source[key];
     }
   }
 
   return target;
-};
+}
 
-babelHelpers.possibleConstructorReturn = function(self, call) {
+babelHelpers.objectWithoutProperties = _objectWithoutProperties;
+
+// ### possibleConstructorReturn ###
+
+function _possibleConstructorReturn(self, call) {
   if (call && (typeof call === 'object' || typeof call === 'function')) {
     return call;
   }
@@ -264,7 +337,11 @@ babelHelpers.possibleConstructorReturn = function(self, call) {
   }
 
   return self;
-};
+}
+
+babelHelpers.possibleConstructorReturn = _possibleConstructorReturn;
+
+// ### slicedToArray ###
 
 function _sliceIterator(arr, i) {
   var _arr = [];
@@ -280,23 +357,29 @@ function _sliceIterator(arr, i) {
     ) {
       _arr.push(_s.value);
 
-      if (i && _arr.length === i) break;
+      if (i && _arr.length === i) {
+        break;
+      }
     }
   } catch (err) {
     _d = true;
     _e = err;
   } finally {
     try {
-      if (!_n && _i['return'] != null) _i['return']();
+      if (!_n && _i.return != null) {
+        _i.return();
+      }
     } finally {
-      if (_d) throw _e;
+      if (_d) {
+        throw _e;
+      }
     }
   }
 
   return _arr;
 }
 
-babelHelpers.slicedToArray = function(arr, i) {
+function _slicedToArray(arr, i) {
   if (Array.isArray(arr)) {
     return arr;
   } else if (Symbol.iterator in Object(arr)) {
@@ -304,9 +387,13 @@ babelHelpers.slicedToArray = function(arr, i) {
   } else {
     throw new TypeError('Invalid attempt to destructure non-iterable instance');
   }
-};
+}
+
+babelHelpers.slicedToArray = _slicedToArray;
+
+// ### taggedTemplateLiteral ###
 
-babelHelpers.taggedTemplateLiteral = function(strings, raw) {
+function _taggedTemplateLiteral(strings, raw) {
   return Object.freeze(
     Object.defineProperties(strings, {
       raw: {
@@ -314,24 +401,37 @@ babelHelpers.taggedTemplateLiteral = function(strings, raw) {
       },
     }),
   );
-};
+}
+
+babelHelpers.taggedTemplateLiteral = _taggedTemplateLiteral;
+
+// ### toArray ###
 
-babelHelpers.toArray = function(arr) {
+function _toArray(arr) {
   return Array.isArray(arr) ? arr : Array.from(arr);
-};
+}
+
+babelHelpers.toArray = _toArray;
 
-babelHelpers.toConsumableArray = function(arr) {
+// ### toConsumableArray ###
+
+function _toConsumableArray(arr) {
   if (Array.isArray(arr)) {
-    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++)
+    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) {
       arr2[i] = arr[i];
+    }
 
     return arr2;
   } else {
     return Array.from(arr);
   }
-};
+}
+
+babelHelpers.toConsumableArray = _toConsumableArray;
+
+// ### assertThisInitialized ###
 
-babelHelpers.assertThisInitialized = function(self) {
+function _assertThisInitialized(self) {
   if (self === void 0) {
     throw new ReferenceError(
       "this hasn't been initialised - super() hasn't been called",
@@ -339,9 +439,15 @@ babelHelpers.assertThisInitialized = function(self) {
   }
 
   return self;
-};
+}
+
+babelHelpers.assertThisInitialized = _assertThisInitialized;
+
+// ### taggedTemplateLiteralLoose ###
 
-babelHelpers.taggedTemplateLiteralLoose = function(strings, raw) {
+function _taggedTemplateLiteralLoose(strings, raw) {
   strings.raw = raw;
   return strings;
-};
+}
+
+babelHelpers.taggedTemplateLiteralLoose = _taggedTemplateLiteralLoose;

From 67ec8498f7a5e9d5bad193d3e960d12d1cf8e5ba Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Fri, 18 May 2018 09:02:50 -0700
Subject: [PATCH 0617/1109] Bump rn babel preset to 5.0.1

Reviewed By: rafeca

Differential Revision: D8047460

fbshipit-source-id: b666266a5e9162383bc807d5bf2d7d3ffa7b19d6
---
 babel-preset/package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/babel-preset/package.json b/babel-preset/package.json
index b69d3d301cc8..e9169a8bfe8e 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -1,6 +1,6 @@
 {
   "name": "babel-preset-react-native",
-  "version": "5.0.0",
+  "version": "5.0.1",
   "description": "Babel preset for React Native applications",
   "main": "index.js",
   "repository": "https://github.com/facebook/react-native/tree/master/babel-preset",

From 0afc70b24a396b08568ff2140352346ba5052c85 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 18 May 2018 19:44:34 -0700
Subject: [PATCH 0618/1109] iOS: Introduced ComponentDescriptorFactory to
 provide app specific component registry

Summary: Each app has its own set of components to support, so this mechanism allows each of them to customize the set. Core library only provides the signature (.h file) without any impl.

Reviewed By: shergin

Differential Revision: D8065360

fbshipit-source-id: c123397afda678e84f1d1fa41a6393f25b2c15e1
---
 RNTester/Podfile                              |  1 +
 RNTester/Podfile.lock                         | 10 ++++--
 React.podspec                                 | 10 ++++++
 .../SampleComponentDescriptorFactor.cpp       | 23 ++++++++++++++
 .../uimanager/ComponentDescriptorFactory.h    | 31 +++++++++++++++++++
 ReactCommon/fabric/uimanager/Scheduler.cpp    |  9 ++----
 6 files changed, 75 insertions(+), 9 deletions(-)
 create mode 100644 ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
 create mode 100644 ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h

diff --git a/RNTester/Podfile b/RNTester/Podfile
index 155cec5aa04e..21f5e3b52c49 100644
--- a/RNTester/Podfile
+++ b/RNTester/Podfile
@@ -16,6 +16,7 @@ target 'RNTester' do
     'RCTBlob',
     'RCTCameraRoll',
     'RCTFabric',
+    'RCTFabricSample', # This is RNTesterPods specific sample.
     'RCTGeolocation',
     'RCTImage',
     'RCTLinkingIOS',
diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index 9afe598993e1..28e43f631bdc 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -27,6 +27,7 @@ PODS:
     - React/fabric/core (= 1000.0.0)
     - React/fabric/debug (= 1000.0.0)
     - React/fabric/graphics (= 1000.0.0)
+    - React/fabric/scrollview (= 1000.0.0)
     - React/fabric/text (= 1000.0.0)
     - React/fabric/textlayoutmanager (= 1000.0.0)
     - React/fabric/uimanager (= 1000.0.0)
@@ -39,6 +40,8 @@ PODS:
     - Folly (= 2016.10.31.00)
   - React/fabric/graphics (1000.0.0):
     - Folly (= 2016.10.31.00)
+  - React/fabric/scrollview (1000.0.0):
+    - Folly (= 2016.10.31.00)
   - React/fabric/text (1000.0.0):
     - Folly (= 2016.10.31.00)
   - React/fabric/textlayoutmanager (1000.0.0):
@@ -67,6 +70,8 @@ PODS:
     - Folly (= 2016.10.31.00)
     - React/Core
     - React/fabric
+  - React/RCTFabricSample (1000.0.0):
+    - Folly (= 2016.10.31.00)
   - React/RCTGeolocation (1000.0.0):
     - React/Core
   - React/RCTImage (1000.0.0):
@@ -103,6 +108,7 @@ DEPENDENCIES:
   - React/RCTBlob (from `../`)
   - React/RCTCameraRoll (from `../`)
   - React/RCTFabric (from `../`)
+  - React/RCTFabricSample (from `../`)
   - React/RCTGeolocation (from `../`)
   - React/RCTImage (from `../`)
   - React/RCTLinkingIOS (from `../`)
@@ -135,9 +141,9 @@ SPEC CHECKSUMS:
   DoubleConversion: e22e0762848812a87afd67ffda3998d9ef29170c
   Folly: 9a8eea4725a0b6ba3256ebf206c21e352c23abf8
   glog: 1de0bb937dccdc981596d3b5825ebfb765017ded
-  React: 3d56cdd885ecc0f2f3534b2f54a11cf9707229fb
+  React: 0a0271674c3a6772a89a6606f337ed8db583abc0
   yoga: bdd268c5812f00bdb52cc2b58f129797e97935eb
 
-PODFILE CHECKSUM: 1a96172007b66aa74825c234f17139dd9c3d3cd7
+PODFILE CHECKSUM: b28ea97efdc10f046a3a1b7b455c1e18a39cb10a
 
 COCOAPODS: 1.5.2
diff --git a/React.podspec b/React.podspec
index 094b5889aef6..470533c2c10c 100644
--- a/React.podspec
+++ b/React.podspec
@@ -218,6 +218,16 @@ Pod::Spec.new do |s|
     end
   end
 
+  # Fabric sample target for sample app purpose.
+  s.subspec "RCTFabricSample" do |ss|
+    ss.dependency             "Folly", folly_version
+    ss.compiler_flags       = folly_compiler_flags
+    ss.source_files         = "ReactCommon/fabric/sample/**/*.{cpp,h}"
+    ss.exclude_files        = "**/tests/*"
+    ss.header_dir           = "fabric/sample"
+    ss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+  end
+
   s.subspec "ART" do |ss|
     ss.dependency             "React/Core"
     ss.source_files         = "Libraries/ART/**/*.{h,m}"
diff --git a/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp b/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
new file mode 100644
index 000000000000..d45a37351fae
--- /dev/null
+++ b/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/uimanager/ComponentDescriptorFactory.h>
+#include <fabric/uimanager/ComponentDescriptorRegistry.h>
+
+namespace facebook {
+namespace react {
+
+/**
+ * This is a sample implementation. Each app should provide its own.
+ */
+SharedComponentDescriptorRegistry ComponentDescriptorFactory::buildRegistry() {
+  auto registry = std::make_shared<ComponentDescriptorRegistry>();
+  return registry;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h b/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
new file mode 100644
index 000000000000..c729c45f4b17
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
@@ -0,0 +1,31 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ComponentDescriptor.h>
+
+#include "ComponentDescriptorRegistry.h"
+
+namespace facebook {
+namespace react {
+
+/**
+ * A factory to provide hosting app specific set of ComponentDescriptor's.
+ * Each app must provide an implementation of the static class method which
+ * should register its specific set of supported components.
+ */
+class ComponentDescriptorFactory {
+
+public:
+  static SharedComponentDescriptorRegistry buildRegistry();
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index 5f43929aa74c..235206dbdc59 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -13,19 +13,14 @@
 #include <fabric/view/ViewProps.h>
 #include <fabric/view/ViewShadowNode.h>
 
+#include "ComponentDescriptorFactory.h"
 #include "Differentiator.h"
 
 namespace facebook {
 namespace react {
 
 Scheduler::Scheduler() {
-  auto componentDescriptorRegistry = std::make_shared<ComponentDescriptorRegistry>();
-  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ViewComponentDescriptor>());
-  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ScrollViewComponentDescriptor>());
-  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<ParagraphComponentDescriptor>());
-  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<TextComponentDescriptor>());
-  componentDescriptorRegistry->registerComponentDescriptor(std::make_shared<RawTextComponentDescriptor>());
-
+  auto componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry();
   uiManager_ = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
   uiManager_->setDelegate(this);
 }

From 17982094e58fcb5fe79e670dab1edd35e0fd1170 Mon Sep 17 00:00:00 2001
From: zhongwuzw <zhongwuzw@qq.com>
Date: Fri, 18 May 2018 20:07:40 -0700
Subject: [PATCH 0619/1109] Fix typo

Summary: Closes https://github.com/facebook/react-native/pull/19317

Differential Revision: D8061509

Pulled By: hramos

fbshipit-source-id: 4a2a066d477b090ee1568df234cfda67d5bbd0f8
---
 React/Base/RCTTouchHandler.m | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/Base/RCTTouchHandler.m b/React/Base/RCTTouchHandler.m
index 00c5af985916..5447a9a8a9f7 100644
--- a/React/Base/RCTTouchHandler.m
+++ b/React/Base/RCTTouchHandler.m
@@ -212,7 +212,7 @@ - (void)_updateAndDispatchTouches:(NSSet<UITouch *> *)touches
   BOOL canBeCoalesced = [eventName isEqualToString:@"touchMove"];
 
   // We increment `_coalescingKey` twice here just for sure that
-  // this `_coalescingKey` will not be reused by ahother (preceding or following) event
+  // this `_coalescingKey` will not be reused by another (preceding or following) event
   // (yes, even if coalescing only happens (and makes sense) on events of the same type).
 
   if (!canBeCoalesced) {

From f59e5a8d28491c64e4d0c08fec3a2b0b3fabb38b Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Fri, 18 May 2018 20:17:11 -0700
Subject: [PATCH 0620/1109] React sync for revisions de84d5c...c0fe8d6

Reviewed By: acdlite

Differential Revision: D8066469

fbshipit-source-id: e228df105c3d9a887793595073ebfe8a1a1d4f3d
---
 Libraries/Renderer/REVISION                   |   2 +-
 Libraries/Renderer/oss/ReactFabric-dev.js     | 472 ++++++++++++++----
 Libraries/Renderer/oss/ReactFabric-prod.js    | 262 ++++++++--
 .../Renderer/oss/ReactNativeRenderer-dev.js   | 218 ++++----
 .../Renderer/oss/ReactNativeRenderer-prod.js  |  91 ++--
 5 files changed, 738 insertions(+), 307 deletions(-)

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index 617cce49d160..06ec4e875f81 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-de84d5c1079b12455058ee177fb3ff97cc0fb8d0
\ No newline at end of file
+c0fe8d6f6942f5cbc93c09825e803ba8cf950522
\ No newline at end of file
diff --git a/Libraries/Renderer/oss/ReactFabric-dev.js b/Libraries/Renderer/oss/ReactFabric-dev.js
index eb3f3e078b39..3597c91b11f8 100644
--- a/Libraries/Renderer/oss/ReactFabric-dev.js
+++ b/Libraries/Renderer/oss/ReactFabric-dev.js
@@ -545,9 +545,53 @@ var validateEventDispatches = void 0;
   };
 }
 
+/**
+ * Dispatch the event to the listener.
+ * @param {SyntheticEvent} event SyntheticEvent to handle
+ * @param {boolean} simulated If the event is simulated (changes exn behavior)
+ * @param {function} listener Application-level callback
+ * @param {*} inst Internal component instance
+ */
+function executeDispatch(event, simulated, listener, inst) {
+  var type = event.type || "unknown-event";
+  event.currentTarget = getNodeFromInstance(inst);
+  ReactErrorUtils.invokeGuardedCallbackAndCatchFirstError(
+    type,
+    listener,
+    undefined,
+    event
+  );
+  event.currentTarget = null;
+}
+
 /**
  * Standard/simple iteration through an event's collected dispatches.
  */
+function executeDispatchesInOrder(event, simulated) {
+  var dispatchListeners = event._dispatchListeners;
+  var dispatchInstances = event._dispatchInstances;
+  {
+    validateEventDispatches(event);
+  }
+  if (Array.isArray(dispatchListeners)) {
+    for (var i = 0; i < dispatchListeners.length; i++) {
+      if (event.isPropagationStopped()) {
+        break;
+      }
+      // Listeners and Instances are two parallel arrays that are always in sync.
+      executeDispatch(
+        event,
+        simulated,
+        dispatchListeners[i],
+        dispatchInstances[i]
+      );
+    }
+  } else if (dispatchListeners) {
+    executeDispatch(event, simulated, dispatchListeners, dispatchInstances);
+  }
+  event._dispatchListeners = null;
+  event._dispatchInstances = null;
+}
 
 /**
  * Standard/simple iteration through an event's collected dispatches, but stops
@@ -686,6 +730,35 @@ function forEachAccumulated(arr, cb, scope) {
   }
 }
 
+/**
+ * Internal queue of events that have accumulated their dispatches and are
+ * waiting to have their dispatches executed.
+ */
+var eventQueue = null;
+
+/**
+ * Dispatches an event and releases it back into the pool, unless persistent.
+ *
+ * @param {?object} event Synthetic event to be dispatched.
+ * @param {boolean} simulated If the event is simulated (changes exn behavior)
+ * @private
+ */
+var executeDispatchesAndRelease = function(event, simulated) {
+  if (event) {
+    executeDispatchesInOrder(event, simulated);
+
+    if (!event.isPersistent()) {
+      event.constructor.release(event);
+    }
+  }
+};
+var executeDispatchesAndReleaseSimulated = function(e) {
+  return executeDispatchesAndRelease(e, true);
+};
+var executeDispatchesAndReleaseTopLevel = function(e) {
+  return executeDispatchesAndRelease(e, false);
+};
+
 function isInteractive(tag) {
   return (
     tag === "button" ||
@@ -785,6 +858,87 @@ function getListener(inst, registrationName) {
   return listener;
 }
 
+/**
+ * Allows registered plugins an opportunity to extract events from top-level
+ * native browser events.
+ *
+ * @return {*} An accumulation of synthetic events.
+ * @internal
+ */
+function extractEvents(
+  topLevelType,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  var events = null;
+  for (var i = 0; i < plugins.length; i++) {
+    // Not every plugin in the ordering may be loaded at runtime.
+    var possiblePlugin = plugins[i];
+    if (possiblePlugin) {
+      var extractedEvents = possiblePlugin.extractEvents(
+        topLevelType,
+        targetInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      if (extractedEvents) {
+        events = accumulateInto(events, extractedEvents);
+      }
+    }
+  }
+  return events;
+}
+
+function runEventsInBatch(events, simulated) {
+  if (events !== null) {
+    eventQueue = accumulateInto(eventQueue, events);
+  }
+
+  // Set `eventQueue` to null before processing it so that we can tell if more
+  // events get enqueued while processing.
+  var processingEventQueue = eventQueue;
+  eventQueue = null;
+
+  if (!processingEventQueue) {
+    return;
+  }
+
+  if (simulated) {
+    forEachAccumulated(
+      processingEventQueue,
+      executeDispatchesAndReleaseSimulated
+    );
+  } else {
+    forEachAccumulated(
+      processingEventQueue,
+      executeDispatchesAndReleaseTopLevel
+    );
+  }
+  invariant(
+    !eventQueue,
+    "processEventQueue(): Additional events were enqueued while processing " +
+      "an event queue. Support for this has not yet been implemented."
+  );
+  // This would be a good time to rethrow if any of the event handlers threw.
+  ReactErrorUtils.rethrowCaughtError();
+}
+
+function runExtractedEventsInBatch(
+  topLevelType,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  var events = extractEvents(
+    topLevelType,
+    targetInst,
+    nativeEvent,
+    nativeEventTarget
+  );
+  runEventsInBatch(events, false);
+}
+
 var IndeterminateComponent = 0; // Before we know whether it is functional or class
 var FunctionalComponent = 1;
 var ClassComponent = 2;
@@ -2331,7 +2485,7 @@ var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
   ? Symbol.for("react.strict_mode")
   : 0xeacc;
-var REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profile_root") : 0xeacc;
+var REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profiler") : 0xead2;
 var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 0xeacd;
 var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 0xeace;
 var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 0xeacf;
@@ -2375,6 +2529,56 @@ function createPortal(
   };
 }
 
+// Use to restore controlled state after a change event has fired.
+
+var fiberHostComponent = null;
+
+var restoreTarget = null;
+var restoreQueue = null;
+
+function restoreStateOfTarget(target) {
+  // We perform this translation at the end of the event loop so that we
+  // always receive the correct fiber here
+  var internalInstance = getInstanceFromNode(target);
+  if (!internalInstance) {
+    // Unmounted
+    return;
+  }
+  invariant(
+    fiberHostComponent &&
+      typeof fiberHostComponent.restoreControlledState === "function",
+    "Fiber needs to be injected to handle a fiber target for controlled " +
+      "events. This error is likely caused by a bug in React. Please file an issue."
+  );
+  var props = getFiberCurrentPropsFromNode(internalInstance.stateNode);
+  fiberHostComponent.restoreControlledState(
+    internalInstance.stateNode,
+    internalInstance.type,
+    props
+  );
+}
+
+function needsStateRestore() {
+  return restoreTarget !== null || restoreQueue !== null;
+}
+
+function restoreStateIfNeeded() {
+  if (!restoreTarget) {
+    return;
+  }
+  var target = restoreTarget;
+  var queuedTargets = restoreQueue;
+  restoreTarget = null;
+  restoreQueue = null;
+
+  restoreStateOfTarget(target);
+  if (queuedTargets) {
+    for (var i = 0; i < queuedTargets.length; i++) {
+      restoreStateOfTarget(queuedTargets[i]);
+    }
+  }
+}
+
 // Used as a way to call batchedUpdates when we don't have a reference to
 // the renderer. Such as when we're dispatching events or if third party
 // libraries need to call batchedUpdates. Eventually, this API will go away when
@@ -2390,6 +2594,33 @@ var _interactiveUpdates = function(fn, a, b) {
 };
 var _flushInteractiveUpdates = function() {};
 
+var isBatching = false;
+function batchedUpdates(fn, bookkeeping) {
+  if (isBatching) {
+    // If we are currently inside another batch, we need to wait until it
+    // fully completes before restoring state.
+    return fn(bookkeeping);
+  }
+  isBatching = true;
+  try {
+    return _batchedUpdates(fn, bookkeeping);
+  } finally {
+    // Here we wait until all updates have propagated, which is important
+    // when using controlled components within layers:
+    // https://github.com/facebook/react/issues/1698
+    // Then we restore state of any controlled component.
+    isBatching = false;
+    var controlledComponentsHavePendingUpdates = needsStateRestore();
+    if (controlledComponentsHavePendingUpdates) {
+      // If a controlled event was fired, we may need to restore the state of
+      // the DOM node back to the controlled value. This is necessary when React
+      // bails out of the update without touching the DOM.
+      _flushInteractiveUpdates();
+      restoreStateIfNeeded();
+    }
+  }
+}
+
 var injection$2 = {
   injectRenderer: function(renderer) {
     _batchedUpdates = renderer.batchedUpdates;
@@ -3914,42 +4145,9 @@ function createFiberFromElement(element, mode, expirationTime) {
         // mode compatible.
         mode |= StrictMode;
         break;
-      default: {
-        if (typeof type === "object" && type !== null) {
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = ContextProvider;
-              break;
-            case REACT_CONTEXT_TYPE:
-              // This is a consumer
-              fiberTag = ContextConsumer;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = ForwardRef;
-              break;
-            default:
-              if (typeof type.tag === "number") {
-                // Currently assumed to be a continuation and therefore is a
-                // fiber already.
-                // TODO: The yield system is currently broken for updates in
-                // some cases. The reified yield stores a fiber, but we don't
-                // know which fiber that is; the current or a workInProgress?
-                // When the continuation gets rendered here we don't know if we
-                // can reuse that fiber or if we need to clone it. There is
-                // probably a clever way to restructure this.
-                fiber = type;
-                fiber.pendingProps = pendingProps;
-                fiber.expirationTime = expirationTime;
-                return fiber;
-              } else {
-                throwOnInvalidElementType(type, owner);
-              }
-              break;
-          }
-        } else {
-          throwOnInvalidElementType(type, owner);
-        }
-      }
+      default:
+        fiberTag = getFiberTagFromObjectType(type, owner);
+        break;
     }
   }
 
@@ -3965,33 +4163,47 @@ function createFiberFromElement(element, mode, expirationTime) {
   return fiber;
 }
 
-function throwOnInvalidElementType(type, owner) {
-  var info = "";
-  {
-    if (
-      type === undefined ||
-      (typeof type === "object" &&
-        type !== null &&
-        Object.keys(type).length === 0)
-    ) {
-      info +=
-        " You likely forgot to export your component from the file " +
-        "it's defined in, or you might have mixed up default and " +
-        "named imports.";
-    }
-    var ownerName = owner ? getComponentName(owner) : null;
-    if (ownerName) {
-      info += "\n\nCheck the render method of `" + ownerName + "`.";
+function getFiberTagFromObjectType(type, owner) {
+  var $$typeof =
+    typeof type === "object" && type !== null ? type.$$typeof : null;
+
+  switch ($$typeof) {
+    case REACT_PROVIDER_TYPE:
+      return ContextProvider;
+    case REACT_CONTEXT_TYPE:
+      // This is a consumer
+      return ContextConsumer;
+    case REACT_FORWARD_REF_TYPE:
+      return ForwardRef;
+    default: {
+      var info = "";
+      {
+        if (
+          type === undefined ||
+          (typeof type === "object" &&
+            type !== null &&
+            Object.keys(type).length === 0)
+        ) {
+          info +=
+            " You likely forgot to export your component from the file " +
+            "it's defined in, or you might have mixed up default and " +
+            "named imports.";
+        }
+        var ownerName = owner ? getComponentName(owner) : null;
+        if (ownerName) {
+          info += "\n\nCheck the render method of `" + ownerName + "`.";
+        }
+      }
+      invariant(
+        false,
+        "Element type is invalid: expected a string (for built-in " +
+          "components) or a class/function (for composite components) " +
+          "but got: %s.%s",
+        type == null ? type : typeof type,
+        info
+      );
     }
   }
-  invariant(
-    false,
-    "Element type is invalid: expected a string (for built-in " +
-      "components) or a class/function (for composite components) " +
-      "but got: %s.%s",
-    type == null ? type : typeof type,
-    info
-  );
 }
 
 function createFiberFromFragment(elements, mode, expirationTime, key) {
@@ -4399,15 +4611,15 @@ var ReactStrictModeWarnings = {
     pendingUnsafeLifecycleWarnings = new Map();
   };
 
-  var getStrictRoot = function(fiber) {
+  var findStrictRoot = function(fiber) {
     var maybeStrictRoot = null;
 
-    while (fiber !== null) {
-      if (fiber.mode & StrictMode) {
-        maybeStrictRoot = fiber;
+    var node = fiber;
+    while (node !== null) {
+      if (node.mode & StrictMode) {
+        maybeStrictRoot = node;
       }
-
-      fiber = fiber.return;
+      node = node.return;
     }
 
     return maybeStrictRoot;
@@ -4517,7 +4729,15 @@ var ReactStrictModeWarnings = {
     fiber,
     instance
   ) {
-    var strictRoot = getStrictRoot(fiber);
+    var strictRoot = findStrictRoot(fiber);
+    if (strictRoot === null) {
+      warning(
+        false,
+        "Expected to find a StrictMode component in a strict mode tree. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
+      return;
+    }
 
     // Dedup strategy: Warn once per component.
     // This is difficult to track any other way since component names
@@ -9832,7 +10052,7 @@ var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
 function logError(boundary, errorInfo) {
   var source = errorInfo.source;
   var stack = errorInfo.stack;
-  if (stack === null) {
+  if (stack === null && source !== null) {
     stack = getStackAddendumByWorkInProgressFiber(source);
   }
 
@@ -11892,6 +12112,7 @@ var ReactFiberNewContext = function(stack, isPrimaryRenderer) {
       context._changedBits = providerFiber.stateNode;
       {
         !(
+          context._currentRenderer === undefined ||
           context._currentRenderer === null ||
           context._currentRenderer === rendererSigil
         )
@@ -11912,6 +12133,7 @@ var ReactFiberNewContext = function(stack, isPrimaryRenderer) {
       context._changedBits2 = providerFiber.stateNode;
       {
         !(
+          context._currentRenderer2 === undefined ||
           context._currentRenderer2 === null ||
           context._currentRenderer2 === rendererSigil
         )
@@ -12260,10 +12482,20 @@ var ReactFiberScheduler = function(config) {
       }
 
       // Restore the original state of the work-in-progress
+      if (stashedWorkInProgressProperties === null) {
+        // This should never happen. Don't throw because this code is DEV-only.
+        warning(
+          false,
+          "Could not replay rendering after an error. This is likely a bug in React. " +
+            "Please file an issue."
+        );
+        return;
+      }
       assignFiberPropertiesInDEV(
         failedUnitOfWork,
         stashedWorkInProgressProperties
       );
+
       switch (failedUnitOfWork.tag) {
         case HostRoot:
           popHostContainer(failedUnitOfWork);
@@ -12988,43 +13220,52 @@ var ReactFiberScheduler = function(config) {
           // This is a fatal error.
           didFatal = true;
           onUncaughtError(thrownValue);
-          break;
-        }
-
-        {
-          // Reset global debug state
-          // We assume this is defined in DEV
-          resetCurrentlyProcessingQueue();
-        }
+        } else {
+          {
+            // Reset global debug state
+            // We assume this is defined in DEV
+            resetCurrentlyProcessingQueue();
+          }
 
-        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
-          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
-        }
-
-        var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber.return;
-        if (returnFiber === null) {
-          // This is the root. The root could capture its own errors. However,
-          // we don't know if it errors before or after we pushed the host
-          // context. This information is needed to avoid a stack mismatch.
-          // Because we're not sure, treat this as a fatal error. We could track
-          // which phase it fails in, but doesn't seem worth it. At least
-          // for now.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-          break;
+          if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+            replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
+          }
+
+          // TODO: we already know this isn't true in some cases.
+          // At least this shows a nicer error message until we figure out the cause.
+          // https://github.com/facebook/react/issues/12449#issuecomment-386727431
+          invariant(
+            nextUnitOfWork !== null,
+            "Failed to replay rendering after an error. This " +
+              "is likely caused by a bug in React. Please file an issue " +
+              "with a reproducing case to help us find it."
+          );
+
+          var sourceFiber = nextUnitOfWork;
+          var returnFiber = sourceFiber.return;
+          if (returnFiber === null) {
+            // This is the root. The root could capture its own errors. However,
+            // we don't know if it errors before or after we pushed the host
+            // context. This information is needed to avoid a stack mismatch.
+            // Because we're not sure, treat this as a fatal error. We could track
+            // which phase it fails in, but doesn't seem worth it. At least
+            // for now.
+            didFatal = true;
+            onUncaughtError(thrownValue);
+            break;
+          }
+          throwException(
+            root,
+            returnFiber,
+            sourceFiber,
+            thrownValue,
+            nextRenderIsExpired,
+            nextRenderExpirationTime,
+            mostRecentCurrentTimeMs
+          );
+          nextUnitOfWork = completeUnitOfWork(sourceFiber);
         }
-        throwException(
-          root,
-          returnFiber,
-          sourceFiber,
-          thrownValue,
-          nextRenderIsExpired,
-          nextRenderExpirationTime,
-          mostRecentCurrentTimeMs
-        );
-        nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
       break;
     } while (true);
@@ -14210,6 +14451,20 @@ function cancelDeferredCallback(callbackID) {
   clearTimeout(callbackID);
 }
 
+function dispatchEvent(target, topLevelType, nativeEvent) {
+  var targetFiber = target;
+  batchedUpdates(function() {
+    runExtractedEventsInBatch(
+      topLevelType,
+      targetFiber,
+      nativeEvent,
+      nativeEvent.target
+    );
+  });
+  // React Native doesn't use ReactControlledComponent but if it did, here's
+  // where it would do it.
+}
+
 function _classCallCheck$1(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
     throw new TypeError("Cannot call a class as a function");
@@ -14223,9 +14478,18 @@ function _classCallCheck$1(instance, Constructor) {
 // This means that they never overlap.
 var nextReactTag = 2;
 
+// TODO: Remove this conditional once all changes have propagated.
+if (FabricUIManager.registerEventHandler) {
+  /**
+   * Register the event emitter with the native bridge
+   */
+  FabricUIManager.registerEventHandler(dispatchEvent);
+}
+
 /**
  * This is used for refs on host components.
  */
+
 var ReactFabricHostComponent = (function() {
   function ReactFabricHostComponent(tag, viewConfig, props) {
     _classCallCheck$1(this, ReactFabricHostComponent);
diff --git a/Libraries/Renderer/oss/ReactFabric-prod.js b/Libraries/Renderer/oss/ReactFabric-prod.js
index c4ca5aba4beb..6f17e0bfb3a8 100644
--- a/Libraries/Renderer/oss/ReactFabric-prod.js
+++ b/Libraries/Renderer/oss/ReactFabric-prod.js
@@ -23,8 +23,72 @@ var invariant = require("fbjs/lib/invariant"),
   emptyObject = require("fbjs/lib/emptyObject"),
   shallowEqual = require("fbjs/lib/shallowEqual"),
   ExceptionsManager = require("ExceptionsManager"),
-  FabricUIManager = require("FabricUIManager"),
-  eventPluginOrder = null,
+  FabricUIManager = require("FabricUIManager");
+function invokeGuardedCallback(name, func, context, a, b, c, d, e, f) {
+  this._hasCaughtError = !1;
+  this._caughtError = null;
+  var funcArgs = Array.prototype.slice.call(arguments, 3);
+  try {
+    func.apply(context, funcArgs);
+  } catch (error) {
+    (this._caughtError = error), (this._hasCaughtError = !0);
+  }
+}
+var ReactErrorUtils = {
+  _caughtError: null,
+  _hasCaughtError: !1,
+  _rethrowError: null,
+  _hasRethrowError: !1,
+  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
+    invokeGuardedCallback.apply(ReactErrorUtils, arguments);
+  },
+  invokeGuardedCallbackAndCatchFirstError: function(
+    name,
+    func,
+    context,
+    a,
+    b,
+    c,
+    d,
+    e,
+    f
+  ) {
+    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
+    if (ReactErrorUtils.hasCaughtError()) {
+      var error = ReactErrorUtils.clearCaughtError();
+      ReactErrorUtils._hasRethrowError ||
+        ((ReactErrorUtils._hasRethrowError = !0),
+        (ReactErrorUtils._rethrowError = error));
+    }
+  },
+  rethrowCaughtError: function() {
+    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
+  },
+  hasCaughtError: function() {
+    return ReactErrorUtils._hasCaughtError;
+  },
+  clearCaughtError: function() {
+    if (ReactErrorUtils._hasCaughtError) {
+      var error = ReactErrorUtils._caughtError;
+      ReactErrorUtils._caughtError = null;
+      ReactErrorUtils._hasCaughtError = !1;
+      return error;
+    }
+    invariant(
+      !1,
+      "clearCaughtError was called but no error was captured. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+};
+function rethrowCaughtError() {
+  if (ReactErrorUtils._hasRethrowError) {
+    var error = ReactErrorUtils._rethrowError;
+    ReactErrorUtils._rethrowError = null;
+    ReactErrorUtils._hasRethrowError = !1;
+    throw error;
+  }
+}
+var eventPluginOrder = null,
   namesToPlugins = {};
 function recomputePluginOrdering() {
   if (eventPluginOrder)
@@ -100,6 +164,17 @@ var plugins = [],
   getFiberCurrentPropsFromNode = null,
   getInstanceFromNode = null,
   getNodeFromInstance = null;
+function executeDispatch(event, simulated, listener, inst) {
+  simulated = event.type || "unknown-event";
+  event.currentTarget = getNodeFromInstance(inst);
+  ReactErrorUtils.invokeGuardedCallbackAndCatchFirstError(
+    simulated,
+    listener,
+    void 0,
+    event
+  );
+  event.currentTarget = null;
+}
 function executeDirectDispatch(event) {
   var dispatchListener = event._dispatchListeners,
     dispatchInstance = event._dispatchInstances;
@@ -132,6 +207,26 @@ function accumulateInto(current, next) {
 function forEachAccumulated(arr, cb, scope) {
   Array.isArray(arr) ? arr.forEach(cb, scope) : arr && cb.call(scope, arr);
 }
+var eventQueue = null;
+function executeDispatchesAndReleaseTopLevel(e) {
+  if (e) {
+    var dispatchListeners = e._dispatchListeners,
+      dispatchInstances = e._dispatchInstances;
+    if (Array.isArray(dispatchListeners))
+      for (
+        var i = 0;
+        i < dispatchListeners.length && !e.isPropagationStopped();
+        i++
+      )
+        executeDispatch(e, !1, dispatchListeners[i], dispatchInstances[i]);
+    else
+      dispatchListeners &&
+        executeDispatch(e, !1, dispatchListeners, dispatchInstances);
+    e._dispatchListeners = null;
+    e._dispatchInstances = null;
+    e.isPersistent() || e.constructor.release(e);
+  }
+}
 var injection = {
   injectEventPluginOrder: function(injectedEventPluginOrder) {
     invariant(
@@ -942,7 +1037,7 @@ var hasSymbol = "function" === typeof Symbol && Symbol.for,
   REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
   REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
   REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
-  REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profile_root") : 60108,
+  REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profiler") : 60114,
   REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
   REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
   REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
@@ -968,6 +1063,43 @@ function createPortal(children, containerInfo, implementation) {
     implementation: implementation
   };
 }
+var restoreTarget = null,
+  restoreQueue = null;
+function restoreStateOfTarget(target) {
+  if ((target = getInstanceFromNode(target))) {
+    invariant(
+      null,
+      "Fiber needs to be injected to handle a fiber target for controlled events. This error is likely caused by a bug in React. Please file an issue."
+    );
+    var props = getFiberCurrentPropsFromNode(target.stateNode);
+    null.restoreControlledState(target.stateNode, target.type, props);
+  }
+}
+function _batchedUpdates(fn, bookkeeping) {
+  return fn(bookkeeping);
+}
+function _flushInteractiveUpdates() {}
+var isBatching = !1;
+function batchedUpdates(fn, bookkeeping) {
+  if (isBatching) return fn(bookkeeping);
+  isBatching = !0;
+  try {
+    return _batchedUpdates(fn, bookkeeping);
+  } finally {
+    if (((isBatching = !1), null !== restoreTarget || null !== restoreQueue))
+      if (
+        (_flushInteractiveUpdates(),
+        restoreTarget &&
+          ((bookkeeping = restoreTarget),
+          (fn = restoreQueue),
+          (restoreQueue = restoreTarget = null),
+          restoreStateOfTarget(bookkeeping),
+          fn))
+      )
+        for (bookkeeping = 0; bookkeeping < fn.length; bookkeeping++)
+          restoreStateOfTarget(fn[bookkeeping]);
+  }
+}
 var emptyObject$1 = {},
   removedKeys = null,
   removedKeyCount = 0;
@@ -1426,9 +1558,8 @@ function createFiberFromElement(element, mode, expirationTime) {
   var type = element.type,
     key = element.key;
   element = element.props;
-  var fiberTag = void 0;
   if ("function" === typeof type)
-    fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
+    var fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
   else if ("string" === typeof type) fiberTag = 5;
   else
     switch (type) {
@@ -1460,42 +1591,35 @@ function createFiberFromElement(element, mode, expirationTime) {
         mode |= 2;
         break;
       default:
-        if ("object" === typeof type && null !== type)
-          switch (type.$$typeof) {
+        a: {
+          switch ("object" === typeof type && null !== type
+            ? type.$$typeof
+            : null) {
             case REACT_PROVIDER_TYPE:
               fiberTag = 13;
-              break;
+              break a;
             case REACT_CONTEXT_TYPE:
               fiberTag = 12;
-              break;
+              break a;
             case REACT_FORWARD_REF_TYPE:
               fiberTag = 14;
-              break;
+              break a;
             default:
-              if ("number" === typeof type.tag)
-                return (
-                  (mode = type),
-                  (mode.pendingProps = element),
-                  (mode.expirationTime = expirationTime),
-                  mode
-                );
-              throwOnInvalidElementType(type, null);
+              invariant(
+                !1,
+                "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
+                null == type ? type : typeof type,
+                ""
+              );
           }
-        else throwOnInvalidElementType(type, null);
+          fiberTag = void 0;
+        }
     }
   mode = new FiberNode(fiberTag, element, key, mode);
   mode.type = type;
   mode.expirationTime = expirationTime;
   return mode;
 }
-function throwOnInvalidElementType(type) {
-  invariant(
-    !1,
-    "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
-    null == type ? type : typeof type,
-    ""
-  );
-}
 function createFiberFromFragment(elements, mode, expirationTime, key) {
   elements = new FiberNode(10, elements, key, mode);
   elements.expirationTime = expirationTime;
@@ -3819,7 +3943,9 @@ function createCapturedValue(value, source) {
 function logError(boundary, errorInfo) {
   var source = errorInfo.source,
     stack = errorInfo.stack;
-  null === stack && (stack = getStackAddendumByWorkInProgressFiber(source));
+  null === stack &&
+    null !== source &&
+    (stack = getStackAddendumByWorkInProgressFiber(source));
   null !== source && getComponentName(source);
   source = null !== stack ? stack : "";
   errorInfo = errorInfo.value;
@@ -4774,28 +4900,31 @@ function ReactFiberScheduler(config) {
           for (; null !== nextUnitOfWork; )
             nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
       } catch (thrownValue) {
-        if (null === nextUnitOfWork) {
-          didFatal = !0;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        isAsync = nextUnitOfWork;
-        var returnFiber = isAsync.return;
-        if (null === returnFiber) {
-          didFatal = !0;
-          onUncaughtError(thrownValue);
-          break;
+        if (null === nextUnitOfWork)
+          (didFatal = !0), onUncaughtError(thrownValue);
+        else {
+          invariant(
+            null !== nextUnitOfWork,
+            "Failed to replay rendering after an error. This is likely caused by a bug in React. Please file an issue with a reproducing case to help us find it."
+          );
+          isAsync = nextUnitOfWork;
+          var returnFiber = isAsync.return;
+          if (null === returnFiber) {
+            didFatal = !0;
+            onUncaughtError(thrownValue);
+            break;
+          }
+          throwException(
+            root,
+            returnFiber,
+            isAsync,
+            thrownValue,
+            nextRenderIsExpired,
+            nextRenderExpirationTime,
+            mostRecentCurrentTimeMs
+          );
+          nextUnitOfWork = completeUnitOfWork(isAsync);
         }
-        throwException(
-          root,
-          returnFiber,
-          isAsync,
-          thrownValue,
-          nextRenderIsExpired,
-          nextRenderExpirationTime,
-          mostRecentCurrentTimeMs
-        );
-        nextUnitOfWork = completeUnitOfWork(isAsync);
       }
       break;
     } while (1);
@@ -5665,8 +5794,37 @@ function setTimeoutCallback() {
   scheduledCallback = null;
   null !== callback && callback(frameDeadlineObject);
 }
-var nextReactTag = 2,
-  ReactFabricHostComponent = (function() {
+function dispatchEvent(target, topLevelType, nativeEvent) {
+  batchedUpdates(function() {
+    var events = nativeEvent.target;
+    for (var events$jscomp$0 = null, i = 0; i < plugins.length; i++) {
+      var possiblePlugin = plugins[i];
+      possiblePlugin &&
+        (possiblePlugin = possiblePlugin.extractEvents(
+          topLevelType,
+          target,
+          nativeEvent,
+          events
+        )) &&
+        (events$jscomp$0 = accumulateInto(events$jscomp$0, possiblePlugin));
+    }
+    events = events$jscomp$0;
+    null !== events && (eventQueue = accumulateInto(eventQueue, events));
+    events = eventQueue;
+    eventQueue = null;
+    events &&
+      (forEachAccumulated(events, executeDispatchesAndReleaseTopLevel),
+      invariant(
+        !eventQueue,
+        "processEventQueue(): Additional events were enqueued while processing an event queue. Support for this has not yet been implemented."
+      ),
+      ReactErrorUtils.rethrowCaughtError());
+  });
+}
+var nextReactTag = 2;
+FabricUIManager.registerEventHandler &&
+  FabricUIManager.registerEventHandler(dispatchEvent);
+var ReactFabricHostComponent = (function() {
     function ReactFabricHostComponent(tag, viewConfig, props) {
       if (!(this instanceof ReactFabricHostComponent))
         throw new TypeError("Cannot call a class as a function");
@@ -5882,6 +6040,8 @@ function findNodeHandle(componentOrHandle) {
       ? componentOrHandle.canonical._nativeTag
       : componentOrHandle._nativeTag;
 }
+_batchedUpdates = ReactFabricRenderer.batchedUpdates;
+_flushInteractiveUpdates = ReactFabricRenderer.flushInteractiveUpdates;
 var roots = new Map(),
   ReactFabric = {
     NativeComponent: (function(findNodeHandle, findHostInstance) {
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
index 9b2b430c1466..f1a8809d897b 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
@@ -2763,7 +2763,7 @@ var REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 0xeacb;
 var REACT_STRICT_MODE_TYPE = hasSymbol
   ? Symbol.for("react.strict_mode")
   : 0xeacc;
-var REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profile_root") : 0xeacc;
+var REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profiler") : 0xead2;
 var REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 0xeacd;
 var REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 0xeace;
 var REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 0xeacf;
@@ -3373,42 +3373,9 @@ function createFiberFromElement(element, mode, expirationTime) {
         // mode compatible.
         mode |= StrictMode;
         break;
-      default: {
-        if (typeof type === "object" && type !== null) {
-          switch (type.$$typeof) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = ContextProvider;
-              break;
-            case REACT_CONTEXT_TYPE:
-              // This is a consumer
-              fiberTag = ContextConsumer;
-              break;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = ForwardRef;
-              break;
-            default:
-              if (typeof type.tag === "number") {
-                // Currently assumed to be a continuation and therefore is a
-                // fiber already.
-                // TODO: The yield system is currently broken for updates in
-                // some cases. The reified yield stores a fiber, but we don't
-                // know which fiber that is; the current or a workInProgress?
-                // When the continuation gets rendered here we don't know if we
-                // can reuse that fiber or if we need to clone it. There is
-                // probably a clever way to restructure this.
-                fiber = type;
-                fiber.pendingProps = pendingProps;
-                fiber.expirationTime = expirationTime;
-                return fiber;
-              } else {
-                throwOnInvalidElementType(type, owner);
-              }
-              break;
-          }
-        } else {
-          throwOnInvalidElementType(type, owner);
-        }
-      }
+      default:
+        fiberTag = getFiberTagFromObjectType(type, owner);
+        break;
     }
   }
 
@@ -3424,33 +3391,47 @@ function createFiberFromElement(element, mode, expirationTime) {
   return fiber;
 }
 
-function throwOnInvalidElementType(type, owner) {
-  var info = "";
-  {
-    if (
-      type === undefined ||
-      (typeof type === "object" &&
-        type !== null &&
-        Object.keys(type).length === 0)
-    ) {
-      info +=
-        " You likely forgot to export your component from the file " +
-        "it's defined in, or you might have mixed up default and " +
-        "named imports.";
-    }
-    var ownerName = owner ? getComponentName(owner) : null;
-    if (ownerName) {
-      info += "\n\nCheck the render method of `" + ownerName + "`.";
+function getFiberTagFromObjectType(type, owner) {
+  var $$typeof =
+    typeof type === "object" && type !== null ? type.$$typeof : null;
+
+  switch ($$typeof) {
+    case REACT_PROVIDER_TYPE:
+      return ContextProvider;
+    case REACT_CONTEXT_TYPE:
+      // This is a consumer
+      return ContextConsumer;
+    case REACT_FORWARD_REF_TYPE:
+      return ForwardRef;
+    default: {
+      var info = "";
+      {
+        if (
+          type === undefined ||
+          (typeof type === "object" &&
+            type !== null &&
+            Object.keys(type).length === 0)
+        ) {
+          info +=
+            " You likely forgot to export your component from the file " +
+            "it's defined in, or you might have mixed up default and " +
+            "named imports.";
+        }
+        var ownerName = owner ? getComponentName(owner) : null;
+        if (ownerName) {
+          info += "\n\nCheck the render method of `" + ownerName + "`.";
+        }
+      }
+      invariant(
+        false,
+        "Element type is invalid: expected a string (for built-in " +
+          "components) or a class/function (for composite components) " +
+          "but got: %s.%s",
+        type == null ? type : typeof type,
+        info
+      );
     }
   }
-  invariant(
-    false,
-    "Element type is invalid: expected a string (for built-in " +
-      "components) or a class/function (for composite components) " +
-      "but got: %s.%s",
-    type == null ? type : typeof type,
-    info
-  );
 }
 
 function createFiberFromFragment(elements, mode, expirationTime, key) {
@@ -3858,15 +3839,15 @@ var ReactStrictModeWarnings = {
     pendingUnsafeLifecycleWarnings = new Map();
   };
 
-  var getStrictRoot = function(fiber) {
+  var findStrictRoot = function(fiber) {
     var maybeStrictRoot = null;
 
-    while (fiber !== null) {
-      if (fiber.mode & StrictMode) {
-        maybeStrictRoot = fiber;
+    var node = fiber;
+    while (node !== null) {
+      if (node.mode & StrictMode) {
+        maybeStrictRoot = node;
       }
-
-      fiber = fiber.return;
+      node = node.return;
     }
 
     return maybeStrictRoot;
@@ -3976,7 +3957,15 @@ var ReactStrictModeWarnings = {
     fiber,
     instance
   ) {
-    var strictRoot = getStrictRoot(fiber);
+    var strictRoot = findStrictRoot(fiber);
+    if (strictRoot === null) {
+      warning(
+        false,
+        "Expected to find a StrictMode component in a strict mode tree. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
+      return;
+    }
 
     // Dedup strategy: Warn once per component.
     // This is difficult to track any other way since component names
@@ -9291,7 +9280,7 @@ var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
 function logError(boundary, errorInfo) {
   var source = errorInfo.source;
   var stack = errorInfo.stack;
-  if (stack === null) {
+  if (stack === null && source !== null) {
     stack = getStackAddendumByWorkInProgressFiber(source);
   }
 
@@ -11351,6 +11340,7 @@ var ReactFiberNewContext = function(stack, isPrimaryRenderer) {
       context._changedBits = providerFiber.stateNode;
       {
         !(
+          context._currentRenderer === undefined ||
           context._currentRenderer === null ||
           context._currentRenderer === rendererSigil
         )
@@ -11371,6 +11361,7 @@ var ReactFiberNewContext = function(stack, isPrimaryRenderer) {
       context._changedBits2 = providerFiber.stateNode;
       {
         !(
+          context._currentRenderer2 === undefined ||
           context._currentRenderer2 === null ||
           context._currentRenderer2 === rendererSigil
         )
@@ -11719,10 +11710,20 @@ var ReactFiberScheduler = function(config) {
       }
 
       // Restore the original state of the work-in-progress
+      if (stashedWorkInProgressProperties === null) {
+        // This should never happen. Don't throw because this code is DEV-only.
+        warning(
+          false,
+          "Could not replay rendering after an error. This is likely a bug in React. " +
+            "Please file an issue."
+        );
+        return;
+      }
       assignFiberPropertiesInDEV(
         failedUnitOfWork,
         stashedWorkInProgressProperties
       );
+
       switch (failedUnitOfWork.tag) {
         case HostRoot:
           popHostContainer(failedUnitOfWork);
@@ -12447,43 +12448,52 @@ var ReactFiberScheduler = function(config) {
           // This is a fatal error.
           didFatal = true;
           onUncaughtError(thrownValue);
-          break;
-        }
-
-        {
-          // Reset global debug state
-          // We assume this is defined in DEV
-          resetCurrentlyProcessingQueue();
-        }
+        } else {
+          {
+            // Reset global debug state
+            // We assume this is defined in DEV
+            resetCurrentlyProcessingQueue();
+          }
 
-        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
           var failedUnitOfWork = nextUnitOfWork;
-          replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
-        }
-
-        var sourceFiber = nextUnitOfWork;
-        var returnFiber = sourceFiber.return;
-        if (returnFiber === null) {
-          // This is the root. The root could capture its own errors. However,
-          // we don't know if it errors before or after we pushed the host
-          // context. This information is needed to avoid a stack mismatch.
-          // Because we're not sure, treat this as a fatal error. We could track
-          // which phase it fails in, but doesn't seem worth it. At least
-          // for now.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-          break;
+          if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+            replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
+          }
+
+          // TODO: we already know this isn't true in some cases.
+          // At least this shows a nicer error message until we figure out the cause.
+          // https://github.com/facebook/react/issues/12449#issuecomment-386727431
+          invariant(
+            nextUnitOfWork !== null,
+            "Failed to replay rendering after an error. This " +
+              "is likely caused by a bug in React. Please file an issue " +
+              "with a reproducing case to help us find it."
+          );
+
+          var sourceFiber = nextUnitOfWork;
+          var returnFiber = sourceFiber.return;
+          if (returnFiber === null) {
+            // This is the root. The root could capture its own errors. However,
+            // we don't know if it errors before or after we pushed the host
+            // context. This information is needed to avoid a stack mismatch.
+            // Because we're not sure, treat this as a fatal error. We could track
+            // which phase it fails in, but doesn't seem worth it. At least
+            // for now.
+            didFatal = true;
+            onUncaughtError(thrownValue);
+            break;
+          }
+          throwException(
+            root,
+            returnFiber,
+            sourceFiber,
+            thrownValue,
+            nextRenderIsExpired,
+            nextRenderExpirationTime,
+            mostRecentCurrentTimeMs
+          );
+          nextUnitOfWork = completeUnitOfWork(sourceFiber);
         }
-        throwException(
-          root,
-          returnFiber,
-          sourceFiber,
-          thrownValue,
-          nextRenderIsExpired,
-          nextRenderExpirationTime,
-          mostRecentCurrentTimeMs
-        );
-        nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
       break;
     } while (true);
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
index 471d04181673..52c14c46bfc3 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
@@ -1148,7 +1148,7 @@ var ReactCurrentOwner =
   REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
   REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
   REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
-  REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profile_root") : 60108,
+  REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profiler") : 60114,
   REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
   REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
   REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
@@ -1368,9 +1368,8 @@ function createFiberFromElement(element, mode, expirationTime) {
   var type = element.type,
     key = element.key;
   element = element.props;
-  var fiberTag = void 0;
   if ("function" === typeof type)
-    fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
+    var fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
   else if ("string" === typeof type) fiberTag = 5;
   else
     switch (type) {
@@ -1402,42 +1401,35 @@ function createFiberFromElement(element, mode, expirationTime) {
         mode |= 2;
         break;
       default:
-        if ("object" === typeof type && null !== type)
-          switch (type.$$typeof) {
+        a: {
+          switch ("object" === typeof type && null !== type
+            ? type.$$typeof
+            : null) {
             case REACT_PROVIDER_TYPE:
               fiberTag = 13;
-              break;
+              break a;
             case REACT_CONTEXT_TYPE:
               fiberTag = 12;
-              break;
+              break a;
             case REACT_FORWARD_REF_TYPE:
               fiberTag = 14;
-              break;
+              break a;
             default:
-              if ("number" === typeof type.tag)
-                return (
-                  (mode = type),
-                  (mode.pendingProps = element),
-                  (mode.expirationTime = expirationTime),
-                  mode
-                );
-              throwOnInvalidElementType(type, null);
+              invariant(
+                !1,
+                "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
+                null == type ? type : typeof type,
+                ""
+              );
           }
-        else throwOnInvalidElementType(type, null);
+          fiberTag = void 0;
+        }
     }
   mode = new FiberNode(fiberTag, element, key, mode);
   mode.type = type;
   mode.expirationTime = expirationTime;
   return mode;
 }
-function throwOnInvalidElementType(type) {
-  invariant(
-    !1,
-    "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
-    null == type ? type : typeof type,
-    ""
-  );
-}
 function createFiberFromFragment(elements, mode, expirationTime, key) {
   elements = new FiberNode(10, elements, key, mode);
   elements.expirationTime = expirationTime;
@@ -3704,7 +3696,9 @@ function createCapturedValue(value, source) {
 function logError(boundary, errorInfo) {
   var source = errorInfo.source,
     stack = errorInfo.stack;
-  null === stack && (stack = getStackAddendumByWorkInProgressFiber(source));
+  null === stack &&
+    null !== source &&
+    (stack = getStackAddendumByWorkInProgressFiber(source));
   null !== source && getComponentName(source);
   source = null !== stack ? stack : "";
   errorInfo = errorInfo.value;
@@ -4837,28 +4831,31 @@ function ReactFiberScheduler(config) {
           for (; null !== nextUnitOfWork; )
             nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
       } catch (thrownValue) {
-        if (null === nextUnitOfWork) {
-          didFatal = !0;
-          onUncaughtError(thrownValue);
-          break;
-        }
-        isAsync = nextUnitOfWork;
-        var returnFiber = isAsync.return;
-        if (null === returnFiber) {
-          didFatal = !0;
-          onUncaughtError(thrownValue);
-          break;
+        if (null === nextUnitOfWork)
+          (didFatal = !0), onUncaughtError(thrownValue);
+        else {
+          invariant(
+            null !== nextUnitOfWork,
+            "Failed to replay rendering after an error. This is likely caused by a bug in React. Please file an issue with a reproducing case to help us find it."
+          );
+          isAsync = nextUnitOfWork;
+          var returnFiber = isAsync.return;
+          if (null === returnFiber) {
+            didFatal = !0;
+            onUncaughtError(thrownValue);
+            break;
+          }
+          throwException(
+            root,
+            returnFiber,
+            isAsync,
+            thrownValue,
+            nextRenderIsExpired,
+            nextRenderExpirationTime,
+            mostRecentCurrentTimeMs
+          );
+          nextUnitOfWork = completeUnitOfWork(isAsync);
         }
-        throwException(
-          root,
-          returnFiber,
-          isAsync,
-          thrownValue,
-          nextRenderIsExpired,
-          nextRenderExpirationTime,
-          mostRecentCurrentTimeMs
-        );
-        nextUnitOfWork = completeUnitOfWork(isAsync);
       }
       break;
     } while (1);

From 6cc597e6e4013ef0fa0bc1d5e0c7df611aef1773 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Fri, 18 May 2018 20:19:03 -0700
Subject: [PATCH 0621/1109] Alternative Instance Handle Approach without
 JSWeakRef

Reviewed By: fkgozali

Differential Revision: D8003736

fbshipit-source-id: 597378555cc3f9c0ae95e8927460a3c813ebfb45
---
 .../react/fabric/FabricUIManager.java         | 14 ++++--
 .../react/fabric/jsc/FabricJSCBinding.java    |  4 ++
 .../react/fabric/jsc/jni/FabricJSCBinding.cpp | 47 ++++++++++++++-----
 .../react/fabric/jsc/jni/FabricJSCBinding.h   |  4 ++
 .../react/fabric/FabricUIManagerTest.java     | 16 +++----
 .../fabric/uimanager/FabricUIManager.cpp      | 12 +++--
 .../fabric/uimanager/FabricUIManager.h        |  8 ++--
 7 files changed, 73 insertions(+), 32 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index c7a539e3ede8..0eabd18204fb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -74,7 +74,7 @@ public FabricUIManager(
   /** Creates a new {@link ReactShadowNode} */
   @Nullable
   public ReactShadowNode createNode(
-      int reactTag, String viewName, int rootTag, ReadableNativeMap props, int instanceHandle) {
+      int reactTag, String viewName, int rootTag, ReadableNativeMap props, long instanceHandle) {
     if (DEBUG) {
       Log.d(TAG, "createNode \n\ttag: " + reactTag +
           "\n\tviewName: " + viewName +
@@ -123,11 +123,12 @@ private ReactStylesDiffMap updateProps(ReactShadowNode node, @Nullable ReadableN
    *     including its children set (note that the children nodes will not be cloned).
    */
   @Nullable
-  public ReactShadowNode cloneNode(ReactShadowNode node) {
+  public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
     if (DEBUG) {
       Log.d(TAG, "cloneNode \n\tnode: " + node);
     }
     try {
+      // TODO: Pass new instanceHandle
       ReactShadowNode clone = node.mutableCopy();
       assertReactShadowNodeCopy(node, clone);
       return clone;
@@ -143,11 +144,12 @@ public ReactShadowNode cloneNode(ReactShadowNode node) {
    *     children set will be empty.
    */
   @Nullable
-  public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node) {
+  public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long instanceHandle) {
     if (DEBUG) {
       Log.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
     }
     try {
+      // TODO: Pass new instanceHandle
       ReactShadowNode clone = node.mutableCopyWithNewChildren();
       assertReactShadowNodeCopy(node, clone);
       return clone;
@@ -164,11 +166,12 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node) {
    */
   @Nullable
   public ReactShadowNode cloneNodeWithNewProps(
-      ReactShadowNode node, @Nullable ReadableNativeMap newProps) {
+      ReactShadowNode node, @Nullable ReadableNativeMap newProps, long instanceHandle) {
     if (DEBUG) {
       Log.d(TAG, "cloneNodeWithNewProps \n\tnode: " + node + "\n\tprops: " + newProps);
     }
     try {
+      // TODO: Pass new instanceHandle
       ReactShadowNode clone =
           node.mutableCopyWithNewProps(newProps == null ? null : new ReactStylesDiffMap(newProps));
       assertReactShadowNodeCopy(node, clone);
@@ -187,11 +190,12 @@ public ReactShadowNode cloneNodeWithNewProps(
    */
   @Nullable
   public ReactShadowNode cloneNodeWithNewChildrenAndProps(
-      ReactShadowNode node, ReadableNativeMap newProps) {
+      ReactShadowNode node, ReadableNativeMap newProps, long instanceHandle) {
     if (DEBUG) {
       Log.d(TAG, "cloneNodeWithNewChildrenAndProps \n\tnode: " + node + "\n\tnewProps: " + newProps);
     }
     try {
+      // TODO: Pass new instanceHandle
       ReactShadowNode clone =
           node.mutableCopyWithNewChildrenAndProps(
               newProps == null ? null : new ReactStylesDiffMap(newProps));
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
index 8ae05ff65808..bc2c8e9269fc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
@@ -27,6 +27,10 @@ public class FabricJSCBinding implements FabricBinding {
 
   private static native HybridData initHybrid();
 
+  private native long createEventTarget(long jsContextNativePointer, long instanceHandlePointer);
+
+  private native void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
+
   private native void installFabric(long jsContextNativePointer, Object fabricModule);
 
   public FabricJSCBinding() {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
index 27aac53bbb81..efc4db619682 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
@@ -88,16 +88,16 @@ JSValueRef createNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisOb
 
   static auto createNode =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(jint, jstring, jint, ReadableNativeMap::javaobject, jint)>("createNode");
+      ->getMethod<alias_ref<JShadowNode>(jint, jstring, jint, ReadableNativeMap::javaobject, jlong)>("createNode");
 
   int reactTag = (int)JSC_JSValueToNumber(ctx, arguments[0], NULL);
   auto viewName = JSValueToJString(ctx, arguments[1]);
   int rootTag = (int)JSC_JSValueToNumber(ctx, arguments[2], NULL);
   auto props = JSC_JSValueIsNull(ctx, arguments[3]) ? local_ref<ReadableNativeMap::jhybridobject>(nullptr) :
                JSValueToReadableMapViaJSON(ctx, arguments[3]);;
-  int instanceHandle = (int)JSC_JSValueToNumber(ctx, arguments[4], NULL);
+  auto instanceHandle = (void *)arguments[4];
 
-  auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get(), instanceHandle);
+  auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get(), (jlong)instanceHandle);
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(node.get()));
 }
@@ -109,10 +109,11 @@ JSValueRef cloneNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObj
 
   static auto cloneNode =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject)>("cloneNode");
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, jlong)>("cloneNode");
 
   auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
-  auto newNode = cloneNode(manager, previousNode.get());
+  auto instanceHandle = (void *)arguments[1];
+  auto newNode = cloneNode(manager, previousNode.get(), (jlong)instanceHandle);
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
 }
@@ -124,10 +125,11 @@ JSValueRef cloneNodeWithNewChildren(JSContextRef ctx, JSObjectRef function, JSOb
 
   static auto cloneNodeWithNewChildren =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject)>("cloneNodeWithNewChildren");
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, jlong)>("cloneNodeWithNewChildren");
 
   auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
-  auto newNode = cloneNodeWithNewChildren(manager, previousNode.get());
+  auto instanceHandle = (void *)arguments[1];
+  auto newNode = cloneNodeWithNewChildren(manager, previousNode.get(), (jlong)instanceHandle);
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
 }
@@ -139,11 +141,12 @@ JSValueRef cloneNodeWithNewProps(JSContextRef ctx, JSObjectRef function, JSObjec
 
   static auto cloneNodeWithNewProps =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject)>("cloneNodeWithNewProps");
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject, jlong)>("cloneNodeWithNewProps");
 
   auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
   auto props = JSValueToReadableMapViaJSON(ctx, arguments[1]);
-  auto newNode = cloneNodeWithNewProps(manager, previousNode.get(), props.get());
+  auto instanceHandle = (void *)arguments[2];
+  auto newNode = cloneNodeWithNewProps(manager, previousNode.get(), props.get(), (jlong)instanceHandle);
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
 }
@@ -155,11 +158,12 @@ JSValueRef cloneNodeWithNewChildrenAndProps(JSContextRef ctx, JSObjectRef functi
 
   static auto cloneNodeWithNewChildrenAndProps =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject)>("cloneNodeWithNewChildrenAndProps");
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject, jlong)>("cloneNodeWithNewChildrenAndProps");
 
   auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
   auto props = JSValueToReadableMapViaJSON(ctx, arguments[1]);
-  auto newNode = cloneNodeWithNewChildrenAndProps(manager, previousNode.get(), props.get());
+  auto instanceHandle = (void *)arguments[2];
+  auto newNode = cloneNodeWithNewChildrenAndProps(manager, previousNode.get(), props.get(), (jlong)instanceHandle);
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
 }
@@ -266,6 +270,27 @@ jni::local_ref<FabricJSCBinding::jhybriddata> FabricJSCBinding::initHybrid(
   return makeCxxInstance();
 }
 
+jlong FabricJSCBinding::createEventTarget(
+  jlong jsContextNativePointer,
+  jlong instanceHandlePointer
+) {
+  JSContextRef context = (JSContextRef)jsContextNativePointer;
+  JSValueRef value = (JSValueRef)instanceHandlePointer;
+  // Retain a strong reference to this object.
+  JSC_JSValueProtect(context, value);
+  return (jlong)((void *)value);
+}
+
+void FabricJSCBinding::releaseEventTarget(
+  jlong jsContextNativePointer,
+  jlong eventTargetPointer
+) {
+  JSContextRef context = (JSContextRef)jsContextNativePointer;
+  JSValueRef value = (JSValueRef)((void *)eventTargetPointer);
+  // Release this object.
+  JSC_JSValueUnprotect(context, value);
+}
+
 void FabricJSCBinding::installFabric(jlong jsContextNativePointer,
     jni::alias_ref<jobject> fabricModule) {
   JSContextRef context = (JSContextRef)jsContextNativePointer;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
index 6327ec690a42..a6b9857b012c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
@@ -26,6 +26,10 @@ class FabricJSCBinding : public jni::HybridClass<FabricJSCBinding> {
 
   static jni::local_ref<jhybriddata> initHybrid(jni::alias_ref<jclass>);
 
+  jlong createEventTarget(jlong jsContextNativePointer, jlong instanceHandlePointer);
+
+  void releaseEventTarget(jlong jsContextNativePointer, jlong eventTargetPointer);
+
   void installFabric(jlong jsContextNativePointer, jni::alias_ref<jobject> fabricModule);
 
 };
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 159352c776fe..69f0293619af 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -97,7 +97,7 @@ public void testCloneNode() {
     ReactShadowNode child = createViewNode();
     node.addChildAt(child, 0);
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, 0);
 
     assertThat(clonedNode).isNotSameAs(node);
     assertThat(clonedNode.getOriginalReactShadowNode()).isSameAs(node);
@@ -111,7 +111,7 @@ public void testDefaultSpacingCloning() {
     ReactShadowNode node = createViewNode();
     node.setDefaultPadding(Spacing.LEFT, 10);
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, 0);
 
     node.setDefaultPadding(Spacing.LEFT, 20);
     assertThat(clonedNode.getStylePadding(Spacing.LEFT).value).isEqualTo(10f, Offset.offset(0.01f));
@@ -144,7 +144,7 @@ public void testCloneNodeWithNewChildren() {
     ReactShadowNode child = createViewNode();
     node.addChildAt(child, 0);
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node, 0);
 
     assertThat(clonedNode.getChildCount()).isZero();
     assertSameFields(clonedNode, node);
@@ -155,7 +155,7 @@ public void testCloneNodeWithNewProps() {
     ReactShadowNode node = createViewNode();
     ReadableNativeMap props = null; // TODO(ayc): Figure out how to create a Native map from tests.
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props, 0);
   }
 
   @Test
@@ -163,7 +163,7 @@ public void testCloneNodeWithNewChildrenAndProps() {
     ReactShadowNode node = createViewNode();
     ReadableNativeMap props = null;
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props, 0);
 
     assertThat(clonedNode.getChildCount()).isZero();
   }
@@ -260,10 +260,10 @@ public void testRemoveOriginalNodeReferences() {
     mFabricUIManager.appendChildToSet(childSet, container);
     mFabricUIManager.completeRoot(rootTag, childSet);
 
-    ReactShadowNode aaClone = mFabricUIManager.cloneNodeWithNewProps(aa, null);
-    ReactShadowNode aClone = mFabricUIManager.cloneNodeWithNewChildren(a);
+    ReactShadowNode aaClone = mFabricUIManager.cloneNodeWithNewProps(aa, null, 0);
+    ReactShadowNode aClone = mFabricUIManager.cloneNodeWithNewChildren(a, 0);
     mFabricUIManager.appendChild(aClone, aaClone);
-    ReactShadowNode containerClone = mFabricUIManager.cloneNodeWithNewChildren(container);
+    ReactShadowNode containerClone = mFabricUIManager.cloneNodeWithNewChildren(container, 0);
     mFabricUIManager.appendChild(containerClone, b);
     mFabricUIManager.appendChild(containerClone, aClone);
     List<ReactShadowNode> childSet2 = mFabricUIManager.createChildSet(rootTag);
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index da5af6f7af04..1e74831ea4a6 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -115,10 +115,11 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
   return shadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode) {
+SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode, void *instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
 
+  // TODO: Retain new instanceHandle
   SharedShadowNode clonedShadowNode =
     componentDescriptor->cloneShadowNode(shadowNode);
 
@@ -126,11 +127,12 @@ SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode)
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode, void *instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   // Assuming semantic: Cloning with same props but empty children.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
 
+  // TODO: Retain new instanceHandle
   SharedShadowNode clonedShadowNode =
     componentDescriptor->cloneShadowNode(
       shadowNode,
@@ -142,12 +144,13 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props, void *instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with same children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
 
+  // TODO: Retain new instanceHandle
   SharedShadowNode clonedShadowNode =
     componentDescriptor->cloneShadowNode(
       shadowNode,
@@ -159,12 +162,13 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props, void *instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with empty children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
 
+  // TODO: Retain new instanceHandle
   SharedShadowNode clonedShadowNode =
     componentDescriptor->cloneShadowNode(
       shadowNode,
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index c2b3dea9bfee..1fa11b521d76 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -36,10 +36,10 @@ class FabricUIManager {
 #pragma mark - JavaScript/React-facing Interface
 
   SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, void *instanceHandle);
-  SharedShadowNode cloneNode(const SharedShadowNode &node);
-  SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node);
-  SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props);
-  SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps);
+  SharedShadowNode cloneNode(const SharedShadowNode &node, void *instanceHandle);
+  SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node, void *instanceHandle);
+  SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props, void *instanceHandle);
+  SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps, void *instanceHandle);
   void appendChild(const SharedShadowNode &parentNode, const SharedShadowNode &childNode);
   SharedShadowNodeUnsharedList createChildSet(Tag rootTag);
   void appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode);

From caaea38ad9e5954397e81f625b06abe0efa02d1c Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 18 May 2018 20:28:57 -0700
Subject: [PATCH 0622/1109] Fabric: Using unique_ptr for storing YGNode inside
 YogaLayoutableShadowNode

Summary:
I recently realized (Thanks David!) that we should not use `shared_ptr` for storing YGNode*
because ShadowNode does not share ownership of the Yoga node with anybody.
So the lifecycle of shadow node and yoga node must be synchronized (this is already the case but changing to unique_ptr makes this explicit and a bit more performant).

Reviewed By: fkgozali

Differential Revision: D8030417

fbshipit-source-id: c7f85ea309598d2a5ebfed55b1d182d3fe1336ae
---
 .../view/yoga/YogaLayoutableShadowNode.cpp    | 54 +++++++++----------
 .../view/yoga/YogaLayoutableShadowNode.h      |  7 +--
 2 files changed, 27 insertions(+), 34 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 9ad1be234f25..43586dea128f 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -37,13 +37,12 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   assert(props);
   assert(children);
 
-  auto yogaNode = std::make_shared<YGNode>();
-  yogaNode->setConfig(suitableYogaConfig().get());
-  yogaNode->setStyle(props->yogaStyle);
-  yogaNode->setContext(this);
-  yogaNode->setDirty(true);
-  YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(*yogaNode, children);
-  yogaNode_ = yogaNode;
+  yogaNode_ = std::make_unique<YGNode>();
+  yogaNode_->setConfig(suitableYogaConfig().get());
+  yogaNode_->setStyle(props->yogaStyle);
+  yogaNode_->setContext(this);
+  yogaNode_->setDirty(true);
+  YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(yogaNode_.get(), children);
 }
 
 YogaLayoutableShadowNode::YogaLayoutableShadowNode(
@@ -51,21 +50,19 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   const SharedYogaStylableProps &props,
   const SharedShadowNodeSharedList &children
 ) {
-  auto yogaNode = std::make_shared<YGNode>(*shadowNode->yogaNode_);
-  yogaNode->setConfig(suitableYogaConfig().get());
-  yogaNode->setContext(this);
-  yogaNode->setOwner(nullptr);
-  yogaNode->setDirty(true);
+  yogaNode_ = std::make_unique<YGNode>(*shadowNode->yogaNode_);
+  yogaNode_->setConfig(suitableYogaConfig().get());
+  yogaNode_->setContext(this);
+  yogaNode_->setOwner(nullptr);
+  yogaNode_->setDirty(true);
 
   if (props) {
-    yogaNode->setStyle(props->yogaStyle);
+    yogaNode_->setStyle(props->yogaStyle);
   }
 
   if (children) {
-    YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(*yogaNode, children);
+    YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(yogaNode_.get(), children);
   }
-
-  yogaNode_ = yogaNode;
 }
 
 void YogaLayoutableShadowNode::cleanLayout() {
@@ -99,21 +96,20 @@ void YogaLayoutableShadowNode::enableMeasurement() {
 void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child) {
   ensureUnsealed();
 
-  auto nonConstYogaNode = std::const_pointer_cast<YGNode>(yogaNode_);
-  auto nonConstChildYogaNode = std::const_pointer_cast<YGNode>(child->yogaNode_);
-  nonConstYogaNode->insertChild(nonConstChildYogaNode.get(), nonConstYogaNode->getChildrenCount());
+  auto yogaNodeRawPtr = yogaNode_.get();
+  auto childYogaNodeRawPtr = child->yogaNode_.get();
+  yogaNodeRawPtr->insertChild(childYogaNodeRawPtr, yogaNodeRawPtr->getChildrenCount());
 
-  if (nonConstChildYogaNode->getOwner() == nullptr) {
+  if (childYogaNodeRawPtr->getOwner() == nullptr) {
     child->ensureUnsealed();
-    nonConstChildYogaNode->setOwner(nonConstYogaNode.get());
+    childYogaNodeRawPtr->setOwner(yogaNodeRawPtr);
   }
 }
 
 void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
   if (!getIsLayoutClean()) {
     ensureUnsealed();
-    YGNode *yogaNode = const_cast<YGNode *>(yogaNode_.get());
-    YGNodeCalculateLayout(yogaNode, YGUndefined, YGUndefined, YGDirectionInherit);
+    YGNodeCalculateLayout(yogaNode_.get(), YGUndefined, YGUndefined, YGDirectionInherit);
   }
 
   LayoutableShadowNode::layout(layoutContext);
@@ -206,7 +202,7 @@ YGSize YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector(YGNode *yogaNo
   };
 }
 
-void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children) {
+void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode *yogaNodeRawPtr, const SharedShadowNodeSharedList &children) {
   auto yogaNodeChildren = YGVector();
 
   for (const SharedShadowNode &shadowNode : *children) {
@@ -216,17 +212,17 @@ void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNo
       continue;
     }
 
-    YGNode *yogaNodeChild = (YGNode *)yogaLayoutableShadowNode->yogaNode_.get();
+    auto &&childYogaNodeRawPtr = (YGNode *)yogaLayoutableShadowNode->yogaNode_.get();
 
-    yogaNodeChildren.push_back(yogaNodeChild);
+    yogaNodeChildren.push_back(childYogaNodeRawPtr);
 
-    if (yogaNodeChild->getOwner() == nullptr) {
+    if (childYogaNodeRawPtr->getOwner() == nullptr) {
       yogaLayoutableShadowNode->ensureUnsealed();
-      yogaNodeChild->setOwner(&yogaNode);
+      childYogaNodeRawPtr->setOwner(yogaNodeRawPtr);
     }
   }
 
-  yogaNode.setChildren(yogaNodeChildren);
+  yogaNodeRawPtr->setChildren(yogaNodeChildren);
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index 7c3a1b2f3d91..4ed364b7513b 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -23,9 +23,6 @@ namespace react {
 
 class YogaLayoutableShadowNode;
 
-// We accept that Yoga node is highly mutable thing and we don't try to enforce immutability,
-// so it does not have `const` qualifier (and we mark it as `mutable` in the class).
-using SharedYogaNode = std::shared_ptr<YGNode>;
 using SharedYogaConfig = std::shared_ptr<YGConfig>;
 
 using SharedYogaLayoutableShadowNode = std::shared_ptr<const YogaLayoutableShadowNode>;
@@ -83,11 +80,11 @@ class YogaLayoutableShadowNode:
   void layoutChildren(LayoutContext layoutContext) override;
 
 protected:
-  mutable SharedYogaNode yogaNode_;
+  std::unique_ptr<YGNode> yogaNode_;
 
 private:
   static SharedYogaConfig suitableYogaConfig();
-  static void setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode &yogaNode, const SharedShadowNodeSharedList &children);
+  static void setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode *yogaNodeRawPtr, const SharedShadowNodeSharedList &children);
   static YGNode *yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex);
   static YGSize yogaNodeMeasureCallbackConnector(YGNode *yogaNode, float width, YGMeasureMode widthMode, float height, YGMeasureMode heightMode);
 };

From 85fc98d437c08cdec883a73161e120478737ba72 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Fri, 18 May 2018 20:43:21 -0700
Subject: [PATCH 0623/1109] Fix JUnit report location when running Jest

Summary:
We were incorrectly writing jest's junit output to ~/reports/ instead of ~/react-native/reports.

Run on Circle and confirm JUnit test results are rendered: https://circleci.com/gh/hramos/react-native/2208

[INTERNAL][MINOR][CI] - JUnit test collection

[skip ci]
Closes https://github.com/facebook/react-native/pull/19349

Differential Revision: D8062654

Pulled By: hramos

fbshipit-source-id: 72066270042dfae8afce62469fcfabb57bd405a6
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index ebae261767a7..1dd9adaf072c 100644
--- a/package.json
+++ b/package.json
@@ -123,7 +123,7 @@
   ],
   "scripts": {
     "test": "jest",
-    "test-ci": "JEST_JUNIT_OUTPUT=\"~/reports/junit/js-test-results.xml\" jest --maxWorkers=2 --ci --testResultsProcessor=\"jest-junit\"",
+    "test-ci": "JEST_JUNIT_OUTPUT=\"reports/junit/js-test-results.xml\" jest --maxWorkers=2 --ci --testResultsProcessor=\"jest-junit\"",
     "flow": "flow",
     "lint": "eslint .",
     "prettier": "find . -name node_modules -prune -or -name '*.js' -print | xargs prettier --write",

From 06b0dabaa724dc7c076fa5950b69d245bb8229db Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 18 May 2018 21:58:16 -0700
Subject: [PATCH 0624/1109] Fabric: Deletion of unused files

Summary: We don't use them anymore.

Reviewed By: fkgozali

Differential Revision: D8048545

fbshipit-source-id: c92aa9ca13ac31eaead87a0982ed613710b7af57
---
 .../RCTFabricPlatformUIOperationManager.h     | 46 --------------
 .../RCTFabricPlatformUIOperationManager.mm    | 48 --------------
 React/Fabric/RCTFabricUIManagerWrapper.h      | 44 -------------
 React/Fabric/RCTFabricUIManagerWrapper.mm     | 62 -------------------
 .../IFabricPlatformUIOperationManager.h       | 23 -------
 5 files changed, 223 deletions(-)
 delete mode 100644 React/Fabric/RCTFabricPlatformUIOperationManager.h
 delete mode 100644 React/Fabric/RCTFabricPlatformUIOperationManager.mm
 delete mode 100644 React/Fabric/RCTFabricUIManagerWrapper.h
 delete mode 100644 React/Fabric/RCTFabricUIManagerWrapper.mm
 delete mode 100644 ReactCommon/fabric/uimanager/IFabricPlatformUIOperationManager.h

diff --git a/React/Fabric/RCTFabricPlatformUIOperationManager.h b/React/Fabric/RCTFabricPlatformUIOperationManager.h
deleted file mode 100644
index fe6c89ea21b8..000000000000
--- a/React/Fabric/RCTFabricPlatformUIOperationManager.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#import <Foundation/Foundation.h>
-#import <UIKit/UIKit.h>
-
-#import <memory>
-
-#include <fabric/uimanager/IFabricPlatformUIOperationManager.h>
-
-@class RCTFabricPlatformUIOperationManager;
-
-namespace facebook {
-namespace react {
-
-/**
- * Connector class (from C++ to ObjC++) to allow FabricUIManager to invoke native UI operations/updates.
- * UIKit-related impl doesn't live here, but this class gets passed to the FabricUIManager C++ impl directly.
- */
-class RCTFabricPlatformUIOperationManagerConnector : public IFabricPlatformUIOperationManager {
-public:
-  RCTFabricPlatformUIOperationManagerConnector();
-  virtual ~RCTFabricPlatformUIOperationManagerConnector();
-
-  void performUIOperation();
-
-private:
-  void *self_;
-  RCTFabricPlatformUIOperationManager *manager_;
-};
-
-} // namespace react
-} // namespace facebook
-
-/**
- * Actual ObjC++ implementation of the UI operations.
- */
-@interface RCTFabricPlatformUIOperationManager : NSObject
-
-- (void)performUIOperation;
-
-@end
diff --git a/React/Fabric/RCTFabricPlatformUIOperationManager.mm b/React/Fabric/RCTFabricPlatformUIOperationManager.mm
deleted file mode 100644
index 3bccc58e0516..000000000000
--- a/React/Fabric/RCTFabricPlatformUIOperationManager.mm
+++ /dev/null
@@ -1,48 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#import "RCTFabricPlatformUIOperationManager.h"
-
-namespace facebook {
-namespace react {
-
-RCTFabricPlatformUIOperationManagerConnector::RCTFabricPlatformUIOperationManagerConnector() {
-  self_ = (__bridge_retained void *)[RCTFabricPlatformUIOperationManager new];
-  manager_ = (__bridge RCTFabricPlatformUIOperationManager *)self_;
-}
-
-RCTFabricPlatformUIOperationManagerConnector::~RCTFabricPlatformUIOperationManagerConnector() {
-  CFRelease(self_);
-  self_ = NULL;
-  manager_ = NULL;
-}
-
-void RCTFabricPlatformUIOperationManagerConnector::performUIOperation() {
-  [manager_ performUIOperation];
-}
-
-} // namespace react
-} // namespace facebook
-
-// -----------------------------------------------------------------------------
-// Start of ObjC++ impl
-// Access UIKit here.
-// -----------------------------------------------------------------------------
-@implementation RCTFabricPlatformUIOperationManager
-
-- (void)dealloc
-{
-  NSLog(@"RCTFabricPlatformUIOperationManager: dealloc()");
-}
-
-- (void)performUIOperation
-{
-  // TODO
-  NSLog(@"RCTFabricPlatformUIOperationManager: performUIOperation()");
-}
-
-@end
diff --git a/React/Fabric/RCTFabricUIManagerWrapper.h b/React/Fabric/RCTFabricUIManagerWrapper.h
deleted file mode 100644
index d40ef78c359c..000000000000
--- a/React/Fabric/RCTFabricUIManagerWrapper.h
+++ /dev/null
@@ -1,44 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#import <UIKit/UIKit.h>
-
-#import <memory>
-
-#import <React/RCTBridge.h>
-#import <React/RCTInvalidating.h>
-#import <React/RCTShadowView.h>
-
-namespace facebook {
-namespace react {
-
-class FabricUIManager;
-
-} // namespace react
-} // namespace facebook
-
-using namespace facebook::react;
-
-/**
- * An ObjC++ wrapper around the C++ FabricUIManager instance, so that the RCTCxxBridge can access it as needed.
- */
-@interface RCTFabricUIManagerWrapper : NSObject <RCTInvalidating>
-
-- (std::shared_ptr<FabricUIManager>)manager;
-
-@end
-
-@interface RCTBridge (RCTFabricUIManagerWrapper)
-
-/**
- * To access via the bridge:
- *
- *   std::shared_ptr<FabricUIManager> fabricUIManager = [_bridge fabricUIManager];
- */
-- (std::shared_ptr<FabricUIManager>)fabricUIManager;
-
-@end
diff --git a/React/Fabric/RCTFabricUIManagerWrapper.mm b/React/Fabric/RCTFabricUIManagerWrapper.mm
deleted file mode 100644
index 0d4613b0c28f..000000000000
--- a/React/Fabric/RCTFabricUIManagerWrapper.mm
+++ /dev/null
@@ -1,62 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#import "RCTFabricUIManagerWrapper.h"
-
-#include <fabric/uimanager/ComponentDescriptorRegistry.h>
-#include <fabric/uimanager/FabricUIManager.h>
-#include <fabric/view/ViewComponentDescriptor.h>
-#include <folly/dynamic.h>
-#include <folly/json.h>
-
-#import "RCTFabricPlatformUIOperationManager.h"
-
-// This file contains experimental placeholders, nothing is finalized.
-@implementation RCTFabricUIManagerWrapper
-{
-  std::shared_ptr<FabricUIManager> _manager;
-  std::shared_ptr<IFabricPlatformUIOperationManager> _platformUIOperationManager;
-}
-
-- (instancetype)init
-{
-  self = [super init];
-  if (self) {
-    _platformUIOperationManager = std::make_shared<RCTFabricPlatformUIOperationManagerConnector>();
-
-    auto componentDescriptorRegistry = std::make_shared<ComponentDescriptorRegistry>();
-    SharedComponentDescriptor viewComponentDescriptor = std::make_shared<ViewComponentDescriptor>();
-    componentDescriptorRegistry->registerComponentDescriptor(viewComponentDescriptor);
-
-    _manager = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
-  }
-  return self;
-}
-
-- (std::shared_ptr<FabricUIManager>)manager
-{
-  return _manager;
-}
-
-- (void)invalidate
-{
-}
-
-@end
-
-@implementation RCTBridge (RCTFabricUIManagerWrapper)
-
-- (std::shared_ptr<FabricUIManager>)fabricUIManager
-{
-  RCTFabricUIManagerWrapper *wrapper = [self jsBoundExtraModuleForClass:[RCTFabricUIManagerWrapper class]];
-  if (wrapper) {
-    return [wrapper manager];
-  }
-  return nullptr;
-}
-
-@end
diff --git a/ReactCommon/fabric/uimanager/IFabricPlatformUIOperationManager.h b/ReactCommon/fabric/uimanager/IFabricPlatformUIOperationManager.h
deleted file mode 100644
index ff1434c7520d..000000000000
--- a/ReactCommon/fabric/uimanager/IFabricPlatformUIOperationManager.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#pragma once
-
-namespace facebook {
-namespace react {
-
-/**
- * An interface for FabricUIManager to perform platform-specific UI operations, like updating native UIView's in iOS.
- */
-class IFabricPlatformUIOperationManager {
-public:
-  // TODO: add meaningful methods
-  virtual void performUIOperation() = 0;
-};
-
-} // namespace react
-} // namespace facebook

From 7d741d1119532213e2c30707320351fb56c63953 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Sat, 19 May 2018 09:14:11 -0700
Subject: [PATCH 0625/1109] Prettier

Reviewed By: bestander

Differential Revision: D8067792

fbshipit-source-id: 6ea8f46c3dce80afc3689ba55f348aa645af391e
---
 Libraries/Lists/VirtualizedList.js | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 37819aaeef9a..d790667e559a 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -759,7 +759,8 @@ class VirtualizedList extends React.PureComponent<Props, State> {
           <View onLayout={this._onLayoutHeader} style={inversionStyle}>
             {
               // $FlowFixMe - Typing ReactNativeComponent revealed errors
-              element}
+              element
+            }
           </View>
         </VirtualizedCellWrapper>,
       );
@@ -894,7 +895,8 @@ class VirtualizedList extends React.PureComponent<Props, State> {
           <View onLayout={this._onLayoutFooter} style={inversionStyle}>
             {
               // $FlowFixMe - Typing ReactNativeComponent revealed errors
-              element}
+              element
+            }
           </View>
         </VirtualizedCellWrapper>,
       );

From 1a7682b2a1d74cee7d01eb2a231b3afeb3390e88 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Sun, 20 May 2018 23:06:59 -0700
Subject: [PATCH 0626/1109] Re-format BUCK to use recommended style.

Reviewed By: yfeldblum

Differential Revision: D8073585

fbshipit-source-id: 12322aebc09b89d5af9cc257b16c1bc0fbb066c1
---
 RNTester/android/app/BUCK                     |  2 +-
 ReactAndroid/src/androidTest/buck-runner/BUCK |  2 +-
 .../java/com/facebook/react/testing/BUCK      |  2 +-
 .../facebook/react/testing/idledetection/BUCK |  2 +-
 .../com/facebook/react/testing/network/BUCK   |  2 +-
 .../java/com/facebook/react/tests/BUCK        |  2 +-
 .../com/facebook/catalyst/appcompat/BUCK      |  2 +-
 ReactAndroid/src/main/java/com/facebook/BUCK  |  2 +-
 .../facebook/debug/debugoverlay/model/BUCK    |  2 +-
 .../main/java/com/facebook/debug/holder/BUCK  |  2 +-
 .../main/java/com/facebook/debug/tags/BUCK    |  2 +-
 .../src/main/java/com/facebook/jni/BUCK       |  2 +-
 .../src/main/java/com/facebook/react/BUCK     |  2 +-
 .../java/com/facebook/react/animated/BUCK     |  2 +-
 .../java/com/facebook/react/animation/BUCK    |  2 +-
 .../main/java/com/facebook/react/bridge/BUCK  |  2 +-
 .../main/java/com/facebook/react/common/BUCK  |  2 +-
 .../com/facebook/react/common/network/BUCK    |  2 +-
 .../java/com/facebook/react/devsupport/BUCK   |  2 +-
 .../main/java/com/facebook/react/fabric/BUCK  |  2 +-
 .../java/com/facebook/react/fabric/jsc/BUCK   |  2 +-
 .../com/facebook/react/fabric/jsc/jni/BUCK    |  2 +-
 .../main/java/com/facebook/react/flat/BUCK    |  2 +-
 .../main/java/com/facebook/react/jstasks/BUCK |  2 +-
 .../facebook/react/module/annotations/BUCK    |  2 +-
 .../java/com/facebook/react/module/model/BUCK |  2 +-
 .../com/facebook/react/module/processing/BUCK |  2 +-
 .../react/modules/accessibilityinfo/BUCK      |  2 +-
 .../facebook/react/modules/appregistry/BUCK   |  2 +-
 .../com/facebook/react/modules/appstate/BUCK  |  2 +-
 .../java/com/facebook/react/modules/blob/BUCK |  2 +-
 .../com/facebook/react/modules/camera/BUCK    |  2 +-
 .../com/facebook/react/modules/clipboard/BUCK |  2 +-
 .../com/facebook/react/modules/common/BUCK    |  2 +-
 .../java/com/facebook/react/modules/core/BUCK |  2 +-
 .../facebook/react/modules/datepicker/BUCK    |  2 +-
 .../com/facebook/react/modules/debug/BUCK     |  2 +-
 .../facebook/react/modules/deviceinfo/BUCK    |  2 +-
 .../com/facebook/react/modules/dialog/BUCK    |  2 +-
 .../com/facebook/react/modules/fabric/BUCK    |  2 +-
 .../com/facebook/react/modules/fresco/BUCK    |  2 +-
 .../facebook/react/modules/i18nmanager/BUCK   |  2 +-
 .../com/facebook/react/modules/image/BUCK     |  2 +-
 .../com/facebook/react/modules/intent/BUCK    |  2 +-
 .../com/facebook/react/modules/location/BUCK  |  2 +-
 .../com/facebook/react/modules/netinfo/BUCK   |  2 +-
 .../com/facebook/react/modules/network/BUCK   |  2 +-
 .../facebook/react/modules/permissions/BUCK   |  2 +-
 .../com/facebook/react/modules/share/BUCK     |  2 +-
 .../com/facebook/react/modules/statusbar/BUCK |  2 +-
 .../com/facebook/react/modules/storage/BUCK   |  2 +-
 .../facebook/react/modules/systeminfo/BUCK    |  2 +-
 .../facebook/react/modules/timepicker/BUCK    |  2 +-
 .../com/facebook/react/modules/toast/BUCK     |  2 +-
 .../com/facebook/react/modules/vibration/BUCK |  2 +-
 .../com/facebook/react/modules/websocket/BUCK |  2 +-
 .../facebook/react/packagerconnection/BUCK    |  2 +-
 .../java/com/facebook/react/processing/BUCK   |  2 +-
 .../main/java/com/facebook/react/shell/BUCK   |  2 +-
 .../main/java/com/facebook/react/touch/BUCK   |  2 +-
 .../java/com/facebook/react/uimanager/BUCK    |  2 +-
 .../facebook/react/uimanager/annotations/BUCK |  2 +-
 .../com/facebook/react/uimanager/common/BUCK  |  2 +-
 .../com/facebook/react/uimanager/util/BUCK    |  2 +-
 .../main/java/com/facebook/react/util/BUCK    |  2 +-
 .../java/com/facebook/react/views/art/BUCK    |  2 +-
 .../com/facebook/react/views/checkbox/BUCK    |  2 +-
 .../java/com/facebook/react/views/common/BUCK |  2 +-
 .../java/com/facebook/react/views/drawer/BUCK |  2 +-
 .../java/com/facebook/react/views/image/BUCK  |  2 +-
 .../com/facebook/react/views/imagehelper/BUCK |  2 +-
 .../java/com/facebook/react/views/modal/BUCK  |  2 +-
 .../java/com/facebook/react/views/picker/BUCK |  2 +-
 .../com/facebook/react/views/progressbar/BUCK |  2 +-
 .../java/com/facebook/react/views/scroll/BUCK |  2 +-
 .../java/com/facebook/react/views/slider/BUCK |  2 +-
 .../facebook/react/views/swiperefresh/BUCK    |  2 +-
 .../com/facebook/react/views/switchview/BUCK  |  2 +-
 .../java/com/facebook/react/views/text/BUCK   |  2 +-
 .../react/views/text/frescosupport/BUCK       |  2 +-
 .../com/facebook/react/views/textinput/BUCK   |  2 +-
 .../com/facebook/react/views/toolbar/BUCK     |  2 +-
 .../java/com/facebook/react/views/view/BUCK   |  2 +-
 .../com/facebook/react/views/viewpager/BUCK   |  2 +-
 .../com/facebook/react/views/webview/BUCK     |  2 +-
 ReactAndroid/src/main/jni/first-party/fb/BUCK | 30 +++++++-------
 .../src/main/jni/first-party/fbgloginit/BUCK  |  2 +-
 .../src/main/jni/first-party/yogajni/BUCK     | 26 ++++++-------
 ReactAndroid/src/main/jni/prebuilt/BUCK       |  2 +-
 ReactAndroid/src/main/jni/react/jni/BUCK      |  2 +-
 .../src/main/jni/react/perftests/BUCK         |  2 +-
 .../src/main/jni/third-party/android-ndk/BUCK | 20 +++++-----
 .../java/com/facebook/common/logging/BUCK     |  2 +-
 ReactAndroid/src/main/res/BUCK                |  2 +-
 .../java/robolectric3/robolectric/BUCK        |  2 +-
 .../java/com/facebook/common/logging/BUCK     |  2 +-
 .../src/test/java/com/facebook/react/BUCK     |  2 +-
 .../java/com/facebook/react/animated/BUCK     |  2 +-
 .../test/java/com/facebook/react/bridge/BUCK  |  2 +-
 .../java/com/facebook/react/devsupport/BUCK   |  2 +-
 .../test/java/com/facebook/react/fabric/BUCK  |  2 +-
 .../test/java/com/facebook/react/modules/BUCK |  2 +-
 .../facebook/react/packagerconnection/BUCK    |  2 +-
 .../java/com/facebook/react/uimanager/BUCK    |  2 +-
 .../test/java/com/facebook/react/views/BUCK   |  2 +-
 .../test/java/org/mockito/configuration/BUCK  |  2 +-
 ReactCommon/cxxreact/BUCK                     |  7 ++--
 ReactCommon/cxxreact/tests/BUCK               | 39 ++++++++++---------
 ReactCommon/fabric/attributedstring/BUCK      |  9 +++--
 ReactCommon/fabric/core/BUCK                  |  9 +++--
 ReactCommon/fabric/debug/BUCK                 |  9 +++--
 ReactCommon/fabric/graphics/BUCK              |  9 +++--
 ReactCommon/fabric/scrollview/BUCK            |  9 +++--
 ReactCommon/fabric/text/BUCK                  |  9 +++--
 ReactCommon/fabric/textlayoutmanager/BUCK     |  9 +++--
 ReactCommon/fabric/uimanager/BUCK             |  7 ++--
 ReactCommon/fabric/view/BUCK                  |  9 +++--
 ReactCommon/jschelpers/BUCK                   |  2 +-
 ReactCommon/microprofiler/BUCK                |  2 +-
 119 files changed, 211 insertions(+), 200 deletions(-)

diff --git a/RNTester/android/app/BUCK b/RNTester/android/app/BUCK
index c54e4b6313cd..e987dc9304db 100644
--- a/RNTester/android/app/BUCK
+++ b/RNTester/android/app/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_android_binary", "rn_android_resource", "react_native_dep", "react_native_target", "KEYSTORE_TARGET")
+load("//ReactNative:DEFS.bzl", "KEYSTORE_TARGET", "react_native_dep", "react_native_target", "rn_android_binary", "rn_android_library", "rn_android_resource")
 
 rn_android_binary(
     name = "app",
diff --git a/ReactAndroid/src/androidTest/buck-runner/BUCK b/ReactAndroid/src/androidTest/buck-runner/BUCK
index 40b1947b01a9..d854a78f7a7a 100644
--- a/ReactAndroid/src/androidTest/buck-runner/BUCK
+++ b/ReactAndroid/src/androidTest/buck-runner/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_binary", "react_native_dep", "react_native_integration_tests_target", "react_native_target", "KEYSTORE_TARGET")
+load("//ReactNative:DEFS.bzl", "KEYSTORE_TARGET", "react_native_dep", "react_native_integration_tests_target", "react_native_target", "rn_android_binary")
 
 # We are running instrumentation tests in simple mode: app code and instrumentation are in the same APK
 # Currently you need to run these commands to execute tests:
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
index 7d96b9b3bb53..647a303619a1 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_integration_tests_target", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_integration_tests_target", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "testing",
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/idledetection/BUCK b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/idledetection/BUCK
index db6b3a8a654a..35312a7305a9 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/idledetection/BUCK
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/idledetection/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "idledetection",
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/network/BUCK b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/network/BUCK
index d44057ef9fc5..bcb816f893a8 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/network/BUCK
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/network/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "network",
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/BUCK b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/BUCK
index 7412d1176688..e39c0147a7cb 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/BUCK
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_integration_tests_target", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_integration_tests_target", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "tests",
diff --git a/ReactAndroid/src/main/android_res/com/facebook/catalyst/appcompat/BUCK b/ReactAndroid/src/main/android_res/com/facebook/catalyst/appcompat/BUCK
index a8bc7113c642..868485a2b73c 100644
--- a/ReactAndroid/src/main/android_res/com/facebook/catalyst/appcompat/BUCK
+++ b/ReactAndroid/src/main/android_res/com/facebook/catalyst/appcompat/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_resource", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_resource")
 
 # used by ReactToolbarManager because of Gradle
 # TODO t10182713 will be replaced with appcompat-orig when we stop using Gradle
diff --git a/ReactAndroid/src/main/java/com/facebook/BUCK b/ReactAndroid/src/main/java/com/facebook/BUCK
index acf8918c917d..bc03b864be0f 100644
--- a/ReactAndroid/src/main/java/com/facebook/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "yoga",
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/debugoverlay/model/BUCK b/ReactAndroid/src/main/java/com/facebook/debug/debugoverlay/model/BUCK
index a6bc3c884208..caed19622ab7 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/debugoverlay/model/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/debug/debugoverlay/model/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "model",
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/holder/BUCK b/ReactAndroid/src/main/java/com/facebook/debug/holder/BUCK
index 25c98e22107c..57a3818bb957 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/holder/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/debug/holder/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "holder",
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/tags/BUCK b/ReactAndroid/src/main/java/com/facebook/debug/tags/BUCK
index a722e9cde137..7349e68dcdd6 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/tags/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/debug/tags/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "tags",
diff --git a/ReactAndroid/src/main/java/com/facebook/jni/BUCK b/ReactAndroid/src/main/java/com/facebook/jni/BUCK
index 0660dbe56f11..b0dee43c7991 100644
--- a/ReactAndroid/src/main/java/com/facebook/jni/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/jni/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "jni",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/BUCK b/ReactAndroid/src/main/java/com/facebook/react/BUCK
index 9a33c9af4192..b9ed1bd4fd15 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "react",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/animated/BUCK b/ReactAndroid/src/main/java/com/facebook/react/animated/BUCK
index 4267abc376b4..245797afcd29 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/animated/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/animated/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "animated",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/animation/BUCK b/ReactAndroid/src/main/java/com/facebook/react/animation/BUCK
index 5ee48c02e3fd..0fa55d8134c0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/animation/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/animation/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "animation",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/BUCK b/ReactAndroid/src/main/java/com/facebook/react/bridge/BUCK
index 69c22f16f8b7..be6ee99800a8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target", "IS_OSS_BUILD")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "bridge",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/common/BUCK b/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
index 04d4ed2a8571..9692208304a6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_android_build_config", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_build_config", "rn_android_library")
 
 SUB_PROJECTS = [
     "network/**/*",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/common/network/BUCK b/ReactAndroid/src/main/java/com/facebook/react/common/network/BUCK
index be92d2ff22da..ae1b2ae7f656 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/common/network/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/common/network/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "network",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BUCK b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BUCK
index 76c0990a2227..16336b6e1be9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "devsupport",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
index fc9da7d6b6f9..4674caa00f04 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "YOGA_TARGET", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "fabric",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
index 38ed913d7aa4..9373a8400345 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library", "IS_OSS_BUILD")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "jsc",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
index 9998937d4703..81f476d41d97 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "react_native_target", "react_native_xplat_target", "rn_xplat_cxx_library", "FBJNI_TARGET", "ANDROID")
+load("//ReactNative:DEFS.bzl", "ANDROID", "FBJNI_TARGET", "react_native_target", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 rn_xplat_cxx_library(
     name = "jni",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/BUCK b/ReactAndroid/src/main/java/com/facebook/react/flat/BUCK
index ec7cf4c57ca8..bff3b936667b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/flat/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "flat",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/jstasks/BUCK b/ReactAndroid/src/main/java/com/facebook/react/jstasks/BUCK
index a8c84b11d5c5..55fea181c649 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/jstasks/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/jstasks/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "jstasks",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/module/annotations/BUCK b/ReactAndroid/src/main/java/com/facebook/react/module/annotations/BUCK
index 7fb76e25cba6..5fb4c959ecf4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/module/annotations/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/module/annotations/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "annotations",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/module/model/BUCK b/ReactAndroid/src/main/java/com/facebook/react/module/model/BUCK
index cab3d3e90e94..85da7f8a66a8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/module/model/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/module/model/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "model",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/module/processing/BUCK b/ReactAndroid/src/main/java/com/facebook/react/module/processing/BUCK
index dc145a71229f..c8ebf04bc92d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/module/processing/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/module/processing/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_java_annotation_processor", "rn_java_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_java_annotation_processor", "rn_java_library")
 
 rn_java_annotation_processor(
     name = "processing",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/accessibilityinfo/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/accessibilityinfo/BUCK
index ff8cd1d87b2e..2c9fcb5f4425 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/accessibilityinfo/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/accessibilityinfo/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "accessibilityinfo",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/appregistry/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/appregistry/BUCK
index 901da3967808..34947b84a03c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/appregistry/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/appregistry/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "appregistry",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/appstate/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/appstate/BUCK
index 2df792602ffc..86d7baccaa09 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/appstate/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/appstate/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "appstate",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BUCK
index 2cdd8327688c..2674bdc7fde4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "blob",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/camera/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/camera/BUCK
index 158e5719b5da..34cbb9cbbae8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/camera/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/camera/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "camera",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/clipboard/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/clipboard/BUCK
index bf37d42d9ba2..246e8fb17b11 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/clipboard/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/clipboard/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "clipboard",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/common/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/common/BUCK
index 21958467b861..265fcc86a56b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/common/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/common/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "common",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/core/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/core/BUCK
index c46015e345a5..eb5205a4c1f3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/core/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/core/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "core",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/datepicker/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/datepicker/BUCK
index 769966093ae2..c8017cafb89e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/datepicker/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/datepicker/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "datepicker",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/debug/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/debug/BUCK
index eede98dfd68f..8f301cc1f2d0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/debug/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/debug/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "debug",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/deviceinfo/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/deviceinfo/BUCK
index ad1855e03032..0b6a9250a7b3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/deviceinfo/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/deviceinfo/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "deviceinfo",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/BUCK
index e7cf90ed2846..6f0bb554ba19 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "dialog",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/fabric/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/fabric/BUCK
index e7b5d9a72c26..3286d603995e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/fabric/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/fabric/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "fabric",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/fresco/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/fresco/BUCK
index f0b8f7d0b993..168d551e5de7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/fresco/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/fresco/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "fresco",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/i18nmanager/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/i18nmanager/BUCK
index 6d2128673d39..3478c1e10e0c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/i18nmanager/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/i18nmanager/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "i18nmanager",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/image/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/image/BUCK
index 2aa7fd46a531..efb0c040eea6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/image/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/image/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "image",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/intent/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/intent/BUCK
index 3fbd36b19f51..43083558b371 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/intent/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/intent/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "intent",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/location/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/location/BUCK
index cffe25702aca..360d381076b0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/location/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/location/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "location",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/netinfo/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/netinfo/BUCK
index c29122b2af4b..81b4e1f788e9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/netinfo/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/netinfo/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "netinfo",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/network/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/network/BUCK
index ad3d4a799b61..76a899eb4b80 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/network/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/network/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "network",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/BUCK
index 468ffbf41bfc..42266b65e8d7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "permissions",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/share/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/share/BUCK
index 70ee6a732ec6..13ca4479af52 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/share/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/share/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "share",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/statusbar/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/statusbar/BUCK
index e4f39dc0c11c..525ff3d930ad 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/statusbar/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/statusbar/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "statusbar",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/storage/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/storage/BUCK
index 8806ad4532fa..be8391c2ad21 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/storage/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/storage/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "storage",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/BUCK
index 7bfe35055a3d..6563321a2651 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "systeminfo",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/timepicker/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/timepicker/BUCK
index b4e26f64a5e1..5b51a3ef489e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/timepicker/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/timepicker/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "timepicker",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/toast/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/toast/BUCK
index 7c1622c190cc..83e213e1ea8d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/toast/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/toast/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "toast",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/vibration/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/vibration/BUCK
index 4b540aa8aa1a..43ce290d72fb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/vibration/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/vibration/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "vibration",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/websocket/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/websocket/BUCK
index c9624857c4b0..989d4ce0e8e3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/websocket/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/websocket/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "websocket",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/BUCK b/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/BUCK
index 3b27ea6f3626..e0aa169fd21e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/packagerconnection/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "packagerconnection",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/processing/BUCK b/ReactAndroid/src/main/java/com/facebook/react/processing/BUCK
index f6f1683f87a8..e61d20f8cb62 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/processing/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/processing/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_java_annotation_processor", "rn_java_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_java_annotation_processor", "rn_java_library")
 
 rn_java_annotation_processor(
     name = "processing",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/shell/BUCK b/ReactAndroid/src/main/java/com/facebook/react/shell/BUCK
index 685b90f75fd6..93d4cab86b29 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/shell/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/shell/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "shell",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/touch/BUCK b/ReactAndroid/src/main/java/com/facebook/react/touch/BUCK
index 5b7dbdc25544..c4b885f791b6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/touch/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/touch/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "touch",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
index 50a22dfcb046..6020ec7df202 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "uimanager",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/BUCK b/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/BUCK
index 727d8c04dbf3..435a4533962f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "annotations",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/BUCK b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/BUCK
index 08230b0a0be1..2e8df3aca77e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "common",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/BUCK b/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/BUCK
index 9b9393650382..72c763fb9065 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "util",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/util/BUCK b/ReactAndroid/src/main/java/com/facebook/react/util/BUCK
index abbf34f4ab69..73bc3fe411b3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/util/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/util/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "util",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/art/BUCK
index 754a1f27addd..dcdd2f51cc84 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "art",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/BUCK
index 31c186d71690..16a570698f62 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "checkbox",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/common/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/common/BUCK
index 059301402c8e..223f3cb2f005 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/common/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/common/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "common",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/drawer/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/drawer/BUCK
index 70a65ded0086..18b5c8d3febb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/drawer/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/drawer/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "drawer",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
index 9646bbddfff0..223141141795 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target", "YOGA_TARGET")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 IMAGE_EVENT_FILES = [
     "ImageLoadEvent.java",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
index 75f0cd973eb3..31b024ea9220 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "imagehelper",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/modal/BUCK
index 50de0adde787..8765148822cf 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "modal",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/picker/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/picker/BUCK
index aca481694273..a558b5f5101c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/picker/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/picker/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "picker",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/BUCK
index bf73d0c46eac..83b2f43751da 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "progressbar",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/BUCK
index e2c20c51f028..247fa4a207e9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "scroll",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/slider/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/slider/BUCK
index 04d91b9bf4b5..a034f695b5d6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/slider/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/slider/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "slider",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/BUCK
index b60b696d7949..af67f891b3a4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "swiperefresh",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/BUCK
index 90811afcf8e1..1bafa2f20020 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "switchview",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/text/BUCK
index 4ed92a824f93..1b5c6c6fff7d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "text",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/BUCK
index cb24e878a784..a070c3424164 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/frescosupport/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "frescosupport",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/BUCK
index 60e261c2a202..bd919beae902 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "textinput",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/BUCK
index a3c96aab6dc4..4cc9bccd7125 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "toolbar",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/view/BUCK
index 4f0d4baeea03..601614384b96 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "YOGA_TARGET", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "view",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/BUCK
index 45ed3f183395..829b41901e0a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "viewpager",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/webview/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/webview/BUCK
index b55bad969c29..e2f8331fb950 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/webview/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/webview/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_android_library")
 
 rn_android_library(
     name = "webview",
diff --git a/ReactAndroid/src/main/jni/first-party/fb/BUCK b/ReactAndroid/src/main/jni/first-party/fb/BUCK
index a372f747440f..a63df0b4b2e5 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/BUCK
+++ b/ReactAndroid/src/main/jni/first-party/fb/BUCK
@@ -1,27 +1,27 @@
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "cxx_library", "JNI_TARGET")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "JNI_TARGET", "cxx_library")
 
 # This target is only used in open source
 if IS_OSS_BUILD:
     cxx_library(
-        name = 'jni',
-        soname = 'libfb.$(ext)',
-        srcs = glob(['*.cpp', 'jni/*.cpp', 'lyra/*.cpp']),
-        header_namespace = '',
+        name = "jni",
+        soname = "libfb.$(ext)",
+        srcs = glob(["*.cpp", "jni/*.cpp", "lyra/*.cpp"]),
+        header_namespace = "",
         compiler_flags = [
-            '-fno-omit-frame-pointer',
-            '-fexceptions',
-            '-Wall',
-            '-Werror',
-            '-std=c++11',
-            '-DDISABLE_CPUCAP',
-            '-DDISABLE_XPLAT',
+            "-fno-omit-frame-pointer",
+            "-fexceptions",
+            "-Wall",
+            "-Werror",
+            "-std=c++11",
+            "-DDISABLE_CPUCAP",
+            "-DDISABLE_XPLAT",
         ],
         exported_headers = subdir_glob([
-            ('include', 'fb/**/*.h'),
-            ('include', 'jni/*.h'),
+            ("include", "fb/**/*.h"),
+            ("include", "jni/*.h"),
         ]),
         deps = [
             JNI_TARGET,
         ],
-        visibility = ['PUBLIC'],
+        visibility = ["PUBLIC"],
     )
diff --git a/ReactAndroid/src/main/jni/first-party/fbgloginit/BUCK b/ReactAndroid/src/main/jni/first-party/fbgloginit/BUCK
index fc54ae9909d2..b38194f8d096 100644
--- a/ReactAndroid/src/main/jni/first-party/fbgloginit/BUCK
+++ b/ReactAndroid/src/main/jni/first-party/fbgloginit/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "cxx_library", "GLOG_DEP")
+load("//ReactNative:DEFS.bzl", "GLOG_DEP", "cxx_library")
 
 cxx_library(
     name = "fbgloginit",
diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/BUCK b/ReactAndroid/src/main/jni/first-party/yogajni/BUCK
index d9b12dae41c8..2bf3af1fb2f1 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/BUCK
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/BUCK
@@ -1,23 +1,23 @@
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "cxx_library", "FBJNI_TARGET")
+load("//ReactNative:DEFS.bzl", "FBJNI_TARGET", "IS_OSS_BUILD", "cxx_library")
 
 # This target is only used in open source
 if IS_OSS_BUILD:
     cxx_library(
-        name = 'jni',
-        soname = 'libyoga.$(ext)',
-        srcs = glob(['jni/*.cpp']),
-        header_namespace = '',
+        name = "jni",
+        soname = "libyoga.$(ext)",
+        srcs = glob(["jni/*.cpp"]),
+        header_namespace = "",
         compiler_flags = [
-            '-fno-omit-frame-pointer',
-            '-fexceptions',
-            '-Wall',
-            '-Werror',
-            '-O3',
-            '-std=c++11',
+            "-fno-omit-frame-pointer",
+            "-fexceptions",
+            "-Wall",
+            "-Werror",
+            "-O3",
+            "-std=c++11",
         ],
         deps = [
-            '//ReactCommon/yoga:yoga',
+            "//ReactCommon/yoga:yoga",
             FBJNI_TARGET,
         ],
-        visibility = ['PUBLIC'],
+        visibility = ["PUBLIC"],
     )
diff --git a/ReactAndroid/src/main/jni/prebuilt/BUCK b/ReactAndroid/src/main/jni/prebuilt/BUCK
index 7279eea7900f..c35807a9513a 100644
--- a/ReactAndroid/src/main/jni/prebuilt/BUCK
+++ b/ReactAndroid/src/main/jni/prebuilt/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_prebuilt_native_library", "rn_android_prebuilt_aar")
+load("//ReactNative:DEFS.bzl", "rn_android_prebuilt_aar", "rn_prebuilt_native_library")
 # Temp workaround to get the build working e2e, Gradle builds them for us
 
 rn_prebuilt_native_library(
diff --git a/ReactAndroid/src/main/jni/react/jni/BUCK b/ReactAndroid/src/main/jni/react/jni/BUCK
index 1272b44f4abd..905cc22462db 100644
--- a/ReactAndroid/src/main/jni/react/jni/BUCK
+++ b/ReactAndroid/src/main/jni/react/jni/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library", "react_native_xplat_target", "FBJNI_TARGET", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "ANDROID", "IS_OSS_BUILD")
+load("//ReactNative:DEFS.bzl", "ANDROID", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "FBJNI_TARGET", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 EXPORTED_HEADERS = [
     "AndroidJSCFactory.h",
diff --git a/ReactAndroid/src/main/jni/react/perftests/BUCK b/ReactAndroid/src/main/jni/react/perftests/BUCK
index 6baeaf89834a..35b3b1970f51 100644
--- a/ReactAndroid/src/main/jni/react/perftests/BUCK
+++ b/ReactAndroid/src/main/jni/react/perftests/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library", "react_native_xplat_target", "ANDROID")
+load("//ReactNative:DEFS.bzl", "ANDROID", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 rn_xplat_cxx_library(
     name = "perftests",
diff --git a/ReactAndroid/src/main/jni/third-party/android-ndk/BUCK b/ReactAndroid/src/main/jni/third-party/android-ndk/BUCK
index 294dfed941af..dc57bd80dc85 100644
--- a/ReactAndroid/src/main/jni/third-party/android-ndk/BUCK
+++ b/ReactAndroid/src/main/jni/third-party/android-ndk/BUCK
@@ -12,13 +12,13 @@ LIBS = (
 )
 
 for lib in LIBS:
-  prebuilt_cxx_library(
-    name = lib,
-    header_only = True,
-    exported_platform_linker_flags = [
-      ('android.*', ['-l' + lib]),
-    ],
-    visibility = [
-      'PUBLIC',
-    ],
-  )
+    prebuilt_cxx_library(
+        name = lib,
+        header_only = True,
+        exported_platform_linker_flags = [
+            ("android.*", ["-l" + lib]),
+        ],
+        visibility = [
+            "PUBLIC",
+        ],
+    )
diff --git a/ReactAndroid/src/main/libraries/fbcore/src/main/java/com/facebook/common/logging/BUCK b/ReactAndroid/src/main/libraries/fbcore/src/main/java/com/facebook/common/logging/BUCK
index fddec2c42f37..4f5bc6c890ec 100644
--- a/ReactAndroid/src/main/libraries/fbcore/src/main/java/com/facebook/common/logging/BUCK
+++ b/ReactAndroid/src/main/libraries/fbcore/src/main/java/com/facebook/common/logging/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "logging",
diff --git a/ReactAndroid/src/main/res/BUCK b/ReactAndroid/src/main/res/BUCK
index 75fd8aa656a5..00aac50e5810 100644
--- a/ReactAndroid/src/main/res/BUCK
+++ b/ReactAndroid/src/main/res/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_resource", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_target", "rn_android_resource")
 
 rn_android_resource(
     name = "devsupport",
diff --git a/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK b/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
index 00ee6d55a874..d3338e4aa630 100644
--- a/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
+++ b/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "rn_prebuilt_jar")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library", "rn_prebuilt_jar")
 
 rn_android_library(
     name = "robolectric",
diff --git a/ReactAndroid/src/test/java/com/facebook/common/logging/BUCK b/ReactAndroid/src/test/java/com/facebook/common/logging/BUCK
index 2592f15dea43..bde102da955d 100644
--- a/ReactAndroid/src/test/java/com/facebook/common/logging/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/common/logging/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "logging",
diff --git a/ReactAndroid/src/test/java/com/facebook/react/BUCK b/ReactAndroid/src/test/java/com/facebook/react/BUCK
index 250a4c23a205..3551cdbeb108 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_robolectric_test")
 
 rn_robolectric_test(
     name = "react",
diff --git a/ReactAndroid/src/test/java/com/facebook/react/animated/BUCK b/ReactAndroid/src/test/java/com/facebook/react/animated/BUCK
index 8922cab95b66..4849a1659049 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/animated/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/animated/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "react_native_dep", "react_native_target", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_robolectric_test")
 
 rn_robolectric_test(
     name = "animated",
diff --git a/ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK b/ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK
index 13c4aaa7672a..b92de1b5f551 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep", "react_native_target", "rn_robolectric_test", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_android_library", "rn_robolectric_test")
 
 STANDARD_TEST_SRCS = [
     "*Test.java",
diff --git a/ReactAndroid/src/test/java/com/facebook/react/devsupport/BUCK b/ReactAndroid/src/test/java/com/facebook/react/devsupport/BUCK
index de5c73bae022..0b3fd967a291 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/devsupport/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/devsupport/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "react_native_dep", "react_native_target", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_robolectric_test")
 
 rn_robolectric_test(
     name = "devsupport",
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
index 6cfe34c2e058..874e64a7ec8a 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_robolectric_test", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_robolectric_test")
 
 if not IS_OSS_BUILD:
     rn_robolectric_test(
diff --git a/ReactAndroid/src/test/java/com/facebook/react/modules/BUCK b/ReactAndroid/src/test/java/com/facebook/react/modules/BUCK
index 860bbf7bf69f..e894c42db496 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/modules/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/modules/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_robolectric_test")
 
 rn_robolectric_test(
     name = "modules",
diff --git a/ReactAndroid/src/test/java/com/facebook/react/packagerconnection/BUCK b/ReactAndroid/src/test/java/com/facebook/react/packagerconnection/BUCK
index 12ef1f5fa30d..686a8ecf6c80 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/packagerconnection/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/packagerconnection/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "react_native_dep", "react_native_target")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "react_native_target", "rn_robolectric_test")
 
 rn_robolectric_test(
     name = "packagerconnection",
diff --git a/ReactAndroid/src/test/java/com/facebook/react/uimanager/BUCK b/ReactAndroid/src/test/java/com/facebook/react/uimanager/BUCK
index 385a2d6609b1..608ba5605db2 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/uimanager/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/uimanager/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_robolectric_test")
 
 rn_robolectric_test(
     name = "uimanager",
diff --git a/ReactAndroid/src/test/java/com/facebook/react/views/BUCK b/ReactAndroid/src/test/java/com/facebook/react/views/BUCK
index 50df82ab6a6c..dc64ad96ed30 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/views/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/views/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_robolectric_test", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target")
+load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_robolectric_test")
 
 rn_robolectric_test(
     name = "views",
diff --git a/ReactAndroid/src/test/java/org/mockito/configuration/BUCK b/ReactAndroid/src/test/java/org/mockito/configuration/BUCK
index 3f6f74e29184..62bf39782350 100644
--- a/ReactAndroid/src/test/java/org/mockito/configuration/BUCK
+++ b/ReactAndroid/src/test/java/org/mockito/configuration/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_android_library", "react_native_dep")
+load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "configuration",
diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 9fa2e3aa4043..12bd664f293a 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_android_inspector_flags", "get_apple_inspector_flags", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//ReactNative:DEFS.bzl", "ANDROID", "ANDROID_JSC_DEPS", "APPLE", "APPLE_JSC_DEPS", "IS_OSS_BUILD", "get_android_inspector_flags", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 CXX_LIBRARY_COMPILER_FLAGS = [
     "-std=c++14",
@@ -10,8 +10,9 @@ APPLE_COMPILER_FLAGS = []
 DEBUG_PREPROCESSOR_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_debug_preprocessor_flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
     DEBUG_PREPROCESSOR_FLAGS = get_debug_preprocessor_flags()
 
 rn_xplat_cxx_library(
diff --git a/ReactCommon/cxxreact/tests/BUCK b/ReactCommon/cxxreact/tests/BUCK
index 67160139c882..f7a3416fd486 100644
--- a/ReactCommon/cxxreact/tests/BUCK
+++ b/ReactCommon/cxxreact/tests/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "APPLE_JSC_DEPS", "ANDROID_JSC_DEPS")
+load("//ReactNative:DEFS.bzl", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "IS_OSS_BUILD", "react_native_xplat_target")
 
 TEST_SRCS = [
     "RecoverableErrorTest.cpp",
@@ -14,41 +14,42 @@ if not IS_OSS_BUILD:
     load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
     load("@xplat//configurations/buck/android:jni_instrumentation_test", "jni_instrumentation_test_lib")
     load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+
     jni_instrumentation_test_lib(
-        name = 'tests',
-        class_under_test = 'com/facebook/react/XplatBridgeTest',
-        soname = 'libxplat-bridge.so',
+        name = "tests",
+        class_under_test = "com/facebook/react/XplatBridgeTest",
+        soname = "libxplat-bridge.so",
         srcs = TEST_SRCS,
         compiler_flags = [
-            '-fexceptions',
-            '-frtti',
-            '-std=c++14',
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
         ],
         deps = [
-            'xplat//third-party/linker_lib:android',
-            'xplat//third-party/gmock:gtest',
-            react_native_xplat_target('cxxreact:bridge'),
+            "xplat//third-party/linker_lib:android",
+            "xplat//third-party/gmock:gtest",
+            react_native_xplat_target("cxxreact:bridge"),
         ] + ANDROID_JSC_DEPS,
         visibility = [
-            'fbandroid//instrumentation_tests/...'
+            "fbandroid//instrumentation_tests/...",
         ],
     )
 
     fb_xplat_cxx_test(
-        name = 'tests',
+        name = "tests",
         srcs = TEST_SRCS,
         compiler_flags = [
-            '-fexceptions',
-            '-frtti',
+            "-fexceptions",
+            "-frtti",
         ],
         platforms = APPLE,
         deps = [
-            'xplat//folly:molly',
-            'xplat//third-party/gmock:gtest',
-            react_native_xplat_target('cxxreact:bridge'),
-            react_native_xplat_target('jschelpers:jschelpers'),
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            react_native_xplat_target("cxxreact:bridge"),
+            react_native_xplat_target("jschelpers:jschelpers"),
         ] + APPLE_JSC_DEPS,
         visibility = [
-            react_native_xplat_target('cxxreact/...'),
+            react_native_xplat_target("cxxreact/..."),
         ],
     )
diff --git a/ReactCommon/fabric/attributedstring/BUCK b/ReactCommon/fabric/attributedstring/BUCK
index e6aa5bab5567..8f2c481cb177 100644
--- a/ReactCommon/fabric/attributedstring/BUCK
+++ b/ReactCommon/fabric/attributedstring/BUCK
@@ -1,11 +1,12 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "attributedstring",
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 02c39ac75579..e63e79ad94d7 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -1,11 +1,12 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "core",
diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index 41fe3bcc5c77..8bdc3602d502 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -1,11 +1,12 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "debug",
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index 2cd6abacfdf0..ed4891382ef2 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -1,11 +1,12 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "graphics",
diff --git a/ReactCommon/fabric/scrollview/BUCK b/ReactCommon/fabric/scrollview/BUCK
index f653943119e2..ed66b72142d1 100644
--- a/ReactCommon/fabric/scrollview/BUCK
+++ b/ReactCommon/fabric/scrollview/BUCK
@@ -1,11 +1,12 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "scrollview",
diff --git a/ReactCommon/fabric/text/BUCK b/ReactCommon/fabric/text/BUCK
index 9ee6fca05f03..b6450f454450 100644
--- a/ReactCommon/fabric/text/BUCK
+++ b/ReactCommon/fabric/text/BUCK
@@ -1,11 +1,12 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "text",
diff --git a/ReactCommon/fabric/textlayoutmanager/BUCK b/ReactCommon/fabric/textlayoutmanager/BUCK
index be8ed19c2885..26f57ef0e908 100644
--- a/ReactCommon/fabric/textlayoutmanager/BUCK
+++ b/ReactCommon/fabric/textlayoutmanager/BUCK
@@ -1,11 +1,12 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "textlayoutmanager",
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 78a4c7ae1fff..2bd48978112f 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -1,11 +1,12 @@
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_xplat_target", "rn_xplat_cxx_library", "get_apple_inspector_flags", "ANDROID", "APPLE")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "uimanager",
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 5665baed32ee..a641805444c7 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -1,11 +1,12 @@
-load("//configurations/buck/apple:flag_defs.bzl", "get_application_ios_flags", "get_debug_preprocessor_flags", "OBJC_ARC_PREPROCESSOR_FLAGS")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "rn_xplat_cxx_library", "get_apple_inspector_flags", "react_native_xplat_target", "ANDROID", "APPLE")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 APPLE_COMPILER_FLAGS = []
 
 if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "get_static_library_ios_flags", "flags")
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), 'compiler_flags')
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
 
 rn_xplat_cxx_library(
     name = "view",
diff --git a/ReactCommon/jschelpers/BUCK b/ReactCommon/jschelpers/BUCK
index 76939bba19e6..990bb9882fa5 100644
--- a/ReactCommon/jschelpers/BUCK
+++ b/ReactCommon/jschelpers/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library", "react_native_xplat_target", "ANDROID_JSC_INTERNAL_DEPS", "APPLE_JSC_INTERNAL_DEPS", "ANDROID", "APPLE")
+load("//ReactNative:DEFS.bzl", "ANDROID", "ANDROID_JSC_INTERNAL_DEPS", "APPLE", "APPLE_JSC_INTERNAL_DEPS", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 EXPORTED_HEADERS = [
     "JavaScriptCore.h",
diff --git a/ReactCommon/microprofiler/BUCK b/ReactCommon/microprofiler/BUCK
index 2b05e8e52c05..d35af4ee2cbd 100644
--- a/ReactCommon/microprofiler/BUCK
+++ b/ReactCommon/microprofiler/BUCK
@@ -1,4 +1,4 @@
-load("//ReactNative:DEFS.bzl", "cxx_library", "GLOG_DEP")
+load("//ReactNative:DEFS.bzl", "GLOG_DEP", "cxx_library")
 
 cxx_library(
     name = "microprofiler",

From eba62803b50991418423ff57a5bfd29acd51c002 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Mon, 21 May 2018 07:52:30 -0700
Subject: [PATCH 0627/1109] Bump Metro to 0.37.1

Reviewed By: rafeca

Differential Revision: D8038396

fbshipit-source-id: 33fe5499825653f205bdb588ff4c7fa232602f24
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 1dd9adaf072c..7f6941ff0777 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.37.0",
-    "metro-babel-register": "^0.37.0",
-    "metro-core": "^0.37.0",
-    "metro-memory-fs": "^0.37.0",
+    "metro": "^0.37.1",
+    "metro-babel-register": "^0.37.1",
+    "metro-core": "^0.37.1",
+    "metro-memory-fs": "^0.37.1",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 10814e2e617259cc177b45c6f5f94de1be9807f4 Mon Sep 17 00:00:00 2001
From: Nurzhan Bakibayev <hypuk@fb.com>
Date: Mon, 21 May 2018 11:08:25 -0700
Subject: [PATCH 0628/1109] Remove __fbUninstallRNGlobalErrorHandler

Reviewed By: pakoito

Differential Revision: D7831179

fbshipit-source-id: 6db9fe617d5a1a23a4aa46c9c3028db13a7a52a0
---
 Libraries/BatchedBridge/MessageQueue.js | 8 ++------
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/Libraries/BatchedBridge/MessageQueue.js b/Libraries/BatchedBridge/MessageQueue.js
index 2d22b90a44c3..7cdc5fe1805d 100644
--- a/Libraries/BatchedBridge/MessageQueue.js
+++ b/Libraries/BatchedBridge/MessageQueue.js
@@ -303,12 +303,8 @@ class MessageQueue {
   __shouldPauseOnThrow() {
     return (
       // $FlowFixMe
-      (typeof DebuggerInternal !== 'undefined' &&
-        DebuggerInternal.shouldPauseOnThrow === true) || // eslint-disable-line no-undef
-      // FIXME(festevezga) Remove once T24034309 is rolled out internally
-      // $FlowFixMe
-      (typeof __fbUninstallRNGlobalErrorHandler !== 'undefined' &&
-        __fbUninstallRNGlobalErrorHandler === true) // eslint-disable-line no-undef
+      typeof DebuggerInternal !== 'undefined' &&
+      DebuggerInternal.shouldPauseOnThrow === true // eslint-disable-line no-undef
     );
   }
 

From 33ffa79a51d4db9ba69148861f2da304646175cd Mon Sep 17 00:00:00 2001
From: Oleg Lokhvitsky <olegbl@fb.com>
Date: Mon, 21 May 2018 11:09:52 -0700
Subject: [PATCH 0629/1109] Prevent RefreshControl from getting stuck when a
 parent is scrolled horizontally

Reviewed By: achen1

Differential Revision: D8044763

fbshipit-source-id: 8f3351de13eb17d2937f3b9e76500889398f9c59
---
 .../react/views/swiperefresh/ReactSwipeRefreshLayout.java | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/ReactSwipeRefreshLayout.java b/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/ReactSwipeRefreshLayout.java
index 3ffa43dfde93..2512b2b21c41 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/ReactSwipeRefreshLayout.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/ReactSwipeRefreshLayout.java
@@ -89,6 +89,14 @@ public void requestDisallowInterceptTouchEvent(boolean disallowIntercept) {
   public boolean onInterceptTouchEvent(MotionEvent ev) {
     if (shouldInterceptTouchEvent(ev) && super.onInterceptTouchEvent(ev)) {
       NativeGestureUtil.notifyNativeGestureStarted(this, ev);
+
+      // If the pull-to-refresh gesture is interrupted by a parent with its own
+      // onInterceptTouchEvent then the refresh indicator gets stuck on-screen
+      // so we ask the parent to not intercept this touch event after it started
+      if (getParent() != null) {
+        getParent().requestDisallowInterceptTouchEvent(true);
+      }
+
       return true;
     }
     return false;

From 782971f60ecb333c73f14464aca8a43a76f3adac Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Mon, 21 May 2018 11:42:07 -0700
Subject: [PATCH 0630/1109] Move Native Extensions from JSContext layer to
 ContextFactory

Reviewed By: michalgr

Differential Revision: D8057886

fbshipit-source-id: 45a63d909169c9a40414de9cd54bdb411f9f595d
---
 .../modules/deviceinfo/DeviceInfoModule.java  | 11 ++++---
 .../react/uimanager/DisplayMetricsHolder.java | 30 +++++++++++++++----
 2 files changed, 30 insertions(+), 11 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/deviceinfo/DeviceInfoModule.java b/ReactAndroid/src/main/java/com/facebook/react/modules/deviceinfo/DeviceInfoModule.java
index ea2f46948121..0b9e95b24014 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/deviceinfo/DeviceInfoModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/deviceinfo/DeviceInfoModule.java
@@ -13,13 +13,10 @@
 import java.util.Map;
 
 import android.content.Context;
-import android.util.DisplayMetrics;
 
-import com.facebook.react.bridge.Arguments;
 import com.facebook.react.bridge.BaseJavaModule;
 import com.facebook.react.bridge.LifecycleEventListener;
 import com.facebook.react.bridge.ReactApplicationContext;
-import com.facebook.react.bridge.WritableMap;
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.modules.core.DeviceEventManagerModule;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
@@ -27,10 +24,12 @@
 /**
  * Module that exposes Android Constants to JS.
  */
-@ReactModule(name = "DeviceInfo")
+@ReactModule(name = DeviceInfoModule.sModuleName)
 public class DeviceInfoModule extends BaseJavaModule implements
     LifecycleEventListener {
 
+  static final String sModuleName = "DeviceInfo";
+
   private @Nullable ReactApplicationContext mReactApplicationContext;
   private float mFontScale;
 
@@ -48,7 +47,7 @@ public DeviceInfoModule(Context context) {
 
   @Override
   public String getName() {
-    return "DeviceInfo";
+    return sModuleName;
   }
 
   @Override
@@ -88,6 +87,6 @@ public void emitUpdateDimensionsEvent() {
 
     mReactApplicationContext
         .getJSModule(DeviceEventManagerModule.RCTDeviceEventEmitter.class)
-        .emit("didUpdateDimensions", DisplayMetricsHolder.getDisplayMetricsMap(mFontScale));
+        .emit("didUpdateDimensions", DisplayMetricsHolder.getDisplayMetricsNativeMap(mFontScale));
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/DisplayMetricsHolder.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/DisplayMetricsHolder.java
index 4d2ad3b55d2d..502242591f24 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/DisplayMetricsHolder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/DisplayMetricsHolder.java
@@ -11,6 +11,8 @@
 
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
+import java.util.HashMap;
+import java.util.Map;
 
 import android.content.Context;
 import android.os.Build;
@@ -104,18 +106,37 @@ public static DisplayMetrics getScreenDisplayMetrics() {
     return sScreenDisplayMetrics;
   }
 
-  public static WritableNativeMap getDisplayMetricsMap(double fontScale) {
+  public static Map<String, Map<String, Object>> getDisplayMetricsMap(double fontScale) {
+    Assertions.assertNotNull(
+        sWindowDisplayMetrics != null || sScreenDisplayMetrics != null,
+        "DisplayMetricsHolder must be initialized with initDisplayMetricsIfNotInitialized or initDisplayMetrics");
+    final Map<String, Map<String, Object>> result = new HashMap<>();
+    result.put("windowPhysicalPixels", getPhysicalPixelsMap(sWindowDisplayMetrics, fontScale));
+    result.put("screenPhysicalPixels", getPhysicalPixelsMap(sScreenDisplayMetrics, fontScale));
+    return result;
+  }
+
+  public static WritableNativeMap getDisplayMetricsNativeMap(double fontScale) {
     Assertions.assertNotNull(
         sWindowDisplayMetrics != null || sScreenDisplayMetrics != null,
         "DisplayMetricsHolder must be initialized with initDisplayMetricsIfNotInitialized or initDisplayMetrics");
     final WritableNativeMap result = new WritableNativeMap();
-    result.putMap("windowPhysicalPixels", getPhysicalPixelsMap(sWindowDisplayMetrics, fontScale));
-    result.putMap("screenPhysicalPixels", getPhysicalPixelsMap(sScreenDisplayMetrics, fontScale));
+    result.putMap("windowPhysicalPixels", getPhysicalPixelsNativeMap(sWindowDisplayMetrics, fontScale));
+    result.putMap("screenPhysicalPixels", getPhysicalPixelsNativeMap(sScreenDisplayMetrics, fontScale));
+    return result;
+  }
 
+  private static Map<String, Object> getPhysicalPixelsMap(DisplayMetrics displayMetrics, double fontScale) {
+    final Map<String, Object> result = new HashMap<>();
+    result.put("width", displayMetrics.widthPixels);
+    result.put("height", displayMetrics.heightPixels);
+    result.put("scale", displayMetrics.density);
+    result.put("fontScale", fontScale);
+    result.put("densityDpi", displayMetrics.densityDpi);
     return result;
   }
 
-  private static WritableNativeMap getPhysicalPixelsMap(DisplayMetrics displayMetrics, double fontScale) {
+  private static WritableNativeMap getPhysicalPixelsNativeMap(DisplayMetrics displayMetrics, double fontScale) {
     final WritableNativeMap result = new WritableNativeMap();
     result.putInt("width", displayMetrics.widthPixels);
     result.putInt("height", displayMetrics.heightPixels);
@@ -124,5 +145,4 @@ private static WritableNativeMap getPhysicalPixelsMap(DisplayMetrics displayMetr
     result.putDouble("densityDpi", displayMetrics.densityDpi);
     return result;
   }
-
 }

From 7c5845a5a26592598c9380df078766a680a23f06 Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Mon, 21 May 2018 11:42:09 -0700
Subject: [PATCH 0631/1109] Remove Native Extensions

Reviewed By: michalgr

Differential Revision: D8057885

fbshipit-source-id: 6af7f7729201d26a704adaadb15813979cd035f8
---
 React/CxxBridge/RCTCxxBridge.mm               |  1 -
 .../main/jni/react/jni/AndroidJSCFactory.cpp  |  4 +--
 .../main/jni/react/jni/AndroidJSCFactory.h    |  2 +-
 .../src/main/jni/react/jni/OnLoad.cpp         |  2 +-
 ReactCommon/cxxreact/JSCExecutor.cpp          | 25 +++----------------
 ReactCommon/cxxreact/JSCExecutor.h            | 10 +++-----
 6 files changed, 10 insertions(+), 34 deletions(-)

diff --git a/React/CxxBridge/RCTCxxBridge.mm b/React/CxxBridge/RCTCxxBridge.mm
index 6fa0813996e9..d820d2f10e31 100644
--- a/React/CxxBridge/RCTCxxBridge.mm
+++ b/React/CxxBridge/RCTCxxBridge.mm
@@ -338,7 +338,6 @@ - (void)start
   #if RCT_PROFILE
         ("StartSamplingProfilerOnInit", (bool)self.devSettings.startSamplingProfilerOnLaunch)
   #endif
-         , nullptr
       ));
     }
   } else {
diff --git a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
index 5208152f54a9..20da272c727a 100644
--- a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
@@ -113,9 +113,9 @@ void injectJSCExecutorAndroidPlatform() {
 }
 
 std::unique_ptr<JSExecutorFactory> makeAndroidJSCExecutorFactory(
-    const folly::dynamic& jscConfig, NativeExtensionsProvider nativeExtensionsProvider) {
+    const folly::dynamic& jscConfig) {
   detail::injectJSCExecutorAndroidPlatform();
-  return folly::make_unique<JSCExecutorFactory>(std::move(jscConfig), std::move(nativeExtensionsProvider));
+  return folly::make_unique<JSCExecutorFactory>(std::move(jscConfig));
 }
 
 }
diff --git a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
index 5de2f99eefc7..8ad7a34df84b 100644
--- a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
+++ b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
@@ -24,7 +24,7 @@ void injectJSCExecutorAndroidPlatform();
 }
 
 std::unique_ptr<JSExecutorFactory> makeAndroidJSCExecutorFactory(
-    const folly::dynamic& jscConfig, NativeExtensionsProvider nativeExtensionsProvider);
+    const folly::dynamic& jscConfig);
 
 }
 }
diff --git a/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp b/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
index 7e7184e71124..662c8bdf2c52 100644
--- a/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
@@ -34,7 +34,7 @@ class JSCJavaScriptExecutorHolder : public HybridClass<JSCJavaScriptExecutorHold
   static constexpr auto kJavaDescriptor = "Lcom/facebook/react/bridge/JSCJavaScriptExecutor;";
 
   static local_ref<jhybriddata> initHybrid(alias_ref<jclass>, ReadableNativeMap* jscConfig) {
-    return makeCxxInstance(makeAndroidJSCExecutorFactory(jscConfig->consume(), nullptr));
+    return makeCxxInstance(makeAndroidJSCExecutorFactory(jscConfig->consume()));
   }
 
   static void registerNatives() {
diff --git a/ReactCommon/cxxreact/JSCExecutor.cpp b/ReactCommon/cxxreact/JSCExecutor.cpp
index 2f1f24fd9676..3c66fb39edc2 100644
--- a/ReactCommon/cxxreact/JSCExecutor.cpp
+++ b/ReactCommon/cxxreact/JSCExecutor.cpp
@@ -120,19 +120,17 @@ std::unique_ptr<JSExecutor> JSCExecutorFactory::createJSExecutor(
     std::shared_ptr<ExecutorDelegate> delegate,
     std::shared_ptr<MessageQueueThread> jsQueue) {
   return folly::make_unique<JSCExecutor>(
-      delegate, jsQueue, m_jscConfig, m_nativeExtensionsProvider);
+      delegate, jsQueue, m_jscConfig);
 }
 
 JSCExecutor::JSCExecutor(
     std::shared_ptr<ExecutorDelegate> delegate,
     std::shared_ptr<MessageQueueThread> messageQueueThread,
-    const folly::dynamic& jscConfig,
-    NativeExtensionsProvider nativeExtensionsProvider) throw(JSException)
+    const folly::dynamic& jscConfig) throw(JSException)
     : m_delegate(delegate),
       m_messageQueueThread(messageQueueThread),
       m_nativeModules(delegate ? delegate->getModuleRegistry() : nullptr),
-      m_jscConfig(jscConfig),
-      m_nativeExtensionsProvider(nativeExtensionsProvider) {
+      m_jscConfig(jscConfig) {
   initOnJSVMThread();
 
   {
@@ -142,12 +140,6 @@ JSCExecutor::JSCExecutor(
         "nativeModuleProxy",
         exceptionWrapMethod<&JSCExecutor::getNativeModule>());
   }
-  if (nativeExtensionsProvider) {
-    installGlobalProxy(
-        m_context,
-        "nativeExtensions",
-        exceptionWrapMethod<&JSCExecutor::getNativeExtension>());
-  }
 }
 
 JSCExecutor::~JSCExecutor() {
@@ -732,17 +724,6 @@ JSValueRef JSCExecutor::getNativeModule(
   return m_nativeModules.getModule(m_context, propertyName);
 }
 
-JSValueRef JSCExecutor::getNativeExtension(
-    JSObjectRef object,
-    JSStringRef propertyName) {
-  if (m_nativeExtensionsProvider) {
-    folly::dynamic value =
-        m_nativeExtensionsProvider(String::ref(m_context, propertyName).str());
-    return Value::fromDynamic(m_context, std::move(value));
-  }
-  return JSC_JSValueMakeUndefined(m_context);
-}
-
 JSValueRef JSCExecutor::nativeRequire(
     size_t count,
     const JSValueRef arguments[]) {
diff --git a/ReactCommon/cxxreact/JSCExecutor.h b/ReactCommon/cxxreact/JSCExecutor.h
index b85e590d7136..151ded934015 100644
--- a/ReactCommon/cxxreact/JSCExecutor.h
+++ b/ReactCommon/cxxreact/JSCExecutor.h
@@ -27,15 +27,14 @@ class RAMBundleRegistry;
 
 class RN_EXPORT JSCExecutorFactory : public JSExecutorFactory {
 public:
-  JSCExecutorFactory(const folly::dynamic& jscConfig, NativeExtensionsProvider provider) :
-    m_jscConfig(jscConfig), m_nativeExtensionsProvider(provider) {}
+  JSCExecutorFactory(const folly::dynamic& jscConfig) :
+    m_jscConfig(jscConfig) {}
   std::unique_ptr<JSExecutor> createJSExecutor(
     std::shared_ptr<ExecutorDelegate> delegate,
     std::shared_ptr<MessageQueueThread> jsQueue) override;
 private:
   std::string m_cacheDir;
   folly::dynamic m_jscConfig;
-  NativeExtensionsProvider m_nativeExtensionsProvider;
 };
 
 template<typename T>
@@ -59,8 +58,7 @@ class RN_EXPORT JSCExecutor : public JSExecutor, public PrivateDataBase {
    */
   explicit JSCExecutor(std::shared_ptr<ExecutorDelegate> delegate,
                        std::shared_ptr<MessageQueueThread> messageQueueThread,
-                       const folly::dynamic& jscConfig,
-                       NativeExtensionsProvider nativeExtensionsProvider) throw(JSException);
+                       const folly::dynamic& jscConfig) throw(JSException);
   ~JSCExecutor() override;
 
   virtual void loadApplicationScript(
@@ -104,7 +102,6 @@ class RN_EXPORT JSCExecutor : public JSExecutor, public PrivateDataBase {
   JSCNativeModules m_nativeModules;
   folly::dynamic m_jscConfig;
   std::once_flag m_bindFlag;
-  NativeExtensionsProvider m_nativeExtensionsProvider;
 
   folly::Optional<Object> m_invokeCallbackAndReturnFlushedQueueJS;
   folly::Optional<Object> m_callFunctionReturnFlushedQueueJS;
@@ -126,7 +123,6 @@ class RN_EXPORT JSCExecutor : public JSExecutor, public PrivateDataBase {
   void installNativeHook(const char* name);
 
   JSValueRef getNativeModule(JSObjectRef object, JSStringRef propertyName);
-  JSValueRef getNativeExtension(JSObjectRef object, JSStringRef propertyName);
 
   JSValueRef nativeRequire(
       size_t argumentCount,

From e2ce22b823661a7dcf6b70a825921a2910383bd1 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 21 May 2018 12:00:01 -0700
Subject: [PATCH 0632/1109] RN: Fix Reponder Logic in Text

Summary:
Fixes a bug I accidentally introduced in the responder logic for `Text`.

I forgot that I was using arrow functions to preserve `context` while still relying on the creation of `arguments`. Oops.

Differential Revision: D8077595

fbshipit-source-id: 1f7dc11ea90ca4d6bb2129823ba09c79fb5a32b0
---
 Libraries/Text/Text.js | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index 884c86a5e964..5da883aa6309 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -167,25 +167,25 @@ class TouchableText extends React.Component<Props, State> {
       onResponderGrant: (event: SyntheticEvent<>, dispatchID: string): void => {
         nullthrows(this.touchableHandleResponderGrant)(event, dispatchID);
         if (this.props.onResponderGrant != null) {
-          this.props.onResponderGrant.apply(this, arguments);
+          this.props.onResponderGrant.call(this, event, dispatchID);
         }
       },
       onResponderMove: (event: SyntheticEvent<>): void => {
         nullthrows(this.touchableHandleResponderMove)(event);
         if (this.props.onResponderMove != null) {
-          this.props.onResponderMove.apply(this, arguments);
+          this.props.onResponderMove.call(this, event);
         }
       },
       onResponderRelease: (event: SyntheticEvent<>): void => {
         nullthrows(this.touchableHandleResponderRelease)(event);
         if (this.props.onResponderRelease != null) {
-          this.props.onResponderRelease.apply(this, arguments);
+          this.props.onResponderRelease.call(this, event);
         }
       },
       onResponderTerminate: (event: SyntheticEvent<>): void => {
         nullthrows(this.touchableHandleResponderTerminate)(event);
         if (this.props.onResponderTerminate != null) {
-          this.props.onResponderTerminate.apply(this, arguments);
+          this.props.onResponderTerminate.call(this, event);
         }
       },
       onResponderTerminationRequest: (): boolean => {

From 18b8dbb9bbebcc9542d2781ace609b56fc4b370c Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Mon, 21 May 2018 12:07:35 -0700
Subject: [PATCH 0633/1109] Wire up event handler bindings

Reviewed By: shergin

Differential Revision: D8068507

fbshipit-source-id: 26326416c0b04cd52dc53af5d91010a1b27e0ec7
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 5 +++++
 ReactCommon/fabric/uimanager/FabricUIManager.h   | 1 +
 2 files changed, 6 insertions(+)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 1e74831ea4a6..8a9d6916b275 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -215,5 +215,10 @@ void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedLi
   }
 }
 
+void FabricUIManager::registerEventHandler(void *eventHandler) {
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::registerEventHandler(eventHandler)";
+  // TODO: Store eventHandler handle.
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index 1fa11b521d76..4fb64c780f0e 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -44,6 +44,7 @@ class FabricUIManager {
   SharedShadowNodeUnsharedList createChildSet(Tag rootTag);
   void appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode);
   void completeRoot(Tag rootTag, const SharedShadowNodeUnsharedList &childSet);
+  void registerEventHandler(void *eventHandler);
 
 private:
   SharedComponentDescriptorRegistry componentDescriptorRegistry_;

From 3bcfdc4b9f00c79f36854405eea58f502f683a95 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 21 May 2018 17:43:06 -0700
Subject: [PATCH 0634/1109] Add more fabric logging information

Reviewed By: fkgozali

Differential Revision: D8084526

fbshipit-source-id: f59c5e60b4814229835a9eaa64bbb45242d04211
---
 .../com/facebook/react/uimanager/ReactShadowNodeImpl.java     | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index a6c152066782..27a70d16780c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -1064,8 +1064,8 @@ private void getHierarchyInfoWithIndentation(StringBuilder result, int level) {
       result.append("  ");
     }
 
-    result.append("<").append(getClass().getSimpleName()).append(" tag=").append(getReactTag()).append(" gen=")
-      .append(mGenerationDebugInformation);
+    result.append("<").append(getClass().getSimpleName()).append(" view='").append(getViewClass())
+      .append("' tag=").append(getReactTag()).append(" gen=").append(mGenerationDebugInformation);
     if (mYogaNode != null) {
       result.append(" layout='x:").append(getScreenX())
         .append(" y:").append(getScreenY()).append(" w:").append(getLayoutWidth()).append(" h:")

From f180300606b1ae894c26721889670c23594eee25 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 21 May 2018 19:59:05 -0700
Subject: [PATCH 0635/1109] Fabric: Support for object notation in
 dynamic-to-Point/Size/Edges converstions

Summary: Trivial.

Reviewed By: fkgozali

Differential Revision: D8086650

fbshipit-source-id: 0850c799811f7cda2dd6786aada6222dcc28a3e4
---
 ReactCommon/fabric/graphics/conversions.h | 17 +++++++++++++++++
 1 file changed, 17 insertions(+)

diff --git a/ReactCommon/fabric/graphics/conversions.h b/ReactCommon/fabric/graphics/conversions.h
index 2ca159c73857..061725c012ac 100644
--- a/ReactCommon/fabric/graphics/conversions.h
+++ b/ReactCommon/fabric/graphics/conversions.h
@@ -60,6 +60,10 @@ inline void fromDynamic(const folly::dynamic &value, Float &result) {
 }
 
 inline void fromDynamic(const folly::dynamic &value, Point &result) {
+  if (value.isObject()) {
+    result = Point {(Float)value["x"].asDouble(), (Float)value["y"].asDouble()};
+    return;
+  }
   if (value.isArray()) {
     result = Point {(Float)value[0].asDouble(), (Float)value[1].asDouble()};
     return;
@@ -68,6 +72,10 @@ inline void fromDynamic(const folly::dynamic &value, Point &result) {
 }
 
 inline void fromDynamic(const folly::dynamic &value, Size &result) {
+  if (value.isObject()) {
+    result = Size {(Float)value["width"].asDouble(), (Float)value["height"].asDouble()};
+    return;
+  }
   if (value.isArray()) {
     result = Size {(Float)value[0].asDouble(), (Float)value[1].asDouble()};
     return;
@@ -76,6 +84,15 @@ inline void fromDynamic(const folly::dynamic &value, Size &result) {
 }
 
 inline void fromDynamic(const folly::dynamic &value, EdgeInsets &result) {
+  if (value.isObject()) {
+    result = EdgeInsets {
+      (Float)value["top"].asDouble(),
+      (Float)value["left"].asDouble(),
+      (Float)value["bottom"].asDouble(),
+      (Float)value["right"].asDouble()
+    };
+    return;
+  }
   if (value.isArray()) {
     result = EdgeInsets {
       (Float)value[0].asDouble(),

From 5028d48382928db1cca140c64f2079bde562d8b8 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Tue, 22 May 2018 00:05:17 -0700
Subject: [PATCH 0636/1109] Wire up event handler bindings

Reviewed By: mdvacca

Differential Revision: D8048409

fbshipit-source-id: 5706130607302b4be2287cc303def7c2fb398bc8
---
 .../react/fabric/FabricUIManager.java         |  4 +
 .../react/fabric/jsc/FabricJSCBinding.java    | 11 +++
 .../react/fabric/jsc/jni/FabricJSCBinding.cpp | 73 ++++++++++++++++++-
 .../react/fabric/jsc/jni/FabricJSCBinding.h   | 11 +++
 4 files changed, 98 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 0eabd18204fb..e4285dff8747 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -71,6 +71,10 @@ public FabricUIManager(
     mFabricReconciler = new FabricReconciler(mUIViewOperationQueue);
   }
 
+  public void registerEventHandler(long eventHandlerPointer) {
+    // TODO: Release this event handler at some point.
+  }
+
   /** Creates a new {@link ReactShadowNode} */
   @Nullable
   public ReactShadowNode createNode(
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
index bc2c8e9269fc..190a1aefcbbd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
@@ -12,6 +12,7 @@
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.fabric.FabricBinding;
 import com.facebook.react.fabric.FabricUIManager;
+import com.facebook.react.bridge.NativeMap;
 import com.facebook.soloader.SoLoader;
 
 @DoNotStrip
@@ -31,6 +32,16 @@ public class FabricJSCBinding implements FabricBinding {
 
   private native void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
 
+  private native void releaseEventHandler(long jsContextNativePointer, long eventHandlerPointer);
+
+  private native void dispatchEventToTarget(
+    long jsContextNativePointer,
+    long eventHandlerPointer,
+    long eventTargetPointer,
+    String type,
+    NativeMap payload
+  );
+
   private native void installFabric(long jsContextNativePointer, Object fabricModule);
 
   public FabricJSCBinding() {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
index efc4db619682..9b18298562c6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
@@ -7,7 +7,6 @@
 
 #include "FabricJSCBinding.h"
 #include <fb/fbjni.h>
-#include <react/jni/ReadableNativeMap.h>
 #include <jschelpers/JavaScriptCore.h>
 #include <jschelpers/Unicode.h>
 
@@ -81,6 +80,15 @@ local_ref<ReadableNativeMap::jhybridobject> JSValueToReadableMapViaJSON(JSContex
   return ReadableNativeMap::newObjectCxxArgs(std::move(dynamicValue));
 }
 
+JSValueRef ReadableMapToJSValueViaJSON(JSContextRef ctx, NativeMap *map) {
+  folly::dynamic dynamicValue = map->consume();
+  auto json = folly::toJson(dynamicValue);
+  JSStringRef jsonRef = JSC_JSStringCreateWithUTF8CString(ctx, json.c_str());
+  auto value = JSC_JSValueMakeFromJSONString(ctx, jsonRef);
+  JSC_JSStringRelease(ctx, jsonRef);
+  return value;
+}
+
 JSValueRef createNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
   FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
   alias_ref<jobject> manager = managerWrapper->fabricUiManager;
@@ -231,6 +239,21 @@ JSValueRef completeRoot(JSContextRef ctx, JSObjectRef function, JSObjectRef this
   return JSC_JSValueMakeUndefined(ctx);
 }
 
+JSValueRef registerEventHandler(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef *exception) {
+  FabricJSCUIManager *managerWrapper = (FabricJSCUIManager *)JSC_JSObjectGetPrivate(useCustomJSC, function);
+  alias_ref<jobject> manager = managerWrapper->fabricUiManager;
+
+  static auto registerEventHandler =
+    jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
+      ->getMethod<void(jlong)>("registerEventHandler");
+
+  auto eventHandler = arguments[0];
+  JSC_JSValueProtect(ctx, eventHandler);
+  registerEventHandler(manager, (jlong)eventHandler);
+
+  return JSC_JSValueMakeUndefined(ctx);
+}
+
 void finalizeJNIObject(JSObjectRef object) {
   // Release whatever global ref object we're storing here.
   jobject globalRef = (jobject)JSC_JSObjectGetPrivate(useCustomJSC, object);
@@ -291,6 +314,47 @@ void FabricJSCBinding::releaseEventTarget(
   JSC_JSValueUnprotect(context, value);
 }
 
+void FabricJSCBinding::releaseEventHandler(
+  jlong jsContextNativePointer,
+  jlong eventHandlerPointer
+) {
+  JSContextRef context = (JSContextRef)jsContextNativePointer;
+  JSValueRef value = (JSValueRef)((void *)eventHandlerPointer);
+  // Release this function.
+  JSC_JSValueUnprotect(context, value);
+}
+
+void FabricJSCBinding::dispatchEventToTarget(
+  jlong jsContextNativePointer,
+  jlong eventHandlerPointer,
+  jlong eventTargetPointer,
+  std::string type,
+  NativeMap *payloadMap
+) {
+  JSContextRef context = (JSContextRef)jsContextNativePointer;
+  JSObjectRef eventHandler = (JSObjectRef)((void *)eventHandlerPointer);
+  JSObjectRef eventTarget = (JSObjectRef)((void *)eventTargetPointer);
+
+  JSObjectRef thisArg = (JSObjectRef)JSC_JSValueMakeUndefined(context);
+  JSStringRef typeStr = JSC_JSStringCreateWithUTF8CString(context, type.c_str());
+  JSValueRef typeRef = JSC_JSValueMakeString(context, typeStr);
+  JSC_JSStringRelease(context, typeStr);
+  JSValueRef payloadRef = ReadableMapToJSValueViaJSON(context, payloadMap);
+  JSValueRef args[] = {eventTarget, typeRef, payloadRef};
+  JSValueRef exn;
+  JSValueRef result = JSC_JSObjectCallAsFunction(
+    context,
+    eventHandler,
+    thisArg,
+    3,
+    args,
+    &exn
+  );
+  if (!result) {
+    // TODO: Handle error in exn
+  }
+}
+
 void FabricJSCBinding::installFabric(jlong jsContextNativePointer,
     jni::alias_ref<jobject> fabricModule) {
   JSContextRef context = (JSContextRef)jsContextNativePointer;
@@ -308,11 +372,14 @@ void FabricJSCBinding::installFabric(jlong jsContextNativePointer,
   addFabricMethod(context, fabricModule, classRef, module, "cloneNodeWithNewChildren", cloneNodeWithNewChildren);
   addFabricMethod(context, fabricModule, classRef, module, "cloneNodeWithNewProps", cloneNodeWithNewProps);
   addFabricMethod(context, fabricModule, classRef, module, "cloneNodeWithNewChildrenAndProps", cloneNodeWithNewChildrenAndProps);
+
   addFabricMethod(context, fabricModule, classRef, module, "appendChild", appendChild);
   addFabricMethod(context, fabricModule, classRef, module, "createChildSet", createChildSet);
   addFabricMethod(context, fabricModule, classRef, module, "appendChildToSet", appendChildToSet);
   addFabricMethod(context, fabricModule, classRef, module, "completeRoot", completeRoot);
 
+  addFabricMethod(context, fabricModule, classRef, module, "registerEventHandler", registerEventHandler);
+
   JSC_JSClassRelease(useCustomJSC, classRef);
 
   JSObjectRef globalObject = JSC_JSContextGetGlobalObject(context);
@@ -325,6 +392,10 @@ void FabricJSCBinding::registerNatives() {
   registerHybrid({
     makeNativeMethod("initHybrid", FabricJSCBinding::initHybrid),
     makeNativeMethod("installFabric", FabricJSCBinding::installFabric),
+    makeNativeMethod("createEventTarget", FabricJSCBinding::createEventTarget),
+    makeNativeMethod("releaseEventTarget", FabricJSCBinding::releaseEventTarget),
+    makeNativeMethod("releaseEventHandler", FabricJSCBinding::releaseEventHandler),
+    makeNativeMethod("dispatchEventToTarget", FabricJSCBinding::dispatchEventToTarget),
   });
 }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
index a6b9857b012c..40b7cbd1681f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
@@ -9,6 +9,7 @@
 
 #include <memory>
 #include <fb/fbjni.h>
+#include <react/jni/ReadableNativeMap.h>
 
 namespace facebook {
 namespace react {
@@ -30,6 +31,16 @@ class FabricJSCBinding : public jni::HybridClass<FabricJSCBinding> {
 
   void releaseEventTarget(jlong jsContextNativePointer, jlong eventTargetPointer);
 
+  void releaseEventHandler(jlong jsContextNativePointer, jlong eventHandlerPointer);
+
+  void dispatchEventToTarget(
+    jlong jsContextNativePointer,
+    jlong eventHandlerPointer,
+    jlong eventTargetPointer,
+    std::string type,
+    NativeMap *payload
+  );
+
   void installFabric(jlong jsContextNativePointer, jni::alias_ref<jobject> fabricModule);
 
 };

From f50df4f5eca4b4324ff18a49dcf8be3694482b51 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 22 May 2018 01:08:20 -0700
Subject: [PATCH 0637/1109] iOS OSS: deployment target 8.0 => 9.0

Summary: Moving target deployment to iOS 9.0+ from now on, removing customization for iOS 8.

Reviewed By: shergin

Differential Revision: D8053439

fbshipit-source-id: 292c58f15c6e6caf8b28d15c1521812d6ed675c5
---
 Libraries/ART/ART.xcodeproj/project.pbxproj   |   4 +-
 .../RCTActionSheet.xcodeproj/project.pbxproj  |   4 +-
 .../Blob/RCTBlob.xcodeproj/project.pbxproj    |   4 +-
 .../RCTCameraRoll.xcodeproj/project.pbxproj   |   4 +-
 .../RCTGeolocation.xcodeproj/project.pbxproj  |   4 +-
 .../Image/RCTImage.xcodeproj/project.pbxproj  |   4 +-
 .../RCTLinking.xcodeproj/project.pbxproj      |   4 +-
 .../RCTAnimation.xcodeproj/project.pbxproj    |   4 +-
 .../RCTNetwork.xcodeproj/project.pbxproj      |   4 +-
 .../project.pbxproj                           |   4 +-
 .../RCTTest/RCTTest.xcodeproj/project.pbxproj |   4 +-
 .../Sample/Sample.xcodeproj/project.pbxproj   |   4 +-
 .../RCTSettings.xcodeproj/project.pbxproj     |   4 +-
 .../Text/RCTText.xcodeproj/project.pbxproj    |   4 +-
 .../RCTVibration.xcodeproj/project.pbxproj    |   4 +-
 .../RCTWebSocket.xcodeproj/project.pbxproj    |   4 +-
 RNTester/Podfile                              |   2 +-
 RNTester/Podfile.lock                         |   2 +-
 RNTester/RNTester.xcodeproj/project.pbxproj   |  16 +-
 .../RNTesterPods.xcodeproj/project.pbxproj    | 166 +-----------------
 RNTester/RNTesterUnitTests/RCTFontTests.m     |   1 -
 React/React.xcodeproj/project.pbxproj         |  10 +-
 React/Views/RCTFont.mm                        |   1 -
 React/Views/RCTFontConstantsOverride.h        |  29 ---
 .../core/__fixtures__/files/project.pbxproj   |   8 +-
 .../link/__fixtures__/linearGradient.pbxproj  |   4 +-
 local-cli/link/__fixtures__/project.pbxproj   |   8 +-
 .../ios/HelloWorld.xcodeproj/project.pbxproj  |   8 +-
 28 files changed, 62 insertions(+), 257 deletions(-)
 delete mode 100644 React/Views/RCTFontConstantsOverride.h

diff --git a/Libraries/ART/ART.xcodeproj/project.pbxproj b/Libraries/ART/ART.xcodeproj/project.pbxproj
index 75eec5411710..b1cafee230d1 100644
--- a/Libraries/ART/ART.xcodeproj/project.pbxproj
+++ b/Libraries/ART/ART.xcodeproj/project.pbxproj
@@ -361,7 +361,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -396,7 +396,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
index 40d08248bc3c..a639137bb7bb 100644
--- a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
+++ b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
@@ -133,7 +133,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -174,7 +174,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj b/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
index 2ffded6f074d..316c157dec50 100755
--- a/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
+++ b/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
@@ -234,7 +234,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -273,7 +273,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
index defe37b47f48..e50301aad75e 100644
--- a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
+++ b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
@@ -176,7 +176,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -218,7 +218,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj b/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
index e00e30ce46ec..b1e18399c683 100644
--- a/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
+++ b/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
@@ -134,7 +134,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -176,7 +176,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/Image/RCTImage.xcodeproj/project.pbxproj b/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
index 0249e7b0c253..0af0af8f1ee6 100644
--- a/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
+++ b/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
@@ -397,7 +397,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -442,7 +442,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj b/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
index b7ab8f88d800..b56dcc67b984 100644
--- a/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
+++ b/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
@@ -198,7 +198,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -239,7 +239,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
index b55c034809b4..f17225d61632 100644
--- a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
+++ b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
@@ -563,7 +563,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -606,7 +606,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj b/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
index 2ca45336dd64..e5a2fc78cfb0 100644
--- a/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
+++ b/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
@@ -243,7 +243,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -288,7 +288,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj b/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
index c9318f7841c0..e709c21454fe 100644
--- a/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
+++ b/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
@@ -242,7 +242,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -285,7 +285,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj b/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
index 3fa7ee8b6805..f2c7c371cd81 100644
--- a/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
+++ b/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
@@ -324,7 +324,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -366,7 +366,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/Sample/Sample.xcodeproj/project.pbxproj b/Libraries/Sample/Sample.xcodeproj/project.pbxproj
index d57369c18aaa..b0fa1f7b34ac 100644
--- a/Libraries/Sample/Sample.xcodeproj/project.pbxproj
+++ b/Libraries/Sample/Sample.xcodeproj/project.pbxproj
@@ -155,7 +155,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -189,7 +189,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				VALIDATE_PRODUCT = YES;
diff --git a/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj b/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
index 5901229e3362..fd0b9c5e4e47 100644
--- a/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
+++ b/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
@@ -199,7 +199,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -241,7 +241,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/Text/RCTText.xcodeproj/project.pbxproj b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
index 9765d035fedd..c882c8843e3c 100644
--- a/Libraries/Text/RCTText.xcodeproj/project.pbxproj
+++ b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
@@ -590,7 +590,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -632,7 +632,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj b/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
index c4403ac147f3..46ee2d4a7fe8 100644
--- a/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
+++ b/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
@@ -133,7 +133,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -174,7 +174,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
index efb2609ad37b..525452a558c4 100644
--- a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
+++ b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
@@ -373,7 +373,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -417,7 +417,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/RNTester/Podfile b/RNTester/Podfile
index 21f5e3b52c49..40877c075559 100644
--- a/RNTester/Podfile
+++ b/RNTester/Podfile
@@ -1,4 +1,4 @@
-platform :ios, '8.0'
+platform :ios, '9.0'
 
 target 'RNTester' do
   # Uncomment for Swift
diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index 28e43f631bdc..837208c89f3a 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -144,6 +144,6 @@ SPEC CHECKSUMS:
   React: 0a0271674c3a6772a89a6606f337ed8db583abc0
   yoga: bdd268c5812f00bdb52cc2b58f129797e97935eb
 
-PODFILE CHECKSUM: b28ea97efdc10f046a3a1b7b455c1e18a39cb10a
+PODFILE CHECKSUM: 30aa63dcdbb3546a2bacdfd4e005bcca50c9b55c
 
 COCOAPODS: 1.5.2
diff --git a/RNTester/RNTester.xcodeproj/project.pbxproj b/RNTester/RNTester.xcodeproj/project.pbxproj
index d8a883ae5637..06921b5616f1 100644
--- a/RNTester/RNTester.xcodeproj/project.pbxproj
+++ b/RNTester/RNTester.xcodeproj/project.pbxproj
@@ -1816,7 +1816,7 @@
 					"$(SRCROOT)/RNTesterUnitTests",
 				);
 				INFOPLIST_FILE = RNTesterUnitTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				LIBRARY_SEARCH_PATHS = (
 					"$(inherited)",
@@ -1835,7 +1835,7 @@
 					"$(SRCROOT)/RNTesterUnitTests",
 				);
 				INFOPLIST_FILE = RNTesterUnitTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				LIBRARY_SEARCH_PATHS = (
 					"$(inherited)",
@@ -1852,7 +1852,7 @@
 				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
 				DEVELOPMENT_TEAM = V9WTTPBFK9;
 				INFOPLIST_FILE = "$(SRCROOT)/RNTester/Info.plist";
-				IPHONEOS_DEPLOYMENT_TARGET = 9.3;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LIBRARY_SEARCH_PATHS = "$(inherited)";
 				PRODUCT_BUNDLE_IDENTIFIER = com.facebook.react.uiapp;
 				PRODUCT_NAME = RNTester;
@@ -1866,7 +1866,7 @@
 				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
 				DEVELOPMENT_TEAM = V9WTTPBFK9;
 				INFOPLIST_FILE = "$(SRCROOT)/RNTester/Info.plist";
-				IPHONEOS_DEPLOYMENT_TARGET = 9.3;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LIBRARY_SEARCH_PATHS = "$(inherited)";
 				PRODUCT_BUNDLE_IDENTIFIER = com.facebook.react.uiapp;
 				PRODUCT_NAME = RNTester;
@@ -1885,7 +1885,7 @@
 					"FB_REFERENCE_IMAGE_DIR=\"\\\"$(SOURCE_ROOT)/$(PROJECT_NAME)IntegrationTests/ReferenceImages\\\"\"",
 				);
 				INFOPLIST_FILE = RNTesterIntegrationTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				PRODUCT_BUNDLE_IDENTIFIER = "com.facebook.React.$(PRODUCT_NAME:rfc1034identifier)";
 				PRODUCT_NAME = "$(TARGET_NAME)";
@@ -1901,7 +1901,7 @@
 				DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
 				GCC_NO_COMMON_BLOCKS = YES;
 				INFOPLIST_FILE = RNTesterIntegrationTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				PRODUCT_BUNDLE_IDENTIFIER = "com.facebook.React.$(PRODUCT_NAME:rfc1034identifier)";
 				PRODUCT_NAME = "$(TARGET_NAME)";
@@ -2134,7 +2134,7 @@
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_LABEL = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				OTHER_LDFLAGS = (
@@ -2195,7 +2195,7 @@
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_LABEL = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				OTHER_LDFLAGS = (
 					"-ObjC",
diff --git a/RNTester/RNTesterPods.xcodeproj/project.pbxproj b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
index 054c9cc2e7e5..0620810141cf 100644
--- a/RNTester/RNTesterPods.xcodeproj/project.pbxproj
+++ b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
@@ -12,12 +12,6 @@
 		13B07FC11A68108700A75B9A /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = 13B07FB71A68108700A75B9A /* main.m */; };
 		272E6B3F1BEA849E001FCF37 /* UpdatePropertiesExampleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 272E6B3C1BEA849E001FCF37 /* UpdatePropertiesExampleView.m */; };
 		27F441EC1BEBE5030039B79C /* FlexibleSizeExampleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 27F441E81BEBE5030039B79C /* FlexibleSizeExampleView.m */; };
-		2DD323DC1DA2DDBF000FE1B8 /* FlexibleSizeExampleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 27F441E81BEBE5030039B79C /* FlexibleSizeExampleView.m */; };
-		2DD323DD1DA2DDBF000FE1B8 /* UpdatePropertiesExampleView.m in Sources */ = {isa = PBXBuildFile; fileRef = 272E6B3C1BEA849E001FCF37 /* UpdatePropertiesExampleView.m */; };
-		2DD323DE1DA2DDBF000FE1B8 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 13B07FB01A68108700A75B9A /* AppDelegate.m */; };
-		2DD323E01DA2DDBF000FE1B8 /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = 13B07FB71A68108700A75B9A /* main.m */; };
-		2DD323E11DA2DDBF000FE1B8 /* legacy_image@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = 3D2AFAF41D646CF80089D1A3 /* legacy_image@2x.png */; };
-		2DD323E21DA2DDBF000FE1B8 /* Info.plist in Resources */ = {isa = PBXBuildFile; fileRef = 13B07FB61A68108700A75B9A /* Info.plist */; };
 		2DDEF0101F84BF7B00DBDF73 /* Images.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2DDEF00F1F84BF7B00DBDF73 /* Images.xcassets */; };
 		3D13F8481D6F6AF900E69E0E /* ImageInBundle.png in Resources */ = {isa = PBXBuildFile; fileRef = 3D13F8441D6F6AF200E69E0E /* ImageInBundle.png */; };
 		3D13F84A1D6F6AFD00E69E0E /* OtherImages.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 3D13F8451D6F6AF200E69E0E /* OtherImages.xcassets */; };
@@ -27,13 +21,6 @@
 /* End PBXBuildFile section */
 
 /* Begin PBXContainerItemProxy section */
-		143BC59B1B21E3E100462512 /* PBXContainerItemProxy */ = {
-			isa = PBXContainerItemProxy;
-			containerPortal = 83CBB9F71A601CBA00E9B192 /* Project object */;
-			proxyType = 1;
-			remoteGlobalIDString = 13B07F861A680F5B00A75B9A;
-			remoteInfo = RNTester;
-		};
 		3D13F84B1D6F6B5F00E69E0E /* PBXContainerItemProxy */ = {
 			isa = PBXContainerItemProxy;
 			containerPortal = 83CBB9F71A601CBA00E9B192 /* Project object */;
@@ -66,13 +53,6 @@
 /* End PBXFileReference section */
 
 /* Begin PBXFrameworksBuildPhase section */
-		004D289B1AAF61C70097A701 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
 		13B07F8C1A680F5B00A75B9A /* Frameworks */ = {
 			isa = PBXFrameworksBuildPhase;
 			buildActionMask = 2147483647;
@@ -81,34 +61,6 @@
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};
-		143BC5921B21E3E100462512 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2D4624D91DA2EA6900C74D09 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2DD3238D1DA2DD8A000FE1B8 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2DD323A21DA2DD8B000FE1B8 /* Frameworks */ = {
-			isa = PBXFrameworksBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
 		3D13F83B1D6F6AE000E69E0E /* Frameworks */ = {
 			isa = PBXFrameworksBuildPhase;
 			buildActionMask = 2147483647;
@@ -254,25 +206,9 @@
 				LastUpgradeCheck = 0820;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
-					004D289D1AAF61C70097A701 = {
-						CreatedOnToolsVersion = 6.1.1;
-					};
 					13B07F861A680F5B00A75B9A = {
 						DevelopmentTeam = V9WTTPBFK9;
 					};
-					143BC5941B21E3E100462512 = {
-						CreatedOnToolsVersion = 6.3.2;
-						TestTargetID = 13B07F861A680F5B00A75B9A;
-					};
-					2DD3238F1DA2DD8A000FE1B8 = {
-						CreatedOnToolsVersion = 8.0;
-						ProvisioningStyle = Automatic;
-					};
-					2DD323A41DA2DD8B000FE1B8 = {
-						CreatedOnToolsVersion = 8.0;
-						ProvisioningStyle = Automatic;
-						TestTargetID = 2DD3238F1DA2DD8A000FE1B8;
-					};
 					3D13F83D1D6F6AE000E69E0E = {
 						CreatedOnToolsVersion = 7.3.1;
 					};
@@ -298,13 +234,6 @@
 /* End PBXProject section */
 
 /* Begin PBXResourcesBuildPhase section */
-		004D289C1AAF61C70097A701 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
 		13B07F8E1A680F5B00A75B9A /* Resources */ = {
 			isa = PBXResourcesBuildPhase;
 			buildActionMask = 2147483647;
@@ -316,36 +245,6 @@
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};
-		143BC5931B21E3E100462512 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2D4624DB1DA2EA6900C74D09 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2DD3238E1DA2DD8A000FE1B8 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				2DD323E11DA2DDBF000FE1B8 /* legacy_image@2x.png in Resources */,
-				2DD323E21DA2DDBF000FE1B8 /* Info.plist in Resources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2DD323A31DA2DD8B000FE1B8 /* Resources */ = {
-			isa = PBXResourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
 		3D13F83C1D6F6AE000E69E0E /* Resources */ = {
 			isa = PBXResourcesBuildPhase;
 			buildActionMask = 2147483647;
@@ -358,19 +257,6 @@
 /* End PBXResourcesBuildPhase section */
 
 /* Begin PBXShellScriptBuildPhase section */
-		2DD323EB1DA2DEC1000FE1B8 /* ShellScript */ = {
-			isa = PBXShellScriptBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			inputPaths = (
-			);
-			outputPaths = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-			shellPath = /bin/sh;
-			shellScript = "export NODE_BINARY=node\n$SRCROOT/../scripts/react-native-xcode.sh RNTester/js/RNTesterApp.ios.js";
-		};
 		5CF0FD27207FC6EC00C13D65 /* Start Metro */ = {
 			isa = PBXShellScriptBuildPhase;
 			buildActionMask = 2147483647;
@@ -421,13 +307,6 @@
 /* End PBXShellScriptBuildPhase section */
 
 /* Begin PBXSourcesBuildPhase section */
-		004D289A1AAF61C70097A701 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
 		13B07F871A680F5B00A75B9A /* Sources */ = {
 			isa = PBXSourcesBuildPhase;
 			buildActionMask = 2147483647;
@@ -439,38 +318,6 @@
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};
-		143BC5911B21E3E100462512 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2D4624C41DA2EA6900C74D09 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2DD3238C1DA2DD8A000FE1B8 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-				2DD323DC1DA2DDBF000FE1B8 /* FlexibleSizeExampleView.m in Sources */,
-				2DD323DD1DA2DDBF000FE1B8 /* UpdatePropertiesExampleView.m in Sources */,
-				2DD323E01DA2DDBF000FE1B8 /* main.m in Sources */,
-				2DD323DE1DA2DDBF000FE1B8 /* AppDelegate.m in Sources */,
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
-		2DD323A11DA2DD8B000FE1B8 /* Sources */ = {
-			isa = PBXSourcesBuildPhase;
-			buildActionMask = 2147483647;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 0;
-		};
 		3D13F83A1D6F6AE000E69E0E /* Sources */ = {
 			isa = PBXSourcesBuildPhase;
 			buildActionMask = 2147483647;
@@ -481,11 +328,6 @@
 /* End PBXSourcesBuildPhase section */
 
 /* Begin PBXTargetDependency section */
-		143BC59C1B21E3E100462512 /* PBXTargetDependency */ = {
-			isa = PBXTargetDependency;
-			target = 13B07F861A680F5B00A75B9A /* RNTester */;
-			targetProxy = 143BC59B1B21E3E100462512 /* PBXContainerItemProxy */;
-		};
 		3D13F84C1D6F6B5F00E69E0E /* PBXTargetDependency */ = {
 			isa = PBXTargetDependency;
 			target = 3D13F83D1D6F6AE000E69E0E /* RNTesterBundle */;
@@ -513,7 +355,7 @@
 				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
 				DEVELOPMENT_TEAM = V9WTTPBFK9;
 				INFOPLIST_FILE = "$(SRCROOT)/RNTester/Info.plist";
-				IPHONEOS_DEPLOYMENT_TARGET = 9.3;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LIBRARY_SEARCH_PATHS = "$(inherited)";
 				PRODUCT_BUNDLE_IDENTIFIER = com.facebook.react.uiapp;
 				PRODUCT_NAME = RNTester;
@@ -528,7 +370,7 @@
 				ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
 				DEVELOPMENT_TEAM = V9WTTPBFK9;
 				INFOPLIST_FILE = "$(SRCROOT)/RNTester/Info.plist";
-				IPHONEOS_DEPLOYMENT_TARGET = 9.3;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LIBRARY_SEARCH_PATHS = "$(inherited)";
 				PRODUCT_BUNDLE_IDENTIFIER = com.facebook.react.uiapp;
 				PRODUCT_NAME = RNTester;
@@ -616,7 +458,7 @@
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_LABEL = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				OTHER_LDFLAGS = (
@@ -677,7 +519,7 @@
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_LABEL = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				OTHER_LDFLAGS = (
 					"-ObjC",
diff --git a/RNTester/RNTesterUnitTests/RCTFontTests.m b/RNTester/RNTesterUnitTests/RCTFontTests.m
index 5d6a3bd1b4d9..1d9573b489e1 100644
--- a/RNTester/RNTesterUnitTests/RCTFontTests.m
+++ b/RNTester/RNTesterUnitTests/RCTFontTests.m
@@ -10,7 +10,6 @@
 #import <XCTest/XCTest.h>
 
 #import <React/RCTFont.h>
-#import <React/RCTFontConstantsOverride.h>
 
 @interface RCTFontTests : XCTestCase
 
diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index ef3189426c62..df9785c3e5ea 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -1152,8 +1152,6 @@
 		59EDBCC61FDF4E55003573DE /* (null) in Copy Headers */ = {isa = PBXBuildFile; };
 		59EDBCC71FDF4E55003573DE /* RCTScrollView.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 59EDBCA31FDF4E0C003573DE /* RCTScrollView.h */; };
 		59EDBCC81FDF4E55003573DE /* RCTScrollViewManager.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 59EDBCA51FDF4E0C003573DE /* RCTScrollViewManager.h */; };
-		5C70426020A1004800FBEEF7 /* RCTFontConstantsOverride.h in Headers */ = {isa = PBXBuildFile; fileRef = 5C70425F20A1004800FBEEF7 /* RCTFontConstantsOverride.h */; };
-		5C70426120A1022C00FBEEF7 /* RCTFontConstantsOverride.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5C70425F20A1004800FBEEF7 /* RCTFontConstantsOverride.h */; };
 		5CE2080220772F7D009A43B3 /* YGConfig.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 5CE2080020772F7C009A43B3 /* YGConfig.cpp */; };
 		5CE2080320772F7D009A43B3 /* YGConfig.h in Headers */ = {isa = PBXBuildFile; fileRef = 5CE2080120772F7C009A43B3 /* YGConfig.h */; };
 		657734841EE834C900A0E9EA /* RCTInspectorDevServerHelper.h in Headers */ = {isa = PBXBuildFile; fileRef = 657734821EE834C900A0E9EA /* RCTInspectorDevServerHelper.h */; };
@@ -1611,7 +1609,6 @@
 			dstPath = include/React;
 			dstSubfolderSpec = 16;
 			files = (
-				5C70426120A1022C00FBEEF7 /* RCTFontConstantsOverride.h in Copy Headers */,
 				39C50FF92046EACF00CEE534 /* RCTVersion.h in Copy Headers */,
 				591F78DE202ADB8F004A668C /* RCTLayout.h in Copy Headers */,
 				59EDBCBD1FDF4E43003573DE /* RCTScrollableProtocol.h in Copy Headers */,
@@ -2257,7 +2254,6 @@
 		59EDBCA41FDF4E0C003573DE /* RCTScrollView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTScrollView.m; sourceTree = "<group>"; };
 		59EDBCA51FDF4E0C003573DE /* RCTScrollViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTScrollViewManager.h; sourceTree = "<group>"; };
 		59EDBCA61FDF4E0C003573DE /* RCTScrollViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTScrollViewManager.m; sourceTree = "<group>"; };
-		5C70425F20A1004800FBEEF7 /* RCTFontConstantsOverride.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTFontConstantsOverride.h; sourceTree = "<group>"; };
 		5CE2080020772F7C009A43B3 /* YGConfig.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = YGConfig.cpp; sourceTree = "<group>"; };
 		5CE2080120772F7C009A43B3 /* YGConfig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = YGConfig.h; sourceTree = "<group>"; };
 		657734821EE834C900A0E9EA /* RCTInspectorDevServerHelper.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInspectorDevServerHelper.h; sourceTree = "<group>"; };
@@ -2580,7 +2576,6 @@
 		13B07FF31A6947C200A75B9A /* Views */ = {
 			isa = PBXGroup;
 			children = (
-				5C70425F20A1004800FBEEF7 /* RCTFontConstantsOverride.h */,
 				B95154301D1B34B200FE7B80 /* RCTActivityIndicatorView.h */,
 				B95154311D1B34B200FE7B80 /* RCTActivityIndicatorView.m */,
 				13B080181A69489C00A75B9A /* RCTActivityIndicatorViewManager.h */,
@@ -3595,7 +3590,6 @@
 				3D80DA621DF820620028D040 /* RCTAutoInsetsProtocol.h in Headers */,
 				C60128AB1F3D1258009DF9FF /* RCTCxxConvert.h in Headers */,
 				59EDBCAD1FDF4E0C003573DE /* RCTScrollContentView.h in Headers */,
-				5C70426020A1004800FBEEF7 /* RCTFontConstantsOverride.h in Headers */,
 				59EDBCA71FDF4E0C003573DE /* RCTScrollableProtocol.h in Headers */,
 				591F78DC202ADB22004A668C /* RCTLayout.h in Headers */,
 				5CE2080320772F7D009A43B3 /* YGConfig.h in Headers */,
@@ -5160,7 +5154,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -5208,7 +5202,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				SKIP_INSTALL = YES;
diff --git a/React/Views/RCTFont.mm b/React/Views/RCTFont.mm
index 8753510d9165..9cd63ce6ffe1 100644
--- a/React/Views/RCTFont.mm
+++ b/React/Views/RCTFont.mm
@@ -7,7 +7,6 @@
 
 #import "RCTAssert.h"
 #import "RCTFont.h"
-#import "RCTFontConstantsOverride.h"
 #import "RCTLog.h"
 
 #import <CoreText/CoreText.h>
diff --git a/React/Views/RCTFontConstantsOverride.h b/React/Views/RCTFontConstantsOverride.h
deleted file mode 100644
index 1563e92e7bca..000000000000
--- a/React/Views/RCTFontConstantsOverride.h
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-// NOTE: Include this header file to ensure consistency of the constants defined here.
-// The values are the ones used in RCTFont.mm.
-// Example: import it for testing RCTFont internals in a unit test.
-
-#if !defined(__IPHONE_8_2) || __IPHONE_OS_VERSION_MIN_REQUIRED < __IPHONE_8_2
-
-// These constants are defined in iPhone SDK 8.2, but the app cannot run on
-// iOS < 8.2 unless we redefine them here. If you target iOS 8.2 or above
-// as a base target, the standard constants will be used instead.
-// These constants can only be removed when React Native drops iOS8 support.
-
-#define UIFontWeightUltraLight -0.8
-#define UIFontWeightThin -0.6
-#define UIFontWeightLight -0.4
-#define UIFontWeightRegular 0
-#define UIFontWeightMedium 0.23
-#define UIFontWeightSemibold 0.3
-#define UIFontWeightBold 0.4
-#define UIFontWeightHeavy 0.56
-#define UIFontWeightBlack 0.62
-
-#endif
diff --git a/local-cli/core/__fixtures__/files/project.pbxproj b/local-cli/core/__fixtures__/files/project.pbxproj
index 004cee72bc27..b27d06606be3 100644
--- a/local-cli/core/__fixtures__/files/project.pbxproj
+++ b/local-cli/core/__fixtures__/files/project.pbxproj
@@ -597,7 +597,7 @@
 					"$(inherited)",
 				);
 				INFOPLIST_FILE = androidTestTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				LIBRARY_SEARCH_PATHS = (
 					"$(inherited)",
@@ -620,7 +620,7 @@
 					"$(inherited)",
 				);
 				INFOPLIST_FILE = androidTestTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				LIBRARY_SEARCH_PATHS = (
 					"$(inherited)",
@@ -717,7 +717,7 @@
 					"$(SRCROOT)/../node_modules/react-native-linear-gradient/**",
 					"$(SRCROOT)/../node_modules/react-native-video",
 				);
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -761,7 +761,7 @@
 					"$(SRCROOT)/../node_modules/react-native-linear-gradient/**",
 					"$(SRCROOT)/../node_modules/react-native-video",
 				);
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				VALIDATE_PRODUCT = YES;
diff --git a/local-cli/link/__fixtures__/linearGradient.pbxproj b/local-cli/link/__fixtures__/linearGradient.pbxproj
index b0d4049ac7c7..ca87c2e43e9e 100644
--- a/local-cli/link/__fixtures__/linearGradient.pbxproj
+++ b/local-cli/link/__fixtures__/linearGradient.pbxproj
@@ -158,7 +158,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -192,7 +192,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				VALIDATE_PRODUCT = YES;
diff --git a/local-cli/link/__fixtures__/project.pbxproj b/local-cli/link/__fixtures__/project.pbxproj
index d5021ec01873..428aa40c9ca1 100644
--- a/local-cli/link/__fixtures__/project.pbxproj
+++ b/local-cli/link/__fixtures__/project.pbxproj
@@ -836,7 +836,7 @@
 					"$(inherited)",
 				);
 				INFOPLIST_FILE = BasicTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				PRODUCT_NAME = "$(TARGET_NAME)";
 				TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Basic.app/Basic";
@@ -852,7 +852,7 @@
 				BUNDLE_LOADER = "$(TEST_HOST)";
 				COPY_PHASE_STRIP = NO;
 				INFOPLIST_FILE = BasicTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				PRODUCT_NAME = "$(TARGET_NAME)";
 				TEST_HOST = "$(BUILT_PRODUCTS_DIR)/Basic.app/Basic";
@@ -933,7 +933,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -968,7 +968,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				VALIDATE_PRODUCT = YES;
diff --git a/local-cli/templates/HelloWorld/ios/HelloWorld.xcodeproj/project.pbxproj b/local-cli/templates/HelloWorld/ios/HelloWorld.xcodeproj/project.pbxproj
index d004c9c3a14d..7346f2749ea6 100644
--- a/local-cli/templates/HelloWorld/ios/HelloWorld.xcodeproj/project.pbxproj
+++ b/local-cli/templates/HelloWorld/ios/HelloWorld.xcodeproj/project.pbxproj
@@ -1173,7 +1173,7 @@
 					"$(inherited)",
 				);
 				INFOPLIST_FILE = HelloWorldTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				OTHER_LDFLAGS = (
 					"-ObjC",
@@ -1190,7 +1190,7 @@
 				BUNDLE_LOADER = "$(TEST_HOST)";
 				COPY_PHASE_STRIP = NO;
 				INFOPLIST_FILE = HelloWorldTests/Info.plist;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
 				OTHER_LDFLAGS = (
 					"-ObjC",
@@ -1372,7 +1372,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = iphoneos;
@@ -1407,7 +1407,7 @@
 				GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
 				GCC_WARN_UNUSED_FUNCTION = YES;
 				GCC_WARN_UNUSED_VARIABLE = YES;
-				IPHONEOS_DEPLOYMENT_TARGET = 8.0;
+				IPHONEOS_DEPLOYMENT_TARGET = 9.0;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = iphoneos;
 				VALIDATE_PRODUCT = YES;

From 0ed8461f6d20e3366f7ba1a6f0cad0655f571804 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 22 May 2018 01:08:22 -0700
Subject: [PATCH 0638/1109] iOS: disable deprecation warning for Xcode 9.3.1+
 for now

Summary:
This is to unbreak builds due to deprecated methods.
Cocoapods build seems unaffected.

Reviewed By: mmmulani

Differential Revision: D8060139

fbshipit-source-id: a4302d649dd75d29d293aeffdcc352bf09b0c504
---
 .../RCTActionSheet.xcodeproj/project.pbxproj           |  2 ++
 .../CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj | 10 ++++------
 2 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
index a639137bb7bb..47a0b8b4d8ba 100644
--- a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
+++ b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
@@ -141,6 +141,7 @@
 				WARNING_CFLAGS = (
 					"-Werror",
 					"-Wall",
+					"-Wno-deprecated-declarations",
 				);
 			};
 			name = Debug;
@@ -182,6 +183,7 @@
 				WARNING_CFLAGS = (
 					"-Werror",
 					"-Wall",
+					"-Wno-deprecated-declarations",
 				);
 			};
 			name = Release;
diff --git a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
index e50301aad75e..1132021a60d4 100644
--- a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
+++ b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
@@ -184,6 +184,7 @@
 				WARNING_CFLAGS = (
 					"-Werror",
 					"-Wall",
+					"-Wno-deprecated-declarations",
 				);
 			};
 			name = Debug;
@@ -226,6 +227,7 @@
 				WARNING_CFLAGS = (
 					"-Werror",
 					"-Wall",
+					"-Wno-deprecated-declarations",
 				);
 			};
 			name = Release;
@@ -234,9 +236,7 @@
 			isa = XCBuildConfiguration;
 			buildSettings = {
 				CLANG_STATIC_ANALYZER_MODE = deep;
-				LIBRARY_SEARCH_PATHS = (
-					"$(inherited)",
-				);
+				LIBRARY_SEARCH_PATHS = "$(inherited)";
 				OTHER_LDFLAGS = "-ObjC";
 				PRODUCT_NAME = RCTCameraRoll;
 				RUN_CLANG_STATIC_ANALYZER = YES;
@@ -247,9 +247,7 @@
 			isa = XCBuildConfiguration;
 			buildSettings = {
 				CLANG_STATIC_ANALYZER_MODE = deep;
-				LIBRARY_SEARCH_PATHS = (
-					"$(inherited)",
-				);
+				LIBRARY_SEARCH_PATHS = "$(inherited)";
 				OTHER_LDFLAGS = "-ObjC";
 				PRODUCT_NAME = RCTCameraRoll;
 				RUN_CLANG_STATIC_ANALYZER = NO;

From 54489b91ab2bed7d12064ef0884e487ea547e4d6 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 22 May 2018 01:19:35 -0700
Subject: [PATCH 0639/1109] Fabric: Implementation of ShimmeringView aka
 <Shimmer>

Reviewed By: shergin

Differential Revision: D8016962

fbshipit-source-id: 5ec598e606f8e4bbf9e5c1db082d6a0b29bed3ee
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 8a9d6916b275..47629e4273ab 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -48,7 +48,7 @@ static const std::string componentNameByReactViewName(std::string viewName) {
   std::string rctPrefix("RCT");
   if (std::mismatch(rctPrefix.begin(), rctPrefix.end(), viewName.begin()).first == rctPrefix.end()) {
     // If `viewName` has "RCT" prefix, remove it.
-    viewName.erase(0, 3);
+    viewName.erase(0, rctPrefix.length());
   }
 
   // Fabric uses slightly new names for Text components because of differences
@@ -70,8 +70,7 @@ static const std::string componentNameByReactViewName(std::string viewName) {
 
   // Other temporary fallback until the native components are implemented.
   if (
-    viewName == "ActivityIndicatorView" ||
-    viewName == "ShimmeringView"
+    viewName == "ActivityIndicatorView"
   ) {
     return "View";
   }

From 55724bcc6266ded83a4d64a5d01517544007c5bb Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 22 May 2018 01:19:37 -0700
Subject: [PATCH 0640/1109] make <Image> fallback to <View> temporarily

Summary: <Image> support isn't there, so fallback to <View> instead of crashing.

Reviewed By: shergin

Differential Revision: D8086403

fbshipit-source-id: 16d7fd8023f93cbe25f2bc0f7d0a03e32cd402ce
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 47629e4273ab..b725b9739caf 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -61,8 +61,9 @@ static const std::string componentNameByReactViewName(std::string viewName) {
   }
 
   // We need this temporarly for testing purposes until we have proper
-  // implementation of <ScrollView> component.
+  // implementation of core components: <Image>, <ScrollContentView>.
   if (
+    viewName == "ImageView" ||
     viewName == "ScrollContentView"
   ) {
     return "View";

From 91f2ffed375673e62619aef71d106dffca108bf0 Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Tue, 22 May 2018 09:25:52 -0700
Subject: [PATCH 0641/1109] Back out "[JSC] Expose new methods to Custom/System
 JSC"

Reviewed By: fkgozali

Differential Revision: D8003558

fbshipit-source-id: 0b90153518f849f66d7c713f99cb44c79b27ca19
---
 React/React.xcodeproj/project.pbxproj       | 10 -------
 ReactCommon/jschelpers/BUCK                 |  1 -
 ReactCommon/jschelpers/JSCWrapper.h         | 11 -------
 ReactCommon/jschelpers/JSWeak.h             | 32 ---------------------
 ReactCommon/jschelpers/JavaScriptCore.h     | 18 +++---------
 ReactCommon/jschelpers/systemJSCWrapper.cpp | 22 --------------
 6 files changed, 4 insertions(+), 90 deletions(-)
 delete mode 100644 ReactCommon/jschelpers/JSWeak.h

diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index df9785c3e5ea..d008bf9e2145 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -1198,10 +1198,6 @@
 		A2440AA21DF8D854006E7BFC /* RCTReloadCommand.h in Headers */ = {isa = PBXBuildFile; fileRef = A2440AA01DF8D854006E7BFC /* RCTReloadCommand.h */; };
 		A2440AA31DF8D854006E7BFC /* RCTReloadCommand.m in Sources */ = {isa = PBXBuildFile; fileRef = A2440AA11DF8D854006E7BFC /* RCTReloadCommand.m */; };
 		A2440AA41DF8D865006E7BFC /* RCTReloadCommand.h in Headers */ = {isa = PBXBuildFile; fileRef = A2440AA01DF8D854006E7BFC /* RCTReloadCommand.h */; };
-		A2C986DF208C7DF700C0D579 /* JSWeak.h in Headers */ = {isa = PBXBuildFile; fileRef = A2E0E69F208AA9EC007044C1 /* JSWeak.h */; };
-		A2C986E0208C7DF900C0D579 /* JSWeak.h in Headers */ = {isa = PBXBuildFile; fileRef = A2E0E69F208AA9EC007044C1 /* JSWeak.h */; };
-		A2C986E1208C7E9C00C0D579 /* JSWeak.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = A2E0E69F208AA9EC007044C1 /* JSWeak.h */; };
-		A2C986E2208C7EA800C0D579 /* JSWeak.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = A2E0E69F208AA9EC007044C1 /* JSWeak.h */; };
 		AC70D2E91DE489E4002E6351 /* RCTJavaScriptLoader.mm in Sources */ = {isa = PBXBuildFile; fileRef = AC70D2E81DE489E4002E6351 /* RCTJavaScriptLoader.mm */; };
 		B233E6EA1D2D845D00BC68BA /* RCTI18nManager.m in Sources */ = {isa = PBXBuildFile; fileRef = B233E6E91D2D845D00BC68BA /* RCTI18nManager.m */; };
 		B95154321D1B34B200FE7B80 /* RCTActivityIndicatorView.m in Sources */ = {isa = PBXBuildFile; fileRef = B95154311D1B34B200FE7B80 /* RCTActivityIndicatorView.m */; };
@@ -1573,7 +1569,6 @@
 			dstPath = include/jschelpers;
 			dstSubfolderSpec = 16;
 			files = (
-				A2C986E2208C7EA800C0D579 /* JSWeak.h in Copy Headers */,
 				3DA982601E5B1089004F2374 /* JSCHelpers.h in Copy Headers */,
 				3DA982611E5B1089004F2374 /* noncopyable.h in Copy Headers */,
 				3DA982621E5B1089004F2374 /* Unicode.h in Copy Headers */,
@@ -1801,7 +1796,6 @@
 			dstPath = include/jschelpers;
 			dstSubfolderSpec = 16;
 			files = (
-				A2C986E1208C7E9C00C0D579 /* JSWeak.h in Copy Headers */,
 				3DA9825A1E5B1079004F2374 /* JavaScriptCore.h in Copy Headers */,
 				3DA9825B1E5B1079004F2374 /* JSCHelpers.h in Copy Headers */,
 				3DA9825C1E5B1079004F2374 /* JSCWrapper.h in Copy Headers */,
@@ -2304,7 +2298,6 @@
 		9936F3361F5F2F480010BF04 /* PrivateDataBase.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = PrivateDataBase.h; path = privatedata/PrivateDataBase.h; sourceTree = "<group>"; };
 		A2440AA01DF8D854006E7BFC /* RCTReloadCommand.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTReloadCommand.h; sourceTree = "<group>"; };
 		A2440AA11DF8D854006E7BFC /* RCTReloadCommand.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTReloadCommand.m; sourceTree = "<group>"; };
-		A2E0E69F208AA9EC007044C1 /* JSWeak.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSWeak.h; sourceTree = "<group>"; };
 		AC70D2E81DE489E4002E6351 /* RCTJavaScriptLoader.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = RCTJavaScriptLoader.mm; sourceTree = "<group>"; };
 		AC70D2EB1DE48A22002E6351 /* JSBundleType.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSBundleType.cpp; sourceTree = "<group>"; };
 		ACDD3FDA1BC7430D00E7DE33 /* RCTBorderStyle.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTBorderStyle.h; sourceTree = "<group>"; };
@@ -2762,7 +2755,6 @@
 		3D4A621D1DDD3985001F41B4 /* jschelpers */ = {
 			isa = PBXGroup;
 			children = (
-				A2E0E69F208AA9EC007044C1 /* JSWeak.h */,
 				19DED2281E77E29200F089BB /* systemJSCWrapper.cpp */,
 				3D7A27DC1DE32541002E3F95 /* JavaScriptCore.h */,
 				3D92B1071E0369AD0018521A /* JSCHelpers.cpp */,
@@ -3379,7 +3371,6 @@
 			files = (
 				19F61C041E8495FF00571D81 /* JSCHelpers.h in Headers */,
 				19F61C051E8495FF00571D81 /* noncopyable.h in Headers */,
-				A2C986E0208C7DF900C0D579 /* JSWeak.h in Headers */,
 				19F61C061E8495FF00571D81 /* Unicode.h in Headers */,
 				19F61C071E8495FF00571D81 /* Value.h in Headers */,
 				3D3030251DF8295E00D6DDAE /* JavaScriptCore.h in Headers */,
@@ -3427,7 +3418,6 @@
 			files = (
 				13EBC6821E28733C00880AC5 /* Value.h in Headers */,
 				13EBC6811E28733C00880AC5 /* Unicode.h in Headers */,
-				A2C986DF208C7DF700C0D579 /* JSWeak.h in Headers */,
 				13EBC6801E28733C00880AC5 /* noncopyable.h in Headers */,
 				13EBC67E1E28726000880AC5 /* JSCHelpers.h in Headers */,
 				3D3CD93D1DE5FC1400167DC4 /* JavaScriptCore.h in Headers */,
diff --git a/ReactCommon/jschelpers/BUCK b/ReactCommon/jschelpers/BUCK
index 990bb9882fa5..3a3bbc41d5d3 100644
--- a/ReactCommon/jschelpers/BUCK
+++ b/ReactCommon/jschelpers/BUCK
@@ -4,7 +4,6 @@ EXPORTED_HEADERS = [
     "JavaScriptCore.h",
     "JSCHelpers.h",
     "JSCWrapper.h",
-    "JSWeak.h",
     "noncopyable.h",
     "Unicode.h",
     "Value.h",
diff --git a/ReactCommon/jschelpers/JSCWrapper.h b/ReactCommon/jschelpers/JSCWrapper.h
index 15c15ef98e81..471c23948b4a 100644
--- a/ReactCommon/jschelpers/JSCWrapper.h
+++ b/ReactCommon/jschelpers/JSCWrapper.h
@@ -10,7 +10,6 @@
 #include <functional>
 #include <string>
 #include <JavaScriptCore/JavaScript.h>
-#include <jschelpers/JSWeak.h>
 
 #if defined(JSCINTERNAL) || (!defined(__APPLE__))
 #define JSC_IMPORT extern "C"
@@ -78,10 +77,6 @@ struct JSCWrapper {
   // JSContext
   JSC_WRAPPER_METHOD(JSContextGetGlobalContext);
   JSC_WRAPPER_METHOD(JSContextGetGlobalObject);
-  JSC_WRAPPER_METHOD(JSContextGetGroup);
-  JSC_WRAPPER_METHOD(JSContextGroupRetain);
-  JSC_WRAPPER_METHOD(JSContextGroupRelease);
-
   JSC_WRAPPER_METHOD(FBJSContextStartGCTimers);
 
   // JSEvaluate
@@ -147,12 +142,6 @@ struct JSCWrapper {
   JSC_WRAPPER_METHOD(JSValueUnprotect);
   JSC_WRAPPER_METHOD(JSValueIsNull);
 
-  // JSWeak
-  JSC_WRAPPER_METHOD(JSWeakCreate);
-  JSC_WRAPPER_METHOD(JSWeakRetain);
-  JSC_WRAPPER_METHOD(JSWeakRelease);
-  JSC_WRAPPER_METHOD(JSWeakGetObject);
-
   // Sampling profiler
   JSC_WRAPPER_METHOD(JSSamplingProfilerEnabled);
   JSC_WRAPPER_METHOD(JSPokeSamplingProfiler);
diff --git a/ReactCommon/jschelpers/JSWeak.h b/ReactCommon/jschelpers/JSWeak.h
deleted file mode 100644
index 9c0704237667..000000000000
--- a/ReactCommon/jschelpers/JSWeak.h
+++ /dev/null
@@ -1,32 +0,0 @@
-/**
- * Copyright (c) 2016-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-#include <JavaScriptCore/JSObjectRef.h>
-
-// These Symbols are included in JSC builds but not exported as part of the public headers.
-
-#ifndef JSWeakPrivate_h
-#define JSWeakPrivate_h
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-typedef struct OpaqueJSWeak* JSWeakRef;
-
-JSWeakRef JSWeakCreate(JSContextGroupRef, JSObjectRef);
-
-void JSWeakRetain(JSContextGroupRef, JSWeakRef);
-void JSWeakRelease(JSContextGroupRef, JSWeakRef);
-
-JSObjectRef JSWeakGetObject(JSWeakRef);
-
-#ifdef __cplusplus
-}
-#endif
-
-#endif // JSWeakPrivate_h
diff --git a/ReactCommon/jschelpers/JavaScriptCore.h b/ReactCommon/jschelpers/JavaScriptCore.h
index 5d7dd3ad891d..4c61e8aeb3a0 100644
--- a/ReactCommon/jschelpers/JavaScriptCore.h
+++ b/ReactCommon/jschelpers/JavaScriptCore.h
@@ -72,20 +72,16 @@
 #define JSC_JSGlobalContextRelease(...) __jsc_wrapper(JSGlobalContextRelease, __VA_ARGS__)
 #define JSC_JSGlobalContextSetName(...) __jsc_wrapper(JSGlobalContextSetName, __VA_ARGS__)
 
-jsc_poison(JSContextGroupCreate JSGlobalContextCreate JSGlobalContextCreateInGroup
-           JSGlobalContextCopyName JSGlobalContextRelease JSGlobalContextRetain
-           JSGlobalContextSetName)
+jsc_poison(JSContextGroupCreate JSContextGroupRelease JSContextGroupRetain
+           JSGlobalContextCreate JSGlobalContextCreateInGroup JSGlobalContextCopyName
+           JSGlobalContextRelease JSGlobalContextRetain JSGlobalContextSetName)
 
 // JSContext
 #define JSC_JSContextGetGlobalContext(...) __jsc_wrapper(JSContextGetGlobalContext, __VA_ARGS__)
 #define JSC_JSContextGetGlobalObject(...) __jsc_wrapper(JSContextGetGlobalObject, __VA_ARGS__)
-#define JSC_JSContextGetGroup(ctx) __jsc_wrapper(JSContextGetGroup, ctx)
-#define JSC_JSContextGroupRetain(...) __jsc_bool_wrapper(JSContextGroupRetain, __VA_ARGS__)
-#define JSC_JSContextGroupRelease(...) __jsc_bool_wrapper(JSContextGroupRelease, __VA_ARGS__)
 #define JSC_FBJSContextStartGCTimers(...) __jsc_wrapper(FBJSContextStartGCTimers, __VA_ARGS__)
 
-jsc_poison(JSContextGetGlobalContext JSContextGetGlobalObject JSContextGetGroup
-           JSContextGroupRelease JSContextGroupRetain FBJSContextStartGCTimers)
+jsc_poison(JSContextGetGlobalContext JSContextGetGlobalObject JSContextGetGroup FBJSContextStartGCTimers)
 
 // JSEvaluate
 #define JSC_JSEvaluateScript(...) __jsc_wrapper(JSEvaluateScript, __VA_ARGS__)
@@ -187,12 +183,6 @@ jsc_poison(JSObjectMakeArrayBufferWithBytesNoCopy JSObjectMakeTypedArray
            JSObjectGetTypedArrayBuffer JSObjectGetTypedArrayLength
            JSObjectGetArrayBufferBytesPtr JSObjectGetArrayBufferByteLength)
 
-// JSWeak
-#define JSC_JSWeakCreate(...) __jsc_bool_wrapper(JSWeakCreate, __VA_ARGS__)
-#define JSC_JSWeakRetain(...) __jsc_bool_wrapper(JSWeakRetain, __VA_ARGS__)
-#define JSC_JSWeakRelease(...) __jsc_bool_wrapper(JSWeakRelease, __VA_ARGS__)
-#define JSC_JSWeakGetObject(...) __jsc_drop_ctx_wrapper(JSWeakGetObject, __VA_ARGS__)
-
 // Sampling profiler
 #define JSC_JSSamplingProfilerEnabled(...) __jsc_drop_ctx_wrapper(JSSamplingProfilerEnabled, __VA_ARGS__)
 #define JSC_JSPokeSamplingProfiler(...) __jsc_wrapper(JSPokeSamplingProfiler, __VA_ARGS__)
diff --git a/ReactCommon/jschelpers/systemJSCWrapper.cpp b/ReactCommon/jschelpers/systemJSCWrapper.cpp
index c97180d7cc3e..eecb036f547c 100644
--- a/ReactCommon/jschelpers/systemJSCWrapper.cpp
+++ b/ReactCommon/jschelpers/systemJSCWrapper.cpp
@@ -34,11 +34,6 @@ UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(configureJSCForIOS)
 
 UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(FBJSContextStartGCTimers)
 
-UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(JSWeakCreate)
-UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(JSWeakRetain)
-UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(JSWeakRelease)
-UNIMPLEMENTED_SYSTEM_JSC_FUNCTION(JSWeakGetObject)
-
 bool JSSamplingProfilerEnabled() {
   return false;
 }
@@ -62,10 +57,6 @@ const JSCWrapper* systemJSCWrapper() {
 
       .JSContextGetGlobalContext = JSContextGetGlobalContext,
       .JSContextGetGlobalObject = JSContextGetGlobalObject,
-      .JSContextGetGroup = JSContextGetGroup,
-      .JSContextGroupRetain = JSContextGroupRetain,
-      .JSContextGroupRelease = JSContextGroupRelease,
-
       .FBJSContextStartGCTimers =
         (decltype(&FBJSContextStartGCTimers))
         Unimplemented_FBJSContextStartGCTimers,
@@ -131,19 +122,6 @@ const JSCWrapper* systemJSCWrapper() {
       .JSValueUnprotect = JSValueUnprotect,
       .JSValueIsNull = JSValueIsNull,
 
-      .JSWeakCreate =
-        (decltype(&JSWeakCreate))
-        Unimplemented_JSWeakCreate,
-      .JSWeakRetain =
-        (decltype(&JSWeakRetain))
-        Unimplemented_JSWeakRetain,
-      .JSWeakRelease =
-        (decltype(&JSWeakRelease))
-        Unimplemented_JSWeakRelease,
-      .JSWeakGetObject =
-        (decltype(&JSWeakGetObject))
-        Unimplemented_JSWeakGetObject,
-
       .JSSamplingProfilerEnabled = JSSamplingProfilerEnabled,
       .JSPokeSamplingProfiler =
         (decltype(&JSPokeSamplingProfiler))

From b8f30db0ae21d5f96547702abbf50aefa93b1094 Mon Sep 17 00:00:00 2001
From: Sean Nicolay <nicolay@fb.com>
Date: Tue, 22 May 2018 09:49:24 -0700
Subject: [PATCH 0642/1109] Fix or mark enum conversions

Reviewed By: adamjernst

Differential Revision: D8077375

fbshipit-source-id: 804ef985a773c7e1af6b7aa690790f57b10368f7
---
 React/Views/RCTShadowView.m | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/React/Views/RCTShadowView.m b/React/Views/RCTShadowView.m
index 84ad1c908c3e..fce31af6534a 100644
--- a/React/Views/RCTShadowView.m
+++ b/React/Views/RCTShadowView.m
@@ -9,6 +9,7 @@
 
 #import "RCTConvert.h"
 #import "RCTI18nUtil.h"
+#import "RCTLayout.h"
 #import "RCTLog.h"
 #import "RCTShadowView+Layout.h"
 #import "RCTUtils.h"
@@ -354,7 +355,7 @@ - (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize maximumSize:(CGSize)maximu
     constraintYogaNode,
     YGUndefined,
     YGUndefined,
-    self.layoutMetrics.layoutDirection
+    RCTYogaLayoutDirectionFromUIKitLayoutDirection(self.layoutMetrics.layoutDirection)
   );
 
   CGSize measuredSize = (CGSize){

From d94a9e2640d1a9cbd24cacd65cb1d1e6b54eca40 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 22 May 2018 15:45:55 -0700
Subject: [PATCH 0643/1109] Fabric: Composing YGNode object inside ShadowNode
 to avoid memory allocation overhead

Summary:
Given that fact that life-time of YGNode and ShadowNode objects must be idential and that we always allocate ShadowNode on heap,
we can embed YGNode object right inside ShadowNode object and use pointer to it safely.
That allows us to save additional memory allocation for every single layoutable shadow node! Whoo-hoo!

Reviewed By: fkgozali

Differential Revision: D8070121

fbshipit-source-id: 6eefbca1b7ac0a8aad235513b4c4899d414835f2
---
 .../fabric/view/root/RootShadowNode.cpp       |  3 +-
 .../view/yoga/YogaLayoutableShadowNode.cpp    | 55 ++++++++++---------
 .../view/yoga/YogaLayoutableShadowNode.h      |  7 ++-
 3 files changed, 35 insertions(+), 30 deletions(-)

diff --git a/ReactCommon/fabric/view/root/RootShadowNode.cpp b/ReactCommon/fabric/view/root/RootShadowNode.cpp
index 8fdbb50565a8..970eb8db7766 100644
--- a/ReactCommon/fabric/view/root/RootShadowNode.cpp
+++ b/ReactCommon/fabric/view/root/RootShadowNode.cpp
@@ -22,8 +22,7 @@ void RootShadowNode::layout() {
 
   // This is the rare place where shadow node must layout (set `layoutMetrics`)
   // itself because there is no a parent node which usually should do it.
-  YGNode *yogaNode = const_cast<YGNode *>(yogaNode_.get());
-  setLayoutMetrics(layoutMetricsFromYogaNode(*yogaNode));
+  setLayoutMetrics(layoutMetricsFromYogaNode(yogaNode_));
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 43586dea128f..d9082bdfc9ce 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -33,56 +33,57 @@ SharedYogaConfig YogaLayoutableShadowNode::suitableYogaConfig() {
 YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   const SharedYogaStylableProps &props,
   const SharedShadowNodeSharedList &children
-) {
+):
+  yogaNode_({}) {
   assert(props);
   assert(children);
 
-  yogaNode_ = std::make_unique<YGNode>();
-  yogaNode_->setConfig(suitableYogaConfig().get());
-  yogaNode_->setStyle(props->yogaStyle);
-  yogaNode_->setContext(this);
-  yogaNode_->setDirty(true);
-  YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(yogaNode_.get(), children);
+  yogaNode_.setConfig(suitableYogaConfig().get());
+  yogaNode_.setStyle(props->yogaStyle);
+  yogaNode_.setContext(this);
+  yogaNode_.setDirty(true);
+
+  YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(&yogaNode_, children);
 }
 
 YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   const SharedYogaLayoutableShadowNode &shadowNode,
   const SharedYogaStylableProps &props,
   const SharedShadowNodeSharedList &children
-) {
-  yogaNode_ = std::make_unique<YGNode>(*shadowNode->yogaNode_);
-  yogaNode_->setConfig(suitableYogaConfig().get());
-  yogaNode_->setContext(this);
-  yogaNode_->setOwner(nullptr);
-  yogaNode_->setDirty(true);
+):
+  yogaNode_(shadowNode->yogaNode_) {
+  yogaNode_.setConfig(suitableYogaConfig().get());
+  yogaNode_.setContext(this);
+  yogaNode_.setOwner(nullptr);
+  yogaNode_.setDirty(true);
 
   if (props) {
-    yogaNode_->setStyle(props->yogaStyle);
+    yogaNode_.setStyle(props->yogaStyle);
   }
 
   if (children) {
-    YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(yogaNode_.get(), children);
+    YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(&yogaNode_, children);
   }
 }
 
 void YogaLayoutableShadowNode::cleanLayout() {
-  yogaNode_->setDirty(false);
+  yogaNode_.setDirty(false);
 }
 
 void YogaLayoutableShadowNode::dirtyLayout() {
-  yogaNode_->markDirtyAndPropogate();
+  yogaNode_.markDirtyAndPropogate();
 }
 
 bool YogaLayoutableShadowNode::getIsLayoutClean() const {
-  return !yogaNode_->isDirty();
+  return !yogaNode_.isDirty();
 }
 
 bool YogaLayoutableShadowNode::getHasNewLayout() const {
-  return yogaNode_->getHasNewLayout();
+  return yogaNode_.getHasNewLayout();
 }
 
 void YogaLayoutableShadowNode::setHasNewLayout(bool hasNewLayout) {
-  yogaNode_->setHasNewLayout(hasNewLayout);
+  yogaNode_.setHasNewLayout(hasNewLayout);
 }
 
 #pragma mark - Mutating Methods
@@ -90,14 +91,14 @@ void YogaLayoutableShadowNode::setHasNewLayout(bool hasNewLayout) {
 void YogaLayoutableShadowNode::enableMeasurement() {
   ensureUnsealed();
 
-  yogaNode_->setMeasureFunc(YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector);
+  yogaNode_.setMeasureFunc(YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector);
 }
 
 void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child) {
   ensureUnsealed();
 
-  auto yogaNodeRawPtr = yogaNode_.get();
-  auto childYogaNodeRawPtr = child->yogaNode_.get();
+  auto yogaNodeRawPtr = &yogaNode_;
+  auto childYogaNodeRawPtr = &child->yogaNode_;
   yogaNodeRawPtr->insertChild(childYogaNodeRawPtr, yogaNodeRawPtr->getChildrenCount());
 
   if (childYogaNodeRawPtr->getOwner() == nullptr) {
@@ -109,7 +110,7 @@ void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child)
 void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
   if (!getIsLayoutClean()) {
     ensureUnsealed();
-    YGNodeCalculateLayout(yogaNode_.get(), YGUndefined, YGUndefined, YGDirectionInherit);
+    YGNodeCalculateLayout(&yogaNode_, YGUndefined, YGUndefined, YGDirectionInherit);
   }
 
   LayoutableShadowNode::layout(layoutContext);
@@ -124,7 +125,7 @@ void YogaLayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
 
     auto nonConstYogaLayoutableChild = std::const_pointer_cast<YogaLayoutableShadowNode>(yogaLayoutableChild);
 
-    LayoutMetrics childLayoutMetrics = layoutMetricsFromYogaNode(*nonConstYogaLayoutableChild->yogaNode_);
+    LayoutMetrics childLayoutMetrics = layoutMetricsFromYogaNode(nonConstYogaLayoutableChild->yogaNode_);
     nonConstYogaLayoutableChild->setLayoutMetrics(childLayoutMetrics);
   }
 }
@@ -160,7 +161,7 @@ YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYoga
     std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(parentShadowNodeRawPtr->cloneAndReplaceChild(oldShadowNode));
   assert(newShadowNode);
 
-  return newShadowNode->yogaNode_.get();
+  return &newShadowNode->yogaNode_;
 }
 
 YGSize YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector(YGNode *yogaNode, float width, YGMeasureMode widthMode, float height, YGMeasureMode heightMode) {
@@ -212,7 +213,7 @@ void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNo
       continue;
     }
 
-    auto &&childYogaNodeRawPtr = (YGNode *)yogaLayoutableShadowNode->yogaNode_.get();
+    auto &&childYogaNodeRawPtr = &yogaLayoutableShadowNode->yogaNode_;
 
     yogaNodeChildren.push_back(childYogaNodeRawPtr);
 
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index 4ed364b7513b..e0fc3b5e0c8b 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -80,7 +80,12 @@ class YogaLayoutableShadowNode:
   void layoutChildren(LayoutContext layoutContext) override;
 
 protected:
-  std::unique_ptr<YGNode> yogaNode_;
+  /*
+   * All Yoga functions only accept non-const arguments, so we have to mark
+   * Yoga node as `mutable` here to avoid `static_cast`ing the pointer to this
+   * all the time.
+   */
+  mutable YGNode yogaNode_;
 
 private:
   static SharedYogaConfig suitableYogaConfig();

From 2a3025da979e4d19792494db1f6d13a13b9b38a4 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 22 May 2018 15:48:19 -0700
Subject: [PATCH 0644/1109] Fabric: Application layer of events infrastructure

Summary: This implements `EventHandlers` abstract class (aka "Events Guy") which encapsulates `eventDispatcher` and `instanceHandle` (and ownership of future `eventTarget`), all of this as part of existing {ShadowNode + Props + LayoutMetrics + LocalData + Descriptor + (and now) EventHandlers} infra. (We don't plan to add anything else to this model. Ever.)

Reviewed By: fkgozali

Differential Revision: D8053351

fbshipit-source-id: 1dd9ccbcbe5a2eb284b59ea351dc8beca645e8bf
---
 ReactCommon/fabric/core/BUCK                  |  1 +
 .../componentdescriptor/ComponentDescriptor.h | 11 +++-
 .../ConcreteComponentDescriptor.h             | 39 ++++++++++---
 .../fabric/core/events/EventDispatcher.h      | 43 ++++++++++++++
 .../fabric/core/events/EventHandlers.cpp      | 34 +++++++++++
 .../fabric/core/events/EventHandlers.h        | 57 +++++++++++++++++++
 .../fabric/core/events/EventPrimitives.h      | 26 +++++++++
 .../core/shadownode/ConcreteShadowNode.h      | 10 +++-
 .../fabric/core/shadownode/ShadowNode.cpp     | 22 ++++---
 .../fabric/core/shadownode/ShadowNode.h       | 15 +++--
 .../core/tests/ComponentDescriptorTest.cpp    | 16 +++---
 .../fabric/core/tests/ShadowNodeTest.cpp      | 41 ++++++-------
 ReactCommon/fabric/core/tests/TestComponent.h |  2 +
 .../SampleComponentDescriptorFactor.cpp       |  2 +-
 .../uimanager/ComponentDescriptorFactory.h    |  3 +-
 .../fabric/uimanager/FabricUIManager.cpp      | 26 +++++----
 .../fabric/uimanager/FabricUIManager.h        | 10 ++--
 ReactCommon/fabric/uimanager/Scheduler.cpp    |  3 +-
 ReactCommon/fabric/uimanager/Scheduler.h      |  2 +
 .../uimanager/SchedulerEventDispatcher.cpp    | 23 ++++++++
 .../uimanager/SchedulerEventDispatcher.h      | 34 +++++++++++
 ReactCommon/fabric/uimanager/ShadowTree.cpp   |  7 ++-
 22 files changed, 350 insertions(+), 77 deletions(-)
 create mode 100644 ReactCommon/fabric/core/events/EventDispatcher.h
 create mode 100644 ReactCommon/fabric/core/events/EventHandlers.cpp
 create mode 100644 ReactCommon/fabric/core/events/EventHandlers.h
 create mode 100644 ReactCommon/fabric/core/events/EventPrimitives.h
 create mode 100644 ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
 create mode 100644 ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h

diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index e63e79ad94d7..a444f0726802 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -22,6 +22,7 @@ rn_xplat_cxx_library(
     exported_headers = subdir_glob(
         [
             ("", "*.h"),
+            ("events", "*.h"),
             ("primitives", "*.h"),
             ("componentdescriptor", "*.h"),
             ("layout", "*.h"),
diff --git a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
index 1b92620d9fdc..4804e5ad70cb 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
@@ -47,7 +47,7 @@ class ComponentDescriptor {
   virtual SharedShadowNode createShadowNode(
     const Tag &tag,
     const Tag &rootTag,
-    const InstanceHandle &instanceHandle,
+    const SharedEventHandlers &eventHandlers,
     const SharedProps &props
   ) const = 0;
 
@@ -57,6 +57,7 @@ class ComponentDescriptor {
   virtual SharedShadowNode cloneShadowNode(
     const SharedShadowNode &shadowNode,
     const SharedProps &props = nullptr,
+    const SharedEventHandlers &eventHandlers = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ) const = 0;
 
@@ -78,6 +79,14 @@ class ComponentDescriptor {
     const SharedProps &props,
     const RawProps &rawProps
   ) const = 0;
+
+  /*
+   * Creates a new `EventHandlers` object compatible with particular type of
+   * shadow nodes.
+   */
+  virtual SharedEventHandlers createEventHandlers(
+    const InstanceHandle &instanceHandle
+  ) const = 0;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 3d2721f81563..6ae4ea67321e 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -29,8 +29,13 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   using SharedShadowNodeT = std::shared_ptr<const ShadowNodeT>;
   using ConcreteProps = typename ShadowNodeT::ConcreteProps;
   using SharedConcreteProps = typename ShadowNodeT::SharedConcreteProps;
+  using ConcreteEventHandlers = typename ShadowNodeT::ConcreteEventHandlers;
+  using SharedConcreteEventHandlers = typename ShadowNodeT::SharedConcreteEventHandlers;
 
 public:
+  ConcreteComponentDescriptor(SharedEventDispatcher eventDispatcher):
+    eventDispatcher_(eventDispatcher) {}
+
   ComponentHandle getComponentHandle() const override {
     return typeid(ShadowNodeT).hash_code();
   }
@@ -43,8 +48,8 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     return std::make_shared<ShadowNodeT>(
       0,
       0,
-      nullptr,
       std::make_shared<const ConcreteProps>(),
+      nullptr,
       ShadowNode::emptySharedShadowNodeSharedList(),
       nullptr
     )->ShadowNodeT::getComponentName();
@@ -53,17 +58,21 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   SharedShadowNode createShadowNode(
     const Tag &tag,
     const Tag &rootTag,
-    const InstanceHandle &instanceHandle,
+    const SharedEventHandlers &eventHandlers,
     const SharedProps &props
   ) const override {
-    UnsharedShadowNode shadowNode = std::make_shared<ShadowNodeT>(
+    assert(std::dynamic_pointer_cast<const ConcreteProps>(props));
+    assert(std::dynamic_pointer_cast<const ConcreteEventHandlers>(eventHandlers));
+
+    auto &&shadowNode = std::make_shared<ShadowNodeT>(
       tag,
       rootTag,
-      instanceHandle,
       std::static_pointer_cast<const ConcreteProps>(props),
+      std::static_pointer_cast<const ConcreteEventHandlers>(eventHandlers),
       ShadowNode::emptySharedShadowNodeSharedList(),
       getCloneFunction()
     );
+
     adopt(shadowNode);
     return shadowNode;
   }
@@ -71,10 +80,18 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   SharedShadowNode cloneShadowNode(
     const SharedShadowNode &sourceShadowNode,
     const SharedProps &props = nullptr,
+    const SharedEventHandlers &eventHandlers = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ) const override {
     assert(std::dynamic_pointer_cast<const ShadowNodeT>(sourceShadowNode));
-    UnsharedShadowNode shadowNode = std::make_shared<ShadowNodeT>(std::static_pointer_cast<const ShadowNodeT>(sourceShadowNode), std::static_pointer_cast<const ConcreteProps>(props), children);
+
+    auto &&shadowNode = std::make_shared<ShadowNodeT>(
+      std::static_pointer_cast<const ShadowNodeT>(sourceShadowNode),
+      std::static_pointer_cast<const ConcreteProps>(props),
+      std::static_pointer_cast<const ConcreteEventHandlers>(eventHandlers),
+      children
+    );
+
     adopt(shadowNode);
     return shadowNode;
   }
@@ -95,6 +112,12 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     return ShadowNodeT::Props(rawProps, props);
   };
 
+  virtual SharedEventHandlers createEventHandlers(
+    const InstanceHandle &instanceHandle
+  ) const override {
+    return std::make_shared<ConcreteEventHandlers>(instanceHandle, eventDispatcher_);
+  }
+
 protected:
 
   virtual void adopt(UnsharedShadowNode shadowNode) const {
@@ -103,13 +126,15 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
 
 private:
 
+  mutable SharedEventDispatcher eventDispatcher_ {nullptr};
+
   mutable ShadowNodeCloneFunction cloneFunction_;
 
   ShadowNodeCloneFunction getCloneFunction() const {
     if (!cloneFunction_) {
-      cloneFunction_ = [this](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedShadowNodeSharedList &children) {
+      cloneFunction_ = [this](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedEventHandlers &eventHandlers, const SharedShadowNodeSharedList &children) {
         assert(std::dynamic_pointer_cast<const ShadowNodeT>(shadowNode));
-        return this->cloneShadowNode(shadowNode, props, children);
+        return this->cloneShadowNode(shadowNode, props, eventHandlers, children);
       };
     }
 
diff --git a/ReactCommon/fabric/core/events/EventDispatcher.h b/ReactCommon/fabric/core/events/EventDispatcher.h
new file mode 100644
index 000000000000..354e35ed4770
--- /dev/null
+++ b/ReactCommon/fabric/core/events/EventDispatcher.h
@@ -0,0 +1,43 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/ReactPrimitives.h>
+#include <fabric/core/EventPrimitives.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+class EventDispatcher;
+
+using SharedEventDispatcher = std::shared_ptr<const EventDispatcher>;
+
+/*
+ * Abstract class that represent event-delivery infrastructure.
+ * Particular `EventHandlers` clases use an object of this class to invoke
+ * events.
+ */
+class EventDispatcher {
+
+public:
+
+  /*
+   * Dispatches "raw" event using some event-delivery infrastructure.
+   */
+  virtual void dispatchEvent(
+    const InstanceHandle &instanceHandle,
+    const std::string &name,
+    const folly::dynamic &payload,
+    const EventPriority &priority
+  ) const = 0;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/events/EventHandlers.cpp b/ReactCommon/fabric/core/events/EventHandlers.cpp
new file mode 100644
index 000000000000..25bd7dfec90a
--- /dev/null
+++ b/ReactCommon/fabric/core/events/EventHandlers.cpp
@@ -0,0 +1,34 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "EventHandlers.h"
+
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+EventHandlers::EventHandlers(InstanceHandle instanceHandle, SharedEventDispatcher eventDispatcher):
+  instanceHandle_(instanceHandle),
+  eventDispatcher_(eventDispatcher) {}
+
+void EventHandlers::dispatchEvent(
+  const std::string &name,
+  const folly::dynamic &payload,
+  const EventPriority &priority
+) const {
+  auto &&eventDispatcher = eventDispatcher_.lock();
+  if (!eventDispatcher) {
+    return;
+  }
+
+  // TODO(T29610783): Reconsider using dynamic dispatch here.
+  eventDispatcher->dispatchEvent(instanceHandle_, name, payload, priority);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/events/EventHandlers.h b/ReactCommon/fabric/core/events/EventHandlers.h
new file mode 100644
index 000000000000..596e8871a90f
--- /dev/null
+++ b/ReactCommon/fabric/core/events/EventHandlers.h
@@ -0,0 +1,57 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+#pragma once
+
+#include <memory>
+
+#include <folly/dynamic.h>
+#include <fabric/core/EventDispatcher.h>
+#include <fabric/core/EventPrimitives.h>
+#include <fabric/core/ReactPrimitives.h>
+
+namespace facebook {
+namespace react {
+
+class EventHandlers;
+
+using SharedEventHandlers = std::shared_ptr<const EventHandlers>;
+
+
+
+/*
+ * Base class for all particular typed event handlers.
+ * Stores `InstanceHandle` identifying a particular component and the pointer
+ * to `EventDispatcher` which is responsible for delivering the event.
+ *
+ * TODO: Reconsider naming of all event-related things.
+ */
+class EventHandlers {
+
+public:
+  EventHandlers(InstanceHandle instanceHandle, SharedEventDispatcher eventDispatcher);
+  virtual ~EventHandlers() = default;
+
+protected:
+
+  /*
+   * Initates an event delivery process.
+   * Is used by particular subclasses only.
+   */
+  void dispatchEvent(
+    const std::string &name,
+    const folly::dynamic &payload = {},
+    const EventPriority &priority = EventPriority::AsynchronousBatched
+  ) const;
+
+private:
+
+  InstanceHandle instanceHandle_;
+  std::weak_ptr<const EventDispatcher> eventDispatcher_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/events/EventPrimitives.h b/ReactCommon/fabric/core/events/EventPrimitives.h
new file mode 100644
index 000000000000..ba12b23b1be0
--- /dev/null
+++ b/ReactCommon/fabric/core/events/EventPrimitives.h
@@ -0,0 +1,26 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+namespace facebook {
+namespace react {
+
+enum class EventPriority {
+  SynchronousUnbatched,
+  SynchronousBatched,
+  AsynchronousUnbatched,
+  AsynchronousBatched,
+
+  Sync = SynchronousUnbatched,
+  Work = SynchronousBatched,
+  Interactive = AsynchronousUnbatched,
+  Deferred = AsynchronousBatched,
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index 6cf911ea1328..86c0976b8ce6 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -19,13 +19,15 @@ namespace react {
  * `ConcreteShadowNode` is a default implementation of `ShadowNode` interface
  * with many handy features.
  */
-template <typename PropsT>
+template <typename PropsT, typename EventHandlersT = EventHandlers>
 class ConcreteShadowNode: public ShadowNode {
   static_assert(std::is_base_of<Props, PropsT>::value, "PropsT must be a descendant of Props");
 
 public:
   using ConcreteProps = PropsT;
   using SharedConcreteProps = std::shared_ptr<const PropsT>;
+  using ConcreteEventHandlers = EventHandlersT;
+  using SharedConcreteEventHandlers = std::shared_ptr<const EventHandlersT>;
   using SharedConcreteShadowNode = std::shared_ptr<const ConcreteShadowNode>;
 
   static SharedConcreteProps Props(const RawProps &rawProps, const SharedProps &baseProps = nullptr) {
@@ -40,16 +42,16 @@ class ConcreteShadowNode: public ShadowNode {
   ConcreteShadowNode(
     const Tag &tag,
     const Tag &rootTag,
-    const InstanceHandle &instanceHandle,
     const SharedConcreteProps &props,
+    const SharedConcreteEventHandlers &eventHandlers,
     const SharedShadowNodeSharedList &children,
     const ShadowNodeCloneFunction &cloneFunction
   ):
     ShadowNode(
       tag,
       rootTag,
-      instanceHandle,
       (SharedProps)props,
+      eventHandlers,
       children,
       cloneFunction
     ) {};
@@ -57,11 +59,13 @@ class ConcreteShadowNode: public ShadowNode {
   ConcreteShadowNode(
     const SharedConcreteShadowNode &shadowNode,
     const SharedProps &props,
+    const SharedEventHandlers &eventHandlers,
     const SharedShadowNodeSharedList &children
   ):
     ShadowNode(
       shadowNode,
       (SharedProps)props,
+      eventHandlers,
       children
     ) {}
 
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index b4883c22f4d8..e18ae2e387d2 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -23,15 +23,15 @@ SharedShadowNodeSharedList ShadowNode::emptySharedShadowNodeSharedList() {
 ShadowNode::ShadowNode(
   const Tag &tag,
   const Tag &rootTag,
-  const InstanceHandle &instanceHandle,
   const SharedProps &props,
+  const SharedEventHandlers &eventHandlers,
   const SharedShadowNodeSharedList &children,
   const ShadowNodeCloneFunction &cloneFunction
 ):
   tag_(tag),
   rootTag_(rootTag),
-  instanceHandle_(instanceHandle),
   props_(props),
+  eventHandlers_(eventHandlers),
   children_(std::make_shared<SharedShadowNodeList>(*children)),
   cloneFunction_(cloneFunction),
   revision_(1) {}
@@ -39,12 +39,13 @@ ShadowNode::ShadowNode(
 ShadowNode::ShadowNode(
   const SharedShadowNode &shadowNode,
   const SharedProps &props,
+  const SharedEventHandlers &eventHandlers,
   const SharedShadowNodeSharedList &children
 ):
   tag_(shadowNode->tag_),
   rootTag_(shadowNode->rootTag_),
-  instanceHandle_(shadowNode->instanceHandle_),
   props_(props ? props : shadowNode->props_),
+  eventHandlers_(eventHandlers ? eventHandlers : shadowNode->eventHandlers_),
   children_(std::make_shared<SharedShadowNodeList>(*(children ? children : shadowNode->children_))),
   sourceNode_(shadowNode),
   localData_(shadowNode->localData_),
@@ -56,7 +57,7 @@ SharedShadowNode ShadowNode::clone(
   const SharedShadowNodeSharedList &children
 ) const {
   assert(cloneFunction_);
-  return cloneFunction_(shared_from_this(), props_, children_);
+  return cloneFunction_(shared_from_this(), props_, eventHandlers_, children_);
 }
 
 #pragma mark - Getters
@@ -69,6 +70,10 @@ SharedProps ShadowNode::getProps() const {
   return props_;
 }
 
+SharedEventHandlers ShadowNode::getEventHandlers() const {
+  return eventHandlers_;
+}
+
 Tag ShadowNode::getTag() const {
   return tag_;
 }
@@ -77,10 +82,6 @@ Tag ShadowNode::getRootTag() const {
   return rootTag_;
 }
 
-InstanceHandle ShadowNode::getInstanceHandle() const {
-  return instanceHandle_;
-}
-
 SharedShadowNode ShadowNode::getSourceNode() const {
   return sourceNode_.lock();
 }
@@ -146,6 +147,7 @@ bool ShadowNode::operator==(const ShadowNode& rhs) const {
     tag_ == rhs.tag_ &&
     rootTag_ == rhs.rootTag_ &&
     props_ == rhs.props_ &&
+    eventHandlers_ == rhs.eventHandlers_ &&
     localData_ == rhs.localData_;
 }
 
@@ -181,10 +183,6 @@ SharedDebugStringConvertibleList ShadowNode::getDebugProps() const {
 
   list.push_back(std::make_shared<DebugStringConvertibleItem>("tag", std::to_string(tag_)));
 
-  if (instanceHandle_) {
-    list.push_back(std::make_shared<DebugStringConvertibleItem>("handle", std::to_string((size_t)instanceHandle_)));
-  }
-
   SharedShadowNode sourceNode = getSourceNode();
   if (sourceNode) {
     list.push_back(std::make_shared<DebugStringConvertibleItem>(
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 927590b868e4..9fa1b9341d9f 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -11,6 +11,7 @@
 #include <memory>
 #include <vector>
 
+#include <fabric/core/EventHandlers.h>
 #include <fabric/core/LocalData.h>
 #include <fabric/core/Props.h>
 #include <fabric/core/ReactPrimitives.h>
@@ -29,7 +30,12 @@ using SharedShadowNodeSharedList = std::shared_ptr<const SharedShadowNodeList>;
 using SharedShadowNodeUnsharedList = std::shared_ptr<SharedShadowNodeList>;
 using WeakShadowNode = std::weak_ptr<const ShadowNode>;
 
-using ShadowNodeCloneFunction = std::function<SharedShadowNode(SharedShadowNode shadowNode, SharedProps props, SharedShadowNodeSharedList children)>;
+using ShadowNodeCloneFunction = std::function<SharedShadowNode(
+  const SharedShadowNode &shadowNode,
+  const SharedProps &props,
+  const SharedEventHandlers &eventHandlers,
+  const SharedShadowNodeSharedList &children
+)>;
 
 class ShadowNode:
   public virtual Sealable,
@@ -43,8 +49,8 @@ class ShadowNode:
   ShadowNode(
     const Tag &tag,
     const Tag &rootTag,
-    const InstanceHandle &instanceHandle,
     const SharedProps &props,
+    const SharedEventHandlers &eventHandlers,
     const SharedShadowNodeSharedList &children,
     const ShadowNodeCloneFunction &cloneFunction
   );
@@ -52,6 +58,7 @@ class ShadowNode:
   ShadowNode(
     const SharedShadowNode &shadowNode,
     const SharedProps &props,
+    const SharedEventHandlers &eventHandlers,
     const SharedShadowNodeSharedList &children
   );
 
@@ -70,9 +77,9 @@ class ShadowNode:
 
   SharedShadowNodeSharedList getChildren() const;
   SharedProps getProps() const;
+  SharedEventHandlers getEventHandlers() const;
   Tag getTag() const;
   Tag getRootTag() const;
-  InstanceHandle getInstanceHandle() const;
 
   /*
    * Returns the node which was used as a prototype in clone constructor.
@@ -135,8 +142,8 @@ class ShadowNode:
 protected:
   Tag tag_;
   Tag rootTag_;
-  InstanceHandle instanceHandle_;
   SharedProps props_;
+  SharedEventHandlers eventHandlers_;
   SharedShadowNodeSharedList children_;
   WeakShadowNode sourceNode_;
   SharedLocalData localData_;
diff --git a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
index f297d3800a84..99fb54201f02 100644
--- a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
+++ b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
@@ -12,7 +12,7 @@
 using namespace facebook::react;
 
 TEST(ComponentDescriptorTest, createShadowNode) {
-  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>();
+  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>(nullptr);
 
   ASSERT_EQ(descriptor->getComponentHandle(), typeid(TestShadowNode).hash_code());
   ASSERT_STREQ(descriptor->getComponentName().c_str(), "Test");
@@ -20,7 +20,7 @@ TEST(ComponentDescriptorTest, createShadowNode) {
   RawProps raw;
   raw["nativeID"] = "abc";
   SharedProps props = descriptor->cloneProps(nullptr, raw);
-  SharedShadowNode node = descriptor->createShadowNode(9, 1, (void *)NULL, props);
+  SharedShadowNode node = descriptor->createShadowNode(9, 1, nullptr, props);
 
   ASSERT_EQ(node->getComponentHandle(), typeid(TestShadowNode).hash_code());
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
@@ -30,12 +30,12 @@ TEST(ComponentDescriptorTest, createShadowNode) {
 }
 
 TEST(ComponentDescriptorTest, cloneShadowNode) {
-  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>();
+  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>(nullptr);
 
   RawProps raw;
   raw["nativeID"] = "abc";
   SharedProps props = descriptor->cloneProps(nullptr, raw);
-  SharedShadowNode node = descriptor->createShadowNode(9, 1, (void *)NULL, props);
+  SharedShadowNode node = descriptor->createShadowNode(9, 1, nullptr, props);
   SharedShadowNode cloned = descriptor->cloneShadowNode(node);
 
   ASSERT_EQ(cloned->getComponentHandle(), typeid(TestShadowNode).hash_code());
@@ -46,14 +46,14 @@ TEST(ComponentDescriptorTest, cloneShadowNode) {
 }
 
 TEST(ComponentDescriptorTest, appendChild) {
-  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>();
+  SharedComponentDescriptor descriptor = std::make_shared<TestComponentDescriptor>(nullptr);
 
   RawProps raw;
   raw["nativeID"] = "abc";
   SharedProps props = descriptor->cloneProps(nullptr, raw);
-  SharedShadowNode node1 = descriptor->createShadowNode(1, 1, (void *)NULL, props);
-  SharedShadowNode node2 = descriptor->createShadowNode(2, 1, (void *)NULL, props);
-  SharedShadowNode node3 = descriptor->createShadowNode(3, 1, (void *)NULL, props);
+  SharedShadowNode node1 = descriptor->createShadowNode(1, 1, nullptr, props);
+  SharedShadowNode node2 = descriptor->createShadowNode(2, 1, nullptr, props);
+  SharedShadowNode node3 = descriptor->createShadowNode(3, 1, nullptr, props);
 
   descriptor->appendChild(node1, node2);
   descriptor->appendChild(node1, node3);
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index dfdf0dec4ae5..7afbafbb5f8a 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -28,13 +28,13 @@ TEST(ShadowNodeTest, handleProps) {
 }
 
 TEST(ShadowNodeTest, handleShadowNodeCreation) {
-  auto node = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, std::make_shared<const TestProps>(), ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto node = std::make_shared<TestShadowNode>(9, 1, std::make_shared<const TestProps>(), nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
 
   ASSERT_FALSE(node->getSealed());
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
   ASSERT_EQ(node->getTag(), 9);
   ASSERT_EQ(node->getRootTag(), 1);
-  ASSERT_EQ(node->getInstanceHandle(), (void *)NULL);
+  ASSERT_EQ(node->getEventHandlers(), nullptr);
   TestShadowNode *nodePtr = node.get();
   ASSERT_EQ(node->getComponentHandle(), typeid(*nodePtr).hash_code());
   ASSERT_EQ(node->getSourceNode(), nullptr);
@@ -48,21 +48,21 @@ TEST(ShadowNodeTest, handleShadowNodeCreation) {
 }
 
 TEST(ShadowNodeTest, handleShadowNodeSimpleCloning) {
-  auto node = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, std::make_shared<const TestProps>(), ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
-  auto node2 = std::make_shared<TestShadowNode>(node, nullptr, nullptr);
+  auto node = std::make_shared<TestShadowNode>(9, 1, std::make_shared<const TestProps>(), nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto node2 = std::make_shared<TestShadowNode>(node, nullptr, nullptr, nullptr);
 
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
   ASSERT_EQ(node->getTag(), 9);
   ASSERT_EQ(node->getRootTag(), 1);
-  ASSERT_EQ(node->getInstanceHandle(), (void *)NULL);
+  ASSERT_EQ(node->getEventHandlers(), nullptr);
   ASSERT_EQ(node2->getSourceNode(), node);
 }
 
 TEST(ShadowNodeTest, handleShadowNodeMutation) {
   auto props = std::make_shared<const TestProps>();
-  auto node1 = std::make_shared<TestShadowNode>(1, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
-  auto node2 = std::make_shared<TestShadowNode>(2, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
-  auto node3 = std::make_shared<TestShadowNode>(3, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto node1 = std::make_shared<TestShadowNode>(1, 1, props, nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto node2 = std::make_shared<TestShadowNode>(2, 1, props, nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto node3 = std::make_shared<TestShadowNode>(3, 1, props, nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
 
   node1->appendChild(node2);
   node1->appendChild(node3);
@@ -71,7 +71,7 @@ TEST(ShadowNodeTest, handleShadowNodeMutation) {
   ASSERT_EQ(node1Children->at(0), node2);
   ASSERT_EQ(node1Children->at(1), node3);
 
-  auto node4 = std::make_shared<TestShadowNode>(node2, nullptr, nullptr);
+  auto node4 = std::make_shared<TestShadowNode>(node2, nullptr, nullptr, nullptr);
   node1->replaceChild(node2, node4);
   node1Children = node1->getChildren();
   ASSERT_EQ(node1Children->size(), 2);
@@ -87,16 +87,16 @@ TEST(ShadowNodeTest, handleShadowNodeMutation) {
   // No more mutation after sealing.
   EXPECT_THROW(node4->clearSourceNode(), std::runtime_error);
 
-  auto node5 = std::make_shared<TestShadowNode>(node4, nullptr, nullptr);
+  auto node5 = std::make_shared<TestShadowNode>(node4, nullptr, nullptr, nullptr);
   node5->clearSourceNode();
   ASSERT_EQ(node5->getSourceNode(), nullptr);
 }
 
 TEST(ShadowNodeTest, handleSourceNode) {
-  auto nodeFirstGeneration = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, std::make_shared<const TestProps>(), ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
-  auto nodeSecondGeneration = std::make_shared<TestShadowNode>(nodeFirstGeneration, nullptr, nullptr);
-  auto nodeThirdGeneration = std::make_shared<TestShadowNode>(nodeSecondGeneration, nullptr, nullptr);
-  auto nodeForthGeneration = std::make_shared<TestShadowNode>(nodeThirdGeneration, nullptr, nullptr);
+  auto nodeFirstGeneration = std::make_shared<TestShadowNode>(9, 1, std::make_shared<const TestProps>(), nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto nodeSecondGeneration = std::make_shared<TestShadowNode>(nodeFirstGeneration, nullptr, nullptr, nullptr);
+  auto nodeThirdGeneration = std::make_shared<TestShadowNode>(nodeSecondGeneration, nullptr, nullptr, nullptr);
+  auto nodeForthGeneration = std::make_shared<TestShadowNode>(nodeThirdGeneration, nullptr, nullptr, nullptr);
 
   // Ensure established shource nodes structure.
   ASSERT_EQ(nodeForthGeneration->getSourceNode(), nodeThirdGeneration);
@@ -117,7 +117,7 @@ TEST(ShadowNodeTest, handleSourceNode) {
 }
 
 TEST(ShadowNodeTest, handleCloneFunction) {
-  auto firstNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, std::make_shared<const TestProps>(), ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto firstNode = std::make_shared<TestShadowNode>(9, 1, std::make_shared<const TestProps>(), nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
 
   // The shadow node is not clonable if `cloneFunction` is not provided,
   ASSERT_DEATH_IF_SUPPORTED(firstNode->clone(), "cloneFunction_");
@@ -125,13 +125,14 @@ TEST(ShadowNodeTest, handleCloneFunction) {
   auto secondNode = std::make_shared<TestShadowNode>(
     9,
     1,
-    (void *)NULL,
     std::make_shared<const TestProps>(),
+    nullptr,
     ShadowNode::emptySharedShadowNodeSharedList(),
-    [](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedShadowNodeSharedList &children) {
+    [](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedEventHandlers &eventHandlers, const SharedShadowNodeSharedList &children) {
       return std::make_shared<const TestShadowNode>(
         std::static_pointer_cast<const TestShadowNode>(shadowNode),
         props,
+        nullptr,
         children
       );
     }
@@ -161,9 +162,9 @@ TEST(ShadowNodeTest, handleLocalData) {
   auto localDataOver9000 = std::make_shared<TestLocalData>();
   localDataOver9000->setNumber(9001);
   auto props = std::make_shared<const TestProps>();
-  auto firstNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
-  auto secondNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
-  auto thirdNode = std::make_shared<TestShadowNode>(9, 1, (void *)NULL, props, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto firstNode = std::make_shared<TestShadowNode>(9, 1, props, nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto secondNode = std::make_shared<TestShadowNode>(9, 1, props, nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
+  auto thirdNode = std::make_shared<TestShadowNode>(9, 1, props, nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
 
   firstNode->setLocalData(localData42);
   secondNode->setLocalData(localData42);
diff --git a/ReactCommon/fabric/core/tests/TestComponent.h b/ReactCommon/fabric/core/tests/TestComponent.h
index b7257caabc06..8659b960ca34 100644
--- a/ReactCommon/fabric/core/tests/TestComponent.h
+++ b/ReactCommon/fabric/core/tests/TestComponent.h
@@ -57,6 +57,8 @@ class TestShadowNode : public ConcreteShadowNode<TestProps> {
 
 class TestComponentDescriptor: public ConcreteComponentDescriptor<TestShadowNode> {
 public:
+  using ConcreteComponentDescriptor::ConcreteComponentDescriptor;
+
   // TODO (shergin): Why does this gets repeated here and the shadow node class?
   ComponentName getComponentName() const override {
     return "Test";
diff --git a/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp b/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
index d45a37351fae..28a8a8b29790 100644
--- a/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
+++ b/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
@@ -14,7 +14,7 @@ namespace react {
 /**
  * This is a sample implementation. Each app should provide its own.
  */
-SharedComponentDescriptorRegistry ComponentDescriptorFactory::buildRegistry() {
+SharedComponentDescriptorRegistry ComponentDescriptorFactory::buildRegistry(const SharedEventDispatcher &eventDispatcher) {
   auto registry = std::make_shared<ComponentDescriptorRegistry>();
   return registry;
 }
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h b/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
index c729c45f4b17..ea6ef34ac6ca 100644
--- a/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
@@ -10,6 +10,7 @@
 #include <memory>
 
 #include <fabric/core/ComponentDescriptor.h>
+#include <fabric/core/EventDispatcher.h>
 
 #include "ComponentDescriptorRegistry.h"
 
@@ -24,7 +25,7 @@ namespace react {
 class ComponentDescriptorFactory {
 
 public:
-  static SharedComponentDescriptorRegistry buildRegistry();
+  static SharedComponentDescriptorRegistry buildRegistry(const SharedEventDispatcher &eventDispatcher);
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index b725b9739caf..c41eddf0da36 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -91,7 +91,7 @@ UIManagerDelegate *FabricUIManager::getDelegate() {
   return delegate_;
 }
 
-SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, void *instanceHandle) {
+SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, InstanceHandle instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
 
   ComponentName componentName = componentNameByReactViewName(viewName);
@@ -102,7 +102,7 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
     componentDescriptor->createShadowNode(
       tag,
       rootTag,
-      instanceHandle,
+      componentDescriptor->createEventHandlers(instanceHandle),
       componentDescriptor->cloneProps(nullptr, rawProps)
     );
 
@@ -115,28 +115,32 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
   return shadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode, void *instanceHandle) {
+SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode, InstanceHandle instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
 
-  // TODO: Retain new instanceHandle
   SharedShadowNode clonedShadowNode =
-    componentDescriptor->cloneShadowNode(shadowNode);
+    componentDescriptor->cloneShadowNode(
+      shadowNode,
+      nullptr,
+      componentDescriptor->createEventHandlers(instanceHandle),
+      nullptr
+    );
 
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNode() -> " << clonedShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false});
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode, void *instanceHandle) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode, InstanceHandle instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   // Assuming semantic: Cloning with same props but empty children.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
 
-  // TODO: Retain new instanceHandle
   SharedShadowNode clonedShadowNode =
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
+      componentDescriptor->createEventHandlers(instanceHandle),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
@@ -144,17 +148,17 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props, void *instanceHandle) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props, InstanceHandle instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with same children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
 
-  // TODO: Retain new instanceHandle
   SharedShadowNode clonedShadowNode =
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
+      componentDescriptor->createEventHandlers(instanceHandle),
       nullptr
     );
 
@@ -162,17 +166,17 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props, void *instanceHandle) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props, InstanceHandle instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with empty children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
   RawProps rawProps = rawPropsFromDynamic(props);
 
-  // TODO: Retain new instanceHandle
   SharedShadowNode clonedShadowNode =
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
+      componentDescriptor->createEventHandlers(instanceHandle),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index 4fb64c780f0e..edf887ebab1d 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -35,11 +35,11 @@ class FabricUIManager {
 
 #pragma mark - JavaScript/React-facing Interface
 
-  SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, void *instanceHandle);
-  SharedShadowNode cloneNode(const SharedShadowNode &node, void *instanceHandle);
-  SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node, void *instanceHandle);
-  SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props, void *instanceHandle);
-  SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps, void *instanceHandle);
+  SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, InstanceHandle instanceHandle);
+  SharedShadowNode cloneNode(const SharedShadowNode &node, InstanceHandle instanceHandle);
+  SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node, InstanceHandle instanceHandle);
+  SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props, InstanceHandle instanceHandle);
+  SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps, InstanceHandle instanceHandle);
   void appendChild(const SharedShadowNode &parentNode, const SharedShadowNode &childNode);
   SharedShadowNodeUnsharedList createChildSet(Tag rootTag);
   void appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode);
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index 235206dbdc59..0183c3a5987a 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -20,7 +20,8 @@ namespace facebook {
 namespace react {
 
 Scheduler::Scheduler() {
-  auto componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry();
+  eventDispatcher_ = std::make_shared<SchedulerEventDispatcher>();
+  auto componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry(eventDispatcher_);
   uiManager_ = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
   uiManager_->setDelegate(this);
 }
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index c3730a03346f..5ccd8cbb3a3c 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -7,6 +7,7 @@
 #include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/uimanager/SchedulerDelegate.h>
+#include <fabric/uimanager/SchedulerEventDispatcher.h>
 #include <fabric/uimanager/UIManagerDelegate.h>
 #include <fabric/uimanager/ShadowTree.h>
 #include <fabric/uimanager/ShadowTreeDelegate.h>
@@ -69,6 +70,7 @@ class Scheduler final:
   SchedulerDelegate *delegate_;
   std::shared_ptr<FabricUIManager> uiManager_;
   std::unordered_map<Tag, SharedShadowTree> shadowTreeRegistry_;
+  std::shared_ptr<SchedulerEventDispatcher> eventDispatcher_;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
new file mode 100644
index 000000000000..ad9f44136361
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "SchedulerEventDispatcher.h"
+
+namespace facebook {
+namespace react {
+
+void SchedulerEventDispatcher::dispatchEvent(
+  const InstanceHandle &instanceHandle,
+  const std::string &name,
+  const folly::dynamic &payload,
+  const EventPriority &priority
+) const {
+  // Some future magic here.
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
new file mode 100644
index 000000000000..17cd7610951f
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
@@ -0,0 +1,34 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/EventDispatcher.h>
+#include <fabric/core/EventPrimitives.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Concrete EventDispatcher.
+ */
+class SchedulerEventDispatcher final:
+  public EventDispatcher {
+
+public:
+
+  void dispatchEvent(
+    const InstanceHandle &instanceHandle,
+    const std::string &name,
+    const folly::dynamic &payload,
+    const EventPriority &priority
+  ) const override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index c274d2e68520..439369b9e550 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -15,11 +15,12 @@ namespace react {
 ShadowTree::ShadowTree(Tag rootTag):
   rootTag_(rootTag) {
 
+  auto &&noopEventHandlers = std::make_shared<const ViewEventHandlers>(nullptr, nullptr);
   rootShadowNode_ = std::make_shared<RootShadowNode>(
     rootTag,
     rootTag,
-    nullptr,
     RootShadowNode::defaultSharedProps(),
+    noopEventHandlers,
     ShadowNode::emptySharedShadowNodeSharedList(),
     nullptr
   );
@@ -47,14 +48,14 @@ void ShadowTree::constraintLayout(const LayoutConstraints &layoutConstraints, co
 UnsharedRootShadowNode ShadowTree::cloneRootShadowNode(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const {
   auto oldRootShadowNode = rootShadowNode_;
   auto &&props = std::make_shared<const RootProps>(*oldRootShadowNode->getProps(), layoutConstraints, layoutContext);
-  auto newRootShadowNode = std::make_shared<RootShadowNode>(oldRootShadowNode, props, nullptr);
+  auto newRootShadowNode = std::make_shared<RootShadowNode>(oldRootShadowNode, props, nullptr, nullptr);
   return newRootShadowNode;
 }
 
 void ShadowTree::complete(const SharedShadowNodeUnsharedList &rootChildNodes) {
   auto oldRootShadowNode = rootShadowNode_;
   auto newRootShadowNode =
-    std::make_shared<RootShadowNode>(oldRootShadowNode, nullptr, SharedShadowNodeSharedList(rootChildNodes));
+    std::make_shared<RootShadowNode>(oldRootShadowNode, nullptr, nullptr, SharedShadowNodeSharedList(rootChildNodes));
 
   complete(newRootShadowNode);
 }

From 1064dad9bf95a21920b19039cc22579ea01198fa Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 22 May 2018 15:48:21 -0700
Subject: [PATCH 0645/1109] Fabric: Support of updating EventHandlers on
 mounting layer

Summary:
Pretty trivial; new type of mount item & new method in the component protocol.
The default implementation in `UIView+ComponentViewProtocol` does nothing.

Reviewed By: fkgozali

Differential Revision: D8053355

fbshipit-source-id: a0418edf17ca75c4b94942b04acd93f3ea5d27e0
---
 .../RCTUpdateEventHandlersMountItem.h         | 26 +++++++++++++
 .../RCTUpdateEventHandlersMountItem.mm        | 37 +++++++++++++++++++
 .../Mounting/RCTComponentViewProtocol.h       |  7 ++++
 React/Fabric/Mounting/RCTMountingManager.mm   | 28 +++++++++++---
 .../Mounting/UIView+ComponentViewProtocol.h   |  3 ++
 .../Mounting/UIView+ComponentViewProtocol.mm  |  5 +++
 6 files changed, 100 insertions(+), 6 deletions(-)
 create mode 100644 React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.h
 create mode 100644 React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.mm

diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.h b/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.h
new file mode 100644
index 000000000000..dd11971b8494
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.h
@@ -0,0 +1,26 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTMountItemProtocol.h>
+#import <React/RCTPrimitives.h>
+#import <fabric/core/EventHandlers.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * Updates event handlers of a component view.
+ */
+@interface RCTUpdateEventHandlersMountItem : NSObject <RCTMountItemProtocol>
+
+- (instancetype)initWithTag:(ReactTag)tag
+              eventHandlers:(facebook::react::SharedEventHandlers)eventHandlers;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.mm b/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.mm
new file mode 100644
index 000000000000..cc3066b059cf
--- /dev/null
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.mm
@@ -0,0 +1,37 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTUpdateEventHandlersMountItem.h"
+
+#import "RCTComponentViewRegistry.h"
+
+using namespace facebook::react;
+
+@implementation RCTUpdateEventHandlersMountItem {
+  ReactTag _tag;
+  SharedEventHandlers _eventHandlers;
+}
+
+- (instancetype)initWithTag:(ReactTag)tag
+              eventHandlers:(SharedEventHandlers)eventHandlers
+{
+  if (self = [super init]) {
+    _tag = tag;
+    _eventHandlers = eventHandlers;
+  }
+
+  return self;
+}
+
+- (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
+{
+  UIView<RCTComponentViewProtocol> *componentView = [registry componentViewByTag:_tag];
+
+  [componentView updateEventHandlers:_eventHandlers];
+}
+
+@end
diff --git a/React/Fabric/Mounting/RCTComponentViewProtocol.h b/React/Fabric/Mounting/RCTComponentViewProtocol.h
index fc56aa7e08e9..47048efa1b57 100644
--- a/React/Fabric/Mounting/RCTComponentViewProtocol.h
+++ b/React/Fabric/Mounting/RCTComponentViewProtocol.h
@@ -7,6 +7,7 @@
 
 #import <UIKit/UIKit.h>
 
+#import <fabric/core/EventHandlers.h>
 #import <fabric/core/LocalData.h>
 #import <fabric/core/Props.h>
 #import <fabric/core/LayoutMetrics.h>
@@ -52,6 +53,12 @@ NS_ASSUME_NONNULL_BEGIN
 - (void)updateLocalData:(facebook::react::SharedLocalData)localData
            oldLocalData:(facebook::react::SharedLocalData)oldLocalData;
 
+/*
+ * Called for updating component's event handlers set.
+ * Receiver must cache `eventHandlers` object inside and use it for emitting
+ * events when needed.
+ */
+- (void)updateEventHandlers:(facebook::react::SharedEventHandlers)eventHandlers;
 
 /*
  * Called for updating component's layout metrics.
diff --git a/React/Fabric/Mounting/RCTMountingManager.mm b/React/Fabric/Mounting/RCTMountingManager.mm
index 5b7e7f1311d5..93e8f0ea809a 100644
--- a/React/Fabric/Mounting/RCTMountingManager.mm
+++ b/React/Fabric/Mounting/RCTMountingManager.mm
@@ -20,6 +20,7 @@
 #import "RCTInsertMountItem.h"
 #import "RCTRemoveMountItem.h"
 #import "RCTUpdatePropsMountItem.h"
+#import "RCTUpdateEventHandlersMountItem.h"
 #import "RCTUpdateLocalDataMountItem.h"
 #import "RCTUpdateLayoutMetricsMountItem.h"
 
@@ -53,6 +54,7 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
         [mountItems addObject:mountItem];
         break;
       }
+
       case TreeMutationInstruction::Deletion: {
         NSString *componentName = [NSString stringWithCString:instruction.getOldChildNode()->getComponentName().c_str()
                                                      encoding:NSASCIIStringEncoding];
@@ -64,17 +66,15 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
       }
 
       case TreeMutationInstruction::Insertion: {
-        RCTInsertMountItem *mountItem =
-          [[RCTInsertMountItem alloc] initWithChildTag:instruction.getNewChildNode()->getTag()
-                                             parentTag:instruction.getParentNode()->getTag()
-                                                 index:instruction.getIndex()];
-        [mountItems addObject:mountItem];
-
         // Props
         [mountItems addObject:[[RCTUpdatePropsMountItem alloc] initWithTag:instruction.getNewChildNode()->getTag()
                                                                   oldProps:nullptr
                                                                   newProps:instruction.getNewChildNode()->getProps()]];
 
+        // EventHandlers
+        [mountItems addObject:[[RCTUpdateEventHandlersMountItem alloc] initWithTag:instruction.getNewChildNode()->getTag()
+                                                                     eventHandlers:instruction.getNewChildNode()->getEventHandlers()]];
+
         // LocalData
         if (instruction.getNewChildNode()->getLocalData()) {
           [mountItems addObject:[[RCTUpdateLocalDataMountItem alloc] initWithTag:instruction.getNewChildNode()->getTag()
@@ -91,6 +91,14 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
                                                                     oldLayoutMetrics:{}
                                                                     newLayoutMetrics:layoutableNewShadowNode->getLayoutMetrics()]];
         }
+
+        // Insertion
+        RCTInsertMountItem *mountItem =
+        [[RCTInsertMountItem alloc] initWithChildTag:instruction.getNewChildNode()->getTag()
+                                           parentTag:instruction.getParentNode()->getTag()
+                                               index:instruction.getIndex()];
+        [mountItems addObject:mountItem];
+
         break;
       }
 
@@ -116,6 +124,14 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
           [mountItems addObject:mountItem];
         }
 
+        // EventHandlers
+        if (oldShadowNode->getEventHandlers() != newShadowNode->getEventHandlers()) {
+          RCTUpdateEventHandlersMountItem *mountItem =
+            [[RCTUpdateEventHandlersMountItem alloc] initWithTag:instruction.getOldChildNode()->getTag()
+                                                   eventHandlers:instruction.getOldChildNode()->getEventHandlers()];
+          [mountItems addObject:mountItem];
+        }
+
         // LocalData
         if (oldShadowNode->getLocalData() != newShadowNode->getLocalData()) {
           RCTUpdateLocalDataMountItem *mountItem =
diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.h b/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
index cffe51a2f851..75524cef771f 100644
--- a/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
@@ -9,6 +9,7 @@
 
 #import <React/RCTComponentViewProtocol.h>
 
+
 NS_ASSUME_NONNULL_BEGIN
 
 /**
@@ -25,6 +26,8 @@ NS_ASSUME_NONNULL_BEGIN
 - (void)updateProps:(facebook::react::SharedProps)props
            oldProps:(facebook::react::SharedProps)oldProps;
 
+- (void)updateEventHandlers:(facebook::react::SharedEventHandlers)eventHandlers;
+
 - (void)updateLocalData:(facebook::react::SharedLocalData)localData
            oldLocalData:(facebook::react::SharedLocalData)oldLocalData;
 
diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
index 5627a699d252..223bb7c9b92e 100644
--- a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
@@ -31,6 +31,11 @@ - (void)updateProps:(facebook::react::SharedProps)props
   // Default implementation does nothing.
 }
 
+- (void)updateEventHandlers:(facebook::react::SharedEventHandlers)eventHandlers
+{
+  // Default implementation does nothing.
+}
+
 - (void)updateLocalData:(facebook::react::SharedLocalData)localData
            oldLocalData:(facebook::react::SharedLocalData)oldLocalData
 {

From 20645681d126e4d36c22a1782849f745e915f43e Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 22 May 2018 15:48:24 -0700
Subject: [PATCH 0646/1109] Fabric: Support of accessibility events for <View>
 component

Summary: This also illustrates how we should use EventHandlers objects.

Reviewed By: fkgozali

Differential Revision: D8053357

fbshipit-source-id: cba084c8a871e40c7536720fce290c3467d33061
---
 .../View/RCTViewComponentView.h               |  3 ++
 .../View/RCTViewComponentView.mm              | 32 ++++++++++++++++--
 .../paragraph/ParagraphComponentDescriptor.h  |  8 +++--
 .../fabric/view/ConcreteViewShadowNode.h      | 17 ++++++----
 ReactCommon/fabric/view/ViewEventHandlers.cpp | 28 ++++++++++++++++
 ReactCommon/fabric/view/ViewEventHandlers.h   | 33 +++++++++++++++++++
 ReactCommon/fabric/view/ViewShadowNode.h      |  2 +-
 .../view/accessibility/AccessibilityProps.h   |  3 --
 8 files changed, 111 insertions(+), 15 deletions(-)
 create mode 100644 ReactCommon/fabric/view/ViewEventHandlers.cpp
 create mode 100644 ReactCommon/fabric/view/ViewEventHandlers.h

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index 8ae84d138f50..f0d482347e86 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -9,8 +9,10 @@
 
 #import <React/RCTComponentViewProtocol.h>
 #import <React/UIView+ComponentViewProtocol.h>
+#import <fabric/core/EventHandlers.h>
 #import <fabric/core/LayoutMetrics.h>
 #import <fabric/core/Props.h>
+#import <fabric/view/ViewEventHandlers.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
@@ -21,6 +23,7 @@ NS_ASSUME_NONNULL_BEGIN
 @protected
   facebook::react::LayoutMetrics _layoutMetrics;
   facebook::react::SharedProps _props;
+  facebook::react::SharedViewEventHandlers _eventHandlers;
 }
 
 @end
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index 9183968b5b01..189850df9095 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -8,13 +8,15 @@
 #import "RCTViewComponentView.h"
 
 #import <fabric/view/ViewProps.h>
+#import <fabric/view/ViewEventHandlers.h>
+
 
 using namespace facebook::react;
 
 @implementation RCTViewComponentView
 
-- (void)updateProps:(facebook::react::SharedProps)props
-           oldProps:(facebook::react::SharedProps)oldProps
+- (void)updateProps:(SharedProps)props
+           oldProps:(SharedProps)oldProps
 {
   if (!oldProps) {
     oldProps = _props ?: std::make_shared<ViewProps>();
@@ -31,6 +33,12 @@ - (void)updateProps:(facebook::react::SharedProps)props
   // TODO: Implement all sutable non-layout <View> props.
 }
 
+- (void)updateEventHandlers:(SharedEventHandlers)eventHandlers
+{
+  assert(std::dynamic_pointer_cast<const ViewEventHandlers>(eventHandlers));
+  _eventHandlers = std::static_pointer_cast<const ViewEventHandlers>(eventHandlers);
+}
+
 - (void)updateLayoutMetrics:(LayoutMetrics)layoutMetrics
            oldLayoutMetrics:(LayoutMetrics)oldLayoutMetrics
 {
@@ -39,4 +47,24 @@ - (void)updateLayoutMetrics:(LayoutMetrics)layoutMetrics
   _layoutMetrics = layoutMetrics;
 }
 
+#pragma mark - Accessibility Events
+
+- (BOOL)accessibilityActivate
+{
+  _eventHandlers->onAccessibilityTap();
+  return YES;
+}
+
+- (BOOL)accessibilityPerformMagicTap
+{
+  _eventHandlers->onAccessibilityMagicTap();
+  return YES;
+}
+
+- (BOOL)didActivateAccessibilityCustomAction:(UIAccessibilityCustomAction *)action
+{
+  _eventHandlers->onAccessibilityAction([action.name cStringUsingEncoding:NSASCIIStringEncoding]);
+  return YES;
+}
+
 @end
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h b/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
index 6648ddb5e142..71e6b8adaa92 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
+++ b/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
@@ -17,11 +17,13 @@ namespace react {
 /*
  * Descriptor for <Paragraph> component.
  */
-class ParagraphComponentDescriptor: public ConcreteComponentDescriptor<ParagraphShadowNode> {
+class ParagraphComponentDescriptor final:
+  public ConcreteComponentDescriptor<ParagraphShadowNode> {
+
 public:
 
-  ParagraphComponentDescriptor():
-    ConcreteComponentDescriptor<ParagraphShadowNode>() {
+  ParagraphComponentDescriptor(SharedEventDispatcher eventDispatcher):
+    ConcreteComponentDescriptor<ParagraphShadowNode>(eventDispatcher) {
     // Every single `ParagraphShadowNode` will have a reference to
     // a shared `TextLayoutManager`.
     textLayoutManager_ = std::make_shared<TextLayoutManager>();
diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
index 83149be3301a..df1707ea5d7c 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -12,6 +12,7 @@
 #include <fabric/core/ShadowNode.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
 #include <fabric/view/AccessibleShadowNode.h>
+#include <fabric/view/ViewEventHandlers.h>
 #include <fabric/view/ViewProps.h>
 #include <fabric/view/YogaLayoutableShadowNode.h>
 
@@ -23,9 +24,9 @@ namespace react {
  * as <View> and similar basic behaviour).
  * For example: <Paragraph>, <Image>, but not <Text>, <RawText>.
  */
-template <typename ViewPropsT>
+template <typename ViewPropsT = ViewProps, typename ViewEventHandlersT = ViewEventHandlers>
 class ConcreteViewShadowNode:
-  public ConcreteShadowNode<ViewPropsT>,
+  public ConcreteShadowNode<ViewPropsT, ViewEventHandlersT>,
   public AccessibleShadowNode,
   public YogaLayoutableShadowNode {
 
@@ -37,21 +38,23 @@ class ConcreteViewShadowNode:
 
   using ConcreteViewProps = ViewPropsT;
   using SharedConcreteViewProps = std::shared_ptr<const ViewPropsT>;
+  using ConcreteViewEventHandlers = ViewEventHandlersT;
+  using SharedConcreteViewEventHandlers = std::shared_ptr<const ViewEventHandlersT>;
   using SharedConcreteViewShadowNode = std::shared_ptr<const ConcreteViewShadowNode>;
 
   ConcreteViewShadowNode(
     const Tag &tag,
     const Tag &rootTag,
-    const InstanceHandle &instanceHandle,
     const SharedConcreteViewProps &props,
+    const SharedConcreteViewEventHandlers &eventHandlers,
     const SharedShadowNodeSharedList &children,
     const ShadowNodeCloneFunction &cloneFunction
   ):
-    ConcreteShadowNode<ViewPropsT>(
+    ConcreteShadowNode<ViewPropsT, ViewEventHandlersT>(
       tag,
       rootTag,
-      instanceHandle,
       props,
+      eventHandlers,
       children,
       cloneFunction
     ),
@@ -66,11 +69,13 @@ class ConcreteViewShadowNode:
   ConcreteViewShadowNode(
     const SharedConcreteViewShadowNode &shadowNode,
     const SharedConcreteViewProps &props,
+    const SharedConcreteViewEventHandlers &eventHandlers,
     const SharedShadowNodeSharedList &children
   ):
-    ConcreteShadowNode<ViewPropsT>(
+    ConcreteShadowNode<ViewPropsT, ViewEventHandlersT>(
       shadowNode,
       props,
+      eventHandlers,
       children
     ),
     AccessibleShadowNode(
diff --git a/ReactCommon/fabric/view/ViewEventHandlers.cpp b/ReactCommon/fabric/view/ViewEventHandlers.cpp
new file mode 100644
index 000000000000..261f38c3ab18
--- /dev/null
+++ b/ReactCommon/fabric/view/ViewEventHandlers.cpp
@@ -0,0 +1,28 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ViewEventHandlers.h"
+
+namespace facebook {
+namespace react {
+
+#pragma mark - Accessibility
+
+void ViewEventHandlers::onAccessibilityAction(const std::string &name) const {
+  dispatchEvent("accessibilityAction", folly::dynamic::object("action", name));
+}
+
+void ViewEventHandlers::onAccessibilityTap() const {
+  dispatchEvent("accessibilityTap");
+}
+
+void ViewEventHandlers::onAccessibilityMagicTap() const {
+  dispatchEvent("magicTap");
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewEventHandlers.h b/ReactCommon/fabric/view/ViewEventHandlers.h
new file mode 100644
index 000000000000..3e8236b4b15c
--- /dev/null
+++ b/ReactCommon/fabric/view/ViewEventHandlers.h
@@ -0,0 +1,33 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+#pragma once
+
+#include <memory>
+
+#include <fabric/core/EventHandlers.h>
+
+namespace facebook {
+namespace react {
+
+class ViewEventHandlers;
+
+using SharedViewEventHandlers = std::shared_ptr<const ViewEventHandlers>;
+
+class ViewEventHandlers:
+  public EventHandlers {
+
+public:
+
+  using EventHandlers::EventHandlers;
+
+  void onAccessibilityAction(const std::string &name) const;
+  void onAccessibilityTap() const;
+  void onAccessibilityMagicTap() const;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/view/ViewShadowNode.h
index d063b0196fc3..4ad05c83f921 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.h
+++ b/ReactCommon/fabric/view/ViewShadowNode.h
@@ -20,7 +20,7 @@ class ViewShadowNode;
 using SharedViewShadowNode = std::shared_ptr<const ViewShadowNode>;
 
 class ViewShadowNode final:
-  public ConcreteViewShadowNode<ViewProps> {
+  public ConcreteViewShadowNode<ViewProps, ViewEventHandlers> {
 
 public:
 
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h b/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
index f807c5b556bd..c19881dfb871 100644
--- a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
+++ b/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
@@ -35,9 +35,6 @@ class AccessibilityProps:
   const AccessibilityTraits accessibilityTraits {AccessibilityTraits::None};
   const bool accessibilityViewIsModal {false};
   const bool accessibilityElementsHidden {false};
-  const SharedDirectEventHandler onAccessibilityAction {nullptr};
-  const SharedDirectEventHandler onAccessibilityTap {nullptr};
-  const SharedDirectEventHandler onMagicTap {nullptr};
 };
 
 } // namespace react

From 21189be7cb9d41c07b2839d10f77e98a7d429098 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 22 May 2018 15:48:27 -0700
Subject: [PATCH 0647/1109] Fabric: ScrollView events

Summary: Note: Some features are not suported yet, e.g. event throttling.

Reviewed By: fkgozali

Differential Revision: D8082771

fbshipit-source-id: d60f6e9011283aeee7aff77dc9178e99f06deb5c
---
 .../ScrollView/RCTScrollViewComponentView.mm  | 63 +++++++++++++++++-
 React/Fabric/RCTConversions.h                 |  8 +++
 .../scrollview/ScrollViewEventHandlers.cpp    | 64 +++++++++++++++++++
 .../scrollview/ScrollViewEventHandlers.h      | 52 +++++++++++++++
 .../scrollview/ScrollViewShadowNode.cpp       |  2 +-
 .../fabric/scrollview/ScrollViewShadowNode.h  |  3 +-
 6 files changed, 188 insertions(+), 4 deletions(-)
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewEventHandlers.cpp
 create mode 100644 ReactCommon/fabric/scrollview/ScrollViewEventHandlers.h

diff --git a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
index 93ee34af86bb..e3b157a57dc8 100644
--- a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
@@ -11,6 +11,7 @@
 #import <fabric/graphics/Geometry.h>
 #import <fabric/scrollview/ScrollViewLocalData.h>
 #import <fabric/scrollview/ScrollViewProps.h>
+#import <fabric/scrollview/ScrollViewEventHandlers.h>
 
 #import "RCTConversions.h"
 #import "RCTEnhancedScrollView.h"
@@ -44,6 +45,8 @@ - (instancetype)initWithFrame:(CGRect)frame
   return self;
 }
 
+#pragma mark - ComponentViewProtocol
+
 - (void)updateProps:(SharedProps)props oldProps:(SharedProps)oldProps
 {
   [super updateProps:props oldProps:oldProps];
@@ -104,8 +107,6 @@ - (void)updateLocalData:(SharedLocalData)localData
   _scrollView.contentSize = contentSize;
 }
 
-#pragma mark - ComponentViewProtocol
-
 - (void)mountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
                           index:(NSInteger)index
 {
@@ -119,4 +120,62 @@ - (void)unmountChildComponentView:(UIView<RCTComponentViewProtocol> *)childCompo
   [childComponentView removeFromSuperview];
 }
 
+- (ScrollViewMetrics)_scrollViewMetrics
+{
+  ScrollViewMetrics metrics;
+  metrics.contentSize = RCTSizeFromCGSize(_scrollView.contentSize);
+  metrics.contentOffset = RCTPointFromCGPoint(_scrollView.contentOffset);
+  metrics.contentInset = RCTEdgeInsetsFromUIEdgeInsets(_scrollView.contentInset);
+  metrics.containerSize = RCTSizeFromCGSize(_scrollView.bounds.size);
+  metrics.zoomScale = _scrollView.zoomScale;
+  return metrics;
+}
+
+#pragma mark - UIScrollViewDelegate
+
+- (void)scrollViewDidScroll:(UIScrollView *)scrollView
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScroll([self _scrollViewMetrics]);
+}
+
+- (void)scrollViewDidZoom:(UIScrollView *)scrollView
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScroll([self _scrollViewMetrics]);
+}
+
+- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScrollBeginDrag([self _scrollViewMetrics]);
+}
+
+- (void)scrollViewWillEndDragging:(UIScrollView *)scrollView withVelocity:(CGPoint)velocity targetContentOffset:(inout CGPoint *)targetContentOffset
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScrollEndDrag([self _scrollViewMetrics]);
+}
+
+- (void)scrollViewWillBeginDecelerating:(UIScrollView *)scrollView
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onMomentumScrollBegin([self _scrollViewMetrics]);
+}
+
+- (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onMomentumScrollEnd([self _scrollViewMetrics]);
+}
+
+- (void)scrollViewDidEndScrollingAnimation:(UIScrollView *)scrollView
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onMomentumScrollEnd([self _scrollViewMetrics]);
+}
+
+- (void)scrollViewWillBeginZooming:(UIScrollView *)scrollView withView:(nullable UIView *)view
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScrollBeginDrag([self _scrollViewMetrics]);
+}
+
+- (void)scrollViewDidEndZooming:(UIScrollView *)scrollView withView:(nullable UIView *)view atScale:(CGFloat)scale
+{
+  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScrollEndDrag([self _scrollViewMetrics]);
+}
+
 @end
diff --git a/React/Fabric/RCTConversions.h b/React/Fabric/RCTConversions.h
index 9e4184651da4..ba2b9cb1ffab 100644
--- a/React/Fabric/RCTConversions.h
+++ b/React/Fabric/RCTConversions.h
@@ -21,6 +21,10 @@ inline CGRect RCTCGRectFromRect(facebook::react::Rect rect) {
   return {RCTCGPointFromPoint(rect.origin), RCTCGSizeFromSize(rect.size)};
 }
 
+inline UIEdgeInsets RCTUIEdgeInsetsFromEdgeInsets(facebook::react::EdgeInsets edgeInsets) {
+  return {edgeInsets.top, edgeInsets.left, edgeInsets.bottom, edgeInsets.right};
+}
+
 inline facebook::react::Point RCTPointFromCGPoint(CGPoint point) {
   return {point.x, point.y};
 }
@@ -32,3 +36,7 @@ inline facebook::react::Size RCTSizeFromCGSize(CGSize size) {
 inline facebook::react::Rect RCTRectFromCGRect(CGRect rect) {
   return {RCTPointFromCGPoint(rect.origin), RCTSizeFromCGSize(rect.size)};
 }
+
+inline facebook::react::EdgeInsets RCTEdgeInsetsFromUIEdgeInsets(UIEdgeInsets edgeInsets) {
+  return {edgeInsets.top, edgeInsets.left, edgeInsets.bottom, edgeInsets.right};
+}
diff --git a/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.cpp b/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.cpp
new file mode 100644
index 000000000000..c331f6b03c87
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.cpp
@@ -0,0 +1,64 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ScrollViewEventHandlers.h"
+
+namespace facebook {
+namespace react {
+
+void ScrollViewEventHandlers::onScroll(const ScrollViewMetrics &scrollViewMetrics) const {
+  dispatchScrollViewEvent("scroll", scrollViewMetrics);
+}
+
+void ScrollViewEventHandlers::onScrollBeginDrag(const ScrollViewMetrics &scrollViewMetrics) const {
+  dispatchScrollViewEvent("scrollBeginDrag", scrollViewMetrics);
+}
+
+void ScrollViewEventHandlers::onScrollEndDrag(const ScrollViewMetrics &scrollViewMetrics) const {
+  dispatchScrollViewEvent("scrollEndDrag", scrollViewMetrics);
+}
+
+void ScrollViewEventHandlers::onMomentumScrollBegin(const ScrollViewMetrics &scrollViewMetrics) const {
+  dispatchScrollViewEvent("momentumScrollBegin", scrollViewMetrics);
+}
+
+void ScrollViewEventHandlers::onMomentumScrollEnd(const ScrollViewMetrics &scrollViewMetrics) const {
+  dispatchScrollViewEvent("momentumScrollEnd", scrollViewMetrics);
+}
+
+void ScrollViewEventHandlers::dispatchScrollViewEvent(const std::string &name, const ScrollViewMetrics &scrollViewMetrics, const folly::dynamic &payload) const {
+  folly::dynamic compoundPayload = folly::dynamic::object();
+
+  compoundPayload["contentOffset"] = folly::dynamic::object
+    ("x", scrollViewMetrics.contentOffset.x)
+    ("y", scrollViewMetrics.contentOffset.y);
+
+  compoundPayload["contentInset"] = folly::dynamic::object
+    ("top", scrollViewMetrics.contentInset.top)
+    ("left", scrollViewMetrics.contentInset.left)
+    ("bottom", scrollViewMetrics.contentInset.bottom)
+    ("right", scrollViewMetrics.contentInset.right);
+
+  compoundPayload["contentSize"] = folly::dynamic::object
+    ("width", scrollViewMetrics.contentSize.width)
+    ("height", scrollViewMetrics.contentSize.height);
+
+  compoundPayload["layoutMeasurement"] = folly::dynamic::object
+    ("width", scrollViewMetrics.containerSize.width)
+    ("height", scrollViewMetrics.containerSize.height);
+
+  compoundPayload["zoomScale"] = scrollViewMetrics.zoomScale;
+
+  if (!payload.isNull()) {
+    compoundPayload.merge_patch(payload);
+  }
+
+  dispatchEvent(name, compoundPayload);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.h b/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.h
new file mode 100644
index 000000000000..8f6a93e7221a
--- /dev/null
+++ b/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.h
@@ -0,0 +1,52 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+#pragma once
+
+#include <memory>
+
+#include <fabric/graphics/Geometry.h>
+#include <fabric/core/EventHandlers.h>
+#include <fabric/view/ViewEventHandlers.h>
+
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+class ScrollViewMetrics {
+public:
+  Size contentSize;
+  Point contentOffset;
+  EdgeInsets contentInset;
+  Size containerSize;
+  Float zoomScale;
+};
+
+class ScrollViewEventHandlers;
+
+using SharedScrollViewEventHandlers = std::shared_ptr<const ScrollViewEventHandlers>;
+
+class ScrollViewEventHandlers:
+  public ViewEventHandlers {
+
+public:
+
+  using ViewEventHandlers::ViewEventHandlers;
+
+  void onScroll(const ScrollViewMetrics &scrollViewMetrics) const;
+  void onScrollBeginDrag(const ScrollViewMetrics &scrollViewMetrics) const;
+  void onScrollEndDrag(const ScrollViewMetrics &scrollViewMetrics) const;
+  void onMomentumScrollBegin(const ScrollViewMetrics &scrollViewMetrics) const;
+  void onMomentumScrollEnd(const ScrollViewMetrics &scrollViewMetrics) const;
+
+private:
+
+  void dispatchScrollViewEvent(const std::string &name, const ScrollViewMetrics &scrollViewMetrics, const folly::dynamic &payload = {}) const;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
index 96c60b2e3f74..2d3efaa8945b 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
+++ b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
@@ -33,7 +33,7 @@ void ScrollViewShadowNode::updateLocalData() {
 #pragma mark - LayoutableShadowNode
 
 void ScrollViewShadowNode::layout(LayoutContext layoutContext) {
-  ConcreteViewShadowNode<ScrollViewProps>::layout(layoutContext);
+  ConcreteViewShadowNode::layout(layoutContext);
   updateLocalData();
 }
 
diff --git a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
index e53e93e29ea9..5a74f0c320df 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
+++ b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
@@ -10,6 +10,7 @@
 #include <memory>
 
 #include <fabric/core/LayoutContext.h>
+#include <fabric/scrollview/ScrollViewEventHandlers.h>
 #include <fabric/scrollview/ScrollViewProps.h>
 #include <fabric/view/ConcreteViewShadowNode.h>
 
@@ -24,7 +25,7 @@ using SharedScrollViewShadowNode = std::shared_ptr<const ScrollViewShadowNode>;
  * `ShadowNode` for <ScrollView> component.
  */
 class ScrollViewShadowNode final:
-  public ConcreteViewShadowNode<ScrollViewProps> {
+  public ConcreteViewShadowNode<ScrollViewProps, ScrollViewEventHandlers> {
 
 public:
 

From 092103e7525e58e04346e0a1a16a67ca4f31c2e9 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 22 May 2018 23:23:05 -0700
Subject: [PATCH 0648/1109] iOS OSS: update podspec's to target iOS 9.0

Summary: A few more places to update to target iOS 9.0 (upgraded from 8.0)

Reviewed By: shergin

Differential Revision: D8108719

fbshipit-source-id: f17aa5e5aa34fdad57196202bf67a842735d4cdc
---
 RNTester/Podfile.lock                         | 10 +++++-----
 React.podspec                                 |  2 +-
 ReactCommon/yoga/yoga.podspec                 |  4 ++--
 third-party-podspecs/DoubleConversion.podspec |  2 +-
 third-party-podspecs/Folly.podspec            |  2 +-
 third-party-podspecs/glog.podspec             |  2 +-
 6 files changed, 11 insertions(+), 11 deletions(-)

diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index 837208c89f3a..cf961ebad09b 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -138,11 +138,11 @@ EXTERNAL SOURCES:
 
 SPEC CHECKSUMS:
   boost-for-react-native: 39c7adb57c4e60d6c5479dd8623128eb5b3f0f2c
-  DoubleConversion: e22e0762848812a87afd67ffda3998d9ef29170c
-  Folly: 9a8eea4725a0b6ba3256ebf206c21e352c23abf8
-  glog: 1de0bb937dccdc981596d3b5825ebfb765017ded
-  React: 0a0271674c3a6772a89a6606f337ed8db583abc0
-  yoga: bdd268c5812f00bdb52cc2b58f129797e97935eb
+  DoubleConversion: a9706f16e388b53ff12cca34473428ee29746a26
+  Folly: c89ac2d5c6ab169cd7397ef27485c44f35f742c7
+  glog: 3931855c9cc99c3fab1355fc162fe369162d8183
+  React: 81df86644d0bca489723c964b33b005901ebfb3b
+  yoga: b1ce48b6cf950b98deae82838f5173ea7cf89e85
 
 PODFILE CHECKSUM: 30aa63dcdbb3546a2bacdfd4e005bcca50c9b55c
 
diff --git a/React.podspec b/React.podspec
index 470533c2c10c..8a67040ecdfb 100644
--- a/React.podspec
+++ b/React.podspec
@@ -38,7 +38,7 @@ Pod::Spec.new do |s|
   s.source                  = source
   s.default_subspec         = "Core"
   s.requires_arc            = true
-  s.platforms               = { :ios => "8.0", :tvos => "9.2" }
+  s.platforms               = { :ios => "9.0", :tvos => "9.2" }
   s.pod_target_xcconfig     = { "CLANG_CXX_LANGUAGE_STANDARD" => "c++14" }
   s.preserve_paths          = "package.json", "LICENSE", "LICENSE-docs"
   s.cocoapods_version       = ">= 1.2.0"
diff --git a/ReactCommon/yoga/yoga.podspec b/ReactCommon/yoga/yoga.podspec
index 69144f9bb01b..6d5dc0357d9d 100644
--- a/ReactCommon/yoga/yoga.podspec
+++ b/ReactCommon/yoga/yoga.podspec
@@ -34,14 +34,14 @@ Pod::Spec.new do |spec|
   ]
 
   # Pinning to the same version as React.podspec.
-  spec.platforms = { :ios => "8.0", :tvos => "9.2" }
+  spec.platforms = { :ios => "9.0", :tvos => "9.2" }
 
   # Set this environment variable when *not* using the `:path` option to install the pod.
   # E.g. when publishing this spec to a spec repo.
   source_files = 'yoga/**/*.{cpp,h}'
   source_files = File.join('ReactCommon/yoga', source_files) if ENV['INSTALL_YOGA_WITHOUT_PATH_OPTION']
   spec.source_files = source_files
-  
+
   header_files = 'yoga/{Yoga,YGEnums,YGMacros}.h'
   header_files = File.join('ReactCommon/yoga', header_files) if ENV['INSTALL_YOGA_WITHOUT_PATH_OPTION']
   spec.public_header_files = header_files
diff --git a/third-party-podspecs/DoubleConversion.podspec b/third-party-podspecs/DoubleConversion.podspec
index 52f7ec1279f9..42965eee743c 100644
--- a/third-party-podspecs/DoubleConversion.podspec
+++ b/third-party-podspecs/DoubleConversion.podspec
@@ -12,6 +12,6 @@ Pod::Spec.new do |spec|
   spec.source_files = 'double-conversion/*.{h,cc}'
 
   # Pinning to the same version as React.podspec.
-  spec.platforms = { :ios => "8.0", :tvos => "9.2" }
+  spec.platforms = { :ios => "9.0", :tvos => "9.2" }
 
 end
diff --git a/third-party-podspecs/Folly.podspec b/third-party-podspecs/Folly.podspec
index c72b88fba93a..6f1ee96dbe77 100644
--- a/third-party-podspecs/Folly.podspec
+++ b/third-party-podspecs/Folly.podspec
@@ -31,5 +31,5 @@ Pod::Spec.new do |spec|
                                "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)\" \"$(PODS_ROOT)/boost-for-react-native\" \"$(PODS_ROOT)/DoubleConversion\"" }
 
   # Pinning to the same version as React.podspec.
-  spec.platforms = { :ios => "8.0", :tvos => "9.2" }
+  spec.platforms = { :ios => "9.0", :tvos => "9.2" }
 end
diff --git a/third-party-podspecs/glog.podspec b/third-party-podspecs/glog.podspec
index 226f9e4cf0fc..03f106b4c645 100644
--- a/third-party-podspecs/glog.podspec
+++ b/third-party-podspecs/glog.podspec
@@ -28,6 +28,6 @@ Pod::Spec.new do |spec|
                                "HEADER_SEARCH_PATHS" => "$(PODS_TARGET_SRCROOT)/src" }
 
   # Pinning to the same version as React.podspec.
-  spec.platforms = { :ios => "8.0", :tvos => "9.2" }
+  spec.platforms = { :ios => "9.0", :tvos => "9.2" }
 
 end

From 7014a30baae0b01378740113d15e4a7d721d916a Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Wed, 23 May 2018 01:32:08 -0700
Subject: [PATCH 0649/1109] Upgrade babel to beta.47 across xplat

Summary:
Upgrade Babel from beta.40 to beta.47

There are two important breaking changes here.

- If you want an AST from the Babel `transform` functions you must pass on `ast:true` in the options.
- The `sourceType` is now the only source of truth on whether to parse with the Script or Module goal. It defaults to `script` and can also be `module` or `unambiguous`. In the `unambiguous` case it will first try to parse with the Module goal and only if it crashes it will try again with the Script goal.

Beyond that there were some fixes and some smaller changes that may affect you. See the Babel changelogs for details (https://github.com/babel/babel/tags).

Also updated the way we generate the babel helpers file.

Reviewed By: rubennorte

Differential Revision: D8075280

fbshipit-source-id: 2bb902690e8a4b19d9cada2b7b0c94812b3d4f0f
---
 Libraries/polyfills/babelHelpers.js | 400 +++++++++++++++++++---------
 babel-preset/package.json           |  54 ++--
 jest/preprocessor.js                |   5 +-
 package.json                        |   2 +-
 4 files changed, 309 insertions(+), 152 deletions(-)

diff --git a/Libraries/polyfills/babelHelpers.js b/Libraries/polyfills/babelHelpers.js
index 9453b150cfb7..991b4fbfbdb2 100644
--- a/Libraries/polyfills/babelHelpers.js
+++ b/Libraries/polyfills/babelHelpers.js
@@ -8,18 +8,29 @@
  *    `js1 upgrade babel-helpers` + manual tweaks
  *
  * Components used for this file;
+ *   - arrayWithHoles
+ *   - arrayWithoutHoles
  *   - assertThisInitialized
  *   - classCallCheck
+ *   - construct
  *   - createClass
  *   - defineProperty
  *   - extends
  *   - get
+ *   - getPrototypeOf
  *   - inherits
  *   - interopRequireDefault
  *   - interopRequireWildcard
+ *   - iterableToArray
+ *   - iterableToArrayLimit
+ *   - nonIterableRest
+ *   - nonIterableSpread
+ *   - objectSpread
  *   - objectWithoutProperties
  *   - possibleConstructorReturn
+ *   - setPrototypeOf
  *   - slicedToArray
+ *   - superPropBase
  *   - taggedTemplateLiteral
  *   - taggedTemplateLiteralLoose
  *   - toArray
@@ -27,7 +38,7 @@
  *   - wrapNativeSuper
  *
  * @flow
- * @generated (with babel 7.0.0-beta.40)
+ * @generated (with babel 7.0.0-beta.47)
  * @format
  * @nolint
  * @polyfill
@@ -116,36 +127,78 @@ function _extends() {
 
 babelHelpers.extends = _extends;
 
-// ### get ###
+// ### setPrototypeOf ###
 
-function _get(object, property, receiver) {
-  if (object === null) {
-    object = Function.prototype;
-  }
-  var desc = Object.getOwnPropertyDescriptor(object, property);
+function _setPrototypeOf(o, p) {
+  babelHelpers.setPrototypeOf = _setPrototypeOf =
+    Object.setPrototypeOf ||
+    function _setPrototypeOf(o, p) {
+      o.__proto__ = p;
+      return o;
+    };
 
-  if (desc === undefined) {
-    var parent = Object.getPrototypeOf(object);
+  return _setPrototypeOf(o, p);
+}
 
-    if (parent === null) {
-      return undefined;
-    } else {
-      return _get(parent, property, receiver);
-    }
-  } else if ('value' in desc) {
-    return desc.value;
-  } else {
-    var getter = desc.get;
+babelHelpers.setPrototypeOf = _setPrototypeOf;
+
+// ### superPropBase ###
 
-    if (getter === undefined) {
-      return undefined;
+function _superPropBase(object, property) {
+  while (!Object.prototype.hasOwnProperty.call(object, property)) {
+    object = babelHelpers.getPrototypeOf(object);
+    if (object === null) {
+      break;
     }
+  }
+
+  return object;
+}
 
-    return getter.call(receiver);
+babelHelpers.superPropBase = _superPropBase;
+
+// ### get ###
+
+// FB:
+// TODO: prepack does not like Reflect (and we can use the fallback just fine)
+// function _get(target, property, receiver) {
+//   if (typeof Reflect !== 'undefined' && Reflect.get) {
+//     babelHelpers.get = _get = Reflect.get;
+//   } else {
+//     babelHelpers.get = _get = function _get(target, property, receiver) {
+//       var base = babelHelpers.superPropBase(target, property);
+//       if (!base) {
+//         return;
+//       }
+//       var desc = Object.getOwnPropertyDescriptor(base, property);
+//
+//       if (desc.get) {
+//         return desc.get.call(receiver);
+//       }
+//
+//       return desc.value;
+//     };
+//   }
+//
+//   return _get(target, property, receiver || target);
+// }
+//
+// babelHelpers.get = _get;
+
+babelHelpers.get = function _get(target, property, receiver = target) {
+  var base = babelHelpers.superPropBase(target, property);
+  if (!base) {
+    return;
+  }
+  var desc = Object.getOwnPropertyDescriptor(base, property);
+
+  if (desc.get) {
+    return desc.get.call(receiver);
   }
+
+  return desc.value;
 }
 
-babelHelpers.get = _get;
 
 // ### inherits ###
 
@@ -154,89 +207,122 @@ function _inherits(subClass, superClass) {
     throw new TypeError('Super expression must either be null or a function');
   }
 
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: false,
-      writable: true,
-      configurable: true,
-    },
-  });
+  babelHelpers.setPrototypeOf(
+    subClass.prototype,
+    superClass && superClass.prototype,
+  );
   if (superClass) {
-    Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass);
+    babelHelpers.setPrototypeOf(subClass, superClass);
   }
 }
 
 babelHelpers.inherits = _inherits;
 
-// ### wrapNativeSuper ###
-
-var _gPO =
-  Object.getPrototypeOf ||
-  function _gPO(o) {
-    return o.__proto__;
-  };
-
-var _sPO =
-  Object.setPrototypeOf ||
-  function _sPO(o, p) {
-    o.__proto__ = p;
-    return o;
-  };
+// ### construct ###
 
-var _construct =
+function _construct(Parent, args, Class) {
   // FB:
   // TODO: prepack does not like this line (and we can use the fallback just fine)
-  // (typeof Reflect === "object" && Reflect.construct) ||
-  function _construct(Parent, args, Class) {
-    var Constructor,
-      a = [null];
+  // if (typeof Reflect !== 'undefined' && Reflect.construct) {
+  //   babelHelpers.construct = _construct = Reflect.construct;
+  // } else {
+  babelHelpers.construct = _construct = function _construct(
+    Parent,
+    args,
+    Class,
+  ) {
+    var a = [null];
     a.push.apply(a, args);
-    Constructor = Parent.bind.apply(Parent, a);
-    return _sPO(new Constructor(), Class.prototype);
+    var Constructor = Parent.bind.apply(Parent, a);
+    var instance = new Constructor();
+    if (Class) {
+      babelHelpers.setPrototypeOf(instance, Class.prototype);
+    }
+    return instance;
   };
+  // }
 
-var _cache = typeof Map === 'function' && new Map();
+  return _construct.apply(null, arguments);
+}
 
-function _wrapNativeSuper(Class) {
-  // FB:
-  // Note: while extending native classes is pretty meh we do have cases, for
-  // example; Error. There is also a false positive, for example; Blob.
-  if (typeof Class !== 'function') {
-    throw new TypeError('Super expression must either be null or a function');
+babelHelpers.construct = _construct;
+
+// ### getPrototypeOf ###
+
+function _getPrototypeOf(o) {
+  babelHelpers.getPrototypeOf = _getPrototypeOf =
+    Object.getPrototypeOf ||
+    function _getPrototypeOf(o) {
+      return o.__proto__;
+    };
+
+  return _getPrototypeOf(o);
+}
+
+babelHelpers.getPrototypeOf = _getPrototypeOf;
+
+// ### assertThisInitialized ###
+
+function _assertThisInitialized(self) {
+  if (self === void 0) {
+    throw new ReferenceError(
+      "this hasn't been initialised - super() hasn't been called",
+    );
   }
 
-  if (typeof _cache !== 'undefined') {
-    if (_cache.has(Class)) {
-      return _cache.get(Class);
+  return self;
+}
+
+babelHelpers.assertThisInitialized = _assertThisInitialized;
+
+// ### wrapNativeSuper ###
+
+function _wrapNativeSuper(Class) {
+  var _cache = typeof Map === 'function' ? new Map() : undefined;
+
+  babelHelpers.wrapNativeSuper = _wrapNativeSuper = function _wrapNativeSuper(
+    Class,
+  ) {
+    if (typeof Class !== 'function') {
+      throw new TypeError('Super expression must either be null or a function');
     }
 
-    _cache.set(Class, Wrapper);
-  }
+    if (typeof _cache !== 'undefined') {
+      if (_cache.has(Class)) {
+        return _cache.get(Class);
+      }
 
-  function Wrapper() {
-    // FB:
-    // this is a temporary fix for a babel bug (it's invoking the wrong func
-    // when you do `super()`)
-    return _construct(Class, arguments, _gPO(this).constructor);
-  }
+      _cache.set(Class, Wrapper);
+    }
 
-  Wrapper.prototype = Object.create(Class.prototype, {
-    constructor: {
-      value: Wrapper,
-      enumerable: false,
-      writeable: true,
-      configurable: true,
-    },
-  });
-  return _sPO(
-    Wrapper,
-    _sPO(function Super() {
-      return _construct(Class, arguments, _gPO(this).constructor);
-    }, Class),
-  );
+    function Wrapper() {
+      // FB:
+      // this is a temporary fix for a babel bug (it's invoking the wrong func
+      // when you do `super()`)
+      return _construct(Class, arguments, _getPrototypeOf(this).constructor);
+    }
+
+    Wrapper.prototype = Object.create(Class.prototype, {
+      constructor: {
+        value: Wrapper,
+        enumerable: false,
+        writable: true,
+        configurable: true,
+      },
+    });
+    return babelHelpers.setPrototypeOf(
+      Wrapper,
+      babelHelpers.setPrototypeOf(function Super() {
+        return babelHelpers.construct(
+          Class,
+          arguments,
+          babelHelpers.getPrototypeOf(this).constructor,
+        );
+      }, Class),
+    );
+  };
+
+  return _wrapNativeSuper(Class);
 }
 
 babelHelpers.wrapNativeSuper = _wrapNativeSuper;
@@ -330,20 +416,38 @@ function _possibleConstructorReturn(self, call) {
     return call;
   }
 
-  if (self === void 0) {
-    throw new ReferenceError(
-      "this hasn't been initialised - super() hasn't been called",
-    );
+  return babelHelpers.assertThisInitialized(self);
+}
+
+babelHelpers.possibleConstructorReturn = _possibleConstructorReturn;
+
+// ### arrayWithHoles ###
+
+function _arrayWithHoles(arr) {
+  if (Array.isArray(arr)) {
+    return arr;
   }
+}
 
-  return self;
+babelHelpers.arrayWithHoles = _arrayWithHoles;
+
+// ### arrayWithoutHoles ###
+
+function _arrayWithoutHoles(arr) {
+  if (Array.isArray(arr)) {
+    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) {
+      arr2[i] = arr[i];
+    }
+
+    return arr2;
+  }
 }
 
-babelHelpers.possibleConstructorReturn = _possibleConstructorReturn;
+babelHelpers.arrayWithoutHoles = _arrayWithoutHoles;
 
-// ### slicedToArray ###
+// ### iterableToArrayLimit ###
 
-function _sliceIterator(arr, i) {
+function _iterableToArrayLimit(arr, i) {
   var _arr = [];
   var _n = true;
   var _d = false;
@@ -379,14 +483,32 @@ function _sliceIterator(arr, i) {
   return _arr;
 }
 
+babelHelpers.iterableToArrayLimit = _iterableToArrayLimit;
+
+// ### nonIterableRest ###
+
+function _nonIterableRest() {
+  throw new TypeError('Invalid attempt to destructure non-iterable instance');
+}
+
+babelHelpers.nonIterableRest = _nonIterableRest;
+
+// ### nonIterableSpread ###
+
+function _nonIterableSpread() {
+  throw new TypeError('Invalid attempt to spread non-iterable instance');
+}
+
+babelHelpers.nonIterableSpread = _nonIterableSpread;
+
+// ### slicedToArray ###
+
 function _slicedToArray(arr, i) {
-  if (Array.isArray(arr)) {
-    return arr;
-  } else if (Symbol.iterator in Object(arr)) {
-    return _sliceIterator(arr, i);
-  } else {
-    throw new TypeError('Invalid attempt to destructure non-iterable instance');
-  }
+  return (
+    babelHelpers.arrayWithHoles(arr) ||
+    babelHelpers.iterableToArrayLimit(arr, i) ||
+    babelHelpers.nonIterableRest()
+  );
 }
 
 babelHelpers.slicedToArray = _slicedToArray;
@@ -394,6 +516,10 @@ babelHelpers.slicedToArray = _slicedToArray;
 // ### taggedTemplateLiteral ###
 
 function _taggedTemplateLiteral(strings, raw) {
+  if (!raw) {
+    raw = strings.slice(0);
+  }
+
   return Object.freeze(
     Object.defineProperties(strings, {
       raw: {
@@ -408,7 +534,11 @@ babelHelpers.taggedTemplateLiteral = _taggedTemplateLiteral;
 // ### toArray ###
 
 function _toArray(arr) {
-  return Array.isArray(arr) ? arr : Array.from(arr);
+  return (
+    babelHelpers.arrayWithHoles(arr) ||
+    babelHelpers.iterableToArray(arr) ||
+    babelHelpers.nonIterableRest()
+  );
 }
 
 babelHelpers.toArray = _toArray;
@@ -416,38 +546,62 @@ babelHelpers.toArray = _toArray;
 // ### toConsumableArray ###
 
 function _toConsumableArray(arr) {
-  if (Array.isArray(arr)) {
-    for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) {
-      arr2[i] = arr[i];
-    }
+  return (
+    babelHelpers.arrayWithoutHoles(arr) ||
+    babelHelpers.iterableToArray(arr) ||
+    babelHelpers.nonIterableSpread()
+  );
+}
 
-    return arr2;
-  } else {
-    return Array.from(arr);
+babelHelpers.toConsumableArray = _toConsumableArray;
+
+// ### taggedTemplateLiteralLoose ###
+
+function _taggedTemplateLiteralLoose(strings, raw) {
+  if (!raw) {
+    raw = strings.slice(0);
   }
+
+  strings.raw = raw;
+  return strings;
 }
 
-babelHelpers.toConsumableArray = _toConsumableArray;
+babelHelpers.taggedTemplateLiteralLoose = _taggedTemplateLiteralLoose;
 
-// ### assertThisInitialized ###
+// ### objectSpread ###
 
-function _assertThisInitialized(self) {
-  if (self === void 0) {
-    throw new ReferenceError(
-      "this hasn't been initialised - super() hasn't been called",
-    );
+function _objectSpread(target) {
+  for (var i = 1; i < arguments.length; i++) {
+    var source = arguments[i] != null ? arguments[i] : {};
+    var ownKeys = Object.keys(source);
+
+    if (typeof Object.getOwnPropertySymbols === 'function') {
+      ownKeys = ownKeys.concat(
+        Object.getOwnPropertySymbols(source).filter(function(sym) {
+          return Object.getOwnPropertyDescriptor(source, sym).enumerable;
+        }),
+      );
+    }
+
+    ownKeys.forEach(function(key) {
+      babelHelpers.defineProperty(target, key, source[key]);
+    });
   }
 
-  return self;
+  return target;
 }
 
-babelHelpers.assertThisInitialized = _assertThisInitialized;
+babelHelpers.objectSpread = _objectSpread;
 
-// ### taggedTemplateLiteralLoose ###
+// ### iterableToArray ###
 
-function _taggedTemplateLiteralLoose(strings, raw) {
-  strings.raw = raw;
-  return strings;
+function _iterableToArray(iter) {
+  if (
+    Symbol.iterator in Object(iter) ||
+    Object.prototype.toString.call(iter) === '[object Arguments]'
+  ) {
+    return Array.from(iter);
+  }
 }
 
-babelHelpers.taggedTemplateLiteralLoose = _taggedTemplateLiteralLoose;
+babelHelpers.iterableToArray = _iterableToArray;
diff --git a/babel-preset/package.json b/babel-preset/package.json
index e9169a8bfe8e..166e804fd085 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -15,32 +15,32 @@
   },
   "homepage": "https://github.com/facebook/react-native/tree/master/babel-preset/README.md",
   "dependencies": {
-    "@babel/plugin-proposal-class-properties": "7.0.0-beta.40",
-    "@babel/plugin-proposal-object-rest-spread": "7.0.0-beta.40",
-    "@babel/plugin-proposal-optional-chaining": "7.0.0-beta.40",
-    "@babel/plugin-transform-arrow-functions": "7.0.0-beta.40",
-    "@babel/plugin-transform-block-scoping": "7.0.0-beta.40",
-    "@babel/plugin-transform-classes": "7.0.0-beta.40",
-    "@babel/plugin-transform-computed-properties": "7.0.0-beta.40",
-    "@babel/plugin-transform-destructuring": "7.0.0-beta.40",
-    "@babel/plugin-transform-exponentiation-operator": "7.0.0-beta.40",
-    "@babel/plugin-transform-flow-strip-types": "7.0.0-beta.40",
-    "@babel/plugin-transform-for-of": "7.0.0-beta.40",
-    "@babel/plugin-transform-function-name": "7.0.0-beta.40",
-    "@babel/plugin-transform-literals": "7.0.0-beta.40",
-    "@babel/plugin-transform-modules-commonjs": "7.0.0-beta.40",
-    "@babel/plugin-transform-object-assign": "7.0.0-beta.40",
-    "@babel/plugin-transform-parameters": "7.0.0-beta.40",
-    "@babel/plugin-transform-react-display-name": "7.0.0-beta.40",
-    "@babel/plugin-transform-react-jsx": "7.0.0-beta.40",
-    "@babel/plugin-transform-react-jsx-source": "7.0.0-beta.40",
-    "@babel/plugin-transform-regenerator": "7.0.0-beta.40",
-    "@babel/plugin-transform-shorthand-properties": "7.0.0-beta.40",
-    "@babel/plugin-transform-spread": "7.0.0-beta.40",
-    "@babel/plugin-transform-sticky-regex": "7.0.0-beta.40",
-    "@babel/plugin-transform-template-literals": "7.0.0-beta.40",
-    "@babel/plugin-transform-unicode-regex": "7.0.0-beta.40",
-    "@babel/template": "7.0.0-beta.40",
-    "metro-babel7-plugin-react-transform": "0.34.0"
+    "@babel/plugin-proposal-class-properties": "7.0.0-beta.47",
+    "@babel/plugin-proposal-object-rest-spread": "7.0.0-beta.47",
+    "@babel/plugin-proposal-optional-chaining": "7.0.0-beta.47",
+    "@babel/plugin-transform-arrow-functions": "7.0.0-beta.47",
+    "@babel/plugin-transform-block-scoping": "7.0.0-beta.47",
+    "@babel/plugin-transform-classes": "7.0.0-beta.47",
+    "@babel/plugin-transform-computed-properties": "7.0.0-beta.47",
+    "@babel/plugin-transform-destructuring": "7.0.0-beta.47",
+    "@babel/plugin-transform-exponentiation-operator": "7.0.0-beta.47",
+    "@babel/plugin-transform-flow-strip-types": "7.0.0-beta.47",
+    "@babel/plugin-transform-for-of": "7.0.0-beta.47",
+    "@babel/plugin-transform-function-name": "7.0.0-beta.47",
+    "@babel/plugin-transform-literals": "7.0.0-beta.47",
+    "@babel/plugin-transform-modules-commonjs": "7.0.0-beta.47",
+    "@babel/plugin-transform-object-assign": "7.0.0-beta.47",
+    "@babel/plugin-transform-parameters": "7.0.0-beta.47",
+    "@babel/plugin-transform-react-display-name": "7.0.0-beta.47",
+    "@babel/plugin-transform-react-jsx": "7.0.0-beta.47",
+    "@babel/plugin-transform-react-jsx-source": "7.0.0-beta.47",
+    "@babel/plugin-transform-regenerator": "7.0.0-beta.47",
+    "@babel/plugin-transform-shorthand-properties": "7.0.0-beta.47",
+    "@babel/plugin-transform-spread": "7.0.0-beta.47",
+    "@babel/plugin-transform-sticky-regex": "7.0.0-beta.47",
+    "@babel/plugin-transform-template-literals": "7.0.0-beta.47",
+    "@babel/plugin-transform-unicode-regex": "7.0.0-beta.47",
+    "@babel/template": "7.0.0-beta.47",
+    "metro-babel7-plugin-react-transform": "0.37.0"
   }
 }
diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index e2796fcf5f61..b8264eb219d6 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -41,7 +41,10 @@ module.exports = {
       // node specific transforms only
       return babelTransformSync(
         src,
-        Object.assign({filename: file}, nodeOptions),
+        Object.assign(
+          {filename: file},
+          {sourceType: 'script', ...nodeOptions, ast: false},
+        ),
       ).code;
     }
 
diff --git a/package.json b/package.json
index 7f6941ff0777..7788e05c1e09 100644
--- a/package.json
+++ b/package.json
@@ -200,7 +200,7 @@
     "yargs": "^9.0.0"
   },
   "devDependencies": {
-    "@babel/core": "7.0.0-beta.40",
+    "@babel/core": "7.0.0-beta.47",
     "async": "^2.4.0",
     "babel-eslint": "8.2.1",
     "babel-generator": "^6.26.0",

From 8bfe78c72307a40d71371195fb89cfa600c05d6b Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Wed, 23 May 2018 10:03:41 -0700
Subject: [PATCH 0650/1109] iOS: Support <ActivityIndicator> component

Summary: Setup for using <ActivityIndicator> component in Fabric.

Reviewed By: shergin

Differential Revision: D8107528

fbshipit-source-id: e3ba46d1538f5d5a2fa6f75639caaaa51156c452
---
 RNTester/Podfile.lock                         |  5 +-
 React.podspec                                 |  9 ++
 .../RCTActivityIndicatorViewComponentView.h   | 21 +++++
 .../RCTActivityIndicatorViewComponentView.mm  | 84 +++++++++++++++++++
 ...ActivityIndicatorViewComponentDescriptor.h | 19 +++++
 .../ActivityIndicatorViewProps.cpp            | 23 +++++
 .../ActivityIndicatorViewProps.h              | 32 +++++++
 .../ActivityIndicatorViewShadowNode.cpp       | 18 ++++
 .../ActivityIndicatorViewShadowNode.h         | 30 +++++++
 ReactCommon/fabric/activityindicator/BUCK     | 78 +++++++++++++++++
 .../fabric/activityindicator/conversions.h    | 31 +++++++
 .../fabric/activityindicator/primitives.h     | 19 +++++
 .../tests/ActivityIndicatorViewTest.cpp       | 14 ++++
 .../fabric/uimanager/FabricUIManager.cpp      |  7 --
 14 files changed, 382 insertions(+), 8 deletions(-)
 create mode 100644 React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.h
 create mode 100644 React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
 create mode 100644 ReactCommon/fabric/activityindicator/ActivityIndicatorViewComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.cpp
 create mode 100644 ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h
 create mode 100644 ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.cpp
 create mode 100644 ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h
 create mode 100644 ReactCommon/fabric/activityindicator/BUCK
 create mode 100644 ReactCommon/fabric/activityindicator/conversions.h
 create mode 100644 ReactCommon/fabric/activityindicator/primitives.h
 create mode 100644 ReactCommon/fabric/activityindicator/tests/ActivityIndicatorViewTest.cpp

diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index cf961ebad09b..f5a55dd3776c 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -23,6 +23,7 @@ PODS:
     - React/Core
     - React/RCTWebSocket
   - React/fabric (1000.0.0):
+    - React/fabric/activityindicator (= 1000.0.0)
     - React/fabric/attributedstring (= 1000.0.0)
     - React/fabric/core (= 1000.0.0)
     - React/fabric/debug (= 1000.0.0)
@@ -32,6 +33,8 @@ PODS:
     - React/fabric/textlayoutmanager (= 1000.0.0)
     - React/fabric/uimanager (= 1000.0.0)
     - React/fabric/view (= 1000.0.0)
+  - React/fabric/activityindicator (1000.0.0):
+    - Folly (= 2016.10.31.00)
   - React/fabric/attributedstring (1000.0.0):
     - Folly (= 2016.10.31.00)
   - React/fabric/core (1000.0.0):
@@ -141,7 +144,7 @@ SPEC CHECKSUMS:
   DoubleConversion: a9706f16e388b53ff12cca34473428ee29746a26
   Folly: c89ac2d5c6ab169cd7397ef27485c44f35f742c7
   glog: 3931855c9cc99c3fab1355fc162fe369162d8183
-  React: 81df86644d0bca489723c964b33b005901ebfb3b
+  React: 1fe0eb13d90b625d94c3b117c274dcfd2e760e11
   yoga: b1ce48b6cf950b98deae82838f5173ea7cf89e85
 
 PODFILE CHECKSUM: 30aa63dcdbb3546a2bacdfd4e005bcca50c9b55c
diff --git a/React.podspec b/React.podspec
index 8a67040ecdfb..946d461b20c9 100644
--- a/React.podspec
+++ b/React.podspec
@@ -135,6 +135,15 @@ Pod::Spec.new do |s|
   end
 
   s.subspec "fabric" do |ss|
+    ss.subspec "activityindicator" do |sss|
+      sss.dependency             "Folly", folly_version
+      sss.compiler_flags       = folly_compiler_flags
+      sss.source_files         = "ReactCommon/fabric/activityindicator/**/*.{cpp,h}"
+      sss.exclude_files        = "**/tests/*"
+      sss.header_dir           = "fabric/activityindicator"
+      sss.pod_target_xcconfig  = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/ReactCommon\" \"$(PODS_ROOT)/Folly\"" }
+    end
+
     ss.subspec "attributedstring" do |sss|
       sss.dependency             "Folly", folly_version
       sss.compiler_flags       = folly_compiler_flags
diff --git a/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.h b/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.h
new file mode 100644
index 000000000000..a1af3f7679d9
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.h
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTViewComponentView.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * UIView class for root <ShimmeringView> component.
+ */
+@interface RCTActivityIndicatorViewComponentView : RCTViewComponentView
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
new file mode 100644
index 000000000000..b0905c9bd61b
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
@@ -0,0 +1,84 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTActivityIndicatorViewComponentView.h"
+
+#import <fabric/activityindicator/ActivityIndicatorViewProps.h>
+
+using namespace facebook::react;
+
+static UIActivityIndicatorViewStyle convertActivityIndicatorViewStyle(const ActivityIndicatorViewSize &size) {
+  switch (size) {
+    case ActivityIndicatorViewSize::Small:
+      return UIActivityIndicatorViewStyleWhite;
+    case ActivityIndicatorViewSize::Large:
+      return UIActivityIndicatorViewStyleWhiteLarge;
+  }
+}
+
+@implementation RCTActivityIndicatorViewComponentView {
+  UIActivityIndicatorView *_activityIndicatorView;
+}
+
+- (instancetype)initWithFrame:(CGRect)frame
+{
+  if (self = [super initWithFrame:frame]) {
+    _activityIndicatorView = [[UIActivityIndicatorView alloc] initWithFrame:self.bounds];
+    _activityIndicatorView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
+
+    auto &&defaultProps = ActivityIndicatorViewProps();
+
+    if (defaultProps.animating) {
+      [_activityIndicatorView startAnimating];
+    } else {
+      [_activityIndicatorView stopAnimating];
+    }
+    _activityIndicatorView.color = [UIColor colorWithCGColor:defaultProps.color.get()];
+    _activityIndicatorView.hidesWhenStopped = defaultProps.hidesWhenStopped;
+    _activityIndicatorView.activityIndicatorViewStyle = convertActivityIndicatorViewStyle(defaultProps.size);
+
+    [self addSubview:_activityIndicatorView];
+  }
+
+  return self;
+}
+
+- (void)updateProps:(SharedProps)props oldProps:(SharedProps)oldProps
+{
+  if (!oldProps) {
+    oldProps = _props ?: std::make_shared<ActivityIndicatorViewProps>();
+  }
+  _props = props;
+
+  [super updateProps:props oldProps:oldProps];
+
+  auto oldViewProps = *std::dynamic_pointer_cast<const ActivityIndicatorViewProps>(oldProps);
+  auto newViewProps = *std::dynamic_pointer_cast<const ActivityIndicatorViewProps>(props);
+
+  if (oldViewProps.animating != newViewProps.animating) {
+    if (newViewProps.animating) {
+      [_activityIndicatorView startAnimating];
+    } else {
+      [_activityIndicatorView stopAnimating];
+    }
+  }
+
+  if (oldViewProps.color.get() != newViewProps.color.get()) {
+    _activityIndicatorView.color = [UIColor colorWithCGColor:newViewProps.color.get()];
+  }
+
+  // TODO: This prop should be deprecated.
+  if (oldViewProps.hidesWhenStopped != newViewProps.hidesWhenStopped) {
+    _activityIndicatorView.hidesWhenStopped = newViewProps.hidesWhenStopped;
+  }
+
+  if (oldViewProps.size != newViewProps.size) {
+    _activityIndicatorView.activityIndicatorViewStyle = convertActivityIndicatorViewStyle(newViewProps.size);
+  }
+}
+
+@end
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewComponentDescriptor.h b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewComponentDescriptor.h
new file mode 100644
index 000000000000..933b8ad59950
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewComponentDescriptor.h
@@ -0,0 +1,19 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/activityindicator/ActivityIndicatorViewShadowNode.h>
+#include <fabric/core/ConcreteComponentDescriptor.h>
+
+namespace facebook {
+namespace react {
+
+using ActivityIndicatorViewComponentDescriptor = ConcreteComponentDescriptor<ActivityIndicatorViewShadowNode>;
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.cpp b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.cpp
new file mode 100644
index 000000000000..cfe19d0eef69
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.cpp
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/activityindicator/ActivityIndicatorViewProps.h>
+#include <fabric/activityindicator/conversions.h>
+#include <fabric/core/propsConversions.h>
+
+namespace facebook {
+namespace react {
+
+ActivityIndicatorViewProps::ActivityIndicatorViewProps(const ActivityIndicatorViewProps &sourceProps, const RawProps &rawProps):
+  ViewProps(sourceProps, rawProps),
+  animating(convertRawProp(rawProps, "animating", sourceProps.animating)),
+  color(convertRawProp(rawProps, "color", sourceProps.color)),
+  hidesWhenStopped(convertRawProp(rawProps, "hidesWhenStopped", sourceProps.hidesWhenStopped)),
+  size(convertRawProp(rawProps, "size", sourceProps.size)) {}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h
new file mode 100644
index 000000000000..470d86e7dc88
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h
@@ -0,0 +1,32 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/activityindicator/primitives.h>
+#include <fabric/graphics/Color.h>
+#include <fabric/view/ViewProps.h>
+
+namespace facebook {
+namespace react {
+
+// TODO (T28334063): Consider for codegen.
+class ActivityIndicatorViewProps final:
+  public ViewProps {
+
+public:
+  ActivityIndicatorViewProps() = default;
+  ActivityIndicatorViewProps(const ActivityIndicatorViewProps &sourceProps, const RawProps &rawProps);
+
+#pragma mark - Props
+
+  const bool animating {true};
+  const SharedColor color {colorFromComponents({153/255.0, 153/255.0, 153/255.0, 1.0})}; // #999999
+  const bool hidesWhenStopped {true};
+  const ActivityIndicatorViewSize size {ActivityIndicatorViewSize::Small};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.cpp b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.cpp
new file mode 100644
index 000000000000..d6a512930a9c
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.cpp
@@ -0,0 +1,18 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/activityindicator/ActivityIndicatorViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+ComponentName ActivityIndicatorViewShadowNode::getComponentName() const {
+  return ComponentName("ActivityIndicatorView");
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h
new file mode 100644
index 000000000000..2cb71f2a7d66
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h
@@ -0,0 +1,30 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/activityindicator/ActivityIndicatorViewProps.h>
+#include <fabric/view/ConcreteViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * `ShadowNode` for <ActivityIndicatorView> component.
+ */
+class ActivityIndicatorViewShadowNode final:
+  public ConcreteViewShadowNode<ActivityIndicatorViewProps> {
+
+public:
+
+  using ConcreteViewShadowNode::ConcreteViewShadowNode;
+
+  ComponentName getComponentName() const override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/activityindicator/BUCK b/ReactCommon/fabric/activityindicator/BUCK
new file mode 100644
index 000000000000..708c5fe41eb5
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/BUCK
@@ -0,0 +1,78 @@
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+
+rn_xplat_cxx_library(
+    name = "activityindicator",
+    srcs = glob(
+        ["**/*.cpp"],
+        exclude = glob(["tests/**/*.cpp"]),
+    ),
+    headers = [],
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/activityindicator",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+        react_native_xplat_target("fabric/view:view"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":activityindicator",
+        ],
+    )
diff --git a/ReactCommon/fabric/activityindicator/conversions.h b/ReactCommon/fabric/activityindicator/conversions.h
new file mode 100644
index 000000000000..33b56b05fa9c
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/conversions.h
@@ -0,0 +1,31 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/activityindicator/primitives.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+inline void fromDynamic(const folly::dynamic &value, ActivityIndicatorViewSize &result) {
+  auto string = value.asString();
+  if (string == "large") { result = ActivityIndicatorViewSize::Large; return; }
+  if (string == "small") { result = ActivityIndicatorViewSize::Small; return; }
+  abort();
+}
+
+inline std::string toString(const ActivityIndicatorViewSize &value) {
+  switch (value) {
+    case ActivityIndicatorViewSize::Large: return "large";
+    case ActivityIndicatorViewSize::Small: return "small";
+  }
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/activityindicator/primitives.h b/ReactCommon/fabric/activityindicator/primitives.h
new file mode 100644
index 000000000000..4d727793be58
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/primitives.h
@@ -0,0 +1,19 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+namespace facebook {
+namespace react {
+
+enum class ActivityIndicatorViewSize {
+  Large,
+  Small,
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/activityindicator/tests/ActivityIndicatorViewTest.cpp b/ReactCommon/fabric/activityindicator/tests/ActivityIndicatorViewTest.cpp
new file mode 100644
index 000000000000..5a168cf958e9
--- /dev/null
+++ b/ReactCommon/fabric/activityindicator/tests/ActivityIndicatorViewTest.cpp
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+TEST(ActivityIndicatorViewTest, testSomething) {
+  // TODO
+}
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index c41eddf0da36..3bb38a7552c0 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -69,13 +69,6 @@ static const std::string componentNameByReactViewName(std::string viewName) {
     return "View";
   }
 
-  // Other temporary fallback until the native components are implemented.
-  if (
-    viewName == "ActivityIndicatorView"
-  ) {
-    return "View";
-  }
-
   return viewName;
 }
 

From 3e0ebc76632238f21c60caa92c7a2b5ee8102b71 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Wed, 23 May 2018 12:43:37 -0700
Subject: [PATCH 0651/1109] Revert bump to API 26 and fix Android tests
 failures

Summary:
This reverts https://github.com/facebook/react-native/commit/a3931e95317acaff5ceb1d2fb0f26ae67744c8a3

The open source `test_android` job is not configured to use Android 26 quite yet. I've spent a couple of days trying to get our Android tests back in working order, with no luck.

I'm reverting the change that bumped React Native to use build tools 26 + Android SDK 26. I encourage contributors interested in making this change happen to work on getting our Android tests working with API 26.

This will allow us to focus on getting `test_android` back to green, and _then_ we can work on bumping to API 26 while keeping tests green.

Reviewed By: fkgozali

Differential Revision: D8066226

fbshipit-source-id: 9bfd58a7f081c0971b78b331073e70545c21ca6d
---
 .circleci/config.yml                                    | 4 ----
 RNTester/android/app/build.gradle                       | 6 +++---
 ReactAndroid/build.gradle                               | 6 +++---
 local-cli/templates/HelloWorld/android/app/build.gradle | 6 +++---
 local-cli/templates/HelloWorld/android/build.gradle     | 8 --------
 scripts/.tests.env                                      | 4 ++--
 6 files changed, 11 insertions(+), 23 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 57d57acdbf42..7ede2ebf81cf 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -328,10 +328,8 @@ jobs:
       - run: *setup-artifacts
 
       - restore-cache: *restore-yarn-cache
-      - restore-cache: *restore-node-modules
       - run: *yarn
       - save-cache: *save-yarn-cache
-      - save-cache: *save-node-modules
 
       # Basic checks against the checkout, cache...
       - run: *run-sanity-checks
@@ -459,10 +457,8 @@ jobs:
       - save-cache: *save-cache-gradle-downloads
 
       - restore-cache: *restore-yarn-cache
-      - restore-cache: *restore-node-modules
       - run: *yarn
       - save-cache: *save-yarn-cache
-      - save-cache: *save-node-modules
 
       - run:
           name: Publish React Native Package
diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index c1149e6a5e6f..5e5503b5eb7c 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -84,8 +84,8 @@ def enableSeparateBuildPerCPUArchitecture = false
 def enableProguardInReleaseBuilds = false
 
 android {
-    compileSdkVersion 26
-    buildToolsVersion "26.0.3"
+    compileSdkVersion 23
+    buildToolsVersion "23.0.1"
 
     defaultConfig {
         applicationId "com.facebook.react.uiapp"
@@ -137,7 +137,7 @@ android {
 
 dependencies {
     compile fileTree(dir: 'libs', include: ['*.jar'])
-    compile 'com.android.support:appcompat-v7:26.0.2'
+    compile 'com.android.support:appcompat-v7:23.0.1'
 
     // Build React Native from source
     compile project(':ReactAndroid')
diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 29fdcd6aae65..503b814f32ac 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -242,8 +242,8 @@ task packageReactNdkLibsForBuck(dependsOn: packageReactNdkLibs, type: Copy) {
 }
 
 android {
-    compileSdkVersion 26
-    buildToolsVersion "26.0.3"
+    compileSdkVersion 23
+    buildToolsVersion "23.0.1"
 
     defaultConfig {
         minSdkVersion 16
@@ -292,7 +292,7 @@ android {
 dependencies {
     compile fileTree(dir: 'src/main/third-party/java/infer-annotations/', include: ['*.jar'])
     compile 'javax.inject:javax.inject:1'
-    compile 'com.android.support:appcompat-v7:26.0.2'
+    compile 'com.android.support:appcompat-v7:23.0.1'
     compile 'com.facebook.fbui.textlayoutbuilder:textlayoutbuilder:1.0.0'
     compile 'com.facebook.fresco:fresco:1.9.0'
     compile 'com.facebook.fresco:imagepipeline-okhttp3:1.9.0'
diff --git a/local-cli/templates/HelloWorld/android/app/build.gradle b/local-cli/templates/HelloWorld/android/app/build.gradle
index f9f5ebc2bb39..ec6f3022572a 100644
--- a/local-cli/templates/HelloWorld/android/app/build.gradle
+++ b/local-cli/templates/HelloWorld/android/app/build.gradle
@@ -94,8 +94,8 @@ def enableSeparateBuildPerCPUArchitecture = false
 def enableProguardInReleaseBuilds = false
 
 android {
-    compileSdkVersion 26
-    buildToolsVersion "26.0.3"
+    compileSdkVersion 23
+    buildToolsVersion "23.0.1"
 
     defaultConfig {
         applicationId "com.helloworld"
@@ -138,7 +138,7 @@ android {
 
 dependencies {
     compile fileTree(dir: "libs", include: ["*.jar"])
-    compile "com.android.support:appcompat-v7:26.0.2"
+    compile "com.android.support:appcompat-v7:23.0.1"
     compile "com.facebook.react:react-native:+"  // From node_modules
 }
 
diff --git a/local-cli/templates/HelloWorld/android/build.gradle b/local-cli/templates/HelloWorld/android/build.gradle
index 8bd0ba32b04f..eed9972b5c13 100644
--- a/local-cli/templates/HelloWorld/android/build.gradle
+++ b/local-cli/templates/HelloWorld/android/build.gradle
@@ -3,10 +3,6 @@
 buildscript {
     repositories {
         jcenter()
-        maven {
-            url 'https://maven.google.com/'
-            name 'Google'
-        }
     }
     dependencies {
         classpath 'com.android.tools.build:gradle:2.2.3'
@@ -20,10 +16,6 @@ allprojects {
     repositories {
         mavenLocal()
         jcenter()
-        maven {
-            url 'https://maven.google.com/'
-            name 'Google'
-        }
         maven {
             // All of React Native (JS, Obj-C sources, Android binaries) is installed from npm
             url "$rootDir/../node_modules/react-native/android"
diff --git a/scripts/.tests.env b/scripts/.tests.env
index ab318809fef5..a03f487abe4d 100644
--- a/scripts/.tests.env
+++ b/scripts/.tests.env
@@ -4,9 +4,9 @@
 
 ## ANDROID ##
 # Android SDK Build Tools revision
-export ANDROID_SDK_BUILD_TOOLS_REVISION=26.0.3
+export ANDROID_SDK_BUILD_TOOLS_REVISION=23.0.1
 # Android API Level we build with
-export ANDROID_SDK_BUILD_API_LEVEL="26"
+export ANDROID_SDK_BUILD_API_LEVEL="23"
 # Google APIs for Android level
 export ANDROID_GOOGLE_API_LEVEL="23"
 # Minimum Android API Level we target

From 390ded871cb905d149e9c1f4a082e67a7ec7addb Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Wed, 23 May 2018 13:21:32 -0700
Subject: [PATCH 0652/1109] Move out "genMockFunction" and "genMockFn" to "fn"

Summary: In the upcoming Jest version `genMockFunction` and `genMockFn` are deprecated, so we need to kill them.

Reviewed By: rafeca

Differential Revision: D8107155

fbshipit-source-id: 4f46ab58e6e34224eb95e9355385da44f005ea94
---
 Libraries/Animated/src/__tests__/AnimatedNative-test.js | 2 +-
 local-cli/util/__mocks__/log.js                         | 4 ++--
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/Libraries/Animated/src/__tests__/AnimatedNative-test.js b/Libraries/Animated/src/__tests__/AnimatedNative-test.js
index 8f59d33c57cb..d3ff6665cbc8 100644
--- a/Libraries/Animated/src/__tests__/AnimatedNative-test.js
+++ b/Libraries/Animated/src/__tests__/AnimatedNative-test.js
@@ -81,7 +81,7 @@ describe('Native Animated', () => {
       // via component refs table that we override here.
       c.refs = {
         node: {
-          setNativeProps: jest.genMockFunction(),
+          setNativeProps: jest.fn(),
         },
       };
 
diff --git a/local-cli/util/__mocks__/log.js b/local-cli/util/__mocks__/log.js
index 12d8627ba478..19247b949010 100644
--- a/local-cli/util/__mocks__/log.js
+++ b/local-cli/util/__mocks__/log.js
@@ -9,5 +9,5 @@
 
 'use strict';
 
-module.exports.out = () => jest.genMockFn();
-module.exports.err = () => jest.genMockFn();
+module.exports.out = () => jest.fn();
+module.exports.err = () => jest.fn();

From 0bbac18cf0ac7434e231cc90604db011602246b8 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Wed, 23 May 2018 13:51:57 -0700
Subject: [PATCH 0653/1109] circle ci: yarn cache uses package.json checksum as
 a key

Summary:
To better utilize Circle CI caching, yarn cache will use package.json file checksum as key in addition to arch, because in most cases yarn cache will be updated if package.json updates.

Circle CI sample apps use yarn.lock checksum as yarn cache key, but react-native don't have yarn.lock in the repo, so it's best to use package.json instead.
Closes https://github.com/facebook/react-native/pull/19395

Differential Revision: D8125405

Pulled By: hramos

fbshipit-source-id: 5c7aa312231cc0b42bc502a5177bb84e31bcd305
---
 .circleci/config.yml | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 7ede2ebf81cf..7b78ebf8f522 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -2,11 +2,12 @@ aliases:
   # Cache Management
   - &restore-yarn-cache
     keys:
+      - v1-yarn-cache-{{ arch }}-{{ checksum "package.json" }}
       - v1-yarn-cache-{{ arch }}
   - &save-yarn-cache
     paths:
       - ~/.cache/yarn
-    key: v1-yarn-cache-{{ arch }}
+    key: v1-yarn-cache-{{ arch }}-{{ checksum "package.json" }}
 
   - &restore-node-modules
     keys:

From e1a36fcf7aa28d37d9a5935bd45400fd6dd3e8e1 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Wed, 23 May 2018 15:58:59 -0700
Subject: [PATCH 0654/1109] Restore catch-all issue template

Summary:
Without this, people may still submit non-templated issues.
Closes https://github.com/facebook/react-native/pull/19415

Differential Revision: D8128095

Pulled By: hramos

fbshipit-source-id: 34666e223cd12eb123501898cb7795cef2834421
---
 .github/ISSUE_TEMPLATE.md               | 3 +++
 .github/ISSUE_TEMPLATE/bug_report.md    | 7 +------
 .github/ISSUE_TEMPLATE/documentation.md | 9 +++++++++
 .github/ISSUE_TEMPLATE/question.md      | 2 +-
 4 files changed, 14 insertions(+), 7 deletions(-)
 create mode 100644 .github/ISSUE_TEMPLATE.md
 create mode 100644 .github/ISSUE_TEMPLATE/documentation.md

diff --git a/.github/ISSUE_TEMPLATE.md b/.github/ISSUE_TEMPLATE.md
new file mode 100644
index 000000000000..d31f3a36ccac
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE.md
@@ -0,0 +1,3 @@
+GitHub Issues in the `facebook/react-native` repository are used exclusively for tracking bugs in React Native.
+
+Please take a look at the issue templates at https://github.com/facebook/react-native/issues/new/choose before submitting a new issue. Following one of the issue templates will ensure maintainers can route your request efficiently. Thanks!
diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md
index 3c4f6e2f67d8..57aac5b85e5b 100644
--- a/.github/ISSUE_TEMPLATE/bug_report.md
+++ b/.github/ISSUE_TEMPLATE/bug_report.md
@@ -4,12 +4,7 @@ about: Something is not working as expected.
 
 ---
 
-<!--
-  We use GitHub Issues exclusively for tracking bugs in React Native.
-  Questions? Visit http://facebook.github.io/react-native/help.html
-  If this issue is about documentation or the website, please file it at:
-  https://github.com/facebook/react-native-website/issues/new
--->
+<!-- GitHub Issues in the `facebook/react-native` repository are used exclusively for tracking bugs in React Native. -->
 
 - [ ] I have reviewed the [documentation](https://facebook.github.io/react-native)
 - [ ] I have searched [existing issues](https://github.com/facebook/react-native/issues)
diff --git a/.github/ISSUE_TEMPLATE/documentation.md b/.github/ISSUE_TEMPLATE/documentation.md
new file mode 100644
index 000000000000..e18bdfaf164f
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/documentation.md
@@ -0,0 +1,9 @@
+---
+name: 📖 Documentation Issue
+about: Report issues with the docs at https://github.com/facebook/react-native-website/issues
+
+---
+
+GitHub Issues in the `facebook/react-native` repository are used exclusively for tracking bugs in React Native.
+
+If you would like to report an issue in the React Native documentation, or anything related to the [React Native website](http://facebook.github.io/react-native), please visit https://github.com/facebook/react-native-website/issues.
diff --git a/.github/ISSUE_TEMPLATE/question.md b/.github/ISSUE_TEMPLATE/question.md
index 503775b920d0..bba783655e1b 100644
--- a/.github/ISSUE_TEMPLATE/question.md
+++ b/.github/ISSUE_TEMPLATE/question.md
@@ -6,7 +6,7 @@ about: For questions about using React Native in your app.
 
 --------------^ Click "Preview" for a nicer view!
 
-We use GitHub Issues exclusively for tracking bugs in React Native. If you need help with your React Native app, the right place to go depends on the type of help that you need.
+GitHub Issues in the `facebook/react-native` repository are used exclusively for tracking bugs in React Native. If you need help with your React Native app, the right place to go depends on the type of help that you need.
 
 ### Stack Overflow
 

From c09d509c2b8a5a02701829e1f0ace8081ce64277 Mon Sep 17 00:00:00 2001
From: Sho Ikeda <suicaicoca@gmail.com>
Date: Thu, 24 May 2018 12:37:32 -0700
Subject: [PATCH 0655/1109] Fix CocoaPods integration without DevSupport
 subspec

Summary:
This is the thing which is handled in https://github.com/orta/cocoapods-fix-react-native today.

https://github.com/orta/cocoapods-fix-react-native/blob/89a78ad34950b5d6b3de657914c8ced8bf37ee8e/lib/cocoapods-fix-react-native/versions/0_55_3-post.rb#L140-L164

This should be the correct fix for #17799.

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Integrating React Native into an existing iOS project using CocoaPods without `DevSupport` subspec and seeing if the project successfully compiles.

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[IOS] [BUGFIX] [DevSupport] - Fix CocoaPods integration without DevSupport subspec
Closes https://github.com/facebook/react-native/pull/19265

Differential Revision: D8149786

Pulled By: hramos

fbshipit-source-id: c665e463b76aacdfb2022e82e36eb381d2d9ff2b
---
 React/Modules/RCTDevSettings.mm | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/React/Modules/RCTDevSettings.mm b/React/Modules/RCTDevSettings.mm
index db61029d8ae8..684e5d2238f2 100644
--- a/React/Modules/RCTDevSettings.mm
+++ b/React/Modules/RCTDevSettings.mm
@@ -18,7 +18,6 @@
 #import "RCTEventDispatcher.h"
 #import "RCTJSCSamplingProfiler.h"
 #import "RCTLog.h"
-#import "RCTPackagerClient.h"
 #import "RCTProfile.h"
 #import "RCTUtils.h"
 
@@ -35,6 +34,7 @@
 static NSString *const kRCTDevSettingsUserDefaultsKey = @"RCTDevMenu";
 
 #if ENABLE_PACKAGER_CONNECTION
+#import "RCTPackagerClient.h"
 #import "RCTPackagerConnection.h"
 #endif
 
@@ -201,6 +201,7 @@ - (void)setBridge:(RCTBridge *)bridge
 #endif
 }
 
+#if ENABLE_PACKAGER_CONNECTION
 static void pokeSamplingProfiler(RCTBridge *const bridge, RCTPackagerClientResponder *const responder)
 {
   if (!bridge) {
@@ -224,6 +225,7 @@ static void pokeSamplingProfiler(RCTBridge *const bridge, RCTPackagerClientRespo
     [responder respondWithResult:results];
   }
 }
+#endif
 
 - (dispatch_queue_t)methodQueue
 {

From 6d2ed2c170a3b94ec425ef1227339ef3293e4364 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Thu, 24 May 2018 12:55:36 -0700
Subject: [PATCH 0656/1109] Improve docker

Summary:
Improve current docker by
* Make android build version and tools version config easily, and bump them to 26.
* use less file layer
* fix current docker error (the maintainer line)
* fix typo in package.json

Since ci on master branch still failed, and I run test the docker build. And in the process I found buck related config still is 23.

none

 [GENERAL] [ENHANCEMENT] [CI] - Improve docker
Closes https://github.com/facebook/react-native/pull/19354

Differential Revision: D8148376

Pulled By: hramos

fbshipit-source-id: 8f965860487467c1a219e64588ff3000d571ddc1
---
 ContainerShip/Dockerfile.android      |  3 +-
 ContainerShip/Dockerfile.android-base | 47 +++++++++++++--------------
 package.json                          |  6 ++--
 3 files changed, 27 insertions(+), 29 deletions(-)

diff --git a/ContainerShip/Dockerfile.android b/ContainerShip/Dockerfile.android
index a72a4b64403e..ab311060b2c3 100644
--- a/ContainerShip/Dockerfile.android
+++ b/ContainerShip/Dockerfile.android
@@ -6,7 +6,8 @@
 # or run tests, as well as unit test failures.
 FROM reactnativeci/android-base:latest
 
-LABEL Description="This image prepares and runs React Native's Android tests." maintainer "Héctor Ramos <hector@fb.com>"
+LABEL Description="This image prepares and runs React Native's Android tests."
+LABEL maintainer="Héctor Ramos <hector@fb.com>"
 
 # set default environment variables
 ENV GRADLE_OPTS="-Dorg.gradle.daemon=false -Dorg.gradle.jvmargs=\"-Xmx512m -XX:+HeapDumpOnOutOfMemoryError\""
diff --git a/ContainerShip/Dockerfile.android-base b/ContainerShip/Dockerfile.android-base
index 083903341e07..c9eb8e4c0230 100644
--- a/ContainerShip/Dockerfile.android-base
+++ b/ContainerShip/Dockerfile.android-base
@@ -13,10 +13,13 @@
 
 FROM library/ubuntu:16.04
 
-LABEL Description="This image provides a base Android development environment for React Native, and may be used to run tests." maintainer "Héctor Ramos <hector@fb.com>"
+LABEL Description="This image provides a base Android development environment for React Native, and may be used to run tests."
+LABEL maintainer="Héctor Ramos <hector@fb.com>"
 
 # set default build arguments
-ARG ANDROID_TOOLS_VERSION=25.2.5
+ARG SDK_VERSION=sdk-tools-linux-3859397.zip
+ARG ANDROID_BUILD_VERSION=26
+ARG ANDROID_TOOLS_VERSION=26.0.3
 ARG BUCK_VERSION=v2018.02.16.01
 ARG NDK_VERSION=10e
 ARG NODE_VERSION=8.10.0
@@ -35,8 +38,8 @@ ENV PATH=${PATH}:${ANDROID_NDK}
 RUN apt-get update && apt-get install ant autoconf automake curl g++ gcc git libqt5widgets5 lib32z1 lib32stdc++6 make maven npm openjdk-8* python-dev python3-dev qml-module-qtquick-controls qtdeclarative5-dev unzip -y
 
 # configure npm
-RUN npm config set spin=false
-RUN npm config set progress=false
+RUN npm config set spin=false && \
+    npm config set progress=false
 
 # install node
 RUN npm install n -g
@@ -51,31 +54,25 @@ RUN ant
 
 # Full reference at https://dl.google.com/android/repository/repository2-1.xml
 # download and unpack android
-RUN mkdir /opt/android
-WORKDIR /opt/android
-RUN curl --silent https://dl.google.com/android/repository/tools_r$ANDROID_TOOLS_VERSION-linux.zip > android.zip
-RUN unzip android.zip
-RUN rm android.zip
+RUN mkdir /opt/android && \
+ cd /opt/android && \
+ curl --silent https://dl.google.com/android/repository/${SDK_VERSION} > android.zip && \
+ unzip android.zip && \
+ rm android.zip
 
 # download and unpack NDK
-RUN mkdir /opt/ndk
-WORKDIR /opt/ndk
-RUN curl --silent https://dl.google.com/android/repository/android-ndk-r$NDK_VERSION-linux-x86_64.zip > ndk.zip
-RUN unzip ndk.zip
-
-# cleanup NDK
-RUN rm ndk.zip
+RUN mkdir /opt/ndk && \
+  cd /opt/ndk && \
+  curl --silent https://dl.google.com/android/repository/android-ndk-r$NDK_VERSION-linux-x86_64.zip > ndk.zip && \
+  unzip ndk.zip && \
+  rm ndk.zip
 
 # Add android SDK tools
-RUN echo "y" | sdkmanager "system-images;android-19;google_apis;armeabi-v7a"
-RUN echo "y" | sdkmanager "platforms;android-23"
-RUN echo "y" | sdkmanager "platforms;android-19"
-RUN echo "y" | sdkmanager "build-tools;23.0.1"
-RUN echo "y" | sdkmanager "add-ons;addon-google_apis-google-23"
-RUN echo "y" | sdkmanager "extras;android;m2repository"
-
-# Link adb executable
-RUN ln -s /opt/android/platform-tools/adb /usr/bin/adb
+RUN sdkmanager "system-images;android-19;google_apis;armeabi-v7a" \
+    "platforms;android-$ANDROID_BUILD_VERSION" \
+    "build-tools;$ANDROID_TOOLS_VERSION" \
+    "add-ons;addon-google_apis-google-23" \
+    "extras;android;m2repository"
 
 # clean up unnecessary directories
 RUN rm -rf /opt/android/system-images/android-19/default/x86
diff --git a/package.json b/package.json
index 7788e05c1e09..7a4741b2e302 100644
--- a/package.json
+++ b/package.json
@@ -131,9 +131,9 @@
     "docker-setup-android": "docker pull reactnativeci/android-base:latest",
     "docker-build-android-base": "docker build -t reactnativeci/android-base -f ContainerShip/Dockerfile.android-base .",
     "docker-build-android": "docker build -t reactnativeci/android -f ContainerShip/Dockerfile.android .",
-    "test-android-run-instrumentation": "docker run --cap-add=SYS_ADMIN -it react/android bash ContainerShip/scripts/run-android-docker-instrumentation-tests.sh",
-    "test-android-run-unit": "docker run --cap-add=SYS_ADMIN -it react/android bash ContainerShip/scripts/run-android-docker-unit-tests.sh",
-    "test-android-run-e2e": "docker run --privileged -it react/android bash ContainerShip/scripts/run-ci-e2e-tests.sh --android --js",
+    "test-android-run-instrumentation": "docker run --cap-add=SYS_ADMIN -it reactnativeci/android bash ContainerShip/scripts/run-android-docker-instrumentation-tests.sh",
+    "test-android-run-unit": "docker run --cap-add=SYS_ADMIN -it reactnativeci/android bash ContainerShip/scripts/run-android-docker-unit-tests.sh",
+    "test-android-run-e2e": "docker run --privileged -it reactnativeci/android bash ContainerShip/scripts/run-ci-e2e-tests.sh --android --js",
     "test-android-all": "yarn run docker-build-android && yarn run test-android-run-unit && yarn run test-android-run-instrumentation && yarn run test-android-run-e2e",
     "test-android-instrumentation": "yarn run docker-build-android && yarn run test-android-run-instrumentation",
     "test-android-unit": "yarn run docker-build-android && yarn run test-android-run-unit",

From d5cfda51c41f5017adea5b805047e44f5708b13b Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 24 May 2018 14:37:10 -0700
Subject: [PATCH 0657/1109] iOS OSS cocoapods: removed deps on RCTFabric for
 now

Summary: There are new patterns that require some upgrades to Folly version we're using for the cocoapods/gradle. Until the upgrade happens, Fabric target doesn't need to be included in the normal RNTester podfile (it was there for sanity build check).

Reviewed By: shergin

Differential Revision: D8151782

fbshipit-source-id: 8d83355d65b1eeeab865585f2ae75ac835bdf826
---
 RNTester/Podfile      |  7 +++++--
 RNTester/Podfile.lock | 42 +-----------------------------------------
 2 files changed, 6 insertions(+), 43 deletions(-)

diff --git a/RNTester/Podfile b/RNTester/Podfile
index 40877c075559..c38e306b080d 100644
--- a/RNTester/Podfile
+++ b/RNTester/Podfile
@@ -15,8 +15,6 @@ target 'RNTester' do
     'RCTAnimation',
     'RCTBlob',
     'RCTCameraRoll',
-    'RCTFabric',
-    'RCTFabricSample', # This is RNTesterPods specific sample.
     'RCTGeolocation',
     'RCTImage',
     'RCTLinkingIOS',
@@ -26,6 +24,11 @@ target 'RNTester' do
     'RCTText',
     'RCTVibration',
     'RCTWebSocket',
+
+    # Below this line is Fabric (experimental) specific.
+    # Currently they are disabled due to missing pre-reqs, e.g. upgrading Folly.
+    # 'RCTFabric',
+    # 'RCTFabricSample', # This is RNTesterPods specific sample.
   ]
 
   pod 'yoga', :path => '../ReactCommon/yoga'
diff --git a/RNTester/Podfile.lock b/RNTester/Podfile.lock
index f5a55dd3776c..e4ba550e92c6 100644
--- a/RNTester/Podfile.lock
+++ b/RNTester/Podfile.lock
@@ -22,38 +22,6 @@ PODS:
   - React/DevSupport (1000.0.0):
     - React/Core
     - React/RCTWebSocket
-  - React/fabric (1000.0.0):
-    - React/fabric/activityindicator (= 1000.0.0)
-    - React/fabric/attributedstring (= 1000.0.0)
-    - React/fabric/core (= 1000.0.0)
-    - React/fabric/debug (= 1000.0.0)
-    - React/fabric/graphics (= 1000.0.0)
-    - React/fabric/scrollview (= 1000.0.0)
-    - React/fabric/text (= 1000.0.0)
-    - React/fabric/textlayoutmanager (= 1000.0.0)
-    - React/fabric/uimanager (= 1000.0.0)
-    - React/fabric/view (= 1000.0.0)
-  - React/fabric/activityindicator (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/attributedstring (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/core (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/debug (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/graphics (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/scrollview (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/text (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/textlayoutmanager (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/uimanager (1000.0.0):
-    - Folly (= 2016.10.31.00)
-  - React/fabric/view (1000.0.0):
-    - Folly (= 2016.10.31.00)
-    - yoga
   - React/fishhook (1000.0.0)
   - React/jschelpers (1000.0.0):
     - Folly (= 2016.10.31.00)
@@ -69,12 +37,6 @@ PODS:
   - React/RCTCameraRoll (1000.0.0):
     - React/Core
     - React/RCTImage
-  - React/RCTFabric (1000.0.0):
-    - Folly (= 2016.10.31.00)
-    - React/Core
-    - React/fabric
-  - React/RCTFabricSample (1000.0.0):
-    - Folly (= 2016.10.31.00)
   - React/RCTGeolocation (1000.0.0):
     - React/Core
   - React/RCTImage (1000.0.0):
@@ -110,8 +72,6 @@ DEPENDENCIES:
   - React/RCTAnimation (from `../`)
   - React/RCTBlob (from `../`)
   - React/RCTCameraRoll (from `../`)
-  - React/RCTFabric (from `../`)
-  - React/RCTFabricSample (from `../`)
   - React/RCTGeolocation (from `../`)
   - React/RCTImage (from `../`)
   - React/RCTLinkingIOS (from `../`)
@@ -147,6 +107,6 @@ SPEC CHECKSUMS:
   React: 1fe0eb13d90b625d94c3b117c274dcfd2e760e11
   yoga: b1ce48b6cf950b98deae82838f5173ea7cf89e85
 
-PODFILE CHECKSUM: 30aa63dcdbb3546a2bacdfd4e005bcca50c9b55c
+PODFILE CHECKSUM: 7af77fbc34af9646e8c6389e7e2c0b4663bb16d9
 
 COCOAPODS: 1.5.2

From b13add753bd913f4cbe9fc0e929c9f5d7f8e3156 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 24 May 2018 17:53:26 -0700
Subject: [PATCH 0658/1109] Fabric: Optimizing yogaNodeCloneCallbackConnector
 in case of correct childIndex

Summary:
YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector is a hot path.
Previous implementation did not use provided `childIndex` which is correct for most cases.
See comments in code for more details.

Reviewed By: fkgozali

Differential Revision: D8070120

fbshipit-source-id: d1a6abe82688387752b66a57b13dc356abb22c96
---
 .../view/yoga/YogaLayoutableShadowNode.cpp    | 25 ++++++++++++++++---
 1 file changed, 21 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index d9082bdfc9ce..c8c66fcf66d3 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -143,11 +143,26 @@ YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYoga
 
   // ... but we have to address this by `shared_ptr`. We cannot create a new `shared_ptr` for it because we will end up with two shared pointers to
   // single object which will cause preluminary destroyng the object.
-  // Another approaches to consider:
-  //  * Create a new `shared_ptr` with empty deleter.
-  //  * Using `childIndex` to find exact node.
+
+  auto &&layoutableChildNodes = parentShadowNodeRawPtr->getLayoutableChildNodes();
   SharedLayoutableShadowNode oldShadowNode = nullptr;
-  for (auto child : parentShadowNodeRawPtr->getLayoutableChildNodes()) {
+
+  // We cannot rely on `childIndex` all the time because `childNodes` can
+  // contain non-layoutable shadow nodes, however chances are good that
+  // `childIndex` points to the right shadow node.
+
+  // Optimistic attempt (in case if `childIndex` is valid):
+  if (childIndex < layoutableChildNodes.size()) {
+    oldShadowNode = layoutableChildNodes[childIndex];
+    if (oldShadowNode.get() == oldShadowNodeRawPtr) {
+      goto found;
+    } else {
+      oldShadowNode = nullptr;
+    }
+  }
+
+  // General solution:
+  for (auto child : layoutableChildNodes) {
     if (child.get() == oldShadowNodeRawPtr) {
       oldShadowNode = child;
       break;
@@ -156,6 +171,8 @@ YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYoga
 
   assert(oldShadowNode);
 
+found:
+
   // The new one does not exist yet. So, we have to clone and replace this using `cloneAndReplaceChild`.
   SharedYogaLayoutableShadowNode newShadowNode =
     std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(parentShadowNodeRawPtr->cloneAndReplaceChild(oldShadowNode));

From 0be26092a5aa151180b16a24e0543a9496a2e1b4 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 24 May 2018 18:23:08 -0700
Subject: [PATCH 0659/1109] Fabric: Wiring FabricUIManager with
 JS*FabricUIManager bindings

Summary: Now FabricUIManager is all you (or I) need to deliver an event.

Reviewed By: fkgozali

Differential Revision: D8086627

fbshipit-source-id: 70d783bee291f4c5d19650ac0768a5d2bd778961
---
 .../fabric/uimanager/FabricUIManager.cpp      | 41 ++++++++++++++++++-
 .../fabric/uimanager/FabricUIManager.h        | 28 +++++++++++++
 2 files changed, 68 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 3bb38a7552c0..94b630c74674 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -76,6 +76,12 @@ FabricUIManager::FabricUIManager(SharedComponentDescriptorRegistry componentDesc
   componentDescriptorRegistry_ = componentDescriptorRegistry;
 }
 
+FabricUIManager::~FabricUIManager() {
+  if (eventHandler_) {
+    releaseEventTargetFunction_(eventHandler_);
+  }
+}
+
 void FabricUIManager::setDelegate(UIManagerDelegate *delegate) {
   delegate_ = delegate;
 }
@@ -84,6 +90,39 @@ UIManagerDelegate *FabricUIManager::getDelegate() {
   return delegate_;
 }
 
+void FabricUIManager::setCreateEventTargetFunction(std::function<CreateEventTargetFunction> createEventTargetFunction) {
+  createEventTargetFunction_ = createEventTargetFunction;
+}
+
+void FabricUIManager::setDispatchEventFunction(std::function<DispatchEventFunction> dispatchEventFunction) {
+  dispatchEventFunction_ = dispatchEventFunction;
+}
+
+void FabricUIManager::setReleaseEventTargetFunction(std::function<ReleaseEventTargetFunction> releaseEventTargetFunction) {
+  releaseEventTargetFunction_ = releaseEventTargetFunction;
+}
+
+void FabricUIManager::setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction) {
+  releaseEventHandlerFunction_ = releaseEventHandlerFunction;
+}
+
+void *FabricUIManager::createEventTarget(void *instanceHandle) {
+  return createEventTargetFunction_(instanceHandle);
+}
+
+void FabricUIManager::dispatchEvent(void *eventTarget, const std::string &type, const folly::dynamic &payload) {
+  dispatchEventFunction_(
+    eventHandler_,
+    eventTarget,
+    const_cast<std::string &>(type),
+    const_cast<folly::dynamic &>(payload)
+  );
+}
+
+void FabricUIManager::releaseEventTarget(void *eventTarget) {
+  releaseEventTargetFunction_(eventTarget);
+}
+
 SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, InstanceHandle instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
 
@@ -214,7 +253,7 @@ void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedLi
 
 void FabricUIManager::registerEventHandler(void *eventHandler) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::registerEventHandler(eventHandler)";
-  // TODO: Store eventHandler handle.
+  eventHandler_ = eventHandler;
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index edf887ebab1d..54d1b8340185 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -18,12 +18,18 @@
 namespace facebook {
 namespace react {
 
+using CreateEventTargetFunction = void *(void *instanceHandle);
+using DispatchEventFunction = void (void *eventHandler, void *eventTarget, std::string type, folly::dynamic payload);
+using ReleaseEventTargetFunction = void (void *eventTarget);
+using ReleaseEventHandlerFunction = void (void *eventHandler);
+
 class FabricUIManager {
 public:
 
 #pragma mark - Native-facing Interface
 
   FabricUIManager(SharedComponentDescriptorRegistry componentDescriptorRegistry);
+  ~FabricUIManager();
 
   /*
    * Sets and gets the UIManager's delegate.
@@ -33,6 +39,22 @@ class FabricUIManager {
   void setDelegate(UIManagerDelegate *delegate);
   UIManagerDelegate *getDelegate();
 
+#pragma mark - Callback Functions
+
+  /*
+   * Registers callback functions.
+   */
+  void setCreateEventTargetFunction(std::function<CreateEventTargetFunction> createEventTargetFunction);
+  void setDispatchEventFunction(std::function<DispatchEventFunction> dispatchEventFunction);
+  void setReleaseEventTargetFunction(std::function<ReleaseEventTargetFunction> releaseEventTargetFunction);
+  void setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction);
+
+#pragma mark - Native-facing Interface
+
+  void *createEventTarget(void *instanceHandle);
+  void dispatchEvent(void *eventTarget, const std::string &type, const folly::dynamic &payload);
+  void releaseEventTarget(void *eventTarget);
+
 #pragma mark - JavaScript/React-facing Interface
 
   SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, InstanceHandle instanceHandle);
@@ -47,8 +69,14 @@ class FabricUIManager {
   void registerEventHandler(void *eventHandler);
 
 private:
+
   SharedComponentDescriptorRegistry componentDescriptorRegistry_;
   UIManagerDelegate *delegate_;
+  void *eventHandler_;
+  std::function<CreateEventTargetFunction> createEventTargetFunction_;
+  std::function<DispatchEventFunction> dispatchEventFunction_;
+  std::function<ReleaseEventTargetFunction> releaseEventTargetFunction_;
+  std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction_;
 };
 
 } // namespace react

From 9b7f6abd877cb8f39a01eae716919ae821436c4d Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Thu, 24 May 2018 18:23:13 -0700
Subject: [PATCH 0660/1109] Fabric: Support for `onLayout` event

Summary: `onLayout` event is fired when some layoutable node got inserted or updated (with changed layout) during commit phase.

Reviewed By: fkgozali

Differential Revision: D8119826

fbshipit-source-id: 831003c88fe5c4358a80328aa715be80e484b52e
---
 ReactCommon/fabric/uimanager/ShadowTree.cpp   | 42 +++++++++++++++++++
 ReactCommon/fabric/uimanager/ShadowTree.h     |  1 +
 ReactCommon/fabric/view/ViewEventHandlers.cpp | 14 +++++++
 ReactCommon/fabric/view/ViewEventHandlers.h   |  7 ++++
 4 files changed, 64 insertions(+)

diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 439369b9e550..4422b43c0c70 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -76,6 +76,8 @@ void ShadowTree::complete(UnsharedRootShadowNode newRootShadowNode) {
   );
 
   if (commit(newRootShadowNode)) {
+    emitLayoutEvents(instructions);
+
     if (delegate_) {
       delegate_->shadowTreeDidCommit(shared_from_this(), instructions);
     }
@@ -93,6 +95,46 @@ bool ShadowTree::commit(const SharedRootShadowNode &newRootShadowNode) {
   return true;
 }
 
+void ShadowTree::emitLayoutEvents(const TreeMutationInstructionList &instructions) {
+  for (auto &&instruction : instructions) {
+    auto &&type = instruction.getType();
+
+    // Only `Insertion` and `Replacement` instructions can affect layout metrics.
+    if (
+        type == TreeMutationInstruction::Insertion ||
+        type == TreeMutationInstruction::Replacement
+    ) {
+      auto &&newShadowNode = instruction.getNewChildNode();
+      auto &&eventHandlers = newShadowNode->getEventHandlers();
+      auto &&viewEventHandlers = std::dynamic_pointer_cast<const ViewEventHandlers>(eventHandlers);
+
+      // Checking if particular shadow node supports `onLayout` event (part of `ViewEventHandlers`).
+      if (viewEventHandlers) {
+        // Now we know that both (old and new) shadow nodes must be `LayoutableShadowNode` subclasses.
+        assert(std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode));
+        // TODO(T29661055): Consider using `std::reinterpret_pointer_cast`.
+        auto &&newLayoutableShadowNode =
+          std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode);
+
+        // In case if we have `oldShadowNode`, we have to check that layout metrics have changed.
+        if (type == TreeMutationInstruction::Replacement) {
+          auto &&oldShadowNode = instruction.getOldChildNode();
+          assert(std::dynamic_pointer_cast<const LayoutableShadowNode>(oldShadowNode));
+          // TODO(T29661055): Consider using `std::reinterpret_pointer_cast`.
+          auto &&oldLayoutableShadowNode =
+            std::dynamic_pointer_cast<const LayoutableShadowNode>(oldShadowNode);
+
+          if (oldLayoutableShadowNode->getLayoutMetrics() == newLayoutableShadowNode->getLayoutMetrics()) {
+            continue;
+          }
+        }
+
+        viewEventHandlers->onLayout(newLayoutableShadowNode->getLayoutMetrics());
+      }
+    }
+  }
+}
+
 #pragma mark - Delegate
 
 void ShadowTree::setDelegate(ShadowTreeDelegate *delegate) {
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.h b/ReactCommon/fabric/uimanager/ShadowTree.h
index e2abea7a37cc..cc20d697d689 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.h
+++ b/ReactCommon/fabric/uimanager/ShadowTree.h
@@ -76,6 +76,7 @@ class ShadowTree final:
   UnsharedRootShadowNode cloneRootShadowNode(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const;
   void complete(UnsharedRootShadowNode newRootShadowNode);
   bool commit(const SharedRootShadowNode &newRootShadowNode);
+  void emitLayoutEvents(const TreeMutationInstructionList &instructions);
 
   const Tag rootTag_;
   SharedRootShadowNode rootShadowNode_;
diff --git a/ReactCommon/fabric/view/ViewEventHandlers.cpp b/ReactCommon/fabric/view/ViewEventHandlers.cpp
index 261f38c3ab18..e673d077efb9 100644
--- a/ReactCommon/fabric/view/ViewEventHandlers.cpp
+++ b/ReactCommon/fabric/view/ViewEventHandlers.cpp
@@ -24,5 +24,19 @@ void ViewEventHandlers::onAccessibilityMagicTap() const {
   dispatchEvent("magicTap");
 }
 
+#pragma mark - Layout
+
+void ViewEventHandlers::onLayout(const LayoutMetrics &layoutMetrics) const {
+  folly::dynamic payload = folly::dynamic::object();
+  auto &&frame = layoutMetrics.frame;
+  payload["layout"] = folly::dynamic::object
+    ("x", frame.origin.x)
+    ("y", frame.origin.y)
+    ("width", frame.size.width)
+    ("height", frame.size.height);
+
+  dispatchEvent("layout", payload);
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewEventHandlers.h b/ReactCommon/fabric/view/ViewEventHandlers.h
index 3e8236b4b15c..e72e41f345b8 100644
--- a/ReactCommon/fabric/view/ViewEventHandlers.h
+++ b/ReactCommon/fabric/view/ViewEventHandlers.h
@@ -9,6 +9,7 @@
 #include <memory>
 
 #include <fabric/core/EventHandlers.h>
+#include <fabric/core/LayoutMetrics.h>
 
 namespace facebook {
 namespace react {
@@ -24,9 +25,15 @@ class ViewEventHandlers:
 
   using EventHandlers::EventHandlers;
 
+#pragma mark - Accessibility
+
   void onAccessibilityAction(const std::string &name) const;
   void onAccessibilityTap() const;
   void onAccessibilityMagicTap() const;
+
+#pragma mark - Layout
+
+  void onLayout(const LayoutMetrics &layoutMetrics) const;
 };
 
 } // namespace react

From 23741470ca706776815f77c757e1dbddb706889e Mon Sep 17 00:00:00 2001
From: Jean Lauliac <jeanlauliac@fb.com>
Date: Fri, 25 May 2018 07:37:42 -0700
Subject: [PATCH 0661/1109] metro-memory-fs: enforce explicit cwd()

Reviewed By: mjesun

Differential Revision: D8137985

fbshipit-source-id: 2154cd758c079678d84f9c371d23bafb9511ec93
---
 local-cli/__mocks__/fs.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/local-cli/__mocks__/fs.js b/local-cli/__mocks__/fs.js
index 0ac81ced62db..3068c0c4e6d7 100644
--- a/local-cli/__mocks__/fs.js
+++ b/local-cli/__mocks__/fs.js
@@ -9,7 +9,7 @@
 
 'use strict';
 
-const fs = new (require('metro-memory-fs'))();
+const fs = new (require('metro-memory-fs'))({cwd: process.cwd});
 
 function setMockFilesystem(object) {
   fs.reset();

From 843cfc3b202433aad9a236b1b623da7c45e1ac15 Mon Sep 17 00:00:00 2001
From: Sujay Jaju <sujay@jajus.com>
Date: Fri, 25 May 2018 10:35:52 -0700
Subject: [PATCH 0662/1109] Fix #18244 Support CRLF build.gradle for Linking

Summary:
Fix for #18244
Add support for build.gradle with CRLF based line ending when running react-native link

<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

`react native link` fails if andorid/app/build.gradle has CRLF based line endings.

Minor 3 character code change.
Ran `react native link` on Windows and Mac to verify.

None

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[CATEGORY] [TYPE] [LOCATION] - MESSAGE

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
 [CLI] [BUGFIX] [local-cli/link/android/patches/makeBuildPath.js] - Support CRLF line endings
Closes https://github.com/facebook/react-native/pull/18245

Differential Revision: D8044774

Pulled By: hramos

fbshipit-source-id: 93fad3db7022784ee949936777aa5ac25e3a64a3
---
 local-cli/link/android/patches/makeBuildPatch.js | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/local-cli/link/android/patches/makeBuildPatch.js b/local-cli/link/android/patches/makeBuildPatch.js
index 58512183fb16..1ee9fb7d5fc6 100644
--- a/local-cli/link/android/patches/makeBuildPatch.js
+++ b/local-cli/link/android/patches/makeBuildPatch.js
@@ -17,7 +17,7 @@ module.exports = function makeBuildPatch(name) {
 
   return {
     installPattern,
-    pattern: /[^ \t]dependencies {\n/,
-    patch: `    compile project(':${normalizedProjectName}')\n`,
+    pattern: /[^ \t]dependencies {(\r\n|\n)/,
+    patch: `    compile project(':${normalizedProjectName}')\n`
   };
 };

From 94393f8652c414806fc861c214ad36e9ac1b6114 Mon Sep 17 00:00:00 2001
From: matheuspiment <matheuspiment@hotmail.com>
Date: Fri, 25 May 2018 10:37:26 -0700
Subject: [PATCH 0663/1109] update android ic_launcher

Summary:
Update the android app icon with the new version.

1. Create a new project using react-native init MyProject
2. Observe the app icon on android

[ANDROID] [MINOR] [ic_launcher.png] - Update the Android app icon with the new version
Closes https://github.com/facebook/react-native/pull/19131

Differential Revision: D8164345

Pulled By: hramos

fbshipit-source-id: 4a2fc308a6b85219561ba99ee8277b5d71dc4bbf
---
 .../src/main/res/mipmap-hdpi/ic_launcher.png  | Bin 3418 -> 3056 bytes
 .../res/mipmap-hdpi/ic_launcher_round.png     | Bin 0 -> 5024 bytes
 .../src/main/res/mipmap-mdpi/ic_launcher.png  | Bin 2206 -> 2096 bytes
 .../res/mipmap-mdpi/ic_launcher_round.png     | Bin 0 -> 2858 bytes
 .../src/main/res/mipmap-xhdpi/ic_launcher.png | Bin 4842 -> 4569 bytes
 .../res/mipmap-xhdpi/ic_launcher_round.png    | Bin 0 -> 7098 bytes
 .../main/res/mipmap-xxhdpi/ic_launcher.png    | Bin 7718 -> 6464 bytes
 .../res/mipmap-xxhdpi/ic_launcher_round.png   | Bin 0 -> 10676 bytes
 .../main/res/mipmap-xxxhdpi/ic_launcher.png   | Bin 0 -> 9250 bytes
 .../res/mipmap-xxxhdpi/ic_launcher_round.png  | Bin 0 -> 15523 bytes
 10 files changed, 0 insertions(+), 0 deletions(-)
 create mode 100644 local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-hdpi/ic_launcher_round.png
 create mode 100644 local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-mdpi/ic_launcher_round.png
 create mode 100644 local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png
 create mode 100644 local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png
 create mode 100644 local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
 create mode 100644 local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png

diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-hdpi/ic_launcher.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-hdpi/ic_launcher.png
index cde69bcccec65160d92116f20ffce4fce0b5245c..a2f5908281d070150700378b64a84c7db1f97aa1 100644
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-hdpi/ic_launcher_round.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-hdpi/ic_launcher_round.png
new file mode 100644
index 0000000000000000000000000000000000000000..1b523998081149a985cef0cdf89045b9ed29964a
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-mdpi/ic_launcher.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-mdpi/ic_launcher.png
index c133a0cbd379f5af6dbf1a899a0293ca5eccfad0..ff10afd6e182edb2b1a63c8f984e9070d9f950ba 100644
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-mdpi/ic_launcher_round.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-mdpi/ic_launcher_round.png
new file mode 100644
index 0000000000000000000000000000000000000000..115a4c768a20c9e13185c17043f4c4d12dd4632a
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xhdpi/ic_launcher.png
index bfa42f0e7b91d006d22352c9ff2f134e504e3c1d..dcd3cd8083358269d6ed7894726283bb9bcbbfea 100644
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xhdpi/ic_launcher_round.png
new file mode 100644
index 0000000000000000000000000000000000000000..459ca609d3ae0d3943ab44cdc27feef9256dc6d7
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxhdpi/ic_launcher.png
index 324e72cdd7480cb983fa1bcc7ce686e51ef87fe7..8ca12fe024be86e868d14e91120a6902f8e88ac6 100644
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.png
new file mode 100644
index 0000000000000000000000000000000000000000..8e19b410a1b15ff180f3dacac19395fe3046cdec
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher.png
new file mode 100644
index 0000000000000000000000000000000000000000..b824ebdd48db917eea2e67a82260a100371f8a24
GIT binary patch
diff --git a/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png b/local-cli/templates/HelloWorld/android/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.png
new file mode 100644
index 0000000000000000000000000000000000000000..4c19a13c239cb67b8a2134ddd5f325db1d2d5bee
GIT binary patch

From 41975f75d96ef4b606b4618461bf24d5db063b77 Mon Sep 17 00:00:00 2001
From: Josh Hargreaves <joshyhargreaves@gmail.com>
Date: Fri, 25 May 2018 10:54:54 -0700
Subject: [PATCH 0664/1109] Disable onKeyPress logic when handler not defined

Summary:
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

There are some bugs surrounding the use of unicode characters that are causing issues with `onKeyPress` on Android: see https://github.com/facebook/react-native/issues/18405#issuecomment-373624413.
We disable the creation and use of `ReactEditTextInputConnectionWrapper` unless the onKeyPress prop is specified, so that this code is 'opt-in' & not a general regression for every use of the TextInput.
N.B. it seems to introduce a lot of unnecessary code complexity to allow for enabling/disabling the onKeyPress events after a InputConnection has been created in `onCreateInputConnection` when the keyboard focusses (a new input connection is created whenever a TextInput gains focus) so I opted not to for simplicity's sake.

Build & debug RNTest app, verify ReactEditTextInputConnectionWrapper code not executed if onKeyPress function not specified.

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

[ANDROID] [BUGFIX] [TextInput] - Disable TextInput onKeyPress event from being fired unless callback specified.
Closes https://github.com/facebook/react-native/pull/18443

Differential Revision: D8149625

Pulled By: hramos

fbshipit-source-id: cdf28141d71cdedd67a6ef350e3a3b955f97e340
---
 .../com/facebook/react/views/textinput/ReactEditText.java  | 7 ++++++-
 .../react/views/textinput/ReactTextInputManager.java       | 5 +++++
 2 files changed, 11 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.java
index 7a9f34e2a6a0..fb4a4d9cfc17 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.java
@@ -81,6 +81,7 @@ public class ReactEditText extends EditText {
   private @Nullable ScrollWatcher mScrollWatcher;
   private final InternalKeyListener mKeyListener;
   private boolean mDetectScrollMovement = false;
+  private boolean mOnKeyPress = false;
   private float mLetterSpacingPt = 0;
 
   private ReactViewBackgroundManager mReactBackgroundManager;
@@ -175,7 +176,7 @@ protected void onScrollChanged(int horiz, int vert, int oldHoriz, int oldVert) {
   public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
     ReactContext reactContext = (ReactContext) getContext();
     InputConnection inputConnection = super.onCreateInputConnection(outAttrs);
-    if (inputConnection != null) {
+    if (inputConnection != null && mOnKeyPress) {
       inputConnection = new ReactEditTextInputConnectionWrapper(inputConnection, reactContext, this);
     }
 
@@ -274,6 +275,10 @@ public void setBlurOnSubmit(@Nullable Boolean blurOnSubmit) {
     mBlurOnSubmit = blurOnSubmit;
   }
 
+  public void setOnKeyPress(boolean onKeyPress) {
+    mOnKeyPress = onKeyPress;
+  }
+
   public boolean getBlurOnSubmit() {
     if (mBlurOnSubmit == null) {
       // Default blurOnSubmit
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
index 2c5013a7e712..fa3c275c6867 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
@@ -308,6 +308,11 @@ public void setOnScroll(final ReactEditText view, boolean onScroll) {
     }
   }
 
+  @ReactProp(name = "onKeyPress", defaultBoolean = false)
+  public void setOnKeyPress(final ReactEditText view, boolean onKeyPress) {
+    view.setOnKeyPress(onKeyPress);
+  }
+
   // Sets the letter spacing as an absolute point size.
   // This extra handling, on top of what ReactBaseTextShadowNode already does, is required for the
   // correct display of spacing in placeholder (hint) text.

From 04028bf2169b01f79bd86ecd6b0d8aa5f99599f1 Mon Sep 17 00:00:00 2001
From: Erik Poort <erik@mediamonks.com>
Date: Fri, 25 May 2018 11:04:46 -0700
Subject: [PATCH 0665/1109] This ensures no illegal cookies are send to okhttp

Summary:
When a website in a ReactNative WebView sets a cookie with an illegal
character, this cookie will automatically be added to any request to the
same domain.

This happens through:
BridgeInterceptor.java (l.84)
ReactCookieJarContainer.java (l.44)
JavaNetCookieJar.java (l.59)
ForwardingCookieHandler.java (l.57)
ForwardingCookieHandler.java (l.168)
CookieManager.java (l.39)

The BridgeInterceptor.java then tries to set a Cookie header, which
validates both keys and values, and then crashes.
okhttp3.6.0 Headers.java (l.320)

This fix will strip illegal characters from any cookie that is being
passed to the okhttp request.

To demonstrate how to crash the app, you can find an example app here:
https://github.com/erikpoort/react-native-test-illegal-cookie

Or you can load the following url into a webview: https://invalidcookietest.us.dev.monkapps.com/
Press the 'Set cookie' button.
Then try to fetch the same url.

[ANDROID] [BREAKING] [ReactCookieJarContainer.java] - I'm filtering cookies containing illegal characters from any request.
Closes https://github.com/facebook/react-native/pull/18203

Differential Revision: D8164302

Pulled By: hramos

fbshipit-source-id: 6e58461df594eb2c7aad4c7ad70b76d12ac09b84
---
 .../network/ReactCookieJarContainer.java      | 14 ++-
 .../network/ReactCookieJarContainerTest.java  | 85 +++++++++++++++++++
 2 files changed, 98 insertions(+), 1 deletion(-)
 create mode 100644 ReactAndroid/src/test/java/com/facebook/react/modules/network/ReactCookieJarContainerTest.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/network/ReactCookieJarContainer.java b/ReactAndroid/src/main/java/com/facebook/react/modules/network/ReactCookieJarContainer.java
index a8436c21875e..370586fa50ca 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/network/ReactCookieJarContainer.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/network/ReactCookieJarContainer.java
@@ -1,5 +1,6 @@
 package com.facebook.react.modules.network;
 
+import java.util.ArrayList;
 import java.util.Collections;
 import java.util.List;
 
@@ -7,6 +8,7 @@
 
 import okhttp3.Cookie;
 import okhttp3.CookieJar;
+import okhttp3.Headers;
 import okhttp3.HttpUrl;
 
 /**
@@ -37,7 +39,17 @@ public void saveFromResponse(HttpUrl url, List<Cookie> cookies) {
   @Override
   public List<Cookie> loadForRequest(HttpUrl url) {
     if (cookieJar != null) {
-      return cookieJar.loadForRequest(url);
+      List<Cookie> cookies = cookieJar.loadForRequest(url);
+      ArrayList<Cookie> validatedCookies = new ArrayList<>();
+      for (Cookie cookie : cookies) {
+        try {
+          Headers.Builder cookieChecker = new Headers.Builder();
+          cookieChecker.add(cookie.name(), cookie.value());
+          validatedCookies.add(cookie);
+        } catch (IllegalArgumentException ignored) {
+        }
+      }
+      return validatedCookies;
     }
     return Collections.emptyList();
   }
diff --git a/ReactAndroid/src/test/java/com/facebook/react/modules/network/ReactCookieJarContainerTest.java b/ReactAndroid/src/test/java/com/facebook/react/modules/network/ReactCookieJarContainerTest.java
new file mode 100644
index 000000000000..b08e514e853d
--- /dev/null
+++ b/ReactAndroid/src/test/java/com/facebook/react/modules/network/ReactCookieJarContainerTest.java
@@ -0,0 +1,85 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.modules.network;
+
+import com.facebook.react.modules.network.ReactCookieJarContainer;
+import okhttp3.Cookie;
+import okhttp3.CookieJar;
+import okhttp3.HttpUrl;
+import java.util.List;
+import java.util.ArrayList;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.powermock.core.classloader.annotations.PowerMockIgnore;
+import org.powermock.core.classloader.annotations.PrepareForTest;
+import org.robolectric.RobolectricTestRunner;
+
+import static org.fest.assertions.api.Assertions.assertThat;
+import static org.mockito.Mockito.any;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
+
+/**
+ * Tests for {@link NetworkingModule}.
+ */
+@PrepareForTest({
+  ReactCookieJarContainer.class
+})
+@RunWith(RobolectricTestRunner.class)
+@PowerMockIgnore({"org.mockito.*", "org.robolectric.*", "android.*"})
+
+public class ReactCookieJarContainerTest {
+
+  @Test
+  public void testMissingJar() throws Exception {
+    ReactCookieJarContainer jarContainer = mock(ReactCookieJarContainer.class);
+    assertThat(jarContainer.loadForRequest(any(HttpUrl.class)).size()).isEqualTo(0);
+  }
+
+  @Test
+  public void testEmptyCookies() throws Exception {
+    ReactCookieJarContainer jarContainer = mock(ReactCookieJarContainer.class);
+    List<Cookie> cookies = new ArrayList<>();
+    when(jarContainer.loadForRequest(any(HttpUrl.class))).thenReturn(cookies);
+    assertThat(jarContainer.loadForRequest(any(HttpUrl.class)).size()).isEqualTo(0);
+  }
+
+  @Test
+  public void testValidCookies() throws Exception {
+    ReactCookieJarContainer jarContainer = new ReactCookieJarContainer();
+    CookieJar cookieJar = mock(CookieJar.class);
+    jarContainer.setCookieJar(cookieJar);
+    List<Cookie> cookies = new ArrayList<>();
+    cookies.add(new Cookie.Builder()
+      .name("valid")
+      .value("valid value")
+      .domain("domain")
+      .build()
+    );
+    when(cookieJar.loadForRequest(any(HttpUrl.class))).thenReturn(cookies);
+    assertThat(jarContainer.loadForRequest(any(HttpUrl.class)).size()).isEqualTo(1);
+  }
+
+  @Test
+  public void testInvalidCookies() throws Exception {
+    ReactCookieJarContainer jarContainer = new ReactCookieJarContainer();
+    CookieJar cookieJar = mock(CookieJar.class);
+    jarContainer.setCookieJar(cookieJar);
+    List<Cookie> cookies = new ArrayList<>();
+    cookies.add(new Cookie.Builder()
+      .name("valid")
+      .value("înválíd välūė")
+      .domain("domain")
+      .build()
+    );
+    when(cookieJar.loadForRequest(any(HttpUrl.class))).thenReturn(cookies);
+    assertThat(jarContainer.loadForRequest(any(HttpUrl.class)).size()).isEqualTo(0);
+  }
+}

From d42697bcf3c9ad4e51c4ef57f01bf4710decf30b Mon Sep 17 00:00:00 2001
From: Andres Suarez <asuarez@fb.com>
Date: Fri, 25 May 2018 11:09:49 -0700
Subject: [PATCH 0666/1109] Run buildifier over BUCK and TARGETS files

Reviewed By: scottrice

Differential Revision: D8163151

fbshipit-source-id: 700a77c09c6ab1bef8fd24a2a3133a4b50e3b3a3
---
 .../src/main/java/com/facebook/debug/holder/BUCK       |  6 +++---
 .../src/main/java/com/facebook/debug/tags/BUCK         |  6 +++---
 .../src/main/java/com/facebook/react/bridge/BUCK       | 10 +++++-----
 .../src/main/java/com/facebook/react/common/BUCK       |  6 +++---
 .../src/main/java/com/facebook/react/fabric/jsc/BUCK   |  8 ++++----
 .../java/com/facebook/react/modules/systeminfo/BUCK    |  6 +++---
 .../src/main/java/com/facebook/react/uimanager/BUCK    | 10 +++++-----
 .../src/main/java/com/facebook/react/views/image/BUCK  |  6 +++---
 .../java/com/facebook/react/views/imagehelper/BUCK     |  6 +++---
 .../src/main/java/com/facebook/common/logging/BUCK     |  2 +-
 .../fbcore/src/test/java/com/facebook/powermock/BUCK   |  2 +-
 .../src/main/libraries/fresco/fresco-react-native/BUCK |  2 +-
 ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK |  2 +-
 .../third-party/android/support/v7/appcompat-orig/BUCK |  6 +++---
 ReactAndroid/src/main/third-party/java/asm/BUCK        |  2 +-
 ReactAndroid/src/main/third-party/java/fest/BUCK       |  2 +-
 ReactAndroid/src/main/third-party/java/junit/BUCK      |  2 +-
 ReactAndroid/src/main/third-party/java/mockito/BUCK    |  2 +-
 .../third-party/java/robolectric3/robolectric/BUCK     |  2 +-
 ReactAndroid/src/main/third-party/java/sqlite/BUCK     |  2 +-
 .../src/test/java/com/facebook/common/logging/BUCK     |  6 +++---
 ReactCommon/jschelpers/BUCK                            |  6 +++---
 22 files changed, 51 insertions(+), 51 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/debug/holder/BUCK b/ReactAndroid/src/main/java/com/facebook/debug/holder/BUCK
index 57a3818bb957..e28e0062d3e4 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/holder/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/debug/holder/BUCK
@@ -3,13 +3,13 @@ load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 rn_android_library(
     name = "holder",
     srcs = glob(["*.java"]),
-    exported_deps = [
-        react_native_dep("java/com/facebook/debug/debugoverlay/model:model"),
-    ],
     visibility = [
         "PUBLIC",
     ],
     deps = [
         react_native_dep("third-party/java/jsr-305:jsr-305"),
     ],
+    exported_deps = [
+        react_native_dep("java/com/facebook/debug/debugoverlay/model:model"),
+    ],
 )
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/tags/BUCK b/ReactAndroid/src/main/java/com/facebook/debug/tags/BUCK
index 7349e68dcdd6..85aaf21d912e 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/tags/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/debug/tags/BUCK
@@ -3,13 +3,13 @@ load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 rn_android_library(
     name = "tags",
     srcs = glob(["*.java"]),
-    exported_deps = [
-        react_native_dep("java/com/facebook/debug/debugoverlay/model:model"),
-    ],
     visibility = [
         "PUBLIC",
     ],
     deps = [
         react_native_dep("third-party/java/jsr-305:jsr-305"),
     ],
+    exported_deps = [
+        react_native_dep("java/com/facebook/debug/debugoverlay/model:model"),
+    ],
 )
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/BUCK b/ReactAndroid/src/main/java/com/facebook/react/bridge/BUCK
index be6ee99800a8..d473c9cf2107 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/BUCK
@@ -3,11 +3,6 @@ load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_dep", "react_native
 rn_android_library(
     name = "bridge",
     srcs = glob(["**/*.java"]),
-    exported_deps = [
-        react_native_dep("java/com/facebook/jni:jni"),
-        react_native_dep("java/com/facebook/proguard/annotations:annotations"),
-        react_native_dep("third-party/java/jsr-330:jsr-330"),
-    ],
     proguard_config = "reactnative.pro",
     provided_deps = [
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
@@ -29,4 +24,9 @@ rn_android_library(
         react_native_target("java/com/facebook/react/module/model:model"),
         react_native_target("java/com/facebook/react/uimanager/common:common"),
     ] + ([react_native_target("jni/react/jni:jni")] if not IS_OSS_BUILD else []),
+    exported_deps = [
+        react_native_dep("java/com/facebook/jni:jni"),
+        react_native_dep("java/com/facebook/proguard/annotations:annotations"),
+        react_native_dep("third-party/java/jsr-330:jsr-330"),
+    ],
 )
diff --git a/ReactAndroid/src/main/java/com/facebook/react/common/BUCK b/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
index 9692208304a6..3cdee118da4f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
@@ -10,9 +10,6 @@ rn_android_library(
         ["**/*.java"],
         excludes = SUB_PROJECTS,
     ),
-    exported_deps = [
-        react_native_dep("java/com/facebook/proguard/annotations:annotations"),
-    ],
     provided_deps = [
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
     ],
@@ -26,6 +23,9 @@ rn_android_library(
         react_native_dep("third-party/java/infer-annotations:infer-annotations"),
         react_native_dep("third-party/java/jsr-305:jsr-305"),
     ],
+    exported_deps = [
+        react_native_dep("java/com/facebook/proguard/annotations:annotations"),
+    ],
 )
 
 rn_android_build_config(
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
index 9373a8400345..18312ac1c7a1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/BUCK
@@ -3,10 +3,6 @@ load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "react_native_dep", "react_native
 rn_android_library(
     name = "jsc",
     srcs = glob(["**/*.java"]),
-    exported_deps = [
-        react_native_dep("java/com/facebook/jni:jni"),
-        react_native_dep("java/com/facebook/proguard/annotations:annotations"),
-    ],
     provided_deps = [
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
     ],
@@ -21,4 +17,8 @@ rn_android_library(
         react_native_target("java/com/facebook/react/fabric:fabric"),
         react_native_target("java/com/facebook/react/fabric/jsc/jni:jni"),
     ],
+    exported_deps = [
+        react_native_dep("java/com/facebook/jni:jni"),
+        react_native_dep("java/com/facebook/proguard/annotations:annotations"),
+    ],
 )
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/BUCK b/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/BUCK
index 6563321a2651..cd24044b70b8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/BUCK
@@ -6,9 +6,6 @@ rn_android_library(
         "AndroidInfoModule.java",
         "ReactNativeVersion.java",
     ],
-    exported_deps = [
-        ":systeminfo-moduleless",
-    ],
     visibility = [
         "PUBLIC",
     ],
@@ -18,6 +15,9 @@ rn_android_library(
         react_native_target("java/com/facebook/react/common:common"),
         react_native_target("java/com/facebook/react/module/annotations:annotations"),
     ],
+    exported_deps = [
+        ":systeminfo-moduleless",
+    ],
 )
 
 rn_android_library(
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
index 6020ec7df202..0a449cfd1384 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
@@ -11,11 +11,6 @@ rn_android_library(
         ],
         excludes = ["DisplayMetricsHolder.java"],
     ),
-    exported_deps = [
-        ":DisplayMetrics",
-        react_native_dep("third-party/java/jsr-305:jsr-305"),
-        react_native_target("java/com/facebook/react/uimanager/common:common"),
-    ],
     provided_deps = [
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
         react_native_dep("third-party/android/support-annotations:android-support-annotations"),
@@ -44,6 +39,11 @@ rn_android_library(
         react_native_target("java/com/facebook/react/uimanager/common:common"),
         react_native_target("res:uimanager"),
     ],
+    exported_deps = [
+        ":DisplayMetrics",
+        react_native_dep("third-party/java/jsr-305:jsr-305"),
+        react_native_target("java/com/facebook/react/uimanager/common:common"),
+    ],
 )
 
 rn_android_library(
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
index 223141141795..ead269cd5d25 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
@@ -26,9 +26,6 @@ rn_android_library(
         ["*.java"],
         excludes = IMAGE_EVENT_FILES,
     ),
-    exported_deps = [
-        ":imageevents",
-    ],
     provided_deps = [
         react_native_dep("third-party/android/support-annotations:android-support-annotations"),
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
@@ -52,4 +49,7 @@ rn_android_library(
         react_native_target("java/com/facebook/react/uimanager/annotations:annotations"),
         react_native_target("java/com/facebook/react/views/imagehelper:withmultisource"),
     ],
+    exported_deps = [
+        ":imageevents",
+    ],
 )
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
index 31b024ea9220..310841c6df43 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
@@ -18,9 +18,6 @@ rn_android_library(
 rn_android_library(
     name = "withmultisource",
     srcs = ["MultiSourceHelper.java"],
-    exported_deps = [
-        ":imagehelper",
-    ],
     visibility = [
         "PUBLIC",
     ],
@@ -29,4 +26,7 @@ rn_android_library(
         react_native_dep("third-party/java/infer-annotations:infer-annotations"),
         react_native_dep("third-party/java/jsr-305:jsr-305"),
     ],
+    exported_deps = [
+        ":imagehelper",
+    ],
 )
diff --git a/ReactAndroid/src/main/libraries/fbcore/src/main/java/com/facebook/common/logging/BUCK b/ReactAndroid/src/main/libraries/fbcore/src/main/java/com/facebook/common/logging/BUCK
index 4f5bc6c890ec..98e1cdf542da 100644
--- a/ReactAndroid/src/main/libraries/fbcore/src/main/java/com/facebook/common/logging/BUCK
+++ b/ReactAndroid/src/main/libraries/fbcore/src/main/java/com/facebook/common/logging/BUCK
@@ -2,8 +2,8 @@ load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 
 rn_android_library(
     name = "logging",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         react_native_dep("libraries/fresco/fresco-react-native:fbcore"),
     ],
-    visibility = ["//ReactAndroid/..."],
 )
diff --git a/ReactAndroid/src/main/libraries/fbcore/src/test/java/com/facebook/powermock/BUCK b/ReactAndroid/src/main/libraries/fbcore/src/test/java/com/facebook/powermock/BUCK
index a34d1224a165..c4360ce160f0 100644
--- a/ReactAndroid/src/main/libraries/fbcore/src/test/java/com/facebook/powermock/BUCK
+++ b/ReactAndroid/src/main/libraries/fbcore/src/test/java/com/facebook/powermock/BUCK
@@ -2,6 +2,7 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_prebuilt_jar")
 
 rn_android_library(
     name = "powermock",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":javassist",
         ":mockito-all",
@@ -16,7 +17,6 @@ rn_android_library(
         ":xpp3",
         ":xstream",
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_prebuilt_jar(
diff --git a/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK b/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
index e4a46ecc3f86..db1216a0fea1 100644
--- a/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
+++ b/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
@@ -26,12 +26,12 @@ remote_file(
 
 rn_android_library(
     name = "imagepipeline",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":bolts",
         ":imagepipeline-base",
         ":imagepipeline-core",
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_android_prebuilt_aar(
diff --git a/ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK b/ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK
index 68ef47370f5d..748dfff536a6 100644
--- a/ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK
+++ b/ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK
@@ -2,11 +2,11 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_android_prebuilt_aar",
 
 rn_android_library(
     name = "textlayoutbuilder",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":staticlayoutproxy",
         ":textlayoutbuilder-base",
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_android_prebuilt_aar(
diff --git a/ReactAndroid/src/main/third-party/android/support/v7/appcompat-orig/BUCK b/ReactAndroid/src/main/third-party/android/support/v7/appcompat-orig/BUCK
index af13e77e107c..98aed703dd10 100644
--- a/ReactAndroid/src/main/third-party/android/support/v7/appcompat-orig/BUCK
+++ b/ReactAndroid/src/main/third-party/android/support/v7/appcompat-orig/BUCK
@@ -11,15 +11,15 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_android_resource", "rn_
 
 rn_android_library(
     name = "appcompat",
-    exported_deps = [
-        ":classes-for-react-native",
-    ],
     visibility = [
         "PUBLIC",
     ],
     deps = [
         ":res-for-appcompat",
     ],
+    exported_deps = [
+        ":classes-for-react-native",
+    ],
 )
 
 # still used by appcompat library internally, so we need both during the build
diff --git a/ReactAndroid/src/main/third-party/java/asm/BUCK b/ReactAndroid/src/main/third-party/java/asm/BUCK
index c88207bc2044..856081a83fd0 100644
--- a/ReactAndroid/src/main/third-party/java/asm/BUCK
+++ b/ReactAndroid/src/main/third-party/java/asm/BUCK
@@ -2,6 +2,7 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_prebuilt_jar")
 
 rn_android_library(
     name = "asm",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":asm-analysis",
         ":asm-commons",
@@ -9,7 +10,6 @@ rn_android_library(
         ":asm-tree",
         ":asm-util",
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_prebuilt_jar(
diff --git a/ReactAndroid/src/main/third-party/java/fest/BUCK b/ReactAndroid/src/main/third-party/java/fest/BUCK
index 6c87cbafd5cd..576ff7eddd53 100644
--- a/ReactAndroid/src/main/third-party/java/fest/BUCK
+++ b/ReactAndroid/src/main/third-party/java/fest/BUCK
@@ -2,11 +2,11 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_prebuilt_jar")
 
 rn_android_library(
     name = "fest",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":fest-core",
         ":fest-util",
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_prebuilt_jar(
diff --git a/ReactAndroid/src/main/third-party/java/junit/BUCK b/ReactAndroid/src/main/third-party/java/junit/BUCK
index 923f3b75f553..fd5e5c1a32a8 100644
--- a/ReactAndroid/src/main/third-party/java/junit/BUCK
+++ b/ReactAndroid/src/main/third-party/java/junit/BUCK
@@ -2,11 +2,11 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_prebuilt_jar")
 
 rn_android_library(
     name = "junit",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":hamcrest",
         ":junit-core",
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_prebuilt_jar(
diff --git a/ReactAndroid/src/main/third-party/java/mockito/BUCK b/ReactAndroid/src/main/third-party/java/mockito/BUCK
index 65627a724c1e..70db14c6ac2e 100644
--- a/ReactAndroid/src/main/third-party/java/mockito/BUCK
+++ b/ReactAndroid/src/main/third-party/java/mockito/BUCK
@@ -2,11 +2,11 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_prebuilt_jar")
 
 rn_android_library(
     name = "mockito",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":mockito-core",
         ":objenesis",
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_prebuilt_jar(
diff --git a/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK b/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
index d3338e4aa630..87946208aa5d 100644
--- a/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
+++ b/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
@@ -2,6 +2,7 @@ load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library", "rn_pre
 
 rn_android_library(
     name = "robolectric",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":android-all-4.1.2_r1-robolectric-0",
         ":bouncycastle",
@@ -17,7 +18,6 @@ rn_android_library(
         react_native_dep("third-party/java/asm:asm"),
         react_native_dep("third-party/java/sqlite:sqlite"),
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_prebuilt_jar(
diff --git a/ReactAndroid/src/main/third-party/java/sqlite/BUCK b/ReactAndroid/src/main/third-party/java/sqlite/BUCK
index f7889715101a..419bc9ed4f70 100644
--- a/ReactAndroid/src/main/third-party/java/sqlite/BUCK
+++ b/ReactAndroid/src/main/third-party/java/sqlite/BUCK
@@ -2,10 +2,10 @@ load("//ReactNative:DEFS.bzl", "rn_android_library", "rn_prebuilt_jar")
 
 rn_android_library(
     name = "sqlite",
+    visibility = ["//ReactAndroid/..."],
     exported_deps = [
         ":sqlite4java",
     ],
-    visibility = ["//ReactAndroid/..."],
 )
 
 rn_prebuilt_jar(
diff --git a/ReactAndroid/src/test/java/com/facebook/common/logging/BUCK b/ReactAndroid/src/test/java/com/facebook/common/logging/BUCK
index bde102da955d..4fd90a102b37 100644
--- a/ReactAndroid/src/test/java/com/facebook/common/logging/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/common/logging/BUCK
@@ -3,13 +3,13 @@ load("//ReactNative:DEFS.bzl", "react_native_dep", "rn_android_library")
 rn_android_library(
     name = "logging",
     srcs = glob(["**/*.java"]),
-    exported_deps = [
-        react_native_dep("libraries/fbcore/src/main/java/com/facebook/common/logging:logging"),
-    ],
     visibility = [
         "PUBLIC",
     ],
     deps = [
         react_native_dep("third-party/java/jsr-305:jsr-305"),
     ],
+    exported_deps = [
+        react_native_dep("libraries/fbcore/src/main/java/com/facebook/common/logging:logging"),
+    ],
 )
diff --git a/ReactCommon/jschelpers/BUCK b/ReactCommon/jschelpers/BUCK
index 3a3bbc41d5d3..9f3c8261714c 100644
--- a/ReactCommon/jschelpers/BUCK
+++ b/ReactCommon/jschelpers/BUCK
@@ -34,9 +34,6 @@ rn_xplat_cxx_library(
         "-fvisibility=hidden",
         "-std=c++1y",
     ],
-    exported_deps = [
-        react_native_xplat_target("privatedata:privatedata"),
-    ],
     fbandroid_deps = ANDROID_JSC_INTERNAL_DEPS,
     fbobjc_deps = APPLE_JSC_INTERNAL_DEPS,
     force_static = True,
@@ -49,6 +46,9 @@ rn_xplat_cxx_library(
         "xplat//third-party/glog:glog",
         react_native_xplat_target("privatedata:privatedata"),
     ],
+    exported_deps = [
+        react_native_xplat_target("privatedata:privatedata"),
+    ],
 )
 
 rn_xplat_cxx_library(

From 4fd594674f3d8a333f3e72d483c2b892b26c6a8f Mon Sep 17 00:00:00 2001
From: "glevi@fb.com" <glevi@fb.com>
Date: Fri, 25 May 2018 13:25:15 -0700
Subject: [PATCH 0667/1109] Upgrade xplat/js to Flow v0.73

Reviewed By: pakoito

Differential Revision: D8153280

fbshipit-source-id: 193b35f12ecfb002283912c29ce08319b52802e6
---
 .flowconfig                                | 2 +-
 local-cli/templates/HelloWorld/_flowconfig | 2 +-
 package.json                               | 2 +-
 3 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index e5367e543cda..0d576609315e 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -69,4 +69,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.72.0
+^0.73.0
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 83ff2c6bd64f..49487641bc41 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -51,4 +51,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.72.0
+^0.73.0
diff --git a/package.json b/package.json
index 7a4741b2e302..ce738d0198ed 100644
--- a/package.json
+++ b/package.json
@@ -213,7 +213,7 @@
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.6.1",
     "eslint-plugin-react-native": "^3.2.1",
-    "flow-bin": "^0.72.0",
+    "flow-bin": "^0.73.0",
     "jest": "23.0.0-charlie.1",
     "jest-junit": "3.7.0",
     "prettier": "1.12.1",

From 488a4c7e1c86ac5900ff9194106511fbf5a8e3cb Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Fri, 25 May 2018 14:59:24 -0700
Subject: [PATCH 0668/1109] Fix VirtualizedSectionList:ItemWithSeparators

Reviewed By: yungsters

Differential Revision: D8021407

fbshipit-source-id: 480547d867eda476fe6ddf4af74072ad1851a427
---
 Libraries/Lists/VirtualizedSectionList.js | 48 ++++++++++++++++-------
 1 file changed, 33 insertions(+), 15 deletions(-)

diff --git a/Libraries/Lists/VirtualizedSectionList.js b/Libraries/Lists/VirtualizedSectionList.js
index 6da08dc1ab66..cfedc61b0919 100644
--- a/Libraries/Lists/VirtualizedSectionList.js
+++ b/Libraries/Lists/VirtualizedSectionList.js
@@ -378,25 +378,40 @@ class VirtualizedSectionList<SectionT: SectionBase> extends React.PureComponent<
   };
 }
 
-type ItemWithSeparatorProps = {
-  LeadingSeparatorComponent: ?React.ComponentType<*>,
-  SeparatorComponent: ?React.ComponentType<*>,
+type ItemWithSeparatorCommonProps = $ReadOnly<{|
+  leadingItem: ?Item,
+  leadingSection: ?Object,
+  section: Object,
+  trailingItem: ?Item,
+  trailingSection: ?Object,
+|}>;
+
+type ItemWithSeparatorProps = $ReadOnly<{|
+  ...ItemWithSeparatorCommonProps,
+  LeadingSeparatorComponent: ?React.ComponentType<any>,
+  SeparatorComponent: ?React.ComponentType<any>,
   cellKey: string,
   index: number,
   item: Item,
   onUpdateSeparator: (cellKey: string, newProps: Object) => void,
   prevCellKey?: ?string,
   renderItem: Function,
-  section: Object,
-  leadingItem: ?Item,
-  leadingSection: ?Object,
-  trailingItem: ?Item,
-  trailingSection: ?Object,
+|}>;
+
+type ItemWithSeparatorState = {
+  separatorProps: $ReadOnly<{|
+    highlighted: false,
+    ...ItemWithSeparatorCommonProps,
+  |}>,
+  leadingSeparatorProps: $ReadOnly<{|
+    highlighted: false,
+    ...ItemWithSeparatorCommonProps,
+  |}>,
 };
 
 class ItemWithSeparator extends React.Component<
   ItemWithSeparatorProps,
-  $FlowFixMeState,
+  ItemWithSeparatorState,
 > {
   state = {
     separatorProps: {
@@ -430,7 +445,7 @@ class ItemWithSeparator extends React.Component<
     },
     updateProps: (select: 'leading' | 'trailing', newProps: Object) => {
       const {LeadingSeparatorComponent, cellKey, prevCellKey} = this.props;
-      if (select === 'leading' && LeadingSeparatorComponent) {
+      if (select === 'leading' && LeadingSeparatorComponent != null) {
         this.setState(state => ({
           leadingSeparatorProps: {...state.leadingSeparatorProps, ...newProps},
         }));
@@ -443,10 +458,13 @@ class ItemWithSeparator extends React.Component<
     },
   };
 
-  UNSAFE_componentWillReceiveProps(props: ItemWithSeparatorProps) {
-    this.setState(state => ({
+  static getDerivedStateFromProps(
+    props: ItemWithSeparatorProps,
+    prevState: ItemWithSeparatorState,
+  ): ?ItemWithSeparatorState  {
+    return {
       separatorProps: {
-        ...this.state.separatorProps,
+        ...prevState.separatorProps,
         leadingItem: props.item,
         leadingSection: props.leadingSection,
         section: props.section,
@@ -454,14 +472,14 @@ class ItemWithSeparator extends React.Component<
         trailingSection: props.trailingSection,
       },
       leadingSeparatorProps: {
-        ...this.state.leadingSeparatorProps,
+        ...prevState.leadingSeparatorProps,
         leadingItem: props.leadingItem,
         leadingSection: props.leadingSection,
         section: props.section,
         trailingItem: props.item,
         trailingSection: props.trailingSection,
       },
-    }));
+    };
   }
 
   updateSeparatorProps(newProps: Object) {

From 26a1eba1cef853b0dab7aad5731699c06d36b781 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Fri, 25 May 2018 14:59:28 -0700
Subject: [PATCH 0669/1109] VirtualizedSectionList

Reviewed By: yungsters

Differential Revision: D8021463

fbshipit-source-id: 8b65585776cf41e194418d127bca85dbe47ea659
---
 Libraries/Lists/VirtualizedSectionList.js | 106 +++++++++++-----------
 1 file changed, 51 insertions(+), 55 deletions(-)

diff --git a/Libraries/Lists/VirtualizedSectionList.js b/Libraries/Lists/VirtualizedSectionList.js
index cfedc61b0919..63c7d9ecdcb6 100644
--- a/Libraries/Lists/VirtualizedSectionList.js
+++ b/Libraries/Lists/VirtualizedSectionList.js
@@ -37,12 +37,12 @@ type SectionBase = {
       updateProps: (select: 'leading' | 'trailing', newProps: Object) => void,
     },
   }) => ?React.Element<any>,
-  ItemSeparatorComponent?: ?React.ComponentType<*>,
+  ItemSeparatorComponent?: ?React.ComponentType<any>,
   keyExtractor?: (item: SectionItem, index: ?number) => string,
 
   // TODO: support more optional/override props
-  // FooterComponent?: ?ReactClass<*>,
-  // HeaderComponent?: ?ReactClass<*>,
+  // FooterComponent?: ?ReactClass<any>,
+  // HeaderComponent?: ?ReactClass<any>,
   // onViewableItemsChanged?: ({viewableItems: Array<ViewToken>, changed: Array<ViewToken>}) => void,
 };
 
@@ -54,11 +54,11 @@ type OptionalProps<SectionT: SectionBase> = {
   /**
    * Rendered after the last item in the last section.
    */
-  ListFooterComponent?: ?(React.ComponentType<*> | React.Element<any>),
+  ListFooterComponent?: ?(React.ComponentType<any> | React.Element<any>),
   /**
    * Rendered at the very beginning of the list.
    */
-  ListHeaderComponent?: ?(React.ComponentType<*> | React.Element<any>),
+  ListHeaderComponent?: ?(React.ComponentType<any> | React.Element<any>),
   /**
    * Default renderer for every item in every section.
    */
@@ -84,11 +84,11 @@ type OptionalProps<SectionT: SectionBase> = {
    * Rendered at the bottom of every Section, except the very last one, in place of the normal
    * ItemSeparatorComponent.
    */
-  SectionSeparatorComponent?: ?React.ComponentType<*>,
+  SectionSeparatorComponent?: ?React.ComponentType<any>,
   /**
    * Rendered at the bottom of every Item except the very last one in the last section.
    */
-  ItemSeparatorComponent?: ?React.ComponentType<*>,
+  ItemSeparatorComponent?: ?React.ComponentType<any>,
   /**
    * Warning: Virtualization can drastically improve memory consumption for long lists, but trashes
    * the state of items when they scroll out of the render window, so make sure all relavent data is
@@ -101,7 +101,7 @@ type OptionalProps<SectionT: SectionBase> = {
    * If provided, a standard RefreshControl will be added for "Pull to Refresh" functionality. Make
    * sure to also set the `refreshing` prop correctly.
    */
-  onRefresh?: ?Function,
+  onRefresh?: ?() => void,
   /**
    * Called when the viewability of rows changes, as defined by the
    * `viewabilityConfig` prop.
@@ -134,10 +134,6 @@ class VirtualizedSectionList<SectionT: SectionBase> extends React.PureComponent<
   Props<SectionT>,
   State,
 > {
-  props: Props<SectionT>;
-
-  state: State;
-
   static defaultProps: DefaultProps = {
     ...VirtualizedList.defaultProps,
     data: [],
@@ -164,6 +160,48 @@ class VirtualizedSectionList<SectionT: SectionBase> extends React.PureComponent<
     return this._listRef;
   }
 
+  constructor(props: Props<SectionT>, context: Object) {
+    super(props, context);
+    this.state = this._computeState(props);
+  }
+
+  UNSAFE_componentWillReceiveProps(nextProps: Props<SectionT>) {
+    this.setState(this._computeState(nextProps));
+  }
+
+  _computeState(props: Props<SectionT>): State {
+    const offset = props.ListHeaderComponent ? 1 : 0;
+    const stickyHeaderIndices = [];
+    const itemCount = props.sections.reduce((v, section) => {
+      stickyHeaderIndices.push(v + offset);
+      return v + section.data.length + 2; // Add two for the section header and footer.
+    }, 0);
+
+    return {
+      childProps: {
+        ...props,
+        renderItem: this._renderItem,
+        ItemSeparatorComponent: undefined, // Rendered with renderItem
+        data: props.sections,
+        getItemCount: () => itemCount,
+        getItem,
+        keyExtractor: this._keyExtractor,
+        onViewableItemsChanged: props.onViewableItemsChanged
+          ? this._onViewableItemsChanged
+          : undefined,
+        stickyHeaderIndices: props.stickySectionHeadersEnabled
+          ? stickyHeaderIndices
+          : undefined,
+      },
+    };
+  }
+
+  render() {
+    return (
+      <VirtualizedList {...this.state.childProps} ref={this._captureRef} />
+    );
+  }
+
   _keyExtractor = (item: Item, index: number) => {
     const info = this._subExtractor(index);
     return (info && info.key) || String(index);
@@ -307,7 +345,7 @@ class VirtualizedSectionList<SectionT: SectionBase> extends React.PureComponent<
   _getSeparatorComponent(
     index: number,
     info?: ?Object,
-  ): ?React.ComponentType<*> {
+  ): ?React.ComponentType<any> {
     info = info || this._subExtractor(index);
     if (!info) {
       return null;
@@ -326,48 +364,6 @@ class VirtualizedSectionList<SectionT: SectionBase> extends React.PureComponent<
     return null;
   }
 
-  _computeState(props: Props<SectionT>): State {
-    const offset = props.ListHeaderComponent ? 1 : 0;
-    const stickyHeaderIndices = [];
-    const itemCount = props.sections.reduce((v, section) => {
-      stickyHeaderIndices.push(v + offset);
-      return v + section.data.length + 2; // Add two for the section header and footer.
-    }, 0);
-
-    return {
-      childProps: {
-        ...props,
-        renderItem: this._renderItem,
-        ItemSeparatorComponent: undefined, // Rendered with renderItem
-        data: props.sections,
-        getItemCount: () => itemCount,
-        getItem,
-        keyExtractor: this._keyExtractor,
-        onViewableItemsChanged: props.onViewableItemsChanged
-          ? this._onViewableItemsChanged
-          : undefined,
-        stickyHeaderIndices: props.stickySectionHeadersEnabled
-          ? stickyHeaderIndices
-          : undefined,
-      },
-    };
-  }
-
-  constructor(props: Props<SectionT>, context: Object) {
-    super(props, context);
-    this.state = this._computeState(props);
-  }
-
-  UNSAFE_componentWillReceiveProps(nextProps: Props<SectionT>) {
-    this.setState(this._computeState(nextProps));
-  }
-
-  render() {
-    return (
-      <VirtualizedList {...this.state.childProps} ref={this._captureRef} />
-    );
-  }
-
   _cellRefs = {};
   _listRef: VirtualizedList;
   _captureRef = ref => {

From a90d0e3614c467c33cf85bcbe65be71903d5aecc Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Fri, 25 May 2018 14:59:34 -0700
Subject: [PATCH 0670/1109] fixup FlatList

Summary:
StrictMode compliance is important for Async Rendering and other Future Tech(tm).

Also clean up some lint.

== Test Plan ==
* No more StrictMode warnings for `FlatList` (`VirtualizedList` is another story....).
* props warnings still show up when appropriate.

Reviewed By: sophiebits

Differential Revision: D8026333

fbshipit-source-id: e6fa2f02d546b883df6f3cff8776c26c6ef91bc9
---
 Libraries/Lists/FlatList.js                   | 66 ++++++++++---------
 .../__snapshots__/FlatList-test.js.snap       | 27 +++-----
 2 files changed, 44 insertions(+), 49 deletions(-)

diff --git a/Libraries/Lists/FlatList.js b/Libraries/Lists/FlatList.js
index cb909bbe74c1..c9b1b94c9104 100644
--- a/Libraries/Lists/FlatList.js
+++ b/Libraries/Lists/FlatList.js
@@ -14,6 +14,7 @@ const React = require('React');
 const View = require('View');
 const VirtualizedList = require('VirtualizedList');
 const ListView = require('ListView');
+const StyleSheet = require('StyleSheet');
 
 const invariant = require('fbjs/lib/invariant');
 
@@ -421,41 +422,15 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
     }
   }
 
-  setNativeProps(props: Object) {
+  setNativeProps(props: {[string]: mixed}) {
     if (this._listRef) {
       this._listRef.setNativeProps(props);
     }
   }
 
-  UNSAFE_componentWillMount() {
-    this._checkProps(this.props);
-  }
-
-  UNSAFE_componentWillReceiveProps(nextProps: Props<ItemT>) {
-    invariant(
-      nextProps.numColumns === this.props.numColumns,
-      'Changing numColumns on the fly is not supported. Change the key prop on FlatList when ' +
-        'changing the number of columns to force a fresh render of the component.',
-    );
-    invariant(
-      nextProps.onViewableItemsChanged === this.props.onViewableItemsChanged,
-      'Changing onViewableItemsChanged on the fly is not supported',
-    );
-    invariant(
-      nextProps.viewabilityConfig === this.props.viewabilityConfig,
-      'Changing viewabilityConfig on the fly is not supported',
-    );
-    invariant(
-      nextProps.viewabilityConfigCallbackPairs ===
-        this.props.viewabilityConfigCallbackPairs,
-      'Changing viewabilityConfigCallbackPairs on the fly is not supported',
-    );
-
-    this._checkProps(nextProps);
-  }
-
-  constructor(props: Props<*>) {
+  constructor(props: Props<ItemT>) {
     super(props);
+    this._checkProps(this.props);
     if (this.props.viewabilityConfigCallbackPairs) {
       this._virtualizedListPairs = this.props.viewabilityConfigCallbackPairs.map(
         pair => ({
@@ -478,6 +453,29 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
     }
   }
 
+  componentDidUpdate(prevProps: Props<ItemT>) {
+    invariant(
+      prevProps.numColumns === this.props.numColumns,
+      'Changing numColumns on the fly is not supported. Change the key prop on FlatList when ' +
+        'changing the number of columns to force a fresh render of the component.',
+    );
+    invariant(
+      prevProps.onViewableItemsChanged === this.props.onViewableItemsChanged,
+      'Changing onViewableItemsChanged on the fly is not supported',
+    );
+    invariant(
+      prevProps.viewabilityConfig === this.props.viewabilityConfig,
+      'Changing viewabilityConfig on the fly is not supported',
+    );
+    invariant(
+      prevProps.viewabilityConfigCallbackPairs ===
+        this.props.viewabilityConfigCallbackPairs,
+      'Changing viewabilityConfigCallbackPairs on the fly is not supported',
+    );
+
+    this._checkProps(this.props);
+  }
+
   _hasWarnedLegacy = false;
   _listRef: null | VirtualizedList | ListView | MetroListView;
   _virtualizedListPairs: Array<ViewabilityConfigCallbackPair> = [];
@@ -537,7 +535,9 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
       const ret = [];
       for (let kk = 0; kk < numColumns; kk++) {
         const item = data[index * numColumns + kk];
-        item && ret.push(item);
+        if (item != null) {
+          ret.push(item);
+        }
       }
       return ret;
     } else {
@@ -614,7 +614,7 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
         'Expected array of items with numColumns > 1',
       );
       return (
-        <View style={[{flexDirection: 'row'}, columnWrapperStyle]}>
+        <View style={StyleSheet.compose(styles.row, columnWrapperStyle)}>
           {item.map((it, kk) => {
             const element = renderItem({
               item: it,
@@ -661,4 +661,8 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
   }
 }
 
+const styles = StyleSheet.create({
+  row: {flexDirection: 'row'},
+});
+
 module.exports = FlatList;
diff --git a/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap b/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
index 837ef99b1f12..525ad54eea84 100644
--- a/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
+++ b/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
@@ -72,12 +72,9 @@ exports[`FlatList renders all the bells and whistles 1`] = `
     >
       <View
         style={
-          Array [
-            Object {
-              "flexDirection": "row",
-            },
-            undefined,
-          ]
+          Object {
+            "flexDirection": "row",
+          }
         }
       >
         <item
@@ -95,12 +92,9 @@ exports[`FlatList renders all the bells and whistles 1`] = `
     >
       <View
         style={
-          Array [
-            Object {
-              "flexDirection": "row",
-            },
-            undefined,
-          ]
+          Object {
+            "flexDirection": "row",
+          }
         }
       >
         <item
@@ -118,12 +112,9 @@ exports[`FlatList renders all the bells and whistles 1`] = `
     >
       <View
         style={
-          Array [
-            Object {
-              "flexDirection": "row",
-            },
-            undefined,
-          ]
+          Object {
+            "flexDirection": "row",
+          }
         }
       >
         <item

From 84c965f0851dd4ca832c18a463e4577764c54244 Mon Sep 17 00:00:00 2001
From: Chirag Shah <shahchirag1709@gmail.com>
Date: Sat, 26 May 2018 20:48:50 -0700
Subject: [PATCH 0671/1109] Typo fixes

Summary:
Spotted a few typos while going through the source code

No tests are required

[INTERNAL] [MINOR] [Webview] - Fixed typos
Closes https://github.com/facebook/react-native/pull/19462

Differential Revision: D8176774

Pulled By: hramos

fbshipit-source-id: f1a9024b210e1a935dcdccd7e27daedb71d794bc
---
 Libraries/Components/WebView/WebView.android.js | 4 ++--
 Libraries/Components/WebView/WebView.ios.js     | 2 +-
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/Libraries/Components/WebView/WebView.android.js b/Libraries/Components/WebView/WebView.android.js
index afc69bfcb912..0d1c7b0c90d9 100644
--- a/Libraries/Components/WebView/WebView.android.js
+++ b/Libraries/Components/WebView/WebView.android.js
@@ -181,7 +181,7 @@ class WebView extends React.Component {
      * List of origin strings to allow being navigated to. The strings allow
      * wildcards and get matched against *just* the origin (not the full URL).
      * If the user taps to navigate to a new page but the new page is not in
-     * this whitelist, the URL will be oppened by the Android OS.
+     * this whitelist, the URL will be opened by the Android OS.
      * The default whitelisted origins are "http://*" and "https://*".
      */
     originWhitelist: PropTypes.arrayOf(PropTypes.string),
@@ -225,7 +225,7 @@ class WebView extends React.Component {
        */
       props: PropTypes.object,
       /*
-       * Set the ViewManager to use for communcation with the native side.
+       * Set the ViewManager to use for communication with the native side.
        * @platform ios
        */
       viewManager: PropTypes.object,
diff --git a/Libraries/Components/WebView/WebView.ios.js b/Libraries/Components/WebView/WebView.ios.js
index 8c0630c2c0e7..8d78103d7013 100644
--- a/Libraries/Components/WebView/WebView.ios.js
+++ b/Libraries/Components/WebView/WebView.ios.js
@@ -388,7 +388,7 @@ class WebView extends React.Component {
        */
       props: PropTypes.object,
       /*
-       * Set the ViewManager to use for communcation with the native side.
+       * Set the ViewManager to use for communication with the native side.
        * @platform ios
        */
       viewManager: PropTypes.object,

From 57e7556b8db61e5fcc3ccea56c1b163b82a091a6 Mon Sep 17 00:00:00 2001
From: Kenneth Geisshirt <geisshirt@gmail.com>
Date: Sun, 27 May 2018 14:44:18 -0700
Subject: [PATCH 0672/1109] Fixing link to Android build guide.

Summary:
While browsing the repository, I noticed that the link to how to build for Android has changed. It's a very simple fix.

Verifying that the URL is correct.

None.

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[DOCS] [BUGFIX] [ReactAndroid/README.md] - Incorrect URL
Closes https://github.com/facebook/react-native/pull/19450

Differential Revision: D8178077

Pulled By: hramos

fbshipit-source-id: 388c35b5322416333681d66ef1b8ca42e9e83151
---
 ReactAndroid/README.md | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/README.md b/ReactAndroid/README.md
index 1a5587481b94..d96e2bf1184d 100644
--- a/ReactAndroid/README.md
+++ b/ReactAndroid/README.md
@@ -1,6 +1,6 @@
 # Building React Native for Android
 
-See the [docs on the website](https://facebook.github.io/react-native/docs/android-building-from-source.html).
+See the [docs on the website](https://facebook.github.io/react-native/docs/building-from-source.html#android).
 
 # Running tests
 

From 957ef606b97769137fc32febd4043a50d3ab22d0 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 29 May 2018 11:20:04 -0700
Subject: [PATCH 0673/1109] Adding `Wrapper` suffix to `EventHandler` and
 `EventHandler` type names

Summary:
It's maybe not so important/crucial, but this thing bothers me a lot.
We use raw opaque `EventTarget`, `InstanceHandle` and `EventHandler` pointers in application layer quite a lot and we don't have any kind of type-safety here. I believe all those opaque types should be represented as named scalar types which compiler at least can differentiate at compile time.
So I propose introducing named aliases for them which will point to particular empty `struct`s. This will allow us to tag types properly in all functions and methods and ensure that we pass right values as right arguments.
Again, they are *just aliases*, which are effectively still `void *`, no any additional logic or names are involved.

Unfortunately, those nice type names are already taken by `JSIFabricUIManager` local anonymous namespace (even if they are inside anonymous namespace we cannot use them https://stackoverflow.com/questions/3673353/anonymous-namespace-ambiguity).  I think it's fair to rename them because... it's local. And we already use `Wrapper` suffix for them anyways.

Reviewed By: fkgozali

Differential Revision: D8181151

fbshipit-source-id: 9b55b43fb671a56b32a862ac54f78d528e1188ce
---
 ReactCommon/fabric/core/events/EventPrimitives.h | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/ReactCommon/fabric/core/events/EventPrimitives.h b/ReactCommon/fabric/core/events/EventPrimitives.h
index ba12b23b1be0..46b71579630c 100644
--- a/ReactCommon/fabric/core/events/EventPrimitives.h
+++ b/ReactCommon/fabric/core/events/EventPrimitives.h
@@ -22,5 +22,11 @@ enum class EventPriority {
   Deferred = AsynchronousBatched,
 };
 
+// `InstanceHandler`, `EventTarget`, and `EventHandler` are all opaque
+// raw pointers. We use `struct {} *` trick to differentiate them in compiler's
+// eyes to ensure type safety.
+using EventTarget = struct {} *;
+using EventHandler = struct {} *;
+
 } // namespace react
 } // namespace facebook

From 2bf47559b5ad69b9b8b8cd960f71f3ba831e3ed2 Mon Sep 17 00:00:00 2001
From: Dan Zimmerman <danzimm@fb.com>
Date: Tue, 29 May 2018 12:07:07 -0700
Subject: [PATCH 0674/1109] Export JSExecutor

Reviewed By: rzito

Differential Revision: D8187754

fbshipit-source-id: e0da3781e2b3e24cef04086d15e3f5394e059d30
---
 ReactCommon/cxxreact/JSExecutor.h | 6 +++++-
 1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/cxxreact/JSExecutor.h b/ReactCommon/cxxreact/JSExecutor.h
index 35338cd0876b..e699c79b2266 100644
--- a/ReactCommon/cxxreact/JSExecutor.h
+++ b/ReactCommon/cxxreact/JSExecutor.h
@@ -8,6 +8,10 @@
 #include <cxxreact/NativeModule.h>
 #include <folly/dynamic.h>
 
+#ifndef RN_EXPORT
+#define RN_EXPORT __attribute__((visibility("default")))
+#endif
+
 namespace facebook {
 namespace react {
 
@@ -42,7 +46,7 @@ class JSExecutorFactory {
   virtual ~JSExecutorFactory() {}
 };
 
-class JSExecutor {
+class RN_EXPORT JSExecutor {
 public:
   /**
    * Execute an application script bundle in the JS context.

From 122b3791ede095345f44666691aa9ce5aa7f725a Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Tue, 29 May 2018 13:46:49 -0700
Subject: [PATCH 0675/1109] Vendor fetch polyfill, remove default blob response
 type

Summary:
While investigating an issue about blobs (https://github.com/facebook/react-native/issues/18223), I noticed that the fetch polyfill (https://github.com/github/fetch) uses blobs as the response type by default if the module is available (https://github.com/github/fetch/blob/master/fetch.js#L454). This surfaced some issue with the blob implementation on iOS that has since been fixed.

However after further review of the fetch polyfill and the way Blobs work in RN, I noticed a major issue that causes blobs created by fetch to leak memory. This is because RN blobs are not deallocated automatically like in the browser (see comment https://github.com/facebook/react-native/blob/master/Libraries/Blob/Blob.js#L108) and the fetch polyfill does not deallocate them explicitly using the close method.

Ideally we should implement automatic blob cleanup when the instance is garbage collected but implementing that is probably somewhat complex as it requires integrating with JSC. For now I suggest disabling the default handling of requests as blobs in the fetch polyfill. This will mitigate the issue for people not using Blobs directly. I'm not sure how well documented the Blob module is but we should make it clear that they currently require explicit deallocation with the close method for people using them directly.

Run a simple http request using fetch and make sure it does not use the Blob module anymore.

[GENERAL] [BUGFIX] [fetch] - Do not use blobs to handle responses in the fetch polyfill, fixes potential memory leak.
Closes https://github.com/facebook/react-native/pull/19333

Differential Revision: D8125463

Pulled By: hramos

fbshipit-source-id: 8f4602190dfc2643606606886c698e8e9b1d91d1
---
 Libraries/vendor/core/whatwg-fetch.js | 520 ++++++++++++++++++++++++++
 package.json                          |   1 -
 2 files changed, 520 insertions(+), 1 deletion(-)
 create mode 100644 Libraries/vendor/core/whatwg-fetch.js

diff --git a/Libraries/vendor/core/whatwg-fetch.js b/Libraries/vendor/core/whatwg-fetch.js
new file mode 100644
index 000000000000..1b5603201686
--- /dev/null
+++ b/Libraries/vendor/core/whatwg-fetch.js
@@ -0,0 +1,520 @@
+// Fork of https://github.com/github/fetch/blob/master/fetch.js that does not
+// use reponseType: 'blob' by default. RN already has specific native implementations
+// for different response types so there is no need to add the extra blob overhead.
+
+// Copyright (c) 2014-2016 GitHub, Inc.
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+(function(self) {
+  'use strict';
+
+  if (self.fetch) {
+    return;
+  }
+
+  var support = {
+    searchParams: 'URLSearchParams' in self,
+    iterable: 'Symbol' in self && 'iterator' in Symbol,
+    blob:
+      'FileReader' in self &&
+      'Blob' in self &&
+      (function() {
+        try {
+          new Blob();
+          return true;
+        } catch (e) {
+          return false;
+        }
+      })(),
+    formData: 'FormData' in self,
+    arrayBuffer: 'ArrayBuffer' in self,
+  };
+
+  if (support.arrayBuffer) {
+    var viewClasses = [
+      '[object Int8Array]',
+      '[object Uint8Array]',
+      '[object Uint8ClampedArray]',
+      '[object Int16Array]',
+      '[object Uint16Array]',
+      '[object Int32Array]',
+      '[object Uint32Array]',
+      '[object Float32Array]',
+      '[object Float64Array]',
+    ];
+
+    var isDataView = function(obj) {
+      return obj && DataView.prototype.isPrototypeOf(obj);
+    };
+
+    var isArrayBufferView =
+      ArrayBuffer.isView ||
+      function(obj) {
+        return (
+          obj && viewClasses.indexOf(Object.prototype.toString.call(obj)) > -1
+        );
+      };
+  }
+
+  function normalizeName(name) {
+    if (typeof name !== 'string') {
+      name = String(name);
+    }
+    if (/[^a-z0-9\-#$%&'*+.\^_`|~]/i.test(name)) {
+      throw new TypeError('Invalid character in header field name');
+    }
+    return name.toLowerCase();
+  }
+
+  function normalizeValue(value) {
+    if (typeof value !== 'string') {
+      value = String(value);
+    }
+    return value;
+  }
+
+  // Build a destructive iterator for the value list
+  function iteratorFor(items) {
+    var iterator = {
+      next: function() {
+        var value = items.shift();
+        return {done: value === undefined, value: value};
+      },
+    };
+
+    if (support.iterable) {
+      iterator[Symbol.iterator] = function() {
+        return iterator;
+      };
+    }
+
+    return iterator;
+  }
+
+  function Headers(headers) {
+    this.map = {};
+
+    if (headers instanceof Headers) {
+      headers.forEach(function(value, name) {
+        this.append(name, value);
+      }, this);
+    } else if (Array.isArray(headers)) {
+      headers.forEach(function(header) {
+        this.append(header[0], header[1]);
+      }, this);
+    } else if (headers) {
+      Object.getOwnPropertyNames(headers).forEach(function(name) {
+        this.append(name, headers[name]);
+      }, this);
+    }
+  }
+
+  Headers.prototype.append = function(name, value) {
+    name = normalizeName(name);
+    value = normalizeValue(value);
+    var oldValue = this.map[name];
+    this.map[name] = oldValue ? oldValue + ',' + value : value;
+  };
+
+  Headers.prototype['delete'] = function(name) {
+    delete this.map[normalizeName(name)];
+  };
+
+  Headers.prototype.get = function(name) {
+    name = normalizeName(name);
+    return this.has(name) ? this.map[name] : null;
+  };
+
+  Headers.prototype.has = function(name) {
+    return this.map.hasOwnProperty(normalizeName(name));
+  };
+
+  Headers.prototype.set = function(name, value) {
+    this.map[normalizeName(name)] = normalizeValue(value);
+  };
+
+  Headers.prototype.forEach = function(callback, thisArg) {
+    for (var name in this.map) {
+      if (this.map.hasOwnProperty(name)) {
+        callback.call(thisArg, this.map[name], name, this);
+      }
+    }
+  };
+
+  Headers.prototype.keys = function() {
+    var items = [];
+    this.forEach(function(value, name) {
+      items.push(name);
+    });
+    return iteratorFor(items);
+  };
+
+  Headers.prototype.values = function() {
+    var items = [];
+    this.forEach(function(value) {
+      items.push(value);
+    });
+    return iteratorFor(items);
+  };
+
+  Headers.prototype.entries = function() {
+    var items = [];
+    this.forEach(function(value, name) {
+      items.push([name, value]);
+    });
+    return iteratorFor(items);
+  };
+
+  if (support.iterable) {
+    Headers.prototype[Symbol.iterator] = Headers.prototype.entries;
+  }
+
+  function consumed(body) {
+    if (body.bodyUsed) {
+      return Promise.reject(new TypeError('Already read'));
+    }
+    body.bodyUsed = true;
+  }
+
+  function fileReaderReady(reader) {
+    return new Promise(function(resolve, reject) {
+      reader.onload = function() {
+        resolve(reader.result);
+      };
+      reader.onerror = function() {
+        reject(reader.error);
+      };
+    });
+  }
+
+  function readBlobAsArrayBuffer(blob) {
+    var reader = new FileReader();
+    var promise = fileReaderReady(reader);
+    reader.readAsArrayBuffer(blob);
+    return promise;
+  }
+
+  function readBlobAsText(blob) {
+    var reader = new FileReader();
+    var promise = fileReaderReady(reader);
+    reader.readAsText(blob);
+    return promise;
+  }
+
+  function readArrayBufferAsText(buf) {
+    var view = new Uint8Array(buf);
+    var chars = new Array(view.length);
+
+    for (var i = 0; i < view.length; i++) {
+      chars[i] = String.fromCharCode(view[i]);
+    }
+    return chars.join('');
+  }
+
+  function bufferClone(buf) {
+    if (buf.slice) {
+      return buf.slice(0);
+    } else {
+      var view = new Uint8Array(buf.byteLength);
+      view.set(new Uint8Array(buf));
+      return view.buffer;
+    }
+  }
+
+  function Body() {
+    this.bodyUsed = false;
+
+    this._initBody = function(body) {
+      this._bodyInit = body;
+      if (!body) {
+        this._bodyText = '';
+      } else if (typeof body === 'string') {
+        this._bodyText = body;
+      } else if (support.blob && Blob.prototype.isPrototypeOf(body)) {
+        this._bodyBlob = body;
+      } else if (support.formData && FormData.prototype.isPrototypeOf(body)) {
+        this._bodyFormData = body;
+      } else if (
+        support.searchParams &&
+        URLSearchParams.prototype.isPrototypeOf(body)
+      ) {
+        this._bodyText = body.toString();
+      } else if (support.arrayBuffer && support.blob && isDataView(body)) {
+        this._bodyArrayBuffer = bufferClone(body.buffer);
+        // IE 10-11 can't handle a DataView body.
+        this._bodyInit = new Blob([this._bodyArrayBuffer]);
+      } else if (
+        support.arrayBuffer &&
+        (ArrayBuffer.prototype.isPrototypeOf(body) || isArrayBufferView(body))
+      ) {
+        this._bodyArrayBuffer = bufferClone(body);
+      } else {
+        throw new Error('unsupported BodyInit type');
+      }
+
+      if (!this.headers.get('content-type')) {
+        if (typeof body === 'string') {
+          this.headers.set('content-type', 'text/plain;charset=UTF-8');
+        } else if (this._bodyBlob && this._bodyBlob.type) {
+          this.headers.set('content-type', this._bodyBlob.type);
+        } else if (
+          support.searchParams &&
+          URLSearchParams.prototype.isPrototypeOf(body)
+        ) {
+          this.headers.set(
+            'content-type',
+            'application/x-www-form-urlencoded;charset=UTF-8',
+          );
+        }
+      }
+    };
+
+    if (support.blob) {
+      this.blob = function() {
+        var rejected = consumed(this);
+        if (rejected) {
+          return rejected;
+        }
+
+        if (this._bodyBlob) {
+          return Promise.resolve(this._bodyBlob);
+        } else if (this._bodyArrayBuffer) {
+          return Promise.resolve(new Blob([this._bodyArrayBuffer]));
+        } else if (this._bodyFormData) {
+          throw new Error('could not read FormData body as blob');
+        } else {
+          return Promise.resolve(new Blob([this._bodyText]));
+        }
+      };
+
+      this.arrayBuffer = function() {
+        if (this._bodyArrayBuffer) {
+          return consumed(this) || Promise.resolve(this._bodyArrayBuffer);
+        } else {
+          return this.blob().then(readBlobAsArrayBuffer);
+        }
+      };
+    }
+
+    this.text = function() {
+      var rejected = consumed(this);
+      if (rejected) {
+        return rejected;
+      }
+
+      if (this._bodyBlob) {
+        return readBlobAsText(this._bodyBlob);
+      } else if (this._bodyArrayBuffer) {
+        return Promise.resolve(readArrayBufferAsText(this._bodyArrayBuffer));
+      } else if (this._bodyFormData) {
+        throw new Error('could not read FormData body as text');
+      } else {
+        return Promise.resolve(this._bodyText);
+      }
+    };
+
+    if (support.formData) {
+      this.formData = function() {
+        return this.text().then(decode);
+      };
+    }
+
+    this.json = function() {
+      return this.text().then(JSON.parse);
+    };
+
+    return this;
+  }
+
+  // HTTP methods whose capitalization should be normalized
+  var methods = ['DELETE', 'GET', 'HEAD', 'OPTIONS', 'POST', 'PUT'];
+
+  function normalizeMethod(method) {
+    var upcased = method.toUpperCase();
+    return methods.indexOf(upcased) > -1 ? upcased : method;
+  }
+
+  function Request(input, options) {
+    options = options || {};
+    var body = options.body;
+
+    if (input instanceof Request) {
+      if (input.bodyUsed) {
+        throw new TypeError('Already read');
+      }
+      this.url = input.url;
+      this.credentials = input.credentials;
+      if (!options.headers) {
+        this.headers = new Headers(input.headers);
+      }
+      this.method = input.method;
+      this.mode = input.mode;
+      if (!body && input._bodyInit != null) {
+        body = input._bodyInit;
+        input.bodyUsed = true;
+      }
+    } else {
+      this.url = String(input);
+    }
+
+    this.credentials = options.credentials || this.credentials || 'omit';
+    if (options.headers || !this.headers) {
+      this.headers = new Headers(options.headers);
+    }
+    this.method = normalizeMethod(options.method || this.method || 'GET');
+    this.mode = options.mode || this.mode || null;
+    this.referrer = null;
+
+    if ((this.method === 'GET' || this.method === 'HEAD') && body) {
+      throw new TypeError('Body not allowed for GET or HEAD requests');
+    }
+    this._initBody(body);
+  }
+
+  Request.prototype.clone = function() {
+    return new Request(this, {body: this._bodyInit});
+  };
+
+  function decode(body) {
+    var form = new FormData();
+    body
+      .trim()
+      .split('&')
+      .forEach(function(bytes) {
+        if (bytes) {
+          var split = bytes.split('=');
+          var name = split.shift().replace(/\+/g, ' ');
+          var value = split.join('=').replace(/\+/g, ' ');
+          form.append(decodeURIComponent(name), decodeURIComponent(value));
+        }
+      });
+    return form;
+  }
+
+  function parseHeaders(rawHeaders) {
+    var headers = new Headers();
+    // Replace instances of \r\n and \n followed by at least one space or horizontal tab with a space
+    // https://tools.ietf.org/html/rfc7230#section-3.2
+    var preProcessedHeaders = rawHeaders.replace(/\r?\n[\t ]+/g, ' ');
+    preProcessedHeaders.split(/\r?\n/).forEach(function(line) {
+      var parts = line.split(':');
+      var key = parts.shift().trim();
+      if (key) {
+        var value = parts.join(':').trim();
+        headers.append(key, value);
+      }
+    });
+    return headers;
+  }
+
+  Body.call(Request.prototype);
+
+  function Response(bodyInit, options) {
+    if (!options) {
+      options = {};
+    }
+
+    this.type = 'default';
+    this.status = options.status === undefined ? 200 : options.status;
+    this.ok = this.status >= 200 && this.status < 300;
+    this.statusText = 'statusText' in options ? options.statusText : 'OK';
+    this.headers = new Headers(options.headers);
+    this.url = options.url || '';
+    this._initBody(bodyInit);
+  }
+
+  Body.call(Response.prototype);
+
+  Response.prototype.clone = function() {
+    return new Response(this._bodyInit, {
+      status: this.status,
+      statusText: this.statusText,
+      headers: new Headers(this.headers),
+      url: this.url,
+    });
+  };
+
+  Response.error = function() {
+    var response = new Response(null, {status: 0, statusText: ''});
+    response.type = 'error';
+    return response;
+  };
+
+  var redirectStatuses = [301, 302, 303, 307, 308];
+
+  Response.redirect = function(url, status) {
+    if (redirectStatuses.indexOf(status) === -1) {
+      throw new RangeError('Invalid status code');
+    }
+
+    return new Response(null, {status: status, headers: {location: url}});
+  };
+
+  self.Headers = Headers;
+  self.Request = Request;
+  self.Response = Response;
+
+  self.fetch = function(input, init) {
+    return new Promise(function(resolve, reject) {
+      var request = new Request(input, init);
+      var xhr = new XMLHttpRequest();
+
+      xhr.onload = function() {
+        var options = {
+          status: xhr.status,
+          statusText: xhr.statusText,
+          headers: parseHeaders(xhr.getAllResponseHeaders() || ''),
+        };
+        options.url =
+          'responseURL' in xhr
+            ? xhr.responseURL
+            : options.headers.get('X-Request-URL');
+        var body = 'response' in xhr ? xhr.response : xhr.responseText;
+        resolve(new Response(body, options));
+      };
+
+      xhr.onerror = function() {
+        reject(new TypeError('Network request failed'));
+      };
+
+      xhr.ontimeout = function() {
+        reject(new TypeError('Network request failed'));
+      };
+
+      xhr.open(request.method, request.url, true);
+
+      if (request.credentials === 'include') {
+        xhr.withCredentials = true;
+      } else if (request.credentials === 'omit') {
+        xhr.withCredentials = false;
+      }
+
+      request.headers.forEach(function(value, name) {
+        xhr.setRequestHeader(name, value);
+      });
+
+      xhr.send(
+        typeof request._bodyInit === 'undefined' ? null : request._bodyInit,
+      );
+    });
+  };
+  self.fetch.polyfill = true;
+})(typeof self !== 'undefined' ? self : this);
diff --git a/package.json b/package.json
index ce738d0198ed..f615190404dd 100644
--- a/package.json
+++ b/package.json
@@ -193,7 +193,6 @@
     "serve-static": "^1.13.1",
     "shell-quote": "1.6.1",
     "stacktrace-parser": "^0.1.3",
-    "whatwg-fetch": "^1.0.0",
     "ws": "^1.1.0",
     "xcode": "^0.9.1",
     "xmldoc": "^0.4.0",

From b3b72bbdcfe296a369e06f5564f7aa398842a520 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 29 May 2018 14:54:52 -0700
Subject: [PATCH 0676/1109] Fabric: Using types `EventTarget`, `EventHandler` &
 co. instead of `void *` everywhere

Summary:
Nothing actually changed besides type names... which actually helps me found an issue in FabricUIManager!
Now there is no a single `void *` in Fabric/C++ and JavaScript bindings. Yay!

Reviewed By: fkgozali

Differential Revision: D8191420

fbshipit-source-id: b1eb60b6bc34dd25ab200aab854ffbd7ccf5b15d
---
 .../fabric/core/events/EventPrimitives.h       | 14 +++++++++-----
 .../fabric/core/primitives/ReactPrimitives.h   |  2 +-
 .../fabric/uimanager/FabricUIManager.cpp       | 14 +++++++-------
 ReactCommon/fabric/uimanager/FabricUIManager.h | 18 +++++++++---------
 4 files changed, 26 insertions(+), 22 deletions(-)

diff --git a/ReactCommon/fabric/core/events/EventPrimitives.h b/ReactCommon/fabric/core/events/EventPrimitives.h
index 46b71579630c..5dc5cb5d62d5 100644
--- a/ReactCommon/fabric/core/events/EventPrimitives.h
+++ b/ReactCommon/fabric/core/events/EventPrimitives.h
@@ -22,11 +22,15 @@ enum class EventPriority {
   Deferred = AsynchronousBatched,
 };
 
-// `InstanceHandler`, `EventTarget`, and `EventHandler` are all opaque
-// raw pointers. We use `struct {} *` trick to differentiate them in compiler's
-// eyes to ensure type safety.
-using EventTarget = struct {} *;
-using EventHandler = struct {} *;
+/* `InstanceHandler`, `EventTarget`, and `EventHandler` are all opaque
+ * raw pointers. We use `struct {} *` trick to differentiate them in compiler's
+ * eyes to ensure type safety.
+ * These structs must have names (and the names must be exported)
+ * to allow consistent template (e.g. `std::function`) instantiating
+ * across different modules.
+ */
+using EventTarget = struct EventTargetDummyStruct {} *;
+using EventHandler = struct EventHandlerDummyStruct {} *;
 
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/core/primitives/ReactPrimitives.h b/ReactCommon/fabric/core/primitives/ReactPrimitives.h
index 0b5004ab2ca0..c81f0ac938a1 100644
--- a/ReactCommon/fabric/core/primitives/ReactPrimitives.h
+++ b/ReactCommon/fabric/core/primitives/ReactPrimitives.h
@@ -19,7 +19,7 @@ namespace react {
  * `Tag` and `InstanceHandle` are used to address React Native components.
  */
 using Tag = int32_t;
-using InstanceHandle = void *;
+using InstanceHandle = struct InstanceHandleDummyStruct {} *;
 
 /*
  * `RawProps` represents untyped map with props comes from JavaScript side.
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 94b630c74674..7bedbfc8e8ec 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -78,7 +78,7 @@ FabricUIManager::FabricUIManager(SharedComponentDescriptorRegistry componentDesc
 
 FabricUIManager::~FabricUIManager() {
   if (eventHandler_) {
-    releaseEventTargetFunction_(eventHandler_);
+    releaseEventHandlerFunction_(eventHandler_);
   }
 }
 
@@ -106,11 +106,11 @@ void FabricUIManager::setReleaseEventHandlerFunction(std::function<ReleaseEventH
   releaseEventHandlerFunction_ = releaseEventHandlerFunction;
 }
 
-void *FabricUIManager::createEventTarget(void *instanceHandle) {
+EventTarget FabricUIManager::createEventTarget(const InstanceHandle &instanceHandle) const {
   return createEventTargetFunction_(instanceHandle);
 }
 
-void FabricUIManager::dispatchEvent(void *eventTarget, const std::string &type, const folly::dynamic &payload) {
+void FabricUIManager::dispatchEvent(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const {
   dispatchEventFunction_(
     eventHandler_,
     eventTarget,
@@ -119,12 +119,12 @@ void FabricUIManager::dispatchEvent(void *eventTarget, const std::string &type,
   );
 }
 
-void FabricUIManager::releaseEventTarget(void *eventTarget) {
+void FabricUIManager::releaseEventTarget(const EventTarget &eventTarget) const {
   releaseEventTargetFunction_(eventTarget);
 }
 
 SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, InstanceHandle instanceHandle) {
-  isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag" << rootTag << ", props: " << props << ")";
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag: " << rootTag << ", props: " << props << ")";
 
   ComponentName componentName = componentNameByReactViewName(viewName);
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[componentName];
@@ -251,8 +251,8 @@ void FabricUIManager::completeRoot(int rootTag, const SharedShadowNodeUnsharedLi
   }
 }
 
-void FabricUIManager::registerEventHandler(void *eventHandler) {
-  isLoggingEnabled && LOG(INFO) << "FabricUIManager::registerEventHandler(eventHandler)";
+void FabricUIManager::registerEventHandler(const EventHandler &eventHandler) {
+  isLoggingEnabled && LOG(INFO) << "FabricUIManager::registerEventHandler(eventHandler: " << eventHandler << ")";
   eventHandler_ = eventHandler;
 }
 
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index 54d1b8340185..ca0987a08a2a 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -18,10 +18,10 @@
 namespace facebook {
 namespace react {
 
-using CreateEventTargetFunction = void *(void *instanceHandle);
-using DispatchEventFunction = void (void *eventHandler, void *eventTarget, std::string type, folly::dynamic payload);
-using ReleaseEventTargetFunction = void (void *eventTarget);
-using ReleaseEventHandlerFunction = void (void *eventHandler);
+using CreateEventTargetFunction = EventTarget (InstanceHandle instanceHandle);
+using DispatchEventFunction = void (EventHandler eventHandler, EventTarget eventTarget, std::string type, folly::dynamic payload);
+using ReleaseEventTargetFunction = void (EventTarget eventTarget);
+using ReleaseEventHandlerFunction = void (EventHandler eventHandler);
 
 class FabricUIManager {
 public:
@@ -51,9 +51,9 @@ class FabricUIManager {
 
 #pragma mark - Native-facing Interface
 
-  void *createEventTarget(void *instanceHandle);
-  void dispatchEvent(void *eventTarget, const std::string &type, const folly::dynamic &payload);
-  void releaseEventTarget(void *eventTarget);
+  EventTarget createEventTarget(const InstanceHandle &instanceHandle) const;
+  void dispatchEvent(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const;
+  void releaseEventTarget(const EventTarget &eventTarget) const;
 
 #pragma mark - JavaScript/React-facing Interface
 
@@ -66,13 +66,13 @@ class FabricUIManager {
   SharedShadowNodeUnsharedList createChildSet(Tag rootTag);
   void appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode);
   void completeRoot(Tag rootTag, const SharedShadowNodeUnsharedList &childSet);
-  void registerEventHandler(void *eventHandler);
+  void registerEventHandler(const EventHandler &eventHandler);
 
 private:
 
   SharedComponentDescriptorRegistry componentDescriptorRegistry_;
   UIManagerDelegate *delegate_;
-  void *eventHandler_;
+  EventHandler eventHandler_;
   std::function<CreateEventTargetFunction> createEventTargetFunction_;
   std::function<DispatchEventFunction> dispatchEventFunction_;
   std::function<ReleaseEventTargetFunction> releaseEventTargetFunction_;

From c39b8041d1042c7699a16e3e7eeb8db7b9e57d58 Mon Sep 17 00:00:00 2001
From: Trevor Brindle <tabrindle@gmail.com>
Date: Tue, 29 May 2018 16:58:32 -0700
Subject: [PATCH 0677/1109] cli: upgrade envinfo for new features in
 `react-native info`

Summary:
envinfo has done a good job reporting issues in the issue template so far, and I've done a lot of work between version 3.x and 5.x that react-native could benefit from. This adds:
- better information organization, including versions and paths
- Platform/CPU/RAM
- Android and iOS SDK version detection
- npm package globbing (select all babel* packages
- global npm packages (with globbing)

envinfo also can report IDE versions, other binaries, languages and browsers if needed, and in different formats. Take a look here if interested: https://github.com/tabrindle/envinfo

- run `react-native info` // standard info
- run `react-native info --packages` // all packages in package.json
- run `react-native info --packages jest,eslint,babel-polyfill` // specified packages
- run `react-native info --packages *babel*` // globbed packages

Sample standard output:
```
  System:
    OS: macOS High Sierra 10.13
    CPU: x64 Intel(R) Core(TM) i7-4870HQ CPU @ 2.50GHz
    Memory: 97.59 MB / 16.00 GB
    Shell: 5.4.2 - /usr/local/bin/zsh
  Binaries:
    Node: 8.11.0 - ~/.nvm/versions/node/v8.11.0/bin/node
    Yarn: 1.5.1 - ~/.yarn/bin/yarn
    npm: 5.6.0 - ~/.nvm/versions/node/v8.11.0/bin/npm
    Watchman: 4.9.0 - /usr/local/bin/watchman
  SDKs:
    iOS SDK:
      Platforms: iOS 11.0, macOS 10.13, tvOS 11.0, watchOS 4.0
    Android SDK:
      Build Tools: 27.0.3
      API Levels: 26
  IDEs:
    Android Studio: 3.0 AI-171.4443003
    Xcode: 9.0/9A235 - /usr/bin/xcodebuild
  npmPackages:
    react: 16.3.2 => 16.3.2
    react-native: 0.55.0 => 0.55.0
  npmGlobalPackages:
    create-react-native-app: 1.0.0
    react-native-cli: 2.0.1
```

https://github.com/facebook/react-native/pull/14428 - original inclusion of `react-native info`

[CLI] [ENHANCEMENT] [local-cli/info/info.js] - add more info to react-native info cli command, like global npm packages, binary paths, and SDK versions
Closes https://github.com/facebook/react-native/pull/19331

Differential Revision: D8049650

Pulled By: hramos

fbshipit-source-id: 35c677f369bcad1a014eb083b2ce60ba33fee0ea
---
 local-cli/info/info.js | 53 ++++++++++++++++++++++++++++++++++--------
 package.json           |  2 +-
 2 files changed, 44 insertions(+), 11 deletions(-)

diff --git a/local-cli/info/info.js b/local-cli/info/info.js
index 0164c0acde54..dc605e052904 100644
--- a/local-cli/info/info.js
+++ b/local-cli/info/info.js
@@ -15,15 +15,36 @@ const info = function() {
   const args = Array.prototype.slice.call(arguments)[2];
 
   try {
-    envinfo.print({
-      packages:
-        typeof args.packages === 'string'
-          ? ['react', 'react-native'].concat(args.packages.split(','))
-          : args.packages,
-    });
-  } catch (error) {
+    envinfo
+      .run(
+        {
+          System: ['OS', 'CPU', 'Memory', 'Shell'],
+          Binaries: ['Node', 'Yarn', 'npm', 'Watchman'],
+          IDEs: ['Xcode', 'Android Studio'],
+          SDKs: ['iOS SDK', 'Android SDK'],
+          npmPackages:
+            (typeof args.packages === 'string' &&
+              !args.packages.includes('*')) ||
+            !args.packages
+              ? ['react', 'react-native'].concat(
+                  (args.packages || '').split(','),
+                )
+              : args.packages,
+          npmGlobalPackages: '*react-native*',
+        },
+        {
+          clipboard: !!args.clipboard,
+          title: 'React Native Environment Info',
+        },
+      )
+      .then(console.log)
+      .catch(err => {
+        console.log('Error: unable to print environment info');
+        console.log(err);
+      });
+  } catch (err) {
     console.log('Error: unable to print environment info');
-    console.log(error);
+    console.log(err);
   }
 };
 
@@ -35,7 +56,11 @@ module.exports = {
       command: '--packages [string]',
       description:
         'Which packages from your package.json to include, in addition to the default React Native and React versions.',
-      default: ['react', 'react-native'],
+    },
+    {
+      command: '--clipboard [boolean]',
+      description:
+        'Automagically copy the environment report output to the clipboard',
     },
   ],
   examples: [
@@ -45,7 +70,15 @@ module.exports = {
     },
     {
       desc: 'Get standard version info & specified package versions',
-      cmd: 'react-native info --packages jest,eslint,babel-polyfill',
+      cmd: 'react-native info --packages jest,eslint',
+    },
+    {
+      desc: 'Get standard version info & globbed package versions',
+      cmd: 'react-native info --packages "*react*"',
+    },
+    {
+      desc: 'Get standard version info & all package versions',
+      cmd: 'react-native info --packages',
     },
   ],
   func: info,
diff --git a/package.json b/package.json
index f615190404dd..5104b1d48229 100644
--- a/package.json
+++ b/package.json
@@ -156,7 +156,7 @@
     "create-react-class": "^15.6.3",
     "debug": "^2.2.0",
     "denodeify": "^1.2.1",
-    "envinfo": "^3.0.0",
+    "envinfo": "^5.7.0",
     "errorhandler": "^1.5.0",
     "escape-string-regexp": "^1.0.5",
     "event-target-shim": "^1.0.5",

From 95554add987b4a9ec4f7aa61afcb041a1f691c96 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 29 May 2018 17:13:32 -0700
Subject: [PATCH 0678/1109] Update Jest snapshots

Summary:
Jest will now exclude undefined props from snapshots (https://github.com/facebook/jest/pull/6162). Updating the snapshots should fix the current `test_javascript` failures.

Circle CI

[INTERNAL][MINOR][Snapshots] - Update snapshots
Closes https://github.com/facebook/react-native/pull/19414

Differential Revision: D8125193

Pulled By: hramos

fbshipit-source-id: db8dcfcd8afbf9d6256f83c6e922680a7872d776
---
 .../TouchableHighlight-test.js.snap           |  9 ---------
 .../__snapshots__/FlatList-test.js.snap       |  9 ---------
 .../__snapshots__/SectionList-test.js.snap    | 16 ----------------
 .../VirtualizedList-test.js.snap              | 19 -------------------
 4 files changed, 53 deletions(-)

diff --git a/Libraries/Components/Touchable/__tests__/__snapshots__/TouchableHighlight-test.js.snap b/Libraries/Components/Touchable/__tests__/__snapshots__/TouchableHighlight-test.js.snap
index 6028d74aaa8a..34d71cc12a52 100644
--- a/Libraries/Components/Touchable/__tests__/__snapshots__/TouchableHighlight-test.js.snap
+++ b/Libraries/Components/Touchable/__tests__/__snapshots__/TouchableHighlight-test.js.snap
@@ -2,15 +2,8 @@
 
 exports[`TouchableHighlight renders correctly 1`] = `
 <View
-  accessibilityComponentType={undefined}
-  accessibilityLabel={undefined}
-  accessibilityTraits={undefined}
   accessible={true}
-  hasTVPreferredFocus={undefined}
-  hitSlop={undefined}
   isTVSelectable={true}
-  nativeID={undefined}
-  onLayout={undefined}
   onResponderGrant={[Function]}
   onResponderMove={[Function]}
   onResponderRelease={[Function]}
@@ -18,8 +11,6 @@ exports[`TouchableHighlight renders correctly 1`] = `
   onResponderTerminationRequest={[Function]}
   onStartShouldSetResponder={[Function]}
   style={Object {}}
-  testID={undefined}
-  tvParallaxProperties={undefined}
 >
   <Text
     style={null}
diff --git a/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap b/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
index 525ad54eea84..d6d008065b24 100644
--- a/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
+++ b/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
@@ -31,7 +31,6 @@ exports[`FlatList renders all the bells and whistles 1`] = `
   getItemLayout={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   numColumns={2}
@@ -46,7 +45,6 @@ exports[`FlatList renders all the bells and whistles 1`] = `
   refreshControl={
     <RefreshControlMock
       onRefresh={[MockFunction]}
-      progressViewOffset={undefined}
       refreshing={false}
     />
   }
@@ -67,7 +65,6 @@ exports[`FlatList renders all the bells and whistles 1`] = `
       <header />
     </View>
     <View
-      onLayout={undefined}
       style={null}
     >
       <View
@@ -87,7 +84,6 @@ exports[`FlatList renders all the bells and whistles 1`] = `
       <separator />
     </View>
     <View
-      onLayout={undefined}
       style={null}
     >
       <View
@@ -107,7 +103,6 @@ exports[`FlatList renders all the bells and whistles 1`] = `
       <separator />
     </View>
     <View
-      onLayout={undefined}
       style={null}
     >
       <View
@@ -140,7 +135,6 @@ exports[`FlatList renders empty list 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   numColumns={1}
@@ -164,13 +158,11 @@ exports[`FlatList renders empty list 1`] = `
 
 exports[`FlatList renders null list 1`] = `
 <RCTScrollView
-  data={undefined}
   disableVirtualization={false}
   getItem={[Function]}
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   numColumns={1}
@@ -212,7 +204,6 @@ exports[`FlatList renders simple list 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   numColumns={1}
diff --git a/Libraries/Lists/__tests__/__snapshots__/SectionList-test.js.snap b/Libraries/Lists/__tests__/__snapshots__/SectionList-test.js.snap
index ec57ef42dc6c..f47dd4e8d626 100644
--- a/Libraries/Lists/__tests__/__snapshots__/SectionList-test.js.snap
+++ b/Libraries/Lists/__tests__/__snapshots__/SectionList-test.js.snap
@@ -2,7 +2,6 @@
 
 exports[`SectionList rendering empty section headers is fine 1`] = `
 <RCTScrollView
-  ItemSeparatorComponent={undefined}
   data={
     Array [
       Object {
@@ -23,7 +22,6 @@ exports[`SectionList rendering empty section headers is fine 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -33,7 +31,6 @@ exports[`SectionList rendering empty section headers is fine 1`] = `
   onScroll={[Function]}
   onScrollBeginDrag={[Function]}
   onScrollEndDrag={[Function]}
-  onViewableItemsChanged={undefined}
   renderItem={[Function]}
   renderSectionHeader={[Function]}
   scrollEventThrottle={50}
@@ -92,7 +89,6 @@ exports[`SectionList rendering empty section headers is fine 1`] = `
 
 exports[`SectionList renders a footer when there is no data 1`] = `
 <RCTScrollView
-  ItemSeparatorComponent={undefined}
   data={
     Array [
       Object {
@@ -106,7 +102,6 @@ exports[`SectionList renders a footer when there is no data 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -116,7 +111,6 @@ exports[`SectionList renders a footer when there is no data 1`] = `
   onScroll={[Function]}
   onScrollBeginDrag={[Function]}
   onScrollEndDrag={[Function]}
-  onViewableItemsChanged={undefined}
   renderItem={[Function]}
   renderSectionFooter={[Function]}
   renderSectionHeader={[Function]}
@@ -161,7 +155,6 @@ exports[`SectionList renders a footer when there is no data 1`] = `
 
 exports[`SectionList renders a footer when there is no data and no header 1`] = `
 <RCTScrollView
-  ItemSeparatorComponent={undefined}
   data={
     Array [
       Object {
@@ -175,7 +168,6 @@ exports[`SectionList renders a footer when there is no data and no header 1`] =
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -185,7 +177,6 @@ exports[`SectionList renders a footer when there is no data and no header 1`] =
   onScroll={[Function]}
   onScrollBeginDrag={[Function]}
   onScrollEndDrag={[Function]}
-  onViewableItemsChanged={undefined}
   renderItem={[Function]}
   renderSectionFooter={[Function]}
   scrollEventThrottle={50}
@@ -225,7 +216,6 @@ exports[`SectionList renders a footer when there is no data and no header 1`] =
 
 exports[`SectionList renders all the bells and whistles 1`] = `
 <RCTScrollView
-  ItemSeparatorComponent={undefined}
   ListEmptyComponent={[Function]}
   ListFooterComponent={[Function]}
   ListHeaderComponent={[Function]}
@@ -275,7 +265,6 @@ exports[`SectionList renders all the bells and whistles 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={Infinity}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -286,11 +275,9 @@ exports[`SectionList renders all the bells and whistles 1`] = `
   onScroll={[Function]}
   onScrollBeginDrag={[Function]}
   onScrollEndDrag={[Function]}
-  onViewableItemsChanged={undefined}
   refreshControl={
     <RefreshControlMock
       onRefresh={[MockFunction]}
-      progressViewOffset={undefined}
       refreshing={false}
     />
   }
@@ -509,14 +496,12 @@ exports[`SectionList renders all the bells and whistles 1`] = `
 
 exports[`SectionList renders empty list 1`] = `
 <RCTScrollView
-  ItemSeparatorComponent={undefined}
   data={Array []}
   disableVirtualization={false}
   getItem={[Function]}
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -526,7 +511,6 @@ exports[`SectionList renders empty list 1`] = `
   onScroll={[Function]}
   onScrollBeginDrag={[Function]}
   onScrollEndDrag={[Function]}
-  onViewableItemsChanged={undefined}
   renderItem={[Function]}
   scrollEventThrottle={50}
   sections={Array []}
diff --git a/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap b/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
index 9cf5c2d9ea29..cb1a86d71805 100644
--- a/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
+++ b/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
@@ -17,7 +17,6 @@ exports[`VirtualizedList handles nested lists 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -54,7 +53,6 @@ exports[`VirtualizedList handles nested lists 1`] = `
         getItemCount={[Function]}
         horizontal={false}
         initialNumToRender={10}
-        invertStickyHeaders={undefined}
         keyExtractor={[Function]}
         maxToRenderPerBatch={10}
         onContentSizeChange={[Function]}
@@ -108,7 +106,6 @@ exports[`VirtualizedList handles nested lists 1`] = `
         getItemCount={[Function]}
         horizontal={true}
         initialNumToRender={10}
-        invertStickyHeaders={undefined}
         keyExtractor={[Function]}
         maxToRenderPerBatch={10}
         onContentSizeChange={[Function]}
@@ -183,7 +180,6 @@ exports[`VirtualizedList handles separators correctly 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -265,7 +261,6 @@ exports[`VirtualizedList handles separators correctly 2`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -347,7 +342,6 @@ exports[`VirtualizedList handles separators correctly 3`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -455,7 +449,6 @@ exports[`VirtualizedList renders all the bells and whistles 1`] = `
   refreshControl={
     <RefreshControlMock
       onRefresh={[MockFunction]}
-      progressViewOffset={undefined}
       refreshing={false}
     />
   }
@@ -495,7 +488,6 @@ exports[`VirtualizedList renders all the bells and whistles 1`] = `
       <header />
     </View>
     <View
-      onLayout={undefined}
       style={
         Array [
           Object {
@@ -517,7 +509,6 @@ exports[`VirtualizedList renders all the bells and whistles 1`] = `
       <separator />
     </View>
     <View
-      onLayout={undefined}
       style={
         Array [
           Object {
@@ -539,7 +530,6 @@ exports[`VirtualizedList renders all the bells and whistles 1`] = `
       <separator />
     </View>
     <View
-      onLayout={undefined}
       style={
         Array [
           Object {
@@ -561,7 +551,6 @@ exports[`VirtualizedList renders all the bells and whistles 1`] = `
       <separator />
     </View>
     <View
-      onLayout={undefined}
       style={
         Array [
           Object {
@@ -583,7 +572,6 @@ exports[`VirtualizedList renders all the bells and whistles 1`] = `
       <separator />
     </View>
     <View
-      onLayout={undefined}
       style={
         Array [
           Object {
@@ -629,7 +617,6 @@ exports[`VirtualizedList renders empty list 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -660,7 +647,6 @@ exports[`VirtualizedList renders empty list with empty component 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -709,7 +695,6 @@ exports[`VirtualizedList renders list with empty component 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -740,13 +725,11 @@ exports[`VirtualizedList renders list with empty component 1`] = `
 
 exports[`VirtualizedList renders null list 1`] = `
 <RCTScrollView
-  data={undefined}
   disableVirtualization={false}
   getItem={[Function]}
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -786,7 +769,6 @@ exports[`VirtualizedList renders simple list 1`] = `
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}
@@ -845,7 +827,6 @@ exports[`VirtualizedList test getItem functionality where data is not an Array 1
   getItemCount={[Function]}
   horizontal={false}
   initialNumToRender={10}
-  invertStickyHeaders={undefined}
   keyExtractor={[Function]}
   maxToRenderPerBatch={10}
   onContentSizeChange={[Function]}

From 829e9ba1803c37f538def6ba25a5a91f9c428914 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 29 May 2018 17:24:31 -0700
Subject: [PATCH 0679/1109] Add Feature Request template

Summary: Closes https://github.com/facebook/react-native/pull/19498

Differential Revision: D8197147

Pulled By: hramos

fbshipit-source-id: 0668b885a0eb04a3af948f5643649d5b68488c71
---
 .github/ISSUE_TEMPLATE/bug_report.md    | 25 ++++++++++++-------------
 .github/ISSUE_TEMPLATE/discussion.md    | 15 +++++++++++++++
 .github/ISSUE_TEMPLATE/documentation.md |  4 +++-
 .github/ISSUE_TEMPLATE/question.md      | 12 ++++++------
 4 files changed, 36 insertions(+), 20 deletions(-)
 create mode 100644 .github/ISSUE_TEMPLATE/discussion.md

diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md
index 57aac5b85e5b..7012b1da2c1a 100644
--- a/.github/ISSUE_TEMPLATE/bug_report.md
+++ b/.github/ISSUE_TEMPLATE/bug_report.md
@@ -1,25 +1,24 @@
 ---
 name: 🐛 Bug Report
-about: Something is not working as expected.
-
+about: Report a reproducible bug or regression in the core React Native library.
 ---
 
-<!-- GitHub Issues in the `facebook/react-native` repository are used exclusively for tracking bugs in React Native. -->
+<!-- Requirements: please go through this checklist before opening a new issue -->
+  - [ ] Review the documentation: https://facebook.github.io/react-native
+  - [ ] Search for existing issues: https://github.com/facebook/react-native/issues
+  - [ ] Use the latest React Native version: https://github.com/facebook/react-native/releases
+  - [ ] Run `react-native info` in your terminal and paste its contents under "Environment"
+  - [ ] Let us know how to reproduce the issue. Include a code sample, share a project, or
+    share an app that reproduces the issue using https://snack.expo.io/
 
-- [ ] I have reviewed the [documentation](https://facebook.github.io/react-native)
-- [ ] I have searched [existing issues](https://github.com/facebook/react-native/issues)
-- [ ] I am using the [latest React Native version](https://github.com/facebook/react-native/releases)
+## Environment
+<!-- Required. -->
 
+## Description
 <!-- Describe your issue in detail. -->
 
-## Environment
-<!-- Required. Run `react-native info` in your terminal and paste its contents here. -->
-
 ## Steps to Reproduce
-<!--
-  Required. Let us know how to reproduce the issue. Include a code sample, share a project,
-  or share an app that reproduces the issue using [Snack](https://snack.expo.io/).
--->
+<!-- Required. -->
 
 ## Expected Behavior
 <!-- Write what you thought would happen. -->
diff --git a/.github/ISSUE_TEMPLATE/discussion.md b/.github/ISSUE_TEMPLATE/discussion.md
new file mode 100644
index 000000000000..ed1ede3944a7
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/discussion.md
@@ -0,0 +1,15 @@
+---
+name: 🗣 Start a Discussion
+about: Use https://discuss.reactjs.org/ to propose changes or discuss feature requests.
+
+guidelines: |
+  If you feel strongly about starting a discussion as a GitHub Issue instead of using the discussion forum, please follow this template.
+  We kindly ask that issues of this type are kept to a minimum to ensure bug reports and regressions are given the priority they require.
+  Maintainers may flag an issue for Stack Overflow or kindly ask you to move the discussion to https://discuss.reactjs.org at their own discretion.
+
+---
+
+## For Discussion
+
+<!-- Describe your issue in detail. -->
+
diff --git a/.github/ISSUE_TEMPLATE/documentation.md b/.github/ISSUE_TEMPLATE/documentation.md
index e18bdfaf164f..1a4751ee5a99 100644
--- a/.github/ISSUE_TEMPLATE/documentation.md
+++ b/.github/ISSUE_TEMPLATE/documentation.md
@@ -1,9 +1,11 @@
 ---
 name: 📖 Documentation Issue
-about: Report issues with the docs at https://github.com/facebook/react-native-website/issues
+about: Report issues with the docs at https://github.com/facebook/react-native-website/issues.
 
 ---
 
+--------------^ Click "Preview" for a nicer view!
+
 GitHub Issues in the `facebook/react-native` repository are used exclusively for tracking bugs in React Native.
 
 If you would like to report an issue in the React Native documentation, or anything related to the [React Native website](http://facebook.github.io/react-native), please visit https://github.com/facebook/react-native-website/issues.
diff --git a/.github/ISSUE_TEMPLATE/question.md b/.github/ISSUE_TEMPLATE/question.md
index bba783655e1b..cc203120f245 100644
--- a/.github/ISSUE_TEMPLATE/question.md
+++ b/.github/ISSUE_TEMPLATE/question.md
@@ -1,21 +1,21 @@
 ---
 name: 💬 Question
-about: For questions about using React Native in your app.
+about: If you need help with your React Native app, the right place to go depends on the type of help that you need.
 
 ---
 
 --------------^ Click "Preview" for a nicer view!
 
-GitHub Issues in the `facebook/react-native` repository are used exclusively for tracking bugs in React Native. If you need help with your React Native app, the right place to go depends on the type of help that you need.
+GitHub Issues in the `facebook/react-native` repository are used exclusively for tracking bugs in React Native. GitHub may not be the ideal place to ask questions about using React Native, but we have compiled a list of resources that should help.
 
-### Stack Overflow
+### Get help with your React Native app or ask code-level questions
 
 Many members of the community use Stack Overflow to ask questions. Read through the [existing questions](http://stackoverflow.com/questions/tagged/react-native?sort=frequent) tagged with **react-native** or [ask your own](http://stackoverflow.com/questions/ask?tags=react-native)!
 
-### Discussion Forum
+### Talk about best practices or propose changes to React Native
 
-For longer-form conversations about React Native, we’ve set up a [discussion forum at **discuss.reactjs.org**](https://discuss.reactjs.org/t/welcome-react-native-community-group/10239). This forum is a great place for discussion about best practices and application architecture as well as the future of React Native. If you have an answerable code-level question, please post it to [Stack Overflow](http://stackoverflow.com/questions/ask?tags=react-native) instead.
+For longer-form conversations about React Native, we’ve set up a [discussion forum at **discuss.reactjs.org**](https://discuss.reactjs.org/t/welcome-react-native-community-group/10239). This forum is a great place for discussion about best practices and application architecture as well as the future of React Native.
 
-### Reactiflux Chat
+### Chat with React and React Native community members
 
 If you need an answer right away, check out the [Reactiflux Discord](https://discord.gg/0ZcbPKXt5bZjGY5n) community. There are usually a number of React Native experts there who can help out or point you to somewhere you might want to look.

From 9d315f4a1e7b0c9cd80a51903db0b1b561b19e33 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Wed, 30 May 2018 00:05:49 -0700
Subject: [PATCH 0680/1109] OSS: ignore xcodeproj in root dir

Summary: We don't need Xcode project in root dir.

Reviewed By: davidaurelio

Differential Revision: D8197985

fbshipit-source-id: dbbb8820111e84181c9880372dab9af55e0876e6
---
 .gitignore | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/.gitignore b/.gitignore
index 1b46fc1ee1ba..7705dae8ffa4 100644
--- a/.gitignore
+++ b/.gitignore
@@ -67,6 +67,8 @@ package-lock.json
 /coverage
 /third-party
 
+# Root dir shouldn't have Xcode project
+/*.xcodeproj
+
 # ReactCommon subdir shouldn't have Xcode project
 /ReactCommon/**/*.xcodeproj
-

From d8bf46ae9095ac595209f0049491fce59a50cbe7 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Wed, 30 May 2018 08:50:10 -0700
Subject: [PATCH 0681/1109] jest@23.0.1 in xplat/js

Reviewed By: rafeca

Differential Revision: D8195559

fbshipit-source-id: 7e96f24ae1f9586e9fbc6e1687f731420979352d
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index 5104b1d48229..1ed8d3aabda8 100644
--- a/package.json
+++ b/package.json
@@ -213,8 +213,8 @@
     "eslint-plugin-react": "7.6.1",
     "eslint-plugin-react-native": "^3.2.1",
     "flow-bin": "^0.73.0",
-    "jest": "23.0.0-charlie.1",
-    "jest-junit": "3.7.0",
+    "jest": "23.0.1",
+    "jest-junit": "4.0.0",
     "prettier": "1.12.1",
     "react": "16.3.2",
     "react-test-renderer": "16.3.2",

From 5863b564f84b9fe97b256f8cde0f7f2e1db9b641 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Wed, 30 May 2018 10:34:33 -0700
Subject: [PATCH 0682/1109] deleted UI Action Sheet Delegate Methods

Reviewed By: PeteTheHeat

Differential Revision: D8191111

fbshipit-source-id: 39867683cf5e0cdf8a94a76269d939b5ecf6bbd4
---
 .../RCTActionSheet.xcodeproj/project.pbxproj        |  2 --
 Libraries/ActionSheetIOS/RCTActionSheetManager.m    | 13 -------------
 2 files changed, 15 deletions(-)

diff --git a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
index 47a0b8b4d8ba..a639137bb7bb 100644
--- a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
+++ b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
@@ -141,7 +141,6 @@
 				WARNING_CFLAGS = (
 					"-Werror",
 					"-Wall",
-					"-Wno-deprecated-declarations",
 				);
 			};
 			name = Debug;
@@ -183,7 +182,6 @@
 				WARNING_CFLAGS = (
 					"-Werror",
 					"-Wall",
-					"-Wno-deprecated-declarations",
 				);
 			};
 			name = Release;
diff --git a/Libraries/ActionSheetIOS/RCTActionSheetManager.m b/Libraries/ActionSheetIOS/RCTActionSheetManager.m
index 91f047323769..cd5d5719ff76 100644
--- a/Libraries/ActionSheetIOS/RCTActionSheetManager.m
+++ b/Libraries/ActionSheetIOS/RCTActionSheetManager.m
@@ -186,17 +186,4 @@ - (CGRect)sourceRectInView:(UIView *)sourceView
   shareController.view.tintColor = [RCTConvert UIColor:options[@"tintColor"]];
 }
 
-#pragma mark UIActionSheetDelegate Methods
-
-- (void)actionSheet:(UIActionSheet *)actionSheet clickedButtonAtIndex:(NSInteger)buttonIndex
-{
-  RCTResponseSenderBlock callback = [_callbacks objectForKey:actionSheet];
-  if (callback) {
-    callback(@[@(buttonIndex)]);
-    [_callbacks removeObjectForKey:actionSheet];
-  } else {
-    RCTLogWarn(@"No callback registered for action sheet: %@", actionSheet.title);
-  }
-}
-
 @end

From 5fc42f308aedcbce0f132f4ec1d10f7fde4e9574 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Wed, 30 May 2018 14:18:34 -0700
Subject: [PATCH 0683/1109] Fix ART surface sleep issue

Summary: Fixes https://github.com/facebook/react-native/issues/17565.

Reviewed By: achen1

Differential Revision: D8194925

fbshipit-source-id: 5448d49d959078eaded697f791e1b382471fabdb
---
 .../react/flat/FlatARTSurfaceViewManager.java  |  4 +++-
 .../flat/FlatARTSurfaceViewShadowNode.java     | 18 +++++++-----------
 .../react/views/art/ARTSurfaceView.java        |  5 ++---
 .../react/views/art/ARTSurfaceViewManager.java |  3 ++-
 .../views/art/ARTSurfaceViewShadowNode.java    | 16 +++++++---------
 5 files changed, 21 insertions(+), 25 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
index f6382b80befc..d1172d82a7e8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
@@ -7,6 +7,7 @@
 
 package com.facebook.react.flat;
 
+import android.view.SurfaceHolder;
 import com.facebook.react.uimanager.BaseViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.views.art.ARTSurfaceView;
@@ -14,6 +15,7 @@
 import com.facebook.yoga.YogaMeasureMode;
 import com.facebook.yoga.YogaNode;
 
+
 public class FlatARTSurfaceViewManager extends
   BaseViewManager<ARTSurfaceView, FlatARTSurfaceViewShadowNode> {
 
@@ -55,6 +57,6 @@ protected ARTSurfaceView createViewInstance(ThemedReactContext reactContext) {
 
   @Override
   public void updateExtraData(ARTSurfaceView root, Object extraData) {
-    root.setSurfaceTextureListener((FlatARTSurfaceViewShadowNode) extraData);
+    root.getHolder().addCallback((FlatARTSurfaceViewShadowNode) extraData);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
index 09fa6a42a429..aefe34104a24 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
@@ -16,7 +16,7 @@
 import android.graphics.SurfaceTexture;
 import android.util.Log;
 import android.view.Surface;
-import android.view.TextureView;
+import android.view.SurfaceHolder;
 
 import com.facebook.react.common.ReactConstants;
 import com.facebook.react.uimanager.ReactShadowNode;
@@ -25,8 +25,9 @@
 import com.facebook.yoga.YogaValue;
 import com.facebook.yoga.YogaUnit;
 
+
 /* package */ class FlatARTSurfaceViewShadowNode extends FlatShadowNode
-    implements AndroidView, TextureView.SurfaceTextureListener {
+    implements AndroidView, SurfaceHolder.Callback {
   private boolean mPaddingChanged = false;
   private @Nullable Surface mSurface;
 
@@ -123,21 +124,16 @@ public void setPaddingPercent(int spacingType, float percent) {
   }
 
   @Override
-  public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) {
-    mSurface = new Surface(surface);
+  public void surfaceCreated(SurfaceHolder holder) {
+    mSurface = holder.getSurface();
     drawOutput();
   }
 
   @Override
-  public boolean onSurfaceTextureDestroyed(SurfaceTexture surface) {
-    surface.release();
+  public void surfaceDestroyed(SurfaceHolder holder) {
     mSurface = null;
-    return true;
   }
 
   @Override
-  public void onSurfaceTextureSizeChanged(SurfaceTexture surface, int width, int height) {}
-
-  @Override
-  public void onSurfaceTextureUpdated(SurfaceTexture surface) {}
+  public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {}
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceView.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceView.java
index 93f2c21eb1aa..ac68a9b2e85f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceView.java
@@ -8,14 +8,13 @@
 package com.facebook.react.views.art;
 
 import android.content.Context;
-import android.view.TextureView;
+import android.view.SurfaceView;
 
 /**
  * Custom {@link View} implementation that draws an ARTSurface React view and its children.
  */
-public class ARTSurfaceView extends TextureView {
+public class ARTSurfaceView extends SurfaceView {
   public ARTSurfaceView(Context context) {
     super(context);
-    setOpaque(false);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewManager.java
index 24787ef84a53..d1ee910d0ab6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewManager.java
@@ -7,6 +7,7 @@
 
 package com.facebook.react.views.art;
 
+import android.view.SurfaceHolder;
 import com.facebook.yoga.YogaMeasureMode;
 import com.facebook.yoga.YogaMeasureFunction;
 import com.facebook.yoga.YogaNode;
@@ -60,7 +61,7 @@ protected ARTSurfaceView createViewInstance(ThemedReactContext reactContext) {
 
   @Override
   public void updateExtraData(ARTSurfaceView root, Object extraData) {
-    root.setSurfaceTextureListener((ARTSurfaceViewShadowNode) extraData);
+    root.getHolder().addCallback((ARTSurfaceViewShadowNode) extraData);
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewShadowNode.java
index 429812e19916..c0a893481c0b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewShadowNode.java
@@ -15,8 +15,10 @@
 import android.view.Surface;
 import android.graphics.PorterDuff;
 import android.graphics.SurfaceTexture;
+import android.view.SurfaceHolder;
 import android.view.TextureView;
 
+
 import com.facebook.common.logging.FLog;
 import com.facebook.react.common.ReactConstants;
 import com.facebook.react.uimanager.LayoutShadowNode;
@@ -29,7 +31,7 @@
  * Shadow node for ART virtual tree root - ARTSurfaceView
  */
 public class ARTSurfaceViewShadowNode extends LayoutShadowNode
-  implements TextureView.SurfaceTextureListener {
+  implements SurfaceHolder.Callback {
 
   private @Nullable Surface mSurface;
 
@@ -97,21 +99,17 @@ private void markChildrenUpdatesSeen(ReactShadowNode shadowNode) {
   }
 
   @Override
-  public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) {
-    mSurface = new Surface(surface);
+  public void surfaceCreated(SurfaceHolder holder) {
+    mSurface = holder.getSurface();
     drawOutput();
   }
 
   @Override
-  public boolean onSurfaceTextureDestroyed(SurfaceTexture surface) {
-    surface.release();
+  public void surfaceDestroyed(SurfaceHolder holder) {
     mSurface = null;
-    return true;
   }
 
   @Override
-  public void onSurfaceTextureSizeChanged(SurfaceTexture surface, int width, int height) {}
+  public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {}
 
-  @Override
-  public void onSurfaceTextureUpdated(SurfaceTexture surface) {}
 }

From c6b4f9f2ce59bc757d9e211f46294faa03df55c6 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 30 May 2018 14:32:18 -0700
Subject: [PATCH 0684/1109] Fix TextInput's initial layout measurements

Reviewed By: mdvacca

Differential Revision: D7732819

fbshipit-source-id: 0ca4e5643d2cfefe304d7f189474a671c4bcb31e
---
 .../textinput/ReactTextInputShadowNode.java   | 23 +++++++++++++++----
 1 file changed, 19 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
index 7ff8d488d728..e121f2b5f22f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
@@ -9,16 +9,19 @@
 
 import android.os.Build;
 import android.text.Layout;
+import android.util.TypedValue;
 import android.view.ViewGroup;
 import android.widget.EditText;
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.bridge.JSApplicationIllegalArgumentException;
 import com.facebook.react.common.annotations.VisibleForTesting;
 import com.facebook.react.uimanager.LayoutShadowNode;
+import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.Spacing;
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.uimanager.UIViewOperationQueue;
+import com.facebook.react.uimanager.ViewDefaults;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.views.text.ReactBaseTextShadowNode;
 import com.facebook.react.views.text.ReactTextUpdate;
@@ -127,12 +130,24 @@ public long measure(
     // measure() should never be called before setThemedContext()
     EditText editText = Assertions.assertNotNull(mDummyEditText);
 
-    if (mLocalData == null) {
-      // No local data, no intrinsic size.
-      return YogaMeasureOutput.make(0, 0);
+    if (mLocalData != null) {
+      mLocalData.apply(editText);
+    } else {
+      editText.setTextSize(
+          TypedValue.COMPLEX_UNIT_PX,
+          mFontSize == UNSET ?
+              (int) Math.ceil(PixelUtil.toPixelFromSP(ViewDefaults.FONT_SIZE_SP)) : mFontSize);
+
+      if (mNumberOfLines != UNSET) {
+        editText.setLines(mNumberOfLines);
+      }
+
+      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M &&
+          editText.getBreakStrategy() != mTextBreakStrategy) {
+        editText.setBreakStrategy(mTextBreakStrategy);
+      }
     }
 
-    mLocalData.apply(editText);
 
     editText.measure(
         MeasureUtil.getMeasureSpec(width, widthMode),

From 4a9b2a73021fb547febe1fa193c3effb7ff8da4e Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Wed, 30 May 2018 15:00:23 -0700
Subject: [PATCH 0685/1109] Fix ReactInstanceManager unmountApplication

Reviewed By: mdvacca

Differential Revision: D7945746

fbshipit-source-id: 0c2eed9a623e442fa4a4ff29ffa01f025466c9b6
---
 .../main/java/com/facebook/react/ReactRootView.java   |  1 +
 .../test/java/com/facebook/react/RootViewTest.java    | 11 +++++++++++
 2 files changed, 12 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 9e7c04ba80cd..4599484e298c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -423,6 +423,7 @@ public void runGuarded() {
   public void unmountReactApplication() {
     if (mReactInstanceManager != null && mIsAttachedToInstance) {
       mReactInstanceManager.detachRootView(this);
+      mReactInstanceManager = null;
       mIsAttachedToInstance = false;
     }
     mShouldLogContentAppeared = false;
diff --git a/ReactAndroid/src/test/java/com/facebook/react/RootViewTest.java b/ReactAndroid/src/test/java/com/facebook/react/RootViewTest.java
index c293858b4b6a..d706b9c79e64 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/RootViewTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/RootViewTest.java
@@ -195,4 +195,15 @@ public void testTouchEmitter() {
         MotionEvent.obtain(50, new Date().getTime(), MotionEvent.ACTION_HOVER_MOVE, 0, 0, 0));
     verifyNoMoreInteractions(eventDispatcher);
   }
+
+  @Test
+  public void testRemountApplication() {
+    ReactInstanceManager instanceManager = mock(ReactInstanceManager.class);
+
+    ReactRootView rootView = new ReactRootView(mReactContext);
+
+    rootView.startReactApplication(instanceManager, "");
+    rootView.unmountReactApplication();
+    rootView.startReactApplication(instanceManager, "");
+  }
 }

From e61341ba321c38175309b70a8c4868f7ebf4e041 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 30 May 2018 21:48:49 -0700
Subject: [PATCH 0686/1109] Introducing Scheduling of JS calls from native

Reviewed By: achen1

Differential Revision: D7729226

fbshipit-source-id: 9869e0a6a2b0c58b7538836ed2c13a4b28dd8887
---
 .../main/java/com/facebook/react/fabric/BUCK  |   5 +-
 .../react/fabric/FabricUIManager.java         |  10 +-
 .../com/facebook/react/fabric/JSHandler.java  |  15 ++
 .../com/facebook/react/fabric/Scheduler.java  |  42 +++++
 .../java/com/facebook/react/fabric/Work.java  |  20 +++
 .../fabric/events/FabricEventEmitter.java     | 163 ++++++++++++++++++
 .../react/uimanager/events/TouchesHelper.java |   8 +-
 7 files changed, 259 insertions(+), 4 deletions(-)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/JSHandler.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/Work.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
index 4674caa00f04..d4d239f3dad8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
@@ -2,7 +2,10 @@ load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_
 
 rn_android_library(
     name = "fabric",
-    srcs = glob(["*.java"]),
+    srcs = glob([
+        "*.java",
+        "events/*.java",
+    ]),
     provided_deps = [
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
     ],
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index e4285dff8747..a565012e52aa 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -21,6 +21,7 @@
 import com.facebook.react.bridge.ReadableNativeMap;
 import com.facebook.react.bridge.UIManager;
 import com.facebook.react.common.ReactConstants;
+import com.facebook.react.bridge.WritableMap;
 import com.facebook.react.common.annotations.VisibleForTesting;
 import com.facebook.react.modules.i18nmanager.I18nUtil;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
@@ -48,7 +49,7 @@
  * API.
  */
 @SuppressWarnings("unused") // used from JNI
-public class FabricUIManager implements UIManager {
+public class FabricUIManager implements UIManager, JSHandler {
 
   private static final String TAG = FabricUIManager.class.getSimpleName();
   private static final boolean DEBUG = true;
@@ -475,4 +476,11 @@ private void handleException(ReactShadowNode node, Throwable t) {
       throw new RuntimeException(ex.getMessage(), t);
     }
   }
+
+  @Override
+  public void invoke(int instanceHandle, String name, WritableMap params) {
+    Log.e(TAG, "Invoking '" + name + "' on instanceHandle: '" + instanceHandle  + "' from FabricUIManager.");
+    // -> call to C++
+  }
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/JSHandler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/JSHandler.java
new file mode 100644
index 000000000000..42b11c46d212
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/JSHandler.java
@@ -0,0 +1,15 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+package com.facebook.react.fabric;
+
+import com.facebook.react.bridge.WritableMap;
+
+public interface JSHandler {
+
+  void invoke(int instanceHandle, String name, WritableMap params);
+
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
new file mode 100644
index 000000000000..0f401f57e672
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
@@ -0,0 +1,42 @@
+package com.facebook.react.fabric;
+
+/**
+ * This class allows Native code to schedule work in JS.
+ * Work (following JS naming) represents a task that needs to be executed in JS.
+ *
+ * Four types of work are supported by this class:
+ *
+ * Synchronous:
+ *  - Sync work                   -> flushSync
+ *  - Work work                   -> flushSerial
+ *
+ * Asynchronous:
+ *  - Interactive work (serial):  -> scheduleSerial
+ *  - Deferred work:              -> scheduleWork
+ */
+public class Scheduler {
+
+  public Scheduler() {
+  }
+
+  public void scheduleWork(Work work) {
+    // TODO T26717866 this method needs to be implemented. The current implementation is just for
+    // testing purpose.
+    work.run();
+  }
+
+  public void flushSync(Work work) {
+    // TODO T26717866 this method needs to be implemented. The current implementation is just for
+    // testing purpose.
+  }
+
+  public void flushSerial(Work work) {
+    // TODO T26717866 this method needs to be implemented. The current implementation is just for
+    // testing purpose.
+  }
+
+  public void scheduleSerial(Work work) {
+    // TODO T26717866 this method needs to be implemented. The current implementation is just for
+    // testing purpose.
+  }
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/Work.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/Work.java
new file mode 100644
index 000000000000..d179b00439dc
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/Work.java
@@ -0,0 +1,20 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.fabric;
+
+/**
+ * Interface that represents a task or piece of code that will be executed by {@link Scheduler}
+ * This follows React API naming for consistency.
+ */
+public interface Work {
+
+  void run();
+
+}
+
+
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
new file mode 100644
index 000000000000..a9cd49ab3f95
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
@@ -0,0 +1,163 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.fabric.events;
+
+import static com.facebook.react.uimanager.events.TouchesHelper.CHANGED_TOUCHES_KEY;
+import static com.facebook.react.uimanager.events.TouchesHelper.TARGET_KEY;
+import static com.facebook.react.uimanager.events.TouchesHelper.TOP_TOUCH_CANCEL_KEY;
+import static com.facebook.react.uimanager.events.TouchesHelper.TOP_TOUCH_END_KEY;
+import static com.facebook.react.uimanager.events.TouchesHelper.TOUCHES_KEY;
+
+import android.annotation.TargetApi;
+import android.os.Build;
+import android.util.Log;
+import android.util.Pair;
+import com.facebook.react.bridge.ReadableMap;
+import com.facebook.react.bridge.WritableArray;
+import com.facebook.react.bridge.WritableMap;
+import com.facebook.react.bridge.WritableNativeArray;
+import com.facebook.react.bridge.WritableNativeMap;
+import com.facebook.react.fabric.FabricUIManager;
+import com.facebook.react.fabric.Scheduler;
+import com.facebook.react.fabric.Work;
+import com.facebook.react.uimanager.events.RCTEventEmitter;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Set;
+import javax.annotation.Nullable;
+
+@TargetApi(Build.VERSION_CODES.ECLAIR)
+public class FabricEventEmitter implements RCTEventEmitter {
+
+  private static final String TAG = FabricEventEmitter.class.getSimpleName();
+
+  private final FabricUIManager mFabricUIManager;
+  private final Scheduler mScheduler;
+
+  public FabricEventEmitter(Scheduler scheduler, FabricUIManager fabricUIManager) {
+    mScheduler = scheduler;
+    mFabricUIManager = fabricUIManager;
+  }
+
+  @Override
+  public void receiveEvent(int targetTag, String eventName, @Nullable WritableMap params) {
+    //TODO get instanceHandle associated with targetTag.
+    int instanceHandle = targetTag;
+    mScheduler.scheduleWork(new FabricUIManagerWork(instanceHandle, eventName, params) );
+  }
+
+  private class FabricUIManagerWork implements Work {
+    private final int mInstanceHandle;
+    private final String mEventName;
+    private final WritableMap mParams;
+
+    public FabricUIManagerWork(int instanceHandle, String eventName, @Nullable WritableMap params) {
+      mInstanceHandle = instanceHandle;
+      mEventName = eventName;
+      mParams = params;
+    }
+
+    @Override
+    public void run() {
+      mFabricUIManager.invoke(mInstanceHandle, mEventName, mParams);
+    }
+  }
+
+  @Override
+  public void receiveTouches(String eventTopLevelType, WritableArray touches,
+    WritableArray changedIndices) {
+    Pair<WritableArray, WritableArray> result =
+      TOP_TOUCH_END_KEY.equalsIgnoreCase(eventTopLevelType) ||
+        TOP_TOUCH_CANCEL_KEY.equalsIgnoreCase(eventTopLevelType)
+        ? removeTouchesAtIndices(touches, changedIndices)
+        : touchSubsequence(touches, changedIndices);
+
+    WritableArray changedTouches = result.first;
+    touches = result.second;
+
+    for (int jj = 0; jj < changedTouches.size(); jj++) {
+      WritableMap touch = getWritableMap(changedTouches.getMap(jj));
+      // Touch objects can fulfill the role of `DOM` `Event` objects if we set
+      // the `changedTouches`/`touches`. This saves allocations.
+      touch.putArray(CHANGED_TOUCHES_KEY, changedTouches);
+      touch.putArray(TOUCHES_KEY, touches);
+      WritableMap nativeEvent = touch;
+      int rootNodeID = 0;
+      int target = nativeEvent.getInt(TARGET_KEY);
+      if (target < 1) {
+        Log.e(TAG,"A view is reporting that a touch occurred on tag zero.");
+      } else {
+        rootNodeID = target;
+      }
+      receiveEvent(rootNodeID, eventTopLevelType, touch);
+    }
+  }
+
+  /**
+   * Destroys `touches` by removing touch objects at indices `indices`. This is
+   * to maintain compatibility with W3C touch "end" events, where the active
+   * touches don't include the set that has just been "ended".
+   *
+   * This method was originally in ReactNativeRenderer.js
+   *
+   * TODO: this method is a copy from ReactNativeRenderer.removeTouchesAtIndices and it needs
+   * to be rewritten in a more efficient way,
+   *
+   * @param touches {@link WritableArray} Deserialized touch objects.
+   * @param indices {WritableArray} Indices to remove from `touches`.
+   * @return {Array<Touch>} Subsequence of removed touch objects.
+   */
+  private Pair<WritableArray, WritableArray> removeTouchesAtIndices(WritableArray touches, WritableArray indices) {
+    WritableArray rippedOut = new WritableNativeArray();
+    // use an unsafe downcast to alias to nullable elements,
+    // so we can delete and then compact.
+    WritableArray tempTouches = new WritableNativeArray();
+    Set<Integer> rippedOutIndices = new HashSet<>();
+    for (int i = 0; i < indices.size(); i++) {
+      int index = indices.getInt(i);
+      rippedOut.pushMap(getWritableMap(touches.getMap(index)));
+      rippedOutIndices.add(index);
+    }
+    for (int j = 0 ; j < touches.size() ; j++) {
+      if (!rippedOutIndices.contains(j)) {
+        tempTouches.pushMap(getWritableMap(touches.getMap(j)));
+      }
+    }
+
+    return new Pair<>(rippedOut, tempTouches);
+  }
+
+  /**
+   * Selects a subsequence of `Touch`es, without destroying `touches`.
+   *
+   * This method was originally in ReactNativeRenderer.js
+   *
+   * @param touches {@link WritableArray} Deserialized touch objects.
+   * @param changedIndices {@link WritableArray} Indices by which to pull subsequence.
+   * @return {Array<Touch>} Subsequence of touch objects.
+   */
+  private Pair<WritableArray, WritableArray> touchSubsequence(WritableArray touches, WritableArray changedIndices) {
+    WritableArray result = new WritableNativeArray();
+    for (int i = 0; i < changedIndices.size(); i++) {
+      result.pushMap(getWritableMap(touches.getMap(i)));
+    }
+    return new Pair<>(result, touches);
+  }
+
+  /**
+   * TODO: this is required because the WritableNativeArray.getMap() returns a ReadableMap instead
+   * of the original writableMap. this will change in the near future.
+   *
+   * @param readableMap {@link ReadableMap} source map
+   */
+  private WritableMap getWritableMap(ReadableMap readableMap) {
+    WritableNativeMap map = new WritableNativeMap();
+    map.merge(readableMap);
+    return map;
+  }
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/TouchesHelper.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/TouchesHelper.java
index cf435590f702..59212aa830d3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/TouchesHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/TouchesHelper.java
@@ -17,11 +17,15 @@
 /**
  * Class responsible for generating catalyst touch events based on android {@link MotionEvent}.
  */
-/*package*/ class TouchesHelper {
+public class TouchesHelper {
 
+  public static final String TARGET_KEY = "target";
+  public static final String CHANGED_TOUCHES_KEY = "changedTouches";
+  public static final String TOUCHES_KEY = "touches";
+  public static final String TOP_TOUCH_END_KEY = "topTouchEnd";
+  public static final String TOP_TOUCH_CANCEL_KEY = "topTouchCancel";
   private static final String PAGE_X_KEY = "pageX";
   private static final String PAGE_Y_KEY = "pageY";
-  private static final String TARGET_KEY = "target";
   private static final String TIMESTAMP_KEY = "timestamp";
   private static final String POINTER_IDENTIFIER_KEY = "identifier";
 

From 58ea20b5e821b35980b3284b268e5d4e43a138a9 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 30 May 2018 21:48:52 -0700
Subject: [PATCH 0687/1109] Refactor setup of Event Dispatcher

Reviewed By: achen1

Differential Revision: D7746311

fbshipit-source-id: cfee1c2ced6d85477628085f3260496e80ae48c2
---
 .../react/testing/ReactAppTestActivity.java   | 56 +++++++++----------
 .../facebook/react/ReactInstanceManager.java  |  3 +
 .../react/bridge/EventDispatcher.java         | 13 +++++
 .../facebook/react/bridge/ReactContext.java   |  9 +++
 .../com/facebook/react/fabric/Scheduler.java  |  1 +
 .../react/uimanager/UIManagerModule.java      | 12 ++--
 .../uimanager/events/EventDispatcher.java     | 27 +++++----
 .../uimanager/events/RCTEventEmitter.java     |  4 +-
 .../uimanager/events/ReactEventEmitter.java   | 53 ++++++++++++++++++
 9 files changed, 127 insertions(+), 51 deletions(-)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/bridge/EventDispatcher.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index 307caf3c0170..e7e6d95e3603 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -7,11 +7,12 @@
 
 package com.facebook.react.testing;
 
+import static com.facebook.react.bridge.UiThreadUtil.runOnUiThread;
+
 import android.content.Intent;
 import android.graphics.Bitmap;
 import android.os.Bundle;
 import android.support.v4.app.FragmentActivity;
-import android.util.Log;
 import android.view.View;
 import android.view.ViewTreeObserver;
 import android.widget.FrameLayout;
@@ -38,7 +39,7 @@
 import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
-import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.List;
 import java.util.concurrent.CountDownLatch;
 import java.util.concurrent.TimeUnit;
@@ -244,35 +245,28 @@ public void loadBundle(
         .setBridgeIdleDebugListener(mBridgeIdleSignaler)
         .setInitialLifecycleState(mLifecycleState)
         .setJSIModulesProvider(
-            new JSIModulesProvider() {
-              @Override
-              public List<JSIModuleHolder> getJSIModules(
-                  final ReactApplicationContext reactApplicationContext,
-                  final JavaScriptContextHolder jsContext) {
-
-                List<JSIModuleHolder> modules = new ArrayList<>();
-                modules.add(
-                    new JSIModuleHolder() {
-
-                      @Override
-                      public Class<? extends JSIModule> getJSIModuleClass() {
-                        return UIManager.class;
-                      }
-
-                      @Override
-                      public FabricUIManager getJSIModule() {
-                        List<ViewManager> viewManagers =
-                          getReactInstanceManager().getOrCreateViewManagers(reactApplicationContext);
-                        FabricUIManager fabricUIManager =
-                            new FabricUIManager(
-                                reactApplicationContext, new ViewManagerRegistry(viewManagers));
-                        new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
-                        return fabricUIManager;
-                      }
-                    });
-
-                return modules;
-              }})
+          new JSIModulesProvider() {
+            @Override
+            public List<JSIModuleHolder> getJSIModules(
+              final ReactApplicationContext reactApplicationContext,
+              final JavaScriptContextHolder jsContext) {
+              return Arrays.<JSIModuleHolder>asList(new JSIModuleHolder() {
+                @Override
+                public Class<? extends JSIModule> getJSIModuleClass() {
+                  return UIManager.class;
+                }
+
+                @Override
+                public FabricUIManager getJSIModule() {
+                  List<ViewManager> viewManagers =
+                    mReactInstanceManager.getOrCreateViewManagers(reactApplicationContext);
+                  FabricUIManager fabricUIManager =
+                    new FabricUIManager(reactApplicationContext, new ViewManagerRegistry(viewManagers));
+                  new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
+                  return fabricUIManager;
+                }
+              });
+            }})
         .setUIImplementationProvider(uiImplementationProvider);
 
     final CountDownLatch latch = new CountDownLatch(1);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 45d678232124..7363d1dda2d2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -82,6 +82,7 @@
 import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerHelper;
 import com.facebook.react.uimanager.ViewManager;
+import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.views.imagehelper.ResourceDrawableIdHelper;
 import com.facebook.soloader.SoLoader;
 import com.facebook.systrace.Systrace;
@@ -1077,6 +1078,8 @@ private ReactApplicationContext createReactContext(
     ReactMarker.logMarker(CREATE_REACT_CONTEXT_START, jsExecutor.getName());
     final ReactApplicationContext reactContext = new ReactApplicationContext(mApplicationContext);
 
+    reactContext.setEventDispatcher(new EventDispatcher(reactContext));
+
     NativeModuleCallExceptionHandler exceptionHandler = mNativeModuleCallExceptionHandler != null
         ? mNativeModuleCallExceptionHandler
         : mDevSupportManager;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/EventDispatcher.java
new file mode 100644
index 000000000000..e596a478258d
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/EventDispatcher.java
@@ -0,0 +1,13 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+package com.facebook.react.bridge;
+
+/**
+ * Marker interface for EventDispatcher.
+ */
+public interface EventDispatcher {
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java
index 713f5a7fd815..cae4c7f5fe1e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java
@@ -39,6 +39,7 @@ public class ReactContext extends ContextWrapper {
 
   private LifecycleState mLifecycleState = LifecycleState.BEFORE_CREATE;
 
+  private @Nullable EventDispatcher mEventDispatcher;
   private @Nullable CatalystInstance mCatalystInstance;
   private @Nullable LayoutInflater mInflater;
   private @Nullable MessageQueueThread mUiMessageQueueThread;
@@ -349,4 +350,12 @@ public boolean startActivityForResult(Intent intent, int code, Bundle bundle) {
   public JavaScriptContextHolder getJavaScriptContextHolder() {
     return mCatalystInstance.getJavaScriptContextHolder();
   }
+
+  public <T extends EventDispatcher> T getEventDispatcher() {
+    return (T) mEventDispatcher;
+  }
+
+  public void setEventDispatcher(EventDispatcher eventDispatcher) {
+    mEventDispatcher = eventDispatcher;
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
index 0f401f57e672..87f7ce6db200 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
@@ -22,6 +22,7 @@ public Scheduler() {
   public void scheduleWork(Work work) {
     // TODO T26717866 this method needs to be implemented. The current implementation is just for
     // testing purpose.
+
     work.run();
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 3937f13deb9e..5a7c7d1ce360 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -9,12 +9,11 @@
 
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_END;
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_START;
-
 import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
 
 import android.content.ComponentCallbacks2;
-import android.content.res.Configuration;
 import android.content.Context;
+import android.content.res.Configuration;
 import android.media.AudioManager;
 import com.facebook.common.logging.FLog;
 import com.facebook.debug.holder.PrinterHolder;
@@ -42,6 +41,7 @@
 import com.facebook.react.uimanager.common.ViewUtil;
 import com.facebook.react.uimanager.debug.NotThreadSafeViewHierarchyUpdateDebugListener;
 import com.facebook.react.uimanager.events.EventDispatcher;
+import com.facebook.react.uimanager.events.RCTEventEmitter;
 import com.facebook.systrace.Systrace;
 import com.facebook.systrace.SystraceMessage;
 import java.util.ArrayList;
@@ -129,7 +129,7 @@ public UIManagerModule(
       int minTimeLeftInFrameForNonBatchedOperationMs) {
     super(reactContext);
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
-    mEventDispatcher = new EventDispatcher(reactContext);
+    mEventDispatcher = reactContext.getEventDispatcher();
     mModuleConstants = createConstants(viewManagerResolver);
     mCustomDirectEvents = UIManagerModuleConstants.getDirectEventTypeConstants();
     mUIImplementation =
@@ -149,7 +149,7 @@ public UIManagerModule(
       int minTimeLeftInFrameForNonBatchedOperationMs) {
     super(reactContext);
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
-    mEventDispatcher = new EventDispatcher(reactContext);
+    mEventDispatcher = reactContext.getEventDispatcher();
     mCustomDirectEvents = MapBuilder.newHashMap();
     mModuleConstants = createConstants(viewManagersList, null, mCustomDirectEvents);
     mUIImplementation =
@@ -182,10 +182,14 @@ public Map<String, Object> getConstants() {
   @Override
   public void initialize() {
     getReactApplicationContext().registerComponentCallbacks(mMemoryTrimCallback);
+    mEventDispatcher.registerEventEmitter(
+      DEFAULT,
+      getReactApplicationContext().getJSModule(RCTEventEmitter.class));
   }
 
   @Override
   public void onHostResume() {
+
     mUIImplementation.onHostResume();
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
index 7feddf17b0d4..c613f8685eee 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
@@ -7,16 +7,7 @@
 
 package com.facebook.react.uimanager.events;
 
-import javax.annotation.Nullable;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Comparator;
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicInteger;
-
 import android.util.LongSparseArray;
-
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.bridge.LifecycleEventListener;
 import com.facebook.react.bridge.ReactApplicationContext;
@@ -26,6 +17,12 @@
 import com.facebook.react.modules.core.ReactChoreographer;
 import com.facebook.react.uimanager.common.UIManagerType;
 import com.facebook.systrace.Systrace;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Comparator;
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicInteger;
+import javax.annotation.Nullable;
 
 /**
  * Class responsible for dispatching UI events to JS. The main purpose of this class is to act as an
@@ -59,7 +56,8 @@
  * EVENT_TYPE_ID_MASK =  0x0000ffff00000000
  * COALESCING_KEY_MASK = 0xffff000000000000
  */
-public class EventDispatcher implements LifecycleEventListener {
+public class EventDispatcher implements LifecycleEventListener,
+  com.facebook.react.bridge.EventDispatcher {
 
   private static final Comparator<Event> EVENT_COMPARATOR = new Comparator<Event>() {
     @Override
@@ -99,7 +97,7 @@ public int compare(Event lhs, Event rhs) {
 
   private Event[] mEventsToDispatch = new Event[16];
   private int mEventsToDispatchSize = 0;
-  private volatile @Nullable RCTEventEmitter mRCTEventEmitter;
+  private volatile @Nullable ReactEventEmitter mRCTEventEmitter = new ReactEventEmitter();
   private short mNextEventTypeId = 0;
   private volatile boolean mHasDispatchScheduled = false;
 
@@ -153,9 +151,6 @@ public void removeListener(EventDispatcherListener listener) {
 
   @Override
   public void onHostResume() {
-    if (mRCTEventEmitter == null) {
-      mRCTEventEmitter = mReactContext.getJSModule(RCTEventEmitter.class);
-    }
     mCurrentFrameCallback.maybePostFromNonUI();
   }
 
@@ -255,6 +250,10 @@ private static long getEventCookie(int viewTag, short eventTypeId, short coalesc
         (((long) coalescingKey) & 0xffff) << 48;
   }
 
+  public void registerEventEmitter(@UIManagerType int uiManagerType, RCTEventEmitter eventEmitter) {
+    mRCTEventEmitter.register(uiManagerType, eventEmitter);
+  }
+
   private class ScheduleDispatchFrameCallback extends ChoreographerCompat.FrameCallback {
     private volatile boolean mIsPosted = false;
     private boolean mShouldStop = false;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/RCTEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/RCTEventEmitter.java
index b964186059f3..a46d0b3ea898 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/RCTEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/RCTEventEmitter.java
@@ -14,8 +14,8 @@
 import com.facebook.react.bridge.WritableMap;
 
 public interface RCTEventEmitter extends JavaScriptModule {
-  public void receiveEvent(int targetTag, String eventName, @Nullable WritableMap event);
-  public void receiveTouches(
+  void receiveEvent(int targetTag, String eventName, @Nullable WritableMap event);
+  void receiveTouches(
       String eventName,
       WritableArray touches,
       WritableArray changedIndices);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
new file mode 100644
index 000000000000..713ce32dbeee
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
@@ -0,0 +1,53 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.uimanager.events;
+
+import static com.facebook.react.uimanager.events.TouchesHelper.TARGET_KEY;
+
+import android.util.SparseArray;
+import com.facebook.infer.annotation.Assertions;
+import com.facebook.react.bridge.WritableArray;
+import com.facebook.react.bridge.WritableMap;
+import com.facebook.react.uimanager.common.UIManagerType;
+import com.facebook.react.uimanager.common.ViewUtil;
+import javax.annotation.Nullable;
+
+public class ReactEventEmitter implements RCTEventEmitter {
+
+  private final SparseArray<RCTEventEmitter> mEventEmitters = new SparseArray<>();
+
+  public ReactEventEmitter() {
+  }
+
+  public void register(@UIManagerType int uiManagerType, RCTEventEmitter eventEmitter) {
+    mEventEmitters.put(uiManagerType, eventEmitter);
+  }
+
+  @Override
+  public void receiveEvent(int targetReactTag, String eventName, @Nullable WritableMap event) {
+    getEventEmitter(targetReactTag).receiveEvent(targetReactTag, eventName, event);
+  }
+
+  @Override
+  public void receiveTouches(
+    String eventName,
+    WritableArray touches,
+    WritableArray changedIndices) {
+
+    Assertions.assertCondition(touches.size() > 0);
+
+    int targetReactTag = touches.getMap(0).getInt(TARGET_KEY);
+    getEventEmitter(targetReactTag).receiveTouches(eventName, touches, changedIndices);
+  }
+
+  private RCTEventEmitter getEventEmitter(int reactTag) {
+    int type = ViewUtil.getUIManagerType(reactTag);
+    return mEventEmitters.get(type);
+  }
+
+}

From a04ad8d8fbf789ce0e2f83ba766c7a8b4b647f85 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 30 May 2018 21:48:57 -0700
Subject: [PATCH 0688/1109] First implementation of scheduleWork method

Reviewed By: shergin

Differential Revision: D7799412

fbshipit-source-id: b78a0bc0e80868f6877a31f862d7e6104fd4a049
---
 .../com/facebook/react/fabric/Scheduler.java  | 72 ++++++++++++++++---
 .../fabric/events/FabricEventEmitter.java     | 14 +++-
 .../uimanager/events/EventDispatcher.java     | 11 +--
 .../uimanager/events/ReactEventEmitter.java   | 19 ++++-
 .../react/views/image/ImageLoadEvent.java     |  5 +-
 5 files changed, 97 insertions(+), 24 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
index 87f7ce6db200..9fb7bddb394d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
@@ -1,5 +1,13 @@
 package com.facebook.react.fabric;
 
+import android.util.Log;
+import com.facebook.react.bridge.ReactContext;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.LinkedBlockingDeque;
+import java.util.concurrent.RejectedExecutionException;
+import java.util.concurrent.ThreadPoolExecutor;
+import java.util.concurrent.TimeUnit;
+
 /**
  * This class allows Native code to schedule work in JS.
  * Work (following JS naming) represents a task that needs to be executed in JS.
@@ -7,23 +15,59 @@
  * Four types of work are supported by this class:
  *
  * Synchronous:
- *  - Sync work                   -> flushSync
- *  - Work work                   -> flushSerial
+ * - Sync work                   -> flushSync()
+ * - Work work                   -> flushSerial()
  *
  * Asynchronous:
- *  - Interactive work (serial):  -> scheduleSerial
- *  - Deferred work:              -> scheduleWork
+ * - Interactive work (serial):  -> scheduleSerial()
+ * - Deferred work:              -> scheduleWork()
+ *
  */
 public class Scheduler {
 
-  public Scheduler() {
-  }
+  private static final String TAG = Scheduler.class.getSimpleName();
+  // The usage of this executor might change in the near future.
+  private final ExecutorService mExecutor = new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingDeque<Runnable>());
+  private final ReactContext mReactContext;
 
-  public void scheduleWork(Work work) {
-    // TODO T26717866 this method needs to be implemented. The current implementation is just for
-    // testing purpose.
+  public Scheduler(ReactContext reactContext) {
+    mReactContext = reactContext;
+  }
 
-    work.run();
+  /**
+   * This method schedules work to be executed with the lowest priority in the JS Thread.
+   *
+   * The current implementation queues "work"s in an unbounded queue tight to a SingleThreadExecutor.
+   * Work objects are going to be submitted one-by-one at the end of the JS Queue Thread.
+   *
+   * Notice that the current implementation might experience some delays in JS work execution,
+   * depending on the size of the JS Queue and the time it takes to execute each work in JS.
+   *
+   * TODO: This implementation is very likely to change in the near future.
+   */
+  public void scheduleWork(final Work work) {
+    try {
+      mExecutor.execute(new Runnable() {
+        @Override
+        public void run() {
+          mReactContext.runOnJSQueueThread(new Runnable() {
+            @Override
+            public void run() {
+              try {
+                work.run();
+              } catch (Exception ex) {
+                Log.w(TAG, "Exception running work in JS.", ex);
+                throw ex;
+              }
+            }
+          });
+        }
+      });
+    } catch (RejectedExecutionException ex) {
+      // This can happen if a Work is scheduled when the Scheduler is being shutdown.
+      // For now, we log and do not take any action.
+      Log.i(TAG, "Unable to schedule task.");
+    }
   }
 
   public void flushSync(Work work) {
@@ -40,4 +84,12 @@ public void scheduleSerial(Work work) {
     // TODO T26717866 this method needs to be implemented. The current implementation is just for
     // testing purpose.
   }
+
+  /**
+   * Shutdowns the {@link Scheduler}. this operation will attempt to stop all "active executing"
+   * Works items and it will "halts:" all the Works items waiting to be executed.
+   */
+  public void shutdown() {
+    mExecutor.shutdownNow();
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
index a9cd49ab3f95..59c701e67e21 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
@@ -17,6 +17,7 @@
 import android.os.Build;
 import android.util.Log;
 import android.util.Pair;
+import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.WritableArray;
 import com.facebook.react.bridge.WritableMap;
@@ -26,21 +27,23 @@
 import com.facebook.react.fabric.Scheduler;
 import com.facebook.react.fabric.Work;
 import com.facebook.react.uimanager.events.RCTEventEmitter;
+import java.io.Closeable;
+import java.io.IOException;
 import java.util.Arrays;
 import java.util.HashSet;
 import java.util.Set;
 import javax.annotation.Nullable;
 
 @TargetApi(Build.VERSION_CODES.ECLAIR)
-public class FabricEventEmitter implements RCTEventEmitter {
+public class FabricEventEmitter implements RCTEventEmitter, Closeable {
 
   private static final String TAG = FabricEventEmitter.class.getSimpleName();
 
   private final FabricUIManager mFabricUIManager;
   private final Scheduler mScheduler;
 
-  public FabricEventEmitter(Scheduler scheduler, FabricUIManager fabricUIManager) {
-    mScheduler = scheduler;
+  public FabricEventEmitter(ReactApplicationContext context, FabricUIManager fabricUIManager) {
+    mScheduler = new Scheduler(context);
     mFabricUIManager = fabricUIManager;
   }
 
@@ -51,6 +54,11 @@ public void receiveEvent(int targetTag, String eventName, @Nullable WritableMap
     mScheduler.scheduleWork(new FabricUIManagerWork(instanceHandle, eventName, params) );
   }
 
+  @Override
+  public void close() {
+    mScheduler.shutdown();
+  }
+
   private class FabricUIManagerWork implements Work {
     private final int mInstanceHandle;
     private final String mEventName;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
index c613f8685eee..ad15ce0a8cf4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
@@ -97,7 +97,7 @@ public int compare(Event lhs, Event rhs) {
 
   private Event[] mEventsToDispatch = new Event[16];
   private int mEventsToDispatchSize = 0;
-  private volatile @Nullable ReactEventEmitter mRCTEventEmitter = new ReactEventEmitter();
+  private volatile @Nullable ReactEventEmitter mReactEventEmitter = new ReactEventEmitter();
   private short mNextEventTypeId = 0;
   private volatile boolean mHasDispatchScheduled = false;
 
@@ -123,7 +123,7 @@ public void dispatchEvent(Event event) {
           event.getEventName(),
           event.getUniqueID());
     }
-    if (mRCTEventEmitter != null) {
+    if (mReactEventEmitter != null) {
       // If the host activity is paused, the frame callback may not be currently
       // posted. Ensure that it is so that this event gets delivered promptly.
       mCurrentFrameCallback.maybePostFromNonUI();
@@ -162,6 +162,7 @@ public void onHostPause() {
   @Override
   public void onHostDestroy() {
     stopFrameCallback();
+    mReactEventEmitter.stop();
   }
 
   public void onCatalystInstanceDestroyed() {
@@ -251,7 +252,7 @@ private static long getEventCookie(int viewTag, short eventTypeId, short coalesc
   }
 
   public void registerEventEmitter(@UIManagerType int uiManagerType, RCTEventEmitter eventEmitter) {
-    mRCTEventEmitter.register(uiManagerType, eventEmitter);
+    mReactEventEmitter.register(uiManagerType, eventEmitter);
   }
 
   private class ScheduleDispatchFrameCallback extends ChoreographerCompat.FrameCallback {
@@ -331,7 +332,7 @@ public void run() {
             "ScheduleDispatchFrameCallback",
             mHasDispatchScheduledCount.getAndIncrement());
         mHasDispatchScheduled = false;
-        Assertions.assertNotNull(mRCTEventEmitter);
+        Assertions.assertNotNull(mReactEventEmitter);
         synchronized (mEventsToDispatchLock) {
           // We avoid allocating an array and iterator, and "sorting" if we don't need to.
           // This occurs when the size of mEventsToDispatch is zero or one.
@@ -348,7 +349,7 @@ public void run() {
                 Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
                 event.getEventName(),
                 event.getUniqueID());
-            event.dispatch(mRCTEventEmitter);
+            event.dispatch(mReactEventEmitter);
             event.dispose();
           }
           clearEventsToDispatch();
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
index 713ce32dbeee..c54af221290a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
@@ -9,20 +9,23 @@
 
 import static com.facebook.react.uimanager.events.TouchesHelper.TARGET_KEY;
 
+import android.util.Log;
 import android.util.SparseArray;
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.bridge.WritableArray;
 import com.facebook.react.bridge.WritableMap;
 import com.facebook.react.uimanager.common.UIManagerType;
 import com.facebook.react.uimanager.common.ViewUtil;
+import java.io.Closeable;
+import java.io.IOException;
 import javax.annotation.Nullable;
 
 public class ReactEventEmitter implements RCTEventEmitter {
 
+  private static final String TAG = ReactEventEmitter.class.getSimpleName();
   private final SparseArray<RCTEventEmitter> mEventEmitters = new SparseArray<>();
 
-  public ReactEventEmitter() {
-  }
+  public ReactEventEmitter() { }
 
   public void register(@UIManagerType int uiManagerType, RCTEventEmitter eventEmitter) {
     mEventEmitters.put(uiManagerType, eventEmitter);
@@ -50,4 +53,16 @@ private RCTEventEmitter getEventEmitter(int reactTag) {
     return mEventEmitters.get(type);
   }
 
+  public void stop() {
+    for (int i = 0 ; i < mEventEmitters.size() ; i++) {
+      RCTEventEmitter eventEmitter = mEventEmitters.valueAt(i);
+      if (eventEmitter instanceof Closeable) {
+        try {
+          ((Closeable) eventEmitter).close();
+        } catch (IOException e) {
+          Log.i(TAG, "Exception when closing EventEmitter: " + eventEmitter, e);
+        }
+      }
+    }
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ImageLoadEvent.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ImageLoadEvent.java
index d21984a3f306..2c85c4ad7abb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ImageLoadEvent.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ImageLoadEvent.java
@@ -7,17 +7,14 @@
 
 package com.facebook.react.views.image;
 
-import javax.annotation.Nullable;
-
 import android.support.annotation.IntDef;
-
 import com.facebook.react.bridge.Arguments;
 import com.facebook.react.bridge.WritableMap;
 import com.facebook.react.uimanager.events.Event;
 import com.facebook.react.uimanager.events.RCTEventEmitter;
-
 import java.lang.annotation.Retention;
 import java.lang.annotation.RetentionPolicy;
+import javax.annotation.Nullable;
 
 public class ImageLoadEvent extends Event<ImageLoadEvent> {
   @IntDef({ON_ERROR, ON_LOAD, ON_LOAD_END, ON_LOAD_START, ON_PROGRESS})

From 54acf3a431bb40b7ccbfc0dee2e3ce1486b91094 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 30 May 2018 21:49:03 -0700
Subject: [PATCH 0689/1109] Deprecate UIManagerModule#getEventDispatcher and
 refactor usages

Reviewed By: shergin

Differential Revision: D7832079

fbshipit-source-id: 263a2f8ff96ab6e14b91395644710b4d5f36dc50
---
 .../com/facebook/react/ReactRootView.java     |  6 ++---
 .../facebook/react/flat/FlatViewGroup.java    | 16 +++++--------
 .../react/uimanager/ThemedReactContext.java   |  6 +++++
 .../react/uimanager/UIManagerModule.java      |  5 ++++
 .../views/checkbox/ReactCheckBoxManager.java  |  5 ++--
 .../drawer/ReactDrawerLayoutManager.java      | 12 ++++------
 .../react/views/image/ReactImageView.java     |  6 +----
 .../views/modal/ReactModalHostManager.java    |  7 ++----
 .../react/views/modal/ReactModalHostView.java |  2 +-
 .../views/picker/ReactPickerManager.java      |  7 ++----
 .../views/scroll/ReactScrollViewHelper.java   |  5 ++--
 .../views/slider/ReactSliderManager.java      |  8 +++----
 .../SwipeRefreshLayoutManager.java            | 13 ++++-------
 .../views/switchview/ReactSwitchManager.java  | 15 ++++++------
 .../ReactEditTextInputConnectionWrapper.java  |  6 ++---
 .../textinput/ReactTextInputManager.java      | 13 +++++------
 .../views/toolbar/ReactToolbarManager.java    |  4 +---
 .../react/views/viewpager/ReactViewPager.java |  3 +--
 .../views/webview/ReactWebViewManager.java    | 23 +++++++++++--------
 19 files changed, 71 insertions(+), 91 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 4599484e298c..66d9db35375c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -194,8 +194,7 @@ public void onChildStartedNativeGesture(MotionEvent androidEvent) {
       return;
     }
     ReactContext reactContext = mReactInstanceManager.getCurrentReactContext();
-    EventDispatcher eventDispatcher = reactContext.getNativeModule(UIManagerModule.class)
-      .getEventDispatcher();
+    EventDispatcher eventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
     mJSTouchDispatcher.onChildStartedNativeGesture(androidEvent, eventDispatcher);
   }
 
@@ -281,8 +280,7 @@ private void dispatchJSTouchEvent(MotionEvent event) {
       return;
     }
     ReactContext reactContext = mReactInstanceManager.getCurrentReactContext();
-    EventDispatcher eventDispatcher = reactContext.getNativeModule(UIManagerModule.class)
-      .getEventDispatcher();
+    EventDispatcher eventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
     mJSTouchDispatcher.handleTouchEvent(event, eventDispatcher);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
index ae94b744b9fd..bfbeb130f56a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
@@ -7,11 +7,6 @@
 
 package com.facebook.react.flat;
 
-import javax.annotation.Nullable;
-
-import java.lang.ref.WeakReference;
-import java.util.ArrayList;
-
 import android.annotation.SuppressLint;
 import android.content.Context;
 import android.graphics.Canvas;
@@ -26,7 +21,6 @@
 import android.view.View;
 import android.view.ViewGroup;
 import android.view.ViewParent;
-
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.bridge.SoftAssertions;
@@ -34,11 +28,14 @@
 import com.facebook.react.touch.ReactHitSlopView;
 import com.facebook.react.touch.ReactInterceptingViewGroup;
 import com.facebook.react.uimanager.PointerEvents;
+import com.facebook.react.uimanager.ReactClippingViewGroup;
 import com.facebook.react.uimanager.ReactCompoundViewGroup;
 import com.facebook.react.uimanager.ReactPointerEventsView;
-import com.facebook.react.uimanager.UIManagerModule;
+import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.views.image.ImageLoadEvent;
-import com.facebook.react.uimanager.ReactClippingViewGroup;
+import java.lang.ref.WeakReference;
+import java.util.ArrayList;
+import javax.annotation.Nullable;
 
 /**
  * A view that the {@link FlatShadowNode} hierarchy maps to.  Can mount and draw native views as
@@ -129,8 +126,7 @@ public void dispatchImageLoadEvent(int reactTag, int imageLoadEvent) {
       }
 
       ReactContext reactContext = ((ReactContext) view.getContext());
-      UIManagerModule uiManagerModule = reactContext.getNativeModule(UIManagerModule.class);
-      uiManagerModule.getEventDispatcher().dispatchEvent(
+      reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
           new ImageLoadEvent(reactTag, imageLoadEvent));
     }
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ThemedReactContext.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ThemedReactContext.java
index 375df0d05ff8..8a6ab8670f3a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ThemedReactContext.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ThemedReactContext.java
@@ -7,6 +7,7 @@
 
 package com.facebook.react.uimanager;
 
+import com.facebook.react.bridge.EventDispatcher;
 import javax.annotation.Nullable;
 
 import android.app.Activity;
@@ -55,4 +56,9 @@ public boolean hasCurrentActivity() {
   public @Nullable Activity getCurrentActivity() {
     return mReactApplicationContext.getCurrentActivity();
   }
+
+  @Override
+  public <T extends EventDispatcher> T getEventDispatcher() {
+    return mReactApplicationContext.getEventDispatcher();
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 5a7c7d1ce360..e0dd1dc4ef16 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -26,6 +26,7 @@
 import com.facebook.react.bridge.OnBatchCompleteListener;
 import com.facebook.react.bridge.PerformanceCounter;
 import com.facebook.react.bridge.ReactApplicationContext;
+import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.bridge.ReactContextBaseJavaModule;
 import com.facebook.react.bridge.ReactMarker;
 import com.facebook.react.bridge.ReactMethod;
@@ -703,6 +704,10 @@ public void setViewHierarchyUpdateDebugListener(
     mUIImplementation.setViewHierarchyUpdateDebugListener(listener);
   }
 
+  /**
+   * This method is deprecated, use {@link ReactContext#getEventDispatcher()}.
+   */
+  @Deprecated
   public EventDispatcher getEventDispatcher() {
     return mEventDispatcher;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBoxManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBoxManager.java
index e71c601f4e7b..bbc3f46504d4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBoxManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBoxManager.java
@@ -10,9 +10,9 @@
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
+import com.facebook.react.uimanager.events.EventDispatcher;
 
 /** View manager for {@link ReactCheckBox} components. */
 public class ReactCheckBoxManager extends SimpleViewManager<ReactCheckBox> {
@@ -25,8 +25,7 @@ public class ReactCheckBoxManager extends SimpleViewManager<ReactCheckBox> {
         public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
           ReactContext reactContext = (ReactContext) buttonView.getContext();
           reactContext
-              .getNativeModule(UIManagerModule.class)
-              .getEventDispatcher()
+              .<EventDispatcher>getEventDispatcher()
               .dispatchEvent(new ReactCheckBoxEvent(buttonView.getId(), isChecked));
         }
       };
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java
index 1620d637a9d9..b7d90bb49fd0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java
@@ -7,16 +7,10 @@
 
 package com.facebook.react.views.drawer;
 
-import javax.annotation.Nullable;
-
-import java.lang.reflect.Method;
-import java.util.Map;
-
 import android.os.Build;
 import android.support.v4.widget.DrawerLayout;
 import android.view.Gravity;
 import android.view.View;
-
 import com.facebook.common.logging.FLog;
 import com.facebook.react.bridge.JSApplicationIllegalArgumentException;
 import com.facebook.react.bridge.ReadableArray;
@@ -25,7 +19,6 @@
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewGroupManager;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -33,6 +26,9 @@
 import com.facebook.react.views.drawer.events.DrawerOpenedEvent;
 import com.facebook.react.views.drawer.events.DrawerSlideEvent;
 import com.facebook.react.views.drawer.events.DrawerStateChangedEvent;
+import java.lang.reflect.Method;
+import java.util.Map;
+import javax.annotation.Nullable;
 
 /**
  * View Manager for {@link ReactDrawerLayout} components.
@@ -55,7 +51,7 @@ protected void addEventEmitters(ThemedReactContext reactContext, ReactDrawerLayo
     view.setDrawerListener(
         new DrawerEventEmitter(
             view,
-            reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher()));
+            reactContext.<EventDispatcher>getEventDispatcher()));
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index cb294cbb93d7..90d053c5faa9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -30,7 +30,6 @@
 import com.facebook.drawee.controller.ForwardingControllerListener;
 import com.facebook.drawee.drawable.AutoRotateDrawable;
 import com.facebook.drawee.drawable.RoundedColorDrawable;
-
 import com.facebook.drawee.drawable.ScalingUtils;
 import com.facebook.drawee.generic.GenericDraweeHierarchy;
 import com.facebook.drawee.generic.GenericDraweeHierarchyBuilder;
@@ -51,9 +50,7 @@
 import com.facebook.react.modules.fresco.ReactNetworkImageRequest;
 import com.facebook.react.uimanager.FloatUtil;
 import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
-import com.facebook.react.views.image.ImageResizeMode;
 import com.facebook.react.views.imagehelper.ImageSource;
 import com.facebook.react.views.imagehelper.MultiSourceHelper;
 import com.facebook.react.views.imagehelper.MultiSourceHelper.MultiSourceResult;
@@ -234,8 +231,7 @@ public void setShouldNotifyLoadEvents(boolean shouldNotify) {
     if (!shouldNotify) {
       mControllerListener = null;
     } else {
-      final EventDispatcher mEventDispatcher = ((ReactContext) getContext()).
-        getNativeModule(UIManagerModule.class).getEventDispatcher();
+      final EventDispatcher mEventDispatcher = ((ReactContext) getContext()).<EventDispatcher>getEventDispatcher();
 
       mControllerListener = new BaseControllerListener<ImageInfo>() {
         @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java
index 0f67e9c9e0bb..fa193e0fa307 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java
@@ -7,18 +7,15 @@
 
 package com.facebook.react.views.modal;
 
-import java.util.Map;
-
 import android.content.DialogInterface;
-
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.LayoutShadowNode;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewGroupManager;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
+import java.util.Map;
 
 /**
  * View manager for {@link ReactModalHostView} components.
@@ -74,7 +71,7 @@ protected void addEventEmitters(
       ThemedReactContext reactContext,
       final ReactModalHostView view) {
     final EventDispatcher dispatcher =
-      reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+      reactContext.<EventDispatcher>getEventDispatcher();
     view.setOnRequestCloseListener(
       new ReactModalHostView.OnRequestCloseListener() {
         @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
index ab0491fe4619..5651e7da89f2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
@@ -370,7 +370,7 @@ public void requestDisallowInterceptTouchEvent(boolean disallowIntercept) {
 
     private EventDispatcher getEventDispatcher() {
       ReactContext reactContext = getReactContext();
-      return reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+      return reactContext.<EventDispatcher>getEventDispatcher();
     }
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java
index 59f5461ab607..9bc18c887751 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java
@@ -7,8 +7,6 @@
 
 package com.facebook.react.views.picker;
 
-import javax.annotation.Nullable;
-
 import android.content.Context;
 import android.view.LayoutInflater;
 import android.view.View;
@@ -16,17 +14,16 @@
 import android.widget.ArrayAdapter;
 import android.widget.Spinner;
 import android.widget.TextView;
-
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.views.picker.events.PickerItemSelectEvent;
+import javax.annotation.Nullable;
 
 /**
  * {@link ViewManager} for the {@link ReactPicker} view. This is abstract because the
@@ -89,7 +86,7 @@ protected void addEventEmitters(
     picker.setOnSelectListener(
             new PickerEventEmitter(
                     picker,
-                    reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher()));
+                    reactContext.<EventDispatcher>getEventDispatcher()));
   }
 
   private static class ReactPickerAdapter extends ArrayAdapter<ReadableMap> {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java
index a034694b4bd9..05ce0d596ed4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java
@@ -9,10 +9,9 @@
 
 import android.view.View;
 import android.view.ViewGroup;
-
 import com.facebook.react.bridge.JSApplicationIllegalArgumentException;
 import com.facebook.react.bridge.ReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
+import com.facebook.react.uimanager.events.EventDispatcher;
 
 /**
  * Helper class that deals with emitting Scroll Events.
@@ -69,7 +68,7 @@ private static void emitScrollEvent(
     }
 
     ReactContext reactContext = (ReactContext) scrollView.getContext();
-    reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
+    reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
         ScrollEvent.obtain(
             scrollView.getId(),
             scrollEventType,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
index 1cd9c261103e..dd8008d5b130 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
@@ -13,21 +13,19 @@
 import android.view.View;
 import android.view.ViewGroup;
 import android.widget.SeekBar;
-
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.uimanager.LayoutShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
+import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.yoga.YogaMeasureFunction;
 import com.facebook.yoga.YogaMeasureMode;
 import com.facebook.yoga.YogaMeasureOutput;
 import com.facebook.yoga.YogaNode;
-
 import java.util.Map;
 
 /**
@@ -109,7 +107,7 @@ public long measure(
         @Override
         public void onProgressChanged(SeekBar seekbar, int progress, boolean fromUser) {
           ReactContext reactContext = (ReactContext) seekbar.getContext();
-          reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
+          reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
               new ReactSliderEvent(
                   seekbar.getId(),
                   ((ReactSlider) seekbar).toRealProgress(progress),
@@ -123,7 +121,7 @@ public void onStartTrackingTouch(SeekBar seekbar) {
         @Override
         public void onStopTrackingTouch(SeekBar seekbar) {
           ReactContext reactContext = (ReactContext) seekbar.getContext();
-          reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
+          reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
               new ReactSlidingCompleteEvent(
                   seekbar.getId(),
                   ((ReactSlider) seekbar).toRealProgress(seekbar.getProgress())));
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java
index 4988129234ed..387f931c1245 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java
@@ -7,24 +7,21 @@
 
 package com.facebook.react.views.swiperefresh;
 
-import javax.annotation.Nullable;
-
-import java.util.Map;
+import static com.facebook.react.views.swiperefresh.SwipeRefreshLayoutManager.REACT_CLASS;
 
 import android.graphics.Color;
 import android.support.v4.widget.SwipeRefreshLayout;
 import android.support.v4.widget.SwipeRefreshLayout.OnRefreshListener;
-
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewGroupManager;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
-
-import static com.facebook.react.views.swiperefresh.SwipeRefreshLayoutManager.REACT_CLASS;
+import com.facebook.react.uimanager.events.EventDispatcher;
+import java.util.Map;
+import javax.annotation.Nullable;
 
 /**
  * ViewManager for {@link ReactSwipeRefreshLayout} which allows the user to "pull to refresh" a
@@ -91,7 +88,7 @@ protected void addEventEmitters(
         new OnRefreshListener() {
           @Override
           public void onRefresh() {
-            reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher()
+            reactContext.<EventDispatcher>getEventDispatcher()
                 .dispatchEvent(new RefreshEvent(view.getId()));
           }
         });
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
index 70c5a5123e94..a1a576b37667 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
@@ -12,19 +12,18 @@
 import android.view.View;
 import android.view.ViewGroup;
 import android.widget.CompoundButton;
-
-import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import com.facebook.yoga.YogaMeasureMode;
-import com.facebook.yoga.YogaMeasureFunction;
-import com.facebook.yoga.YogaNode;
-import com.facebook.yoga.YogaMeasureOutput;
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.uimanager.LayoutShadowNode;
+import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
+import com.facebook.react.uimanager.events.EventDispatcher;
+import com.facebook.yoga.YogaMeasureFunction;
+import com.facebook.yoga.YogaMeasureMode;
+import com.facebook.yoga.YogaMeasureOutput;
+import com.facebook.yoga.YogaNode;
 
 /**
  * View manager for {@link ReactSwitch} components.
@@ -105,7 +104,7 @@ public long measure(
         @Override
         public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
           ReactContext reactContext = (ReactContext) buttonView.getContext();
-          reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
+          reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
               new ReactSwitchEvent(
                   buttonView.getId(),
                   isChecked));
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditTextInputConnectionWrapper.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditTextInputConnectionWrapper.java
index cc2976efdf86..8f7f631caadd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditTextInputConnectionWrapper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditTextInputConnectionWrapper.java
@@ -7,15 +7,13 @@
 
 package com.facebook.react.views.textinput;
 
-import javax.annotation.Nullable;
-
 import android.view.KeyEvent;
 import android.view.inputmethod.EditorInfo;
 import android.view.inputmethod.InputConnection;
 import android.view.inputmethod.InputConnectionWrapper;
 import com.facebook.react.bridge.ReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
+import javax.annotation.Nullable;
 
 /**
  * A class to implement the TextInput 'onKeyPress' API on android for soft keyboards.
@@ -66,7 +64,7 @@ public ReactEditTextInputConnectionWrapper(
       final ReactEditText editText
   ) {
     super(target, false);
-    mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+    mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
     mEditText = editText;
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
index fa3c275c6867..74671b06a832 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
@@ -34,7 +34,6 @@
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.Spacing;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewDefaults;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
@@ -694,7 +693,7 @@ private class ReactTextInputTextWatcher implements TextWatcher {
     public ReactTextInputTextWatcher(
         final ReactContext reactContext,
         final ReactEditText editText) {
-      mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+      mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
       mEditText = editText;
       mPreviousText = null;
     }
@@ -752,7 +751,7 @@ protected void addEventEmitters(
         new View.OnFocusChangeListener() {
           public void onFocusChange(View v, boolean hasFocus) {
             EventDispatcher eventDispatcher =
-                reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+                reactContext.<EventDispatcher>getEventDispatcher();
             if (hasFocus) {
               eventDispatcher.dispatchEvent(
                   new ReactTextInputFocusEvent(
@@ -789,7 +788,7 @@ public boolean onEditorAction(TextView v, int actionId, KeyEvent keyEvent) {
               // Additionally we always generate a `submit` event.
 
               EventDispatcher eventDispatcher =
-                  reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+                  reactContext.<EventDispatcher>getEventDispatcher();
 
               eventDispatcher.dispatchEvent(
                   new ReactTextInputSubmitEditingEvent(
@@ -818,7 +817,7 @@ private class ReactContentSizeWatcher implements ContentSizeWatcher {
     public ReactContentSizeWatcher(ReactEditText editText) {
       mEditText = editText;
       ReactContext reactContext = (ReactContext) editText.getContext();
-      mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+      mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
     }
 
     @Override
@@ -857,7 +856,7 @@ private class ReactSelectionWatcher implements SelectionWatcher {
     public ReactSelectionWatcher(ReactEditText editText) {
       mReactEditText = editText;
       ReactContext reactContext = (ReactContext) editText.getContext();
-      mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+      mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
     }
 
     @Override
@@ -889,7 +888,7 @@ private class ReactScrollWatcher implements ScrollWatcher {
     public ReactScrollWatcher(ReactEditText editText) {
       mReactEditText = editText;
       ReactContext reactContext = (ReactContext) editText.getContext();
-      mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+      mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
     }
 
     @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
index 0de356f1b95e..805d6ec56761 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
@@ -19,7 +19,6 @@
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewGroupManager;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -118,8 +117,7 @@ public void setActions(ReactToolbar view, @Nullable ReadableArray actions) {
 
   @Override
   protected void addEventEmitters(final ThemedReactContext reactContext, final ReactToolbar view) {
-    final EventDispatcher mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class)
-        .getEventDispatcher();
+    final EventDispatcher mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
     view.setNavigationOnClickListener(
         new View.OnClickListener() {
           @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java b/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java
index 48b5f1a61949..1bc2e36f61fe 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java
@@ -15,7 +15,6 @@
 import android.view.ViewGroup;
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.common.ReactConstants;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.uimanager.events.NativeGestureUtil;
 import java.util.ArrayList;
@@ -159,7 +158,7 @@ public void onPageScrollStateChanged(int state) {
 
   public ReactViewPager(ReactContext reactContext) {
     super(reactContext);
-    mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+    mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
     mIsCurrentItemFromJs = false;
     setOnPageChangeListener(new PageChangeListener());
     setAdapter(new Adapter());
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
index 7f07b2742677..df6c8776270e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
@@ -29,17 +29,15 @@
 import android.text.TextUtils;
 import android.view.ViewGroup.LayoutParams;
 import android.webkit.ConsoleMessage;
+import android.webkit.CookieManager;
 import android.webkit.GeolocationPermissions;
-import android.webkit.WebChromeClient;
-import android.webkit.WebView;
-import android.webkit.WebViewClient;
 import android.webkit.JavascriptInterface;
 import android.webkit.ValueCallback;
+import android.webkit.WebChromeClient;
 import android.webkit.WebSettings;
-import android.webkit.CookieManager;
-
+import android.webkit.WebView;
+import android.webkit.WebViewClient;
 import com.facebook.common.logging.FLog;
-import com.facebook.react.common.ReactConstants;
 import com.facebook.react.bridge.Arguments;
 import com.facebook.react.bridge.LifecycleEventListener;
 import com.facebook.react.bridge.ReactContext;
@@ -48,11 +46,11 @@
 import com.facebook.react.bridge.ReadableMapKeySetIterator;
 import com.facebook.react.bridge.WritableMap;
 import com.facebook.react.common.MapBuilder;
+import com.facebook.react.common.ReactConstants;
 import com.facebook.react.common.build.ReactBuildConfig;
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.ContentSizeChangeEvent;
 import com.facebook.react.uimanager.events.Event;
@@ -61,9 +59,14 @@
 import com.facebook.react.views.webview.events.TopLoadingFinishEvent;
 import com.facebook.react.views.webview.events.TopLoadingStartEvent;
 import com.facebook.react.views.webview.events.TopMessageEvent;
-
-import org.json.JSONObject;
+import java.io.UnsupportedEncodingException;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Locale;
+import java.util.Map;
+import javax.annotation.Nullable;
 import org.json.JSONException;
+import org.json.JSONObject;
 
 /**
  * Manages instances of {@link WebView}
@@ -683,7 +686,7 @@ public void onNewPicture(WebView webView, Picture picture) {
   protected static void dispatchEvent(WebView webView, Event event) {
     ReactContext reactContext = (ReactContext) webView.getContext();
     EventDispatcher eventDispatcher =
-      reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
+      reactContext.<EventDispatcher>getEventDispatcher();
     eventDispatcher.dispatchEvent(event);
   }
 }

From 40c724834578d2a2db217039b01cb8f8e9849585 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 30 May 2018 21:49:10 -0700
Subject: [PATCH 0690/1109] store / retrieve instanceHandle from View

Reviewed By: shergin, achen1

Differential Revision: D8074014

fbshipit-source-id: aee0d41e0e9da44e8748f47da04dcd76dbe96d8d
---
 .../react/fabric/FabricReconciler.java        | 14 +++----
 .../react/fabric/FabricUIManager.java         | 20 +++++++++-
 .../uimanager/NativeViewHierarchyManager.java | 40 ++++++++++++++++++-
 .../react/uimanager/UIViewOperationQueue.java | 20 ++++++++++
 .../main/res/views/uimanager/values/ids.xml   |  3 ++
 .../react/fabric/FabricReconcilerTest.java    |  1 +
 6 files changed, 88 insertions(+), 10 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index ddd3a386fc38..5f61d943fe4c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -8,7 +8,6 @@
 package com.facebook.react.fabric;
 
 import android.util.Log;
-import android.util.SparseArray;
 import com.facebook.react.common.ArrayUtils;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.UIViewOperationQueue;
@@ -118,19 +117,20 @@ private void manageChildren(
   }
 
   private void enqueueUpdateProperties(ReactShadowNode node) {
-    if (node.getNewProps() == null) {
-      return;
-    }
+    int reactTag = node.getReactTag();
     if (DEBUG) {
       Log.d(
           TAG,
           "manageChildren.enqueueUpdateProperties " +
-              "\n\ttag: " + node.getReactTag() +
+              "\n\ttag: " + reactTag +
               "\n\tviewClass: " + node.getViewClass() +
               "\n\tnewProps: " + node.getNewProps());
     }
-    uiViewOperationQueue.enqueueUpdateProperties(
-        node.getReactTag(), node.getViewClass(), node.getNewProps());
+
+    if (node.getNewProps() != null) {
+      uiViewOperationQueue.enqueueUpdateProperties(
+        reactTag, node.getViewClass(), node.getNewProps());
+    }
   }
 
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index a565012e52aa..7021c78310ed 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -15,6 +15,7 @@
 import android.view.View;
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.bridge.GuardedRunnable;
+import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
@@ -58,17 +59,22 @@ public class FabricUIManager implements UIManager, JSHandler {
   private final ReactApplicationContext mReactApplicationContext;
   private final ViewManagerRegistry mViewManagerRegistry;
   private final UIViewOperationQueue mUIViewOperationQueue;
+  private final NativeViewHierarchyManager mNativeViewHierarchyManager;
   private volatile int mCurrentBatch = 0;
-  private FabricReconciler mFabricReconciler;
+  private final FabricReconciler mFabricReconciler;
+  // TODO: Initialize new Binding (waiting for C++ implemenation to be landed)
+  private FabricBinding mBinding;
+  private JavaScriptContextHolder mContext;
 
   public FabricUIManager(
       ReactApplicationContext reactContext, ViewManagerRegistry viewManagerRegistry) {
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
     mReactApplicationContext = reactContext;
     mViewManagerRegistry = viewManagerRegistry;
+    mNativeViewHierarchyManager = new NativeViewHierarchyManager(viewManagerRegistry);
     mUIViewOperationQueue =
         new UIViewOperationQueue(
-            reactContext, new NativeViewHierarchyManager(viewManagerRegistry), 0);
+            reactContext, mNativeViewHierarchyManager, 0);
     mFabricReconciler = new FabricReconciler(mUIViewOperationQueue);
   }
 
@@ -483,4 +489,14 @@ public void invoke(int instanceHandle, String name, WritableMap params) {
     // -> call to C++
   }
 
+  public long createEventTarget(int targetTag) throws IllegalStateException {
+    long instanceHandle = mNativeViewHierarchyManager.getInstanceHandle(targetTag);
+    if (instanceHandle == 0) {
+      throw new IllegalStateException("View with targetTag " + targetTag + " does not exist.");
+    }
+
+    // TODO: uncomment after diff including Binding is landed
+    // return mBinding.createEventTarget(mContext.get(), instanceHandle);
+    return 0;
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
index a57205b861eb..7a59df26f600 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
@@ -7,7 +7,9 @@
 
 package com.facebook.react.uimanager;
 
+import android.annotation.TargetApi;
 import android.content.res.Resources;
+import android.os.Build;
 import android.util.Log;
 import android.util.SparseArray;
 import android.util.SparseBooleanArray;
@@ -17,6 +19,7 @@
 import android.view.ViewGroup;
 import android.view.ViewParent;
 import android.widget.PopupMenu;
+import com.facebook.react.R;
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.animation.Animation;
 import com.facebook.react.animation.AnimationListener;
@@ -114,13 +117,26 @@ public void setLayoutAnimationEnabled(boolean enabled) {
     mLayoutAnimationEnabled = enabled;
   }
 
+  public synchronized void updateInstanceHandle(int tag, long instanceHandle) {
+    UiThreadUtil.assertOnUiThread();
+
+    try {
+      updateInstanceHandle(resolveView(tag), instanceHandle);
+    } catch (IllegalViewOperationException e) {
+      Log.e(TAG, "Unable to update properties for view tag " + tag, e);
+    }
+  }
+
   public synchronized void updateProperties(int tag, ReactStylesDiffMap props) {
     UiThreadUtil.assertOnUiThread();
 
     try {
       ViewManager viewManager = resolveViewManager(tag);
       View viewToUpdate = resolveView(tag);
-      viewManager.updateProperties(viewToUpdate, props);
+
+      if (props != null) {
+        viewManager.updateProperties(viewToUpdate, props);
+      }
     } catch (IllegalViewOperationException e) {
       Log.e(TAG, "Unable to update properties for view tag " + tag, e);
     }
@@ -197,6 +213,28 @@ public synchronized void updateLayout(
     }
   }
 
+  @TargetApi(Build.VERSION_CODES.DONUT)
+  private void updateInstanceHandle(View viewToUpdate, long instanceHandle) {
+    UiThreadUtil.assertOnUiThread();
+    viewToUpdate.setTag(R.id.view_tag_instance_handle, instanceHandle);
+  }
+
+  @Nullable
+  @TargetApi(Build.VERSION_CODES.DONUT)
+  public long getInstanceHandle(int targetTag) {
+    UiThreadUtil.assertOnUiThread();
+
+    View view = mTagsToViews.get(targetTag);
+    if (view == null) {
+      throw new IllegalArgumentException("Unable to find view for tag: " + targetTag);
+    }
+    Long tag = (Long) view.getTag(R.id.view_tag_instance_handle);
+    if (tag == null) {
+      throw new IllegalArgumentException("Unable to find instanceHandle for tag: " + targetTag);
+    }
+    return tag;
+  }
+
   private void updateLayout(View viewToUpdate, int x, int y, int width, int height) {
     if (mLayoutAnimationEnabled &&
         mLayoutAnimator.shouldAnimateLayout(viewToUpdate)) {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
index 183fcf436a88..90e4d82bb9bc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
@@ -96,6 +96,22 @@ public void execute() {
     }
   }
 
+
+  private final class UpdateInstanceHandleOperation extends ViewOperation {
+
+    private final long mInstanceHandle;
+
+    private UpdateInstanceHandleOperation(int tag, long instanceHandle) {
+      super(tag);
+      mInstanceHandle = instanceHandle;
+    }
+
+    @Override
+    public void execute() {
+      mNativeViewHierarchyManager.updateInstanceHandle(mTag, mInstanceHandle);
+    }
+  }
+
   /**
    * Operation for updating native view's position and size. The operation is not created directly
    * by a {@link UIManagerModule} call from JS. Instead it gets inflated using computed position
@@ -682,6 +698,10 @@ public void enqueueCreateView(
     }
   }
 
+  public void enqueueUpdateInstanceHandle(int reactTag, long instanceHandle) {
+    mOperations.add(new UpdateInstanceHandleOperation(reactTag, instanceHandle));
+  }
+
   public void enqueueUpdateProperties(int reactTag, String className, ReactStylesDiffMap props) {
     mOperations.add(new UpdatePropertiesOperation(reactTag, props));
   }
diff --git a/ReactAndroid/src/main/res/views/uimanager/values/ids.xml b/ReactAndroid/src/main/res/views/uimanager/values/ids.xml
index 75ac81d17106..8ccd44d4b613 100644
--- a/ReactAndroid/src/main/res/views/uimanager/values/ids.xml
+++ b/ReactAndroid/src/main/res/views/uimanager/values/ids.xml
@@ -5,4 +5,7 @@
 
   <!-- tag is used to store the nativeID tag -->
   <item type="id" name="view_tag_native_id"/>
+
+  <!-- tag is used to store the nativeID tag -->
+  <item type="id" name="view_tag_instance_handle"/>
 </resources>
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
index 2cb680067c55..bf4d69dffa24 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
@@ -109,6 +109,7 @@ private static ReactShadowNode createNode(int tag, boolean virtual) {
       node = new ReactShadowNodeImpl();
     }
     node.setReactTag(tag);
+    node.setViewClassName("View");
     node.setThemedContext(mock(ThemedReactContext.class));
     return node;
   }

From 23fbd312aa80233d4062de28cb950c91786fb3f1 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 30 May 2018 21:49:15 -0700
Subject: [PATCH 0691/1109] Include instanceHandle in cloning mechanism

Reviewed By: shergin, achen1

Differential Revision: D8072075

fbshipit-source-id: 2fcfdfa5116850ce0bac6c2c86d87e5bf00fd7f0
---
 .../react/fabric/FabricReconciler.java        | 15 +++---
 .../react/fabric/FabricUIManager.java         | 25 +++++-----
 .../uimanager/NativeViewHierarchyManager.java |  8 ++--
 .../react/uimanager/ReactShadowNode.java      | 12 +++--
 .../react/uimanager/ReactShadowNodeImpl.java  | 29 ++++++++---
 .../progressbar/ProgressBarShadowNode.java    |  8 ++--
 .../views/slider/ReactSliderManager.java      |  8 ++--
 .../views/switchview/ReactSwitchManager.java  |  8 ++--
 .../react/views/text/ReactTextShadowNode.java |  8 ++--
 .../textinput/ReactTextInputShadowNode.java   |  8 ++--
 .../react/bridge/InstanceHandleHelper.java    | 20 ++++++++
 .../react/fabric/FabricUIManagerTest.java     | 48 ++++++++++++-------
 .../react/fabric/ReactShadowNodeTest.java     |  2 +-
 13 files changed, 126 insertions(+), 73 deletions(-)
 create mode 100644 ReactAndroid/src/test/java/com/facebook/react/bridge/InstanceHandleHelper.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index 5f61d943fe4c..c42de9efec38 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -120,17 +120,20 @@ private void enqueueUpdateProperties(ReactShadowNode node) {
     int reactTag = node.getReactTag();
     if (DEBUG) {
       Log.d(
-          TAG,
-          "manageChildren.enqueueUpdateProperties " +
-              "\n\ttag: " + reactTag +
-              "\n\tviewClass: " + node.getViewClass() +
-              "\n\tnewProps: " + node.getNewProps());
+        TAG,
+        "manageChildren.enqueueUpdateProperties " +
+          "\n\ttag: " + reactTag +
+          "\n\tviewClass: " + node.getViewClass() +
+          "\n\tinstanceHandle: " + node.getInstanceHandle() +
+          "\n\tnewProps: " + node.getNewProps());
     }
 
     if (node.getNewProps() != null) {
       uiViewOperationQueue.enqueueUpdateProperties(
         reactTag, node.getViewClass(), node.getNewProps());
     }
-  }
 
+    uiViewOperationQueue.enqueueUpdateInstanceHandle(
+      reactTag, node.getInstanceHandle());
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 7021c78310ed..6b7bfff47de0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -98,6 +98,7 @@ public ReactShadowNode createNode(
       ReactShadowNode rootNode = getRootNode(rootTag);
       node.setRootTag(rootNode.getReactTag());
       node.setViewClassName(viewName);
+      node.setInstanceHandle(instanceHandle);
       node.setReactTag(reactTag);
       node.setThemedContext(rootNode.getThemedContext());
 
@@ -139,8 +140,7 @@ public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
       Log.d(TAG, "cloneNode \n\tnode: " + node);
     }
     try {
-      // TODO: Pass new instanceHandle
-      ReactShadowNode clone = node.mutableCopy();
+      ReactShadowNode clone = node.mutableCopy(instanceHandle);
       assertReactShadowNodeCopy(node, clone);
       return clone;
     } catch (Throwable t) {
@@ -160,8 +160,7 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long insta
       Log.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
     }
     try {
-      // TODO: Pass new instanceHandle
-      ReactShadowNode clone = node.mutableCopyWithNewChildren();
+      ReactShadowNode clone = node.mutableCopyWithNewChildren(instanceHandle);
       assertReactShadowNodeCopy(node, clone);
       return clone;
     } catch (Throwable t) {
@@ -182,9 +181,8 @@ public ReactShadowNode cloneNodeWithNewProps(
       Log.d(TAG, "cloneNodeWithNewProps \n\tnode: " + node + "\n\tprops: " + newProps);
     }
     try {
-      // TODO: Pass new instanceHandle
-      ReactShadowNode clone =
-          node.mutableCopyWithNewProps(newProps == null ? null : new ReactStylesDiffMap(newProps));
+      ReactShadowNode clone = node.mutableCopyWithNewProps(instanceHandle,
+            newProps == null ? null : new ReactStylesDiffMap(newProps));
       assertReactShadowNodeCopy(node, clone);
       return clone;
     } catch (Throwable t) {
@@ -206,9 +204,8 @@ public ReactShadowNode cloneNodeWithNewChildrenAndProps(
       Log.d(TAG, "cloneNodeWithNewChildrenAndProps \n\tnode: " + node + "\n\tnewProps: " + newProps);
     }
     try {
-      // TODO: Pass new instanceHandle
       ReactShadowNode clone =
-          node.mutableCopyWithNewChildrenAndProps(
+          node.mutableCopyWithNewChildrenAndProps(instanceHandle,
               newProps == null ? null : new ReactStylesDiffMap(newProps));
       assertReactShadowNodeCopy(node, clone);
       return clone;
@@ -244,7 +241,7 @@ public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
       // then we add a mutation of it. In the future this will be performed by FabricJS / Fiber.
       //TODO: T27926878 avoid cloning shared child
       if (child.getParent() != null) {
-        child = child.mutableCopy();
+        child = child.mutableCopy(child.getInstanceHandle());
       }
       parent.addChildAt(child, parent.getChildCount());
     } catch (Throwable t) {
@@ -315,7 +312,7 @@ private void notifyOnBeforeLayoutRecursive(ReactShadowNode node) {
 
   private ReactShadowNode calculateDiffingAndCreateNewRootNode(
     ReactShadowNode currentRootShadowNode, List<ReactShadowNode> newChildList) {
-    ReactShadowNode newRootShadowNode = currentRootShadowNode.mutableCopyWithNewChildren();
+    ReactShadowNode newRootShadowNode = currentRootShadowNode.mutableCopyWithNewChildren(currentRootShadowNode.getInstanceHandle());
     for (ReactShadowNode child : newChildList) {
       appendChild(newRootShadowNode, child);
     }
@@ -489,10 +486,10 @@ public void invoke(int instanceHandle, String name, WritableMap params) {
     // -> call to C++
   }
 
-  public long createEventTarget(int targetTag) throws IllegalStateException {
-    long instanceHandle = mNativeViewHierarchyManager.getInstanceHandle(targetTag);
+  public long createEventTarget(int reactTag) throws IllegalStateException {
+    long instanceHandle = mNativeViewHierarchyManager.getInstanceHandle(reactTag);
     if (instanceHandle == 0) {
-      throw new IllegalStateException("View with targetTag " + targetTag + " does not exist.");
+      throw new IllegalStateException("View with reactTag " + reactTag + " does not exist.");
     }
 
     // TODO: uncomment after diff including Binding is landed
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
index 7a59df26f600..d5a20471943a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
@@ -221,16 +221,16 @@ private void updateInstanceHandle(View viewToUpdate, long instanceHandle) {
 
   @Nullable
   @TargetApi(Build.VERSION_CODES.DONUT)
-  public long getInstanceHandle(int targetTag) {
+  public long getInstanceHandle(int reactTag) {
     UiThreadUtil.assertOnUiThread();
 
-    View view = mTagsToViews.get(targetTag);
+    View view = mTagsToViews.get(reactTag);
     if (view == null) {
-      throw new IllegalArgumentException("Unable to find view for tag: " + targetTag);
+      throw new IllegalArgumentException("Unable to find view for tag: " + reactTag);
     }
     Long tag = (Long) view.getTag(R.id.view_tag_instance_handle);
     if (tag == null) {
-      throw new IllegalArgumentException("Unable to find instanceHandle for tag: " + targetTag);
+      throw new IllegalArgumentException("Unable to find instanceHandle for tag: " + reactTag);
     }
     return tag;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
index 7790a49ddf61..ed134e2160b7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
@@ -71,13 +71,13 @@ public interface ReactShadowNode<T extends ReactShadowNode> {
   /**
    * @return a mutable copy of the {@link ReactShadowNode}
    */
-  T mutableCopy();
+  T mutableCopy(long instanceHandle);
 
-  T mutableCopyWithNewProps(@Nullable ReactStylesDiffMap newProps);
+  T mutableCopyWithNewProps(long instanceHandle, @Nullable ReactStylesDiffMap newProps);
 
-  T mutableCopyWithNewChildren();
+  T mutableCopyWithNewChildren(long instanceHandle);
 
-  T mutableCopyWithNewChildrenAndProps(@Nullable ReactStylesDiffMap newProps);
+  T mutableCopyWithNewChildrenAndProps(long instanceHandle, @Nullable ReactStylesDiffMap newProps);
 
   String getViewClass();
 
@@ -373,4 +373,8 @@ public interface ReactShadowNode<T extends ReactShadowNode> {
   @Nullable ReactShadowNode getOriginalReactShadowNode();
 
   void setOriginalReactShadowNode(@Nullable ReactShadowNode node);
+
+  long getInstanceHandle();
+
+  void setInstanceHandle(long instanceHandle);
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 27a70d16780c..3b3929646810 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -81,7 +81,7 @@ public YogaNode cloneNode(YogaNode oldYogaNode,
               + parentReactShadowNode + " index: " + childIndex);
         }
 
-        ReactShadowNodeImpl newNode = oldReactShadowNode.mutableCopy();
+        ReactShadowNodeImpl newNode = oldReactShadowNode.mutableCopy(oldReactShadowNode.getInstanceHandle());
         parentReactShadowNode.replaceChild(newNode, childIndex);
         return newNode.mYogaNode;
       }
@@ -114,6 +114,7 @@ public YogaNode cloneNode(YogaNode oldYogaNode,
   private ReactShadowNode mOriginalReactShadowNode = null;
 
   private @Nullable ReactStylesDiffMap mNewProps;
+  private long mInstanceHandle;
 
   public ReactShadowNodeImpl() {
     mDefaultPadding = new Spacing(0);
@@ -166,11 +167,12 @@ protected ReactShadowNodeImpl copy() {
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopy() {
+  public ReactShadowNodeImpl mutableCopy(long instanceHandle) {
     ReactShadowNodeImpl copy = copy();
     Assertions.assertCondition(
         getClass() == copy.getClass(),
         "Copied shadow node must use the same class");
+    copy.mInstanceHandle = instanceHandle;
     if (mYogaNode != null) {
       copy.mYogaNode = mYogaNode.clone();
       copy.mYogaNode.setData(copy);
@@ -185,8 +187,9 @@ public ReactShadowNodeImpl mutableCopy() {
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopyWithNewChildren() {
+  public ReactShadowNodeImpl mutableCopyWithNewChildren(long instanceHandle) {
     ReactShadowNodeImpl copy = copy();
+    copy.mInstanceHandle = instanceHandle;
     Assertions.assertCondition(
         getClass() == copy.getClass(),
         "Copied shadow node must use the same class");
@@ -204,8 +207,9 @@ public ReactShadowNodeImpl mutableCopyWithNewChildren() {
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopyWithNewProps(@Nullable ReactStylesDiffMap newProps) {
-    ReactShadowNodeImpl copy = mutableCopy();
+  public ReactShadowNodeImpl mutableCopyWithNewProps(long instanceHandle,
+      @Nullable ReactStylesDiffMap newProps) {
+    ReactShadowNodeImpl copy = mutableCopy(instanceHandle);
     if (newProps != null) {
       copy.updateProperties(newProps);
       copy.mNewProps = newProps;
@@ -214,8 +218,9 @@ public ReactShadowNodeImpl mutableCopyWithNewProps(@Nullable ReactStylesDiffMap
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopyWithNewChildrenAndProps(@Nullable ReactStylesDiffMap newProps) {
-    ReactShadowNodeImpl copy = mutableCopyWithNewChildren();
+  public ReactShadowNodeImpl mutableCopyWithNewChildrenAndProps(long instanceHandle,
+      @Nullable ReactStylesDiffMap newProps) {
+    ReactShadowNodeImpl copy = mutableCopyWithNewChildren(instanceHandle);
     if (newProps != null) {
       copy.updateProperties(newProps);
       copy.mNewProps = newProps;
@@ -1107,4 +1112,14 @@ public ReactShadowNode getOriginalReactShadowNode() {
   public void setOriginalReactShadowNode(ReactShadowNode node) {
     mOriginalReactShadowNode = node;
   }
+
+  @Override
+  public long getInstanceHandle() {
+    return mInstanceHandle;
+  }
+
+  @Override
+  public void setInstanceHandle(long instanceHandle) {
+    mInstanceHandle = instanceHandle;
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
index 779d647f658b..d18466e58af9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarShadowNode.java
@@ -53,8 +53,8 @@ public ProgressBarShadowNode(ProgressBarShadowNode node) {
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopyWithNewChildren() {
-    ProgressBarShadowNode node = (ProgressBarShadowNode) super.mutableCopyWithNewChildren();
+  public ReactShadowNodeImpl mutableCopyWithNewChildren(long instanceHandle) {
+    ProgressBarShadowNode node = (ProgressBarShadowNode) super.mutableCopyWithNewChildren(instanceHandle);
     node.initMeasureFunction();
     return node;
   }
@@ -64,8 +64,8 @@ private void initMeasureFunction() {
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopy() {
-    ProgressBarShadowNode node = (ProgressBarShadowNode) super.mutableCopy();
+  public ReactShadowNodeImpl mutableCopy(long instanceHandle) {
+    ProgressBarShadowNode node = (ProgressBarShadowNode) super.mutableCopy(instanceHandle);
     node.initMeasureFunction();
     return node;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
index dd8008d5b130..43aca591b2f2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
@@ -62,15 +62,15 @@ private void initMeasureFunction() {
     }
 
     @Override
-    public ReactShadowNodeImpl mutableCopy() {
-      ReactSliderShadowNode reactShadowNode = (ReactSliderShadowNode) super.mutableCopy();
+    public ReactShadowNodeImpl mutableCopy(long instanceHandle) {
+      ReactSliderShadowNode reactShadowNode = (ReactSliderShadowNode) super.mutableCopy(instanceHandle);
       reactShadowNode.initMeasureFunction();
       return reactShadowNode;
     }
 
     @Override
-    public ReactShadowNodeImpl mutableCopyWithNewChildren() {
-      ReactSliderShadowNode reactShadowNode = (ReactSliderShadowNode) super.mutableCopyWithNewChildren();
+    public ReactShadowNodeImpl mutableCopyWithNewChildren(long instanceHandle) {
+      ReactSliderShadowNode reactShadowNode = (ReactSliderShadowNode) super.mutableCopyWithNewChildren(instanceHandle);
       reactShadowNode.initMeasureFunction();
       return reactShadowNode;
     }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
index a1a576b37667..f6a7f2d8eb5d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
@@ -55,15 +55,15 @@ private void initMeasureFunction() {
     }
 
     @Override
-    public ReactShadowNodeImpl mutableCopy() {
-      ReactSwitchShadowNode reactShadowNode = (ReactSwitchShadowNode) super.mutableCopy();
+    public ReactShadowNodeImpl mutableCopy(long instanceHandle) {
+      ReactSwitchShadowNode reactShadowNode = (ReactSwitchShadowNode) super.mutableCopy(instanceHandle);
       reactShadowNode.initMeasureFunction();
       return reactShadowNode;
     }
 
     @Override
-    public ReactShadowNodeImpl mutableCopyWithNewChildren() {
-      ReactSwitchShadowNode reactShadowNode = (ReactSwitchShadowNode) super.mutableCopyWithNewChildren();
+    public ReactShadowNodeImpl mutableCopyWithNewChildren(long instanceHandle) {
+      ReactSwitchShadowNode reactShadowNode = (ReactSwitchShadowNode) super.mutableCopyWithNewChildren(instanceHandle);
       reactShadowNode.initMeasureFunction();
       return reactShadowNode;
     }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
index 1cec7c690bcb..1f4f52fd7bf8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextShadowNode.java
@@ -159,15 +159,15 @@ protected LayoutShadowNode copy() {
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopy() {
-    ReactTextShadowNode copy = (ReactTextShadowNode) super.mutableCopy();
+  public ReactShadowNodeImpl mutableCopy(long instanceHandle) {
+    ReactTextShadowNode copy = (ReactTextShadowNode) super.mutableCopy(instanceHandle);
     copy.initMeasureFunction();
     return copy;
   }
 
   @Override
-  public ReactShadowNodeImpl mutableCopyWithNewChildren() {
-    ReactTextShadowNode copy = (ReactTextShadowNode) super.mutableCopyWithNewChildren();
+  public ReactShadowNodeImpl mutableCopyWithNewChildren(long instanceHandle) {
+    ReactTextShadowNode copy = (ReactTextShadowNode) super.mutableCopyWithNewChildren(instanceHandle);
     copy.initMeasureFunction();
     return copy;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
index e121f2b5f22f..28c559afbc12 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
@@ -65,8 +65,8 @@ protected ReactTextInputShadowNode copy() {
   }
 
   @Override
-  public ReactTextInputShadowNode mutableCopy() {
-    ReactTextInputShadowNode node = (ReactTextInputShadowNode) super.mutableCopy();
+  public ReactTextInputShadowNode mutableCopy(long instanceHandle) {
+    ReactTextInputShadowNode node = (ReactTextInputShadowNode) super.mutableCopy(instanceHandle);
     node.initMeasureFunction();
     ThemedReactContext themedContext = getThemedContext();
     if (themedContext != null) {
@@ -80,8 +80,8 @@ private void initMeasureFunction() {
   }
 
   @Override
-  public ReactTextInputShadowNode mutableCopyWithNewChildren() {
-    ReactTextInputShadowNode node = (ReactTextInputShadowNode) super.mutableCopyWithNewChildren();
+  public ReactTextInputShadowNode mutableCopyWithNewChildren(long instanceHandle) {
+    ReactTextInputShadowNode node = (ReactTextInputShadowNode) super.mutableCopyWithNewChildren(instanceHandle);
     node.initMeasureFunction();
     ThemedReactContext themedContext = getThemedContext();
     if (themedContext != null) {
diff --git a/ReactAndroid/src/test/java/com/facebook/react/bridge/InstanceHandleHelper.java b/ReactAndroid/src/test/java/com/facebook/react/bridge/InstanceHandleHelper.java
new file mode 100644
index 000000000000..bb47fd0dac32
--- /dev/null
+++ b/ReactAndroid/src/test/java/com/facebook/react/bridge/InstanceHandleHelper.java
@@ -0,0 +1,20 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.bridge;
+
+
+import java.util.Random;
+
+public class InstanceHandleHelper {
+
+  private static final Random random = new Random();
+
+  public static long randomInstanceHandle() {
+    return random.nextLong();
+  }
+}
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 69f0293619af..1b651817e677 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -2,6 +2,7 @@
 package com.facebook.react.fabric;
 
 import static org.fest.assertions.api.Assertions.assertThat;
+import static com.facebook.react.bridge.InstanceHandleHelper.randomInstanceHandle;
 
 import com.facebook.react.ReactRootView;
 import com.facebook.react.bridge.ReactApplicationContext;
@@ -28,6 +29,7 @@
 import org.robolectric.RobolectricTestRunner;
 import org.robolectric.RuntimeEnvironment;
 
+
 /** Tests {@link FabricUIManager} */
 @RunWith(RobolectricTestRunner.class)
 public class FabricUIManagerTest {
@@ -35,7 +37,6 @@ public class FabricUIManagerTest {
   private FabricUIManager mFabricUIManager;
   private ThemedReactContext mThemedReactContext;
   private int mNextReactTag;
-  private int mNextInstanceHandle;
 
   @Before
   public void setUp() throws Exception {
@@ -58,10 +59,9 @@ public void testCreateNode() {
         new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
     int rootTag = mFabricUIManager.addRootView(rootView);
     int reactTag = mNextReactTag++;
-    int instanceHandle = mNextInstanceHandle++;
     String viewClass = ReactViewManager.REACT_CLASS;
     ReactShadowNode node =
-        mFabricUIManager.createNode(reactTag, viewClass, rootTag, null, instanceHandle);
+        mFabricUIManager.createNode(reactTag, viewClass, rootTag, null, randomInstanceHandle());
 
     assertThat(reactTag).isEqualTo(node.getReactTag());
     assertThat(viewClass).isEqualTo(node.getViewClass());
@@ -79,10 +79,9 @@ private int createAndRenderRootView() {
         new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
     int rootTag = mFabricUIManager.addRootView(rootView);
     int reactTag = mNextReactTag++;
-    int instanceHandle = mNextInstanceHandle++;
     String viewClass = ReactViewManager.REACT_CLASS;
     ReactShadowNode node =
-        mFabricUIManager.createNode(reactTag, viewClass, rootTag, null, instanceHandle);
+        mFabricUIManager.createNode(reactTag, viewClass, rootTag, null, randomInstanceHandle());
 
     List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(rootTag);
     mFabricUIManager.appendChildToSet(childSet, node);
@@ -106,6 +105,21 @@ public void testCloneNode() {
     assertThat(clonedNode.getChildAt(0)).isEqualTo(child);
   }
 
+
+  @Test
+  public void testCloneWithInstanceHandle() {
+    ReactShadowNode node = createViewNode();
+
+    long oldInstanceHandle = node.getInstanceHandle();
+    long newInstanceHandle = oldInstanceHandle + 1;
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, newInstanceHandle);
+
+    assertThat(clonedNode).isNotSameAs(node);
+    assertThat(clonedNode.getInstanceHandle()).isSameAs(newInstanceHandle);
+    assertThat(node.getInstanceHandle()).isSameAs(oldInstanceHandle);
+  }
+
+
   @Test
   public void testDefaultSpacingCloning() {
     ReactShadowNode node = createViewNode();
@@ -124,7 +138,7 @@ public void testCloneVirtualNode() {
     node.setText("test");
     assertThat(node.isVirtual()).isTrue();
 
-    ReactRawTextShadowNode clonedNode = (ReactRawTextShadowNode) node.mutableCopy();
+    ReactRawTextShadowNode clonedNode = (ReactRawTextShadowNode) node.mutableCopy(randomInstanceHandle());
 
     assertThat(clonedNode.getText()).isEqualTo("test");
     assertThat(clonedNode).isNotEqualTo(node);
@@ -134,7 +148,7 @@ public void testCloneVirtualNode() {
   public void testLayoutProgressBarAfterClonning() {
     ProgressBarShadowNode node = new ProgressBarShadowNode();
     node.setThemedContext(mThemedReactContext);
-    ProgressBarShadowNode clone = (ProgressBarShadowNode) node.mutableCopy();
+    ProgressBarShadowNode clone = (ProgressBarShadowNode) node.mutableCopy(randomInstanceHandle());
     clone.calculateLayout();
   }
 
@@ -144,7 +158,7 @@ public void testCloneNodeWithNewChildren() {
     ReactShadowNode child = createViewNode();
     node.addChildAt(child, 0);
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node, 0);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node, randomInstanceHandle());
 
     assertThat(clonedNode.getChildCount()).isZero();
     assertSameFields(clonedNode, node);
@@ -155,7 +169,7 @@ public void testCloneNodeWithNewProps() {
     ReactShadowNode node = createViewNode();
     ReadableNativeMap props = null; // TODO(ayc): Figure out how to create a Native map from tests.
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props, 0);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props, randomInstanceHandle());
   }
 
   @Test
@@ -163,7 +177,7 @@ public void testCloneNodeWithNewChildrenAndProps() {
     ReactShadowNode node = createViewNode();
     ReadableNativeMap props = null;
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props, 0);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props, randomInstanceHandle());
 
     assertThat(clonedNode.getChildCount()).isZero();
   }
@@ -221,10 +235,10 @@ public void testTextMutableClone() {
         new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
     int rootTag = mFabricUIManager.addRootView(rootView);
     ReactShadowNode text =
-        mFabricUIManager.createNode(0, ReactTextViewManager.REACT_CLASS, rootTag, null, mNextInstanceHandle++);
+        mFabricUIManager.createNode(0, ReactTextViewManager.REACT_CLASS, rootTag, null, randomInstanceHandle());
     assertThat(text.isMeasureDefined()).isTrue();
 
-    ReactShadowNode textCopy = text.mutableCopy();
+    ReactShadowNode textCopy = text.mutableCopy(randomInstanceHandle());
     assertThat(textCopy.isMeasureDefined()).isTrue();
 
     textCopy.setStyleWidth(200);
@@ -247,13 +261,13 @@ public void testRemoveOriginalNodeReferences() {
     int rootTag = mFabricUIManager.addRootView(rootView);
     String viewClass = ReactViewManager.REACT_CLASS;
 
-    ReactShadowNode aa = mFabricUIManager.createNode(2, viewClass, rootTag, null, mNextInstanceHandle++);
-    ReactShadowNode a = mFabricUIManager.createNode(3, viewClass, rootTag, null, mNextInstanceHandle++);
+    ReactShadowNode aa = mFabricUIManager.createNode(2, viewClass, rootTag, null, randomInstanceHandle());
+    ReactShadowNode a = mFabricUIManager.createNode(3, viewClass, rootTag, null, randomInstanceHandle());
     mFabricUIManager.appendChild(a, aa);
-    ReactShadowNode bb = mFabricUIManager.createNode(4, viewClass, rootTag, null, mNextInstanceHandle++);
-    ReactShadowNode b = mFabricUIManager.createNode(5, viewClass, rootTag, null, mNextInstanceHandle++);
+    ReactShadowNode bb = mFabricUIManager.createNode(4, viewClass, rootTag, null, randomInstanceHandle());
+    ReactShadowNode b = mFabricUIManager.createNode(5, viewClass, rootTag, null, randomInstanceHandle());
     mFabricUIManager.appendChild(b, bb);
-    ReactShadowNode container = mFabricUIManager.createNode(6, viewClass, rootTag, null, mNextInstanceHandle++);
+    ReactShadowNode container = mFabricUIManager.createNode(6, viewClass, rootTag, null, randomInstanceHandle());
     mFabricUIManager.appendChild(container, a);
     mFabricUIManager.appendChild(container, b);
     List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(rootTag);
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
index 12f4ddb58fcc..7148da735640 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
@@ -13,7 +13,7 @@ public class ReactShadowNodeTest {
   @Test(expected = AssertionError.class)
   public void testClonedInstance() {
     TestReactShadowNode node = new TestReactShadowNode();
-    node.mutableCopy();
+    node.mutableCopy(node.getInstanceHandle());
   }
 
   private static class TestReactShadowNode extends ReactShadowNodeImpl {}

From 0f10e03dd8abeed4e6965cb16fc9720a8190b7a8 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 30 May 2018 21:49:20 -0700
Subject: [PATCH 0692/1109] Binding for js events

Reviewed By: fkgozali

Differential Revision: D8181616

fbshipit-source-id: 5937c83f22ac09e3041fcb0f8d4e9e3026b2b397
---
 .../react/testing/ReactAppTestActivity.java   |  2 +-
 .../facebook/react/fabric/FabricBinding.java  | 15 +++++
 .../react/fabric/FabricUIManager.java         | 62 ++++++++++++-------
 .../com/facebook/react/fabric/JSHandler.java  |  2 +-
 .../fabric/events/FabricEventEmitter.java     | 20 +++---
 .../react/fabric/jsc/FabricJSCBinding.java    | 13 ++--
 .../uimanager/NativeViewHierarchyManager.java |  8 +--
 .../uimanager/events/EventDispatcher.java     |  2 +-
 .../react/fabric/FabricReconcilerTest.java    |  4 +-
 .../react/fabric/FabricUIManagerTest.java     |  6 +-
 10 files changed, 91 insertions(+), 43 deletions(-)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index e7e6d95e3603..ddaae9d17e50 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -261,7 +261,7 @@ public FabricUIManager getJSIModule() {
                   List<ViewManager> viewManagers =
                     mReactInstanceManager.getOrCreateViewManagers(reactApplicationContext);
                   FabricUIManager fabricUIManager =
-                    new FabricUIManager(reactApplicationContext, new ViewManagerRegistry(viewManagers));
+                    new FabricUIManager(reactApplicationContext, new ViewManagerRegistry(viewManagers), jsContext);
                   new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
                   return fabricUIManager;
                 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
index 97535f0a0d74..0636c17c24ef 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
@@ -8,9 +8,24 @@
 package com.facebook.react.fabric;
 
 import com.facebook.react.bridge.JavaScriptContextHolder;
+import com.facebook.react.bridge.NativeMap;
 
 public interface FabricBinding {
 
   void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule);
 
+  long createEventTarget(long jsContextNativePointer, long instanceHandlePointer);
+
+  void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
+
+  void releaseEventHandler(long jsContextNativePointer, long eventHandlerPointer);
+
+  void dispatchEventToTarget(
+    long jsContextNativePointer,
+    long eventHandlerPointer,
+    long eventTargetPointer,
+    String type,
+    NativeMap payload
+  );
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 6b7bfff47de0..10a187108ebd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -14,15 +14,15 @@
 import android.util.Log;
 import android.view.View;
 import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.GuardedRunnable;
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.ReadableNativeMap;
 import com.facebook.react.bridge.UIManager;
-import com.facebook.react.common.ReactConstants;
 import com.facebook.react.bridge.WritableMap;
+import com.facebook.react.bridge.WritableNativeMap;
+import com.facebook.react.common.ReactConstants;
 import com.facebook.react.common.annotations.VisibleForTesting;
 import com.facebook.react.modules.i18nmanager.I18nUtil;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
@@ -39,10 +39,8 @@
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 import com.facebook.yoga.YogaDirection;
 import java.util.ArrayList;
-import java.util.HashSet;
 import java.util.LinkedList;
 import java.util.List;
-import java.util.Set;
 import javax.annotation.Nullable;
 
 /**
@@ -60,14 +58,16 @@ public class FabricUIManager implements UIManager, JSHandler {
   private final ViewManagerRegistry mViewManagerRegistry;
   private final UIViewOperationQueue mUIViewOperationQueue;
   private final NativeViewHierarchyManager mNativeViewHierarchyManager;
+  private final JavaScriptContextHolder mJSContext;
   private volatile int mCurrentBatch = 0;
   private final FabricReconciler mFabricReconciler;
-  // TODO: Initialize new Binding (waiting for C++ implemenation to be landed)
   private FabricBinding mBinding;
-  private JavaScriptContextHolder mContext;
+  private long mEventHandlerPointer;
 
   public FabricUIManager(
-      ReactApplicationContext reactContext, ViewManagerRegistry viewManagerRegistry) {
+      ReactApplicationContext reactContext,
+      ViewManagerRegistry viewManagerRegistry,
+      JavaScriptContextHolder jsContext) {
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
     mReactApplicationContext = reactContext;
     mViewManagerRegistry = viewManagerRegistry;
@@ -76,10 +76,11 @@ public FabricUIManager(
         new UIViewOperationQueue(
             reactContext, mNativeViewHierarchyManager, 0);
     mFabricReconciler = new FabricReconciler(mUIViewOperationQueue);
+    mJSContext = jsContext;
   }
 
-  public void registerEventHandler(long eventHandlerPointer) {
-    // TODO: Release this event handler at some point.
+  public void setBinding(FabricBinding binding) {
+    mBinding = binding;
   }
 
   /** Creates a new {@link ReactShadowNode} */
@@ -480,20 +481,39 @@ private void handleException(ReactShadowNode node, Throwable t) {
     }
   }
 
-  @Override
-  public void invoke(int instanceHandle, String name, WritableMap params) {
-    Log.e(TAG, "Invoking '" + name + "' on instanceHandle: '" + instanceHandle  + "' from FabricUIManager.");
-    // -> call to C++
-  }
-
-  public long createEventTarget(int reactTag) throws IllegalStateException {
+  @Nullable
+  public long createEventTarget(int reactTag) {
     long instanceHandle = mNativeViewHierarchyManager.getInstanceHandle(reactTag);
-    if (instanceHandle == 0) {
-      throw new IllegalStateException("View with reactTag " + reactTag + " does not exist.");
+    long context = mJSContext.get();
+    long eventTarget = mBinding.createEventTarget(context, instanceHandle);
+    if (DEBUG) {
+      Log.e(
+        TAG,
+        "Created EventTarget: " + eventTarget + " for tag: " + reactTag + " with instanceHandle: " + instanceHandle);
     }
+    return eventTarget;
+  }
+
+  public void registerEventHandler(long eventHandlerPointer) {
+    mEventHandlerPointer = eventHandlerPointer;
+  }
+
+  public void releaseEventTarget(long eventTargetPointer) {
+    mBinding.releaseEventTarget(mJSContext.get(), eventTargetPointer);
+  }
 
-    // TODO: uncomment after diff including Binding is landed
-    // return mBinding.createEventTarget(mContext.get(), instanceHandle);
-    return 0;
+  public void releaseEventHandler(long eventHandlerPointer) {
+    mBinding.releaseEventHandler(mJSContext.get(), eventHandlerPointer);
   }
+
+  @Override
+  public void invoke(long eventTarget, String name, WritableMap params) {
+    if (DEBUG) {
+      Log.e(
+        TAG,
+        "Dispatching event for target: " + eventTarget);
+    }
+    mBinding.dispatchEventToTarget(mJSContext.get(), mEventHandlerPointer, eventTarget, name, (WritableNativeMap) params);
+  }
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/JSHandler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/JSHandler.java
index 42b11c46d212..471c016a6888 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/JSHandler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/JSHandler.java
@@ -10,6 +10,6 @@
 
 public interface JSHandler {
 
-  void invoke(int instanceHandle, String name, WritableMap params);
+  void invoke(long instanceHandle, String name, WritableMap params);
 
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
index 59c701e67e21..6ec640bf3cdb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
@@ -49,9 +49,8 @@ public FabricEventEmitter(ReactApplicationContext context, FabricUIManager fabri
 
   @Override
   public void receiveEvent(int targetTag, String eventName, @Nullable WritableMap params) {
-    //TODO get instanceHandle associated with targetTag.
-    int instanceHandle = targetTag;
-    mScheduler.scheduleWork(new FabricUIManagerWork(instanceHandle, eventName, params) );
+    long eventTarget = mFabricUIManager.createEventTarget(targetTag);
+    mScheduler.scheduleWork(new FabricUIManagerWork(eventTarget, eventName, params));
   }
 
   @Override
@@ -60,19 +59,26 @@ public void close() {
   }
 
   private class FabricUIManagerWork implements Work {
-    private final int mInstanceHandle;
+    private final long mEventTarget;
     private final String mEventName;
     private final WritableMap mParams;
 
-    public FabricUIManagerWork(int instanceHandle, String eventName, @Nullable WritableMap params) {
-      mInstanceHandle = instanceHandle;
+    public FabricUIManagerWork(long eventTarget, String eventName, @Nullable WritableMap params) {
+      mEventTarget = eventTarget;
       mEventName = eventName;
       mParams = params;
     }
 
     @Override
     public void run() {
-      mFabricUIManager.invoke(mInstanceHandle, mEventName, mParams);
+      try {
+        mFabricUIManager.invoke(mEventTarget, mEventName, mParams);
+      } catch (Throwable t) {
+        Log.e(TAG, "Error sending event " + mEventName, t);
+        //TODO: manage exception properly
+      } finally{
+        mFabricUIManager.releaseEventTarget(mEventTarget);
+      }
     }
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
index 190a1aefcbbd..38bbbfe636fa 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
@@ -28,13 +28,17 @@ public class FabricJSCBinding implements FabricBinding {
 
   private static native HybridData initHybrid();
 
-  private native long createEventTarget(long jsContextNativePointer, long instanceHandlePointer);
+  @Override
+  public native long createEventTarget(long jsContextNativePointer, long instanceHandlePointer);
 
-  private native void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
+  @Override
+  public native void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
 
-  private native void releaseEventHandler(long jsContextNativePointer, long eventHandlerPointer);
+  @Override
+  public native void releaseEventHandler(long jsContextNativePointer, long eventHandlerPointer);
 
-  private native void dispatchEventToTarget(
+  @Override
+  public native void dispatchEventToTarget(
     long jsContextNativePointer,
     long eventHandlerPointer,
     long eventTargetPointer,
@@ -50,6 +54,7 @@ public FabricJSCBinding() {
 
   @Override
   public void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule) {
+    fabricModule.setBinding(this);
     installFabric(jsContext.get(), fabricModule);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
index d5a20471943a..4cb9a92dc50d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
@@ -222,17 +222,15 @@ private void updateInstanceHandle(View viewToUpdate, long instanceHandle) {
   @Nullable
   @TargetApi(Build.VERSION_CODES.DONUT)
   public long getInstanceHandle(int reactTag) {
-    UiThreadUtil.assertOnUiThread();
-
     View view = mTagsToViews.get(reactTag);
     if (view == null) {
       throw new IllegalArgumentException("Unable to find view for tag: " + reactTag);
     }
-    Long tag = (Long) view.getTag(R.id.view_tag_instance_handle);
-    if (tag == null) {
+    Long instanceHandle = (Long) view.getTag(R.id.view_tag_instance_handle);
+    if (instanceHandle == null) {
       throw new IllegalArgumentException("Unable to find instanceHandle for tag: " + reactTag);
     }
-    return tag;
+    return instanceHandle;
   }
 
   private void updateLayout(View viewToUpdate, int x, int y, int width, int height) {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
index ad15ce0a8cf4..c9bc7af5d9b1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
@@ -115,7 +115,7 @@ public void dispatchEvent(Event event) {
     for (EventDispatcherListener listener : mListeners) {
       listener.onEventDispatch(event);
     }
-
+    
     synchronized (mEventsStagingLock) {
       mEventStaging.add(event);
       Systrace.startAsyncFlow(
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
index bf4d69dffa24..d5f2104087f8 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
@@ -5,6 +5,7 @@
 import static org.mockito.Mockito.mock;
 
 import com.facebook.react.bridge.CatalystInstance;
+import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReactTestHelper;
 import com.facebook.react.uimanager.NativeViewHierarchyManager;
@@ -41,7 +42,8 @@ public void setUp() {
     reactContext.initializeWithInstance(catalystInstance);
     List<ViewManager> viewManagers = new ArrayList<>();
     ViewManagerRegistry viewManagerRegistry = new ViewManagerRegistry(viewManagers);
-    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry);
+    JavaScriptContextHolder jsContext = mock(JavaScriptContextHolder.class);
+    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry, jsContext);
     mMockUIViewOperationQueue = new MockUIViewOperationQueue(reactContext);
     mFabricReconciler = new FabricReconciler(mMockUIViewOperationQueue);
   }
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 1b651817e677..8d70d85f6470 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -3,8 +3,10 @@
 
 import static org.fest.assertions.api.Assertions.assertThat;
 import static com.facebook.react.bridge.InstanceHandleHelper.randomInstanceHandle;
+import static org.mockito.Mockito.mock;
 
 import com.facebook.react.ReactRootView;
+import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReactTestHelper;
 import com.facebook.react.bridge.ReadableNativeMap;
@@ -49,8 +51,8 @@ public void setUp() throws Exception {
         Arrays.<ViewManager>asList(
             new ReactViewManager(), new ReactTextViewManager(), new ReactRawTextManager());
     ViewManagerRegistry viewManagerRegistry = new ViewManagerRegistry(viewManagers);
-
-    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry);
+    JavaScriptContextHolder jsContext = mock(JavaScriptContextHolder.class);
+    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry, jsContext);
   }
 
   @Test

From 6e359c4589b0627de59332ce56fe28804425a609 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Wed, 30 May 2018 21:49:26 -0700
Subject: [PATCH 0693/1109] Initialize Event Emitter as part of UIManagerModule

Reviewed By: achen1

Differential Revision: D8216184

fbshipit-source-id: 3b188804e2dad2b112f566da49a939eb4338713d
---
 .../com/facebook/react/ReactInstanceManager.java   |  2 --
 .../java/com/facebook/react/ReactRootView.java     |  4 ++--
 .../com/facebook/react/bridge/ReactContext.java    |  8 --------
 .../com/facebook/react/flat/FlatViewGroup.java     |  3 ++-
 .../react/uimanager/ThemedReactContext.java        |  8 --------
 .../facebook/react/uimanager/UIManagerModule.java  |  8 ++------
 .../react/uimanager/events/EventDispatcher.java    |  3 +--
 .../react/views/checkbox/ReactCheckBoxManager.java |  3 ++-
 .../views/drawer/ReactDrawerLayoutManager.java     |  3 ++-
 .../facebook/react/views/image/ReactImageView.java |  3 ++-
 .../react/views/modal/ReactModalHostManager.java   |  3 ++-
 .../react/views/modal/ReactModalHostView.java      |  2 +-
 .../react/views/picker/ReactPickerManager.java     |  3 ++-
 .../react/views/scroll/ReactScrollViewHelper.java  |  3 ++-
 .../react/views/slider/ReactSliderManager.java     |  5 +++--
 .../swiperefresh/SwipeRefreshLayoutManager.java    |  3 ++-
 .../react/views/switchview/ReactSwitchManager.java |  3 ++-
 .../ReactEditTextInputConnectionWrapper.java       |  3 ++-
 .../views/textinput/ReactTextInputManager.java     | 14 ++++++++------
 .../react/views/toolbar/ReactToolbarManager.java   |  3 ++-
 .../react/views/viewpager/ReactViewPager.java      |  3 ++-
 .../react/views/webview/ReactWebViewManager.java   |  3 ++-
 22 files changed, 43 insertions(+), 50 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 7363d1dda2d2..661f0d6914d7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -1078,8 +1078,6 @@ private ReactApplicationContext createReactContext(
     ReactMarker.logMarker(CREATE_REACT_CONTEXT_START, jsExecutor.getName());
     final ReactApplicationContext reactContext = new ReactApplicationContext(mApplicationContext);
 
-    reactContext.setEventDispatcher(new EventDispatcher(reactContext));
-
     NativeModuleCallExceptionHandler exceptionHandler = mNativeModuleCallExceptionHandler != null
         ? mNativeModuleCallExceptionHandler
         : mDevSupportManager;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 66d9db35375c..5f8ff1699f14 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -194,7 +194,7 @@ public void onChildStartedNativeGesture(MotionEvent androidEvent) {
       return;
     }
     ReactContext reactContext = mReactInstanceManager.getCurrentReactContext();
-    EventDispatcher eventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+    EventDispatcher eventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     mJSTouchDispatcher.onChildStartedNativeGesture(androidEvent, eventDispatcher);
   }
 
@@ -280,7 +280,7 @@ private void dispatchJSTouchEvent(MotionEvent event) {
       return;
     }
     ReactContext reactContext = mReactInstanceManager.getCurrentReactContext();
-    EventDispatcher eventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+    EventDispatcher eventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     mJSTouchDispatcher.handleTouchEvent(event, eventDispatcher);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java
index cae4c7f5fe1e..6818d17727fe 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java
@@ -39,7 +39,6 @@ public class ReactContext extends ContextWrapper {
 
   private LifecycleState mLifecycleState = LifecycleState.BEFORE_CREATE;
 
-  private @Nullable EventDispatcher mEventDispatcher;
   private @Nullable CatalystInstance mCatalystInstance;
   private @Nullable LayoutInflater mInflater;
   private @Nullable MessageQueueThread mUiMessageQueueThread;
@@ -351,11 +350,4 @@ public JavaScriptContextHolder getJavaScriptContextHolder() {
     return mCatalystInstance.getJavaScriptContextHolder();
   }
 
-  public <T extends EventDispatcher> T getEventDispatcher() {
-    return (T) mEventDispatcher;
-  }
-
-  public void setEventDispatcher(EventDispatcher eventDispatcher) {
-    mEventDispatcher = eventDispatcher;
-  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
index bfbeb130f56a..eb5f4cf15615 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
@@ -31,6 +31,7 @@
 import com.facebook.react.uimanager.ReactClippingViewGroup;
 import com.facebook.react.uimanager.ReactCompoundViewGroup;
 import com.facebook.react.uimanager.ReactPointerEventsView;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.views.image.ImageLoadEvent;
 import java.lang.ref.WeakReference;
@@ -126,7 +127,7 @@ public void dispatchImageLoadEvent(int reactTag, int imageLoadEvent) {
       }
 
       ReactContext reactContext = ((ReactContext) view.getContext());
-      reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
+      reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
           new ImageLoadEvent(reactTag, imageLoadEvent));
     }
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ThemedReactContext.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ThemedReactContext.java
index 8a6ab8670f3a..69dec9309e5c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ThemedReactContext.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ThemedReactContext.java
@@ -7,7 +7,6 @@
 
 package com.facebook.react.uimanager;
 
-import com.facebook.react.bridge.EventDispatcher;
 import javax.annotation.Nullable;
 
 import android.app.Activity;
@@ -17,8 +16,6 @@
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.bridge.LifecycleEventListener;
 
-//
-
 /**
  * Wraps {@link ReactContext} with the base {@link Context} passed into the constructor.
  * It provides also a way to start activities using the viewContext to which RN native views belong.
@@ -56,9 +53,4 @@ public boolean hasCurrentActivity() {
   public @Nullable Activity getCurrentActivity() {
     return mReactApplicationContext.getCurrentActivity();
   }
-
-  @Override
-  public <T extends EventDispatcher> T getEventDispatcher() {
-    return mReactApplicationContext.getEventDispatcher();
-  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index e0dd1dc4ef16..9022686a73ec 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -130,7 +130,7 @@ public UIManagerModule(
       int minTimeLeftInFrameForNonBatchedOperationMs) {
     super(reactContext);
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
-    mEventDispatcher = reactContext.getEventDispatcher();
+    mEventDispatcher = new EventDispatcher(reactContext);
     mModuleConstants = createConstants(viewManagerResolver);
     mCustomDirectEvents = UIManagerModuleConstants.getDirectEventTypeConstants();
     mUIImplementation =
@@ -150,7 +150,7 @@ public UIManagerModule(
       int minTimeLeftInFrameForNonBatchedOperationMs) {
     super(reactContext);
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
-    mEventDispatcher = reactContext.getEventDispatcher();
+    mEventDispatcher = new EventDispatcher(reactContext);
     mCustomDirectEvents = MapBuilder.newHashMap();
     mModuleConstants = createConstants(viewManagersList, null, mCustomDirectEvents);
     mUIImplementation =
@@ -704,10 +704,6 @@ public void setViewHierarchyUpdateDebugListener(
     mUIImplementation.setViewHierarchyUpdateDebugListener(listener);
   }
 
-  /**
-   * This method is deprecated, use {@link ReactContext#getEventDispatcher()}.
-   */
-  @Deprecated
   public EventDispatcher getEventDispatcher() {
     return mEventDispatcher;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
index c9bc7af5d9b1..cd8b44eb943a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
@@ -56,8 +56,7 @@
  * EVENT_TYPE_ID_MASK =  0x0000ffff00000000
  * COALESCING_KEY_MASK = 0xffff000000000000
  */
-public class EventDispatcher implements LifecycleEventListener,
-  com.facebook.react.bridge.EventDispatcher {
+public class EventDispatcher implements LifecycleEventListener {
 
   private static final Comparator<Event> EVENT_COMPARATOR = new Comparator<Event>() {
     @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBoxManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBoxManager.java
index bbc3f46504d4..c520f2fc8f5a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBoxManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBoxManager.java
@@ -10,6 +10,7 @@
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -25,7 +26,7 @@ public class ReactCheckBoxManager extends SimpleViewManager<ReactCheckBox> {
         public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
           ReactContext reactContext = (ReactContext) buttonView.getContext();
           reactContext
-              .<EventDispatcher>getEventDispatcher()
+              .getNativeModule(UIManagerModule.class).getEventDispatcher()
               .dispatchEvent(new ReactCheckBoxEvent(buttonView.getId(), isChecked));
         }
       };
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java
index b7d90bb49fd0..61139f8a01d2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/drawer/ReactDrawerLayoutManager.java
@@ -19,6 +19,7 @@
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewGroupManager;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -51,7 +52,7 @@ protected void addEventEmitters(ThemedReactContext reactContext, ReactDrawerLayo
     view.setDrawerListener(
         new DrawerEventEmitter(
             view,
-            reactContext.<EventDispatcher>getEventDispatcher()));
+            reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher()));
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index 90d053c5faa9..440bf3f2c775 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -50,6 +50,7 @@
 import com.facebook.react.modules.fresco.ReactNetworkImageRequest;
 import com.facebook.react.uimanager.FloatUtil;
 import com.facebook.react.uimanager.PixelUtil;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.views.imagehelper.ImageSource;
 import com.facebook.react.views.imagehelper.MultiSourceHelper;
@@ -231,7 +232,7 @@ public void setShouldNotifyLoadEvents(boolean shouldNotify) {
     if (!shouldNotify) {
       mControllerListener = null;
     } else {
-      final EventDispatcher mEventDispatcher = ((ReactContext) getContext()).<EventDispatcher>getEventDispatcher();
+      final EventDispatcher mEventDispatcher = ((ReactContext) getContext()).getNativeModule(UIManagerModule.class).getEventDispatcher();
 
       mControllerListener = new BaseControllerListener<ImageInfo>() {
         @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java
index fa193e0fa307..16df07953b8c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostManager.java
@@ -12,6 +12,7 @@
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.LayoutShadowNode;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewGroupManager;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -71,7 +72,7 @@ protected void addEventEmitters(
       ThemedReactContext reactContext,
       final ReactModalHostView view) {
     final EventDispatcher dispatcher =
-      reactContext.<EventDispatcher>getEventDispatcher();
+      reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     view.setOnRequestCloseListener(
       new ReactModalHostView.OnRequestCloseListener() {
         @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
index 5651e7da89f2..ab0491fe4619 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ReactModalHostView.java
@@ -370,7 +370,7 @@ public void requestDisallowInterceptTouchEvent(boolean disallowIntercept) {
 
     private EventDispatcher getEventDispatcher() {
       ReactContext reactContext = getReactContext();
-      return reactContext.<EventDispatcher>getEventDispatcher();
+      return reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     }
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java
index 9bc18c887751..a8b3fa7d1189 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/picker/ReactPickerManager.java
@@ -19,6 +19,7 @@
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -86,7 +87,7 @@ protected void addEventEmitters(
     picker.setOnSelectListener(
             new PickerEventEmitter(
                     picker,
-                    reactContext.<EventDispatcher>getEventDispatcher()));
+                    reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher()));
   }
 
   private static class ReactPickerAdapter extends ArrayAdapter<ReadableMap> {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java
index 05ce0d596ed4..9d6f51d058c9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.java
@@ -11,6 +11,7 @@
 import android.view.ViewGroup;
 import com.facebook.react.bridge.JSApplicationIllegalArgumentException;
 import com.facebook.react.bridge.ReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
 
 /**
@@ -68,7 +69,7 @@ private static void emitScrollEvent(
     }
 
     ReactContext reactContext = (ReactContext) scrollView.getContext();
-    reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
+    reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
         ScrollEvent.obtain(
             scrollView.getId(),
             scrollEventType,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
index 43aca591b2f2..4111ce3b2ea6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/slider/ReactSliderManager.java
@@ -19,6 +19,7 @@
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -107,7 +108,7 @@ public long measure(
         @Override
         public void onProgressChanged(SeekBar seekbar, int progress, boolean fromUser) {
           ReactContext reactContext = (ReactContext) seekbar.getContext();
-          reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
+          reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
               new ReactSliderEvent(
                   seekbar.getId(),
                   ((ReactSlider) seekbar).toRealProgress(progress),
@@ -121,7 +122,7 @@ public void onStartTrackingTouch(SeekBar seekbar) {
         @Override
         public void onStopTrackingTouch(SeekBar seekbar) {
           ReactContext reactContext = (ReactContext) seekbar.getContext();
-          reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
+          reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
               new ReactSlidingCompleteEvent(
                   seekbar.getId(),
                   ((ReactSlider) seekbar).toRealProgress(seekbar.getProgress())));
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java
index 387f931c1245..ab551d9436cc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/swiperefresh/SwipeRefreshLayoutManager.java
@@ -16,6 +16,7 @@
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewGroupManager;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
@@ -88,7 +89,7 @@ protected void addEventEmitters(
         new OnRefreshListener() {
           @Override
           public void onRefresh() {
-            reactContext.<EventDispatcher>getEventDispatcher()
+            reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher()
                 .dispatchEvent(new RefreshEvent(view.getId()));
           }
         });
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
index f6a7f2d8eb5d..0d802c13c45b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/switchview/ReactSwitchManager.java
@@ -17,6 +17,7 @@
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.SimpleViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -104,7 +105,7 @@ public long measure(
         @Override
         public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
           ReactContext reactContext = (ReactContext) buttonView.getContext();
-          reactContext.<EventDispatcher>getEventDispatcher().dispatchEvent(
+          reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
               new ReactSwitchEvent(
                   buttonView.getId(),
                   isChecked));
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditTextInputConnectionWrapper.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditTextInputConnectionWrapper.java
index 8f7f631caadd..26bead54761d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditTextInputConnectionWrapper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditTextInputConnectionWrapper.java
@@ -12,6 +12,7 @@
 import android.view.inputmethod.InputConnection;
 import android.view.inputmethod.InputConnectionWrapper;
 import com.facebook.react.bridge.ReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import javax.annotation.Nullable;
 
@@ -64,7 +65,7 @@ public ReactEditTextInputConnectionWrapper(
       final ReactEditText editText
   ) {
     super(target, false);
-    mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+    mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     mEditText = editText;
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
index 74671b06a832..9311a74ab7d0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
@@ -27,6 +27,7 @@
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
+import com.facebook.react.bridge.UIManager;
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.BaseViewManager;
@@ -34,6 +35,7 @@
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.Spacing;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewDefaults;
 import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.annotations.ReactProp;
@@ -693,7 +695,7 @@ private class ReactTextInputTextWatcher implements TextWatcher {
     public ReactTextInputTextWatcher(
         final ReactContext reactContext,
         final ReactEditText editText) {
-      mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+      mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
       mEditText = editText;
       mPreviousText = null;
     }
@@ -751,7 +753,7 @@ protected void addEventEmitters(
         new View.OnFocusChangeListener() {
           public void onFocusChange(View v, boolean hasFocus) {
             EventDispatcher eventDispatcher =
-                reactContext.<EventDispatcher>getEventDispatcher();
+                reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
             if (hasFocus) {
               eventDispatcher.dispatchEvent(
                   new ReactTextInputFocusEvent(
@@ -788,7 +790,7 @@ public boolean onEditorAction(TextView v, int actionId, KeyEvent keyEvent) {
               // Additionally we always generate a `submit` event.
 
               EventDispatcher eventDispatcher =
-                  reactContext.<EventDispatcher>getEventDispatcher();
+                  reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
 
               eventDispatcher.dispatchEvent(
                   new ReactTextInputSubmitEditingEvent(
@@ -817,7 +819,7 @@ private class ReactContentSizeWatcher implements ContentSizeWatcher {
     public ReactContentSizeWatcher(ReactEditText editText) {
       mEditText = editText;
       ReactContext reactContext = (ReactContext) editText.getContext();
-      mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+      mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     }
 
     @Override
@@ -856,7 +858,7 @@ private class ReactSelectionWatcher implements SelectionWatcher {
     public ReactSelectionWatcher(ReactEditText editText) {
       mReactEditText = editText;
       ReactContext reactContext = (ReactContext) editText.getContext();
-      mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+      mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     }
 
     @Override
@@ -888,7 +890,7 @@ private class ReactScrollWatcher implements ScrollWatcher {
     public ReactScrollWatcher(ReactEditText editText) {
       mReactEditText = editText;
       ReactContext reactContext = (ReactContext) editText.getContext();
-      mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+      mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     }
 
     @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
index 805d6ec56761..99cca31692fc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/toolbar/ReactToolbarManager.java
@@ -19,6 +19,7 @@
 import com.facebook.react.common.MapBuilder;
 import com.facebook.react.uimanager.PixelUtil;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewGroupManager;
 import com.facebook.react.uimanager.annotations.ReactProp;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -117,7 +118,7 @@ public void setActions(ReactToolbar view, @Nullable ReadableArray actions) {
 
   @Override
   protected void addEventEmitters(final ThemedReactContext reactContext, final ReactToolbar view) {
-    final EventDispatcher mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+    final EventDispatcher mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     view.setNavigationOnClickListener(
         new View.OnClickListener() {
           @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java b/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java
index 1bc2e36f61fe..48b5f1a61949 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/viewpager/ReactViewPager.java
@@ -15,6 +15,7 @@
 import android.view.ViewGroup;
 import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.common.ReactConstants;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.uimanager.events.NativeGestureUtil;
 import java.util.ArrayList;
@@ -158,7 +159,7 @@ public void onPageScrollStateChanged(int state) {
 
   public ReactViewPager(ReactContext reactContext) {
     super(reactContext);
-    mEventDispatcher = reactContext.<EventDispatcher>getEventDispatcher();
+    mEventDispatcher = reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     mIsCurrentItemFromJs = false;
     setOnPageChangeListener(new PageChangeListener());
     setAdapter(new Adapter());
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
index df6c8776270e..6bcc4e1857fc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/webview/ReactWebViewManager.java
@@ -9,6 +9,7 @@
 
 import android.annotation.TargetApi;
 import android.content.Context;
+import com.facebook.react.uimanager.UIManagerModule;
 import java.util.LinkedList;
 import java.util.List;
 import java.util.regex.Pattern;
@@ -686,7 +687,7 @@ public void onNewPicture(WebView webView, Picture picture) {
   protected static void dispatchEvent(WebView webView, Event event) {
     ReactContext reactContext = (ReactContext) webView.getContext();
     EventDispatcher eventDispatcher =
-      reactContext.<EventDispatcher>getEventDispatcher();
+      reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
     eventDispatcher.dispatchEvent(event);
   }
 }

From ce7dd53dab2b33b0cab640e48a089a8ef81d89ab Mon Sep 17 00:00:00 2001
From: Alexey Lang <alexeylang@fb.com>
Date: Thu, 31 May 2018 02:37:33 -0700
Subject: [PATCH 0694/1109] Use timestamps from QPL by default

Differential Revision: D8207166

fbshipit-source-id: 1e43d6874ee400cb2e26a11cbcfb12ee32d28d3c
---
 Libraries/Utilities/PerformanceLogger.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/Libraries/Utilities/PerformanceLogger.js b/Libraries/Utilities/PerformanceLogger.js
index 23fcac7951f7..203e24125879 100644
--- a/Libraries/Utilities/PerformanceLogger.js
+++ b/Libraries/Utilities/PerformanceLogger.js
@@ -16,7 +16,9 @@ const performanceNow =
   /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an
    * error found when Flow v0.54 was deployed. To see the error delete this
    * comment and run Flow. */
-  global.nativePerformanceNow || require('fbjs/lib/performanceNow');
+  global.nativeQPLTimestamp ||
+  global.nativePerformanceNow ||
+  require('fbjs/lib/performanceNow');
 
 type Timespan = {
   description?: string,

From 536c9372692712b12317e657fc3e4263ecc70164 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Thu, 31 May 2018 04:26:28 -0700
Subject: [PATCH 0695/1109] Upgrade Jest to 23.1.0

Reviewed By: davidaurelio

Differential Revision: D8212583

fbshipit-source-id: 245a5ccc9bcd63a0995dcb5a1770a6f5f34cd04e
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 1ed8d3aabda8..d619cb176d40 100644
--- a/package.json
+++ b/package.json
@@ -213,7 +213,7 @@
     "eslint-plugin-react": "7.6.1",
     "eslint-plugin-react-native": "^3.2.1",
     "flow-bin": "^0.73.0",
-    "jest": "23.0.1",
+    "jest": "23.1.0",
     "jest-junit": "4.0.0",
     "prettier": "1.12.1",
     "react": "16.3.2",

From fecfa2a5537e057c677e5c8a76b95b251cc218f2 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Thu, 31 May 2018 11:53:20 -0700
Subject: [PATCH 0696/1109] Revert D8194925: Fix ART surface sleep issue

Differential Revision:
D8194925

Original commit changeset: 5448d49d9590

fbshipit-source-id: c01e11d44424e1f6fb79866bb845ed60764c5f13
---
 .../react/flat/FlatARTSurfaceViewManager.java  |  4 +---
 .../flat/FlatARTSurfaceViewShadowNode.java     | 18 +++++++++++-------
 .../react/views/art/ARTSurfaceView.java        |  5 +++--
 .../react/views/art/ARTSurfaceViewManager.java |  3 +--
 .../views/art/ARTSurfaceViewShadowNode.java    | 16 +++++++++-------
 5 files changed, 25 insertions(+), 21 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
index d1172d82a7e8..f6382b80befc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
@@ -7,7 +7,6 @@
 
 package com.facebook.react.flat;
 
-import android.view.SurfaceHolder;
 import com.facebook.react.uimanager.BaseViewManager;
 import com.facebook.react.uimanager.ThemedReactContext;
 import com.facebook.react.views.art.ARTSurfaceView;
@@ -15,7 +14,6 @@
 import com.facebook.yoga.YogaMeasureMode;
 import com.facebook.yoga.YogaNode;
 
-
 public class FlatARTSurfaceViewManager extends
   BaseViewManager<ARTSurfaceView, FlatARTSurfaceViewShadowNode> {
 
@@ -57,6 +55,6 @@ protected ARTSurfaceView createViewInstance(ThemedReactContext reactContext) {
 
   @Override
   public void updateExtraData(ARTSurfaceView root, Object extraData) {
-    root.getHolder().addCallback((FlatARTSurfaceViewShadowNode) extraData);
+    root.setSurfaceTextureListener((FlatARTSurfaceViewShadowNode) extraData);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
index aefe34104a24..09fa6a42a429 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
@@ -16,7 +16,7 @@
 import android.graphics.SurfaceTexture;
 import android.util.Log;
 import android.view.Surface;
-import android.view.SurfaceHolder;
+import android.view.TextureView;
 
 import com.facebook.react.common.ReactConstants;
 import com.facebook.react.uimanager.ReactShadowNode;
@@ -25,9 +25,8 @@
 import com.facebook.yoga.YogaValue;
 import com.facebook.yoga.YogaUnit;
 
-
 /* package */ class FlatARTSurfaceViewShadowNode extends FlatShadowNode
-    implements AndroidView, SurfaceHolder.Callback {
+    implements AndroidView, TextureView.SurfaceTextureListener {
   private boolean mPaddingChanged = false;
   private @Nullable Surface mSurface;
 
@@ -124,16 +123,21 @@ public void setPaddingPercent(int spacingType, float percent) {
   }
 
   @Override
-  public void surfaceCreated(SurfaceHolder holder) {
-    mSurface = holder.getSurface();
+  public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) {
+    mSurface = new Surface(surface);
     drawOutput();
   }
 
   @Override
-  public void surfaceDestroyed(SurfaceHolder holder) {
+  public boolean onSurfaceTextureDestroyed(SurfaceTexture surface) {
+    surface.release();
     mSurface = null;
+    return true;
   }
 
   @Override
-  public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {}
+  public void onSurfaceTextureSizeChanged(SurfaceTexture surface, int width, int height) {}
+
+  @Override
+  public void onSurfaceTextureUpdated(SurfaceTexture surface) {}
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceView.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceView.java
index ac68a9b2e85f..93f2c21eb1aa 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceView.java
@@ -8,13 +8,14 @@
 package com.facebook.react.views.art;
 
 import android.content.Context;
-import android.view.SurfaceView;
+import android.view.TextureView;
 
 /**
  * Custom {@link View} implementation that draws an ARTSurface React view and its children.
  */
-public class ARTSurfaceView extends SurfaceView {
+public class ARTSurfaceView extends TextureView {
   public ARTSurfaceView(Context context) {
     super(context);
+    setOpaque(false);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewManager.java
index d1ee910d0ab6..24787ef84a53 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewManager.java
@@ -7,7 +7,6 @@
 
 package com.facebook.react.views.art;
 
-import android.view.SurfaceHolder;
 import com.facebook.yoga.YogaMeasureMode;
 import com.facebook.yoga.YogaMeasureFunction;
 import com.facebook.yoga.YogaNode;
@@ -61,7 +60,7 @@ protected ARTSurfaceView createViewInstance(ThemedReactContext reactContext) {
 
   @Override
   public void updateExtraData(ARTSurfaceView root, Object extraData) {
-    root.getHolder().addCallback((ARTSurfaceViewShadowNode) extraData);
+    root.setSurfaceTextureListener((ARTSurfaceViewShadowNode) extraData);
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewShadowNode.java
index c0a893481c0b..429812e19916 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTSurfaceViewShadowNode.java
@@ -15,10 +15,8 @@
 import android.view.Surface;
 import android.graphics.PorterDuff;
 import android.graphics.SurfaceTexture;
-import android.view.SurfaceHolder;
 import android.view.TextureView;
 
-
 import com.facebook.common.logging.FLog;
 import com.facebook.react.common.ReactConstants;
 import com.facebook.react.uimanager.LayoutShadowNode;
@@ -31,7 +29,7 @@
  * Shadow node for ART virtual tree root - ARTSurfaceView
  */
 public class ARTSurfaceViewShadowNode extends LayoutShadowNode
-  implements SurfaceHolder.Callback {
+  implements TextureView.SurfaceTextureListener {
 
   private @Nullable Surface mSurface;
 
@@ -99,17 +97,21 @@ private void markChildrenUpdatesSeen(ReactShadowNode shadowNode) {
   }
 
   @Override
-  public void surfaceCreated(SurfaceHolder holder) {
-    mSurface = holder.getSurface();
+  public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) {
+    mSurface = new Surface(surface);
     drawOutput();
   }
 
   @Override
-  public void surfaceDestroyed(SurfaceHolder holder) {
+  public boolean onSurfaceTextureDestroyed(SurfaceTexture surface) {
+    surface.release();
     mSurface = null;
+    return true;
   }
 
   @Override
-  public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {}
+  public void onSurfaceTextureSizeChanged(SurfaceTexture surface, int width, int height) {}
 
+  @Override
+  public void onSurfaceTextureUpdated(SurfaceTexture surface) {}
 }

From 216bce31632480ce70cc03b1b2a57ec12440afd7 Mon Sep 17 00:00:00 2001
From: sAm_vdP <bartsteinmayr@gmail.com>
Date: Thu, 31 May 2018 12:49:00 -0700
Subject: [PATCH 0697/1109] Fix jest snapshot testing on windows

Summary:
Fixes #19370

Applied changes to existing project that uses jest snapshot testing. Testing was broken before and now works.

To verify: Run any snapshot test containing an image reference on Windows before and after this PR.

[WINDOWS][BUGFIX][jest] - Fixed jest snapshot testing on windows
Closes https://github.com/facebook/react-native/pull/19496

Differential Revision: D8195947

Pulled By: hramos

fbshipit-source-id: 909b5fe7cfd8c6286baf161a227a359854a37603
---
 jest-preset.json             | 2 +-
 jest/assetFileTransformer.js | 5 ++++-
 package.json                 | 2 +-
 3 files changed, 6 insertions(+), 3 deletions(-)

diff --git a/jest-preset.json b/jest-preset.json
index afd12eb96e73..c7fb437e470b 100644
--- a/jest-preset.json
+++ b/jest-preset.json
@@ -15,7 +15,7 @@
   ],
   "transform": {
     "^.+\\.js$": "babel-jest",
-    "^[./a-zA-Z0-9$_-]+\\.(bmp|gif|jpg|jpeg|mp4|png|psd|svg|webp)$": "<rootDir>/node_modules/react-native/jest/assetFileTransformer.js"
+    "^.+\\.(bmp|gif|jpg|jpeg|mp4|png|psd|svg|webp)$": "<rootDir>/node_modules/react-native/jest/assetFileTransformer.js"
   },
   "transformIgnorePatterns": [
     "node_modules/(?!(jest-)?react-native|react-clone-referenced-element)"
diff --git a/jest/assetFileTransformer.js b/jest/assetFileTransformer.js
index da6cf34a0da5..85f4a7bceb2a 100644
--- a/jest/assetFileTransformer.js
+++ b/jest/assetFileTransformer.js
@@ -21,7 +21,10 @@ module.exports = {
   // the Jest snapshot.
   process: (_, filename) =>
     `module.exports = {
-      testUri: ${JSON.stringify(path.relative(__dirname, filename))}
+      testUri: 
+        ${JSON.stringify(
+          path.relative(__dirname, filename).replace(/\\/g, '/'),
+        )}
     };`,
   getCacheKey: createCacheKeyFunction([__filename]),
 };
diff --git a/package.json b/package.json
index d619cb176d40..373cdc2e6b8c 100644
--- a/package.json
+++ b/package.json
@@ -20,7 +20,7 @@
   },
   "jest": {
     "transform": {
-      "^[./a-zA-Z0-9$_-]+\\.(bmp|gif|jpg|jpeg|mp4|png|psd|svg|webp)$": "<rootDir>/jest/assetFileTransformer.js",
+      "^.+\\.(bmp|gif|jpg|jpeg|mp4|png|psd|svg|webp)$": "<rootDir>/jest/assetFileTransformer.js",
       ".*": "./jest/preprocessor.js"
     },
     "setupFiles": [

From dcfe4ef26f9316d9fad4cf97bd6f63ecc7fd5b4f Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Thu, 31 May 2018 14:50:41 -0700
Subject: [PATCH 0698/1109] Enable webhooks on Circle

Summary:
Release Notes
=============

[INTERNAL][MINOR][CircleCI] - Send webhooks to Facebook.
Closes https://github.com/facebook/react-native/pull/19527

Differential Revision: D8228361

Pulled By: hramos

fbshipit-source-id: 5d7c0960392b9a860d3f665e2a316c18153879eb
---
 .circleci/config.yml | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 7b78ebf8f522..7e694fb89695 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -672,3 +672,11 @@ workflows:
   #         filters: *filter-ignore-gh-pages
   #         requires:
   #           - checkout_code
+
+experimental:
+  notify:
+    webhooks:
+      - url: https://code.facebook.com/circle/webhook/
+    branches:
+      only:
+        - master

From da7873563bff945086a70306cc25fa4c048bb84b Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Thu, 31 May 2018 15:31:03 -0700
Subject: [PATCH 0699/1109] Migrate Android sources to MIT license header

Reviewed By: fkgozali

Differential Revision: D8065619

fbshipit-source-id: 719c303b40c96950bab8e5dde9a75f449b2956c6
---
 React/CxxBridge/RCTCxxBridge.mm                            | 2 --
 React/CxxBridge/RCTJSCHelpers.h                            | 2 --
 React/CxxBridge/RCTJSCHelpers.mm                           | 2 --
 React/DevSupport/RCTInspectorDevServerHelper.h             | 5 ++++-
 React/Inspector/RCTInspector.h                             | 5 ++++-
 React/Inspector/RCTInspectorPackagerConnection.h           | 5 ++++-
 ReactAndroid/build.gradle                                  | 5 ++++-
 ReactAndroid/release.gradle                                | 5 ++++-
 .../facebook/debug/debugoverlay/model/DebugOverlayTag.java | 5 ++++-
 .../main/java/com/facebook/debug/holder/NoopPrinter.java   | 5 ++++-
 .../src/main/java/com/facebook/debug/holder/Printer.java   | 5 ++++-
 .../main/java/com/facebook/debug/holder/PrinterHolder.java | 5 ++++-
 .../com/facebook/debug/tags/ReactDebugOverlayTags.java     | 5 ++++-
 ReactAndroid/src/main/java/com/facebook/jni/Countable.java | 5 ++++-
 .../src/main/java/com/facebook/jni/CpuCapabilitiesJni.java | 5 ++++-
 .../src/main/java/com/facebook/jni/DestructorThread.java   | 5 ++++-
 .../src/main/java/com/facebook/jni/HybridClassBase.java    | 5 ++++-
 .../src/main/java/com/facebook/jni/HybridData.java         | 5 ++++-
 .../main/java/com/facebook/jni/JniTerminateHandler.java    | 5 ++++-
 .../src/main/java/com/facebook/jni/ThreadScopeSupport.java | 5 ++++-
 .../main/java/com/facebook/react/EagerModuleProvider.java  | 5 ++++-
 .../main/java/com/facebook/react/MemoryPressureRouter.java | 5 ++++-
 .../com/facebook/react/NativeModuleRegistryBuilder.java    | 5 ++++-
 .../java/com/facebook/react/ReactActivityDelegate.java     | 5 ++++-
 .../com/facebook/react/ReactInstanceManagerBuilder.java    | 5 ++++-
 .../main/java/com/facebook/react/ReactPackageLogger.java   | 5 ++++-
 .../com/facebook/react/bridge/ActivityEventListener.java   | 5 ++++-
 .../facebook/react/bridge/BaseActivityEventListener.java   | 5 ++++-
 .../java/com/facebook/react/bridge/CxxCallbackImpl.java    | 5 ++++-
 .../java/com/facebook/react/bridge/CxxModuleWrapper.java   | 5 ++++-
 .../com/facebook/react/bridge/CxxModuleWrapperBase.java    | 5 ++++-
 .../com/facebook/react/bridge/GuardedResultAsyncTask.java  | 5 ++++-
 .../java/com/facebook/react/bridge/GuardedRunnable.java    | 5 ++++-
 .../src/main/java/com/facebook/react/bridge/Inspector.java | 5 ++++-
 .../com/facebook/react/bridge/JavaScriptContextHolder.java | 5 ++++-
 .../java/com/facebook/react/bridge/MemoryPressure.java     | 5 ++++-
 .../com/facebook/react/bridge/MemoryPressureListener.java  | 5 ++++-
 .../main/java/com/facebook/react/bridge/ModuleHolder.java  | 5 ++++-
 .../main/java/com/facebook/react/bridge/ReactMarker.java   | 5 ++++-
 .../com/facebook/react/bridge/ReactMarkerConstants.java    | 5 ++++-
 .../src/main/java/com/facebook/react/bridge/Systrace.java  | 5 ++++-
 .../facebook/react/common/ClearableSynchronizedPool.java   | 5 ++++-
 .../react/devsupport/InspectorPackagerConnection.java      | 5 ++++-
 .../java/com/facebook/react/devsupport/JSDevSupport.java   | 5 ++++-
 .../com/facebook/react/jstasks/HeadlessJsTaskConfig.java   | 5 ++++-
 .../com/facebook/react/jstasks/HeadlessJsTaskContext.java  | 5 ++++-
 .../facebook/react/module/annotations/ReactModuleList.java | 5 ++++-
 .../com/facebook/react/module/model/ReactModuleInfo.java   | 5 ++++-
 .../react/module/model/ReactModuleInfoProvider.java        | 5 ++++-
 .../react/module/processing/ReactModuleSpecProcessor.java  | 5 ++++-
 .../modules/accessibilityinfo/AccessibilityInfoModule.java | 5 ++++-
 .../react/modules/fresco/SystraceRequestListener.java      | 5 ++++-
 .../react/modules/network/ForwardingCookieHandler.java     | 5 ++++-
 .../react/modules/network/ProgressResponseBody.java        | 5 ++++-
 .../react/modules/systeminfo/AndroidInfoHelpers.java       | 5 ++++-
 .../facebook/react/processing/ReactPropertyProcessor.java  | 5 ++++-
 .../java/com/facebook/react/uimanager/BaseViewManager.java | 5 ++++-
 .../com/facebook/react/uimanager/LayoutShadowNode.java     | 5 ++++-
 .../react/uimanager/ReactRootViewTagGenerator.java         | 5 ++++-
 .../facebook/react/uimanager/ReactZIndexedViewGroup.java   | 5 ++++-
 .../react/uimanager/ViewManagerPropertyUpdater.java        | 5 ++++-
 .../react/uimanager/ViewManagersPropertyCache.java         | 5 ++++-
 .../java/com/facebook/react/uimanager/YogaNodePool.java    | 5 ++++-
 .../facebook/react/uimanager/annotations/ReactProp.java    | 5 ++++-
 .../react/uimanager/annotations/ReactPropGroup.java        | 5 ++++-
 .../react/uimanager/annotations/ReactPropertyHolder.java   | 5 ++++-
 .../react/uimanager/common/MeasureSpecProvider.java        | 5 ++++-
 .../react/uimanager/events/ContentSizeChangeEvent.java     | 5 ++++-
 .../react/uimanager/events/EventDispatcherListener.java    | 5 ++++-
 .../uimanager/layoutanimation/AbstractLayoutAnimation.java | 5 ++++-
 .../uimanager/layoutanimation/AnimatedPropertyType.java    | 5 ++++-
 .../uimanager/layoutanimation/BaseLayoutAnimation.java     | 5 ++++-
 .../react/uimanager/layoutanimation/InterpolatorType.java  | 5 ++++-
 .../layoutanimation/LayoutAnimationController.java         | 5 ++++-
 .../uimanager/layoutanimation/LayoutAnimationListener.java | 5 ++++-
 .../uimanager/layoutanimation/LayoutAnimationType.java     | 5 ++++-
 .../uimanager/layoutanimation/LayoutCreateAnimation.java   | 5 ++++-
 .../uimanager/layoutanimation/LayoutDeleteAnimation.java   | 5 ++++-
 .../uimanager/layoutanimation/LayoutHandlingAnimation.java | 5 ++++-
 .../uimanager/layoutanimation/LayoutUpdateAnimation.java   | 5 ++++-
 .../react/uimanager/layoutanimation/OpacityAnimation.java  | 5 ++++-
 .../layoutanimation/PositionAndSizeAnimation.java          | 5 ++++-
 .../layoutanimation/SimpleSpringInterpolator.java          | 5 ++++-
 .../facebook/react/uimanager/util/ReactFindViewUtil.java   | 5 ++++-
 .../com/facebook/react/views/art/ARTGroupViewManager.java  | 5 ++++-
 .../com/facebook/react/views/art/ARTShapeViewManager.java  | 5 ++++-
 .../com/facebook/react/views/art/ARTTextViewManager.java   | 5 ++++-
 .../java/com/facebook/react/views/common/ViewHelper.java   | 5 ++++-
 .../react/views/image/GlobalImageLoadListener.java         | 5 ++++-
 .../com/facebook/react/views/modal/ModalHostHelper.java    | 5 ++++-
 .../react/views/progressbar/ProgressBarContainerView.java  | 5 ++++-
 .../views/scroll/ReactHorizontalScrollContainerView.java   | 5 ++++-
 .../scroll/ReactHorizontalScrollContainerViewManager.java  | 5 ++++-
 .../react/views/text/ReactVirtualTextShadowNode.java       | 5 ++++-
 .../java/com/facebook/react/views/view/MeasureUtil.java    | 5 ++++-
 .../react/views/view/ReactViewBackgroundManager.java       | 5 ++++-
 .../src/main/java/com/facebook/systrace/TraceListener.java | 5 ++++-
 .../src/main/jni/first-party/fb/include/fb/Build.h         | 5 ++++-
 .../jni/first-party/fb/include/fb/fbjni/JWeakReference.h   | 5 ++++-
 .../main/jni/first-party/fb/include/fb/fbjni/MetaConvert.h | 5 ++++-
 ReactAndroid/src/main/jni/first-party/fb/include/fb/lyra.h | 5 ++++-
 .../jni/first-party/fb/jni/android/CpuCapabilities.cpp     | 5 ++++-
 ReactAndroid/src/main/jni/first-party/fb/lyra/lyra.cpp     | 5 ++++-
 .../src/main/jni/first-party/fbgloginit/fb/glog_init.h     | 5 ++++-
 .../src/main/jni/first-party/fbgloginit/glog_init.cpp      | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp  | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h    | 5 ++++-
 .../src/main/jni/react/jni/CatalystInstanceImpl.cpp        | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.cpp   | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.h     | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/CxxModuleWrapperBase.h | 5 ++++-
 .../src/main/jni/react/jni/CxxSharedModuleWrapper.h        | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JCallback.h            | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JInspector.cpp         | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JInspector.h           | 5 ++++-
 .../src/main/jni/react/jni/JMessageQueueThread.cpp         | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.h  | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JNativeRunnable.h      | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JReactMarker.cpp       | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JReactMarker.h         | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp     | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.h       | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JSLoader.cpp           | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JSLoader.h             | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JSLogging.cpp          | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JSLogging.h            | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.cpp  | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.h    | 5 ++++-
 .../src/main/jni/react/jni/JavaScriptExecutorHolder.h      | 5 ++++-
 .../src/main/jni/react/jni/JniJSModulesUnbundle.cpp        | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.h | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/MethodInvoker.cpp      | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/MethodInvoker.h        | 5 ++++-
 .../src/main/jni/react/jni/ModuleRegistryBuilder.cpp       | 5 ++++-
 .../src/main/jni/react/jni/ModuleRegistryBuilder.h         | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/NativeArray.cpp        | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/NativeArray.h          | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/NativeCommon.cpp       | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/NativeCommon.h         | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp  | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h    | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/NativeMap.cpp          | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/NativeMap.h            | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/OnLoad.cpp             | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/OnLoad.h               | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/ProxyExecutor.cpp      | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/ProxyExecutor.h        | 5 ++++-
 .../src/main/jni/react/jni/ReadableNativeArray.cpp         | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.cpp  | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.h    | 5 ++++-
 .../src/main/jni/react/jni/WritableNativeArray.cpp         | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/WritableNativeArray.h  | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/WritableNativeMap.cpp  | 5 ++++-
 ReactAndroid/src/main/jni/react/jni/WritableNativeMap.h    | 5 ++++-
 ReactAndroid/src/main/jni/react/perftests/OnLoad.cpp       | 5 ++++-
 .../com/facebook/react/fabric/FabricReconcilerTest.java    | 5 ++++-
 .../com/facebook/react/fabric/FabricUIManagerTest.java     | 5 ++++-
 .../com/facebook/react/fabric/ReactShadowNodeTest.java     | 5 ++++-
 ReactCommon/cxxreact/CxxModule.h                           | 5 ++++-
 ReactCommon/cxxreact/CxxNativeModule.cpp                   | 5 ++++-
 ReactCommon/cxxreact/CxxNativeModule.h                     | 5 ++++-
 ReactCommon/cxxreact/Instance.cpp                          | 5 ++++-
 ReactCommon/cxxreact/Instance.h                            | 5 ++++-
 ReactCommon/cxxreact/JSBigString.cpp                       | 5 ++++-
 ReactCommon/cxxreact/JSBigString.h                         | 5 ++++-
 ReactCommon/cxxreact/JSBundleType.cpp                      | 5 ++++-
 ReactCommon/cxxreact/JSBundleType.h                        | 5 ++++-
 ReactCommon/cxxreact/JSCExecutor.cpp                       | 5 ++++-
 ReactCommon/cxxreact/JSCExecutor.h                         | 5 ++++-
 ReactCommon/cxxreact/JSCLegacyTracing.cpp                  | 5 ++++-
 ReactCommon/cxxreact/JSCLegacyTracing.h                    | 5 ++++-
 ReactCommon/cxxreact/JSCMemory.cpp                         | 5 ++++-
 ReactCommon/cxxreact/JSCMemory.h                           | 5 ++++-
 ReactCommon/cxxreact/JSCNativeModules.cpp                  | 5 ++++-
 ReactCommon/cxxreact/JSCNativeModules.h                    | 5 ++++-
 ReactCommon/cxxreact/JSCPerfStats.cpp                      | 5 ++++-
 ReactCommon/cxxreact/JSCPerfStats.h                        | 5 ++++-
 ReactCommon/cxxreact/JSCSamplingProfiler.cpp               | 5 ++++-
 ReactCommon/cxxreact/JSCSamplingProfiler.h                 | 5 ++++-
 ReactCommon/cxxreact/JSCTracing.cpp                        | 5 ++++-
 ReactCommon/cxxreact/JSCTracing.h                          | 5 ++++-
 ReactCommon/cxxreact/JSCUtils.cpp                          | 5 ++++-
 ReactCommon/cxxreact/JSCUtils.h                            | 5 ++++-
 ReactCommon/cxxreact/JSDeltaBundleClient.h                 | 5 ++++-
 ReactCommon/cxxreact/JSExecutor.cpp                        | 5 ++++-
 ReactCommon/cxxreact/JSExecutor.h                          | 5 ++++-
 ReactCommon/cxxreact/JSIndexedRAMBundle.cpp                | 5 ++++-
 ReactCommon/cxxreact/JSIndexedRAMBundle.h                  | 5 ++++-
 ReactCommon/cxxreact/JSModulesUnbundle.h                   | 5 ++++-
 ReactCommon/cxxreact/JsArgumentHelpers-inl.h               | 5 ++++-
 ReactCommon/cxxreact/JsArgumentHelpers.h                   | 5 ++++-
 ReactCommon/cxxreact/MessageQueueThread.h                  | 5 ++++-
 ReactCommon/cxxreact/MethodCall.cpp                        | 5 ++++-
 ReactCommon/cxxreact/MethodCall.h                          | 5 ++++-
 ReactCommon/cxxreact/ModuleRegistry.cpp                    | 5 ++++-
 ReactCommon/cxxreact/ModuleRegistry.h                      | 5 ++++-
 ReactCommon/cxxreact/NativeModule.h                        | 5 ++++-
 ReactCommon/cxxreact/NativeToJsBridge.cpp                  | 5 ++++-
 ReactCommon/cxxreact/NativeToJsBridge.h                    | 5 ++++-
 ReactCommon/cxxreact/Platform.cpp                          | 5 ++++-
 ReactCommon/cxxreact/Platform.h                            | 5 ++++-
 ReactCommon/cxxreact/RAMBundleRegistry.cpp                 | 5 ++++-
 ReactCommon/cxxreact/RAMBundleRegistry.h                   | 5 ++++-
 ReactCommon/cxxreact/ReactMarker.cpp                       | 5 ++++-
 ReactCommon/cxxreact/ReactMarker.h                         | 5 ++++-
 ReactCommon/cxxreact/RecoverableError.h                    | 5 ++++-
 ReactCommon/cxxreact/SampleCxxModule.cpp                   | 5 ++++-
 ReactCommon/cxxreact/SampleCxxModule.h                     | 5 ++++-
 ReactCommon/cxxreact/SharedProxyCxxModule.h                | 5 ++++-
 ReactCommon/cxxreact/SystraceSection.h                     | 5 ++++-
 ReactCommon/cxxreact/tests/RecoverableErrorTest.cpp        | 5 ++++-
 ReactCommon/cxxreact/tests/jsarg_helpers.cpp               | 5 ++++-
 ReactCommon/cxxreact/tests/jsbigstring.cpp                 | 5 ++++-
 ReactCommon/cxxreact/tests/jscexecutor.cpp                 | 5 ++++-
 ReactCommon/cxxreact/tests/jsclogging.cpp                  | 5 ++++-
 ReactCommon/cxxreact/tests/methodcall.cpp                  | 5 ++++-
 ReactCommon/cxxreact/tests/value.cpp                       | 5 ++++-
 ReactCommon/fabric/graphics/Geometry.h                     | 5 ++++-
 .../fabric/uimanager/ComponentDescriptorRegistry.cpp       | 5 ++++-
 ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h | 5 ++++-
 ReactCommon/fabric/uimanager/Differentiator.cpp            | 5 ++++-
 ReactCommon/fabric/uimanager/Differentiator.h              | 5 ++++-
 ReactCommon/fabric/uimanager/Scheduler.cpp                 | 7 +++++--
 ReactCommon/fabric/uimanager/Scheduler.h                   | 5 ++++-
 ReactCommon/fabric/uimanager/SchedulerDelegate.h           | 5 ++++-
 ReactCommon/fabric/uimanager/ShadowTree.cpp                | 5 ++++-
 ReactCommon/fabric/uimanager/ShadowTree.h                  | 5 ++++-
 ReactCommon/fabric/uimanager/ShadowTreeDelegate.h          | 5 ++++-
 ReactCommon/jschelpers/JSCHelpers.cpp                      | 5 ++++-
 ReactCommon/jschelpers/JSCHelpers.h                        | 5 ++++-
 ReactCommon/jschelpers/Unicode.cpp                         | 5 ++++-
 ReactCommon/jschelpers/Unicode.h                           | 5 ++++-
 ReactCommon/jschelpers/Value.cpp                           | 5 ++++-
 ReactCommon/jschelpers/Value.h                             | 5 ++++-
 ReactCommon/jschelpers/noncopyable.h                       | 5 ++++-
 ReactCommon/microprofiler/MicroProfiler.cpp                | 5 ++++-
 ReactCommon/microprofiler/MicroProfiler.h                  | 5 ++++-
 ReactCommon/privatedata/PrivateDataBase.cpp                | 5 ++++-
 ReactCommon/privatedata/PrivateDataBase.h                  | 5 ++++-
 build.gradle                                               | 5 ++++-
 settings.gradle                                            | 5 ++++-
 242 files changed, 957 insertions(+), 246 deletions(-)

diff --git a/React/CxxBridge/RCTCxxBridge.mm b/React/CxxBridge/RCTCxxBridge.mm
index d820d2f10e31..b445991fbb34 100644
--- a/React/CxxBridge/RCTCxxBridge.mm
+++ b/React/CxxBridge/RCTCxxBridge.mm
@@ -1,5 +1,3 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
 /**
  * Copyright (c) 2015-present, Facebook, Inc.
  *
diff --git a/React/CxxBridge/RCTJSCHelpers.h b/React/CxxBridge/RCTJSCHelpers.h
index 38eb26a1dad1..b58ccbf58efd 100644
--- a/React/CxxBridge/RCTJSCHelpers.h
+++ b/React/CxxBridge/RCTJSCHelpers.h
@@ -1,5 +1,3 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
 /**
  * Copyright (c) 2015-present, Facebook, Inc.
  *
diff --git a/React/CxxBridge/RCTJSCHelpers.mm b/React/CxxBridge/RCTJSCHelpers.mm
index 760c50022aa1..a7e7a8a9b723 100644
--- a/React/CxxBridge/RCTJSCHelpers.mm
+++ b/React/CxxBridge/RCTJSCHelpers.mm
@@ -1,5 +1,3 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
-
 /**
  * Copyright (c) 2015-present, Facebook, Inc.
  *
diff --git a/React/DevSupport/RCTInspectorDevServerHelper.h b/React/DevSupport/RCTInspectorDevServerHelper.h
index 42a4f6a2e408..f377926bb126 100644
--- a/React/DevSupport/RCTInspectorDevServerHelper.h
+++ b/React/DevSupport/RCTInspectorDevServerHelper.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #import <Foundation/Foundation.h>
 #import <JavaScriptCore/JSBase.h>
diff --git a/React/Inspector/RCTInspector.h b/React/Inspector/RCTInspector.h
index 41bd146e0031..e653f917886f 100644
--- a/React/Inspector/RCTInspector.h
+++ b/React/Inspector/RCTInspector.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #import <Foundation/Foundation.h>
 #import <React/RCTDefines.h>
diff --git a/React/Inspector/RCTInspectorPackagerConnection.h b/React/Inspector/RCTInspectorPackagerConnection.h
index 8499ea406327..ad15e043c307 100644
--- a/React/Inspector/RCTInspectorPackagerConnection.h
+++ b/React/Inspector/RCTInspectorPackagerConnection.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #import <Foundation/Foundation.h>
 #import <React/RCTDefines.h>
diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 503b814f32ac..aa23d8898c0f 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -1,4 +1,7 @@
-// Copyright 2015-present Facebook. All Rights Reserved.
+// Copyright (c) 2015-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 apply plugin: 'com.android.library'
 apply plugin: 'maven'
diff --git a/ReactAndroid/release.gradle b/ReactAndroid/release.gradle
index 3e67beb0a3f2..d01daf739de1 100644
--- a/ReactAndroid/release.gradle
+++ b/ReactAndroid/release.gradle
@@ -1,4 +1,7 @@
-// Copyright 2015-present Facebook. All Rights Reserved.
+// Copyright (c) 2015-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 apply plugin: 'maven'
 apply plugin: 'signing'
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/debugoverlay/model/DebugOverlayTag.java b/ReactAndroid/src/main/java/com/facebook/debug/debugoverlay/model/DebugOverlayTag.java
index c0a1790d8868..07d2605717a6 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/debugoverlay/model/DebugOverlayTag.java
+++ b/ReactAndroid/src/main/java/com/facebook/debug/debugoverlay/model/DebugOverlayTag.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.debug.debugoverlay.model;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/holder/NoopPrinter.java b/ReactAndroid/src/main/java/com/facebook/debug/holder/NoopPrinter.java
index 6c31109a78f7..a7bba0583105 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/holder/NoopPrinter.java
+++ b/ReactAndroid/src/main/java/com/facebook/debug/holder/NoopPrinter.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.debug.holder;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/holder/Printer.java b/ReactAndroid/src/main/java/com/facebook/debug/holder/Printer.java
index dffe707da1e6..4fcfc24ca6f1 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/holder/Printer.java
+++ b/ReactAndroid/src/main/java/com/facebook/debug/holder/Printer.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.debug.holder;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/holder/PrinterHolder.java b/ReactAndroid/src/main/java/com/facebook/debug/holder/PrinterHolder.java
index 3634646333c9..e0405a4b99c9 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/holder/PrinterHolder.java
+++ b/ReactAndroid/src/main/java/com/facebook/debug/holder/PrinterHolder.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.debug.holder;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/debug/tags/ReactDebugOverlayTags.java b/ReactAndroid/src/main/java/com/facebook/debug/tags/ReactDebugOverlayTags.java
index 4df1f1aba797..6bc6b598373b 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/tags/ReactDebugOverlayTags.java
+++ b/ReactAndroid/src/main/java/com/facebook/debug/tags/ReactDebugOverlayTags.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.debug.tags;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/jni/Countable.java b/ReactAndroid/src/main/java/com/facebook/jni/Countable.java
index a319e187aac3..342a6f01e28c 100644
--- a/ReactAndroid/src/main/java/com/facebook/jni/Countable.java
+++ b/ReactAndroid/src/main/java/com/facebook/jni/Countable.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.jni;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/jni/CpuCapabilitiesJni.java b/ReactAndroid/src/main/java/com/facebook/jni/CpuCapabilitiesJni.java
index f8f3054c885d..ce3ae8da14b9 100644
--- a/ReactAndroid/src/main/java/com/facebook/jni/CpuCapabilitiesJni.java
+++ b/ReactAndroid/src/main/java/com/facebook/jni/CpuCapabilitiesJni.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.jni;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/jni/DestructorThread.java b/ReactAndroid/src/main/java/com/facebook/jni/DestructorThread.java
index 6b00078f0b12..3ae10379969d 100644
--- a/ReactAndroid/src/main/java/com/facebook/jni/DestructorThread.java
+++ b/ReactAndroid/src/main/java/com/facebook/jni/DestructorThread.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.jni;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/jni/HybridClassBase.java b/ReactAndroid/src/main/java/com/facebook/jni/HybridClassBase.java
index a20b92b8f1b4..3e39175c42f6 100644
--- a/ReactAndroid/src/main/java/com/facebook/jni/HybridClassBase.java
+++ b/ReactAndroid/src/main/java/com/facebook/jni/HybridClassBase.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.jni;
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/jni/HybridData.java b/ReactAndroid/src/main/java/com/facebook/jni/HybridData.java
index 9ace5f3ddc95..ad4077e669c9 100644
--- a/ReactAndroid/src/main/java/com/facebook/jni/HybridData.java
+++ b/ReactAndroid/src/main/java/com/facebook/jni/HybridData.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.jni;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/jni/JniTerminateHandler.java b/ReactAndroid/src/main/java/com/facebook/jni/JniTerminateHandler.java
index 29f66003aefa..eec0fbc1610b 100644
--- a/ReactAndroid/src/main/java/com/facebook/jni/JniTerminateHandler.java
+++ b/ReactAndroid/src/main/java/com/facebook/jni/JniTerminateHandler.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.jni;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/jni/ThreadScopeSupport.java b/ReactAndroid/src/main/java/com/facebook/jni/ThreadScopeSupport.java
index 89610c43798d..9490f87062c3 100644
--- a/ReactAndroid/src/main/java/com/facebook/jni/ThreadScopeSupport.java
+++ b/ReactAndroid/src/main/java/com/facebook/jni/ThreadScopeSupport.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.jni;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/EagerModuleProvider.java b/ReactAndroid/src/main/java/com/facebook/react/EagerModuleProvider.java
index 3270ca340382..9b429baa3a88 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/EagerModuleProvider.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/EagerModuleProvider.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/MemoryPressureRouter.java b/ReactAndroid/src/main/java/com/facebook/react/MemoryPressureRouter.java
index e83d53f9a588..627b962f6675 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/MemoryPressureRouter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/MemoryPressureRouter.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/NativeModuleRegistryBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/NativeModuleRegistryBuilder.java
index cabe52043d83..fe0a2624ac00 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/NativeModuleRegistryBuilder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/NativeModuleRegistryBuilder.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactActivityDelegate.java b/ReactAndroid/src/main/java/com/facebook/react/ReactActivityDelegate.java
index 03141fb00b07..c0691c748db5 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactActivityDelegate.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactActivityDelegate.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
index 0b6454086ace..9c48a2338f6d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactPackageLogger.java b/ReactAndroid/src/main/java/com/facebook/react/ReactPackageLogger.java
index 50a4c05e99f8..eba45f3be229 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactPackageLogger.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactPackageLogger.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ActivityEventListener.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ActivityEventListener.java
index 834b2267eb2f..6642260e68b3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ActivityEventListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ActivityEventListener.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/BaseActivityEventListener.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/BaseActivityEventListener.java
index a855e21bb440..2e9b492e1d59 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/BaseActivityEventListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/BaseActivityEventListener.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxCallbackImpl.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxCallbackImpl.java
index bb774a6afe28..8d33451f4268 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxCallbackImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxCallbackImpl.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxModuleWrapper.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxModuleWrapper.java
index 3b14ec4423b1..b270579443a3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxModuleWrapper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxModuleWrapper.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxModuleWrapperBase.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxModuleWrapperBase.java
index d10cbb0aa412..6b3a9346cf0c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxModuleWrapperBase.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/CxxModuleWrapperBase.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/GuardedResultAsyncTask.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/GuardedResultAsyncTask.java
index db13a71464e4..0145c26dfc2a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/GuardedResultAsyncTask.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/GuardedResultAsyncTask.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/GuardedRunnable.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/GuardedRunnable.java
index 82c4d86ea8e1..e69bc052e5f6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/GuardedRunnable.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/GuardedRunnable.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/Inspector.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/Inspector.java
index 9aebad6c7182..8cac13506402 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/Inspector.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/Inspector.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JavaScriptContextHolder.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JavaScriptContextHolder.java
index edc3f2421936..fdf5fc8f6c67 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JavaScriptContextHolder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JavaScriptContextHolder.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/MemoryPressure.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/MemoryPressure.java
index 7412204e678b..f0cd074795c9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/MemoryPressure.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/MemoryPressure.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/MemoryPressureListener.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/MemoryPressureListener.java
index 41c45d217532..35e014d59297 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/MemoryPressureListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/MemoryPressureListener.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ModuleHolder.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ModuleHolder.java
index 25259afaf966..e438d06c49d6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ModuleHolder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ModuleHolder.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactMarker.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactMarker.java
index 2ac299ea2906..efc480dc47c1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactMarker.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactMarker.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactMarkerConstants.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactMarkerConstants.java
index 6a818d22e9ed..c3dffabbaa7a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactMarkerConstants.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactMarkerConstants.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/Systrace.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/Systrace.java
index 9f571e8651fa..cd5c4615a5b8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/Systrace.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/Systrace.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.bridge;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/common/ClearableSynchronizedPool.java b/ReactAndroid/src/main/java/com/facebook/react/common/ClearableSynchronizedPool.java
index 783b2035aeab..5d12c9f16d40 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/common/ClearableSynchronizedPool.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/common/ClearableSynchronizedPool.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.common;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/InspectorPackagerConnection.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/InspectorPackagerConnection.java
index 8df47d9d3a07..45b7897f8c03 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/InspectorPackagerConnection.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/InspectorPackagerConnection.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.devsupport;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/JSDevSupport.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/JSDevSupport.java
index 4e306ba1035d..4a84be20254a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/JSDevSupport.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/JSDevSupport.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.devsupport;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/jstasks/HeadlessJsTaskConfig.java b/ReactAndroid/src/main/java/com/facebook/react/jstasks/HeadlessJsTaskConfig.java
index 747d0132eac4..5a9136fb908c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/jstasks/HeadlessJsTaskConfig.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/jstasks/HeadlessJsTaskConfig.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.jstasks;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/jstasks/HeadlessJsTaskContext.java b/ReactAndroid/src/main/java/com/facebook/react/jstasks/HeadlessJsTaskContext.java
index ea092e6de813..86196f0db997 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/jstasks/HeadlessJsTaskContext.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/jstasks/HeadlessJsTaskContext.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.jstasks;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/module/annotations/ReactModuleList.java b/ReactAndroid/src/main/java/com/facebook/react/module/annotations/ReactModuleList.java
index fc47945ac9be..a2b13a407018 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/module/annotations/ReactModuleList.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/module/annotations/ReactModuleList.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.module.annotations;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/module/model/ReactModuleInfo.java b/ReactAndroid/src/main/java/com/facebook/react/module/model/ReactModuleInfo.java
index 2b0b324728f7..b980df1f4600 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/module/model/ReactModuleInfo.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/module/model/ReactModuleInfo.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.module.model;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/module/model/ReactModuleInfoProvider.java b/ReactAndroid/src/main/java/com/facebook/react/module/model/ReactModuleInfoProvider.java
index 8c30f955e759..24d2c80aff11 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/module/model/ReactModuleInfoProvider.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/module/model/ReactModuleInfoProvider.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.module.model;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/module/processing/ReactModuleSpecProcessor.java b/ReactAndroid/src/main/java/com/facebook/react/module/processing/ReactModuleSpecProcessor.java
index 31128454268c..9f269ef6ebf0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/module/processing/ReactModuleSpecProcessor.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/module/processing/ReactModuleSpecProcessor.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.module.processing;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/accessibilityinfo/AccessibilityInfoModule.java b/ReactAndroid/src/main/java/com/facebook/react/modules/accessibilityinfo/AccessibilityInfoModule.java
index 257cb0d51674..e4e2b4eadf09 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/accessibilityinfo/AccessibilityInfoModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/accessibilityinfo/AccessibilityInfoModule.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.modules.accessibilityinfo;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/fresco/SystraceRequestListener.java b/ReactAndroid/src/main/java/com/facebook/react/modules/fresco/SystraceRequestListener.java
index 253a361f658e..6cdcb5d7545d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/fresco/SystraceRequestListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/fresco/SystraceRequestListener.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.modules.fresco;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/network/ForwardingCookieHandler.java b/ReactAndroid/src/main/java/com/facebook/react/modules/network/ForwardingCookieHandler.java
index d24540ceaa4d..65a33066741a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/network/ForwardingCookieHandler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/network/ForwardingCookieHandler.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.modules.network;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/network/ProgressResponseBody.java b/ReactAndroid/src/main/java/com/facebook/react/modules/network/ProgressResponseBody.java
index 4ec808caa07d..66c439820ddd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/network/ProgressResponseBody.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/network/ProgressResponseBody.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.modules.network;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/AndroidInfoHelpers.java b/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/AndroidInfoHelpers.java
index bbe0c07695d0..da1e3fad8946 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/AndroidInfoHelpers.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/AndroidInfoHelpers.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.modules.systeminfo;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/processing/ReactPropertyProcessor.java b/ReactAndroid/src/main/java/com/facebook/react/processing/ReactPropertyProcessor.java
index a78daa34bb8b..9b9b94607c81 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/processing/ReactPropertyProcessor.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/processing/ReactPropertyProcessor.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.processing;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
index f1d1413d0792..0fb71f1aa1a6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
index c9d8de0eaef7..2bbe858f014a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/LayoutShadowNode.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactRootViewTagGenerator.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactRootViewTagGenerator.java
index 6483d3490ca2..47d1daa54a06 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactRootViewTagGenerator.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactRootViewTagGenerator.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactZIndexedViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactZIndexedViewGroup.java
index 1e7725badc47..a170ed75fb90 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactZIndexedViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactZIndexedViewGroup.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewManagerPropertyUpdater.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewManagerPropertyUpdater.java
index 47d9ecf1cd07..b64606acd4d8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewManagerPropertyUpdater.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewManagerPropertyUpdater.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewManagersPropertyCache.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewManagersPropertyCache.java
index 9a3a798ea5d6..2c4098b0d71a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewManagersPropertyCache.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewManagersPropertyCache.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/YogaNodePool.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/YogaNodePool.java
index ac6f5b380b3b..e4c259197ff2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/YogaNodePool.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/YogaNodePool.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactProp.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactProp.java
index f5bfacdf8ad8..15ac3306534a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactProp.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactProp.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.annotations;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactPropGroup.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactPropGroup.java
index fa9e0d9948ea..ff1689840bac 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactPropGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactPropGroup.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.annotations;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactPropertyHolder.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactPropertyHolder.java
index f676e7e0c69c..cfe591a9dc53 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactPropertyHolder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/annotations/ReactPropertyHolder.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.annotations;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/MeasureSpecProvider.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/MeasureSpecProvider.java
index 7cc657470d1b..69fef4693d2e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/MeasureSpecProvider.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/common/MeasureSpecProvider.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.common;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ContentSizeChangeEvent.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ContentSizeChangeEvent.java
index 03cc05a25c19..2b7600f00a98 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ContentSizeChangeEvent.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ContentSizeChangeEvent.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.events;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcherListener.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcherListener.java
index a3e3298eef59..acf018bec5d7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcherListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcherListener.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.events;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
index 67e7f19d2c3f..499057316069 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AbstractLayoutAnimation.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AnimatedPropertyType.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AnimatedPropertyType.java
index b979799747ca..78e6a2b01fc0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AnimatedPropertyType.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/AnimatedPropertyType.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/BaseLayoutAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/BaseLayoutAnimation.java
index be06aedbc195..32c2c48fd7f6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/BaseLayoutAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/BaseLayoutAnimation.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/InterpolatorType.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/InterpolatorType.java
index f59675a8fbe1..2f4d54b16d7d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/InterpolatorType.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/InterpolatorType.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationController.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationController.java
index 7c88514f9003..62568dcc4fbb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationController.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationController.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationListener.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationListener.java
index 7edd4251d4cb..be181bbc55cc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationListener.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationType.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationType.java
index a21c0d49cd13..23f325226f57 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationType.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutAnimationType.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutCreateAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutCreateAnimation.java
index a989e625c675..07040597f6f4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutCreateAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutCreateAnimation.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutDeleteAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutDeleteAnimation.java
index f2c3ccb2c2e3..5d507c3dedb9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutDeleteAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutDeleteAnimation.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutHandlingAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutHandlingAnimation.java
index 69234e27029a..53a8863059e8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutHandlingAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutHandlingAnimation.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutUpdateAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutUpdateAnimation.java
index 8189716f729d..0c8477270c78 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutUpdateAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/LayoutUpdateAnimation.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/OpacityAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/OpacityAnimation.java
index 033b6a4ae15f..71d5aa7b5d9b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/OpacityAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/OpacityAnimation.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/PositionAndSizeAnimation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/PositionAndSizeAnimation.java
index 9bce9f781627..1f742f2a0126 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/PositionAndSizeAnimation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/PositionAndSizeAnimation.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/SimpleSpringInterpolator.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/SimpleSpringInterpolator.java
index 7ca2de98a060..4340625b5b48 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/SimpleSpringInterpolator.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/layoutanimation/SimpleSpringInterpolator.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.layoutanimation;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/ReactFindViewUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/ReactFindViewUtil.java
index cd3104ae3726..c1e10388223f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/ReactFindViewUtil.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/util/ReactFindViewUtil.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.uimanager.util;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTGroupViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTGroupViewManager.java
index 06f46bf00e4a..c164ebda5c12 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTGroupViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTGroupViewManager.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.art;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTShapeViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTShapeViewManager.java
index a6343046d23d..5c2c8a938a6b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTShapeViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTShapeViewManager.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.art;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTTextViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTTextViewManager.java
index 44d6245df922..a697c31ae6fc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTTextViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/art/ARTTextViewManager.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.art;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/common/ViewHelper.java b/ReactAndroid/src/main/java/com/facebook/react/views/common/ViewHelper.java
index a560cafcb88c..0c5bf42e1bed 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/common/ViewHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/common/ViewHelper.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.common;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/GlobalImageLoadListener.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/GlobalImageLoadListener.java
index f8df20157317..842bb60da66b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/GlobalImageLoadListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/GlobalImageLoadListener.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.image;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ModalHostHelper.java b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ModalHostHelper.java
index d63643266db4..cecde6218046 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/modal/ModalHostHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/modal/ModalHostHelper.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.modal;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarContainerView.java b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarContainerView.java
index 9e29777d243d..e1d8f6fe0b58 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarContainerView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/progressbar/ProgressBarContainerView.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.progressbar;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java
index 9dc4a2821c1c..bcda656077c6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.scroll;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerViewManager.java
index f84f72aa5dfc..284f41451f5f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerViewManager.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.scroll;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactVirtualTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactVirtualTextShadowNode.java
index 59ae82cc7102..cfd6009b0708 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactVirtualTextShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactVirtualTextShadowNode.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.text;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/MeasureUtil.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/MeasureUtil.java
index 338428f0e73c..6f764282e7e1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/MeasureUtil.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/MeasureUtil.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.view;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundManager.java
index 0248b93c61a0..95fe29f7970b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewBackgroundManager.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.react.views.view;
 
diff --git a/ReactAndroid/src/main/java/com/facebook/systrace/TraceListener.java b/ReactAndroid/src/main/java/com/facebook/systrace/TraceListener.java
index d9f650d2dc80..27fe3441b5ed 100644
--- a/ReactAndroid/src/main/java/com/facebook/systrace/TraceListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/systrace/TraceListener.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 package com.facebook.systrace;
 
diff --git a/ReactAndroid/src/main/jni/first-party/fb/include/fb/Build.h b/ReactAndroid/src/main/jni/first-party/fb/include/fb/Build.h
index 98ad557467df..394f9d6e1346 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/include/fb/Build.h
+++ b/ReactAndroid/src/main/jni/first-party/fb/include/fb/Build.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/JWeakReference.h b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/JWeakReference.h
index aca55f2034a6..941bc3b0d428 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/JWeakReference.h
+++ b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/JWeakReference.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/MetaConvert.h b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/MetaConvert.h
index 69d1babb5fc7..7750304bd656 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/MetaConvert.h
+++ b/ReactAndroid/src/main/jni/first-party/fb/include/fb/fbjni/MetaConvert.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/first-party/fb/include/fb/lyra.h b/ReactAndroid/src/main/jni/first-party/fb/include/fb/lyra.h
index c60ff27b6152..38bca5ef7f8e 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/include/fb/lyra.h
+++ b/ReactAndroid/src/main/jni/first-party/fb/include/fb/lyra.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/first-party/fb/jni/android/CpuCapabilities.cpp b/ReactAndroid/src/main/jni/first-party/fb/jni/android/CpuCapabilities.cpp
index f16fbeef6d93..18974660f699 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/jni/android/CpuCapabilities.cpp
+++ b/ReactAndroid/src/main/jni/first-party/fb/jni/android/CpuCapabilities.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <fb/CpuCapabilities.h>
 #include <cpu-features.h>
diff --git a/ReactAndroid/src/main/jni/first-party/fb/lyra/lyra.cpp b/ReactAndroid/src/main/jni/first-party/fb/lyra/lyra.cpp
index f915ecef29d6..4e1f2e9240aa 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/lyra/lyra.cpp
+++ b/ReactAndroid/src/main/jni/first-party/fb/lyra/lyra.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <fb/lyra.h>
 
diff --git a/ReactAndroid/src/main/jni/first-party/fbgloginit/fb/glog_init.h b/ReactAndroid/src/main/jni/first-party/fbgloginit/fb/glog_init.h
index 311f703500ae..18d591ee49ae 100644
--- a/ReactAndroid/src/main/jni/first-party/fbgloginit/fb/glog_init.h
+++ b/ReactAndroid/src/main/jni/first-party/fbgloginit/fb/glog_init.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/first-party/fbgloginit/glog_init.cpp b/ReactAndroid/src/main/jni/first-party/fbgloginit/glog_init.cpp
index e9688372c692..614cc881d7a9 100644
--- a/ReactAndroid/src/main/jni/first-party/fbgloginit/glog_init.cpp
+++ b/ReactAndroid/src/main/jni/first-party/fbgloginit/glog_init.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "fb/glog_init.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
index 20da272c727a..7b20f4caab32 100644
--- a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <cxxreact/JSCExecutor.h>
 
diff --git a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
index 8ad7a34df84b..0e6a34b96e28 100644
--- a/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
+++ b/ReactAndroid/src/main/jni/react/jni/AndroidJSCFactory.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
index 0c5cf5c8f68e..10a3fb826823 100644
--- a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "CatalystInstanceImpl.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h
index 622edb769d0f..fcd7aef70209 100644
--- a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h
+++ b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <string>
 
diff --git a/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.cpp b/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.cpp
index 8f0ec406449b..b9205cc6ae5f 100644
--- a/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "CxxModuleWrapper.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.h b/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.h
index 74d51563fae9..0055965c6cb4 100644
--- a/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.h
+++ b/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapper.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapperBase.h b/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapperBase.h
index c184464f162a..128135453595 100644
--- a/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapperBase.h
+++ b/ReactAndroid/src/main/jni/react/jni/CxxModuleWrapperBase.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/CxxSharedModuleWrapper.h b/ReactAndroid/src/main/jni/react/jni/CxxSharedModuleWrapper.h
index 81ca0a200193..53f8b653c2d4 100644
--- a/ReactAndroid/src/main/jni/react/jni/CxxSharedModuleWrapper.h
+++ b/ReactAndroid/src/main/jni/react/jni/CxxSharedModuleWrapper.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JCallback.h b/ReactAndroid/src/main/jni/react/jni/JCallback.h
index b4b68d1f8479..00502ab56b0b 100644
--- a/ReactAndroid/src/main/jni/react/jni/JCallback.h
+++ b/ReactAndroid/src/main/jni/react/jni/JCallback.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JInspector.cpp b/ReactAndroid/src/main/jni/react/jni/JInspector.cpp
index 1d326e3e7337..0f1b5593ad2c 100644
--- a/ReactAndroid/src/main/jni/react/jni/JInspector.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JInspector.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JInspector.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JInspector.h b/ReactAndroid/src/main/jni/react/jni/JInspector.h
index 9e089687eb87..a199989c998d 100644
--- a/ReactAndroid/src/main/jni/react/jni/JInspector.h
+++ b/ReactAndroid/src/main/jni/react/jni/JInspector.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.cpp b/ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.cpp
index b881b6115943..614f2fc95f8a 100644
--- a/ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JMessageQueueThread.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.h b/ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.h
index 944854ea82fa..604429671c0b 100644
--- a/ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.h
+++ b/ReactAndroid/src/main/jni/react/jni/JMessageQueueThread.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JNativeRunnable.h b/ReactAndroid/src/main/jni/react/jni/JNativeRunnable.h
index 5550af34299b..53a973e85a61 100644
--- a/ReactAndroid/src/main/jni/react/jni/JNativeRunnable.h
+++ b/ReactAndroid/src/main/jni/react/jni/JNativeRunnable.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JReactMarker.cpp b/ReactAndroid/src/main/jni/react/jni/JReactMarker.cpp
index e210aedca7fb..ead1c689d121 100644
--- a/ReactAndroid/src/main/jni/react/jni/JReactMarker.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JReactMarker.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JReactMarker.h"
 #include <mutex>
diff --git a/ReactAndroid/src/main/jni/react/jni/JReactMarker.h b/ReactAndroid/src/main/jni/react/jni/JReactMarker.h
index 6a46d083c40e..f9e6d27d1685 100644
--- a/ReactAndroid/src/main/jni/react/jni/JReactMarker.h
+++ b/ReactAndroid/src/main/jni/react/jni/JReactMarker.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp b/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp
index d2c9973ecb9e..ea9c7285ec80 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCPerfLogging.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.h b/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.h
index 241e716b8fbd..43805243af2c 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.h
+++ b/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JSLoader.cpp b/ReactAndroid/src/main/jni/react/jni/JSLoader.cpp
index 187f96fb791a..2f435dfda932 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSLoader.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JSLoader.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSLoader.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JSLoader.h b/ReactAndroid/src/main/jni/react/jni/JSLoader.h
index d6ea1fbe6d55..543534a9707b 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSLoader.h
+++ b/ReactAndroid/src/main/jni/react/jni/JSLoader.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp b/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
index 02cd21ddd755..bb3762bf06c1 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JSLogging.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSLogging.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JSLogging.h b/ReactAndroid/src/main/jni/react/jni/JSLogging.h
index aaf5718ccf15..173b4745ccd5 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSLogging.h
+++ b/ReactAndroid/src/main/jni/react/jni/JSLogging.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.cpp b/ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.cpp
index 9f667f23aa90..4d7e52e4945c 100644
--- a/ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JavaModuleWrapper.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.h b/ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.h
index 6bc4f6b75692..cdd081b69d4f 100644
--- a/ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.h
+++ b/ReactAndroid/src/main/jni/react/jni/JavaModuleWrapper.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JavaScriptExecutorHolder.h b/ReactAndroid/src/main/jni/react/jni/JavaScriptExecutorHolder.h
index b23cc9e370df..7f7141716ede 100644
--- a/ReactAndroid/src/main/jni/react/jni/JavaScriptExecutorHolder.h
+++ b/ReactAndroid/src/main/jni/react/jni/JavaScriptExecutorHolder.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <memory>
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.cpp b/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.cpp
index 504f937c0cf2..643ef80d2f61 100644
--- a/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JniJSModulesUnbundle.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.h b/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.h
index 8ca93b3ed88f..17fcd2d6742e 100644
--- a/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.h
+++ b/ReactAndroid/src/main/jni/react/jni/JniJSModulesUnbundle.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/MethodInvoker.cpp b/ReactAndroid/src/main/jni/react/jni/MethodInvoker.cpp
index deb289714ce7..4abba9308cf7 100644
--- a/ReactAndroid/src/main/jni/react/jni/MethodInvoker.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/MethodInvoker.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "MethodInvoker.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/MethodInvoker.h b/ReactAndroid/src/main/jni/react/jni/MethodInvoker.h
index 288c0b875c29..e86ebe1be77d 100644
--- a/ReactAndroid/src/main/jni/react/jni/MethodInvoker.h
+++ b/ReactAndroid/src/main/jni/react/jni/MethodInvoker.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/ModuleRegistryBuilder.cpp b/ReactAndroid/src/main/jni/react/jni/ModuleRegistryBuilder.cpp
index eb204dd3ee91..e902f6037292 100644
--- a/ReactAndroid/src/main/jni/react/jni/ModuleRegistryBuilder.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/ModuleRegistryBuilder.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "ModuleRegistryBuilder.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/ModuleRegistryBuilder.h b/ReactAndroid/src/main/jni/react/jni/ModuleRegistryBuilder.h
index 3a8cc09258e0..b179c5ba44e3 100644
--- a/ReactAndroid/src/main/jni/react/jni/ModuleRegistryBuilder.h
+++ b/ReactAndroid/src/main/jni/react/jni/ModuleRegistryBuilder.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <string>
 
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeArray.cpp b/ReactAndroid/src/main/jni/react/jni/NativeArray.cpp
index 09026055bf42..2c6bc8f1d56b 100644
--- a/ReactAndroid/src/main/jni/react/jni/NativeArray.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/NativeArray.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "NativeArray.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeArray.h b/ReactAndroid/src/main/jni/react/jni/NativeArray.h
index 3b48928356b5..54efd849ec0a 100644
--- a/ReactAndroid/src/main/jni/react/jni/NativeArray.h
+++ b/ReactAndroid/src/main/jni/react/jni/NativeArray.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeCommon.cpp b/ReactAndroid/src/main/jni/react/jni/NativeCommon.cpp
index 633792a7d2e5..fd46ea949ee5 100644
--- a/ReactAndroid/src/main/jni/react/jni/NativeCommon.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/NativeCommon.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "NativeCommon.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeCommon.h b/ReactAndroid/src/main/jni/react/jni/NativeCommon.h
index 1f4a926fd18b..738edb097547 100644
--- a/ReactAndroid/src/main/jni/react/jni/NativeCommon.h
+++ b/ReactAndroid/src/main/jni/react/jni/NativeCommon.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp b/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp
index 2c35306caf84..cb7d10fafda4 100644
--- a/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "NativeDeltaClient.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h b/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h
index 5e2eea14ae22..957465d7fdb1 100644
--- a/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h
+++ b/ReactAndroid/src/main/jni/react/jni/NativeDeltaClient.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeMap.cpp b/ReactAndroid/src/main/jni/react/jni/NativeMap.cpp
index ebc7fa88bdb7..c8c948cd440e 100644
--- a/ReactAndroid/src/main/jni/react/jni/NativeMap.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/NativeMap.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "NativeMap.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/NativeMap.h b/ReactAndroid/src/main/jni/react/jni/NativeMap.h
index 3baf03242a44..7089b6d9fbe5 100644
--- a/ReactAndroid/src/main/jni/react/jni/NativeMap.h
+++ b/ReactAndroid/src/main/jni/react/jni/NativeMap.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp b/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
index 662c8bdf2c52..75f1300f921f 100644
--- a/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/OnLoad.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <string>
 
diff --git a/ReactAndroid/src/main/jni/react/jni/OnLoad.h b/ReactAndroid/src/main/jni/react/jni/OnLoad.h
index 9da83c447b96..18682b925604 100644
--- a/ReactAndroid/src/main/jni/react/jni/OnLoad.h
+++ b/ReactAndroid/src/main/jni/react/jni/OnLoad.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/ProxyExecutor.cpp b/ReactAndroid/src/main/jni/react/jni/ProxyExecutor.cpp
index 1b9395ceae4c..1a030f5d4d24 100644
--- a/ReactAndroid/src/main/jni/react/jni/ProxyExecutor.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/ProxyExecutor.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "ProxyExecutor.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/ProxyExecutor.h b/ReactAndroid/src/main/jni/react/jni/ProxyExecutor.h
index b77d35f63745..5e1b1b786876 100644
--- a/ReactAndroid/src/main/jni/react/jni/ProxyExecutor.h
+++ b/ReactAndroid/src/main/jni/react/jni/ProxyExecutor.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/ReadableNativeArray.cpp b/ReactAndroid/src/main/jni/react/jni/ReadableNativeArray.cpp
index 2ea8742fae5a..008738f6af2a 100644
--- a/ReactAndroid/src/main/jni/react/jni/ReadableNativeArray.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/ReadableNativeArray.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "ReadableNativeArray.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.cpp b/ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.cpp
index 1a7aa3d8af56..5c91620ac550 100644
--- a/ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "ReadableNativeMap.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.h b/ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.h
index de06d69753ab..7258adaaeace 100644
--- a/ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.h
+++ b/ReactAndroid/src/main/jni/react/jni/ReadableNativeMap.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/WritableNativeArray.cpp b/ReactAndroid/src/main/jni/react/jni/WritableNativeArray.cpp
index 77de9ff22037..20510758b8a4 100644
--- a/ReactAndroid/src/main/jni/react/jni/WritableNativeArray.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/WritableNativeArray.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "WritableNativeArray.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/WritableNativeArray.h b/ReactAndroid/src/main/jni/react/jni/WritableNativeArray.h
index e47769517f00..23dea3eb9fe4 100644
--- a/ReactAndroid/src/main/jni/react/jni/WritableNativeArray.h
+++ b/ReactAndroid/src/main/jni/react/jni/WritableNativeArray.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/jni/WritableNativeMap.cpp b/ReactAndroid/src/main/jni/react/jni/WritableNativeMap.cpp
index 3460f5810478..f33dcd131796 100644
--- a/ReactAndroid/src/main/jni/react/jni/WritableNativeMap.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/WritableNativeMap.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "WritableNativeMap.h"
 
diff --git a/ReactAndroid/src/main/jni/react/jni/WritableNativeMap.h b/ReactAndroid/src/main/jni/react/jni/WritableNativeMap.h
index d577f0dffbdd..3373350266e6 100644
--- a/ReactAndroid/src/main/jni/react/jni/WritableNativeMap.h
+++ b/ReactAndroid/src/main/jni/react/jni/WritableNativeMap.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactAndroid/src/main/jni/react/perftests/OnLoad.cpp b/ReactAndroid/src/main/jni/react/perftests/OnLoad.cpp
index 89610b203be0..b4d5f7d028b3 100644
--- a/ReactAndroid/src/main/jni/react/perftests/OnLoad.cpp
+++ b/ReactAndroid/src/main/jni/react/perftests/OnLoad.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <fb/log.h>
 #include <fb/fbjni.h>
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
index d5f2104087f8..a696d21e4def 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 package com.facebook.react.fabric;
 
 import static org.fest.assertions.api.Assertions.assertThat;
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 8d70d85f6470..9b1c95db67be 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 package com.facebook.react.fabric;
 
 import static org.fest.assertions.api.Assertions.assertThat;
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
index 7148da735640..68881c7f4453 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/ReactShadowNodeTest.java
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 package com.facebook.react.fabric;
 
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
diff --git a/ReactCommon/cxxreact/CxxModule.h b/ReactCommon/cxxreact/CxxModule.h
index 73587a4e5c3d..f31b20642590 100644
--- a/ReactCommon/cxxreact/CxxModule.h
+++ b/ReactCommon/cxxreact/CxxModule.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/CxxNativeModule.cpp b/ReactCommon/cxxreact/CxxNativeModule.cpp
index 4b71e3bef2e0..757098e535e2 100644
--- a/ReactCommon/cxxreact/CxxNativeModule.cpp
+++ b/ReactCommon/cxxreact/CxxNativeModule.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "CxxNativeModule.h"
 #include "Instance.h"
diff --git a/ReactCommon/cxxreact/CxxNativeModule.h b/ReactCommon/cxxreact/CxxNativeModule.h
index 9d60ee17df8c..b02dec1ce5de 100644
--- a/ReactCommon/cxxreact/CxxNativeModule.h
+++ b/ReactCommon/cxxreact/CxxNativeModule.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/Instance.cpp b/ReactCommon/cxxreact/Instance.cpp
index 534f4b981cd8..cc951813e716 100644
--- a/ReactCommon/cxxreact/Instance.cpp
+++ b/ReactCommon/cxxreact/Instance.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "Instance.h"
 
diff --git a/ReactCommon/cxxreact/Instance.h b/ReactCommon/cxxreact/Instance.h
index dffbe72465dd..95f4b905a60b 100644
--- a/ReactCommon/cxxreact/Instance.h
+++ b/ReactCommon/cxxreact/Instance.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSBigString.cpp b/ReactCommon/cxxreact/JSBigString.cpp
index 2bd444800405..dda34f084c20 100644
--- a/ReactCommon/cxxreact/JSBigString.cpp
+++ b/ReactCommon/cxxreact/JSBigString.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSBigString.h"
 
diff --git a/ReactCommon/cxxreact/JSBigString.h b/ReactCommon/cxxreact/JSBigString.h
index 6f9667e3f6f8..bac6fc03774c 100644
--- a/ReactCommon/cxxreact/JSBigString.h
+++ b/ReactCommon/cxxreact/JSBigString.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSBundleType.cpp b/ReactCommon/cxxreact/JSBundleType.cpp
index 72c60ebf6563..f74fa7d46fca 100644
--- a/ReactCommon/cxxreact/JSBundleType.cpp
+++ b/ReactCommon/cxxreact/JSBundleType.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSBundleType.h"
 
diff --git a/ReactCommon/cxxreact/JSBundleType.h b/ReactCommon/cxxreact/JSBundleType.h
index 3e8627f9300e..b6ed106ce2d1 100644
--- a/ReactCommon/cxxreact/JSBundleType.h
+++ b/ReactCommon/cxxreact/JSBundleType.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSCExecutor.cpp b/ReactCommon/cxxreact/JSCExecutor.cpp
index 3c66fb39edc2..65ee3bdd8025 100644
--- a/ReactCommon/cxxreact/JSCExecutor.cpp
+++ b/ReactCommon/cxxreact/JSCExecutor.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCExecutor.h"
 
diff --git a/ReactCommon/cxxreact/JSCExecutor.h b/ReactCommon/cxxreact/JSCExecutor.h
index 151ded934015..a52842b386d7 100644
--- a/ReactCommon/cxxreact/JSCExecutor.h
+++ b/ReactCommon/cxxreact/JSCExecutor.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSCLegacyTracing.cpp b/ReactCommon/cxxreact/JSCLegacyTracing.cpp
index e2783055c4e9..64d5803fb877 100644
--- a/ReactCommon/cxxreact/JSCLegacyTracing.cpp
+++ b/ReactCommon/cxxreact/JSCLegacyTracing.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCLegacyTracing.h"
 
diff --git a/ReactCommon/cxxreact/JSCLegacyTracing.h b/ReactCommon/cxxreact/JSCLegacyTracing.h
index 2803c4302b32..e0f1b7bf5204 100644
--- a/ReactCommon/cxxreact/JSCLegacyTracing.h
+++ b/ReactCommon/cxxreact/JSCLegacyTracing.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSCMemory.cpp b/ReactCommon/cxxreact/JSCMemory.cpp
index 976c98114a5e..38a4590850a9 100644
--- a/ReactCommon/cxxreact/JSCMemory.cpp
+++ b/ReactCommon/cxxreact/JSCMemory.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCMemory.h"
 
diff --git a/ReactCommon/cxxreact/JSCMemory.h b/ReactCommon/cxxreact/JSCMemory.h
index 899bba82b09b..d8e797aab2d4 100644
--- a/ReactCommon/cxxreact/JSCMemory.h
+++ b/ReactCommon/cxxreact/JSCMemory.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSCNativeModules.cpp b/ReactCommon/cxxreact/JSCNativeModules.cpp
index 1a440086c486..50d199a25ef6 100644
--- a/ReactCommon/cxxreact/JSCNativeModules.cpp
+++ b/ReactCommon/cxxreact/JSCNativeModules.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCNativeModules.h"
 
diff --git a/ReactCommon/cxxreact/JSCNativeModules.h b/ReactCommon/cxxreact/JSCNativeModules.h
index e81e98d2a795..40f0fd69f552 100644
--- a/ReactCommon/cxxreact/JSCNativeModules.h
+++ b/ReactCommon/cxxreact/JSCNativeModules.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSCPerfStats.cpp b/ReactCommon/cxxreact/JSCPerfStats.cpp
index f1f487569f7d..0373d6ad5e80 100644
--- a/ReactCommon/cxxreact/JSCPerfStats.cpp
+++ b/ReactCommon/cxxreact/JSCPerfStats.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCPerfStats.h"
 
diff --git a/ReactCommon/cxxreact/JSCPerfStats.h b/ReactCommon/cxxreact/JSCPerfStats.h
index 9dab4b9c2a67..1ecf70bf14bc 100644
--- a/ReactCommon/cxxreact/JSCPerfStats.h
+++ b/ReactCommon/cxxreact/JSCPerfStats.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSCSamplingProfiler.cpp b/ReactCommon/cxxreact/JSCSamplingProfiler.cpp
index 813a19c68657..425e4e69e1ab 100644
--- a/ReactCommon/cxxreact/JSCSamplingProfiler.cpp
+++ b/ReactCommon/cxxreact/JSCSamplingProfiler.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCSamplingProfiler.h"
 
diff --git a/ReactCommon/cxxreact/JSCSamplingProfiler.h b/ReactCommon/cxxreact/JSCSamplingProfiler.h
index bed56cbc2ec0..b252db61f57e 100644
--- a/ReactCommon/cxxreact/JSCSamplingProfiler.h
+++ b/ReactCommon/cxxreact/JSCSamplingProfiler.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSCTracing.cpp b/ReactCommon/cxxreact/JSCTracing.cpp
index ca11a8e72109..ca870f544be8 100644
--- a/ReactCommon/cxxreact/JSCTracing.cpp
+++ b/ReactCommon/cxxreact/JSCTracing.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCTracing.h"
 
diff --git a/ReactCommon/cxxreact/JSCTracing.h b/ReactCommon/cxxreact/JSCTracing.h
index 63af9aa9d0af..0a0b1b39a756 100644
--- a/ReactCommon/cxxreact/JSCTracing.h
+++ b/ReactCommon/cxxreact/JSCTracing.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSCUtils.cpp b/ReactCommon/cxxreact/JSCUtils.cpp
index 45cc591bf76d..25e4da185407 100644
--- a/ReactCommon/cxxreact/JSCUtils.cpp
+++ b/ReactCommon/cxxreact/JSCUtils.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCUtils.h"
 
diff --git a/ReactCommon/cxxreact/JSCUtils.h b/ReactCommon/cxxreact/JSCUtils.h
index dfa1df715945..feeae32c7a93 100644
--- a/ReactCommon/cxxreact/JSCUtils.h
+++ b/ReactCommon/cxxreact/JSCUtils.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSDeltaBundleClient.h b/ReactCommon/cxxreact/JSDeltaBundleClient.h
index 107bd39880df..021ae6c622cf 100644
--- a/ReactCommon/cxxreact/JSDeltaBundleClient.h
+++ b/ReactCommon/cxxreact/JSDeltaBundleClient.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSExecutor.cpp b/ReactCommon/cxxreact/JSExecutor.cpp
index 9548f9664acb..846273ab37f7 100644
--- a/ReactCommon/cxxreact/JSExecutor.cpp
+++ b/ReactCommon/cxxreact/JSExecutor.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSExecutor.h"
 
diff --git a/ReactCommon/cxxreact/JSExecutor.h b/ReactCommon/cxxreact/JSExecutor.h
index e699c79b2266..6627304abbe6 100644
--- a/ReactCommon/cxxreact/JSExecutor.h
+++ b/ReactCommon/cxxreact/JSExecutor.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSIndexedRAMBundle.cpp b/ReactCommon/cxxreact/JSIndexedRAMBundle.cpp
index 57d2a4afeb7d..cca4ab20338f 100644
--- a/ReactCommon/cxxreact/JSIndexedRAMBundle.cpp
+++ b/ReactCommon/cxxreact/JSIndexedRAMBundle.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSIndexedRAMBundle.h"
 
diff --git a/ReactCommon/cxxreact/JSIndexedRAMBundle.h b/ReactCommon/cxxreact/JSIndexedRAMBundle.h
index 6467977279fa..e91ed076813d 100644
--- a/ReactCommon/cxxreact/JSIndexedRAMBundle.h
+++ b/ReactCommon/cxxreact/JSIndexedRAMBundle.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JSModulesUnbundle.h b/ReactCommon/cxxreact/JSModulesUnbundle.h
index 83a997f5495d..f1662776c312 100644
--- a/ReactCommon/cxxreact/JSModulesUnbundle.h
+++ b/ReactCommon/cxxreact/JSModulesUnbundle.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JsArgumentHelpers-inl.h b/ReactCommon/cxxreact/JsArgumentHelpers-inl.h
index ce8de89364b5..63ce70cf060f 100644
--- a/ReactCommon/cxxreact/JsArgumentHelpers-inl.h
+++ b/ReactCommon/cxxreact/JsArgumentHelpers-inl.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/JsArgumentHelpers.h b/ReactCommon/cxxreact/JsArgumentHelpers.h
index a66c40167117..ba6cd62af898 100644
--- a/ReactCommon/cxxreact/JsArgumentHelpers.h
+++ b/ReactCommon/cxxreact/JsArgumentHelpers.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/MessageQueueThread.h b/ReactCommon/cxxreact/MessageQueueThread.h
index 72d13749f9d1..5158646281ab 100644
--- a/ReactCommon/cxxreact/MessageQueueThread.h
+++ b/ReactCommon/cxxreact/MessageQueueThread.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/MethodCall.cpp b/ReactCommon/cxxreact/MethodCall.cpp
index c125c4bd959c..70abb4250305 100644
--- a/ReactCommon/cxxreact/MethodCall.cpp
+++ b/ReactCommon/cxxreact/MethodCall.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "MethodCall.h"
 
diff --git a/ReactCommon/cxxreact/MethodCall.h b/ReactCommon/cxxreact/MethodCall.h
index 38a288ed507e..ec6bc334e6a0 100644
--- a/ReactCommon/cxxreact/MethodCall.h
+++ b/ReactCommon/cxxreact/MethodCall.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/ModuleRegistry.cpp b/ReactCommon/cxxreact/ModuleRegistry.cpp
index 8779e7e94399..17f177469848 100644
--- a/ReactCommon/cxxreact/ModuleRegistry.cpp
+++ b/ReactCommon/cxxreact/ModuleRegistry.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "ModuleRegistry.h"
 
diff --git a/ReactCommon/cxxreact/ModuleRegistry.h b/ReactCommon/cxxreact/ModuleRegistry.h
index 8df870e88c5c..183996dc7b80 100644
--- a/ReactCommon/cxxreact/ModuleRegistry.h
+++ b/ReactCommon/cxxreact/ModuleRegistry.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/NativeModule.h b/ReactCommon/cxxreact/NativeModule.h
index afde69d8517c..a7229b24aa7d 100644
--- a/ReactCommon/cxxreact/NativeModule.h
+++ b/ReactCommon/cxxreact/NativeModule.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/NativeToJsBridge.cpp b/ReactCommon/cxxreact/NativeToJsBridge.cpp
index 3cf374f068df..32cb06b9c4fd 100644
--- a/ReactCommon/cxxreact/NativeToJsBridge.cpp
+++ b/ReactCommon/cxxreact/NativeToJsBridge.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "NativeToJsBridge.h"
 
diff --git a/ReactCommon/cxxreact/NativeToJsBridge.h b/ReactCommon/cxxreact/NativeToJsBridge.h
index 7e7aaf77ee21..0a6110f67e43 100644
--- a/ReactCommon/cxxreact/NativeToJsBridge.h
+++ b/ReactCommon/cxxreact/NativeToJsBridge.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/Platform.cpp b/ReactCommon/cxxreact/Platform.cpp
index c4aeb2e0e700..d9835ea94dd2 100644
--- a/ReactCommon/cxxreact/Platform.cpp
+++ b/ReactCommon/cxxreact/Platform.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "Platform.h"
 
diff --git a/ReactCommon/cxxreact/Platform.h b/ReactCommon/cxxreact/Platform.h
index be9c1737ec15..59f49222ceac 100644
--- a/ReactCommon/cxxreact/Platform.h
+++ b/ReactCommon/cxxreact/Platform.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/RAMBundleRegistry.cpp b/ReactCommon/cxxreact/RAMBundleRegistry.cpp
index cc61ea254540..d10308975426 100644
--- a/ReactCommon/cxxreact/RAMBundleRegistry.cpp
+++ b/ReactCommon/cxxreact/RAMBundleRegistry.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "RAMBundleRegistry.h"
 
diff --git a/ReactCommon/cxxreact/RAMBundleRegistry.h b/ReactCommon/cxxreact/RAMBundleRegistry.h
index 6314dce036ed..7670b90b53de 100644
--- a/ReactCommon/cxxreact/RAMBundleRegistry.h
+++ b/ReactCommon/cxxreact/RAMBundleRegistry.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/ReactMarker.cpp b/ReactCommon/cxxreact/ReactMarker.cpp
index f2c28c404b37..ae1a502efeb8 100644
--- a/ReactCommon/cxxreact/ReactMarker.cpp
+++ b/ReactCommon/cxxreact/ReactMarker.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "ReactMarker.h"
 
diff --git a/ReactCommon/cxxreact/ReactMarker.h b/ReactCommon/cxxreact/ReactMarker.h
index 26f84ea35e73..ae176b78867a 100644
--- a/ReactCommon/cxxreact/ReactMarker.h
+++ b/ReactCommon/cxxreact/ReactMarker.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/RecoverableError.h b/ReactCommon/cxxreact/RecoverableError.h
index d71e1c95aa0d..ab62e9a98d08 100644
--- a/ReactCommon/cxxreact/RecoverableError.h
+++ b/ReactCommon/cxxreact/RecoverableError.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/SampleCxxModule.cpp b/ReactCommon/cxxreact/SampleCxxModule.cpp
index 89b5c5279dda..358350eeaf2c 100644
--- a/ReactCommon/cxxreact/SampleCxxModule.cpp
+++ b/ReactCommon/cxxreact/SampleCxxModule.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "SampleCxxModule.h"
 #include <cxxreact/JsArgumentHelpers.h>
diff --git a/ReactCommon/cxxreact/SampleCxxModule.h b/ReactCommon/cxxreact/SampleCxxModule.h
index ded0b43613d3..6a7ba9bcec72 100644
--- a/ReactCommon/cxxreact/SampleCxxModule.h
+++ b/ReactCommon/cxxreact/SampleCxxModule.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/SharedProxyCxxModule.h b/ReactCommon/cxxreact/SharedProxyCxxModule.h
index b8c9769a6972..18a66ebccf7e 100644
--- a/ReactCommon/cxxreact/SharedProxyCxxModule.h
+++ b/ReactCommon/cxxreact/SharedProxyCxxModule.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <memory>
 
diff --git a/ReactCommon/cxxreact/SystraceSection.h b/ReactCommon/cxxreact/SystraceSection.h
index ea73046e8a46..5c5041854683 100644
--- a/ReactCommon/cxxreact/SystraceSection.h
+++ b/ReactCommon/cxxreact/SystraceSection.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/cxxreact/tests/RecoverableErrorTest.cpp b/ReactCommon/cxxreact/tests/RecoverableErrorTest.cpp
index 8b2f39f6b121..d598d8318960 100644
--- a/ReactCommon/cxxreact/tests/RecoverableErrorTest.cpp
+++ b/ReactCommon/cxxreact/tests/RecoverableErrorTest.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <gtest/gtest.h>
 
diff --git a/ReactCommon/cxxreact/tests/jsarg_helpers.cpp b/ReactCommon/cxxreact/tests/jsarg_helpers.cpp
index 8f246bc1ec58..7e23dcd26c52 100644
--- a/ReactCommon/cxxreact/tests/jsarg_helpers.cpp
+++ b/ReactCommon/cxxreact/tests/jsarg_helpers.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <cxxreact/JsArgumentHelpers.h>
 
diff --git a/ReactCommon/cxxreact/tests/jsbigstring.cpp b/ReactCommon/cxxreact/tests/jsbigstring.cpp
index 21bd22cc29ae..f0081c889b66 100644
--- a/ReactCommon/cxxreact/tests/jsbigstring.cpp
+++ b/ReactCommon/cxxreact/tests/jsbigstring.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 #include <sys/mman.h>
 #include <fcntl.h>
 
diff --git a/ReactCommon/cxxreact/tests/jscexecutor.cpp b/ReactCommon/cxxreact/tests/jscexecutor.cpp
index eb1382e8dce2..867d68cd7f9d 100644
--- a/ReactCommon/cxxreact/tests/jscexecutor.cpp
+++ b/ReactCommon/cxxreact/tests/jscexecutor.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <gtest/gtest.h>
 #include <cxxreact/JSCExecutor.h>
diff --git a/ReactCommon/cxxreact/tests/jsclogging.cpp b/ReactCommon/cxxreact/tests/jsclogging.cpp
index ca325b44212f..5f4fb0a66ad3 100644
--- a/ReactCommon/cxxreact/tests/jsclogging.cpp
+++ b/ReactCommon/cxxreact/tests/jsclogging.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <gtest/gtest.h>
 #include <cxxreact/JSCExecutor.h>
diff --git a/ReactCommon/cxxreact/tests/methodcall.cpp b/ReactCommon/cxxreact/tests/methodcall.cpp
index fdd1f9a08e01..395a81b4984e 100644
--- a/ReactCommon/cxxreact/tests/methodcall.cpp
+++ b/ReactCommon/cxxreact/tests/methodcall.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <cxxreact/MethodCall.h>
 
diff --git a/ReactCommon/cxxreact/tests/value.cpp b/ReactCommon/cxxreact/tests/value.cpp
index 4ce30f94bc61..f7c4b6fd2771 100644
--- a/ReactCommon/cxxreact/tests/value.cpp
+++ b/ReactCommon/cxxreact/tests/value.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 #include <string>
 #include <gtest/gtest.h>
 #include <folly/json.h>
diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index ec5de4100194..9c198c4be447 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
index 298e6c999c52..a41c4311a6bd 100644
--- a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "ComponentDescriptorRegistry.h"
 
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
index 57d03d5242cc..4fec41dff1ea 100644
--- a/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorRegistry.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/fabric/uimanager/Differentiator.cpp b/ReactCommon/fabric/uimanager/Differentiator.cpp
index a689d51d9db6..b180587eed88 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.cpp
+++ b/ReactCommon/fabric/uimanager/Differentiator.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "Differentiator.h"
 
diff --git a/ReactCommon/fabric/uimanager/Differentiator.h b/ReactCommon/fabric/uimanager/Differentiator.h
index c1d7a8b1d4e8..fe2caf5e913b 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.h
+++ b/ReactCommon/fabric/uimanager/Differentiator.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index 0183c3a5987a..d20e1f1b0a80 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "Scheduler.h"
 
@@ -75,7 +78,7 @@ void Scheduler::shadowTreeDidCommit(const SharedShadowTree &shadowTree, const Tr
 }
 
 #pragma mark - UIManagerDelegate
-  
+
 void Scheduler::uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNodeUnsharedList &rootChildNodes) {
   auto &&iterator = shadowTreeRegistry_.find(rootTag);
   auto &&shadowTree = iterator->second;
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index 5ccd8cbb3a3c..b63fbf666e2b 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/fabric/uimanager/SchedulerDelegate.h b/ReactCommon/fabric/uimanager/SchedulerDelegate.h
index 3f2d9bf5fd24..a6e98dae6cb4 100644
--- a/ReactCommon/fabric/uimanager/SchedulerDelegate.h
+++ b/ReactCommon/fabric/uimanager/SchedulerDelegate.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 4422b43c0c70..06e259f86d08 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "ShadowTree.h"
 
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.h b/ReactCommon/fabric/uimanager/ShadowTree.h
index cc20d697d689..d056e4b56224 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.h
+++ b/ReactCommon/fabric/uimanager/ShadowTree.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/fabric/uimanager/ShadowTreeDelegate.h b/ReactCommon/fabric/uimanager/ShadowTreeDelegate.h
index 59ca85f46be5..f2da57031b04 100644
--- a/ReactCommon/fabric/uimanager/ShadowTreeDelegate.h
+++ b/ReactCommon/fabric/uimanager/ShadowTreeDelegate.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/jschelpers/JSCHelpers.cpp b/ReactCommon/jschelpers/JSCHelpers.cpp
index e691d2d1ea9d..3c28eb81ac6b 100644
--- a/ReactCommon/jschelpers/JSCHelpers.cpp
+++ b/ReactCommon/jschelpers/JSCHelpers.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "JSCHelpers.h"
 
diff --git a/ReactCommon/jschelpers/JSCHelpers.h b/ReactCommon/jschelpers/JSCHelpers.h
index 45e69191888c..9bf2e5ee9021 100644
--- a/ReactCommon/jschelpers/JSCHelpers.h
+++ b/ReactCommon/jschelpers/JSCHelpers.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/jschelpers/Unicode.cpp b/ReactCommon/jschelpers/Unicode.cpp
index 5c515b4a7158..8b6dc78a970d 100644
--- a/ReactCommon/jschelpers/Unicode.cpp
+++ b/ReactCommon/jschelpers/Unicode.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "Unicode.h"
 
diff --git a/ReactCommon/jschelpers/Unicode.h b/ReactCommon/jschelpers/Unicode.h
index a3e5fa939724..91ac16726983 100644
--- a/ReactCommon/jschelpers/Unicode.h
+++ b/ReactCommon/jschelpers/Unicode.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/jschelpers/Value.cpp b/ReactCommon/jschelpers/Value.cpp
index 72e303b18a15..09dc1c9ef2db 100644
--- a/ReactCommon/jschelpers/Value.cpp
+++ b/ReactCommon/jschelpers/Value.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "Value.h"
 
diff --git a/ReactCommon/jschelpers/Value.h b/ReactCommon/jschelpers/Value.h
index e7df097096fd..d902732cc256 100644
--- a/ReactCommon/jschelpers/Value.h
+++ b/ReactCommon/jschelpers/Value.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/jschelpers/noncopyable.h b/ReactCommon/jschelpers/noncopyable.h
index 96b32d44b835..d8a1cca4b062 100644
--- a/ReactCommon/jschelpers/noncopyable.h
+++ b/ReactCommon/jschelpers/noncopyable.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 namespace facebook {
diff --git a/ReactCommon/microprofiler/MicroProfiler.cpp b/ReactCommon/microprofiler/MicroProfiler.cpp
index 0487d96477b3..0f1e860e4a99 100644
--- a/ReactCommon/microprofiler/MicroProfiler.cpp
+++ b/ReactCommon/microprofiler/MicroProfiler.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include <algorithm>
 #include <chrono>
diff --git a/ReactCommon/microprofiler/MicroProfiler.h b/ReactCommon/microprofiler/MicroProfiler.h
index 79a102d7189a..30658da0b723 100644
--- a/ReactCommon/microprofiler/MicroProfiler.h
+++ b/ReactCommon/microprofiler/MicroProfiler.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/ReactCommon/privatedata/PrivateDataBase.cpp b/ReactCommon/privatedata/PrivateDataBase.cpp
index 133f526e6115..dd76506594c4 100644
--- a/ReactCommon/privatedata/PrivateDataBase.cpp
+++ b/ReactCommon/privatedata/PrivateDataBase.cpp
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #include "PrivateDataBase.h"
 
diff --git a/ReactCommon/privatedata/PrivateDataBase.h b/ReactCommon/privatedata/PrivateDataBase.h
index 599660c9f232..4553e80efcd9 100644
--- a/ReactCommon/privatedata/PrivateDataBase.h
+++ b/ReactCommon/privatedata/PrivateDataBase.h
@@ -1,4 +1,7 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 #pragma once
 
diff --git a/build.gradle b/build.gradle
index e40f43e2799a..8cd3d00b2dd0 100644
--- a/build.gradle
+++ b/build.gradle
@@ -1,4 +1,7 @@
-// Copyright 2015-present Facebook. All Rights Reserved.
+// Copyright (c) 2015-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 buildscript {
     repositories {
diff --git a/settings.gradle b/settings.gradle
index 7d558841ac0d..c68c5a20fdf8 100644
--- a/settings.gradle
+++ b/settings.gradle
@@ -1,3 +1,6 @@
-// Copyright 2004-present Facebook. All Rights Reserved.
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
 
 include ':ReactAndroid', ':RNTester:android:app'

From 6c02cdc066bf8fababee57a562e51fdde1b024ab Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Fri, 1 Jun 2018 04:01:58 -0700
Subject: [PATCH 0700/1109] Upgrade Metro to 0.37.2

Reviewed By: rafeca

Differential Revision: D8223545

fbshipit-source-id: fdaacbb514e2947b9244cb55ef9170af55ba2f60
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 373cdc2e6b8c..7e30db656ae3 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.37.1",
-    "metro-babel-register": "^0.37.1",
-    "metro-core": "^0.37.1",
-    "metro-memory-fs": "^0.37.1",
+    "metro": "^0.37.2",
+    "metro-babel-register": "^0.37.2",
+    "metro-core": "^0.37.2",
+    "metro-memory-fs": "^0.37.2",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From b90cbd195a806875a660fd109709780104a68941 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 1 Jun 2018 06:40:41 -0700
Subject: [PATCH 0701/1109] Rename default RN transformer

Differential Revision: D8235001

fbshipit-source-id: 59a4b2f13185dd9be0d33f01589d907d49493a26
---
 jest/preprocessor.js | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index b8264eb219d6..b9ae6faf22af 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -34,7 +34,7 @@ const nodeOptions = babelRegisterOnly.config([nodeFiles]);
 babelRegisterOnly([]);
 
 /* $FlowFixMe(site=react_native_oss) */
-const transformer = require('metro/src/transformer.js');
+const transformer = require('metro/src/reactNativeTransformer');
 module.exports = {
   process(src /*: string */, file /*: string */) {
     if (nodeFiles.test(file)) {
@@ -118,7 +118,7 @@ module.exports = {
 
   getCacheKey: createCacheKeyFunction([
     __filename,
-    require.resolve('metro/src/transformer.js'),
+    require.resolve('metro/src/reactNativeTransformer'),
     require.resolve('@babel/core/package.json'),
   ]),
 };

From bdb8089268e26a7cbfc9859bb46d675034406882 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 1 Jun 2018 06:40:51 -0700
Subject: [PATCH 0702/1109] Change default metro transformer

Differential Revision: D8234984

fbshipit-source-id: 83cecfbfa3300f7703ea197009d985bbbc58127a
---
 local-cli/util/Config.js | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/local-cli/util/Config.js b/local-cli/util/Config.js
index 5cd7b0f5fc22..fc996aa067ce 100644
--- a/local-cli/util/Config.js
+++ b/local-cli/util/Config.js
@@ -78,6 +78,8 @@ const Config = {
     getModulesRunBeforeMainModule: () => [
       require.resolve('../../Libraries/Core/InitializeCore'),
     ],
+    getTransformModulePath: () =>
+      require.resolve('metro/src/reactNativeTransformer'),
   }: ConfigT),
 
   find(startDir: string): ConfigT {

From d081f83a0487ffbc7d19f8edc7532611b359dfc6 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 1 Jun 2018 08:32:29 -0700
Subject: [PATCH 0703/1109] Bump metro@0.38.0

Reviewed By: davidaurelio

Differential Revision: D8235787

fbshipit-source-id: a22802c829920e7e182a9aae70bd69a6446d5f8f
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 7e30db656ae3..e51a032af2ab 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.37.2",
-    "metro-babel-register": "^0.37.2",
-    "metro-core": "^0.37.2",
-    "metro-memory-fs": "^0.37.2",
+    "metro": "^0.38.0",
+    "metro-babel-register": "^0.38.0",
+    "metro-core": "^0.38.0",
+    "metro-memory-fs": "^0.38.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 0fc5a91889292eaf4fc2f9b7ba971478040c441e Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 1 Jun 2018 09:36:19 -0700
Subject: [PATCH 0704/1109] Fabric: Integrating `tag` into `EventHandlers`

Summary:
In order to dispatch event, `EventHandlers` must also know react tag. So we have to store it inside.
We plan to illuminate this requirement (and `tag` from `EventHandlers`) eventually.

Reviewed By: fkgozali

Differential Revision: D8211685

fbshipit-source-id: 2064c0f4a7869cbf4d2c92d0349f4ee3998cb8f5
---
 .../core/componentdescriptor/ComponentDescriptor.h   |  3 ++-
 .../ConcreteComponentDescriptor.h                    |  5 +++--
 ReactCommon/fabric/core/events/EventHandlers.cpp     | 12 +++++++++---
 ReactCommon/fabric/core/events/EventHandlers.h       |  7 ++++---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp     | 10 +++++-----
 ReactCommon/fabric/uimanager/ShadowTree.cpp          |  2 +-
 6 files changed, 24 insertions(+), 15 deletions(-)

diff --git a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
index 4804e5ad70cb..669f8475fa4f 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
@@ -85,7 +85,8 @@ class ComponentDescriptor {
    * shadow nodes.
    */
   virtual SharedEventHandlers createEventHandlers(
-    const InstanceHandle &instanceHandle
+    const InstanceHandle &instanceHandle,
+    const Tag &tag
   ) const = 0;
 };
 
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 6ae4ea67321e..8b5ab2ce7cea 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -113,9 +113,10 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   };
 
   virtual SharedEventHandlers createEventHandlers(
-    const InstanceHandle &instanceHandle
+    const InstanceHandle &instanceHandle,
+    const Tag &tag
   ) const override {
-    return std::make_shared<ConcreteEventHandlers>(instanceHandle, eventDispatcher_);
+    return std::make_shared<ConcreteEventHandlers>(instanceHandle, tag, eventDispatcher_);
   }
 
 protected:
diff --git a/ReactCommon/fabric/core/events/EventHandlers.cpp b/ReactCommon/fabric/core/events/EventHandlers.cpp
index 25bd7dfec90a..6980b3e7c103 100644
--- a/ReactCommon/fabric/core/events/EventHandlers.cpp
+++ b/ReactCommon/fabric/core/events/EventHandlers.cpp
@@ -12,12 +12,13 @@
 namespace facebook {
 namespace react {
 
-EventHandlers::EventHandlers(InstanceHandle instanceHandle, SharedEventDispatcher eventDispatcher):
+EventHandlers::EventHandlers(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher):
   instanceHandle_(instanceHandle),
+  tag_(tag),
   eventDispatcher_(eventDispatcher) {}
 
 void EventHandlers::dispatchEvent(
-  const std::string &name,
+  const std::string &type,
   const folly::dynamic &payload,
   const EventPriority &priority
 ) const {
@@ -26,8 +27,13 @@ void EventHandlers::dispatchEvent(
     return;
   }
 
+  // Mixing `target` into `payload`.
+  assert(payload.isObject());
+  folly::dynamic extendedPayload = folly::dynamic::object("target", tag_);
+  extendedPayload.merge_patch(payload);
+
   // TODO(T29610783): Reconsider using dynamic dispatch here.
-  eventDispatcher->dispatchEvent(instanceHandle_, name, payload, priority);
+  eventDispatcher->dispatchEvent(instanceHandle_, type, extendedPayload, priority);
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/events/EventHandlers.h b/ReactCommon/fabric/core/events/EventHandlers.h
index 596e8871a90f..f2ae16fd6f0b 100644
--- a/ReactCommon/fabric/core/events/EventHandlers.h
+++ b/ReactCommon/fabric/core/events/EventHandlers.h
@@ -32,8 +32,8 @@ using SharedEventHandlers = std::shared_ptr<const EventHandlers>;
 class EventHandlers {
 
 public:
-  EventHandlers(InstanceHandle instanceHandle, SharedEventDispatcher eventDispatcher);
   virtual ~EventHandlers() = default;
+  EventHandlers(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
 
 protected:
 
@@ -42,14 +42,15 @@ class EventHandlers {
    * Is used by particular subclasses only.
    */
   void dispatchEvent(
-    const std::string &name,
-    const folly::dynamic &payload = {},
+    const std::string &type,
+    const folly::dynamic &payload = folly::dynamic::object(),
     const EventPriority &priority = EventPriority::AsynchronousBatched
   ) const;
 
 private:
 
   InstanceHandle instanceHandle_;
+  Tag tag_;
   std::weak_ptr<const EventDispatcher> eventDispatcher_;
 };
 
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 7bedbfc8e8ec..41115a191eeb 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -134,7 +134,7 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
     componentDescriptor->createShadowNode(
       tag,
       rootTag,
-      componentDescriptor->createEventHandlers(instanceHandle),
+      componentDescriptor->createEventHandlers(instanceHandle, tag),
       componentDescriptor->cloneProps(nullptr, rawProps)
     );
 
@@ -155,7 +155,7 @@ SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode,
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
-      componentDescriptor->createEventHandlers(instanceHandle),
+      componentDescriptor->createEventHandlers(instanceHandle, shadowNode->getTag()),
       nullptr
     );
 
@@ -172,7 +172,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
-      componentDescriptor->createEventHandlers(instanceHandle),
+      componentDescriptor->createEventHandlers(instanceHandle, shadowNode->getTag()),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
@@ -190,7 +190,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
-      componentDescriptor->createEventHandlers(instanceHandle),
+      componentDescriptor->createEventHandlers(instanceHandle, shadowNode->getTag()),
       nullptr
     );
 
@@ -208,7 +208,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
-      componentDescriptor->createEventHandlers(instanceHandle),
+      componentDescriptor->createEventHandlers(instanceHandle, shadowNode->getTag()),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 06e259f86d08..140ff8071e1c 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -18,7 +18,7 @@ namespace react {
 ShadowTree::ShadowTree(Tag rootTag):
   rootTag_(rootTag) {
 
-  auto &&noopEventHandlers = std::make_shared<const ViewEventHandlers>(nullptr, nullptr);
+  auto &&noopEventHandlers = std::make_shared<const ViewEventHandlers>(nullptr, rootTag, nullptr);
   rootShadowNode_ = std::make_shared<RootShadowNode>(
     rootTag,
     rootTag,

From beb3fcda34395b165070c2b8f34d51fddde1d62a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 1 Jun 2018 09:36:25 -0700
Subject: [PATCH 0705/1109] Fabric: The first version of event dispatching
 pipeline

Summary:
This is the first attempt to implement some base part of event dispatching pipeline from end-to-end.
Even when it is working, all this is still incomplete and generally up in the air. We are still messing proper implementation of event queue, priority, and synchronization of react reconciliation process with event scheduling.

Reviewed By: fkgozali

Differential Revision: D8212271

fbshipit-source-id: 92f9427d14726441c70ffff294ac95eeb004152a
---
 .../fabric/core/events/EventDispatcher.h      |  8 +++--
 .../fabric/core/events/EventHandlers.cpp      | 32 ++++++++++++++++++-
 .../fabric/core/events/EventHandlers.h        | 10 ++++--
 ReactCommon/fabric/uimanager/Scheduler.cpp    |  8 +++--
 ReactCommon/fabric/uimanager/Scheduler.h      |  2 +-
 .../uimanager/SchedulerEventDispatcher.cpp    | 30 +++++++++++++++--
 .../uimanager/SchedulerEventDispatcher.h      | 21 ++++++++++--
 7 files changed, 97 insertions(+), 14 deletions(-)

diff --git a/ReactCommon/fabric/core/events/EventDispatcher.h b/ReactCommon/fabric/core/events/EventDispatcher.h
index 354e35ed4770..40e5184a2124 100644
--- a/ReactCommon/fabric/core/events/EventDispatcher.h
+++ b/ReactCommon/fabric/core/events/EventDispatcher.h
@@ -28,12 +28,16 @@ class EventDispatcher {
 
 public:
 
+  virtual EventTarget createEventTarget(const InstanceHandle &instanceHandle) const = 0;
+
+  virtual void releaseEventTarget(const EventTarget &eventTarget) const = 0;
+
   /*
    * Dispatches "raw" event using some event-delivery infrastructure.
    */
   virtual void dispatchEvent(
-    const InstanceHandle &instanceHandle,
-    const std::string &name,
+    const EventTarget &eventTarget,
+    const std::string &type,
     const folly::dynamic &payload,
     const EventPriority &priority
   ) const = 0;
diff --git a/ReactCommon/fabric/core/events/EventHandlers.cpp b/ReactCommon/fabric/core/events/EventHandlers.cpp
index 6980b3e7c103..3d4ecc804885 100644
--- a/ReactCommon/fabric/core/events/EventHandlers.cpp
+++ b/ReactCommon/fabric/core/events/EventHandlers.cpp
@@ -17,6 +17,10 @@ EventHandlers::EventHandlers(const InstanceHandle &instanceHandle, const Tag &ta
   tag_(tag),
   eventDispatcher_(eventDispatcher) {}
 
+EventHandlers::~EventHandlers() {
+  releaseEventTargetIfNeeded();
+}
+
 void EventHandlers::dispatchEvent(
   const std::string &type,
   const folly::dynamic &payload,
@@ -27,13 +31,39 @@ void EventHandlers::dispatchEvent(
     return;
   }
 
+  createEventTargetIfNeeded();
+
   // Mixing `target` into `payload`.
   assert(payload.isObject());
   folly::dynamic extendedPayload = folly::dynamic::object("target", tag_);
   extendedPayload.merge_patch(payload);
 
   // TODO(T29610783): Reconsider using dynamic dispatch here.
-  eventDispatcher->dispatchEvent(instanceHandle_, type, extendedPayload, priority);
+  eventDispatcher->dispatchEvent(eventTarget_, type, extendedPayload, priority);
+}
+
+void EventHandlers::createEventTargetIfNeeded() const {
+  std::lock_guard<std::mutex> lock(mutex_);
+
+  if (eventTarget_) {
+    return;
+  }
+
+  auto &&eventDispatcher = eventDispatcher_.lock();
+  assert(eventDispatcher);
+  eventTarget_ = eventDispatcher->createEventTarget(instanceHandle_);
+}
+
+void EventHandlers::releaseEventTargetIfNeeded() const {
+  std::lock_guard<std::mutex> lock(mutex_);
+
+  if (!eventTarget_) {
+    return;
+  }
+
+  auto &&eventDispatcher = eventDispatcher_.lock();
+  assert(eventDispatcher);
+  eventDispatcher->releaseEventTarget(eventTarget_);
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/events/EventHandlers.h b/ReactCommon/fabric/core/events/EventHandlers.h
index f2ae16fd6f0b..b55db7dc7e48 100644
--- a/ReactCommon/fabric/core/events/EventHandlers.h
+++ b/ReactCommon/fabric/core/events/EventHandlers.h
@@ -7,6 +7,7 @@
 #pragma once
 
 #include <memory>
+#include <mutex>
 
 #include <folly/dynamic.h>
 #include <fabric/core/EventDispatcher.h>
@@ -20,8 +21,6 @@ class EventHandlers;
 
 using SharedEventHandlers = std::shared_ptr<const EventHandlers>;
 
-
-
 /*
  * Base class for all particular typed event handlers.
  * Stores `InstanceHandle` identifying a particular component and the pointer
@@ -32,8 +31,8 @@ using SharedEventHandlers = std::shared_ptr<const EventHandlers>;
 class EventHandlers {
 
 public:
-  virtual ~EventHandlers() = default;
   EventHandlers(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
+  virtual ~EventHandlers();
 
 protected:
 
@@ -49,9 +48,14 @@ class EventHandlers {
 
 private:
 
+  void createEventTargetIfNeeded() const;
+  void releaseEventTargetIfNeeded() const;
+
   InstanceHandle instanceHandle_;
   Tag tag_;
   std::weak_ptr<const EventDispatcher> eventDispatcher_;
+  mutable EventTarget eventTarget_ {nullptr};
+  mutable std::mutex mutex_;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index d20e1f1b0a80..5a488f4da476 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -23,10 +23,14 @@ namespace facebook {
 namespace react {
 
 Scheduler::Scheduler() {
-  eventDispatcher_ = std::make_shared<SchedulerEventDispatcher>();
-  auto componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry(eventDispatcher_);
+  auto &&eventDispatcher = std::make_shared<SchedulerEventDispatcher>();
+  auto &&componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry(eventDispatcher);
+
   uiManager_ = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
   uiManager_->setDelegate(this);
+
+  eventDispatcher->setUIManager(uiManager_);
+  eventDispatcher_ = eventDispatcher;
 }
 
 Scheduler::~Scheduler() {
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index b63fbf666e2b..6b6fae79dc1a 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -73,7 +73,7 @@ class Scheduler final:
   SchedulerDelegate *delegate_;
   std::shared_ptr<FabricUIManager> uiManager_;
   std::unordered_map<Tag, SharedShadowTree> shadowTreeRegistry_;
-  std::shared_ptr<SchedulerEventDispatcher> eventDispatcher_;
+  SharedSchedulerEventDispatcher eventDispatcher_;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
index ad9f44136361..5cd608667b63 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
@@ -10,13 +10,37 @@
 namespace facebook {
 namespace react {
 
+// TODO(T29874519): Get rid of "top" prefix once and for all.
+/*
+ * Capitalizes the first letter of the event type and adds "top" prefix
+ * (e.g. "layout" becames "topLayout").
+ */
+static std::string normalizeEventType(const std::string &type) {
+  std::string prefixedType = type;
+  prefixedType[0] = toupper(prefixedType[0]);
+  prefixedType.insert(0, "top");
+  return prefixedType;
+}
+
+void SchedulerEventDispatcher::setUIManager(std::shared_ptr<const FabricUIManager> uiManager) {
+  uiManager_ = uiManager;
+}
+
+EventTarget SchedulerEventDispatcher::createEventTarget(const InstanceHandle &instanceHandle) const {
+  return uiManager_->createEventTarget(instanceHandle);
+}
+
+void SchedulerEventDispatcher::releaseEventTarget(const EventTarget &eventTarget) const {
+  uiManager_->releaseEventTarget(eventTarget);
+}
+
 void SchedulerEventDispatcher::dispatchEvent(
-  const InstanceHandle &instanceHandle,
-  const std::string &name,
+  const EventTarget &eventTarget,
+  const std::string &type,
   const folly::dynamic &payload,
   const EventPriority &priority
 ) const {
-  // Some future magic here.
+  uiManager_->dispatchEvent(eventTarget, normalizeEventType(type), payload);
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
index 17cd7610951f..d7f6e190c0ff 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
@@ -9,11 +9,16 @@
 
 #include <fabric/core/EventDispatcher.h>
 #include <fabric/core/EventPrimitives.h>
+#include <fabric/uimanager/FabricUIManager.h>
 #include <folly/dynamic.h>
 
 namespace facebook {
 namespace react {
 
+class SchedulerEventDispatcher;
+
+using SharedSchedulerEventDispatcher = std::shared_ptr<const SchedulerEventDispatcher>;
+
 /*
  * Concrete EventDispatcher.
  */
@@ -22,12 +27,24 @@ class SchedulerEventDispatcher final:
 
 public:
 
+  void setUIManager(std::shared_ptr<const FabricUIManager> uiManager);
+
+#pragma mark - EventDispatcher
+
+  EventTarget createEventTarget(const InstanceHandle &instanceHandle) const override;
+
+  void releaseEventTarget(const EventTarget &eventTarget) const override;
+
   void dispatchEvent(
-    const InstanceHandle &instanceHandle,
-    const std::string &name,
+    const EventTarget &eventTarget,
+    const std::string &type,
     const folly::dynamic &payload,
     const EventPriority &priority
   ) const override;
+
+private:
+
+  std::shared_ptr<const FabricUIManager> uiManager_;
 };
 
 } // namespace react

From ec265df1d2ffd71b9c3f4753a9b2633984ee9ea7 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 1 Jun 2018 09:36:30 -0700
Subject: [PATCH 0706/1109] Fabric: Removed unused type aliases

Summary: Trivial.

Reviewed By: fkgozali

Differential Revision: D8212287

fbshipit-source-id: 228951742568d28a064ee03b6314a4c01532b9c9
---
 ReactCommon/fabric/core/primitives/ReactPrimitives.h | 9 ---------
 1 file changed, 9 deletions(-)

diff --git a/ReactCommon/fabric/core/primitives/ReactPrimitives.h b/ReactCommon/fabric/core/primitives/ReactPrimitives.h
index c81f0ac938a1..836fdb741758 100644
--- a/ReactCommon/fabric/core/primitives/ReactPrimitives.h
+++ b/ReactCommon/fabric/core/primitives/ReactPrimitives.h
@@ -28,15 +28,6 @@ using InstanceHandle = struct InstanceHandleDummyStruct {} *;
 using RawProps = std::map<std::string, folly::dynamic>;
 using SharedRawProps = std::shared_ptr<const RawProps>;
 
-/*
- * Components event handlers.
- * Something which usually called from JavaScript side.
- */
-using BubblingEventHandler = void (*)(void);
-using SharedBubblingEventHandler = std::shared_ptr<BubblingEventHandler>;
-using DirectEventHandler = void (*)(void);
-using SharedDirectEventHandler = std::shared_ptr<DirectEventHandler>;
-
 /*
  * Universal component handle which allows to refer to `ComponentDescriptor`s
  * in maps efficiently.

From 2314c83258b53b29d9c6a27411b6fb67ded4d8cc Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 1 Jun 2018 10:11:12 -0700
Subject: [PATCH 0707/1109] Clamp typechecks -> Flow

Reviewed By: yungsters

Differential Revision: D8219220

fbshipit-source-id: e849d9dae573459e4b09e317cc6dc37bec9ce4e8
---
 Libraries/Utilities/clamp.js | 10 ++--------
 1 file changed, 2 insertions(+), 8 deletions(-)

diff --git a/Libraries/Utilities/clamp.js b/Libraries/Utilities/clamp.js
index 50f60f17c8ce..a3f0a2c957e7 100644
--- a/Libraries/Utilities/clamp.js
+++ b/Libraries/Utilities/clamp.js
@@ -5,18 +5,12 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @typechecks
+ * @flow
  */
 
 'use strict';
 
-/**
- * @param {number} min
- * @param {number} value
- * @param {number} max
- * @return {number}
- */
-function clamp(min, value, max) {
+function clamp(min: number, value: number, max: number): number {
   if (value < min) {
     return min;
   }

From a35a23831789030e17f766f72d307ae315be107d Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 1 Jun 2018 10:11:17 -0700
Subject: [PATCH 0708/1109] RefreshControl ES6 Class

Reviewed By: sahrens

Differential Revision: D8219221

fbshipit-source-id: 445243964d64dd5274c1e47bdc137645dc8eecaf
---
 .../RefreshControl/RefreshControl.js          | 150 +++++++-----------
 1 file changed, 55 insertions(+), 95 deletions(-)

diff --git a/Libraries/Components/RefreshControl/RefreshControl.js b/Libraries/Components/RefreshControl/RefreshControl.js
index 665a1bd91ea9..9b287cc4a180 100644
--- a/Libraries/Components/RefreshControl/RefreshControl.js
+++ b/Libraries/Components/RefreshControl/RefreshControl.js
@@ -10,16 +10,12 @@
 
 'use strict';
 
-const ColorPropType = require('ColorPropType');
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const Platform = require('Platform');
 const React = require('React');
-const ReactNative = require('ReactNative');
-const PropTypes = require('prop-types');
-const ViewPropTypes = require('ViewPropTypes');
+const {NativeComponent} = require('ReactNative');
 
-const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
+const nullthrows = require('fbjs/lib/nullthrows');
 
 import type {ColorValue} from 'StyleSheetTypes';
 import type {ViewProps} from 'ViewPropTypes';
@@ -33,21 +29,51 @@ if (Platform.OS === 'android') {
 } else {
   var RefreshLayoutConsts = {SIZE: {}};
 }
+type NativeRefreshControlType = Class<NativeComponent<Props>>;
+
+const NativeRefreshControl: NativeRefreshControlType =
+  Platform.OS === 'ios'
+    ? (requireNativeComponent('RCTRefreshControl'): any)
+    : (requireNativeComponent('AndroidSwipeRefreshLayout'): any);
 
 type IOSProps = $ReadOnly<{|
+  /**
+   * The color of the refresh indicator.
+   */
   tintColor?: ?ColorValue,
+  /**
+   * Title color.
+   */
   titleColor?: ?ColorValue,
+  /**
+   * The title displayed under the refresh indicator.
+   */
   title?: ?string,
 |}>;
 
 type AndroidProps = $ReadOnly<{|
+  /**
+   * Whether the pull to refresh functionality is enabled.
+   */
   enabled?: ?boolean,
+  /**
+   * The colors (at least one) that will be used to draw the refresh indicator.
+   */
   colors?: ?$ReadOnlyArray<ColorValue>,
+  /**
+   * The background color of the refresh indicator.
+   */
   progressBackgroundColor?: ?ColorValue,
+  /**
+   * Size of the refresh indicator, see RefreshControl.SIZE.
+   */
   size?: ?(
     | typeof RefreshLayoutConsts.SIZE.DEFAULT
     | typeof RefreshLayoutConsts.SIZE.LARGE
   ),
+  /**
+   * Progress view top offset
+   */
   progressViewOffset?: ?number,
 |}>;
 
@@ -55,7 +81,15 @@ type Props = $ReadOnly<{|
   ...ViewProps,
   ...IOSProps,
   ...AndroidProps,
+
+  /**
+   * Called when the view starts refreshing.
+   */
   onRefresh?: ?Function,
+
+  /**
+   * Whether the view should be indicating an active refresh.
+   */
   refreshing: boolean,
 |}>;
 
@@ -104,87 +138,29 @@ type Props = $ReadOnly<{|
  * __Note:__ `refreshing` is a controlled prop, this is why it needs to be set to true
  * in the `onRefresh` function otherwise the refresh indicator will stop immediately.
  */
-const RefreshControl = createReactClass({
-  displayName: 'RefreshControl',
-  statics: {
-    SIZE: RefreshLayoutConsts.SIZE,
-  },
-
-  mixins: [NativeMethodsMixin],
-
-  propTypes: {
-    ...ViewPropTypes,
-    /**
-     * Called when the view starts refreshing.
-     */
-    onRefresh: PropTypes.func,
-    /**
-     * Whether the view should be indicating an active refresh.
-     */
-    refreshing: PropTypes.bool.isRequired,
-    /**
-     * The color of the refresh indicator.
-     * @platform ios
-     */
-    tintColor: ColorPropType,
-    /**
-     * Title color.
-     * @platform ios
-     */
-    titleColor: ColorPropType,
-    /**
-     * The title displayed under the refresh indicator.
-     * @platform ios
-     */
-    title: PropTypes.string,
-    /**
-     * Whether the pull to refresh functionality is enabled.
-     * @platform android
-     */
-    enabled: PropTypes.bool,
-    /**
-     * The colors (at least one) that will be used to draw the refresh indicator.
-     * @platform android
-     */
-    colors: PropTypes.arrayOf(ColorPropType),
-    /**
-     * The background color of the refresh indicator.
-     * @platform android
-     */
-    progressBackgroundColor: ColorPropType,
-    /**
-     * Size of the refresh indicator, see RefreshControl.SIZE.
-     * @platform android
-     */
-    size: PropTypes.oneOf([
-      RefreshLayoutConsts.SIZE.DEFAULT,
-      RefreshLayoutConsts.SIZE.LARGE,
-    ]),
-    /**
-     * Progress view top offset
-     * @platform android
-     */
-    progressViewOffset: PropTypes.number,
-  },
-
-  _nativeRef: (null: any),
-  _lastNativeRefreshing: false,
+class RefreshControl extends React.Component<Props> {
+  static SIZE = RefreshLayoutConsts.SIZE;
+
+  _nativeRef: ?React.ElementRef<NativeRefreshControlType> = null;
+  _lastNativeRefreshing = false;
 
   componentDidMount() {
     this._lastNativeRefreshing = this.props.refreshing;
-  },
+  }
 
-  componentDidUpdate(prevProps: {refreshing: boolean}) {
+  componentDidUpdate(prevProps: Props) {
     // RefreshControl is a controlled component so if the native refreshing
     // value doesn't match the current js refreshing prop update it to
     // the js value.
     if (this.props.refreshing !== prevProps.refreshing) {
       this._lastNativeRefreshing = this.props.refreshing;
     } else if (this.props.refreshing !== this._lastNativeRefreshing) {
-      this._nativeRef.setNativeProps({refreshing: this.props.refreshing});
+      nullthrows(this._nativeRef).setNativeProps({
+        refreshing: this.props.refreshing,
+      });
       this._lastNativeRefreshing = this.props.refreshing;
     }
-  },
+  }
 
   render() {
     return (
@@ -196,9 +172,9 @@ const RefreshControl = createReactClass({
         onRefresh={this._onRefresh}
       />
     );
-  },
+  }
 
-  _onRefresh() {
+  _onRefresh = () => {
     this._lastNativeRefreshing = true;
 
     this.props.onRefresh && this.props.onRefresh();
@@ -206,23 +182,7 @@ const RefreshControl = createReactClass({
     // The native component will start refreshing so force an update to
     // make sure it stays in sync with the js component.
     this.forceUpdate();
-  },
-});
-
-class TypedRefreshControl extends ReactNative.NativeComponent<Props> {
-  static SIZE = RefreshLayoutConsts.SIZE;
-}
-
-if (Platform.OS === 'ios') {
-  var NativeRefreshControl = requireNativeComponent(
-    'RCTRefreshControl',
-    RefreshControl,
-  );
-} else if (Platform.OS === 'android') {
-  var NativeRefreshControl = requireNativeComponent(
-    'AndroidSwipeRefreshLayout',
-    RefreshControl,
-  );
+  };
 }
 
-module.exports = ((RefreshControl: any): Class<TypedRefreshControl>);
+module.exports = RefreshControl;

From edd7acbb1e6fe185600a19cc1cbb38feb16c85ad Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 1 Jun 2018 10:11:23 -0700
Subject: [PATCH 0709/1109] ActivityIndicator ES6 Class

Reviewed By: yungsters

Differential Revision: D8219463

fbshipit-source-id: 7d252d15bb4a7345d156b1659b09be2a4a69ba6c
---
 .../ActivityIndicator/ActivityIndicator.js    | 174 ++++++++----------
 jest/mockComponent.js                         |  17 +-
 2 files changed, 96 insertions(+), 95 deletions(-)

diff --git a/Libraries/Components/ActivityIndicator/ActivityIndicator.js b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
index 7438d1e35f12..65809a32300f 100644
--- a/Libraries/Components/ActivityIndicator/ActivityIndicator.js
+++ b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
@@ -10,19 +10,15 @@
 
 'use strict';
 
-const ColorPropType = require('ColorPropType');
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const Platform = require('Platform');
 const ProgressBarAndroid = require('ProgressBarAndroid');
-const PropTypes = require('prop-types');
 const React = require('React');
 const StyleSheet = require('StyleSheet');
 const View = require('View');
-const ViewPropTypes = require('ViewPropTypes');
 
-const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {NativeComponent} from 'ReactNative';
 import type {ViewProps} from 'ViewPropTypes';
 
 let RCTActivityIndicator;
@@ -31,113 +27,103 @@ const GRAY = '#999999';
 
 type IndicatorSize = number | 'small' | 'large';
 
+type IOSProps = $ReadOnly<{|
+  /**
+   * Whether the indicator should hide when not animating (true by default).
+   *
+   * See http://facebook.github.io/react-native/docs/activityindicator.html#hideswhenstopped
+   */
+  hidesWhenStopped?: ?boolean,
+|}>;
 type Props = $ReadOnly<{|
   ...ViewProps,
+  ...IOSProps,
 
+  /**
+   * Whether to show the indicator (true, the default) or hide it (false).
+   *
+   * See http://facebook.github.io/react-native/docs/activityindicator.html#animating
+   */
   animating?: ?boolean,
+
+  /**
+   * The foreground color of the spinner (default is gray).
+   *
+   * See http://facebook.github.io/react-native/docs/activityindicator.html#color
+   */
   color?: ?string,
-  hidesWhenStopped?: ?boolean,
+
+  /**
+   * Size of the indicator (default is 'small').
+   * Passing a number to the size prop is only supported on Android.
+   *
+   * See http://facebook.github.io/react-native/docs/activityindicator.html#size
+   */
   size?: ?IndicatorSize,
 |}>;
 
-type DefaultProps = {
-  animating: boolean,
-  color: ?string,
-  hidesWhenStopped: boolean,
-  size: IndicatorSize,
-};
-
 /**
  * Displays a circular loading indicator.
  *
  * See http://facebook.github.io/react-native/docs/activityindicator.html
  */
-const ActivityIndicator = ((createReactClass({
-  displayName: 'ActivityIndicator',
-  mixins: [NativeMethodsMixin],
-
-  propTypes: {
-    ...ViewPropTypes,
-    /**
-     * Whether to show the indicator (true, the default) or hide it (false).
-     *
-     * See http://facebook.github.io/react-native/docs/activityindicator.html#animating
-     */
-    animating: PropTypes.bool,
-    /**
-     * The foreground color of the spinner (default is gray).
-     *
-     * See http://facebook.github.io/react-native/docs/activityindicator.html#color
-     */
-    color: ColorPropType,
-    /**
-     * Size of the indicator (default is 'small').
-     * Passing a number to the size prop is only supported on Android.
-     *
-     * See http://facebook.github.io/react-native/docs/activityindicator.html#size
-     */
-    size: PropTypes.oneOfType([
-      PropTypes.oneOf(['small', 'large']),
-      PropTypes.number,
-    ]),
-    /**
-     * Whether the indicator should hide when not animating (true by default).
-     *
-     * @platform ios
-     *
-     * See http://facebook.github.io/react-native/docs/activityindicator.html#hideswhenstopped
-     */
-    hidesWhenStopped: PropTypes.bool,
-  },
+const ActivityIndicator = (
+  props: $ReadOnly<{|
+    ...Props,
+    forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
+  |}>,
+) => {
+  const {onLayout, style, forwardedRef, ...restProps} = props;
+  let sizeStyle;
+
+  switch (props.size) {
+    case 'small':
+      sizeStyle = styles.sizeSmall;
+      break;
+    case 'large':
+      sizeStyle = styles.sizeLarge;
+      break;
+    default:
+      sizeStyle = {height: props.size, width: props.size};
+      break;
+  }
+
+  const nativeProps = {
+    ...restProps,
+    ref: forwardedRef,
+    style: sizeStyle,
+    styleAttr: 'Normal',
+    indeterminate: true,
+  };
+
+  return (
+    <View onLayout={onLayout} style={[styles.container, style]}>
+      {Platform.OS === 'ios' ? (
+        <RCTActivityIndicator {...nativeProps} />
+      ) : (
+        <ProgressBarAndroid {...nativeProps} />
+      )}
+    </View>
+  );
+};
 
-  getDefaultProps(): DefaultProps {
-    return {
-      animating: true,
-      color: Platform.OS === 'ios' ? GRAY : null,
-      hidesWhenStopped: true,
-      size: 'small',
-    };
-  },
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+const ActivityIndicatorWithRef = React.forwardRef((props: Props, ref) => {
+  return <ActivityIndicator {...props} forwardedRef={ref} />;
+});
 
-  render() {
-    const {onLayout, style, ...props} = this.props;
-    let sizeStyle;
-
-    switch (props.size) {
-      case 'small':
-        sizeStyle = styles.sizeSmall;
-        break;
-      case 'large':
-        sizeStyle = styles.sizeLarge;
-        break;
-      default:
-        sizeStyle = {height: props.size, width: props.size};
-        break;
-    }
-
-    const nativeProps = {
-      ...props,
-      style: sizeStyle,
-      styleAttr: 'Normal',
-      indeterminate: true,
-    };
-
-    return (
-      <View onLayout={onLayout} style={[styles.container, style]}>
-        {Platform.OS === 'ios' ? (
-          <RCTActivityIndicator {...nativeProps} />
-        ) : (
-          <ProgressBarAndroid {...nativeProps} />
-        )}
-      </View>
-    );
-  },
-}): any): React.ComponentType<Props>);
+ActivityIndicatorWithRef.defaultProps = {
+  animating: true,
+  color: Platform.OS === 'ios' ? GRAY : null,
+  hidesWhenStopped: true,
+  size: 'small',
+};
+ActivityIndicatorWithRef.displayName = 'ActivityIndicator';
 
 if (Platform.OS === 'ios') {
   RCTActivityIndicator = requireNativeComponent(
     'RCTActivityIndicatorView',
-    ActivityIndicator,
+    null,
     {nativeOnly: {activityIndicatorViewStyle: true}},
   );
 }
@@ -157,4 +143,4 @@ const styles = StyleSheet.create({
   },
 });
 
-module.exports = ActivityIndicator;
+module.exports = (ActivityIndicatorWithRef: Class<NativeComponent<Props>>);
diff --git a/jest/mockComponent.js b/jest/mockComponent.js
index e22c34ccaa43..6d5a80b47e07 100644
--- a/jest/mockComponent.js
+++ b/jest/mockComponent.js
@@ -20,9 +20,24 @@ module.exports = (moduleName, instanceMethods) => {
     render() {
       const name = RealComponent.displayName || RealComponent.name;
 
+      const props = Object.assign({}, RealComponent.defaultProps);
+
+      if (this.props) {
+        Object.keys(this.props).forEach(prop => {
+          // We can't just assign props on top of defaultProps
+          // because React treats undefined as special and different from null.
+          // If a prop is specified but set to undefined it is ignored and the
+          // default prop is used instead. If it is set to null, then the
+          // null value overwrites the default value.
+          if (this.props[prop] !== undefined) {
+            props[prop] = this.props[prop];
+          }
+        });
+      }
+
       return React.createElement(
         name.replace(/^(RCT|RK)/, ''),
-        this.props,
+        props,
         this.props.children,
       );
     }

From 3b53091869b673ea33a4af34242e2227ca944768 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 1 Jun 2018 10:11:28 -0700
Subject: [PATCH 0710/1109] DatePickerIOS add onChange event definition

Reviewed By: sahrens

Differential Revision: D8219622

fbshipit-source-id: 37f26d0981318b7eab9d3c734c44e7714fa6f0e8
---
 .../DatePicker/DatePickerIOS.ios.js           | 23 +++++++++----------
 1 file changed, 11 insertions(+), 12 deletions(-)

diff --git a/Libraries/Components/DatePicker/DatePickerIOS.ios.js b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
index c089d9ea8a5a..2010e8c1fce5 100644
--- a/Libraries/Components/DatePicker/DatePickerIOS.ios.js
+++ b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
@@ -40,6 +40,7 @@ type Props = $ReadOnly<{|
   minimumDate?: ?Date,
   minuteInterval?: ?(1 | 2 | 3 | 4 | 5 | 6 | 10 | 12 | 15 | 20 | 30),
   mode?: ?('date' | 'time' | 'datetime'),
+  onChange?: ?(event: Event) => void,
   onDateChange: (date: Date) => void,
   timeZoneOffsetInMinutes?: ?number,
 |}>;
@@ -75,6 +76,15 @@ const DatePickerIOS = ((createReactClass({
      */
     initialDate: PropTypes.instanceOf(Date),
 
+    /**
+     * Date change handler.
+     *
+     * This is called when the user changes the date or time in the UI.
+     * The first and only argument is an Event. For getting the date the picker
+     * was changed to, use onDateChange instead.
+     */
+    onChange: PropTypes.func,
+
     /**
      * Date change handler.
      *
@@ -144,7 +154,6 @@ const DatePickerIOS = ((createReactClass({
     const nativeTimeStamp = event.nativeEvent.timestamp;
     this.props.onDateChange &&
       this.props.onDateChange(new Date(nativeTimeStamp));
-    // $FlowFixMe(>=0.41.0)
     this.props.onChange && this.props.onChange(event);
   },
 
@@ -193,16 +202,6 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTDatePickerIOS = requireNativeComponent('RCTDatePicker', {
-  propTypes: {
-    ...DatePickerIOS.propTypes,
-    date: PropTypes.number,
-    locale: PropTypes.string,
-    minimumDate: PropTypes.number,
-    maximumDate: PropTypes.number,
-    onDateChange: () => null,
-    onChange: PropTypes.func,
-  },
-});
+const RCTDatePickerIOS = requireNativeComponent('RCTDatePicker');
 
 module.exports = DatePickerIOS;

From f8c8231706492b588331354d45b833aa21434e13 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 1 Jun 2018 10:11:35 -0700
Subject: [PATCH 0711/1109] DatePickerIOS ES6 Class

Reviewed By: sahrens

Differential Revision: D8219657

fbshipit-source-id: cef48cf3ad24ad442f07df0edad55ab97d96c6f2
---
 .../DatePicker/DatePickerIOS.ios.js           | 173 ++++++++----------
 1 file changed, 74 insertions(+), 99 deletions(-)

diff --git a/Libraries/Components/DatePicker/DatePickerIOS.ios.js b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
index 2010e8c1fce5..f76902d852b4 100644
--- a/Libraries/Components/DatePicker/DatePickerIOS.ios.js
+++ b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
@@ -13,35 +13,89 @@
 
 'use strict';
 
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const React = require('React');
 const invariant = require('fbjs/lib/invariant');
-const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
 const View = require('View');
-const ViewPropTypes = require('ViewPropTypes');
 
-const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
 import type {ViewProps} from 'ViewPropTypes';
-type DefaultProps = {
-  mode: 'date' | 'time' | 'datetime',
-};
 
 type Event = Object;
 
 type Props = $ReadOnly<{|
   ...ViewProps,
+
+  /**
+   * The currently selected date.
+   */
   date?: ?Date,
+
+  /**
+   * Provides an initial value that will change when the user starts selecting
+   * a date. It is useful for simple use-cases where you do not want to deal
+   * with listening to events and updating the date prop to keep the
+   * controlled state in sync. The controlled state has known bugs which
+   * causes it to go out of sync with native. The initialDate prop is intended
+   * to allow you to have native be source of truth.
+   */
   initialDate?: ?Date,
+
+  /**
+   * The date picker locale.
+   */
   locale?: ?string,
+
+  /**
+   * Maximum date.
+   *
+   * Restricts the range of possible date/time values.
+   */
   maximumDate?: ?Date,
+
+  /**
+   * Minimum date.
+   *
+   * Restricts the range of possible date/time values.
+   */
   minimumDate?: ?Date,
+
+  /**
+   * The interval at which minutes can be selected.
+   */
   minuteInterval?: ?(1 | 2 | 3 | 4 | 5 | 6 | 10 | 12 | 15 | 20 | 30),
+
+  /**
+   * The date picker mode.
+   */
   mode?: ?('date' | 'time' | 'datetime'),
+
+  /**
+   * Date change handler.
+   *
+   * This is called when the user changes the date or time in the UI.
+   * The first and only argument is an Event. For getting the date the picker
+   * was changed to, use onDateChange instead.
+   */
   onChange?: ?(event: Event) => void,
+
+  /**
+   * Date change handler.
+   *
+   * This is called when the user changes the date or time in the UI.
+   * The first and only argument is a Date object representing the new
+   * date and time.
+   */
   onDateChange: (date: Date) => void,
+
+  /**
+   * Timezone offset in minutes.
+   *
+   * By default, the date picker will use the device's timezone. With this
+   * parameter, it is possible to force a certain timezone offset. For
+   * instance, to show times in Pacific Standard Time, pass -7 * 60.
+   */
   timeZoneOffsetInMinutes?: ?number,
 |}>;
 
@@ -52,94 +106,15 @@ type Props = $ReadOnly<{|
  * the user's change will be reverted immediately to reflect `props.date` as the
  * source of truth.
  */
-const DatePickerIOS = ((createReactClass({
-  displayName: 'DatePickerIOS',
-  // TOOD: Put a better type for _picker
-  _picker: (undefined: ?$FlowFixMe),
-
-  mixins: [NativeMethodsMixin],
-
-  propTypes: {
-    ...ViewPropTypes,
-    /**
-     * The currently selected date.
-     */
-    date: PropTypes.instanceOf(Date),
-
-    /**
-     * Provides an initial value that will change when the user starts selecting
-     * a date. It is useful for simple use-cases where you do not want to deal
-     * with listening to events and updating the date prop to keep the
-     * controlled state in sync. The controlled state has known bugs which
-     * causes it to go out of sync with native. The initialDate prop is intended
-     * to allow you to have native be source of truth.
-     */
-    initialDate: PropTypes.instanceOf(Date),
-
-    /**
-     * Date change handler.
-     *
-     * This is called when the user changes the date or time in the UI.
-     * The first and only argument is an Event. For getting the date the picker
-     * was changed to, use onDateChange instead.
-     */
-    onChange: PropTypes.func,
-
-    /**
-     * Date change handler.
-     *
-     * This is called when the user changes the date or time in the UI.
-     * The first and only argument is a Date object representing the new
-     * date and time.
-     */
-    onDateChange: PropTypes.func.isRequired,
-
-    /**
-     * Maximum date.
-     *
-     * Restricts the range of possible date/time values.
-     */
-    maximumDate: PropTypes.instanceOf(Date),
-
-    /**
-     * Minimum date.
-     *
-     * Restricts the range of possible date/time values.
-     */
-    minimumDate: PropTypes.instanceOf(Date),
-
-    /**
-     * The date picker mode.
-     */
-    mode: PropTypes.oneOf(['date', 'time', 'datetime']),
-
-    /**
-     * The date picker locale.
-     */
-    locale: PropTypes.string,
-
-    /**
-     * The interval at which minutes can be selected.
-     */
-    minuteInterval: PropTypes.oneOf([1, 2, 3, 4, 5, 6, 10, 12, 15, 20, 30]),
-
-    /**
-     * Timezone offset in minutes.
-     *
-     * By default, the date picker will use the device's timezone. With this
-     * parameter, it is possible to force a certain timezone offset. For
-     * instance, to show times in Pacific Standard Time, pass -7 * 60.
-     */
-    timeZoneOffsetInMinutes: PropTypes.number,
-  },
+class DatePickerIOS extends React.Component<Props> {
+  static DefaultProps = {
+    mode: 'datetime',
+  };
 
-  getDefaultProps: function(): DefaultProps {
-    return {
-      mode: 'datetime',
-    };
-  },
+  // $FlowFixMe How to type a native component to be able to call setNativeProps
+  _picker: ?React.ElementRef<typeof RCTDatePickerIOS> = null;
 
-  componentDidUpdate: function() {
+  componentDidUpdate() {
     if (this.props.date) {
       const propsTimeStamp = this.props.date.getTime();
       if (this._picker) {
@@ -148,16 +123,16 @@ const DatePickerIOS = ((createReactClass({
         });
       }
     }
-  },
+  }
 
-  _onChange: function(event: Event) {
+  _onChange = (event: Event) => {
     const nativeTimeStamp = event.nativeEvent.timestamp;
     this.props.onDateChange &&
       this.props.onDateChange(new Date(nativeTimeStamp));
     this.props.onChange && this.props.onChange(event);
-  },
+  };
 
-  render: function() {
+  render() {
     const props = this.props;
     invariant(
       props.date || props.initialDate,
@@ -193,8 +168,8 @@ const DatePickerIOS = ((createReactClass({
         />
       </View>
     );
-  },
-}): any): React.ComponentType<Props>);
+  }
+}
 
 const styles = StyleSheet.create({
   datePickerIOS: {

From 6c910549d8525ce8d190226991ea5c8826dc3b81 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 1 Jun 2018 10:56:28 -0700
Subject: [PATCH 0712/1109] Delete EventDispatcher interface

Reviewed By: achen1

Differential Revision: D8232129

fbshipit-source-id: 6d618b4a587c0b0e1dfac967e8d22c05a62c44ee
---
 .../com/facebook/react/bridge/EventDispatcher.java  | 13 -------------
 1 file changed, 13 deletions(-)
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/bridge/EventDispatcher.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/EventDispatcher.java
deleted file mode 100644
index e596a478258d..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/EventDispatcher.java
+++ /dev/null
@@ -1,13 +0,0 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-package com.facebook.react.bridge;
-
-/**
- * Marker interface for EventDispatcher.
- */
-public interface EventDispatcher {
-}

From 8dc3ba0444c94d9bbb66295b5af885bff9b9cd34 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Fri, 1 Jun 2018 12:37:22 -0700
Subject: [PATCH 0713/1109] RN: Remove Native Prop Validation

Summary:
As we migrate over to static typing solutions for props, we cannot rely on always having `propTypes` available at runtime.

This gets us started on that journey by removing the native prop validation that happens when we require native components.

bypass-lint

Reviewed By: TheSavior

Differential Revision: D7976854

fbshipit-source-id: f3ab579a7f0f8cfb716b0eb7fd4625f8168f3d96
---
 .../ActivityIndicator/ActivityIndicator.js    | 20 ++---
 .../DatePicker/DatePickerIOS.ios.js           |  4 +-
 .../MaskedView/MaskedViewIOS.ios.js           | 10 +--
 .../ProgressViewIOS/ProgressViewIOS.ios.js    |  7 +-
 .../SafeAreaView/SafeAreaView.ios.js          | 10 +--
 Libraries/Components/ScrollView/ScrollView.js | 74 ++++++-------------
 .../SegmentedControlIOS.ios.js                |  7 +-
 Libraries/Components/Slider/Slider.js         | 12 +--
 Libraries/Components/Switch/Switch.js         | 23 ++----
 .../Components/TabBarIOS/TabBarIOS.ios.js     |  4 +-
 Libraries/Components/TextInput/TextInput.js   | 14 ++--
 Libraries/Components/View/View.js             | 29 +-------
 Libraries/Image/Image.ios.js                  |  4 +-
 Libraries/Modal/Modal.js                      |  4 +-
 Libraries/RCTTest/SnapshotViewIOS.ios.js      | 14 ++--
 .../ReactNative/requireNativeComponent.js     | 62 ++++------------
 Libraries/ReactNative/verifyPropTypes.js      | 64 ----------------
 17 files changed, 79 insertions(+), 283 deletions(-)
 delete mode 100644 Libraries/ReactNative/verifyPropTypes.js

diff --git a/Libraries/Components/ActivityIndicator/ActivityIndicator.js b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
index 65809a32300f..f2a648797eb0 100644
--- a/Libraries/Components/ActivityIndicator/ActivityIndicator.js
+++ b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
@@ -11,7 +11,6 @@
 'use strict';
 
 const Platform = require('Platform');
-const ProgressBarAndroid = require('ProgressBarAndroid');
 const React = require('React');
 const StyleSheet = require('StyleSheet');
 const View = require('View');
@@ -21,7 +20,10 @@ const requireNativeComponent = require('requireNativeComponent');
 import type {NativeComponent} from 'ReactNative';
 import type {ViewProps} from 'ViewPropTypes';
 
-let RCTActivityIndicator;
+const RCTActivityIndicator =
+  Platform.OS === 'android'
+    ? require('ProgressBarAndroid')
+    : requireNativeComponent('RCTActivityIndicatorView');
 
 const GRAY = '#999999';
 
@@ -98,11 +100,7 @@ const ActivityIndicator = (
 
   return (
     <View onLayout={onLayout} style={[styles.container, style]}>
-      {Platform.OS === 'ios' ? (
-        <RCTActivityIndicator {...nativeProps} />
-      ) : (
-        <ProgressBarAndroid {...nativeProps} />
-      )}
+      <RCTActivityIndicator {...nativeProps} />
     </View>
   );
 };
@@ -120,14 +118,6 @@ ActivityIndicatorWithRef.defaultProps = {
 };
 ActivityIndicatorWithRef.displayName = 'ActivityIndicator';
 
-if (Platform.OS === 'ios') {
-  RCTActivityIndicator = requireNativeComponent(
-    'RCTActivityIndicatorView',
-    null,
-    {nativeOnly: {activityIndicatorViewStyle: true}},
-  );
-}
-
 const styles = StyleSheet.create({
   container: {
     alignItems: 'center',
diff --git a/Libraries/Components/DatePicker/DatePickerIOS.ios.js b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
index f76902d852b4..1202364665fc 100644
--- a/Libraries/Components/DatePicker/DatePickerIOS.ios.js
+++ b/Libraries/Components/DatePicker/DatePickerIOS.ios.js
@@ -22,6 +22,8 @@ const requireNativeComponent = require('requireNativeComponent');
 
 import type {ViewProps} from 'ViewPropTypes';
 
+const RCTDatePickerIOS = requireNativeComponent('RCTDatePicker');
+
 type Event = Object;
 
 type Props = $ReadOnly<{|
@@ -177,6 +179,4 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTDatePickerIOS = requireNativeComponent('RCTDatePicker');
-
 module.exports = DatePickerIOS;
diff --git a/Libraries/Components/MaskedView/MaskedViewIOS.ios.js b/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
index b0d1ab490a98..c65822a64b2d 100644
--- a/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
+++ b/Libraries/Components/MaskedView/MaskedViewIOS.ios.js
@@ -17,6 +17,8 @@ const requireNativeComponent = require('requireNativeComponent');
 
 import type {ViewProps} from 'ViewPropTypes';
 
+const RCTMaskedView = requireNativeComponent('RCTMaskedView');
+
 type Props = {
   ...ViewProps,
 
@@ -97,12 +99,4 @@ class MaskedViewIOS extends React.Component<Props> {
   }
 }
 
-const RCTMaskedView = requireNativeComponent('RCTMaskedView', {
-  name: 'RCTMaskedView',
-  displayName: 'RCTMaskedView',
-  propTypes: {
-    ...ViewPropTypes,
-  },
-});
-
 module.exports = MaskedViewIOS;
diff --git a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
index a7d6d61e5b5e..ea92fccb9805 100644
--- a/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
+++ b/Libraries/Components/ProgressViewIOS/ProgressViewIOS.ios.js
@@ -25,6 +25,8 @@ import type {ImageSource} from 'ImageSource';
 import type {ColorValue} from 'StyleSheetTypes';
 import type {ViewProps} from 'ViewPropTypes';
 
+const RCTProgressView = requireNativeComponent('RCTProgressView');
+
 type Props = $ReadOnly<{|
   ...ViewProps,
   progressViewStyle?: ?('default' | 'bar'),
@@ -91,11 +93,6 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTProgressView = requireNativeComponent(
-  'RCTProgressView',
-  ProgressViewIOS,
-);
-
 module.exports = ((ProgressViewIOS: any): Class<
   ReactNative.NativeComponent<Props>,
 >);
diff --git a/Libraries/Components/SafeAreaView/SafeAreaView.ios.js b/Libraries/Components/SafeAreaView/SafeAreaView.ios.js
index 65daa32fd754..5fb0406b8d51 100644
--- a/Libraries/Components/SafeAreaView/SafeAreaView.ios.js
+++ b/Libraries/Components/SafeAreaView/SafeAreaView.ios.js
@@ -14,6 +14,8 @@ const requireNativeComponent = require('requireNativeComponent');
 
 import type {ViewProps} from 'ViewPropTypes';
 
+const RCTSafeAreaView = requireNativeComponent('RCTSafeAreaView');
+
 type Props = ViewProps & {
   children: any,
 };
@@ -34,12 +36,4 @@ class SafeAreaView extends React.Component<Props> {
   }
 }
 
-const RCTSafeAreaView = requireNativeComponent('RCTSafeAreaView', {
-  name: 'RCTSafeAreaView',
-  displayName: 'RCTSafeAreaView',
-  propTypes: {
-    ...ViewPropTypes,
-  },
-});
-
 module.exports = SafeAreaView;
diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 4b1b76848c7a..6e9e40d60e73 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -45,6 +45,28 @@ import type {PointProp} from 'PointPropType';
 
 import type {ColorValue} from 'StyleSheetTypes';
 
+let AndroidScrollView;
+let AndroidHorizontalScrollContentView;
+let AndroidHorizontalScrollView;
+let RCTScrollView;
+let RCTScrollContentView;
+
+if (Platform.OS === 'android') {
+  AndroidScrollView = requireNativeComponent('RCTScrollView');
+  AndroidHorizontalScrollView = requireNativeComponent(
+    'AndroidHorizontalScrollView',
+  );
+  AndroidHorizontalScrollContentView = requireNativeComponent(
+    'AndroidHorizontalScrollContentView',
+  );
+} else if (Platform.OS === 'ios') {
+  RCTScrollView = requireNativeComponent('RCTScrollView');
+  RCTScrollContentView = requireNativeComponent('RCTScrollContentView');
+} else {
+  RCTScrollView = requireNativeComponent('RCTScrollView');
+  RCTScrollContentView = requireNativeComponent('RCTScrollContentView');
+}
+
 type TouchableProps = $ReadOnly<{|
   onTouchStart?: (event: PressEvent) => void,
   onTouchMove?: (event: PressEvent) => void,
@@ -1074,56 +1096,4 @@ const styles = StyleSheet.create({
   },
 });
 
-let nativeOnlyProps,
-  AndroidScrollView,
-  AndroidHorizontalScrollContentView,
-  AndroidHorizontalScrollView,
-  RCTScrollView,
-  RCTScrollContentView;
-if (Platform.OS === 'android') {
-  nativeOnlyProps = {
-    nativeOnly: {
-      sendMomentumEvents: true,
-    },
-  };
-  AndroidScrollView = requireNativeComponent(
-    'RCTScrollView',
-    (ScrollView: React.ComponentType<any>),
-    nativeOnlyProps,
-  );
-  AndroidHorizontalScrollView = requireNativeComponent(
-    'AndroidHorizontalScrollView',
-    (ScrollView: React.ComponentType<any>),
-    nativeOnlyProps,
-  );
-  AndroidHorizontalScrollContentView = requireNativeComponent(
-    'AndroidHorizontalScrollContentView',
-  );
-} else if (Platform.OS === 'ios') {
-  nativeOnlyProps = {
-    nativeOnly: {
-      onMomentumScrollBegin: true,
-      onMomentumScrollEnd: true,
-      onScrollBeginDrag: true,
-      onScrollEndDrag: true,
-    },
-  };
-  RCTScrollView = requireNativeComponent(
-    'RCTScrollView',
-    (ScrollView: React.ComponentType<any>),
-    nativeOnlyProps,
-  );
-  RCTScrollContentView = requireNativeComponent('RCTScrollContentView', View);
-} else {
-  nativeOnlyProps = {
-    nativeOnly: {},
-  };
-  RCTScrollView = requireNativeComponent(
-    'RCTScrollView',
-    null,
-    nativeOnlyProps,
-  );
-  RCTScrollContentView = requireNativeComponent('RCTScrollContentView', View);
-}
-
 module.exports = TypedScrollView;
diff --git a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
index f0a407245041..b4635f13f8e4 100644
--- a/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
+++ b/Libraries/Components/SegmentedControlIOS/SegmentedControlIOS.ios.js
@@ -22,6 +22,8 @@ const requireNativeComponent = require('requireNativeComponent');
 
 import type {ViewProps} from 'ViewPropTypes';
 
+const RCTSegmentedControl = requireNativeComponent('RCTSegmentedControl');
+
 type DefaultProps = {
   values: $ReadOnlyArray<string>,
   enabled: boolean,
@@ -139,11 +141,6 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTSegmentedControl = requireNativeComponent(
-  'RCTSegmentedControl',
-  SegmentedControlIOS,
-);
-
 module.exports = ((SegmentedControlIOS: any): Class<
   ReactNative.NativeComponent<Props>,
 >);
diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index 4c4c0b979028..efe22529f287 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -29,6 +29,8 @@ import type {ViewStyleProp} from 'StyleSheet';
 import type {ColorValue} from 'StyleSheetTypes';
 import type {ViewProps} from 'ViewPropTypes';
 
+const RCTSlider = requireNativeComponent('RCTSlider');
+
 type Event = Object;
 
 type IOSProps = $ReadOnly<{|
@@ -306,14 +308,4 @@ if (Platform.OS === 'ios') {
   });
 }
 
-let options = {};
-if (Platform.OS === 'android') {
-  options = {
-    nativeOnly: {
-      enabled: true,
-    },
-  };
-}
-const RCTSlider = requireNativeComponent('RCTSlider', Slider, options);
-
 module.exports = ((Slider: any): Class<ReactNative.NativeComponent<Props>>);
diff --git a/Libraries/Components/Switch/Switch.js b/Libraries/Components/Switch/Switch.js
index 1730e7cbf019..c2288d25c673 100644
--- a/Libraries/Components/Switch/Switch.js
+++ b/Libraries/Components/Switch/Switch.js
@@ -25,6 +25,11 @@ const requireNativeComponent = require('requireNativeComponent');
 import type {ColorValue} from 'StyleSheetTypes';
 import type {ViewProps} from 'ViewPropTypes';
 
+const RCTSwitch =
+  Platform.OS === 'android'
+    ? requireNativeComponent('AndroidSwitch')
+    : requireNativeComponent('RCTSwitch');
+
 type DefaultProps = $ReadOnly<{|
   value: boolean,
   disabled: boolean,
@@ -40,6 +45,7 @@ type Props = $ReadOnly<{|
   onTintColor?: ?ColorValue,
   thumbTintColor?: ?ColorValue,
 |}>;
+
 /**
  * Renders a boolean input.
  *
@@ -158,21 +164,4 @@ const styles = StyleSheet.create({
   },
 });
 
-if (Platform.OS === 'android') {
-  var RCTSwitch = requireNativeComponent('AndroidSwitch', Switch, {
-    nativeOnly: {
-      onChange: true,
-      on: true,
-      enabled: true,
-      trackTintColor: true,
-    },
-  });
-} else {
-  var RCTSwitch = requireNativeComponent('RCTSwitch', Switch, {
-    nativeOnly: {
-      onChange: true,
-    },
-  });
-}
-
 module.exports = ((Switch: any): Class<ReactNative.NativeComponent<Props>>);
diff --git a/Libraries/Components/TabBarIOS/TabBarIOS.ios.js b/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
index 42d6cb238e90..6cbe213f7fc3 100644
--- a/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
+++ b/Libraries/Components/TabBarIOS/TabBarIOS.ios.js
@@ -22,6 +22,8 @@ const requireNativeComponent = require('requireNativeComponent');
 import type {DangerouslyImpreciseStyleProp} from 'StyleSheet';
 import type {ViewProps} from 'ViewPropTypes';
 
+const RCTTabBar = requireNativeComponent('RCTTabBar');
+
 type Props = $ReadOnly<{|
   ...ViewProps,
   style?: DangerouslyImpreciseStyleProp,
@@ -102,6 +104,4 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTTabBar = requireNativeComponent('RCTTabBar', TabBarIOS);
-
 module.exports = TabBarIOS;
diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index 7909b5a8fae5..c08033e8d43f 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -40,24 +40,22 @@ let AndroidTextInput;
 let RCTMultilineTextInputView;
 let RCTSinglelineTextInputView;
 
-const onlyMultiline = {
-  onTextInput: true,
-  children: true,
-};
-
 if (Platform.OS === 'android') {
-  AndroidTextInput = requireNativeComponent('AndroidTextInput', null);
+  AndroidTextInput = requireNativeComponent('AndroidTextInput');
 } else if (Platform.OS === 'ios') {
   RCTMultilineTextInputView = requireNativeComponent(
     'RCTMultilineTextInputView',
-    null,
   );
   RCTSinglelineTextInputView = requireNativeComponent(
     'RCTSinglelineTextInputView',
-    null,
   );
 }
 
+const onlyMultiline = {
+  onTextInput: true,
+  children: true,
+};
+
 type Event = Object;
 type Selection = {
   start: number,
diff --git a/Libraries/Components/View/View.js b/Libraries/Components/View/View.js
index 5e1b6bdb57ab..c494643c4740 100644
--- a/Libraries/Components/View/View.js
+++ b/Libraries/Components/View/View.js
@@ -10,11 +10,8 @@
 
 'use strict';
 
-const Platform = require('Platform');
 const React = require('React');
-const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
 const TextAncestor = require('TextAncestor');
-const ViewPropTypes = require('ViewPropTypes');
 
 const invariant = require('fbjs/lib/invariant');
 const requireNativeComponent = require('requireNativeComponent');
@@ -31,31 +28,7 @@ export type Props = ViewProps;
  *
  * @see http://facebook.github.io/react-native/docs/view.html
  */
-const RCTView = requireNativeComponent(
-  'RCTView',
-  {
-    propTypes: ViewPropTypes,
-  },
-  {
-    nativeOnly: {
-      nativeBackgroundAndroid: true,
-      nativeForegroundAndroid: true,
-    },
-  },
-);
-
-if (__DEV__) {
-  const UIManager = require('UIManager');
-  const viewConfig =
-    (UIManager.viewConfigs && UIManager.viewConfigs.RCTView) || {};
-  for (const prop in viewConfig.nativeProps) {
-    if (!ViewPropTypes[prop] && !ReactNativeStyleAttributes[prop]) {
-      throw new Error(
-        'View is missing propType for native prop `' + prop + '`',
-      );
-    }
-  }
-}
+const RCTView = requireNativeComponent('RCTView');
 
 let ViewToExport = RCTView;
 if (__DEV__) {
diff --git a/Libraries/Image/Image.ios.js b/Libraries/Image/Image.ios.js
index 86a5525374fe..e3f153242df8 100644
--- a/Libraries/Image/Image.ios.js
+++ b/Libraries/Image/Image.ios.js
@@ -23,6 +23,8 @@ const resolveAssetSource = require('resolveAssetSource');
 
 const ImageViewManager = NativeModules.ImageViewManager;
 
+const RCTImageView = requireNativeComponent('RCTImageView');
+
 /**
  * A React component for displaying different types of images,
  * including network images, static resources, temporary local images, and
@@ -139,6 +141,4 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTImageView = requireNativeComponent('RCTImageView', Image);
-
 module.exports = Image;
diff --git a/Libraries/Modal/Modal.js b/Libraries/Modal/Modal.js
index d414a288fee3..fcc3900da443 100644
--- a/Libraries/Modal/Modal.js
+++ b/Libraries/Modal/Modal.js
@@ -22,7 +22,9 @@ const View = require('View');
 
 const deprecatedPropType = require('deprecatedPropType');
 const requireNativeComponent = require('requireNativeComponent');
-const RCTModalHostView = requireNativeComponent('RCTModalHostView', null);
+
+const RCTModalHostView = requireNativeComponent('RCTModalHostView');
+
 const ModalEventEmitter =
   Platform.OS === 'ios' && NativeModules.ModalManager
     ? new NativeEventEmitter(NativeModules.ModalManager)
diff --git a/Libraries/RCTTest/SnapshotViewIOS.ios.js b/Libraries/RCTTest/SnapshotViewIOS.ios.js
index f2a53511bc1b..9fbc70302cf4 100644
--- a/Libraries/RCTTest/SnapshotViewIOS.ios.js
+++ b/Libraries/RCTTest/SnapshotViewIOS.ios.js
@@ -21,6 +21,13 @@ const ViewPropTypes = require('ViewPropTypes');
 
 const requireNativeComponent = require('requireNativeComponent');
 
+// Verify that RCTSnapshot is part of the UIManager since it is only loaded
+// if you have linked against RCTTest like in tests, otherwise we will have
+// a warning printed out
+const RCTSnapshot = UIManager.RCTSnapshot
+  ? requireNativeComponent('RCTSnapshot')
+  : View;
+
 class SnapshotViewIOS extends React.Component<{
   onSnapshotReady?: Function,
   testIdentifier?: string,
@@ -59,11 +66,4 @@ const style = StyleSheet.create({
   },
 });
 
-// Verify that RCTSnapshot is part of the UIManager since it is only loaded
-// if you have linked against RCTTest like in tests, otherwise we will have
-// a warning printed out
-const RCTSnapshot = UIManager.RCTSnapshot
-  ? requireNativeComponent('RCTSnapshot', SnapshotViewIOS)
-  : View;
-
 module.exports = SnapshotViewIOS;
diff --git a/Libraries/ReactNative/requireNativeComponent.js b/Libraries/ReactNative/requireNativeComponent.js
index c6f2a35d352a..dce6a900bb00 100644
--- a/Libraries/ReactNative/requireNativeComponent.js
+++ b/Libraries/ReactNative/requireNativeComponent.js
@@ -10,7 +10,6 @@
 
 'use strict';
 
-const Platform = require('Platform');
 const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
 const UIManager = require('UIManager');
 
@@ -21,51 +20,25 @@ const pointsDiffer = require('pointsDiffer');
 const processColor = require('processColor');
 const resolveAssetSource = require('resolveAssetSource');
 const sizesDiffer = require('sizesDiffer');
-const verifyPropTypes = require('verifyPropTypes');
 const invariant = require('fbjs/lib/invariant');
 const warning = require('fbjs/lib/warning');
 
-type ComponentInterface =
-  | React$ComponentType<any>
-  | $ReadOnly<{
-      propTypes?: $ReadOnly<{
-        [propName: string]: mixed,
-      }>,
-    }>;
-
-type ExtraOptions = $ReadOnly<{|
-  nativeOnly?: $ReadOnly<{
-    [propName: string]: boolean,
-  }>,
-|}>;
-
 /**
- * Used to create React components that directly wrap native component
- * implementations.  Config information is extracted from data exported from the
- * UIManager module.  You should also wrap the native component in a
- * hand-written component with full propTypes definitions and other
- * documentation - pass the hand-written component in as `componentInterface` to
- * verify all the native props are documented via `propTypes`.
+ * Creates values that can be used like React components which represent native
+ * view managers. You should create JavaScript modules that wrap these values so
+ * that the results are memoized. Example:
  *
- * If some native props shouldn't be exposed in the wrapper interface, you can
- * pass null for `componentInterface` and call `verifyPropTypes` directly
- * with `nativePropsToIgnore`;
+ *   const View = requireNativeComponent('RCTView');
  *
- * Common types are lined up with the appropriate prop differs with
- * `TypeToDifferMap`.  Non-scalar types not in the map default to `deepDiffer`.
  */
-const requireNativeComponent = (
-  viewName: string,
-  componentInterface?: ?ComponentInterface,
-  extraConfig?: ?ExtraOptions,
-): string =>
-  createReactNativeComponentClass(viewName, () => {
-    const viewConfig = UIManager[viewName];
+const requireNativeComponent = (uiViewClassName: string): string =>
+  createReactNativeComponentClass(uiViewClassName, () => {
+    const viewConfig = UIManager[uiViewClassName];
 
     invariant(
       viewConfig != null && viewConfig.NativeProps != null,
       'requireNativeComponent: "%s" was not found in the UIManager.',
-      viewName,
+      uiViewClassName,
     );
 
     // TODO: This seems like a whole lot of runtime initialization for every
@@ -94,14 +67,14 @@ const requireNativeComponent = (
       }
     }
 
-    const viewAttributes = {};
+    const validAttributes = {};
 
     for (const key in nativeProps) {
       const typeName = nativeProps[key];
       const diff = getDifferForType(typeName);
       const process = getProcessorForType(typeName);
 
-      viewAttributes[key] =
+      validAttributes[key] =
         diff == null && process == null ? true : {diff, process};
     }
 
@@ -109,24 +82,15 @@ const requireNativeComponent = (
     // props. This makes it so we allow style properties in the `style` prop.
     // TODO: Move style properties into a `style` prop and disallow them as
     // top-level props on the native side.
-    viewAttributes.style = ReactNativeStyleAttributes;
+    validAttributes.style = ReactNativeStyleAttributes;
 
     Object.assign(viewConfig, {
-      uiViewClassName: viewName,
-      validAttributes: viewAttributes,
-      propTypes:
-        componentInterface == null ? null : componentInterface.propTypes,
+      uiViewClassName,
+      validAttributes,
       bubblingEventTypes,
       directEventTypes,
     });
 
-    if (__DEV__) {
-      verifyPropTypes(
-        viewConfig,
-        extraConfig == null ? null : extraConfig.nativeOnly,
-      );
-    }
-
     if (!hasAttachedDefaultEventTypes) {
       attachDefaultEventTypes(viewConfig);
       hasAttachedDefaultEventTypes = true;
diff --git a/Libraries/ReactNative/verifyPropTypes.js b/Libraries/ReactNative/verifyPropTypes.js
deleted file mode 100644
index 6193b1ac1c03..000000000000
--- a/Libraries/ReactNative/verifyPropTypes.js
+++ /dev/null
@@ -1,64 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- * @flow
- */
-
-'use strict';
-
-const ReactNativeStyleAttributes = require('ReactNativeStyleAttributes');
-
-function verifyPropTypes(
-  viewConfig: $ReadOnly<{
-    NativeProps: $ReadOnly<{
-      [propName: string]: mixed,
-    }>,
-    propTypes: ?$ReadOnly<{
-      [propName: string]: mixed,
-    }>,
-    uiViewClassName: string,
-  }>,
-  nativePropsToIgnore: ?$ReadOnly<{
-    [propName: string]: boolean,
-  }>,
-) {
-  const {NativeProps, propTypes, uiViewClassName} = viewConfig;
-
-  if (propTypes == null) {
-    return;
-  }
-
-  for (const propName in NativeProps) {
-    if (
-      propTypes[propName] ||
-      ReactNativeStyleAttributes[propName] ||
-      (nativePropsToIgnore && nativePropsToIgnore[propName])
-    ) {
-      continue;
-    }
-    const prettyName = `${uiViewClassName}.${propName}`;
-    const nativeType = String(NativeProps[propName]);
-    const suggestion =
-      '\n\nIf you have not changed this prop yourself, this usually means ' +
-      'that the versions of your native and JavaScript code are out of sync. ' +
-      'Updating both should make this error go away.';
-
-    if (propTypes.hasOwnProperty(propName)) {
-      console.error(
-        `Invalid propType to configure \`${prettyName}\` (${nativeType}).` +
-          suggestion,
-      );
-    } else {
-      console.error(
-        `Missing a propType to configure \`${prettyName}\` (${nativeType}).` +
-          suggestion,
-      );
-    }
-  }
-}
-
-module.exports = verifyPropTypes;

From 1324e7b5580db815471172cf6dd140124bd2f11a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Fri, 1 Jun 2018 13:31:13 -0700
Subject: [PATCH 0714/1109] Bump to BUCK v2018.03.26.01

Summary:
Bumps CI to latest BUCK release.

Test Plan
---------

Run on Circle CI.

Release Notes
-------------

[INTERNAL] [MINOR] [Tests] - Bump to BUCK v2018.03.26.01
Closes https://github.com/facebook/react-native/pull/19535

Differential Revision: D8240382

Pulled By: hramos

fbshipit-source-id: 60812cc90542201b362ef264083dd79dbf5d9360
---
 .circleci/config.yml                  | 6 +++---
 ContainerShip/Dockerfile.android-base | 2 +-
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 7e694fb89695..5f720a8d32fb 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -67,12 +67,12 @@ aliases:
 
   - &restore-cache-buck
     keys:
-      - v3-buck-{{ arch }}-v2018.02.16.01
+      - v3-buck-{{ arch }}-v2018.03.26.01
   - &save-cache-buck
     paths:
       - ~/buck
       - ~/okbuck
-    key: v3-buck-{{ arch }}-v2018.02.16.01
+    key: v3-buck-{{ arch }}-v2018.03.26.01
 
   - &restore-cache-watchman
     keys:
@@ -140,7 +140,7 @@ aliases:
     name: Install BUCK
     command: |
       if [[ ! -e ~/buck ]]; then
-        git clone https://github.com/facebook/buck.git ~/buck --branch v2018.02.16.01 --depth=1
+        git clone https://github.com/facebook/buck.git ~/buck --branch v2018.03.26.01 --depth=1
       fi
       cd ~/buck && ant
       buck --version
diff --git a/ContainerShip/Dockerfile.android-base b/ContainerShip/Dockerfile.android-base
index c9eb8e4c0230..b630b396e959 100644
--- a/ContainerShip/Dockerfile.android-base
+++ b/ContainerShip/Dockerfile.android-base
@@ -20,7 +20,7 @@ LABEL maintainer="Héctor Ramos <hector@fb.com>"
 ARG SDK_VERSION=sdk-tools-linux-3859397.zip
 ARG ANDROID_BUILD_VERSION=26
 ARG ANDROID_TOOLS_VERSION=26.0.3
-ARG BUCK_VERSION=v2018.02.16.01
+ARG BUCK_VERSION=v2018.03.26.01
 ARG NDK_VERSION=10e
 ARG NODE_VERSION=8.10.0
 ARG WATCHMAN_VERSION=4.9.0

From 83c990b25c6636c8855fea15aa48be9dc7d3effd Mon Sep 17 00:00:00 2001
From: Marc Horowitz <mhorowitz@fb.com>
Date: Fri, 1 Jun 2018 14:55:56 -0700
Subject: [PATCH 0715/1109] make logMarker visible for consistency with
 logTaggedMarker

Differential Revision: D8240294

fbshipit-source-id: 8d056dc89adff41ff43c0df2f752b01ac1fb189f
---
 ReactCommon/cxxreact/ReactMarker.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/cxxreact/ReactMarker.h b/ReactCommon/cxxreact/ReactMarker.h
index ae176b78867a..3a71579ab8f0 100644
--- a/ReactCommon/cxxreact/ReactMarker.h
+++ b/ReactCommon/cxxreact/ReactMarker.h
@@ -37,7 +37,7 @@ typedef void(*LogTaggedMarker)(const ReactMarkerId, const char* tag);
 
 extern RN_EXPORT LogTaggedMarker logTaggedMarker;
 
-extern void logMarker(const ReactMarkerId markerId);
+extern RN_EXPORT void logMarker(const ReactMarkerId markerId);
 
 }
 }

From 0964135a178b459e06b44a49a4ecb0dd6c5bec9b Mon Sep 17 00:00:00 2001
From: Sho Ikeda <suicaicoca@gmail.com>
Date: Fri, 1 Jun 2018 15:56:49 -0700
Subject: [PATCH 0716/1109] react-native-xcode.sh: Support Homebrew-installed
 nodenv

Summary:
As well as nvm.

https://github.com/facebook/react-native/blob/9d315f4a1e7b0c9cd80a51903db0b1b561b19e33/scripts/react-native-xcode.sh#L56-L60

Build React Native iOS app with Release configuration and run the script using `node` command which is installed through Homebrew-installed `nodenv` and `node-build`.

None.

[IOS] [ENHANCEMENT] [scripts/react-native-xcode.sh] - Support Homebrew-installed nodenv
Closes https://github.com/facebook/react-native/pull/19509

Differential Revision: D8243181

Pulled By: hramos

fbshipit-source-id: fbd75f377f4aebf89ce35b96a47c59238e62e9ce
---
 scripts/react-native-xcode.sh | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/scripts/react-native-xcode.sh b/scripts/react-native-xcode.sh
index 1e2597412762..7194c2a1856c 100755
--- a/scripts/react-native-xcode.sh
+++ b/scripts/react-native-xcode.sh
@@ -62,6 +62,8 @@ fi
 # Set up the nodenv node version manager if present
 if [[ -x "$HOME/.nodenv/bin/nodenv" ]]; then
   eval "$("$HOME/.nodenv/bin/nodenv" init -)"
+elif [[ -x "$(command -v brew)" && -x "$(brew --prefix nodenv)/bin/nodenv" ]]; then
+  eval "$("$(brew --prefix nodenv)/bin/nodenv" init -)"
 fi
 
 [ -z "$NODE_BINARY" ] && export NODE_BINARY="node"

From b2b2caa3444db4d21566ef918add7235f709538d Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 1 Jun 2018 17:01:42 -0700
Subject: [PATCH 0717/1109] Low the priority for logging events in fabric

Reviewed By: achen1

Differential Revision: D8238957

fbshipit-source-id: f2e8bd941ac68ead4c5ed7cadfcf83a753e44cab
---
 .../main/java/com/facebook/react/fabric/FabricUIManager.java  | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 10a187108ebd..d6d730bf8c9a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -487,7 +487,7 @@ public long createEventTarget(int reactTag) {
     long context = mJSContext.get();
     long eventTarget = mBinding.createEventTarget(context, instanceHandle);
     if (DEBUG) {
-      Log.e(
+      Log.d(
         TAG,
         "Created EventTarget: " + eventTarget + " for tag: " + reactTag + " with instanceHandle: " + instanceHandle);
     }
@@ -509,7 +509,7 @@ public void releaseEventHandler(long eventHandlerPointer) {
   @Override
   public void invoke(long eventTarget, String name, WritableMap params) {
     if (DEBUG) {
-      Log.e(
+      Log.d(
         TAG,
         "Dispatching event for target: " + eventTarget);
     }

From d29821278e435255a2cbe1f2c59ff31ec16d2854 Mon Sep 17 00:00:00 2001
From: Sokovikov <skv-headless@yandex.ru>
Date: Fri, 1 Jun 2018 17:21:28 -0700
Subject: [PATCH 0718/1109] better place for dismiss all button

Summary:
This pr makes a little bit simpler to dismiss all warnings (1 click instead of 2)
Sometimes you don't want to use `YellowBox.ignoreWarnings` to remember.

RNTester sceenshot:

<img width="322" alt="screen shot 2018-05-30 at 09 51 25" src="https://user-images.githubusercontent.com/1488195/40701475-1142506a-63ef-11e8-8fc9-ea1696d9cb65.png">
Or RNTester -> Native Animation Example -> Force JS Stalls (in the end of the list) also cause warning to test.

[GENERAL][ENHANCEMENT][YellowBox] - Move `Dismiss All` yellow box button to another place which makes a little bit simpler to dismiss warnings.
Closes https://github.com/facebook/react-native/pull/19501

Differential Revision: D8243823

Pulled By: hramos

fbshipit-source-id: 31887469cddb4adfd7b889ae0c29a3bf41e87b7b
---
 Libraries/ReactNative/YellowBox.js | 31 +++++++++++++++++++++---------
 1 file changed, 22 insertions(+), 9 deletions(-)

diff --git a/Libraries/ReactNative/YellowBox.js b/Libraries/ReactNative/YellowBox.js
index f25de5a2a60c..f1e756a8a4c4 100644
--- a/Libraries/ReactNative/YellowBox.js
+++ b/Libraries/ReactNative/YellowBox.js
@@ -247,7 +247,6 @@ const WarningInspector = ({
   warning,
   stacktraceVisible,
   onDismiss,
-  onDismissAll,
   onMinimize,
   toggleStacktrace,
 }) => {
@@ -301,13 +300,6 @@ const WarningInspector = ({
             underlayColor="transparent">
             <Text style={styles.inspectorButtonText}>Dismiss</Text>
           </TouchableHighlight>
-          <TouchableHighlight
-            activeOpacity={0.5}
-            onPress={onDismissAll}
-            style={styles.inspectorButton}
-            underlayColor="transparent">
-            <Text style={styles.inspectorButtonText}>Dismiss All</Text>
-          </TouchableHighlight>
         </View>
       </SafeAreaView>
     </View>
@@ -392,6 +384,8 @@ class YellowBox extends React.Component<
     }
     const ScrollView = require('ScrollView');
     const View = require('View');
+    const Text = require('Text');
+    const TouchableHighlight = require('TouchableHighlight');
 
     const {inspecting, stacktraceVisible} = this.state;
     const inspector =
@@ -401,7 +395,6 @@ class YellowBox extends React.Component<
           warning={inspecting}
           stacktraceVisible={stacktraceVisible}
           onDismiss={() => this.dismissWarning(inspecting)}
-          onDismissAll={() => this.dismissWarning(null)}
           onMinimize={() => this.setState({inspecting: null})}
           toggleStacktrace={() =>
             this.setState({stacktraceVisible: !stacktraceVisible})
@@ -431,6 +424,13 @@ class YellowBox extends React.Component<
     ];
     return (
       <View style={inspector ? styles.fullScreen : listStyle}>
+        {!inspector && (
+          <TouchableHighlight
+            style={styles.dismissAllContainer}
+            onPress={() => this.dismissWarning(null)}>
+            <Text style={styles.dismissAll}>Dismiss All</Text>
+          </TouchableHighlight>
+        )}
         <ScrollView style={listStyle} scrollsToTop={false}>
           {rows}
         </ScrollView>
@@ -535,6 +535,19 @@ const styles = StyleSheet.create({
     marginLeft: 15,
     marginRight: 15,
   },
+  dismissAllContainer: {
+    height: 20,
+    justifyContent: 'center',
+    marginTop: -30,
+    marginRight: 5,
+    backgroundColor: backgroundColor(0.95),
+    alignSelf: 'flex-end',
+    paddingHorizontal: 10,
+    borderRadius: 10,
+  },
+  dismissAll: {
+    color: 'white',
+  },
 });
 
 module.exports = YellowBox;

From e0db8ee645a237b96d7d0d8a20bf8ae70cbee04c Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 1 Jun 2018 17:46:01 -0700
Subject: [PATCH 0719/1109] Slider remove $FlowFixMe

Reviewed By: sahrens

Differential Revision: D8234803

fbshipit-source-id: cfc0466a54f3c219d8a2eadfebf840399a2abdd8
---
 Libraries/Components/Slider/Slider.js | 40 ++++++++++++---------------
 1 file changed, 17 insertions(+), 23 deletions(-)

diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index efe22529f287..e1de6b3c3886 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -249,17 +249,10 @@ const Slider = createReactClass({
   },
 
   render: function() {
-    const {style, onValueChange, onSlidingComplete, ...props} = this.props;
-    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error found when Flow v0.54 was deployed. To see the error
-     * delete this comment and run Flow. */
-    props.style = [styles.slider, style];
-
-    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error found when Flow v0.54 was deployed. To see the error
-     * delete this comment and run Flow. */
-    props.onValueChange =
-      onValueChange &&
+    const style = StyleSheet.compose(styles.slider, this.props.style);
+
+    const onValueChange =
+      this.props.onValueChange &&
       ((event: Event) => {
         let userEvent = true;
         if (Platform.OS === 'android') {
@@ -267,26 +260,27 @@ const Slider = createReactClass({
           // dragging the slider.
           userEvent = event.nativeEvent.fromUser;
         }
-        onValueChange && userEvent && onValueChange(event.nativeEvent.value);
+        this.props.onValueChange &&
+          userEvent &&
+          this.props.onValueChange(event.nativeEvent.value);
       });
 
-    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error found when Flow v0.54 was deployed. To see the error
-     * delete this comment and run Flow. */
-    props.onChange = props.onValueChange;
+    const onChange = this.props.onValueChange;
 
-    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error found when Flow v0.54 was deployed. To see the error
-     * delete this comment and run Flow. */
-    props.onSlidingComplete =
-      onSlidingComplete &&
+    const onSlidingComplete =
+      this.props.onSlidingComplete &&
       ((event: Event) => {
-        onSlidingComplete && onSlidingComplete(event.nativeEvent.value);
+        this.props.onSlidingComplete &&
+          this.props.onSlidingComplete(event.nativeEvent.value);
       });
 
     return (
       <RCTSlider
-        {...props}
+        {...this.props}
+        style={style}
+        onChange={onChange}
+        onSlidingComplete={onSlidingComplete}
+        onValueChange={onValueChange}
         enabled={!this.props.disabled}
         onStartShouldSetResponder={() => true}
         onResponderTerminationRequest={() => false}

From 6c989fe7c68164c6cd65a8dfbcc609e55b98a6f5 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 1 Jun 2018 17:47:34 -0700
Subject: [PATCH 0720/1109] refactor JSI module initialization

Reviewed By: fkgozali

Differential Revision: D8111636

fbshipit-source-id: 6e32703b077144962519485002adff8c9f6084ad
---
 .../react/testing/ReactAppTestActivity.java   | 57 +++++++++++--------
 .../facebook/react/ReactInstanceManager.java  | 12 ++--
 .../react/ReactInstanceManagerBuilder.java    | 12 ++--
 .../com/facebook/react/ReactNativeHost.java   |  7 +--
 .../react/bridge/CatalystInstance.java        |  2 +-
 .../react/bridge/CatalystInstanceImpl.java    |  2 +-
 .../react/bridge/JSIModuleHolder.java         | 23 ++++++--
 .../react/bridge/JSIModulePackage.java        | 15 +++++
 .../react/bridge/JSIModuleProvider.java       |  7 +++
 .../react/bridge/JSIModuleRegistry.java       | 27 +++------
 .../facebook/react/bridge/JSIModuleSpec.java  | 12 ++++
 .../react/bridge/JSIModulesProvider.java      | 15 -----
 12 files changed, 109 insertions(+), 82 deletions(-)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModulePackage.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleProvider.java
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleSpec.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModulesProvider.java

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index ddaae9d17e50..f01d74e1fef5 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -21,8 +21,9 @@
 import com.facebook.react.ReactInstanceManagerBuilder;
 import com.facebook.react.ReactRootView;
 import com.facebook.react.bridge.JSIModule;
-import com.facebook.react.bridge.JSIModuleHolder;
-import com.facebook.react.bridge.JSIModulesProvider;
+import com.facebook.react.bridge.JSIModulePackage;
+import com.facebook.react.bridge.JSIModuleProvider;
+import com.facebook.react.bridge.JSIModuleSpec;
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReactContext;
@@ -244,29 +245,35 @@ public void loadBundle(
         .setUseDeveloperSupport(useDevSupport)
         .setBridgeIdleDebugListener(mBridgeIdleSignaler)
         .setInitialLifecycleState(mLifecycleState)
-        .setJSIModulesProvider(
-          new JSIModulesProvider() {
-            @Override
-            public List<JSIModuleHolder> getJSIModules(
-              final ReactApplicationContext reactApplicationContext,
-              final JavaScriptContextHolder jsContext) {
-              return Arrays.<JSIModuleHolder>asList(new JSIModuleHolder() {
-                @Override
-                public Class<? extends JSIModule> getJSIModuleClass() {
-                  return UIManager.class;
-                }
-
-                @Override
-                public FabricUIManager getJSIModule() {
-                  List<ViewManager> viewManagers =
-                    mReactInstanceManager.getOrCreateViewManagers(reactApplicationContext);
-                  FabricUIManager fabricUIManager =
-                    new FabricUIManager(reactApplicationContext, new ViewManagerRegistry(viewManagers), jsContext);
-                  new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
-                  return fabricUIManager;
-                }
-              });
-            }})
+        .setJSIModulesPackage(
+            new JSIModulePackage() {
+              @Override
+              public List<JSIModuleSpec> getJSIModules(
+                  final ReactApplicationContext reactApplicationContext,
+                  final JavaScriptContextHolder jsContext) {
+                return Arrays.<JSIModuleSpec>asList(
+                  new JSIModuleSpec() {
+                    @Override
+                    public Class<? extends JSIModule> getJSIModuleClass() {
+                      return UIManager.class;
+                    }
+
+                    @Override
+                    public JSIModuleProvider getJSIModuleProvider() {
+                      return new JSIModuleProvider() {
+                        @Override
+                        public FabricUIManager get() {
+                          List<ViewManager> viewManagers =
+                            mReactInstanceManager.getOrCreateViewManagers(reactApplicationContext);
+                          FabricUIManager fabricUIManager =
+                            new FabricUIManager(reactApplicationContext, new ViewManagerRegistry(viewManagers), jsContext);
+                          new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
+                          return fabricUIManager;
+                        }
+                      };
+                    }
+                  });
+              }})
         .setUIImplementationProvider(uiImplementationProvider);
 
     final CountDownLatch latch = new CountDownLatch(1);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 661f0d6914d7..35c188eb707a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -47,7 +47,7 @@
 import com.facebook.react.bridge.CatalystInstance;
 import com.facebook.react.bridge.CatalystInstanceImpl;
 import com.facebook.react.bridge.JSBundleLoader;
-import com.facebook.react.bridge.JSIModulesProvider;
+import com.facebook.react.bridge.JSIModulePackage;
 import com.facebook.react.bridge.JavaJSExecutor;
 import com.facebook.react.bridge.JavaScriptExecutor;
 import com.facebook.react.bridge.JavaScriptExecutorFactory;
@@ -159,7 +159,7 @@ public interface ReactInstanceEventListener {
   private final MemoryPressureRouter mMemoryPressureRouter;
   private final @Nullable NativeModuleCallExceptionHandler mNativeModuleCallExceptionHandler;
   private final boolean mLazyNativeModulesEnabled;
-  private final @Nullable JSIModulesProvider mJSIModulesProvider;
+  private final @Nullable JSIModulePackage mJSIModulePackage;
   private List<ViewManager> mViewManagers;
 
   private class ReactContextInitParams {
@@ -208,7 +208,7 @@ public static ReactInstanceManagerBuilder builder() {
     @Nullable DevBundleDownloadListener devBundleDownloadListener,
     int minNumShakes,
     int minTimeLeftInFrameForNonBatchedOperationMs,
-    @Nullable JSIModulesProvider jsiModulesProvider) {
+    @Nullable JSIModulePackage jsiModulePackage) {
     Log.d(ReactConstants.TAG, "ReactInstanceManager.ctor()");
     initializeSoLoaderIfNecessary(applicationContext);
 
@@ -256,7 +256,7 @@ public void invokeDefaultOnBackPressed() {
       }
       mPackages.addAll(packages);
     }
-    mJSIModulesProvider = jsiModulesProvider;
+    mJSIModulePackage = jsiModulePackage;
 
     // Instantiate ReactChoreographer in UI thread.
     ReactChoreographer.initialize();
@@ -1102,8 +1102,8 @@ private ReactApplicationContext createReactContext(
       Systrace.endSection(TRACE_TAG_REACT_JAVA_BRIDGE);
       ReactMarker.logMarker(CREATE_CATALYST_INSTANCE_END);
     }
-    if (mJSIModulesProvider != null) {
-      catalystInstance.addJSIModules(mJSIModulesProvider
+    if (mJSIModulePackage != null) {
+      catalystInstance.addJSIModules(mJSIModulePackage
         .getJSIModules(reactContext, catalystInstance.getJavaScriptContextHolder()));
     }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
index 9c48a2338f6d..d90f08f75c80 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
@@ -10,7 +10,7 @@
 import android.app.Activity;
 import android.app.Application;
 import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.JSIModulesProvider;
+import com.facebook.react.bridge.JSIModulePackage;
 import com.facebook.react.bridge.JSBundleLoader;
 import com.facebook.react.bridge.JSCJavaScriptExecutorFactory;
 import com.facebook.react.bridge.JavaScriptExecutorFactory;
@@ -51,7 +51,7 @@ public class ReactInstanceManagerBuilder {
   private @Nullable JavaScriptExecutorFactory mJavaScriptExecutorFactory;
   private int mMinNumShakes = 1;
   private int mMinTimeLeftInFrameForNonBatchedOperationMs = -1;
-  private @Nullable JSIModulesProvider mJSIModulesProvider;
+  private @Nullable JSIModulePackage mJSIModulesPackage;
 
   /* package protected */ ReactInstanceManagerBuilder() {
   }
@@ -66,9 +66,9 @@ public ReactInstanceManagerBuilder setUIImplementationProvider(
     return this;
   }
 
-  public ReactInstanceManagerBuilder setJSIModulesProvider(
-    @Nullable JSIModulesProvider jsiModulesProvider) {
-    mJSIModulesProvider = jsiModulesProvider;
+  public ReactInstanceManagerBuilder setJSIModulesPackage(
+    @Nullable JSIModulePackage jsiModulePackage) {
+    mJSIModulesPackage = jsiModulePackage;
     return this;
   }
 
@@ -284,6 +284,6 @@ public ReactInstanceManager build() {
         mDevBundleDownloadListener,
         mMinNumShakes,
         mMinTimeLeftInFrameForNonBatchedOperationMs,
-        mJSIModulesProvider);
+      mJSIModulesPackage);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactNativeHost.java b/ReactAndroid/src/main/java/com/facebook/react/ReactNativeHost.java
index e1537d550f36..2efa28daaacd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactNativeHost.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactNativeHost.java
@@ -7,7 +7,7 @@
 
 package com.facebook.react;
 
-import com.facebook.react.bridge.JSIModulesProvider;
+import com.facebook.react.bridge.JSIModulePackage;
 import javax.annotation.Nullable;
 
 import java.util.List;
@@ -15,7 +15,6 @@
 import android.app.Application;
 
 import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.JSIModulesProvider;
 import com.facebook.react.bridge.JavaScriptExecutorFactory;
 import com.facebook.react.bridge.ReactMarker;
 import com.facebook.react.bridge.ReactMarkerConstants;
@@ -76,7 +75,7 @@ protected ReactInstanceManager createReactInstanceManager() {
       .setRedBoxHandler(getRedBoxHandler())
       .setJavaScriptExecutorFactory(getJavaScriptExecutorFactory())
       .setUIImplementationProvider(getUIImplementationProvider())
-      .setJSIModulesProvider(getJSIModulesProvider())
+      .setJSIModulesPackage(getJSIModulePackage())
       .setInitialLifecycleState(LifecycleState.BEFORE_CREATE);
 
     for (ReactPackage reactPackage : getPackages()) {
@@ -124,7 +123,7 @@ protected UIImplementationProvider getUIImplementationProvider() {
   }
 
   protected @Nullable
-  JSIModulesProvider getJSIModulesProvider() {
+  JSIModulePackage getJSIModulePackage() {
     return null;
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstance.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstance.java
index fe6d46112266..c58e1afe09eb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstance.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstance.java
@@ -101,5 +101,5 @@ void callFunction(
    */
   JavaScriptContextHolder getJavaScriptContextHolder();
 
-  void addJSIModules(List<JSIModuleHolder> jsiModules);
+  void addJSIModules(List<JSIModuleSpec> jsiModules);
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
index b8930d1a4154..b247b9b5470c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
@@ -464,7 +464,7 @@ public JavaScriptContextHolder getJavaScriptContextHolder() {
   }
 
   @Override
-  public void addJSIModules(List<JSIModuleHolder> jsiModules) {
+  public void addJSIModules(List<JSIModuleSpec> jsiModules) {
     mJSIModuleRegistry.registerModules(jsiModules);
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleHolder.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleHolder.java
index de98ae54b51c..8b35a5577f46 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleHolder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleHolder.java
@@ -1,12 +1,23 @@
 package com.facebook.react.bridge;
 
-/**
- * Holder class used to register {@link JSIModule} into JSI Bridge.
- */
-public interface JSIModuleHolder {
+public class JSIModuleHolder {
 
-  Class<? extends JSIModule> getJSIModuleClass();
+  private JSIModule mModule;
+  private final JSIModuleSpec mSpec;
 
-  <T extends JSIModule> T getJSIModule();
+  public JSIModuleHolder(JSIModuleSpec spec) {
+    mSpec = spec;
+  }
 
+  public JSIModule getJSIModule() {
+    if (mModule == null) {
+      synchronized (this) {
+        if (mModule != null) {
+          return mModule;
+        }
+        mModule = mSpec.getJSIModuleProvider().get();
+      }
+    }
+    return mModule;
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModulePackage.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModulePackage.java
new file mode 100644
index 000000000000..9a85f68d69f0
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModulePackage.java
@@ -0,0 +1,15 @@
+package com.facebook.react.bridge;
+
+import java.util.List;
+
+/**
+ * Interface used to initialize JSI Modules into the JSI Bridge.
+ */
+public interface JSIModulePackage {
+
+  /**
+   * @return a {@link List< JSIModuleSpec >} that contain the list of JSI Modules.
+   */
+  List<JSIModuleSpec> getJSIModules(ReactApplicationContext reactApplicationContext, JavaScriptContextHolder jsContext);
+
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleProvider.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleProvider.java
new file mode 100644
index 000000000000..a94162f12a06
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleProvider.java
@@ -0,0 +1,7 @@
+package com.facebook.react.bridge;
+
+public interface JSIModuleProvider<T extends JSIModule> {
+
+  T get();
+
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
index 7d4e1141bcad..cb4eb7478045 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
@@ -1,37 +1,28 @@
 package com.facebook.react.bridge;
 
 import com.facebook.infer.annotation.Assertions;
-import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
 
 public class JSIModuleRegistry {
 
-  private final List<JSIModuleHolder> mModuleList = new ArrayList<>();
-  private final Map<Class, JSIModule> mModules = new HashMap<>();
-  private volatile boolean mIsInitialized = false;
+  private final Map<Class, JSIModuleHolder> mModules = new HashMap<>();
 
   public JSIModuleRegistry() { }
 
   public <T extends JSIModule> T getModule(Class<T> moduleClass) {
-    JSIModule jsiModule = mModules.get(moduleClass);
-    if (jsiModule == null) {
-      initModules();
+    JSIModuleHolder jsiModuleHolder = mModules.get(moduleClass);
+    if (jsiModuleHolder == null) {
+      throw new IllegalArgumentException("Unable to find JSIModule for class " + moduleClass);
     }
-    return (T) Assertions.assertNotNull(mModules.get(moduleClass));
+    return (T) Assertions.assertNotNull(jsiModuleHolder.getJSIModule());
   }
 
-  public void registerModules(List<JSIModuleHolder> jsiModules) {
-    mModuleList.addAll(jsiModules);
-  }
-
-  public synchronized void initModules() {
-    if (!mIsInitialized) {
-      for (JSIModuleHolder holder : mModuleList) {
-        mModules.put(holder.getJSIModuleClass(), holder.getJSIModule());
-      }
-      mIsInitialized = true;
+  public void registerModules(List<JSIModuleSpec> jsiModules) {
+    for (JSIModuleSpec spec : jsiModules) {
+      mModules.put(spec.getJSIModuleClass(), new JSIModuleHolder(spec));
     }
   }
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleSpec.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleSpec.java
new file mode 100644
index 000000000000..d8c212200490
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleSpec.java
@@ -0,0 +1,12 @@
+package com.facebook.react.bridge;
+
+/**
+ * Holder class used to register {@link JSIModule} into JSI Bridge.
+ */
+public interface JSIModuleSpec<T extends JSIModule> {
+
+  Class<? extends JSIModule> getJSIModuleClass();
+
+  JSIModuleProvider<T> getJSIModuleProvider();
+
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModulesProvider.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModulesProvider.java
deleted file mode 100644
index 8abaa1ff79e2..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModulesProvider.java
+++ /dev/null
@@ -1,15 +0,0 @@
-package com.facebook.react.bridge;
-
-import java.util.List;
-
-/**
- * Interface used to initialize JSI Modules into the JSI Bridge.
- */
-public interface JSIModulesProvider {
-
-  /**
-   * @return a {@link List<JSIModuleHolder>} that contain the list of JSI Modules.
-   */
-  List<JSIModuleHolder> getJSIModules(ReactApplicationContext reactApplicationContext, JavaScriptContextHolder jsContext);
-
-}

From 6aea98441a375dddc524f21abc53cafe9cfa5ebb Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 1 Jun 2018 17:47:40 -0700
Subject: [PATCH 0721/1109] Add backward compatible support for onLayout event
 in Fabric

Reviewed By: achen1

Differential Revision: D8231722

fbshipit-source-id: 3d0641a7813e742ca81b98576f9ffc30ee597f30
---
 .../react/testing/ReactAppTestActivity.java   |  6 ++-
 .../testing/ReactInstrumentationTest.java     |  5 ++-
 .../react/fabric/FabricUIManager.java         | 24 ++++++++++-
 .../fabric/events/FabricEventEmitter.java     | 11 +++--
 .../uimanager/NativeViewHierarchyManager.java |  4 +-
 .../react/uimanager/UIViewOperationQueue.java | 42 +++++++++++++++++++
 .../react/fabric/FabricReconcilerTest.java    |  4 +-
 .../react/fabric/FabricUIManagerTest.java     |  4 +-
 8 files changed, 90 insertions(+), 10 deletions(-)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index f01d74e1fef5..77b211217796 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -37,7 +37,9 @@
 import com.facebook.react.shell.MainReactPackage;
 import com.facebook.react.testing.idledetection.ReactBridgeIdleSignaler;
 import com.facebook.react.testing.idledetection.ReactIdleDetectionUtil;
+import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.uimanager.UIImplementationProvider;
+import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
 import java.util.Arrays;
@@ -265,8 +267,10 @@ public JSIModuleProvider getJSIModuleProvider() {
                         public FabricUIManager get() {
                           List<ViewManager> viewManagers =
                             mReactInstanceManager.getOrCreateViewManagers(reactApplicationContext);
+                          EventDispatcher eventDispatcher =
+                            reactApplicationContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
                           FabricUIManager fabricUIManager =
-                            new FabricUIManager(reactApplicationContext, new ViewManagerRegistry(viewManagers), jsContext);
+                            new FabricUIManager(reactApplicationContext, new ViewManagerRegistry(viewManagers), jsContext, eventDispatcher);
                           new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
                           return fabricUIManager;
                         }
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
index 20dcc3ef516c..938835f3def7 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactInstrumentationTest.java
@@ -25,6 +25,8 @@
 public abstract class ReactInstrumentationTest extends
     ActivityInstrumentationTestCase2<ReactAppTestActivity> implements IdleWaiter {
 
+  protected StringRecordingModule mRecordingModule;
+
   public ReactInstrumentationTest() {
     super(ReactAppTestActivity.class);
   }
@@ -36,6 +38,7 @@ protected void setUp() throws Exception {
     Intent intent = new Intent();
     intent.putExtra(ReactAppTestActivity.EXTRA_IS_FABRIC_TEST, isFabricTest());
     setActivityIntent(intent);
+    mRecordingModule = new StringRecordingModule();
     final ReactAppTestActivity activity = getActivity();
     activity.loadBundle(
         createReactInstanceSpecForTest(),
@@ -95,7 +98,7 @@ protected <T extends JavaScriptModule> T getJSModule(Class<T> jsInterface) {
    * Override this method to provide extra native modules to be loaded before the app starts
    */
   protected ReactInstanceSpecForTest createReactInstanceSpecForTest() {
-    return new ReactInstanceSpecForTest();
+    return new ReactInstanceSpecForTest().addNativeModule(mRecordingModule);
   }
 
   /**
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index d6d730bf8c9a..4442a8b15377 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -10,6 +10,7 @@
 import static android.view.View.MeasureSpec.AT_MOST;
 import static android.view.View.MeasureSpec.EXACTLY;
 import static android.view.View.MeasureSpec.UNSPECIFIED;
+import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 
 import android.util.Log;
 import android.view.View;
@@ -24,9 +25,11 @@
 import com.facebook.react.bridge.WritableNativeMap;
 import com.facebook.react.common.ReactConstants;
 import com.facebook.react.common.annotations.VisibleForTesting;
+import com.facebook.react.fabric.events.FabricEventEmitter;
 import com.facebook.react.modules.i18nmanager.I18nUtil;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
 import com.facebook.react.uimanager.NativeViewHierarchyManager;
+import com.facebook.react.uimanager.OnLayoutEvent;
 import com.facebook.react.uimanager.ReactRootViewTagGenerator;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
@@ -37,6 +40,7 @@
 import com.facebook.react.uimanager.ViewManagerRegistry;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
+import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.yoga.YogaDirection;
 import java.util.ArrayList;
 import java.util.LinkedList;
@@ -61,13 +65,15 @@ public class FabricUIManager implements UIManager, JSHandler {
   private final JavaScriptContextHolder mJSContext;
   private volatile int mCurrentBatch = 0;
   private final FabricReconciler mFabricReconciler;
+  private final EventDispatcher mEventDispatcher;
   private FabricBinding mBinding;
   private long mEventHandlerPointer;
 
   public FabricUIManager(
       ReactApplicationContext reactContext,
       ViewManagerRegistry viewManagerRegistry,
-      JavaScriptContextHolder jsContext) {
+      JavaScriptContextHolder jsContext,
+      EventDispatcher eventDispatcher) {
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
     mReactApplicationContext = reactContext;
     mViewManagerRegistry = viewManagerRegistry;
@@ -76,7 +82,12 @@ public FabricUIManager(
         new UIViewOperationQueue(
             reactContext, mNativeViewHierarchyManager, 0);
     mFabricReconciler = new FabricReconciler(mUIViewOperationQueue);
+    mEventDispatcher = eventDispatcher;
     mJSContext = jsContext;
+
+    FabricEventEmitter eventEmitter =
+      new FabricEventEmitter(reactContext, this);
+    eventDispatcher.registerEventEmitter(FABRIC, eventEmitter);
   }
 
   public void setBinding(FabricBinding binding) {
@@ -355,7 +366,18 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
     if (mRootShadowNodeRegistry.getNode(tag) == null) {
       boolean frameDidChange =
           node.dispatchUpdates(absoluteX, absoluteY, mUIViewOperationQueue, null);
+      // Notify JS about layout event if requested
+      // and if the position or dimensions actually changed
+      // (consistent with iOS and Android Default implementation).
+      if (frameDidChange && node.shouldNotifyOnLayout()) {
+        mUIViewOperationQueue.enqueueOnLayoutEvent(tag,
+          node.getScreenX(),
+          node.getScreenY(),
+          node.getScreenWidth(),
+          node.getScreenHeight());
+      }
     }
+
     // Set the reference to the OriginalReactShadowNode to NULL, as the tree is already committed
     // and we do not need to hold references to the previous tree anymore
     node.setOriginalReactShadowNode(null);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
index 6ec640bf3cdb..0077b953dc45 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
@@ -26,6 +26,7 @@
 import com.facebook.react.fabric.FabricUIManager;
 import com.facebook.react.fabric.Scheduler;
 import com.facebook.react.fabric.Work;
+import com.facebook.react.uimanager.IllegalViewOperationException;
 import com.facebook.react.uimanager.events.RCTEventEmitter;
 import java.io.Closeable;
 import java.io.IOException;
@@ -48,9 +49,13 @@ public FabricEventEmitter(ReactApplicationContext context, FabricUIManager fabri
   }
 
   @Override
-  public void receiveEvent(int targetTag, String eventName, @Nullable WritableMap params) {
-    long eventTarget = mFabricUIManager.createEventTarget(targetTag);
-    mScheduler.scheduleWork(new FabricUIManagerWork(eventTarget, eventName, params));
+  public void receiveEvent(int reactTag, String eventName, @Nullable WritableMap params) {
+    try {
+      long eventTarget = mFabricUIManager.createEventTarget(reactTag);
+      mScheduler.scheduleWork(new FabricUIManagerWork(eventTarget, eventName, params));
+    } catch (IllegalViewOperationException e) {
+      Log.e(TAG, "Unable to emmit event for tag " + reactTag, e);
+    }
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
index 4cb9a92dc50d..8fe0c5cdd3dd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
@@ -224,11 +224,11 @@ private void updateInstanceHandle(View viewToUpdate, long instanceHandle) {
   public long getInstanceHandle(int reactTag) {
     View view = mTagsToViews.get(reactTag);
     if (view == null) {
-      throw new IllegalArgumentException("Unable to find view for tag: " + reactTag);
+      throw new IllegalViewOperationException("Unable to find view for tag: " + reactTag);
     }
     Long instanceHandle = (Long) view.getTag(R.id.view_tag_instance_handle);
     if (instanceHandle == null) {
-      throw new IllegalArgumentException("Unable to find instanceHandle for tag: " + reactTag);
+      throw new IllegalViewOperationException("Unable to find instanceHandle for tag: " + reactTag);
     }
     return instanceHandle;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
index 90e4d82bb9bc..783110b96af6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIViewOperationQueue.java
@@ -96,6 +96,38 @@ public void execute() {
     }
   }
 
+  private final class EmitOnLayoutEventOperation extends ViewOperation {
+
+    private final int mScreenX;
+    private final int mScreenY;
+    private final int mScreenWidth;
+    private final int mScreenHeight;
+
+    public EmitOnLayoutEventOperation(
+        int tag,
+        int screenX,
+        int screenY,
+        int screenWidth,
+        int screenHeight) {
+      super(tag);
+      mScreenX = screenX;
+      mScreenY = screenY;
+      mScreenWidth = screenWidth;
+      mScreenHeight = screenHeight;
+    }
+
+    @Override
+    public void execute() {
+      mReactApplicationContext.getNativeModule(UIManagerModule.class)
+        .getEventDispatcher()
+        .dispatchEvent(OnLayoutEvent.obtain(
+          mTag,
+          mScreenX,
+          mScreenY,
+          mScreenWidth,
+          mScreenHeight));
+    }
+  }
 
   private final class UpdateInstanceHandleOperation extends ViewOperation {
 
@@ -706,6 +738,16 @@ public void enqueueUpdateProperties(int reactTag, String className, ReactStylesD
     mOperations.add(new UpdatePropertiesOperation(reactTag, props));
   }
 
+  public void enqueueOnLayoutEvent(
+    int tag,
+    int screenX,
+    int screenY,
+    int screenWidth,
+    int screenHeight) {
+    mOperations.add(new EmitOnLayoutEventOperation(tag, screenX, screenY, screenWidth, screenHeight));
+  }
+
+
   public void enqueueUpdateLayout(
       int parentTag,
       int reactTag,
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
index a696d21e4def..b627df9af6bc 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricReconcilerTest.java
@@ -11,6 +11,7 @@
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReactTestHelper;
+import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.uimanager.NativeViewHierarchyManager;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
@@ -46,7 +47,8 @@ public void setUp() {
     List<ViewManager> viewManagers = new ArrayList<>();
     ViewManagerRegistry viewManagerRegistry = new ViewManagerRegistry(viewManagers);
     JavaScriptContextHolder jsContext = mock(JavaScriptContextHolder.class);
-    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry, jsContext);
+    EventDispatcher eventDispatcher = mock(EventDispatcher.class);
+    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry, jsContext, eventDispatcher);
     mMockUIViewOperationQueue = new MockUIViewOperationQueue(reactContext);
     mFabricReconciler = new FabricReconciler(mMockUIViewOperationQueue);
   }
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index 9b1c95db67be..ba6b10c8c3fd 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -13,6 +13,7 @@
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReactTestHelper;
 import com.facebook.react.bridge.ReadableNativeMap;
+import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.Spacing;
@@ -55,7 +56,8 @@ public void setUp() throws Exception {
             new ReactViewManager(), new ReactTextViewManager(), new ReactRawTextManager());
     ViewManagerRegistry viewManagerRegistry = new ViewManagerRegistry(viewManagers);
     JavaScriptContextHolder jsContext = mock(JavaScriptContextHolder.class);
-    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry, jsContext);
+    EventDispatcher eventDispatcher = mock(EventDispatcher.class);
+    mFabricUIManager = new FabricUIManager(reactContext, viewManagerRegistry, jsContext, eventDispatcher);
   }
 
   @Test

From 8529b1ee913229ba0696399a3132c2bd4034eead Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 1 Jun 2018 17:47:46 -0700
Subject: [PATCH 0722/1109] Implement release of FabricUIManager resources

Reviewed By: achen1

Differential Revision: D8232155

fbshipit-source-id: 6683c692a830f5a73aab2c606167e54d668ae5c2
---
 .../idledetection/ReactBridgeIdleSignaler.java  |  5 +++++
 .../react/bridge/CatalystInstanceImpl.java      | 11 ++++++++---
 .../com/facebook/react/bridge/JSIModule.java    | 12 ++++++++++++
 .../facebook/react/bridge/JSIModuleHolder.java  |  7 +++++++
 .../react/bridge/JSIModuleRegistry.java         |  5 +++++
 .../NotThreadSafeBridgeIdleDebugListener.java   |  5 +++++
 .../facebook/react/fabric/FabricUIManager.java  | 17 ++++++++++++-----
 .../debug/DidJSUpdateUiDuringFrameDetector.java |  5 +++++
 8 files changed, 59 insertions(+), 8 deletions(-)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/idledetection/ReactBridgeIdleSignaler.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/idledetection/ReactBridgeIdleSignaler.java
index 6509897a3425..05b6662493fd 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/idledetection/ReactBridgeIdleSignaler.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/idledetection/ReactBridgeIdleSignaler.java
@@ -30,6 +30,11 @@ public void onTransitionToBridgeIdle() {
     mBridgeIdleSemaphore.release();
   }
 
+  @Override
+  public void onBridgeDestroyed() {
+    // Do nothing
+  }
+
   @Override
   public void onTransitionToBridgeBusy() {
     mIsBridgeIdle = false;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
index b247b9b5470c..71c6f25baa10 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/CatalystInstanceImpl.java
@@ -338,10 +338,14 @@ public void destroy() {
           @Override
           public void run() {
             mNativeModuleRegistry.notifyJSInstanceDestroy();
+            mJSIModuleRegistry.notifyJSInstanceDestroy();
             boolean wasIdle = (mPendingJSCalls.getAndSet(0) == 0);
-            if (!wasIdle && !mBridgeIdleListeners.isEmpty()) {
+            if (!mBridgeIdleListeners.isEmpty()) {
               for (NotThreadSafeBridgeIdleDebugListener listener : mBridgeIdleListeners) {
-                listener.onTransitionToBridgeIdle();
+                if (!wasIdle) {
+                  listener.onTransitionToBridgeIdle();
+                }
+                listener.onBridgeDestroyed();
               }
             }
             AsyncTask.execute(
@@ -351,7 +355,8 @@ public void run() {
                     // Kill non-UI threads from neutral third party
                     // potentially expensive, so don't run on UI thread
 
-                    // contextHolder is used as a lock to guard against other users of the JS VM having
+                    // contextHolder is used as a lock to guard against other users of the JS VM
+                    // having
                     // the VM destroyed underneath them, so notify them before we resetNative
                     mJavaScriptContextHolder.clear();
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModule.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModule.java
index 5b9e2495449d..8ee96fee2181 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModule.java
@@ -4,4 +4,16 @@
  * Marker interface used to represent a JSI Module.
  */
 public interface JSIModule {
+
+  /**
+   * This is called at the end of {@link CatalystApplicationFragment#createCatalystInstance()}
+   * after the CatalystInstance has been created, in order to initialize NativeModules that require
+   * the CatalystInstance or JS modules.
+   */
+  void initialize();
+
+  /**
+   * Called before {CatalystInstance#onHostDestroy}
+   */
+  void onCatalystInstanceDestroy();
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleHolder.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleHolder.java
index 8b35a5577f46..14d0f97eba0b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleHolder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleHolder.java
@@ -16,8 +16,15 @@ public JSIModule getJSIModule() {
           return mModule;
         }
         mModule = mSpec.getJSIModuleProvider().get();
+        mModule.initialize();
       }
     }
     return mModule;
   }
+
+  public void notifyJSInstanceDestroy() {
+    if (mModule != null) {
+      mModule.onCatalystInstanceDestroy();
+    }
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
index cb4eb7478045..dbca620dcfcc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/JSIModuleRegistry.java
@@ -25,4 +25,9 @@ public void registerModules(List<JSIModuleSpec> jsiModules) {
     }
   }
 
+  public void notifyJSInstanceDestroy() {
+    for (JSIModuleHolder moduleHolder : mModules.values()) {
+      moduleHolder.notifyJSInstanceDestroy();
+    }
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/NotThreadSafeBridgeIdleDebugListener.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/NotThreadSafeBridgeIdleDebugListener.java
index a10fa295399d..2531b9793b5d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/NotThreadSafeBridgeIdleDebugListener.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/NotThreadSafeBridgeIdleDebugListener.java
@@ -28,4 +28,9 @@ public interface NotThreadSafeBridgeIdleDebugListener {
    * Called when the bridge was in an idle state and executes a JS call or callback.
    */
   void onTransitionToBridgeBusy();
+
+  /**
+   * Called when the bridge is destroyed
+   */
+  void onBridgeDestroyed();
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 4442a8b15377..0a35242d1128 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -29,7 +29,6 @@
 import com.facebook.react.modules.i18nmanager.I18nUtil;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
 import com.facebook.react.uimanager.NativeViewHierarchyManager;
-import com.facebook.react.uimanager.OnLayoutEvent;
 import com.facebook.react.uimanager.ReactRootViewTagGenerator;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
@@ -84,10 +83,6 @@ public FabricUIManager(
     mFabricReconciler = new FabricReconciler(mUIViewOperationQueue);
     mEventDispatcher = eventDispatcher;
     mJSContext = jsContext;
-
-    FabricEventEmitter eventEmitter =
-      new FabricEventEmitter(reactContext, this);
-    eventDispatcher.registerEventEmitter(FABRIC, eventEmitter);
   }
 
   public void setBinding(FabricBinding binding) {
@@ -538,4 +533,16 @@ public void invoke(long eventTarget, String name, WritableMap params) {
     mBinding.dispatchEventToTarget(mJSContext.get(), mEventHandlerPointer, eventTarget, name, (WritableNativeMap) params);
   }
 
+  @Override
+  public void initialize() {
+    FabricEventEmitter eventEmitter =
+      new FabricEventEmitter(mReactApplicationContext, this);
+    mEventDispatcher.registerEventEmitter(FABRIC, eventEmitter);
+  }
+
+  @Override
+  public void onCatalystInstanceDestroy() {
+    mBinding.releaseEventHandler(mJSContext.get(), mEventHandlerPointer);
+  }
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/debug/DidJSUpdateUiDuringFrameDetector.java b/ReactAndroid/src/main/java/com/facebook/react/modules/debug/DidJSUpdateUiDuringFrameDetector.java
index 37bf6596f6da..f0a65ff1c773 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/debug/DidJSUpdateUiDuringFrameDetector.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/debug/DidJSUpdateUiDuringFrameDetector.java
@@ -42,6 +42,11 @@ public synchronized void onTransitionToBridgeBusy() {
     mTransitionToBusyEvents.add(System.nanoTime());
   }
 
+  @Override
+  public synchronized void onBridgeDestroyed() {
+    // do nothing
+  }
+
   @Override
   public synchronized void onViewHierarchyUpdateEnqueued() {
     mViewHierarchyUpdateEnqueuedEvents.add(System.nanoTime());

From ac9a3d0c992aecc1f645aa68aad89a9f201c4380 Mon Sep 17 00:00:00 2001
From: Peter Ammon <pca@fb.com>
Date: Fri, 1 Jun 2018 17:48:58 -0700
Subject: [PATCH 0723/1109] normalizeColor to compute regexps lazily

Reviewed By: johnislarry

Differential Revision: D8241955

fbshipit-source-id: 0939f442bb1e51118207449e0b95c6da97b899da
---
 Libraries/Color/normalizeColor.js | 28 ++++++++++++++++++----------
 1 file changed, 18 insertions(+), 10 deletions(-)

diff --git a/Libraries/Color/normalizeColor.js b/Libraries/Color/normalizeColor.js
index 7b4ca253107d..690090b8c9ca 100755
--- a/Libraries/Color/normalizeColor.js
+++ b/Libraries/Color/normalizeColor.js
@@ -12,6 +12,7 @@
 'use strict';
 
 function normalizeColor(color: string | number): ?number {
+  const matchers = getMatchers();
   let match;
 
   if (typeof color === 'number') {
@@ -156,16 +157,23 @@ function call(...args) {
   return '\\(\\s*(' + args.join(')\\s*,\\s*(') + ')\\s*\\)';
 }
 
-const matchers = {
-  rgb: new RegExp('rgb' + call(NUMBER, NUMBER, NUMBER)),
-  rgba: new RegExp('rgba' + call(NUMBER, NUMBER, NUMBER, NUMBER)),
-  hsl: new RegExp('hsl' + call(NUMBER, PERCENTAGE, PERCENTAGE)),
-  hsla: new RegExp('hsla' + call(NUMBER, PERCENTAGE, PERCENTAGE, NUMBER)),
-  hex3: /^#([0-9a-fA-F]{1})([0-9a-fA-F]{1})([0-9a-fA-F]{1})$/,
-  hex4: /^#([0-9a-fA-F]{1})([0-9a-fA-F]{1})([0-9a-fA-F]{1})([0-9a-fA-F]{1})$/,
-  hex6: /^#([0-9a-fA-F]{6})$/,
-  hex8: /^#([0-9a-fA-F]{8})$/,
-};
+let cachedMatchers;
+
+function getMatchers() {
+  if (cachedMatchers === undefined) {
+    cachedMatchers = {
+      rgb: new RegExp('rgb' + call(NUMBER, NUMBER, NUMBER)),
+      rgba: new RegExp('rgba' + call(NUMBER, NUMBER, NUMBER, NUMBER)),
+      hsl: new RegExp('hsl' + call(NUMBER, PERCENTAGE, PERCENTAGE)),
+      hsla: new RegExp('hsla' + call(NUMBER, PERCENTAGE, PERCENTAGE, NUMBER)),
+      hex3: /^#([0-9a-fA-F]{1})([0-9a-fA-F]{1})([0-9a-fA-F]{1})$/,
+      hex4: /^#([0-9a-fA-F]{1})([0-9a-fA-F]{1})([0-9a-fA-F]{1})([0-9a-fA-F]{1})$/,
+      hex6: /^#([0-9a-fA-F]{6})$/,
+      hex8: /^#([0-9a-fA-F]{8})$/,
+    };
+  }
+  return cachedMatchers;
+}
 
 function parse255(str: string): number {
   const int = parseInt(str, 10);

From 7498e5ce77a7b5c2d3aadf9da0413559f701ed94 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 1 Jun 2018 19:48:11 -0700
Subject: [PATCH 0724/1109] Revert D8234803: [RN] Slider remove $FlowFixMe

Differential Revision:
D8234803

Original commit changeset: cfc0466a54f3

fbshipit-source-id: 354fcc1853597cbcd518abaf4be5b11116f594b3
---
 Libraries/Components/Slider/Slider.js | 40 +++++++++++++++------------
 1 file changed, 23 insertions(+), 17 deletions(-)

diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index e1de6b3c3886..efe22529f287 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -249,10 +249,17 @@ const Slider = createReactClass({
   },
 
   render: function() {
-    const style = StyleSheet.compose(styles.slider, this.props.style);
-
-    const onValueChange =
-      this.props.onValueChange &&
+    const {style, onValueChange, onSlidingComplete, ...props} = this.props;
+    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
+     * suppresses an error found when Flow v0.54 was deployed. To see the error
+     * delete this comment and run Flow. */
+    props.style = [styles.slider, style];
+
+    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
+     * suppresses an error found when Flow v0.54 was deployed. To see the error
+     * delete this comment and run Flow. */
+    props.onValueChange =
+      onValueChange &&
       ((event: Event) => {
         let userEvent = true;
         if (Platform.OS === 'android') {
@@ -260,27 +267,26 @@ const Slider = createReactClass({
           // dragging the slider.
           userEvent = event.nativeEvent.fromUser;
         }
-        this.props.onValueChange &&
-          userEvent &&
-          this.props.onValueChange(event.nativeEvent.value);
+        onValueChange && userEvent && onValueChange(event.nativeEvent.value);
       });
 
-    const onChange = this.props.onValueChange;
+    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
+     * suppresses an error found when Flow v0.54 was deployed. To see the error
+     * delete this comment and run Flow. */
+    props.onChange = props.onValueChange;
 
-    const onSlidingComplete =
-      this.props.onSlidingComplete &&
+    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
+     * suppresses an error found when Flow v0.54 was deployed. To see the error
+     * delete this comment and run Flow. */
+    props.onSlidingComplete =
+      onSlidingComplete &&
       ((event: Event) => {
-        this.props.onSlidingComplete &&
-          this.props.onSlidingComplete(event.nativeEvent.value);
+        onSlidingComplete && onSlidingComplete(event.nativeEvent.value);
       });
 
     return (
       <RCTSlider
-        {...this.props}
-        style={style}
-        onChange={onChange}
-        onSlidingComplete={onSlidingComplete}
-        onValueChange={onValueChange}
+        {...props}
         enabled={!this.props.disabled}
         onStartShouldSetResponder={() => true}
         onResponderTerminationRequest={() => false}

From 1615f9d16149c7082ce0e1485aa04a6f2108f7ba Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 1 Jun 2018 21:58:03 -0700
Subject: [PATCH 0725/1109] Slider remove $FlowFixMe #take2

Reviewed By: fkgozali

Differential Revision: D8246336

fbshipit-source-id: 21555a318bd823309ac2c285b49c2045338c2b28
---
 Libraries/Components/Slider/Slider.js | 40 ++++++++++++---------------
 1 file changed, 17 insertions(+), 23 deletions(-)

diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index efe22529f287..52786a133d6f 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -249,17 +249,10 @@ const Slider = createReactClass({
   },
 
   render: function() {
-    const {style, onValueChange, onSlidingComplete, ...props} = this.props;
-    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error found when Flow v0.54 was deployed. To see the error
-     * delete this comment and run Flow. */
-    props.style = [styles.slider, style];
-
-    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error found when Flow v0.54 was deployed. To see the error
-     * delete this comment and run Flow. */
-    props.onValueChange =
-      onValueChange &&
+    const style = StyleSheet.compose(styles.slider, this.props.style);
+
+    const onValueChange =
+      this.props.onValueChange &&
       ((event: Event) => {
         let userEvent = true;
         if (Platform.OS === 'android') {
@@ -267,26 +260,27 @@ const Slider = createReactClass({
           // dragging the slider.
           userEvent = event.nativeEvent.fromUser;
         }
-        onValueChange && userEvent && onValueChange(event.nativeEvent.value);
+        this.props.onValueChange &&
+          userEvent &&
+          this.props.onValueChange(event.nativeEvent.value);
       });
 
-    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error found when Flow v0.54 was deployed. To see the error
-     * delete this comment and run Flow. */
-    props.onChange = props.onValueChange;
+    const onChange = onValueChange;
 
-    /* $FlowFixMe(>=0.54.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error found when Flow v0.54 was deployed. To see the error
-     * delete this comment and run Flow. */
-    props.onSlidingComplete =
-      onSlidingComplete &&
+    const onSlidingComplete =
+      this.props.onSlidingComplete &&
       ((event: Event) => {
-        onSlidingComplete && onSlidingComplete(event.nativeEvent.value);
+        this.props.onSlidingComplete &&
+          this.props.onSlidingComplete(event.nativeEvent.value);
       });
 
     return (
       <RCTSlider
-        {...props}
+        {...this.props}
+        style={style}
+        onChange={onChange}
+        onSlidingComplete={onSlidingComplete}
+        onValueChange={onValueChange}
         enabled={!this.props.disabled}
         onStartShouldSetResponder={() => true}
         onResponderTerminationRequest={() => false}

From 615daeb68f4d42856cdbcd2609fd103bd689dd40 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 2 Jun 2018 22:35:45 -0700
Subject: [PATCH 0726/1109] Slider move prop comments to flow types

Reviewed By: yungsters

Differential Revision: D8246378

fbshipit-source-id: f62a77d64016f6502b3445ab6d0d1558034333e6
---
 Libraries/Components/Slider/Slider.js | 164 +++++++++++++-------------
 1 file changed, 79 insertions(+), 85 deletions(-)

diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index 52786a133d6f..ec4120b64b74 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -34,13 +34,35 @@ const RCTSlider = requireNativeComponent('RCTSlider');
 type Event = Object;
 
 type IOSProps = $ReadOnly<{|
+  /**
+   * Assigns a single image for the track. Only static images are supported.
+   * The center pixel of the image will be stretched to fill the track.
+   */
   trackImage?: ?ImageSource,
+
+  /**
+   * Assigns a minimum track image. Only static images are supported. The
+   * rightmost pixel of the image will be stretched to fill the track.
+   */
   minimumTrackImage?: ?ImageSource,
+
+  /**
+   * Assigns a maximum track image. Only static images are supported. The
+   * leftmost pixel of the image will be stretched to fill the track.
+   */
   maximumTrackImage?: ?ImageSource,
+
+  /**
+   * Sets an image for the thumb. Only static images are supported.
+   */
   thumbImage?: ?ImageSource,
 |}>;
 
 type AndroidProps = $ReadOnly<{|
+  /**
+   * Color of the foreground switch grip.
+   * @platform android
+   */
   thumbTintColor?: ?ColorValue,
 |}>;
 
@@ -48,16 +70,73 @@ type Props = $ReadOnly<{|
   ...ViewProps,
   ...IOSProps,
   ...AndroidProps,
+
+  /**
+   * Used to style and layout the `Slider`.  See `StyleSheet.js` and
+   * `ViewStylePropTypes.js` for more info.
+   */
   style?: ?ViewStyleProp,
+
+  /**
+   * Initial value of the slider. The value should be between minimumValue
+   * and maximumValue, which default to 0 and 1 respectively.
+   * Default value is 0.
+   *
+   * *This is not a controlled component*, you don't need to update the
+   * value during dragging.
+   */
   value?: ?number,
+
+  /**
+   * Step value of the slider. The value should be
+   * between 0 and (maximumValue - minimumValue).
+   * Default value is 0.
+   */
   step?: ?number,
+
+  /**
+   * Initial minimum value of the slider. Default value is 0.
+   */
   minimumValue?: ?number,
+
+  /**
+   * Initial maximum value of the slider. Default value is 1.
+   */
   maximumValue?: ?number,
+
+  /**
+   * The color used for the track to the left of the button.
+   * Overrides the default blue gradient image on iOS.
+   */
   minimumTrackTintColor?: ?ColorValue,
+
+  /**
+   * The color used for the track to the right of the button.
+   * Overrides the default blue gradient image on iOS.
+   */
   maximumTrackTintColor?: ?ColorValue,
+
+  /**
+   * If true the user won't be able to move the slider.
+   * Default value is false.
+   */
   disabled?: ?boolean,
+
+  /**
+   * Callback continuously called while the user is dragging the slider.
+   */
   onValueChange?: ?Function,
+
+  /**
+   * Callback that is called when the user releases the slider,
+   * regardless if the value has changed. The current value is passed
+   * as an argument to the callback handler.
+   */
   onSlidingComplete?: ?Function,
+
+  /**
+   * Used to locate this view in UI automation tests.
+   */
   testID?: ?string,
 |}>;
 
@@ -127,106 +206,21 @@ const Slider = createReactClass({
 
   propTypes: {
     ...ViewPropTypes,
-
-    /**
-     * Used to style and layout the `Slider`.  See `StyleSheet.js` and
-     * `ViewStylePropTypes.js` for more info.
-     */
     style: ViewPropTypes.style,
-
-    /**
-     * Initial value of the slider. The value should be between minimumValue
-     * and maximumValue, which default to 0 and 1 respectively.
-     * Default value is 0.
-     *
-     * *This is not a controlled component*, you don't need to update the
-     * value during dragging.
-     */
     value: PropTypes.number,
-
-    /**
-     * Step value of the slider. The value should be
-     * between 0 and (maximumValue - minimumValue).
-     * Default value is 0.
-     */
     step: PropTypes.number,
-
-    /**
-     * Initial minimum value of the slider. Default value is 0.
-     */
     minimumValue: PropTypes.number,
-
-    /**
-     * Initial maximum value of the slider. Default value is 1.
-     */
     maximumValue: PropTypes.number,
-
-    /**
-     * The color used for the track to the left of the button.
-     * Overrides the default blue gradient image on iOS.
-     */
     minimumTrackTintColor: ColorPropType,
-
-    /**
-     * The color used for the track to the right of the button.
-     * Overrides the default blue gradient image on iOS.
-     */
     maximumTrackTintColor: ColorPropType,
-
-    /**
-     * If true the user won't be able to move the slider.
-     * Default value is false.
-     */
     disabled: PropTypes.bool,
-
-    /**
-     * Assigns a single image for the track. Only static images are supported.
-     * The center pixel of the image will be stretched to fill the track.
-     * @platform ios
-     */
     trackImage: Image.propTypes.source,
-
-    /**
-     * Assigns a minimum track image. Only static images are supported. The
-     * rightmost pixel of the image will be stretched to fill the track.
-     * @platform ios
-     */
     minimumTrackImage: Image.propTypes.source,
-
-    /**
-     * Assigns a maximum track image. Only static images are supported. The
-     * leftmost pixel of the image will be stretched to fill the track.
-     * @platform ios
-     */
     maximumTrackImage: Image.propTypes.source,
-
-    /**
-     * Sets an image for the thumb. Only static images are supported.
-     * @platform ios
-     */
     thumbImage: Image.propTypes.source,
-
-    /**
-     * Color of the foreground switch grip.
-     * @platform android
-     */
     thumbTintColor: ColorPropType,
-
-    /**
-     * Callback continuously called while the user is dragging the slider.
-     */
     onValueChange: PropTypes.func,
-
-    /**
-     * Callback that is called when the user releases the slider,
-     * regardless if the value has changed. The current value is passed
-     * as an argument to the callback handler.
-     */
     onSlidingComplete: PropTypes.func,
-
-    /**
-     * Used to locate this view in UI automation tests.
-     */
     testID: PropTypes.string,
   },
 

From 5259450c143f71c65e157d6b7d3f0e1655eb7aa1 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 2 Jun 2018 22:35:48 -0700
Subject: [PATCH 0727/1109] Slider to ES6 Class

Reviewed By: yungsters

Differential Revision: D8246422

fbshipit-source-id: 1955ae87abe077115ac8f8ea105be85db8ea66b4
---
 Libraries/Components/Slider/Slider.js | 147 ++++++++++----------------
 1 file changed, 58 insertions(+), 89 deletions(-)

diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index ec4120b64b74..a7998ef28bfc 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -10,18 +10,11 @@
 
 'use strict';
 
-const Image = require('Image');
-const ColorPropType = require('ColorPropType');
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const ReactNative = require('ReactNative');
-const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const Platform = require('Platform');
 const React = require('React');
-const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
-const ViewPropTypes = require('ViewPropTypes');
 
-const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
 import type {ImageSource} from 'ImageSource';
@@ -200,89 +193,65 @@ type Props = $ReadOnly<{|
  *```
  *
  */
-const Slider = createReactClass({
-  displayName: 'Slider',
-  mixins: [NativeMethodsMixin],
-
-  propTypes: {
-    ...ViewPropTypes,
-    style: ViewPropTypes.style,
-    value: PropTypes.number,
-    step: PropTypes.number,
-    minimumValue: PropTypes.number,
-    maximumValue: PropTypes.number,
-    minimumTrackTintColor: ColorPropType,
-    maximumTrackTintColor: ColorPropType,
-    disabled: PropTypes.bool,
-    trackImage: Image.propTypes.source,
-    minimumTrackImage: Image.propTypes.source,
-    maximumTrackImage: Image.propTypes.source,
-    thumbImage: Image.propTypes.source,
-    thumbTintColor: ColorPropType,
-    onValueChange: PropTypes.func,
-    onSlidingComplete: PropTypes.func,
-    testID: PropTypes.string,
-  },
-
-  getDefaultProps: function(): any {
-    return {
-      disabled: false,
-      value: 0,
-      minimumValue: 0,
-      maximumValue: 1,
-      step: 0,
-    };
-  },
-
-  viewConfig: {
-    uiViewClassName: 'RCTSlider',
-    validAttributes: {
-      ...ReactNativeViewAttributes.RCTView,
-      value: true,
-    },
-  },
-
-  render: function() {
-    const style = StyleSheet.compose(styles.slider, this.props.style);
-
-    const onValueChange =
-      this.props.onValueChange &&
-      ((event: Event) => {
-        let userEvent = true;
-        if (Platform.OS === 'android') {
-          // On Android there's a special flag telling us the user is
-          // dragging the slider.
-          userEvent = event.nativeEvent.fromUser;
-        }
-        this.props.onValueChange &&
-          userEvent &&
-          this.props.onValueChange(event.nativeEvent.value);
-      });
-
-    const onChange = onValueChange;
-
-    const onSlidingComplete =
-      this.props.onSlidingComplete &&
-      ((event: Event) => {
-        this.props.onSlidingComplete &&
-          this.props.onSlidingComplete(event.nativeEvent.value);
-      });
-
-    return (
-      <RCTSlider
-        {...this.props}
-        style={style}
-        onChange={onChange}
-        onSlidingComplete={onSlidingComplete}
-        onValueChange={onValueChange}
-        enabled={!this.props.disabled}
-        onStartShouldSetResponder={() => true}
-        onResponderTerminationRequest={() => false}
-      />
-    );
-  },
+const Slider = (
+  props: $ReadOnly<{|
+    ...Props,
+    forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
+  |}>,
+) => {
+  const style = StyleSheet.compose(styles.slider, props.style);
+
+  const onValueChange =
+    props.onValueChange &&
+    ((event: Event) => {
+      let userEvent = true;
+      if (Platform.OS === 'android') {
+        // On Android there's a special flag telling us the user is
+        // dragging the slider.
+        userEvent = event.nativeEvent.fromUser;
+      }
+      props.onValueChange &&
+        userEvent &&
+        props.onValueChange(event.nativeEvent.value);
+    });
+
+  const onChange = onValueChange;
+
+  const onSlidingComplete =
+    props.onSlidingComplete &&
+    ((event: Event) => {
+      props.onSlidingComplete &&
+        props.onSlidingComplete(event.nativeEvent.value);
+    });
+
+  return (
+    <RCTSlider
+      {...props}
+      style={style}
+      onChange={onChange}
+      onSlidingComplete={onSlidingComplete}
+      onValueChange={onValueChange}
+      enabled={!props.disabled}
+      onStartShouldSetResponder={() => true}
+      onResponderTerminationRequest={() => false}
+    />
+  );
+};
+
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+const SliderWithRef = React.forwardRef((props: Props, ref) => {
+  return <Slider {...props} forwardedRef={ref} />;
 });
 
+SliderWithRef.defaultProps = {
+  disabled: false,
+  value: 0,
+  minimumValue: 0,
+  maximumValue: 1,
+  step: 0,
+};
+SliderWithRef.displayName = 'Slider';
+
 let styles;
 if (Platform.OS === 'ios') {
   styles = StyleSheet.create({
@@ -296,4 +265,4 @@ if (Platform.OS === 'ios') {
   });
 }
 
-module.exports = ((Slider: any): Class<ReactNative.NativeComponent<Props>>);
+module.exports = (SliderWithRef: Class<ReactNative.NativeComponent<Props>>);

From 970caa4552d4ba87c1a954391535ff42b00832e7 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 2 Jun 2018 22:35:54 -0700
Subject: [PATCH 0728/1109] Switch to ES6 Class

Reviewed By: yungsters

Differential Revision: D8246980

fbshipit-source-id: fbd6998429e6791000ea093d3fa15c1a486914bd
---
 Libraries/Components/Switch/Switch.js | 187 +++++++++++++-------------
 1 file changed, 90 insertions(+), 97 deletions(-)

diff --git a/Libraries/Components/Switch/Switch.js b/Libraries/Components/Switch/Switch.js
index c2288d25c673..c1d38619a6ac 100644
--- a/Libraries/Components/Switch/Switch.js
+++ b/Libraries/Components/Switch/Switch.js
@@ -10,42 +10,81 @@
 
 'use strict';
 
-const ColorPropType = require('ColorPropType');
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const Platform = require('Platform');
 const React = require('React');
 const ReactNative = require('ReactNative');
-const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
-const ViewPropTypes = require('ViewPropTypes');
 
-const createReactClass = require('create-react-class');
+const nullthrows = require('fbjs/lib/nullthrows');
 const requireNativeComponent = require('requireNativeComponent');
 
 import type {ColorValue} from 'StyleSheetTypes';
 import type {ViewProps} from 'ViewPropTypes';
 
-const RCTSwitch =
-  Platform.OS === 'android'
-    ? requireNativeComponent('AndroidSwitch')
-    : requireNativeComponent('RCTSwitch');
-
-type DefaultProps = $ReadOnly<{|
-  value: boolean,
-  disabled: boolean,
-|}>;
-
 type Props = $ReadOnly<{|
   ...ViewProps,
+  /**
+   * The value of the switch.  If true the switch will be turned on.
+   * Default value is false.
+   */
   value?: ?boolean,
+
+  /**
+   * If true the user won't be able to toggle the switch.
+   * Default value is false.
+   */
   disabled?: ?boolean,
+
+  /**
+   * Switch change handler.
+   *
+   * Invoked with the event when the value changes. For getting the value
+   * the switch was changed to use onValueChange instead.
+   */
+  onChange?: ?Function,
+
+  /**
+   * Invoked with the new value when the value changes.
+   */
   onValueChange?: ?Function,
+
+  /**
+   * Used to locate this view in end-to-end tests.
+   */
   testID?: ?string,
+
+  /**
+   * Border color on iOS and background color on Android when the switch is turned off.
+   */
   tintColor?: ?ColorValue,
+
+  /**
+   * Background color when the switch is turned on.
+   */
   onTintColor?: ?ColorValue,
+
+  /**
+   * Color of the foreground switch grip.
+   */
   thumbTintColor?: ?ColorValue,
 |}>;
 
+type NativeSwitchType = Class<
+  ReactNative.NativeComponent<
+    $ReadOnly<{|
+      ...Props,
+      enabled?: ?boolean,
+      on?: ?boolean,
+      trackTintColor?: ?ColorValue,
+    |}>,
+  >,
+>;
+
+const RCTSwitch: NativeSwitchType =
+  Platform.OS === 'android'
+    ? (requireNativeComponent('AndroidSwitch'): any)
+    : (requireNativeComponent('RCTSwitch'): any);
+
 /**
  * Renders a boolean input.
  *
@@ -57,105 +96,59 @@ type Props = $ReadOnly<{|
  * @keyword checkbox
  * @keyword toggle
  */
-const Switch = createReactClass({
-  displayName: 'Switch',
-  propTypes: {
-    ...ViewPropTypes,
-    /**
-     * The value of the switch.  If true the switch will be turned on.
-     * Default value is false.
-     */
-    value: PropTypes.bool,
-    /**
-     * If true the user won't be able to toggle the switch.
-     * Default value is false.
-     */
-    disabled: PropTypes.bool,
-    /**
-     * Invoked with the new value when the value changes.
-     */
-    onValueChange: PropTypes.func,
-    /**
-     * Used to locate this view in end-to-end tests.
-     */
-    testID: PropTypes.string,
-
-    /**
-     * Border color on iOS and background color on Android when the switch is turned off.
-     */
-    tintColor: ColorPropType,
-    /**
-     * Background color when the switch is turned on.
-     */
-    onTintColor: ColorPropType,
-    /**
-     * Color of the foreground switch grip.
-     */
-    thumbTintColor: ColorPropType,
-  },
-
-  getDefaultProps: function(): DefaultProps {
-    return {
-      value: false,
-      disabled: false,
-    };
-  },
+class Switch extends React.Component<Props> {
+  static defaultProps = {
+    value: false,
+    disabled: false,
+  };
 
-  mixins: [NativeMethodsMixin],
+  _rctSwitch: ?React.ElementRef<NativeSwitchType> = null;
 
-  _rctSwitch: {},
-  _onChange: function(event: Object) {
+  _onChange = (event: Object) => {
     if (Platform.OS === 'android') {
-      this._rctSwitch.setNativeProps({on: this.props.value});
+      nullthrows(this._rctSwitch).setNativeProps({on: this.props.value});
     } else {
-      this._rctSwitch.setNativeProps({value: this.props.value});
+      nullthrows(this._rctSwitch).setNativeProps({value: this.props.value});
     }
-    //Change the props after the native props are set in case the props change removes the component
-    /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This comment
-     * suppresses an error when upgrading Flow's support for React. To see the
-     * error delete this comment and run Flow. */
+
     this.props.onChange && this.props.onChange(event);
     this.props.onValueChange &&
       this.props.onValueChange(event.nativeEvent.value);
-  },
+  };
+
+  render() {
+    const props = {
+      ...this.props,
+      onStartShouldSetResponder: () => true,
+      onResponderTerminationRequest: () => false,
+    };
+
+    const platformProps =
+      Platform.OS === 'android'
+        ? {
+            enabled: !this.props.disabled,
+            on: this.props.value,
+            style: this.props.style,
+            trackTintColor: this.props.value
+              ? this.props.onTintColor
+              : this.props.tintColor,
+          }
+        : {
+            style: StyleSheet.compose(styles.rctSwitchIOS, this.props.style),
+          };
 
-  render: function() {
-    const props = {...this.props};
-    props.onStartShouldSetResponder = () => true;
-    props.onResponderTerminationRequest = () => false;
-    if (Platform.OS === 'android') {
-      /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
-       * error found when Flow v0.70 was deployed. To see the error delete
-       * this comment and run Flow. */
-      props.enabled = !this.props.disabled;
-      /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
-       * error found when Flow v0.70 was deployed. To see the error delete
-       * this comment and run Flow. */
-      props.on = this.props.value;
-      props.style = this.props.style;
-      /* $FlowFixMe(>=0.70.0 site=react_native_fb) This comment suppresses an
-       * error found when Flow v0.70 was deployed. To see the error delete
-       * this comment and run Flow. */
-      props.trackTintColor = this.props.value
-        ? this.props.onTintColor
-        : this.props.tintColor;
-    } else if (Platform.OS === 'ios') {
-      props.style = [styles.rctSwitchIOS, this.props.style];
-    }
     return (
       <RCTSwitch
         {...props}
+        {...platformProps}
         ref={ref => {
-          /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This
-          * comment suppresses an error when upgrading Flow's support for React.
-          * To see the error delete this comment and run Flow. */
           this._rctSwitch = ref;
         }}
         onChange={this._onChange}
       />
     );
-  },
-});
+  }
+}
 
 const styles = StyleSheet.create({
   rctSwitchIOS: {
@@ -164,4 +157,4 @@ const styles = StyleSheet.create({
   },
 });
 
-module.exports = ((Switch: any): Class<ReactNative.NativeComponent<Props>>);
+module.exports = Switch;

From f68a04b05be25c27e877708d78662966249364ef Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Mon, 4 Jun 2018 02:22:44 -0700
Subject: [PATCH 0729/1109] Remove duplicated attachWebsocketServer module

Reviewed By: jeanlauliac

Differential Revision: D8248752

fbshipit-source-id: b829de4b0d75d154dd80196b589fe70b0050be4d
---
 local-cli/server/runServer.js                 |  2 +-
 .../server/util/attachWebsocketServer.js      | 76 -------------------
 2 files changed, 1 insertion(+), 77 deletions(-)
 delete mode 100644 local-cli/server/util/attachWebsocketServer.js

diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index e9b5f3e35bba..ed2af28da942 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -18,7 +18,7 @@ const HmrServer = require('metro/src/HmrServer');
 
 const {Terminal} = require('metro-core');
 
-const attachWebsocketServer = require('./util/attachWebsocketServer');
+const attachWebsocketServer = require('metro/src/lib/attachWebsocketServer');
 const compression = require('compression');
 const connect = require('connect');
 const copyToClipBoardMiddleware = require('./middleware/copyToClipBoardMiddleware');
diff --git a/local-cli/server/util/attachWebsocketServer.js b/local-cli/server/util/attachWebsocketServer.js
deleted file mode 100644
index 66f8fe953a4a..000000000000
--- a/local-cli/server/util/attachWebsocketServer.js
+++ /dev/null
@@ -1,76 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- * @flow
- */
-
-'use strict';
-
-import type {Server as HTTPServer} from 'http';
-import type {Server as HTTPSServer} from 'https';
-
-type WebsocketServiceInterface<T> = {
-  +onClientConnect: (
-    url: string,
-    sendFn: (data: string) => mixed,
-  ) => Promise<T>,
-  +onClientDisconnect?: (client: T) => mixed,
-  +onClientError?: (client: T, e: Error) => mixed,
-  +onClientMessage?: (client: T, message: string) => mixed,
-};
-
-type HMROptions<TClient> = {
-  httpServer: HTTPServer | HTTPSServer,
-  websocketServer: WebsocketServiceInterface<TClient>,
-  path: string,
-};
-
-/**
- * Attaches a WebSocket based connection to the Packager to expose
- * Hot Module Replacement updates to the simulator.
- */
-function attachWebsocketServer<TClient: Object>({
-  httpServer,
-  websocketServer,
-  path,
-}: HMROptions<TClient>) {
-  const WebSocketServer = require('ws').Server;
-  const wss = new WebSocketServer({
-    server: httpServer,
-    path: path,
-  });
-
-  wss.on('connection', async ws => {
-    let connected = true;
-    const url = ws.upgradeReq.url;
-
-    const sendFn = (...args) => {
-      if (connected) {
-        ws.send(...args);
-      }
-    };
-
-    const client = await websocketServer.onClientConnect(url, sendFn);
-
-    ws.on('error', e => {
-      websocketServer.onClientError && websocketServer.onClientError(client, e);
-    });
-
-    ws.on('close', () => {
-      websocketServer.onClientDisconnect &&
-        websocketServer.onClientDisconnect(client);
-      connected = false;
-    });
-
-    ws.on('message', message => {
-      websocketServer.onClientMessage &&
-        websocketServer.onClientMessage(client, message);
-    });
-  });
-}
-
-module.exports = attachWebsocketServer;

From 30320f1feda64f9069d96d1e55d098854e5f9ed6 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Mon, 4 Jun 2018 03:12:09 -0700
Subject: [PATCH 0730/1109] Bump metro@0.38.1

Reviewed By: jeanlauliac

Differential Revision: D8248753

fbshipit-source-id: aa6d0da4e96e8b4109b6b5bca050614ec1860fc2
---
 babel-preset/package.json | 2 +-
 package.json              | 8 ++++----
 2 files changed, 5 insertions(+), 5 deletions(-)

diff --git a/babel-preset/package.json b/babel-preset/package.json
index 166e804fd085..77eaafb46f82 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -41,6 +41,6 @@
     "@babel/plugin-transform-template-literals": "7.0.0-beta.47",
     "@babel/plugin-transform-unicode-regex": "7.0.0-beta.47",
     "@babel/template": "7.0.0-beta.47",
-    "metro-babel7-plugin-react-transform": "0.37.0"
+    "metro-babel7-plugin-react-transform": "^0.38.1"
   }
 }
diff --git a/package.json b/package.json
index e51a032af2ab..5c322acca9a6 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.38.0",
-    "metro-babel-register": "^0.38.0",
-    "metro-core": "^0.38.0",
-    "metro-memory-fs": "^0.38.0",
+    "metro": "^0.38.1",
+    "metro-babel-register": "^0.38.1",
+    "metro-core": "^0.38.1",
+    "metro-memory-fs": "^0.38.1",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 4435f087713e1d0ac3639e3b3196d71c6402898e Mon Sep 17 00:00:00 2001
From: Logan Daniels <logand@fb.com>
Date: Mon, 4 Jun 2018 20:49:37 -0700
Subject: [PATCH 0731/1109] Trigger nested VirtualizedLists to re-measure if
 their containing cell's onLayout fires

Reviewed By: sahrens

Differential Revision: D8272040

fbshipit-source-id: c490ffa875bfd0547ac54d214c5ebbeb23c99942
---
 Libraries/Lists/VirtualizedList.js | 15 +++++++++++++--
 1 file changed, 13 insertions(+), 2 deletions(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index d790667e559a..004599e8d76c 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -1074,6 +1074,17 @@ class VirtualizedList extends React.PureComponent<Props, State> {
     } else {
       this._frames[cellKey].inLayout = true;
     }
+
+    const childListKeys = this._cellKeysToChildListKeys.get(cellKey);
+    if (childListKeys) {
+      for (let childKey of childListKeys) {
+        const childList = this._nestedChildLists.get(childKey);
+        childList &&
+          childList.ref &&
+          childList.ref.measureLayoutRelativeToContainingList();
+      }
+    }
+
     this._computeBlankness();
   }
 
@@ -1084,7 +1095,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
     }
   };
 
-  _measureLayoutRelativeToContainingList(): void {
+  measureLayoutRelativeToContainingList(): void {
     UIManager.measureLayout(
       ReactNative.findNodeHandle(this),
       ReactNative.findNodeHandle(
@@ -1113,7 +1124,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
     if (this._isNestedWithSameOrientation()) {
       // Need to adjust our scroll metrics to be relative to our containing
       // VirtualizedList before we can make claims about list item viewability
-      this._measureLayoutRelativeToContainingList();
+      this.measureLayoutRelativeToContainingList();
     } else {
       this._scrollMetrics.visibleLength = this._selectLength(
         e.nativeEvent.layout,

From de18dd2648e72f156da1b99ec945dae8b30b0b45 Mon Sep 17 00:00:00 2001
From: Sokovikov <skv-headless@yandex.ru>
Date: Tue, 5 Jun 2018 05:52:18 -0700
Subject: [PATCH 0732/1109] skip dismiss all if all rows are hidden (#19564)

Summary:
Small fix based on
https://github.com/facebook/react-native/pull/19501#issuecomment-394486884

No need to mention it

[GENERAL] [BUGFIX] [YellowBox] - Message
Closes https://github.com/facebook/react-native/pull/19564

Differential Revision: D8276808

Pulled By: hramos

fbshipit-source-id: 59832d3d6e60ae30afbeb7c9303405746e9eec45
---
 Libraries/ReactNative/YellowBox.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/ReactNative/YellowBox.js b/Libraries/ReactNative/YellowBox.js
index f1e756a8a4c4..5ad6311b73b6 100644
--- a/Libraries/ReactNative/YellowBox.js
+++ b/Libraries/ReactNative/YellowBox.js
@@ -424,7 +424,7 @@ class YellowBox extends React.Component<
     ];
     return (
       <View style={inspector ? styles.fullScreen : listStyle}>
-        {!inspector && (
+        {!inspector && rows.length > 0 && (
           <TouchableHighlight
             style={styles.dismissAllContainer}
             onPress={() => this.dismissWarning(null)}>

From e95e73aaa7a06500e7db961613d5edb8ecf3d0d7 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 5 Jun 2018 13:12:59 -0700
Subject: [PATCH 0733/1109] Fix events not working after closing and navigating
 back to Fabric screen in FB4A

Reviewed By: fkgozali

Differential Revision: D8240344

fbshipit-source-id: 992945f94843589cefdf7ea24da709449ee38778
---
 .../facebook/react/fabric/FabricUIManager.java  |  7 ++++++-
 .../react/uimanager/events/EventDispatcher.java |  5 ++++-
 .../uimanager/events/ReactEventEmitter.java     | 17 ++++-------------
 3 files changed, 14 insertions(+), 15 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 0a35242d1128..91098711e198 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -66,6 +66,7 @@ public class FabricUIManager implements UIManager, JSHandler {
   private final FabricReconciler mFabricReconciler;
   private final EventDispatcher mEventDispatcher;
   private FabricBinding mBinding;
+  private final FabricEventEmitter mFabricEventEmitter;
   private long mEventHandlerPointer;
 
   public FabricUIManager(
@@ -81,6 +82,8 @@ public FabricUIManager(
         new UIViewOperationQueue(
             reactContext, mNativeViewHierarchyManager, 0);
     mFabricReconciler = new FabricReconciler(mUIViewOperationQueue);
+    mFabricEventEmitter =
+      new FabricEventEmitter(mReactApplicationContext, this);
     mEventDispatcher = eventDispatcher;
     mJSContext = jsContext;
   }
@@ -537,12 +540,14 @@ public void invoke(long eventTarget, String name, WritableMap params) {
   public void initialize() {
     FabricEventEmitter eventEmitter =
       new FabricEventEmitter(mReactApplicationContext, this);
-    mEventDispatcher.registerEventEmitter(FABRIC, eventEmitter);
+    mEventDispatcher.registerEventEmitter(FABRIC, mFabricEventEmitter);
   }
 
   @Override
   public void onCatalystInstanceDestroy() {
     mBinding.releaseEventHandler(mJSContext.get(), mEventHandlerPointer);
+    mEventDispatcher.unregisterEventEmitter(FABRIC);
+    mFabricEventEmitter.close();
   }
 
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
index cd8b44eb943a..d983eebebad5 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
@@ -161,7 +161,6 @@ public void onHostPause() {
   @Override
   public void onHostDestroy() {
     stopFrameCallback();
-    mReactEventEmitter.stop();
   }
 
   public void onCatalystInstanceDestroyed() {
@@ -254,6 +253,10 @@ public void registerEventEmitter(@UIManagerType int uiManagerType, RCTEventEmitt
     mReactEventEmitter.register(uiManagerType, eventEmitter);
   }
 
+  public void unregisterEventEmitter(@UIManagerType int uiManagerType) {
+    mReactEventEmitter.unregister(uiManagerType);
+  }
+
   private class ScheduleDispatchFrameCallback extends ChoreographerCompat.FrameCallback {
     private volatile boolean mIsPosted = false;
     private boolean mShouldStop = false;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
index c54af221290a..5d07b3564777 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
@@ -31,6 +31,10 @@ public void register(@UIManagerType int uiManagerType, RCTEventEmitter eventEmit
     mEventEmitters.put(uiManagerType, eventEmitter);
   }
 
+  public void unregister(@UIManagerType int uiManagerType) {
+    mEventEmitters.remove(uiManagerType);
+  }
+
   @Override
   public void receiveEvent(int targetReactTag, String eventName, @Nullable WritableMap event) {
     getEventEmitter(targetReactTag).receiveEvent(targetReactTag, eventName, event);
@@ -52,17 +56,4 @@ private RCTEventEmitter getEventEmitter(int reactTag) {
     int type = ViewUtil.getUIManagerType(reactTag);
     return mEventEmitters.get(type);
   }
-
-  public void stop() {
-    for (int i = 0 ; i < mEventEmitters.size() ; i++) {
-      RCTEventEmitter eventEmitter = mEventEmitters.valueAt(i);
-      if (eventEmitter instanceof Closeable) {
-        try {
-          ((Closeable) eventEmitter).close();
-        } catch (IOException e) {
-          Log.i(TAG, "Exception when closing EventEmitter: " + eventEmitter, e);
-        }
-      }
-    }
-  }
 }

From e09c56af970ba76a928117194d198200dc48e3f0 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 5 Jun 2018 13:13:03 -0700
Subject: [PATCH 0734/1109] Enable proguard for Fabric in release builds

Reviewed By: shergin

Differential Revision: D8247814

fbshipit-source-id: 94ed8a767fcf4f6093646618a5691ff17753ffe0
---
 .../react/fabric/FabricUIManager.java         | 20 ++++++++++++++++++-
 1 file changed, 19 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 91098711e198..588d7bc596f8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -15,6 +15,7 @@
 import android.util.Log;
 import android.view.View;
 import com.facebook.infer.annotation.Assertions;
+import com.facebook.proguard.annotations.DoNotStrip;
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableArray;
@@ -51,6 +52,7 @@
  * API.
  */
 @SuppressWarnings("unused") // used from JNI
+@DoNotStrip
 public class FabricUIManager implements UIManager, JSHandler {
 
   private static final String TAG = FabricUIManager.class.getSimpleName();
@@ -94,6 +96,7 @@ public void setBinding(FabricBinding binding) {
 
   /** Creates a new {@link ReactShadowNode} */
   @Nullable
+  @DoNotStrip
   public ReactShadowNode createNode(
       int reactTag, String viewName, int rootTag, ReadableNativeMap props, long instanceHandle) {
     if (DEBUG) {
@@ -145,6 +148,7 @@ private ReactStylesDiffMap updateProps(ReactShadowNode node, @Nullable ReadableN
    *     including its children set (note that the children nodes will not be cloned).
    */
   @Nullable
+  @DoNotStrip
   public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
     if (DEBUG) {
       Log.d(TAG, "cloneNode \n\tnode: " + node);
@@ -165,6 +169,7 @@ public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
    *     children set will be empty.
    */
   @Nullable
+  @DoNotStrip
   public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long instanceHandle) {
     if (DEBUG) {
       Log.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
@@ -185,6 +190,7 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long insta
    *     props will be overridden with the {@link ReadableMap} received by parameter.
    */
   @Nullable
+  @DoNotStrip
   public ReactShadowNode cloneNodeWithNewProps(
       ReactShadowNode node, @Nullable ReadableNativeMap newProps, long instanceHandle) {
     if (DEBUG) {
@@ -208,6 +214,7 @@ public ReactShadowNode cloneNodeWithNewProps(
    *     children set will be empty.
    */
   @Nullable
+  @DoNotStrip
   public ReactShadowNode cloneNodeWithNewChildrenAndProps(
       ReactShadowNode node, ReadableNativeMap newProps, long instanceHandle) {
     if (DEBUG) {
@@ -242,6 +249,7 @@ private void assertReactShadowNodeCopy(ReactShadowNode source, ReactShadowNode t
    * ReactShadowNode}.
    */
   @Nullable
+  @DoNotStrip
   public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
     if (DEBUG) {
       Log.d(TAG, "appendChild \n\tparent: " + parent + "\n\tchild: " + child);
@@ -263,6 +271,7 @@ public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
    * @return an empty {@link List<ReactShadowNode>} that will be used to append the {@link
    *     ReactShadowNode} elements of the root. Typically this List will contain one element.
    */
+  @DoNotStrip
   public List<ReactShadowNode> createChildSet(int rootTag) {
     if (DEBUG) {
       Log.d(TAG, "createChildSet rootTag: " + rootTag);
@@ -273,10 +282,12 @@ public List<ReactShadowNode> createChildSet(int rootTag) {
   /**
    * Adds the {@link ReactShadowNode} to the {@link List<ReactShadowNode>} received by parameter.
    */
+  @DoNotStrip
   public void appendChildToSet(List<ReactShadowNode> childList, ReactShadowNode child) {
     childList.add(child);
   }
 
+  @DoNotStrip
   public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNode> childList) {
     try {
       childList = childList == null ? new LinkedList<ReactShadowNode>() : childList;
@@ -383,6 +394,7 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
   }
 
   @Override
+  @DoNotStrip
   public <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(
       final T rootView) {
     final int rootTag = ReactRootViewTagGenerator.getNextRootViewTag();
@@ -409,6 +421,7 @@ public void onSizeChanged(final int width, final int height, int oldW, int oldH)
   }
 
   @Override
+  @DoNotStrip
   public void updateRootLayoutSpecs(int rootViewTag, int widthMeasureSpec, int heightMeasureSpec) {
     ReactShadowNode rootNode = mRootShadowNodeRegistry.getNode(rootViewTag);
     if (rootNode == null) {
@@ -458,7 +471,7 @@ private ReactShadowNode createRootShadowNode(int rootTag, ThemedReactContext the
    * Updates the styles of the {@link ReactShadowNode} based on the Measure specs received by
    * parameters.
    */
-  public void updateRootView(
+  private void updateRootView(
       ReactShadowNode node, int widthMeasureSpec, int heightMeasureSpec) {
     int widthMode = View.MeasureSpec.getMode(widthMeasureSpec);
     int widthSize = View.MeasureSpec.getSize(widthMeasureSpec);
@@ -502,6 +515,7 @@ private void handleException(ReactShadowNode node, Throwable t) {
   }
 
   @Nullable
+  @DoNotStrip
   public long createEventTarget(int reactTag) {
     long instanceHandle = mNativeViewHierarchyManager.getInstanceHandle(reactTag);
     long context = mJSContext.get();
@@ -514,19 +528,23 @@ public long createEventTarget(int reactTag) {
     return eventTarget;
   }
 
+  @DoNotStrip
   public void registerEventHandler(long eventHandlerPointer) {
     mEventHandlerPointer = eventHandlerPointer;
   }
 
+  @DoNotStrip
   public void releaseEventTarget(long eventTargetPointer) {
     mBinding.releaseEventTarget(mJSContext.get(), eventTargetPointer);
   }
 
+  @DoNotStrip
   public void releaseEventHandler(long eventHandlerPointer) {
     mBinding.releaseEventHandler(mJSContext.get(), eventHandlerPointer);
   }
 
   @Override
+  @DoNotStrip
   public void invoke(long eventTarget, String name, WritableMap params) {
     if (DEBUG) {
       Log.d(

From a8b74576da6f1a42fde4e39f97e88c8f45a3a51d Mon Sep 17 00:00:00 2001
From: Eli Perkins <eli@clubhouse.io>
Date: Tue, 5 Jun 2018 14:14:17 -0700
Subject: [PATCH 0735/1109] Use correct library reference for libfishhook.a in
 RCTWebSocket (#19579)

Summary:
This uses the reference for `libfishhook.a` from the Products, rather than
the reference from the Frameworks group.

This fixes the build for the new Xcode build system, on both Xcode 9 and
Xcode 10.

Fixes #19569

- Using Xcode 10:
	- Open `RNTester/RNTester.xcodeproj`
	- Build RNTester, noting build errors
- Using Xcode 9:
	- Open `RNTester/RNTester.xcodeproj`
	- Switch to using new build system in `File > Project Settings > Build System`, selecting `New Build System (Preview)`
	- Build RNTester, noting build errors

none

[IOS] [BUGFIX] [RCTWebSocket] - Fix build for new Xcode build system
Closes https://github.com/facebook/react-native/pull/19579

Differential Revision: D8287487

Pulled By: hramos

fbshipit-source-id: 5bfc9decb09ebc763824df8474b5897099d39ad7
---
 Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
index 525452a558c4..f5e60eb16698 100644
--- a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
+++ b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
@@ -9,7 +9,7 @@
 /* Begin PBXBuildFile section */
 		1338BBE01B04ACC80064A9C9 /* RCTSRWebSocket.m in Sources */ = {isa = PBXBuildFile; fileRef = 1338BBDD1B04ACC80064A9C9 /* RCTSRWebSocket.m */; };
 		1338BBE11B04ACC80064A9C9 /* RCTWebSocketExecutor.m in Sources */ = {isa = PBXBuildFile; fileRef = 1338BBDF1B04ACC80064A9C9 /* RCTWebSocketExecutor.m */; };
-		13526A521F362F7F0008EF00 /* libfishhook.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 13526A511F362F7F0008EF00 /* libfishhook.a */; };
+		2D3ABDC220C7206E00DF56E9 /* libfishhook.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 3DBE0D001F3B181A0099AA32 /* libfishhook.a */; };
 		2D3B5F3D1D9B165B00451313 /* RCTSRWebSocket.m in Sources */ = {isa = PBXBuildFile; fileRef = 1338BBDD1B04ACC80064A9C9 /* RCTSRWebSocket.m */; };
 		2D3B5F3E1D9B165B00451313 /* RCTWebSocketExecutor.m in Sources */ = {isa = PBXBuildFile; fileRef = 1338BBDF1B04ACC80064A9C9 /* RCTWebSocketExecutor.m */; };
 		2D3B5F401D9B165B00451313 /* RCTWebSocketModule.m in Sources */ = {isa = PBXBuildFile; fileRef = 3C86DF7B1ADF695F0047B81A /* RCTWebSocketModule.m */; };
@@ -87,7 +87,7 @@
 			isa = PBXFrameworksBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
-				13526A521F362F7F0008EF00 /* libfishhook.a in Frameworks */,
+				2D3ABDC220C7206E00DF56E9 /* libfishhook.a in Frameworks */,
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};
@@ -435,7 +435,7 @@
 				EXECUTABLE_PREFIX = lib;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
-          "RCT_METRO_PORT=${RCT_METRO_PORT}",
+					"RCT_METRO_PORT=${RCT_METRO_PORT}",
 					"$(inherited)",
 				);
 				GCC_TREAT_WARNINGS_AS_ERRORS = NO;

From 1853e1519030caaeeb7f31017d98823aa5696daf Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 5 Jun 2018 18:51:26 -0700
Subject: [PATCH 0736/1109] Add open source Flow declaration for Metro module

Summary:
Fix Flow failure by adding a declaration to the Flow config used in open source. This did not get caught internally because we use a different Flow config.

Release Notes
-------------
[INTERNAL] [MINOR] [Flow] - Fix Flow config.

Reviewed By: rafeca

Differential Revision: D8257641

fbshipit-source-id: 3f4b2cbe622b2e76aa018e9369216a6b9ac25f47
---
 flow-github/metro.js | 8 ++++++--
 1 file changed, 6 insertions(+), 2 deletions(-)

diff --git a/flow-github/metro.js b/flow-github/metro.js
index db5dbdc28c7a..2e262712c5ae 100644
--- a/flow-github/metro.js
+++ b/flow-github/metro.js
@@ -12,14 +12,18 @@ declare module 'metro' {
   declare module.exports: any;
 }
 
-declare module 'metro/src/lib/TerminalReporter' {
+declare module 'metro/src/HmrServer' {
   declare module.exports: any;
 }
 
-declare module 'metro/src/HmrServer' {
+declare module 'metro/src/lib/attachWebsocketServer' {
   declare module.exports: any;
 }
 
 declare module 'metro/src/lib/bundle-modules/HMRClient' {
   declare module.exports: any;
 }
+
+declare module 'metro/src/lib/TerminalReporter' {
+  declare module.exports: any;
+}

From 3a1d949906acb0c3b44d125d54d0c99305bbbb56 Mon Sep 17 00:00:00 2001
From: Cedric van Putten <me@bycedric.com>
Date: Tue, 5 Jun 2018 19:21:29 -0700
Subject: [PATCH 0737/1109] Fix/security issues (#19373)

Summary:
This updates both [`react-devtools-core`](https://github.com/facebook/react-devtools/issues/941) and [`plist`](https://github.com/TooTallNate/plist.js/commit/04c8ee7646d4abcfe13b3fdc3037b75047069ead) to include security fixes, reported by `npm audit`.

Fixes #18854

_Only dependencies are updated with security patches, no change in actual code._

_Only dependencies are updated with security patches, no change in actual code._

[GENERAL] [ENHANCEMENT] [react-devtools-core] - Bump to `3.2.2` for a security fix for `ws`
[GENERAL] [ENHANCEMENT] [plist] - Bump to `3.0.0` for a security fix for `xmlbuilder`

Closes https://github.com/facebook/react-native/pull/19373

Reviewed By: sophiebits

Differential Revision: D8149200

Pulled By: hramos

fbshipit-source-id: 732fd627b232c315be60ed2da432742e8256a38a
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index 5c322acca9a6..9eb0e2bb5560 100644
--- a/package.json
+++ b/package.json
@@ -180,12 +180,12 @@
     "npmlog": "^2.0.4",
     "opn": "^3.0.2",
     "optimist": "^0.6.1",
-    "plist": "^1.2.0",
+    "plist": "^3.0.0",
     "pretty-format": "^4.2.1",
     "promise": "^7.1.1",
     "prop-types": "^15.5.8",
     "react-clone-referenced-element": "^1.0.1",
-    "react-devtools-core": "3.1.0",
+    "react-devtools-core": "^3.2.2",
     "react-timer-mixin": "^0.13.2",
     "regenerator-runtime": "^0.11.0",
     "rimraf": "^2.5.4",

From 29fb2a8e90fa3811f9485d4b89d9dbcfffea93a6 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Wed, 6 Jun 2018 05:20:40 -0700
Subject: [PATCH 0738/1109] Bump Prettier to 1.13.4 on xplat

Summary:
Bump Prettier to use version 1.13.4
All code changes are caused by running Prettier and should only affect files that have an `format` header.
All other changes caused by yarn.

Reviewed By: ryanmce

Differential Revision: D8251255

fbshipit-source-id: 0b4445c35f1269d72730f2000002a27c1bc35914
---
 Libraries/ART/ReactNativeART.js               |  4 ++--
 Libraries/Animated/src/Easing.js              |  4 ++--
 .../Animated/src/__tests__/Easing-test.js     |  2 +-
 .../Animated/src/animations/DecayAnimation.js |  3 +--
 .../src/animations/SpringAnimation.js         |  4 ++--
 .../src/nodes/AnimatedInterpolation.js        |  2 +-
 .../Animated/src/nodes/AnimatedModulo.js      |  2 +-
 Libraries/Color/normalizeColor.js             |  2 +-
 .../Keyboard/KeyboardAvoidingView.js          | 19 ++++++++++++++-----
 Libraries/Components/Slider/Slider.js         |  5 ++++-
 Libraries/Components/Switch/Switch.js         |  5 ++++-
 Libraries/Lists/FlatList.js                   |  6 +++++-
 Libraries/Lists/VirtualizedList.js            |  2 +-
 Libraries/Lists/VirtualizedSectionList.js     |  2 +-
 Libraries/ReactNative/YellowBox.js            | 15 ++++++++-------
 Libraries/StyleSheet/processTransform.js      |  2 +-
 Libraries/Utilities/MatrixMath.js             |  2 +-
 .../Utilities/__tests__/MatrixMath-test.js    |  2 +-
 Libraries/WebSocket/WebSocket.js              |  7 ++++++-
 RNTester/js/AlertExample.js                   |  5 +++--
 RNTester/js/AnimatedGratuitousApp/AnExApp.js  |  5 +++--
 RNTester/js/DatePickerIOSExample.js           |  2 +-
 RNTester/js/ImageExample.js                   |  2 +-
 RNTester/js/InputAccessoryViewExample.js      |  3 ++-
 RNTester/js/KeyboardAvoidingViewExample.js    |  3 ++-
 RNTester/js/ListExampleShared.js              |  2 +-
 RNTester/js/ListViewExample.js                |  2 +-
 RNTester/js/MaskedViewExample.js              |  3 ++-
 RNTester/js/PickerExample.js                  |  3 ++-
 RNTester/js/RTLExample.js                     |  3 ++-
 RNTester/js/ScrollViewSimpleExample.js        |  3 ++-
 RNTester/js/SwipeableListViewExample.js       |  2 +-
 RNTester/js/ToastAndroidExample.android.js    |  3 ++-
 .../js/ViewPagerAndroidExample.android.js     |  5 +++--
 local-cli/bundle/saveAssets.js                |  3 +--
 .../link/android/patches/makeBuildPatch.js    |  2 +-
 package.json                                  |  2 +-
 37 files changed, 88 insertions(+), 55 deletions(-)

diff --git a/Libraries/ART/ReactNativeART.js b/Libraries/ART/ReactNativeART.js
index 465ddc6b13f2..760b5ff809de 100644
--- a/Libraries/ART/ReactNativeART.js
+++ b/Libraries/ART/ReactNativeART.js
@@ -297,7 +297,7 @@ function insertOffsetsIntoArray(stops, targetArray, atIndex, multi, reverse) {
   let i = 0;
   if ('length' in stops) {
     while (i < stops.length) {
-      offsetNumber = i / (stops.length - 1) * multi;
+      offsetNumber = (i / (stops.length - 1)) * multi;
       targetArray[atIndex + i] = reverse ? 1 - offsetNumber : offsetNumber;
       i++;
     }
@@ -530,7 +530,7 @@ function LinearGradient(stops, x1, y1, x2, y2) {
   const type = LINEAR_GRADIENT;
 
   if (arguments.length < 5) {
-    const angle = (x1 == null ? 270 : x1) * Math.PI / 180;
+    const angle = ((x1 == null ? 270 : x1) * Math.PI) / 180;
 
     let x = Math.cos(angle);
     let y = -Math.sin(angle);
diff --git a/Libraries/Animated/src/Easing.js b/Libraries/Animated/src/Easing.js
index c5e54b24723e..94fb865882c0 100644
--- a/Libraries/Animated/src/Easing.js
+++ b/Libraries/Animated/src/Easing.js
@@ -131,7 +131,7 @@ class Easing {
    * http://easings.net/#easeInSine
    */
   static sin(t: number) {
-    return 1 - Math.cos(t * Math.PI / 2);
+    return 1 - Math.cos((t * Math.PI) / 2);
   }
 
   /**
@@ -164,7 +164,7 @@ class Easing {
    */
   static elastic(bounciness: number = 1): (t: number) => number {
     const p = bounciness * Math.PI;
-    return t => 1 - Math.pow(Math.cos(t * Math.PI / 2), 3) * Math.cos(t * p);
+    return t => 1 - Math.pow(Math.cos((t * Math.PI) / 2), 3) * Math.cos(t * p);
   }
 
   /**
diff --git a/Libraries/Animated/src/__tests__/Easing-test.js b/Libraries/Animated/src/__tests__/Easing-test.js
index 1e2a3a2f4a7c..0284f3f0b697 100644
--- a/Libraries/Animated/src/__tests__/Easing-test.js
+++ b/Libraries/Animated/src/__tests__/Easing-test.js
@@ -81,7 +81,7 @@ describe('Easing', () => {
 
   function sampleEasingFunction(easing) {
     const DURATION = 300;
-    const tickCount = Math.round(DURATION * 60 / 1000);
+    const tickCount = Math.round((DURATION * 60) / 1000);
     const samples = [];
     for (let i = 0; i <= tickCount; i++) {
       samples.push(easing(i / tickCount));
diff --git a/Libraries/Animated/src/animations/DecayAnimation.js b/Libraries/Animated/src/animations/DecayAnimation.js
index 78f6e2b7cc85..a6fe05bb3f63 100644
--- a/Libraries/Animated/src/animations/DecayAnimation.js
+++ b/Libraries/Animated/src/animations/DecayAnimation.js
@@ -81,8 +81,7 @@ class DecayAnimation extends Animation {
 
     const value =
       this._fromValue +
-      this._velocity /
-        (1 - this._deceleration) *
+      (this._velocity / (1 - this._deceleration)) *
         (1 - Math.exp(-(1 - this._deceleration) * (now - this._startTime)));
 
     this._onUpdate(value);
diff --git a/Libraries/Animated/src/animations/SpringAnimation.js b/Libraries/Animated/src/animations/SpringAnimation.js
index 2bc610eed752..a0f38d3b024e 100644
--- a/Libraries/Animated/src/animations/SpringAnimation.js
+++ b/Libraries/Animated/src/animations/SpringAnimation.js
@@ -266,7 +266,7 @@ class SpringAnimation extends Animation {
       position =
         this._toValue -
         envelope *
-          ((v0 + zeta * omega0 * x0) / omega1 * Math.sin(omega1 * t) +
+          (((v0 + zeta * omega0 * x0) / omega1) * Math.sin(omega1 * t) +
             x0 * Math.cos(omega1 * t));
       // This looks crazy -- it's actually just the derivative of the
       // oscillation function
@@ -274,7 +274,7 @@ class SpringAnimation extends Animation {
         zeta *
           omega0 *
           envelope *
-          (Math.sin(omega1 * t) * (v0 + zeta * omega0 * x0) / omega1 +
+          ((Math.sin(omega1 * t) * (v0 + zeta * omega0 * x0)) / omega1 +
             x0 * Math.cos(omega1 * t)) -
         envelope *
           (Math.cos(omega1 * t) * (v0 + zeta * omega0 * x0) -
diff --git a/Libraries/Animated/src/nodes/AnimatedInterpolation.js b/Libraries/Animated/src/nodes/AnimatedInterpolation.js
index e8f9823c20e4..067efbca731f 100644
--- a/Libraries/Animated/src/nodes/AnimatedInterpolation.js
+++ b/Libraries/Animated/src/nodes/AnimatedInterpolation.js
@@ -358,7 +358,7 @@ class AnimatedInterpolation extends AnimatedWithChildren {
       }
       if (/deg$/.test(value)) {
         const degrees = parseFloat(value) || 0;
-        const radians = degrees * Math.PI / 180.0;
+        const radians = (degrees * Math.PI) / 180.0;
         return radians;
       } else {
         // Assume radians
diff --git a/Libraries/Animated/src/nodes/AnimatedModulo.js b/Libraries/Animated/src/nodes/AnimatedModulo.js
index 6699ded50a65..a3968566e9a2 100644
--- a/Libraries/Animated/src/nodes/AnimatedModulo.js
+++ b/Libraries/Animated/src/nodes/AnimatedModulo.js
@@ -32,7 +32,7 @@ class AnimatedModulo extends AnimatedWithChildren {
 
   __getValue(): number {
     return (
-      (this._a.__getValue() % this._modulus + this._modulus) % this._modulus
+      ((this._a.__getValue() % this._modulus) + this._modulus) % this._modulus
     );
   }
 
diff --git a/Libraries/Color/normalizeColor.js b/Libraries/Color/normalizeColor.js
index 690090b8c9ca..edede79ee6e2 100755
--- a/Libraries/Color/normalizeColor.js
+++ b/Libraries/Color/normalizeColor.js
@@ -188,7 +188,7 @@ function parse255(str: string): number {
 
 function parse360(str: string): number {
   const int = parseFloat(str);
-  return ((int % 360 + 360) % 360) / 360;
+  return (((int % 360) + 360) % 360) / 360;
 }
 
 function parse1(str: string): number {
diff --git a/Libraries/Components/Keyboard/KeyboardAvoidingView.js b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
index 104fabd0f53a..4973fd4a0a38 100644
--- a/Libraries/Components/Keyboard/KeyboardAvoidingView.js
+++ b/Libraries/Components/Keyboard/KeyboardAvoidingView.js
@@ -171,7 +171,10 @@ class KeyboardAvoidingView extends React.Component<Props, State> {
         return (
           <View
             ref={viewRef}
-            style={StyleSheet.compose(style, heightStyle)}
+            style={StyleSheet.compose(
+              style,
+              heightStyle,
+            )}
             onLayout={this._onLayout}
             {...props}>
             {children}
@@ -186,9 +189,12 @@ class KeyboardAvoidingView extends React.Component<Props, State> {
             onLayout={this._onLayout}
             {...props}>
             <View
-              style={StyleSheet.compose(contentContainerStyle, {
-                bottom: bottomHeight,
-              })}>
+              style={StyleSheet.compose(
+                contentContainerStyle,
+                {
+                  bottom: bottomHeight,
+                },
+              )}>
               {children}
             </View>
           </View>
@@ -198,7 +204,10 @@ class KeyboardAvoidingView extends React.Component<Props, State> {
         return (
           <View
             ref={viewRef}
-            style={StyleSheet.compose(style, {paddingBottom: bottomHeight})}
+            style={StyleSheet.compose(
+              style,
+              {paddingBottom: bottomHeight},
+            )}
             onLayout={this._onLayout}
             {...props}>
             {children}
diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index a7998ef28bfc..aacfb14f34cb 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -199,7 +199,10 @@ const Slider = (
     forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
   |}>,
 ) => {
-  const style = StyleSheet.compose(styles.slider, props.style);
+  const style = StyleSheet.compose(
+    styles.slider,
+    props.style,
+  );
 
   const onValueChange =
     props.onValueChange &&
diff --git a/Libraries/Components/Switch/Switch.js b/Libraries/Components/Switch/Switch.js
index c1d38619a6ac..39ccd9a1de16 100644
--- a/Libraries/Components/Switch/Switch.js
+++ b/Libraries/Components/Switch/Switch.js
@@ -134,7 +134,10 @@ class Switch extends React.Component<Props> {
               : this.props.tintColor,
           }
         : {
-            style: StyleSheet.compose(styles.rctSwitchIOS, this.props.style),
+            style: StyleSheet.compose(
+              styles.rctSwitchIOS,
+              this.props.style,
+            ),
           };
 
     return (
diff --git a/Libraries/Lists/FlatList.js b/Libraries/Lists/FlatList.js
index c9b1b94c9104..cfa4ae858088 100644
--- a/Libraries/Lists/FlatList.js
+++ b/Libraries/Lists/FlatList.js
@@ -614,7 +614,11 @@ class FlatList<ItemT> extends React.PureComponent<Props<ItemT>, void> {
         'Expected array of items with numColumns > 1',
       );
       return (
-        <View style={StyleSheet.compose(styles.row, columnWrapperStyle)}>
+        <View
+          style={StyleSheet.compose(
+            styles.row,
+            columnWrapperStyle,
+          )}>
           {item.map((it, kk) => {
             const element = renderItem({
               item: it,
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 004599e8d76c..56364823f06d 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -1369,7 +1369,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
       /* $FlowFixMe(>=0.63.0 site=react_native_fb) This comment suppresses an
        * error found when Flow v0.63 was deployed. To see the error delete
        * this comment and run Flow. */
-      this.props.onEndReachedThreshold * visibleLength / 2;
+      (this.props.onEndReachedThreshold * visibleLength) / 2;
     // Mark as high priority if we're close to the start of the first item
     // But only if there are items before the first rendered item
     if (first > 0) {
diff --git a/Libraries/Lists/VirtualizedSectionList.js b/Libraries/Lists/VirtualizedSectionList.js
index 63c7d9ecdcb6..616d976bbe12 100644
--- a/Libraries/Lists/VirtualizedSectionList.js
+++ b/Libraries/Lists/VirtualizedSectionList.js
@@ -457,7 +457,7 @@ class ItemWithSeparator extends React.Component<
   static getDerivedStateFromProps(
     props: ItemWithSeparatorProps,
     prevState: ItemWithSeparatorState,
-  ): ?ItemWithSeparatorState  {
+  ): ?ItemWithSeparatorState {
     return {
       separatorProps: {
         ...prevState.separatorProps,
diff --git a/Libraries/ReactNative/YellowBox.js b/Libraries/ReactNative/YellowBox.js
index 5ad6311b73b6..01a4bd82dee6 100644
--- a/Libraries/ReactNative/YellowBox.js
+++ b/Libraries/ReactNative/YellowBox.js
@@ -424,13 +424,14 @@ class YellowBox extends React.Component<
     ];
     return (
       <View style={inspector ? styles.fullScreen : listStyle}>
-        {!inspector && rows.length > 0 && (
-          <TouchableHighlight
-            style={styles.dismissAllContainer}
-            onPress={() => this.dismissWarning(null)}>
-            <Text style={styles.dismissAll}>Dismiss All</Text>
-          </TouchableHighlight>
-        )}
+        {!inspector &&
+          rows.length > 0 && (
+            <TouchableHighlight
+              style={styles.dismissAllContainer}
+              onPress={() => this.dismissWarning(null)}>
+              <Text style={styles.dismissAll}>Dismiss All</Text>
+            </TouchableHighlight>
+          )}
         <ScrollView style={listStyle} scrollsToTop={false}>
           {rows}
         </ScrollView>
diff --git a/Libraries/StyleSheet/processTransform.js b/Libraries/StyleSheet/processTransform.js
index 9bcfd4f4b65e..e9076493c289 100644
--- a/Libraries/StyleSheet/processTransform.js
+++ b/Libraries/StyleSheet/processTransform.js
@@ -133,7 +133,7 @@ function _multiplyTransform(
  */
 function _convertToRadians(value: string): number {
   const floatValue = parseFloat(value);
-  return value.indexOf('rad') > -1 ? floatValue : floatValue * Math.PI / 180;
+  return value.indexOf('rad') > -1 ? floatValue : (floatValue * Math.PI) / 180;
 }
 
 function _validateTransforms(transform: Array<Object>): void {
diff --git a/Libraries/Utilities/MatrixMath.js b/Libraries/Utilities/MatrixMath.js
index 6a523fa4a4a4..bb91c1d32918 100755
--- a/Libraries/Utilities/MatrixMath.js
+++ b/Libraries/Utilities/MatrixMath.js
@@ -719,7 +719,7 @@ const MatrixMath = {
         0,
         0,
         MatrixMath.roundTo3Places(
-          Math.atan2(row[0][1], row[0][0]) * 180 / Math.PI,
+          (Math.atan2(row[0][1], row[0][0]) * 180) / Math.PI,
         ),
       ];
     } else {
diff --git a/Libraries/Utilities/__tests__/MatrixMath-test.js b/Libraries/Utilities/__tests__/MatrixMath-test.js
index 8a779d3676bf..e70fbed91477 100644
--- a/Libraries/Utilities/__tests__/MatrixMath-test.js
+++ b/Libraries/Utilities/__tests__/MatrixMath-test.js
@@ -13,7 +13,7 @@
 const MatrixMath = require('MatrixMath');
 
 function degreesToRadians(degrees) {
-  return degrees * Math.PI / 180;
+  return (degrees * Math.PI) / 180;
 }
 
 function convertZeroes(degrees) {
diff --git a/Libraries/WebSocket/WebSocket.js b/Libraries/WebSocket/WebSocket.js
index 578d55e55d9c..bef05b0d70e8 100644
--- a/Libraries/WebSocket/WebSocket.js
+++ b/Libraries/WebSocket/WebSocket.js
@@ -145,7 +145,12 @@ class WebSocket extends EventTarget(...WEBSOCKET_EVENTS) {
     this._eventEmitter = new NativeEventEmitter(WebSocketModule);
     this._socketId = nextWebSocketId++;
     this._registerEvents();
-    WebSocketModule.connect(url, protocols, {headers}, this._socketId);
+    WebSocketModule.connect(
+      url,
+      protocols,
+      {headers},
+      this._socketId,
+    );
   }
 
   get binaryType(): ?BinaryType {
diff --git a/RNTester/js/AlertExample.js b/RNTester/js/AlertExample.js
index 02382e769ebb..b573356919d8 100644
--- a/RNTester/js/AlertExample.js
+++ b/RNTester/js/AlertExample.js
@@ -121,8 +121,9 @@ class SimpleAlertExampleBlock extends React.Component {
 class AlertExample extends React.Component {
   static title = 'Alert';
 
-  static description = 'Alerts display a concise and informative message ' +
-  'and prompt the user to make a decision.';
+  static description =
+    'Alerts display a concise and informative message ' +
+    'and prompt the user to make a decision.';
 
   render() {
     return (
diff --git a/RNTester/js/AnimatedGratuitousApp/AnExApp.js b/RNTester/js/AnimatedGratuitousApp/AnExApp.js
index 1ade55e2ffc8..5131f9641ca5 100644
--- a/RNTester/js/AnimatedGratuitousApp/AnExApp.js
+++ b/RNTester/js/AnimatedGratuitousApp/AnExApp.js
@@ -193,8 +193,9 @@ class Circle extends React.Component<any, any> {
 
 class AnExApp extends React.Component<any, any> {
   static title = 'Animated - Gratuitous App';
-  static description = 'Bunch of Animations - tap a circle to ' +
-  'open a view with more animations, or longPress and drag to reorder circles.';
+  static description =
+    'Bunch of Animations - tap a circle to ' +
+    'open a view with more animations, or longPress and drag to reorder circles.';
 
   _onMove: (position: Point) => void;
   constructor(props: any): void {
diff --git a/RNTester/js/DatePickerIOSExample.js b/RNTester/js/DatePickerIOSExample.js
index 5bd76259742e..ec338471d693 100644
--- a/RNTester/js/DatePickerIOSExample.js
+++ b/RNTester/js/DatePickerIOSExample.js
@@ -20,7 +20,7 @@ class DatePickerExample extends React.Component<
 > {
   static defaultProps = {
     date: new Date(),
-    timeZoneOffsetInHours: -1 * new Date().getTimezoneOffset() / 60,
+    timeZoneOffsetInHours: (-1 * new Date().getTimezoneOffset()) / 60,
   };
 
   state = {
diff --git a/RNTester/js/ImageExample.js b/RNTester/js/ImageExample.js
index 2125e2669e72..5465b6608117 100644
--- a/RNTester/js/ImageExample.js
+++ b/RNTester/js/ImageExample.js
@@ -158,7 +158,7 @@ var NetworkImageExample = createReactClass({
         onProgress={e =>
           this.setState({
             progress: Math.round(
-              100 * e.nativeEvent.loaded / e.nativeEvent.total,
+              (100 * e.nativeEvent.loaded) / e.nativeEvent.total,
             ),
           })
         }
diff --git a/RNTester/js/InputAccessoryViewExample.js b/RNTester/js/InputAccessoryViewExample.js
index 45b63e20d9f5..a848b961436e 100644
--- a/RNTester/js/InputAccessoryViewExample.js
+++ b/RNTester/js/InputAccessoryViewExample.js
@@ -60,7 +60,8 @@ class TextInputBar extends React.PureComponent<*, *> {
 
 class InputAccessoryViewExample extends React.Component<*> {
   static title = '<InputAccessoryView>';
-  static description = 'Example showing how to use an InputAccessoryView to build an iMessage-like sticky text input';
+  static description =
+    'Example showing how to use an InputAccessoryView to build an iMessage-like sticky text input';
 
   render() {
     return (
diff --git a/RNTester/js/KeyboardAvoidingViewExample.js b/RNTester/js/KeyboardAvoidingViewExample.js
index 2e51ed842016..0e86e432d79f 100644
--- a/RNTester/js/KeyboardAvoidingViewExample.js
+++ b/RNTester/js/KeyboardAvoidingViewExample.js
@@ -27,7 +27,8 @@ const RNTesterPage = require('./RNTesterPage');
 
 class KeyboardAvoidingViewExample extends React.Component {
   static title = '<KeyboardAvoidingView>';
-  static description = 'Base component for views that automatically adjust their height or position to move out of the way of the keyboard.';
+  static description =
+    'Base component for views that automatically adjust their height or position to move out of the way of the keyboard.';
 
   state = {
     behavior: 'padding',
diff --git a/RNTester/js/ListExampleShared.js b/RNTester/js/ListExampleShared.js
index 0edb7fe181ad..905985b52b28 100644
--- a/RNTester/js/ListExampleShared.js
+++ b/RNTester/js/ListExampleShared.js
@@ -38,7 +38,7 @@ function genItemData(count: number, start: number = 0): Array<Item> {
     const itemHash = Math.abs(hashCode('Item ' + ii));
     dataBlob.push({
       title: 'Item ' + ii,
-      text: LOREM_IPSUM.substr(0, itemHash % 301 + 20),
+      text: LOREM_IPSUM.substr(0, (itemHash % 301) + 20),
       key: String(ii),
       pressed: false,
     });
diff --git a/RNTester/js/ListViewExample.js b/RNTester/js/ListViewExample.js
index 9e008dd400b7..a274c353949f 100644
--- a/RNTester/js/ListViewExample.js
+++ b/RNTester/js/ListViewExample.js
@@ -70,7 +70,7 @@ var ListViewSimpleExample = createReactClass({
           <View style={styles.row}>
             <Image style={styles.thumb} source={imgSource} />
             <Text style={styles.text}>
-              {rowData + ' - ' + LOREM_IPSUM.substr(0, rowHash % 301 + 10)}
+              {rowData + ' - ' + LOREM_IPSUM.substr(0, (rowHash % 301) + 10)}
             </Text>
           </View>
         </View>
diff --git a/RNTester/js/MaskedViewExample.js b/RNTester/js/MaskedViewExample.js
index 081496b6f1b6..b944fbc16f73 100644
--- a/RNTester/js/MaskedViewExample.js
+++ b/RNTester/js/MaskedViewExample.js
@@ -24,7 +24,8 @@ const {
 
 class MaskedViewExample extends React.Component<{}, $FlowFixMeState> {
   static title = '<MaskedViewIOS>';
-  static description = 'Renders the child view with a mask specified in the `renderMask` prop.';
+  static description =
+    'Renders the child view with a mask specified in the `renderMask` prop.';
 
   state = {
     alternateChildren: true,
diff --git a/RNTester/js/PickerExample.js b/RNTester/js/PickerExample.js
index 6026ac74eb4d..0fd21fc7de32 100644
--- a/RNTester/js/PickerExample.js
+++ b/RNTester/js/PickerExample.js
@@ -22,7 +22,8 @@ const Item = Picker.Item;
 
 class PickerExample extends React.Component<{}, $FlowFixMeState> {
   static title = '<Picker>';
-  static description = 'Provides multiple options to choose from, using either a dropdown menu or a dialog.';
+  static description =
+    'Provides multiple options to choose from, using either a dropdown menu or a dialog.';
 
   state = {
     selected1: 'key1',
diff --git a/RNTester/js/RTLExample.js b/RNTester/js/RTLExample.js
index b833adfcbe3c..bab56a1d3691 100644
--- a/RNTester/js/RTLExample.js
+++ b/RNTester/js/RTLExample.js
@@ -373,7 +373,8 @@ const BorderExample = withRTLState(({isRTL, setRTL}) => {
 
 class RTLExample extends React.Component<any, State> {
   static title = 'RTLExample';
-  static description = 'Examples to show how to apply components to RTL layout.';
+  static description =
+    'Examples to show how to apply components to RTL layout.';
 
   _panResponder: Object;
 
diff --git a/RNTester/js/ScrollViewSimpleExample.js b/RNTester/js/ScrollViewSimpleExample.js
index 85c4147470d2..b7d95b2fb2f9 100644
--- a/RNTester/js/ScrollViewSimpleExample.js
+++ b/RNTester/js/ScrollViewSimpleExample.js
@@ -18,7 +18,8 @@ var NUM_ITEMS = 20;
 
 class ScrollViewSimpleExample extends React.Component<{}> {
   static title = '<ScrollView>';
-  static description = 'Component that enables scrolling through child components.';
+  static description =
+    'Component that enables scrolling through child components.';
 
   makeItems = (nItems: number, styles): Array<any> => {
     var items = [];
diff --git a/RNTester/js/SwipeableListViewExample.js b/RNTester/js/SwipeableListViewExample.js
index 1fec55d93e43..ee359ed1fcf6 100644
--- a/RNTester/js/SwipeableListViewExample.js
+++ b/RNTester/js/SwipeableListViewExample.js
@@ -94,7 +94,7 @@ var SwipeableListViewSimpleExample = createReactClass({
           <View style={styles.row}>
             <Image style={styles.thumb} source={imgSource} />
             <Text style={styles.text}>
-              {rowData.id + ' - ' + LOREM_IPSUM.substr(0, rowHash % 301 + 10)}
+              {rowData.id + ' - ' + LOREM_IPSUM.substr(0, (rowHash % 301) + 10)}
             </Text>
           </View>
         </View>
diff --git a/RNTester/js/ToastAndroidExample.android.js b/RNTester/js/ToastAndroidExample.android.js
index 7274fa969cf1..80ea97715ba3 100644
--- a/RNTester/js/ToastAndroidExample.android.js
+++ b/RNTester/js/ToastAndroidExample.android.js
@@ -19,7 +19,8 @@ var RNTesterPage = require('RNTesterPage');
 
 class ToastExample extends React.Component<{}, $FlowFixMeState> {
   static title = 'Toast Example';
-  static description = 'Example that demonstrates the use of an Android Toast to provide feedback.';
+  static description =
+    'Example that demonstrates the use of an Android Toast to provide feedback.';
   state = {};
 
   render() {
diff --git a/RNTester/js/ViewPagerAndroidExample.android.js b/RNTester/js/ViewPagerAndroidExample.android.js
index 1eb60ad3d6c6..f4aaca4a0984 100644
--- a/RNTester/js/ViewPagerAndroidExample.android.js
+++ b/RNTester/js/ViewPagerAndroidExample.android.js
@@ -81,7 +81,7 @@ class ProgressBar extends React.Component {
   render() {
     var fractionalPosition =
       this.props.progress.position + this.props.progress.offset;
-    var progressBarSize = fractionalPosition / (PAGES - 1) * this.props.size;
+    var progressBarSize = (fractionalPosition / (PAGES - 1)) * this.props.size;
     return (
       <View style={[styles.progressBarContainer, {width: this.props.size}]}>
         <View style={[styles.progressBar, {width: progressBarSize}]} />
@@ -92,7 +92,8 @@ class ProgressBar extends React.Component {
 
 class ViewPagerAndroidExample extends React.Component {
   static title = '<ViewPagerAndroid>';
-  static description = 'Container that allows to flip left and right between child views.';
+  static description =
+    'Container that allows to flip left and right between child views.';
 
   state = {
     page: 0,
diff --git a/local-cli/bundle/saveAssets.js b/local-cli/bundle/saveAssets.js
index b069c332b48d..0961ed7d525d 100644
--- a/local-cli/bundle/saveAssets.js
+++ b/local-cli/bundle/saveAssets.js
@@ -75,8 +75,7 @@ function copy(src, dest, callback) {
     if (err) {
       return callback(err);
     }
-    fs
-      .createReadStream(src)
+    fs.createReadStream(src)
       .pipe(fs.createWriteStream(dest))
       .on('finish', callback);
   });
diff --git a/local-cli/link/android/patches/makeBuildPatch.js b/local-cli/link/android/patches/makeBuildPatch.js
index 1ee9fb7d5fc6..dfaab8f6998b 100644
--- a/local-cli/link/android/patches/makeBuildPatch.js
+++ b/local-cli/link/android/patches/makeBuildPatch.js
@@ -18,6 +18,6 @@ module.exports = function makeBuildPatch(name) {
   return {
     installPattern,
     pattern: /[^ \t]dependencies {(\r\n|\n)/,
-    patch: `    compile project(':${normalizedProjectName}')\n`
+    patch: `    compile project(':${normalizedProjectName}')\n`,
   };
 };
diff --git a/package.json b/package.json
index 9eb0e2bb5560..f36d371e6630 100644
--- a/package.json
+++ b/package.json
@@ -215,7 +215,7 @@
     "flow-bin": "^0.73.0",
     "jest": "23.1.0",
     "jest-junit": "4.0.0",
-    "prettier": "1.12.1",
+    "prettier": "1.13.4",
     "react": "16.3.2",
     "react-test-renderer": "16.3.2",
     "shelljs": "^0.7.8",

From cb1bdf1e37236f5147ee5ef745573c0ced1b4f14 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Micha=C5=82=20Osadnik?= <micosa97@gmail.com>
Date: Wed, 6 Jun 2018 22:16:12 -0700
Subject: [PATCH 0739/1109] Change error message on interpolation (#19571)

Summary:
Change message in Animated.Interpolation to "inputRange must be monotonically non-decreasing" as it's allowed to give the same x's like in the test [example](https://github.com/facebook/react-native/blob/4435f087713e1d0ac3639e3b3196d71c6402898e/Libraries/Animated/src/__tests__/Interpolation-test.js#L71)

Simply giving improper value of interpolation input

[GENERAL] [MINOR] [AnimatedInterpolation.js] - Change error message on interpolation improper range error
Closes https://github.com/facebook/react-native/pull/19571

Differential Revision: D8310791

Pulled By: TheSavior

fbshipit-source-id: 803ef55104ad2a36231c5f18c0c089bd14822bf3
---
 Libraries/Animated/src/nodes/AnimatedInterpolation.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/Animated/src/nodes/AnimatedInterpolation.js b/Libraries/Animated/src/nodes/AnimatedInterpolation.js
index 067efbca731f..8ee7cbba8a7f 100644
--- a/Libraries/Animated/src/nodes/AnimatedInterpolation.js
+++ b/Libraries/Animated/src/nodes/AnimatedInterpolation.js
@@ -285,7 +285,7 @@ function checkValidInputRange(arr: Array<number>) {
        * mean this implicit string conversion, you can do something like
        * String(myThing)
        */
-      'inputRange must be monotonically increasing ' + arr,
+      'inputRange must be monotonically non-decreasing ' + arr,
     );
   }
 }

From 02d1bcc047e54297fc8f8dae41f1966f55d62496 Mon Sep 17 00:00:00 2001
From: Keith Brown <keith.brown@sony.com>
Date: Thu, 7 Jun 2018 02:26:17 -0700
Subject: [PATCH 0740/1109] =?UTF-8?q?Modified=20deepFreezeAndThrowOnMutati?=
 =?UTF-8?q?onInDev=20to=20use=20Object.prototype.ha=E2=80=A6=20(#19598)?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
This PR fixes a bug in `deepFreezeAndThrowOnMutationInDev` which did not take into account that objects passed to it may have been created with `Object.create(null)` and thus may not have a prototype. Such objects don't have the methods `hasOwnProperty`, `__defineGetter__`, or `__defineSetter__` on the instance.

I ran into an unrecoverable error in React Native when passing this type of object across the bridge because `deepFreezeAndThrowOnMutationInDev` attempts to call `object.hasOwnProperty(key)`, `object.__defineGetter__` and `object__defineSetter__` on objects passed to it. But my object instance does not have these prototype methods.

Changes:
* Defined `Object.prototype.hasOwnProperty` as a `const` (pattern used elsewhere in React Native)
* Modified calls to `object.hasOwnProperty(key)` to use `hasOwnProperty.call(object, key)` (Per ESLint rule [here](https://eslint.org/docs/rules/no-prototype-builtins))
* Modified calls to deprecated methods `object.__defineGetter__` and `object.__defineSetter__` to instead use `Object.defineProperty` to define get and set methods on the object. (Per guidance on [MDN](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/__defineGetter__))
* Added a new test to `deepFreezeAndThrowOnMutationInDev-test` to verify the fix.

I tried to create a reproducible example to post to Snack by passing prototype-less objects to a `Text` component, in various ways, but they appear to be converted to plain objects before crossing the bridge and therefore they do not throw an error.

However, I was able to create a new test to reproduce the issue. I added the following test to `deepFreezeAndThrowOnMutationInDev-test`:

```JavaScript
it('should not throw on object without prototype', () => {
    __DEV__ = true;
    var o = Object.create(null);
    o.key = 'Value';
    expect(() => deepFreezeAndThrowOnMutationInDev(o)).not.toThrow();
  });
```

The changes in this PR include this new test.

ESLint test produced no change in Error count (3) or Warnings (671)

N/A
Other areas with _possibly_ the same issue:
https://github.com/facebook/react-native/blob/c6b96c0df789717d53ec520ad28ba0ae00db6ec2/Libraries/vendor/core/mergeInto.js#L50
https://github.com/facebook/react-native/blob/8dc3ba0444c94d9bbb66295b5af885bff9b9cd34/Libraries/ReactNative/requireNativeComponent.js#L134

 [GENERAL] [BUGFIX] [Libraries/Utilities/deepFreezeAndThrowOnMutationInDev] -Fix for compatibility with objects without a prototype.
Closes https://github.com/facebook/react-native/pull/19598

Differential Revision: D8310845

Pulled By: TheSavior

fbshipit-source-id: 020c414a1062a637e97f9ee99bf8e5ba2d1fcf4f
---
 .../deepFreezeAndThrowOnMutationInDev-test.js       |  7 +++++++
 .../Utilities/deepFreezeAndThrowOnMutationInDev.js  | 13 +++++++++----
 2 files changed, 16 insertions(+), 4 deletions(-)

diff --git a/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js b/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
index 3ec7c7bab78b..4b5e11ea5f37 100644
--- a/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
+++ b/Libraries/Utilities/__tests__/deepFreezeAndThrowOnMutationInDev-test.js
@@ -26,6 +26,13 @@ describe('deepFreezeAndThrowOnMutationInDev', function() {
     expect(() => deepFreezeAndThrowOnMutationInDev()).not.toThrow();
   });
 
+  it('should not throw on object without prototype', () => {
+    __DEV__ = true;
+    var o = Object.create(null);
+    o.key = 'Value';
+    expect(() => deepFreezeAndThrowOnMutationInDev(o)).not.toThrow();
+  });
+
   it('should throw on mutation in dev with strict', () => {
     'use strict';
     __DEV__ = true;
diff --git a/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js b/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
index 71a29584a358..2e2c4952ee0a 100644
--- a/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
+++ b/Libraries/Utilities/deepFreezeAndThrowOnMutationInDev.js
@@ -39,12 +39,17 @@ function deepFreezeAndThrowOnMutationInDev<T: Object>(object: T): T {
     }
 
     const keys = Object.keys(object);
+    const hasOwnProperty = Object.prototype.hasOwnProperty;
 
     for (var i = 0; i < keys.length; i++) {
       var key = keys[i];
-      if (object.hasOwnProperty(key)) {
-        object.__defineGetter__(key, identity.bind(null, object[key]));
-        object.__defineSetter__(key, throwOnImmutableMutation.bind(null, key));
+      if (hasOwnProperty.call(object, key)) {
+        Object.defineProperty(object, key, {
+          get: identity.bind(null, object[key]),
+        });
+        Object.defineProperty(object, key, {
+          set: throwOnImmutableMutation.bind(null, key),
+        });
       }
     }
 
@@ -53,7 +58,7 @@ function deepFreezeAndThrowOnMutationInDev<T: Object>(object: T): T {
 
     for (var i = 0; i < keys.length; i++) {
       var key = keys[i];
-      if (object.hasOwnProperty(key)) {
+      if (hasOwnProperty.call(object, key)) {
         deepFreezeAndThrowOnMutationInDev(object[key]);
       }
     }

From 9cc14ec99c18f497cf5f3bb4a1f6ba6e3a494f8c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Thu, 7 Jun 2018 07:33:29 -0700
Subject: [PATCH 0741/1109] Update Danger token (#19606)

Summary:
Trivial.
Closes https://github.com/facebook/react-native/pull/19606

Differential Revision: D8314419

Pulled By: hramos

fbshipit-source-id: b298e265c2c87cdc01175b1a014f9003e0673f40
---
 .circleci/config.yml | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 5f720a8d32fb..31ea483c70c8 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -567,9 +567,9 @@ jobs:
       - run:
           name: Analyze Pull Request
           command: |
-            # DANGER_GITHUB_API_TOKEN=Facebook-Open-Source-Bot public_repo access token
+            # DANGER_GITHUB_API_TOKEN=React-Linter public_repo access token
             if [ -n "$CIRCLE_PR_NUMBER" ]; then
-              cd bots && DANGER_GITHUB_API_TOKEN="b186c9a82bab3b08ec80""c0818117619eec6f281a" yarn danger
+              cd bots && DANGER_GITHUB_API_TOKEN="80aa64c50f38a267e9ba""575d41d528f9c234edb8" yarn danger
             else
               echo "Skipping pull request analysis."
             fi

From 79c5b8eb9758a1eb8b87725419e1c6652371598c Mon Sep 17 00:00:00 2001
From: Robert Sayre <sayrer@gmail.com>
Date: Thu, 7 Jun 2018 08:13:16 -0700
Subject: [PATCH 0742/1109] Remove unused include. (#19548)

Summary:
`LayoutableShadowNode.cpp` includes `"LayoutableShadowNode.h"` as well as `<fabric/core/LayoutContext.h>`. In turn, `LayoutContext.h` then includes `<fabric/core/LayoutableShadowNode.h>`. `LayoutContext.h` doesn't actually require `LayoutableShadowNode.h`, but this unnecessary inclusion can cause duplicate definition errors if the two include paths don't map to exactly the same file. This patch removes the unnecessary include.

The CI's build system should cover the testing needed.

[INTERNAL] [MINOR] [fabric] - Remove an unnecessary include in fabric/core/layout.
Closes https://github.com/facebook/react-native/pull/19548

Differential Revision: D8313337

Pulled By: shergin

fbshipit-source-id: 2e01e29ff25131543d9a8601483c2e716c7437be
---
 ReactCommon/fabric/core/layout/LayoutContext.h | 3 ---
 1 file changed, 3 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutContext.h b/ReactCommon/fabric/core/layout/LayoutContext.h
index 1046fd00147f..d7197cd9632e 100644
--- a/ReactCommon/fabric/core/layout/LayoutContext.h
+++ b/ReactCommon/fabric/core/layout/LayoutContext.h
@@ -7,9 +7,6 @@
 
 #pragma once
 
-#include <unordered_set>
-
-#include <fabric/core/LayoutableShadowNode.h>
 #include <fabric/graphics/Geometry.h>
 
 namespace facebook {

From a52d84d7e1cdb287f2877c4d85f2e9866c248d43 Mon Sep 17 00:00:00 2001
From: Andrew Jack <me@andrewjack.uk>
Date: Thu, 7 Jun 2018 16:47:08 -0700
Subject: [PATCH 0743/1109] Fix ReactImagePropertyTest SoLoader failures
 (#19607)

Summary:
Fixes #18637 & #19309

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

Check Android `ReactImagePropertyTest` tests pass.

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

 [ANDROID] [BUGFIX] [Unit Tests] - Fix ReactImagePropertyTest SoLoader failure

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/19607

Differential Revision: D8325415

Pulled By: hramos

fbshipit-source-id: 598baa3499646bb50da065815c19bb9f76bf6c87
---
 ReactAndroid/src/test/java/com/facebook/react/views/BUCK        | 1 +
 .../com/facebook/react/views/image/ReactImagePropertyTest.java  | 2 ++
 2 files changed, 3 insertions(+)

diff --git a/ReactAndroid/src/test/java/com/facebook/react/views/BUCK b/ReactAndroid/src/test/java/com/facebook/react/views/BUCK
index dc64ad96ed30..c50da6f542f4 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/views/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/views/BUCK
@@ -13,6 +13,7 @@ rn_robolectric_test(
         react_native_dep("libraries/fresco/fresco-react-native:fresco-drawee"),
         react_native_dep("libraries/fresco/fresco-react-native:fresco-react-native"),
         react_native_dep("libraries/fresco/fresco-react-native:imagepipeline"),
+        react_native_dep("libraries/soloader/java/com/facebook/soloader:soloader"),
         react_native_dep("third-party/java/fest:fest"),
         react_native_dep("third-party/java/jsr-305:jsr-305"),
         react_native_dep("third-party/java/junit:junit"),
diff --git a/ReactAndroid/src/test/java/com/facebook/react/views/image/ReactImagePropertyTest.java b/ReactAndroid/src/test/java/com/facebook/react/views/image/ReactImagePropertyTest.java
index 93dc7845007e..2a1ee5755f81 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/views/image/ReactImagePropertyTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/views/image/ReactImagePropertyTest.java
@@ -20,6 +20,7 @@
 import com.facebook.react.uimanager.ReactStylesDiffMap;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.soloader.SoLoader;
 
 import org.junit.After;
 import org.junit.Before;
@@ -53,6 +54,7 @@ public class ReactImagePropertyTest {
 
   @Before
   public void setup() {
+    SoLoader.setInTestMode();
     mContext = new ReactApplicationContext(RuntimeEnvironment.application);
     mCatalystInstanceMock = ReactTestHelper.createMockCatalystInstance();
     mContext.initializeWithInstance(mCatalystInstanceMock);

From e5aa5b7c508c5e0e51f7abfcee350e27bef24ba2 Mon Sep 17 00:00:00 2001
From: Martin Sherburn <mns@oculus.com>
Date: Fri, 8 Jun 2018 02:57:15 -0700
Subject: [PATCH 0744/1109] Fixed concurrency issue in remote debugger

Reviewed By: rafeca

Differential Revision: D8316215

fbshipit-source-id: 70b5000a9bf09897bb9b9d505bfc5dcc7c4c3a41
---
 local-cli/server/util/debugger-ui/index.html | 20 +++++++++++++++++---
 1 file changed, 17 insertions(+), 3 deletions(-)

diff --git a/local-cli/server/util/debugger-ui/index.html b/local-cli/server/util/debugger-ui/index.html
index 57d377629abd..8a7f2b3206fe 100644
--- a/local-cli/server/util/debugger-ui/index.html
+++ b/local-cli/server/util/debugger-ui/index.html
@@ -1,7 +1,7 @@
 <!DOCTYPE html>
 <!--
   Copyright (c) 2015-present, Facebook, Inc.
-  
+
   This source code is licensed under the MIT license found in the
   LICENSE file in the root directory of this source tree.
 -->
@@ -112,6 +112,8 @@
   function connectToDebuggerProxy() {
     const ws = new WebSocket('ws://' + window.location.host + '/debugger-proxy?role=debugger&name=Chrome');
     let worker;
+    let queuedMessages = [];
+    let appExecuted = false;
 
     function createJSRuntime() {
       // This worker will run the application JavaScript code,
@@ -181,9 +183,21 @@
           ...object,
           url: await getBlobUrl(object.url),
         });
+        appExecuted = true;
+        // Flush any messages queued up and clear them
+        for (const message of queuedMessages) {
+          worker.postMessage(message);
+        }
+        queuedMessages = [];
       } else {
-        // Otherwise, pass through to the worker.
-        worker.postMessage(object);
+        // Otherwise, pass through to the worker provided the
+        // application script has been executed. If not add
+        // it to a queue until it has been executed.
+        if (appExecuted) {
+          worker.postMessage(object);
+        } else {
+          queuedMessages.push(object);
+        }
       }
     };
 

From 291c01f4ffe614760852e36b05d78b42cb4271df Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 8 Jun 2018 06:15:49 -0700
Subject: [PATCH 0745/1109] Fix NullPointerException when emiting event using
 UIManagerModule

Reviewed By: achen1

Differential Revision: D8321766

fbshipit-source-id: ae5052c83f46e08d540b90bf5b71c68f354c566d
---
 .../react/uimanager/events/EventDispatcher.java  |  3 ++-
 .../uimanager/events/ReactEventEmitter.java      | 16 ++++++++++++----
 2 files changed, 14 insertions(+), 5 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
index d983eebebad5..37fcadda30ad 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/EventDispatcher.java
@@ -96,13 +96,14 @@ public int compare(Event lhs, Event rhs) {
 
   private Event[] mEventsToDispatch = new Event[16];
   private int mEventsToDispatchSize = 0;
-  private volatile @Nullable ReactEventEmitter mReactEventEmitter = new ReactEventEmitter();
+  private volatile ReactEventEmitter mReactEventEmitter;
   private short mNextEventTypeId = 0;
   private volatile boolean mHasDispatchScheduled = false;
 
   public EventDispatcher(ReactApplicationContext reactContext) {
     mReactContext = reactContext;
     mReactContext.addLifecycleEventListener(this);
+    mReactEventEmitter = new ReactEventEmitter(mReactContext);
   }
 
   /**
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
index 5d07b3564777..64aac3f795fc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/events/ReactEventEmitter.java
@@ -12,6 +12,7 @@
 import android.util.Log;
 import android.util.SparseArray;
 import com.facebook.infer.annotation.Assertions;
+import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.WritableArray;
 import com.facebook.react.bridge.WritableMap;
 import com.facebook.react.uimanager.common.UIManagerType;
@@ -24,8 +25,11 @@ public class ReactEventEmitter implements RCTEventEmitter {
 
   private static final String TAG = ReactEventEmitter.class.getSimpleName();
   private final SparseArray<RCTEventEmitter> mEventEmitters = new SparseArray<>();
+  private final ReactApplicationContext mReactContext;
 
-  public ReactEventEmitter() { }
+  public ReactEventEmitter(ReactApplicationContext reactContext) {
+    mReactContext = reactContext;
+  }
 
   public void register(@UIManagerType int uiManagerType, RCTEventEmitter eventEmitter) {
     mEventEmitters.put(uiManagerType, eventEmitter);
@@ -48,12 +52,16 @@ public void receiveTouches(
 
     Assertions.assertCondition(touches.size() > 0);
 
-    int targetReactTag = touches.getMap(0).getInt(TARGET_KEY);
-    getEventEmitter(targetReactTag).receiveTouches(eventName, touches, changedIndices);
+    int reactTag = touches.getMap(0).getInt(TARGET_KEY);
+    getEventEmitter(reactTag).receiveTouches(eventName, touches, changedIndices);
   }
 
   private RCTEventEmitter getEventEmitter(int reactTag) {
     int type = ViewUtil.getUIManagerType(reactTag);
-    return mEventEmitters.get(type);
+    RCTEventEmitter eventEmitter = mEventEmitters.get(type);
+    if (eventEmitter == null) {
+      eventEmitter = mReactContext.getJSModule(RCTEventEmitter.class);
+    }
+    return eventEmitter;
   }
 }

From 078d6e3a9d36d8e58201e0e33e58ca5137ec8c10 Mon Sep 17 00:00:00 2001
From: Oleksandr Sokolov <asokol@fb.com>
Date: Fri, 8 Jun 2018 08:24:47 -0700
Subject: [PATCH 0746/1109] QuickPerformanceLogger.js: markerPoint +
 iOS/Android JS binding

Reviewed By: alexeylang

Differential Revision: D8125546

fbshipit-source-id: bb02921c7d89faba64001bff3b9aaf13f64a7f8b
---
 .../Performance/QuickPerformanceLogger.js     | 11 +++++
 .../src/main/jni/react/jni/JSCPerfLogging.cpp | 41 ++++++++++++++++++-
 2 files changed, 51 insertions(+), 1 deletion(-)

diff --git a/Libraries/Performance/QuickPerformanceLogger.js b/Libraries/Performance/QuickPerformanceLogger.js
index 360d5b96a8a5..6d50626b1fe7 100644
--- a/Libraries/Performance/QuickPerformanceLogger.js
+++ b/Libraries/Performance/QuickPerformanceLogger.js
@@ -81,6 +81,17 @@ const QuickPerformanceLogger = {
     }
   },
 
+  markerPoint(
+    markerId: number,
+    name: string,
+    instanceKey: number = DUMMY_INSTANCE_KEY,
+    timestamp: number = AUTO_SET_TIMESTAMP,
+  ): void {
+    if (global.nativeQPLMarkerPoint) {
+      global.nativeQPLMarkerPoint(markerId, name, instanceKey, timestamp);
+    }
+  },
+
   currentTimestamp(): number {
     if (global.nativeQPLTimestamp) {
       return global.nativeQPLTimestamp();
diff --git a/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp b/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp
index ea9c7285ec80..6516932e1961 100644
--- a/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/JSCPerfLogging.cpp
@@ -62,6 +62,12 @@ struct JQuickPerformanceLogger : JavaClass<JQuickPerformanceLogger> {
       javaClassStatic()->getMethod<jlong()>("currentMonotonicTimestamp");
     return currentTimestampMethod(self());
   }
+
+  void markerPoint(int markerId, alias_ref<jstring> name, int instanceKey) {
+    static auto markerPointMethod =
+      javaClassStatic()->getMethod<void(jint, jint, alias_ref<jstring>)>("markerPoint");
+    markerPointMethod(self(), markerId, instanceKey, name);
+  }
 };
 
 struct JQuickPerformanceLoggerProvider : JavaClass<JQuickPerformanceLoggerProvider> {
@@ -106,6 +112,14 @@ static bool isNan(double value) {
   return (value != value);
 }
 
+static double grabDouble(
+    JSContextRef ctx,
+    const JSValueRef arguments[],
+    size_t argumentIndex,
+    JSValueRef* exception) {
+  return JSValueToNumber(ctx, arguments[argumentIndex], exception);
+}
+
 // Safely translates JSValues to an array of doubles.
 static bool grabDoubles(
     size_t targetsCount,
@@ -118,7 +132,7 @@ static bool grabDoubles(
     return false;
   }
   for (size_t i = 0 ; i < targetsCount ; i++) {
-    targets[i] = JSValueToNumber(ctx, arguments[i], exception);
+    targets[i] = grabDouble(ctx, arguments, i, exception);
     if (isNan(targets[i])) {
       return false;
     }
@@ -254,6 +268,30 @@ static JSValueRef nativeQPLTimestamp(
   return JSValueMakeNumber(ctx, timestamp);
 }
 
+static JSValueRef nativeQPLMarkerPoint(
+    JSContextRef ctx,
+    JSObjectRef function,
+    JSObjectRef thisObject,
+    size_t argumentCount,
+    const JSValueRef arguments[],
+    JSValueRef* exception) {
+  if (isReady() && argumentCount == 4) {
+    double markerIdArgument = grabDouble(ctx, arguments, 0, exception);
+    double instanceKeyArgument = grabDouble(ctx, arguments, 2, exception);
+    if (isNan(markerIdArgument) || isNan(instanceKeyArgument)) {
+      return JSValueMakeUndefined(ctx);
+    }
+
+    int32_t markerId = (int32_t) markerIdArgument;
+    local_ref<jstring> name = getJStringFromJSValueRef(ctx, arguments[1]);
+    int32_t instanceKey = (int32_t) instanceKeyArgument;
+    // timestamp is not used as QuickPerformanceLogger::markerPoint with all
+    // params is missing
+    JQuickPerformanceLoggerProvider::get()->markerPoint(markerId, name, instanceKey);
+  }
+  return JSValueMakeUndefined(ctx);
+}
+
 void addNativePerfLoggingHooks(JSGlobalContextRef ctx) {
   installGlobalFunction(ctx, "nativeQPLMarkerStart", nativeQPLMarkerStart);
   installGlobalFunction(ctx, "nativeQPLMarkerEnd", nativeQPLMarkerEnd);
@@ -262,6 +300,7 @@ void addNativePerfLoggingHooks(JSGlobalContextRef ctx) {
   installGlobalFunction(ctx, "nativeQPLMarkerNote", nativeQPLMarkerNote);
   installGlobalFunction(ctx, "nativeQPLMarkerCancel", nativeQPLMarkerCancel);
   installGlobalFunction(ctx, "nativeQPLTimestamp", nativeQPLTimestamp);
+  installGlobalFunction(ctx, "nativeQPLMarkerPoint", nativeQPLMarkerPoint);
 }
 
 } }

From 8b62e7a5506f335c35ce3bd33dbf599426cb3fbf Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 8 Jun 2018 20:16:13 -0700
Subject: [PATCH 0747/1109] Fabric: Using Size instead of Point as
 textShadowOffset's type

Summary:
The current implementation of React Native uses `Size` as the underlying type of `textShadowOffset` which is clearly terribly wrong (especially because negative size values makes no sense). This mistake was borrowed from `NSShadow`, I believe.
I don't have time to fix this in every implementation of RN now, so let's use `Size` in Fabric as well.

Reviewed By: fkgozali

Differential Revision: D8246714

fbshipit-source-id: 1f0bf9b9dfa83802ef3faef2971fed5510494bfd
---
 ReactCommon/fabric/attributedstring/TextAttributes.h           | 3 ++-
 ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm | 2 +-
 2 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.h b/ReactCommon/fabric/attributedstring/TextAttributes.h
index c474e7e2aa6a..584387bf5471 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.h
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.h
@@ -57,7 +57,8 @@ class TextAttributes:
   folly::Optional<TextDecorationLinePattern> textDecorationLinePattern {};
 
   // Shadow
-  folly::Optional<Point> textShadowOffset {};
+  // TODO: Use `Point` type instead of `Size` for `textShadowOffset` attribute.
+  folly::Optional<Size> textShadowOffset {};
   Float textShadowRadius {std::numeric_limits<Float>::quiet_NaN()};
   SharedColor textShadowColor {nullptr};
 
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
index 11d4db50c075..542b7859f071 100644
--- a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
+++ b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
@@ -154,7 +154,7 @@ inline static CGFloat RCTEffectiveFontSizeMultiplierFromTextAttributes(const Tex
   if (textAttributes.textShadowOffset.hasValue()) {
     auto textShadowOffset = textAttributes.textShadowOffset.value();
     NSShadow *shadow = [NSShadow new];
-    shadow.shadowOffset = CGSize {textShadowOffset.x, textShadowOffset.y};
+    shadow.shadowOffset = CGSize {textShadowOffset.width, textShadowOffset.height};
     shadow.shadowBlurRadius = textAttributes.textShadowRadius;
     shadow.shadowColor = RCTUIColorFromSharedColor(textAttributes.textShadowColor);
     attributes[NSShadowAttributeName] = shadow;

From bb9bf2616956cfc3559642a847b113ea905aa6e6 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 8 Jun 2018 20:16:15 -0700
Subject: [PATCH 0748/1109] Fabric: Using exact UIFontWeight* constants instead
 of CGFloat

Summary: SUDDENLY, `-[UIFont systemFontOfSize:weight:]` returns incorrect result if `weight` is not exactly equal to any of built-in constants.

Reviewed By: fkgozali

Differential Revision: D8246712

fbshipit-source-id: 13d59cc8d66a4494437f28d791fd93fa83ebe6fb
---
 .../fabric/textlayoutmanager/RCTFontUtils.mm  | 24 +++++++++++++++++--
 1 file changed, 22 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm b/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm
index 38a3d80f5a5d..954051f864bd 100644
--- a/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm
+++ b/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm
@@ -7,6 +7,7 @@
 
 #import "RCTFontUtils.h"
 
+#import <cmath>
 #import <mutex>
 
 static RCTFontProperties RCTDefaultFontProperties() {
@@ -55,6 +56,25 @@ static RCTFontStyle RCTGetFontStyle(UIFont *font) {
   return @[];
 }
 
+static UIFontWeight RCTUIFontWeightFromFloat(CGFloat fontWeight) {
+  // Note: Even if the underlying type of `UIFontWeight` is `CGFloat`
+  // and UIKit uses the same numerical notation, we have to use exact
+  // `UIFontWeight*` constants to make it work properly (because
+  // float values comparison is tricky).
+  static UIFontWeight weights[] = {
+    /* ~100 */ UIFontWeightUltraLight,
+    /* ~200 */ UIFontWeightThin,
+    /* ~300 */ UIFontWeightLight,
+    /* ~400 */ UIFontWeightRegular,
+    /* ~500 */ UIFontWeightMedium,
+    /* ~600 */ UIFontWeightSemibold,
+    /* ~700 */ UIFontWeightBold,
+    /* ~800 */ UIFontWeightHeavy,
+    /* ~900 */ UIFontWeightBlack
+  };
+  return weights[std::llround((fontWeight / 100) - 1)];
+}
+
 static UIFont *RCTDefaultFontWithFontProperties(RCTFontProperties fontProperties) {
   static NSCache *fontCache;
   static std::mutex fontCacheMutex;
@@ -72,7 +92,7 @@ static RCTFontStyle RCTGetFontStyle(UIFont *font) {
 
   if (!font) {
     font = [UIFont systemFontOfSize:fontProperties.size
-                             weight:fontProperties.weight];
+                             weight:RCTUIFontWeightFromFloat(fontProperties.weight)];
 
     if (fontProperties.variant == RCTFontStyleItalic) {
       UIFontDescriptor *fontDescriptor = [font fontDescriptor];
@@ -114,7 +134,7 @@ static RCTFontStyle RCTGetFontStyle(UIFont *font) {
 
       if (!font) {
         // Failback to system font.
-        font = [UIFont systemFontOfSize:effectiveFontSize weight:fontProperties.weight];
+        font = [UIFont systemFontOfSize:effectiveFontSize weight:RCTUIFontWeightFromFloat(fontProperties.weight)];
       }
     } else {
       // Get the closest font that matches the given weight for the fontFamily

From d01290dd34c0274f49adcd75b7488c90fe70f562 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 8 Jun 2018 20:16:17 -0700
Subject: [PATCH 0749/1109] Fabric: Data model of Touch Events

Summary: The data model of Touch events and payload serialization. The implementation mimics W3C standard and current React Native implementation.

Reviewed By: fkgozali

Differential Revision: D8246711

fbshipit-source-id: 955b2068674f290d8bdb82da1ebfb796dd32971b
---
 ReactCommon/fabric/view/ViewEventHandlers.cpp | 49 ++++++++++
 ReactCommon/fabric/view/ViewEventHandlers.h   | 90 +++++++++++++++++++
 2 files changed, 139 insertions(+)

diff --git a/ReactCommon/fabric/view/ViewEventHandlers.cpp b/ReactCommon/fabric/view/ViewEventHandlers.cpp
index e673d077efb9..3cdadd3527c6 100644
--- a/ReactCommon/fabric/view/ViewEventHandlers.cpp
+++ b/ReactCommon/fabric/view/ViewEventHandlers.cpp
@@ -38,5 +38,54 @@ void ViewEventHandlers::onLayout(const LayoutMetrics &layoutMetrics) const {
   dispatchEvent("layout", payload);
 }
 
+#pragma mark - Touches
+
+static folly::dynamic touchPayload(const Touch &touch) {
+  folly::dynamic object = folly::dynamic::object();
+  object["locationX"] = touch.offsetPoint.x;
+  object["locationY"] = touch.offsetPoint.x;
+  object["pageX"] = touch.pagePoint.x;
+  object["pageY"] = touch.pagePoint.x;
+  object["screenX"] = touch.screenPoint.x;
+  object["screenY"] = touch.screenPoint.x;
+  object["identifier"] = touch.identifier;
+  object["target"] = touch.target;
+  object["timestamp"] = touch.timestamp * 1000;
+  object["force"] = touch.force;
+  return object;
+}
+
+static folly::dynamic touchesPayload(const Touches &touches) {
+  folly::dynamic array = folly::dynamic::array();
+  for (auto &&touch : touches) {
+    array.push_back(touchPayload(touch));
+  }
+  return array;
+}
+
+static folly::dynamic touchEventPayload(const TouchEvent &event) {
+  folly::dynamic object = folly::dynamic::object();
+  object["touches"] = touchesPayload(event.touches);
+  object["changedTouches"] = touchesPayload(event.changedTouches);
+  object["targetTouches"] = touchesPayload(event.targetTouches);
+  return object;
+}
+
+void ViewEventHandlers::onTouchStart(const TouchEvent &event) const {
+  dispatchEvent("touchStart", touchEventPayload(event));
+}
+
+void ViewEventHandlers::onTouchMove(const TouchEvent &event) const {
+  dispatchEvent("touchMove", touchEventPayload(event));
+}
+
+void ViewEventHandlers::onTouchEnd(const TouchEvent &event) const {
+  dispatchEvent("touchEnd", touchEventPayload(event));
+}
+
+void ViewEventHandlers::onTouchCancel(const TouchEvent &event) const {
+  dispatchEvent("touchCancel", touchEventPayload(event));
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/view/ViewEventHandlers.h b/ReactCommon/fabric/view/ViewEventHandlers.h
index e72e41f345b8..654649ed384a 100644
--- a/ReactCommon/fabric/view/ViewEventHandlers.h
+++ b/ReactCommon/fabric/view/ViewEventHandlers.h
@@ -10,10 +10,93 @@
 
 #include <fabric/core/EventHandlers.h>
 #include <fabric/core/LayoutMetrics.h>
+#include <fabric/core/ReactPrimitives.h>
 
 namespace facebook {
 namespace react {
 
+/*
+ * Describes an individual touch point for a touch event.
+ * See https://www.w3.org/TR/touch-events/ for more details.
+ */
+struct Touch {
+  /*
+   * The coordinate of point relative to the root component in points.
+   */
+  Point pagePoint;
+
+  /*
+   * The coordinate of point relative to the target component in points.
+   */
+  Point offsetPoint;
+
+  /*
+   * The coordinate of point relative to the screen component in points.
+   */
+  Point screenPoint;
+
+  /*
+   * An identification number for each touch point.
+   */
+  int identifier;
+
+  /*
+   * The tag of a component on which the touch point started when it was first placed on the surface,
+   * even if the touch point has since moved outside the interactive area of that element.
+   */
+  Tag target;
+
+  /*
+   * The force of the touch.
+   */
+  Float force;
+
+  /*
+   * The time in seconds when the touch occurred or when it was last mutated.
+   */
+  Float timestamp;
+
+  /*
+   * The particular implementation of `Hasher` and (especially) `Comparator`
+   * make sense only when `Touch` object is used as a *key* in indexed collections.
+   * Because of that they are expressed as separate classes.
+   */
+  struct Hasher {
+    size_t operator()(const Touch &touch) const {
+      return std::hash<decltype(touch.identifier)>()(touch.identifier);
+    }
+  };
+
+  struct Comparator {
+    bool operator()(const Touch &lhs, const Touch &rhs) const {
+      return lhs.identifier == rhs.identifier;
+    }
+  };
+};
+
+using Touches = std::unordered_set<Touch, Touch::Hasher, Touch::Comparator>;
+
+/*
+ * Defines the `touchstart`, `touchend`, `touchmove`, and `touchcancel` event types.
+ */
+struct TouchEvent {
+  /*
+   * A list of Touches for every point of contact currently touching the surface.
+   */
+  Touches touches;
+
+  /*
+   * A list of Touches for every point of contact which contributed to the event.
+   */
+  Touches changedTouches;
+
+  /*
+   * A list of Touches for every point of contact that is touching the surface
+   * and started on the element that is the target of the current event.
+   */
+  Touches targetTouches;
+};
+
 class ViewEventHandlers;
 
 using SharedViewEventHandlers = std::shared_ptr<const ViewEventHandlers>;
@@ -34,6 +117,13 @@ class ViewEventHandlers:
 #pragma mark - Layout
 
   void onLayout(const LayoutMetrics &layoutMetrics) const;
+
+#pragma mark - Touches
+
+  void onTouchStart(const TouchEvent &event) const;
+  void onTouchMove(const TouchEvent &event) const;
+  void onTouchEnd(const TouchEvent &event) const;
+  void onTouchCancel(const TouchEvent &event) const;
 };
 
 } // namespace react

From a32be38017fa635152b40ede35d9a5c06f69aa72 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 8 Jun 2018 20:16:19 -0700
Subject: [PATCH 0750/1109] Fabric: Introducing RCTSurfaceTouchHandler

Summary:
RCTSurfaceTouchHandler is a complete rewrite of RCTTouchHandler which uses direct Fabric-specific event dispatching pipeline and several new approaches to managing active events (such as high-performant C++ collections, better management of identifier pool, and so on).
Besides that, the new implementation is much more W3C compliant that it used to be (see old TODOs near `receiveTouches()` implementation in Javascript).
So, touch events work now!

Reviewed By: fkgozali

Differential Revision: D8246713

fbshipit-source-id: 218dc15cd8f982237de7e2497ff36a7bfe6d37cc
---
 .../View/RCTViewComponentView.mm              |   5 +
 React/Fabric/RCTSurfaceTouchHandler.h         |  19 +
 React/Fabric/RCTSurfaceTouchHandler.mm        | 360 ++++++++++++++++++
 React/Fabric/Surface/RCTFabricSurface.mm      |   7 +-
 4 files changed, 389 insertions(+), 2 deletions(-)
 create mode 100644 React/Fabric/RCTSurfaceTouchHandler.h
 create mode 100644 React/Fabric/RCTSurfaceTouchHandler.mm

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index 189850df9095..fb688d031924 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -67,4 +67,9 @@ - (BOOL)didActivateAccessibilityCustomAction:(UIAccessibilityCustomAction *)acti
   return YES;
 }
 
+- (SharedEventHandlers)touchEventHandlers
+{
+  return _eventHandlers;
+}
+
 @end
diff --git a/React/Fabric/RCTSurfaceTouchHandler.h b/React/Fabric/RCTSurfaceTouchHandler.h
new file mode 100644
index 000000000000..670ef284832c
--- /dev/null
+++ b/React/Fabric/RCTSurfaceTouchHandler.h
@@ -0,0 +1,19 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface RCTSurfaceTouchHandler : UIGestureRecognizer
+
+- (void)attachToView:(UIView *)view;
+- (void)detachFromView:(UIView *)view;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/RCTSurfaceTouchHandler.mm b/React/Fabric/RCTSurfaceTouchHandler.mm
new file mode 100644
index 000000000000..09f586646d7f
--- /dev/null
+++ b/React/Fabric/RCTSurfaceTouchHandler.mm
@@ -0,0 +1,360 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTSurfaceTouchHandler.h"
+
+#import <UIKit/UIGestureRecognizerSubclass.h>
+#import <fabric/view/ViewEventHandlers.h>
+#import <React/RCTUtils.h>
+#import <React/RCTViewComponentView.h>
+
+#import "RCTConversions.h"
+
+using namespace facebook::react;
+
+template <size_t size>
+class IdentifierPool {
+public:
+
+  void enqueue(int index) {
+    usage[index] = false;
+  }
+
+  int dequeue() {
+    while (true) {
+      if (!usage[lastIndex]) {
+        usage[lastIndex] = true;
+        return lastIndex;
+      }
+      lastIndex = (lastIndex + 1) % size;
+    }
+  }
+
+  void reset() {
+    for (int i = 0; i < size; i++) {
+      usage[i] = false;
+    }
+  }
+
+private:
+
+  bool usage[size];
+  int lastIndex;
+};
+
+@protocol RCTTouchableComponentViewProtocol <NSObject>
+  - (SharedViewEventHandlers)touchEventHandlers;
+@end
+
+typedef NS_ENUM(NSInteger, RCTTouchEventType) {
+  RCTTouchEventTypeTouchStart,
+  RCTTouchEventTypeTouchMove,
+  RCTTouchEventTypeTouchEnd,
+  RCTTouchEventTypeTouchCancel,
+};
+
+struct ActiveTouch {
+  Touch touch;
+  SharedViewEventHandlers eventHandlers;
+
+  struct Hasher {
+    size_t operator()(const ActiveTouch &activeTouch) const {
+      return std::hash<decltype(activeTouch.touch.identifier)>()(activeTouch.touch.identifier);
+    }
+  };
+
+  struct Comparator {
+    bool operator()(const ActiveTouch &lhs, const ActiveTouch &rhs) const {
+      return lhs.touch.identifier == rhs.touch.identifier;
+    }
+  };
+};
+
+static void UpdateActiveTouchWithUITouch(ActiveTouch &activeTouch, UITouch *uiTouch, UIView *rootComponentView) {
+  CGPoint offsetPoint = [uiTouch locationInView:uiTouch.view];
+  CGPoint screenPoint = [uiTouch locationInView:uiTouch.window];
+  CGPoint pagePoint = [uiTouch locationInView:rootComponentView];
+
+  activeTouch.touch.offsetPoint = RCTPointFromCGPoint(offsetPoint);
+  activeTouch.touch.screenPoint = RCTPointFromCGPoint(screenPoint);
+  activeTouch.touch.pagePoint = RCTPointFromCGPoint(pagePoint);
+
+  activeTouch.touch.timestamp = uiTouch.timestamp;
+
+  if (RCTForceTouchAvailable()) {
+    activeTouch.touch.force = uiTouch.force / uiTouch.maximumPossibleForce;
+  }
+}
+
+static ActiveTouch CreateTouchWithUITouch(UITouch *uiTouch, UIView *rootComponentView) {
+  UIView *componentView = uiTouch.view;
+
+  ActiveTouch activeTouch = {};
+
+  if ([componentView respondsToSelector:@selector(touchEventHandlers)]) {
+    activeTouch.eventHandlers = [(id<RCTTouchableComponentViewProtocol>)componentView touchEventHandlers];
+    activeTouch.touch.target = (Tag)componentView.tag;
+  }
+
+  UpdateActiveTouchWithUITouch(activeTouch, uiTouch, rootComponentView);
+  return activeTouch;
+}
+
+static BOOL AllTouchesAreCancelledOrEnded(NSSet<UITouch *> *touches) {
+  for (UITouch *touch in touches) {
+    if (touch.phase == UITouchPhaseBegan ||
+        touch.phase == UITouchPhaseMoved ||
+        touch.phase == UITouchPhaseStationary) {
+      return NO;
+    }
+  }
+  return YES;
+}
+
+static BOOL AnyTouchesChanged(NSSet<UITouch *> *touches) {
+  for (UITouch *touch in touches) {
+    if (touch.phase == UITouchPhaseBegan ||
+        touch.phase == UITouchPhaseMoved) {
+      return YES;
+    }
+  }
+  return NO;
+}
+
+/**
+ * Surprisingly, `__unsafe_unretained id` pointers are not regular pointers
+ * and `std::hash<>` cannot hash them.
+ * This is quite trivial but decent implementation of hasher function
+ * inspired by this research: https://stackoverflow.com/a/21062520/496389.
+ */
+template<typename PointerT>
+struct PointerHasher {
+  constexpr std::size_t operator()(const PointerT &value) const {
+    return reinterpret_cast<size_t>(&value);
+  }
+};
+
+@interface RCTSurfaceTouchHandler () <UIGestureRecognizerDelegate>
+@end
+
+@implementation RCTSurfaceTouchHandler {
+  std::unordered_map<
+    __unsafe_unretained UITouch *,
+    ActiveTouch,
+    PointerHasher<__unsafe_unretained UITouch *>
+  > _activeTouches;
+
+  UIView *_rootComponentView;
+  IdentifierPool<11> _identifierPool;
+}
+
+- (instancetype)init
+{
+  if (self = [super initWithTarget:nil action:nil]) {
+    // `cancelsTouchesInView` and `delaysTouches*` are needed in order
+    // to be used as a top level event delegated recognizer.
+    // Otherwise, lower-level components not built using React Native,
+    // will fail to recognize gestures.
+    self.cancelsTouchesInView = NO;
+    self.delaysTouchesBegan = NO; // This is default value.
+    self.delaysTouchesEnded = NO;
+
+    self.delegate = self;
+  }
+
+  return self;
+}
+
+RCT_NOT_IMPLEMENTED(- (instancetype)initWithTarget:(id)target action:(SEL)action)
+
+- (void)attachToView:(UIView *)view
+{
+  RCTAssert(self.view == nil, @"RCTTouchHandler already has attached view.");
+
+  [view addGestureRecognizer:self];
+  _rootComponentView = view;
+}
+
+- (void)detachFromView:(UIView *)view
+{
+  RCTAssertParam(view);
+  RCTAssert(self.view == view, @"RCTTouchHandler attached to another view.");
+
+  [view removeGestureRecognizer:self];
+  _rootComponentView = nil;
+}
+
+- (void)_registerTouches:(NSSet<UITouch *> *)touches
+{
+  for (UITouch *touch in touches) {
+    auto &&activeTouch = CreateTouchWithUITouch(touch, _rootComponentView);
+    activeTouch.touch.identifier = _identifierPool.dequeue();
+    _activeTouches.emplace(touch, activeTouch);
+  }
+}
+
+- (void)_updateTouches:(NSSet<UITouch *> *)touches
+{
+  for (UITouch *touch in touches) {
+    UpdateActiveTouchWithUITouch(_activeTouches[touch], touch, _rootComponentView);
+  }
+}
+
+- (void)_unregisterTouches:(NSSet<UITouch *> *)touches
+{
+  for (UITouch *touch in touches) {
+    auto &&activeTouch = _activeTouches[touch];
+    _identifierPool.enqueue(activeTouch.touch.identifier);
+    _activeTouches.erase(touch);
+  }
+}
+
+- (void)_dispatchTouches:(NSSet<UITouch *> *)touches eventType:(RCTTouchEventType)eventType
+{
+  TouchEvent event = {};
+  std::unordered_set<ActiveTouch, ActiveTouch::Hasher, ActiveTouch::Comparator> changedActiveTouches = {};
+  std::unordered_set<SharedViewEventHandlers> uniqueEventHandlers = {};
+  BOOL isEndishEventType = eventType == RCTTouchEventTypeTouchEnd || eventType == RCTTouchEventTypeTouchCancel;
+
+  for (UITouch *touch in touches) {
+    auto &&activeTouch = _activeTouches[touch];
+
+    if (!activeTouch.eventHandlers) {
+      continue;
+    }
+
+    changedActiveTouches.insert(activeTouch);
+    event.changedTouches.insert(activeTouch.touch);
+    uniqueEventHandlers.insert(activeTouch.eventHandlers);
+  }
+
+  for (auto &&pair : _activeTouches) {
+    if (!pair.second.eventHandlers) {
+      continue;
+    }
+
+    if (
+        isEndishEventType &&
+        event.changedTouches.find(pair.second.touch) != event.changedTouches.end()
+    ) {
+      continue;
+    }
+
+    event.touches.insert(pair.second.touch);
+  }
+
+  for (auto &&eventHandlers : uniqueEventHandlers) {
+    event.targetTouches.clear();
+
+    for (auto &&pair : _activeTouches) {
+      if (pair.second.eventHandlers == eventHandlers) {
+        event.targetTouches.insert(pair.second.touch);
+      }
+    }
+
+    switch (eventType) {
+      case RCTTouchEventTypeTouchStart:
+        eventHandlers->onTouchStart(event);
+        break;
+      case RCTTouchEventTypeTouchMove:
+        eventHandlers->onTouchMove(event);
+        break;
+      case RCTTouchEventTypeTouchEnd:
+        eventHandlers->onTouchEnd(event);
+        break;
+      case RCTTouchEventTypeTouchCancel:
+        eventHandlers->onTouchCancel(event);
+        break;
+    }
+  }
+}
+
+#pragma mark - `UIResponder`-ish touch-delivery methods
+
+- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
+{
+  [super touchesBegan:touches withEvent:event];
+
+  [self _registerTouches:touches];
+  [self _dispatchTouches:touches eventType:RCTTouchEventTypeTouchStart];
+
+  if (self.state == UIGestureRecognizerStatePossible) {
+    self.state = UIGestureRecognizerStateBegan;
+  } else if (self.state == UIGestureRecognizerStateBegan) {
+    self.state = UIGestureRecognizerStateChanged;
+  }
+}
+
+- (void)touchesMoved:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
+{
+  [super touchesMoved:touches withEvent:event];
+
+  [self _updateTouches:touches];
+  [self _dispatchTouches:touches eventType:RCTTouchEventTypeTouchMove];
+
+  self.state = UIGestureRecognizerStateChanged;
+}
+
+- (void)touchesEnded:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
+{
+  [super touchesEnded:touches withEvent:event];
+
+  [self _updateTouches:touches];
+  [self _dispatchTouches:touches eventType:RCTTouchEventTypeTouchEnd];
+  [self _unregisterTouches:touches];
+
+  if (AllTouchesAreCancelledOrEnded(event.allTouches)) {
+    self.state = UIGestureRecognizerStateEnded;
+  } else if (AnyTouchesChanged(event.allTouches)) {
+    self.state = UIGestureRecognizerStateChanged;
+  }
+}
+
+- (void)touchesCancelled:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
+{
+  [super touchesCancelled:touches withEvent:event];
+
+  [self _updateTouches:touches];
+  [self _dispatchTouches:touches eventType:RCTTouchEventTypeTouchCancel];
+  [self _unregisterTouches:touches];
+
+  if (AllTouchesAreCancelledOrEnded(event.allTouches)) {
+    self.state = UIGestureRecognizerStateCancelled;
+  } else if (AnyTouchesChanged(event.allTouches)) {
+    self.state = UIGestureRecognizerStateChanged;
+  }
+}
+
+- (void)reset
+{
+  // Technically, `_activeTouches` must be already empty at this point,
+  // but just to be sure, we clear it explicitly.
+  _activeTouches.clear();
+  _identifierPool.reset();
+}
+
+- (BOOL)canPreventGestureRecognizer:(__unused UIGestureRecognizer *)preventedGestureRecognizer
+{
+  return NO;
+}
+
+- (BOOL)canBePreventedByGestureRecognizer:(UIGestureRecognizer *)preventingGestureRecognizer
+{
+  // We fail in favour of other external gesture recognizers.
+  // iOS will ask `delegate`'s opinion about this gesture recognizer little bit later.
+  return ![preventingGestureRecognizer.view isDescendantOfView:self.view];
+}
+
+#pragma mark - UIGestureRecognizerDelegate
+
+- (BOOL)gestureRecognizer:(__unused UIGestureRecognizer *)gestureRecognizer shouldRequireFailureOfGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer
+{
+  // Same condition for `failure of` as for `be prevented by`.
+  return [self canBePreventedByGestureRecognizer:otherGestureRecognizer];
+}
+
+@end
diff --git a/React/Fabric/Surface/RCTFabricSurface.mm b/React/Fabric/Surface/RCTFabricSurface.mm
index 3028a204e97e..2e06d361d01e 100644
--- a/React/Fabric/Surface/RCTFabricSurface.mm
+++ b/React/Fabric/Surface/RCTFabricSurface.mm
@@ -17,7 +17,7 @@
 #import <React/RCTSurfaceDelegate.h>
 #import <React/RCTSurfaceRootView.h>
 #import <React/RCTSurfaceView.h>
-#import <React/RCTTouchHandler.h>
+#import <React/RCTSurfaceTouchHandler.h>
 #import <React/RCTUIManagerUtils.h>
 #import <React/RCTUtils.h>
 
@@ -39,7 +39,7 @@ @implementation RCTFabricSurface {
 
   // The Main thread only
   RCTSurfaceView *_Nullable _view;
-  RCTTouchHandler *_Nullable _touchHandler;
+  RCTSurfaceTouchHandler *_Nullable _touchHandler;
 }
 
 - (instancetype)initWithBridge:(RCTBridge *)bridge
@@ -71,6 +71,8 @@ - (instancetype)initWithSurfacePresenter:(RCTSurfacePresenter *)surfacePresenter
 
     _stage = RCTSurfaceStageSurfaceDidInitialize;
 
+    _touchHandler = [RCTSurfaceTouchHandler new];
+
     [self _run];
   }
 
@@ -102,6 +104,7 @@ - (RCTSurfaceView *)view
 
   if (!_view) {
     _view = [[RCTSurfaceView alloc] initWithSurface:(RCTSurface *)self];
+    [_touchHandler attachToView:_view];
   }
 
   return _view;

From 7f1ed6848f89bdccc7f7a5cc76019eec67e76b2f Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 8 Jun 2018 20:16:22 -0700
Subject: [PATCH 0751/1109] Fabric: `convertRawProp` was extended to accept an
 optional default value

Summary:
During transforming raw prop (`rawProps[<prop>]`) to typed props (`MyProps.<prop>`) we can face three different cases:
 * `rawProps` collection has proper serialized value for the key. In this case, we have to set a new value of the typed prop converting value using `fromDynamic`.
 * `rawProps` collection does not have value for the key. In this case, we have to copy a value from source prop (`sourceValue`).
 * `rawProps` collection has `null` value for the key. This is the special case which means that the prop was removed from the particular component instance and we have to reset it to some *default* value (which is *not* the same as `sourceValue`). Now the default value of the `defaultValue` (sic!) argument is a default value of the type of the value (which may be different from logical default value).

We didn't handle the last case previously and this caused crashes (and unexpected behavior) because `fromDynamic` often cannot handle `null` value.

And yes, all this mean that we also have to update all `convertRawProp` call sites where logical default values are not equal to type-specific default values. This is a potential error-prone place, especially because now we have to specify logical default values in two places (in a prop declaration and in a parameterized constructor). And seems there is no way to avoid that without performance loss (because both of those places are basically constructors).

My hope is that codegen (where default values are also defined in JavaScript) will help with it eventually.

Reviewed By: fkgozali

Differential Revision: D8247652

fbshipit-source-id: 2cbe65f5f5cccd7a0d34aaa19e385aacebfe8cb1
---
 ReactCommon/fabric/core/propsConversions.h | 30 +++++++++++++++++-----
 1 file changed, 23 insertions(+), 7 deletions(-)

diff --git a/ReactCommon/fabric/core/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
index f4a25f8dff9e..548b88f3de4a 100644
--- a/ReactCommon/fabric/core/propsConversions.h
+++ b/ReactCommon/fabric/core/propsConversions.h
@@ -21,33 +21,49 @@ inline void fromDynamic(const folly::dynamic &value, int &result) { result = val
 inline void fromDynamic(const folly::dynamic &value, std::string &result) { result = value.getString(); }
 
 template <typename T>
-inline T convertRawProp(const RawProps &rawProps, const std::string &name, const T &defaultValue) {
+inline T convertRawProp(
+  const RawProps &rawProps,
+  const std::string &name,
+  const T &sourceValue,
+  const T &defaultValue = T()
+) {
   auto &&iterator = rawProps.find(name);
   if (iterator == rawProps.end()) {
-    return defaultValue;
+    return sourceValue;
   }
 
   auto &&value = iterator->second;
+
+  // Special case: `null` always means `the prop was removed, use default value`.
+  if (value.isNull()) {
+    return defaultValue;
+  }
+
   T result;
   fromDynamic(value, result);
   return result;
 }
 
 template <typename T>
-inline static folly::Optional<T> convertRawProp(const RawProps &rawProps, const std::string &name, const folly::Optional<T> &defaultValue) {
+inline static folly::Optional<T> convertRawProp(
+  const RawProps &rawProps,
+  const std::string &name,
+  const folly::Optional<T> &sourceValue,
+  const folly::Optional<T> &defaultValue = {}
+) {
   auto &&iterator = rawProps.find(name);
   if (iterator == rawProps.end()) {
-    return defaultValue;
+    return sourceValue;
   }
 
   auto &&value = iterator->second;
-  T result;
 
-  // Special case for optionals: `null` always means `no value`.
+  // Special case: `null` always means `the prop was removed, use default value`.
   if (value.isNull()) {
-    return {};
+    return defaultValue;
   }
 
+  T result;
   fromDynamic(value, result);
   return result;
 }

From 63540874eccba29cff42d33088ebe8c92c602647 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Fri, 8 Jun 2018 20:24:34 -0700
Subject: [PATCH 0752/1109] Bump eslint-plugin-react in FBSource

Reviewed By: yungsters

Differential Revision: D8247892

fbshipit-source-id: 4072e65ccf2fdc654f58087a16b4c7709ce393f8
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index f36d371e6630..db192e67092c 100644
--- a/package.json
+++ b/package.json
@@ -210,7 +210,7 @@
     "eslint-plugin-flowtype": "2.43.0",
     "eslint-plugin-jest": "21.8.0",
     "eslint-plugin-prettier": "2.6.0",
-    "eslint-plugin-react": "7.6.1",
+    "eslint-plugin-react": "7.8.2",
     "eslint-plugin-react-native": "^3.2.1",
     "flow-bin": "^0.73.0",
     "jest": "23.1.0",

From c55bcd6ea729cdf57fc14a5478b7c2e3f6b2a94d Mon Sep 17 00:00:00 2001
From: Joshua Wang <wangjoshuah@gmail.com>
Date: Sat, 9 Jun 2018 00:19:06 -0700
Subject: [PATCH 0753/1109] have circle ci use xcode 9.4 (#19629)

Summary:
Circle CI just released Xcode 9.4 https://discuss.circleci.com/t/xcode-9-4-availability-on-circleci/22648/5

Make sure react native still works with Xcode 9.4.

None

[IOS][MINOR] Upgrade CI
Closes https://github.com/facebook/react-native/pull/19629

Differential Revision: D8343236

Pulled By: hramos

fbshipit-source-id: 2266aeafc9a1b1c77ad842f06c9a137bb05b135d
---
 .circleci/config.yml | 10 ++++------
 1 file changed, 4 insertions(+), 6 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 31ea483c70c8..f77c7392272b 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -316,7 +316,7 @@ android_defaults: &android_defaults
 macos_defaults: &macos_defaults
   <<: *defaults
   macos:
-    xcode: "9.2.0"
+    xcode: "9.4.0"
 
 version: 2
 jobs:
@@ -374,9 +374,8 @@ jobs:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "iPhone 5s (11.2)" || true
+      - run: xcrun instruments -w "iPhone 5s (11.4)" || true
       # See https://github.com/Homebrew/homebrew-core/issues/26358.
-      - run: brew upgrade python > /dev/null
       - run: brew install watchman
       - run: *run-objc-ios-tests
 
@@ -390,9 +389,8 @@ jobs:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "Apple TV 1080p (11.2)" || true
+      - run: xcrun instruments -w "Apple TV (11.4)" || true
       # See https://github.com/Homebrew/homebrew-core/issues/26358.
-      - run: brew upgrade python > /dev/null
       - run: brew install watchman
       - run: *run-objc-tvos-tests
 
@@ -406,7 +404,7 @@ jobs:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "iPhone 5s (11.2)" || true
+      - run: xcrun instruments -w "iPhone 5s (11.4)" || true
       - run: *run-objc-ios-e2e-tests
 
       - store_test_results:

From 521fb6d041167ec8a8d0e98ac606db1f27f0c5c8 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 9 Jun 2018 10:57:39 -0700
Subject: [PATCH 0754/1109] Disallow requiring from invariant/warning (#19634)

Summary:
In this repo we have to require from fbjs/lib/invariant and issues occur when we require directly from invariant/warning. Flow doesn't complain about those requires right now because we have a transitive dependency on invariant and warning causing them to happen to be at the root of node_modules.

This change blacklists requiring directly from invariant and warning using Flow. janicduplessis opened a pull request to do this with ESLint back in 2017: https://github.com/facebook/react-native/pull/13014
Closes https://github.com/facebook/react-native/pull/19634

Reviewed By: hramos

Differential Revision: D8343060

Pulled By: TheSavior

fbshipit-source-id: 9cfc7915b2fb68a567355fc2f5edc4dfcd46f4af
---
 .flowconfig | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/.flowconfig b/.flowconfig
index 0d576609315e..10c13ea400f5 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -25,6 +25,11 @@
 ; Ignore metro
 .*/node_modules/metro/.*
 
+; These should not be required directly
+; require from fbjs/lib instead: require('fbjs/lib/invariant')
+.*/node_modules/invariant/.*
+.*/node_modules/warning/.*
+
 [include]
 
 [libs]

From d49ebbcf6278ef54739be0f99b43c743d898a582 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sat, 9 Jun 2018 13:02:55 -0700
Subject: [PATCH 0755/1109] Fabric: All *EventHandlers were renamed to
 *EventEmitter

Summary:
Using `EventHandlers` name was a bad idea, and I cannot tolerate it anymore.
The worst part of it is that when you have a collection of `EventHandlers` objects you cannot use plural word to describe it because `EventHandlers` is an already plural word.

And, this object is actually an event emitter, the thing on which we call events.

Reviewed By: fkgozali

Differential Revision: D8247723

fbshipit-source-id: b3303a4b9529bd6d32bb8ca0378287ebefaedda8
---
 .../ScrollView/RCTScrollViewComponentView.mm  | 20 ++++++-------
 .../View/RCTViewComponentView.h               |  6 ++--
 .../View/RCTViewComponentView.mm              | 18 +++++------
 ...tem.h => RCTUpdateEventEmitterMountItem.h} |  6 ++--
 ...m.mm => RCTUpdateEventEmitterMountItem.mm} | 12 ++++----
 .../Mounting/RCTComponentViewProtocol.h       |  6 ++--
 React/Fabric/Mounting/RCTMountingManager.mm   | 18 +++++------
 .../Mounting/UIView+ComponentViewProtocol.h   |  2 +-
 .../Mounting/UIView+ComponentViewProtocol.mm  |  2 +-
 React/Fabric/RCTSurfaceTouchHandler.mm        | 30 +++++++++----------
 .../componentdescriptor/ComponentDescriptor.h |  8 ++---
 .../ConcreteComponentDescriptor.h             | 22 +++++++-------
 .../fabric/core/events/EventDispatcher.h      |  2 +-
 .../{EventHandlers.cpp => EventEmitter.cpp}   | 12 ++++----
 .../{EventHandlers.h => EventEmitter.h}       | 10 +++----
 .../core/shadownode/ConcreteShadowNode.h      | 14 ++++-----
 .../fabric/core/shadownode/ShadowNode.cpp     | 16 +++++-----
 .../fabric/core/shadownode/ShadowNode.h       | 12 ++++----
 .../fabric/core/tests/ShadowNodeTest.cpp      |  6 ++--
 ...andlers.cpp => ScrollViewEventEmitter.cpp} | 14 ++++-----
 ...entHandlers.h => ScrollViewEventEmitter.h} | 14 ++++-----
 .../fabric/scrollview/ScrollViewShadowNode.h  |  4 +--
 .../fabric/uimanager/FabricUIManager.cpp      | 10 +++----
 ReactCommon/fabric/uimanager/ShadowTree.cpp   | 14 ++++-----
 .../fabric/view/ConcreteViewShadowNode.h      | 22 +++++++-------
 ...EventHandlers.cpp => ViewEventEmitter.cpp} | 18 +++++------
 ...ViewEventHandlers.h => ViewEventEmitter.h} | 12 ++++----
 ReactCommon/fabric/view/ViewShadowNode.h      |  2 +-
 28 files changed, 166 insertions(+), 166 deletions(-)
 rename React/Fabric/Mounting/MountItems/{RCTUpdateEventHandlersMountItem.h => RCTUpdateEventEmitterMountItem.h} (68%)
 rename React/Fabric/Mounting/MountItems/{RCTUpdateEventHandlersMountItem.mm => RCTUpdateEventEmitterMountItem.mm} (65%)
 rename ReactCommon/fabric/core/events/{EventHandlers.cpp => EventEmitter.cpp} (80%)
 rename ReactCommon/fabric/core/events/{EventHandlers.h => EventEmitter.h} (83%)
 rename ReactCommon/fabric/scrollview/{ScrollViewEventHandlers.cpp => ScrollViewEventEmitter.cpp} (69%)
 rename ReactCommon/fabric/scrollview/{ScrollViewEventHandlers.h => ScrollViewEventEmitter.h} (77%)
 rename ReactCommon/fabric/view/{ViewEventHandlers.cpp => ViewEventEmitter.cpp} (79%)
 rename ReactCommon/fabric/view/{ViewEventHandlers.h => ViewEventEmitter.h} (92%)

diff --git a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
index e3b157a57dc8..90e47e77f5d6 100644
--- a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
@@ -11,7 +11,7 @@
 #import <fabric/graphics/Geometry.h>
 #import <fabric/scrollview/ScrollViewLocalData.h>
 #import <fabric/scrollview/ScrollViewProps.h>
-#import <fabric/scrollview/ScrollViewEventHandlers.h>
+#import <fabric/scrollview/ScrollViewEventEmitter.h>
 
 #import "RCTConversions.h"
 #import "RCTEnhancedScrollView.h"
@@ -135,47 +135,47 @@ - (ScrollViewMetrics)_scrollViewMetrics
 
 - (void)scrollViewDidScroll:(UIScrollView *)scrollView
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScroll([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onScroll([self _scrollViewMetrics]);
 }
 
 - (void)scrollViewDidZoom:(UIScrollView *)scrollView
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScroll([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onScroll([self _scrollViewMetrics]);
 }
 
 - (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScrollBeginDrag([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onScrollBeginDrag([self _scrollViewMetrics]);
 }
 
 - (void)scrollViewWillEndDragging:(UIScrollView *)scrollView withVelocity:(CGPoint)velocity targetContentOffset:(inout CGPoint *)targetContentOffset
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScrollEndDrag([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onScrollEndDrag([self _scrollViewMetrics]);
 }
 
 - (void)scrollViewWillBeginDecelerating:(UIScrollView *)scrollView
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onMomentumScrollBegin([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onMomentumScrollBegin([self _scrollViewMetrics]);
 }
 
 - (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onMomentumScrollEnd([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onMomentumScrollEnd([self _scrollViewMetrics]);
 }
 
 - (void)scrollViewDidEndScrollingAnimation:(UIScrollView *)scrollView
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onMomentumScrollEnd([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onMomentumScrollEnd([self _scrollViewMetrics]);
 }
 
 - (void)scrollViewWillBeginZooming:(UIScrollView *)scrollView withView:(nullable UIView *)view
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScrollBeginDrag([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onScrollBeginDrag([self _scrollViewMetrics]);
 }
 
 - (void)scrollViewDidEndZooming:(UIScrollView *)scrollView withView:(nullable UIView *)view atScale:(CGFloat)scale
 {
-  std::static_pointer_cast<const ScrollViewEventHandlers>(_eventHandlers)->onScrollEndDrag([self _scrollViewMetrics]);
+  std::static_pointer_cast<const ScrollViewEventEmitter>(_eventEmitter)->onScrollEndDrag([self _scrollViewMetrics]);
 }
 
 @end
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index f0d482347e86..73c3302a65bc 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -9,10 +9,10 @@
 
 #import <React/RCTComponentViewProtocol.h>
 #import <React/UIView+ComponentViewProtocol.h>
-#import <fabric/core/EventHandlers.h>
+#import <fabric/core/EventEmitter.h>
 #import <fabric/core/LayoutMetrics.h>
 #import <fabric/core/Props.h>
-#import <fabric/view/ViewEventHandlers.h>
+#import <fabric/view/ViewEventEmitter.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
@@ -23,7 +23,7 @@ NS_ASSUME_NONNULL_BEGIN
 @protected
   facebook::react::LayoutMetrics _layoutMetrics;
   facebook::react::SharedProps _props;
-  facebook::react::SharedViewEventHandlers _eventHandlers;
+  facebook::react::SharedViewEventEmitter _eventEmitter;
 }
 
 @end
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index fb688d031924..f6e74eda4b12 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -8,7 +8,7 @@
 #import "RCTViewComponentView.h"
 
 #import <fabric/view/ViewProps.h>
-#import <fabric/view/ViewEventHandlers.h>
+#import <fabric/view/ViewEventEmitter.h>
 
 
 using namespace facebook::react;
@@ -33,10 +33,10 @@ - (void)updateProps:(SharedProps)props
   // TODO: Implement all sutable non-layout <View> props.
 }
 
-- (void)updateEventHandlers:(SharedEventHandlers)eventHandlers
+- (void)updateEventEmitter:(SharedEventEmitter)eventEmitter
 {
-  assert(std::dynamic_pointer_cast<const ViewEventHandlers>(eventHandlers));
-  _eventHandlers = std::static_pointer_cast<const ViewEventHandlers>(eventHandlers);
+  assert(std::dynamic_pointer_cast<const ViewEventEmitter>(eventEmitter));
+  _eventEmitter = std::static_pointer_cast<const ViewEventEmitter>(eventEmitter);
 }
 
 - (void)updateLayoutMetrics:(LayoutMetrics)layoutMetrics
@@ -51,25 +51,25 @@ - (void)updateLayoutMetrics:(LayoutMetrics)layoutMetrics
 
 - (BOOL)accessibilityActivate
 {
-  _eventHandlers->onAccessibilityTap();
+  _eventEmitter->onAccessibilityTap();
   return YES;
 }
 
 - (BOOL)accessibilityPerformMagicTap
 {
-  _eventHandlers->onAccessibilityMagicTap();
+  _eventEmitter->onAccessibilityMagicTap();
   return YES;
 }
 
 - (BOOL)didActivateAccessibilityCustomAction:(UIAccessibilityCustomAction *)action
 {
-  _eventHandlers->onAccessibilityAction([action.name cStringUsingEncoding:NSASCIIStringEncoding]);
+  _eventEmitter->onAccessibilityAction([action.name cStringUsingEncoding:NSASCIIStringEncoding]);
   return YES;
 }
 
-- (SharedEventHandlers)touchEventHandlers
+- (SharedEventEmitter)touchEventEmitter
 {
-  return _eventHandlers;
+  return _eventEmitter;
 }
 
 @end
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.h b/React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.h
similarity index 68%
rename from React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.h
rename to React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.h
index dd11971b8494..7db403b1dd33 100644
--- a/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.h
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.h
@@ -9,17 +9,17 @@
 
 #import <React/RCTMountItemProtocol.h>
 #import <React/RCTPrimitives.h>
-#import <fabric/core/EventHandlers.h>
+#import <fabric/core/EventEmitter.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
 /**
  * Updates event handlers of a component view.
  */
-@interface RCTUpdateEventHandlersMountItem : NSObject <RCTMountItemProtocol>
+@interface RCTUpdateEventEmitterMountItem : NSObject <RCTMountItemProtocol>
 
 - (instancetype)initWithTag:(ReactTag)tag
-              eventHandlers:(facebook::react::SharedEventHandlers)eventHandlers;
+              eventEmitter:(facebook::react::SharedEventEmitter)eventEmitter;
 
 @end
 
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.mm b/React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.mm
similarity index 65%
rename from React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.mm
rename to React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.mm
index cc3066b059cf..18de9cc3a5d0 100644
--- a/React/Fabric/Mounting/MountItems/RCTUpdateEventHandlersMountItem.mm
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.mm
@@ -5,23 +5,23 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#import "RCTUpdateEventHandlersMountItem.h"
+#import "RCTUpdateEventEmitterMountItem.h"
 
 #import "RCTComponentViewRegistry.h"
 
 using namespace facebook::react;
 
-@implementation RCTUpdateEventHandlersMountItem {
+@implementation RCTUpdateEventEmitterMountItem {
   ReactTag _tag;
-  SharedEventHandlers _eventHandlers;
+  SharedEventEmitter _eventEmitter;
 }
 
 - (instancetype)initWithTag:(ReactTag)tag
-              eventHandlers:(SharedEventHandlers)eventHandlers
+              eventEmitter:(SharedEventEmitter)eventEmitter
 {
   if (self = [super init]) {
     _tag = tag;
-    _eventHandlers = eventHandlers;
+    _eventEmitter = eventEmitter;
   }
 
   return self;
@@ -31,7 +31,7 @@ - (void)executeWithRegistry:(RCTComponentViewRegistry *)registry
 {
   UIView<RCTComponentViewProtocol> *componentView = [registry componentViewByTag:_tag];
 
-  [componentView updateEventHandlers:_eventHandlers];
+  [componentView updateEventEmitter:_eventEmitter];
 }
 
 @end
diff --git a/React/Fabric/Mounting/RCTComponentViewProtocol.h b/React/Fabric/Mounting/RCTComponentViewProtocol.h
index 47048efa1b57..a426bfd081fe 100644
--- a/React/Fabric/Mounting/RCTComponentViewProtocol.h
+++ b/React/Fabric/Mounting/RCTComponentViewProtocol.h
@@ -7,7 +7,7 @@
 
 #import <UIKit/UIKit.h>
 
-#import <fabric/core/EventHandlers.h>
+#import <fabric/core/EventEmitter.h>
 #import <fabric/core/LocalData.h>
 #import <fabric/core/Props.h>
 #import <fabric/core/LayoutMetrics.h>
@@ -55,10 +55,10 @@ NS_ASSUME_NONNULL_BEGIN
 
 /*
  * Called for updating component's event handlers set.
- * Receiver must cache `eventHandlers` object inside and use it for emitting
+ * Receiver must cache `eventEmitter` object inside and use it for emitting
  * events when needed.
  */
-- (void)updateEventHandlers:(facebook::react::SharedEventHandlers)eventHandlers;
+- (void)updateEventEmitter:(facebook::react::SharedEventEmitter)eventEmitter;
 
 /*
  * Called for updating component's layout metrics.
diff --git a/React/Fabric/Mounting/RCTMountingManager.mm b/React/Fabric/Mounting/RCTMountingManager.mm
index 93e8f0ea809a..8df452c0c5b2 100644
--- a/React/Fabric/Mounting/RCTMountingManager.mm
+++ b/React/Fabric/Mounting/RCTMountingManager.mm
@@ -20,7 +20,7 @@
 #import "RCTInsertMountItem.h"
 #import "RCTRemoveMountItem.h"
 #import "RCTUpdatePropsMountItem.h"
-#import "RCTUpdateEventHandlersMountItem.h"
+#import "RCTUpdateEventEmitterMountItem.h"
 #import "RCTUpdateLocalDataMountItem.h"
 #import "RCTUpdateLayoutMetricsMountItem.h"
 
@@ -71,9 +71,9 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
                                                                   oldProps:nullptr
                                                                   newProps:instruction.getNewChildNode()->getProps()]];
 
-        // EventHandlers
-        [mountItems addObject:[[RCTUpdateEventHandlersMountItem alloc] initWithTag:instruction.getNewChildNode()->getTag()
-                                                                     eventHandlers:instruction.getNewChildNode()->getEventHandlers()]];
+        // EventEmitter
+        [mountItems addObject:[[RCTUpdateEventEmitterMountItem alloc] initWithTag:instruction.getNewChildNode()->getTag()
+                                                                     eventEmitter:instruction.getNewChildNode()->getEventEmitter()]];
 
         // LocalData
         if (instruction.getNewChildNode()->getLocalData()) {
@@ -124,11 +124,11 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
           [mountItems addObject:mountItem];
         }
 
-        // EventHandlers
-        if (oldShadowNode->getEventHandlers() != newShadowNode->getEventHandlers()) {
-          RCTUpdateEventHandlersMountItem *mountItem =
-            [[RCTUpdateEventHandlersMountItem alloc] initWithTag:instruction.getOldChildNode()->getTag()
-                                                   eventHandlers:instruction.getOldChildNode()->getEventHandlers()];
+        // EventEmitter
+        if (oldShadowNode->getEventEmitter() != newShadowNode->getEventEmitter()) {
+          RCTUpdateEventEmitterMountItem *mountItem =
+            [[RCTUpdateEventEmitterMountItem alloc] initWithTag:instruction.getOldChildNode()->getTag()
+                                                   eventEmitter:instruction.getOldChildNode()->getEventEmitter()];
           [mountItems addObject:mountItem];
         }
 
diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.h b/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
index 75524cef771f..61c981b59563 100644
--- a/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.h
@@ -26,7 +26,7 @@ NS_ASSUME_NONNULL_BEGIN
 - (void)updateProps:(facebook::react::SharedProps)props
            oldProps:(facebook::react::SharedProps)oldProps;
 
-- (void)updateEventHandlers:(facebook::react::SharedEventHandlers)eventHandlers;
+- (void)updateEventEmitter:(facebook::react::SharedEventEmitter)eventEmitter;
 
 - (void)updateLocalData:(facebook::react::SharedLocalData)localData
            oldLocalData:(facebook::react::SharedLocalData)oldLocalData;
diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
index 223bb7c9b92e..eeb64581167f 100644
--- a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
@@ -31,7 +31,7 @@ - (void)updateProps:(facebook::react::SharedProps)props
   // Default implementation does nothing.
 }
 
-- (void)updateEventHandlers:(facebook::react::SharedEventHandlers)eventHandlers
+- (void)updateEventEmitter:(facebook::react::SharedEventEmitter)eventEmitter
 {
   // Default implementation does nothing.
 }
diff --git a/React/Fabric/RCTSurfaceTouchHandler.mm b/React/Fabric/RCTSurfaceTouchHandler.mm
index 09f586646d7f..b668da0d8b57 100644
--- a/React/Fabric/RCTSurfaceTouchHandler.mm
+++ b/React/Fabric/RCTSurfaceTouchHandler.mm
@@ -8,7 +8,7 @@
 #import "RCTSurfaceTouchHandler.h"
 
 #import <UIKit/UIGestureRecognizerSubclass.h>
-#import <fabric/view/ViewEventHandlers.h>
+#import <fabric/view/ViewEventEmitter.h>
 #import <React/RCTUtils.h>
 #import <React/RCTViewComponentView.h>
 
@@ -47,7 +47,7 @@ void reset() {
 };
 
 @protocol RCTTouchableComponentViewProtocol <NSObject>
-  - (SharedViewEventHandlers)touchEventHandlers;
+  - (SharedViewEventEmitter)touchEventEmitter;
 @end
 
 typedef NS_ENUM(NSInteger, RCTTouchEventType) {
@@ -59,7 +59,7 @@ typedef NS_ENUM(NSInteger, RCTTouchEventType) {
 
 struct ActiveTouch {
   Touch touch;
-  SharedViewEventHandlers eventHandlers;
+  SharedViewEventEmitter eventEmitter;
 
   struct Hasher {
     size_t operator()(const ActiveTouch &activeTouch) const {
@@ -95,8 +95,8 @@ static ActiveTouch CreateTouchWithUITouch(UITouch *uiTouch, UIView *rootComponen
 
   ActiveTouch activeTouch = {};
 
-  if ([componentView respondsToSelector:@selector(touchEventHandlers)]) {
-    activeTouch.eventHandlers = [(id<RCTTouchableComponentViewProtocol>)componentView touchEventHandlers];
+  if ([componentView respondsToSelector:@selector(touchEventEmitter)]) {
+    activeTouch.eventEmitter = [(id<RCTTouchableComponentViewProtocol>)componentView touchEventEmitter];
     activeTouch.touch.target = (Tag)componentView.tag;
   }
 
@@ -217,23 +217,23 @@ - (void)_dispatchTouches:(NSSet<UITouch *> *)touches eventType:(RCTTouchEventTyp
 {
   TouchEvent event = {};
   std::unordered_set<ActiveTouch, ActiveTouch::Hasher, ActiveTouch::Comparator> changedActiveTouches = {};
-  std::unordered_set<SharedViewEventHandlers> uniqueEventHandlers = {};
+  std::unordered_set<SharedViewEventEmitter> uniqueEventEmitter = {};
   BOOL isEndishEventType = eventType == RCTTouchEventTypeTouchEnd || eventType == RCTTouchEventTypeTouchCancel;
 
   for (UITouch *touch in touches) {
     auto &&activeTouch = _activeTouches[touch];
 
-    if (!activeTouch.eventHandlers) {
+    if (!activeTouch.eventEmitter) {
       continue;
     }
 
     changedActiveTouches.insert(activeTouch);
     event.changedTouches.insert(activeTouch.touch);
-    uniqueEventHandlers.insert(activeTouch.eventHandlers);
+    uniqueEventEmitter.insert(activeTouch.eventEmitter);
   }
 
   for (auto &&pair : _activeTouches) {
-    if (!pair.second.eventHandlers) {
+    if (!pair.second.eventEmitter) {
       continue;
     }
 
@@ -247,27 +247,27 @@ - (void)_dispatchTouches:(NSSet<UITouch *> *)touches eventType:(RCTTouchEventTyp
     event.touches.insert(pair.second.touch);
   }
 
-  for (auto &&eventHandlers : uniqueEventHandlers) {
+  for (auto &&eventEmitter : uniqueEventEmitter) {
     event.targetTouches.clear();
 
     for (auto &&pair : _activeTouches) {
-      if (pair.second.eventHandlers == eventHandlers) {
+      if (pair.second.eventEmitter == eventEmitter) {
         event.targetTouches.insert(pair.second.touch);
       }
     }
 
     switch (eventType) {
       case RCTTouchEventTypeTouchStart:
-        eventHandlers->onTouchStart(event);
+        eventEmitter->onTouchStart(event);
         break;
       case RCTTouchEventTypeTouchMove:
-        eventHandlers->onTouchMove(event);
+        eventEmitter->onTouchMove(event);
         break;
       case RCTTouchEventTypeTouchEnd:
-        eventHandlers->onTouchEnd(event);
+        eventEmitter->onTouchEnd(event);
         break;
       case RCTTouchEventTypeTouchCancel:
-        eventHandlers->onTouchCancel(event);
+        eventEmitter->onTouchCancel(event);
         break;
     }
   }
diff --git a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
index 669f8475fa4f..1718860b4343 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
@@ -47,7 +47,7 @@ class ComponentDescriptor {
   virtual SharedShadowNode createShadowNode(
     const Tag &tag,
     const Tag &rootTag,
-    const SharedEventHandlers &eventHandlers,
+    const SharedEventEmitter &eventEmitter,
     const SharedProps &props
   ) const = 0;
 
@@ -57,7 +57,7 @@ class ComponentDescriptor {
   virtual SharedShadowNode cloneShadowNode(
     const SharedShadowNode &shadowNode,
     const SharedProps &props = nullptr,
-    const SharedEventHandlers &eventHandlers = nullptr,
+    const SharedEventEmitter &eventEmitter = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ) const = 0;
 
@@ -81,10 +81,10 @@ class ComponentDescriptor {
   ) const = 0;
 
   /*
-   * Creates a new `EventHandlers` object compatible with particular type of
+   * Creates a new `EventEmitter` object compatible with particular type of
    * shadow nodes.
    */
-  virtual SharedEventHandlers createEventHandlers(
+  virtual SharedEventEmitter createEventEmitter(
     const InstanceHandle &instanceHandle,
     const Tag &tag
   ) const = 0;
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 8b5ab2ce7cea..4af3582c1795 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -29,8 +29,8 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   using SharedShadowNodeT = std::shared_ptr<const ShadowNodeT>;
   using ConcreteProps = typename ShadowNodeT::ConcreteProps;
   using SharedConcreteProps = typename ShadowNodeT::SharedConcreteProps;
-  using ConcreteEventHandlers = typename ShadowNodeT::ConcreteEventHandlers;
-  using SharedConcreteEventHandlers = typename ShadowNodeT::SharedConcreteEventHandlers;
+  using ConcreteEventEmitter = typename ShadowNodeT::ConcreteEventEmitter;
+  using SharedConcreteEventEmitter = typename ShadowNodeT::SharedConcreteEventEmitter;
 
 public:
   ConcreteComponentDescriptor(SharedEventDispatcher eventDispatcher):
@@ -58,17 +58,17 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   SharedShadowNode createShadowNode(
     const Tag &tag,
     const Tag &rootTag,
-    const SharedEventHandlers &eventHandlers,
+    const SharedEventEmitter &eventEmitter,
     const SharedProps &props
   ) const override {
     assert(std::dynamic_pointer_cast<const ConcreteProps>(props));
-    assert(std::dynamic_pointer_cast<const ConcreteEventHandlers>(eventHandlers));
+    assert(std::dynamic_pointer_cast<const ConcreteEventEmitter>(eventEmitter));
 
     auto &&shadowNode = std::make_shared<ShadowNodeT>(
       tag,
       rootTag,
       std::static_pointer_cast<const ConcreteProps>(props),
-      std::static_pointer_cast<const ConcreteEventHandlers>(eventHandlers),
+      std::static_pointer_cast<const ConcreteEventEmitter>(eventEmitter),
       ShadowNode::emptySharedShadowNodeSharedList(),
       getCloneFunction()
     );
@@ -80,7 +80,7 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   SharedShadowNode cloneShadowNode(
     const SharedShadowNode &sourceShadowNode,
     const SharedProps &props = nullptr,
-    const SharedEventHandlers &eventHandlers = nullptr,
+    const SharedEventEmitter &eventEmitter = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ) const override {
     assert(std::dynamic_pointer_cast<const ShadowNodeT>(sourceShadowNode));
@@ -88,7 +88,7 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     auto &&shadowNode = std::make_shared<ShadowNodeT>(
       std::static_pointer_cast<const ShadowNodeT>(sourceShadowNode),
       std::static_pointer_cast<const ConcreteProps>(props),
-      std::static_pointer_cast<const ConcreteEventHandlers>(eventHandlers),
+      std::static_pointer_cast<const ConcreteEventEmitter>(eventEmitter),
       children
     );
 
@@ -112,11 +112,11 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     return ShadowNodeT::Props(rawProps, props);
   };
 
-  virtual SharedEventHandlers createEventHandlers(
+  virtual SharedEventEmitter createEventEmitter(
     const InstanceHandle &instanceHandle,
     const Tag &tag
   ) const override {
-    return std::make_shared<ConcreteEventHandlers>(instanceHandle, tag, eventDispatcher_);
+    return std::make_shared<ConcreteEventEmitter>(instanceHandle, tag, eventDispatcher_);
   }
 
 protected:
@@ -133,9 +133,9 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
 
   ShadowNodeCloneFunction getCloneFunction() const {
     if (!cloneFunction_) {
-      cloneFunction_ = [this](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedEventHandlers &eventHandlers, const SharedShadowNodeSharedList &children) {
+      cloneFunction_ = [this](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedEventEmitter &eventEmitter, const SharedShadowNodeSharedList &children) {
         assert(std::dynamic_pointer_cast<const ShadowNodeT>(shadowNode));
-        return this->cloneShadowNode(shadowNode, props, eventHandlers, children);
+        return this->cloneShadowNode(shadowNode, props, eventEmitter, children);
       };
     }
 
diff --git a/ReactCommon/fabric/core/events/EventDispatcher.h b/ReactCommon/fabric/core/events/EventDispatcher.h
index 40e5184a2124..930a547f4ae6 100644
--- a/ReactCommon/fabric/core/events/EventDispatcher.h
+++ b/ReactCommon/fabric/core/events/EventDispatcher.h
@@ -21,7 +21,7 @@ using SharedEventDispatcher = std::shared_ptr<const EventDispatcher>;
 
 /*
  * Abstract class that represent event-delivery infrastructure.
- * Particular `EventHandlers` clases use an object of this class to invoke
+ * Particular `EventEmitter` clases use an object of this class to invoke
  * events.
  */
 class EventDispatcher {
diff --git a/ReactCommon/fabric/core/events/EventHandlers.cpp b/ReactCommon/fabric/core/events/EventEmitter.cpp
similarity index 80%
rename from ReactCommon/fabric/core/events/EventHandlers.cpp
rename to ReactCommon/fabric/core/events/EventEmitter.cpp
index 3d4ecc804885..b4b3b8db38be 100644
--- a/ReactCommon/fabric/core/events/EventHandlers.cpp
+++ b/ReactCommon/fabric/core/events/EventEmitter.cpp
@@ -5,23 +5,23 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#include "EventHandlers.h"
+#include "EventEmitter.h"
 
 #include <folly/dynamic.h>
 
 namespace facebook {
 namespace react {
 
-EventHandlers::EventHandlers(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher):
+EventEmitter::EventEmitter(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher):
   instanceHandle_(instanceHandle),
   tag_(tag),
   eventDispatcher_(eventDispatcher) {}
 
-EventHandlers::~EventHandlers() {
+EventEmitter::~EventEmitter() {
   releaseEventTargetIfNeeded();
 }
 
-void EventHandlers::dispatchEvent(
+void EventEmitter::dispatchEvent(
   const std::string &type,
   const folly::dynamic &payload,
   const EventPriority &priority
@@ -42,7 +42,7 @@ void EventHandlers::dispatchEvent(
   eventDispatcher->dispatchEvent(eventTarget_, type, extendedPayload, priority);
 }
 
-void EventHandlers::createEventTargetIfNeeded() const {
+void EventEmitter::createEventTargetIfNeeded() const {
   std::lock_guard<std::mutex> lock(mutex_);
 
   if (eventTarget_) {
@@ -54,7 +54,7 @@ void EventHandlers::createEventTargetIfNeeded() const {
   eventTarget_ = eventDispatcher->createEventTarget(instanceHandle_);
 }
 
-void EventHandlers::releaseEventTargetIfNeeded() const {
+void EventEmitter::releaseEventTargetIfNeeded() const {
   std::lock_guard<std::mutex> lock(mutex_);
 
   if (!eventTarget_) {
diff --git a/ReactCommon/fabric/core/events/EventHandlers.h b/ReactCommon/fabric/core/events/EventEmitter.h
similarity index 83%
rename from ReactCommon/fabric/core/events/EventHandlers.h
rename to ReactCommon/fabric/core/events/EventEmitter.h
index b55db7dc7e48..eb05bd1c6257 100644
--- a/ReactCommon/fabric/core/events/EventHandlers.h
+++ b/ReactCommon/fabric/core/events/EventEmitter.h
@@ -17,9 +17,9 @@
 namespace facebook {
 namespace react {
 
-class EventHandlers;
+class EventEmitter;
 
-using SharedEventHandlers = std::shared_ptr<const EventHandlers>;
+using SharedEventEmitter = std::shared_ptr<const EventEmitter>;
 
 /*
  * Base class for all particular typed event handlers.
@@ -28,11 +28,11 @@ using SharedEventHandlers = std::shared_ptr<const EventHandlers>;
  *
  * TODO: Reconsider naming of all event-related things.
  */
-class EventHandlers {
+class EventEmitter {
 
 public:
-  EventHandlers(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
-  virtual ~EventHandlers();
+  EventEmitter(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
+  virtual ~EventEmitter();
 
 protected:
 
diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index 86c0976b8ce6..c4f08a45a65e 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -19,15 +19,15 @@ namespace react {
  * `ConcreteShadowNode` is a default implementation of `ShadowNode` interface
  * with many handy features.
  */
-template <typename PropsT, typename EventHandlersT = EventHandlers>
+template <typename PropsT, typename EventEmitterT = EventEmitter>
 class ConcreteShadowNode: public ShadowNode {
   static_assert(std::is_base_of<Props, PropsT>::value, "PropsT must be a descendant of Props");
 
 public:
   using ConcreteProps = PropsT;
   using SharedConcreteProps = std::shared_ptr<const PropsT>;
-  using ConcreteEventHandlers = EventHandlersT;
-  using SharedConcreteEventHandlers = std::shared_ptr<const EventHandlersT>;
+  using ConcreteEventEmitter = EventEmitterT;
+  using SharedConcreteEventEmitter = std::shared_ptr<const EventEmitterT>;
   using SharedConcreteShadowNode = std::shared_ptr<const ConcreteShadowNode>;
 
   static SharedConcreteProps Props(const RawProps &rawProps, const SharedProps &baseProps = nullptr) {
@@ -43,7 +43,7 @@ class ConcreteShadowNode: public ShadowNode {
     const Tag &tag,
     const Tag &rootTag,
     const SharedConcreteProps &props,
-    const SharedConcreteEventHandlers &eventHandlers,
+    const SharedConcreteEventEmitter &eventEmitter,
     const SharedShadowNodeSharedList &children,
     const ShadowNodeCloneFunction &cloneFunction
   ):
@@ -51,7 +51,7 @@ class ConcreteShadowNode: public ShadowNode {
       tag,
       rootTag,
       (SharedProps)props,
-      eventHandlers,
+      eventEmitter,
       children,
       cloneFunction
     ) {};
@@ -59,13 +59,13 @@ class ConcreteShadowNode: public ShadowNode {
   ConcreteShadowNode(
     const SharedConcreteShadowNode &shadowNode,
     const SharedProps &props,
-    const SharedEventHandlers &eventHandlers,
+    const SharedEventEmitter &eventEmitter,
     const SharedShadowNodeSharedList &children
   ):
     ShadowNode(
       shadowNode,
       (SharedProps)props,
-      eventHandlers,
+      eventEmitter,
       children
     ) {}
 
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index e18ae2e387d2..54e1465eb19e 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -24,14 +24,14 @@ ShadowNode::ShadowNode(
   const Tag &tag,
   const Tag &rootTag,
   const SharedProps &props,
-  const SharedEventHandlers &eventHandlers,
+  const SharedEventEmitter &eventEmitter,
   const SharedShadowNodeSharedList &children,
   const ShadowNodeCloneFunction &cloneFunction
 ):
   tag_(tag),
   rootTag_(rootTag),
   props_(props),
-  eventHandlers_(eventHandlers),
+  eventEmitter_(eventEmitter),
   children_(std::make_shared<SharedShadowNodeList>(*children)),
   cloneFunction_(cloneFunction),
   revision_(1) {}
@@ -39,13 +39,13 @@ ShadowNode::ShadowNode(
 ShadowNode::ShadowNode(
   const SharedShadowNode &shadowNode,
   const SharedProps &props,
-  const SharedEventHandlers &eventHandlers,
+  const SharedEventEmitter &eventEmitter,
   const SharedShadowNodeSharedList &children
 ):
   tag_(shadowNode->tag_),
   rootTag_(shadowNode->rootTag_),
   props_(props ? props : shadowNode->props_),
-  eventHandlers_(eventHandlers ? eventHandlers : shadowNode->eventHandlers_),
+  eventEmitter_(eventEmitter ? eventEmitter : shadowNode->eventEmitter_),
   children_(std::make_shared<SharedShadowNodeList>(*(children ? children : shadowNode->children_))),
   sourceNode_(shadowNode),
   localData_(shadowNode->localData_),
@@ -57,7 +57,7 @@ SharedShadowNode ShadowNode::clone(
   const SharedShadowNodeSharedList &children
 ) const {
   assert(cloneFunction_);
-  return cloneFunction_(shared_from_this(), props_, eventHandlers_, children_);
+  return cloneFunction_(shared_from_this(), props_, eventEmitter_, children_);
 }
 
 #pragma mark - Getters
@@ -70,8 +70,8 @@ SharedProps ShadowNode::getProps() const {
   return props_;
 }
 
-SharedEventHandlers ShadowNode::getEventHandlers() const {
-  return eventHandlers_;
+SharedEventEmitter ShadowNode::getEventEmitter() const {
+  return eventEmitter_;
 }
 
 Tag ShadowNode::getTag() const {
@@ -147,7 +147,7 @@ bool ShadowNode::operator==(const ShadowNode& rhs) const {
     tag_ == rhs.tag_ &&
     rootTag_ == rhs.rootTag_ &&
     props_ == rhs.props_ &&
-    eventHandlers_ == rhs.eventHandlers_ &&
+    eventEmitter_ == rhs.eventEmitter_ &&
     localData_ == rhs.localData_;
 }
 
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 9fa1b9341d9f..a526fd698692 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -11,7 +11,7 @@
 #include <memory>
 #include <vector>
 
-#include <fabric/core/EventHandlers.h>
+#include <fabric/core/EventEmitter.h>
 #include <fabric/core/LocalData.h>
 #include <fabric/core/Props.h>
 #include <fabric/core/ReactPrimitives.h>
@@ -33,7 +33,7 @@ using WeakShadowNode = std::weak_ptr<const ShadowNode>;
 using ShadowNodeCloneFunction = std::function<SharedShadowNode(
   const SharedShadowNode &shadowNode,
   const SharedProps &props,
-  const SharedEventHandlers &eventHandlers,
+  const SharedEventEmitter &eventEmitter,
   const SharedShadowNodeSharedList &children
 )>;
 
@@ -50,7 +50,7 @@ class ShadowNode:
     const Tag &tag,
     const Tag &rootTag,
     const SharedProps &props,
-    const SharedEventHandlers &eventHandlers,
+    const SharedEventEmitter &eventEmitter,
     const SharedShadowNodeSharedList &children,
     const ShadowNodeCloneFunction &cloneFunction
   );
@@ -58,7 +58,7 @@ class ShadowNode:
   ShadowNode(
     const SharedShadowNode &shadowNode,
     const SharedProps &props,
-    const SharedEventHandlers &eventHandlers,
+    const SharedEventEmitter &eventEmitter,
     const SharedShadowNodeSharedList &children
   );
 
@@ -77,7 +77,7 @@ class ShadowNode:
 
   SharedShadowNodeSharedList getChildren() const;
   SharedProps getProps() const;
-  SharedEventHandlers getEventHandlers() const;
+  SharedEventEmitter getEventEmitter() const;
   Tag getTag() const;
   Tag getRootTag() const;
 
@@ -143,7 +143,7 @@ class ShadowNode:
   Tag tag_;
   Tag rootTag_;
   SharedProps props_;
-  SharedEventHandlers eventHandlers_;
+  SharedEventEmitter eventEmitter_;
   SharedShadowNodeSharedList children_;
   WeakShadowNode sourceNode_;
   SharedLocalData localData_;
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index 7afbafbb5f8a..a1f7d16b6ffa 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -34,7 +34,7 @@ TEST(ShadowNodeTest, handleShadowNodeCreation) {
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
   ASSERT_EQ(node->getTag(), 9);
   ASSERT_EQ(node->getRootTag(), 1);
-  ASSERT_EQ(node->getEventHandlers(), nullptr);
+  ASSERT_EQ(node->getEventEmitter(), nullptr);
   TestShadowNode *nodePtr = node.get();
   ASSERT_EQ(node->getComponentHandle(), typeid(*nodePtr).hash_code());
   ASSERT_EQ(node->getSourceNode(), nullptr);
@@ -54,7 +54,7 @@ TEST(ShadowNodeTest, handleShadowNodeSimpleCloning) {
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
   ASSERT_EQ(node->getTag(), 9);
   ASSERT_EQ(node->getRootTag(), 1);
-  ASSERT_EQ(node->getEventHandlers(), nullptr);
+  ASSERT_EQ(node->getEventEmitter(), nullptr);
   ASSERT_EQ(node2->getSourceNode(), node);
 }
 
@@ -128,7 +128,7 @@ TEST(ShadowNodeTest, handleCloneFunction) {
     std::make_shared<const TestProps>(),
     nullptr,
     ShadowNode::emptySharedShadowNodeSharedList(),
-    [](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedEventHandlers &eventHandlers, const SharedShadowNodeSharedList &children) {
+    [](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedEventEmitter &eventEmitter, const SharedShadowNodeSharedList &children) {
       return std::make_shared<const TestShadowNode>(
         std::static_pointer_cast<const TestShadowNode>(shadowNode),
         props,
diff --git a/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.cpp b/ReactCommon/fabric/scrollview/ScrollViewEventEmitter.cpp
similarity index 69%
rename from ReactCommon/fabric/scrollview/ScrollViewEventHandlers.cpp
rename to ReactCommon/fabric/scrollview/ScrollViewEventEmitter.cpp
index c331f6b03c87..c416b98b4dde 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.cpp
+++ b/ReactCommon/fabric/scrollview/ScrollViewEventEmitter.cpp
@@ -5,32 +5,32 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#include "ScrollViewEventHandlers.h"
+#include "ScrollViewEventEmitter.h"
 
 namespace facebook {
 namespace react {
 
-void ScrollViewEventHandlers::onScroll(const ScrollViewMetrics &scrollViewMetrics) const {
+void ScrollViewEventEmitter::onScroll(const ScrollViewMetrics &scrollViewMetrics) const {
   dispatchScrollViewEvent("scroll", scrollViewMetrics);
 }
 
-void ScrollViewEventHandlers::onScrollBeginDrag(const ScrollViewMetrics &scrollViewMetrics) const {
+void ScrollViewEventEmitter::onScrollBeginDrag(const ScrollViewMetrics &scrollViewMetrics) const {
   dispatchScrollViewEvent("scrollBeginDrag", scrollViewMetrics);
 }
 
-void ScrollViewEventHandlers::onScrollEndDrag(const ScrollViewMetrics &scrollViewMetrics) const {
+void ScrollViewEventEmitter::onScrollEndDrag(const ScrollViewMetrics &scrollViewMetrics) const {
   dispatchScrollViewEvent("scrollEndDrag", scrollViewMetrics);
 }
 
-void ScrollViewEventHandlers::onMomentumScrollBegin(const ScrollViewMetrics &scrollViewMetrics) const {
+void ScrollViewEventEmitter::onMomentumScrollBegin(const ScrollViewMetrics &scrollViewMetrics) const {
   dispatchScrollViewEvent("momentumScrollBegin", scrollViewMetrics);
 }
 
-void ScrollViewEventHandlers::onMomentumScrollEnd(const ScrollViewMetrics &scrollViewMetrics) const {
+void ScrollViewEventEmitter::onMomentumScrollEnd(const ScrollViewMetrics &scrollViewMetrics) const {
   dispatchScrollViewEvent("momentumScrollEnd", scrollViewMetrics);
 }
 
-void ScrollViewEventHandlers::dispatchScrollViewEvent(const std::string &name, const ScrollViewMetrics &scrollViewMetrics, const folly::dynamic &payload) const {
+void ScrollViewEventEmitter::dispatchScrollViewEvent(const std::string &name, const ScrollViewMetrics &scrollViewMetrics, const folly::dynamic &payload) const {
   folly::dynamic compoundPayload = folly::dynamic::object();
 
   compoundPayload["contentOffset"] = folly::dynamic::object
diff --git a/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.h b/ReactCommon/fabric/scrollview/ScrollViewEventEmitter.h
similarity index 77%
rename from ReactCommon/fabric/scrollview/ScrollViewEventHandlers.h
rename to ReactCommon/fabric/scrollview/ScrollViewEventEmitter.h
index 8f6a93e7221a..c9bd52543ad2 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewEventHandlers.h
+++ b/ReactCommon/fabric/scrollview/ScrollViewEventEmitter.h
@@ -9,8 +9,8 @@
 #include <memory>
 
 #include <fabric/graphics/Geometry.h>
-#include <fabric/core/EventHandlers.h>
-#include <fabric/view/ViewEventHandlers.h>
+#include <fabric/core/EventEmitter.h>
+#include <fabric/view/ViewEventEmitter.h>
 
 #include <folly/dynamic.h>
 
@@ -26,16 +26,16 @@ class ScrollViewMetrics {
   Float zoomScale;
 };
 
-class ScrollViewEventHandlers;
+class ScrollViewEventEmitter;
 
-using SharedScrollViewEventHandlers = std::shared_ptr<const ScrollViewEventHandlers>;
+using SharedScrollViewEventEmitter = std::shared_ptr<const ScrollViewEventEmitter>;
 
-class ScrollViewEventHandlers:
-  public ViewEventHandlers {
+class ScrollViewEventEmitter:
+  public ViewEventEmitter {
 
 public:
 
-  using ViewEventHandlers::ViewEventHandlers;
+  using ViewEventEmitter::ViewEventEmitter;
 
   void onScroll(const ScrollViewMetrics &scrollViewMetrics) const;
   void onScrollBeginDrag(const ScrollViewMetrics &scrollViewMetrics) const;
diff --git a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
index 5a74f0c320df..c2db4ed66c8f 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
+++ b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
@@ -10,7 +10,7 @@
 #include <memory>
 
 #include <fabric/core/LayoutContext.h>
-#include <fabric/scrollview/ScrollViewEventHandlers.h>
+#include <fabric/scrollview/ScrollViewEventEmitter.h>
 #include <fabric/scrollview/ScrollViewProps.h>
 #include <fabric/view/ConcreteViewShadowNode.h>
 
@@ -25,7 +25,7 @@ using SharedScrollViewShadowNode = std::shared_ptr<const ScrollViewShadowNode>;
  * `ShadowNode` for <ScrollView> component.
  */
 class ScrollViewShadowNode final:
-  public ConcreteViewShadowNode<ScrollViewProps, ScrollViewEventHandlers> {
+  public ConcreteViewShadowNode<ScrollViewProps, ScrollViewEventEmitter> {
 
 public:
 
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 41115a191eeb..30df1137cbfb 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -134,7 +134,7 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
     componentDescriptor->createShadowNode(
       tag,
       rootTag,
-      componentDescriptor->createEventHandlers(instanceHandle, tag),
+      componentDescriptor->createEventEmitter(instanceHandle, tag),
       componentDescriptor->cloneProps(nullptr, rawProps)
     );
 
@@ -155,7 +155,7 @@ SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode,
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
-      componentDescriptor->createEventHandlers(instanceHandle, shadowNode->getTag()),
+      componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
       nullptr
     );
 
@@ -172,7 +172,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
-      componentDescriptor->createEventHandlers(instanceHandle, shadowNode->getTag()),
+      componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
@@ -190,7 +190,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
-      componentDescriptor->createEventHandlers(instanceHandle, shadowNode->getTag()),
+      componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
       nullptr
     );
 
@@ -208,7 +208,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
-      componentDescriptor->createEventHandlers(instanceHandle, shadowNode->getTag()),
+      componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 140ff8071e1c..bc19c1b329bf 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -18,12 +18,12 @@ namespace react {
 ShadowTree::ShadowTree(Tag rootTag):
   rootTag_(rootTag) {
 
-  auto &&noopEventHandlers = std::make_shared<const ViewEventHandlers>(nullptr, rootTag, nullptr);
+  auto &&noopEventEmitter = std::make_shared<const ViewEventEmitter>(nullptr, rootTag, nullptr);
   rootShadowNode_ = std::make_shared<RootShadowNode>(
     rootTag,
     rootTag,
     RootShadowNode::defaultSharedProps(),
-    noopEventHandlers,
+    noopEventEmitter,
     ShadowNode::emptySharedShadowNodeSharedList(),
     nullptr
   );
@@ -108,11 +108,11 @@ void ShadowTree::emitLayoutEvents(const TreeMutationInstructionList &instruction
         type == TreeMutationInstruction::Replacement
     ) {
       auto &&newShadowNode = instruction.getNewChildNode();
-      auto &&eventHandlers = newShadowNode->getEventHandlers();
-      auto &&viewEventHandlers = std::dynamic_pointer_cast<const ViewEventHandlers>(eventHandlers);
+      auto &&eventEmitter = newShadowNode->getEventEmitter();
+      auto &&viewEventEmitter = std::dynamic_pointer_cast<const ViewEventEmitter>(eventEmitter);
 
-      // Checking if particular shadow node supports `onLayout` event (part of `ViewEventHandlers`).
-      if (viewEventHandlers) {
+      // Checking if particular shadow node supports `onLayout` event (part of `ViewEventEmitter`).
+      if (viewEventEmitter) {
         // Now we know that both (old and new) shadow nodes must be `LayoutableShadowNode` subclasses.
         assert(std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode));
         // TODO(T29661055): Consider using `std::reinterpret_pointer_cast`.
@@ -132,7 +132,7 @@ void ShadowTree::emitLayoutEvents(const TreeMutationInstructionList &instruction
           }
         }
 
-        viewEventHandlers->onLayout(newLayoutableShadowNode->getLayoutMetrics());
+        viewEventEmitter->onLayout(newLayoutableShadowNode->getLayoutMetrics());
       }
     }
   }
diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
index df1707ea5d7c..dc898dcdd7bc 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -12,7 +12,7 @@
 #include <fabric/core/ShadowNode.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
 #include <fabric/view/AccessibleShadowNode.h>
-#include <fabric/view/ViewEventHandlers.h>
+#include <fabric/view/ViewEventEmitter.h>
 #include <fabric/view/ViewProps.h>
 #include <fabric/view/YogaLayoutableShadowNode.h>
 
@@ -24,9 +24,9 @@ namespace react {
  * as <View> and similar basic behaviour).
  * For example: <Paragraph>, <Image>, but not <Text>, <RawText>.
  */
-template <typename ViewPropsT = ViewProps, typename ViewEventHandlersT = ViewEventHandlers>
+template <typename ViewPropsT = ViewProps, typename ViewEventEmitterT = ViewEventEmitter>
 class ConcreteViewShadowNode:
-  public ConcreteShadowNode<ViewPropsT, ViewEventHandlersT>,
+  public ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>,
   public AccessibleShadowNode,
   public YogaLayoutableShadowNode {
 
@@ -38,23 +38,23 @@ class ConcreteViewShadowNode:
 
   using ConcreteViewProps = ViewPropsT;
   using SharedConcreteViewProps = std::shared_ptr<const ViewPropsT>;
-  using ConcreteViewEventHandlers = ViewEventHandlersT;
-  using SharedConcreteViewEventHandlers = std::shared_ptr<const ViewEventHandlersT>;
+  using ConcreteViewEventEmitter = ViewEventEmitterT;
+  using SharedConcreteViewEventEmitter = std::shared_ptr<const ViewEventEmitterT>;
   using SharedConcreteViewShadowNode = std::shared_ptr<const ConcreteViewShadowNode>;
 
   ConcreteViewShadowNode(
     const Tag &tag,
     const Tag &rootTag,
     const SharedConcreteViewProps &props,
-    const SharedConcreteViewEventHandlers &eventHandlers,
+    const SharedConcreteViewEventEmitter &eventEmitter,
     const SharedShadowNodeSharedList &children,
     const ShadowNodeCloneFunction &cloneFunction
   ):
-    ConcreteShadowNode<ViewPropsT, ViewEventHandlersT>(
+    ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>(
       tag,
       rootTag,
       props,
-      eventHandlers,
+      eventEmitter,
       children,
       cloneFunction
     ),
@@ -69,13 +69,13 @@ class ConcreteViewShadowNode:
   ConcreteViewShadowNode(
     const SharedConcreteViewShadowNode &shadowNode,
     const SharedConcreteViewProps &props,
-    const SharedConcreteViewEventHandlers &eventHandlers,
+    const SharedConcreteViewEventEmitter &eventEmitter,
     const SharedShadowNodeSharedList &children
   ):
-    ConcreteShadowNode<ViewPropsT, ViewEventHandlersT>(
+    ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>(
       shadowNode,
       props,
-      eventHandlers,
+      eventEmitter,
       children
     ),
     AccessibleShadowNode(
diff --git a/ReactCommon/fabric/view/ViewEventHandlers.cpp b/ReactCommon/fabric/view/ViewEventEmitter.cpp
similarity index 79%
rename from ReactCommon/fabric/view/ViewEventHandlers.cpp
rename to ReactCommon/fabric/view/ViewEventEmitter.cpp
index 3cdadd3527c6..fe1b246db983 100644
--- a/ReactCommon/fabric/view/ViewEventHandlers.cpp
+++ b/ReactCommon/fabric/view/ViewEventEmitter.cpp
@@ -5,28 +5,28 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#include "ViewEventHandlers.h"
+#include "ViewEventEmitter.h"
 
 namespace facebook {
 namespace react {
 
 #pragma mark - Accessibility
 
-void ViewEventHandlers::onAccessibilityAction(const std::string &name) const {
+void ViewEventEmitter::onAccessibilityAction(const std::string &name) const {
   dispatchEvent("accessibilityAction", folly::dynamic::object("action", name));
 }
 
-void ViewEventHandlers::onAccessibilityTap() const {
+void ViewEventEmitter::onAccessibilityTap() const {
   dispatchEvent("accessibilityTap");
 }
 
-void ViewEventHandlers::onAccessibilityMagicTap() const {
+void ViewEventEmitter::onAccessibilityMagicTap() const {
   dispatchEvent("magicTap");
 }
 
 #pragma mark - Layout
 
-void ViewEventHandlers::onLayout(const LayoutMetrics &layoutMetrics) const {
+void ViewEventEmitter::onLayout(const LayoutMetrics &layoutMetrics) const {
   folly::dynamic payload = folly::dynamic::object();
   auto &&frame = layoutMetrics.frame;
   payload["layout"] = folly::dynamic::object
@@ -71,19 +71,19 @@ static folly::dynamic touchEventPayload(const TouchEvent &event) {
   return object;
 }
 
-void ViewEventHandlers::onTouchStart(const TouchEvent &event) const {
+void ViewEventEmitter::onTouchStart(const TouchEvent &event) const {
   dispatchEvent("touchStart", touchEventPayload(event));
 }
 
-void ViewEventHandlers::onTouchMove(const TouchEvent &event) const {
+void ViewEventEmitter::onTouchMove(const TouchEvent &event) const {
   dispatchEvent("touchMove", touchEventPayload(event));
 }
 
-void ViewEventHandlers::onTouchEnd(const TouchEvent &event) const {
+void ViewEventEmitter::onTouchEnd(const TouchEvent &event) const {
   dispatchEvent("touchEnd", touchEventPayload(event));
 }
 
-void ViewEventHandlers::onTouchCancel(const TouchEvent &event) const {
+void ViewEventEmitter::onTouchCancel(const TouchEvent &event) const {
   dispatchEvent("touchCancel", touchEventPayload(event));
 }
 
diff --git a/ReactCommon/fabric/view/ViewEventHandlers.h b/ReactCommon/fabric/view/ViewEventEmitter.h
similarity index 92%
rename from ReactCommon/fabric/view/ViewEventHandlers.h
rename to ReactCommon/fabric/view/ViewEventEmitter.h
index 654649ed384a..04af2fee6e10 100644
--- a/ReactCommon/fabric/view/ViewEventHandlers.h
+++ b/ReactCommon/fabric/view/ViewEventEmitter.h
@@ -8,7 +8,7 @@
 
 #include <memory>
 
-#include <fabric/core/EventHandlers.h>
+#include <fabric/core/EventEmitter.h>
 #include <fabric/core/LayoutMetrics.h>
 #include <fabric/core/ReactPrimitives.h>
 
@@ -97,16 +97,16 @@ struct TouchEvent {
   Touches targetTouches;
 };
 
-class ViewEventHandlers;
+class ViewEventEmitter;
 
-using SharedViewEventHandlers = std::shared_ptr<const ViewEventHandlers>;
+using SharedViewEventEmitter = std::shared_ptr<const ViewEventEmitter>;
 
-class ViewEventHandlers:
-  public EventHandlers {
+class ViewEventEmitter:
+  public EventEmitter {
 
 public:
 
-  using EventHandlers::EventHandlers;
+  using EventEmitter::EventEmitter;
 
 #pragma mark - Accessibility
 
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/view/ViewShadowNode.h
index 4ad05c83f921..a406f34de8a9 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.h
+++ b/ReactCommon/fabric/view/ViewShadowNode.h
@@ -20,7 +20,7 @@ class ViewShadowNode;
 using SharedViewShadowNode = std::shared_ptr<const ViewShadowNode>;
 
 class ViewShadowNode final:
-  public ConcreteViewShadowNode<ViewProps, ViewEventHandlers> {
+  public ConcreteViewShadowNode<ViewProps, ViewEventEmitter> {
 
 public:
 

From e79b945f75ae7fa0fe3858082f6b4006df19ae50 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Sat, 9 Jun 2018 18:01:25 -0700
Subject: [PATCH 0756/1109] Add MIT License Header

Summary: When a third party library is vendored, both the original copyright header as well as React Native's header are required.

Reviewed By: fkgozali

Differential Revision: D8284116

fbshipit-source-id: 1748eb011c843a87e9ed421597571b66334edfd2
---
 Libraries/vendor/core/whatwg-fetch.js | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/Libraries/vendor/core/whatwg-fetch.js b/Libraries/vendor/core/whatwg-fetch.js
index 1b5603201686..cdfa4fc69a44 100644
--- a/Libraries/vendor/core/whatwg-fetch.js
+++ b/Libraries/vendor/core/whatwg-fetch.js
@@ -1,3 +1,12 @@
+/**
+* Copyright (c) 2015-present, Facebook, Inc.
+*
+* This source code is licensed under the MIT license found in the
+* LICENSE file in the root directory of this source tree.
+*
+* @format
+*/
+
 // Fork of https://github.com/github/fetch/blob/master/fetch.js that does not
 // use reponseType: 'blob' by default. RN already has specific native implementations
 // for different response types so there is no need to add the extra blob overhead.

From ad67f556fb145d38fe547e1e8baa73ccc7a431b0 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sat, 9 Jun 2018 18:05:12 -0700
Subject: [PATCH 0757/1109] Migrate PickerIOS to ES6 Class

Reviewed By: sahrens

Differential Revision: D8343380

fbshipit-source-id: 9432f0810c67034f20b44ba9f4955d4ffd2ef1d2
---
 Libraries/Components/Picker/PickerIOS.ios.js | 142 +++++++++----------
 Libraries/StyleSheet/processColor.js         |   2 +-
 2 files changed, 70 insertions(+), 74 deletions(-)

diff --git a/Libraries/Components/Picker/PickerIOS.ios.js b/Libraries/Components/Picker/PickerIOS.ios.js
index 6eef251e5b4c..62ebe53e89a3 100644
--- a/Libraries/Components/Picker/PickerIOS.ios.js
+++ b/Libraries/Components/Picker/PickerIOS.ios.js
@@ -8,57 +8,90 @@
  * This is a controlled component version of RCTPickerIOS
  *
  * @format
+ * @flow
  */
 
 'use strict';
 
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const React = require('React');
 const ReactNative = require('ReactNative');
-const PropTypes = require('prop-types');
 const StyleSheet = require('StyleSheet');
-const StyleSheetPropType = require('StyleSheetPropType');
-const TextStylePropTypes = require('TextStylePropTypes');
 const View = require('View');
-const ViewPropTypes = require('ViewPropTypes');
 const processColor = require('processColor');
-
-const createReactClass = require('create-react-class');
-const itemStylePropType = StyleSheetPropType(TextStylePropTypes);
 const requireNativeComponent = require('requireNativeComponent');
 
+import type {SyntheticEvent} from 'CoreEventTypes';
 import type {ColorValue} from 'StyleSheetTypes';
 import type {ViewProps} from 'ViewPropTypes';
+import type {TextStyleProp} from 'StyleSheet';
+
+type PickerIOSChangeEvent = SyntheticEvent<
+  $ReadOnly<{|
+    newValue: any,
+    newIndex: number,
+  |}>,
+>;
+
+type RCTPickerIOSItemType = $ReadOnly<{|
+  label: ?Label,
+  value: ?any,
+  textColor: ?number,
+|}>;
+
+type RCTPickerIOSType = Class<
+  ReactNative.NativeComponent<
+    $ReadOnly<{|
+      items: $ReadOnlyArray<RCTPickerIOSItemType>,
+      onChange: (event: PickerIOSChangeEvent) => void,
+      onResponderTerminationRequest: () => boolean,
+      onStartShouldSetResponder: () => boolean,
+      selectedIndex: number,
+      style?: ?TextStyleProp,
+    |}>,
+  >,
+>;
+
+const RCTPickerIOS: RCTPickerIOSType = (requireNativeComponent(
+  'RCTPicker',
+): any);
+
+type Label = Stringish | number;
 
 type Props = $ReadOnly<{|
   ...ViewProps,
-  color?: ?ColorValue,
-  label: string,
-  testID?: ?string,
+  children: React.ChildrenArray<React.Element<typeof PickerIOSItem>>,
+  itemStyle?: ?TextStyleProp,
+  onChange?: ?(event: PickerIOSChangeEvent) => mixed,
+  onValueChange?: ?(newValue: any, newIndex: number) => mixed,
+  selectedValue: any,
+|}>;
+
+type State = {|
+  selectedIndex: number,
+  items: $ReadOnlyArray<RCTPickerIOSItemType>,
+|};
+
+type ItemProps = $ReadOnly<{|
+  label: ?Label,
   value?: ?any,
+  color?: ?ColorValue,
 |}>;
 
-const PickerIOS = createReactClass({
-  displayName: 'PickerIOS',
-  mixins: [NativeMethodsMixin],
+const PickerIOSItem = (props: ItemProps) => {
+  return null;
+};
 
-  propTypes: {
-    ...ViewPropTypes,
-    itemStyle: itemStylePropType,
-    onValueChange: PropTypes.func,
-    selectedValue: PropTypes.any, // string or integer basically
-  },
+class PickerIOS extends React.Component<Props, State> {
+  _picker: ?React.ElementRef<RCTPickerIOSType> = null;
 
-  getInitialState: function() {
-    return this._stateFromProps(this.props);
-  },
+  state = {
+    selectedIndex: 0,
+    items: [],
+  };
 
-  UNSAFE_componentWillReceiveProps: function(nextProps) {
-    this.setState(this._stateFromProps(nextProps));
-  },
+  static Item = PickerIOSItem;
 
-  // Translate PickerIOS prop and children into stuff that RCTPickerIOS understands.
-  _stateFromProps: function(props) {
+  static getDerivedStateFromProps(props: Props): State {
     let selectedIndex = 0;
     const items = [];
     React.Children.toArray(props.children).forEach(function(child, index) {
@@ -72,13 +105,15 @@ const PickerIOS = createReactClass({
       });
     });
     return {selectedIndex, items};
-  },
+  }
 
-  render: function() {
+  render() {
     return (
       <View style={this.props.style}>
         <RCTPickerIOS
-          ref={picker => (this._picker = picker)}
+          ref={picker => {
+            this._picker = picker;
+          }}
           style={[styles.pickerIOS, this.props.itemStyle]}
           items={this.state.items}
           selectedIndex={this.state.selectedIndex}
@@ -88,9 +123,9 @@ const PickerIOS = createReactClass({
         />
       </View>
     );
-  },
+  }
 
-  _onChange: function(event) {
+  _onChange = event => {
     if (this.props.onChange) {
       this.props.onChange(event);
     }
@@ -115,30 +150,7 @@ const PickerIOS = createReactClass({
         selectedIndex: this.state.selectedIndex,
       });
     }
-  },
-});
-
-PickerIOS.Item = class extends React.Component<
-  $ReadOnly<{|
-    label: string,
-    value?: ?any,
-    color?: ?ColorValue,
-  |}>,
-> {
-  static propTypes = {
-    value: PropTypes.any, // string or integer basically
-    label: PropTypes.string,
-    color: PropTypes.string,
   };
-
-  render() {
-    // These items don't get rendered directly.
-    return null;
-  }
-};
-
-class TypedPickerIOS extends ReactNative.NativeComponent<Props> {
-  static Item = PickerIOS.Item;
 }
 
 const styles = StyleSheet.create({
@@ -150,20 +162,4 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTPickerIOS = requireNativeComponent(
-  'RCTPicker',
-  {
-    propTypes: {
-      style: itemStylePropType,
-    },
-  },
-  {
-    nativeOnly: {
-      items: true,
-      onChange: true,
-      selectedIndex: true,
-    },
-  },
-);
-
-module.exports = ((PickerIOS: any): Class<TypedPickerIOS>);
+module.exports = PickerIOS;
diff --git a/Libraries/StyleSheet/processColor.js b/Libraries/StyleSheet/processColor.js
index 99b5ecf468cb..77ba69ded17e 100644
--- a/Libraries/StyleSheet/processColor.js
+++ b/Libraries/StyleSheet/processColor.js
@@ -15,7 +15,7 @@ const Platform = require('Platform');
 const normalizeColor = require('normalizeColor');
 
 /* eslint no-bitwise: 0 */
-function processColor(color?: string | number): ?number {
+function processColor(color?: ?(string | number)): ?number {
   if (color === undefined || color === null) {
     return color;
   }

From 5fbb307e24e144614b559bac57d1dfab6f52f2f4 Mon Sep 17 00:00:00 2001
From: Felix Yan <felixonmars@archlinux.org>
Date: Sat, 9 Jun 2018 20:07:08 -0700
Subject: [PATCH 0758/1109] Fix some typos in dumpReactTree.js (#19636)

Summary:
Simple doc fixes
Closes https://github.com/facebook/react-native/pull/19636

Differential Revision: D8344481

Pulled By: TheSavior

fbshipit-source-id: b6fa064f70793bdaf1d6346b2775373b74c2ae3b
---
 Libraries/BugReporting/dumpReactTree.js | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/Libraries/BugReporting/dumpReactTree.js b/Libraries/BugReporting/dumpReactTree.js
index 844585714703..7cbb2530f205 100644
--- a/Libraries/BugReporting/dumpReactTree.js
+++ b/Libraries/BugReporting/dumpReactTree.js
@@ -51,14 +51,14 @@ function getReactTree() {
 }
 
 /*
-function dumpNode(node: Object, identation: number) {
+function dumpNode(node: Object, indentation: number) {
   const data = getReactData(node);
   if (data.nodeType === 'Text') {
-    return indent(identation) + data.text + '\n';
+    return indent(indentation) + data.text + '\n';
   } else if (data.nodeType === 'Empty') {
     return '';
   }
-  let output = indent(identation) + `<${data.name}`;
+  let output = indent(indentation) + `<${data.name}`;
   if (data.nodeType === 'Composite') {
     for (const propName of Object.getOwnPropertyNames(data.props || {})) {
       if (isNormalProp(propName)) {
@@ -76,11 +76,11 @@ function dumpNode(node: Object, identation: number) {
   }
   let childOutput = '';
   for (const child of data.children || []) {
-    childOutput += dumpNode(child, identation + 1);
+    childOutput += dumpNode(child, indentation + 1);
   }
 
   if (childOutput) {
-    output += '>\n' + childOutput + indent(identation) + `</${data.name}>\n`;
+    output += '>\n' + childOutput + indent(indentation) + `</${data.name}>\n`;
   } else {
     output += ' />\n';
   }

From f573ea8a6679e8d32bbff05750148b942591c4c3 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Sat, 9 Jun 2018 21:18:23 -0700
Subject: [PATCH 0759/1109] iOS: fix fabric core test

Reviewed By: shergin

Differential Revision: D8344613

fbshipit-source-id: 10c604e7fbe2ff3b8c47babedea12a197c0c56b2
---
 .../fabric/core/tests/ComponentDescriptorTest.cpp      | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
index 99fb54201f02..12e09787a7ad 100644
--- a/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
+++ b/ReactCommon/fabric/core/tests/ComponentDescriptorTest.cpp
@@ -20,7 +20,7 @@ TEST(ComponentDescriptorTest, createShadowNode) {
   RawProps raw;
   raw["nativeID"] = "abc";
   SharedProps props = descriptor->cloneProps(nullptr, raw);
-  SharedShadowNode node = descriptor->createShadowNode(9, 1, nullptr, props);
+  SharedShadowNode node = descriptor->createShadowNode(9, 1, descriptor->createEventEmitter(0, 9), props);
 
   ASSERT_EQ(node->getComponentHandle(), typeid(TestShadowNode).hash_code());
   ASSERT_STREQ(node->getComponentName().c_str(), "Test");
@@ -35,7 +35,7 @@ TEST(ComponentDescriptorTest, cloneShadowNode) {
   RawProps raw;
   raw["nativeID"] = "abc";
   SharedProps props = descriptor->cloneProps(nullptr, raw);
-  SharedShadowNode node = descriptor->createShadowNode(9, 1, nullptr, props);
+  SharedShadowNode node = descriptor->createShadowNode(9, 1, descriptor->createEventEmitter(0, 9), props);
   SharedShadowNode cloned = descriptor->cloneShadowNode(node);
 
   ASSERT_EQ(cloned->getComponentHandle(), typeid(TestShadowNode).hash_code());
@@ -51,9 +51,9 @@ TEST(ComponentDescriptorTest, appendChild) {
   RawProps raw;
   raw["nativeID"] = "abc";
   SharedProps props = descriptor->cloneProps(nullptr, raw);
-  SharedShadowNode node1 = descriptor->createShadowNode(1, 1, nullptr, props);
-  SharedShadowNode node2 = descriptor->createShadowNode(2, 1, nullptr, props);
-  SharedShadowNode node3 = descriptor->createShadowNode(3, 1, nullptr, props);
+  SharedShadowNode node1 = descriptor->createShadowNode(1, 1, descriptor->createEventEmitter(0, 1), props);
+  SharedShadowNode node2 = descriptor->createShadowNode(2, 1, descriptor->createEventEmitter(0, 2), props);
+  SharedShadowNode node3 = descriptor->createShadowNode(3, 1, descriptor->createEventEmitter(0, 3), props);
 
   descriptor->appendChild(node1, node2);
   descriptor->appendChild(node1, node3);

From 160bf731e5daa0d2932aa3c4d1165aecb7ba9ff0 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sun, 10 Jun 2018 13:37:53 -0700
Subject: [PATCH 0760/1109] Switch to Platform.isTV to pass Android Flow

Reviewed By: sahrens

Differential Revision: D8345911

fbshipit-source-id: 9af7a25127e7c35844a6c59b267a77cf8adba535
---
 Libraries/Components/ScrollView/ScrollView.js        |  2 +-
 Libraries/Components/Touchable/TouchableHighlight.js |  2 +-
 Libraries/Components/View/ViewPropTypes.js           |  2 +-
 Libraries/Modal/Modal.js                             |  2 +-
 Libraries/Utilities/BackHandler.ios.js               |  2 +-
 RNTester/js/ARTExample.js                            |  2 +-
 RNTester/js/ListExampleShared.js                     |  2 +-
 RNTester/js/ModalExample.js                          |  4 ++--
 RNTester/js/RNTesterExampleList.js                   |  2 +-
 RNTester/js/TVEventHandlerExample.js                 |  2 +-
 RNTester/js/TextExample.ios.js                       | 12 ++++++------
 11 files changed, 17 insertions(+), 17 deletions(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 6e9e40d60e73..a2be38422765 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -1041,7 +1041,7 @@ const ScrollView = createReactClass({
         return (
           // $FlowFixMe Invalid prop usage
           <ScrollViewClass {...props} ref={this._setScrollViewRef}>
-            {Platform.isTVOS ? null : refreshControl}
+            {Platform.isTV ? null : refreshControl}
             {contentContainer}
           </ScrollViewClass>
         );
diff --git a/Libraries/Components/Touchable/TouchableHighlight.js b/Libraries/Components/Touchable/TouchableHighlight.js
index 117884faf864..5a681c099125 100644
--- a/Libraries/Components/Touchable/TouchableHighlight.js
+++ b/Libraries/Components/Touchable/TouchableHighlight.js
@@ -269,7 +269,7 @@ const TouchableHighlight = ((createReactClass({
 
   touchableHandlePress: function(e: PressEvent) {
     clearTimeout(this._hideTimeout);
-    if (!Platform.isTVOS) {
+    if (!Platform.isTV) {
       this._showUnderlay();
       this._hideTimeout = setTimeout(
         this._hideUnderlay,
diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index addbc6e7e81d..0f7dea210694 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -72,7 +72,7 @@ export type ViewProps = $ReadOnly<{|
   ...GestureResponderEventProps,
   ...TouchEventProps,
 
-  // There's no easy way to create a different type if (Platform.isTVOS):
+  // There's no easy way to create a different type if (Platform.isTV):
   // so we must include TVViewProps
   ...TVViewProps,
 
diff --git a/Libraries/Modal/Modal.js b/Libraries/Modal/Modal.js
index fcc3900da443..1af6fec61486 100644
--- a/Libraries/Modal/Modal.js
+++ b/Libraries/Modal/Modal.js
@@ -90,7 +90,7 @@ class Modal extends React.Component<Object> {
      * See https://facebook.github.io/react-native/docs/modal.html#onrequestclose
      */
     onRequestClose:
-      Platform.isTVOS || Platform.OS === 'android'
+      Platform.isTV || Platform.OS === 'android'
         ? PropTypes.func.isRequired
         : PropTypes.func,
     /**
diff --git a/Libraries/Utilities/BackHandler.ios.js b/Libraries/Utilities/BackHandler.ios.js
index 968b707d690f..969a031ab62a 100644
--- a/Libraries/Utilities/BackHandler.ios.js
+++ b/Libraries/Utilities/BackHandler.ios.js
@@ -53,7 +53,7 @@ function emptyFunction() {}
  */
 let BackHandler;
 
-if (Platform.isTVOS) {
+if (Platform.isTV) {
   const _tvEventHandler = new TVEventHandler();
   const _backPressSubscriptions = new Set();
 
diff --git a/RNTester/js/ARTExample.js b/RNTester/js/ARTExample.js
index 15ae6de031ee..1a0745ec43f2 100644
--- a/RNTester/js/ARTExample.js
+++ b/RNTester/js/ARTExample.js
@@ -16,7 +16,7 @@ var {ART, Platform, View} = ReactNative;
 
 const {Surface, Path, Group, Transform, Shape} = ART;
 
-var scale = Platform.isTVOS ? 4 : 1;
+var scale = Platform.isTV ? 4 : 1;
 
 class ARTExample extends React.Component<{}> {
   render() {
diff --git a/RNTester/js/ListExampleShared.js b/RNTester/js/ListExampleShared.js
index 905985b52b28..62654e78e181 100644
--- a/RNTester/js/ListExampleShared.js
+++ b/RNTester/js/ListExampleShared.js
@@ -237,7 +237,7 @@ function pressItem(context: Object, key: string) {
 }
 
 function renderSmallSwitchOption(context: Object, key: string) {
-  if (Platform.isTVOS) {
+  if (Platform.isTV) {
     return null;
   }
   return (
diff --git a/RNTester/js/ModalExample.js b/RNTester/js/ModalExample.js
index cfb51abe6297..a66d331d03c9 100644
--- a/RNTester/js/ModalExample.js
+++ b/RNTester/js/ModalExample.js
@@ -94,7 +94,7 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
   };
 
   renderSwitch() {
-    if (Platform.isTVOS) {
+    if (Platform.isTV) {
       return null;
     }
     return (
@@ -191,7 +191,7 @@ class ModalExample extends React.Component<{}, $FlowFixMeState> {
     );
   }
   renderPickers() {
-    if (Platform.isTVOS) {
+    if (Platform.isTV) {
       return null;
     }
     return (
diff --git a/RNTester/js/RNTesterExampleList.js b/RNTester/js/RNTesterExampleList.js
index c9ccce1a88a0..325a5bce88a5 100644
--- a/RNTester/js/RNTesterExampleList.js
+++ b/RNTester/js/RNTesterExampleList.js
@@ -80,7 +80,7 @@ class RNTesterExampleList extends React.Component<Props, $FlowFixMeState> {
        * comment and run Flow. */
       this.props.disableSearch ||
       (filterRegex.test(example.module.title) &&
-        (!Platform.isTVOS || example.supportsTVOS));
+        (!Platform.isTV || example.supportsTVOS));
 
     const sections = [
       {
diff --git a/RNTester/js/TVEventHandlerExample.js b/RNTester/js/TVEventHandlerExample.js
index 177614e7cf67..757a27ef9466 100644
--- a/RNTester/js/TVEventHandlerExample.js
+++ b/RNTester/js/TVEventHandlerExample.js
@@ -74,7 +74,7 @@ class TVEventHandlerView extends React.Component<
   }
 
   render() {
-    if (Platform.isTVOS) {
+    if (Platform.isTV) {
       return (
         <View>
           <TouchableOpacity onPress={() => {}}>
diff --git a/RNTester/js/TextExample.ios.js b/RNTester/js/TextExample.ios.js
index 6fdd942d4b84..52274d7c032c 100644
--- a/RNTester/js/TextExample.ios.js
+++ b/RNTester/js/TextExample.ios.js
@@ -324,12 +324,12 @@ exports.examples = [
     render: function() {
       return (
         <View>
-          <Text style={{fontFamily: Platform.isTVOS ? 'Times' : 'Cochin'}}>
+          <Text style={{fontFamily: Platform.isTV ? 'Times' : 'Cochin'}}>
             Cochin
           </Text>
           <Text
             style={{
-              fontFamily: Platform.isTVOS ? 'Times' : 'Cochin',
+              fontFamily: Platform.isTV ? 'Times' : 'Cochin',
               fontWeight: 'bold',
             }}>
             Cochin bold
@@ -338,12 +338,12 @@ exports.examples = [
           <Text style={{fontFamily: 'Helvetica', fontWeight: 'bold'}}>
             Helvetica bold
           </Text>
-          <Text style={{fontFamily: Platform.isTVOS ? 'Courier' : 'Verdana'}}>
+          <Text style={{fontFamily: Platform.isTV ? 'Courier' : 'Verdana'}}>
             Verdana
           </Text>
           <Text
             style={{
-              fontFamily: Platform.isTVOS ? 'Courier' : 'Verdana',
+              fontFamily: Platform.isTV ? 'Courier' : 'Verdana',
               fontWeight: 'bold',
             }}>
             Verdana bold
@@ -817,14 +817,14 @@ exports.examples = [
           <Text style={{fontVariant: ['small-caps']}}>Small Caps{'\n'}</Text>
           <Text
             style={{
-              fontFamily: Platform.isTVOS ? 'Times' : 'Hoefler Text',
+              fontFamily: Platform.isTV ? 'Times' : 'Hoefler Text',
               fontVariant: ['oldstyle-nums'],
             }}>
             Old Style nums 0123456789{'\n'}
           </Text>
           <Text
             style={{
-              fontFamily: Platform.isTVOS ? 'Times' : 'Hoefler Text',
+              fontFamily: Platform.isTV ? 'Times' : 'Hoefler Text',
               fontVariant: ['lining-nums'],
             }}>
             Lining nums 0123456789{'\n'}

From f50ce0850d4c8986b383c6399415bcf98e39d73c Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sun, 10 Jun 2018 14:17:13 -0700
Subject: [PATCH 0761/1109] Passing forwardedRef to Slider

Reviewed By: sahrens

Differential Revision: D8345883

fbshipit-source-id: d2affdba14d38593541e591fe72006c76fca166f
---
 Libraries/Components/Slider/Slider.js | 11 ++++-------
 1 file changed, 4 insertions(+), 7 deletions(-)

diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index aacfb14f34cb..d9efe0170d8d 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -194,10 +194,8 @@ type Props = $ReadOnly<{|
  *
  */
 const Slider = (
-  props: $ReadOnly<{|
-    ...Props,
-    forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
-  |}>,
+  props: Props,
+  forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
 ) => {
   const style = StyleSheet.compose(
     styles.slider,
@@ -230,6 +228,7 @@ const Slider = (
   return (
     <RCTSlider
       {...props}
+      ref={forwardedRef}
       style={style}
       onChange={onChange}
       onSlidingComplete={onSlidingComplete}
@@ -242,9 +241,7 @@ const Slider = (
 };
 
 // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
-const SliderWithRef = React.forwardRef((props: Props, ref) => {
-  return <Slider {...props} forwardedRef={ref} />;
-});
+const SliderWithRef = React.forwardRef(Slider);
 
 SliderWithRef.defaultProps = {
   disabled: false,

From 6b1bb018043aaf9d55aa23ca74120dfeb94a463c Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sun, 10 Jun 2018 15:09:41 -0700
Subject: [PATCH 0762/1109] Enable Flow for bezier

Reviewed By: sahrens

Differential Revision: D8346102

fbshipit-source-id: bb1a2eccb5472bf6f3fe113303ad96cf3f386cab
---
 Libraries/Animated/src/__tests__/bezier-test.js |  4 ++--
 Libraries/Animated/src/bezier.js                | 12 ++++++++----
 2 files changed, 10 insertions(+), 6 deletions(-)

diff --git a/Libraries/Animated/src/__tests__/bezier-test.js b/Libraries/Animated/src/__tests__/bezier-test.js
index 46c7f043b331..e9f00a7d2148 100644
--- a/Libraries/Animated/src/__tests__/bezier-test.js
+++ b/Libraries/Animated/src/__tests__/bezier-test.js
@@ -3,8 +3,8 @@
  * https://github.com/gre/bezier-easing
  *
  * @copyright 2014-2015 Gaetan Renaudeau. MIT License.
- * @noflow
  * @emails oncall+react_native
+ * @flow
  * @format
  */
 
@@ -39,7 +39,7 @@ function allEquals(be1, be2, samples, assertion) {
 function repeat(n) {
   return function(f) {
     for (let i = 0; i < n; ++i) {
-      f(i);
+      f();
     }
   };
 }
diff --git a/Libraries/Animated/src/bezier.js b/Libraries/Animated/src/bezier.js
index 41a83b545f72..15f8e2dc1b68 100644
--- a/Libraries/Animated/src/bezier.js
+++ b/Libraries/Animated/src/bezier.js
@@ -2,9 +2,9 @@
  * BezierEasing - use bezier curve for transition easing function
  * https://github.com/gre/bezier-easing
  *
+ * @flow
  * @format
  * @copyright 2014-2015 Gaëtan Renaudeau. MIT License.
- * @noflow
  */
 
 'use strict';
@@ -71,9 +71,13 @@ function newtonRaphsonIterate(aX, aGuessT, mX1, mX2) {
   return aGuessT;
 }
 
-module.exports = function bezier(mX1, mY1, mX2, mY2) {
+module.exports = function bezier(
+  mX1: number,
+  mY1: number,
+  mX2: number,
+  mY2: number,
+) {
   if (!(0 <= mX1 && mX1 <= 1 && 0 <= mX2 && mX2 <= 1)) {
-    // eslint-disable-line yoda
     throw new Error('bezier x values must be in [0, 1] range');
   }
 
@@ -123,7 +127,7 @@ module.exports = function bezier(mX1, mY1, mX2, mY2) {
     }
   }
 
-  return function BezierEasing(x) {
+  return function BezierEasing(x: number): number {
     if (mX1 === mY1 && mX2 === mY2) {
       return x; // linear
     }

From a51e8b19cc4dc36dee42ac95278b883c06b2e40f Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sun, 10 Jun 2018 15:34:37 -0700
Subject: [PATCH 0763/1109] Don't pass additional args to
 requireNativeComponent in .android.js files

Reviewed By: sahrens

Differential Revision: D8345921

fbshipit-source-id: 187048ad4c1b361f0b99b993052bdcaf47a266db
---
 .../Components/CheckBox/CheckBox.android.js   | 10 ++-------
 .../DrawerLayoutAndroid.android.js            |  5 +----
 .../Picker/PickerAndroid.android.js           | 21 +++----------------
 .../ProgressBarAndroid.android.js             | 11 +---------
 .../Components/TabBarIOS/TabBarItemIOS.ios.js |  2 +-
 .../ToolbarAndroid/ToolbarAndroid.android.js  |  7 +------
 .../ViewPager/ViewPagerAndroid.android.js     |  7 ++-----
 .../Components/WebView/WebView.android.js     | 14 +------------
 Libraries/Components/WebView/WebView.ios.js   | 18 +---------------
 Libraries/Image/Image.android.js              | 19 +++--------------
 .../js/SubviewsClippingTestModule.js          |  3 +--
 11 files changed, 17 insertions(+), 100 deletions(-)

diff --git a/Libraries/Components/CheckBox/CheckBox.android.js b/Libraries/Components/CheckBox/CheckBox.android.js
index 5417a0e811de..0c7f13decd8c 100644
--- a/Libraries/Components/CheckBox/CheckBox.android.js
+++ b/Libraries/Components/CheckBox/CheckBox.android.js
@@ -18,6 +18,8 @@ const ViewPropTypes = require('ViewPropTypes');
 const createReactClass = require('create-react-class');
 const requireNativeComponent = require('requireNativeComponent');
 
+const RCTCheckBox = requireNativeComponent('AndroidCheckBox');
+
 type DefaultProps = {
   value: boolean,
   disabled: boolean,
@@ -155,12 +157,4 @@ let styles = StyleSheet.create({
   },
 });
 
-let RCTCheckBox = requireNativeComponent('AndroidCheckBox', CheckBox, {
-  nativeOnly: {
-    onChange: true,
-    on: true,
-    enabled: true,
-  },
-});
-
 module.exports = CheckBox;
diff --git a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
index 6b983cb2ad27..d4b3fa9f7f63 100644
--- a/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
+++ b/Libraries/Components/DrawerAndroid/DrawerLayoutAndroid.android.js
@@ -321,9 +321,6 @@ const styles = StyleSheet.create({
 });
 
 // The View that contains both the actual drawer and the main view
-const AndroidDrawerLayout = requireNativeComponent(
-  'AndroidDrawerLayout',
-  DrawerLayoutAndroid,
-);
+const AndroidDrawerLayout = requireNativeComponent('AndroidDrawerLayout');
 
 module.exports = DrawerLayoutAndroid;
diff --git a/Libraries/Components/Picker/PickerAndroid.android.js b/Libraries/Components/Picker/PickerAndroid.android.js
index c0ce723e479a..1f80aa3928d0 100644
--- a/Libraries/Components/Picker/PickerAndroid.android.js
+++ b/Libraries/Components/Picker/PickerAndroid.android.js
@@ -21,6 +21,9 @@ const ViewStylePropTypes = require('ViewStylePropTypes');
 const processColor = require('processColor');
 const requireNativeComponent = require('requireNativeComponent');
 
+const DropdownPicker = requireNativeComponent('AndroidDropdownPicker');
+const DialogPicker = requireNativeComponent('AndroidDialogPicker');
+
 const REF_PICKER = 'picker';
 const MODE_DROPDOWN = 'dropdown';
 
@@ -158,22 +161,4 @@ const styles = StyleSheet.create({
   },
 });
 
-const cfg = {
-  nativeOnly: {
-    items: true,
-    selected: true,
-  },
-};
-
-const DropdownPicker = requireNativeComponent(
-  'AndroidDropdownPicker',
-  PickerAndroid,
-  cfg,
-);
-const DialogPicker = requireNativeComponent(
-  'AndroidDialogPicker',
-  PickerAndroid,
-  cfg,
-);
-
 module.exports = PickerAndroid;
diff --git a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
index 9ee432f56bd5..7ea083dd0f19 100644
--- a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
+++ b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
@@ -12,7 +12,6 @@
 const ColorPropType = require('ColorPropType');
 const PropTypes = require('prop-types');
 const React = require('React');
-const ReactNative = require('ReactNative');
 const ViewPropTypes = require('ViewPropTypes');
 
 const requireNativeComponent = require('requireNativeComponent');
@@ -115,15 +114,7 @@ class ProgressBarAndroid extends React.Component {
   }
 }
 
-const AndroidProgressBar = requireNativeComponent(
-  'AndroidProgressBar',
-  ProgressBarAndroid,
-  {
-    nativeOnly: {
-      animating: true,
-    },
-  },
-);
+const AndroidProgressBar = requireNativeComponent('AndroidProgressBar');
 
 module.exports = React.forwardRef((props, ref) => (
   <ProgressBarAndroid {...props} forwardedRef={ref} />
diff --git a/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js b/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
index 44fb44da4486..b8825977a8ca 100644
--- a/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
+++ b/Libraries/Components/TabBarIOS/TabBarItemIOS.ios.js
@@ -143,6 +143,6 @@ const styles = StyleSheet.create({
   },
 });
 
-const RCTTabBarItem = requireNativeComponent('RCTTabBarItem', TabBarItemIOS);
+const RCTTabBarItem = requireNativeComponent('RCTTabBarItem');
 
 module.exports = TabBarItemIOS;
diff --git a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
index 5fc04a425301..44bcfc03d804 100644
--- a/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
+++ b/Libraries/Components/ToolbarAndroid/ToolbarAndroid.android.js
@@ -13,7 +13,6 @@ const Image = require('Image');
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const React = require('React');
 const PropTypes = require('prop-types');
-const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const UIManager = require('UIManager');
 const ViewPropTypes = require('ViewPropTypes');
 const ColorPropType = require('ColorPropType');
@@ -207,10 +206,6 @@ const ToolbarAndroid = createReactClass({
   },
 });
 
-const NativeToolbar = requireNativeComponent('ToolbarAndroid', ToolbarAndroid, {
-  nativeOnly: {
-    nativeActions: true,
-  },
-});
+const NativeToolbar = requireNativeComponent('ToolbarAndroid');
 
 module.exports = ToolbarAndroid;
diff --git a/Libraries/Components/ViewPager/ViewPagerAndroid.android.js b/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
index 4b75cfb42d52..2ccdd31b5636 100644
--- a/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
+++ b/Libraries/Components/ViewPager/ViewPagerAndroid.android.js
@@ -19,6 +19,8 @@ const ViewPropTypes = require('ViewPropTypes');
 const dismissKeyboard = require('dismissKeyboard');
 const requireNativeComponent = require('requireNativeComponent');
 
+const NativeAndroidViewPager = requireNativeComponent('AndroidViewPager');
+
 const VIEWPAGER_REF = 'viewPager';
 
 type Event = Object;
@@ -255,9 +257,4 @@ class ViewPagerAndroid extends React.Component<{
   }
 }
 
-const NativeAndroidViewPager = requireNativeComponent(
-  'AndroidViewPager',
-  ViewPagerAndroid,
-);
-
 module.exports = ViewPagerAndroid;
diff --git a/Libraries/Components/WebView/WebView.android.js b/Libraries/Components/WebView/WebView.android.js
index 0d1c7b0c90d9..4d4b65fb11fd 100644
--- a/Libraries/Components/WebView/WebView.android.js
+++ b/Libraries/Components/WebView/WebView.android.js
@@ -43,14 +43,6 @@ const defaultRenderLoading = () => (
  * Renders a native WebView.
  */
 class WebView extends React.Component {
-  static get extraNativeComponentConfig() {
-    return {
-      nativeOnly: {
-        messagingEnabled: PropTypes.bool,
-      },
-    };
-  }
-
   static propTypes = {
     ...ViewPropTypes,
     renderError: PropTypes.func,
@@ -464,11 +456,7 @@ class WebView extends React.Component {
   };
 }
 
-const RCTWebView = requireNativeComponent(
-  'RCTWebView',
-  WebView,
-  WebView.extraNativeComponentConfig,
-);
+const RCTWebView = requireNativeComponent('RCTWebView');
 
 const styles = StyleSheet.create({
   container: {
diff --git a/Libraries/Components/WebView/WebView.ios.js b/Libraries/Components/WebView/WebView.ios.js
index 8d78103d7013..ca91bc3b877e 100644
--- a/Libraries/Components/WebView/WebView.ios.js
+++ b/Libraries/Components/WebView/WebView.ios.js
@@ -109,18 +109,6 @@ const defaultRenderError = (errorDomain, errorCode, errorDesc) => (
 class WebView extends React.Component {
   static JSNavigationScheme = JSNavigationScheme;
   static NavigationType = NavigationType;
-  static get extraNativeComponentConfig() {
-    return {
-      nativeOnly: {
-        onLoadingStart: true,
-        onLoadingError: true,
-        onLoadingFinish: true,
-        onMessage: true,
-        messagingEnabled: PropTypes.bool,
-      },
-    };
-  }
-
   static propTypes = {
     ...ViewPropTypes,
 
@@ -651,11 +639,7 @@ class WebView extends React.Component {
   };
 }
 
-const RCTWebView = requireNativeComponent(
-  'RCTWebView',
-  WebView,
-  WebView.extraNativeComponentConfig,
-);
+const RCTWebView = requireNativeComponent('RCTWebView');
 
 const styles = StyleSheet.create({
   container: {
diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index cf87d4bc782e..350bba68ea89 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -29,6 +29,9 @@ const resolveAssetSource = require('resolveAssetSource');
 
 const {ImageLoader} = NativeModules;
 
+const RKImage = requireNativeComponent('RCTImageView');
+const RCTTextInlineImage = requireNativeComponent('RCTTextInlineImage');
+
 let _requestId = 1;
 function generateRequestId() {
   return _requestId++;
@@ -278,20 +281,4 @@ const styles = StyleSheet.create({
   },
 });
 
-const cfg = {
-  nativeOnly: {
-    src: true,
-    headers: true,
-    defaultSrc: true,
-    loadingIndicatorSrc: true,
-    shouldNotifyLoadEvents: true,
-  },
-};
-const RKImage = requireNativeComponent('RCTImageView', Image, cfg);
-const RCTTextInlineImage = requireNativeComponent(
-  'RCTTextInlineImage',
-  Image,
-  cfg,
-);
-
 module.exports = Image;
diff --git a/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js b/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
index 9f19e0e39034..312dcb2c5d63 100644
--- a/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
+++ b/ReactAndroid/src/androidTest/js/SubviewsClippingTestModule.js
@@ -11,14 +11,13 @@
 
 var BatchedBridge = require('BatchedBridge');
 var React = require('React');
-var ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 var ScrollView = require('ScrollView');
 var StyleSheet = require('StyleSheet');
 var View = require('View');
 
 var requireNativeComponent = require('requireNativeComponent');
 
-var ClippableView = requireNativeComponent('ClippableView', null);
+var ClippableView = requireNativeComponent('ClippableView');
 
 class ClippingSample1 extends React.Component {
   render() {

From e315ec9891eb0bcb51afb0e797dbd49aa8f9ac71 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Sun, 10 Jun 2018 16:53:22 -0700
Subject: [PATCH 0764/1109] Fix iOS e2e tests: bump react-native-babel-preset
 to ^5 (#19625)

Summary:
We opt in to version ^5 of the React Native Babel Preset, as required after the bump to Babel 7. This fixes the Objective-C end-to-end test failure in master. (Fixes #19538)

See https://github.com/facebook/react-native/commit/34bd776af2f2529009188fced91083203a48fd40#commitcomment-29024085 for prior discussion.

There have already been several changes made to the repo during the transition to Babel 7. This PR brings all tests back to green and allows us to move forward with the 0.56 branch cut.

We also bump our tests to use Xcode 9.4.0 and iOS 11.4, the latest stable versions of both.

Once the 0.56 branch makes it to stable, we can change `react-native-babel-preset@latest` on npm to point to `react-native-babel-preset@5.0.1` (or newer), and undo the change made to `init.js` we made as part of this diff.

Wait for Circle CI to run: https://circleci.com/workflow-run/e39a66d7-bf8a-4b31-a22f-eef30a2c53bc

[GENERAL] [BREAKING] [Babel] - Bump React Native Babel Preset version used by RN CLI to Babel v7 compliant release
Closes https://github.com/facebook/react-native/pull/19625

Reviewed By: TheSavior

Differential Revision: D8343861

Pulled By: hramos

fbshipit-source-id: 42644d5b0bfb40a8bc592ae3461c5008deef8232
---
 .circleci/config.yml                          | 50 ++++++++++++-------
 .../run-android-ci-instrumentation-tests.js   |  8 +--
 local-cli/init/init.js                        |  2 +-
 scripts/.tests.env                            |  2 +-
 scripts/objc-test-ios.sh                      |  7 +--
 scripts/objc-test-tvos.sh                     |  7 +--
 scripts/objc-test.sh                          |  2 +-
 scripts/run-ci-e2e-tests.js                   | 50 +++++++++++++------
 8 files changed, 84 insertions(+), 44 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index f77c7392272b..185be9135eb4 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -198,7 +198,7 @@ aliases:
   # eslint sometimes runs into trouble generating the reports
   - &run-lint-checks
     name: Lint code
-    command: scripts/circleci/exec_swallow_error.sh yarn lint --format junit -o ~/react-native/reports/junit/js-lint-results.xml
+    command: scripts/circleci/exec_swallow_error.sh yarn lint --format junit -o ~/react-native/reports/junit/eslint/results.xml
     when: always
 
   - &run-flow-checks
@@ -274,6 +274,14 @@ aliases:
       mkdir -p ~/react-native/reports/junit/
       mkdir -p ~/react-native/reports/outputs/
 
+  - &boot-simulator-iphone
+    name: Boot iPhone Simulator
+    command: xcrun simctl boot "iPhone 5s" || true
+
+  - &boot-simulator-appletv
+    name: Boot Apple TV Simulator
+    command: xcrun simctl boot "Apple TV" || true
+
   - &run-objc-ios-tests
     name: iOS Test Suite
     command: ./scripts/objc-test-ios.sh test
@@ -282,9 +290,13 @@ aliases:
     name: tvOS Test Suite
     command: ./scripts/objc-test-tvos.sh test
 
+  - &run-e2e-tests
+    name: End-to-End Test Suite
+    command: node ./scripts/run-ci-e2e-tests.js --ios --tvos --js --retries 3;
+
   - &run-objc-ios-e2e-tests
     name: iOS End-to-End Test Suite
-    command: node ./scripts/run-ci-e2e-tests.js --ios --js --retries 3;
+    command: node ./scripts/run-ci-e2e-tests.js --ios --retries 3;
 
   - &run-objc-tvos-e2e-tests
     name: tvOS End-to-End Test Suite
@@ -374,8 +386,7 @@ jobs:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "iPhone 5s (11.4)" || true
-      # See https://github.com/Homebrew/homebrew-core/issues/26358.
+      - run: *boot-simulator-iphone
       - run: brew install watchman
       - run: *run-objc-ios-tests
 
@@ -389,8 +400,7 @@ jobs:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "Apple TV (11.4)" || true
-      # See https://github.com/Homebrew/homebrew-core/issues/26358.
+      - run: *boot-simulator-appletv
       - run: brew install watchman
       - run: *run-objc-tvos-tests
 
@@ -398,13 +408,27 @@ jobs:
           path: ~/react-native/reports/junit
 
   # Runs end to end tests
-  test_ios_e2e:
+  test_end_to_end:
     <<: *macos_defaults
     steps:
       - attach_workspace:
           at: ~/react-native
 
-      - run: xcrun instruments -w "iPhone 5s (11.4)" || true
+      - run: *boot-simulator-iphone
+
+      - run:
+          name: Configure Environment Variables
+          command: |
+            echo 'export PATH=/usr/local/opt/node@8/bin:$PATH' >> $BASH_ENV
+            source $BASH_ENV
+
+      - run:
+          name: Install Node 8
+          command: |
+            brew install node@8
+            brew link node@8
+            node -v
+
       - run: *run-objc-ios-e2e-tests
 
       - store_test_results:
@@ -623,7 +647,7 @@ workflows:
             - checkout_code
 
       # End-to-end tests
-      - test_ios_e2e:
+      - test_end_to_end:
           filters: *filter-ignore-gh-pages
           requires:
             - checkout_code
@@ -670,11 +694,3 @@ workflows:
   #         filters: *filter-ignore-gh-pages
   #         requires:
   #           - checkout_code
-
-experimental:
-  notify:
-    webhooks:
-      - url: https://code.facebook.com/circle/webhook/
-    branches:
-      only:
-        - master
diff --git a/ContainerShip/scripts/run-android-ci-instrumentation-tests.js b/ContainerShip/scripts/run-android-ci-instrumentation-tests.js
index 706159c4902b..c16c7990ed31 100644
--- a/ContainerShip/scripts/run-android-ci-instrumentation-tests.js
+++ b/ContainerShip/scripts/run-android-ci-instrumentation-tests.js
@@ -28,7 +28,7 @@ const path = require('path');
 const colors = {
     GREEN: '\x1b[32m',
     RED: '\x1b[31m',
-    RESET: '\x1b[0m'
+    RESET: '\x1b[0m',
 };
 
 const test_opts = {
@@ -41,7 +41,7 @@ const test_opts = {
     TEST_TIMEOUT: parseInt(argv['test-timeout'] || 1000 * 60 * 10),
 
     OFFSET: argv.offset,
-    COUNT: argv.count
+    COUNT: argv.count,
 };
 
 let max_test_class_length = Number.NEGATIVE_INFINITY;
@@ -88,7 +88,7 @@ return async.mapSeries(testClasses, (clazz, callback) => {
 
     return async.retry(test_opts.RETRIES, (retryCb) => {
         const test_process = child_process.spawn('./ContainerShip/scripts/run-instrumentation-tests-via-adb-shell.sh', [test_opts.PACKAGE, clazz], {
-            stdio: 'inherit'
+            stdio: 'inherit',
         });
 
         const timeout = setTimeout(() => {
@@ -112,7 +112,7 @@ return async.mapSeries(testClasses, (clazz, callback) => {
     }, (err) => {
         return callback(null, {
             name: clazz,
-            status: err ? 'failure' : 'success'
+            status: err ? 'failure' : 'success',
         });
     });
 }, (err, results) => {
diff --git a/local-cli/init/init.js b/local-cli/init/init.js
index 17273f9881d8..d7497a4a8284 100644
--- a/local-cli/init/init.js
+++ b/local-cli/init/init.js
@@ -99,7 +99,7 @@ function generateProject(destinationRoot, newProjectName, options) {
     });
   }
   if (!options['skip-jest']) {
-    const jestDeps = `jest babel-jest babel-preset-react-native react-test-renderer@${reactVersion}`;
+    const jestDeps = `jest babel-jest babel-preset-react-native@^5 react-test-renderer@${reactVersion}`;
     if (yarnVersion) {
       console.log('Adding Jest...');
       execSync(`yarn add ${jestDeps} --dev --exact`, {stdio: 'inherit'});
diff --git a/scripts/.tests.env b/scripts/.tests.env
index a03f487abe4d..285578295970 100644
--- a/scripts/.tests.env
+++ b/scripts/.tests.env
@@ -17,7 +17,7 @@ export AVD_NAME="testAVD"
 export AVD_ABI=x86
 
 ## IOS ##
-export IOS_TARGET_OS="11.3"
+export IOS_TARGET_OS="11.4"
 export IOS_DEVICE="iPhone 5s"
 
 export SCHEME="RNTester"
diff --git a/scripts/objc-test-ios.sh b/scripts/objc-test-ios.sh
index eaa4f7a86865..d466f877540a 100755
--- a/scripts/objc-test-ios.sh
+++ b/scripts/objc-test-ios.sh
@@ -13,9 +13,10 @@ ROOT=$(dirname "$SCRIPTS")
 
 cd "$ROOT"
 
-SCHEME="RNTester"
-SDK="iphonesimulator"
-DESTINATION="platform=iOS Simulator,name=iPhone 5s,OS=10.3.1"
+export TEST_NAME="iOS"
+export SCHEME="RNTester"
+export SDK="iphonesimulator"
+export DESTINATION="platform=iOS Simulator,name=iPhone 5s,OS=11.4"
 
 # If there's a "test" argument, pass it to the test script.
 . ./scripts/objc-test.sh $1
diff --git a/scripts/objc-test-tvos.sh b/scripts/objc-test-tvos.sh
index 9d17f7defeb6..98016598df0f 100755
--- a/scripts/objc-test-tvos.sh
+++ b/scripts/objc-test-tvos.sh
@@ -13,9 +13,10 @@ ROOT=$(dirname "$SCRIPTS")
 
 cd "$ROOT"
 
-SCHEME="RNTester-tvOS"
-SDK="appletvsimulator"
-DESTINATION="platform=tvOS Simulator,name=Apple TV 1080p,OS=10.2"
+export TEST_NAME="tvOS"
+export SCHEME="RNTester-tvOS"
+export SDK="appletvsimulator"
+export DESTINATION="platform=tvOS Simulator,name=Apple TV,OS=11.4"
 
 # If there's a "test" argument, pass it to the test script.
 . ./scripts/objc-test.sh $1
diff --git a/scripts/objc-test.sh b/scripts/objc-test.sh
index f2c0459989da..c2a9a94d182e 100755
--- a/scripts/objc-test.sh
+++ b/scripts/objc-test.sh
@@ -79,7 +79,7 @@ xcodebuild \
   -sdk $SDK \
   -destination "$DESTINATION" \
   build test \
-  | xcpretty --report junit --output ~/react-native/reports/junit/objc-xcodebuild-results.xml
+  | xcpretty --report junit --output "$HOME/react-native/reports/junit/$TEST_NAME/results.xml"
 
 else
 
diff --git a/scripts/run-ci-e2e-tests.js b/scripts/run-ci-e2e-tests.js
index f3096c083a28..ba436a27ad46 100644
--- a/scripts/run-ci-e2e-tests.js
+++ b/scripts/run-ci-e2e-tests.js
@@ -104,8 +104,8 @@ try {
   cd('EndToEndTest');
 
   if (argv.android) {
-    echo('Running an Android e2e test');
-    echo('Installing e2e framework');
+    echo('Running an Android end-to-end test');
+    echo('Installing end-to-end framework');
     if (
       tryExecNTimes(
         () =>
@@ -155,14 +155,14 @@ try {
     SERVER_PID = packagerProcess.pid;
     // wait a bit to allow packager to startup
     exec('sleep 15s');
-    echo('Executing android e2e test');
+    echo('Executing android end-to-end test');
     if (
       tryExecNTimes(() => {
         exec('sleep 10s');
         return exec('node node_modules/.bin/_mocha android-e2e-test.js').code;
       }, numberOfRetries)
     ) {
-      echo('Failed to run Android e2e tests');
+      echo('Failed to run Android end-to-end tests');
       echo('Most likely the code is broken');
       exitCode = 1;
       throw Error(exitCode);
@@ -171,7 +171,7 @@ try {
 
   if (argv.ios || argv.tvos) {
     var iosTestType = argv.tvos ? 'tvOS' : 'iOS';
-    echo('Running the ' + iosTestType + 'app');
+    echo('Running the ' + iosTestType + ' app');
     cd('ios');
     // Make sure we installed local version of react-native
     if (!test('-e', path.join('EndToEndTest', path.basename(MARKER_IOS)))) {
@@ -193,22 +193,44 @@ try {
       'response=$(curl --write-out %{http_code} --silent --output /dev/null localhost:8081/index.bundle?platform=ios&dev=true)',
     );
     echo(`Starting packager server, ${SERVER_PID}`);
-    echo('Executing ' + iosTestType + ' e2e test');
+    echo('Executing ' + iosTestType + ' end-to-end test');
     if (
       tryExecNTimes(() => {
         exec('sleep 10s');
+        let destination = 'platform=iOS Simulator,name=iPhone 5s,OS=11.4';
+        let sdk = 'iphonesimulator';
+        let scheme = 'EndToEndTest';
+
         if (argv.tvos) {
-          return exec(
-            'xcodebuild -destination "platform=tvOS Simulator,name=Apple TV 1080p,OS=10.0" -scheme EndToEndTest-tvOS -sdk appletvsimulator test | xcpretty && exit ${PIPESTATUS[0]}',
-          ).code;
-        } else {
-          return exec(
-            'xcodebuild -destination "platform=iOS Simulator,name=iPhone 5s,OS=10.3.1" -scheme EndToEndTest -sdk iphonesimulator test | xcpretty && exit ${PIPESTATUS[0]}',
-          ).code;
+          destination = 'platform=tvOS Simulator,name=Apple TV,OS=11.4';
+          sdk = 'appletvsimulator';
+          scheme = 'EndToEndTest-tvOS';
         }
+
+        return exec(
+          [
+            'xcodebuild',
+            '-destination',
+            `"${destination}"`,
+            '-scheme',
+            `"${scheme}"`,
+            '-sdk',
+            sdk,
+            'test',
+          ].join(' ') +
+            ' | ' +
+            [
+              'xcpretty',
+              '--report',
+              'junit',
+              '--output',
+              `"~/react-native/reports/junit/${iosTestType}-e2e/results.xml"`,
+            ].join(' ') +
+            ' && exit ${PIPESTATUS[0]}',
+        ).code;
       }, numberOfRetries)
     ) {
-      echo('Failed to run ' + iosTestType + ' e2e tests');
+      echo('Failed to run ' + iosTestType + ' end-to-end tests');
       echo('Most likely the code is broken');
       exitCode = 1;
       throw Error(exitCode);

From 3bed272a620ac806a6142327013265ea8138641a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Ma=C3=ABl=20Nison?= <mael@fb.com>
Date: Sun, 10 Jun 2018 17:43:36 -0700
Subject: [PATCH 0765/1109] Upgrade to Flow v0.74.0

Reviewed By: panagosg7

Differential Revision: D8322344

fbshipit-source-id: 1208528009785f7f797201777287af525d0a9ca1
---
 .flowconfig                                | 2 +-
 local-cli/templates/HelloWorld/_flowconfig | 2 +-
 package.json                               | 2 +-
 3 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index 10c13ea400f5..32624ea479b9 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -74,4 +74,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.73.0
+^0.74.0
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 49487641bc41..2f3267d3164c 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -51,4 +51,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.73.0
+^0.74.0
diff --git a/package.json b/package.json
index db192e67092c..16554be62ee1 100644
--- a/package.json
+++ b/package.json
@@ -212,7 +212,7 @@
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.8.2",
     "eslint-plugin-react-native": "^3.2.1",
-    "flow-bin": "^0.73.0",
+    "flow-bin": "^0.74.0",
     "jest": "23.1.0",
     "jest-junit": "4.0.0",
     "prettier": "1.13.4",

From 4aeefa54844b87a0a2aafa2726447d139d1ac89f Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Sun, 10 Jun 2018 22:26:00 -0700
Subject: [PATCH 0766/1109] Open source Flow definition for Jest

Reviewed By: sahrens

Differential Revision: D8347198

fbshipit-source-id: 0b6194bfd14bad09db7dcd462f0bf342c9c6fe44
---
 flow/jest.js | 179 +++++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 179 insertions(+)
 create mode 100644 flow/jest.js

diff --git a/flow/jest.js b/flow/jest.js
new file mode 100644
index 000000000000..7f6b79573255
--- /dev/null
+++ b/flow/jest.js
@@ -0,0 +1,179 @@
+/**
+ * Copyright (c) 2004-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * Modified from https://raw.githubusercontent.com/flowtype/flow-typed/e3b0f3034929e0f0fb85c790450a201b380ac2fd/definitions/npm/jest_v17.x.x/flow_v0.33.x-/jest_v17.x.x.js
+ * Duplicated from www/flow/shared/jest.js
+ * @flow
+ * @format
+ */
+
+'use strict';
+
+type JestMockFn = {
+  (...args: Array<any>): any,
+  mock: {
+    calls: Array<Array<any>>,
+    instances: mixed,
+  },
+  mockClear(): Function,
+  mockReset(): Function,
+  mockImplementation(fn: Function): JestMockFn,
+  mockImplementationOnce(fn: Function): JestMockFn,
+  mockReturnThis(): void,
+  mockReturnValue(value: any): JestMockFn,
+  mockReturnValueOnce(value: any): JestMockFn,
+};
+
+type JestAsymmetricEqualityType = {
+  asymmetricMatch(value: mixed): boolean,
+};
+
+type JestCallsType = {
+  allArgs(): mixed,
+  all(): mixed,
+  any(): boolean,
+  count(): number,
+  first(): mixed,
+  mostRecent(): mixed,
+  reset(): void,
+};
+
+type JestClockType = {
+  install(): void,
+  mockDate(date: Date): void,
+  tick(): void,
+  uninstall(): void,
+};
+
+type JestMatcherResult = {
+  message?: string | (() => string),
+  pass: boolean,
+};
+
+type JestMatcher = (actual: any, expected: any) => JestMatcherResult;
+
+type JestPromiseType = {
+  /**
+   * Use rejects to unwrap the reason of a rejected promise so any other
+   * matcher can be chained. If the promise is fulfilled the assertion fails.
+   */
+  rejects: JestExpectType,
+  /**
+   * Use resolves to unwrap the value of a fulfilled promise so any other
+   * matcher can be chained. If the promise is rejected the assertion fails.
+   */
+  resolves: JestExpectType,
+};
+
+type JestExpectType = {
+  not: JestExpectType,
+  lastCalledWith(...args: Array<any>): void,
+  toBe(value: any): void,
+  toBeCalled(): void,
+  toBeCalledWith(...args: Array<any>): void,
+  toBeCloseTo(num: number, delta: any): void,
+  toBeDefined(): void,
+  toBeFalsy(): void,
+  toBeGreaterThan(number: number): void,
+  toBeGreaterThanOrEqual(number: number): void,
+  toBeLessThan(number: number): void,
+  toBeLessThanOrEqual(number: number): void,
+  toBeInstanceOf(cls: Class<*>): void,
+  toBeNull(): void,
+  toBeTruthy(): void,
+  toBeUndefined(): void,
+  toContain(item: any): void,
+  toContainEqual(item: any): void,
+  toEqual(value: any): void,
+  toHaveBeenCalled(): void,
+  toHaveBeenCalledTimes(number: number): void,
+  toHaveBeenCalledWith(...args: Array<any>): void,
+  toHaveProperty(path: string, value?: any): void,
+  toMatch(regexp: RegExp): void,
+  toMatchObject(object: Object): void,
+  toMatchSnapshot(): void,
+  toThrow(message?: string | Error | Class<Error>): void,
+  toThrowError(message?: string | Error | Class<Error> | RegExp): void,
+  toThrowErrorMatchingSnapshot(): void,
+};
+
+type JestSpyType = {
+  calls: JestCallsType,
+};
+
+declare function afterEach(fn: Function): void;
+declare function beforeEach(fn: Function): void;
+declare function afterAll(fn: Function): void;
+declare function beforeAll(fn: Function): void;
+declare function describe(name: string, fn: Function): void;
+declare var it: {
+  (name: string, fn: Function): ?Promise<void>,
+  only(name: string, fn: Function): ?Promise<void>,
+  skip(name: string, fn: Function): ?Promise<void>,
+};
+declare function fit(name: string, fn: Function): ?Promise<void>;
+declare function pit(name: string, fn: () => Promise<any>): Promise<void>;
+declare var test: typeof it;
+declare var xdescribe: typeof describe;
+declare var fdescribe: typeof describe;
+declare var xit: typeof it;
+declare var xtest: typeof it;
+
+declare var expect: {
+  (value: any): JestExpectType & JestPromiseType,
+  any: any,
+  extend(matchers: {[name: string]: JestMatcher}): void,
+  objectContaining(any): void,
+};
+declare function fail(message?: string): void;
+
+// TODO handle return type
+// http://jasmine.github.io/2.4/introduction.html#section-Spies
+declare function spyOn(value: mixed, method: string): Object;
+
+type Jest = {
+  autoMockOff(): Jest,
+  autoMockOn(): Jest,
+  resetAllMocks(): Jest,
+  clearAllTimers(): void,
+  currentTestPath(): void,
+  disableAutomock(): Jest,
+  doMock(moduleName: string, moduleFactory?: any): void,
+  dontMock(moduleName: string): Jest,
+  enableAutomock(): Jest,
+  fn(implementation?: Function): JestMockFn,
+  genMockFromModule(moduleName: string): any,
+  isMockFunction(fn: Function): boolean,
+  mock(
+    moduleName: string,
+    moduleFactory?: any,
+    options?: {virtual?: boolean},
+  ): Jest,
+  resetModuleRegistry(): Jest, // undocumented alias for resetModuleRegistry
+  resetModules(): Jest,
+  restoreAllMocks(): Jest,
+  runAllTicks(): Jest,
+  runAllTimers(): Jest,
+  runTimersToTime(msToRun: number): Jest,
+  runOnlyPendingTimers(): Jest,
+  setMock(moduleName: string, moduleExports: any): Jest,
+  unmock(moduleName: string): Jest,
+  useFakeTimers(): Jest,
+  useRealTimers(): Jest,
+};
+
+declare var jest: Jest;
+
+declare var jasmine: {
+  DEFAULT_TIMEOUT_INTERVAL: number,
+  any(value: mixed): JestAsymmetricEqualityType,
+  anything(): void,
+  arrayContaining(value: Array<mixed>): void,
+  clock(): JestClockType,
+  createSpy(name: string): JestSpyType,
+  objectContaining(value: Object): void,
+  stringMatching(value: string): void,
+};

From c3c5c3cbce24a31f73ae6339e377ee76ca6401ad Mon Sep 17 00:00:00 2001
From: Vince Mi <vinc3m1@gmail.com>
Date: Mon, 11 Jun 2018 04:07:38 -0700
Subject: [PATCH 0767/1109] Add back deprecated getParent methods for
 non-breaking API change (#775)

Summary:
I'm not totally sure what I'm doing so if this needs changes let me know.
Closes https://github.com/facebook/yoga/pull/775

Reviewed By: emilsjolander

Differential Revision: D8331892

Pulled By: passy

fbshipit-source-id: eb1023e666322d2472e4081fd4a4e72a7b43d049
---
 ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java | 5 ++---
 ReactCommon/yoga/yoga/YGNode.cpp                           | 4 ++++
 ReactCommon/yoga/yoga/YGNode.h                             | 2 ++
 ReactCommon/yoga/yoga/Yoga.cpp                             | 4 ++++
 ReactCommon/yoga/yoga/Yoga.h                               | 1 +
 5 files changed, 13 insertions(+), 3 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index fdb5b4be5017..90caf8f81e01 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -234,15 +234,14 @@ public YogaNode removeChildAt(int i) {
    * {@link YogaNode} is shared between two or more YogaTrees.
    */
   @Nullable
-  public
-  YogaNode getOwner() {
+  public YogaNode getOwner() {
     return mOwner;
   }
 
   /** @deprecated Use #getOwner() instead. This will be removed in the next version. */
   @Deprecated
   @Nullable
-  YogaNode getParent() {
+  public YogaNode getParent() {
     return getOwner();
   }
 
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 64a47d356a37..16f9e4d0092e 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -53,6 +53,10 @@ YGNodeRef YGNode::getOwner() const {
   return owner_;
 }
 
+YGNodeRef YGNode::getParent() const {
+  return getOwner();
+}
+
 YGVector YGNode::getChildren() const {
   return children_;
 }
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index 96541a575eeb..e3562bb60529 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -78,6 +78,8 @@ struct YGNode {
   // to one YogaTree or nullptr when the YGNode is shared between two or more
   // YogaTrees.
   YGNodeRef getOwner() const;
+  // Deprecated, use getOwner() instead.
+  YGNodeRef getParent() const;
   YGVector getChildren() const;
   uint32_t getChildrenCount() const;
   YGNodeRef getChild(uint32_t index) const;
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index a927ef556c47..c6a8ffd2ea1e 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -535,6 +535,10 @@ YGNodeRef YGNodeGetOwner(const YGNodeRef node) {
   return node->getOwner();
 }
 
+YGNodeRef YGNodeGetParent(const YGNodeRef node) {
+  return node->getOwner();
+}
+
 void YGNodeMarkDirty(const YGNodeRef node) {
   YGAssertWithNode(
       node,
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index 25eb0eb6f5a8..a9fc89d7df4d 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -92,6 +92,7 @@ WIN_EXPORT void YGNodeRemoveChild(const YGNodeRef node, const YGNodeRef child);
 WIN_EXPORT void YGNodeRemoveAllChildren(const YGNodeRef node);
 WIN_EXPORT YGNodeRef YGNodeGetChild(const YGNodeRef node, const uint32_t index);
 WIN_EXPORT YGNodeRef YGNodeGetOwner(const YGNodeRef node);
+WIN_EXPORT YGNodeRef YGNodeGetParent(const YGNodeRef node);
 WIN_EXPORT uint32_t YGNodeGetChildCount(const YGNodeRef node);
 WIN_EXPORT void YGNodeSetChildren(
     YGNodeRef const owner,

From baa61ddc9c088c70456fd4c4561a43b02bdfc428 Mon Sep 17 00:00:00 2001
From: Jay Phelps <hello@jayphelps.com>
Date: Mon, 11 Jun 2018 15:11:01 -0700
Subject: [PATCH 0768/1109] Trigger onFocus/onBlur instead of
 onPressIn/onPressOut (eventually, but for now just deprecate) (#18470)

Summary:
Currently on iOS and Android focus/blur events trigger onPressIn/onPressOut. Based on discussions with people are several companies who use react-native we're proposing instead triggering new events onFocus/onBlur. Initial discussion on Slack with some from the core team on Slack seemed positive.

Couple reasons:

* The current API behavior overloads onPressIn/onPressOut. That means on platforms like react-native-web, if focus/blur support was added (as we're hoping for), even though onPressIn/onPressOut would be useful as the name describes, you wouldn't be able to distinguish between it and browser element focus/blur events.
* The names aren't as self-documenting/intuitive as onFocus/onBlur, especially for react-dom users.

There aren't any current tests around this, but I intend to add them if we solidify the API.

There's also an option question on the transition--do we deprecate the existing API with a warning? This PR just deprecates them, though it will on any TV platform when something becomes focused regardless of whether they use the API or not. This isn't ideal. It's not clear if there are alternatives or if just right away breaking the API for TV users is the correct solution, if we can get consensus between the few parties who are using it.

***

I'm interested to hear counter points or prior discussions.

Cc/ matthargett dlowder-salesforce rozele
Closes https://github.com/facebook/react-native/pull/18470

Differential Revision: D8368109

Pulled By: hramos

fbshipit-source-id: 22587b82e091645e748b6c2d721fdff06d54837f
---
 Libraries/Components/Touchable/Touchable.js   | 31 +++++++++++++++++--
 .../Components/Touchable/TouchableBounce.js   |  1 -
 .../Touchable/TouchableWithoutFeedback.js     | 12 +++++++
 3 files changed, 41 insertions(+), 3 deletions(-)

diff --git a/Libraries/Components/Touchable/Touchable.js b/Libraries/Components/Touchable/Touchable.js
index ce449d6d99f8..1af0887d46cd 100644
--- a/Libraries/Components/Touchable/Touchable.js
+++ b/Libraries/Components/Touchable/Touchable.js
@@ -325,11 +325,17 @@ const TouchableMixin = {
       evt.dispatchConfig = {};
       if (myTag === evt.tag) {
         if (evt.eventType === 'focus') {
-          cmp.touchableHandleActivePressIn &&
+          if (cmp.touchableHandleActivePressIn) {
+            console.warn('Using `touchableHandleActivePressIn` or `onPressIn` to listen for focus events is deprecated. Use `touchableHandleFocus` or `onFocus` instead.');
             cmp.touchableHandleActivePressIn(evt);
+          }
+          cmp.touchableHandleFocus(evt);
         } else if (evt.eventType === 'blur') {
-          cmp.touchableHandleActivePressOut &&
+          if (cmp.touchableHandleActivePressOut) {
+            console.warn('Using `touchableHandleActivePressOut` or `onPressOut` to listen for blur events is deprecated. Use `touchableHandleBlur` or `onBlur` instead.');
             cmp.touchableHandleActivePressOut(evt);
+          }
+          cmp.touchableHandleBlur(evt);
         } else if (evt.eventType === 'select') {
           cmp.touchableHandlePress &&
             !cmp.props.disabled &&
@@ -528,6 +534,27 @@ const TouchableMixin = {
     }
   },
 
+  /**
+   * Invoked when the item receives focus. Mixers might override this to
+   * visually distinguish the `VisualRect` so that the user knows that it
+   * currently has the focus. Most platforms only support a single element being
+   * focused at a time, in which case there may have been a previously focused
+   * element that was blurred just prior to this.
+   */
+  touchableHandleFocus: function (e: Event) {
+    this.props.onFocus && this.props.onFocus(e);
+  },
+
+  /**
+   * Invoked when the item loses focus. Mixers might override this to
+   * visually distinguish the `VisualRect` so that the user knows that it
+   * no longer has focus. Most platforms only support a single element being
+   * focused at a time, in which case the focus may have moved to another.
+   */
+  touchableHandleBlur: function (e: Event) {
+    this.props.onBlur && this.props.onBlur(e);
+  },
+
   // ==== Abstract Application Callbacks ====
 
   /**
diff --git a/Libraries/Components/Touchable/TouchableBounce.js b/Libraries/Components/Touchable/TouchableBounce.js
index 4a61ef0bc89d..c899748b44fd 100644
--- a/Libraries/Components/Touchable/TouchableBounce.js
+++ b/Libraries/Components/Touchable/TouchableBounce.js
@@ -56,7 +56,6 @@ const TouchableBounce = ((createReactClass({
 
   propTypes: {
     ...TouchableWithoutFeedback.propTypes,
-
     // The function passed takes a callback to start the animation which should
     // be run after this onPress handler is done. You can use this (for example)
     // to update UI before starting the animation.
diff --git a/Libraries/Components/Touchable/TouchableWithoutFeedback.js b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
index 2cd249cb5be6..9228d271a90f 100755
--- a/Libraries/Components/Touchable/TouchableWithoutFeedback.js
+++ b/Libraries/Components/Touchable/TouchableWithoutFeedback.js
@@ -80,6 +80,18 @@ const TouchableWithoutFeedback = ((createReactClass({
       PropTypes.oneOf(AccessibilityTraits),
       PropTypes.arrayOf(PropTypes.oneOf(AccessibilityTraits)),
     ]),
+    /**
+     * When `accessible` is true (which is the default) this may be called when
+     * the OS-specific concept of "focus" occurs. Some platforms may not have
+     * the concept of focus.
+     */
+    onFocus: PropTypes.func,
+    /**
+     * When `accessible` is true (which is the default) this may be called when
+     * the OS-specific concept of "blur" occurs, meaning the element lost focus.
+     * Some platforms may not have the concept of blur.
+     */
+    onBlur: PropTypes.func,
     /**
      * If true, disable all interactions for this component.
      */

From f8b4850425f115c8a23dead7ec0716b61663aed6 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 11 Jun 2018 17:45:29 -0700
Subject: [PATCH 0769/1109] Jest: Upgrade Flow Definition in RN + Metro

Reviewed By: sahrens

Differential Revision: D8371076

fbshipit-source-id: 12d03c545ca190a5fda1ff319e5ea906173d2241
---
 flow/jest.js | 592 +++++++++++++++++++++++++++++++++++++++++++++------
 1 file changed, 528 insertions(+), 64 deletions(-)

diff --git a/flow/jest.js b/flow/jest.js
index 7f6b79573255..ebd7c9ec0726 100644
--- a/flow/jest.js
+++ b/flow/jest.js
@@ -4,30 +4,124 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * Modified from https://raw.githubusercontent.com/flowtype/flow-typed/e3b0f3034929e0f0fb85c790450a201b380ac2fd/definitions/npm/jest_v17.x.x/flow_v0.33.x-/jest_v17.x.x.js
+ * Modified from https://raw.githubusercontent.com/flowtype/flow-typed/b43dff3e0ed5ccf7033839045f4819e8db40faa9/definitions/npm/jest_v20.x.x/flow_v0.22.x-/jest_v20.x.x.js
  * Duplicated from www/flow/shared/jest.js
+ * List of modifications:
+ *  - added function fail
+ *  - added jest.requireActual
+ *  - added jest.requireMock
+ *  - added JestMockFn.mockName
+ *  - added JestMockFn.mockRejectedValue
+ *  - added JestMockFn.mockRejectedValueOnce
+ *  - added JestMockFn.mockResolvedValue
+ *  - added JestMockFn.mockResolvedValueOnce
+ *  - added JestMockFn.mock.thrownErrors
+ *  - added JestMockFn.mock.returnValues
+ *  - added jest.setTimeout
  * @flow
  * @format
  */
 
-'use strict';
+/* eslint-disable lint/no-unclear-flowtypes */
 
-type JestMockFn = {
-  (...args: Array<any>): any,
+type JestMockFn<TArguments: $ReadOnlyArray<*>, TReturn> = {
+  (...args: TArguments): TReturn,
+  /**
+   * An object for introspecting mock calls
+   */
   mock: {
-    calls: Array<Array<any>>,
-    instances: mixed,
+    /**
+     * An array that represents all calls that have been made into this mock
+     * function. Each call is represented by an array of arguments that were
+     * passed during the call.
+     */
+    calls: Array<TArguments>,
+    /**
+     * An array that contains all the object instances that have been
+     * instantiated from this mock function.
+     */
+    instances: Array<TReturn>,
+    /**
+     * An array containing the results of a method, and whether they were
+     * returned or thrown.
+     */
+    results: Array<{isThrown: boolean}>,
   },
-  mockClear(): Function,
-  mockReset(): Function,
-  mockImplementation(fn: Function): JestMockFn,
-  mockImplementationOnce(fn: Function): JestMockFn,
+  /**
+   * Resets all information stored in the mockFn.mock.calls and
+   * mockFn.mock.instances arrays. Often this is useful when you want to clean
+   * up a mock's usage data between two assertions.
+   */
+  mockClear(): void,
+  /**
+   * Resets all information stored in the mock. This is useful when you want to
+   * completely restore a mock back to its initial state.
+   */
+  mockReset(): void,
+  /**
+   * Removes the mock and restores the initial implementation. This is useful
+   * when you want to mock functions in certain test cases and restore the
+   * original implementation in others. Beware that mockFn.mockRestore only
+   * works when mock was created with jest.spyOn. Thus you have to take care of
+   * restoration yourself when manually assigning jest.fn().
+   */
+  mockRestore(): void,
+  /**
+   * Accepts a function that should be used as the implementation of the mock.
+   * The mock itself will still record all calls that go into and instances
+   * that come from itself -- the only difference is that the implementation
+   * will also be executed when the mock is called.
+   */
+  mockImplementation(
+    fn: (...args: TArguments) => TReturn,
+  ): JestMockFn<TArguments, TReturn>,
+  /**
+   * Accepts a function that will be used as an implementation of the mock for
+   * one call to the mocked function. Can be chained so that multiple function
+   * calls produce different results.
+   */
+  mockImplementationOnce(
+    fn: (...args: TArguments) => TReturn,
+  ): JestMockFn<TArguments, TReturn>,
+  /**
+   * Accepts a string to use in test result output in place of "jest.fn()" to
+   * indicate which mock function is being referenced.
+   */
+  mockName(name: string): JestMockFn<TArguments, TReturn>,
+  /**
+   * Sugar for: jest.fn().mockReturnValue(Promise.reject(value));
+   */
+  mockRejectedValue(value: TReturn): JestMockFn<TArguments, TReturn>,
+  /**
+   * Sugar for: jest.fn().mockReturnValueOnce(Promise.reject(value));
+   */
+  mockRejectedValueOnce(value: TReturn): JestMockFn<TArguments, TReturn>,
+  /**
+   * Sugar for: jest.fn().mockReturnValue(Promise.resolve(value));
+   */
+  mockResolvedValue(value: TReturn): JestMockFn<TArguments, TReturn>,
+  /**
+   * Sugar for: jest.fn().mockReturnValueOnce(Promise.resolve(value));
+   */
+  mockResolvedValueOnce(value: TReturn): JestMockFn<TArguments, TReturn>,
+  /**
+   * Just a simple sugar function for returning `this`
+   */
   mockReturnThis(): void,
-  mockReturnValue(value: any): JestMockFn,
-  mockReturnValueOnce(value: any): JestMockFn,
+  /**
+   * Deprecated: use jest.fn(() => value) instead
+   */
+  mockReturnValue(value: TReturn): JestMockFn<TArguments, TReturn>,
+  /**
+   * Sugar for only returning a value once inside your mock
+   */
+  mockReturnValueOnce(value: TReturn): JestMockFn<TArguments, TReturn>,
 };
 
 type JestAsymmetricEqualityType = {
+  /**
+   * A custom Jasmine equality tester
+   */
   asymmetricMatch(value: mixed): boolean,
 };
 
@@ -44,7 +138,7 @@ type JestCallsType = {
 type JestClockType = {
   install(): void,
   mockDate(date: Date): void,
-  tick(): void,
+  tick(milliseconds?: number): void,
   uninstall(): void,
 };
 
@@ -68,105 +162,471 @@ type JestPromiseType = {
   resolves: JestExpectType,
 };
 
+/**
+ *  Plugin: jest-enzyme
+ */
+type EnzymeMatchersType = {
+  toBeChecked(): void,
+  toBeDisabled(): void,
+  toBeEmpty(): void,
+  toBePresent(): void,
+  toContainReact(element: React$Element<any>): void,
+  toHaveClassName(className: string): void,
+  toHaveHTML(html: string): void,
+  toHaveProp(propKey: string, propValue?: any): void,
+  toHaveRef(refName: string): void,
+  toHaveState(stateKey: string, stateValue?: any): void,
+  toHaveStyle(styleKey: string, styleValue?: any): void,
+  toHaveTagName(tagName: string): void,
+  toHaveText(text: string): void,
+  toIncludeText(text: string): void,
+  toHaveValue(value: any): void,
+  toMatchElement(element: React$Element<any>): void,
+  toMatchSelector(selector: string): void,
+};
+
 type JestExpectType = {
-  not: JestExpectType,
+  not: JestExpectType & EnzymeMatchersType,
+  /**
+   * If you have a mock function, you can use .lastCalledWith to test what
+   * arguments it was last called with.
+   */
   lastCalledWith(...args: Array<any>): void,
+  /**
+   * toBe just checks that a value is what you expect. It uses === to check
+   * strict equality.
+   */
   toBe(value: any): void,
+  /**
+   * Use .toHaveBeenCalled to ensure that a mock function got called.
+   */
   toBeCalled(): void,
+  /**
+   * Use .toBeCalledWith to ensure that a mock function was called with
+   * specific arguments.
+   */
   toBeCalledWith(...args: Array<any>): void,
+  /**
+   * Using exact equality with floating point numbers is a bad idea. Rounding
+   * means that intuitive things fail.
+   */
   toBeCloseTo(num: number, delta: any): void,
+  /**
+   * Use .toBeDefined to check that a variable is not undefined.
+   */
   toBeDefined(): void,
+  /**
+   * Use .toBeFalsy when you don't care what a value is, you just want to
+   * ensure a value is false in a boolean context.
+   */
   toBeFalsy(): void,
+  /**
+   * To compare floating point numbers, you can use toBeGreaterThan.
+   */
   toBeGreaterThan(number: number): void,
+  /**
+   * To compare floating point numbers, you can use toBeGreaterThanOrEqual.
+   */
   toBeGreaterThanOrEqual(number: number): void,
+  /**
+   * To compare floating point numbers, you can use toBeLessThan.
+   */
   toBeLessThan(number: number): void,
+  /**
+   * To compare floating point numbers, you can use toBeLessThanOrEqual.
+   */
   toBeLessThanOrEqual(number: number): void,
+  /**
+   * Use .toBeInstanceOf(Class) to check that an object is an instance of a
+   * class.
+   */
   toBeInstanceOf(cls: Class<*>): void,
+  /**
+   * .toBeNull() is the same as .toBe(null) but the error messages are a bit
+   * nicer.
+   */
   toBeNull(): void,
+  /**
+   * Use .toBeTruthy when you don't care what a value is, you just want to
+   * ensure a value is true in a boolean context.
+   */
   toBeTruthy(): void,
+  /**
+   * Use .toBeUndefined to check that a variable is undefined.
+   */
   toBeUndefined(): void,
+  /**
+   * Use .toContain when you want to check that an item is in a list. For
+   * testing the items in the list, this uses ===, a strict equality check.
+   */
   toContain(item: any): void,
+  /**
+   * Use .toContainEqual when you want to check that an item is in a list. For
+   * testing the items in the list, this matcher recursively checks the
+   * equality of all fields, rather than checking for object identity.
+   */
   toContainEqual(item: any): void,
+  /**
+   * Use .toEqual when you want to check that two objects have the same value.
+   * This matcher recursively checks the equality of all fields, rather than
+   * checking for object identity.
+   */
   toEqual(value: any): void,
+  /**
+   * Use .toHaveBeenCalled to ensure that a mock function got called.
+   */
   toHaveBeenCalled(): void,
+  /**
+   * Use .toHaveBeenCalledTimes to ensure that a mock function got called exact
+   * number of times.
+   */
   toHaveBeenCalledTimes(number: number): void,
+  /**
+   * Use .toHaveBeenCalledWith to ensure that a mock function was called with
+   * specific arguments.
+   */
   toHaveBeenCalledWith(...args: Array<any>): void,
-  toHaveProperty(path: string, value?: any): void,
-  toMatch(regexp: RegExp): void,
+  /**
+   * Use .toHaveBeenLastCalledWith to ensure that a mock function was last called
+   * with specific arguments.
+   */
+  toHaveBeenLastCalledWith(...args: Array<any>): void,
+  /**
+   * Check that an object has a .length property and it is set to a certain
+   * numeric value.
+   */
+  toHaveLength(number: number): void,
+  /**
+   *
+   */
+  toHaveProperty(propPath: string, value?: any): void,
+  /**
+   * Use .toMatch to check that a string matches a regular expression or string.
+   */
+  toMatch(regexpOrString: RegExp | string): void,
+  /**
+   * Use .toMatchObject to check that a javascript object matches a subset of the properties of an object.
+   */
   toMatchObject(object: Object): void,
-  toMatchSnapshot(): void,
-  toThrow(message?: string | Error | Class<Error>): void,
-  toThrowError(message?: string | Error | Class<Error> | RegExp): void,
+  /**
+   * This ensures that a React component matches the most recent snapshot.
+   */
+  toMatchSnapshot(name?: string): void,
+  /**
+   * Use .toThrow to test that a function throws when it is called.
+   * If you want to test that a specific error gets thrown, you can provide an
+   * argument to toThrow. The argument can be a string for the error message,
+   * a class for the error, or a regex that should match the error.
+   *
+   * Alias: .toThrowError
+   */
+  toThrow(message?: string | Error | RegExp): void,
+  toThrowError(message?: string | Error | RegExp): void,
+  /**
+   * Use .toThrowErrorMatchingSnapshot to test that a function throws a error
+   * matching the most recent snapshot when it is called.
+   */
   toThrowErrorMatchingSnapshot(): void,
 };
 
+type JestObjectType = {
+  /**
+   *  Disables automatic mocking in the module loader.
+   *
+   *  After this method is called, all `require()`s will return the real
+   *  versions of each module (rather than a mocked version).
+   */
+  disableAutomock(): JestObjectType,
+  /**
+   * An un-hoisted version of disableAutomock
+   */
+  autoMockOff(): JestObjectType,
+  /**
+   * Enables automatic mocking in the module loader.
+   */
+  enableAutomock(): JestObjectType,
+  /**
+   * An un-hoisted version of enableAutomock
+   */
+  autoMockOn(): JestObjectType,
+  /**
+   * Clears the mock.calls and mock.instances properties of all mocks.
+   * Equivalent to calling .mockClear() on every mocked function.
+   */
+  clearAllMocks(): JestObjectType,
+  /**
+   * Resets the state of all mocks. Equivalent to calling .mockReset() on every
+   * mocked function.
+   */
+  resetAllMocks(): JestObjectType,
+  /**
+   * Restores all mocks back to their original value.
+   */
+  restoreAllMocks(): JestObjectType,
+  /**
+   * Removes any pending timers from the timer system.
+   */
+  clearAllTimers(): void,
+  /**
+   * The same as `mock` but not moved to the top of the expectation by
+   * babel-jest.
+   */
+  doMock(moduleName: string, moduleFactory?: any): JestObjectType,
+  /**
+   * The same as `unmock` but not moved to the top of the expectation by
+   * babel-jest.
+   */
+  dontMock(moduleName: string): JestObjectType,
+  /**
+   * Returns a new, unused mock function. Optionally takes a mock
+   * implementation.
+   */
+  fn<TArguments: $ReadOnlyArray<*>, TReturn>(
+    implementation?: (...args: TArguments) => TReturn,
+  ): JestMockFn<TArguments, TReturn>,
+  /**
+   * Determines if the given function is a mocked function.
+   */
+  isMockFunction(fn: Function): boolean,
+  /**
+   * Given the name of a module, use the automatic mocking system to generate a
+   * mocked version of the module for you.
+   */
+  genMockFromModule(moduleName: string): any,
+  /**
+   * Mocks a module with an auto-mocked version when it is being required.
+   *
+   * The second argument can be used to specify an explicit module factory that
+   * is being run instead of using Jest's automocking feature.
+   *
+   * The third argument can be used to create virtual mocks -- mocks of modules
+   * that don't exist anywhere in the system.
+   */
+  mock(
+    moduleName: string,
+    moduleFactory?: any,
+    options?: Object,
+  ): JestObjectType,
+  /**
+   * Resets the module registry - the cache of all required modules. This is
+   * useful to isolate modules where local state might conflict between tests.
+   */
+  resetModules(): JestObjectType,
+  /**
+   * Exhausts the micro-task queue (usually interfaced in node via
+   * process.nextTick).
+   */
+  runAllTicks(): void,
+  /**
+   * Exhausts the macro-task queue (i.e., all tasks queued by setTimeout(),
+   * setInterval(), and setImmediate()).
+   */
+  runAllTimers(): void,
+  /**
+   * Exhausts all tasks queued by setImmediate().
+   */
+  runAllImmediates(): void,
+  /**
+   * Executes only the macro task queue (i.e. all tasks queued by setTimeout()
+   * or setInterval() and setImmediate()).
+   */
+  advanceTimersByTime(msToRun: number): void,
+  /**
+   * Executes only the macro task queue (i.e. all tasks queued by setTimeout()
+   * or setInterval() and setImmediate()).
+   *
+   * Renamed to `advanceTimersByTime`.
+   */
+  runTimersToTime(msToRun: number): void,
+  /**
+   * Executes only the macro-tasks that are currently pending (i.e., only the
+   * tasks that have been queued by setTimeout() or setInterval() up to this
+   * point)
+   */
+  runOnlyPendingTimers(): void,
+  /**
+   * Explicitly supplies the mock object that the module system should return
+   * for the specified module. Note: It is recommended to use jest.mock()
+   * instead.
+   */
+  setMock(moduleName: string, moduleExports: any): JestObjectType,
+  /**
+   * Indicates that the module system should never return a mocked version of
+   * the specified module from require() (e.g. that it should always return the
+   * real module).
+   */
+  unmock(moduleName: string): JestObjectType,
+  /**
+   * Instructs Jest to use fake versions of the standard timer functions
+   * (setTimeout, setInterval, clearTimeout, clearInterval, nextTick,
+   * setImmediate and clearImmediate).
+   */
+  useFakeTimers(): JestObjectType,
+  /**
+   * Instructs Jest to use the real versions of the standard timer functions.
+   */
+  useRealTimers(): JestObjectType,
+  /**
+   * Creates a mock function similar to jest.fn but also tracks calls to
+   * object[methodName].
+   */
+  spyOn(object: Object, methodName: string): JestMockFn<any, any>,
+  /**
+   * Set the default timeout interval for tests and before/after hooks in milliseconds.
+   * Note: The default timeout interval is 5 seconds if this method is not called.
+   */
+  setTimeout(timeout: number): JestObjectType,
+
+  // These methods are added separately and not a part of flow-typed OSS
+  // version of this file. They were added in jest@21.0.0.alpha-2 which is not
+  // yet publicly released yet.
+  // TODO T21262347 Add them to OSS version of flow-typed
+  requireActual(module: string): any,
+  requireMock(module: string): any,
+};
+
 type JestSpyType = {
   calls: JestCallsType,
 };
 
-declare function afterEach(fn: Function): void;
-declare function beforeEach(fn: Function): void;
-declare function afterAll(fn: Function): void;
-declare function beforeAll(fn: Function): void;
-declare function describe(name: string, fn: Function): void;
+/** Runs this function after every test inside this context */
+declare function afterEach(
+  fn: (done: () => void) => ?Promise<mixed>,
+  timeout?: number,
+): void;
+/** Runs this function before every test inside this context */
+declare function beforeEach(
+  fn: (done: () => void) => ?Promise<mixed>,
+  timeout?: number,
+): void;
+/** Runs this function after all tests have finished inside this context */
+declare function afterAll(
+  fn: (done: () => void) => ?Promise<mixed>,
+  timeout?: number,
+): void;
+/** Runs this function before any tests have started inside this context */
+declare function beforeAll(
+  fn: (done: () => void) => ?Promise<mixed>,
+  timeout?: number,
+): void;
+
+/** A context for grouping tests together */
+declare var describe: {
+  /**
+   * Creates a block that groups together several related tests in one "test suite"
+   */
+  (name: string, fn: () => void): void,
+
+  /**
+   * Only run this describe block
+   */
+  only(name: string, fn: () => void): void,
+
+  /**
+   * Skip running this describe block
+   */
+  skip(name: string, fn: () => void): void,
+};
+
+/** An individual test unit */
 declare var it: {
-  (name: string, fn: Function): ?Promise<void>,
-  only(name: string, fn: Function): ?Promise<void>,
-  skip(name: string, fn: Function): ?Promise<void>,
+  /**
+   * An individual test unit
+   *
+   * @param {string} Name of Test
+   * @param {Function} Test
+   * @param {number} Timeout for the test, in milliseconds.
+   */
+  (
+    name: string,
+    fn?: (done: () => void) => ?Promise<mixed>,
+    timeout?: number,
+  ): void,
+  /**
+   * Only run this test
+   *
+   * @param {string} Name of Test
+   * @param {Function} Test
+   * @param {number} Timeout for the test, in milliseconds.
+   */
+  only(
+    name: string,
+    fn?: (done: () => void) => ?Promise<mixed>,
+    timeout?: number,
+  ): void,
+  /**
+   * Skip running this test
+   *
+   * @param {string} Name of Test
+   * @param {Function} Test
+   * @param {number} Timeout for the test, in milliseconds.
+   */
+  skip(
+    name: string,
+    fn?: (done: () => void) => ?Promise<mixed>,
+    timeout?: number,
+  ): void,
+  /**
+   * Run the test concurrently
+   *
+   * @param {string} Name of Test
+   * @param {Function} Test
+   * @param {number} Timeout for the test, in milliseconds.
+   */
+  concurrent(
+    name: string,
+    fn?: (done: () => void) => ?Promise<mixed>,
+    timeout?: number,
+  ): void,
 };
-declare function fit(name: string, fn: Function): ?Promise<void>;
-declare function pit(name: string, fn: () => Promise<any>): Promise<void>;
+declare function fit(
+  name: string,
+  fn: (done: () => void) => ?Promise<mixed>,
+  timeout?: number,
+): void;
+/** An individual test unit */
 declare var test: typeof it;
+/** A disabled group of tests */
 declare var xdescribe: typeof describe;
+/** A focused group of tests */
 declare var fdescribe: typeof describe;
+/** A disabled individual test */
 declare var xit: typeof it;
+/** A disabled individual test */
 declare var xtest: typeof it;
 
+/** The expect function is used every time you want to test a value */
 declare var expect: {
-  (value: any): JestExpectType & JestPromiseType,
-  any: any,
+  /** The object that you want to make assertions against */
+  (value: any): JestExpectType & JestPromiseType & EnzymeMatchersType,
+  /** Add additional Jasmine matchers to Jest's roster */
   extend(matchers: {[name: string]: JestMatcher}): void,
-  objectContaining(any): void,
+  /** Add a module that formats application-specific data structures. */
+  addSnapshotSerializer(serializer: (input: Object) => string): void,
+  assertions(expectedAssertions: number): void,
+  hasAssertions(): void,
+  any(value: mixed): JestAsymmetricEqualityType,
+  anything(): void,
+  arrayContaining(value: Array<mixed>): void,
+  objectContaining(value: Object): void,
+  /** Matches any received string that contains the exact expected string. */
+  stringContaining(value: string): void,
+  stringMatching(value: string | RegExp): void,
 };
+
 declare function fail(message?: string): void;
 
 // TODO handle return type
 // http://jasmine.github.io/2.4/introduction.html#section-Spies
 declare function spyOn(value: mixed, method: string): Object;
 
-type Jest = {
-  autoMockOff(): Jest,
-  autoMockOn(): Jest,
-  resetAllMocks(): Jest,
-  clearAllTimers(): void,
-  currentTestPath(): void,
-  disableAutomock(): Jest,
-  doMock(moduleName: string, moduleFactory?: any): void,
-  dontMock(moduleName: string): Jest,
-  enableAutomock(): Jest,
-  fn(implementation?: Function): JestMockFn,
-  genMockFromModule(moduleName: string): any,
-  isMockFunction(fn: Function): boolean,
-  mock(
-    moduleName: string,
-    moduleFactory?: any,
-    options?: {virtual?: boolean},
-  ): Jest,
-  resetModuleRegistry(): Jest, // undocumented alias for resetModuleRegistry
-  resetModules(): Jest,
-  restoreAllMocks(): Jest,
-  runAllTicks(): Jest,
-  runAllTimers(): Jest,
-  runTimersToTime(msToRun: number): Jest,
-  runOnlyPendingTimers(): Jest,
-  setMock(moduleName: string, moduleExports: any): Jest,
-  unmock(moduleName: string): Jest,
-  useFakeTimers(): Jest,
-  useRealTimers(): Jest,
-};
-
-declare var jest: Jest;
+/** Holds all functions related to manipulating test runner */
+declare var jest: JestObjectType;
 
+/**
+ * The global Jamine object, this is generally not exposed as the public API,
+ * using features inside here could break in later versions of Jest.
+ */
 declare var jasmine: {
   DEFAULT_TIMEOUT_INTERVAL: number,
   any(value: mixed): JestAsymmetricEqualityType,
@@ -174,6 +634,10 @@ declare var jasmine: {
   arrayContaining(value: Array<mixed>): void,
   clock(): JestClockType,
   createSpy(name: string): JestSpyType,
+  createSpyObj(
+    baseName: string,
+    methodNames: Array<string>,
+  ): {[methodName: string]: JestSpyType},
   objectContaining(value: Object): void,
   stringMatching(value: string): void,
 };

From d0219a0301e59e8b0ef75dbd786318d4b4619f4c Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Mon, 11 Jun 2018 18:20:52 -0700
Subject: [PATCH 0770/1109] RN: A wild YellowBox has appeared!

Summary:
Replaces the existing `YellowBox` with a modern one.

Here are the notable changes:

- Sort warnings by recency (with most recent on top).
- Group warnings by format string if present.
- Present stack traces similar to RedBox.
- Show status of loading source maps.
- Support inspecting each occurrence of a warning.
- Fixed a bunch of edge cases and race conditions.

Reviewed By: TheSavior

Differential Revision: D8345180

fbshipit-source-id: b9e10d526b262c3985bbea639ba2ea0e7cad5081
---
 Libraries/ReactNative/AppContainer.js         |   7 +
 Libraries/ReactNative/YellowBox.js            | 554 ------------------
 Libraries/StyleSheet/StyleSheetTypes.js       |   8 +-
 Libraries/UTFSequence.js                      |   3 +
 Libraries/YellowBox/Data/YellowBoxCategory.js | 146 +++++
 Libraries/YellowBox/Data/YellowBoxRegistry.js | 141 +++++
 .../YellowBox/Data/YellowBoxSymbolication.js  |  75 +++
 Libraries/YellowBox/Data/YellowBoxWarning.js  | 108 ++++
 .../Data/__tests__/YellowBoxCategory-test.js  | 100 ++++
 .../Data/__tests__/YellowBoxRegistry-test.js  | 267 +++++++++
 .../__tests__/YellowBoxSymbolication-test.js  |  52 ++
 .../Data/__tests__/YellowBoxWarning-test.js   | 126 ++++
 Libraries/YellowBox/UI/YellowBoxButton.js     |  53 ++
 .../YellowBox/UI/YellowBoxImageSource.js      |  52 ++
 Libraries/YellowBox/UI/YellowBoxInspector.js  | 190 ++++++
 .../YellowBox/UI/YellowBoxInspectorFooter.js  |  76 +++
 .../YellowBox/UI/YellowBoxInspectorHeader.js  | 108 ++++
 .../UI/YellowBoxInspectorSourceMapStatus.js   | 149 +++++
 .../UI/YellowBoxInspectorStackFrame.js        |  81 +++
 Libraries/YellowBox/UI/YellowBoxList.js       | 142 +++++
 Libraries/YellowBox/UI/YellowBoxListRow.js    | 100 ++++
 Libraries/YellowBox/UI/YellowBoxPressable.js  |  86 +++
 Libraries/YellowBox/UI/YellowBoxStyle.js      |  31 +
 Libraries/YellowBox/YellowBox.js              | 132 +++++
 .../YellowBox/__tests__/YellowBox-test.js     |  77 +++
 25 files changed, 2306 insertions(+), 558 deletions(-)
 delete mode 100644 Libraries/ReactNative/YellowBox.js
 create mode 100644 Libraries/YellowBox/Data/YellowBoxCategory.js
 create mode 100644 Libraries/YellowBox/Data/YellowBoxRegistry.js
 create mode 100644 Libraries/YellowBox/Data/YellowBoxSymbolication.js
 create mode 100644 Libraries/YellowBox/Data/YellowBoxWarning.js
 create mode 100644 Libraries/YellowBox/Data/__tests__/YellowBoxCategory-test.js
 create mode 100644 Libraries/YellowBox/Data/__tests__/YellowBoxRegistry-test.js
 create mode 100644 Libraries/YellowBox/Data/__tests__/YellowBoxSymbolication-test.js
 create mode 100644 Libraries/YellowBox/Data/__tests__/YellowBoxWarning-test.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxButton.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxImageSource.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxInspector.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxInspectorFooter.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxInspectorHeader.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxInspectorSourceMapStatus.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxInspectorStackFrame.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxList.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxListRow.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxPressable.js
 create mode 100644 Libraries/YellowBox/UI/YellowBoxStyle.js
 create mode 100644 Libraries/YellowBox/YellowBox.js
 create mode 100644 Libraries/YellowBox/__tests__/YellowBox-test.js

diff --git a/Libraries/ReactNative/AppContainer.js b/Libraries/ReactNative/AppContainer.js
index ad5f8c06a35f..58ffb095fe53 100644
--- a/Libraries/ReactNative/AppContainer.js
+++ b/Libraries/ReactNative/AppContainer.js
@@ -127,4 +127,11 @@ const styles = StyleSheet.create({
   },
 });
 
+if (__DEV__) {
+  if (!global.__RCTProfileIsProfiling) {
+    const YellowBox = require('YellowBox');
+    YellowBox.install();
+  }
+}
+
 module.exports = AppContainer;
diff --git a/Libraries/ReactNative/YellowBox.js b/Libraries/ReactNative/YellowBox.js
deleted file mode 100644
index 01a4bd82dee6..000000000000
--- a/Libraries/ReactNative/YellowBox.js
+++ /dev/null
@@ -1,554 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @flow
- * @format
- */
-
-'use strict';
-
-const EventEmitter = require('EventEmitter');
-const Platform = require('Platform');
-const React = require('React');
-const SafeAreaView = require('SafeAreaView');
-const StyleSheet = require('StyleSheet');
-const RCTLog = require('RCTLog');
-
-const infoLog = require('infoLog');
-const openFileInEditor = require('openFileInEditor');
-const parseErrorStack = require('parseErrorStack');
-const stringifySafe = require('stringifySafe');
-const symbolicateStackTrace = require('symbolicateStackTrace');
-
-import type EmitterSubscription from 'EmitterSubscription';
-import type {StackFrame} from 'parseErrorStack';
-
-type WarningInfo = {
-  count: number,
-  stacktrace: Array<StackFrame>,
-  symbolicated: boolean,
-};
-
-const _warningEmitter = new EventEmitter();
-const _warningMap: Map<string, WarningInfo> = new Map();
-const IGNORED_WARNINGS: Array<string> = [];
-
-/**
- * YellowBox renders warnings at the bottom of the app being developed.
- *
- * Warnings help guard against subtle yet significant issues that can impact the
- * quality of the app. This "in your face" style of warning allows developers to
- * notice and correct these issues as quickly as possible.
- *
- * By default, the warning box is enabled in `__DEV__`. Set the following flag
- * to disable it (and call `console.warn` to update any rendered <YellowBox>):
- *
- *   console.disableYellowBox = true;
- *   console.warn('YellowBox is disabled.');
- *
- * Ignore specific warnings by calling:
- *
- *   YellowBox.ignoreWarnings(['Warning: ...']);
- *
- * (DEPRECATED) Warnings can be ignored programmatically by setting the array:
- *
- *   console.ignoredYellowBox = ['Warning: ...'];
- *
- * Strings in `console.ignoredYellowBox` can be a prefix of the warning that
- * should be ignored.
- */
-
-if (__DEV__) {
-  const {error, warn} = console;
-
-  (console: any).error = function() {
-    error.apply(console, arguments);
-    // Show yellow box for the `warning` module.
-    if (
-      typeof arguments[0] === 'string' &&
-      arguments[0].startsWith('Warning: ')
-    ) {
-      updateWarningMap.apply(null, arguments);
-    }
-  };
-
-  (console: any).warn = function() {
-    warn.apply(console, arguments);
-    updateWarningMap.apply(null, arguments);
-  };
-
-  if (Platform.isTesting) {
-    (console: any).disableYellowBox = true;
-  }
-
-  RCTLog.setWarningHandler((...args) => {
-    updateWarningMap.apply(null, args);
-  });
-}
-
-/**
- * Simple function for formatting strings.
- *
- * Replaces placeholders with values passed as extra arguments
- *
- * @param {string} format the base string
- * @param ...args the values to insert
- * @return {string} the replaced string
- */
-function sprintf(format, ...args) {
-  let index = 0;
-  return format.replace(/%s/g, match => args[index++]);
-}
-
-function updateWarningMap(...args): void {
-  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
-   * found when Flow v0.68 was deployed. To see the error delete this comment
-   * and run Flow. */
-  if (console.disableYellowBox) {
-    return;
-  }
-
-  let warning;
-  if (typeof args[0] === 'string') {
-    const [format, ...formatArgs] = args;
-    const argCount = (format.match(/%s/g) || []).length;
-    warning = [
-      sprintf(format, ...formatArgs.slice(0, argCount).map(stringifySafe)),
-      ...formatArgs.slice(argCount).map(stringifySafe),
-    ].join(' ');
-  } else {
-    warning = args.map(stringifySafe).join(' ');
-  }
-
-  if (warning.startsWith('(ADVICE)')) {
-    return;
-  }
-
-  const warningInfo = _warningMap.get(warning);
-  if (warningInfo) {
-    warningInfo.count += 1;
-  } else {
-    const error: any = new Error();
-    error.framesToPop = 2;
-
-    _warningMap.set(warning, {
-      count: 1,
-      stacktrace: parseErrorStack(error),
-      symbolicated: false,
-    });
-  }
-
-  _warningEmitter.emit('warning', _warningMap);
-}
-
-function ensureSymbolicatedWarning(warning: string): void {
-  const prevWarningInfo = _warningMap.get(warning);
-  if (!prevWarningInfo || prevWarningInfo.symbolicated) {
-    return;
-  }
-  prevWarningInfo.symbolicated = true;
-
-  symbolicateStackTrace(prevWarningInfo.stacktrace).then(
-    stack => {
-      const nextWarningInfo = _warningMap.get(warning);
-      if (nextWarningInfo) {
-        nextWarningInfo.stacktrace = stack;
-        _warningEmitter.emit('warning', _warningMap);
-      }
-    },
-    error => {
-      const nextWarningInfo = _warningMap.get(warning);
-      if (nextWarningInfo) {
-        infoLog('Failed to symbolicate warning, "%s":', warning, error);
-        _warningEmitter.emit('warning', _warningMap);
-      }
-    },
-  );
-}
-
-function isWarningIgnored(warning: string): boolean {
-  const isIgnored = IGNORED_WARNINGS.some((ignoredWarning: string) =>
-    warning.includes(ignoredWarning),
-  );
-
-  if (isIgnored) {
-    return true;
-  }
-
-  // DEPRECATED
-  return (
-    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
-     * error found when Flow v0.68 was deployed. To see the error delete this
-     * comment and run Flow. */
-    Array.isArray(console.ignoredYellowBox) &&
-    console.ignoredYellowBox.some(ignorePrefix =>
-      warning.startsWith(String(ignorePrefix)),
-    )
-  );
-}
-
-const WarningRow = ({count, warning, onPress}) => {
-  const Text = require('Text');
-  const TouchableHighlight = require('TouchableHighlight');
-  const View = require('View');
-
-  const countText =
-    count > 1 ? (
-      <Text style={styles.listRowCount}>{'(' + count + ') '}</Text>
-    ) : null;
-
-  return (
-    <View style={styles.listRow}>
-      <TouchableHighlight
-        activeOpacity={0.5}
-        onPress={onPress}
-        style={styles.listRowContent}
-        underlayColor="transparent">
-        <Text style={styles.listRowText} numberOfLines={2}>
-          {countText}
-          {warning}
-        </Text>
-      </TouchableHighlight>
-    </View>
-  );
-};
-
-type StackRowProps = {frame: StackFrame};
-const StackRow = ({frame}: StackRowProps) => {
-  const Text = require('Text');
-  const TouchableHighlight = require('TouchableHighlight');
-  const {file, lineNumber} = frame;
-  let fileName;
-  if (file) {
-    const fileParts = file.split('/');
-    fileName = fileParts[fileParts.length - 1];
-  } else {
-    fileName = '<unknown file>';
-  }
-
-  return (
-    <TouchableHighlight
-      activeOpacity={0.5}
-      style={styles.openInEditorButton}
-      underlayColor="transparent"
-      onPress={openFileInEditor.bind(null, file, lineNumber)}>
-      <Text style={styles.inspectorCountText}>
-        {fileName}:{lineNumber}
-      </Text>
-    </TouchableHighlight>
-  );
-};
-
-const WarningInspector = ({
-  warningInfo,
-  warning,
-  stacktraceVisible,
-  onDismiss,
-  onMinimize,
-  toggleStacktrace,
-}) => {
-  const ScrollView = require('ScrollView');
-  const Text = require('Text');
-  const TouchableHighlight = require('TouchableHighlight');
-  const View = require('View');
-  const {count, stacktrace} = warningInfo || {};
-
-  const countSentence =
-    'Warning encountered ' + count + ' time' + (count - 1 ? 's' : '') + '.';
-
-  let stacktraceList;
-  if (stacktraceVisible && stacktrace) {
-    stacktraceList = (
-      <View style={styles.stacktraceList}>
-        {stacktrace.map((frame, ii) => <StackRow frame={frame} key={ii} />)}
-      </View>
-    );
-  }
-
-  return (
-    <View style={styles.inspector}>
-      <SafeAreaView style={styles.safeArea}>
-        <View style={styles.inspectorCount}>
-          <Text style={styles.inspectorCountText}>{countSentence}</Text>
-          <TouchableHighlight
-            onPress={toggleStacktrace}
-            underlayColor="transparent">
-            <Text style={styles.inspectorButtonText}>
-              {stacktraceVisible ? '\u{25BC}' : '\u{25B6}'} Stacktrace
-            </Text>
-          </TouchableHighlight>
-        </View>
-        <ScrollView style={styles.inspectorWarning}>
-          {stacktraceList}
-          <Text style={styles.inspectorWarningText}>{warning}</Text>
-        </ScrollView>
-        <View style={styles.inspectorButtons}>
-          <TouchableHighlight
-            activeOpacity={0.5}
-            onPress={onMinimize}
-            style={styles.inspectorButton}
-            underlayColor="transparent">
-            <Text style={styles.inspectorButtonText}>Minimize</Text>
-          </TouchableHighlight>
-          <TouchableHighlight
-            activeOpacity={0.5}
-            onPress={onDismiss}
-            style={styles.inspectorButton}
-            underlayColor="transparent">
-            <Text style={styles.inspectorButtonText}>Dismiss</Text>
-          </TouchableHighlight>
-        </View>
-      </SafeAreaView>
-    </View>
-  );
-};
-
-class YellowBox extends React.Component<
-  mixed,
-  {
-    stacktraceVisible: boolean,
-    inspecting: ?string,
-    warningMap: Map<any, any>,
-  },
-> {
-  _listener: ?EmitterSubscription;
-  dismissWarning: (warning: ?string) => void;
-
-  constructor(props: mixed, context: mixed) {
-    super(props, context);
-    this.state = {
-      inspecting: null,
-      stacktraceVisible: false,
-      warningMap: _warningMap,
-    };
-    this.dismissWarning = warning => {
-      const {inspecting, warningMap} = this.state;
-      if (warning) {
-        warningMap.delete(warning);
-      } else {
-        warningMap.clear();
-      }
-      this.setState({
-        inspecting: warning && inspecting !== warning ? inspecting : null,
-        warningMap,
-      });
-    };
-  }
-
-  static ignoreWarnings(warnings: Array<string>): void {
-    warnings.forEach((warning: string) => {
-      if (IGNORED_WARNINGS.indexOf(warning) === -1) {
-        IGNORED_WARNINGS.push(warning);
-      }
-    });
-  }
-
-  componentDidMount() {
-    let scheduled = null;
-    this._listener = _warningEmitter.addListener('warning', warningMap => {
-      // Use `setImmediate` because warnings often happen during render, but
-      // state cannot be set while rendering.
-      scheduled =
-        scheduled ||
-        setImmediate(() => {
-          scheduled = null;
-          this.setState({
-            warningMap,
-          });
-        });
-    });
-  }
-
-  componentDidUpdate() {
-    const {inspecting} = this.state;
-    if (inspecting != null) {
-      ensureSymbolicatedWarning(inspecting);
-    }
-  }
-
-  componentWillUnmount() {
-    if (this._listener) {
-      this._listener.remove();
-    }
-  }
-
-  render() {
-    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
-     * error found when Flow v0.68 was deployed. To see the error delete this
-     * comment and run Flow. */
-    if (console.disableYellowBox || this.state.warningMap.size === 0) {
-      return null;
-    }
-    const ScrollView = require('ScrollView');
-    const View = require('View');
-    const Text = require('Text');
-    const TouchableHighlight = require('TouchableHighlight');
-
-    const {inspecting, stacktraceVisible} = this.state;
-    const inspector =
-      inspecting !== null ? (
-        <WarningInspector
-          warningInfo={this.state.warningMap.get(inspecting)}
-          warning={inspecting}
-          stacktraceVisible={stacktraceVisible}
-          onDismiss={() => this.dismissWarning(inspecting)}
-          onMinimize={() => this.setState({inspecting: null})}
-          toggleStacktrace={() =>
-            this.setState({stacktraceVisible: !stacktraceVisible})
-          }
-        />
-      ) : null;
-
-    const rows = [];
-    this.state.warningMap.forEach((warningInfo, warning) => {
-      if (!isWarningIgnored(warning)) {
-        rows.push(
-          <WarningRow
-            key={warning}
-            count={warningInfo.count}
-            warning={warning}
-            onPress={() => this.setState({inspecting: warning})}
-            onDismiss={() => this.dismissWarning(warning)}
-          />,
-        );
-      }
-    });
-
-    const listStyle = [
-      styles.list,
-      // Additional `0.4` so the 5th row can peek into view.
-      {height: Math.min(rows.length, 4.4) * (rowGutter + rowHeight)},
-    ];
-    return (
-      <View style={inspector ? styles.fullScreen : listStyle}>
-        {!inspector &&
-          rows.length > 0 && (
-            <TouchableHighlight
-              style={styles.dismissAllContainer}
-              onPress={() => this.dismissWarning(null)}>
-              <Text style={styles.dismissAll}>Dismiss All</Text>
-            </TouchableHighlight>
-          )}
-        <ScrollView style={listStyle} scrollsToTop={false}>
-          {rows}
-        </ScrollView>
-        {inspector}
-      </View>
-    );
-  }
-}
-
-const backgroundColor = opacity => 'rgba(250, 186, 48, ' + opacity + ')';
-const textColor = 'white';
-const rowGutter = 1;
-const rowHeight = 46;
-
-// For unknown reasons, setting elevation: Number.MAX_VALUE causes remote debugging to
-// hang on iOS (some sort of overflow maybe). Setting it to Number.MAX_SAFE_INTEGER fixes the iOS issue, but since
-// elevation is an android-only style property we might as well remove it altogether for iOS.
-// See: https://github.com/facebook/react-native/issues/12223
-const elevation =
-  Platform.OS === 'android' ? Number.MAX_SAFE_INTEGER : undefined;
-
-const styles = StyleSheet.create({
-  fullScreen: {
-    height: '100%',
-    width: '100%',
-    elevation: elevation,
-    position: 'absolute',
-  },
-  inspector: {
-    backgroundColor: backgroundColor(0.95),
-    height: '100%',
-    paddingTop: 5,
-    elevation: elevation,
-  },
-  inspectorButtons: {
-    flexDirection: 'row',
-  },
-  inspectorButton: {
-    flex: 1,
-    paddingVertical: 22,
-    backgroundColor: backgroundColor(1),
-  },
-  safeArea: {
-    flex: 1,
-  },
-  stacktraceList: {
-    paddingBottom: 5,
-  },
-  inspectorButtonText: {
-    color: textColor,
-    fontSize: 14,
-    opacity: 0.8,
-    textAlign: 'center',
-  },
-  openInEditorButton: {
-    paddingTop: 5,
-    paddingBottom: 5,
-  },
-  inspectorCount: {
-    padding: 15,
-    paddingBottom: 0,
-    flexDirection: 'row',
-    justifyContent: 'space-between',
-  },
-  inspectorCountText: {
-    color: textColor,
-    fontSize: 14,
-  },
-  inspectorWarning: {
-    flex: 1,
-    paddingHorizontal: 15,
-  },
-  inspectorWarningText: {
-    color: textColor,
-    fontSize: 16,
-    fontWeight: '600',
-  },
-  list: {
-    backgroundColor: 'transparent',
-    position: 'absolute',
-    left: 0,
-    right: 0,
-    bottom: 0,
-    elevation: elevation,
-  },
-  listRow: {
-    backgroundColor: backgroundColor(0.95),
-    height: rowHeight,
-    marginTop: rowGutter,
-  },
-  listRowContent: {
-    flex: 1,
-  },
-  listRowCount: {
-    color: 'rgba(255, 255, 255, 0.5)',
-  },
-  listRowText: {
-    color: textColor,
-    position: 'absolute',
-    left: 0,
-    top: Platform.OS === 'android' ? 5 : 7,
-    marginLeft: 15,
-    marginRight: 15,
-  },
-  dismissAllContainer: {
-    height: 20,
-    justifyContent: 'center',
-    marginTop: -30,
-    marginRight: 5,
-    backgroundColor: backgroundColor(0.95),
-    alignSelf: 'flex-end',
-    paddingHorizontal: 10,
-    borderRadius: 10,
-  },
-  dismissAll: {
-    color: 'white',
-  },
-});
-
-module.exports = YellowBox;
diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index 321bdc86922d..cf385bb7df66 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -92,10 +92,10 @@ export type ____LayoutStyle_Internal = $ReadOnly<{|
 export type ____TransformStyle_Internal = $ReadOnly<{|
   transform?: $ReadOnlyArray<
     | {|+perspective: number | AnimatedNode|}
-    | {|+rotate: string|}
-    | {|+rotateX: string|}
-    | {|+rotateY: string|}
-    | {|+rotateZ: string|}
+    | {|+rotate: string | AnimatedNode|}
+    | {|+rotateX: string | AnimatedNode|}
+    | {|+rotateY: string | AnimatedNode|}
+    | {|+rotateZ: string | AnimatedNode|}
     | {|+scale: number | AnimatedNode|}
     | {|+scaleX: number | AnimatedNode|}
     | {|+scaleY: number | AnimatedNode|}
diff --git a/Libraries/UTFSequence.js b/Libraries/UTFSequence.js
index f1e9e28e505e..5c450cd2bdcf 100644
--- a/Libraries/UTFSequence.js
+++ b/Libraries/UTFSequence.js
@@ -20,6 +20,7 @@ const deepFreezeAndThrowOnMutationInDev = require('deepFreezeAndThrowOnMutationI
  *  - Less chance of typos.
  */
 const UTFSequence = deepFreezeAndThrowOnMutationInDev({
+  BOM: '\ufeff', // byte order mark
   BULLET: '\u2022', // bullet: &#8226;
   BULLET_SP: '\u00A0\u2022\u00A0', // &nbsp;&#8226;&nbsp;
   MIDDOT: '\u00B7', // normal middle dot: &middot;
@@ -31,6 +32,8 @@ const UTFSequence = deepFreezeAndThrowOnMutationInDev({
   NDASH_SP: '\u00A0\u2013\u00A0', // &nbsp;&ndash;&nbsp;
   NBSP: '\u00A0', // non-breaking space: &nbsp;
   PIZZA: '\uD83C\uDF55',
+  TRIANGLE_LEFT: '\u25c0', // black left-pointing triangle
+  TRIANGLE_RIGHT: '\u25b6', // black right-pointing triangle
 });
 
 module.exports = UTFSequence;
diff --git a/Libraries/YellowBox/Data/YellowBoxCategory.js b/Libraries/YellowBox/Data/YellowBoxCategory.js
new file mode 100644
index 000000000000..5e22fa96bdf7
--- /dev/null
+++ b/Libraries/YellowBox/Data/YellowBoxCategory.js
@@ -0,0 +1,146 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const React = require('React');
+const Text = require('Text');
+const UTFSequence = require('UTFSequence');
+
+const stringifySafe = require('stringifySafe');
+
+import type {TextStyleProp} from 'StyleSheet';
+
+export type Category = string;
+export type Message = $ReadOnly<{|
+  content: string,
+  substitutions: $ReadOnlyArray<
+    $ReadOnly<{|
+      length: number,
+      offset: number,
+    |}>,
+  >,
+|}>;
+
+const SUBSTITUTION = UTFSequence.BOM + '%s';
+
+const YellowBoxCategory = {
+  parse(
+    args: $ReadOnlyArray<mixed>,
+  ): $ReadOnly<{|
+    category: Category,
+    message: Message,
+  |}> {
+    const categoryParts = [];
+    const contentParts = [];
+    const substitutionOffsets = [];
+
+    const remaining = [...args];
+
+    if (typeof remaining[0] === 'string') {
+      const formatString = String(remaining.shift());
+      const formatStringParts = formatString.split('%s');
+      const substitutionCount = formatStringParts.length - 1;
+      const substitutions = remaining.splice(0, substitutionCount);
+
+      let categoryString = '';
+      let contentString = '';
+
+      let substitutionIndex = 0;
+      for (const formatStringPart of formatStringParts) {
+        categoryString += formatStringPart;
+        contentString += formatStringPart;
+
+        if (substitutionIndex < substitutionCount) {
+          if (substitutionIndex < substitutions.length) {
+            const substitution = stringifySafe(
+              substitutions[substitutionIndex],
+            );
+            substitutionOffsets.push({
+              length: substitution.length,
+              offset: contentString.length,
+            });
+
+            categoryString += SUBSTITUTION;
+            contentString += substitution;
+          } else {
+            substitutionOffsets.push({
+              length: 2,
+              offset: contentString.length,
+            });
+
+            categoryString += '%s';
+            contentString += '%s';
+          }
+
+          substitutionIndex++;
+        }
+      }
+
+      categoryParts.push(categoryString);
+      contentParts.push(contentString);
+    }
+
+    const remainingArgs = remaining.map(stringifySafe);
+    categoryParts.push(...remainingArgs);
+    contentParts.push(...remainingArgs);
+
+    return {
+      category: categoryParts.join(' '),
+      message: {
+        content: contentParts.join(' '),
+        substitutions: substitutionOffsets,
+      },
+    };
+  },
+
+  render(
+    {content, substitutions}: Message,
+    substitutionStyle: TextStyleProp,
+  ): React.Node {
+    const elements = [];
+
+    const lastOffset = substitutions.reduce(
+      (prevOffset, substitution, index) => {
+        const key = String(index);
+
+        if (substitution.offset > prevOffset) {
+          const prevPart = content.substr(
+            prevOffset,
+            substitution.offset - prevOffset,
+          );
+          elements.push(<Text key={key}>{prevPart}</Text>);
+        }
+
+        const substititionPart = content.substr(
+          substitution.offset,
+          substitution.length,
+        );
+        elements.push(
+          <Text key={key + '.5'} style={substitutionStyle}>
+            {substititionPart}
+          </Text>,
+        );
+
+        return substitution.offset + substitution.length;
+      },
+      0,
+    );
+
+    if (lastOffset < content.length - 1) {
+      const lastPart = content.substr(lastOffset);
+      elements.push(<Text key="-1">{lastPart}</Text>);
+    }
+
+    return elements;
+  },
+};
+
+module.exports = YellowBoxCategory;
diff --git a/Libraries/YellowBox/Data/YellowBoxRegistry.js b/Libraries/YellowBox/Data/YellowBoxRegistry.js
new file mode 100644
index 000000000000..9c8e11079db5
--- /dev/null
+++ b/Libraries/YellowBox/Data/YellowBoxRegistry.js
@@ -0,0 +1,141 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const YellowBoxWarning = require('YellowBoxWarning');
+
+import type {Category} from 'YellowBoxCategory';
+
+export type Registry = Map<Category, $ReadOnlyArray<YellowBoxWarning>>;
+
+export type Observer = (registry: Registry) => void;
+
+export type Subscription = $ReadOnly<{|
+  unsubscribe: () => void,
+|}>;
+
+const observers: Set<{observer: Observer}> = new Set();
+const ignorePatterns: Set<string> = new Set();
+const registry: Registry = new Map();
+
+let disabled = false;
+let projection = new Map();
+let updateTimeout = null;
+
+function isWarningIgnored(warning: YellowBoxWarning): boolean {
+  for (const pattern of ignorePatterns) {
+    if (warning.message.content.includes(pattern)) {
+      return true;
+    }
+  }
+  return false;
+}
+
+function handleUpdate(): void {
+  projection = new Map();
+  if (!disabled) {
+    for (const [category, warnings] of registry) {
+      const filtered = warnings.filter(warning => !isWarningIgnored(warning));
+      if (filtered.length > 0) {
+        projection.set(category, filtered);
+      }
+    }
+  }
+  if (updateTimeout == null) {
+    updateTimeout = setImmediate(() => {
+      updateTimeout = null;
+      for (const {observer} of observers) {
+        observer(projection);
+      }
+    });
+  }
+}
+
+const YellowBoxRegistry = {
+  add({
+    args,
+    framesToPop,
+  }: $ReadOnly<{|
+    args: $ReadOnlyArray<mixed>,
+    framesToPop: number,
+  |}>): void {
+    if (typeof args[0] === 'string' && args[0].startsWith('(ADVICE)')) {
+      return;
+    }
+    const {category, message, stack} = YellowBoxWarning.parse({
+      args,
+      framesToPop: framesToPop + 1,
+    });
+
+    let warnings = registry.get(category);
+    if (warnings == null) {
+      warnings = [];
+    }
+    warnings = [...warnings, new YellowBoxWarning(message, stack)];
+
+    registry.delete(category);
+    registry.set(category, warnings);
+
+    handleUpdate();
+  },
+
+  delete(category: Category): void {
+    if (registry.has(category)) {
+      registry.delete(category);
+      handleUpdate();
+    }
+  },
+
+  clear(): void {
+    if (registry.size > 0) {
+      registry.clear();
+      handleUpdate();
+    }
+  },
+
+  addIgnorePatterns(patterns: $ReadOnlyArray<string>): void {
+    const newPatterns = patterns.filter(
+      pattern => !ignorePatterns.has(pattern),
+    );
+    if (newPatterns.length === 0) {
+      return;
+    }
+    for (const pattern of newPatterns) {
+      ignorePatterns.add(pattern);
+    }
+    handleUpdate();
+  },
+
+  setDisabled(value: boolean): void {
+    if (value === disabled) {
+      return;
+    }
+    disabled = value;
+    handleUpdate();
+  },
+
+  isDisabled(): boolean {
+    return disabled;
+  },
+
+  observe(observer: Observer): Subscription {
+    const subscription = {observer};
+    observers.add(subscription);
+    observer(projection);
+    return {
+      unsubscribe(): void {
+        observers.delete(subscription);
+      },
+    };
+  },
+};
+
+module.exports = YellowBoxRegistry;
diff --git a/Libraries/YellowBox/Data/YellowBoxSymbolication.js b/Libraries/YellowBox/Data/YellowBoxSymbolication.js
new file mode 100644
index 000000000000..c97b52857ca8
--- /dev/null
+++ b/Libraries/YellowBox/Data/YellowBoxSymbolication.js
@@ -0,0 +1,75 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const symbolicateStackTrace = require('symbolicateStackTrace');
+
+import type {StackFrame} from 'parseErrorStack';
+
+type CacheKey = string;
+
+export type Stack = Array<StackFrame>;
+
+const cache: Map<CacheKey, Promise<Stack>> = new Map();
+
+const YellowBoxSymbolication = {
+  symbolicate(stack: Stack): Promise<Stack> {
+    const key = getCacheKey(stack);
+
+    let promise = cache.get(key);
+    if (promise == null) {
+      promise = symbolicateStackTrace(stack).then(sanitize);
+      cache.set(key, promise);
+    }
+
+    return promise;
+  },
+};
+
+const getCacheKey = (stack: Stack): CacheKey => {
+  return JSON.stringify(stack);
+};
+
+/**
+ * Sanitize because sometimes, `symbolicateStackTrace` gives us invalid values.
+ */
+const sanitize = (maybeStack: mixed): Stack => {
+  if (!Array.isArray(maybeStack)) {
+    throw new Error('Expected stack to be an array.');
+  }
+  const stack = [];
+  for (const maybeFrame of maybeStack) {
+    if (typeof maybeFrame !== 'object' || maybeFrame == null) {
+      throw new Error('Expected each stack frame to be an object.');
+    }
+    if (typeof maybeFrame.column !== 'number' && maybeFrame.column != null) {
+      throw new Error('Expected stack frame `column` to be a nullable number.');
+    }
+    if (typeof maybeFrame.file !== 'string') {
+      throw new Error('Expected stack frame `file` to be a string.');
+    }
+    if (typeof maybeFrame.lineNumber !== 'number') {
+      throw new Error('Expected stack frame `lineNumber` to be a number.');
+    }
+    if (typeof maybeFrame.methodName !== 'string') {
+      throw new Error('Expected stack frame `methodName` to be a string.');
+    }
+    stack.push({
+      column: maybeFrame.column,
+      file: maybeFrame.file,
+      lineNumber: maybeFrame.lineNumber,
+      methodName: maybeFrame.methodName,
+    });
+  }
+  return stack;
+};
+
+module.exports = YellowBoxSymbolication;
diff --git a/Libraries/YellowBox/Data/YellowBoxWarning.js b/Libraries/YellowBox/Data/YellowBoxWarning.js
new file mode 100644
index 000000000000..6841bc9da329
--- /dev/null
+++ b/Libraries/YellowBox/Data/YellowBoxWarning.js
@@ -0,0 +1,108 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ * @format
+ */
+
+'use strict';
+
+const YellowBoxCategory = require('YellowBoxCategory');
+const YellowBoxSymbolication = require('YellowBoxSymbolication');
+
+const parseErrorStack = require('parseErrorStack');
+
+import type {Category, Message} from 'YellowBoxCategory';
+import type {Stack} from 'YellowBoxSymbolication';
+
+export type SymbolicationRequest = $ReadOnly<{|
+  abort: () => void,
+|}>;
+
+class YellowBoxWarning {
+  static parse({
+    args,
+    framesToPop,
+  }: $ReadOnly<{|
+    args: $ReadOnlyArray<mixed>,
+    framesToPop: number,
+  |}>): {|
+    category: Category,
+    message: Message,
+    stack: Stack,
+  |} {
+    return {
+      ...YellowBoxCategory.parse(args),
+      stack: createStack({framesToPop: framesToPop + 1}),
+    };
+  }
+
+  message: Message;
+  stack: Stack;
+  symbolicated:
+    | $ReadOnly<{|error: null, stack: null, status: 'NONE'|}>
+    | $ReadOnly<{|error: null, stack: null, status: 'PENDING'|}>
+    | $ReadOnly<{|error: null, stack: Stack, status: 'COMPLETE'|}>
+    | $ReadOnly<{|error: Error, stack: null, status: 'FAILED'|}> = {
+    error: null,
+    stack: null,
+    status: 'NONE',
+  };
+
+  constructor(message: Message, stack: Stack) {
+    this.message = message;
+    this.stack = stack;
+  }
+
+  getAvailableStack(): Stack {
+    return this.symbolicated.status === 'COMPLETE'
+      ? this.symbolicated.stack
+      : this.stack;
+  }
+
+  symbolicate(callback: () => void): SymbolicationRequest {
+    let aborted = false;
+
+    if (this.symbolicated.status !== 'COMPLETE') {
+      const updateStatus = (error: ?Error, stack: ?Stack): void => {
+        if (error != null) {
+          this.symbolicated = {error, stack: null, status: 'FAILED'};
+        } else if (stack != null) {
+          this.symbolicated = {error: null, stack, status: 'COMPLETE'};
+        } else {
+          this.symbolicated = {error: null, stack: null, status: 'PENDING'};
+        }
+        if (!aborted) {
+          callback();
+        }
+      };
+
+      updateStatus(null, null);
+      YellowBoxSymbolication.symbolicate(this.stack).then(
+        stack => {
+          updateStatus(null, stack);
+        },
+        error => {
+          updateStatus(error, null);
+        },
+      );
+    }
+
+    return {
+      abort(): void {
+        aborted = true;
+      },
+    };
+  }
+}
+
+function createStack({framesToPop}: $ReadOnly<{|framesToPop: number|}>): Stack {
+  const error: any = new Error();
+  error.framesToPop = framesToPop + 1;
+  return parseErrorStack(error);
+}
+
+module.exports = YellowBoxWarning;
diff --git a/Libraries/YellowBox/Data/__tests__/YellowBoxCategory-test.js b/Libraries/YellowBox/Data/__tests__/YellowBoxCategory-test.js
new file mode 100644
index 000000000000..5c7ab61b409a
--- /dev/null
+++ b/Libraries/YellowBox/Data/__tests__/YellowBoxCategory-test.js
@@ -0,0 +1,100 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @emails oncall+react_native
+ * @format
+ * @flow strict-local
+ */
+
+'use strict';
+
+const YellowBoxCategory = require('YellowBoxCategory');
+
+describe('YellowBoxCategory', () => {
+  it('parses strings', () => {
+    expect(YellowBoxCategory.parse(['A'])).toEqual({
+      category: 'A',
+      message: {
+        content: 'A',
+        substitutions: [],
+      },
+    });
+  });
+
+  it('parses strings with arguments', () => {
+    expect(YellowBoxCategory.parse(['A', 'B', 'C'])).toEqual({
+      category: 'A "B" "C"',
+      message: {
+        content: 'A "B" "C"',
+        substitutions: [],
+      },
+    });
+  });
+
+  it('parses formatted strings', () => {
+    expect(YellowBoxCategory.parse(['%s', 'A'])).toEqual({
+      category: '\ufeff%s',
+      message: {
+        content: '"A"',
+        substitutions: [
+          {
+            length: 3,
+            offset: 0,
+          },
+        ],
+      },
+    });
+  });
+
+  it('parses formatted strings with insufficient arguments', () => {
+    expect(YellowBoxCategory.parse(['%s %s', 'A'])).toEqual({
+      category: '\ufeff%s %s',
+      message: {
+        content: '"A" %s',
+        substitutions: [
+          {
+            length: 3,
+            offset: 0,
+          },
+          {
+            length: 2,
+            offset: 4,
+          },
+        ],
+      },
+    });
+  });
+
+  it('parses formatted strings with excess arguments', () => {
+    expect(YellowBoxCategory.parse(['%s', 'A', 'B'])).toEqual({
+      category: '\ufeff%s "B"',
+      message: {
+        content: '"A" "B"',
+        substitutions: [
+          {
+            length: 3,
+            offset: 0,
+          },
+        ],
+      },
+    });
+  });
+
+  it('treats "%s" in arguments as literals', () => {
+    expect(YellowBoxCategory.parse(['%s', '%s', 'A'])).toEqual({
+      category: '\ufeff%s "A"',
+      message: {
+        content: '"%s" "A"',
+        substitutions: [
+          {
+            length: 4,
+            offset: 0,
+          },
+        ],
+      },
+    });
+  });
+});
diff --git a/Libraries/YellowBox/Data/__tests__/YellowBoxRegistry-test.js b/Libraries/YellowBox/Data/__tests__/YellowBoxRegistry-test.js
new file mode 100644
index 000000000000..af596ce4ee6a
--- /dev/null
+++ b/Libraries/YellowBox/Data/__tests__/YellowBoxRegistry-test.js
@@ -0,0 +1,267 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @emails oncall+react_native
+ * @format
+ * @flow strict-local
+ */
+
+'use strict';
+
+const YellowBoxCategory = require('YellowBoxCategory');
+const YellowBoxRegistry = require('YellowBoxRegistry');
+
+const registry = () => {
+  const observer = jest.fn();
+  YellowBoxRegistry.observe(observer).unsubscribe();
+  return observer.mock.calls[0][0];
+};
+
+const observe = () => {
+  const observer = jest.fn();
+  return {
+    observer,
+    subscription: YellowBoxRegistry.observe(observer),
+  };
+};
+
+describe('YellowBoxRegistry', () => {
+  beforeEach(() => {
+    jest.resetModules();
+  });
+
+  it('adds and deletes warnings', () => {
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    const {category: categoryA} = YellowBoxCategory.parse(['A']);
+
+    expect(registry().size).toBe(1);
+    expect(registry().get(categoryA)).not.toBe(undefined);
+
+    YellowBoxRegistry.delete(categoryA);
+    expect(registry().size).toBe(0);
+    expect(registry().get(categoryA)).toBe(undefined);
+  });
+
+  it('clears all warnings', () => {
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['B'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['C'], framesToPop: 0});
+
+    expect(registry().size).toBe(3);
+
+    YellowBoxRegistry.clear();
+    expect(registry().size).toBe(0);
+  });
+
+  it('sorts warnings in chronological order', () => {
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['B'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['C'], framesToPop: 0});
+
+    const {category: categoryA} = YellowBoxCategory.parse(['A']);
+    const {category: categoryB} = YellowBoxCategory.parse(['B']);
+    const {category: categoryC} = YellowBoxCategory.parse(['C']);
+
+    expect(Array.from(registry().keys())).toEqual([
+      categoryA,
+      categoryB,
+      categoryC,
+    ]);
+
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+
+    // Expect `A` to be hoisted to the end of the registry.
+    expect(Array.from(registry().keys())).toEqual([
+      categoryB,
+      categoryC,
+      categoryA,
+    ]);
+  });
+
+  it('ignores warnings matching patterns', () => {
+    YellowBoxRegistry.add({args: ['A!'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['B?'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['C!'], framesToPop: 0});
+    expect(registry().size).toBe(3);
+
+    YellowBoxRegistry.addIgnorePatterns(['!']);
+    expect(registry().size).toBe(1);
+
+    YellowBoxRegistry.addIgnorePatterns(['?']);
+    expect(registry().size).toBe(0);
+  });
+
+  it('ignores all warnings when disabled', () => {
+    YellowBoxRegistry.add({args: ['A!'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['B?'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['C!'], framesToPop: 0});
+    expect(registry().size).toBe(3);
+
+    YellowBoxRegistry.setDisabled(true);
+    expect(registry().size).toBe(0);
+
+    YellowBoxRegistry.setDisabled(false);
+    expect(registry().size).toBe(3);
+  });
+
+  it('groups warnings by simple categories', () => {
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    expect(registry().size).toBe(1);
+
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    expect(registry().size).toBe(1);
+
+    YellowBoxRegistry.add({args: ['B'], framesToPop: 0});
+    expect(registry().size).toBe(2);
+  });
+
+  it('groups warnings by format string categories', () => {
+    YellowBoxRegistry.add({args: ['%s', 'A'], framesToPop: 0});
+    expect(registry().size).toBe(1);
+
+    YellowBoxRegistry.add({args: ['%s', 'B'], framesToPop: 0});
+    expect(registry().size).toBe(1);
+
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    expect(registry().size).toBe(2);
+
+    YellowBoxRegistry.add({args: ['B'], framesToPop: 0});
+    expect(registry().size).toBe(3);
+  });
+
+  it('groups warnings with consideration for arguments', () => {
+    YellowBoxRegistry.add({args: ['A', 'B'], framesToPop: 0});
+    expect(registry().size).toBe(1);
+
+    YellowBoxRegistry.add({args: ['A', 'B'], framesToPop: 0});
+    expect(registry().size).toBe(1);
+
+    YellowBoxRegistry.add({args: ['A', 'C'], framesToPop: 0});
+    expect(registry().size).toBe(2);
+
+    YellowBoxRegistry.add({args: ['%s', 'A', 'A'], framesToPop: 0});
+    expect(registry().size).toBe(3);
+
+    YellowBoxRegistry.add({args: ['%s', 'B', 'A'], framesToPop: 0});
+    expect(registry().size).toBe(3);
+
+    YellowBoxRegistry.add({args: ['%s', 'B', 'B'], framesToPop: 0});
+    expect(registry().size).toBe(4);
+  });
+
+  it('ignores warnings starting with "(ADVICE)"', () => {
+    YellowBoxRegistry.add({args: ['(ADVICE) ...'], framesToPop: 0});
+    expect(registry().size).toBe(0);
+  });
+
+  it('does not ignore warnings formatted to start with "(ADVICE)"', () => {
+    YellowBoxRegistry.add({args: ['%s ...', '(ADVICE)'], framesToPop: 0});
+    expect(registry().size).toBe(1);
+  });
+
+  it('immediately updates new observers', () => {
+    const {observer} = observe();
+
+    expect(observer.mock.calls.length).toBe(1);
+    expect(observer.mock.calls[0][0]).toBe(registry());
+  });
+
+  it('sends batched updates asynchoronously', () => {
+    const {observer} = observe();
+    expect(observer.mock.calls.length).toBe(1);
+
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    YellowBoxRegistry.add({args: ['B'], framesToPop: 0});
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(2);
+  });
+
+  it('stops sending updates to unsubscribed observers', () => {
+    const {observer, subscription} = observe();
+    subscription.unsubscribe();
+
+    expect(observer.mock.calls.length).toBe(1);
+    expect(observer.mock.calls[0][0]).toBe(registry());
+  });
+
+  it('updates observers when a warning is added or deleted', () => {
+    const {observer} = observe();
+    expect(observer.mock.calls.length).toBe(1);
+
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(2);
+
+    const {category: categoryA} = YellowBoxCategory.parse(['A']);
+    YellowBoxRegistry.delete(categoryA);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(3);
+
+    // Does nothing when category does not exist.
+    YellowBoxRegistry.delete(categoryA);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(3);
+  });
+
+  it('updates observers when cleared', () => {
+    const {observer} = observe();
+    expect(observer.mock.calls.length).toBe(1);
+
+    YellowBoxRegistry.add({args: ['A'], framesToPop: 0});
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(2);
+
+    YellowBoxRegistry.clear();
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(3);
+
+    // Does nothing when already empty.
+    YellowBoxRegistry.clear();
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(3);
+  });
+
+  it('updates observers when an ignore pattern is added', () => {
+    const {observer} = observe();
+    expect(observer.mock.calls.length).toBe(1);
+
+    YellowBoxRegistry.addIgnorePatterns(['?']);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(2);
+
+    YellowBoxRegistry.addIgnorePatterns(['!']);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(3);
+
+    // Does nothing for an existing ignore pattern.
+    YellowBoxRegistry.addIgnorePatterns(['!']);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(3);
+  });
+
+  it('updates observers when disabled or enabled', () => {
+    const {observer} = observe();
+    expect(observer.mock.calls.length).toBe(1);
+
+    YellowBoxRegistry.setDisabled(true);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(2);
+
+    // Does nothing when already disabled.
+    YellowBoxRegistry.setDisabled(true);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(2);
+
+    YellowBoxRegistry.setDisabled(false);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(3);
+
+    // Does nothing when already enabled.
+    YellowBoxRegistry.setDisabled(false);
+    jest.runAllImmediates();
+    expect(observer.mock.calls.length).toBe(3);
+  });
+});
diff --git a/Libraries/YellowBox/Data/__tests__/YellowBoxSymbolication-test.js b/Libraries/YellowBox/Data/__tests__/YellowBoxSymbolication-test.js
new file mode 100644
index 000000000000..c4ca0ad53188
--- /dev/null
+++ b/Libraries/YellowBox/Data/__tests__/YellowBoxSymbolication-test.js
@@ -0,0 +1,52 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @emails oncall+react_native
+ * @format
+ * @flow
+ */
+
+'use strict';
+
+import type {StackFrame} from 'parseErrorStack';
+
+jest.mock('symbolicateStackTrace');
+
+const YellowBoxSymbolication = require('YellowBoxSymbolication');
+
+const symbolicateStackTrace: JestMockFn<
+  $ReadOnlyArray<Array<StackFrame>>,
+  Promise<Array<StackFrame>>,
+> = (require('symbolicateStackTrace'): any);
+
+const createStack = methodNames =>
+  methodNames.map(methodName => ({
+    column: null,
+    file: 'file://path/to/file.js',
+    lineNumber: 1,
+    methodName,
+  }));
+
+describe('YellowBoxSymbolication', () => {
+  beforeEach(() => {
+    jest.resetModules();
+    symbolicateStackTrace.mockImplementation(async stack => stack);
+  });
+
+  it('symbolicates different stacks', () => {
+    YellowBoxSymbolication.symbolicate(createStack(['A', 'B', 'C']));
+    YellowBoxSymbolication.symbolicate(createStack(['D', 'E', 'F']));
+
+    expect(symbolicateStackTrace.mock.calls.length).toBe(2);
+  });
+
+  it('batch symbolicates equivalent stacks', () => {
+    YellowBoxSymbolication.symbolicate(createStack(['A', 'B', 'C']));
+    YellowBoxSymbolication.symbolicate(createStack(['A', 'B', 'C']));
+
+    expect(symbolicateStackTrace.mock.calls.length).toBe(1);
+  });
+});
diff --git a/Libraries/YellowBox/Data/__tests__/YellowBoxWarning-test.js b/Libraries/YellowBox/Data/__tests__/YellowBoxWarning-test.js
new file mode 100644
index 000000000000..8918741b1190
--- /dev/null
+++ b/Libraries/YellowBox/Data/__tests__/YellowBoxWarning-test.js
@@ -0,0 +1,126 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @emails oncall+react_native
+ * @format
+ * @flow
+ */
+
+'use strict';
+
+import type {StackFrame} from 'parseErrorStack';
+
+jest.mock('YellowBoxSymbolication');
+
+const YellowBoxSymbolication: {|
+  symbolicate: JestMockFn<
+    $ReadOnlyArray<Array<StackFrame>>,
+    Promise<Array<StackFrame>>,
+  >,
+|} = (require('YellowBoxSymbolication'): any);
+const YellowBoxWarning = require('YellowBoxWarning');
+
+const createStack = methodNames =>
+  methodNames.map(methodName => ({
+    column: null,
+    file: 'file://path/to/file.js',
+    lineNumber: 1,
+    methodName,
+  }));
+
+describe('YellowBoxWarning', () => {
+  beforeEach(() => {
+    jest.resetModules();
+
+    YellowBoxSymbolication.symbolicate.mockImplementation(async stack =>
+      createStack(stack.map(frame => `S(${frame.methodName})`)),
+    );
+  });
+
+  it('starts without a symbolicated stack', () => {
+    const warning = new YellowBoxWarning(
+      {content: '...', substitutions: []},
+      createStack(['A', 'B', 'C']),
+    );
+
+    expect(warning.symbolicated).toEqual({
+      error: null,
+      stack: null,
+      status: 'NONE',
+    });
+  });
+
+  it('updates when symbolication is in progress', () => {
+    const warning = new YellowBoxWarning(
+      {content: '...', substitutions: []},
+      createStack(['A', 'B', 'C']),
+    );
+    const callback = jest.fn();
+    warning.symbolicate(callback);
+
+    expect(callback.mock.calls.length).toBe(1);
+    expect(warning.symbolicated).toEqual({
+      error: null,
+      stack: null,
+      status: 'PENDING',
+    });
+  });
+
+  it('updates when symbolication finishes', () => {
+    const warning = new YellowBoxWarning(
+      {content: '...', substitutions: []},
+      createStack(['A', 'B', 'C']),
+    );
+    const callback = jest.fn();
+    warning.symbolicate(callback);
+
+    jest.runAllTicks();
+
+    expect(callback.mock.calls.length).toBe(2);
+    expect(warning.symbolicated).toEqual({
+      error: null,
+      stack: createStack(['S(A)', 'S(B)', 'S(C)']),
+      status: 'COMPLETE',
+    });
+  });
+
+  it('updates when symbolication fails', () => {
+    const error = new Error('...');
+    YellowBoxSymbolication.symbolicate.mockImplementation(async stack => {
+      throw error;
+    });
+
+    const warning = new YellowBoxWarning(
+      {content: '...', substitutions: []},
+      createStack(['A', 'B', 'C']),
+    );
+    const callback = jest.fn();
+    warning.symbolicate(callback);
+
+    jest.runAllTicks();
+
+    expect(callback.mock.calls.length).toBe(2);
+    expect(warning.symbolicated).toEqual({
+      error,
+      stack: null,
+      status: 'FAILED',
+    });
+  });
+
+  it('does not update aborted requests', () => {
+    const warning = new YellowBoxWarning(
+      {content: '...', substitutions: []},
+      createStack(['A', 'B', 'C']),
+    );
+    const callback = jest.fn();
+    const request = warning.symbolicate(callback);
+    request.abort();
+
+    jest.runAllTicks();
+
+    expect(callback.mock.calls.length).toBe(1);
+  });
+});
diff --git a/Libraries/YellowBox/UI/YellowBoxButton.js b/Libraries/YellowBox/UI/YellowBoxButton.js
new file mode 100644
index 000000000000..6ea9f4525822
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxButton.js
@@ -0,0 +1,53 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const YellowBoxPressable = require('YellowBoxPressable');
+const YellowBoxStyle = require('YellowBoxStyle');
+
+import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
+
+type Props = $ReadOnly<{|
+  hitSlop?: ?EdgeInsetsProp,
+  label: string,
+  onPress: () => void,
+|}>;
+
+const YellowBoxButton = (props: Props): React.Node => (
+  <YellowBoxPressable
+    hitSlop={props.hitSlop}
+    onPress={props.onPress}
+    style={styles.root}>
+    <Text numberOfLines={1} style={styles.label}>
+      {props.label}
+    </Text>
+  </YellowBoxPressable>
+);
+
+const styles = StyleSheet.create({
+  root: {
+    borderRadius: 14,
+    height: 28,
+    justifyContent: 'center',
+    paddingHorizontal: 12,
+  },
+  label: {
+    color: YellowBoxStyle.getTextColor(1),
+    fontSize: 12,
+    includeFontPadding: false,
+    lineHeight: 16,
+  },
+});
+
+module.exports = YellowBoxButton;
diff --git a/Libraries/YellowBox/UI/YellowBoxImageSource.js b/Libraries/YellowBox/UI/YellowBoxImageSource.js
new file mode 100644
index 000000000000..dca95fa82316
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxImageSource.js
@@ -0,0 +1,52 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const PixelRatio = require('PixelRatio');
+
+const scale = PixelRatio.get();
+
+/**
+ * We use inline images for YellowBox in order to avoid display latency due to
+ * resource contention with symbolicating stack traces.
+ *
+ * The following steps were used to create these:
+ *
+ *   1. Download SVG files from: https://feathericons.com
+ *   2. Rasterize SVG files to PNG files at 16dp, 36dp, and 48dp.
+ *   3. Convert to Base64: https://www.google.com/search?q=base64+image+encoder
+ *
+ * @see https://github.com/feathericons/feather
+ * @copyright 2013-2017 Cole Bemis
+ * @license MIT
+ */
+const YellowBoxImageSource = {
+  alertTriangle:
+    scale > 2
+      ? 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAAwCAYAAABXAvmHAAAB60lEQVRoge2Z3W3DIBSFj9oFPAIjZARGyAiMkBHuJh4hI2QEj5AR3Me+tQ91JALHmD8bKvmTkCr5Auc6/kzUACcnRXzuvL4GoAB8Afjeea9qXADcAfw4475c65orgBl++NeYl5ouUQiHt5tQTRJuwB6b5zLY49QVGn7I0bo+kuv60IQbuHf5CWCIqOkCgX93maia1MkRAUMo+OI+AvUPp7a50EzcUCBF6psJrUkYiZgnZJ7eId8mMeIyhpW5hyLw72LKCXsl86VqwgAKceKapW5e/nZpJnSsuHaTM7muyDq7C63JprJS69YxhNTpSlkpKeLGNHCo0EJChcSNaQA4SGiFtBMXJFSI3YVOPXFB6kMoUl9NaE0Wl4h5KQ0AOwqde+KmNrCL0EKCxJ64qQ0AlYVWSBfXZusgW6Oa0Dni2hiEv0qsoci+yUJrsoikLlKAkP11ygK54taiSOgb/O5b/DMqS+gBZeLWJlnoEX7XwQkBDPIktlEkz7hWrEmxZG4M5L9GXYTk0qxwcopKxa3VABN6cosM/C5LxTUof4ReMKHf1nRlaSnuGsGM7kfU4w8RF5Bz4aNlokLe/HQ/ngl9/Qih4L9k3h4hA1+S3odxu3Q77Hl4r1Hg75n6D01M2Difbp02Mi3ZTk5OLH4BUyEtOlDYuK0AAAAASUVORK5CYII='
+      : scale > 1
+        ? 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAABVklEQVRYheWX4U3DMBBGH4gBMoJHyAgeoSNkAxjBG5QNOkJHCGzQDcoGZQP4gY3Oqe1cEscS4pNOqs9Jvqvv6ZrCf9fDhnutD4A3H810Br4mcW5l7hLmIdze5mZi+OJD5syeBYzC6CjyR5Ef9zI/CJMb0Im9zufC/qG2eQdchcGQuGYQ+9dJgZvl0B2xbJGrZW6IIevFXp9YVwcyB540syJfFcgSeJb0cVcDcg68XAFQCUhH+ShLBcBGIA158LQFqIB8zBRwEp9fgctcxQld/L2pZxZVAk/KkucjaDGQmoknrz35KEE2sABIRxm8tVIBaZgHb61UQOYmXk7aFgQVJ6QWPCnLAriYAVILnpTxD7yh/9EZiIEE4m+y29uMkGy1nQ6i9wYFRB5PwKdYP/v1msmnUe89gn695bG0iqjdXeMiRu9599csvGKZ0jlu0Ac/7d2rxX9Q37HW6QfX/ZguAAAAAElFTkSuQmCC'
+        : 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAvUlEQVQ4jbWT4Q3CIBCFP40DdANxg24gIzhKuwEjuIFxAkcwTtARGicoG+iPXlMCB8UfvoQc4e7ePV4A/ogWuMlqc0W7AsEo0QMNcPplugMmwMia5KwKWkNIuIkHq3wLXGQ/Sq4IC3wkLpOfmZyKeEpIEKsDYB8VN0Afkfpg30uNiycbdKcNqXEOxdBEWoEAoqta8uZ0iqqkxwGDUrSFAXAHZpOWd/+ubD5Kz335Cx1wZna4Bh54AddauVl8ARfCLO9Xq7xGAAAAAElFTkSuQmCC',
+  check:
+    scale > 2
+      ? 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAAwCAYAAABXAvmHAAAAqElEQVRoge3YTQ7CIBRF4bPUu/8JS6gTSaqilh95vuR+CaO2cGgYNAUzMzOzFgHlPhRaMkDAcRoltKaTeIxPtQHxGn+Q5AgJx8cQjo8hHB9DOP76Yiu/RcTmN18WLiQCjs3zBkYXVGOeLWd+xcIr5pgyEzDz7FIjISPP/FRPUM+9W4nvYVfuCSXeB3669ldEOzRFfCUSx1cicXwlEsdXIvEPKDMzM7PMbtugw3XTpNA2AAAAAElFTkSuQmCC'
+      : scale > 1
+        ? 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAAAf0lEQVRYhe2UvQ2AIBQGL3EBR3AESkv3bxxFN8DmWUgwvkI+En1X0cBd+IMg+DuDyDMCs413kfMiX4EMbD3l8oCaPIU85B4mYLEF5XJscrYFPRGvb/sZ4IlocubJGdH0wj1FSG77XYT0qdUi5O+8jOjyyZQRUnkZ0UUeBMF3OQC/0VsyGlxligAAAABJRU5ErkJggg=='
+        : 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAASElEQVQ4jWNgGJHAgIGBIYESze8ZGBjWU6L5PAMDgwBNNCdAFZJt83qoQmRDSHK2AFQhzBCy/IxsCNkBJsDAwLAfiknWPBIBAETPFeuA4fr6AAAAAElFTkSuQmCC',
+  loader:
+    scale > 2
+      ? 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAAwCAYAAABXAvmHAAABXElEQVRoge2a3W3DMAyEr+0CHkGjaISOcKN4k6zQETpCR+gGzgbpQ10kcamIpKQ6avQBBPxg3pHwL2UDg/8LASxrcNdKnCwATmssrUyeWgnju/DmXs8tRP+Sh2kgAJga1rFlWj2rcMD5YqQh77QJLbzIORjyRIJQCJW5ngYo5AVlrsgkCGqbsDbAhFfxqZsSZibP0oDXQ43HQPsg82i7sBoR+VcJq2YxKcPo0IoJLRZXmYGC6ezQmQUdVqhPBVH/CNBTSMkLVlzjA8Bbocb7GoPBoADi+umZilYzbrG/JrnljOvy734iu4To/BQaDB6Rl4LciPPF9Lmjhgvi+s7w6tCIGw3WKS0P8fvWNjt0ZkGHFeq7CQXTbkZKGg2JOxrqPUZ3s6ziNdju38IjS/dLi0EQpDLX2gDQYHEX6Hx5/YcA+6H0NgAYPnCMj3x7Mxq4wTGx3Q1E578aDDR8AX0mOGD6BEN/AAAAAElFTkSuQmCC'
+      : scale > 1
+        ? 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAABN0lEQVRYhe2WzU3EMBCFP34KyJEjJaQDXAIlJJ24BSow2wEdhHSwJSwd7JHbcmC0mOxMnDiWDIInWbHkN29exo4n8IvRAEFGU8OAA04yulyR60Jm7msbyIZloAMGwBfI4UWrWxM08LW/weC4iOMNTog4g0awKjBG827GxBwC3996NHizAifsSrTRmlsZm23CT9adktyXSq6ZUPdxgiXnZzW8CLcLuC3lvqA/gCt5NtjlPQL7TP0Wu1HtRRu4PO3T4TKTz2kG+AG9IN6CR/Su9iojBw69egfghWgL/pGCp+JFVPUqTjWjlsuqeAo1o6rt2C8QcNiV0UxoHPMieojmz0CfMKyhl1hN84xbI3gnz5Ftp7kH3iT5LsFdDUf6pzSJ6r2glIFDbuDNhqRH4I7Pvv4EvG/QqocP2Jh/xzzX/zUAAAAASUVORK5CYII='
+        : 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAsklEQVQ4jaWTYRHCMAyFP7gJmIQ6oChgEpBQKXMwC3MADpAAEiphDuBHC4QuDRu8u9ylyWtem7Rgw2X7GT1wsghb4beAVzhtsfYyJgs44AoEQzBkjrMId1HkKPwyZ6oMSnxYsnk1NqT7yMo34Fzhd9meGJvs7Hh3NhqCLXDI/rT0lKsR+KOJgc9RdaRRarkZvELogYsi8HqxjUhGYE+aQg1jzketwFTZXHbbEpjB8eU7PwAbLiJz46707gAAAABJRU5ErkJggg==',
+};
+
+module.exports = YellowBoxImageSource;
diff --git a/Libraries/YellowBox/UI/YellowBoxInspector.js b/Libraries/YellowBox/UI/YellowBoxInspector.js
new file mode 100644
index 000000000000..aa0c742d77ff
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxInspector.js
@@ -0,0 +1,190 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const Platform = require('Platform');
+const React = require('React');
+const ScrollView = require('ScrollView');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const View = require('View');
+const YellowBoxCategory = require('YellowBoxCategory');
+const YellowBoxInspectorFooter = require('YellowBoxInspectorFooter');
+const YellowBoxInspectorHeader = require('YellowBoxInspectorHeader');
+const YellowBoxInspectorSourceMapStatus = require('YellowBoxInspectorSourceMapStatus');
+const YellowBoxInspectorStackFrame = require('YellowBoxInspectorStackFrame');
+const YellowBoxStyle = require('YellowBoxStyle');
+
+const openFileInEditor = require('openFileInEditor');
+
+import type YellowBoxWarning from 'YellowBoxWarning';
+import type {SymbolicationRequest} from 'YellowBoxWarning';
+
+type Props = $ReadOnly<{|
+  onDismiss: () => void,
+  onMinimize: () => void,
+  warnings: $ReadOnlyArray<YellowBoxWarning>,
+|}>;
+
+type State = {|
+  selectedIndex: number,
+|};
+
+class YellowBoxInspector extends React.Component<Props, State> {
+  _symbolication: ?SymbolicationRequest;
+
+  state = {
+    selectedIndex: 0,
+  };
+
+  render(): React.Node {
+    const {warnings} = this.props;
+    const {selectedIndex} = this.state;
+
+    const warning = warnings[selectedIndex];
+
+    return (
+      <View style={styles.root}>
+        <YellowBoxInspectorHeader
+          onSelectIndex={this._handleSelectIndex}
+          selectedIndex={selectedIndex}
+          warnings={warnings}
+        />
+        <ScrollView
+          contentContainerStyle={styles.bodyContent}
+          key={selectedIndex}
+          style={styles.body}>
+          <View>
+            <View style={styles.bodyHeading}>
+              <Text style={styles.bodyHeadingText}>Warning</Text>
+            </View>
+            <Text style={styles.bodyText}>
+              {YellowBoxCategory.render(
+                warning.message,
+                styles.substitutionText,
+              )}
+            </Text>
+          </View>
+          <View style={styles.bodySection}>
+            <View style={styles.bodyHeading}>
+              <Text style={styles.bodyHeadingText}>Stack</Text>
+              <YellowBoxInspectorSourceMapStatus
+                status={warning.symbolicated.status}
+              />
+            </View>
+            {warning.getAvailableStack().map((frame, index) => (
+              <YellowBoxInspectorStackFrame
+                key={index}
+                frame={frame}
+                onPress={
+                  warning.symbolicated.status === 'COMPLETE'
+                    ? () => {
+                        openFileInEditor(frame.file, frame.lineNumber);
+                      }
+                    : null
+                }
+              />
+            ))}
+          </View>
+        </ScrollView>
+        <YellowBoxInspectorFooter
+          onDismiss={this.props.onDismiss}
+          onMinimize={this.props.onMinimize}
+        />
+      </View>
+    );
+  }
+
+  componentDidMount(): void {
+    this._handleSymbolication();
+  }
+
+  componentDidUpdate(prevProps: Props, prevState: State): void {
+    if (
+      prevProps.warnings !== this.props.warnings ||
+      prevState.selectedIndex !== this.state.selectedIndex
+    ) {
+      this._cancelSymbolication();
+      this._handleSymbolication();
+    }
+  }
+
+  componentWillUnmount(): void {
+    this._cancelSymbolication();
+  }
+
+  _handleSymbolication(): void {
+    const warning = this.props.warnings[this.state.selectedIndex];
+    if (warning.symbolicated.status !== 'COMPLETE') {
+      this._symbolication = warning.symbolicate(() => {
+        this.forceUpdate();
+      });
+    }
+  }
+
+  _cancelSymbolication(): void {
+    if (this._symbolication != null) {
+      this._symbolication.abort();
+      this._symbolication = null;
+    }
+  }
+
+  _handleSelectIndex = (selectedIndex: number): void => {
+    this.setState({selectedIndex});
+  };
+}
+
+const styles = StyleSheet.create({
+  root: {
+    elevation: Platform.OS === 'android' ? Number.MAX_SAFE_INTEGER : undefined,
+    height: '100%',
+  },
+  body: {
+    backgroundColor: YellowBoxStyle.getBackgroundColor(0.95),
+    borderBottomColor: YellowBoxStyle.getDividerColor(0.95),
+    borderBottomWidth: StyleSheet.hairlineWidth,
+    borderTopColor: YellowBoxStyle.getDividerColor(0.95),
+    borderTopWidth: StyleSheet.hairlineWidth,
+    flex: 1,
+  },
+  bodyContent: {
+    paddingVertical: 12,
+  },
+  bodyHeading: {
+    alignItems: 'center',
+    flexDirection: 'row',
+    marginBottom: 6,
+    paddingHorizontal: 12,
+  },
+  bodyHeadingText: {
+    color: YellowBoxStyle.getTextColor(1),
+    flex: 1,
+    fontSize: 20,
+    fontWeight: '600',
+    includeFontPadding: false,
+    lineHeight: 28,
+  },
+  bodyText: {
+    color: YellowBoxStyle.getTextColor(1),
+    fontSize: 14,
+    includeFontPadding: false,
+    lineHeight: 18,
+    paddingHorizontal: 12,
+  },
+  substitutionText: {
+    color: YellowBoxStyle.getTextColor(0.6),
+  },
+  bodySection: {
+    marginTop: 20,
+  },
+});
+
+module.exports = YellowBoxInspector;
diff --git a/Libraries/YellowBox/UI/YellowBoxInspectorFooter.js b/Libraries/YellowBox/UI/YellowBoxInspectorFooter.js
new file mode 100644
index 000000000000..71a45702a6a8
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxInspectorFooter.js
@@ -0,0 +1,76 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const React = require('React');
+const SafeAreaView = require('SafeAreaView');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const View = require('View');
+const YellowBoxPressable = require('YellowBoxPressable');
+const YellowBoxStyle = require('YellowBoxStyle');
+
+type Props = $ReadOnly<{|
+  onDismiss: () => void,
+  onMinimize: () => void,
+|}>;
+
+const YellowBoxInspectorFooter = (props: Props): React.Node => (
+  <View style={styles.root}>
+    <YellowBoxPressable
+      backgroundColor={{
+        default: 'transparent',
+        pressed: YellowBoxStyle.getHighlightColor(1),
+      }}
+      onPress={props.onMinimize}
+      style={styles.button}>
+      <View style={styles.content}>
+        <Text style={styles.label}>Minimize</Text>
+      </View>
+      <SafeAreaView />
+    </YellowBoxPressable>
+    <YellowBoxPressable
+      backgroundColor={{
+        default: 'transparent',
+        pressed: YellowBoxStyle.getHighlightColor(1),
+      }}
+      onPress={props.onDismiss}
+      style={styles.button}>
+      <View style={styles.content}>
+        <Text style={styles.label}>Dismiss</Text>
+      </View>
+      <SafeAreaView />
+    </YellowBoxPressable>
+  </View>
+);
+
+const styles = StyleSheet.create({
+  root: {
+    backgroundColor: YellowBoxStyle.getBackgroundColor(0.95),
+    flexDirection: 'row',
+  },
+  button: {
+    flex: 1,
+  },
+  content: {
+    alignItems: 'center',
+    height: 48,
+    justifyContent: 'center',
+  },
+  label: {
+    color: YellowBoxStyle.getTextColor(1),
+    fontSize: 14,
+    includeFontPadding: false,
+    lineHeight: 18,
+  },
+});
+
+module.exports = YellowBoxInspectorFooter;
diff --git a/Libraries/YellowBox/UI/YellowBoxInspectorHeader.js b/Libraries/YellowBox/UI/YellowBoxInspectorHeader.js
new file mode 100644
index 000000000000..4ed124eaba22
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxInspectorHeader.js
@@ -0,0 +1,108 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const Platform = require('Platform');
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const UTFSequence = require('UTFSequence');
+const View = require('View');
+const YellowBoxPressable = require('YellowBoxPressable');
+const YellowBoxStyle = require('YellowBoxStyle');
+
+import type YellowBoxWarning from 'YellowBoxWarning';
+
+type Props = $ReadOnly<{|
+  onSelectIndex: (selectedIndex: number) => void,
+  selectedIndex: number,
+  warnings: $ReadOnlyArray<YellowBoxWarning>,
+|}>;
+
+const YellowBoxInspectorHeader = (props: Props): React.Node => {
+  const prevIndex = props.selectedIndex - 1;
+  const nextIndex = props.selectedIndex + 1;
+
+  const titleText =
+    props.warnings.length === 1
+      ? 'Single Occurrence'
+      : `Occurrence ${props.selectedIndex + 1} of ${props.warnings.length}`;
+
+  return (
+    <View style={styles.header}>
+      <YellowBoxInspectorHeaderButton
+        disabled={props.warnings[prevIndex] == null}
+        label={UTFSequence.TRIANGLE_LEFT}
+        onPress={() => props.onSelectIndex(prevIndex)}
+      />
+      <View style={styles.headerTitle}>
+        <Text style={styles.headerTitleText}>{titleText}</Text>
+      </View>
+      <YellowBoxInspectorHeaderButton
+        disabled={props.warnings[nextIndex] == null}
+        label={UTFSequence.TRIANGLE_RIGHT}
+        onPress={() => props.onSelectIndex(nextIndex)}
+      />
+    </View>
+  );
+};
+
+const YellowBoxInspectorHeaderButton = (
+  props: $ReadOnly<{|
+    disabled: boolean,
+    label: React.Node,
+    onPress?: ?() => void,
+  |}>,
+): React.Node => (
+  <YellowBoxPressable
+    onPress={props.disabled ? null : props.onPress}
+    style={styles.headerButton}>
+    {props.disabled ? null : (
+      <Text style={styles.headerButtonText}>{props.label}</Text>
+    )}
+  </YellowBoxPressable>
+);
+
+const styles = StyleSheet.create({
+  header: {
+    flexDirection: 'row',
+    height: Platform.select({
+      android: 48,
+      ios: 44,
+    }),
+  },
+  headerButton: {
+    alignItems: 'center',
+    aspectRatio: 1,
+    justifyContent: 'center',
+  },
+  headerButtonText: {
+    color: YellowBoxStyle.getTextColor(1),
+    fontSize: 16,
+    includeFontPadding: false,
+    lineHeight: 20,
+  },
+  headerTitle: {
+    alignItems: 'center',
+    backgroundColor: YellowBoxStyle.getBackgroundColor(0.95),
+    flex: 1,
+    justifyContent: 'center',
+  },
+  headerTitleText: {
+    color: YellowBoxStyle.getTextColor(1),
+    fontSize: 16,
+    fontWeight: '600',
+    includeFontPadding: false,
+    lineHeight: 20,
+  },
+});
+
+module.exports = YellowBoxInspectorHeader;
diff --git a/Libraries/YellowBox/UI/YellowBoxInspectorSourceMapStatus.js b/Libraries/YellowBox/UI/YellowBoxInspectorSourceMapStatus.js
new file mode 100644
index 000000000000..831305d74ea5
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxInspectorSourceMapStatus.js
@@ -0,0 +1,149 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ * @format
+ */
+
+'use strict';
+
+const Animated = require('Animated');
+const Easing = require('Easing');
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const View = require('View');
+const YellowBoxImageSource = require('YellowBoxImageSource');
+const YellowBoxStyle = require('YellowBoxStyle');
+
+import type {CompositeAnimation} from 'AnimatedImplementation';
+import type AnimatedInterpolation from 'AnimatedInterpolation';
+
+type Props = $ReadOnly<{|
+  status: 'COMPLETE' | 'FAILED' | 'NONE' | 'PENDING',
+|}>;
+
+type State = {|
+  animation: ?CompositeAnimation,
+  rotate: ?AnimatedInterpolation,
+|};
+
+class YellowBoxInspectorSourceMapStatus extends React.Component<Props, State> {
+  state = {
+    animation: null,
+    rotate: null,
+  };
+
+  render(): React.Node {
+    let image;
+    switch (this.props.status) {
+      case 'COMPLETE':
+        image = YellowBoxImageSource.check;
+        break;
+      case 'FAILED':
+        image = YellowBoxImageSource.alertTriangle;
+        break;
+      case 'PENDING':
+        image = YellowBoxImageSource.loader;
+        break;
+    }
+
+    return image == null ? null : (
+      <View
+        style={StyleSheet.compose(
+          styles.root,
+          this.props.status === 'PENDING' ? styles.pending : null,
+        )}>
+        <Animated.Image
+          source={{height: 16, uri: image, width: 16}}
+          style={StyleSheet.compose(
+            styles.image,
+            this.state.rotate == null
+              ? null
+              : {transform: [{rotate: this.state.rotate}]},
+          )}
+        />
+        <Text style={styles.text}>Source Map</Text>
+      </View>
+    );
+  }
+
+  componentDidMount(): void {
+    this._updateAnimation();
+  }
+
+  componentDidUpdate(): void {
+    this._updateAnimation();
+  }
+
+  componentWillUnmount(): void {
+    if (this.state.animation != null) {
+      this.state.animation.stop();
+    }
+  }
+
+  _updateAnimation(): void {
+    if (this.props.status === 'PENDING') {
+      if (this.state.animation == null) {
+        const animated = new Animated.Value(0);
+        const animation = Animated.loop(
+          Animated.timing(animated, {
+            duration: 2000,
+            easing: Easing.linear,
+            toValue: 1,
+            useNativeDriver: true,
+          }),
+        );
+        this.setState(
+          {
+            animation,
+            rotate: animated.interpolate({
+              inputRange: [0, 1],
+              outputRange: ['0deg', '360deg'],
+            }),
+          },
+          () => {
+            animation.start();
+          },
+        );
+      }
+    } else {
+      if (this.state.animation != null) {
+        this.state.animation.stop();
+        this.setState({
+          animation: null,
+          rotate: null,
+        });
+      }
+    }
+  }
+}
+
+const styles = StyleSheet.create({
+  root: {
+    alignItems: 'center',
+    backgroundColor: YellowBoxStyle.getTextColor(0.8),
+    borderRadius: 12,
+    flexDirection: 'row',
+    height: 24,
+    paddingHorizontal: 8,
+  },
+  pending: {
+    backgroundColor: YellowBoxStyle.getTextColor(0.6),
+  },
+  image: {
+    marginEnd: 4,
+    tintColor: YellowBoxStyle.getBackgroundColor(1),
+  },
+  text: {
+    color: YellowBoxStyle.getBackgroundColor(1),
+    fontSize: 12,
+    includeFontPadding: false,
+    lineHeight: 16,
+  },
+});
+
+module.exports = YellowBoxInspectorSourceMapStatus;
diff --git a/Libraries/YellowBox/UI/YellowBoxInspectorStackFrame.js b/Libraries/YellowBox/UI/YellowBoxInspectorStackFrame.js
new file mode 100644
index 000000000000..8ee0d04b9cdf
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxInspectorStackFrame.js
@@ -0,0 +1,81 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const YellowBoxPressable = require('YellowBoxPressable');
+const YellowBoxStyle = require('YellowBoxStyle');
+
+import type {PressEvent} from 'CoreEventTypes';
+import type {StackFrame} from 'parseErrorStack';
+
+type Props = $ReadOnly<{|
+  frame: StackFrame,
+  onPress?: ?(event: PressEvent) => void,
+|}>;
+
+const YellowBoxInspectorStackFrame = (props: Props): React.Node => {
+  const {frame, onPress} = props;
+
+  return (
+    <YellowBoxPressable
+      backgroundColor={{
+        default: YellowBoxStyle.getBackgroundColor(0),
+        pressed: YellowBoxStyle.getHighlightColor(1),
+      }}
+      onPress={onPress}
+      style={styles.frame}>
+      <Text style={styles.frameName}>{frame.methodName}</Text>
+      <Text
+        ellipsizeMode="middle"
+        numberOfLines={1}
+        style={styles.frameLocation}>
+        {`${getFrameLocation(frame.file)}:${frame.lineNumber}${
+          frame.column == null ? '' : ':' + frame.column
+        }`}
+      </Text>
+    </YellowBoxPressable>
+  );
+};
+
+const getFrameLocation = (uri: string): string => {
+  const queryIndex = uri.indexOf('?');
+  const query = queryIndex < 0 ? '' : uri.substr(queryIndex);
+
+  const path = queryIndex < 0 ? uri : uri.substr(0, queryIndex);
+  const file = path.substr(path.lastIndexOf('/') + 1);
+
+  return file + query;
+};
+
+const styles = StyleSheet.create({
+  frame: {
+    paddingHorizontal: 12,
+    paddingVertical: 4,
+  },
+  frameName: {
+    color: YellowBoxStyle.getTextColor(1),
+    fontSize: 14,
+    includeFontPadding: false,
+    lineHeight: 18,
+  },
+  frameLocation: {
+    color: YellowBoxStyle.getTextColor(0.7),
+    fontSize: 12,
+    fontWeight: '300',
+    includeFontPadding: false,
+    lineHeight: 16,
+  },
+});
+
+module.exports = YellowBoxInspectorStackFrame;
diff --git a/Libraries/YellowBox/UI/YellowBoxList.js b/Libraries/YellowBox/UI/YellowBoxList.js
new file mode 100644
index 000000000000..63b321cde972
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxList.js
@@ -0,0 +1,142 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const Dimensions = require('Dimensions');
+const React = require('React');
+const FlatList = require('FlatList');
+const SafeAreaView = require('SafeAreaView');
+const StyleSheet = require('StyleSheet');
+const View = require('View');
+const YellowBoxButton = require('YellowBoxButton');
+const YellowBoxInspector = require('YellowBoxInspector');
+const YellowBoxListRow = require('YellowBoxListRow');
+const YellowBoxStyle = require('YellowBoxStyle');
+
+import type {Category} from 'YellowBoxCategory';
+import type {Registry} from 'YellowBoxRegistry';
+
+type Props = $ReadOnly<{|
+  onDismiss: (category: Category) => void,
+  onDismissAll: () => void,
+  registry: Registry,
+|}>;
+
+type State = {|
+  selectedCategory: ?Category,
+|};
+
+const VIEWPORT_RATIO = 0.5;
+const MAX_ITEMS = Math.floor(
+  (Dimensions.get('window').height * VIEWPORT_RATIO) /
+    (YellowBoxListRow.GUTTER + YellowBoxListRow.HEIGHT),
+);
+
+class YellowBoxList extends React.Component<Props, State> {
+  state = {
+    selectedCategory: null,
+  };
+
+  render(): React.Node {
+    const selectedWarnings =
+      this.state.selectedCategory == null
+        ? null
+        : this.props.registry.get(this.state.selectedCategory);
+
+    if (selectedWarnings != null) {
+      return (
+        <View style={StyleSheet.absoluteFill}>
+          <YellowBoxInspector
+            onDismiss={this._handleInspectorDismiss}
+            onMinimize={this._handleInspectorMinimize}
+            warnings={selectedWarnings}
+          />
+        </View>
+      );
+    }
+
+    const items = [];
+    for (const [category, warnings] of this.props.registry) {
+      items.unshift({category, warnings});
+    }
+
+    const listStyle = {
+      height:
+        // Additional `0.5` so the (N + 1)th row can peek into view.
+        Math.min(items.length, MAX_ITEMS + 0.5) *
+        (YellowBoxListRow.GUTTER + YellowBoxListRow.HEIGHT),
+    };
+
+    return items.length === 0 ? null : (
+      <View style={styles.list}>
+        <View pointerEvents="box-none" style={styles.dismissAll}>
+          <YellowBoxButton
+            hitSlop={{bottom: 4, left: 4, right: 4, top: 4}}
+            label="Dismiss All"
+            onPress={this.props.onDismissAll}
+          />
+        </View>
+        <FlatList
+          data={items}
+          keyExtractor={item => item.category}
+          renderItem={({item}) => (
+            <YellowBoxListRow {...item} onPress={this._handleRowPress} />
+          )}
+          scrollEnabled={items.length > MAX_ITEMS}
+          scrollsToTop={false}
+          style={listStyle}
+        />
+        <SafeAreaView style={styles.safeArea} />
+      </View>
+    );
+  }
+
+  _handleInspectorDismiss = () => {
+    const category = this.state.selectedCategory;
+    if (category == null) {
+      return;
+    }
+    this.setState({selectedCategory: null}, () => {
+      this.props.onDismiss(category);
+    });
+  };
+
+  _handleInspectorMinimize = () => {
+    this.setState({selectedCategory: null});
+  };
+
+  _handleRowPress = (category: Category) => {
+    this.setState({selectedCategory: category});
+  };
+}
+
+const styles = StyleSheet.create({
+  list: {
+    bottom: 0,
+    position: 'absolute',
+    width: '100%',
+  },
+  dismissAll: {
+    bottom: '100%',
+    flexDirection: 'row',
+    justifyContent: 'flex-end',
+    paddingBottom: 4,
+    paddingEnd: 4,
+    position: 'absolute',
+    width: '100%',
+  },
+  safeArea: {
+    backgroundColor: YellowBoxStyle.getBackgroundColor(0.95),
+    marginTop: StyleSheet.hairlineWidth,
+  },
+});
+
+module.exports = YellowBoxList;
diff --git a/Libraries/YellowBox/UI/YellowBoxListRow.js b/Libraries/YellowBox/UI/YellowBoxListRow.js
new file mode 100644
index 000000000000..e59d0e89e227
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxListRow.js
@@ -0,0 +1,100 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const Text = require('Text');
+const YellowBoxPressable = require('YellowBoxPressable');
+const View = require('View');
+const YellowBoxCategory = require('YellowBoxCategory');
+const YellowBoxStyle = require('YellowBoxStyle');
+const YellowBoxWarning = require('YellowBoxWarning');
+
+import type {Category} from 'YellowBoxCategory';
+
+type Props = $ReadOnly<{|
+  category: Category,
+  warnings: $ReadOnlyArray<YellowBoxWarning>,
+  onPress: (category: Category) => void,
+|}>;
+
+class YellowBoxListRow extends React.Component<Props> {
+  static GUTTER = StyleSheet.hairlineWidth;
+  static HEIGHT = 48;
+
+  shouldComponentUpdate(nextProps: Props): boolean {
+    const prevProps = this.props;
+    return (
+      prevProps.category !== nextProps.category ||
+      prevProps.onPress !== nextProps.onPress ||
+      prevProps.warnings.length !== nextProps.warnings.length ||
+      prevProps.warnings.some(
+        (prevWarning, index) => prevWarning !== nextProps[index],
+      )
+    );
+  }
+
+  render(): React.Node {
+    const {warnings} = this.props;
+
+    return (
+      <YellowBoxPressable onPress={this._handlePress} style={styles.root}>
+        <View style={styles.content}>
+          {warnings.length < 2 ? null : (
+            <Text style={styles.metaText}>{'(' + warnings.length + ') '}</Text>
+          )}
+          <Text numberOfLines={2} style={styles.bodyText}>
+            {YellowBoxCategory.render(
+              warnings[warnings.length - 1].message,
+              styles.substitutionText,
+            )}
+          </Text>
+        </View>
+      </YellowBoxPressable>
+    );
+  }
+
+  _handlePress = () => {
+    this.props.onPress(this.props.category);
+  };
+}
+
+const styles = StyleSheet.create({
+  root: {
+    height: YellowBoxListRow.HEIGHT,
+    justifyContent: 'center',
+    marginTop: YellowBoxListRow.GUTTER,
+    paddingHorizontal: 12,
+  },
+  content: {
+    alignItems: 'flex-start',
+    flexDirection: 'row',
+  },
+  bodyText: {
+    color: YellowBoxStyle.getTextColor(1),
+    flex: 1,
+    fontSize: 14,
+    includeFontPadding: false,
+    lineHeight: 18,
+  },
+  metaText: {
+    color: YellowBoxStyle.getTextColor(0.5),
+    fontSize: 14,
+    includeFontPadding: false,
+    lineHeight: 18,
+  },
+  substitutionText: {
+    color: YellowBoxStyle.getTextColor(0.6),
+  },
+});
+
+module.exports = YellowBoxListRow;
diff --git a/Libraries/YellowBox/UI/YellowBoxPressable.js b/Libraries/YellowBox/UI/YellowBoxPressable.js
new file mode 100644
index 000000000000..39149c251214
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxPressable.js
@@ -0,0 +1,86 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const React = require('React');
+const StyleSheet = require('StyleSheet');
+const TouchableWithoutFeedback = require('TouchableWithoutFeedback');
+const View = require('View');
+const YellowBoxStyle = require('YellowBoxStyle');
+
+import type {PressEvent} from 'CoreEventTypes';
+import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
+import type {ViewStyleProp} from 'StyleSheet';
+
+type Props = $ReadOnly<{|
+  backgroundColor: $ReadOnly<{|
+    default: string,
+    pressed: string,
+  |}>,
+  children?: React.Node,
+  hitSlop?: ?EdgeInsetsProp,
+  onPress?: ?(event: PressEvent) => void,
+  style?: ViewStyleProp,
+|}>;
+
+type State = {|
+  pressed: boolean,
+|};
+
+class YellowBoxPressable extends React.Component<Props, State> {
+  static defaultProps = {
+    backgroundColor: {
+      default: YellowBoxStyle.getBackgroundColor(0.95),
+      pressed: YellowBoxStyle.getHighlightColor(1),
+    },
+  };
+
+  state = {
+    pressed: false,
+  };
+
+  render(): React.Node {
+    const content = (
+      <View
+        style={StyleSheet.compose(
+          {
+            backgroundColor: this.state.pressed
+              ? this.props.backgroundColor.pressed
+              : this.props.backgroundColor.default,
+          },
+          this.props.style,
+        )}>
+        {this.props.children}
+      </View>
+    );
+    return this.props.onPress == null ? (
+      content
+    ) : (
+      <TouchableWithoutFeedback
+        hitSlop={this.props.hitSlop}
+        onPress={this.props.onPress}
+        onPressIn={this._handlePressIn}
+        onPressOut={this._handlePressOut}>
+        {content}
+      </TouchableWithoutFeedback>
+    );
+  }
+
+  _handlePressIn = () => {
+    this.setState({pressed: true});
+  };
+
+  _handlePressOut = () => {
+    this.setState({pressed: false});
+  };
+}
+
+module.exports = YellowBoxPressable;
diff --git a/Libraries/YellowBox/UI/YellowBoxStyle.js b/Libraries/YellowBox/UI/YellowBoxStyle.js
new file mode 100644
index 000000000000..2ceec6f28d48
--- /dev/null
+++ b/Libraries/YellowBox/UI/YellowBoxStyle.js
@@ -0,0 +1,31 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const YellowBoxStyle = {
+  getBackgroundColor(opacity: number): string {
+    return `rgba(250, 186, 48, ${opacity})`;
+  },
+
+  getDividerColor(opacity: number): string {
+    return `rgba(255, 255, 255, ${opacity})`;
+  },
+
+  getHighlightColor(opacity: number): string {
+    return `rgba(252, 176, 29, ${opacity})`;
+  },
+
+  getTextColor(opacity: number): string {
+    return `rgba(255, 255, 255, ${opacity})`;
+  },
+};
+
+module.exports = YellowBoxStyle;
diff --git a/Libraries/YellowBox/YellowBox.js b/Libraries/YellowBox/YellowBox.js
new file mode 100644
index 000000000000..45a6dbc3bcf9
--- /dev/null
+++ b/Libraries/YellowBox/YellowBox.js
@@ -0,0 +1,132 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ * @format
+ */
+
+'use strict';
+
+const Platform = require('Platform');
+const RCTLog = require('RCTLog');
+const React = require('React');
+const YellowBoxList = require('YellowBoxList');
+const YellowBoxRegistry = require('YellowBoxRegistry');
+
+import type {Category} from 'YellowBoxCategory';
+import type {Registry, Subscription} from 'YellowBoxRegistry';
+
+type Props = $ReadOnly<{||}>;
+type State = {|
+  registry: ?Registry,
+|};
+
+const {error, warn} = console;
+
+/**
+ * YellowBox displays warnings at the bottom of the screen.
+ *
+ * Warnings help guard against subtle yet significant issues that can impact the
+ * quality of the app. This "in your face" style of warning allows developers to
+ * notice and correct these issues as quickly as possible.
+ *
+ * YellowBox is only enabled in `__DEV__`. Set the following flag to disable it:
+ *
+ *   console.disableYellowBox = true;
+ *
+ * Ignore specific warnings by calling:
+ *
+ *   YellowBox.ignoreWarnings(['Warning: ...']);
+ *
+ * Strings supplied to `YellowBox.ignoreWarnings` only need to be a substring of
+ * the ignored warning messages.
+ */
+class YellowBox extends React.Component<Props, State> {
+  static ignoreWarnings(patterns: $ReadOnlyArray<string>): void {
+    YellowBoxRegistry.addIgnorePatterns(patterns);
+  }
+
+  static install(): void {
+    (console: any).error = function(...args) {
+      error.call(console, ...args);
+      // Show YellowBox for the `warning` module.
+      if (typeof args[0] === 'string' && args[0].startsWith('Warning: ')) {
+        registerWarning(...args);
+      }
+    };
+
+    (console: any).warn = function(...args) {
+      warn.call(console, ...args);
+      registerWarning(...args);
+    };
+
+    if ((console: any).disableYellowBox === true) {
+      YellowBoxRegistry.setDisabled(true);
+    }
+    (Object.defineProperty: any)(console, 'disableYellowBox', {
+      configurable: true,
+      get: () => YellowBoxRegistry.isDisabled(),
+      set: value => YellowBoxRegistry.setDisabled(value),
+    });
+
+    if (Platform.isTesting) {
+      (console: any).disableYellowBox = true;
+    }
+
+    RCTLog.setWarningHandler((...args) => {
+      registerWarning(...args);
+    });
+  }
+
+  static uninstall(): void {
+    (console: any).error = error;
+    (console: any).warn = error;
+    delete (console: any).disableYellowBox;
+  }
+
+  _subscription: ?Subscription;
+
+  state = {
+    registry: null,
+  };
+
+  render() {
+    // TODO: Ignore warnings that fire when rendering `YellowBox` itself.
+    return this.state.registry == null ? null : (
+      <YellowBoxList
+        onDismiss={this._handleDismiss}
+        onDismissAll={this._handleDismissAll}
+        registry={this.state.registry}
+      />
+    );
+  }
+
+  componentDidMount(): void {
+    this._subscription = YellowBoxRegistry.observe(registry => {
+      this.setState({registry});
+    });
+  }
+
+  componentWillUnmount(): void {
+    if (this._subscription != null) {
+      this._subscription.unsubscribe();
+    }
+  }
+
+  _handleDismiss = (category: Category): void => {
+    YellowBoxRegistry.delete(category);
+  };
+
+  _handleDismissAll(): void {
+    YellowBoxRegistry.clear();
+  }
+}
+
+function registerWarning(...args): void {
+  YellowBoxRegistry.add({args, framesToPop: 2});
+}
+
+module.exports = YellowBox;
diff --git a/Libraries/YellowBox/__tests__/YellowBox-test.js b/Libraries/YellowBox/__tests__/YellowBox-test.js
new file mode 100644
index 000000000000..e22168b2417b
--- /dev/null
+++ b/Libraries/YellowBox/__tests__/YellowBox-test.js
@@ -0,0 +1,77 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @emails oncall+react_native
+ * @format
+ * @flow
+ */
+
+'use strict';
+
+const YellowBox = require('YellowBox');
+const YellowBoxRegistry = require('YellowBoxRegistry');
+
+describe('YellowBox', () => {
+  const {error, warn} = console;
+
+  beforeEach(() => {
+    jest.resetModules();
+    (console: any).error = jest.fn();
+    (console: any).warn = jest.fn();
+  });
+
+  afterEach(() => {
+    YellowBox.uninstall();
+    (console: any).error = error;
+    (console: any).warn = warn;
+  });
+
+  it('can set `disableYellowBox` after installing', () => {
+    expect((console: any).disableYellowBox).toBe(undefined);
+
+    YellowBox.install();
+
+    expect((console: any).disableYellowBox).toBe(false);
+    expect(YellowBoxRegistry.isDisabled()).toBe(false);
+
+    (console: any).disableYellowBox = true;
+
+    expect((console: any).disableYellowBox).toBe(true);
+    expect(YellowBoxRegistry.isDisabled()).toBe(true);
+  });
+
+  it('can set `disableYellowBox` before installing', () => {
+    expect((console: any).disableYellowBox).toBe(undefined);
+
+    (console: any).disableYellowBox = true;
+    YellowBox.install();
+
+    expect((console: any).disableYellowBox).toBe(true);
+    expect(YellowBoxRegistry.isDisabled()).toBe(true);
+  });
+
+  it('registers warnings', () => {
+    jest.mock('YellowBoxRegistry');
+
+    YellowBox.install();
+
+    expect(YellowBoxRegistry.add).not.toBeCalled();
+    (console: any).warn('...');
+    expect(YellowBoxRegistry.add).toBeCalled();
+  });
+
+  it('registers errors beginning with "Warning: "', () => {
+    jest.mock('YellowBoxRegistry');
+
+    YellowBox.install();
+
+    (console: any).error('...');
+    expect(YellowBoxRegistry.add).not.toBeCalled();
+
+    (console: any).error('Warning: ...');
+    expect(YellowBoxRegistry.add).toBeCalled();
+  });
+});

From ddf2c2ffd6f58743f25253289297bfe19fa17c75 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Mon, 11 Jun 2018 19:10:27 -0700
Subject: [PATCH 0771/1109] fix forwardRef displayName on Text and View

Reviewed By: TheSavior

Differential Revision: D8342852

fbshipit-source-id: 5af80edfd5de5b6d6ea6fdc24abf8931f767c812
---
 Libraries/Components/View/View.js | 31 ++++++++++++++++++-------------
 Libraries/Text/Text.js            | 16 ++++++++++------
 jest/mockComponent.js             |  7 ++++++-
 3 files changed, 34 insertions(+), 20 deletions(-)

diff --git a/Libraries/Components/View/View.js b/Libraries/Components/View/View.js
index c494643c4740..ed420338c243 100644
--- a/Libraries/Components/View/View.js
+++ b/Libraries/Components/View/View.js
@@ -32,19 +32,24 @@ const RCTView = requireNativeComponent('RCTView');
 
 let ViewToExport = RCTView;
 if (__DEV__) {
+  const View = (props: Props, forwardedRef: ?React.Ref<'RCTView'>) => {
+    return (
+      <TextAncestor.Consumer>
+        {hasTextAncestor => {
+          invariant(
+            !hasTextAncestor,
+            'Nesting of <View> within <Text> is not currently supported.',
+          );
+          return <RCTView {...props} ref={forwardedRef} />;
+        }}
+      </TextAncestor.Consumer>
+    );
+  };
+  View.displayName = 'View'; // TODO(T30332650) remove bug workaround
   // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
-  ViewToExport = React.forwardRef((props, ref) => (
-    <TextAncestor.Consumer>
-      {hasTextAncestor => {
-        invariant(
-          !hasTextAncestor,
-          'Nesting of <View> within <Text> is not currently supported.',
-        );
-        return <RCTView {...props} ref={ref} />;
-      }}
-    </TextAncestor.Consumer>
-  ));
-  ViewToExport.displayName = 'View';
+  ViewToExport = React.forwardRef(View);
 }
 
-module.exports = ((ViewToExport: any): Class<NativeComponent<ViewProps>>);
+module.exports = ((ViewToExport: $FlowFixMe): Class<
+  NativeComponent<ViewProps>,
+>);
diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index 5da883aa6309..aaa283a6dafa 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -261,13 +261,17 @@ const RCTVirtualText =
         uiViewClassName: 'RCTVirtualText',
       }));
 
+const Text = (
+  props: TextProps,
+  forwardedRef: ?React.Ref<'RCTText' | 'RCTVirtualText'>,
+) => {
+  return <TouchableText {...props} forwardedRef={forwardedRef} />;
+};
+Text.displayName = 'Text'; // TODO(T30332650) remove bug workaround
 // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
-const Text = React.forwardRef((props, ref) => (
-  <TouchableText {...props} forwardedRef={ref} />
-));
-Text.displayName = 'Text';
+const TextToExport = React.forwardRef(Text);
 
 // TODO: Deprecate this.
-Text.propTypes = TextPropTypes;
+TextToExport.propTypes = TextPropTypes;
 
-module.exports = ((Text: any): Class<NativeComponent<TextProps>>);
+module.exports = (TextToExport: Class<NativeComponent<TextProps>>);
diff --git a/jest/mockComponent.js b/jest/mockComponent.js
index 6d5a80b47e07..3f98a160d5c9 100644
--- a/jest/mockComponent.js
+++ b/jest/mockComponent.js
@@ -18,7 +18,12 @@ module.exports = (moduleName, instanceMethods) => {
 
   const Component = class extends SuperClass {
     render() {
-      const name = RealComponent.displayName || RealComponent.name;
+      const name =
+        RealComponent.displayName ||
+        RealComponent.name ||
+        (RealComponent.render // handle React.forwardRef
+          ? RealComponent.render.displayName || RealComponent.render.name
+          : 'Unknown');
 
       const props = Object.assign({}, RealComponent.defaultProps);
 

From d1336ab16efc26449509b938dd46cf606d3caf34 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Mon, 11 Jun 2018 19:10:28 -0700
Subject: [PATCH 0772/1109] Fix more forwardRef displayNames

Reviewed By: TheSavior

Differential Revision: D8342904

fbshipit-source-id: b6e53da7305d71635528a42e80910f4a9db0455c
---
 .../ActivityIndicator/ActivityIndicator.js    |  22 +--
 .../ProgressBarAndroid.android.js             | 136 ++++++++----------
 Libraries/Components/Slider/Slider.js         |  19 +--
 3 files changed, 74 insertions(+), 103 deletions(-)

diff --git a/Libraries/Components/ActivityIndicator/ActivityIndicator.js b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
index f2a648797eb0..fccb42983450 100644
--- a/Libraries/Components/ActivityIndicator/ActivityIndicator.js
+++ b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
@@ -70,12 +70,10 @@ type Props = $ReadOnly<{|
  * See http://facebook.github.io/react-native/docs/activityindicator.html
  */
 const ActivityIndicator = (
-  props: $ReadOnly<{|
-    ...Props,
-    forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
-  |}>,
+  props: Props,
+  forwardedRef: ?React.Ref<'RCTActivityIndicatorView'>,
 ) => {
-  const {onLayout, style, forwardedRef, ...restProps} = props;
+  const {onLayout, style, ...restProps} = props;
   let sizeStyle;
 
   switch (props.size) {
@@ -99,16 +97,19 @@ const ActivityIndicator = (
   };
 
   return (
-    <View onLayout={onLayout} style={[styles.container, style]}>
+    <View
+      onLayout={onLayout}
+      style={StyleSheet.compose(
+        styles.container,
+        style,
+      )}>
       <RCTActivityIndicator {...nativeProps} />
     </View>
   );
 };
-
+ActivityIndicator.displayName = 'ActivityIndicator'; // TODO(T30332650) remove workaround for hermes bug
 // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
-const ActivityIndicatorWithRef = React.forwardRef((props: Props, ref) => {
-  return <ActivityIndicator {...props} forwardedRef={ref} />;
-});
+const ActivityIndicatorWithRef = React.forwardRef(ActivityIndicator);
 
 ActivityIndicatorWithRef.defaultProps = {
   animating: true,
@@ -116,7 +117,6 @@ ActivityIndicatorWithRef.defaultProps = {
   hidesWhenStopped: true,
   size: 'small',
 };
-ActivityIndicatorWithRef.displayName = 'ActivityIndicator';
 
 const styles = StyleSheet.create({
   container: {
diff --git a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
index 7ea083dd0f19..de3a0c7045aa 100644
--- a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
+++ b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
@@ -4,41 +4,60 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @flow
  * @format
  */
 
 'use strict';
 
-const ColorPropType = require('ColorPropType');
-const PropTypes = require('prop-types');
 const React = require('React');
-const ViewPropTypes = require('ViewPropTypes');
 
 const requireNativeComponent = require('requireNativeComponent');
 
-const STYLE_ATTRIBUTES = [
-  'Horizontal',
-  'Normal',
-  'Small',
-  'Large',
-  'Inverse',
-  'SmallInverse',
-  'LargeInverse',
-];
+const RCTAndroidProgressBar = requireNativeComponent('AndroidProgressBar');
 
-const indeterminateType = function(props, propName, componentName, ...rest) {
-  const checker = function() {
-    const indeterminate = props[propName];
-    const styleAttr = props.styleAttr;
-    if (!indeterminate && styleAttr !== 'Horizontal') {
-      return new Error(
-        'indeterminate=false is only valid for styleAttr=Horizontal',
-      );
-    }
-  };
+import type {NativeComponent} from 'ReactNative';
+import type {ViewProps} from 'ViewPropTypes';
 
-  return PropTypes.bool(props, propName, componentName, ...rest) || checker();
-};
+type Props = $ReadOnly<{|
+  ...ViewProps,
+
+  /**
+   * Style of the ProgressBar and whether it shows indeterminate progress (e.g. spinner).
+   *
+   * `indeterminate` can only be false if `styleAttr` is Horizontal, and requires a
+   * `progress` value.
+   */
+  ...
+    | {|
+        styleAttr: 'Horizontal',
+        indeterminate: false,
+        progress: number,
+      |}
+    | {|
+        typeAttr:
+          | 'Horizontal'
+          | 'Normal'
+          | 'Small'
+          | 'Large'
+          | 'Inverse'
+          | 'SmallInverse'
+          | 'LargeInverse',
+        indeterminate: true,
+      |},
+  /**
+   * Whether to show the ProgressBar (true, the default) or hide it (false).
+   */
+  animating?: ?boolean,
+  /**
+   * Color of the progress bar.
+   */
+  color?: ?string,
+  /**
+   * Used to locate this view in end-to-end tests.
+   */
+  testID?: ?string,
+|}>;
 
 /**
  * React component that wraps the Android-only `ProgressBar`. This component is
@@ -63,59 +82,20 @@ const indeterminateType = function(props, propName, componentName, ...rest) {
  * },
  * ```
  */
-class ProgressBarAndroid extends React.Component {
-  static propTypes = {
-    ...ViewPropTypes,
-
-    /**
-     * Style of the ProgressBar. One of:
-     *
-     * - Horizontal
-     * - Normal (default)
-     * - Small
-     * - Large
-     * - Inverse
-     * - SmallInverse
-     * - LargeInverse
-     */
-    styleAttr: PropTypes.oneOf(STYLE_ATTRIBUTES),
-    /**
-     * Whether to show the ProgressBar (true, the default) or hide it (false).
-     */
-    animating: PropTypes.bool,
-    /**
-     * If the progress bar will show indeterminate progress. Note that this
-     * can only be false if styleAttr is Horizontal.
-     */
-    indeterminate: indeterminateType,
-    /**
-     * The progress value (between 0 and 1).
-     */
-    progress: PropTypes.number,
-    /**
-     * Color of the progress bar.
-     */
-    color: ColorPropType,
-    /**
-     * Used to locate this view in end-to-end tests.
-     */
-    testID: PropTypes.string,
-  };
-
-  static defaultProps = {
-    styleAttr: 'Normal',
-    indeterminate: true,
-    animating: true,
-  };
-
-  render() {
-    const {forwardedRef, ...props} = this.props;
-    return <AndroidProgressBar {...props} ref={forwardedRef} />;
-  }
-}
+const ProgressBarAndroid = (
+  props: Props,
+  forwardedRef: ?React.Ref<'RCTAndroidProgressBar'>,
+) => {
+  return <RCTAndroidProgressBar {...props} ref={forwardedRef} />;
+};
+ProgressBarAndroid.displayName = 'ProgressBarAndroid'; // TODO(T30332650) remove bug workaround
 
-const AndroidProgressBar = requireNativeComponent('AndroidProgressBar');
+ProgressBarAndroid.defaultProps = {
+  styleAttr: 'Normal',
+  indeterminate: true,
+  animating: true,
+};
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+const ProgressBarAndroidToExport = React.forwardRef(ProgressBarAndroid);
 
-module.exports = React.forwardRef((props, ref) => (
-  <ProgressBarAndroid {...props} forwardedRef={ref} />
-));
+module.exports = (ProgressBarAndroidToExport: Class<NativeComponent<Props>>);
diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index d9efe0170d8d..17bd7cef971f 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -239,6 +239,7 @@ const Slider = (
     />
   );
 };
+Slider.displayName = 'Slider'; // TODO(T30332650) remove bug workaround
 
 // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
 const SliderWithRef = React.forwardRef(Slider);
@@ -250,19 +251,9 @@ SliderWithRef.defaultProps = {
   maximumValue: 1,
   step: 0,
 };
-SliderWithRef.displayName = 'Slider';
-
-let styles;
-if (Platform.OS === 'ios') {
-  styles = StyleSheet.create({
-    slider: {
-      height: 40,
-    },
-  });
-} else {
-  styles = StyleSheet.create({
-    slider: {},
-  });
-}
+
+const styles = StyleSheet.create({
+  slider: Platform.OS === 'ios' ? {height: 40} : {},
+});
 
 module.exports = (SliderWithRef: Class<ReactNative.NativeComponent<Props>>);

From 741c53c2fbd777c11cec672002a6ea9b881fd930 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Mon, 11 Jun 2018 19:10:30 -0700
Subject: [PATCH 0773/1109] Upgrade react-test-render to handle
 React.forwardRef

Reviewed By: TheSavior

Differential Revision: D8346704

fbshipit-source-id: fc6686fab12a429780fb16e4129e8987529b13af
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 16554be62ee1..ee5360c5108f 100644
--- a/package.json
+++ b/package.json
@@ -217,7 +217,7 @@
     "jest-junit": "4.0.0",
     "prettier": "1.13.4",
     "react": "16.3.2",
-    "react-test-renderer": "16.3.2",
+    "react-test-renderer": "16.4.0",
     "shelljs": "^0.7.8",
     "sinon": "^2.2.0"
   }

From 119fd1efe7c52db9d6591f48dac60d0a35dca031 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Mon, 11 Jun 2018 19:47:26 -0700
Subject: [PATCH 0774/1109] iOS: Fixed some props conversion errors

Summary:
* numbers in JS are doubles in native land, since there's no notion of int or int64 in JS - so simply convert numbers to int instead of assuming it's int
* the parsing of Yoga props with `'...%'` string value has a bug: it should be copying the number instead of the `%`

Reviewed By: shergin

Differential Revision: D8370873

fbshipit-source-id: 44e9e3f0530c000c963e8e9ca66e8b0a48d80bcd
---
 ReactCommon/fabric/core/propsConversions.h | 6 +++++-
 ReactCommon/fabric/view/conversions.h      | 2 +-
 2 files changed, 6 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/core/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
index 548b88f3de4a..bf2f96f6c908 100644
--- a/ReactCommon/fabric/core/propsConversions.h
+++ b/ReactCommon/fabric/core/propsConversions.h
@@ -17,7 +17,11 @@ namespace facebook {
 namespace react {
 
 inline void fromDynamic(const folly::dynamic &value, bool &result) { result = value.getBool(); }
-inline void fromDynamic(const folly::dynamic &value, int &result) { result = value.getInt(); }
+inline void fromDynamic(const folly::dynamic &value, int &result) {
+  // All numbers from JS are treated as double, and JS cannot represent int64 in practice.
+  // So this always converts the value to int64 instead.
+  result = value.asInt();
+}
 inline void fromDynamic(const folly::dynamic &value, std::string &result) { result = value.getString(); }
 
 template <typename T>
diff --git a/ReactCommon/fabric/view/conversions.h b/ReactCommon/fabric/view/conversions.h
index cec142a7b949..66cb25da0d15 100644
--- a/ReactCommon/fabric/view/conversions.h
+++ b/ReactCommon/fabric/view/conversions.h
@@ -201,7 +201,7 @@ inline void fromDynamic(const folly::dynamic &value, YGValue &result) {
       return;
     } else {
       if (stringValue.back() == '%') {
-        result = { folly::to<float>(stringValue.substr(stringValue.length() - 1)), YGUnitPercent };
+        result = { folly::to<float>(stringValue.substr(0, stringValue.length() - 1)), YGUnitPercent };
         return;
       } else {
         result = { folly::to<float>(stringValue), YGUnitPoint };

From 5cdd141636d940ed881efbf67d66583135fba8d3 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Mon, 11 Jun 2018 19:47:27 -0700
Subject: [PATCH 0775/1109] Flow: textShadownOffest needs to be stricter

Summary: `width` and `height` are required for this style prop, for the sake of consistency (and Fabric). Callsites should set one of them to 0 instead of not specifying it.

Reviewed By: TheSavior, shergin

Differential Revision: D8371064

fbshipit-source-id: b0ffd6b6543ac5456a3708382966e7b3df241f7e
---
 Libraries/StyleSheet/StyleSheetTypes.js | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index cf385bb7df66..8fb8edd7bd90 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -185,8 +185,8 @@ export type ____TextStyle_Internal = $ReadOnly<{|
     | 'proportional-nums',
   >,
   textShadowOffset?: $ReadOnly<{|
-    width?: number,
-    height?: number,
+    width: number,
+    height: number,
   |}>,
   textShadowRadius?: number,
   textShadowColor?: ColorValue,

From 70fb3651f913f8f159c882c4c530ea73603d94b0 Mon Sep 17 00:00:00 2001
From: Reem Helou <helouree@fb.com>
Date: Mon, 11 Jun 2018 20:44:48 -0700
Subject: [PATCH 0776/1109] Revert D8346704: Upgrade react-test-render to
 handle React.forwardRef

Differential Revision:
D8346704

Original commit changeset: fc6686fab12a

fbshipit-source-id: 4d1a9d109ef5be93c40df2701f35966bf441eb0a
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index ee5360c5108f..16554be62ee1 100644
--- a/package.json
+++ b/package.json
@@ -217,7 +217,7 @@
     "jest-junit": "4.0.0",
     "prettier": "1.13.4",
     "react": "16.3.2",
-    "react-test-renderer": "16.4.0",
+    "react-test-renderer": "16.3.2",
     "shelljs": "^0.7.8",
     "sinon": "^2.2.0"
   }

From 95e8592dcb9b50772336d2801f46305fdc95250d Mon Sep 17 00:00:00 2001
From: Reem Helou <helouree@fb.com>
Date: Mon, 11 Jun 2018 20:44:49 -0700
Subject: [PATCH 0777/1109] Revert D8342904: [StrictMode] Fix more forwardRef
 displayNames

Differential Revision:
D8342904

Original commit changeset: b6e53da7305d

fbshipit-source-id: abf5fa6ccb16058f20cbb569ecfc790fad017133
---
 .../ActivityIndicator/ActivityIndicator.js    |  22 +--
 .../ProgressBarAndroid.android.js             | 136 ++++++++++--------
 Libraries/Components/Slider/Slider.js         |  19 ++-
 3 files changed, 103 insertions(+), 74 deletions(-)

diff --git a/Libraries/Components/ActivityIndicator/ActivityIndicator.js b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
index fccb42983450..f2a648797eb0 100644
--- a/Libraries/Components/ActivityIndicator/ActivityIndicator.js
+++ b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
@@ -70,10 +70,12 @@ type Props = $ReadOnly<{|
  * See http://facebook.github.io/react-native/docs/activityindicator.html
  */
 const ActivityIndicator = (
-  props: Props,
-  forwardedRef: ?React.Ref<'RCTActivityIndicatorView'>,
+  props: $ReadOnly<{|
+    ...Props,
+    forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
+  |}>,
 ) => {
-  const {onLayout, style, ...restProps} = props;
+  const {onLayout, style, forwardedRef, ...restProps} = props;
   let sizeStyle;
 
   switch (props.size) {
@@ -97,19 +99,16 @@ const ActivityIndicator = (
   };
 
   return (
-    <View
-      onLayout={onLayout}
-      style={StyleSheet.compose(
-        styles.container,
-        style,
-      )}>
+    <View onLayout={onLayout} style={[styles.container, style]}>
       <RCTActivityIndicator {...nativeProps} />
     </View>
   );
 };
-ActivityIndicator.displayName = 'ActivityIndicator'; // TODO(T30332650) remove workaround for hermes bug
+
 // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
-const ActivityIndicatorWithRef = React.forwardRef(ActivityIndicator);
+const ActivityIndicatorWithRef = React.forwardRef((props: Props, ref) => {
+  return <ActivityIndicator {...props} forwardedRef={ref} />;
+});
 
 ActivityIndicatorWithRef.defaultProps = {
   animating: true,
@@ -117,6 +116,7 @@ ActivityIndicatorWithRef.defaultProps = {
   hidesWhenStopped: true,
   size: 'small',
 };
+ActivityIndicatorWithRef.displayName = 'ActivityIndicator';
 
 const styles = StyleSheet.create({
   container: {
diff --git a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
index de3a0c7045aa..7ea083dd0f19 100644
--- a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
+++ b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
@@ -4,60 +4,41 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
  * @format
  */
 
 'use strict';
 
+const ColorPropType = require('ColorPropType');
+const PropTypes = require('prop-types');
 const React = require('React');
+const ViewPropTypes = require('ViewPropTypes');
 
 const requireNativeComponent = require('requireNativeComponent');
 
-const RCTAndroidProgressBar = requireNativeComponent('AndroidProgressBar');
+const STYLE_ATTRIBUTES = [
+  'Horizontal',
+  'Normal',
+  'Small',
+  'Large',
+  'Inverse',
+  'SmallInverse',
+  'LargeInverse',
+];
 
-import type {NativeComponent} from 'ReactNative';
-import type {ViewProps} from 'ViewPropTypes';
+const indeterminateType = function(props, propName, componentName, ...rest) {
+  const checker = function() {
+    const indeterminate = props[propName];
+    const styleAttr = props.styleAttr;
+    if (!indeterminate && styleAttr !== 'Horizontal') {
+      return new Error(
+        'indeterminate=false is only valid for styleAttr=Horizontal',
+      );
+    }
+  };
 
-type Props = $ReadOnly<{|
-  ...ViewProps,
-
-  /**
-   * Style of the ProgressBar and whether it shows indeterminate progress (e.g. spinner).
-   *
-   * `indeterminate` can only be false if `styleAttr` is Horizontal, and requires a
-   * `progress` value.
-   */
-  ...
-    | {|
-        styleAttr: 'Horizontal',
-        indeterminate: false,
-        progress: number,
-      |}
-    | {|
-        typeAttr:
-          | 'Horizontal'
-          | 'Normal'
-          | 'Small'
-          | 'Large'
-          | 'Inverse'
-          | 'SmallInverse'
-          | 'LargeInverse',
-        indeterminate: true,
-      |},
-  /**
-   * Whether to show the ProgressBar (true, the default) or hide it (false).
-   */
-  animating?: ?boolean,
-  /**
-   * Color of the progress bar.
-   */
-  color?: ?string,
-  /**
-   * Used to locate this view in end-to-end tests.
-   */
-  testID?: ?string,
-|}>;
+  return PropTypes.bool(props, propName, componentName, ...rest) || checker();
+};
 
 /**
  * React component that wraps the Android-only `ProgressBar`. This component is
@@ -82,20 +63,59 @@ type Props = $ReadOnly<{|
  * },
  * ```
  */
-const ProgressBarAndroid = (
-  props: Props,
-  forwardedRef: ?React.Ref<'RCTAndroidProgressBar'>,
-) => {
-  return <RCTAndroidProgressBar {...props} ref={forwardedRef} />;
-};
-ProgressBarAndroid.displayName = 'ProgressBarAndroid'; // TODO(T30332650) remove bug workaround
+class ProgressBarAndroid extends React.Component {
+  static propTypes = {
+    ...ViewPropTypes,
 
-ProgressBarAndroid.defaultProps = {
-  styleAttr: 'Normal',
-  indeterminate: true,
-  animating: true,
-};
-// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
-const ProgressBarAndroidToExport = React.forwardRef(ProgressBarAndroid);
+    /**
+     * Style of the ProgressBar. One of:
+     *
+     * - Horizontal
+     * - Normal (default)
+     * - Small
+     * - Large
+     * - Inverse
+     * - SmallInverse
+     * - LargeInverse
+     */
+    styleAttr: PropTypes.oneOf(STYLE_ATTRIBUTES),
+    /**
+     * Whether to show the ProgressBar (true, the default) or hide it (false).
+     */
+    animating: PropTypes.bool,
+    /**
+     * If the progress bar will show indeterminate progress. Note that this
+     * can only be false if styleAttr is Horizontal.
+     */
+    indeterminate: indeterminateType,
+    /**
+     * The progress value (between 0 and 1).
+     */
+    progress: PropTypes.number,
+    /**
+     * Color of the progress bar.
+     */
+    color: ColorPropType,
+    /**
+     * Used to locate this view in end-to-end tests.
+     */
+    testID: PropTypes.string,
+  };
+
+  static defaultProps = {
+    styleAttr: 'Normal',
+    indeterminate: true,
+    animating: true,
+  };
+
+  render() {
+    const {forwardedRef, ...props} = this.props;
+    return <AndroidProgressBar {...props} ref={forwardedRef} />;
+  }
+}
+
+const AndroidProgressBar = requireNativeComponent('AndroidProgressBar');
 
-module.exports = (ProgressBarAndroidToExport: Class<NativeComponent<Props>>);
+module.exports = React.forwardRef((props, ref) => (
+  <ProgressBarAndroid {...props} forwardedRef={ref} />
+));
diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index 17bd7cef971f..d9efe0170d8d 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -239,7 +239,6 @@ const Slider = (
     />
   );
 };
-Slider.displayName = 'Slider'; // TODO(T30332650) remove bug workaround
 
 // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
 const SliderWithRef = React.forwardRef(Slider);
@@ -251,9 +250,19 @@ SliderWithRef.defaultProps = {
   maximumValue: 1,
   step: 0,
 };
-
-const styles = StyleSheet.create({
-  slider: Platform.OS === 'ios' ? {height: 40} : {},
-});
+SliderWithRef.displayName = 'Slider';
+
+let styles;
+if (Platform.OS === 'ios') {
+  styles = StyleSheet.create({
+    slider: {
+      height: 40,
+    },
+  });
+} else {
+  styles = StyleSheet.create({
+    slider: {},
+  });
+}
 
 module.exports = (SliderWithRef: Class<ReactNative.NativeComponent<Props>>);

From 123512c5deb797759fd653f5a336b433013e83b5 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Mon, 11 Jun 2018 22:45:23 -0700
Subject: [PATCH 0778/1109] fix No bundle url present in iOS (#19643)

Summary:
fix No bundle url present in iOS.
Related issue: https://github.com/facebook/react-native/issues/14118, https://github.com/facebook/react-native/issues/12754.
Pass all current ci
none
 [GENERAL] [BUGFIX] [iOS] - fix No bundle url present in iOS
Closes https://github.com/facebook/react-native/pull/19643

Differential Revision: D8374583

Pulled By: hramos

fbshipit-source-id: 62d621f431d2067825dc701f87044ecb1d720f14
---
 local-cli/templates/HelloWorld/ios/HelloWorld/Info.plist | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/local-cli/templates/HelloWorld/ios/HelloWorld/Info.plist b/local-cli/templates/HelloWorld/ios/HelloWorld/Info.plist
index a58201cfa82b..51c65f542121 100644
--- a/local-cli/templates/HelloWorld/ios/HelloWorld/Info.plist
+++ b/local-cli/templates/HelloWorld/ios/HelloWorld/Info.plist
@@ -43,6 +43,8 @@
 	<key>NSAppTransportSecurity</key>
 	<!--See http://ste.vn/2015/06/10/configuring-app-transport-security-ios-9-osx-10-11/ -->
 	<dict>
+    <key>NSAllowsArbitraryLoads</key>
+    <true/>
 		<key>NSExceptionDomains</key>
 		<dict>
 			<key>localhost</key>

From cc07c9f0a3b667abb431c0da1555ef2f059a962c Mon Sep 17 00:00:00 2001
From: "Choma, Matus" <matus.choma@wirecard.com>
Date: Tue, 12 Jun 2018 08:42:14 -0700
Subject: [PATCH 0779/1109] Fixed comparison on possible null object (#19675)

Summary:
Motivation: getting NPE on BlobModule part

<img width="1718" alt="screen shot 2018-06-12 at 3 03 48 pm" src="https://user-images.githubusercontent.com/4340636/41292212-31e0acc8-6e52-11e8-916a-dd6fc2bb695a.png">

Should still build and pass all tests since project settings changes should be safe changes.

<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->

No documentation change is required
<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID][BUGFIX][BlobModule] safe equals checks

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/19675

Differential Revision: D8380228

Pulled By: hramos

fbshipit-source-id: 1d3caefdb7a7d638228490ef7b3771617745d26f
---
 .../java/com/facebook/react/modules/blob/BlobModule.java  | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BlobModule.java b/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BlobModule.java
index ee62d2cd2784..379a5735ebd4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BlobModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/blob/BlobModule.java
@@ -81,7 +81,7 @@ public boolean supports(Uri uri, String responseType) {
         String scheme = uri.getScheme();
         boolean isRemote = "http".equals(scheme) || "https".equals(scheme);
 
-        return (!isRemote && responseType.equals("blob"));
+        return (!isRemote && "blob".equals(responseType));
       }
 
       @Override
@@ -133,7 +133,7 @@ public RequestBody toRequestBody(ReadableMap data, String contentType) {
     new NetworkingModule.ResponseHandler() {
       @Override
       public boolean supports(String responseType) {
-        return responseType.equals("blob");
+        return "blob".equals(responseType);
       }
 
       @Override
@@ -236,7 +236,7 @@ private byte[] getBytesFromUri(Uri contentUri) throws IOException {
   }
 
   private String getNameFromUri(Uri contentUri) {
-    if (contentUri.getScheme().equals("file")) {
+    if ("file".equals(contentUri.getScheme())) {
       return contentUri.getLastPathSegment();
     }
     String[] projection = {MediaStore.MediaColumns.DISPLAY_NAME};
@@ -256,7 +256,7 @@ private String getNameFromUri(Uri contentUri) {
   }
 
   private long getLastModifiedFromUri(Uri contentUri) {
-    if (contentUri.getScheme().equals("file")) {
+    if ("file".equals(contentUri.getScheme())) {
       return new File(contentUri.toString()).lastModified();
     }
     return 0;

From f7657eaf027977e6855abad7c23cea4baad9cc16 Mon Sep 17 00:00:00 2001
From: Andrew Goodale <andrewgoodale@upserve.com>
Date: Tue, 12 Jun 2018 11:14:46 -0700
Subject: [PATCH 0780/1109] Implement console group APIs (#18555)

Summary:
Thank you for sending the PR! We appreciate you spending the time to work on these changes.
Help us understand your motivation by explaining why you decided to make this change.

React Native provides an implementation of the Web "Console" API, which is a powerful mechanism for debugging and analyzing RN apps. However, one subset of the Console API that RN does not provide is the "grouping" functions, namely `console.group` and `console.groupEnd`. These functions provide a useful way to see how an application behaves within a different parts of an application hierarchy.

I modified the "RNTester" app to create a console group each time an example is tapped, and the group is ended when the "Back" button is tapped. Here is an example of the grouping as seen in the Xcode console.

<img width="651" alt="console grouping" src="https://user-images.githubusercontent.com/445421/37882070-d2ae7860-306d-11e8-8cf4-be843a864f43.png">

https://github.com/facebook/react-native-website/pull/270

[GENERAL] [ENHANCEMENT] [console.js] - Add `console.group()` and `console.groupEnd()` APIs, matching the Web Console API.
Closes https://github.com/facebook/react-native/pull/18555

Differential Revision: D7992131

Pulled By: hramos

fbshipit-source-id: 0d28896292563922240ae2100ed49e35b6d1f102
---
 Libraries/polyfills/console.js | 26 ++++++++++++++++++++++++++
 1 file changed, 26 insertions(+)

diff --git a/Libraries/polyfills/console.js b/Libraries/polyfills/console.js
index 47970958a066..738dc8324442 100644
--- a/Libraries/polyfills/console.js
+++ b/Libraries/polyfills/console.js
@@ -428,6 +428,9 @@ function getNativeLogFunction(level) {
         INSPECTOR_FRAMES_TO_SKIP,
       );
     }
+    if (groupStack.length) {
+      str = groupFormat('', str);
+    }
     global.nativeLoggingHook(str, logLevel);
   };
 }
@@ -501,6 +504,27 @@ function consoleTablePolyfill(rows) {
   global.nativeLoggingHook('\n' + table.join('\n'), LOG_LEVELS.info);
 }
 
+const GROUP_PAD = '\u2502'; // Box light vertical
+const GROUP_OPEN = '\u2510'; // Box light down+left
+const GROUP_CLOSE = '\u2518'; // Box light up+left
+
+const groupStack = [];
+
+function groupFormat(prefix, msg) {
+  // Insert group formatting before the console message
+  return groupStack.join('') + prefix + ' ' + (msg || '');
+}
+
+function consoleGroupPolyfill(label) {
+  global.nativeLoggingHook(groupFormat(GROUP_OPEN, label), LOG_LEVELS.info);
+  groupStack.push(GROUP_PAD);
+}
+
+function consoleGroupEndPolyfill() {
+  groupStack.pop();
+  global.nativeLoggingHook(groupFormat(GROUP_CLOSE), LOG_LEVELS.info);
+}
+
 if (global.nativeLoggingHook) {
   const originalConsole = global.console;
   global.console = {
@@ -511,6 +535,8 @@ if (global.nativeLoggingHook) {
     trace: getNativeLogFunction(LOG_LEVELS.trace),
     debug: getNativeLogFunction(LOG_LEVELS.trace),
     table: consoleTablePolyfill,
+    group: consoleGroupPolyfill,
+    groupEnd: consoleGroupEndPolyfill,
   };
 
   // If available, also call the original `console` method since that is

From e3c5524bc65026a4c3d062cb05cee85b6d835286 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 12 Jun 2018 11:38:16 -0700
Subject: [PATCH 0781/1109] Bump soloader to 0.5.0 (#19676)

Summary:
Closes https://github.com/facebook/react-native/pull/19676

0.5.0 adds compatibility for Android P.

Reviewed By: mdvacca

Differential Revision: D8379610

fbshipit-source-id: cbef6c2e5e82e2d9e17756b00d210fecb04e8a40
---
 ReactAndroid/build.gradle | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index aa23d8898c0f..a8b472dfd24d 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -299,7 +299,7 @@ dependencies {
     compile 'com.facebook.fbui.textlayoutbuilder:textlayoutbuilder:1.0.0'
     compile 'com.facebook.fresco:fresco:1.9.0'
     compile 'com.facebook.fresco:imagepipeline-okhttp3:1.9.0'
-    compile 'com.facebook.soloader:soloader:0.3.0'
+    compile 'com.facebook.soloader:soloader:0.5.0'
     compile 'com.google.code.findbugs:jsr305:3.0.0'
     compile 'com.squareup.okhttp3:okhttp:3.10.0'
     compile 'com.squareup.okhttp3:okhttp-urlconnection:3.10.0'

From 39d9d71adbb77eff543fe442bd3061edc9858dd6 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 12 Jun 2018 13:43:47 -0700
Subject: [PATCH 0782/1109] Expose getResolverMainFields() config param

Reviewed By: mjesun

Differential Revision: D8380198

fbshipit-source-id: 3d5b7a5873095db2b90a23b5054fb94579df3f1a
---
 local-cli/bundle/buildBundle.js | 1 +
 local-cli/server/runServer.js   | 1 +
 local-cli/util/Config.js        | 5 +++--
 3 files changed, 5 insertions(+), 2 deletions(-)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index b6ad5a551053..818ddec9cbcd 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -88,6 +88,7 @@ async function buildBundle(
     extraNodeModules: config.extraNodeModules,
     getModulesRunBeforeMainModule: config.getModulesRunBeforeMainModule,
     getPolyfills: config.getPolyfills,
+    getResolverMainFields: config.getResolverMainFields,
     getRunModuleStatement: config.getRunModuleStatement,
     getTransformOptions: config.getTransformOptions,
     hasteImplModulePath: config.hasteImplModulePath,
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index ed2af28da942..0bd092cf4420 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -187,6 +187,7 @@ function getPackagerServer(args, config, reporter) {
     dynamicDepsInPackages: config.dynamicDepsInPackages,
     getModulesRunBeforeMainModule: config.getModulesRunBeforeMainModule,
     getPolyfills: config.getPolyfills,
+    getResolverMainFields: config.getResolverMainFields,
     getRunModuleStatement: config.getRunModuleStatement,
     getTransformOptions: config.getTransformOptions,
     hasteImplModulePath: config.hasteImplModulePath,
diff --git a/local-cli/util/Config.js b/local-cli/util/Config.js
index fc996aa067ce..bc7ba4716cdb 100644
--- a/local-cli/util/Config.js
+++ b/local-cli/util/Config.js
@@ -73,11 +73,12 @@ const Config = {
   DEFAULT: ({
     ...MetroConfig.DEFAULT,
     getBlacklistRE,
-    getProjectRoots,
-    getPolyfills,
     getModulesRunBeforeMainModule: () => [
       require.resolve('../../Libraries/Core/InitializeCore'),
     ],
+    getProjectRoots,
+    getPolyfills,
+    getResolverMainFields: () => ['react-native', 'browser', 'main'],
     getTransformModulePath: () =>
       require.resolve('metro/src/reactNativeTransformer'),
   }: ConfigT),

From a7a5b666eb4ccff5d4647bf8a5e31254b87a85ed Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 12 Jun 2018 13:43:49 -0700
Subject: [PATCH 0783/1109] Bump metro@0.39.0

Reviewed By: mjesun, davidaurelio

Differential Revision: D8380199

fbshipit-source-id: 6b9e3aa343e8d0526a3c42d5ea266c44428d31f8
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 16554be62ee1..9a34ef966ac7 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.38.1",
-    "metro-babel-register": "^0.38.1",
-    "metro-core": "^0.38.1",
-    "metro-memory-fs": "^0.38.1",
+    "metro": "^0.39.0",
+    "metro-babel-register": "^0.39.0",
+    "metro-core": "^0.39.0",
+    "metro-memory-fs": "^0.39.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 4f0b9e25545006fa22e745fdc8d0e6761b0e6d4e Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 12 Jun 2018 17:35:32 -0700
Subject: [PATCH 0784/1109] YellowBox: Apply SafeAreaView in Header

Summary: Uses `SafeAreaView` in the YellowBox inspector header so that it does not collide with the status bar.

Reviewed By: sahrens

Differential Revision: D8374861

fbshipit-source-id: e67358ac9268db8291cacf79df402f3bd5a2173d
---
 .../YellowBox/UI/YellowBoxInspectorHeader.js  | 39 ++++++++++++-------
 1 file changed, 24 insertions(+), 15 deletions(-)

diff --git a/Libraries/YellowBox/UI/YellowBoxInspectorHeader.js b/Libraries/YellowBox/UI/YellowBoxInspectorHeader.js
index 4ed124eaba22..b84afd8ca447 100644
--- a/Libraries/YellowBox/UI/YellowBoxInspectorHeader.js
+++ b/Libraries/YellowBox/UI/YellowBoxInspectorHeader.js
@@ -12,6 +12,7 @@
 
 const Platform = require('Platform');
 const React = require('React');
+const SafeAreaView = require('SafeAreaView');
 const StyleSheet = require('StyleSheet');
 const Text = require('Text');
 const UTFSequence = require('UTFSequence');
@@ -37,21 +38,23 @@ const YellowBoxInspectorHeader = (props: Props): React.Node => {
       : `Occurrence ${props.selectedIndex + 1} of ${props.warnings.length}`;
 
   return (
-    <View style={styles.header}>
-      <YellowBoxInspectorHeaderButton
-        disabled={props.warnings[prevIndex] == null}
-        label={UTFSequence.TRIANGLE_LEFT}
-        onPress={() => props.onSelectIndex(prevIndex)}
-      />
-      <View style={styles.headerTitle}>
-        <Text style={styles.headerTitleText}>{titleText}</Text>
+    <SafeAreaView style={styles.root}>
+      <View style={styles.header}>
+        <YellowBoxInspectorHeaderButton
+          disabled={props.warnings[prevIndex] == null}
+          label={UTFSequence.TRIANGLE_LEFT}
+          onPress={() => props.onSelectIndex(prevIndex)}
+        />
+        <View style={styles.headerTitle}>
+          <Text style={styles.headerTitleText}>{titleText}</Text>
+        </View>
+        <YellowBoxInspectorHeaderButton
+          disabled={props.warnings[nextIndex] == null}
+          label={UTFSequence.TRIANGLE_RIGHT}
+          onPress={() => props.onSelectIndex(nextIndex)}
+        />
       </View>
-      <YellowBoxInspectorHeaderButton
-        disabled={props.warnings[nextIndex] == null}
-        label={UTFSequence.TRIANGLE_RIGHT}
-        onPress={() => props.onSelectIndex(nextIndex)}
-      />
-    </View>
+    </SafeAreaView>
   );
 };
 
@@ -63,6 +66,10 @@ const YellowBoxInspectorHeaderButton = (
   |}>,
 ): React.Node => (
   <YellowBoxPressable
+    backgroundColor={{
+      default: 'transparent',
+      pressed: YellowBoxStyle.getHighlightColor(1),
+    }}
     onPress={props.disabled ? null : props.onPress}
     style={styles.headerButton}>
     {props.disabled ? null : (
@@ -72,6 +79,9 @@ const YellowBoxInspectorHeaderButton = (
 );
 
 const styles = StyleSheet.create({
+  root: {
+    backgroundColor: YellowBoxStyle.getBackgroundColor(0.95),
+  },
   header: {
     flexDirection: 'row',
     height: Platform.select({
@@ -92,7 +102,6 @@ const styles = StyleSheet.create({
   },
   headerTitle: {
     alignItems: 'center',
-    backgroundColor: YellowBoxStyle.getBackgroundColor(0.95),
     flex: 1,
     justifyContent: 'center',
   },

From 065c5b6590de18281a8c592a04240751c655c03c Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Wed, 13 Jun 2018 10:25:54 -0700
Subject: [PATCH 0785/1109] use android build-tools 26.0.2 and set compileSdk
 to 26 (#19662)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
Android Target API Level 26 will be required starting from August 2018, it's so soon 😄.Read https://android-developers.googleblog.com/2017/12/improving-app-security-and-performance.html

This PR uses android build tools 26.0.2, support library 26.1.0 (with android lifecycle) and setting compileSdkVersion to 26, but leaving minSdkVersion and targetSdkVersion intact, which will make targeting 26 easy.

Circle CI: https://circleci.com/gh/dulmandakh/react-native/209

Everything will build and work just fine.

[ANDROID] [ENHANCEMENT] [TOOLS] - Use android build-tools 26.0.2 and set compileSdk to 26, and use support library version 26.1.0.
Closes https://github.com/facebook/react-native/pull/19662

Differential Revision: D8398855

Pulled By: hramos

fbshipit-source-id: a4066eb04cb5f947efe1f3202b638c1092b79aae
---
 .buckconfig                                   |   3 +-
 RNTester/android/app/build.gradle             |   6 +-
 ReactAndroid/build.gradle                     |   6 +-
 ReactAndroid/libs/BUCK                        |   4 +-
 .../android/support-annotations/BUCK          |   4 +-
 .../main/third-party/android/support/v4/BUCK  | 101 +++++++++++++++++-
 .../android/support/v7/appcompat-orig/BUCK    |   4 +-
 .../link/__fixtures__/android/build.gradle    |   4 +-
 .../__fixtures__/android/patchedBuild.gradle  |   4 +-
 .../HelloWorld/android/app/build.gradle       |   6 +-
 scripts/.tests.env                            |   4 +-
 11 files changed, 119 insertions(+), 27 deletions(-)

diff --git a/.buckconfig b/.buckconfig
index 19c2d6302ea9..a4c6d696ba66 100644
--- a/.buckconfig
+++ b/.buckconfig
@@ -1,12 +1,13 @@
 
 [android]
-  target = Google Inc.:Google APIs:23
+  target = android-26
 
 [download]
   max_number_of_retries = 3
 
 [maven_repositories]
   central = https://repo1.maven.org/maven2
+  google = https://maven.google.com
 
 [alias]
   rntester = //RNTester/android/app:app
diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index 5e5503b5eb7c..b13742c58507 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -84,8 +84,8 @@ def enableSeparateBuildPerCPUArchitecture = false
 def enableProguardInReleaseBuilds = false
 
 android {
-    compileSdkVersion 23
-    buildToolsVersion "23.0.1"
+    compileSdkVersion 26
+    buildToolsVersion "26.0.2"
 
     defaultConfig {
         applicationId "com.facebook.react.uiapp"
@@ -137,7 +137,7 @@ android {
 
 dependencies {
     compile fileTree(dir: 'libs', include: ['*.jar'])
-    compile 'com.android.support:appcompat-v7:23.0.1'
+    compile 'com.android.support:appcompat-v7:26.1.0'
 
     // Build React Native from source
     compile project(':ReactAndroid')
diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index a8b472dfd24d..289ad9acd1e5 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -245,8 +245,8 @@ task packageReactNdkLibsForBuck(dependsOn: packageReactNdkLibs, type: Copy) {
 }
 
 android {
-    compileSdkVersion 23
-    buildToolsVersion "23.0.1"
+    compileSdkVersion 26
+    buildToolsVersion "26.0.2"
 
     defaultConfig {
         minSdkVersion 16
@@ -295,7 +295,7 @@ android {
 dependencies {
     compile fileTree(dir: 'src/main/third-party/java/infer-annotations/', include: ['*.jar'])
     compile 'javax.inject:javax.inject:1'
-    compile 'com.android.support:appcompat-v7:23.0.1'
+    compile 'com.android.support:appcompat-v7:26.1.0'
     compile 'com.facebook.fbui.textlayoutbuilder:textlayoutbuilder:1.0.0'
     compile 'com.facebook.fresco:fresco:1.9.0'
     compile 'com.facebook.fresco:imagepipeline-okhttp3:1.9.0'
diff --git a/ReactAndroid/libs/BUCK b/ReactAndroid/libs/BUCK
index f25db3234c62..018a73b2d7cb 100644
--- a/ReactAndroid/libs/BUCK
+++ b/ReactAndroid/libs/BUCK
@@ -6,8 +6,8 @@ android_prebuilt_aar(
 
 remote_file(
     name = "appcompat-binary-aar",
-    sha1 = "7d659f671541394a8bc2b9f909950aa2a5ec87ff",
-    url = "mvn:com.android.support:appcompat-v7:aar:23.0.1",
+    sha1 = "da5771a9ac6e8f3a461360eed3c6f921dc7580fd",
+    url = "mvn:com.android.support:appcompat-v7:aar:26.1.0",
 )
 
 android_prebuilt_aar(
diff --git a/ReactAndroid/src/main/third-party/android/support-annotations/BUCK b/ReactAndroid/src/main/third-party/android/support-annotations/BUCK
index bc18a5b2726b..dcffb71746b6 100644
--- a/ReactAndroid/src/main/third-party/android/support-annotations/BUCK
+++ b/ReactAndroid/src/main/third-party/android/support-annotations/BUCK
@@ -6,6 +6,6 @@ prebuilt_jar(
 
 remote_file(
     name = "support-annotations-binary-aar",
-    sha1 = "1fce89a6428c51467090d7f424e4c9c3dbd55f7e",
-    url = "mvn:com.android.support:support-annotations:jar:23.0.1",
+    sha1 = "0814258103cf26a15fcc26ecce35f5b7d24b73f8",
+    url = "mvn:com.android.support:support-annotations:jar:26.1.0",
 )
diff --git a/ReactAndroid/src/main/third-party/android/support/v4/BUCK b/ReactAndroid/src/main/third-party/android/support/v4/BUCK
index 92f5422141cb..39f58e962842 100644
--- a/ReactAndroid/src/main/third-party/android/support/v4/BUCK
+++ b/ReactAndroid/src/main/third-party/android/support/v4/BUCK
@@ -1,11 +1,102 @@
-android_prebuilt_aar(
+android_library(
     name = "lib-support-v4",
-    aar = ":lib-support-v4-binary-aar",
+    exported_deps = [
+      ":lib-support-v4-support-compat",
+      ":lib-support-v4-support-core-utils",
+      ":lib-support-v4-support-core-ui",
+      ":lib-support-v4-support-media-compat",
+      ":lib-support-v4-support-fragment",
+      ":android-lifecycle-runtime",
+      ":android-lifecycle-common.jar",
+      ":android-lifecycle-core.jar"
+    ],
     visibility = ["PUBLIC"],
 )
 
+prebuilt_jar(
+    name = "android-lifecycle-common.jar",
+    binary_jar = ":android-lifecycle-common-jar"
+)
+
+prebuilt_jar(
+    name = "android-lifecycle-core.jar",
+    binary_jar = ":android-lifecycle-core-jar"
+)
+
+android_prebuilt_aar(
+    name = "android-lifecycle-runtime",
+    aar = ":android-lifecycle-runtime-aar",
+)
+
+android_prebuilt_aar(
+    name = "lib-support-v4-support-compat",
+    aar = ":lib-support-v4-support-compat-aar",
+)
+
+android_prebuilt_aar(
+    name = "lib-support-v4-support-core-utils",
+    aar = ":lib-support-v4-support-core-utils-aar",
+)
+
+android_prebuilt_aar(
+    name = "lib-support-v4-support-core-ui",
+    aar = ":lib-support-v4-support-core-ui-aar",
+)
+
+android_prebuilt_aar(
+    name = "lib-support-v4-support-media-compat",
+    aar = ":lib-support-v4-support-media-compat-aar",
+)
+
+android_prebuilt_aar(
+    name = "lib-support-v4-support-fragment",
+    aar = ":lib-support-v4-support-fragment-aar",
+)
+
+remote_file(
+  name = "android-lifecycle-runtime-aar",
+  sha1 = "30c60a8a357ee1321ffd0c9f08ef54b24045cd10",
+  url = "mvn:android.arch.lifecycle:runtime:aar:1.0.0"
+)
+
 remote_file(
-    name = "lib-support-v4-binary-aar",
-    sha1 = "9e8da0e4ecf9f63258c7fbd273889252cba2d0c3",
-    url = "mvn:com.android.support:support-v4:aar:23.0.1",
+  name = "android-lifecycle-common-jar",
+  sha1 = "e414a4cb28434e25c4f6aa71426eb20cf4874ae9",
+  url = "mvn:android.arch.lifecycle:common:jar:1.0.0"
 )
+
+remote_file(
+  name = "android-lifecycle-core-jar",
+  sha1 = "a2d487452376193fc8c103dd2b9bd5f2b1b44563",
+  url = "mvn:android.arch.core:common:jar:1.0.0"
+)
+
+remote_file(
+    name = "lib-support-v4-support-compat-aar",
+    sha1 = "1e1c8ffc01d277d8f01dfd11d5d2ce3a2af4b98c",
+    url = "mvn:com.android.support:support-compat:aar:26.1.0",
+)
+
+remote_file(
+    name = "lib-support-v4-support-core-utils-aar",
+    sha1 = "1bfaae21c4d5c5532c5e732071e9ce234cd58cff",
+    url = "mvn:com.android.support:support-core-utils:aar:26.1.0",
+)
+
+remote_file(
+  name = "lib-support-v4-support-core-ui-aar",
+  sha1 = "e306308d54052a1ded7bf9c2f5c2fdf5152a1f22",
+  url = "mvn:com.android.support:support-core-ui:aar:26.1.0",
+)
+
+remote_file(
+  name = "lib-support-v4-support-media-compat-aar",
+  sha1 = "09fb587f27cde19aa8f2e50c5c9ee645d9aec44d",
+  url = "mvn:com.android.support:support-media-compat:aar:26.1.0",
+)
+
+remote_file(
+  name = "lib-support-v4-support-fragment-aar",
+  sha1 = "ddacf369bb98dd6558606558de8ddcd53895cf91",
+  url = "mvn:com.android.support:support-fragment:aar:26.1.0",
+)
\ No newline at end of file
diff --git a/ReactAndroid/src/main/third-party/android/support/v7/appcompat-orig/BUCK b/ReactAndroid/src/main/third-party/android/support/v7/appcompat-orig/BUCK
index 98aed703dd10..1dda81db7323 100644
--- a/ReactAndroid/src/main/third-party/android/support/v7/appcompat-orig/BUCK
+++ b/ReactAndroid/src/main/third-party/android/support/v7/appcompat-orig/BUCK
@@ -56,6 +56,6 @@ python_binary(
 
 remote_file(
     name = "appcompat-binary-aar",
-    sha1 = "7d659f671541394a8bc2b9f909950aa2a5ec87ff",
-    url = "mvn:com.android.support:appcompat-v7:aar:23.0.1",
+    sha1 = "da5771a9ac6e8f3a461360eed3c6f921dc7580fd",
+    url = "mvn:com.android.support:appcompat-v7:aar:26.1.0",
 )
diff --git a/local-cli/link/__fixtures__/android/build.gradle b/local-cli/link/__fixtures__/android/build.gradle
index 07f260d6d480..9eb0a44ae524 100644
--- a/local-cli/link/__fixtures__/android/build.gradle
+++ b/local-cli/link/__fixtures__/android/build.gradle
@@ -1,5 +1,5 @@
 dependencies {
     compile fileTree(dir: "libs", include: ["*.jar"])
-    compile "com.android.support:appcompat-v7:23.0.1"
-    compile "com.facebook.react:react-native:0.18.+"
+    compile "com.android.support:appcompat-v7:26.1.0"
+    compile "com.facebook.react:react-native:+"
 }
diff --git a/local-cli/link/__fixtures__/android/patchedBuild.gradle b/local-cli/link/__fixtures__/android/patchedBuild.gradle
index 68ccfec2eaa5..f6b9a22054cf 100644
--- a/local-cli/link/__fixtures__/android/patchedBuild.gradle
+++ b/local-cli/link/__fixtures__/android/patchedBuild.gradle
@@ -4,6 +4,6 @@ dependencies {
       exclude(group: 'org.unwanted', module: 'test10')
     }
     compile fileTree(dir: "libs", include: ["*.jar"])
-    compile "com.android.support:appcompat-v7:23.0.1"
-    compile "com.facebook.react:react-native:0.18.+"
+    compile "com.android.support:appcompat-v7:26.1.0"
+    compile "com.facebook.react:react-native:+"
 }
diff --git a/local-cli/templates/HelloWorld/android/app/build.gradle b/local-cli/templates/HelloWorld/android/app/build.gradle
index ec6f3022572a..2fad86f24a06 100644
--- a/local-cli/templates/HelloWorld/android/app/build.gradle
+++ b/local-cli/templates/HelloWorld/android/app/build.gradle
@@ -94,8 +94,8 @@ def enableSeparateBuildPerCPUArchitecture = false
 def enableProguardInReleaseBuilds = false
 
 android {
-    compileSdkVersion 23
-    buildToolsVersion "23.0.1"
+    compileSdkVersion 26
+    buildToolsVersion "26.0.2"
 
     defaultConfig {
         applicationId "com.helloworld"
@@ -138,7 +138,7 @@ android {
 
 dependencies {
     compile fileTree(dir: "libs", include: ["*.jar"])
-    compile "com.android.support:appcompat-v7:23.0.1"
+    compile "com.android.support:appcompat-v7:26.1.0"
     compile "com.facebook.react:react-native:+"  // From node_modules
 }
 
diff --git a/scripts/.tests.env b/scripts/.tests.env
index 285578295970..83e38520d58b 100644
--- a/scripts/.tests.env
+++ b/scripts/.tests.env
@@ -4,9 +4,9 @@
 
 ## ANDROID ##
 # Android SDK Build Tools revision
-export ANDROID_SDK_BUILD_TOOLS_REVISION=23.0.1
+export ANDROID_SDK_BUILD_TOOLS_REVISION=26.0.2
 # Android API Level we build with
-export ANDROID_SDK_BUILD_API_LEVEL="23"
+export ANDROID_SDK_BUILD_API_LEVEL="26"
 # Google APIs for Android level
 export ANDROID_GOOGLE_API_LEVEL="23"
 # Minimum Android API Level we target

From 3e3b10f4044ada7b523d363afb614720468c217f Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 13 Jun 2018 17:27:37 -0700
Subject: [PATCH 0786/1109] Support animated values for border dimensions

Summary:
The flow types for these were too restrictive.

Fixes https://github.com/facebook/react-native/issues/19093

Reviewed By: yungsters

Differential Revision: D8409550

fbshipit-source-id: e4774e8856efc998ff1fa6cdcbe7b0cb6db2c4e3
---
 Libraries/StyleSheet/StyleSheetTypes.js | 32 ++++++++++++-------------
 1 file changed, 16 insertions(+), 16 deletions(-)

diff --git a/Libraries/StyleSheet/StyleSheetTypes.js b/Libraries/StyleSheet/StyleSheetTypes.js
index 8fb8edd7bd90..41cab5de3b42 100644
--- a/Libraries/StyleSheet/StyleSheetTypes.js
+++ b/Libraries/StyleSheet/StyleSheetTypes.js
@@ -138,23 +138,23 @@ export type ____ViewStyle_Internal = $ReadOnly<{|
   borderRightColor?: ColorValue,
   borderStartColor?: ColorValue,
   borderTopColor?: ColorValue,
-  borderRadius?: number,
-  borderBottomEndRadius?: number,
-  borderBottomLeftRadius?: number,
-  borderBottomRightRadius?: number,
-  borderBottomStartRadius?: number,
-  borderTopEndRadius?: number,
-  borderTopLeftRadius?: number,
-  borderTopRightRadius?: number,
-  borderTopStartRadius?: number,
+  borderRadius?: number | AnimatedNode,
+  borderBottomEndRadius?: number | AnimatedNode,
+  borderBottomLeftRadius?: number | AnimatedNode,
+  borderBottomRightRadius?: number | AnimatedNode,
+  borderBottomStartRadius?: number | AnimatedNode,
+  borderTopEndRadius?: number | AnimatedNode,
+  borderTopLeftRadius?: number | AnimatedNode,
+  borderTopRightRadius?: number | AnimatedNode,
+  borderTopStartRadius?: number | AnimatedNode,
   borderStyle?: 'solid' | 'dotted' | 'dashed',
-  borderWidth?: number,
-  borderBottomWidth?: number,
-  borderEndWidth?: number,
-  borderLeftWidth?: number,
-  borderRightWidth?: number,
-  borderStartWidth?: number,
-  borderTopWidth?: number,
+  borderWidth?: number | AnimatedNode,
+  borderBottomWidth?: number | AnimatedNode,
+  borderEndWidth?: number | AnimatedNode,
+  borderLeftWidth?: number | AnimatedNode,
+  borderRightWidth?: number | AnimatedNode,
+  borderStartWidth?: number | AnimatedNode,
+  borderTopWidth?: number | AnimatedNode,
   opacity?: number | AnimatedNode,
   elevation?: number,
 |}>;

From f6da9e1a9a932d2775cc998469d2f9b4ebd858c5 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Wed, 13 Jun 2018 17:55:14 -0700
Subject: [PATCH 0787/1109] YellowBox: Define in __DEV__ Only

Summary: This makes it so that `YellowBox` and its dependencies are completely stripped from production bundles.

Reviewed By: sahrens

Differential Revision: D8402545

fbshipit-source-id: 6993521280a02dfe5eab8863d12c46781f35444f
---
 Libraries/YellowBox/YellowBox.js | 163 ++++++++++++++++++-------------
 1 file changed, 94 insertions(+), 69 deletions(-)

diff --git a/Libraries/YellowBox/YellowBox.js b/Libraries/YellowBox/YellowBox.js
index 45a6dbc3bcf9..10d8ba4a007f 100644
--- a/Libraries/YellowBox/YellowBox.js
+++ b/Libraries/YellowBox/YellowBox.js
@@ -10,11 +10,7 @@
 
 'use strict';
 
-const Platform = require('Platform');
-const RCTLog = require('RCTLog');
 const React = require('React');
-const YellowBoxList = require('YellowBoxList');
-const YellowBoxRegistry = require('YellowBoxRegistry');
 
 import type {Category} from 'YellowBoxCategory';
 import type {Registry, Subscription} from 'YellowBoxRegistry';
@@ -24,7 +20,7 @@ type State = {|
   registry: ?Registry,
 |};
 
-const {error, warn} = console;
+let YellowBox;
 
 /**
  * YellowBox displays warnings at the bottom of the screen.
@@ -44,89 +40,118 @@ const {error, warn} = console;
  * Strings supplied to `YellowBox.ignoreWarnings` only need to be a substring of
  * the ignored warning messages.
  */
-class YellowBox extends React.Component<Props, State> {
-  static ignoreWarnings(patterns: $ReadOnlyArray<string>): void {
-    YellowBoxRegistry.addIgnorePatterns(patterns);
-  }
+if (__DEV__) {
+  const Platform = require('Platform');
+  const RCTLog = require('RCTLog');
+  const YellowBoxList = require('YellowBoxList');
+  const YellowBoxRegistry = require('YellowBoxRegistry');
+
+  const {error, warn} = console;
+
+  // eslint-disable-next-line no-shadow
+  YellowBox = class YellowBox extends React.Component<Props, State> {
+    static ignoreWarnings(patterns: $ReadOnlyArray<string>): void {
+      YellowBoxRegistry.addIgnorePatterns(patterns);
+    }
 
-  static install(): void {
-    (console: any).error = function(...args) {
-      error.call(console, ...args);
-      // Show YellowBox for the `warning` module.
-      if (typeof args[0] === 'string' && args[0].startsWith('Warning: ')) {
+    static install(): void {
+      (console: any).error = function(...args) {
+        error.call(console, ...args);
+        // Show YellowBox for the `warning` module.
+        if (typeof args[0] === 'string' && args[0].startsWith('Warning: ')) {
+          registerWarning(...args);
+        }
+      };
+
+      (console: any).warn = function(...args) {
+        warn.call(console, ...args);
         registerWarning(...args);
+      };
+
+      if ((console: any).disableYellowBox === true) {
+        YellowBoxRegistry.setDisabled(true);
+      }
+      (Object.defineProperty: any)(console, 'disableYellowBox', {
+        configurable: true,
+        get: () => YellowBoxRegistry.isDisabled(),
+        set: value => YellowBoxRegistry.setDisabled(value),
+      });
+
+      if (Platform.isTesting) {
+        (console: any).disableYellowBox = true;
       }
-    };
 
-    (console: any).warn = function(...args) {
-      warn.call(console, ...args);
-      registerWarning(...args);
-    };
+      RCTLog.setWarningHandler((...args) => {
+        registerWarning(...args);
+      });
+    }
 
-    if ((console: any).disableYellowBox === true) {
-      YellowBoxRegistry.setDisabled(true);
+    static uninstall(): void {
+      (console: any).error = error;
+      (console: any).warn = error;
+      delete (console: any).disableYellowBox;
     }
-    (Object.defineProperty: any)(console, 'disableYellowBox', {
-      configurable: true,
-      get: () => YellowBoxRegistry.isDisabled(),
-      set: value => YellowBoxRegistry.setDisabled(value),
-    });
-
-    if (Platform.isTesting) {
-      (console: any).disableYellowBox = true;
+
+    _subscription: ?Subscription;
+
+    state = {
+      registry: null,
+    };
+
+    render(): React.Node {
+      // TODO: Ignore warnings that fire when rendering `YellowBox` itself.
+      return this.state.registry == null ? null : (
+        <YellowBoxList
+          onDismiss={this._handleDismiss}
+          onDismissAll={this._handleDismissAll}
+          registry={this.state.registry}
+        />
+      );
     }
 
-    RCTLog.setWarningHandler((...args) => {
-      registerWarning(...args);
-    });
-  }
+    componentDidMount(): void {
+      this._subscription = YellowBoxRegistry.observe(registry => {
+        this.setState({registry});
+      });
+    }
 
-  static uninstall(): void {
-    (console: any).error = error;
-    (console: any).warn = error;
-    delete (console: any).disableYellowBox;
-  }
+    componentWillUnmount(): void {
+      if (this._subscription != null) {
+        this._subscription.unsubscribe();
+      }
+    }
 
-  _subscription: ?Subscription;
+    _handleDismiss = (category: Category): void => {
+      YellowBoxRegistry.delete(category);
+    };
 
-  state = {
-    registry: null,
+    _handleDismissAll(): void {
+      YellowBoxRegistry.clear();
+    }
   };
 
-  render() {
-    // TODO: Ignore warnings that fire when rendering `YellowBox` itself.
-    return this.state.registry == null ? null : (
-      <YellowBoxList
-        onDismiss={this._handleDismiss}
-        onDismissAll={this._handleDismissAll}
-        registry={this.state.registry}
-      />
-    );
+  function registerWarning(...args): void {
+    YellowBoxRegistry.add({args, framesToPop: 2});
   }
+} else {
+  // eslint-disable-next-line no-shadow
+  YellowBox = class YellowBox extends React.Component<Props> {
+    static ignoreWarnings(patterns: $ReadOnlyArray<string>): void {
+      // Do nothing.
+    }
 
-  componentDidMount(): void {
-    this._subscription = YellowBoxRegistry.observe(registry => {
-      this.setState({registry});
-    });
-  }
+    static install(): void {
+      // Do nothing.
+    }
 
-  componentWillUnmount(): void {
-    if (this._subscription != null) {
-      this._subscription.unsubscribe();
+    static uninstall(): void {
+      // Do nothing.
     }
-  }
 
-  _handleDismiss = (category: Category): void => {
-    YellowBoxRegistry.delete(category);
+    render(): React.Node {
+      return null;
+    }
   };
-
-  _handleDismissAll(): void {
-    YellowBoxRegistry.clear();
-  }
-}
-
-function registerWarning(...args): void {
-  YellowBoxRegistry.add({args, framesToPop: 2});
 }
 
 module.exports = YellowBox;

From 8baaacb66458dd706421fcbc1fc1934cd1ebbb94 Mon Sep 17 00:00:00 2001
From: Mattijs Fuijkschot <mattijs@innovactory.com>
Date: Wed, 13 Jun 2018 22:44:29 -0700
Subject: [PATCH 0788/1109] - Keyboard layout now updates when changing
 keyboardType while it has focus (#19027)

Summary:
This PR makes sure that changing the `keyboardType` props of `<TextInput>` is reflected while the text field has focus. It is something that is also discusses in #13782. The workaround mentioned in that issue using `key` causes the TextInput to re-render itself which has some undesired side-effects.

Fixes #13782

```javascript
export default class KeyboardTypeApp extends Component {
  state = { keyboardType: 'default' };

  toggleKeyboardType = () => {
    this.setState({
      keyboardType: this.state.keyboardType === 'default' ? 'numeric' : 'default'
    });
  }

  render() {
    return (
      <View style={{ padding: 40 }}>
        <TextInput autoFocus value="Press Toggle :)" keyboardType={this.state.keyboardType} />
        <Button title="Toggle" onPress={this.toggleKeyboardType} />
      </View>
    );
  }
}
```

![video](https://user-images.githubusercontent.com/706368/39268429-3e331440-48d0-11e8-947c-7d334e3cec50.gif)

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

 [IOS] [ENHANCEMENT] [TextInput] - Keyboard layout now updates when changing `keyboardType` while it has focus

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/19027

Differential Revision: D8416007

Pulled By: PeteTheHeat

fbshipit-source-id: c4f89ab3dc0819bca52feddbc9c7a9f62fd96794
---
 Libraries/Text/TextInput/RCTBaseTextInputView.h |  1 +
 Libraries/Text/TextInput/RCTBaseTextInputView.m | 17 +++++++++++++++++
 .../TextInput/RCTBaseTextInputViewManager.m     |  2 +-
 3 files changed, 19 insertions(+), 1 deletion(-)

diff --git a/Libraries/Text/TextInput/RCTBaseTextInputView.h b/Libraries/Text/TextInput/RCTBaseTextInputView.h
index 6de343f2fa06..1ea3d8df46be 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputView.h
+++ b/Libraries/Text/TextInput/RCTBaseTextInputView.h
@@ -47,6 +47,7 @@ NS_ASSUME_NONNULL_BEGIN
 @property (nonatomic, strong, nullable) NSNumber *maxLength;
 @property (nonatomic, copy) NSAttributedString *attributedText;
 @property (nonatomic, copy) NSString *inputAccessoryViewID;
+@property (nonatomic, assign) UIKeyboardType keyboardType;
 
 @end
 
diff --git a/Libraries/Text/TextInput/RCTBaseTextInputView.m b/Libraries/Text/TextInput/RCTBaseTextInputView.m
index cbfa24d1ab4f..9ba7df140a3e 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputView.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputView.m
@@ -178,6 +178,23 @@ - (void)setTextContentType:(NSString *)type
   #endif
 }
 
+- (UIKeyboardType)keyboardType
+{
+  return self.backedTextInputView.keyboardType;
+}
+
+- (void)setKeyboardType:(UIKeyboardType)keyboardType
+{
+  UIView<RCTBackedTextInputViewProtocol> *textInputView = self.backedTextInputView;
+  if (textInputView.keyboardType != keyboardType) {
+    textInputView.keyboardType = keyboardType;
+    // Without the call to reloadInputViews, the keyboard will not change until the textview field (the first responder) loses and regains focus.
+    if (textInputView.isFirstResponder) {
+      [textInputView reloadInputViews];
+    }
+  }
+}
+
 #pragma mark - RCTBackedTextInputDelegate
 
 - (BOOL)textInputShouldBeginEditing
diff --git a/Libraries/Text/TextInput/RCTBaseTextInputViewManager.m b/Libraries/Text/TextInput/RCTBaseTextInputViewManager.m
index 42266eacfb91..d5c493280428 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputViewManager.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputViewManager.m
@@ -40,7 +40,6 @@ @implementation RCTBaseTextInputViewManager
 RCT_REMAP_VIEW_PROPERTY(editable, backedTextInputView.editable, BOOL)
 RCT_REMAP_VIEW_PROPERTY(enablesReturnKeyAutomatically, backedTextInputView.enablesReturnKeyAutomatically, BOOL)
 RCT_REMAP_VIEW_PROPERTY(keyboardAppearance, backedTextInputView.keyboardAppearance, UIKeyboardAppearance)
-RCT_REMAP_VIEW_PROPERTY(keyboardType, backedTextInputView.keyboardType, UIKeyboardType)
 RCT_REMAP_VIEW_PROPERTY(placeholder, backedTextInputView.placeholder, NSString)
 RCT_REMAP_VIEW_PROPERTY(placeholderTextColor, backedTextInputView.placeholderColor, UIColor)
 RCT_REMAP_VIEW_PROPERTY(returnKeyType, backedTextInputView.returnKeyType, UIReturnKeyType)
@@ -51,6 +50,7 @@ @implementation RCTBaseTextInputViewManager
 RCT_REMAP_VIEW_PROPERTY(clearButtonMode, backedTextInputView.clearButtonMode, UITextFieldViewMode)
 RCT_EXPORT_VIEW_PROPERTY(blurOnSubmit, BOOL)
 RCT_EXPORT_VIEW_PROPERTY(clearTextOnFocus, BOOL)
+RCT_EXPORT_VIEW_PROPERTY(keyboardType, UIKeyboardType)
 RCT_EXPORT_VIEW_PROPERTY(maxLength, NSNumber)
 RCT_EXPORT_VIEW_PROPERTY(selectTextOnFocus, BOOL)
 RCT_EXPORT_VIEW_PROPERTY(selection, RCTTextSelection)

From ef4c42d2848afe82b3e17caea20dff16eff55e05 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Thu, 14 Jun 2018 06:15:06 -0700
Subject: [PATCH 0789/1109] Bumping Metro to 0.39.1

Reviewed By: rafeca

Differential Revision: D8418105

fbshipit-source-id: 66032deb53f46a388b81233e8d00d7af6a2c7fa7
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 9a34ef966ac7..b76351695c7d 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.39.0",
-    "metro-babel-register": "^0.39.0",
-    "metro-core": "^0.39.0",
-    "metro-memory-fs": "^0.39.0",
+    "metro": "^0.39.1",
+    "metro-babel-register": "^0.39.1",
+    "metro-core": "^0.39.1",
+    "metro-memory-fs": "^0.39.1",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From e3d3533bc5da16ea9cefdb1e1404c1f7d56b1e65 Mon Sep 17 00:00:00 2001
From: Vojtech Novak <vonovak@gmail.com>
Date: Thu, 14 Jun 2018 08:19:37 -0700
Subject: [PATCH 0790/1109] improve NativeModuleRegistryBuilder.java (#16402)

Summary:
I met the error `Native module xyz tried to override xyz for module name xyzModuleName. If this was your intention...` after something went wrong during `react-native link` - one module somehow ended up being included twice in the `getPackages` method, as in:

```java
Override
        protected List<ReactPackage> getPackages() {
            return Arrays.<ReactPackage>asList(
                    new MainReactPackage(),
            new WowPackage(),
            new WowPackage(),
```

Since I have > 20 native modules it took me a little while to find out what the problem was. The improved error message should make the problem clearer to anybody who may encounter it. I did try to refactor the code a little more, by extracting the whole part of:

```java
        String name = moduleHolder.getName();
        if (namesToType.containsKey(name)) {
          Class<? extends NativeModule> existingNativeModule = namesToType.get(name);
          if (!moduleHolder.getCanOverrideExistingModule()) {
            throw new IllegalStateException(getModuleOverridingExceptionMessage(
              type.getSimpleName(),
              existingNativeModule.getSimpleName(),
              name
            ));
          }

          mModules.remove(existingNativeModule);
        }

        namesToType.put(name, type);
        mModules.put(type, moduleHolder);
```

out into a separate method since there were two places where nearly identical code was written.

I have built RN from source and used it in a very simple app with RN vector icons (the package creates a native module as can be seen [here](https://github.com/oblador/react-native-vector-icons/blob/master/android/src/main/java/com/oblador/vectoricons/VectorIconsPackage.java#L19)).

After including the module twice, ie.

```java
        Override
        protected List<ReactPackage> getPackages() {
            return Arrays.<ReactPackage>asList(
                    new MainReactPackage(),
                    new VectorIconsPackage(),
                    new VectorIconsPackage()
            );
        }
```

I get the improved error description, as seen in the screenshot.

<img src="https://user-images.githubusercontent.com/1566403/36340960-3289d9d0-13e7-11e8-8d17-e1651da17841.png" height="500">

[ANDROID] [MINOR] [NativeModuleRegistryBuilder] - Improve error message and refactor putting native modules to module maps
Closes https://github.com/facebook/react-native/pull/16402

Differential Revision: D8421392

Pulled By: hramos

fbshipit-source-id: 719bd37b4681933d35858621b402ae73dd460a5b
---
 .../react/NativeModuleRegistryBuilder.java    | 36 ++++++++-----------
 1 file changed, 15 insertions(+), 21 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/NativeModuleRegistryBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/NativeModuleRegistryBuilder.java
index fe0a2624ac00..85097e7a6036 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/NativeModuleRegistryBuilder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/NativeModuleRegistryBuilder.java
@@ -80,19 +80,7 @@ public void processPackage(ReactPackage reactPackage) {
         }
 
         String name = moduleHolder.getName();
-        if (namesToType.containsKey(name)) {
-          Class<? extends NativeModule> existingNativeModule = namesToType.get(name);
-          if (!moduleHolder.getCanOverrideExistingModule()) {
-            throw new IllegalStateException("Native module " + type.getSimpleName() +
-              " tried to override " + existingNativeModule.getSimpleName() + " for module name " +
-              name + ". If this was your intention, set canOverrideExistingModule=true");
-          }
-
-          mModules.remove(existingNativeModule);
-        }
-
-        namesToType.put(name, type);
-        mModules.put(type, moduleHolder);
+        putModuleTypeAndHolderToModuleMaps(type, name, moduleHolder);
       }
     } else {
       FLog.d(
@@ -117,19 +105,25 @@ public void processPackage(ReactPackage reactPackage) {
   public void addNativeModule(NativeModule nativeModule) {
     String name = nativeModule.getName();
     Class<? extends NativeModule> type = nativeModule.getClass();
-    if (namesToType.containsKey(name)) {
-      Class<? extends NativeModule> existingModule = namesToType.get(name);
-      if (!nativeModule.canOverrideExistingModule()) {
+    putModuleTypeAndHolderToModuleMaps(type, name, new ModuleHolder(nativeModule));
+  }
+
+  private void putModuleTypeAndHolderToModuleMaps(Class<? extends NativeModule> type, String underName,
+                                                  ModuleHolder moduleHolder) throws IllegalStateException {
+    if (namesToType.containsKey(underName)) {
+      Class<? extends NativeModule> existingNativeModule = namesToType.get(underName);
+      if (!moduleHolder.getCanOverrideExistingModule()) {
         throw new IllegalStateException("Native module " + type.getSimpleName() +
-          " tried to override " + existingModule.getSimpleName() + " for module name " +
-          name + ". If this was your intention, set canOverrideExistingModule=true");
+          " tried to override " + existingNativeModule.getSimpleName() + " for module name " +
+          underName + ". Check the getPackages() method in MainApplication.java, it might be " +
+          "that module is being created twice. " +
+          "If this was your intention, set canOverrideExistingModule=true");
       }
 
-      mModules.remove(existingModule);
+      mModules.remove(existingNativeModule);
     }
 
-    namesToType.put(name, type);
-    ModuleHolder moduleHolder = new ModuleHolder(nativeModule);
+    namesToType.put(underName, type);
     mModules.put(type, moduleHolder);
   }
 

From e8087eccdb65465d36bea483e208db526188e575 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Thu, 14 Jun 2018 08:55:39 -0700
Subject: [PATCH 0791/1109] YellowBox: Restore ES5 Compatibility

Reviewed By: sahrens

Differential Revision: D8421561

fbshipit-source-id: c2b8d430f4d0c9ce0d5177f0af5eb5f404916024
---
 Libraries/YellowBox/YellowBox.js | 7 +++----
 1 file changed, 3 insertions(+), 4 deletions(-)

diff --git a/Libraries/YellowBox/YellowBox.js b/Libraries/YellowBox/YellowBox.js
index 10d8ba4a007f..16d1b453cf9c 100644
--- a/Libraries/YellowBox/YellowBox.js
+++ b/Libraries/YellowBox/YellowBox.js
@@ -130,12 +130,11 @@ if (__DEV__) {
     }
   };
 
-  function registerWarning(...args): void {
+  const registerWarning = (...args): void => {
     YellowBoxRegistry.add({args, framesToPop: 2});
-  }
+  };
 } else {
-  // eslint-disable-next-line no-shadow
-  YellowBox = class YellowBox extends React.Component<Props> {
+  YellowBox = class extends React.Component<Props> {
     static ignoreWarnings(patterns: $ReadOnlyArray<string>): void {
       // Do nothing.
     }

From 0858300f747d672e6b4b44208a22169a2224bd5d Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Thu, 14 Jun 2018 13:48:15 -0700
Subject: [PATCH 0792/1109] Publish releases automatically, update docs
 (#19715)

Summary:
Now that tests are green, we can return to automatic publishing to npm based on git tags. As long as all tests are passing, deploying a new release of React Native is as easy as tagging a commit. I've updated `Releases.md` to reflect today's release process.

Future Work: Include information about updating the website, as this is no longer done automatically.
Closes https://github.com/facebook/react-native/pull/19715

Differential Revision: D8429834

Pulled By: hramos

fbshipit-source-id: 2c6f2c80ac43c4e6d20c01e06ba14a7e4b16180d
---
 .circleci/config.yml | 25 +++++++------
 Releases.md          | 86 ++++++++++++++++----------------------------
 2 files changed, 45 insertions(+), 66 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 185be9135eb4..7b838f52fce7 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -652,6 +652,20 @@ workflows:
           requires:
             - checkout_code
 
+      # Only runs on vX.X.X tags if all tests are green
+      - publish_npm_package:
+          filters:
+            branches:
+              ignore: /.*/
+            tags:
+              only: /v[0-9]+(\.[0-9]+)*(\-rc(\.[0-9]+)?)?/
+          requires:
+            - test_javascript
+            - test_ios
+            - test_tvos
+            - test_end_to_end
+            - analyze
+
   # Only runs on PRs
   analyze:
     jobs:
@@ -665,17 +679,6 @@ workflows:
           requires:
             - checkout_code
 
-  # Only runs on NN-stable branches
-  deploy:
-    jobs:
-      # If we are on a stable branch, wait for approval to deploy to npm
-      - approve_publish_npm_package:
-          filters: *filter-only-stable
-          type: approval
-
-      - publish_npm_package:
-          requires:
-            - approve_publish_npm_package
 
   # These tests are flaky or are yet to be fixed. They are placed on their own
   # workflow to avoid marking benign PRs as broken.
diff --git a/Releases.md b/Releases.md
index 62e0a8f5c1d3..cd6948ae13e3 100644
--- a/Releases.md
+++ b/Releases.md
@@ -14,14 +14,10 @@ React Native follows a monthly release train. Every month, a new branch created
 | 0.40.0  | 1st of December     | 1st of January   |
 | 0.41.0  | 1st of January      | 1st of February  |
 | 0.42.0  | 1st of February     | 1st of March     |
-| 0.43.0  | 1st of March        | 1st of April     |
-| 0.44.0  | 1st of April        | 1st of May       |
-| 0.45.0  | 1st of May          | 1st of June      |
-| 0.46.0  | 1st of June         | 1st of July      |
-| 0.47.0  | 1st of July         | 1st of August    |
-| 0.48.0  | 1st of August       | 1st of September |
-| 0.49.0  | 1st of September    | 1st of October   |
-| 0.50.0  | 1st of October      | 1st of November  |
+|  ...    |       ...           |      ...         |
+| 0.56.0  | 1st of June         | 1st of July      |
+| 0.57.0  | 1st of July         | 1st of August    |
+| 0.58.0  | 1st of August       | 1st of October   |
 | ...     | ...                 | ...              |
 
 -------------------
@@ -31,15 +27,16 @@ React Native follows a monthly release train. Every month, a new branch created
 ### Prerequisites
 
 The following are required for the local test suite to run:
+
 - macOS with [Android dev environment set up](https://github.com/facebook/react-native/blob/master/ReactAndroid/README.md)
-- At least 0.2.0 [react-native-cli](https://www.npmjs.com/package/react-native-cli) installed globally
+- [react-native-cli](https://www.npmjs.com/package/react-native-cli) installed globally (v0.2.0 or newer)
 
 ### Step 1: Check everything works
 
 Before cutting a release branch, make sure [Circle](https://circleci.com/gh/facebook/react-native) CI system is green.
 
-
 Before executing the following script, make sure you have:
+
 - An Android emulator / Genymotion device running
 - No packager running in any of the projects
 
@@ -57,18 +54,14 @@ Run:
 
 ```bash
 git checkout -b <version_you_are_releasing>-stable
-# e.g. git checkout -b 0.50-stable
+# e.g. git checkout -b 0.57-stable
 
-./scripts/bump-oss-version.js <exact-version_you_are_releasing>
-# e.g. ./scripts/bump-oss-version.js 0.50.0-rc
-# You can use the --remote option to specify a Git remote other than the default "origin"
-git push --tags
-git push
+./scripts/bump-oss-version.js <exact_version_you_are_releasing>
+# e.g. ./scripts/bump-oss-version.js 0.57.0-rc.0
+#  or  ./scripts/bump-oss-version.js 0.58.0
 ```
 
-Circle CI will automatically run the tests and publish to npm with the version you have specified (e.g `0.50.0-rc`) and tag `next` meaning that this version will not be installed for users by default.
-
-Go to [Circle CI](https://circleci.com/gh/facebook/react-native) and look for the build triggered by your push (e.g. _0.50-stable, [0.50.0] Bump version numbers_), then scroll down to the npm publish step to verify the package was published successfully (the build will be red if not).
+Circle CI will automatically run the tests and publish to npm with the version you have specified (e.g `0.57.0-rc.0`) and tag `next` meaning that this version will not be installed for users by default.
 
 ### Step 3: Write the release notes
 
@@ -89,7 +82,9 @@ Sometimes commit messages might be really short / confusing - try rewording them
 - `Fix logging reported by RUN_JS_BUNDLE` -> `Fix systrace logging of RUN_JS_BUNDLE event`
 - `Fixes hot code reloading issue` -> `Fix an edge case in hot module reloading`
 
-Before posting the list of changes, consider asking one of contributors for their opinion. Once everything is ready, post the release notes: https://github.com/facebook/react-native/releases
+Open a pull request against CHANGELOG.md at https://github.com/react-native-community/react-native-releases and ask for feedback.
+
+Once everything is ready, create a new release at https://github.com/facebook/react-native/releases and link to the release notes.
 
 **Important**: For release candidate releases, make sure to check "This is a pre-release".
 
@@ -109,7 +104,7 @@ Now that the release is out in the open, go ahead and create a GitHub issue titl
 
 -------------------
 
-## How to release an RC update (e.g. 0.50.0-rc.1, 0.50.0-rc.2)
+## How to release an RC update (e.g. 0.57.0-rc.1, 0.57.0-rc.2)
 
 The release is now in the open, people are finding bugs, and fixes have landed in master. People have been nominating fixes in the issue you created above. Use your best judgment to decide which commits merit an RC update. It's a good idea to do a new RC release when several small and non-risky bugs have been fixed. Having a few RC releases can also help people bisect in case we cherry-pick a bad commit by mistake.
 
@@ -122,10 +117,10 @@ Follow these steps to check out the release branch:
 
 ```bash
 git checkout <version_you_are_patching>-stable
-# e.g. git checkout 0.50-stable
+# e.g. git checkout 0.57-stable
 
 git pull origin <version_you_are_patching>-stable
-# e.g. git pull origin 0.50-stable
+# e.g. git pull origin 0.57-stable
 ```
 
 > If you don't have a local checkout of the release branch, you can run the following instead:
@@ -153,40 +148,31 @@ If everything worked, run the following to bump the version number:
 
 ```bash
 ./scripts/bump-oss-version.js <exact_version_you_are_releasing>
-# e.g. ./scripts/bump-oss-version.js 0.50.0-rc.1
+# e.g. ./scripts/bump-oss-version.js 0.57.0-rc.1
 ```
 
-### Step 5: Push to GitHub
-
-Finally, push the new tags and commits to GitHub:
-
-```
-git push --tags
-git push
-````
+Again, Circle CI will automatically run the tests and publish to npm with the version you have specified (e.g `0.57.0-rc.1`).
 
-Again, Circle CI will automatically run the tests and publish to npm with the version you have specified (e.g `0.50.0-rc.1`).
-
-### Step 6: Update the release notes
+### Step 5: Update the release notes
 
-Go to https://github.com/facebook/react-native/releases and find the release notes for this release candidate. Edit them so that they now point to the tag that you've just created. We want single release notes per version. For example, if there is v0.50.0-rc and you just released v0.50.0-rc.1, the release notes should live on the v0.50.0-rc.1 tag at https://github.com/facebook/react-native/tags
+Go to https://github.com/facebook/react-native/releases and find the release notes for this release candidate. Edit them so that they now point to the tag that you've just created. We want single release notes per version. For example, if there is v0.57.0-rc and you just released v0.57.0-rc.1, the release notes should live on the v0.57.0-rc.1 tag at https://github.com/facebook/react-native/tags
 
 -------------------
 
-## How to do the final stable release (e.g. 0.50.0, 0.50.1)
+## How to do the final stable release (e.g. 0.57.0, 0.57.1)
 
 A stable release is promoted roughly a month after the release branch is cut (refer to the schedule above). The release may be delayed for several reasons, including major issues in the release candidate. Make sure that all bug fixes that have been nominated in your tracking issue have been addressed as needed. Avoid cherry-picking commits that have not been vetted in the release candidate phase at this point.
 
-Once you are sure that the release is solid, perform the following steps. Note that they're similar to the steps you may have followed earlier when patching the release candidate, but we're not cherry-picking any additional commits at this point. 
+Once you are sure that the release is solid, perform the following steps. Note that they're similar to the steps you may have followed earlier when patching the release candidate, but we're not cherry-picking any additional commits at this point.
 
 ### Step 1: Check out the release branch
 
 ```bash
 git checkout <version_you_are_patching>-stable
-# e.g. git checkout 0.50-stable
+# e.g. git checkout 0.57-stable
 
 git pull origin <version_you_are_patching>-stable
-# e.g. git pull origin 0.50-stable
+# e.g. git pull origin 0.57-stable
 ```
 
 > If you don't have a local checkout of the release branch, you can run the following instead:
@@ -206,28 +192,18 @@ If everything worked:
 
 ```bash
 ./scripts/bump-oss-version.js <exact_version_you_are_releasing>
-# e.g. ./scripts/bump-oss-version.js 0.50.0
-```
-
-### Step 4: Push to GitHub
-
-Finally, push the new tags and commits to GitHub:
-
-```
-git push --tags
-git push
+# e.g. ./scripts/bump-oss-version.js 0.57.0
 ```
 
-As with the release candidate, Circle CI will automatically run the tests and publish to npm with the version you have specified (e.g `0.50.0`).
+As with the release candidate, Circle CI will automatically run the tests and publish to npm with the version you have specified (e.g `0.57.0`).
 
-Go to [Circle CI](https://circleci.com/gh/facebook/react-native) and look for the build triggered by your push (e.g. _0.50-stable, [0.50.0] Bump version numbers_), then scroll down to the npm publish step to verify the package was published successfully (the build will be red if not).
+Go to [Circle CI](https://circleci.com/gh/facebook/react-native) and look for the build triggered by your push (e.g. _0.57-stable, [0.57.0] Bump version numbers_), then scroll down to the npm publish step to verify the package was published successfully (the build will be red if not).
 
 This will now become the latest release, and will be installed by users by default. At this point, the website will be updated and the docs for this release will be displayed by default.
 
-### Step 5: Update the release notes
+### Step 4: Update the release notes
 
-Once you see that the website is displaying the version that you have just created, you will need to update the release notes. Move the release notes from the release candidate, to the tag that you've just created. We want single release notes per version. For example, if there is v0.50.0-rc and later we release v0.50.0, the release notes should live on v0.50.0:
-https://github.com/facebook/react-native/tags
+Go to https://github.com/facebook/react-native/releases and find the release notes for this release candidate. Edit them so that they now point to the tag that you've just created. We want single release notes per version. For example, if there is v0.57.0 and you just released v0.57.1, the release notes should live on the v0.57.1 tag at https://github.com/facebook/react-native/tags
 
 For non-RC releases: Uncheck the box "This is a pre-release" and publish the notes.
 

From 75e49a0637eaa3bd3bb7e445648f084a42d9c8af Mon Sep 17 00:00:00 2001
From: Jens Panneel <jens.panneel@ing.nl>
Date: Thu, 14 Jun 2018 13:53:58 -0700
Subject: [PATCH 0793/1109] Feature/add decimal pad to android (#19714)

Summary:
For a current use-case we need the a keyboard with characters 0-9 and a decimal point (or comma depending on language settings)

This exists on iOS as UIKeyboardType "decimalPad" and this is what react-native maps to for both "numeric" and "decimal-pad". This also exists on Android as inputType "numberDecimal", but is currently not accessible through react-native.

This PR maps the value "decimal-pad" of the keyboardType property of TextInput to the Android inputType "numberDecimal", effectively making "decimal-pad" cross platform without breaking anything.

* https://facebook.github.io/react-native/docs/textinput.html#keyboardtype
* https://developer.apple.com/documentation/uikit/uikeyboardtype
* https://developer.android.com/reference/android/widget/TextView#attr_android:inputType

There is this bug in some Samsung keyboards where both the - sign and decimal sign disappear when the keyboardType is set to "number" and both the "signed" and "decimal" flags are set. (Like is the case when using the react-native keyboardType prop "numeric".) https://androidforums.com/threads/numeric-soft-keyboard-missing-minus-sign-in-android-8-0-samsung-a5.1272628/

For developers that need decimal numbers but not negative ones, using "decimal-pad" will provide a workaround. I reproduced this on a Samsung A5 only, but maybe other phones have this exact issue. https://github.com/facebook/react-native/issues/12988 https://github.com/facebook/react-native/issues/12977 https://github.com/facebook/react-native/issues/17473 https://github.com/facebook/react-native/issues/17474

* Added testcase consistent with existing keyboardType tests
* Also added testcase for the related, but missing number-pad

This PR follows the same approach as the recently merged PR introducing "number-pad" https://github.com/facebook/react-native/pull/18350/commits/b638847a46491bd75e7ce7928c73f7cb78399195

Documentation PR: https://github.com/facebook/react-native-website/pull/405

 [ANDROID] [ENHANCEMENT] [TextInput] - Added "decimal-pad" keyboard type
Closes https://github.com/facebook/react-native/pull/19714

Differential Revision: D8429185

Pulled By: mdvacca

fbshipit-source-id: 6b56da2088f2be427ebffa04c4e17c91ffb9f7d9
---
 Libraries/Components/TextInput/TextInput.js               | 4 ++--
 .../react/views/textinput/ReactTextInputManager.java      | 8 ++++++--
 .../react/views/textinput/ReactTextInputPropertyTest.java | 8 ++++++++
 3 files changed, 16 insertions(+), 4 deletions(-)

diff --git a/Libraries/Components/TextInput/TextInput.js b/Libraries/Components/TextInput/TextInput.js
index c08033e8d43f..ef8d6a81f123 100644
--- a/Libraries/Components/TextInput/TextInput.js
+++ b/Libraries/Components/TextInput/TextInput.js
@@ -86,12 +86,12 @@ export type KeyboardType =
   | 'numeric'
   | 'phone-pad'
   | 'number-pad'
+  | 'decimal-pad'
   // iOS-only
   | 'ascii-capable'
   | 'numbers-and-punctuation'
   | 'url'
   | 'name-phone-pad'
-  | 'decimal-pad'
   | 'twitter'
   | 'web-search'
   // Android-only
@@ -388,6 +388,7 @@ const TextInput = createReactClass({
      * - `default`
      * - `numeric`
      * - `number-pad`
+     * - `decimal-pad`
      * - `email-address`
      * - `phone-pad`
      *
@@ -399,7 +400,6 @@ const TextInput = createReactClass({
      * - `numbers-and-punctuation`
      * - `url`
      * - `name-phone-pad`
-     * - `decimal-pad`
      * - `twitter`
      * - `web-search`
      *
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
index 9311a74ab7d0..3ee99b6c84c6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.java
@@ -70,8 +70,9 @@ public class ReactTextInputManager extends BaseViewManager<ReactEditText, Layout
   private static final int BLUR_TEXT_INPUT = 2;
 
   private static final int INPUT_TYPE_KEYBOARD_NUMBER_PAD = InputType.TYPE_CLASS_NUMBER; 
-  private static final int INPUT_TYPE_KEYBOARD_NUMBERED = INPUT_TYPE_KEYBOARD_NUMBER_PAD |
-          InputType.TYPE_NUMBER_FLAG_DECIMAL |
+  private static final int INPUT_TYPE_KEYBOARD_DECIMAL_PAD = INPUT_TYPE_KEYBOARD_NUMBER_PAD |
+          InputType.TYPE_NUMBER_FLAG_DECIMAL;
+  private static final int INPUT_TYPE_KEYBOARD_NUMBERED = INPUT_TYPE_KEYBOARD_DECIMAL_PAD |
           InputType.TYPE_NUMBER_FLAG_SIGNED;
   private static final int PASSWORD_VISIBILITY_FLAG = InputType.TYPE_TEXT_VARIATION_VISIBLE_PASSWORD &
         ~InputType.TYPE_TEXT_VARIATION_PASSWORD;
@@ -82,6 +83,7 @@ public class ReactTextInputManager extends BaseViewManager<ReactEditText, Layout
 
   private static final String KEYBOARD_TYPE_EMAIL_ADDRESS = "email-address";
   private static final String KEYBOARD_TYPE_NUMERIC = "numeric";
+  private static final String KEYBOARD_TYPE_DECIMAL_PAD = "decimal-pad";
   private static final String KEYBOARD_TYPE_NUMBER_PAD = "number-pad";
   private static final String KEYBOARD_TYPE_PHONE_PAD = "phone-pad";
   private static final String KEYBOARD_TYPE_VISIBLE_PASSWORD = "visible-password";
@@ -567,6 +569,8 @@ public void setKeyboardType(ReactEditText view, @Nullable String keyboardType) {
       flagsToSet = INPUT_TYPE_KEYBOARD_NUMBERED;
     } else if (KEYBOARD_TYPE_NUMBER_PAD.equalsIgnoreCase(keyboardType)) {
       flagsToSet = INPUT_TYPE_KEYBOARD_NUMBER_PAD;
+    } else if (KEYBOARD_TYPE_DECIMAL_PAD.equalsIgnoreCase(keyboardType)) {
+      flagsToSet = INPUT_TYPE_KEYBOARD_DECIMAL_PAD;
     } else if (KEYBOARD_TYPE_EMAIL_ADDRESS.equalsIgnoreCase(keyboardType)) {
       flagsToSet = InputType.TYPE_TEXT_VARIATION_EMAIL_ADDRESS | InputType.TYPE_CLASS_TEXT;
     } else if (KEYBOARD_TYPE_PHONE_PAD.equalsIgnoreCase(keyboardType)) {
diff --git a/ReactAndroid/src/test/java/com/facebook/react/views/textinput/ReactTextInputPropertyTest.java b/ReactAndroid/src/test/java/com/facebook/react/views/textinput/ReactTextInputPropertyTest.java
index 89e9b0a5bdfe..dc6a8dc10abd 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/views/textinput/ReactTextInputPropertyTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/views/textinput/ReactTextInputPropertyTest.java
@@ -231,6 +231,8 @@ public void testNumLines() {
   @Test
   public void testKeyboardType() {
     ReactEditText view = mManager.createViewInstance(mThemedContext);
+    int numberPadTypeFlags = InputType.TYPE_CLASS_NUMBER;
+    int decimalPadTypeFlags = InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_FLAG_DECIMAL;
     int numericTypeFlags =
         InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_FLAG_DECIMAL |
         InputType.TYPE_NUMBER_FLAG_SIGNED;
@@ -249,6 +251,12 @@ public void testKeyboardType() {
     mManager.updateProperties(view, buildStyles("keyboardType", "text"));
     assertThat(view.getInputType() & generalKeyboardTypeFlags).isEqualTo(InputType.TYPE_CLASS_TEXT);
 
+    mManager.updateProperties(view, buildStyles("keyboardType", "number-pad"));
+    assertThat(view.getInputType() & generalKeyboardTypeFlags).isEqualTo(numberPadTypeFlags);
+
+    mManager.updateProperties(view, buildStyles("keyboardType", "decimal-pad"));
+    assertThat(view.getInputType() & generalKeyboardTypeFlags).isEqualTo(decimalPadTypeFlags);
+
     mManager.updateProperties(view, buildStyles("keyboardType", "numeric"));
     assertThat(view.getInputType() & generalKeyboardTypeFlags).isEqualTo(numericTypeFlags);
 

From 6d56a234e3cf5984335ff2713236260fac977f5f Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Thu, 14 Jun 2018 16:14:59 -0700
Subject: [PATCH 0794/1109] add google maven repo in android project template
 (#19712)

Summary:
This PR will add Google maven repo to RN project template that contains com.android.support:appcompat-v7:26.1.0, thus fixes `react-native run-android` using version 0.56.0-rc.1

CI is Green - https://circleci.com/gh/dulmandakh/react-native/235

new Android projects will build and run just fine.
Closes https://github.com/facebook/react-native/pull/19712

Differential Revision: D8433730

Pulled By: hramos

fbshipit-source-id: b7d5a1cd5a97b1c4aad2a307158d6dbfcf9a42a5
---
 local-cli/templates/HelloWorld/android/build.gradle | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/local-cli/templates/HelloWorld/android/build.gradle b/local-cli/templates/HelloWorld/android/build.gradle
index eed9972b5c13..d9ab00a1c7f5 100644
--- a/local-cli/templates/HelloWorld/android/build.gradle
+++ b/local-cli/templates/HelloWorld/android/build.gradle
@@ -3,6 +3,10 @@
 buildscript {
     repositories {
         jcenter()
+        maven {
+            url 'https://maven.google.com/'
+            name 'Google'
+        }
     }
     dependencies {
         classpath 'com.android.tools.build:gradle:2.2.3'
@@ -20,5 +24,9 @@ allprojects {
             // All of React Native (JS, Obj-C sources, Android binaries) is installed from npm
             url "$rootDir/../node_modules/react-native/android"
         }
+        maven {
+            url 'https://maven.google.com/'
+            name 'Google'
+        }
     }
 }

From 699e5eebe807d1ced660d2d2f39b5679d26925da Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Thu, 14 Jun 2018 16:59:40 -0700
Subject: [PATCH 0795/1109] bump gradle-plugin@2.3.3, gradle@3.5.1,
 gradle-download-task@3.4.3 (#19697)

Summary:
bump gradle-plugin@2.3.3, gradle@3.5.1, gradle-download-task@3.4.3, as we landed build tools 26.0.2 with https://github.com/facebook/react-native/commit/065c5b6590de18281a8c592a04240751c655c03c

Will improve Android build performance.

Everything will work as normal, but build faster.

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[ANDROID] [ENHANCEMENT] [TOOLS] - bump gradle-plugin@2.3.3, gradle@3.5.1, gradle-download-task@3.4.3
Closes https://github.com/facebook/react-native/pull/19697

Differential Revision: D8433743

Pulled By: hramos

fbshipit-source-id: da72aeb314bed7f63807a0c69bebd24c633cc807
---
 build.gradle                                                  | 4 ++--
 gradle/wrapper/gradle-wrapper.properties                      | 2 +-
 local-cli/templates/HelloWorld/android/build.gradle           | 2 +-
 .../android/gradle/wrapper/gradle-wrapper.properties          | 2 +-
 4 files changed, 5 insertions(+), 5 deletions(-)

diff --git a/build.gradle b/build.gradle
index 8cd3d00b2dd0..71634a0cbefc 100644
--- a/build.gradle
+++ b/build.gradle
@@ -13,8 +13,8 @@ buildscript {
         }
     }
     dependencies {
-        classpath 'com.android.tools.build:gradle:2.2.2'
-        classpath 'de.undercouch:gradle-download-task:3.1.2'
+        classpath 'com.android.tools.build:gradle:2.3.3'
+        classpath 'de.undercouch:gradle-download-task:3.4.3'
 
         // NOTE: Do not place your application dependencies here; they belong
         // in the individual module build.gradle files
diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
index c8fabc8de009..ec9c72459fa2 100644
--- a/gradle/wrapper/gradle-wrapper.properties
+++ b/gradle/wrapper/gradle-wrapper.properties
@@ -3,4 +3,4 @@ distributionBase=GRADLE_USER_HOME
 distributionPath=wrapper/dists
 zipStoreBase=GRADLE_USER_HOME
 zipStorePath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-2.14.1-all.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-3.5.1-all.zip
diff --git a/local-cli/templates/HelloWorld/android/build.gradle b/local-cli/templates/HelloWorld/android/build.gradle
index d9ab00a1c7f5..225b5f682d0f 100644
--- a/local-cli/templates/HelloWorld/android/build.gradle
+++ b/local-cli/templates/HelloWorld/android/build.gradle
@@ -9,7 +9,7 @@ buildscript {
         }
     }
     dependencies {
-        classpath 'com.android.tools.build:gradle:2.2.3'
+        classpath 'com.android.tools.build:gradle:2.3.3'
 
         // NOTE: Do not place your application dependencies here; they belong
         // in the individual module build.gradle files
diff --git a/local-cli/templates/HelloWorld/android/gradle/wrapper/gradle-wrapper.properties b/local-cli/templates/HelloWorld/android/gradle/wrapper/gradle-wrapper.properties
index dbdc05d274d7..81a86e213401 100644
--- a/local-cli/templates/HelloWorld/android/gradle/wrapper/gradle-wrapper.properties
+++ b/local-cli/templates/HelloWorld/android/gradle/wrapper/gradle-wrapper.properties
@@ -2,4 +2,4 @@ distributionBase=GRADLE_USER_HOME
 distributionPath=wrapper/dists
 zipStoreBase=GRADLE_USER_HOME
 zipStorePath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-2.14.1-all.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-3.5.1-all.zip

From e8fea879fd2611badb6d9d9933f803e2c4c96c71 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Thu, 14 Jun 2018 17:36:20 -0700
Subject: [PATCH 0796/1109] Update GitHub Issue templates (#19723)

Summary:
Now that we have templates for everything we want to handle in the repo, the bot will go back to automatically closing issues that do not use one of the provided templates.

We have an escape valve for generic issues ("For Discussion"), so anyone who gets their issue closed automatically by the bot is unlikely to have read our instructions.
Closes https://github.com/facebook/react-native/pull/19723

Differential Revision: D8435415

Pulled By: hramos

fbshipit-source-id: 41db33cefce1367ad8f3d9440b7bba27565679cb
---
 .github/ISSUE_TEMPLATE/bug_report.md | 19 +++++--------------
 .github/ISSUE_TEMPLATE/discussion.md | 14 +++++++++-----
 2 files changed, 14 insertions(+), 19 deletions(-)

diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md
index 7012b1da2c1a..85c66cde5f62 100644
--- a/.github/ISSUE_TEMPLATE/bug_report.md
+++ b/.github/ISSUE_TEMPLATE/bug_report.md
@@ -6,22 +6,13 @@ about: Report a reproducible bug or regression in the core React Native library.
 <!-- Requirements: please go through this checklist before opening a new issue -->
   - [ ] Review the documentation: https://facebook.github.io/react-native
   - [ ] Search for existing issues: https://github.com/facebook/react-native/issues
-  - [ ] Use the latest React Native version: https://github.com/facebook/react-native/releases
-  - [ ] Run `react-native info` in your terminal and paste its contents under "Environment"
-  - [ ] Let us know how to reproduce the issue. Include a code sample, share a project, or
-    share an app that reproduces the issue using https://snack.expo.io/
+  - [ ] Use the latest React Native release: https://github.com/facebook/react-native/releases
 
 ## Environment
-<!-- Required. -->
+Run `react-native info` in your terminal and paste its contents here.
 
 ## Description
-<!-- Describe your issue in detail. -->
+Describe your issue in detail. Include screenshots if needed. If this is a regression, let us know.
 
-## Steps to Reproduce
-<!-- Required. -->
-
-## Expected Behavior
-<!-- Write what you thought would happen. -->
-
-## Actual Behavior
-<!-- Write what happened. Include screenshots if needed. If this is a regression, let us know. -->
+## Reproducible Demo
+Let us know how to reproduce the issue. Include a code sample, share a project, or     share an app that reproduces the issue using https://snack.expo.io/. Please follow the guidelines for providing a MCVE: https://stackoverflow.com/help/mcve
diff --git a/.github/ISSUE_TEMPLATE/discussion.md b/.github/ISSUE_TEMPLATE/discussion.md
index ed1ede3944a7..a576b0de5c75 100644
--- a/.github/ISSUE_TEMPLATE/discussion.md
+++ b/.github/ISSUE_TEMPLATE/discussion.md
@@ -1,15 +1,19 @@
 ---
 name: 🗣 Start a Discussion
 about: Use https://discuss.reactjs.org/ to propose changes or discuss feature requests.
+---
+
+Please use https://discuss.reactjs.org/ to propose changes or discuss feature requests.
+
+If you feel strongly about starting a discussion as a GitHub Issue instead of using the discussion forum, you may follow this template.
+
+We kindly ask that issues of this type are kept to a minimum to ensure bug reports and regressions are given the priority they require.
 
-guidelines: |
-  If you feel strongly about starting a discussion as a GitHub Issue instead of using the discussion forum, please follow this template.
-  We kindly ask that issues of this type are kept to a minimum to ensure bug reports and regressions are given the priority they require.
-  Maintainers may flag an issue for Stack Overflow or kindly ask you to move the discussion to https://discuss.reactjs.org at their own discretion.
+Maintainers may flag an issue for Stack Overflow or kindly ask you to move the discussion to https://discuss.reactjs.org at their own discretion.
 
 ---
 
-## For Discussion
+# For Discussion
 
 <!-- Describe your issue in detail. -->
 

From 8200c98029782579de3c38e98c733e7d57534b56 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Thu, 14 Jun 2018 17:59:05 -0700
Subject: [PATCH 0797/1109] add RNTester to ci (#19673)

Summary:
* Current ci is missing an important part to test the whole part. With this we can make sure the js and android part compiles.
* Ensure the current android proguard rules is okay.

The `my-release-key.keystore` is just a copy of debug.keystore in `react-native/keystores`.
Pass all ci.
none
 [GENERAL] [ENHANCEMENT] [CI] - Add RNTester to ci
Closes https://github.com/facebook/react-native/pull/19673

Differential Revision: D8435419

Pulled By: hramos

fbshipit-source-id: d3d92a5d1b8477c1f298643cc96695769e5c93ea
---
 .circleci/config.yml                         |   6 ++++++
 RNTester/android/app/build.gradle            |   2 +-
 RNTester/android/app/gradle.properties       |   6 +++---
 RNTester/android/app/my-release-key.keystore | Bin 0 -> 2257 bytes
 4 files changed, 10 insertions(+), 4 deletions(-)
 create mode 100644 RNTester/android/app/my-release-key.keystore

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 7b838f52fce7..663c678228ca 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -558,6 +558,12 @@ jobs:
       - run: *run-android-unit-tests
       - run: *run-android-instrumentation-tests
 
+      # Build Android RNTester
+      - run:
+          name: Build Android RNTester
+          command: |
+            ./gradlew RNTester:android:app:assembleRelease
+
       # Collect Results
       - run: *collect-android-test-results
       - store_test_results:
diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index b13742c58507..9ccb79c0b053 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -81,7 +81,7 @@ def enableSeparateBuildPerCPUArchitecture = false
 /**
  * Run Proguard to shrink the Java bytecode in release builds.
  */
-def enableProguardInReleaseBuilds = false
+def enableProguardInReleaseBuilds = true
 
 android {
     compileSdkVersion 26
diff --git a/RNTester/android/app/gradle.properties b/RNTester/android/app/gradle.properties
index 04cbf4f74219..926d2479c3f3 100644
--- a/RNTester/android/app/gradle.properties
+++ b/RNTester/android/app/gradle.properties
@@ -2,6 +2,6 @@ android.useDeprecatedNdk=true
 org.gradle.parallel=true
 org.gradle.configureondemand=true
 MYAPP_RELEASE_STORE_FILE=my-release-key.keystore
-MYAPP_RELEASE_KEY_ALIAS=my-key-alias
-MYAPP_RELEASE_STORE_PASSWORD=*****
-MYAPP_RELEASE_KEY_PASSWORD=*****
+MYAPP_RELEASE_KEY_ALIAS=androiddebugkey
+MYAPP_RELEASE_STORE_PASSWORD=android
+MYAPP_RELEASE_KEY_PASSWORD=android
diff --git a/RNTester/android/app/my-release-key.keystore b/RNTester/android/app/my-release-key.keystore
new file mode 100644
index 0000000000000000000000000000000000000000..364e105ed39fbfd62001429a68140672b06ec0de
GIT binary patch

From 1ffb2b63be4c4af331fece0b4286e5c92b1e575d Mon Sep 17 00:00:00 2001
From: hamaron <takashi@junify.com>
Date: Thu, 14 Jun 2018 18:06:05 -0700
Subject: [PATCH 0798/1109] iOS: Fixed the bug where a Backspace event was
 emitted when entering characters after clearing a text in TextInput by an
 empty string (#18627)

Summary:
The bug #18374 was caused by the loose condition to execute `stringByReplacingCharactersInRange` in the method `textInputShouldChangeTextInRange` . As a result, `findMismatch` wrongly returning `true` which ends up the Backspace event being fired in another `textInputShouldChangeTextInRange` call in `textInputDidChange`.

<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

1. Pass all the tests by `yarn run test`
2. Run the following code and type any text. (This code is brought from #18374. Thank you michalpetrov!!) And then verify that 'Backspace' events are not emitted after clearing text
and entering any letters.

```javascript
type Props = {};
type State = {
  text: string,
  keys: string
};
export default class App extends Component<Props, State> {
  state = {text: '', keys: ''}
  render() {
    return (
      <View style={styles.container}>
        <TextInput style={styles.textInput} value={this.state.text} onChangeText={this.onChangeText} onKeyPress={this.onKeyPress}/>
        <Button title="Clear" onPress={this.onClear}/>
        <Text>Text: {this.state.text}</Text>
        <Text>Keys: {this.state.keys}</Text>
      </View>
    );
  }

  onChangeText = (text: string) => {
    this.setState({text})
  }

  onKeyPress = ({ nativeEvent }: Object) => {
    this.setState({keys: this.state.keys + nativeEvent.key + ', '})
  }

  onClear = () => {
    this.setState({text: '', keys: ''})
  }
}
```

<!--
  Does this PR require a documentation change?
  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
-->

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[IOS] [BUGFIX] [TextInput] - Fixed the bug where Backspace event was emitted when entering a character after clearing a text in TextInput by an empty string

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/18627

Differential Revision: D8436331

Pulled By: hramos

fbshipit-source-id: ec75a6ca926061cbf7cb106db652f2b4a71c9a0c
---
 Libraries/Text/TextInput/RCTBaseTextInputView.m | 7 ++++++-
 1 file changed, 6 insertions(+), 1 deletion(-)

diff --git a/Libraries/Text/TextInput/RCTBaseTextInputView.m b/Libraries/Text/TextInput/RCTBaseTextInputView.m
index 9ba7df140a3e..ebb8a8308188 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputView.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputView.m
@@ -306,7 +306,12 @@ - (BOOL)textInputShouldChangeTextInRange:(NSRange)range replacementText:(NSStrin
 
   NSString *previousText = [_predictedText substringWithRange:range] ?: @"";
 
-  if (_predictedText) {
+  // After clearing the text by replacing it with an empty string, `_predictedText`
+  // still preserves the deleted text.
+  // As the first character in the TextInput always comes with the range value (0, 0),
+  // we should check the range value in order to avoid appending a character to the deleted string
+  // (which caused the issue #18374)
+  if (!NSEqualRanges(range, NSMakeRange(0, 0)) && _predictedText) {
     _predictedText = [_predictedText stringByReplacingCharactersInRange:range withString:text];
   } else {
     _predictedText = text;

From e773b36990089ac242ada89e26b7fa2803e3c13a Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Thu, 14 Jun 2018 18:36:32 -0700
Subject: [PATCH 0799/1109] Refactor Log to Flog in Fabric

Reviewed By: shergin

Differential Revision: D8363593

fbshipit-source-id: fb4104b66ef3d50d4101c39a1bf4515e6d0ecd19
---
 .../debug/tags/ReactDebugOverlayTags.java     | 10 +++++
 .../react/bridge/PerformanceCounter.java      |  2 +-
 .../main/java/com/facebook/react/fabric/BUCK  |  3 ++
 .../react/fabric/FabricReconciler.java        | 12 ++++--
 .../react/fabric/FabricUIManager.java         | 40 ++++++++++---------
 .../java/com/facebook/react/uimanager/BUCK    |  1 +
 .../react/uimanager/ReactShadowNodeImpl.java  |  9 +++--
 7 files changed, 51 insertions(+), 26 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/debug/tags/ReactDebugOverlayTags.java b/ReactAndroid/src/main/java/com/facebook/debug/tags/ReactDebugOverlayTags.java
index 6bc6b598373b..879743ce91a0 100644
--- a/ReactAndroid/src/main/java/com/facebook/debug/tags/ReactDebugOverlayTags.java
+++ b/ReactAndroid/src/main/java/com/facebook/debug/tags/ReactDebugOverlayTags.java
@@ -27,6 +27,16 @@ public class ReactDebugOverlayTags {
           "UI Manager",
           "UI Manager View Operations (requires restart\nwarning: this is spammy)",
           Color.CYAN);
+  public static final DebugOverlayTag FABRIC_UI_MANAGER =
+    new DebugOverlayTag(
+      "FabricUIManager",
+      "Fabric UI Manager View Operations",
+      Color.CYAN);
+  public static final DebugOverlayTag FABRIC_RECONCILER =
+    new DebugOverlayTag(
+      "FabricReconciler",
+      "Reconciler for Fabric",
+      Color.CYAN);
   public static final DebugOverlayTag RELAY =
       new DebugOverlayTag("Relay", "including prefetching", Color.rgb(0xFF, 0x99, 0x00));
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/PerformanceCounter.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/PerformanceCounter.java
index b4a075ae6c34..7acd416a940e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/PerformanceCounter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/PerformanceCounter.java
@@ -9,5 +9,5 @@
 import java.util.Map;
 
 public interface PerformanceCounter {
-  public Map<String, Long> getPerformanceCounters();
+  Map<String, Long> getPerformanceCounters();
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
index d4d239f3dad8..88dfe4bd5965 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
@@ -15,9 +15,12 @@ rn_android_library(
     ],
     deps = [
         YOGA_TARGET,
+        react_native_dep("libraries/fbcore/src/main/java/com/facebook/common/logging:logging"),
         react_native_dep("third-party/java/infer-annotations:infer-annotations"),
         react_native_dep("third-party/java/jsr-305:jsr-305"),
         react_native_target("java/com/facebook/react:react"),
+        react_native_target("java/com/facebook/debug/tags:tags"),
+        react_native_target("java/com/facebook/debug/holder:holder"),
         react_native_target("java/com/facebook/react/bridge:bridge"),
         react_native_target("java/com/facebook/react/uimanager:uimanager"),
         react_native_target("java/com/facebook/react/uimanager/annotations:annotations"),
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index c42de9efec38..ba8b592ed387 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -7,8 +7,11 @@
 
 package com.facebook.react.fabric;
 
-import android.util.Log;
+import com.facebook.common.logging.FLog;
+import com.facebook.debug.holder.PrinterHolder;
+import com.facebook.debug.tags.ReactDebugOverlayTags;
 import com.facebook.react.common.ArrayUtils;
+import com.facebook.react.common.build.ReactBuildConfig;
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.UIViewOperationQueue;
 import com.facebook.react.uimanager.ViewAtIndex;
@@ -23,7 +26,8 @@
 public class FabricReconciler {
 
   private static final String TAG = FabricReconciler.class.getSimpleName();
-  private static final boolean DEBUG = true;
+  private static final boolean DEBUG = ReactBuildConfig.DEBUG || PrinterHolder
+    .getPrinter().shouldDisplayLogMessage(ReactDebugOverlayTags.FABRIC_RECONCILER);
 
   private UIViewOperationQueue uiViewOperationQueue;
 
@@ -104,7 +108,7 @@ private void manageChildren(
       ViewAtIndex[] viewsToAddArray = viewsToAdd.toArray(new ViewAtIndex[viewsToAdd.size()]);
       int[] tagsToDeleteArray = ArrayUtils.copyListToArray(tagsToDelete);
       if (DEBUG) {
-        Log.d(
+        FLog.d(
             TAG,
             "manageChildren.enqueueManageChildren parent: " + parent.getReactTag() +
                 "\n\tIndices2Remove: " + Arrays.toString(indicesToRemoveArray) +
@@ -119,7 +123,7 @@ private void manageChildren(
   private void enqueueUpdateProperties(ReactShadowNode node) {
     int reactTag = node.getReactTag();
     if (DEBUG) {
-      Log.d(
+      FLog.d(
         TAG,
         "manageChildren.enqueueUpdateProperties " +
           "\n\ttag: " + reactTag +
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 588d7bc596f8..b0b8edbf783a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -12,8 +12,10 @@
 import static android.view.View.MeasureSpec.UNSPECIFIED;
 import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 
-import android.util.Log;
 import android.view.View;
+import com.facebook.common.logging.FLog;
+import com.facebook.debug.holder.PrinterHolder;
+import com.facebook.debug.tags.ReactDebugOverlayTags;
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.proguard.annotations.DoNotStrip;
 import com.facebook.react.bridge.JavaScriptContextHolder;
@@ -26,6 +28,7 @@
 import com.facebook.react.bridge.WritableNativeMap;
 import com.facebook.react.common.ReactConstants;
 import com.facebook.react.common.annotations.VisibleForTesting;
+import com.facebook.react.common.build.ReactBuildConfig;
 import com.facebook.react.fabric.events.FabricEventEmitter;
 import com.facebook.react.modules.i18nmanager.I18nUtil;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
@@ -56,7 +59,7 @@
 public class FabricUIManager implements UIManager, JSHandler {
 
   private static final String TAG = FabricUIManager.class.getSimpleName();
-  private static final boolean DEBUG = true;
+  private static final boolean DEBUG = ReactBuildConfig.DEBUG || PrinterHolder.getPrinter().shouldDisplayLogMessage(ReactDebugOverlayTags.FABRIC_UI_MANAGER);
 
   private final RootShadowNodeRegistry mRootShadowNodeRegistry = new RootShadowNodeRegistry();
   private final ReactApplicationContext mReactApplicationContext;
@@ -100,7 +103,7 @@ public void setBinding(FabricBinding binding) {
   public ReactShadowNode createNode(
       int reactTag, String viewName, int rootTag, ReadableNativeMap props, long instanceHandle) {
     if (DEBUG) {
-      Log.d(TAG, "createNode \n\ttag: " + reactTag +
+      FLog.d(TAG, "createNode \n\ttag: " + reactTag +
           "\n\tviewName: " + viewName +
           "\n\trootTag: " + rootTag +
           "\n\tprops: " + props);
@@ -151,7 +154,7 @@ private ReactStylesDiffMap updateProps(ReactShadowNode node, @Nullable ReadableN
   @DoNotStrip
   public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
     if (DEBUG) {
-      Log.d(TAG, "cloneNode \n\tnode: " + node);
+      FLog.d(TAG, "cloneNode \n\tnode: " + node);
     }
     try {
       ReactShadowNode clone = node.mutableCopy(instanceHandle);
@@ -172,7 +175,7 @@ public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
   @DoNotStrip
   public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long instanceHandle) {
     if (DEBUG) {
-      Log.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
+      FLog.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
     }
     try {
       ReactShadowNode clone = node.mutableCopyWithNewChildren(instanceHandle);
@@ -194,7 +197,7 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long insta
   public ReactShadowNode cloneNodeWithNewProps(
       ReactShadowNode node, @Nullable ReadableNativeMap newProps, long instanceHandle) {
     if (DEBUG) {
-      Log.d(TAG, "cloneNodeWithNewProps \n\tnode: " + node + "\n\tprops: " + newProps);
+      FLog.d(TAG, "cloneNodeWithNewProps \n\tnode: " + node + "\n\tprops: " + newProps);
     }
     try {
       ReactShadowNode clone = node.mutableCopyWithNewProps(instanceHandle,
@@ -218,7 +221,7 @@ public ReactShadowNode cloneNodeWithNewProps(
   public ReactShadowNode cloneNodeWithNewChildrenAndProps(
       ReactShadowNode node, ReadableNativeMap newProps, long instanceHandle) {
     if (DEBUG) {
-      Log.d(TAG, "cloneNodeWithNewChildrenAndProps \n\tnode: " + node + "\n\tnewProps: " + newProps);
+      FLog.d(TAG, "cloneNodeWithNewChildrenAndProps \n\tnode: " + node + "\n\tnewProps: " + newProps);
     }
     try {
       ReactShadowNode clone =
@@ -252,7 +255,7 @@ private void assertReactShadowNodeCopy(ReactShadowNode source, ReactShadowNode t
   @DoNotStrip
   public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
     if (DEBUG) {
-      Log.d(TAG, "appendChild \n\tparent: " + parent + "\n\tchild: " + child);
+      FLog.d(TAG, "appendChild \n\tparent: " + parent + "\n\tchild: " + child);
     }
     try {
       // If the child to append is shared with another tree (child.getParent() != null),
@@ -274,7 +277,7 @@ public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
   @DoNotStrip
   public List<ReactShadowNode> createChildSet(int rootTag) {
     if (DEBUG) {
-      Log.d(TAG, "createChildSet rootTag: " + rootTag);
+      FLog.d(TAG, "createChildSet rootTag: " + rootTag);
     }
     return new ArrayList<>(1);
   }
@@ -292,7 +295,7 @@ public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNod
     try {
       childList = childList == null ? new LinkedList<ReactShadowNode>() : childList;
       if (DEBUG) {
-        Log.d(TAG, "completeRoot rootTag: " + rootTag + ", childList: " + childList);
+        FLog.d(TAG, "completeRoot rootTag: " + rootTag + ", childList: " + childList);
       }
       ReactShadowNode currentRootShadowNode = getRootNode(rootTag);
       Assertions.assertNotNull(
@@ -302,7 +305,7 @@ public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNod
       currentRootShadowNode = calculateDiffingAndCreateNewRootNode(currentRootShadowNode, childList);
 
       if (DEBUG) {
-        Log.d(
+        FLog.d(
           TAG,
           "ReactShadowNodeHierarchy after diffing: " + currentRootShadowNode.getHierarchyInfo());
       }
@@ -339,16 +342,17 @@ private ReactShadowNode calculateDiffingAndCreateNewRootNode(
     }
 
     if (DEBUG) {
-      Log.d(
+      FLog.d(
         TAG,
         "ReactShadowNodeHierarchy before calculateLayout: " + newRootShadowNode.getHierarchyInfo());
     }
 
     notifyOnBeforeLayoutRecursive(newRootShadowNode);
+
     newRootShadowNode.calculateLayout();
 
     if (DEBUG) {
-      Log.d(
+      FLog.d(
         TAG,
         "ReactShadowNodeHierarchy after calculateLayout: " + newRootShadowNode.getHierarchyInfo());
     }
@@ -425,7 +429,7 @@ public void onSizeChanged(final int width, final int height, int oldW, int oldH)
   public void updateRootLayoutSpecs(int rootViewTag, int widthMeasureSpec, int heightMeasureSpec) {
     ReactShadowNode rootNode = mRootShadowNodeRegistry.getNode(rootViewTag);
     if (rootNode == null) {
-      Log.w(ReactConstants.TAG, "Tried to update non-existent root tag: " + rootViewTag);
+      FLog.w(ReactConstants.TAG, "Tried to update non-existent root tag: " + rootViewTag);
       return;
     }
     updateRootView(rootNode, widthMeasureSpec, heightMeasureSpec);
@@ -439,7 +443,7 @@ public void updateRootLayoutSpecs(int rootViewTag, int widthMeasureSpec, int hei
   private synchronized void updateRootSize(int rootTag, int newWidth, int newHeight) {
     ReactShadowNode rootNode = mRootShadowNodeRegistry.getNode(rootTag);
     if (rootNode == null) {
-      Log.w(
+      FLog.w(
         ReactConstants.TAG,
         "Tried to update size of non-existent tag: " + rootTag);
       return;
@@ -509,7 +513,7 @@ private void handleException(ReactShadowNode node, Throwable t) {
       // a RuntimeException
       context.handleException(new RuntimeException(t));
     } catch (Exception ex) {
-      Log.e(TAG, "Exception while executing a Fabric method", t);
+      FLog.e(TAG, "Exception while executing a Fabric method", t);
       throw new RuntimeException(ex.getMessage(), t);
     }
   }
@@ -521,7 +525,7 @@ public long createEventTarget(int reactTag) {
     long context = mJSContext.get();
     long eventTarget = mBinding.createEventTarget(context, instanceHandle);
     if (DEBUG) {
-      Log.d(
+      FLog.d(
         TAG,
         "Created EventTarget: " + eventTarget + " for tag: " + reactTag + " with instanceHandle: " + instanceHandle);
     }
@@ -547,7 +551,7 @@ public void releaseEventHandler(long eventHandlerPointer) {
   @DoNotStrip
   public void invoke(long eventTarget, String name, WritableMap params) {
     if (DEBUG) {
-      Log.d(
+      FLog.d(
         TAG,
         "Dispatching event for target: " + eventTarget);
     }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
index 0a449cfd1384..99dbb6328f36 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
@@ -30,6 +30,7 @@ rn_android_library(
         react_native_target("java/com/facebook/react/animation:animation"),
         react_native_target("java/com/facebook/react/bridge:bridge"),
         react_native_target("java/com/facebook/react/common:common"),
+        react_native_target("java/com/facebook/react/common:common"),
         react_native_target("java/com/facebook/react/module/annotations:annotations"),
         react_native_target("java/com/facebook/react/modules/core:core"),
         react_native_target("java/com/facebook/react/modules/i18nmanager:i18nmanager"),
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 3b3929646810..c98c12bb07d3 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -8,8 +8,11 @@
 
 import static java.lang.System.arraycopy;
 
-import android.util.Log;
+import com.facebook.common.logging.FLog;
+import com.facebook.debug.holder.PrinterHolder;
+import com.facebook.debug.tags.ReactDebugOverlayTags;
 import com.facebook.infer.annotation.Assertions;
+import com.facebook.react.common.build.ReactBuildConfig;
 import com.facebook.react.uimanager.annotations.ReactPropertyHolder;
 import com.facebook.yoga.YogaAlign;
 import com.facebook.yoga.YogaBaselineFunction;
@@ -59,7 +62,7 @@
 @ReactPropertyHolder
 public class ReactShadowNodeImpl implements ReactShadowNode<ReactShadowNodeImpl> {
 
-  private static final boolean DEBUG = true;
+  private static final boolean DEBUG = ReactBuildConfig.DEBUG || PrinterHolder.getPrinter().shouldDisplayLogMessage(ReactDebugOverlayTags.FABRIC_UI_MANAGER);
   private static final String TAG = ReactShadowNodeImpl.class.getSimpleName();
   private static final YogaConfig sYogaConfig;
   static {
@@ -75,7 +78,7 @@ public YogaNode cloneNode(YogaNode oldYogaNode,
         Assertions.assertNotNull(oldReactShadowNode);
 
         if (DEBUG) {
-          Log.d(
+          FLog.d(
             TAG,
             "YogaNode started cloning: oldYogaNode: " + oldReactShadowNode + " - parent: "
               + parentReactShadowNode + " index: " + childIndex);

From d62e4324468a4c2f352eb954fa6bbc85acb2c736 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Thu, 14 Jun 2018 18:36:34 -0700
Subject: [PATCH 0800/1109] Adding UIManager performance counters in Fabric

Reviewed By: fkgozali

Differential Revision: D8381255

fbshipit-source-id: d817557c8a3033d0d7ae47e5ea0a21d224279e29
---
 .../react/bridge/PerformanceCounter.java      |  4 ++++
 .../com/facebook/react/bridge/UIManager.java  |  2 +-
 .../react/fabric/FabricUIManager.java         | 24 +++++++++++++++++--
 .../react/uimanager/UIManagerModule.java      |  7 +++++-
 4 files changed, 33 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/PerformanceCounter.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/PerformanceCounter.java
index 7acd416a940e..984eb7859046 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/PerformanceCounter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/PerformanceCounter.java
@@ -9,5 +9,9 @@
 import java.util.Map;
 
 public interface PerformanceCounter {
+
+  void profileNextBatch();
+
   Map<String, Long> getPerformanceCounters();
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
index 875f42cbf12b..e1f778b8c30a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
@@ -5,7 +5,7 @@
 
 import javax.annotation.Nullable;
 
-public interface UIManager extends JSIModule {
+public interface UIManager extends JSIModule, PerformanceCounter {
 
   /**
    * Registers a new root view.
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index b0b8edbf783a..ea0ff8f2ccc1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -12,6 +12,7 @@
 import static android.view.View.MeasureSpec.UNSPECIFIED;
 import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 
+import android.os.SystemClock;
 import android.view.View;
 import com.facebook.common.logging.FLog;
 import com.facebook.debug.holder.PrinterHolder;
@@ -19,6 +20,7 @@
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.proguard.annotations.DoNotStrip;
 import com.facebook.react.bridge.JavaScriptContextHolder;
+import com.facebook.react.bridge.PerformanceCounter;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
@@ -48,6 +50,7 @@
 import java.util.ArrayList;
 import java.util.LinkedList;
 import java.util.List;
+import java.util.Map;
 import javax.annotation.Nullable;
 
 /**
@@ -73,6 +76,7 @@ public class FabricUIManager implements UIManager, JSHandler {
   private FabricBinding mBinding;
   private final FabricEventEmitter mFabricEventEmitter;
   private long mEventHandlerPointer;
+  private long mLastCalculateLayoutTime = 0;
 
   public FabricUIManager(
       ReactApplicationContext reactContext,
@@ -293,6 +297,7 @@ public void appendChildToSet(List<ReactShadowNode> childList, ReactShadowNode ch
   @DoNotStrip
   public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNode> childList) {
     try {
+      long startTime = SystemClock.uptimeMillis();
       childList = childList == null ? new LinkedList<ReactShadowNode>() : childList;
       if (DEBUG) {
         FLog.d(TAG, "completeRoot rootTag: " + rootTag + ", childList: " + childList);
@@ -312,7 +317,7 @@ public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNod
 
       applyUpdatesRecursive(currentRootShadowNode, 0, 0);
       mUIViewOperationQueue.dispatchViewUpdates(
-        mCurrentBatch++, System.currentTimeMillis(), System.currentTimeMillis());
+        mCurrentBatch++, startTime, mLastCalculateLayoutTime);
 
       mRootShadowNodeRegistry.replaceNode(currentRootShadowNode);
     } catch (Exception e) {
@@ -349,7 +354,12 @@ private ReactShadowNode calculateDiffingAndCreateNewRootNode(
 
     notifyOnBeforeLayoutRecursive(newRootShadowNode);
 
-    newRootShadowNode.calculateLayout();
+    long startTime = SystemClock.uptimeMillis();
+    try {
+      newRootShadowNode.calculateLayout();
+    } finally{
+      mLastCalculateLayoutTime = SystemClock.uptimeMillis() - startTime;
+    }
 
     if (DEBUG) {
       FLog.d(
@@ -572,4 +582,14 @@ public void onCatalystInstanceDestroy() {
     mFabricEventEmitter.close();
   }
 
+  @Override
+  public void profileNextBatch() {
+    mUIViewOperationQueue.profileNextBatch();
+  }
+
+  @Override
+  public Map<String, Long> getPerformanceCounters() {
+    // TODO change profiling when enabling multi-thread rendering.
+    return mUIViewOperationQueue.getProfiledBatchPerfCounters();
+  }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 9022686a73ec..f35511c3395b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -81,7 +81,7 @@
  */
 @ReactModule(name = UIManagerModule.NAME)
 public class UIManagerModule extends ReactContextBaseJavaModule implements
-    OnBatchCompleteListener, LifecycleEventListener, PerformanceCounter, UIManager {
+    OnBatchCompleteListener, LifecycleEventListener, UIManager {
 
   /**
    * Enables lazy discovery of a specific {@link ViewManager} by its name.
@@ -286,6 +286,11 @@ public CustomEventNamesResolver getDirectEventNamesResolver() {
     };
   }
 
+  @Override
+  public void profileNextBatch() {
+    mUIImplementation.profileNextBatch();
+  }
+
   @Override
   public Map<String, Long> getPerformanceCounters() {
     return mUIImplementation.getProfiledBatchPerfCounters();

From 0dc86dfd9143d095279387622ac4f00be50e5f8b Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Thu, 14 Jun 2018 18:36:36 -0700
Subject: [PATCH 0801/1109] Add systrace logging for Fabric android

Reviewed By: fkgozali

Differential Revision: D8387339

fbshipit-source-id: 2e202566541cc25fb6b8773a94e607e8b40fb0ce
---
 .../main/java/com/facebook/react/fabric/BUCK  |   1 +
 .../react/fabric/FabricReconciler.java        |  19 ++-
 .../react/fabric/FabricUIManager.java         | 155 +++++++++++++-----
 .../react/uimanager/ReactShadowNodeImpl.java  |  38 +++--
 4 files changed, 155 insertions(+), 58 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
index 88dfe4bd5965..ef2e3e18772d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/BUCK
@@ -15,6 +15,7 @@ rn_android_library(
     ],
     deps = [
         YOGA_TARGET,
+        react_native_dep("java/com/facebook/systrace:systrace"),
         react_native_dep("libraries/fbcore/src/main/java/com/facebook/common/logging:logging"),
         react_native_dep("third-party/java/infer-annotations:infer-annotations"),
         react_native_dep("third-party/java/jsr-305:jsr-305"),
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index ba8b592ed387..41784624288d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -15,6 +15,8 @@
 import com.facebook.react.uimanager.ReactShadowNode;
 import com.facebook.react.uimanager.UIViewOperationQueue;
 import com.facebook.react.uimanager.ViewAtIndex;
+import com.facebook.systrace.Systrace;
+import com.facebook.systrace.SystraceMessage;
 import java.util.Arrays;
 import java.util.Collections;
 import java.util.HashSet;
@@ -26,7 +28,7 @@
 public class FabricReconciler {
 
   private static final String TAG = FabricReconciler.class.getSimpleName();
-  private static final boolean DEBUG = ReactBuildConfig.DEBUG || PrinterHolder
+    private static final boolean DEBUG = ReactBuildConfig.DEBUG || PrinterHolder
     .getPrinter().shouldDisplayLogMessage(ReactDebugOverlayTags.FABRIC_RECONCILER);
 
   private UIViewOperationQueue uiViewOperationQueue;
@@ -36,9 +38,18 @@ public FabricReconciler(UIViewOperationQueue uiViewOperationQueue) {
   }
 
   public void manageChildren(ReactShadowNode previousRootShadowNode, ReactShadowNode newRootShadowNode) {
-    List<ReactShadowNode> prevList =
-      previousRootShadowNode == null ? null :  previousRootShadowNode.getChildrenList();
-    manageChildren(newRootShadowNode, prevList, newRootShadowNode.getChildrenList());
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricReconciler.manageChildren")
+      .flush();
+
+    try {
+      List<ReactShadowNode> prevList =
+        previousRootShadowNode == null ? null :  previousRootShadowNode.getChildrenList();
+      manageChildren(newRootShadowNode, prevList, newRootShadowNode.getChildrenList());
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
+    }
   }
 
   private void manageChildren(
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index ea0ff8f2ccc1..d6b7fd97f5cb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -46,6 +46,8 @@
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 import com.facebook.react.uimanager.events.EventDispatcher;
+import com.facebook.systrace.Systrace;
+import com.facebook.systrace.SystraceMessage;
 import com.facebook.yoga.YogaDirection;
 import java.util.ArrayList;
 import java.util.LinkedList;
@@ -160,6 +162,10 @@ public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
     if (DEBUG) {
       FLog.d(TAG, "cloneNode \n\tnode: " + node);
     }
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.cloneNode")
+      .flush();
     try {
       ReactShadowNode clone = node.mutableCopy(instanceHandle);
       assertReactShadowNodeCopy(node, clone);
@@ -167,6 +173,8 @@ public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
     } catch (Throwable t) {
       handleException(node, t);
       return null;
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
     }
   }
 
@@ -181,6 +189,10 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long insta
     if (DEBUG) {
       FLog.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
     }
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.cloneNodeWithNewChildren")
+      .flush();
     try {
       ReactShadowNode clone = node.mutableCopyWithNewChildren(instanceHandle);
       assertReactShadowNodeCopy(node, clone);
@@ -188,6 +200,8 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long insta
     } catch (Throwable t) {
       handleException(node, t);
       return null;
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
     }
   }
 
@@ -203,6 +217,10 @@ public ReactShadowNode cloneNodeWithNewProps(
     if (DEBUG) {
       FLog.d(TAG, "cloneNodeWithNewProps \n\tnode: " + node + "\n\tprops: " + newProps);
     }
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.cloneNodeWithNewProps")
+      .flush();
     try {
       ReactShadowNode clone = node.mutableCopyWithNewProps(instanceHandle,
             newProps == null ? null : new ReactStylesDiffMap(newProps));
@@ -211,6 +229,8 @@ public ReactShadowNode cloneNodeWithNewProps(
     } catch (Throwable t) {
       handleException(node, t);
       return null;
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
     }
   }
 
@@ -227,6 +247,10 @@ public ReactShadowNode cloneNodeWithNewChildrenAndProps(
     if (DEBUG) {
       FLog.d(TAG, "cloneNodeWithNewChildrenAndProps \n\tnode: " + node + "\n\tnewProps: " + newProps);
     }
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.cloneNodeWithNewChildrenAndProps")
+      .flush();
     try {
       ReactShadowNode clone =
           node.mutableCopyWithNewChildrenAndProps(instanceHandle,
@@ -236,6 +260,8 @@ public ReactShadowNode cloneNodeWithNewChildrenAndProps(
     } catch (Throwable t) {
       handleException(node, t);
       return null;
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
     }
   }
 
@@ -261,6 +287,10 @@ public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
     if (DEBUG) {
       FLog.d(TAG, "appendChild \n\tparent: " + parent + "\n\tchild: " + child);
     }
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.appendChild")
+      .flush();
     try {
       // If the child to append is shared with another tree (child.getParent() != null),
       // then we add a mutation of it. In the future this will be performed by FabricJS / Fiber.
@@ -271,6 +301,8 @@ public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
       parent.addChildAt(child, parent.getChildCount());
     } catch (Throwable t) {
       handleException(parent, t);
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
     }
   }
 
@@ -296,6 +328,10 @@ public void appendChildToSet(List<ReactShadowNode> childList, ReactShadowNode ch
 
   @DoNotStrip
   public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNode> childList) {
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.completeRoot")
+      .flush();
     try {
       long startTime = SystemClock.uptimeMillis();
       childList = childList == null ? new LinkedList<ReactShadowNode>() : childList;
@@ -315,13 +351,15 @@ public synchronized void completeRoot(int rootTag, @Nullable List<ReactShadowNod
           "ReactShadowNodeHierarchy after diffing: " + currentRootShadowNode.getHierarchyInfo());
       }
 
-      applyUpdatesRecursive(currentRootShadowNode, 0, 0);
+      applyUpdatesRecursive(currentRootShadowNode);
       mUIViewOperationQueue.dispatchViewUpdates(
         mCurrentBatch++, startTime, mLastCalculateLayoutTime);
 
       mRootShadowNodeRegistry.replaceNode(currentRootShadowNode);
     } catch (Exception e) {
       handleException(getRootNode(rootTag), e);
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
     }
   }
 
@@ -340,35 +378,63 @@ private void notifyOnBeforeLayoutRecursive(ReactShadowNode node) {
   }
 
   private ReactShadowNode calculateDiffingAndCreateNewRootNode(
-    ReactShadowNode currentRootShadowNode, List<ReactShadowNode> newChildList) {
-    ReactShadowNode newRootShadowNode = currentRootShadowNode.mutableCopyWithNewChildren(currentRootShadowNode.getInstanceHandle());
-    for (ReactShadowNode child : newChildList) {
-      appendChild(newRootShadowNode, child);
-    }
+      ReactShadowNode currentRootShadowNode, List<ReactShadowNode> newChildList) {
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.calculateDiffingAndCreateNewRootNode")
+      .flush();
+    try {
+      ReactShadowNode newRootShadowNode = currentRootShadowNode.mutableCopyWithNewChildren(currentRootShadowNode.getInstanceHandle());
+      for (ReactShadowNode child : newChildList) {
+        appendChild(newRootShadowNode, child);
+      }
 
-    if (DEBUG) {
-      FLog.d(
-        TAG,
-        "ReactShadowNodeHierarchy before calculateLayout: " + newRootShadowNode.getHierarchyInfo());
-    }
+      if (DEBUG) {
+        FLog.d(
+          TAG,
+          "ReactShadowNodeHierarchy before calculateLayout: " + newRootShadowNode.getHierarchyInfo());
+      }
+
+      notifyOnBeforeLayoutRecursive(newRootShadowNode);
+
+      calculateLayout(newRootShadowNode);
 
-    notifyOnBeforeLayoutRecursive(newRootShadowNode);
+      if (DEBUG) {
+        FLog.d(
+          TAG,
+          "ReactShadowNodeHierarchy after calculateLayout: " + newRootShadowNode.getHierarchyInfo());
+      }
+
+      mFabricReconciler.manageChildren(currentRootShadowNode, newRootShadowNode);
+      return newRootShadowNode;
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
+    }
+  }
 
+  private void calculateLayout(ReactShadowNode newRootShadowNode) {
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.calculateLayout")
+      .flush();
     long startTime = SystemClock.uptimeMillis();
     try {
       newRootShadowNode.calculateLayout();
     } finally{
       mLastCalculateLayoutTime = SystemClock.uptimeMillis() - startTime;
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
     }
+  }
 
-    if (DEBUG) {
-      FLog.d(
-        TAG,
-        "ReactShadowNodeHierarchy after calculateLayout: " + newRootShadowNode.getHierarchyInfo());
+  private void applyUpdatesRecursive(ReactShadowNode node) {
+    SystraceMessage.beginSection(
+            Systrace.TRACE_TAG_REACT_JAVA_BRIDGE, "FabricUIManager.applyUpdatesRecursive")
+        .flush();
+    try {
+      applyUpdatesRecursive(node, 0, 0);
+    } finally{
+      SystraceMessage.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
     }
-
-    mFabricReconciler.manageChildren(currentRootShadowNode, newRootShadowNode);
-    return newRootShadowNode;
   }
 
   private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float absoluteY) {
@@ -411,27 +477,36 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
   @DoNotStrip
   public <T extends SizeMonitoringFrameLayout & MeasureSpecProvider> int addRootView(
       final T rootView) {
-    final int rootTag = ReactRootViewTagGenerator.getNextRootViewTag();
-    ThemedReactContext themedRootContext =
-        new ThemedReactContext(mReactApplicationContext, rootView.getContext());
-
-    ReactShadowNode rootShadowNode = createRootShadowNode(rootTag, themedRootContext);
-
-    int widthMeasureSpec = rootView.getWidthMeasureSpec();
-    int heightMeasureSpec = rootView.getHeightMeasureSpec();
-    updateRootView(rootShadowNode, widthMeasureSpec, heightMeasureSpec);
-
-    rootView.setOnSizeChangedListener(
-      new SizeMonitoringFrameLayout.OnSizeChangedListener() {
-        @Override
-        public void onSizeChanged(final int width, final int height, int oldW, int oldH) {
-          updateRootSize(rootTag, width, height);
-        }
-      });
-
-    mRootShadowNodeRegistry.registerNode(rootShadowNode);
-    mUIViewOperationQueue.addRootView(rootTag, rootView, themedRootContext);
-    return rootTag;
+
+    SystraceMessage.beginSection(
+      Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+      "FabricUIManager.addRootView")
+      .flush();
+    try {
+      final int rootTag = ReactRootViewTagGenerator.getNextRootViewTag();
+      ThemedReactContext themedRootContext =
+          new ThemedReactContext(mReactApplicationContext, rootView.getContext());
+
+      ReactShadowNode rootShadowNode = createRootShadowNode(rootTag, themedRootContext);
+
+      int widthMeasureSpec = rootView.getWidthMeasureSpec();
+      int heightMeasureSpec = rootView.getHeightMeasureSpec();
+      updateRootView(rootShadowNode, widthMeasureSpec, heightMeasureSpec);
+
+      rootView.setOnSizeChangedListener(
+        new SizeMonitoringFrameLayout.OnSizeChangedListener() {
+          @Override
+          public void onSizeChanged(final int width, final int height, int oldW, int oldH) {
+            updateRootSize(rootTag, width, height);
+          }
+        });
+
+      mRootShadowNodeRegistry.registerNode(rootShadowNode);
+      mUIViewOperationQueue.addRootView(rootTag, rootView, themedRootContext);
+      return rootTag;
+    } finally{
+      Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
+    }
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index c98c12bb07d3..35406a11aa01 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -14,6 +14,8 @@
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.react.common.build.ReactBuildConfig;
 import com.facebook.react.uimanager.annotations.ReactPropertyHolder;
+import com.facebook.systrace.Systrace;
+import com.facebook.systrace.SystraceMessage;
 import com.facebook.yoga.YogaAlign;
 import com.facebook.yoga.YogaBaselineFunction;
 import com.facebook.yoga.YogaConfig;
@@ -72,21 +74,29 @@ public class ReactShadowNodeImpl implements ReactShadowNode<ReactShadowNodeImpl>
       public YogaNode cloneNode(YogaNode oldYogaNode,
           YogaNode parent,
           int childIndex) {
-        ReactShadowNodeImpl parentReactShadowNode = (ReactShadowNodeImpl) parent.getData();
-        Assertions.assertNotNull(parentReactShadowNode);
-        ReactShadowNodeImpl oldReactShadowNode = (ReactShadowNodeImpl) oldYogaNode.getData();
-        Assertions.assertNotNull(oldReactShadowNode);
-
-        if (DEBUG) {
-          FLog.d(
-            TAG,
-            "YogaNode started cloning: oldYogaNode: " + oldReactShadowNode + " - parent: "
-              + parentReactShadowNode + " index: " + childIndex);
+        SystraceMessage.beginSection(
+          Systrace.TRACE_TAG_REACT_JAVA_BRIDGE,
+          "FabricReconciler.YogaNodeCloneFunction")
+          .flush();
+        try {
+          ReactShadowNodeImpl parentReactShadowNode = (ReactShadowNodeImpl) parent.getData();
+          Assertions.assertNotNull(parentReactShadowNode);
+          ReactShadowNodeImpl oldReactShadowNode = (ReactShadowNodeImpl) oldYogaNode.getData();
+          Assertions.assertNotNull(oldReactShadowNode);
+
+          if (DEBUG) {
+            FLog.d(
+              TAG,
+              "YogaNode started cloning: oldYogaNode: " + oldReactShadowNode + " - parent: "
+                + parentReactShadowNode + " index: " + childIndex);
+          }
+
+          ReactShadowNodeImpl newNode = oldReactShadowNode.mutableCopy(oldReactShadowNode.getInstanceHandle());
+          parentReactShadowNode.replaceChild(newNode, childIndex);
+          return newNode.mYogaNode;
+        } finally{
+          Systrace.endSection(Systrace.TRACE_TAG_REACT_JAVA_BRIDGE);
         }
-
-        ReactShadowNodeImpl newNode = oldReactShadowNode.mutableCopy(oldReactShadowNode.getInstanceHandle());
-        parentReactShadowNode.replaceChild(newNode, childIndex);
-        return newNode.mYogaNode;
       }
     });
   }

From d9043614778fe675ff100123751f59f0620ac312 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Thu, 14 Jun 2018 19:42:38 -0700
Subject: [PATCH 0802/1109] Tightening some Image Flow Types

Reviewed By: yungsters

Differential Revision: D7270059

fbshipit-source-id: 3b9727363aeb6910fbbdc613a70d9e8cac97b3b1
---
 Libraries/Image/ImageSource.js | 19 +++++++++----------
 1 file changed, 9 insertions(+), 10 deletions(-)

diff --git a/Libraries/Image/ImageSource.js b/Libraries/Image/ImageSource.js
index 4fdd7f270a53..8338d5feb24a 100644
--- a/Libraries/Image/ImageSource.js
+++ b/Libraries/Image/ImageSource.js
@@ -10,17 +10,16 @@
 'use strict';
 
 // This is to sync with ImageSourcePropTypes.js.
-
 type ImageURISource = $ReadOnly<{|
-  uri?: string,
-  bundle?: string,
-  method?: string,
-  headers?: Object,
-  body?: string,
-  cache?: 'default' | 'reload' | 'force-cache' | 'only-if-cached',
-  width?: number,
-  height?: number,
-  scale?: number,
+  uri?: ?string,
+  bundle?: ?string,
+  method?: ?string,
+  headers?: ?Object,
+  body?: ?string,
+  cache?: ?('default' | 'reload' | 'force-cache' | 'only-if-cached'),
+  width?: ?number,
+  height?: ?number,
+  scale?: ?number,
 |}>;
 
 export type ImageSource = ImageURISource | number | Array<ImageURISource>;

From 5230b2313060102fe6d039badc582f2124b48855 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 14 Jun 2018 20:39:44 -0700
Subject: [PATCH 0803/1109] ios: expose surfaceForRootTag: up the chain

Summary: The app needs to find the surface by rootTag at some point.

Reviewed By: shergin

Differential Revision: D8391957

fbshipit-source-id: b0bb107b7be882071890afb46de17b50e7ee060d
---
 React/Fabric/RCTSurfacePresenter.h  |  3 +++
 React/Fabric/RCTSurfacePresenter.mm | 14 +++++++++-----
 2 files changed, 12 insertions(+), 5 deletions(-)

diff --git a/React/Fabric/RCTSurfacePresenter.h b/React/Fabric/RCTSurfacePresenter.h
index 52c44fbda763..65e86b1289d0 100644
--- a/React/Fabric/RCTSurfacePresenter.h
+++ b/React/Fabric/RCTSurfacePresenter.h
@@ -9,6 +9,7 @@
 #import <memory>
 
 #import <React/RCTBridge.h>
+#import <React/RCTPrimitives.h>
 #import <fabric/uimanager/FabricUIManager.h>
 
 NS_ASSUME_NONNULL_BEGIN
@@ -36,6 +37,7 @@ NS_ASSUME_NONNULL_BEGIN
  */
 - (void)registerSurface:(RCTFabricSurface *)surface;
 - (void)unregisterSurface:(RCTFabricSurface *)surface;
+- (nullable RCTFabricSurface *)surfaceForRootTag:(ReactTag)rootTag;
 
 /**
  * Measures the Surface with given constraints.
@@ -50,6 +52,7 @@ NS_ASSUME_NONNULL_BEGIN
 - (void)setMinimumSize:(CGSize)minimumSize
            maximumSize:(CGSize)maximumSize
                surface:(RCTFabricSurface *)surface;
+
 @end
 
 @interface RCTSurfacePresenter (Deprecated)
diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
index 8673a2fc70cc..190429897644 100644
--- a/React/Fabric/RCTSurfacePresenter.mm
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -8,16 +8,15 @@
 #import "RCTSurfacePresenter.h"
 
 #import <React/RCTAssert.h>
-#import <React/RCTScheduler.h>
-#import <React/RCTMountingManager.h>
-#import <React/RCTFabricSurface.h>
 #import <React/RCTBridge+Private.h>
+#import <React/RCTComponentViewRegistry.h>
+#import <React/RCTFabricSurface.h>
+#import <React/RCTMountingManager.h>
 #import <React/RCTMountingManagerDelegate.h>
+#import <React/RCTScheduler.h>
 #import <React/RCTSurfaceRegistry.h>
-#import <React/RCTComponentViewRegistry.h>
 #import <React/RCTSurfaceView.h>
 #import <React/RCTSurfaceView+Internal.h>
-
 #import <fabric/core/LayoutContext.h>
 #import <fabric/core/LayoutConstraints.h>
 
@@ -83,6 +82,11 @@ - (void)unregisterSurface:(RCTFabricSurface *)surface
   [_surfaceRegistry unregisterSurface:surface];
 }
 
+- (RCTFabricSurface *)surfaceForRootTag:(ReactTag)rootTag
+{
+  return [_surfaceRegistry surfaceForRootTag:rootTag];
+}
+
 - (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize
                       maximumSize:(CGSize)maximumSize
                           surface:(RCTFabricSurface *)surface

From 3bc62f361043b4c12f6d504e79454ea4e2f63a30 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Thu, 14 Jun 2018 22:44:57 -0700
Subject: [PATCH 0804/1109] Keep UIManagerModule as a default renderer

Reviewed By: fkgozali

Differential Revision: D8439626

fbshipit-source-id: d761d977c9e6dab38f21e18da72b045483431f79
---
 .../facebook/react/uimanager/UIManagerHelper.java | 15 +++------------
 1 file changed, 3 insertions(+), 12 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java
index 6503ccb067f0..fa2ac80a572a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerHelper.java
@@ -26,18 +26,9 @@ public static UIManager getUIManagerForReactTag(ReactContext context, int reactT
    */
   public static UIManager getUIManager(ReactContext context, @UIManagerType int uiManagerType) {
     CatalystInstance catalystInstance = context.getCatalystInstance();
-    UIManager uiManager;
-    switch (uiManagerType) {
-      case FABRIC:
-        uiManager = catalystInstance.getJSIModule(UIManager.class);
-        break;
-      case DEFAULT:
-        uiManager = catalystInstance.getNativeModule(UIManagerModule.class);
-        break;
-      default:
-        throw new IllegalArgumentException("Invalid UIManagerType: " + uiManagerType);
-    }
-    return uiManager;
+    return uiManagerType == FABRIC ?
+      catalystInstance.getJSIModule(UIManager.class) :
+      catalystInstance.getNativeModule(UIManagerModule.class);
   }
 
 }

From 1723b6cd9c1eb834de137c8800b12ef6eadeb82a Mon Sep 17 00:00:00 2001
From: Vojtech Novak <vonovak@gmail.com>
Date: Fri, 15 Jun 2018 00:24:51 -0700
Subject: [PATCH 0805/1109] Checkbox to inherit from AppCompatCheckBox (#18318)

Summary:
The checkbox components inherits from `android.widget.CheckBox`. `AppCompatCheckBox` offers better appearance and support for advanced features (eg. tinting) on older APIs.

~~However, the build fails for some reason; If somebody could shed some light on this, I'd appreciate it.~~ Thanks for the comment, I was being blind and somehow ignored the BUCK file.

I have created a simple app with a checkbox.

Screenshot from android 4.1 (current master):

<img src="https://user-images.githubusercontent.com/1566403/37357997-2d34bdb8-26ea-11e8-8c77-709a4f96c6bf.png" width="300" />

Screenshot after applying the change, also android 4.1:

<img src="https://user-images.githubusercontent.com/1566403/37358016-3c28fb86-26ea-11e8-8dca-3a92e41450c9.png" width="300" />

https://github.com/facebook/react-native/pull/18300 (this PR is needed to support tinting on older android api levels)

[ANDROID]  [ENHANCEMENT]  [Checkbox] - Checkbox inherits from AppCompatCheckBox
Closes https://github.com/facebook/react-native/pull/18318

Differential Revision: D7268393

Pulled By: hramos

fbshipit-source-id: 01cb2819f4d56c4e0f94cdd1fb5e1a90667a398a
---
 .../src/main/java/com/facebook/react/views/checkbox/BUCK      | 1 +
 .../java/com/facebook/react/views/checkbox/ReactCheckBox.java | 4 ++--
 2 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/BUCK
index 16a570698f62..7bf08765acca 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/BUCK
@@ -5,6 +5,7 @@ rn_android_library(
     srcs = glob(["*.java"]),
     provided_deps = [
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
+        react_native_dep("third-party/android/support/v7/appcompat-orig:appcompat"),
     ],
     visibility = [
         "PUBLIC",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBox.java b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBox.java
index 324a9b2c7869..98c0b67aa424 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBox.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/checkbox/ReactCheckBox.java
@@ -7,10 +7,10 @@
 package com.facebook.react.views.checkbox;
 
 import android.content.Context;
-import android.widget.CheckBox;
+import android.support.v7.widget.AppCompatCheckBox;
 
 /** CheckBox that has its value controlled by JS. */
-/*package*/ class ReactCheckBox extends CheckBox {
+/*package*/ class ReactCheckBox extends AppCompatCheckBox {
 
   private boolean mAllowChange;
 

From b8402852a2337e7b1425bc9937c300ae1c88fca4 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Fri, 15 Jun 2018 06:50:01 -0700
Subject: [PATCH 0806/1109] Bump Metro dep in RN preset to 39.1, preset to
 5.0.2

Reviewed By: rubennorte

Differential Revision: D8445528

fbshipit-source-id: e8937509bb1384a2d62e880c860306d8c86dab92
---
 babel-preset/package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/babel-preset/package.json b/babel-preset/package.json
index 77eaafb46f82..e69445202ca8 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -1,6 +1,6 @@
 {
   "name": "babel-preset-react-native",
-  "version": "5.0.1",
+  "version": "5.0.2",
   "description": "Babel preset for React Native applications",
   "main": "index.js",
   "repository": "https://github.com/facebook/react-native/tree/master/babel-preset",
@@ -41,6 +41,6 @@
     "@babel/plugin-transform-template-literals": "7.0.0-beta.47",
     "@babel/plugin-transform-unicode-regex": "7.0.0-beta.47",
     "@babel/template": "7.0.0-beta.47",
-    "metro-babel7-plugin-react-transform": "^0.38.1"
+    "metro-babel7-plugin-react-transform": "^0.39.1"
   }
 }

From 5fd5e6b230c83d7a8011d9a2fb0b8a2f1bd49b34 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Fri, 15 Jun 2018 07:39:24 -0700
Subject: [PATCH 0807/1109] Revert "Bump soloader to 0.5.0 (#19676)" (#19739)

Summary:
This reverts commit e3c5524bc65026a4c3d062cb05cee85b6d835286.
Closes https://github.com/facebook/react-native/pull/19739

Differential Revision: D8446714

Pulled By: hramos

fbshipit-source-id: 1b0e78fe57e9864faafcc766364bd76a1ba5bd03
---
 ReactAndroid/build.gradle | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 289ad9acd1e5..601071cdec1f 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -299,7 +299,7 @@ dependencies {
     compile 'com.facebook.fbui.textlayoutbuilder:textlayoutbuilder:1.0.0'
     compile 'com.facebook.fresco:fresco:1.9.0'
     compile 'com.facebook.fresco:imagepipeline-okhttp3:1.9.0'
-    compile 'com.facebook.soloader:soloader:0.5.0'
+    compile 'com.facebook.soloader:soloader:0.3.0'
     compile 'com.google.code.findbugs:jsr305:3.0.0'
     compile 'com.squareup.okhttp3:okhttp:3.10.0'
     compile 'com.squareup.okhttp3:okhttp-urlconnection:3.10.0'

From 86d8c7a9b37c93955ac0a444093fbd4b1b0c31c0 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Fri, 15 Jun 2018 07:54:22 -0700
Subject: [PATCH 0808/1109] Bugfix/ci lint proguard (#19724)

Summary:
* avoid lint to interrupt ci
* add proguard rules
pass all ci
none
 [GENERAL] [ENHANCEMENT] [CI] - Fix lint and proguard
Closes https://github.com/facebook/react-native/pull/19724

Differential Revision: D8446721

Pulled By: hramos

fbshipit-source-id: b21c5418210b27dda6a7194995a25df39af0c92a
---
 RNTester/android/app/build.gradle | 5 +++++
 build.gradle                      | 8 ++++++++
 2 files changed, 13 insertions(+)

diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index 9ccb79c0b053..2a2e3834c95b 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -120,6 +120,11 @@ android {
             signingConfig signingConfigs.release
         }
     }
+
+    lintOptions {
+        abortOnError false
+    }
+
     // applicationVariants are e.g. debug, release
     applicationVariants.all { variant ->
         variant.outputs.each { output ->
diff --git a/build.gradle b/build.gradle
index 71634a0cbefc..c9c43736f86c 100644
--- a/build.gradle
+++ b/build.gradle
@@ -35,4 +35,12 @@ allprojects {
             url "$androidSdk/extras/m2repository/"
         }
     }
+
+    project.configurations.all {
+        resolutionStrategy.eachDependency { details ->
+            if (details.requested.group == 'com.facebook.soloader') {
+                details.useVersion "0.3.0"
+            }
+        }
+    }
 }

From 4e1abdd74dc4127a86d62e7750d01d39bb781c08 Mon Sep 17 00:00:00 2001
From: Vojtech Novak <vonovak@gmail.com>
Date: Fri, 15 Jun 2018 10:33:28 -0700
Subject: [PATCH 0809/1109] fix permission requests on pre-M android (#19734)

Summary:
On pre-M devices, `PermissionsAndroid.request` currently returns a boolean, whereas on newer, it returns GRANTED, DENIED or other constants defined in `PermissionsModule.java`

given the example form the [docs](https://facebook.github.io/react-native/docs/permissionsandroid.html) which I guess many people use, this will lead to code that does not work before M (it will tell you that permissions are not given even if they are in the manifest).

I believe the author of [this](https://github.com/facebook/react-native/commit/51efaab1209a41254c90dcba596d49e3cbc2d925) forgot to change the resolved value in this one place but changed it in other places, eg [here](https://github.com/facebook/react-native/commit/51efaab1209a41254c90dcba596d49e3cbc2d925#diff-2a74096453bc8faa5d4a1599ad0ab33fL99).

The docs are written correctly:

> On devices before SDK version 23, the permissions are automatically granted if they appear in the manifest, so check and request should always be true.

but the code is not right because we'd need to check for `if (granted === PermissionsAndroid.RESULTS.GRANTED || granted === true) {`

Also, the behavior is done correctly in [requestMultiplePermissions](https://github.com/facebook/react-native/blob/26684cf3adf4094eb6c405d345a75bf8c7c0bf88/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/PermissionsModule.java#L148) so returning a boolean is an inconsistency.

I tested this locally. The code is the same as on line [148](https://github.com/facebook/react-native/blob/26684cf3adf4094eb6c405d345a75bf8c7c0bf88/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/PermissionsModule.java#L148) where it is done correctly.

[ANDROID] [BUGFIX] [PermissionAndroid] - return GRANTED / DENIED instead of true / false on pre-M android

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/19734

Differential Revision: D8450402

Pulled By: hramos

fbshipit-source-id: 46b0b7f83f81d817d60234f155d43de7f57248c7
---
 .../react/modules/permissions/PermissionsModule.java      | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/PermissionsModule.java b/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/PermissionsModule.java
index 0b943bc6c08e..26701edd94cd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/PermissionsModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/permissions/PermissionsModule.java
@@ -86,9 +86,9 @@ public void shouldShowRequestPermissionRationale(final String permission, final
   }
 
   /**
-   * Request the given permission. successCallback is called with true if the permission had been
-   * granted, false otherwise. For devices before Android M, this instead checks if the user has
-   * the permission given or not.
+   * Request the given permission. successCallback is called with GRANTED if the permission had been
+   * granted, DENIED or NEVER_ASK_AGAIN otherwise. For devices before Android M, this checks if the user has
+   * the permission given or not and resolves with GRANTED or DENIED.
    * See {@link Activity#checkSelfPermission}.
    */
   @ReactMethod
@@ -96,7 +96,7 @@ public void requestPermission(final String permission, final Promise promise) {
     Context context = getReactApplicationContext().getBaseContext();
     if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) {
       promise.resolve(context.checkPermission(permission, Process.myPid(), Process.myUid()) ==
-              PackageManager.PERMISSION_GRANTED);
+              PackageManager.PERMISSION_GRANTED ? GRANTED : DENIED);
       return;
     }
     if (context.checkSelfPermission(permission) == PackageManager.PERMISSION_GRANTED) {

From a7a2ef1bb65c6908b8ac68f8addaac1c75de98e3 Mon Sep 17 00:00:00 2001
From: Eoin Norris <e.norris@mac.com>
Date: Fri, 15 Jun 2018 10:34:12 -0700
Subject: [PATCH 0810/1109] Possible fix for 18890 (#19687)

Summary:
Potential fixes for 18890. The issue was that when the setAttributedText method in RCTBaseTextInputView.m is called it does two main things:

Check that the attributed text that it receives is equal to the existing attributed text in the underlying backed up view ( backedTextInputView)
If not set the attributed text of the backed up view to the value passed into the method. This kills the dictation as it is effectively the equivalent of typing in the backed up text view.
    self.backedTextInputView.attributedText = attributedText;
is the problem. It kills the dictation. It may have other effects as well.

In all cases I have seen the underlying text of the attributed string that is passed in the same as the text in the backedTextInputView, what was said to the dictation; however the attributes are different, which causes the isEqualToAttributedString: check to fail and thus the update happens, and the keyboard is killed.

Fix is to test for the underlying string equality not the attributed string equality when the input mode is dictation.

By necessity this had to be an integration test on an existing application. To test I enabled the keyboard and started the dictation. It worked with this fixes and not without. Will upload videos later.

This might break attributes on dictation, as it is happening. However anything set on the existing underlying text view should hold.

[IOS] [BUG] [Textinput] fixed an issue where the keyboard dictation ended abruptly.
Closes https://github.com/facebook/react-native/pull/19687

Differential Revision: D8450590

Pulled By: hramos

fbshipit-source-id: f97084131f98e9e0ed1f32111afc0f9f510f3b3b
---
 .../Text/TextInput/RCTBaseTextInputView.m     | 28 ++++++++++++++-----
 1 file changed, 21 insertions(+), 7 deletions(-)

diff --git a/Libraries/Text/TextInput/RCTBaseTextInputView.m b/Libraries/Text/TextInput/RCTBaseTextInputView.m
index ebb8a8308188..0d085c19cac6 100644
--- a/Libraries/Text/TextInput/RCTBaseTextInputView.m
+++ b/Libraries/Text/TextInput/RCTBaseTextInputView.m
@@ -98,10 +98,22 @@ - (NSAttributedString *)attributedText
   return self.backedTextInputView.attributedText;
 }
 
+- (BOOL)textOf:(NSAttributedString*)newText equals:(NSAttributedString*)oldText{
+  UITextInputMode *currentInputMode =  self.backedTextInputView.textInputMode;
+  if ([currentInputMode.primaryLanguage isEqualToString:@"dictation"]) {
+    // When the dictation is running we can't update the attibuted text on the backed up text view
+    // because setting the attributed string will kill the dictation. This means that we can't impose
+    // the settings on a dictation.
+    return ([newText.string isEqualToString:oldText.string]);
+  } else {
+    return ([newText isEqualToAttributedString:oldText]);
+  }
+}
+
 - (void)setAttributedText:(NSAttributedString *)attributedText
 {
   NSInteger eventLag = _nativeEventCount - _mostRecentEventCount;
-
+  BOOL textNeedsUpdate = NO;
   // Remove tag attribute to ensure correct attributed string comparison.
   NSMutableAttributedString *const backedTextInputViewTextCopy = [self.backedTextInputView.attributedText mutableCopy];
   NSMutableAttributedString *const attributedTextCopy = [attributedText mutableCopy];
@@ -111,8 +123,10 @@ - (void)setAttributedText:(NSAttributedString *)attributedText
 
   [attributedTextCopy removeAttribute:RCTTextAttributesTagAttributeName
                                 range:NSMakeRange(0, attributedTextCopy.length)];
-
-  if (eventLag == 0 && ![attributedTextCopy isEqualToAttributedString:backedTextInputViewTextCopy]) {
+  
+  textNeedsUpdate = ([self textOf:attributedTextCopy equals:backedTextInputViewTextCopy] == NO);
+  
+  if (eventLag == 0 && textNeedsUpdate) {
     UITextRange *selection = self.backedTextInputView.selectedTextRange;
     NSInteger oldTextLength = self.backedTextInputView.attributedText.string.length;
 
@@ -121,13 +135,13 @@ - (void)setAttributedText:(NSAttributedString *)attributedText
     if (selection.empty) {
       // Maintaining a cursor position relative to the end of the old text.
       NSInteger offsetStart =
-        [self.backedTextInputView offsetFromPosition:self.backedTextInputView.beginningOfDocument
-                                          toPosition:selection.start];
+      [self.backedTextInputView offsetFromPosition:self.backedTextInputView.beginningOfDocument
+                                        toPosition:selection.start];
       NSInteger offsetFromEnd = oldTextLength - offsetStart;
       NSInteger newOffset = attributedText.string.length - offsetFromEnd;
       UITextPosition *position =
-        [self.backedTextInputView positionFromPosition:self.backedTextInputView.beginningOfDocument
-                                                offset:newOffset];
+      [self.backedTextInputView positionFromPosition:self.backedTextInputView.beginningOfDocument
+                                              offset:newOffset];
       [self.backedTextInputView setSelectedTextRange:[self.backedTextInputView textRangeFromPosition:position toPosition:position]
                                       notifyDelegate:YES];
     }

From 0883e52c74a59f750107c63fff61753bbd74611d Mon Sep 17 00:00:00 2001
From: Jay Phelps <hello@jayphelps.com>
Date: Fri, 15 Jun 2018 10:37:23 -0700
Subject: [PATCH 0811/1109] remove deprecated behavior of
 touchableHandleActivePressIn/Out called for focus/blur (#19718)

Summary:
Follow up to #18470, which has not yet landed in a release so we may want to hold off merging this until it has so that people receive the deprecation warning.

***

This PR removes the previously deprecated behavior of touchableHandleActivePressIn/Out (as well as onPressIn/Out being called on TV platforms for focus/blur. Instead, users should utilize the new `onFocus` and `onBlur` for these events.

This was because on TV platforms onPressIn/Out was overloaded to trigger for not only presses but these focus events as well. The normal behavior of true presses will still defer to touchableHandleActivePressIn/Out (which defers to onPressIn/Out).

<!--
  Required.
  Help reviewers and the release process by writing your own release notes. See below for an example.
-->

[TV] [BREAKING] [Touchable] - On TV platforms `onPressIn` and `onPressOut` on Touchables will now only be triggered for press events, not for focus/blur. Instead, you can use `onFocus` and `onBlur`.

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->

Cc/ matthargett
Closes https://github.com/facebook/react-native/pull/19718

Differential Revision: D8450514

Pulled By: hramos

fbshipit-source-id: 818e85a338a451834b54d8965602699fc9b24e87
---
 Libraries/Components/Touchable/Touchable.js | 8 --------
 1 file changed, 8 deletions(-)

diff --git a/Libraries/Components/Touchable/Touchable.js b/Libraries/Components/Touchable/Touchable.js
index 1af0887d46cd..6a8fa3cb5d82 100644
--- a/Libraries/Components/Touchable/Touchable.js
+++ b/Libraries/Components/Touchable/Touchable.js
@@ -325,16 +325,8 @@ const TouchableMixin = {
       evt.dispatchConfig = {};
       if (myTag === evt.tag) {
         if (evt.eventType === 'focus') {
-          if (cmp.touchableHandleActivePressIn) {
-            console.warn('Using `touchableHandleActivePressIn` or `onPressIn` to listen for focus events is deprecated. Use `touchableHandleFocus` or `onFocus` instead.');
-            cmp.touchableHandleActivePressIn(evt);
-          }
           cmp.touchableHandleFocus(evt);
         } else if (evt.eventType === 'blur') {
-          if (cmp.touchableHandleActivePressOut) {
-            console.warn('Using `touchableHandleActivePressOut` or `onPressOut` to listen for blur events is deprecated. Use `touchableHandleBlur` or `onBlur` instead.');
-            cmp.touchableHandleActivePressOut(evt);
-          }
           cmp.touchableHandleBlur(evt);
         } else if (evt.eventType === 'select') {
           cmp.touchableHandlePress &&

From 2ca4770011cf1cfeb5803126bdf6d457ff57cc47 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 15 Jun 2018 10:56:38 -0700
Subject: [PATCH 0812/1109] fabric: send events via JS thread

Summary: Calling the event emitters on the main thread seems to be problematic, so let's dispatch it via the JS thread. This requires some changes to make "eventTarget" single-use because otherwise the binding would need to synchronize the actual JS call with the act of releasing the target.

Reviewed By: shergin

Differential Revision: D8375291

fbshipit-source-id: bd2b42731176ae209f4a19c232309c163fb1c01b
---
 React/CxxBridge/RCTCxxBridge.mm               |  5 ++++
 .../fabric/core/events/EventDispatcher.h      |  2 --
 .../fabric/core/events/EventEmitter.cpp       | 30 ++++---------------
 ReactCommon/fabric/core/events/EventEmitter.h |  5 +---
 .../fabric/uimanager/FabricUIManager.cpp      |  8 -----
 .../fabric/uimanager/FabricUIManager.h        |  4 ---
 .../uimanager/SchedulerEventDispatcher.cpp    |  5 +---
 .../uimanager/SchedulerEventDispatcher.h      |  2 --
 8 files changed, 12 insertions(+), 49 deletions(-)

diff --git a/React/CxxBridge/RCTCxxBridge.mm b/React/CxxBridge/RCTCxxBridge.mm
index b445991fbb34..42c3fdbf565a 100644
--- a/React/CxxBridge/RCTCxxBridge.mm
+++ b/React/CxxBridge/RCTCxxBridge.mm
@@ -188,6 +188,11 @@ - (JSGlobalContextRef)jsContextRef
   return (JSGlobalContextRef)(_reactInstance ? _reactInstance->getJavaScriptContext() : nullptr);
 }
 
+- (std::shared_ptr<MessageQueueThread>)jsMessageThread
+{
+  return _jsMessageThread;
+}
+
 - (BOOL)isInspectable
 {
   return _reactInstance ? _reactInstance->isInspectable() : NO;
diff --git a/ReactCommon/fabric/core/events/EventDispatcher.h b/ReactCommon/fabric/core/events/EventDispatcher.h
index 930a547f4ae6..d241f3a2953e 100644
--- a/ReactCommon/fabric/core/events/EventDispatcher.h
+++ b/ReactCommon/fabric/core/events/EventDispatcher.h
@@ -30,8 +30,6 @@ class EventDispatcher {
 
   virtual EventTarget createEventTarget(const InstanceHandle &instanceHandle) const = 0;
 
-  virtual void releaseEventTarget(const EventTarget &eventTarget) const = 0;
-
   /*
    * Dispatches "raw" event using some event-delivery infrastructure.
    */
diff --git a/ReactCommon/fabric/core/events/EventEmitter.cpp b/ReactCommon/fabric/core/events/EventEmitter.cpp
index b4b3b8db38be..ec42f0f1d195 100644
--- a/ReactCommon/fabric/core/events/EventEmitter.cpp
+++ b/ReactCommon/fabric/core/events/EventEmitter.cpp
@@ -17,9 +17,7 @@ EventEmitter::EventEmitter(const InstanceHandle &instanceHandle, const Tag &tag,
   tag_(tag),
   eventDispatcher_(eventDispatcher) {}
 
-EventEmitter::~EventEmitter() {
-  releaseEventTargetIfNeeded();
-}
+EventEmitter::~EventEmitter() {}
 
 void EventEmitter::dispatchEvent(
   const std::string &type,
@@ -31,7 +29,7 @@ void EventEmitter::dispatchEvent(
     return;
   }
 
-  createEventTargetIfNeeded();
+  EventTarget eventTarget = createEventTarget();
 
   // Mixing `target` into `payload`.
   assert(payload.isObject());
@@ -39,31 +37,13 @@ void EventEmitter::dispatchEvent(
   extendedPayload.merge_patch(payload);
 
   // TODO(T29610783): Reconsider using dynamic dispatch here.
-  eventDispatcher->dispatchEvent(eventTarget_, type, extendedPayload, priority);
+  eventDispatcher->dispatchEvent(eventTarget, type, extendedPayload, priority);
 }
 
-void EventEmitter::createEventTargetIfNeeded() const {
-  std::lock_guard<std::mutex> lock(mutex_);
-
-  if (eventTarget_) {
-    return;
-  }
-
-  auto &&eventDispatcher = eventDispatcher_.lock();
-  assert(eventDispatcher);
-  eventTarget_ = eventDispatcher->createEventTarget(instanceHandle_);
-}
-
-void EventEmitter::releaseEventTargetIfNeeded() const {
-  std::lock_guard<std::mutex> lock(mutex_);
-
-  if (!eventTarget_) {
-    return;
-  }
-
+EventTarget EventEmitter::createEventTarget() const {
   auto &&eventDispatcher = eventDispatcher_.lock();
   assert(eventDispatcher);
-  eventDispatcher->releaseEventTarget(eventTarget_);
+  return eventDispatcher->createEventTarget(instanceHandle_);
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/events/EventEmitter.h b/ReactCommon/fabric/core/events/EventEmitter.h
index eb05bd1c6257..f63c59d73245 100644
--- a/ReactCommon/fabric/core/events/EventEmitter.h
+++ b/ReactCommon/fabric/core/events/EventEmitter.h
@@ -48,14 +48,11 @@ class EventEmitter {
 
 private:
 
-  void createEventTargetIfNeeded() const;
-  void releaseEventTargetIfNeeded() const;
+  EventTarget createEventTarget() const;
 
   InstanceHandle instanceHandle_;
   Tag tag_;
   std::weak_ptr<const EventDispatcher> eventDispatcher_;
-  mutable EventTarget eventTarget_ {nullptr};
-  mutable std::mutex mutex_;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 30df1137cbfb..1c8f96b3db48 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -98,10 +98,6 @@ void FabricUIManager::setDispatchEventFunction(std::function<DispatchEventFuncti
   dispatchEventFunction_ = dispatchEventFunction;
 }
 
-void FabricUIManager::setReleaseEventTargetFunction(std::function<ReleaseEventTargetFunction> releaseEventTargetFunction) {
-  releaseEventTargetFunction_ = releaseEventTargetFunction;
-}
-
 void FabricUIManager::setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction) {
   releaseEventHandlerFunction_ = releaseEventHandlerFunction;
 }
@@ -119,10 +115,6 @@ void FabricUIManager::dispatchEvent(const EventTarget &eventTarget, const std::s
   );
 }
 
-void FabricUIManager::releaseEventTarget(const EventTarget &eventTarget) const {
-  releaseEventTargetFunction_(eventTarget);
-}
-
 SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, InstanceHandle instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag: " << rootTag << ", props: " << props << ")";
 
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index ca0987a08a2a..bd16f02946c0 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -20,7 +20,6 @@ namespace react {
 
 using CreateEventTargetFunction = EventTarget (InstanceHandle instanceHandle);
 using DispatchEventFunction = void (EventHandler eventHandler, EventTarget eventTarget, std::string type, folly::dynamic payload);
-using ReleaseEventTargetFunction = void (EventTarget eventTarget);
 using ReleaseEventHandlerFunction = void (EventHandler eventHandler);
 
 class FabricUIManager {
@@ -46,14 +45,12 @@ class FabricUIManager {
    */
   void setCreateEventTargetFunction(std::function<CreateEventTargetFunction> createEventTargetFunction);
   void setDispatchEventFunction(std::function<DispatchEventFunction> dispatchEventFunction);
-  void setReleaseEventTargetFunction(std::function<ReleaseEventTargetFunction> releaseEventTargetFunction);
   void setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction);
 
 #pragma mark - Native-facing Interface
 
   EventTarget createEventTarget(const InstanceHandle &instanceHandle) const;
   void dispatchEvent(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const;
-  void releaseEventTarget(const EventTarget &eventTarget) const;
 
 #pragma mark - JavaScript/React-facing Interface
 
@@ -75,7 +72,6 @@ class FabricUIManager {
   EventHandler eventHandler_;
   std::function<CreateEventTargetFunction> createEventTargetFunction_;
   std::function<DispatchEventFunction> dispatchEventFunction_;
-  std::function<ReleaseEventTargetFunction> releaseEventTargetFunction_;
   std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction_;
 };
 
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
index 5cd608667b63..0dce7c6b0c2a 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
@@ -30,16 +30,13 @@ EventTarget SchedulerEventDispatcher::createEventTarget(const InstanceHandle &in
   return uiManager_->createEventTarget(instanceHandle);
 }
 
-void SchedulerEventDispatcher::releaseEventTarget(const EventTarget &eventTarget) const {
-  uiManager_->releaseEventTarget(eventTarget);
-}
-
 void SchedulerEventDispatcher::dispatchEvent(
   const EventTarget &eventTarget,
   const std::string &type,
   const folly::dynamic &payload,
   const EventPriority &priority
 ) const {
+  // TODO: Schedule the event based on priority.
   uiManager_->dispatchEvent(eventTarget, normalizeEventType(type), payload);
 }
 
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
index d7f6e190c0ff..313d3b2ee182 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
@@ -33,8 +33,6 @@ class SchedulerEventDispatcher final:
 
   EventTarget createEventTarget(const InstanceHandle &instanceHandle) const override;
 
-  void releaseEventTarget(const EventTarget &eventTarget) const override;
-
   void dispatchEvent(
     const EventTarget &eventTarget,
     const std::string &type,

From cb19621dfe51879407337a1cc19ef27355a451aa Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 15 Jun 2018 10:56:40 -0700
Subject: [PATCH 0813/1109] Implementation of JS reload without crashing

Summary:
On JS reload the FabricUIManager and EventDispatcher didn't get release due to a retain cycle. This breaks the cycle.

In addition, force release the Scheduler on reload so that the stale classes get cleaned up properly, avoiding crashes. Also the surface now remounts the content correctly

Reviewed By: shergin

Differential Revision: D8414916

fbshipit-source-id: 4b14031f29b3bc9987d7aa765dc0d930a7de2b1e
---
 React/Fabric/RCTSurfacePresenter.mm           | 28 +++++++++++++
 React/Fabric/Surface/RCTFabricSurface.mm      | 40 +++++++++++++++++++
 ReactCommon/fabric/uimanager/Scheduler.cpp    |  1 +
 .../uimanager/SchedulerEventDispatcher.cpp    |  2 +-
 .../uimanager/SchedulerEventDispatcher.h      |  5 ++-
 5 files changed, 73 insertions(+), 3 deletions(-)

diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
index 190429897644..9c9c15955bbb 100644
--- a/React/Fabric/RCTSurfacePresenter.mm
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -47,6 +47,15 @@ - (instancetype)initWithBridge:(RCTBridge *)bridge
     _surfaceRegistry = [[RCTSurfaceRegistry alloc] init];
     _mountingManager = [[RCTMountingManager alloc] init];
     _mountingManager.delegate = self;
+
+    [[NSNotificationCenter defaultCenter] addObserver:self
+                                             selector:@selector(handleBridgeWillReloadNotification:)
+                                                 name:RCTBridgeWillReloadNotification
+                                               object:_bridge];
+    [[NSNotificationCenter defaultCenter] addObserver:self
+                                             selector:@selector(handleJavaScriptDidLoadNotification:)
+                                                 name:RCTJavaScriptDidLoadNotification
+                                               object:_bridge];
   }
 
   return self;
@@ -153,6 +162,25 @@ - (void)mountingManager:(RCTMountingManager *)mountingManager didMountComponents
   surface.view.rootView = (RCTSurfaceRootView *)rootComponentView;
 }
 
+#pragma mark - Bridge events
+
+- (void)handleBridgeWillReloadNotification:(NSNotification *)notification
+{
+  // TODO: Define a lifecycle contract for the pieces involved here including the scheduler, mounting manager, and
+  // the surface registry. For now simply recreate the scheduler on reload.
+  // The goal is to deallocate the Scheduler and its underlying references before the JS runtime is destroyed.
+  _scheduler = [[RCTScheduler alloc] init];
+  _scheduler.delegate = self;
+}
+
+- (void)handleJavaScriptDidLoadNotification:(NSNotification *)notification
+{
+  RCTBridge *bridge = notification.userInfo[@"bridge"];
+  if (bridge != _batchedBridge) {
+    _batchedBridge = bridge;
+  }
+}
+
 @end
 
 @implementation RCTSurfacePresenter (Deprecated)
diff --git a/React/Fabric/Surface/RCTFabricSurface.mm b/React/Fabric/Surface/RCTFabricSurface.mm
index 2e06d361d01e..267ef61c0251 100644
--- a/React/Fabric/Surface/RCTFabricSurface.mm
+++ b/React/Fabric/Surface/RCTFabricSurface.mm
@@ -74,6 +74,15 @@ - (instancetype)initWithSurfacePresenter:(RCTSurfacePresenter *)surfacePresenter
     _touchHandler = [RCTSurfaceTouchHandler new];
 
     [self _run];
+
+    [[NSNotificationCenter defaultCenter] addObserver:self
+                                             selector:@selector(handleJavaScriptWillStartLoadingNotification:)
+                                                 name:RCTJavaScriptWillStartLoadingNotification
+                                               object:_bridge];
+    [[NSNotificationCenter defaultCenter] addObserver:self
+                                             selector:@selector(handleJavaScriptDidLoadNotification:)
+                                                 name:RCTJavaScriptDidLoadNotification
+                                               object:_bridge];
   }
 
   return self;
@@ -268,4 +277,35 @@ - (BOOL)synchronouslyWaitForStage:(RCTSurfaceStage)stage timeout:(NSTimeInterval
   return NO;
 }
 
+#pragma mark - Bridge events
+
+- (void)handleJavaScriptWillStartLoadingNotification:(NSNotification *)notification
+{
+  // TODO: Move the bridge lifecycle handling up to the RCTSurfacePresenter.
+
+  RCTAssertMainQueue();
+
+  // Reset states because the bridge is reloading. This is similar to initialization phase.
+  _stage = RCTSurfaceStageSurfaceDidInitialize;
+  _view = nil;
+  _touchHandler = [RCTSurfaceTouchHandler new];
+  [self _setStage:RCTSurfaceStageBridgeDidLoad];
+}
+
+- (void)handleJavaScriptDidLoadNotification:(NSNotification *)notification
+{
+  // TODO: Move the bridge lifecycle handling up to the RCTSurfacePresenter.
+
+  // Note: this covers only JS reloads.
+  [self _setStage:RCTSurfaceStageModuleDidLoad];
+  [self _run];
+
+  // After a reload surfacePresenter needs to know the last min/max size for this surface, because the surface hosting
+  // view was already attached to the ViewController's view.
+  // TODO: Find a better automatic way.
+  [_surfacePresenter setMinimumSize:_minimumSize
+                        maximumSize:_maximumSize
+                            surface:self];
+}
+
 @end
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index 5a488f4da476..bcb89f0ad8ba 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -35,6 +35,7 @@ Scheduler::Scheduler() {
 
 Scheduler::~Scheduler() {
   uiManager_->setDelegate(nullptr);
+  eventDispatcher_->setUIManager(nullptr);
 }
 
 void Scheduler::registerRootTag(Tag rootTag) {
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
index 0dce7c6b0c2a..11d40c1d32e5 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
@@ -22,7 +22,7 @@ static std::string normalizeEventType(const std::string &type) {
   return prefixedType;
 }
 
-void SchedulerEventDispatcher::setUIManager(std::shared_ptr<const FabricUIManager> uiManager) {
+void SchedulerEventDispatcher::setUIManager(std::shared_ptr<const FabricUIManager> uiManager) const {
   uiManager_ = uiManager;
 }
 
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
index 313d3b2ee182..bb6fd12de35e 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
@@ -27,7 +27,7 @@ class SchedulerEventDispatcher final:
 
 public:
 
-  void setUIManager(std::shared_ptr<const FabricUIManager> uiManager);
+  void setUIManager(std::shared_ptr<const FabricUIManager> uiManager) const;
 
 #pragma mark - EventDispatcher
 
@@ -42,7 +42,8 @@ class SchedulerEventDispatcher final:
 
 private:
 
-  std::shared_ptr<const FabricUIManager> uiManager_;
+  // TODO: consider using std::weak_ptr<> instead for better memory management.
+  mutable std::shared_ptr<const FabricUIManager> uiManager_;
 };
 
 } // namespace react

From e311fbb79754fffc68ae1e2289672fca8bd63f0a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:13 -0700
Subject: [PATCH 0814/1109] Fabric: CornerInsets: Graphical primitive for
 rect-corner-specific values

Summary: CornerInsets is something like EdgeInsets but about corners instead of edges.

Reviewed By: fkgozali

Differential Revision: D8344062

fbshipit-source-id: 9bf7a8696fba96e3124cb15e8e84093c1f4f8747
---
 ReactCommon/fabric/graphics/Geometry.h    | 20 +++++++++++++++
 ReactCommon/fabric/graphics/conversions.h | 30 +++++++++++++++++++++++
 2 files changed, 50 insertions(+)

diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index 9c198c4be447..e44dba31ea4f 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -125,5 +125,25 @@ struct EdgeInsets {
   }
 };
 
+/*
+ * CornerInsets
+ */
+struct CornerInsets {
+  Float topLeft {0};
+  Float topRight {0};
+  Float bottomLeft {0};
+  Float bottomRight {0};
+
+  bool operator ==(const CornerInsets& rhs) const {
+    return
+    std::tie(this->topLeft, this->topRight, this->bottomLeft, this->bottomRight) ==
+    std::tie(rhs.topLeft, rhs.topRight, rhs.bottomLeft, rhs.bottomRight);
+  }
+
+  bool operator !=(const CornerInsets& rhs) const {
+    return !(*this == rhs);
+  }
+};
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/graphics/conversions.h b/ReactCommon/fabric/graphics/conversions.h
index 061725c012ac..7c79d0b38d39 100644
--- a/ReactCommon/fabric/graphics/conversions.h
+++ b/ReactCommon/fabric/graphics/conversions.h
@@ -105,6 +105,28 @@ inline void fromDynamic(const folly::dynamic &value, EdgeInsets &result) {
   abort();
 }
 
+inline void fromDynamic(const folly::dynamic &value, CornerInsets &result) {
+  if (value.isObject()) {
+    result = CornerInsets {
+      (Float)value["topLeft"].asDouble(),
+      (Float)value["topRight"].asDouble(),
+      (Float)value["bottomLeft"].asDouble(),
+      (Float)value["bottomRight"].asDouble()
+    };
+    return;
+  }
+  if (value.isArray()) {
+    result = CornerInsets {
+      (Float)value[0].asDouble(),
+      (Float)value[1].asDouble(),
+      (Float)value[2].asDouble(),
+      (Float)value[3].asDouble()
+    };
+    return;
+  }
+  abort();
+}
+
 inline std::string toString(const Point &point) {
   return "{" + folly::to<std::string>(point.x) + ", " + folly::to<std::string>(point.y) + "}";
 }
@@ -125,5 +147,13 @@ inline std::string toString(const EdgeInsets &edgeInsets) {
     folly::to<std::string>(edgeInsets.bottom) + "}";
 }
 
+inline std::string toString(const CornerInsets &cornerInsets) {
+  return "{" +
+    folly::to<std::string>(cornerInsets.topLeft) + ", " +
+    folly::to<std::string>(cornerInsets.topRight) + ", " +
+    folly::to<std::string>(cornerInsets.bottomLeft) + ", " +
+    folly::to<std::string>(cornerInsets.bottomRight) + "}";
+}
+
 } // namespace react
 } // namespace facebook

From 8fa2d847b6070f13f5a18e63c7d82cf56530a8b5 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:14 -0700
Subject: [PATCH 0815/1109] Fabric: `-[RCTViewComponentView setContentView:]`:

Summary:
This is just the convenient way to embed native views inside custom View components.
See coming <Switch> implementation as an example.

Reviewed By: fkgozali

Differential Revision: D8344056

fbshipit-source-id: 7f5f8cfeeffa7676bc7b562aa07f006cb9006575
---
 .../View/RCTViewComponentView.h               | 10 ++++++++
 .../View/RCTViewComponentView.mm              | 25 ++++++++++++++++++-
 2 files changed, 34 insertions(+), 1 deletion(-)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index 73c3302a65bc..d45bcce07e20 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -26,6 +26,16 @@ NS_ASSUME_NONNULL_BEGIN
   facebook::react::SharedViewEventEmitter _eventEmitter;
 }
 
+/**
+ * Represents the `UIView` instance that is being automatically attached to
+ * the component view and laid out using on `layoutMetrics` (especially `size`
+ * and `padding`) of the component.
+ * This view must not be a component view; it's just a convenient way
+ * to embed/bridge pure native views as component views.
+ * Defaults to `nil`. Assing `nil` to remove view as subview.
+ */
+@property (nonatomic, strong, nullable) UIView *contentView;
+
 @end
 
 NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index f6e74eda4b12..a5f0c67283d2 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -14,6 +14,28 @@
 using namespace facebook::react;
 
 @implementation RCTViewComponentView
+- (void)setContentView:(UIView *)contentView
+{
+  if (_contentView) {
+    [_contentView removeFromSuperview];
+  }
+
+  _contentView = contentView;
+
+  if (_contentView) {
+    [self addSubview:_contentView];
+  }
+}
+
+- (void)layoutSubviews
+{
+  [super layoutSubviews];
+
+  if (_contentView) {
+    _contentView.frame = RCTCGRectFromRect(_layoutMetrics.getContentFrame());
+  }
+}
+
 
 - (void)updateProps:(SharedProps)props
            oldProps:(SharedProps)oldProps
@@ -42,9 +64,10 @@ - (void)updateEventEmitter:(SharedEventEmitter)eventEmitter
 - (void)updateLayoutMetrics:(LayoutMetrics)layoutMetrics
            oldLayoutMetrics:(LayoutMetrics)oldLayoutMetrics
 {
+  _layoutMetrics = layoutMetrics;
+
   [super updateLayoutMetrics:layoutMetrics oldLayoutMetrics:oldLayoutMetrics];
 
-  _layoutMetrics = layoutMetrics;
 }
 
 #pragma mark - Accessibility Events

From f65e4e0174e27170689155b90ccaee0d9fc489b0 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:16 -0700
Subject: [PATCH 0816/1109] Fabric: Implemetation of <Switch> component

Summary:
This is pretty straightforward implementation uses native `UISwitch`.
Suddenly we need Switch to test a bunch of other things.

Reviewed By: fkgozali

Differential Revision: D8344055

fbshipit-source-id: cfc51b8bc11198eb9d4d5e4745b96fb3a7f14de1
---
 .../Switch/RCTSwitchComponentView.h           | 21 +++++
 .../Switch/RCTSwitchComponentView.mm          | 88 +++++++++++++++++++
 ReactCommon/fabric/components/switch/BUCK     | 78 ++++++++++++++++
 .../switch/SwitchComponentDescriptor.h        | 19 ++++
 .../components/switch/SwitchEventEmitter.cpp  | 18 ++++
 .../components/switch/SwitchEventEmitter.h    | 25 ++++++
 .../fabric/components/switch/SwitchProps.cpp  | 23 +++++
 .../fabric/components/switch/SwitchProps.h    | 32 +++++++
 .../components/switch/SwitchShadowNode.cpp    | 18 ++++
 .../components/switch/SwitchShadowNode.h      | 31 +++++++
 .../components/switch/tests/SwitchTest.cpp    | 14 +++
 11 files changed, 367 insertions(+)
 create mode 100644 React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.h
 create mode 100644 React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.mm
 create mode 100644 ReactCommon/fabric/components/switch/BUCK
 create mode 100644 ReactCommon/fabric/components/switch/SwitchComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/components/switch/SwitchEventEmitter.cpp
 create mode 100644 ReactCommon/fabric/components/switch/SwitchEventEmitter.h
 create mode 100644 ReactCommon/fabric/components/switch/SwitchProps.cpp
 create mode 100644 ReactCommon/fabric/components/switch/SwitchProps.h
 create mode 100644 ReactCommon/fabric/components/switch/SwitchShadowNode.cpp
 create mode 100644 ReactCommon/fabric/components/switch/SwitchShadowNode.h
 create mode 100644 ReactCommon/fabric/components/switch/tests/SwitchTest.cpp

diff --git a/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.h b/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.h
new file mode 100644
index 000000000000..470a3e7e0ee2
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.h
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTViewComponentView.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * UIView class for root <Switch> component.
+ */
+@interface RCTSwitchComponentView : RCTViewComponentView
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.mm b/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.mm
new file mode 100644
index 000000000000..ec54418bfd86
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.mm
@@ -0,0 +1,88 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTSwitchComponentView.h"
+
+#import <fabric/components/switch/SwitchEventEmitter.h>
+#import <fabric/components/switch/SwitchProps.h>
+
+using namespace facebook::react;
+
+@implementation RCTSwitchComponentView {
+  UISwitch *_switchView;
+  BOOL _wasOn;
+}
+
+- (instancetype)initWithFrame:(CGRect)frame
+{
+  if (self = [super initWithFrame:frame]) {
+    _switchView = [[UISwitch alloc] initWithFrame:self.bounds];
+
+    [_switchView addTarget:self
+                 action:@selector(onChange:)
+       forControlEvents:UIControlEventValueChanged];
+
+    auto &&defaultProps = SwitchProps();
+
+    _switchView.on = defaultProps.value;
+
+    self.contentView = _switchView;
+  }
+
+  return self;
+}
+
+- (void)updateProps:(SharedProps)props oldProps:(SharedProps)oldProps
+{
+  if (!oldProps) {
+    oldProps = _props ?: std::make_shared<SwitchProps>();
+  }
+  _props = props;
+
+  [super updateProps:props oldProps:oldProps];
+
+  auto oldSwitchProps = *std::dynamic_pointer_cast<const SwitchProps>(oldProps);
+  auto newSwitchProps = *std::dynamic_pointer_cast<const SwitchProps>(props);
+
+  // `value`
+  if (oldSwitchProps.value != newSwitchProps.value) {
+    _switchView.on = newSwitchProps.value;
+    _wasOn = newSwitchProps.value;
+  }
+
+  // `disabled`
+  if (oldSwitchProps.disabled != newSwitchProps.disabled) {
+    _switchView.enabled = !newSwitchProps.disabled;
+  }
+
+  // `tintColor`
+  if (oldSwitchProps.tintColor != newSwitchProps.tintColor) {
+    _switchView.tintColor = [UIColor colorWithCGColor:newSwitchProps.tintColor.get()];
+  }
+
+  // `onTintColor
+  if (oldSwitchProps.onTintColor != newSwitchProps.onTintColor) {
+    _switchView.onTintColor = [UIColor colorWithCGColor:newSwitchProps.onTintColor.get()];
+  }
+
+  // `thumbTintColor`
+  if (oldSwitchProps.thumbTintColor != newSwitchProps.thumbTintColor) {
+    _switchView.thumbTintColor = [UIColor colorWithCGColor:newSwitchProps.thumbTintColor.get()];
+  }
+}
+
+- (void)onChange:(UISwitch *)sender
+{
+  if (_wasOn == sender.on) {
+    return;
+  }
+  _wasOn = sender.on;
+
+  std::dynamic_pointer_cast<const SwitchEventEmitter>(_eventEmitter)->onChange(sender.on);
+}
+
+@end
diff --git a/ReactCommon/fabric/components/switch/BUCK b/ReactCommon/fabric/components/switch/BUCK
new file mode 100644
index 000000000000..8a4a27ff3253
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/BUCK
@@ -0,0 +1,78 @@
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+
+rn_xplat_cxx_library(
+    name = "switch",
+    srcs = glob(
+        ["**/*.cpp"],
+        exclude = glob(["tests/**/*.cpp"]),
+    ),
+    headers = [],
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/components/switch",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+        react_native_xplat_target("fabric/view:view"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":switch",
+        ],
+    )
diff --git a/ReactCommon/fabric/components/switch/SwitchComponentDescriptor.h b/ReactCommon/fabric/components/switch/SwitchComponentDescriptor.h
new file mode 100644
index 000000000000..1ea9e4582c2b
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/SwitchComponentDescriptor.h
@@ -0,0 +1,19 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/components/switch/SwitchShadowNode.h>
+#include <fabric/core/ConcreteComponentDescriptor.h>
+
+namespace facebook {
+namespace react {
+
+using SwitchComponentDescriptor = ConcreteComponentDescriptor<SwitchShadowNode>;
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/switch/SwitchEventEmitter.cpp b/ReactCommon/fabric/components/switch/SwitchEventEmitter.cpp
new file mode 100644
index 000000000000..680f1dbd5e3d
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/SwitchEventEmitter.cpp
@@ -0,0 +1,18 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "SwitchEventEmitter.h"
+
+namespace facebook {
+namespace react {
+
+void SwitchEventEmitter::onChange(const bool &value) const {
+  dispatchEvent("change", folly::dynamic::object("value", value));
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/switch/SwitchEventEmitter.h b/ReactCommon/fabric/components/switch/SwitchEventEmitter.h
new file mode 100644
index 000000000000..2f1cf3733fd6
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/SwitchEventEmitter.h
@@ -0,0 +1,25 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+#pragma once
+
+#include <fabric/view/ViewEventEmitter.h>
+
+namespace facebook {
+namespace react {
+
+class SwitchEventEmitter:
+  public ViewEventEmitter {
+
+public:
+
+  using ViewEventEmitter::ViewEventEmitter;
+
+  void onChange(const bool &value) const;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/switch/SwitchProps.cpp b/ReactCommon/fabric/components/switch/SwitchProps.cpp
new file mode 100644
index 000000000000..9f80943c6fa9
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/SwitchProps.cpp
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/components/switch/SwitchProps.h>
+#include <fabric/core/propsConversions.h>
+
+namespace facebook {
+namespace react {
+
+SwitchProps::SwitchProps(const SwitchProps &sourceProps, const RawProps &rawProps):
+  ViewProps(sourceProps, rawProps),
+  value(convertRawProp(rawProps, "value", sourceProps.value, value)),
+  disabled(convertRawProp(rawProps, "disabled", sourceProps.disabled, disabled)),
+  tintColor(convertRawProp(rawProps, "tintColor", sourceProps.tintColor, tintColor)),
+  onTintColor(convertRawProp(rawProps, "onTintColor", sourceProps.onTintColor, onTintColor)),
+  thumbTintColor(convertRawProp(rawProps, "thumbTintColor", sourceProps.thumbTintColor, thumbTintColor)) {}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/switch/SwitchProps.h b/ReactCommon/fabric/components/switch/SwitchProps.h
new file mode 100644
index 000000000000..6ddac619b4b4
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/SwitchProps.h
@@ -0,0 +1,32 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/graphics/Color.h>
+#include <fabric/view/ViewProps.h>
+
+namespace facebook {
+namespace react {
+
+// TODO (T28334063): Consider for codegen.
+class SwitchProps final:
+  public ViewProps {
+
+public:
+  SwitchProps() = default;
+  SwitchProps(const SwitchProps &sourceProps, const RawProps &rawProps);
+
+#pragma mark - Props
+
+  const bool value {false};
+  const bool disabled {false};
+  const SharedColor tintColor {};
+  const SharedColor onTintColor {};
+  const SharedColor thumbTintColor {};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/switch/SwitchShadowNode.cpp b/ReactCommon/fabric/components/switch/SwitchShadowNode.cpp
new file mode 100644
index 000000000000..87896d0c6915
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/SwitchShadowNode.cpp
@@ -0,0 +1,18 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/components/switch/SwitchShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+ComponentName SwitchShadowNode::getComponentName() const {
+  return ComponentName("Switch");
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/switch/SwitchShadowNode.h b/ReactCommon/fabric/components/switch/SwitchShadowNode.h
new file mode 100644
index 000000000000..b94256c74d2a
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/SwitchShadowNode.h
@@ -0,0 +1,31 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/components/switch/SwitchEventEmitter.h>
+#include <fabric/components/switch/SwitchProps.h>
+#include <fabric/view/ConcreteViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * `ShadowNode` for <Switch> component.
+ */
+class SwitchShadowNode final:
+  public ConcreteViewShadowNode<SwitchProps, SwitchEventEmitter> {
+
+public:
+
+  using ConcreteViewShadowNode::ConcreteViewShadowNode;
+
+  ComponentName getComponentName() const override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/switch/tests/SwitchTest.cpp b/ReactCommon/fabric/components/switch/tests/SwitchTest.cpp
new file mode 100644
index 000000000000..a55a5783d83c
--- /dev/null
+++ b/ReactCommon/fabric/components/switch/tests/SwitchTest.cpp
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+TEST(SwitchTest, testSomething) {
+  // TODO
+}

From da55ef1367c29b606107e4df65addcd974590ff4 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:19 -0700
Subject: [PATCH 0817/1109] Fabric: Definition of the rest <View> props on C++
 side

Summary:
Just definition; we don't have an implementation on the native view layer yet.
And we don't have `transform` prop yet (because it's quite complex).

Reviewed By: fkgozali

Differential Revision: D8344058

fbshipit-source-id: 3b7b41480be8295cbc90b95ebe8562e52c6f81d7
---
 ReactCommon/fabric/view/ViewProps.cpp | 19 +++++++++++++++---
 ReactCommon/fabric/view/ViewProps.h   | 26 ++++++++++++++++++++----
 ReactCommon/fabric/view/conversions.h | 20 ++++++++++++++++++
 ReactCommon/fabric/view/primitives.h  | 29 +++++++++++++++++++++++++++
 4 files changed, 87 insertions(+), 7 deletions(-)
 create mode 100644 ReactCommon/fabric/view/primitives.h

diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index 5f667312c7e9..c6d3ddccef4e 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -10,6 +10,7 @@
 #include <fabric/core/propsConversions.h>
 #include <fabric/debug/debugStringConvertibleUtils.h>
 #include <fabric/graphics/conversions.h>
+#include <fabric/view/conversions.h>
 
 namespace facebook {
 namespace react {
@@ -20,10 +21,22 @@ ViewProps::ViewProps(const YGStyle &yogaStyle):
 ViewProps::ViewProps(const ViewProps &sourceProps, const RawProps &rawProps):
   Props(sourceProps, rawProps),
   YogaStylableProps(sourceProps, rawProps),
-  zIndex(convertRawProp(rawProps, "zIndex", sourceProps.zIndex)),
   opacity(convertRawProp(rawProps, "opacity", sourceProps.opacity)),
-  foregroundColor(convertRawProp(rawProps, "color", sourceProps.foregroundColor)),
-  backgroundColor(convertRawProp(rawProps, "backgroundColor", sourceProps.backgroundColor)) {};
+  foregroundColor(convertRawProp(rawProps, "foregroundColor", sourceProps.foregroundColor)),
+  backgroundColor(convertRawProp(rawProps, "backgroundColor", sourceProps.backgroundColor)),
+  borderWidth(convertRawProp(rawProps, "borderWidth", sourceProps.borderWidth)),
+  borderRadus(convertRawProp(rawProps, "borderRadus", sourceProps.borderRadus)),
+  borderColor(convertRawProp(rawProps, "borderColor", sourceProps.borderColor)),
+  borderStyle(convertRawProp(rawProps, "borderStyle", sourceProps.borderStyle)),
+  shadowColor(convertRawProp(rawProps, "shadowColor", sourceProps.shadowColor)),
+  shadowOffset(convertRawProp(rawProps, "shadowOffset", sourceProps.shadowOffset)),
+  shadowOpacity(convertRawProp(rawProps, "shadowOpacity", sourceProps.shadowOpacity)),
+  shadowRadius(convertRawProp(rawProps, "shadowRadius", sourceProps.shadowRadius)),
+  backfaceVisibility(convertRawProp(rawProps, "backfaceVisibility", sourceProps.backfaceVisibility)),
+  shouldRasterize(convertRawProp(rawProps, "shouldRasterize", sourceProps.shouldRasterize)),
+  zIndex(convertRawProp(rawProps, "zIndex", sourceProps.zIndex)),
+  pointerEvents(convertRawProp(rawProps, "pointerEvents", sourceProps.pointerEvents)),
+  hitSlop(convertRawProp(rawProps, "hitSlop", sourceProps.hitSlop)) {};
 
 #pragma mark - DebugStringConvertible
 
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
index b0fa20369c3c..5f49e039584a 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -10,8 +10,9 @@
 #include <fabric/core/Props.h>
 #include <fabric/graphics/Geometry.h>
 #include <fabric/graphics/Color.h>
-#include <fabric/view/YogaStylableProps.h>
 #include <fabric/view/AccessibilityProps.h>
+#include <fabric/view/primitives.h>
+#include <fabric/view/YogaStylableProps.h>
 
 namespace facebook {
 namespace react {
@@ -33,14 +34,31 @@ class ViewProps:
 
 #pragma mark - Props
 
-  const int zIndex {0};
+  // Color
   const Float opacity {1};
-
   const SharedColor foregroundColor {nullptr};
   const SharedColor backgroundColor {nullptr};
 
+  // Borders
+  const EdgeInsets borderWidth {};
+  const CornerInsets borderRadus {};
+  const SharedColor borderColor {};
+  const BorderStyle borderStyle {};
+
+  // Shadow
   const SharedColor shadowColor {nullptr};
-  const Point shadowOffset {};
+  const Size shadowOffset {};
+  const Float shadowOpacity {};
+  const Float shadowRadius {};
+
+  // Transform
+  const bool backfaceVisibility {false};
+  const bool shouldRasterize {false};
+  const int zIndex {0};
+
+  // Events
+  const PointerEventsMode pointerEvents {};
+  const EdgeInsets hitSlop {};
 
 #pragma mark - DebugStringConvertible
 
diff --git a/ReactCommon/fabric/view/conversions.h b/ReactCommon/fabric/view/conversions.h
index 66cb25da0d15..2a228b510cc0 100644
--- a/ReactCommon/fabric/view/conversions.h
+++ b/ReactCommon/fabric/view/conversions.h
@@ -9,6 +9,7 @@
 
 #include <fabric/core/LayoutMetrics.h>
 #include <fabric/graphics/Geometry.h>
+#include <fabric/view/primitives.h>
 #include <folly/dynamic.h>
 #include <folly/Conv.h>
 #include <yoga/Yoga.h>
@@ -226,6 +227,25 @@ inline void fromDynamic(const folly::dynamic &value, YGFloatOptional &result) {
   abort();
 }
 
+inline void fromDynamic(const folly::dynamic &value, PointerEventsMode &result) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+  if (stringValue == "auto") { result = PointerEventsMode::Auto; return; }
+  if (stringValue == "none") { result = PointerEventsMode::None; return; }
+  if (stringValue == "box-none") { result = PointerEventsMode::BoxNone; return; }
+  if (stringValue == "box-only") { result = PointerEventsMode::BoxOnly; return; }
+  abort();
+}
+
+inline void fromDynamic(const folly::dynamic &value, BorderStyle &result) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+  if (stringValue == "solid") { result = BorderStyle::Solid; return; }
+  if (stringValue == "dotted") { result = BorderStyle::Dotted; return; }
+  if (stringValue == "dashed") { result = BorderStyle::Dashed; return; }
+  abort();
+}
+
 inline std::string toString(const std::array<float, YGDimensionCount> &dimensions) {
   return "{" + folly::to<std::string>(dimensions[0]) + ", " + folly::to<std::string>(dimensions[1]) + "}";
 }
diff --git a/ReactCommon/fabric/view/primitives.h b/ReactCommon/fabric/view/primitives.h
new file mode 100644
index 000000000000..1aced96844b6
--- /dev/null
+++ b/ReactCommon/fabric/view/primitives.h
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <cmath>
+
+namespace facebook {
+namespace react {
+
+enum class PointerEventsMode {
+  Auto,
+  None,
+  BoxNone,
+  BoxOnly
+};
+
+enum class BorderStyle {
+  Solid,
+  Dotted,
+  Dashed
+};
+
+} // namespace react
+} // namespace facebook

From cde30eb6b7cce72ba8caa4d61b493f906dabc378 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:22 -0700
Subject: [PATCH 0818/1109] Fabric: Basic implementation of <View
 nativeId={...}>

Summary:
Trivial.
`nativeId` is meant to be used by subclasses of external inspector-like tools, so it does not have any real functionality.

Reviewed By: fkgozali

Differential Revision: D8344064

fbshipit-source-id: d86ef378cda1f7f0e9a7b4ffc09f51004ae530d2
---
 .../Mounting/ComponentViews/View/RCTViewComponentView.h  | 9 +++++++++
 .../Mounting/ComponentViews/View/RCTViewComponentView.mm | 5 +++++
 2 files changed, 14 insertions(+)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index d45bcce07e20..a9be808e6b64 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -36,6 +36,15 @@ NS_ASSUME_NONNULL_BEGIN
  */
 @property (nonatomic, strong, nullable) UIView *contentView;
 
+/**
+ * Provides access to `nativeId` prop of the component.
+ * It might be used by subclasses (which need to refer to the view from
+ * other platform-specific external views or systems by some id) or
+ * by debugging/inspection tools.
+ * Defaults to `nil`.
+ */
+@property (nonatomic, strong, nullable) NSString *nativeId;
+
 @end
 
 NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index a5f0c67283d2..dd8cb4df3544 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -53,6 +53,11 @@ - (void)updateProps:(SharedProps)props
   }
 
   // TODO: Implement all sutable non-layout <View> props.
+  // `nativeId`
+  if (oldViewProps.nativeId != newViewProps.nativeId) {
+    self.nativeId = [NSString stringWithCString:newViewProps.nativeId.c_str()
+                                       encoding:NSASCIIStringEncoding];
+  }
 }
 
 - (void)updateEventEmitter:(SharedEventEmitter)eventEmitter

From 8bdc1ff10b0298b27cec539d6764c9b8d2c17f30 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:24 -0700
Subject: [PATCH 0819/1109] Fabric: Implementatiton of <View hitSlop={}/> on
 the native side

Summary: The implementation was basically ported from existing one.

Reviewed By: fkgozali

Differential Revision: D8344057

fbshipit-source-id: c0ec3b7b986080eab62532244da73859b445fcbb
---
 .../ComponentViews/View/RCTViewComponentView.h      |  5 +++++
 .../ComponentViews/View/RCTViewComponentView.mm     | 13 +++++++++++++
 2 files changed, 18 insertions(+)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index a9be808e6b64..ac9d7187f925 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -45,6 +45,11 @@ NS_ASSUME_NONNULL_BEGIN
  */
 @property (nonatomic, strong, nullable) NSString *nativeId;
 
+/**
+ * Insets used when hit testing inside this view.
+ */
+@property (nonatomic, assign) UIEdgeInsets hitTestEdgeInsets;
+
 @end
 
 NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index dd8cb4df3544..89b905b77592 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -36,6 +36,14 @@ - (void)layoutSubviews
   }
 }
 
+- (BOOL)pointInside:(CGPoint)point withEvent:(UIEvent *)event
+{
+  if (UIEdgeInsetsEqualToEdgeInsets(self.hitTestEdgeInsets, UIEdgeInsetsZero)) {
+    return [super pointInside:point withEvent:event];
+  }
+  CGRect hitFrame = UIEdgeInsetsInsetRect(self.bounds, self.hitTestEdgeInsets);
+  return CGRectContainsPoint(hitFrame, point);
+}
 
 - (void)updateProps:(SharedProps)props
            oldProps:(SharedProps)oldProps
@@ -53,6 +61,11 @@ - (void)updateProps:(SharedProps)props
   }
 
   // TODO: Implement all sutable non-layout <View> props.
+  // `hitSlop`
+  if (oldViewProps.hitSlop != newViewProps.hitSlop) {
+    self.hitTestEdgeInsets = RCTUIEdgeInsetsFromEdgeInsets(newViewProps.hitSlop);
+  }
+
   // `nativeId`
   if (oldViewProps.nativeId != newViewProps.nativeId) {
     self.nativeId = [NSString stringWithCString:newViewProps.nativeId.c_str()

From 3c8c01791f24a5876de58fbea17f3b147d180239 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:26 -0700
Subject: [PATCH 0820/1109] Fabric: Implementation of bunch of trivial <View>
 props

Summary: Pretty straightforward.

Reviewed By: fkgozali

Differential Revision: D8344063

fbshipit-source-id: e6d35353cb3f3e374d2f2b723a612eda2d19c8b7
---
 .../View/RCTViewComponentView.h               |  6 +++
 .../View/RCTViewComponentView.mm              | 37 ++++++++++++++++++-
 2 files changed, 42 insertions(+), 1 deletion(-)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index ac9d7187f925..507c09056fbd 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -45,6 +45,12 @@ NS_ASSUME_NONNULL_BEGIN
  */
 @property (nonatomic, strong, nullable) NSString *nativeId;
 
+/**
+ * Provides access to `foregroundColor` prop of the component.
+ * Must be used by subclasses only.
+ */
+@property (nonatomic, strong, nullable) UIColor *foregroundColor;
+
 /**
  * Insets used when hit testing inside this view.
  */
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index 89b905b77592..b2c785d86845 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -10,6 +10,7 @@
 #import <fabric/view/ViewProps.h>
 #import <fabric/view/ViewEventEmitter.h>
 
+#import "RCTConversions.h"
 
 using namespace facebook::react;
 
@@ -56,8 +57,37 @@ - (void)updateProps:(SharedProps)props
   auto oldViewProps = *std::dynamic_pointer_cast<const ViewProps>(oldProps);
   auto newViewProps = *std::dynamic_pointer_cast<const ViewProps>(props);
 
+  // `opacity`
+  if (oldViewProps.opacity != newViewProps.opacity) {
+    self.layer.opacity = (CGFloat)newViewProps.opacity;
+  }
+
+  // `backgroundColor`
   if (oldViewProps.backgroundColor != newViewProps.backgroundColor) {
-    self.backgroundColor = [UIColor colorWithCGColor:newViewProps.backgroundColor.get()];
+    self.backgroundColor = RCTUIColorFromSharedColor(newViewProps.backgroundColor);
+  }
+
+  // `foregroundColor`
+  if (oldViewProps.foregroundColor != newViewProps.foregroundColor) {
+    self.foregroundColor = RCTUIColorFromSharedColor(newViewProps.foregroundColor);
+  }
+
+  // `backfaceVisibility`
+  if (oldViewProps.backfaceVisibility != newViewProps.backfaceVisibility) {
+    self.layer.doubleSided = newViewProps.backfaceVisibility;
+  }
+
+  // `shouldRasterize`
+  if (oldViewProps.shouldRasterize != newViewProps.shouldRasterize) {
+    self.layer.shouldRasterize = newViewProps.shouldRasterize;
+    self.layer.rasterizationScale = newViewProps.shouldRasterize ? [UIScreen mainScreen].scale : 1.0;
+  }
+
+  // `pointerEvents`
+  if (oldViewProps.pointerEvents != newViewProps.pointerEvents) {
+    self.userInteractionEnabled = newViewProps.pointerEvents != PointerEventsMode::None;
+  }
+
   }
 
   // TODO: Implement all sutable non-layout <View> props.
@@ -66,6 +96,11 @@ - (void)updateProps:(SharedProps)props
     self.hitTestEdgeInsets = RCTUIEdgeInsetsFromEdgeInsets(newViewProps.hitSlop);
   }
 
+  // `zIndex`
+  if (oldViewProps.zIndex != newViewProps.zIndex) {
+    self.layer.zPosition = (CGFloat)newViewProps.zIndex;
+  }
+
   // `nativeId`
   if (oldViewProps.nativeId != newViewProps.nativeId) {
     self.nativeId = [NSString stringWithCString:newViewProps.nativeId.c_str()

From 8df7d516006041ff703d68ea277795ff758572ff Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:28 -0700
Subject: [PATCH 0821/1109] Fabric: Transform type and <View transform/> prop

Summary: The matrix magic and parsing approach are mixins between current iOS and Android implementation.

Reviewed By: fkgozali

Differential Revision: D8344054

fbshipit-source-id: 524b48c5ab61959ce740373534d0d435eb37b647
---
 ReactCommon/fabric/view/ViewProps.cpp |   1 +
 ReactCommon/fabric/view/ViewProps.h   |   1 +
 ReactCommon/fabric/view/conversions.h |  48 ++++++++++
 ReactCommon/fabric/view/primitives.h  | 131 ++++++++++++++++++++++++++
 4 files changed, 181 insertions(+)

diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index c6d3ddccef4e..5a123f9c99d2 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -32,6 +32,7 @@ ViewProps::ViewProps(const ViewProps &sourceProps, const RawProps &rawProps):
   shadowOffset(convertRawProp(rawProps, "shadowOffset", sourceProps.shadowOffset)),
   shadowOpacity(convertRawProp(rawProps, "shadowOpacity", sourceProps.shadowOpacity)),
   shadowRadius(convertRawProp(rawProps, "shadowRadius", sourceProps.shadowRadius)),
+  transform(convertRawProp(rawProps, "transform", sourceProps.transform)),
   backfaceVisibility(convertRawProp(rawProps, "backfaceVisibility", sourceProps.backfaceVisibility)),
   shouldRasterize(convertRawProp(rawProps, "shouldRasterize", sourceProps.shouldRasterize)),
   zIndex(convertRawProp(rawProps, "zIndex", sourceProps.zIndex)),
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
index 5f49e039584a..472966e6e700 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -52,6 +52,7 @@ class ViewProps:
   const Float shadowRadius {};
 
   // Transform
+  const Transform transform {};
   const bool backfaceVisibility {false};
   const bool shouldRasterize {false};
   const int zIndex {0};
diff --git a/ReactCommon/fabric/view/conversions.h b/ReactCommon/fabric/view/conversions.h
index 2a228b510cc0..10dc24de7767 100644
--- a/ReactCommon/fabric/view/conversions.h
+++ b/ReactCommon/fabric/view/conversions.h
@@ -227,6 +227,54 @@ inline void fromDynamic(const folly::dynamic &value, YGFloatOptional &result) {
   abort();
 }
 
+inline void fromDynamic(const folly::dynamic &value, Transform &result) {
+  assert(value.isArray());
+  Transform transformMatrix;
+  for (auto &&tranformConfiguration : value) {
+    assert(tranformConfiguration.isObject());
+    auto pair = *tranformConfiguration.items().begin();
+    auto &&operation = pair.first.asString();
+    auto &&parameters = pair.second;
+
+    if (operation == "matrix") {
+      assert(parameters.isArray());
+      assert(parameters.size() == transformMatrix.matrix.size());
+      int i = 0;
+      for (auto item : parameters) {
+        transformMatrix.matrix[i++] = (Float)item.asDouble();
+      }
+    } else if (operation == "perspective") {
+      transformMatrix = transformMatrix * Transform::Perspective((Float)parameters.asDouble());
+    } else if (operation == "rotateX") {
+      transformMatrix = transformMatrix * Transform::Rotate((Float)parameters.asDouble(), 0, 0);
+    } else if (operation == "rotateY") {
+      transformMatrix = transformMatrix * Transform::Rotate(0, (Float)parameters.asDouble(), 0);
+    } else if (operation == "rotateZ") {
+      transformMatrix = transformMatrix * Transform::Rotate(0, 0, (Float)parameters.asDouble());
+    } else if (operation == "scale") {
+      transformMatrix = transformMatrix * Transform::Scale((Float)parameters.asDouble(), (Float)parameters.asDouble(), (Float)parameters.asDouble());
+    } else if (operation == "scaleX") {
+      transformMatrix = transformMatrix * Transform::Scale((Float)parameters.asDouble(), 0, 0);
+    } else if (operation == "scaleY") {
+      transformMatrix = transformMatrix * Transform::Scale(0, (Float)parameters.asDouble(), 0);
+    } else if (operation == "scaleZ") {
+      transformMatrix = transformMatrix * Transform::Scale(0, 0, (Float)parameters.asDouble());
+    } else if (operation == "translate") {
+      transformMatrix = transformMatrix * Transform::Translate(parameters[0].asDouble(), parameters[1].asDouble(), 0);
+    } else if (operation == "translateX") {
+      transformMatrix = transformMatrix * Transform::Translate(parameters[0].asDouble(), 0, 0);
+    } else if (operation == "translateY") {
+      transformMatrix = transformMatrix * Transform::Translate(0, parameters[0].asDouble(), 0);
+    } else if (operation == "skewX") {
+      transformMatrix = transformMatrix * Transform::Skew(parameters.asDouble(), 0);
+    } else if (operation == "skewY") {
+      transformMatrix = transformMatrix * Transform::Skew(0, parameters.asDouble());
+    }
+  }
+
+  result = transformMatrix;
+}
+
 inline void fromDynamic(const folly::dynamic &value, PointerEventsMode &result) {
   assert(value.isString());
   auto stringValue = value.asString();
diff --git a/ReactCommon/fabric/view/primitives.h b/ReactCommon/fabric/view/primitives.h
index 1aced96844b6..3e57f4bf8592 100644
--- a/ReactCommon/fabric/view/primitives.h
+++ b/ReactCommon/fabric/view/primitives.h
@@ -12,6 +12,137 @@
 namespace facebook {
 namespace react {
 
+struct Transform {
+  std::array<Float, 16> matrix {{
+    0, 0, 0, 0,
+    0, 1, 0, 0,
+    0, 0, 1, 0,
+    0, 0, 0, 1
+  }};
+
+  static Transform Identity() {
+    Transform transform;
+    return transform;
+  }
+
+  static Transform Perspective(const Float &perspective) {
+    Transform transform;
+    transform.matrix[11] = -1.0 / perspective;
+    return transform;
+  }
+
+  static Transform Scale(const Float &factorX, const Float &factorY, const Float &factorZ) {
+    Transform transform;
+    transform.matrix[0] = factorX;
+    transform.matrix[5] = factorY;
+    transform.matrix[10] = factorZ;
+    return transform;
+  }
+
+  static Transform Translate(const Float &x, const Float &y, const Float &z) {
+    Transform transform;
+    transform.matrix[12] = x;
+    transform.matrix[13] = y;
+    transform.matrix[14] = z;
+    return transform;
+  }
+
+  static Transform Skew(const Float &x, const Float &y) {
+    Transform transform;
+    transform.matrix[4] = std::tan(x);
+    transform.matrix[1] = std::tan(y);
+    return transform;
+  }
+
+  static Transform RotateX(const Float &radians) {
+    Transform transform;
+    transform.matrix[5] = std::cos(radians);
+    transform.matrix[6] = std::sin(radians);
+    transform.matrix[9] = -std::sin(radians);
+    transform.matrix[10] = std::cos(radians);
+    return transform;
+  }
+
+  static Transform RotateY(const Float &radians) {
+    Transform transform;
+    transform.matrix[0] = std::cos(radians);
+    transform.matrix[2] = -std::sin(radians);
+    transform.matrix[8] = std::sin(radians);
+    transform.matrix[10] = std::cos(radians);
+    return transform;
+  }
+
+  static Transform RotateZ(const Float &radians) {
+    Transform transform;
+    transform.matrix[0] = std::cos(radians);
+    transform.matrix[1] = std::sin(radians);
+    transform.matrix[4] = -std::sin(radians);
+    transform.matrix[5] = std::cos(radians);
+    return transform;
+  }
+
+  static Transform Rotate(const Float &x, const Float &y, const Float &z) {
+    Transform transform;
+    if (x != 0) { transform = transform * Transform::RotateX(x); }
+    if (y != 0) { transform = transform * Transform::RotateY(y); }
+    if (z != 0) { transform = transform * Transform::RotateZ(z); }
+    return transform;
+  }
+
+  bool operator ==(const Transform& rhs) const {
+    for (int i = 0; i < 16; i++) {
+      if (matrix[i] != rhs.matrix[i]) {
+        return false;
+      }
+    }
+    return true;
+  }
+
+  bool operator !=(const Transform& rhs) const {
+    return !(*this == rhs);
+  }
+
+  Transform operator *(const Transform& rhs) const {
+    if (*this == Transform::Identity()) {
+      return rhs;
+    }
+
+    const Transform &lhs = *this;
+    Transform result;
+
+    Float lhs00 = lhs.matrix[0], lhs01 = lhs.matrix[1], lhs02 = lhs.matrix[2], lhs03 = lhs.matrix[3],
+    lhs10 = lhs.matrix[4], lhs11 = lhs.matrix[5], lhs12 = lhs.matrix[6], lhs13 = lhs.matrix[7],
+    lhs20 = lhs.matrix[8], lhs21 = lhs.matrix[9], lhs22 = lhs.matrix[10], lhs23 = lhs.matrix[11],
+    lhs30 = lhs.matrix[12], lhs31 = lhs.matrix[13], lhs32 = lhs.matrix[14], lhs33 = lhs.matrix[15];
+
+    Float rhs0 = rhs.matrix[0], rhs1 = rhs.matrix[1], rhs2 = rhs.matrix[2], rhs3 = rhs.matrix[3];
+    result.matrix[0] = rhs0 * lhs00 + rhs1 * lhs10 + rhs2 * lhs20 + rhs3 * lhs30;
+    result.matrix[1] = rhs0 * lhs01 + rhs1 * lhs11 + rhs2 * lhs21 + rhs3 * lhs31;
+    result.matrix[2] = rhs0 * lhs02 + rhs1 * lhs12 + rhs2 * lhs22 + rhs3 * lhs32;
+    result.matrix[3] = rhs0 * lhs03 + rhs1 * lhs13 + rhs2 * lhs23 + rhs3 * lhs33;
+
+    rhs0 = rhs.matrix[4]; rhs1 = rhs.matrix[5]; rhs2 = rhs.matrix[6]; rhs3 = rhs.matrix[7];
+    result.matrix[4] = rhs0 * lhs00 + rhs1 * lhs10 + rhs2 * lhs20 + rhs3 * lhs30;
+    result.matrix[5] = rhs0 * lhs01 + rhs1 * lhs11 + rhs2 * lhs21 + rhs3 * lhs31;
+    result.matrix[6] = rhs0 * lhs02 + rhs1 * lhs12 + rhs2 * lhs22 + rhs3 * lhs32;
+    result.matrix[7] = rhs0 * lhs03 + rhs1 * lhs13 + rhs2 * lhs23 + rhs3 * lhs33;
+
+    rhs0 = rhs.matrix[8]; rhs1 = rhs.matrix[9]; rhs2 = rhs.matrix[10]; rhs3 = rhs.matrix[11];
+    result.matrix[8] = rhs0 * lhs00 + rhs1 * lhs10 + rhs2 * lhs20 + rhs3 * lhs30;
+    result.matrix[9] = rhs0 * lhs01 + rhs1 * lhs11 + rhs2 * lhs21 + rhs3 * lhs31;
+    result.matrix[10] = rhs0 * lhs02 + rhs1 * lhs12 + rhs2 * lhs22 + rhs3 * lhs32;
+    result.matrix[11] = rhs0 * lhs03 + rhs1 * lhs13 + rhs2 * lhs23 + rhs3 * lhs33;
+
+    rhs0 = rhs.matrix[12]; rhs1 = rhs.matrix[13]; rhs2 = rhs.matrix[14]; rhs3 = rhs.matrix[15];
+    result.matrix[12] = rhs0 * lhs00 + rhs1 * lhs10 + rhs2 * lhs20 + rhs3 * lhs30;
+    result.matrix[13] = rhs0 * lhs01 + rhs1 * lhs11 + rhs2 * lhs21 + rhs3 * lhs31;
+    result.matrix[14] = rhs0 * lhs02 + rhs1 * lhs12 + rhs2 * lhs22 + rhs3 * lhs32;
+    result.matrix[15] = rhs0 * lhs03 + rhs1 * lhs13 + rhs2 * lhs23 + rhs3 * lhs33;
+
+    return result;
+  }
+};
+
 enum class PointerEventsMode {
   Auto,
   None,

From 5bb538ab5c21a872c49181d3c450fa2165de2726 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:30 -0700
Subject: [PATCH 0822/1109] Fabric: Color conversions function in
 RCTConversions

Summary:
This is quite interesting.
In Fabric, on C++ layer we store `color` values as `SharedColor` objects which (on iOS) are `shared_ptr`s with custom deallocater (which calls CoreFramework's `CFRelease` function). All this means that we cannot directly transfer ovenership of this managed pointer to ARC (honestly, I am not 100% sure about that, but at least this "shared ownershipt between ARC and non-ARC worlds" concept is as dangerous as any "relying on implementation details" approach). To to so, we have to create a copy and transfer ownership of the copy to ARC (which we do in 1RCTCGColorRefFromSharedColor`).

Reviewed By: fkgozali

Differential Revision: D8344061

fbshipit-source-id: 8b6764e1539b1982b41f502bbd3307c7b6900fd9
---
 React/Fabric/RCTConversions.h | 10 ++++++++++
 1 file changed, 10 insertions(+)

diff --git a/React/Fabric/RCTConversions.h b/React/Fabric/RCTConversions.h
index ba2b9cb1ffab..49ba410843a8 100644
--- a/React/Fabric/RCTConversions.h
+++ b/React/Fabric/RCTConversions.h
@@ -7,7 +7,17 @@
 
 #import <UIKit/UIKit.h>
 
+#import <fabric/graphics/Color.h>
 #import <fabric/graphics/Geometry.h>
+#import <fabric/view/primitives.h>
+
+inline UIColor *_Nullable RCTUIColorFromSharedColor(const facebook::react::SharedColor &sharedColor) {
+  return sharedColor ? [UIColor colorWithCGColor:sharedColor.get()] : nil;
+}
+
+inline CGColorRef RCTCGColorRefFromSharedColor(const facebook::react::SharedColor &sharedColor) {
+  return sharedColor ? CGColorCreateCopy(sharedColor.get()) : nil;
+}
 
 inline CGPoint RCTCGPointFromPoint(facebook::react::Point point) {
   return {point.x, point.y};

From 55f8cfe693faa26fb298c213c8b249d308dfd646 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:32 -0700
Subject: [PATCH 0823/1109] Fabric: Implementation of shadow related props of
 <View> component

Summary: Quite trivial.

Reviewed By: fkgozali

Differential Revision: D8344060

fbshipit-source-id: 1e44a2ad78e98699dd0ae7ca2816f8c8349bf6d6
---
 .../View/RCTViewComponentView.mm              | 22 +++++++++++++++++++
 1 file changed, 22 insertions(+)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index b2c785d86845..5fb8f11dfcc4 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -72,6 +72,28 @@ - (void)updateProps:(SharedProps)props
     self.foregroundColor = RCTUIColorFromSharedColor(newViewProps.foregroundColor);
   }
 
+  // `shadowColor`
+  if (oldViewProps.shadowColor != newViewProps.shadowColor) {
+    CGColorRef shadowColor = RCTCGColorRefFromSharedColor(newViewProps.shadowColor);
+    self.layer.shadowColor = shadowColor;
+    CGColorRelease(shadowColor);
+  }
+
+  // `shadowOffset`
+  if (oldViewProps.shadowOffset != newViewProps.shadowOffset) {
+    self.layer.shadowOffset = RCTCGSizeFromSize(newViewProps.shadowOffset);
+  }
+
+  // `shadowOpacity`
+  if (oldViewProps.shadowOpacity != newViewProps.shadowOpacity) {
+    self.layer.shadowOpacity = (CGFloat)newViewProps.shadowOpacity;
+  }
+
+  // `shadowRadius`
+  if (oldViewProps.shadowRadius != newViewProps.shadowRadius) {
+    self.layer.shadowRadius = (CGFloat)newViewProps.shadowRadius;
+  }
+
   // `backfaceVisibility`
   if (oldViewProps.backfaceVisibility != newViewProps.backfaceVisibility) {
     self.layer.doubleSided = newViewProps.backfaceVisibility;

From dc0ebf7cb05dc808f12e160124b9c434dabb91bc Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 15 Jun 2018 11:25:34 -0700
Subject: [PATCH 0824/1109] Fabric: Implementation of <View transform={...}/>
 property

Summary: After moving all matrix math to C++, the actual client native code is quite trivial.

Reviewed By: fkgozali

Differential Revision: D8344059

fbshipit-source-id: 6910c6af5de64d5f901e82075d30edbde177af40
---
 .../View/RCTViewComponentView.mm              |  4 ++++
 React/Fabric/RCTConversions.h                 | 22 +++++++++++++++++++
 2 files changed, 26 insertions(+)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index 5fb8f11dfcc4..763f7a3d81bb 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -110,6 +110,10 @@ - (void)updateProps:(SharedProps)props
     self.userInteractionEnabled = newViewProps.pointerEvents != PointerEventsMode::None;
   }
 
+  // `transform`
+  if (oldViewProps.transform != newViewProps.transform) {
+    self.layer.transform = RCTCATransform3DFromTransformMatrix(newViewProps.transform);
+    self.layer.allowsEdgeAntialiasing = newViewProps.transform != Transform::Identity();
   }
 
   // TODO: Implement all sutable non-layout <View> props.
diff --git a/React/Fabric/RCTConversions.h b/React/Fabric/RCTConversions.h
index 49ba410843a8..2fe12e105076 100644
--- a/React/Fabric/RCTConversions.h
+++ b/React/Fabric/RCTConversions.h
@@ -35,6 +35,28 @@ inline UIEdgeInsets RCTUIEdgeInsetsFromEdgeInsets(facebook::react::EdgeInsets ed
   return {edgeInsets.top, edgeInsets.left, edgeInsets.bottom, edgeInsets.right};
 }
 
+
+inline CATransform3D RCTCATransform3DFromTransformMatrix(facebook::react::Transform transformMatrix) {
+  return {
+    (CGFloat)transformMatrix.matrix[0],
+    (CGFloat)transformMatrix.matrix[1],
+    (CGFloat)transformMatrix.matrix[2],
+    (CGFloat)transformMatrix.matrix[3],
+    (CGFloat)transformMatrix.matrix[4],
+    (CGFloat)transformMatrix.matrix[5],
+    (CGFloat)transformMatrix.matrix[6],
+    (CGFloat)transformMatrix.matrix[7],
+    (CGFloat)transformMatrix.matrix[8],
+    (CGFloat)transformMatrix.matrix[9],
+    (CGFloat)transformMatrix.matrix[10],
+    (CGFloat)transformMatrix.matrix[11],
+    (CGFloat)transformMatrix.matrix[12],
+    (CGFloat)transformMatrix.matrix[13],
+    (CGFloat)transformMatrix.matrix[14],
+    (CGFloat)transformMatrix.matrix[15]
+  };
+}
+
 inline facebook::react::Point RCTPointFromCGPoint(CGPoint point) {
   return {point.x, point.y};
 }

From 3f29d2c4403f272264b829b5ecb2d8b49177b01e Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Fri, 15 Jun 2018 11:34:19 -0700
Subject: [PATCH 0825/1109] Skip metro bump commits (#19680)

Summary:
New metro releases are published to npm when a "Bump metro" commit is synced to GitHub and picked up by facebook/metro's Circle CI.
The same commit is picked up by facebook/react-native's Circle CI, but it will fail the checkout job because yarn will not find the new package on npm.
This is expected because the package will only be published to npm after Circle CI is done running on facebook/metro.

We can safely skip `yarn install` on these commits, and rely on the restored yarn cache instead.
Closes https://github.com/facebook/react-native/pull/19680

Differential Revision: D8450638

Pulled By: hramos

fbshipit-source-id: 436c229d09bfb4f9f92236c5aeec4a60d8317922
---
 .circleci/config.yml | 11 +++++++++--
 1 file changed, 9 insertions(+), 2 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 663c678228ca..1985e9c89de4 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -122,8 +122,13 @@ aliases:
     command: source scripts/android-setup.sh && getAndroidNDK
 
   - &yarn
-    |
-      yarn install --non-interactive --cache-folder ~/.cache/yarn
+    name: Run Yarn
+    command: |
+      # Skip yarn install on metro bump commits as the package is not yet
+      # available on npm
+      if [[ $(echo "$GIT_COMMIT_DESC" | grep -c "Bump metro@") -eq 0 ]]; then
+        yarn install --non-interactive --cache-folder ~/.cache/yarn
+      fi
 
   - &install-yarn
     name: Install Yarn
@@ -304,6 +309,8 @@ aliases:
 
 defaults: &defaults
   working_directory: ~/react-native
+  environment:
+    - GIT_COMMIT_DESC: git log --format=oneline -n 1 $CIRCLE_SHA1
 
 js_defaults: &js_defaults
   <<: *defaults

From 0a530f5d16bc8c97c49c22c152c0ad1eff1a1196 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Fri, 15 Jun 2018 12:23:30 -0700
Subject: [PATCH 0826/1109] iOS: fix up nullability annotation for
 UIAppDelegate method signature

Reviewed By: TheSavior

Differential Revision: D8454576

fbshipit-source-id: 879b695b1b014a92453bf85f23cc1a0e64f015a3
---
 Libraries/LinkingIOS/RCTLinkingManager.h | 2 +-
 Libraries/LinkingIOS/RCTLinkingManager.m | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/LinkingIOS/RCTLinkingManager.h b/Libraries/LinkingIOS/RCTLinkingManager.h
index 55187727ac95..16d7e8f5986a 100644
--- a/Libraries/LinkingIOS/RCTLinkingManager.h
+++ b/Libraries/LinkingIOS/RCTLinkingManager.h
@@ -22,6 +22,6 @@
 
 + (BOOL)application:(UIApplication *)application
 continueUserActivity:(NSUserActivity *)userActivity
-  restorationHandler:(void (^)(NSArray *))restorationHandler;
+  restorationHandler:(void (^)(NSArray * __nullable))restorationHandler;
 
 @end
diff --git a/Libraries/LinkingIOS/RCTLinkingManager.m b/Libraries/LinkingIOS/RCTLinkingManager.m
index 50982fa976d6..4aa6df0882e3 100644
--- a/Libraries/LinkingIOS/RCTLinkingManager.m
+++ b/Libraries/LinkingIOS/RCTLinkingManager.m
@@ -67,7 +67,7 @@ + (BOOL)application:(UIApplication *)application
 
 + (BOOL)application:(UIApplication *)application
 continueUserActivity:(NSUserActivity *)userActivity
-  restorationHandler:(void (^)(NSArray *))restorationHandler
+  restorationHandler:(void (^)(NSArray * __nullable))restorationHandler
 {
   if ([userActivity.activityType isEqualToString:NSUserActivityTypeBrowsingWeb]) {
     NSDictionary *payload = @{@"url": userActivity.webpageURL.absoluteString};

From 77a02c0d83dbfcd9a5397cf63e1ab2e6c94cfdde Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Fri, 15 Jun 2018 12:59:38 -0700
Subject: [PATCH 0827/1109] deprecate ReactFragmentActivity (#19741)

Summary:
Android Support Library page says https://developer.android.com/topic/libraries/support-library/
> Caution: Starting with Support Library release 26.0.0 (July 2017), the minimum supported API level across most support libraries has increased to Android 4.0 (API level 14) for most library packages. For more information, see Version Support and Package Names in this document.

_android.support.v4.app.FragmentActivity_ is used to support **Fragment**s on Android API versions below 11. Now, we support only API version 14 and above, it's ok to remove _ReactFragmentActivity_ that extends _FragmentActivity_.

Once ReactFragmentActivity removed, we can remove some codes that use _android.support.v4_ to work support _ReactFragmentActivity_ on **unsupported** Android versions.

CI is failing for unknown reasons: https://circleci.com/gh/dulmandakh/react-native/278
> Received 'killed' signal

Everything will build and work just fine, except showing _ ReactFragmentActivity_ as deprecated
Closes https://github.com/facebook/react-native/pull/19741

Differential Revision: D8454968

Pulled By: hramos

fbshipit-source-id: e5f901438ef764163af013fe854904a28c73070a
---
 .../main/java/com/facebook/react/ReactFragmentActivity.java | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactFragmentActivity.java b/ReactAndroid/src/main/java/com/facebook/react/ReactFragmentActivity.java
index 10bbd9d89639..b104b91e4ef5 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactFragmentActivity.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactFragmentActivity.java
@@ -19,9 +19,11 @@
 import com.facebook.react.modules.core.PermissionListener;
 
 /**
- * Base Activity for React Native applications. Like {@link ReactActivity} but extends
- * {@link FragmentActivity} instead of {@link android.app.Activity}.
+ * @deprecated
+ * ReactFragmentActivity will be removed in 0.57 release.
+ * Use {@link ReactActivity} instead.
  */
+@Deprecated
 public abstract class ReactFragmentActivity extends FragmentActivity implements
   DefaultHardwareBackBtnHandler, PermissionAwareActivity {
 

From 18e9ea211296d2ce553d3fb37411f18e31d00181 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Fri, 15 Jun 2018 14:26:20 -0700
Subject: [PATCH 0828/1109] Suppress lint errors in Dialog module. remove
 abortOnError=false (#19740)

Summary:
Suppress lint errors in Dialog module. remove abortOnError=false.

This might hide future problems, so removing it
``` gradle
lintOptions {
  abortOnError false
}
```

Builds locally just fine. But CI is failing for unknown reasons. https://circleci.com/gh/dulmandakh/react-native/265

RNTester will built without errors
Closes https://github.com/facebook/react-native/pull/19740

Differential Revision: D8450600

Pulled By: hramos

fbshipit-source-id: faf508a0c546af18a05ee224628f88b02a38ab9f
---
 RNTester/android/app/build.gradle                         | 4 ----
 .../com/facebook/react/modules/dialog/AlertFragment.java  | 2 ++
 .../react/modules/dialog/SupportAlertFragment.java        | 2 ++
 build.gradle                                              | 8 --------
 4 files changed, 4 insertions(+), 12 deletions(-)

diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index 2a2e3834c95b..fdaa2753034b 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -121,10 +121,6 @@ android {
         }
     }
 
-    lintOptions {
-        abortOnError false
-    }
-
     // applicationVariants are e.g. debug, release
     applicationVariants.all { variant ->
         variant.outputs.each { output ->
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/AlertFragment.java b/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/AlertFragment.java
index a233b9130fc0..ecb0229e32b1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/AlertFragment.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/AlertFragment.java
@@ -9,6 +9,7 @@
 
 import javax.annotation.Nullable;
 
+import android.annotation.SuppressLint;
 import android.app.AlertDialog;
 import android.app.Dialog;
 import android.app.DialogFragment;
@@ -34,6 +35,7 @@ public AlertFragment() {
       mListener = null;
   }
 
+  @SuppressLint("ValidFragment")
   public AlertFragment(@Nullable DialogModule.AlertFragmentListener listener, Bundle arguments) {
     mListener = listener;
     setArguments(arguments);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/SupportAlertFragment.java b/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/SupportAlertFragment.java
index dea3c71a6f60..0b360683d4dc 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/SupportAlertFragment.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/modules/dialog/SupportAlertFragment.java
@@ -9,6 +9,7 @@
 
 import javax.annotation.Nullable;
 
+import android.annotation.SuppressLint;
 import android.app.Dialog;
 import android.content.DialogInterface;
 import android.os.Bundle;
@@ -27,6 +28,7 @@ public SupportAlertFragment() {
       mListener = null;
   }
 
+  @SuppressLint("ValidFragment")
   public SupportAlertFragment(@Nullable DialogModule.AlertFragmentListener listener, Bundle arguments) {
     mListener = listener;
     setArguments(arguments);
diff --git a/build.gradle b/build.gradle
index c9c43736f86c..71634a0cbefc 100644
--- a/build.gradle
+++ b/build.gradle
@@ -35,12 +35,4 @@ allprojects {
             url "$androidSdk/extras/m2repository/"
         }
     }
-
-    project.configurations.all {
-        resolutionStrategy.eachDependency { details ->
-            if (details.requested.group == 'com.facebook.soloader') {
-                details.useVersion "0.3.0"
-            }
-        }
-    }
 }

From 52f431b4bb29062abd8ce20e01a4e60b47151a80 Mon Sep 17 00:00:00 2001
From: Kirill Nikolaev <cyriln@google.com>
Date: Fri, 15 Jun 2018 17:00:53 -0700
Subject: [PATCH 0829/1109] Eliminate circular dependency between MessageQueue
 and JSTimers modules. (#19526)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
This makes JSTimers actively register a callback for callImmediates.

Besides being generally tricky, circular dependency prevent compiling React Native code with bundlers that rely on concatenating module sources rather that evaluating code at the time of requiring, like Google Closure Compiler.

Sadly, Google Closure Compiler setup that prompted this change is complicated and brittle. And there are no good public tools to find circular dependencies among Haste-style modules (with unqualified require paths).

So some advice on a good test plan would be useful. Does Facebook have any tools to find circular dependencies with Haste-style requires?

FWIW, a check that worked for me was to replace all import paths in React Native from Haste style to normal relative paths (which I needed anyway) and then run [`madge`](https://www.npmjs.com/package/madge) on the code base:

```
$ ~/node_modules/.bin/madge --circular react-native/Libraries
Processed 390 files (7.4s) (81 warnings)

✖ Found 2 circular dependencies!

1) BatchedBridge/NativeModules.js > BatchedBridge/BatchedBridge.js > BatchedBridge/MessageQueue.js > Core/Timers/JSTimers.js
2) StyleSheet/flattenStyle.js > StyleSheet/StyleSheet.js
```

(The second cycle is already eliminated in https://github.com/facebook/react-native/commit/a8e3c7f5780516eb0297830632862484ad032c10).

[GENERAL] [MINOR] [MessageQueue] - MessageQueue implementation doesn't have a circular dependency on JSTimers.
Closes https://github.com/facebook/react-native/pull/19526

Reviewed By: hramos

Differential Revision: D8458755

Pulled By: yungsters

fbshipit-source-id: e753139b920ba1ad1a6db10f974c03ca195340c7
---
 Libraries/BatchedBridge/MessageQueue.js | 17 +++++++++++------
 Libraries/Core/Timers/JSTimers.js       |  5 +++++
 2 files changed, 16 insertions(+), 6 deletions(-)

diff --git a/Libraries/BatchedBridge/MessageQueue.js b/Libraries/BatchedBridge/MessageQueue.js
index 7cdc5fe1805d..c9b750df9efd 100644
--- a/Libraries/BatchedBridge/MessageQueue.js
+++ b/Libraries/BatchedBridge/MessageQueue.js
@@ -37,9 +37,6 @@ const TRACE_TAG_REACT_APPS = 1 << 17;
 
 const DEBUG_INFO_LIMIT = 32;
 
-// Work around an initialization order issue
-let JSTimers = null;
-
 class MessageQueue {
   _lazyCallableModules: {[key: string]: (void) => Object};
   _queue: [number[], number[], any[], number];
@@ -48,6 +45,7 @@ class MessageQueue {
   _callID: number;
   _lastFlush: number;
   _eventLoopStartTime: number;
+  _immediatesCallback: ?() => void;
 
   _debugInfo: {[number]: [number, number]};
   _remoteModuleTable: {[number]: string};
@@ -63,6 +61,7 @@ class MessageQueue {
     this._callID = 0;
     this._lastFlush = 0;
     this._eventLoopStartTime = new Date().getTime();
+    this._immediatesCallback = null;
 
     if (__DEV__) {
       this._debugInfo = {};
@@ -279,6 +278,13 @@ class MessageQueue {
     }
   }
 
+  // For JSTimers to register its callback. Otherwise a circular dependency
+  // between modules is introduced. Note that only one callback may be
+  // registered at a time.
+  setImmediatesCallback(fn: () => void) {
+    this._immediatesCallback = fn;
+  }
+
   /**
    * Private methods
    */
@@ -310,10 +316,9 @@ class MessageQueue {
 
   __callImmediates() {
     Systrace.beginEvent('JSTimers.callImmediates()');
-    if (!JSTimers) {
-      JSTimers = require('JSTimers');
+    if (this._immediatesCallback != null) {
+      this._immediatesCallback();
     }
-    JSTimers.callImmediates();
     Systrace.endEvent();
   }
 
diff --git a/Libraries/Core/Timers/JSTimers.js b/Libraries/Core/Timers/JSTimers.js
index dbd23f807f81..7cffb4e3d06d 100644
--- a/Libraries/Core/Timers/JSTimers.js
+++ b/Libraries/Core/Timers/JSTimers.js
@@ -14,6 +14,7 @@ const Systrace = require('Systrace');
 
 const invariant = require('fbjs/lib/invariant');
 const {Timing} = require('NativeModules');
+const BatchedBridge = require('BatchedBridge');
 
 import type {ExtendedError} from 'parseErrorStack';
 
@@ -494,4 +495,8 @@ if (!Timing) {
   ExportedJSTimers = JSTimers;
 }
 
+BatchedBridge.setImmediatesCallback(
+  ExportedJSTimers.callImmediates.bind(ExportedJSTimers),
+);
+
 module.exports = ExportedJSTimers;

From 23f959aab8b1becb85767567583d45b87e0ec153 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Sat, 16 Jun 2018 00:38:39 -0700
Subject: [PATCH 0830/1109] FBJS: Upgrade to 0.8.17

Reviewed By: hramos

Differential Revision: D8458729

fbshipit-source-id: 1e92098b2651751f1b7ba3c8da1316fe4c0ca808
---
 Libraries/Animated/release/package.json | 2 +-
 package.json                            | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/Animated/release/package.json b/Libraries/Animated/release/package.json
index 74f457a4dcd3..49f6a2081ffd 100644
--- a/Libraries/Animated/release/package.json
+++ b/Libraries/Animated/release/package.json
@@ -10,7 +10,7 @@
   "license": "MIT",
   "main": "Animated.js",
   "dependencies": {
-    "fbjs": "^0.2.1"
+    "fbjs": "0.8.17"
   },
   "scripts": {
     "build": "gulp"
diff --git a/package.json b/package.json
index b76351695c7d..f6d00306385f 100644
--- a/package.json
+++ b/package.json
@@ -160,7 +160,7 @@
     "errorhandler": "^1.5.0",
     "escape-string-regexp": "^1.0.5",
     "event-target-shim": "^1.0.5",
-    "fbjs": "0.8.16",
+    "fbjs": "0.8.17",
     "fbjs-scripts": "^0.8.1",
     "fs-extra": "^1.0.0",
     "glob": "^7.1.1",

From c749d951ada829c6f6fb76f35e68142e61054433 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Sat, 16 Jun 2018 00:38:41 -0700
Subject: [PATCH 0831/1109] React sync for revisions c0fe8d6...ae14317
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
This sync includes the following changes:
- **[ae14317d6](https://github.com/facebook/react/commit/ae14317d6)**: Inline fbjs/lib/emptyFunction (#13054) //<Dan Abramov>//
- **[72434a768](https://github.com/facebook/react/commit/72434a768)**: Remove or inline some fbjs dependencies (#13046) //<Dan Abramov>//
- **[64c54edea](https://github.com/facebook/react/commit/64c54edea)**: Adding movementX and movementY to synthenticMouseEvent fixes #6723 (#9018) //<Jason Williams>//
- **[9bd4d1fae](https://github.com/facebook/react/commit/9bd4d1fae)**: Synchronously restart when an error is thrown during async rendering (#13041) //<Andrew Clark>//
- **[9bda7b28f](https://github.com/facebook/react/commit/9bda7b28f)**: Suspended high pri work forces lower priority work to expire early  (#12965) //<Andrew Clark>//
- **[2e7577907](https://github.com/facebook/react/commit/2e7577907)**: Fix incorrect data in compositionend event with Korean IME on IE11 (#10217) (#12563) //<Crux>//
- **[bc963f353](https://github.com/facebook/react/commit/bc963f353)**: setJSResponder in Fabric renderer (#13031) //<Sebastian Markbåge>//
- **[051637da6](https://github.com/facebook/react/commit/051637da6)**: Extract Fabric event handlers from canonical props (#13024) //<Sebastian Markbåge>//
- **[2a8085980](https://github.com/facebook/react/commit/2a8085980)**: Remove rAF fork (#12980) //<Flarnie Marchan>//
- **[e0c78344e](https://github.com/facebook/react/commit/e0c78344e)**: Retry on error if there's lower priority pending work (#12957) //<Andrew Clark>//
- **[9725065eb](https://github.com/facebook/react/commit/9725065eb)**: Update bundle sizes for 16.4.1 release //<Dan Abramov>//
- **[0b87b2790](https://github.com/facebook/react/commit/0b87b2790)**: Updating package versions for release 16.4.1 //<Dan Abramov>//
- **[036ae3c6e](https://github.com/facebook/react/commit/036ae3c6e)**: Use native event dispatching instead of Simulate or SimulateNative (#13023) //<Philipp Spieß>//
- **[945fc1bfc](https://github.com/facebook/react/commit/945fc1bfc)**: Call gDSFP with the right state in react-test-render (#13030) //<Rafał Ruciński>//
- **[392530104](https://github.com/facebook/react/commit/392530104)**: Remove feature flag around 'getDerivedStateFromProps' bug fix (#13022) //<Flarnie Marchan>//
- **[1594409fa](https://github.com/facebook/react/commit/1594409fa)**: Scheduler depends on common packages (#13020) //<Dan Abramov>//
- **[d5c11193e](https://github.com/facebook/react/commit/d5c11193e)**: Added production profiling bundle type (#12886) //<Brian Vaughn>//
- **[ec60457bc](https://github.com/facebook/react/commit/ec60457bc)**: Popping context is O(1) in SSR (#13019) //<Dan Abramov>//
- **[30bc8ef79](https://github.com/facebook/react/commit/30bc8ef79)**: Allow multiple root children in test renderer traversal API (#13017) //<Dan Abramov>//
- **[d480782c4](https://github.com/facebook/react/commit/d480782c4)**: Don’t error when returning an empty Fragment (#12966) //<Philipp Spieß>//
- **[4ac6f133a](https://github.com/facebook/react/commit/4ac6f133a)**: Fallback to event.srcElement for IE9 (#12976) //<Nathan Hunzaker>//
- **[23be4102d](https://github.com/facebook/react/commit/23be4102d)**: Fixed an issue with nested contexts unwinding when server rendering. Issue #12984 (#12985) //<Eric Soderberg>//
- **[d0d428064](https://github.com/facebook/react/commit/d0d428064)**: Remove old reference to inst._wrapperState (#12987) //<Nathan Hunzaker>//
- **[c78957eac](https://github.com/facebook/react/commit/c78957eac)**: Fix an SVG focusing crash in IE11 (#12996) //<Jifa Jiang>//
- **[bfb12ebb5](https://github.com/facebook/react/commit/bfb12ebb5)**: delete a couple of redundant lines in performWorkOnRoot() in ReactFiberScheduler.js (#13003) //<Nathan Quarles>//
- **[394b17eed](https://github.com/facebook/react/commit/394b17eed)**: Update custom renderer docs //<Dan Abramov>//
- **[188c4252a](https://github.com/facebook/react/commit/188c4252a)**: Fix react-dom ReferenceError requestAnimationFrame in non-browser env (#13000) (#13001) //<Ivan Babak>//
- **[9cf3733a9](https://github.com/facebook/react/commit/9cf3733a9)**: update comment in computeAsyncExpiration() to reflect code (#12994) //<Nathan Quarles>//
- **[c5a733e1e](https://github.com/facebook/react/commit/c5a733e1e)**: Fix links of docs on the comment (#12795) //<Ende93>//
- **[36546b513](https://github.com/facebook/react/commit/36546b513)**: Set the correct initial value on input range (#12939) //<Maxime Nory>//
- **[15767a8f8](https://github.com/facebook/react/commit/15767a8f8)**: [scheduler] 5/n Error handling in scheduler (#12920) //<Flarnie Marchan>//
- **[3118ed9d6](https://github.com/facebook/react/commit/3118ed9d6)**: Expose unstable_interactiveUpdates on ReactDOM (#12943) //<Andrew Clark>//
- **[524a74331](https://github.com/facebook/react/commit/524a74331)**: Fix for Flow issues in SimpleCacheProvider (#12942) //<Flarnie Marchan>//
- **[ae57b125c](https://github.com/facebook/react/commit/ae57b125c)**: [simple-cache-provider] Use LRU cache eviction (#12851) //<Andrew Clark>//
- **[e0a03c1b4](https://github.com/facebook/react/commit/e0a03c1b4)**: Extend input type check in selection capabilities (#12062) (#12135) //<Spyros Ioakeimidis>//
- **[79a740c6e](https://github.com/facebook/react/commit/79a740c6e)**: Rename variables to remove references to 'global' global (#12931) //<Flarnie Marchan>//
- **[ff724d3c2](https://github.com/facebook/react/commit/ff724d3c2)**: [scheduler] 4/n Allow splitting out `schedule` in fb-www, prepare to fix polyfill issue internally (#12900) //<Flarnie Marchan>//
- **[83f76e4db](https://github.com/facebook/react/commit/83f76e4db)**: ForwardRefs supports propTypes (#12911) //<Brian Vaughn>//
- **[8aeea5afa](https://github.com/facebook/react/commit/8aeea5afa)**: Do not assign node.value on input creation if no change will occur (#12925) //<Nathan Hunzaker>//
- **[aa85b0fd5](https://github.com/facebook/react/commit/aa85b0fd5)**: Upgrade to Jest 23 (#12894) //<Simen Bekkhus>//
- **[61777a78f](https://github.com/facebook/react/commit/61777a78f)**: [scheduler] 3/n Use a linked list instead of map and queue for callback storage (#12893) //<Flarnie Marchan>//
- **[e7bd3d59a](https://github.com/facebook/react/commit/e7bd3d59a)**: No longer expose ReactNativeComponentTree (#12904) //<Sebastian Markbåge>//
- **[f35d989be](https://github.com/facebook/react/commit/f35d989be)**: TestRenderer warns if flushThrough is passed the wrong params (#12909) //<Brian Vaughn>//
- **[557870067](https://github.com/facebook/react/commit/557870067)**: Record "actual" times for all Fibers within a Profiler tree (alt) (#12910) //<Brian Vaughn>//
- **[76e07071a](https://github.com/facebook/react/commit/76e07071a)**: [scheduler] 2/n Adding 'schedule' fixture (#12884) //<Flarnie Marchan>//
- **[345e0a71a](https://github.com/facebook/react/commit/345e0a71a)**: Improve tests for 'schedule' module (#12880) //<Flarnie Marchan>//
- **[8765d6089](https://github.com/facebook/react/commit/8765d6089)**: Update bundle sizes for 16.4.0 release //<Andrew Clark>//
- **[d427a563d](https://github.com/facebook/react/commit/d427a563d)**: Updating package versions for release 16.4.0 //<Andrew Clark>//
- **[53852a887](https://github.com/facebook/react/commit/53852a887)**: add functional components warning about legacy context api (#12892) //<Chang Yan>//
- **[fe747a51c](https://github.com/facebook/react/commit/fe747a51c)**: Add React.Timeout to getComponentName (#12890) //<Toru Kobayashi>//
- **[c601f7a64](https://github.com/facebook/react/commit/c601f7a64)**: add siblings Timeout components test case (#12862) //<Chang Yan>//
- **[735035837](https://github.com/facebook/react/commit/735035837)**: add legacy context API warning in strict mode (#12849) //<Chang Yan>//
- **[e88579184](https://github.com/facebook/react/commit/e88579184)**: Fix a regression that caused us to listen to extra events at the top (#12878) //<Dan Abramov>//
- **[7c0aca289](https://github.com/facebook/react/commit/7c0aca289)**: Rollup freeze: false (#12879) //<Brian Vaughn>//
- **[33289b530](https://github.com/facebook/react/commit/33289b530)**: Tests and fixes for 'timing out' behavior (#12858) //<Flarnie Marchan>//
- **[ad27845cc](https://github.com/facebook/react/commit/ad27845cc)**: Fix double-firing submit events (#12877) //<Sophie Alpert>//
- **[dd5fad296](https://github.com/facebook/react/commit/dd5fad296)**: Update Flow to 0.70 (#12875) //<Dan Abramov>//
- **[13003654e](https://github.com/facebook/react/commit/13003654e)**: Pass "start time" and "commit time" to Profiler callback (#12852) //<Brian Vaughn>//
- **[dc3b144f4](https://github.com/facebook/react/commit/dc3b144f4)**: Treat Rollup "warnings" as errors (#12868) //<Dan Abramov>//
- **[d7b9b4921](https://github.com/facebook/react/commit/d7b9b4921)**: Fix react native example links in README of 'react-reconciler' (#12871) //<Kevin (Kun) "Kassimo" Qian>//
- **[9bed4a6ae](https://github.com/facebook/react/commit/9bed4a6ae)**: https in reactProdInvariant text (#12869) //<Sophie Alpert>//
- **[47b003a82](https://github.com/facebook/react/commit/47b003a82)**: Resolve host configs at build time (#12792) //<Dan Abramov>//

Release Notes:
[GENERAL] [FEATURE] [React] - React sync for revisions c0fe8d6...ae14317

Reviewed By: bvaughn

Differential Revision: D8458731

fbshipit-source-id: afefaa50685d43e70c8ea85c70d2e29dee311cbb
---
 Libraries/Renderer/REVISION                   |     2 +-
 Libraries/Renderer/oss/ReactFabric-dev.js     | 19505 ++++++++--------
 Libraries/Renderer/oss/ReactFabric-prod.js    |  6431 +++--
 .../Renderer/oss/ReactFabric-profiling.js     |  5645 +++++
 .../Renderer/oss/ReactNativeRenderer-dev.js   | 19249 ++++++++-------
 .../Renderer/oss/ReactNativeRenderer-prod.js  |  7140 +++---
 .../oss/ReactNativeRenderer-profiling.js      |  5899 +++++
 .../shims/ReactNativeComponentTree.js         |    18 -
 Libraries/Renderer/shims/ReactNativeTypes.js  |     2 -
 package.json                                  |     6 +-
 10 files changed, 36815 insertions(+), 27082 deletions(-)
 create mode 100644 Libraries/Renderer/oss/ReactFabric-profiling.js
 create mode 100644 Libraries/Renderer/oss/ReactNativeRenderer-profiling.js
 delete mode 100644 Libraries/Renderer/shims/ReactNativeComponentTree.js

diff --git a/Libraries/Renderer/REVISION b/Libraries/Renderer/REVISION
index 06ec4e875f81..7e020bc8087b 100644
--- a/Libraries/Renderer/REVISION
+++ b/Libraries/Renderer/REVISION
@@ -1 +1 @@
-c0fe8d6f6942f5cbc93c09825e803ba8cf950522
\ No newline at end of file
+ae14317d6810d5b07d01308a2116a707e5e09983
\ No newline at end of file
diff --git a/Libraries/Renderer/oss/ReactFabric-dev.js b/Libraries/Renderer/oss/ReactFabric-dev.js
index 3597c91b11f8..c81fac1813cc 100644
--- a/Libraries/Renderer/oss/ReactFabric-dev.js
+++ b/Libraries/Renderer/oss/ReactFabric-dev.js
@@ -19,19 +19,17 @@ if (__DEV__) {
 require("InitializeCore");
 var invariant = require("fbjs/lib/invariant");
 var warning = require("fbjs/lib/warning");
-var emptyFunction = require("fbjs/lib/emptyFunction");
 var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
 var UIManager = require("UIManager");
-var TextInputState = require("TextInputState");
-var deepDiffer = require("deepDiffer");
-var flattenStyle = require("flattenStyle");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
-var checkPropTypes = require("prop-types/checkPropTypes");
-var shallowEqual = require("fbjs/lib/shallowEqual");
-var ExceptionsManager = require("ExceptionsManager");
+var deepDiffer = require("deepDiffer");
+var flattenStyle = require("flattenStyle");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
+var TextInputState = require("TextInputState");
 var FabricUIManager = require("FabricUIManager");
+var checkPropTypes = require("prop-types/checkPropTypes");
+var ExceptionsManager = require("ExceptionsManager");
 
 var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
   this._hasCaughtError = false;
@@ -1183,7 +1181,9 @@ var EventInterface = {
   type: null,
   target: null,
   // currentTarget is set when dispatching; no use in copying it here
-  currentTarget: emptyFunction.thatReturnsNull,
+  currentTarget: function() {
+    return null;
+  },
   eventPhase: null,
   bubbles: null,
   cancelable: null,
@@ -1194,6 +1194,14 @@ var EventInterface = {
   isTrusted: null
 };
 
+function functionThatReturnsTrue() {
+  return true;
+}
+
+function functionThatReturnsFalse() {
+  return false;
+}
+
 /**
  * Synthetic events are dispatched by event plugins, typically in response to a
  * top-level event delegation handler.
@@ -1254,11 +1262,11 @@ function SyntheticEvent(
       ? nativeEvent.defaultPrevented
       : nativeEvent.returnValue === false;
   if (defaultPrevented) {
-    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
+    this.isDefaultPrevented = functionThatReturnsTrue;
   } else {
-    this.isDefaultPrevented = emptyFunction.thatReturnsFalse;
+    this.isDefaultPrevented = functionThatReturnsFalse;
   }
-  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
+  this.isPropagationStopped = functionThatReturnsFalse;
   return this;
 }
 
@@ -1275,7 +1283,7 @@ Object.assign(SyntheticEvent.prototype, {
     } else if (typeof event.returnValue !== "unknown") {
       event.returnValue = false;
     }
-    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
+    this.isDefaultPrevented = functionThatReturnsTrue;
   },
 
   stopPropagation: function() {
@@ -1295,7 +1303,7 @@ Object.assign(SyntheticEvent.prototype, {
       event.cancelBubble = true;
     }
 
-    this.isPropagationStopped = emptyFunction.thatReturnsTrue;
+    this.isPropagationStopped = functionThatReturnsTrue;
   },
 
   /**
@@ -1304,7 +1312,7 @@ Object.assign(SyntheticEvent.prototype, {
    * won't be added back into the pool.
    */
   persist: function() {
-    this.isPersistent = emptyFunction.thatReturnsTrue;
+    this.isPersistent = functionThatReturnsTrue;
   },
 
   /**
@@ -1312,7 +1320,7 @@ Object.assign(SyntheticEvent.prototype, {
    *
    * @return {boolean} True if this should not be released, false otherwise.
    */
-  isPersistent: emptyFunction.thatReturnsFalse,
+  isPersistent: functionThatReturnsFalse,
 
   /**
    * `PooledClass` looks for `destructor` on each instance it releases.
@@ -1340,12 +1348,12 @@ Object.assign(SyntheticEvent.prototype, {
       Object.defineProperty(
         this,
         "preventDefault",
-        getPooledWarningPropertyDefinition("preventDefault", emptyFunction)
+        getPooledWarningPropertyDefinition("preventDefault", function() {})
       );
       Object.defineProperty(
         this,
         "stopPropagation",
-        getPooledWarningPropertyDefinition("stopPropagation", emptyFunction)
+        getPooledWarningPropertyDefinition("stopPropagation", function() {})
       );
     }
   }
@@ -2371,64 +2379,58 @@ var ReactNativeBridgeEventPlugin = {
   }
 };
 
-var instanceCache = {};
-var instanceProps = {};
+var ReactNativeEventPluginOrder = [
+  "ResponderEventPlugin",
+  "ReactNativeBridgeEventPlugin"
+];
 
-function precacheFiberNode(hostInst, tag) {
-  instanceCache[tag] = hostInst;
-}
+/**
+ * Make sure essential globals are available and are patched correctly. Please don't remove this
+ * line. Bundles created by react-packager `require` it before executing any application code. This
+ * ensures it exists in the dependency graph and can be `require`d.
+ * TODO: require this in packager, not in React #10932517
+ */
+// Module provided by RN:
+/**
+ * Inject module for resolving DOM hierarchy and plugin ordering.
+ */
+injection.injectEventPluginOrder(ReactNativeEventPluginOrder);
 
-function uncacheFiberNode(tag) {
-  delete instanceCache[tag];
-  delete instanceProps[tag];
-}
+/**
+ * Some important event plugins included by default (without having to require
+ * them).
+ */
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
 
-function getInstanceFromTag(tag) {
-  if (typeof tag === "number") {
-    return instanceCache[tag] || null;
-  } else {
-    // Fabric will invoke event emitters on a direct fiber reference
-    return tag;
-  }
+function getInstanceFromInstance(instanceHandle) {
+  return instanceHandle;
 }
 
 function getTagFromInstance(inst) {
-  var tag = inst.stateNode._nativeTag;
-  if (tag === undefined) {
-    tag = inst.stateNode.canonical._nativeTag;
-  }
+  var tag = inst.stateNode.canonical._nativeTag;
   invariant(tag, "All native instances should have a tag.");
   return tag;
 }
 
-function getFiberCurrentPropsFromNode$1(stateNode) {
-  return instanceProps[stateNode._nativeTag] || null;
+function getFiberCurrentPropsFromNode$1(inst) {
+  return inst.canonical.currentProps;
 }
 
-function updateFiberProps(tag, props) {
-  instanceProps[tag] = props;
-}
-
-var ReactNativeComponentTree = Object.freeze({
-  precacheFiberNode: precacheFiberNode,
-  uncacheFiberNode: uncacheFiberNode,
-  getClosestInstanceFromNode: getInstanceFromTag,
-  getInstanceFromNode: getInstanceFromTag,
+var ReactFabricComponentTree = Object.freeze({
+  getClosestInstanceFromNode: getInstanceFromInstance,
+  getInstanceFromNode: getInstanceFromInstance,
   getNodeFromInstance: getTagFromInstance,
-  getFiberCurrentPropsFromNode: getFiberCurrentPropsFromNode$1,
-  updateFiberProps: updateFiberProps
+  getFiberCurrentPropsFromNode: getFiberCurrentPropsFromNode$1
 });
 
-var ReactNativeEventPluginOrder = [
-  "ResponderEventPlugin",
-  "ReactNativeBridgeEventPlugin"
-];
-
 // Module provided by RN:
-var ReactNativeGlobalResponderHandler = {
+var ReactFabricGlobalResponderHandler = {
   onChange: function(from, to, blockNativeResponder) {
     if (to !== null) {
-      var tag = to.stateNode._nativeTag;
+      var tag = to.stateNode.canonical._nativeTag;
       UIManager.setJSResponder(tag, blockNativeResponder);
     } else {
       UIManager.clearJSResponder();
@@ -2436,44 +2438,40 @@ var ReactNativeGlobalResponderHandler = {
   }
 };
 
-/**
- * Make sure essential globals are available and are patched correctly. Please don't remove this
- * line. Bundles created by react-packager `require` it before executing any application code. This
- * ensures it exists in the dependency graph and can be `require`d.
- * TODO: require this in packager, not in React #10932517
- */
-// Module provided by RN:
-/**
- * Inject module for resolving DOM hierarchy and plugin ordering.
- */
-injection.injectEventPluginOrder(ReactNativeEventPluginOrder);
-injection$1.injectComponentTree(ReactNativeComponentTree);
+injection$1.injectComponentTree(ReactFabricComponentTree);
 
 ResponderEventPlugin.injection.injectGlobalResponderHandler(
-  ReactNativeGlobalResponderHandler
+  ReactFabricGlobalResponderHandler
 );
 
 /**
- * Some important event plugins included by default (without having to require
- * them).
+ * `ReactInstanceMap` maintains a mapping from a public facing stateful
+ * instance (key) and the internal representation (value). This allows public
+ * methods to accept the user facing instance as an argument and map them back
+ * to internal methods.
+ *
+ * Note that this module is currently shared and assumed to be stateless.
+ * If this becomes an actual Map, that will break.
+ */
+
+/**
+ * This API should be called `delete` but we'd have to make sure to always
+ * transform these to strings for IE support. When this transform is fully
+ * supported we can rename it.
  */
-injection.injectEventPluginsByName({
-  ResponderEventPlugin: ResponderEventPlugin,
-  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
-});
 
-// TODO: The event emitter registration is interfering with the existing
-// ReactNative renderer. So disable it for Fabric for now.
+function get$1(key) {
+  return key._reactInternalFiber;
+}
 
-// import * as ReactNativeEventEmitter from './ReactNativeEventEmitter';
+function set(key, value) {
+  key._reactInternalFiber = value;
+}
 
-// Module provided by RN:
-// import RCTEventEmitter from 'RCTEventEmitter';
+var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
 
-/**
- * Register the event emitter with the native bridge
- */
-// RCTEventEmitter.register(ReactNativeEventEmitter);
+var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
+var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
 
 // The Symbol used to tag the ReactElement-like types. If there is no native Symbol
 // nor polyfill, then a plain number is used for performance.
@@ -2510,238 +2508,503 @@ function getIteratorFn(maybeIterable) {
   return null;
 }
 
-function createPortal(
-  children,
-  containerInfo,
-  // TODO: figure out the API for cross-renderer implementation.
-  implementation
-) {
-  var key =
-    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
+function getComponentName(fiber) {
+  var type = fiber.type;
 
-  return {
-    // This tag allow us to uniquely identify this as a React Portal
-    $$typeof: REACT_PORTAL_TYPE,
-    key: key == null ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
+  if (typeof type === "function") {
+    return type.displayName || type.name;
+  }
+  if (typeof type === "string") {
+    return type;
+  }
+  switch (type) {
+    case REACT_ASYNC_MODE_TYPE:
+      return "AsyncMode";
+    case REACT_CONTEXT_TYPE:
+      return "Context.Consumer";
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_PROFILER_TYPE:
+      return "Profiler(" + fiber.pendingProps.id + ")";
+    case REACT_PROVIDER_TYPE:
+      return "Context.Provider";
+    case REACT_STRICT_MODE_TYPE:
+      return "StrictMode";
+    case REACT_TIMEOUT_TYPE:
+      return "Timeout";
+  }
+  if (typeof type === "object" && type !== null) {
+    switch (type.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        var functionName = type.render.displayName || type.render.name || "";
+        return functionName !== ""
+          ? "ForwardRef(" + functionName + ")"
+          : "ForwardRef";
+    }
+  }
+  return null;
 }
 
-// Use to restore controlled state after a change event has fired.
+// Don't change these two values. They're used by React Dev Tools.
+var NoEffect = /*              */ 0;
+var PerformedWork = /*         */ 1;
 
-var fiberHostComponent = null;
+// You can change the rest (and add more).
+var Placement = /*             */ 2;
+var Update = /*                */ 4;
+var PlacementAndUpdate = /*    */ 6;
+var Deletion = /*              */ 8;
+var ContentReset = /*          */ 16;
+var Callback = /*              */ 32;
+var DidCapture = /*            */ 64;
+var Ref = /*                   */ 128;
+var Snapshot = /*              */ 256;
 
-var restoreTarget = null;
-var restoreQueue = null;
+// Union of all host effects
+var HostEffectMask = /*        */ 511;
 
-function restoreStateOfTarget(target) {
-  // We perform this translation at the end of the event loop so that we
-  // always receive the correct fiber here
-  var internalInstance = getInstanceFromNode(target);
-  if (!internalInstance) {
-    // Unmounted
-    return;
+var Incomplete = /*            */ 512;
+var ShouldCapture = /*         */ 1024;
+
+var MOUNTING = 1;
+var MOUNTED = 2;
+var UNMOUNTED = 3;
+
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (!fiber.alternate) {
+    // If there is no alternate, this might be a new tree that isn't inserted
+    // yet. If it is, then it will have a pending insertion effect on it.
+    if ((node.effectTag & Placement) !== NoEffect) {
+      return MOUNTING;
+    }
+    while (node.return) {
+      node = node.return;
+      if ((node.effectTag & Placement) !== NoEffect) {
+        return MOUNTING;
+      }
+    }
+  } else {
+    while (node.return) {
+      node = node.return;
+    }
   }
-  invariant(
-    fiberHostComponent &&
-      typeof fiberHostComponent.restoreControlledState === "function",
-    "Fiber needs to be injected to handle a fiber target for controlled " +
-      "events. This error is likely caused by a bug in React. Please file an issue."
-  );
-  var props = getFiberCurrentPropsFromNode(internalInstance.stateNode);
-  fiberHostComponent.restoreControlledState(
-    internalInstance.stateNode,
-    internalInstance.type,
-    props
-  );
+  if (node.tag === HostRoot) {
+    // TODO: Check if this was a nested HostRoot when used with
+    // renderContainerIntoSubtree.
+    return MOUNTED;
+  }
+  // If we didn't hit the root, that means that we're in an disconnected tree
+  // that has been unmounted.
+  return UNMOUNTED;
 }
 
-function needsStateRestore() {
-  return restoreTarget !== null || restoreQueue !== null;
+function isFiberMounted(fiber) {
+  return isFiberMountedImpl(fiber) === MOUNTED;
 }
 
-function restoreStateIfNeeded() {
-  if (!restoreTarget) {
-    return;
-  }
-  var target = restoreTarget;
-  var queuedTargets = restoreQueue;
-  restoreTarget = null;
-  restoreQueue = null;
-
-  restoreStateOfTarget(target);
-  if (queuedTargets) {
-    for (var i = 0; i < queuedTargets.length; i++) {
-      restoreStateOfTarget(queuedTargets[i]);
+function isMounted(component) {
+  {
+    var owner = ReactCurrentOwner.current;
+    if (owner !== null && owner.tag === ClassComponent) {
+      var ownerFiber = owner;
+      var instance = ownerFiber.stateNode;
+      !instance._warnedAboutRefsInRender
+        ? warning(
+            false,
+            "%s is accessing isMounted inside its render() function. " +
+              "render() should be a pure function of props and state. It should " +
+              "never access something that requires stale data from the previous " +
+              "render, such as refs. Move this logic to componentDidMount and " +
+              "componentDidUpdate instead.",
+            getComponentName(ownerFiber) || "A component"
+          )
+        : void 0;
+      instance._warnedAboutRefsInRender = true;
     }
   }
-}
 
-// Used as a way to call batchedUpdates when we don't have a reference to
-// the renderer. Such as when we're dispatching events or if third party
-// libraries need to call batchedUpdates. Eventually, this API will go away when
-// everything is batched by default. We'll then have a similar API to opt-out of
-// scheduled work and instead do synchronous work.
-
-// Defaults
-var _batchedUpdates = function(fn, bookkeeping) {
-  return fn(bookkeeping);
-};
-var _interactiveUpdates = function(fn, a, b) {
-  return fn(a, b);
-};
-var _flushInteractiveUpdates = function() {};
-
-var isBatching = false;
-function batchedUpdates(fn, bookkeeping) {
-  if (isBatching) {
-    // If we are currently inside another batch, we need to wait until it
-    // fully completes before restoring state.
-    return fn(bookkeeping);
-  }
-  isBatching = true;
-  try {
-    return _batchedUpdates(fn, bookkeeping);
-  } finally {
-    // Here we wait until all updates have propagated, which is important
-    // when using controlled components within layers:
-    // https://github.com/facebook/react/issues/1698
-    // Then we restore state of any controlled component.
-    isBatching = false;
-    var controlledComponentsHavePendingUpdates = needsStateRestore();
-    if (controlledComponentsHavePendingUpdates) {
-      // If a controlled event was fired, we may need to restore the state of
-      // the DOM node back to the controlled value. This is necessary when React
-      // bails out of the update without touching the DOM.
-      _flushInteractiveUpdates();
-      restoreStateIfNeeded();
-    }
+  var fiber = get$1(component);
+  if (!fiber) {
+    return false;
   }
+  return isFiberMountedImpl(fiber) === MOUNTED;
 }
 
-var injection$2 = {
-  injectRenderer: function(renderer) {
-    _batchedUpdates = renderer.batchedUpdates;
-    _interactiveUpdates = renderer.interactiveUpdates;
-    _flushInteractiveUpdates = renderer.flushInteractiveUpdates;
-  }
-};
-
-// TODO: this is special because it gets imported during build.
-
-var ReactVersion = "16.3.2";
-
-// Modules provided by RN:
-var emptyObject$1 = {};
-
-/**
- * Create a payload that contains all the updates between two sets of props.
- *
- * These helpers are all encapsulated into a single module, because they use
- * mutation as a performance optimization which leads to subtle shared
- * dependencies between the code paths. To avoid this mutable state leaking
- * across modules, I've kept them isolated to this module.
- */
-
-// Tracks removed keys
-var removedKeys = null;
-var removedKeyCount = 0;
-
-function defaultDiffer(prevProp, nextProp) {
-  if (typeof nextProp !== "object" || nextProp === null) {
-    // Scalars have already been checked for equality
-    return true;
-  } else {
-    // For objects and arrays, the default diffing algorithm is a deep compare
-    return deepDiffer(prevProp, nextProp);
-  }
+function assertIsMounted(fiber) {
+  invariant(
+    isFiberMountedImpl(fiber) === MOUNTED,
+    "Unable to find node on an unmounted component."
+  );
 }
 
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node)) {
-    var i = node.length;
-    while (i-- && removedKeyCount > 0) {
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate) {
+    // If there is no alternate, then we only need to check if it is mounted.
+    var state = isFiberMountedImpl(fiber);
+    invariant(
+      state !== UNMOUNTED,
+      "Unable to find node on an unmounted component."
+    );
+    if (state === MOUNTING) {
+      return null;
+    }
+    return fiber;
+  }
+  // If we have two possible branches, we'll walk backwards up to the root
+  // to see what path the root points to. On the way we may hit one of the
+  // special cases and we'll deal with them.
+  var a = fiber;
+  var b = alternate;
+  while (true) {
+    var parentA = a.return;
+    var parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) {
+      // We're at the root.
+      break;
     }
-  } else if (node && removedKeyCount > 0) {
-    var obj = node;
-    for (var propKey in removedKeys) {
-      if (!removedKeys[propKey]) {
-        continue;
-      }
-      var _nextProp = obj[propKey];
-      if (_nextProp === undefined) {
-        continue;
-      }
 
-      var attributeConfig = validAttributes[propKey];
-      if (!attributeConfig) {
-        continue; // not a valid native prop
+    // If both copies of the parent fiber point to the same child, we can
+    // assume that the child is current. This happens when we bailout on low
+    // priority: the bailed out fiber's child reuses the current child.
+    if (parentA.child === parentB.child) {
+      var child = parentA.child;
+      while (child) {
+        if (child === a) {
+          // We've determined that A is the current branch.
+          assertIsMounted(parentA);
+          return fiber;
+        }
+        if (child === b) {
+          // We've determined that B is the current branch.
+          assertIsMounted(parentA);
+          return alternate;
+        }
+        child = child.sibling;
       }
+      // We should never have an alternate for any mounting node. So the only
+      // way this could possibly happen is if this was unmounted, if at all.
+      invariant(false, "Unable to find node on an unmounted component.");
+    }
 
-      if (typeof _nextProp === "function") {
-        _nextProp = true;
-      }
-      if (typeof _nextProp === "undefined") {
-        _nextProp = null;
+    if (a.return !== b.return) {
+      // The return pointer of A and the return pointer of B point to different
+      // fibers. We assume that return pointers never criss-cross, so A must
+      // belong to the child set of A.return, and B must belong to the child
+      // set of B.return.
+      a = parentA;
+      b = parentB;
+    } else {
+      // The return pointers point to the same fiber. We'll have to use the
+      // default, slow path: scan the child sets of each parent alternate to see
+      // which child belongs to which set.
+      //
+      // Search parent A's child set
+      var didFindChild = false;
+      var _child = parentA.child;
+      while (_child) {
+        if (_child === a) {
+          didFindChild = true;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          didFindChild = true;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
       }
-
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = _nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(_nextProp)
-            : _nextProp;
-        updatePayload[propKey] = nextValue;
+      if (!didFindChild) {
+        // Search parent B's child set
+        _child = parentB.child;
+        while (_child) {
+          if (_child === a) {
+            didFindChild = true;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            didFindChild = true;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          didFindChild,
+          "Child was not found in either parent set. This indicates a bug " +
+            "in React related to the return pointer. Please file an issue."
+        );
       }
-      removedKeys[propKey] = false;
-      removedKeyCount--;
     }
-  }
-}
 
-function diffNestedArrayProperty(
-  updatePayload,
-  prevArray,
-  nextArray,
-  validAttributes
-) {
-  var minLength =
-    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
-  var i = void 0;
-  for (i = 0; i < minLength; i++) {
-    // Diff any items in the array in the forward direction. Repeated keys
-    // will be overwritten by later values.
-    updatePayload = diffNestedProperty(
-      updatePayload,
-      prevArray[i],
-      nextArray[i],
-      validAttributes
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. " +
+        "This error is likely caused by a bug in React. Please file an issue."
     );
   }
-  for (; i < prevArray.length; i++) {
-    // Clear out all remaining properties.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevArray[i],
-      validAttributes
-    );
+  // If the root is not a host container, we're in a disconnected tree. I.e.
+  // unmounted.
+  invariant(
+    a.tag === HostRoot,
+    "Unable to find node on an unmounted component."
+  );
+  if (a.stateNode.current === a) {
+    // We've determined that A is the current branch.
+    return fiber;
+  }
+  // Otherwise B has to be current branch.
+  return alternate;
+}
+
+function findCurrentHostFiber(parent) {
+  var currentParent = findCurrentFiberUsingSlowPath(parent);
+  if (!currentParent) {
+    return null;
+  }
+
+  // Next we'll drill down this component to find the first HostComponent/Text.
+  var node = currentParent;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      return node;
+    } else if (node.child) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === currentParent) {
+      return null;
+    }
+    while (!node.sibling) {
+      if (!node.return || node.return === currentParent) {
+        return null;
+      }
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+  // Flow needs the return null here, but ESLint complains about it.
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
+
+function findCurrentHostFiberWithNoPortals(parent) {
+  var currentParent = findCurrentFiberUsingSlowPath(parent);
+  if (!currentParent) {
+    return null;
+  }
+
+  // Next we'll drill down this component to find the first HostComponent/Text.
+  var node = currentParent;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      return node;
+    } else if (node.child && node.tag !== HostPortal) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === currentParent) {
+      return null;
+    }
+    while (!node.sibling) {
+      if (!node.return || node.return === currentParent) {
+        return null;
+      }
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+  // Flow needs the return null here, but ESLint complains about it.
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
+
+/**
+ * In the future, we should cleanup callbacks by cancelling them instead of
+ * using this.
+ */
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (!callback) {
+      return undefined;
+    }
+    if (typeof context.__isMounted === "boolean") {
+      // TODO(gaearon): this is gross and should be removed.
+      // It is currently necessary because View uses createClass,
+      // and so any measure() calls on View (which are done by React
+      // DevTools) trigger the isMounted() deprecation warning.
+      if (!context.__isMounted) {
+        return undefined;
+      }
+      // The else branch is important so that we don't
+      // trigger the deprecation warning by calling isMounted.
+    } else if (typeof context.isMounted === "function") {
+      if (!context.isMounted()) {
+        return undefined;
+      }
+    }
+    return callback.apply(context, arguments);
+  };
+}
+
+function throwOnStylesProp(component, props) {
+  if (props.styles !== undefined) {
+    var owner = component._owner || null;
+    var name = component.constructor.displayName;
+    var msg =
+      "`styles` is not a supported property of `" +
+      name +
+      "`, did " +
+      "you mean `style` (singular)?";
+    if (owner && owner.constructor && owner.constructor.displayName) {
+      msg +=
+        "\n\nCheck the `" +
+        owner.constructor.displayName +
+        "` parent " +
+        " component.";
+    }
+    throw new Error(msg);
+  }
+}
+
+function warnForStyleProps(props, validAttributes) {
+  for (var key in validAttributes.style) {
+    if (!(validAttributes[key] || props[key] === undefined)) {
+      console.error(
+        "You are setting the style `{ " +
+          key +
+          ": ... }` as a prop. You " +
+          "should nest it in a style object. " +
+          "E.g. `{ style: { " +
+          key +
+          ": ... } }`"
+      );
+    }
+  }
+}
+
+// Modules provided by RN:
+var emptyObject$1 = {};
+
+/**
+ * Create a payload that contains all the updates between two sets of props.
+ *
+ * These helpers are all encapsulated into a single module, because they use
+ * mutation as a performance optimization which leads to subtle shared
+ * dependencies between the code paths. To avoid this mutable state leaking
+ * across modules, I've kept them isolated to this module.
+ */
+
+// Tracks removed keys
+var removedKeys = null;
+var removedKeyCount = 0;
+
+function defaultDiffer(prevProp, nextProp) {
+  if (typeof nextProp !== "object" || nextProp === null) {
+    // Scalars have already been checked for equality
+    return true;
+  } else {
+    // For objects and arrays, the default diffing algorithm is a deep compare
+    return deepDiffer(prevProp, nextProp);
+  }
+}
+
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node)) {
+    var i = node.length;
+    while (i-- && removedKeyCount > 0) {
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+    }
+  } else if (node && removedKeyCount > 0) {
+    var obj = node;
+    for (var propKey in removedKeys) {
+      if (!removedKeys[propKey]) {
+        continue;
+      }
+      var _nextProp = obj[propKey];
+      if (_nextProp === undefined) {
+        continue;
+      }
+
+      var attributeConfig = validAttributes[propKey];
+      if (!attributeConfig) {
+        continue; // not a valid native prop
+      }
+
+      if (typeof _nextProp === "function") {
+        _nextProp = true;
+      }
+      if (typeof _nextProp === "undefined") {
+        _nextProp = null;
+      }
+
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = _nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(_nextProp)
+            : _nextProp;
+        updatePayload[propKey] = nextValue;
+      }
+      removedKeys[propKey] = false;
+      removedKeyCount--;
+    }
+  }
+}
+
+function diffNestedArrayProperty(
+  updatePayload,
+  prevArray,
+  nextArray,
+  validAttributes
+) {
+  var minLength =
+    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
+  var i = void 0;
+  for (i = 0; i < minLength; i++) {
+    // Diff any items in the array in the forward direction. Repeated keys
+    // will be overwritten by later values.
+    updatePayload = diffNestedProperty(
+      updatePayload,
+      prevArray[i],
+      nextArray[i],
+      validAttributes
+    );
+  }
+  for (; i < prevArray.length; i++) {
+    // Clear out all remaining properties.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevArray[i],
+      validAttributes
+    );
   }
   for (; i < nextArray.length; i++) {
     // Add all remaining properties.
@@ -3072,2355 +3335,2552 @@ function diff(prevProps, nextProps, validAttributes) {
   );
 }
 
-/**
- * In the future, we should cleanup callbacks by cancelling them instead of
- * using this.
- */
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (!callback) {
-      return undefined;
-    }
-    if (typeof context.__isMounted === "boolean") {
-      // TODO(gaearon): this is gross and should be removed.
-      // It is currently necessary because View uses createClass,
-      // and so any measure() calls on View (which are done by React
-      // DevTools) trigger the isMounted() deprecation warning.
-      if (!context.__isMounted) {
-        return undefined;
-      }
-      // The else branch is important so that we don't
-      // trigger the deprecation warning by calling isMounted.
-    } else if (typeof context.isMounted === "function") {
-      if (!context.isMounted()) {
-        return undefined;
-      }
-    }
-    return callback.apply(context, arguments);
-  };
-}
+var hasNativePerformanceNow =
+  typeof performance === "object" && typeof performance.now === "function";
 
-function throwOnStylesProp(component, props) {
-  if (props.styles !== undefined) {
-    var owner = component._owner || null;
-    var name = component.constructor.displayName;
-    var msg =
-      "`styles` is not a supported property of `" +
-      name +
-      "`, did " +
-      "you mean `style` (singular)?";
-    if (owner && owner.constructor && owner.constructor.displayName) {
-      msg +=
-        "\n\nCheck the `" +
-        owner.constructor.displayName +
-        "` parent " +
-        " component.";
+var now$1 = hasNativePerformanceNow
+  ? function() {
+      return performance.now();
     }
-    throw new Error(msg);
+  : function() {
+      return Date.now();
+    };
+
+var scheduledCallback = null;
+var frameDeadline = 0;
+
+var frameDeadlineObject = {
+  timeRemaining: function() {
+    return frameDeadline - now$1();
+  },
+  didTimeout: false
+};
+
+function setTimeoutCallback() {
+  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
+  // React API probably changing to boolean rather than time remaining.
+  // Longer-term plan is to rewrite this using shared memory,
+  // And just return the value of the bit as the boolean.
+  frameDeadline = now$1() + 5;
+
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  if (callback !== null) {
+    callback(frameDeadlineObject);
   }
 }
 
-function warnForStyleProps(props, validAttributes) {
-  for (var key in validAttributes.style) {
-    if (!(validAttributes[key] || props[key] === undefined)) {
-      console.error(
-        "You are setting the style `{ " +
-          key +
-          ": ... }` as a prop. You " +
-          "should nest it in a style object. " +
-          "E.g. `{ style: { " +
-          key +
-          ": ... } }`"
-      );
-    }
-  }
+// RN has a poor polyfill for requestIdleCallback so we aren't using it.
+// This implementation is only intended for short-term use anyway.
+// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
+function scheduleDeferredCallback$1(callback, options) {
+  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
+  scheduledCallback = callback;
+  var timeoutId = setTimeout(setTimeoutCallback, 1);
+  return timeoutId; // Timeouts are always numbers on RN
 }
 
-// Modules provided by RN:
-var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
-  /**
-   * `NativeMethodsMixin` provides methods to access the underlying native
-   * component directly. This can be useful in cases when you want to focus
-   * a view or measure its on-screen dimensions, for example.
-   *
-   * The methods described here are available on most of the default components
-   * provided by React Native. Note, however, that they are *not* available on
-   * composite components that aren't directly backed by a native view. This will
-   * generally include most components that you define in your own app. For more
-   * information, see [Direct
-   * Manipulation](docs/direct-manipulation.html).
-   *
-   * Note the Flow $Exact<> syntax is required to support mixins.
-   * React createClass mixins can only be used with exact types.
-   */
-  var NativeMethodsMixin = {
-    /**
-     * Determines the location on screen, width, and height of the given view and
-     * returns the values via an async callback. If successful, the callback will
-     * be called with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *  - pageX
-     *  - pageY
-     *
-     * Note that these measurements are not available until after the rendering
-     * has been completed in native. If you need the measurements as soon as
-     * possible, consider using the [`onLayout`
-     * prop](docs/view.html#onlayout) instead.
-     */
-    measure: function(callback) {
-      UIManager.measure(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    },
+function cancelDeferredCallback$1(callbackID) {
+  scheduledCallback = null;
+  clearTimeout(callbackID); // Timeouts are always numbers on RN
+}
 
-    /**
-     * Determines the location of the given view in the window and returns the
-     * values via an async callback. If the React root view is embedded in
-     * another native view, this will give you the absolute coordinates. If
-     * successful, the callback will be called with the following
-     * arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *
-     * Note that these measurements are not available until after the rendering
-     * has been completed in native.
-     */
-    measureInWindow: function(callback) {
-      UIManager.measureInWindow(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    },
+// Use to restore controlled state after a change event has fired.
 
-    /**
-     * Like [`measure()`](#measure), but measures the view relative an ancestor,
-     * specified as `relativeToNativeNode`. This means that the returned x, y
-     * are relative to the origin x, y of the ancestor view.
-     *
-     * As always, to obtain a native node handle for a component, you can use
-     * `findNodeHandle(component)`.
-     */
-    measureLayout: function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail /* currently unused */
-    ) {
-      UIManager.measureLayout(
-        findNodeHandle(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    },
+var fiberHostComponent = null;
 
-    /**
-     * This function sends props straight to native. They will not participate in
-     * future diff process - this means that if you do not include them in the
-     * next render, they will remain active (see [Direct
-     * Manipulation](docs/direct-manipulation.html)).
-     */
-    setNativeProps: function(nativeProps) {
-      // Class components don't have viewConfig -> validateAttributes.
-      // Nor does it make sense to set native props on a non-native component.
-      // Instead, find the nearest host component and set props on it.
-      // Use findNodeHandle() rather than findNodeHandle() because
-      // We want the instance/wrapper (not the native tag).
-      var maybeInstance = void 0;
+var restoreTarget = null;
+var restoreQueue = null;
 
-      // Fiber errors if findNodeHandle is called for an umounted component.
-      // Tests using ReactTestRenderer will trigger this case indirectly.
-      // Mimicking stack behavior, we should silently ignore this case.
-      // TODO Fix ReactTestRenderer so we can remove this try/catch.
-      try {
-        maybeInstance = findHostInstance(this);
-      } catch (error) {}
+function restoreStateOfTarget(target) {
+  // We perform this translation at the end of the event loop so that we
+  // always receive the correct fiber here
+  var internalInstance = getInstanceFromNode(target);
+  if (!internalInstance) {
+    // Unmounted
+    return;
+  }
+  invariant(
+    fiberHostComponent &&
+      typeof fiberHostComponent.restoreControlledState === "function",
+    "Fiber needs to be injected to handle a fiber target for controlled " +
+      "events. This error is likely caused by a bug in React. Please file an issue."
+  );
+  var props = getFiberCurrentPropsFromNode(internalInstance.stateNode);
+  fiberHostComponent.restoreControlledState(
+    internalInstance.stateNode,
+    internalInstance.type,
+    props
+  );
+}
 
-      // If there is no host component beneath this we should fail silently.
-      // This is not an error; it could mean a class component rendered null.
-      if (maybeInstance == null) {
-        return;
-      }
+function needsStateRestore() {
+  return restoreTarget !== null || restoreQueue !== null;
+}
 
-      var viewConfig = maybeInstance.viewConfig;
+function restoreStateIfNeeded() {
+  if (!restoreTarget) {
+    return;
+  }
+  var target = restoreTarget;
+  var queuedTargets = restoreQueue;
+  restoreTarget = null;
+  restoreQueue = null;
 
-      {
-        warnForStyleProps(nativeProps, viewConfig.validAttributes);
-      }
+  restoreStateOfTarget(target);
+  if (queuedTargets) {
+    for (var i = 0; i < queuedTargets.length; i++) {
+      restoreStateOfTarget(queuedTargets[i]);
+    }
+  }
+}
 
-      var updatePayload = create(nativeProps, viewConfig.validAttributes);
+// Used as a way to call batchedUpdates when we don't have a reference to
+// the renderer. Such as when we're dispatching events or if third party
+// libraries need to call batchedUpdates. Eventually, this API will go away when
+// everything is batched by default. We'll then have a similar API to opt-out of
+// scheduled work and instead do synchronous work.
 
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          updatePayload
-        );
-      }
-    },
-
-    /**
-     * Requests focus for the given input or view. The exact behavior triggered
-     * will depend on the platform and type of view.
-     */
-    focus: function() {
-      TextInputState.focusTextInput(findNodeHandle(this));
-    },
+// Defaults
+var _batchedUpdates = function(fn, bookkeeping) {
+  return fn(bookkeeping);
+};
+var _interactiveUpdates = function(fn, a, b) {
+  return fn(a, b);
+};
+var _flushInteractiveUpdates = function() {};
 
-    /**
-     * Removes focus from an input or view. This is the opposite of `focus()`.
-     */
-    blur: function() {
-      TextInputState.blurTextInput(findNodeHandle(this));
+var isBatching = false;
+function batchedUpdates(fn, bookkeeping) {
+  if (isBatching) {
+    // If we are currently inside another batch, we need to wait until it
+    // fully completes before restoring state.
+    return fn(bookkeeping);
+  }
+  isBatching = true;
+  try {
+    return _batchedUpdates(fn, bookkeeping);
+  } finally {
+    // Here we wait until all updates have propagated, which is important
+    // when using controlled components within layers:
+    // https://github.com/facebook/react/issues/1698
+    // Then we restore state of any controlled component.
+    isBatching = false;
+    var controlledComponentsHavePendingUpdates = needsStateRestore();
+    if (controlledComponentsHavePendingUpdates) {
+      // If a controlled event was fired, we may need to restore the state of
+      // the DOM node back to the controlled value. This is necessary when React
+      // bails out of the update without touching the DOM.
+      _flushInteractiveUpdates();
+      restoreStateIfNeeded();
     }
-  };
-
-  {
-    // hide this from Flow since we can't define these properties outside of
-    // true without actually implementing them (setting them to undefined
-    // isn't allowed by ReactClass)
-    var NativeMethodsMixin_DEV = NativeMethodsMixin;
-    invariant(
-      !NativeMethodsMixin_DEV.componentWillMount &&
-        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
-        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
-        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
-      "Do not override existing functions."
-    );
-    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
-    // Once these lifecycles have been remove from the reconciler.
-    NativeMethodsMixin_DEV.componentWillMount = function() {
-      throwOnStylesProp(this, this.props);
-    };
-    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
-      throwOnStylesProp(this, newProps);
-    };
-    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
-      throwOnStylesProp(this, this.props);
-    };
-    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
-      newProps
-    ) {
-      throwOnStylesProp(this, newProps);
-    };
-
-    // React may warn about cWM/cWRP/cWU methods being deprecated.
-    // Add a flag to suppress these warnings for this special case.
-    // TODO (bvaughn) Remove this flag once the above methods have been removed.
-    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
-    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
   }
+}
 
-  return NativeMethodsMixin;
+var injection$2 = {
+  injectRenderer: function(renderer) {
+    _batchedUpdates = renderer.batchedUpdates;
+    _interactiveUpdates = renderer.interactiveUpdates;
+    _flushInteractiveUpdates = renderer.flushInteractiveUpdates;
+  }
 };
 
-function _classCallCheck(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
-  }
+function dispatchEvent(target, topLevelType, nativeEvent) {
+  var targetFiber = target;
+  batchedUpdates(function() {
+    runExtractedEventsInBatch(
+      topLevelType,
+      targetFiber,
+      nativeEvent,
+      nativeEvent.target
+    );
+  });
+  // React Native doesn't use ReactControlledComponent but if it did, here's
+  // where it would do it.
 }
 
-function _possibleConstructorReturn(self, call) {
-  if (!self) {
-    throw new ReferenceError(
-      "this hasn't been initialised - super() hasn't been called"
-    );
-  }
-  return call && (typeof call === "object" || typeof call === "function")
-    ? call
-    : self;
+// Renderers that don't support mutation
+// can re-export everything from this module.
+
+function shim() {
+  invariant(
+    false,
+    "The current renderer does not support mutation. " +
+      "This error is likely caused by a bug in React. " +
+      "Please file an issue."
+  );
 }
 
-function _inherits(subClass, superClass) {
-  if (typeof superClass !== "function" && superClass !== null) {
-    throw new TypeError(
-      "Super expression must either be null or a function, not " +
-        typeof superClass
-    );
+// Mutation (when unsupported)
+var supportsMutation = false;
+var appendChild$1 = shim;
+var appendChildToContainer = shim;
+var commitTextUpdate = shim;
+var commitMount = shim;
+var commitUpdate = shim;
+var insertBefore = shim;
+var insertInContainerBefore = shim;
+var removeChild = shim;
+var removeChildFromContainer = shim;
+var resetTextContent = shim;
+
+// Renderers that don't support hydration
+// can re-export everything from this module.
+
+function shim$1() {
+  invariant(
+    false,
+    "The current renderer does not support hyration. " +
+      "This error is likely caused by a bug in React. " +
+      "Please file an issue."
+  );
+}
+
+// Hydration (when unsupported)
+var supportsHydration = false;
+var canHydrateInstance = shim$1;
+var canHydrateTextInstance = shim$1;
+var getNextHydratableSibling = shim$1;
+var getFirstHydratableChild = shim$1;
+var hydrateInstance = shim$1;
+var hydrateTextInstance = shim$1;
+var didNotMatchHydratedContainerTextInstance = shim$1;
+var didNotMatchHydratedTextInstance = shim$1;
+var didNotHydrateContainerInstance = shim$1;
+var didNotHydrateInstance = shim$1;
+var didNotFindHydratableContainerInstance = shim$1;
+var didNotFindHydratableContainerTextInstance = shim$1;
+var didNotFindHydratableInstance = shim$1;
+var didNotFindHydratableTextInstance = shim$1;
+
+function _classCallCheck(instance, Constructor) {
+  if (!(instance instanceof Constructor)) {
+    throw new TypeError("Cannot call a class as a function");
   }
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: false,
-      writable: true,
-      configurable: true
-    }
-  });
-  if (superClass)
-    Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass);
 }
 
 // Modules provided by RN:
-var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
+// Counter for uniquely identifying views.
+// % 10 === 1 means it is a rootTag.
+// % 2 === 0 means it is a Fabric tag.
+// This means that they never overlap.
+var nextReactTag = 2;
+
+// TODO: Remove this conditional once all changes have propagated.
+if (FabricUIManager.registerEventHandler) {
   /**
-   * Superclass that provides methods to access the underlying native component.
-   * This can be useful when you want to focus a view or measure its dimensions.
-   *
-   * Methods implemented by this class are available on most default components
-   * provided by React Native. However, they are *not* available on composite
-   * components that are not directly backed by a native view. For more
-   * information, see [Direct Manipulation](docs/direct-manipulation.html).
-   *
-   * @abstract
+   * Register the event emitter with the native bridge
    */
-  var ReactNativeComponent = (function(_React$Component) {
-    _inherits(ReactNativeComponent, _React$Component);
+  FabricUIManager.registerEventHandler(dispatchEvent);
+}
 
-    function ReactNativeComponent() {
-      _classCallCheck(this, ReactNativeComponent);
+/**
+ * This is used for refs on host components.
+ */
 
-      return _possibleConstructorReturn(
-        this,
-        _React$Component.apply(this, arguments)
-      );
-    }
+var ReactFabricHostComponent = (function() {
+  function ReactFabricHostComponent(tag, viewConfig, props) {
+    _classCallCheck(this, ReactFabricHostComponent);
 
-    /**
-     * Removes focus. This is the opposite of `focus()`.
-     */
+    this._nativeTag = tag;
+    this.viewConfig = viewConfig;
+    this.currentProps = props;
+  }
 
-    /**
-     * Due to bugs in Flow's handling of React.createClass, some fields already
-     * declared in the base class need to be redeclared below.
-     */
-    ReactNativeComponent.prototype.blur = function blur() {
-      TextInputState.blurTextInput(findNodeHandle(this));
-    };
+  ReactFabricHostComponent.prototype.blur = function blur() {
+    TextInputState.blurTextInput(this._nativeTag);
+  };
 
-    /**
-     * Requests focus. The exact behavior depends on the platform and view.
-     */
+  ReactFabricHostComponent.prototype.focus = function focus() {
+    TextInputState.focusTextInput(this._nativeTag);
+  };
 
-    ReactNativeComponent.prototype.focus = function focus() {
-      TextInputState.focusTextInput(findNodeHandle(this));
-    };
+  ReactFabricHostComponent.prototype.measure = function measure(callback) {
+    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+  };
 
-    /**
-     * Measures the on-screen location and dimensions. If successful, the callback
-     * will be called asynchronously with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *  - pageX
-     *  - pageY
-     *
-     * These values are not available until after natives rendering completes. If
-     * you need the measurements as soon as possible, consider using the
-     * [`onLayout` prop](docs/view.html#onlayout) instead.
-     */
+  ReactFabricHostComponent.prototype.measureInWindow = function measureInWindow(
+    callback
+  ) {
+    UIManager.measureInWindow(
+      this._nativeTag,
+      mountSafeCallback(this, callback)
+    );
+  };
 
-    ReactNativeComponent.prototype.measure = function measure(callback) {
-      UIManager.measure(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    };
+  ReactFabricHostComponent.prototype.measureLayout = function measureLayout(
+    relativeToNativeNode,
+    onSuccess,
+    onFail /* currently unused */
+  ) {
+    UIManager.measureLayout(
+      this._nativeTag,
+      relativeToNativeNode,
+      mountSafeCallback(this, onFail),
+      mountSafeCallback(this, onSuccess)
+    );
+  };
 
-    /**
-     * Measures the on-screen location and dimensions. Even if the React Native
-     * root view is embedded within another native view, this method will give you
-     * the absolute coordinates measured from the window. If successful, the
-     * callback will be called asynchronously with the following arguments:
-     *
-     *  - x
-     *  - y
-     *  - width
-     *  - height
-     *
-     * These values are not available until after natives rendering completes.
-     */
-
-    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
-      callback
-    ) {
-      UIManager.measureInWindow(
-        findNodeHandle(this),
-        mountSafeCallback(this, callback)
-      );
-    };
+  ReactFabricHostComponent.prototype.setNativeProps = function setNativeProps(
+    nativeProps
+  ) {
+    {
+      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
+    }
 
-    /**
-     * Similar to [`measure()`](#measure), but the resulting location will be
-     * relative to the supplied ancestor's location.
-     *
-     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
-     */
+    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
 
-    ReactNativeComponent.prototype.measureLayout = function measureLayout(
-      relativeToNativeNode,
-      onSuccess,
-      onFail /* currently unused */
-    ) {
-      UIManager.measureLayout(
-        findNodeHandle(this),
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
+    // Avoid the overhead of bridge calls if there's no update.
+    // This is an expensive no-op for Android, and causes an unnecessary
+    // view invalidation for certain components (eg RCTTextInput) on iOS.
+    if (updatePayload != null) {
+      UIManager.updateView(
+        this._nativeTag,
+        this.viewConfig.uiViewClassName,
+        updatePayload
       );
-    };
+    }
+  };
 
-    /**
-     * This function sends props straight to native. They will not participate in
-     * future diff process - this means that if you do not include them in the
-     * next render, they will remain active (see [Direct
-     * Manipulation](docs/direct-manipulation.html)).
-     */
+  return ReactFabricHostComponent;
+})();
 
-    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
-      nativeProps
-    ) {
-      // Class components don't have viewConfig -> validateAttributes.
-      // Nor does it make sense to set native props on a non-native component.
-      // Instead, find the nearest host component and set props on it.
-      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
-      // We want the instance/wrapper (not the native tag).
-      var maybeInstance = void 0;
+function appendInitialChild(parentInstance, child) {
+  FabricUIManager.appendChild(parentInstance.node, child.node);
+}
 
-      // Fiber errors if findNodeHandle is called for an umounted component.
-      // Tests using ReactTestRenderer will trigger this case indirectly.
-      // Mimicking stack behavior, we should silently ignore this case.
-      // TODO Fix ReactTestRenderer so we can remove this try/catch.
-      try {
-        maybeInstance = findHostInstance(this);
-      } catch (error) {}
+function createInstance(
+  type,
+  props,
+  rootContainerInstance,
+  hostContext,
+  internalInstanceHandle
+) {
+  var tag = nextReactTag;
+  nextReactTag += 2;
 
-      // If there is no host component beneath this we should fail silently.
-      // This is not an error; it could mean a class component rendered null.
-      if (maybeInstance == null) {
-        return;
+  var viewConfig = ReactNativeViewConfigRegistry.get(type);
+
+  {
+    for (var key in viewConfig.validAttributes) {
+      if (props.hasOwnProperty(key)) {
+        deepFreezeAndThrowOnMutationInDev(props[key]);
       }
+    }
+  }
 
-      var viewConfig =
-        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+  invariant(
+    type !== "RCTView" || !hostContext.isInAParentText,
+    "Nesting of <View> within <Text> is not currently supported."
+  );
 
-      var updatePayload = create(nativeProps, viewConfig.validAttributes);
+  var updatePayload = create(props, viewConfig.validAttributes);
 
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          maybeInstance._nativeTag,
-          viewConfig.uiViewClassName,
-          updatePayload
-        );
-      }
-    };
+  var node = FabricUIManager.createNode(
+    tag, // reactTag
+    viewConfig.uiViewClassName, // viewName
+    rootContainerInstance, // rootTag
+    updatePayload, // props
+    internalInstanceHandle // internalInstanceHandle
+  );
 
-    return ReactNativeComponent;
-  })(React.Component);
+  var component = new ReactFabricHostComponent(tag, viewConfig, props);
 
-  // eslint-disable-next-line no-unused-expressions
+  return {
+    node: node,
+    canonical: component
+  };
+}
 
-  return ReactNativeComponent;
-};
+function createTextInstance(
+  text,
+  rootContainerInstance,
+  hostContext,
+  internalInstanceHandle
+) {
+  invariant(
+    hostContext.isInAParentText,
+    "Text strings must be rendered within a <Text> component."
+  );
 
-/**
- * `ReactInstanceMap` maintains a mapping from a public facing stateful
- * instance (key) and the internal representation (value). This allows public
- * methods to accept the user facing instance as an argument and map them back
- * to internal methods.
- *
- * Note that this module is currently shared and assumed to be stateless.
- * If this becomes an actual Map, that will break.
- */
+  var tag = nextReactTag;
+  nextReactTag += 2;
 
-/**
- * This API should be called `delete` but we'd have to make sure to always
- * transform these to strings for IE support. When this transform is fully
- * supported we can rename it.
- */
+  var node = FabricUIManager.createNode(
+    tag, // reactTag
+    "RCTRawText", // viewName
+    rootContainerInstance, // rootTag
+    { text: text }, // props
+    internalInstanceHandle // instance handle
+  );
 
-function get$1(key) {
-  return key._reactInternalFiber;
+  return {
+    node: node
+  };
 }
 
-function set(key, value) {
-  key._reactInternalFiber = value;
+function finalizeInitialChildren(
+  parentInstance,
+  type,
+  props,
+  rootContainerInstance,
+  hostContext
+) {
+  return false;
 }
 
-var ReactInternals = React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED;
-
-var ReactCurrentOwner = ReactInternals.ReactCurrentOwner;
-var ReactDebugCurrentFrame = ReactInternals.ReactDebugCurrentFrame;
+function getRootHostContext(rootContainerInstance) {
+  return { isInAParentText: false };
+}
 
-function getComponentName(fiber) {
-  var type = fiber.type;
+function getChildHostContext(parentHostContext, type, rootContainerInstance) {
+  var prevIsInAParentText = parentHostContext.isInAParentText;
+  var isInAParentText =
+    type === "AndroidTextInput" || // Android
+    type === "RCTMultilineTextInputView" || // iOS
+    type === "RCTSinglelineTextInputView" || // iOS
+    type === "RCTText" ||
+    type === "RCTVirtualText";
 
-  if (typeof type === "function") {
-    return type.displayName || type.name;
-  }
-  if (typeof type === "string") {
-    return type;
-  }
-  switch (type) {
-    case REACT_ASYNC_MODE_TYPE:
-      return "AsyncMode";
-    case REACT_CONTEXT_TYPE:
-      return "Context.Consumer";
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_PROFILER_TYPE:
-      return "Profiler(" + fiber.pendingProps.id + ")";
-    case REACT_PROVIDER_TYPE:
-      return "Context.Provider";
-    case REACT_STRICT_MODE_TYPE:
-      return "StrictMode";
-  }
-  if (typeof type === "object" && type !== null) {
-    switch (type.$$typeof) {
-      case REACT_FORWARD_REF_TYPE:
-        var functionName = type.render.displayName || type.render.name || "";
-        return functionName !== ""
-          ? "ForwardRef(" + functionName + ")"
-          : "ForwardRef";
-    }
+  if (prevIsInAParentText !== isInAParentText) {
+    return { isInAParentText: isInAParentText };
+  } else {
+    return parentHostContext;
   }
-  return null;
 }
 
-// Don't change these two values. They're used by React Dev Tools.
-var NoEffect = /*              */ 0;
-var PerformedWork = /*         */ 1;
+function getPublicInstance(instance) {
+  return instance.canonical;
+}
 
-// You can change the rest (and add more).
-var Placement = /*             */ 2;
-var Update = /*                */ 4;
-var PlacementAndUpdate = /*    */ 6;
-var Deletion = /*              */ 8;
-var ContentReset = /*          */ 16;
-var Callback = /*              */ 32;
-var DidCapture = /*            */ 64;
-var Ref = /*                   */ 128;
-var Snapshot = /*              */ 256;
+function prepareForCommit(containerInfo) {
+  // Noop
+}
 
-// Union of all host effects
-var HostEffectMask = /*        */ 511;
+function prepareUpdate(
+  instance,
+  type,
+  oldProps,
+  newProps,
+  rootContainerInstance,
+  hostContext
+) {
+  var viewConfig = instance.canonical.viewConfig;
+  var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
+  // TODO: If the event handlers have changed, we need to update the current props
+  // in the commit phase but there is no host config hook to do it yet.
+  // So instead we hack it by updating it in the render phase.
+  instance.canonical.currentProps = newProps;
+  return updatePayload;
+}
 
-var Incomplete = /*            */ 512;
-var ShouldCapture = /*         */ 1024;
+function resetAfterCommit(containerInfo) {
+  // Noop
+}
 
-var MOUNTING = 1;
-var MOUNTED = 2;
-var UNMOUNTED = 3;
+function shouldDeprioritizeSubtree(type, props) {
+  return false;
+}
 
-function isFiberMountedImpl(fiber) {
-  var node = fiber;
-  if (!fiber.alternate) {
-    // If there is no alternate, this might be a new tree that isn't inserted
-    // yet. If it is, then it will have a pending insertion effect on it.
-    if ((node.effectTag & Placement) !== NoEffect) {
-      return MOUNTING;
-    }
-    while (node.return) {
-      node = node.return;
-      if ((node.effectTag & Placement) !== NoEffect) {
-        return MOUNTING;
-      }
+function shouldSetTextContent(type, props) {
+  // TODO (bvaughn) Revisit this decision.
+  // Always returning false simplifies the createInstance() implementation,
+  // But creates an additional child Fiber for raw text children.
+  // No additional native views are created though.
+  // It's not clear to me which is better so I'm deferring for now.
+  // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
+  return false;
+}
+
+// The Fabric renderer is secondary to the existing React Native renderer.
+var isPrimaryRenderer = false;
+var now = now$1;
+var scheduleDeferredCallback = scheduleDeferredCallback$1;
+var cancelDeferredCallback = cancelDeferredCallback$1;
+
+// -------------------
+//     Persistence
+// -------------------
+
+var supportsPersistence = true;
+
+function cloneInstance(
+  instance,
+  updatePayload,
+  type,
+  oldProps,
+  newProps,
+  internalInstanceHandle,
+  keepChildren,
+  recyclableInstance
+) {
+  var node = instance.node;
+  var clone = void 0;
+  if (keepChildren) {
+    if (updatePayload !== null) {
+      clone = FabricUIManager.cloneNodeWithNewProps(
+        node,
+        updatePayload,
+        internalInstanceHandle
+      );
+    } else {
+      clone = FabricUIManager.cloneNode(node, internalInstanceHandle);
     }
   } else {
-    while (node.return) {
-      node = node.return;
+    if (updatePayload !== null) {
+      clone = FabricUIManager.cloneNodeWithNewChildrenAndProps(
+        node,
+        updatePayload,
+        internalInstanceHandle
+      );
+    } else {
+      clone = FabricUIManager.cloneNodeWithNewChildren(
+        node,
+        internalInstanceHandle
+      );
     }
   }
-  if (node.tag === HostRoot) {
-    // TODO: Check if this was a nested HostRoot when used with
-    // renderContainerIntoSubtree.
-    return MOUNTED;
-  }
-  // If we didn't hit the root, that means that we're in an disconnected tree
-  // that has been unmounted.
-  return UNMOUNTED;
+  return {
+    node: clone,
+    canonical: instance.canonical
+  };
 }
 
-function isFiberMounted(fiber) {
-  return isFiberMountedImpl(fiber) === MOUNTED;
+function createContainerChildSet(container) {
+  return FabricUIManager.createChildSet(container);
 }
 
-function isMounted(component) {
-  {
-    var owner = ReactCurrentOwner.current;
-    if (owner !== null && owner.tag === ClassComponent) {
-      var ownerFiber = owner;
-      var instance = ownerFiber.stateNode;
-      !instance._warnedAboutRefsInRender
-        ? warning(
-            false,
-            "%s is accessing isMounted inside its render() function. " +
-              "render() should be a pure function of props and state. It should " +
-              "never access something that requires stale data from the previous " +
-              "render, such as refs. Move this logic to componentDidMount and " +
-              "componentDidUpdate instead.",
-            getComponentName(ownerFiber) || "A component"
-          )
-        : void 0;
-      instance._warnedAboutRefsInRender = true;
-    }
-  }
+function appendChildToContainerChildSet(childSet, child) {
+  FabricUIManager.appendChildToSet(childSet, child.node);
+}
 
-  var fiber = get$1(component);
-  if (!fiber) {
-    return false;
-  }
-  return isFiberMountedImpl(fiber) === MOUNTED;
+function finalizeContainerChildren(container, newChildren) {
+  FabricUIManager.completeRoot(container, newChildren);
 }
 
-function assertIsMounted(fiber) {
-  invariant(
-    isFiberMountedImpl(fiber) === MOUNTED,
-    "Unable to find node on an unmounted component."
+var describeComponentFrame = function(name, source, ownerName) {
+  return (
+    "\n    in " +
+    (name || "Unknown") +
+    (source
+      ? " (at " +
+        source.fileName.replace(/^.*[\\\/]/, "") +
+        ":" +
+        source.lineNumber +
+        ")"
+      : ownerName ? " (created by " + ownerName + ")" : "")
   );
+};
+
+function describeFiber(fiber) {
+  switch (fiber.tag) {
+    case IndeterminateComponent:
+    case FunctionalComponent:
+    case ClassComponent:
+    case HostComponent:
+      var owner = fiber._debugOwner;
+      var source = fiber._debugSource;
+      var name = getComponentName(fiber);
+      var ownerName = null;
+      if (owner) {
+        ownerName = getComponentName(owner);
+      }
+      return describeComponentFrame(name, source, ownerName);
+    default:
+      return "";
+  }
 }
 
-function findCurrentFiberUsingSlowPath(fiber) {
-  var alternate = fiber.alternate;
-  if (!alternate) {
-    // If there is no alternate, then we only need to check if it is mounted.
-    var state = isFiberMountedImpl(fiber);
-    invariant(
-      state !== UNMOUNTED,
-      "Unable to find node on an unmounted component."
-    );
-    if (state === MOUNTING) {
+// This function can only be called with a work-in-progress fiber and
+// only during begin or complete phase. Do not call it under any other
+// circumstances.
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  var node = workInProgress;
+  do {
+    info += describeFiber(node);
+    // Otherwise this return pointer might point to the wrong tree:
+    node = node.return;
+  } while (node);
+  return info;
+}
+
+function getCurrentFiberOwnerName() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
       return null;
     }
-    return fiber;
-  }
-  // If we have two possible branches, we'll walk backwards up to the root
-  // to see what path the root points to. On the way we may hit one of the
-  // special cases and we'll deal with them.
-  var a = fiber;
-  var b = alternate;
-  while (true) {
-    var parentA = a.return;
-    var parentB = parentA ? parentA.alternate : null;
-    if (!parentA || !parentB) {
-      // We're at the root.
-      break;
+    var owner = fiber._debugOwner;
+    if (owner !== null && typeof owner !== "undefined") {
+      return getComponentName(owner);
     }
+  }
+  return null;
+}
 
-    // If both copies of the parent fiber point to the same child, we can
-    // assume that the child is current. This happens when we bailout on low
-    // priority: the bailed out fiber's child reuses the current child.
-    if (parentA.child === parentB.child) {
-      var child = parentA.child;
-      while (child) {
-        if (child === a) {
-          // We've determined that A is the current branch.
-          assertIsMounted(parentA);
-          return fiber;
-        }
-        if (child === b) {
-          // We've determined that B is the current branch.
-          assertIsMounted(parentA);
-          return alternate;
-        }
-        child = child.sibling;
-      }
-      // We should never have an alternate for any mounting node. So the only
-      // way this could possibly happen is if this was unmounted, if at all.
-      invariant(false, "Unable to find node on an unmounted component.");
+function getCurrentFiberStackAddendum() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
     }
+    // Safe because if current fiber exists, we are reconciling,
+    // and it is guaranteed to be the work-in-progress version.
+    return getStackAddendumByWorkInProgressFiber(fiber);
+  }
+  return null;
+}
 
-    if (a.return !== b.return) {
-      // The return pointer of A and the return pointer of B point to different
-      // fibers. We assume that return pointers never criss-cross, so A must
-      // belong to the child set of A.return, and B must belong to the child
-      // set of B.return.
-      a = parentA;
-      b = parentB;
-    } else {
-      // The return pointers point to the same fiber. We'll have to use the
-      // default, slow path: scan the child sets of each parent alternate to see
-      // which child belongs to which set.
-      //
-      // Search parent A's child set
-      var didFindChild = false;
-      var _child = parentA.child;
-      while (_child) {
-        if (_child === a) {
-          didFindChild = true;
-          a = parentA;
-          b = parentB;
-          break;
-        }
-        if (_child === b) {
-          didFindChild = true;
-          b = parentA;
-          a = parentB;
-          break;
-        }
-        _child = _child.sibling;
-      }
-      if (!didFindChild) {
-        // Search parent B's child set
-        _child = parentB.child;
-        while (_child) {
-          if (_child === a) {
-            didFindChild = true;
-            a = parentB;
-            b = parentA;
-            break;
-          }
-          if (_child === b) {
-            didFindChild = true;
-            b = parentB;
-            a = parentA;
-            break;
-          }
-          _child = _child.sibling;
-        }
-        invariant(
-          didFindChild,
-          "Child was not found in either parent set. This indicates a bug " +
-            "in React related to the return pointer. Please file an issue."
-        );
-      }
-    }
+function resetCurrentFiber() {
+  ReactDebugCurrentFrame.getCurrentStack = null;
+  ReactDebugCurrentFiber.current = null;
+  ReactDebugCurrentFiber.phase = null;
+}
 
-    invariant(
-      a.alternate === b,
-      "Return fibers should always be each others' alternates. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
+function setCurrentFiber(fiber) {
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
+  ReactDebugCurrentFiber.current = fiber;
+  ReactDebugCurrentFiber.phase = null;
+}
+
+function setCurrentPhase(phase) {
+  ReactDebugCurrentFiber.phase = phase;
+}
+
+var ReactDebugCurrentFiber = {
+  current: null,
+  phase: null,
+  resetCurrentFiber: resetCurrentFiber,
+  setCurrentFiber: setCurrentFiber,
+  setCurrentPhase: setCurrentPhase,
+  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
+};
+
+var debugRenderPhaseSideEffects = false;
+var debugRenderPhaseSideEffectsForStrictMode = false;
+var enableUserTimingAPI = true;
+var enableGetDerivedStateFromCatch = false;
+var enableSuspense = false;
+var warnAboutDeprecatedLifecycles = false;
+var warnAboutLegacyContextAPI = false;
+var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
+var enableProfilerTimer = true;
+
+// Only used in www builds.
+
+// Prefix measurements so that it's possible to filter them.
+// Longer prefixes are hard to read in DevTools.
+var reactEmoji = "\u269B";
+var warningEmoji = "\u26D4";
+var supportsUserTiming =
+  typeof performance !== "undefined" &&
+  typeof performance.mark === "function" &&
+  typeof performance.clearMarks === "function" &&
+  typeof performance.measure === "function" &&
+  typeof performance.clearMeasures === "function";
+
+// Keep track of current fiber so that we know the path to unwind on pause.
+// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
+var currentFiber = null;
+// If we're in the middle of user code, which fiber and method is it?
+// Reusing `currentFiber` would be confusing for this because user code fiber
+// can change during commit phase too, but we don't need to unwind it (since
+// lifecycles in the commit phase don't resemble a tree).
+var currentPhase = null;
+var currentPhaseFiber = null;
+// Did lifecycle hook schedule an update? This is often a performance problem,
+// so we will keep track of it, and include it in the report.
+// Track commits caused by cascading updates.
+var isCommitting = false;
+var hasScheduledUpdateInCurrentCommit = false;
+var hasScheduledUpdateInCurrentPhase = false;
+var commitCountInCurrentWorkLoop = 0;
+var effectCountInCurrentCommit = 0;
+var isWaitingForCallback = false;
+// During commits, we only show a measurement once per method name
+// to avoid stretch the commit phase with measurement overhead.
+var labelsInCurrentCommit = new Set();
+
+var formatMarkName = function(markName) {
+  return reactEmoji + " " + markName;
+};
+
+var formatLabel = function(label, warning$$1) {
+  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
+  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
+  return "" + prefix + label + suffix;
+};
+
+var beginMark = function(markName) {
+  performance.mark(formatMarkName(markName));
+};
+
+var clearMark = function(markName) {
+  performance.clearMarks(formatMarkName(markName));
+};
+
+var endMark = function(label, markName, warning$$1) {
+  var formattedMarkName = formatMarkName(markName);
+  var formattedLabel = formatLabel(label, warning$$1);
+  try {
+    performance.measure(formattedLabel, formattedMarkName);
+  } catch (err) {}
+  // If previous mark was missing for some reason, this will throw.
+  // This could only happen if React crashed in an unexpected place earlier.
+  // Don't pile on with more errors.
+
+  // Clear marks immediately to avoid growing buffer.
+  performance.clearMarks(formattedMarkName);
+  performance.clearMeasures(formattedLabel);
+};
+
+var getFiberMarkName = function(label, debugID) {
+  return label + " (#" + debugID + ")";
+};
+
+var getFiberLabel = function(componentName, isMounted, phase) {
+  if (phase === null) {
+    // These are composite component total time measurements.
+    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
+  } else {
+    // Composite component methods.
+    return componentName + "." + phase;
   }
-  // If the root is not a host container, we're in a disconnected tree. I.e.
-  // unmounted.
-  invariant(
-    a.tag === HostRoot,
-    "Unable to find node on an unmounted component."
-  );
-  if (a.stateNode.current === a) {
-    // We've determined that A is the current branch.
-    return fiber;
+};
+
+var beginFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+
+  if (isCommitting && labelsInCurrentCommit.has(label)) {
+    // During the commit phase, we don't show duplicate labels because
+    // there is a fixed overhead for every measurement, and we don't
+    // want to stretch the commit phase beyond necessary.
+    return false;
   }
-  // Otherwise B has to be current branch.
-  return alternate;
-}
+  labelsInCurrentCommit.add(label);
 
-function findCurrentHostFiber(parent) {
-  var currentParent = findCurrentFiberUsingSlowPath(parent);
-  if (!currentParent) {
-    return null;
+  var markName = getFiberMarkName(label, debugID);
+  beginMark(markName);
+  return true;
+};
+
+var clearFiberMark = function(fiber, phase) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  clearMark(markName);
+};
+
+var endFiberMark = function(fiber, phase, warning$$1) {
+  var componentName = getComponentName(fiber) || "Unknown";
+  var debugID = fiber._debugID;
+  var isMounted = fiber.alternate !== null;
+  var label = getFiberLabel(componentName, isMounted, phase);
+  var markName = getFiberMarkName(label, debugID);
+  endMark(label, markName, warning$$1);
+};
+
+var shouldIgnoreFiber = function(fiber) {
+  // Host components should be skipped in the timeline.
+  // We could check typeof fiber.type, but does this work with RN?
+  switch (fiber.tag) {
+    case HostRoot:
+    case HostComponent:
+    case HostText:
+    case HostPortal:
+    case Fragment:
+    case ContextProvider:
+    case ContextConsumer:
+    case Mode:
+      return true;
+    default:
+      return false;
+  }
+};
+
+var clearPendingPhaseMeasurement = function() {
+  if (currentPhase !== null && currentPhaseFiber !== null) {
+    clearFiberMark(currentPhaseFiber, currentPhase);
+  }
+  currentPhaseFiber = null;
+  currentPhase = null;
+  hasScheduledUpdateInCurrentPhase = false;
+};
+
+var pauseTimers = function() {
+  // Stops all currently active measurements so that they can be resumed
+  // if we continue in a later deferred loop from the same unit of work.
+  var fiber = currentFiber;
+  while (fiber) {
+    if (fiber._debugIsCurrentlyTiming) {
+      endFiberMark(fiber, null, null);
+    }
+    fiber = fiber.return;
+  }
+};
+
+var resumeTimersRecursively = function(fiber) {
+  if (fiber.return !== null) {
+    resumeTimersRecursively(fiber.return);
+  }
+  if (fiber._debugIsCurrentlyTiming) {
+    beginFiberMark(fiber, null);
   }
+};
 
-  // Next we'll drill down this component to find the first HostComponent/Text.
-  var node = currentParent;
-  while (true) {
-    if (node.tag === HostComponent || node.tag === HostText) {
-      return node;
-    } else if (node.child) {
-      node.child.return = node;
-      node = node.child;
-      continue;
-    }
-    if (node === currentParent) {
-      return null;
-    }
-    while (!node.sibling) {
-      if (!node.return || node.return === currentParent) {
-        return null;
-      }
-      node = node.return;
-    }
-    node.sibling.return = node.return;
-    node = node.sibling;
+var resumeTimers = function() {
+  // Resumes all measurements that were active during the last deferred loop.
+  if (currentFiber !== null) {
+    resumeTimersRecursively(currentFiber);
   }
-  // Flow needs the return null here, but ESLint complains about it.
-  // eslint-disable-next-line no-unreachable
-  return null;
-}
+};
 
-function findCurrentHostFiberWithNoPortals(parent) {
-  var currentParent = findCurrentFiberUsingSlowPath(parent);
-  if (!currentParent) {
-    return null;
+function recordEffect() {
+  if (enableUserTimingAPI) {
+    effectCountInCurrentCommit++;
   }
+}
 
-  // Next we'll drill down this component to find the first HostComponent/Text.
-  var node = currentParent;
-  while (true) {
-    if (node.tag === HostComponent || node.tag === HostText) {
-      return node;
-    } else if (node.child && node.tag !== HostPortal) {
-      node.child.return = node;
-      node = node.child;
-      continue;
-    }
-    if (node === currentParent) {
-      return null;
+function recordScheduleUpdate() {
+  if (enableUserTimingAPI) {
+    if (isCommitting) {
+      hasScheduledUpdateInCurrentCommit = true;
     }
-    while (!node.sibling) {
-      if (!node.return || node.return === currentParent) {
-        return null;
-      }
-      node = node.return;
+    if (
+      currentPhase !== null &&
+      currentPhase !== "componentWillMount" &&
+      currentPhase !== "componentWillReceiveProps"
+    ) {
+      hasScheduledUpdateInCurrentPhase = true;
     }
-    node.sibling.return = node.return;
-    node = node.sibling;
   }
-  // Flow needs the return null here, but ESLint complains about it.
-  // eslint-disable-next-line no-unreachable
-  return null;
 }
 
-var debugRenderPhaseSideEffects = false;
-var debugRenderPhaseSideEffectsForStrictMode = false;
-var enableUserTimingAPI = true;
-var enableGetDerivedStateFromCatch = false;
-var enableSuspense = false;
-var warnAboutDeprecatedLifecycles = false;
-var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
-var enableProfilerTimer = false;
-
-// React Fabric uses persistent reconciler.
-var enableMutatingReconciler = false;
-var enableNoopReconciler = false;
-var enablePersistentReconciler = true;
-var fireGetDerivedStateFromPropsOnStateUpdates = true;
-
-// Only used in www builds.
-
-// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
-// Math.pow(2, 30) - 1
-// 0b111111111111111111111111111111
-var MAX_SIGNED_31_BIT_INT = 1073741823;
-
-// TODO: Use an opaque type once ESLint et al support the syntax
-
-var NoWork = 0;
-var Sync = 1;
-var Never = MAX_SIGNED_31_BIT_INT;
-
-var UNIT_SIZE = 10;
-var MAGIC_NUMBER_OFFSET = 2;
-
-// 1 unit of expiration time represents 10ms.
-function msToExpirationTime(ms) {
-  // Always add an offset so that we don't clash with the magic number for NoWork.
-  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
+function startRequestCallbackTimer() {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming && !isWaitingForCallback) {
+      isWaitingForCallback = true;
+      beginMark("(Waiting for async callback...)");
+    }
+  }
 }
 
-function expirationTimeToMs(expirationTime) {
-  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
+function stopRequestCallbackTimer(didExpire, expirationTime) {
+  if (enableUserTimingAPI) {
+    if (supportsUserTiming) {
+      isWaitingForCallback = false;
+      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
+      endMark(
+        "(Waiting for async callback... will force flush in " +
+          expirationTime +
+          " ms)",
+        "(Waiting for async callback...)",
+        warning$$1
+      );
+    }
+  }
 }
 
-function ceiling(num, precision) {
-  return (((num / precision) | 0) + 1) * precision;
+function startWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, this is the fiber to unwind from.
+    currentFiber = fiber;
+    if (!beginFiberMark(fiber, null)) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = true;
+  }
 }
 
-function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
-  return (
-    MAGIC_NUMBER_OFFSET +
-    ceiling(
-      currentTime - MAGIC_NUMBER_OFFSET + expirationInMs / UNIT_SIZE,
-      bucketSizeMs / UNIT_SIZE
-    )
-  );
+function cancelWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // Remember we shouldn't complete measurement for this fiber.
+    // Otherwise flamechart will be deep even for small updates.
+    fiber._debugIsCurrentlyTiming = false;
+    clearFiberMark(fiber, null);
+  }
 }
 
-var NoContext = 0;
-var AsyncMode = 1;
-var StrictMode = 2;
-var ProfileMode = 4;
-
-var hasBadMapPolyfill = void 0;
-
-{
-  hasBadMapPolyfill = false;
-  try {
-    var nonExtensibleObject = Object.preventExtensions({});
-    var testMap = new Map([[nonExtensibleObject, null]]);
-    var testSet = new Set([nonExtensibleObject]);
-    // This is necessary for Rollup to not consider these unused.
-    // https://github.com/rollup/rollup/issues/1771
-    // TODO: we can remove these if Rollup fixes the bug.
-    testMap.set(0, 0);
-    testSet.add(0);
-  } catch (e) {
-    // TODO: Consider warning about bad polyfills
-    hasBadMapPolyfill = true;
+function stopWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber.return;
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = false;
+    endFiberMark(fiber, null, null);
   }
 }
 
-// A Fiber is work on a Component that needs to be done or was done. There can
-// be more than one per component.
-
-var debugCounter = void 0;
-
-{
-  debugCounter = 1;
+function stopFailedWorkTimer(fiber) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
+      return;
+    }
+    // If we pause, its parent is the fiber to unwind from.
+    currentFiber = fiber.return;
+    if (!fiber._debugIsCurrentlyTiming) {
+      return;
+    }
+    fiber._debugIsCurrentlyTiming = false;
+    var warning$$1 = "An error was thrown inside this error boundary";
+    endFiberMark(fiber, null, warning$$1);
+  }
 }
 
-function FiberNode(tag, pendingProps, key, mode) {
-  // Instance
-  this.tag = tag;
-  this.key = key;
-  this.type = null;
-  this.stateNode = null;
-
-  // Fiber
-  this.return = null;
-  this.child = null;
-  this.sibling = null;
-  this.index = 0;
-
-  this.ref = null;
-
-  this.pendingProps = pendingProps;
-  this.memoizedProps = null;
-  this.updateQueue = null;
-  this.memoizedState = null;
-
-  this.mode = mode;
-
-  // Effects
-  this.effectTag = NoEffect;
-  this.nextEffect = null;
-
-  this.firstEffect = null;
-  this.lastEffect = null;
-
-  this.expirationTime = NoWork;
-
-  this.alternate = null;
-
-  if (enableProfilerTimer) {
-    this.selfBaseTime = 0;
-    this.treeBaseTime = 0;
+function startPhaseTimer(fiber, phase) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    clearPendingPhaseMeasurement();
+    if (!beginFiberMark(fiber, phase)) {
+      return;
+    }
+    currentPhaseFiber = fiber;
+    currentPhase = phase;
   }
+}
 
-  {
-    this._debugID = debugCounter++;
-    this._debugSource = null;
-    this._debugOwner = null;
-    this._debugIsCurrentlyTiming = false;
-    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
-      Object.preventExtensions(this);
+function stopPhaseTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
+    if (currentPhase !== null && currentPhaseFiber !== null) {
+      var warning$$1 = hasScheduledUpdateInCurrentPhase
+        ? "Scheduled a cascading update"
+        : null;
+      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
+    }
+    currentPhase = null;
+    currentPhaseFiber = null;
   }
 }
 
-// This is a constructor function, rather than a POJO constructor, still
-// please ensure we do the following:
-// 1) Nobody should add any instance methods on this. Instance methods can be
-//    more difficult to predict when they get optimized and they are almost
-//    never inlined properly in static compilers.
-// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
-//    always know when it is a fiber.
-// 3) We might want to experiment with using numeric keys since they are easier
-//    to optimize in a non-JIT environment.
-// 4) We can easily go from a constructor to a createFiber object literal if that
-//    is faster.
-// 5) It should be easy to port this to a C struct and keep a C implementation
-//    compatible.
-var createFiber = function(tag, pendingProps, key, mode) {
-  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
-  return new FiberNode(tag, pendingProps, key, mode);
-};
-
-function shouldConstruct(Component) {
-  return !!(Component.prototype && Component.prototype.isReactComponent);
+function startWorkLoopTimer(nextUnitOfWork) {
+  if (enableUserTimingAPI) {
+    currentFiber = nextUnitOfWork;
+    if (!supportsUserTiming) {
+      return;
+    }
+    commitCountInCurrentWorkLoop = 0;
+    // This is top level call.
+    // Any other measurements are performed within.
+    beginMark("(React Tree Reconciliation)");
+    // Resume any measurements that were in progress during the last loop.
+    resumeTimers();
+  }
 }
 
-// This is used to create an alternate fiber to do work on.
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  if (workInProgress === null) {
-    // We use a double buffering pooling technique because we know that we'll
-    // only ever need at most two versions of a tree. We pool the "other" unused
-    // node that we're free to reuse. This is lazily created to avoid allocating
-    // extra objects for things that are never updated. It also allow us to
-    // reclaim the extra memory if needed.
-    workInProgress = createFiber(
-      current.tag,
-      pendingProps,
-      current.key,
-      current.mode
-    );
-    workInProgress.type = current.type;
-    workInProgress.stateNode = current.stateNode;
-
-    {
-      // DEV-only fields
-      workInProgress._debugID = current._debugID;
-      workInProgress._debugSource = current._debugSource;
-      workInProgress._debugOwner = current._debugOwner;
+function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
+    var warning$$1 = null;
+    if (interruptedBy !== null) {
+      if (interruptedBy.tag === HostRoot) {
+        warning$$1 = "A top-level update interrupted the previous render";
+      } else {
+        var componentName = getComponentName(interruptedBy) || "Unknown";
+        warning$$1 =
+          "An update to " + componentName + " interrupted the previous render";
+      }
+    } else if (commitCountInCurrentWorkLoop > 1) {
+      warning$$1 = "There were cascading updates";
+    }
+    commitCountInCurrentWorkLoop = 0;
+    var label = didCompleteRoot
+      ? "(React Tree Reconciliation: Completed Root)"
+      : "(React Tree Reconciliation: Yielded)";
+    // Pause any measurements until the next loop.
+    pauseTimers();
+    endMark(label, "(React Tree Reconciliation)", warning$$1);
+  }
+}
 
-    workInProgress.alternate = current;
-    current.alternate = workInProgress;
-  } else {
-    workInProgress.pendingProps = pendingProps;
-
-    // We already have an alternate.
-    // Reset the effect tag.
-    workInProgress.effectTag = NoEffect;
-
-    // The effect list is no longer valid.
-    workInProgress.nextEffect = null;
-    workInProgress.firstEffect = null;
-    workInProgress.lastEffect = null;
+function startCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    isCommitting = true;
+    hasScheduledUpdateInCurrentCommit = false;
+    labelsInCurrentCommit.clear();
+    beginMark("(Committing Changes)");
   }
+}
 
-  workInProgress.expirationTime = expirationTime;
+function stopCommitTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
 
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
+    var warning$$1 = null;
+    if (hasScheduledUpdateInCurrentCommit) {
+      warning$$1 = "Lifecycle hook scheduled a cascading update";
+    } else if (commitCountInCurrentWorkLoop > 0) {
+      warning$$1 = "Caused by a cascading update in earlier commit";
+    }
+    hasScheduledUpdateInCurrentCommit = false;
+    commitCountInCurrentWorkLoop++;
+    isCommitting = false;
+    labelsInCurrentCommit.clear();
 
-  // These will be overridden during the parent's reconciliation
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
+    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
+  }
+}
 
-  if (enableProfilerTimer) {
-    workInProgress.selfBaseTime = current.selfBaseTime;
-    workInProgress.treeBaseTime = current.treeBaseTime;
+function startCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Snapshot Effects)");
   }
+}
 
-  return workInProgress;
+function stopCommitSnapshotEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Snapshot Effects: " + count + " Total)",
+      "(Committing Snapshot Effects)",
+      null
+    );
+  }
 }
 
-function createHostRootFiber(isAsync) {
-  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
-  return createFiber(HostRoot, null, null, mode);
+function startCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Committing Host Effects)");
+  }
 }
 
-function createFiberFromElement(element, mode, expirationTime) {
-  var owner = null;
-  {
-    owner = element._owner;
+function stopCommitHostEffectsTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Committing Host Effects: " + count + " Total)",
+      "(Committing Host Effects)",
+      null
+    );
   }
+}
 
-  var fiber = void 0;
-  var type = element.type;
-  var key = element.key;
-  var pendingProps = element.props;
+function startCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
+    }
+    effectCountInCurrentCommit = 0;
+    beginMark("(Calling Lifecycle Methods)");
+  }
+}
 
-  var fiberTag = void 0;
-  if (typeof type === "function") {
-    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
-  } else if (typeof type === "string") {
-    fiberTag = HostComponent;
-  } else {
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          pendingProps.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= AsyncMode | StrictMode;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= StrictMode;
-        break;
-      case REACT_PROFILER_TYPE:
-        return createFiberFromProfiler(pendingProps, mode, expirationTime, key);
-      case REACT_TIMEOUT_TYPE:
-        fiberTag = TimeoutComponent;
-        // Suspense does not require async, but its children should be strict
-        // mode compatible.
-        mode |= StrictMode;
-        break;
-      default:
-        fiberTag = getFiberTagFromObjectType(type, owner);
-        break;
+function stopCommitLifeCyclesTimer() {
+  if (enableUserTimingAPI) {
+    if (!supportsUserTiming) {
+      return;
     }
+    var count = effectCountInCurrentCommit;
+    effectCountInCurrentCommit = 0;
+    endMark(
+      "(Calling Lifecycle Methods: " + count + " Total)",
+      "(Calling Lifecycle Methods)",
+      null
+    );
   }
+}
 
-  fiber = createFiber(fiberTag, pendingProps, key, mode);
-  fiber.type = type;
-  fiber.expirationTime = expirationTime;
+var valueStack = [];
 
-  {
-    fiber._debugSource = element._source;
-    fiber._debugOwner = element._owner;
-  }
+var fiberStack = void 0;
 
-  return fiber;
+{
+  fiberStack = [];
 }
 
-function getFiberTagFromObjectType(type, owner) {
-  var $$typeof =
-    typeof type === "object" && type !== null ? type.$$typeof : null;
+var index = -1;
 
-  switch ($$typeof) {
-    case REACT_PROVIDER_TYPE:
-      return ContextProvider;
-    case REACT_CONTEXT_TYPE:
-      // This is a consumer
-      return ContextConsumer;
-    case REACT_FORWARD_REF_TYPE:
-      return ForwardRef;
-    default: {
-      var info = "";
-      {
-        if (
-          type === undefined ||
-          (typeof type === "object" &&
-            type !== null &&
-            Object.keys(type).length === 0)
-        ) {
-          info +=
-            " You likely forgot to export your component from the file " +
-            "it's defined in, or you might have mixed up default and " +
-            "named imports.";
-        }
-        var ownerName = owner ? getComponentName(owner) : null;
-        if (ownerName) {
-          info += "\n\nCheck the render method of `" + ownerName + "`.";
-        }
-      }
-      invariant(
-        false,
-        "Element type is invalid: expected a string (for built-in " +
-          "components) or a class/function (for composite components) " +
-          "but got: %s.%s",
-        type == null ? type : typeof type,
-        info
-      );
+function createCursor(defaultValue) {
+  return {
+    current: defaultValue
+  };
+}
+
+function pop(cursor, fiber) {
+  if (index < 0) {
+    {
+      warning(false, "Unexpected pop.");
+    }
+    return;
+  }
+
+  {
+    if (fiber !== fiberStack[index]) {
+      warning(false, "Unexpected Fiber popped.");
     }
   }
+
+  cursor.current = valueStack[index];
+
+  valueStack[index] = null;
+
+  {
+    fiberStack[index] = null;
+  }
+
+  index--;
 }
 
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  var fiber = createFiber(Fragment, elements, key, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
+function push(cursor, value, fiber) {
+  index++;
+
+  valueStack[index] = cursor.current;
+
+  {
+    fiberStack[index] = fiber;
+  }
+
+  cursor.current = value;
 }
 
-function createFiberFromProfiler(pendingProps, mode, expirationTime, key) {
+function checkThatStackIsEmpty() {
   {
-    if (
-      typeof pendingProps.id !== "string" ||
-      typeof pendingProps.onRender !== "function"
-    ) {
-      invariant(
+    if (index !== -1) {
+      warning(
         false,
-        'Profiler must specify an "id" string and "onRender" function as props'
+        "Expected an empty stack. Something was not reset properly."
       );
     }
   }
+}
 
-  var fiber = createFiber(Profiler, pendingProps, key, mode | ProfileMode);
-  fiber.type = REACT_PROFILER_TYPE;
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    duration: 0,
-    startTime: 0
-  };
-
-  return fiber;
+function resetStackAfterFatalErrorInDev() {
+  {
+    index = -1;
+    valueStack.length = 0;
+    fiberStack.length = 0;
+  }
 }
 
-function createFiberFromText(content, mode, expirationTime) {
-  var fiber = createFiber(HostText, content, null, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
+var warnedAboutMissingGetChildContext = void 0;
+
+{
+  warnedAboutMissingGetChildContext = {};
 }
 
-function createFiberFromHostInstanceForDeletion() {
-  var fiber = createFiber(HostComponent, null, null, NoContext);
-  fiber.type = "DELETED";
-  return fiber;
+// A cursor to the current merged context object on the stack.
+var contextStackCursor = createCursor(emptyObject);
+// A cursor to a boolean indicating whether the context has changed.
+var didPerformWorkStackCursor = createCursor(false);
+// Keep track of the previous context object that was on the stack.
+// We use this to get access to the parent context after we have already
+// pushed the next context provider, and now need to merge their contexts.
+var previousContext = emptyObject;
+
+function getUnmaskedContext(workInProgress) {
+  var hasOwnContext = isContextProvider(workInProgress);
+  if (hasOwnContext) {
+    // If the fiber is a context provider itself, when we read its context
+    // we have already pushed its own child context on the stack. A context
+    // provider should not "see" its own child context. Therefore we read the
+    // previous (parent) context instead for a context provider.
+    return previousContext;
+  }
+  return contextStackCursor.current;
 }
 
-function createFiberFromPortal(portal, mode, expirationTime) {
-  var pendingProps = portal.children !== null ? portal.children : [];
-  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null, // Used by persistent updates
-    implementation: portal.implementation
-  };
-  return fiber;
+function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+  var instance = workInProgress.stateNode;
+  instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+  instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
 }
 
-// Used for stashing WIP properties to replay failed work in DEV.
-function assignFiberPropertiesInDEV(target, source) {
-  if (target === null) {
-    // This Fiber's initial properties will always be overwritten.
-    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
-    target = createFiber(IndeterminateComponent, null, null, NoContext);
+function getMaskedContext(workInProgress, unmaskedContext) {
+  var type = workInProgress.type;
+  var contextTypes = type.contextTypes;
+  if (!contextTypes) {
+    return emptyObject;
   }
 
-  // This is intentionally written as a list of all properties.
-  // We tried to use Object.assign() instead but this is called in
-  // the hottest path, and Object.assign() was too slow:
-  // https://github.com/facebook/react/issues/12502
-  // This code is DEV-only so size is not a concern.
+  // Avoid recreating masked context unless unmasked context has changed.
+  // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
+  // This may trigger infinite loops if componentWillReceiveProps calls setState.
+  var instance = workInProgress.stateNode;
+  if (
+    instance &&
+    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+  ) {
+    return instance.__reactInternalMemoizedMaskedChildContext;
+  }
 
-  target.tag = source.tag;
-  target.key = source.key;
-  target.type = source.type;
-  target.stateNode = source.stateNode;
-  target.return = source.return;
-  target.child = source.child;
-  target.sibling = source.sibling;
-  target.index = source.index;
-  target.ref = source.ref;
-  target.pendingProps = source.pendingProps;
-  target.memoizedProps = source.memoizedProps;
-  target.updateQueue = source.updateQueue;
-  target.memoizedState = source.memoizedState;
-  target.mode = source.mode;
-  target.effectTag = source.effectTag;
-  target.nextEffect = source.nextEffect;
-  target.firstEffect = source.firstEffect;
-  target.lastEffect = source.lastEffect;
-  target.expirationTime = source.expirationTime;
-  target.alternate = source.alternate;
-  if (enableProfilerTimer) {
-    target.selfBaseTime = source.selfBaseTime;
-    target.treeBaseTime = source.treeBaseTime;
+  var context = {};
+  for (var key in contextTypes) {
+    context[key] = unmaskedContext[key];
   }
-  target._debugID = source._debugID;
-  target._debugSource = source._debugSource;
-  target._debugOwner = source._debugOwner;
-  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
-  return target;
-}
 
-// TODO: This should be lifted into the renderer.
+  {
+    var name = getComponentName(workInProgress) || "Unknown";
+    checkPropTypes(
+      contextTypes,
+      context,
+      "context",
+      name,
+      ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+    );
+  }
 
-function createFiberRoot(containerInfo, isAsync, hydrate) {
-  // Cyclic construction. This cheats the type system right now because
-  // stateNode is any.
-  var uninitializedFiber = createHostRootFiber(isAsync);
-  var root = {
-    current: uninitializedFiber,
-    containerInfo: containerInfo,
-    pendingChildren: null,
+  // Cache unmasked context so we can avoid recreating masked context unless necessary.
+  // Context is created before the class component is instantiated so check for instance.
+  if (instance) {
+    cacheContext(workInProgress, unmaskedContext, context);
+  }
 
-    earliestPendingTime: NoWork,
-    latestPendingTime: NoWork,
-    earliestSuspendedTime: NoWork,
-    latestSuspendedTime: NoWork,
-    latestPingedTime: NoWork,
+  return context;
+}
 
-    pendingCommitExpirationTime: NoWork,
-    finishedWork: null,
-    context: null,
-    pendingContext: null,
-    hydrate: hydrate,
-    remainingExpirationTime: NoWork,
-    firstBatch: null,
-    nextScheduledRoot: null
-  };
-  uninitializedFiber.stateNode = root;
-  return root;
+function hasContextChanged() {
+  return didPerformWorkStackCursor.current;
 }
 
-var onCommitFiberRoot = null;
-var onCommitFiberUnmount = null;
-var hasLoggedError = false;
+function isContextConsumer(fiber) {
+  return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+}
 
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {
-      if (true && !hasLoggedError) {
-        hasLoggedError = true;
-        warning(false, "React DevTools encountered an error: %s", err);
-      }
-    }
-  };
+function isContextProvider(fiber) {
+  return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
 }
 
-function injectInternals(internals) {
-  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
-    // No DevTools
-    return false;
-  }
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled) {
-    // This isn't a real property on the hook, but it can be set to opt out
-    // of DevTools integration and associated warnings and logs.
-    // https://github.com/facebook/react/issues/3877
-    return true;
-  }
-  if (!hook.supportsFiber) {
-    {
-      warning(
-        false,
-        "The installed version of React DevTools is too old and will not work " +
-          "with the current version of React. Please update React DevTools. " +
-          "https://fb.me/react-devtools"
-      );
-    }
-    // DevTools exists, even though it doesn't support Fiber.
-    return true;
+function popContextProvider(fiber) {
+  if (!isContextProvider(fiber)) {
+    return;
   }
-  try {
-    var rendererID = hook.inject(internals);
-    // We have successfully injected, so now it is safe to set up hooks.
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {
-    // Catch all errors because it is unsafe to throw during initialization.
+
+  pop(didPerformWorkStackCursor, fiber);
+  pop(contextStackCursor, fiber);
+}
+
+function popTopLevelContextObject(fiber) {
+  pop(didPerformWorkStackCursor, fiber);
+  pop(contextStackCursor, fiber);
+}
+
+function pushTopLevelContextObject(fiber, context, didChange) {
+  invariant(
+    contextStackCursor.current === emptyObject,
+    "Unexpected context found on stack. " +
+      "This error is likely caused by a bug in React. Please file an issue."
+  );
+
+  push(contextStackCursor, context, fiber);
+  push(didPerformWorkStackCursor, didChange, fiber);
+}
+
+function processChildContext(fiber, parentContext) {
+  var instance = fiber.stateNode;
+  var childContextTypes = fiber.type.childContextTypes;
+
+  // TODO (bvaughn) Replace this behavior with an invariant() in the future.
+  // It has only been added in Fiber to match the (unintentional) behavior in Stack.
+  if (typeof instance.getChildContext !== "function") {
     {
-      warning(false, "React DevTools encountered an error: %s.", err);
+      var componentName = getComponentName(fiber) || "Unknown";
+
+      if (!warnedAboutMissingGetChildContext[componentName]) {
+        warnedAboutMissingGetChildContext[componentName] = true;
+        warning(
+          false,
+          "%s.childContextTypes is specified but there is no getChildContext() method " +
+            "on the instance. You can either define getChildContext() on %s or remove " +
+            "childContextTypes from it.",
+          componentName,
+          componentName
+        );
+      }
     }
+    return parentContext;
   }
-  // DevTools exists
+
+  var childContext = void 0;
+  {
+    ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
+  }
+  startPhaseTimer(fiber, "getChildContext");
+  childContext = instance.getChildContext();
+  stopPhaseTimer();
+  {
+    ReactDebugCurrentFiber.setCurrentPhase(null);
+  }
+  for (var contextKey in childContext) {
+    invariant(
+      contextKey in childContextTypes,
+      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+      getComponentName(fiber) || "Unknown",
+      contextKey
+    );
+  }
+  {
+    var name = getComponentName(fiber) || "Unknown";
+    checkPropTypes(
+      childContextTypes,
+      childContext,
+      "child context",
+      name,
+      // In practice, there is one case in which we won't get a stack. It's when
+      // somebody calls unstable_renderSubtreeIntoContainer() and we process
+      // context from the parent component instance. The stack will be missing
+      // because it's outside of the reconciliation, and so the pointer has not
+      // been set. This is rare and doesn't matter. We'll also remove that API.
+      ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+    );
+  }
+
+  return Object.assign({}, parentContext, childContext);
+}
+
+function pushContextProvider(workInProgress) {
+  if (!isContextProvider(workInProgress)) {
+    return false;
+  }
+
+  var instance = workInProgress.stateNode;
+  // We push the context as early as possible to ensure stack integrity.
+  // If the instance does not exist yet, we will push null at first,
+  // and replace it on the stack later when invalidating the context.
+  var memoizedMergedChildContext =
+    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+    emptyObject;
+
+  // Remember the parent context so we can merge with it later.
+  // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
+  previousContext = contextStackCursor.current;
+  push(contextStackCursor, memoizedMergedChildContext, workInProgress);
+  push(
+    didPerformWorkStackCursor,
+    didPerformWorkStackCursor.current,
+    workInProgress
+  );
+
   return true;
 }
 
-function onCommitRoot(root) {
-  if (typeof onCommitFiberRoot === "function") {
-    onCommitFiberRoot(root);
+function invalidateContextProvider(workInProgress, didChange) {
+  var instance = workInProgress.stateNode;
+  invariant(
+    instance,
+    "Expected to have an instance by this point. " +
+      "This error is likely caused by a bug in React. Please file an issue."
+  );
+
+  if (didChange) {
+    // Merge parent and own context.
+    // Skip this if we're not updating due to sCU.
+    // This avoids unnecessarily recomputing memoized values.
+    var mergedContext = processChildContext(workInProgress, previousContext);
+    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+
+    // Replace the old (or empty) context with the new one.
+    // It is important to unwind the context in the reverse order.
+    pop(didPerformWorkStackCursor, workInProgress);
+    pop(contextStackCursor, workInProgress);
+    // Now push the new context and mark that it has changed.
+    push(contextStackCursor, mergedContext, workInProgress);
+    push(didPerformWorkStackCursor, didChange, workInProgress);
+  } else {
+    pop(didPerformWorkStackCursor, workInProgress);
+    push(didPerformWorkStackCursor, didChange, workInProgress);
   }
 }
 
-function onCommitUnmount(fiber) {
-  if (typeof onCommitFiberUnmount === "function") {
-    onCommitFiberUnmount(fiber);
+function findCurrentUnmaskedContext(fiber) {
+  // Currently this is only used with renderSubtreeIntoContainer; not sure if it
+  // makes sense elsewhere
+  invariant(
+    isFiberMounted(fiber) && fiber.tag === ClassComponent,
+    "Expected subtree parent to be a mounted class component. " +
+      "This error is likely caused by a bug in React. Please file an issue."
+  );
+
+  var node = fiber;
+  while (node.tag !== HostRoot) {
+    if (isContextProvider(node)) {
+      return node.stateNode.__reactInternalMemoizedMergedChildContext;
+    }
+    var parent = node.return;
+    invariant(
+      parent,
+      "Found unexpected detached subtree parent. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+    node = parent;
   }
+  return node.stateNode.context;
 }
 
-var describeComponentFrame = function(name, source, ownerName) {
+// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
+// Math.pow(2, 30) - 1
+// 0b111111111111111111111111111111
+var MAX_SIGNED_31_BIT_INT = 1073741823;
+
+var NoWork = 0;
+var Sync = 1;
+var Never = MAX_SIGNED_31_BIT_INT;
+
+var UNIT_SIZE = 10;
+var MAGIC_NUMBER_OFFSET = 2;
+
+// 1 unit of expiration time represents 10ms.
+function msToExpirationTime(ms) {
+  // Always add an offset so that we don't clash with the magic number for NoWork.
+  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
+}
+
+function expirationTimeToMs(expirationTime) {
+  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
+}
+
+function ceiling(num, precision) {
+  return (((num / precision) | 0) + 1) * precision;
+}
+
+function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
   return (
-    "\n    in " +
-    (name || "Unknown") +
-    (source
-      ? " (at " +
-        source.fileName.replace(/^.*[\\\/]/, "") +
-        ":" +
-        source.lineNumber +
-        ")"
-      : ownerName ? " (created by " + ownerName + ")" : "")
+    MAGIC_NUMBER_OFFSET +
+    ceiling(
+      currentTime - MAGIC_NUMBER_OFFSET + expirationInMs / UNIT_SIZE,
+      bucketSizeMs / UNIT_SIZE
+    )
   );
-};
+}
 
-function describeFiber(fiber) {
-  switch (fiber.tag) {
-    case IndeterminateComponent:
-    case FunctionalComponent:
-    case ClassComponent:
-    case HostComponent:
-      var owner = fiber._debugOwner;
-      var source = fiber._debugSource;
-      var name = getComponentName(fiber);
-      var ownerName = null;
-      if (owner) {
-        ownerName = getComponentName(owner);
-      }
-      return describeComponentFrame(name, source, ownerName);
-    default:
-      return "";
+var NoContext = 0;
+var AsyncMode = 1;
+var StrictMode = 2;
+var ProfileMode = 4;
+
+var hasBadMapPolyfill = void 0;
+
+{
+  hasBadMapPolyfill = false;
+  try {
+    var nonExtensibleObject = Object.preventExtensions({});
+    var testMap = new Map([[nonExtensibleObject, null]]);
+    var testSet = new Set([nonExtensibleObject]);
+    // This is necessary for Rollup to not consider these unused.
+    // https://github.com/rollup/rollup/issues/1771
+    // TODO: we can remove these if Rollup fixes the bug.
+    testMap.set(0, 0);
+    testSet.add(0);
+  } catch (e) {
+    // TODO: Consider warning about bad polyfills
+    hasBadMapPolyfill = true;
   }
 }
 
-// This function can only be called with a work-in-progress fiber and
-// only during begin or complete phase. Do not call it under any other
-// circumstances.
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  var node = workInProgress;
-  do {
-    info += describeFiber(node);
-    // Otherwise this return pointer might point to the wrong tree:
-    node = node.return;
-  } while (node);
-  return info;
+// A Fiber is work on a Component that needs to be done or was done. There can
+// be more than one per component.
+
+var debugCounter = void 0;
+
+{
+  debugCounter = 1;
 }
 
-/**
- * Forked from fbjs/warning:
- * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
- *
- * Only change is we use console.warn instead of console.error,
- * and do nothing when 'console' is not supported.
- * This really simplifies the code.
- * ---
- * Similar to invariant but only logs a warning if the condition is not met.
- * This can be used to log issues in development environments in critical
- * paths. Removing the logging code for production environments will keep the
- * same logic and follow the same code paths.
- */
+function FiberNode(tag, pendingProps, key, mode) {
+  // Instance
+  this.tag = tag;
+  this.key = key;
+  this.type = null;
+  this.stateNode = null;
 
-var lowPriorityWarning = function() {};
+  // Fiber
+  this.return = null;
+  this.child = null;
+  this.sibling = null;
+  this.index = 0;
 
-{
-  var printWarning = function(format) {
-    for (
-      var _len = arguments.length,
-        args = Array(_len > 1 ? _len - 1 : 0),
-        _key = 1;
-      _key < _len;
-      _key++
-    ) {
-      args[_key - 1] = arguments[_key];
-    }
+  this.ref = null;
 
-    var argIndex = 0;
-    var message =
-      "Warning: " +
-      format.replace(/%s/g, function() {
-        return args[argIndex++];
-      });
-    if (typeof console !== "undefined") {
-      console.warn(message);
-    }
-    try {
-      // --- Welcome to debugging React ---
-      // This error was thrown as a convenience so that you can use this stack
-      // to find the callsite that caused this warning to fire.
-      throw new Error(message);
-    } catch (x) {}
-  };
+  this.pendingProps = pendingProps;
+  this.memoizedProps = null;
+  this.updateQueue = null;
+  this.memoizedState = null;
 
-  lowPriorityWarning = function(condition, format) {
-    if (format === undefined) {
-      throw new Error(
-        "`warning(condition, format, ...args)` requires a warning " +
-          "message argument"
-      );
+  this.mode = mode;
+
+  // Effects
+  this.effectTag = NoEffect;
+  this.nextEffect = null;
+
+  this.firstEffect = null;
+  this.lastEffect = null;
+
+  this.expirationTime = NoWork;
+
+  this.alternate = null;
+
+  if (enableProfilerTimer) {
+    this.actualDuration = 0;
+    this.actualStartTime = 0;
+    this.selfBaseTime = 0;
+    this.treeBaseTime = 0;
+  }
+
+  {
+    this._debugID = debugCounter++;
+    this._debugSource = null;
+    this._debugOwner = null;
+    this._debugIsCurrentlyTiming = false;
+    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
+      Object.preventExtensions(this);
     }
-    if (!condition) {
-      for (
-        var _len2 = arguments.length,
-          args = Array(_len2 > 2 ? _len2 - 2 : 0),
-          _key2 = 2;
-        _key2 < _len2;
-        _key2++
-      ) {
-        args[_key2 - 2] = arguments[_key2];
-      }
+  }
+}
+
+// This is a constructor function, rather than a POJO constructor, still
+// please ensure we do the following:
+// 1) Nobody should add any instance methods on this. Instance methods can be
+//    more difficult to predict when they get optimized and they are almost
+//    never inlined properly in static compilers.
+// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
+//    always know when it is a fiber.
+// 3) We might want to experiment with using numeric keys since they are easier
+//    to optimize in a non-JIT environment.
+// 4) We can easily go from a constructor to a createFiber object literal if that
+//    is faster.
+// 5) It should be easy to port this to a C struct and keep a C implementation
+//    compatible.
+var createFiber = function(tag, pendingProps, key, mode) {
+  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
+  return new FiberNode(tag, pendingProps, key, mode);
+};
 
-      printWarning.apply(undefined, [format].concat(args));
-    }
-  };
+function shouldConstruct(Component) {
+  return !!(Component.prototype && Component.prototype.isReactComponent);
 }
 
-var lowPriorityWarning$1 = lowPriorityWarning;
-
-var ReactStrictModeWarnings = {
-  discardPendingWarnings: function() {},
-  flushPendingDeprecationWarnings: function() {},
-  flushPendingUnsafeLifecycleWarnings: function() {},
-  recordDeprecationWarnings: function(fiber, instance) {},
-  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
-};
+// This is used to create an alternate fiber to do work on.
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  if (workInProgress === null) {
+    // We use a double buffering pooling technique because we know that we'll
+    // only ever need at most two versions of a tree. We pool the "other" unused
+    // node that we're free to reuse. This is lazily created to avoid allocating
+    // extra objects for things that are never updated. It also allow us to
+    // reclaim the extra memory if needed.
+    workInProgress = createFiber(
+      current.tag,
+      pendingProps,
+      current.key,
+      current.mode
+    );
+    workInProgress.type = current.type;
+    workInProgress.stateNode = current.stateNode;
 
-{
-  var LIFECYCLE_SUGGESTIONS = {
-    UNSAFE_componentWillMount: "componentDidMount",
-    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
-    UNSAFE_componentWillUpdate: "componentDidUpdate"
-  };
+    {
+      // DEV-only fields
+      workInProgress._debugID = current._debugID;
+      workInProgress._debugSource = current._debugSource;
+      workInProgress._debugOwner = current._debugOwner;
+    }
 
-  var pendingComponentWillMountWarnings = [];
-  var pendingComponentWillReceivePropsWarnings = [];
-  var pendingComponentWillUpdateWarnings = [];
-  var pendingUnsafeLifecycleWarnings = new Map();
+    workInProgress.alternate = current;
+    current.alternate = workInProgress;
+  } else {
+    workInProgress.pendingProps = pendingProps;
 
-  // Tracks components we have already warned about.
-  var didWarnAboutDeprecatedLifecycles = new Set();
-  var didWarnAboutUnsafeLifecycles = new Set();
+    // We already have an alternate.
+    // Reset the effect tag.
+    workInProgress.effectTag = NoEffect;
 
-  var setToSortedString = function(set) {
-    var array = [];
-    set.forEach(function(value) {
-      array.push(value);
-    });
-    return array.sort().join(", ");
-  };
+    // The effect list is no longer valid.
+    workInProgress.nextEffect = null;
+    workInProgress.firstEffect = null;
+    workInProgress.lastEffect = null;
 
-  ReactStrictModeWarnings.discardPendingWarnings = function() {
-    pendingComponentWillMountWarnings = [];
-    pendingComponentWillReceivePropsWarnings = [];
-    pendingComponentWillUpdateWarnings = [];
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+    if (enableProfilerTimer) {
+      // We intentionally reset, rather than copy, actualDuration & actualStartTime.
+      // This prevents time from endlessly accumulating in new commits.
+      // This has the downside of resetting values for different priority renders,
+      // But works for yielding (the common case) and should support resuming.
+      workInProgress.actualDuration = 0;
+      workInProgress.actualStartTime = 0;
+    }
+  }
 
-  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
-    pendingUnsafeLifecycleWarnings.forEach(function(
-      lifecycleWarningsMap,
-      strictRoot
-    ) {
-      var lifecyclesWarningMesages = [];
+  workInProgress.expirationTime = expirationTime;
 
-      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
-        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
-        if (lifecycleWarnings.length > 0) {
-          var componentNames = new Set();
-          lifecycleWarnings.forEach(function(fiber) {
-            componentNames.add(getComponentName(fiber) || "Component");
-            didWarnAboutUnsafeLifecycles.add(fiber.type);
-          });
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
 
-          var formatted = lifecycle.replace("UNSAFE_", "");
-          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = setToSortedString(componentNames);
+  // These will be overridden during the parent's reconciliation
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
 
-          lifecyclesWarningMesages.push(
-            formatted +
-              ": Please update the following components to use " +
-              (suggestion + " instead: " + sortedComponentNames)
-          );
-        }
-      });
+  if (enableProfilerTimer) {
+    workInProgress.selfBaseTime = current.selfBaseTime;
+    workInProgress.treeBaseTime = current.treeBaseTime;
+  }
 
-      if (lifecyclesWarningMesages.length > 0) {
-        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
-          strictRoot
-        );
+  return workInProgress;
+}
 
-        warning(
-          false,
-          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
-            "\n\n%s" +
-            "\n\nLearn more about this warning here:" +
-            "\nhttps://fb.me/react-strict-mode-warnings",
-          strictRootComponentStack,
-          lifecyclesWarningMesages.join("\n\n")
-        );
-      }
-    });
+function createHostRootFiber(isAsync) {
+  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
+  return createFiber(HostRoot, null, null, mode);
+}
 
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+function createFiberFromElement(element, mode, expirationTime) {
+  var owner = null;
+  {
+    owner = element._owner;
+  }
 
-  var findStrictRoot = function(fiber) {
-    var maybeStrictRoot = null;
+  var fiber = void 0;
+  var type = element.type;
+  var key = element.key;
+  var pendingProps = element.props;
 
-    var node = fiber;
-    while (node !== null) {
-      if (node.mode & StrictMode) {
-        maybeStrictRoot = node;
-      }
-      node = node.return;
+  var fiberTag = void 0;
+  if (typeof type === "function") {
+    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
+  } else if (typeof type === "string") {
+    fiberTag = HostComponent;
+  } else {
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          pendingProps.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= AsyncMode | StrictMode;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= StrictMode;
+        break;
+      case REACT_PROFILER_TYPE:
+        return createFiberFromProfiler(pendingProps, mode, expirationTime, key);
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = TimeoutComponent;
+        // Suspense does not require async, but its children should be strict
+        // mode compatible.
+        mode |= StrictMode;
+        break;
+      default:
+        fiberTag = getFiberTagFromObjectType(type, owner);
+        break;
     }
+  }
 
-    return maybeStrictRoot;
-  };
+  fiber = createFiber(fiberTag, pendingProps, key, mode);
+  fiber.type = type;
+  fiber.expirationTime = expirationTime;
 
-  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
-    if (pendingComponentWillMountWarnings.length > 0) {
-      var uniqueNames = new Set();
-      pendingComponentWillMountWarnings.forEach(function(fiber) {
-        uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+  {
+    fiber._debugSource = element._source;
+    fiber._debugOwner = element._owner;
+  }
 
-      var sortedNames = setToSortedString(uniqueNames);
+  return fiber;
+}
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillMount is deprecated and will be removed in the next major version. " +
-          "Use componentDidMount instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillMount." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        sortedNames
+function getFiberTagFromObjectType(type, owner) {
+  var $$typeof =
+    typeof type === "object" && type !== null ? type.$$typeof : null;
+
+  switch ($$typeof) {
+    case REACT_PROVIDER_TYPE:
+      return ContextProvider;
+    case REACT_CONTEXT_TYPE:
+      // This is a consumer
+      return ContextConsumer;
+    case REACT_FORWARD_REF_TYPE:
+      return ForwardRef;
+    default: {
+      var info = "";
+      {
+        if (
+          type === undefined ||
+          (typeof type === "object" &&
+            type !== null &&
+            Object.keys(type).length === 0)
+        ) {
+          info +=
+            " You likely forgot to export your component from the file " +
+            "it's defined in, or you might have mixed up default and " +
+            "named imports.";
+        }
+        var ownerName = owner ? getComponentName(owner) : null;
+        if (ownerName) {
+          info += "\n\nCheck the render method of `" + ownerName + "`.";
+        }
+      }
+      invariant(
+        false,
+        "Element type is invalid: expected a string (for built-in " +
+          "components) or a class/function (for composite components) " +
+          "but got: %s.%s",
+        type == null ? type : typeof type,
+        info
       );
-
-      pendingComponentWillMountWarnings = [];
     }
+  }
+}
 
-    if (pendingComponentWillReceivePropsWarnings.length > 0) {
-      var _uniqueNames = new Set();
-      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
-        _uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
-
-      var _sortedNames = setToSortedString(_uniqueNames);
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  var fiber = createFiber(Fragment, elements, key, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
+}
 
-      lowPriorityWarning$1(
+function createFiberFromProfiler(pendingProps, mode, expirationTime, key) {
+  {
+    if (
+      typeof pendingProps.id !== "string" ||
+      typeof pendingProps.onRender !== "function"
+    ) {
+      invariant(
         false,
-        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
-          "Use static getDerivedStateFromProps instead." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames
+        'Profiler must specify an "id" string and "onRender" function as props'
       );
-
-      pendingComponentWillReceivePropsWarnings = [];
     }
+  }
 
-    if (pendingComponentWillUpdateWarnings.length > 0) {
-      var _uniqueNames2 = new Set();
-      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
-        _uniqueNames2.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+  var fiber = createFiber(Profiler, pendingProps, key, mode | ProfileMode);
+  fiber.type = REACT_PROFILER_TYPE;
+  fiber.expirationTime = expirationTime;
 
-      var _sortedNames2 = setToSortedString(_uniqueNames2);
+  return fiber;
+}
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillUpdate is deprecated and will be removed in the next major version. " +
-          "Use componentDidUpdate instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillUpdate." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames2
-      );
+function createFiberFromText(content, mode, expirationTime) {
+  var fiber = createFiber(HostText, content, null, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
+}
 
-      pendingComponentWillUpdateWarnings = [];
-    }
+function createFiberFromHostInstanceForDeletion() {
+  var fiber = createFiber(HostComponent, null, null, NoContext);
+  fiber.type = "DELETED";
+  return fiber;
+}
+
+function createFiberFromPortal(portal, mode, expirationTime) {
+  var pendingProps = portal.children !== null ? portal.children : [];
+  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null, // Used by persistent updates
+    implementation: portal.implementation
   };
+  return fiber;
+}
 
-  ReactStrictModeWarnings.recordDeprecationWarnings = function(
-    fiber,
-    instance
-  ) {
-    // Dedup strategy: Warn once per component.
-    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
-      return;
-    }
+// Used for stashing WIP properties to replay failed work in DEV.
+function assignFiberPropertiesInDEV(target, source) {
+  if (target === null) {
+    // This Fiber's initial properties will always be overwritten.
+    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
+    target = createFiber(IndeterminateComponent, null, null, NoContext);
+  }
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillMountWarnings.push(fiber);
-    }
-    if (
-      typeof instance.componentWillReceiveProps === "function" &&
-      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillReceivePropsWarnings.push(fiber);
-    }
-    if (
-      typeof instance.componentWillUpdate === "function" &&
-      instance.componentWillUpdate.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillUpdateWarnings.push(fiber);
-    }
-  };
+  // This is intentionally written as a list of all properties.
+  // We tried to use Object.assign() instead but this is called in
+  // the hottest path, and Object.assign() was too slow:
+  // https://github.com/facebook/react/issues/12502
+  // This code is DEV-only so size is not a concern.
 
-  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
-    fiber,
-    instance
-  ) {
-    var strictRoot = findStrictRoot(fiber);
-    if (strictRoot === null) {
-      warning(
-        false,
-        "Expected to find a StrictMode component in a strict mode tree. " +
-          "This error is likely caused by a bug in React. Please file an issue."
-      );
-      return;
-    }
+  target.tag = source.tag;
+  target.key = source.key;
+  target.type = source.type;
+  target.stateNode = source.stateNode;
+  target.return = source.return;
+  target.child = source.child;
+  target.sibling = source.sibling;
+  target.index = source.index;
+  target.ref = source.ref;
+  target.pendingProps = source.pendingProps;
+  target.memoizedProps = source.memoizedProps;
+  target.updateQueue = source.updateQueue;
+  target.memoizedState = source.memoizedState;
+  target.mode = source.mode;
+  target.effectTag = source.effectTag;
+  target.nextEffect = source.nextEffect;
+  target.firstEffect = source.firstEffect;
+  target.lastEffect = source.lastEffect;
+  target.expirationTime = source.expirationTime;
+  target.alternate = source.alternate;
+  if (enableProfilerTimer) {
+    target.actualDuration = source.actualDuration;
+    target.actualStartTime = source.actualStartTime;
+    target.selfBaseTime = source.selfBaseTime;
+    target.treeBaseTime = source.treeBaseTime;
+  }
+  target._debugID = source._debugID;
+  target._debugSource = source._debugSource;
+  target._debugOwner = source._debugOwner;
+  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
+  return target;
+}
 
-    // Dedup strategy: Warn once per component.
-    // This is difficult to track any other way since component names
-    // are often vague and are likely to collide between 3rd party libraries.
-    // An expand property is probably okay to use here since it's DEV-only,
-    // and will only be set in the event of serious warnings.
-    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
-      return;
-    }
+// TODO: This should be lifted into the renderer.
 
-    var warningsForRoot = void 0;
-    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
-      warningsForRoot = {
-        UNSAFE_componentWillMount: [],
-        UNSAFE_componentWillReceiveProps: [],
-        UNSAFE_componentWillUpdate: []
-      };
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  // Cyclic construction. This cheats the type system right now because
+  // stateNode is any.
+  var uninitializedFiber = createHostRootFiber(isAsync);
+  var root = {
+    current: uninitializedFiber,
+    containerInfo: containerInfo,
+    pendingChildren: null,
 
-      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
-    } else {
-      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
-    }
+    earliestPendingTime: NoWork,
+    latestPendingTime: NoWork,
+    earliestSuspendedTime: NoWork,
+    latestSuspendedTime: NoWork,
+    latestPingedTime: NoWork,
 
-    var unsafeLifecycles = [];
-    if (
-      (typeof instance.componentWillMount === "function" &&
-        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
-      typeof instance.UNSAFE_componentWillMount === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillMount");
-    }
-    if (
-      (typeof instance.componentWillReceiveProps === "function" &&
-        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-          true) ||
-      typeof instance.UNSAFE_componentWillReceiveProps === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
-    }
-    if (
-      (typeof instance.componentWillUpdate === "function" &&
-        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
-      typeof instance.UNSAFE_componentWillUpdate === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
-    }
+    didError: false,
 
-    if (unsafeLifecycles.length > 0) {
-      unsafeLifecycles.forEach(function(lifecycle) {
-        warningsForRoot[lifecycle].push(fiber);
-      });
+    pendingCommitExpirationTime: NoWork,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    nextExpirationTimeToWorkOn: NoWork,
+    expirationTime: NoWork,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  uninitializedFiber.stateNode = root;
+  return root;
+}
+
+var onCommitFiberRoot = null;
+var onCommitFiberUnmount = null;
+var hasLoggedError = false;
+
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {
+      if (true && !hasLoggedError) {
+        hasLoggedError = true;
+        warning(false, "React DevTools encountered an error: %s", err);
+      }
     }
   };
 }
 
-/**
- * The "actual" render time is total time required to render the descendants of a Profiler component.
- * This time is stored as a stack, since Profilers can be nested.
- * This time is started during the "begin" phase and stopped during the "complete" phase.
- * It is paused (and accumulated) in the event of an interruption or an aborted render.
- */
-
-function createProfilerTimer(now) {
-  var fiberStack = void 0;
-
-  {
-    fiberStack = [];
+function injectInternals(internals) {
+  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
+    // No DevTools
+    return false;
   }
-
-  var timerPausedAt = 0;
-  var totalElapsedPauseTime = 0;
-
-  function checkActualRenderTimeStackEmpty() {
-    {
-      !(fiberStack.length === 0)
-        ? warning(
-            false,
-            "Expected an empty stack. Something was not reset properly."
-          )
-        : void 0;
-    }
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled) {
+    // This isn't a real property on the hook, but it can be set to opt out
+    // of DevTools integration and associated warnings and logs.
+    // https://github.com/facebook/react/issues/3877
+    return true;
   }
-
-  function markActualRenderTimeStarted(fiber) {
+  if (!hook.supportsFiber) {
     {
-      fiberStack.push(fiber);
-    }
-    fiber.stateNode.startTime = now() - totalElapsedPauseTime;
-  }
-
-  function pauseActualRenderTimerIfRunning() {
-    if (timerPausedAt === 0) {
-      timerPausedAt = now();
+      warning(
+        false,
+        "The installed version of React DevTools is too old and will not work " +
+          "with the current version of React. Please update React DevTools. " +
+          "https://fb.me/react-devtools"
+      );
     }
+    // DevTools exists, even though it doesn't support Fiber.
+    return true;
   }
-
-  function recordElapsedActualRenderTime(fiber) {
+  try {
+    var rendererID = hook.inject(internals);
+    // We have successfully injected, so now it is safe to set up hooks.
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {
+    // Catch all errors because it is unsafe to throw during initialization.
     {
-      !(fiber === fiberStack.pop())
-        ? warning(false, "Unexpected Fiber popped.")
-        : void 0;
+      warning(false, "React DevTools encountered an error: %s.", err);
     }
-    fiber.stateNode.duration +=
-      now() - totalElapsedPauseTime - fiber.stateNode.startTime;
   }
+  // DevTools exists
+  return true;
+}
 
-  function resetActualRenderTimer() {
-    totalElapsedPauseTime = 0;
+function onCommitRoot(root) {
+  if (typeof onCommitFiberRoot === "function") {
+    onCommitFiberRoot(root);
   }
+}
 
-  function resumeActualRenderTimerIfPaused() {
-    if (timerPausedAt > 0) {
-      totalElapsedPauseTime += now() - timerPausedAt;
-      timerPausedAt = 0;
-    }
+function onCommitUnmount(fiber) {
+  if (typeof onCommitFiberUnmount === "function") {
+    onCommitFiberUnmount(fiber);
   }
+}
 
-  /**
-   * The "base" render time is the duration of the “begin” phase of work for a particular fiber.
-   * This time is measured and stored on each fiber.
-   * The time for all sibling fibers are accumulated and stored on their parent during the "complete" phase.
-   * If a fiber bails out (sCU false) then its "base" timer is cancelled and the fiber is not updated.
-   */
+/**
+ * Forked from fbjs/warning:
+ * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
+ *
+ * Only change is we use console.warn instead of console.error,
+ * and do nothing when 'console' is not supported.
+ * This really simplifies the code.
+ * ---
+ * Similar to invariant but only logs a warning if the condition is not met.
+ * This can be used to log issues in development environments in critical
+ * paths. Removing the logging code for production environments will keep the
+ * same logic and follow the same code paths.
+ */
 
-  var baseStartTime = -1;
+var lowPriorityWarning = function() {};
 
-  function recordElapsedBaseRenderTimeIfRunning(fiber) {
-    if (baseStartTime !== -1) {
-      fiber.selfBaseTime = now() - baseStartTime;
+{
+  var printWarning = function(format) {
+    for (
+      var _len = arguments.length,
+        args = Array(_len > 1 ? _len - 1 : 0),
+        _key = 1;
+      _key < _len;
+      _key++
+    ) {
+      args[_key - 1] = arguments[_key];
     }
-  }
 
-  function startBaseRenderTimer() {
-    {
-      if (baseStartTime !== -1) {
-        warning(
-          false,
-          "Cannot start base timer that is already running. " +
-            "This error is likely caused by a bug in React. " +
-            "Please file an issue."
-        );
-      }
+    var argIndex = 0;
+    var message =
+      "Warning: " +
+      format.replace(/%s/g, function() {
+        return args[argIndex++];
+      });
+    if (typeof console !== "undefined") {
+      console.warn(message);
     }
-    baseStartTime = now();
-  }
-
-  function stopBaseRenderTimerIfRunning() {
-    baseStartTime = -1;
-  }
-
-  if (enableProfilerTimer) {
-    return {
-      checkActualRenderTimeStackEmpty: checkActualRenderTimeStackEmpty,
-      markActualRenderTimeStarted: markActualRenderTimeStarted,
-      pauseActualRenderTimerIfRunning: pauseActualRenderTimerIfRunning,
-      recordElapsedActualRenderTime: recordElapsedActualRenderTime,
-      resetActualRenderTimer: resetActualRenderTimer,
-      resumeActualRenderTimerIfPaused: resumeActualRenderTimerIfPaused,
-      recordElapsedBaseRenderTimeIfRunning: recordElapsedBaseRenderTimeIfRunning,
-      startBaseRenderTimer: startBaseRenderTimer,
-      stopBaseRenderTimerIfRunning: stopBaseRenderTimerIfRunning
-    };
-  } else {
-    return {
-      checkActualRenderTimeStackEmpty: function() {},
-      markActualRenderTimeStarted: function(fiber) {},
-      pauseActualRenderTimerIfRunning: function() {},
-      recordElapsedActualRenderTime: function(fiber) {},
-      resetActualRenderTimer: function() {},
-      resumeActualRenderTimerIfPaused: function() {},
-      recordElapsedBaseRenderTimeIfRunning: function(fiber) {},
-      startBaseRenderTimer: function() {},
-      stopBaseRenderTimerIfRunning: function() {}
-    };
-  }
-}
+    try {
+      // --- Welcome to debugging React ---
+      // This error was thrown as a convenience so that you can use this stack
+      // to find the callsite that caused this warning to fire.
+      throw new Error(message);
+    } catch (x) {}
+  };
 
-function getCurrentFiberOwnerName() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    var owner = fiber._debugOwner;
-    if (owner !== null && typeof owner !== "undefined") {
-      return getComponentName(owner);
+  lowPriorityWarning = function(condition, format) {
+    if (format === undefined) {
+      throw new Error(
+        "`warning(condition, format, ...args)` requires a warning " +
+          "message argument"
+      );
     }
-  }
-  return null;
-}
+    if (!condition) {
+      for (
+        var _len2 = arguments.length,
+          args = Array(_len2 > 2 ? _len2 - 2 : 0),
+          _key2 = 2;
+        _key2 < _len2;
+        _key2++
+      ) {
+        args[_key2 - 2] = arguments[_key2];
+      }
 
-function getCurrentFiberStackAddendum$1() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
+      printWarning.apply(undefined, [format].concat(args));
     }
-    // Safe because if current fiber exists, we are reconciling,
-    // and it is guaranteed to be the work-in-progress version.
-    return getStackAddendumByWorkInProgressFiber(fiber);
-  }
-  return null;
+  };
 }
 
-function resetCurrentFiber() {
-  ReactDebugCurrentFrame.getCurrentStack = null;
-  ReactDebugCurrentFiber.current = null;
-  ReactDebugCurrentFiber.phase = null;
-}
+var lowPriorityWarning$1 = lowPriorityWarning;
 
-function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum$1;
-  ReactDebugCurrentFiber.current = fiber;
-  ReactDebugCurrentFiber.phase = null;
-}
+var ReactStrictModeWarnings = {
+  discardPendingWarnings: function() {},
+  flushPendingDeprecationWarnings: function() {},
+  flushPendingUnsafeLifecycleWarnings: function() {},
+  recordDeprecationWarnings: function(fiber, instance) {},
+  recordUnsafeLifecycleWarnings: function(fiber, instance) {},
+  recordLegacyContextWarning: function(fiber, instance) {},
+  flushLegacyContextWarning: function() {}
+};
 
-function setCurrentPhase(phase) {
-  ReactDebugCurrentFiber.phase = phase;
-}
+{
+  var LIFECYCLE_SUGGESTIONS = {
+    UNSAFE_componentWillMount: "componentDidMount",
+    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
+    UNSAFE_componentWillUpdate: "componentDidUpdate"
+  };
 
-var ReactDebugCurrentFiber = {
-  current: null,
-  phase: null,
-  resetCurrentFiber: resetCurrentFiber,
-  setCurrentFiber: setCurrentFiber,
-  setCurrentPhase: setCurrentPhase,
-  getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum$1
-};
+  var pendingComponentWillMountWarnings = [];
+  var pendingComponentWillReceivePropsWarnings = [];
+  var pendingComponentWillUpdateWarnings = [];
+  var pendingUnsafeLifecycleWarnings = new Map();
+  var pendingLegacyContextWarning = new Map();
 
-// Prefix measurements so that it's possible to filter them.
-// Longer prefixes are hard to read in DevTools.
-var reactEmoji = "\u269B";
-var warningEmoji = "\u26D4";
-var supportsUserTiming =
-  typeof performance !== "undefined" &&
-  typeof performance.mark === "function" &&
-  typeof performance.clearMarks === "function" &&
-  typeof performance.measure === "function" &&
-  typeof performance.clearMeasures === "function";
+  // Tracks components we have already warned about.
+  var didWarnAboutDeprecatedLifecycles = new Set();
+  var didWarnAboutUnsafeLifecycles = new Set();
+  var didWarnAboutLegacyContext = new Set();
 
-// Keep track of current fiber so that we know the path to unwind on pause.
-// TODO: this looks the same as nextUnitOfWork in scheduler. Can we unify them?
-var currentFiber = null;
-// If we're in the middle of user code, which fiber and method is it?
-// Reusing `currentFiber` would be confusing for this because user code fiber
-// can change during commit phase too, but we don't need to unwind it (since
-// lifecycles in the commit phase don't resemble a tree).
-var currentPhase = null;
-var currentPhaseFiber = null;
-// Did lifecycle hook schedule an update? This is often a performance problem,
-// so we will keep track of it, and include it in the report.
-// Track commits caused by cascading updates.
-var isCommitting = false;
-var hasScheduledUpdateInCurrentCommit = false;
-var hasScheduledUpdateInCurrentPhase = false;
-var commitCountInCurrentWorkLoop = 0;
-var effectCountInCurrentCommit = 0;
-var isWaitingForCallback = false;
-// During commits, we only show a measurement once per method name
-// to avoid stretch the commit phase with measurement overhead.
-var labelsInCurrentCommit = new Set();
+  var setToSortedString = function(set) {
+    var array = [];
+    set.forEach(function(value) {
+      array.push(value);
+    });
+    return array.sort().join(", ");
+  };
+
+  ReactStrictModeWarnings.discardPendingWarnings = function() {
+    pendingComponentWillMountWarnings = [];
+    pendingComponentWillReceivePropsWarnings = [];
+    pendingComponentWillUpdateWarnings = [];
+    pendingUnsafeLifecycleWarnings = new Map();
+    pendingLegacyContextWarning = new Map();
+  };
+
+  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
+    pendingUnsafeLifecycleWarnings.forEach(function(
+      lifecycleWarningsMap,
+      strictRoot
+    ) {
+      var lifecyclesWarningMesages = [];
 
-var formatMarkName = function(markName) {
-  return reactEmoji + " " + markName;
-};
+      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
+        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
+        if (lifecycleWarnings.length > 0) {
+          var componentNames = new Set();
+          lifecycleWarnings.forEach(function(fiber) {
+            componentNames.add(getComponentName(fiber) || "Component");
+            didWarnAboutUnsafeLifecycles.add(fiber.type);
+          });
 
-var formatLabel = function(label, warning$$1) {
-  var prefix = warning$$1 ? warningEmoji + " " : reactEmoji + " ";
-  var suffix = warning$$1 ? " Warning: " + warning$$1 : "";
-  return "" + prefix + label + suffix;
-};
+          var formatted = lifecycle.replace("UNSAFE_", "");
+          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
+          var sortedComponentNames = setToSortedString(componentNames);
 
-var beginMark = function(markName) {
-  performance.mark(formatMarkName(markName));
-};
+          lifecyclesWarningMesages.push(
+            formatted +
+              ": Please update the following components to use " +
+              (suggestion + " instead: " + sortedComponentNames)
+          );
+        }
+      });
 
-var clearMark = function(markName) {
-  performance.clearMarks(formatMarkName(markName));
-};
+      if (lifecyclesWarningMesages.length > 0) {
+        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+          strictRoot
+        );
 
-var endMark = function(label, markName, warning$$1) {
-  var formattedMarkName = formatMarkName(markName);
-  var formattedLabel = formatLabel(label, warning$$1);
-  try {
-    performance.measure(formattedLabel, formattedMarkName);
-  } catch (err) {}
-  // If previous mark was missing for some reason, this will throw.
-  // This could only happen if React crashed in an unexpected place earlier.
-  // Don't pile on with more errors.
+        warning(
+          false,
+          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
+            "\n\n%s" +
+            "\n\nLearn more about this warning here:" +
+            "\nhttps://fb.me/react-strict-mode-warnings",
+          strictRootComponentStack,
+          lifecyclesWarningMesages.join("\n\n")
+        );
+      }
+    });
 
-  // Clear marks immediately to avoid growing buffer.
-  performance.clearMarks(formattedMarkName);
-  performance.clearMeasures(formattedLabel);
-};
+    pendingUnsafeLifecycleWarnings = new Map();
+  };
 
-var getFiberMarkName = function(label, debugID) {
-  return label + " (#" + debugID + ")";
-};
+  var findStrictRoot = function(fiber) {
+    var maybeStrictRoot = null;
 
-var getFiberLabel = function(componentName, isMounted, phase) {
-  if (phase === null) {
-    // These are composite component total time measurements.
-    return componentName + " [" + (isMounted ? "update" : "mount") + "]";
-  } else {
-    // Composite component methods.
-    return componentName + "." + phase;
-  }
-};
+    var node = fiber;
+    while (node !== null) {
+      if (node.mode & StrictMode) {
+        maybeStrictRoot = node;
+      }
+      node = node.return;
+    }
 
-var beginFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
+    return maybeStrictRoot;
+  };
 
-  if (isCommitting && labelsInCurrentCommit.has(label)) {
-    // During the commit phase, we don't show duplicate labels because
-    // there is a fixed overhead for every measurement, and we don't
-    // want to stretch the commit phase beyond necessary.
-    return false;
-  }
-  labelsInCurrentCommit.add(label);
+  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
+    if (pendingComponentWillMountWarnings.length > 0) {
+      var uniqueNames = new Set();
+      pendingComponentWillMountWarnings.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-  var markName = getFiberMarkName(label, debugID);
-  beginMark(markName);
-  return true;
-};
+      var sortedNames = setToSortedString(uniqueNames);
 
-var clearFiberMark = function(fiber, phase) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  clearMark(markName);
-};
+      lowPriorityWarning$1(
+        false,
+        "componentWillMount is deprecated and will be removed in the next major version. " +
+          "Use componentDidMount instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillMount." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        sortedNames
+      );
 
-var endFiberMark = function(fiber, phase, warning$$1) {
-  var componentName = getComponentName(fiber) || "Unknown";
-  var debugID = fiber._debugID;
-  var isMounted = fiber.alternate !== null;
-  var label = getFiberLabel(componentName, isMounted, phase);
-  var markName = getFiberMarkName(label, debugID);
-  endMark(label, markName, warning$$1);
-};
+      pendingComponentWillMountWarnings = [];
+    }
 
-var shouldIgnoreFiber = function(fiber) {
-  // Host components should be skipped in the timeline.
-  // We could check typeof fiber.type, but does this work with RN?
-  switch (fiber.tag) {
-    case HostRoot:
-    case HostComponent:
-    case HostText:
-    case HostPortal:
-    case Fragment:
-    case ContextProvider:
-    case ContextConsumer:
-    case Mode:
-      return true;
-    default:
-      return false;
-  }
-};
+    if (pendingComponentWillReceivePropsWarnings.length > 0) {
+      var _uniqueNames = new Set();
+      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
+        _uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-var clearPendingPhaseMeasurement = function() {
-  if (currentPhase !== null && currentPhaseFiber !== null) {
-    clearFiberMark(currentPhaseFiber, currentPhase);
-  }
-  currentPhaseFiber = null;
-  currentPhase = null;
-  hasScheduledUpdateInCurrentPhase = false;
-};
+      var _sortedNames = setToSortedString(_uniqueNames);
 
-var pauseTimers = function() {
-  // Stops all currently active measurements so that they can be resumed
-  // if we continue in a later deferred loop from the same unit of work.
-  var fiber = currentFiber;
-  while (fiber) {
-    if (fiber._debugIsCurrentlyTiming) {
-      endFiberMark(fiber, null, null);
+      lowPriorityWarning$1(
+        false,
+        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
+          "Use static getDerivedStateFromProps instead." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames
+      );
+
+      pendingComponentWillReceivePropsWarnings = [];
     }
-    fiber = fiber.return;
-  }
-};
 
-var resumeTimersRecursively = function(fiber) {
-  if (fiber.return !== null) {
-    resumeTimersRecursively(fiber.return);
-  }
-  if (fiber._debugIsCurrentlyTiming) {
-    beginFiberMark(fiber, null);
-  }
-};
+    if (pendingComponentWillUpdateWarnings.length > 0) {
+      var _uniqueNames2 = new Set();
+      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
+        _uniqueNames2.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-var resumeTimers = function() {
-  // Resumes all measurements that were active during the last deferred loop.
-  if (currentFiber !== null) {
-    resumeTimersRecursively(currentFiber);
-  }
-};
+      var _sortedNames2 = setToSortedString(_uniqueNames2);
 
-function recordEffect() {
-  if (enableUserTimingAPI) {
-    effectCountInCurrentCommit++;
-  }
-}
+      lowPriorityWarning$1(
+        false,
+        "componentWillUpdate is deprecated and will be removed in the next major version. " +
+          "Use componentDidUpdate instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillUpdate." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames2
+      );
 
-function recordScheduleUpdate() {
-  if (enableUserTimingAPI) {
-    if (isCommitting) {
-      hasScheduledUpdateInCurrentCommit = true;
+      pendingComponentWillUpdateWarnings = [];
+    }
+  };
+
+  ReactStrictModeWarnings.recordDeprecationWarnings = function(
+    fiber,
+    instance
+  ) {
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
+      return;
+    }
+
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillMountWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillReceiveProps === "function" &&
+      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillReceivePropsWarnings.push(fiber);
     }
     if (
-      currentPhase !== null &&
-      currentPhase !== "componentWillMount" &&
-      currentPhase !== "componentWillReceiveProps"
+      typeof instance.componentWillUpdate === "function" &&
+      instance.componentWillUpdate.__suppressDeprecationWarning !== true
     ) {
-      hasScheduledUpdateInCurrentPhase = true;
-    }
-  }
-}
-
-function startRequestCallbackTimer() {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming && !isWaitingForCallback) {
-      isWaitingForCallback = true;
-      beginMark("(Waiting for async callback...)");
+      pendingComponentWillUpdateWarnings.push(fiber);
     }
-  }
-}
+  };
 
-function stopRequestCallbackTimer(didExpire, expirationTime) {
-  if (enableUserTimingAPI) {
-    if (supportsUserTiming) {
-      isWaitingForCallback = false;
-      var warning$$1 = didExpire ? "React was blocked by main thread" : null;
-      endMark(
-        "(Waiting for async callback... will force flush in " +
-          expirationTime +
-          " ms)",
-        "(Waiting for async callback...)",
-        warning$$1
+  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = findStrictRoot(fiber);
+    if (strictRoot === null) {
+      warning(
+        false,
+        "Expected to find a StrictMode component in a strict mode tree. " +
+          "This error is likely caused by a bug in React. Please file an issue."
       );
-    }
-  }
-}
-
-function startWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
       return;
     }
-    // If we pause, this is the fiber to unwind from.
-    currentFiber = fiber;
-    if (!beginFiberMark(fiber, null)) {
+
+    // Dedup strategy: Warn once per component.
+    // This is difficult to track any other way since component names
+    // are often vague and are likely to collide between 3rd party libraries.
+    // An expand property is probably okay to use here since it's DEV-only,
+    // and will only be set in the event of serious warnings.
+    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
       return;
     }
-    fiber._debugIsCurrentlyTiming = true;
-  }
-}
 
-function cancelWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
+    var warningsForRoot = void 0;
+    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
+      warningsForRoot = {
+        UNSAFE_componentWillMount: [],
+        UNSAFE_componentWillReceiveProps: [],
+        UNSAFE_componentWillUpdate: []
+      };
+
+      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
+    } else {
+      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
     }
-    // Remember we shouldn't complete measurement for this fiber.
-    // Otherwise flamechart will be deep even for small updates.
-    fiber._debugIsCurrentlyTiming = false;
-    clearFiberMark(fiber, null);
-  }
-}
 
-function stopWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
+    var unsafeLifecycles = [];
+    if (
+      (typeof instance.componentWillMount === "function" &&
+        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
+      typeof instance.UNSAFE_componentWillMount === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillMount");
     }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber.return;
-    if (!fiber._debugIsCurrentlyTiming) {
-      return;
+    if (
+      (typeof instance.componentWillReceiveProps === "function" &&
+        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+          true) ||
+      typeof instance.UNSAFE_componentWillReceiveProps === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    }
+    if (
+      (typeof instance.componentWillUpdate === "function" &&
+        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
+      typeof instance.UNSAFE_componentWillUpdate === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
     }
-    fiber._debugIsCurrentlyTiming = false;
-    endFiberMark(fiber, null, null);
-  }
-}
 
-function stopFailedWorkTimer(fiber) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming || shouldIgnoreFiber(fiber)) {
-      return;
+    if (unsafeLifecycles.length > 0) {
+      unsafeLifecycles.forEach(function(lifecycle) {
+        warningsForRoot[lifecycle].push(fiber);
+      });
     }
-    // If we pause, its parent is the fiber to unwind from.
-    currentFiber = fiber.return;
-    if (!fiber._debugIsCurrentlyTiming) {
+  };
+
+  ReactStrictModeWarnings.recordLegacyContextWarning = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = findStrictRoot(fiber);
+    if (strictRoot === null) {
+      warning(
+        false,
+        "Expected to find a StrictMode component in a strict mode tree. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
       return;
     }
-    fiber._debugIsCurrentlyTiming = false;
-    var warning$$1 = "An error was thrown inside this error boundary";
-    endFiberMark(fiber, null, warning$$1);
-  }
-}
 
-function startPhaseTimer(fiber, phase) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutLegacyContext.has(fiber.type)) {
       return;
     }
-    clearPendingPhaseMeasurement();
-    if (!beginFiberMark(fiber, phase)) {
-      return;
+
+    var warningsForRoot = pendingLegacyContextWarning.get(strictRoot);
+
+    if (
+      fiber.type.contextTypes != null ||
+      fiber.type.childContextTypes != null ||
+      (instance !== null && typeof instance.getChildContext === "function")
+    ) {
+      if (warningsForRoot === undefined) {
+        warningsForRoot = [];
+        pendingLegacyContextWarning.set(strictRoot, warningsForRoot);
+      }
+      warningsForRoot.push(fiber);
     }
-    currentPhaseFiber = fiber;
-    currentPhase = phase;
-  }
+  };
+
+  ReactStrictModeWarnings.flushLegacyContextWarning = function() {
+    pendingLegacyContextWarning.forEach(function(fiberArray, strictRoot) {
+      var uniqueNames = new Set();
+      fiberArray.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutLegacyContext.add(fiber.type);
+      });
+
+      var sortedNames = setToSortedString(uniqueNames);
+      var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+        strictRoot
+      );
+
+      warning(
+        false,
+        "Legacy context API has been detected within a strict-mode tree: %s" +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-strict-mode-warnings",
+        strictRootComponentStack,
+        sortedNames
+      );
+    });
+  };
 }
 
-function stopPhaseTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    if (currentPhase !== null && currentPhaseFiber !== null) {
-      var warning$$1 = hasScheduledUpdateInCurrentPhase
-        ? "Scheduled a cascading update"
-        : null;
-      endFiberMark(currentPhaseFiber, currentPhase, warning$$1);
+// This lets us hook into Fiber to debug what it's doing.
+// See https://github.com/facebook/react/pull/8033.
+// This is not part of the public API, not even for React DevTools.
+// You may only inject a debugTool if you work on React Fiber itself.
+var ReactFiberInstrumentation = {
+  debugTool: null
+};
+
+var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
+
+// TODO: Offscreen updates
+
+function markPendingPriorityLevel(root, expirationTime) {
+  // If there's a gap between completing a failed root and retrying it,
+  // additional updates may be scheduled. Clear `didError`, in case the update
+  // is sufficient to fix the error.
+  root.didError = false;
+
+  // Update the latest and earliest pending times
+  var earliestPendingTime = root.earliestPendingTime;
+  if (earliestPendingTime === NoWork) {
+    // No other pending updates.
+    root.earliestPendingTime = root.latestPendingTime = expirationTime;
+  } else {
+    if (earliestPendingTime > expirationTime) {
+      // This is the earliest pending update.
+      root.earliestPendingTime = expirationTime;
+    } else {
+      var latestPendingTime = root.latestPendingTime;
+      if (latestPendingTime < expirationTime) {
+        // This is the latest pending update
+        root.latestPendingTime = expirationTime;
+      }
     }
-    currentPhase = null;
-    currentPhaseFiber = null;
   }
+  findNextPendingPriorityLevel(root);
 }
 
-function startWorkLoopTimer(nextUnitOfWork) {
-  if (enableUserTimingAPI) {
-    currentFiber = nextUnitOfWork;
-    if (!supportsUserTiming) {
-      return;
-    }
-    commitCountInCurrentWorkLoop = 0;
-    // This is top level call.
-    // Any other measurements are performed within.
-    beginMark("(React Tree Reconciliation)");
-    // Resume any measurements that were in progress during the last loop.
-    resumeTimers();
+function markCommittedPriorityLevels(root, currentTime, earliestRemainingTime) {
+  root.didError = false;
+
+  if (earliestRemainingTime === NoWork) {
+    // Fast path. There's no remaining work. Clear everything.
+    root.earliestPendingTime = NoWork;
+    root.latestPendingTime = NoWork;
+    root.earliestSuspendedTime = NoWork;
+    root.latestSuspendedTime = NoWork;
+    root.latestPingedTime = NoWork;
+    findNextPendingPriorityLevel(root);
+    return;
   }
-}
 
-function stopWorkLoopTimer(interruptedBy, didCompleteRoot) {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var warning$$1 = null;
-    if (interruptedBy !== null) {
-      if (interruptedBy.tag === HostRoot) {
-        warning$$1 = "A top-level update interrupted the previous render";
-      } else {
-        var componentName = getComponentName(interruptedBy) || "Unknown";
-        warning$$1 =
-          "An update to " + componentName + " interrupted the previous render";
+  // Let's see if the previous latest known pending level was just flushed.
+  var latestPendingTime = root.latestPendingTime;
+  if (latestPendingTime !== NoWork) {
+    if (latestPendingTime < earliestRemainingTime) {
+      // We've flushed all the known pending levels.
+      root.earliestPendingTime = root.latestPendingTime = NoWork;
+    } else {
+      var earliestPendingTime = root.earliestPendingTime;
+      if (earliestPendingTime < earliestRemainingTime) {
+        // We've flushed the earliest known pending level. Set this to the
+        // latest pending time.
+        root.earliestPendingTime = root.latestPendingTime;
       }
-    } else if (commitCountInCurrentWorkLoop > 1) {
-      warning$$1 = "There were cascading updates";
     }
-    commitCountInCurrentWorkLoop = 0;
-    var label = didCompleteRoot
-      ? "(React Tree Reconciliation: Completed Root)"
-      : "(React Tree Reconciliation: Yielded)";
-    // Pause any measurements until the next loop.
-    pauseTimers();
-    endMark(label, "(React Tree Reconciliation)", warning$$1);
   }
-}
 
-function startCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    isCommitting = true;
-    hasScheduledUpdateInCurrentCommit = false;
-    labelsInCurrentCommit.clear();
-    beginMark("(Committing Changes)");
+  // Now let's handle the earliest remaining level in the whole tree. We need to
+  // decide whether to treat it as a pending level or as suspended. Check
+  // it falls within the range of known suspended levels.
+
+  var earliestSuspendedTime = root.earliestSuspendedTime;
+  if (earliestSuspendedTime === NoWork) {
+    // There's no suspended work. Treat the earliest remaining level as a
+    // pending level.
+    markPendingPriorityLevel(root, earliestRemainingTime);
+    findNextPendingPriorityLevel(root);
+    return;
   }
-}
 
-function stopCommitTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
+  var latestSuspendedTime = root.latestSuspendedTime;
+  if (earliestRemainingTime > latestSuspendedTime) {
+    // The earliest remaining level is later than all the suspended work. That
+    // means we've flushed all the suspended work.
+    root.earliestSuspendedTime = NoWork;
+    root.latestSuspendedTime = NoWork;
+    root.latestPingedTime = NoWork;
 
-    var warning$$1 = null;
-    if (hasScheduledUpdateInCurrentCommit) {
-      warning$$1 = "Lifecycle hook scheduled a cascading update";
-    } else if (commitCountInCurrentWorkLoop > 0) {
-      warning$$1 = "Caused by a cascading update in earlier commit";
-    }
-    hasScheduledUpdateInCurrentCommit = false;
-    commitCountInCurrentWorkLoop++;
-    isCommitting = false;
-    labelsInCurrentCommit.clear();
+    // There's no suspended work. Treat the earliest remaining level as a
+    // pending level.
+    markPendingPriorityLevel(root, earliestRemainingTime);
+    findNextPendingPriorityLevel(root);
+    return;
+  }
 
-    endMark("(Committing Changes)", "(Committing Changes)", warning$$1);
+  if (earliestRemainingTime < earliestSuspendedTime) {
+    // The earliest remaining time is earlier than all the suspended work.
+    // Treat it as a pending update.
+    markPendingPriorityLevel(root, earliestRemainingTime);
+    findNextPendingPriorityLevel(root);
+    return;
   }
+
+  // The earliest remaining time falls within the range of known suspended
+  // levels. We should treat this as suspended work.
+  findNextPendingPriorityLevel(root);
 }
 
-function startCommitSnapshotEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Snapshot Effects)");
-  }
+function hasLowerPriorityWork(root, renderExpirationTime) {
+  return (
+    renderExpirationTime !== root.latestPendingTime &&
+    renderExpirationTime !== root.latestSuspendedTime
+  );
 }
 
-function stopCommitSnapshotEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Snapshot Effects: " + count + " Total)",
-      "(Committing Snapshot Effects)",
-      null
-    );
+function markSuspendedPriorityLevel(root, suspendedTime, didError) {
+  if (didError && !hasLowerPriorityWork(root, suspendedTime)) {
+    // TODO: When we add back resuming, we need to ensure the progressed work
+    // is thrown out and not reused during the restarted render. One way to
+    // invalidate the progressed work is to restart at expirationTime + 1.
+    root.didError = true;
+    findNextPendingPriorityLevel(root);
+    return;
   }
-}
 
-function startCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
+  // First, check the known pending levels and update them if needed.
+  var earliestPendingTime = root.earliestPendingTime;
+  var latestPendingTime = root.latestPendingTime;
+  if (earliestPendingTime === suspendedTime) {
+    if (latestPendingTime === suspendedTime) {
+      // Both known pending levels were suspended. Clear them.
+      root.earliestPendingTime = root.latestPendingTime = NoWork;
+    } else {
+      // The earliest pending level was suspended. Clear by setting it to the
+      // latest pending level.
+      root.earliestPendingTime = latestPendingTime;
     }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Committing Host Effects)");
+  } else if (latestPendingTime === suspendedTime) {
+    // The latest pending level was suspended. Clear by setting it to the
+    // latest pending level.
+    root.latestPendingTime = earliestPendingTime;
   }
-}
 
-function stopCommitHostEffectsTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
+  // Next, if we're working on the lowest known suspended level, clear the ping.
+  // TODO: What if a promise suspends and pings before the root completes?
+  var latestSuspendedTime = root.latestSuspendedTime;
+  if (latestSuspendedTime === suspendedTime) {
+    root.latestPingedTime = NoWork;
+  }
+
+  // Finally, update the known suspended levels.
+  var earliestSuspendedTime = root.earliestSuspendedTime;
+  if (earliestSuspendedTime === NoWork) {
+    // No other suspended levels.
+    root.earliestSuspendedTime = root.latestSuspendedTime = suspendedTime;
+  } else {
+    if (earliestSuspendedTime > suspendedTime) {
+      // This is the earliest suspended level.
+      root.earliestSuspendedTime = suspendedTime;
+    } else if (latestSuspendedTime < suspendedTime) {
+      // This is the latest suspended level
+      root.latestSuspendedTime = suspendedTime;
     }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Committing Host Effects: " + count + " Total)",
-      "(Committing Host Effects)",
-      null
-    );
   }
+  findNextPendingPriorityLevel(root);
 }
 
-function startCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
+function markPingedPriorityLevel(root, pingedTime) {
+  var latestSuspendedTime = root.latestSuspendedTime;
+  if (latestSuspendedTime !== NoWork && latestSuspendedTime <= pingedTime) {
+    var latestPingedTime = root.latestPingedTime;
+    if (latestPingedTime === NoWork || latestPingedTime < pingedTime) {
+      root.latestPingedTime = pingedTime;
     }
-    effectCountInCurrentCommit = 0;
-    beginMark("(Calling Lifecycle Methods)");
   }
+  findNextPendingPriorityLevel(root);
 }
 
-function stopCommitLifeCyclesTimer() {
-  if (enableUserTimingAPI) {
-    if (!supportsUserTiming) {
-      return;
-    }
-    var count = effectCountInCurrentCommit;
-    effectCountInCurrentCommit = 0;
-    endMark(
-      "(Calling Lifecycle Methods: " + count + " Total)",
-      "(Calling Lifecycle Methods)",
-      null
-    );
+function findNextPendingPriorityLevel(root) {
+  var earliestSuspendedTime = root.earliestSuspendedTime;
+  var earliestPendingTime = root.earliestPendingTime;
+  var nextExpirationTimeToWorkOn = void 0;
+  var expirationTime = void 0;
+  if (earliestSuspendedTime === NoWork) {
+    // Fast path. There's no suspended work.
+    nextExpirationTimeToWorkOn = expirationTime = earliestPendingTime;
+  } else if (earliestPendingTime !== NoWork) {
+    // Check if there's known pending work.
+    nextExpirationTimeToWorkOn = earliestPendingTime;
+    expirationTime =
+      earliestSuspendedTime < earliestPendingTime
+        ? earliestSuspendedTime
+        : earliestPendingTime;
+  } else {
+    // Finally, if a suspended level was pinged, work on that. Otherwise there's
+    // nothing to work on.
+    nextExpirationTimeToWorkOn = expirationTime = root.latestPingedTime;
+  }
+
+  if (root.didError) {
+    // Revert to synchronous mode.
+    expirationTime = Sync;
   }
+
+  root.nextExpirationTimeToWorkOn = nextExpirationTimeToWorkOn;
+  root.expirationTime = expirationTime;
 }
 
 // UpdateQueue is a linked list of prioritized updates.
@@ -5998,4634 +6458,4124 @@ function commitUpdateQueue(
   }
 }
 
-var fakeInternalInstance = {};
-var isArray = Array.isArray;
-
-var didWarnAboutStateAssignmentForComponent = void 0;
-var didWarnAboutUninitializedState = void 0;
-var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
-var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
-var warnOnUndefinedDerivedState = void 0;
-var warnOnInvalidCallback = void 0;
-
-{
-  didWarnAboutStateAssignmentForComponent = new Set();
-  didWarnAboutUninitializedState = new Set();
-  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
-  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
-
-  var didWarnOnInvalidCallback = new Set();
-
-  warnOnInvalidCallback = function(callback, callerName) {
-    if (callback === null || typeof callback === "function") {
-      return;
-    }
-    var key = callerName + "_" + callback;
-    if (!didWarnOnInvalidCallback.has(key)) {
-      didWarnOnInvalidCallback.add(key);
-      warning(
-        false,
-        "%s(...): Expected the last optional `callback` argument to be a " +
-          "function. Instead received: %s.",
-        callerName,
-        callback
-      );
-    }
-  };
-
-  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
-    if (partialState === undefined) {
-      var componentName = getComponentName(workInProgress) || "Component";
-      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-        didWarnAboutUndefinedDerivedState.add(componentName);
-        warning(
-          false,
-          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-            "You have returned undefined.",
-          componentName
-        );
-      }
-    }
-  };
-
-  // This is so gross but it's at least non-critical and can be removed if
-  // it causes problems. This is meant to give a nicer error message for
-  // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
-  // ...)) which otherwise throws a "_processChildContext is not a function"
-  // exception.
-  Object.defineProperty(fakeInternalInstance, "_processChildContext", {
-    enumerable: false,
-    value: function() {
-      invariant(
-        false,
-        "_processChildContext is not available in React 16+. This likely " +
-          "means you have multiple copies of React and are attempting to nest " +
-          "a React 15 tree inside a React 16 tree using " +
-          "unstable_renderSubtreeIntoContainer, which isn't supported. Try " +
-          "to make sure you have only one copy of React (and ideally, switch " +
-          "to ReactDOM.createPortal)."
-      );
-    }
-  });
-  Object.freeze(fakeInternalInstance);
-}
-
-function applyDerivedStateFromProps(
-  workInProgress,
-  getDerivedStateFromProps,
-  nextProps
-) {
-  var prevState = workInProgress.memoizedState;
-
-  {
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      // Invoke the function an extra time to help detect side-effects.
-      getDerivedStateFromProps(nextProps, prevState);
-    }
-  }
-
-  var partialState = getDerivedStateFromProps(nextProps, prevState);
-
-  {
-    warnOnUndefinedDerivedState(workInProgress, partialState);
-  }
-  // Merge the partial state and the previous state.
-  var memoizedState =
-    partialState === null || partialState === undefined
-      ? prevState
-      : Object.assign({}, prevState, partialState);
-  workInProgress.memoizedState = memoizedState;
-
-  // Once the update queue is empty, persist the derived state onto the
-  // base state.
-  var updateQueue = workInProgress.updateQueue;
-  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
-    updateQueue.baseState = memoizedState;
-  }
-}
-
-var ReactFiberClassComponent = function(
-  legacyContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState,
-  recalculateCurrentTime
-) {
-  var cacheContext = legacyContext.cacheContext,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    isContextConsumer = legacyContext.isContextConsumer,
-    hasContextChanged = legacyContext.hasContextChanged;
-
-  var classComponentUpdater = {
-    isMounted: isMounted,
-    enqueueSetState: function(inst, payload, callback) {
-      var fiber = get$1(inst);
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(currentTime, fiber);
-
-      var update = createUpdate(expirationTime);
-      update.payload = payload;
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "setState");
-        }
-        update.callback = callback;
-      }
-
-      enqueueUpdate(fiber, update, expirationTime);
-      scheduleWork(fiber, expirationTime);
-    },
-    enqueueReplaceState: function(inst, payload, callback) {
-      var fiber = get$1(inst);
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(currentTime, fiber);
-
-      var update = createUpdate(expirationTime);
-      update.tag = ReplaceState;
-      update.payload = payload;
-
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "replaceState");
-        }
-        update.callback = callback;
-      }
-
-      enqueueUpdate(fiber, update, expirationTime);
-      scheduleWork(fiber, expirationTime);
-    },
-    enqueueForceUpdate: function(inst, callback) {
-      var fiber = get$1(inst);
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(currentTime, fiber);
-
-      var update = createUpdate(expirationTime);
-      update.tag = ForceUpdate;
-
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "forceUpdate");
-        }
-        update.callback = callback;
-      }
-
-      enqueueUpdate(fiber, update, expirationTime);
-      scheduleWork(fiber, expirationTime);
-    }
-  };
-
-  function checkShouldComponentUpdate(
-    workInProgress,
-    oldProps,
-    newProps,
-    oldState,
-    newState,
-    newContext
-  ) {
-    var instance = workInProgress.stateNode;
-    var ctor = workInProgress.type;
-    if (typeof instance.shouldComponentUpdate === "function") {
-      startPhaseTimer(workInProgress, "shouldComponentUpdate");
-      var shouldUpdate = instance.shouldComponentUpdate(
-        newProps,
-        newState,
-        newContext
-      );
-      stopPhaseTimer();
-
-      {
-        !(shouldUpdate !== undefined)
-          ? warning(
-              false,
-              "%s.shouldComponentUpdate(): Returned undefined instead of a " +
-                "boolean value. Make sure to return true or false.",
-              getComponentName(workInProgress) || "Component"
-            )
-          : void 0;
-      }
-
-      return shouldUpdate;
-    }
-
-    if (ctor.prototype && ctor.prototype.isPureReactComponent) {
-      return (
-        !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
-      );
-    }
-
-    return true;
-  }
+function createCapturedValue(value, source) {
+  // If the value is an error, call this function immediately after it is thrown
+  // so the stack is accurate.
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
 
-  function checkClassInstance(workInProgress) {
-    var instance = workInProgress.stateNode;
-    var type = workInProgress.type;
-    {
-      var name = getComponentName(workInProgress) || "Component";
-      var renderPresent = instance.render;
+var providerCursor = createCursor(null);
+var valueCursor = createCursor(null);
+var changedBitsCursor = createCursor(0);
 
-      if (!renderPresent) {
-        if (type.prototype && typeof type.prototype.render === "function") {
-          warning(
-            false,
-            "%s(...): No `render` method found on the returned component " +
-              "instance: did you accidentally return an object from the constructor?",
-            name
-          );
-        } else {
-          warning(
-            false,
-            "%s(...): No `render` method found on the returned component " +
-              "instance: you may have forgotten to define `render`.",
-            name
-          );
-        }
-      }
+var rendererSigil = void 0;
+{
+  // Use this to detect multiple renderers using the same context
+  rendererSigil = {};
+}
 
-      var noGetInitialStateOnES6 =
-        !instance.getInitialState ||
-        instance.getInitialState.isReactClassApproved ||
-        instance.state;
-      !noGetInitialStateOnES6
-        ? warning(
-            false,
-            "getInitialState was defined on %s, a plain JavaScript class. " +
-              "This is only supported for classes created using React.createClass. " +
-              "Did you mean to define a state property instead?",
-            name
-          )
-        : void 0;
-      var noGetDefaultPropsOnES6 =
-        !instance.getDefaultProps ||
-        instance.getDefaultProps.isReactClassApproved;
-      !noGetDefaultPropsOnES6
-        ? warning(
-            false,
-            "getDefaultProps was defined on %s, a plain JavaScript class. " +
-              "This is only supported for classes created using React.createClass. " +
-              "Use a static property to define defaultProps instead.",
-            name
-          )
-        : void 0;
-      var noInstancePropTypes = !instance.propTypes;
-      !noInstancePropTypes
-        ? warning(
-            false,
-            "propTypes was defined as an instance property on %s. Use a static " +
-              "property to define propTypes instead.",
-            name
-          )
-        : void 0;
-      var noInstanceContextTypes = !instance.contextTypes;
-      !noInstanceContextTypes
-        ? warning(
-            false,
-            "contextTypes was defined as an instance property on %s. Use a static " +
-              "property to define contextTypes instead.",
-            name
-          )
-        : void 0;
-      var noComponentShouldUpdate =
-        typeof instance.componentShouldUpdate !== "function";
-      !noComponentShouldUpdate
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
-              "The name is phrased as a question because the function is " +
-              "expected to return a value.",
-            name
-          )
-        : void 0;
-      if (
-        type.prototype &&
-        type.prototype.isPureReactComponent &&
-        typeof instance.shouldComponentUpdate !== "undefined"
-      ) {
-        warning(
-          false,
-          "%s has a method called shouldComponentUpdate(). " +
-            "shouldComponentUpdate should not be used when extending React.PureComponent. " +
-            "Please extend React.Component if shouldComponentUpdate is used.",
-          getComponentName(workInProgress) || "A pure component"
-        );
-      }
-      var noComponentDidUnmount =
-        typeof instance.componentDidUnmount !== "function";
-      !noComponentDidUnmount
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentDidUnmount(). But there is no such lifecycle method. " +
-              "Did you mean componentWillUnmount()?",
-            name
-          )
-        : void 0;
-      var noComponentDidReceiveProps =
-        typeof instance.componentDidReceiveProps !== "function";
-      !noComponentDidReceiveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentDidReceiveProps(). But there is no such lifecycle method. " +
-              "If you meant to update the state in response to changing props, " +
-              "use componentWillReceiveProps(). If you meant to fetch data or " +
-              "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
-            name
-          )
-        : void 0;
-      var noComponentWillRecieveProps =
-        typeof instance.componentWillRecieveProps !== "function";
-      !noComponentWillRecieveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
-            name
-          )
-        : void 0;
-      var noUnsafeComponentWillRecieveProps =
-        typeof instance.UNSAFE_componentWillRecieveProps !== "function";
-      !noUnsafeComponentWillRecieveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
-            name
-          )
-        : void 0;
-      var hasMutatedProps = instance.props !== workInProgress.pendingProps;
-      !(instance.props === undefined || !hasMutatedProps)
-        ? warning(
-            false,
-            "%s(...): When calling super() in `%s`, make sure to pass " +
-              "up the same props that your component's constructor was passed.",
-            name,
-            name
-          )
-        : void 0;
-      var noInstanceDefaultProps = !instance.defaultProps;
-      !noInstanceDefaultProps
-        ? warning(
-            false,
-            "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
-              " Instead, define defaultProps as a static property on %s.",
-            name,
-            name
-          )
-        : void 0;
+function pushProvider(providerFiber) {
+  var context = providerFiber.type._context;
 
-      if (
-        typeof instance.getSnapshotBeforeUpdate === "function" &&
-        typeof instance.componentDidUpdate !== "function" &&
-        !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
-      ) {
-        didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
-        warning(
-          false,
-          "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
-            "This component defines getSnapshotBeforeUpdate() only.",
-          getComponentName(workInProgress)
-        );
-      }
+  if (isPrimaryRenderer) {
+    push(changedBitsCursor, context._changedBits, providerFiber);
+    push(valueCursor, context._currentValue, providerFiber);
+    push(providerCursor, providerFiber, providerFiber);
 
-      var noInstanceGetDerivedStateFromProps =
-        typeof instance.getDerivedStateFromProps !== "function";
-      !noInstanceGetDerivedStateFromProps
-        ? warning(
-            false,
-            "%s: getDerivedStateFromProps() is defined as an instance method " +
-              "and will be ignored. Instead, declare it as a static method.",
-            name
-          )
-        : void 0;
-      var noInstanceGetDerivedStateFromCatch =
-        typeof instance.getDerivedStateFromCatch !== "function";
-      !noInstanceGetDerivedStateFromCatch
+    context._currentValue = providerFiber.pendingProps.value;
+    context._changedBits = providerFiber.stateNode;
+    {
+      !(
+        context._currentRenderer === undefined ||
+        context._currentRenderer === null ||
+        context._currentRenderer === rendererSigil
+      )
         ? warning(
             false,
-            "%s: getDerivedStateFromCatch() is defined as an instance method " +
-              "and will be ignored. Instead, declare it as a static method.",
-            name
+            "Detected multiple renderers concurrently rendering the " +
+              "same context provider. This is currently unsupported."
           )
         : void 0;
-      var noStaticGetSnapshotBeforeUpdate =
-        typeof type.getSnapshotBeforeUpdate !== "function";
-      !noStaticGetSnapshotBeforeUpdate
+      context._currentRenderer = rendererSigil;
+    }
+  } else {
+    push(changedBitsCursor, context._changedBits2, providerFiber);
+    push(valueCursor, context._currentValue2, providerFiber);
+    push(providerCursor, providerFiber, providerFiber);
+
+    context._currentValue2 = providerFiber.pendingProps.value;
+    context._changedBits2 = providerFiber.stateNode;
+    {
+      !(
+        context._currentRenderer2 === undefined ||
+        context._currentRenderer2 === null ||
+        context._currentRenderer2 === rendererSigil
+      )
         ? warning(
             false,
-            "%s: getSnapshotBeforeUpdate() is defined as a static method " +
-              "and will be ignored. Instead, declare it as an instance method.",
-            name
+            "Detected multiple renderers concurrently rendering the " +
+              "same context provider. This is currently unsupported."
           )
         : void 0;
-      var _state = instance.state;
-      if (_state && (typeof _state !== "object" || isArray(_state))) {
-        warning(false, "%s.state: must be set to an object or null", name);
-      }
-      if (typeof instance.getChildContext === "function") {
-        !(typeof type.childContextTypes === "object")
-          ? warning(
-              false,
-              "%s.getChildContext(): childContextTypes must be defined in order to " +
-                "use getChildContext().",
-              name
-            )
-          : void 0;
-      }
+      context._currentRenderer2 = rendererSigil;
     }
   }
+}
 
-  function adoptClassInstance(workInProgress, instance) {
-    instance.updater = classComponentUpdater;
-    workInProgress.stateNode = instance;
-    // The instance needs access to the fiber so that it can schedule updates
-    set(instance, workInProgress);
-    {
-      instance._reactInternalInstance = fakeInternalInstance;
-    }
+function popProvider(providerFiber) {
+  var changedBits = changedBitsCursor.current;
+  var currentValue = valueCursor.current;
+
+  pop(providerCursor, providerFiber);
+  pop(valueCursor, providerFiber);
+  pop(changedBitsCursor, providerFiber);
+
+  var context = providerFiber.type._context;
+  if (isPrimaryRenderer) {
+    context._currentValue = currentValue;
+    context._changedBits = changedBits;
+  } else {
+    context._currentValue2 = currentValue;
+    context._changedBits2 = changedBits;
   }
+}
 
-  function constructClassInstance(workInProgress, props, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var needsContext = isContextConsumer(workInProgress);
-    var context = needsContext
-      ? getMaskedContext(workInProgress, unmaskedContext)
-      : emptyObject;
+function getContextCurrentValue(context) {
+  return isPrimaryRenderer ? context._currentValue : context._currentValue2;
+}
 
-    // Instantiate twice to help detect side-effects.
-    {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        new ctor(props, context); // eslint-disable-line no-new
-      }
-    }
+function getContextChangedBits(context) {
+  return isPrimaryRenderer ? context._changedBits : context._changedBits2;
+}
 
-    var instance = new ctor(props, context);
-    var state = (workInProgress.memoizedState =
-      instance.state !== null && instance.state !== undefined
-        ? instance.state
-        : null);
-    adoptClassInstance(workInProgress, instance);
+var NO_CONTEXT = {};
 
-    {
-      if (
-        typeof ctor.getDerivedStateFromProps === "function" &&
-        state === null
-      ) {
-        var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutUninitializedState.has(componentName)) {
-          didWarnAboutUninitializedState.add(componentName);
-          warning(
-            false,
-            "%s: Did not properly initialize state during construction. " +
-              "Expected state to be an object, but it was %s.",
-            componentName,
-            instance.state === null ? "null" : "undefined"
-          );
-        }
-      }
+var contextStackCursor$1 = createCursor(NO_CONTEXT);
+var contextFiberStackCursor = createCursor(NO_CONTEXT);
+var rootInstanceStackCursor = createCursor(NO_CONTEXT);
 
-      // If new component APIs are defined, "unsafe" lifecycles won't be called.
-      // Warn about these lifecycles if they are present.
-      // Don't warn about react-lifecycles-compat polyfilled methods though.
-      if (
-        typeof ctor.getDerivedStateFromProps === "function" ||
-        typeof instance.getSnapshotBeforeUpdate === "function"
-      ) {
-        var foundWillMountName = null;
-        var foundWillReceivePropsName = null;
-        var foundWillUpdateName = null;
-        if (
-          typeof instance.componentWillMount === "function" &&
-          instance.componentWillMount.__suppressDeprecationWarning !== true
-        ) {
-          foundWillMountName = "componentWillMount";
-        } else if (typeof instance.UNSAFE_componentWillMount === "function") {
-          foundWillMountName = "UNSAFE_componentWillMount";
-        }
-        if (
-          typeof instance.componentWillReceiveProps === "function" &&
-          instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-            true
-        ) {
-          foundWillReceivePropsName = "componentWillReceiveProps";
-        } else if (
-          typeof instance.UNSAFE_componentWillReceiveProps === "function"
-        ) {
-          foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
-        }
-        if (
-          typeof instance.componentWillUpdate === "function" &&
-          instance.componentWillUpdate.__suppressDeprecationWarning !== true
-        ) {
-          foundWillUpdateName = "componentWillUpdate";
-        } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          foundWillUpdateName = "UNSAFE_componentWillUpdate";
-        }
-        if (
-          foundWillMountName !== null ||
-          foundWillReceivePropsName !== null ||
-          foundWillUpdateName !== null
-        ) {
-          var _componentName = getComponentName(workInProgress) || "Component";
-          var newApiName =
-            typeof ctor.getDerivedStateFromProps === "function"
-              ? "getDerivedStateFromProps()"
-              : "getSnapshotBeforeUpdate()";
-          if (
-            !didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)
-          ) {
-            didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
-            warning(
-              false,
-              "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
-                "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
-                "The above lifecycles should be removed. Learn more about this warning here:\n" +
-                "https://fb.me/react-async-component-lifecycle-hooks",
-              _componentName,
-              newApiName,
-              foundWillMountName !== null ? "\n  " + foundWillMountName : "",
-              foundWillReceivePropsName !== null
-                ? "\n  " + foundWillReceivePropsName
-                : "",
-              foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
-            );
-          }
-        }
-      }
-    }
+function requiredContext(c) {
+  invariant(
+    c !== NO_CONTEXT,
+    "Expected host context to exist. This error is likely caused by a bug " +
+      "in React. Please file an issue."
+  );
+  return c;
+}
 
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // ReactFiberContext usually updates this cache but can't for newly-created instances.
-    if (needsContext) {
-      cacheContext(workInProgress, unmaskedContext, context);
-    }
+function getRootHostContainer() {
+  var rootInstance = requiredContext(rootInstanceStackCursor.current);
+  return rootInstance;
+}
 
-    return instance;
+function pushHostContainer(fiber, nextRootInstance) {
+  // Push current root instance onto the stack;
+  // This allows us to reset root when portals are popped.
+  push(rootInstanceStackCursor, nextRootInstance, fiber);
+  // Track the context and the Fiber that provided it.
+  // This enables us to pop only Fibers that provide unique contexts.
+  push(contextFiberStackCursor, fiber, fiber);
+
+  // Finally, we need to push the host context to the stack.
+  // However, we can't just call getRootHostContext() and push it because
+  // we'd have a different number of entries on the stack depending on
+  // whether getRootHostContext() throws somewhere in renderer code or not.
+  // So we push an empty value first. This lets us safely unwind on errors.
+  push(contextStackCursor$1, NO_CONTEXT, fiber);
+  var nextRootContext = getRootHostContext(nextRootInstance);
+  // Now that we know this function doesn't throw, replace it.
+  pop(contextStackCursor$1, fiber);
+  push(contextStackCursor$1, nextRootContext, fiber);
+}
+
+function popHostContainer(fiber) {
+  pop(contextStackCursor$1, fiber);
+  pop(contextFiberStackCursor, fiber);
+  pop(rootInstanceStackCursor, fiber);
+}
+
+function getHostContext() {
+  var context = requiredContext(contextStackCursor$1.current);
+  return context;
+}
+
+function pushHostContext(fiber) {
+  var rootInstance = requiredContext(rootInstanceStackCursor.current);
+  var context = requiredContext(contextStackCursor$1.current);
+  var nextContext = getChildHostContext(context, fiber.type, rootInstance);
+
+  // Don't push this Fiber's context unless it's unique.
+  if (context === nextContext) {
+    return;
   }
 
-  function callComponentWillMount(workInProgress, instance) {
-    startPhaseTimer(workInProgress, "componentWillMount");
-    var oldState = instance.state;
+  // Track the context and the Fiber that provided it.
+  // This enables us to pop only Fibers that provide unique contexts.
+  push(contextFiberStackCursor, fiber, fiber);
+  push(contextStackCursor$1, nextContext, fiber);
+}
 
-    if (typeof instance.componentWillMount === "function") {
-      instance.componentWillMount();
-    }
-    if (typeof instance.UNSAFE_componentWillMount === "function") {
-      instance.UNSAFE_componentWillMount();
-    }
+function popHostContext(fiber) {
+  // Do not pop unless this Fiber provided the current context.
+  // pushHostContext() only pushes Fibers that provide unique contexts.
+  if (contextFiberStackCursor.current !== fiber) {
+    return;
+  }
 
-    stopPhaseTimer();
+  pop(contextStackCursor$1, fiber);
+  pop(contextFiberStackCursor, fiber);
+}
 
-    if (oldState !== instance.state) {
-      {
-        warning(
+var commitTime = 0;
+
+function getCommitTime() {
+  return commitTime;
+}
+
+function recordCommitTime() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  commitTime = now();
+}
+
+/**
+ * The "actual" render time is total time required to render the descendants of a Profiler component.
+ * This time is stored as a stack, since Profilers can be nested.
+ * This time is started during the "begin" phase and stopped during the "complete" phase.
+ * It is paused (and accumulated) in the event of an interruption or an aborted render.
+ */
+
+var fiberStack$1 = void 0;
+
+{
+  fiberStack$1 = [];
+}
+
+var timerPausedAt = 0;
+var totalElapsedPauseTime = 0;
+
+function checkActualRenderTimeStackEmpty() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  {
+    !(fiberStack$1.length === 0)
+      ? warning(
           false,
-          "%s.componentWillMount(): Assigning directly to this.state is " +
-            "deprecated (except inside a component's " +
-            "constructor). Use setState instead.",
-          getComponentName(workInProgress) || "Component"
-        );
-      }
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
-    }
+          "Expected an empty stack. Something was not reset properly."
+        )
+      : void 0;
   }
+}
 
-  function callComponentWillReceiveProps(
-    workInProgress,
-    instance,
-    newProps,
-    newContext
-  ) {
-    var oldState = instance.state;
-    startPhaseTimer(workInProgress, "componentWillReceiveProps");
-    if (typeof instance.componentWillReceiveProps === "function") {
-      instance.componentWillReceiveProps(newProps, newContext);
-    }
-    if (typeof instance.UNSAFE_componentWillReceiveProps === "function") {
-      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
-    }
-    stopPhaseTimer();
+function markActualRenderTimeStarted(fiber) {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  {
+    fiberStack$1.push(fiber);
+  }
 
-    if (instance.state !== oldState) {
-      {
-        var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
-          didWarnAboutStateAssignmentForComponent.add(componentName);
-          warning(
-            false,
-            "%s.componentWillReceiveProps(): Assigning directly to " +
-              "this.state is deprecated (except inside a component's " +
-              "constructor). Use setState instead.",
-            componentName
-          );
-        }
-      }
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+  fiber.actualDuration = now() - fiber.actualDuration - totalElapsedPauseTime;
+  fiber.actualStartTime = now();
+}
+
+function pauseActualRenderTimerIfRunning() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  if (timerPausedAt === 0) {
+    timerPausedAt = now();
+  }
+}
+
+function recordElapsedActualRenderTime(fiber) {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  {
+    !(fiber === fiberStack$1.pop())
+      ? warning(false, "Unexpected Fiber (%s) popped.", getComponentName(fiber))
+      : void 0;
+  }
+
+  fiber.actualDuration = now() - totalElapsedPauseTime - fiber.actualDuration;
+}
+
+function resetActualRenderTimer() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  totalElapsedPauseTime = 0;
+}
+
+function resumeActualRenderTimerIfPaused() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  if (timerPausedAt > 0) {
+    totalElapsedPauseTime += now() - timerPausedAt;
+    timerPausedAt = 0;
+  }
+}
+
+/**
+ * The "base" render time is the duration of the “begin” phase of work for a particular fiber.
+ * This time is measured and stored on each fiber.
+ * The time for all sibling fibers are accumulated and stored on their parent during the "complete" phase.
+ * If a fiber bails out (sCU false) then its "base" timer is cancelled and the fiber is not updated.
+ */
+
+var baseStartTime = -1;
+
+function recordElapsedBaseRenderTimeIfRunning(fiber) {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  if (baseStartTime !== -1) {
+    fiber.selfBaseTime = now() - baseStartTime;
+  }
+}
+
+function startBaseRenderTimer() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  {
+    if (baseStartTime !== -1) {
+      warning(
+        false,
+        "Cannot start base timer that is already running. " +
+          "This error is likely caused by a bug in React. " +
+          "Please file an issue."
+      );
     }
   }
+  baseStartTime = now();
+}
 
-  // Invokes the mount life-cycles on a previously never rendered instance.
-  function mountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
+function stopBaseRenderTimerIfRunning() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  baseStartTime = -1;
+}
 
-    {
-      checkClassInstance(workInProgress);
-    }
+/*eslint-disable no-self-compare */
 
-    var instance = workInProgress.stateNode;
-    var props = workInProgress.pendingProps;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
+var hasOwnProperty = Object.prototype.hasOwnProperty;
 
-    instance.props = props;
-    instance.state = workInProgress.memoizedState;
-    instance.refs = emptyObject;
-    instance.context = getMaskedContext(workInProgress, unmaskedContext);
+/**
+ * inlined Object.is polyfill to avoid requiring consumers ship their own
+ * https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+ */
+function is(x, y) {
+  // SameValue algorithm
+  if (x === y) {
+    // Steps 1-5, 7-10
+    // Steps 6.b-6.e: +0 != -0
+    // Added the nonzero y check to make Flow happy, but it is redundant
+    return x !== 0 || y !== 0 || 1 / x === 1 / y;
+  } else {
+    // Step 6.a: NaN == NaN
+    return x !== x && y !== y;
+  }
+}
 
-    {
-      if (workInProgress.mode & StrictMode) {
-        ReactStrictModeWarnings.recordUnsafeLifecycleWarnings(
-          workInProgress,
-          instance
-        );
-      }
+/**
+ * Performs equality by iterating through keys on an object and returning false
+ * when any key has values which are not strictly equal between the arguments.
+ * Returns true when the values of all keys are strictly equal.
+ */
+function shallowEqual(objA, objB) {
+  if (is(objA, objB)) {
+    return true;
+  }
 
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.recordDeprecationWarnings(
-          workInProgress,
-          instance
-        );
-      }
-    }
+  if (
+    typeof objA !== "object" ||
+    objA === null ||
+    typeof objB !== "object" ||
+    objB === null
+  ) {
+    return false;
+  }
 
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        props,
-        instance,
-        renderExpirationTime
-      );
-      instance.state = workInProgress.memoizedState;
-    }
+  var keysA = Object.keys(objA);
+  var keysB = Object.keys(objB);
 
-    var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
-        workInProgress,
-        getDerivedStateFromProps,
-        props
-      );
-      instance.state = workInProgress.memoizedState;
-    }
+  if (keysA.length !== keysB.length) {
+    return false;
+  }
 
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
+  // Test for A's keys different from B.
+  for (var i = 0; i < keysA.length; i++) {
     if (
-      typeof ctor.getDerivedStateFromProps !== "function" &&
-      typeof instance.getSnapshotBeforeUpdate !== "function" &&
-      (typeof instance.UNSAFE_componentWillMount === "function" ||
-        typeof instance.componentWillMount === "function")
+      !hasOwnProperty.call(objB, keysA[i]) ||
+      !is(objA[keysA[i]], objB[keysA[i]])
     ) {
-      callComponentWillMount(workInProgress, instance);
-      // If we had additional state updates during this life-cycle, let's
-      // process them now.
-      updateQueue = workInProgress.updateQueue;
-      if (updateQueue !== null) {
-        processUpdateQueue(
-          workInProgress,
-          updateQueue,
-          props,
-          instance,
-          renderExpirationTime
-        );
-        instance.state = workInProgress.memoizedState;
-      }
-    }
-
-    if (typeof instance.componentDidMount === "function") {
-      workInProgress.effectTag |= Update;
+      return false;
     }
   }
 
-  function resumeMountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
+  return true;
+}
 
-    var oldProps = workInProgress.memoizedProps;
-    var newProps = workInProgress.pendingProps;
-    instance.props = oldProps;
+var fakeInternalInstance = {};
+var isArray = Array.isArray;
 
-    var oldContext = instance.context;
-    var newUnmaskedContext = getUnmaskedContext(workInProgress);
-    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+var didWarnAboutStateAssignmentForComponent = void 0;
+var didWarnAboutUninitializedState = void 0;
+var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
+var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
+var warnOnUndefinedDerivedState = void 0;
+var warnOnInvalidCallback = void 0;
 
-    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
-    var hasNewLifecycles =
-      typeof getDerivedStateFromProps === "function" ||
-      typeof instance.getSnapshotBeforeUpdate === "function";
+{
+  didWarnAboutStateAssignmentForComponent = new Set();
+  didWarnAboutUninitializedState = new Set();
+  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
+  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
 
-    // Note: During these life-cycles, instance.props/instance.state are what
-    // ever the previously attempted to render - not the "current". However,
-    // during componentDidUpdate we pass the "current" props.
+  var didWarnOnInvalidCallback = new Set();
 
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      !hasNewLifecycles &&
-      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function")
-    ) {
-      if (oldProps !== newProps || oldContext !== newContext) {
-        callComponentWillReceiveProps(
-          workInProgress,
-          instance,
-          newProps,
-          newContext
-        );
-      }
+  warnOnInvalidCallback = function(callback, callerName) {
+    if (callback === null || typeof callback === "function") {
+      return;
     }
-
-    resetHasForceUpdateBeforeProcessing();
-
-    var oldState = workInProgress.memoizedState;
-    var newState = (instance.state = oldState);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        newProps,
-        instance,
-        renderExpirationTime
+    var key = callerName + "_" + callback;
+    if (!didWarnOnInvalidCallback.has(key)) {
+      didWarnOnInvalidCallback.add(key);
+      warning(
+        false,
+        "%s(...): Expected the last optional `callback` argument to be a " +
+          "function. Instead received: %s.",
+        callerName,
+        callback
       );
-      newState = workInProgress.memoizedState;
     }
-    if (
-      oldProps === newProps &&
-      oldState === newState &&
-      !hasContextChanged() &&
-      !checkHasForceUpdateAfterProcessing()
-    ) {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
+  };
+
+  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
+    if (partialState === undefined) {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+        didWarnAboutUndefinedDerivedState.add(componentName);
+        warning(
+          false,
+          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+            "You have returned undefined.",
+          componentName
+        );
       }
-      return false;
     }
+  };
 
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
-        workInProgress,
-        getDerivedStateFromProps,
-        newProps
+  // This is so gross but it's at least non-critical and can be removed if
+  // it causes problems. This is meant to give a nicer error message for
+  // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
+  // ...)) which otherwise throws a "_processChildContext is not a function"
+  // exception.
+  Object.defineProperty(fakeInternalInstance, "_processChildContext", {
+    enumerable: false,
+    value: function() {
+      invariant(
+        false,
+        "_processChildContext is not available in React 16+. This likely " +
+          "means you have multiple copies of React and are attempting to nest " +
+          "a React 15 tree inside a React 16 tree using " +
+          "unstable_renderSubtreeIntoContainer, which isn't supported. Try " +
+          "to make sure you have only one copy of React (and ideally, switch " +
+          "to ReactDOM.createPortal)."
       );
-      newState = workInProgress.memoizedState;
     }
+  });
+  Object.freeze(fakeInternalInstance);
+}
 
-    var shouldUpdate =
-      checkHasForceUpdateAfterProcessing() ||
-      checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldState,
-        newState,
-        newContext
-      );
-
-    if (shouldUpdate) {
-      // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for components using the new APIs.
-      if (
-        !hasNewLifecycles &&
-        (typeof instance.UNSAFE_componentWillMount === "function" ||
-          typeof instance.componentWillMount === "function")
-      ) {
-        startPhaseTimer(workInProgress, "componentWillMount");
-        if (typeof instance.componentWillMount === "function") {
-          instance.componentWillMount();
-        }
-        if (typeof instance.UNSAFE_componentWillMount === "function") {
-          instance.UNSAFE_componentWillMount();
-        }
-        stopPhaseTimer();
-      }
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-    } else {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
 
-      // If shouldComponentUpdate returned false, we should still update the
-      // memoized state to indicate that this work can be reused.
-      workInProgress.memoizedProps = newProps;
-      workInProgress.memoizedState = newState;
+  {
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      // Invoke the function an extra time to help detect side-effects.
+      getDerivedStateFromProps(nextProps, prevState);
     }
-
-    // Update the existing instance's state, props, and context pointers even
-    // if shouldComponentUpdate returns false.
-    instance.props = newProps;
-    instance.state = newState;
-    instance.context = newContext;
-
-    return shouldUpdate;
   }
 
-  // Invokes the update life-cycles and returns false if it shouldn't rerender.
-  function updateClassInstance(current, workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-
-    var oldProps = workInProgress.memoizedProps;
-    var newProps = workInProgress.pendingProps;
-    instance.props = oldProps;
+  var partialState = getDerivedStateFromProps(nextProps, prevState);
 
-    var oldContext = instance.context;
-    var newUnmaskedContext = getUnmaskedContext(workInProgress);
-    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+  {
+    warnOnUndefinedDerivedState(workInProgress, partialState);
+  }
+  // Merge the partial state and the previous state.
+  var memoizedState =
+    partialState === null || partialState === undefined
+      ? prevState
+      : Object.assign({}, prevState, partialState);
+  workInProgress.memoizedState = memoizedState;
 
-    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
-    var hasNewLifecycles =
-      typeof getDerivedStateFromProps === "function" ||
-      typeof instance.getSnapshotBeforeUpdate === "function";
+  // Once the update queue is empty, persist the derived state onto the
+  // base state.
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
+    updateQueue.baseState = memoizedState;
+  }
+}
 
-    // Note: During these life-cycles, instance.props/instance.state are what
-    // ever the previously attempted to render - not the "current". However,
-    // during componentDidUpdate we pass the "current" props.
+var classComponentUpdater = {
+  isMounted: isMounted,
+  enqueueSetState: function(inst, payload, callback) {
+    var fiber = get$1(inst);
+    var currentTime = recalculateCurrentTime();
+    var expirationTime = computeExpirationForFiber(currentTime, fiber);
 
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      !hasNewLifecycles &&
-      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function")
-    ) {
-      if (oldProps !== newProps || oldContext !== newContext) {
-        callComponentWillReceiveProps(
-          workInProgress,
-          instance,
-          newProps,
-          newContext
-        );
+    var update = createUpdate(expirationTime);
+    update.payload = payload;
+    if (callback !== undefined && callback !== null) {
+      {
+        warnOnInvalidCallback(callback, "setState");
       }
+      update.callback = callback;
     }
 
-    resetHasForceUpdateBeforeProcessing();
+    enqueueUpdate(fiber, update, expirationTime);
+    scheduleWork(fiber, expirationTime);
+  },
+  enqueueReplaceState: function(inst, payload, callback) {
+    var fiber = get$1(inst);
+    var currentTime = recalculateCurrentTime();
+    var expirationTime = computeExpirationForFiber(currentTime, fiber);
 
-    var oldState = workInProgress.memoizedState;
-    var newState = (instance.state = oldState);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        newProps,
-        instance,
-        renderExpirationTime
-      );
-      newState = workInProgress.memoizedState;
-    }
+    var update = createUpdate(expirationTime);
+    update.tag = ReplaceState;
+    update.payload = payload;
 
-    if (
-      oldProps === newProps &&
-      oldState === newState &&
-      !hasContextChanged() &&
-      !checkHasForceUpdateAfterProcessing()
-    ) {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Update;
-        }
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Snapshot;
-        }
+    if (callback !== undefined && callback !== null) {
+      {
+        warnOnInvalidCallback(callback, "replaceState");
       }
-      return false;
+      update.callback = callback;
     }
 
-    if (typeof getDerivedStateFromProps === "function") {
-      if (fireGetDerivedStateFromPropsOnStateUpdates || oldProps !== newProps) {
-        applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        );
-        newState = workInProgress.memoizedState;
+    enqueueUpdate(fiber, update, expirationTime);
+    scheduleWork(fiber, expirationTime);
+  },
+  enqueueForceUpdate: function(inst, callback) {
+    var fiber = get$1(inst);
+    var currentTime = recalculateCurrentTime();
+    var expirationTime = computeExpirationForFiber(currentTime, fiber);
+
+    var update = createUpdate(expirationTime);
+    update.tag = ForceUpdate;
+
+    if (callback !== undefined && callback !== null) {
+      {
+        warnOnInvalidCallback(callback, "forceUpdate");
       }
+      update.callback = callback;
     }
 
-    var shouldUpdate =
-      checkHasForceUpdateAfterProcessing() ||
-      checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldState,
-        newState,
-        newContext
-      );
+    enqueueUpdate(fiber, update, expirationTime);
+    scheduleWork(fiber, expirationTime);
+  }
+};
 
-    if (shouldUpdate) {
-      // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for components using the new APIs.
-      if (
-        !hasNewLifecycles &&
-        (typeof instance.UNSAFE_componentWillUpdate === "function" ||
-          typeof instance.componentWillUpdate === "function")
-      ) {
-        startPhaseTimer(workInProgress, "componentWillUpdate");
-        if (typeof instance.componentWillUpdate === "function") {
-          instance.componentWillUpdate(newProps, newState, newContext);
-        }
-        if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
-        }
-        stopPhaseTimer();
-      }
-      if (typeof instance.componentDidUpdate === "function") {
-        workInProgress.effectTag |= Update;
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        workInProgress.effectTag |= Snapshot;
-      }
-    } else {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Update;
-        }
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Snapshot;
-        }
-      }
+function checkShouldComponentUpdate(
+  workInProgress,
+  oldProps,
+  newProps,
+  oldState,
+  newState,
+  newContext
+) {
+  var instance = workInProgress.stateNode;
+  var ctor = workInProgress.type;
+  if (typeof instance.shouldComponentUpdate === "function") {
+    startPhaseTimer(workInProgress, "shouldComponentUpdate");
+    var shouldUpdate = instance.shouldComponentUpdate(
+      newProps,
+      newState,
+      newContext
+    );
+    stopPhaseTimer();
 
-      // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      workInProgress.memoizedProps = newProps;
-      workInProgress.memoizedState = newState;
+    {
+      !(shouldUpdate !== undefined)
+        ? warning(
+            false,
+            "%s.shouldComponentUpdate(): Returned undefined instead of a " +
+              "boolean value. Make sure to return true or false.",
+            getComponentName(workInProgress) || "Component"
+          )
+        : void 0;
     }
 
-    // Update the existing instance's state, props, and context pointers even
-    // if shouldComponentUpdate returns false.
-    instance.props = newProps;
-    instance.state = newState;
-    instance.context = newContext;
-
     return shouldUpdate;
   }
 
-  return {
-    adoptClassInstance: adoptClassInstance,
-    constructClassInstance: constructClassInstance,
-    mountClassInstance: mountClassInstance,
-    resumeMountClassInstance: resumeMountClassInstance,
-    updateClassInstance: updateClassInstance
-  };
-};
-
-var getCurrentFiberStackAddendum$2 =
-  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+  if (ctor.prototype && ctor.prototype.isPureReactComponent) {
+    return (
+      !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+    );
+  }
 
-var didWarnAboutMaps = void 0;
-var didWarnAboutStringRefInStrictMode = void 0;
-var ownerHasKeyUseWarning = void 0;
-var ownerHasFunctionTypeWarning = void 0;
-var warnForMissingKey = function(child) {};
+  return true;
+}
 
-{
-  didWarnAboutMaps = false;
-  didWarnAboutStringRefInStrictMode = {};
+function checkClassInstance(workInProgress) {
+  var instance = workInProgress.stateNode;
+  var type = workInProgress.type;
+  {
+    var name = getComponentName(workInProgress) || "Component";
+    var renderPresent = instance.render;
 
-  /**
-   * Warn if there's no key explicitly set on dynamic arrays of children or
-   * object keys are not valid. This allows us to keep track of children between
-   * updates.
-   */
-  ownerHasKeyUseWarning = {};
-  ownerHasFunctionTypeWarning = {};
+    if (!renderPresent) {
+      if (type.prototype && typeof type.prototype.render === "function") {
+        warning(
+          false,
+          "%s(...): No `render` method found on the returned component " +
+            "instance: did you accidentally return an object from the constructor?",
+          name
+        );
+      } else {
+        warning(
+          false,
+          "%s(...): No `render` method found on the returned component " +
+            "instance: you may have forgotten to define `render`.",
+          name
+        );
+      }
+    }
 
-  warnForMissingKey = function(child) {
-    if (child === null || typeof child !== "object") {
-      return;
+    var noGetInitialStateOnES6 =
+      !instance.getInitialState ||
+      instance.getInitialState.isReactClassApproved ||
+      instance.state;
+    !noGetInitialStateOnES6
+      ? warning(
+          false,
+          "getInitialState was defined on %s, a plain JavaScript class. " +
+            "This is only supported for classes created using React.createClass. " +
+            "Did you mean to define a state property instead?",
+          name
+        )
+      : void 0;
+    var noGetDefaultPropsOnES6 =
+      !instance.getDefaultProps ||
+      instance.getDefaultProps.isReactClassApproved;
+    !noGetDefaultPropsOnES6
+      ? warning(
+          false,
+          "getDefaultProps was defined on %s, a plain JavaScript class. " +
+            "This is only supported for classes created using React.createClass. " +
+            "Use a static property to define defaultProps instead.",
+          name
+        )
+      : void 0;
+    var noInstancePropTypes = !instance.propTypes;
+    !noInstancePropTypes
+      ? warning(
+          false,
+          "propTypes was defined as an instance property on %s. Use a static " +
+            "property to define propTypes instead.",
+          name
+        )
+      : void 0;
+    var noInstanceContextTypes = !instance.contextTypes;
+    !noInstanceContextTypes
+      ? warning(
+          false,
+          "contextTypes was defined as an instance property on %s. Use a static " +
+            "property to define contextTypes instead.",
+          name
+        )
+      : void 0;
+    var noComponentShouldUpdate =
+      typeof instance.componentShouldUpdate !== "function";
+    !noComponentShouldUpdate
+      ? warning(
+          false,
+          "%s has a method called " +
+            "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
+            "The name is phrased as a question because the function is " +
+            "expected to return a value.",
+          name
+        )
+      : void 0;
+    if (
+      type.prototype &&
+      type.prototype.isPureReactComponent &&
+      typeof instance.shouldComponentUpdate !== "undefined"
+    ) {
+      warning(
+        false,
+        "%s has a method called shouldComponentUpdate(). " +
+          "shouldComponentUpdate should not be used when extending React.PureComponent. " +
+          "Please extend React.Component if shouldComponentUpdate is used.",
+        getComponentName(workInProgress) || "A pure component"
+      );
     }
-    if (!child._store || child._store.validated || child.key != null) {
-      return;
+    var noComponentDidUnmount =
+      typeof instance.componentDidUnmount !== "function";
+    !noComponentDidUnmount
+      ? warning(
+          false,
+          "%s has a method called " +
+            "componentDidUnmount(). But there is no such lifecycle method. " +
+            "Did you mean componentWillUnmount()?",
+          name
+        )
+      : void 0;
+    var noComponentDidReceiveProps =
+      typeof instance.componentDidReceiveProps !== "function";
+    !noComponentDidReceiveProps
+      ? warning(
+          false,
+          "%s has a method called " +
+            "componentDidReceiveProps(). But there is no such lifecycle method. " +
+            "If you meant to update the state in response to changing props, " +
+            "use componentWillReceiveProps(). If you meant to fetch data or " +
+            "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
+          name
+        )
+      : void 0;
+    var noComponentWillRecieveProps =
+      typeof instance.componentWillRecieveProps !== "function";
+    !noComponentWillRecieveProps
+      ? warning(
+          false,
+          "%s has a method called " +
+            "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
+          name
+        )
+      : void 0;
+    var noUnsafeComponentWillRecieveProps =
+      typeof instance.UNSAFE_componentWillRecieveProps !== "function";
+    !noUnsafeComponentWillRecieveProps
+      ? warning(
+          false,
+          "%s has a method called " +
+            "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
+          name
+        )
+      : void 0;
+    var hasMutatedProps = instance.props !== workInProgress.pendingProps;
+    !(instance.props === undefined || !hasMutatedProps)
+      ? warning(
+          false,
+          "%s(...): When calling super() in `%s`, make sure to pass " +
+            "up the same props that your component's constructor was passed.",
+          name,
+          name
+        )
+      : void 0;
+    var noInstanceDefaultProps = !instance.defaultProps;
+    !noInstanceDefaultProps
+      ? warning(
+          false,
+          "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
+            " Instead, define defaultProps as a static property on %s.",
+          name,
+          name
+        )
+      : void 0;
+
+    if (
+      typeof instance.getSnapshotBeforeUpdate === "function" &&
+      typeof instance.componentDidUpdate !== "function" &&
+      !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
+    ) {
+      didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
+      warning(
+        false,
+        "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
+          "This component defines getSnapshotBeforeUpdate() only.",
+        getComponentName(workInProgress)
+      );
     }
-    invariant(
-      typeof child._store === "object",
-      "React Component in warnForMissingKey should have a _store. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-    child._store.validated = true;
 
-    var currentComponentErrorInfo =
-      "Each child in an array or iterator should have a unique " +
-      '"key" prop. See https://fb.me/react-warning-keys for ' +
-      "more information." +
-      (getCurrentFiberStackAddendum$2() || "");
-    if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
-      return;
+    var noInstanceGetDerivedStateFromProps =
+      typeof instance.getDerivedStateFromProps !== "function";
+    !noInstanceGetDerivedStateFromProps
+      ? warning(
+          false,
+          "%s: getDerivedStateFromProps() is defined as an instance method " +
+            "and will be ignored. Instead, declare it as a static method.",
+          name
+        )
+      : void 0;
+    var noInstanceGetDerivedStateFromCatch =
+      typeof instance.getDerivedStateFromCatch !== "function";
+    !noInstanceGetDerivedStateFromCatch
+      ? warning(
+          false,
+          "%s: getDerivedStateFromCatch() is defined as an instance method " +
+            "and will be ignored. Instead, declare it as a static method.",
+          name
+        )
+      : void 0;
+    var noStaticGetSnapshotBeforeUpdate =
+      typeof type.getSnapshotBeforeUpdate !== "function";
+    !noStaticGetSnapshotBeforeUpdate
+      ? warning(
+          false,
+          "%s: getSnapshotBeforeUpdate() is defined as a static method " +
+            "and will be ignored. Instead, declare it as an instance method.",
+          name
+        )
+      : void 0;
+    var _state = instance.state;
+    if (_state && (typeof _state !== "object" || isArray(_state))) {
+      warning(false, "%s.state: must be set to an object or null", name);
     }
-    ownerHasKeyUseWarning[currentComponentErrorInfo] = true;
+    if (typeof instance.getChildContext === "function") {
+      !(typeof type.childContextTypes === "object")
+        ? warning(
+            false,
+            "%s.getChildContext(): childContextTypes must be defined in order to " +
+              "use getChildContext().",
+            name
+          )
+        : void 0;
+    }
+  }
+}
 
-    warning(
-      false,
-      "Each child in an array or iterator should have a unique " +
-        '"key" prop. See https://fb.me/react-warning-keys for ' +
-        "more information.%s",
-      getCurrentFiberStackAddendum$2()
-    );
-  };
+function adoptClassInstance(workInProgress, instance) {
+  instance.updater = classComponentUpdater;
+  workInProgress.stateNode = instance;
+  // The instance needs access to the fiber so that it can schedule updates
+  set(instance, workInProgress);
+  {
+    instance._reactInternalInstance = fakeInternalInstance;
+  }
 }
 
-var isArray$1 = Array.isArray;
+function constructClassInstance(workInProgress, props, renderExpirationTime) {
+  var ctor = workInProgress.type;
+  var unmaskedContext = getUnmaskedContext(workInProgress);
+  var needsContext = isContextConsumer(workInProgress);
+  var context = needsContext
+    ? getMaskedContext(workInProgress, unmaskedContext)
+    : emptyObject;
 
-function coerceRef(returnFiber, current, element) {
-  var mixedRef = element.ref;
-  if (
-    mixedRef !== null &&
-    typeof mixedRef !== "function" &&
-    typeof mixedRef !== "object"
-  ) {
-    {
-      if (returnFiber.mode & StrictMode) {
-        var componentName = getComponentName(returnFiber) || "Component";
-        if (!didWarnAboutStringRefInStrictMode[componentName]) {
-          warning(
-            false,
-            'A string ref, "%s", has been found within a strict mode tree. ' +
-              "String refs are a source of potential bugs and should be avoided. " +
-              "We recommend using createRef() instead." +
-              "\n%s" +
-              "\n\nLearn more about using refs safely here:" +
-              "\nhttps://fb.me/react-strict-mode-string-ref",
-            mixedRef,
-            getStackAddendumByWorkInProgressFiber(returnFiber)
-          );
-          didWarnAboutStringRefInStrictMode[componentName] = true;
-        }
-      }
+  // Instantiate twice to help detect side-effects.
+  {
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      new ctor(props, context); // eslint-disable-line no-new
     }
+  }
 
-    if (element._owner) {
-      var owner = element._owner;
-      var inst = void 0;
-      if (owner) {
-        var ownerFiber = owner;
-        invariant(
-          ownerFiber.tag === ClassComponent,
-          "Stateless function components cannot have refs."
+  var instance = new ctor(props, context);
+  var state = (workInProgress.memoizedState =
+    instance.state !== null && instance.state !== undefined
+      ? instance.state
+      : null);
+  adoptClassInstance(workInProgress, instance);
+
+  {
+    if (typeof ctor.getDerivedStateFromProps === "function" && state === null) {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutUninitializedState.has(componentName)) {
+        didWarnAboutUninitializedState.add(componentName);
+        warning(
+          false,
+          "%s: Did not properly initialize state during construction. " +
+            "Expected state to be an object, but it was %s.",
+          componentName,
+          instance.state === null ? "null" : "undefined"
         );
-        inst = ownerFiber.stateNode;
       }
-      invariant(
-        inst,
-        "Missing owner for string ref %s. This error is likely caused by a " +
-          "bug in React. Please file an issue.",
-        mixedRef
-      );
-      var stringRef = "" + mixedRef;
-      // Check if previous string ref matches new string ref
+    }
+
+    // If new component APIs are defined, "unsafe" lifecycles won't be called.
+    // Warn about these lifecycles if they are present.
+    // Don't warn about react-lifecycles-compat polyfilled methods though.
+    if (
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function"
+    ) {
+      var foundWillMountName = null;
+      var foundWillReceivePropsName = null;
+      var foundWillUpdateName = null;
       if (
-        current !== null &&
-        current.ref !== null &&
-        current.ref._stringRef === stringRef
+        typeof instance.componentWillMount === "function" &&
+        instance.componentWillMount.__suppressDeprecationWarning !== true
       ) {
-        return current.ref;
+        foundWillMountName = "componentWillMount";
+      } else if (typeof instance.UNSAFE_componentWillMount === "function") {
+        foundWillMountName = "UNSAFE_componentWillMount";
       }
-      var ref = function(value) {
-        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
-        if (value === null) {
-          delete refs[stringRef];
-        } else {
-          refs[stringRef] = value;
+      if (
+        typeof instance.componentWillReceiveProps === "function" &&
+        instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+      ) {
+        foundWillReceivePropsName = "componentWillReceiveProps";
+      } else if (
+        typeof instance.UNSAFE_componentWillReceiveProps === "function"
+      ) {
+        foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
+      }
+      if (
+        typeof instance.componentWillUpdate === "function" &&
+        instance.componentWillUpdate.__suppressDeprecationWarning !== true
+      ) {
+        foundWillUpdateName = "componentWillUpdate";
+      } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+        foundWillUpdateName = "UNSAFE_componentWillUpdate";
+      }
+      if (
+        foundWillMountName !== null ||
+        foundWillReceivePropsName !== null ||
+        foundWillUpdateName !== null
+      ) {
+        var _componentName = getComponentName(workInProgress) || "Component";
+        var newApiName =
+          typeof ctor.getDerivedStateFromProps === "function"
+            ? "getDerivedStateFromProps()"
+            : "getSnapshotBeforeUpdate()";
+        if (!didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)) {
+          didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
+          warning(
+            false,
+            "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
+              "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
+              "The above lifecycles should be removed. Learn more about this warning here:\n" +
+              "https://fb.me/react-async-component-lifecycle-hooks",
+            _componentName,
+            newApiName,
+            foundWillMountName !== null ? "\n  " + foundWillMountName : "",
+            foundWillReceivePropsName !== null
+              ? "\n  " + foundWillReceivePropsName
+              : "",
+            foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
+          );
         }
-      };
-      ref._stringRef = stringRef;
-      return ref;
-    } else {
-      invariant(
-        typeof mixedRef === "string",
-        "Expected ref to be a function or a string."
-      );
-      invariant(
-        element._owner,
-        "Element ref was specified as a string (%s) but no owner was set. This could happen for one of" +
-          " the following reasons:\n" +
-          "1. You may be adding a ref to a functional component\n" +
-          "2. You may be adding a ref to a component that was not created inside a component's render method\n" +
-          "3. You have multiple copies of React loaded\n" +
-          "See https://fb.me/react-refs-must-have-owner for more information.",
-        mixedRef
+      }
+    }
+  }
+
+  // Cache unmasked context so we can avoid recreating masked context unless necessary.
+  // ReactFiberContext usually updates this cache but can't for newly-created instances.
+  if (needsContext) {
+    cacheContext(workInProgress, unmaskedContext, context);
+  }
+
+  return instance;
+}
+
+function callComponentWillMount(workInProgress, instance) {
+  startPhaseTimer(workInProgress, "componentWillMount");
+  var oldState = instance.state;
+
+  if (typeof instance.componentWillMount === "function") {
+    instance.componentWillMount();
+  }
+  if (typeof instance.UNSAFE_componentWillMount === "function") {
+    instance.UNSAFE_componentWillMount();
+  }
+
+  stopPhaseTimer();
+
+  if (oldState !== instance.state) {
+    {
+      warning(
+        false,
+        "%s.componentWillMount(): Assigning directly to this.state is " +
+          "deprecated (except inside a component's " +
+          "constructor). Use setState instead.",
+        getComponentName(workInProgress) || "Component"
       );
     }
+    classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
   }
-  return mixedRef;
 }
 
-function throwOnInvalidObjectType(returnFiber, newChild) {
-  if (returnFiber.type !== "textarea") {
-    var addendum = "";
+function callComponentWillReceiveProps(
+  workInProgress,
+  instance,
+  newProps,
+  newContext
+) {
+  var oldState = instance.state;
+  startPhaseTimer(workInProgress, "componentWillReceiveProps");
+  if (typeof instance.componentWillReceiveProps === "function") {
+    instance.componentWillReceiveProps(newProps, newContext);
+  }
+  if (typeof instance.UNSAFE_componentWillReceiveProps === "function") {
+    instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+  }
+  stopPhaseTimer();
+
+  if (instance.state !== oldState) {
     {
-      addendum =
-        " If you meant to render a collection of children, use an array " +
-        "instead." +
-        (getCurrentFiberStackAddendum$2() || "");
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
+        didWarnAboutStateAssignmentForComponent.add(componentName);
+        warning(
+          false,
+          "%s.componentWillReceiveProps(): Assigning directly to " +
+            "this.state is deprecated (except inside a component's " +
+            "constructor). Use setState instead.",
+          componentName
+        );
+      }
     }
-    invariant(
-      false,
-      "Objects are not valid as a React child (found: %s).%s",
-      Object.prototype.toString.call(newChild) === "[object Object]"
-        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
-        : newChild,
-      addendum
-    );
+    classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
   }
 }
 
-function warnOnFunctionType() {
-  var currentComponentErrorInfo =
-    "Functions are not valid as a React child. This may happen if " +
-    "you return a Component instead of <Component /> from render. " +
-    "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$2() || "");
+// Invokes the mount life-cycles on a previously never rendered instance.
+function mountClassInstance(workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type;
 
-  if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
-    return;
+  {
+    checkClassInstance(workInProgress);
   }
-  ownerHasFunctionTypeWarning[currentComponentErrorInfo] = true;
 
-  warning(
-    false,
-    "Functions are not valid as a React child. This may happen if " +
-      "you return a Component instead of <Component /> from render. " +
-      "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$2() || ""
-  );
-}
+  var instance = workInProgress.stateNode;
+  var props = workInProgress.pendingProps;
+  var unmaskedContext = getUnmaskedContext(workInProgress);
 
-// This wrapper function exists because I expect to clone the code in each path
-// to be able to optimize each path individually by branching early. This needs
-// a compiler or we can do it manually. Helpers that don't need this branching
-// live outside of this function.
-function ChildReconciler(shouldTrackSideEffects) {
-  function deleteChild(returnFiber, childToDelete) {
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return;
+  instance.props = props;
+  instance.state = workInProgress.memoizedState;
+  instance.refs = emptyObject;
+  instance.context = getMaskedContext(workInProgress, unmaskedContext);
+
+  {
+    if (workInProgress.mode & StrictMode) {
+      ReactStrictModeWarnings.recordUnsafeLifecycleWarnings(
+        workInProgress,
+        instance
+      );
+
+      ReactStrictModeWarnings.recordLegacyContextWarning(
+        workInProgress,
+        instance
+      );
     }
-    // Deletions are added in reversed order so we add it to the front.
-    // At this point, the return fiber's effect list is empty except for
-    // deletions, so we can just append the deletion to the list. The remaining
-    // effects aren't added until the complete phase. Once we implement
-    // resuming, this may not be true.
-    var last = returnFiber.lastEffect;
-    if (last !== null) {
-      last.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
-    } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+
+    if (warnAboutDeprecatedLifecycles) {
+      ReactStrictModeWarnings.recordDeprecationWarnings(
+        workInProgress,
+        instance
+      );
     }
-    childToDelete.nextEffect = null;
-    childToDelete.effectTag = Deletion;
   }
 
-  function deleteRemainingChildren(returnFiber, currentFirstChild) {
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return null;
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null) {
+    processUpdateQueue(
+      workInProgress,
+      updateQueue,
+      props,
+      instance,
+      renderExpirationTime
+    );
+    instance.state = workInProgress.memoizedState;
+  }
+
+  var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
+  if (typeof getDerivedStateFromProps === "function") {
+    applyDerivedStateFromProps(workInProgress, getDerivedStateFromProps, props);
+    instance.state = workInProgress.memoizedState;
+  }
+
+  // In order to support react-lifecycles-compat polyfilled components,
+  // Unsafe lifecycles should not be invoked for components using the new APIs.
+  if (
+    typeof ctor.getDerivedStateFromProps !== "function" &&
+    typeof instance.getSnapshotBeforeUpdate !== "function" &&
+    (typeof instance.UNSAFE_componentWillMount === "function" ||
+      typeof instance.componentWillMount === "function")
+  ) {
+    callComponentWillMount(workInProgress, instance);
+    // If we had additional state updates during this life-cycle, let's
+    // process them now.
+    updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
+        workInProgress,
+        updateQueue,
+        props,
+        instance,
+        renderExpirationTime
+      );
+      instance.state = workInProgress.memoizedState;
     }
+  }
 
-    // TODO: For the shouldClone case, this could be micro-optimized a bit by
-    // assuming that after the first child we've already added everything.
-    var childToDelete = currentFirstChild;
-    while (childToDelete !== null) {
-      deleteChild(returnFiber, childToDelete);
-      childToDelete = childToDelete.sibling;
+  if (typeof instance.componentDidMount === "function") {
+    workInProgress.effectTag |= Update;
+  }
+}
+
+function resumeMountClassInstance(workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type;
+  var instance = workInProgress.stateNode;
+
+  var oldProps = workInProgress.memoizedProps;
+  var newProps = workInProgress.pendingProps;
+  instance.props = oldProps;
+
+  var oldContext = instance.context;
+  var newUnmaskedContext = getUnmaskedContext(workInProgress);
+  var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+
+  var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
+  var hasNewLifecycles =
+    typeof getDerivedStateFromProps === "function" ||
+    typeof instance.getSnapshotBeforeUpdate === "function";
+
+  // Note: During these life-cycles, instance.props/instance.state are what
+  // ever the previously attempted to render - not the "current". However,
+  // during componentDidUpdate we pass the "current" props.
+
+  // In order to support react-lifecycles-compat polyfilled components,
+  // Unsafe lifecycles should not be invoked for components using the new APIs.
+  if (
+    !hasNewLifecycles &&
+    (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
+      typeof instance.componentWillReceiveProps === "function")
+  ) {
+    if (oldProps !== newProps || oldContext !== newContext) {
+      callComponentWillReceiveProps(
+        workInProgress,
+        instance,
+        newProps,
+        newContext
+      );
     }
-    return null;
   }
 
-  function mapRemainingChildren(returnFiber, currentFirstChild) {
-    // Add the remaining children to a temporary map so that we can find them by
-    // keys quickly. Implicit (null) keys get added to this set with their index
-    var existingChildren = new Map();
+  resetHasForceUpdateBeforeProcessing();
 
-    var existingChild = currentFirstChild;
-    while (existingChild !== null) {
-      if (existingChild.key !== null) {
-        existingChildren.set(existingChild.key, existingChild);
-      } else {
-        existingChildren.set(existingChild.index, existingChild);
-      }
-      existingChild = existingChild.sibling;
+  var oldState = workInProgress.memoizedState;
+  var newState = (instance.state = oldState);
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null) {
+    processUpdateQueue(
+      workInProgress,
+      updateQueue,
+      newProps,
+      instance,
+      renderExpirationTime
+    );
+    newState = workInProgress.memoizedState;
+  }
+  if (
+    oldProps === newProps &&
+    oldState === newState &&
+    !hasContextChanged() &&
+    !checkHasForceUpdateAfterProcessing()
+  ) {
+    // If an update was already in progress, we should schedule an Update
+    // effect even though we're bailing out, so that cWU/cDU are called.
+    if (typeof instance.componentDidMount === "function") {
+      workInProgress.effectTag |= Update;
     }
-    return existingChildren;
+    return false;
   }
 
-  function useFiber(fiber, pendingProps, expirationTime) {
-    // We currently set sibling to null and index to 0 here because it is easy
-    // to forget to do before returning it. E.g. for the single child case.
-    var clone = createWorkInProgress(fiber, pendingProps, expirationTime);
-    clone.index = 0;
-    clone.sibling = null;
-    return clone;
+  if (typeof getDerivedStateFromProps === "function") {
+    applyDerivedStateFromProps(
+      workInProgress,
+      getDerivedStateFromProps,
+      newProps
+    );
+    newState = workInProgress.memoizedState;
   }
 
-  function placeChild(newFiber, lastPlacedIndex, newIndex) {
-    newFiber.index = newIndex;
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return lastPlacedIndex;
-    }
-    var current = newFiber.alternate;
-    if (current !== null) {
-      var oldIndex = current.index;
-      if (oldIndex < lastPlacedIndex) {
-        // This is a move.
-        newFiber.effectTag = Placement;
-        return lastPlacedIndex;
-      } else {
-        // This item can stay in place.
-        return oldIndex;
+  var shouldUpdate =
+    checkHasForceUpdateAfterProcessing() ||
+    checkShouldComponentUpdate(
+      workInProgress,
+      oldProps,
+      newProps,
+      oldState,
+      newState,
+      newContext
+    );
+
+  if (shouldUpdate) {
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      !hasNewLifecycles &&
+      (typeof instance.UNSAFE_componentWillMount === "function" ||
+        typeof instance.componentWillMount === "function")
+    ) {
+      startPhaseTimer(workInProgress, "componentWillMount");
+      if (typeof instance.componentWillMount === "function") {
+        instance.componentWillMount();
       }
-    } else {
-      // This is an insertion.
-      newFiber.effectTag = Placement;
-      return lastPlacedIndex;
+      if (typeof instance.UNSAFE_componentWillMount === "function") {
+        instance.UNSAFE_componentWillMount();
+      }
+      stopPhaseTimer();
     }
-  }
-
-  function placeSingleChild(newFiber) {
-    // This is simpler for the single child case. We only need to do a
-    // placement for inserting new children.
-    if (shouldTrackSideEffects && newFiber.alternate === null) {
-      newFiber.effectTag = Placement;
+    if (typeof instance.componentDidMount === "function") {
+      workInProgress.effectTag |= Update;
     }
-    return newFiber;
+  } else {
+    // If an update was already in progress, we should schedule an Update
+    // effect even though we're bailing out, so that cWU/cDU are called.
+    if (typeof instance.componentDidMount === "function") {
+      workInProgress.effectTag |= Update;
+    }
+
+    // If shouldComponentUpdate returned false, we should still update the
+    // memoized state to indicate that this work can be reused.
+    workInProgress.memoizedProps = newProps;
+    workInProgress.memoizedState = newState;
   }
 
-  function updateTextNode(returnFiber, current, textContent, expirationTime) {
-    if (current === null || current.tag !== HostText) {
-      // Insert
-      var created = createFiberFromText(
-        textContent,
-        returnFiber.mode,
-        expirationTime
+  // Update the existing instance's state, props, and context pointers even
+  // if shouldComponentUpdate returns false.
+  instance.props = newProps;
+  instance.state = newState;
+  instance.context = newContext;
+
+  return shouldUpdate;
+}
+
+// Invokes the update life-cycles and returns false if it shouldn't rerender.
+function updateClassInstance(current, workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type;
+  var instance = workInProgress.stateNode;
+
+  var oldProps = workInProgress.memoizedProps;
+  var newProps = workInProgress.pendingProps;
+  instance.props = oldProps;
+
+  var oldContext = instance.context;
+  var newUnmaskedContext = getUnmaskedContext(workInProgress);
+  var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+
+  var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
+  var hasNewLifecycles =
+    typeof getDerivedStateFromProps === "function" ||
+    typeof instance.getSnapshotBeforeUpdate === "function";
+
+  // Note: During these life-cycles, instance.props/instance.state are what
+  // ever the previously attempted to render - not the "current". However,
+  // during componentDidUpdate we pass the "current" props.
+
+  // In order to support react-lifecycles-compat polyfilled components,
+  // Unsafe lifecycles should not be invoked for components using the new APIs.
+  if (
+    !hasNewLifecycles &&
+    (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
+      typeof instance.componentWillReceiveProps === "function")
+  ) {
+    if (oldProps !== newProps || oldContext !== newContext) {
+      callComponentWillReceiveProps(
+        workInProgress,
+        instance,
+        newProps,
+        newContext
       );
-      created.return = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, textContent, expirationTime);
-      existing.return = returnFiber;
-      return existing;
     }
   }
 
-  function updateElement(returnFiber, current, element, expirationTime) {
-    if (current !== null && current.type === element.type) {
-      // Move based on index
-      var existing = useFiber(current, element.props, expirationTime);
-      existing.ref = coerceRef(returnFiber, current, element);
-      existing.return = returnFiber;
-      {
-        existing._debugSource = element._source;
-        existing._debugOwner = element._owner;
+  resetHasForceUpdateBeforeProcessing();
+
+  var oldState = workInProgress.memoizedState;
+  var newState = (instance.state = oldState);
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null) {
+    processUpdateQueue(
+      workInProgress,
+      updateQueue,
+      newProps,
+      instance,
+      renderExpirationTime
+    );
+    newState = workInProgress.memoizedState;
+  }
+
+  if (
+    oldProps === newProps &&
+    oldState === newState &&
+    !hasContextChanged() &&
+    !checkHasForceUpdateAfterProcessing()
+  ) {
+    // If an update was already in progress, we should schedule an Update
+    // effect even though we're bailing out, so that cWU/cDU are called.
+    if (typeof instance.componentDidUpdate === "function") {
+      if (
+        oldProps !== current.memoizedProps ||
+        oldState !== current.memoizedState
+      ) {
+        workInProgress.effectTag |= Update;
       }
-      return existing;
-    } else {
-      // Insert
-      var created = createFiberFromElement(
-        element,
-        returnFiber.mode,
-        expirationTime
-      );
-      created.ref = coerceRef(returnFiber, current, element);
-      created.return = returnFiber;
-      return created;
     }
+    if (typeof instance.getSnapshotBeforeUpdate === "function") {
+      if (
+        oldProps !== current.memoizedProps ||
+        oldState !== current.memoizedState
+      ) {
+        workInProgress.effectTag |= Snapshot;
+      }
+    }
+    return false;
   }
 
-  function updatePortal(returnFiber, current, portal, expirationTime) {
+  if (typeof getDerivedStateFromProps === "function") {
+    applyDerivedStateFromProps(
+      workInProgress,
+      getDerivedStateFromProps,
+      newProps
+    );
+    newState = workInProgress.memoizedState;
+  }
+
+  var shouldUpdate =
+    checkHasForceUpdateAfterProcessing() ||
+    checkShouldComponentUpdate(
+      workInProgress,
+      oldProps,
+      newProps,
+      oldState,
+      newState,
+      newContext
+    );
+
+  if (shouldUpdate) {
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
     if (
-      current === null ||
-      current.tag !== HostPortal ||
-      current.stateNode.containerInfo !== portal.containerInfo ||
-      current.stateNode.implementation !== portal.implementation
+      !hasNewLifecycles &&
+      (typeof instance.UNSAFE_componentWillUpdate === "function" ||
+        typeof instance.componentWillUpdate === "function")
     ) {
-      // Insert
-      var created = createFiberFromPortal(
-        portal,
-        returnFiber.mode,
-        expirationTime
-      );
-      created.return = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, portal.children || [], expirationTime);
-      existing.return = returnFiber;
-      return existing;
+      startPhaseTimer(workInProgress, "componentWillUpdate");
+      if (typeof instance.componentWillUpdate === "function") {
+        instance.componentWillUpdate(newProps, newState, newContext);
+      }
+      if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+        instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
+      }
+      stopPhaseTimer();
     }
-  }
-
-  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
-    if (current === null || current.tag !== Fragment) {
-      // Insert
-      var created = createFiberFromFragment(
-        fragment,
-        returnFiber.mode,
-        expirationTime,
-        key
-      );
-      created.return = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, fragment, expirationTime);
-      existing.return = returnFiber;
-      return existing;
+    if (typeof instance.componentDidUpdate === "function") {
+      workInProgress.effectTag |= Update;
+    }
+    if (typeof instance.getSnapshotBeforeUpdate === "function") {
+      workInProgress.effectTag |= Snapshot;
+    }
+  } else {
+    // If an update was already in progress, we should schedule an Update
+    // effect even though we're bailing out, so that cWU/cDU are called.
+    if (typeof instance.componentDidUpdate === "function") {
+      if (
+        oldProps !== current.memoizedProps ||
+        oldState !== current.memoizedState
+      ) {
+        workInProgress.effectTag |= Update;
+      }
+    }
+    if (typeof instance.getSnapshotBeforeUpdate === "function") {
+      if (
+        oldProps !== current.memoizedProps ||
+        oldState !== current.memoizedState
+      ) {
+        workInProgress.effectTag |= Snapshot;
+      }
     }
+
+    // If shouldComponentUpdate returned false, we should still update the
+    // memoized props/state to indicate that this work can be reused.
+    workInProgress.memoizedProps = newProps;
+    workInProgress.memoizedState = newState;
   }
 
-  function createChild(returnFiber, newChild, expirationTime) {
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys. If the previous node is implicitly keyed
-      // we can continue to replace it without aborting even if it is not a text
-      // node.
-      var created = createFiberFromText(
-        "" + newChild,
-        returnFiber.mode,
-        expirationTime
-      );
-      created.return = returnFiber;
-      return created;
-    }
+  // Update the existing instance's state, props, and context pointers even
+  // if shouldComponentUpdate returns false.
+  instance.props = newProps;
+  instance.state = newState;
+  instance.context = newContext;
 
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          var _created = createFiberFromElement(
-            newChild,
-            returnFiber.mode,
-            expirationTime
-          );
-          _created.ref = coerceRef(returnFiber, null, newChild);
-          _created.return = returnFiber;
-          return _created;
-        }
-        case REACT_PORTAL_TYPE: {
-          var _created2 = createFiberFromPortal(
-            newChild,
-            returnFiber.mode,
-            expirationTime
-          );
-          _created2.return = returnFiber;
-          return _created2;
-        }
-      }
+  return shouldUpdate;
+}
 
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        var _created3 = createFiberFromFragment(
-          newChild,
-          returnFiber.mode,
-          expirationTime,
-          null
-        );
-        _created3.return = returnFiber;
-        return _created3;
-      }
+var getCurrentFiberStackAddendum$2 =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
 
-      throwOnInvalidObjectType(returnFiber, newChild);
+var didWarnAboutMaps = void 0;
+var didWarnAboutStringRefInStrictMode = void 0;
+var ownerHasKeyUseWarning = void 0;
+var ownerHasFunctionTypeWarning = void 0;
+var warnForMissingKey = function(child) {};
+
+{
+  didWarnAboutMaps = false;
+  didWarnAboutStringRefInStrictMode = {};
+
+  /**
+   * Warn if there's no key explicitly set on dynamic arrays of children or
+   * object keys are not valid. This allows us to keep track of children between
+   * updates.
+   */
+  ownerHasKeyUseWarning = {};
+  ownerHasFunctionTypeWarning = {};
+
+  warnForMissingKey = function(child) {
+    if (child === null || typeof child !== "object") {
+      return;
+    }
+    if (!child._store || child._store.validated || child.key != null) {
+      return;
+    }
+    invariant(
+      typeof child._store === "object",
+      "React Component in warnForMissingKey should have a _store. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+    child._store.validated = true;
+
+    var currentComponentErrorInfo =
+      "Each child in an array or iterator should have a unique " +
+      '"key" prop. See https://fb.me/react-warning-keys for ' +
+      "more information." +
+      (getCurrentFiberStackAddendum$2() || "");
+    if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
+      return;
     }
+    ownerHasKeyUseWarning[currentComponentErrorInfo] = true;
+
+    warning(
+      false,
+      "Each child in an array or iterator should have a unique " +
+        '"key" prop. See https://fb.me/react-warning-keys for ' +
+        "more information.%s",
+      getCurrentFiberStackAddendum$2()
+    );
+  };
+}
 
+var isArray$1 = Array.isArray;
+
+function coerceRef(returnFiber, current, element) {
+  var mixedRef = element.ref;
+  if (
+    mixedRef !== null &&
+    typeof mixedRef !== "function" &&
+    typeof mixedRef !== "object"
+  ) {
     {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
+      if (returnFiber.mode & StrictMode) {
+        var componentName = getComponentName(returnFiber) || "Component";
+        if (!didWarnAboutStringRefInStrictMode[componentName]) {
+          warning(
+            false,
+            'A string ref, "%s", has been found within a strict mode tree. ' +
+              "String refs are a source of potential bugs and should be avoided. " +
+              "We recommend using createRef() instead." +
+              "\n%s" +
+              "\n\nLearn more about using refs safely here:" +
+              "\nhttps://fb.me/react-strict-mode-string-ref",
+            mixedRef,
+            getStackAddendumByWorkInProgressFiber(returnFiber)
+          );
+          didWarnAboutStringRefInStrictMode[componentName] = true;
+        }
       }
     }
 
-    return null;
-  }
-
-  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
-    // Update the fiber if the keys match, otherwise return null.
-
-    var key = oldFiber !== null ? oldFiber.key : null;
-
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys. If the previous node is implicitly keyed
-      // we can continue to replace it without aborting even if it is not a text
-      // node.
-      if (key !== null) {
-        return null;
+    if (element._owner) {
+      var owner = element._owner;
+      var inst = void 0;
+      if (owner) {
+        var ownerFiber = owner;
+        invariant(
+          ownerFiber.tag === ClassComponent,
+          "Stateless function components cannot have refs."
+        );
+        inst = ownerFiber.stateNode;
       }
-      return updateTextNode(
-        returnFiber,
-        oldFiber,
-        "" + newChild,
-        expirationTime
+      invariant(
+        inst,
+        "Missing owner for string ref %s. This error is likely caused by a " +
+          "bug in React. Please file an issue.",
+        mixedRef
       );
-    }
-
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          if (newChild.key === key) {
-            if (newChild.type === REACT_FRAGMENT_TYPE) {
-              return updateFragment(
-                returnFiber,
-                oldFiber,
-                newChild.props.children,
-                expirationTime,
-                key
-              );
-            }
-            return updateElement(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime
-            );
-          } else {
-            return null;
-          }
-        }
-        case REACT_PORTAL_TYPE: {
-          if (newChild.key === key) {
-            return updatePortal(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime
-            );
-          } else {
-            return null;
-          }
-        }
+      var stringRef = "" + mixedRef;
+      // Check if previous string ref matches new string ref
+      if (
+        current !== null &&
+        current.ref !== null &&
+        typeof current.ref === "function" &&
+        current.ref._stringRef === stringRef
+      ) {
+        return current.ref;
       }
-
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        if (key !== null) {
-          return null;
+      var ref = function(value) {
+        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
+        if (value === null) {
+          delete refs[stringRef];
+        } else {
+          refs[stringRef] = value;
         }
-
-        return updateFragment(
-          returnFiber,
-          oldFiber,
-          newChild,
-          expirationTime,
-          null
-        );
-      }
-
-      throwOnInvalidObjectType(returnFiber, newChild);
+      };
+      ref._stringRef = stringRef;
+      return ref;
+    } else {
+      invariant(
+        typeof mixedRef === "string",
+        "Expected ref to be a function or a string."
+      );
+      invariant(
+        element._owner,
+        "Element ref was specified as a string (%s) but no owner was set. This could happen for one of" +
+          " the following reasons:\n" +
+          "1. You may be adding a ref to a functional component\n" +
+          "2. You may be adding a ref to a component that was not created inside a component's render method\n" +
+          "3. You have multiple copies of React loaded\n" +
+          "See https://fb.me/react-refs-must-have-owner for more information.",
+        mixedRef
+      );
     }
+  }
+  return mixedRef;
+}
 
+function throwOnInvalidObjectType(returnFiber, newChild) {
+  if (returnFiber.type !== "textarea") {
+    var addendum = "";
     {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
+      addendum =
+        " If you meant to render a collection of children, use an array " +
+        "instead." +
+        (getCurrentFiberStackAddendum$2() || "");
     }
-
-    return null;
+    invariant(
+      false,
+      "Objects are not valid as a React child (found: %s).%s",
+      Object.prototype.toString.call(newChild) === "[object Object]"
+        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
+        : newChild,
+      addendum
+    );
   }
+}
 
-  function updateFromMap(
-    existingChildren,
-    returnFiber,
-    newIdx,
-    newChild,
-    expirationTime
-  ) {
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys, so we neither have to check the old nor
-      // new node for the key. If both are text nodes, they match.
-      var matchedFiber = existingChildren.get(newIdx) || null;
-      return updateTextNode(
-        returnFiber,
-        matchedFiber,
-        "" + newChild,
-        expirationTime
-      );
-    }
+function warnOnFunctionType() {
+  var currentComponentErrorInfo =
+    "Functions are not valid as a React child. This may happen if " +
+    "you return a Component instead of <Component /> from render. " +
+    "Or maybe you meant to call this function rather than return it." +
+    (getCurrentFiberStackAddendum$2() || "");
 
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          var _matchedFiber =
-            existingChildren.get(
-              newChild.key === null ? newIdx : newChild.key
-            ) || null;
-          if (newChild.type === REACT_FRAGMENT_TYPE) {
-            return updateFragment(
-              returnFiber,
-              _matchedFiber,
-              newChild.props.children,
-              expirationTime,
-              newChild.key
-            );
-          }
-          return updateElement(
-            returnFiber,
-            _matchedFiber,
-            newChild,
-            expirationTime
-          );
-        }
-        case REACT_PORTAL_TYPE: {
-          var _matchedFiber2 =
-            existingChildren.get(
-              newChild.key === null ? newIdx : newChild.key
-            ) || null;
-          return updatePortal(
-            returnFiber,
-            _matchedFiber2,
-            newChild,
-            expirationTime
-          );
-        }
-      }
+  if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
+    return;
+  }
+  ownerHasFunctionTypeWarning[currentComponentErrorInfo] = true;
 
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        var _matchedFiber3 = existingChildren.get(newIdx) || null;
-        return updateFragment(
-          returnFiber,
-          _matchedFiber3,
-          newChild,
-          expirationTime,
-          null
-        );
-      }
+  warning(
+    false,
+    "Functions are not valid as a React child. This may happen if " +
+      "you return a Component instead of <Component /> from render. " +
+      "Or maybe you meant to call this function rather than return it.%s",
+    getCurrentFiberStackAddendum$2() || ""
+  );
+}
+
+// This wrapper function exists because I expect to clone the code in each path
+// to be able to optimize each path individually by branching early. This needs
+// a compiler or we can do it manually. Helpers that don't need this branching
+// live outside of this function.
+function ChildReconciler(shouldTrackSideEffects) {
+  function deleteChild(returnFiber, childToDelete) {
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return;
+    }
+    // Deletions are added in reversed order so we add it to the front.
+    // At this point, the return fiber's effect list is empty except for
+    // deletions, so we can just append the deletion to the list. The remaining
+    // effects aren't added until the complete phase. Once we implement
+    // resuming, this may not be true.
+    var last = returnFiber.lastEffect;
+    if (last !== null) {
+      last.nextEffect = childToDelete;
+      returnFiber.lastEffect = childToDelete;
+    } else {
+      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+    }
+    childToDelete.nextEffect = null;
+    childToDelete.effectTag = Deletion;
+  }
 
-      throwOnInvalidObjectType(returnFiber, newChild);
+  function deleteRemainingChildren(returnFiber, currentFirstChild) {
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return null;
     }
 
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
+    // TODO: For the shouldClone case, this could be micro-optimized a bit by
+    // assuming that after the first child we've already added everything.
+    var childToDelete = currentFirstChild;
+    while (childToDelete !== null) {
+      deleteChild(returnFiber, childToDelete);
+      childToDelete = childToDelete.sibling;
     }
-
     return null;
   }
 
-  /**
-   * Warns if there is a duplicate or missing key
-   */
-  function warnOnInvalidKey(child, knownKeys) {
-    {
-      if (typeof child !== "object" || child === null) {
-        return knownKeys;
-      }
-      switch (child.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-        case REACT_PORTAL_TYPE:
-          warnForMissingKey(child);
-          var key = child.key;
-          if (typeof key !== "string") {
-            break;
-          }
-          if (knownKeys === null) {
-            knownKeys = new Set();
-            knownKeys.add(key);
-            break;
-          }
-          if (!knownKeys.has(key)) {
-            knownKeys.add(key);
-            break;
-          }
-          warning(
-            false,
-            "Encountered two children with the same key, `%s`. " +
-              "Keys should be unique so that components maintain their identity " +
-              "across updates. Non-unique keys may cause children to be " +
-              "duplicated and/or omitted — the behavior is unsupported and " +
-              "could change in a future version.%s",
-            key,
-            getCurrentFiberStackAddendum$2()
-          );
-          break;
-        default:
-          break;
+  function mapRemainingChildren(returnFiber, currentFirstChild) {
+    // Add the remaining children to a temporary map so that we can find them by
+    // keys quickly. Implicit (null) keys get added to this set with their index
+    var existingChildren = new Map();
+
+    var existingChild = currentFirstChild;
+    while (existingChild !== null) {
+      if (existingChild.key !== null) {
+        existingChildren.set(existingChild.key, existingChild);
+      } else {
+        existingChildren.set(existingChild.index, existingChild);
       }
+      existingChild = existingChild.sibling;
     }
-    return knownKeys;
+    return existingChildren;
   }
 
-  function reconcileChildrenArray(
-    returnFiber,
-    currentFirstChild,
-    newChildren,
-    expirationTime
-  ) {
-    // This algorithm can't optimize by searching from boths ends since we
-    // don't have backpointers on fibers. I'm trying to see how far we can get
-    // with that model. If it ends up not being worth the tradeoffs, we can
-    // add it later.
-
-    // Even with a two ended optimization, we'd want to optimize for the case
-    // where there are few changes and brute force the comparison instead of
-    // going for the Map. It'd like to explore hitting that path first in
-    // forward-only mode and only go for the Map once we notice that we need
-    // lots of look ahead. This doesn't handle reversal as well as two ended
-    // search but that's unusual. Besides, for the two ended optimization to
-    // work on Iterables, we'd need to copy the whole set.
-
-    // In this first iteration, we'll just live with hitting the bad case
-    // (adding everything to a Map) in for every insert/move.
-
-    // If you change this code, also update reconcileChildrenIterator() which
-    // uses the same algorithm.
+  function useFiber(fiber, pendingProps, expirationTime) {
+    // We currently set sibling to null and index to 0 here because it is easy
+    // to forget to do before returning it. E.g. for the single child case.
+    var clone = createWorkInProgress(fiber, pendingProps, expirationTime);
+    clone.index = 0;
+    clone.sibling = null;
+    return clone;
+  }
 
-    {
-      // First, validate keys.
-      var knownKeys = null;
-      for (var i = 0; i < newChildren.length; i++) {
-        var child = newChildren[i];
-        knownKeys = warnOnInvalidKey(child, knownKeys);
-      }
+  function placeChild(newFiber, lastPlacedIndex, newIndex) {
+    newFiber.index = newIndex;
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return lastPlacedIndex;
     }
-
-    var resultingFirstChild = null;
-    var previousNewFiber = null;
-
-    var oldFiber = currentFirstChild;
-    var lastPlacedIndex = 0;
-    var newIdx = 0;
-    var nextOldFiber = null;
-    for (; oldFiber !== null && newIdx < newChildren.length; newIdx++) {
-      if (oldFiber.index > newIdx) {
-        nextOldFiber = oldFiber;
-        oldFiber = null;
-      } else {
-        nextOldFiber = oldFiber.sibling;
-      }
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        newChildren[newIdx],
-        expirationTime
-      );
-      if (newFiber === null) {
-        // TODO: This breaks on empty slots like null children. That's
-        // unfortunate because it triggers the slow path all the time. We need
-        // a better way to communicate whether this was a miss or null,
-        // boolean, undefined, etc.
-        if (oldFiber === null) {
-          oldFiber = nextOldFiber;
-        }
-        break;
-      }
-      if (shouldTrackSideEffects) {
-        if (oldFiber && newFiber.alternate === null) {
-          // We matched the slot, but we didn't reuse the existing fiber, so we
-          // need to delete the existing child.
-          deleteChild(returnFiber, oldFiber);
-        }
-      }
-      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
-      if (previousNewFiber === null) {
-        // TODO: Move out of the loop. This only happens for the first run.
-        resultingFirstChild = newFiber;
+    var current = newFiber.alternate;
+    if (current !== null) {
+      var oldIndex = current.index;
+      if (oldIndex < lastPlacedIndex) {
+        // This is a move.
+        newFiber.effectTag = Placement;
+        return lastPlacedIndex;
       } else {
-        // TODO: Defer siblings if we're not at the right index for this slot.
-        // I.e. if we had null values before, then we want to defer this
-        // for each null value. However, we also don't want to call updateSlot
-        // with the previous one.
-        previousNewFiber.sibling = newFiber;
+        // This item can stay in place.
+        return oldIndex;
       }
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
-
-    if (newIdx === newChildren.length) {
-      // We've reached the end of the new children. We can delete the rest.
-      deleteRemainingChildren(returnFiber, oldFiber);
-      return resultingFirstChild;
+    } else {
+      // This is an insertion.
+      newFiber.effectTag = Placement;
+      return lastPlacedIndex;
     }
+  }
 
-    if (oldFiber === null) {
-      // If we don't have any more existing children we can choose a fast path
-      // since the rest will all be insertions.
-      for (; newIdx < newChildren.length; newIdx++) {
-        var _newFiber = createChild(
-          returnFiber,
-          newChildren[newIdx],
-          expirationTime
-        );
-        if (!_newFiber) {
-          continue;
-        }
-        lastPlacedIndex = placeChild(_newFiber, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          // TODO: Move out of the loop. This only happens for the first run.
-          resultingFirstChild = _newFiber;
-        } else {
-          previousNewFiber.sibling = _newFiber;
-        }
-        previousNewFiber = _newFiber;
-      }
-      return resultingFirstChild;
+  function placeSingleChild(newFiber) {
+    // This is simpler for the single child case. We only need to do a
+    // placement for inserting new children.
+    if (shouldTrackSideEffects && newFiber.alternate === null) {
+      newFiber.effectTag = Placement;
     }
+    return newFiber;
+  }
 
-    // Add all children to a key map for quick lookups.
-    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
-
-    // Keep scanning and use the map to restore deleted items as moves.
-    for (; newIdx < newChildren.length; newIdx++) {
-      var _newFiber2 = updateFromMap(
-        existingChildren,
-        returnFiber,
-        newIdx,
-        newChildren[newIdx],
+  function updateTextNode(returnFiber, current, textContent, expirationTime) {
+    if (current === null || current.tag !== HostText) {
+      // Insert
+      var created = createFiberFromText(
+        textContent,
+        returnFiber.mode,
         expirationTime
       );
-      if (_newFiber2) {
-        if (shouldTrackSideEffects) {
-          if (_newFiber2.alternate !== null) {
-            // The new fiber is a work in progress, but if there exists a
-            // current, that means that we reused the fiber. We need to delete
-            // it from the child list so that we don't add it to the deletion
-            // list.
-            existingChildren.delete(
-              _newFiber2.key === null ? newIdx : _newFiber2.key
-            );
-          }
-        }
-        lastPlacedIndex = placeChild(_newFiber2, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          resultingFirstChild = _newFiber2;
-        } else {
-          previousNewFiber.sibling = _newFiber2;
-        }
-        previousNewFiber = _newFiber2;
-      }
-    }
-
-    if (shouldTrackSideEffects) {
-      // Any existing children that weren't consumed above were deleted. We need
-      // to add them to the deletion list.
-      existingChildren.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
+      created.return = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, textContent, expirationTime);
+      existing.return = returnFiber;
+      return existing;
     }
-
-    return resultingFirstChild;
   }
 
-  function reconcileChildrenIterator(
-    returnFiber,
-    currentFirstChild,
-    newChildrenIterable,
-    expirationTime
-  ) {
-    // This is the same implementation as reconcileChildrenArray(),
-    // but using the iterator instead.
-
-    var iteratorFn = getIteratorFn(newChildrenIterable);
-    invariant(
-      typeof iteratorFn === "function",
-      "An object is not an iterable. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-
-    {
-      // Warn about using Maps as children
-      if (typeof newChildrenIterable.entries === "function") {
-        var possibleMap = newChildrenIterable;
-        if (possibleMap.entries === iteratorFn) {
-          !didWarnAboutMaps
-            ? warning(
-                false,
-                "Using Maps as children is unsupported and will likely yield " +
-                  "unexpected results. Convert it to a sequence/iterable of keyed " +
-                  "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$2()
-              )
-            : void 0;
-          didWarnAboutMaps = true;
-        }
-      }
-
-      // First, validate keys.
-      // We'll get a different iterator later for the main pass.
-      var _newChildren = iteratorFn.call(newChildrenIterable);
-      if (_newChildren) {
-        var knownKeys = null;
-        var _step = _newChildren.next();
-        for (; !_step.done; _step = _newChildren.next()) {
-          var child = _step.value;
-          knownKeys = warnOnInvalidKey(child, knownKeys);
-        }
+  function updateElement(returnFiber, current, element, expirationTime) {
+    if (current !== null && current.type === element.type) {
+      // Move based on index
+      var existing = useFiber(current, element.props, expirationTime);
+      existing.ref = coerceRef(returnFiber, current, element);
+      existing.return = returnFiber;
+      {
+        existing._debugSource = element._source;
+        existing._debugOwner = element._owner;
       }
+      return existing;
+    } else {
+      // Insert
+      var created = createFiberFromElement(
+        element,
+        returnFiber.mode,
+        expirationTime
+      );
+      created.ref = coerceRef(returnFiber, current, element);
+      created.return = returnFiber;
+      return created;
     }
+  }
 
-    var newChildren = iteratorFn.call(newChildrenIterable);
-    invariant(newChildren != null, "An iterable object provided no iterator.");
-
-    var resultingFirstChild = null;
-    var previousNewFiber = null;
+  function updatePortal(returnFiber, current, portal, expirationTime) {
+    if (
+      current === null ||
+      current.tag !== HostPortal ||
+      current.stateNode.containerInfo !== portal.containerInfo ||
+      current.stateNode.implementation !== portal.implementation
+    ) {
+      // Insert
+      var created = createFiberFromPortal(
+        portal,
+        returnFiber.mode,
+        expirationTime
+      );
+      created.return = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, portal.children || [], expirationTime);
+      existing.return = returnFiber;
+      return existing;
+    }
+  }
 
-    var oldFiber = currentFirstChild;
-    var lastPlacedIndex = 0;
-    var newIdx = 0;
-    var nextOldFiber = null;
+  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
+    if (current === null || current.tag !== Fragment) {
+      // Insert
+      var created = createFiberFromFragment(
+        fragment,
+        returnFiber.mode,
+        expirationTime,
+        key
+      );
+      created.return = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, fragment, expirationTime);
+      existing.return = returnFiber;
+      return existing;
+    }
+  }
 
-    var step = newChildren.next();
-    for (
-      ;
-      oldFiber !== null && !step.done;
-      newIdx++, step = newChildren.next()
-    ) {
-      if (oldFiber.index > newIdx) {
-        nextOldFiber = oldFiber;
-        oldFiber = null;
-      } else {
-        nextOldFiber = oldFiber.sibling;
-      }
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        step.value,
+  function createChild(returnFiber, newChild, expirationTime) {
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys. If the previous node is implicitly keyed
+      // we can continue to replace it without aborting even if it is not a text
+      // node.
+      var created = createFiberFromText(
+        "" + newChild,
+        returnFiber.mode,
         expirationTime
       );
-      if (newFiber === null) {
-        // TODO: This breaks on empty slots like null children. That's
-        // unfortunate because it triggers the slow path all the time. We need
-        // a better way to communicate whether this was a miss or null,
-        // boolean, undefined, etc.
-        if (!oldFiber) {
-          oldFiber = nextOldFiber;
+      created.return = returnFiber;
+      return created;
+    }
+
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          var _created = createFiberFromElement(
+            newChild,
+            returnFiber.mode,
+            expirationTime
+          );
+          _created.ref = coerceRef(returnFiber, null, newChild);
+          _created.return = returnFiber;
+          return _created;
         }
-        break;
-      }
-      if (shouldTrackSideEffects) {
-        if (oldFiber && newFiber.alternate === null) {
-          // We matched the slot, but we didn't reuse the existing fiber, so we
-          // need to delete the existing child.
-          deleteChild(returnFiber, oldFiber);
+        case REACT_PORTAL_TYPE: {
+          var _created2 = createFiberFromPortal(
+            newChild,
+            returnFiber.mode,
+            expirationTime
+          );
+          _created2.return = returnFiber;
+          return _created2;
         }
       }
-      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
-      if (previousNewFiber === null) {
-        // TODO: Move out of the loop. This only happens for the first run.
-        resultingFirstChild = newFiber;
-      } else {
-        // TODO: Defer siblings if we're not at the right index for this slot.
-        // I.e. if we had null values before, then we want to defer this
-        // for each null value. However, we also don't want to call updateSlot
-        // with the previous one.
-        previousNewFiber.sibling = newFiber;
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        var _created3 = createFiberFromFragment(
+          newChild,
+          returnFiber.mode,
+          expirationTime,
+          null
+        );
+        _created3.return = returnFiber;
+        return _created3;
       }
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
-    }
 
-    if (step.done) {
-      // We've reached the end of the new children. We can delete the rest.
-      deleteRemainingChildren(returnFiber, oldFiber);
-      return resultingFirstChild;
+      throwOnInvalidObjectType(returnFiber, newChild);
     }
 
-    if (oldFiber === null) {
-      // If we don't have any more existing children we can choose a fast path
-      // since the rest will all be insertions.
-      for (; !step.done; newIdx++, step = newChildren.next()) {
-        var _newFiber3 = createChild(returnFiber, step.value, expirationTime);
-        if (_newFiber3 === null) {
-          continue;
-        }
-        lastPlacedIndex = placeChild(_newFiber3, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          // TODO: Move out of the loop. This only happens for the first run.
-          resultingFirstChild = _newFiber3;
-        } else {
-          previousNewFiber.sibling = _newFiber3;
-        }
-        previousNewFiber = _newFiber3;
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
       }
-      return resultingFirstChild;
     }
 
-    // Add all children to a key map for quick lookups.
-    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
+    return null;
+  }
 
-    // Keep scanning and use the map to restore deleted items as moves.
-    for (; !step.done; newIdx++, step = newChildren.next()) {
-      var _newFiber4 = updateFromMap(
-        existingChildren,
+  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
+    // Update the fiber if the keys match, otherwise return null.
+
+    var key = oldFiber !== null ? oldFiber.key : null;
+
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys. If the previous node is implicitly keyed
+      // we can continue to replace it without aborting even if it is not a text
+      // node.
+      if (key !== null) {
+        return null;
+      }
+      return updateTextNode(
         returnFiber,
-        newIdx,
-        step.value,
+        oldFiber,
+        "" + newChild,
         expirationTime
       );
-      if (_newFiber4 !== null) {
-        if (shouldTrackSideEffects) {
-          if (_newFiber4.alternate !== null) {
-            // The new fiber is a work in progress, but if there exists a
-            // current, that means that we reused the fiber. We need to delete
-            // it from the child list so that we don't add it to the deletion
-            // list.
-            existingChildren.delete(
-              _newFiber4.key === null ? newIdx : _newFiber4.key
+    }
+
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          if (newChild.key === key) {
+            if (newChild.type === REACT_FRAGMENT_TYPE) {
+              return updateFragment(
+                returnFiber,
+                oldFiber,
+                newChild.props.children,
+                expirationTime,
+                key
+              );
+            }
+            return updateElement(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime
             );
+          } else {
+            return null;
           }
         }
-        lastPlacedIndex = placeChild(_newFiber4, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          resultingFirstChild = _newFiber4;
-        } else {
-          previousNewFiber.sibling = _newFiber4;
+        case REACT_PORTAL_TYPE: {
+          if (newChild.key === key) {
+            return updatePortal(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime
+            );
+          } else {
+            return null;
+          }
         }
-        previousNewFiber = _newFiber4;
       }
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        if (key !== null) {
+          return null;
+        }
+
+        return updateFragment(
+          returnFiber,
+          oldFiber,
+          newChild,
+          expirationTime,
+          null
+        );
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
     }
 
-    if (shouldTrackSideEffects) {
-      // Any existing children that weren't consumed above were deleted. We need
-      // to add them to the deletion list.
-      existingChildren.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
     }
 
-    return resultingFirstChild;
+    return null;
   }
 
-  function reconcileSingleTextNode(
+  function updateFromMap(
+    existingChildren,
     returnFiber,
-    currentFirstChild,
-    textContent,
+    newIdx,
+    newChild,
     expirationTime
   ) {
-    // There's no need to check for keys on text nodes since we don't have a
-    // way to define them.
-    if (currentFirstChild !== null && currentFirstChild.tag === HostText) {
-      // We already have an existing node so let's just update it and delete
-      // the rest.
-      deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
-      var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing.return = returnFiber;
-      return existing;
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys, so we neither have to check the old nor
+      // new node for the key. If both are text nodes, they match.
+      var matchedFiber = existingChildren.get(newIdx) || null;
+      return updateTextNode(
+        returnFiber,
+        matchedFiber,
+        "" + newChild,
+        expirationTime
+      );
     }
-    // The existing first child is not a text node so we need to create one
-    // and delete the existing ones.
-    deleteRemainingChildren(returnFiber, currentFirstChild);
-    var created = createFiberFromText(
-      textContent,
-      returnFiber.mode,
-      expirationTime
-    );
-    created.return = returnFiber;
-    return created;
-  }
 
-  function reconcileSingleElement(
-    returnFiber,
-    currentFirstChild,
-    element,
-    expirationTime
-  ) {
-    var key = element.key;
-    var child = currentFirstChild;
-    while (child !== null) {
-      // TODO: If key === null and child.key === null, then this only applies to
-      // the first item in the list.
-      if (child.key === key) {
-        if (
-          child.tag === Fragment
-            ? element.type === REACT_FRAGMENT_TYPE
-            : child.type === element.type
-        ) {
-          deleteRemainingChildren(returnFiber, child.sibling);
-          var existing = useFiber(
-            child,
-            element.type === REACT_FRAGMENT_TYPE
-              ? element.props.children
-              : element.props,
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          var _matchedFiber =
+            existingChildren.get(
+              newChild.key === null ? newIdx : newChild.key
+            ) || null;
+          if (newChild.type === REACT_FRAGMENT_TYPE) {
+            return updateFragment(
+              returnFiber,
+              _matchedFiber,
+              newChild.props.children,
+              expirationTime,
+              newChild.key
+            );
+          }
+          return updateElement(
+            returnFiber,
+            _matchedFiber,
+            newChild,
+            expirationTime
+          );
+        }
+        case REACT_PORTAL_TYPE: {
+          var _matchedFiber2 =
+            existingChildren.get(
+              newChild.key === null ? newIdx : newChild.key
+            ) || null;
+          return updatePortal(
+            returnFiber,
+            _matchedFiber2,
+            newChild,
             expirationTime
           );
-          existing.ref = coerceRef(returnFiber, child, element);
-          existing.return = returnFiber;
-          {
-            existing._debugSource = element._source;
-            existing._debugOwner = element._owner;
-          }
-          return existing;
-        } else {
-          deleteRemainingChildren(returnFiber, child);
-          break;
         }
-      } else {
-        deleteChild(returnFiber, child);
       }
-      child = child.sibling;
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        var _matchedFiber3 = existingChildren.get(newIdx) || null;
+        return updateFragment(
+          returnFiber,
+          _matchedFiber3,
+          newChild,
+          expirationTime,
+          null
+        );
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
     }
 
-    if (element.type === REACT_FRAGMENT_TYPE) {
-      var created = createFiberFromFragment(
-        element.props.children,
-        returnFiber.mode,
-        expirationTime,
-        element.key
-      );
-      created.return = returnFiber;
-      return created;
-    } else {
-      var _created4 = createFiberFromElement(
-        element,
-        returnFiber.mode,
-        expirationTime
-      );
-      _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4.return = returnFiber;
-      return _created4;
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
     }
+
+    return null;
   }
 
-  function reconcileSinglePortal(
-    returnFiber,
-    currentFirstChild,
-    portal,
-    expirationTime
-  ) {
-    var key = portal.key;
-    var child = currentFirstChild;
-    while (child !== null) {
-      // TODO: If key === null and child.key === null, then this only applies to
-      // the first item in the list.
-      if (child.key === key) {
-        if (
-          child.tag === HostPortal &&
-          child.stateNode.containerInfo === portal.containerInfo &&
-          child.stateNode.implementation === portal.implementation
-        ) {
-          deleteRemainingChildren(returnFiber, child.sibling);
-          var existing = useFiber(child, portal.children || [], expirationTime);
-          existing.return = returnFiber;
-          return existing;
-        } else {
-          deleteRemainingChildren(returnFiber, child);
+  /**
+   * Warns if there is a duplicate or missing key
+   */
+  function warnOnInvalidKey(child, knownKeys) {
+    {
+      if (typeof child !== "object" || child === null) {
+        return knownKeys;
+      }
+      switch (child.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+        case REACT_PORTAL_TYPE:
+          warnForMissingKey(child);
+          var key = child.key;
+          if (typeof key !== "string") {
+            break;
+          }
+          if (knownKeys === null) {
+            knownKeys = new Set();
+            knownKeys.add(key);
+            break;
+          }
+          if (!knownKeys.has(key)) {
+            knownKeys.add(key);
+            break;
+          }
+          warning(
+            false,
+            "Encountered two children with the same key, `%s`. " +
+              "Keys should be unique so that components maintain their identity " +
+              "across updates. Non-unique keys may cause children to be " +
+              "duplicated and/or omitted — the behavior is unsupported and " +
+              "could change in a future version.%s",
+            key,
+            getCurrentFiberStackAddendum$2()
+          );
+          break;
+        default:
           break;
-        }
-      } else {
-        deleteChild(returnFiber, child);
       }
-      child = child.sibling;
     }
-
-    var created = createFiberFromPortal(
-      portal,
-      returnFiber.mode,
-      expirationTime
-    );
-    created.return = returnFiber;
-    return created;
+    return knownKeys;
   }
 
-  // This API will tag the children with the side-effect of the reconciliation
-  // itself. They will be added to the side-effect list as we pass through the
-  // children and the parent.
-  function reconcileChildFibers(
+  function reconcileChildrenArray(
     returnFiber,
     currentFirstChild,
-    newChild,
+    newChildren,
     expirationTime
   ) {
-    // This function is not recursive.
-    // If the top level item is an array, we treat it as a set of children,
-    // not as a fragment. Nested arrays on the other hand will be treated as
-    // fragment nodes. Recursion happens at the normal flow.
+    // This algorithm can't optimize by searching from boths ends since we
+    // don't have backpointers on fibers. I'm trying to see how far we can get
+    // with that model. If it ends up not being worth the tradeoffs, we can
+    // add it later.
 
-    // Handle top level unkeyed fragments as if they were arrays.
-    // This leads to an ambiguity between <>{[...]}</> and <>...</>.
-    // We treat the ambiguous cases above the same.
-    if (
-      typeof newChild === "object" &&
-      newChild !== null &&
-      newChild.type === REACT_FRAGMENT_TYPE &&
-      newChild.key === null
-    ) {
-      newChild = newChild.props.children;
-    }
+    // Even with a two ended optimization, we'd want to optimize for the case
+    // where there are few changes and brute force the comparison instead of
+    // going for the Map. It'd like to explore hitting that path first in
+    // forward-only mode and only go for the Map once we notice that we need
+    // lots of look ahead. This doesn't handle reversal as well as two ended
+    // search but that's unusual. Besides, for the two ended optimization to
+    // work on Iterables, we'd need to copy the whole set.
 
-    // Handle object types
-    var isObject = typeof newChild === "object" && newChild !== null;
+    // In this first iteration, we'll just live with hitting the bad case
+    // (adding everything to a Map) in for every insert/move.
 
-    if (isObject) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return placeSingleChild(
-            reconcileSingleElement(
-              returnFiber,
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )
-          );
-        case REACT_PORTAL_TYPE:
-          return placeSingleChild(
-            reconcileSinglePortal(
-              returnFiber,
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )
-          );
-      }
-    }
+    // If you change this code, also update reconcileChildrenIterator() which
+    // uses the same algorithm.
 
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      return placeSingleChild(
-        reconcileSingleTextNode(
-          returnFiber,
-          currentFirstChild,
-          "" + newChild,
-          expirationTime
-        )
-      );
+    {
+      // First, validate keys.
+      var knownKeys = null;
+      for (var i = 0; i < newChildren.length; i++) {
+        var child = newChildren[i];
+        knownKeys = warnOnInvalidKey(child, knownKeys);
+      }
     }
 
-    if (isArray$1(newChild)) {
-      return reconcileChildrenArray(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
-      );
-    }
+    var resultingFirstChild = null;
+    var previousNewFiber = null;
 
-    if (getIteratorFn(newChild)) {
-      return reconcileChildrenIterator(
+    var oldFiber = currentFirstChild;
+    var lastPlacedIndex = 0;
+    var newIdx = 0;
+    var nextOldFiber = null;
+    for (; oldFiber !== null && newIdx < newChildren.length; newIdx++) {
+      if (oldFiber.index > newIdx) {
+        nextOldFiber = oldFiber;
+        oldFiber = null;
+      } else {
+        nextOldFiber = oldFiber.sibling;
+      }
+      var newFiber = updateSlot(
         returnFiber,
-        currentFirstChild,
-        newChild,
+        oldFiber,
+        newChildren[newIdx],
         expirationTime
       );
+      if (newFiber === null) {
+        // TODO: This breaks on empty slots like null children. That's
+        // unfortunate because it triggers the slow path all the time. We need
+        // a better way to communicate whether this was a miss or null,
+        // boolean, undefined, etc.
+        if (oldFiber === null) {
+          oldFiber = nextOldFiber;
+        }
+        break;
+      }
+      if (shouldTrackSideEffects) {
+        if (oldFiber && newFiber.alternate === null) {
+          // We matched the slot, but we didn't reuse the existing fiber, so we
+          // need to delete the existing child.
+          deleteChild(returnFiber, oldFiber);
+        }
+      }
+      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
+      if (previousNewFiber === null) {
+        // TODO: Move out of the loop. This only happens for the first run.
+        resultingFirstChild = newFiber;
+      } else {
+        // TODO: Defer siblings if we're not at the right index for this slot.
+        // I.e. if we had null values before, then we want to defer this
+        // for each null value. However, we also don't want to call updateSlot
+        // with the previous one.
+        previousNewFiber.sibling = newFiber;
+      }
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
     }
 
-    if (isObject) {
-      throwOnInvalidObjectType(returnFiber, newChild);
+    if (newIdx === newChildren.length) {
+      // We've reached the end of the new children. We can delete the rest.
+      deleteRemainingChildren(returnFiber, oldFiber);
+      return resultingFirstChild;
     }
 
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-    if (typeof newChild === "undefined") {
-      // If the new child is undefined, and the return fiber is a composite
-      // component, throw an error. If Fiber return types are disabled,
-      // we already threw above.
-      switch (returnFiber.tag) {
-        case ClassComponent: {
-          {
-            var instance = returnFiber.stateNode;
-            if (instance.render._isMockFunction) {
-              // We allow auto-mocks to proceed as if they're returning null.
-              break;
-            }
-          }
+    if (oldFiber === null) {
+      // If we don't have any more existing children we can choose a fast path
+      // since the rest will all be insertions.
+      for (; newIdx < newChildren.length; newIdx++) {
+        var _newFiber = createChild(
+          returnFiber,
+          newChildren[newIdx],
+          expirationTime
+        );
+        if (!_newFiber) {
+          continue;
         }
-        // Intentionally fall through to the next case, which handles both
-        // functions and classes
-        // eslint-disable-next-lined no-fallthrough
-        case FunctionalComponent: {
-          var Component = returnFiber.type;
-          invariant(
-            false,
-            "%s(...): Nothing was returned from render. This usually means a " +
-              "return statement is missing. Or, to render nothing, " +
-              "return null.",
-            Component.displayName || Component.name || "Component"
-          );
+        lastPlacedIndex = placeChild(_newFiber, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          // TODO: Move out of the loop. This only happens for the first run.
+          resultingFirstChild = _newFiber;
+        } else {
+          previousNewFiber.sibling = _newFiber;
         }
+        previousNewFiber = _newFiber;
       }
+      return resultingFirstChild;
     }
 
-    // Remaining cases are all treated as empty.
-    return deleteRemainingChildren(returnFiber, currentFirstChild);
-  }
-
-  return reconcileChildFibers;
-}
-
-var reconcileChildFibers = ChildReconciler(true);
-var mountChildFibers = ChildReconciler(false);
-
-function cloneChildFibers(current, workInProgress) {
-  invariant(
-    current === null || workInProgress.child === current.child,
-    "Resuming work not yet implemented."
-  );
-
-  if (workInProgress.child === null) {
-    return;
-  }
-
-  var currentChild = workInProgress.child;
-  var newChild = createWorkInProgress(
-    currentChild,
-    currentChild.pendingProps,
-    currentChild.expirationTime
-  );
-  workInProgress.child = newChild;
-
-  newChild.return = workInProgress;
-  while (currentChild.sibling !== null) {
-    currentChild = currentChild.sibling;
-    newChild = newChild.sibling = createWorkInProgress(
-      currentChild,
-      currentChild.pendingProps,
-      currentChild.expirationTime
-    );
-    newChild.return = workInProgress;
-  }
-  newChild.sibling = null;
-}
-
-var getCurrentFiberStackAddendum =
-  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+    // Add all children to a key map for quick lookups.
+    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
 
-var didWarnAboutBadClass = void 0;
-var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
-var didWarnAboutStatelessRefs = void 0;
+    // Keep scanning and use the map to restore deleted items as moves.
+    for (; newIdx < newChildren.length; newIdx++) {
+      var _newFiber2 = updateFromMap(
+        existingChildren,
+        returnFiber,
+        newIdx,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (_newFiber2) {
+        if (shouldTrackSideEffects) {
+          if (_newFiber2.alternate !== null) {
+            // The new fiber is a work in progress, but if there exists a
+            // current, that means that we reused the fiber. We need to delete
+            // it from the child list so that we don't add it to the deletion
+            // list.
+            existingChildren.delete(
+              _newFiber2.key === null ? newIdx : _newFiber2.key
+            );
+          }
+        }
+        lastPlacedIndex = placeChild(_newFiber2, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          resultingFirstChild = _newFiber2;
+        } else {
+          previousNewFiber.sibling = _newFiber2;
+        }
+        previousNewFiber = _newFiber2;
+      }
+    }
 
-{
-  didWarnAboutBadClass = {};
-  didWarnAboutGetDerivedStateOnFunctionalComponent = {};
-  didWarnAboutStatelessRefs = {};
-}
+    if (shouldTrackSideEffects) {
+      // Any existing children that weren't consumed above were deleted. We need
+      // to add them to the deletion list.
+      existingChildren.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    }
 
-var ReactFiberBeginWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  profilerTimer,
-  recalculateCurrentTime
-) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
-  var pushHostContext = hostContext.pushHostContext,
-    pushHostContainer = hostContext.pushHostContainer;
-  var pushProvider = newContext.pushProvider,
-    getContextCurrentValue = newContext.getContextCurrentValue,
-    getContextChangedBits = newContext.getContextChangedBits;
-  var markActualRenderTimeStarted = profilerTimer.markActualRenderTimeStarted,
-    stopBaseRenderTimerIfRunning = profilerTimer.stopBaseRenderTimerIfRunning;
-  var getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    hasLegacyContextChanged = legacyContext.hasContextChanged,
-    pushLegacyContextProvider = legacyContext.pushContextProvider,
-    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
-    invalidateContextProvider = legacyContext.invalidateContextProvider;
-  var enterHydrationState = hydrationContext.enterHydrationState,
-    resetHydrationState = hydrationContext.resetHydrationState,
-    tryToClaimNextHydratableInstance =
-      hydrationContext.tryToClaimNextHydratableInstance;
-
-  var _ReactFiberClassCompo = ReactFiberClassComponent(
-      legacyContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      memoizeProps,
-      memoizeState,
-      recalculateCurrentTime
-    ),
-    adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
-    constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
-    mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
-    resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
-    updateClassInstance = _ReactFiberClassCompo.updateClassInstance;
-
-  // TODO: Remove this and use reconcileChildrenAtExpirationTime directly.
-
-  function reconcileChildren(current, workInProgress, nextChildren) {
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      workInProgress.expirationTime
-    );
+    return resultingFirstChild;
   }
 
-  function reconcileChildrenAtExpirationTime(
-    current,
-    workInProgress,
-    nextChildren,
-    renderExpirationTime
+  function reconcileChildrenIterator(
+    returnFiber,
+    currentFirstChild,
+    newChildrenIterable,
+    expirationTime
   ) {
-    if (current === null) {
-      // If this is a fresh new component that hasn't been rendered yet, we
-      // won't update its child set by applying minimal side-effects. Instead,
-      // we will add them all to the child before it gets rendered. That means
-      // we can optimize this reconciliation pass by not tracking side-effects.
-      workInProgress.child = mountChildFibers(
-        workInProgress,
-        null,
-        nextChildren,
-        renderExpirationTime
-      );
-    } else {
-      // If the current child is the same as the work in progress, it means that
-      // we haven't yet started any work on these children. Therefore, we use
-      // the clone algorithm to create a copy of all the current children.
+    // This is the same implementation as reconcileChildrenArray(),
+    // but using the iterator instead.
 
-      // If we had any progressed work already, that is invalid at this point so
-      // let's throw it out.
-      workInProgress.child = reconcileChildFibers(
-        workInProgress,
-        current.child,
-        nextChildren,
-        renderExpirationTime
-      );
-    }
-  }
+    var iteratorFn = getIteratorFn(newChildrenIterable);
+    invariant(
+      typeof iteratorFn === "function",
+      "An object is not an iterable. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
 
-  function updateForwardRef(current, workInProgress) {
-    var render = workInProgress.type.render;
-    var nextProps = workInProgress.pendingProps;
-    var ref = workInProgress.ref;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextProps) {
-      var currentRef = current !== null ? current.ref : null;
-      if (ref === currentRef) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    {
+      // Warn about using Maps as children
+      if (newChildrenIterable.entries === iteratorFn) {
+        !didWarnAboutMaps
+          ? warning(
+              false,
+              "Using Maps as children is unsupported and will likely yield " +
+                "unexpected results. Convert it to a sequence/iterable of keyed " +
+                "ReactElements instead.%s",
+              getCurrentFiberStackAddendum$2()
+            )
+          : void 0;
+        didWarnAboutMaps = true;
       }
-    }
 
-    var nextChildren = void 0;
-    {
-      ReactCurrentOwner.current = workInProgress;
-      ReactDebugCurrentFiber.setCurrentPhase("render");
-      nextChildren = render(nextProps, ref);
-      ReactDebugCurrentFiber.setCurrentPhase(null);
+      // First, validate keys.
+      // We'll get a different iterator later for the main pass.
+      var _newChildren = iteratorFn.call(newChildrenIterable);
+      if (_newChildren) {
+        var knownKeys = null;
+        var _step = _newChildren.next();
+        for (; !_step.done; _step = _newChildren.next()) {
+          var child = _step.value;
+          knownKeys = warnOnInvalidKey(child, knownKeys);
+        }
+      }
     }
 
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
-  }
+    var newChildren = iteratorFn.call(newChildrenIterable);
+    invariant(newChildren != null, "An iterable object provided no iterator.");
 
-  function updateFragment(current, workInProgress) {
-    var nextChildren = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextChildren) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
-  }
+    var resultingFirstChild = null;
+    var previousNewFiber = null;
 
-  function updateMode(current, workInProgress) {
-    var nextChildren = workInProgress.pendingProps.children;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (
-      nextChildren === null ||
-      workInProgress.memoizedProps === nextChildren
+    var oldFiber = currentFirstChild;
+    var lastPlacedIndex = 0;
+    var newIdx = 0;
+    var nextOldFiber = null;
+
+    var step = newChildren.next();
+    for (
+      ;
+      oldFiber !== null && !step.done;
+      newIdx++, step = newChildren.next()
     ) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      if (oldFiber.index > newIdx) {
+        nextOldFiber = oldFiber;
+        oldFiber = null;
+      } else {
+        nextOldFiber = oldFiber.sibling;
+      }
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        step.value,
+        expirationTime
+      );
+      if (newFiber === null) {
+        // TODO: This breaks on empty slots like null children. That's
+        // unfortunate because it triggers the slow path all the time. We need
+        // a better way to communicate whether this was a miss or null,
+        // boolean, undefined, etc.
+        if (!oldFiber) {
+          oldFiber = nextOldFiber;
+        }
+        break;
+      }
+      if (shouldTrackSideEffects) {
+        if (oldFiber && newFiber.alternate === null) {
+          // We matched the slot, but we didn't reuse the existing fiber, so we
+          // need to delete the existing child.
+          deleteChild(returnFiber, oldFiber);
+        }
+      }
+      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
+      if (previousNewFiber === null) {
+        // TODO: Move out of the loop. This only happens for the first run.
+        resultingFirstChild = newFiber;
+      } else {
+        // TODO: Defer siblings if we're not at the right index for this slot.
+        // I.e. if we had null values before, then we want to defer this
+        // for each null value. However, we also don't want to call updateSlot
+        // with the previous one.
+        previousNewFiber.sibling = newFiber;
+      }
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
     }
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
-  }
-
-  function updateProfiler(current, workInProgress) {
-    var nextProps = workInProgress.pendingProps;
-    if (enableProfilerTimer) {
-      // Start render timer here and push start time onto queue
-      markActualRenderTimeStarted(workInProgress);
 
-      // Let the "complete" phase know to stop the timer,
-      // And the scheduler to record the measured time.
-      workInProgress.effectTag |= Update;
-    }
-    if (workInProgress.memoizedProps === nextProps) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    if (step.done) {
+      // We've reached the end of the new children. We can delete the rest.
+      deleteRemainingChildren(returnFiber, oldFiber);
+      return resultingFirstChild;
     }
-    var nextChildren = nextProps.children;
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
-  }
 
-  function markRef(current, workInProgress) {
-    var ref = workInProgress.ref;
-    if (
-      (current === null && ref !== null) ||
-      (current !== null && current.ref !== ref)
-    ) {
-      // Schedule a Ref effect
-      workInProgress.effectTag |= Ref;
+    if (oldFiber === null) {
+      // If we don't have any more existing children we can choose a fast path
+      // since the rest will all be insertions.
+      for (; !step.done; newIdx++, step = newChildren.next()) {
+        var _newFiber3 = createChild(returnFiber, step.value, expirationTime);
+        if (_newFiber3 === null) {
+          continue;
+        }
+        lastPlacedIndex = placeChild(_newFiber3, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          // TODO: Move out of the loop. This only happens for the first run.
+          resultingFirstChild = _newFiber3;
+        } else {
+          previousNewFiber.sibling = _newFiber3;
+        }
+        previousNewFiber = _newFiber3;
+      }
+      return resultingFirstChild;
     }
-  }
 
-  function updateFunctionalComponent(current, workInProgress) {
-    var fn = workInProgress.type;
-    var nextProps = workInProgress.pendingProps;
+    // Add all children to a key map for quick lookups.
+    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
 
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else {
-      if (workInProgress.memoizedProps === nextProps) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    // Keep scanning and use the map to restore deleted items as moves.
+    for (; !step.done; newIdx++, step = newChildren.next()) {
+      var _newFiber4 = updateFromMap(
+        existingChildren,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      );
+      if (_newFiber4 !== null) {
+        if (shouldTrackSideEffects) {
+          if (_newFiber4.alternate !== null) {
+            // The new fiber is a work in progress, but if there exists a
+            // current, that means that we reused the fiber. We need to delete
+            // it from the child list so that we don't add it to the deletion
+            // list.
+            existingChildren.delete(
+              _newFiber4.key === null ? newIdx : _newFiber4.key
+            );
+          }
+        }
+        lastPlacedIndex = placeChild(_newFiber4, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          resultingFirstChild = _newFiber4;
+        } else {
+          previousNewFiber.sibling = _newFiber4;
+        }
+        previousNewFiber = _newFiber4;
       }
-      // TODO: consider bringing fn.shouldComponentUpdate() back.
-      // It used to be here.
     }
 
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var context = getMaskedContext(workInProgress, unmaskedContext);
+    if (shouldTrackSideEffects) {
+      // Any existing children that weren't consumed above were deleted. We need
+      // to add them to the deletion list.
+      existingChildren.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    }
 
-    var nextChildren = void 0;
+    return resultingFirstChild;
+  }
 
-    {
-      ReactCurrentOwner.current = workInProgress;
-      ReactDebugCurrentFiber.setCurrentPhase("render");
-      nextChildren = fn(nextProps, context);
-      ReactDebugCurrentFiber.setCurrentPhase(null);
+  function reconcileSingleTextNode(
+    returnFiber,
+    currentFirstChild,
+    textContent,
+    expirationTime
+  ) {
+    // There's no need to check for keys on text nodes since we don't have a
+    // way to define them.
+    if (currentFirstChild !== null && currentFirstChild.tag === HostText) {
+      // We already have an existing node so let's just update it and delete
+      // the rest.
+      deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
+      var existing = useFiber(currentFirstChild, textContent, expirationTime);
+      existing.return = returnFiber;
+      return existing;
     }
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
+    // The existing first child is not a text node so we need to create one
+    // and delete the existing ones.
+    deleteRemainingChildren(returnFiber, currentFirstChild);
+    var created = createFiberFromText(
+      textContent,
+      returnFiber.mode,
+      expirationTime
+    );
+    created.return = returnFiber;
+    return created;
   }
 
-  function updateClassComponent(current, workInProgress, renderExpirationTime) {
-    // Push context providers early to prevent context stack mismatches.
-    // During mounting we don't know the child context yet as the instance doesn't exist.
-    // We will invalidate the child context in finishClassComponent() right after rendering.
-    var hasContext = pushLegacyContextProvider(workInProgress);
-    var shouldUpdate = void 0;
-    if (current === null) {
-      if (workInProgress.stateNode === null) {
-        // In the initial pass we might need to construct the instance.
-        constructClassInstance(
-          workInProgress,
-          workInProgress.pendingProps,
-          renderExpirationTime
-        );
-        mountClassInstance(workInProgress, renderExpirationTime);
-
-        shouldUpdate = true;
+  function reconcileSingleElement(
+    returnFiber,
+    currentFirstChild,
+    element,
+    expirationTime
+  ) {
+    var key = element.key;
+    var child = currentFirstChild;
+    while (child !== null) {
+      // TODO: If key === null and child.key === null, then this only applies to
+      // the first item in the list.
+      if (child.key === key) {
+        if (
+          child.tag === Fragment
+            ? element.type === REACT_FRAGMENT_TYPE
+            : child.type === element.type
+        ) {
+          deleteRemainingChildren(returnFiber, child.sibling);
+          var existing = useFiber(
+            child,
+            element.type === REACT_FRAGMENT_TYPE
+              ? element.props.children
+              : element.props,
+            expirationTime
+          );
+          existing.ref = coerceRef(returnFiber, child, element);
+          existing.return = returnFiber;
+          {
+            existing._debugSource = element._source;
+            existing._debugOwner = element._owner;
+          }
+          return existing;
+        } else {
+          deleteRemainingChildren(returnFiber, child);
+          break;
+        }
       } else {
-        // In a resume, we'll already have an instance we can reuse.
-        shouldUpdate = resumeMountClassInstance(
-          workInProgress,
-          renderExpirationTime
-        );
+        deleteChild(returnFiber, child);
       }
+      child = child.sibling;
+    }
+
+    if (element.type === REACT_FRAGMENT_TYPE) {
+      var created = createFiberFromFragment(
+        element.props.children,
+        returnFiber.mode,
+        expirationTime,
+        element.key
+      );
+      created.return = returnFiber;
+      return created;
     } else {
-      shouldUpdate = updateClassInstance(
-        current,
-        workInProgress,
-        renderExpirationTime
+      var _created4 = createFiberFromElement(
+        element,
+        returnFiber.mode,
+        expirationTime
       );
+      _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
+      _created4.return = returnFiber;
+      return _created4;
     }
-    return finishClassComponent(
-      current,
-      workInProgress,
-      shouldUpdate,
-      hasContext,
-      renderExpirationTime
-    );
   }
 
-  function finishClassComponent(
-    current,
-    workInProgress,
-    shouldUpdate,
-    hasContext,
-    renderExpirationTime
+  function reconcileSinglePortal(
+    returnFiber,
+    currentFirstChild,
+    portal,
+    expirationTime
   ) {
-    // Refs should update even if shouldComponentUpdate returns false
-    markRef(current, workInProgress);
-
-    var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
-
-    if (!shouldUpdate && !didCaptureError) {
-      // Context providers should defer to sCU for rendering
-      if (hasContext) {
-        invalidateContextProvider(workInProgress, false);
-      }
-
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-
-    // Rerender
-    ReactCurrentOwner.current = workInProgress;
-    var nextChildren = void 0;
-    if (
-      didCaptureError &&
-      (!enableGetDerivedStateFromCatch ||
-        typeof ctor.getDerivedStateFromCatch !== "function")
-    ) {
-      // If we captured an error, but getDerivedStateFrom catch is not defined,
-      // unmount all the children. componentDidCatch will schedule an update to
-      // re-render a fallback. This is temporary until we migrate everyone to
-      // the new API.
-      // TODO: Warn in a future release.
-      nextChildren = null;
-
-      if (enableProfilerTimer) {
-        stopBaseRenderTimerIfRunning();
-      }
-    } else {
-      {
-        ReactDebugCurrentFiber.setCurrentPhase("render");
-        nextChildren = instance.render();
+    var key = portal.key;
+    var child = currentFirstChild;
+    while (child !== null) {
+      // TODO: If key === null and child.key === null, then this only applies to
+      // the first item in the list.
+      if (child.key === key) {
         if (
-          debugRenderPhaseSideEffects ||
-          (debugRenderPhaseSideEffectsForStrictMode &&
-            workInProgress.mode & StrictMode)
+          child.tag === HostPortal &&
+          child.stateNode.containerInfo === portal.containerInfo &&
+          child.stateNode.implementation === portal.implementation
         ) {
-          instance.render();
+          deleteRemainingChildren(returnFiber, child.sibling);
+          var existing = useFiber(child, portal.children || [], expirationTime);
+          existing.return = returnFiber;
+          return existing;
+        } else {
+          deleteRemainingChildren(returnFiber, child);
+          break;
         }
-        ReactDebugCurrentFiber.setCurrentPhase(null);
+      } else {
+        deleteChild(returnFiber, child);
       }
+      child = child.sibling;
     }
 
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    if (didCaptureError) {
-      // If we're recovering from an error, reconcile twice: first to delete
-      // all the existing children.
-      reconcileChildrenAtExpirationTime(
-        current,
-        workInProgress,
-        null,
-        renderExpirationTime
-      );
-      workInProgress.child = null;
-      // Now we can continue reconciling like normal. This has the effect of
-      // remounting all children regardless of whether their their
-      // identity matches.
-    }
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      renderExpirationTime
+    var created = createFiberFromPortal(
+      portal,
+      returnFiber.mode,
+      expirationTime
     );
-    // Memoize props and state using the values we just used to render.
-    // TODO: Restructure so we never read values from the instance.
-    memoizeState(workInProgress, instance.state);
-    memoizeProps(workInProgress, instance.props);
+    created.return = returnFiber;
+    return created;
+  }
 
-    // The context might have changed so we need to recalculate it.
-    if (hasContext) {
-      invalidateContextProvider(workInProgress, true);
+  // This API will tag the children with the side-effect of the reconciliation
+  // itself. They will be added to the side-effect list as we pass through the
+  // children and the parent.
+  function reconcileChildFibers(
+    returnFiber,
+    currentFirstChild,
+    newChild,
+    expirationTime
+  ) {
+    // This function is not recursive.
+    // If the top level item is an array, we treat it as a set of children,
+    // not as a fragment. Nested arrays on the other hand will be treated as
+    // fragment nodes. Recursion happens at the normal flow.
+
+    // Handle top level unkeyed fragments as if they were arrays.
+    // This leads to an ambiguity between <>{[...]}</> and <>...</>.
+    // We treat the ambiguous cases above the same.
+    var isUnkeyedTopLevelFragment =
+      typeof newChild === "object" &&
+      newChild !== null &&
+      newChild.type === REACT_FRAGMENT_TYPE &&
+      newChild.key === null;
+    if (isUnkeyedTopLevelFragment) {
+      newChild = newChild.props.children;
     }
 
-    return workInProgress.child;
-  }
+    // Handle object types
+    var isObject = typeof newChild === "object" && newChild !== null;
 
-  function pushHostRootContext(workInProgress) {
-    var root = workInProgress.stateNode;
-    if (root.pendingContext) {
-      pushTopLevelContextObject(
-        workInProgress,
-        root.pendingContext,
-        root.pendingContext !== root.context
-      );
-    } else if (root.context) {
-      // Should always be set
-      pushTopLevelContextObject(workInProgress, root.context, false);
+    if (isObject) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return placeSingleChild(
+            reconcileSingleElement(
+              returnFiber,
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )
+          );
+        case REACT_PORTAL_TYPE:
+          return placeSingleChild(
+            reconcileSinglePortal(
+              returnFiber,
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )
+          );
+      }
     }
-    pushHostContainer(workInProgress, root.containerInfo);
-  }
 
-  function updateHostRoot(current, workInProgress, renderExpirationTime) {
-    pushHostRootContext(workInProgress);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      var nextProps = workInProgress.pendingProps;
-      var prevState = workInProgress.memoizedState;
-      var prevChildren = prevState !== null ? prevState.element : null;
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        nextProps,
-        null,
-        renderExpirationTime
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      return placeSingleChild(
+        reconcileSingleTextNode(
+          returnFiber,
+          currentFirstChild,
+          "" + newChild,
+          expirationTime
+        )
       );
-      var nextState = workInProgress.memoizedState;
-      // Caution: React DevTools currently depends on this property
-      // being called "element".
-      var nextChildren = nextState.element;
-
-      if (nextChildren === prevChildren) {
-        // If the state is the same as before, that's a bailout because we had
-        // no work that expires at this time.
-        resetHydrationState();
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-      var root = workInProgress.stateNode;
-      if (
-        (current === null || current.child === null) &&
-        root.hydrate &&
-        enterHydrationState(workInProgress)
-      ) {
-        // If we don't have any current children this might be the first pass.
-        // We always try to hydrate. If this isn't a hydration pass there won't
-        // be any children to hydrate which is effectively the same thing as
-        // not hydrating.
-
-        // This is a bit of a hack. We track the host root as a placement to
-        // know that we're currently in a mounting state. That way isMounted
-        // works as expected. We must reset this before committing.
-        // TODO: Delete this when we delete isMounted and findDOMNode.
-        workInProgress.effectTag |= Placement;
-
-        // Ensure that children mount into this root without tracking
-        // side-effects. This ensures that we don't store Placement effects on
-        // nodes that will be hydrated.
-        workInProgress.child = mountChildFibers(
-          workInProgress,
-          null,
-          nextChildren,
-          renderExpirationTime
-        );
-      } else {
-        // Otherwise reset hydration state in case we aborted and resumed another
-        // root.
-        resetHydrationState();
-        reconcileChildren(current, workInProgress, nextChildren);
-      }
-      return workInProgress.child;
     }
-    resetHydrationState();
-    // If there is no update queue, that's a bailout because the root has no props.
-    return bailoutOnAlreadyFinishedWork(current, workInProgress);
-  }
 
-  function updateHostComponent(current, workInProgress, renderExpirationTime) {
-    pushHostContext(workInProgress);
+    if (isArray$1(newChild)) {
+      return reconcileChildrenArray(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    }
 
-    if (current === null) {
-      tryToClaimNextHydratableInstance(workInProgress);
+    if (getIteratorFn(newChild)) {
+      return reconcileChildrenIterator(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
     }
 
-    var type = workInProgress.type;
-    var memoizedProps = workInProgress.memoizedProps;
-    var nextProps = workInProgress.pendingProps;
-    var prevProps = current !== null ? current.memoizedProps : null;
+    if (isObject) {
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
 
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (memoizedProps === nextProps) {
-      var isHidden =
-        workInProgress.mode & AsyncMode &&
-        shouldDeprioritizeSubtree(type, nextProps);
-      if (isHidden) {
-        // Before bailing out, make sure we've deprioritized a hidden component.
-        workInProgress.expirationTime = Never;
-      }
-      if (!isHidden || renderExpirationTime !== Never) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
+    if (typeof newChild === "undefined" && !isUnkeyedTopLevelFragment) {
+      // If the new child is undefined, and the return fiber is a composite
+      // component, throw an error. If Fiber return types are disabled,
+      // we already threw above.
+      switch (returnFiber.tag) {
+        case ClassComponent: {
+          {
+            var instance = returnFiber.stateNode;
+            if (instance.render._isMockFunction) {
+              // We allow auto-mocks to proceed as if they're returning null.
+              break;
+            }
+          }
+        }
+        // Intentionally fall through to the next case, which handles both
+        // functions and classes
+        // eslint-disable-next-lined no-fallthrough
+        case FunctionalComponent: {
+          var Component = returnFiber.type;
+          invariant(
+            false,
+            "%s(...): Nothing was returned from render. This usually means a " +
+              "return statement is missing. Or, to render nothing, " +
+              "return null.",
+            Component.displayName || Component.name || "Component"
+          );
+        }
       }
-      // If we're rendering a hidden node at hidden priority, don't bailout. The
-      // parent is complete, but the children may not be.
     }
 
-    var nextChildren = nextProps.children;
-    var isDirectTextChild = shouldSetTextContent(type, nextProps);
+    // Remaining cases are all treated as empty.
+    return deleteRemainingChildren(returnFiber, currentFirstChild);
+  }
 
-    if (isDirectTextChild) {
-      // We special case a direct text child of a host node. This is a common
-      // case. We won't handle it as a reified child. We will instead handle
-      // this in the host environment that also have access to this prop. That
-      // avoids allocating another HostText fiber and traversing it.
-      nextChildren = null;
-    } else if (prevProps && shouldSetTextContent(type, prevProps)) {
-      // If we're switching from a direct text child to a normal child, or to
-      // empty, we need to schedule the text content to be reset.
-      workInProgress.effectTag |= ContentReset;
-    }
+  return reconcileChildFibers;
+}
 
-    markRef(current, workInProgress);
+var reconcileChildFibers = ChildReconciler(true);
+var mountChildFibers = ChildReconciler(false);
 
-    // Check the host config to see if the children are offscreen/hidden.
-    if (
-      renderExpirationTime !== Never &&
-      workInProgress.mode & AsyncMode &&
-      shouldDeprioritizeSubtree(type, nextProps)
-    ) {
-      // Down-prioritize the children.
-      workInProgress.expirationTime = Never;
-      // Bailout and come back to this fiber later.
-      workInProgress.memoizedProps = nextProps;
-      return null;
-    }
+function cloneChildFibers(current, workInProgress) {
+  invariant(
+    current === null || workInProgress.child === current.child,
+    "Resuming work not yet implemented."
+  );
 
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
+  if (workInProgress.child === null) {
+    return;
   }
 
-  function updateHostText(current, workInProgress) {
-    if (current === null) {
-      tryToClaimNextHydratableInstance(workInProgress);
-    }
-    var nextProps = workInProgress.pendingProps;
-    memoizeProps(workInProgress, nextProps);
-    // Nothing to do here. This is terminal. We'll do the completion step
-    // immediately after.
-    return null;
-  }
+  var currentChild = workInProgress.child;
+  var newChild = createWorkInProgress(
+    currentChild,
+    currentChild.pendingProps,
+    currentChild.expirationTime
+  );
+  workInProgress.child = newChild;
 
-  function mountIndeterminateComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    invariant(
-      current === null,
-      "An indeterminate component should never have mounted. This error is " +
-        "likely caused by a bug in React. Please file an issue."
+  newChild.return = workInProgress;
+  while (currentChild.sibling !== null) {
+    currentChild = currentChild.sibling;
+    newChild = newChild.sibling = createWorkInProgress(
+      currentChild,
+      currentChild.pendingProps,
+      currentChild.expirationTime
     );
-    var fn = workInProgress.type;
-    var props = workInProgress.pendingProps;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var context = getMaskedContext(workInProgress, unmaskedContext);
-
-    var value = void 0;
-
-    {
-      if (fn.prototype && typeof fn.prototype.render === "function") {
-        var componentName = getComponentName(workInProgress) || "Unknown";
-
-        if (!didWarnAboutBadClass[componentName]) {
-          warning(
-            false,
-            "The <%s /> component appears to have a render method, but doesn't extend React.Component. " +
-              "This is likely to cause errors. Change %s to extend React.Component instead.",
-            componentName,
-            componentName
-          );
-          didWarnAboutBadClass[componentName] = true;
-        }
-      }
-      ReactCurrentOwner.current = workInProgress;
-      value = fn(props, context);
-    }
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
+    newChild.return = workInProgress;
+  }
+  newChild.sibling = null;
+}
 
-    if (
-      typeof value === "object" &&
-      value !== null &&
-      typeof value.render === "function" &&
-      value.$$typeof === undefined
-    ) {
-      var Component = workInProgress.type;
+// The deepest Fiber on the stack involved in a hydration context.
+// This may have been an insertion or a hydration.
+var hydrationParentFiber = null;
+var nextHydratableInstance = null;
+var isHydrating = false;
 
-      // Proceed under the assumption that this is a class instance
-      workInProgress.tag = ClassComponent;
+function enterHydrationState(fiber) {
+  if (!supportsHydration) {
+    return false;
+  }
 
-      workInProgress.memoizedState =
-        value.state !== null && value.state !== undefined ? value.state : null;
+  var parentInstance = fiber.stateNode.containerInfo;
+  nextHydratableInstance = getFirstHydratableChild(parentInstance);
+  hydrationParentFiber = fiber;
+  isHydrating = true;
+  return true;
+}
 
-      var getDerivedStateFromProps = Component.getDerivedStateFromProps;
-      if (typeof getDerivedStateFromProps === "function") {
-        applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          props
+function deleteHydratableInstance(returnFiber, instance) {
+  {
+    switch (returnFiber.tag) {
+      case HostRoot:
+        didNotHydrateContainerInstance(
+          returnFiber.stateNode.containerInfo,
+          instance
         );
-      }
+        break;
+      case HostComponent:
+        didNotHydrateInstance(
+          returnFiber.type,
+          returnFiber.memoizedProps,
+          returnFiber.stateNode,
+          instance
+        );
+        break;
+    }
+  }
 
-      // Push context providers early to prevent context stack mismatches.
-      // During mounting we don't know the child context yet as the instance doesn't exist.
-      // We will invalidate the child context in finishClassComponent() right after rendering.
-      var hasContext = pushLegacyContextProvider(workInProgress);
-      adoptClassInstance(workInProgress, value);
-      mountClassInstance(workInProgress, renderExpirationTime);
-      return finishClassComponent(
-        current,
-        workInProgress,
-        true,
-        hasContext,
-        renderExpirationTime
-      );
-    } else {
-      // Proceed under the assumption that this is a functional component
-      workInProgress.tag = FunctionalComponent;
-      {
-        var _Component = workInProgress.type;
+  var childToDelete = createFiberFromHostInstanceForDeletion();
+  childToDelete.stateNode = instance;
+  childToDelete.return = returnFiber;
+  childToDelete.effectTag = Deletion;
 
-        if (_Component) {
-          !!_Component.childContextTypes
-            ? warning(
-                false,
-                "%s(...): childContextTypes cannot be defined on a functional component.",
-                _Component.displayName || _Component.name || "Component"
-              )
-            : void 0;
-        }
-        if (workInProgress.ref !== null) {
-          var info = "";
-          var ownerName = ReactDebugCurrentFiber.getCurrentFiberOwnerName();
-          if (ownerName) {
-            info += "\n\nCheck the render method of `" + ownerName + "`.";
-          }
+  // This might seem like it belongs on progressedFirstDeletion. However,
+  // these children are not part of the reconciliation list of children.
+  // Even if we abort and rereconcile the children, that will try to hydrate
+  // again and the nodes are still in the host tree so these will be
+  // recreated.
+  if (returnFiber.lastEffect !== null) {
+    returnFiber.lastEffect.nextEffect = childToDelete;
+    returnFiber.lastEffect = childToDelete;
+  } else {
+    returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+  }
+}
 
-          var warningKey = ownerName || workInProgress._debugID || "";
-          var debugSource = workInProgress._debugSource;
-          if (debugSource) {
-            warningKey = debugSource.fileName + ":" + debugSource.lineNumber;
-          }
-          if (!didWarnAboutStatelessRefs[warningKey]) {
-            didWarnAboutStatelessRefs[warningKey] = true;
-            warning(
-              false,
-              "Stateless function components cannot be given refs. " +
-                "Attempts to access this ref will fail.%s%s",
-              info,
-              ReactDebugCurrentFiber.getCurrentFiberStackAddendum()
-            );
-          }
+function insertNonHydratedInstance(returnFiber, fiber) {
+  fiber.effectTag |= Placement;
+  {
+    switch (returnFiber.tag) {
+      case HostRoot: {
+        var parentContainer = returnFiber.stateNode.containerInfo;
+        switch (fiber.tag) {
+          case HostComponent:
+            var type = fiber.type;
+            var props = fiber.pendingProps;
+            didNotFindHydratableContainerInstance(parentContainer, type, props);
+            break;
+          case HostText:
+            var text = fiber.pendingProps;
+            didNotFindHydratableContainerTextInstance(parentContainer, text);
+            break;
         }
-
-        if (typeof fn.getDerivedStateFromProps === "function") {
-          var _componentName = getComponentName(workInProgress) || "Unknown";
-
-          if (
-            !didWarnAboutGetDerivedStateOnFunctionalComponent[_componentName]
-          ) {
-            warning(
-              false,
-              "%s: Stateless functional components do not support getDerivedStateFromProps.",
-              _componentName
+        break;
+      }
+      case HostComponent: {
+        var parentType = returnFiber.type;
+        var parentProps = returnFiber.memoizedProps;
+        var parentInstance = returnFiber.stateNode;
+        switch (fiber.tag) {
+          case HostComponent:
+            var _type = fiber.type;
+            var _props = fiber.pendingProps;
+            didNotFindHydratableInstance(
+              parentType,
+              parentProps,
+              parentInstance,
+              _type,
+              _props
             );
-            didWarnAboutGetDerivedStateOnFunctionalComponent[
-              _componentName
-            ] = true;
-          }
+            break;
+          case HostText:
+            var _text = fiber.pendingProps;
+            didNotFindHydratableTextInstance(
+              parentType,
+              parentProps,
+              parentInstance,
+              _text
+            );
+            break;
         }
+        break;
       }
-      reconcileChildren(current, workInProgress, value);
-      memoizeProps(workInProgress, props);
-      return workInProgress.child;
+      default:
+        return;
     }
   }
+}
 
-  function updateTimeoutComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    if (enableSuspense) {
-      var nextProps = workInProgress.pendingProps;
-      var prevProps = workInProgress.memoizedProps;
-
-      var prevDidTimeout = workInProgress.memoizedState;
-
-      // Check if we already attempted to render the normal state. If we did,
-      // and we timed out, render the placeholder state.
-      var alreadyCaptured =
-        (workInProgress.effectTag & DidCapture) === NoEffect;
-      var nextDidTimeout = !alreadyCaptured;
-
-      if (hasLegacyContextChanged()) {
-        // Normally we can bail out on props equality but if context has changed
-        // we don't do the bailout and we have to reuse existing props instead.
-      } else if (nextProps === prevProps && nextDidTimeout === prevDidTimeout) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+function tryHydrate(fiber, nextInstance) {
+  switch (fiber.tag) {
+    case HostComponent: {
+      var type = fiber.type;
+      var props = fiber.pendingProps;
+      var instance = canHydrateInstance(nextInstance, type, props);
+      if (instance !== null) {
+        fiber.stateNode = instance;
+        return true;
       }
-
-      var render = nextProps.children;
-      var nextChildren = render(nextDidTimeout);
-      workInProgress.memoizedProps = nextProps;
-      workInProgress.memoizedState = nextDidTimeout;
-      reconcileChildren(current, workInProgress, nextChildren);
-      return workInProgress.child;
-    } else {
-      return null;
+      return false;
+    }
+    case HostText: {
+      var text = fiber.pendingProps;
+      var textInstance = canHydrateTextInstance(nextInstance, text);
+      if (textInstance !== null) {
+        fiber.stateNode = textInstance;
+        return true;
+      }
+      return false;
     }
+    default:
+      return false;
   }
+}
 
-  function updatePortalComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
-    var nextChildren = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextChildren) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+function tryToClaimNextHydratableInstance(fiber) {
+  if (!isHydrating) {
+    return;
+  }
+  var nextInstance = nextHydratableInstance;
+  if (!nextInstance) {
+    // Nothing to hydrate. Make it an insertion.
+    insertNonHydratedInstance(hydrationParentFiber, fiber);
+    isHydrating = false;
+    hydrationParentFiber = fiber;
+    return;
+  }
+  var firstAttemptedInstance = nextInstance;
+  if (!tryHydrate(fiber, nextInstance)) {
+    // If we can't hydrate this instance let's try the next one.
+    // We use this as a heuristic. It's based on intuition and not data so it
+    // might be flawed or unnecessary.
+    nextInstance = getNextHydratableSibling(firstAttemptedInstance);
+    if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
+      // Nothing to hydrate. Make it an insertion.
+      insertNonHydratedInstance(hydrationParentFiber, fiber);
+      isHydrating = false;
+      hydrationParentFiber = fiber;
+      return;
     }
+    // We matched the next one, we'll now assume that the first one was
+    // superfluous and we'll delete it. Since we can't eagerly delete it
+    // we'll have to schedule a deletion. To do that, this node needs a dummy
+    // fiber associated with it.
+    deleteHydratableInstance(hydrationParentFiber, firstAttemptedInstance);
+  }
+  hydrationParentFiber = fiber;
+  nextHydratableInstance = getFirstHydratableChild(nextInstance);
+}
 
-    if (current === null) {
-      // Portals are special because we don't append the children during mount
-      // but at commit. Therefore we need to track insertions which the normal
-      // flow doesn't do during mount. This doesn't happen at the root because
-      // the root always starts with a "current" with a null child.
-      // TODO: Consider unifying this with how the root works.
-      workInProgress.child = reconcileChildFibers(
-        workInProgress,
-        null,
-        nextChildren,
-        renderExpirationTime
-      );
-      memoizeProps(workInProgress, nextChildren);
-    } else {
-      reconcileChildren(current, workInProgress, nextChildren);
-      memoizeProps(workInProgress, nextChildren);
-    }
-    return workInProgress.child;
+function prepareToHydrateHostInstance(
+  fiber,
+  rootContainerInstance,
+  hostContext
+) {
+  if (!supportsHydration) {
+    invariant(
+      false,
+      "Expected prepareToHydrateHostInstance() to never be called. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
   }
 
-  function propagateContextChange(
-    workInProgress,
-    context,
-    changedBits,
-    renderExpirationTime
-  ) {
-    var fiber = workInProgress.child;
-    if (fiber !== null) {
-      // Set the return pointer of the child to the work-in-progress fiber.
-      fiber.return = workInProgress;
-    }
-    while (fiber !== null) {
-      var nextFiber = void 0;
-      // Visit this fiber.
-      switch (fiber.tag) {
-        case ContextConsumer:
-          // Check if the context matches.
-          var observedBits = fiber.stateNode | 0;
-          if (fiber.type === context && (observedBits & changedBits) !== 0) {
-            // Update the expiration time of all the ancestors, including
-            // the alternates.
-            var node = fiber;
-            while (node !== null) {
-              var alternate = node.alternate;
-              if (
-                node.expirationTime === NoWork ||
-                node.expirationTime > renderExpirationTime
-              ) {
-                node.expirationTime = renderExpirationTime;
-                if (
-                  alternate !== null &&
-                  (alternate.expirationTime === NoWork ||
-                    alternate.expirationTime > renderExpirationTime)
-                ) {
-                  alternate.expirationTime = renderExpirationTime;
-                }
-              } else if (
-                alternate !== null &&
-                (alternate.expirationTime === NoWork ||
-                  alternate.expirationTime > renderExpirationTime)
-              ) {
-                alternate.expirationTime = renderExpirationTime;
-              } else {
-                // Neither alternate was updated, which means the rest of the
-                // ancestor path already has sufficient priority.
-                break;
-              }
-              node = node.return;
-            }
-            // Don't scan deeper than a matching consumer. When we render the
-            // consumer, we'll continue scanning from that point. This way the
-            // scanning work is time-sliced.
-            nextFiber = null;
-          } else {
-            // Traverse down.
-            nextFiber = fiber.child;
-          }
-          break;
-        case ContextProvider:
-          // Don't scan deeper if this is a matching provider
-          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
-          break;
-        default:
-          // Traverse down.
-          nextFiber = fiber.child;
-          break;
-      }
-      if (nextFiber !== null) {
-        // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber.return = fiber;
-      } else {
-        // No child. Traverse to next sibling.
-        nextFiber = fiber;
-        while (nextFiber !== null) {
-          if (nextFiber === workInProgress) {
-            // We're back to the root of this subtree. Exit.
-            nextFiber = null;
+  var instance = fiber.stateNode;
+  var updatePayload = hydrateInstance(
+    instance,
+    fiber.type,
+    fiber.memoizedProps,
+    rootContainerInstance,
+    hostContext,
+    fiber
+  );
+  // TODO: Type this specific to this type of component.
+  fiber.updateQueue = updatePayload;
+  // If the update payload indicates that there is a change or if there
+  // is a new ref we mark this as an update.
+  if (updatePayload !== null) {
+    return true;
+  }
+  return false;
+}
+
+function prepareToHydrateHostTextInstance(fiber) {
+  if (!supportsHydration) {
+    invariant(
+      false,
+      "Expected prepareToHydrateHostTextInstance() to never be called. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+
+  var textInstance = fiber.stateNode;
+  var textContent = fiber.memoizedProps;
+  var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
+  {
+    if (shouldUpdate) {
+      // We assume that prepareToHydrateHostTextInstance is called in a context where the
+      // hydration parent is the parent host component of this host text.
+      var returnFiber = hydrationParentFiber;
+      if (returnFiber !== null) {
+        switch (returnFiber.tag) {
+          case HostRoot: {
+            var parentContainer = returnFiber.stateNode.containerInfo;
+            didNotMatchHydratedContainerTextInstance(
+              parentContainer,
+              textInstance,
+              textContent
+            );
             break;
           }
-          var sibling = nextFiber.sibling;
-          if (sibling !== null) {
-            // Set the return pointer of the sibling to the work-in-progress fiber.
-            sibling.return = nextFiber.return;
-            nextFiber = sibling;
+          case HostComponent: {
+            var parentType = returnFiber.type;
+            var parentProps = returnFiber.memoizedProps;
+            var parentInstance = returnFiber.stateNode;
+            didNotMatchHydratedTextInstance(
+              parentType,
+              parentProps,
+              parentInstance,
+              textInstance,
+              textContent
+            );
             break;
           }
-          // No more siblings. Traverse up.
-          nextFiber = nextFiber.return;
         }
       }
-      fiber = nextFiber;
     }
   }
+  return shouldUpdate;
+}
 
-  function updateContextProvider(
-    current,
-    workInProgress,
-    renderExpirationTime
+function popToNextHostParent(fiber) {
+  var parent = fiber.return;
+  while (
+    parent !== null &&
+    parent.tag !== HostComponent &&
+    parent.tag !== HostRoot
   ) {
-    var providerType = workInProgress.type;
-    var context = providerType._context;
+    parent = parent.return;
+  }
+  hydrationParentFiber = parent;
+}
+
+function popHydrationState(fiber) {
+  if (!supportsHydration) {
+    return false;
+  }
+  if (fiber !== hydrationParentFiber) {
+    // We're deeper than the current hydration context, inside an inserted
+    // tree.
+    return false;
+  }
+  if (!isHydrating) {
+    // If we're not currently hydrating but we're in a hydration context, then
+    // we were an insertion and now need to pop up reenter hydration of our
+    // siblings.
+    popToNextHostParent(fiber);
+    isHydrating = true;
+    return false;
+  }
 
-    var newProps = workInProgress.pendingProps;
-    var oldProps = workInProgress.memoizedProps;
-    var canBailOnProps = true;
+  var type = fiber.type;
 
-    if (hasLegacyContextChanged()) {
-      canBailOnProps = false;
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (oldProps === newProps) {
-      workInProgress.stateNode = 0;
-      pushProvider(workInProgress);
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  // If we have any remaining hydratable nodes, we need to delete them now.
+  // We only do this deeper than head and body since they tend to have random
+  // other nodes in them. We also ignore components with pure text content in
+  // side of them.
+  // TODO: Better heuristic.
+  if (
+    fiber.tag !== HostComponent ||
+    (type !== "head" &&
+      type !== "body" &&
+      !shouldSetTextContent(type, fiber.memoizedProps))
+  ) {
+    var nextInstance = nextHydratableInstance;
+    while (nextInstance) {
+      deleteHydratableInstance(fiber, nextInstance);
+      nextInstance = getNextHydratableSibling(nextInstance);
     }
+  }
 
-    var newValue = newProps.value;
-    workInProgress.memoizedProps = newProps;
+  popToNextHostParent(fiber);
+  nextHydratableInstance = hydrationParentFiber
+    ? getNextHydratableSibling(fiber.stateNode)
+    : null;
+  return true;
+}
 
-    {
-      var providerPropTypes = workInProgress.type.propTypes;
+function resetHydrationState() {
+  if (!supportsHydration) {
+    return;
+  }
 
-      if (providerPropTypes) {
-        checkPropTypes(
-          providerPropTypes,
-          newProps,
-          "prop",
-          "Context.Provider",
-          getCurrentFiberStackAddendum
-        );
-      }
-    }
+  hydrationParentFiber = null;
+  nextHydratableInstance = null;
+  isHydrating = false;
+}
 
-    var changedBits = void 0;
-    if (oldProps === null) {
-      // Initial render
-      changedBits = MAX_SIGNED_31_BIT_INT;
-    } else {
-      if (oldProps.value === newProps.value) {
-        // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children && canBailOnProps) {
-          workInProgress.stateNode = 0;
-          pushProvider(workInProgress);
-          return bailoutOnAlreadyFinishedWork(current, workInProgress);
-        }
-        changedBits = 0;
-      } else {
-        var oldValue = oldProps.value;
-        // Use Object.is to compare the new context value to the old value.
-        // Inlined Object.is polyfill.
-        // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
-        if (
-          (oldValue === newValue &&
-            (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
-          (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
-        ) {
-          // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children && canBailOnProps) {
-            workInProgress.stateNode = 0;
-            pushProvider(workInProgress);
-            return bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
-          changedBits = 0;
-        } else {
-          changedBits =
-            typeof context._calculateChangedBits === "function"
-              ? context._calculateChangedBits(oldValue, newValue)
-              : MAX_SIGNED_31_BIT_INT;
-          {
-            !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
-              ? warning(
-                  false,
-                  "calculateChangedBits: Expected the return value to be a " +
-                    "31-bit integer. Instead received: %s",
-                  changedBits
-                )
-              : void 0;
-          }
-          changedBits |= 0;
-
-          if (changedBits === 0) {
-            // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children && canBailOnProps) {
-              workInProgress.stateNode = 0;
-              pushProvider(workInProgress);
-              return bailoutOnAlreadyFinishedWork(current, workInProgress);
-            }
-          } else {
-            propagateContextChange(
-              workInProgress,
-              context,
-              changedBits,
-              renderExpirationTime
-            );
-          }
-        }
-      }
-    }
+var getCurrentFiberStackAddendum$1 =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
 
-    workInProgress.stateNode = changedBits;
-    pushProvider(workInProgress);
+var didWarnAboutBadClass = void 0;
+var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
+var didWarnAboutStatelessRefs = void 0;
 
-    var newChildren = newProps.children;
-    reconcileChildren(current, workInProgress, newChildren);
-    return workInProgress.child;
-  }
+{
+  didWarnAboutBadClass = {};
+  didWarnAboutGetDerivedStateOnFunctionalComponent = {};
+  didWarnAboutStatelessRefs = {};
+}
 
-  function updateContextConsumer(
+// TODO: Remove this and use reconcileChildrenAtExpirationTime directly.
+function reconcileChildren(current, workInProgress, nextChildren) {
+  reconcileChildrenAtExpirationTime(
     current,
     workInProgress,
-    renderExpirationTime
-  ) {
-    var context = workInProgress.type;
-    var newProps = workInProgress.pendingProps;
-    var oldProps = workInProgress.memoizedProps;
-
-    var newValue = getContextCurrentValue(context);
-    var changedBits = getContextChangedBits(context);
+    nextChildren,
+    workInProgress.expirationTime
+  );
+}
 
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (changedBits === 0 && oldProps === newProps) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    workInProgress.memoizedProps = newProps;
+function reconcileChildrenAtExpirationTime(
+  current,
+  workInProgress,
+  nextChildren,
+  renderExpirationTime
+) {
+  if (current === null) {
+    // If this is a fresh new component that hasn't been rendered yet, we
+    // won't update its child set by applying minimal side-effects. Instead,
+    // we will add them all to the child before it gets rendered. That means
+    // we can optimize this reconciliation pass by not tracking side-effects.
+    workInProgress.child = mountChildFibers(
+      workInProgress,
+      null,
+      nextChildren,
+      renderExpirationTime
+    );
+  } else {
+    // If the current child is the same as the work in progress, it means that
+    // we haven't yet started any work on these children. Therefore, we use
+    // the clone algorithm to create a copy of all the current children.
 
-    var observedBits = newProps.unstable_observedBits;
-    if (observedBits === undefined || observedBits === null) {
-      // Subscribe to all changes by default
-      observedBits = MAX_SIGNED_31_BIT_INT;
-    }
-    // Store the observedBits on the fiber's stateNode for quick access.
-    workInProgress.stateNode = observedBits;
+    // If we had any progressed work already, that is invalid at this point so
+    // let's throw it out.
+    workInProgress.child = reconcileChildFibers(
+      workInProgress,
+      current.child,
+      nextChildren,
+      renderExpirationTime
+    );
+  }
+}
 
-    if ((changedBits & observedBits) !== 0) {
-      // Context change propagation stops at matching consumers, for time-
-      // slicing. Continue the propagation here.
-      propagateContextChange(
-        workInProgress,
-        context,
-        changedBits,
-        renderExpirationTime
-      );
-    } else if (oldProps === newProps) {
-      // Skip over a memoized parent with a bitmask bailout even
-      // if we began working on it because of a deeper matching child.
+function updateForwardRef(current, workInProgress) {
+  var render = workInProgress.type.render;
+  var nextProps = workInProgress.pendingProps;
+  var ref = workInProgress.ref;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (workInProgress.memoizedProps === nextProps) {
+    var currentRef = current !== null ? current.ref : null;
+    if (ref === currentRef) {
       return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
-    // There is no bailout on `children` equality because we expect people
-    // to often pass a bound method as a child, but it may reference
-    // `this.state` or `this.props` (and thus needs to re-render on `setState`).
-
-    var render = newProps.children;
+  }
 
-    {
-      !(typeof render === "function")
-        ? warning(
-            false,
-            "A context consumer was rendered with multiple children, or a child " +
-              "that isn't a function. A context consumer expects a single child " +
-              "that is a function. If you did pass a function, make sure there " +
-              "is no trailing or leading whitespace around it."
-          )
-        : void 0;
-    }
+  var nextChildren = void 0;
+  {
+    ReactCurrentOwner.current = workInProgress;
+    ReactDebugCurrentFiber.setCurrentPhase("render");
+    nextChildren = render(nextProps, ref);
+    ReactDebugCurrentFiber.setCurrentPhase(null);
+  }
 
-    var newChildren = void 0;
-    {
-      ReactCurrentOwner.current = workInProgress;
-      ReactDebugCurrentFiber.setCurrentPhase("render");
-      newChildren = render(newValue);
-      ReactDebugCurrentFiber.setCurrentPhase(null);
-    }
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextProps);
+  return workInProgress.child;
+}
 
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    reconcileChildren(current, workInProgress, newChildren);
-    return workInProgress.child;
+function updateFragment(current, workInProgress) {
+  var nextChildren = workInProgress.pendingProps;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (workInProgress.memoizedProps === nextChildren) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextChildren);
+  return workInProgress.child;
+}
 
-  /*
-  function reuseChildrenEffects(returnFiber : Fiber, firstChild : Fiber) {
-    let child = firstChild;
-    do {
-      // Ensure that the first and last effect of the parent corresponds
-      // to the children's first and last effect.
-      if (!returnFiber.firstEffect) {
-        returnFiber.firstEffect = child.firstEffect;
-      }
-      if (child.lastEffect) {
-        if (returnFiber.lastEffect) {
-          returnFiber.lastEffect.nextEffect = child.firstEffect;
-        }
-        returnFiber.lastEffect = child.lastEffect;
-      }
-    } while (child = child.sibling);
+function updateMode(current, workInProgress) {
+  var nextChildren = workInProgress.pendingProps.children;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (
+    nextChildren === null ||
+    workInProgress.memoizedProps === nextChildren
+  ) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
-  */
-
-  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
-    cancelWorkTimer(workInProgress);
-
-    if (enableProfilerTimer) {
-      // Don't update "base" render times for bailouts.
-      stopBaseRenderTimerIfRunning();
-    }
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextChildren);
+  return workInProgress.child;
+}
 
-    // TODO: We should ideally be able to bail out early if the children have no
-    // more work to do. However, since we don't have a separation of this
-    // Fiber's priority and its children yet - we don't know without doing lots
-    // of the same work we do anyway. Once we have that separation we can just
-    // bail out here if the children has no more work at this priority level.
-    // if (workInProgress.priorityOfChildren <= priorityLevel) {
-    //   // If there are side-effects in these children that have not yet been
-    //   // committed we need to ensure that they get properly transferred up.
-    //   if (current && current.child !== workInProgress.child) {
-    //     reuseChildrenEffects(workInProgress, child);
-    //   }
-    //   return null;
-    // }
-
-    cloneChildFibers(current, workInProgress);
-    return workInProgress.child;
+function updateProfiler(current, workInProgress) {
+  var nextProps = workInProgress.pendingProps;
+  if (enableProfilerTimer) {
+    workInProgress.effectTag |= Update;
+  }
+  if (workInProgress.memoizedProps === nextProps) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
+  var nextChildren = nextProps.children;
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextProps);
+  return workInProgress.child;
+}
 
-  function bailoutOnLowPriority(current, workInProgress) {
-    cancelWorkTimer(workInProgress);
+function markRef(current, workInProgress) {
+  var ref = workInProgress.ref;
+  if (
+    (current === null && ref !== null) ||
+    (current !== null && current.ref !== ref)
+  ) {
+    // Schedule a Ref effect
+    workInProgress.effectTag |= Ref;
+  }
+}
 
-    if (enableProfilerTimer) {
-      // Don't update "base" render times for bailouts.
-      stopBaseRenderTimerIfRunning();
-    }
+function updateFunctionalComponent(current, workInProgress) {
+  var fn = workInProgress.type;
+  var nextProps = workInProgress.pendingProps;
 
-    // TODO: Handle HostComponent tags here as well and call pushHostContext()?
-    // See PR 8590 discussion for context
-    switch (workInProgress.tag) {
-      case HostRoot:
-        pushHostRootContext(workInProgress);
-        break;
-      case ClassComponent:
-        pushLegacyContextProvider(workInProgress);
-        break;
-      case HostPortal:
-        pushHostContainer(
-          workInProgress,
-          workInProgress.stateNode.containerInfo
-        );
-        break;
-      case ContextProvider:
-        pushProvider(workInProgress);
-        break;
-      case Profiler:
-        if (enableProfilerTimer) {
-          markActualRenderTimeStarted(workInProgress);
-        }
-        break;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else {
+    if (workInProgress.memoizedProps === nextProps) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
-    // TODO: What if this is currently in progress?
-    // How can that happen? How is this not being cloned?
-    return null;
+    // TODO: consider bringing fn.shouldComponentUpdate() back.
+    // It used to be here.
   }
 
-  // TODO: Delete memoizeProps/State and move to reconcile/bailout instead
-  function memoizeProps(workInProgress, nextProps) {
-    workInProgress.memoizedProps = nextProps;
-  }
+  var unmaskedContext = getUnmaskedContext(workInProgress);
+  var context = getMaskedContext(workInProgress, unmaskedContext);
 
-  function memoizeState(workInProgress, nextState) {
-    workInProgress.memoizedState = nextState;
-    // Don't reset the updateQueue, in case there are pending updates. Resetting
-    // is handled by processUpdateQueue.
-  }
+  var nextChildren = void 0;
 
-  function beginWork(current, workInProgress, renderExpirationTime) {
-    if (
-      workInProgress.expirationTime === NoWork ||
-      workInProgress.expirationTime > renderExpirationTime
-    ) {
-      return bailoutOnLowPriority(current, workInProgress);
-    }
+  {
+    ReactCurrentOwner.current = workInProgress;
+    ReactDebugCurrentFiber.setCurrentPhase("render");
+    nextChildren = fn(nextProps, context);
+    ReactDebugCurrentFiber.setCurrentPhase(null);
+  }
+  // React DevTools reads this flag.
+  workInProgress.effectTag |= PerformedWork;
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextProps);
+  return workInProgress.child;
+}
+
+function updateClassComponent(current, workInProgress, renderExpirationTime) {
+  // Push context providers early to prevent context stack mismatches.
+  // During mounting we don't know the child context yet as the instance doesn't exist.
+  // We will invalidate the child context in finishClassComponent() right after rendering.
+  var hasContext = pushContextProvider(workInProgress);
+  var shouldUpdate = void 0;
+  if (current === null) {
+    if (workInProgress.stateNode === null) {
+      // In the initial pass we might need to construct the instance.
+      constructClassInstance(
+        workInProgress,
+        workInProgress.pendingProps,
+        renderExpirationTime
+      );
+      mountClassInstance(workInProgress, renderExpirationTime);
 
-    switch (workInProgress.tag) {
-      case IndeterminateComponent:
-        return mountIndeterminateComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case FunctionalComponent:
-        return updateFunctionalComponent(current, workInProgress);
-      case ClassComponent:
-        return updateClassComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostRoot:
-        return updateHostRoot(current, workInProgress, renderExpirationTime);
-      case HostComponent:
-        return updateHostComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostText:
-        return updateHostText(current, workInProgress);
-      case TimeoutComponent:
-        return updateTimeoutComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostPortal:
-        return updatePortalComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ForwardRef:
-        return updateForwardRef(current, workInProgress);
-      case Fragment:
-        return updateFragment(current, workInProgress);
-      case Mode:
-        return updateMode(current, workInProgress);
-      case Profiler:
-        return updateProfiler(current, workInProgress);
-      case ContextProvider:
-        return updateContextProvider(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ContextConsumer:
-        return updateContextConsumer(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      default:
-        invariant(
-          false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
-        );
+      shouldUpdate = true;
+    } else {
+      // In a resume, we'll already have an instance we can reuse.
+      shouldUpdate = resumeMountClassInstance(
+        workInProgress,
+        renderExpirationTime
+      );
     }
+  } else {
+    shouldUpdate = updateClassInstance(
+      current,
+      workInProgress,
+      renderExpirationTime
+    );
   }
+  return finishClassComponent(
+    current,
+    workInProgress,
+    shouldUpdate,
+    hasContext,
+    renderExpirationTime
+  );
+}
 
-  return {
-    beginWork: beginWork
-  };
-};
-
-var ReactFiberCompleteWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  profilerTimer
+function finishClassComponent(
+  current,
+  workInProgress,
+  shouldUpdate,
+  hasContext,
+  renderExpirationTime
 ) {
-  var createInstance = config.createInstance,
-    createTextInstance = config.createTextInstance,
-    appendInitialChild = config.appendInitialChild,
-    finalizeInitialChildren = config.finalizeInitialChildren,
-    prepareUpdate = config.prepareUpdate,
-    mutation = config.mutation,
-    persistence = config.persistence;
-  var getRootHostContainer = hostContext.getRootHostContainer,
-    popHostContext = hostContext.popHostContext,
-    getHostContext = hostContext.getHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var recordElapsedActualRenderTime =
-    profilerTimer.recordElapsedActualRenderTime;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-  var prepareToHydrateHostInstance =
-      hydrationContext.prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance =
-      hydrationContext.prepareToHydrateHostTextInstance,
-    popHydrationState = hydrationContext.popHydrationState;
-
-  function markUpdate(workInProgress) {
-    // Tag the fiber with an update effect. This turns a Placement into
-    // a PlacementAndUpdate.
-    workInProgress.effectTag |= Update;
-  }
+  // Refs should update even if shouldComponentUpdate returns false
+  markRef(current, workInProgress);
 
-  function markRef(workInProgress) {
-    workInProgress.effectTag |= Ref;
-  }
+  var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
 
-  function appendAllChildren(parent, workInProgress) {
-    // We only have the top Fiber that was created but we need recurse down its
-    // children to find all the terminal nodes.
-    var node = workInProgress.child;
-    while (node !== null) {
-      if (node.tag === HostComponent || node.tag === HostText) {
-        appendInitialChild(parent, node.stateNode);
-      } else if (node.tag === HostPortal) {
-        // If we have a portal child, then we don't want to traverse
-        // down its children. Instead, we'll get insertions from each child in
-        // the portal directly.
-      } else if (node.child !== null) {
-        node.child.return = node;
-        node = node.child;
-        continue;
-      }
-      if (node === workInProgress) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === workInProgress) {
-          return;
-        }
-        node = node.return;
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
+  if (!shouldUpdate && !didCaptureError) {
+    // Context providers should defer to sCU for rendering
+    if (hasContext) {
+      invalidateContextProvider(workInProgress, false);
     }
+
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
 
-  var updateHostContainer = void 0;
-  var updateHostComponent = void 0;
-  var updateHostText = void 0;
-  if (mutation) {
-    if (enableMutatingReconciler) {
-      // Mutation mode
-      updateHostContainer = function(workInProgress) {
-        // Noop
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // TODO: Type this specific to this type of component.
-        workInProgress.updateQueue = updatePayload;
-        // If the update payload indicates that there is a change or if there
-        // is a new ref we mark this as an update. All the work is done in commitWork.
-        if (updatePayload) {
-          markUpdate(workInProgress);
-        }
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        // If the text differs, mark it as an update. All the work in done in commitWork.
-        if (oldText !== newText) {
-          markUpdate(workInProgress);
-        }
-      };
-    } else {
-      invariant(false, "Mutating reconciler is disabled.");
-    }
-  } else if (persistence) {
-    if (enablePersistentReconciler) {
-      // Persistent host tree mode
-      var cloneInstance = persistence.cloneInstance,
-        createContainerChildSet = persistence.createContainerChildSet,
-        appendChildToContainerChildSet =
-          persistence.appendChildToContainerChildSet,
-        finalizeContainerChildren = persistence.finalizeContainerChildren;
+  var ctor = workInProgress.type;
+  var instance = workInProgress.stateNode;
 
-      // An unfortunate fork of appendAllChildren because we have two different parent types.
+  // Rerender
+  ReactCurrentOwner.current = workInProgress;
+  var nextChildren = void 0;
+  if (
+    didCaptureError &&
+    (!enableGetDerivedStateFromCatch ||
+      typeof ctor.getDerivedStateFromCatch !== "function")
+  ) {
+    // If we captured an error, but getDerivedStateFrom catch is not defined,
+    // unmount all the children. componentDidCatch will schedule an update to
+    // re-render a fallback. This is temporary until we migrate everyone to
+    // the new API.
+    // TODO: Warn in a future release.
+    nextChildren = null;
 
-      var appendAllChildrenToContainer = function(
-        containerChildSet,
-        workInProgress
-      ) {
-        // We only have the top Fiber that was created but we need recurse down its
-        // children to find all the terminal nodes.
-        var node = workInProgress.child;
-        while (node !== null) {
-          if (node.tag === HostComponent || node.tag === HostText) {
-            appendChildToContainerChildSet(containerChildSet, node.stateNode);
-          } else if (node.tag === HostPortal) {
-            // If we have a portal child, then we don't want to traverse
-            // down its children. Instead, we'll get insertions from each child in
-            // the portal directly.
-          } else if (node.child !== null) {
-            node.child.return = node;
-            node = node.child;
-            continue;
-          }
-          if (node === workInProgress) {
-            return;
-          }
-          while (node.sibling === null) {
-            if (node.return === null || node.return === workInProgress) {
-              return;
-            }
-            node = node.return;
-          }
-          node.sibling.return = node.return;
-          node = node.sibling;
-        }
-      };
-      updateHostContainer = function(workInProgress) {
-        var portalOrRoot = workInProgress.stateNode;
-        var childrenUnchanged = workInProgress.firstEffect === null;
-        if (childrenUnchanged) {
-          // No changes, just reuse the existing instance.
-        } else {
-          var container = portalOrRoot.containerInfo;
-          var newChildSet = createContainerChildSet(container);
-          // If children might have changed, we have to add them all to the set.
-          appendAllChildrenToContainer(newChildSet, workInProgress);
-          portalOrRoot.pendingChildren = newChildSet;
-          // Schedule an update on the container to swap out the container.
-          markUpdate(workInProgress);
-          finalizeContainerChildren(container, newChildSet);
-        }
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // If there are no effects associated with this node, then none of our children had any updates.
-        // This guarantees that we can reuse all of them.
-        var childrenUnchanged = workInProgress.firstEffect === null;
-        var currentInstance = current.stateNode;
-        if (childrenUnchanged && updatePayload === null) {
-          // No changes, just reuse the existing instance.
-          // Note that this might release a previous clone.
-          workInProgress.stateNode = currentInstance;
-        } else {
-          var recyclableInstance = workInProgress.stateNode;
-          var newInstance = cloneInstance(
-            currentInstance,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            workInProgress,
-            childrenUnchanged,
-            recyclableInstance
-          );
-          if (
-            finalizeInitialChildren(
-              newInstance,
-              type,
-              newProps,
-              rootContainerInstance,
-              currentHostContext
-            )
-          ) {
-            markUpdate(workInProgress);
-          }
-          workInProgress.stateNode = newInstance;
-          if (childrenUnchanged) {
-            // If there are no other effects in this tree, we need to flag this node as having one.
-            // Even though we're not going to use it for anything.
-            // Otherwise parents won't know that there are new children to propagate upwards.
-            markUpdate(workInProgress);
-          } else {
-            // If children might have changed, we have to add them all to the set.
-            appendAllChildren(newInstance, workInProgress);
-          }
-        }
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        if (oldText !== newText) {
-          // If the text content differs, we'll create a new text instance for it.
-          var rootContainerInstance = getRootHostContainer();
-          var currentHostContext = getHostContext();
-          workInProgress.stateNode = createTextInstance(
-            newText,
-            rootContainerInstance,
-            currentHostContext,
-            workInProgress
-          );
-          // We'll have to mark it as having an effect, even though we won't use the effect for anything.
-          // This lets the parents know that at least one of their children has changed.
-          markUpdate(workInProgress);
-        }
-      };
-    } else {
-      invariant(false, "Persistent reconciler is disabled.");
+    if (enableProfilerTimer) {
+      stopBaseRenderTimerIfRunning();
     }
   } else {
-    if (enableNoopReconciler) {
-      // No host operations
-      updateHostContainer = function(workInProgress) {
-        // Noop
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
+    {
+      ReactDebugCurrentFiber.setCurrentPhase("render");
+      nextChildren = instance.render();
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
       ) {
-        // Noop
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        // Noop
-      };
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
+        instance.render();
+      }
+      ReactDebugCurrentFiber.setCurrentPhase(null);
     }
   }
 
-  function completeWork(current, workInProgress, renderExpirationTime) {
-    var newProps = workInProgress.pendingProps;
-    switch (workInProgress.tag) {
-      case FunctionalComponent:
-        return null;
-      case ClassComponent: {
-        // We are leaving this subtree, so pop context if any.
-        popLegacyContextProvider(workInProgress);
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var fiberRoot = workInProgress.stateNode;
-        if (fiberRoot.pendingContext) {
-          fiberRoot.context = fiberRoot.pendingContext;
-          fiberRoot.pendingContext = null;
-        }
-        if (current === null || current.child === null) {
-          // If we hydrated, pop so that we can delete any remaining children
-          // that weren't hydrated.
-          popHydrationState(workInProgress);
-          // This resets the hacky state to fix isMounted before committing.
-          // TODO: Delete this when we delete isMounted and findDOMNode.
-          workInProgress.effectTag &= ~Placement;
-        }
-        updateHostContainer(workInProgress);
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        var rootContainerInstance = getRootHostContainer();
-        var type = workInProgress.type;
-        if (current !== null && workInProgress.stateNode != null) {
-          // If we have an alternate, that means this is an update and we need to
-          // schedule a side-effect to do the updates.
-          var oldProps = current.memoizedProps;
-          // If we get updated because one of our children updated, we don't
-          // have newProps so we'll have to reuse them.
-          // TODO: Split the update API as separate for the props vs. children.
-          // Even better would be if children weren't special cased at all tho.
-          var instance = workInProgress.stateNode;
-          var currentHostContext = getHostContext();
-          // TODO: Experiencing an error where oldProps is null. Suggests a host
-          // component is hitting the resume path. Figure out why. Possibly
-          // related to `hidden`.
-          var updatePayload = prepareUpdate(
-            instance,
-            type,
-            oldProps,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          );
+  // React DevTools reads this flag.
+  workInProgress.effectTag |= PerformedWork;
+  if (didCaptureError) {
+    // If we're recovering from an error, reconcile twice: first to delete
+    // all the existing children.
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      null,
+      renderExpirationTime
+    );
+    workInProgress.child = null;
+    // Now we can continue reconciling like normal. This has the effect of
+    // remounting all children regardless of whether their their
+    // identity matches.
+  }
+  reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    renderExpirationTime
+  );
+  // Memoize props and state using the values we just used to render.
+  // TODO: Restructure so we never read values from the instance.
+  memoizeState(workInProgress, instance.state);
+  memoizeProps(workInProgress, instance.props);
 
-          updateHostComponent(
-            current,
-            workInProgress,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          );
+  // The context might have changed so we need to recalculate it.
+  if (hasContext) {
+    invalidateContextProvider(workInProgress, true);
+  }
 
-          if (current.ref !== workInProgress.ref) {
-            markRef(workInProgress);
-          }
-        } else {
-          if (!newProps) {
-            invariant(
-              workInProgress.stateNode !== null,
-              "We must have new props for new mounts. This error is likely " +
-                "caused by a bug in React. Please file an issue."
-            );
-            // This can happen when we abort work.
-            return null;
-          }
+  return workInProgress.child;
+}
 
-          var _currentHostContext = getHostContext();
-          // TODO: Move createInstance to beginWork and keep it on a context
-          // "stack" as the parent. Then append children as we go in beginWork
-          // or completeWork depending on we want to add then top->down or
-          // bottom->up. Top->down is faster in IE11.
-          var wasHydrated = popHydrationState(workInProgress);
-          if (wasHydrated) {
-            // TODO: Move this and createInstance step into the beginPhase
-            // to consolidate.
-            if (
-              prepareToHydrateHostInstance(
-                workInProgress,
-                rootContainerInstance,
-                _currentHostContext
-              )
-            ) {
-              // If changes to the hydrated node needs to be applied at the
-              // commit-phase we mark this as such.
-              markUpdate(workInProgress);
-            }
-          } else {
-            var _instance = createInstance(
-              type,
-              newProps,
-              rootContainerInstance,
-              _currentHostContext,
-              workInProgress
-            );
+function pushHostRootContext(workInProgress) {
+  var root = workInProgress.stateNode;
+  if (root.pendingContext) {
+    pushTopLevelContextObject(
+      workInProgress,
+      root.pendingContext,
+      root.pendingContext !== root.context
+    );
+  } else if (root.context) {
+    // Should always be set
+    pushTopLevelContextObject(workInProgress, root.context, false);
+  }
+  pushHostContainer(workInProgress, root.containerInfo);
+}
 
-            appendAllChildren(_instance, workInProgress);
+function updateHostRoot(current, workInProgress, renderExpirationTime) {
+  pushHostRootContext(workInProgress);
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null) {
+    var nextProps = workInProgress.pendingProps;
+    var prevState = workInProgress.memoizedState;
+    var prevChildren = prevState !== null ? prevState.element : null;
+    processUpdateQueue(
+      workInProgress,
+      updateQueue,
+      nextProps,
+      null,
+      renderExpirationTime
+    );
+    var nextState = workInProgress.memoizedState;
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    var nextChildren = nextState.element;
 
-            // Certain renderers require commit-time effects for initial mount.
-            // (eg DOM renderer supports auto-focus for certain elements).
-            // Make sure such renderers get scheduled for later work.
-            if (
-              finalizeInitialChildren(
-                _instance,
-                type,
-                newProps,
-                rootContainerInstance,
-                _currentHostContext
-              )
-            ) {
-              markUpdate(workInProgress);
-            }
-            workInProgress.stateNode = _instance;
-          }
+    if (nextChildren === prevChildren) {
+      // If the state is the same as before, that's a bailout because we had
+      // no work that expires at this time.
+      resetHydrationState();
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    var root = workInProgress.stateNode;
+    if (
+      (current === null || current.child === null) &&
+      root.hydrate &&
+      enterHydrationState(workInProgress)
+    ) {
+      // If we don't have any current children this might be the first pass.
+      // We always try to hydrate. If this isn't a hydration pass there won't
+      // be any children to hydrate which is effectively the same thing as
+      // not hydrating.
+
+      // This is a bit of a hack. We track the host root as a placement to
+      // know that we're currently in a mounting state. That way isMounted
+      // works as expected. We must reset this before committing.
+      // TODO: Delete this when we delete isMounted and findDOMNode.
+      workInProgress.effectTag |= Placement;
+
+      // Ensure that children mount into this root without tracking
+      // side-effects. This ensures that we don't store Placement effects on
+      // nodes that will be hydrated.
+      workInProgress.child = mountChildFibers(
+        workInProgress,
+        null,
+        nextChildren,
+        renderExpirationTime
+      );
+    } else {
+      // Otherwise reset hydration state in case we aborted and resumed another
+      // root.
+      resetHydrationState();
+      reconcileChildren(current, workInProgress, nextChildren);
+    }
+    return workInProgress.child;
+  }
+  resetHydrationState();
+  // If there is no update queue, that's a bailout because the root has no props.
+  return bailoutOnAlreadyFinishedWork(current, workInProgress);
+}
 
-          if (workInProgress.ref !== null) {
-            // If there is a ref on a host node we need to schedule a callback
-            markRef(workInProgress);
-          }
-        }
-        return null;
-      }
-      case HostText: {
-        var newText = newProps;
-        if (current && workInProgress.stateNode != null) {
-          var oldText = current.memoizedProps;
-          // If we have an alternate, that means this is an update and we need
-          // to schedule a side-effect to do the updates.
-          updateHostText(current, workInProgress, oldText, newText);
-        } else {
-          if (typeof newText !== "string") {
-            invariant(
-              workInProgress.stateNode !== null,
-              "We must have new props for new mounts. This error is likely " +
-                "caused by a bug in React. Please file an issue."
-            );
-            // This can happen when we abort work.
-            return null;
-          }
-          var _rootContainerInstance = getRootHostContainer();
-          var _currentHostContext2 = getHostContext();
-          var _wasHydrated = popHydrationState(workInProgress);
-          if (_wasHydrated) {
-            if (prepareToHydrateHostTextInstance(workInProgress)) {
-              markUpdate(workInProgress);
-            }
-          } else {
-            workInProgress.stateNode = createTextInstance(
-              newText,
-              _rootContainerInstance,
-              _currentHostContext2,
-              workInProgress
-            );
-          }
-        }
-        return null;
-      }
-      case ForwardRef:
-        return null;
-      case TimeoutComponent:
-        return null;
-      case Fragment:
-        return null;
-      case Mode:
-        return null;
-      case Profiler:
-        if (enableProfilerTimer) {
-          recordElapsedActualRenderTime(workInProgress);
-        }
-        return null;
-      case HostPortal:
-        popHostContainer(workInProgress);
-        updateHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        // Pop provider fiber
-        popProvider(workInProgress);
-        return null;
-      case ContextConsumer:
-        return null;
-      // Error cases
-      case IndeterminateComponent:
-        invariant(
-          false,
-          "An indeterminate component should have become determinate before " +
-            "completing. This error is likely caused by a bug in React. Please " +
-            "file an issue."
-        );
-      // eslint-disable-next-line no-fallthrough
-      default:
-        invariant(
-          false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
-        );
+function updateHostComponent(current, workInProgress, renderExpirationTime) {
+  pushHostContext(workInProgress);
+
+  if (current === null) {
+    tryToClaimNextHydratableInstance(workInProgress);
+  }
+
+  var type = workInProgress.type;
+  var memoizedProps = workInProgress.memoizedProps;
+  var nextProps = workInProgress.pendingProps;
+  var prevProps = current !== null ? current.memoizedProps : null;
+
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (memoizedProps === nextProps) {
+    var isHidden =
+      workInProgress.mode & AsyncMode &&
+      shouldDeprioritizeSubtree(type, nextProps);
+    if (isHidden) {
+      // Before bailing out, make sure we've deprioritized a hidden component.
+      workInProgress.expirationTime = Never;
+    }
+    if (!isHidden || renderExpirationTime !== Never) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
+    // If we're rendering a hidden node at hidden priority, don't bailout. The
+    // parent is complete, but the children may not be.
+  }
+
+  var nextChildren = nextProps.children;
+  var isDirectTextChild = shouldSetTextContent(type, nextProps);
+
+  if (isDirectTextChild) {
+    // We special case a direct text child of a host node. This is a common
+    // case. We won't handle it as a reified child. We will instead handle
+    // this in the host environment that also have access to this prop. That
+    // avoids allocating another HostText fiber and traversing it.
+    nextChildren = null;
+  } else if (prevProps && shouldSetTextContent(type, prevProps)) {
+    // If we're switching from a direct text child to a normal child, or to
+    // empty, we need to schedule the text content to be reset.
+    workInProgress.effectTag |= ContentReset;
   }
 
-  return {
-    completeWork: completeWork
-  };
-};
+  markRef(current, workInProgress);
 
-function createCapturedValue(value, source) {
-  // If the value is an error, call this function immediately after it is thrown
-  // so the stack is accurate.
-  return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
-  };
+  // Check the host config to see if the children are offscreen/hidden.
+  if (
+    renderExpirationTime !== Never &&
+    workInProgress.mode & AsyncMode &&
+    shouldDeprioritizeSubtree(type, nextProps)
+  ) {
+    // Down-prioritize the children.
+    workInProgress.expirationTime = Never;
+    // Bailout and come back to this fiber later.
+    workInProgress.memoizedProps = nextProps;
+    return null;
+  }
+
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextProps);
+  return workInProgress.child;
 }
 
-// Module provided by RN:
-/**
- * Intercept lifecycle errors and ensure they are shown with the correct stack
- * trace within the native redbox component.
- */
-function showErrorDialog(capturedError) {
-  var componentStack = capturedError.componentStack,
-    error = capturedError.error;
+function updateHostText(current, workInProgress) {
+  if (current === null) {
+    tryToClaimNextHydratableInstance(workInProgress);
+  }
+  var nextProps = workInProgress.pendingProps;
+  memoizeProps(workInProgress, nextProps);
+  // Nothing to do here. This is terminal. We'll do the completion step
+  // immediately after.
+  return null;
+}
 
-  var errorToHandle = void 0;
+function mountIndeterminateComponent(
+  current,
+  workInProgress,
+  renderExpirationTime
+) {
+  invariant(
+    current === null,
+    "An indeterminate component should never have mounted. This error is " +
+      "likely caused by a bug in React. Please file an issue."
+  );
+  var fn = workInProgress.type;
+  var props = workInProgress.pendingProps;
+  var unmaskedContext = getUnmaskedContext(workInProgress);
+  var context = getMaskedContext(workInProgress, unmaskedContext);
 
-  // Typically Errors are thrown but eg strings or null can be thrown as well.
-  if (error instanceof Error) {
-    var message = error.message,
-      name = error.name;
+  var value = void 0;
 
-    var summary = message ? name + ": " + message : name;
+  {
+    if (fn.prototype && typeof fn.prototype.render === "function") {
+      var componentName = getComponentName(workInProgress) || "Unknown";
 
-    errorToHandle = error;
+      if (!didWarnAboutBadClass[componentName]) {
+        warning(
+          false,
+          "The <%s /> component appears to have a render method, but doesn't extend React.Component. " +
+            "This is likely to cause errors. Change %s to extend React.Component instead.",
+          componentName,
+          componentName
+        );
+        didWarnAboutBadClass[componentName] = true;
+      }
+    }
 
-    try {
-      errorToHandle.message =
-        summary + "\n\nThis error is located at:" + componentStack;
-    } catch (e) {}
-  } else if (typeof error === "string") {
-    errorToHandle = new Error(
-      error + "\n\nThis error is located at:" + componentStack
-    );
-  } else {
-    errorToHandle = new Error("Unspecified error at:" + componentStack);
+    if (workInProgress.mode & StrictMode) {
+      ReactStrictModeWarnings.recordLegacyContextWarning(workInProgress, null);
+    }
+
+    ReactCurrentOwner.current = workInProgress;
+    value = fn(props, context);
   }
+  // React DevTools reads this flag.
+  workInProgress.effectTag |= PerformedWork;
 
-  ExceptionsManager.handleException(errorToHandle, false);
+  if (
+    typeof value === "object" &&
+    value !== null &&
+    typeof value.render === "function" &&
+    value.$$typeof === undefined
+  ) {
+    var Component = workInProgress.type;
 
-  // Return false here to prevent ReactFiberErrorLogger default behavior of
-  // logging error details to console.error. Calls to console.error are
-  // automatically routed to the native redbox controller, which we've already
-  // done above by calling ExceptionsManager.
-  return false;
-}
+    // Proceed under the assumption that this is a class instance
+    workInProgress.tag = ClassComponent;
 
-function logCapturedError(capturedError) {
-  var logError = showErrorDialog(capturedError);
+    workInProgress.memoizedState =
+      value.state !== null && value.state !== undefined ? value.state : null;
 
-  // Allow injected showErrorDialog() to prevent default console.error logging.
-  // This enables renderers like ReactNative to better manage redbox behavior.
-  if (logError === false) {
-    return;
-  }
+    var getDerivedStateFromProps = Component.getDerivedStateFromProps;
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
+        workInProgress,
+        getDerivedStateFromProps,
+        props
+      );
+    }
 
-  var error = capturedError.error;
-  var suppressLogging = error && error.suppressReactErrorLogging;
-  if (suppressLogging) {
-    return;
-  }
+    // Push context providers early to prevent context stack mismatches.
+    // During mounting we don't know the child context yet as the instance doesn't exist.
+    // We will invalidate the child context in finishClassComponent() right after rendering.
+    var hasContext = pushContextProvider(workInProgress);
+    adoptClassInstance(workInProgress, value);
+    mountClassInstance(workInProgress, renderExpirationTime);
+    return finishClassComponent(
+      current,
+      workInProgress,
+      true,
+      hasContext,
+      renderExpirationTime
+    );
+  } else {
+    // Proceed under the assumption that this is a functional component
+    workInProgress.tag = FunctionalComponent;
+    {
+      var _Component = workInProgress.type;
 
-  {
-    var componentName = capturedError.componentName,
-      componentStack = capturedError.componentStack,
-      errorBoundaryName = capturedError.errorBoundaryName,
-      errorBoundaryFound = capturedError.errorBoundaryFound,
-      willRetry = capturedError.willRetry;
+      if (_Component) {
+        !!_Component.childContextTypes
+          ? warning(
+              false,
+              "%s(...): childContextTypes cannot be defined on a functional component.",
+              _Component.displayName || _Component.name || "Component"
+            )
+          : void 0;
+      }
+      if (workInProgress.ref !== null) {
+        var info = "";
+        var ownerName = ReactDebugCurrentFiber.getCurrentFiberOwnerName();
+        if (ownerName) {
+          info += "\n\nCheck the render method of `" + ownerName + "`.";
+        }
 
-    var componentNameMessage = componentName
-      ? "The above error occurred in the <" + componentName + "> component:"
-      : "The above error occurred in one of your React components:";
+        var warningKey = ownerName || workInProgress._debugID || "";
+        var debugSource = workInProgress._debugSource;
+        if (debugSource) {
+          warningKey = debugSource.fileName + ":" + debugSource.lineNumber;
+        }
+        if (!didWarnAboutStatelessRefs[warningKey]) {
+          didWarnAboutStatelessRefs[warningKey] = true;
+          warning(
+            false,
+            "Stateless function components cannot be given refs. " +
+              "Attempts to access this ref will fail.%s%s",
+            info,
+            ReactDebugCurrentFiber.getCurrentFiberStackAddendum()
+          );
+        }
+      }
 
-    var errorBoundaryMessage = void 0;
-    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
-    if (errorBoundaryFound && errorBoundaryName) {
-      if (willRetry) {
-        errorBoundaryMessage =
-          "React will try to recreate this component tree from scratch " +
-          ("using the error boundary you provided, " + errorBoundaryName + ".");
-      } else {
-        errorBoundaryMessage =
-          "This error was initially handled by the error boundary " +
-          errorBoundaryName +
-          ".\n" +
-          "Recreating the tree from scratch failed so React will unmount the tree.";
+      if (typeof fn.getDerivedStateFromProps === "function") {
+        var _componentName = getComponentName(workInProgress) || "Unknown";
+
+        if (!didWarnAboutGetDerivedStateOnFunctionalComponent[_componentName]) {
+          warning(
+            false,
+            "%s: Stateless functional components do not support getDerivedStateFromProps.",
+            _componentName
+          );
+          didWarnAboutGetDerivedStateOnFunctionalComponent[
+            _componentName
+          ] = true;
+        }
       }
-    } else {
-      errorBoundaryMessage =
-        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
-        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
     }
-    var combinedMessage =
-      "" +
-      componentNameMessage +
-      componentStack +
-      "\n\n" +
-      ("" + errorBoundaryMessage);
-
-    // In development, we provide our own message with just the component stack.
-    // We don't include the original error message and JS stack because the browser
-    // has already printed it. Even if the application swallows the error, it is still
-    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
-    console.error(combinedMessage);
+    reconcileChildren(current, workInProgress, value);
+    memoizeProps(workInProgress, props);
+    return workInProgress.child;
   }
 }
 
-var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
-var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
+function updateTimeoutComponent(current, workInProgress, renderExpirationTime) {
+  if (enableSuspense) {
+    var nextProps = workInProgress.pendingProps;
+    var prevProps = workInProgress.memoizedProps;
 
-var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
-{
-  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
-}
+    var prevDidTimeout = workInProgress.memoizedState;
 
-function logError(boundary, errorInfo) {
-  var source = errorInfo.source;
-  var stack = errorInfo.stack;
-  if (stack === null && source !== null) {
-    stack = getStackAddendumByWorkInProgressFiber(source);
+    // Check if we already attempted to render the normal state. If we did,
+    // and we timed out, render the placeholder state.
+    var alreadyCaptured = (workInProgress.effectTag & DidCapture) === NoEffect;
+    var nextDidTimeout = !alreadyCaptured;
+
+    if (hasContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (nextProps === prevProps && nextDidTimeout === prevDidTimeout) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+
+    var render = nextProps.children;
+    var nextChildren = render(nextDidTimeout);
+    workInProgress.memoizedProps = nextProps;
+    workInProgress.memoizedState = nextDidTimeout;
+    reconcileChildren(current, workInProgress, nextChildren);
+    return workInProgress.child;
+  } else {
+    return null;
   }
+}
 
-  var capturedError = {
-    componentName: source !== null ? getComponentName(source) : null,
-    componentStack: stack !== null ? stack : "",
-    error: errorInfo.value,
-    errorBoundary: null,
-    errorBoundaryName: null,
-    errorBoundaryFound: false,
-    willRetry: false
-  };
+function updatePortalComponent(current, workInProgress, renderExpirationTime) {
+  pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
+  var nextChildren = workInProgress.pendingProps;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (workInProgress.memoizedProps === nextChildren) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  }
 
-  if (boundary !== null && boundary.tag === ClassComponent) {
-    capturedError.errorBoundary = boundary.stateNode;
-    capturedError.errorBoundaryName = getComponentName(boundary);
-    capturedError.errorBoundaryFound = true;
-    capturedError.willRetry = true;
+  if (current === null) {
+    // Portals are special because we don't append the children during mount
+    // but at commit. Therefore we need to track insertions which the normal
+    // flow doesn't do during mount. This doesn't happen at the root because
+    // the root always starts with a "current" with a null child.
+    // TODO: Consider unifying this with how the root works.
+    workInProgress.child = reconcileChildFibers(
+      workInProgress,
+      null,
+      nextChildren,
+      renderExpirationTime
+    );
+    memoizeProps(workInProgress, nextChildren);
+  } else {
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
   }
+  return workInProgress.child;
+}
 
-  try {
-    logCapturedError(capturedError);
-  } catch (e) {
-    // Prevent cycle if logCapturedError() throws.
-    // A cycle may still occur if logCapturedError renders a component that throws.
-    var suppressLogging = e && e.suppressReactErrorLogging;
-    if (!suppressLogging) {
-      console.error(e);
+function propagateContextChange(
+  workInProgress,
+  context,
+  changedBits,
+  renderExpirationTime
+) {
+  var fiber = workInProgress.child;
+  if (fiber !== null) {
+    // Set the return pointer of the child to the work-in-progress fiber.
+    fiber.return = workInProgress;
+  }
+  while (fiber !== null) {
+    var nextFiber = void 0;
+    // Visit this fiber.
+    switch (fiber.tag) {
+      case ContextConsumer:
+        // Check if the context matches.
+        var observedBits = fiber.stateNode | 0;
+        if (fiber.type === context && (observedBits & changedBits) !== 0) {
+          // Update the expiration time of all the ancestors, including
+          // the alternates.
+          var node = fiber;
+          while (node !== null) {
+            var alternate = node.alternate;
+            if (
+              node.expirationTime === NoWork ||
+              node.expirationTime > renderExpirationTime
+            ) {
+              node.expirationTime = renderExpirationTime;
+              if (
+                alternate !== null &&
+                (alternate.expirationTime === NoWork ||
+                  alternate.expirationTime > renderExpirationTime)
+              ) {
+                alternate.expirationTime = renderExpirationTime;
+              }
+            } else if (
+              alternate !== null &&
+              (alternate.expirationTime === NoWork ||
+                alternate.expirationTime > renderExpirationTime)
+            ) {
+              alternate.expirationTime = renderExpirationTime;
+            } else {
+              // Neither alternate was updated, which means the rest of the
+              // ancestor path already has sufficient priority.
+              break;
+            }
+            node = node.return;
+          }
+          // Don't scan deeper than a matching consumer. When we render the
+          // consumer, we'll continue scanning from that point. This way the
+          // scanning work is time-sliced.
+          nextFiber = null;
+        } else {
+          // Traverse down.
+          nextFiber = fiber.child;
+        }
+        break;
+      case ContextProvider:
+        // Don't scan deeper if this is a matching provider
+        nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+        break;
+      default:
+        // Traverse down.
+        nextFiber = fiber.child;
+        break;
+    }
+    if (nextFiber !== null) {
+      // Set the return pointer of the child to the work-in-progress fiber.
+      nextFiber.return = fiber;
+    } else {
+      // No child. Traverse to next sibling.
+      nextFiber = fiber;
+      while (nextFiber !== null) {
+        if (nextFiber === workInProgress) {
+          // We're back to the root of this subtree. Exit.
+          nextFiber = null;
+          break;
+        }
+        var sibling = nextFiber.sibling;
+        if (sibling !== null) {
+          // Set the return pointer of the sibling to the work-in-progress fiber.
+          sibling.return = nextFiber.return;
+          nextFiber = sibling;
+          break;
+        }
+        // No more siblings. Traverse up.
+        nextFiber = nextFiber.return;
+      }
     }
+    fiber = nextFiber;
   }
 }
 
-var ReactFiberCommitWork = function(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed,
-  recalculateCurrentTime
-) {
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation,
-    persistence = config.persistence;
-
-  var callComponentWillUnmountWithTimer = function(current, instance) {
-    startPhaseTimer(current, "componentWillUnmount");
-    instance.props = current.memoizedProps;
-    instance.state = current.memoizedState;
-    instance.componentWillUnmount();
-    stopPhaseTimer();
-  };
+function updateContextProvider(current, workInProgress, renderExpirationTime) {
+  var providerType = workInProgress.type;
+  var context = providerType._context;
 
-  // Capture errors so they don't interrupt unmounting.
-  function safelyCallComponentWillUnmount(current, instance) {
-    {
-      invokeGuardedCallback$3(
-        null,
-        callComponentWillUnmountWithTimer,
-        null,
-        current,
-        instance
-      );
-      if (hasCaughtError$1()) {
-        var unmountError = clearCaughtError$1();
-        captureError(current, unmountError);
-      }
-    }
-  }
+  var newProps = workInProgress.pendingProps;
+  var oldProps = workInProgress.memoizedProps;
+  var canBailOnProps = true;
 
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (ref !== null) {
-      if (typeof ref === "function") {
-        {
-          invokeGuardedCallback$3(null, ref, null, null);
-          if (hasCaughtError$1()) {
-            var refError = clearCaughtError$1();
-            captureError(current, refError);
-          }
-        }
-      } else {
-        ref.current = null;
-      }
-    }
+  if (hasContextChanged()) {
+    canBailOnProps = false;
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (oldProps === newProps) {
+    workInProgress.stateNode = 0;
+    pushProvider(workInProgress);
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
 
-  function commitBeforeMutationLifeCycles(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        if (finishedWork.effectTag & Snapshot) {
-          if (current !== null) {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
-            var _instance = finishedWork.stateNode;
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            var snapshot = _instance.getSnapshotBeforeUpdate(
-              prevProps,
-              prevState
-            );
-            {
-              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
-              if (
-                snapshot === undefined &&
-                !didWarnSet.has(finishedWork.type)
-              ) {
-                didWarnSet.add(finishedWork.type);
-                warning(
-                  false,
-                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
-                    "must be returned. You have returned undefined.",
-                  getComponentName(finishedWork)
-                );
-              }
-            }
-            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
-            stopPhaseTimer();
-          }
-        }
-        return;
-      }
-      case HostRoot:
-      case HostComponent:
-      case HostText:
-      case HostPortal:
-        // Nothing to do for these component types
-        return;
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
+  var newValue = newProps.value;
+  workInProgress.memoizedProps = newProps;
+
+  {
+    var providerPropTypes = workInProgress.type.propTypes;
+
+    if (providerPropTypes) {
+      checkPropTypes(
+        providerPropTypes,
+        newProps,
+        "prop",
+        "Context.Provider",
+        getCurrentFiberStackAddendum$1
+      );
     }
   }
 
-  function commitLifeCycles(
-    finishedRoot,
-    current,
-    finishedWork,
-    currentTime,
-    committedExpirationTime
-  ) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        var _instance2 = finishedWork.stateNode;
-        if (finishedWork.effectTag & Update) {
-          if (current === null) {
-            startPhaseTimer(finishedWork, "componentDidMount");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidMount();
-            stopPhaseTimer();
-          } else {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "componentDidUpdate");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidUpdate(
-              prevProps,
-              prevState,
-              _instance2.__reactInternalSnapshotBeforeUpdate
-            );
-            stopPhaseTimer();
-          }
+  var changedBits = void 0;
+  if (oldProps === null) {
+    // Initial render
+    changedBits = MAX_SIGNED_31_BIT_INT;
+  } else {
+    if (oldProps.value === newProps.value) {
+      // No change. Bailout early if children are the same.
+      if (oldProps.children === newProps.children && canBailOnProps) {
+        workInProgress.stateNode = 0;
+        pushProvider(workInProgress);
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+      changedBits = 0;
+    } else {
+      var oldValue = oldProps.value;
+      // Use Object.is to compare the new context value to the old value.
+      // Inlined Object.is polyfill.
+      // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+      if (
+        (oldValue === newValue &&
+          (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
+        (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
+      ) {
+        // No change. Bailout early if children are the same.
+        if (oldProps.children === newProps.children && canBailOnProps) {
+          workInProgress.stateNode = 0;
+          pushProvider(workInProgress);
+          return bailoutOnAlreadyFinishedWork(current, workInProgress);
         }
-        var updateQueue = finishedWork.updateQueue;
-        if (updateQueue !== null) {
-          _instance2.props = finishedWork.memoizedProps;
-          _instance2.state = finishedWork.memoizedState;
-          commitUpdateQueue(
-            finishedWork,
-            updateQueue,
-            _instance2,
-            committedExpirationTime
-          );
+        changedBits = 0;
+      } else {
+        changedBits =
+          typeof context._calculateChangedBits === "function"
+            ? context._calculateChangedBits(oldValue, newValue)
+            : MAX_SIGNED_31_BIT_INT;
+        {
+          !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
+            ? warning(
+                false,
+                "calculateChangedBits: Expected the return value to be a " +
+                  "31-bit integer. Instead received: %s",
+                changedBits
+              )
+            : void 0;
         }
-        return;
-      }
-      case HostRoot: {
-        var _updateQueue = finishedWork.updateQueue;
-        if (_updateQueue !== null) {
-          var _instance3 = null;
-          if (finishedWork.child !== null) {
-            switch (finishedWork.child.tag) {
-              case HostComponent:
-                _instance3 = getPublicInstance(finishedWork.child.stateNode);
-                break;
-              case ClassComponent:
-                _instance3 = finishedWork.child.stateNode;
-                break;
-            }
+        changedBits |= 0;
+
+        if (changedBits === 0) {
+          // No change. Bailout early if children are the same.
+          if (oldProps.children === newProps.children && canBailOnProps) {
+            workInProgress.stateNode = 0;
+            pushProvider(workInProgress);
+            return bailoutOnAlreadyFinishedWork(current, workInProgress);
           }
-          commitUpdateQueue(
-            finishedWork,
-            _updateQueue,
-            _instance3,
-            committedExpirationTime
+        } else {
+          propagateContextChange(
+            workInProgress,
+            context,
+            changedBits,
+            renderExpirationTime
           );
         }
-        return;
-      }
-      case HostComponent: {
-        var _instance4 = finishedWork.stateNode;
-
-        // Renderers may schedule work to be done after host components are mounted
-        // (eg DOM renderer may schedule auto-focus for inputs and form controls).
-        // These effects should only be committed when components are first mounted,
-        // aka when there is no current/alternate.
-        if (current === null && finishedWork.effectTag & Update) {
-          var type = finishedWork.type;
-          var props = finishedWork.memoizedProps;
-          commitMount(_instance4, type, props, finishedWork);
-        }
-
-        return;
-      }
-      case HostText: {
-        // We have no life-cycles associated with text.
-        return;
-      }
-      case HostPortal: {
-        // We have no life-cycles associated with portals.
-        return;
-      }
-      case Profiler: {
-        // We have no life-cycles associated with Profiler.
-        return;
-      }
-      case TimeoutComponent: {
-        // We have no life-cycles associated with Timeouts.
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
       }
     }
   }
 
-  function commitAttachRef(finishedWork) {
-    var ref = finishedWork.ref;
-    if (ref !== null) {
-      var _instance5 = finishedWork.stateNode;
-      var instanceToUse = void 0;
-      switch (finishedWork.tag) {
-        case HostComponent:
-          instanceToUse = getPublicInstance(_instance5);
-          break;
-        default:
-          instanceToUse = _instance5;
-      }
-      if (typeof ref === "function") {
-        ref(instanceToUse);
-      } else {
-        {
-          if (!ref.hasOwnProperty("current")) {
-            warning(
-              false,
-              "Unexpected ref object provided for %s. " +
-                "Use either a ref-setter function or React.createRef().%s",
-              getComponentName(finishedWork),
-              getStackAddendumByWorkInProgressFiber(finishedWork)
-            );
-          }
-        }
+  workInProgress.stateNode = changedBits;
+  pushProvider(workInProgress);
 
-        ref.current = instanceToUse;
-      }
-    }
+  var newChildren = newProps.children;
+  reconcileChildren(current, workInProgress, newChildren);
+  return workInProgress.child;
+}
+
+function updateContextConsumer(current, workInProgress, renderExpirationTime) {
+  var context = workInProgress.type;
+  var newProps = workInProgress.pendingProps;
+  var oldProps = workInProgress.memoizedProps;
+
+  var newValue = getContextCurrentValue(context);
+  var changedBits = getContextChangedBits(context);
+
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (changedBits === 0 && oldProps === newProps) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
+  workInProgress.memoizedProps = newProps;
 
-  function commitDetachRef(current) {
-    var currentRef = current.ref;
-    if (currentRef !== null) {
-      if (typeof currentRef === "function") {
-        currentRef(null);
-      } else {
-        currentRef.current = null;
-      }
-    }
+  var observedBits = newProps.unstable_observedBits;
+  if (observedBits === undefined || observedBits === null) {
+    // Subscribe to all changes by default
+    observedBits = MAX_SIGNED_31_BIT_INT;
   }
+  // Store the observedBits on the fiber's stateNode for quick access.
+  workInProgress.stateNode = observedBits;
 
-  // User-originating errors (lifecycles and refs) should not interrupt
-  // deletion, so don't let them throw. Host-originating errors should
-  // interrupt deletion, so it's okay
-  function commitUnmount(current) {
-    if (typeof onCommitUnmount === "function") {
-      onCommitUnmount(current);
-    }
+  if ((changedBits & observedBits) !== 0) {
+    // Context change propagation stops at matching consumers, for time-
+    // slicing. Continue the propagation here.
+    propagateContextChange(
+      workInProgress,
+      context,
+      changedBits,
+      renderExpirationTime
+    );
+  } else if (oldProps === newProps) {
+    // Skip over a memoized parent with a bitmask bailout even
+    // if we began working on it because of a deeper matching child.
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  }
+  // There is no bailout on `children` equality because we expect people
+  // to often pass a bound method as a child, but it may reference
+  // `this.state` or `this.props` (and thus needs to re-render on `setState`).
 
-    switch (current.tag) {
-      case ClassComponent: {
-        safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if (typeof _instance6.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance6);
-        }
-        return;
-      }
-      case HostComponent: {
-        safelyDetachRef(current);
-        return;
-      }
-      case HostPortal: {
-        // TODO: this is recursive.
-        // We are also not using this parent because
-        // the portal will get pushed immediately.
-        if (enableMutatingReconciler && mutation) {
-          unmountHostComponents(current);
-        } else if (enablePersistentReconciler && persistence) {
-          emptyPortalContainer(current);
-        }
-        return;
-      }
-    }
+  var render = newProps.children;
+
+  {
+    !(typeof render === "function")
+      ? warning(
+          false,
+          "A context consumer was rendered with multiple children, or a child " +
+            "that isn't a function. A context consumer expects a single child " +
+            "that is a function. If you did pass a function, make sure there " +
+            "is no trailing or leading whitespace around it."
+        )
+      : void 0;
   }
 
-  function commitNestedUnmounts(root) {
-    // While we're inside a removed host node we don't want to call
-    // removeChild on the inner nodes because they're removed by the top
-    // call anyway. We also want to call componentWillUnmount on all
-    // composites before this host node is removed from the tree. Therefore
-    var node = root;
-    while (true) {
-      commitUnmount(node);
-      // Visit children because they may contain more composite or host nodes.
-      // Skip portals because commitUnmount() currently visits them recursively.
-      if (
-        node.child !== null &&
-        // If we use mutation we drill down into portals using commitUnmount above.
-        // If we don't use mutation we drill down into portals here instead.
-        (!mutation || node.tag !== HostPortal)
-      ) {
-        node.child.return = node;
-        node = node.child;
-        continue;
-      }
-      if (node === root) {
-        return;
+  var newChildren = void 0;
+  {
+    ReactCurrentOwner.current = workInProgress;
+    ReactDebugCurrentFiber.setCurrentPhase("render");
+    newChildren = render(newValue);
+    ReactDebugCurrentFiber.setCurrentPhase(null);
+  }
+
+  // React DevTools reads this flag.
+  workInProgress.effectTag |= PerformedWork;
+  reconcileChildren(current, workInProgress, newChildren);
+  return workInProgress.child;
+}
+
+/*
+  function reuseChildrenEffects(returnFiber : Fiber, firstChild : Fiber) {
+    let child = firstChild;
+    do {
+      // Ensure that the first and last effect of the parent corresponds
+      // to the children's first and last effect.
+      if (!returnFiber.firstEffect) {
+        returnFiber.firstEffect = child.firstEffect;
       }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === root) {
-          return;
+      if (child.lastEffect) {
+        if (returnFiber.lastEffect) {
+          returnFiber.lastEffect.nextEffect = child.firstEffect;
         }
-        node = node.return;
+        returnFiber.lastEffect = child.lastEffect;
       }
-      node.sibling.return = node.return;
-      node = node.sibling;
-    }
+    } while (child = child.sibling);
   }
+  */
 
-  function detachFiber(current) {
-    // Cut off the return pointers to disconnect it from the tree. Ideally, we
-    // should clear the child pointer of the parent alternate to let this
-    // get GC:ed but we don't know which for sure which parent is the current
-    // one so we'll settle for GC:ing the subtree of this child. This child
-    // itself will be GC:ed when the parent updates the next time.
-    current.return = null;
-    current.child = null;
-    if (current.alternate) {
-      current.alternate.child = null;
-      current.alternate.return = null;
-    }
+function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+  cancelWorkTimer(workInProgress);
+
+  if (enableProfilerTimer) {
+    // Don't update "base" render times for bailouts.
+    stopBaseRenderTimerIfRunning();
   }
 
-  var emptyPortalContainer = void 0;
+  // TODO: We should ideally be able to bail out early if the children have no
+  // more work to do. However, since we don't have a separation of this
+  // Fiber's priority and its children yet - we don't know without doing lots
+  // of the same work we do anyway. Once we have that separation we can just
+  // bail out here if the children has no more work at this priority level.
+  // if (workInProgress.priorityOfChildren <= priorityLevel) {
+  //   // If there are side-effects in these children that have not yet been
+  //   // committed we need to ensure that they get properly transferred up.
+  //   if (current && current.child !== workInProgress.child) {
+  //     reuseChildrenEffects(workInProgress, child);
+  //   }
+  //   return null;
+  // }
 
-  if (!mutation) {
-    var commitContainer = void 0;
-    if (persistence) {
-      var replaceContainerChildren = persistence.replaceContainerChildren,
-        createContainerChildSet = persistence.createContainerChildSet;
+  cloneChildFibers(current, workInProgress);
+  return workInProgress.child;
+}
 
-      emptyPortalContainer = function(current) {
-        var portal = current.stateNode;
-        var containerInfo = portal.containerInfo;
+function bailoutOnLowPriority(current, workInProgress) {
+  cancelWorkTimer(workInProgress);
 
-        var emptyChildSet = createContainerChildSet(containerInfo);
-        replaceContainerChildren(containerInfo, emptyChildSet);
-      };
-      commitContainer = function(finishedWork) {
-        switch (finishedWork.tag) {
-          case ClassComponent: {
-            return;
-          }
-          case HostComponent: {
-            return;
-          }
-          case HostText: {
-            return;
-          }
-          case HostRoot:
-          case HostPortal: {
-            var portalOrRoot = finishedWork.stateNode;
-            var containerInfo = portalOrRoot.containerInfo,
-              _pendingChildren = portalOrRoot.pendingChildren;
+  if (enableProfilerTimer) {
+    // Don't update "base" render times for bailouts.
+    stopBaseRenderTimerIfRunning();
+  }
 
-            replaceContainerChildren(containerInfo, _pendingChildren);
-            return;
-          }
-          default: {
-            invariant(
-              false,
-              "This unit of work tag should not have side-effects. This error is " +
-                "likely caused by a bug in React. Please file an issue."
-            );
-          }
-        }
-      };
-    } else {
-      commitContainer = function(finishedWork) {
-        // Noop
-      };
-    }
-    if (enablePersistentReconciler || enableNoopReconciler) {
-      return {
-        commitResetTextContent: function(finishedWork) {},
-        commitPlacement: function(finishedWork) {},
-        commitDeletion: function(current) {
-          // Detach refs and call componentWillUnmount() on the whole subtree.
-          commitNestedUnmounts(current);
-          detachFiber(current);
-        },
-        commitWork: function(current, finishedWork) {
-          commitContainer(finishedWork);
-        },
-
-        commitLifeCycles: commitLifeCycles,
-        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-        commitAttachRef: commitAttachRef,
-        commitDetachRef: commitDetachRef
-      };
-    } else if (persistence) {
-      invariant(false, "Persistent reconciler is disabled.");
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
+  // TODO: Handle HostComponent tags here as well and call pushHostContext()?
+  // See PR 8590 discussion for context
+  switch (workInProgress.tag) {
+    case HostRoot:
+      pushHostRootContext(workInProgress);
+      break;
+    case ClassComponent:
+      pushContextProvider(workInProgress);
+      break;
+    case HostPortal:
+      pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
+      break;
+    case ContextProvider:
+      pushProvider(workInProgress);
+      break;
+  }
+  // TODO: What if this is currently in progress?
+  // How can that happen? How is this not being cloned?
+  return null;
+}
+
+// TODO: Delete memoizeProps/State and move to reconcile/bailout instead
+function memoizeProps(workInProgress, nextProps) {
+  workInProgress.memoizedProps = nextProps;
+}
+
+function memoizeState(workInProgress, nextState) {
+  workInProgress.memoizedState = nextState;
+  // Don't reset the updateQueue, in case there are pending updates. Resetting
+  // is handled by processUpdateQueue.
+}
+
+function beginWork(current, workInProgress, renderExpirationTime) {
+  if (enableProfilerTimer) {
+    if (workInProgress.mode & ProfileMode) {
+      markActualRenderTimeStarted(workInProgress);
     }
   }
-  var commitMount = mutation.commitMount,
-    commitUpdate = mutation.commitUpdate,
-    resetTextContent = mutation.resetTextContent,
-    commitTextUpdate = mutation.commitTextUpdate,
-    appendChild$$1 = mutation.appendChild,
-    appendChildToContainer = mutation.appendChildToContainer,
-    insertBefore = mutation.insertBefore,
-    insertInContainerBefore = mutation.insertInContainerBefore,
-    removeChild = mutation.removeChild,
-    removeChildFromContainer = mutation.removeChildFromContainer;
 
-  function getHostParentFiber(fiber) {
-    var parent = fiber.return;
-    while (parent !== null) {
-      if (isHostParent(parent)) {
-        return parent;
-      }
-      parent = parent.return;
-    }
-    invariant(
-      false,
-      "Expected to find a host parent. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-  }
+  if (
+    workInProgress.expirationTime === NoWork ||
+    workInProgress.expirationTime > renderExpirationTime
+  ) {
+    return bailoutOnLowPriority(current, workInProgress);
+  }
+
+  switch (workInProgress.tag) {
+    case IndeterminateComponent:
+      return mountIndeterminateComponent(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case FunctionalComponent:
+      return updateFunctionalComponent(current, workInProgress);
+    case ClassComponent:
+      return updateClassComponent(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case HostRoot:
+      return updateHostRoot(current, workInProgress, renderExpirationTime);
+    case HostComponent:
+      return updateHostComponent(current, workInProgress, renderExpirationTime);
+    case HostText:
+      return updateHostText(current, workInProgress);
+    case TimeoutComponent:
+      return updateTimeoutComponent(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case HostPortal:
+      return updatePortalComponent(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case ForwardRef:
+      return updateForwardRef(current, workInProgress);
+    case Fragment:
+      return updateFragment(current, workInProgress);
+    case Mode:
+      return updateMode(current, workInProgress);
+    case Profiler:
+      return updateProfiler(current, workInProgress);
+    case ContextProvider:
+      return updateContextProvider(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case ContextConsumer:
+      return updateContextConsumer(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    default:
+      invariant(
+        false,
+        "Unknown unit of work tag. This error is likely caused by a bug in " +
+          "React. Please file an issue."
+      );
+  }
+}
+
+function markUpdate(workInProgress) {
+  // Tag the fiber with an update effect. This turns a Placement into
+  // a PlacementAndUpdate.
+  workInProgress.effectTag |= Update;
+}
 
-  function isHostParent(fiber) {
-    return (
-      fiber.tag === HostComponent ||
-      fiber.tag === HostRoot ||
-      fiber.tag === HostPortal
-    );
-  }
+function markRef$1(workInProgress) {
+  workInProgress.effectTag |= Ref;
+}
 
-  function getHostSibling(fiber) {
-    // We're going to search forward into the tree until we find a sibling host
-    // node. Unfortunately, if multiple insertions are done in a row we have to
-    // search past them. This leads to exponential search for the next sibling.
-    var node = fiber;
-    siblings: while (true) {
-      // If we didn't find anything, let's try the next sibling.
-      while (node.sibling === null) {
-        if (node.return === null || isHostParent(node.return)) {
-          // If we pop out of the root or hit the parent the fiber we are the
-          // last sibling.
-          return null;
-        }
-        node = node.return;
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
-      while (node.tag !== HostComponent && node.tag !== HostText) {
-        // If it is not host node and, we might have a host node inside it.
-        // Try to search down until we find one.
-        if (node.effectTag & Placement) {
-          // If we don't have a child, try the siblings instead.
-          continue siblings;
-        }
-        // If we don't have a child, try the siblings instead.
-        // We also skip portals because they are not part of this host tree.
-        if (node.child === null || node.tag === HostPortal) {
-          continue siblings;
-        } else {
-          node.child.return = node;
-          node = node.child;
-        }
-      }
-      // Check if this host node is stable or about to be placed.
-      if (!(node.effectTag & Placement)) {
-        // Found it!
-        return node.stateNode;
+function appendAllChildren(parent, workInProgress) {
+  // We only have the top Fiber that was created but we need recurse down its
+  // children to find all the terminal nodes.
+  var node = workInProgress.child;
+  while (node !== null) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      appendInitialChild(parent, node.stateNode);
+    } else if (node.tag === HostPortal) {
+      // If we have a portal child, then we don't want to traverse
+      // down its children. Instead, we'll get insertions from each child in
+      // the portal directly.
+    } else if (node.child !== null) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === workInProgress) {
+      return;
+    }
+    while (node.sibling === null) {
+      if (node.return === null || node.return === workInProgress) {
+        return;
       }
+      node = node.return;
     }
+    node.sibling.return = node.return;
+    node = node.sibling;
   }
+}
 
-  function commitPlacement(finishedWork) {
-    // Recursively insert all host nodes into the parent.
-    var parentFiber = getHostParentFiber(finishedWork);
-    var parent = void 0;
-    var isContainer = void 0;
-    switch (parentFiber.tag) {
-      case HostComponent:
-        parent = parentFiber.stateNode;
-        isContainer = false;
-        break;
-      case HostRoot:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      case HostPortal:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      default:
-        invariant(
-          false,
-          "Invalid host parent fiber. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
+var updateHostContainer = void 0;
+var updateHostComponent$1 = void 0;
+var updateHostText$1 = void 0;
+if (supportsMutation) {
+  // Mutation mode
+
+  updateHostContainer = function(workInProgress) {
+    // Noop
+  };
+  updateHostComponent$1 = function(
+    current,
+    workInProgress,
+    updatePayload,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    currentHostContext
+  ) {
+    // TODO: Type this specific to this type of component.
+    workInProgress.updateQueue = updatePayload;
+    // If the update payload indicates that there is a change or if there
+    // is a new ref we mark this as an update. All the work is done in commitWork.
+    if (updatePayload) {
+      markUpdate(workInProgress);
     }
-    if (parentFiber.effectTag & ContentReset) {
-      // Reset the text content of the parent before doing any insertions
-      resetTextContent(parent);
-      // Clear ContentReset from the effect tag
-      parentFiber.effectTag &= ~ContentReset;
+  };
+  updateHostText$1 = function(current, workInProgress, oldText, newText) {
+    // If the text differs, mark it as an update. All the work in done in commitWork.
+    if (oldText !== newText) {
+      markUpdate(workInProgress);
     }
+  };
+} else if (supportsPersistence) {
+  // Persistent host tree mode
 
-    var before = getHostSibling(finishedWork);
-    // We only have the top Fiber that was inserted but we need recurse down its
+  // An unfortunate fork of appendAllChildren because we have two different parent types.
+  var appendAllChildrenToContainer = function(
+    containerChildSet,
+    workInProgress
+  ) {
+    // We only have the top Fiber that was created but we need recurse down its
     // children to find all the terminal nodes.
-    var node = finishedWork;
-    while (true) {
+    var node = workInProgress.child;
+    while (node !== null) {
       if (node.tag === HostComponent || node.tag === HostText) {
-        if (before) {
-          if (isContainer) {
-            insertInContainerBefore(parent, node.stateNode, before);
-          } else {
-            insertBefore(parent, node.stateNode, before);
-          }
-        } else {
-          if (isContainer) {
-            appendChildToContainer(parent, node.stateNode);
-          } else {
-            appendChild$$1(parent, node.stateNode);
-          }
-        }
+        appendChildToContainerChildSet(containerChildSet, node.stateNode);
       } else if (node.tag === HostPortal) {
-        // If the insertion itself is a portal, then we don't want to traverse
+        // If we have a portal child, then we don't want to traverse
         // down its children. Instead, we'll get insertions from each child in
         // the portal directly.
       } else if (node.child !== null) {
@@ -10633,11 +10583,11 @@ var ReactFiberCommitWork = function(
         node = node.child;
         continue;
       }
-      if (node === finishedWork) {
+      if (node === workInProgress) {
         return;
       }
       while (node.sibling === null) {
-        if (node.return === null || node.return === finishedWork) {
+        if (node.return === null || node.return === workInProgress) {
           return;
         }
         node = node.return;
@@ -10645,1629 +10595,1489 @@ var ReactFiberCommitWork = function(
       node.sibling.return = node.return;
       node = node.sibling;
     }
-  }
-
-  function unmountHostComponents(current) {
-    // We only have the top Fiber that was inserted but we need recurse down its
-    var node = current;
-
-    // Each iteration, currentParent is populated with node's host parent if not
-    // currentParentIsValid.
-    var currentParentIsValid = false;
-    var currentParent = void 0;
-    var currentParentIsContainer = void 0;
-
-    while (true) {
-      if (!currentParentIsValid) {
-        var parent = node.return;
-        findParent: while (true) {
-          invariant(
-            parent !== null,
-            "Expected to find a host parent. This error is likely caused by " +
-              "a bug in React. Please file an issue."
-          );
-          switch (parent.tag) {
-            case HostComponent:
-              currentParent = parent.stateNode;
-              currentParentIsContainer = false;
-              break findParent;
-            case HostRoot:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-            case HostPortal:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-          }
-          parent = parent.return;
-        }
-        currentParentIsValid = true;
-      }
-
-      if (node.tag === HostComponent || node.tag === HostText) {
-        commitNestedUnmounts(node);
-        // After all the children have unmounted, it is now safe to remove the
-        // node from the tree.
-        if (currentParentIsContainer) {
-          removeChildFromContainer(currentParent, node.stateNode);
-        } else {
-          removeChild(currentParent, node.stateNode);
-        }
-        // Don't visit children because we already visited them.
-      } else if (node.tag === HostPortal) {
-        // When we go into a portal, it becomes the parent to remove from.
-        // We will reassign it back when we pop the portal on the way up.
-        currentParent = node.stateNode.containerInfo;
-        // Visit children because portals might contain host components.
-        if (node.child !== null) {
-          node.child.return = node;
-          node = node.child;
-          continue;
-        }
+  };
+  updateHostContainer = function(workInProgress) {
+    var portalOrRoot = workInProgress.stateNode;
+    var childrenUnchanged = workInProgress.firstEffect === null;
+    if (childrenUnchanged) {
+      // No changes, just reuse the existing instance.
+    } else {
+      var container = portalOrRoot.containerInfo;
+      var newChildSet = createContainerChildSet(container);
+      // If children might have changed, we have to add them all to the set.
+      appendAllChildrenToContainer(newChildSet, workInProgress);
+      portalOrRoot.pendingChildren = newChildSet;
+      // Schedule an update on the container to swap out the container.
+      markUpdate(workInProgress);
+      finalizeContainerChildren(container, newChildSet);
+    }
+  };
+  updateHostComponent$1 = function(
+    current,
+    workInProgress,
+    updatePayload,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    currentHostContext
+  ) {
+    // If there are no effects associated with this node, then none of our children had any updates.
+    // This guarantees that we can reuse all of them.
+    var childrenUnchanged = workInProgress.firstEffect === null;
+    var currentInstance = current.stateNode;
+    if (childrenUnchanged && updatePayload === null) {
+      // No changes, just reuse the existing instance.
+      // Note that this might release a previous clone.
+      workInProgress.stateNode = currentInstance;
+    } else {
+      var recyclableInstance = workInProgress.stateNode;
+      var newInstance = cloneInstance(
+        currentInstance,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        workInProgress,
+        childrenUnchanged,
+        recyclableInstance
+      );
+      if (
+        finalizeInitialChildren(
+          newInstance,
+          type,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        )
+      ) {
+        markUpdate(workInProgress);
+      }
+      workInProgress.stateNode = newInstance;
+      if (childrenUnchanged) {
+        // If there are no other effects in this tree, we need to flag this node as having one.
+        // Even though we're not going to use it for anything.
+        // Otherwise parents won't know that there are new children to propagate upwards.
+        markUpdate(workInProgress);
       } else {
-        commitUnmount(node);
-        // Visit children because we may find more host components below.
-        if (node.child !== null) {
-          node.child.return = node;
-          node = node.child;
-          continue;
-        }
-      }
-      if (node === current) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === current) {
-          return;
-        }
-        node = node.return;
-        if (node.tag === HostPortal) {
-          // When we go out of the portal, we need to restore the parent.
-          // Since we don't keep a stack of them, we will search for it.
-          currentParentIsValid = false;
-        }
+        // If children might have changed, we have to add them all to the set.
+        appendAllChildren(newInstance, workInProgress);
       }
-      node.sibling.return = node.return;
-      node = node.sibling;
     }
-  }
-
-  function commitDeletion(current) {
-    // Recursively delete all host nodes from the parent.
-    // Detach refs and call componentWillUnmount() on the whole subtree.
-    unmountHostComponents(current);
-    detachFiber(current);
-  }
-
-  function commitWork(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        return;
-      }
-      case HostComponent: {
-        var _instance7 = finishedWork.stateNode;
-        if (_instance7 != null) {
-          // Commit the work prepared earlier.
-          var newProps = finishedWork.memoizedProps;
-          // For hydration we reuse the update path but we treat the oldProps
-          // as the newProps. The updatePayload will contain the real change in
-          // this case.
-          var oldProps = current !== null ? current.memoizedProps : newProps;
-          var type = finishedWork.type;
-          // TODO: Type the updateQueue to be specific to host components.
-          var updatePayload = finishedWork.updateQueue;
-          finishedWork.updateQueue = null;
-          if (updatePayload !== null) {
-            commitUpdate(
-              _instance7,
-              updatePayload,
-              type,
-              oldProps,
-              newProps,
-              finishedWork
-            );
-          }
-        }
-        return;
-      }
-      case HostText: {
-        invariant(
-          finishedWork.stateNode !== null,
-          "This should have a text node initialized. This error is likely " +
-            "caused by a bug in React. Please file an issue."
-        );
-        var textInstance = finishedWork.stateNode;
-        var newText = finishedWork.memoizedProps;
-        // For hydration we reuse the update path but we treat the oldProps
-        // as the newProps. The updatePayload will contain the real change in
-        // this case.
-        var oldText = current !== null ? current.memoizedProps : newText;
-        commitTextUpdate(textInstance, oldText, newText);
-        return;
-      }
-      case HostRoot: {
-        return;
-      }
-      case Profiler: {
-        if (enableProfilerTimer) {
-          var onRender = finishedWork.memoizedProps.onRender;
-          onRender(
-            finishedWork.memoizedProps.id,
-            current === null ? "mount" : "update",
-            finishedWork.stateNode.duration,
-            finishedWork.treeBaseTime
-          );
-
-          // Reset actualTime after successful commit.
-          // By default, we append to this time to account for errors and pauses.
-          finishedWork.stateNode.duration = 0;
-        }
-        return;
-      }
-      case TimeoutComponent: {
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
+  };
+  updateHostText$1 = function(current, workInProgress, oldText, newText) {
+    if (oldText !== newText) {
+      // If the text content differs, we'll create a new text instance for it.
+      var rootContainerInstance = getRootHostContainer();
+      var currentHostContext = getHostContext();
+      workInProgress.stateNode = createTextInstance(
+        newText,
+        rootContainerInstance,
+        currentHostContext,
+        workInProgress
+      );
+      // We'll have to mark it as having an effect, even though we won't use the effect for anything.
+      // This lets the parents know that at least one of their children has changed.
+      markUpdate(workInProgress);
     }
-  }
-
-  function commitResetTextContent(current) {
-    resetTextContent(current.stateNode);
-  }
-
-  if (enableMutatingReconciler) {
-    return {
-      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitResetTextContent: commitResetTextContent,
-      commitPlacement: commitPlacement,
-      commitDeletion: commitDeletion,
-      commitWork: commitWork,
-      commitLifeCycles: commitLifeCycles,
-      commitAttachRef: commitAttachRef,
-      commitDetachRef: commitDetachRef
-    };
-  } else {
-    invariant(false, "Mutating reconciler is disabled.");
-  }
-};
-
-var ReactFiberUnwindWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  recalculateCurrentTime,
-  markLegacyErrorBoundaryAsFailed,
-  isAlreadyFailedLegacyErrorBoundary,
-  onUncaughtError,
-  profilerTimer,
-  suspendRoot,
-  retrySuspendedRoot
-) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-  var resumeActualRenderTimerIfPaused =
-      profilerTimer.resumeActualRenderTimerIfPaused,
-    recordElapsedActualRenderTime = profilerTimer.recordElapsedActualRenderTime;
-
-  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
-    var update = createUpdate(expirationTime);
-    // Unmount the root by rendering null.
-    update.tag = CaptureUpdate;
-    // Caution: React DevTools currently depends on this property
-    // being called "element".
-    update.payload = { element: null };
-    var error = errorInfo.value;
-    update.callback = function() {
-      onUncaughtError(error);
-      logError(fiber, errorInfo);
-    };
-    return update;
-  }
+  };
+} else {
+  // No host operations
+  updateHostContainer = function(workInProgress) {
+    // Noop
+  };
+  updateHostComponent$1 = function(
+    current,
+    workInProgress,
+    updatePayload,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    currentHostContext
+  ) {
+    // Noop
+  };
+  updateHostText$1 = function(current, workInProgress, oldText, newText) {
+    // Noop
+  };
+}
 
-  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
-    var update = createUpdate(expirationTime);
-    update.tag = CaptureUpdate;
-    var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
-    if (
-      enableGetDerivedStateFromCatch &&
-      typeof getDerivedStateFromCatch === "function"
-    ) {
-      var _error = errorInfo.value;
-      update.payload = function() {
-        return getDerivedStateFromCatch(_error);
-      };
-    }
+function completeWork(current, workInProgress, renderExpirationTime) {
+  var newProps = workInProgress.pendingProps;
 
-    var inst = fiber.stateNode;
-    if (inst !== null && typeof inst.componentDidCatch === "function") {
-      update.callback = function callback() {
-        if (
-          !enableGetDerivedStateFromCatch ||
-          getDerivedStateFromCatch !== "function"
-        ) {
-          // To preserve the preexisting retry behavior of error boundaries,
-          // we keep track of which ones already failed during this batch.
-          // This gets reset before we yield back to the browser.
-          // TODO: Warn in strict mode if getDerivedStateFromCatch is
-          // not defined.
-          markLegacyErrorBoundaryAsFailed(this);
-        }
-        var error = errorInfo.value;
-        var stack = errorInfo.stack;
-        logError(fiber, errorInfo);
-        this.componentDidCatch(error, {
-          componentStack: stack !== null ? stack : ""
-        });
-      };
+  if (enableProfilerTimer) {
+    if (workInProgress.mode & ProfileMode) {
+      recordElapsedActualRenderTime(workInProgress);
     }
-    return update;
-  }
-
-  function schedulePing(finishedWork) {
-    // Once the promise resolves, we should try rendering the non-
-    // placeholder state again.
-    var currentTime = recalculateCurrentTime();
-    var expirationTime = computeExpirationForFiber(currentTime, finishedWork);
-    var recoveryUpdate = createUpdate(expirationTime);
-    enqueueUpdate(finishedWork, recoveryUpdate, expirationTime);
-    scheduleWork(finishedWork, expirationTime);
   }
 
-  function throwException(
-    root,
-    returnFiber,
-    sourceFiber,
-    value,
-    renderIsExpired,
-    renderExpirationTime,
-    currentTimeMs
-  ) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-
-    if (
-      enableSuspense &&
-      value !== null &&
-      typeof value === "object" &&
-      typeof value.then === "function"
-    ) {
-      // This is a thenable.
-      var _thenable = value;
-
-      var expirationTimeMs = expirationTimeToMs(renderExpirationTime);
-      var startTimeMs = expirationTimeMs - 5000;
-      var elapsedMs = currentTimeMs - startTimeMs;
-      if (elapsedMs < 0) {
-        elapsedMs = 0;
-      }
-      var remainingTimeMs = expirationTimeMs - currentTimeMs;
-
-      // Find the earliest timeout of all the timeouts in the ancestor path.
-      // TODO: Alternatively, we could store the earliest timeout on the context
-      // stack, rather than searching on every suspend.
-      var _workInProgress = returnFiber;
-      var earliestTimeoutMs = -1;
-      searchForEarliestTimeout: do {
-        if (_workInProgress.tag === TimeoutComponent) {
-          var current = _workInProgress.alternate;
-          if (current !== null && current.memoizedState === true) {
-            // A parent Timeout already committed in a placeholder state. We
-            // need to handle this promise immediately. In other words, we
-            // should never suspend inside a tree that already expired.
-            earliestTimeoutMs = 0;
-            break searchForEarliestTimeout;
-          }
-          var timeoutPropMs = _workInProgress.pendingProps.ms;
-          if (typeof timeoutPropMs === "number") {
-            if (timeoutPropMs <= 0) {
-              earliestTimeoutMs = 0;
-              break searchForEarliestTimeout;
-            } else if (
-              earliestTimeoutMs === -1 ||
-              timeoutPropMs < earliestTimeoutMs
-            ) {
-              earliestTimeoutMs = timeoutPropMs;
-            }
-          } else if (earliestTimeoutMs === -1) {
-            earliestTimeoutMs = remainingTimeMs;
-          }
-        }
-        _workInProgress = _workInProgress.return;
-      } while (_workInProgress !== null);
-
-      // Compute the remaining time until the timeout.
-      var msUntilTimeout = earliestTimeoutMs - elapsedMs;
-
-      if (renderExpirationTime === Never || msUntilTimeout > 0) {
-        // There's still time remaining.
-        suspendRoot(root, _thenable, msUntilTimeout, renderExpirationTime);
-        var onResolveOrReject = function() {
-          retrySuspendedRoot(root, renderExpirationTime);
-        };
-        _thenable.then(onResolveOrReject, onResolveOrReject);
-        return;
-      } else {
-        // No time remaining. Need to fallback to placeholder.
-        // Find the nearest timeout that can be retried.
-        _workInProgress = returnFiber;
-        do {
-          switch (_workInProgress.tag) {
-            case HostRoot: {
-              // The root expired, but no fallback was provided. Throw a
-              // helpful error.
-              var message =
-                renderExpirationTime === Sync
-                  ? "A synchronous update was suspended, but no fallback UI " +
-                    "was provided."
-                  : "An update was suspended for longer than the timeout, " +
-                    "but no fallback UI was provided.";
-              value = new Error(message);
-              break;
-            }
-            case TimeoutComponent: {
-              if ((_workInProgress.effectTag & DidCapture) === NoEffect) {
-                _workInProgress.effectTag |= ShouldCapture;
-                var _onResolveOrReject = schedulePing.bind(
-                  null,
-                  _workInProgress
-                );
-                _thenable.then(_onResolveOrReject, _onResolveOrReject);
-                return;
-              }
-              // Already captured during this render. Continue to the next
-              // Timeout ancestor.
-              break;
-            }
-          }
-          _workInProgress = _workInProgress.return;
-        } while (_workInProgress !== null);
+  switch (workInProgress.tag) {
+    case FunctionalComponent:
+      return null;
+    case ClassComponent: {
+      // We are leaving this subtree, so pop context if any.
+      popContextProvider(workInProgress);
+      return null;
+    }
+    case HostRoot: {
+      popHostContainer(workInProgress);
+      popTopLevelContextObject(workInProgress);
+      var fiberRoot = workInProgress.stateNode;
+      if (fiberRoot.pendingContext) {
+        fiberRoot.context = fiberRoot.pendingContext;
+        fiberRoot.pendingContext = null;
+      }
+      if (current === null || current.child === null) {
+        // If we hydrated, pop so that we can delete any remaining children
+        // that weren't hydrated.
+        popHydrationState(workInProgress);
+        // This resets the hacky state to fix isMounted before committing.
+        // TODO: Delete this when we delete isMounted and findDOMNode.
+        workInProgress.effectTag &= ~Placement;
       }
+      updateHostContainer(workInProgress);
+      return null;
     }
+    case HostComponent: {
+      popHostContext(workInProgress);
+      var rootContainerInstance = getRootHostContainer();
+      var type = workInProgress.type;
+      if (current !== null && workInProgress.stateNode != null) {
+        // If we have an alternate, that means this is an update and we need to
+        // schedule a side-effect to do the updates.
+        var oldProps = current.memoizedProps;
+        // If we get updated because one of our children updated, we don't
+        // have newProps so we'll have to reuse them.
+        // TODO: Split the update API as separate for the props vs. children.
+        // Even better would be if children weren't special cased at all tho.
+        var instance = workInProgress.stateNode;
+        var currentHostContext = getHostContext();
+        // TODO: Experiencing an error where oldProps is null. Suggests a host
+        // component is hitting the resume path. Figure out why. Possibly
+        // related to `hidden`.
+        var updatePayload = prepareUpdate(
+          instance,
+          type,
+          oldProps,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        );
 
-    // We didn't find a boundary that could handle this type of exception. Start
-    // over and traverse parent path again, this time treating the exception
-    // as an error.
-    value = createCapturedValue(value, sourceFiber);
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          var _errorInfo = value;
-          workInProgress.effectTag |= ShouldCapture;
-          var update = createRootErrorUpdate(
-            workInProgress,
-            _errorInfo,
-            renderExpirationTime
+        updateHostComponent$1(
+          current,
+          workInProgress,
+          updatePayload,
+          type,
+          oldProps,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        );
+
+        if (current.ref !== workInProgress.ref) {
+          markRef$1(workInProgress);
+        }
+      } else {
+        if (!newProps) {
+          invariant(
+            workInProgress.stateNode !== null,
+            "We must have new props for new mounts. This error is likely " +
+              "caused by a bug in React. Please file an issue."
           );
-          enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
-          return;
+          // This can happen when we abort work.
+          return null;
         }
-        case ClassComponent:
-          // Capture and retry
-          var errorInfo = value;
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
+
+        var _currentHostContext = getHostContext();
+        // TODO: Move createInstance to beginWork and keep it on a context
+        // "stack" as the parent. Then append children as we go in beginWork
+        // or completeWork depending on we want to add then top->down or
+        // bottom->up. Top->down is faster in IE11.
+        var wasHydrated = popHydrationState(workInProgress);
+        if (wasHydrated) {
+          // TODO: Move this and createInstance step into the beginPhase
+          // to consolidate.
           if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            workInProgress.effectTag |= ShouldCapture;
-            // Schedule the error boundary to re-render using updated state
-            var _update = createClassErrorUpdate(
+            prepareToHydrateHostInstance(
               workInProgress,
-              errorInfo,
-              renderExpirationTime
-            );
-            enqueueCapturedUpdate(
-              workInProgress,
-              _update,
-              renderExpirationTime
-            );
-            return;
+              rootContainerInstance,
+              _currentHostContext
+            )
+          ) {
+            // If changes to the hydrated node needs to be applied at the
+            // commit-phase we mark this as such.
+            markUpdate(workInProgress);
           }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress.return;
-    } while (workInProgress !== null);
-  }
+        } else {
+          var _instance = createInstance(
+            type,
+            newProps,
+            rootContainerInstance,
+            _currentHostContext,
+            workInProgress
+          );
 
-  function unwindWork(workInProgress, renderIsExpired, renderExpirationTime) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
+          appendAllChildren(_instance, workInProgress);
+
+          // Certain renderers require commit-time effects for initial mount.
+          // (eg DOM renderer supports auto-focus for certain elements).
+          // Make sure such renderers get scheduled for later work.
+          if (
+            finalizeInitialChildren(
+              _instance,
+              type,
+              newProps,
+              rootContainerInstance,
+              _currentHostContext
+            )
+          ) {
+            markUpdate(workInProgress);
+          }
+          workInProgress.stateNode = _instance;
         }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
+
+        if (workInProgress.ref !== null) {
+          // If there is a ref on a host node we need to schedule a callback
+          markRef$1(workInProgress);
         }
-        return null;
       }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case TimeoutComponent: {
-        var _effectTag2 = workInProgress.effectTag;
-        if (_effectTag2 & ShouldCapture) {
-          workInProgress.effectTag =
-            (_effectTag2 & ~ShouldCapture) | DidCapture;
-          return workInProgress;
+      return null;
+    }
+    case HostText: {
+      var newText = newProps;
+      if (current && workInProgress.stateNode != null) {
+        var oldText = current.memoizedProps;
+        // If we have an alternate, that means this is an update and we need
+        // to schedule a side-effect to do the updates.
+        updateHostText$1(current, workInProgress, oldText, newText);
+      } else {
+        if (typeof newText !== "string") {
+          invariant(
+            workInProgress.stateNode !== null,
+            "We must have new props for new mounts. This error is likely " +
+              "caused by a bug in React. Please file an issue."
+          );
+          // This can happen when we abort work.
+          return null;
+        }
+        var _rootContainerInstance = getRootHostContainer();
+        var _currentHostContext2 = getHostContext();
+        var _wasHydrated = popHydrationState(workInProgress);
+        if (_wasHydrated) {
+          if (prepareToHydrateHostTextInstance(workInProgress)) {
+            markUpdate(workInProgress);
+          }
+        } else {
+          workInProgress.stateNode = createTextInstance(
+            newText,
+            _rootContainerInstance,
+            _currentHostContext2,
+            workInProgress
+          );
         }
-        return null;
       }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
+      return null;
     }
+    case ForwardRef:
+      return null;
+    case TimeoutComponent:
+      return null;
+    case Fragment:
+      return null;
+    case Mode:
+      return null;
+    case Profiler:
+      return null;
+    case HostPortal:
+      popHostContainer(workInProgress);
+      updateHostContainer(workInProgress);
+      return null;
+    case ContextProvider:
+      // Pop provider fiber
+      popProvider(workInProgress);
+      return null;
+    case ContextConsumer:
+      return null;
+    // Error cases
+    case IndeterminateComponent:
+      invariant(
+        false,
+        "An indeterminate component should have become determinate before " +
+          "completing. This error is likely caused by a bug in React. Please " +
+          "file an issue."
+      );
+    // eslint-disable-next-line no-fallthrough
+    default:
+      invariant(
+        false,
+        "Unknown unit of work tag. This error is likely caused by a bug in " +
+          "React. Please file an issue."
+      );
   }
+}
 
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      case Profiler:
-        if (enableProfilerTimer) {
-          // Resume in case we're picking up on work that was paused.
-          resumeActualRenderTimerIfPaused();
-          recordElapsedActualRenderTime(interruptedWork);
-        }
-        break;
-      default:
-        break;
-    }
-  }
+// Module provided by RN:
+/**
+ * Intercept lifecycle errors and ensure they are shown with the correct stack
+ * trace within the native redbox component.
+ */
+function showErrorDialog(capturedError) {
+  var componentStack = capturedError.componentStack,
+    error = capturedError.error;
 
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork,
-    createRootErrorUpdate: createRootErrorUpdate,
-    createClassErrorUpdate: createClassErrorUpdate
-  };
-};
+  var errorToHandle = void 0;
 
-var NO_CONTEXT = {};
+  // Typically Errors are thrown but eg strings or null can be thrown as well.
+  if (error instanceof Error) {
+    var message = error.message,
+      name = error.name;
 
-var ReactFiberHostContext = function(config, stack) {
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
+    var summary = message ? name + ": " + message : name;
 
-  var contextStackCursor = createCursor(NO_CONTEXT);
-  var contextFiberStackCursor = createCursor(NO_CONTEXT);
-  var rootInstanceStackCursor = createCursor(NO_CONTEXT);
+    errorToHandle = error;
 
-  function requiredContext(c) {
-    invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug " +
-        "in React. Please file an issue."
+    try {
+      errorToHandle.message =
+        summary + "\n\nThis error is located at:" + componentStack;
+    } catch (e) {}
+  } else if (typeof error === "string") {
+    errorToHandle = new Error(
+      error + "\n\nThis error is located at:" + componentStack
     );
-    return c;
+  } else {
+    errorToHandle = new Error("Unspecified error at:" + componentStack);
   }
 
-  function getRootHostContainer() {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    return rootInstance;
-  }
+  ExceptionsManager.handleException(errorToHandle, false);
+
+  // Return false here to prevent ReactFiberErrorLogger default behavior of
+  // logging error details to console.error. Calls to console.error are
+  // automatically routed to the native redbox controller, which we've already
+  // done above by calling ExceptionsManager.
+  return false;
+}
 
-  function pushHostContainer(fiber, nextRootInstance) {
-    // Push current root instance onto the stack;
-    // This allows us to reset root when portals are popped.
-    push(rootInstanceStackCursor, nextRootInstance, fiber);
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
+function logCapturedError(capturedError) {
+  var logError = showErrorDialog(capturedError);
 
-    // Finally, we need to push the host context to the stack.
-    // However, we can't just call getRootHostContext() and push it because
-    // we'd have a different number of entries on the stack depending on
-    // whether getRootHostContext() throws somewhere in renderer code or not.
-    // So we push an empty value first. This lets us safely unwind on errors.
-    push(contextStackCursor, NO_CONTEXT, fiber);
-    var nextRootContext = getRootHostContext(nextRootInstance);
-    // Now that we know this function doesn't throw, replace it.
-    pop(contextStackCursor, fiber);
-    push(contextStackCursor, nextRootContext, fiber);
+  // Allow injected showErrorDialog() to prevent default console.error logging.
+  // This enables renderers like ReactNative to better manage redbox behavior.
+  if (logError === false) {
+    return;
   }
 
-  function popHostContainer(fiber) {
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
-    pop(rootInstanceStackCursor, fiber);
+  var error = capturedError.error;
+  var suppressLogging = error && error.suppressReactErrorLogging;
+  if (suppressLogging) {
+    return;
   }
 
-  function getHostContext() {
-    var context = requiredContext(contextStackCursor.current);
-    return context;
-  }
+  {
+    var componentName = capturedError.componentName,
+      componentStack = capturedError.componentStack,
+      errorBoundaryName = capturedError.errorBoundaryName,
+      errorBoundaryFound = capturedError.errorBoundaryFound,
+      willRetry = capturedError.willRetry;
 
-  function pushHostContext(fiber) {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    var context = requiredContext(contextStackCursor.current);
-    var nextContext = getChildHostContext(context, fiber.type, rootInstance);
+    var componentNameMessage = componentName
+      ? "The above error occurred in the <" + componentName + "> component:"
+      : "The above error occurred in one of your React components:";
 
-    // Don't push this Fiber's context unless it's unique.
-    if (context === nextContext) {
-      return;
+    var errorBoundaryMessage = void 0;
+    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
+    if (errorBoundaryFound && errorBoundaryName) {
+      if (willRetry) {
+        errorBoundaryMessage =
+          "React will try to recreate this component tree from scratch " +
+          ("using the error boundary you provided, " + errorBoundaryName + ".");
+      } else {
+        errorBoundaryMessage =
+          "This error was initially handled by the error boundary " +
+          errorBoundaryName +
+          ".\n" +
+          "Recreating the tree from scratch failed so React will unmount the tree.";
+      }
+    } else {
+      errorBoundaryMessage =
+        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
+        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
     }
+    var combinedMessage =
+      "" +
+      componentNameMessage +
+      componentStack +
+      "\n\n" +
+      ("" + errorBoundaryMessage);
 
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
-    push(contextStackCursor, nextContext, fiber);
+    // In development, we provide our own message with just the component stack.
+    // We don't include the original error message and JS stack because the browser
+    // has already printed it. Even if the application swallows the error, it is still
+    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
+    console.error(combinedMessage);
   }
+}
 
-  function popHostContext(fiber) {
-    // Do not pop unless this Fiber provided the current context.
-    // pushHostContext() only pushes Fibers that provide unique contexts.
-    if (contextFiberStackCursor.current !== fiber) {
-      return;
+var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
+var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
+
+var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
+{
+  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
+}
+
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source;
+  var stack = errorInfo.stack;
+  if (stack === null && source !== null) {
+    stack = getStackAddendumByWorkInProgressFiber(source);
+  }
+
+  var capturedError = {
+    componentName: source !== null ? getComponentName(source) : null,
+    componentStack: stack !== null ? stack : "",
+    error: errorInfo.value,
+    errorBoundary: null,
+    errorBoundaryName: null,
+    errorBoundaryFound: false,
+    willRetry: false
+  };
+
+  if (boundary !== null && boundary.tag === ClassComponent) {
+    capturedError.errorBoundary = boundary.stateNode;
+    capturedError.errorBoundaryName = getComponentName(boundary);
+    capturedError.errorBoundaryFound = true;
+    capturedError.willRetry = true;
+  }
+
+  try {
+    logCapturedError(capturedError);
+  } catch (e) {
+    // Prevent cycle if logCapturedError() throws.
+    // A cycle may still occur if logCapturedError renders a component that throws.
+    var suppressLogging = e && e.suppressReactErrorLogging;
+    if (!suppressLogging) {
+      console.error(e);
     }
-
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
   }
+}
 
-  return {
-    getHostContext: getHostContext,
-    getRootHostContainer: getRootHostContainer,
-    popHostContainer: popHostContainer,
-    popHostContext: popHostContext,
-    pushHostContainer: pushHostContainer,
-    pushHostContext: pushHostContext
-  };
+var callComponentWillUnmountWithTimer = function(current, instance) {
+  startPhaseTimer(current, "componentWillUnmount");
+  instance.props = current.memoizedProps;
+  instance.state = current.memoizedState;
+  instance.componentWillUnmount();
+  stopPhaseTimer();
 };
 
-var ReactFiberHydrationContext = function(config) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    hydration = config.hydration;
-
-  // If this doesn't have hydration mode.
-
-  if (!hydration) {
-    return {
-      enterHydrationState: function() {
-        return false;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostTextInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      popHydrationState: function(fiber) {
-        return false;
-      }
-    };
-  }
-
-  var canHydrateInstance = hydration.canHydrateInstance,
-    canHydrateTextInstance = hydration.canHydrateTextInstance,
-    getNextHydratableSibling = hydration.getNextHydratableSibling,
-    getFirstHydratableChild = hydration.getFirstHydratableChild,
-    hydrateInstance = hydration.hydrateInstance,
-    hydrateTextInstance = hydration.hydrateTextInstance,
-    didNotMatchHydratedContainerTextInstance =
-      hydration.didNotMatchHydratedContainerTextInstance,
-    didNotMatchHydratedTextInstance = hydration.didNotMatchHydratedTextInstance,
-    didNotHydrateContainerInstance = hydration.didNotHydrateContainerInstance,
-    didNotHydrateInstance = hydration.didNotHydrateInstance,
-    didNotFindHydratableContainerInstance =
-      hydration.didNotFindHydratableContainerInstance,
-    didNotFindHydratableContainerTextInstance =
-      hydration.didNotFindHydratableContainerTextInstance,
-    didNotFindHydratableInstance = hydration.didNotFindHydratableInstance,
-    didNotFindHydratableTextInstance =
-      hydration.didNotFindHydratableTextInstance;
-
-  // The deepest Fiber on the stack involved in a hydration context.
-  // This may have been an insertion or a hydration.
-
-  var hydrationParentFiber = null;
-  var nextHydratableInstance = null;
-  var isHydrating = false;
-
-  function enterHydrationState(fiber) {
-    var parentInstance = fiber.stateNode.containerInfo;
-    nextHydratableInstance = getFirstHydratableChild(parentInstance);
-    hydrationParentFiber = fiber;
-    isHydrating = true;
-    return true;
+// Capture errors so they don't interrupt unmounting.
+function safelyCallComponentWillUnmount(current, instance) {
+  {
+    invokeGuardedCallback$3(
+      null,
+      callComponentWillUnmountWithTimer,
+      null,
+      current,
+      instance
+    );
+    if (hasCaughtError$1()) {
+      var unmountError = clearCaughtError$1();
+      captureCommitPhaseError(current, unmountError);
+    }
   }
+}
 
-  function deleteHydratableInstance(returnFiber, instance) {
-    {
-      switch (returnFiber.tag) {
-        case HostRoot:
-          didNotHydrateContainerInstance(
-            returnFiber.stateNode.containerInfo,
-            instance
-          );
-          break;
-        case HostComponent:
-          didNotHydrateInstance(
-            returnFiber.type,
-            returnFiber.memoizedProps,
-            returnFiber.stateNode,
-            instance
-          );
-          break;
+function safelyDetachRef(current) {
+  var ref = current.ref;
+  if (ref !== null) {
+    if (typeof ref === "function") {
+      {
+        invokeGuardedCallback$3(null, ref, null, null);
+        if (hasCaughtError$1()) {
+          var refError = clearCaughtError$1();
+          captureCommitPhaseError(current, refError);
+        }
       }
-    }
-
-    var childToDelete = createFiberFromHostInstanceForDeletion();
-    childToDelete.stateNode = instance;
-    childToDelete.return = returnFiber;
-    childToDelete.effectTag = Deletion;
-
-    // This might seem like it belongs on progressedFirstDeletion. However,
-    // these children are not part of the reconciliation list of children.
-    // Even if we abort and rereconcile the children, that will try to hydrate
-    // again and the nodes are still in the host tree so these will be
-    // recreated.
-    if (returnFiber.lastEffect !== null) {
-      returnFiber.lastEffect.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
     } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+      ref.current = null;
     }
   }
+}
 
-  function insertNonHydratedInstance(returnFiber, fiber) {
-    fiber.effectTag |= Placement;
-    {
-      switch (returnFiber.tag) {
-        case HostRoot: {
-          var parentContainer = returnFiber.stateNode.containerInfo;
-          switch (fiber.tag) {
-            case HostComponent:
-              var type = fiber.type;
-              var props = fiber.pendingProps;
-              didNotFindHydratableContainerInstance(
-                parentContainer,
-                type,
-                props
-              );
-              break;
-            case HostText:
-              var text = fiber.pendingProps;
-              didNotFindHydratableContainerTextInstance(parentContainer, text);
-              break;
-          }
-          break;
-        }
-        case HostComponent: {
-          var parentType = returnFiber.type;
-          var parentProps = returnFiber.memoizedProps;
-          var parentInstance = returnFiber.stateNode;
-          switch (fiber.tag) {
-            case HostComponent:
-              var _type = fiber.type;
-              var _props = fiber.pendingProps;
-              didNotFindHydratableInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _type,
-                _props
-              );
-              break;
-            case HostText:
-              var _text = fiber.pendingProps;
-              didNotFindHydratableTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _text
+function commitBeforeMutationLifeCycles(current, finishedWork) {
+  switch (finishedWork.tag) {
+    case ClassComponent: {
+      if (finishedWork.effectTag & Snapshot) {
+        if (current !== null) {
+          var prevProps = current.memoizedProps;
+          var prevState = current.memoizedState;
+          startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
+          var instance = finishedWork.stateNode;
+          instance.props = finishedWork.memoizedProps;
+          instance.state = finishedWork.memoizedState;
+          var snapshot = instance.getSnapshotBeforeUpdate(prevProps, prevState);
+          {
+            var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
+            if (snapshot === undefined && !didWarnSet.has(finishedWork.type)) {
+              didWarnSet.add(finishedWork.type);
+              warning(
+                false,
+                "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
+                  "must be returned. You have returned undefined.",
+                getComponentName(finishedWork)
               );
-              break;
+            }
           }
-          break;
+          instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+          stopPhaseTimer();
         }
-        default:
-          return;
       }
+      return;
+    }
+    case HostRoot:
+    case HostComponent:
+    case HostText:
+    case HostPortal:
+      // Nothing to do for these component types
+      return;
+    default: {
+      invariant(
+        false,
+        "This unit of work tag should not have side-effects. This error is " +
+          "likely caused by a bug in React. Please file an issue."
+      );
     }
   }
+}
 
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case HostComponent: {
-        var type = fiber.type;
-        var props = fiber.pendingProps;
-        var instance = canHydrateInstance(nextInstance, type, props);
-        if (instance !== null) {
-          fiber.stateNode = instance;
-          return true;
+function commitLifeCycles(
+  finishedRoot,
+  current,
+  finishedWork,
+  currentTime,
+  committedExpirationTime
+) {
+  switch (finishedWork.tag) {
+    case ClassComponent: {
+      var instance = finishedWork.stateNode;
+      if (finishedWork.effectTag & Update) {
+        if (current === null) {
+          startPhaseTimer(finishedWork, "componentDidMount");
+          instance.props = finishedWork.memoizedProps;
+          instance.state = finishedWork.memoizedState;
+          instance.componentDidMount();
+          stopPhaseTimer();
+        } else {
+          var prevProps = current.memoizedProps;
+          var prevState = current.memoizedState;
+          startPhaseTimer(finishedWork, "componentDidUpdate");
+          instance.props = finishedWork.memoizedProps;
+          instance.state = finishedWork.memoizedState;
+          instance.componentDidUpdate(
+            prevProps,
+            prevState,
+            instance.__reactInternalSnapshotBeforeUpdate
+          );
+          stopPhaseTimer();
         }
-        return false;
       }
-      case HostText: {
-        var text = fiber.pendingProps;
-        var textInstance = canHydrateTextInstance(nextInstance, text);
-        if (textInstance !== null) {
-          fiber.stateNode = textInstance;
-          return true;
-        }
-        return false;
+      var updateQueue = finishedWork.updateQueue;
+      if (updateQueue !== null) {
+        instance.props = finishedWork.memoizedProps;
+        instance.state = finishedWork.memoizedState;
+        commitUpdateQueue(
+          finishedWork,
+          updateQueue,
+          instance,
+          committedExpirationTime
+        );
       }
-      default:
-        return false;
-    }
-  }
-
-  function tryToClaimNextHydratableInstance(fiber) {
-    if (!isHydrating) {
-      return;
-    }
-    var nextInstance = nextHydratableInstance;
-    if (!nextInstance) {
-      // Nothing to hydrate. Make it an insertion.
-      insertNonHydratedInstance(hydrationParentFiber, fiber);
-      isHydrating = false;
-      hydrationParentFiber = fiber;
       return;
     }
-    if (!tryHydrate(fiber, nextInstance)) {
-      // If we can't hydrate this instance let's try the next one.
-      // We use this as a heuristic. It's based on intuition and not data so it
-      // might be flawed or unnecessary.
-      nextInstance = getNextHydratableSibling(nextInstance);
-      if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-        // Nothing to hydrate. Make it an insertion.
-        insertNonHydratedInstance(hydrationParentFiber, fiber);
-        isHydrating = false;
-        hydrationParentFiber = fiber;
-        return;
-      }
-      // We matched the next one, we'll now assume that the first one was
-      // superfluous and we'll delete it. Since we can't eagerly delete it
-      // we'll have to schedule a deletion. To do that, this node needs a dummy
-      // fiber associated with it.
-      deleteHydratableInstance(hydrationParentFiber, nextHydratableInstance);
-    }
-    hydrationParentFiber = fiber;
-    nextHydratableInstance = getFirstHydratableChild(nextInstance);
-  }
-
-  function prepareToHydrateHostInstance(
-    fiber,
-    rootContainerInstance,
-    hostContext
-  ) {
-    var instance = fiber.stateNode;
-    var updatePayload = hydrateInstance(
-      instance,
-      fiber.type,
-      fiber.memoizedProps,
-      rootContainerInstance,
-      hostContext,
-      fiber
-    );
-    // TODO: Type this specific to this type of component.
-    fiber.updateQueue = updatePayload;
-    // If the update payload indicates that there is a change or if there
-    // is a new ref we mark this as an update.
-    if (updatePayload !== null) {
-      return true;
-    }
-    return false;
-  }
-
-  function prepareToHydrateHostTextInstance(fiber) {
-    var textInstance = fiber.stateNode;
-    var textContent = fiber.memoizedProps;
-    var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
-    {
-      if (shouldUpdate) {
-        // We assume that prepareToHydrateHostTextInstance is called in a context where the
-        // hydration parent is the parent host component of this host text.
-        var returnFiber = hydrationParentFiber;
-        if (returnFiber !== null) {
-          switch (returnFiber.tag) {
-            case HostRoot: {
-              var parentContainer = returnFiber.stateNode.containerInfo;
-              didNotMatchHydratedContainerTextInstance(
-                parentContainer,
-                textInstance,
-                textContent
-              );
+    case HostRoot: {
+      var _updateQueue = finishedWork.updateQueue;
+      if (_updateQueue !== null) {
+        var _instance = null;
+        if (finishedWork.child !== null) {
+          switch (finishedWork.child.tag) {
+            case HostComponent:
+              _instance = getPublicInstance(finishedWork.child.stateNode);
               break;
-            }
-            case HostComponent: {
-              var parentType = returnFiber.type;
-              var parentProps = returnFiber.memoizedProps;
-              var parentInstance = returnFiber.stateNode;
-              didNotMatchHydratedTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                textInstance,
-                textContent
-              );
+            case ClassComponent:
+              _instance = finishedWork.child.stateNode;
               break;
-            }
           }
         }
+        commitUpdateQueue(
+          finishedWork,
+          _updateQueue,
+          _instance,
+          committedExpirationTime
+        );
       }
+      return;
     }
-    return shouldUpdate;
-  }
-
-  function popToNextHostParent(fiber) {
-    var parent = fiber.return;
-    while (
-      parent !== null &&
-      parent.tag !== HostComponent &&
-      parent.tag !== HostRoot
-    ) {
-      parent = parent.return;
-    }
-    hydrationParentFiber = parent;
-  }
-
-  function popHydrationState(fiber) {
-    if (fiber !== hydrationParentFiber) {
-      // We're deeper than the current hydration context, inside an inserted
-      // tree.
-      return false;
-    }
-    if (!isHydrating) {
-      // If we're not currently hydrating but we're in a hydration context, then
-      // we were an insertion and now need to pop up reenter hydration of our
-      // siblings.
-      popToNextHostParent(fiber);
-      isHydrating = true;
-      return false;
-    }
-
-    var type = fiber.type;
-
-    // If we have any remaining hydratable nodes, we need to delete them now.
-    // We only do this deeper than head and body since they tend to have random
-    // other nodes in them. We also ignore components with pure text content in
-    // side of them.
-    // TODO: Better heuristic.
-    if (
-      fiber.tag !== HostComponent ||
-      (type !== "head" &&
-        type !== "body" &&
-        !shouldSetTextContent(type, fiber.memoizedProps))
-    ) {
-      var nextInstance = nextHydratableInstance;
-      while (nextInstance) {
-        deleteHydratableInstance(fiber, nextInstance);
-        nextInstance = getNextHydratableSibling(nextInstance);
-      }
-    }
-
-    popToNextHostParent(fiber);
-    nextHydratableInstance = hydrationParentFiber
-      ? getNextHydratableSibling(fiber.stateNode)
-      : null;
-    return true;
-  }
-
-  function resetHydrationState() {
-    hydrationParentFiber = null;
-    nextHydratableInstance = null;
-    isHydrating = false;
-  }
+    case HostComponent: {
+      var _instance2 = finishedWork.stateNode;
 
-  return {
-    enterHydrationState: enterHydrationState,
-    resetHydrationState: resetHydrationState,
-    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
-    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
-    popHydrationState: popHydrationState
-  };
-};
-
-// This lets us hook into Fiber to debug what it's doing.
-// See https://github.com/facebook/react/pull/8033.
-// This is not part of the public API, not even for React DevTools.
-// You may only inject a debugTool if you work on React Fiber itself.
-var ReactFiberInstrumentation = {
-  debugTool: null
-};
-
-var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
-
-// TODO: Offscreen updates
-
-function markPendingPriorityLevel(root, expirationTime) {
-  if (enableSuspense) {
-    // Update the latest and earliest pending times
-    var earliestPendingTime = root.earliestPendingTime;
-    if (earliestPendingTime === NoWork) {
-      // No other pending updates.
-      root.earliestPendingTime = root.latestPendingTime = expirationTime;
-    } else {
-      if (earliestPendingTime > expirationTime) {
-        // This is the earliest pending update.
-        root.earliestPendingTime = expirationTime;
-      } else {
-        var latestPendingTime = root.latestPendingTime;
-        if (latestPendingTime < expirationTime) {
-          // This is the latest pending update
-          root.latestPendingTime = expirationTime;
-        }
+      // Renderers may schedule work to be done after host components are mounted
+      // (eg DOM renderer may schedule auto-focus for inputs and form controls).
+      // These effects should only be committed when components are first mounted,
+      // aka when there is no current/alternate.
+      if (current === null && finishedWork.effectTag & Update) {
+        var type = finishedWork.type;
+        var props = finishedWork.memoizedProps;
+        commitMount(_instance2, type, props, finishedWork);
       }
-    }
-  }
-}
 
-function markCommittedPriorityLevels(root, currentTime, earliestRemainingTime) {
-  if (enableSuspense) {
-    if (earliestRemainingTime === NoWork) {
-      // Fast path. There's no remaining work. Clear everything.
-      root.earliestPendingTime = NoWork;
-      root.latestPendingTime = NoWork;
-      root.earliestSuspendedTime = NoWork;
-      root.latestSuspendedTime = NoWork;
-      root.latestPingedTime = NoWork;
       return;
     }
-
-    // Let's see if the previous latest known pending level was just flushed.
-    var latestPendingTime = root.latestPendingTime;
-    if (latestPendingTime !== NoWork) {
-      if (latestPendingTime < earliestRemainingTime) {
-        // We've flushed all the known pending levels.
-        root.earliestPendingTime = root.latestPendingTime = NoWork;
-      } else {
-        var earliestPendingTime = root.earliestPendingTime;
-        if (earliestPendingTime < earliestRemainingTime) {
-          // We've flushed the earliest known pending level. Set this to the
-          // latest pending time.
-          root.earliestPendingTime = root.latestPendingTime;
-        }
-      }
+    case HostText: {
+      // We have no life-cycles associated with text.
+      return;
     }
-
-    // Now let's handle the earliest remaining level in the whole tree. We need to
-    // decide whether to treat it as a pending level or as suspended. Check
-    // it falls within the range of known suspended levels.
-
-    var earliestSuspendedTime = root.earliestSuspendedTime;
-    if (earliestSuspendedTime === NoWork) {
-      // There's no suspended work. Treat the earliest remaining level as a
-      // pending level.
-      markPendingPriorityLevel(root, earliestRemainingTime);
+    case HostPortal: {
+      // We have no life-cycles associated with portals.
       return;
     }
-
-    var latestSuspendedTime = root.latestSuspendedTime;
-    if (earliestRemainingTime > latestSuspendedTime) {
-      // The earliest remaining level is later than all the suspended work. That
-      // means we've flushed all the suspended work.
-      root.earliestSuspendedTime = NoWork;
-      root.latestSuspendedTime = NoWork;
-      root.latestPingedTime = NoWork;
-
-      // There's no suspended work. Treat the earliest remaining level as a
-      // pending level.
-      markPendingPriorityLevel(root, earliestRemainingTime);
+    case Profiler: {
+      // We have no life-cycles associated with Profiler.
       return;
     }
-
-    if (earliestRemainingTime < earliestSuspendedTime) {
-      // The earliest remaining time is earlier than all the suspended work.
-      // Treat it as a pending update.
-      markPendingPriorityLevel(root, earliestRemainingTime);
+    case TimeoutComponent: {
+      // We have no life-cycles associated with Timeouts.
       return;
     }
-
-    // The earliest remaining time falls within the range of known suspended
-    // levels. We should treat this as suspended work.
+    default: {
+      invariant(
+        false,
+        "This unit of work tag should not have side-effects. This error is " +
+          "likely caused by a bug in React. Please file an issue."
+      );
+    }
   }
 }
 
-function markSuspendedPriorityLevel(root, suspendedTime) {
-  if (enableSuspense) {
-    // First, check the known pending levels and update them if needed.
-    var earliestPendingTime = root.earliestPendingTime;
-    var latestPendingTime = root.latestPendingTime;
-    if (earliestPendingTime === suspendedTime) {
-      if (latestPendingTime === suspendedTime) {
-        // Both known pending levels were suspended. Clear them.
-        root.earliestPendingTime = root.latestPendingTime = NoWork;
-      } else {
-        // The earliest pending level was suspended. Clear by setting it to the
-        // latest pending level.
-        root.earliestPendingTime = latestPendingTime;
-      }
-    } else if (latestPendingTime === suspendedTime) {
-      // The latest pending level was suspended. Clear by setting it to the
-      // latest pending level.
-      root.latestPendingTime = earliestPendingTime;
-    }
-
-    // Next, if we're working on the lowest known suspended level, clear the ping.
-    // TODO: What if a promise suspends and pings before the root completes?
-    var latestSuspendedTime = root.latestSuspendedTime;
-    if (latestSuspendedTime === suspendedTime) {
-      root.latestPingedTime = NoWork;
+function commitAttachRef(finishedWork) {
+  var ref = finishedWork.ref;
+  if (ref !== null) {
+    var instance = finishedWork.stateNode;
+    var instanceToUse = void 0;
+    switch (finishedWork.tag) {
+      case HostComponent:
+        instanceToUse = getPublicInstance(instance);
+        break;
+      default:
+        instanceToUse = instance;
     }
-
-    // Finally, update the known suspended levels.
-    var earliestSuspendedTime = root.earliestSuspendedTime;
-    if (earliestSuspendedTime === NoWork) {
-      // No other suspended levels.
-      root.earliestSuspendedTime = root.latestSuspendedTime = suspendedTime;
+    if (typeof ref === "function") {
+      ref(instanceToUse);
     } else {
-      if (earliestSuspendedTime > suspendedTime) {
-        // This is the earliest suspended level.
-        root.earliestSuspendedTime = suspendedTime;
-      } else if (latestSuspendedTime < suspendedTime) {
-        // This is the latest suspended level
-        root.latestSuspendedTime = suspendedTime;
+      {
+        if (!ref.hasOwnProperty("current")) {
+          warning(
+            false,
+            "Unexpected ref object provided for %s. " +
+              "Use either a ref-setter function or React.createRef().%s",
+            getComponentName(finishedWork),
+            getStackAddendumByWorkInProgressFiber(finishedWork)
+          );
+        }
       }
+
+      ref.current = instanceToUse;
     }
   }
 }
 
-function markPingedPriorityLevel(root, pingedTime) {
-  if (enableSuspense) {
-    var latestSuspendedTime = root.latestSuspendedTime;
-    if (latestSuspendedTime !== NoWork && latestSuspendedTime <= pingedTime) {
-      var latestPingedTime = root.latestPingedTime;
-      if (latestPingedTime === NoWork || latestPingedTime < pingedTime) {
-        root.latestPingedTime = pingedTime;
-      }
+function commitDetachRef(current) {
+  var currentRef = current.ref;
+  if (currentRef !== null) {
+    if (typeof currentRef === "function") {
+      currentRef(null);
+    } else {
+      currentRef.current = null;
     }
   }
 }
 
-function findNextPendingPriorityLevel(root) {
-  if (enableSuspense) {
-    var earliestSuspendedTime = root.earliestSuspendedTime;
-    var earliestPendingTime = root.earliestPendingTime;
-    if (earliestSuspendedTime === NoWork) {
-      // Fast path. There's no suspended work.
-      return earliestPendingTime;
-    }
+// User-originating errors (lifecycles and refs) should not interrupt
+// deletion, so don't let them throw. Host-originating errors should
+// interrupt deletion, so it's okay
+function commitUnmount(current) {
+  if (typeof onCommitUnmount === "function") {
+    onCommitUnmount(current);
+  }
 
-    // First, check if there's known pending work.
-    if (earliestPendingTime !== NoWork) {
-      return earliestPendingTime;
+  switch (current.tag) {
+    case ClassComponent: {
+      safelyDetachRef(current);
+      var instance = current.stateNode;
+      if (typeof instance.componentWillUnmount === "function") {
+        safelyCallComponentWillUnmount(current, instance);
+      }
+      return;
+    }
+    case HostComponent: {
+      safelyDetachRef(current);
+      return;
+    }
+    case HostPortal: {
+      // TODO: this is recursive.
+      // We are also not using this parent because
+      // the portal will get pushed immediately.
+      if (supportsMutation) {
+        unmountHostComponents(current);
+      } else if (supportsPersistence) {
+        emptyPortalContainer(current);
+      }
+      return;
     }
-
-    // Finally, if a suspended level was pinged, work on that. Otherwise there's
-    // nothing to work on.
-    return root.latestPingedTime;
-  } else {
-    return root.current.expirationTime;
   }
 }
 
-var warnedAboutMissingGetChildContext = void 0;
-
-{
-  warnedAboutMissingGetChildContext = {};
+function commitNestedUnmounts(root) {
+  // While we're inside a removed host node we don't want to call
+  // removeChild on the inner nodes because they're removed by the top
+  // call anyway. We also want to call componentWillUnmount on all
+  // composites before this host node is removed from the tree. Therefore
+  var node = root;
+  while (true) {
+    commitUnmount(node);
+    // Visit children because they may contain more composite or host nodes.
+    // Skip portals because commitUnmount() currently visits them recursively.
+    if (
+      node.child !== null &&
+      // If we use mutation we drill down into portals using commitUnmount above.
+      // If we don't use mutation we drill down into portals here instead.
+      (!supportsMutation || node.tag !== HostPortal)
+    ) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === root) {
+      return;
+    }
+    while (node.sibling === null) {
+      if (node.return === null || node.return === root) {
+        return;
+      }
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
 }
 
-var ReactFiberLegacyContext = function(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
+function detachFiber(current) {
+  // Cut off the return pointers to disconnect it from the tree. Ideally, we
+  // should clear the child pointer of the parent alternate to let this
+  // get GC:ed but we don't know which for sure which parent is the current
+  // one so we'll settle for GC:ing the subtree of this child. This child
+  // itself will be GC:ed when the parent updates the next time.
+  current.return = null;
+  current.child = null;
+  if (current.alternate) {
+    current.alternate.child = null;
+    current.alternate.return = null;
+  }
+}
 
-  // A cursor to the current merged context object on the stack.
+function emptyPortalContainer(current) {
+  if (!supportsPersistence) {
+    return;
+  }
 
-  var contextStackCursor = createCursor(emptyObject);
-  // A cursor to a boolean indicating whether the context has changed.
-  var didPerformWorkStackCursor = createCursor(false);
-  // Keep track of the previous context object that was on the stack.
-  // We use this to get access to the parent context after we have already
-  // pushed the next context provider, and now need to merge their contexts.
-  var previousContext = emptyObject;
+  var portal = current.stateNode;
+  var containerInfo = portal.containerInfo;
 
-  function getUnmaskedContext(workInProgress) {
-    var hasOwnContext = isContextProvider(workInProgress);
-    if (hasOwnContext) {
-      // If the fiber is a context provider itself, when we read its context
-      // we have already pushed its own child context on the stack. A context
-      // provider should not "see" its own child context. Therefore we read the
-      // previous (parent) context instead for a context provider.
-      return previousContext;
-    }
-    return contextStackCursor.current;
-  }
+  var emptyChildSet = createContainerChildSet(containerInfo);
+}
 
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    var instance = workInProgress.stateNode;
-    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
+function commitContainer(finishedWork) {
+  if (!supportsPersistence) {
+    return;
   }
 
-  function getMaskedContext(workInProgress, unmaskedContext) {
-    var type = workInProgress.type;
-    var contextTypes = type.contextTypes;
-    if (!contextTypes) {
-      return emptyObject;
+  switch (finishedWork.tag) {
+    case ClassComponent: {
+      return;
     }
-
-    // Avoid recreating masked context unless unmasked context has changed.
-    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
-    // This may trigger infinite loops if componentWillReceiveProps calls setState.
-    var instance = workInProgress.stateNode;
-    if (
-      instance &&
-      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-    ) {
-      return instance.__reactInternalMemoizedMaskedChildContext;
+    case HostComponent: {
+      return;
     }
-
-    var context = {};
-    for (var key in contextTypes) {
-      context[key] = unmaskedContext[key];
+    case HostText: {
+      return;
     }
+    case HostRoot:
+    case HostPortal: {
+      var portalOrRoot = finishedWork.stateNode;
+      var containerInfo = portalOrRoot.containerInfo,
+        _pendingChildren = portalOrRoot.pendingChildren;
 
-    {
-      var name = getComponentName(workInProgress) || "Unknown";
-      checkPropTypes(
-        contextTypes,
-        context,
-        "context",
-        name,
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+      return;
+    }
+    default: {
+      invariant(
+        false,
+        "This unit of work tag should not have side-effects. This error is " +
+          "likely caused by a bug in React. Please file an issue."
       );
     }
+  }
+}
 
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // Context is created before the class component is instantiated so check for instance.
-    if (instance) {
-      cacheContext(workInProgress, unmaskedContext, context);
+function getHostParentFiber(fiber) {
+  var parent = fiber.return;
+  while (parent !== null) {
+    if (isHostParent(parent)) {
+      return parent;
     }
-
-    return context;
+    parent = parent.return;
   }
+  invariant(
+    false,
+    "Expected to find a host parent. This error is likely caused by a bug " +
+      "in React. Please file an issue."
+  );
+}
 
-  function hasContextChanged() {
-    return didPerformWorkStackCursor.current;
-  }
+function isHostParent(fiber) {
+  return (
+    fiber.tag === HostComponent ||
+    fiber.tag === HostRoot ||
+    fiber.tag === HostPortal
+  );
+}
 
-  function isContextConsumer(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+function getHostSibling(fiber) {
+  // We're going to search forward into the tree until we find a sibling host
+  // node. Unfortunately, if multiple insertions are done in a row we have to
+  // search past them. This leads to exponential search for the next sibling.
+  var node = fiber;
+  siblings: while (true) {
+    // If we didn't find anything, let's try the next sibling.
+    while (node.sibling === null) {
+      if (node.return === null || isHostParent(node.return)) {
+        // If we pop out of the root or hit the parent the fiber we are the
+        // last sibling.
+        return null;
+      }
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
+    while (node.tag !== HostComponent && node.tag !== HostText) {
+      // If it is not host node and, we might have a host node inside it.
+      // Try to search down until we find one.
+      if (node.effectTag & Placement) {
+        // If we don't have a child, try the siblings instead.
+        continue siblings;
+      }
+      // If we don't have a child, try the siblings instead.
+      // We also skip portals because they are not part of this host tree.
+      if (node.child === null || node.tag === HostPortal) {
+        continue siblings;
+      } else {
+        node.child.return = node;
+        node = node.child;
+      }
+    }
+    // Check if this host node is stable or about to be placed.
+    if (!(node.effectTag & Placement)) {
+      // Found it!
+      return node.stateNode;
+    }
   }
+}
 
-  function isContextProvider(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+function commitPlacement(finishedWork) {
+  if (!supportsMutation) {
+    return;
   }
 
-  function popContextProvider(fiber) {
-    if (!isContextProvider(fiber)) {
-      return;
-    }
-
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
+  // Recursively insert all host nodes into the parent.
+  var parentFiber = getHostParentFiber(finishedWork);
+  var parent = void 0;
+  var isContainer = void 0;
+  switch (parentFiber.tag) {
+    case HostComponent:
+      parent = parentFiber.stateNode;
+      isContainer = false;
+      break;
+    case HostRoot:
+      parent = parentFiber.stateNode.containerInfo;
+      isContainer = true;
+      break;
+    case HostPortal:
+      parent = parentFiber.stateNode.containerInfo;
+      isContainer = true;
+      break;
+    default:
+      invariant(
+        false,
+        "Invalid host parent fiber. This error is likely caused by a bug " +
+          "in React. Please file an issue."
+      );
   }
-
-  function popTopLevelContextObject(fiber) {
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
+  if (parentFiber.effectTag & ContentReset) {
+    // Reset the text content of the parent before doing any insertions
+    resetTextContent(parent);
+    // Clear ContentReset from the effect tag
+    parentFiber.effectTag &= ~ContentReset;
   }
 
-  function pushTopLevelContextObject(fiber, context, didChange) {
-    invariant(
-      contextStackCursor.cursor == null,
-      "Unexpected context found on stack. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    push(contextStackCursor, context, fiber);
-    push(didPerformWorkStackCursor, didChange, fiber);
+  var before = getHostSibling(finishedWork);
+  // We only have the top Fiber that was inserted but we need recurse down its
+  // children to find all the terminal nodes.
+  var node = finishedWork;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      if (before) {
+        if (isContainer) {
+          insertInContainerBefore(parent, node.stateNode, before);
+        } else {
+          insertBefore(parent, node.stateNode, before);
+        }
+      } else {
+        if (isContainer) {
+          appendChildToContainer(parent, node.stateNode);
+        } else {
+          appendChild$1(parent, node.stateNode);
+        }
+      }
+    } else if (node.tag === HostPortal) {
+      // If the insertion itself is a portal, then we don't want to traverse
+      // down its children. Instead, we'll get insertions from each child in
+      // the portal directly.
+    } else if (node.child !== null) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === finishedWork) {
+      return;
+    }
+    while (node.sibling === null) {
+      if (node.return === null || node.return === finishedWork) {
+        return;
+      }
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
   }
+}
 
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode;
-    var childContextTypes = fiber.type.childContextTypes;
+function unmountHostComponents(current) {
+  // We only have the top Fiber that was inserted but we need recurse down its
+  var node = current;
 
-    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
-    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
-    if (typeof instance.getChildContext !== "function") {
-      {
-        var componentName = getComponentName(fiber) || "Unknown";
+  // Each iteration, currentParent is populated with node's host parent if not
+  // currentParentIsValid.
+  var currentParentIsValid = false;
+  var currentParent = void 0;
+  var currentParentIsContainer = void 0;
 
-        if (!warnedAboutMissingGetChildContext[componentName]) {
-          warnedAboutMissingGetChildContext[componentName] = true;
-          warning(
-            false,
-            "%s.childContextTypes is specified but there is no getChildContext() method " +
-              "on the instance. You can either define getChildContext() on %s or remove " +
-              "childContextTypes from it.",
-            componentName,
-            componentName
-          );
+  while (true) {
+    if (!currentParentIsValid) {
+      var parent = node.return;
+      findParent: while (true) {
+        invariant(
+          parent !== null,
+          "Expected to find a host parent. This error is likely caused by " +
+            "a bug in React. Please file an issue."
+        );
+        switch (parent.tag) {
+          case HostComponent:
+            currentParent = parent.stateNode;
+            currentParentIsContainer = false;
+            break findParent;
+          case HostRoot:
+            currentParent = parent.stateNode.containerInfo;
+            currentParentIsContainer = true;
+            break findParent;
+          case HostPortal:
+            currentParent = parent.stateNode.containerInfo;
+            currentParentIsContainer = true;
+            break findParent;
         }
+        parent = parent.return;
       }
-      return parentContext;
+      currentParentIsValid = true;
     }
 
-    var childContext = void 0;
-    {
-      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
-    }
-    startPhaseTimer(fiber, "getChildContext");
-    childContext = instance.getChildContext();
-    stopPhaseTimer();
-    {
-      ReactDebugCurrentFiber.setCurrentPhase(null);
+    if (node.tag === HostComponent || node.tag === HostText) {
+      commitNestedUnmounts(node);
+      // After all the children have unmounted, it is now safe to remove the
+      // node from the tree.
+      if (currentParentIsContainer) {
+        removeChildFromContainer(currentParent, node.stateNode);
+      } else {
+        removeChild(currentParent, node.stateNode);
+      }
+      // Don't visit children because we already visited them.
+    } else if (node.tag === HostPortal) {
+      // When we go into a portal, it becomes the parent to remove from.
+      // We will reassign it back when we pop the portal on the way up.
+      currentParent = node.stateNode.containerInfo;
+      // Visit children because portals might contain host components.
+      if (node.child !== null) {
+        node.child.return = node;
+        node = node.child;
+        continue;
+      }
+    } else {
+      commitUnmount(node);
+      // Visit children because we may find more host components below.
+      if (node.child !== null) {
+        node.child.return = node;
+        node = node.child;
+        continue;
+      }
     }
-    for (var contextKey in childContext) {
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
-      );
+    if (node === current) {
+      return;
     }
-    {
-      var name = getComponentName(fiber) || "Unknown";
-      checkPropTypes(
-        childContextTypes,
-        childContext,
-        "child context",
-        name,
-        // In practice, there is one case in which we won't get a stack. It's when
-        // somebody calls unstable_renderSubtreeIntoContainer() and we process
-        // context from the parent component instance. The stack will be missing
-        // because it's outside of the reconciliation, and so the pointer has not
-        // been set. This is rare and doesn't matter. We'll also remove that API.
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-      );
+    while (node.sibling === null) {
+      if (node.return === null || node.return === current) {
+        return;
+      }
+      node = node.return;
+      if (node.tag === HostPortal) {
+        // When we go out of the portal, we need to restore the parent.
+        // Since we don't keep a stack of them, we will search for it.
+        currentParentIsValid = false;
+      }
     }
-
-    return Object.assign({}, parentContext, childContext);
+    node.sibling.return = node.return;
+    node = node.sibling;
   }
+}
 
-  function pushContextProvider(workInProgress) {
-    if (!isContextProvider(workInProgress)) {
-      return false;
-    }
-
-    var instance = workInProgress.stateNode;
-    // We push the context as early as possible to ensure stack integrity.
-    // If the instance does not exist yet, we will push null at first,
-    // and replace it on the stack later when invalidating the context.
-    var memoizedMergedChildContext =
-      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-      emptyObject;
-
-    // Remember the parent context so we can merge with it later.
-    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
-    previousContext = contextStackCursor.current;
-    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
-    push(
-      didPerformWorkStackCursor,
-      didPerformWorkStackCursor.current,
-      workInProgress
-    );
-
-    return true;
+function commitDeletion(current) {
+  if (supportsMutation) {
+    // Recursively delete all host nodes from the parent.
+    // Detach refs and call componentWillUnmount() on the whole subtree.
+    unmountHostComponents(current);
+  } else {
+    // Detach refs and call componentWillUnmount() on the whole subtree.
+    commitNestedUnmounts(current);
   }
+  detachFiber(current);
+}
 
-  function invalidateContextProvider(workInProgress, didChange) {
-    var instance = workInProgress.stateNode;
-    invariant(
-      instance,
-      "Expected to have an instance by this point. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    if (didChange) {
-      // Merge parent and own context.
-      // Skip this if we're not updating due to sCU.
-      // This avoids unnecessarily recomputing memoized values.
-      var mergedContext = processChildContext(workInProgress, previousContext);
-      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-
-      // Replace the old (or empty) context with the new one.
-      // It is important to unwind the context in the reverse order.
-      pop(didPerformWorkStackCursor, workInProgress);
-      pop(contextStackCursor, workInProgress);
-      // Now push the new context and mark that it has changed.
-      push(contextStackCursor, mergedContext, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    } else {
-      pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    }
+function commitWork(current, finishedWork) {
+  if (!supportsMutation) {
+    commitContainer(finishedWork);
+    return;
   }
 
-  function findCurrentUnmaskedContext(fiber) {
-    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
-    // makes sense elsewhere
-    invariant(
-      isFiberMounted(fiber) && fiber.tag === ClassComponent,
-      "Expected subtree parent to be a mounted class component. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-
-    var node = fiber;
-    while (node.tag !== HostRoot) {
-      if (isContextProvider(node)) {
-        return node.stateNode.__reactInternalMemoizedMergedChildContext;
+  switch (finishedWork.tag) {
+    case ClassComponent: {
+      return;
+    }
+    case HostComponent: {
+      var instance = finishedWork.stateNode;
+      if (instance != null) {
+        // Commit the work prepared earlier.
+        var newProps = finishedWork.memoizedProps;
+        // For hydration we reuse the update path but we treat the oldProps
+        // as the newProps. The updatePayload will contain the real change in
+        // this case.
+        var oldProps = current !== null ? current.memoizedProps : newProps;
+        var type = finishedWork.type;
+        // TODO: Type the updateQueue to be specific to host components.
+        var updatePayload = finishedWork.updateQueue;
+        finishedWork.updateQueue = null;
+        if (updatePayload !== null) {
+          commitUpdate(
+            instance,
+            updatePayload,
+            type,
+            oldProps,
+            newProps,
+            finishedWork
+          );
+        }
       }
-      var parent = node.return;
+      return;
+    }
+    case HostText: {
       invariant(
-        parent,
-        "Found unexpected detached subtree parent. " +
-          "This error is likely caused by a bug in React. Please file an issue."
+        finishedWork.stateNode !== null,
+        "This should have a text node initialized. This error is likely " +
+          "caused by a bug in React. Please file an issue."
       );
-      node = parent;
+      var textInstance = finishedWork.stateNode;
+      var newText = finishedWork.memoizedProps;
+      // For hydration we reuse the update path but we treat the oldProps
+      // as the newProps. The updatePayload will contain the real change in
+      // this case.
+      var oldText = current !== null ? current.memoizedProps : newText;
+      commitTextUpdate(textInstance, oldText, newText);
+      return;
     }
-    return node.stateNode.context;
-  }
-
-  return {
-    getUnmaskedContext: getUnmaskedContext,
-    cacheContext: cacheContext,
-    getMaskedContext: getMaskedContext,
-    hasContextChanged: hasContextChanged,
-    isContextConsumer: isContextConsumer,
-    isContextProvider: isContextProvider,
-    popContextProvider: popContextProvider,
-    popTopLevelContextObject: popTopLevelContextObject,
-    pushTopLevelContextObject: pushTopLevelContextObject,
-    processChildContext: processChildContext,
-    pushContextProvider: pushContextProvider,
-    invalidateContextProvider: invalidateContextProvider,
-    findCurrentUnmaskedContext: findCurrentUnmaskedContext
-  };
-};
-
-var ReactFiberNewContext = function(stack, isPrimaryRenderer) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
-
-  var providerCursor = createCursor(null);
-  var valueCursor = createCursor(null);
-  var changedBitsCursor = createCursor(0);
-
-  var rendererSigil = void 0;
-  {
-    // Use this to detect multiple renderers using the same context
-    rendererSigil = {};
-  }
-
-  function pushProvider(providerFiber) {
-    var context = providerFiber.type._context;
-
-    if (isPrimaryRenderer) {
-      push(changedBitsCursor, context._changedBits, providerFiber);
-      push(valueCursor, context._currentValue, providerFiber);
-      push(providerCursor, providerFiber, providerFiber);
-
-      context._currentValue = providerFiber.pendingProps.value;
-      context._changedBits = providerFiber.stateNode;
-      {
-        !(
-          context._currentRenderer === undefined ||
-          context._currentRenderer === null ||
-          context._currentRenderer === rendererSigil
-        )
-          ? warning(
-              false,
-              "Detected multiple renderers concurrently rendering the " +
-                "same context provider. This is currently unsupported."
-            )
-          : void 0;
-        context._currentRenderer = rendererSigil;
-      }
-    } else {
-      push(changedBitsCursor, context._changedBits2, providerFiber);
-      push(valueCursor, context._currentValue2, providerFiber);
-      push(providerCursor, providerFiber, providerFiber);
-
-      context._currentValue2 = providerFiber.pendingProps.value;
-      context._changedBits2 = providerFiber.stateNode;
-      {
-        !(
-          context._currentRenderer2 === undefined ||
-          context._currentRenderer2 === null ||
-          context._currentRenderer2 === rendererSigil
-        )
-          ? warning(
-              false,
-              "Detected multiple renderers concurrently rendering the " +
-                "same context provider. This is currently unsupported."
-            )
-          : void 0;
-        context._currentRenderer2 = rendererSigil;
+    case HostRoot: {
+      return;
+    }
+    case Profiler: {
+      if (enableProfilerTimer) {
+        var onRender = finishedWork.memoizedProps.onRender;
+        onRender(
+          finishedWork.memoizedProps.id,
+          current === null ? "mount" : "update",
+          finishedWork.actualDuration,
+          finishedWork.treeBaseTime,
+          finishedWork.actualStartTime,
+          getCommitTime()
+        );
       }
+      return;
     }
-  }
-
-  function popProvider(providerFiber) {
-    var changedBits = changedBitsCursor.current;
-    var currentValue = valueCursor.current;
-
-    pop(providerCursor, providerFiber);
-    pop(valueCursor, providerFiber);
-    pop(changedBitsCursor, providerFiber);
-
-    var context = providerFiber.type._context;
-    if (isPrimaryRenderer) {
-      context._currentValue = currentValue;
-      context._changedBits = changedBits;
-    } else {
-      context._currentValue2 = currentValue;
-      context._changedBits2 = changedBits;
+    case TimeoutComponent: {
+      return;
+    }
+    default: {
+      invariant(
+        false,
+        "This unit of work tag should not have side-effects. This error is " +
+          "likely caused by a bug in React. Please file an issue."
+      );
     }
   }
+}
 
-  function getContextCurrentValue(context) {
-    return isPrimaryRenderer ? context._currentValue : context._currentValue2;
-  }
-
-  function getContextChangedBits(context) {
-    return isPrimaryRenderer ? context._changedBits : context._changedBits2;
+function commitResetTextContent(current) {
+  if (!supportsMutation) {
+    return;
   }
+  resetTextContent(current.stateNode);
+}
 
-  return {
-    pushProvider: pushProvider,
-    popProvider: popProvider,
-    getContextCurrentValue: getContextCurrentValue,
-    getContextChangedBits: getContextChangedBits
+function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+  var update = createUpdate(expirationTime);
+  // Unmount the root by rendering null.
+  update.tag = CaptureUpdate;
+  // Caution: React DevTools currently depends on this property
+  // being called "element".
+  update.payload = { element: null };
+  var error = errorInfo.value;
+  update.callback = function() {
+    onUncaughtError(error);
+    logError(fiber, errorInfo);
   };
-};
-
-var ReactFiberStack = function() {
-  var valueStack = [];
-
-  var fiberStack = void 0;
+  return update;
+}
 
-  {
-    fiberStack = [];
+function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+  var update = createUpdate(expirationTime);
+  update.tag = CaptureUpdate;
+  var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
+  if (
+    enableGetDerivedStateFromCatch &&
+    typeof getDerivedStateFromCatch === "function"
+  ) {
+    var error = errorInfo.value;
+    update.payload = function() {
+      return getDerivedStateFromCatch(error);
+    };
   }
 
-  var index = -1;
-
-  function createCursor(defaultValue) {
-    return {
-      current: defaultValue
+  var inst = fiber.stateNode;
+  if (inst !== null && typeof inst.componentDidCatch === "function") {
+    update.callback = function callback() {
+      if (
+        !enableGetDerivedStateFromCatch ||
+        getDerivedStateFromCatch !== "function"
+      ) {
+        // To preserve the preexisting retry behavior of error boundaries,
+        // we keep track of which ones already failed during this batch.
+        // This gets reset before we yield back to the browser.
+        // TODO: Warn in strict mode if getDerivedStateFromCatch is
+        // not defined.
+        markLegacyErrorBoundaryAsFailed(this);
+      }
+      var error = errorInfo.value;
+      var stack = errorInfo.stack;
+      logError(fiber, errorInfo);
+      this.componentDidCatch(error, {
+        componentStack: stack !== null ? stack : ""
+      });
     };
   }
+  return update;
+}
+
+function schedulePing(finishedWork) {
+  // Once the promise resolves, we should try rendering the non-
+  // placeholder state again.
+  var currentTime = recalculateCurrentTime();
+  var expirationTime = computeExpirationForFiber(currentTime, finishedWork);
+  var recoveryUpdate = createUpdate(expirationTime);
+  enqueueUpdate(finishedWork, recoveryUpdate, expirationTime);
+  scheduleWork(finishedWork, expirationTime);
+}
+
+function throwException(
+  root,
+  returnFiber,
+  sourceFiber,
+  value,
+  renderExpirationTime,
+  currentTimeMs
+) {
+  // The source fiber did not complete.
+  sourceFiber.effectTag |= Incomplete;
+  // Its effect list is no longer valid.
+  sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+
+  if (
+    enableSuspense &&
+    value !== null &&
+    typeof value === "object" &&
+    typeof value.then === "function"
+  ) {
+    // This is a thenable.
+    var thenable = value;
+
+    // TODO: Should use the earliest known expiration time
+    var expirationTimeMs = expirationTimeToMs(renderExpirationTime);
+    var startTimeMs = expirationTimeMs - 5000;
+    var elapsedMs = currentTimeMs - startTimeMs;
+    if (elapsedMs < 0) {
+      elapsedMs = 0;
+    }
+    var remainingTimeMs = expirationTimeMs - currentTimeMs;
+
+    // Find the earliest timeout of all the timeouts in the ancestor path.
+    // TODO: Alternatively, we could store the earliest timeout on the context
+    // stack, rather than searching on every suspend.
+    var _workInProgress = returnFiber;
+    var earliestTimeoutMs = -1;
+    searchForEarliestTimeout: do {
+      if (_workInProgress.tag === TimeoutComponent) {
+        var current = _workInProgress.alternate;
+        if (current !== null && current.memoizedState === true) {
+          // A parent Timeout already committed in a placeholder state. We
+          // need to handle this promise immediately. In other words, we
+          // should never suspend inside a tree that already expired.
+          earliestTimeoutMs = 0;
+          break searchForEarliestTimeout;
+        }
+        var timeoutPropMs = _workInProgress.pendingProps.ms;
+        if (typeof timeoutPropMs === "number") {
+          if (timeoutPropMs <= 0) {
+            earliestTimeoutMs = 0;
+            break searchForEarliestTimeout;
+          } else if (
+            earliestTimeoutMs === -1 ||
+            timeoutPropMs < earliestTimeoutMs
+          ) {
+            earliestTimeoutMs = timeoutPropMs;
+          }
+        } else if (earliestTimeoutMs === -1) {
+          earliestTimeoutMs = remainingTimeMs;
+        }
+      }
+      _workInProgress = _workInProgress.return;
+    } while (_workInProgress !== null);
 
-  function isEmpty() {
-    return index === -1;
-  }
+    // Compute the remaining time until the timeout.
+    var msUntilTimeout = earliestTimeoutMs - elapsedMs;
 
-  function pop(cursor, fiber) {
-    if (index < 0) {
-      {
-        warning(false, "Unexpected pop.");
-      }
+    if (renderExpirationTime === Never || msUntilTimeout > 0) {
+      // There's still time remaining.
+      markTimeout(root, thenable, msUntilTimeout, renderExpirationTime);
+      var onResolveOrReject = function() {
+        retrySuspendedRoot(root, renderExpirationTime);
+      };
+      thenable.then(onResolveOrReject, onResolveOrReject);
+      return;
+    } else {
+      // No time remaining. Need to fallback to placeholder.
+      // Find the nearest timeout that can be retried.
+      _workInProgress = returnFiber;
+      do {
+        switch (_workInProgress.tag) {
+          case HostRoot: {
+            // The root expired, but no fallback was provided. Throw a
+            // helpful error.
+            var message =
+              renderExpirationTime === Sync
+                ? "A synchronous update was suspended, but no fallback UI " +
+                  "was provided."
+                : "An update was suspended for longer than the timeout, " +
+                  "but no fallback UI was provided.";
+            value = new Error(message);
+            break;
+          }
+          case TimeoutComponent: {
+            if ((_workInProgress.effectTag & DidCapture) === NoEffect) {
+              _workInProgress.effectTag |= ShouldCapture;
+              var _onResolveOrReject = schedulePing.bind(null, _workInProgress);
+              thenable.then(_onResolveOrReject, _onResolveOrReject);
+              return;
+            }
+            // Already captured during this render. Continue to the next
+            // Timeout ancestor.
+            break;
+          }
+        }
+        _workInProgress = _workInProgress.return;
+      } while (_workInProgress !== null);
+    }
+  } else {
+    // This is an error.
+    markError(root);
+    if (
+      // Retry (at the same priority) one more time before handling the error.
+      // The retry will flush synchronously. (Unless we're already rendering
+      // synchronously, in which case move to the next check.)
+      (!root.didError && renderExpirationTime !== Sync) ||
+      // There's lower priority work. If so, it may have the effect of fixing
+      // the exception that was just thrown.
+      hasLowerPriorityWork(root, renderExpirationTime)
+    ) {
       return;
     }
+  }
 
-    {
-      if (fiber !== fiberStack[index]) {
-        warning(false, "Unexpected Fiber popped.");
+  // We didn't find a boundary that could handle this type of exception. Start
+  // over and traverse parent path again, this time treating the exception
+  // as an error.
+  value = createCapturedValue(value, sourceFiber);
+  var workInProgress = returnFiber;
+  do {
+    switch (workInProgress.tag) {
+      case HostRoot: {
+        var _errorInfo = value;
+        workInProgress.effectTag |= ShouldCapture;
+        var update = createRootErrorUpdate(
+          workInProgress,
+          _errorInfo,
+          renderExpirationTime
+        );
+        enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
+        return;
       }
+      case ClassComponent:
+        // Capture and retry
+        var errorInfo = value;
+        var ctor = workInProgress.type;
+        var instance = workInProgress.stateNode;
+        if (
+          (workInProgress.effectTag & DidCapture) === NoEffect &&
+          ((typeof ctor.getDerivedStateFromCatch === "function" &&
+            enableGetDerivedStateFromCatch) ||
+            (instance !== null &&
+              typeof instance.componentDidCatch === "function" &&
+              !isAlreadyFailedLegacyErrorBoundary(instance)))
+        ) {
+          workInProgress.effectTag |= ShouldCapture;
+          // Schedule the error boundary to re-render using updated state
+          var _update = createClassErrorUpdate(
+            workInProgress,
+            errorInfo,
+            renderExpirationTime
+          );
+          enqueueCapturedUpdate(workInProgress, _update, renderExpirationTime);
+          return;
+        }
+        break;
+      default:
+        break;
     }
+    workInProgress = workInProgress.return;
+  } while (workInProgress !== null);
+}
 
-    cursor.current = valueStack[index];
-
-    valueStack[index] = null;
-
-    {
-      fiberStack[index] = null;
+function unwindWork(workInProgress, renderExpirationTime) {
+  if (enableProfilerTimer) {
+    if (workInProgress.mode & ProfileMode) {
+      recordElapsedActualRenderTime(workInProgress);
     }
-
-    index--;
   }
 
-  function push(cursor, value, fiber) {
-    index++;
-
-    valueStack[index] = cursor.current;
-
-    {
-      fiberStack[index] = fiber;
+  switch (workInProgress.tag) {
+    case ClassComponent: {
+      popContextProvider(workInProgress);
+      var effectTag = workInProgress.effectTag;
+      if (effectTag & ShouldCapture) {
+        workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+        return workInProgress;
+      }
+      return null;
     }
-
-    cursor.current = value;
-  }
-
-  function checkThatStackIsEmpty() {
-    {
-      if (index !== -1) {
-        warning(
-          false,
-          "Expected an empty stack. Something was not reset properly."
-        );
+    case HostRoot: {
+      popHostContainer(workInProgress);
+      popTopLevelContextObject(workInProgress);
+      var _effectTag = workInProgress.effectTag;
+      if (_effectTag & ShouldCapture) {
+        workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+        return workInProgress;
+      }
+      return null;
+    }
+    case HostComponent: {
+      popHostContext(workInProgress);
+      return null;
+    }
+    case TimeoutComponent: {
+      var _effectTag2 = workInProgress.effectTag;
+      if (_effectTag2 & ShouldCapture) {
+        workInProgress.effectTag = (_effectTag2 & ~ShouldCapture) | DidCapture;
+        return workInProgress;
       }
+      return null;
     }
+    case HostPortal:
+      popHostContainer(workInProgress);
+      return null;
+    case ContextProvider:
+      popProvider(workInProgress);
+      return null;
+    default:
+      return null;
   }
+}
 
-  function resetStackAfterFatalErrorInDev() {
-    {
-      index = -1;
-      valueStack.length = 0;
-      fiberStack.length = 0;
+function unwindInterruptedWork(interruptedWork) {
+  if (enableProfilerTimer) {
+    if (interruptedWork.mode & ProfileMode) {
+      // Resume in case we're picking up on work that was paused.
+      resumeActualRenderTimerIfPaused();
+      recordElapsedActualRenderTime(interruptedWork);
     }
   }
 
-  return {
-    createCursor: createCursor,
-    isEmpty: isEmpty,
-    pop: pop,
-    push: push,
-    checkThatStackIsEmpty: checkThatStackIsEmpty,
-    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
-  };
-};
+  switch (interruptedWork.tag) {
+    case ClassComponent: {
+      popContextProvider(interruptedWork);
+      break;
+    }
+    case HostRoot: {
+      popHostContainer(interruptedWork);
+      popTopLevelContextObject(interruptedWork);
+      break;
+    }
+    case HostComponent: {
+      popHostContext(interruptedWork);
+      break;
+    }
+    case HostPortal:
+      popHostContainer(interruptedWork);
+      break;
+    case ContextProvider:
+      popProvider(interruptedWork);
+      break;
+    default:
+      break;
+  }
+}
 
 var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
 var hasCaughtError = ReactErrorUtils.hasCaughtError;
@@ -12330,1821 +12140,1713 @@ var warnAboutInvalidUpdates = void 0;
   };
 }
 
-var ReactFiberScheduler = function(config) {
-  var now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit;
-
-  var stack = ReactFiberStack();
-  var hostContext = ReactFiberHostContext(config, stack);
-  var legacyContext = ReactFiberLegacyContext(stack);
-  var newContext = ReactFiberNewContext(stack, config.isPrimaryRenderer);
-  var profilerTimer = createProfilerTimer(now);
-  var popHostContext = hostContext.popHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popLegacyContextProvider = legacyContext.popContextProvider;
-  var popProvider = newContext.popProvider;
-
-  var hydrationContext = ReactFiberHydrationContext(config);
-
-  var _ReactFiberBeginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      profilerTimer,
-      recalculateCurrentTime
-    ),
-    beginWork = _ReactFiberBeginWork.beginWork;
-
-  var _ReactFiberCompleteWo = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext,
-      profilerTimer
-    ),
-    completeWork = _ReactFiberCompleteWo.completeWork;
-
-  var _ReactFiberUnwindWork = ReactFiberUnwindWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      recalculateCurrentTime,
-      markLegacyErrorBoundaryAsFailed,
-      isAlreadyFailedLegacyErrorBoundary,
-      onUncaughtError,
-      profilerTimer,
-      suspendRoot,
-      retrySuspendedRoot
-    ),
-    throwException = _ReactFiberUnwindWork.throwException,
-    unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork,
-    createRootErrorUpdate = _ReactFiberUnwindWork.createRootErrorUpdate,
-    createClassErrorUpdate = _ReactFiberUnwindWork.createClassErrorUpdate;
-
-  var _ReactFiberCommitWork = ReactFiberCommitWork(
-      config,
-      onCommitPhaseError,
-      scheduleWork,
-      computeExpirationForFiber,
-      markLegacyErrorBoundaryAsFailed,
-      recalculateCurrentTime
-    ),
-    commitBeforeMutationLifeCycles =
-      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
-    commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
-    commitPlacement = _ReactFiberCommitWork.commitPlacement,
-    commitDeletion = _ReactFiberCommitWork.commitDeletion,
-    commitWork = _ReactFiberCommitWork.commitWork,
-    commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
-    commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
-    commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
-
-  var checkActualRenderTimeStackEmpty =
-      profilerTimer.checkActualRenderTimeStackEmpty,
-    pauseActualRenderTimerIfRunning =
-      profilerTimer.pauseActualRenderTimerIfRunning,
-    recordElapsedBaseRenderTimeIfRunning =
-      profilerTimer.recordElapsedBaseRenderTimeIfRunning,
-    resetActualRenderTimer = profilerTimer.resetActualRenderTimer,
-    resumeActualRenderTimerIfPaused =
-      profilerTimer.resumeActualRenderTimerIfPaused,
-    startBaseRenderTimer = profilerTimer.startBaseRenderTimer,
-    stopBaseRenderTimerIfRunning = profilerTimer.stopBaseRenderTimerIfRunning;
-
-  // Represents the current time in ms.
-
-  var originalStartTimeMs = now();
-  var mostRecentCurrentTime = msToExpirationTime(0);
-  var mostRecentCurrentTimeMs = originalStartTimeMs;
-
-  // Used to ensure computeUniqueAsyncExpiration is monotonically increases.
-  var lastUniqueAsyncExpiration = 0;
-
-  // Represents the expiration time that incoming updates should use. (If this
-  // is NoWork, use the default strategy: async updates in async mode, sync
-  // updates in sync mode.)
-  var expirationContext = NoWork;
-
-  var isWorking = false;
-
-  // The next work in progress fiber that we're currently working on.
-  var nextUnitOfWork = null;
-  var nextRoot = null;
-  // The time at which we're currently rendering work.
-  var nextRenderExpirationTime = NoWork;
-  var nextLatestTimeoutMs = -1;
-  var nextRenderIsExpired = false;
-
-  // The next fiber with an effect that we're currently committing.
-  var nextEffect = null;
-
-  var isCommitting = false;
-
-  var isRootReadyForCommit = false;
-
-  var legacyErrorBoundariesThatAlreadyFailed = null;
-
-  // Used for performance tracking.
-  var interruptedBy = null;
-
-  var stashedWorkInProgressProperties = void 0;
-  var replayUnitOfWork = void 0;
-  var isReplayingFailedUnitOfWork = void 0;
-  var originalReplayError = void 0;
-  var rethrowOriginalError = void 0;
-  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-    stashedWorkInProgressProperties = null;
-    isReplayingFailedUnitOfWork = false;
-    originalReplayError = null;
-    replayUnitOfWork = function(failedUnitOfWork, thrownValue, isAsync) {
-      if (
-        thrownValue !== null &&
-        typeof thrownValue === "object" &&
-        typeof thrownValue.then === "function"
-      ) {
-        // Don't replay promises. Treat everything else like an error.
-        // TODO: Need to figure out a different strategy if/when we add
-        // support for catching other types.
-        return;
-      }
+// Represents the current time in ms.
+var originalStartTimeMs = now();
+var mostRecentCurrentTime = msToExpirationTime(0);
+var mostRecentCurrentTimeMs = originalStartTimeMs;
 
-      // Restore the original state of the work-in-progress
-      if (stashedWorkInProgressProperties === null) {
-        // This should never happen. Don't throw because this code is DEV-only.
-        warning(
-          false,
-          "Could not replay rendering after an error. This is likely a bug in React. " +
-            "Please file an issue."
-        );
-        return;
-      }
-      assignFiberPropertiesInDEV(
-        failedUnitOfWork,
-        stashedWorkInProgressProperties
-      );
+// Used to ensure computeUniqueAsyncExpiration is monotonically increases.
+var lastUniqueAsyncExpiration = 0;
 
-      switch (failedUnitOfWork.tag) {
-        case HostRoot:
-          popHostContainer(failedUnitOfWork);
-          popTopLevelLegacyContextObject(failedUnitOfWork);
-          break;
-        case HostComponent:
-          popHostContext(failedUnitOfWork);
-          break;
-        case ClassComponent:
-          popLegacyContextProvider(failedUnitOfWork);
-          break;
-        case HostPortal:
-          popHostContainer(failedUnitOfWork);
-          break;
-        case ContextProvider:
-          popProvider(failedUnitOfWork);
-          break;
-      }
-      // Replay the begin phase.
-      isReplayingFailedUnitOfWork = true;
-      originalReplayError = thrownValue;
-      invokeGuardedCallback$2(null, workLoop, null, isAsync);
-      isReplayingFailedUnitOfWork = false;
-      originalReplayError = null;
-      if (hasCaughtError()) {
-        clearCaughtError();
+// Represents the expiration time that incoming updates should use. (If this
+// is NoWork, use the default strategy: async updates in async mode, sync
+// updates in sync mode.)
+var expirationContext = NoWork;
 
-        if (enableProfilerTimer) {
-          // Stop "base" render timer again (after the re-thrown error).
-          stopBaseRenderTimerIfRunning();
-        }
-      } else {
-        // If the begin phase did not fail the second time, set this pointer
-        // back to the original value.
-        nextUnitOfWork = failedUnitOfWork;
-      }
-    };
-    rethrowOriginalError = function() {
-      throw originalReplayError;
-    };
-  }
+var isWorking = false;
 
-  function resetStack() {
-    if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork.return;
-      while (interruptedWork !== null) {
-        unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork.return;
-      }
-    }
+// The next work in progress fiber that we're currently working on.
+var nextUnitOfWork = null;
+var nextRoot = null;
+// The time at which we're currently rendering work.
+var nextRenderExpirationTime = NoWork;
+var nextLatestTimeoutMs = -1;
+var nextRenderDidError = false;
 
-    {
-      ReactStrictModeWarnings.discardPendingWarnings();
-      stack.checkThatStackIsEmpty();
-    }
+// The next fiber with an effect that we're currently committing.
+var nextEffect = null;
 
-    nextRoot = null;
-    nextRenderExpirationTime = NoWork;
-    nextLatestTimeoutMs = -1;
-    nextRenderIsExpired = false;
-    nextUnitOfWork = null;
+var isCommitting$1 = false;
 
-    isRootReadyForCommit = false;
-  }
+var legacyErrorBoundariesThatAlreadyFailed = null;
 
-  function commitAllHostEffects() {
-    while (nextEffect !== null) {
-      {
-        ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
-      }
-      recordEffect();
+// Used for performance tracking.
+var interruptedBy = null;
+
+var stashedWorkInProgressProperties = void 0;
+var replayUnitOfWork = void 0;
+var isReplayingFailedUnitOfWork = void 0;
+var originalReplayError = void 0;
+var rethrowOriginalError = void 0;
+if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+  stashedWorkInProgressProperties = null;
+  isReplayingFailedUnitOfWork = false;
+  originalReplayError = null;
+  replayUnitOfWork = function(failedUnitOfWork, thrownValue, isYieldy) {
+    if (
+      thrownValue !== null &&
+      typeof thrownValue === "object" &&
+      typeof thrownValue.then === "function"
+    ) {
+      // Don't replay promises. Treat everything else like an error.
+      // TODO: Need to figure out a different strategy if/when we add
+      // support for catching other types.
+      return;
+    }
 
-      var effectTag = nextEffect.effectTag;
+    // Restore the original state of the work-in-progress
+    if (stashedWorkInProgressProperties === null) {
+      // This should never happen. Don't throw because this code is DEV-only.
+      warning(
+        false,
+        "Could not replay rendering after an error. This is likely a bug in React. " +
+          "Please file an issue."
+      );
+      return;
+    }
+    assignFiberPropertiesInDEV(
+      failedUnitOfWork,
+      stashedWorkInProgressProperties
+    );
 
-      if (effectTag & ContentReset) {
-        commitResetTextContent(nextEffect);
-      }
+    switch (failedUnitOfWork.tag) {
+      case HostRoot:
+        popHostContainer(failedUnitOfWork);
+        popTopLevelContextObject(failedUnitOfWork);
+        break;
+      case HostComponent:
+        popHostContext(failedUnitOfWork);
+        break;
+      case ClassComponent:
+        popContextProvider(failedUnitOfWork);
+        break;
+      case HostPortal:
+        popHostContainer(failedUnitOfWork);
+        break;
+      case ContextProvider:
+        popProvider(failedUnitOfWork);
+        break;
+    }
+    // Replay the begin phase.
+    isReplayingFailedUnitOfWork = true;
+    originalReplayError = thrownValue;
+    invokeGuardedCallback$2(null, workLoop, null, isYieldy);
+    isReplayingFailedUnitOfWork = false;
+    originalReplayError = null;
+    if (hasCaughtError()) {
+      clearCaughtError();
 
-      if (effectTag & Ref) {
-        var current = nextEffect.alternate;
-        if (current !== null) {
-          commitDetachRef(current);
+      if (enableProfilerTimer) {
+        if (failedUnitOfWork.mode & ProfileMode) {
+          recordElapsedActualRenderTime(failedUnitOfWork);
         }
-      }
 
-      // The following switch statement is only concerned about placement,
-      // updates, and deletions. To avoid needing to add a case for every
-      // possible bitmap value, we remove the secondary effects from the
-      // effect tag and switch on that value.
-      var primaryEffectTag = effectTag & (Placement | Update | Deletion);
-      switch (primaryEffectTag) {
-        case Placement: {
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          // TODO: findDOMNode doesn't rely on this any more but isMounted
-          // does and isMounted is deprecated anyway so we should be able
-          // to kill this.
-          nextEffect.effectTag &= ~Placement;
-          break;
-        }
-        case PlacementAndUpdate: {
-          // Placement
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          nextEffect.effectTag &= ~Placement;
-
-          // Update
-          var _current = nextEffect.alternate;
-          commitWork(_current, nextEffect);
-          break;
-        }
-        case Update: {
-          var _current2 = nextEffect.alternate;
-          commitWork(_current2, nextEffect);
-          break;
-        }
-        case Deletion: {
-          commitDeletion(nextEffect);
-          break;
-        }
+        // Stop "base" render timer again (after the re-thrown error).
+        stopBaseRenderTimerIfRunning();
       }
-      nextEffect = nextEffect.nextEffect;
+    } else {
+      // If the begin phase did not fail the second time, set this pointer
+      // back to the original value.
+      nextUnitOfWork = failedUnitOfWork;
     }
+  };
+  rethrowOriginalError = function() {
+    throw originalReplayError;
+  };
+}
 
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
+function resetStack() {
+  if (nextUnitOfWork !== null) {
+    var interruptedWork = nextUnitOfWork.return;
+    while (interruptedWork !== null) {
+      unwindInterruptedWork(interruptedWork);
+      interruptedWork = interruptedWork.return;
     }
   }
 
-  function commitBeforeMutationLifecycles() {
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
+  {
+    ReactStrictModeWarnings.discardPendingWarnings();
+    checkThatStackIsEmpty();
+  }
 
-      if (effectTag & Snapshot) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitBeforeMutationLifeCycles(current, nextEffect);
-      }
+  nextRoot = null;
+  nextRenderExpirationTime = NoWork;
+  nextLatestTimeoutMs = -1;
+  nextRenderDidError = false;
+  nextUnitOfWork = null;
+}
 
-      // Don't cleanup effects yet;
-      // This will be done by commitAllLifeCycles()
-      nextEffect = nextEffect.nextEffect;
+function commitAllHostEffects() {
+  while (nextEffect !== null) {
+    {
+      ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
     }
-  }
+    recordEffect();
 
-  function commitAllLifeCycles(
-    finishedRoot,
-    currentTime,
-    committedExpirationTime
-  ) {
-    {
-      ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
+    var effectTag = nextEffect.effectTag;
+
+    if (effectTag & ContentReset) {
+      commitResetTextContent(nextEffect);
+    }
 
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.flushPendingDeprecationWarnings();
+    if (effectTag & Ref) {
+      var current = nextEffect.alternate;
+      if (current !== null) {
+        commitDetachRef(current);
       }
     }
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
 
-      if (effectTag & (Update | Callback)) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitLifeCycles(
-          finishedRoot,
-          current,
-          nextEffect,
-          currentTime,
-          committedExpirationTime
-        );
+    // The following switch statement is only concerned about placement,
+    // updates, and deletions. To avoid needing to add a case for every
+    // possible bitmap value, we remove the secondary effects from the
+    // effect tag and switch on that value.
+    var primaryEffectTag = effectTag & (Placement | Update | Deletion);
+    switch (primaryEffectTag) {
+      case Placement: {
+        commitPlacement(nextEffect);
+        // Clear the "placement" from effect tag so that we know that this is inserted, before
+        // any life-cycles like componentDidMount gets called.
+        // TODO: findDOMNode doesn't rely on this any more but isMounted
+        // does and isMounted is deprecated anyway so we should be able
+        // to kill this.
+        nextEffect.effectTag &= ~Placement;
+        break;
       }
+      case PlacementAndUpdate: {
+        // Placement
+        commitPlacement(nextEffect);
+        // Clear the "placement" from effect tag so that we know that this is inserted, before
+        // any life-cycles like componentDidMount gets called.
+        nextEffect.effectTag &= ~Placement;
 
-      if (effectTag & Ref) {
-        recordEffect();
-        commitAttachRef(nextEffect);
+        // Update
+        var _current = nextEffect.alternate;
+        commitWork(_current, nextEffect);
+        break;
       }
+      case Update: {
+        var _current2 = nextEffect.alternate;
+        commitWork(_current2, nextEffect);
+        break;
+      }
+      case Deletion: {
+        commitDeletion(nextEffect);
+        break;
+      }
+    }
+    nextEffect = nextEffect.nextEffect;
+  }
+
+  {
+    ReactDebugCurrentFiber.resetCurrentFiber();
+  }
+}
 
-      var next = nextEffect.nextEffect;
-      // Ensure that we clean these up so that we don't accidentally keep them.
-      // I'm not actually sure this matters because we can't reset firstEffect
-      // and lastEffect since they're on every node, not just the effectful
-      // ones. So we have to clean everything as we reuse nodes anyway.
-      nextEffect.nextEffect = null;
-      // Ensure that we reset the effectTag here so that we can rely on effect
-      // tags to reason about the current life-cycle.
-      nextEffect = next;
+function commitBeforeMutationLifecycles() {
+  while (nextEffect !== null) {
+    var effectTag = nextEffect.effectTag;
+
+    if (effectTag & Snapshot) {
+      recordEffect();
+      var current = nextEffect.alternate;
+      commitBeforeMutationLifeCycles(current, nextEffect);
     }
+
+    // Don't cleanup effects yet;
+    // This will be done by commitAllLifeCycles()
+    nextEffect = nextEffect.nextEffect;
   }
+}
 
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      legacyErrorBoundariesThatAlreadyFailed !== null &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
+function commitAllLifeCycles(
+  finishedRoot,
+  currentTime,
+  committedExpirationTime
+) {
+  {
+    ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
+
+    if (warnAboutDeprecatedLifecycles) {
+      ReactStrictModeWarnings.flushPendingDeprecationWarnings();
+    }
+
+    if (warnAboutLegacyContextAPI) {
+      ReactStrictModeWarnings.flushLegacyContextWarning();
+    }
   }
+  while (nextEffect !== null) {
+    var effectTag = nextEffect.effectTag;
 
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    if (legacyErrorBoundariesThatAlreadyFailed === null) {
-      legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
-    } else {
-      legacyErrorBoundariesThatAlreadyFailed.add(instance);
+    if (effectTag & (Update | Callback)) {
+      recordEffect();
+      var current = nextEffect.alternate;
+      commitLifeCycles(
+        finishedRoot,
+        current,
+        nextEffect,
+        currentTime,
+        committedExpirationTime
+      );
+    }
+
+    if (effectTag & Ref) {
+      recordEffect();
+      commitAttachRef(nextEffect);
     }
+
+    var next = nextEffect.nextEffect;
+    // Ensure that we clean these up so that we don't accidentally keep them.
+    // I'm not actually sure this matters because we can't reset firstEffect
+    // and lastEffect since they're on every node, not just the effectful
+    // ones. So we have to clean everything as we reuse nodes anyway.
+    nextEffect.nextEffect = null;
+    // Ensure that we reset the effectTag here so that we can rely on effect
+    // tags to reason about the current life-cycle.
+    nextEffect = next;
   }
+}
 
-  function commitRoot(finishedWork) {
-    isWorking = true;
-    isCommitting = true;
-    startCommitTimer();
+function isAlreadyFailedLegacyErrorBoundary(instance) {
+  return (
+    legacyErrorBoundariesThatAlreadyFailed !== null &&
+    legacyErrorBoundariesThatAlreadyFailed.has(instance)
+  );
+}
 
-    var root = finishedWork.stateNode;
-    invariant(
-      root.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug " +
-        "related to the return field. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-    var committedExpirationTime = root.pendingCommitExpirationTime;
-    invariant(
-      committedExpirationTime !== NoWork,
-      "Cannot commit an incomplete root. This error is likely caused by a " +
-        "bug in React. Please file an issue."
-    );
-    root.pendingCommitExpirationTime = NoWork;
+function markLegacyErrorBoundaryAsFailed(instance) {
+  if (legacyErrorBoundariesThatAlreadyFailed === null) {
+    legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
+  } else {
+    legacyErrorBoundariesThatAlreadyFailed.add(instance);
+  }
+}
 
-    var currentTime = recalculateCurrentTime();
+function commitRoot(root, finishedWork) {
+  isWorking = true;
+  isCommitting$1 = true;
+  startCommitTimer();
 
-    // Reset this to null before calling lifecycles
-    ReactCurrentOwner.current = null;
-
-    var firstEffect = void 0;
-    if (finishedWork.effectTag > PerformedWork) {
-      // A fiber's effect list consists only of its children, not itself. So if
-      // the root has an effect, we need to add it to the end of the list. The
-      // resulting list is the set that would belong to the root's parent, if
-      // it had one; that is, all the effects in the tree including the root.
-      if (finishedWork.lastEffect !== null) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        firstEffect = finishedWork.firstEffect;
-      } else {
-        firstEffect = finishedWork;
-      }
-    } else {
-      // There is no effect on the root.
+  invariant(
+    root.current !== finishedWork,
+    "Cannot commit the same tree as before. This is probably a bug " +
+      "related to the return field. This error is likely caused by a bug " +
+      "in React. Please file an issue."
+  );
+  var committedExpirationTime = root.pendingCommitExpirationTime;
+  invariant(
+    committedExpirationTime !== NoWork,
+    "Cannot commit an incomplete root. This error is likely caused by a " +
+      "bug in React. Please file an issue."
+  );
+  root.pendingCommitExpirationTime = NoWork;
+
+  // Update the pending priority levels to account for the work that we are
+  // about to commit. This needs to happen before calling the lifecycles, since
+  // they may schedule additional updates.
+  var earliestRemainingTime = finishedWork.expirationTime;
+  var currentTime = recalculateCurrentTime();
+  markCommittedPriorityLevels(root, currentTime, earliestRemainingTime);
+
+  // Reset this to null before calling lifecycles
+  ReactCurrentOwner.current = null;
+
+  var firstEffect = void 0;
+  if (finishedWork.effectTag > PerformedWork) {
+    // A fiber's effect list consists only of its children, not itself. So if
+    // the root has an effect, we need to add it to the end of the list. The
+    // resulting list is the set that would belong to the root's parent, if
+    // it had one; that is, all the effects in the tree including the root.
+    if (finishedWork.lastEffect !== null) {
+      finishedWork.lastEffect.nextEffect = finishedWork;
       firstEffect = finishedWork.firstEffect;
+    } else {
+      firstEffect = finishedWork;
     }
+  } else {
+    // There is no effect on the root.
+    firstEffect = finishedWork.firstEffect;
+  }
 
-    prepareForCommit(root.containerInfo);
+  prepareForCommit(root.containerInfo);
 
-    // Invoke instances of getSnapshotBeforeUpdate before mutation.
-    nextEffect = firstEffect;
-    startCommitSnapshotEffectsTimer();
-    while (nextEffect !== null) {
-      var didError = false;
-      var error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
-        if (hasCaughtError()) {
-          didError = true;
-          error = clearCaughtError();
-        }
+  // Invoke instances of getSnapshotBeforeUpdate before mutation.
+  nextEffect = firstEffect;
+  startCommitSnapshotEffectsTimer();
+  while (nextEffect !== null) {
+    var didError = false;
+    var error = void 0;
+    {
+      invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
+      if (hasCaughtError()) {
+        didError = true;
+        error = clearCaughtError();
       }
-      if (didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
+    }
+    if (didError) {
+      invariant(
+        nextEffect !== null,
+        "Should have next effect. This error is likely caused by a bug " +
+          "in React. Please file an issue."
+      );
+      captureCommitPhaseError(nextEffect, error);
+      // Clean-up
+      if (nextEffect !== null) {
+        nextEffect = nextEffect.nextEffect;
       }
     }
-    stopCommitSnapshotEffectsTimer();
+  }
+  stopCommitSnapshotEffectsTimer();
 
-    // Commit all the side-effects within a tree. We'll do this in two passes.
-    // The first pass performs all the host insertions, updates, deletions and
-    // ref unmounts.
-    nextEffect = firstEffect;
-    startCommitHostEffectsTimer();
-    while (nextEffect !== null) {
-      var _didError = false;
-      var _error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitAllHostEffects, null);
-        if (hasCaughtError()) {
-          _didError = true;
-          _error = clearCaughtError();
-        }
+  if (enableProfilerTimer) {
+    // Mark the current commit time to be shared by all Profilers in this batch.
+    // This enables them to be grouped later.
+    recordCommitTime();
+  }
+
+  // Commit all the side-effects within a tree. We'll do this in two passes.
+  // The first pass performs all the host insertions, updates, deletions and
+  // ref unmounts.
+  nextEffect = firstEffect;
+  startCommitHostEffectsTimer();
+  while (nextEffect !== null) {
+    var _didError = false;
+    var _error = void 0;
+    {
+      invokeGuardedCallback$2(null, commitAllHostEffects, null);
+      if (hasCaughtError()) {
+        _didError = true;
+        _error = clearCaughtError();
       }
-      if (_didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
+    }
+    if (_didError) {
+      invariant(
+        nextEffect !== null,
+        "Should have next effect. This error is likely caused by a bug " +
+          "in React. Please file an issue."
+      );
+      captureCommitPhaseError(nextEffect, _error);
+      // Clean-up
+      if (nextEffect !== null) {
+        nextEffect = nextEffect.nextEffect;
       }
     }
-    stopCommitHostEffectsTimer();
+  }
+  stopCommitHostEffectsTimer();
 
-    resetAfterCommit(root.containerInfo);
+  resetAfterCommit(root.containerInfo);
 
-    // The work-in-progress tree is now the current tree. This must come after
-    // the first pass of the commit phase, so that the previous tree is still
-    // current during componentWillUnmount, but before the second pass, so that
-    // the finished work is current during componentDidMount/Update.
-    root.current = finishedWork;
+  // The work-in-progress tree is now the current tree. This must come after
+  // the first pass of the commit phase, so that the previous tree is still
+  // current during componentWillUnmount, but before the second pass, so that
+  // the finished work is current during componentDidMount/Update.
+  root.current = finishedWork;
 
-    // In the second pass we'll perform all life-cycles and ref callbacks.
-    // Life-cycles happen as a separate pass so that all placements, updates,
-    // and deletions in the entire tree have already been invoked.
-    // This pass also triggers any renderer-specific initial effects.
-    nextEffect = firstEffect;
-    startCommitLifeCyclesTimer();
-    while (nextEffect !== null) {
-      var _didError2 = false;
-      var _error2 = void 0;
-      {
-        invokeGuardedCallback$2(
-          null,
-          commitAllLifeCycles,
-          null,
-          root,
-          currentTime,
-          committedExpirationTime
-        );
-        if (hasCaughtError()) {
-          _didError2 = true;
-          _error2 = clearCaughtError();
-        }
-      }
-      if (_didError2) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error2);
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
+  // In the second pass we'll perform all life-cycles and ref callbacks.
+  // Life-cycles happen as a separate pass so that all placements, updates,
+  // and deletions in the entire tree have already been invoked.
+  // This pass also triggers any renderer-specific initial effects.
+  nextEffect = firstEffect;
+  startCommitLifeCyclesTimer();
+  while (nextEffect !== null) {
+    var _didError2 = false;
+    var _error2 = void 0;
+    {
+      invokeGuardedCallback$2(
+        null,
+        commitAllLifeCycles,
+        null,
+        root,
+        currentTime,
+        committedExpirationTime
+      );
+      if (hasCaughtError()) {
+        _didError2 = true;
+        _error2 = clearCaughtError();
       }
     }
-
-    if (enableProfilerTimer) {
-      {
-        checkActualRenderTimeStackEmpty();
+    if (_didError2) {
+      invariant(
+        nextEffect !== null,
+        "Should have next effect. This error is likely caused by a bug " +
+          "in React. Please file an issue."
+      );
+      captureCommitPhaseError(nextEffect, _error2);
+      if (nextEffect !== null) {
+        nextEffect = nextEffect.nextEffect;
       }
-      resetActualRenderTimer();
     }
+  }
 
-    isCommitting = false;
-    isWorking = false;
-    stopCommitLifeCyclesTimer();
-    stopCommitTimer();
-    if (typeof onCommitRoot === "function") {
-      onCommitRoot(finishedWork.stateNode);
-    }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
+  if (enableProfilerTimer) {
+    {
+      checkActualRenderTimeStackEmpty();
     }
+    resetActualRenderTimer();
+  }
 
-    markCommittedPriorityLevels(root, currentTime, root.current.expirationTime);
-    var remainingTime = findNextPendingPriorityLevel(root);
-    if (remainingTime === NoWork) {
-      // If there's no remaining work, we can clear the set of already failed
-      // error boundaries.
-      legacyErrorBoundariesThatAlreadyFailed = null;
-    }
-    return remainingTime;
+  isCommitting$1 = false;
+  isWorking = false;
+  stopCommitLifeCyclesTimer();
+  stopCommitTimer();
+  if (typeof onCommitRoot === "function") {
+    onCommitRoot(finishedWork.stateNode);
+  }
+  if (true && ReactFiberInstrumentation_1.debugTool) {
+    ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
   }
 
-  function resetExpirationTime(workInProgress, renderTime) {
-    if (renderTime !== Never && workInProgress.expirationTime === Never) {
-      // The children of this component are hidden. Don't bubble their
-      // expiration times.
-      return;
-    }
+  var expirationTime = root.expirationTime;
+  if (expirationTime === NoWork) {
+    // If there's no remaining work, we can clear the set of already failed
+    // error boundaries.
+    legacyErrorBoundariesThatAlreadyFailed = null;
+  }
+  onCommit(root, expirationTime);
+}
 
-    // Check for pending updates.
-    var newExpirationTime = NoWork;
-    switch (workInProgress.tag) {
-      case HostRoot:
-      case ClassComponent: {
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null) {
-          newExpirationTime = updateQueue.expirationTime;
-        }
+function resetExpirationTime(workInProgress, renderTime) {
+  if (renderTime !== Never && workInProgress.expirationTime === Never) {
+    // The children of this component are hidden. Don't bubble their
+    // expiration times.
+    return;
+  }
+
+  // Check for pending updates.
+  var newExpirationTime = NoWork;
+  switch (workInProgress.tag) {
+    case HostRoot:
+    case ClassComponent: {
+      var updateQueue = workInProgress.updateQueue;
+      if (updateQueue !== null) {
+        newExpirationTime = updateQueue.expirationTime;
       }
     }
+  }
 
-    // TODO: Calls need to visit stateNode
+  // TODO: Calls need to visit stateNode
 
-    // Bubble up the earliest expiration time.
-    // (And "base" render timers if that feature flag is enabled)
-    if (enableProfilerTimer && workInProgress.mode & ProfileMode) {
-      var treeBaseTime = workInProgress.selfBaseTime;
-      var child = workInProgress.child;
-      while (child !== null) {
-        treeBaseTime += child.treeBaseTime;
-        if (
-          child.expirationTime !== NoWork &&
-          (newExpirationTime === NoWork ||
-            newExpirationTime > child.expirationTime)
-        ) {
-          newExpirationTime = child.expirationTime;
-        }
-        child = child.sibling;
+  // Bubble up the earliest expiration time.
+  // (And "base" render timers if that feature flag is enabled)
+  if (enableProfilerTimer && workInProgress.mode & ProfileMode) {
+    var treeBaseTime = workInProgress.selfBaseTime;
+    var child = workInProgress.child;
+    while (child !== null) {
+      treeBaseTime += child.treeBaseTime;
+      if (
+        child.expirationTime !== NoWork &&
+        (newExpirationTime === NoWork ||
+          newExpirationTime > child.expirationTime)
+      ) {
+        newExpirationTime = child.expirationTime;
       }
-      workInProgress.treeBaseTime = treeBaseTime;
-    } else {
-      var _child = workInProgress.child;
-      while (_child !== null) {
-        if (
-          _child.expirationTime !== NoWork &&
-          (newExpirationTime === NoWork ||
-            newExpirationTime > _child.expirationTime)
-        ) {
-          newExpirationTime = _child.expirationTime;
-        }
-        _child = _child.sibling;
+      child = child.sibling;
+    }
+    workInProgress.treeBaseTime = treeBaseTime;
+  } else {
+    var _child = workInProgress.child;
+    while (_child !== null) {
+      if (
+        _child.expirationTime !== NoWork &&
+        (newExpirationTime === NoWork ||
+          newExpirationTime > _child.expirationTime)
+      ) {
+        newExpirationTime = _child.expirationTime;
       }
+      _child = _child.sibling;
     }
-
-    workInProgress.expirationTime = newExpirationTime;
   }
 
-  function completeUnitOfWork(workInProgress) {
-    // Attempt to complete the current unit of work, then move to the
-    // next sibling. If there are no more siblings, return to the
-    // parent fiber.
-    while (true) {
-      // The current, flushed, state of this fiber is the alternate.
-      // Ideally nothing should rely on this, but relying on it here
-      // means that we don't need an additional field on the work in
-      // progress.
-      var current = workInProgress.alternate;
+  workInProgress.expirationTime = newExpirationTime;
+}
+
+function completeUnitOfWork(workInProgress) {
+  // Attempt to complete the current unit of work, then move to the
+  // next sibling. If there are no more siblings, return to the
+  // parent fiber.
+  while (true) {
+    // The current, flushed, state of this fiber is the alternate.
+    // Ideally nothing should rely on this, but relying on it here
+    // means that we don't need an additional field on the work in
+    // progress.
+    var current = workInProgress.alternate;
+    {
+      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+    }
+
+    var returnFiber = workInProgress.return;
+    var siblingFiber = workInProgress.sibling;
+
+    if ((workInProgress.effectTag & Incomplete) === NoEffect) {
+      // This fiber completed.
+      var next = completeWork(
+        current,
+        workInProgress,
+        nextRenderExpirationTime
+      );
+      stopWorkTimer(workInProgress);
+      resetExpirationTime(workInProgress, nextRenderExpirationTime);
       {
-        ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+        ReactDebugCurrentFiber.resetCurrentFiber();
       }
 
-      var returnFiber = workInProgress.return;
-      var siblingFiber = workInProgress.sibling;
-
-      if ((workInProgress.effectTag & Incomplete) === NoEffect) {
-        // This fiber completed.
-        var next = completeWork(
-          current,
-          workInProgress,
-          nextRenderExpirationTime
-        );
+      if (next !== null) {
         stopWorkTimer(workInProgress);
-        resetExpirationTime(workInProgress, nextRenderExpirationTime);
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
         }
+        // If completing this work spawned new work, do that next. We'll come
+        // back here again.
+        return next;
+      }
 
-        if (next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
+      if (
+        returnFiber !== null &&
+        // Do not append effects to parents if a sibling failed to complete
+        (returnFiber.effectTag & Incomplete) === NoEffect
+      ) {
+        // Append all the effects of the subtree and this fiber onto the effect
+        // list of the parent. The completion order of the children affects the
+        // side-effect order.
+        if (returnFiber.firstEffect === null) {
+          returnFiber.firstEffect = workInProgress.firstEffect;
+        }
+        if (workInProgress.lastEffect !== null) {
+          if (returnFiber.lastEffect !== null) {
+            returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
           }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          return next;
+          returnFiber.lastEffect = workInProgress.lastEffect;
         }
 
-        if (
-          returnFiber !== null &&
-          // Do not append effects to parents if a sibling failed to complete
-          (returnFiber.effectTag & Incomplete) === NoEffect
-        ) {
-          // Append all the effects of the subtree and this fiber onto the effect
-          // list of the parent. The completion order of the children affects the
-          // side-effect order.
-          if (returnFiber.firstEffect === null) {
-            returnFiber.firstEffect = workInProgress.firstEffect;
-          }
-          if (workInProgress.lastEffect !== null) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
-            }
-            returnFiber.lastEffect = workInProgress.lastEffect;
-          }
-
-          // If this fiber had side-effects, we append it AFTER the children's
-          // side-effects. We can perform certain side-effects earlier if
-          // needed, by doing multiple passes over the effect list. We don't want
-          // to schedule our own side-effect on our own list because if end up
-          // reusing children we'll schedule this effect onto itself since we're
-          // at the end.
-          var effectTag = workInProgress.effectTag;
-          // Skip both NoWork and PerformedWork tags when creating the effect list.
-          // PerformedWork effect is read by React DevTools but shouldn't be committed.
-          if (effectTag > PerformedWork) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress;
-            } else {
-              returnFiber.firstEffect = workInProgress;
-            }
-            returnFiber.lastEffect = workInProgress;
+        // If this fiber had side-effects, we append it AFTER the children's
+        // side-effects. We can perform certain side-effects earlier if
+        // needed, by doing multiple passes over the effect list. We don't want
+        // to schedule our own side-effect on our own list because if end up
+        // reusing children we'll schedule this effect onto itself since we're
+        // at the end.
+        var effectTag = workInProgress.effectTag;
+        // Skip both NoWork and PerformedWork tags when creating the effect list.
+        // PerformedWork effect is read by React DevTools but shouldn't be committed.
+        if (effectTag > PerformedWork) {
+          if (returnFiber.lastEffect !== null) {
+            returnFiber.lastEffect.nextEffect = workInProgress;
+          } else {
+            returnFiber.firstEffect = workInProgress;
           }
+          returnFiber.lastEffect = workInProgress;
         }
+      }
 
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
-        }
+      if (true && ReactFiberInstrumentation_1.debugTool) {
+        ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+      }
 
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
-        } else {
-          // We've reached the root.
-          isRootReadyForCommit = true;
-          return null;
-        }
+      if (siblingFiber !== null) {
+        // If there is more work to do in this returnFiber, do that next.
+        return siblingFiber;
+      } else if (returnFiber !== null) {
+        // If there's no more work in this returnFiber. Complete the returnFiber.
+        workInProgress = returnFiber;
+        continue;
       } else {
-        // This fiber did not complete because something threw. Pop values off
-        // the stack without entering the complete phase. If this is a boundary,
-        // capture values if possible.
-        var _next = unwindWork(
-          workInProgress,
-          nextRenderIsExpired,
-          nextRenderExpirationTime
-        );
-        // Because this fiber did not complete, don't reset its expiration time.
-        if (workInProgress.effectTag & DidCapture) {
-          // Restarting an error boundary
-          stopFailedWorkTimer(workInProgress);
-        } else {
-          stopWorkTimer(workInProgress);
-        }
-
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
-
-        if (_next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
-          }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          // Since we're restarting, remove anything that is not a host effect
-          // from the effect tag.
-          _next.effectTag &= HostEffectMask;
-          return _next;
-        }
+        // We've reached the root.
+        return null;
+      }
+    } else {
+      // This fiber did not complete because something threw. Pop values off
+      // the stack without entering the complete phase. If this is a boundary,
+      // capture values if possible.
+      var _next = unwindWork(workInProgress, nextRenderExpirationTime);
+      // Because this fiber did not complete, don't reset its expiration time.
+      if (workInProgress.effectTag & DidCapture) {
+        // Restarting an error boundary
+        stopFailedWorkTimer(workInProgress);
+      } else {
+        stopWorkTimer(workInProgress);
+      }
 
-        if (returnFiber !== null) {
-          // Mark the parent fiber as incomplete and clear its effect list.
-          returnFiber.firstEffect = returnFiber.lastEffect = null;
-          returnFiber.effectTag |= Incomplete;
-        }
+      {
+        ReactDebugCurrentFiber.resetCurrentFiber();
+      }
 
+      if (_next !== null) {
+        stopWorkTimer(workInProgress);
         if (true && ReactFiberInstrumentation_1.debugTool) {
           ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
         }
+        // If completing this work spawned new work, do that next. We'll come
+        // back here again.
+        // Since we're restarting, remove anything that is not a host effect
+        // from the effect tag.
+        _next.effectTag &= HostEffectMask;
+        return _next;
+      }
 
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
-        } else {
-          return null;
-        }
+      if (returnFiber !== null) {
+        // Mark the parent fiber as incomplete and clear its effect list.
+        returnFiber.firstEffect = returnFiber.lastEffect = null;
+        returnFiber.effectTag |= Incomplete;
+      }
+
+      if (true && ReactFiberInstrumentation_1.debugTool) {
+        ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+      }
+
+      if (siblingFiber !== null) {
+        // If there is more work to do in this returnFiber, do that next.
+        return siblingFiber;
+      } else if (returnFiber !== null) {
+        // If there's no more work in this returnFiber. Complete the returnFiber.
+        workInProgress = returnFiber;
+        continue;
+      } else {
+        return null;
       }
     }
+  }
 
-    // Without this explicit null return Flow complains of invalid return type
-    // TODO Remove the above while(true) loop
-    // eslint-disable-next-line no-unreachable
-    return null;
+  // Without this explicit null return Flow complains of invalid return type
+  // TODO Remove the above while(true) loop
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
+
+function performUnitOfWork(workInProgress) {
+  // The current, flushed, state of this fiber is the alternate.
+  // Ideally nothing should rely on this, but relying on it here
+  // means that we don't need an additional field on the work in
+  // progress.
+  var current = workInProgress.alternate;
+
+  // See if beginning this work spawns more work.
+  startWorkTimer(workInProgress);
+  {
+    ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
   }
 
-  function performUnitOfWork(workInProgress) {
-    // The current, flushed, state of this fiber is the alternate.
-    // Ideally nothing should rely on this, but relying on it here
-    // means that we don't need an additional field on the work in
-    // progress.
-    var current = workInProgress.alternate;
+  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+    stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
+      stashedWorkInProgressProperties,
+      workInProgress
+    );
+  }
 
-    // See if beginning this work spawns more work.
-    startWorkTimer(workInProgress);
-    {
-      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+  var next = void 0;
+  if (enableProfilerTimer) {
+    if (workInProgress.mode & ProfileMode) {
+      startBaseRenderTimer();
     }
 
-    if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
-        stashedWorkInProgressProperties,
-        workInProgress
-      );
+    next = beginWork(current, workInProgress, nextRenderExpirationTime);
+
+    if (workInProgress.mode & ProfileMode) {
+      // Update "base" time if the render wasn't bailed out on.
+      recordElapsedBaseRenderTimeIfRunning(workInProgress);
+      stopBaseRenderTimerIfRunning();
     }
+  } else {
+    next = beginWork(current, workInProgress, nextRenderExpirationTime);
+  }
 
-    var next = void 0;
-    if (enableProfilerTimer) {
-      if (workInProgress.mode & ProfileMode) {
-        startBaseRenderTimer();
-      }
+  {
+    ReactDebugCurrentFiber.resetCurrentFiber();
+    if (isReplayingFailedUnitOfWork) {
+      // Currently replaying a failed unit of work. This should be unreachable,
+      // because the render phase is meant to be idempotent, and it should
+      // have thrown again. Since it didn't, rethrow the original error, so
+      // React's internal stack is not misaligned.
+      rethrowOriginalError();
+    }
+  }
+  if (true && ReactFiberInstrumentation_1.debugTool) {
+    ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
+  }
 
-      next = beginWork(current, workInProgress, nextRenderExpirationTime);
+  if (next === null) {
+    // If this doesn't spawn new work, complete the current work.
+    next = completeUnitOfWork(workInProgress);
+  }
 
-      if (workInProgress.mode & ProfileMode) {
-        // Update "base" time if the render wasn't bailed out on.
-        recordElapsedBaseRenderTimeIfRunning(workInProgress);
-        stopBaseRenderTimerIfRunning();
-      }
-    } else {
-      next = beginWork(current, workInProgress, nextRenderExpirationTime);
-    }
+  ReactCurrentOwner.current = null;
 
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
-      if (isReplayingFailedUnitOfWork) {
-        // Currently replaying a failed unit of work. This should be unreachable,
-        // because the render phase is meant to be idempotent, and it should
-        // have thrown again. Since it didn't, rethrow the original error, so
-        // React's internal stack is not misaligned.
-        rethrowOriginalError();
-      }
+  return next;
+}
+
+function workLoop(isYieldy) {
+  if (!isYieldy) {
+    // Flush work without yielding
+    while (nextUnitOfWork !== null) {
+      nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
     }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
+  } else {
+    // Flush asynchronous work until the deadline runs out of time.
+    while (nextUnitOfWork !== null && !shouldYield()) {
+      nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
     }
 
-    if (next === null) {
-      // If this doesn't spawn new work, complete the current work.
-      next = completeUnitOfWork(workInProgress);
+    if (enableProfilerTimer) {
+      // If we didn't finish, pause the "actual" render timer.
+      // We'll restart it when we resume work.
+      pauseActualRenderTimerIfRunning();
     }
-
-    ReactCurrentOwner.current = null;
-
-    return next;
   }
+}
 
-  function workLoop(isAsync) {
-    if (!isAsync) {
-      // Flush all expired work.
-      while (nextUnitOfWork !== null) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      }
-    } else {
-      // Flush asynchronous work until the deadline runs out of time.
-      while (nextUnitOfWork !== null && !shouldYield()) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      }
+function renderRoot(root, isYieldy) {
+  invariant(
+    !isWorking,
+    "renderRoot was called recursively. This error is likely caused " +
+      "by a bug in React. Please file an issue."
+  );
+  isWorking = true;
 
-      if (enableProfilerTimer) {
-        // If we didn't finish, pause the "actual" render timer.
-        // We'll restart it when we resume work.
-        pauseActualRenderTimerIfRunning();
-      }
-    }
-  }
+  var expirationTime = root.nextExpirationTimeToWorkOn;
 
-  function renderRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
+  // Check if we're starting from a fresh stack, or if we're resuming from
+  // previously yielded work.
+  if (
+    expirationTime !== nextRenderExpirationTime ||
+    root !== nextRoot ||
+    nextUnitOfWork === null
+  ) {
+    // Reset the stack and start working from the root.
+    resetStack();
+    nextRoot = root;
+    nextRenderExpirationTime = expirationTime;
+    nextLatestTimeoutMs = -1;
+    nextRenderDidError = false;
+    nextUnitOfWork = createWorkInProgress(
+      nextRoot.current,
+      null,
+      nextRenderExpirationTime
     );
-    isWorking = true;
+    root.pendingCommitExpirationTime = NoWork;
+  }
 
-    // Check if we're starting from a fresh stack, or if we're resuming from
-    // previously yielded work.
-    if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      nextUnitOfWork === null
-    ) {
-      // Reset the stack and start working from the root.
-      resetStack();
-      nextRoot = root;
-      nextRenderExpirationTime = expirationTime;
-      nextLatestTimeoutMs = -1;
-      nextUnitOfWork = createWorkInProgress(
-        nextRoot.current,
-        null,
-        nextRenderExpirationTime
-      );
-      root.pendingCommitExpirationTime = NoWork;
-    }
+  var didFatal = false;
 
-    var didFatal = false;
+  startWorkLoopTimer(nextUnitOfWork);
 
-    nextRenderIsExpired =
-      !isAsync || nextRenderExpirationTime <= mostRecentCurrentTime;
+  do {
+    try {
+      workLoop(isYieldy);
+    } catch (thrownValue) {
+      if (enableProfilerTimer) {
+        // Stop "base" render timer in the event of an error.
+        stopBaseRenderTimerIfRunning();
+      }
 
-    startWorkLoopTimer(nextUnitOfWork);
+      if (nextUnitOfWork === null) {
+        // This is a fatal error.
+        didFatal = true;
+        onUncaughtError(thrownValue);
+      } else {
+        {
+          // Reset global debug state
+          // We assume this is defined in DEV
+          resetCurrentlyProcessingQueue();
+        }
 
-    do {
-      try {
-        workLoop(isAsync);
-      } catch (thrownValue) {
-        if (enableProfilerTimer) {
-          // Stop "base" render timer in the event of an error.
-          stopBaseRenderTimerIfRunning();
+        var failedUnitOfWork = nextUnitOfWork;
+        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+          replayUnitOfWork(failedUnitOfWork, thrownValue, isYieldy);
         }
 
-        if (nextUnitOfWork === null) {
-          // This is a fatal error.
+        // TODO: we already know this isn't true in some cases.
+        // At least this shows a nicer error message until we figure out the cause.
+        // https://github.com/facebook/react/issues/12449#issuecomment-386727431
+        invariant(
+          nextUnitOfWork !== null,
+          "Failed to replay rendering after an error. This " +
+            "is likely caused by a bug in React. Please file an issue " +
+            "with a reproducing case to help us find it."
+        );
+
+        var sourceFiber = nextUnitOfWork;
+        var returnFiber = sourceFiber.return;
+        if (returnFiber === null) {
+          // This is the root. The root could capture its own errors. However,
+          // we don't know if it errors before or after we pushed the host
+          // context. This information is needed to avoid a stack mismatch.
+          // Because we're not sure, treat this as a fatal error. We could track
+          // which phase it fails in, but doesn't seem worth it. At least
+          // for now.
           didFatal = true;
           onUncaughtError(thrownValue);
-        } else {
-          {
-            // Reset global debug state
-            // We assume this is defined in DEV
-            resetCurrentlyProcessingQueue();
-          }
-
-          var failedUnitOfWork = nextUnitOfWork;
-          if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-            replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
-          }
-
-          // TODO: we already know this isn't true in some cases.
-          // At least this shows a nicer error message until we figure out the cause.
-          // https://github.com/facebook/react/issues/12449#issuecomment-386727431
-          invariant(
-            nextUnitOfWork !== null,
-            "Failed to replay rendering after an error. This " +
-              "is likely caused by a bug in React. Please file an issue " +
-              "with a reproducing case to help us find it."
-          );
-
-          var sourceFiber = nextUnitOfWork;
-          var returnFiber = sourceFiber.return;
-          if (returnFiber === null) {
-            // This is the root. The root could capture its own errors. However,
-            // we don't know if it errors before or after we pushed the host
-            // context. This information is needed to avoid a stack mismatch.
-            // Because we're not sure, treat this as a fatal error. We could track
-            // which phase it fails in, but doesn't seem worth it. At least
-            // for now.
-            didFatal = true;
-            onUncaughtError(thrownValue);
-            break;
-          }
-          throwException(
-            root,
-            returnFiber,
-            sourceFiber,
-            thrownValue,
-            nextRenderIsExpired,
-            nextRenderExpirationTime,
-            mostRecentCurrentTimeMs
-          );
-          nextUnitOfWork = completeUnitOfWork(sourceFiber);
+          break;
         }
-      }
-      break;
-    } while (true);
-
-    // We're done performing work. Time to clean up.
-    var didCompleteRoot = false;
-    isWorking = false;
-
-    // Yield back to main thread.
-    if (didFatal) {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There was a fatal error.
-      {
-        stack.resetStackAfterFatalErrorInDev();
-      }
-      return null;
-    } else if (nextUnitOfWork === null) {
-      // We reached the root.
-      if (isRootReadyForCommit) {
-        didCompleteRoot = true;
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        // The root successfully completed. It's ready for commit.
-        root.pendingCommitExpirationTime = expirationTime;
-        var finishedWork = root.current.alternate;
-        return finishedWork;
-      } else {
-        // The root did not complete.
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        invariant(
-          !nextRenderIsExpired,
-          "Expired work should have completed. This error is likely caused " +
-            "by a bug in React. Please file an issue."
+        throwException(
+          root,
+          returnFiber,
+          sourceFiber,
+          thrownValue,
+          nextRenderExpirationTime,
+          mostRecentCurrentTimeMs
         );
-        markSuspendedPriorityLevel(root, expirationTime);
-        if (nextLatestTimeoutMs >= 0) {
-          setTimeout(function() {
-            retrySuspendedRoot(root, expirationTime);
-          }, nextLatestTimeoutMs);
-        }
-        var firstUnblockedExpirationTime = findNextPendingPriorityLevel(root);
-        onBlock(firstUnblockedExpirationTime);
-        return null;
+        nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
+    }
+    break;
+  } while (true);
+
+  // We're done performing work. Time to clean up.
+  isWorking = false;
+
+  // Yield back to main thread.
+  if (didFatal) {
+    var didCompleteRoot = false;
+    stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+    interruptedBy = null;
+    // There was a fatal error.
+    {
+      resetStackAfterFatalErrorInDev();
+    }
+    onFatal(root);
+  } else if (nextUnitOfWork === null) {
+    // We reached the root.
+    var rootWorkInProgress = root.current.alternate;
+    invariant(
+      rootWorkInProgress !== null,
+      "Finished root should have a work-in-progress. This error is likely " +
+        "caused by a bug in React. Please file an issue."
+    );
+    if ((rootWorkInProgress.effectTag & Incomplete) === NoEffect) {
+      var _didCompleteRoot = true;
+      stopWorkLoopTimer(interruptedBy, _didCompleteRoot);
+      interruptedBy = null;
+      // The root successfully completed.
+      onComplete(root, rootWorkInProgress, expirationTime);
     } else {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+      // The root did not complete.
+      var _didCompleteRoot2 = false;
+      stopWorkLoopTimer(interruptedBy, _didCompleteRoot2);
       interruptedBy = null;
-      // There's more work to do, but we ran out of time. Yield back to
-      // the renderer.
-      return null;
+      markSuspendedPriorityLevel(root, expirationTime, nextRenderDidError);
+      var suspendedExpirationTime = expirationTime;
+      var newExpirationTime = root.expirationTime;
+      onSuspend(
+        root,
+        suspendedExpirationTime,
+        newExpirationTime,
+        nextLatestTimeoutMs
+      );
     }
+  } else {
+    var _didCompleteRoot3 = false;
+    stopWorkLoopTimer(interruptedBy, _didCompleteRoot3);
+    interruptedBy = null;
+    onYield(root);
   }
+}
 
-  function dispatch(sourceFiber, value, expirationTime) {
-    invariant(
-      !isWorking || isCommitting,
-      "dispatch: Cannot dispatch during the render phase."
-    );
+function dispatch(sourceFiber, value, expirationTime) {
+  invariant(
+    !isWorking || isCommitting$1,
+    "dispatch: Cannot dispatch during the render phase."
+  );
 
-    var fiber = sourceFiber.return;
-    while (fiber !== null) {
-      switch (fiber.tag) {
-        case ClassComponent:
-          var ctor = fiber.type;
-          var instance = fiber.stateNode;
-          if (
-            typeof ctor.getDerivedStateFromCatch === "function" ||
-            (typeof instance.componentDidCatch === "function" &&
-              !isAlreadyFailedLegacyErrorBoundary(instance))
-          ) {
-            var errorInfo = createCapturedValue(value, sourceFiber);
-            var update = createClassErrorUpdate(
-              fiber,
-              errorInfo,
-              expirationTime
-            );
-            enqueueUpdate(fiber, update, expirationTime);
-            scheduleWork(fiber, expirationTime);
-            return;
-          }
-          break;
-        case HostRoot: {
-          var _errorInfo = createCapturedValue(value, sourceFiber);
-          var _update = createRootErrorUpdate(
-            fiber,
-            _errorInfo,
-            expirationTime
-          );
-          enqueueUpdate(fiber, _update, expirationTime);
+  var fiber = sourceFiber.return;
+  while (fiber !== null) {
+    switch (fiber.tag) {
+      case ClassComponent:
+        var ctor = fiber.type;
+        var instance = fiber.stateNode;
+        if (
+          typeof ctor.getDerivedStateFromCatch === "function" ||
+          (typeof instance.componentDidCatch === "function" &&
+            !isAlreadyFailedLegacyErrorBoundary(instance))
+        ) {
+          var errorInfo = createCapturedValue(value, sourceFiber);
+          var update = createClassErrorUpdate(fiber, errorInfo, expirationTime);
+          enqueueUpdate(fiber, update, expirationTime);
           scheduleWork(fiber, expirationTime);
           return;
         }
+        break;
+      case HostRoot: {
+        var _errorInfo = createCapturedValue(value, sourceFiber);
+        var _update = createRootErrorUpdate(fiber, _errorInfo, expirationTime);
+        enqueueUpdate(fiber, _update, expirationTime);
+        scheduleWork(fiber, expirationTime);
+        return;
       }
-      fiber = fiber.return;
-    }
-
-    if (sourceFiber.tag === HostRoot) {
-      // Error was thrown at the root. There is no parent, so the root
-      // itself should capture it.
-      var rootFiber = sourceFiber;
-      var _errorInfo2 = createCapturedValue(value, rootFiber);
-      var _update2 = createRootErrorUpdate(
-        rootFiber,
-        _errorInfo2,
-        expirationTime
-      );
-      enqueueUpdate(rootFiber, _update2, expirationTime);
-      scheduleWork(rootFiber, expirationTime);
     }
+    fiber = fiber.return;
   }
 
-  function onCommitPhaseError(fiber, error) {
-    return dispatch(fiber, error, Sync);
+  if (sourceFiber.tag === HostRoot) {
+    // Error was thrown at the root. There is no parent, so the root
+    // itself should capture it.
+    var rootFiber = sourceFiber;
+    var _errorInfo2 = createCapturedValue(value, rootFiber);
+    var _update2 = createRootErrorUpdate(
+      rootFiber,
+      _errorInfo2,
+      expirationTime
+    );
+    enqueueUpdate(rootFiber, _update2, expirationTime);
+    scheduleWork(rootFiber, expirationTime);
   }
+}
 
-  function computeAsyncExpiration(currentTime) {
-    // Given the current clock time, returns an expiration time. We use rounding
-    // to batch like updates together.
-    // Should complete within ~1000ms. 1200ms max.
-    var expirationMs = 5000;
-    var bucketSizeMs = 250;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
+function captureCommitPhaseError(fiber, error) {
+  return dispatch(fiber, error, Sync);
+}
 
-  function computeInteractiveExpiration(currentTime) {
-    var expirationMs = void 0;
-    // We intentionally set a higher expiration time for interactive updates in
-    // dev than in production.
-    // If the main thread is being blocked so long that you hit the expiration,
-    // it's a problem that could be solved with better scheduling.
-    // People will be more likely to notice this and fix it with the long
-    // expiration time in development.
-    // In production we opt for better UX at the risk of masking scheduling
-    // problems, by expiring fast.
-    {
-      // Should complete within ~500ms. 600ms max.
-      expirationMs = 500;
-    }
-    var bucketSizeMs = 100;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
+function computeAsyncExpiration(currentTime) {
+  // Given the current clock time, returns an expiration time. We use rounding
+  // to batch like updates together.
+  // Should complete within ~5000ms. 5250ms max.
+  var expirationMs = 5000;
+  var bucketSizeMs = 250;
+  return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+}
 
-  // Creates a unique async expiration time.
-  function computeUniqueAsyncExpiration() {
-    var currentTime = recalculateCurrentTime();
-    var result = computeAsyncExpiration(currentTime);
-    if (result <= lastUniqueAsyncExpiration) {
-      // Since we assume the current time monotonically increases, we only hit
-      // this branch when computeUniqueAsyncExpiration is fired multiple times
-      // within a 200ms window (or whatever the async bucket size is).
-      result = lastUniqueAsyncExpiration + 1;
-    }
-    lastUniqueAsyncExpiration = result;
-    return lastUniqueAsyncExpiration;
-  }
-
-  function computeExpirationForFiber(currentTime, fiber) {
-    var expirationTime = void 0;
-    if (expirationContext !== NoWork) {
-      // An explicit expiration context was set;
-      expirationTime = expirationContext;
-    } else if (isWorking) {
-      if (isCommitting) {
-        // Updates that occur during the commit phase should have sync priority
-        // by default.
-        expirationTime = Sync;
-      } else {
-        // Updates during the render phase should expire at the same time as
-        // the work that is being rendered.
-        expirationTime = nextRenderExpirationTime;
-      }
+function computeInteractiveExpiration(currentTime) {
+  var expirationMs = void 0;
+  // We intentionally set a higher expiration time for interactive updates in
+  // dev than in production.
+  // If the main thread is being blocked so long that you hit the expiration,
+  // it's a problem that could be solved with better scheduling.
+  // People will be more likely to notice this and fix it with the long
+  // expiration time in development.
+  // In production we opt for better UX at the risk of masking scheduling
+  // problems, by expiring fast.
+  {
+    // Should complete within ~500ms. 600ms max.
+    expirationMs = 500;
+  }
+  var bucketSizeMs = 100;
+  return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+}
+
+// Creates a unique async expiration time.
+function computeUniqueAsyncExpiration() {
+  var currentTime = recalculateCurrentTime();
+  var result = computeAsyncExpiration(currentTime);
+  if (result <= lastUniqueAsyncExpiration) {
+    // Since we assume the current time monotonically increases, we only hit
+    // this branch when computeUniqueAsyncExpiration is fired multiple times
+    // within a 200ms window (or whatever the async bucket size is).
+    result = lastUniqueAsyncExpiration + 1;
+  }
+  lastUniqueAsyncExpiration = result;
+  return lastUniqueAsyncExpiration;
+}
+
+function computeExpirationForFiber(currentTime, fiber) {
+  var expirationTime = void 0;
+  if (expirationContext !== NoWork) {
+    // An explicit expiration context was set;
+    expirationTime = expirationContext;
+  } else if (isWorking) {
+    if (isCommitting$1) {
+      // Updates that occur during the commit phase should have sync priority
+      // by default.
+      expirationTime = Sync;
     } else {
-      // No explicit expiration context was set, and we're not currently
-      // performing work. Calculate a new expiration time.
-      if (fiber.mode & AsyncMode) {
-        if (isBatchingInteractiveUpdates) {
-          // This is an interactive update
-          expirationTime = computeInteractiveExpiration(currentTime);
-        } else {
-          // This is an async update
-          expirationTime = computeAsyncExpiration(currentTime);
-        }
+      // Updates during the render phase should expire at the same time as
+      // the work that is being rendered.
+      expirationTime = nextRenderExpirationTime;
+    }
+  } else {
+    // No explicit expiration context was set, and we're not currently
+    // performing work. Calculate a new expiration time.
+    if (fiber.mode & AsyncMode) {
+      if (isBatchingInteractiveUpdates) {
+        // This is an interactive update
+        expirationTime = computeInteractiveExpiration(currentTime);
       } else {
-        // This is a sync update
-        expirationTime = Sync;
+        // This is an async update
+        expirationTime = computeAsyncExpiration(currentTime);
       }
+    } else {
+      // This is a sync update
+      expirationTime = Sync;
     }
-    if (isBatchingInteractiveUpdates) {
-      // This is an interactive update. Keep track of the lowest pending
-      // interactive expiration time. This allows us to synchronously flush
-      // all interactive updates when needed.
-      if (
-        lowestPendingInteractiveExpirationTime === NoWork ||
-        expirationTime > lowestPendingInteractiveExpirationTime
-      ) {
-        lowestPendingInteractiveExpirationTime = expirationTime;
-      }
+  }
+  if (isBatchingInteractiveUpdates) {
+    // This is an interactive update. Keep track of the lowest pending
+    // interactive expiration time. This allows us to synchronously flush
+    // all interactive updates when needed.
+    if (
+      lowestPendingInteractiveExpirationTime === NoWork ||
+      expirationTime > lowestPendingInteractiveExpirationTime
+    ) {
+      lowestPendingInteractiveExpirationTime = expirationTime;
     }
-    return expirationTime;
   }
+  return expirationTime;
+}
 
-  // TODO: Rename this to scheduleTimeout or something
-  function suspendRoot(root, thenable, timeoutMs, suspendedTime) {
-    // Schedule the timeout.
-    if (timeoutMs >= 0 && nextLatestTimeoutMs < timeoutMs) {
-      nextLatestTimeoutMs = timeoutMs;
-    }
+function markTimeout(root, thenable, timeoutMs, suspendedTime) {
+  // Schedule the timeout.
+  if (timeoutMs >= 0 && nextLatestTimeoutMs < timeoutMs) {
+    nextLatestTimeoutMs = timeoutMs;
   }
+}
 
-  function retrySuspendedRoot(root, suspendedTime) {
-    markPingedPriorityLevel(root, suspendedTime);
-    var retryTime = findNextPendingPriorityLevel(root);
-    if (retryTime !== NoWork) {
-      requestRetry(root, retryTime);
-    }
+function markError(root) {
+  nextRenderDidError = true;
+}
+
+function retrySuspendedRoot(root, suspendedTime) {
+  markPingedPriorityLevel(root, suspendedTime);
+  var retryTime = root.expirationTime;
+  if (retryTime !== NoWork) {
+    requestWork(root, retryTime);
   }
+}
 
-  function scheduleWork(fiber, expirationTime) {
-    recordScheduleUpdate();
+function scheduleWork(fiber, expirationTime) {
+  recordScheduleUpdate();
 
-    {
-      if (fiber.tag === ClassComponent) {
-        var instance = fiber.stateNode;
-        warnAboutInvalidUpdates(instance);
-      }
+  {
+    if (fiber.tag === ClassComponent) {
+      var instance = fiber.stateNode;
+      warnAboutInvalidUpdates(instance);
     }
+  }
 
-    var node = fiber;
-    while (node !== null) {
-      // Walk the parent path to the root and update each node's
-      // expiration time.
+  var node = fiber;
+  while (node !== null) {
+    // Walk the parent path to the root and update each node's
+    // expiration time.
+    if (
+      node.expirationTime === NoWork ||
+      node.expirationTime > expirationTime
+    ) {
+      node.expirationTime = expirationTime;
+    }
+    if (node.alternate !== null) {
       if (
-        node.expirationTime === NoWork ||
-        node.expirationTime > expirationTime
+        node.alternate.expirationTime === NoWork ||
+        node.alternate.expirationTime > expirationTime
       ) {
-        node.expirationTime = expirationTime;
+        node.alternate.expirationTime = expirationTime;
       }
-      if (node.alternate !== null) {
+    }
+    if (node.return === null) {
+      if (node.tag === HostRoot) {
+        var root = node.stateNode;
         if (
-          node.alternate.expirationTime === NoWork ||
-          node.alternate.expirationTime > expirationTime
+          !isWorking &&
+          nextRenderExpirationTime !== NoWork &&
+          expirationTime < nextRenderExpirationTime
         ) {
-          node.alternate.expirationTime = expirationTime;
+          // This is an interruption. (Used for performance tracking.)
+          interruptedBy = fiber;
+          resetStack();
         }
-      }
-      if (node.return === null) {
-        if (node.tag === HostRoot) {
-          var root = node.stateNode;
-          if (
-            !isWorking &&
-            nextRenderExpirationTime !== NoWork &&
-            expirationTime < nextRenderExpirationTime
-          ) {
-            // This is an interruption. (Used for performance tracking.)
-            interruptedBy = fiber;
-            resetStack();
-          }
-          markPendingPriorityLevel(root, expirationTime);
-          var nextExpirationTimeToWorkOn = findNextPendingPriorityLevel(root);
-          if (
-            // If we're in the render phase, we don't need to schedule this root
-            // for an update, because we'll do it before we exit...
-            !isWorking ||
-            isCommitting ||
-            // ...unless this is a different root than the one we're rendering.
-            nextRoot !== root
-          ) {
-            requestWork(root, nextExpirationTimeToWorkOn);
-          }
-          if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
-            invariant(
-              false,
-              "Maximum update depth exceeded. This can happen when a " +
-                "component repeatedly calls setState inside " +
-                "componentWillUpdate or componentDidUpdate. React limits " +
-                "the number of nested updates to prevent infinite loops."
-            );
-          }
-        } else {
-          {
-            if (fiber.tag === ClassComponent) {
-              warnAboutUpdateOnUnmounted(fiber);
-            }
+        markPendingPriorityLevel(root, expirationTime);
+        if (
+          // If we're in the render phase, we don't need to schedule this root
+          // for an update, because we'll do it before we exit...
+          !isWorking ||
+          isCommitting$1 ||
+          // ...unless this is a different root than the one we're rendering.
+          nextRoot !== root
+        ) {
+          var rootExpirationTime = root.expirationTime;
+          requestWork(root, rootExpirationTime);
+        }
+        if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
+          invariant(
+            false,
+            "Maximum update depth exceeded. This can happen when a " +
+              "component repeatedly calls setState inside " +
+              "componentWillUpdate or componentDidUpdate. React limits " +
+              "the number of nested updates to prevent infinite loops."
+          );
+        }
+      } else {
+        {
+          if (fiber.tag === ClassComponent) {
+            warnAboutUpdateOnUnmounted(fiber);
           }
-          return;
         }
+        return;
       }
-      node = node.return;
     }
+    node = node.return;
   }
+}
 
-  function recalculateCurrentTime() {
-    // Subtract initial time so it fits inside 32bits
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
-    return mostRecentCurrentTime;
-  }
+function recalculateCurrentTime() {
+  // Subtract initial time so it fits inside 32bits
+  mostRecentCurrentTimeMs = now() - originalStartTimeMs;
+  mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
+  return mostRecentCurrentTime;
+}
 
-  function deferredUpdates(fn) {
-    var previousExpirationContext = expirationContext;
-    var currentTime = recalculateCurrentTime();
-    expirationContext = computeAsyncExpiration(currentTime);
-    try {
-      return fn();
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
+function deferredUpdates(fn) {
+  var previousExpirationContext = expirationContext;
+  var currentTime = recalculateCurrentTime();
+  expirationContext = computeAsyncExpiration(currentTime);
+  try {
+    return fn();
+  } finally {
+    expirationContext = previousExpirationContext;
   }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = Sync;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
+}
+function syncUpdates(fn, a, b, c, d) {
+  var previousExpirationContext = expirationContext;
+  expirationContext = Sync;
+  try {
+    return fn(a, b, c, d);
+  } finally {
+    expirationContext = previousExpirationContext;
   }
+}
 
-  // TODO: Everything below this is written as if it has been lifted to the
-  // renderers. I'll do this in a follow-up.
+// TODO: Everything below this is written as if it has been lifted to the
+// renderers. I'll do this in a follow-up.
 
-  // Linked-list of roots
-  var firstScheduledRoot = null;
-  var lastScheduledRoot = null;
+// Linked-list of roots
+var firstScheduledRoot = null;
+var lastScheduledRoot = null;
 
-  var callbackExpirationTime = NoWork;
-  var callbackID = -1;
-  var isRendering = false;
-  var nextFlushedRoot = null;
-  var nextFlushedExpirationTime = NoWork;
-  var lowestPendingInteractiveExpirationTime = NoWork;
-  var deadlineDidExpire = false;
-  var hasUnhandledError = false;
-  var unhandledError = null;
-  var deadline = null;
+var callbackExpirationTime = NoWork;
+var callbackID = void 0;
+var isRendering = false;
+var nextFlushedRoot = null;
+var nextFlushedExpirationTime = NoWork;
+var lowestPendingInteractiveExpirationTime = NoWork;
+var deadlineDidExpire = false;
+var hasUnhandledError = false;
+var unhandledError = null;
+var deadline = null;
 
-  var isBatchingUpdates = false;
-  var isUnbatchingUpdates = false;
-  var isBatchingInteractiveUpdates = false;
+var isBatchingUpdates = false;
+var isUnbatchingUpdates = false;
+var isBatchingInteractiveUpdates = false;
 
-  var completedBatches = null;
+var completedBatches = null;
 
-  // Use these to prevent an infinite loop of nested updates
-  var NESTED_UPDATE_LIMIT = 1000;
-  var nestedUpdateCount = 0;
+// Use these to prevent an infinite loop of nested updates
+var NESTED_UPDATE_LIMIT = 1000;
+var nestedUpdateCount = 0;
 
-  var timeHeuristicForUnitOfWork = 1;
+var timeHeuristicForUnitOfWork = 1;
 
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (callbackExpirationTime !== NoWork) {
-      // A callback is already scheduled. Check its expiration time (timeout).
-      if (expirationTime > callbackExpirationTime) {
-        // Existing callback has sufficient timeout. Exit.
-        return;
-      } else {
+function scheduleCallbackWithExpirationTime(expirationTime) {
+  if (callbackExpirationTime !== NoWork) {
+    // A callback is already scheduled. Check its expiration time (timeout).
+    if (expirationTime > callbackExpirationTime) {
+      // Existing callback has sufficient timeout. Exit.
+      return;
+    } else {
+      if (callbackID !== null) {
         // Existing callback has insufficient timeout. Cancel and schedule a
         // new one.
         cancelDeferredCallback(callbackID);
       }
-      // The request callback timer is already running. Don't start a new one.
-    } else {
-      startRequestCallbackTimer();
     }
+    // The request callback timer is already running. Don't start a new one.
+  } else {
+    startRequestCallbackTimer();
+  }
 
-    // Compute a timeout for the given expiration time.
-    var currentMs = now() - originalStartTimeMs;
-    var expirationMs = expirationTimeToMs(expirationTime);
-    var timeout = expirationMs - currentMs;
+  callbackExpirationTime = expirationTime;
+  var currentMs = now() - originalStartTimeMs;
+  var expirationTimeMs = expirationTimeToMs(expirationTime);
+  var timeout = expirationTimeMs - currentMs;
+  callbackID = scheduleDeferredCallback(performAsyncWork, { timeout: timeout });
+}
 
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: timeout
-    });
-  }
+// For every call to renderRoot, one of onFatal, onComplete, onSuspend, and
+// onYield is called upon exiting. We use these in lieu of returning a tuple.
+// I've also chosen not to inline them into renderRoot because these will
+// eventually be lifted into the renderer.
+function onFatal(root) {
+  root.finishedWork = null;
+}
 
-  function requestRetry(root, expirationTime) {
-    if (
-      root.remainingExpirationTime === NoWork ||
-      root.remainingExpirationTime < expirationTime
-    ) {
-      // For a retry, only update the remaining expiration time if it has a
-      // *lower priority* than the existing value. This is because, on a retry,
-      // we should attempt to coalesce as much as possible.
-      requestWork(root, expirationTime);
-    }
+function onComplete(root, finishedWork, expirationTime) {
+  root.pendingCommitExpirationTime = expirationTime;
+  root.finishedWork = finishedWork;
+}
+
+function onSuspend(root, suspendedExpirationTime, expirationTime, timeoutMs) {
+  if (timeoutMs >= 0) {
+    var suspendedRoot = root;
+    setTimeout(function() {
+      retrySuspendedRoot(suspendedRoot, suspendedExpirationTime);
+    }, timeoutMs);
   }
+  root.expirationTime = expirationTime;
+}
 
-  // requestWork is called by the scheduler whenever a root receives an update.
-  // It's up to the renderer to call renderRoot at some point in the future.
-  function requestWork(root, expirationTime) {
-    addRootToSchedule(root, expirationTime);
+function onYield(root) {
+  root.finishedWork = null;
+}
 
-    if (isRendering) {
-      // Prevent reentrancy. Remaining work will be scheduled at the end of
-      // the currently rendering batch.
-      return;
-    }
+function onCommit(root, expirationTime) {
+  root.expirationTime = expirationTime;
+  root.finishedWork = null;
+}
 
-    if (isBatchingUpdates) {
-      // Flush work at the end of the batch.
-      if (isUnbatchingUpdates) {
-        // ...unless we're inside unbatchedUpdates, in which case we should
-        // flush it now.
-        nextFlushedRoot = root;
-        nextFlushedExpirationTime = Sync;
-        performWorkOnRoot(root, Sync, false);
-      }
-      return;
-    }
+// requestWork is called by the scheduler whenever a root receives an update.
+// It's up to the renderer to call renderRoot at some point in the future.
+function requestWork(root, expirationTime) {
+  addRootToSchedule(root, expirationTime);
 
-    // TODO: Get rid of Sync and use current time?
-    if (expirationTime === Sync) {
-      performSyncWork();
-    } else {
-      scheduleCallbackWithExpiration(expirationTime);
-    }
+  if (isRendering) {
+    // Prevent reentrancy. Remaining work will be scheduled at the end of
+    // the currently rendering batch.
+    return;
   }
 
-  function addRootToSchedule(root, expirationTime) {
-    // Add the root to the schedule.
-    // Check if this root is already part of the schedule.
-    if (root.nextScheduledRoot === null) {
-      // This root is not already scheduled. Add it.
-      root.remainingExpirationTime = expirationTime;
-      if (lastScheduledRoot === null) {
-        firstScheduledRoot = lastScheduledRoot = root;
-        root.nextScheduledRoot = root;
-      } else {
-        lastScheduledRoot.nextScheduledRoot = root;
-        lastScheduledRoot = root;
-        lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-      }
-    } else {
-      // This root is already scheduled, but its priority may have increased.
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        remainingExpirationTime === NoWork ||
-        expirationTime < remainingExpirationTime
-      ) {
-        // Update the priority.
-        root.remainingExpirationTime = expirationTime;
-      }
+  if (isBatchingUpdates) {
+    // Flush work at the end of the batch.
+    if (isUnbatchingUpdates) {
+      // ...unless we're inside unbatchedUpdates, in which case we should
+      // flush it now.
+      nextFlushedRoot = root;
+      nextFlushedExpirationTime = Sync;
+      performWorkOnRoot(root, Sync, false);
     }
+    return;
   }
 
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = NoWork;
-    var highestPriorityRoot = null;
-    if (lastScheduledRoot !== null) {
-      var previousScheduledRoot = lastScheduledRoot;
-      var root = firstScheduledRoot;
-      while (root !== null) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (remainingExpirationTime === NoWork) {
-          // This root no longer has work. Remove it from the scheduler.
+  // TODO: Get rid of Sync and use current time?
+  if (expirationTime === Sync) {
+    performSyncWork();
+  } else {
+    scheduleCallbackWithExpirationTime(expirationTime);
+  }
+}
 
-          // TODO: This check is redudant, but Flow is confused by the branch
-          // below where we set lastScheduledRoot to null, even though we break
-          // from the loop right after.
-          invariant(
-            previousScheduledRoot !== null && lastScheduledRoot !== null,
-            "Should have a previous and last root. This error is likely " +
-              "caused by a bug in React. Please file an issue."
-          );
-          if (root === root.nextScheduledRoot) {
-            // This is the only root in the list.
-            root.nextScheduledRoot = null;
-            firstScheduledRoot = lastScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot) {
-            // This is the first root in the list.
-            var next = root.nextScheduledRoot;
-            firstScheduledRoot = next;
-            lastScheduledRoot.nextScheduledRoot = next;
-            root.nextScheduledRoot = null;
-          } else if (root === lastScheduledRoot) {
-            // This is the last root in the list.
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else {
-            previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
-            root.nextScheduledRoot = null;
-          }
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            highestPriorityWork === NoWork ||
-            remainingExpirationTime < highestPriorityWork
-          ) {
-            // Update the priority, if it's higher
-            highestPriorityWork = remainingExpirationTime;
-            highestPriorityRoot = root;
-          }
-          if (root === lastScheduledRoot) {
-            break;
-          }
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
-        }
-      }
+function addRootToSchedule(root, expirationTime) {
+  // Add the root to the schedule.
+  // Check if this root is already part of the schedule.
+  if (root.nextScheduledRoot === null) {
+    // This root is not already scheduled. Add it.
+    root.expirationTime = expirationTime;
+    if (lastScheduledRoot === null) {
+      firstScheduledRoot = lastScheduledRoot = root;
+      root.nextScheduledRoot = root;
+    } else {
+      lastScheduledRoot.nextScheduledRoot = root;
+      lastScheduledRoot = root;
+      lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
     }
-
-    // If the next root is the same as the previous root, this is a nested
-    // update. To prevent an infinite loop, increment the nested update count.
-    var previousFlushedRoot = nextFlushedRoot;
+  } else {
+    // This root is already scheduled, but its priority may have increased.
+    var remainingExpirationTime = root.expirationTime;
     if (
-      previousFlushedRoot !== null &&
-      previousFlushedRoot === highestPriorityRoot &&
-      highestPriorityWork === Sync
+      remainingExpirationTime === NoWork ||
+      expirationTime < remainingExpirationTime
     ) {
-      nestedUpdateCount++;
-    } else {
-      // Reset whenever we switch roots.
-      nestedUpdateCount = 0;
+      // Update the priority.
+      root.expirationTime = expirationTime;
     }
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
   }
+}
+
+function findHighestPriorityRoot() {
+  var highestPriorityWork = NoWork;
+  var highestPriorityRoot = null;
+  if (lastScheduledRoot !== null) {
+    var previousScheduledRoot = lastScheduledRoot;
+    var root = firstScheduledRoot;
+    while (root !== null) {
+      var remainingExpirationTime = root.expirationTime;
+      if (remainingExpirationTime === NoWork) {
+        // This root no longer has work. Remove it from the scheduler.
 
-  function performAsyncWork(dl) {
-    performWork(NoWork, true, dl);
+        // TODO: This check is redudant, but Flow is confused by the branch
+        // below where we set lastScheduledRoot to null, even though we break
+        // from the loop right after.
+        invariant(
+          previousScheduledRoot !== null && lastScheduledRoot !== null,
+          "Should have a previous and last root. This error is likely " +
+            "caused by a bug in React. Please file an issue."
+        );
+        if (root === root.nextScheduledRoot) {
+          // This is the only root in the list.
+          root.nextScheduledRoot = null;
+          firstScheduledRoot = lastScheduledRoot = null;
+          break;
+        } else if (root === firstScheduledRoot) {
+          // This is the first root in the list.
+          var next = root.nextScheduledRoot;
+          firstScheduledRoot = next;
+          lastScheduledRoot.nextScheduledRoot = next;
+          root.nextScheduledRoot = null;
+        } else if (root === lastScheduledRoot) {
+          // This is the last root in the list.
+          lastScheduledRoot = previousScheduledRoot;
+          lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+          root.nextScheduledRoot = null;
+          break;
+        } else {
+          previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
+          root.nextScheduledRoot = null;
+        }
+        root = previousScheduledRoot.nextScheduledRoot;
+      } else {
+        if (
+          highestPriorityWork === NoWork ||
+          remainingExpirationTime < highestPriorityWork
+        ) {
+          // Update the priority, if it's higher
+          highestPriorityWork = remainingExpirationTime;
+          highestPriorityRoot = root;
+        }
+        if (root === lastScheduledRoot) {
+          break;
+        }
+        previousScheduledRoot = root;
+        root = root.nextScheduledRoot;
+      }
+    }
   }
 
-  function performSyncWork() {
-    performWork(Sync, false, null);
+  // If the next root is the same as the previous root, this is a nested
+  // update. To prevent an infinite loop, increment the nested update count.
+  var previousFlushedRoot = nextFlushedRoot;
+  if (
+    previousFlushedRoot !== null &&
+    previousFlushedRoot === highestPriorityRoot &&
+    highestPriorityWork === Sync
+  ) {
+    nestedUpdateCount++;
+  } else {
+    // Reset whenever we switch roots.
+    nestedUpdateCount = 0;
   }
+  nextFlushedRoot = highestPriorityRoot;
+  nextFlushedExpirationTime = highestPriorityWork;
+}
 
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
+function performAsyncWork(dl) {
+  performWork(NoWork, dl);
+}
 
-    // Keep working on roots until there's no more work, or until the we reach
-    // the deadline.
-    findHighestPriorityRoot();
+function performSyncWork() {
+  performWork(Sync, null);
+}
 
-    if (enableProfilerTimer) {
-      resumeActualRenderTimerIfPaused();
-    }
+function performWork(minExpirationTime, dl) {
+  deadline = dl;
 
-    if (enableUserTimingAPI && deadline !== null) {
-      var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
-      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
-      stopRequestCallbackTimer(didExpire, timeout);
-    }
+  // Keep working on roots until there's no more work, or until the we reach
+  // the deadline.
+  findHighestPriorityRoot();
 
-    if (isAsync) {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime)
-      ) {
-        recalculateCurrentTime();
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        );
-        findHighestPriorityRoot();
-      }
-    } else {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime)
-      ) {
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
-        findHighestPriorityRoot();
-      }
-    }
+  if (enableProfilerTimer) {
+    resumeActualRenderTimerIfPaused();
+  }
 
-    // We're done flushing work. Either we ran out of time in this callback,
-    // or there's no more work left with sufficient priority.
+  if (enableUserTimingAPI && deadline !== null) {
+    var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
+    var timeout = expirationTimeToMs(nextFlushedExpirationTime);
+    stopRequestCallbackTimer(didExpire, timeout);
+  }
 
-    // If we're inside a callback, set this to false since we just completed it.
-    if (deadline !== null) {
-      callbackExpirationTime = NoWork;
-      callbackID = -1;
+  if (deadline !== null) {
+    while (
+      nextFlushedRoot !== null &&
+      nextFlushedExpirationTime !== NoWork &&
+      (minExpirationTime === NoWork ||
+        minExpirationTime >= nextFlushedExpirationTime) &&
+      (!deadlineDidExpire ||
+        recalculateCurrentTime() >= nextFlushedExpirationTime)
+    ) {
+      recalculateCurrentTime();
+      performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, true);
+      findHighestPriorityRoot();
     }
-    // If there's work left over, schedule a new callback.
-    if (nextFlushedExpirationTime !== NoWork) {
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
+  } else {
+    while (
+      nextFlushedRoot !== null &&
+      nextFlushedExpirationTime !== NoWork &&
+      (minExpirationTime === NoWork ||
+        minExpirationTime >= nextFlushedExpirationTime)
+    ) {
+      performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
+      findHighestPriorityRoot();
     }
+  }
 
-    // Clean-up.
-    deadline = null;
-    deadlineDidExpire = false;
+  // We're done flushing work. Either we ran out of time in this callback,
+  // or there's no more work left with sufficient priority.
 
-    finishRendering();
+  // If we're inside a callback, set this to false since we just completed it.
+  if (deadline !== null) {
+    callbackExpirationTime = NoWork;
+    callbackID = null;
   }
-
-  function flushRoot(root, expirationTime) {
-    invariant(
-      !isRendering,
-      "work.commit(): Cannot commit while already rendering. This likely " +
-        "means you attempted to commit from inside a lifecycle method."
-    );
-    // Perform work on root as if the given expiration time is the current time.
-    // This has the effect of synchronously flushing all work up to and
-    // including the given time.
-    nextFlushedRoot = root;
-    nextFlushedExpirationTime = expirationTime;
-    performWorkOnRoot(root, expirationTime, false);
-    // Flush any sync work that was scheduled by lifecycles
-    performSyncWork();
-    finishRendering();
+  // If there's work left over, schedule a new callback.
+  if (nextFlushedExpirationTime !== NoWork) {
+    scheduleCallbackWithExpirationTime(nextFlushedExpirationTime);
   }
 
-  function finishRendering() {
-    nestedUpdateCount = 0;
+  // Clean-up.
+  deadline = null;
+  deadlineDidExpire = false;
 
-    if (completedBatches !== null) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          if (!hasUnhandledError) {
-            hasUnhandledError = true;
-            unhandledError = error;
-          }
+  finishRendering();
+}
+
+function flushRoot(root, expirationTime) {
+  invariant(
+    !isRendering,
+    "work.commit(): Cannot commit while already rendering. This likely " +
+      "means you attempted to commit from inside a lifecycle method."
+  );
+  // Perform work on root as if the given expiration time is the current time.
+  // This has the effect of synchronously flushing all work up to and
+  // including the given time.
+  nextFlushedRoot = root;
+  nextFlushedExpirationTime = expirationTime;
+  performWorkOnRoot(root, expirationTime, false);
+  // Flush any sync work that was scheduled by lifecycles
+  performSyncWork();
+  finishRendering();
+}
+
+function finishRendering() {
+  nestedUpdateCount = 0;
+
+  if (completedBatches !== null) {
+    var batches = completedBatches;
+    completedBatches = null;
+    for (var i = 0; i < batches.length; i++) {
+      var batch = batches[i];
+      try {
+        batch._onComplete();
+      } catch (error) {
+        if (!hasUnhandledError) {
+          hasUnhandledError = true;
+          unhandledError = error;
         }
       }
     }
+  }
 
-    if (hasUnhandledError) {
-      var error = unhandledError;
-      unhandledError = null;
-      hasUnhandledError = false;
-      throw error;
-    }
+  if (hasUnhandledError) {
+    var error = unhandledError;
+    unhandledError = null;
+    hasUnhandledError = false;
+    throw error;
   }
+}
 
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
-    );
+function performWorkOnRoot(root, expirationTime, isYieldy) {
+  invariant(
+    !isRendering,
+    "performWorkOnRoot was called recursively. This error is likely caused " +
+      "by a bug in React. Please file an issue."
+  );
 
-    isRendering = true;
+  isRendering = true;
 
-    // Check if this is async work or sync/expired work.
-    if (!isAsync) {
-      // Flush sync work.
-      var finishedWork = root.finishedWork;
+  // Check if this is async work or sync/expired work.
+  if (!isYieldy) {
+    // Flush work without yielding.
+    var finishedWork = root.finishedWork;
+    if (finishedWork !== null) {
+      // This root is already complete. We can commit it.
+      completeRoot$1(root, finishedWork, expirationTime);
+    } else {
+      root.finishedWork = null;
+      renderRoot(root, false);
+      finishedWork = root.finishedWork;
       if (finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot$$1(root, finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        finishedWork = renderRoot(root, expirationTime, false);
-        if (finishedWork !== null) {
-          // We've completed the root. Commit it.
-          completeRoot$$1(root, finishedWork, expirationTime);
-        }
+        // We've completed the root. Commit it.
+        completeRoot$1(root, finishedWork, expirationTime);
       }
+    }
+  } else {
+    // Flush async work.
+    var _finishedWork = root.finishedWork;
+    if (_finishedWork !== null) {
+      // This root is already complete. We can commit it.
+      completeRoot$1(root, _finishedWork, expirationTime);
     } else {
-      // Flush async work.
-      var _finishedWork = root.finishedWork;
-      if (_finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot$$1(root, _finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        _finishedWork = renderRoot(root, expirationTime, true);
-        if (_finishedWork !== null) {
-          // We've completed the root. Check the deadline one more time
-          // before committing.
-          if (!shouldYield()) {
-            // Still time left. Commit the root.
-            completeRoot$$1(root, _finishedWork, expirationTime);
-          } else {
-            // There's no time left. Mark this root as complete. We'll come
-            // back and commit it later.
-            root.finishedWork = _finishedWork;
-
-            if (enableProfilerTimer) {
-              // If we didn't finish, pause the "actual" render timer.
-              // We'll restart it when we resume work.
-              pauseActualRenderTimerIfRunning();
-            }
+      root.finishedWork = null;
+      renderRoot(root, true);
+      _finishedWork = root.finishedWork;
+      if (_finishedWork !== null) {
+        // We've completed the root. Check the deadline one more time
+        // before committing.
+        if (!shouldYield()) {
+          // Still time left. Commit the root.
+          completeRoot$1(root, _finishedWork, expirationTime);
+        } else {
+          // There's no time left. Mark this root as complete. We'll come
+          // back and commit it later.
+          root.finishedWork = _finishedWork;
+
+          if (enableProfilerTimer) {
+            // If we didn't finish, pause the "actual" render timer.
+            // We'll restart it when we resume work.
+            pauseActualRenderTimerIfRunning();
           }
         }
       }
     }
-
-    isRendering = false;
   }
 
-  function completeRoot$$1(root, finishedWork, expirationTime) {
-    // Check if there's a batch that matches this expiration time.
-    var firstBatch = root.firstBatch;
-    if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
-      if (completedBatches === null) {
-        completedBatches = [firstBatch];
-      } else {
-        completedBatches.push(firstBatch);
-      }
-      if (firstBatch._defer) {
-        // This root is blocked from committing by a batch. Unschedule it until
-        // we receive another update.
-        root.finishedWork = finishedWork;
-        root.remainingExpirationTime = NoWork;
-        return;
-      }
-    }
-
-    // Commit the root.
-    root.finishedWork = null;
-    root.remainingExpirationTime = commitRoot(finishedWork);
-  }
+  isRendering = false;
+}
 
-  // When working on async work, the reconciler asks the renderer if it should
-  // yield execution. For DOM, we implement this with requestIdleCallback.
-  function shouldYield() {
-    if (deadline === null) {
-      return false;
+function completeRoot$1(root, finishedWork, expirationTime) {
+  // Check if there's a batch that matches this expiration time.
+  var firstBatch = root.firstBatch;
+  if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
+    if (completedBatches === null) {
+      completedBatches = [firstBatch];
+    } else {
+      completedBatches.push(firstBatch);
     }
-    if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
-      // Disregard deadline.didTimeout. Only expired work should be flushed
-      // during a timeout. This path is only hit for non-expired work.
-      return false;
+    if (firstBatch._defer) {
+      // This root is blocked from committing by a batch. Unschedule it until
+      // we receive another update.
+      root.finishedWork = finishedWork;
+      root.expirationTime = NoWork;
+      return;
     }
-    deadlineDidExpire = true;
-    return true;
   }
 
-  function onUncaughtError(error) {
-    invariant(
-      nextFlushedRoot !== null,
-      "Should be working on a root. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-    // Unschedule this root so we don't work on it again until there's
-    // another update.
-    nextFlushedRoot.remainingExpirationTime = NoWork;
-    if (!hasUnhandledError) {
-      hasUnhandledError = true;
-      unhandledError = error;
-    }
-  }
+  // Commit the root.
+  root.finishedWork = null;
+  commitRoot(root, finishedWork);
+}
 
-  function onBlock(remainingExpirationTime) {
-    invariant(
-      nextFlushedRoot !== null,
-      "Should be working on a root. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-    // This root was blocked. Unschedule it until there's another update.
-    nextFlushedRoot.remainingExpirationTime = remainingExpirationTime;
+// When working on async work, the reconciler asks the renderer if it should
+// yield execution. For DOM, we implement this with requestIdleCallback.
+function shouldYield() {
+  if (deadline === null || deadlineDidExpire) {
+    return false;
   }
-
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function batchedUpdates(fn, a) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return fn(a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
-      }
-    }
+  if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
+    // Disregard deadline.didTimeout. Only expired work should be flushed
+    // during a timeout. This path is only hit for non-expired work.
+    return false;
   }
+  deadlineDidExpire = true;
+  return true;
+}
 
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function unbatchedUpdates(fn, a) {
-    if (isBatchingUpdates && !isUnbatchingUpdates) {
-      isUnbatchingUpdates = true;
-      try {
-        return fn(a);
-      } finally {
-        isUnbatchingUpdates = false;
-      }
-    }
-    return fn(a);
+function onUncaughtError(error) {
+  invariant(
+    nextFlushedRoot !== null,
+    "Should be working on a root. This error is likely caused by a bug in " +
+      "React. Please file an issue."
+  );
+  // Unschedule this root so we don't work on it again until there's
+  // another update.
+  nextFlushedRoot.expirationTime = NoWork;
+  if (!hasUnhandledError) {
+    hasUnhandledError = true;
+    unhandledError = error;
   }
+}
 
-  // TODO: Batching should be implemented at the renderer level, not within
-  // the reconciler.
-  function flushSync(fn, a) {
-    invariant(
-      !isRendering,
-      "flushSync was called from inside a lifecycle method. It cannot be " +
-        "called when React is already rendering."
-    );
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return syncUpdates(fn, a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
+// TODO: Batching should be implemented at the renderer level, not inside
+// the reconciler.
+function batchedUpdates$1(fn, a) {
+  var previousIsBatchingUpdates = isBatchingUpdates;
+  isBatchingUpdates = true;
+  try {
+    return fn(a);
+  } finally {
+    isBatchingUpdates = previousIsBatchingUpdates;
+    if (!isBatchingUpdates && !isRendering) {
       performSyncWork();
     }
   }
+}
 
-  function interactiveUpdates(fn, a, b) {
-    if (isBatchingInteractiveUpdates) {
-      return fn(a, b);
-    }
-    // If there are any pending interactive updates, synchronously flush them.
-    // This needs to happen before we read any handlers, because the effect of
-    // the previous event may influence which handlers are called during
-    // this event.
-    if (
-      !isBatchingUpdates &&
-      !isRendering &&
-      lowestPendingInteractiveExpirationTime !== NoWork
-    ) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
-    }
-    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingInteractiveUpdates = true;
-    isBatchingUpdates = true;
+// TODO: Batching should be implemented at the renderer level, not inside
+// the reconciler.
+function unbatchedUpdates(fn, a) {
+  if (isBatchingUpdates && !isUnbatchingUpdates) {
+    isUnbatchingUpdates = true;
     try {
-      return fn(a, b);
+      return fn(a);
     } finally {
-      isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
-      }
+      isUnbatchingUpdates = false;
     }
   }
+  return fn(a);
+}
+
+// TODO: Batching should be implemented at the renderer level, not within
+// the reconciler.
+function flushSync(fn, a) {
+  invariant(
+    !isRendering,
+    "flushSync was called from inside a lifecycle method. It cannot be " +
+      "called when React is already rendering."
+  );
+  var previousIsBatchingUpdates = isBatchingUpdates;
+  isBatchingUpdates = true;
+  try {
+    return syncUpdates(fn, a);
+  } finally {
+    isBatchingUpdates = previousIsBatchingUpdates;
+    performSyncWork();
+  }
+}
 
-  function flushInteractiveUpdates() {
-    if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
+function interactiveUpdates$1(fn, a, b) {
+  if (isBatchingInteractiveUpdates) {
+    return fn(a, b);
+  }
+  // If there are any pending interactive updates, synchronously flush them.
+  // This needs to happen before we read any handlers, because the effect of
+  // the previous event may influence which handlers are called during
+  // this event.
+  if (
+    !isBatchingUpdates &&
+    !isRendering &&
+    lowestPendingInteractiveExpirationTime !== NoWork
+  ) {
+    // Synchronously flush pending interactive updates.
+    performWork(lowestPendingInteractiveExpirationTime, null);
+    lowestPendingInteractiveExpirationTime = NoWork;
+  }
+  var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
+  var previousIsBatchingUpdates = isBatchingUpdates;
+  isBatchingInteractiveUpdates = true;
+  isBatchingUpdates = true;
+  try {
+    return fn(a, b);
+  } finally {
+    isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
+    isBatchingUpdates = previousIsBatchingUpdates;
+    if (!isBatchingUpdates && !isRendering) {
+      performSyncWork();
     }
   }
+}
 
-  function flushControlled(fn) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      syncUpdates(fn);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performWork(Sync, false, null);
-      }
+function flushInteractiveUpdates$1() {
+  if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
+    // Synchronously flush pending interactive updates.
+    performWork(lowestPendingInteractiveExpirationTime, null);
+    lowestPendingInteractiveExpirationTime = NoWork;
+  }
+}
+
+function flushControlled(fn) {
+  var previousIsBatchingUpdates = isBatchingUpdates;
+  isBatchingUpdates = true;
+  try {
+    syncUpdates(fn);
+  } finally {
+    isBatchingUpdates = previousIsBatchingUpdates;
+    if (!isBatchingUpdates && !isRendering) {
+      performWork(Sync, null);
     }
   }
+}
 
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: flushRoot,
-    batchedUpdates: batchedUpdates,
-    unbatchedUpdates: unbatchedUpdates,
-    flushSync: flushSync,
-    flushControlled: flushControlled,
-    deferredUpdates: deferredUpdates,
-    syncUpdates: syncUpdates,
-    interactiveUpdates: interactiveUpdates,
-    flushInteractiveUpdates: flushInteractiveUpdates,
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-    legacyContext: legacyContext
-  };
-};
+// 0 is PROD, 1 is DEV.
+// Might add PROFILE later.
 
 var didWarnAboutNestedUpdates = void 0;
 
@@ -14152,318 +13854,407 @@ var didWarnAboutNestedUpdates = void 0;
   didWarnAboutNestedUpdates = false;
 }
 
-// 0 is PROD, 1 is DEV.
-// Might add PROFILE later.
+function getContextForSubtree(parentComponent) {
+  if (!parentComponent) {
+    return emptyObject;
+  }
 
-var ReactFiberReconciler$1 = function(config) {
-  var getPublicInstance = config.getPublicInstance;
-
-  var _ReactFiberScheduler = ReactFiberScheduler(config),
-    computeUniqueAsyncExpiration =
-      _ReactFiberScheduler.computeUniqueAsyncExpiration,
-    recalculateCurrentTime = _ReactFiberScheduler.recalculateCurrentTime,
-    computeExpirationForFiber = _ReactFiberScheduler.computeExpirationForFiber,
-    scheduleWork = _ReactFiberScheduler.scheduleWork,
-    requestWork = _ReactFiberScheduler.requestWork,
-    flushRoot = _ReactFiberScheduler.flushRoot,
-    batchedUpdates = _ReactFiberScheduler.batchedUpdates,
-    unbatchedUpdates = _ReactFiberScheduler.unbatchedUpdates,
-    flushSync = _ReactFiberScheduler.flushSync,
-    flushControlled = _ReactFiberScheduler.flushControlled,
-    deferredUpdates = _ReactFiberScheduler.deferredUpdates,
-    syncUpdates = _ReactFiberScheduler.syncUpdates,
-    interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
-    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
-    legacyContext = _ReactFiberScheduler.legacyContext;
-
-  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
-
-  function getContextForSubtree(parentComponent) {
-    if (!parentComponent) {
-      return emptyObject;
-    }
-
-    var fiber = get$1(parentComponent);
-    var parentContext = findCurrentUnmaskedContext(fiber);
-    return isContextProvider(fiber)
-      ? processChildContext(fiber, parentContext)
-      : parentContext;
-  }
-
-  function scheduleRootUpdate(current, element, expirationTime, callback) {
-    {
-      if (
-        ReactDebugCurrentFiber.phase === "render" &&
-        ReactDebugCurrentFiber.current !== null &&
-        !didWarnAboutNestedUpdates
-      ) {
-        didWarnAboutNestedUpdates = true;
-        warning(
+  var fiber = get$1(parentComponent);
+  var parentContext = findCurrentUnmaskedContext(fiber);
+  return isContextProvider(fiber)
+    ? processChildContext(fiber, parentContext)
+    : parentContext;
+}
+
+function scheduleRootUpdate(current, element, expirationTime, callback) {
+  {
+    if (
+      ReactDebugCurrentFiber.phase === "render" &&
+      ReactDebugCurrentFiber.current !== null &&
+      !didWarnAboutNestedUpdates
+    ) {
+      didWarnAboutNestedUpdates = true;
+      warning(
+        false,
+        "Render methods should be a pure function of props and state; " +
+          "triggering nested component updates from render is not allowed. " +
+          "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
+          "Check the render method of %s.",
+        getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
+      );
+    }
+  }
+
+  var update = createUpdate(expirationTime);
+  // Caution: React DevTools currently depends on this property
+  // being called "element".
+  update.payload = { element: element };
+
+  callback = callback === undefined ? null : callback;
+  if (callback !== null) {
+    !(typeof callback === "function")
+      ? warning(
           false,
-          "Render methods should be a pure function of props and state; " +
-            "triggering nested component updates from render is not allowed. " +
-            "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
-            "Check the render method of %s.",
-          getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
-        );
+          "render(...): Expected the last optional `callback` argument to be a " +
+            "function. Instead received: %s.",
+          callback
+        )
+      : void 0;
+    update.callback = callback;
+  }
+  enqueueUpdate(current, update, expirationTime);
+
+  scheduleWork(current, expirationTime);
+  return expirationTime;
+}
+
+function updateContainerAtExpirationTime(
+  element,
+  container,
+  parentComponent,
+  expirationTime,
+  callback
+) {
+  // TODO: If this is a nested container, this won't be the root.
+  var current = container.current;
+
+  {
+    if (ReactFiberInstrumentation_1.debugTool) {
+      if (current.alternate === null) {
+        ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
+      } else if (element === null) {
+        ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
+      } else {
+        ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
       }
     }
+  }
 
-    var update = createUpdate(expirationTime);
-    // Caution: React DevTools currently depends on this property
-    // being called "element".
-    update.payload = { element: element };
+  var context = getContextForSubtree(parentComponent);
+  if (container.context === null) {
+    container.context = context;
+  } else {
+    container.pendingContext = context;
+  }
 
-    callback = callback === undefined ? null : callback;
-    if (callback !== null) {
-      !(typeof callback === "function")
-        ? warning(
-            false,
-            "render(...): Expected the last optional `callback` argument to be a " +
-              "function. Instead received: %s.",
-            callback
-          )
-        : void 0;
-      update.callback = callback;
-    }
-    enqueueUpdate(current, update, expirationTime);
+  return scheduleRootUpdate(current, element, expirationTime, callback);
+}
 
-    scheduleWork(current, expirationTime);
-    return expirationTime;
+function findHostInstance$1(component) {
+  var fiber = get$1(component);
+  if (fiber === undefined) {
+    if (typeof component.render === "function") {
+      invariant(false, "Unable to find node on an unmounted component.");
+    } else {
+      invariant(
+        false,
+        "Argument appears to not be a ReactComponent. Keys: %s",
+        Object.keys(component)
+      );
+    }
+  }
+  var hostFiber = findCurrentHostFiber(fiber);
+  if (hostFiber === null) {
+    return null;
   }
+  return hostFiber.stateNode;
+}
+
+function createContainer(containerInfo, isAsync, hydrate) {
+  return createFiberRoot(containerInfo, isAsync, hydrate);
+}
 
-  function updateContainerAtExpirationTime(
+function updateContainer(element, container, parentComponent, callback) {
+  var current = container.current;
+  var currentTime = recalculateCurrentTime();
+  var expirationTime = computeExpirationForFiber(currentTime, current);
+  return updateContainerAtExpirationTime(
     element,
     container,
     parentComponent,
     expirationTime,
     callback
-  ) {
-    // TODO: If this is a nested container, this won't be the root.
-    var current = container.current;
-
-    {
-      if (ReactFiberInstrumentation_1.debugTool) {
-        if (current.alternate === null) {
-          ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
-        } else if (element === null) {
-          ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
-        } else {
-          ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
-        }
-      }
-    }
+  );
+}
 
-    var context = getContextForSubtree(parentComponent);
-    if (container.context === null) {
-      container.context = context;
-    } else {
-      container.pendingContext = context;
-    }
+function getPublicRootInstance(container) {
+  var containerFiber = container.current;
+  if (!containerFiber.child) {
+    return null;
+  }
+  switch (containerFiber.child.tag) {
+    case HostComponent:
+      return getPublicInstance(containerFiber.child.stateNode);
+    default:
+      return containerFiber.child.stateNode;
+  }
+}
 
-    return scheduleRootUpdate(current, element, expirationTime, callback);
+function findHostInstanceWithNoPortals(fiber) {
+  var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
+  if (hostFiber === null) {
+    return null;
   }
+  return hostFiber.stateNode;
+}
 
-  function findHostInstance(component) {
-    var fiber = get$1(component);
-    if (fiber === undefined) {
-      if (typeof component.render === "function") {
-        invariant(false, "Unable to find node on an unmounted component.");
-      } else {
-        invariant(
-          false,
-          "Argument appears to not be a ReactComponent. Keys: %s",
-          Object.keys(component)
-        );
+function injectIntoDevTools(devToolsConfig) {
+  var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+
+  return injectInternals(
+    Object.assign({}, devToolsConfig, {
+      findHostInstanceByFiber: function(fiber) {
+        var hostFiber = findCurrentHostFiber(fiber);
+        if (hostFiber === null) {
+          return null;
+        }
+        return hostFiber.stateNode;
+      },
+      findFiberByHostInstance: function(instance) {
+        if (!findFiberByHostInstance) {
+          // Might not be implemented by the renderer.
+          return null;
+        }
+        return findFiberByHostInstance(instance);
       }
-    }
-    var hostFiber = findCurrentHostFiber(fiber);
-    if (hostFiber === null) {
-      return null;
-    }
-    return hostFiber.stateNode;
-  }
+    })
+  );
+}
+
+// This file intentionally does *not* have the Flow annotation.
+// Don't add it. See `./inline-typed.js` for an explanation.
+
+var ReactFabricRenderer = Object.freeze({
+  updateContainerAtExpirationTime: updateContainerAtExpirationTime,
+  createContainer: createContainer,
+  updateContainer: updateContainer,
+  flushRoot: flushRoot,
+  requestWork: requestWork,
+  computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+  batchedUpdates: batchedUpdates$1,
+  unbatchedUpdates: unbatchedUpdates,
+  deferredUpdates: deferredUpdates,
+  syncUpdates: syncUpdates,
+  interactiveUpdates: interactiveUpdates$1,
+  flushInteractiveUpdates: flushInteractiveUpdates$1,
+  flushControlled: flushControlled,
+  flushSync: flushSync,
+  getPublicRootInstance: getPublicRootInstance,
+  findHostInstance: findHostInstance$1,
+  findHostInstanceWithNoPortals: findHostInstanceWithNoPortals,
+  injectIntoDevTools: injectIntoDevTools
+});
+
+function createPortal(
+  children,
+  containerInfo,
+  // TODO: figure out the API for cross-renderer implementation.
+  implementation
+) {
+  var key =
+    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
 
   return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      return createFiberRoot(containerInfo, isAsync, hydrate);
+    // This tag allow us to uniquely identify this as a React Portal
+    $$typeof: REACT_PORTAL_TYPE,
+    key: key == null ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+
+// TODO: this is special because it gets imported during build.
+
+var ReactVersion = "16.4.1";
+
+// Modules provided by RN:
+var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
+  /**
+   * `NativeMethodsMixin` provides methods to access the underlying native
+   * component directly. This can be useful in cases when you want to focus
+   * a view or measure its on-screen dimensions, for example.
+   *
+   * The methods described here are available on most of the default components
+   * provided by React Native. Note, however, that they are *not* available on
+   * composite components that aren't directly backed by a native view. This will
+   * generally include most components that you define in your own app. For more
+   * information, see [Direct
+   * Manipulation](docs/direct-manipulation.html).
+   *
+   * Note the Flow $Exact<> syntax is required to support mixins.
+   * React createClass mixins can only be used with exact types.
+   */
+  var NativeMethodsMixin = {
+    /**
+     * Determines the location on screen, width, and height of the given view and
+     * returns the values via an async callback. If successful, the callback will
+     * be called with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native. If you need the measurements as soon as
+     * possible, consider using the [`onLayout`
+     * prop](docs/view.html#onlayout) instead.
+     */
+    measure: function(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
     },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current;
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(currentTime, current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        expirationTime,
-        callback
+
+    /**
+     * Determines the location of the given view in the window and returns the
+     * values via an async callback. If the React root view is embedded in
+     * another native view, this will give you the absolute coordinates. If
+     * successful, the callback will be called with the following
+     * arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * Note that these measurements are not available until after the rendering
+     * has been completed in native.
+     */
+    measureInWindow: function(callback) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
       );
     },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
+
+    /**
+     * Like [`measure()`](#measure), but measures the view relative an ancestor,
+     * specified as `relativeToNativeNode`. This means that the returned x, y
+     * are relative to the origin x, y of the ancestor view.
+     *
+     * As always, to obtain a native node handle for a component, you can use
+     * `findNodeHandle(component)`.
+     */
+    measureLayout: function(
+      relativeToNativeNode,
+      onSuccess,
+      onFail /* currently unused */
     ) {
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        expirationTime,
-        callback
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
       );
     },
 
-    flushRoot: flushRoot,
-
-    requestWork: requestWork,
-
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-
-    batchedUpdates: batchedUpdates,
-
-    unbatchedUpdates: unbatchedUpdates,
-
-    deferredUpdates: deferredUpdates,
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
+    setNativeProps: function(nativeProps) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
 
-    syncUpdates: syncUpdates,
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
 
-    interactiveUpdates: interactiveUpdates,
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
 
-    flushInteractiveUpdates: flushInteractiveUpdates,
+      var viewConfig = maybeInstance.viewConfig;
 
-    flushControlled: flushControlled,
+      {
+        warnForStyleProps(nativeProps, viewConfig.validAttributes);
+      }
 
-    flushSync: flushSync,
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
 
-    getPublicRootInstance: function(container) {
-      var containerFiber = container.current;
-      if (!containerFiber.child) {
-        return null;
-      }
-      switch (containerFiber.child.tag) {
-        case HostComponent:
-          return getPublicInstance(containerFiber.child.stateNode);
-        default:
-          return containerFiber.child.stateNode;
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
       }
     },
 
-    findHostInstance: findHostInstance,
-
-    findHostInstanceWithNoPortals: function(fiber) {
-      var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
-      if (hostFiber === null) {
-        return null;
-      }
-      return hostFiber.stateNode;
+    /**
+     * Requests focus for the given input or view. The exact behavior triggered
+     * will depend on the platform and type of view.
+     */
+    focus: function() {
+      TextInputState.focusTextInput(findNodeHandle(this));
     },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            var hostFiber = findCurrentHostFiber(fiber);
-            if (hostFiber === null) {
-              return null;
-            }
-            return hostFiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            if (!findFiberByHostInstance) {
-              // Might not be implemented by the renderer.
-              return null;
-            }
-            return findFiberByHostInstance(instance);
-          }
-        })
-      );
+
+    /**
+     * Removes focus from an input or view. This is the opposite of `focus()`.
+     */
+    blur: function() {
+      TextInputState.blurTextInput(findNodeHandle(this));
     }
   };
-};
-
-var ReactFiberReconciler$2 = Object.freeze({
-  default: ReactFiberReconciler$1
-});
-
-var ReactFiberReconciler$3 =
-  (ReactFiberReconciler$2 && ReactFiberReconciler$1) || ReactFiberReconciler$2;
-
-// TODO: bundle Flow types with the package.
-
-// TODO: decide on the top-level export form.
-// This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3.default
-  ? ReactFiberReconciler$3.default
-  : ReactFiberReconciler$3;
 
-var hasNativePerformanceNow =
-  typeof performance === "object" && typeof performance.now === "function";
-
-var now = hasNativePerformanceNow
-  ? function() {
-      return performance.now();
-    }
-  : function() {
-      return Date.now();
+  {
+    // hide this from Flow since we can't define these properties outside of
+    // true without actually implementing them (setting them to undefined
+    // isn't allowed by ReactClass)
+    var NativeMethodsMixin_DEV = NativeMethodsMixin;
+    invariant(
+      !NativeMethodsMixin_DEV.componentWillMount &&
+        !NativeMethodsMixin_DEV.componentWillReceiveProps &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillMount &&
+        !NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps,
+      "Do not override existing functions."
+    );
+    // TODO (bvaughn) Remove cWM and cWRP in a future version of React Native,
+    // Once these lifecycles have been remove from the reconciler.
+    NativeMethodsMixin_DEV.componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.componentWillReceiveProps = function(newProps) {
+      throwOnStylesProp(this, newProps);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillMount = function() {
+      throwOnStylesProp(this, this.props);
+    };
+    NativeMethodsMixin_DEV.UNSAFE_componentWillReceiveProps = function(
+      newProps
+    ) {
+      throwOnStylesProp(this, newProps);
     };
 
-var scheduledCallback = null;
-var frameDeadline = 0;
-
-var frameDeadlineObject = {
-  timeRemaining: function() {
-    return frameDeadline - now();
-  },
-  didTimeout: false
-};
-
-function setTimeoutCallback() {
-  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
-  // React API probably changing to boolean rather than time remaining.
-  // Longer-term plan is to rewrite this using shared memory,
-  // And just return the value of the bit as the boolean.
-  frameDeadline = now() + 5;
-
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  if (callback !== null) {
-    callback(frameDeadlineObject);
+    // React may warn about cWM/cWRP/cWU methods being deprecated.
+    // Add a flag to suppress these warnings for this special case.
+    // TODO (bvaughn) Remove this flag once the above methods have been removed.
+    NativeMethodsMixin_DEV.componentWillMount.__suppressDeprecationWarning = true;
+    NativeMethodsMixin_DEV.componentWillReceiveProps.__suppressDeprecationWarning = true;
   }
-}
-
-// RN has a poor polyfill for requestIdleCallback so we aren't using it.
-// This implementation is only intended for short-term use anyway.
-// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
-function scheduleDeferredCallback(callback) {
-  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
-  scheduledCallback = callback;
-  return setTimeout(setTimeoutCallback, 1);
-}
-
-function cancelDeferredCallback(callbackID) {
-  scheduledCallback = null;
-  clearTimeout(callbackID);
-}
 
-function dispatchEvent(target, topLevelType, nativeEvent) {
-  var targetFiber = target;
-  batchedUpdates(function() {
-    runExtractedEventsInBatch(
-      topLevelType,
-      targetFiber,
-      nativeEvent,
-      nativeEvent.target
-    );
-  });
-  // React Native doesn't use ReactControlledComponent but if it did, here's
-  // where it would do it.
-}
+  return NativeMethodsMixin;
+};
 
 function _classCallCheck$1(instance, Constructor) {
   if (!(instance instanceof Constructor)) {
@@ -14471,292 +14262,210 @@ function _classCallCheck$1(instance, Constructor) {
   }
 }
 
-// Modules provided by RN:
-// Counter for uniquely identifying views.
-// % 10 === 1 means it is a rootTag.
-// % 2 === 0 means it is a Fabric tag.
-// This means that they never overlap.
-var nextReactTag = 2;
-
-// TODO: Remove this conditional once all changes have propagated.
-if (FabricUIManager.registerEventHandler) {
-  /**
-   * Register the event emitter with the native bridge
-   */
-  FabricUIManager.registerEventHandler(dispatchEvent);
-}
-
-/**
- * This is used for refs on host components.
- */
-
-var ReactFabricHostComponent = (function() {
-  function ReactFabricHostComponent(tag, viewConfig, props) {
-    _classCallCheck$1(this, ReactFabricHostComponent);
-
-    this._nativeTag = tag;
-    this.viewConfig = viewConfig;
-    this.currentProps = props;
-  }
-
-  ReactFabricHostComponent.prototype.blur = function blur() {
-    TextInputState.blurTextInput(this._nativeTag);
-  };
-
-  ReactFabricHostComponent.prototype.focus = function focus() {
-    TextInputState.focusTextInput(this._nativeTag);
-  };
-
-  ReactFabricHostComponent.prototype.measure = function measure(callback) {
-    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-  };
-
-  ReactFabricHostComponent.prototype.measureInWindow = function measureInWindow(
-    callback
-  ) {
-    UIManager.measureInWindow(
-      this._nativeTag,
-      mountSafeCallback(this, callback)
+function _possibleConstructorReturn(self, call) {
+  if (!self) {
+    throw new ReferenceError(
+      "this hasn't been initialised - super() hasn't been called"
     );
-  };
+  }
+  return call && (typeof call === "object" || typeof call === "function")
+    ? call
+    : self;
+}
 
-  ReactFabricHostComponent.prototype.measureLayout = function measureLayout(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      this._nativeTag,
-      relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
+function _inherits(subClass, superClass) {
+  if (typeof superClass !== "function" && superClass !== null) {
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
     );
-  };
-
-  ReactFabricHostComponent.prototype.setNativeProps = function setNativeProps(
-    nativeProps
-  ) {
-    {
-      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
+  }
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: false,
+      writable: true,
+      configurable: true
     }
+  });
+  if (superClass)
+    Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass);
+}
 
-    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
+// Modules provided by RN:
+var ReactNativeComponent = function(findNodeHandle, findHostInstance) {
+  /**
+   * Superclass that provides methods to access the underlying native component.
+   * This can be useful when you want to focus a view or measure its dimensions.
+   *
+   * Methods implemented by this class are available on most default components
+   * provided by React Native. However, they are *not* available on composite
+   * components that are not directly backed by a native view. For more
+   * information, see [Direct Manipulation](docs/direct-manipulation.html).
+   *
+   * @abstract
+   */
+  var ReactNativeComponent = (function(_React$Component) {
+    _inherits(ReactNativeComponent, _React$Component);
 
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        this._nativeTag,
-        this.viewConfig.uiViewClassName,
-        updatePayload
+    function ReactNativeComponent() {
+      _classCallCheck$1(this, ReactNativeComponent);
+
+      return _possibleConstructorReturn(
+        this,
+        _React$Component.apply(this, arguments)
       );
     }
-  };
-
-  return ReactFabricHostComponent;
-})();
 
-var ReactFabricHostConfig = {
-  appendInitialChild: function(parentInstance, child) {
-    FabricUIManager.appendChild(parentInstance.node, child.node);
-  },
-  createInstance: function(
-    type,
-    props,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    var tag = nextReactTag;
-    nextReactTag += 2;
+    /**
+     * Removes focus. This is the opposite of `focus()`.
+     */
 
-    var viewConfig = ReactNativeViewConfigRegistry.get(type);
+    /**
+     * Due to bugs in Flow's handling of React.createClass, some fields already
+     * declared in the base class need to be redeclared below.
+     */
+    ReactNativeComponent.prototype.blur = function blur() {
+      TextInputState.blurTextInput(findNodeHandle(this));
+    };
 
-    {
-      for (var key in viewConfig.validAttributes) {
-        if (props.hasOwnProperty(key)) {
-          deepFreezeAndThrowOnMutationInDev(props[key]);
-        }
-      }
-    }
+    /**
+     * Requests focus. The exact behavior depends on the platform and view.
+     */
 
-    invariant(
-      type !== "RCTView" || !hostContext.isInAParentText,
-      "Nesting of <View> within <Text> is not currently supported."
-    );
+    ReactNativeComponent.prototype.focus = function focus() {
+      TextInputState.focusTextInput(findNodeHandle(this));
+    };
 
-    var updatePayload = create(props, viewConfig.validAttributes);
+    /**
+     * Measures the on-screen location and dimensions. If successful, the callback
+     * will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *  - pageX
+     *  - pageY
+     *
+     * These values are not available until after natives rendering completes. If
+     * you need the measurements as soon as possible, consider using the
+     * [`onLayout` prop](docs/view.html#onlayout) instead.
+     */
 
-    var node = FabricUIManager.createNode(
-      tag, // reactTag
-      viewConfig.uiViewClassName, // viewName
-      rootContainerInstance, // rootTag
-      updatePayload, // props
-      internalInstanceHandle // internalInstanceHandle
-    );
+    ReactNativeComponent.prototype.measure = function measure(callback) {
+      UIManager.measure(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
+    };
 
-    var component = new ReactFabricHostComponent(tag, viewConfig, props);
+    /**
+     * Measures the on-screen location and dimensions. Even if the React Native
+     * root view is embedded within another native view, this method will give you
+     * the absolute coordinates measured from the window. If successful, the
+     * callback will be called asynchronously with the following arguments:
+     *
+     *  - x
+     *  - y
+     *  - width
+     *  - height
+     *
+     * These values are not available until after natives rendering completes.
+     */
 
-    return {
-      node: node,
-      canonical: component
+    ReactNativeComponent.prototype.measureInWindow = function measureInWindow(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        findNodeHandle(this),
+        mountSafeCallback(this, callback)
+      );
     };
-  },
-  createTextInstance: function(
-    text,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    invariant(
-      hostContext.isInAParentText,
-      "Text strings must be rendered within a <Text> component."
-    );
-
-    var tag = nextReactTag;
-    nextReactTag += 2;
 
-    var node = FabricUIManager.createNode(
-      tag, // reactTag
-      "RCTRawText", // viewName
-      rootContainerInstance, // rootTag
-      { text: text }, // props
-      internalInstanceHandle // instance handle
-    );
+    /**
+     * Similar to [`measure()`](#measure), but the resulting location will be
+     * relative to the supplied ancestor's location.
+     *
+     * Obtain a native node handle with `ReactNative.findNodeHandle(component)`.
+     */
 
-    return {
-      node: node
+    ReactNativeComponent.prototype.measureLayout = function measureLayout(
+      relativeToNativeNode,
+      onSuccess,
+      onFail /* currently unused */
+    ) {
+      UIManager.measureLayout(
+        findNodeHandle(this),
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
     };
-  },
-  finalizeInitialChildren: function(
-    parentInstance,
-    type,
-    props,
-    rootContainerInstance
-  ) {
-    return false;
-  },
-  getRootHostContext: function(rootContainerInstance) {
-    return { isInAParentText: false };
-  },
-  getChildHostContext: function(parentHostContext, type) {
-    var prevIsInAParentText = parentHostContext.isInAParentText;
-    var isInAParentText =
-      type === "AndroidTextInput" || // Android
-      type === "RCTMultilineTextInputView" || // iOS
-      type === "RCTSinglelineTextInputView" || // iOS
-      type === "RCTText" ||
-      type === "RCTVirtualText";
-
-    if (prevIsInAParentText !== isInAParentText) {
-      return { isInAParentText: isInAParentText };
-    } else {
-      return parentHostContext;
-    }
-  },
-  getPublicInstance: function(instance) {
-    return instance.canonical;
-  },
 
-  now: now,
+    /**
+     * This function sends props straight to native. They will not participate in
+     * future diff process - this means that if you do not include them in the
+     * next render, they will remain active (see [Direct
+     * Manipulation](docs/direct-manipulation.html)).
+     */
 
-  // The Fabric renderer is secondary to the existing React Native renderer.
-  isPrimaryRenderer: false,
+    ReactNativeComponent.prototype.setNativeProps = function setNativeProps(
+      nativeProps
+    ) {
+      // Class components don't have viewConfig -> validateAttributes.
+      // Nor does it make sense to set native props on a non-native component.
+      // Instead, find the nearest host component and set props on it.
+      // Use findNodeHandle() rather than ReactNative.findNodeHandle() because
+      // We want the instance/wrapper (not the native tag).
+      var maybeInstance = void 0;
 
-  prepareForCommit: function() {
-    // Noop
-  },
-  prepareUpdate: function(
-    instance,
-    type,
-    oldProps,
-    newProps,
-    rootContainerInstance,
-    hostContext
-  ) {
-    var viewConfig = instance.canonical.viewConfig;
-    var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
-    // TODO: If the event handlers have changed, we need to update the current props
-    // in the commit phase but there is no host config hook to do it yet.
-    return updatePayload;
-  },
-  resetAfterCommit: function() {
-    // Noop
-  },
+      // Fiber errors if findNodeHandle is called for an umounted component.
+      // Tests using ReactTestRenderer will trigger this case indirectly.
+      // Mimicking stack behavior, we should silently ignore this case.
+      // TODO Fix ReactTestRenderer so we can remove this try/catch.
+      try {
+        maybeInstance = findHostInstance(this);
+      } catch (error) {}
 
-  scheduleDeferredCallback: scheduleDeferredCallback,
-  cancelDeferredCallback: cancelDeferredCallback,
+      // If there is no host component beneath this we should fail silently.
+      // This is not an error; it could mean a class component rendered null.
+      if (maybeInstance == null) {
+        return;
+      }
 
-  shouldDeprioritizeSubtree: function(type, props) {
-    return false;
-  },
-  shouldSetTextContent: function(type, props) {
-    // TODO (bvaughn) Revisit this decision.
-    // Always returning false simplifies the createInstance() implementation,
-    // But creates an additional child Fiber for raw text children.
-    // No additional native views are created though.
-    // It's not clear to me which is better so I'm deferring for now.
-    // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
-    return false;
-  },
+      var viewConfig =
+        maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
 
-  persistence: {
-    cloneInstance: function(
-      instance,
-      updatePayload,
-      type,
-      oldProps,
-      newProps,
-      internalInstanceHandle,
-      keepChildren,
-      recyclableInstance
-    ) {
-      var node = instance.node;
-      var clone = void 0;
-      if (keepChildren) {
-        if (updatePayload !== null) {
-          clone = FabricUIManager.cloneNodeWithNewProps(
-            node,
-            updatePayload,
-            internalInstanceHandle
-          );
-        } else {
-          clone = FabricUIManager.cloneNode(node, internalInstanceHandle);
-        }
-      } else {
-        if (updatePayload !== null) {
-          clone = FabricUIManager.cloneNodeWithNewChildrenAndProps(
-            node,
-            updatePayload,
-            internalInstanceHandle
-          );
-        } else {
-          clone = FabricUIManager.cloneNodeWithNewChildren(
-            node,
-            internalInstanceHandle
-          );
-        }
+      var updatePayload = create(nativeProps, viewConfig.validAttributes);
+
+      // Avoid the overhead of bridge calls if there's no update.
+      // This is an expensive no-op for Android, and causes an unnecessary
+      // view invalidation for certain components (eg RCTTextInput) on iOS.
+      if (updatePayload != null) {
+        UIManager.updateView(
+          maybeInstance._nativeTag,
+          viewConfig.uiViewClassName,
+          updatePayload
+        );
       }
-      return {
-        node: clone,
-        canonical: instance.canonical
-      };
-    },
-    createContainerChildSet: function(container) {
-      return FabricUIManager.createChildSet(container);
-    },
-    appendChildToContainerChildSet: function(childSet, child) {
-      FabricUIManager.appendChildToSet(childSet, child.node);
-    },
-    finalizeContainerChildren: function(container, newChildren) {
-      FabricUIManager.completeRoot(container, newChildren);
-    },
-    replaceContainerChildren: function(container, newChildren) {}
-  }
+    };
+
+    return ReactNativeComponent;
+  })(React.Component);
+
+  // eslint-disable-next-line no-unused-expressions
+
+  return ReactNativeComponent;
 };
 
-var ReactFabricRenderer = reactReconciler(ReactFabricHostConfig);
+var instanceCache = {};
+
+function getInstanceFromTag(tag) {
+  return instanceCache[tag] || null;
+}
 
 // Module provided by RN:
 var getInspectorDataForViewTag = void 0;
@@ -14860,7 +14569,7 @@ var getInspectorDataForViewTag = void 0;
   };
 }
 
-var findHostInstance = ReactFabricRenderer.findHostInstance;
+var findHostInstance = findHostInstance$1;
 
 function findNodeHandle(componentOrHandle) {
   {
@@ -14898,6 +14607,8 @@ function findNodeHandle(componentOrHandle) {
   if (hostInstance == null) {
     return hostInstance;
   }
+  // TODO: the code is right but the types here are wrong.
+  // https://github.com/facebook/react/pull/12863
   if (hostInstance.canonical) {
     // Fabric
     return hostInstance.canonical._nativeTag;
@@ -14920,18 +14631,18 @@ var ReactFabric = {
     if (!root) {
       // TODO (bvaughn): If we decide to keep the wrapper component,
       // We could create a wrapper for containerTag as well to reduce special casing.
-      root = ReactFabricRenderer.createContainer(containerTag, false, false);
+      root = createContainer(containerTag, false, false);
       roots.set(containerTag, root);
     }
-    ReactFabricRenderer.updateContainer(element, root, null, callback);
+    updateContainer(element, root, null, callback);
 
-    return ReactFabricRenderer.getPublicRootInstance(root);
+    return getPublicRootInstance(root);
   },
   unmountComponentAtNode: function(containerTag) {
     var root = roots.get(containerTag);
     if (root) {
       // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
-      ReactFabricRenderer.updateContainer(null, root, null, function() {
+      updateContainer(null, root, null, function() {
         roots.delete(containerTag);
       });
     }
@@ -14945,14 +14656,12 @@ var ReactFabric = {
 
   __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
     // Used as a mixin in many createClass-based components
-    NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
-    // Used by react-native-github/Libraries/ components
-    ReactNativeComponentTree: ReactNativeComponentTree // ScrollResponder
+    NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance)
   }
 };
 
-ReactFabricRenderer.injectIntoDevTools({
-  findFiberByHostInstance: getInstanceFromTag,
+injectIntoDevTools({
+  findFiberByHostInstance: getInstanceFromInstance,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 1,
   version: ReactVersion,
diff --git a/Libraries/Renderer/oss/ReactFabric-prod.js b/Libraries/Renderer/oss/ReactFabric-prod.js
index 6f17e0bfb3a8..b64b8908f410 100644
--- a/Libraries/Renderer/oss/ReactFabric-prod.js
+++ b/Libraries/Renderer/oss/ReactFabric-prod.js
@@ -13,17 +13,15 @@
 "use strict";
 require("InitializeCore");
 var invariant = require("fbjs/lib/invariant"),
-  emptyFunction = require("fbjs/lib/emptyFunction"),
   ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
   UIManager = require("UIManager"),
-  TextInputState = require("TextInputState"),
-  deepDiffer = require("deepDiffer"),
-  flattenStyle = require("flattenStyle"),
   React = require("react"),
   emptyObject = require("fbjs/lib/emptyObject"),
-  shallowEqual = require("fbjs/lib/shallowEqual"),
-  ExceptionsManager = require("ExceptionsManager"),
-  FabricUIManager = require("FabricUIManager");
+  deepDiffer = require("deepDiffer"),
+  flattenStyle = require("flattenStyle"),
+  TextInputState = require("TextInputState"),
+  FabricUIManager = require("FabricUIManager"),
+  ExceptionsManager = require("ExceptionsManager");
 function invokeGuardedCallback(name, func, context, a, b, c, d, e, f) {
   this._hasCaughtError = !1;
   this._caughtError = null;
@@ -350,21 +348,14 @@ function accumulateDirectDispatchesSingle(event) {
   }
 }
 var shouldBeReleasedProperties = "dispatchConfig _targetInst nativeEvent isDefaultPrevented isPropagationStopped _dispatchListeners _dispatchInstances".split(
-    " "
-  ),
-  EventInterface = {
-    type: null,
-    target: null,
-    currentTarget: emptyFunction.thatReturnsNull,
-    eventPhase: null,
-    bubbles: null,
-    cancelable: null,
-    timeStamp: function(event) {
-      return event.timeStamp || Date.now();
-    },
-    defaultPrevented: null,
-    isTrusted: null
-  };
+  " "
+);
+function functionThatReturnsTrue() {
+  return !0;
+}
+function functionThatReturnsFalse() {
+  return !1;
+}
 function SyntheticEvent(
   dispatchConfig,
   targetInst,
@@ -385,9 +376,9 @@ function SyntheticEvent(
   this.isDefaultPrevented = (null != nativeEvent.defaultPrevented
   ? nativeEvent.defaultPrevented
   : !1 === nativeEvent.returnValue)
-    ? emptyFunction.thatReturnsTrue
-    : emptyFunction.thatReturnsFalse;
-  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
+    ? functionThatReturnsTrue
+    : functionThatReturnsFalse;
+  this.isPropagationStopped = functionThatReturnsFalse;
   return this;
 }
 Object.assign(SyntheticEvent.prototype, {
@@ -398,7 +389,7 @@ Object.assign(SyntheticEvent.prototype, {
       (event.preventDefault
         ? event.preventDefault()
         : "unknown" !== typeof event.returnValue && (event.returnValue = !1),
-      (this.isDefaultPrevented = emptyFunction.thatReturnsTrue));
+      (this.isDefaultPrevented = functionThatReturnsTrue));
   },
   stopPropagation: function() {
     var event = this.nativeEvent;
@@ -406,12 +397,12 @@ Object.assign(SyntheticEvent.prototype, {
       (event.stopPropagation
         ? event.stopPropagation()
         : "unknown" !== typeof event.cancelBubble && (event.cancelBubble = !0),
-      (this.isPropagationStopped = emptyFunction.thatReturnsTrue));
+      (this.isPropagationStopped = functionThatReturnsTrue));
   },
   persist: function() {
-    this.isPersistent = emptyFunction.thatReturnsTrue;
+    this.isPersistent = functionThatReturnsTrue;
   },
-  isPersistent: emptyFunction.thatReturnsFalse,
+  isPersistent: functionThatReturnsFalse,
   destructor: function() {
     var Interface = this.constructor.Interface,
       propName;
@@ -424,7 +415,21 @@ Object.assign(SyntheticEvent.prototype, {
       this[shouldBeReleasedProperties[Interface]] = null;
   }
 });
-SyntheticEvent.Interface = EventInterface;
+SyntheticEvent.Interface = {
+  type: null,
+  target: null,
+  currentTarget: function() {
+    return null;
+  },
+  eventPhase: null,
+  bubbles: null,
+  cancelable: null,
+  timeStamp: function(event) {
+    return event.timeStamp || Date.now();
+  },
+  defaultPrevented: null,
+  isTrusted: null
+};
 SyntheticEvent.extend = function(Interface) {
   function E() {}
   function Class() {
@@ -984,55 +989,47 @@ var eventTypes$1 = {
       else return null;
       return topLevelType;
     }
-  },
-  instanceCache = {},
-  instanceProps = {};
-function getInstanceFromTag(tag) {
-  return "number" === typeof tag ? instanceCache[tag] || null : tag;
-}
-var ReactNativeComponentTree = Object.freeze({
-  precacheFiberNode: function(hostInst, tag) {
-    instanceCache[tag] = hostInst;
-  },
-  uncacheFiberNode: function(tag) {
-    delete instanceCache[tag];
-    delete instanceProps[tag];
-  },
-  getClosestInstanceFromNode: getInstanceFromTag,
-  getInstanceFromNode: getInstanceFromTag,
-  getNodeFromInstance: function(inst) {
-    var tag = inst.stateNode._nativeTag;
-    void 0 === tag && (tag = inst.stateNode.canonical._nativeTag);
-    invariant(tag, "All native instances should have a tag.");
-    return tag;
-  },
-  getFiberCurrentPropsFromNode: function(stateNode) {
-    return instanceProps[stateNode._nativeTag] || null;
-  },
-  updateFiberProps: function(tag, props) {
-    instanceProps[tag] = props;
-  }
-});
+  };
 injection.injectEventPluginOrder([
   "ResponderEventPlugin",
   "ReactNativeBridgeEventPlugin"
 ]);
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
+function getInstanceFromInstance(instanceHandle) {
+  return instanceHandle;
+}
+var Injected$jscomp$inline_574 = {
+  getClosestInstanceFromNode: getInstanceFromInstance,
+  getInstanceFromNode: getInstanceFromInstance,
+  getNodeFromInstance: function(inst) {
+    inst = inst.stateNode.canonical._nativeTag;
+    invariant(inst, "All native instances should have a tag.");
+    return inst;
+  },
+  getFiberCurrentPropsFromNode: function(inst) {
+    return inst.canonical.currentProps;
+  }
+};
 getFiberCurrentPropsFromNode =
-  ReactNativeComponentTree.getFiberCurrentPropsFromNode;
-getInstanceFromNode = ReactNativeComponentTree.getInstanceFromNode;
-getNodeFromInstance = ReactNativeComponentTree.getNodeFromInstance;
+  Injected$jscomp$inline_574.getFiberCurrentPropsFromNode;
+getInstanceFromNode = Injected$jscomp$inline_574.getInstanceFromNode;
+getNodeFromInstance = Injected$jscomp$inline_574.getNodeFromInstance;
 ResponderEventPlugin.injection.injectGlobalResponderHandler({
   onChange: function(from, to, blockNativeResponder) {
     null !== to
-      ? UIManager.setJSResponder(to.stateNode._nativeTag, blockNativeResponder)
+      ? UIManager.setJSResponder(
+          to.stateNode.canonical._nativeTag,
+          blockNativeResponder
+        )
       : UIManager.clearJSResponder();
   }
 });
-injection.injectEventPluginsByName({
-  ResponderEventPlugin: ResponderEventPlugin,
-  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
-});
-var hasSymbol = "function" === typeof Symbol && Symbol.for,
+var ReactCurrentOwner =
+    React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner,
+  hasSymbol = "function" === typeof Symbol && Symbol.for,
   REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
   REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
   REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
@@ -1052,53 +1049,175 @@ function getIteratorFn(maybeIterable) {
     maybeIterable["@@iterator"];
   return "function" === typeof maybeIterable ? maybeIterable : null;
 }
-function createPortal(children, containerInfo, implementation) {
-  var key =
-    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
-  return {
-    $$typeof: REACT_PORTAL_TYPE,
-    key: null == key ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
+function getComponentName(fiber) {
+  var type = fiber.type;
+  if ("function" === typeof type) return type.displayName || type.name;
+  if ("string" === typeof type) return type;
+  switch (type) {
+    case REACT_ASYNC_MODE_TYPE:
+      return "AsyncMode";
+    case REACT_CONTEXT_TYPE:
+      return "Context.Consumer";
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_PROFILER_TYPE:
+      return "Profiler(" + fiber.pendingProps.id + ")";
+    case REACT_PROVIDER_TYPE:
+      return "Context.Provider";
+    case REACT_STRICT_MODE_TYPE:
+      return "StrictMode";
+    case REACT_TIMEOUT_TYPE:
+      return "Timeout";
+  }
+  if ("object" === typeof type && null !== type)
+    switch (type.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        return (
+          (fiber = type.render.displayName || type.render.name || ""),
+          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
+        );
+    }
+  return null;
 }
-var restoreTarget = null,
-  restoreQueue = null;
-function restoreStateOfTarget(target) {
-  if ((target = getInstanceFromNode(target))) {
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (fiber.alternate) for (; node.return; ) node = node.return;
+  else {
+    if (0 !== (node.effectTag & 2)) return 1;
+    for (; node.return; )
+      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
+  }
+  return 3 === node.tag ? 2 : 3;
+}
+function assertIsMounted(fiber) {
+  invariant(
+    2 === isFiberMountedImpl(fiber),
+    "Unable to find node on an unmounted component."
+  );
+}
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate)
+    return (
+      (alternate = isFiberMountedImpl(fiber)),
+      invariant(
+        3 !== alternate,
+        "Unable to find node on an unmounted component."
+      ),
+      1 === alternate ? null : fiber
+    );
+  for (var a = fiber, b = alternate; ; ) {
+    var parentA = a.return,
+      parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) break;
+    if (parentA.child === parentB.child) {
+      for (var child = parentA.child; child; ) {
+        if (child === a) return assertIsMounted(parentA), fiber;
+        if (child === b) return assertIsMounted(parentA), alternate;
+        child = child.sibling;
+      }
+      invariant(!1, "Unable to find node on an unmounted component.");
+    }
+    if (a.return !== b.return) (a = parentA), (b = parentB);
+    else {
+      child = !1;
+      for (var _child = parentA.child; _child; ) {
+        if (_child === a) {
+          child = !0;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          child = !0;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!child) {
+        for (_child = parentB.child; _child; ) {
+          if (_child === a) {
+            child = !0;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            child = !0;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          child,
+          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
+        );
+      }
+    }
     invariant(
-      null,
-      "Fiber needs to be injected to handle a fiber target for controlled events. This error is likely caused by a bug in React. Please file an issue."
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
     );
-    var props = getFiberCurrentPropsFromNode(target.stateNode);
-    null.restoreControlledState(target.stateNode, target.type, props);
   }
+  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
+  return a.stateNode.current === a ? fiber : alternate;
 }
-function _batchedUpdates(fn, bookkeeping) {
-  return fn(bookkeeping);
+function findCurrentHostFiber(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child) (node.child.return = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+  return null;
 }
-function _flushInteractiveUpdates() {}
-var isBatching = !1;
-function batchedUpdates(fn, bookkeeping) {
-  if (isBatching) return fn(bookkeeping);
-  isBatching = !0;
-  try {
-    return _batchedUpdates(fn, bookkeeping);
-  } finally {
-    if (((isBatching = !1), null !== restoreTarget || null !== restoreQueue))
-      if (
-        (_flushInteractiveUpdates(),
-        restoreTarget &&
-          ((bookkeeping = restoreTarget),
-          (fn = restoreQueue),
-          (restoreQueue = restoreTarget = null),
-          restoreStateOfTarget(bookkeeping),
-          fn))
-      )
-        for (bookkeeping = 0; bookkeeping < fn.length; bookkeeping++)
-          restoreStateOfTarget(fn[bookkeeping]);
+function findCurrentHostFiberWithNoPortals(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child && 4 !== node.tag)
+      (node.child.return = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
   }
+  return null;
+}
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (callback) {
+      if ("boolean" === typeof context.__isMounted) {
+        if (!context.__isMounted) return;
+      } else if (
+        "function" === typeof context.isMounted &&
+        !context.isMounted()
+      )
+        return;
+      return callback.apply(context, arguments);
+    }
+  };
 }
 var emptyObject$1 = {},
   removedKeys = null,
@@ -1318,199 +1437,310 @@ function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
               )))));
   return updatePayload;
 }
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (callback) {
-      if ("boolean" === typeof context.__isMounted) {
-        if (!context.__isMounted) return;
-      } else if (
-        "function" === typeof context.isMounted &&
-        !context.isMounted()
-      )
-        return;
-      return callback.apply(context, arguments);
-    }
-  };
-}
-function _inherits(subClass, superClass) {
-  if ("function" !== typeof superClass && null !== superClass)
-    throw new TypeError(
-      "Super expression must either be null or a function, not " +
-        typeof superClass
+var now$1 =
+    "object" === typeof performance && "function" === typeof performance.now
+      ? function() {
+          return performance.now();
+        }
+      : function() {
+          return Date.now();
+        },
+  scheduledCallback = null,
+  frameDeadline = 0,
+  frameDeadlineObject = {
+    timeRemaining: function() {
+      return frameDeadline - now$1();
+    },
+    didTimeout: !1
+  };
+function setTimeoutCallback() {
+  frameDeadline = now$1() + 5;
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  null !== callback && callback(frameDeadlineObject);
+}
+var restoreTarget = null,
+  restoreQueue = null;
+function restoreStateOfTarget(target) {
+  if ((target = getInstanceFromNode(target))) {
+    invariant(
+      null,
+      "Fiber needs to be injected to handle a fiber target for controlled events. This error is likely caused by a bug in React. Please file an issue."
     );
-  subClass.prototype = Object.create(superClass && superClass.prototype, {
-    constructor: {
-      value: subClass,
-      enumerable: !1,
-      writable: !0,
-      configurable: !0
+    var props = getFiberCurrentPropsFromNode(target.stateNode);
+    null.restoreControlledState(target.stateNode, target.type, props);
+  }
+}
+function _batchedUpdates(fn, bookkeeping) {
+  return fn(bookkeeping);
+}
+function _flushInteractiveUpdates() {}
+var isBatching = !1;
+function batchedUpdates(fn, bookkeeping) {
+  if (isBatching) return fn(bookkeeping);
+  isBatching = !0;
+  try {
+    return _batchedUpdates(fn, bookkeeping);
+  } finally {
+    if (((isBatching = !1), null !== restoreTarget || null !== restoreQueue))
+      if (
+        (_flushInteractiveUpdates(),
+        restoreTarget &&
+          ((bookkeeping = restoreTarget),
+          (fn = restoreQueue),
+          (restoreQueue = restoreTarget = null),
+          restoreStateOfTarget(bookkeeping),
+          fn))
+      )
+        for (bookkeeping = 0; bookkeeping < fn.length; bookkeeping++)
+          restoreStateOfTarget(fn[bookkeeping]);
+  }
+}
+function dispatchEvent(target, topLevelType, nativeEvent) {
+  batchedUpdates(function() {
+    var events = nativeEvent.target;
+    for (var events$jscomp$0 = null, i = 0; i < plugins.length; i++) {
+      var possiblePlugin = plugins[i];
+      possiblePlugin &&
+        (possiblePlugin = possiblePlugin.extractEvents(
+          topLevelType,
+          target,
+          nativeEvent,
+          events
+        )) &&
+        (events$jscomp$0 = accumulateInto(events$jscomp$0, possiblePlugin));
     }
+    events = events$jscomp$0;
+    null !== events && (eventQueue = accumulateInto(eventQueue, events));
+    events = eventQueue;
+    eventQueue = null;
+    events &&
+      (forEachAccumulated(events, executeDispatchesAndReleaseTopLevel),
+      invariant(
+        !eventQueue,
+        "processEventQueue(): Additional events were enqueued while processing an event queue. Support for this has not yet been implemented."
+      ),
+      ReactErrorUtils.rethrowCaughtError());
   });
-  superClass &&
-    (Object.setPrototypeOf
-      ? Object.setPrototypeOf(subClass, superClass)
-      : (subClass.__proto__ = superClass));
 }
-var ReactCurrentOwner =
-  React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner;
-function getComponentName(fiber) {
-  var type = fiber.type;
-  if ("function" === typeof type) return type.displayName || type.name;
-  if ("string" === typeof type) return type;
-  switch (type) {
-    case REACT_ASYNC_MODE_TYPE:
-      return "AsyncMode";
-    case REACT_CONTEXT_TYPE:
-      return "Context.Consumer";
-    case REACT_FRAGMENT_TYPE:
-      return "ReactFragment";
-    case REACT_PORTAL_TYPE:
-      return "ReactPortal";
-    case REACT_PROFILER_TYPE:
-      return "Profiler(" + fiber.pendingProps.id + ")";
-    case REACT_PROVIDER_TYPE:
-      return "Context.Provider";
-    case REACT_STRICT_MODE_TYPE:
-      return "StrictMode";
+function shim$1() {
+  invariant(
+    !1,
+    "The current renderer does not support hyration. This error is likely caused by a bug in React. Please file an issue."
+  );
+}
+var nextReactTag = 2;
+FabricUIManager.registerEventHandler &&
+  FabricUIManager.registerEventHandler(dispatchEvent);
+var ReactFabricHostComponent = (function() {
+  function ReactFabricHostComponent(tag, viewConfig, props) {
+    if (!(this instanceof ReactFabricHostComponent))
+      throw new TypeError("Cannot call a class as a function");
+    this._nativeTag = tag;
+    this.viewConfig = viewConfig;
+    this.currentProps = props;
   }
-  if ("object" === typeof type && null !== type)
-    switch (type.$$typeof) {
-      case REACT_FORWARD_REF_TYPE:
-        return (
-          (fiber = type.render.displayName || type.render.name || ""),
-          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
-        );
+  ReactFabricHostComponent.prototype.blur = function() {
+    TextInputState.blurTextInput(this._nativeTag);
+  };
+  ReactFabricHostComponent.prototype.focus = function() {
+    TextInputState.focusTextInput(this._nativeTag);
+  };
+  ReactFabricHostComponent.prototype.measure = function(callback) {
+    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+  };
+  ReactFabricHostComponent.prototype.measureInWindow = function(callback) {
+    UIManager.measureInWindow(
+      this._nativeTag,
+      mountSafeCallback(this, callback)
+    );
+  };
+  ReactFabricHostComponent.prototype.measureLayout = function(
+    relativeToNativeNode,
+    onSuccess,
+    onFail
+  ) {
+    UIManager.measureLayout(
+      this._nativeTag,
+      relativeToNativeNode,
+      mountSafeCallback(this, onFail),
+      mountSafeCallback(this, onSuccess)
+    );
+  };
+  ReactFabricHostComponent.prototype.setNativeProps = function(nativeProps) {
+    nativeProps = diffProperties(
+      null,
+      emptyObject$1,
+      nativeProps,
+      this.viewConfig.validAttributes
+    );
+    null != nativeProps &&
+      UIManager.updateView(
+        this._nativeTag,
+        this.viewConfig.uiViewClassName,
+        nativeProps
+      );
+  };
+  return ReactFabricHostComponent;
+})();
+function createTextInstance(
+  text,
+  rootContainerInstance,
+  hostContext,
+  internalInstanceHandle
+) {
+  invariant(
+    hostContext.isInAParentText,
+    "Text strings must be rendered within a <Text> component."
+  );
+  hostContext = nextReactTag;
+  nextReactTag += 2;
+  return {
+    node: FabricUIManager.createNode(
+      hostContext,
+      "RCTRawText",
+      rootContainerInstance,
+      { text: text },
+      internalInstanceHandle
+    )
+  };
+}
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
     }
-  return null;
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress.return;
+  } while (workInProgress);
+  return info;
 }
-function isFiberMountedImpl(fiber) {
-  var node = fiber;
-  if (fiber.alternate) for (; node.return; ) node = node.return;
-  else {
-    if (0 !== (node.effectTag & 2)) return 1;
-    for (; node.return; )
-      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
-  }
-  return 3 === node.tag ? 2 : 3;
+new Set();
+var valueStack = [],
+  index = -1;
+function createCursor(defaultValue) {
+  return { current: defaultValue };
 }
-function isMounted(component) {
-  return (component = component._reactInternalFiber)
-    ? 2 === isFiberMountedImpl(component)
-    : !1;
+function pop(cursor) {
+  0 > index ||
+    ((cursor.current = valueStack[index]), (valueStack[index] = null), index--);
 }
-function assertIsMounted(fiber) {
+function push(cursor, value) {
+  index++;
+  valueStack[index] = cursor.current;
+  cursor.current = value;
+}
+var contextStackCursor = createCursor(emptyObject),
+  didPerformWorkStackCursor = createCursor(!1),
+  previousContext = emptyObject;
+function getUnmaskedContext(workInProgress) {
+  return isContextProvider(workInProgress)
+    ? previousContext
+    : contextStackCursor.current;
+}
+function getMaskedContext(workInProgress, unmaskedContext) {
+  var contextTypes = workInProgress.type.contextTypes;
+  if (!contextTypes) return emptyObject;
+  var instance = workInProgress.stateNode;
+  if (
+    instance &&
+    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+  )
+    return instance.__reactInternalMemoizedMaskedChildContext;
+  var context = {},
+    key;
+  for (key in contextTypes) context[key] = unmaskedContext[key];
+  instance &&
+    ((workInProgress = workInProgress.stateNode),
+    (workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext),
+    (workInProgress.__reactInternalMemoizedMaskedChildContext = context));
+  return context;
+}
+function isContextProvider(fiber) {
+  return 2 === fiber.tag && null != fiber.type.childContextTypes;
+}
+function popContextProvider(fiber) {
+  isContextProvider(fiber) &&
+    (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
+}
+function popTopLevelContextObject(fiber) {
+  pop(didPerformWorkStackCursor, fiber);
+  pop(contextStackCursor, fiber);
+}
+function pushTopLevelContextObject(fiber, context, didChange) {
   invariant(
-    2 === isFiberMountedImpl(fiber),
-    "Unable to find node on an unmounted component."
+    contextStackCursor.current === emptyObject,
+    "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
   );
+  push(contextStackCursor, context, fiber);
+  push(didPerformWorkStackCursor, didChange, fiber);
 }
-function findCurrentFiberUsingSlowPath(fiber) {
-  var alternate = fiber.alternate;
-  if (!alternate)
-    return (
-      (alternate = isFiberMountedImpl(fiber)),
-      invariant(
-        3 !== alternate,
-        "Unable to find node on an unmounted component."
-      ),
-      1 === alternate ? null : fiber
-    );
-  for (var a = fiber, b = alternate; ; ) {
-    var parentA = a.return,
-      parentB = parentA ? parentA.alternate : null;
-    if (!parentA || !parentB) break;
-    if (parentA.child === parentB.child) {
-      for (var child = parentA.child; child; ) {
-        if (child === a) return assertIsMounted(parentA), fiber;
-        if (child === b) return assertIsMounted(parentA), alternate;
-        child = child.sibling;
-      }
-      invariant(!1, "Unable to find node on an unmounted component.");
-    }
-    if (a.return !== b.return) (a = parentA), (b = parentB);
-    else {
-      child = !1;
-      for (var _child = parentA.child; _child; ) {
-        if (_child === a) {
-          child = !0;
-          a = parentA;
-          b = parentB;
-          break;
-        }
-        if (_child === b) {
-          child = !0;
-          b = parentA;
-          a = parentB;
-          break;
-        }
-        _child = _child.sibling;
-      }
-      if (!child) {
-        for (_child = parentB.child; _child; ) {
-          if (_child === a) {
-            child = !0;
-            a = parentB;
-            b = parentA;
-            break;
-          }
-          if (_child === b) {
-            child = !0;
-            b = parentB;
-            a = parentA;
-            break;
-          }
-          _child = _child.sibling;
-        }
-        invariant(
-          child,
-          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
-        );
-      }
-    }
+function processChildContext(fiber, parentContext) {
+  var instance = fiber.stateNode,
+    childContextTypes = fiber.type.childContextTypes;
+  if ("function" !== typeof instance.getChildContext) return parentContext;
+  instance = instance.getChildContext();
+  for (var contextKey in instance)
     invariant(
-      a.alternate === b,
-      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
+      contextKey in childContextTypes,
+      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+      getComponentName(fiber) || "Unknown",
+      contextKey
     );
-  }
-  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
-  return a.stateNode.current === a ? fiber : alternate;
+  return Object.assign({}, parentContext, instance);
 }
-function findCurrentHostFiber(parent) {
-  parent = findCurrentFiberUsingSlowPath(parent);
-  if (!parent) return null;
-  for (var node = parent; ; ) {
-    if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child) (node.child.return = node), (node = node.child);
-    else {
-      if (node === parent) break;
-      for (; !node.sibling; ) {
-        if (!node.return || node.return === parent) return null;
-        node = node.return;
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
-    }
-  }
-  return null;
+function pushContextProvider(workInProgress) {
+  if (!isContextProvider(workInProgress)) return !1;
+  var instance = workInProgress.stateNode;
+  instance =
+    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+    emptyObject;
+  previousContext = contextStackCursor.current;
+  push(contextStackCursor, instance, workInProgress);
+  push(
+    didPerformWorkStackCursor,
+    didPerformWorkStackCursor.current,
+    workInProgress
+  );
+  return !0;
 }
-function findCurrentHostFiberWithNoPortals(parent) {
-  parent = findCurrentFiberUsingSlowPath(parent);
-  if (!parent) return null;
-  for (var node = parent; ; ) {
-    if (5 === node.tag || 6 === node.tag) return node;
-    if (node.child && 4 !== node.tag)
-      (node.child.return = node), (node = node.child);
-    else {
-      if (node === parent) break;
-      for (; !node.sibling; ) {
-        if (!node.return || node.return === parent) return null;
-        node = node.return;
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
-    }
-  }
-  return null;
+function invalidateContextProvider(workInProgress, didChange) {
+  var instance = workInProgress.stateNode;
+  invariant(
+    instance,
+    "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+  );
+  if (didChange) {
+    var mergedContext = processChildContext(workInProgress, previousContext);
+    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+    pop(didPerformWorkStackCursor, workInProgress);
+    pop(contextStackCursor, workInProgress);
+    push(contextStackCursor, mergedContext, workInProgress);
+  } else pop(didPerformWorkStackCursor, workInProgress);
+  push(didPerformWorkStackCursor, didChange, workInProgress);
 }
 function FiberNode(tag, pendingProps, key, mode) {
   this.tag = tag;
@@ -1583,7 +1813,6 @@ function createFiberFromElement(element, mode, expirationTime) {
           (type = new FiberNode(15, element, key, mode | 4)),
           (type.type = REACT_PROFILER_TYPE),
           (type.expirationTime = expirationTime),
-          (type.stateNode = { duration: 0, startTime: 0 }),
           type
         );
       case REACT_TIMEOUT_TYPE:
@@ -1645,6 +1874,30 @@ function createFiberFromPortal(portal, mode, expirationTime) {
   };
   return mode;
 }
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
+  containerInfo = {
+    current: isAsync,
+    containerInfo: containerInfo,
+    pendingChildren: null,
+    earliestPendingTime: 0,
+    latestPendingTime: 0,
+    earliestSuspendedTime: 0,
+    latestSuspendedTime: 0,
+    latestPingedTime: 0,
+    didError: !1,
+    pendingCommitExpirationTime: 0,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    nextExpirationTimeToWorkOn: 0,
+    expirationTime: 0,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  return (isAsync.stateNode = containerInfo);
+}
 var onCommitFiberRoot = null,
   onCommitFiberUnmount = null;
 function catchErrors(fn) {
@@ -1675,53 +1928,35 @@ function onCommitRoot(root) {
 function onCommitUnmount(fiber) {
   "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
 }
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  do {
-    a: switch (workInProgress.tag) {
-      case 0:
-      case 1:
-      case 2:
-      case 5:
-        var owner = workInProgress._debugOwner,
-          source = workInProgress._debugSource;
-        var JSCompiler_inline_result = getComponentName(workInProgress);
-        var ownerName = null;
-        owner && (ownerName = getComponentName(owner));
-        owner = source;
-        JSCompiler_inline_result =
-          "\n    in " +
-          (JSCompiler_inline_result || "Unknown") +
-          (owner
-            ? " (at " +
-              owner.fileName.replace(/^.*[\\\/]/, "") +
-              ":" +
-              owner.lineNumber +
-              ")"
-            : ownerName ? " (created by " + ownerName + ")" : "");
-        break a;
-      default:
-        JSCompiler_inline_result = "";
-    }
-    info += JSCompiler_inline_result;
-    workInProgress = workInProgress.return;
-  } while (workInProgress);
-  return info;
+function markPendingPriorityLevel(root, expirationTime) {
+  root.didError = !1;
+  var earliestPendingTime = root.earliestPendingTime;
+  0 === earliestPendingTime
+    ? (root.earliestPendingTime = root.latestPendingTime = expirationTime)
+    : earliestPendingTime > expirationTime
+      ? (root.earliestPendingTime = expirationTime)
+      : root.latestPendingTime < expirationTime &&
+        (root.latestPendingTime = expirationTime);
+  findNextPendingPriorityLevel(root);
 }
-function createProfilerTimer() {
-  return {
-    checkActualRenderTimeStackEmpty: function() {},
-    markActualRenderTimeStarted: function() {},
-    pauseActualRenderTimerIfRunning: function() {},
-    recordElapsedActualRenderTime: function() {},
-    resetActualRenderTimer: function() {},
-    resumeActualRenderTimerIfPaused: function() {},
-    recordElapsedBaseRenderTimeIfRunning: function() {},
-    startBaseRenderTimer: function() {},
-    stopBaseRenderTimerIfRunning: function() {}
-  };
+function findNextPendingPriorityLevel(root) {
+  var earliestSuspendedTime = root.earliestSuspendedTime,
+    earliestPendingTime = root.earliestPendingTime;
+  if (0 === earliestSuspendedTime)
+    var nextExpirationTimeToWorkOn = (earliestSuspendedTime = earliestPendingTime);
+  else
+    0 !== earliestPendingTime
+      ? ((nextExpirationTimeToWorkOn = earliestPendingTime),
+        (earliestSuspendedTime =
+          earliestSuspendedTime < earliestPendingTime
+            ? earliestSuspendedTime
+            : earliestPendingTime))
+      : (nextExpirationTimeToWorkOn = earliestSuspendedTime =
+          root.latestPingedTime);
+  root.didError && (earliestSuspendedTime = 1);
+  root.nextExpirationTimeToWorkOn = nextExpirationTimeToWorkOn;
+  root.expirationTime = earliestSuspendedTime;
 }
-new Set();
 var hasForceUpdate = !1;
 function createUpdateQueue(baseState) {
   return {
@@ -1979,6 +2214,85 @@ function commitUpdateQueue(finishedWork, finishedQueue, instance) {
         ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
       (finishedWork = finishedWork.nextEffect);
 }
+function createCapturedValue(value, source) {
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
+var providerCursor = createCursor(null),
+  valueCursor = createCursor(null),
+  changedBitsCursor = createCursor(0);
+function pushProvider(providerFiber) {
+  var context = providerFiber.type._context;
+  push(changedBitsCursor, context._changedBits2, providerFiber);
+  push(valueCursor, context._currentValue2, providerFiber);
+  push(providerCursor, providerFiber, providerFiber);
+  context._currentValue2 = providerFiber.pendingProps.value;
+  context._changedBits2 = providerFiber.stateNode;
+}
+function popProvider(providerFiber) {
+  var changedBits = changedBitsCursor.current,
+    currentValue = valueCursor.current;
+  pop(providerCursor, providerFiber);
+  pop(valueCursor, providerFiber);
+  pop(changedBitsCursor, providerFiber);
+  providerFiber = providerFiber.type._context;
+  providerFiber._currentValue2 = currentValue;
+  providerFiber._changedBits2 = changedBits;
+}
+var NO_CONTEXT = {},
+  contextStackCursor$1 = createCursor(NO_CONTEXT),
+  contextFiberStackCursor = createCursor(NO_CONTEXT),
+  rootInstanceStackCursor = createCursor(NO_CONTEXT);
+function requiredContext(c) {
+  invariant(
+    c !== NO_CONTEXT,
+    "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
+  );
+  return c;
+}
+function pushHostContainer(fiber, nextRootInstance) {
+  push(rootInstanceStackCursor, nextRootInstance, fiber);
+  push(contextFiberStackCursor, fiber, fiber);
+  push(contextStackCursor$1, NO_CONTEXT, fiber);
+  pop(contextStackCursor$1, fiber);
+  push(contextStackCursor$1, { isInAParentText: !1 }, fiber);
+}
+function popHostContainer(fiber) {
+  pop(contextStackCursor$1, fiber);
+  pop(contextFiberStackCursor, fiber);
+  pop(rootInstanceStackCursor, fiber);
+}
+function popHostContext(fiber) {
+  contextFiberStackCursor.current === fiber &&
+    (pop(contextStackCursor$1, fiber), pop(contextFiberStackCursor, fiber));
+}
+var hasOwnProperty = Object.prototype.hasOwnProperty;
+function is(x, y) {
+  return x === y ? 0 !== x || 0 !== y || 1 / x === 1 / y : x !== x && y !== y;
+}
+function shallowEqual(objA, objB) {
+  if (is(objA, objB)) return !0;
+  if (
+    "object" !== typeof objA ||
+    null === objA ||
+    "object" !== typeof objB ||
+    null === objB
+  )
+    return !1;
+  var keysA = Object.keys(objA),
+    keysB = Object.keys(objB);
+  if (keysA.length !== keysB.length) return !1;
+  for (keysB = 0; keysB < keysA.length; keysB++)
+    if (
+      !hasOwnProperty.call(objB, keysA[keysB]) ||
+      !is(objA[keysA[keysB]], objB[keysA[keysB]])
+    )
+      return !1;
+  return !0;
+}
 function applyDerivedStateFromProps(
   workInProgress,
   getDerivedStateFromProps,
@@ -1996,351 +2310,120 @@ function applyDerivedStateFromProps(
     0 === workInProgress.expirationTime &&
     (workInProgress.baseState = prevState);
 }
-function ReactFiberClassComponent(
-  legacyContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState,
-  recalculateCurrentTime
-) {
-  function checkShouldComponentUpdate(
-    workInProgress,
-    oldProps,
-    newProps,
-    oldState,
-    newState,
-    newContext
-  ) {
-    var instance = workInProgress.stateNode;
-    workInProgress = workInProgress.type;
-    return "function" === typeof instance.shouldComponentUpdate
-      ? instance.shouldComponentUpdate(newProps, newState, newContext)
-      : workInProgress.prototype &&
-        workInProgress.prototype.isPureReactComponent
-        ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
-        : !0;
-  }
-  function adoptClassInstance(workInProgress, instance) {
-    instance.updater = classComponentUpdater;
-    workInProgress.stateNode = instance;
-    instance._reactInternalFiber = workInProgress;
-  }
-  function callComponentWillReceiveProps(
-    workInProgress,
-    instance,
-    newProps,
-    newContext
-  ) {
-    workInProgress = instance.state;
-    "function" === typeof instance.componentWillReceiveProps &&
-      instance.componentWillReceiveProps(newProps, newContext);
-    "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
-      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
-    instance.state !== workInProgress &&
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+var classComponentUpdater = {
+  isMounted: function(component) {
+    return (component = component._reactInternalFiber)
+      ? 2 === isFiberMountedImpl(component)
+      : !1;
+  },
+  enqueueSetState: function(inst, payload, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.payload = payload;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  },
+  enqueueReplaceState: function(inst, payload, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.tag = 1;
+    update.payload = payload;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  },
+  enqueueForceUpdate: function(inst, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.tag = 2;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
   }
-  var cacheContext = legacyContext.cacheContext,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    isContextConsumer = legacyContext.isContextConsumer,
-    hasContextChanged = legacyContext.hasContextChanged,
-    classComponentUpdater = {
-      isMounted: isMounted,
-      enqueueSetState: function(inst, payload, callback) {
-        inst = inst._reactInternalFiber;
-        var currentTime = recalculateCurrentTime();
-        currentTime = computeExpirationForFiber(currentTime, inst);
-        var update = createUpdate(currentTime);
-        update.payload = payload;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, currentTime);
-        scheduleWork(inst, currentTime);
-      },
-      enqueueReplaceState: function(inst, payload, callback) {
-        inst = inst._reactInternalFiber;
-        var currentTime = recalculateCurrentTime();
-        currentTime = computeExpirationForFiber(currentTime, inst);
-        var update = createUpdate(currentTime);
-        update.tag = 1;
-        update.payload = payload;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, currentTime);
-        scheduleWork(inst, currentTime);
-      },
-      enqueueForceUpdate: function(inst, callback) {
-        inst = inst._reactInternalFiber;
-        var currentTime = recalculateCurrentTime();
-        currentTime = computeExpirationForFiber(currentTime, inst);
-        var update = createUpdate(currentTime);
-        update.tag = 2;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, currentTime);
-        scheduleWork(inst, currentTime);
-      }
-    };
-  return {
-    adoptClassInstance: adoptClassInstance,
-    constructClassInstance: function(workInProgress, props) {
-      var ctor = workInProgress.type,
-        unmaskedContext = getUnmaskedContext(workInProgress),
-        needsContext = isContextConsumer(workInProgress),
-        context = needsContext
-          ? getMaskedContext(workInProgress, unmaskedContext)
-          : emptyObject;
-      props = new ctor(props, context);
-      workInProgress.memoizedState =
-        null !== props.state && void 0 !== props.state ? props.state : null;
-      adoptClassInstance(workInProgress, props);
-      needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return props;
-    },
-    mountClassInstance: function(workInProgress, renderExpirationTime) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        props = workInProgress.pendingProps,
-        unmaskedContext = getUnmaskedContext(workInProgress);
-      instance.props = props;
-      instance.state = workInProgress.memoizedState;
-      instance.refs = emptyObject;
-      instance.context = getMaskedContext(workInProgress, unmaskedContext);
-      unmaskedContext = workInProgress.updateQueue;
-      null !== unmaskedContext &&
-        (processUpdateQueue(
-          workInProgress,
-          unmaskedContext,
-          props,
-          instance,
-          renderExpirationTime
-        ),
-        (instance.state = workInProgress.memoizedState));
-      unmaskedContext = workInProgress.type.getDerivedStateFromProps;
-      "function" === typeof unmaskedContext &&
-        (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
-        (instance.state = workInProgress.memoizedState));
-      "function" === typeof ctor.getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate ||
-        ("function" !== typeof instance.UNSAFE_componentWillMount &&
-          "function" !== typeof instance.componentWillMount) ||
-        ((ctor = instance.state),
-        "function" === typeof instance.componentWillMount &&
-          instance.componentWillMount(),
-        "function" === typeof instance.UNSAFE_componentWillMount &&
-          instance.UNSAFE_componentWillMount(),
-        ctor !== instance.state &&
-          classComponentUpdater.enqueueReplaceState(
-            instance,
-            instance.state,
-            null
-          ),
-        (unmaskedContext = workInProgress.updateQueue),
-        null !== unmaskedContext &&
-          (processUpdateQueue(
-            workInProgress,
-            unmaskedContext,
-            props,
-            instance,
-            renderExpirationTime
-          ),
-          (instance.state = workInProgress.memoizedState)));
-      "function" === typeof instance.componentDidMount &&
-        (workInProgress.effectTag |= 4);
-    },
-    resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps;
-      instance.props = oldProps;
-      var oldContext = instance.context,
-        newUnmaskedContext = getUnmaskedContext(workInProgress);
-      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
-      (ctor =
-        "function" === typeof getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate) ||
-        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-          "function" !== typeof instance.componentWillReceiveProps) ||
-        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
-          callComponentWillReceiveProps(
-            workInProgress,
-            instance,
-            newProps,
-            newUnmaskedContext
-          ));
-      hasForceUpdate = !1;
-      var oldState = workInProgress.memoizedState;
-      oldContext = instance.state = oldState;
-      var updateQueue = workInProgress.updateQueue;
-      null !== updateQueue &&
-        (processUpdateQueue(
-          workInProgress,
-          updateQueue,
-          newProps,
-          instance,
-          renderExpirationTime
-        ),
-        (oldContext = workInProgress.memoizedState));
-      if (
-        oldProps === newProps &&
-        oldState === oldContext &&
-        !hasContextChanged() &&
-        !hasForceUpdate
-      )
-        return (
-          "function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4),
-          !1
-        );
-      "function" === typeof getDerivedStateFromProps &&
-        (applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        ),
-        (oldContext = workInProgress.memoizedState));
-      (renderExpirationTime =
-        hasForceUpdate ||
-        checkShouldComponentUpdate(
-          workInProgress,
-          oldProps,
-          newProps,
-          oldState,
-          oldContext,
-          newUnmaskedContext
-        ))
-        ? (ctor ||
-            ("function" !== typeof instance.UNSAFE_componentWillMount &&
-              "function" !== typeof instance.componentWillMount) ||
-            ("function" === typeof instance.componentWillMount &&
-              instance.componentWillMount(),
-            "function" === typeof instance.UNSAFE_componentWillMount &&
-              instance.UNSAFE_componentWillMount()),
-          "function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4))
-        : ("function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4),
-          (workInProgress.memoizedProps = newProps),
-          (workInProgress.memoizedState = oldContext));
-      instance.props = newProps;
-      instance.state = oldContext;
-      instance.context = newUnmaskedContext;
-      return renderExpirationTime;
-    },
-    updateClassInstance: function(
-      current,
+};
+function checkShouldComponentUpdate(
+  workInProgress,
+  oldProps,
+  newProps,
+  oldState,
+  newState,
+  newContext
+) {
+  var instance = workInProgress.stateNode;
+  workInProgress = workInProgress.type;
+  return "function" === typeof instance.shouldComponentUpdate
+    ? instance.shouldComponentUpdate(newProps, newState, newContext)
+    : workInProgress.prototype && workInProgress.prototype.isPureReactComponent
+      ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+      : !0;
+}
+function callComponentWillReceiveProps(
+  workInProgress,
+  instance,
+  newProps,
+  newContext
+) {
+  workInProgress = instance.state;
+  "function" === typeof instance.componentWillReceiveProps &&
+    instance.componentWillReceiveProps(newProps, newContext);
+  "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
+    instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+  instance.state !== workInProgress &&
+    classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+}
+function mountClassInstance(workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type,
+    instance = workInProgress.stateNode,
+    props = workInProgress.pendingProps,
+    unmaskedContext = getUnmaskedContext(workInProgress);
+  instance.props = props;
+  instance.state = workInProgress.memoizedState;
+  instance.refs = emptyObject;
+  instance.context = getMaskedContext(workInProgress, unmaskedContext);
+  unmaskedContext = workInProgress.updateQueue;
+  null !== unmaskedContext &&
+    (processUpdateQueue(
       workInProgress,
+      unmaskedContext,
+      props,
+      instance,
       renderExpirationTime
-    ) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps;
-      instance.props = oldProps;
-      var oldContext = instance.context,
-        newUnmaskedContext = getUnmaskedContext(workInProgress);
-      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
-      (ctor =
-        "function" === typeof getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate) ||
-        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-          "function" !== typeof instance.componentWillReceiveProps) ||
-        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
-          callComponentWillReceiveProps(
-            workInProgress,
-            instance,
-            newProps,
-            newUnmaskedContext
-          ));
-      hasForceUpdate = !1;
-      oldContext = workInProgress.memoizedState;
-      var newState = (instance.state = oldContext),
-        updateQueue = workInProgress.updateQueue;
-      null !== updateQueue &&
-        (processUpdateQueue(
-          workInProgress,
-          updateQueue,
-          newProps,
-          instance,
-          renderExpirationTime
-        ),
-        (newState = workInProgress.memoizedState));
-      if (
-        oldProps === newProps &&
-        oldContext === newState &&
-        !hasContextChanged() &&
-        !hasForceUpdate
-      )
-        return (
-          "function" !== typeof instance.componentDidUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 4),
-          "function" !== typeof instance.getSnapshotBeforeUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 256),
-          !1
-        );
-      "function" === typeof getDerivedStateFromProps &&
-        (applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        ),
-        (newState = workInProgress.memoizedState));
-      (renderExpirationTime =
-        hasForceUpdate ||
-        checkShouldComponentUpdate(
-          workInProgress,
-          oldProps,
-          newProps,
-          oldContext,
-          newState,
-          newUnmaskedContext
-        ))
-        ? (ctor ||
-            ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
-              "function" !== typeof instance.componentWillUpdate) ||
-            ("function" === typeof instance.componentWillUpdate &&
-              instance.componentWillUpdate(
-                newProps,
-                newState,
-                newUnmaskedContext
-              ),
-            "function" === typeof instance.UNSAFE_componentWillUpdate &&
-              instance.UNSAFE_componentWillUpdate(
-                newProps,
-                newState,
-                newUnmaskedContext
-              )),
-          "function" === typeof instance.componentDidUpdate &&
-            (workInProgress.effectTag |= 4),
-          "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 256))
-        : ("function" !== typeof instance.componentDidUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 4),
-          "function" !== typeof instance.getSnapshotBeforeUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 256),
-          (workInProgress.memoizedProps = newProps),
-          (workInProgress.memoizedState = newState));
-      instance.props = newProps;
-      instance.state = newState;
-      instance.context = newUnmaskedContext;
-      return renderExpirationTime;
-    }
-  };
+    ),
+    (instance.state = workInProgress.memoizedState));
+  unmaskedContext = workInProgress.type.getDerivedStateFromProps;
+  "function" === typeof unmaskedContext &&
+    (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+    (instance.state = workInProgress.memoizedState));
+  "function" === typeof ctor.getDerivedStateFromProps ||
+    "function" === typeof instance.getSnapshotBeforeUpdate ||
+    ("function" !== typeof instance.UNSAFE_componentWillMount &&
+      "function" !== typeof instance.componentWillMount) ||
+    ((ctor = instance.state),
+    "function" === typeof instance.componentWillMount &&
+      instance.componentWillMount(),
+    "function" === typeof instance.UNSAFE_componentWillMount &&
+      instance.UNSAFE_componentWillMount(),
+    ctor !== instance.state &&
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null),
+    (unmaskedContext = workInProgress.updateQueue),
+    null !== unmaskedContext &&
+      (processUpdateQueue(
+        workInProgress,
+        unmaskedContext,
+        props,
+        instance,
+        renderExpirationTime
+      ),
+      (instance.state = workInProgress.memoizedState)));
+  "function" === typeof instance.componentDidMount &&
+    (workInProgress.effectTag |= 4);
 }
 var isArray$1 = Array.isArray;
 function coerceRef(returnFiber, current, element) {
@@ -2368,6 +2451,7 @@ function coerceRef(returnFiber, current, element) {
       if (
         null !== current &&
         null !== current.ref &&
+        "function" === typeof current.ref &&
         current.ref._stringRef === stringRef
       )
         return current.ref;
@@ -2863,27 +2947,35 @@ function ChildReconciler(shouldTrackSideEffects) {
     return iteratorFn;
   }
   return function(returnFiber, currentFirstChild, newChild, expirationTime) {
-    "object" === typeof newChild &&
+    var isUnkeyedTopLevelFragment =
+      "object" === typeof newChild &&
       null !== newChild &&
       newChild.type === REACT_FRAGMENT_TYPE &&
-      null === newChild.key &&
-      (newChild = newChild.props.children);
+      null === newChild.key;
+    isUnkeyedTopLevelFragment && (newChild = newChild.props.children);
     var isObject = "object" === typeof newChild && null !== newChild;
     if (isObject)
       switch (newChild.$$typeof) {
         case REACT_ELEMENT_TYPE:
           a: {
-            var key = newChild.key;
-            for (isObject = currentFirstChild; null !== isObject; ) {
-              if (isObject.key === key)
+            isObject = newChild.key;
+            for (
+              isUnkeyedTopLevelFragment = currentFirstChild;
+              null !== isUnkeyedTopLevelFragment;
+
+            ) {
+              if (isUnkeyedTopLevelFragment.key === isObject)
                 if (
-                  10 === isObject.tag
+                  10 === isUnkeyedTopLevelFragment.tag
                     ? newChild.type === REACT_FRAGMENT_TYPE
-                    : isObject.type === newChild.type
+                    : isUnkeyedTopLevelFragment.type === newChild.type
                 ) {
-                  deleteRemainingChildren(returnFiber, isObject.sibling);
+                  deleteRemainingChildren(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment.sibling
+                  );
                   currentFirstChild = useFiber(
-                    isObject,
+                    isUnkeyedTopLevelFragment,
                     newChild.type === REACT_FRAGMENT_TYPE
                       ? newChild.props.children
                       : newChild.props,
@@ -2891,18 +2983,21 @@ function ChildReconciler(shouldTrackSideEffects) {
                   );
                   currentFirstChild.ref = coerceRef(
                     returnFiber,
-                    isObject,
+                    isUnkeyedTopLevelFragment,
                     newChild
                   );
                   currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
-                  deleteRemainingChildren(returnFiber, isObject);
+                  deleteRemainingChildren(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment
+                  );
                   break;
                 }
-              else deleteChild(returnFiber, isObject);
-              isObject = isObject.sibling;
+              else deleteChild(returnFiber, isUnkeyedTopLevelFragment);
+              isUnkeyedTopLevelFragment = isUnkeyedTopLevelFragment.sibling;
             }
             newChild.type === REACT_FRAGMENT_TYPE
               ? ((currentFirstChild = createFiberFromFragment(
@@ -2929,8 +3024,12 @@ function ChildReconciler(shouldTrackSideEffects) {
           return placeSingleChild(returnFiber);
         case REACT_PORTAL_TYPE:
           a: {
-            for (isObject = newChild.key; null !== currentFirstChild; ) {
-              if (currentFirstChild.key === isObject)
+            for (
+              isUnkeyedTopLevelFragment = newChild.key;
+              null !== currentFirstChild;
+
+            ) {
+              if (currentFirstChild.key === isUnkeyedTopLevelFragment)
                 if (
                   4 === currentFirstChild.tag &&
                   currentFirstChild.stateNode.containerInfo ===
@@ -3004,7 +3103,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
     isObject && throwOnInvalidObjectType(returnFiber, newChild);
-    if ("undefined" === typeof newChild)
+    if ("undefined" === typeof newChild && !isUnkeyedTopLevelFragment)
       switch (returnFiber.tag) {
         case 2:
         case 1:
@@ -3018,185 +3117,235 @@ function ChildReconciler(shouldTrackSideEffects) {
     return deleteRemainingChildren(returnFiber, currentFirstChild);
   };
 }
-var reconcileChildFibers = ChildReconciler(!0),
-  mountChildFibers = ChildReconciler(!1);
-function ReactFiberBeginWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  profilerTimer,
-  recalculateCurrentTime
-) {
-  function reconcileChildren(current, workInProgress, nextChildren) {
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      workInProgress.expirationTime
-    );
+var reconcileChildFibers = ChildReconciler(!0),
+  mountChildFibers = ChildReconciler(!1),
+  hydrationParentFiber = null,
+  nextHydratableInstance = null,
+  isHydrating = !1;
+function tryHydrate(fiber, nextInstance) {
+  switch (fiber.tag) {
+    case 5:
+      return (
+        (nextInstance = shim$1(nextInstance, fiber.type, fiber.pendingProps)),
+        null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+      );
+    case 6:
+      return (
+        (nextInstance = shim$1(nextInstance, fiber.pendingProps)),
+        null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+      );
+    default:
+      return !1;
+  }
+}
+function tryToClaimNextHydratableInstance(fiber$jscomp$0) {
+  if (isHydrating) {
+    var nextInstance = nextHydratableInstance;
+    if (nextInstance) {
+      var firstAttemptedInstance = nextInstance;
+      if (!tryHydrate(fiber$jscomp$0, nextInstance)) {
+        nextInstance = shim$1(firstAttemptedInstance);
+        if (!nextInstance || !tryHydrate(fiber$jscomp$0, nextInstance)) {
+          fiber$jscomp$0.effectTag |= 2;
+          isHydrating = !1;
+          hydrationParentFiber = fiber$jscomp$0;
+          return;
+        }
+        var returnFiber = hydrationParentFiber,
+          fiber = new FiberNode(5, null, null, 0);
+        fiber.type = "DELETED";
+        fiber.stateNode = firstAttemptedInstance;
+        fiber.return = returnFiber;
+        fiber.effectTag = 8;
+        null !== returnFiber.lastEffect
+          ? ((returnFiber.lastEffect.nextEffect = fiber),
+            (returnFiber.lastEffect = fiber))
+          : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
+      }
+      hydrationParentFiber = fiber$jscomp$0;
+      nextHydratableInstance = shim$1(nextInstance);
+    } else
+      (fiber$jscomp$0.effectTag |= 2),
+        (isHydrating = !1),
+        (hydrationParentFiber = fiber$jscomp$0);
   }
-  function reconcileChildrenAtExpirationTime(
+}
+function reconcileChildren(current, workInProgress, nextChildren) {
+  reconcileChildrenAtExpirationTime(
     current,
     workInProgress,
     nextChildren,
-    renderExpirationTime
-  ) {
-    workInProgress.child =
-      null === current
-        ? mountChildFibers(
-            workInProgress,
-            null,
-            nextChildren,
-            renderExpirationTime
-          )
-        : reconcileChildFibers(
-            workInProgress,
-            current.child,
-            nextChildren,
-            renderExpirationTime
-          );
-  }
-  function markRef(current, workInProgress) {
-    var ref = workInProgress.ref;
-    if (
-      (null === current && null !== ref) ||
-      (null !== current && current.ref !== ref)
-    )
-      workInProgress.effectTag |= 128;
-  }
-  function finishClassComponent(
-    current,
-    workInProgress,
-    shouldUpdate,
-    hasContext,
-    renderExpirationTime
-  ) {
-    markRef(current, workInProgress);
-    var didCaptureError = 0 !== (workInProgress.effectTag & 64);
-    if (!shouldUpdate && !didCaptureError)
-      return (
-        hasContext && invalidateContextProvider(workInProgress, !1),
-        bailoutOnAlreadyFinishedWork(current, workInProgress)
-      );
-    shouldUpdate = workInProgress.stateNode;
-    ReactCurrentOwner.current = workInProgress;
-    var nextChildren = didCaptureError ? null : shouldUpdate.render();
-    workInProgress.effectTag |= 1;
-    didCaptureError &&
-      (reconcileChildrenAtExpirationTime(
-        current,
-        workInProgress,
-        null,
-        renderExpirationTime
-      ),
-      (workInProgress.child = null));
-    reconcileChildrenAtExpirationTime(
+    workInProgress.expirationTime
+  );
+}
+function reconcileChildrenAtExpirationTime(
+  current,
+  workInProgress,
+  nextChildren,
+  renderExpirationTime
+) {
+  workInProgress.child =
+    null === current
+      ? mountChildFibers(
+          workInProgress,
+          null,
+          nextChildren,
+          renderExpirationTime
+        )
+      : reconcileChildFibers(
+          workInProgress,
+          current.child,
+          nextChildren,
+          renderExpirationTime
+        );
+}
+function markRef(current, workInProgress) {
+  var ref = workInProgress.ref;
+  if (
+    (null === current && null !== ref) ||
+    (null !== current && current.ref !== ref)
+  )
+    workInProgress.effectTag |= 128;
+}
+function finishClassComponent(
+  current,
+  workInProgress,
+  shouldUpdate,
+  hasContext,
+  renderExpirationTime
+) {
+  markRef(current, workInProgress);
+  var didCaptureError = 0 !== (workInProgress.effectTag & 64);
+  if (!shouldUpdate && !didCaptureError)
+    return (
+      hasContext && invalidateContextProvider(workInProgress, !1),
+      bailoutOnAlreadyFinishedWork(current, workInProgress)
+    );
+  shouldUpdate = workInProgress.stateNode;
+  ReactCurrentOwner.current = workInProgress;
+  var nextChildren = didCaptureError ? null : shouldUpdate.render();
+  workInProgress.effectTag |= 1;
+  didCaptureError &&
+    (reconcileChildrenAtExpirationTime(
       current,
       workInProgress,
-      nextChildren,
+      null,
       renderExpirationTime
-    );
-    workInProgress.memoizedState = shouldUpdate.state;
-    workInProgress.memoizedProps = shouldUpdate.props;
-    hasContext && invalidateContextProvider(workInProgress, !0);
-    return workInProgress.child;
-  }
-  function pushHostRootContext(workInProgress) {
-    var root = workInProgress.stateNode;
-    root.pendingContext
-      ? pushTopLevelContextObject(
-          workInProgress,
-          root.pendingContext,
-          root.pendingContext !== root.context
-        )
-      : root.context &&
-        pushTopLevelContextObject(workInProgress, root.context, !1);
-    pushHostContainer(workInProgress, root.containerInfo);
-  }
-  function propagateContextChange(
+    ),
+    (workInProgress.child = null));
+  reconcileChildrenAtExpirationTime(
+    current,
     workInProgress,
-    context,
-    changedBits,
+    nextChildren,
     renderExpirationTime
-  ) {
-    var fiber = workInProgress.child;
-    null !== fiber && (fiber.return = workInProgress);
-    for (; null !== fiber; ) {
-      switch (fiber.tag) {
-        case 12:
-          var nextFiber = fiber.stateNode | 0;
-          if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
-            for (nextFiber = fiber; null !== nextFiber; ) {
-              var alternate = nextFiber.alternate;
-              if (
-                0 === nextFiber.expirationTime ||
-                nextFiber.expirationTime > renderExpirationTime
-              )
-                (nextFiber.expirationTime = renderExpirationTime),
-                  null !== alternate &&
-                    (0 === alternate.expirationTime ||
-                      alternate.expirationTime > renderExpirationTime) &&
-                    (alternate.expirationTime = renderExpirationTime);
-              else if (
+  );
+  workInProgress.memoizedState = shouldUpdate.state;
+  workInProgress.memoizedProps = shouldUpdate.props;
+  hasContext && invalidateContextProvider(workInProgress, !0);
+  return workInProgress.child;
+}
+function pushHostRootContext(workInProgress) {
+  var root = workInProgress.stateNode;
+  root.pendingContext
+    ? pushTopLevelContextObject(
+        workInProgress,
+        root.pendingContext,
+        root.pendingContext !== root.context
+      )
+    : root.context &&
+      pushTopLevelContextObject(workInProgress, root.context, !1);
+  pushHostContainer(workInProgress, root.containerInfo);
+}
+function propagateContextChange(
+  workInProgress,
+  context,
+  changedBits,
+  renderExpirationTime
+) {
+  var fiber = workInProgress.child;
+  null !== fiber && (fiber.return = workInProgress);
+  for (; null !== fiber; ) {
+    switch (fiber.tag) {
+      case 12:
+        var nextFiber = fiber.stateNode | 0;
+        if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
+          for (nextFiber = fiber; null !== nextFiber; ) {
+            var alternate = nextFiber.alternate;
+            if (
+              0 === nextFiber.expirationTime ||
+              nextFiber.expirationTime > renderExpirationTime
+            )
+              (nextFiber.expirationTime = renderExpirationTime),
                 null !== alternate &&
-                (0 === alternate.expirationTime ||
-                  alternate.expirationTime > renderExpirationTime)
-              )
-                alternate.expirationTime = renderExpirationTime;
-              else break;
-              nextFiber = nextFiber.return;
-            }
-            nextFiber = null;
-          } else nextFiber = fiber.child;
+                  (0 === alternate.expirationTime ||
+                    alternate.expirationTime > renderExpirationTime) &&
+                  (alternate.expirationTime = renderExpirationTime);
+            else if (
+              null !== alternate &&
+              (0 === alternate.expirationTime ||
+                alternate.expirationTime > renderExpirationTime)
+            )
+              alternate.expirationTime = renderExpirationTime;
+            else break;
+            nextFiber = nextFiber.return;
+          }
+          nextFiber = null;
+        } else nextFiber = fiber.child;
+        break;
+      case 13:
+        nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+        break;
+      default:
+        nextFiber = fiber.child;
+    }
+    if (null !== nextFiber) nextFiber.return = fiber;
+    else
+      for (nextFiber = fiber; null !== nextFiber; ) {
+        if (nextFiber === workInProgress) {
+          nextFiber = null;
           break;
-        case 13:
-          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+        }
+        fiber = nextFiber.sibling;
+        if (null !== fiber) {
+          fiber.return = nextFiber.return;
+          nextFiber = fiber;
           break;
-        default:
-          nextFiber = fiber.child;
-      }
-      if (null !== nextFiber) nextFiber.return = fiber;
-      else
-        for (nextFiber = fiber; null !== nextFiber; ) {
-          if (nextFiber === workInProgress) {
-            nextFiber = null;
-            break;
-          }
-          fiber = nextFiber.sibling;
-          if (null !== fiber) {
-            fiber.return = nextFiber.return;
-            nextFiber = fiber;
-            break;
-          }
-          nextFiber = nextFiber.return;
         }
-      fiber = nextFiber;
-    }
+        nextFiber = nextFiber.return;
+      }
+    fiber = nextFiber;
   }
-  function updateContextProvider(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var context = workInProgress.type._context,
-      newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps,
-      canBailOnProps = !0;
-    if (hasLegacyContextChanged()) canBailOnProps = !1;
-    else if (oldProps === newProps)
+}
+function updateContextProvider(current, workInProgress, renderExpirationTime) {
+  var context = workInProgress.type._context,
+    newProps = workInProgress.pendingProps,
+    oldProps = workInProgress.memoizedProps,
+    canBailOnProps = !0;
+  if (didPerformWorkStackCursor.current) canBailOnProps = !1;
+  else if (oldProps === newProps)
+    return (
+      (workInProgress.stateNode = 0),
+      pushProvider(workInProgress),
+      bailoutOnAlreadyFinishedWork(current, workInProgress)
+    );
+  var newValue = newProps.value;
+  workInProgress.memoizedProps = newProps;
+  if (null === oldProps) newValue = 1073741823;
+  else if (oldProps.value === newProps.value) {
+    if (oldProps.children === newProps.children && canBailOnProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
         bailoutOnAlreadyFinishedWork(current, workInProgress)
       );
-    var newValue = newProps.value;
-    workInProgress.memoizedProps = newProps;
-    if (null === oldProps) newValue = 1073741823;
-    else if (oldProps.value === newProps.value) {
+    newValue = 0;
+  } else {
+    var oldValue = oldProps.value;
+    if (
+      (oldValue === newValue &&
+        (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
+      (oldValue !== oldValue && newValue !== newValue)
+    ) {
       if (oldProps.children === newProps.children && canBailOnProps)
         return (
           (workInProgress.stateNode = 0),
@@ -3204,393 +3353,364 @@ function ReactFiberBeginWork(
           bailoutOnAlreadyFinishedWork(current, workInProgress)
         );
       newValue = 0;
-    } else {
-      var oldValue = oldProps.value;
-      if (
-        (oldValue === newValue &&
-          (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
-        (oldValue !== oldValue && newValue !== newValue)
-      ) {
-        if (oldProps.children === newProps.children && canBailOnProps)
-          return (
-            (workInProgress.stateNode = 0),
-            pushProvider(workInProgress),
-            bailoutOnAlreadyFinishedWork(current, workInProgress)
-          );
-        newValue = 0;
-      } else if (
-        ((newValue =
-          "function" === typeof context._calculateChangedBits
-            ? context._calculateChangedBits(oldValue, newValue)
-            : 1073741823),
-        (newValue |= 0),
-        0 === newValue)
-      ) {
-        if (oldProps.children === newProps.children && canBailOnProps)
-          return (
-            (workInProgress.stateNode = 0),
-            pushProvider(workInProgress),
-            bailoutOnAlreadyFinishedWork(current, workInProgress)
-          );
-      } else
-        propagateContextChange(
+    } else if (
+      ((newValue =
+        "function" === typeof context._calculateChangedBits
+          ? context._calculateChangedBits(oldValue, newValue)
+          : 1073741823),
+      (newValue |= 0),
+      0 === newValue)
+    ) {
+      if (oldProps.children === newProps.children && canBailOnProps)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+    } else
+      propagateContextChange(
+        workInProgress,
+        context,
+        newValue,
+        renderExpirationTime
+      );
+  }
+  workInProgress.stateNode = newValue;
+  pushProvider(workInProgress);
+  reconcileChildren(current, workInProgress, newProps.children);
+  return workInProgress.child;
+}
+function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+  invariant(
+    null === current || workInProgress.child === current.child,
+    "Resuming work not yet implemented."
+  );
+  if (null !== workInProgress.child) {
+    current = workInProgress.child;
+    var newChild = createWorkInProgress(
+      current,
+      current.pendingProps,
+      current.expirationTime
+    );
+    workInProgress.child = newChild;
+    for (newChild.return = workInProgress; null !== current.sibling; )
+      (current = current.sibling),
+        (newChild = newChild.sibling = createWorkInProgress(
+          current,
+          current.pendingProps,
+          current.expirationTime
+        )),
+        (newChild.return = workInProgress);
+    newChild.sibling = null;
+  }
+  return workInProgress.child;
+}
+function beginWork(current, workInProgress, renderExpirationTime) {
+  if (
+    0 === workInProgress.expirationTime ||
+    workInProgress.expirationTime > renderExpirationTime
+  ) {
+    switch (workInProgress.tag) {
+      case 3:
+        pushHostRootContext(workInProgress);
+        break;
+      case 2:
+        pushContextProvider(workInProgress);
+        break;
+      case 4:
+        pushHostContainer(
           workInProgress,
-          context,
-          newValue,
-          renderExpirationTime
+          workInProgress.stateNode.containerInfo
         );
+        break;
+      case 13:
+        pushProvider(workInProgress);
     }
-    workInProgress.stateNode = newValue;
-    pushProvider(workInProgress);
-    reconcileChildren(current, workInProgress, newProps.children);
-    return workInProgress.child;
+    return null;
   }
-  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
-    invariant(
-      null === current || workInProgress.child === current.child,
-      "Resuming work not yet implemented."
-    );
-    if (null !== workInProgress.child) {
-      current = workInProgress.child;
-      var newChild = createWorkInProgress(
-        current,
-        current.pendingProps,
-        current.expirationTime
+  switch (workInProgress.tag) {
+    case 0:
+      invariant(
+        null === current,
+        "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
       );
-      workInProgress.child = newChild;
-      for (newChild.return = workInProgress; null !== current.sibling; )
-        (current = current.sibling),
-          (newChild = newChild.sibling = createWorkInProgress(
+      var fn = workInProgress.type,
+        props = workInProgress.pendingProps,
+        unmaskedContext = getUnmaskedContext(workInProgress);
+      unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
+      fn = fn(props, unmaskedContext);
+      workInProgress.effectTag |= 1;
+      "object" === typeof fn &&
+      null !== fn &&
+      "function" === typeof fn.render &&
+      void 0 === fn.$$typeof
+        ? ((unmaskedContext = workInProgress.type),
+          (workInProgress.tag = 2),
+          (workInProgress.memoizedState =
+            null !== fn.state && void 0 !== fn.state ? fn.state : null),
+          (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
+          "function" === typeof unmaskedContext &&
+            applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+          (props = pushContextProvider(workInProgress)),
+          (fn.updater = classComponentUpdater),
+          (workInProgress.stateNode = fn),
+          (fn._reactInternalFiber = workInProgress),
+          mountClassInstance(workInProgress, renderExpirationTime),
+          (current = finishClassComponent(
             current,
-            current.pendingProps,
-            current.expirationTime
-          )),
-          (newChild.return = workInProgress);
-      newChild.sibling = null;
-    }
-    return workInProgress.child;
-  }
-  var shouldSetTextContent = config.shouldSetTextContent,
-    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree,
-    pushHostContext = hostContext.pushHostContext,
-    pushHostContainer = hostContext.pushHostContainer,
-    pushProvider = newContext.pushProvider,
-    getContextCurrentValue = newContext.getContextCurrentValue,
-    getContextChangedBits = newContext.getContextChangedBits,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    hasLegacyContextChanged = legacyContext.hasContextChanged,
-    pushLegacyContextProvider = legacyContext.pushContextProvider,
-    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
-    invalidateContextProvider = legacyContext.invalidateContextProvider,
-    enterHydrationState = hydrationContext.enterHydrationState,
-    resetHydrationState = hydrationContext.resetHydrationState,
-    tryToClaimNextHydratableInstance =
-      hydrationContext.tryToClaimNextHydratableInstance;
-  config = ReactFiberClassComponent(
-    legacyContext,
-    scheduleWork,
-    computeExpirationForFiber,
-    function(workInProgress, nextProps) {
-      workInProgress.memoizedProps = nextProps;
-    },
-    function(workInProgress, nextState) {
-      workInProgress.memoizedState = nextState;
-    },
-    recalculateCurrentTime
-  );
-  var adoptClassInstance = config.adoptClassInstance,
-    constructClassInstance = config.constructClassInstance,
-    mountClassInstance = config.mountClassInstance,
-    resumeMountClassInstance = config.resumeMountClassInstance,
-    updateClassInstance = config.updateClassInstance;
-  return {
-    beginWork: function(current, workInProgress, renderExpirationTime) {
-      if (
-        0 === workInProgress.expirationTime ||
-        workInProgress.expirationTime > renderExpirationTime
-      ) {
-        switch (workInProgress.tag) {
-          case 3:
-            pushHostRootContext(workInProgress);
-            break;
-          case 2:
-            pushLegacyContextProvider(workInProgress);
-            break;
-          case 4:
-            pushHostContainer(
-              workInProgress,
-              workInProgress.stateNode.containerInfo
-            );
-            break;
-          case 13:
-            pushProvider(workInProgress);
-        }
-        return null;
-      }
-      switch (workInProgress.tag) {
-        case 0:
-          invariant(
-            null === current,
-            "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
-          );
-          var fn = workInProgress.type,
-            props = workInProgress.pendingProps,
-            unmaskedContext = getUnmaskedContext(workInProgress);
-          unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
-          fn = fn(props, unmaskedContext);
-          workInProgress.effectTag |= 1;
-          "object" === typeof fn &&
-          null !== fn &&
-          "function" === typeof fn.render &&
-          void 0 === fn.$$typeof
-            ? ((unmaskedContext = workInProgress.type),
-              (workInProgress.tag = 2),
-              (workInProgress.memoizedState =
-                null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
-              "function" === typeof unmaskedContext &&
-                applyDerivedStateFromProps(
-                  workInProgress,
-                  unmaskedContext,
-                  props
-                ),
-              (props = pushLegacyContextProvider(workInProgress)),
-              adoptClassInstance(workInProgress, fn),
-              mountClassInstance(workInProgress, renderExpirationTime),
-              (current = finishClassComponent(
-                current,
+            workInProgress,
+            !0,
+            props,
+            renderExpirationTime
+          )))
+        : ((workInProgress.tag = 1),
+          reconcileChildren(current, workInProgress, fn),
+          (workInProgress.memoizedProps = props),
+          (current = workInProgress.child));
+      return current;
+    case 1:
+      return (
+        (props = workInProgress.type),
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime
+          ? ((fn = getUnmaskedContext(workInProgress)),
+            (fn = getMaskedContext(workInProgress, fn)),
+            (props = props(renderExpirationTime, fn)),
+            (workInProgress.effectTag |= 1),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 2:
+      props = pushContextProvider(workInProgress);
+      if (null === current)
+        if (null === workInProgress.stateNode) {
+          var props$jscomp$0 = workInProgress.pendingProps,
+            ctor = workInProgress.type;
+          fn = getUnmaskedContext(workInProgress);
+          var needsContext =
+            2 === workInProgress.tag &&
+            null != workInProgress.type.contextTypes;
+          unmaskedContext = needsContext
+            ? getMaskedContext(workInProgress, fn)
+            : emptyObject;
+          props$jscomp$0 = new ctor(props$jscomp$0, unmaskedContext);
+          workInProgress.memoizedState =
+            null !== props$jscomp$0.state && void 0 !== props$jscomp$0.state
+              ? props$jscomp$0.state
+              : null;
+          props$jscomp$0.updater = classComponentUpdater;
+          workInProgress.stateNode = props$jscomp$0;
+          props$jscomp$0._reactInternalFiber = workInProgress;
+          needsContext &&
+            ((needsContext = workInProgress.stateNode),
+            (needsContext.__reactInternalMemoizedUnmaskedChildContext = fn),
+            (needsContext.__reactInternalMemoizedMaskedChildContext = unmaskedContext));
+          mountClassInstance(workInProgress, renderExpirationTime);
+          fn = !0;
+        } else {
+          ctor = workInProgress.type;
+          fn = workInProgress.stateNode;
+          needsContext = workInProgress.memoizedProps;
+          unmaskedContext = workInProgress.pendingProps;
+          fn.props = needsContext;
+          var oldContext = fn.context;
+          props$jscomp$0 = getUnmaskedContext(workInProgress);
+          props$jscomp$0 = getMaskedContext(workInProgress, props$jscomp$0);
+          var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
+          (ctor =
+            "function" === typeof getDerivedStateFromProps ||
+            "function" === typeof fn.getSnapshotBeforeUpdate) ||
+            ("function" !== typeof fn.UNSAFE_componentWillReceiveProps &&
+              "function" !== typeof fn.componentWillReceiveProps) ||
+            ((needsContext !== unmaskedContext ||
+              oldContext !== props$jscomp$0) &&
+              callComponentWillReceiveProps(
                 workInProgress,
-                !0,
-                props,
-                renderExpirationTime
-              )))
-            : ((workInProgress.tag = 1),
-              reconcileChildren(current, workInProgress, fn),
-              (workInProgress.memoizedProps = props),
-              (current = workInProgress.child));
-          return current;
-        case 1:
-          return (
-            (props = workInProgress.type),
-            (renderExpirationTime = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime
-              ? ((fn = getUnmaskedContext(workInProgress)),
-                (fn = getMaskedContext(workInProgress, fn)),
-                (props = props(renderExpirationTime, fn)),
-                (workInProgress.effectTag |= 1),
-                reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 2:
-          return (
-            (props = pushLegacyContextProvider(workInProgress)),
-            null === current
-              ? null === workInProgress.stateNode
-                ? (constructClassInstance(
-                    workInProgress,
-                    workInProgress.pendingProps,
-                    renderExpirationTime
-                  ),
-                  mountClassInstance(workInProgress, renderExpirationTime),
-                  (fn = !0))
-                : (fn = resumeMountClassInstance(
-                    workInProgress,
-                    renderExpirationTime
-                  ))
-              : (fn = updateClassInstance(
-                  current,
-                  workInProgress,
-                  renderExpirationTime
-                )),
-            finishClassComponent(
-              current,
+                fn,
+                unmaskedContext,
+                props$jscomp$0
+              ));
+          hasForceUpdate = !1;
+          var oldState = workInProgress.memoizedState;
+          oldContext = fn.state = oldState;
+          var updateQueue = workInProgress.updateQueue;
+          null !== updateQueue &&
+            (processUpdateQueue(
               workInProgress,
+              updateQueue,
+              unmaskedContext,
               fn,
-              props,
               renderExpirationTime
-            )
-          );
-        case 3:
-          return (
-            pushHostRootContext(workInProgress),
-            (props = workInProgress.updateQueue),
-            null !== props
-              ? ((fn = workInProgress.memoizedState),
-                (fn = null !== fn ? fn.element : null),
-                processUpdateQueue(
-                  workInProgress,
-                  props,
-                  workInProgress.pendingProps,
-                  null,
-                  renderExpirationTime
-                ),
-                (props = workInProgress.memoizedState.element),
-                props === fn
-                  ? (resetHydrationState(),
-                    (current = bailoutOnAlreadyFinishedWork(
-                      current,
-                      workInProgress
-                    )))
-                  : ((fn = workInProgress.stateNode),
-                    (null === current || null === current.child) &&
-                    fn.hydrate &&
-                    enterHydrationState(workInProgress)
-                      ? ((workInProgress.effectTag |= 2),
-                        (workInProgress.child = mountChildFibers(
-                          workInProgress,
-                          null,
-                          props,
-                          renderExpirationTime
-                        )))
-                      : (resetHydrationState(),
-                        reconcileChildren(current, workInProgress, props)),
-                    (current = workInProgress.child)))
-              : (resetHydrationState(),
-                (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                ))),
-            current
-          );
-        case 5:
-          a: {
-            pushHostContext(workInProgress);
-            null === current &&
-              tryToClaimNextHydratableInstance(workInProgress);
-            props = workInProgress.type;
-            var memoizedProps = workInProgress.memoizedProps;
-            fn = workInProgress.pendingProps;
-            unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && memoizedProps === fn) {
-              if (
-                (memoizedProps =
-                  workInProgress.mode & 1 &&
-                  shouldDeprioritizeSubtree(props, fn))
-              )
-                workInProgress.expirationTime = 1073741823;
-              if (!memoizedProps || 1073741823 !== renderExpirationTime) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-            }
-            memoizedProps = fn.children;
-            shouldSetTextContent(props, fn)
-              ? (memoizedProps = null)
-              : unmaskedContext &&
-                shouldSetTextContent(props, unmaskedContext) &&
-                (workInProgress.effectTag |= 16);
-            markRef(current, workInProgress);
-            1073741823 !== renderExpirationTime &&
-            workInProgress.mode & 1 &&
-            shouldDeprioritizeSubtree(props, fn)
-              ? ((workInProgress.expirationTime = 1073741823),
-                (workInProgress.memoizedProps = fn),
-                (current = null))
-              : (reconcileChildren(current, workInProgress, memoizedProps),
-                (workInProgress.memoizedProps = fn),
-                (current = workInProgress.child));
-          }
-          return current;
-        case 6:
-          return (
-            null === current &&
-              tryToClaimNextHydratableInstance(workInProgress),
-            (workInProgress.memoizedProps = workInProgress.pendingProps),
-            null
-          );
-        case 16:
-          return null;
-        case 4:
-          return (
-            pushHostContainer(
-              workInProgress,
-              workInProgress.stateNode.containerInfo
             ),
-            (props = workInProgress.pendingProps),
-            hasLegacyContextChanged() || workInProgress.memoizedProps !== props
-              ? (null === current
-                  ? (workInProgress.child = reconcileChildFibers(
-                      workInProgress,
-                      null,
-                      props,
-                      renderExpirationTime
-                    ))
-                  : reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = props),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 14:
-          return (
-            (props = workInProgress.type.render),
-            (renderExpirationTime = workInProgress.pendingProps),
-            (fn = workInProgress.ref),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime ||
-            fn !== (null !== current ? current.ref : null)
-              ? ((props = props(renderExpirationTime, fn)),
-                reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 10:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime
-              ? (reconcileChildren(
-                  current,
+            (oldContext = workInProgress.memoizedState));
+          needsContext !== unmaskedContext ||
+          oldState !== oldContext ||
+          didPerformWorkStackCursor.current ||
+          hasForceUpdate
+            ? ("function" === typeof getDerivedStateFromProps &&
+                (applyDerivedStateFromProps(
                   workInProgress,
-                  renderExpirationTime
+                  getDerivedStateFromProps,
+                  unmaskedContext
                 ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 11:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps.children),
-            hasLegacyContextChanged() ||
-            (null !== renderExpirationTime &&
-              workInProgress.memoizedProps !== renderExpirationTime)
-              ? (reconcileChildren(
-                  current,
+                (oldContext = workInProgress.memoizedState)),
+              (needsContext =
+                hasForceUpdate ||
+                checkShouldComponentUpdate(
+                  workInProgress,
+                  needsContext,
+                  unmaskedContext,
+                  oldState,
+                  oldContext,
+                  props$jscomp$0
+                ))
+                ? (ctor ||
+                    ("function" !== typeof fn.UNSAFE_componentWillMount &&
+                      "function" !== typeof fn.componentWillMount) ||
+                    ("function" === typeof fn.componentWillMount &&
+                      fn.componentWillMount(),
+                    "function" === typeof fn.UNSAFE_componentWillMount &&
+                      fn.UNSAFE_componentWillMount()),
+                  "function" === typeof fn.componentDidMount &&
+                    (workInProgress.effectTag |= 4))
+                : ("function" === typeof fn.componentDidMount &&
+                    (workInProgress.effectTag |= 4),
+                  (workInProgress.memoizedProps = unmaskedContext),
+                  (workInProgress.memoizedState = oldContext)),
+              (fn.props = unmaskedContext),
+              (fn.state = oldContext),
+              (fn.context = props$jscomp$0),
+              (fn = needsContext))
+            : ("function" === typeof fn.componentDidMount &&
+                (workInProgress.effectTag |= 4),
+              (fn = !1));
+        }
+      else
+        (ctor = workInProgress.type),
+          (fn = workInProgress.stateNode),
+          (unmaskedContext = workInProgress.memoizedProps),
+          (needsContext = workInProgress.pendingProps),
+          (fn.props = unmaskedContext),
+          (oldContext = fn.context),
+          (props$jscomp$0 = getUnmaskedContext(workInProgress)),
+          (props$jscomp$0 = getMaskedContext(workInProgress, props$jscomp$0)),
+          (getDerivedStateFromProps = ctor.getDerivedStateFromProps),
+          (ctor =
+            "function" === typeof getDerivedStateFromProps ||
+            "function" === typeof fn.getSnapshotBeforeUpdate) ||
+            ("function" !== typeof fn.UNSAFE_componentWillReceiveProps &&
+              "function" !== typeof fn.componentWillReceiveProps) ||
+            ((unmaskedContext !== needsContext ||
+              oldContext !== props$jscomp$0) &&
+              callComponentWillReceiveProps(
+                workInProgress,
+                fn,
+                needsContext,
+                props$jscomp$0
+              )),
+          (hasForceUpdate = !1),
+          (oldContext = workInProgress.memoizedState),
+          (oldState = fn.state = oldContext),
+          (updateQueue = workInProgress.updateQueue),
+          null !== updateQueue &&
+            (processUpdateQueue(
+              workInProgress,
+              updateQueue,
+              needsContext,
+              fn,
+              renderExpirationTime
+            ),
+            (oldState = workInProgress.memoizedState)),
+          unmaskedContext !== needsContext ||
+          oldContext !== oldState ||
+          didPerformWorkStackCursor.current ||
+          hasForceUpdate
+            ? ("function" === typeof getDerivedStateFromProps &&
+                (applyDerivedStateFromProps(
                   workInProgress,
-                  renderExpirationTime
+                  getDerivedStateFromProps,
+                  needsContext
                 ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 15:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps),
-            workInProgress.memoizedProps === renderExpirationTime
+                (oldState = workInProgress.memoizedState)),
+              (getDerivedStateFromProps =
+                hasForceUpdate ||
+                checkShouldComponentUpdate(
+                  workInProgress,
+                  unmaskedContext,
+                  needsContext,
+                  oldContext,
+                  oldState,
+                  props$jscomp$0
+                ))
+                ? (ctor ||
+                    ("function" !== typeof fn.UNSAFE_componentWillUpdate &&
+                      "function" !== typeof fn.componentWillUpdate) ||
+                    ("function" === typeof fn.componentWillUpdate &&
+                      fn.componentWillUpdate(
+                        needsContext,
+                        oldState,
+                        props$jscomp$0
+                      ),
+                    "function" === typeof fn.UNSAFE_componentWillUpdate &&
+                      fn.UNSAFE_componentWillUpdate(
+                        needsContext,
+                        oldState,
+                        props$jscomp$0
+                      )),
+                  "function" === typeof fn.componentDidUpdate &&
+                    (workInProgress.effectTag |= 4),
+                  "function" === typeof fn.getSnapshotBeforeUpdate &&
+                    (workInProgress.effectTag |= 256))
+                : ("function" !== typeof fn.componentDidUpdate ||
+                    (unmaskedContext === current.memoizedProps &&
+                      oldContext === current.memoizedState) ||
+                    (workInProgress.effectTag |= 4),
+                  "function" !== typeof fn.getSnapshotBeforeUpdate ||
+                    (unmaskedContext === current.memoizedProps &&
+                      oldContext === current.memoizedState) ||
+                    (workInProgress.effectTag |= 256),
+                  (workInProgress.memoizedProps = needsContext),
+                  (workInProgress.memoizedState = oldState)),
+              (fn.props = needsContext),
+              (fn.state = oldState),
+              (fn.context = props$jscomp$0),
+              (fn = getDerivedStateFromProps))
+            : ("function" !== typeof fn.componentDidUpdate ||
+                (unmaskedContext === current.memoizedProps &&
+                  oldContext === current.memoizedState) ||
+                (workInProgress.effectTag |= 4),
+              "function" !== typeof fn.getSnapshotBeforeUpdate ||
+                (unmaskedContext === current.memoizedProps &&
+                  oldContext === current.memoizedState) ||
+                (workInProgress.effectTag |= 256),
+              (fn = !1));
+      return finishClassComponent(
+        current,
+        workInProgress,
+        fn,
+        props,
+        renderExpirationTime
+      );
+    case 3:
+      return (
+        pushHostRootContext(workInProgress),
+        (props = workInProgress.updateQueue),
+        null !== props
+          ? ((fn = workInProgress.memoizedState),
+            (fn = null !== fn ? fn.element : null),
+            processUpdateQueue(
+              workInProgress,
+              props,
+              workInProgress.pendingProps,
+              null,
+              renderExpirationTime
+            ),
+            (renderExpirationTime = workInProgress.memoizedState.element),
+            renderExpirationTime === fn
               ? (current = bailoutOnAlreadyFinishedWork(
                   current,
                   workInProgress
@@ -3598,347 +3718,403 @@ function ReactFiberBeginWork(
               : (reconcileChildren(
                   current,
                   workInProgress,
-                  renderExpirationTime.children
+                  renderExpirationTime
                 ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child)),
-            current
-          );
-        case 13:
-          return updateContextProvider(
-            current,
-            workInProgress,
-            renderExpirationTime
-          );
-        case 12:
-          a: {
-            fn = workInProgress.type;
-            unmaskedContext = workInProgress.pendingProps;
-            memoizedProps = workInProgress.memoizedProps;
-            props = getContextCurrentValue(fn);
-            var changedBits = getContextChangedBits(fn);
-            if (
-              hasLegacyContextChanged() ||
-              0 !== changedBits ||
-              memoizedProps !== unmaskedContext
-            ) {
-              workInProgress.memoizedProps = unmaskedContext;
-              var observedBits = unmaskedContext.unstable_observedBits;
-              if (void 0 === observedBits || null === observedBits)
-                observedBits = 1073741823;
-              workInProgress.stateNode = observedBits;
-              if (0 !== (changedBits & observedBits))
-                propagateContextChange(
+                (current = workInProgress.child)))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 5:
+      return (
+        requiredContext(rootInstanceStackCursor.current),
+        (renderExpirationTime = requiredContext(contextStackCursor$1.current)),
+        (props = workInProgress.type),
+        (props =
+          "AndroidTextInput" === props ||
+          "RCTMultilineTextInputView" === props ||
+          "RCTSinglelineTextInputView" === props ||
+          "RCTText" === props ||
+          "RCTVirtualText" === props),
+        (props =
+          renderExpirationTime.isInAParentText !== props
+            ? { isInAParentText: props }
+            : renderExpirationTime),
+        renderExpirationTime !== props &&
+          (push(contextFiberStackCursor, workInProgress, workInProgress),
+          push(contextStackCursor$1, props, workInProgress)),
+        null === current && tryToClaimNextHydratableInstance(workInProgress),
+        (props = workInProgress.memoizedProps),
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current || props !== renderExpirationTime
+          ? ((props = renderExpirationTime.children),
+            markRef(current, workInProgress),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 6:
+      return (
+        null === current && tryToClaimNextHydratableInstance(workInProgress),
+        (workInProgress.memoizedProps = workInProgress.pendingProps),
+        null
+      );
+    case 16:
+      return null;
+    case 4:
+      return (
+        pushHostContainer(
+          workInProgress,
+          workInProgress.stateNode.containerInfo
+        ),
+        (props = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== props
+          ? (null === current
+              ? (workInProgress.child = reconcileChildFibers(
                   workInProgress,
-                  fn,
-                  changedBits,
+                  null,
+                  props,
                   renderExpirationTime
-                );
-              else if (memoizedProps === unmaskedContext) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-              renderExpirationTime = unmaskedContext.children;
-              renderExpirationTime = renderExpirationTime(props);
-              workInProgress.effectTag |= 1;
-              reconcileChildren(current, workInProgress, renderExpirationTime);
-              current = workInProgress.child;
-            } else
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
-          return current;
-        default:
-          invariant(
-            !1,
-            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+                ))
+              : reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = props),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 14:
+      return (
+        (props = workInProgress.type.render),
+        (renderExpirationTime = workInProgress.pendingProps),
+        (fn = workInProgress.ref),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime ||
+        fn !== (null !== current ? current.ref : null)
+          ? ((props = props(renderExpirationTime, fn)),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 10:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime
+          ? (reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 11:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps.children),
+        didPerformWorkStackCursor.current ||
+        (null !== renderExpirationTime &&
+          workInProgress.memoizedProps !== renderExpirationTime)
+          ? (reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 15:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps),
+        workInProgress.memoizedProps === renderExpirationTime
+          ? (current = bailoutOnAlreadyFinishedWork(current, workInProgress))
+          : (reconcileChildren(
+              current,
+              workInProgress,
+              renderExpirationTime.children
+            ),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child)),
+        current
+      );
+    case 13:
+      return updateContextProvider(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case 12:
+      a: if (
+        ((fn = workInProgress.type),
+        (unmaskedContext = workInProgress.pendingProps),
+        (needsContext = workInProgress.memoizedProps),
+        (props = fn._currentValue2),
+        (props$jscomp$0 = fn._changedBits2),
+        didPerformWorkStackCursor.current ||
+          0 !== props$jscomp$0 ||
+          needsContext !== unmaskedContext)
+      ) {
+        workInProgress.memoizedProps = unmaskedContext;
+        ctor = unmaskedContext.unstable_observedBits;
+        if (void 0 === ctor || null === ctor) ctor = 1073741823;
+        workInProgress.stateNode = ctor;
+        if (0 !== (props$jscomp$0 & ctor))
+          propagateContextChange(
+            workInProgress,
+            fn,
+            props$jscomp$0,
+            renderExpirationTime
           );
-      }
-    }
-  };
+        else if (needsContext === unmaskedContext) {
+          current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          break a;
+        }
+        renderExpirationTime = unmaskedContext.children;
+        renderExpirationTime = renderExpirationTime(props);
+        workInProgress.effectTag |= 1;
+        reconcileChildren(current, workInProgress, renderExpirationTime);
+        current = workInProgress.child;
+      } else current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+      return current;
+    default:
+      invariant(
+        !1,
+        "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
 }
-function ReactFiberCompleteWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext
-) {
-  function markUpdate(workInProgress) {
-    workInProgress.effectTag |= 4;
+function appendAllChildren(parent, workInProgress) {
+  for (var node = workInProgress.child; null !== node; ) {
+    if (5 === node.tag || 6 === node.tag)
+      FabricUIManager.appendChild(parent.node, node.stateNode.node);
+    else if (4 !== node.tag && null !== node.child) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === workInProgress) break;
+    for (; null === node.sibling; ) {
+      if (null === node.return || node.return === workInProgress) return;
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
   }
-  function appendAllChildren(parent, workInProgress) {
-    for (var node = workInProgress.child; null !== node; ) {
+}
+var updateHostContainer = void 0,
+  updateHostComponent$1 = void 0,
+  updateHostText$1 = void 0;
+updateHostContainer = function(workInProgress) {
+  var portalOrRoot = workInProgress.stateNode;
+  if (null !== workInProgress.firstEffect) {
+    var container = portalOrRoot.containerInfo,
+      newChildSet = FabricUIManager.createChildSet(container);
+    a: for (var node = workInProgress.child; null !== node; ) {
       if (5 === node.tag || 6 === node.tag)
-        appendInitialChild(parent, node.stateNode);
+        FabricUIManager.appendChildToSet(newChildSet, node.stateNode.node);
       else if (4 !== node.tag && null !== node.child) {
         node.child.return = node;
         node = node.child;
         continue;
       }
-      if (node === workInProgress) break;
+      if (node === workInProgress) break a;
       for (; null === node.sibling; ) {
-        if (null === node.return || node.return === workInProgress) return;
+        if (null === node.return || node.return === workInProgress) break a;
         node = node.return;
       }
       node.sibling.return = node.return;
       node = node.sibling;
     }
+    portalOrRoot.pendingChildren = newChildSet;
+    workInProgress.effectTag |= 4;
+    FabricUIManager.completeRoot(container, newChildSet);
   }
-  var createInstance = config.createInstance,
-    createTextInstance = config.createTextInstance,
-    appendInitialChild = config.appendInitialChild,
-    finalizeInitialChildren = config.finalizeInitialChildren,
-    prepareUpdate = config.prepareUpdate,
-    persistence = config.persistence,
-    getRootHostContainer = hostContext.getRootHostContainer,
-    popHostContext = hostContext.popHostContext,
-    getHostContext = hostContext.getHostContext,
-    popHostContainer = hostContext.popHostContainer,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider,
-    prepareToHydrateHostInstance =
-      hydrationContext.prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance =
-      hydrationContext.prepareToHydrateHostTextInstance,
-    popHydrationState = hydrationContext.popHydrationState,
-    updateHostContainer = void 0,
-    updateHostComponent = void 0,
-    updateHostText = void 0;
-  if (config.mutation) invariant(!1, "Mutating reconciler is disabled.");
-  else if (persistence) {
-    var cloneInstance = persistence.cloneInstance,
-      createContainerChildSet = persistence.createContainerChildSet,
-      appendChildToContainerChildSet =
-        persistence.appendChildToContainerChildSet,
-      finalizeContainerChildren = persistence.finalizeContainerChildren;
-    updateHostContainer = function(workInProgress) {
-      var portalOrRoot = workInProgress.stateNode;
-      if (null !== workInProgress.firstEffect) {
-        var container = portalOrRoot.containerInfo,
-          newChildSet = createContainerChildSet(container);
-        a: for (var node = workInProgress.child; null !== node; ) {
-          if (5 === node.tag || 6 === node.tag)
-            appendChildToContainerChildSet(newChildSet, node.stateNode);
-          else if (4 !== node.tag && null !== node.child) {
-            node.child.return = node;
-            node = node.child;
-            continue;
-          }
-          if (node === workInProgress) break a;
-          for (; null === node.sibling; ) {
-            if (null === node.return || node.return === workInProgress) break a;
-            node = node.return;
-          }
-          node.sibling.return = node.return;
-          node = node.sibling;
-        }
-        portalOrRoot.pendingChildren = newChildSet;
-        markUpdate(workInProgress);
-        finalizeContainerChildren(container, newChildSet);
-      }
+};
+updateHostComponent$1 = function(current, workInProgress, updatePayload) {
+  var childrenUnchanged = null === workInProgress.firstEffect;
+  current = current.stateNode;
+  if (childrenUnchanged && null === updatePayload)
+    workInProgress.stateNode = current;
+  else {
+    var node = current.node;
+    updatePayload = {
+      node: childrenUnchanged
+        ? null !== updatePayload
+          ? FabricUIManager.cloneNodeWithNewProps(
+              node,
+              updatePayload,
+              workInProgress
+            )
+          : FabricUIManager.cloneNode(node, workInProgress)
+        : null !== updatePayload
+          ? FabricUIManager.cloneNodeWithNewChildrenAndProps(
+              node,
+              updatePayload,
+              workInProgress
+            )
+          : FabricUIManager.cloneNodeWithNewChildren(node, workInProgress),
+      canonical: current.canonical
     };
-    updateHostComponent = function(
+    workInProgress.stateNode = updatePayload;
+    childrenUnchanged
+      ? (workInProgress.effectTag |= 4)
+      : appendAllChildren(updatePayload, workInProgress);
+  }
+};
+updateHostText$1 = function(current, workInProgress, oldText, newText) {
+  oldText !== newText &&
+    ((current = requiredContext(rootInstanceStackCursor.current)),
+    (oldText = requiredContext(contextStackCursor$1.current)),
+    (workInProgress.stateNode = createTextInstance(
+      newText,
       current,
-      workInProgress,
-      updatePayload,
-      type,
-      oldProps,
-      newProps,
-      rootContainerInstance,
-      currentHostContext
-    ) {
-      var childrenUnchanged = null === workInProgress.firstEffect;
-      current = current.stateNode;
-      childrenUnchanged && null === updatePayload
-        ? (workInProgress.stateNode = current)
-        : ((updatePayload = cloneInstance(
-            current,
-            updatePayload,
-            type,
+      oldText,
+      workInProgress
+    )),
+    (workInProgress.effectTag |= 4));
+};
+function completeWork(current, workInProgress) {
+  var newProps = workInProgress.pendingProps;
+  switch (workInProgress.tag) {
+    case 1:
+      return null;
+    case 2:
+      return popContextProvider(workInProgress), null;
+    case 3:
+      popHostContainer(workInProgress);
+      popTopLevelContextObject(workInProgress);
+      newProps = workInProgress.stateNode;
+      newProps.pendingContext &&
+        ((newProps.context = newProps.pendingContext),
+        (newProps.pendingContext = null));
+      if (null === current || null === current.child)
+        workInProgress.effectTag &= -3;
+      updateHostContainer(workInProgress);
+      return null;
+    case 5:
+      popHostContext(workInProgress);
+      var rootContainerInstance = requiredContext(
+          rootInstanceStackCursor.current
+        ),
+        type = workInProgress.type;
+      if (null !== current && null != workInProgress.stateNode) {
+        var oldProps = current.memoizedProps,
+          instance = workInProgress.stateNode,
+          currentHostContext = requiredContext(contextStackCursor$1.current),
+          updatePayload = diffProperties(
+            null,
             oldProps,
             newProps,
-            workInProgress,
-            childrenUnchanged,
-            workInProgress.stateNode
-          )),
-          finalizeInitialChildren(
-            updatePayload,
-            type,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          ) && markUpdate(workInProgress),
-          (workInProgress.stateNode = updatePayload),
-          childrenUnchanged
-            ? markUpdate(workInProgress)
-            : appendAllChildren(updatePayload, workInProgress));
-    };
-    updateHostText = function(current, workInProgress, oldText, newText) {
-      oldText !== newText &&
-        ((current = getRootHostContainer()),
-        (oldText = getHostContext()),
-        (workInProgress.stateNode = createTextInstance(
-          newText,
+            instance.canonical.viewConfig.validAttributes
+          );
+        instance.canonical.currentProps = newProps;
+        updateHostComponent$1(
           current,
-          oldText,
-          workInProgress
-        )),
-        markUpdate(workInProgress));
-    };
-  } else invariant(!1, "Noop reconciler is disabled.");
-  return {
-    completeWork: function(current, workInProgress) {
-      var newProps = workInProgress.pendingProps;
-      switch (workInProgress.tag) {
-        case 1:
-          return null;
-        case 2:
-          return popLegacyContextProvider(workInProgress), null;
-        case 3:
-          popHostContainer(workInProgress);
-          popTopLevelLegacyContextObject(workInProgress);
-          newProps = workInProgress.stateNode;
-          newProps.pendingContext &&
-            ((newProps.context = newProps.pendingContext),
-            (newProps.pendingContext = null));
-          if (null === current || null === current.child)
-            popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
-          updateHostContainer(workInProgress);
-          return null;
-        case 5:
-          popHostContext(workInProgress);
-          var rootContainerInstance = getRootHostContainer(),
-            type = workInProgress.type;
-          if (null !== current && null != workInProgress.stateNode) {
-            var oldProps = current.memoizedProps,
-              instance = workInProgress.stateNode,
-              currentHostContext = getHostContext();
-            instance = prepareUpdate(
-              instance,
-              type,
-              oldProps,
-              newProps,
-              rootContainerInstance,
-              currentHostContext
-            );
-            updateHostComponent(
-              current,
-              workInProgress,
-              instance,
-              type,
-              oldProps,
-              newProps,
-              rootContainerInstance,
-              currentHostContext
-            );
-            current.ref !== workInProgress.ref &&
-              (workInProgress.effectTag |= 128);
-          } else {
-            if (!newProps)
-              return (
-                invariant(
-                  null !== workInProgress.stateNode,
-                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
-                ),
-                null
-              );
-            current = getHostContext();
-            popHydrationState(workInProgress)
-              ? prepareToHydrateHostInstance(
-                  workInProgress,
-                  rootContainerInstance,
-                  current
-                ) && markUpdate(workInProgress)
-              : ((oldProps = createInstance(
-                  type,
-                  newProps,
-                  rootContainerInstance,
-                  current,
-                  workInProgress
-                )),
-                appendAllChildren(oldProps, workInProgress),
-                finalizeInitialChildren(
-                  oldProps,
-                  type,
-                  newProps,
-                  rootContainerInstance,
-                  current
-                ) && markUpdate(workInProgress),
-                (workInProgress.stateNode = oldProps));
-            null !== workInProgress.ref && (workInProgress.effectTag |= 128);
-          }
-          return null;
-        case 6:
-          if (current && null != workInProgress.stateNode)
-            updateHostText(
-              current,
-              workInProgress,
-              current.memoizedProps,
-              newProps
-            );
-          else {
-            if ("string" !== typeof newProps)
-              return (
-                invariant(
-                  null !== workInProgress.stateNode,
-                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
-                ),
-                null
-              );
-            rootContainerInstance = getRootHostContainer();
-            type = getHostContext();
-            popHydrationState(workInProgress)
-              ? prepareToHydrateHostTextInstance(workInProgress) &&
-                markUpdate(workInProgress)
-              : (workInProgress.stateNode = createTextInstance(
-                  newProps,
-                  rootContainerInstance,
-                  type,
-                  workInProgress
-                ));
-          }
-          return null;
-        case 14:
-          return null;
-        case 16:
-          return null;
-        case 10:
-          return null;
-        case 11:
-          return null;
-        case 15:
-          return null;
-        case 4:
+          workInProgress,
+          updatePayload,
+          type,
+          oldProps,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        );
+        current.ref !== workInProgress.ref && (workInProgress.effectTag |= 128);
+      } else {
+        if (!newProps)
           return (
-            popHostContainer(workInProgress),
-            updateHostContainer(workInProgress),
+            invariant(
+              null !== workInProgress.stateNode,
+              "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+            ),
             null
           );
-        case 13:
-          return popProvider(workInProgress), null;
-        case 12:
-          return null;
-        case 0:
-          invariant(
-            !1,
-            "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
-          );
-        default:
-          invariant(
-            !1,
-            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+        instance = requiredContext(contextStackCursor$1.current);
+        current = nextReactTag;
+        nextReactTag += 2;
+        oldProps = ReactNativeViewConfigRegistry.get(type);
+        invariant(
+          "RCTView" !== type || !instance.isInAParentText,
+          "Nesting of <View> within <Text> is not currently supported."
+        );
+        type = diffProperties(
+          null,
+          emptyObject$1,
+          newProps,
+          oldProps.validAttributes
+        );
+        rootContainerInstance = FabricUIManager.createNode(
+          current,
+          oldProps.uiViewClassName,
+          rootContainerInstance,
+          type,
+          workInProgress
+        );
+        newProps = new ReactFabricHostComponent(current, oldProps, newProps);
+        newProps = { node: rootContainerInstance, canonical: newProps };
+        appendAllChildren(newProps, workInProgress);
+        workInProgress.stateNode = newProps;
+        null !== workInProgress.ref && (workInProgress.effectTag |= 128);
+      }
+      return null;
+    case 6:
+      if (current && null != workInProgress.stateNode)
+        updateHostText$1(
+          current,
+          workInProgress,
+          current.memoizedProps,
+          newProps
+        );
+      else {
+        if ("string" !== typeof newProps)
+          return (
+            invariant(
+              null !== workInProgress.stateNode,
+              "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+            ),
+            null
           );
+        rootContainerInstance = requiredContext(
+          rootInstanceStackCursor.current
+        );
+        type = requiredContext(contextStackCursor$1.current);
+        workInProgress.stateNode = createTextInstance(
+          newProps,
+          rootContainerInstance,
+          type,
+          workInProgress
+        );
       }
-    }
-  };
-}
-function createCapturedValue(value, source) {
-  return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
-  };
+      return null;
+    case 14:
+      return null;
+    case 16:
+      return null;
+    case 10:
+      return null;
+    case 11:
+      return null;
+    case 15:
+      return null;
+    case 4:
+      return (
+        popHostContainer(workInProgress),
+        updateHostContainer(workInProgress),
+        null
+      );
+    case 13:
+      return popProvider(workInProgress), null;
+    case 12:
+      return null;
+    case 0:
+      invariant(
+        !1,
+        "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
+      );
+    default:
+      invariant(
+        !1,
+        "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
 }
 function logError(boundary, errorInfo) {
   var source = errorInfo.source,
@@ -3966,2074 +4142,1290 @@ function logError(boundary, errorInfo) {
         "string" === typeof errorInfo
           ? Error(errorInfo + "\n\nThis error is located at:" + source)
           : Error("Unspecified error at:" + source);
-    ExceptionsManager.handleException(errorToHandle, !1);
-  } catch (e) {
-    (e && e.suppressReactErrorLogging) || console.error(e);
-  }
-}
-function ReactFiberCommitWork(config, captureError) {
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (null !== ref)
-      if ("function" === typeof ref)
-        try {
-          ref(null);
-        } catch (refError) {
-          captureError(current, refError);
-        }
-      else ref.current = null;
-  }
-  function commitBeforeMutationLifeCycles(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case 2:
-        if (finishedWork.effectTag & 256 && null !== current) {
-          var prevProps = current.memoizedProps,
-            prevState = current.memoizedState;
-          current = finishedWork.stateNode;
-          current.props = finishedWork.memoizedProps;
-          current.state = finishedWork.memoizedState;
-          finishedWork = current.getSnapshotBeforeUpdate(prevProps, prevState);
-          current.__reactInternalSnapshotBeforeUpdate = finishedWork;
-        }
-        break;
-      case 3:
-      case 5:
-      case 6:
-      case 4:
-        break;
-      default:
-        invariant(
-          !1,
-          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-        );
-    }
-  }
-  function commitLifeCycles(
-    finishedRoot,
-    current,
-    finishedWork,
-    currentTime,
-    committedExpirationTime
-  ) {
-    switch (finishedWork.tag) {
-      case 2:
-        finishedRoot = finishedWork.stateNode;
-        finishedWork.effectTag & 4 &&
-          (null === current
-            ? ((finishedRoot.props = finishedWork.memoizedProps),
-              (finishedRoot.state = finishedWork.memoizedState),
-              finishedRoot.componentDidMount())
-            : ((currentTime = current.memoizedProps),
-              (current = current.memoizedState),
-              (finishedRoot.props = finishedWork.memoizedProps),
-              (finishedRoot.state = finishedWork.memoizedState),
-              finishedRoot.componentDidUpdate(
-                currentTime,
-                current,
-                finishedRoot.__reactInternalSnapshotBeforeUpdate
-              )));
-        current = finishedWork.updateQueue;
-        null !== current &&
-          ((finishedRoot.props = finishedWork.memoizedProps),
-          (finishedRoot.state = finishedWork.memoizedState),
-          commitUpdateQueue(
-            finishedWork,
-            current,
-            finishedRoot,
-            committedExpirationTime
-          ));
-        break;
-      case 3:
-        current = finishedWork.updateQueue;
-        if (null !== current) {
-          finishedRoot = null;
-          if (null !== finishedWork.child)
-            switch (finishedWork.child.tag) {
-              case 5:
-                finishedRoot = getPublicInstance(finishedWork.child.stateNode);
-                break;
-              case 2:
-                finishedRoot = finishedWork.child.stateNode;
-            }
-          commitUpdateQueue(
-            finishedWork,
-            current,
-            finishedRoot,
-            committedExpirationTime
-          );
-        }
-        break;
-      case 5:
-        committedExpirationTime = finishedWork.stateNode;
-        null === current &&
-          finishedWork.effectTag & 4 &&
-          commitMount(
-            committedExpirationTime,
-            finishedWork.type,
-            finishedWork.memoizedProps,
-            finishedWork
-          );
-        break;
-      case 6:
-        break;
-      case 4:
-        break;
-      case 15:
-        break;
-      case 16:
-        break;
-      default:
-        invariant(
-          !1,
-          "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-        );
-    }
+    ExceptionsManager.handleException(errorToHandle, !1);
+  } catch (e) {
+    (e && e.suppressReactErrorLogging) || console.error(e);
   }
-  function commitAttachRef(finishedWork) {
-    var ref = finishedWork.ref;
-    if (null !== ref) {
-      var _instance5 = finishedWork.stateNode;
-      switch (finishedWork.tag) {
-        case 5:
-          finishedWork = getPublicInstance(_instance5);
-          break;
-        default:
-          finishedWork = _instance5;
+}
+function safelyDetachRef(current) {
+  var ref = current.ref;
+  if (null !== ref)
+    if ("function" === typeof ref)
+      try {
+        ref(null);
+      } catch (refError) {
+        captureCommitPhaseError(current, refError);
       }
-      "function" === typeof ref
-        ? ref(finishedWork)
-        : (ref.current = finishedWork);
-    }
-  }
-  function commitDetachRef(current) {
-    current = current.ref;
-    null !== current &&
-      ("function" === typeof current
-        ? current(null)
-        : (current.current = null));
-  }
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation,
-    persistence = config.persistence,
-    emptyPortalContainer = void 0;
-  if (!mutation) {
-    var commitContainer = void 0;
-    if (persistence) {
-      var replaceContainerChildren = persistence.replaceContainerChildren,
-        createContainerChildSet = persistence.createContainerChildSet;
-      emptyPortalContainer = function(current) {
-        current = current.stateNode.containerInfo;
-        var emptyChildSet = createContainerChildSet(current);
-        replaceContainerChildren(current, emptyChildSet);
-      };
-      commitContainer = function(finishedWork) {
-        switch (finishedWork.tag) {
-          case 2:
-            break;
-          case 5:
-            break;
-          case 6:
-            break;
-          case 3:
-          case 4:
-            finishedWork = finishedWork.stateNode;
-            replaceContainerChildren(
-              finishedWork.containerInfo,
-              finishedWork.pendingChildren
-            );
-            break;
-          default:
-            invariant(
-              !1,
-              "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-            );
-        }
-      };
-    } else commitContainer = function() {};
-    return {
-      commitResetTextContent: function() {},
-      commitPlacement: function() {},
-      commitDeletion: function(current$jscomp$0) {
-        a: for (var node = current$jscomp$0; ; ) {
-          var current = node;
-          "function" === typeof onCommitUnmount && onCommitUnmount(current);
-          switch (current.tag) {
-            case 2:
-              safelyDetachRef(current);
-              var _instance6 = current.stateNode;
-              if ("function" === typeof _instance6.componentWillUnmount)
-                try {
-                  (_instance6.props = current.memoizedProps),
-                    (_instance6.state = current.memoizedState),
-                    _instance6.componentWillUnmount();
-                } catch (unmountError) {
-                  captureError(current, unmountError);
-                }
-              break;
-            case 5:
-              safelyDetachRef(current);
-              break;
-            case 4:
-              persistence && emptyPortalContainer(current);
-          }
-          if (null === node.child || (mutation && 4 === node.tag)) {
-            if (node === current$jscomp$0) break;
-            for (; null === node.sibling; ) {
-              if (null === node.return || node.return === current$jscomp$0)
-                break a;
-              node = node.return;
-            }
-            node.sibling.return = node.return;
-            node = node.sibling;
-          } else (node.child.return = node), (node = node.child);
-        }
-        current$jscomp$0.return = null;
-        current$jscomp$0.child = null;
-        current$jscomp$0.alternate &&
-          ((current$jscomp$0.alternate.child = null),
-          (current$jscomp$0.alternate.return = null));
-      },
-      commitWork: function(current, finishedWork) {
-        commitContainer(finishedWork);
-      },
-      commitLifeCycles: commitLifeCycles,
-      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitAttachRef: commitAttachRef,
-      commitDetachRef: commitDetachRef
-    };
+    else ref.current = null;
+}
+function commitWork(current, finishedWork) {
+  switch (finishedWork.tag) {
+    case 2:
+      break;
+    case 5:
+      break;
+    case 6:
+      break;
+    case 3:
+    case 4:
+      break;
+    default:
+      invariant(
+        !1,
+        "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+      );
   }
-  var commitMount = mutation.commitMount;
-  invariant(!1, "Mutating reconciler is disabled.");
 }
-function ReactFiberUnwindWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  recalculateCurrentTime,
-  markLegacyErrorBoundaryAsFailed,
-  isAlreadyFailedLegacyErrorBoundary,
-  onUncaughtError
-) {
-  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
-    expirationTime = createUpdate(expirationTime);
-    expirationTime.tag = 3;
-    expirationTime.payload = { element: null };
-    var error = errorInfo.value;
-    expirationTime.callback = function() {
-      onUncaughtError(error);
+function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+  expirationTime = createUpdate(expirationTime);
+  expirationTime.tag = 3;
+  expirationTime.payload = { element: null };
+  var error = errorInfo.value;
+  expirationTime.callback = function() {
+    onUncaughtError(error);
+    logError(fiber, errorInfo);
+  };
+  return expirationTime;
+}
+function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+  expirationTime = createUpdate(expirationTime);
+  expirationTime.tag = 3;
+  var inst = fiber.stateNode;
+  null !== inst &&
+    "function" === typeof inst.componentDidCatch &&
+    (expirationTime.callback = function() {
+      null === legacyErrorBoundariesThatAlreadyFailed
+        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([this]))
+        : legacyErrorBoundariesThatAlreadyFailed.add(this);
+      var error = errorInfo.value,
+        stack = errorInfo.stack;
       logError(fiber, errorInfo);
-    };
-    return expirationTime;
-  }
-  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
-    expirationTime = createUpdate(expirationTime);
-    expirationTime.tag = 3;
-    var inst = fiber.stateNode;
-    null !== inst &&
-      "function" === typeof inst.componentDidCatch &&
-      (expirationTime.callback = function() {
-        markLegacyErrorBoundaryAsFailed(this);
-        var error = errorInfo.value,
-          stack = errorInfo.stack;
-        logError(fiber, errorInfo);
-        this.componentDidCatch(error, {
-          componentStack: null !== stack ? stack : ""
-        });
+      this.componentDidCatch(error, {
+        componentStack: null !== stack ? stack : ""
       });
-    return expirationTime;
+    });
+  return expirationTime;
+}
+function unwindWork(workInProgress) {
+  switch (workInProgress.tag) {
+    case 2:
+      popContextProvider(workInProgress);
+      var effectTag = workInProgress.effectTag;
+      return effectTag & 1024
+        ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+          workInProgress)
+        : null;
+    case 3:
+      return (
+        popHostContainer(workInProgress),
+        popTopLevelContextObject(workInProgress),
+        (effectTag = workInProgress.effectTag),
+        effectTag & 1024
+          ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+            workInProgress)
+          : null
+      );
+    case 5:
+      return popHostContext(workInProgress), null;
+    case 16:
+      return (
+        (effectTag = workInProgress.effectTag),
+        effectTag & 1024
+          ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+            workInProgress)
+          : null
+      );
+    case 4:
+      return popHostContainer(workInProgress), null;
+    case 13:
+      return popProvider(workInProgress), null;
+    default:
+      return null;
   }
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
-  return {
-    throwException: function(
-      root,
-      returnFiber,
-      sourceFiber,
-      value,
-      renderIsExpired,
-      renderExpirationTime
+}
+var originalStartTimeMs = now$1(),
+  mostRecentCurrentTime = 2,
+  mostRecentCurrentTimeMs = originalStartTimeMs,
+  lastUniqueAsyncExpiration = 0,
+  expirationContext = 0,
+  isWorking = !1,
+  nextUnitOfWork = null,
+  nextRoot = null,
+  nextRenderExpirationTime = 0,
+  nextLatestTimeoutMs = -1,
+  nextRenderDidError = !1,
+  nextEffect = null,
+  isCommitting$1 = !1,
+  legacyErrorBoundariesThatAlreadyFailed = null;
+function resetStack() {
+  if (null !== nextUnitOfWork)
+    for (
+      var interruptedWork = nextUnitOfWork.return;
+      null !== interruptedWork;
+
     ) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      value = createCapturedValue(value, sourceFiber);
-      root = returnFiber;
-      do {
-        switch (root.tag) {
-          case 3:
-            root.effectTag |= 1024;
-            value = createRootErrorUpdate(root, value, renderExpirationTime);
-            enqueueCapturedUpdate(root, value, renderExpirationTime);
-            return;
-          case 2:
-            if (
-              ((returnFiber = value),
-              (sourceFiber = root.stateNode),
-              0 === (root.effectTag & 64) &&
-                null !== sourceFiber &&
-                "function" === typeof sourceFiber.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(sourceFiber))
-            ) {
-              root.effectTag |= 1024;
-              value = createClassErrorUpdate(
-                root,
-                returnFiber,
-                renderExpirationTime
-              );
-              enqueueCapturedUpdate(root, value, renderExpirationTime);
-              return;
-            }
-        }
-        root = root.return;
-      } while (null !== root);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 16:
-          return (
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
+      var interruptedWork$jscomp$0 = interruptedWork;
+      switch (interruptedWork$jscomp$0.tag) {
         case 2:
-          popLegacyContextProvider(interruptedWork);
+          popContextProvider(interruptedWork$jscomp$0);
           break;
         case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
+          popHostContainer(interruptedWork$jscomp$0);
+          popTopLevelContextObject(interruptedWork$jscomp$0);
           break;
         case 5:
-          popHostContext(interruptedWork);
+          popHostContext(interruptedWork$jscomp$0);
           break;
         case 4:
-          popHostContainer(interruptedWork);
+          popHostContainer(interruptedWork$jscomp$0);
           break;
         case 13:
-          popProvider(interruptedWork);
-      }
-    },
-    createRootErrorUpdate: createRootErrorUpdate,
-    createClassErrorUpdate: createClassErrorUpdate
-  };
-}
-var NO_CONTEXT = {};
-function ReactFiberHostContext(config, stack) {
-  function requiredContext(c) {
-    invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
-    );
-    return c;
-  }
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  config = stack.createCursor;
-  var push = stack.push,
-    pop = stack.pop,
-    contextStackCursor = config(NO_CONTEXT),
-    contextFiberStackCursor = config(NO_CONTEXT),
-    rootInstanceStackCursor = config(NO_CONTEXT);
-  return {
-    getHostContext: function() {
-      return requiredContext(contextStackCursor.current);
-    },
-    getRootHostContainer: function() {
-      return requiredContext(rootInstanceStackCursor.current);
-    },
-    popHostContainer: function(fiber) {
-      pop(contextStackCursor, fiber);
-      pop(contextFiberStackCursor, fiber);
-      pop(rootInstanceStackCursor, fiber);
-    },
-    popHostContext: function(fiber) {
-      contextFiberStackCursor.current === fiber &&
-        (pop(contextStackCursor, fiber), pop(contextFiberStackCursor, fiber));
-    },
-    pushHostContainer: function(fiber, nextRootInstance) {
-      push(rootInstanceStackCursor, nextRootInstance, fiber);
-      push(contextFiberStackCursor, fiber, fiber);
-      push(contextStackCursor, NO_CONTEXT, fiber);
-      nextRootInstance = getRootHostContext(nextRootInstance);
-      pop(contextStackCursor, fiber);
-      push(contextStackCursor, nextRootInstance, fiber);
-    },
-    pushHostContext: function(fiber) {
-      var rootInstance = requiredContext(rootInstanceStackCursor.current),
-        context = requiredContext(contextStackCursor.current);
-      rootInstance = getChildHostContext(context, fiber.type, rootInstance);
-      context !== rootInstance &&
-        (push(contextFiberStackCursor, fiber, fiber),
-        push(contextStackCursor, rootInstance, fiber));
-    }
-  };
-}
-function ReactFiberHydrationContext(config) {
-  function deleteHydratableInstance(returnFiber, instance) {
-    var fiber = new FiberNode(5, null, null, 0);
-    fiber.type = "DELETED";
-    fiber.stateNode = instance;
-    fiber.return = returnFiber;
-    fiber.effectTag = 8;
-    null !== returnFiber.lastEffect
-      ? ((returnFiber.lastEffect.nextEffect = fiber),
-        (returnFiber.lastEffect = fiber))
-      : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
-  }
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case 5:
-        return (
-          (nextInstance = canHydrateInstance(
-            nextInstance,
-            fiber.type,
-            fiber.pendingProps
-          )),
-          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
-        );
-      case 6:
-        return (
-          (nextInstance = canHydrateTextInstance(
-            nextInstance,
-            fiber.pendingProps
-          )),
-          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
-        );
-      default:
-        return !1;
-    }
-  }
-  function popToNextHostParent(fiber) {
-    for (
-      fiber = fiber.return;
-      null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
-
-    )
-      fiber = fiber.return;
-    hydrationParentFiber = fiber;
-  }
-  var shouldSetTextContent = config.shouldSetTextContent;
-  config = config.hydration;
-  if (!config)
-    return {
-      enterHydrationState: function() {
-        return !1;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          !1,
-          "Expected prepareToHydrateHostInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
-        invariant(
-          !1,
-          "Expected prepareToHydrateHostTextInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      popHydrationState: function() {
-        return !1;
-      }
-    };
-  var canHydrateInstance = config.canHydrateInstance,
-    canHydrateTextInstance = config.canHydrateTextInstance,
-    getNextHydratableSibling = config.getNextHydratableSibling,
-    getFirstHydratableChild = config.getFirstHydratableChild,
-    hydrateInstance = config.hydrateInstance,
-    hydrateTextInstance = config.hydrateTextInstance,
-    hydrationParentFiber = null,
-    nextHydratableInstance = null,
-    isHydrating = !1;
-  return {
-    enterHydrationState: function(fiber) {
-      nextHydratableInstance = getFirstHydratableChild(
-        fiber.stateNode.containerInfo
-      );
-      hydrationParentFiber = fiber;
-      return (isHydrating = !0);
-    },
-    resetHydrationState: function() {
-      nextHydratableInstance = hydrationParentFiber = null;
-      isHydrating = !1;
-    },
-    tryToClaimNextHydratableInstance: function(fiber) {
-      if (isHydrating) {
-        var nextInstance = nextHydratableInstance;
-        if (nextInstance) {
-          if (!tryHydrate(fiber, nextInstance)) {
-            nextInstance = getNextHydratableSibling(nextInstance);
-            if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-              fiber.effectTag |= 2;
-              isHydrating = !1;
-              hydrationParentFiber = fiber;
-              return;
-            }
-            deleteHydratableInstance(
-              hydrationParentFiber,
-              nextHydratableInstance
-            );
-          }
-          hydrationParentFiber = fiber;
-          nextHydratableInstance = getFirstHydratableChild(nextInstance);
-        } else
-          (fiber.effectTag |= 2),
-            (isHydrating = !1),
-            (hydrationParentFiber = fiber);
+          popProvider(interruptedWork$jscomp$0);
       }
-    },
-    prepareToHydrateHostInstance: function(
-      fiber,
-      rootContainerInstance,
-      hostContext
-    ) {
-      rootContainerInstance = hydrateInstance(
-        fiber.stateNode,
-        fiber.type,
-        fiber.memoizedProps,
-        rootContainerInstance,
-        hostContext,
-        fiber
-      );
-      fiber.updateQueue = rootContainerInstance;
-      return null !== rootContainerInstance ? !0 : !1;
-    },
-    prepareToHydrateHostTextInstance: function(fiber) {
-      return hydrateTextInstance(fiber.stateNode, fiber.memoizedProps, fiber);
-    },
-    popHydrationState: function(fiber) {
-      if (fiber !== hydrationParentFiber) return !1;
-      if (!isHydrating)
-        return popToNextHostParent(fiber), (isHydrating = !0), !1;
-      var type = fiber.type;
-      if (
-        5 !== fiber.tag ||
-        ("head" !== type &&
-          "body" !== type &&
-          !shouldSetTextContent(type, fiber.memoizedProps))
-      )
-        for (type = nextHydratableInstance; type; )
-          deleteHydratableInstance(fiber, type),
-            (type = getNextHydratableSibling(type));
-      popToNextHostParent(fiber);
-      nextHydratableInstance = hydrationParentFiber
-        ? getNextHydratableSibling(fiber.stateNode)
-        : null;
-      return !0;
+      interruptedWork = interruptedWork.return;
     }
-  };
+  nextRoot = null;
+  nextRenderExpirationTime = 0;
+  nextLatestTimeoutMs = -1;
+  nextRenderDidError = !1;
+  nextUnitOfWork = null;
 }
-function ReactFiberLegacyContext(stack) {
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    workInProgress = workInProgress.stateNode;
-    workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    workInProgress.__reactInternalMemoizedMaskedChildContext = maskedContext;
-  }
-  function isContextProvider(fiber) {
-    return 2 === fiber.tag && null != fiber.type.childContextTypes;
-  }
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode,
-      childContextTypes = fiber.type.childContextTypes;
-    if ("function" !== typeof instance.getChildContext) return parentContext;
-    instance = instance.getChildContext();
-    for (var contextKey in instance)
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
+function completeUnitOfWork(workInProgress$jscomp$0) {
+  for (;;) {
+    var current = workInProgress$jscomp$0.alternate,
+      returnFiber = workInProgress$jscomp$0.return,
+      siblingFiber = workInProgress$jscomp$0.sibling;
+    if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
+      current = completeWork(
+        current,
+        workInProgress$jscomp$0,
+        nextRenderExpirationTime
       );
-    return Object.assign({}, parentContext, instance);
-  }
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop,
-    contextStackCursor = createCursor(emptyObject),
-    didPerformWorkStackCursor = createCursor(!1),
-    previousContext = emptyObject;
-  return {
-    getUnmaskedContext: function(workInProgress) {
-      return isContextProvider(workInProgress)
-        ? previousContext
-        : contextStackCursor.current;
-    },
-    cacheContext: cacheContext,
-    getMaskedContext: function(workInProgress, unmaskedContext) {
-      var contextTypes = workInProgress.type.contextTypes;
-      if (!contextTypes) return emptyObject;
-      var instance = workInProgress.stateNode;
+      var workInProgress = workInProgress$jscomp$0;
       if (
-        instance &&
-        instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-      )
-        return instance.__reactInternalMemoizedMaskedChildContext;
-      var context = {},
-        key;
-      for (key in contextTypes) context[key] = unmaskedContext[key];
-      instance && cacheContext(workInProgress, unmaskedContext, context);
-      return context;
-    },
-    hasContextChanged: function() {
-      return didPerformWorkStackCursor.current;
-    },
-    isContextConsumer: function(fiber) {
-      return 2 === fiber.tag && null != fiber.type.contextTypes;
-    },
-    isContextProvider: isContextProvider,
-    popContextProvider: function(fiber) {
-      isContextProvider(fiber) &&
-        (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
-    },
-    popTopLevelContextObject: function(fiber) {
-      pop(didPerformWorkStackCursor, fiber);
-      pop(contextStackCursor, fiber);
-    },
-    pushTopLevelContextObject: function(fiber, context, didChange) {
-      invariant(
-        null == contextStackCursor.cursor,
-        "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
-      );
-      push(contextStackCursor, context, fiber);
-      push(didPerformWorkStackCursor, didChange, fiber);
-    },
-    processChildContext: processChildContext,
-    pushContextProvider: function(workInProgress) {
-      if (!isContextProvider(workInProgress)) return !1;
-      var instance = workInProgress.stateNode;
-      instance =
-        (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-        emptyObject;
-      previousContext = contextStackCursor.current;
-      push(contextStackCursor, instance, workInProgress);
-      push(
-        didPerformWorkStackCursor,
-        didPerformWorkStackCursor.current,
-        workInProgress
-      );
-      return !0;
-    },
-    invalidateContextProvider: function(workInProgress, didChange) {
-      var instance = workInProgress.stateNode;
-      invariant(
-        instance,
-        "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
-      );
-      if (didChange) {
-        var mergedContext = processChildContext(
-          workInProgress,
-          previousContext
-        );
-        instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-        pop(didPerformWorkStackCursor, workInProgress);
-        pop(contextStackCursor, workInProgress);
-        push(contextStackCursor, mergedContext, workInProgress);
-      } else pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    },
-    findCurrentUnmaskedContext: function(fiber) {
-      for (
-        invariant(
-          2 === isFiberMountedImpl(fiber) && 2 === fiber.tag,
-          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
-        );
-        3 !== fiber.tag;
-
+        1073741823 === nextRenderExpirationTime ||
+        1073741823 !== workInProgress.expirationTime
       ) {
-        if (isContextProvider(fiber))
-          return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber.return;
-        invariant(
-          fiber,
-          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
-        );
-      }
-      return fiber.stateNode.context;
-    }
-  };
-}
-function ReactFiberNewContext(stack, isPrimaryRenderer) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop,
-    providerCursor = createCursor(null),
-    valueCursor = createCursor(null),
-    changedBitsCursor = createCursor(0);
-  return {
-    pushProvider: function(providerFiber) {
-      var context = providerFiber.type._context;
-      isPrimaryRenderer
-        ? (push(changedBitsCursor, context._changedBits, providerFiber),
-          push(valueCursor, context._currentValue, providerFiber),
-          push(providerCursor, providerFiber, providerFiber),
-          (context._currentValue = providerFiber.pendingProps.value),
-          (context._changedBits = providerFiber.stateNode))
-        : (push(changedBitsCursor, context._changedBits2, providerFiber),
-          push(valueCursor, context._currentValue2, providerFiber),
-          push(providerCursor, providerFiber, providerFiber),
-          (context._currentValue2 = providerFiber.pendingProps.value),
-          (context._changedBits2 = providerFiber.stateNode));
-    },
-    popProvider: function(providerFiber) {
-      var changedBits = changedBitsCursor.current,
-        currentValue = valueCursor.current;
-      pop(providerCursor, providerFiber);
-      pop(valueCursor, providerFiber);
-      pop(changedBitsCursor, providerFiber);
-      providerFiber = providerFiber.type._context;
-      isPrimaryRenderer
-        ? ((providerFiber._currentValue = currentValue),
-          (providerFiber._changedBits = changedBits))
-        : ((providerFiber._currentValue2 = currentValue),
-          (providerFiber._changedBits2 = changedBits));
-    },
-    getContextCurrentValue: function(context) {
-      return isPrimaryRenderer ? context._currentValue : context._currentValue2;
-    },
-    getContextChangedBits: function(context) {
-      return isPrimaryRenderer ? context._changedBits : context._changedBits2;
-    }
-  };
-}
-function ReactFiberStack() {
-  var valueStack = [],
-    index = -1;
-  return {
-    createCursor: function(defaultValue) {
-      return { current: defaultValue };
-    },
-    isEmpty: function() {
-      return -1 === index;
-    },
-    pop: function(cursor) {
-      0 > index ||
-        ((cursor.current = valueStack[index]),
-        (valueStack[index] = null),
-        index--);
-    },
-    push: function(cursor, value) {
-      index++;
-      valueStack[index] = cursor.current;
-      cursor.current = value;
-    },
-    checkThatStackIsEmpty: function() {},
-    resetStackAfterFatalErrorInDev: function() {}
-  };
-}
-function ReactFiberScheduler(config) {
-  function resetStack() {
-    if (null !== nextUnitOfWork)
-      for (
-        var interruptedWork = nextUnitOfWork.return;
-        null !== interruptedWork;
-
-      )
-        unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork.return);
-    nextRoot = null;
-    nextRenderExpirationTime = 0;
-    nextLatestTimeoutMs = -1;
-    nextRenderIsExpired = !1;
-    nextUnitOfWork = null;
-    isRootReadyForCommit = !1;
-  }
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      null !== legacyErrorBoundariesThatAlreadyFailed &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
-  }
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    null === legacyErrorBoundariesThatAlreadyFailed
-      ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-      : legacyErrorBoundariesThatAlreadyFailed.add(instance);
-  }
-  function completeUnitOfWork(workInProgress$jscomp$0) {
-    for (;;) {
-      var current = workInProgress$jscomp$0.alternate,
-        returnFiber = workInProgress$jscomp$0.return,
-        siblingFiber = workInProgress$jscomp$0.sibling;
-      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
-        current = completeWork(
-          current,
-          workInProgress$jscomp$0,
-          nextRenderExpirationTime
-        );
-        var workInProgress = workInProgress$jscomp$0;
-        if (
-          1073741823 === nextRenderExpirationTime ||
-          1073741823 !== workInProgress.expirationTime
-        ) {
-          var newExpirationTime = 0;
-          switch (workInProgress.tag) {
-            case 3:
-            case 2:
-              var updateQueue = workInProgress.updateQueue;
-              null !== updateQueue &&
-                (newExpirationTime = updateQueue.expirationTime);
-          }
-          for (updateQueue = workInProgress.child; null !== updateQueue; )
-            0 !== updateQueue.expirationTime &&
-              (0 === newExpirationTime ||
-                newExpirationTime > updateQueue.expirationTime) &&
-              (newExpirationTime = updateQueue.expirationTime),
-              (updateQueue = updateQueue.sibling);
-          workInProgress.expirationTime = newExpirationTime;
-        }
-        if (null !== current) return current;
-        null !== returnFiber &&
-          0 === (returnFiber.effectTag & 512) &&
-          (null === returnFiber.firstEffect &&
-            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
-          null !== workInProgress$jscomp$0.lastEffect &&
-            (null !== returnFiber.lastEffect &&
-              (returnFiber.lastEffect.nextEffect =
-                workInProgress$jscomp$0.firstEffect),
-            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
-          1 < workInProgress$jscomp$0.effectTag &&
-            (null !== returnFiber.lastEffect
-              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
-              : (returnFiber.firstEffect = workInProgress$jscomp$0),
-            (returnFiber.lastEffect = workInProgress$jscomp$0)));
-        if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
-        else {
-          isRootReadyForCommit = !0;
-          break;
+        var newExpirationTime = 0;
+        switch (workInProgress.tag) {
+          case 3:
+          case 2:
+            var updateQueue = workInProgress.updateQueue;
+            null !== updateQueue &&
+              (newExpirationTime = updateQueue.expirationTime);
         }
-      } else {
-        workInProgress$jscomp$0 = unwindWork(
-          workInProgress$jscomp$0,
-          nextRenderIsExpired,
-          nextRenderExpirationTime
-        );
-        if (null !== workInProgress$jscomp$0)
-          return (
-            (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
-          );
-        null !== returnFiber &&
-          ((returnFiber.firstEffect = returnFiber.lastEffect = null),
-          (returnFiber.effectTag |= 512));
-        if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
-        else break;
+        for (updateQueue = workInProgress.child; null !== updateQueue; )
+          0 !== updateQueue.expirationTime &&
+            (0 === newExpirationTime ||
+              newExpirationTime > updateQueue.expirationTime) &&
+            (newExpirationTime = updateQueue.expirationTime),
+            (updateQueue = updateQueue.sibling);
+        workInProgress.expirationTime = newExpirationTime;
       }
+      if (null !== current) return current;
+      null !== returnFiber &&
+        0 === (returnFiber.effectTag & 512) &&
+        (null === returnFiber.firstEffect &&
+          (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
+        null !== workInProgress$jscomp$0.lastEffect &&
+          (null !== returnFiber.lastEffect &&
+            (returnFiber.lastEffect.nextEffect =
+              workInProgress$jscomp$0.firstEffect),
+          (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
+        1 < workInProgress$jscomp$0.effectTag &&
+          (null !== returnFiber.lastEffect
+            ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
+            : (returnFiber.firstEffect = workInProgress$jscomp$0),
+          (returnFiber.lastEffect = workInProgress$jscomp$0)));
+    } else {
+      workInProgress$jscomp$0 = unwindWork(
+        workInProgress$jscomp$0,
+        nextRenderExpirationTime
+      );
+      if (null !== workInProgress$jscomp$0)
+        return (
+          (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
+        );
+      null !== returnFiber &&
+        ((returnFiber.firstEffect = returnFiber.lastEffect = null),
+        (returnFiber.effectTag |= 512));
     }
-    return null;
+    if (null !== siblingFiber) return siblingFiber;
+    if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+    else break;
   }
-  function performUnitOfWork(workInProgress) {
-    var next = beginWork(
-      workInProgress.alternate,
-      workInProgress,
-      nextRenderExpirationTime
-    );
-    null === next && (next = completeUnitOfWork(workInProgress));
-    ReactCurrentOwner.current = null;
-    return next;
-  }
-  function renderRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
-    );
-    isWorking = !0;
-    if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      null === nextUnitOfWork
-    )
-      resetStack(),
-        (nextRoot = root),
-        (nextRenderExpirationTime = expirationTime),
-        (nextLatestTimeoutMs = -1),
-        (nextUnitOfWork = createWorkInProgress(
-          nextRoot.current,
-          null,
-          nextRenderExpirationTime
-        )),
-        (root.pendingCommitExpirationTime = 0);
-    var didFatal = !1;
-    nextRenderIsExpired =
-      !isAsync || nextRenderExpirationTime <= mostRecentCurrentTime;
-    do {
-      try {
-        if (isAsync)
-          for (; null !== nextUnitOfWork && !shouldYield(); )
-            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-        else
-          for (; null !== nextUnitOfWork; )
-            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      } catch (thrownValue) {
-        if (null === nextUnitOfWork)
-          (didFatal = !0), onUncaughtError(thrownValue);
-        else {
-          invariant(
-            null !== nextUnitOfWork,
-            "Failed to replay rendering after an error. This is likely caused by a bug in React. Please file an issue with a reproducing case to help us find it."
-          );
-          isAsync = nextUnitOfWork;
-          var returnFiber = isAsync.return;
-          if (null === returnFiber) {
-            didFatal = !0;
-            onUncaughtError(thrownValue);
-            break;
+  return null;
+}
+function performUnitOfWork(workInProgress) {
+  var next = beginWork(
+    workInProgress.alternate,
+    workInProgress,
+    nextRenderExpirationTime
+  );
+  null === next && (next = completeUnitOfWork(workInProgress));
+  ReactCurrentOwner.current = null;
+  return next;
+}
+function renderRoot(root$jscomp$0, isYieldy) {
+  invariant(
+    !isWorking,
+    "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+  );
+  isWorking = !0;
+  var expirationTime = root$jscomp$0.nextExpirationTimeToWorkOn;
+  if (
+    expirationTime !== nextRenderExpirationTime ||
+    root$jscomp$0 !== nextRoot ||
+    null === nextUnitOfWork
+  )
+    resetStack(),
+      (nextRoot = root$jscomp$0),
+      (nextRenderExpirationTime = expirationTime),
+      (nextLatestTimeoutMs = -1),
+      (nextRenderDidError = !1),
+      (nextUnitOfWork = createWorkInProgress(
+        nextRoot.current,
+        null,
+        nextRenderExpirationTime
+      )),
+      (root$jscomp$0.pendingCommitExpirationTime = 0);
+  var didFatal = !1;
+  do {
+    try {
+      if (isYieldy)
+        for (; null !== nextUnitOfWork && !shouldYield(); )
+          nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      else
+        for (; null !== nextUnitOfWork; )
+          nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+    } catch (thrownValue) {
+      if (null === nextUnitOfWork)
+        (didFatal = !0), onUncaughtError(thrownValue);
+      else {
+        invariant(
+          null !== nextUnitOfWork,
+          "Failed to replay rendering after an error. This is likely caused by a bug in React. Please file an issue with a reproducing case to help us find it."
+        );
+        isYieldy = nextUnitOfWork;
+        var returnFiber = isYieldy.return;
+        if (null === returnFiber) {
+          didFatal = !0;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        a: {
+          var root = root$jscomp$0,
+            returnFiber$jscomp$0 = returnFiber,
+            sourceFiber = isYieldy,
+            value = thrownValue;
+          returnFiber = nextRenderExpirationTime;
+          sourceFiber.effectTag |= 512;
+          sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+          nextRenderDidError = !0;
+          if (
+            (root.didError || 1 === returnFiber) &&
+            (returnFiber === root.latestPendingTime ||
+              returnFiber === root.latestSuspendedTime)
+          ) {
+            value = createCapturedValue(value, sourceFiber);
+            root = returnFiber$jscomp$0;
+            do {
+              switch (root.tag) {
+                case 3:
+                  root.effectTag |= 1024;
+                  value = createRootErrorUpdate(root, value, returnFiber);
+                  enqueueCapturedUpdate(root, value, returnFiber);
+                  break a;
+                case 2:
+                  if (
+                    ((returnFiber$jscomp$0 = value),
+                    (sourceFiber = root.stateNode),
+                    0 === (root.effectTag & 64) &&
+                      null !== sourceFiber &&
+                      "function" === typeof sourceFiber.componentDidCatch &&
+                      (null === legacyErrorBoundariesThatAlreadyFailed ||
+                        !legacyErrorBoundariesThatAlreadyFailed.has(
+                          sourceFiber
+                        )))
+                  ) {
+                    root.effectTag |= 1024;
+                    value = createClassErrorUpdate(
+                      root,
+                      returnFiber$jscomp$0,
+                      returnFiber
+                    );
+                    enqueueCapturedUpdate(root, value, returnFiber);
+                    break a;
+                  }
+              }
+              root = root.return;
+            } while (null !== root);
           }
-          throwException(
-            root,
-            returnFiber,
-            isAsync,
-            thrownValue,
-            nextRenderIsExpired,
-            nextRenderExpirationTime,
-            mostRecentCurrentTimeMs
-          );
-          nextUnitOfWork = completeUnitOfWork(isAsync);
         }
+        nextUnitOfWork = completeUnitOfWork(isYieldy);
       }
-      break;
-    } while (1);
-    isWorking = !1;
-    if (didFatal) return null;
-    if (null === nextUnitOfWork) {
-      if (isRootReadyForCommit)
-        return (
-          (root.pendingCommitExpirationTime = expirationTime),
-          root.current.alternate
-        );
-      invariant(
-        !nextRenderIsExpired,
-        "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
-      );
-      0 <= nextLatestTimeoutMs &&
-        setTimeout(function() {
-          retrySuspendedRoot(root, expirationTime);
-        }, nextLatestTimeoutMs);
-      onBlock(root.current.expirationTime);
     }
-    return null;
-  }
-  function onCommitPhaseError(fiber, error) {
-    var JSCompiler_inline_result;
-    a: {
-      invariant(
-        !isWorking || isCommitting,
-        "dispatch: Cannot dispatch during the render phase."
-      );
-      for (
-        JSCompiler_inline_result = fiber.return;
-        null !== JSCompiler_inline_result;
+    break;
+  } while (1);
+  isWorking = !1;
+  didFatal
+    ? (root$jscomp$0.finishedWork = null)
+    : null === nextUnitOfWork
+      ? ((didFatal = root$jscomp$0.current.alternate),
+        invariant(
+          null !== didFatal,
+          "Finished root should have a work-in-progress. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        0 === (didFatal.effectTag & 512)
+          ? ((root$jscomp$0.pendingCommitExpirationTime = expirationTime),
+            (root$jscomp$0.finishedWork = didFatal))
+          : (!nextRenderDidError ||
+            (expirationTime !== root$jscomp$0.latestPendingTime &&
+              expirationTime !== root$jscomp$0.latestSuspendedTime)
+              ? ((didFatal = root$jscomp$0.earliestPendingTime),
+                (isYieldy = root$jscomp$0.latestPendingTime),
+                didFatal === expirationTime
+                  ? (root$jscomp$0.earliestPendingTime =
+                      isYieldy === expirationTime
+                        ? (root$jscomp$0.latestPendingTime = 0)
+                        : isYieldy)
+                  : isYieldy === expirationTime &&
+                    (root$jscomp$0.latestPendingTime = didFatal),
+                (didFatal = root$jscomp$0.latestSuspendedTime),
+                didFatal === expirationTime &&
+                  (root$jscomp$0.latestPingedTime = 0),
+                (isYieldy = root$jscomp$0.earliestSuspendedTime),
+                0 === isYieldy
+                  ? (root$jscomp$0.earliestSuspendedTime = root$jscomp$0.latestSuspendedTime = expirationTime)
+                  : isYieldy > expirationTime
+                    ? (root$jscomp$0.earliestSuspendedTime = expirationTime)
+                    : didFatal < expirationTime &&
+                      (root$jscomp$0.latestSuspendedTime = expirationTime))
+              : (root$jscomp$0.didError = !0),
+            findNextPendingPriorityLevel(root$jscomp$0),
+            onSuspend(
+              root$jscomp$0,
+              expirationTime,
+              root$jscomp$0.expirationTime,
+              nextLatestTimeoutMs
+            )))
+      : (root$jscomp$0.finishedWork = null);
+}
+function captureCommitPhaseError(fiber, error) {
+  var JSCompiler_inline_result;
+  a: {
+    invariant(
+      !isWorking || isCommitting$1,
+      "dispatch: Cannot dispatch during the render phase."
+    );
+    for (
+      JSCompiler_inline_result = fiber.return;
+      null !== JSCompiler_inline_result;
 
-      ) {
-        switch (JSCompiler_inline_result.tag) {
-          case 2:
-            var instance = JSCompiler_inline_result.stateNode;
-            if (
-              "function" ===
-                typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
-              ("function" === typeof instance.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(instance))
-            ) {
-              fiber = createCapturedValue(error, fiber);
-              fiber = createClassErrorUpdate(
-                JSCompiler_inline_result,
-                fiber,
-                1
-              );
-              enqueueUpdate(JSCompiler_inline_result, fiber, 1);
-              scheduleWork(JSCompiler_inline_result, 1);
-              JSCompiler_inline_result = void 0;
-              break a;
-            }
-            break;
-          case 3:
+    ) {
+      switch (JSCompiler_inline_result.tag) {
+        case 2:
+          var instance = JSCompiler_inline_result.stateNode;
+          if (
+            "function" ===
+              typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
+            ("function" === typeof instance.componentDidCatch &&
+              (null === legacyErrorBoundariesThatAlreadyFailed ||
+                !legacyErrorBoundariesThatAlreadyFailed.has(instance)))
+          ) {
             fiber = createCapturedValue(error, fiber);
-            fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+            fiber = createClassErrorUpdate(JSCompiler_inline_result, fiber, 1);
             enqueueUpdate(JSCompiler_inline_result, fiber, 1);
             scheduleWork(JSCompiler_inline_result, 1);
             JSCompiler_inline_result = void 0;
             break a;
-        }
-        JSCompiler_inline_result = JSCompiler_inline_result.return;
+          }
+          break;
+        case 3:
+          fiber = createCapturedValue(error, fiber);
+          fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+          enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+          scheduleWork(JSCompiler_inline_result, 1);
+          JSCompiler_inline_result = void 0;
+          break a;
       }
-      3 === fiber.tag &&
-        ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
-        (JSCompiler_inline_result = createRootErrorUpdate(
-          fiber,
-          JSCompiler_inline_result,
-          1
-        )),
-        enqueueUpdate(fiber, JSCompiler_inline_result, 1),
-        scheduleWork(fiber, 1));
-      JSCompiler_inline_result = void 0;
-    }
-    return JSCompiler_inline_result;
-  }
-  function computeExpirationForFiber(currentTime, fiber) {
-    currentTime =
-      0 !== expirationContext
-        ? expirationContext
-        : isWorking
-          ? isCommitting ? 1 : nextRenderExpirationTime
-          : fiber.mode & 1
-            ? isBatchingInteractiveUpdates
-              ? 2 + 10 * ((((currentTime - 2 + 15) / 10) | 0) + 1)
-              : 2 + 25 * ((((currentTime - 2 + 500) / 25) | 0) + 1)
-            : 1;
-    isBatchingInteractiveUpdates &&
-      (0 === lowestPendingInteractiveExpirationTime ||
-        currentTime > lowestPendingInteractiveExpirationTime) &&
-      (lowestPendingInteractiveExpirationTime = currentTime);
-    return currentTime;
-  }
-  function retrySuspendedRoot(root) {
-    var retryTime = root.current.expirationTime;
-    0 !== retryTime &&
-      (0 === root.remainingExpirationTime ||
-        root.remainingExpirationTime < retryTime) &&
-      requestWork(root, retryTime);
-  }
-  function scheduleWork(fiber, expirationTime) {
-    for (; null !== fiber; ) {
-      if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
-        fiber.expirationTime = expirationTime;
-      null !== fiber.alternate &&
-        (0 === fiber.alternate.expirationTime ||
-          fiber.alternate.expirationTime > expirationTime) &&
-        (fiber.alternate.expirationTime = expirationTime);
-      if (null === fiber.return)
-        if (3 === fiber.tag) {
-          var root = fiber.stateNode;
-          !isWorking &&
-            0 !== nextRenderExpirationTime &&
-            expirationTime < nextRenderExpirationTime &&
-            resetStack();
-          var nextExpirationTimeToWorkOn = root.current.expirationTime;
-          (isWorking && !isCommitting && nextRoot === root) ||
-            requestWork(root, nextExpirationTimeToWorkOn);
-          nestedUpdateCount > NESTED_UPDATE_LIMIT &&
-            invariant(
-              !1,
-              "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
-            );
-        } else break;
-      fiber = fiber.return;
+      JSCompiler_inline_result = JSCompiler_inline_result.return;
     }
+    3 === fiber.tag &&
+      ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
+      (JSCompiler_inline_result = createRootErrorUpdate(
+        fiber,
+        JSCompiler_inline_result,
+        1
+      )),
+      enqueueUpdate(fiber, JSCompiler_inline_result, 1),
+      scheduleWork(fiber, 1));
+    JSCompiler_inline_result = void 0;
   }
-  function recalculateCurrentTime() {
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
+  return JSCompiler_inline_result;
+}
+function computeExpirationForFiber(currentTime, fiber) {
+  currentTime =
+    0 !== expirationContext
+      ? expirationContext
+      : isWorking
+        ? isCommitting$1 ? 1 : nextRenderExpirationTime
+        : fiber.mode & 1
+          ? isBatchingInteractiveUpdates
+            ? 2 + 10 * ((((currentTime - 2 + 15) / 10) | 0) + 1)
+            : 2 + 25 * ((((currentTime - 2 + 500) / 25) | 0) + 1)
+          : 1;
+  isBatchingInteractiveUpdates &&
+    (0 === lowestPendingInteractiveExpirationTime ||
+      currentTime > lowestPendingInteractiveExpirationTime) &&
+    (lowestPendingInteractiveExpirationTime = currentTime);
+  return currentTime;
+}
+function scheduleWork(fiber, expirationTime) {
+  for (; null !== fiber; ) {
+    if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
+      fiber.expirationTime = expirationTime;
+    null !== fiber.alternate &&
+      (0 === fiber.alternate.expirationTime ||
+        fiber.alternate.expirationTime > expirationTime) &&
+      (fiber.alternate.expirationTime = expirationTime);
+    if (null === fiber.return)
+      if (3 === fiber.tag) {
+        var root = fiber.stateNode;
+        !isWorking &&
+          0 !== nextRenderExpirationTime &&
+          expirationTime < nextRenderExpirationTime &&
+          resetStack();
+        markPendingPriorityLevel(root, expirationTime);
+        (isWorking && !isCommitting$1 && nextRoot === root) ||
+          requestWork(root, root.expirationTime);
+        nestedUpdateCount > NESTED_UPDATE_LIMIT &&
+          invariant(
+            !1,
+            "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
+          );
+      } else break;
+    fiber = fiber.return;
   }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = 1;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
+}
+function recalculateCurrentTime() {
+  mostRecentCurrentTimeMs = now$1() - originalStartTimeMs;
+  return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
+}
+function syncUpdates(fn, a, b, c, d) {
+  var previousExpirationContext = expirationContext;
+  expirationContext = 1;
+  try {
+    return fn(a, b, c, d);
+  } finally {
+    expirationContext = previousExpirationContext;
   }
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (0 !== callbackExpirationTime) {
-      if (expirationTime > callbackExpirationTime) return;
-      cancelDeferredCallback(callbackID);
+}
+var firstScheduledRoot = null,
+  lastScheduledRoot = null,
+  callbackExpirationTime = 0,
+  callbackID = void 0,
+  isRendering = !1,
+  nextFlushedRoot = null,
+  nextFlushedExpirationTime = 0,
+  lowestPendingInteractiveExpirationTime = 0,
+  deadlineDidExpire = !1,
+  hasUnhandledError = !1,
+  unhandledError = null,
+  deadline = null,
+  isBatchingUpdates = !1,
+  isUnbatchingUpdates = !1,
+  isBatchingInteractiveUpdates = !1,
+  completedBatches = null,
+  NESTED_UPDATE_LIMIT = 1e3,
+  nestedUpdateCount = 0,
+  timeHeuristicForUnitOfWork = 1;
+function scheduleCallbackWithExpirationTime(expirationTime) {
+  if (0 !== callbackExpirationTime) {
+    if (expirationTime > callbackExpirationTime) return;
+    if (null !== callbackID) {
+      var callbackID$jscomp$0 = callbackID;
+      scheduledCallback = null;
+      clearTimeout(callbackID$jscomp$0);
     }
-    var currentMs = now() - originalStartTimeMs;
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: 10 * (expirationTime - 2) - currentMs
-    });
   }
-  function requestWork(root, expirationTime) {
-    if (null === root.nextScheduledRoot)
-      (root.remainingExpirationTime = expirationTime),
-        null === lastScheduledRoot
-          ? ((firstScheduledRoot = lastScheduledRoot = root),
-            (root.nextScheduledRoot = root))
-          : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
-            (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
-    else {
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        expirationTime < remainingExpirationTime
-      )
-        root.remainingExpirationTime = expirationTime;
-    }
-    isRendering ||
-      (isBatchingUpdates
-        ? isUnbatchingUpdates &&
-          ((nextFlushedRoot = root),
-          (nextFlushedExpirationTime = 1),
-          performWorkOnRoot(root, 1, !1))
-        : 1 === expirationTime
-          ? performSyncWork()
-          : scheduleCallbackWithExpiration(expirationTime));
+  callbackExpirationTime = expirationTime;
+  now$1();
+  scheduledCallback = performAsyncWork;
+  callbackID = setTimeout(setTimeoutCallback, 1);
+}
+function onSuspend(root, suspendedExpirationTime, expirationTime, timeoutMs) {
+  0 <= timeoutMs &&
+    setTimeout(function() {
+      var latestSuspendedTime = root.latestSuspendedTime;
+      0 !== latestSuspendedTime &&
+        latestSuspendedTime <= suspendedExpirationTime &&
+        ((latestSuspendedTime = root.latestPingedTime),
+        0 === latestSuspendedTime ||
+          latestSuspendedTime < suspendedExpirationTime) &&
+        (root.latestPingedTime = suspendedExpirationTime);
+      findNextPendingPriorityLevel(root);
+      latestSuspendedTime = root.expirationTime;
+      0 !== latestSuspendedTime && requestWork(root, latestSuspendedTime);
+    }, timeoutMs);
+  root.expirationTime = expirationTime;
+}
+function requestWork(root, expirationTime) {
+  if (null === root.nextScheduledRoot)
+    (root.expirationTime = expirationTime),
+      null === lastScheduledRoot
+        ? ((firstScheduledRoot = lastScheduledRoot = root),
+          (root.nextScheduledRoot = root))
+        : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
+          (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
+  else {
+    var remainingExpirationTime = root.expirationTime;
+    if (
+      0 === remainingExpirationTime ||
+      expirationTime < remainingExpirationTime
+    )
+      root.expirationTime = expirationTime;
   }
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = 0,
-      highestPriorityRoot = null;
-    if (null !== lastScheduledRoot)
-      for (
-        var previousScheduledRoot = lastScheduledRoot,
-          root = firstScheduledRoot;
-        null !== root;
+  isRendering ||
+    (isBatchingUpdates
+      ? isUnbatchingUpdates &&
+        ((nextFlushedRoot = root),
+        (nextFlushedExpirationTime = 1),
+        performWorkOnRoot(root, 1, !1))
+      : 1 === expirationTime
+        ? performWork(1, null)
+        : scheduleCallbackWithExpirationTime(expirationTime));
+}
+function findHighestPriorityRoot() {
+  var highestPriorityWork = 0,
+    highestPriorityRoot = null;
+  if (null !== lastScheduledRoot)
+    for (
+      var previousScheduledRoot = lastScheduledRoot, root = firstScheduledRoot;
+      null !== root;
 
-      ) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (0 === remainingExpirationTime) {
-          invariant(
-            null !== previousScheduledRoot && null !== lastScheduledRoot,
-            "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
-          );
-          if (root === root.nextScheduledRoot) {
-            firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot)
-            (firstScheduledRoot = remainingExpirationTime =
-              root.nextScheduledRoot),
-              (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
-              (root.nextScheduledRoot = null);
-          else if (root === lastScheduledRoot) {
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else
-            (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
-              (root.nextScheduledRoot = null);
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            0 === highestPriorityWork ||
-            remainingExpirationTime < highestPriorityWork
-          )
-            (highestPriorityWork = remainingExpirationTime),
-              (highestPriorityRoot = root);
-          if (root === lastScheduledRoot) break;
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
-        }
+    ) {
+      var remainingExpirationTime = root.expirationTime;
+      if (0 === remainingExpirationTime) {
+        invariant(
+          null !== previousScheduledRoot && null !== lastScheduledRoot,
+          "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
+        );
+        if (root === root.nextScheduledRoot) {
+          firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
+          break;
+        } else if (root === firstScheduledRoot)
+          (firstScheduledRoot = remainingExpirationTime =
+            root.nextScheduledRoot),
+            (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
+            (root.nextScheduledRoot = null);
+        else if (root === lastScheduledRoot) {
+          lastScheduledRoot = previousScheduledRoot;
+          lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+          root.nextScheduledRoot = null;
+          break;
+        } else
+          (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
+            (root.nextScheduledRoot = null);
+        root = previousScheduledRoot.nextScheduledRoot;
+      } else {
+        if (
+          0 === highestPriorityWork ||
+          remainingExpirationTime < highestPriorityWork
+        )
+          (highestPriorityWork = remainingExpirationTime),
+            (highestPriorityRoot = root);
+        if (root === lastScheduledRoot) break;
+        previousScheduledRoot = root;
+        root = root.nextScheduledRoot;
       }
-    previousScheduledRoot = nextFlushedRoot;
-    null !== previousScheduledRoot &&
-    previousScheduledRoot === highestPriorityRoot &&
-    1 === highestPriorityWork
-      ? nestedUpdateCount++
-      : (nestedUpdateCount = 0);
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
-  }
-  function performAsyncWork(dl) {
-    performWork(0, !0, dl);
-  }
-  function performSyncWork() {
-    performWork(1, !1, null);
-  }
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
-    findHighestPriorityRoot();
-    if (isAsync)
-      for (
-        ;
-        null !== nextFlushedRoot &&
-        0 !== nextFlushedExpirationTime &&
-        (0 === minExpirationTime ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime);
+    }
+  previousScheduledRoot = nextFlushedRoot;
+  null !== previousScheduledRoot &&
+  previousScheduledRoot === highestPriorityRoot &&
+  1 === highestPriorityWork
+    ? nestedUpdateCount++
+    : (nestedUpdateCount = 0);
+  nextFlushedRoot = highestPriorityRoot;
+  nextFlushedExpirationTime = highestPriorityWork;
+}
+function performAsyncWork(dl) {
+  performWork(0, dl);
+}
+function performWork(minExpirationTime, dl) {
+  deadline = dl;
+  findHighestPriorityRoot();
+  if (null !== deadline)
+    for (
+      ;
+      null !== nextFlushedRoot &&
+      0 !== nextFlushedExpirationTime &&
+      (0 === minExpirationTime ||
+        minExpirationTime >= nextFlushedExpirationTime) &&
+      (!deadlineDidExpire ||
+        recalculateCurrentTime() >= nextFlushedExpirationTime);
 
-      )
-        recalculateCurrentTime(),
-          performWorkOnRoot(
-            nextFlushedRoot,
-            nextFlushedExpirationTime,
-            !deadlineDidExpire
-          ),
-          findHighestPriorityRoot();
-    else
-      for (
-        ;
-        null !== nextFlushedRoot &&
-        0 !== nextFlushedExpirationTime &&
-        (0 === minExpirationTime ||
-          minExpirationTime >= nextFlushedExpirationTime);
+    )
+      recalculateCurrentTime(),
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !0),
+        findHighestPriorityRoot();
+  else
+    for (
+      ;
+      null !== nextFlushedRoot &&
+      0 !== nextFlushedExpirationTime &&
+      (0 === minExpirationTime ||
+        minExpirationTime >= nextFlushedExpirationTime);
 
-      )
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
-          findHighestPriorityRoot();
-    null !== deadline && ((callbackExpirationTime = 0), (callbackID = -1));
-    0 !== nextFlushedExpirationTime &&
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
-    deadline = null;
-    deadlineDidExpire = !1;
-    finishRendering();
-  }
-  function finishRendering() {
-    nestedUpdateCount = 0;
-    if (null !== completedBatches) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          hasUnhandledError ||
-            ((hasUnhandledError = !0), (unhandledError = error));
-        }
+    )
+      performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
+        findHighestPriorityRoot();
+  null !== deadline && ((callbackExpirationTime = 0), (callbackID = null));
+  0 !== nextFlushedExpirationTime &&
+    scheduleCallbackWithExpirationTime(nextFlushedExpirationTime);
+  deadline = null;
+  deadlineDidExpire = !1;
+  finishRendering();
+}
+function finishRendering() {
+  nestedUpdateCount = 0;
+  if (null !== completedBatches) {
+    var batches = completedBatches;
+    completedBatches = null;
+    for (var i = 0; i < batches.length; i++) {
+      var batch = batches[i];
+      try {
+        batch._onComplete();
+      } catch (error) {
+        hasUnhandledError ||
+          ((hasUnhandledError = !0), (unhandledError = error));
       }
     }
-    if (hasUnhandledError)
-      throw ((batches = unhandledError),
-      (unhandledError = null),
-      (hasUnhandledError = !1),
-      batches);
   }
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
-    );
-    isRendering = !0;
-    isAsync
-      ? ((isAsync = root.finishedWork),
-        null !== isAsync
-          ? completeRoot$$1(root, isAsync, expirationTime)
-          : ((root.finishedWork = null),
-            (isAsync = renderRoot(root, expirationTime, !0)),
-            null !== isAsync &&
-              (shouldYield()
-                ? (root.finishedWork = isAsync)
-                : completeRoot$$1(root, isAsync, expirationTime))))
-      : ((isAsync = root.finishedWork),
-        null !== isAsync
-          ? completeRoot$$1(root, isAsync, expirationTime)
-          : ((root.finishedWork = null),
-            (isAsync = renderRoot(root, expirationTime, !1)),
-            null !== isAsync &&
-              completeRoot$$1(root, isAsync, expirationTime)));
-    isRendering = !1;
+  if (hasUnhandledError)
+    throw ((batches = unhandledError),
+    (unhandledError = null),
+    (hasUnhandledError = !1),
+    batches);
+}
+function performWorkOnRoot(root, expirationTime, isYieldy) {
+  invariant(
+    !isRendering,
+    "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+  );
+  isRendering = !0;
+  isYieldy
+    ? ((isYieldy = root.finishedWork),
+      null !== isYieldy
+        ? completeRoot$1(root, isYieldy, expirationTime)
+        : ((root.finishedWork = null),
+          renderRoot(root, !0),
+          (isYieldy = root.finishedWork),
+          null !== isYieldy &&
+            (shouldYield()
+              ? (root.finishedWork = isYieldy)
+              : completeRoot$1(root, isYieldy, expirationTime))))
+    : ((isYieldy = root.finishedWork),
+      null !== isYieldy
+        ? completeRoot$1(root, isYieldy, expirationTime)
+        : ((root.finishedWork = null),
+          renderRoot(root, !1),
+          (isYieldy = root.finishedWork),
+          null !== isYieldy && completeRoot$1(root, isYieldy, expirationTime)));
+  isRendering = !1;
+}
+function completeRoot$1(root, finishedWork$jscomp$0, expirationTime) {
+  var firstBatch = root.firstBatch;
+  if (
+    null !== firstBatch &&
+    firstBatch._expirationTime <= expirationTime &&
+    (null === completedBatches
+      ? (completedBatches = [firstBatch])
+      : completedBatches.push(firstBatch),
+    firstBatch._defer)
+  ) {
+    root.finishedWork = finishedWork$jscomp$0;
+    root.expirationTime = 0;
+    return;
   }
-  function completeRoot$$1(root, finishedWork, expirationTime) {
-    var firstBatch = root.firstBatch;
-    if (
-      null !== firstBatch &&
-      firstBatch._expirationTime <= expirationTime &&
-      (null === completedBatches
-        ? (completedBatches = [firstBatch])
-        : completedBatches.push(firstBatch),
-      firstBatch._defer)
-    ) {
-      root.finishedWork = finishedWork;
-      root.remainingExpirationTime = 0;
-      return;
-    }
-    root.finishedWork = null;
-    isCommitting = isWorking = !0;
-    expirationTime = finishedWork.stateNode;
-    invariant(
-      expirationTime.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
-    );
-    firstBatch = expirationTime.pendingCommitExpirationTime;
-    invariant(
-      0 !== firstBatch,
-      "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    expirationTime.pendingCommitExpirationTime = 0;
-    var currentTime = recalculateCurrentTime();
-    ReactCurrentOwner.current = null;
-    if (1 < finishedWork.effectTag)
-      if (null !== finishedWork.lastEffect) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        var firstEffect = finishedWork.firstEffect;
-      } else firstEffect = finishedWork;
-    else firstEffect = finishedWork.firstEffect;
-    prepareForCommit(expirationTime.containerInfo);
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      var didError = !1,
-        error = void 0;
-      try {
-        for (; null !== nextEffect; )
-          nextEffect.effectTag & 256 &&
-            commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
-            (nextEffect = nextEffect.nextEffect);
-      } catch (e) {
-        (didError = !0), (error = e);
-      }
-      didError &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, error),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      didError = !1;
-      error = void 0;
-      try {
-        for (; null !== nextEffect; ) {
-          var effectTag = nextEffect.effectTag;
-          effectTag & 16 && commitResetTextContent(nextEffect);
-          if (effectTag & 128) {
-            var current = nextEffect.alternate;
-            null !== current && commitDetachRef(current);
-          }
-          switch (effectTag & 14) {
+  root.finishedWork = null;
+  isCommitting$1 = isWorking = !0;
+  invariant(
+    root.current !== finishedWork$jscomp$0,
+    "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
+  );
+  expirationTime = root.pendingCommitExpirationTime;
+  invariant(
+    0 !== expirationTime,
+    "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
+  );
+  root.pendingCommitExpirationTime = 0;
+  firstBatch = finishedWork$jscomp$0.expirationTime;
+  recalculateCurrentTime();
+  root.didError = !1;
+  if (0 === firstBatch)
+    (root.earliestPendingTime = 0),
+      (root.latestPendingTime = 0),
+      (root.earliestSuspendedTime = 0),
+      (root.latestSuspendedTime = 0),
+      (root.latestPingedTime = 0);
+  else {
+    var latestPendingTime = root.latestPendingTime;
+    0 !== latestPendingTime &&
+      (latestPendingTime < firstBatch
+        ? (root.earliestPendingTime = root.latestPendingTime = 0)
+        : root.earliestPendingTime < firstBatch &&
+          (root.earliestPendingTime = root.latestPendingTime));
+    latestPendingTime = root.earliestSuspendedTime;
+    0 === latestPendingTime
+      ? markPendingPriorityLevel(root, firstBatch)
+      : firstBatch > root.latestSuspendedTime
+        ? ((root.earliestSuspendedTime = 0),
+          (root.latestSuspendedTime = 0),
+          (root.latestPingedTime = 0),
+          markPendingPriorityLevel(root, firstBatch))
+        : firstBatch < latestPendingTime &&
+          markPendingPriorityLevel(root, firstBatch);
+  }
+  findNextPendingPriorityLevel(root);
+  ReactCurrentOwner.current = null;
+  1 < finishedWork$jscomp$0.effectTag
+    ? null !== finishedWork$jscomp$0.lastEffect
+      ? ((finishedWork$jscomp$0.lastEffect.nextEffect = finishedWork$jscomp$0),
+        (firstBatch = finishedWork$jscomp$0.firstEffect))
+      : (firstBatch = finishedWork$jscomp$0)
+    : (firstBatch = finishedWork$jscomp$0.firstEffect);
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    latestPendingTime = !1;
+    var error = void 0;
+    try {
+      for (; null !== nextEffect; ) {
+        if (nextEffect.effectTag & 256) {
+          var current = nextEffect.alternate,
+            finishedWork = nextEffect;
+          switch (finishedWork.tag) {
             case 2:
-              commitPlacement(nextEffect);
-              nextEffect.effectTag &= -3;
+              if (finishedWork.effectTag & 256 && null !== current) {
+                var prevProps = current.memoizedProps,
+                  prevState = current.memoizedState,
+                  instance = finishedWork.stateNode;
+                instance.props = finishedWork.memoizedProps;
+                instance.state = finishedWork.memoizedState;
+                var snapshot = instance.getSnapshotBeforeUpdate(
+                  prevProps,
+                  prevState
+                );
+                instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+              }
               break;
+            case 3:
+            case 5:
             case 6:
-              commitPlacement(nextEffect);
-              nextEffect.effectTag &= -3;
-              commitWork(nextEffect.alternate, nextEffect);
-              break;
             case 4:
-              commitWork(nextEffect.alternate, nextEffect);
               break;
-            case 8:
-              commitDeletion(nextEffect);
+            default:
+              invariant(
+                !1,
+                "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+              );
           }
-          nextEffect = nextEffect.nextEffect;
         }
-      } catch (e) {
-        (didError = !0), (error = e);
+        nextEffect = nextEffect.nextEffect;
       }
-      didError &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, error),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    } catch (e) {
+      (latestPendingTime = !0), (error = e);
     }
-    resetAfterCommit(expirationTime.containerInfo);
-    expirationTime.current = finishedWork;
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      effectTag = !1;
-      current = void 0;
-      try {
-        for (
-          firstEffect = expirationTime,
-            didError = currentTime,
-            error = firstBatch;
-          null !== nextEffect;
-
-        ) {
-          var effectTag$jscomp$0 = nextEffect.effectTag;
-          effectTag$jscomp$0 & 36 &&
-            commitLifeCycles(
-              firstEffect,
-              nextEffect.alternate,
-              nextEffect,
-              didError,
-              error
-            );
-          effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
-          var next = nextEffect.nextEffect;
-          nextEffect.nextEffect = null;
-          nextEffect = next;
+    latestPendingTime &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, error),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    current = !1;
+    prevProps = void 0;
+    try {
+      for (; null !== nextEffect; ) {
+        var effectTag = nextEffect.effectTag;
+        if (effectTag & 128) {
+          var current$jscomp$0 = nextEffect.alternate;
+          if (null !== current$jscomp$0) {
+            var currentRef = current$jscomp$0.ref;
+            null !== currentRef &&
+              ("function" === typeof currentRef
+                ? currentRef(null)
+                : (currentRef.current = null));
+          }
+        }
+        switch (effectTag & 14) {
+          case 2:
+            nextEffect.effectTag &= -3;
+            break;
+          case 6:
+            nextEffect.effectTag &= -3;
+            commitWork(nextEffect.alternate, nextEffect);
+            break;
+          case 4:
+            commitWork(nextEffect.alternate, nextEffect);
+            break;
+          case 8:
+            prevState = nextEffect;
+            a: for (snapshot = instance = prevState; ; ) {
+              latestPendingTime = snapshot;
+              "function" === typeof onCommitUnmount &&
+                onCommitUnmount(latestPendingTime);
+              switch (latestPendingTime.tag) {
+                case 2:
+                  safelyDetachRef(latestPendingTime);
+                  var instance$jscomp$0 = latestPendingTime.stateNode;
+                  if (
+                    "function" === typeof instance$jscomp$0.componentWillUnmount
+                  )
+                    try {
+                      (instance$jscomp$0.props =
+                        latestPendingTime.memoizedProps),
+                        (instance$jscomp$0.state =
+                          latestPendingTime.memoizedState),
+                        instance$jscomp$0.componentWillUnmount();
+                    } catch (unmountError) {
+                      captureCommitPhaseError(latestPendingTime, unmountError);
+                    }
+                  break;
+                case 5:
+                  safelyDetachRef(latestPendingTime);
+                  break;
+                case 4:
+                  FabricUIManager.createChildSet(
+                    latestPendingTime.stateNode.containerInfo
+                  );
+              }
+              if (null !== snapshot.child)
+                (snapshot.child.return = snapshot), (snapshot = snapshot.child);
+              else {
+                if (snapshot === instance) break;
+                for (; null === snapshot.sibling; ) {
+                  if (null === snapshot.return || snapshot.return === instance)
+                    break a;
+                  snapshot = snapshot.return;
+                }
+                snapshot.sibling.return = snapshot.return;
+                snapshot = snapshot.sibling;
+              }
+            }
+            prevState.return = null;
+            prevState.child = null;
+            prevState.alternate &&
+              ((prevState.alternate.child = null),
+              (prevState.alternate.return = null));
         }
-      } catch (e) {
-        (effectTag = !0), (current = e);
+        nextEffect = nextEffect.nextEffect;
       }
-      effectTag &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, current),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+    } catch (e) {
+      (current = !0), (prevProps = e);
     }
-    isWorking = isCommitting = !1;
-    "function" === typeof onCommitRoot && onCommitRoot(finishedWork.stateNode);
-    finishedWork = expirationTime.current.expirationTime;
-    0 === finishedWork && (legacyErrorBoundariesThatAlreadyFailed = null);
-    root.remainingExpirationTime = finishedWork;
-  }
-  function shouldYield() {
-    return null === deadline ||
-      deadline.timeRemaining() > timeHeuristicForUnitOfWork
-      ? !1
-      : (deadlineDidExpire = !0);
-  }
-  function onUncaughtError(error) {
-    invariant(
-      null !== nextFlushedRoot,
-      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    nextFlushedRoot.remainingExpirationTime = 0;
-    hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
-  }
-  function onBlock(remainingExpirationTime) {
-    invariant(
-      null !== nextFlushedRoot,
-      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    nextFlushedRoot.remainingExpirationTime = remainingExpirationTime;
+    current &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, prevProps),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
   }
-  var now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit,
-    stack = ReactFiberStack(),
-    hostContext = ReactFiberHostContext(config, stack),
-    legacyContext = ReactFiberLegacyContext(stack);
-  stack = ReactFiberNewContext(stack, config.isPrimaryRenderer);
-  var profilerTimer = createProfilerTimer(now),
-    hydrationContext = ReactFiberHydrationContext(config),
-    beginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      stack,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      profilerTimer,
-      recalculateCurrentTime
-    ).beginWork,
-    completeWork = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      stack,
-      hydrationContext,
-      profilerTimer
-    ).completeWork;
-  hostContext = ReactFiberUnwindWork(
-    config,
-    hostContext,
-    legacyContext,
-    stack,
-    scheduleWork,
-    computeExpirationForFiber,
-    recalculateCurrentTime,
-    markLegacyErrorBoundaryAsFailed,
-    isAlreadyFailedLegacyErrorBoundary,
-    onUncaughtError,
-    profilerTimer,
-    function(root, thenable, timeoutMs) {
-      0 <= timeoutMs &&
-        nextLatestTimeoutMs < timeoutMs &&
-        (nextLatestTimeoutMs = timeoutMs);
-    },
-    retrySuspendedRoot
-  );
-  var throwException = hostContext.throwException,
-    unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork,
-    createRootErrorUpdate = hostContext.createRootErrorUpdate,
-    createClassErrorUpdate = hostContext.createClassErrorUpdate;
-  config = ReactFiberCommitWork(
-    config,
-    onCommitPhaseError,
-    scheduleWork,
-    computeExpirationForFiber,
-    markLegacyErrorBoundaryAsFailed,
-    recalculateCurrentTime
-  );
-  var commitBeforeMutationLifeCycles = config.commitBeforeMutationLifeCycles,
-    commitResetTextContent = config.commitResetTextContent,
-    commitPlacement = config.commitPlacement,
-    commitDeletion = config.commitDeletion,
-    commitWork = config.commitWork,
-    commitLifeCycles = config.commitLifeCycles,
-    commitAttachRef = config.commitAttachRef,
-    commitDetachRef = config.commitDetachRef,
-    originalStartTimeMs = now(),
-    mostRecentCurrentTime = 2,
-    mostRecentCurrentTimeMs = originalStartTimeMs,
-    lastUniqueAsyncExpiration = 0,
-    expirationContext = 0,
-    isWorking = !1,
-    nextUnitOfWork = null,
-    nextRoot = null,
-    nextRenderExpirationTime = 0,
-    nextLatestTimeoutMs = -1,
-    nextRenderIsExpired = !1,
-    nextEffect = null,
-    isCommitting = !1,
-    isRootReadyForCommit = !1,
-    legacyErrorBoundariesThatAlreadyFailed = null,
-    firstScheduledRoot = null,
-    lastScheduledRoot = null,
-    callbackExpirationTime = 0,
-    callbackID = -1,
-    isRendering = !1,
-    nextFlushedRoot = null,
-    nextFlushedExpirationTime = 0,
-    lowestPendingInteractiveExpirationTime = 0,
-    deadlineDidExpire = !1,
-    hasUnhandledError = !1,
-    unhandledError = null,
-    deadline = null,
-    isBatchingUpdates = !1,
-    isUnbatchingUpdates = !1,
-    isBatchingInteractiveUpdates = !1,
-    completedBatches = null,
-    NESTED_UPDATE_LIMIT = 1e3,
-    nestedUpdateCount = 0,
-    timeHeuristicForUnitOfWork = 1;
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: function(root, expirationTime) {
-      invariant(
-        !isRendering,
-        "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
-      );
-      nextFlushedRoot = root;
-      nextFlushedExpirationTime = expirationTime;
-      performWorkOnRoot(root, expirationTime, !1);
-      performSyncWork();
-      finishRendering();
-    },
-    batchedUpdates: function(fn, a) {
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        return fn(a);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates) ||
-          isRendering ||
-          performSyncWork();
-      }
-    },
-    unbatchedUpdates: function(fn, a) {
-      if (isBatchingUpdates && !isUnbatchingUpdates) {
-        isUnbatchingUpdates = !0;
-        try {
-          return fn(a);
-        } finally {
-          isUnbatchingUpdates = !1;
+  root.current = finishedWork$jscomp$0;
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    effectTag = !1;
+    current$jscomp$0 = void 0;
+    try {
+      for (currentRef = expirationTime; null !== nextEffect; ) {
+        var effectTag$jscomp$0 = nextEffect.effectTag;
+        if (effectTag$jscomp$0 & 36) {
+          var current$jscomp$1 = nextEffect.alternate;
+          instance$jscomp$0 = nextEffect;
+          firstBatch = currentRef;
+          switch (instance$jscomp$0.tag) {
+            case 2:
+              var instance$jscomp$1 = instance$jscomp$0.stateNode;
+              if (instance$jscomp$0.effectTag & 4)
+                if (null === current$jscomp$1)
+                  (instance$jscomp$1.props = instance$jscomp$0.memoizedProps),
+                    (instance$jscomp$1.state = instance$jscomp$0.memoizedState),
+                    instance$jscomp$1.componentDidMount();
+                else {
+                  var prevProps$jscomp$0 = current$jscomp$1.memoizedProps,
+                    prevState$jscomp$0 = current$jscomp$1.memoizedState;
+                  instance$jscomp$1.props = instance$jscomp$0.memoizedProps;
+                  instance$jscomp$1.state = instance$jscomp$0.memoizedState;
+                  instance$jscomp$1.componentDidUpdate(
+                    prevProps$jscomp$0,
+                    prevState$jscomp$0,
+                    instance$jscomp$1.__reactInternalSnapshotBeforeUpdate
+                  );
+                }
+              var updateQueue = instance$jscomp$0.updateQueue;
+              null !== updateQueue &&
+                ((instance$jscomp$1.props = instance$jscomp$0.memoizedProps),
+                (instance$jscomp$1.state = instance$jscomp$0.memoizedState),
+                commitUpdateQueue(
+                  instance$jscomp$0,
+                  updateQueue,
+                  instance$jscomp$1,
+                  firstBatch
+                ));
+              break;
+            case 3:
+              var _updateQueue = instance$jscomp$0.updateQueue;
+              if (null !== _updateQueue) {
+                current = null;
+                if (null !== instance$jscomp$0.child)
+                  switch (instance$jscomp$0.child.tag) {
+                    case 5:
+                      current = instance$jscomp$0.child.stateNode.canonical;
+                      break;
+                    case 2:
+                      current = instance$jscomp$0.child.stateNode;
+                  }
+                commitUpdateQueue(
+                  instance$jscomp$0,
+                  _updateQueue,
+                  current,
+                  firstBatch
+                );
+              }
+              break;
+            case 5:
+              null === current$jscomp$1 &&
+                instance$jscomp$0.effectTag & 4 &&
+                invariant(
+                  !1,
+                  "The current renderer does not support mutation. This error is likely caused by a bug in React. Please file an issue."
+                );
+              break;
+            case 6:
+              break;
+            case 4:
+              break;
+            case 15:
+              break;
+            case 16:
+              break;
+            default:
+              invariant(
+                !1,
+                "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+              );
+          }
+        }
+        if (effectTag$jscomp$0 & 128) {
+          instance$jscomp$0 = void 0;
+          var ref = nextEffect.ref;
+          if (null !== ref) {
+            var instance$jscomp$2 = nextEffect.stateNode;
+            switch (nextEffect.tag) {
+              case 5:
+                instance$jscomp$0 = instance$jscomp$2.canonical;
+                break;
+              default:
+                instance$jscomp$0 = instance$jscomp$2;
+            }
+            "function" === typeof ref
+              ? ref(instance$jscomp$0)
+              : (ref.current = instance$jscomp$0);
+          }
         }
+        var next = nextEffect.nextEffect;
+        nextEffect.nextEffect = null;
+        nextEffect = next;
       }
-      return fn(a);
-    },
-    flushSync: function(fn, a) {
+    } catch (e) {
+      (effectTag = !0), (current$jscomp$0 = e);
+    }
+    effectTag &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, current$jscomp$0),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  isWorking = isCommitting$1 = !1;
+  "function" === typeof onCommitRoot &&
+    onCommitRoot(finishedWork$jscomp$0.stateNode);
+  finishedWork$jscomp$0 = root.expirationTime;
+  0 === finishedWork$jscomp$0 &&
+    (legacyErrorBoundariesThatAlreadyFailed = null);
+  root.expirationTime = finishedWork$jscomp$0;
+  root.finishedWork = null;
+}
+function shouldYield() {
+  return null === deadline ||
+    deadlineDidExpire ||
+    deadline.timeRemaining() > timeHeuristicForUnitOfWork
+    ? !1
+    : (deadlineDidExpire = !0);
+}
+function onUncaughtError(error) {
+  invariant(
+    null !== nextFlushedRoot,
+    "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
+  );
+  nextFlushedRoot.expirationTime = 0;
+  hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
+}
+function updateContainerAtExpirationTime(
+  element,
+  container,
+  parentComponent,
+  expirationTime,
+  callback
+) {
+  var current = container.current;
+  if (parentComponent) {
+    parentComponent = parentComponent._reactInternalFiber;
+    var parentContext;
+    b: {
       invariant(
-        !isRendering,
-        "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
+        2 === isFiberMountedImpl(parentComponent) && 2 === parentComponent.tag,
+        "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
       );
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        return syncUpdates(fn, a);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates), performSyncWork();
-      }
-    },
-    flushControlled: function(fn) {
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        syncUpdates(fn);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates) ||
-          isRendering ||
-          performWork(1, !1, null);
-      }
-    },
-    deferredUpdates: function(fn) {
-      var previousExpirationContext = expirationContext;
-      expirationContext =
-        2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
-      try {
-        return fn();
-      } finally {
-        expirationContext = previousExpirationContext;
-      }
-    },
-    syncUpdates: syncUpdates,
-    interactiveUpdates: function(fn, a, b) {
-      if (isBatchingInteractiveUpdates) return fn(a, b);
-      isBatchingUpdates ||
-        isRendering ||
-        0 === lowestPendingInteractiveExpirationTime ||
-        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
-        (lowestPendingInteractiveExpirationTime = 0));
-      var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
-        previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = isBatchingInteractiveUpdates = !0;
-      try {
-        return fn(a, b);
-      } finally {
-        (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
-          (isBatchingUpdates = previousIsBatchingUpdates) ||
-            isRendering ||
-            performSyncWork();
+      for (parentContext = parentComponent; 3 !== parentContext.tag; ) {
+        if (isContextProvider(parentContext)) {
+          parentContext =
+            parentContext.stateNode.__reactInternalMemoizedMergedChildContext;
+          break b;
+        }
+        parentContext = parentContext.return;
+        invariant(
+          parentContext,
+          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
+        );
       }
-    },
-    flushInteractiveUpdates: function() {
-      isRendering ||
-        0 === lowestPendingInteractiveExpirationTime ||
-        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
-        (lowestPendingInteractiveExpirationTime = 0));
-    },
-    computeUniqueAsyncExpiration: function() {
-      var result =
-        2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
-      result <= lastUniqueAsyncExpiration &&
-        (result = lastUniqueAsyncExpiration + 1);
-      return (lastUniqueAsyncExpiration = result);
-    },
-    legacyContext: legacyContext
-  };
+      parentContext = parentContext.stateNode.context;
+    }
+    parentComponent = isContextProvider(parentComponent)
+      ? processChildContext(parentComponent, parentContext)
+      : parentContext;
+  } else parentComponent = emptyObject;
+  null === container.context
+    ? (container.context = parentComponent)
+    : (container.pendingContext = parentComponent);
+  container = callback;
+  callback = createUpdate(expirationTime);
+  callback.payload = { element: element };
+  container = void 0 === container ? null : container;
+  null !== container && (callback.callback = container);
+  enqueueUpdate(current, callback, expirationTime);
+  scheduleWork(current, expirationTime);
+  return expirationTime;
+}
+function findHostInstance$1(component) {
+  var fiber = component._reactInternalFiber;
+  void 0 === fiber &&
+    ("function" === typeof component.render
+      ? invariant(!1, "Unable to find node on an unmounted component.")
+      : invariant(
+          !1,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        ));
+  component = findCurrentHostFiber(fiber);
+  return null === component ? null : component.stateNode;
 }
-function ReactFiberReconciler$1(config) {
-  function updateContainerAtExpirationTime(
+function updateContainer(element, container, parentComponent, callback) {
+  var current = container.current,
+    currentTime = recalculateCurrentTime();
+  current = computeExpirationForFiber(currentTime, current);
+  return updateContainerAtExpirationTime(
     element,
     container,
     parentComponent,
-    expirationTime,
+    current,
     callback
-  ) {
-    var current = container.current;
-    if (parentComponent) {
-      parentComponent = parentComponent._reactInternalFiber;
-      var parentContext = findCurrentUnmaskedContext(parentComponent);
-      parentComponent = isContextProvider(parentComponent)
-        ? processChildContext(parentComponent, parentContext)
-        : parentContext;
-    } else parentComponent = emptyObject;
-    null === container.context
-      ? (container.context = parentComponent)
-      : (container.pendingContext = parentComponent);
-    container = callback;
-    callback = createUpdate(expirationTime);
-    callback.payload = { element: element };
-    container = void 0 === container ? null : container;
-    null !== container && (callback.callback = container);
-    enqueueUpdate(current, callback, expirationTime);
-    scheduleWork(current, expirationTime);
-    return expirationTime;
+  );
+}
+function getPublicRootInstance(container) {
+  container = container.current;
+  if (!container.child) return null;
+  switch (container.child.tag) {
+    case 5:
+      return container.child.stateNode.canonical;
+    default:
+      return container.child.stateNode;
   }
-  var getPublicInstance = config.getPublicInstance;
-  config = ReactFiberScheduler(config);
-  var recalculateCurrentTime = config.recalculateCurrentTime,
-    computeExpirationForFiber = config.computeExpirationForFiber,
-    scheduleWork = config.scheduleWork,
-    legacyContext = config.legacyContext,
-    findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
-  return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
-      containerInfo = {
-        current: isAsync,
-        containerInfo: containerInfo,
-        pendingChildren: null,
-        earliestPendingTime: 0,
-        latestPendingTime: 0,
-        earliestSuspendedTime: 0,
-        latestSuspendedTime: 0,
-        latestPingedTime: 0,
-        pendingCommitExpirationTime: 0,
-        finishedWork: null,
-        context: null,
-        pendingContext: null,
-        hydrate: hydrate,
-        remainingExpirationTime: 0,
-        firstBatch: null,
-        nextScheduledRoot: null
-      };
-      return (isAsync.stateNode = containerInfo);
-    },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current,
-        currentTime = recalculateCurrentTime();
-      current = computeExpirationForFiber(currentTime, current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        current,
-        callback
-      );
-    },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
-    ) {
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        expirationTime,
-        callback
-      );
-    },
-    flushRoot: config.flushRoot,
-    requestWork: config.requestWork,
-    computeUniqueAsyncExpiration: config.computeUniqueAsyncExpiration,
-    batchedUpdates: config.batchedUpdates,
-    unbatchedUpdates: config.unbatchedUpdates,
-    deferredUpdates: config.deferredUpdates,
-    syncUpdates: config.syncUpdates,
-    interactiveUpdates: config.interactiveUpdates,
-    flushInteractiveUpdates: config.flushInteractiveUpdates,
-    flushControlled: config.flushControlled,
-    flushSync: config.flushSync,
-    getPublicRootInstance: function(container) {
-      container = container.current;
-      if (!container.child) return null;
-      switch (container.child.tag) {
-        case 5:
-          return getPublicInstance(container.child.stateNode);
-        default:
-          return container.child.stateNode;
+}
+function injectIntoDevTools(devToolsConfig) {
+  var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+  return injectInternals(
+    Object.assign({}, devToolsConfig, {
+      findHostInstanceByFiber: function(fiber) {
+        fiber = findCurrentHostFiber(fiber);
+        return null === fiber ? null : fiber.stateNode;
+      },
+      findFiberByHostInstance: function(instance) {
+        return findFiberByHostInstance
+          ? findFiberByHostInstance(instance)
+          : null;
       }
-    },
-    findHostInstance: function(component) {
-      var fiber = component._reactInternalFiber;
-      void 0 === fiber &&
-        ("function" === typeof component.render
-          ? invariant(!1, "Unable to find node on an unmounted component.")
-          : invariant(
-              !1,
-              "Argument appears to not be a ReactComponent. Keys: %s",
-              Object.keys(component)
-            ));
-      component = findCurrentHostFiber(fiber);
-      return null === component ? null : component.stateNode;
-    },
-    findHostInstanceWithNoPortals: function(fiber) {
-      fiber = findCurrentHostFiberWithNoPortals(fiber);
-      return null === fiber ? null : fiber.stateNode;
-    },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            fiber = findCurrentHostFiber(fiber);
-            return null === fiber ? null : fiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            return findFiberByHostInstance
-              ? findFiberByHostInstance(instance)
-              : null;
-          }
-        })
-      );
-    }
-  };
+    })
+  );
 }
-var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
-  ReactFiberReconciler$3 =
-    (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
-    ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3.default
-    ? ReactFiberReconciler$3.default
-    : ReactFiberReconciler$3,
-  now =
-    "object" === typeof performance && "function" === typeof performance.now
-      ? function() {
-          return performance.now();
-        }
-      : function() {
-          return Date.now();
-        },
-  scheduledCallback = null,
-  frameDeadline = 0,
-  frameDeadlineObject = {
-    timeRemaining: function() {
-      return frameDeadline - now();
-    },
-    didTimeout: !1
+var ReactFabricRenderer = {
+  updateContainerAtExpirationTime: updateContainerAtExpirationTime,
+  createContainer: function(containerInfo, isAsync, hydrate) {
+    return createFiberRoot(containerInfo, isAsync, hydrate);
+  },
+  updateContainer: updateContainer,
+  flushRoot: function(root, expirationTime) {
+    invariant(
+      !isRendering,
+      "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
+    );
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
+    performWorkOnRoot(root, expirationTime, !1);
+    performWork(1, null);
+    finishRendering();
+  },
+  requestWork: requestWork,
+  computeUniqueAsyncExpiration: function() {
+    var result =
+      2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
+    result <= lastUniqueAsyncExpiration &&
+      (result = lastUniqueAsyncExpiration + 1);
+    return (lastUniqueAsyncExpiration = result);
+  },
+  batchedUpdates: function(fn, a) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      return fn(a);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates) ||
+        isRendering ||
+        performWork(1, null);
+    }
+  },
+  unbatchedUpdates: function(fn, a) {
+    if (isBatchingUpdates && !isUnbatchingUpdates) {
+      isUnbatchingUpdates = !0;
+      try {
+        return fn(a);
+      } finally {
+        isUnbatchingUpdates = !1;
+      }
+    }
+    return fn(a);
+  },
+  deferredUpdates: function(fn) {
+    var previousExpirationContext = expirationContext;
+    expirationContext =
+      2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
+    try {
+      return fn();
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  },
+  syncUpdates: syncUpdates,
+  interactiveUpdates: function(fn, a, b) {
+    if (isBatchingInteractiveUpdates) return fn(a, b);
+    isBatchingUpdates ||
+      isRendering ||
+      0 === lowestPendingInteractiveExpirationTime ||
+      (performWork(lowestPendingInteractiveExpirationTime, null),
+      (lowestPendingInteractiveExpirationTime = 0));
+    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
+      previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = isBatchingInteractiveUpdates = !0;
+    try {
+      return fn(a, b);
+    } finally {
+      (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
+        (isBatchingUpdates = previousIsBatchingUpdates) ||
+          isRendering ||
+          performWork(1, null);
+    }
+  },
+  flushInteractiveUpdates: function() {
+    isRendering ||
+      0 === lowestPendingInteractiveExpirationTime ||
+      (performWork(lowestPendingInteractiveExpirationTime, null),
+      (lowestPendingInteractiveExpirationTime = 0));
+  },
+  flushControlled: function(fn) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      syncUpdates(fn);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates) ||
+        isRendering ||
+        performWork(1, null);
+    }
+  },
+  flushSync: function(fn, a) {
+    invariant(
+      !isRendering,
+      "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
+    );
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      return syncUpdates(fn, a);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates), performWork(1, null);
+    }
+  },
+  getPublicRootInstance: getPublicRootInstance,
+  findHostInstance: findHostInstance$1,
+  findHostInstanceWithNoPortals: function(fiber) {
+    fiber = findCurrentHostFiberWithNoPortals(fiber);
+    return null === fiber ? null : fiber.stateNode;
+  },
+  injectIntoDevTools: injectIntoDevTools
+};
+function createPortal(children, containerInfo, implementation) {
+  var key =
+    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
+  return {
+    $$typeof: REACT_PORTAL_TYPE,
+    key: null == key ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
   };
-function setTimeoutCallback() {
-  frameDeadline = now() + 5;
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  null !== callback && callback(frameDeadlineObject);
 }
-function dispatchEvent(target, topLevelType, nativeEvent) {
-  batchedUpdates(function() {
-    var events = nativeEvent.target;
-    for (var events$jscomp$0 = null, i = 0; i < plugins.length; i++) {
-      var possiblePlugin = plugins[i];
-      possiblePlugin &&
-        (possiblePlugin = possiblePlugin.extractEvents(
-          topLevelType,
-          target,
-          nativeEvent,
-          events
-        )) &&
-        (events$jscomp$0 = accumulateInto(events$jscomp$0, possiblePlugin));
+function _inherits(subClass, superClass) {
+  if ("function" !== typeof superClass && null !== superClass)
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: !1,
+      writable: !0,
+      configurable: !0
     }
-    events = events$jscomp$0;
-    null !== events && (eventQueue = accumulateInto(eventQueue, events));
-    events = eventQueue;
-    eventQueue = null;
-    events &&
-      (forEachAccumulated(events, executeDispatchesAndReleaseTopLevel),
-      invariant(
-        !eventQueue,
-        "processEventQueue(): Additional events were enqueued while processing an event queue. Support for this has not yet been implemented."
-      ),
-      ReactErrorUtils.rethrowCaughtError());
   });
+  superClass &&
+    (Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass));
 }
-var nextReactTag = 2;
-FabricUIManager.registerEventHandler &&
-  FabricUIManager.registerEventHandler(dispatchEvent);
-var ReactFabricHostComponent = (function() {
-    function ReactFabricHostComponent(tag, viewConfig, props) {
-      if (!(this instanceof ReactFabricHostComponent))
-        throw new TypeError("Cannot call a class as a function");
-      this._nativeTag = tag;
-      this.viewConfig = viewConfig;
-      this.currentProps = props;
-    }
-    ReactFabricHostComponent.prototype.blur = function() {
-      TextInputState.blurTextInput(this._nativeTag);
-    };
-    ReactFabricHostComponent.prototype.focus = function() {
-      TextInputState.focusTextInput(this._nativeTag);
-    };
-    ReactFabricHostComponent.prototype.measure = function(callback) {
-      UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-    };
-    ReactFabricHostComponent.prototype.measureInWindow = function(callback) {
-      UIManager.measureInWindow(
-        this._nativeTag,
-        mountSafeCallback(this, callback)
-      );
-    };
-    ReactFabricHostComponent.prototype.measureLayout = function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail
-    ) {
-      UIManager.measureLayout(
-        this._nativeTag,
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    };
-    ReactFabricHostComponent.prototype.setNativeProps = function(nativeProps) {
-      nativeProps = diffProperties(
-        null,
-        emptyObject$1,
-        nativeProps,
-        this.viewConfig.validAttributes
-      );
-      null != nativeProps &&
-        UIManager.updateView(
-          this._nativeTag,
-          this.viewConfig.uiViewClassName,
-          nativeProps
-        );
-    };
-    return ReactFabricHostComponent;
-  })(),
-  ReactFabricRenderer = reactReconciler({
-    appendInitialChild: function(parentInstance, child) {
-      FabricUIManager.appendChild(parentInstance.node, child.node);
-    },
-    createInstance: function(
-      type,
-      props,
-      rootContainerInstance,
-      hostContext,
-      internalInstanceHandle
-    ) {
-      var tag = nextReactTag;
-      nextReactTag += 2;
-      var viewConfig = ReactNativeViewConfigRegistry.get(type);
-      invariant(
-        "RCTView" !== type || !hostContext.isInAParentText,
-        "Nesting of <View> within <Text> is not currently supported."
-      );
-      type = diffProperties(
-        null,
-        emptyObject$1,
-        props,
-        viewConfig.validAttributes
-      );
-      rootContainerInstance = FabricUIManager.createNode(
-        tag,
-        viewConfig.uiViewClassName,
-        rootContainerInstance,
-        type,
-        internalInstanceHandle
-      );
-      props = new ReactFabricHostComponent(tag, viewConfig, props);
-      return { node: rootContainerInstance, canonical: props };
-    },
-    createTextInstance: function(
-      text,
-      rootContainerInstance,
-      hostContext,
-      internalInstanceHandle
-    ) {
-      invariant(
-        hostContext.isInAParentText,
-        "Text strings must be rendered within a <Text> component."
-      );
-      hostContext = nextReactTag;
-      nextReactTag += 2;
-      return {
-        node: FabricUIManager.createNode(
-          hostContext,
-          "RCTRawText",
-          rootContainerInstance,
-          { text: text },
-          internalInstanceHandle
-        )
-      };
-    },
-    finalizeInitialChildren: function() {
-      return !1;
-    },
-    getRootHostContext: function() {
-      return { isInAParentText: !1 };
-    },
-    getChildHostContext: function(parentHostContext, type) {
-      type =
-        "AndroidTextInput" === type ||
-        "RCTMultilineTextInputView" === type ||
-        "RCTSinglelineTextInputView" === type ||
-        "RCTText" === type ||
-        "RCTVirtualText" === type;
-      return parentHostContext.isInAParentText !== type
-        ? { isInAParentText: type }
-        : parentHostContext;
-    },
-    getPublicInstance: function(instance) {
-      return instance.canonical;
-    },
-    now: now,
-    isPrimaryRenderer: !1,
-    prepareForCommit: function() {},
-    prepareUpdate: function(instance, type, oldProps, newProps) {
-      return diffProperties(
-        null,
-        oldProps,
-        newProps,
-        instance.canonical.viewConfig.validAttributes
-      );
-    },
-    resetAfterCommit: function() {},
-    scheduleDeferredCallback: function(callback) {
-      scheduledCallback = callback;
-      return setTimeout(setTimeoutCallback, 1);
-    },
-    cancelDeferredCallback: function(callbackID) {
-      scheduledCallback = null;
-      clearTimeout(callbackID);
-    },
-    shouldDeprioritizeSubtree: function() {
-      return !1;
-    },
-    shouldSetTextContent: function() {
-      return !1;
-    },
-    persistence: {
-      cloneInstance: function(
-        instance,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        internalInstanceHandle,
-        keepChildren
-      ) {
-        type = instance.node;
-        return {
-          node: keepChildren
-            ? null !== updatePayload
-              ? FabricUIManager.cloneNodeWithNewProps(
-                  type,
-                  updatePayload,
-                  internalInstanceHandle
-                )
-              : FabricUIManager.cloneNode(type, internalInstanceHandle)
-            : null !== updatePayload
-              ? FabricUIManager.cloneNodeWithNewChildrenAndProps(
-                  type,
-                  updatePayload,
-                  internalInstanceHandle
-                )
-              : FabricUIManager.cloneNodeWithNewChildren(
-                  type,
-                  internalInstanceHandle
-                ),
-          canonical: instance.canonical
-        };
-      },
-      createContainerChildSet: function(container) {
-        return FabricUIManager.createChildSet(container);
-      },
-      appendChildToContainerChildSet: function(childSet, child) {
-        FabricUIManager.appendChildToSet(childSet, child.node);
-      },
-      finalizeContainerChildren: function(container, newChildren) {
-        FabricUIManager.completeRoot(container, newChildren);
-      },
-      replaceContainerChildren: function() {}
-    }
-  }),
-  getInspectorDataForViewTag = void 0;
+var getInspectorDataForViewTag = void 0;
 getInspectorDataForViewTag = function() {
   invariant(!1, "getInspectorDataForViewTag() is not available in production");
 };
-var findHostInstance = ReactFabricRenderer.findHostInstance;
 function findNodeHandle(componentOrHandle) {
   if (null == componentOrHandle) return null;
   if ("number" === typeof componentOrHandle) return componentOrHandle;
   if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
   if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
     return componentOrHandle.canonical._nativeTag;
-  componentOrHandle = findHostInstance(componentOrHandle);
+  componentOrHandle = findHostInstance$1(componentOrHandle);
   return null == componentOrHandle
     ? componentOrHandle
     : componentOrHandle.canonical
@@ -6114,20 +5506,20 @@ var roots = new Map(),
         };
         return ReactNativeComponent;
       })(React.Component);
-    })(findNodeHandle, findHostInstance),
+    })(findNodeHandle, findHostInstance$1),
     findNodeHandle: findNodeHandle,
     render: function(element, containerTag, callback) {
       var root = roots.get(containerTag);
       root ||
-        ((root = ReactFabricRenderer.createContainer(containerTag, !1, !1)),
+        ((root = createFiberRoot(containerTag, !1, !1)),
         roots.set(containerTag, root));
-      ReactFabricRenderer.updateContainer(element, root, null, callback);
-      return ReactFabricRenderer.getPublicRootInstance(root);
+      updateContainer(element, root, null, callback);
+      return getPublicRootInstance(root);
     },
     unmountComponentAtNode: function(containerTag) {
       var root = roots.get(containerTag);
       root &&
-        ReactFabricRenderer.updateContainer(null, root, null, function() {
+        updateContainer(null, root, null, function() {
           roots.delete(containerTag);
         });
     },
@@ -6190,17 +5582,16 @@ var roots = new Map(),
             TextInputState.blurTextInput(findNodeHandle(this));
           }
         };
-      })(findNodeHandle, findHostInstance),
-      ReactNativeComponentTree: ReactNativeComponentTree
+      })(findNodeHandle, findHostInstance$1)
     }
   };
-ReactFabricRenderer.injectIntoDevTools({
-  findFiberByHostInstance: getInstanceFromTag,
+injectIntoDevTools({
+  findFiberByHostInstance: getInstanceFromInstance,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
-  version: "16.3.2",
+  version: "16.4.1",
   rendererPackageName: "react-native-renderer"
 });
-var ReactFabric$2 = Object.freeze({ default: ReactFabric }),
+var ReactFabric$2 = { default: ReactFabric },
   ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
 module.exports = ReactFabric$3.default ? ReactFabric$3.default : ReactFabric$3;
diff --git a/Libraries/Renderer/oss/ReactFabric-profiling.js b/Libraries/Renderer/oss/ReactFabric-profiling.js
new file mode 100644
index 000000000000..f1962978797b
--- /dev/null
+++ b/Libraries/Renderer/oss/ReactFabric-profiling.js
@@ -0,0 +1,5645 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @noflow
+ * @providesModule ReactFabric-profiling
+ * @preventMunge
+ * @generated
+ */
+
+"use strict";
+require("InitializeCore");
+var invariant = require("fbjs/lib/invariant"),
+  ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
+  UIManager = require("UIManager"),
+  React = require("react"),
+  emptyObject = require("fbjs/lib/emptyObject"),
+  deepDiffer = require("deepDiffer"),
+  flattenStyle = require("flattenStyle"),
+  TextInputState = require("TextInputState"),
+  FabricUIManager = require("FabricUIManager"),
+  ExceptionsManager = require("ExceptionsManager");
+function invokeGuardedCallback(name, func, context, a, b, c, d, e, f) {
+  this._hasCaughtError = !1;
+  this._caughtError = null;
+  var funcArgs = Array.prototype.slice.call(arguments, 3);
+  try {
+    func.apply(context, funcArgs);
+  } catch (error) {
+    (this._caughtError = error), (this._hasCaughtError = !0);
+  }
+}
+var ReactErrorUtils = {
+  _caughtError: null,
+  _hasCaughtError: !1,
+  _rethrowError: null,
+  _hasRethrowError: !1,
+  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
+    invokeGuardedCallback.apply(ReactErrorUtils, arguments);
+  },
+  invokeGuardedCallbackAndCatchFirstError: function(
+    name,
+    func,
+    context,
+    a,
+    b,
+    c,
+    d,
+    e,
+    f
+  ) {
+    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
+    if (ReactErrorUtils.hasCaughtError()) {
+      var error = ReactErrorUtils.clearCaughtError();
+      ReactErrorUtils._hasRethrowError ||
+        ((ReactErrorUtils._hasRethrowError = !0),
+        (ReactErrorUtils._rethrowError = error));
+    }
+  },
+  rethrowCaughtError: function() {
+    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
+  },
+  hasCaughtError: function() {
+    return ReactErrorUtils._hasCaughtError;
+  },
+  clearCaughtError: function() {
+    if (ReactErrorUtils._hasCaughtError) {
+      var error = ReactErrorUtils._caughtError;
+      ReactErrorUtils._caughtError = null;
+      ReactErrorUtils._hasCaughtError = !1;
+      return error;
+    }
+    invariant(
+      !1,
+      "clearCaughtError was called but no error was captured. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+};
+function rethrowCaughtError() {
+  if (ReactErrorUtils._hasRethrowError) {
+    var error = ReactErrorUtils._rethrowError;
+    ReactErrorUtils._rethrowError = null;
+    ReactErrorUtils._hasRethrowError = !1;
+    throw error;
+  }
+}
+var eventPluginOrder = null,
+  namesToPlugins = {};
+function recomputePluginOrdering() {
+  if (eventPluginOrder)
+    for (var pluginName in namesToPlugins) {
+      var pluginModule = namesToPlugins[pluginName],
+        pluginIndex = eventPluginOrder.indexOf(pluginName);
+      invariant(
+        -1 < pluginIndex,
+        "EventPluginRegistry: Cannot inject event plugins that do not exist in the plugin ordering, `%s`.",
+        pluginName
+      );
+      if (!plugins[pluginIndex]) {
+        invariant(
+          pluginModule.extractEvents,
+          "EventPluginRegistry: Event plugins must implement an `extractEvents` method, but `%s` does not.",
+          pluginName
+        );
+        plugins[pluginIndex] = pluginModule;
+        pluginIndex = pluginModule.eventTypes;
+        for (var eventName in pluginIndex) {
+          var JSCompiler_inline_result = void 0;
+          var dispatchConfig = pluginIndex[eventName],
+            pluginModule$jscomp$0 = pluginModule,
+            eventName$jscomp$0 = eventName;
+          invariant(
+            !eventNameDispatchConfigs.hasOwnProperty(eventName$jscomp$0),
+            "EventPluginHub: More than one plugin attempted to publish the same event name, `%s`.",
+            eventName$jscomp$0
+          );
+          eventNameDispatchConfigs[eventName$jscomp$0] = dispatchConfig;
+          var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
+          if (phasedRegistrationNames) {
+            for (JSCompiler_inline_result in phasedRegistrationNames)
+              phasedRegistrationNames.hasOwnProperty(
+                JSCompiler_inline_result
+              ) &&
+                publishRegistrationName(
+                  phasedRegistrationNames[JSCompiler_inline_result],
+                  pluginModule$jscomp$0,
+                  eventName$jscomp$0
+                );
+            JSCompiler_inline_result = !0;
+          } else
+            dispatchConfig.registrationName
+              ? (publishRegistrationName(
+                  dispatchConfig.registrationName,
+                  pluginModule$jscomp$0,
+                  eventName$jscomp$0
+                ),
+                (JSCompiler_inline_result = !0))
+              : (JSCompiler_inline_result = !1);
+          invariant(
+            JSCompiler_inline_result,
+            "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
+            eventName,
+            pluginName
+          );
+        }
+      }
+    }
+}
+function publishRegistrationName(registrationName, pluginModule) {
+  invariant(
+    !registrationNameModules[registrationName],
+    "EventPluginHub: More than one plugin attempted to publish the same registration name, `%s`.",
+    registrationName
+  );
+  registrationNameModules[registrationName] = pluginModule;
+}
+var plugins = [],
+  eventNameDispatchConfigs = {},
+  registrationNameModules = {},
+  getFiberCurrentPropsFromNode = null,
+  getInstanceFromNode = null,
+  getNodeFromInstance = null;
+function executeDispatch(event, simulated, listener, inst) {
+  simulated = event.type || "unknown-event";
+  event.currentTarget = getNodeFromInstance(inst);
+  ReactErrorUtils.invokeGuardedCallbackAndCatchFirstError(
+    simulated,
+    listener,
+    void 0,
+    event
+  );
+  event.currentTarget = null;
+}
+function executeDirectDispatch(event) {
+  var dispatchListener = event._dispatchListeners,
+    dispatchInstance = event._dispatchInstances;
+  invariant(
+    !Array.isArray(dispatchListener),
+    "executeDirectDispatch(...): Invalid `event`."
+  );
+  event.currentTarget = dispatchListener
+    ? getNodeFromInstance(dispatchInstance)
+    : null;
+  dispatchListener = dispatchListener ? dispatchListener(event) : null;
+  event.currentTarget = null;
+  event._dispatchListeners = null;
+  event._dispatchInstances = null;
+  return dispatchListener;
+}
+function accumulateInto(current, next) {
+  invariant(
+    null != next,
+    "accumulateInto(...): Accumulated items must not be null or undefined."
+  );
+  if (null == current) return next;
+  if (Array.isArray(current)) {
+    if (Array.isArray(next)) return current.push.apply(current, next), current;
+    current.push(next);
+    return current;
+  }
+  return Array.isArray(next) ? [current].concat(next) : [current, next];
+}
+function forEachAccumulated(arr, cb, scope) {
+  Array.isArray(arr) ? arr.forEach(cb, scope) : arr && cb.call(scope, arr);
+}
+var eventQueue = null;
+function executeDispatchesAndReleaseTopLevel(e) {
+  if (e) {
+    var dispatchListeners = e._dispatchListeners,
+      dispatchInstances = e._dispatchInstances;
+    if (Array.isArray(dispatchListeners))
+      for (
+        var i = 0;
+        i < dispatchListeners.length && !e.isPropagationStopped();
+        i++
+      )
+        executeDispatch(e, !1, dispatchListeners[i], dispatchInstances[i]);
+    else
+      dispatchListeners &&
+        executeDispatch(e, !1, dispatchListeners, dispatchInstances);
+    e._dispatchListeners = null;
+    e._dispatchInstances = null;
+    e.isPersistent() || e.constructor.release(e);
+  }
+}
+var injection = {
+  injectEventPluginOrder: function(injectedEventPluginOrder) {
+    invariant(
+      !eventPluginOrder,
+      "EventPluginRegistry: Cannot inject event plugin ordering more than once. You are likely trying to load more than one copy of React."
+    );
+    eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
+    recomputePluginOrdering();
+  },
+  injectEventPluginsByName: function(injectedNamesToPlugins) {
+    var isOrderingDirty = !1,
+      pluginName;
+    for (pluginName in injectedNamesToPlugins)
+      if (injectedNamesToPlugins.hasOwnProperty(pluginName)) {
+        var pluginModule = injectedNamesToPlugins[pluginName];
+        (namesToPlugins.hasOwnProperty(pluginName) &&
+          namesToPlugins[pluginName] === pluginModule) ||
+          (invariant(
+            !namesToPlugins[pluginName],
+            "EventPluginRegistry: Cannot inject two different event plugins using the same name, `%s`.",
+            pluginName
+          ),
+          (namesToPlugins[pluginName] = pluginModule),
+          (isOrderingDirty = !0));
+      }
+    isOrderingDirty && recomputePluginOrdering();
+  }
+};
+function getListener(inst, registrationName) {
+  var listener = inst.stateNode;
+  if (!listener) return null;
+  var props = getFiberCurrentPropsFromNode(listener);
+  if (!props) return null;
+  listener = props[registrationName];
+  a: switch (registrationName) {
+    case "onClick":
+    case "onClickCapture":
+    case "onDoubleClick":
+    case "onDoubleClickCapture":
+    case "onMouseDown":
+    case "onMouseDownCapture":
+    case "onMouseMove":
+    case "onMouseMoveCapture":
+    case "onMouseUp":
+    case "onMouseUpCapture":
+      (props = !props.disabled) ||
+        ((inst = inst.type),
+        (props = !(
+          "button" === inst ||
+          "input" === inst ||
+          "select" === inst ||
+          "textarea" === inst
+        )));
+      inst = !props;
+      break a;
+    default:
+      inst = !1;
+  }
+  if (inst) return null;
+  invariant(
+    !listener || "function" === typeof listener,
+    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
+    registrationName,
+    typeof listener
+  );
+  return listener;
+}
+function getParent(inst) {
+  do inst = inst.return;
+  while (inst && 5 !== inst.tag);
+  return inst ? inst : null;
+}
+function traverseTwoPhase(inst, fn, arg) {
+  for (var path = []; inst; ) path.push(inst), (inst = getParent(inst));
+  for (inst = path.length; 0 < inst--; ) fn(path[inst], "captured", arg);
+  for (inst = 0; inst < path.length; inst++) fn(path[inst], "bubbled", arg);
+}
+function accumulateDirectionalDispatches(inst, phase, event) {
+  if (
+    (phase = getListener(
+      inst,
+      event.dispatchConfig.phasedRegistrationNames[phase]
+    ))
+  )
+    (event._dispatchListeners = accumulateInto(
+      event._dispatchListeners,
+      phase
+    )),
+      (event._dispatchInstances = accumulateInto(
+        event._dispatchInstances,
+        inst
+      ));
+}
+function accumulateTwoPhaseDispatchesSingle(event) {
+  event &&
+    event.dispatchConfig.phasedRegistrationNames &&
+    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
+}
+function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
+  if (event && event.dispatchConfig.phasedRegistrationNames) {
+    var targetInst = event._targetInst;
+    targetInst = targetInst ? getParent(targetInst) : null;
+    traverseTwoPhase(targetInst, accumulateDirectionalDispatches, event);
+  }
+}
+function accumulateDirectDispatchesSingle(event) {
+  if (event && event.dispatchConfig.registrationName) {
+    var inst = event._targetInst;
+    if (inst && event && event.dispatchConfig.registrationName) {
+      var listener = getListener(inst, event.dispatchConfig.registrationName);
+      listener &&
+        ((event._dispatchListeners = accumulateInto(
+          event._dispatchListeners,
+          listener
+        )),
+        (event._dispatchInstances = accumulateInto(
+          event._dispatchInstances,
+          inst
+        )));
+    }
+  }
+}
+var shouldBeReleasedProperties = "dispatchConfig _targetInst nativeEvent isDefaultPrevented isPropagationStopped _dispatchListeners _dispatchInstances".split(
+  " "
+);
+function functionThatReturnsTrue() {
+  return !0;
+}
+function functionThatReturnsFalse() {
+  return !1;
+}
+function SyntheticEvent(
+  dispatchConfig,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  this.dispatchConfig = dispatchConfig;
+  this._targetInst = targetInst;
+  this.nativeEvent = nativeEvent;
+  dispatchConfig = this.constructor.Interface;
+  for (var propName in dispatchConfig)
+    dispatchConfig.hasOwnProperty(propName) &&
+      ((targetInst = dispatchConfig[propName])
+        ? (this[propName] = targetInst(nativeEvent))
+        : "target" === propName
+          ? (this.target = nativeEventTarget)
+          : (this[propName] = nativeEvent[propName]));
+  this.isDefaultPrevented = (null != nativeEvent.defaultPrevented
+  ? nativeEvent.defaultPrevented
+  : !1 === nativeEvent.returnValue)
+    ? functionThatReturnsTrue
+    : functionThatReturnsFalse;
+  this.isPropagationStopped = functionThatReturnsFalse;
+  return this;
+}
+Object.assign(SyntheticEvent.prototype, {
+  preventDefault: function() {
+    this.defaultPrevented = !0;
+    var event = this.nativeEvent;
+    event &&
+      (event.preventDefault
+        ? event.preventDefault()
+        : "unknown" !== typeof event.returnValue && (event.returnValue = !1),
+      (this.isDefaultPrevented = functionThatReturnsTrue));
+  },
+  stopPropagation: function() {
+    var event = this.nativeEvent;
+    event &&
+      (event.stopPropagation
+        ? event.stopPropagation()
+        : "unknown" !== typeof event.cancelBubble && (event.cancelBubble = !0),
+      (this.isPropagationStopped = functionThatReturnsTrue));
+  },
+  persist: function() {
+    this.isPersistent = functionThatReturnsTrue;
+  },
+  isPersistent: functionThatReturnsFalse,
+  destructor: function() {
+    var Interface = this.constructor.Interface,
+      propName;
+    for (propName in Interface) this[propName] = null;
+    for (
+      Interface = 0;
+      Interface < shouldBeReleasedProperties.length;
+      Interface++
+    )
+      this[shouldBeReleasedProperties[Interface]] = null;
+  }
+});
+SyntheticEvent.Interface = {
+  type: null,
+  target: null,
+  currentTarget: function() {
+    return null;
+  },
+  eventPhase: null,
+  bubbles: null,
+  cancelable: null,
+  timeStamp: function(event) {
+    return event.timeStamp || Date.now();
+  },
+  defaultPrevented: null,
+  isTrusted: null
+};
+SyntheticEvent.extend = function(Interface) {
+  function E() {}
+  function Class() {
+    return Super.apply(this, arguments);
+  }
+  var Super = this;
+  E.prototype = Super.prototype;
+  var prototype = new E();
+  Object.assign(prototype, Class.prototype);
+  Class.prototype = prototype;
+  Class.prototype.constructor = Class;
+  Class.Interface = Object.assign({}, Super.Interface, Interface);
+  Class.extend = Super.extend;
+  addEventPoolingTo(Class);
+  return Class;
+};
+addEventPoolingTo(SyntheticEvent);
+function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
+  if (this.eventPool.length) {
+    var instance = this.eventPool.pop();
+    this.call(instance, dispatchConfig, targetInst, nativeEvent, nativeInst);
+    return instance;
+  }
+  return new this(dispatchConfig, targetInst, nativeEvent, nativeInst);
+}
+function releasePooledEvent(event) {
+  invariant(
+    event instanceof this,
+    "Trying to release an event instance  into a pool of a different type."
+  );
+  event.destructor();
+  10 > this.eventPool.length && this.eventPool.push(event);
+}
+function addEventPoolingTo(EventConstructor) {
+  EventConstructor.eventPool = [];
+  EventConstructor.getPooled = getPooledEvent;
+  EventConstructor.release = releasePooledEvent;
+}
+var ResponderSyntheticEvent = SyntheticEvent.extend({
+  touchHistory: function() {
+    return null;
+  }
+});
+function isStartish(topLevelType) {
+  return "topTouchStart" === topLevelType;
+}
+function isMoveish(topLevelType) {
+  return "topTouchMove" === topLevelType;
+}
+var startDependencies = ["topTouchStart"],
+  moveDependencies = ["topTouchMove"],
+  endDependencies = ["topTouchCancel", "topTouchEnd"],
+  touchBank = [],
+  touchHistory = {
+    touchBank: touchBank,
+    numberActiveTouches: 0,
+    indexOfSingleActiveTouch: -1,
+    mostRecentTimeStamp: 0
+  };
+function timestampForTouch(touch) {
+  return touch.timeStamp || touch.timestamp;
+}
+function getTouchIdentifier(_ref) {
+  _ref = _ref.identifier;
+  invariant(null != _ref, "Touch object is missing identifier.");
+  return _ref;
+}
+function recordTouchStart(touch) {
+  var identifier = getTouchIdentifier(touch),
+    touchRecord = touchBank[identifier];
+  touchRecord
+    ? ((touchRecord.touchActive = !0),
+      (touchRecord.startPageX = touch.pageX),
+      (touchRecord.startPageY = touch.pageY),
+      (touchRecord.startTimeStamp = timestampForTouch(touch)),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchRecord.previousPageX = touch.pageX),
+      (touchRecord.previousPageY = touch.pageY),
+      (touchRecord.previousTimeStamp = timestampForTouch(touch)))
+    : ((touchRecord = {
+        touchActive: !0,
+        startPageX: touch.pageX,
+        startPageY: touch.pageY,
+        startTimeStamp: timestampForTouch(touch),
+        currentPageX: touch.pageX,
+        currentPageY: touch.pageY,
+        currentTimeStamp: timestampForTouch(touch),
+        previousPageX: touch.pageX,
+        previousPageY: touch.pageY,
+        previousTimeStamp: timestampForTouch(touch)
+      }),
+      (touchBank[identifier] = touchRecord));
+  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+}
+function recordTouchMove(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  touchRecord
+    ? ((touchRecord.touchActive = !0),
+      (touchRecord.previousPageX = touchRecord.currentPageX),
+      (touchRecord.previousPageY = touchRecord.currentPageY),
+      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
+    : console.error(
+        "Cannot record touch move without a touch start.\nTouch Move: %s\n",
+        "Touch Bank: %s",
+        printTouch(touch),
+        printTouchBank()
+      );
+}
+function recordTouchEnd(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  touchRecord
+    ? ((touchRecord.touchActive = !1),
+      (touchRecord.previousPageX = touchRecord.currentPageX),
+      (touchRecord.previousPageY = touchRecord.currentPageY),
+      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
+    : console.error(
+        "Cannot record touch end without a touch start.\nTouch End: %s\n",
+        "Touch Bank: %s",
+        printTouch(touch),
+        printTouchBank()
+      );
+}
+function printTouch(touch) {
+  return JSON.stringify({
+    identifier: touch.identifier,
+    pageX: touch.pageX,
+    pageY: touch.pageY,
+    timestamp: timestampForTouch(touch)
+  });
+}
+function printTouchBank() {
+  var printed = JSON.stringify(touchBank.slice(0, 20));
+  20 < touchBank.length &&
+    (printed += " (original size: " + touchBank.length + ")");
+  return printed;
+}
+var ResponderTouchHistoryStore = {
+  recordTouchTrack: function(topLevelType, nativeEvent) {
+    if (isMoveish(topLevelType))
+      nativeEvent.changedTouches.forEach(recordTouchMove);
+    else if (isStartish(topLevelType))
+      nativeEvent.changedTouches.forEach(recordTouchStart),
+        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+        1 === touchHistory.numberActiveTouches &&
+          (touchHistory.indexOfSingleActiveTouch =
+            nativeEvent.touches[0].identifier);
+    else if (
+      "topTouchEnd" === topLevelType ||
+      "topTouchCancel" === topLevelType
+    )
+      if (
+        (nativeEvent.changedTouches.forEach(recordTouchEnd),
+        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+        1 === touchHistory.numberActiveTouches)
+      )
+        for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
+          if (
+            ((nativeEvent = touchBank[topLevelType]),
+            null != nativeEvent && nativeEvent.touchActive)
+          ) {
+            touchHistory.indexOfSingleActiveTouch = topLevelType;
+            break;
+          }
+  },
+  touchHistory: touchHistory
+};
+function accumulate(current, next) {
+  invariant(
+    null != next,
+    "accumulate(...): Accumulated items must be not be null or undefined."
+  );
+  return null == current
+    ? next
+    : Array.isArray(current)
+      ? current.concat(next)
+      : Array.isArray(next) ? [current].concat(next) : [current, next];
+}
+var responderInst = null,
+  trackedTouchCount = 0;
+function changeResponder(nextResponderInst, blockHostResponder) {
+  var oldResponderInst = responderInst;
+  responderInst = nextResponderInst;
+  if (null !== ResponderEventPlugin.GlobalResponderHandler)
+    ResponderEventPlugin.GlobalResponderHandler.onChange(
+      oldResponderInst,
+      nextResponderInst,
+      blockHostResponder
+    );
+}
+var eventTypes$1 = {
+    startShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onStartShouldSetResponder",
+        captured: "onStartShouldSetResponderCapture"
+      },
+      dependencies: startDependencies
+    },
+    scrollShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onScrollShouldSetResponder",
+        captured: "onScrollShouldSetResponderCapture"
+      },
+      dependencies: ["topScroll"]
+    },
+    selectionChangeShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onSelectionChangeShouldSetResponder",
+        captured: "onSelectionChangeShouldSetResponderCapture"
+      },
+      dependencies: ["topSelectionChange"]
+    },
+    moveShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onMoveShouldSetResponder",
+        captured: "onMoveShouldSetResponderCapture"
+      },
+      dependencies: moveDependencies
+    },
+    responderStart: {
+      registrationName: "onResponderStart",
+      dependencies: startDependencies
+    },
+    responderMove: {
+      registrationName: "onResponderMove",
+      dependencies: moveDependencies
+    },
+    responderEnd: {
+      registrationName: "onResponderEnd",
+      dependencies: endDependencies
+    },
+    responderRelease: {
+      registrationName: "onResponderRelease",
+      dependencies: endDependencies
+    },
+    responderTerminationRequest: {
+      registrationName: "onResponderTerminationRequest",
+      dependencies: []
+    },
+    responderGrant: { registrationName: "onResponderGrant", dependencies: [] },
+    responderReject: {
+      registrationName: "onResponderReject",
+      dependencies: []
+    },
+    responderTerminate: {
+      registrationName: "onResponderTerminate",
+      dependencies: []
+    }
+  },
+  ResponderEventPlugin = {
+    _getResponder: function() {
+      return responderInst;
+    },
+    eventTypes: eventTypes$1,
+    extractEvents: function(
+      topLevelType,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    ) {
+      if (isStartish(topLevelType)) trackedTouchCount += 1;
+      else if (
+        "topTouchEnd" === topLevelType ||
+        "topTouchCancel" === topLevelType
+      )
+        if (0 <= trackedTouchCount) --trackedTouchCount;
+        else
+          return (
+            console.error(
+              "Ended a touch event which was not counted in `trackedTouchCount`."
+            ),
+            null
+          );
+      ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
+      if (
+        targetInst &&
+        (("topScroll" === topLevelType && !nativeEvent.responderIgnoreScroll) ||
+          (0 < trackedTouchCount && "topSelectionChange" === topLevelType) ||
+          isStartish(topLevelType) ||
+          isMoveish(topLevelType))
+      ) {
+        var JSCompiler_temp = isStartish(topLevelType)
+          ? eventTypes$1.startShouldSetResponder
+          : isMoveish(topLevelType)
+            ? eventTypes$1.moveShouldSetResponder
+            : "topSelectionChange" === topLevelType
+              ? eventTypes$1.selectionChangeShouldSetResponder
+              : eventTypes$1.scrollShouldSetResponder;
+        if (responderInst)
+          b: {
+            var JSCompiler_temp$jscomp$0 = responderInst;
+            for (
+              var depthA = 0, tempA = JSCompiler_temp$jscomp$0;
+              tempA;
+              tempA = getParent(tempA)
+            )
+              depthA++;
+            tempA = 0;
+            for (var tempB = targetInst; tempB; tempB = getParent(tempB))
+              tempA++;
+            for (; 0 < depthA - tempA; )
+              (JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0)),
+                depthA--;
+            for (; 0 < tempA - depthA; )
+              (targetInst = getParent(targetInst)), tempA--;
+            for (; depthA--; ) {
+              if (
+                JSCompiler_temp$jscomp$0 === targetInst ||
+                JSCompiler_temp$jscomp$0 === targetInst.alternate
+              )
+                break b;
+              JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0);
+              targetInst = getParent(targetInst);
+            }
+            JSCompiler_temp$jscomp$0 = null;
+          }
+        else JSCompiler_temp$jscomp$0 = targetInst;
+        targetInst = JSCompiler_temp$jscomp$0 === responderInst;
+        JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
+          JSCompiler_temp,
+          JSCompiler_temp$jscomp$0,
+          nativeEvent,
+          nativeEventTarget
+        );
+        JSCompiler_temp$jscomp$0.touchHistory =
+          ResponderTouchHistoryStore.touchHistory;
+        targetInst
+          ? forEachAccumulated(
+              JSCompiler_temp$jscomp$0,
+              accumulateTwoPhaseDispatchesSingleSkipTarget
+            )
+          : forEachAccumulated(
+              JSCompiler_temp$jscomp$0,
+              accumulateTwoPhaseDispatchesSingle
+            );
+        b: {
+          JSCompiler_temp = JSCompiler_temp$jscomp$0._dispatchListeners;
+          targetInst = JSCompiler_temp$jscomp$0._dispatchInstances;
+          if (Array.isArray(JSCompiler_temp))
+            for (
+              depthA = 0;
+              depthA < JSCompiler_temp.length &&
+              !JSCompiler_temp$jscomp$0.isPropagationStopped();
+              depthA++
+            ) {
+              if (
+                JSCompiler_temp[depthA](
+                  JSCompiler_temp$jscomp$0,
+                  targetInst[depthA]
+                )
+              ) {
+                JSCompiler_temp = targetInst[depthA];
+                break b;
+              }
+            }
+          else if (
+            JSCompiler_temp &&
+            JSCompiler_temp(JSCompiler_temp$jscomp$0, targetInst)
+          ) {
+            JSCompiler_temp = targetInst;
+            break b;
+          }
+          JSCompiler_temp = null;
+        }
+        JSCompiler_temp$jscomp$0._dispatchInstances = null;
+        JSCompiler_temp$jscomp$0._dispatchListeners = null;
+        JSCompiler_temp$jscomp$0.isPersistent() ||
+          JSCompiler_temp$jscomp$0.constructor.release(
+            JSCompiler_temp$jscomp$0
+          );
+        JSCompiler_temp && JSCompiler_temp !== responderInst
+          ? ((JSCompiler_temp$jscomp$0 = void 0),
+            (targetInst = ResponderSyntheticEvent.getPooled(
+              eventTypes$1.responderGrant,
+              JSCompiler_temp,
+              nativeEvent,
+              nativeEventTarget
+            )),
+            (targetInst.touchHistory = ResponderTouchHistoryStore.touchHistory),
+            forEachAccumulated(targetInst, accumulateDirectDispatchesSingle),
+            (depthA = !0 === executeDirectDispatch(targetInst)),
+            responderInst
+              ? ((tempA = ResponderSyntheticEvent.getPooled(
+                  eventTypes$1.responderTerminationRequest,
+                  responderInst,
+                  nativeEvent,
+                  nativeEventTarget
+                )),
+                (tempA.touchHistory = ResponderTouchHistoryStore.touchHistory),
+                forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
+                (tempB =
+                  !tempA._dispatchListeners || executeDirectDispatch(tempA)),
+                tempA.isPersistent() || tempA.constructor.release(tempA),
+                tempB
+                  ? ((tempA = ResponderSyntheticEvent.getPooled(
+                      eventTypes$1.responderTerminate,
+                      responderInst,
+                      nativeEvent,
+                      nativeEventTarget
+                    )),
+                    (tempA.touchHistory =
+                      ResponderTouchHistoryStore.touchHistory),
+                    forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
+                    (JSCompiler_temp$jscomp$0 = accumulate(
+                      JSCompiler_temp$jscomp$0,
+                      [targetInst, tempA]
+                    )),
+                    changeResponder(JSCompiler_temp, depthA))
+                  : ((JSCompiler_temp = ResponderSyntheticEvent.getPooled(
+                      eventTypes$1.responderReject,
+                      JSCompiler_temp,
+                      nativeEvent,
+                      nativeEventTarget
+                    )),
+                    (JSCompiler_temp.touchHistory =
+                      ResponderTouchHistoryStore.touchHistory),
+                    forEachAccumulated(
+                      JSCompiler_temp,
+                      accumulateDirectDispatchesSingle
+                    ),
+                    (JSCompiler_temp$jscomp$0 = accumulate(
+                      JSCompiler_temp$jscomp$0,
+                      JSCompiler_temp
+                    ))))
+              : ((JSCompiler_temp$jscomp$0 = accumulate(
+                  JSCompiler_temp$jscomp$0,
+                  targetInst
+                )),
+                changeResponder(JSCompiler_temp, depthA)),
+            (JSCompiler_temp = JSCompiler_temp$jscomp$0))
+          : (JSCompiler_temp = null);
+      } else JSCompiler_temp = null;
+      JSCompiler_temp$jscomp$0 = responderInst && isStartish(topLevelType);
+      targetInst = responderInst && isMoveish(topLevelType);
+      depthA =
+        responderInst &&
+        ("topTouchEnd" === topLevelType || "topTouchCancel" === topLevelType);
+      if (
+        (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
+          ? eventTypes$1.responderStart
+          : targetInst
+            ? eventTypes$1.responderMove
+            : depthA ? eventTypes$1.responderEnd : null)
+      )
+        (JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
+          JSCompiler_temp$jscomp$0,
+          responderInst,
+          nativeEvent,
+          nativeEventTarget
+        )),
+          (JSCompiler_temp$jscomp$0.touchHistory =
+            ResponderTouchHistoryStore.touchHistory),
+          forEachAccumulated(
+            JSCompiler_temp$jscomp$0,
+            accumulateDirectDispatchesSingle
+          ),
+          (JSCompiler_temp = accumulate(
+            JSCompiler_temp,
+            JSCompiler_temp$jscomp$0
+          ));
+      JSCompiler_temp$jscomp$0 =
+        responderInst && "topTouchCancel" === topLevelType;
+      if (
+        (topLevelType =
+          responderInst &&
+          !JSCompiler_temp$jscomp$0 &&
+          ("topTouchEnd" === topLevelType || "topTouchCancel" === topLevelType))
+      )
+        a: {
+          if ((topLevelType = nativeEvent.touches) && 0 !== topLevelType.length)
+            for (targetInst = 0; targetInst < topLevelType.length; targetInst++)
+              if (
+                ((depthA = topLevelType[targetInst].target),
+                null !== depthA && void 0 !== depthA && 0 !== depthA)
+              ) {
+                tempA = getInstanceFromNode(depthA);
+                b: {
+                  for (depthA = responderInst; tempA; ) {
+                    if (depthA === tempA || depthA === tempA.alternate) {
+                      depthA = !0;
+                      break b;
+                    }
+                    tempA = getParent(tempA);
+                  }
+                  depthA = !1;
+                }
+                if (depthA) {
+                  topLevelType = !1;
+                  break a;
+                }
+              }
+          topLevelType = !0;
+        }
+      if (
+        (topLevelType = JSCompiler_temp$jscomp$0
+          ? eventTypes$1.responderTerminate
+          : topLevelType ? eventTypes$1.responderRelease : null)
+      )
+        (nativeEvent = ResponderSyntheticEvent.getPooled(
+          topLevelType,
+          responderInst,
+          nativeEvent,
+          nativeEventTarget
+        )),
+          (nativeEvent.touchHistory = ResponderTouchHistoryStore.touchHistory),
+          forEachAccumulated(nativeEvent, accumulateDirectDispatchesSingle),
+          (JSCompiler_temp = accumulate(JSCompiler_temp, nativeEvent)),
+          changeResponder(null);
+      return JSCompiler_temp;
+    },
+    GlobalResponderHandler: null,
+    injection: {
+      injectGlobalResponderHandler: function(GlobalResponderHandler) {
+        ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
+      }
+    }
+  },
+  customBubblingEventTypes$1 =
+    ReactNativeViewConfigRegistry.customBubblingEventTypes,
+  customDirectEventTypes$1 =
+    ReactNativeViewConfigRegistry.customDirectEventTypes,
+  ReactNativeBridgeEventPlugin = {
+    eventTypes: ReactNativeViewConfigRegistry.eventTypes,
+    extractEvents: function(
+      topLevelType,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    ) {
+      if (null == targetInst) return null;
+      var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType],
+        directDispatchConfig = customDirectEventTypes$1[topLevelType];
+      invariant(
+        bubbleDispatchConfig || directDispatchConfig,
+        'Unsupported top level event type "%s" dispatched',
+        topLevelType
+      );
+      topLevelType = SyntheticEvent.getPooled(
+        bubbleDispatchConfig || directDispatchConfig,
+        targetInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      if (bubbleDispatchConfig)
+        forEachAccumulated(topLevelType, accumulateTwoPhaseDispatchesSingle);
+      else if (directDispatchConfig)
+        forEachAccumulated(topLevelType, accumulateDirectDispatchesSingle);
+      else return null;
+      return topLevelType;
+    }
+  };
+injection.injectEventPluginOrder([
+  "ResponderEventPlugin",
+  "ReactNativeBridgeEventPlugin"
+]);
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
+function getInstanceFromInstance(instanceHandle) {
+  return instanceHandle;
+}
+var Injected$jscomp$inline_574 = {
+  getClosestInstanceFromNode: getInstanceFromInstance,
+  getInstanceFromNode: getInstanceFromInstance,
+  getNodeFromInstance: function(inst) {
+    inst = inst.stateNode.canonical._nativeTag;
+    invariant(inst, "All native instances should have a tag.");
+    return inst;
+  },
+  getFiberCurrentPropsFromNode: function(inst) {
+    return inst.canonical.currentProps;
+  }
+};
+getFiberCurrentPropsFromNode =
+  Injected$jscomp$inline_574.getFiberCurrentPropsFromNode;
+getInstanceFromNode = Injected$jscomp$inline_574.getInstanceFromNode;
+getNodeFromInstance = Injected$jscomp$inline_574.getNodeFromInstance;
+ResponderEventPlugin.injection.injectGlobalResponderHandler({
+  onChange: function(from, to, blockNativeResponder) {
+    null !== to
+      ? UIManager.setJSResponder(
+          to.stateNode.canonical._nativeTag,
+          blockNativeResponder
+        )
+      : UIManager.clearJSResponder();
+  }
+});
+var ReactCurrentOwner =
+    React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner,
+  hasSymbol = "function" === typeof Symbol && Symbol.for,
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
+  REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profiler") : 60114,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for("react.forward_ref") : 60112,
+  REACT_TIMEOUT_TYPE = hasSymbol ? Symbol.for("react.timeout") : 60113,
+  MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
+function getIteratorFn(maybeIterable) {
+  if (null === maybeIterable || "undefined" === typeof maybeIterable)
+    return null;
+  maybeIterable =
+    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
+    maybeIterable["@@iterator"];
+  return "function" === typeof maybeIterable ? maybeIterable : null;
+}
+function getComponentName(fiber) {
+  var type = fiber.type;
+  if ("function" === typeof type) return type.displayName || type.name;
+  if ("string" === typeof type) return type;
+  switch (type) {
+    case REACT_ASYNC_MODE_TYPE:
+      return "AsyncMode";
+    case REACT_CONTEXT_TYPE:
+      return "Context.Consumer";
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_PROFILER_TYPE:
+      return "Profiler(" + fiber.pendingProps.id + ")";
+    case REACT_PROVIDER_TYPE:
+      return "Context.Provider";
+    case REACT_STRICT_MODE_TYPE:
+      return "StrictMode";
+    case REACT_TIMEOUT_TYPE:
+      return "Timeout";
+  }
+  if ("object" === typeof type && null !== type)
+    switch (type.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        return (
+          (fiber = type.render.displayName || type.render.name || ""),
+          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
+        );
+    }
+  return null;
+}
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (fiber.alternate) for (; node.return; ) node = node.return;
+  else {
+    if (0 !== (node.effectTag & 2)) return 1;
+    for (; node.return; )
+      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
+  }
+  return 3 === node.tag ? 2 : 3;
+}
+function assertIsMounted(fiber) {
+  invariant(
+    2 === isFiberMountedImpl(fiber),
+    "Unable to find node on an unmounted component."
+  );
+}
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate)
+    return (
+      (alternate = isFiberMountedImpl(fiber)),
+      invariant(
+        3 !== alternate,
+        "Unable to find node on an unmounted component."
+      ),
+      1 === alternate ? null : fiber
+    );
+  for (var a = fiber, b = alternate; ; ) {
+    var parentA = a.return,
+      parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) break;
+    if (parentA.child === parentB.child) {
+      for (var child = parentA.child; child; ) {
+        if (child === a) return assertIsMounted(parentA), fiber;
+        if (child === b) return assertIsMounted(parentA), alternate;
+        child = child.sibling;
+      }
+      invariant(!1, "Unable to find node on an unmounted component.");
+    }
+    if (a.return !== b.return) (a = parentA), (b = parentB);
+    else {
+      child = !1;
+      for (var _child = parentA.child; _child; ) {
+        if (_child === a) {
+          child = !0;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          child = !0;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!child) {
+        for (_child = parentB.child; _child; ) {
+          if (_child === a) {
+            child = !0;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            child = !0;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          child,
+          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
+        );
+      }
+    }
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
+  return a.stateNode.current === a ? fiber : alternate;
+}
+function findCurrentHostFiber(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child) (node.child.return = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+  return null;
+}
+function findCurrentHostFiberWithNoPortals(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child && 4 !== node.tag)
+      (node.child.return = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+  return null;
+}
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (callback) {
+      if ("boolean" === typeof context.__isMounted) {
+        if (!context.__isMounted) return;
+      } else if (
+        "function" === typeof context.isMounted &&
+        !context.isMounted()
+      )
+        return;
+      return callback.apply(context, arguments);
+    }
+  };
+}
+var emptyObject$1 = {},
+  removedKeys = null,
+  removedKeyCount = 0;
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node))
+    for (var i = node.length; i-- && 0 < removedKeyCount; )
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+  else if (node && 0 < removedKeyCount)
+    for (i in removedKeys)
+      if (removedKeys[i]) {
+        var _nextProp = node[i];
+        if (void 0 !== _nextProp) {
+          var attributeConfig = validAttributes[i];
+          if (attributeConfig) {
+            "function" === typeof _nextProp && (_nextProp = !0);
+            "undefined" === typeof _nextProp && (_nextProp = null);
+            if ("object" !== typeof attributeConfig)
+              updatePayload[i] = _nextProp;
+            else if (
+              "function" === typeof attributeConfig.diff ||
+              "function" === typeof attributeConfig.process
+            )
+              (_nextProp =
+                "function" === typeof attributeConfig.process
+                  ? attributeConfig.process(_nextProp)
+                  : _nextProp),
+                (updatePayload[i] = _nextProp);
+            removedKeys[i] = !1;
+            removedKeyCount--;
+          }
+        }
+      }
+}
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) return updatePayload;
+  if (!prevProp || !nextProp)
+    return nextProp
+      ? addNestedProperty(updatePayload, nextProp, validAttributes)
+      : prevProp
+        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
+        : updatePayload;
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    var minLength =
+        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
+      i;
+    for (i = 0; i < minLength; i++)
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp[i],
+        nextProp[i],
+        validAttributes
+      );
+    for (; i < prevProp.length; i++)
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp[i],
+        validAttributes
+      );
+    for (; i < nextProp.length; i++)
+      updatePayload = addNestedProperty(
+        updatePayload,
+        nextProp[i],
+        validAttributes
+      );
+    return updatePayload;
+  }
+  return Array.isArray(prevProp)
+    ? diffProperties(
+        updatePayload,
+        flattenStyle(prevProp),
+        nextProp,
+        validAttributes
+      )
+    : diffProperties(
+        updatePayload,
+        prevProp,
+        flattenStyle(nextProp),
+        validAttributes
+      );
+}
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) return updatePayload;
+  if (!Array.isArray(nextProp))
+    return diffProperties(
+      updatePayload,
+      emptyObject$1,
+      nextProp,
+      validAttributes
+    );
+  for (var i = 0; i < nextProp.length; i++)
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) return updatePayload;
+  if (!Array.isArray(prevProp))
+    return diffProperties(
+      updatePayload,
+      prevProp,
+      emptyObject$1,
+      validAttributes
+    );
+  for (var i = 0; i < prevProp.length; i++)
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig, propKey;
+  for (propKey in nextProps)
+    if ((attributeConfig = validAttributes[propKey])) {
+      var prevProp = prevProps[propKey];
+      var nextProp = nextProps[propKey];
+      "function" === typeof nextProp &&
+        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
+      "undefined" === typeof nextProp &&
+        ((nextProp = null),
+        "undefined" === typeof prevProp && (prevProp = null));
+      removedKeys && (removedKeys[propKey] = !1);
+      if (updatePayload && void 0 !== updatePayload[propKey])
+        if ("object" !== typeof attributeConfig)
+          updatePayload[propKey] = nextProp;
+        else {
+          if (
+            "function" === typeof attributeConfig.diff ||
+            "function" === typeof attributeConfig.process
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              (updatePayload[propKey] = attributeConfig);
+        }
+      else if (prevProp !== nextProp)
+        if ("object" !== typeof attributeConfig)
+          ("object" !== typeof nextProp ||
+            null === nextProp ||
+            deepDiffer(prevProp, nextProp)) &&
+            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
+        else if (
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+        ) {
+          if (
+            void 0 === prevProp ||
+            ("function" === typeof attributeConfig.diff
+              ? attributeConfig.diff(prevProp, nextProp)
+              : "object" !== typeof nextProp ||
+                null === nextProp ||
+                deepDiffer(prevProp, nextProp))
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              ((updatePayload || (updatePayload = {}))[
+                propKey
+              ] = attributeConfig);
+        } else
+          (removedKeys = null),
+            (removedKeyCount = 0),
+            (updatePayload = diffNestedProperty(
+              updatePayload,
+              prevProp,
+              nextProp,
+              attributeConfig
+            )),
+            0 < removedKeyCount &&
+              updatePayload &&
+              (restoreDeletedValuesInNestedArray(
+                updatePayload,
+                nextProp,
+                attributeConfig
+              ),
+              (removedKeys = null));
+    }
+  for (var _propKey in prevProps)
+    void 0 === nextProps[_propKey] &&
+      (!(attributeConfig = validAttributes[_propKey]) ||
+        (updatePayload && void 0 !== updatePayload[_propKey]) ||
+        ((prevProp = prevProps[_propKey]),
+        void 0 !== prevProp &&
+          ("object" !== typeof attributeConfig ||
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
+              removedKeys || (removedKeys = {}),
+              removedKeys[_propKey] ||
+                ((removedKeys[_propKey] = !0), removedKeyCount++))
+            : (updatePayload = clearNestedProperty(
+                updatePayload,
+                prevProp,
+                attributeConfig
+              )))));
+  return updatePayload;
+}
+var now$1 =
+    "object" === typeof performance && "function" === typeof performance.now
+      ? function() {
+          return performance.now();
+        }
+      : function() {
+          return Date.now();
+        },
+  scheduledCallback = null,
+  frameDeadline = 0,
+  frameDeadlineObject = {
+    timeRemaining: function() {
+      return frameDeadline - now$1();
+    },
+    didTimeout: !1
+  };
+function setTimeoutCallback() {
+  frameDeadline = now$1() + 5;
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  null !== callback && callback(frameDeadlineObject);
+}
+var restoreTarget = null,
+  restoreQueue = null;
+function restoreStateOfTarget(target) {
+  if ((target = getInstanceFromNode(target))) {
+    invariant(
+      null,
+      "Fiber needs to be injected to handle a fiber target for controlled events. This error is likely caused by a bug in React. Please file an issue."
+    );
+    var props = getFiberCurrentPropsFromNode(target.stateNode);
+    null.restoreControlledState(target.stateNode, target.type, props);
+  }
+}
+function _batchedUpdates(fn, bookkeeping) {
+  return fn(bookkeeping);
+}
+function _flushInteractiveUpdates() {}
+var isBatching = !1;
+function batchedUpdates(fn, bookkeeping) {
+  if (isBatching) return fn(bookkeeping);
+  isBatching = !0;
+  try {
+    return _batchedUpdates(fn, bookkeeping);
+  } finally {
+    if (((isBatching = !1), null !== restoreTarget || null !== restoreQueue))
+      if (
+        (_flushInteractiveUpdates(),
+        restoreTarget &&
+          ((bookkeeping = restoreTarget),
+          (fn = restoreQueue),
+          (restoreQueue = restoreTarget = null),
+          restoreStateOfTarget(bookkeeping),
+          fn))
+      )
+        for (bookkeeping = 0; bookkeeping < fn.length; bookkeeping++)
+          restoreStateOfTarget(fn[bookkeeping]);
+  }
+}
+function dispatchEvent(target, topLevelType, nativeEvent) {
+  batchedUpdates(function() {
+    var events = nativeEvent.target;
+    for (var events$jscomp$0 = null, i = 0; i < plugins.length; i++) {
+      var possiblePlugin = plugins[i];
+      possiblePlugin &&
+        (possiblePlugin = possiblePlugin.extractEvents(
+          topLevelType,
+          target,
+          nativeEvent,
+          events
+        )) &&
+        (events$jscomp$0 = accumulateInto(events$jscomp$0, possiblePlugin));
+    }
+    events = events$jscomp$0;
+    null !== events && (eventQueue = accumulateInto(eventQueue, events));
+    events = eventQueue;
+    eventQueue = null;
+    events &&
+      (forEachAccumulated(events, executeDispatchesAndReleaseTopLevel),
+      invariant(
+        !eventQueue,
+        "processEventQueue(): Additional events were enqueued while processing an event queue. Support for this has not yet been implemented."
+      ),
+      ReactErrorUtils.rethrowCaughtError());
+  });
+}
+function shim$1() {
+  invariant(
+    !1,
+    "The current renderer does not support hyration. This error is likely caused by a bug in React. Please file an issue."
+  );
+}
+var nextReactTag = 2;
+FabricUIManager.registerEventHandler &&
+  FabricUIManager.registerEventHandler(dispatchEvent);
+var ReactFabricHostComponent = (function() {
+  function ReactFabricHostComponent(tag, viewConfig, props) {
+    if (!(this instanceof ReactFabricHostComponent))
+      throw new TypeError("Cannot call a class as a function");
+    this._nativeTag = tag;
+    this.viewConfig = viewConfig;
+    this.currentProps = props;
+  }
+  ReactFabricHostComponent.prototype.blur = function() {
+    TextInputState.blurTextInput(this._nativeTag);
+  };
+  ReactFabricHostComponent.prototype.focus = function() {
+    TextInputState.focusTextInput(this._nativeTag);
+  };
+  ReactFabricHostComponent.prototype.measure = function(callback) {
+    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+  };
+  ReactFabricHostComponent.prototype.measureInWindow = function(callback) {
+    UIManager.measureInWindow(
+      this._nativeTag,
+      mountSafeCallback(this, callback)
+    );
+  };
+  ReactFabricHostComponent.prototype.measureLayout = function(
+    relativeToNativeNode,
+    onSuccess,
+    onFail
+  ) {
+    UIManager.measureLayout(
+      this._nativeTag,
+      relativeToNativeNode,
+      mountSafeCallback(this, onFail),
+      mountSafeCallback(this, onSuccess)
+    );
+  };
+  ReactFabricHostComponent.prototype.setNativeProps = function(nativeProps) {
+    nativeProps = diffProperties(
+      null,
+      emptyObject$1,
+      nativeProps,
+      this.viewConfig.validAttributes
+    );
+    null != nativeProps &&
+      UIManager.updateView(
+        this._nativeTag,
+        this.viewConfig.uiViewClassName,
+        nativeProps
+      );
+  };
+  return ReactFabricHostComponent;
+})();
+function createTextInstance(
+  text,
+  rootContainerInstance,
+  hostContext,
+  internalInstanceHandle
+) {
+  invariant(
+    hostContext.isInAParentText,
+    "Text strings must be rendered within a <Text> component."
+  );
+  hostContext = nextReactTag;
+  nextReactTag += 2;
+  return {
+    node: FabricUIManager.createNode(
+      hostContext,
+      "RCTRawText",
+      rootContainerInstance,
+      { text: text },
+      internalInstanceHandle
+    )
+  };
+}
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
+    }
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress.return;
+  } while (workInProgress);
+  return info;
+}
+new Set();
+var valueStack = [],
+  index = -1;
+function createCursor(defaultValue) {
+  return { current: defaultValue };
+}
+function pop(cursor) {
+  0 > index ||
+    ((cursor.current = valueStack[index]), (valueStack[index] = null), index--);
+}
+function push(cursor, value) {
+  index++;
+  valueStack[index] = cursor.current;
+  cursor.current = value;
+}
+var contextStackCursor = createCursor(emptyObject),
+  didPerformWorkStackCursor = createCursor(!1),
+  previousContext = emptyObject;
+function getUnmaskedContext(workInProgress) {
+  return isContextProvider(workInProgress)
+    ? previousContext
+    : contextStackCursor.current;
+}
+function getMaskedContext(workInProgress, unmaskedContext) {
+  var contextTypes = workInProgress.type.contextTypes;
+  if (!contextTypes) return emptyObject;
+  var instance = workInProgress.stateNode;
+  if (
+    instance &&
+    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+  )
+    return instance.__reactInternalMemoizedMaskedChildContext;
+  var context = {},
+    key;
+  for (key in contextTypes) context[key] = unmaskedContext[key];
+  instance &&
+    ((workInProgress = workInProgress.stateNode),
+    (workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext),
+    (workInProgress.__reactInternalMemoizedMaskedChildContext = context));
+  return context;
+}
+function isContextProvider(fiber) {
+  return 2 === fiber.tag && null != fiber.type.childContextTypes;
+}
+function popContextProvider(fiber) {
+  isContextProvider(fiber) &&
+    (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
+}
+function popTopLevelContextObject(fiber) {
+  pop(didPerformWorkStackCursor, fiber);
+  pop(contextStackCursor, fiber);
+}
+function pushTopLevelContextObject(fiber, context, didChange) {
+  invariant(
+    contextStackCursor.current === emptyObject,
+    "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
+  );
+  push(contextStackCursor, context, fiber);
+  push(didPerformWorkStackCursor, didChange, fiber);
+}
+function processChildContext(fiber, parentContext) {
+  var instance = fiber.stateNode,
+    childContextTypes = fiber.type.childContextTypes;
+  if ("function" !== typeof instance.getChildContext) return parentContext;
+  instance = instance.getChildContext();
+  for (var contextKey in instance)
+    invariant(
+      contextKey in childContextTypes,
+      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+      getComponentName(fiber) || "Unknown",
+      contextKey
+    );
+  return Object.assign({}, parentContext, instance);
+}
+function pushContextProvider(workInProgress) {
+  if (!isContextProvider(workInProgress)) return !1;
+  var instance = workInProgress.stateNode;
+  instance =
+    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+    emptyObject;
+  previousContext = contextStackCursor.current;
+  push(contextStackCursor, instance, workInProgress);
+  push(
+    didPerformWorkStackCursor,
+    didPerformWorkStackCursor.current,
+    workInProgress
+  );
+  return !0;
+}
+function invalidateContextProvider(workInProgress, didChange) {
+  var instance = workInProgress.stateNode;
+  invariant(
+    instance,
+    "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+  );
+  if (didChange) {
+    var mergedContext = processChildContext(workInProgress, previousContext);
+    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+    pop(didPerformWorkStackCursor, workInProgress);
+    pop(contextStackCursor, workInProgress);
+    push(contextStackCursor, mergedContext, workInProgress);
+  } else pop(didPerformWorkStackCursor, workInProgress);
+  push(didPerformWorkStackCursor, didChange, workInProgress);
+}
+function FiberNode(tag, pendingProps, key, mode) {
+  this.tag = tag;
+  this.key = key;
+  this.sibling = this.child = this.return = this.stateNode = this.type = null;
+  this.index = 0;
+  this.ref = null;
+  this.pendingProps = pendingProps;
+  this.memoizedState = this.updateQueue = this.memoizedProps = null;
+  this.mode = mode;
+  this.effectTag = 0;
+  this.lastEffect = this.firstEffect = this.nextEffect = null;
+  this.expirationTime = 0;
+  this.alternate = null;
+  this.treeBaseTime = this.selfBaseTime = this.actualStartTime = this.actualDuration = 0;
+}
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  null === workInProgress
+    ? ((workInProgress = new FiberNode(
+        current.tag,
+        pendingProps,
+        current.key,
+        current.mode
+      )),
+      (workInProgress.type = current.type),
+      (workInProgress.stateNode = current.stateNode),
+      (workInProgress.alternate = current),
+      (current.alternate = workInProgress))
+    : ((workInProgress.pendingProps = pendingProps),
+      (workInProgress.effectTag = 0),
+      (workInProgress.nextEffect = null),
+      (workInProgress.firstEffect = null),
+      (workInProgress.lastEffect = null),
+      (workInProgress.actualDuration = 0),
+      (workInProgress.actualStartTime = 0));
+  workInProgress.expirationTime = expirationTime;
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+  workInProgress.selfBaseTime = current.selfBaseTime;
+  workInProgress.treeBaseTime = current.treeBaseTime;
+  return workInProgress;
+}
+function createFiberFromElement(element, mode, expirationTime) {
+  var type = element.type,
+    key = element.key;
+  element = element.props;
+  if ("function" === typeof type)
+    var fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
+  else if ("string" === typeof type) fiberTag = 5;
+  else
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          element.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 3;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 2;
+        break;
+      case REACT_PROFILER_TYPE:
+        return (
+          (type = new FiberNode(15, element, key, mode | 4)),
+          (type.type = REACT_PROFILER_TYPE),
+          (type.expirationTime = expirationTime),
+          type
+        );
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = 16;
+        mode |= 2;
+        break;
+      default:
+        a: {
+          switch ("object" === typeof type && null !== type
+            ? type.$$typeof
+            : null) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = 13;
+              break a;
+            case REACT_CONTEXT_TYPE:
+              fiberTag = 12;
+              break a;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = 14;
+              break a;
+            default:
+              invariant(
+                !1,
+                "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
+                null == type ? type : typeof type,
+                ""
+              );
+          }
+          fiberTag = void 0;
+        }
+    }
+  mode = new FiberNode(fiberTag, element, key, mode);
+  mode.type = type;
+  mode.expirationTime = expirationTime;
+  return mode;
+}
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  elements = new FiberNode(10, elements, key, mode);
+  elements.expirationTime = expirationTime;
+  return elements;
+}
+function createFiberFromText(content, mode, expirationTime) {
+  content = new FiberNode(6, content, null, mode);
+  content.expirationTime = expirationTime;
+  return content;
+}
+function createFiberFromPortal(portal, mode, expirationTime) {
+  mode = new FiberNode(
+    4,
+    null !== portal.children ? portal.children : [],
+    portal.key,
+    mode
+  );
+  mode.expirationTime = expirationTime;
+  mode.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null,
+    implementation: portal.implementation
+  };
+  return mode;
+}
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
+  containerInfo = {
+    current: isAsync,
+    containerInfo: containerInfo,
+    pendingChildren: null,
+    earliestPendingTime: 0,
+    latestPendingTime: 0,
+    earliestSuspendedTime: 0,
+    latestSuspendedTime: 0,
+    latestPingedTime: 0,
+    didError: !1,
+    pendingCommitExpirationTime: 0,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    nextExpirationTimeToWorkOn: 0,
+    expirationTime: 0,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  return (isAsync.stateNode = containerInfo);
+}
+var onCommitFiberRoot = null,
+  onCommitFiberUnmount = null;
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {}
+  };
+}
+function injectInternals(internals) {
+  if ("undefined" === typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) return !1;
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled || !hook.supportsFiber) return !0;
+  try {
+    var rendererID = hook.inject(internals);
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {}
+  return !0;
+}
+function onCommitRoot(root) {
+  "function" === typeof onCommitFiberRoot && onCommitFiberRoot(root);
+}
+function onCommitUnmount(fiber) {
+  "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
+}
+function markPendingPriorityLevel(root, expirationTime) {
+  root.didError = !1;
+  var earliestPendingTime = root.earliestPendingTime;
+  0 === earliestPendingTime
+    ? (root.earliestPendingTime = root.latestPendingTime = expirationTime)
+    : earliestPendingTime > expirationTime
+      ? (root.earliestPendingTime = expirationTime)
+      : root.latestPendingTime < expirationTime &&
+        (root.latestPendingTime = expirationTime);
+  findNextPendingPriorityLevel(root);
+}
+function findNextPendingPriorityLevel(root) {
+  var earliestSuspendedTime = root.earliestSuspendedTime,
+    earliestPendingTime = root.earliestPendingTime;
+  if (0 === earliestSuspendedTime)
+    var nextExpirationTimeToWorkOn = (earliestSuspendedTime = earliestPendingTime);
+  else
+    0 !== earliestPendingTime
+      ? ((nextExpirationTimeToWorkOn = earliestPendingTime),
+        (earliestSuspendedTime =
+          earliestSuspendedTime < earliestPendingTime
+            ? earliestSuspendedTime
+            : earliestPendingTime))
+      : (nextExpirationTimeToWorkOn = earliestSuspendedTime =
+          root.latestPingedTime);
+  root.didError && (earliestSuspendedTime = 1);
+  root.nextExpirationTimeToWorkOn = nextExpirationTimeToWorkOn;
+  root.expirationTime = earliestSuspendedTime;
+}
+var hasForceUpdate = !1;
+function createUpdateQueue(baseState) {
+  return {
+    expirationTime: 0,
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function cloneUpdateQueue(currentQueue) {
+  return {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+    tag: 0,
+    payload: null,
+    callback: null,
+    next: null,
+    nextEffect: null
+  };
+}
+function appendUpdateToQueue(queue, update, expirationTime) {
+  null === queue.lastUpdate
+    ? (queue.firstUpdate = queue.lastUpdate = update)
+    : ((queue.lastUpdate.next = update), (queue.lastUpdate = update));
+  if (0 === queue.expirationTime || queue.expirationTime > expirationTime)
+    queue.expirationTime = expirationTime;
+}
+function enqueueUpdate(fiber, update, expirationTime) {
+  var alternate = fiber.alternate;
+  if (null === alternate) {
+    var queue1 = fiber.updateQueue;
+    var queue2 = null;
+    null === queue1 &&
+      (queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState));
+  } else
+    (queue1 = fiber.updateQueue),
+      (queue2 = alternate.updateQueue),
+      null === queue1
+        ? null === queue2
+          ? ((queue1 = fiber.updateQueue = createUpdateQueue(
+              fiber.memoizedState
+            )),
+            (queue2 = alternate.updateQueue = createUpdateQueue(
+              alternate.memoizedState
+            )))
+          : (queue1 = fiber.updateQueue = cloneUpdateQueue(queue2))
+        : null === queue2 &&
+          (queue2 = alternate.updateQueue = cloneUpdateQueue(queue1));
+  null === queue2 || queue1 === queue2
+    ? appendUpdateToQueue(queue1, update, expirationTime)
+    : null === queue1.lastUpdate || null === queue2.lastUpdate
+      ? (appendUpdateToQueue(queue1, update, expirationTime),
+        appendUpdateToQueue(queue2, update, expirationTime))
+      : (appendUpdateToQueue(queue1, update, expirationTime),
+        (queue2.lastUpdate = update));
+}
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  var workInProgressQueue = workInProgress.updateQueue;
+  workInProgressQueue =
+    null === workInProgressQueue
+      ? (workInProgress.updateQueue = createUpdateQueue(
+          workInProgress.memoizedState
+        ))
+      : ensureWorkInProgressQueueIsAClone(workInProgress, workInProgressQueue);
+  null === workInProgressQueue.lastCapturedUpdate
+    ? (workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update)
+    : ((workInProgressQueue.lastCapturedUpdate.next = update),
+      (workInProgressQueue.lastCapturedUpdate = update));
+  if (
+    0 === workInProgressQueue.expirationTime ||
+    workInProgressQueue.expirationTime > renderExpirationTime
+  )
+    workInProgressQueue.expirationTime = renderExpirationTime;
+}
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  null !== current &&
+    queue === current.updateQueue &&
+    (queue = workInProgress.updateQueue = cloneUpdateQueue(queue));
+  return queue;
+}
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case 1:
+      return (
+        (workInProgress = update.payload),
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress
+      );
+    case 3:
+      workInProgress.effectTag = (workInProgress.effectTag & -1025) | 64;
+    case 0:
+      workInProgress = update.payload;
+      nextProps =
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress;
+      if (null === nextProps || void 0 === nextProps) break;
+      return Object.assign({}, prevState, nextProps);
+    case 2:
+      hasForceUpdate = !0;
+  }
+  return prevState;
+}
+function processUpdateQueue(
+  workInProgress,
+  queue,
+  props,
+  instance,
+  renderExpirationTime
+) {
+  hasForceUpdate = !1;
+  if (
+    !(0 === queue.expirationTime || queue.expirationTime > renderExpirationTime)
+  ) {
+    queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+    for (
+      var newBaseState = queue.baseState,
+        newFirstUpdate = null,
+        newExpirationTime = 0,
+        update = queue.firstUpdate,
+        resultState = newBaseState;
+      null !== update;
+
+    ) {
+      var updateExpirationTime = update.expirationTime;
+      if (updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === newFirstUpdate &&
+            ((newFirstUpdate = update), (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > updateExpirationTime)
+        )
+          newExpirationTime = updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
+          update,
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastEffect
+              ? (queue.firstEffect = queue.lastEffect = update)
+              : ((queue.lastEffect.nextEffect = update),
+                (queue.lastEffect = update)));
+      update = update.next;
+    }
+    updateExpirationTime = null;
+    for (update = queue.firstCapturedUpdate; null !== update; ) {
+      var _updateExpirationTime = update.expirationTime;
+      if (_updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === updateExpirationTime &&
+            ((updateExpirationTime = update),
+            null === newFirstUpdate && (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > _updateExpirationTime)
+        )
+          newExpirationTime = _updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
+          update,
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastCapturedEffect
+              ? (queue.firstCapturedEffect = queue.lastCapturedEffect = update)
+              : ((queue.lastCapturedEffect.nextEffect = update),
+                (queue.lastCapturedEffect = update)));
+      update = update.next;
+    }
+    null === newFirstUpdate && (queue.lastUpdate = null);
+    null === updateExpirationTime
+      ? (queue.lastCapturedUpdate = null)
+      : (workInProgress.effectTag |= 32);
+    null === newFirstUpdate &&
+      null === updateExpirationTime &&
+      (newBaseState = resultState);
+    queue.baseState = newBaseState;
+    queue.firstUpdate = newFirstUpdate;
+    queue.firstCapturedUpdate = updateExpirationTime;
+    queue.expirationTime = newExpirationTime;
+    workInProgress.memoizedState = resultState;
+  }
+}
+function callCallback(callback, context) {
+  invariant(
+    "function" === typeof callback,
+    "Invalid argument passed as callback. Expected a function. Instead received: %s",
+    callback
+  );
+  callback.call(context);
+}
+function commitUpdateQueue(finishedWork, finishedQueue, instance) {
+  null !== finishedQueue.firstCapturedUpdate &&
+    (null !== finishedQueue.lastUpdate &&
+      ((finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate),
+      (finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate)),
+    (finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null));
+  finishedWork = finishedQueue.firstEffect;
+  for (
+    finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+    null !== finishedWork;
+
+  ) {
+    var _callback3 = finishedWork.callback;
+    null !== _callback3 &&
+      ((finishedWork.callback = null), callCallback(_callback3, instance));
+    finishedWork = finishedWork.nextEffect;
+  }
+  finishedWork = finishedQueue.firstCapturedEffect;
+  for (
+    finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+    null !== finishedWork;
+
+  )
+    (finishedQueue = finishedWork.callback),
+      null !== finishedQueue &&
+        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
+      (finishedWork = finishedWork.nextEffect);
+}
+function createCapturedValue(value, source) {
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
+var providerCursor = createCursor(null),
+  valueCursor = createCursor(null),
+  changedBitsCursor = createCursor(0);
+function pushProvider(providerFiber) {
+  var context = providerFiber.type._context;
+  push(changedBitsCursor, context._changedBits2, providerFiber);
+  push(valueCursor, context._currentValue2, providerFiber);
+  push(providerCursor, providerFiber, providerFiber);
+  context._currentValue2 = providerFiber.pendingProps.value;
+  context._changedBits2 = providerFiber.stateNode;
+}
+function popProvider(providerFiber) {
+  var changedBits = changedBitsCursor.current,
+    currentValue = valueCursor.current;
+  pop(providerCursor, providerFiber);
+  pop(valueCursor, providerFiber);
+  pop(changedBitsCursor, providerFiber);
+  providerFiber = providerFiber.type._context;
+  providerFiber._currentValue2 = currentValue;
+  providerFiber._changedBits2 = changedBits;
+}
+var NO_CONTEXT = {},
+  contextStackCursor$1 = createCursor(NO_CONTEXT),
+  contextFiberStackCursor = createCursor(NO_CONTEXT),
+  rootInstanceStackCursor = createCursor(NO_CONTEXT);
+function requiredContext(c) {
+  invariant(
+    c !== NO_CONTEXT,
+    "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
+  );
+  return c;
+}
+function pushHostContainer(fiber, nextRootInstance) {
+  push(rootInstanceStackCursor, nextRootInstance, fiber);
+  push(contextFiberStackCursor, fiber, fiber);
+  push(contextStackCursor$1, NO_CONTEXT, fiber);
+  pop(contextStackCursor$1, fiber);
+  push(contextStackCursor$1, { isInAParentText: !1 }, fiber);
+}
+function popHostContainer(fiber) {
+  pop(contextStackCursor$1, fiber);
+  pop(contextFiberStackCursor, fiber);
+  pop(rootInstanceStackCursor, fiber);
+}
+function popHostContext(fiber) {
+  contextFiberStackCursor.current === fiber &&
+    (pop(contextStackCursor$1, fiber), pop(contextFiberStackCursor, fiber));
+}
+var timerPausedAt = 0,
+  totalElapsedPauseTime = 0;
+function recordElapsedActualRenderTime(fiber) {
+  fiber.actualDuration = now$1() - totalElapsedPauseTime - fiber.actualDuration;
+}
+function resumeActualRenderTimerIfPaused() {
+  0 < timerPausedAt &&
+    ((totalElapsedPauseTime += now$1() - timerPausedAt), (timerPausedAt = 0));
+}
+var baseStartTime = -1,
+  hasOwnProperty = Object.prototype.hasOwnProperty;
+function is(x, y) {
+  return x === y ? 0 !== x || 0 !== y || 1 / x === 1 / y : x !== x && y !== y;
+}
+function shallowEqual(objA, objB) {
+  if (is(objA, objB)) return !0;
+  if (
+    "object" !== typeof objA ||
+    null === objA ||
+    "object" !== typeof objB ||
+    null === objB
+  )
+    return !1;
+  var keysA = Object.keys(objA),
+    keysB = Object.keys(objB);
+  if (keysA.length !== keysB.length) return !1;
+  for (keysB = 0; keysB < keysA.length; keysB++)
+    if (
+      !hasOwnProperty.call(objB, keysA[keysB]) ||
+      !is(objA[keysA[keysB]], objB[keysA[keysB]])
+    )
+      return !1;
+  return !0;
+}
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+  getDerivedStateFromProps = getDerivedStateFromProps(nextProps, prevState);
+  prevState =
+    null === getDerivedStateFromProps || void 0 === getDerivedStateFromProps
+      ? prevState
+      : Object.assign({}, prevState, getDerivedStateFromProps);
+  workInProgress.memoizedState = prevState;
+  workInProgress = workInProgress.updateQueue;
+  null !== workInProgress &&
+    0 === workInProgress.expirationTime &&
+    (workInProgress.baseState = prevState);
+}
+var classComponentUpdater = {
+  isMounted: function(component) {
+    return (component = component._reactInternalFiber)
+      ? 2 === isFiberMountedImpl(component)
+      : !1;
+  },
+  enqueueSetState: function(inst, payload, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.payload = payload;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  },
+  enqueueReplaceState: function(inst, payload, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.tag = 1;
+    update.payload = payload;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  },
+  enqueueForceUpdate: function(inst, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.tag = 2;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  }
+};
+function checkShouldComponentUpdate(
+  workInProgress,
+  oldProps,
+  newProps,
+  oldState,
+  newState,
+  newContext
+) {
+  var instance = workInProgress.stateNode;
+  workInProgress = workInProgress.type;
+  return "function" === typeof instance.shouldComponentUpdate
+    ? instance.shouldComponentUpdate(newProps, newState, newContext)
+    : workInProgress.prototype && workInProgress.prototype.isPureReactComponent
+      ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+      : !0;
+}
+function callComponentWillReceiveProps(
+  workInProgress,
+  instance,
+  newProps,
+  newContext
+) {
+  workInProgress = instance.state;
+  "function" === typeof instance.componentWillReceiveProps &&
+    instance.componentWillReceiveProps(newProps, newContext);
+  "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
+    instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+  instance.state !== workInProgress &&
+    classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+}
+function mountClassInstance(workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type,
+    instance = workInProgress.stateNode,
+    props = workInProgress.pendingProps,
+    unmaskedContext = getUnmaskedContext(workInProgress);
+  instance.props = props;
+  instance.state = workInProgress.memoizedState;
+  instance.refs = emptyObject;
+  instance.context = getMaskedContext(workInProgress, unmaskedContext);
+  unmaskedContext = workInProgress.updateQueue;
+  null !== unmaskedContext &&
+    (processUpdateQueue(
+      workInProgress,
+      unmaskedContext,
+      props,
+      instance,
+      renderExpirationTime
+    ),
+    (instance.state = workInProgress.memoizedState));
+  unmaskedContext = workInProgress.type.getDerivedStateFromProps;
+  "function" === typeof unmaskedContext &&
+    (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+    (instance.state = workInProgress.memoizedState));
+  "function" === typeof ctor.getDerivedStateFromProps ||
+    "function" === typeof instance.getSnapshotBeforeUpdate ||
+    ("function" !== typeof instance.UNSAFE_componentWillMount &&
+      "function" !== typeof instance.componentWillMount) ||
+    ((ctor = instance.state),
+    "function" === typeof instance.componentWillMount &&
+      instance.componentWillMount(),
+    "function" === typeof instance.UNSAFE_componentWillMount &&
+      instance.UNSAFE_componentWillMount(),
+    ctor !== instance.state &&
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null),
+    (unmaskedContext = workInProgress.updateQueue),
+    null !== unmaskedContext &&
+      (processUpdateQueue(
+        workInProgress,
+        unmaskedContext,
+        props,
+        instance,
+        renderExpirationTime
+      ),
+      (instance.state = workInProgress.memoizedState)));
+  "function" === typeof instance.componentDidMount &&
+    (workInProgress.effectTag |= 4);
+}
+var isArray$1 = Array.isArray;
+function coerceRef(returnFiber, current, element) {
+  returnFiber = element.ref;
+  if (
+    null !== returnFiber &&
+    "function" !== typeof returnFiber &&
+    "object" !== typeof returnFiber
+  ) {
+    if (element._owner) {
+      element = element._owner;
+      var inst = void 0;
+      element &&
+        (invariant(
+          2 === element.tag,
+          "Stateless function components cannot have refs."
+        ),
+        (inst = element.stateNode));
+      invariant(
+        inst,
+        "Missing owner for string ref %s. This error is likely caused by a bug in React. Please file an issue.",
+        returnFiber
+      );
+      var stringRef = "" + returnFiber;
+      if (
+        null !== current &&
+        null !== current.ref &&
+        "function" === typeof current.ref &&
+        current.ref._stringRef === stringRef
+      )
+        return current.ref;
+      current = function(value) {
+        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
+        null === value ? delete refs[stringRef] : (refs[stringRef] = value);
+      };
+      current._stringRef = stringRef;
+      return current;
+    }
+    invariant(
+      "string" === typeof returnFiber,
+      "Expected ref to be a function or a string."
+    );
+    invariant(
+      element._owner,
+      "Element ref was specified as a string (%s) but no owner was set. This could happen for one of the following reasons:\n1. You may be adding a ref to a functional component\n2. You may be adding a ref to a component that was not created inside a component's render method\n3. You have multiple copies of React loaded\nSee https://fb.me/react-refs-must-have-owner for more information.",
+      returnFiber
+    );
+  }
+  return returnFiber;
+}
+function throwOnInvalidObjectType(returnFiber, newChild) {
+  "textarea" !== returnFiber.type &&
+    invariant(
+      !1,
+      "Objects are not valid as a React child (found: %s).%s",
+      "[object Object]" === Object.prototype.toString.call(newChild)
+        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
+        : newChild,
+      ""
+    );
+}
+function ChildReconciler(shouldTrackSideEffects) {
+  function deleteChild(returnFiber, childToDelete) {
+    if (shouldTrackSideEffects) {
+      var last = returnFiber.lastEffect;
+      null !== last
+        ? ((last.nextEffect = childToDelete),
+          (returnFiber.lastEffect = childToDelete))
+        : (returnFiber.firstEffect = returnFiber.lastEffect = childToDelete);
+      childToDelete.nextEffect = null;
+      childToDelete.effectTag = 8;
+    }
+  }
+  function deleteRemainingChildren(returnFiber, currentFirstChild) {
+    if (!shouldTrackSideEffects) return null;
+    for (; null !== currentFirstChild; )
+      deleteChild(returnFiber, currentFirstChild),
+        (currentFirstChild = currentFirstChild.sibling);
+    return null;
+  }
+  function mapRemainingChildren(returnFiber, currentFirstChild) {
+    for (returnFiber = new Map(); null !== currentFirstChild; )
+      null !== currentFirstChild.key
+        ? returnFiber.set(currentFirstChild.key, currentFirstChild)
+        : returnFiber.set(currentFirstChild.index, currentFirstChild),
+        (currentFirstChild = currentFirstChild.sibling);
+    return returnFiber;
+  }
+  function useFiber(fiber, pendingProps, expirationTime) {
+    fiber = createWorkInProgress(fiber, pendingProps, expirationTime);
+    fiber.index = 0;
+    fiber.sibling = null;
+    return fiber;
+  }
+  function placeChild(newFiber, lastPlacedIndex, newIndex) {
+    newFiber.index = newIndex;
+    if (!shouldTrackSideEffects) return lastPlacedIndex;
+    newIndex = newFiber.alternate;
+    if (null !== newIndex)
+      return (
+        (newIndex = newIndex.index),
+        newIndex < lastPlacedIndex
+          ? ((newFiber.effectTag = 2), lastPlacedIndex)
+          : newIndex
+      );
+    newFiber.effectTag = 2;
+    return lastPlacedIndex;
+  }
+  function placeSingleChild(newFiber) {
+    shouldTrackSideEffects &&
+      null === newFiber.alternate &&
+      (newFiber.effectTag = 2);
+    return newFiber;
+  }
+  function updateTextNode(returnFiber, current, textContent, expirationTime) {
+    if (null === current || 6 !== current.tag)
+      return (
+        (current = createFiberFromText(
+          textContent,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (current.return = returnFiber),
+        current
+      );
+    current = useFiber(current, textContent, expirationTime);
+    current.return = returnFiber;
+    return current;
+  }
+  function updateElement(returnFiber, current, element, expirationTime) {
+    if (null !== current && current.type === element.type)
+      return (
+        (expirationTime = useFiber(current, element.props, expirationTime)),
+        (expirationTime.ref = coerceRef(returnFiber, current, element)),
+        (expirationTime.return = returnFiber),
+        expirationTime
+      );
+    expirationTime = createFiberFromElement(
+      element,
+      returnFiber.mode,
+      expirationTime
+    );
+    expirationTime.ref = coerceRef(returnFiber, current, element);
+    expirationTime.return = returnFiber;
+    return expirationTime;
+  }
+  function updatePortal(returnFiber, current, portal, expirationTime) {
+    if (
+      null === current ||
+      4 !== current.tag ||
+      current.stateNode.containerInfo !== portal.containerInfo ||
+      current.stateNode.implementation !== portal.implementation
+    )
+      return (
+        (current = createFiberFromPortal(
+          portal,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (current.return = returnFiber),
+        current
+      );
+    current = useFiber(current, portal.children || [], expirationTime);
+    current.return = returnFiber;
+    return current;
+  }
+  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
+    if (null === current || 10 !== current.tag)
+      return (
+        (current = createFiberFromFragment(
+          fragment,
+          returnFiber.mode,
+          expirationTime,
+          key
+        )),
+        (current.return = returnFiber),
+        current
+      );
+    current = useFiber(current, fragment, expirationTime);
+    current.return = returnFiber;
+    return current;
+  }
+  function createChild(returnFiber, newChild, expirationTime) {
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (newChild = createFiberFromText(
+          "" + newChild,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (newChild.return = returnFiber),
+        newChild
+      );
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return (
+            (expirationTime = createFiberFromElement(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
+            (expirationTime.return = returnFiber),
+            expirationTime
+          );
+        case REACT_PORTAL_TYPE:
+          return (
+            (newChild = createFiberFromPortal(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (newChild.return = returnFiber),
+            newChild
+          );
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return (
+          (newChild = createFiberFromFragment(
+            newChild,
+            returnFiber.mode,
+            expirationTime,
+            null
+          )),
+          (newChild.return = returnFiber),
+          newChild
+        );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
+    var key = null !== oldFiber ? oldFiber.key : null;
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return null !== key
+        ? null
+        : updateTextNode(returnFiber, oldFiber, "" + newChild, expirationTime);
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return newChild.key === key
+            ? newChild.type === REACT_FRAGMENT_TYPE
+              ? updateFragment(
+                  returnFiber,
+                  oldFiber,
+                  newChild.props.children,
+                  expirationTime,
+                  key
+                )
+              : updateElement(returnFiber, oldFiber, newChild, expirationTime)
+            : null;
+        case REACT_PORTAL_TYPE:
+          return newChild.key === key
+            ? updatePortal(returnFiber, oldFiber, newChild, expirationTime)
+            : null;
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return null !== key
+          ? null
+          : updateFragment(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime,
+              null
+            );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function updateFromMap(
+    existingChildren,
+    returnFiber,
+    newIdx,
+    newChild,
+    expirationTime
+  ) {
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (existingChildren = existingChildren.get(newIdx) || null),
+        updateTextNode(
+          returnFiber,
+          existingChildren,
+          "" + newChild,
+          expirationTime
+        )
+      );
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return (
+            (existingChildren =
+              existingChildren.get(
+                null === newChild.key ? newIdx : newChild.key
+              ) || null),
+            newChild.type === REACT_FRAGMENT_TYPE
+              ? updateFragment(
+                  returnFiber,
+                  existingChildren,
+                  newChild.props.children,
+                  expirationTime,
+                  newChild.key
+                )
+              : updateElement(
+                  returnFiber,
+                  existingChildren,
+                  newChild,
+                  expirationTime
+                )
+          );
+        case REACT_PORTAL_TYPE:
+          return (
+            (existingChildren =
+              existingChildren.get(
+                null === newChild.key ? newIdx : newChild.key
+              ) || null),
+            updatePortal(
+              returnFiber,
+              existingChildren,
+              newChild,
+              expirationTime
+            )
+          );
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return (
+          (existingChildren = existingChildren.get(newIdx) || null),
+          updateFragment(
+            returnFiber,
+            existingChildren,
+            newChild,
+            expirationTime,
+            null
+          )
+        );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function reconcileChildrenArray(
+    returnFiber,
+    currentFirstChild,
+    newChildren,
+    expirationTime
+  ) {
+    for (
+      var resultingFirstChild = null,
+        previousNewFiber = null,
+        oldFiber = currentFirstChild,
+        newIdx = (currentFirstChild = 0),
+        nextOldFiber = null;
+      null !== oldFiber && newIdx < newChildren.length;
+      newIdx++
+    ) {
+      oldFiber.index > newIdx
+        ? ((nextOldFiber = oldFiber), (oldFiber = null))
+        : (nextOldFiber = oldFiber.sibling);
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (null === newFiber) {
+        null === oldFiber && (oldFiber = nextOldFiber);
+        break;
+      }
+      shouldTrackSideEffects &&
+        oldFiber &&
+        null === newFiber.alternate &&
+        deleteChild(returnFiber, oldFiber);
+      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
+      null === previousNewFiber
+        ? (resultingFirstChild = newFiber)
+        : (previousNewFiber.sibling = newFiber);
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+    if (newIdx === newChildren.length)
+      return (
+        deleteRemainingChildren(returnFiber, oldFiber), resultingFirstChild
+      );
+    if (null === oldFiber) {
+      for (; newIdx < newChildren.length; newIdx++)
+        if (
+          (oldFiber = createChild(
+            returnFiber,
+            newChildren[newIdx],
+            expirationTime
+          ))
+        )
+          (currentFirstChild = placeChild(oldFiber, currentFirstChild, newIdx)),
+            null === previousNewFiber
+              ? (resultingFirstChild = oldFiber)
+              : (previousNewFiber.sibling = oldFiber),
+            (previousNewFiber = oldFiber);
+      return resultingFirstChild;
+    }
+    for (
+      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
+      newIdx < newChildren.length;
+      newIdx++
+    )
+      if (
+        (nextOldFiber = updateFromMap(
+          oldFiber,
+          returnFiber,
+          newIdx,
+          newChildren[newIdx],
+          expirationTime
+        ))
+      )
+        shouldTrackSideEffects &&
+          null !== nextOldFiber.alternate &&
+          oldFiber.delete(
+            null === nextOldFiber.key ? newIdx : nextOldFiber.key
+          ),
+          (currentFirstChild = placeChild(
+            nextOldFiber,
+            currentFirstChild,
+            newIdx
+          )),
+          null === previousNewFiber
+            ? (resultingFirstChild = nextOldFiber)
+            : (previousNewFiber.sibling = nextOldFiber),
+          (previousNewFiber = nextOldFiber);
+    shouldTrackSideEffects &&
+      oldFiber.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    return resultingFirstChild;
+  }
+  function reconcileChildrenIterator(
+    returnFiber,
+    currentFirstChild,
+    newChildrenIterable,
+    expirationTime
+  ) {
+    var iteratorFn = getIteratorFn(newChildrenIterable);
+    invariant(
+      "function" === typeof iteratorFn,
+      "An object is not an iterable. This error is likely caused by a bug in React. Please file an issue."
+    );
+    newChildrenIterable = iteratorFn.call(newChildrenIterable);
+    invariant(
+      null != newChildrenIterable,
+      "An iterable object provided no iterator."
+    );
+    for (
+      var previousNewFiber = (iteratorFn = null),
+        oldFiber = currentFirstChild,
+        newIdx = (currentFirstChild = 0),
+        nextOldFiber = null,
+        step = newChildrenIterable.next();
+      null !== oldFiber && !step.done;
+      newIdx++, step = newChildrenIterable.next()
+    ) {
+      oldFiber.index > newIdx
+        ? ((nextOldFiber = oldFiber), (oldFiber = null))
+        : (nextOldFiber = oldFiber.sibling);
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        step.value,
+        expirationTime
+      );
+      if (null === newFiber) {
+        oldFiber || (oldFiber = nextOldFiber);
+        break;
+      }
+      shouldTrackSideEffects &&
+        oldFiber &&
+        null === newFiber.alternate &&
+        deleteChild(returnFiber, oldFiber);
+      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
+      null === previousNewFiber
+        ? (iteratorFn = newFiber)
+        : (previousNewFiber.sibling = newFiber);
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+    if (step.done)
+      return deleteRemainingChildren(returnFiber, oldFiber), iteratorFn;
+    if (null === oldFiber) {
+      for (; !step.done; newIdx++, step = newChildrenIterable.next())
+        (step = createChild(returnFiber, step.value, expirationTime)),
+          null !== step &&
+            ((currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+            null === previousNewFiber
+              ? (iteratorFn = step)
+              : (previousNewFiber.sibling = step),
+            (previousNewFiber = step));
+      return iteratorFn;
+    }
+    for (
+      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
+      !step.done;
+      newIdx++, step = newChildrenIterable.next()
+    )
+      (step = updateFromMap(
+        oldFiber,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      )),
+        null !== step &&
+          (shouldTrackSideEffects &&
+            null !== step.alternate &&
+            oldFiber.delete(null === step.key ? newIdx : step.key),
+          (currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+          null === previousNewFiber
+            ? (iteratorFn = step)
+            : (previousNewFiber.sibling = step),
+          (previousNewFiber = step));
+    shouldTrackSideEffects &&
+      oldFiber.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    return iteratorFn;
+  }
+  return function(returnFiber, currentFirstChild, newChild, expirationTime) {
+    var isUnkeyedTopLevelFragment =
+      "object" === typeof newChild &&
+      null !== newChild &&
+      newChild.type === REACT_FRAGMENT_TYPE &&
+      null === newChild.key;
+    isUnkeyedTopLevelFragment && (newChild = newChild.props.children);
+    var isObject = "object" === typeof newChild && null !== newChild;
+    if (isObject)
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          a: {
+            isObject = newChild.key;
+            for (
+              isUnkeyedTopLevelFragment = currentFirstChild;
+              null !== isUnkeyedTopLevelFragment;
+
+            ) {
+              if (isUnkeyedTopLevelFragment.key === isObject)
+                if (
+                  10 === isUnkeyedTopLevelFragment.tag
+                    ? newChild.type === REACT_FRAGMENT_TYPE
+                    : isUnkeyedTopLevelFragment.type === newChild.type
+                ) {
+                  deleteRemainingChildren(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment.sibling
+                  );
+                  currentFirstChild = useFiber(
+                    isUnkeyedTopLevelFragment,
+                    newChild.type === REACT_FRAGMENT_TYPE
+                      ? newChild.props.children
+                      : newChild.props,
+                    expirationTime
+                  );
+                  currentFirstChild.ref = coerceRef(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment,
+                    newChild
+                  );
+                  currentFirstChild.return = returnFiber;
+                  returnFiber = currentFirstChild;
+                  break a;
+                } else {
+                  deleteRemainingChildren(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment
+                  );
+                  break;
+                }
+              else deleteChild(returnFiber, isUnkeyedTopLevelFragment);
+              isUnkeyedTopLevelFragment = isUnkeyedTopLevelFragment.sibling;
+            }
+            newChild.type === REACT_FRAGMENT_TYPE
+              ? ((currentFirstChild = createFiberFromFragment(
+                  newChild.props.children,
+                  returnFiber.mode,
+                  expirationTime,
+                  newChild.key
+                )),
+                (currentFirstChild.return = returnFiber),
+                (returnFiber = currentFirstChild))
+              : ((expirationTime = createFiberFromElement(
+                  newChild,
+                  returnFiber.mode,
+                  expirationTime
+                )),
+                (expirationTime.ref = coerceRef(
+                  returnFiber,
+                  currentFirstChild,
+                  newChild
+                )),
+                (expirationTime.return = returnFiber),
+                (returnFiber = expirationTime));
+          }
+          return placeSingleChild(returnFiber);
+        case REACT_PORTAL_TYPE:
+          a: {
+            for (
+              isUnkeyedTopLevelFragment = newChild.key;
+              null !== currentFirstChild;
+
+            ) {
+              if (currentFirstChild.key === isUnkeyedTopLevelFragment)
+                if (
+                  4 === currentFirstChild.tag &&
+                  currentFirstChild.stateNode.containerInfo ===
+                    newChild.containerInfo &&
+                  currentFirstChild.stateNode.implementation ===
+                    newChild.implementation
+                ) {
+                  deleteRemainingChildren(
+                    returnFiber,
+                    currentFirstChild.sibling
+                  );
+                  currentFirstChild = useFiber(
+                    currentFirstChild,
+                    newChild.children || [],
+                    expirationTime
+                  );
+                  currentFirstChild.return = returnFiber;
+                  returnFiber = currentFirstChild;
+                  break a;
+                } else {
+                  deleteRemainingChildren(returnFiber, currentFirstChild);
+                  break;
+                }
+              else deleteChild(returnFiber, currentFirstChild);
+              currentFirstChild = currentFirstChild.sibling;
+            }
+            currentFirstChild = createFiberFromPortal(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            );
+            currentFirstChild.return = returnFiber;
+            returnFiber = currentFirstChild;
+          }
+          return placeSingleChild(returnFiber);
+      }
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (newChild = "" + newChild),
+        null !== currentFirstChild && 6 === currentFirstChild.tag
+          ? (deleteRemainingChildren(returnFiber, currentFirstChild.sibling),
+            (currentFirstChild = useFiber(
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )),
+            (currentFirstChild.return = returnFiber),
+            (returnFiber = currentFirstChild))
+          : (deleteRemainingChildren(returnFiber, currentFirstChild),
+            (currentFirstChild = createFiberFromText(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (currentFirstChild.return = returnFiber),
+            (returnFiber = currentFirstChild)),
+        placeSingleChild(returnFiber)
+      );
+    if (isArray$1(newChild))
+      return reconcileChildrenArray(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    if (getIteratorFn(newChild))
+      return reconcileChildrenIterator(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    isObject && throwOnInvalidObjectType(returnFiber, newChild);
+    if ("undefined" === typeof newChild && !isUnkeyedTopLevelFragment)
+      switch (returnFiber.tag) {
+        case 2:
+        case 1:
+          (expirationTime = returnFiber.type),
+            invariant(
+              !1,
+              "%s(...): Nothing was returned from render. This usually means a return statement is missing. Or, to render nothing, return null.",
+              expirationTime.displayName || expirationTime.name || "Component"
+            );
+      }
+    return deleteRemainingChildren(returnFiber, currentFirstChild);
+  };
+}
+var reconcileChildFibers = ChildReconciler(!0),
+  mountChildFibers = ChildReconciler(!1),
+  hydrationParentFiber = null,
+  nextHydratableInstance = null,
+  isHydrating = !1;
+function tryHydrate(fiber, nextInstance) {
+  switch (fiber.tag) {
+    case 5:
+      return (
+        (nextInstance = shim$1(nextInstance, fiber.type, fiber.pendingProps)),
+        null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+      );
+    case 6:
+      return (
+        (nextInstance = shim$1(nextInstance, fiber.pendingProps)),
+        null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+      );
+    default:
+      return !1;
+  }
+}
+function tryToClaimNextHydratableInstance(fiber$jscomp$0) {
+  if (isHydrating) {
+    var nextInstance = nextHydratableInstance;
+    if (nextInstance) {
+      var firstAttemptedInstance = nextInstance;
+      if (!tryHydrate(fiber$jscomp$0, nextInstance)) {
+        nextInstance = shim$1(firstAttemptedInstance);
+        if (!nextInstance || !tryHydrate(fiber$jscomp$0, nextInstance)) {
+          fiber$jscomp$0.effectTag |= 2;
+          isHydrating = !1;
+          hydrationParentFiber = fiber$jscomp$0;
+          return;
+        }
+        var returnFiber = hydrationParentFiber,
+          fiber = new FiberNode(5, null, null, 0);
+        fiber.type = "DELETED";
+        fiber.stateNode = firstAttemptedInstance;
+        fiber.return = returnFiber;
+        fiber.effectTag = 8;
+        null !== returnFiber.lastEffect
+          ? ((returnFiber.lastEffect.nextEffect = fiber),
+            (returnFiber.lastEffect = fiber))
+          : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
+      }
+      hydrationParentFiber = fiber$jscomp$0;
+      nextHydratableInstance = shim$1(nextInstance);
+    } else
+      (fiber$jscomp$0.effectTag |= 2),
+        (isHydrating = !1),
+        (hydrationParentFiber = fiber$jscomp$0);
+  }
+}
+function reconcileChildren(current, workInProgress, nextChildren) {
+  reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    workInProgress.expirationTime
+  );
+}
+function reconcileChildrenAtExpirationTime(
+  current,
+  workInProgress,
+  nextChildren,
+  renderExpirationTime
+) {
+  workInProgress.child =
+    null === current
+      ? mountChildFibers(
+          workInProgress,
+          null,
+          nextChildren,
+          renderExpirationTime
+        )
+      : reconcileChildFibers(
+          workInProgress,
+          current.child,
+          nextChildren,
+          renderExpirationTime
+        );
+}
+function markRef(current, workInProgress) {
+  var ref = workInProgress.ref;
+  if (
+    (null === current && null !== ref) ||
+    (null !== current && current.ref !== ref)
+  )
+    workInProgress.effectTag |= 128;
+}
+function finishClassComponent(
+  current,
+  workInProgress,
+  shouldUpdate,
+  hasContext,
+  renderExpirationTime
+) {
+  markRef(current, workInProgress);
+  var didCaptureError = 0 !== (workInProgress.effectTag & 64);
+  if (!shouldUpdate && !didCaptureError)
+    return (
+      hasContext && invalidateContextProvider(workInProgress, !1),
+      bailoutOnAlreadyFinishedWork(current, workInProgress)
+    );
+  shouldUpdate = workInProgress.stateNode;
+  ReactCurrentOwner.current = workInProgress;
+  if (didCaptureError) {
+    var nextChildren = null;
+    baseStartTime = -1;
+  } else nextChildren = shouldUpdate.render();
+  workInProgress.effectTag |= 1;
+  didCaptureError &&
+    (reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      null,
+      renderExpirationTime
+    ),
+    (workInProgress.child = null));
+  reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    renderExpirationTime
+  );
+  workInProgress.memoizedState = shouldUpdate.state;
+  workInProgress.memoizedProps = shouldUpdate.props;
+  hasContext && invalidateContextProvider(workInProgress, !0);
+  return workInProgress.child;
+}
+function pushHostRootContext(workInProgress) {
+  var root = workInProgress.stateNode;
+  root.pendingContext
+    ? pushTopLevelContextObject(
+        workInProgress,
+        root.pendingContext,
+        root.pendingContext !== root.context
+      )
+    : root.context &&
+      pushTopLevelContextObject(workInProgress, root.context, !1);
+  pushHostContainer(workInProgress, root.containerInfo);
+}
+function propagateContextChange(
+  workInProgress,
+  context,
+  changedBits,
+  renderExpirationTime
+) {
+  var fiber = workInProgress.child;
+  null !== fiber && (fiber.return = workInProgress);
+  for (; null !== fiber; ) {
+    switch (fiber.tag) {
+      case 12:
+        var nextFiber = fiber.stateNode | 0;
+        if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
+          for (nextFiber = fiber; null !== nextFiber; ) {
+            var alternate = nextFiber.alternate;
+            if (
+              0 === nextFiber.expirationTime ||
+              nextFiber.expirationTime > renderExpirationTime
+            )
+              (nextFiber.expirationTime = renderExpirationTime),
+                null !== alternate &&
+                  (0 === alternate.expirationTime ||
+                    alternate.expirationTime > renderExpirationTime) &&
+                  (alternate.expirationTime = renderExpirationTime);
+            else if (
+              null !== alternate &&
+              (0 === alternate.expirationTime ||
+                alternate.expirationTime > renderExpirationTime)
+            )
+              alternate.expirationTime = renderExpirationTime;
+            else break;
+            nextFiber = nextFiber.return;
+          }
+          nextFiber = null;
+        } else nextFiber = fiber.child;
+        break;
+      case 13:
+        nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+        break;
+      default:
+        nextFiber = fiber.child;
+    }
+    if (null !== nextFiber) nextFiber.return = fiber;
+    else
+      for (nextFiber = fiber; null !== nextFiber; ) {
+        if (nextFiber === workInProgress) {
+          nextFiber = null;
+          break;
+        }
+        fiber = nextFiber.sibling;
+        if (null !== fiber) {
+          fiber.return = nextFiber.return;
+          nextFiber = fiber;
+          break;
+        }
+        nextFiber = nextFiber.return;
+      }
+    fiber = nextFiber;
+  }
+}
+function updateContextProvider(current, workInProgress, renderExpirationTime) {
+  var context = workInProgress.type._context,
+    newProps = workInProgress.pendingProps,
+    oldProps = workInProgress.memoizedProps,
+    canBailOnProps = !0;
+  if (didPerformWorkStackCursor.current) canBailOnProps = !1;
+  else if (oldProps === newProps)
+    return (
+      (workInProgress.stateNode = 0),
+      pushProvider(workInProgress),
+      bailoutOnAlreadyFinishedWork(current, workInProgress)
+    );
+  var newValue = newProps.value;
+  workInProgress.memoizedProps = newProps;
+  if (null === oldProps) newValue = 1073741823;
+  else if (oldProps.value === newProps.value) {
+    if (oldProps.children === newProps.children && canBailOnProps)
+      return (
+        (workInProgress.stateNode = 0),
+        pushProvider(workInProgress),
+        bailoutOnAlreadyFinishedWork(current, workInProgress)
+      );
+    newValue = 0;
+  } else {
+    var oldValue = oldProps.value;
+    if (
+      (oldValue === newValue &&
+        (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
+      (oldValue !== oldValue && newValue !== newValue)
+    ) {
+      if (oldProps.children === newProps.children && canBailOnProps)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+      newValue = 0;
+    } else if (
+      ((newValue =
+        "function" === typeof context._calculateChangedBits
+          ? context._calculateChangedBits(oldValue, newValue)
+          : 1073741823),
+      (newValue |= 0),
+      0 === newValue)
+    ) {
+      if (oldProps.children === newProps.children && canBailOnProps)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+    } else
+      propagateContextChange(
+        workInProgress,
+        context,
+        newValue,
+        renderExpirationTime
+      );
+  }
+  workInProgress.stateNode = newValue;
+  pushProvider(workInProgress);
+  reconcileChildren(current, workInProgress, newProps.children);
+  return workInProgress.child;
+}
+function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+  baseStartTime = -1;
+  invariant(
+    null === current || workInProgress.child === current.child,
+    "Resuming work not yet implemented."
+  );
+  if (null !== workInProgress.child) {
+    current = workInProgress.child;
+    var newChild = createWorkInProgress(
+      current,
+      current.pendingProps,
+      current.expirationTime
+    );
+    workInProgress.child = newChild;
+    for (newChild.return = workInProgress; null !== current.sibling; )
+      (current = current.sibling),
+        (newChild = newChild.sibling = createWorkInProgress(
+          current,
+          current.pendingProps,
+          current.expirationTime
+        )),
+        (newChild.return = workInProgress);
+    newChild.sibling = null;
+  }
+  return workInProgress.child;
+}
+function beginWork(current, workInProgress, renderExpirationTime) {
+  workInProgress.mode & 4 &&
+    ((workInProgress.actualDuration =
+      now$1() - workInProgress.actualDuration - totalElapsedPauseTime),
+    (workInProgress.actualStartTime = now$1()));
+  if (
+    0 === workInProgress.expirationTime ||
+    workInProgress.expirationTime > renderExpirationTime
+  ) {
+    baseStartTime = -1;
+    switch (workInProgress.tag) {
+      case 3:
+        pushHostRootContext(workInProgress);
+        break;
+      case 2:
+        pushContextProvider(workInProgress);
+        break;
+      case 4:
+        pushHostContainer(
+          workInProgress,
+          workInProgress.stateNode.containerInfo
+        );
+        break;
+      case 13:
+        pushProvider(workInProgress);
+    }
+    return null;
+  }
+  switch (workInProgress.tag) {
+    case 0:
+      invariant(
+        null === current,
+        "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
+      );
+      var fn = workInProgress.type,
+        props = workInProgress.pendingProps,
+        unmaskedContext = getUnmaskedContext(workInProgress);
+      unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
+      fn = fn(props, unmaskedContext);
+      workInProgress.effectTag |= 1;
+      "object" === typeof fn &&
+      null !== fn &&
+      "function" === typeof fn.render &&
+      void 0 === fn.$$typeof
+        ? ((unmaskedContext = workInProgress.type),
+          (workInProgress.tag = 2),
+          (workInProgress.memoizedState =
+            null !== fn.state && void 0 !== fn.state ? fn.state : null),
+          (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
+          "function" === typeof unmaskedContext &&
+            applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+          (props = pushContextProvider(workInProgress)),
+          (fn.updater = classComponentUpdater),
+          (workInProgress.stateNode = fn),
+          (fn._reactInternalFiber = workInProgress),
+          mountClassInstance(workInProgress, renderExpirationTime),
+          (current = finishClassComponent(
+            current,
+            workInProgress,
+            !0,
+            props,
+            renderExpirationTime
+          )))
+        : ((workInProgress.tag = 1),
+          reconcileChildren(current, workInProgress, fn),
+          (workInProgress.memoizedProps = props),
+          (current = workInProgress.child));
+      return current;
+    case 1:
+      return (
+        (props = workInProgress.type),
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime
+          ? ((fn = getUnmaskedContext(workInProgress)),
+            (fn = getMaskedContext(workInProgress, fn)),
+            (props = props(renderExpirationTime, fn)),
+            (workInProgress.effectTag |= 1),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 2:
+      props = pushContextProvider(workInProgress);
+      if (null === current)
+        if (null === workInProgress.stateNode) {
+          var props$jscomp$0 = workInProgress.pendingProps,
+            ctor = workInProgress.type;
+          fn = getUnmaskedContext(workInProgress);
+          var needsContext =
+            2 === workInProgress.tag &&
+            null != workInProgress.type.contextTypes;
+          unmaskedContext = needsContext
+            ? getMaskedContext(workInProgress, fn)
+            : emptyObject;
+          props$jscomp$0 = new ctor(props$jscomp$0, unmaskedContext);
+          workInProgress.memoizedState =
+            null !== props$jscomp$0.state && void 0 !== props$jscomp$0.state
+              ? props$jscomp$0.state
+              : null;
+          props$jscomp$0.updater = classComponentUpdater;
+          workInProgress.stateNode = props$jscomp$0;
+          props$jscomp$0._reactInternalFiber = workInProgress;
+          needsContext &&
+            ((needsContext = workInProgress.stateNode),
+            (needsContext.__reactInternalMemoizedUnmaskedChildContext = fn),
+            (needsContext.__reactInternalMemoizedMaskedChildContext = unmaskedContext));
+          mountClassInstance(workInProgress, renderExpirationTime);
+          fn = !0;
+        } else {
+          ctor = workInProgress.type;
+          fn = workInProgress.stateNode;
+          needsContext = workInProgress.memoizedProps;
+          unmaskedContext = workInProgress.pendingProps;
+          fn.props = needsContext;
+          var oldContext = fn.context;
+          props$jscomp$0 = getUnmaskedContext(workInProgress);
+          props$jscomp$0 = getMaskedContext(workInProgress, props$jscomp$0);
+          var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
+          (ctor =
+            "function" === typeof getDerivedStateFromProps ||
+            "function" === typeof fn.getSnapshotBeforeUpdate) ||
+            ("function" !== typeof fn.UNSAFE_componentWillReceiveProps &&
+              "function" !== typeof fn.componentWillReceiveProps) ||
+            ((needsContext !== unmaskedContext ||
+              oldContext !== props$jscomp$0) &&
+              callComponentWillReceiveProps(
+                workInProgress,
+                fn,
+                unmaskedContext,
+                props$jscomp$0
+              ));
+          hasForceUpdate = !1;
+          var oldState = workInProgress.memoizedState;
+          oldContext = fn.state = oldState;
+          var updateQueue = workInProgress.updateQueue;
+          null !== updateQueue &&
+            (processUpdateQueue(
+              workInProgress,
+              updateQueue,
+              unmaskedContext,
+              fn,
+              renderExpirationTime
+            ),
+            (oldContext = workInProgress.memoizedState));
+          needsContext !== unmaskedContext ||
+          oldState !== oldContext ||
+          didPerformWorkStackCursor.current ||
+          hasForceUpdate
+            ? ("function" === typeof getDerivedStateFromProps &&
+                (applyDerivedStateFromProps(
+                  workInProgress,
+                  getDerivedStateFromProps,
+                  unmaskedContext
+                ),
+                (oldContext = workInProgress.memoizedState)),
+              (needsContext =
+                hasForceUpdate ||
+                checkShouldComponentUpdate(
+                  workInProgress,
+                  needsContext,
+                  unmaskedContext,
+                  oldState,
+                  oldContext,
+                  props$jscomp$0
+                ))
+                ? (ctor ||
+                    ("function" !== typeof fn.UNSAFE_componentWillMount &&
+                      "function" !== typeof fn.componentWillMount) ||
+                    ("function" === typeof fn.componentWillMount &&
+                      fn.componentWillMount(),
+                    "function" === typeof fn.UNSAFE_componentWillMount &&
+                      fn.UNSAFE_componentWillMount()),
+                  "function" === typeof fn.componentDidMount &&
+                    (workInProgress.effectTag |= 4))
+                : ("function" === typeof fn.componentDidMount &&
+                    (workInProgress.effectTag |= 4),
+                  (workInProgress.memoizedProps = unmaskedContext),
+                  (workInProgress.memoizedState = oldContext)),
+              (fn.props = unmaskedContext),
+              (fn.state = oldContext),
+              (fn.context = props$jscomp$0),
+              (fn = needsContext))
+            : ("function" === typeof fn.componentDidMount &&
+                (workInProgress.effectTag |= 4),
+              (fn = !1));
+        }
+      else
+        (ctor = workInProgress.type),
+          (fn = workInProgress.stateNode),
+          (unmaskedContext = workInProgress.memoizedProps),
+          (needsContext = workInProgress.pendingProps),
+          (fn.props = unmaskedContext),
+          (oldContext = fn.context),
+          (props$jscomp$0 = getUnmaskedContext(workInProgress)),
+          (props$jscomp$0 = getMaskedContext(workInProgress, props$jscomp$0)),
+          (getDerivedStateFromProps = ctor.getDerivedStateFromProps),
+          (ctor =
+            "function" === typeof getDerivedStateFromProps ||
+            "function" === typeof fn.getSnapshotBeforeUpdate) ||
+            ("function" !== typeof fn.UNSAFE_componentWillReceiveProps &&
+              "function" !== typeof fn.componentWillReceiveProps) ||
+            ((unmaskedContext !== needsContext ||
+              oldContext !== props$jscomp$0) &&
+              callComponentWillReceiveProps(
+                workInProgress,
+                fn,
+                needsContext,
+                props$jscomp$0
+              )),
+          (hasForceUpdate = !1),
+          (oldContext = workInProgress.memoizedState),
+          (oldState = fn.state = oldContext),
+          (updateQueue = workInProgress.updateQueue),
+          null !== updateQueue &&
+            (processUpdateQueue(
+              workInProgress,
+              updateQueue,
+              needsContext,
+              fn,
+              renderExpirationTime
+            ),
+            (oldState = workInProgress.memoizedState)),
+          unmaskedContext !== needsContext ||
+          oldContext !== oldState ||
+          didPerformWorkStackCursor.current ||
+          hasForceUpdate
+            ? ("function" === typeof getDerivedStateFromProps &&
+                (applyDerivedStateFromProps(
+                  workInProgress,
+                  getDerivedStateFromProps,
+                  needsContext
+                ),
+                (oldState = workInProgress.memoizedState)),
+              (getDerivedStateFromProps =
+                hasForceUpdate ||
+                checkShouldComponentUpdate(
+                  workInProgress,
+                  unmaskedContext,
+                  needsContext,
+                  oldContext,
+                  oldState,
+                  props$jscomp$0
+                ))
+                ? (ctor ||
+                    ("function" !== typeof fn.UNSAFE_componentWillUpdate &&
+                      "function" !== typeof fn.componentWillUpdate) ||
+                    ("function" === typeof fn.componentWillUpdate &&
+                      fn.componentWillUpdate(
+                        needsContext,
+                        oldState,
+                        props$jscomp$0
+                      ),
+                    "function" === typeof fn.UNSAFE_componentWillUpdate &&
+                      fn.UNSAFE_componentWillUpdate(
+                        needsContext,
+                        oldState,
+                        props$jscomp$0
+                      )),
+                  "function" === typeof fn.componentDidUpdate &&
+                    (workInProgress.effectTag |= 4),
+                  "function" === typeof fn.getSnapshotBeforeUpdate &&
+                    (workInProgress.effectTag |= 256))
+                : ("function" !== typeof fn.componentDidUpdate ||
+                    (unmaskedContext === current.memoizedProps &&
+                      oldContext === current.memoizedState) ||
+                    (workInProgress.effectTag |= 4),
+                  "function" !== typeof fn.getSnapshotBeforeUpdate ||
+                    (unmaskedContext === current.memoizedProps &&
+                      oldContext === current.memoizedState) ||
+                    (workInProgress.effectTag |= 256),
+                  (workInProgress.memoizedProps = needsContext),
+                  (workInProgress.memoizedState = oldState)),
+              (fn.props = needsContext),
+              (fn.state = oldState),
+              (fn.context = props$jscomp$0),
+              (fn = getDerivedStateFromProps))
+            : ("function" !== typeof fn.componentDidUpdate ||
+                (unmaskedContext === current.memoizedProps &&
+                  oldContext === current.memoizedState) ||
+                (workInProgress.effectTag |= 4),
+              "function" !== typeof fn.getSnapshotBeforeUpdate ||
+                (unmaskedContext === current.memoizedProps &&
+                  oldContext === current.memoizedState) ||
+                (workInProgress.effectTag |= 256),
+              (fn = !1));
+      return finishClassComponent(
+        current,
+        workInProgress,
+        fn,
+        props,
+        renderExpirationTime
+      );
+    case 3:
+      return (
+        pushHostRootContext(workInProgress),
+        (props = workInProgress.updateQueue),
+        null !== props
+          ? ((fn = workInProgress.memoizedState),
+            (fn = null !== fn ? fn.element : null),
+            processUpdateQueue(
+              workInProgress,
+              props,
+              workInProgress.pendingProps,
+              null,
+              renderExpirationTime
+            ),
+            (renderExpirationTime = workInProgress.memoizedState.element),
+            renderExpirationTime === fn
+              ? (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                ))
+              : (reconcileChildren(
+                  current,
+                  workInProgress,
+                  renderExpirationTime
+                ),
+                (current = workInProgress.child)))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 5:
+      return (
+        requiredContext(rootInstanceStackCursor.current),
+        (renderExpirationTime = requiredContext(contextStackCursor$1.current)),
+        (props = workInProgress.type),
+        (props =
+          "AndroidTextInput" === props ||
+          "RCTMultilineTextInputView" === props ||
+          "RCTSinglelineTextInputView" === props ||
+          "RCTText" === props ||
+          "RCTVirtualText" === props),
+        (props =
+          renderExpirationTime.isInAParentText !== props
+            ? { isInAParentText: props }
+            : renderExpirationTime),
+        renderExpirationTime !== props &&
+          (push(contextFiberStackCursor, workInProgress, workInProgress),
+          push(contextStackCursor$1, props, workInProgress)),
+        null === current && tryToClaimNextHydratableInstance(workInProgress),
+        (props = workInProgress.memoizedProps),
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current || props !== renderExpirationTime
+          ? ((props = renderExpirationTime.children),
+            markRef(current, workInProgress),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 6:
+      return (
+        null === current && tryToClaimNextHydratableInstance(workInProgress),
+        (workInProgress.memoizedProps = workInProgress.pendingProps),
+        null
+      );
+    case 16:
+      return null;
+    case 4:
+      return (
+        pushHostContainer(
+          workInProgress,
+          workInProgress.stateNode.containerInfo
+        ),
+        (props = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== props
+          ? (null === current
+              ? (workInProgress.child = reconcileChildFibers(
+                  workInProgress,
+                  null,
+                  props,
+                  renderExpirationTime
+                ))
+              : reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = props),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 14:
+      return (
+        (props = workInProgress.type.render),
+        (renderExpirationTime = workInProgress.pendingProps),
+        (fn = workInProgress.ref),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime ||
+        fn !== (null !== current ? current.ref : null)
+          ? ((props = props(renderExpirationTime, fn)),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 10:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime
+          ? (reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 11:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps.children),
+        didPerformWorkStackCursor.current ||
+        (null !== renderExpirationTime &&
+          workInProgress.memoizedProps !== renderExpirationTime)
+          ? (reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 15:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps),
+        (workInProgress.effectTag |= 4),
+        workInProgress.memoizedProps === renderExpirationTime
+          ? (current = bailoutOnAlreadyFinishedWork(current, workInProgress))
+          : (reconcileChildren(
+              current,
+              workInProgress,
+              renderExpirationTime.children
+            ),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child)),
+        current
+      );
+    case 13:
+      return updateContextProvider(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case 12:
+      a: if (
+        ((fn = workInProgress.type),
+        (unmaskedContext = workInProgress.pendingProps),
+        (needsContext = workInProgress.memoizedProps),
+        (props = fn._currentValue2),
+        (props$jscomp$0 = fn._changedBits2),
+        didPerformWorkStackCursor.current ||
+          0 !== props$jscomp$0 ||
+          needsContext !== unmaskedContext)
+      ) {
+        workInProgress.memoizedProps = unmaskedContext;
+        ctor = unmaskedContext.unstable_observedBits;
+        if (void 0 === ctor || null === ctor) ctor = 1073741823;
+        workInProgress.stateNode = ctor;
+        if (0 !== (props$jscomp$0 & ctor))
+          propagateContextChange(
+            workInProgress,
+            fn,
+            props$jscomp$0,
+            renderExpirationTime
+          );
+        else if (needsContext === unmaskedContext) {
+          current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          break a;
+        }
+        renderExpirationTime = unmaskedContext.children;
+        renderExpirationTime = renderExpirationTime(props);
+        workInProgress.effectTag |= 1;
+        reconcileChildren(current, workInProgress, renderExpirationTime);
+        current = workInProgress.child;
+      } else current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+      return current;
+    default:
+      invariant(
+        !1,
+        "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
+}
+function appendAllChildren(parent, workInProgress) {
+  for (var node = workInProgress.child; null !== node; ) {
+    if (5 === node.tag || 6 === node.tag)
+      FabricUIManager.appendChild(parent.node, node.stateNode.node);
+    else if (4 !== node.tag && null !== node.child) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === workInProgress) break;
+    for (; null === node.sibling; ) {
+      if (null === node.return || node.return === workInProgress) return;
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+}
+var updateHostContainer = void 0,
+  updateHostComponent$1 = void 0,
+  updateHostText$1 = void 0;
+updateHostContainer = function(workInProgress) {
+  var portalOrRoot = workInProgress.stateNode;
+  if (null !== workInProgress.firstEffect) {
+    var container = portalOrRoot.containerInfo,
+      newChildSet = FabricUIManager.createChildSet(container);
+    a: for (var node = workInProgress.child; null !== node; ) {
+      if (5 === node.tag || 6 === node.tag)
+        FabricUIManager.appendChildToSet(newChildSet, node.stateNode.node);
+      else if (4 !== node.tag && null !== node.child) {
+        node.child.return = node;
+        node = node.child;
+        continue;
+      }
+      if (node === workInProgress) break a;
+      for (; null === node.sibling; ) {
+        if (null === node.return || node.return === workInProgress) break a;
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+    portalOrRoot.pendingChildren = newChildSet;
+    workInProgress.effectTag |= 4;
+    FabricUIManager.completeRoot(container, newChildSet);
+  }
+};
+updateHostComponent$1 = function(current, workInProgress, updatePayload) {
+  var childrenUnchanged = null === workInProgress.firstEffect;
+  current = current.stateNode;
+  if (childrenUnchanged && null === updatePayload)
+    workInProgress.stateNode = current;
+  else {
+    var node = current.node;
+    updatePayload = {
+      node: childrenUnchanged
+        ? null !== updatePayload
+          ? FabricUIManager.cloneNodeWithNewProps(
+              node,
+              updatePayload,
+              workInProgress
+            )
+          : FabricUIManager.cloneNode(node, workInProgress)
+        : null !== updatePayload
+          ? FabricUIManager.cloneNodeWithNewChildrenAndProps(
+              node,
+              updatePayload,
+              workInProgress
+            )
+          : FabricUIManager.cloneNodeWithNewChildren(node, workInProgress),
+      canonical: current.canonical
+    };
+    workInProgress.stateNode = updatePayload;
+    childrenUnchanged
+      ? (workInProgress.effectTag |= 4)
+      : appendAllChildren(updatePayload, workInProgress);
+  }
+};
+updateHostText$1 = function(current, workInProgress, oldText, newText) {
+  oldText !== newText &&
+    ((current = requiredContext(rootInstanceStackCursor.current)),
+    (oldText = requiredContext(contextStackCursor$1.current)),
+    (workInProgress.stateNode = createTextInstance(
+      newText,
+      current,
+      oldText,
+      workInProgress
+    )),
+    (workInProgress.effectTag |= 4));
+};
+function completeWork(current, workInProgress) {
+  var newProps = workInProgress.pendingProps;
+  workInProgress.mode & 4 && recordElapsedActualRenderTime(workInProgress);
+  switch (workInProgress.tag) {
+    case 1:
+      return null;
+    case 2:
+      return popContextProvider(workInProgress), null;
+    case 3:
+      popHostContainer(workInProgress);
+      popTopLevelContextObject(workInProgress);
+      newProps = workInProgress.stateNode;
+      newProps.pendingContext &&
+        ((newProps.context = newProps.pendingContext),
+        (newProps.pendingContext = null));
+      if (null === current || null === current.child)
+        workInProgress.effectTag &= -3;
+      updateHostContainer(workInProgress);
+      return null;
+    case 5:
+      popHostContext(workInProgress);
+      var rootContainerInstance = requiredContext(
+          rootInstanceStackCursor.current
+        ),
+        type = workInProgress.type;
+      if (null !== current && null != workInProgress.stateNode) {
+        var oldProps = current.memoizedProps,
+          instance = workInProgress.stateNode,
+          currentHostContext = requiredContext(contextStackCursor$1.current),
+          updatePayload = diffProperties(
+            null,
+            oldProps,
+            newProps,
+            instance.canonical.viewConfig.validAttributes
+          );
+        instance.canonical.currentProps = newProps;
+        updateHostComponent$1(
+          current,
+          workInProgress,
+          updatePayload,
+          type,
+          oldProps,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        );
+        current.ref !== workInProgress.ref && (workInProgress.effectTag |= 128);
+      } else {
+        if (!newProps)
+          return (
+            invariant(
+              null !== workInProgress.stateNode,
+              "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+            ),
+            null
+          );
+        instance = requiredContext(contextStackCursor$1.current);
+        current = nextReactTag;
+        nextReactTag += 2;
+        oldProps = ReactNativeViewConfigRegistry.get(type);
+        invariant(
+          "RCTView" !== type || !instance.isInAParentText,
+          "Nesting of <View> within <Text> is not currently supported."
+        );
+        type = diffProperties(
+          null,
+          emptyObject$1,
+          newProps,
+          oldProps.validAttributes
+        );
+        rootContainerInstance = FabricUIManager.createNode(
+          current,
+          oldProps.uiViewClassName,
+          rootContainerInstance,
+          type,
+          workInProgress
+        );
+        newProps = new ReactFabricHostComponent(current, oldProps, newProps);
+        newProps = { node: rootContainerInstance, canonical: newProps };
+        appendAllChildren(newProps, workInProgress);
+        workInProgress.stateNode = newProps;
+        null !== workInProgress.ref && (workInProgress.effectTag |= 128);
+      }
+      return null;
+    case 6:
+      if (current && null != workInProgress.stateNode)
+        updateHostText$1(
+          current,
+          workInProgress,
+          current.memoizedProps,
+          newProps
+        );
+      else {
+        if ("string" !== typeof newProps)
+          return (
+            invariant(
+              null !== workInProgress.stateNode,
+              "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+            ),
+            null
+          );
+        rootContainerInstance = requiredContext(
+          rootInstanceStackCursor.current
+        );
+        type = requiredContext(contextStackCursor$1.current);
+        workInProgress.stateNode = createTextInstance(
+          newProps,
+          rootContainerInstance,
+          type,
+          workInProgress
+        );
+      }
+      return null;
+    case 14:
+      return null;
+    case 16:
+      return null;
+    case 10:
+      return null;
+    case 11:
+      return null;
+    case 15:
+      return null;
+    case 4:
+      return (
+        popHostContainer(workInProgress),
+        updateHostContainer(workInProgress),
+        null
+      );
+    case 13:
+      return popProvider(workInProgress), null;
+    case 12:
+      return null;
+    case 0:
+      invariant(
+        !1,
+        "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
+      );
+    default:
+      invariant(
+        !1,
+        "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
+}
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source,
+    stack = errorInfo.stack;
+  null === stack &&
+    null !== source &&
+    (stack = getStackAddendumByWorkInProgressFiber(source));
+  null !== source && getComponentName(source);
+  source = null !== stack ? stack : "";
+  errorInfo = errorInfo.value;
+  null !== boundary && 2 === boundary.tag && getComponentName(boundary);
+  try {
+    if (errorInfo instanceof Error) {
+      var message = errorInfo.message,
+        name = errorInfo.name;
+      var errorToHandle = errorInfo;
+      try {
+        errorToHandle.message =
+          (message ? name + ": " + message : name) +
+          "\n\nThis error is located at:" +
+          source;
+      } catch (e) {}
+    } else
+      errorToHandle =
+        "string" === typeof errorInfo
+          ? Error(errorInfo + "\n\nThis error is located at:" + source)
+          : Error("Unspecified error at:" + source);
+    ExceptionsManager.handleException(errorToHandle, !1);
+  } catch (e) {
+    (e && e.suppressReactErrorLogging) || console.error(e);
+  }
+}
+function safelyDetachRef(current) {
+  var ref = current.ref;
+  if (null !== ref)
+    if ("function" === typeof ref)
+      try {
+        ref(null);
+      } catch (refError) {
+        captureCommitPhaseError(current, refError);
+      }
+    else ref.current = null;
+}
+function commitWork(current, finishedWork) {
+  switch (finishedWork.tag) {
+    case 2:
+      break;
+    case 5:
+      break;
+    case 6:
+      break;
+    case 3:
+    case 4:
+      break;
+    default:
+      invariant(
+        !1,
+        "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
+}
+function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+  expirationTime = createUpdate(expirationTime);
+  expirationTime.tag = 3;
+  expirationTime.payload = { element: null };
+  var error = errorInfo.value;
+  expirationTime.callback = function() {
+    onUncaughtError(error);
+    logError(fiber, errorInfo);
+  };
+  return expirationTime;
+}
+function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+  expirationTime = createUpdate(expirationTime);
+  expirationTime.tag = 3;
+  var inst = fiber.stateNode;
+  null !== inst &&
+    "function" === typeof inst.componentDidCatch &&
+    (expirationTime.callback = function() {
+      null === legacyErrorBoundariesThatAlreadyFailed
+        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([this]))
+        : legacyErrorBoundariesThatAlreadyFailed.add(this);
+      var error = errorInfo.value,
+        stack = errorInfo.stack;
+      logError(fiber, errorInfo);
+      this.componentDidCatch(error, {
+        componentStack: null !== stack ? stack : ""
+      });
+    });
+  return expirationTime;
+}
+function unwindWork(workInProgress) {
+  workInProgress.mode & 4 && recordElapsedActualRenderTime(workInProgress);
+  switch (workInProgress.tag) {
+    case 2:
+      popContextProvider(workInProgress);
+      var effectTag = workInProgress.effectTag;
+      return effectTag & 1024
+        ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+          workInProgress)
+        : null;
+    case 3:
+      return (
+        popHostContainer(workInProgress),
+        popTopLevelContextObject(workInProgress),
+        (effectTag = workInProgress.effectTag),
+        effectTag & 1024
+          ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+            workInProgress)
+          : null
+      );
+    case 5:
+      return popHostContext(workInProgress), null;
+    case 16:
+      return (
+        (effectTag = workInProgress.effectTag),
+        effectTag & 1024
+          ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+            workInProgress)
+          : null
+      );
+    case 4:
+      return popHostContainer(workInProgress), null;
+    case 13:
+      return popProvider(workInProgress), null;
+    default:
+      return null;
+  }
+}
+var originalStartTimeMs = now$1(),
+  mostRecentCurrentTime = 2,
+  mostRecentCurrentTimeMs = originalStartTimeMs,
+  lastUniqueAsyncExpiration = 0,
+  expirationContext = 0,
+  isWorking = !1,
+  nextUnitOfWork = null,
+  nextRoot = null,
+  nextRenderExpirationTime = 0,
+  nextLatestTimeoutMs = -1,
+  nextRenderDidError = !1,
+  nextEffect = null,
+  isCommitting$1 = !1,
+  legacyErrorBoundariesThatAlreadyFailed = null;
+function resetStack() {
+  if (null !== nextUnitOfWork)
+    for (
+      var interruptedWork = nextUnitOfWork.return;
+      null !== interruptedWork;
+
+    ) {
+      var interruptedWork$jscomp$0 = interruptedWork;
+      interruptedWork$jscomp$0.mode & 4 &&
+        (resumeActualRenderTimerIfPaused(),
+        recordElapsedActualRenderTime(interruptedWork$jscomp$0));
+      switch (interruptedWork$jscomp$0.tag) {
+        case 2:
+          popContextProvider(interruptedWork$jscomp$0);
+          break;
+        case 3:
+          popHostContainer(interruptedWork$jscomp$0);
+          popTopLevelContextObject(interruptedWork$jscomp$0);
+          break;
+        case 5:
+          popHostContext(interruptedWork$jscomp$0);
+          break;
+        case 4:
+          popHostContainer(interruptedWork$jscomp$0);
+          break;
+        case 13:
+          popProvider(interruptedWork$jscomp$0);
+      }
+      interruptedWork = interruptedWork.return;
+    }
+  nextRoot = null;
+  nextRenderExpirationTime = 0;
+  nextLatestTimeoutMs = -1;
+  nextRenderDidError = !1;
+  nextUnitOfWork = null;
+}
+function completeUnitOfWork(workInProgress$jscomp$0) {
+  for (;;) {
+    var current = workInProgress$jscomp$0.alternate,
+      returnFiber = workInProgress$jscomp$0.return,
+      siblingFiber = workInProgress$jscomp$0.sibling;
+    if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
+      current = completeWork(
+        current,
+        workInProgress$jscomp$0,
+        nextRenderExpirationTime
+      );
+      var workInProgress = workInProgress$jscomp$0;
+      if (
+        1073741823 === nextRenderExpirationTime ||
+        1073741823 !== workInProgress.expirationTime
+      ) {
+        var newExpirationTime = 0;
+        switch (workInProgress.tag) {
+          case 3:
+          case 2:
+            var updateQueue = workInProgress.updateQueue;
+            null !== updateQueue &&
+              (newExpirationTime = updateQueue.expirationTime);
+        }
+        if (workInProgress.mode & 4) {
+          updateQueue = workInProgress.selfBaseTime;
+          for (var child = workInProgress.child; null !== child; )
+            (updateQueue += child.treeBaseTime),
+              0 !== child.expirationTime &&
+                (0 === newExpirationTime ||
+                  newExpirationTime > child.expirationTime) &&
+                (newExpirationTime = child.expirationTime),
+              (child = child.sibling);
+          workInProgress.treeBaseTime = updateQueue;
+        } else
+          for (updateQueue = workInProgress.child; null !== updateQueue; )
+            0 !== updateQueue.expirationTime &&
+              (0 === newExpirationTime ||
+                newExpirationTime > updateQueue.expirationTime) &&
+              (newExpirationTime = updateQueue.expirationTime),
+              (updateQueue = updateQueue.sibling);
+        workInProgress.expirationTime = newExpirationTime;
+      }
+      if (null !== current) return current;
+      null !== returnFiber &&
+        0 === (returnFiber.effectTag & 512) &&
+        (null === returnFiber.firstEffect &&
+          (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
+        null !== workInProgress$jscomp$0.lastEffect &&
+          (null !== returnFiber.lastEffect &&
+            (returnFiber.lastEffect.nextEffect =
+              workInProgress$jscomp$0.firstEffect),
+          (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
+        1 < workInProgress$jscomp$0.effectTag &&
+          (null !== returnFiber.lastEffect
+            ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
+            : (returnFiber.firstEffect = workInProgress$jscomp$0),
+          (returnFiber.lastEffect = workInProgress$jscomp$0)));
+    } else {
+      workInProgress$jscomp$0 = unwindWork(
+        workInProgress$jscomp$0,
+        nextRenderExpirationTime
+      );
+      if (null !== workInProgress$jscomp$0)
+        return (
+          (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
+        );
+      null !== returnFiber &&
+        ((returnFiber.firstEffect = returnFiber.lastEffect = null),
+        (returnFiber.effectTag |= 512));
+    }
+    if (null !== siblingFiber) return siblingFiber;
+    if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+    else break;
+  }
+  return null;
+}
+function performUnitOfWork(workInProgress) {
+  var current = workInProgress.alternate;
+  workInProgress.mode & 4 && (baseStartTime = now$1());
+  current = beginWork(current, workInProgress, nextRenderExpirationTime);
+  workInProgress.mode & 4 &&
+    (-1 !== baseStartTime &&
+      (workInProgress.selfBaseTime = now$1() - baseStartTime),
+    (baseStartTime = -1));
+  null === current && (current = completeUnitOfWork(workInProgress));
+  ReactCurrentOwner.current = null;
+  return current;
+}
+function renderRoot(root$jscomp$0, isYieldy) {
+  invariant(
+    !isWorking,
+    "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+  );
+  isWorking = !0;
+  var expirationTime = root$jscomp$0.nextExpirationTimeToWorkOn;
+  if (
+    expirationTime !== nextRenderExpirationTime ||
+    root$jscomp$0 !== nextRoot ||
+    null === nextUnitOfWork
+  )
+    resetStack(),
+      (nextRoot = root$jscomp$0),
+      (nextRenderExpirationTime = expirationTime),
+      (nextLatestTimeoutMs = -1),
+      (nextRenderDidError = !1),
+      (nextUnitOfWork = createWorkInProgress(
+        nextRoot.current,
+        null,
+        nextRenderExpirationTime
+      )),
+      (root$jscomp$0.pendingCommitExpirationTime = 0);
+  var didFatal = !1;
+  do {
+    try {
+      if (isYieldy) {
+        for (; null !== nextUnitOfWork && !shouldYield(); )
+          nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+        0 === timerPausedAt && (timerPausedAt = now$1());
+      } else
+        for (; null !== nextUnitOfWork; )
+          nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+    } catch (thrownValue) {
+      if (((baseStartTime = -1), null === nextUnitOfWork))
+        (didFatal = !0), onUncaughtError(thrownValue);
+      else {
+        invariant(
+          null !== nextUnitOfWork,
+          "Failed to replay rendering after an error. This is likely caused by a bug in React. Please file an issue with a reproducing case to help us find it."
+        );
+        isYieldy = nextUnitOfWork;
+        var returnFiber = isYieldy.return;
+        if (null === returnFiber) {
+          didFatal = !0;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        a: {
+          var root = root$jscomp$0,
+            returnFiber$jscomp$0 = returnFiber,
+            sourceFiber = isYieldy,
+            value = thrownValue;
+          returnFiber = nextRenderExpirationTime;
+          sourceFiber.effectTag |= 512;
+          sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+          nextRenderDidError = !0;
+          if (
+            (root.didError || 1 === returnFiber) &&
+            (returnFiber === root.latestPendingTime ||
+              returnFiber === root.latestSuspendedTime)
+          ) {
+            value = createCapturedValue(value, sourceFiber);
+            root = returnFiber$jscomp$0;
+            do {
+              switch (root.tag) {
+                case 3:
+                  root.effectTag |= 1024;
+                  value = createRootErrorUpdate(root, value, returnFiber);
+                  enqueueCapturedUpdate(root, value, returnFiber);
+                  break a;
+                case 2:
+                  if (
+                    ((returnFiber$jscomp$0 = value),
+                    (sourceFiber = root.stateNode),
+                    0 === (root.effectTag & 64) &&
+                      null !== sourceFiber &&
+                      "function" === typeof sourceFiber.componentDidCatch &&
+                      (null === legacyErrorBoundariesThatAlreadyFailed ||
+                        !legacyErrorBoundariesThatAlreadyFailed.has(
+                          sourceFiber
+                        )))
+                  ) {
+                    root.effectTag |= 1024;
+                    value = createClassErrorUpdate(
+                      root,
+                      returnFiber$jscomp$0,
+                      returnFiber
+                    );
+                    enqueueCapturedUpdate(root, value, returnFiber);
+                    break a;
+                  }
+              }
+              root = root.return;
+            } while (null !== root);
+          }
+        }
+        nextUnitOfWork = completeUnitOfWork(isYieldy);
+      }
+    }
+    break;
+  } while (1);
+  isWorking = !1;
+  didFatal
+    ? (root$jscomp$0.finishedWork = null)
+    : null === nextUnitOfWork
+      ? ((didFatal = root$jscomp$0.current.alternate),
+        invariant(
+          null !== didFatal,
+          "Finished root should have a work-in-progress. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        0 === (didFatal.effectTag & 512)
+          ? ((root$jscomp$0.pendingCommitExpirationTime = expirationTime),
+            (root$jscomp$0.finishedWork = didFatal))
+          : (!nextRenderDidError ||
+            (expirationTime !== root$jscomp$0.latestPendingTime &&
+              expirationTime !== root$jscomp$0.latestSuspendedTime)
+              ? ((didFatal = root$jscomp$0.earliestPendingTime),
+                (isYieldy = root$jscomp$0.latestPendingTime),
+                didFatal === expirationTime
+                  ? (root$jscomp$0.earliestPendingTime =
+                      isYieldy === expirationTime
+                        ? (root$jscomp$0.latestPendingTime = 0)
+                        : isYieldy)
+                  : isYieldy === expirationTime &&
+                    (root$jscomp$0.latestPendingTime = didFatal),
+                (didFatal = root$jscomp$0.latestSuspendedTime),
+                didFatal === expirationTime &&
+                  (root$jscomp$0.latestPingedTime = 0),
+                (isYieldy = root$jscomp$0.earliestSuspendedTime),
+                0 === isYieldy
+                  ? (root$jscomp$0.earliestSuspendedTime = root$jscomp$0.latestSuspendedTime = expirationTime)
+                  : isYieldy > expirationTime
+                    ? (root$jscomp$0.earliestSuspendedTime = expirationTime)
+                    : didFatal < expirationTime &&
+                      (root$jscomp$0.latestSuspendedTime = expirationTime))
+              : (root$jscomp$0.didError = !0),
+            findNextPendingPriorityLevel(root$jscomp$0),
+            onSuspend(
+              root$jscomp$0,
+              expirationTime,
+              root$jscomp$0.expirationTime,
+              nextLatestTimeoutMs
+            )))
+      : (root$jscomp$0.finishedWork = null);
+}
+function captureCommitPhaseError(fiber, error) {
+  var JSCompiler_inline_result;
+  a: {
+    invariant(
+      !isWorking || isCommitting$1,
+      "dispatch: Cannot dispatch during the render phase."
+    );
+    for (
+      JSCompiler_inline_result = fiber.return;
+      null !== JSCompiler_inline_result;
+
+    ) {
+      switch (JSCompiler_inline_result.tag) {
+        case 2:
+          var instance = JSCompiler_inline_result.stateNode;
+          if (
+            "function" ===
+              typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
+            ("function" === typeof instance.componentDidCatch &&
+              (null === legacyErrorBoundariesThatAlreadyFailed ||
+                !legacyErrorBoundariesThatAlreadyFailed.has(instance)))
+          ) {
+            fiber = createCapturedValue(error, fiber);
+            fiber = createClassErrorUpdate(JSCompiler_inline_result, fiber, 1);
+            enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+            scheduleWork(JSCompiler_inline_result, 1);
+            JSCompiler_inline_result = void 0;
+            break a;
+          }
+          break;
+        case 3:
+          fiber = createCapturedValue(error, fiber);
+          fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+          enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+          scheduleWork(JSCompiler_inline_result, 1);
+          JSCompiler_inline_result = void 0;
+          break a;
+      }
+      JSCompiler_inline_result = JSCompiler_inline_result.return;
+    }
+    3 === fiber.tag &&
+      ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
+      (JSCompiler_inline_result = createRootErrorUpdate(
+        fiber,
+        JSCompiler_inline_result,
+        1
+      )),
+      enqueueUpdate(fiber, JSCompiler_inline_result, 1),
+      scheduleWork(fiber, 1));
+    JSCompiler_inline_result = void 0;
+  }
+  return JSCompiler_inline_result;
+}
+function computeExpirationForFiber(currentTime, fiber) {
+  currentTime =
+    0 !== expirationContext
+      ? expirationContext
+      : isWorking
+        ? isCommitting$1 ? 1 : nextRenderExpirationTime
+        : fiber.mode & 1
+          ? isBatchingInteractiveUpdates
+            ? 2 + 10 * ((((currentTime - 2 + 15) / 10) | 0) + 1)
+            : 2 + 25 * ((((currentTime - 2 + 500) / 25) | 0) + 1)
+          : 1;
+  isBatchingInteractiveUpdates &&
+    (0 === lowestPendingInteractiveExpirationTime ||
+      currentTime > lowestPendingInteractiveExpirationTime) &&
+    (lowestPendingInteractiveExpirationTime = currentTime);
+  return currentTime;
+}
+function scheduleWork(fiber, expirationTime) {
+  for (; null !== fiber; ) {
+    if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
+      fiber.expirationTime = expirationTime;
+    null !== fiber.alternate &&
+      (0 === fiber.alternate.expirationTime ||
+        fiber.alternate.expirationTime > expirationTime) &&
+      (fiber.alternate.expirationTime = expirationTime);
+    if (null === fiber.return)
+      if (3 === fiber.tag) {
+        var root = fiber.stateNode;
+        !isWorking &&
+          0 !== nextRenderExpirationTime &&
+          expirationTime < nextRenderExpirationTime &&
+          resetStack();
+        markPendingPriorityLevel(root, expirationTime);
+        (isWorking && !isCommitting$1 && nextRoot === root) ||
+          requestWork(root, root.expirationTime);
+        nestedUpdateCount > NESTED_UPDATE_LIMIT &&
+          invariant(
+            !1,
+            "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
+          );
+      } else break;
+    fiber = fiber.return;
+  }
+}
+function recalculateCurrentTime() {
+  mostRecentCurrentTimeMs = now$1() - originalStartTimeMs;
+  return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
+}
+function syncUpdates(fn, a, b, c, d) {
+  var previousExpirationContext = expirationContext;
+  expirationContext = 1;
+  try {
+    return fn(a, b, c, d);
+  } finally {
+    expirationContext = previousExpirationContext;
+  }
+}
+var firstScheduledRoot = null,
+  lastScheduledRoot = null,
+  callbackExpirationTime = 0,
+  callbackID = void 0,
+  isRendering = !1,
+  nextFlushedRoot = null,
+  nextFlushedExpirationTime = 0,
+  lowestPendingInteractiveExpirationTime = 0,
+  deadlineDidExpire = !1,
+  hasUnhandledError = !1,
+  unhandledError = null,
+  deadline = null,
+  isBatchingUpdates = !1,
+  isUnbatchingUpdates = !1,
+  isBatchingInteractiveUpdates = !1,
+  completedBatches = null,
+  NESTED_UPDATE_LIMIT = 1e3,
+  nestedUpdateCount = 0,
+  timeHeuristicForUnitOfWork = 1;
+function scheduleCallbackWithExpirationTime(expirationTime) {
+  if (0 !== callbackExpirationTime) {
+    if (expirationTime > callbackExpirationTime) return;
+    if (null !== callbackID) {
+      var callbackID$jscomp$0 = callbackID;
+      scheduledCallback = null;
+      clearTimeout(callbackID$jscomp$0);
+    }
+  }
+  callbackExpirationTime = expirationTime;
+  now$1();
+  scheduledCallback = performAsyncWork;
+  callbackID = setTimeout(setTimeoutCallback, 1);
+}
+function onSuspend(root, suspendedExpirationTime, expirationTime, timeoutMs) {
+  0 <= timeoutMs &&
+    setTimeout(function() {
+      var latestSuspendedTime = root.latestSuspendedTime;
+      0 !== latestSuspendedTime &&
+        latestSuspendedTime <= suspendedExpirationTime &&
+        ((latestSuspendedTime = root.latestPingedTime),
+        0 === latestSuspendedTime ||
+          latestSuspendedTime < suspendedExpirationTime) &&
+        (root.latestPingedTime = suspendedExpirationTime);
+      findNextPendingPriorityLevel(root);
+      latestSuspendedTime = root.expirationTime;
+      0 !== latestSuspendedTime && requestWork(root, latestSuspendedTime);
+    }, timeoutMs);
+  root.expirationTime = expirationTime;
+}
+function requestWork(root, expirationTime) {
+  if (null === root.nextScheduledRoot)
+    (root.expirationTime = expirationTime),
+      null === lastScheduledRoot
+        ? ((firstScheduledRoot = lastScheduledRoot = root),
+          (root.nextScheduledRoot = root))
+        : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
+          (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
+  else {
+    var remainingExpirationTime = root.expirationTime;
+    if (
+      0 === remainingExpirationTime ||
+      expirationTime < remainingExpirationTime
+    )
+      root.expirationTime = expirationTime;
+  }
+  isRendering ||
+    (isBatchingUpdates
+      ? isUnbatchingUpdates &&
+        ((nextFlushedRoot = root),
+        (nextFlushedExpirationTime = 1),
+        performWorkOnRoot(root, 1, !1))
+      : 1 === expirationTime
+        ? performWork(1, null)
+        : scheduleCallbackWithExpirationTime(expirationTime));
+}
+function findHighestPriorityRoot() {
+  var highestPriorityWork = 0,
+    highestPriorityRoot = null;
+  if (null !== lastScheduledRoot)
+    for (
+      var previousScheduledRoot = lastScheduledRoot, root = firstScheduledRoot;
+      null !== root;
+
+    ) {
+      var remainingExpirationTime = root.expirationTime;
+      if (0 === remainingExpirationTime) {
+        invariant(
+          null !== previousScheduledRoot && null !== lastScheduledRoot,
+          "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
+        );
+        if (root === root.nextScheduledRoot) {
+          firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
+          break;
+        } else if (root === firstScheduledRoot)
+          (firstScheduledRoot = remainingExpirationTime =
+            root.nextScheduledRoot),
+            (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
+            (root.nextScheduledRoot = null);
+        else if (root === lastScheduledRoot) {
+          lastScheduledRoot = previousScheduledRoot;
+          lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+          root.nextScheduledRoot = null;
+          break;
+        } else
+          (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
+            (root.nextScheduledRoot = null);
+        root = previousScheduledRoot.nextScheduledRoot;
+      } else {
+        if (
+          0 === highestPriorityWork ||
+          remainingExpirationTime < highestPriorityWork
+        )
+          (highestPriorityWork = remainingExpirationTime),
+            (highestPriorityRoot = root);
+        if (root === lastScheduledRoot) break;
+        previousScheduledRoot = root;
+        root = root.nextScheduledRoot;
+      }
+    }
+  previousScheduledRoot = nextFlushedRoot;
+  null !== previousScheduledRoot &&
+  previousScheduledRoot === highestPriorityRoot &&
+  1 === highestPriorityWork
+    ? nestedUpdateCount++
+    : (nestedUpdateCount = 0);
+  nextFlushedRoot = highestPriorityRoot;
+  nextFlushedExpirationTime = highestPriorityWork;
+}
+function performAsyncWork(dl) {
+  performWork(0, dl);
+}
+function performWork(minExpirationTime, dl) {
+  deadline = dl;
+  findHighestPriorityRoot();
+  resumeActualRenderTimerIfPaused();
+  if (null !== deadline)
+    for (
+      ;
+      null !== nextFlushedRoot &&
+      0 !== nextFlushedExpirationTime &&
+      (0 === minExpirationTime ||
+        minExpirationTime >= nextFlushedExpirationTime) &&
+      (!deadlineDidExpire ||
+        recalculateCurrentTime() >= nextFlushedExpirationTime);
+
+    )
+      recalculateCurrentTime(),
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !0),
+        findHighestPriorityRoot();
+  else
+    for (
+      ;
+      null !== nextFlushedRoot &&
+      0 !== nextFlushedExpirationTime &&
+      (0 === minExpirationTime ||
+        minExpirationTime >= nextFlushedExpirationTime);
+
+    )
+      performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
+        findHighestPriorityRoot();
+  null !== deadline && ((callbackExpirationTime = 0), (callbackID = null));
+  0 !== nextFlushedExpirationTime &&
+    scheduleCallbackWithExpirationTime(nextFlushedExpirationTime);
+  deadline = null;
+  deadlineDidExpire = !1;
+  finishRendering();
+}
+function finishRendering() {
+  nestedUpdateCount = 0;
+  if (null !== completedBatches) {
+    var batches = completedBatches;
+    completedBatches = null;
+    for (var i = 0; i < batches.length; i++) {
+      var batch = batches[i];
+      try {
+        batch._onComplete();
+      } catch (error) {
+        hasUnhandledError ||
+          ((hasUnhandledError = !0), (unhandledError = error));
+      }
+    }
+  }
+  if (hasUnhandledError)
+    throw ((batches = unhandledError),
+    (unhandledError = null),
+    (hasUnhandledError = !1),
+    batches);
+}
+function performWorkOnRoot(root, expirationTime, isYieldy) {
+  invariant(
+    !isRendering,
+    "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+  );
+  isRendering = !0;
+  isYieldy
+    ? ((isYieldy = root.finishedWork),
+      null !== isYieldy
+        ? completeRoot$1(root, isYieldy, expirationTime)
+        : ((root.finishedWork = null),
+          renderRoot(root, !0),
+          (isYieldy = root.finishedWork),
+          null !== isYieldy &&
+            (shouldYield()
+              ? ((root.finishedWork = isYieldy),
+                0 === timerPausedAt && (timerPausedAt = now$1()))
+              : completeRoot$1(root, isYieldy, expirationTime))))
+    : ((isYieldy = root.finishedWork),
+      null !== isYieldy
+        ? completeRoot$1(root, isYieldy, expirationTime)
+        : ((root.finishedWork = null),
+          renderRoot(root, !1),
+          (isYieldy = root.finishedWork),
+          null !== isYieldy && completeRoot$1(root, isYieldy, expirationTime)));
+  isRendering = !1;
+}
+function completeRoot$1(root, finishedWork$jscomp$0, expirationTime) {
+  var firstBatch = root.firstBatch;
+  if (
+    null !== firstBatch &&
+    firstBatch._expirationTime <= expirationTime &&
+    (null === completedBatches
+      ? (completedBatches = [firstBatch])
+      : completedBatches.push(firstBatch),
+    firstBatch._defer)
+  ) {
+    root.finishedWork = finishedWork$jscomp$0;
+    root.expirationTime = 0;
+    return;
+  }
+  root.finishedWork = null;
+  isCommitting$1 = isWorking = !0;
+  invariant(
+    root.current !== finishedWork$jscomp$0,
+    "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
+  );
+  expirationTime = root.pendingCommitExpirationTime;
+  invariant(
+    0 !== expirationTime,
+    "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
+  );
+  root.pendingCommitExpirationTime = 0;
+  firstBatch = finishedWork$jscomp$0.expirationTime;
+  recalculateCurrentTime();
+  root.didError = !1;
+  if (0 === firstBatch)
+    (root.earliestPendingTime = 0),
+      (root.latestPendingTime = 0),
+      (root.earliestSuspendedTime = 0),
+      (root.latestSuspendedTime = 0),
+      (root.latestPingedTime = 0);
+  else {
+    var latestPendingTime = root.latestPendingTime;
+    0 !== latestPendingTime &&
+      (latestPendingTime < firstBatch
+        ? (root.earliestPendingTime = root.latestPendingTime = 0)
+        : root.earliestPendingTime < firstBatch &&
+          (root.earliestPendingTime = root.latestPendingTime));
+    latestPendingTime = root.earliestSuspendedTime;
+    0 === latestPendingTime
+      ? markPendingPriorityLevel(root, firstBatch)
+      : firstBatch > root.latestSuspendedTime
+        ? ((root.earliestSuspendedTime = 0),
+          (root.latestSuspendedTime = 0),
+          (root.latestPingedTime = 0),
+          markPendingPriorityLevel(root, firstBatch))
+        : firstBatch < latestPendingTime &&
+          markPendingPriorityLevel(root, firstBatch);
+  }
+  findNextPendingPriorityLevel(root);
+  ReactCurrentOwner.current = null;
+  1 < finishedWork$jscomp$0.effectTag
+    ? null !== finishedWork$jscomp$0.lastEffect
+      ? ((finishedWork$jscomp$0.lastEffect.nextEffect = finishedWork$jscomp$0),
+        (firstBatch = finishedWork$jscomp$0.firstEffect))
+      : (firstBatch = finishedWork$jscomp$0)
+    : (firstBatch = finishedWork$jscomp$0.firstEffect);
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    latestPendingTime = !1;
+    var error = void 0;
+    try {
+      for (; null !== nextEffect; ) {
+        if (nextEffect.effectTag & 256) {
+          var current = nextEffect.alternate,
+            finishedWork = nextEffect;
+          switch (finishedWork.tag) {
+            case 2:
+              if (finishedWork.effectTag & 256 && null !== current) {
+                var prevProps = current.memoizedProps,
+                  prevState = current.memoizedState,
+                  instance = finishedWork.stateNode;
+                instance.props = finishedWork.memoizedProps;
+                instance.state = finishedWork.memoizedState;
+                var snapshot = instance.getSnapshotBeforeUpdate(
+                  prevProps,
+                  prevState
+                );
+                instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+              }
+              break;
+            case 3:
+            case 5:
+            case 6:
+            case 4:
+              break;
+            default:
+              invariant(
+                !1,
+                "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+              );
+          }
+        }
+        nextEffect = nextEffect.nextEffect;
+      }
+    } catch (e) {
+      (latestPendingTime = !0), (error = e);
+    }
+    latestPendingTime &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, error),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  now$1();
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    current = !1;
+    prevProps = void 0;
+    try {
+      for (; null !== nextEffect; ) {
+        var effectTag = nextEffect.effectTag;
+        if (effectTag & 128) {
+          var current$jscomp$0 = nextEffect.alternate;
+          if (null !== current$jscomp$0) {
+            var currentRef = current$jscomp$0.ref;
+            null !== currentRef &&
+              ("function" === typeof currentRef
+                ? currentRef(null)
+                : (currentRef.current = null));
+          }
+        }
+        switch (effectTag & 14) {
+          case 2:
+            nextEffect.effectTag &= -3;
+            break;
+          case 6:
+            nextEffect.effectTag &= -3;
+            commitWork(nextEffect.alternate, nextEffect);
+            break;
+          case 4:
+            commitWork(nextEffect.alternate, nextEffect);
+            break;
+          case 8:
+            prevState = nextEffect;
+            a: for (snapshot = instance = prevState; ; ) {
+              latestPendingTime = snapshot;
+              "function" === typeof onCommitUnmount &&
+                onCommitUnmount(latestPendingTime);
+              switch (latestPendingTime.tag) {
+                case 2:
+                  safelyDetachRef(latestPendingTime);
+                  var instance$jscomp$0 = latestPendingTime.stateNode;
+                  if (
+                    "function" === typeof instance$jscomp$0.componentWillUnmount
+                  )
+                    try {
+                      (instance$jscomp$0.props =
+                        latestPendingTime.memoizedProps),
+                        (instance$jscomp$0.state =
+                          latestPendingTime.memoizedState),
+                        instance$jscomp$0.componentWillUnmount();
+                    } catch (unmountError) {
+                      captureCommitPhaseError(latestPendingTime, unmountError);
+                    }
+                  break;
+                case 5:
+                  safelyDetachRef(latestPendingTime);
+                  break;
+                case 4:
+                  FabricUIManager.createChildSet(
+                    latestPendingTime.stateNode.containerInfo
+                  );
+              }
+              if (null !== snapshot.child)
+                (snapshot.child.return = snapshot), (snapshot = snapshot.child);
+              else {
+                if (snapshot === instance) break;
+                for (; null === snapshot.sibling; ) {
+                  if (null === snapshot.return || snapshot.return === instance)
+                    break a;
+                  snapshot = snapshot.return;
+                }
+                snapshot.sibling.return = snapshot.return;
+                snapshot = snapshot.sibling;
+              }
+            }
+            prevState.return = null;
+            prevState.child = null;
+            prevState.alternate &&
+              ((prevState.alternate.child = null),
+              (prevState.alternate.return = null));
+        }
+        nextEffect = nextEffect.nextEffect;
+      }
+    } catch (e) {
+      (current = !0), (prevProps = e);
+    }
+    current &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, prevProps),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  root.current = finishedWork$jscomp$0;
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    effectTag = !1;
+    current$jscomp$0 = void 0;
+    try {
+      for (currentRef = expirationTime; null !== nextEffect; ) {
+        var effectTag$jscomp$0 = nextEffect.effectTag;
+        if (effectTag$jscomp$0 & 36) {
+          var current$jscomp$1 = nextEffect.alternate;
+          instance$jscomp$0 = nextEffect;
+          firstBatch = currentRef;
+          switch (instance$jscomp$0.tag) {
+            case 2:
+              var instance$jscomp$1 = instance$jscomp$0.stateNode;
+              if (instance$jscomp$0.effectTag & 4)
+                if (null === current$jscomp$1)
+                  (instance$jscomp$1.props = instance$jscomp$0.memoizedProps),
+                    (instance$jscomp$1.state = instance$jscomp$0.memoizedState),
+                    instance$jscomp$1.componentDidMount();
+                else {
+                  var prevProps$jscomp$0 = current$jscomp$1.memoizedProps,
+                    prevState$jscomp$0 = current$jscomp$1.memoizedState;
+                  instance$jscomp$1.props = instance$jscomp$0.memoizedProps;
+                  instance$jscomp$1.state = instance$jscomp$0.memoizedState;
+                  instance$jscomp$1.componentDidUpdate(
+                    prevProps$jscomp$0,
+                    prevState$jscomp$0,
+                    instance$jscomp$1.__reactInternalSnapshotBeforeUpdate
+                  );
+                }
+              var updateQueue = instance$jscomp$0.updateQueue;
+              null !== updateQueue &&
+                ((instance$jscomp$1.props = instance$jscomp$0.memoizedProps),
+                (instance$jscomp$1.state = instance$jscomp$0.memoizedState),
+                commitUpdateQueue(
+                  instance$jscomp$0,
+                  updateQueue,
+                  instance$jscomp$1,
+                  firstBatch
+                ));
+              break;
+            case 3:
+              var _updateQueue = instance$jscomp$0.updateQueue;
+              if (null !== _updateQueue) {
+                current = null;
+                if (null !== instance$jscomp$0.child)
+                  switch (instance$jscomp$0.child.tag) {
+                    case 5:
+                      current = instance$jscomp$0.child.stateNode.canonical;
+                      break;
+                    case 2:
+                      current = instance$jscomp$0.child.stateNode;
+                  }
+                commitUpdateQueue(
+                  instance$jscomp$0,
+                  _updateQueue,
+                  current,
+                  firstBatch
+                );
+              }
+              break;
+            case 5:
+              null === current$jscomp$1 &&
+                instance$jscomp$0.effectTag & 4 &&
+                invariant(
+                  !1,
+                  "The current renderer does not support mutation. This error is likely caused by a bug in React. Please file an issue."
+                );
+              break;
+            case 6:
+              break;
+            case 4:
+              break;
+            case 15:
+              break;
+            case 16:
+              break;
+            default:
+              invariant(
+                !1,
+                "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+              );
+          }
+        }
+        if (effectTag$jscomp$0 & 128) {
+          instance$jscomp$0 = void 0;
+          var ref = nextEffect.ref;
+          if (null !== ref) {
+            var instance$jscomp$2 = nextEffect.stateNode;
+            switch (nextEffect.tag) {
+              case 5:
+                instance$jscomp$0 = instance$jscomp$2.canonical;
+                break;
+              default:
+                instance$jscomp$0 = instance$jscomp$2;
+            }
+            "function" === typeof ref
+              ? ref(instance$jscomp$0)
+              : (ref.current = instance$jscomp$0);
+          }
+        }
+        var next = nextEffect.nextEffect;
+        nextEffect.nextEffect = null;
+        nextEffect = next;
+      }
+    } catch (e) {
+      (effectTag = !0), (current$jscomp$0 = e);
+    }
+    effectTag &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, current$jscomp$0),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  totalElapsedPauseTime = 0;
+  isWorking = isCommitting$1 = !1;
+  "function" === typeof onCommitRoot &&
+    onCommitRoot(finishedWork$jscomp$0.stateNode);
+  finishedWork$jscomp$0 = root.expirationTime;
+  0 === finishedWork$jscomp$0 &&
+    (legacyErrorBoundariesThatAlreadyFailed = null);
+  root.expirationTime = finishedWork$jscomp$0;
+  root.finishedWork = null;
+}
+function shouldYield() {
+  return null === deadline ||
+    deadlineDidExpire ||
+    deadline.timeRemaining() > timeHeuristicForUnitOfWork
+    ? !1
+    : (deadlineDidExpire = !0);
+}
+function onUncaughtError(error) {
+  invariant(
+    null !== nextFlushedRoot,
+    "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
+  );
+  nextFlushedRoot.expirationTime = 0;
+  hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
+}
+function updateContainerAtExpirationTime(
+  element,
+  container,
+  parentComponent,
+  expirationTime,
+  callback
+) {
+  var current = container.current;
+  if (parentComponent) {
+    parentComponent = parentComponent._reactInternalFiber;
+    var parentContext;
+    b: {
+      invariant(
+        2 === isFiberMountedImpl(parentComponent) && 2 === parentComponent.tag,
+        "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
+      );
+      for (parentContext = parentComponent; 3 !== parentContext.tag; ) {
+        if (isContextProvider(parentContext)) {
+          parentContext =
+            parentContext.stateNode.__reactInternalMemoizedMergedChildContext;
+          break b;
+        }
+        parentContext = parentContext.return;
+        invariant(
+          parentContext,
+          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+      }
+      parentContext = parentContext.stateNode.context;
+    }
+    parentComponent = isContextProvider(parentComponent)
+      ? processChildContext(parentComponent, parentContext)
+      : parentContext;
+  } else parentComponent = emptyObject;
+  null === container.context
+    ? (container.context = parentComponent)
+    : (container.pendingContext = parentComponent);
+  container = callback;
+  callback = createUpdate(expirationTime);
+  callback.payload = { element: element };
+  container = void 0 === container ? null : container;
+  null !== container && (callback.callback = container);
+  enqueueUpdate(current, callback, expirationTime);
+  scheduleWork(current, expirationTime);
+  return expirationTime;
+}
+function findHostInstance$1(component) {
+  var fiber = component._reactInternalFiber;
+  void 0 === fiber &&
+    ("function" === typeof component.render
+      ? invariant(!1, "Unable to find node on an unmounted component.")
+      : invariant(
+          !1,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        ));
+  component = findCurrentHostFiber(fiber);
+  return null === component ? null : component.stateNode;
+}
+function updateContainer(element, container, parentComponent, callback) {
+  var current = container.current,
+    currentTime = recalculateCurrentTime();
+  current = computeExpirationForFiber(currentTime, current);
+  return updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    current,
+    callback
+  );
+}
+function getPublicRootInstance(container) {
+  container = container.current;
+  if (!container.child) return null;
+  switch (container.child.tag) {
+    case 5:
+      return container.child.stateNode.canonical;
+    default:
+      return container.child.stateNode;
+  }
+}
+function injectIntoDevTools(devToolsConfig) {
+  var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+  return injectInternals(
+    Object.assign({}, devToolsConfig, {
+      findHostInstanceByFiber: function(fiber) {
+        fiber = findCurrentHostFiber(fiber);
+        return null === fiber ? null : fiber.stateNode;
+      },
+      findFiberByHostInstance: function(instance) {
+        return findFiberByHostInstance
+          ? findFiberByHostInstance(instance)
+          : null;
+      }
+    })
+  );
+}
+var ReactFabricRenderer = {
+  updateContainerAtExpirationTime: updateContainerAtExpirationTime,
+  createContainer: function(containerInfo, isAsync, hydrate) {
+    return createFiberRoot(containerInfo, isAsync, hydrate);
+  },
+  updateContainer: updateContainer,
+  flushRoot: function(root, expirationTime) {
+    invariant(
+      !isRendering,
+      "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
+    );
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
+    performWorkOnRoot(root, expirationTime, !1);
+    performWork(1, null);
+    finishRendering();
+  },
+  requestWork: requestWork,
+  computeUniqueAsyncExpiration: function() {
+    var result =
+      2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
+    result <= lastUniqueAsyncExpiration &&
+      (result = lastUniqueAsyncExpiration + 1);
+    return (lastUniqueAsyncExpiration = result);
+  },
+  batchedUpdates: function(fn, a) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      return fn(a);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates) ||
+        isRendering ||
+        performWork(1, null);
+    }
+  },
+  unbatchedUpdates: function(fn, a) {
+    if (isBatchingUpdates && !isUnbatchingUpdates) {
+      isUnbatchingUpdates = !0;
+      try {
+        return fn(a);
+      } finally {
+        isUnbatchingUpdates = !1;
+      }
+    }
+    return fn(a);
+  },
+  deferredUpdates: function(fn) {
+    var previousExpirationContext = expirationContext;
+    expirationContext =
+      2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
+    try {
+      return fn();
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  },
+  syncUpdates: syncUpdates,
+  interactiveUpdates: function(fn, a, b) {
+    if (isBatchingInteractiveUpdates) return fn(a, b);
+    isBatchingUpdates ||
+      isRendering ||
+      0 === lowestPendingInteractiveExpirationTime ||
+      (performWork(lowestPendingInteractiveExpirationTime, null),
+      (lowestPendingInteractiveExpirationTime = 0));
+    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
+      previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = isBatchingInteractiveUpdates = !0;
+    try {
+      return fn(a, b);
+    } finally {
+      (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
+        (isBatchingUpdates = previousIsBatchingUpdates) ||
+          isRendering ||
+          performWork(1, null);
+    }
+  },
+  flushInteractiveUpdates: function() {
+    isRendering ||
+      0 === lowestPendingInteractiveExpirationTime ||
+      (performWork(lowestPendingInteractiveExpirationTime, null),
+      (lowestPendingInteractiveExpirationTime = 0));
+  },
+  flushControlled: function(fn) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      syncUpdates(fn);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates) ||
+        isRendering ||
+        performWork(1, null);
+    }
+  },
+  flushSync: function(fn, a) {
+    invariant(
+      !isRendering,
+      "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
+    );
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      return syncUpdates(fn, a);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates), performWork(1, null);
+    }
+  },
+  getPublicRootInstance: getPublicRootInstance,
+  findHostInstance: findHostInstance$1,
+  findHostInstanceWithNoPortals: function(fiber) {
+    fiber = findCurrentHostFiberWithNoPortals(fiber);
+    return null === fiber ? null : fiber.stateNode;
+  },
+  injectIntoDevTools: injectIntoDevTools
+};
+function createPortal(children, containerInfo, implementation) {
+  var key =
+    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
+  return {
+    $$typeof: REACT_PORTAL_TYPE,
+    key: null == key ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+function _inherits(subClass, superClass) {
+  if ("function" !== typeof superClass && null !== superClass)
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: !1,
+      writable: !0,
+      configurable: !0
+    }
+  });
+  superClass &&
+    (Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass));
+}
+var getInspectorDataForViewTag = void 0;
+getInspectorDataForViewTag = function() {
+  invariant(!1, "getInspectorDataForViewTag() is not available in production");
+};
+function findNodeHandle(componentOrHandle) {
+  if (null == componentOrHandle) return null;
+  if ("number" === typeof componentOrHandle) return componentOrHandle;
+  if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
+    return componentOrHandle.canonical._nativeTag;
+  componentOrHandle = findHostInstance$1(componentOrHandle);
+  return null == componentOrHandle
+    ? componentOrHandle
+    : componentOrHandle.canonical
+      ? componentOrHandle.canonical._nativeTag
+      : componentOrHandle._nativeTag;
+}
+_batchedUpdates = ReactFabricRenderer.batchedUpdates;
+_flushInteractiveUpdates = ReactFabricRenderer.flushInteractiveUpdates;
+var roots = new Map(),
+  ReactFabric = {
+    NativeComponent: (function(findNodeHandle, findHostInstance) {
+      return (function(_React$Component) {
+        function ReactNativeComponent() {
+          if (!(this instanceof ReactNativeComponent))
+            throw new TypeError("Cannot call a class as a function");
+          var call = _React$Component.apply(this, arguments);
+          if (!this)
+            throw new ReferenceError(
+              "this hasn't been initialised - super() hasn't been called"
+            );
+          return !call ||
+            ("object" !== typeof call && "function" !== typeof call)
+            ? this
+            : call;
+        }
+        _inherits(ReactNativeComponent, _React$Component);
+        ReactNativeComponent.prototype.blur = function() {
+          TextInputState.blurTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.focus = function() {
+          TextInputState.focusTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.measure = function(callback) {
+          UIManager.measure(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureInWindow = function(callback) {
+          UIManager.measureInWindow(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureLayout = function(
+          relativeToNativeNode,
+          onSuccess,
+          onFail
+        ) {
+          UIManager.measureLayout(
+            findNodeHandle(this),
+            relativeToNativeNode,
+            mountSafeCallback(this, onFail),
+            mountSafeCallback(this, onSuccess)
+          );
+        };
+        ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
+          var maybeInstance = void 0;
+          try {
+            maybeInstance = findHostInstance(this);
+          } catch (error) {}
+          if (null != maybeInstance) {
+            var viewConfig =
+              maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+            nativeProps = diffProperties(
+              null,
+              emptyObject$1,
+              nativeProps,
+              viewConfig.validAttributes
+            );
+            null != nativeProps &&
+              UIManager.updateView(
+                maybeInstance._nativeTag,
+                viewConfig.uiViewClassName,
+                nativeProps
+              );
+          }
+        };
+        return ReactNativeComponent;
+      })(React.Component);
+    })(findNodeHandle, findHostInstance$1),
+    findNodeHandle: findNodeHandle,
+    render: function(element, containerTag, callback) {
+      var root = roots.get(containerTag);
+      root ||
+        ((root = createFiberRoot(containerTag, !1, !1)),
+        roots.set(containerTag, root));
+      updateContainer(element, root, null, callback);
+      return getPublicRootInstance(root);
+    },
+    unmountComponentAtNode: function(containerTag) {
+      var root = roots.get(containerTag);
+      root &&
+        updateContainer(null, root, null, function() {
+          roots.delete(containerTag);
+        });
+    },
+    createPortal: function(children, containerTag) {
+      return createPortal(
+        children,
+        containerTag,
+        null,
+        2 < arguments.length && void 0 !== arguments[2] ? arguments[2] : null
+      );
+    },
+    __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
+      NativeMethodsMixin: (function(findNodeHandle, findHostInstance) {
+        return {
+          measure: function(callback) {
+            UIManager.measure(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureInWindow: function(callback) {
+            UIManager.measureInWindow(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
+            UIManager.measureLayout(
+              findNodeHandle(this),
+              relativeToNativeNode,
+              mountSafeCallback(this, onFail),
+              mountSafeCallback(this, onSuccess)
+            );
+          },
+          setNativeProps: function(nativeProps) {
+            var maybeInstance = void 0;
+            try {
+              maybeInstance = findHostInstance(this);
+            } catch (error) {}
+            if (null != maybeInstance) {
+              var viewConfig = maybeInstance.viewConfig;
+              nativeProps = diffProperties(
+                null,
+                emptyObject$1,
+                nativeProps,
+                viewConfig.validAttributes
+              );
+              null != nativeProps &&
+                UIManager.updateView(
+                  maybeInstance._nativeTag,
+                  viewConfig.uiViewClassName,
+                  nativeProps
+                );
+            }
+          },
+          focus: function() {
+            TextInputState.focusTextInput(findNodeHandle(this));
+          },
+          blur: function() {
+            TextInputState.blurTextInput(findNodeHandle(this));
+          }
+        };
+      })(findNodeHandle, findHostInstance$1)
+    }
+  };
+injectIntoDevTools({
+  findFiberByHostInstance: getInstanceFromInstance,
+  getInspectorDataForViewTag: getInspectorDataForViewTag,
+  bundleType: 0,
+  version: "16.4.1",
+  rendererPackageName: "react-native-renderer"
+});
+var ReactFabric$2 = { default: ReactFabric },
+  ReactFabric$3 = (ReactFabric$2 && ReactFabric) || ReactFabric$2;
+module.exports = ReactFabric$3.default ? ReactFabric$3.default : ReactFabric$3;
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
index f1a8809d897b..c18f1f137a6a 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-dev.js
@@ -19,19 +19,17 @@ if (__DEV__) {
 require("InitializeCore");
 var invariant = require("fbjs/lib/invariant");
 var warning = require("fbjs/lib/warning");
-var emptyFunction = require("fbjs/lib/emptyFunction");
 var ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry");
 var UIManager = require("UIManager");
 var RCTEventEmitter = require("RCTEventEmitter");
 var React = require("react");
 var emptyObject = require("fbjs/lib/emptyObject");
-var checkPropTypes = require("prop-types/checkPropTypes");
-var shallowEqual = require("fbjs/lib/shallowEqual");
-var ExceptionsManager = require("ExceptionsManager");
 var deepFreezeAndThrowOnMutationInDev = require("deepFreezeAndThrowOnMutationInDev");
 var deepDiffer = require("deepDiffer");
 var flattenStyle = require("flattenStyle");
 var TextInputState = require("TextInputState");
+var checkPropTypes = require("prop-types/checkPropTypes");
+var ExceptionsManager = require("ExceptionsManager");
 
 var invokeGuardedCallback = function(name, func, context, a, b, c, d, e, f) {
   this._hasCaughtError = false;
@@ -1183,7 +1181,9 @@ var EventInterface = {
   type: null,
   target: null,
   // currentTarget is set when dispatching; no use in copying it here
-  currentTarget: emptyFunction.thatReturnsNull,
+  currentTarget: function() {
+    return null;
+  },
   eventPhase: null,
   bubbles: null,
   cancelable: null,
@@ -1194,6 +1194,14 @@ var EventInterface = {
   isTrusted: null
 };
 
+function functionThatReturnsTrue() {
+  return true;
+}
+
+function functionThatReturnsFalse() {
+  return false;
+}
+
 /**
  * Synthetic events are dispatched by event plugins, typically in response to a
  * top-level event delegation handler.
@@ -1254,11 +1262,11 @@ function SyntheticEvent(
       ? nativeEvent.defaultPrevented
       : nativeEvent.returnValue === false;
   if (defaultPrevented) {
-    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
+    this.isDefaultPrevented = functionThatReturnsTrue;
   } else {
-    this.isDefaultPrevented = emptyFunction.thatReturnsFalse;
+    this.isDefaultPrevented = functionThatReturnsFalse;
   }
-  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
+  this.isPropagationStopped = functionThatReturnsFalse;
   return this;
 }
 
@@ -1275,7 +1283,7 @@ Object.assign(SyntheticEvent.prototype, {
     } else if (typeof event.returnValue !== "unknown") {
       event.returnValue = false;
     }
-    this.isDefaultPrevented = emptyFunction.thatReturnsTrue;
+    this.isDefaultPrevented = functionThatReturnsTrue;
   },
 
   stopPropagation: function() {
@@ -1295,7 +1303,7 @@ Object.assign(SyntheticEvent.prototype, {
       event.cancelBubble = true;
     }
 
-    this.isPropagationStopped = emptyFunction.thatReturnsTrue;
+    this.isPropagationStopped = functionThatReturnsTrue;
   },
 
   /**
@@ -1304,7 +1312,7 @@ Object.assign(SyntheticEvent.prototype, {
    * won't be added back into the pool.
    */
   persist: function() {
-    this.isPersistent = emptyFunction.thatReturnsTrue;
+    this.isPersistent = functionThatReturnsTrue;
   },
 
   /**
@@ -1312,7 +1320,7 @@ Object.assign(SyntheticEvent.prototype, {
    *
    * @return {boolean} True if this should not be released, false otherwise.
    */
-  isPersistent: emptyFunction.thatReturnsFalse,
+  isPersistent: functionThatReturnsFalse,
 
   /**
    * `PooledClass` looks for `destructor` on each instance it releases.
@@ -1340,12 +1348,12 @@ Object.assign(SyntheticEvent.prototype, {
       Object.defineProperty(
         this,
         "preventDefault",
-        getPooledWarningPropertyDefinition("preventDefault", emptyFunction)
+        getPooledWarningPropertyDefinition("preventDefault", function() {})
       );
       Object.defineProperty(
         this,
         "stopPropagation",
-        getPooledWarningPropertyDefinition("stopPropagation", emptyFunction)
+        getPooledWarningPropertyDefinition("stopPropagation", function() {})
       );
     }
   }
@@ -2371,6 +2379,32 @@ var ReactNativeBridgeEventPlugin = {
   }
 };
 
+var ReactNativeEventPluginOrder = [
+  "ResponderEventPlugin",
+  "ReactNativeBridgeEventPlugin"
+];
+
+/**
+ * Make sure essential globals are available and are patched correctly. Please don't remove this
+ * line. Bundles created by react-packager `require` it before executing any application code. This
+ * ensures it exists in the dependency graph and can be `require`d.
+ * TODO: require this in packager, not in React #10932517
+ */
+// Module provided by RN:
+/**
+ * Inject module for resolving DOM hierarchy and plugin ordering.
+ */
+injection.injectEventPluginOrder(ReactNativeEventPluginOrder);
+
+/**
+ * Some important event plugins included by default (without having to require
+ * them).
+ */
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
+
 var instanceCache = {};
 var instanceProps = {};
 
@@ -2384,12 +2418,7 @@ function uncacheFiberNode(tag) {
 }
 
 function getInstanceFromTag(tag) {
-  if (typeof tag === "number") {
-    return instanceCache[tag] || null;
-  } else {
-    // Fabric will invoke event emitters on a direct fiber reference
-    return tag;
-  }
+  return instanceCache[tag] || null;
 }
 
 function getTagFromInstance(inst) {
@@ -2419,49 +2448,6 @@ var ReactNativeComponentTree = Object.freeze({
   updateFiberProps: updateFiberProps
 });
 
-var ReactNativeEventPluginOrder = [
-  "ResponderEventPlugin",
-  "ReactNativeBridgeEventPlugin"
-];
-
-// Module provided by RN:
-var ReactNativeGlobalResponderHandler = {
-  onChange: function(from, to, blockNativeResponder) {
-    if (to !== null) {
-      var tag = to.stateNode._nativeTag;
-      UIManager.setJSResponder(tag, blockNativeResponder);
-    } else {
-      UIManager.clearJSResponder();
-    }
-  }
-};
-
-/**
- * Make sure essential globals are available and are patched correctly. Please don't remove this
- * line. Bundles created by react-packager `require` it before executing any application code. This
- * ensures it exists in the dependency graph and can be `require`d.
- * TODO: require this in packager, not in React #10932517
- */
-// Module provided by RN:
-/**
- * Inject module for resolving DOM hierarchy and plugin ordering.
- */
-injection.injectEventPluginOrder(ReactNativeEventPluginOrder);
-injection$1.injectComponentTree(ReactNativeComponentTree);
-
-ResponderEventPlugin.injection.injectGlobalResponderHandler(
-  ReactNativeGlobalResponderHandler
-);
-
-/**
- * Some important event plugins included by default (without having to require
- * them).
- */
-injection.injectEventPluginsByName({
-  ResponderEventPlugin: ResponderEventPlugin,
-  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
-});
-
 // Use to restore controlled state after a change event has fired.
 
 var fiberHostComponent = null;
@@ -2718,12 +2704,30 @@ var ReactNativeEventEmitter = Object.freeze({
   receiveTouches: receiveTouches
 });
 
+// Module provided by RN:
+var ReactNativeGlobalResponderHandler = {
+  onChange: function(from, to, blockNativeResponder) {
+    if (to !== null) {
+      var tag = to.stateNode._nativeTag;
+      UIManager.setJSResponder(tag, blockNativeResponder);
+    } else {
+      UIManager.clearJSResponder();
+    }
+  }
+};
+
 // Module provided by RN:
 /**
  * Register the event emitter with the native bridge
  */
 RCTEventEmitter.register(ReactNativeEventEmitter);
 
+injection$1.injectComponentTree(ReactNativeComponentTree);
+
+ResponderEventPlugin.injection.injectGlobalResponderHandler(
+  ReactNativeGlobalResponderHandler
+);
+
 /**
  * `ReactInstanceMap` maintains a mapping from a public facing stateful
  * instance (key) and the internal representation (value). This allows public
@@ -2812,6 +2816,8 @@ function getComponentName(fiber) {
       return "Context.Provider";
     case REACT_STRICT_MODE_TYPE:
       return "StrictMode";
+    case REACT_TIMEOUT_TYPE:
+      return "Timeout";
   }
   if (typeof type === "object" && type !== null) {
     switch (type.$$typeof) {
@@ -3110,1057 +3116,1101 @@ function findCurrentHostFiberWithNoPortals(parent) {
   return null;
 }
 
-var debugRenderPhaseSideEffects = false;
-var debugRenderPhaseSideEffectsForStrictMode = false;
-var enableGetDerivedStateFromCatch = false;
-var enableSuspense = false;
-var enableMutatingReconciler = true;
-var enableNoopReconciler = false;
-var enablePersistentReconciler = false;
-var enableUserTimingAPI = true;
-var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
-var warnAboutDeprecatedLifecycles = false;
-var enableProfilerTimer = true;
-var fireGetDerivedStateFromPropsOnStateUpdates = true;
-
-// Only used in www builds.
-
-// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
-// Math.pow(2, 30) - 1
-// 0b111111111111111111111111111111
-var MAX_SIGNED_31_BIT_INT = 1073741823;
-
-// TODO: Use an opaque type once ESLint et al support the syntax
-
-var NoWork = 0;
-var Sync = 1;
-var Never = MAX_SIGNED_31_BIT_INT;
-
-var UNIT_SIZE = 10;
-var MAGIC_NUMBER_OFFSET = 2;
+// Modules provided by RN:
+var emptyObject$1 = {};
 
-// 1 unit of expiration time represents 10ms.
-function msToExpirationTime(ms) {
-  // Always add an offset so that we don't clash with the magic number for NoWork.
-  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
-}
+/**
+ * Create a payload that contains all the updates between two sets of props.
+ *
+ * These helpers are all encapsulated into a single module, because they use
+ * mutation as a performance optimization which leads to subtle shared
+ * dependencies between the code paths. To avoid this mutable state leaking
+ * across modules, I've kept them isolated to this module.
+ */
 
-function expirationTimeToMs(expirationTime) {
-  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
-}
+// Tracks removed keys
+var removedKeys = null;
+var removedKeyCount = 0;
 
-function ceiling(num, precision) {
-  return (((num / precision) | 0) + 1) * precision;
+function defaultDiffer(prevProp, nextProp) {
+  if (typeof nextProp !== "object" || nextProp === null) {
+    // Scalars have already been checked for equality
+    return true;
+  } else {
+    // For objects and arrays, the default diffing algorithm is a deep compare
+    return deepDiffer(prevProp, nextProp);
+  }
 }
 
-function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
-  return (
-    MAGIC_NUMBER_OFFSET +
-    ceiling(
-      currentTime - MAGIC_NUMBER_OFFSET + expirationInMs / UNIT_SIZE,
-      bucketSizeMs / UNIT_SIZE
-    )
-  );
-}
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node)) {
+    var i = node.length;
+    while (i-- && removedKeyCount > 0) {
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+    }
+  } else if (node && removedKeyCount > 0) {
+    var obj = node;
+    for (var propKey in removedKeys) {
+      if (!removedKeys[propKey]) {
+        continue;
+      }
+      var _nextProp = obj[propKey];
+      if (_nextProp === undefined) {
+        continue;
+      }
 
-var NoContext = 0;
-var AsyncMode = 1;
-var StrictMode = 2;
-var ProfileMode = 4;
+      var attributeConfig = validAttributes[propKey];
+      if (!attributeConfig) {
+        continue; // not a valid native prop
+      }
 
-var hasBadMapPolyfill = void 0;
+      if (typeof _nextProp === "function") {
+        _nextProp = true;
+      }
+      if (typeof _nextProp === "undefined") {
+        _nextProp = null;
+      }
 
-{
-  hasBadMapPolyfill = false;
-  try {
-    var nonExtensibleObject = Object.preventExtensions({});
-    var testMap = new Map([[nonExtensibleObject, null]]);
-    var testSet = new Set([nonExtensibleObject]);
-    // This is necessary for Rollup to not consider these unused.
-    // https://github.com/rollup/rollup/issues/1771
-    // TODO: we can remove these if Rollup fixes the bug.
-    testMap.set(0, 0);
-    testSet.add(0);
-  } catch (e) {
-    // TODO: Consider warning about bad polyfills
-    hasBadMapPolyfill = true;
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = _nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(_nextProp)
+            : _nextProp;
+        updatePayload[propKey] = nextValue;
+      }
+      removedKeys[propKey] = false;
+      removedKeyCount--;
+    }
   }
 }
 
-// A Fiber is work on a Component that needs to be done or was done. There can
-// be more than one per component.
-
-var debugCounter = void 0;
-
-{
-  debugCounter = 1;
-}
-
-function FiberNode(tag, pendingProps, key, mode) {
-  // Instance
-  this.tag = tag;
-  this.key = key;
-  this.type = null;
-  this.stateNode = null;
-
-  // Fiber
-  this.return = null;
-  this.child = null;
-  this.sibling = null;
-  this.index = 0;
-
-  this.ref = null;
-
-  this.pendingProps = pendingProps;
-  this.memoizedProps = null;
-  this.updateQueue = null;
-  this.memoizedState = null;
-
-  this.mode = mode;
-
-  // Effects
-  this.effectTag = NoEffect;
-  this.nextEffect = null;
-
-  this.firstEffect = null;
-  this.lastEffect = null;
-
-  this.expirationTime = NoWork;
-
-  this.alternate = null;
+function diffNestedArrayProperty(
+  updatePayload,
+  prevArray,
+  nextArray,
+  validAttributes
+) {
+  var minLength =
+    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
+  var i = void 0;
+  for (i = 0; i < minLength; i++) {
+    // Diff any items in the array in the forward direction. Repeated keys
+    // will be overwritten by later values.
+    updatePayload = diffNestedProperty(
+      updatePayload,
+      prevArray[i],
+      nextArray[i],
+      validAttributes
+    );
+  }
+  for (; i < prevArray.length; i++) {
+    // Clear out all remaining properties.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevArray[i],
+      validAttributes
+    );
+  }
+  for (; i < nextArray.length; i++) {
+    // Add all remaining properties.
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextArray[i],
+      validAttributes
+    );
+  }
+  return updatePayload;
+}
 
-  if (enableProfilerTimer) {
-    this.selfBaseTime = 0;
-    this.treeBaseTime = 0;
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) {
+    // If no properties have been added, then we can bail out quickly on object
+    // equality.
+    return updatePayload;
   }
 
-  {
-    this._debugID = debugCounter++;
-    this._debugSource = null;
-    this._debugOwner = null;
-    this._debugIsCurrentlyTiming = false;
-    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
-      Object.preventExtensions(this);
+  if (!prevProp || !nextProp) {
+    if (nextProp) {
+      return addNestedProperty(updatePayload, nextProp, validAttributes);
+    }
+    if (prevProp) {
+      return clearNestedProperty(updatePayload, prevProp, validAttributes);
     }
+    return updatePayload;
   }
-}
-
-// This is a constructor function, rather than a POJO constructor, still
-// please ensure we do the following:
-// 1) Nobody should add any instance methods on this. Instance methods can be
-//    more difficult to predict when they get optimized and they are almost
-//    never inlined properly in static compilers.
-// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
-//    always know when it is a fiber.
-// 3) We might want to experiment with using numeric keys since they are easier
-//    to optimize in a non-JIT environment.
-// 4) We can easily go from a constructor to a createFiber object literal if that
-//    is faster.
-// 5) It should be easy to port this to a C struct and keep a C implementation
-//    compatible.
-var createFiber = function(tag, pendingProps, key, mode) {
-  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
-  return new FiberNode(tag, pendingProps, key, mode);
-};
 
-function shouldConstruct(Component) {
-  return !!(Component.prototype && Component.prototype.isReactComponent);
-}
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
+    // Both are leaves, we can diff the leaves.
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  }
 
-// This is used to create an alternate fiber to do work on.
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  if (workInProgress === null) {
-    // We use a double buffering pooling technique because we know that we'll
-    // only ever need at most two versions of a tree. We pool the "other" unused
-    // node that we're free to reuse. This is lazily created to avoid allocating
-    // extra objects for things that are never updated. It also allow us to
-    // reclaim the extra memory if needed.
-    workInProgress = createFiber(
-      current.tag,
-      pendingProps,
-      current.key,
-      current.mode
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    // Both are arrays, we can diff the arrays.
+    return diffNestedArrayProperty(
+      updatePayload,
+      prevProp,
+      nextProp,
+      validAttributes
     );
-    workInProgress.type = current.type;
-    workInProgress.stateNode = current.stateNode;
+  }
 
-    {
-      // DEV-only fields
-      workInProgress._debugID = current._debugID;
-      workInProgress._debugSource = current._debugSource;
-      workInProgress._debugOwner = current._debugOwner;
-    }
+  if (Array.isArray(prevProp)) {
+    return diffProperties(
+      updatePayload,
+      // $FlowFixMe - We know that this is always an object when the input is.
+      flattenStyle(prevProp),
+      // $FlowFixMe - We know that this isn't an array because of above flow.
+      nextProp,
+      validAttributes
+    );
+  }
 
-    workInProgress.alternate = current;
-    current.alternate = workInProgress;
-  } else {
-    workInProgress.pendingProps = pendingProps;
+  return diffProperties(
+    updatePayload,
+    prevProp,
+    // $FlowFixMe - We know that this is always an object when the input is.
+    flattenStyle(nextProp),
+    validAttributes
+  );
+}
 
-    // We already have an alternate.
-    // Reset the effect tag.
-    workInProgress.effectTag = NoEffect;
+/**
+ * addNestedProperty takes a single set of props and valid attribute
+ * attribute configurations. It processes each prop and adds it to the
+ * updatePayload.
+ */
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) {
+    return updatePayload;
+  }
 
-    // The effect list is no longer valid.
-    workInProgress.nextEffect = null;
-    workInProgress.firstEffect = null;
-    workInProgress.lastEffect = null;
+  if (!Array.isArray(nextProp)) {
+    // Add each property of the leaf.
+    return addProperties(updatePayload, nextProp, validAttributes);
   }
 
-  workInProgress.expirationTime = expirationTime;
+  for (var i = 0; i < nextProp.length; i++) {
+    // Add all the properties of the array.
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  }
 
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
+  return updatePayload;
+}
 
-  // These will be overridden during the parent's reconciliation
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
+/**
+ * clearNestedProperty takes a single set of props and valid attributes. It
+ * adds a null sentinel to the updatePayload, for each prop key.
+ */
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) {
+    return updatePayload;
+  }
 
-  if (enableProfilerTimer) {
-    workInProgress.selfBaseTime = current.selfBaseTime;
-    workInProgress.treeBaseTime = current.treeBaseTime;
+  if (!Array.isArray(prevProp)) {
+    // Add each property of the leaf.
+    return clearProperties(updatePayload, prevProp, validAttributes);
   }
 
-  return workInProgress;
+  for (var i = 0; i < prevProp.length; i++) {
+    // Add all the properties of the array.
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  }
+  return updatePayload;
 }
 
-function createHostRootFiber(isAsync) {
-  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
-  return createFiber(HostRoot, null, null, mode);
-}
+/**
+ * diffProperties takes two sets of props and a set of valid attributes
+ * and write to updatePayload the values that changed or were deleted.
+ * If no updatePayload is provided, a new one is created and returned if
+ * anything changed.
+ */
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig = void 0;
+  var nextProp = void 0;
+  var prevProp = void 0;
 
-function createFiberFromElement(element, mode, expirationTime) {
-  var owner = null;
-  {
-    owner = element._owner;
-  }
+  for (var propKey in nextProps) {
+    attributeConfig = validAttributes[propKey];
+    if (!attributeConfig) {
+      continue; // not a valid native prop
+    }
 
-  var fiber = void 0;
-  var type = element.type;
-  var key = element.key;
-  var pendingProps = element.props;
+    prevProp = prevProps[propKey];
+    nextProp = nextProps[propKey];
 
-  var fiberTag = void 0;
-  if (typeof type === "function") {
-    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
-  } else if (typeof type === "string") {
-    fiberTag = HostComponent;
-  } else {
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          pendingProps.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= AsyncMode | StrictMode;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = Mode;
-        mode |= StrictMode;
-        break;
-      case REACT_PROFILER_TYPE:
-        return createFiberFromProfiler(pendingProps, mode, expirationTime, key);
-      case REACT_TIMEOUT_TYPE:
-        fiberTag = TimeoutComponent;
-        // Suspense does not require async, but its children should be strict
-        // mode compatible.
-        mode |= StrictMode;
-        break;
-      default:
-        fiberTag = getFiberTagFromObjectType(type, owner);
-        break;
+    // functions are converted to booleans as markers that the associated
+    // events should be sent from native.
+    if (typeof nextProp === "function") {
+      nextProp = true;
+      // If nextProp is not a function, then don't bother changing prevProp
+      // since nextProp will win and go into the updatePayload regardless.
+      if (typeof prevProp === "function") {
+        prevProp = true;
+      }
     }
-  }
 
-  fiber = createFiber(fiberTag, pendingProps, key, mode);
-  fiber.type = type;
-  fiber.expirationTime = expirationTime;
+    // An explicit value of undefined is treated as a null because it overrides
+    // any other preceding value.
+    if (typeof nextProp === "undefined") {
+      nextProp = null;
+      if (typeof prevProp === "undefined") {
+        prevProp = null;
+      }
+    }
 
-  {
-    fiber._debugSource = element._source;
-    fiber._debugOwner = element._owner;
-  }
+    if (removedKeys) {
+      removedKeys[propKey] = false;
+    }
 
-  return fiber;
-}
+    if (updatePayload && updatePayload[propKey] !== undefined) {
+      // Something else already triggered an update to this key because another
+      // value diffed. Since we're now later in the nested arrays our value is
+      // more important so we need to calculate it and override the existing
+      // value. It doesn't matter if nothing changed, we'll set it anyway.
 
-function getFiberTagFromObjectType(type, owner) {
-  var $$typeof =
-    typeof type === "object" && type !== null ? type.$$typeof : null;
+      // Pattern match on: attributeConfig
+      if (typeof attributeConfig !== "object") {
+        // case: !Object is the default case
+        updatePayload[propKey] = nextProp;
+      } else if (
+        typeof attributeConfig.diff === "function" ||
+        typeof attributeConfig.process === "function"
+      ) {
+        // case: CustomAttributeConfiguration
+        var nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(nextProp)
+            : nextProp;
+        updatePayload[propKey] = nextValue;
+      }
+      continue;
+    }
 
-  switch ($$typeof) {
-    case REACT_PROVIDER_TYPE:
-      return ContextProvider;
-    case REACT_CONTEXT_TYPE:
-      // This is a consumer
-      return ContextConsumer;
-    case REACT_FORWARD_REF_TYPE:
-      return ForwardRef;
-    default: {
-      var info = "";
-      {
-        if (
-          type === undefined ||
-          (typeof type === "object" &&
-            type !== null &&
-            Object.keys(type).length === 0)
-        ) {
-          info +=
-            " You likely forgot to export your component from the file " +
-            "it's defined in, or you might have mixed up default and " +
-            "named imports.";
-        }
-        var ownerName = owner ? getComponentName(owner) : null;
-        if (ownerName) {
-          info += "\n\nCheck the render method of `" + ownerName + "`.";
-        }
+    if (prevProp === nextProp) {
+      continue; // nothing changed
+    }
+
+    // Pattern match on: attributeConfig
+    if (typeof attributeConfig !== "object") {
+      // case: !Object is the default case
+      if (defaultDiffer(prevProp, nextProp)) {
+        // a normal leaf has changed
+        (updatePayload || (updatePayload = {}))[propKey] = nextProp;
       }
-      invariant(
-        false,
-        "Element type is invalid: expected a string (for built-in " +
-          "components) or a class/function (for composite components) " +
-          "but got: %s.%s",
-        type == null ? type : typeof type,
-        info
+    } else if (
+      typeof attributeConfig.diff === "function" ||
+      typeof attributeConfig.process === "function"
+    ) {
+      // case: CustomAttributeConfiguration
+      var shouldUpdate =
+        prevProp === undefined ||
+        (typeof attributeConfig.diff === "function"
+          ? attributeConfig.diff(prevProp, nextProp)
+          : defaultDiffer(prevProp, nextProp));
+      if (shouldUpdate) {
+        var _nextValue =
+          typeof attributeConfig.process === "function"
+            ? attributeConfig.process(nextProp)
+            : nextProp;
+        (updatePayload || (updatePayload = {}))[propKey] = _nextValue;
+      }
+    } else {
+      // default: fallthrough case when nested properties are defined
+      removedKeys = null;
+      removedKeyCount = 0;
+      // We think that attributeConfig is not CustomAttributeConfiguration at
+      // this point so we assume it must be AttributeConfiguration.
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp,
+        nextProp,
+        attributeConfig
       );
+      if (removedKeyCount > 0 && updatePayload) {
+        restoreDeletedValuesInNestedArray(
+          updatePayload,
+          nextProp,
+          attributeConfig
+        );
+        removedKeys = null;
+      }
     }
   }
-}
 
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  var fiber = createFiber(Fragment, elements, key, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
-}
+  // Also iterate through all the previous props to catch any that have been
+  // removed and make sure native gets the signal so it can reset them to the
+  // default.
+  for (var _propKey in prevProps) {
+    if (nextProps[_propKey] !== undefined) {
+      continue; // we've already covered this key in the previous pass
+    }
+    attributeConfig = validAttributes[_propKey];
+    if (!attributeConfig) {
+      continue; // not a valid native prop
+    }
 
-function createFiberFromProfiler(pendingProps, mode, expirationTime, key) {
-  {
+    if (updatePayload && updatePayload[_propKey] !== undefined) {
+      // This was already updated to a diff result earlier.
+      continue;
+    }
+
+    prevProp = prevProps[_propKey];
+    if (prevProp === undefined) {
+      continue; // was already empty anyway
+    }
+    // Pattern match on: attributeConfig
     if (
-      typeof pendingProps.id !== "string" ||
-      typeof pendingProps.onRender !== "function"
+      typeof attributeConfig !== "object" ||
+      typeof attributeConfig.diff === "function" ||
+      typeof attributeConfig.process === "function"
     ) {
-      invariant(
-        false,
-        'Profiler must specify an "id" string and "onRender" function as props'
+      // case: CustomAttributeConfiguration | !Object
+      // Flag the leaf property for removal by sending a sentinel.
+      (updatePayload || (updatePayload = {}))[_propKey] = null;
+      if (!removedKeys) {
+        removedKeys = {};
+      }
+      if (!removedKeys[_propKey]) {
+        removedKeys[_propKey] = true;
+        removedKeyCount++;
+      }
+    } else {
+      // default:
+      // This is a nested attribute configuration where all the properties
+      // were removed so we need to go through and clear out all of them.
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp,
+        attributeConfig
       );
     }
   }
-
-  var fiber = createFiber(Profiler, pendingProps, key, mode | ProfileMode);
-  fiber.type = REACT_PROFILER_TYPE;
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    duration: 0,
-    startTime: 0
-  };
-
-  return fiber;
+  return updatePayload;
 }
 
-function createFiberFromText(content, mode, expirationTime) {
-  var fiber = createFiber(HostText, content, null, mode);
-  fiber.expirationTime = expirationTime;
-  return fiber;
+/**
+ * addProperties adds all the valid props to the payload after being processed.
+ */
+function addProperties(updatePayload, props, validAttributes) {
+  // TODO: Fast path
+  return diffProperties(updatePayload, emptyObject$1, props, validAttributes);
 }
 
-function createFiberFromHostInstanceForDeletion() {
-  var fiber = createFiber(HostComponent, null, null, NoContext);
-  fiber.type = "DELETED";
-  return fiber;
+/**
+ * clearProperties clears all the previous props by adding a null sentinel
+ * to the payload for each valid key.
+ */
+function clearProperties(updatePayload, prevProps, validAttributes) {
+  // TODO: Fast path
+  return diffProperties(
+    updatePayload,
+    prevProps,
+    emptyObject$1,
+    validAttributes
+  );
 }
 
-function createFiberFromPortal(portal, mode, expirationTime) {
-  var pendingProps = portal.children !== null ? portal.children : [];
-  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
-  fiber.expirationTime = expirationTime;
-  fiber.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null, // Used by persistent updates
-    implementation: portal.implementation
-  };
-  return fiber;
-}
-
-// Used for stashing WIP properties to replay failed work in DEV.
-function assignFiberPropertiesInDEV(target, source) {
-  if (target === null) {
-    // This Fiber's initial properties will always be overwritten.
-    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
-    target = createFiber(IndeterminateComponent, null, null, NoContext);
-  }
-
-  // This is intentionally written as a list of all properties.
-  // We tried to use Object.assign() instead but this is called in
-  // the hottest path, and Object.assign() was too slow:
-  // https://github.com/facebook/react/issues/12502
-  // This code is DEV-only so size is not a concern.
-
-  target.tag = source.tag;
-  target.key = source.key;
-  target.type = source.type;
-  target.stateNode = source.stateNode;
-  target.return = source.return;
-  target.child = source.child;
-  target.sibling = source.sibling;
-  target.index = source.index;
-  target.ref = source.ref;
-  target.pendingProps = source.pendingProps;
-  target.memoizedProps = source.memoizedProps;
-  target.updateQueue = source.updateQueue;
-  target.memoizedState = source.memoizedState;
-  target.mode = source.mode;
-  target.effectTag = source.effectTag;
-  target.nextEffect = source.nextEffect;
-  target.firstEffect = source.firstEffect;
-  target.lastEffect = source.lastEffect;
-  target.expirationTime = source.expirationTime;
-  target.alternate = source.alternate;
-  if (enableProfilerTimer) {
-    target.selfBaseTime = source.selfBaseTime;
-    target.treeBaseTime = source.treeBaseTime;
-  }
-  target._debugID = source._debugID;
-  target._debugSource = source._debugSource;
-  target._debugOwner = source._debugOwner;
-  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
-  return target;
+function create(props, validAttributes) {
+  return addProperties(
+    null, // updatePayload
+    props,
+    validAttributes
+  );
 }
 
-// TODO: This should be lifted into the renderer.
-
-function createFiberRoot(containerInfo, isAsync, hydrate) {
-  // Cyclic construction. This cheats the type system right now because
-  // stateNode is any.
-  var uninitializedFiber = createHostRootFiber(isAsync);
-  var root = {
-    current: uninitializedFiber,
-    containerInfo: containerInfo,
-    pendingChildren: null,
-
-    earliestPendingTime: NoWork,
-    latestPendingTime: NoWork,
-    earliestSuspendedTime: NoWork,
-    latestSuspendedTime: NoWork,
-    latestPingedTime: NoWork,
-
-    pendingCommitExpirationTime: NoWork,
-    finishedWork: null,
-    context: null,
-    pendingContext: null,
-    hydrate: hydrate,
-    remainingExpirationTime: NoWork,
-    firstBatch: null,
-    nextScheduledRoot: null
-  };
-  uninitializedFiber.stateNode = root;
-  return root;
+function diff(prevProps, nextProps, validAttributes) {
+  return diffProperties(
+    null, // updatePayload
+    prevProps,
+    nextProps,
+    validAttributes
+  );
 }
 
-var onCommitFiberRoot = null;
-var onCommitFiberUnmount = null;
-var hasLoggedError = false;
-
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {
-      if (true && !hasLoggedError) {
-        hasLoggedError = true;
-        warning(false, "React DevTools encountered an error: %s", err);
+/**
+ * In the future, we should cleanup callbacks by cancelling them instead of
+ * using this.
+ */
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (!callback) {
+      return undefined;
+    }
+    if (typeof context.__isMounted === "boolean") {
+      // TODO(gaearon): this is gross and should be removed.
+      // It is currently necessary because View uses createClass,
+      // and so any measure() calls on View (which are done by React
+      // DevTools) trigger the isMounted() deprecation warning.
+      if (!context.__isMounted) {
+        return undefined;
+      }
+      // The else branch is important so that we don't
+      // trigger the deprecation warning by calling isMounted.
+    } else if (typeof context.isMounted === "function") {
+      if (!context.isMounted()) {
+        return undefined;
       }
     }
+    return callback.apply(context, arguments);
   };
 }
 
-function injectInternals(internals) {
-  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
-    // No DevTools
-    return false;
-  }
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled) {
-    // This isn't a real property on the hook, but it can be set to opt out
-    // of DevTools integration and associated warnings and logs.
-    // https://github.com/facebook/react/issues/3877
-    return true;
-  }
-  if (!hook.supportsFiber) {
-    {
-      warning(
-        false,
-        "The installed version of React DevTools is too old and will not work " +
-          "with the current version of React. Please update React DevTools. " +
-          "https://fb.me/react-devtools"
-      );
-    }
-    // DevTools exists, even though it doesn't support Fiber.
-    return true;
-  }
-  try {
-    var rendererID = hook.inject(internals);
-    // We have successfully injected, so now it is safe to set up hooks.
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {
-    // Catch all errors because it is unsafe to throw during initialization.
-    {
-      warning(false, "React DevTools encountered an error: %s.", err);
+function throwOnStylesProp(component, props) {
+  if (props.styles !== undefined) {
+    var owner = component._owner || null;
+    var name = component.constructor.displayName;
+    var msg =
+      "`styles` is not a supported property of `" +
+      name +
+      "`, did " +
+      "you mean `style` (singular)?";
+    if (owner && owner.constructor && owner.constructor.displayName) {
+      msg +=
+        "\n\nCheck the `" +
+        owner.constructor.displayName +
+        "` parent " +
+        " component.";
     }
+    throw new Error(msg);
   }
-  // DevTools exists
-  return true;
 }
 
-function onCommitRoot(root) {
-  if (typeof onCommitFiberRoot === "function") {
-    onCommitFiberRoot(root);
+function warnForStyleProps(props, validAttributes) {
+  for (var key in validAttributes.style) {
+    if (!(validAttributes[key] || props[key] === undefined)) {
+      console.error(
+        "You are setting the style `{ " +
+          key +
+          ": ... }` as a prop. You " +
+          "should nest it in a style object. " +
+          "E.g. `{ style: { " +
+          key +
+          ": ... } }`"
+      );
+    }
   }
 }
 
-function onCommitUnmount(fiber) {
-  if (typeof onCommitFiberUnmount === "function") {
-    onCommitFiberUnmount(fiber);
+function _classCallCheck(instance, Constructor) {
+  if (!(instance instanceof Constructor)) {
+    throw new TypeError("Cannot call a class as a function");
   }
 }
 
-var describeComponentFrame = function(name, source, ownerName) {
-  return (
-    "\n    in " +
-    (name || "Unknown") +
-    (source
-      ? " (at " +
-        source.fileName.replace(/^.*[\\\/]/, "") +
-        ":" +
-        source.lineNumber +
-        ")"
-      : ownerName ? " (created by " + ownerName + ")" : "")
-  );
-};
+// Modules provided by RN:
+/**
+ * This component defines the same methods as NativeMethodsMixin but without the
+ * findNodeHandle wrapper. This wrapper is unnecessary for HostComponent views
+ * and would also result in a circular require.js dependency (since
+ * ReactNativeFiber depends on this component and NativeMethodsMixin depends on
+ * ReactNativeFiber).
+ */
 
-function describeFiber(fiber) {
-  switch (fiber.tag) {
-    case IndeterminateComponent:
-    case FunctionalComponent:
-    case ClassComponent:
-    case HostComponent:
-      var owner = fiber._debugOwner;
-      var source = fiber._debugSource;
-      var name = getComponentName(fiber);
-      var ownerName = null;
-      if (owner) {
-        ownerName = getComponentName(owner);
-      }
-      return describeComponentFrame(name, source, ownerName);
-    default:
-      return "";
+var ReactNativeFiberHostComponent = (function() {
+  function ReactNativeFiberHostComponent(tag, viewConfig) {
+    _classCallCheck(this, ReactNativeFiberHostComponent);
+
+    this._nativeTag = tag;
+    this._children = [];
+    this.viewConfig = viewConfig;
   }
-}
 
-// This function can only be called with a work-in-progress fiber and
-// only during begin or complete phase. Do not call it under any other
-// circumstances.
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
-  var info = "";
-  var node = workInProgress;
-  do {
-    info += describeFiber(node);
-    // Otherwise this return pointer might point to the wrong tree:
-    node = node.return;
-  } while (node);
-  return info;
-}
+  ReactNativeFiberHostComponent.prototype.blur = function blur() {
+    TextInputState.blurTextInput(this._nativeTag);
+  };
 
-/**
- * Forked from fbjs/warning:
- * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
- *
- * Only change is we use console.warn instead of console.error,
- * and do nothing when 'console' is not supported.
- * This really simplifies the code.
- * ---
- * Similar to invariant but only logs a warning if the condition is not met.
- * This can be used to log issues in development environments in critical
- * paths. Removing the logging code for production environments will keep the
- * same logic and follow the same code paths.
- */
+  ReactNativeFiberHostComponent.prototype.focus = function focus() {
+    TextInputState.focusTextInput(this._nativeTag);
+  };
 
-var lowPriorityWarning = function() {};
+  ReactNativeFiberHostComponent.prototype.measure = function measure(callback) {
+    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+  };
 
-{
-  var printWarning = function(format) {
-    for (
-      var _len = arguments.length,
-        args = Array(_len > 1 ? _len - 1 : 0),
-        _key = 1;
-      _key < _len;
-      _key++
-    ) {
-      args[_key - 1] = arguments[_key];
-    }
+  ReactNativeFiberHostComponent.prototype.measureInWindow = function measureInWindow(
+    callback
+  ) {
+    UIManager.measureInWindow(
+      this._nativeTag,
+      mountSafeCallback(this, callback)
+    );
+  };
 
-    var argIndex = 0;
-    var message =
-      "Warning: " +
-      format.replace(/%s/g, function() {
-        return args[argIndex++];
-      });
-    if (typeof console !== "undefined") {
-      console.warn(message);
-    }
-    try {
-      // --- Welcome to debugging React ---
-      // This error was thrown as a convenience so that you can use this stack
-      // to find the callsite that caused this warning to fire.
-      throw new Error(message);
-    } catch (x) {}
+  ReactNativeFiberHostComponent.prototype.measureLayout = function measureLayout(
+    relativeToNativeNode,
+    onSuccess,
+    onFail /* currently unused */
+  ) {
+    UIManager.measureLayout(
+      this._nativeTag,
+      relativeToNativeNode,
+      mountSafeCallback(this, onFail),
+      mountSafeCallback(this, onSuccess)
+    );
   };
 
-  lowPriorityWarning = function(condition, format) {
-    if (format === undefined) {
-      throw new Error(
-        "`warning(condition, format, ...args)` requires a warning " +
-          "message argument"
-      );
+  ReactNativeFiberHostComponent.prototype.setNativeProps = function setNativeProps(
+    nativeProps
+  ) {
+    {
+      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
     }
-    if (!condition) {
-      for (
-        var _len2 = arguments.length,
-          args = Array(_len2 > 2 ? _len2 - 2 : 0),
-          _key2 = 2;
-        _key2 < _len2;
-        _key2++
-      ) {
-        args[_key2 - 2] = arguments[_key2];
-      }
 
-      printWarning.apply(undefined, [format].concat(args));
+    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
+
+    // Avoid the overhead of bridge calls if there's no update.
+    // This is an expensive no-op for Android, and causes an unnecessary
+    // view invalidation for certain components (eg RCTTextInput) on iOS.
+    if (updatePayload != null) {
+      UIManager.updateView(
+        this._nativeTag,
+        this.viewConfig.uiViewClassName,
+        updatePayload
+      );
     }
   };
-}
 
-var lowPriorityWarning$1 = lowPriorityWarning;
+  return ReactNativeFiberHostComponent;
+})();
 
-var ReactStrictModeWarnings = {
-  discardPendingWarnings: function() {},
-  flushPendingDeprecationWarnings: function() {},
-  flushPendingUnsafeLifecycleWarnings: function() {},
-  recordDeprecationWarnings: function(fiber, instance) {},
-  recordUnsafeLifecycleWarnings: function(fiber, instance) {}
-};
+var hasNativePerformanceNow =
+  typeof performance === "object" && typeof performance.now === "function";
 
-{
-  var LIFECYCLE_SUGGESTIONS = {
-    UNSAFE_componentWillMount: "componentDidMount",
-    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
-    UNSAFE_componentWillUpdate: "componentDidUpdate"
-  };
+var now$1 = hasNativePerformanceNow
+  ? function() {
+      return performance.now();
+    }
+  : function() {
+      return Date.now();
+    };
 
-  var pendingComponentWillMountWarnings = [];
-  var pendingComponentWillReceivePropsWarnings = [];
-  var pendingComponentWillUpdateWarnings = [];
-  var pendingUnsafeLifecycleWarnings = new Map();
+var scheduledCallback = null;
+var frameDeadline = 0;
 
-  // Tracks components we have already warned about.
-  var didWarnAboutDeprecatedLifecycles = new Set();
-  var didWarnAboutUnsafeLifecycles = new Set();
+var frameDeadlineObject = {
+  timeRemaining: function() {
+    return frameDeadline - now$1();
+  },
+  didTimeout: false
+};
 
-  var setToSortedString = function(set) {
-    var array = [];
-    set.forEach(function(value) {
-      array.push(value);
-    });
-    return array.sort().join(", ");
-  };
+function setTimeoutCallback() {
+  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
+  // React API probably changing to boolean rather than time remaining.
+  // Longer-term plan is to rewrite this using shared memory,
+  // And just return the value of the bit as the boolean.
+  frameDeadline = now$1() + 5;
 
-  ReactStrictModeWarnings.discardPendingWarnings = function() {
-    pendingComponentWillMountWarnings = [];
-    pendingComponentWillReceivePropsWarnings = [];
-    pendingComponentWillUpdateWarnings = [];
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  if (callback !== null) {
+    callback(frameDeadlineObject);
+  }
+}
 
-  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
-    pendingUnsafeLifecycleWarnings.forEach(function(
-      lifecycleWarningsMap,
-      strictRoot
-    ) {
-      var lifecyclesWarningMesages = [];
+// RN has a poor polyfill for requestIdleCallback so we aren't using it.
+// This implementation is only intended for short-term use anyway.
+// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
+function scheduleDeferredCallback$1(callback, options) {
+  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
+  scheduledCallback = callback;
+  var timeoutId = setTimeout(setTimeoutCallback, 1);
+  return timeoutId; // Timeouts are always numbers on RN
+}
 
-      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
-        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
-        if (lifecycleWarnings.length > 0) {
-          var componentNames = new Set();
-          lifecycleWarnings.forEach(function(fiber) {
-            componentNames.add(getComponentName(fiber) || "Component");
-            didWarnAboutUnsafeLifecycles.add(fiber.type);
-          });
+function cancelDeferredCallback$1(callbackID) {
+  scheduledCallback = null;
+  clearTimeout(callbackID); // Timeouts are always numbers on RN
+}
 
-          var formatted = lifecycle.replace("UNSAFE_", "");
-          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
-          var sortedComponentNames = setToSortedString(componentNames);
+// Renderers that don't support persistence
+// can re-export everything from this module.
 
-          lifecyclesWarningMesages.push(
-            formatted +
-              ": Please update the following components to use " +
-              (suggestion + " instead: " + sortedComponentNames)
-          );
-        }
-      });
+function shim() {
+  invariant(
+    false,
+    "The current renderer does not support persistence. " +
+      "This error is likely caused by a bug in React. " +
+      "Please file an issue."
+  );
+}
 
-      if (lifecyclesWarningMesages.length > 0) {
-        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
-          strictRoot
-        );
+// Persistence (when unsupported)
+var supportsPersistence = false;
+var cloneInstance = shim;
+var createContainerChildSet = shim;
+var appendChildToContainerChildSet = shim;
+var finalizeContainerChildren = shim;
+var replaceContainerChildren = shim;
 
-        warning(
-          false,
-          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
-            "\n\n%s" +
-            "\n\nLearn more about this warning here:" +
-            "\nhttps://fb.me/react-strict-mode-warnings",
-          strictRootComponentStack,
-          lifecyclesWarningMesages.join("\n\n")
-        );
-      }
-    });
+// Renderers that don't support hydration
+// can re-export everything from this module.
 
-    pendingUnsafeLifecycleWarnings = new Map();
-  };
+function shim$1() {
+  invariant(
+    false,
+    "The current renderer does not support hyration. " +
+      "This error is likely caused by a bug in React. " +
+      "Please file an issue."
+  );
+}
 
-  var findStrictRoot = function(fiber) {
-    var maybeStrictRoot = null;
+// Hydration (when unsupported)
+var supportsHydration = false;
+var canHydrateInstance = shim$1;
+var canHydrateTextInstance = shim$1;
+var getNextHydratableSibling = shim$1;
+var getFirstHydratableChild = shim$1;
+var hydrateInstance = shim$1;
+var hydrateTextInstance = shim$1;
+var didNotMatchHydratedContainerTextInstance = shim$1;
+var didNotMatchHydratedTextInstance = shim$1;
+var didNotHydrateContainerInstance = shim$1;
+var didNotHydrateInstance = shim$1;
+var didNotFindHydratableContainerInstance = shim$1;
+var didNotFindHydratableContainerTextInstance = shim$1;
+var didNotFindHydratableInstance = shim$1;
+var didNotFindHydratableTextInstance = shim$1;
 
-    var node = fiber;
-    while (node !== null) {
-      if (node.mode & StrictMode) {
-        maybeStrictRoot = node;
-      }
-      node = node.return;
-    }
+// Modules provided by RN:
+// Unused
 
-    return maybeStrictRoot;
-  };
+// Counter for uniquely identifying views.
+// % 10 === 1 means it is a rootTag.
+// % 2 === 0 means it is a Fabric tag.
+var nextReactTag = 3;
+function allocateTag() {
+  var tag = nextReactTag;
+  if (tag % 10 === 1) {
+    tag += 2;
+  }
+  nextReactTag = tag + 2;
+  return tag;
+}
 
-  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
-    if (pendingComponentWillMountWarnings.length > 0) {
-      var uniqueNames = new Set();
-      pendingComponentWillMountWarnings.forEach(function(fiber) {
-        uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+function recursivelyUncacheFiberNode(node) {
+  if (typeof node === "number") {
+    // Leaf node (eg text)
+    uncacheFiberNode(node);
+  } else {
+    uncacheFiberNode(node._nativeTag);
 
-      var sortedNames = setToSortedString(uniqueNames);
+    node._children.forEach(recursivelyUncacheFiberNode);
+  }
+}
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillMount is deprecated and will be removed in the next major version. " +
-          "Use componentDidMount instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillMount." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        sortedNames
-      );
+function appendInitialChild(parentInstance, child) {
+  parentInstance._children.push(child);
+}
 
-      pendingComponentWillMountWarnings = [];
-    }
+function createInstance(
+  type,
+  props,
+  rootContainerInstance,
+  hostContext,
+  internalInstanceHandle
+) {
+  var tag = allocateTag();
+  var viewConfig = ReactNativeViewConfigRegistry.get(type);
 
-    if (pendingComponentWillReceivePropsWarnings.length > 0) {
-      var _uniqueNames = new Set();
-      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
-        _uniqueNames.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+  {
+    for (var key in viewConfig.validAttributes) {
+      if (props.hasOwnProperty(key)) {
+        deepFreezeAndThrowOnMutationInDev(props[key]);
+      }
+    }
+  }
 
-      var _sortedNames = setToSortedString(_uniqueNames);
+  invariant(
+    type !== "RCTView" || !hostContext.isInAParentText,
+    "Nesting of <View> within <Text> is not currently supported."
+  );
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
-          "Use static getDerivedStateFromProps instead." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames
-      );
+  var updatePayload = create(props, viewConfig.validAttributes);
 
-      pendingComponentWillReceivePropsWarnings = [];
-    }
+  UIManager.createView(
+    tag, // reactTag
+    viewConfig.uiViewClassName, // viewName
+    rootContainerInstance, // rootTag
+    updatePayload // props
+  );
 
-    if (pendingComponentWillUpdateWarnings.length > 0) {
-      var _uniqueNames2 = new Set();
-      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
-        _uniqueNames2.add(getComponentName(fiber) || "Component");
-        didWarnAboutDeprecatedLifecycles.add(fiber.type);
-      });
+  var component = new ReactNativeFiberHostComponent(tag, viewConfig);
 
-      var _sortedNames2 = setToSortedString(_uniqueNames2);
+  precacheFiberNode(internalInstanceHandle, tag);
+  updateFiberProps(tag, props);
 
-      lowPriorityWarning$1(
-        false,
-        "componentWillUpdate is deprecated and will be removed in the next major version. " +
-          "Use componentDidUpdate instead. As a temporary workaround, " +
-          "you can rename to UNSAFE_componentWillUpdate." +
-          "\n\nPlease update the following components: %s" +
-          "\n\nLearn more about this warning here:" +
-          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
-        _sortedNames2
-      );
+  // Not sure how to avoid this cast. Flow is okay if the component is defined
+  // in the same file but if it's external it can't see the types.
+  return component;
+}
 
-      pendingComponentWillUpdateWarnings = [];
-    }
-  };
+function createTextInstance(
+  text,
+  rootContainerInstance,
+  hostContext,
+  internalInstanceHandle
+) {
+  invariant(
+    hostContext.isInAParentText,
+    "Text strings must be rendered within a <Text> component."
+  );
 
-  ReactStrictModeWarnings.recordDeprecationWarnings = function(
-    fiber,
-    instance
-  ) {
-    // Dedup strategy: Warn once per component.
-    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
-      return;
-    }
+  var tag = allocateTag();
 
-    // Don't warn about react-lifecycles-compat polyfilled components.
-    if (
-      typeof instance.componentWillMount === "function" &&
-      instance.componentWillMount.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillMountWarnings.push(fiber);
-    }
-    if (
-      typeof instance.componentWillReceiveProps === "function" &&
-      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillReceivePropsWarnings.push(fiber);
-    }
-    if (
-      typeof instance.componentWillUpdate === "function" &&
-      instance.componentWillUpdate.__suppressDeprecationWarning !== true
-    ) {
-      pendingComponentWillUpdateWarnings.push(fiber);
-    }
-  };
+  UIManager.createView(
+    tag, // reactTag
+    "RCTRawText", // viewName
+    rootContainerInstance, // rootTag
+    { text: text } // props
+  );
 
-  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
-    fiber,
-    instance
-  ) {
-    var strictRoot = findStrictRoot(fiber);
-    if (strictRoot === null) {
-      warning(
-        false,
-        "Expected to find a StrictMode component in a strict mode tree. " +
-          "This error is likely caused by a bug in React. Please file an issue."
-      );
-      return;
-    }
+  precacheFiberNode(internalInstanceHandle, tag);
 
-    // Dedup strategy: Warn once per component.
-    // This is difficult to track any other way since component names
-    // are often vague and are likely to collide between 3rd party libraries.
-    // An expand property is probably okay to use here since it's DEV-only,
-    // and will only be set in the event of serious warnings.
-    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
-      return;
-    }
+  return tag;
+}
 
-    var warningsForRoot = void 0;
-    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
-      warningsForRoot = {
-        UNSAFE_componentWillMount: [],
-        UNSAFE_componentWillReceiveProps: [],
-        UNSAFE_componentWillUpdate: []
-      };
+function finalizeInitialChildren(
+  parentInstance,
+  type,
+  props,
+  rootContainerInstance,
+  hostContext
+) {
+  // Don't send a no-op message over the bridge.
+  if (parentInstance._children.length === 0) {
+    return false;
+  }
 
-      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
-    } else {
-      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
-    }
+  // Map from child objects to native tags.
+  // Either way we need to pass a copy of the Array to prevent it from being frozen.
+  var nativeTags = parentInstance._children.map(function(child) {
+    return typeof child === "number"
+      ? child // Leaf node (eg text)
+      : child._nativeTag;
+  });
 
-    var unsafeLifecycles = [];
-    if (
-      (typeof instance.componentWillMount === "function" &&
-        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
-      typeof instance.UNSAFE_componentWillMount === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillMount");
-    }
-    if (
-      (typeof instance.componentWillReceiveProps === "function" &&
-        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-          true) ||
-      typeof instance.UNSAFE_componentWillReceiveProps === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
-    }
-    if (
-      (typeof instance.componentWillUpdate === "function" &&
-        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
-      typeof instance.UNSAFE_componentWillUpdate === "function"
-    ) {
-      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
-    }
+  UIManager.setChildren(
+    parentInstance._nativeTag, // containerTag
+    nativeTags // reactTags
+  );
 
-    if (unsafeLifecycles.length > 0) {
-      unsafeLifecycles.forEach(function(lifecycle) {
-        warningsForRoot[lifecycle].push(fiber);
-      });
-    }
-  };
+  return false;
 }
 
-/**
- * The "actual" render time is total time required to render the descendants of a Profiler component.
- * This time is stored as a stack, since Profilers can be nested.
- * This time is started during the "begin" phase and stopped during the "complete" phase.
- * It is paused (and accumulated) in the event of an interruption or an aborted render.
- */
+function getRootHostContext(rootContainerInstance) {
+  return { isInAParentText: false };
+}
 
-function createProfilerTimer(now) {
-  var fiberStack = void 0;
+function getChildHostContext(parentHostContext, type, rootContainerInstance) {
+  var prevIsInAParentText = parentHostContext.isInAParentText;
+  var isInAParentText =
+    type === "AndroidTextInput" || // Android
+    type === "RCTMultilineTextInputView" || // iOS
+    type === "RCTSinglelineTextInputView" || // iOS
+    type === "RCTText" ||
+    type === "RCTVirtualText";
 
-  {
-    fiberStack = [];
+  if (prevIsInAParentText !== isInAParentText) {
+    return { isInAParentText: isInAParentText };
+  } else {
+    return parentHostContext;
   }
+}
 
-  var timerPausedAt = 0;
-  var totalElapsedPauseTime = 0;
-
-  function checkActualRenderTimeStackEmpty() {
-    {
-      !(fiberStack.length === 0)
-        ? warning(
-            false,
-            "Expected an empty stack. Something was not reset properly."
-          )
-        : void 0;
-    }
-  }
+function getPublicInstance(instance) {
+  return instance;
+}
 
-  function markActualRenderTimeStarted(fiber) {
-    {
-      fiberStack.push(fiber);
-    }
-    fiber.stateNode.startTime = now() - totalElapsedPauseTime;
-  }
+function prepareForCommit(containerInfo) {
+  // Noop
+}
 
-  function pauseActualRenderTimerIfRunning() {
-    if (timerPausedAt === 0) {
-      timerPausedAt = now();
-    }
-  }
+function prepareUpdate(
+  instance,
+  type,
+  oldProps,
+  newProps,
+  rootContainerInstance,
+  hostContext
+) {
+  return emptyObject;
+}
 
-  function recordElapsedActualRenderTime(fiber) {
-    {
-      !(fiber === fiberStack.pop())
-        ? warning(false, "Unexpected Fiber popped.")
-        : void 0;
-    }
-    fiber.stateNode.duration +=
-      now() - totalElapsedPauseTime - fiber.stateNode.startTime;
-  }
+function resetAfterCommit(containerInfo) {
+  // Noop
+}
 
-  function resetActualRenderTimer() {
-    totalElapsedPauseTime = 0;
-  }
+var now = now$1;
+var isPrimaryRenderer = true;
+var scheduleDeferredCallback = scheduleDeferredCallback$1;
+var cancelDeferredCallback = cancelDeferredCallback$1;
 
-  function resumeActualRenderTimerIfPaused() {
-    if (timerPausedAt > 0) {
-      totalElapsedPauseTime += now() - timerPausedAt;
-      timerPausedAt = 0;
-    }
-  }
+function shouldDeprioritizeSubtree(type, props) {
+  return false;
+}
 
-  /**
-   * The "base" render time is the duration of the “begin” phase of work for a particular fiber.
-   * This time is measured and stored on each fiber.
-   * The time for all sibling fibers are accumulated and stored on their parent during the "complete" phase.
-   * If a fiber bails out (sCU false) then its "base" timer is cancelled and the fiber is not updated.
-   */
+function shouldSetTextContent(type, props) {
+  // TODO (bvaughn) Revisit this decision.
+  // Always returning false simplifies the createInstance() implementation,
+  // But creates an additional child Fiber for raw text children.
+  // No additional native views are created though.
+  // It's not clear to me which is better so I'm deferring for now.
+  // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
+  return false;
+}
 
-  var baseStartTime = -1;
+// -------------------
+//     Mutation
+// -------------------
 
-  function recordElapsedBaseRenderTimeIfRunning(fiber) {
-    if (baseStartTime !== -1) {
-      fiber.selfBaseTime = now() - baseStartTime;
-    }
-  }
+var supportsMutation = true;
 
-  function startBaseRenderTimer() {
-    {
-      if (baseStartTime !== -1) {
-        warning(
-          false,
-          "Cannot start base timer that is already running. " +
-            "This error is likely caused by a bug in React. " +
-            "Please file an issue."
-        );
-      }
-    }
-    baseStartTime = now();
-  }
+function appendChild(parentInstance, child) {
+  var childTag = typeof child === "number" ? child : child._nativeTag;
+  var children = parentInstance._children;
+  var index = children.indexOf(child);
 
-  function stopBaseRenderTimerIfRunning() {
-    baseStartTime = -1;
-  }
+  if (index >= 0) {
+    children.splice(index, 1);
+    children.push(child);
 
-  if (enableProfilerTimer) {
-    return {
-      checkActualRenderTimeStackEmpty: checkActualRenderTimeStackEmpty,
-      markActualRenderTimeStarted: markActualRenderTimeStarted,
-      pauseActualRenderTimerIfRunning: pauseActualRenderTimerIfRunning,
-      recordElapsedActualRenderTime: recordElapsedActualRenderTime,
-      resetActualRenderTimer: resetActualRenderTimer,
-      resumeActualRenderTimerIfPaused: resumeActualRenderTimerIfPaused,
-      recordElapsedBaseRenderTimeIfRunning: recordElapsedBaseRenderTimeIfRunning,
-      startBaseRenderTimer: startBaseRenderTimer,
-      stopBaseRenderTimerIfRunning: stopBaseRenderTimerIfRunning
-    };
+    UIManager.manageChildren(
+      parentInstance._nativeTag, // containerTag
+      [index], // moveFromIndices
+      [children.length - 1], // moveToIndices
+      [], // addChildReactTags
+      [], // addAtIndices
+      [] // removeAtIndices
+    );
   } else {
-    return {
-      checkActualRenderTimeStackEmpty: function() {},
-      markActualRenderTimeStarted: function(fiber) {},
-      pauseActualRenderTimerIfRunning: function() {},
-      recordElapsedActualRenderTime: function(fiber) {},
-      resetActualRenderTimer: function() {},
-      resumeActualRenderTimerIfPaused: function() {},
-      recordElapsedBaseRenderTimeIfRunning: function(fiber) {},
-      startBaseRenderTimer: function() {},
-      stopBaseRenderTimerIfRunning: function() {}
-    };
+    children.push(child);
+
+    UIManager.manageChildren(
+      parentInstance._nativeTag, // containerTag
+      [], // moveFromIndices
+      [], // moveToIndices
+      [childTag], // addChildReactTags
+      [children.length - 1], // addAtIndices
+      [] // removeAtIndices
+    );
   }
 }
 
-function getCurrentFiberOwnerName() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
-      return null;
-    }
-    var owner = fiber._debugOwner;
-    if (owner !== null && typeof owner !== "undefined") {
-      return getComponentName(owner);
-    }
-  }
-  return null;
+function appendChildToContainer(parentInstance, child) {
+  var childTag = typeof child === "number" ? child : child._nativeTag;
+  UIManager.setChildren(
+    parentInstance, // containerTag
+    [childTag] // reactTags
+  );
 }
 
-function getCurrentFiberStackAddendum$1() {
-  {
-    var fiber = ReactDebugCurrentFiber.current;
-    if (fiber === null) {
+function commitTextUpdate(textInstance, oldText, newText) {
+  UIManager.updateView(
+    textInstance, // reactTag
+    "RCTRawText", // viewName
+    { text: newText } // props
+  );
+}
+
+function commitUpdate(
+  instance,
+  updatePayloadTODO,
+  type,
+  oldProps,
+  newProps,
+  internalInstanceHandle
+) {
+  var viewConfig = instance.viewConfig;
+
+  updateFiberProps(instance._nativeTag, newProps);
+
+  var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
+
+  // Avoid the overhead of bridge calls if there's no update.
+  // This is an expensive no-op for Android, and causes an unnecessary
+  // view invalidation for certain components (eg RCTTextInput) on iOS.
+  if (updatePayload != null) {
+    UIManager.updateView(
+      instance._nativeTag, // reactTag
+      viewConfig.uiViewClassName, // viewName
+      updatePayload // props
+    );
+  }
+}
+
+function insertBefore(parentInstance, child, beforeChild) {
+  var children = parentInstance._children;
+  var index = children.indexOf(child);
+
+  // Move existing child or add new child?
+  if (index >= 0) {
+    children.splice(index, 1);
+    var beforeChildIndex = children.indexOf(beforeChild);
+    children.splice(beforeChildIndex, 0, child);
+
+    UIManager.manageChildren(
+      parentInstance._nativeTag, // containerID
+      [index], // moveFromIndices
+      [beforeChildIndex], // moveToIndices
+      [], // addChildReactTags
+      [], // addAtIndices
+      [] // removeAtIndices
+    );
+  } else {
+    var _beforeChildIndex = children.indexOf(beforeChild);
+    children.splice(_beforeChildIndex, 0, child);
+
+    var childTag = typeof child === "number" ? child : child._nativeTag;
+
+    UIManager.manageChildren(
+      parentInstance._nativeTag, // containerID
+      [], // moveFromIndices
+      [], // moveToIndices
+      [childTag], // addChildReactTags
+      [_beforeChildIndex], // addAtIndices
+      [] // removeAtIndices
+    );
+  }
+}
+
+function insertInContainerBefore(parentInstance, child, beforeChild) {
+  // TODO (bvaughn): Remove this check when...
+  // We create a wrapper object for the container in ReactNative render()
+  // Or we refactor to remove wrapper objects entirely.
+  // For more info on pros/cons see PR #8560 description.
+  invariant(
+    typeof parentInstance !== "number",
+    "Container does not support insertBefore operation"
+  );
+}
+
+function removeChild(parentInstance, child) {
+  recursivelyUncacheFiberNode(child);
+  var children = parentInstance._children;
+  var index = children.indexOf(child);
+
+  children.splice(index, 1);
+
+  UIManager.manageChildren(
+    parentInstance._nativeTag, // containerID
+    [], // moveFromIndices
+    [], // moveToIndices
+    [], // addChildReactTags
+    [], // addAtIndices
+    [index] // removeAtIndices
+  );
+}
+
+function removeChildFromContainer(parentInstance, child) {
+  recursivelyUncacheFiberNode(child);
+  UIManager.manageChildren(
+    parentInstance, // containerID
+    [], // moveFromIndices
+    [], // moveToIndices
+    [], // addChildReactTags
+    [], // addAtIndices
+    [0] // removeAtIndices
+  );
+}
+
+function resetTextContent(instance) {
+  // Noop
+}
+
+var describeComponentFrame = function(name, source, ownerName) {
+  return (
+    "\n    in " +
+    (name || "Unknown") +
+    (source
+      ? " (at " +
+        source.fileName.replace(/^.*[\\\/]/, "") +
+        ":" +
+        source.lineNumber +
+        ")"
+      : ownerName ? " (created by " + ownerName + ")" : "")
+  );
+};
+
+function describeFiber(fiber) {
+  switch (fiber.tag) {
+    case IndeterminateComponent:
+    case FunctionalComponent:
+    case ClassComponent:
+    case HostComponent:
+      var owner = fiber._debugOwner;
+      var source = fiber._debugSource;
+      var name = getComponentName(fiber);
+      var ownerName = null;
+      if (owner) {
+        ownerName = getComponentName(owner);
+      }
+      return describeComponentFrame(name, source, ownerName);
+    default:
+      return "";
+  }
+}
+
+// This function can only be called with a work-in-progress fiber and
+// only during begin or complete phase. Do not call it under any other
+// circumstances.
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  var node = workInProgress;
+  do {
+    info += describeFiber(node);
+    // Otherwise this return pointer might point to the wrong tree:
+    node = node.return;
+  } while (node);
+  return info;
+}
+
+function getCurrentFiberOwnerName() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
+      return null;
+    }
+    var owner = fiber._debugOwner;
+    if (owner !== null && typeof owner !== "undefined") {
+      return getComponentName(owner);
+    }
+  }
+  return null;
+}
+
+function getCurrentFiberStackAddendum() {
+  {
+    var fiber = ReactDebugCurrentFiber.current;
+    if (fiber === null) {
       return null;
     }
     // Safe because if current fiber exists, we are reconciling,
@@ -4177,7 +4227,7 @@ function resetCurrentFiber() {
 }
 
 function setCurrentFiber(fiber) {
-  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum$1;
+  ReactDebugCurrentFrame.getCurrentStack = getCurrentFiberStackAddendum;
   ReactDebugCurrentFiber.current = fiber;
   ReactDebugCurrentFiber.phase = null;
 }
@@ -4193,9 +4243,21 @@ var ReactDebugCurrentFiber = {
   setCurrentFiber: setCurrentFiber,
   setCurrentPhase: setCurrentPhase,
   getCurrentFiberOwnerName: getCurrentFiberOwnerName,
-  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum$1
+  getCurrentFiberStackAddendum: getCurrentFiberStackAddendum
 };
 
+var debugRenderPhaseSideEffects = false;
+var debugRenderPhaseSideEffectsForStrictMode = false;
+var enableGetDerivedStateFromCatch = false;
+var enableSuspense = false;
+var enableUserTimingAPI = true;
+var replayFailedUnitOfWorkWithInvokeGuardedCallback = true;
+var warnAboutDeprecatedLifecycles = false;
+var warnAboutLegacyContextAPI = false;
+var enableProfilerTimer = true;
+
+// Only used in www builds.
+
 // Prefix measurements so that it's possible to filter them.
 // Longer prefixes are hard to read in DevTools.
 var reactEmoji = "\u269B";
@@ -4651,9970 +4713,9647 @@ function stopCommitLifeCyclesTimer() {
   }
 }
 
-// UpdateQueue is a linked list of prioritized updates.
-//
-// Like fibers, update queues come in pairs: a current queue, which represents
-// the visible state of the screen, and a work-in-progress queue, which is
-// can be mutated and processed asynchronously before it is committed — a form
-// of double buffering. If a work-in-progress render is discarded before
-// finishing, we create a new work-in-progress by cloning the current queue.
-//
-// Both queues share a persistent, singly-linked list structure. To schedule an
-// update, we append it to the end of both queues. Each queue maintains a
-// pointer to first update in the persistent list that hasn't been processed.
-// The work-in-progress pointer always has a position equal to or greater than
-// the current queue, since we always work on that one. The current queue's
-// pointer is only updated during the commit phase, when we swap in the
-// work-in-progress.
-//
-// For example:
-//
-//   Current pointer:           A - B - C - D - E - F
-//   Work-in-progress pointer:              D - E - F
-//                                          ^
-//                                          The work-in-progress queue has
-//                                          processed more updates than current.
-//
-// The reason we append to both queues is because otherwise we might drop
-// updates without ever processing them. For example, if we only add updates to
-// the work-in-progress queue, some updates could be lost whenever a work-in
-// -progress render restarts by cloning from current. Similarly, if we only add
-// updates to the current queue, the updates will be lost whenever an already
-// in-progress queue commits and swaps with the current queue. However, by
-// adding to both queues, we guarantee that the update will be part of the next
-// work-in-progress. (And because the work-in-progress queue becomes the
-// current queue once it commits, there's no danger of applying the same
-// update twice.)
-//
-// Prioritization
-// --------------
-//
-// Updates are not sorted by priority, but by insertion; new updates are always
-// appended to the end of the list.
-//
-// The priority is still important, though. When processing the update queue
-// during the render phase, only the updates with sufficient priority are
-// included in the result. If we skip an update because it has insufficient
-// priority, it remains in the queue to be processed later, during a lower
-// priority render. Crucially, all updates subsequent to a skipped update also
-// remain in the queue *regardless of their priority*. That means high priority
-// updates are sometimes processed twice, at two separate priorities. We also
-// keep track of a base state, that represents the state before the first
-// update in the queue is applied.
-//
-// For example:
-//
-//   Given a base state of '', and the following queue of updates
-//
-//     A1 - B2 - C1 - D2
-//
-//   where the number indicates the priority, and the update is applied to the
-//   previous state by appending a letter, React will process these updates as
-//   two separate renders, one per distinct priority level:
-//
-//   First render, at priority 1:
-//     Base state: ''
-//     Updates: [A1, C1]
-//     Result state: 'AC'
-//
-//   Second render, at priority 2:
-//     Base state: 'A'            <-  The base state does not include C1,
-//                                    because B2 was skipped.
-//     Updates: [B2, C1, D2]      <-  C1 was rebased on top of B2
-//     Result state: 'ABCD'
-//
-// Because we process updates in insertion order, and rebase high priority
-// updates when preceding updates are skipped, the final result is deterministic
-// regardless of priority. Intermediate state may vary according to system
-// resources, but the final state is always the same.
-
-var UpdateState = 0;
-var ReplaceState = 1;
-var ForceUpdate = 2;
-var CaptureUpdate = 3;
+var valueStack = [];
 
-// Global state that is reset at the beginning of calling `processUpdateQueue`.
-// It should only be read right after calling `processUpdateQueue`, via
-// `checkHasForceUpdateAfterProcessing`.
-var hasForceUpdate = false;
+var fiberStack = void 0;
 
-var didWarnUpdateInsideUpdate = void 0;
-var currentlyProcessingQueue = void 0;
-var resetCurrentlyProcessingQueue = void 0;
 {
-  didWarnUpdateInsideUpdate = false;
-  currentlyProcessingQueue = null;
-  resetCurrentlyProcessingQueue = function() {
-    currentlyProcessingQueue = null;
-  };
+  fiberStack = [];
 }
 
-function createUpdateQueue(baseState) {
-  var queue = {
-    expirationTime: NoWork,
-    baseState: baseState,
-    firstUpdate: null,
-    lastUpdate: null,
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
-    firstEffect: null,
-    lastEffect: null,
-    firstCapturedEffect: null,
-    lastCapturedEffect: null
+var index = -1;
+
+function createCursor(defaultValue) {
+  return {
+    current: defaultValue
   };
-  return queue;
 }
 
-function cloneUpdateQueue(currentQueue) {
-  var queue = {
-    expirationTime: currentQueue.expirationTime,
-    baseState: currentQueue.baseState,
-    firstUpdate: currentQueue.firstUpdate,
-    lastUpdate: currentQueue.lastUpdate,
-
-    // TODO: With resuming, if we bail out and resuse the child tree, we should
-    // keep these effects.
-    firstCapturedUpdate: null,
-    lastCapturedUpdate: null,
+function pop(cursor, fiber) {
+  if (index < 0) {
+    {
+      warning(false, "Unexpected pop.");
+    }
+    return;
+  }
 
-    firstEffect: null,
-    lastEffect: null,
+  {
+    if (fiber !== fiberStack[index]) {
+      warning(false, "Unexpected Fiber popped.");
+    }
+  }
 
-    firstCapturedEffect: null,
-    lastCapturedEffect: null
-  };
-  return queue;
-}
+  cursor.current = valueStack[index];
 
-function createUpdate(expirationTime) {
-  return {
-    expirationTime: expirationTime,
+  valueStack[index] = null;
 
-    tag: UpdateState,
-    payload: null,
-    callback: null,
+  {
+    fiberStack[index] = null;
+  }
 
-    next: null,
-    nextEffect: null
-  };
+  index--;
 }
 
-function appendUpdateToQueue(queue, update, expirationTime) {
-  // Append the update to the end of the list.
-  if (queue.lastUpdate === null) {
-    // Queue is empty
-    queue.firstUpdate = queue.lastUpdate = update;
-  } else {
-    queue.lastUpdate.next = update;
-    queue.lastUpdate = update;
-  }
-  if (
-    queue.expirationTime === NoWork ||
-    queue.expirationTime > expirationTime
-  ) {
-    // The incoming update has the earliest expiration of any update in the
-    // queue. Update the queue's expiration time.
-    queue.expirationTime = expirationTime;
-  }
-}
+function push(cursor, value, fiber) {
+  index++;
 
-function enqueueUpdate(fiber, update, expirationTime) {
-  // Update queues are created lazily.
-  var alternate = fiber.alternate;
-  var queue1 = void 0;
-  var queue2 = void 0;
-  if (alternate === null) {
-    // There's only one fiber.
-    queue1 = fiber.updateQueue;
-    queue2 = null;
-    if (queue1 === null) {
-      queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
-    }
-  } else {
-    // There are two owners.
-    queue1 = fiber.updateQueue;
-    queue2 = alternate.updateQueue;
-    if (queue1 === null) {
-      if (queue2 === null) {
-        // Neither fiber has an update queue. Create new ones.
-        queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
-        queue2 = alternate.updateQueue = createUpdateQueue(
-          alternate.memoizedState
-        );
-      } else {
-        // Only one fiber has an update queue. Clone to create a new one.
-        queue1 = fiber.updateQueue = cloneUpdateQueue(queue2);
-      }
-    } else {
-      if (queue2 === null) {
-        // Only one fiber has an update queue. Clone to create a new one.
-        queue2 = alternate.updateQueue = cloneUpdateQueue(queue1);
-      } else {
-        // Both owners have an update queue.
-      }
-    }
-  }
-  if (queue2 === null || queue1 === queue2) {
-    // There's only a single queue.
-    appendUpdateToQueue(queue1, update, expirationTime);
-  } else {
-    // There are two queues. We need to append the update to both queues,
-    // while accounting for the persistent structure of the list — we don't
-    // want the same update to be added multiple times.
-    if (queue1.lastUpdate === null || queue2.lastUpdate === null) {
-      // One of the queues is not empty. We must add the update to both queues.
-      appendUpdateToQueue(queue1, update, expirationTime);
-      appendUpdateToQueue(queue2, update, expirationTime);
-    } else {
-      // Both queues are non-empty. The last update is the same in both lists,
-      // because of structural sharing. So, only append to one of the lists.
-      appendUpdateToQueue(queue1, update, expirationTime);
-      // But we still need to update the `lastUpdate` pointer of queue2.
-      queue2.lastUpdate = update;
-    }
+  valueStack[index] = cursor.current;
+
+  {
+    fiberStack[index] = fiber;
   }
 
+  cursor.current = value;
+}
+
+function checkThatStackIsEmpty() {
   {
-    if (
-      fiber.tag === ClassComponent &&
-      (currentlyProcessingQueue === queue1 ||
-        (queue2 !== null && currentlyProcessingQueue === queue2)) &&
-      !didWarnUpdateInsideUpdate
-    ) {
+    if (index !== -1) {
       warning(
         false,
-        "An update (setState, replaceState, or forceUpdate) was scheduled " +
-          "from inside an update function. Update functions should be pure, " +
-          "with zero side-effects. Consider using componentDidUpdate or a " +
-          "callback."
+        "Expected an empty stack. Something was not reset properly."
       );
-      didWarnUpdateInsideUpdate = true;
     }
   }
 }
 
-function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
-  // Captured updates go into a separate list, and only on the work-in-
-  // progress queue.
-  var workInProgressQueue = workInProgress.updateQueue;
-  if (workInProgressQueue === null) {
-    workInProgressQueue = workInProgress.updateQueue = createUpdateQueue(
-      workInProgress.memoizedState
-    );
-  } else {
-    // TODO: I put this here rather than createWorkInProgress so that we don't
-    // clone the queue unnecessarily. There's probably a better way to
-    // structure this.
-    workInProgressQueue = ensureWorkInProgressQueueIsAClone(
-      workInProgress,
-      workInProgressQueue
-    );
+function resetStackAfterFatalErrorInDev() {
+  {
+    index = -1;
+    valueStack.length = 0;
+    fiberStack.length = 0;
   }
+}
 
-  // Append the update to the end of the list.
-  if (workInProgressQueue.lastCapturedUpdate === null) {
-    // This is the first render phase update
-    workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update;
-  } else {
-    workInProgressQueue.lastCapturedUpdate.next = update;
-    workInProgressQueue.lastCapturedUpdate = update;
-  }
-  if (
-    workInProgressQueue.expirationTime === NoWork ||
-    workInProgressQueue.expirationTime > renderExpirationTime
-  ) {
-    // The incoming update has the earliest expiration of any update in the
-    // queue. Update the queue's expiration time.
-    workInProgressQueue.expirationTime = renderExpirationTime;
-  }
+var warnedAboutMissingGetChildContext = void 0;
+
+{
+  warnedAboutMissingGetChildContext = {};
 }
 
-function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
-  var current = workInProgress.alternate;
-  if (current !== null) {
-    // If the work-in-progress queue is equal to the current queue,
-    // we need to clone it first.
-    if (queue === current.updateQueue) {
-      queue = workInProgress.updateQueue = cloneUpdateQueue(queue);
-    }
+// A cursor to the current merged context object on the stack.
+var contextStackCursor = createCursor(emptyObject);
+// A cursor to a boolean indicating whether the context has changed.
+var didPerformWorkStackCursor = createCursor(false);
+// Keep track of the previous context object that was on the stack.
+// We use this to get access to the parent context after we have already
+// pushed the next context provider, and now need to merge their contexts.
+var previousContext = emptyObject;
+
+function getUnmaskedContext(workInProgress) {
+  var hasOwnContext = isContextProvider(workInProgress);
+  if (hasOwnContext) {
+    // If the fiber is a context provider itself, when we read its context
+    // we have already pushed its own child context on the stack. A context
+    // provider should not "see" its own child context. Therefore we read the
+    // previous (parent) context instead for a context provider.
+    return previousContext;
   }
-  return queue;
+  return contextStackCursor.current;
 }
 
-function getStateFromUpdate(
-  workInProgress,
-  queue,
-  update,
-  prevState,
-  nextProps,
-  instance
-) {
-  switch (update.tag) {
-    case ReplaceState: {
-      var _payload = update.payload;
-      if (typeof _payload === "function") {
-        // Updater function
-        {
-          if (
-            debugRenderPhaseSideEffects ||
-            (debugRenderPhaseSideEffectsForStrictMode &&
-              workInProgress.mode & StrictMode)
-          ) {
-            _payload.call(instance, prevState, nextProps);
-          }
-        }
-        return _payload.call(instance, prevState, nextProps);
-      }
-      // State object
-      return _payload;
-    }
-    case CaptureUpdate: {
-      workInProgress.effectTag =
-        (workInProgress.effectTag & ~ShouldCapture) | DidCapture;
-    }
-    // Intentional fallthrough
-    case UpdateState: {
-      var _payload2 = update.payload;
-      var partialState = void 0;
-      if (typeof _payload2 === "function") {
-        // Updater function
-        {
-          if (
-            debugRenderPhaseSideEffects ||
-            (debugRenderPhaseSideEffectsForStrictMode &&
-              workInProgress.mode & StrictMode)
-          ) {
-            _payload2.call(instance, prevState, nextProps);
-          }
-        }
-        partialState = _payload2.call(instance, prevState, nextProps);
-      } else {
-        // Partial state object
-        partialState = _payload2;
-      }
-      if (partialState === null || partialState === undefined) {
-        // Null and undefined are treated as no-ops.
-        return prevState;
-      }
-      // Merge the partial state and the previous state.
-      return Object.assign({}, prevState, partialState);
-    }
-    case ForceUpdate: {
-      hasForceUpdate = true;
-      return prevState;
-    }
-  }
-  return prevState;
+function cacheContext(workInProgress, unmaskedContext, maskedContext) {
+  var instance = workInProgress.stateNode;
+  instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
+  instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
 }
 
-function processUpdateQueue(
-  workInProgress,
-  queue,
-  props,
-  instance,
-  renderExpirationTime
-) {
-  hasForceUpdate = false;
+function getMaskedContext(workInProgress, unmaskedContext) {
+  var type = workInProgress.type;
+  var contextTypes = type.contextTypes;
+  if (!contextTypes) {
+    return emptyObject;
+  }
 
+  // Avoid recreating masked context unless unmasked context has changed.
+  // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
+  // This may trigger infinite loops if componentWillReceiveProps calls setState.
+  var instance = workInProgress.stateNode;
   if (
-    queue.expirationTime === NoWork ||
-    queue.expirationTime > renderExpirationTime
+    instance &&
+    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
   ) {
-    // Insufficient priority. Bailout.
-    return;
+    return instance.__reactInternalMemoizedMaskedChildContext;
   }
 
-  queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+  var context = {};
+  for (var key in contextTypes) {
+    context[key] = unmaskedContext[key];
+  }
 
   {
-    currentlyProcessingQueue = queue;
+    var name = getComponentName(workInProgress) || "Unknown";
+    checkPropTypes(
+      contextTypes,
+      context,
+      "context",
+      name,
+      ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+    );
   }
 
-  // These values may change as we process the queue.
-  var newBaseState = queue.baseState;
-  var newFirstUpdate = null;
-  var newExpirationTime = NoWork;
+  // Cache unmasked context so we can avoid recreating masked context unless necessary.
+  // Context is created before the class component is instantiated so check for instance.
+  if (instance) {
+    cacheContext(workInProgress, unmaskedContext, context);
+  }
 
-  // Iterate through the list of updates to compute the result.
-  var update = queue.firstUpdate;
-  var resultState = newBaseState;
-  while (update !== null) {
-    var updateExpirationTime = update.expirationTime;
-    if (updateExpirationTime > renderExpirationTime) {
-      // This update does not have sufficient priority. Skip it.
-      if (newFirstUpdate === null) {
-        // This is the first skipped update. It will be the first update in
-        // the new list.
-        newFirstUpdate = update;
-        // Since this is the first update that was skipped, the current result
-        // is the new base state.
-        newBaseState = resultState;
-      }
-      // Since this update will remain in the list, update the remaining
-      // expiration time.
-      if (
-        newExpirationTime === NoWork ||
-        newExpirationTime > updateExpirationTime
-      ) {
-        newExpirationTime = updateExpirationTime;
-      }
-    } else {
-      // This update does have sufficient priority. Process it and compute
-      // a new result.
-      resultState = getStateFromUpdate(
-        workInProgress,
-        queue,
-        update,
-        resultState,
-        props,
-        instance
-      );
-      var _callback = update.callback;
-      if (_callback !== null) {
-        workInProgress.effectTag |= Callback;
-        // Set this to null, in case it was mutated during an aborted render.
-        update.nextEffect = null;
-        if (queue.lastEffect === null) {
-          queue.firstEffect = queue.lastEffect = update;
-        } else {
-          queue.lastEffect.nextEffect = update;
-          queue.lastEffect = update;
-        }
-      }
-    }
-    // Continue to the next update.
-    update = update.next;
+  return context;
+}
+
+function hasContextChanged() {
+  return didPerformWorkStackCursor.current;
+}
+
+function isContextConsumer(fiber) {
+  return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+}
+
+function isContextProvider(fiber) {
+  return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+}
+
+function popContextProvider(fiber) {
+  if (!isContextProvider(fiber)) {
+    return;
   }
 
-  // Separately, iterate though the list of captured updates.
-  var newFirstCapturedUpdate = null;
-  update = queue.firstCapturedUpdate;
-  while (update !== null) {
-    var _updateExpirationTime = update.expirationTime;
-    if (_updateExpirationTime > renderExpirationTime) {
-      // This update does not have sufficient priority. Skip it.
-      if (newFirstCapturedUpdate === null) {
-        // This is the first skipped captured update. It will be the first
-        // update in the new list.
-        newFirstCapturedUpdate = update;
-        // If this is the first update that was skipped, the current result is
-        // the new base state.
-        if (newFirstUpdate === null) {
-          newBaseState = resultState;
-        }
-      }
-      // Since this update will remain in the list, update the remaining
-      // expiration time.
-      if (
-        newExpirationTime === NoWork ||
-        newExpirationTime > _updateExpirationTime
-      ) {
-        newExpirationTime = _updateExpirationTime;
-      }
-    } else {
-      // This update does have sufficient priority. Process it and compute
-      // a new result.
-      resultState = getStateFromUpdate(
-        workInProgress,
-        queue,
-        update,
-        resultState,
-        props,
-        instance
-      );
-      var _callback2 = update.callback;
-      if (_callback2 !== null) {
-        workInProgress.effectTag |= Callback;
-        // Set this to null, in case it was mutated during an aborted render.
-        update.nextEffect = null;
-        if (queue.lastCapturedEffect === null) {
-          queue.firstCapturedEffect = queue.lastCapturedEffect = update;
-        } else {
-          queue.lastCapturedEffect.nextEffect = update;
-          queue.lastCapturedEffect = update;
-        }
+  pop(didPerformWorkStackCursor, fiber);
+  pop(contextStackCursor, fiber);
+}
+
+function popTopLevelContextObject(fiber) {
+  pop(didPerformWorkStackCursor, fiber);
+  pop(contextStackCursor, fiber);
+}
+
+function pushTopLevelContextObject(fiber, context, didChange) {
+  invariant(
+    contextStackCursor.current === emptyObject,
+    "Unexpected context found on stack. " +
+      "This error is likely caused by a bug in React. Please file an issue."
+  );
+
+  push(contextStackCursor, context, fiber);
+  push(didPerformWorkStackCursor, didChange, fiber);
+}
+
+function processChildContext(fiber, parentContext) {
+  var instance = fiber.stateNode;
+  var childContextTypes = fiber.type.childContextTypes;
+
+  // TODO (bvaughn) Replace this behavior with an invariant() in the future.
+  // It has only been added in Fiber to match the (unintentional) behavior in Stack.
+  if (typeof instance.getChildContext !== "function") {
+    {
+      var componentName = getComponentName(fiber) || "Unknown";
+
+      if (!warnedAboutMissingGetChildContext[componentName]) {
+        warnedAboutMissingGetChildContext[componentName] = true;
+        warning(
+          false,
+          "%s.childContextTypes is specified but there is no getChildContext() method " +
+            "on the instance. You can either define getChildContext() on %s or remove " +
+            "childContextTypes from it.",
+          componentName,
+          componentName
+        );
       }
     }
-    update = update.next;
+    return parentContext;
   }
 
-  if (newFirstUpdate === null) {
-    queue.lastUpdate = null;
+  var childContext = void 0;
+  {
+    ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
   }
-  if (newFirstCapturedUpdate === null) {
-    queue.lastCapturedUpdate = null;
-  } else {
-    workInProgress.effectTag |= Callback;
+  startPhaseTimer(fiber, "getChildContext");
+  childContext = instance.getChildContext();
+  stopPhaseTimer();
+  {
+    ReactDebugCurrentFiber.setCurrentPhase(null);
   }
-  if (newFirstUpdate === null && newFirstCapturedUpdate === null) {
-    // We processed every update, without skipping. That means the new base
-    // state is the same as the result state.
-    newBaseState = resultState;
+  for (var contextKey in childContext) {
+    invariant(
+      contextKey in childContextTypes,
+      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+      getComponentName(fiber) || "Unknown",
+      contextKey
+    );
+  }
+  {
+    var name = getComponentName(fiber) || "Unknown";
+    checkPropTypes(
+      childContextTypes,
+      childContext,
+      "child context",
+      name,
+      // In practice, there is one case in which we won't get a stack. It's when
+      // somebody calls unstable_renderSubtreeIntoContainer() and we process
+      // context from the parent component instance. The stack will be missing
+      // because it's outside of the reconciliation, and so the pointer has not
+      // been set. This is rare and doesn't matter. We'll also remove that API.
+      ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+    );
   }
 
-  queue.baseState = newBaseState;
-  queue.firstUpdate = newFirstUpdate;
-  queue.firstCapturedUpdate = newFirstCapturedUpdate;
-  queue.expirationTime = newExpirationTime;
+  return Object.assign({}, parentContext, childContext);
+}
 
-  workInProgress.memoizedState = resultState;
+function pushContextProvider(workInProgress) {
+  if (!isContextProvider(workInProgress)) {
+    return false;
+  }
 
-  {
-    currentlyProcessingQueue = null;
+  var instance = workInProgress.stateNode;
+  // We push the context as early as possible to ensure stack integrity.
+  // If the instance does not exist yet, we will push null at first,
+  // and replace it on the stack later when invalidating the context.
+  var memoizedMergedChildContext =
+    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+    emptyObject;
+
+  // Remember the parent context so we can merge with it later.
+  // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
+  previousContext = contextStackCursor.current;
+  push(contextStackCursor, memoizedMergedChildContext, workInProgress);
+  push(
+    didPerformWorkStackCursor,
+    didPerformWorkStackCursor.current,
+    workInProgress
+  );
+
+  return true;
+}
+
+function invalidateContextProvider(workInProgress, didChange) {
+  var instance = workInProgress.stateNode;
+  invariant(
+    instance,
+    "Expected to have an instance by this point. " +
+      "This error is likely caused by a bug in React. Please file an issue."
+  );
+
+  if (didChange) {
+    // Merge parent and own context.
+    // Skip this if we're not updating due to sCU.
+    // This avoids unnecessarily recomputing memoized values.
+    var mergedContext = processChildContext(workInProgress, previousContext);
+    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+
+    // Replace the old (or empty) context with the new one.
+    // It is important to unwind the context in the reverse order.
+    pop(didPerformWorkStackCursor, workInProgress);
+    pop(contextStackCursor, workInProgress);
+    // Now push the new context and mark that it has changed.
+    push(contextStackCursor, mergedContext, workInProgress);
+    push(didPerformWorkStackCursor, didChange, workInProgress);
+  } else {
+    pop(didPerformWorkStackCursor, workInProgress);
+    push(didPerformWorkStackCursor, didChange, workInProgress);
   }
 }
 
-function callCallback(callback, context) {
+function findCurrentUnmaskedContext(fiber) {
+  // Currently this is only used with renderSubtreeIntoContainer; not sure if it
+  // makes sense elsewhere
   invariant(
-    typeof callback === "function",
-    "Invalid argument passed as callback. Expected a function. Instead " +
-      "received: %s",
-    callback
+    isFiberMounted(fiber) && fiber.tag === ClassComponent,
+    "Expected subtree parent to be a mounted class component. " +
+      "This error is likely caused by a bug in React. Please file an issue."
   );
-  callback.call(context);
+
+  var node = fiber;
+  while (node.tag !== HostRoot) {
+    if (isContextProvider(node)) {
+      return node.stateNode.__reactInternalMemoizedMergedChildContext;
+    }
+    var parent = node.return;
+    invariant(
+      parent,
+      "Found unexpected detached subtree parent. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+    node = parent;
+  }
+  return node.stateNode.context;
 }
 
-function resetHasForceUpdateBeforeProcessing() {
-  hasForceUpdate = false;
+// Max 31 bit integer. The max integer size in V8 for 32-bit systems.
+// Math.pow(2, 30) - 1
+// 0b111111111111111111111111111111
+var MAX_SIGNED_31_BIT_INT = 1073741823;
+
+var NoWork = 0;
+var Sync = 1;
+var Never = MAX_SIGNED_31_BIT_INT;
+
+var UNIT_SIZE = 10;
+var MAGIC_NUMBER_OFFSET = 2;
+
+// 1 unit of expiration time represents 10ms.
+function msToExpirationTime(ms) {
+  // Always add an offset so that we don't clash with the magic number for NoWork.
+  return ((ms / UNIT_SIZE) | 0) + MAGIC_NUMBER_OFFSET;
 }
 
-function checkHasForceUpdateAfterProcessing() {
-  return hasForceUpdate;
+function expirationTimeToMs(expirationTime) {
+  return (expirationTime - MAGIC_NUMBER_OFFSET) * UNIT_SIZE;
 }
 
-function commitUpdateQueue(
-  finishedWork,
-  finishedQueue,
-  instance,
-  renderExpirationTime
-) {
-  // If the finished render included captured updates, and there are still
-  // lower priority updates left over, we need to keep the captured updates
-  // in the queue so that they are rebased and not dropped once we process the
-  // queue again at the lower priority.
-  if (finishedQueue.firstCapturedUpdate !== null) {
-    // Join the captured update list to the end of the normal list.
-    if (finishedQueue.lastUpdate !== null) {
-      finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate;
-      finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate;
-    }
-    // Clear the list of captured updates.
-    finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null;
-  }
+function ceiling(num, precision) {
+  return (((num / precision) | 0) + 1) * precision;
+}
 
-  // Commit the effects
-  var effect = finishedQueue.firstEffect;
-  finishedQueue.firstEffect = finishedQueue.lastEffect = null;
-  while (effect !== null) {
-    var _callback3 = effect.callback;
-    if (_callback3 !== null) {
-      effect.callback = null;
-      callCallback(_callback3, instance);
-    }
-    effect = effect.nextEffect;
-  }
+function computeExpirationBucket(currentTime, expirationInMs, bucketSizeMs) {
+  return (
+    MAGIC_NUMBER_OFFSET +
+    ceiling(
+      currentTime - MAGIC_NUMBER_OFFSET + expirationInMs / UNIT_SIZE,
+      bucketSizeMs / UNIT_SIZE
+    )
+  );
+}
 
-  effect = finishedQueue.firstCapturedEffect;
-  finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
-  while (effect !== null) {
-    var _callback4 = effect.callback;
-    if (_callback4 !== null) {
-      effect.callback = null;
-      callCallback(_callback4, instance);
-    }
-    effect = effect.nextEffect;
+var NoContext = 0;
+var AsyncMode = 1;
+var StrictMode = 2;
+var ProfileMode = 4;
+
+var hasBadMapPolyfill = void 0;
+
+{
+  hasBadMapPolyfill = false;
+  try {
+    var nonExtensibleObject = Object.preventExtensions({});
+    var testMap = new Map([[nonExtensibleObject, null]]);
+    var testSet = new Set([nonExtensibleObject]);
+    // This is necessary for Rollup to not consider these unused.
+    // https://github.com/rollup/rollup/issues/1771
+    // TODO: we can remove these if Rollup fixes the bug.
+    testMap.set(0, 0);
+    testSet.add(0);
+  } catch (e) {
+    // TODO: Consider warning about bad polyfills
+    hasBadMapPolyfill = true;
   }
 }
 
-var fakeInternalInstance = {};
-var isArray = Array.isArray;
+// A Fiber is work on a Component that needs to be done or was done. There can
+// be more than one per component.
 
-var didWarnAboutStateAssignmentForComponent = void 0;
-var didWarnAboutUninitializedState = void 0;
-var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
-var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
-var didWarnAboutUndefinedDerivedState = void 0;
-var warnOnUndefinedDerivedState = void 0;
-var warnOnInvalidCallback = void 0;
+var debugCounter = void 0;
 
 {
-  didWarnAboutStateAssignmentForComponent = new Set();
-  didWarnAboutUninitializedState = new Set();
-  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
-  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
-  didWarnAboutUndefinedDerivedState = new Set();
-
-  var didWarnOnInvalidCallback = new Set();
+  debugCounter = 1;
+}
 
-  warnOnInvalidCallback = function(callback, callerName) {
-    if (callback === null || typeof callback === "function") {
-      return;
-    }
-    var key = callerName + "_" + callback;
-    if (!didWarnOnInvalidCallback.has(key)) {
-      didWarnOnInvalidCallback.add(key);
-      warning(
-        false,
-        "%s(...): Expected the last optional `callback` argument to be a " +
-          "function. Instead received: %s.",
-        callerName,
-        callback
-      );
-    }
-  };
+function FiberNode(tag, pendingProps, key, mode) {
+  // Instance
+  this.tag = tag;
+  this.key = key;
+  this.type = null;
+  this.stateNode = null;
 
-  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
-    if (partialState === undefined) {
-      var componentName = getComponentName(workInProgress) || "Component";
-      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
-        didWarnAboutUndefinedDerivedState.add(componentName);
-        warning(
-          false,
-          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
-            "You have returned undefined.",
-          componentName
-        );
-      }
-    }
-  };
+  // Fiber
+  this.return = null;
+  this.child = null;
+  this.sibling = null;
+  this.index = 0;
 
-  // This is so gross but it's at least non-critical and can be removed if
-  // it causes problems. This is meant to give a nicer error message for
-  // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
-  // ...)) which otherwise throws a "_processChildContext is not a function"
-  // exception.
-  Object.defineProperty(fakeInternalInstance, "_processChildContext", {
-    enumerable: false,
-    value: function() {
-      invariant(
-        false,
-        "_processChildContext is not available in React 16+. This likely " +
-          "means you have multiple copies of React and are attempting to nest " +
-          "a React 15 tree inside a React 16 tree using " +
-          "unstable_renderSubtreeIntoContainer, which isn't supported. Try " +
-          "to make sure you have only one copy of React (and ideally, switch " +
-          "to ReactDOM.createPortal)."
-      );
-    }
-  });
-  Object.freeze(fakeInternalInstance);
-}
+  this.ref = null;
 
-function applyDerivedStateFromProps(
-  workInProgress,
-  getDerivedStateFromProps,
-  nextProps
-) {
-  var prevState = workInProgress.memoizedState;
+  this.pendingProps = pendingProps;
+  this.memoizedProps = null;
+  this.updateQueue = null;
+  this.memoizedState = null;
 
-  {
-    if (
-      debugRenderPhaseSideEffects ||
-      (debugRenderPhaseSideEffectsForStrictMode &&
-        workInProgress.mode & StrictMode)
-    ) {
-      // Invoke the function an extra time to help detect side-effects.
-      getDerivedStateFromProps(nextProps, prevState);
-    }
-  }
+  this.mode = mode;
 
-  var partialState = getDerivedStateFromProps(nextProps, prevState);
+  // Effects
+  this.effectTag = NoEffect;
+  this.nextEffect = null;
 
-  {
-    warnOnUndefinedDerivedState(workInProgress, partialState);
+  this.firstEffect = null;
+  this.lastEffect = null;
+
+  this.expirationTime = NoWork;
+
+  this.alternate = null;
+
+  if (enableProfilerTimer) {
+    this.actualDuration = 0;
+    this.actualStartTime = 0;
+    this.selfBaseTime = 0;
+    this.treeBaseTime = 0;
   }
-  // Merge the partial state and the previous state.
-  var memoizedState =
-    partialState === null || partialState === undefined
-      ? prevState
-      : Object.assign({}, prevState, partialState);
-  workInProgress.memoizedState = memoizedState;
 
-  // Once the update queue is empty, persist the derived state onto the
-  // base state.
-  var updateQueue = workInProgress.updateQueue;
-  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
-    updateQueue.baseState = memoizedState;
+  {
+    this._debugID = debugCounter++;
+    this._debugSource = null;
+    this._debugOwner = null;
+    this._debugIsCurrentlyTiming = false;
+    if (!hasBadMapPolyfill && typeof Object.preventExtensions === "function") {
+      Object.preventExtensions(this);
+    }
   }
 }
 
-var ReactFiberClassComponent = function(
-  legacyContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState,
-  recalculateCurrentTime
-) {
-  var cacheContext = legacyContext.cacheContext,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    isContextConsumer = legacyContext.isContextConsumer,
-    hasContextChanged = legacyContext.hasContextChanged;
-
-  var classComponentUpdater = {
-    isMounted: isMounted,
-    enqueueSetState: function(inst, payload, callback) {
-      var fiber = get$1(inst);
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(currentTime, fiber);
-
-      var update = createUpdate(expirationTime);
-      update.payload = payload;
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "setState");
-        }
-        update.callback = callback;
-      }
+// This is a constructor function, rather than a POJO constructor, still
+// please ensure we do the following:
+// 1) Nobody should add any instance methods on this. Instance methods can be
+//    more difficult to predict when they get optimized and they are almost
+//    never inlined properly in static compilers.
+// 2) Nobody should rely on `instanceof Fiber` for type testing. We should
+//    always know when it is a fiber.
+// 3) We might want to experiment with using numeric keys since they are easier
+//    to optimize in a non-JIT environment.
+// 4) We can easily go from a constructor to a createFiber object literal if that
+//    is faster.
+// 5) It should be easy to port this to a C struct and keep a C implementation
+//    compatible.
+var createFiber = function(tag, pendingProps, key, mode) {
+  // $FlowFixMe: the shapes are exact here but Flow doesn't like constructors
+  return new FiberNode(tag, pendingProps, key, mode);
+};
 
-      enqueueUpdate(fiber, update, expirationTime);
-      scheduleWork(fiber, expirationTime);
-    },
-    enqueueReplaceState: function(inst, payload, callback) {
-      var fiber = get$1(inst);
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(currentTime, fiber);
+function shouldConstruct(Component) {
+  return !!(Component.prototype && Component.prototype.isReactComponent);
+}
 
-      var update = createUpdate(expirationTime);
-      update.tag = ReplaceState;
-      update.payload = payload;
+// This is used to create an alternate fiber to do work on.
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  if (workInProgress === null) {
+    // We use a double buffering pooling technique because we know that we'll
+    // only ever need at most two versions of a tree. We pool the "other" unused
+    // node that we're free to reuse. This is lazily created to avoid allocating
+    // extra objects for things that are never updated. It also allow us to
+    // reclaim the extra memory if needed.
+    workInProgress = createFiber(
+      current.tag,
+      pendingProps,
+      current.key,
+      current.mode
+    );
+    workInProgress.type = current.type;
+    workInProgress.stateNode = current.stateNode;
 
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "replaceState");
-        }
-        update.callback = callback;
-      }
+    {
+      // DEV-only fields
+      workInProgress._debugID = current._debugID;
+      workInProgress._debugSource = current._debugSource;
+      workInProgress._debugOwner = current._debugOwner;
+    }
 
-      enqueueUpdate(fiber, update, expirationTime);
-      scheduleWork(fiber, expirationTime);
-    },
-    enqueueForceUpdate: function(inst, callback) {
-      var fiber = get$1(inst);
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(currentTime, fiber);
+    workInProgress.alternate = current;
+    current.alternate = workInProgress;
+  } else {
+    workInProgress.pendingProps = pendingProps;
 
-      var update = createUpdate(expirationTime);
-      update.tag = ForceUpdate;
+    // We already have an alternate.
+    // Reset the effect tag.
+    workInProgress.effectTag = NoEffect;
 
-      if (callback !== undefined && callback !== null) {
-        {
-          warnOnInvalidCallback(callback, "forceUpdate");
-        }
-        update.callback = callback;
-      }
+    // The effect list is no longer valid.
+    workInProgress.nextEffect = null;
+    workInProgress.firstEffect = null;
+    workInProgress.lastEffect = null;
 
-      enqueueUpdate(fiber, update, expirationTime);
-      scheduleWork(fiber, expirationTime);
+    if (enableProfilerTimer) {
+      // We intentionally reset, rather than copy, actualDuration & actualStartTime.
+      // This prevents time from endlessly accumulating in new commits.
+      // This has the downside of resetting values for different priority renders,
+      // But works for yielding (the common case) and should support resuming.
+      workInProgress.actualDuration = 0;
+      workInProgress.actualStartTime = 0;
     }
-  };
-
-  function checkShouldComponentUpdate(
-    workInProgress,
-    oldProps,
-    newProps,
-    oldState,
-    newState,
-    newContext
-  ) {
-    var instance = workInProgress.stateNode;
-    var ctor = workInProgress.type;
-    if (typeof instance.shouldComponentUpdate === "function") {
-      startPhaseTimer(workInProgress, "shouldComponentUpdate");
-      var shouldUpdate = instance.shouldComponentUpdate(
-        newProps,
-        newState,
-        newContext
-      );
-      stopPhaseTimer();
+  }
 
-      {
-        !(shouldUpdate !== undefined)
-          ? warning(
-              false,
-              "%s.shouldComponentUpdate(): Returned undefined instead of a " +
-                "boolean value. Make sure to return true or false.",
-              getComponentName(workInProgress) || "Component"
-            )
-          : void 0;
-      }
+  workInProgress.expirationTime = expirationTime;
 
-      return shouldUpdate;
-    }
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
 
-    if (ctor.prototype && ctor.prototype.isPureReactComponent) {
-      return (
-        !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
-      );
-    }
+  // These will be overridden during the parent's reconciliation
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
 
-    return true;
+  if (enableProfilerTimer) {
+    workInProgress.selfBaseTime = current.selfBaseTime;
+    workInProgress.treeBaseTime = current.treeBaseTime;
   }
 
-  function checkClassInstance(workInProgress) {
-    var instance = workInProgress.stateNode;
-    var type = workInProgress.type;
-    {
-      var name = getComponentName(workInProgress) || "Component";
-      var renderPresent = instance.render;
+  return workInProgress;
+}
 
-      if (!renderPresent) {
-        if (type.prototype && typeof type.prototype.render === "function") {
-          warning(
-            false,
-            "%s(...): No `render` method found on the returned component " +
-              "instance: did you accidentally return an object from the constructor?",
-            name
-          );
-        } else {
-          warning(
-            false,
-            "%s(...): No `render` method found on the returned component " +
-              "instance: you may have forgotten to define `render`.",
-            name
-          );
-        }
-      }
+function createHostRootFiber(isAsync) {
+  var mode = isAsync ? AsyncMode | StrictMode : NoContext;
+  return createFiber(HostRoot, null, null, mode);
+}
 
-      var noGetInitialStateOnES6 =
-        !instance.getInitialState ||
-        instance.getInitialState.isReactClassApproved ||
-        instance.state;
-      !noGetInitialStateOnES6
-        ? warning(
-            false,
-            "getInitialState was defined on %s, a plain JavaScript class. " +
-              "This is only supported for classes created using React.createClass. " +
-              "Did you mean to define a state property instead?",
-            name
-          )
-        : void 0;
-      var noGetDefaultPropsOnES6 =
-        !instance.getDefaultProps ||
-        instance.getDefaultProps.isReactClassApproved;
-      !noGetDefaultPropsOnES6
-        ? warning(
-            false,
-            "getDefaultProps was defined on %s, a plain JavaScript class. " +
-              "This is only supported for classes created using React.createClass. " +
-              "Use a static property to define defaultProps instead.",
-            name
-          )
-        : void 0;
-      var noInstancePropTypes = !instance.propTypes;
-      !noInstancePropTypes
-        ? warning(
-            false,
-            "propTypes was defined as an instance property on %s. Use a static " +
-              "property to define propTypes instead.",
-            name
-          )
-        : void 0;
-      var noInstanceContextTypes = !instance.contextTypes;
-      !noInstanceContextTypes
-        ? warning(
-            false,
-            "contextTypes was defined as an instance property on %s. Use a static " +
-              "property to define contextTypes instead.",
-            name
-          )
-        : void 0;
-      var noComponentShouldUpdate =
-        typeof instance.componentShouldUpdate !== "function";
-      !noComponentShouldUpdate
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
-              "The name is phrased as a question because the function is " +
-              "expected to return a value.",
-            name
-          )
-        : void 0;
-      if (
-        type.prototype &&
-        type.prototype.isPureReactComponent &&
-        typeof instance.shouldComponentUpdate !== "undefined"
-      ) {
-        warning(
-          false,
-          "%s has a method called shouldComponentUpdate(). " +
-            "shouldComponentUpdate should not be used when extending React.PureComponent. " +
-            "Please extend React.Component if shouldComponentUpdate is used.",
-          getComponentName(workInProgress) || "A pure component"
-        );
-      }
-      var noComponentDidUnmount =
-        typeof instance.componentDidUnmount !== "function";
-      !noComponentDidUnmount
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentDidUnmount(). But there is no such lifecycle method. " +
-              "Did you mean componentWillUnmount()?",
-            name
-          )
-        : void 0;
-      var noComponentDidReceiveProps =
-        typeof instance.componentDidReceiveProps !== "function";
-      !noComponentDidReceiveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentDidReceiveProps(). But there is no such lifecycle method. " +
-              "If you meant to update the state in response to changing props, " +
-              "use componentWillReceiveProps(). If you meant to fetch data or " +
-              "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
-            name
-          )
-        : void 0;
-      var noComponentWillRecieveProps =
-        typeof instance.componentWillRecieveProps !== "function";
-      !noComponentWillRecieveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
-            name
-          )
-        : void 0;
-      var noUnsafeComponentWillRecieveProps =
-        typeof instance.UNSAFE_componentWillRecieveProps !== "function";
-      !noUnsafeComponentWillRecieveProps
-        ? warning(
-            false,
-            "%s has a method called " +
-              "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
-            name
-          )
-        : void 0;
-      var hasMutatedProps = instance.props !== workInProgress.pendingProps;
-      !(instance.props === undefined || !hasMutatedProps)
-        ? warning(
-            false,
-            "%s(...): When calling super() in `%s`, make sure to pass " +
-              "up the same props that your component's constructor was passed.",
-            name,
-            name
-          )
-        : void 0;
-      var noInstanceDefaultProps = !instance.defaultProps;
-      !noInstanceDefaultProps
-        ? warning(
-            false,
-            "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
-              " Instead, define defaultProps as a static property on %s.",
-            name,
-            name
-          )
-        : void 0;
-
-      if (
-        typeof instance.getSnapshotBeforeUpdate === "function" &&
-        typeof instance.componentDidUpdate !== "function" &&
-        !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
-      ) {
-        didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
-        warning(
-          false,
-          "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
-            "This component defines getSnapshotBeforeUpdate() only.",
-          getComponentName(workInProgress)
-        );
-      }
-
-      var noInstanceGetDerivedStateFromProps =
-        typeof instance.getDerivedStateFromProps !== "function";
-      !noInstanceGetDerivedStateFromProps
-        ? warning(
-            false,
-            "%s: getDerivedStateFromProps() is defined as an instance method " +
-              "and will be ignored. Instead, declare it as a static method.",
-            name
-          )
-        : void 0;
-      var noInstanceGetDerivedStateFromCatch =
-        typeof instance.getDerivedStateFromCatch !== "function";
-      !noInstanceGetDerivedStateFromCatch
-        ? warning(
-            false,
-            "%s: getDerivedStateFromCatch() is defined as an instance method " +
-              "and will be ignored. Instead, declare it as a static method.",
-            name
-          )
-        : void 0;
-      var noStaticGetSnapshotBeforeUpdate =
-        typeof type.getSnapshotBeforeUpdate !== "function";
-      !noStaticGetSnapshotBeforeUpdate
-        ? warning(
-            false,
-            "%s: getSnapshotBeforeUpdate() is defined as a static method " +
-              "and will be ignored. Instead, declare it as an instance method.",
-            name
-          )
-        : void 0;
-      var _state = instance.state;
-      if (_state && (typeof _state !== "object" || isArray(_state))) {
-        warning(false, "%s.state: must be set to an object or null", name);
-      }
-      if (typeof instance.getChildContext === "function") {
-        !(typeof type.childContextTypes === "object")
-          ? warning(
-              false,
-              "%s.getChildContext(): childContextTypes must be defined in order to " +
-                "use getChildContext().",
-              name
-            )
-          : void 0;
-      }
-    }
+function createFiberFromElement(element, mode, expirationTime) {
+  var owner = null;
+  {
+    owner = element._owner;
   }
 
-  function adoptClassInstance(workInProgress, instance) {
-    instance.updater = classComponentUpdater;
-    workInProgress.stateNode = instance;
-    // The instance needs access to the fiber so that it can schedule updates
-    set(instance, workInProgress);
-    {
-      instance._reactInternalInstance = fakeInternalInstance;
+  var fiber = void 0;
+  var type = element.type;
+  var key = element.key;
+  var pendingProps = element.props;
+
+  var fiberTag = void 0;
+  if (typeof type === "function") {
+    fiberTag = shouldConstruct(type) ? ClassComponent : IndeterminateComponent;
+  } else if (typeof type === "string") {
+    fiberTag = HostComponent;
+  } else {
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          pendingProps.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= AsyncMode | StrictMode;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = Mode;
+        mode |= StrictMode;
+        break;
+      case REACT_PROFILER_TYPE:
+        return createFiberFromProfiler(pendingProps, mode, expirationTime, key);
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = TimeoutComponent;
+        // Suspense does not require async, but its children should be strict
+        // mode compatible.
+        mode |= StrictMode;
+        break;
+      default:
+        fiberTag = getFiberTagFromObjectType(type, owner);
+        break;
     }
   }
 
-  function constructClassInstance(workInProgress, props, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var needsContext = isContextConsumer(workInProgress);
-    var context = needsContext
-      ? getMaskedContext(workInProgress, unmaskedContext)
-      : emptyObject;
+  fiber = createFiber(fiberTag, pendingProps, key, mode);
+  fiber.type = type;
+  fiber.expirationTime = expirationTime;
 
-    // Instantiate twice to help detect side-effects.
-    {
-      if (
-        debugRenderPhaseSideEffects ||
-        (debugRenderPhaseSideEffectsForStrictMode &&
-          workInProgress.mode & StrictMode)
-      ) {
-        new ctor(props, context); // eslint-disable-line no-new
-      }
-    }
+  {
+    fiber._debugSource = element._source;
+    fiber._debugOwner = element._owner;
+  }
 
-    var instance = new ctor(props, context);
-    var state = (workInProgress.memoizedState =
-      instance.state !== null && instance.state !== undefined
-        ? instance.state
-        : null);
-    adoptClassInstance(workInProgress, instance);
+  return fiber;
+}
 
-    {
-      if (
-        typeof ctor.getDerivedStateFromProps === "function" &&
-        state === null
-      ) {
-        var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutUninitializedState.has(componentName)) {
-          didWarnAboutUninitializedState.add(componentName);
-          warning(
-            false,
-            "%s: Did not properly initialize state during construction. " +
-              "Expected state to be an object, but it was %s.",
-            componentName,
-            instance.state === null ? "null" : "undefined"
-          );
-        }
-      }
+function getFiberTagFromObjectType(type, owner) {
+  var $$typeof =
+    typeof type === "object" && type !== null ? type.$$typeof : null;
 
-      // If new component APIs are defined, "unsafe" lifecycles won't be called.
-      // Warn about these lifecycles if they are present.
-      // Don't warn about react-lifecycles-compat polyfilled methods though.
-      if (
-        typeof ctor.getDerivedStateFromProps === "function" ||
-        typeof instance.getSnapshotBeforeUpdate === "function"
-      ) {
-        var foundWillMountName = null;
-        var foundWillReceivePropsName = null;
-        var foundWillUpdateName = null;
-        if (
-          typeof instance.componentWillMount === "function" &&
-          instance.componentWillMount.__suppressDeprecationWarning !== true
-        ) {
-          foundWillMountName = "componentWillMount";
-        } else if (typeof instance.UNSAFE_componentWillMount === "function") {
-          foundWillMountName = "UNSAFE_componentWillMount";
-        }
-        if (
-          typeof instance.componentWillReceiveProps === "function" &&
-          instance.componentWillReceiveProps.__suppressDeprecationWarning !==
-            true
-        ) {
-          foundWillReceivePropsName = "componentWillReceiveProps";
-        } else if (
-          typeof instance.UNSAFE_componentWillReceiveProps === "function"
-        ) {
-          foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
-        }
+  switch ($$typeof) {
+    case REACT_PROVIDER_TYPE:
+      return ContextProvider;
+    case REACT_CONTEXT_TYPE:
+      // This is a consumer
+      return ContextConsumer;
+    case REACT_FORWARD_REF_TYPE:
+      return ForwardRef;
+    default: {
+      var info = "";
+      {
         if (
-          typeof instance.componentWillUpdate === "function" &&
-          instance.componentWillUpdate.__suppressDeprecationWarning !== true
+          type === undefined ||
+          (typeof type === "object" &&
+            type !== null &&
+            Object.keys(type).length === 0)
         ) {
-          foundWillUpdateName = "componentWillUpdate";
-        } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          foundWillUpdateName = "UNSAFE_componentWillUpdate";
+          info +=
+            " You likely forgot to export your component from the file " +
+            "it's defined in, or you might have mixed up default and " +
+            "named imports.";
         }
-        if (
-          foundWillMountName !== null ||
-          foundWillReceivePropsName !== null ||
-          foundWillUpdateName !== null
-        ) {
-          var _componentName = getComponentName(workInProgress) || "Component";
-          var newApiName =
-            typeof ctor.getDerivedStateFromProps === "function"
-              ? "getDerivedStateFromProps()"
-              : "getSnapshotBeforeUpdate()";
-          if (
-            !didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)
-          ) {
-            didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
-            warning(
-              false,
-              "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
-                "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
-                "The above lifecycles should be removed. Learn more about this warning here:\n" +
-                "https://fb.me/react-async-component-lifecycle-hooks",
-              _componentName,
-              newApiName,
-              foundWillMountName !== null ? "\n  " + foundWillMountName : "",
-              foundWillReceivePropsName !== null
-                ? "\n  " + foundWillReceivePropsName
-                : "",
-              foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
-            );
-          }
+        var ownerName = owner ? getComponentName(owner) : null;
+        if (ownerName) {
+          info += "\n\nCheck the render method of `" + ownerName + "`.";
         }
       }
-    }
-
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // ReactFiberContext usually updates this cache but can't for newly-created instances.
-    if (needsContext) {
-      cacheContext(workInProgress, unmaskedContext, context);
-    }
-
-    return instance;
-  }
-
-  function callComponentWillMount(workInProgress, instance) {
-    startPhaseTimer(workInProgress, "componentWillMount");
-    var oldState = instance.state;
-
-    if (typeof instance.componentWillMount === "function") {
-      instance.componentWillMount();
-    }
-    if (typeof instance.UNSAFE_componentWillMount === "function") {
-      instance.UNSAFE_componentWillMount();
-    }
-
-    stopPhaseTimer();
-
-    if (oldState !== instance.state) {
-      {
-        warning(
-          false,
-          "%s.componentWillMount(): Assigning directly to this.state is " +
-            "deprecated (except inside a component's " +
-            "constructor). Use setState instead.",
-          getComponentName(workInProgress) || "Component"
-        );
-      }
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+      invariant(
+        false,
+        "Element type is invalid: expected a string (for built-in " +
+          "components) or a class/function (for composite components) " +
+          "but got: %s.%s",
+        type == null ? type : typeof type,
+        info
+      );
     }
   }
+}
 
-  function callComponentWillReceiveProps(
-    workInProgress,
-    instance,
-    newProps,
-    newContext
-  ) {
-    var oldState = instance.state;
-    startPhaseTimer(workInProgress, "componentWillReceiveProps");
-    if (typeof instance.componentWillReceiveProps === "function") {
-      instance.componentWillReceiveProps(newProps, newContext);
-    }
-    if (typeof instance.UNSAFE_componentWillReceiveProps === "function") {
-      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
-    }
-    stopPhaseTimer();
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  var fiber = createFiber(Fragment, elements, key, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
+}
 
-    if (instance.state !== oldState) {
-      {
-        var componentName = getComponentName(workInProgress) || "Component";
-        if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
-          didWarnAboutStateAssignmentForComponent.add(componentName);
-          warning(
-            false,
-            "%s.componentWillReceiveProps(): Assigning directly to " +
-              "this.state is deprecated (except inside a component's " +
-              "constructor). Use setState instead.",
-            componentName
-          );
-        }
-      }
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+function createFiberFromProfiler(pendingProps, mode, expirationTime, key) {
+  {
+    if (
+      typeof pendingProps.id !== "string" ||
+      typeof pendingProps.onRender !== "function"
+    ) {
+      invariant(
+        false,
+        'Profiler must specify an "id" string and "onRender" function as props'
+      );
     }
   }
 
-  // Invokes the mount life-cycles on a previously never rendered instance.
-  function mountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
+  var fiber = createFiber(Profiler, pendingProps, key, mode | ProfileMode);
+  fiber.type = REACT_PROFILER_TYPE;
+  fiber.expirationTime = expirationTime;
 
-    {
-      checkClassInstance(workInProgress);
-    }
+  return fiber;
+}
 
-    var instance = workInProgress.stateNode;
-    var props = workInProgress.pendingProps;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
+function createFiberFromText(content, mode, expirationTime) {
+  var fiber = createFiber(HostText, content, null, mode);
+  fiber.expirationTime = expirationTime;
+  return fiber;
+}
 
-    instance.props = props;
-    instance.state = workInProgress.memoizedState;
-    instance.refs = emptyObject;
-    instance.context = getMaskedContext(workInProgress, unmaskedContext);
+function createFiberFromHostInstanceForDeletion() {
+  var fiber = createFiber(HostComponent, null, null, NoContext);
+  fiber.type = "DELETED";
+  return fiber;
+}
 
-    {
-      if (workInProgress.mode & StrictMode) {
-        ReactStrictModeWarnings.recordUnsafeLifecycleWarnings(
-          workInProgress,
-          instance
-        );
-      }
-
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.recordDeprecationWarnings(
-          workInProgress,
-          instance
-        );
-      }
-    }
-
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        props,
-        instance,
-        renderExpirationTime
-      );
-      instance.state = workInProgress.memoizedState;
-    }
+function createFiberFromPortal(portal, mode, expirationTime) {
+  var pendingProps = portal.children !== null ? portal.children : [];
+  var fiber = createFiber(HostPortal, pendingProps, portal.key, mode);
+  fiber.expirationTime = expirationTime;
+  fiber.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null, // Used by persistent updates
+    implementation: portal.implementation
+  };
+  return fiber;
+}
 
-    var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
-        workInProgress,
-        getDerivedStateFromProps,
-        props
-      );
-      instance.state = workInProgress.memoizedState;
-    }
+// Used for stashing WIP properties to replay failed work in DEV.
+function assignFiberPropertiesInDEV(target, source) {
+  if (target === null) {
+    // This Fiber's initial properties will always be overwritten.
+    // We only use a Fiber to ensure the same hidden class so DEV isn't slow.
+    target = createFiber(IndeterminateComponent, null, null, NoContext);
+  }
 
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      typeof ctor.getDerivedStateFromProps !== "function" &&
-      typeof instance.getSnapshotBeforeUpdate !== "function" &&
-      (typeof instance.UNSAFE_componentWillMount === "function" ||
-        typeof instance.componentWillMount === "function")
-    ) {
-      callComponentWillMount(workInProgress, instance);
-      // If we had additional state updates during this life-cycle, let's
-      // process them now.
-      updateQueue = workInProgress.updateQueue;
-      if (updateQueue !== null) {
-        processUpdateQueue(
-          workInProgress,
-          updateQueue,
-          props,
-          instance,
-          renderExpirationTime
-        );
-        instance.state = workInProgress.memoizedState;
-      }
-    }
+  // This is intentionally written as a list of all properties.
+  // We tried to use Object.assign() instead but this is called in
+  // the hottest path, and Object.assign() was too slow:
+  // https://github.com/facebook/react/issues/12502
+  // This code is DEV-only so size is not a concern.
 
-    if (typeof instance.componentDidMount === "function") {
-      workInProgress.effectTag |= Update;
-    }
+  target.tag = source.tag;
+  target.key = source.key;
+  target.type = source.type;
+  target.stateNode = source.stateNode;
+  target.return = source.return;
+  target.child = source.child;
+  target.sibling = source.sibling;
+  target.index = source.index;
+  target.ref = source.ref;
+  target.pendingProps = source.pendingProps;
+  target.memoizedProps = source.memoizedProps;
+  target.updateQueue = source.updateQueue;
+  target.memoizedState = source.memoizedState;
+  target.mode = source.mode;
+  target.effectTag = source.effectTag;
+  target.nextEffect = source.nextEffect;
+  target.firstEffect = source.firstEffect;
+  target.lastEffect = source.lastEffect;
+  target.expirationTime = source.expirationTime;
+  target.alternate = source.alternate;
+  if (enableProfilerTimer) {
+    target.actualDuration = source.actualDuration;
+    target.actualStartTime = source.actualStartTime;
+    target.selfBaseTime = source.selfBaseTime;
+    target.treeBaseTime = source.treeBaseTime;
   }
+  target._debugID = source._debugID;
+  target._debugSource = source._debugSource;
+  target._debugOwner = source._debugOwner;
+  target._debugIsCurrentlyTiming = source._debugIsCurrentlyTiming;
+  return target;
+}
 
-  function resumeMountClassInstance(workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-
-    var oldProps = workInProgress.memoizedProps;
-    var newProps = workInProgress.pendingProps;
-    instance.props = oldProps;
+// TODO: This should be lifted into the renderer.
 
-    var oldContext = instance.context;
-    var newUnmaskedContext = getUnmaskedContext(workInProgress);
-    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  // Cyclic construction. This cheats the type system right now because
+  // stateNode is any.
+  var uninitializedFiber = createHostRootFiber(isAsync);
+  var root = {
+    current: uninitializedFiber,
+    containerInfo: containerInfo,
+    pendingChildren: null,
 
-    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
-    var hasNewLifecycles =
-      typeof getDerivedStateFromProps === "function" ||
-      typeof instance.getSnapshotBeforeUpdate === "function";
+    earliestPendingTime: NoWork,
+    latestPendingTime: NoWork,
+    earliestSuspendedTime: NoWork,
+    latestSuspendedTime: NoWork,
+    latestPingedTime: NoWork,
 
-    // Note: During these life-cycles, instance.props/instance.state are what
-    // ever the previously attempted to render - not the "current". However,
-    // during componentDidUpdate we pass the "current" props.
+    didError: false,
 
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      !hasNewLifecycles &&
-      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function")
-    ) {
-      if (oldProps !== newProps || oldContext !== newContext) {
-        callComponentWillReceiveProps(
-          workInProgress,
-          instance,
-          newProps,
-          newContext
-        );
-      }
-    }
+    pendingCommitExpirationTime: NoWork,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    nextExpirationTimeToWorkOn: NoWork,
+    expirationTime: NoWork,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  uninitializedFiber.stateNode = root;
+  return root;
+}
 
-    resetHasForceUpdateBeforeProcessing();
+var onCommitFiberRoot = null;
+var onCommitFiberUnmount = null;
+var hasLoggedError = false;
 
-    var oldState = workInProgress.memoizedState;
-    var newState = (instance.state = oldState);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        newProps,
-        instance,
-        renderExpirationTime
-      );
-      newState = workInProgress.memoizedState;
-    }
-    if (
-      oldProps === newProps &&
-      oldState === newState &&
-      !hasContextChanged() &&
-      !checkHasForceUpdateAfterProcessing()
-    ) {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {
+      if (true && !hasLoggedError) {
+        hasLoggedError = true;
+        warning(false, "React DevTools encountered an error: %s", err);
       }
-      return false;
     }
+  };
+}
 
-    if (typeof getDerivedStateFromProps === "function") {
-      applyDerivedStateFromProps(
-        workInProgress,
-        getDerivedStateFromProps,
-        newProps
+function injectInternals(internals) {
+  if (typeof __REACT_DEVTOOLS_GLOBAL_HOOK__ === "undefined") {
+    // No DevTools
+    return false;
+  }
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled) {
+    // This isn't a real property on the hook, but it can be set to opt out
+    // of DevTools integration and associated warnings and logs.
+    // https://github.com/facebook/react/issues/3877
+    return true;
+  }
+  if (!hook.supportsFiber) {
+    {
+      warning(
+        false,
+        "The installed version of React DevTools is too old and will not work " +
+          "with the current version of React. Please update React DevTools. " +
+          "https://fb.me/react-devtools"
       );
-      newState = workInProgress.memoizedState;
     }
-
-    var shouldUpdate =
-      checkHasForceUpdateAfterProcessing() ||
-      checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldState,
-        newState,
-        newContext
-      );
-
-    if (shouldUpdate) {
-      // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for components using the new APIs.
-      if (
-        !hasNewLifecycles &&
-        (typeof instance.UNSAFE_componentWillMount === "function" ||
-          typeof instance.componentWillMount === "function")
-      ) {
-        startPhaseTimer(workInProgress, "componentWillMount");
-        if (typeof instance.componentWillMount === "function") {
-          instance.componentWillMount();
-        }
-        if (typeof instance.UNSAFE_componentWillMount === "function") {
-          instance.UNSAFE_componentWillMount();
-        }
-        stopPhaseTimer();
-      }
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-    } else {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidMount === "function") {
-        workInProgress.effectTag |= Update;
-      }
-
-      // If shouldComponentUpdate returned false, we should still update the
-      // memoized state to indicate that this work can be reused.
-      workInProgress.memoizedProps = newProps;
-      workInProgress.memoizedState = newState;
+    // DevTools exists, even though it doesn't support Fiber.
+    return true;
+  }
+  try {
+    var rendererID = hook.inject(internals);
+    // We have successfully injected, so now it is safe to set up hooks.
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {
+    // Catch all errors because it is unsafe to throw during initialization.
+    {
+      warning(false, "React DevTools encountered an error: %s.", err);
     }
-
-    // Update the existing instance's state, props, and context pointers even
-    // if shouldComponentUpdate returns false.
-    instance.props = newProps;
-    instance.state = newState;
-    instance.context = newContext;
-
-    return shouldUpdate;
   }
+  // DevTools exists
+  return true;
+}
 
-  // Invokes the update life-cycles and returns false if it shouldn't rerender.
-  function updateClassInstance(current, workInProgress, renderExpirationTime) {
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-
-    var oldProps = workInProgress.memoizedProps;
-    var newProps = workInProgress.pendingProps;
-    instance.props = oldProps;
+function onCommitRoot(root) {
+  if (typeof onCommitFiberRoot === "function") {
+    onCommitFiberRoot(root);
+  }
+}
 
-    var oldContext = instance.context;
-    var newUnmaskedContext = getUnmaskedContext(workInProgress);
-    var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+function onCommitUnmount(fiber) {
+  if (typeof onCommitFiberUnmount === "function") {
+    onCommitFiberUnmount(fiber);
+  }
+}
 
-    var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
-    var hasNewLifecycles =
-      typeof getDerivedStateFromProps === "function" ||
-      typeof instance.getSnapshotBeforeUpdate === "function";
+/**
+ * Forked from fbjs/warning:
+ * https://github.com/facebook/fbjs/blob/e66ba20ad5be433eb54423f2b097d829324d9de6/packages/fbjs/src/__forks__/warning.js
+ *
+ * Only change is we use console.warn instead of console.error,
+ * and do nothing when 'console' is not supported.
+ * This really simplifies the code.
+ * ---
+ * Similar to invariant but only logs a warning if the condition is not met.
+ * This can be used to log issues in development environments in critical
+ * paths. Removing the logging code for production environments will keep the
+ * same logic and follow the same code paths.
+ */
 
-    // Note: During these life-cycles, instance.props/instance.state are what
-    // ever the previously attempted to render - not the "current". However,
-    // during componentDidUpdate we pass the "current" props.
+var lowPriorityWarning = function() {};
 
-    // In order to support react-lifecycles-compat polyfilled components,
-    // Unsafe lifecycles should not be invoked for components using the new APIs.
-    if (
-      !hasNewLifecycles &&
-      (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
-        typeof instance.componentWillReceiveProps === "function")
-    ) {
-      if (oldProps !== newProps || oldContext !== newContext) {
-        callComponentWillReceiveProps(
-          workInProgress,
-          instance,
-          newProps,
-          newContext
-        );
-      }
+{
+  var printWarning = function(format) {
+    for (
+      var _len = arguments.length,
+        args = Array(_len > 1 ? _len - 1 : 0),
+        _key = 1;
+      _key < _len;
+      _key++
+    ) {
+      args[_key - 1] = arguments[_key];
     }
 
-    resetHasForceUpdateBeforeProcessing();
+    var argIndex = 0;
+    var message =
+      "Warning: " +
+      format.replace(/%s/g, function() {
+        return args[argIndex++];
+      });
+    if (typeof console !== "undefined") {
+      console.warn(message);
+    }
+    try {
+      // --- Welcome to debugging React ---
+      // This error was thrown as a convenience so that you can use this stack
+      // to find the callsite that caused this warning to fire.
+      throw new Error(message);
+    } catch (x) {}
+  };
 
-    var oldState = workInProgress.memoizedState;
-    var newState = (instance.state = oldState);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        newProps,
-        instance,
-        renderExpirationTime
+  lowPriorityWarning = function(condition, format) {
+    if (format === undefined) {
+      throw new Error(
+        "`warning(condition, format, ...args)` requires a warning " +
+          "message argument"
       );
-      newState = workInProgress.memoizedState;
     }
-
-    if (
-      oldProps === newProps &&
-      oldState === newState &&
-      !hasContextChanged() &&
-      !checkHasForceUpdateAfterProcessing()
-    ) {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Update;
-        }
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Snapshot;
-        }
+    if (!condition) {
+      for (
+        var _len2 = arguments.length,
+          args = Array(_len2 > 2 ? _len2 - 2 : 0),
+          _key2 = 2;
+        _key2 < _len2;
+        _key2++
+      ) {
+        args[_key2 - 2] = arguments[_key2];
       }
-      return false;
-    }
 
-    if (typeof getDerivedStateFromProps === "function") {
-      if (fireGetDerivedStateFromPropsOnStateUpdates || oldProps !== newProps) {
-        applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        );
-        newState = workInProgress.memoizedState;
-      }
+      printWarning.apply(undefined, [format].concat(args));
     }
+  };
+}
 
-    var shouldUpdate =
-      checkHasForceUpdateAfterProcessing() ||
-      checkShouldComponentUpdate(
-        workInProgress,
-        oldProps,
-        newProps,
-        oldState,
-        newState,
-        newContext
-      );
+var lowPriorityWarning$1 = lowPriorityWarning;
 
-    if (shouldUpdate) {
-      // In order to support react-lifecycles-compat polyfilled components,
-      // Unsafe lifecycles should not be invoked for components using the new APIs.
-      if (
-        !hasNewLifecycles &&
-        (typeof instance.UNSAFE_componentWillUpdate === "function" ||
-          typeof instance.componentWillUpdate === "function")
-      ) {
-        startPhaseTimer(workInProgress, "componentWillUpdate");
-        if (typeof instance.componentWillUpdate === "function") {
-          instance.componentWillUpdate(newProps, newState, newContext);
-        }
-        if (typeof instance.UNSAFE_componentWillUpdate === "function") {
-          instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
-        }
-        stopPhaseTimer();
-      }
-      if (typeof instance.componentDidUpdate === "function") {
-        workInProgress.effectTag |= Update;
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        workInProgress.effectTag |= Snapshot;
-      }
-    } else {
-      // If an update was already in progress, we should schedule an Update
-      // effect even though we're bailing out, so that cWU/cDU are called.
-      if (typeof instance.componentDidUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Update;
-        }
-      }
-      if (typeof instance.getSnapshotBeforeUpdate === "function") {
-        if (
-          oldProps !== current.memoizedProps ||
-          oldState !== current.memoizedState
-        ) {
-          workInProgress.effectTag |= Snapshot;
-        }
-      }
+var ReactStrictModeWarnings = {
+  discardPendingWarnings: function() {},
+  flushPendingDeprecationWarnings: function() {},
+  flushPendingUnsafeLifecycleWarnings: function() {},
+  recordDeprecationWarnings: function(fiber, instance) {},
+  recordUnsafeLifecycleWarnings: function(fiber, instance) {},
+  recordLegacyContextWarning: function(fiber, instance) {},
+  flushLegacyContextWarning: function() {}
+};
 
-      // If shouldComponentUpdate returned false, we should still update the
-      // memoized props/state to indicate that this work can be reused.
-      workInProgress.memoizedProps = newProps;
-      workInProgress.memoizedState = newState;
-    }
+{
+  var LIFECYCLE_SUGGESTIONS = {
+    UNSAFE_componentWillMount: "componentDidMount",
+    UNSAFE_componentWillReceiveProps: "static getDerivedStateFromProps",
+    UNSAFE_componentWillUpdate: "componentDidUpdate"
+  };
 
-    // Update the existing instance's state, props, and context pointers even
-    // if shouldComponentUpdate returns false.
-    instance.props = newProps;
-    instance.state = newState;
-    instance.context = newContext;
+  var pendingComponentWillMountWarnings = [];
+  var pendingComponentWillReceivePropsWarnings = [];
+  var pendingComponentWillUpdateWarnings = [];
+  var pendingUnsafeLifecycleWarnings = new Map();
+  var pendingLegacyContextWarning = new Map();
 
-    return shouldUpdate;
-  }
+  // Tracks components we have already warned about.
+  var didWarnAboutDeprecatedLifecycles = new Set();
+  var didWarnAboutUnsafeLifecycles = new Set();
+  var didWarnAboutLegacyContext = new Set();
 
-  return {
-    adoptClassInstance: adoptClassInstance,
-    constructClassInstance: constructClassInstance,
-    mountClassInstance: mountClassInstance,
-    resumeMountClassInstance: resumeMountClassInstance,
-    updateClassInstance: updateClassInstance
+  var setToSortedString = function(set) {
+    var array = [];
+    set.forEach(function(value) {
+      array.push(value);
+    });
+    return array.sort().join(", ");
   };
-};
 
-var getCurrentFiberStackAddendum$2 =
-  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+  ReactStrictModeWarnings.discardPendingWarnings = function() {
+    pendingComponentWillMountWarnings = [];
+    pendingComponentWillReceivePropsWarnings = [];
+    pendingComponentWillUpdateWarnings = [];
+    pendingUnsafeLifecycleWarnings = new Map();
+    pendingLegacyContextWarning = new Map();
+  };
 
-var didWarnAboutMaps = void 0;
-var didWarnAboutStringRefInStrictMode = void 0;
-var ownerHasKeyUseWarning = void 0;
-var ownerHasFunctionTypeWarning = void 0;
-var warnForMissingKey = function(child) {};
+  ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings = function() {
+    pendingUnsafeLifecycleWarnings.forEach(function(
+      lifecycleWarningsMap,
+      strictRoot
+    ) {
+      var lifecyclesWarningMesages = [];
 
-{
-  didWarnAboutMaps = false;
-  didWarnAboutStringRefInStrictMode = {};
+      Object.keys(lifecycleWarningsMap).forEach(function(lifecycle) {
+        var lifecycleWarnings = lifecycleWarningsMap[lifecycle];
+        if (lifecycleWarnings.length > 0) {
+          var componentNames = new Set();
+          lifecycleWarnings.forEach(function(fiber) {
+            componentNames.add(getComponentName(fiber) || "Component");
+            didWarnAboutUnsafeLifecycles.add(fiber.type);
+          });
 
-  /**
-   * Warn if there's no key explicitly set on dynamic arrays of children or
-   * object keys are not valid. This allows us to keep track of children between
-   * updates.
-   */
-  ownerHasKeyUseWarning = {};
-  ownerHasFunctionTypeWarning = {};
+          var formatted = lifecycle.replace("UNSAFE_", "");
+          var suggestion = LIFECYCLE_SUGGESTIONS[lifecycle];
+          var sortedComponentNames = setToSortedString(componentNames);
 
-  warnForMissingKey = function(child) {
-    if (child === null || typeof child !== "object") {
-      return;
-    }
-    if (!child._store || child._store.validated || child.key != null) {
-      return;
-    }
-    invariant(
-      typeof child._store === "object",
-      "React Component in warnForMissingKey should have a _store. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
-    child._store.validated = true;
+          lifecyclesWarningMesages.push(
+            formatted +
+              ": Please update the following components to use " +
+              (suggestion + " instead: " + sortedComponentNames)
+          );
+        }
+      });
 
-    var currentComponentErrorInfo =
-      "Each child in an array or iterator should have a unique " +
-      '"key" prop. See https://fb.me/react-warning-keys for ' +
-      "more information." +
-      (getCurrentFiberStackAddendum$2() || "");
-    if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
-      return;
-    }
-    ownerHasKeyUseWarning[currentComponentErrorInfo] = true;
+      if (lifecyclesWarningMesages.length > 0) {
+        var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+          strictRoot
+        );
 
-    warning(
-      false,
-      "Each child in an array or iterator should have a unique " +
-        '"key" prop. See https://fb.me/react-warning-keys for ' +
-        "more information.%s",
-      getCurrentFiberStackAddendum$2()
-    );
+        warning(
+          false,
+          "Unsafe lifecycle methods were found within a strict-mode tree:%s" +
+            "\n\n%s" +
+            "\n\nLearn more about this warning here:" +
+            "\nhttps://fb.me/react-strict-mode-warnings",
+          strictRootComponentStack,
+          lifecyclesWarningMesages.join("\n\n")
+        );
+      }
+    });
+
+    pendingUnsafeLifecycleWarnings = new Map();
   };
-}
 
-var isArray$1 = Array.isArray;
+  var findStrictRoot = function(fiber) {
+    var maybeStrictRoot = null;
 
-function coerceRef(returnFiber, current, element) {
-  var mixedRef = element.ref;
-  if (
-    mixedRef !== null &&
-    typeof mixedRef !== "function" &&
-    typeof mixedRef !== "object"
-  ) {
-    {
-      if (returnFiber.mode & StrictMode) {
-        var componentName = getComponentName(returnFiber) || "Component";
-        if (!didWarnAboutStringRefInStrictMode[componentName]) {
-          warning(
-            false,
-            'A string ref, "%s", has been found within a strict mode tree. ' +
-              "String refs are a source of potential bugs and should be avoided. " +
-              "We recommend using createRef() instead." +
-              "\n%s" +
-              "\n\nLearn more about using refs safely here:" +
-              "\nhttps://fb.me/react-strict-mode-string-ref",
-            mixedRef,
-            getStackAddendumByWorkInProgressFiber(returnFiber)
-          );
-          didWarnAboutStringRefInStrictMode[componentName] = true;
-        }
+    var node = fiber;
+    while (node !== null) {
+      if (node.mode & StrictMode) {
+        maybeStrictRoot = node;
       }
+      node = node.return;
     }
 
-    if (element._owner) {
-      var owner = element._owner;
-      var inst = void 0;
-      if (owner) {
-        var ownerFiber = owner;
-        invariant(
-          ownerFiber.tag === ClassComponent,
-          "Stateless function components cannot have refs."
-        );
-        inst = ownerFiber.stateNode;
-      }
-      invariant(
-        inst,
-        "Missing owner for string ref %s. This error is likely caused by a " +
-          "bug in React. Please file an issue.",
-        mixedRef
-      );
-      var stringRef = "" + mixedRef;
-      // Check if previous string ref matches new string ref
-      if (
-        current !== null &&
-        current.ref !== null &&
-        current.ref._stringRef === stringRef
-      ) {
-        return current.ref;
-      }
-      var ref = function(value) {
-        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
-        if (value === null) {
-          delete refs[stringRef];
-        } else {
-          refs[stringRef] = value;
-        }
-      };
-      ref._stringRef = stringRef;
-      return ref;
-    } else {
-      invariant(
-        typeof mixedRef === "string",
-        "Expected ref to be a function or a string."
-      );
-      invariant(
-        element._owner,
-        "Element ref was specified as a string (%s) but no owner was set. This could happen for one of" +
-          " the following reasons:\n" +
-          "1. You may be adding a ref to a functional component\n" +
-          "2. You may be adding a ref to a component that was not created inside a component's render method\n" +
-          "3. You have multiple copies of React loaded\n" +
-          "See https://fb.me/react-refs-must-have-owner for more information.",
-        mixedRef
+    return maybeStrictRoot;
+  };
+
+  ReactStrictModeWarnings.flushPendingDeprecationWarnings = function() {
+    if (pendingComponentWillMountWarnings.length > 0) {
+      var uniqueNames = new Set();
+      pendingComponentWillMountWarnings.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var sortedNames = setToSortedString(uniqueNames);
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillMount is deprecated and will be removed in the next major version. " +
+          "Use componentDidMount instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillMount." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        sortedNames
       );
+
+      pendingComponentWillMountWarnings = [];
     }
-  }
-  return mixedRef;
-}
 
-function throwOnInvalidObjectType(returnFiber, newChild) {
-  if (returnFiber.type !== "textarea") {
-    var addendum = "";
-    {
-      addendum =
-        " If you meant to render a collection of children, use an array " +
-        "instead." +
-        (getCurrentFiberStackAddendum$2() || "");
+    if (pendingComponentWillReceivePropsWarnings.length > 0) {
+      var _uniqueNames = new Set();
+      pendingComponentWillReceivePropsWarnings.forEach(function(fiber) {
+        _uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
+
+      var _sortedNames = setToSortedString(_uniqueNames);
+
+      lowPriorityWarning$1(
+        false,
+        "componentWillReceiveProps is deprecated and will be removed in the next major version. " +
+          "Use static getDerivedStateFromProps instead." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames
+      );
+
+      pendingComponentWillReceivePropsWarnings = [];
     }
-    invariant(
-      false,
-      "Objects are not valid as a React child (found: %s).%s",
-      Object.prototype.toString.call(newChild) === "[object Object]"
-        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
-        : newChild,
-      addendum
-    );
-  }
-}
 
-function warnOnFunctionType() {
-  var currentComponentErrorInfo =
-    "Functions are not valid as a React child. This may happen if " +
-    "you return a Component instead of <Component /> from render. " +
-    "Or maybe you meant to call this function rather than return it." +
-    (getCurrentFiberStackAddendum$2() || "");
+    if (pendingComponentWillUpdateWarnings.length > 0) {
+      var _uniqueNames2 = new Set();
+      pendingComponentWillUpdateWarnings.forEach(function(fiber) {
+        _uniqueNames2.add(getComponentName(fiber) || "Component");
+        didWarnAboutDeprecatedLifecycles.add(fiber.type);
+      });
 
-  if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
-    return;
-  }
-  ownerHasFunctionTypeWarning[currentComponentErrorInfo] = true;
+      var _sortedNames2 = setToSortedString(_uniqueNames2);
 
-  warning(
-    false,
-    "Functions are not valid as a React child. This may happen if " +
-      "you return a Component instead of <Component /> from render. " +
-      "Or maybe you meant to call this function rather than return it.%s",
-    getCurrentFiberStackAddendum$2() || ""
-  );
-}
+      lowPriorityWarning$1(
+        false,
+        "componentWillUpdate is deprecated and will be removed in the next major version. " +
+          "Use componentDidUpdate instead. As a temporary workaround, " +
+          "you can rename to UNSAFE_componentWillUpdate." +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-async-component-lifecycle-hooks",
+        _sortedNames2
+      );
 
-// This wrapper function exists because I expect to clone the code in each path
-// to be able to optimize each path individually by branching early. This needs
-// a compiler or we can do it manually. Helpers that don't need this branching
-// live outside of this function.
-function ChildReconciler(shouldTrackSideEffects) {
-  function deleteChild(returnFiber, childToDelete) {
-    if (!shouldTrackSideEffects) {
-      // Noop.
+      pendingComponentWillUpdateWarnings = [];
+    }
+  };
+
+  ReactStrictModeWarnings.recordDeprecationWarnings = function(
+    fiber,
+    instance
+  ) {
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutDeprecatedLifecycles.has(fiber.type)) {
       return;
     }
-    // Deletions are added in reversed order so we add it to the front.
-    // At this point, the return fiber's effect list is empty except for
-    // deletions, so we can just append the deletion to the list. The remaining
-    // effects aren't added until the complete phase. Once we implement
-    // resuming, this may not be true.
-    var last = returnFiber.lastEffect;
-    if (last !== null) {
-      last.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
-    } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+
+    // Don't warn about react-lifecycles-compat polyfilled components.
+    if (
+      typeof instance.componentWillMount === "function" &&
+      instance.componentWillMount.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillMountWarnings.push(fiber);
     }
-    childToDelete.nextEffect = null;
-    childToDelete.effectTag = Deletion;
-  }
+    if (
+      typeof instance.componentWillReceiveProps === "function" &&
+      instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillReceivePropsWarnings.push(fiber);
+    }
+    if (
+      typeof instance.componentWillUpdate === "function" &&
+      instance.componentWillUpdate.__suppressDeprecationWarning !== true
+    ) {
+      pendingComponentWillUpdateWarnings.push(fiber);
+    }
+  };
 
-  function deleteRemainingChildren(returnFiber, currentFirstChild) {
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return null;
+  ReactStrictModeWarnings.recordUnsafeLifecycleWarnings = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = findStrictRoot(fiber);
+    if (strictRoot === null) {
+      warning(
+        false,
+        "Expected to find a StrictMode component in a strict mode tree. " +
+          "This error is likely caused by a bug in React. Please file an issue."
+      );
+      return;
     }
 
-    // TODO: For the shouldClone case, this could be micro-optimized a bit by
-    // assuming that after the first child we've already added everything.
-    var childToDelete = currentFirstChild;
-    while (childToDelete !== null) {
-      deleteChild(returnFiber, childToDelete);
-      childToDelete = childToDelete.sibling;
+    // Dedup strategy: Warn once per component.
+    // This is difficult to track any other way since component names
+    // are often vague and are likely to collide between 3rd party libraries.
+    // An expand property is probably okay to use here since it's DEV-only,
+    // and will only be set in the event of serious warnings.
+    if (didWarnAboutUnsafeLifecycles.has(fiber.type)) {
+      return;
     }
-    return null;
-  }
 
-  function mapRemainingChildren(returnFiber, currentFirstChild) {
-    // Add the remaining children to a temporary map so that we can find them by
-    // keys quickly. Implicit (null) keys get added to this set with their index
-    var existingChildren = new Map();
+    var warningsForRoot = void 0;
+    if (!pendingUnsafeLifecycleWarnings.has(strictRoot)) {
+      warningsForRoot = {
+        UNSAFE_componentWillMount: [],
+        UNSAFE_componentWillReceiveProps: [],
+        UNSAFE_componentWillUpdate: []
+      };
 
-    var existingChild = currentFirstChild;
-    while (existingChild !== null) {
-      if (existingChild.key !== null) {
-        existingChildren.set(existingChild.key, existingChild);
-      } else {
-        existingChildren.set(existingChild.index, existingChild);
-      }
-      existingChild = existingChild.sibling;
+      pendingUnsafeLifecycleWarnings.set(strictRoot, warningsForRoot);
+    } else {
+      warningsForRoot = pendingUnsafeLifecycleWarnings.get(strictRoot);
     }
-    return existingChildren;
-  }
 
-  function useFiber(fiber, pendingProps, expirationTime) {
-    // We currently set sibling to null and index to 0 here because it is easy
-    // to forget to do before returning it. E.g. for the single child case.
-    var clone = createWorkInProgress(fiber, pendingProps, expirationTime);
-    clone.index = 0;
-    clone.sibling = null;
-    return clone;
-  }
-
-  function placeChild(newFiber, lastPlacedIndex, newIndex) {
-    newFiber.index = newIndex;
-    if (!shouldTrackSideEffects) {
-      // Noop.
-      return lastPlacedIndex;
+    var unsafeLifecycles = [];
+    if (
+      (typeof instance.componentWillMount === "function" &&
+        instance.componentWillMount.__suppressDeprecationWarning !== true) ||
+      typeof instance.UNSAFE_componentWillMount === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillMount");
     }
-    var current = newFiber.alternate;
-    if (current !== null) {
-      var oldIndex = current.index;
-      if (oldIndex < lastPlacedIndex) {
-        // This is a move.
-        newFiber.effectTag = Placement;
-        return lastPlacedIndex;
-      } else {
-        // This item can stay in place.
-        return oldIndex;
-      }
-    } else {
-      // This is an insertion.
-      newFiber.effectTag = Placement;
-      return lastPlacedIndex;
+    if (
+      (typeof instance.componentWillReceiveProps === "function" &&
+        instance.componentWillReceiveProps.__suppressDeprecationWarning !==
+          true) ||
+      typeof instance.UNSAFE_componentWillReceiveProps === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillReceiveProps");
+    }
+    if (
+      (typeof instance.componentWillUpdate === "function" &&
+        instance.componentWillUpdate.__suppressDeprecationWarning !== true) ||
+      typeof instance.UNSAFE_componentWillUpdate === "function"
+    ) {
+      unsafeLifecycles.push("UNSAFE_componentWillUpdate");
     }
-  }
 
-  function placeSingleChild(newFiber) {
-    // This is simpler for the single child case. We only need to do a
-    // placement for inserting new children.
-    if (shouldTrackSideEffects && newFiber.alternate === null) {
-      newFiber.effectTag = Placement;
+    if (unsafeLifecycles.length > 0) {
+      unsafeLifecycles.forEach(function(lifecycle) {
+        warningsForRoot[lifecycle].push(fiber);
+      });
     }
-    return newFiber;
-  }
+  };
 
-  function updateTextNode(returnFiber, current, textContent, expirationTime) {
-    if (current === null || current.tag !== HostText) {
-      // Insert
-      var created = createFiberFromText(
-        textContent,
-        returnFiber.mode,
-        expirationTime
+  ReactStrictModeWarnings.recordLegacyContextWarning = function(
+    fiber,
+    instance
+  ) {
+    var strictRoot = findStrictRoot(fiber);
+    if (strictRoot === null) {
+      warning(
+        false,
+        "Expected to find a StrictMode component in a strict mode tree. " +
+          "This error is likely caused by a bug in React. Please file an issue."
       );
-      created.return = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, textContent, expirationTime);
-      existing.return = returnFiber;
-      return existing;
+      return;
     }
-  }
 
-  function updateElement(returnFiber, current, element, expirationTime) {
-    if (current !== null && current.type === element.type) {
-      // Move based on index
-      var existing = useFiber(current, element.props, expirationTime);
-      existing.ref = coerceRef(returnFiber, current, element);
-      existing.return = returnFiber;
-      {
-        existing._debugSource = element._source;
-        existing._debugOwner = element._owner;
-      }
-      return existing;
-    } else {
-      // Insert
-      var created = createFiberFromElement(
-        element,
-        returnFiber.mode,
-        expirationTime
-      );
-      created.ref = coerceRef(returnFiber, current, element);
-      created.return = returnFiber;
-      return created;
+    // Dedup strategy: Warn once per component.
+    if (didWarnAboutLegacyContext.has(fiber.type)) {
+      return;
     }
-  }
 
-  function updatePortal(returnFiber, current, portal, expirationTime) {
+    var warningsForRoot = pendingLegacyContextWarning.get(strictRoot);
+
     if (
-      current === null ||
-      current.tag !== HostPortal ||
-      current.stateNode.containerInfo !== portal.containerInfo ||
-      current.stateNode.implementation !== portal.implementation
+      fiber.type.contextTypes != null ||
+      fiber.type.childContextTypes != null ||
+      (instance !== null && typeof instance.getChildContext === "function")
     ) {
-      // Insert
-      var created = createFiberFromPortal(
-        portal,
-        returnFiber.mode,
-        expirationTime
-      );
-      created.return = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, portal.children || [], expirationTime);
-      existing.return = returnFiber;
-      return existing;
+      if (warningsForRoot === undefined) {
+        warningsForRoot = [];
+        pendingLegacyContextWarning.set(strictRoot, warningsForRoot);
+      }
+      warningsForRoot.push(fiber);
     }
-  }
+  };
 
-  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
-    if (current === null || current.tag !== Fragment) {
-      // Insert
-      var created = createFiberFromFragment(
-        fragment,
-        returnFiber.mode,
-        expirationTime,
-        key
+  ReactStrictModeWarnings.flushLegacyContextWarning = function() {
+    pendingLegacyContextWarning.forEach(function(fiberArray, strictRoot) {
+      var uniqueNames = new Set();
+      fiberArray.forEach(function(fiber) {
+        uniqueNames.add(getComponentName(fiber) || "Component");
+        didWarnAboutLegacyContext.add(fiber.type);
+      });
+
+      var sortedNames = setToSortedString(uniqueNames);
+      var strictRootComponentStack = getStackAddendumByWorkInProgressFiber(
+        strictRoot
       );
-      created.return = returnFiber;
-      return created;
-    } else {
-      // Update
-      var existing = useFiber(current, fragment, expirationTime);
-      existing.return = returnFiber;
-      return existing;
-    }
-  }
 
-  function createChild(returnFiber, newChild, expirationTime) {
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys. If the previous node is implicitly keyed
-      // we can continue to replace it without aborting even if it is not a text
-      // node.
-      var created = createFiberFromText(
-        "" + newChild,
-        returnFiber.mode,
-        expirationTime
+      warning(
+        false,
+        "Legacy context API has been detected within a strict-mode tree: %s" +
+          "\n\nPlease update the following components: %s" +
+          "\n\nLearn more about this warning here:" +
+          "\nhttps://fb.me/react-strict-mode-warnings",
+        strictRootComponentStack,
+        sortedNames
       );
-      created.return = returnFiber;
-      return created;
-    }
+    });
+  };
+}
 
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          var _created = createFiberFromElement(
-            newChild,
-            returnFiber.mode,
-            expirationTime
-          );
-          _created.ref = coerceRef(returnFiber, null, newChild);
-          _created.return = returnFiber;
-          return _created;
-        }
-        case REACT_PORTAL_TYPE: {
-          var _created2 = createFiberFromPortal(
-            newChild,
-            returnFiber.mode,
-            expirationTime
-          );
-          _created2.return = returnFiber;
-          return _created2;
-        }
-      }
+// This lets us hook into Fiber to debug what it's doing.
+// See https://github.com/facebook/react/pull/8033.
+// This is not part of the public API, not even for React DevTools.
+// You may only inject a debugTool if you work on React Fiber itself.
+var ReactFiberInstrumentation = {
+  debugTool: null
+};
 
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        var _created3 = createFiberFromFragment(
-          newChild,
-          returnFiber.mode,
-          expirationTime,
-          null
-        );
-        _created3.return = returnFiber;
-        return _created3;
-      }
+var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
 
-      throwOnInvalidObjectType(returnFiber, newChild);
+// TODO: Offscreen updates
+
+function markPendingPriorityLevel(root, expirationTime) {
+  // If there's a gap between completing a failed root and retrying it,
+  // additional updates may be scheduled. Clear `didError`, in case the update
+  // is sufficient to fix the error.
+  root.didError = false;
+
+  // Update the latest and earliest pending times
+  var earliestPendingTime = root.earliestPendingTime;
+  if (earliestPendingTime === NoWork) {
+    // No other pending updates.
+    root.earliestPendingTime = root.latestPendingTime = expirationTime;
+  } else {
+    if (earliestPendingTime > expirationTime) {
+      // This is the earliest pending update.
+      root.earliestPendingTime = expirationTime;
+    } else {
+      var latestPendingTime = root.latestPendingTime;
+      if (latestPendingTime < expirationTime) {
+        // This is the latest pending update
+        root.latestPendingTime = expirationTime;
+      }
     }
+  }
+  findNextPendingPriorityLevel(root);
+}
 
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
+function markCommittedPriorityLevels(root, currentTime, earliestRemainingTime) {
+  root.didError = false;
+
+  if (earliestRemainingTime === NoWork) {
+    // Fast path. There's no remaining work. Clear everything.
+    root.earliestPendingTime = NoWork;
+    root.latestPendingTime = NoWork;
+    root.earliestSuspendedTime = NoWork;
+    root.latestSuspendedTime = NoWork;
+    root.latestPingedTime = NoWork;
+    findNextPendingPriorityLevel(root);
+    return;
+  }
+
+  // Let's see if the previous latest known pending level was just flushed.
+  var latestPendingTime = root.latestPendingTime;
+  if (latestPendingTime !== NoWork) {
+    if (latestPendingTime < earliestRemainingTime) {
+      // We've flushed all the known pending levels.
+      root.earliestPendingTime = root.latestPendingTime = NoWork;
+    } else {
+      var earliestPendingTime = root.earliestPendingTime;
+      if (earliestPendingTime < earliestRemainingTime) {
+        // We've flushed the earliest known pending level. Set this to the
+        // latest pending time.
+        root.earliestPendingTime = root.latestPendingTime;
       }
     }
+  }
 
-    return null;
+  // Now let's handle the earliest remaining level in the whole tree. We need to
+  // decide whether to treat it as a pending level or as suspended. Check
+  // it falls within the range of known suspended levels.
+
+  var earliestSuspendedTime = root.earliestSuspendedTime;
+  if (earliestSuspendedTime === NoWork) {
+    // There's no suspended work. Treat the earliest remaining level as a
+    // pending level.
+    markPendingPriorityLevel(root, earliestRemainingTime);
+    findNextPendingPriorityLevel(root);
+    return;
   }
 
-  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
-    // Update the fiber if the keys match, otherwise return null.
+  var latestSuspendedTime = root.latestSuspendedTime;
+  if (earliestRemainingTime > latestSuspendedTime) {
+    // The earliest remaining level is later than all the suspended work. That
+    // means we've flushed all the suspended work.
+    root.earliestSuspendedTime = NoWork;
+    root.latestSuspendedTime = NoWork;
+    root.latestPingedTime = NoWork;
 
-    var key = oldFiber !== null ? oldFiber.key : null;
+    // There's no suspended work. Treat the earliest remaining level as a
+    // pending level.
+    markPendingPriorityLevel(root, earliestRemainingTime);
+    findNextPendingPriorityLevel(root);
+    return;
+  }
 
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys. If the previous node is implicitly keyed
-      // we can continue to replace it without aborting even if it is not a text
-      // node.
-      if (key !== null) {
-        return null;
-      }
-      return updateTextNode(
-        returnFiber,
-        oldFiber,
-        "" + newChild,
-        expirationTime
-      );
-    }
+  if (earliestRemainingTime < earliestSuspendedTime) {
+    // The earliest remaining time is earlier than all the suspended work.
+    // Treat it as a pending update.
+    markPendingPriorityLevel(root, earliestRemainingTime);
+    findNextPendingPriorityLevel(root);
+    return;
+  }
 
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          if (newChild.key === key) {
-            if (newChild.type === REACT_FRAGMENT_TYPE) {
-              return updateFragment(
-                returnFiber,
-                oldFiber,
-                newChild.props.children,
-                expirationTime,
-                key
-              );
-            }
-            return updateElement(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime
-            );
-          } else {
-            return null;
+  // The earliest remaining time falls within the range of known suspended
+  // levels. We should treat this as suspended work.
+  findNextPendingPriorityLevel(root);
+}
+
+function hasLowerPriorityWork(root, renderExpirationTime) {
+  return (
+    renderExpirationTime !== root.latestPendingTime &&
+    renderExpirationTime !== root.latestSuspendedTime
+  );
+}
+
+function markSuspendedPriorityLevel(root, suspendedTime, didError) {
+  if (didError && !hasLowerPriorityWork(root, suspendedTime)) {
+    // TODO: When we add back resuming, we need to ensure the progressed work
+    // is thrown out and not reused during the restarted render. One way to
+    // invalidate the progressed work is to restart at expirationTime + 1.
+    root.didError = true;
+    findNextPendingPriorityLevel(root);
+    return;
+  }
+
+  // First, check the known pending levels and update them if needed.
+  var earliestPendingTime = root.earliestPendingTime;
+  var latestPendingTime = root.latestPendingTime;
+  if (earliestPendingTime === suspendedTime) {
+    if (latestPendingTime === suspendedTime) {
+      // Both known pending levels were suspended. Clear them.
+      root.earliestPendingTime = root.latestPendingTime = NoWork;
+    } else {
+      // The earliest pending level was suspended. Clear by setting it to the
+      // latest pending level.
+      root.earliestPendingTime = latestPendingTime;
+    }
+  } else if (latestPendingTime === suspendedTime) {
+    // The latest pending level was suspended. Clear by setting it to the
+    // latest pending level.
+    root.latestPendingTime = earliestPendingTime;
+  }
+
+  // Next, if we're working on the lowest known suspended level, clear the ping.
+  // TODO: What if a promise suspends and pings before the root completes?
+  var latestSuspendedTime = root.latestSuspendedTime;
+  if (latestSuspendedTime === suspendedTime) {
+    root.latestPingedTime = NoWork;
+  }
+
+  // Finally, update the known suspended levels.
+  var earliestSuspendedTime = root.earliestSuspendedTime;
+  if (earliestSuspendedTime === NoWork) {
+    // No other suspended levels.
+    root.earliestSuspendedTime = root.latestSuspendedTime = suspendedTime;
+  } else {
+    if (earliestSuspendedTime > suspendedTime) {
+      // This is the earliest suspended level.
+      root.earliestSuspendedTime = suspendedTime;
+    } else if (latestSuspendedTime < suspendedTime) {
+      // This is the latest suspended level
+      root.latestSuspendedTime = suspendedTime;
+    }
+  }
+  findNextPendingPriorityLevel(root);
+}
+
+function markPingedPriorityLevel(root, pingedTime) {
+  var latestSuspendedTime = root.latestSuspendedTime;
+  if (latestSuspendedTime !== NoWork && latestSuspendedTime <= pingedTime) {
+    var latestPingedTime = root.latestPingedTime;
+    if (latestPingedTime === NoWork || latestPingedTime < pingedTime) {
+      root.latestPingedTime = pingedTime;
+    }
+  }
+  findNextPendingPriorityLevel(root);
+}
+
+function findNextPendingPriorityLevel(root) {
+  var earliestSuspendedTime = root.earliestSuspendedTime;
+  var earliestPendingTime = root.earliestPendingTime;
+  var nextExpirationTimeToWorkOn = void 0;
+  var expirationTime = void 0;
+  if (earliestSuspendedTime === NoWork) {
+    // Fast path. There's no suspended work.
+    nextExpirationTimeToWorkOn = expirationTime = earliestPendingTime;
+  } else if (earliestPendingTime !== NoWork) {
+    // Check if there's known pending work.
+    nextExpirationTimeToWorkOn = earliestPendingTime;
+    expirationTime =
+      earliestSuspendedTime < earliestPendingTime
+        ? earliestSuspendedTime
+        : earliestPendingTime;
+  } else {
+    // Finally, if a suspended level was pinged, work on that. Otherwise there's
+    // nothing to work on.
+    nextExpirationTimeToWorkOn = expirationTime = root.latestPingedTime;
+  }
+
+  if (root.didError) {
+    // Revert to synchronous mode.
+    expirationTime = Sync;
+  }
+
+  root.nextExpirationTimeToWorkOn = nextExpirationTimeToWorkOn;
+  root.expirationTime = expirationTime;
+}
+
+// UpdateQueue is a linked list of prioritized updates.
+//
+// Like fibers, update queues come in pairs: a current queue, which represents
+// the visible state of the screen, and a work-in-progress queue, which is
+// can be mutated and processed asynchronously before it is committed — a form
+// of double buffering. If a work-in-progress render is discarded before
+// finishing, we create a new work-in-progress by cloning the current queue.
+//
+// Both queues share a persistent, singly-linked list structure. To schedule an
+// update, we append it to the end of both queues. Each queue maintains a
+// pointer to first update in the persistent list that hasn't been processed.
+// The work-in-progress pointer always has a position equal to or greater than
+// the current queue, since we always work on that one. The current queue's
+// pointer is only updated during the commit phase, when we swap in the
+// work-in-progress.
+//
+// For example:
+//
+//   Current pointer:           A - B - C - D - E - F
+//   Work-in-progress pointer:              D - E - F
+//                                          ^
+//                                          The work-in-progress queue has
+//                                          processed more updates than current.
+//
+// The reason we append to both queues is because otherwise we might drop
+// updates without ever processing them. For example, if we only add updates to
+// the work-in-progress queue, some updates could be lost whenever a work-in
+// -progress render restarts by cloning from current. Similarly, if we only add
+// updates to the current queue, the updates will be lost whenever an already
+// in-progress queue commits and swaps with the current queue. However, by
+// adding to both queues, we guarantee that the update will be part of the next
+// work-in-progress. (And because the work-in-progress queue becomes the
+// current queue once it commits, there's no danger of applying the same
+// update twice.)
+//
+// Prioritization
+// --------------
+//
+// Updates are not sorted by priority, but by insertion; new updates are always
+// appended to the end of the list.
+//
+// The priority is still important, though. When processing the update queue
+// during the render phase, only the updates with sufficient priority are
+// included in the result. If we skip an update because it has insufficient
+// priority, it remains in the queue to be processed later, during a lower
+// priority render. Crucially, all updates subsequent to a skipped update also
+// remain in the queue *regardless of their priority*. That means high priority
+// updates are sometimes processed twice, at two separate priorities. We also
+// keep track of a base state, that represents the state before the first
+// update in the queue is applied.
+//
+// For example:
+//
+//   Given a base state of '', and the following queue of updates
+//
+//     A1 - B2 - C1 - D2
+//
+//   where the number indicates the priority, and the update is applied to the
+//   previous state by appending a letter, React will process these updates as
+//   two separate renders, one per distinct priority level:
+//
+//   First render, at priority 1:
+//     Base state: ''
+//     Updates: [A1, C1]
+//     Result state: 'AC'
+//
+//   Second render, at priority 2:
+//     Base state: 'A'            <-  The base state does not include C1,
+//                                    because B2 was skipped.
+//     Updates: [B2, C1, D2]      <-  C1 was rebased on top of B2
+//     Result state: 'ABCD'
+//
+// Because we process updates in insertion order, and rebase high priority
+// updates when preceding updates are skipped, the final result is deterministic
+// regardless of priority. Intermediate state may vary according to system
+// resources, but the final state is always the same.
+
+var UpdateState = 0;
+var ReplaceState = 1;
+var ForceUpdate = 2;
+var CaptureUpdate = 3;
+
+// Global state that is reset at the beginning of calling `processUpdateQueue`.
+// It should only be read right after calling `processUpdateQueue`, via
+// `checkHasForceUpdateAfterProcessing`.
+var hasForceUpdate = false;
+
+var didWarnUpdateInsideUpdate = void 0;
+var currentlyProcessingQueue = void 0;
+var resetCurrentlyProcessingQueue = void 0;
+{
+  didWarnUpdateInsideUpdate = false;
+  currentlyProcessingQueue = null;
+  resetCurrentlyProcessingQueue = function() {
+    currentlyProcessingQueue = null;
+  };
+}
+
+function createUpdateQueue(baseState) {
+  var queue = {
+    expirationTime: NoWork,
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+  return queue;
+}
+
+function cloneUpdateQueue(currentQueue) {
+  var queue = {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+
+    // TODO: With resuming, if we bail out and resuse the child tree, we should
+    // keep these effects.
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+
+    firstEffect: null,
+    lastEffect: null,
+
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+  return queue;
+}
+
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+
+    tag: UpdateState,
+    payload: null,
+    callback: null,
+
+    next: null,
+    nextEffect: null
+  };
+}
+
+function appendUpdateToQueue(queue, update, expirationTime) {
+  // Append the update to the end of the list.
+  if (queue.lastUpdate === null) {
+    // Queue is empty
+    queue.firstUpdate = queue.lastUpdate = update;
+  } else {
+    queue.lastUpdate.next = update;
+    queue.lastUpdate = update;
+  }
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > expirationTime
+  ) {
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    queue.expirationTime = expirationTime;
+  }
+}
+
+function enqueueUpdate(fiber, update, expirationTime) {
+  // Update queues are created lazily.
+  var alternate = fiber.alternate;
+  var queue1 = void 0;
+  var queue2 = void 0;
+  if (alternate === null) {
+    // There's only one fiber.
+    queue1 = fiber.updateQueue;
+    queue2 = null;
+    if (queue1 === null) {
+      queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
+    }
+  } else {
+    // There are two owners.
+    queue1 = fiber.updateQueue;
+    queue2 = alternate.updateQueue;
+    if (queue1 === null) {
+      if (queue2 === null) {
+        // Neither fiber has an update queue. Create new ones.
+        queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState);
+        queue2 = alternate.updateQueue = createUpdateQueue(
+          alternate.memoizedState
+        );
+      } else {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue1 = fiber.updateQueue = cloneUpdateQueue(queue2);
+      }
+    } else {
+      if (queue2 === null) {
+        // Only one fiber has an update queue. Clone to create a new one.
+        queue2 = alternate.updateQueue = cloneUpdateQueue(queue1);
+      } else {
+        // Both owners have an update queue.
+      }
+    }
+  }
+  if (queue2 === null || queue1 === queue2) {
+    // There's only a single queue.
+    appendUpdateToQueue(queue1, update, expirationTime);
+  } else {
+    // There are two queues. We need to append the update to both queues,
+    // while accounting for the persistent structure of the list — we don't
+    // want the same update to be added multiple times.
+    if (queue1.lastUpdate === null || queue2.lastUpdate === null) {
+      // One of the queues is not empty. We must add the update to both queues.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      appendUpdateToQueue(queue2, update, expirationTime);
+    } else {
+      // Both queues are non-empty. The last update is the same in both lists,
+      // because of structural sharing. So, only append to one of the lists.
+      appendUpdateToQueue(queue1, update, expirationTime);
+      // But we still need to update the `lastUpdate` pointer of queue2.
+      queue2.lastUpdate = update;
+    }
+  }
+
+  {
+    if (
+      fiber.tag === ClassComponent &&
+      (currentlyProcessingQueue === queue1 ||
+        (queue2 !== null && currentlyProcessingQueue === queue2)) &&
+      !didWarnUpdateInsideUpdate
+    ) {
+      warning(
+        false,
+        "An update (setState, replaceState, or forceUpdate) was scheduled " +
+          "from inside an update function. Update functions should be pure, " +
+          "with zero side-effects. Consider using componentDidUpdate or a " +
+          "callback."
+      );
+      didWarnUpdateInsideUpdate = true;
+    }
+  }
+}
+
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  // Captured updates go into a separate list, and only on the work-in-
+  // progress queue.
+  var workInProgressQueue = workInProgress.updateQueue;
+  if (workInProgressQueue === null) {
+    workInProgressQueue = workInProgress.updateQueue = createUpdateQueue(
+      workInProgress.memoizedState
+    );
+  } else {
+    // TODO: I put this here rather than createWorkInProgress so that we don't
+    // clone the queue unnecessarily. There's probably a better way to
+    // structure this.
+    workInProgressQueue = ensureWorkInProgressQueueIsAClone(
+      workInProgress,
+      workInProgressQueue
+    );
+  }
+
+  // Append the update to the end of the list.
+  if (workInProgressQueue.lastCapturedUpdate === null) {
+    // This is the first render phase update
+    workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update;
+  } else {
+    workInProgressQueue.lastCapturedUpdate.next = update;
+    workInProgressQueue.lastCapturedUpdate = update;
+  }
+  if (
+    workInProgressQueue.expirationTime === NoWork ||
+    workInProgressQueue.expirationTime > renderExpirationTime
+  ) {
+    // The incoming update has the earliest expiration of any update in the
+    // queue. Update the queue's expiration time.
+    workInProgressQueue.expirationTime = renderExpirationTime;
+  }
+}
+
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  if (current !== null) {
+    // If the work-in-progress queue is equal to the current queue,
+    // we need to clone it first.
+    if (queue === current.updateQueue) {
+      queue = workInProgress.updateQueue = cloneUpdateQueue(queue);
+    }
+  }
+  return queue;
+}
+
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case ReplaceState: {
+      var _payload = update.payload;
+      if (typeof _payload === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload.call(instance, prevState, nextProps);
           }
         }
-        case REACT_PORTAL_TYPE: {
-          if (newChild.key === key) {
-            return updatePortal(
-              returnFiber,
-              oldFiber,
-              newChild,
-              expirationTime
-            );
-          } else {
-            return null;
+        return _payload.call(instance, prevState, nextProps);
+      }
+      // State object
+      return _payload;
+    }
+    case CaptureUpdate: {
+      workInProgress.effectTag =
+        (workInProgress.effectTag & ~ShouldCapture) | DidCapture;
+    }
+    // Intentional fallthrough
+    case UpdateState: {
+      var _payload2 = update.payload;
+      var partialState = void 0;
+      if (typeof _payload2 === "function") {
+        // Updater function
+        {
+          if (
+            debugRenderPhaseSideEffects ||
+            (debugRenderPhaseSideEffectsForStrictMode &&
+              workInProgress.mode & StrictMode)
+          ) {
+            _payload2.call(instance, prevState, nextProps);
           }
         }
+        partialState = _payload2.call(instance, prevState, nextProps);
+      } else {
+        // Partial state object
+        partialState = _payload2;
+      }
+      if (partialState === null || partialState === undefined) {
+        // Null and undefined are treated as no-ops.
+        return prevState;
+      }
+      // Merge the partial state and the previous state.
+      return Object.assign({}, prevState, partialState);
+    }
+    case ForceUpdate: {
+      hasForceUpdate = true;
+      return prevState;
+    }
+  }
+  return prevState;
+}
+
+function processUpdateQueue(
+  workInProgress,
+  queue,
+  props,
+  instance,
+  renderExpirationTime
+) {
+  hasForceUpdate = false;
+
+  if (
+    queue.expirationTime === NoWork ||
+    queue.expirationTime > renderExpirationTime
+  ) {
+    // Insufficient priority. Bailout.
+    return;
+  }
+
+  queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+
+  {
+    currentlyProcessingQueue = queue;
+  }
+
+  // These values may change as we process the queue.
+  var newBaseState = queue.baseState;
+  var newFirstUpdate = null;
+  var newExpirationTime = NoWork;
+
+  // Iterate through the list of updates to compute the result.
+  var update = queue.firstUpdate;
+  var resultState = newBaseState;
+  while (update !== null) {
+    var updateExpirationTime = update.expirationTime;
+    if (updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      if (newFirstUpdate === null) {
+        // This is the first skipped update. It will be the first update in
+        // the new list.
+        newFirstUpdate = update;
+        // Since this is the first update that was skipped, the current result
+        // is the new base state.
+        newBaseState = resultState;
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
+      if (
+        newExpirationTime === NoWork ||
+        newExpirationTime > updateExpirationTime
+      ) {
+        newExpirationTime = updateExpirationTime;
+      }
+    } else {
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback = update.callback;
+      if (_callback !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastEffect === null) {
+          queue.firstEffect = queue.lastEffect = update;
+        } else {
+          queue.lastEffect.nextEffect = update;
+          queue.lastEffect = update;
+        }
+      }
+    }
+    // Continue to the next update.
+    update = update.next;
+  }
+
+  // Separately, iterate though the list of captured updates.
+  var newFirstCapturedUpdate = null;
+  update = queue.firstCapturedUpdate;
+  while (update !== null) {
+    var _updateExpirationTime = update.expirationTime;
+    if (_updateExpirationTime > renderExpirationTime) {
+      // This update does not have sufficient priority. Skip it.
+      if (newFirstCapturedUpdate === null) {
+        // This is the first skipped captured update. It will be the first
+        // update in the new list.
+        newFirstCapturedUpdate = update;
+        // If this is the first update that was skipped, the current result is
+        // the new base state.
+        if (newFirstUpdate === null) {
+          newBaseState = resultState;
+        }
+      }
+      // Since this update will remain in the list, update the remaining
+      // expiration time.
+      if (
+        newExpirationTime === NoWork ||
+        newExpirationTime > _updateExpirationTime
+      ) {
+        newExpirationTime = _updateExpirationTime;
+      }
+    } else {
+      // This update does have sufficient priority. Process it and compute
+      // a new result.
+      resultState = getStateFromUpdate(
+        workInProgress,
+        queue,
+        update,
+        resultState,
+        props,
+        instance
+      );
+      var _callback2 = update.callback;
+      if (_callback2 !== null) {
+        workInProgress.effectTag |= Callback;
+        // Set this to null, in case it was mutated during an aborted render.
+        update.nextEffect = null;
+        if (queue.lastCapturedEffect === null) {
+          queue.firstCapturedEffect = queue.lastCapturedEffect = update;
+        } else {
+          queue.lastCapturedEffect.nextEffect = update;
+          queue.lastCapturedEffect = update;
+        }
       }
+    }
+    update = update.next;
+  }
+
+  if (newFirstUpdate === null) {
+    queue.lastUpdate = null;
+  }
+  if (newFirstCapturedUpdate === null) {
+    queue.lastCapturedUpdate = null;
+  } else {
+    workInProgress.effectTag |= Callback;
+  }
+  if (newFirstUpdate === null && newFirstCapturedUpdate === null) {
+    // We processed every update, without skipping. That means the new base
+    // state is the same as the result state.
+    newBaseState = resultState;
+  }
 
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        if (key !== null) {
-          return null;
-        }
+  queue.baseState = newBaseState;
+  queue.firstUpdate = newFirstUpdate;
+  queue.firstCapturedUpdate = newFirstCapturedUpdate;
+  queue.expirationTime = newExpirationTime;
 
-        return updateFragment(
-          returnFiber,
-          oldFiber,
-          newChild,
-          expirationTime,
-          null
-        );
-      }
+  workInProgress.memoizedState = resultState;
 
-      throwOnInvalidObjectType(returnFiber, newChild);
+  {
+    currentlyProcessingQueue = null;
+  }
+}
+
+function callCallback(callback, context) {
+  invariant(
+    typeof callback === "function",
+    "Invalid argument passed as callback. Expected a function. Instead " +
+      "received: %s",
+    callback
+  );
+  callback.call(context);
+}
+
+function resetHasForceUpdateBeforeProcessing() {
+  hasForceUpdate = false;
+}
+
+function checkHasForceUpdateAfterProcessing() {
+  return hasForceUpdate;
+}
+
+function commitUpdateQueue(
+  finishedWork,
+  finishedQueue,
+  instance,
+  renderExpirationTime
+) {
+  // If the finished render included captured updates, and there are still
+  // lower priority updates left over, we need to keep the captured updates
+  // in the queue so that they are rebased and not dropped once we process the
+  // queue again at the lower priority.
+  if (finishedQueue.firstCapturedUpdate !== null) {
+    // Join the captured update list to the end of the normal list.
+    if (finishedQueue.lastUpdate !== null) {
+      finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate;
+      finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate;
     }
+    // Clear the list of captured updates.
+    finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null;
+  }
 
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
+  // Commit the effects
+  var effect = finishedQueue.firstEffect;
+  finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+  while (effect !== null) {
+    var _callback3 = effect.callback;
+    if (_callback3 !== null) {
+      effect.callback = null;
+      callCallback(_callback3, instance);
     }
+    effect = effect.nextEffect;
+  }
 
-    return null;
+  effect = finishedQueue.firstCapturedEffect;
+  finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+  while (effect !== null) {
+    var _callback4 = effect.callback;
+    if (_callback4 !== null) {
+      effect.callback = null;
+      callCallback(_callback4, instance);
+    }
+    effect = effect.nextEffect;
   }
+}
 
-  function updateFromMap(
-    existingChildren,
-    returnFiber,
-    newIdx,
-    newChild,
-    expirationTime
-  ) {
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      // Text nodes don't have keys, so we neither have to check the old nor
-      // new node for the key. If both are text nodes, they match.
-      var matchedFiber = existingChildren.get(newIdx) || null;
-      return updateTextNode(
-        returnFiber,
-        matchedFiber,
-        "" + newChild,
-        expirationTime
-      );
+function createCapturedValue(value, source) {
+  // If the value is an error, call this function immediately after it is thrown
+  // so the stack is accurate.
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
+
+var providerCursor = createCursor(null);
+var valueCursor = createCursor(null);
+var changedBitsCursor = createCursor(0);
+
+var rendererSigil = void 0;
+{
+  // Use this to detect multiple renderers using the same context
+  rendererSigil = {};
+}
+
+function pushProvider(providerFiber) {
+  var context = providerFiber.type._context;
+
+  if (isPrimaryRenderer) {
+    push(changedBitsCursor, context._changedBits, providerFiber);
+    push(valueCursor, context._currentValue, providerFiber);
+    push(providerCursor, providerFiber, providerFiber);
+
+    context._currentValue = providerFiber.pendingProps.value;
+    context._changedBits = providerFiber.stateNode;
+    {
+      !(
+        context._currentRenderer === undefined ||
+        context._currentRenderer === null ||
+        context._currentRenderer === rendererSigil
+      )
+        ? warning(
+            false,
+            "Detected multiple renderers concurrently rendering the " +
+              "same context provider. This is currently unsupported."
+          )
+        : void 0;
+      context._currentRenderer = rendererSigil;
+    }
+  } else {
+    push(changedBitsCursor, context._changedBits2, providerFiber);
+    push(valueCursor, context._currentValue2, providerFiber);
+    push(providerCursor, providerFiber, providerFiber);
+
+    context._currentValue2 = providerFiber.pendingProps.value;
+    context._changedBits2 = providerFiber.stateNode;
+    {
+      !(
+        context._currentRenderer2 === undefined ||
+        context._currentRenderer2 === null ||
+        context._currentRenderer2 === rendererSigil
+      )
+        ? warning(
+            false,
+            "Detected multiple renderers concurrently rendering the " +
+              "same context provider. This is currently unsupported."
+          )
+        : void 0;
+      context._currentRenderer2 = rendererSigil;
     }
+  }
+}
 
-    if (typeof newChild === "object" && newChild !== null) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE: {
-          var _matchedFiber =
-            existingChildren.get(
-              newChild.key === null ? newIdx : newChild.key
-            ) || null;
-          if (newChild.type === REACT_FRAGMENT_TYPE) {
-            return updateFragment(
-              returnFiber,
-              _matchedFiber,
-              newChild.props.children,
-              expirationTime,
-              newChild.key
-            );
-          }
-          return updateElement(
-            returnFiber,
-            _matchedFiber,
-            newChild,
-            expirationTime
-          );
-        }
-        case REACT_PORTAL_TYPE: {
-          var _matchedFiber2 =
-            existingChildren.get(
-              newChild.key === null ? newIdx : newChild.key
-            ) || null;
-          return updatePortal(
-            returnFiber,
-            _matchedFiber2,
-            newChild,
-            expirationTime
-          );
-        }
-      }
+function popProvider(providerFiber) {
+  var changedBits = changedBitsCursor.current;
+  var currentValue = valueCursor.current;
+
+  pop(providerCursor, providerFiber);
+  pop(valueCursor, providerFiber);
+  pop(changedBitsCursor, providerFiber);
+
+  var context = providerFiber.type._context;
+  if (isPrimaryRenderer) {
+    context._currentValue = currentValue;
+    context._changedBits = changedBits;
+  } else {
+    context._currentValue2 = currentValue;
+    context._changedBits2 = changedBits;
+  }
+}
+
+function getContextCurrentValue(context) {
+  return isPrimaryRenderer ? context._currentValue : context._currentValue2;
+}
+
+function getContextChangedBits(context) {
+  return isPrimaryRenderer ? context._changedBits : context._changedBits2;
+}
+
+var NO_CONTEXT = {};
+
+var contextStackCursor$1 = createCursor(NO_CONTEXT);
+var contextFiberStackCursor = createCursor(NO_CONTEXT);
+var rootInstanceStackCursor = createCursor(NO_CONTEXT);
+
+function requiredContext(c) {
+  invariant(
+    c !== NO_CONTEXT,
+    "Expected host context to exist. This error is likely caused by a bug " +
+      "in React. Please file an issue."
+  );
+  return c;
+}
+
+function getRootHostContainer() {
+  var rootInstance = requiredContext(rootInstanceStackCursor.current);
+  return rootInstance;
+}
+
+function pushHostContainer(fiber, nextRootInstance) {
+  // Push current root instance onto the stack;
+  // This allows us to reset root when portals are popped.
+  push(rootInstanceStackCursor, nextRootInstance, fiber);
+  // Track the context and the Fiber that provided it.
+  // This enables us to pop only Fibers that provide unique contexts.
+  push(contextFiberStackCursor, fiber, fiber);
+
+  // Finally, we need to push the host context to the stack.
+  // However, we can't just call getRootHostContext() and push it because
+  // we'd have a different number of entries on the stack depending on
+  // whether getRootHostContext() throws somewhere in renderer code or not.
+  // So we push an empty value first. This lets us safely unwind on errors.
+  push(contextStackCursor$1, NO_CONTEXT, fiber);
+  var nextRootContext = getRootHostContext(nextRootInstance);
+  // Now that we know this function doesn't throw, replace it.
+  pop(contextStackCursor$1, fiber);
+  push(contextStackCursor$1, nextRootContext, fiber);
+}
+
+function popHostContainer(fiber) {
+  pop(contextStackCursor$1, fiber);
+  pop(contextFiberStackCursor, fiber);
+  pop(rootInstanceStackCursor, fiber);
+}
+
+function getHostContext() {
+  var context = requiredContext(contextStackCursor$1.current);
+  return context;
+}
+
+function pushHostContext(fiber) {
+  var rootInstance = requiredContext(rootInstanceStackCursor.current);
+  var context = requiredContext(contextStackCursor$1.current);
+  var nextContext = getChildHostContext(context, fiber.type, rootInstance);
+
+  // Don't push this Fiber's context unless it's unique.
+  if (context === nextContext) {
+    return;
+  }
+
+  // Track the context and the Fiber that provided it.
+  // This enables us to pop only Fibers that provide unique contexts.
+  push(contextFiberStackCursor, fiber, fiber);
+  push(contextStackCursor$1, nextContext, fiber);
+}
+
+function popHostContext(fiber) {
+  // Do not pop unless this Fiber provided the current context.
+  // pushHostContext() only pushes Fibers that provide unique contexts.
+  if (contextFiberStackCursor.current !== fiber) {
+    return;
+  }
+
+  pop(contextStackCursor$1, fiber);
+  pop(contextFiberStackCursor, fiber);
+}
+
+var commitTime = 0;
+
+function getCommitTime() {
+  return commitTime;
+}
+
+function recordCommitTime() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  commitTime = now();
+}
+
+/**
+ * The "actual" render time is total time required to render the descendants of a Profiler component.
+ * This time is stored as a stack, since Profilers can be nested.
+ * This time is started during the "begin" phase and stopped during the "complete" phase.
+ * It is paused (and accumulated) in the event of an interruption or an aborted render.
+ */
+
+var fiberStack$1 = void 0;
+
+{
+  fiberStack$1 = [];
+}
+
+var timerPausedAt = 0;
+var totalElapsedPauseTime = 0;
+
+function checkActualRenderTimeStackEmpty() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  {
+    !(fiberStack$1.length === 0)
+      ? warning(
+          false,
+          "Expected an empty stack. Something was not reset properly."
+        )
+      : void 0;
+  }
+}
+
+function markActualRenderTimeStarted(fiber) {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  {
+    fiberStack$1.push(fiber);
+  }
+
+  fiber.actualDuration = now() - fiber.actualDuration - totalElapsedPauseTime;
+  fiber.actualStartTime = now();
+}
+
+function pauseActualRenderTimerIfRunning() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  if (timerPausedAt === 0) {
+    timerPausedAt = now();
+  }
+}
+
+function recordElapsedActualRenderTime(fiber) {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  {
+    !(fiber === fiberStack$1.pop())
+      ? warning(false, "Unexpected Fiber (%s) popped.", getComponentName(fiber))
+      : void 0;
+  }
 
-      if (isArray$1(newChild) || getIteratorFn(newChild)) {
-        var _matchedFiber3 = existingChildren.get(newIdx) || null;
-        return updateFragment(
-          returnFiber,
-          _matchedFiber3,
-          newChild,
-          expirationTime,
-          null
-        );
-      }
+  fiber.actualDuration = now() - totalElapsedPauseTime - fiber.actualDuration;
+}
 
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
+function resetActualRenderTimer() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  totalElapsedPauseTime = 0;
+}
 
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
+function resumeActualRenderTimerIfPaused() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  if (timerPausedAt > 0) {
+    totalElapsedPauseTime += now() - timerPausedAt;
+    timerPausedAt = 0;
+  }
+}
 
-    return null;
+/**
+ * The "base" render time is the duration of the “begin” phase of work for a particular fiber.
+ * This time is measured and stored on each fiber.
+ * The time for all sibling fibers are accumulated and stored on their parent during the "complete" phase.
+ * If a fiber bails out (sCU false) then its "base" timer is cancelled and the fiber is not updated.
+ */
+
+var baseStartTime = -1;
+
+function recordElapsedBaseRenderTimeIfRunning(fiber) {
+  if (!enableProfilerTimer) {
+    return;
   }
+  if (baseStartTime !== -1) {
+    fiber.selfBaseTime = now() - baseStartTime;
+  }
+}
 
-  /**
-   * Warns if there is a duplicate or missing key
-   */
-  function warnOnInvalidKey(child, knownKeys) {
-    {
-      if (typeof child !== "object" || child === null) {
-        return knownKeys;
-      }
-      switch (child.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-        case REACT_PORTAL_TYPE:
-          warnForMissingKey(child);
-          var key = child.key;
-          if (typeof key !== "string") {
-            break;
-          }
-          if (knownKeys === null) {
-            knownKeys = new Set();
-            knownKeys.add(key);
-            break;
-          }
-          if (!knownKeys.has(key)) {
-            knownKeys.add(key);
-            break;
-          }
-          warning(
-            false,
-            "Encountered two children with the same key, `%s`. " +
-              "Keys should be unique so that components maintain their identity " +
-              "across updates. Non-unique keys may cause children to be " +
-              "duplicated and/or omitted — the behavior is unsupported and " +
-              "could change in a future version.%s",
-            key,
-            getCurrentFiberStackAddendum$2()
-          );
-          break;
-        default:
-          break;
-      }
+function startBaseRenderTimer() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  {
+    if (baseStartTime !== -1) {
+      warning(
+        false,
+        "Cannot start base timer that is already running. " +
+          "This error is likely caused by a bug in React. " +
+          "Please file an issue."
+      );
     }
-    return knownKeys;
   }
+  baseStartTime = now();
+}
 
-  function reconcileChildrenArray(
-    returnFiber,
-    currentFirstChild,
-    newChildren,
-    expirationTime
-  ) {
-    // This algorithm can't optimize by searching from boths ends since we
-    // don't have backpointers on fibers. I'm trying to see how far we can get
-    // with that model. If it ends up not being worth the tradeoffs, we can
-    // add it later.
+function stopBaseRenderTimerIfRunning() {
+  if (!enableProfilerTimer) {
+    return;
+  }
+  baseStartTime = -1;
+}
 
-    // Even with a two ended optimization, we'd want to optimize for the case
-    // where there are few changes and brute force the comparison instead of
-    // going for the Map. It'd like to explore hitting that path first in
-    // forward-only mode and only go for the Map once we notice that we need
-    // lots of look ahead. This doesn't handle reversal as well as two ended
-    // search but that's unusual. Besides, for the two ended optimization to
-    // work on Iterables, we'd need to copy the whole set.
+/*eslint-disable no-self-compare */
 
-    // In this first iteration, we'll just live with hitting the bad case
-    // (adding everything to a Map) in for every insert/move.
+var hasOwnProperty = Object.prototype.hasOwnProperty;
 
-    // If you change this code, also update reconcileChildrenIterator() which
-    // uses the same algorithm.
+/**
+ * inlined Object.is polyfill to avoid requiring consumers ship their own
+ * https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+ */
+function is(x, y) {
+  // SameValue algorithm
+  if (x === y) {
+    // Steps 1-5, 7-10
+    // Steps 6.b-6.e: +0 != -0
+    // Added the nonzero y check to make Flow happy, but it is redundant
+    return x !== 0 || y !== 0 || 1 / x === 1 / y;
+  } else {
+    // Step 6.a: NaN == NaN
+    return x !== x && y !== y;
+  }
+}
 
-    {
-      // First, validate keys.
-      var knownKeys = null;
-      for (var i = 0; i < newChildren.length; i++) {
-        var child = newChildren[i];
-        knownKeys = warnOnInvalidKey(child, knownKeys);
-      }
-    }
+/**
+ * Performs equality by iterating through keys on an object and returning false
+ * when any key has values which are not strictly equal between the arguments.
+ * Returns true when the values of all keys are strictly equal.
+ */
+function shallowEqual(objA, objB) {
+  if (is(objA, objB)) {
+    return true;
+  }
 
-    var resultingFirstChild = null;
-    var previousNewFiber = null;
+  if (
+    typeof objA !== "object" ||
+    objA === null ||
+    typeof objB !== "object" ||
+    objB === null
+  ) {
+    return false;
+  }
 
-    var oldFiber = currentFirstChild;
-    var lastPlacedIndex = 0;
-    var newIdx = 0;
-    var nextOldFiber = null;
-    for (; oldFiber !== null && newIdx < newChildren.length; newIdx++) {
-      if (oldFiber.index > newIdx) {
-        nextOldFiber = oldFiber;
-        oldFiber = null;
-      } else {
-        nextOldFiber = oldFiber.sibling;
-      }
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        newChildren[newIdx],
-        expirationTime
-      );
-      if (newFiber === null) {
-        // TODO: This breaks on empty slots like null children. That's
-        // unfortunate because it triggers the slow path all the time. We need
-        // a better way to communicate whether this was a miss or null,
-        // boolean, undefined, etc.
-        if (oldFiber === null) {
-          oldFiber = nextOldFiber;
-        }
-        break;
-      }
-      if (shouldTrackSideEffects) {
-        if (oldFiber && newFiber.alternate === null) {
-          // We matched the slot, but we didn't reuse the existing fiber, so we
-          // need to delete the existing child.
-          deleteChild(returnFiber, oldFiber);
-        }
-      }
-      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
-      if (previousNewFiber === null) {
-        // TODO: Move out of the loop. This only happens for the first run.
-        resultingFirstChild = newFiber;
-      } else {
-        // TODO: Defer siblings if we're not at the right index for this slot.
-        // I.e. if we had null values before, then we want to defer this
-        // for each null value. However, we also don't want to call updateSlot
-        // with the previous one.
-        previousNewFiber.sibling = newFiber;
-      }
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
+  var keysA = Object.keys(objA);
+  var keysB = Object.keys(objB);
+
+  if (keysA.length !== keysB.length) {
+    return false;
+  }
+
+  // Test for A's keys different from B.
+  for (var i = 0; i < keysA.length; i++) {
+    if (
+      !hasOwnProperty.call(objB, keysA[i]) ||
+      !is(objA[keysA[i]], objB[keysA[i]])
+    ) {
+      return false;
     }
+  }
 
-    if (newIdx === newChildren.length) {
-      // We've reached the end of the new children. We can delete the rest.
-      deleteRemainingChildren(returnFiber, oldFiber);
-      return resultingFirstChild;
+  return true;
+}
+
+var fakeInternalInstance = {};
+var isArray = Array.isArray;
+
+var didWarnAboutStateAssignmentForComponent = void 0;
+var didWarnAboutUninitializedState = void 0;
+var didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = void 0;
+var didWarnAboutLegacyLifecyclesAndDerivedState = void 0;
+var didWarnAboutUndefinedDerivedState = void 0;
+var warnOnUndefinedDerivedState = void 0;
+var warnOnInvalidCallback = void 0;
+
+{
+  didWarnAboutStateAssignmentForComponent = new Set();
+  didWarnAboutUninitializedState = new Set();
+  didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate = new Set();
+  didWarnAboutLegacyLifecyclesAndDerivedState = new Set();
+  didWarnAboutUndefinedDerivedState = new Set();
+
+  var didWarnOnInvalidCallback = new Set();
+
+  warnOnInvalidCallback = function(callback, callerName) {
+    if (callback === null || typeof callback === "function") {
+      return;
+    }
+    var key = callerName + "_" + callback;
+    if (!didWarnOnInvalidCallback.has(key)) {
+      didWarnOnInvalidCallback.add(key);
+      warning(
+        false,
+        "%s(...): Expected the last optional `callback` argument to be a " +
+          "function. Instead received: %s.",
+        callerName,
+        callback
+      );
     }
+  };
 
-    if (oldFiber === null) {
-      // If we don't have any more existing children we can choose a fast path
-      // since the rest will all be insertions.
-      for (; newIdx < newChildren.length; newIdx++) {
-        var _newFiber = createChild(
-          returnFiber,
-          newChildren[newIdx],
-          expirationTime
+  warnOnUndefinedDerivedState = function(workInProgress, partialState) {
+    if (partialState === undefined) {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutUndefinedDerivedState.has(componentName)) {
+        didWarnAboutUndefinedDerivedState.add(componentName);
+        warning(
+          false,
+          "%s.getDerivedStateFromProps(): A valid state object (or null) must be returned. " +
+            "You have returned undefined.",
+          componentName
         );
-        if (!_newFiber) {
-          continue;
-        }
-        lastPlacedIndex = placeChild(_newFiber, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          // TODO: Move out of the loop. This only happens for the first run.
-          resultingFirstChild = _newFiber;
-        } else {
-          previousNewFiber.sibling = _newFiber;
-        }
-        previousNewFiber = _newFiber;
       }
-      return resultingFirstChild;
     }
+  };
 
-    // Add all children to a key map for quick lookups.
-    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
-
-    // Keep scanning and use the map to restore deleted items as moves.
-    for (; newIdx < newChildren.length; newIdx++) {
-      var _newFiber2 = updateFromMap(
-        existingChildren,
-        returnFiber,
-        newIdx,
-        newChildren[newIdx],
-        expirationTime
+  // This is so gross but it's at least non-critical and can be removed if
+  // it causes problems. This is meant to give a nicer error message for
+  // ReactDOM15.unstable_renderSubtreeIntoContainer(reactDOM16Component,
+  // ...)) which otherwise throws a "_processChildContext is not a function"
+  // exception.
+  Object.defineProperty(fakeInternalInstance, "_processChildContext", {
+    enumerable: false,
+    value: function() {
+      invariant(
+        false,
+        "_processChildContext is not available in React 16+. This likely " +
+          "means you have multiple copies of React and are attempting to nest " +
+          "a React 15 tree inside a React 16 tree using " +
+          "unstable_renderSubtreeIntoContainer, which isn't supported. Try " +
+          "to make sure you have only one copy of React (and ideally, switch " +
+          "to ReactDOM.createPortal)."
       );
-      if (_newFiber2) {
-        if (shouldTrackSideEffects) {
-          if (_newFiber2.alternate !== null) {
-            // The new fiber is a work in progress, but if there exists a
-            // current, that means that we reused the fiber. We need to delete
-            // it from the child list so that we don't add it to the deletion
-            // list.
-            existingChildren.delete(
-              _newFiber2.key === null ? newIdx : _newFiber2.key
-            );
-          }
-        }
-        lastPlacedIndex = placeChild(_newFiber2, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          resultingFirstChild = _newFiber2;
-        } else {
-          previousNewFiber.sibling = _newFiber2;
-        }
-        previousNewFiber = _newFiber2;
-      }
     }
+  });
+  Object.freeze(fakeInternalInstance);
+}
 
-    if (shouldTrackSideEffects) {
-      // Any existing children that weren't consumed above were deleted. We need
-      // to add them to the deletion list.
-      existingChildren.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
-    }
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
 
-    return resultingFirstChild;
+  {
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      // Invoke the function an extra time to help detect side-effects.
+      getDerivedStateFromProps(nextProps, prevState);
+    }
   }
 
-  function reconcileChildrenIterator(
-    returnFiber,
-    currentFirstChild,
-    newChildrenIterable,
-    expirationTime
-  ) {
-    // This is the same implementation as reconcileChildrenArray(),
-    // but using the iterator instead.
+  var partialState = getDerivedStateFromProps(nextProps, prevState);
 
-    var iteratorFn = getIteratorFn(newChildrenIterable);
-    invariant(
-      typeof iteratorFn === "function",
-      "An object is not an iterable. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
+  {
+    warnOnUndefinedDerivedState(workInProgress, partialState);
+  }
+  // Merge the partial state and the previous state.
+  var memoizedState =
+    partialState === null || partialState === undefined
+      ? prevState
+      : Object.assign({}, prevState, partialState);
+  workInProgress.memoizedState = memoizedState;
 
-    {
-      // Warn about using Maps as children
-      if (typeof newChildrenIterable.entries === "function") {
-        var possibleMap = newChildrenIterable;
-        if (possibleMap.entries === iteratorFn) {
-          !didWarnAboutMaps
-            ? warning(
-                false,
-                "Using Maps as children is unsupported and will likely yield " +
-                  "unexpected results. Convert it to a sequence/iterable of keyed " +
-                  "ReactElements instead.%s",
-                getCurrentFiberStackAddendum$2()
-              )
-            : void 0;
-          didWarnAboutMaps = true;
-        }
-      }
+  // Once the update queue is empty, persist the derived state onto the
+  // base state.
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null && updateQueue.expirationTime === NoWork) {
+    updateQueue.baseState = memoizedState;
+  }
+}
 
-      // First, validate keys.
-      // We'll get a different iterator later for the main pass.
-      var _newChildren = iteratorFn.call(newChildrenIterable);
-      if (_newChildren) {
-        var knownKeys = null;
-        var _step = _newChildren.next();
-        for (; !_step.done; _step = _newChildren.next()) {
-          var child = _step.value;
-          knownKeys = warnOnInvalidKey(child, knownKeys);
-        }
+var classComponentUpdater = {
+  isMounted: isMounted,
+  enqueueSetState: function(inst, payload, callback) {
+    var fiber = get$1(inst);
+    var currentTime = recalculateCurrentTime();
+    var expirationTime = computeExpirationForFiber(currentTime, fiber);
+
+    var update = createUpdate(expirationTime);
+    update.payload = payload;
+    if (callback !== undefined && callback !== null) {
+      {
+        warnOnInvalidCallback(callback, "setState");
       }
+      update.callback = callback;
     }
 
-    var newChildren = iteratorFn.call(newChildrenIterable);
-    invariant(newChildren != null, "An iterable object provided no iterator.");
-
-    var resultingFirstChild = null;
-    var previousNewFiber = null;
+    enqueueUpdate(fiber, update, expirationTime);
+    scheduleWork(fiber, expirationTime);
+  },
+  enqueueReplaceState: function(inst, payload, callback) {
+    var fiber = get$1(inst);
+    var currentTime = recalculateCurrentTime();
+    var expirationTime = computeExpirationForFiber(currentTime, fiber);
 
-    var oldFiber = currentFirstChild;
-    var lastPlacedIndex = 0;
-    var newIdx = 0;
-    var nextOldFiber = null;
+    var update = createUpdate(expirationTime);
+    update.tag = ReplaceState;
+    update.payload = payload;
 
-    var step = newChildren.next();
-    for (
-      ;
-      oldFiber !== null && !step.done;
-      newIdx++, step = newChildren.next()
-    ) {
-      if (oldFiber.index > newIdx) {
-        nextOldFiber = oldFiber;
-        oldFiber = null;
-      } else {
-        nextOldFiber = oldFiber.sibling;
-      }
-      var newFiber = updateSlot(
-        returnFiber,
-        oldFiber,
-        step.value,
-        expirationTime
-      );
-      if (newFiber === null) {
-        // TODO: This breaks on empty slots like null children. That's
-        // unfortunate because it triggers the slow path all the time. We need
-        // a better way to communicate whether this was a miss or null,
-        // boolean, undefined, etc.
-        if (!oldFiber) {
-          oldFiber = nextOldFiber;
-        }
-        break;
-      }
-      if (shouldTrackSideEffects) {
-        if (oldFiber && newFiber.alternate === null) {
-          // We matched the slot, but we didn't reuse the existing fiber, so we
-          // need to delete the existing child.
-          deleteChild(returnFiber, oldFiber);
-        }
-      }
-      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
-      if (previousNewFiber === null) {
-        // TODO: Move out of the loop. This only happens for the first run.
-        resultingFirstChild = newFiber;
-      } else {
-        // TODO: Defer siblings if we're not at the right index for this slot.
-        // I.e. if we had null values before, then we want to defer this
-        // for each null value. However, we also don't want to call updateSlot
-        // with the previous one.
-        previousNewFiber.sibling = newFiber;
+    if (callback !== undefined && callback !== null) {
+      {
+        warnOnInvalidCallback(callback, "replaceState");
       }
-      previousNewFiber = newFiber;
-      oldFiber = nextOldFiber;
+      update.callback = callback;
     }
 
-    if (step.done) {
-      // We've reached the end of the new children. We can delete the rest.
-      deleteRemainingChildren(returnFiber, oldFiber);
-      return resultingFirstChild;
-    }
+    enqueueUpdate(fiber, update, expirationTime);
+    scheduleWork(fiber, expirationTime);
+  },
+  enqueueForceUpdate: function(inst, callback) {
+    var fiber = get$1(inst);
+    var currentTime = recalculateCurrentTime();
+    var expirationTime = computeExpirationForFiber(currentTime, fiber);
 
-    if (oldFiber === null) {
-      // If we don't have any more existing children we can choose a fast path
-      // since the rest will all be insertions.
-      for (; !step.done; newIdx++, step = newChildren.next()) {
-        var _newFiber3 = createChild(returnFiber, step.value, expirationTime);
-        if (_newFiber3 === null) {
-          continue;
-        }
-        lastPlacedIndex = placeChild(_newFiber3, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          // TODO: Move out of the loop. This only happens for the first run.
-          resultingFirstChild = _newFiber3;
-        } else {
-          previousNewFiber.sibling = _newFiber3;
-        }
-        previousNewFiber = _newFiber3;
+    var update = createUpdate(expirationTime);
+    update.tag = ForceUpdate;
+
+    if (callback !== undefined && callback !== null) {
+      {
+        warnOnInvalidCallback(callback, "forceUpdate");
       }
-      return resultingFirstChild;
+      update.callback = callback;
     }
 
-    // Add all children to a key map for quick lookups.
-    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
+    enqueueUpdate(fiber, update, expirationTime);
+    scheduleWork(fiber, expirationTime);
+  }
+};
 
-    // Keep scanning and use the map to restore deleted items as moves.
-    for (; !step.done; newIdx++, step = newChildren.next()) {
-      var _newFiber4 = updateFromMap(
-        existingChildren,
-        returnFiber,
-        newIdx,
-        step.value,
-        expirationTime
-      );
-      if (_newFiber4 !== null) {
-        if (shouldTrackSideEffects) {
-          if (_newFiber4.alternate !== null) {
-            // The new fiber is a work in progress, but if there exists a
-            // current, that means that we reused the fiber. We need to delete
-            // it from the child list so that we don't add it to the deletion
-            // list.
-            existingChildren.delete(
-              _newFiber4.key === null ? newIdx : _newFiber4.key
-            );
-          }
-        }
-        lastPlacedIndex = placeChild(_newFiber4, lastPlacedIndex, newIdx);
-        if (previousNewFiber === null) {
-          resultingFirstChild = _newFiber4;
-        } else {
-          previousNewFiber.sibling = _newFiber4;
-        }
-        previousNewFiber = _newFiber4;
-      }
-    }
+function checkShouldComponentUpdate(
+  workInProgress,
+  oldProps,
+  newProps,
+  oldState,
+  newState,
+  newContext
+) {
+  var instance = workInProgress.stateNode;
+  var ctor = workInProgress.type;
+  if (typeof instance.shouldComponentUpdate === "function") {
+    startPhaseTimer(workInProgress, "shouldComponentUpdate");
+    var shouldUpdate = instance.shouldComponentUpdate(
+      newProps,
+      newState,
+      newContext
+    );
+    stopPhaseTimer();
 
-    if (shouldTrackSideEffects) {
-      // Any existing children that weren't consumed above were deleted. We need
-      // to add them to the deletion list.
-      existingChildren.forEach(function(child) {
-        return deleteChild(returnFiber, child);
-      });
+    {
+      !(shouldUpdate !== undefined)
+        ? warning(
+            false,
+            "%s.shouldComponentUpdate(): Returned undefined instead of a " +
+              "boolean value. Make sure to return true or false.",
+            getComponentName(workInProgress) || "Component"
+          )
+        : void 0;
     }
 
-    return resultingFirstChild;
+    return shouldUpdate;
   }
 
-  function reconcileSingleTextNode(
-    returnFiber,
-    currentFirstChild,
-    textContent,
-    expirationTime
-  ) {
-    // There's no need to check for keys on text nodes since we don't have a
-    // way to define them.
-    if (currentFirstChild !== null && currentFirstChild.tag === HostText) {
-      // We already have an existing node so let's just update it and delete
-      // the rest.
-      deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
-      var existing = useFiber(currentFirstChild, textContent, expirationTime);
-      existing.return = returnFiber;
-      return existing;
-    }
-    // The existing first child is not a text node so we need to create one
-    // and delete the existing ones.
-    deleteRemainingChildren(returnFiber, currentFirstChild);
-    var created = createFiberFromText(
-      textContent,
-      returnFiber.mode,
-      expirationTime
+  if (ctor.prototype && ctor.prototype.isPureReactComponent) {
+    return (
+      !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
     );
-    created.return = returnFiber;
-    return created;
   }
 
-  function reconcileSingleElement(
-    returnFiber,
-    currentFirstChild,
-    element,
-    expirationTime
-  ) {
-    var key = element.key;
-    var child = currentFirstChild;
-    while (child !== null) {
-      // TODO: If key === null and child.key === null, then this only applies to
-      // the first item in the list.
-      if (child.key === key) {
-        if (
-          child.tag === Fragment
-            ? element.type === REACT_FRAGMENT_TYPE
-            : child.type === element.type
-        ) {
-          deleteRemainingChildren(returnFiber, child.sibling);
-          var existing = useFiber(
-            child,
-            element.type === REACT_FRAGMENT_TYPE
-              ? element.props.children
-              : element.props,
-            expirationTime
-          );
-          existing.ref = coerceRef(returnFiber, child, element);
-          existing.return = returnFiber;
-          {
-            existing._debugSource = element._source;
-            existing._debugOwner = element._owner;
-          }
-          return existing;
-        } else {
-          deleteRemainingChildren(returnFiber, child);
-          break;
-        }
+  return true;
+}
+
+function checkClassInstance(workInProgress) {
+  var instance = workInProgress.stateNode;
+  var type = workInProgress.type;
+  {
+    var name = getComponentName(workInProgress) || "Component";
+    var renderPresent = instance.render;
+
+    if (!renderPresent) {
+      if (type.prototype && typeof type.prototype.render === "function") {
+        warning(
+          false,
+          "%s(...): No `render` method found on the returned component " +
+            "instance: did you accidentally return an object from the constructor?",
+          name
+        );
       } else {
-        deleteChild(returnFiber, child);
+        warning(
+          false,
+          "%s(...): No `render` method found on the returned component " +
+            "instance: you may have forgotten to define `render`.",
+          name
+        );
       }
-      child = child.sibling;
     }
 
-    if (element.type === REACT_FRAGMENT_TYPE) {
-      var created = createFiberFromFragment(
-        element.props.children,
-        returnFiber.mode,
-        expirationTime,
-        element.key
+    var noGetInitialStateOnES6 =
+      !instance.getInitialState ||
+      instance.getInitialState.isReactClassApproved ||
+      instance.state;
+    !noGetInitialStateOnES6
+      ? warning(
+          false,
+          "getInitialState was defined on %s, a plain JavaScript class. " +
+            "This is only supported for classes created using React.createClass. " +
+            "Did you mean to define a state property instead?",
+          name
+        )
+      : void 0;
+    var noGetDefaultPropsOnES6 =
+      !instance.getDefaultProps ||
+      instance.getDefaultProps.isReactClassApproved;
+    !noGetDefaultPropsOnES6
+      ? warning(
+          false,
+          "getDefaultProps was defined on %s, a plain JavaScript class. " +
+            "This is only supported for classes created using React.createClass. " +
+            "Use a static property to define defaultProps instead.",
+          name
+        )
+      : void 0;
+    var noInstancePropTypes = !instance.propTypes;
+    !noInstancePropTypes
+      ? warning(
+          false,
+          "propTypes was defined as an instance property on %s. Use a static " +
+            "property to define propTypes instead.",
+          name
+        )
+      : void 0;
+    var noInstanceContextTypes = !instance.contextTypes;
+    !noInstanceContextTypes
+      ? warning(
+          false,
+          "contextTypes was defined as an instance property on %s. Use a static " +
+            "property to define contextTypes instead.",
+          name
+        )
+      : void 0;
+    var noComponentShouldUpdate =
+      typeof instance.componentShouldUpdate !== "function";
+    !noComponentShouldUpdate
+      ? warning(
+          false,
+          "%s has a method called " +
+            "componentShouldUpdate(). Did you mean shouldComponentUpdate()? " +
+            "The name is phrased as a question because the function is " +
+            "expected to return a value.",
+          name
+        )
+      : void 0;
+    if (
+      type.prototype &&
+      type.prototype.isPureReactComponent &&
+      typeof instance.shouldComponentUpdate !== "undefined"
+    ) {
+      warning(
+        false,
+        "%s has a method called shouldComponentUpdate(). " +
+          "shouldComponentUpdate should not be used when extending React.PureComponent. " +
+          "Please extend React.Component if shouldComponentUpdate is used.",
+        getComponentName(workInProgress) || "A pure component"
       );
-      created.return = returnFiber;
-      return created;
-    } else {
-      var _created4 = createFiberFromElement(
-        element,
-        returnFiber.mode,
-        expirationTime
+    }
+    var noComponentDidUnmount =
+      typeof instance.componentDidUnmount !== "function";
+    !noComponentDidUnmount
+      ? warning(
+          false,
+          "%s has a method called " +
+            "componentDidUnmount(). But there is no such lifecycle method. " +
+            "Did you mean componentWillUnmount()?",
+          name
+        )
+      : void 0;
+    var noComponentDidReceiveProps =
+      typeof instance.componentDidReceiveProps !== "function";
+    !noComponentDidReceiveProps
+      ? warning(
+          false,
+          "%s has a method called " +
+            "componentDidReceiveProps(). But there is no such lifecycle method. " +
+            "If you meant to update the state in response to changing props, " +
+            "use componentWillReceiveProps(). If you meant to fetch data or " +
+            "run side-effects or mutations after React has updated the UI, use componentDidUpdate().",
+          name
+        )
+      : void 0;
+    var noComponentWillRecieveProps =
+      typeof instance.componentWillRecieveProps !== "function";
+    !noComponentWillRecieveProps
+      ? warning(
+          false,
+          "%s has a method called " +
+            "componentWillRecieveProps(). Did you mean componentWillReceiveProps()?",
+          name
+        )
+      : void 0;
+    var noUnsafeComponentWillRecieveProps =
+      typeof instance.UNSAFE_componentWillRecieveProps !== "function";
+    !noUnsafeComponentWillRecieveProps
+      ? warning(
+          false,
+          "%s has a method called " +
+            "UNSAFE_componentWillRecieveProps(). Did you mean UNSAFE_componentWillReceiveProps()?",
+          name
+        )
+      : void 0;
+    var hasMutatedProps = instance.props !== workInProgress.pendingProps;
+    !(instance.props === undefined || !hasMutatedProps)
+      ? warning(
+          false,
+          "%s(...): When calling super() in `%s`, make sure to pass " +
+            "up the same props that your component's constructor was passed.",
+          name,
+          name
+        )
+      : void 0;
+    var noInstanceDefaultProps = !instance.defaultProps;
+    !noInstanceDefaultProps
+      ? warning(
+          false,
+          "Setting defaultProps as an instance property on %s is not supported and will be ignored." +
+            " Instead, define defaultProps as a static property on %s.",
+          name,
+          name
+        )
+      : void 0;
+
+    if (
+      typeof instance.getSnapshotBeforeUpdate === "function" &&
+      typeof instance.componentDidUpdate !== "function" &&
+      !didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.has(type)
+    ) {
+      didWarnAboutGetSnapshotBeforeUpdateWithoutDidUpdate.add(type);
+      warning(
+        false,
+        "%s: getSnapshotBeforeUpdate() should be used with componentDidUpdate(). " +
+          "This component defines getSnapshotBeforeUpdate() only.",
+        getComponentName(workInProgress)
       );
-      _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
-      _created4.return = returnFiber;
-      return _created4;
+    }
+
+    var noInstanceGetDerivedStateFromProps =
+      typeof instance.getDerivedStateFromProps !== "function";
+    !noInstanceGetDerivedStateFromProps
+      ? warning(
+          false,
+          "%s: getDerivedStateFromProps() is defined as an instance method " +
+            "and will be ignored. Instead, declare it as a static method.",
+          name
+        )
+      : void 0;
+    var noInstanceGetDerivedStateFromCatch =
+      typeof instance.getDerivedStateFromCatch !== "function";
+    !noInstanceGetDerivedStateFromCatch
+      ? warning(
+          false,
+          "%s: getDerivedStateFromCatch() is defined as an instance method " +
+            "and will be ignored. Instead, declare it as a static method.",
+          name
+        )
+      : void 0;
+    var noStaticGetSnapshotBeforeUpdate =
+      typeof type.getSnapshotBeforeUpdate !== "function";
+    !noStaticGetSnapshotBeforeUpdate
+      ? warning(
+          false,
+          "%s: getSnapshotBeforeUpdate() is defined as a static method " +
+            "and will be ignored. Instead, declare it as an instance method.",
+          name
+        )
+      : void 0;
+    var _state = instance.state;
+    if (_state && (typeof _state !== "object" || isArray(_state))) {
+      warning(false, "%s.state: must be set to an object or null", name);
+    }
+    if (typeof instance.getChildContext === "function") {
+      !(typeof type.childContextTypes === "object")
+        ? warning(
+            false,
+            "%s.getChildContext(): childContextTypes must be defined in order to " +
+              "use getChildContext().",
+            name
+          )
+        : void 0;
     }
   }
+}
 
-  function reconcileSinglePortal(
-    returnFiber,
-    currentFirstChild,
-    portal,
-    expirationTime
-  ) {
-    var key = portal.key;
-    var child = currentFirstChild;
-    while (child !== null) {
-      // TODO: If key === null and child.key === null, then this only applies to
-      // the first item in the list.
-      if (child.key === key) {
-        if (
-          child.tag === HostPortal &&
-          child.stateNode.containerInfo === portal.containerInfo &&
-          child.stateNode.implementation === portal.implementation
-        ) {
-          deleteRemainingChildren(returnFiber, child.sibling);
-          var existing = useFiber(child, portal.children || [], expirationTime);
-          existing.return = returnFiber;
-          return existing;
-        } else {
-          deleteRemainingChildren(returnFiber, child);
-          break;
+function adoptClassInstance(workInProgress, instance) {
+  instance.updater = classComponentUpdater;
+  workInProgress.stateNode = instance;
+  // The instance needs access to the fiber so that it can schedule updates
+  set(instance, workInProgress);
+  {
+    instance._reactInternalInstance = fakeInternalInstance;
+  }
+}
+
+function constructClassInstance(workInProgress, props, renderExpirationTime) {
+  var ctor = workInProgress.type;
+  var unmaskedContext = getUnmaskedContext(workInProgress);
+  var needsContext = isContextConsumer(workInProgress);
+  var context = needsContext
+    ? getMaskedContext(workInProgress, unmaskedContext)
+    : emptyObject;
+
+  // Instantiate twice to help detect side-effects.
+  {
+    if (
+      debugRenderPhaseSideEffects ||
+      (debugRenderPhaseSideEffectsForStrictMode &&
+        workInProgress.mode & StrictMode)
+    ) {
+      new ctor(props, context); // eslint-disable-line no-new
+    }
+  }
+
+  var instance = new ctor(props, context);
+  var state = (workInProgress.memoizedState =
+    instance.state !== null && instance.state !== undefined
+      ? instance.state
+      : null);
+  adoptClassInstance(workInProgress, instance);
+
+  {
+    if (typeof ctor.getDerivedStateFromProps === "function" && state === null) {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutUninitializedState.has(componentName)) {
+        didWarnAboutUninitializedState.add(componentName);
+        warning(
+          false,
+          "%s: Did not properly initialize state during construction. " +
+            "Expected state to be an object, but it was %s.",
+          componentName,
+          instance.state === null ? "null" : "undefined"
+        );
+      }
+    }
+
+    // If new component APIs are defined, "unsafe" lifecycles won't be called.
+    // Warn about these lifecycles if they are present.
+    // Don't warn about react-lifecycles-compat polyfilled methods though.
+    if (
+      typeof ctor.getDerivedStateFromProps === "function" ||
+      typeof instance.getSnapshotBeforeUpdate === "function"
+    ) {
+      var foundWillMountName = null;
+      var foundWillReceivePropsName = null;
+      var foundWillUpdateName = null;
+      if (
+        typeof instance.componentWillMount === "function" &&
+        instance.componentWillMount.__suppressDeprecationWarning !== true
+      ) {
+        foundWillMountName = "componentWillMount";
+      } else if (typeof instance.UNSAFE_componentWillMount === "function") {
+        foundWillMountName = "UNSAFE_componentWillMount";
+      }
+      if (
+        typeof instance.componentWillReceiveProps === "function" &&
+        instance.componentWillReceiveProps.__suppressDeprecationWarning !== true
+      ) {
+        foundWillReceivePropsName = "componentWillReceiveProps";
+      } else if (
+        typeof instance.UNSAFE_componentWillReceiveProps === "function"
+      ) {
+        foundWillReceivePropsName = "UNSAFE_componentWillReceiveProps";
+      }
+      if (
+        typeof instance.componentWillUpdate === "function" &&
+        instance.componentWillUpdate.__suppressDeprecationWarning !== true
+      ) {
+        foundWillUpdateName = "componentWillUpdate";
+      } else if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+        foundWillUpdateName = "UNSAFE_componentWillUpdate";
+      }
+      if (
+        foundWillMountName !== null ||
+        foundWillReceivePropsName !== null ||
+        foundWillUpdateName !== null
+      ) {
+        var _componentName = getComponentName(workInProgress) || "Component";
+        var newApiName =
+          typeof ctor.getDerivedStateFromProps === "function"
+            ? "getDerivedStateFromProps()"
+            : "getSnapshotBeforeUpdate()";
+        if (!didWarnAboutLegacyLifecyclesAndDerivedState.has(_componentName)) {
+          didWarnAboutLegacyLifecyclesAndDerivedState.add(_componentName);
+          warning(
+            false,
+            "Unsafe legacy lifecycles will not be called for components using new component APIs.\n\n" +
+              "%s uses %s but also contains the following legacy lifecycles:%s%s%s\n\n" +
+              "The above lifecycles should be removed. Learn more about this warning here:\n" +
+              "https://fb.me/react-async-component-lifecycle-hooks",
+            _componentName,
+            newApiName,
+            foundWillMountName !== null ? "\n  " + foundWillMountName : "",
+            foundWillReceivePropsName !== null
+              ? "\n  " + foundWillReceivePropsName
+              : "",
+            foundWillUpdateName !== null ? "\n  " + foundWillUpdateName : ""
+          );
         }
-      } else {
-        deleteChild(returnFiber, child);
       }
-      child = child.sibling;
     }
+  }
 
-    var created = createFiberFromPortal(
-      portal,
-      returnFiber.mode,
-      expirationTime
-    );
-    created.return = returnFiber;
-    return created;
+  // Cache unmasked context so we can avoid recreating masked context unless necessary.
+  // ReactFiberContext usually updates this cache but can't for newly-created instances.
+  if (needsContext) {
+    cacheContext(workInProgress, unmaskedContext, context);
+  }
+
+  return instance;
+}
+
+function callComponentWillMount(workInProgress, instance) {
+  startPhaseTimer(workInProgress, "componentWillMount");
+  var oldState = instance.state;
+
+  if (typeof instance.componentWillMount === "function") {
+    instance.componentWillMount();
+  }
+  if (typeof instance.UNSAFE_componentWillMount === "function") {
+    instance.UNSAFE_componentWillMount();
   }
 
-  // This API will tag the children with the side-effect of the reconciliation
-  // itself. They will be added to the side-effect list as we pass through the
-  // children and the parent.
-  function reconcileChildFibers(
-    returnFiber,
-    currentFirstChild,
-    newChild,
-    expirationTime
-  ) {
-    // This function is not recursive.
-    // If the top level item is an array, we treat it as a set of children,
-    // not as a fragment. Nested arrays on the other hand will be treated as
-    // fragment nodes. Recursion happens at the normal flow.
+  stopPhaseTimer();
 
-    // Handle top level unkeyed fragments as if they were arrays.
-    // This leads to an ambiguity between <>{[...]}</> and <>...</>.
-    // We treat the ambiguous cases above the same.
-    if (
-      typeof newChild === "object" &&
-      newChild !== null &&
-      newChild.type === REACT_FRAGMENT_TYPE &&
-      newChild.key === null
-    ) {
-      newChild = newChild.props.children;
+  if (oldState !== instance.state) {
+    {
+      warning(
+        false,
+        "%s.componentWillMount(): Assigning directly to this.state is " +
+          "deprecated (except inside a component's " +
+          "constructor). Use setState instead.",
+        getComponentName(workInProgress) || "Component"
+      );
     }
+    classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+  }
+}
 
-    // Handle object types
-    var isObject = typeof newChild === "object" && newChild !== null;
+function callComponentWillReceiveProps(
+  workInProgress,
+  instance,
+  newProps,
+  newContext
+) {
+  var oldState = instance.state;
+  startPhaseTimer(workInProgress, "componentWillReceiveProps");
+  if (typeof instance.componentWillReceiveProps === "function") {
+    instance.componentWillReceiveProps(newProps, newContext);
+  }
+  if (typeof instance.UNSAFE_componentWillReceiveProps === "function") {
+    instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+  }
+  stopPhaseTimer();
 
-    if (isObject) {
-      switch (newChild.$$typeof) {
-        case REACT_ELEMENT_TYPE:
-          return placeSingleChild(
-            reconcileSingleElement(
-              returnFiber,
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )
-          );
-        case REACT_PORTAL_TYPE:
-          return placeSingleChild(
-            reconcileSinglePortal(
-              returnFiber,
-              currentFirstChild,
-              newChild,
-              expirationTime
-            )
-          );
+  if (instance.state !== oldState) {
+    {
+      var componentName = getComponentName(workInProgress) || "Component";
+      if (!didWarnAboutStateAssignmentForComponent.has(componentName)) {
+        didWarnAboutStateAssignmentForComponent.add(componentName);
+        warning(
+          false,
+          "%s.componentWillReceiveProps(): Assigning directly to " +
+            "this.state is deprecated (except inside a component's " +
+            "constructor). Use setState instead.",
+          componentName
+        );
       }
     }
+    classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+  }
+}
 
-    if (typeof newChild === "string" || typeof newChild === "number") {
-      return placeSingleChild(
-        reconcileSingleTextNode(
-          returnFiber,
-          currentFirstChild,
-          "" + newChild,
-          expirationTime
-        )
+// Invokes the mount life-cycles on a previously never rendered instance.
+function mountClassInstance(workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type;
+
+  {
+    checkClassInstance(workInProgress);
+  }
+
+  var instance = workInProgress.stateNode;
+  var props = workInProgress.pendingProps;
+  var unmaskedContext = getUnmaskedContext(workInProgress);
+
+  instance.props = props;
+  instance.state = workInProgress.memoizedState;
+  instance.refs = emptyObject;
+  instance.context = getMaskedContext(workInProgress, unmaskedContext);
+
+  {
+    if (workInProgress.mode & StrictMode) {
+      ReactStrictModeWarnings.recordUnsafeLifecycleWarnings(
+        workInProgress,
+        instance
       );
-    }
 
-    if (isArray$1(newChild)) {
-      return reconcileChildrenArray(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
+      ReactStrictModeWarnings.recordLegacyContextWarning(
+        workInProgress,
+        instance
       );
     }
 
-    if (getIteratorFn(newChild)) {
-      return reconcileChildrenIterator(
-        returnFiber,
-        currentFirstChild,
-        newChild,
-        expirationTime
+    if (warnAboutDeprecatedLifecycles) {
+      ReactStrictModeWarnings.recordDeprecationWarnings(
+        workInProgress,
+        instance
       );
     }
+  }
 
-    if (isObject) {
-      throwOnInvalidObjectType(returnFiber, newChild);
-    }
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null) {
+    processUpdateQueue(
+      workInProgress,
+      updateQueue,
+      props,
+      instance,
+      renderExpirationTime
+    );
+    instance.state = workInProgress.memoizedState;
+  }
 
-    {
-      if (typeof newChild === "function") {
-        warnOnFunctionType();
-      }
-    }
-    if (typeof newChild === "undefined") {
-      // If the new child is undefined, and the return fiber is a composite
-      // component, throw an error. If Fiber return types are disabled,
-      // we already threw above.
-      switch (returnFiber.tag) {
-        case ClassComponent: {
-          {
-            var instance = returnFiber.stateNode;
-            if (instance.render._isMockFunction) {
-              // We allow auto-mocks to proceed as if they're returning null.
-              break;
-            }
-          }
-        }
-        // Intentionally fall through to the next case, which handles both
-        // functions and classes
-        // eslint-disable-next-lined no-fallthrough
-        case FunctionalComponent: {
-          var Component = returnFiber.type;
-          invariant(
-            false,
-            "%s(...): Nothing was returned from render. This usually means a " +
-              "return statement is missing. Or, to render nothing, " +
-              "return null.",
-            Component.displayName || Component.name || "Component"
-          );
-        }
-      }
-    }
+  var getDerivedStateFromProps = workInProgress.type.getDerivedStateFromProps;
+  if (typeof getDerivedStateFromProps === "function") {
+    applyDerivedStateFromProps(workInProgress, getDerivedStateFromProps, props);
+    instance.state = workInProgress.memoizedState;
+  }
 
-    // Remaining cases are all treated as empty.
-    return deleteRemainingChildren(returnFiber, currentFirstChild);
+  // In order to support react-lifecycles-compat polyfilled components,
+  // Unsafe lifecycles should not be invoked for components using the new APIs.
+  if (
+    typeof ctor.getDerivedStateFromProps !== "function" &&
+    typeof instance.getSnapshotBeforeUpdate !== "function" &&
+    (typeof instance.UNSAFE_componentWillMount === "function" ||
+      typeof instance.componentWillMount === "function")
+  ) {
+    callComponentWillMount(workInProgress, instance);
+    // If we had additional state updates during this life-cycle, let's
+    // process them now.
+    updateQueue = workInProgress.updateQueue;
+    if (updateQueue !== null) {
+      processUpdateQueue(
+        workInProgress,
+        updateQueue,
+        props,
+        instance,
+        renderExpirationTime
+      );
+      instance.state = workInProgress.memoizedState;
+    }
   }
 
-  return reconcileChildFibers;
+  if (typeof instance.componentDidMount === "function") {
+    workInProgress.effectTag |= Update;
+  }
 }
 
-var reconcileChildFibers = ChildReconciler(true);
-var mountChildFibers = ChildReconciler(false);
+function resumeMountClassInstance(workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type;
+  var instance = workInProgress.stateNode;
 
-function cloneChildFibers(current, workInProgress) {
-  invariant(
-    current === null || workInProgress.child === current.child,
-    "Resuming work not yet implemented."
-  );
+  var oldProps = workInProgress.memoizedProps;
+  var newProps = workInProgress.pendingProps;
+  instance.props = oldProps;
 
-  if (workInProgress.child === null) {
-    return;
-  }
+  var oldContext = instance.context;
+  var newUnmaskedContext = getUnmaskedContext(workInProgress);
+  var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
 
-  var currentChild = workInProgress.child;
-  var newChild = createWorkInProgress(
-    currentChild,
-    currentChild.pendingProps,
-    currentChild.expirationTime
-  );
-  workInProgress.child = newChild;
+  var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
+  var hasNewLifecycles =
+    typeof getDerivedStateFromProps === "function" ||
+    typeof instance.getSnapshotBeforeUpdate === "function";
 
-  newChild.return = workInProgress;
-  while (currentChild.sibling !== null) {
-    currentChild = currentChild.sibling;
-    newChild = newChild.sibling = createWorkInProgress(
-      currentChild,
-      currentChild.pendingProps,
-      currentChild.expirationTime
-    );
-    newChild.return = workInProgress;
+  // Note: During these life-cycles, instance.props/instance.state are what
+  // ever the previously attempted to render - not the "current". However,
+  // during componentDidUpdate we pass the "current" props.
+
+  // In order to support react-lifecycles-compat polyfilled components,
+  // Unsafe lifecycles should not be invoked for components using the new APIs.
+  if (
+    !hasNewLifecycles &&
+    (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
+      typeof instance.componentWillReceiveProps === "function")
+  ) {
+    if (oldProps !== newProps || oldContext !== newContext) {
+      callComponentWillReceiveProps(
+        workInProgress,
+        instance,
+        newProps,
+        newContext
+      );
+    }
   }
-  newChild.sibling = null;
-}
 
-var getCurrentFiberStackAddendum =
-  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+  resetHasForceUpdateBeforeProcessing();
 
-var didWarnAboutBadClass = void 0;
-var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
-var didWarnAboutStatelessRefs = void 0;
+  var oldState = workInProgress.memoizedState;
+  var newState = (instance.state = oldState);
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null) {
+    processUpdateQueue(
+      workInProgress,
+      updateQueue,
+      newProps,
+      instance,
+      renderExpirationTime
+    );
+    newState = workInProgress.memoizedState;
+  }
+  if (
+    oldProps === newProps &&
+    oldState === newState &&
+    !hasContextChanged() &&
+    !checkHasForceUpdateAfterProcessing()
+  ) {
+    // If an update was already in progress, we should schedule an Update
+    // effect even though we're bailing out, so that cWU/cDU are called.
+    if (typeof instance.componentDidMount === "function") {
+      workInProgress.effectTag |= Update;
+    }
+    return false;
+  }
 
-{
-  didWarnAboutBadClass = {};
-  didWarnAboutGetDerivedStateOnFunctionalComponent = {};
-  didWarnAboutStatelessRefs = {};
-}
+  if (typeof getDerivedStateFromProps === "function") {
+    applyDerivedStateFromProps(
+      workInProgress,
+      getDerivedStateFromProps,
+      newProps
+    );
+    newState = workInProgress.memoizedState;
+  }
 
-var ReactFiberBeginWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  profilerTimer,
-  recalculateCurrentTime
-) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree;
-  var pushHostContext = hostContext.pushHostContext,
-    pushHostContainer = hostContext.pushHostContainer;
-  var pushProvider = newContext.pushProvider,
-    getContextCurrentValue = newContext.getContextCurrentValue,
-    getContextChangedBits = newContext.getContextChangedBits;
-  var markActualRenderTimeStarted = profilerTimer.markActualRenderTimeStarted,
-    stopBaseRenderTimerIfRunning = profilerTimer.stopBaseRenderTimerIfRunning;
-  var getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    hasLegacyContextChanged = legacyContext.hasContextChanged,
-    pushLegacyContextProvider = legacyContext.pushContextProvider,
-    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
-    invalidateContextProvider = legacyContext.invalidateContextProvider;
-  var enterHydrationState = hydrationContext.enterHydrationState,
-    resetHydrationState = hydrationContext.resetHydrationState,
-    tryToClaimNextHydratableInstance =
-      hydrationContext.tryToClaimNextHydratableInstance;
-
-  var _ReactFiberClassCompo = ReactFiberClassComponent(
-      legacyContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      memoizeProps,
-      memoizeState,
-      recalculateCurrentTime
-    ),
-    adoptClassInstance = _ReactFiberClassCompo.adoptClassInstance,
-    constructClassInstance = _ReactFiberClassCompo.constructClassInstance,
-    mountClassInstance = _ReactFiberClassCompo.mountClassInstance,
-    resumeMountClassInstance = _ReactFiberClassCompo.resumeMountClassInstance,
-    updateClassInstance = _ReactFiberClassCompo.updateClassInstance;
-
-  // TODO: Remove this and use reconcileChildrenAtExpirationTime directly.
-
-  function reconcileChildren(current, workInProgress, nextChildren) {
-    reconcileChildrenAtExpirationTime(
-      current,
+  var shouldUpdate =
+    checkHasForceUpdateAfterProcessing() ||
+    checkShouldComponentUpdate(
       workInProgress,
-      nextChildren,
-      workInProgress.expirationTime
+      oldProps,
+      newProps,
+      oldState,
+      newState,
+      newContext
     );
+
+  if (shouldUpdate) {
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      !hasNewLifecycles &&
+      (typeof instance.UNSAFE_componentWillMount === "function" ||
+        typeof instance.componentWillMount === "function")
+    ) {
+      startPhaseTimer(workInProgress, "componentWillMount");
+      if (typeof instance.componentWillMount === "function") {
+        instance.componentWillMount();
+      }
+      if (typeof instance.UNSAFE_componentWillMount === "function") {
+        instance.UNSAFE_componentWillMount();
+      }
+      stopPhaseTimer();
+    }
+    if (typeof instance.componentDidMount === "function") {
+      workInProgress.effectTag |= Update;
+    }
+  } else {
+    // If an update was already in progress, we should schedule an Update
+    // effect even though we're bailing out, so that cWU/cDU are called.
+    if (typeof instance.componentDidMount === "function") {
+      workInProgress.effectTag |= Update;
+    }
+
+    // If shouldComponentUpdate returned false, we should still update the
+    // memoized state to indicate that this work can be reused.
+    workInProgress.memoizedProps = newProps;
+    workInProgress.memoizedState = newState;
   }
 
-  function reconcileChildrenAtExpirationTime(
-    current,
-    workInProgress,
-    nextChildren,
-    renderExpirationTime
-  ) {
-    if (current === null) {
-      // If this is a fresh new component that hasn't been rendered yet, we
-      // won't update its child set by applying minimal side-effects. Instead,
-      // we will add them all to the child before it gets rendered. That means
-      // we can optimize this reconciliation pass by not tracking side-effects.
-      workInProgress.child = mountChildFibers(
-        workInProgress,
-        null,
-        nextChildren,
-        renderExpirationTime
-      );
-    } else {
-      // If the current child is the same as the work in progress, it means that
-      // we haven't yet started any work on these children. Therefore, we use
-      // the clone algorithm to create a copy of all the current children.
+  // Update the existing instance's state, props, and context pointers even
+  // if shouldComponentUpdate returns false.
+  instance.props = newProps;
+  instance.state = newState;
+  instance.context = newContext;
+
+  return shouldUpdate;
+}
 
-      // If we had any progressed work already, that is invalid at this point so
-      // let's throw it out.
-      workInProgress.child = reconcileChildFibers(
+// Invokes the update life-cycles and returns false if it shouldn't rerender.
+function updateClassInstance(current, workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type;
+  var instance = workInProgress.stateNode;
+
+  var oldProps = workInProgress.memoizedProps;
+  var newProps = workInProgress.pendingProps;
+  instance.props = oldProps;
+
+  var oldContext = instance.context;
+  var newUnmaskedContext = getUnmaskedContext(workInProgress);
+  var newContext = getMaskedContext(workInProgress, newUnmaskedContext);
+
+  var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
+  var hasNewLifecycles =
+    typeof getDerivedStateFromProps === "function" ||
+    typeof instance.getSnapshotBeforeUpdate === "function";
+
+  // Note: During these life-cycles, instance.props/instance.state are what
+  // ever the previously attempted to render - not the "current". However,
+  // during componentDidUpdate we pass the "current" props.
+
+  // In order to support react-lifecycles-compat polyfilled components,
+  // Unsafe lifecycles should not be invoked for components using the new APIs.
+  if (
+    !hasNewLifecycles &&
+    (typeof instance.UNSAFE_componentWillReceiveProps === "function" ||
+      typeof instance.componentWillReceiveProps === "function")
+  ) {
+    if (oldProps !== newProps || oldContext !== newContext) {
+      callComponentWillReceiveProps(
         workInProgress,
-        current.child,
-        nextChildren,
-        renderExpirationTime
+        instance,
+        newProps,
+        newContext
       );
     }
   }
 
-  function updateForwardRef(current, workInProgress) {
-    var render = workInProgress.type.render;
-    var nextProps = workInProgress.pendingProps;
-    var ref = workInProgress.ref;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextProps) {
-      var currentRef = current !== null ? current.ref : null;
-      if (ref === currentRef) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-    }
-
-    var nextChildren = void 0;
-    {
-      ReactCurrentOwner.current = workInProgress;
-      ReactDebugCurrentFiber.setCurrentPhase("render");
-      nextChildren = render(nextProps, ref);
-      ReactDebugCurrentFiber.setCurrentPhase(null);
-    }
+  resetHasForceUpdateBeforeProcessing();
 
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
+  var oldState = workInProgress.memoizedState;
+  var newState = (instance.state = oldState);
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null) {
+    processUpdateQueue(
+      workInProgress,
+      updateQueue,
+      newProps,
+      instance,
+      renderExpirationTime
+    );
+    newState = workInProgress.memoizedState;
   }
 
-  function updateFragment(current, workInProgress) {
-    var nextChildren = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextChildren) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  if (
+    oldProps === newProps &&
+    oldState === newState &&
+    !hasContextChanged() &&
+    !checkHasForceUpdateAfterProcessing()
+  ) {
+    // If an update was already in progress, we should schedule an Update
+    // effect even though we're bailing out, so that cWU/cDU are called.
+    if (typeof instance.componentDidUpdate === "function") {
+      if (
+        oldProps !== current.memoizedProps ||
+        oldState !== current.memoizedState
+      ) {
+        workInProgress.effectTag |= Update;
+      }
     }
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
+    if (typeof instance.getSnapshotBeforeUpdate === "function") {
+      if (
+        oldProps !== current.memoizedProps ||
+        oldState !== current.memoizedState
+      ) {
+        workInProgress.effectTag |= Snapshot;
+      }
+    }
+    return false;
   }
 
-  function updateMode(current, workInProgress) {
-    var nextChildren = workInProgress.pendingProps.children;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (
-      nextChildren === null ||
-      workInProgress.memoizedProps === nextChildren
-    ) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextChildren);
-    return workInProgress.child;
+  if (typeof getDerivedStateFromProps === "function") {
+    applyDerivedStateFromProps(
+      workInProgress,
+      getDerivedStateFromProps,
+      newProps
+    );
+    newState = workInProgress.memoizedState;
   }
 
-  function updateProfiler(current, workInProgress) {
-    var nextProps = workInProgress.pendingProps;
-    if (enableProfilerTimer) {
-      // Start render timer here and push start time onto queue
-      markActualRenderTimeStarted(workInProgress);
+  var shouldUpdate =
+    checkHasForceUpdateAfterProcessing() ||
+    checkShouldComponentUpdate(
+      workInProgress,
+      oldProps,
+      newProps,
+      oldState,
+      newState,
+      newContext
+    );
 
-      // Let the "complete" phase know to stop the timer,
-      // And the scheduler to record the measured time.
+  if (shouldUpdate) {
+    // In order to support react-lifecycles-compat polyfilled components,
+    // Unsafe lifecycles should not be invoked for components using the new APIs.
+    if (
+      !hasNewLifecycles &&
+      (typeof instance.UNSAFE_componentWillUpdate === "function" ||
+        typeof instance.componentWillUpdate === "function")
+    ) {
+      startPhaseTimer(workInProgress, "componentWillUpdate");
+      if (typeof instance.componentWillUpdate === "function") {
+        instance.componentWillUpdate(newProps, newState, newContext);
+      }
+      if (typeof instance.UNSAFE_componentWillUpdate === "function") {
+        instance.UNSAFE_componentWillUpdate(newProps, newState, newContext);
+      }
+      stopPhaseTimer();
+    }
+    if (typeof instance.componentDidUpdate === "function") {
       workInProgress.effectTag |= Update;
     }
-    if (workInProgress.memoizedProps === nextProps) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    if (typeof instance.getSnapshotBeforeUpdate === "function") {
+      workInProgress.effectTag |= Snapshot;
     }
-    var nextChildren = nextProps.children;
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
-  }
-
-  function markRef(current, workInProgress) {
-    var ref = workInProgress.ref;
-    if (
-      (current === null && ref !== null) ||
-      (current !== null && current.ref !== ref)
-    ) {
-      // Schedule a Ref effect
-      workInProgress.effectTag |= Ref;
+  } else {
+    // If an update was already in progress, we should schedule an Update
+    // effect even though we're bailing out, so that cWU/cDU are called.
+    if (typeof instance.componentDidUpdate === "function") {
+      if (
+        oldProps !== current.memoizedProps ||
+        oldState !== current.memoizedState
+      ) {
+        workInProgress.effectTag |= Update;
+      }
+    }
+    if (typeof instance.getSnapshotBeforeUpdate === "function") {
+      if (
+        oldProps !== current.memoizedProps ||
+        oldState !== current.memoizedState
+      ) {
+        workInProgress.effectTag |= Snapshot;
+      }
     }
+
+    // If shouldComponentUpdate returned false, we should still update the
+    // memoized props/state to indicate that this work can be reused.
+    workInProgress.memoizedProps = newProps;
+    workInProgress.memoizedState = newState;
   }
 
-  function updateFunctionalComponent(current, workInProgress) {
-    var fn = workInProgress.type;
-    var nextProps = workInProgress.pendingProps;
+  // Update the existing instance's state, props, and context pointers even
+  // if shouldComponentUpdate returns false.
+  instance.props = newProps;
+  instance.state = newState;
+  instance.context = newContext;
 
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else {
-      if (workInProgress.memoizedProps === nextProps) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-      // TODO: consider bringing fn.shouldComponentUpdate() back.
-      // It used to be here.
+  return shouldUpdate;
+}
+
+var getCurrentFiberStackAddendum$2 =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+
+var didWarnAboutMaps = void 0;
+var didWarnAboutStringRefInStrictMode = void 0;
+var ownerHasKeyUseWarning = void 0;
+var ownerHasFunctionTypeWarning = void 0;
+var warnForMissingKey = function(child) {};
+
+{
+  didWarnAboutMaps = false;
+  didWarnAboutStringRefInStrictMode = {};
+
+  /**
+   * Warn if there's no key explicitly set on dynamic arrays of children or
+   * object keys are not valid. This allows us to keep track of children between
+   * updates.
+   */
+  ownerHasKeyUseWarning = {};
+  ownerHasFunctionTypeWarning = {};
+
+  warnForMissingKey = function(child) {
+    if (child === null || typeof child !== "object") {
+      return;
+    }
+    if (!child._store || child._store.validated || child.key != null) {
+      return;
+    }
+    invariant(
+      typeof child._store === "object",
+      "React Component in warnForMissingKey should have a _store. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
+    child._store.validated = true;
+
+    var currentComponentErrorInfo =
+      "Each child in an array or iterator should have a unique " +
+      '"key" prop. See https://fb.me/react-warning-keys for ' +
+      "more information." +
+      (getCurrentFiberStackAddendum$2() || "");
+    if (ownerHasKeyUseWarning[currentComponentErrorInfo]) {
+      return;
     }
+    ownerHasKeyUseWarning[currentComponentErrorInfo] = true;
 
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var context = getMaskedContext(workInProgress, unmaskedContext);
+    warning(
+      false,
+      "Each child in an array or iterator should have a unique " +
+        '"key" prop. See https://fb.me/react-warning-keys for ' +
+        "more information.%s",
+      getCurrentFiberStackAddendum$2()
+    );
+  };
+}
 
-    var nextChildren = void 0;
+var isArray$1 = Array.isArray;
 
+function coerceRef(returnFiber, current, element) {
+  var mixedRef = element.ref;
+  if (
+    mixedRef !== null &&
+    typeof mixedRef !== "function" &&
+    typeof mixedRef !== "object"
+  ) {
     {
-      ReactCurrentOwner.current = workInProgress;
-      ReactDebugCurrentFiber.setCurrentPhase("render");
-      nextChildren = fn(nextProps, context);
-      ReactDebugCurrentFiber.setCurrentPhase(null);
+      if (returnFiber.mode & StrictMode) {
+        var componentName = getComponentName(returnFiber) || "Component";
+        if (!didWarnAboutStringRefInStrictMode[componentName]) {
+          warning(
+            false,
+            'A string ref, "%s", has been found within a strict mode tree. ' +
+              "String refs are a source of potential bugs and should be avoided. " +
+              "We recommend using createRef() instead." +
+              "\n%s" +
+              "\n\nLearn more about using refs safely here:" +
+              "\nhttps://fb.me/react-strict-mode-string-ref",
+            mixedRef,
+            getStackAddendumByWorkInProgressFiber(returnFiber)
+          );
+          didWarnAboutStringRefInStrictMode[componentName] = true;
+        }
+      }
     }
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
-  }
-
-  function updateClassComponent(current, workInProgress, renderExpirationTime) {
-    // Push context providers early to prevent context stack mismatches.
-    // During mounting we don't know the child context yet as the instance doesn't exist.
-    // We will invalidate the child context in finishClassComponent() right after rendering.
-    var hasContext = pushLegacyContextProvider(workInProgress);
-    var shouldUpdate = void 0;
-    if (current === null) {
-      if (workInProgress.stateNode === null) {
-        // In the initial pass we might need to construct the instance.
-        constructClassInstance(
-          workInProgress,
-          workInProgress.pendingProps,
-          renderExpirationTime
-        );
-        mountClassInstance(workInProgress, renderExpirationTime);
 
-        shouldUpdate = true;
-      } else {
-        // In a resume, we'll already have an instance we can reuse.
-        shouldUpdate = resumeMountClassInstance(
-          workInProgress,
-          renderExpirationTime
+    if (element._owner) {
+      var owner = element._owner;
+      var inst = void 0;
+      if (owner) {
+        var ownerFiber = owner;
+        invariant(
+          ownerFiber.tag === ClassComponent,
+          "Stateless function components cannot have refs."
         );
+        inst = ownerFiber.stateNode;
+      }
+      invariant(
+        inst,
+        "Missing owner for string ref %s. This error is likely caused by a " +
+          "bug in React. Please file an issue.",
+        mixedRef
+      );
+      var stringRef = "" + mixedRef;
+      // Check if previous string ref matches new string ref
+      if (
+        current !== null &&
+        current.ref !== null &&
+        typeof current.ref === "function" &&
+        current.ref._stringRef === stringRef
+      ) {
+        return current.ref;
       }
+      var ref = function(value) {
+        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
+        if (value === null) {
+          delete refs[stringRef];
+        } else {
+          refs[stringRef] = value;
+        }
+      };
+      ref._stringRef = stringRef;
+      return ref;
     } else {
-      shouldUpdate = updateClassInstance(
-        current,
-        workInProgress,
-        renderExpirationTime
+      invariant(
+        typeof mixedRef === "string",
+        "Expected ref to be a function or a string."
+      );
+      invariant(
+        element._owner,
+        "Element ref was specified as a string (%s) but no owner was set. This could happen for one of" +
+          " the following reasons:\n" +
+          "1. You may be adding a ref to a functional component\n" +
+          "2. You may be adding a ref to a component that was not created inside a component's render method\n" +
+          "3. You have multiple copies of React loaded\n" +
+          "See https://fb.me/react-refs-must-have-owner for more information.",
+        mixedRef
       );
     }
-    return finishClassComponent(
-      current,
-      workInProgress,
-      shouldUpdate,
-      hasContext,
-      renderExpirationTime
+  }
+  return mixedRef;
+}
+
+function throwOnInvalidObjectType(returnFiber, newChild) {
+  if (returnFiber.type !== "textarea") {
+    var addendum = "";
+    {
+      addendum =
+        " If you meant to render a collection of children, use an array " +
+        "instead." +
+        (getCurrentFiberStackAddendum$2() || "");
+    }
+    invariant(
+      false,
+      "Objects are not valid as a React child (found: %s).%s",
+      Object.prototype.toString.call(newChild) === "[object Object]"
+        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
+        : newChild,
+      addendum
     );
   }
+}
 
-  function finishClassComponent(
-    current,
-    workInProgress,
-    shouldUpdate,
-    hasContext,
-    renderExpirationTime
-  ) {
-    // Refs should update even if shouldComponentUpdate returns false
-    markRef(current, workInProgress);
+function warnOnFunctionType() {
+  var currentComponentErrorInfo =
+    "Functions are not valid as a React child. This may happen if " +
+    "you return a Component instead of <Component /> from render. " +
+    "Or maybe you meant to call this function rather than return it." +
+    (getCurrentFiberStackAddendum$2() || "");
 
-    var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
+  if (ownerHasFunctionTypeWarning[currentComponentErrorInfo]) {
+    return;
+  }
+  ownerHasFunctionTypeWarning[currentComponentErrorInfo] = true;
 
-    if (!shouldUpdate && !didCaptureError) {
-      // Context providers should defer to sCU for rendering
-      if (hasContext) {
-        invalidateContextProvider(workInProgress, false);
-      }
+  warning(
+    false,
+    "Functions are not valid as a React child. This may happen if " +
+      "you return a Component instead of <Component /> from render. " +
+      "Or maybe you meant to call this function rather than return it.%s",
+    getCurrentFiberStackAddendum$2() || ""
+  );
+}
 
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+// This wrapper function exists because I expect to clone the code in each path
+// to be able to optimize each path individually by branching early. This needs
+// a compiler or we can do it manually. Helpers that don't need this branching
+// live outside of this function.
+function ChildReconciler(shouldTrackSideEffects) {
+  function deleteChild(returnFiber, childToDelete) {
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return;
     }
-
-    var ctor = workInProgress.type;
-    var instance = workInProgress.stateNode;
-
-    // Rerender
-    ReactCurrentOwner.current = workInProgress;
-    var nextChildren = void 0;
-    if (
-      didCaptureError &&
-      (!enableGetDerivedStateFromCatch ||
-        typeof ctor.getDerivedStateFromCatch !== "function")
-    ) {
-      // If we captured an error, but getDerivedStateFrom catch is not defined,
-      // unmount all the children. componentDidCatch will schedule an update to
-      // re-render a fallback. This is temporary until we migrate everyone to
-      // the new API.
-      // TODO: Warn in a future release.
-      nextChildren = null;
-
-      if (enableProfilerTimer) {
-        stopBaseRenderTimerIfRunning();
-      }
+    // Deletions are added in reversed order so we add it to the front.
+    // At this point, the return fiber's effect list is empty except for
+    // deletions, so we can just append the deletion to the list. The remaining
+    // effects aren't added until the complete phase. Once we implement
+    // resuming, this may not be true.
+    var last = returnFiber.lastEffect;
+    if (last !== null) {
+      last.nextEffect = childToDelete;
+      returnFiber.lastEffect = childToDelete;
     } else {
-      {
-        ReactDebugCurrentFiber.setCurrentPhase("render");
-        nextChildren = instance.render();
-        if (
-          debugRenderPhaseSideEffects ||
-          (debugRenderPhaseSideEffectsForStrictMode &&
-            workInProgress.mode & StrictMode)
-        ) {
-          instance.render();
-        }
-        ReactDebugCurrentFiber.setCurrentPhase(null);
-      }
-    }
-
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    if (didCaptureError) {
-      // If we're recovering from an error, reconcile twice: first to delete
-      // all the existing children.
-      reconcileChildrenAtExpirationTime(
-        current,
-        workInProgress,
-        null,
-        renderExpirationTime
-      );
-      workInProgress.child = null;
-      // Now we can continue reconciling like normal. This has the effect of
-      // remounting all children regardless of whether their their
-      // identity matches.
+      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
     }
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      renderExpirationTime
-    );
-    // Memoize props and state using the values we just used to render.
-    // TODO: Restructure so we never read values from the instance.
-    memoizeState(workInProgress, instance.state);
-    memoizeProps(workInProgress, instance.props);
+    childToDelete.nextEffect = null;
+    childToDelete.effectTag = Deletion;
+  }
 
-    // The context might have changed so we need to recalculate it.
-    if (hasContext) {
-      invalidateContextProvider(workInProgress, true);
+  function deleteRemainingChildren(returnFiber, currentFirstChild) {
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return null;
     }
 
-    return workInProgress.child;
-  }
-
-  function pushHostRootContext(workInProgress) {
-    var root = workInProgress.stateNode;
-    if (root.pendingContext) {
-      pushTopLevelContextObject(
-        workInProgress,
-        root.pendingContext,
-        root.pendingContext !== root.context
-      );
-    } else if (root.context) {
-      // Should always be set
-      pushTopLevelContextObject(workInProgress, root.context, false);
+    // TODO: For the shouldClone case, this could be micro-optimized a bit by
+    // assuming that after the first child we've already added everything.
+    var childToDelete = currentFirstChild;
+    while (childToDelete !== null) {
+      deleteChild(returnFiber, childToDelete);
+      childToDelete = childToDelete.sibling;
     }
-    pushHostContainer(workInProgress, root.containerInfo);
+    return null;
   }
 
-  function updateHostRoot(current, workInProgress, renderExpirationTime) {
-    pushHostRootContext(workInProgress);
-    var updateQueue = workInProgress.updateQueue;
-    if (updateQueue !== null) {
-      var nextProps = workInProgress.pendingProps;
-      var prevState = workInProgress.memoizedState;
-      var prevChildren = prevState !== null ? prevState.element : null;
-      processUpdateQueue(
-        workInProgress,
-        updateQueue,
-        nextProps,
-        null,
-        renderExpirationTime
-      );
-      var nextState = workInProgress.memoizedState;
-      // Caution: React DevTools currently depends on this property
-      // being called "element".
-      var nextChildren = nextState.element;
-
-      if (nextChildren === prevChildren) {
-        // If the state is the same as before, that's a bailout because we had
-        // no work that expires at this time.
-        resetHydrationState();
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-      var root = workInProgress.stateNode;
-      if (
-        (current === null || current.child === null) &&
-        root.hydrate &&
-        enterHydrationState(workInProgress)
-      ) {
-        // If we don't have any current children this might be the first pass.
-        // We always try to hydrate. If this isn't a hydration pass there won't
-        // be any children to hydrate which is effectively the same thing as
-        // not hydrating.
-
-        // This is a bit of a hack. We track the host root as a placement to
-        // know that we're currently in a mounting state. That way isMounted
-        // works as expected. We must reset this before committing.
-        // TODO: Delete this when we delete isMounted and findDOMNode.
-        workInProgress.effectTag |= Placement;
+  function mapRemainingChildren(returnFiber, currentFirstChild) {
+    // Add the remaining children to a temporary map so that we can find them by
+    // keys quickly. Implicit (null) keys get added to this set with their index
+    var existingChildren = new Map();
 
-        // Ensure that children mount into this root without tracking
-        // side-effects. This ensures that we don't store Placement effects on
-        // nodes that will be hydrated.
-        workInProgress.child = mountChildFibers(
-          workInProgress,
-          null,
-          nextChildren,
-          renderExpirationTime
-        );
+    var existingChild = currentFirstChild;
+    while (existingChild !== null) {
+      if (existingChild.key !== null) {
+        existingChildren.set(existingChild.key, existingChild);
       } else {
-        // Otherwise reset hydration state in case we aborted and resumed another
-        // root.
-        resetHydrationState();
-        reconcileChildren(current, workInProgress, nextChildren);
+        existingChildren.set(existingChild.index, existingChild);
       }
-      return workInProgress.child;
+      existingChild = existingChild.sibling;
     }
-    resetHydrationState();
-    // If there is no update queue, that's a bailout because the root has no props.
-    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    return existingChildren;
   }
 
-  function updateHostComponent(current, workInProgress, renderExpirationTime) {
-    pushHostContext(workInProgress);
+  function useFiber(fiber, pendingProps, expirationTime) {
+    // We currently set sibling to null and index to 0 here because it is easy
+    // to forget to do before returning it. E.g. for the single child case.
+    var clone = createWorkInProgress(fiber, pendingProps, expirationTime);
+    clone.index = 0;
+    clone.sibling = null;
+    return clone;
+  }
 
-    if (current === null) {
-      tryToClaimNextHydratableInstance(workInProgress);
+  function placeChild(newFiber, lastPlacedIndex, newIndex) {
+    newFiber.index = newIndex;
+    if (!shouldTrackSideEffects) {
+      // Noop.
+      return lastPlacedIndex;
     }
-
-    var type = workInProgress.type;
-    var memoizedProps = workInProgress.memoizedProps;
-    var nextProps = workInProgress.pendingProps;
-    var prevProps = current !== null ? current.memoizedProps : null;
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (memoizedProps === nextProps) {
-      var isHidden =
-        workInProgress.mode & AsyncMode &&
-        shouldDeprioritizeSubtree(type, nextProps);
-      if (isHidden) {
-        // Before bailing out, make sure we've deprioritized a hidden component.
-        workInProgress.expirationTime = Never;
-      }
-      if (!isHidden || renderExpirationTime !== Never) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    var current = newFiber.alternate;
+    if (current !== null) {
+      var oldIndex = current.index;
+      if (oldIndex < lastPlacedIndex) {
+        // This is a move.
+        newFiber.effectTag = Placement;
+        return lastPlacedIndex;
+      } else {
+        // This item can stay in place.
+        return oldIndex;
       }
-      // If we're rendering a hidden node at hidden priority, don't bailout. The
-      // parent is complete, but the children may not be.
-    }
-
-    var nextChildren = nextProps.children;
-    var isDirectTextChild = shouldSetTextContent(type, nextProps);
-
-    if (isDirectTextChild) {
-      // We special case a direct text child of a host node. This is a common
-      // case. We won't handle it as a reified child. We will instead handle
-      // this in the host environment that also have access to this prop. That
-      // avoids allocating another HostText fiber and traversing it.
-      nextChildren = null;
-    } else if (prevProps && shouldSetTextContent(type, prevProps)) {
-      // If we're switching from a direct text child to a normal child, or to
-      // empty, we need to schedule the text content to be reset.
-      workInProgress.effectTag |= ContentReset;
+    } else {
+      // This is an insertion.
+      newFiber.effectTag = Placement;
+      return lastPlacedIndex;
     }
+  }
 
-    markRef(current, workInProgress);
-
-    // Check the host config to see if the children are offscreen/hidden.
-    if (
-      renderExpirationTime !== Never &&
-      workInProgress.mode & AsyncMode &&
-      shouldDeprioritizeSubtree(type, nextProps)
-    ) {
-      // Down-prioritize the children.
-      workInProgress.expirationTime = Never;
-      // Bailout and come back to this fiber later.
-      workInProgress.memoizedProps = nextProps;
-      return null;
+  function placeSingleChild(newFiber) {
+    // This is simpler for the single child case. We only need to do a
+    // placement for inserting new children.
+    if (shouldTrackSideEffects && newFiber.alternate === null) {
+      newFiber.effectTag = Placement;
     }
-
-    reconcileChildren(current, workInProgress, nextChildren);
-    memoizeProps(workInProgress, nextProps);
-    return workInProgress.child;
+    return newFiber;
   }
 
-  function updateHostText(current, workInProgress) {
-    if (current === null) {
-      tryToClaimNextHydratableInstance(workInProgress);
+  function updateTextNode(returnFiber, current, textContent, expirationTime) {
+    if (current === null || current.tag !== HostText) {
+      // Insert
+      var created = createFiberFromText(
+        textContent,
+        returnFiber.mode,
+        expirationTime
+      );
+      created.return = returnFiber;
+      return created;
+    } else {
+      // Update
+      var existing = useFiber(current, textContent, expirationTime);
+      existing.return = returnFiber;
+      return existing;
     }
-    var nextProps = workInProgress.pendingProps;
-    memoizeProps(workInProgress, nextProps);
-    // Nothing to do here. This is terminal. We'll do the completion step
-    // immediately after.
-    return null;
   }
 
-  function mountIndeterminateComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    invariant(
-      current === null,
-      "An indeterminate component should never have mounted. This error is " +
-        "likely caused by a bug in React. Please file an issue."
-    );
-    var fn = workInProgress.type;
-    var props = workInProgress.pendingProps;
-    var unmaskedContext = getUnmaskedContext(workInProgress);
-    var context = getMaskedContext(workInProgress, unmaskedContext);
-
-    var value = void 0;
-
-    {
-      if (fn.prototype && typeof fn.prototype.render === "function") {
-        var componentName = getComponentName(workInProgress) || "Unknown";
-
-        if (!didWarnAboutBadClass[componentName]) {
-          warning(
-            false,
-            "The <%s /> component appears to have a render method, but doesn't extend React.Component. " +
-              "This is likely to cause errors. Change %s to extend React.Component instead.",
-            componentName,
-            componentName
-          );
-          didWarnAboutBadClass[componentName] = true;
-        }
+  function updateElement(returnFiber, current, element, expirationTime) {
+    if (current !== null && current.type === element.type) {
+      // Move based on index
+      var existing = useFiber(current, element.props, expirationTime);
+      existing.ref = coerceRef(returnFiber, current, element);
+      existing.return = returnFiber;
+      {
+        existing._debugSource = element._source;
+        existing._debugOwner = element._owner;
       }
-      ReactCurrentOwner.current = workInProgress;
-      value = fn(props, context);
+      return existing;
+    } else {
+      // Insert
+      var created = createFiberFromElement(
+        element,
+        returnFiber.mode,
+        expirationTime
+      );
+      created.ref = coerceRef(returnFiber, current, element);
+      created.return = returnFiber;
+      return created;
     }
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
+  }
 
+  function updatePortal(returnFiber, current, portal, expirationTime) {
     if (
-      typeof value === "object" &&
-      value !== null &&
-      typeof value.render === "function" &&
-      value.$$typeof === undefined
+      current === null ||
+      current.tag !== HostPortal ||
+      current.stateNode.containerInfo !== portal.containerInfo ||
+      current.stateNode.implementation !== portal.implementation
     ) {
-      var Component = workInProgress.type;
-
-      // Proceed under the assumption that this is a class instance
-      workInProgress.tag = ClassComponent;
-
-      workInProgress.memoizedState =
-        value.state !== null && value.state !== undefined ? value.state : null;
-
-      var getDerivedStateFromProps = Component.getDerivedStateFromProps;
-      if (typeof getDerivedStateFromProps === "function") {
-        applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          props
-        );
-      }
-
-      // Push context providers early to prevent context stack mismatches.
-      // During mounting we don't know the child context yet as the instance doesn't exist.
-      // We will invalidate the child context in finishClassComponent() right after rendering.
-      var hasContext = pushLegacyContextProvider(workInProgress);
-      adoptClassInstance(workInProgress, value);
-      mountClassInstance(workInProgress, renderExpirationTime);
-      return finishClassComponent(
-        current,
-        workInProgress,
-        true,
-        hasContext,
-        renderExpirationTime
+      // Insert
+      var created = createFiberFromPortal(
+        portal,
+        returnFiber.mode,
+        expirationTime
       );
+      created.return = returnFiber;
+      return created;
     } else {
-      // Proceed under the assumption that this is a functional component
-      workInProgress.tag = FunctionalComponent;
-      {
-        var _Component = workInProgress.type;
-
-        if (_Component) {
-          !!_Component.childContextTypes
-            ? warning(
-                false,
-                "%s(...): childContextTypes cannot be defined on a functional component.",
-                _Component.displayName || _Component.name || "Component"
-              )
-            : void 0;
-        }
-        if (workInProgress.ref !== null) {
-          var info = "";
-          var ownerName = ReactDebugCurrentFiber.getCurrentFiberOwnerName();
-          if (ownerName) {
-            info += "\n\nCheck the render method of `" + ownerName + "`.";
-          }
-
-          var warningKey = ownerName || workInProgress._debugID || "";
-          var debugSource = workInProgress._debugSource;
-          if (debugSource) {
-            warningKey = debugSource.fileName + ":" + debugSource.lineNumber;
-          }
-          if (!didWarnAboutStatelessRefs[warningKey]) {
-            didWarnAboutStatelessRefs[warningKey] = true;
-            warning(
-              false,
-              "Stateless function components cannot be given refs. " +
-                "Attempts to access this ref will fail.%s%s",
-              info,
-              ReactDebugCurrentFiber.getCurrentFiberStackAddendum()
-            );
-          }
-        }
-
-        if (typeof fn.getDerivedStateFromProps === "function") {
-          var _componentName = getComponentName(workInProgress) || "Unknown";
-
-          if (
-            !didWarnAboutGetDerivedStateOnFunctionalComponent[_componentName]
-          ) {
-            warning(
-              false,
-              "%s: Stateless functional components do not support getDerivedStateFromProps.",
-              _componentName
-            );
-            didWarnAboutGetDerivedStateOnFunctionalComponent[
-              _componentName
-            ] = true;
-          }
-        }
-      }
-      reconcileChildren(current, workInProgress, value);
-      memoizeProps(workInProgress, props);
-      return workInProgress.child;
+      // Update
+      var existing = useFiber(current, portal.children || [], expirationTime);
+      existing.return = returnFiber;
+      return existing;
     }
   }
 
-  function updateTimeoutComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    if (enableSuspense) {
-      var nextProps = workInProgress.pendingProps;
-      var prevProps = workInProgress.memoizedProps;
-
-      var prevDidTimeout = workInProgress.memoizedState;
-
-      // Check if we already attempted to render the normal state. If we did,
-      // and we timed out, render the placeholder state.
-      var alreadyCaptured =
-        (workInProgress.effectTag & DidCapture) === NoEffect;
-      var nextDidTimeout = !alreadyCaptured;
-
-      if (hasLegacyContextChanged()) {
-        // Normally we can bail out on props equality but if context has changed
-        // we don't do the bailout and we have to reuse existing props instead.
-      } else if (nextProps === prevProps && nextDidTimeout === prevDidTimeout) {
-        return bailoutOnAlreadyFinishedWork(current, workInProgress);
-      }
-
-      var render = nextProps.children;
-      var nextChildren = render(nextDidTimeout);
-      workInProgress.memoizedProps = nextProps;
-      workInProgress.memoizedState = nextDidTimeout;
-      reconcileChildren(current, workInProgress, nextChildren);
-      return workInProgress.child;
+  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
+    if (current === null || current.tag !== Fragment) {
+      // Insert
+      var created = createFiberFromFragment(
+        fragment,
+        returnFiber.mode,
+        expirationTime,
+        key
+      );
+      created.return = returnFiber;
+      return created;
     } else {
-      return null;
+      // Update
+      var existing = useFiber(current, fragment, expirationTime);
+      existing.return = returnFiber;
+      return existing;
     }
   }
 
-  function updatePortalComponent(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
-    var nextChildren = workInProgress.pendingProps;
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (workInProgress.memoizedProps === nextChildren) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-
-    if (current === null) {
-      // Portals are special because we don't append the children during mount
-      // but at commit. Therefore we need to track insertions which the normal
-      // flow doesn't do during mount. This doesn't happen at the root because
-      // the root always starts with a "current" with a null child.
-      // TODO: Consider unifying this with how the root works.
-      workInProgress.child = reconcileChildFibers(
-        workInProgress,
-        null,
-        nextChildren,
-        renderExpirationTime
+  function createChild(returnFiber, newChild, expirationTime) {
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys. If the previous node is implicitly keyed
+      // we can continue to replace it without aborting even if it is not a text
+      // node.
+      var created = createFiberFromText(
+        "" + newChild,
+        returnFiber.mode,
+        expirationTime
       );
-      memoizeProps(workInProgress, nextChildren);
-    } else {
-      reconcileChildren(current, workInProgress, nextChildren);
-      memoizeProps(workInProgress, nextChildren);
+      created.return = returnFiber;
+      return created;
     }
-    return workInProgress.child;
-  }
 
-  function propagateContextChange(
-    workInProgress,
-    context,
-    changedBits,
-    renderExpirationTime
-  ) {
-    var fiber = workInProgress.child;
-    if (fiber !== null) {
-      // Set the return pointer of the child to the work-in-progress fiber.
-      fiber.return = workInProgress;
-    }
-    while (fiber !== null) {
-      var nextFiber = void 0;
-      // Visit this fiber.
-      switch (fiber.tag) {
-        case ContextConsumer:
-          // Check if the context matches.
-          var observedBits = fiber.stateNode | 0;
-          if (fiber.type === context && (observedBits & changedBits) !== 0) {
-            // Update the expiration time of all the ancestors, including
-            // the alternates.
-            var node = fiber;
-            while (node !== null) {
-              var alternate = node.alternate;
-              if (
-                node.expirationTime === NoWork ||
-                node.expirationTime > renderExpirationTime
-              ) {
-                node.expirationTime = renderExpirationTime;
-                if (
-                  alternate !== null &&
-                  (alternate.expirationTime === NoWork ||
-                    alternate.expirationTime > renderExpirationTime)
-                ) {
-                  alternate.expirationTime = renderExpirationTime;
-                }
-              } else if (
-                alternate !== null &&
-                (alternate.expirationTime === NoWork ||
-                  alternate.expirationTime > renderExpirationTime)
-              ) {
-                alternate.expirationTime = renderExpirationTime;
-              } else {
-                // Neither alternate was updated, which means the rest of the
-                // ancestor path already has sufficient priority.
-                break;
-              }
-              node = node.return;
-            }
-            // Don't scan deeper than a matching consumer. When we render the
-            // consumer, we'll continue scanning from that point. This way the
-            // scanning work is time-sliced.
-            nextFiber = null;
-          } else {
-            // Traverse down.
-            nextFiber = fiber.child;
-          }
-          break;
-        case ContextProvider:
-          // Don't scan deeper if this is a matching provider
-          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
-          break;
-        default:
-          // Traverse down.
-          nextFiber = fiber.child;
-          break;
-      }
-      if (nextFiber !== null) {
-        // Set the return pointer of the child to the work-in-progress fiber.
-        nextFiber.return = fiber;
-      } else {
-        // No child. Traverse to next sibling.
-        nextFiber = fiber;
-        while (nextFiber !== null) {
-          if (nextFiber === workInProgress) {
-            // We're back to the root of this subtree. Exit.
-            nextFiber = null;
-            break;
-          }
-          var sibling = nextFiber.sibling;
-          if (sibling !== null) {
-            // Set the return pointer of the sibling to the work-in-progress fiber.
-            sibling.return = nextFiber.return;
-            nextFiber = sibling;
-            break;
-          }
-          // No more siblings. Traverse up.
-          nextFiber = nextFiber.return;
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          var _created = createFiberFromElement(
+            newChild,
+            returnFiber.mode,
+            expirationTime
+          );
+          _created.ref = coerceRef(returnFiber, null, newChild);
+          _created.return = returnFiber;
+          return _created;
+        }
+        case REACT_PORTAL_TYPE: {
+          var _created2 = createFiberFromPortal(
+            newChild,
+            returnFiber.mode,
+            expirationTime
+          );
+          _created2.return = returnFiber;
+          return _created2;
         }
       }
-      fiber = nextFiber;
-    }
-  }
 
-  function updateContextProvider(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var providerType = workInProgress.type;
-    var context = providerType._context;
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        var _created3 = createFiberFromFragment(
+          newChild,
+          returnFiber.mode,
+          expirationTime,
+          null
+        );
+        _created3.return = returnFiber;
+        return _created3;
+      }
 
-    var newProps = workInProgress.pendingProps;
-    var oldProps = workInProgress.memoizedProps;
-    var canBailOnProps = true;
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
 
-    if (hasLegacyContextChanged()) {
-      canBailOnProps = false;
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (oldProps === newProps) {
-      workInProgress.stateNode = 0;
-      pushProvider(workInProgress);
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
     }
 
-    var newValue = newProps.value;
-    workInProgress.memoizedProps = newProps;
+    return null;
+  }
 
-    {
-      var providerPropTypes = workInProgress.type.propTypes;
+  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
+    // Update the fiber if the keys match, otherwise return null.
 
-      if (providerPropTypes) {
-        checkPropTypes(
-          providerPropTypes,
-          newProps,
-          "prop",
-          "Context.Provider",
-          getCurrentFiberStackAddendum
-        );
+    var key = oldFiber !== null ? oldFiber.key : null;
+
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys. If the previous node is implicitly keyed
+      // we can continue to replace it without aborting even if it is not a text
+      // node.
+      if (key !== null) {
+        return null;
       }
+      return updateTextNode(
+        returnFiber,
+        oldFiber,
+        "" + newChild,
+        expirationTime
+      );
     }
 
-    var changedBits = void 0;
-    if (oldProps === null) {
-      // Initial render
-      changedBits = MAX_SIGNED_31_BIT_INT;
-    } else {
-      if (oldProps.value === newProps.value) {
-        // No change. Bailout early if children are the same.
-        if (oldProps.children === newProps.children && canBailOnProps) {
-          workInProgress.stateNode = 0;
-          pushProvider(workInProgress);
-          return bailoutOnAlreadyFinishedWork(current, workInProgress);
-        }
-        changedBits = 0;
-      } else {
-        var oldValue = oldProps.value;
-        // Use Object.is to compare the new context value to the old value.
-        // Inlined Object.is polyfill.
-        // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
-        if (
-          (oldValue === newValue &&
-            (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
-          (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
-        ) {
-          // No change. Bailout early if children are the same.
-          if (oldProps.children === newProps.children && canBailOnProps) {
-            workInProgress.stateNode = 0;
-            pushProvider(workInProgress);
-            return bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
-          changedBits = 0;
-        } else {
-          changedBits =
-            typeof context._calculateChangedBits === "function"
-              ? context._calculateChangedBits(oldValue, newValue)
-              : MAX_SIGNED_31_BIT_INT;
-          {
-            !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
-              ? warning(
-                  false,
-                  "calculateChangedBits: Expected the return value to be a " +
-                    "31-bit integer. Instead received: %s",
-                  changedBits
-                )
-              : void 0;
-          }
-          changedBits |= 0;
-
-          if (changedBits === 0) {
-            // No change. Bailout early if children are the same.
-            if (oldProps.children === newProps.children && canBailOnProps) {
-              workInProgress.stateNode = 0;
-              pushProvider(workInProgress);
-              return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          if (newChild.key === key) {
+            if (newChild.type === REACT_FRAGMENT_TYPE) {
+              return updateFragment(
+                returnFiber,
+                oldFiber,
+                newChild.props.children,
+                expirationTime,
+                key
+              );
             }
+            return updateElement(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime
+            );
           } else {
-            propagateContextChange(
-              workInProgress,
-              context,
-              changedBits,
-              renderExpirationTime
+            return null;
+          }
+        }
+        case REACT_PORTAL_TYPE: {
+          if (newChild.key === key) {
+            return updatePortal(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime
             );
+          } else {
+            return null;
           }
         }
       }
+
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        if (key !== null) {
+          return null;
+        }
+
+        return updateFragment(
+          returnFiber,
+          oldFiber,
+          newChild,
+          expirationTime,
+          null
+        );
+      }
+
+      throwOnInvalidObjectType(returnFiber, newChild);
     }
 
-    workInProgress.stateNode = changedBits;
-    pushProvider(workInProgress);
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
+    }
 
-    var newChildren = newProps.children;
-    reconcileChildren(current, workInProgress, newChildren);
-    return workInProgress.child;
+    return null;
   }
 
-  function updateContextConsumer(
-    current,
-    workInProgress,
-    renderExpirationTime
+  function updateFromMap(
+    existingChildren,
+    returnFiber,
+    newIdx,
+    newChild,
+    expirationTime
   ) {
-    var context = workInProgress.type;
-    var newProps = workInProgress.pendingProps;
-    var oldProps = workInProgress.memoizedProps;
-
-    var newValue = getContextCurrentValue(context);
-    var changedBits = getContextChangedBits(context);
-
-    if (hasLegacyContextChanged()) {
-      // Normally we can bail out on props equality but if context has changed
-      // we don't do the bailout and we have to reuse existing props instead.
-    } else if (changedBits === 0 && oldProps === newProps) {
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    workInProgress.memoizedProps = newProps;
-
-    var observedBits = newProps.unstable_observedBits;
-    if (observedBits === undefined || observedBits === null) {
-      // Subscribe to all changes by default
-      observedBits = MAX_SIGNED_31_BIT_INT;
-    }
-    // Store the observedBits on the fiber's stateNode for quick access.
-    workInProgress.stateNode = observedBits;
-
-    if ((changedBits & observedBits) !== 0) {
-      // Context change propagation stops at matching consumers, for time-
-      // slicing. Continue the propagation here.
-      propagateContextChange(
-        workInProgress,
-        context,
-        changedBits,
-        renderExpirationTime
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      // Text nodes don't have keys, so we neither have to check the old nor
+      // new node for the key. If both are text nodes, they match.
+      var matchedFiber = existingChildren.get(newIdx) || null;
+      return updateTextNode(
+        returnFiber,
+        matchedFiber,
+        "" + newChild,
+        expirationTime
       );
-    } else if (oldProps === newProps) {
-      // Skip over a memoized parent with a bitmask bailout even
-      // if we began working on it because of a deeper matching child.
-      return bailoutOnAlreadyFinishedWork(current, workInProgress);
-    }
-    // There is no bailout on `children` equality because we expect people
-    // to often pass a bound method as a child, but it may reference
-    // `this.state` or `this.props` (and thus needs to re-render on `setState`).
-
-    var render = newProps.children;
-
-    {
-      !(typeof render === "function")
-        ? warning(
-            false,
-            "A context consumer was rendered with multiple children, or a child " +
-              "that isn't a function. A context consumer expects a single child " +
-              "that is a function. If you did pass a function, make sure there " +
-              "is no trailing or leading whitespace around it."
-          )
-        : void 0;
-    }
-
-    var newChildren = void 0;
-    {
-      ReactCurrentOwner.current = workInProgress;
-      ReactDebugCurrentFiber.setCurrentPhase("render");
-      newChildren = render(newValue);
-      ReactDebugCurrentFiber.setCurrentPhase(null);
     }
 
-    // React DevTools reads this flag.
-    workInProgress.effectTag |= PerformedWork;
-    reconcileChildren(current, workInProgress, newChildren);
-    return workInProgress.child;
-  }
-
-  /*
-  function reuseChildrenEffects(returnFiber : Fiber, firstChild : Fiber) {
-    let child = firstChild;
-    do {
-      // Ensure that the first and last effect of the parent corresponds
-      // to the children's first and last effect.
-      if (!returnFiber.firstEffect) {
-        returnFiber.firstEffect = child.firstEffect;
-      }
-      if (child.lastEffect) {
-        if (returnFiber.lastEffect) {
-          returnFiber.lastEffect.nextEffect = child.firstEffect;
+    if (typeof newChild === "object" && newChild !== null) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE: {
+          var _matchedFiber =
+            existingChildren.get(
+              newChild.key === null ? newIdx : newChild.key
+            ) || null;
+          if (newChild.type === REACT_FRAGMENT_TYPE) {
+            return updateFragment(
+              returnFiber,
+              _matchedFiber,
+              newChild.props.children,
+              expirationTime,
+              newChild.key
+            );
+          }
+          return updateElement(
+            returnFiber,
+            _matchedFiber,
+            newChild,
+            expirationTime
+          );
+        }
+        case REACT_PORTAL_TYPE: {
+          var _matchedFiber2 =
+            existingChildren.get(
+              newChild.key === null ? newIdx : newChild.key
+            ) || null;
+          return updatePortal(
+            returnFiber,
+            _matchedFiber2,
+            newChild,
+            expirationTime
+          );
         }
-        returnFiber.lastEffect = child.lastEffect;
       }
-    } while (child = child.sibling);
-  }
-  */
 
-  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
-    cancelWorkTimer(workInProgress);
+      if (isArray$1(newChild) || getIteratorFn(newChild)) {
+        var _matchedFiber3 = existingChildren.get(newIdx) || null;
+        return updateFragment(
+          returnFiber,
+          _matchedFiber3,
+          newChild,
+          expirationTime,
+          null
+        );
+      }
 
-    if (enableProfilerTimer) {
-      // Don't update "base" render times for bailouts.
-      stopBaseRenderTimerIfRunning();
+      throwOnInvalidObjectType(returnFiber, newChild);
     }
 
-    // TODO: We should ideally be able to bail out early if the children have no
-    // more work to do. However, since we don't have a separation of this
-    // Fiber's priority and its children yet - we don't know without doing lots
-    // of the same work we do anyway. Once we have that separation we can just
-    // bail out here if the children has no more work at this priority level.
-    // if (workInProgress.priorityOfChildren <= priorityLevel) {
-    //   // If there are side-effects in these children that have not yet been
-    //   // committed we need to ensure that they get properly transferred up.
-    //   if (current && current.child !== workInProgress.child) {
-    //     reuseChildrenEffects(workInProgress, child);
-    //   }
-    //   return null;
-    // }
-
-    cloneChildFibers(current, workInProgress);
-    return workInProgress.child;
-  }
-
-  function bailoutOnLowPriority(current, workInProgress) {
-    cancelWorkTimer(workInProgress);
-
-    if (enableProfilerTimer) {
-      // Don't update "base" render times for bailouts.
-      stopBaseRenderTimerIfRunning();
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
+      }
     }
 
-    // TODO: Handle HostComponent tags here as well and call pushHostContext()?
-    // See PR 8590 discussion for context
-    switch (workInProgress.tag) {
-      case HostRoot:
-        pushHostRootContext(workInProgress);
-        break;
-      case ClassComponent:
-        pushLegacyContextProvider(workInProgress);
-        break;
-      case HostPortal:
-        pushHostContainer(
-          workInProgress,
-          workInProgress.stateNode.containerInfo
-        );
-        break;
-      case ContextProvider:
-        pushProvider(workInProgress);
-        break;
-      case Profiler:
-        if (enableProfilerTimer) {
-          markActualRenderTimeStarted(workInProgress);
-        }
-        break;
-    }
-    // TODO: What if this is currently in progress?
-    // How can that happen? How is this not being cloned?
     return null;
   }
 
-  // TODO: Delete memoizeProps/State and move to reconcile/bailout instead
-  function memoizeProps(workInProgress, nextProps) {
-    workInProgress.memoizedProps = nextProps;
-  }
-
-  function memoizeState(workInProgress, nextState) {
-    workInProgress.memoizedState = nextState;
-    // Don't reset the updateQueue, in case there are pending updates. Resetting
-    // is handled by processUpdateQueue.
+  /**
+   * Warns if there is a duplicate or missing key
+   */
+  function warnOnInvalidKey(child, knownKeys) {
+    {
+      if (typeof child !== "object" || child === null) {
+        return knownKeys;
+      }
+      switch (child.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+        case REACT_PORTAL_TYPE:
+          warnForMissingKey(child);
+          var key = child.key;
+          if (typeof key !== "string") {
+            break;
+          }
+          if (knownKeys === null) {
+            knownKeys = new Set();
+            knownKeys.add(key);
+            break;
+          }
+          if (!knownKeys.has(key)) {
+            knownKeys.add(key);
+            break;
+          }
+          warning(
+            false,
+            "Encountered two children with the same key, `%s`. " +
+              "Keys should be unique so that components maintain their identity " +
+              "across updates. Non-unique keys may cause children to be " +
+              "duplicated and/or omitted — the behavior is unsupported and " +
+              "could change in a future version.%s",
+            key,
+            getCurrentFiberStackAddendum$2()
+          );
+          break;
+        default:
+          break;
+      }
+    }
+    return knownKeys;
   }
 
-  function beginWork(current, workInProgress, renderExpirationTime) {
-    if (
-      workInProgress.expirationTime === NoWork ||
-      workInProgress.expirationTime > renderExpirationTime
-    ) {
-      return bailoutOnLowPriority(current, workInProgress);
-    }
+  function reconcileChildrenArray(
+    returnFiber,
+    currentFirstChild,
+    newChildren,
+    expirationTime
+  ) {
+    // This algorithm can't optimize by searching from boths ends since we
+    // don't have backpointers on fibers. I'm trying to see how far we can get
+    // with that model. If it ends up not being worth the tradeoffs, we can
+    // add it later.
 
-    switch (workInProgress.tag) {
-      case IndeterminateComponent:
-        return mountIndeterminateComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case FunctionalComponent:
-        return updateFunctionalComponent(current, workInProgress);
-      case ClassComponent:
-        return updateClassComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostRoot:
-        return updateHostRoot(current, workInProgress, renderExpirationTime);
-      case HostComponent:
-        return updateHostComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostText:
-        return updateHostText(current, workInProgress);
-      case TimeoutComponent:
-        return updateTimeoutComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case HostPortal:
-        return updatePortalComponent(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ForwardRef:
-        return updateForwardRef(current, workInProgress);
-      case Fragment:
-        return updateFragment(current, workInProgress);
-      case Mode:
-        return updateMode(current, workInProgress);
-      case Profiler:
-        return updateProfiler(current, workInProgress);
-      case ContextProvider:
-        return updateContextProvider(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      case ContextConsumer:
-        return updateContextConsumer(
-          current,
-          workInProgress,
-          renderExpirationTime
-        );
-      default:
-        invariant(
-          false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
-        );
-    }
-  }
+    // Even with a two ended optimization, we'd want to optimize for the case
+    // where there are few changes and brute force the comparison instead of
+    // going for the Map. It'd like to explore hitting that path first in
+    // forward-only mode and only go for the Map once we notice that we need
+    // lots of look ahead. This doesn't handle reversal as well as two ended
+    // search but that's unusual. Besides, for the two ended optimization to
+    // work on Iterables, we'd need to copy the whole set.
 
-  return {
-    beginWork: beginWork
-  };
-};
+    // In this first iteration, we'll just live with hitting the bad case
+    // (adding everything to a Map) in for every insert/move.
 
-var ReactFiberCompleteWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  profilerTimer
-) {
-  var createInstance = config.createInstance,
-    createTextInstance = config.createTextInstance,
-    appendInitialChild = config.appendInitialChild,
-    finalizeInitialChildren = config.finalizeInitialChildren,
-    prepareUpdate = config.prepareUpdate,
-    mutation = config.mutation,
-    persistence = config.persistence;
-  var getRootHostContainer = hostContext.getRootHostContainer,
-    popHostContext = hostContext.popHostContext,
-    getHostContext = hostContext.getHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var recordElapsedActualRenderTime =
-    profilerTimer.recordElapsedActualRenderTime;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-  var prepareToHydrateHostInstance =
-      hydrationContext.prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance =
-      hydrationContext.prepareToHydrateHostTextInstance,
-    popHydrationState = hydrationContext.popHydrationState;
-
-  function markUpdate(workInProgress) {
-    // Tag the fiber with an update effect. This turns a Placement into
-    // a PlacementAndUpdate.
-    workInProgress.effectTag |= Update;
-  }
+    // If you change this code, also update reconcileChildrenIterator() which
+    // uses the same algorithm.
 
-  function markRef(workInProgress) {
-    workInProgress.effectTag |= Ref;
-  }
+    {
+      // First, validate keys.
+      var knownKeys = null;
+      for (var i = 0; i < newChildren.length; i++) {
+        var child = newChildren[i];
+        knownKeys = warnOnInvalidKey(child, knownKeys);
+      }
+    }
 
-  function appendAllChildren(parent, workInProgress) {
-    // We only have the top Fiber that was created but we need recurse down its
-    // children to find all the terminal nodes.
-    var node = workInProgress.child;
-    while (node !== null) {
-      if (node.tag === HostComponent || node.tag === HostText) {
-        appendInitialChild(parent, node.stateNode);
-      } else if (node.tag === HostPortal) {
-        // If we have a portal child, then we don't want to traverse
-        // down its children. Instead, we'll get insertions from each child in
-        // the portal directly.
-      } else if (node.child !== null) {
-        node.child.return = node;
-        node = node.child;
-        continue;
+    var resultingFirstChild = null;
+    var previousNewFiber = null;
+
+    var oldFiber = currentFirstChild;
+    var lastPlacedIndex = 0;
+    var newIdx = 0;
+    var nextOldFiber = null;
+    for (; oldFiber !== null && newIdx < newChildren.length; newIdx++) {
+      if (oldFiber.index > newIdx) {
+        nextOldFiber = oldFiber;
+        oldFiber = null;
+      } else {
+        nextOldFiber = oldFiber.sibling;
       }
-      if (node === workInProgress) {
-        return;
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (newFiber === null) {
+        // TODO: This breaks on empty slots like null children. That's
+        // unfortunate because it triggers the slow path all the time. We need
+        // a better way to communicate whether this was a miss or null,
+        // boolean, undefined, etc.
+        if (oldFiber === null) {
+          oldFiber = nextOldFiber;
+        }
+        break;
       }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === workInProgress) {
-          return;
+      if (shouldTrackSideEffects) {
+        if (oldFiber && newFiber.alternate === null) {
+          // We matched the slot, but we didn't reuse the existing fiber, so we
+          // need to delete the existing child.
+          deleteChild(returnFiber, oldFiber);
         }
-        node = node.return;
       }
-      node.sibling.return = node.return;
-      node = node.sibling;
+      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
+      if (previousNewFiber === null) {
+        // TODO: Move out of the loop. This only happens for the first run.
+        resultingFirstChild = newFiber;
+      } else {
+        // TODO: Defer siblings if we're not at the right index for this slot.
+        // I.e. if we had null values before, then we want to defer this
+        // for each null value. However, we also don't want to call updateSlot
+        // with the previous one.
+        previousNewFiber.sibling = newFiber;
+      }
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
     }
-  }
 
-  var updateHostContainer = void 0;
-  var updateHostComponent = void 0;
-  var updateHostText = void 0;
-  if (mutation) {
-    if (enableMutatingReconciler) {
-      // Mutation mode
-      updateHostContainer = function(workInProgress) {
-        // Noop
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // TODO: Type this specific to this type of component.
-        workInProgress.updateQueue = updatePayload;
-        // If the update payload indicates that there is a change or if there
-        // is a new ref we mark this as an update. All the work is done in commitWork.
-        if (updatePayload) {
-          markUpdate(workInProgress);
-        }
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        // If the text differs, mark it as an update. All the work in done in commitWork.
-        if (oldText !== newText) {
-          markUpdate(workInProgress);
-        }
-      };
-    } else {
-      invariant(false, "Mutating reconciler is disabled.");
+    if (newIdx === newChildren.length) {
+      // We've reached the end of the new children. We can delete the rest.
+      deleteRemainingChildren(returnFiber, oldFiber);
+      return resultingFirstChild;
     }
-  } else if (persistence) {
-    if (enablePersistentReconciler) {
-      // Persistent host tree mode
-      var cloneInstance = persistence.cloneInstance,
-        createContainerChildSet = persistence.createContainerChildSet,
-        appendChildToContainerChildSet =
-          persistence.appendChildToContainerChildSet,
-        finalizeContainerChildren = persistence.finalizeContainerChildren;
-
-      // An unfortunate fork of appendAllChildren because we have two different parent types.
 
-      var appendAllChildrenToContainer = function(
-        containerChildSet,
-        workInProgress
-      ) {
-        // We only have the top Fiber that was created but we need recurse down its
-        // children to find all the terminal nodes.
-        var node = workInProgress.child;
-        while (node !== null) {
-          if (node.tag === HostComponent || node.tag === HostText) {
-            appendChildToContainerChildSet(containerChildSet, node.stateNode);
-          } else if (node.tag === HostPortal) {
-            // If we have a portal child, then we don't want to traverse
-            // down its children. Instead, we'll get insertions from each child in
-            // the portal directly.
-          } else if (node.child !== null) {
-            node.child.return = node;
-            node = node.child;
-            continue;
-          }
-          if (node === workInProgress) {
-            return;
-          }
-          while (node.sibling === null) {
-            if (node.return === null || node.return === workInProgress) {
-              return;
-            }
-            node = node.return;
-          }
-          node.sibling.return = node.return;
-          node = node.sibling;
-        }
-      };
-      updateHostContainer = function(workInProgress) {
-        var portalOrRoot = workInProgress.stateNode;
-        var childrenUnchanged = workInProgress.firstEffect === null;
-        if (childrenUnchanged) {
-          // No changes, just reuse the existing instance.
-        } else {
-          var container = portalOrRoot.containerInfo;
-          var newChildSet = createContainerChildSet(container);
-          // If children might have changed, we have to add them all to the set.
-          appendAllChildrenToContainer(newChildSet, workInProgress);
-          portalOrRoot.pendingChildren = newChildSet;
-          // Schedule an update on the container to swap out the container.
-          markUpdate(workInProgress);
-          finalizeContainerChildren(container, newChildSet);
+    if (oldFiber === null) {
+      // If we don't have any more existing children we can choose a fast path
+      // since the rest will all be insertions.
+      for (; newIdx < newChildren.length; newIdx++) {
+        var _newFiber = createChild(
+          returnFiber,
+          newChildren[newIdx],
+          expirationTime
+        );
+        if (!_newFiber) {
+          continue;
         }
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // If there are no effects associated with this node, then none of our children had any updates.
-        // This guarantees that we can reuse all of them.
-        var childrenUnchanged = workInProgress.firstEffect === null;
-        var currentInstance = current.stateNode;
-        if (childrenUnchanged && updatePayload === null) {
-          // No changes, just reuse the existing instance.
-          // Note that this might release a previous clone.
-          workInProgress.stateNode = currentInstance;
+        lastPlacedIndex = placeChild(_newFiber, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          // TODO: Move out of the loop. This only happens for the first run.
+          resultingFirstChild = _newFiber;
         } else {
-          var recyclableInstance = workInProgress.stateNode;
-          var newInstance = cloneInstance(
-            currentInstance,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            workInProgress,
-            childrenUnchanged,
-            recyclableInstance
-          );
-          if (
-            finalizeInitialChildren(
-              newInstance,
-              type,
-              newProps,
-              rootContainerInstance,
-              currentHostContext
-            )
-          ) {
-            markUpdate(workInProgress);
-          }
-          workInProgress.stateNode = newInstance;
-          if (childrenUnchanged) {
-            // If there are no other effects in this tree, we need to flag this node as having one.
-            // Even though we're not going to use it for anything.
-            // Otherwise parents won't know that there are new children to propagate upwards.
-            markUpdate(workInProgress);
-          } else {
-            // If children might have changed, we have to add them all to the set.
-            appendAllChildren(newInstance, workInProgress);
-          }
-        }
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        if (oldText !== newText) {
-          // If the text content differs, we'll create a new text instance for it.
-          var rootContainerInstance = getRootHostContainer();
-          var currentHostContext = getHostContext();
-          workInProgress.stateNode = createTextInstance(
-            newText,
-            rootContainerInstance,
-            currentHostContext,
-            workInProgress
-          );
-          // We'll have to mark it as having an effect, even though we won't use the effect for anything.
-          // This lets the parents know that at least one of their children has changed.
-          markUpdate(workInProgress);
-        }
-      };
-    } else {
-      invariant(false, "Persistent reconciler is disabled.");
-    }
-  } else {
-    if (enableNoopReconciler) {
-      // No host operations
-      updateHostContainer = function(workInProgress) {
-        // Noop
-      };
-      updateHostComponent = function(
-        current,
-        workInProgress,
-        updatePayload,
-        type,
-        oldProps,
-        newProps,
-        rootContainerInstance,
-        currentHostContext
-      ) {
-        // Noop
-      };
-      updateHostText = function(current, workInProgress, oldText, newText) {
-        // Noop
-      };
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
-    }
-  }
-
-  function completeWork(current, workInProgress, renderExpirationTime) {
-    var newProps = workInProgress.pendingProps;
-    switch (workInProgress.tag) {
-      case FunctionalComponent:
-        return null;
-      case ClassComponent: {
-        // We are leaving this subtree, so pop context if any.
-        popLegacyContextProvider(workInProgress);
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var fiberRoot = workInProgress.stateNode;
-        if (fiberRoot.pendingContext) {
-          fiberRoot.context = fiberRoot.pendingContext;
-          fiberRoot.pendingContext = null;
-        }
-        if (current === null || current.child === null) {
-          // If we hydrated, pop so that we can delete any remaining children
-          // that weren't hydrated.
-          popHydrationState(workInProgress);
-          // This resets the hacky state to fix isMounted before committing.
-          // TODO: Delete this when we delete isMounted and findDOMNode.
-          workInProgress.effectTag &= ~Placement;
+          previousNewFiber.sibling = _newFiber;
         }
-        updateHostContainer(workInProgress);
-        return null;
+        previousNewFiber = _newFiber;
       }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        var rootContainerInstance = getRootHostContainer();
-        var type = workInProgress.type;
-        if (current !== null && workInProgress.stateNode != null) {
-          // If we have an alternate, that means this is an update and we need to
-          // schedule a side-effect to do the updates.
-          var oldProps = current.memoizedProps;
-          // If we get updated because one of our children updated, we don't
-          // have newProps so we'll have to reuse them.
-          // TODO: Split the update API as separate for the props vs. children.
-          // Even better would be if children weren't special cased at all tho.
-          var instance = workInProgress.stateNode;
-          var currentHostContext = getHostContext();
-          // TODO: Experiencing an error where oldProps is null. Suggests a host
-          // component is hitting the resume path. Figure out why. Possibly
-          // related to `hidden`.
-          var updatePayload = prepareUpdate(
-            instance,
-            type,
-            oldProps,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          );
-
-          updateHostComponent(
-            current,
-            workInProgress,
-            updatePayload,
-            type,
-            oldProps,
-            newProps,
-            rootContainerInstance,
-            currentHostContext
-          );
-
-          if (current.ref !== workInProgress.ref) {
-            markRef(workInProgress);
-          }
-        } else {
-          if (!newProps) {
-            invariant(
-              workInProgress.stateNode !== null,
-              "We must have new props for new mounts. This error is likely " +
-                "caused by a bug in React. Please file an issue."
-            );
-            // This can happen when we abort work.
-            return null;
-          }
-
-          var _currentHostContext = getHostContext();
-          // TODO: Move createInstance to beginWork and keep it on a context
-          // "stack" as the parent. Then append children as we go in beginWork
-          // or completeWork depending on we want to add then top->down or
-          // bottom->up. Top->down is faster in IE11.
-          var wasHydrated = popHydrationState(workInProgress);
-          if (wasHydrated) {
-            // TODO: Move this and createInstance step into the beginPhase
-            // to consolidate.
-            if (
-              prepareToHydrateHostInstance(
-                workInProgress,
-                rootContainerInstance,
-                _currentHostContext
-              )
-            ) {
-              // If changes to the hydrated node needs to be applied at the
-              // commit-phase we mark this as such.
-              markUpdate(workInProgress);
-            }
-          } else {
-            var _instance = createInstance(
-              type,
-              newProps,
-              rootContainerInstance,
-              _currentHostContext,
-              workInProgress
-            );
-
-            appendAllChildren(_instance, workInProgress);
+      return resultingFirstChild;
+    }
 
-            // Certain renderers require commit-time effects for initial mount.
-            // (eg DOM renderer supports auto-focus for certain elements).
-            // Make sure such renderers get scheduled for later work.
-            if (
-              finalizeInitialChildren(
-                _instance,
-                type,
-                newProps,
-                rootContainerInstance,
-                _currentHostContext
-              )
-            ) {
-              markUpdate(workInProgress);
-            }
-            workInProgress.stateNode = _instance;
-          }
+    // Add all children to a key map for quick lookups.
+    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
 
-          if (workInProgress.ref !== null) {
-            // If there is a ref on a host node we need to schedule a callback
-            markRef(workInProgress);
+    // Keep scanning and use the map to restore deleted items as moves.
+    for (; newIdx < newChildren.length; newIdx++) {
+      var _newFiber2 = updateFromMap(
+        existingChildren,
+        returnFiber,
+        newIdx,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (_newFiber2) {
+        if (shouldTrackSideEffects) {
+          if (_newFiber2.alternate !== null) {
+            // The new fiber is a work in progress, but if there exists a
+            // current, that means that we reused the fiber. We need to delete
+            // it from the child list so that we don't add it to the deletion
+            // list.
+            existingChildren.delete(
+              _newFiber2.key === null ? newIdx : _newFiber2.key
+            );
           }
         }
-        return null;
-      }
-      case HostText: {
-        var newText = newProps;
-        if (current && workInProgress.stateNode != null) {
-          var oldText = current.memoizedProps;
-          // If we have an alternate, that means this is an update and we need
-          // to schedule a side-effect to do the updates.
-          updateHostText(current, workInProgress, oldText, newText);
+        lastPlacedIndex = placeChild(_newFiber2, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          resultingFirstChild = _newFiber2;
         } else {
-          if (typeof newText !== "string") {
-            invariant(
-              workInProgress.stateNode !== null,
-              "We must have new props for new mounts. This error is likely " +
-                "caused by a bug in React. Please file an issue."
-            );
-            // This can happen when we abort work.
-            return null;
-          }
-          var _rootContainerInstance = getRootHostContainer();
-          var _currentHostContext2 = getHostContext();
-          var _wasHydrated = popHydrationState(workInProgress);
-          if (_wasHydrated) {
-            if (prepareToHydrateHostTextInstance(workInProgress)) {
-              markUpdate(workInProgress);
-            }
-          } else {
-            workInProgress.stateNode = createTextInstance(
-              newText,
-              _rootContainerInstance,
-              _currentHostContext2,
-              workInProgress
-            );
-          }
+          previousNewFiber.sibling = _newFiber2;
         }
-        return null;
+        previousNewFiber = _newFiber2;
       }
-      case ForwardRef:
-        return null;
-      case TimeoutComponent:
-        return null;
-      case Fragment:
-        return null;
-      case Mode:
-        return null;
-      case Profiler:
-        if (enableProfilerTimer) {
-          recordElapsedActualRenderTime(workInProgress);
-        }
-        return null;
-      case HostPortal:
-        popHostContainer(workInProgress);
-        updateHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        // Pop provider fiber
-        popProvider(workInProgress);
-        return null;
-      case ContextConsumer:
-        return null;
-      // Error cases
-      case IndeterminateComponent:
-        invariant(
-          false,
-          "An indeterminate component should have become determinate before " +
-            "completing. This error is likely caused by a bug in React. Please " +
-            "file an issue."
-        );
-      // eslint-disable-next-line no-fallthrough
-      default:
-        invariant(
-          false,
-          "Unknown unit of work tag. This error is likely caused by a bug in " +
-            "React. Please file an issue."
-        );
     }
-  }
-
-  return {
-    completeWork: completeWork
-  };
-};
-
-function createCapturedValue(value, source) {
-  // If the value is an error, call this function immediately after it is thrown
-  // so the stack is accurate.
-  return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
-  };
-}
-
-// Module provided by RN:
-/**
- * Intercept lifecycle errors and ensure they are shown with the correct stack
- * trace within the native redbox component.
- */
-function showErrorDialog(capturedError) {
-  var componentStack = capturedError.componentStack,
-    error = capturedError.error;
-
-  var errorToHandle = void 0;
-
-  // Typically Errors are thrown but eg strings or null can be thrown as well.
-  if (error instanceof Error) {
-    var message = error.message,
-      name = error.name;
-
-    var summary = message ? name + ": " + message : name;
-
-    errorToHandle = error;
-
-    try {
-      errorToHandle.message =
-        summary + "\n\nThis error is located at:" + componentStack;
-    } catch (e) {}
-  } else if (typeof error === "string") {
-    errorToHandle = new Error(
-      error + "\n\nThis error is located at:" + componentStack
-    );
-  } else {
-    errorToHandle = new Error("Unspecified error at:" + componentStack);
-  }
-
-  ExceptionsManager.handleException(errorToHandle, false);
-
-  // Return false here to prevent ReactFiberErrorLogger default behavior of
-  // logging error details to console.error. Calls to console.error are
-  // automatically routed to the native redbox controller, which we've already
-  // done above by calling ExceptionsManager.
-  return false;
-}
 
-function logCapturedError(capturedError) {
-  var logError = showErrorDialog(capturedError);
+    if (shouldTrackSideEffects) {
+      // Any existing children that weren't consumed above were deleted. We need
+      // to add them to the deletion list.
+      existingChildren.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    }
 
-  // Allow injected showErrorDialog() to prevent default console.error logging.
-  // This enables renderers like ReactNative to better manage redbox behavior.
-  if (logError === false) {
-    return;
+    return resultingFirstChild;
   }
 
-  var error = capturedError.error;
-  var suppressLogging = error && error.suppressReactErrorLogging;
-  if (suppressLogging) {
-    return;
-  }
+  function reconcileChildrenIterator(
+    returnFiber,
+    currentFirstChild,
+    newChildrenIterable,
+    expirationTime
+  ) {
+    // This is the same implementation as reconcileChildrenArray(),
+    // but using the iterator instead.
 
-  {
-    var componentName = capturedError.componentName,
-      componentStack = capturedError.componentStack,
-      errorBoundaryName = capturedError.errorBoundaryName,
-      errorBoundaryFound = capturedError.errorBoundaryFound,
-      willRetry = capturedError.willRetry;
+    var iteratorFn = getIteratorFn(newChildrenIterable);
+    invariant(
+      typeof iteratorFn === "function",
+      "An object is not an iterable. This error is likely caused by a bug in " +
+        "React. Please file an issue."
+    );
 
-    var componentNameMessage = componentName
-      ? "The above error occurred in the <" + componentName + "> component:"
-      : "The above error occurred in one of your React components:";
+    {
+      // Warn about using Maps as children
+      if (newChildrenIterable.entries === iteratorFn) {
+        !didWarnAboutMaps
+          ? warning(
+              false,
+              "Using Maps as children is unsupported and will likely yield " +
+                "unexpected results. Convert it to a sequence/iterable of keyed " +
+                "ReactElements instead.%s",
+              getCurrentFiberStackAddendum$2()
+            )
+          : void 0;
+        didWarnAboutMaps = true;
+      }
 
-    var errorBoundaryMessage = void 0;
-    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
-    if (errorBoundaryFound && errorBoundaryName) {
-      if (willRetry) {
-        errorBoundaryMessage =
-          "React will try to recreate this component tree from scratch " +
-          ("using the error boundary you provided, " + errorBoundaryName + ".");
-      } else {
-        errorBoundaryMessage =
-          "This error was initially handled by the error boundary " +
-          errorBoundaryName +
-          ".\n" +
-          "Recreating the tree from scratch failed so React will unmount the tree.";
+      // First, validate keys.
+      // We'll get a different iterator later for the main pass.
+      var _newChildren = iteratorFn.call(newChildrenIterable);
+      if (_newChildren) {
+        var knownKeys = null;
+        var _step = _newChildren.next();
+        for (; !_step.done; _step = _newChildren.next()) {
+          var child = _step.value;
+          knownKeys = warnOnInvalidKey(child, knownKeys);
+        }
       }
-    } else {
-      errorBoundaryMessage =
-        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
-        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
     }
-    var combinedMessage =
-      "" +
-      componentNameMessage +
-      componentStack +
-      "\n\n" +
-      ("" + errorBoundaryMessage);
-
-    // In development, we provide our own message with just the component stack.
-    // We don't include the original error message and JS stack because the browser
-    // has already printed it. Even if the application swallows the error, it is still
-    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
-    console.error(combinedMessage);
-  }
-}
 
-var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
-var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
+    var newChildren = iteratorFn.call(newChildrenIterable);
+    invariant(newChildren != null, "An iterable object provided no iterator.");
 
-var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
-{
-  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
-}
+    var resultingFirstChild = null;
+    var previousNewFiber = null;
 
-function logError(boundary, errorInfo) {
-  var source = errorInfo.source;
-  var stack = errorInfo.stack;
-  if (stack === null && source !== null) {
-    stack = getStackAddendumByWorkInProgressFiber(source);
-  }
+    var oldFiber = currentFirstChild;
+    var lastPlacedIndex = 0;
+    var newIdx = 0;
+    var nextOldFiber = null;
 
-  var capturedError = {
-    componentName: source !== null ? getComponentName(source) : null,
-    componentStack: stack !== null ? stack : "",
-    error: errorInfo.value,
-    errorBoundary: null,
-    errorBoundaryName: null,
-    errorBoundaryFound: false,
-    willRetry: false
-  };
+    var step = newChildren.next();
+    for (
+      ;
+      oldFiber !== null && !step.done;
+      newIdx++, step = newChildren.next()
+    ) {
+      if (oldFiber.index > newIdx) {
+        nextOldFiber = oldFiber;
+        oldFiber = null;
+      } else {
+        nextOldFiber = oldFiber.sibling;
+      }
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        step.value,
+        expirationTime
+      );
+      if (newFiber === null) {
+        // TODO: This breaks on empty slots like null children. That's
+        // unfortunate because it triggers the slow path all the time. We need
+        // a better way to communicate whether this was a miss or null,
+        // boolean, undefined, etc.
+        if (!oldFiber) {
+          oldFiber = nextOldFiber;
+        }
+        break;
+      }
+      if (shouldTrackSideEffects) {
+        if (oldFiber && newFiber.alternate === null) {
+          // We matched the slot, but we didn't reuse the existing fiber, so we
+          // need to delete the existing child.
+          deleteChild(returnFiber, oldFiber);
+        }
+      }
+      lastPlacedIndex = placeChild(newFiber, lastPlacedIndex, newIdx);
+      if (previousNewFiber === null) {
+        // TODO: Move out of the loop. This only happens for the first run.
+        resultingFirstChild = newFiber;
+      } else {
+        // TODO: Defer siblings if we're not at the right index for this slot.
+        // I.e. if we had null values before, then we want to defer this
+        // for each null value. However, we also don't want to call updateSlot
+        // with the previous one.
+        previousNewFiber.sibling = newFiber;
+      }
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
 
-  if (boundary !== null && boundary.tag === ClassComponent) {
-    capturedError.errorBoundary = boundary.stateNode;
-    capturedError.errorBoundaryName = getComponentName(boundary);
-    capturedError.errorBoundaryFound = true;
-    capturedError.willRetry = true;
-  }
+    if (step.done) {
+      // We've reached the end of the new children. We can delete the rest.
+      deleteRemainingChildren(returnFiber, oldFiber);
+      return resultingFirstChild;
+    }
 
-  try {
-    logCapturedError(capturedError);
-  } catch (e) {
-    // Prevent cycle if logCapturedError() throws.
-    // A cycle may still occur if logCapturedError renders a component that throws.
-    var suppressLogging = e && e.suppressReactErrorLogging;
-    if (!suppressLogging) {
-      console.error(e);
+    if (oldFiber === null) {
+      // If we don't have any more existing children we can choose a fast path
+      // since the rest will all be insertions.
+      for (; !step.done; newIdx++, step = newChildren.next()) {
+        var _newFiber3 = createChild(returnFiber, step.value, expirationTime);
+        if (_newFiber3 === null) {
+          continue;
+        }
+        lastPlacedIndex = placeChild(_newFiber3, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          // TODO: Move out of the loop. This only happens for the first run.
+          resultingFirstChild = _newFiber3;
+        } else {
+          previousNewFiber.sibling = _newFiber3;
+        }
+        previousNewFiber = _newFiber3;
+      }
+      return resultingFirstChild;
     }
-  }
-}
 
-var ReactFiberCommitWork = function(
-  config,
-  captureError,
-  scheduleWork,
-  computeExpirationForFiber,
-  markLegacyErrorBoundaryAsFailed,
-  recalculateCurrentTime
-) {
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation,
-    persistence = config.persistence;
-
-  var callComponentWillUnmountWithTimer = function(current, instance) {
-    startPhaseTimer(current, "componentWillUnmount");
-    instance.props = current.memoizedProps;
-    instance.state = current.memoizedState;
-    instance.componentWillUnmount();
-    stopPhaseTimer();
-  };
+    // Add all children to a key map for quick lookups.
+    var existingChildren = mapRemainingChildren(returnFiber, oldFiber);
 
-  // Capture errors so they don't interrupt unmounting.
-  function safelyCallComponentWillUnmount(current, instance) {
-    {
-      invokeGuardedCallback$3(
-        null,
-        callComponentWillUnmountWithTimer,
-        null,
-        current,
-        instance
+    // Keep scanning and use the map to restore deleted items as moves.
+    for (; !step.done; newIdx++, step = newChildren.next()) {
+      var _newFiber4 = updateFromMap(
+        existingChildren,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
       );
-      if (hasCaughtError$1()) {
-        var unmountError = clearCaughtError$1();
-        captureError(current, unmountError);
+      if (_newFiber4 !== null) {
+        if (shouldTrackSideEffects) {
+          if (_newFiber4.alternate !== null) {
+            // The new fiber is a work in progress, but if there exists a
+            // current, that means that we reused the fiber. We need to delete
+            // it from the child list so that we don't add it to the deletion
+            // list.
+            existingChildren.delete(
+              _newFiber4.key === null ? newIdx : _newFiber4.key
+            );
+          }
+        }
+        lastPlacedIndex = placeChild(_newFiber4, lastPlacedIndex, newIdx);
+        if (previousNewFiber === null) {
+          resultingFirstChild = _newFiber4;
+        } else {
+          previousNewFiber.sibling = _newFiber4;
+        }
+        previousNewFiber = _newFiber4;
       }
     }
+
+    if (shouldTrackSideEffects) {
+      // Any existing children that weren't consumed above were deleted. We need
+      // to add them to the deletion list.
+      existingChildren.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    }
+
+    return resultingFirstChild;
   }
 
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (ref !== null) {
-      if (typeof ref === "function") {
-        {
-          invokeGuardedCallback$3(null, ref, null, null);
-          if (hasCaughtError$1()) {
-            var refError = clearCaughtError$1();
-            captureError(current, refError);
+  function reconcileSingleTextNode(
+    returnFiber,
+    currentFirstChild,
+    textContent,
+    expirationTime
+  ) {
+    // There's no need to check for keys on text nodes since we don't have a
+    // way to define them.
+    if (currentFirstChild !== null && currentFirstChild.tag === HostText) {
+      // We already have an existing node so let's just update it and delete
+      // the rest.
+      deleteRemainingChildren(returnFiber, currentFirstChild.sibling);
+      var existing = useFiber(currentFirstChild, textContent, expirationTime);
+      existing.return = returnFiber;
+      return existing;
+    }
+    // The existing first child is not a text node so we need to create one
+    // and delete the existing ones.
+    deleteRemainingChildren(returnFiber, currentFirstChild);
+    var created = createFiberFromText(
+      textContent,
+      returnFiber.mode,
+      expirationTime
+    );
+    created.return = returnFiber;
+    return created;
+  }
+
+  function reconcileSingleElement(
+    returnFiber,
+    currentFirstChild,
+    element,
+    expirationTime
+  ) {
+    var key = element.key;
+    var child = currentFirstChild;
+    while (child !== null) {
+      // TODO: If key === null and child.key === null, then this only applies to
+      // the first item in the list.
+      if (child.key === key) {
+        if (
+          child.tag === Fragment
+            ? element.type === REACT_FRAGMENT_TYPE
+            : child.type === element.type
+        ) {
+          deleteRemainingChildren(returnFiber, child.sibling);
+          var existing = useFiber(
+            child,
+            element.type === REACT_FRAGMENT_TYPE
+              ? element.props.children
+              : element.props,
+            expirationTime
+          );
+          existing.ref = coerceRef(returnFiber, child, element);
+          existing.return = returnFiber;
+          {
+            existing._debugSource = element._source;
+            existing._debugOwner = element._owner;
           }
+          return existing;
+        } else {
+          deleteRemainingChildren(returnFiber, child);
+          break;
         }
       } else {
-        ref.current = null;
+        deleteChild(returnFiber, child);
       }
+      child = child.sibling;
+    }
+
+    if (element.type === REACT_FRAGMENT_TYPE) {
+      var created = createFiberFromFragment(
+        element.props.children,
+        returnFiber.mode,
+        expirationTime,
+        element.key
+      );
+      created.return = returnFiber;
+      return created;
+    } else {
+      var _created4 = createFiberFromElement(
+        element,
+        returnFiber.mode,
+        expirationTime
+      );
+      _created4.ref = coerceRef(returnFiber, currentFirstChild, element);
+      _created4.return = returnFiber;
+      return _created4;
     }
   }
 
-  function commitBeforeMutationLifeCycles(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        if (finishedWork.effectTag & Snapshot) {
-          if (current !== null) {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
-            var _instance = finishedWork.stateNode;
-            _instance.props = finishedWork.memoizedProps;
-            _instance.state = finishedWork.memoizedState;
-            var snapshot = _instance.getSnapshotBeforeUpdate(
-              prevProps,
-              prevState
-            );
-            {
-              var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
-              if (
-                snapshot === undefined &&
-                !didWarnSet.has(finishedWork.type)
-              ) {
-                didWarnSet.add(finishedWork.type);
-                warning(
-                  false,
-                  "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
-                    "must be returned. You have returned undefined.",
-                  getComponentName(finishedWork)
-                );
-              }
-            }
-            _instance.__reactInternalSnapshotBeforeUpdate = snapshot;
-            stopPhaseTimer();
-          }
+  function reconcileSinglePortal(
+    returnFiber,
+    currentFirstChild,
+    portal,
+    expirationTime
+  ) {
+    var key = portal.key;
+    var child = currentFirstChild;
+    while (child !== null) {
+      // TODO: If key === null and child.key === null, then this only applies to
+      // the first item in the list.
+      if (child.key === key) {
+        if (
+          child.tag === HostPortal &&
+          child.stateNode.containerInfo === portal.containerInfo &&
+          child.stateNode.implementation === portal.implementation
+        ) {
+          deleteRemainingChildren(returnFiber, child.sibling);
+          var existing = useFiber(child, portal.children || [], expirationTime);
+          existing.return = returnFiber;
+          return existing;
+        } else {
+          deleteRemainingChildren(returnFiber, child);
+          break;
         }
-        return;
-      }
-      case HostRoot:
-      case HostComponent:
-      case HostText:
-      case HostPortal:
-        // Nothing to do for these component types
-        return;
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
+      } else {
+        deleteChild(returnFiber, child);
       }
+      child = child.sibling;
     }
+
+    var created = createFiberFromPortal(
+      portal,
+      returnFiber.mode,
+      expirationTime
+    );
+    created.return = returnFiber;
+    return created;
   }
 
-  function commitLifeCycles(
-    finishedRoot,
-    current,
-    finishedWork,
-    currentTime,
-    committedExpirationTime
+  // This API will tag the children with the side-effect of the reconciliation
+  // itself. They will be added to the side-effect list as we pass through the
+  // children and the parent.
+  function reconcileChildFibers(
+    returnFiber,
+    currentFirstChild,
+    newChild,
+    expirationTime
   ) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        var _instance2 = finishedWork.stateNode;
-        if (finishedWork.effectTag & Update) {
-          if (current === null) {
-            startPhaseTimer(finishedWork, "componentDidMount");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidMount();
-            stopPhaseTimer();
-          } else {
-            var prevProps = current.memoizedProps;
-            var prevState = current.memoizedState;
-            startPhaseTimer(finishedWork, "componentDidUpdate");
-            _instance2.props = finishedWork.memoizedProps;
-            _instance2.state = finishedWork.memoizedState;
-            _instance2.componentDidUpdate(
-              prevProps,
-              prevState,
-              _instance2.__reactInternalSnapshotBeforeUpdate
-            );
-            stopPhaseTimer();
-          }
-        }
-        var updateQueue = finishedWork.updateQueue;
-        if (updateQueue !== null) {
-          _instance2.props = finishedWork.memoizedProps;
-          _instance2.state = finishedWork.memoizedState;
-          commitUpdateQueue(
-            finishedWork,
-            updateQueue,
-            _instance2,
-            committedExpirationTime
-          );
-        }
-        return;
-      }
-      case HostRoot: {
-        var _updateQueue = finishedWork.updateQueue;
-        if (_updateQueue !== null) {
-          var _instance3 = null;
-          if (finishedWork.child !== null) {
-            switch (finishedWork.child.tag) {
-              case HostComponent:
-                _instance3 = getPublicInstance(finishedWork.child.stateNode);
-                break;
-              case ClassComponent:
-                _instance3 = finishedWork.child.stateNode;
-                break;
-            }
-          }
-          commitUpdateQueue(
-            finishedWork,
-            _updateQueue,
-            _instance3,
-            committedExpirationTime
-          );
-        }
-        return;
-      }
-      case HostComponent: {
-        var _instance4 = finishedWork.stateNode;
-
-        // Renderers may schedule work to be done after host components are mounted
-        // (eg DOM renderer may schedule auto-focus for inputs and form controls).
-        // These effects should only be committed when components are first mounted,
-        // aka when there is no current/alternate.
-        if (current === null && finishedWork.effectTag & Update) {
-          var type = finishedWork.type;
-          var props = finishedWork.memoizedProps;
-          commitMount(_instance4, type, props, finishedWork);
-        }
+    // This function is not recursive.
+    // If the top level item is an array, we treat it as a set of children,
+    // not as a fragment. Nested arrays on the other hand will be treated as
+    // fragment nodes. Recursion happens at the normal flow.
 
-        return;
-      }
-      case HostText: {
-        // We have no life-cycles associated with text.
-        return;
-      }
-      case HostPortal: {
-        // We have no life-cycles associated with portals.
-        return;
-      }
-      case Profiler: {
-        // We have no life-cycles associated with Profiler.
-        return;
-      }
-      case TimeoutComponent: {
-        // We have no life-cycles associated with Timeouts.
-        return;
-      }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
-      }
+    // Handle top level unkeyed fragments as if they were arrays.
+    // This leads to an ambiguity between <>{[...]}</> and <>...</>.
+    // We treat the ambiguous cases above the same.
+    var isUnkeyedTopLevelFragment =
+      typeof newChild === "object" &&
+      newChild !== null &&
+      newChild.type === REACT_FRAGMENT_TYPE &&
+      newChild.key === null;
+    if (isUnkeyedTopLevelFragment) {
+      newChild = newChild.props.children;
     }
-  }
 
-  function commitAttachRef(finishedWork) {
-    var ref = finishedWork.ref;
-    if (ref !== null) {
-      var _instance5 = finishedWork.stateNode;
-      var instanceToUse = void 0;
-      switch (finishedWork.tag) {
-        case HostComponent:
-          instanceToUse = getPublicInstance(_instance5);
-          break;
-        default:
-          instanceToUse = _instance5;
-      }
-      if (typeof ref === "function") {
-        ref(instanceToUse);
-      } else {
-        {
-          if (!ref.hasOwnProperty("current")) {
-            warning(
-              false,
-              "Unexpected ref object provided for %s. " +
-                "Use either a ref-setter function or React.createRef().%s",
-              getComponentName(finishedWork),
-              getStackAddendumByWorkInProgressFiber(finishedWork)
-            );
-          }
-        }
+    // Handle object types
+    var isObject = typeof newChild === "object" && newChild !== null;
 
-        ref.current = instanceToUse;
+    if (isObject) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return placeSingleChild(
+            reconcileSingleElement(
+              returnFiber,
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )
+          );
+        case REACT_PORTAL_TYPE:
+          return placeSingleChild(
+            reconcileSinglePortal(
+              returnFiber,
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )
+          );
       }
     }
-  }
 
-  function commitDetachRef(current) {
-    var currentRef = current.ref;
-    if (currentRef !== null) {
-      if (typeof currentRef === "function") {
-        currentRef(null);
-      } else {
-        currentRef.current = null;
-      }
+    if (typeof newChild === "string" || typeof newChild === "number") {
+      return placeSingleChild(
+        reconcileSingleTextNode(
+          returnFiber,
+          currentFirstChild,
+          "" + newChild,
+          expirationTime
+        )
+      );
     }
-  }
 
-  // User-originating errors (lifecycles and refs) should not interrupt
-  // deletion, so don't let them throw. Host-originating errors should
-  // interrupt deletion, so it's okay
-  function commitUnmount(current) {
-    if (typeof onCommitUnmount === "function") {
-      onCommitUnmount(current);
+    if (isArray$1(newChild)) {
+      return reconcileChildrenArray(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
     }
 
-    switch (current.tag) {
-      case ClassComponent: {
-        safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if (typeof _instance6.componentWillUnmount === "function") {
-          safelyCallComponentWillUnmount(current, _instance6);
-        }
-        return;
-      }
-      case HostComponent: {
-        safelyDetachRef(current);
-        return;
-      }
-      case HostPortal: {
-        // TODO: this is recursive.
-        // We are also not using this parent because
-        // the portal will get pushed immediately.
-        if (enableMutatingReconciler && mutation) {
-          unmountHostComponents(current);
-        } else if (enablePersistentReconciler && persistence) {
-          emptyPortalContainer(current);
-        }
-        return;
-      }
+    if (getIteratorFn(newChild)) {
+      return reconcileChildrenIterator(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
     }
-  }
 
-  function commitNestedUnmounts(root) {
-    // While we're inside a removed host node we don't want to call
-    // removeChild on the inner nodes because they're removed by the top
-    // call anyway. We also want to call componentWillUnmount on all
-    // composites before this host node is removed from the tree. Therefore
-    var node = root;
-    while (true) {
-      commitUnmount(node);
-      // Visit children because they may contain more composite or host nodes.
-      // Skip portals because commitUnmount() currently visits them recursively.
-      if (
-        node.child !== null &&
-        // If we use mutation we drill down into portals using commitUnmount above.
-        // If we don't use mutation we drill down into portals here instead.
-        (!mutation || node.tag !== HostPortal)
-      ) {
-        node.child.return = node;
-        node = node.child;
-        continue;
-      }
-      if (node === root) {
-        return;
+    if (isObject) {
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+
+    {
+      if (typeof newChild === "function") {
+        warnOnFunctionType();
       }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === root) {
-          return;
+    }
+    if (typeof newChild === "undefined" && !isUnkeyedTopLevelFragment) {
+      // If the new child is undefined, and the return fiber is a composite
+      // component, throw an error. If Fiber return types are disabled,
+      // we already threw above.
+      switch (returnFiber.tag) {
+        case ClassComponent: {
+          {
+            var instance = returnFiber.stateNode;
+            if (instance.render._isMockFunction) {
+              // We allow auto-mocks to proceed as if they're returning null.
+              break;
+            }
+          }
+        }
+        // Intentionally fall through to the next case, which handles both
+        // functions and classes
+        // eslint-disable-next-lined no-fallthrough
+        case FunctionalComponent: {
+          var Component = returnFiber.type;
+          invariant(
+            false,
+            "%s(...): Nothing was returned from render. This usually means a " +
+              "return statement is missing. Or, to render nothing, " +
+              "return null.",
+            Component.displayName || Component.name || "Component"
+          );
         }
-        node = node.return;
       }
-      node.sibling.return = node.return;
-      node = node.sibling;
     }
-  }
 
-  function detachFiber(current) {
-    // Cut off the return pointers to disconnect it from the tree. Ideally, we
-    // should clear the child pointer of the parent alternate to let this
-    // get GC:ed but we don't know which for sure which parent is the current
-    // one so we'll settle for GC:ing the subtree of this child. This child
-    // itself will be GC:ed when the parent updates the next time.
-    current.return = null;
-    current.child = null;
-    if (current.alternate) {
-      current.alternate.child = null;
-      current.alternate.return = null;
-    }
+    // Remaining cases are all treated as empty.
+    return deleteRemainingChildren(returnFiber, currentFirstChild);
   }
 
-  var emptyPortalContainer = void 0;
-
-  if (!mutation) {
-    var commitContainer = void 0;
-    if (persistence) {
-      var replaceContainerChildren = persistence.replaceContainerChildren,
-        createContainerChildSet = persistence.createContainerChildSet;
+  return reconcileChildFibers;
+}
 
-      emptyPortalContainer = function(current) {
-        var portal = current.stateNode;
-        var containerInfo = portal.containerInfo;
+var reconcileChildFibers = ChildReconciler(true);
+var mountChildFibers = ChildReconciler(false);
 
-        var emptyChildSet = createContainerChildSet(containerInfo);
-        replaceContainerChildren(containerInfo, emptyChildSet);
-      };
-      commitContainer = function(finishedWork) {
-        switch (finishedWork.tag) {
-          case ClassComponent: {
-            return;
-          }
-          case HostComponent: {
-            return;
-          }
-          case HostText: {
-            return;
-          }
-          case HostRoot:
-          case HostPortal: {
-            var portalOrRoot = finishedWork.stateNode;
-            var containerInfo = portalOrRoot.containerInfo,
-              _pendingChildren = portalOrRoot.pendingChildren;
+function cloneChildFibers(current, workInProgress) {
+  invariant(
+    current === null || workInProgress.child === current.child,
+    "Resuming work not yet implemented."
+  );
 
-            replaceContainerChildren(containerInfo, _pendingChildren);
-            return;
-          }
-          default: {
-            invariant(
-              false,
-              "This unit of work tag should not have side-effects. This error is " +
-                "likely caused by a bug in React. Please file an issue."
-            );
-          }
-        }
-      };
-    } else {
-      commitContainer = function(finishedWork) {
-        // Noop
-      };
-    }
-    if (enablePersistentReconciler || enableNoopReconciler) {
-      return {
-        commitResetTextContent: function(finishedWork) {},
-        commitPlacement: function(finishedWork) {},
-        commitDeletion: function(current) {
-          // Detach refs and call componentWillUnmount() on the whole subtree.
-          commitNestedUnmounts(current);
-          detachFiber(current);
-        },
-        commitWork: function(current, finishedWork) {
-          commitContainer(finishedWork);
-        },
-
-        commitLifeCycles: commitLifeCycles,
-        commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-        commitAttachRef: commitAttachRef,
-        commitDetachRef: commitDetachRef
-      };
-    } else if (persistence) {
-      invariant(false, "Persistent reconciler is disabled.");
-    } else {
-      invariant(false, "Noop reconciler is disabled.");
-    }
+  if (workInProgress.child === null) {
+    return;
   }
-  var commitMount = mutation.commitMount,
-    commitUpdate = mutation.commitUpdate,
-    resetTextContent = mutation.resetTextContent,
-    commitTextUpdate = mutation.commitTextUpdate,
-    appendChild = mutation.appendChild,
-    appendChildToContainer = mutation.appendChildToContainer,
-    insertBefore = mutation.insertBefore,
-    insertInContainerBefore = mutation.insertInContainerBefore,
-    removeChild = mutation.removeChild,
-    removeChildFromContainer = mutation.removeChildFromContainer;
 
-  function getHostParentFiber(fiber) {
-    var parent = fiber.return;
-    while (parent !== null) {
-      if (isHostParent(parent)) {
-        return parent;
-      }
-      parent = parent.return;
-    }
-    invariant(
-      false,
-      "Expected to find a host parent. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-  }
+  var currentChild = workInProgress.child;
+  var newChild = createWorkInProgress(
+    currentChild,
+    currentChild.pendingProps,
+    currentChild.expirationTime
+  );
+  workInProgress.child = newChild;
 
-  function isHostParent(fiber) {
-    return (
-      fiber.tag === HostComponent ||
-      fiber.tag === HostRoot ||
-      fiber.tag === HostPortal
+  newChild.return = workInProgress;
+  while (currentChild.sibling !== null) {
+    currentChild = currentChild.sibling;
+    newChild = newChild.sibling = createWorkInProgress(
+      currentChild,
+      currentChild.pendingProps,
+      currentChild.expirationTime
     );
+    newChild.return = workInProgress;
   }
+  newChild.sibling = null;
+}
 
-  function getHostSibling(fiber) {
-    // We're going to search forward into the tree until we find a sibling host
-    // node. Unfortunately, if multiple insertions are done in a row we have to
-    // search past them. This leads to exponential search for the next sibling.
-    var node = fiber;
-    siblings: while (true) {
-      // If we didn't find anything, let's try the next sibling.
-      while (node.sibling === null) {
-        if (node.return === null || isHostParent(node.return)) {
-          // If we pop out of the root or hit the parent the fiber we are the
-          // last sibling.
-          return null;
-        }
-        node = node.return;
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
-      while (node.tag !== HostComponent && node.tag !== HostText) {
-        // If it is not host node and, we might have a host node inside it.
-        // Try to search down until we find one.
-        if (node.effectTag & Placement) {
-          // If we don't have a child, try the siblings instead.
-          continue siblings;
-        }
-        // If we don't have a child, try the siblings instead.
-        // We also skip portals because they are not part of this host tree.
-        if (node.child === null || node.tag === HostPortal) {
-          continue siblings;
-        } else {
-          node.child.return = node;
-          node = node.child;
-        }
-      }
-      // Check if this host node is stable or about to be placed.
-      if (!(node.effectTag & Placement)) {
-        // Found it!
-        return node.stateNode;
-      }
-    }
-  }
-
-  function commitPlacement(finishedWork) {
-    // Recursively insert all host nodes into the parent.
-    var parentFiber = getHostParentFiber(finishedWork);
-    var parent = void 0;
-    var isContainer = void 0;
-    switch (parentFiber.tag) {
-      case HostComponent:
-        parent = parentFiber.stateNode;
-        isContainer = false;
-        break;
-      case HostRoot:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      case HostPortal:
-        parent = parentFiber.stateNode.containerInfo;
-        isContainer = true;
-        break;
-      default:
-        invariant(
-          false,
-          "Invalid host parent fiber. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-    }
-    if (parentFiber.effectTag & ContentReset) {
-      // Reset the text content of the parent before doing any insertions
-      resetTextContent(parent);
-      // Clear ContentReset from the effect tag
-      parentFiber.effectTag &= ~ContentReset;
-    }
+// The deepest Fiber on the stack involved in a hydration context.
+// This may have been an insertion or a hydration.
+var hydrationParentFiber = null;
+var nextHydratableInstance = null;
+var isHydrating = false;
 
-    var before = getHostSibling(finishedWork);
-    // We only have the top Fiber that was inserted but we need recurse down its
-    // children to find all the terminal nodes.
-    var node = finishedWork;
-    while (true) {
-      if (node.tag === HostComponent || node.tag === HostText) {
-        if (before) {
-          if (isContainer) {
-            insertInContainerBefore(parent, node.stateNode, before);
-          } else {
-            insertBefore(parent, node.stateNode, before);
-          }
-        } else {
-          if (isContainer) {
-            appendChildToContainer(parent, node.stateNode);
-          } else {
-            appendChild(parent, node.stateNode);
-          }
-        }
-      } else if (node.tag === HostPortal) {
-        // If the insertion itself is a portal, then we don't want to traverse
-        // down its children. Instead, we'll get insertions from each child in
-        // the portal directly.
-      } else if (node.child !== null) {
-        node.child.return = node;
-        node = node.child;
-        continue;
-      }
-      if (node === finishedWork) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === finishedWork) {
-          return;
-        }
-        node = node.return;
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
-    }
+function enterHydrationState(fiber) {
+  if (!supportsHydration) {
+    return false;
   }
 
-  function unmountHostComponents(current) {
-    // We only have the top Fiber that was inserted but we need recurse down its
-    var node = current;
-
-    // Each iteration, currentParent is populated with node's host parent if not
-    // currentParentIsValid.
-    var currentParentIsValid = false;
-    var currentParent = void 0;
-    var currentParentIsContainer = void 0;
-
-    while (true) {
-      if (!currentParentIsValid) {
-        var parent = node.return;
-        findParent: while (true) {
-          invariant(
-            parent !== null,
-            "Expected to find a host parent. This error is likely caused by " +
-              "a bug in React. Please file an issue."
-          );
-          switch (parent.tag) {
-            case HostComponent:
-              currentParent = parent.stateNode;
-              currentParentIsContainer = false;
-              break findParent;
-            case HostRoot:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-            case HostPortal:
-              currentParent = parent.stateNode.containerInfo;
-              currentParentIsContainer = true;
-              break findParent;
-          }
-          parent = parent.return;
-        }
-        currentParentIsValid = true;
-      }
+  var parentInstance = fiber.stateNode.containerInfo;
+  nextHydratableInstance = getFirstHydratableChild(parentInstance);
+  hydrationParentFiber = fiber;
+  isHydrating = true;
+  return true;
+}
 
-      if (node.tag === HostComponent || node.tag === HostText) {
-        commitNestedUnmounts(node);
-        // After all the children have unmounted, it is now safe to remove the
-        // node from the tree.
-        if (currentParentIsContainer) {
-          removeChildFromContainer(currentParent, node.stateNode);
-        } else {
-          removeChild(currentParent, node.stateNode);
-        }
-        // Don't visit children because we already visited them.
-      } else if (node.tag === HostPortal) {
-        // When we go into a portal, it becomes the parent to remove from.
-        // We will reassign it back when we pop the portal on the way up.
-        currentParent = node.stateNode.containerInfo;
-        // Visit children because portals might contain host components.
-        if (node.child !== null) {
-          node.child.return = node;
-          node = node.child;
-          continue;
-        }
-      } else {
-        commitUnmount(node);
-        // Visit children because we may find more host components below.
-        if (node.child !== null) {
-          node.child.return = node;
-          node = node.child;
-          continue;
-        }
-      }
-      if (node === current) {
-        return;
-      }
-      while (node.sibling === null) {
-        if (node.return === null || node.return === current) {
-          return;
-        }
-        node = node.return;
-        if (node.tag === HostPortal) {
-          // When we go out of the portal, we need to restore the parent.
-          // Since we don't keep a stack of them, we will search for it.
-          currentParentIsValid = false;
-        }
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
+function deleteHydratableInstance(returnFiber, instance) {
+  {
+    switch (returnFiber.tag) {
+      case HostRoot:
+        didNotHydrateContainerInstance(
+          returnFiber.stateNode.containerInfo,
+          instance
+        );
+        break;
+      case HostComponent:
+        didNotHydrateInstance(
+          returnFiber.type,
+          returnFiber.memoizedProps,
+          returnFiber.stateNode,
+          instance
+        );
+        break;
     }
   }
 
-  function commitDeletion(current) {
-    // Recursively delete all host nodes from the parent.
-    // Detach refs and call componentWillUnmount() on the whole subtree.
-    unmountHostComponents(current);
-    detachFiber(current);
+  var childToDelete = createFiberFromHostInstanceForDeletion();
+  childToDelete.stateNode = instance;
+  childToDelete.return = returnFiber;
+  childToDelete.effectTag = Deletion;
+
+  // This might seem like it belongs on progressedFirstDeletion. However,
+  // these children are not part of the reconciliation list of children.
+  // Even if we abort and rereconcile the children, that will try to hydrate
+  // again and the nodes are still in the host tree so these will be
+  // recreated.
+  if (returnFiber.lastEffect !== null) {
+    returnFiber.lastEffect.nextEffect = childToDelete;
+    returnFiber.lastEffect = childToDelete;
+  } else {
+    returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
   }
+}
 
-  function commitWork(current, finishedWork) {
-    switch (finishedWork.tag) {
-      case ClassComponent: {
-        return;
+function insertNonHydratedInstance(returnFiber, fiber) {
+  fiber.effectTag |= Placement;
+  {
+    switch (returnFiber.tag) {
+      case HostRoot: {
+        var parentContainer = returnFiber.stateNode.containerInfo;
+        switch (fiber.tag) {
+          case HostComponent:
+            var type = fiber.type;
+            var props = fiber.pendingProps;
+            didNotFindHydratableContainerInstance(parentContainer, type, props);
+            break;
+          case HostText:
+            var text = fiber.pendingProps;
+            didNotFindHydratableContainerTextInstance(parentContainer, text);
+            break;
+        }
+        break;
       }
       case HostComponent: {
-        var _instance7 = finishedWork.stateNode;
-        if (_instance7 != null) {
-          // Commit the work prepared earlier.
-          var newProps = finishedWork.memoizedProps;
-          // For hydration we reuse the update path but we treat the oldProps
-          // as the newProps. The updatePayload will contain the real change in
-          // this case.
-          var oldProps = current !== null ? current.memoizedProps : newProps;
-          var type = finishedWork.type;
-          // TODO: Type the updateQueue to be specific to host components.
-          var updatePayload = finishedWork.updateQueue;
-          finishedWork.updateQueue = null;
-          if (updatePayload !== null) {
-            commitUpdate(
-              _instance7,
-              updatePayload,
-              type,
-              oldProps,
-              newProps,
-              finishedWork
+        var parentType = returnFiber.type;
+        var parentProps = returnFiber.memoizedProps;
+        var parentInstance = returnFiber.stateNode;
+        switch (fiber.tag) {
+          case HostComponent:
+            var _type = fiber.type;
+            var _props = fiber.pendingProps;
+            didNotFindHydratableInstance(
+              parentType,
+              parentProps,
+              parentInstance,
+              _type,
+              _props
             );
-          }
+            break;
+          case HostText:
+            var _text = fiber.pendingProps;
+            didNotFindHydratableTextInstance(
+              parentType,
+              parentProps,
+              parentInstance,
+              _text
+            );
+            break;
         }
-        return;
-      }
-      case HostText: {
-        invariant(
-          finishedWork.stateNode !== null,
-          "This should have a text node initialized. This error is likely " +
-            "caused by a bug in React. Please file an issue."
-        );
-        var textInstance = finishedWork.stateNode;
-        var newText = finishedWork.memoizedProps;
-        // For hydration we reuse the update path but we treat the oldProps
-        // as the newProps. The updatePayload will contain the real change in
-        // this case.
-        var oldText = current !== null ? current.memoizedProps : newText;
-        commitTextUpdate(textInstance, oldText, newText);
-        return;
+        break;
       }
-      case HostRoot: {
+      default:
         return;
-      }
-      case Profiler: {
-        if (enableProfilerTimer) {
-          var onRender = finishedWork.memoizedProps.onRender;
-          onRender(
-            finishedWork.memoizedProps.id,
-            current === null ? "mount" : "update",
-            finishedWork.stateNode.duration,
-            finishedWork.treeBaseTime
-          );
+    }
+  }
+}
 
-          // Reset actualTime after successful commit.
-          // By default, we append to this time to account for errors and pauses.
-          finishedWork.stateNode.duration = 0;
-        }
-        return;
-      }
-      case TimeoutComponent: {
-        return;
+function tryHydrate(fiber, nextInstance) {
+  switch (fiber.tag) {
+    case HostComponent: {
+      var type = fiber.type;
+      var props = fiber.pendingProps;
+      var instance = canHydrateInstance(nextInstance, type, props);
+      if (instance !== null) {
+        fiber.stateNode = instance;
+        return true;
       }
-      default: {
-        invariant(
-          false,
-          "This unit of work tag should not have side-effects. This error is " +
-            "likely caused by a bug in React. Please file an issue."
-        );
+      return false;
+    }
+    case HostText: {
+      var text = fiber.pendingProps;
+      var textInstance = canHydrateTextInstance(nextInstance, text);
+      if (textInstance !== null) {
+        fiber.stateNode = textInstance;
+        return true;
       }
+      return false;
     }
+    default:
+      return false;
   }
+}
 
-  function commitResetTextContent(current) {
-    resetTextContent(current.stateNode);
+function tryToClaimNextHydratableInstance(fiber) {
+  if (!isHydrating) {
+    return;
   }
-
-  if (enableMutatingReconciler) {
-    return {
-      commitBeforeMutationLifeCycles: commitBeforeMutationLifeCycles,
-      commitResetTextContent: commitResetTextContent,
-      commitPlacement: commitPlacement,
-      commitDeletion: commitDeletion,
-      commitWork: commitWork,
-      commitLifeCycles: commitLifeCycles,
-      commitAttachRef: commitAttachRef,
-      commitDetachRef: commitDetachRef
-    };
-  } else {
-    invariant(false, "Mutating reconciler is disabled.");
+  var nextInstance = nextHydratableInstance;
+  if (!nextInstance) {
+    // Nothing to hydrate. Make it an insertion.
+    insertNonHydratedInstance(hydrationParentFiber, fiber);
+    isHydrating = false;
+    hydrationParentFiber = fiber;
+    return;
   }
-};
+  var firstAttemptedInstance = nextInstance;
+  if (!tryHydrate(fiber, nextInstance)) {
+    // If we can't hydrate this instance let's try the next one.
+    // We use this as a heuristic. It's based on intuition and not data so it
+    // might be flawed or unnecessary.
+    nextInstance = getNextHydratableSibling(firstAttemptedInstance);
+    if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
+      // Nothing to hydrate. Make it an insertion.
+      insertNonHydratedInstance(hydrationParentFiber, fiber);
+      isHydrating = false;
+      hydrationParentFiber = fiber;
+      return;
+    }
+    // We matched the next one, we'll now assume that the first one was
+    // superfluous and we'll delete it. Since we can't eagerly delete it
+    // we'll have to schedule a deletion. To do that, this node needs a dummy
+    // fiber associated with it.
+    deleteHydratableInstance(hydrationParentFiber, firstAttemptedInstance);
+  }
+  hydrationParentFiber = fiber;
+  nextHydratableInstance = getFirstHydratableChild(nextInstance);
+}
 
-var ReactFiberUnwindWork = function(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  recalculateCurrentTime,
-  markLegacyErrorBoundaryAsFailed,
-  isAlreadyFailedLegacyErrorBoundary,
-  onUncaughtError,
-  profilerTimer,
-  suspendRoot,
-  retrySuspendedRoot
+function prepareToHydrateHostInstance(
+  fiber,
+  rootContainerInstance,
+  hostContext
 ) {
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext;
-  var popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject;
-  var popProvider = newContext.popProvider;
-  var resumeActualRenderTimerIfPaused =
-      profilerTimer.resumeActualRenderTimerIfPaused,
-    recordElapsedActualRenderTime = profilerTimer.recordElapsedActualRenderTime;
-
-  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
-    var update = createUpdate(expirationTime);
-    // Unmount the root by rendering null.
-    update.tag = CaptureUpdate;
-    // Caution: React DevTools currently depends on this property
-    // being called "element".
-    update.payload = { element: null };
-    var error = errorInfo.value;
-    update.callback = function() {
-      onUncaughtError(error);
-      logError(fiber, errorInfo);
-    };
-    return update;
+  if (!supportsHydration) {
+    invariant(
+      false,
+      "Expected prepareToHydrateHostInstance() to never be called. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
   }
 
-  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
-    var update = createUpdate(expirationTime);
-    update.tag = CaptureUpdate;
-    var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
-    if (
-      enableGetDerivedStateFromCatch &&
-      typeof getDerivedStateFromCatch === "function"
-    ) {
-      var _error = errorInfo.value;
-      update.payload = function() {
-        return getDerivedStateFromCatch(_error);
-      };
-    }
-
-    var inst = fiber.stateNode;
-    if (inst !== null && typeof inst.componentDidCatch === "function") {
-      update.callback = function callback() {
-        if (
-          !enableGetDerivedStateFromCatch ||
-          getDerivedStateFromCatch !== "function"
-        ) {
-          // To preserve the preexisting retry behavior of error boundaries,
-          // we keep track of which ones already failed during this batch.
-          // This gets reset before we yield back to the browser.
-          // TODO: Warn in strict mode if getDerivedStateFromCatch is
-          // not defined.
-          markLegacyErrorBoundaryAsFailed(this);
-        }
-        var error = errorInfo.value;
-        var stack = errorInfo.stack;
-        logError(fiber, errorInfo);
-        this.componentDidCatch(error, {
-          componentStack: stack !== null ? stack : ""
-        });
-      };
-    }
-    return update;
+  var instance = fiber.stateNode;
+  var updatePayload = hydrateInstance(
+    instance,
+    fiber.type,
+    fiber.memoizedProps,
+    rootContainerInstance,
+    hostContext,
+    fiber
+  );
+  // TODO: Type this specific to this type of component.
+  fiber.updateQueue = updatePayload;
+  // If the update payload indicates that there is a change or if there
+  // is a new ref we mark this as an update.
+  if (updatePayload !== null) {
+    return true;
   }
+  return false;
+}
 
-  function schedulePing(finishedWork) {
-    // Once the promise resolves, we should try rendering the non-
-    // placeholder state again.
-    var currentTime = recalculateCurrentTime();
-    var expirationTime = computeExpirationForFiber(currentTime, finishedWork);
-    var recoveryUpdate = createUpdate(expirationTime);
-    enqueueUpdate(finishedWork, recoveryUpdate, expirationTime);
-    scheduleWork(finishedWork, expirationTime);
+function prepareToHydrateHostTextInstance(fiber) {
+  if (!supportsHydration) {
+    invariant(
+      false,
+      "Expected prepareToHydrateHostTextInstance() to never be called. " +
+        "This error is likely caused by a bug in React. Please file an issue."
+    );
   }
 
-  function throwException(
-    root,
-    returnFiber,
-    sourceFiber,
-    value,
-    renderIsExpired,
-    renderExpirationTime,
-    currentTimeMs
-  ) {
-    // The source fiber did not complete.
-    sourceFiber.effectTag |= Incomplete;
-    // Its effect list is no longer valid.
-    sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-
-    if (
-      enableSuspense &&
-      value !== null &&
-      typeof value === "object" &&
-      typeof value.then === "function"
-    ) {
-      // This is a thenable.
-      var _thenable = value;
-
-      var expirationTimeMs = expirationTimeToMs(renderExpirationTime);
-      var startTimeMs = expirationTimeMs - 5000;
-      var elapsedMs = currentTimeMs - startTimeMs;
-      if (elapsedMs < 0) {
-        elapsedMs = 0;
-      }
-      var remainingTimeMs = expirationTimeMs - currentTimeMs;
-
-      // Find the earliest timeout of all the timeouts in the ancestor path.
-      // TODO: Alternatively, we could store the earliest timeout on the context
-      // stack, rather than searching on every suspend.
-      var _workInProgress = returnFiber;
-      var earliestTimeoutMs = -1;
-      searchForEarliestTimeout: do {
-        if (_workInProgress.tag === TimeoutComponent) {
-          var current = _workInProgress.alternate;
-          if (current !== null && current.memoizedState === true) {
-            // A parent Timeout already committed in a placeholder state. We
-            // need to handle this promise immediately. In other words, we
-            // should never suspend inside a tree that already expired.
-            earliestTimeoutMs = 0;
-            break searchForEarliestTimeout;
+  var textInstance = fiber.stateNode;
+  var textContent = fiber.memoizedProps;
+  var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
+  {
+    if (shouldUpdate) {
+      // We assume that prepareToHydrateHostTextInstance is called in a context where the
+      // hydration parent is the parent host component of this host text.
+      var returnFiber = hydrationParentFiber;
+      if (returnFiber !== null) {
+        switch (returnFiber.tag) {
+          case HostRoot: {
+            var parentContainer = returnFiber.stateNode.containerInfo;
+            didNotMatchHydratedContainerTextInstance(
+              parentContainer,
+              textInstance,
+              textContent
+            );
+            break;
           }
-          var timeoutPropMs = _workInProgress.pendingProps.ms;
-          if (typeof timeoutPropMs === "number") {
-            if (timeoutPropMs <= 0) {
-              earliestTimeoutMs = 0;
-              break searchForEarliestTimeout;
-            } else if (
-              earliestTimeoutMs === -1 ||
-              timeoutPropMs < earliestTimeoutMs
-            ) {
-              earliestTimeoutMs = timeoutPropMs;
-            }
-          } else if (earliestTimeoutMs === -1) {
-            earliestTimeoutMs = remainingTimeMs;
+          case HostComponent: {
+            var parentType = returnFiber.type;
+            var parentProps = returnFiber.memoizedProps;
+            var parentInstance = returnFiber.stateNode;
+            didNotMatchHydratedTextInstance(
+              parentType,
+              parentProps,
+              parentInstance,
+              textInstance,
+              textContent
+            );
+            break;
           }
         }
-        _workInProgress = _workInProgress.return;
-      } while (_workInProgress !== null);
-
-      // Compute the remaining time until the timeout.
-      var msUntilTimeout = earliestTimeoutMs - elapsedMs;
-
-      if (renderExpirationTime === Never || msUntilTimeout > 0) {
-        // There's still time remaining.
-        suspendRoot(root, _thenable, msUntilTimeout, renderExpirationTime);
-        var onResolveOrReject = function() {
-          retrySuspendedRoot(root, renderExpirationTime);
-        };
-        _thenable.then(onResolveOrReject, onResolveOrReject);
-        return;
-      } else {
-        // No time remaining. Need to fallback to placeholder.
-        // Find the nearest timeout that can be retried.
-        _workInProgress = returnFiber;
-        do {
-          switch (_workInProgress.tag) {
-            case HostRoot: {
-              // The root expired, but no fallback was provided. Throw a
-              // helpful error.
-              var message =
-                renderExpirationTime === Sync
-                  ? "A synchronous update was suspended, but no fallback UI " +
-                    "was provided."
-                  : "An update was suspended for longer than the timeout, " +
-                    "but no fallback UI was provided.";
-              value = new Error(message);
-              break;
-            }
-            case TimeoutComponent: {
-              if ((_workInProgress.effectTag & DidCapture) === NoEffect) {
-                _workInProgress.effectTag |= ShouldCapture;
-                var _onResolveOrReject = schedulePing.bind(
-                  null,
-                  _workInProgress
-                );
-                _thenable.then(_onResolveOrReject, _onResolveOrReject);
-                return;
-              }
-              // Already captured during this render. Continue to the next
-              // Timeout ancestor.
-              break;
-            }
-          }
-          _workInProgress = _workInProgress.return;
-        } while (_workInProgress !== null);
       }
     }
+  }
+  return shouldUpdate;
+}
 
-    // We didn't find a boundary that could handle this type of exception. Start
-    // over and traverse parent path again, this time treating the exception
-    // as an error.
-    value = createCapturedValue(value, sourceFiber);
-    var workInProgress = returnFiber;
-    do {
-      switch (workInProgress.tag) {
-        case HostRoot: {
-          var _errorInfo = value;
-          workInProgress.effectTag |= ShouldCapture;
-          var update = createRootErrorUpdate(
-            workInProgress,
-            _errorInfo,
-            renderExpirationTime
-          );
-          enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
-          return;
-        }
-        case ClassComponent:
-          // Capture and retry
-          var errorInfo = value;
-          var ctor = workInProgress.type;
-          var _instance = workInProgress.stateNode;
-          if (
-            (workInProgress.effectTag & DidCapture) === NoEffect &&
-            ((typeof ctor.getDerivedStateFromCatch === "function" &&
-              enableGetDerivedStateFromCatch) ||
-              (_instance !== null &&
-                typeof _instance.componentDidCatch === "function" &&
-                !isAlreadyFailedLegacyErrorBoundary(_instance)))
-          ) {
-            workInProgress.effectTag |= ShouldCapture;
-            // Schedule the error boundary to re-render using updated state
-            var _update = createClassErrorUpdate(
-              workInProgress,
-              errorInfo,
-              renderExpirationTime
-            );
-            enqueueCapturedUpdate(
-              workInProgress,
-              _update,
-              renderExpirationTime
-            );
-            return;
-          }
-          break;
-        default:
-          break;
-      }
-      workInProgress = workInProgress.return;
-    } while (workInProgress !== null);
+function popToNextHostParent(fiber) {
+  var parent = fiber.return;
+  while (
+    parent !== null &&
+    parent.tag !== HostComponent &&
+    parent.tag !== HostRoot
+  ) {
+    parent = parent.return;
   }
+  hydrationParentFiber = parent;
+}
 
-  function unwindWork(workInProgress, renderIsExpired, renderExpirationTime) {
-    switch (workInProgress.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(workInProgress);
-        var effectTag = workInProgress.effectTag;
-        if (effectTag & ShouldCapture) {
-          workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostRoot: {
-        popHostContainer(workInProgress);
-        popTopLevelLegacyContextObject(workInProgress);
-        var _effectTag = workInProgress.effectTag;
-        if (_effectTag & ShouldCapture) {
-          workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostComponent: {
-        popHostContext(workInProgress);
-        return null;
-      }
-      case TimeoutComponent: {
-        var _effectTag2 = workInProgress.effectTag;
-        if (_effectTag2 & ShouldCapture) {
-          workInProgress.effectTag =
-            (_effectTag2 & ~ShouldCapture) | DidCapture;
-          return workInProgress;
-        }
-        return null;
-      }
-      case HostPortal:
-        popHostContainer(workInProgress);
-        return null;
-      case ContextProvider:
-        popProvider(workInProgress);
-        return null;
-      default:
-        return null;
-    }
+function popHydrationState(fiber) {
+  if (!supportsHydration) {
+    return false;
+  }
+  if (fiber !== hydrationParentFiber) {
+    // We're deeper than the current hydration context, inside an inserted
+    // tree.
+    return false;
+  }
+  if (!isHydrating) {
+    // If we're not currently hydrating but we're in a hydration context, then
+    // we were an insertion and now need to pop up reenter hydration of our
+    // siblings.
+    popToNextHostParent(fiber);
+    isHydrating = true;
+    return false;
   }
 
-  function unwindInterruptedWork(interruptedWork) {
-    switch (interruptedWork.tag) {
-      case ClassComponent: {
-        popLegacyContextProvider(interruptedWork);
-        break;
-      }
-      case HostRoot: {
-        popHostContainer(interruptedWork);
-        popTopLevelLegacyContextObject(interruptedWork);
-        break;
-      }
-      case HostComponent: {
-        popHostContext(interruptedWork);
-        break;
-      }
-      case HostPortal:
-        popHostContainer(interruptedWork);
-        break;
-      case ContextProvider:
-        popProvider(interruptedWork);
-        break;
-      case Profiler:
-        if (enableProfilerTimer) {
-          // Resume in case we're picking up on work that was paused.
-          resumeActualRenderTimerIfPaused();
-          recordElapsedActualRenderTime(interruptedWork);
-        }
-        break;
-      default:
-        break;
+  var type = fiber.type;
+
+  // If we have any remaining hydratable nodes, we need to delete them now.
+  // We only do this deeper than head and body since they tend to have random
+  // other nodes in them. We also ignore components with pure text content in
+  // side of them.
+  // TODO: Better heuristic.
+  if (
+    fiber.tag !== HostComponent ||
+    (type !== "head" &&
+      type !== "body" &&
+      !shouldSetTextContent(type, fiber.memoizedProps))
+  ) {
+    var nextInstance = nextHydratableInstance;
+    while (nextInstance) {
+      deleteHydratableInstance(fiber, nextInstance);
+      nextInstance = getNextHydratableSibling(nextInstance);
     }
   }
 
-  return {
-    throwException: throwException,
-    unwindWork: unwindWork,
-    unwindInterruptedWork: unwindInterruptedWork,
-    createRootErrorUpdate: createRootErrorUpdate,
-    createClassErrorUpdate: createClassErrorUpdate
-  };
-};
+  popToNextHostParent(fiber);
+  nextHydratableInstance = hydrationParentFiber
+    ? getNextHydratableSibling(fiber.stateNode)
+    : null;
+  return true;
+}
+
+function resetHydrationState() {
+  if (!supportsHydration) {
+    return;
+  }
+
+  hydrationParentFiber = null;
+  nextHydratableInstance = null;
+  isHydrating = false;
+}
+
+var getCurrentFiberStackAddendum$1 =
+  ReactDebugCurrentFiber.getCurrentFiberStackAddendum;
+
+var didWarnAboutBadClass = void 0;
+var didWarnAboutGetDerivedStateOnFunctionalComponent = void 0;
+var didWarnAboutStatelessRefs = void 0;
 
-var NO_CONTEXT = {};
+{
+  didWarnAboutBadClass = {};
+  didWarnAboutGetDerivedStateOnFunctionalComponent = {};
+  didWarnAboutStatelessRefs = {};
+}
 
-var ReactFiberHostContext = function(config, stack) {
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
+// TODO: Remove this and use reconcileChildrenAtExpirationTime directly.
+function reconcileChildren(current, workInProgress, nextChildren) {
+  reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    workInProgress.expirationTime
+  );
+}
 
-  var contextStackCursor = createCursor(NO_CONTEXT);
-  var contextFiberStackCursor = createCursor(NO_CONTEXT);
-  var rootInstanceStackCursor = createCursor(NO_CONTEXT);
+function reconcileChildrenAtExpirationTime(
+  current,
+  workInProgress,
+  nextChildren,
+  renderExpirationTime
+) {
+  if (current === null) {
+    // If this is a fresh new component that hasn't been rendered yet, we
+    // won't update its child set by applying minimal side-effects. Instead,
+    // we will add them all to the child before it gets rendered. That means
+    // we can optimize this reconciliation pass by not tracking side-effects.
+    workInProgress.child = mountChildFibers(
+      workInProgress,
+      null,
+      nextChildren,
+      renderExpirationTime
+    );
+  } else {
+    // If the current child is the same as the work in progress, it means that
+    // we haven't yet started any work on these children. Therefore, we use
+    // the clone algorithm to create a copy of all the current children.
 
-  function requiredContext(c) {
-    invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug " +
-        "in React. Please file an issue."
+    // If we had any progressed work already, that is invalid at this point so
+    // let's throw it out.
+    workInProgress.child = reconcileChildFibers(
+      workInProgress,
+      current.child,
+      nextChildren,
+      renderExpirationTime
     );
-    return c;
   }
+}
 
-  function getRootHostContainer() {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    return rootInstance;
+function updateForwardRef(current, workInProgress) {
+  var render = workInProgress.type.render;
+  var nextProps = workInProgress.pendingProps;
+  var ref = workInProgress.ref;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (workInProgress.memoizedProps === nextProps) {
+    var currentRef = current !== null ? current.ref : null;
+    if (ref === currentRef) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
   }
 
-  function pushHostContainer(fiber, nextRootInstance) {
-    // Push current root instance onto the stack;
-    // This allows us to reset root when portals are popped.
-    push(rootInstanceStackCursor, nextRootInstance, fiber);
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
-
-    // Finally, we need to push the host context to the stack.
-    // However, we can't just call getRootHostContext() and push it because
-    // we'd have a different number of entries on the stack depending on
-    // whether getRootHostContext() throws somewhere in renderer code or not.
-    // So we push an empty value first. This lets us safely unwind on errors.
-    push(contextStackCursor, NO_CONTEXT, fiber);
-    var nextRootContext = getRootHostContext(nextRootInstance);
-    // Now that we know this function doesn't throw, replace it.
-    pop(contextStackCursor, fiber);
-    push(contextStackCursor, nextRootContext, fiber);
+  var nextChildren = void 0;
+  {
+    ReactCurrentOwner.current = workInProgress;
+    ReactDebugCurrentFiber.setCurrentPhase("render");
+    nextChildren = render(nextProps, ref);
+    ReactDebugCurrentFiber.setCurrentPhase(null);
   }
 
-  function popHostContainer(fiber) {
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
-    pop(rootInstanceStackCursor, fiber);
-  }
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextProps);
+  return workInProgress.child;
+}
 
-  function getHostContext() {
-    var context = requiredContext(contextStackCursor.current);
-    return context;
+function updateFragment(current, workInProgress) {
+  var nextChildren = workInProgress.pendingProps;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (workInProgress.memoizedProps === nextChildren) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextChildren);
+  return workInProgress.child;
+}
 
-  function pushHostContext(fiber) {
-    var rootInstance = requiredContext(rootInstanceStackCursor.current);
-    var context = requiredContext(contextStackCursor.current);
-    var nextContext = getChildHostContext(context, fiber.type, rootInstance);
+function updateMode(current, workInProgress) {
+  var nextChildren = workInProgress.pendingProps.children;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (
+    nextChildren === null ||
+    workInProgress.memoizedProps === nextChildren
+  ) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  }
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextChildren);
+  return workInProgress.child;
+}
 
-    // Don't push this Fiber's context unless it's unique.
-    if (context === nextContext) {
-      return;
-    }
+function updateProfiler(current, workInProgress) {
+  var nextProps = workInProgress.pendingProps;
+  if (enableProfilerTimer) {
+    workInProgress.effectTag |= Update;
+  }
+  if (workInProgress.memoizedProps === nextProps) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  }
+  var nextChildren = nextProps.children;
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextProps);
+  return workInProgress.child;
+}
 
-    // Track the context and the Fiber that provided it.
-    // This enables us to pop only Fibers that provide unique contexts.
-    push(contextFiberStackCursor, fiber, fiber);
-    push(contextStackCursor, nextContext, fiber);
+function markRef(current, workInProgress) {
+  var ref = workInProgress.ref;
+  if (
+    (current === null && ref !== null) ||
+    (current !== null && current.ref !== ref)
+  ) {
+    // Schedule a Ref effect
+    workInProgress.effectTag |= Ref;
   }
+}
 
-  function popHostContext(fiber) {
-    // Do not pop unless this Fiber provided the current context.
-    // pushHostContext() only pushes Fibers that provide unique contexts.
-    if (contextFiberStackCursor.current !== fiber) {
-      return;
-    }
+function updateFunctionalComponent(current, workInProgress) {
+  var fn = workInProgress.type;
+  var nextProps = workInProgress.pendingProps;
 
-    pop(contextStackCursor, fiber);
-    pop(contextFiberStackCursor, fiber);
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else {
+    if (workInProgress.memoizedProps === nextProps) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    // TODO: consider bringing fn.shouldComponentUpdate() back.
+    // It used to be here.
   }
 
-  return {
-    getHostContext: getHostContext,
-    getRootHostContainer: getRootHostContainer,
-    popHostContainer: popHostContainer,
-    popHostContext: popHostContext,
-    pushHostContainer: pushHostContainer,
-    pushHostContext: pushHostContext
-  };
-};
-
-var ReactFiberHydrationContext = function(config) {
-  var shouldSetTextContent = config.shouldSetTextContent,
-    hydration = config.hydration;
+  var unmaskedContext = getUnmaskedContext(workInProgress);
+  var context = getMaskedContext(workInProgress, unmaskedContext);
 
-  // If this doesn't have hydration mode.
+  var nextChildren = void 0;
 
-  if (!hydration) {
-    return {
-      enterHydrationState: function() {
-        return false;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
-        invariant(
-          false,
-          "Expected prepareToHydrateHostTextInstance() to never be called. " +
-            "This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      popHydrationState: function(fiber) {
-        return false;
-      }
-    };
-  }
+  {
+    ReactCurrentOwner.current = workInProgress;
+    ReactDebugCurrentFiber.setCurrentPhase("render");
+    nextChildren = fn(nextProps, context);
+    ReactDebugCurrentFiber.setCurrentPhase(null);
+  }
+  // React DevTools reads this flag.
+  workInProgress.effectTag |= PerformedWork;
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextProps);
+  return workInProgress.child;
+}
+
+function updateClassComponent(current, workInProgress, renderExpirationTime) {
+  // Push context providers early to prevent context stack mismatches.
+  // During mounting we don't know the child context yet as the instance doesn't exist.
+  // We will invalidate the child context in finishClassComponent() right after rendering.
+  var hasContext = pushContextProvider(workInProgress);
+  var shouldUpdate = void 0;
+  if (current === null) {
+    if (workInProgress.stateNode === null) {
+      // In the initial pass we might need to construct the instance.
+      constructClassInstance(
+        workInProgress,
+        workInProgress.pendingProps,
+        renderExpirationTime
+      );
+      mountClassInstance(workInProgress, renderExpirationTime);
 
-  var canHydrateInstance = hydration.canHydrateInstance,
-    canHydrateTextInstance = hydration.canHydrateTextInstance,
-    getNextHydratableSibling = hydration.getNextHydratableSibling,
-    getFirstHydratableChild = hydration.getFirstHydratableChild,
-    hydrateInstance = hydration.hydrateInstance,
-    hydrateTextInstance = hydration.hydrateTextInstance,
-    didNotMatchHydratedContainerTextInstance =
-      hydration.didNotMatchHydratedContainerTextInstance,
-    didNotMatchHydratedTextInstance = hydration.didNotMatchHydratedTextInstance,
-    didNotHydrateContainerInstance = hydration.didNotHydrateContainerInstance,
-    didNotHydrateInstance = hydration.didNotHydrateInstance,
-    didNotFindHydratableContainerInstance =
-      hydration.didNotFindHydratableContainerInstance,
-    didNotFindHydratableContainerTextInstance =
-      hydration.didNotFindHydratableContainerTextInstance,
-    didNotFindHydratableInstance = hydration.didNotFindHydratableInstance,
-    didNotFindHydratableTextInstance =
-      hydration.didNotFindHydratableTextInstance;
-
-  // The deepest Fiber on the stack involved in a hydration context.
-  // This may have been an insertion or a hydration.
-
-  var hydrationParentFiber = null;
-  var nextHydratableInstance = null;
-  var isHydrating = false;
-
-  function enterHydrationState(fiber) {
-    var parentInstance = fiber.stateNode.containerInfo;
-    nextHydratableInstance = getFirstHydratableChild(parentInstance);
-    hydrationParentFiber = fiber;
-    isHydrating = true;
-    return true;
+      shouldUpdate = true;
+    } else {
+      // In a resume, we'll already have an instance we can reuse.
+      shouldUpdate = resumeMountClassInstance(
+        workInProgress,
+        renderExpirationTime
+      );
+    }
+  } else {
+    shouldUpdate = updateClassInstance(
+      current,
+      workInProgress,
+      renderExpirationTime
+    );
   }
+  return finishClassComponent(
+    current,
+    workInProgress,
+    shouldUpdate,
+    hasContext,
+    renderExpirationTime
+  );
+}
 
-  function deleteHydratableInstance(returnFiber, instance) {
-    {
-      switch (returnFiber.tag) {
-        case HostRoot:
-          didNotHydrateContainerInstance(
-            returnFiber.stateNode.containerInfo,
-            instance
-          );
-          break;
-        case HostComponent:
-          didNotHydrateInstance(
-            returnFiber.type,
-            returnFiber.memoizedProps,
-            returnFiber.stateNode,
-            instance
-          );
-          break;
-      }
-    }
+function finishClassComponent(
+  current,
+  workInProgress,
+  shouldUpdate,
+  hasContext,
+  renderExpirationTime
+) {
+  // Refs should update even if shouldComponentUpdate returns false
+  markRef(current, workInProgress);
 
-    var childToDelete = createFiberFromHostInstanceForDeletion();
-    childToDelete.stateNode = instance;
-    childToDelete.return = returnFiber;
-    childToDelete.effectTag = Deletion;
+  var didCaptureError = (workInProgress.effectTag & DidCapture) !== NoEffect;
 
-    // This might seem like it belongs on progressedFirstDeletion. However,
-    // these children are not part of the reconciliation list of children.
-    // Even if we abort and rereconcile the children, that will try to hydrate
-    // again and the nodes are still in the host tree so these will be
-    // recreated.
-    if (returnFiber.lastEffect !== null) {
-      returnFiber.lastEffect.nextEffect = childToDelete;
-      returnFiber.lastEffect = childToDelete;
-    } else {
-      returnFiber.firstEffect = returnFiber.lastEffect = childToDelete;
+  if (!shouldUpdate && !didCaptureError) {
+    // Context providers should defer to sCU for rendering
+    if (hasContext) {
+      invalidateContextProvider(workInProgress, false);
     }
+
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
 
-  function insertNonHydratedInstance(returnFiber, fiber) {
-    fiber.effectTag |= Placement;
+  var ctor = workInProgress.type;
+  var instance = workInProgress.stateNode;
+
+  // Rerender
+  ReactCurrentOwner.current = workInProgress;
+  var nextChildren = void 0;
+  if (
+    didCaptureError &&
+    (!enableGetDerivedStateFromCatch ||
+      typeof ctor.getDerivedStateFromCatch !== "function")
+  ) {
+    // If we captured an error, but getDerivedStateFrom catch is not defined,
+    // unmount all the children. componentDidCatch will schedule an update to
+    // re-render a fallback. This is temporary until we migrate everyone to
+    // the new API.
+    // TODO: Warn in a future release.
+    nextChildren = null;
+
+    if (enableProfilerTimer) {
+      stopBaseRenderTimerIfRunning();
+    }
+  } else {
     {
-      switch (returnFiber.tag) {
-        case HostRoot: {
-          var parentContainer = returnFiber.stateNode.containerInfo;
-          switch (fiber.tag) {
-            case HostComponent:
-              var type = fiber.type;
-              var props = fiber.pendingProps;
-              didNotFindHydratableContainerInstance(
-                parentContainer,
-                type,
-                props
-              );
-              break;
-            case HostText:
-              var text = fiber.pendingProps;
-              didNotFindHydratableContainerTextInstance(parentContainer, text);
-              break;
-          }
-          break;
-        }
-        case HostComponent: {
-          var parentType = returnFiber.type;
-          var parentProps = returnFiber.memoizedProps;
-          var parentInstance = returnFiber.stateNode;
-          switch (fiber.tag) {
-            case HostComponent:
-              var _type = fiber.type;
-              var _props = fiber.pendingProps;
-              didNotFindHydratableInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _type,
-                _props
-              );
-              break;
-            case HostText:
-              var _text = fiber.pendingProps;
-              didNotFindHydratableTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                _text
-              );
-              break;
-          }
-          break;
-        }
-        default:
-          return;
+      ReactDebugCurrentFiber.setCurrentPhase("render");
+      nextChildren = instance.render();
+      if (
+        debugRenderPhaseSideEffects ||
+        (debugRenderPhaseSideEffectsForStrictMode &&
+          workInProgress.mode & StrictMode)
+      ) {
+        instance.render();
       }
+      ReactDebugCurrentFiber.setCurrentPhase(null);
     }
   }
 
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case HostComponent: {
-        var type = fiber.type;
-        var props = fiber.pendingProps;
-        var instance = canHydrateInstance(nextInstance, type, props);
-        if (instance !== null) {
-          fiber.stateNode = instance;
-          return true;
-        }
-        return false;
-      }
-      case HostText: {
-        var text = fiber.pendingProps;
-        var textInstance = canHydrateTextInstance(nextInstance, text);
-        if (textInstance !== null) {
-          fiber.stateNode = textInstance;
-          return true;
-        }
-        return false;
-      }
-      default:
-        return false;
-    }
+  // React DevTools reads this flag.
+  workInProgress.effectTag |= PerformedWork;
+  if (didCaptureError) {
+    // If we're recovering from an error, reconcile twice: first to delete
+    // all the existing children.
+    reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      null,
+      renderExpirationTime
+    );
+    workInProgress.child = null;
+    // Now we can continue reconciling like normal. This has the effect of
+    // remounting all children regardless of whether their their
+    // identity matches.
   }
+  reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    renderExpirationTime
+  );
+  // Memoize props and state using the values we just used to render.
+  // TODO: Restructure so we never read values from the instance.
+  memoizeState(workInProgress, instance.state);
+  memoizeProps(workInProgress, instance.props);
 
-  function tryToClaimNextHydratableInstance(fiber) {
-    if (!isHydrating) {
-      return;
-    }
-    var nextInstance = nextHydratableInstance;
-    if (!nextInstance) {
-      // Nothing to hydrate. Make it an insertion.
-      insertNonHydratedInstance(hydrationParentFiber, fiber);
-      isHydrating = false;
-      hydrationParentFiber = fiber;
-      return;
-    }
-    if (!tryHydrate(fiber, nextInstance)) {
-      // If we can't hydrate this instance let's try the next one.
-      // We use this as a heuristic. It's based on intuition and not data so it
-      // might be flawed or unnecessary.
-      nextInstance = getNextHydratableSibling(nextInstance);
-      if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-        // Nothing to hydrate. Make it an insertion.
-        insertNonHydratedInstance(hydrationParentFiber, fiber);
-        isHydrating = false;
-        hydrationParentFiber = fiber;
-        return;
-      }
-      // We matched the next one, we'll now assume that the first one was
-      // superfluous and we'll delete it. Since we can't eagerly delete it
-      // we'll have to schedule a deletion. To do that, this node needs a dummy
-      // fiber associated with it.
-      deleteHydratableInstance(hydrationParentFiber, nextHydratableInstance);
-    }
-    hydrationParentFiber = fiber;
-    nextHydratableInstance = getFirstHydratableChild(nextInstance);
+  // The context might have changed so we need to recalculate it.
+  if (hasContext) {
+    invalidateContextProvider(workInProgress, true);
   }
 
-  function prepareToHydrateHostInstance(
-    fiber,
-    rootContainerInstance,
-    hostContext
-  ) {
-    var instance = fiber.stateNode;
-    var updatePayload = hydrateInstance(
-      instance,
-      fiber.type,
-      fiber.memoizedProps,
-      rootContainerInstance,
-      hostContext,
-      fiber
+  return workInProgress.child;
+}
+
+function pushHostRootContext(workInProgress) {
+  var root = workInProgress.stateNode;
+  if (root.pendingContext) {
+    pushTopLevelContextObject(
+      workInProgress,
+      root.pendingContext,
+      root.pendingContext !== root.context
     );
-    // TODO: Type this specific to this type of component.
-    fiber.updateQueue = updatePayload;
-    // If the update payload indicates that there is a change or if there
-    // is a new ref we mark this as an update.
-    if (updatePayload !== null) {
-      return true;
-    }
-    return false;
+  } else if (root.context) {
+    // Should always be set
+    pushTopLevelContextObject(workInProgress, root.context, false);
   }
+  pushHostContainer(workInProgress, root.containerInfo);
+}
 
-  function prepareToHydrateHostTextInstance(fiber) {
-    var textInstance = fiber.stateNode;
-    var textContent = fiber.memoizedProps;
-    var shouldUpdate = hydrateTextInstance(textInstance, textContent, fiber);
-    {
-      if (shouldUpdate) {
-        // We assume that prepareToHydrateHostTextInstance is called in a context where the
-        // hydration parent is the parent host component of this host text.
-        var returnFiber = hydrationParentFiber;
-        if (returnFiber !== null) {
-          switch (returnFiber.tag) {
-            case HostRoot: {
-              var parentContainer = returnFiber.stateNode.containerInfo;
-              didNotMatchHydratedContainerTextInstance(
-                parentContainer,
-                textInstance,
-                textContent
-              );
-              break;
-            }
-            case HostComponent: {
-              var parentType = returnFiber.type;
-              var parentProps = returnFiber.memoizedProps;
-              var parentInstance = returnFiber.stateNode;
-              didNotMatchHydratedTextInstance(
-                parentType,
-                parentProps,
-                parentInstance,
-                textInstance,
-                textContent
-              );
-              break;
-            }
-          }
-        }
-      }
-    }
-    return shouldUpdate;
-  }
+function updateHostRoot(current, workInProgress, renderExpirationTime) {
+  pushHostRootContext(workInProgress);
+  var updateQueue = workInProgress.updateQueue;
+  if (updateQueue !== null) {
+    var nextProps = workInProgress.pendingProps;
+    var prevState = workInProgress.memoizedState;
+    var prevChildren = prevState !== null ? prevState.element : null;
+    processUpdateQueue(
+      workInProgress,
+      updateQueue,
+      nextProps,
+      null,
+      renderExpirationTime
+    );
+    var nextState = workInProgress.memoizedState;
+    // Caution: React DevTools currently depends on this property
+    // being called "element".
+    var nextChildren = nextState.element;
 
-  function popToNextHostParent(fiber) {
-    var parent = fiber.return;
-    while (
-      parent !== null &&
-      parent.tag !== HostComponent &&
-      parent.tag !== HostRoot
+    if (nextChildren === prevChildren) {
+      // If the state is the same as before, that's a bailout because we had
+      // no work that expires at this time.
+      resetHydrationState();
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
+    }
+    var root = workInProgress.stateNode;
+    if (
+      (current === null || current.child === null) &&
+      root.hydrate &&
+      enterHydrationState(workInProgress)
     ) {
-      parent = parent.return;
+      // If we don't have any current children this might be the first pass.
+      // We always try to hydrate. If this isn't a hydration pass there won't
+      // be any children to hydrate which is effectively the same thing as
+      // not hydrating.
+
+      // This is a bit of a hack. We track the host root as a placement to
+      // know that we're currently in a mounting state. That way isMounted
+      // works as expected. We must reset this before committing.
+      // TODO: Delete this when we delete isMounted and findDOMNode.
+      workInProgress.effectTag |= Placement;
+
+      // Ensure that children mount into this root without tracking
+      // side-effects. This ensures that we don't store Placement effects on
+      // nodes that will be hydrated.
+      workInProgress.child = mountChildFibers(
+        workInProgress,
+        null,
+        nextChildren,
+        renderExpirationTime
+      );
+    } else {
+      // Otherwise reset hydration state in case we aborted and resumed another
+      // root.
+      resetHydrationState();
+      reconcileChildren(current, workInProgress, nextChildren);
     }
-    hydrationParentFiber = parent;
+    return workInProgress.child;
   }
+  resetHydrationState();
+  // If there is no update queue, that's a bailout because the root has no props.
+  return bailoutOnAlreadyFinishedWork(current, workInProgress);
+}
 
-  function popHydrationState(fiber) {
-    if (fiber !== hydrationParentFiber) {
-      // We're deeper than the current hydration context, inside an inserted
-      // tree.
-      return false;
-    }
-    if (!isHydrating) {
-      // If we're not currently hydrating but we're in a hydration context, then
-      // we were an insertion and now need to pop up reenter hydration of our
-      // siblings.
-      popToNextHostParent(fiber);
-      isHydrating = true;
-      return false;
-    }
+function updateHostComponent(current, workInProgress, renderExpirationTime) {
+  pushHostContext(workInProgress);
 
-    var type = fiber.type;
+  if (current === null) {
+    tryToClaimNextHydratableInstance(workInProgress);
+  }
 
-    // If we have any remaining hydratable nodes, we need to delete them now.
-    // We only do this deeper than head and body since they tend to have random
-    // other nodes in them. We also ignore components with pure text content in
-    // side of them.
-    // TODO: Better heuristic.
-    if (
-      fiber.tag !== HostComponent ||
-      (type !== "head" &&
-        type !== "body" &&
-        !shouldSetTextContent(type, fiber.memoizedProps))
-    ) {
-      var nextInstance = nextHydratableInstance;
-      while (nextInstance) {
-        deleteHydratableInstance(fiber, nextInstance);
-        nextInstance = getNextHydratableSibling(nextInstance);
-      }
+  var type = workInProgress.type;
+  var memoizedProps = workInProgress.memoizedProps;
+  var nextProps = workInProgress.pendingProps;
+  var prevProps = current !== null ? current.memoizedProps : null;
+
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (memoizedProps === nextProps) {
+    var isHidden =
+      workInProgress.mode & AsyncMode &&
+      shouldDeprioritizeSubtree(type, nextProps);
+    if (isHidden) {
+      // Before bailing out, make sure we've deprioritized a hidden component.
+      workInProgress.expirationTime = Never;
+    }
+    if (!isHidden || renderExpirationTime !== Never) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
+    // If we're rendering a hidden node at hidden priority, don't bailout. The
+    // parent is complete, but the children may not be.
+  }
 
-    popToNextHostParent(fiber);
-    nextHydratableInstance = hydrationParentFiber
-      ? getNextHydratableSibling(fiber.stateNode)
-      : null;
-    return true;
+  var nextChildren = nextProps.children;
+  var isDirectTextChild = shouldSetTextContent(type, nextProps);
+
+  if (isDirectTextChild) {
+    // We special case a direct text child of a host node. This is a common
+    // case. We won't handle it as a reified child. We will instead handle
+    // this in the host environment that also have access to this prop. That
+    // avoids allocating another HostText fiber and traversing it.
+    nextChildren = null;
+  } else if (prevProps && shouldSetTextContent(type, prevProps)) {
+    // If we're switching from a direct text child to a normal child, or to
+    // empty, we need to schedule the text content to be reset.
+    workInProgress.effectTag |= ContentReset;
   }
 
-  function resetHydrationState() {
-    hydrationParentFiber = null;
-    nextHydratableInstance = null;
-    isHydrating = false;
+  markRef(current, workInProgress);
+
+  // Check the host config to see if the children are offscreen/hidden.
+  if (
+    renderExpirationTime !== Never &&
+    workInProgress.mode & AsyncMode &&
+    shouldDeprioritizeSubtree(type, nextProps)
+  ) {
+    // Down-prioritize the children.
+    workInProgress.expirationTime = Never;
+    // Bailout and come back to this fiber later.
+    workInProgress.memoizedProps = nextProps;
+    return null;
   }
 
-  return {
-    enterHydrationState: enterHydrationState,
-    resetHydrationState: resetHydrationState,
-    tryToClaimNextHydratableInstance: tryToClaimNextHydratableInstance,
-    prepareToHydrateHostInstance: prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance: prepareToHydrateHostTextInstance,
-    popHydrationState: popHydrationState
-  };
-};
+  reconcileChildren(current, workInProgress, nextChildren);
+  memoizeProps(workInProgress, nextProps);
+  return workInProgress.child;
+}
 
-// This lets us hook into Fiber to debug what it's doing.
-// See https://github.com/facebook/react/pull/8033.
-// This is not part of the public API, not even for React DevTools.
-// You may only inject a debugTool if you work on React Fiber itself.
-var ReactFiberInstrumentation = {
-  debugTool: null
-};
+function updateHostText(current, workInProgress) {
+  if (current === null) {
+    tryToClaimNextHydratableInstance(workInProgress);
+  }
+  var nextProps = workInProgress.pendingProps;
+  memoizeProps(workInProgress, nextProps);
+  // Nothing to do here. This is terminal. We'll do the completion step
+  // immediately after.
+  return null;
+}
 
-var ReactFiberInstrumentation_1 = ReactFiberInstrumentation;
+function mountIndeterminateComponent(
+  current,
+  workInProgress,
+  renderExpirationTime
+) {
+  invariant(
+    current === null,
+    "An indeterminate component should never have mounted. This error is " +
+      "likely caused by a bug in React. Please file an issue."
+  );
+  var fn = workInProgress.type;
+  var props = workInProgress.pendingProps;
+  var unmaskedContext = getUnmaskedContext(workInProgress);
+  var context = getMaskedContext(workInProgress, unmaskedContext);
 
-// TODO: Offscreen updates
+  var value = void 0;
 
-function markPendingPriorityLevel(root, expirationTime) {
-  if (enableSuspense) {
-    // Update the latest and earliest pending times
-    var earliestPendingTime = root.earliestPendingTime;
-    if (earliestPendingTime === NoWork) {
-      // No other pending updates.
-      root.earliestPendingTime = root.latestPendingTime = expirationTime;
-    } else {
-      if (earliestPendingTime > expirationTime) {
-        // This is the earliest pending update.
-        root.earliestPendingTime = expirationTime;
-      } else {
-        var latestPendingTime = root.latestPendingTime;
-        if (latestPendingTime < expirationTime) {
-          // This is the latest pending update
-          root.latestPendingTime = expirationTime;
-        }
+  {
+    if (fn.prototype && typeof fn.prototype.render === "function") {
+      var componentName = getComponentName(workInProgress) || "Unknown";
+
+      if (!didWarnAboutBadClass[componentName]) {
+        warning(
+          false,
+          "The <%s /> component appears to have a render method, but doesn't extend React.Component. " +
+            "This is likely to cause errors. Change %s to extend React.Component instead.",
+          componentName,
+          componentName
+        );
+        didWarnAboutBadClass[componentName] = true;
       }
     }
-  }
-}
 
-function markCommittedPriorityLevels(root, currentTime, earliestRemainingTime) {
-  if (enableSuspense) {
-    if (earliestRemainingTime === NoWork) {
-      // Fast path. There's no remaining work. Clear everything.
-      root.earliestPendingTime = NoWork;
-      root.latestPendingTime = NoWork;
-      root.earliestSuspendedTime = NoWork;
-      root.latestSuspendedTime = NoWork;
-      root.latestPingedTime = NoWork;
-      return;
+    if (workInProgress.mode & StrictMode) {
+      ReactStrictModeWarnings.recordLegacyContextWarning(workInProgress, null);
     }
 
-    // Let's see if the previous latest known pending level was just flushed.
-    var latestPendingTime = root.latestPendingTime;
-    if (latestPendingTime !== NoWork) {
-      if (latestPendingTime < earliestRemainingTime) {
-        // We've flushed all the known pending levels.
-        root.earliestPendingTime = root.latestPendingTime = NoWork;
-      } else {
-        var earliestPendingTime = root.earliestPendingTime;
-        if (earliestPendingTime < earliestRemainingTime) {
-          // We've flushed the earliest known pending level. Set this to the
-          // latest pending time.
-          root.earliestPendingTime = root.latestPendingTime;
-        }
-      }
-    }
+    ReactCurrentOwner.current = workInProgress;
+    value = fn(props, context);
+  }
+  // React DevTools reads this flag.
+  workInProgress.effectTag |= PerformedWork;
 
-    // Now let's handle the earliest remaining level in the whole tree. We need to
-    // decide whether to treat it as a pending level or as suspended. Check
-    // it falls within the range of known suspended levels.
+  if (
+    typeof value === "object" &&
+    value !== null &&
+    typeof value.render === "function" &&
+    value.$$typeof === undefined
+  ) {
+    var Component = workInProgress.type;
 
-    var earliestSuspendedTime = root.earliestSuspendedTime;
-    if (earliestSuspendedTime === NoWork) {
-      // There's no suspended work. Treat the earliest remaining level as a
-      // pending level.
-      markPendingPriorityLevel(root, earliestRemainingTime);
-      return;
-    }
+    // Proceed under the assumption that this is a class instance
+    workInProgress.tag = ClassComponent;
 
-    var latestSuspendedTime = root.latestSuspendedTime;
-    if (earliestRemainingTime > latestSuspendedTime) {
-      // The earliest remaining level is later than all the suspended work. That
-      // means we've flushed all the suspended work.
-      root.earliestSuspendedTime = NoWork;
-      root.latestSuspendedTime = NoWork;
-      root.latestPingedTime = NoWork;
+    workInProgress.memoizedState =
+      value.state !== null && value.state !== undefined ? value.state : null;
 
-      // There's no suspended work. Treat the earliest remaining level as a
-      // pending level.
-      markPendingPriorityLevel(root, earliestRemainingTime);
-      return;
+    var getDerivedStateFromProps = Component.getDerivedStateFromProps;
+    if (typeof getDerivedStateFromProps === "function") {
+      applyDerivedStateFromProps(
+        workInProgress,
+        getDerivedStateFromProps,
+        props
+      );
     }
 
-    if (earliestRemainingTime < earliestSuspendedTime) {
-      // The earliest remaining time is earlier than all the suspended work.
-      // Treat it as a pending update.
-      markPendingPriorityLevel(root, earliestRemainingTime);
-      return;
-    }
+    // Push context providers early to prevent context stack mismatches.
+    // During mounting we don't know the child context yet as the instance doesn't exist.
+    // We will invalidate the child context in finishClassComponent() right after rendering.
+    var hasContext = pushContextProvider(workInProgress);
+    adoptClassInstance(workInProgress, value);
+    mountClassInstance(workInProgress, renderExpirationTime);
+    return finishClassComponent(
+      current,
+      workInProgress,
+      true,
+      hasContext,
+      renderExpirationTime
+    );
+  } else {
+    // Proceed under the assumption that this is a functional component
+    workInProgress.tag = FunctionalComponent;
+    {
+      var _Component = workInProgress.type;
 
-    // The earliest remaining time falls within the range of known suspended
-    // levels. We should treat this as suspended work.
-  }
-}
+      if (_Component) {
+        !!_Component.childContextTypes
+          ? warning(
+              false,
+              "%s(...): childContextTypes cannot be defined on a functional component.",
+              _Component.displayName || _Component.name || "Component"
+            )
+          : void 0;
+      }
+      if (workInProgress.ref !== null) {
+        var info = "";
+        var ownerName = ReactDebugCurrentFiber.getCurrentFiberOwnerName();
+        if (ownerName) {
+          info += "\n\nCheck the render method of `" + ownerName + "`.";
+        }
 
-function markSuspendedPriorityLevel(root, suspendedTime) {
-  if (enableSuspense) {
-    // First, check the known pending levels and update them if needed.
-    var earliestPendingTime = root.earliestPendingTime;
-    var latestPendingTime = root.latestPendingTime;
-    if (earliestPendingTime === suspendedTime) {
-      if (latestPendingTime === suspendedTime) {
-        // Both known pending levels were suspended. Clear them.
-        root.earliestPendingTime = root.latestPendingTime = NoWork;
-      } else {
-        // The earliest pending level was suspended. Clear by setting it to the
-        // latest pending level.
-        root.earliestPendingTime = latestPendingTime;
+        var warningKey = ownerName || workInProgress._debugID || "";
+        var debugSource = workInProgress._debugSource;
+        if (debugSource) {
+          warningKey = debugSource.fileName + ":" + debugSource.lineNumber;
+        }
+        if (!didWarnAboutStatelessRefs[warningKey]) {
+          didWarnAboutStatelessRefs[warningKey] = true;
+          warning(
+            false,
+            "Stateless function components cannot be given refs. " +
+              "Attempts to access this ref will fail.%s%s",
+            info,
+            ReactDebugCurrentFiber.getCurrentFiberStackAddendum()
+          );
+        }
       }
-    } else if (latestPendingTime === suspendedTime) {
-      // The latest pending level was suspended. Clear by setting it to the
-      // latest pending level.
-      root.latestPendingTime = earliestPendingTime;
-    }
 
-    // Next, if we're working on the lowest known suspended level, clear the ping.
-    // TODO: What if a promise suspends and pings before the root completes?
-    var latestSuspendedTime = root.latestSuspendedTime;
-    if (latestSuspendedTime === suspendedTime) {
-      root.latestPingedTime = NoWork;
-    }
+      if (typeof fn.getDerivedStateFromProps === "function") {
+        var _componentName = getComponentName(workInProgress) || "Unknown";
 
-    // Finally, update the known suspended levels.
-    var earliestSuspendedTime = root.earliestSuspendedTime;
-    if (earliestSuspendedTime === NoWork) {
-      // No other suspended levels.
-      root.earliestSuspendedTime = root.latestSuspendedTime = suspendedTime;
-    } else {
-      if (earliestSuspendedTime > suspendedTime) {
-        // This is the earliest suspended level.
-        root.earliestSuspendedTime = suspendedTime;
-      } else if (latestSuspendedTime < suspendedTime) {
-        // This is the latest suspended level
-        root.latestSuspendedTime = suspendedTime;
+        if (!didWarnAboutGetDerivedStateOnFunctionalComponent[_componentName]) {
+          warning(
+            false,
+            "%s: Stateless functional components do not support getDerivedStateFromProps.",
+            _componentName
+          );
+          didWarnAboutGetDerivedStateOnFunctionalComponent[
+            _componentName
+          ] = true;
+        }
       }
     }
+    reconcileChildren(current, workInProgress, value);
+    memoizeProps(workInProgress, props);
+    return workInProgress.child;
   }
 }
 
-function markPingedPriorityLevel(root, pingedTime) {
+function updateTimeoutComponent(current, workInProgress, renderExpirationTime) {
   if (enableSuspense) {
-    var latestSuspendedTime = root.latestSuspendedTime;
-    if (latestSuspendedTime !== NoWork && latestSuspendedTime <= pingedTime) {
-      var latestPingedTime = root.latestPingedTime;
-      if (latestPingedTime === NoWork || latestPingedTime < pingedTime) {
-        root.latestPingedTime = pingedTime;
-      }
-    }
-  }
-}
+    var nextProps = workInProgress.pendingProps;
+    var prevProps = workInProgress.memoizedProps;
 
-function findNextPendingPriorityLevel(root) {
-  if (enableSuspense) {
-    var earliestSuspendedTime = root.earliestSuspendedTime;
-    var earliestPendingTime = root.earliestPendingTime;
-    if (earliestSuspendedTime === NoWork) {
-      // Fast path. There's no suspended work.
-      return earliestPendingTime;
-    }
+    var prevDidTimeout = workInProgress.memoizedState;
 
-    // First, check if there's known pending work.
-    if (earliestPendingTime !== NoWork) {
-      return earliestPendingTime;
+    // Check if we already attempted to render the normal state. If we did,
+    // and we timed out, render the placeholder state.
+    var alreadyCaptured = (workInProgress.effectTag & DidCapture) === NoEffect;
+    var nextDidTimeout = !alreadyCaptured;
+
+    if (hasContextChanged()) {
+      // Normally we can bail out on props equality but if context has changed
+      // we don't do the bailout and we have to reuse existing props instead.
+    } else if (nextProps === prevProps && nextDidTimeout === prevDidTimeout) {
+      return bailoutOnAlreadyFinishedWork(current, workInProgress);
     }
 
-    // Finally, if a suspended level was pinged, work on that. Otherwise there's
-    // nothing to work on.
-    return root.latestPingedTime;
+    var render = nextProps.children;
+    var nextChildren = render(nextDidTimeout);
+    workInProgress.memoizedProps = nextProps;
+    workInProgress.memoizedState = nextDidTimeout;
+    reconcileChildren(current, workInProgress, nextChildren);
+    return workInProgress.child;
   } else {
-    return root.current.expirationTime;
+    return null;
   }
 }
 
-var warnedAboutMissingGetChildContext = void 0;
+function updatePortalComponent(current, workInProgress, renderExpirationTime) {
+  pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
+  var nextChildren = workInProgress.pendingProps;
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (workInProgress.memoizedProps === nextChildren) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  }
 
-{
-  warnedAboutMissingGetChildContext = {};
+  if (current === null) {
+    // Portals are special because we don't append the children during mount
+    // but at commit. Therefore we need to track insertions which the normal
+    // flow doesn't do during mount. This doesn't happen at the root because
+    // the root always starts with a "current" with a null child.
+    // TODO: Consider unifying this with how the root works.
+    workInProgress.child = reconcileChildFibers(
+      workInProgress,
+      null,
+      nextChildren,
+      renderExpirationTime
+    );
+    memoizeProps(workInProgress, nextChildren);
+  } else {
+    reconcileChildren(current, workInProgress, nextChildren);
+    memoizeProps(workInProgress, nextChildren);
+  }
+  return workInProgress.child;
 }
 
-var ReactFiberLegacyContext = function(stack) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
-
-  // A cursor to the current merged context object on the stack.
-
-  var contextStackCursor = createCursor(emptyObject);
-  // A cursor to a boolean indicating whether the context has changed.
-  var didPerformWorkStackCursor = createCursor(false);
-  // Keep track of the previous context object that was on the stack.
-  // We use this to get access to the parent context after we have already
-  // pushed the next context provider, and now need to merge their contexts.
-  var previousContext = emptyObject;
-
-  function getUnmaskedContext(workInProgress) {
-    var hasOwnContext = isContextProvider(workInProgress);
-    if (hasOwnContext) {
-      // If the fiber is a context provider itself, when we read its context
-      // we have already pushed its own child context on the stack. A context
-      // provider should not "see" its own child context. Therefore we read the
-      // previous (parent) context instead for a context provider.
-      return previousContext;
+function propagateContextChange(
+  workInProgress,
+  context,
+  changedBits,
+  renderExpirationTime
+) {
+  var fiber = workInProgress.child;
+  if (fiber !== null) {
+    // Set the return pointer of the child to the work-in-progress fiber.
+    fiber.return = workInProgress;
+  }
+  while (fiber !== null) {
+    var nextFiber = void 0;
+    // Visit this fiber.
+    switch (fiber.tag) {
+      case ContextConsumer:
+        // Check if the context matches.
+        var observedBits = fiber.stateNode | 0;
+        if (fiber.type === context && (observedBits & changedBits) !== 0) {
+          // Update the expiration time of all the ancestors, including
+          // the alternates.
+          var node = fiber;
+          while (node !== null) {
+            var alternate = node.alternate;
+            if (
+              node.expirationTime === NoWork ||
+              node.expirationTime > renderExpirationTime
+            ) {
+              node.expirationTime = renderExpirationTime;
+              if (
+                alternate !== null &&
+                (alternate.expirationTime === NoWork ||
+                  alternate.expirationTime > renderExpirationTime)
+              ) {
+                alternate.expirationTime = renderExpirationTime;
+              }
+            } else if (
+              alternate !== null &&
+              (alternate.expirationTime === NoWork ||
+                alternate.expirationTime > renderExpirationTime)
+            ) {
+              alternate.expirationTime = renderExpirationTime;
+            } else {
+              // Neither alternate was updated, which means the rest of the
+              // ancestor path already has sufficient priority.
+              break;
+            }
+            node = node.return;
+          }
+          // Don't scan deeper than a matching consumer. When we render the
+          // consumer, we'll continue scanning from that point. This way the
+          // scanning work is time-sliced.
+          nextFiber = null;
+        } else {
+          // Traverse down.
+          nextFiber = fiber.child;
+        }
+        break;
+      case ContextProvider:
+        // Don't scan deeper if this is a matching provider
+        nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+        break;
+      default:
+        // Traverse down.
+        nextFiber = fiber.child;
+        break;
+    }
+    if (nextFiber !== null) {
+      // Set the return pointer of the child to the work-in-progress fiber.
+      nextFiber.return = fiber;
+    } else {
+      // No child. Traverse to next sibling.
+      nextFiber = fiber;
+      while (nextFiber !== null) {
+        if (nextFiber === workInProgress) {
+          // We're back to the root of this subtree. Exit.
+          nextFiber = null;
+          break;
+        }
+        var sibling = nextFiber.sibling;
+        if (sibling !== null) {
+          // Set the return pointer of the sibling to the work-in-progress fiber.
+          sibling.return = nextFiber.return;
+          nextFiber = sibling;
+          break;
+        }
+        // No more siblings. Traverse up.
+        nextFiber = nextFiber.return;
+      }
     }
-    return contextStackCursor.current;
+    fiber = nextFiber;
   }
+}
 
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    var instance = workInProgress.stateNode;
-    instance.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    instance.__reactInternalMemoizedMaskedChildContext = maskedContext;
-  }
+function updateContextProvider(current, workInProgress, renderExpirationTime) {
+  var providerType = workInProgress.type;
+  var context = providerType._context;
 
-  function getMaskedContext(workInProgress, unmaskedContext) {
-    var type = workInProgress.type;
-    var contextTypes = type.contextTypes;
-    if (!contextTypes) {
-      return emptyObject;
-    }
+  var newProps = workInProgress.pendingProps;
+  var oldProps = workInProgress.memoizedProps;
+  var canBailOnProps = true;
 
-    // Avoid recreating masked context unless unmasked context has changed.
-    // Failing to do this will result in unnecessary calls to componentWillReceiveProps.
-    // This may trigger infinite loops if componentWillReceiveProps calls setState.
-    var instance = workInProgress.stateNode;
-    if (
-      instance &&
-      instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-    ) {
-      return instance.__reactInternalMemoizedMaskedChildContext;
-    }
+  if (hasContextChanged()) {
+    canBailOnProps = false;
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (oldProps === newProps) {
+    workInProgress.stateNode = 0;
+    pushProvider(workInProgress);
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
+  }
 
-    var context = {};
-    for (var key in contextTypes) {
-      context[key] = unmaskedContext[key];
-    }
+  var newValue = newProps.value;
+  workInProgress.memoizedProps = newProps;
 
-    {
-      var name = getComponentName(workInProgress) || "Unknown";
+  {
+    var providerPropTypes = workInProgress.type.propTypes;
+
+    if (providerPropTypes) {
       checkPropTypes(
-        contextTypes,
-        context,
-        "context",
-        name,
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
+        providerPropTypes,
+        newProps,
+        "prop",
+        "Context.Provider",
+        getCurrentFiberStackAddendum$1
       );
     }
+  }
 
-    // Cache unmasked context so we can avoid recreating masked context unless necessary.
-    // Context is created before the class component is instantiated so check for instance.
-    if (instance) {
-      cacheContext(workInProgress, unmaskedContext, context);
-    }
+  var changedBits = void 0;
+  if (oldProps === null) {
+    // Initial render
+    changedBits = MAX_SIGNED_31_BIT_INT;
+  } else {
+    if (oldProps.value === newProps.value) {
+      // No change. Bailout early if children are the same.
+      if (oldProps.children === newProps.children && canBailOnProps) {
+        workInProgress.stateNode = 0;
+        pushProvider(workInProgress);
+        return bailoutOnAlreadyFinishedWork(current, workInProgress);
+      }
+      changedBits = 0;
+    } else {
+      var oldValue = oldProps.value;
+      // Use Object.is to compare the new context value to the old value.
+      // Inlined Object.is polyfill.
+      // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/is
+      if (
+        (oldValue === newValue &&
+          (oldValue !== 0 || 1 / oldValue === 1 / newValue)) ||
+        (oldValue !== oldValue && newValue !== newValue) // eslint-disable-line no-self-compare
+      ) {
+        // No change. Bailout early if children are the same.
+        if (oldProps.children === newProps.children && canBailOnProps) {
+          workInProgress.stateNode = 0;
+          pushProvider(workInProgress);
+          return bailoutOnAlreadyFinishedWork(current, workInProgress);
+        }
+        changedBits = 0;
+      } else {
+        changedBits =
+          typeof context._calculateChangedBits === "function"
+            ? context._calculateChangedBits(oldValue, newValue)
+            : MAX_SIGNED_31_BIT_INT;
+        {
+          !((changedBits & MAX_SIGNED_31_BIT_INT) === changedBits)
+            ? warning(
+                false,
+                "calculateChangedBits: Expected the return value to be a " +
+                  "31-bit integer. Instead received: %s",
+                changedBits
+              )
+            : void 0;
+        }
+        changedBits |= 0;
 
-    return context;
+        if (changedBits === 0) {
+          // No change. Bailout early if children are the same.
+          if (oldProps.children === newProps.children && canBailOnProps) {
+            workInProgress.stateNode = 0;
+            pushProvider(workInProgress);
+            return bailoutOnAlreadyFinishedWork(current, workInProgress);
+          }
+        } else {
+          propagateContextChange(
+            workInProgress,
+            context,
+            changedBits,
+            renderExpirationTime
+          );
+        }
+      }
+    }
   }
 
-  function hasContextChanged() {
-    return didPerformWorkStackCursor.current;
+  workInProgress.stateNode = changedBits;
+  pushProvider(workInProgress);
+
+  var newChildren = newProps.children;
+  reconcileChildren(current, workInProgress, newChildren);
+  return workInProgress.child;
+}
+
+function updateContextConsumer(current, workInProgress, renderExpirationTime) {
+  var context = workInProgress.type;
+  var newProps = workInProgress.pendingProps;
+  var oldProps = workInProgress.memoizedProps;
+
+  var newValue = getContextCurrentValue(context);
+  var changedBits = getContextChangedBits(context);
+
+  if (hasContextChanged()) {
+    // Normally we can bail out on props equality but if context has changed
+    // we don't do the bailout and we have to reuse existing props instead.
+  } else if (changedBits === 0 && oldProps === newProps) {
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
+  workInProgress.memoizedProps = newProps;
 
-  function isContextConsumer(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.contextTypes != null;
+  var observedBits = newProps.unstable_observedBits;
+  if (observedBits === undefined || observedBits === null) {
+    // Subscribe to all changes by default
+    observedBits = MAX_SIGNED_31_BIT_INT;
   }
+  // Store the observedBits on the fiber's stateNode for quick access.
+  workInProgress.stateNode = observedBits;
 
-  function isContextProvider(fiber) {
-    return fiber.tag === ClassComponent && fiber.type.childContextTypes != null;
+  if ((changedBits & observedBits) !== 0) {
+    // Context change propagation stops at matching consumers, for time-
+    // slicing. Continue the propagation here.
+    propagateContextChange(
+      workInProgress,
+      context,
+      changedBits,
+      renderExpirationTime
+    );
+  } else if (oldProps === newProps) {
+    // Skip over a memoized parent with a bitmask bailout even
+    // if we began working on it because of a deeper matching child.
+    return bailoutOnAlreadyFinishedWork(current, workInProgress);
   }
+  // There is no bailout on `children` equality because we expect people
+  // to often pass a bound method as a child, but it may reference
+  // `this.state` or `this.props` (and thus needs to re-render on `setState`).
 
-  function popContextProvider(fiber) {
-    if (!isContextProvider(fiber)) {
-      return;
-    }
+  var render = newProps.children;
+
+  {
+    !(typeof render === "function")
+      ? warning(
+          false,
+          "A context consumer was rendered with multiple children, or a child " +
+            "that isn't a function. A context consumer expects a single child " +
+            "that is a function. If you did pass a function, make sure there " +
+            "is no trailing or leading whitespace around it."
+        )
+      : void 0;
+  }
 
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
+  var newChildren = void 0;
+  {
+    ReactCurrentOwner.current = workInProgress;
+    ReactDebugCurrentFiber.setCurrentPhase("render");
+    newChildren = render(newValue);
+    ReactDebugCurrentFiber.setCurrentPhase(null);
   }
 
-  function popTopLevelContextObject(fiber) {
-    pop(didPerformWorkStackCursor, fiber);
-    pop(contextStackCursor, fiber);
+  // React DevTools reads this flag.
+  workInProgress.effectTag |= PerformedWork;
+  reconcileChildren(current, workInProgress, newChildren);
+  return workInProgress.child;
+}
+
+/*
+  function reuseChildrenEffects(returnFiber : Fiber, firstChild : Fiber) {
+    let child = firstChild;
+    do {
+      // Ensure that the first and last effect of the parent corresponds
+      // to the children's first and last effect.
+      if (!returnFiber.firstEffect) {
+        returnFiber.firstEffect = child.firstEffect;
+      }
+      if (child.lastEffect) {
+        if (returnFiber.lastEffect) {
+          returnFiber.lastEffect.nextEffect = child.firstEffect;
+        }
+        returnFiber.lastEffect = child.lastEffect;
+      }
+    } while (child = child.sibling);
   }
+  */
 
-  function pushTopLevelContextObject(fiber, context, didChange) {
-    invariant(
-      contextStackCursor.cursor == null,
-      "Unexpected context found on stack. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
+function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+  cancelWorkTimer(workInProgress);
 
-    push(contextStackCursor, context, fiber);
-    push(didPerformWorkStackCursor, didChange, fiber);
+  if (enableProfilerTimer) {
+    // Don't update "base" render times for bailouts.
+    stopBaseRenderTimerIfRunning();
   }
 
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode;
-    var childContextTypes = fiber.type.childContextTypes;
+  // TODO: We should ideally be able to bail out early if the children have no
+  // more work to do. However, since we don't have a separation of this
+  // Fiber's priority and its children yet - we don't know without doing lots
+  // of the same work we do anyway. Once we have that separation we can just
+  // bail out here if the children has no more work at this priority level.
+  // if (workInProgress.priorityOfChildren <= priorityLevel) {
+  //   // If there are side-effects in these children that have not yet been
+  //   // committed we need to ensure that they get properly transferred up.
+  //   if (current && current.child !== workInProgress.child) {
+  //     reuseChildrenEffects(workInProgress, child);
+  //   }
+  //   return null;
+  // }
 
-    // TODO (bvaughn) Replace this behavior with an invariant() in the future.
-    // It has only been added in Fiber to match the (unintentional) behavior in Stack.
-    if (typeof instance.getChildContext !== "function") {
-      {
-        var componentName = getComponentName(fiber) || "Unknown";
-
-        if (!warnedAboutMissingGetChildContext[componentName]) {
-          warnedAboutMissingGetChildContext[componentName] = true;
-          warning(
-            false,
-            "%s.childContextTypes is specified but there is no getChildContext() method " +
-              "on the instance. You can either define getChildContext() on %s or remove " +
-              "childContextTypes from it.",
-            componentName,
-            componentName
-          );
-        }
-      }
-      return parentContext;
-    }
+  cloneChildFibers(current, workInProgress);
+  return workInProgress.child;
+}
 
-    var childContext = void 0;
-    {
-      ReactDebugCurrentFiber.setCurrentPhase("getChildContext");
-    }
-    startPhaseTimer(fiber, "getChildContext");
-    childContext = instance.getChildContext();
-    stopPhaseTimer();
-    {
-      ReactDebugCurrentFiber.setCurrentPhase(null);
-    }
-    for (var contextKey in childContext) {
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
-      );
-    }
-    {
-      var name = getComponentName(fiber) || "Unknown";
-      checkPropTypes(
-        childContextTypes,
-        childContext,
-        "child context",
-        name,
-        // In practice, there is one case in which we won't get a stack. It's when
-        // somebody calls unstable_renderSubtreeIntoContainer() and we process
-        // context from the parent component instance. The stack will be missing
-        // because it's outside of the reconciliation, and so the pointer has not
-        // been set. This is rare and doesn't matter. We'll also remove that API.
-        ReactDebugCurrentFiber.getCurrentFiberStackAddendum
-      );
-    }
+function bailoutOnLowPriority(current, workInProgress) {
+  cancelWorkTimer(workInProgress);
 
-    return Object.assign({}, parentContext, childContext);
+  if (enableProfilerTimer) {
+    // Don't update "base" render times for bailouts.
+    stopBaseRenderTimerIfRunning();
   }
 
-  function pushContextProvider(workInProgress) {
-    if (!isContextProvider(workInProgress)) {
-      return false;
-    }
-
-    var instance = workInProgress.stateNode;
-    // We push the context as early as possible to ensure stack integrity.
-    // If the instance does not exist yet, we will push null at first,
-    // and replace it on the stack later when invalidating the context.
-    var memoizedMergedChildContext =
-      (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-      emptyObject;
-
-    // Remember the parent context so we can merge with it later.
-    // Inherit the parent's did-perform-work value to avoid inadvertently blocking updates.
-    previousContext = contextStackCursor.current;
-    push(contextStackCursor, memoizedMergedChildContext, workInProgress);
-    push(
-      didPerformWorkStackCursor,
-      didPerformWorkStackCursor.current,
-      workInProgress
-    );
-
-    return true;
+  // TODO: Handle HostComponent tags here as well and call pushHostContext()?
+  // See PR 8590 discussion for context
+  switch (workInProgress.tag) {
+    case HostRoot:
+      pushHostRootContext(workInProgress);
+      break;
+    case ClassComponent:
+      pushContextProvider(workInProgress);
+      break;
+    case HostPortal:
+      pushHostContainer(workInProgress, workInProgress.stateNode.containerInfo);
+      break;
+    case ContextProvider:
+      pushProvider(workInProgress);
+      break;
   }
+  // TODO: What if this is currently in progress?
+  // How can that happen? How is this not being cloned?
+  return null;
+}
 
-  function invalidateContextProvider(workInProgress, didChange) {
-    var instance = workInProgress.stateNode;
-    invariant(
-      instance,
-      "Expected to have an instance by this point. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
+// TODO: Delete memoizeProps/State and move to reconcile/bailout instead
+function memoizeProps(workInProgress, nextProps) {
+  workInProgress.memoizedProps = nextProps;
+}
 
-    if (didChange) {
-      // Merge parent and own context.
-      // Skip this if we're not updating due to sCU.
-      // This avoids unnecessarily recomputing memoized values.
-      var mergedContext = processChildContext(workInProgress, previousContext);
-      instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-
-      // Replace the old (or empty) context with the new one.
-      // It is important to unwind the context in the reverse order.
-      pop(didPerformWorkStackCursor, workInProgress);
-      pop(contextStackCursor, workInProgress);
-      // Now push the new context and mark that it has changed.
-      push(contextStackCursor, mergedContext, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    } else {
-      pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
+function memoizeState(workInProgress, nextState) {
+  workInProgress.memoizedState = nextState;
+  // Don't reset the updateQueue, in case there are pending updates. Resetting
+  // is handled by processUpdateQueue.
+}
+
+function beginWork(current, workInProgress, renderExpirationTime) {
+  if (enableProfilerTimer) {
+    if (workInProgress.mode & ProfileMode) {
+      markActualRenderTimeStarted(workInProgress);
     }
   }
 
-  function findCurrentUnmaskedContext(fiber) {
-    // Currently this is only used with renderSubtreeIntoContainer; not sure if it
-    // makes sense elsewhere
-    invariant(
-      isFiberMounted(fiber) && fiber.tag === ClassComponent,
-      "Expected subtree parent to be a mounted class component. " +
-        "This error is likely caused by a bug in React. Please file an issue."
-    );
+  if (
+    workInProgress.expirationTime === NoWork ||
+    workInProgress.expirationTime > renderExpirationTime
+  ) {
+    return bailoutOnLowPriority(current, workInProgress);
+  }
 
-    var node = fiber;
-    while (node.tag !== HostRoot) {
-      if (isContextProvider(node)) {
-        return node.stateNode.__reactInternalMemoizedMergedChildContext;
-      }
-      var parent = node.return;
+  switch (workInProgress.tag) {
+    case IndeterminateComponent:
+      return mountIndeterminateComponent(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case FunctionalComponent:
+      return updateFunctionalComponent(current, workInProgress);
+    case ClassComponent:
+      return updateClassComponent(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case HostRoot:
+      return updateHostRoot(current, workInProgress, renderExpirationTime);
+    case HostComponent:
+      return updateHostComponent(current, workInProgress, renderExpirationTime);
+    case HostText:
+      return updateHostText(current, workInProgress);
+    case TimeoutComponent:
+      return updateTimeoutComponent(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case HostPortal:
+      return updatePortalComponent(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case ForwardRef:
+      return updateForwardRef(current, workInProgress);
+    case Fragment:
+      return updateFragment(current, workInProgress);
+    case Mode:
+      return updateMode(current, workInProgress);
+    case Profiler:
+      return updateProfiler(current, workInProgress);
+    case ContextProvider:
+      return updateContextProvider(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case ContextConsumer:
+      return updateContextConsumer(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    default:
       invariant(
-        parent,
-        "Found unexpected detached subtree parent. " +
-          "This error is likely caused by a bug in React. Please file an issue."
+        false,
+        "Unknown unit of work tag. This error is likely caused by a bug in " +
+          "React. Please file an issue."
       );
-      node = parent;
-    }
-    return node.stateNode.context;
   }
+}
 
-  return {
-    getUnmaskedContext: getUnmaskedContext,
-    cacheContext: cacheContext,
-    getMaskedContext: getMaskedContext,
-    hasContextChanged: hasContextChanged,
-    isContextConsumer: isContextConsumer,
-    isContextProvider: isContextProvider,
-    popContextProvider: popContextProvider,
-    popTopLevelContextObject: popTopLevelContextObject,
-    pushTopLevelContextObject: pushTopLevelContextObject,
-    processChildContext: processChildContext,
-    pushContextProvider: pushContextProvider,
-    invalidateContextProvider: invalidateContextProvider,
-    findCurrentUnmaskedContext: findCurrentUnmaskedContext
-  };
-};
-
-var ReactFiberNewContext = function(stack, isPrimaryRenderer) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop;
+function markUpdate(workInProgress) {
+  // Tag the fiber with an update effect. This turns a Placement into
+  // a PlacementAndUpdate.
+  workInProgress.effectTag |= Update;
+}
 
-  var providerCursor = createCursor(null);
-  var valueCursor = createCursor(null);
-  var changedBitsCursor = createCursor(0);
+function markRef$1(workInProgress) {
+  workInProgress.effectTag |= Ref;
+}
 
-  var rendererSigil = void 0;
-  {
-    // Use this to detect multiple renderers using the same context
-    rendererSigil = {};
+function appendAllChildren(parent, workInProgress) {
+  // We only have the top Fiber that was created but we need recurse down its
+  // children to find all the terminal nodes.
+  var node = workInProgress.child;
+  while (node !== null) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      appendInitialChild(parent, node.stateNode);
+    } else if (node.tag === HostPortal) {
+      // If we have a portal child, then we don't want to traverse
+      // down its children. Instead, we'll get insertions from each child in
+      // the portal directly.
+    } else if (node.child !== null) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === workInProgress) {
+      return;
+    }
+    while (node.sibling === null) {
+      if (node.return === null || node.return === workInProgress) {
+        return;
+      }
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
   }
+}
 
-  function pushProvider(providerFiber) {
-    var context = providerFiber.type._context;
+var updateHostContainer = void 0;
+var updateHostComponent$1 = void 0;
+var updateHostText$1 = void 0;
+if (supportsMutation) {
+  // Mutation mode
 
-    if (isPrimaryRenderer) {
-      push(changedBitsCursor, context._changedBits, providerFiber);
-      push(valueCursor, context._currentValue, providerFiber);
-      push(providerCursor, providerFiber, providerFiber);
+  updateHostContainer = function(workInProgress) {
+    // Noop
+  };
+  updateHostComponent$1 = function(
+    current,
+    workInProgress,
+    updatePayload,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    currentHostContext
+  ) {
+    // TODO: Type this specific to this type of component.
+    workInProgress.updateQueue = updatePayload;
+    // If the update payload indicates that there is a change or if there
+    // is a new ref we mark this as an update. All the work is done in commitWork.
+    if (updatePayload) {
+      markUpdate(workInProgress);
+    }
+  };
+  updateHostText$1 = function(current, workInProgress, oldText, newText) {
+    // If the text differs, mark it as an update. All the work in done in commitWork.
+    if (oldText !== newText) {
+      markUpdate(workInProgress);
+    }
+  };
+} else if (supportsPersistence) {
+  // Persistent host tree mode
 
-      context._currentValue = providerFiber.pendingProps.value;
-      context._changedBits = providerFiber.stateNode;
-      {
-        !(
-          context._currentRenderer === undefined ||
-          context._currentRenderer === null ||
-          context._currentRenderer === rendererSigil
-        )
-          ? warning(
-              false,
-              "Detected multiple renderers concurrently rendering the " +
-                "same context provider. This is currently unsupported."
-            )
-          : void 0;
-        context._currentRenderer = rendererSigil;
+  // An unfortunate fork of appendAllChildren because we have two different parent types.
+  var appendAllChildrenToContainer = function(
+    containerChildSet,
+    workInProgress
+  ) {
+    // We only have the top Fiber that was created but we need recurse down its
+    // children to find all the terminal nodes.
+    var node = workInProgress.child;
+    while (node !== null) {
+      if (node.tag === HostComponent || node.tag === HostText) {
+        appendChildToContainerChildSet(containerChildSet, node.stateNode);
+      } else if (node.tag === HostPortal) {
+        // If we have a portal child, then we don't want to traverse
+        // down its children. Instead, we'll get insertions from each child in
+        // the portal directly.
+      } else if (node.child !== null) {
+        node.child.return = node;
+        node = node.child;
+        continue;
+      }
+      if (node === workInProgress) {
+        return;
+      }
+      while (node.sibling === null) {
+        if (node.return === null || node.return === workInProgress) {
+          return;
+        }
+        node = node.return;
       }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  };
+  updateHostContainer = function(workInProgress) {
+    var portalOrRoot = workInProgress.stateNode;
+    var childrenUnchanged = workInProgress.firstEffect === null;
+    if (childrenUnchanged) {
+      // No changes, just reuse the existing instance.
     } else {
-      push(changedBitsCursor, context._changedBits2, providerFiber);
-      push(valueCursor, context._currentValue2, providerFiber);
-      push(providerCursor, providerFiber, providerFiber);
-
-      context._currentValue2 = providerFiber.pendingProps.value;
-      context._changedBits2 = providerFiber.stateNode;
-      {
-        !(
-          context._currentRenderer2 === undefined ||
-          context._currentRenderer2 === null ||
-          context._currentRenderer2 === rendererSigil
+      var container = portalOrRoot.containerInfo;
+      var newChildSet = createContainerChildSet(container);
+      // If children might have changed, we have to add them all to the set.
+      appendAllChildrenToContainer(newChildSet, workInProgress);
+      portalOrRoot.pendingChildren = newChildSet;
+      // Schedule an update on the container to swap out the container.
+      markUpdate(workInProgress);
+      finalizeContainerChildren(container, newChildSet);
+    }
+  };
+  updateHostComponent$1 = function(
+    current,
+    workInProgress,
+    updatePayload,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    currentHostContext
+  ) {
+    // If there are no effects associated with this node, then none of our children had any updates.
+    // This guarantees that we can reuse all of them.
+    var childrenUnchanged = workInProgress.firstEffect === null;
+    var currentInstance = current.stateNode;
+    if (childrenUnchanged && updatePayload === null) {
+      // No changes, just reuse the existing instance.
+      // Note that this might release a previous clone.
+      workInProgress.stateNode = currentInstance;
+    } else {
+      var recyclableInstance = workInProgress.stateNode;
+      var newInstance = cloneInstance(
+        currentInstance,
+        updatePayload,
+        type,
+        oldProps,
+        newProps,
+        workInProgress,
+        childrenUnchanged,
+        recyclableInstance
+      );
+      if (
+        finalizeInitialChildren(
+          newInstance,
+          type,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
         )
-          ? warning(
-              false,
-              "Detected multiple renderers concurrently rendering the " +
-                "same context provider. This is currently unsupported."
-            )
-          : void 0;
-        context._currentRenderer2 = rendererSigil;
+      ) {
+        markUpdate(workInProgress);
+      }
+      workInProgress.stateNode = newInstance;
+      if (childrenUnchanged) {
+        // If there are no other effects in this tree, we need to flag this node as having one.
+        // Even though we're not going to use it for anything.
+        // Otherwise parents won't know that there are new children to propagate upwards.
+        markUpdate(workInProgress);
+      } else {
+        // If children might have changed, we have to add them all to the set.
+        appendAllChildren(newInstance, workInProgress);
       }
     }
-  }
-
-  function popProvider(providerFiber) {
-    var changedBits = changedBitsCursor.current;
-    var currentValue = valueCursor.current;
-
-    pop(providerCursor, providerFiber);
-    pop(valueCursor, providerFiber);
-    pop(changedBitsCursor, providerFiber);
-
-    var context = providerFiber.type._context;
-    if (isPrimaryRenderer) {
-      context._currentValue = currentValue;
-      context._changedBits = changedBits;
-    } else {
-      context._currentValue2 = currentValue;
-      context._changedBits2 = changedBits;
+  };
+  updateHostText$1 = function(current, workInProgress, oldText, newText) {
+    if (oldText !== newText) {
+      // If the text content differs, we'll create a new text instance for it.
+      var rootContainerInstance = getRootHostContainer();
+      var currentHostContext = getHostContext();
+      workInProgress.stateNode = createTextInstance(
+        newText,
+        rootContainerInstance,
+        currentHostContext,
+        workInProgress
+      );
+      // We'll have to mark it as having an effect, even though we won't use the effect for anything.
+      // This lets the parents know that at least one of their children has changed.
+      markUpdate(workInProgress);
     }
-  }
+  };
+} else {
+  // No host operations
+  updateHostContainer = function(workInProgress) {
+    // Noop
+  };
+  updateHostComponent$1 = function(
+    current,
+    workInProgress,
+    updatePayload,
+    type,
+    oldProps,
+    newProps,
+    rootContainerInstance,
+    currentHostContext
+  ) {
+    // Noop
+  };
+  updateHostText$1 = function(current, workInProgress, oldText, newText) {
+    // Noop
+  };
+}
 
-  function getContextCurrentValue(context) {
-    return isPrimaryRenderer ? context._currentValue : context._currentValue2;
-  }
+function completeWork(current, workInProgress, renderExpirationTime) {
+  var newProps = workInProgress.pendingProps;
 
-  function getContextChangedBits(context) {
-    return isPrimaryRenderer ? context._changedBits : context._changedBits2;
+  if (enableProfilerTimer) {
+    if (workInProgress.mode & ProfileMode) {
+      recordElapsedActualRenderTime(workInProgress);
+    }
   }
 
-  return {
-    pushProvider: pushProvider,
-    popProvider: popProvider,
-    getContextCurrentValue: getContextCurrentValue,
-    getContextChangedBits: getContextChangedBits
-  };
-};
-
-var ReactFiberStack = function() {
-  var valueStack = [];
+  switch (workInProgress.tag) {
+    case FunctionalComponent:
+      return null;
+    case ClassComponent: {
+      // We are leaving this subtree, so pop context if any.
+      popContextProvider(workInProgress);
+      return null;
+    }
+    case HostRoot: {
+      popHostContainer(workInProgress);
+      popTopLevelContextObject(workInProgress);
+      var fiberRoot = workInProgress.stateNode;
+      if (fiberRoot.pendingContext) {
+        fiberRoot.context = fiberRoot.pendingContext;
+        fiberRoot.pendingContext = null;
+      }
+      if (current === null || current.child === null) {
+        // If we hydrated, pop so that we can delete any remaining children
+        // that weren't hydrated.
+        popHydrationState(workInProgress);
+        // This resets the hacky state to fix isMounted before committing.
+        // TODO: Delete this when we delete isMounted and findDOMNode.
+        workInProgress.effectTag &= ~Placement;
+      }
+      updateHostContainer(workInProgress);
+      return null;
+    }
+    case HostComponent: {
+      popHostContext(workInProgress);
+      var rootContainerInstance = getRootHostContainer();
+      var type = workInProgress.type;
+      if (current !== null && workInProgress.stateNode != null) {
+        // If we have an alternate, that means this is an update and we need to
+        // schedule a side-effect to do the updates.
+        var oldProps = current.memoizedProps;
+        // If we get updated because one of our children updated, we don't
+        // have newProps so we'll have to reuse them.
+        // TODO: Split the update API as separate for the props vs. children.
+        // Even better would be if children weren't special cased at all tho.
+        var instance = workInProgress.stateNode;
+        var currentHostContext = getHostContext();
+        // TODO: Experiencing an error where oldProps is null. Suggests a host
+        // component is hitting the resume path. Figure out why. Possibly
+        // related to `hidden`.
+        var updatePayload = prepareUpdate(
+          instance,
+          type,
+          oldProps,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        );
 
-  var fiberStack = void 0;
+        updateHostComponent$1(
+          current,
+          workInProgress,
+          updatePayload,
+          type,
+          oldProps,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        );
 
-  {
-    fiberStack = [];
-  }
+        if (current.ref !== workInProgress.ref) {
+          markRef$1(workInProgress);
+        }
+      } else {
+        if (!newProps) {
+          invariant(
+            workInProgress.stateNode !== null,
+            "We must have new props for new mounts. This error is likely " +
+              "caused by a bug in React. Please file an issue."
+          );
+          // This can happen when we abort work.
+          return null;
+        }
 
-  var index = -1;
+        var _currentHostContext = getHostContext();
+        // TODO: Move createInstance to beginWork and keep it on a context
+        // "stack" as the parent. Then append children as we go in beginWork
+        // or completeWork depending on we want to add then top->down or
+        // bottom->up. Top->down is faster in IE11.
+        var wasHydrated = popHydrationState(workInProgress);
+        if (wasHydrated) {
+          // TODO: Move this and createInstance step into the beginPhase
+          // to consolidate.
+          if (
+            prepareToHydrateHostInstance(
+              workInProgress,
+              rootContainerInstance,
+              _currentHostContext
+            )
+          ) {
+            // If changes to the hydrated node needs to be applied at the
+            // commit-phase we mark this as such.
+            markUpdate(workInProgress);
+          }
+        } else {
+          var _instance = createInstance(
+            type,
+            newProps,
+            rootContainerInstance,
+            _currentHostContext,
+            workInProgress
+          );
 
-  function createCursor(defaultValue) {
-    return {
-      current: defaultValue
-    };
-  }
+          appendAllChildren(_instance, workInProgress);
 
-  function isEmpty() {
-    return index === -1;
-  }
+          // Certain renderers require commit-time effects for initial mount.
+          // (eg DOM renderer supports auto-focus for certain elements).
+          // Make sure such renderers get scheduled for later work.
+          if (
+            finalizeInitialChildren(
+              _instance,
+              type,
+              newProps,
+              rootContainerInstance,
+              _currentHostContext
+            )
+          ) {
+            markUpdate(workInProgress);
+          }
+          workInProgress.stateNode = _instance;
+        }
 
-  function pop(cursor, fiber) {
-    if (index < 0) {
-      {
-        warning(false, "Unexpected pop.");
+        if (workInProgress.ref !== null) {
+          // If there is a ref on a host node we need to schedule a callback
+          markRef$1(workInProgress);
+        }
       }
-      return;
+      return null;
     }
-
-    {
-      if (fiber !== fiberStack[index]) {
-        warning(false, "Unexpected Fiber popped.");
+    case HostText: {
+      var newText = newProps;
+      if (current && workInProgress.stateNode != null) {
+        var oldText = current.memoizedProps;
+        // If we have an alternate, that means this is an update and we need
+        // to schedule a side-effect to do the updates.
+        updateHostText$1(current, workInProgress, oldText, newText);
+      } else {
+        if (typeof newText !== "string") {
+          invariant(
+            workInProgress.stateNode !== null,
+            "We must have new props for new mounts. This error is likely " +
+              "caused by a bug in React. Please file an issue."
+          );
+          // This can happen when we abort work.
+          return null;
+        }
+        var _rootContainerInstance = getRootHostContainer();
+        var _currentHostContext2 = getHostContext();
+        var _wasHydrated = popHydrationState(workInProgress);
+        if (_wasHydrated) {
+          if (prepareToHydrateHostTextInstance(workInProgress)) {
+            markUpdate(workInProgress);
+          }
+        } else {
+          workInProgress.stateNode = createTextInstance(
+            newText,
+            _rootContainerInstance,
+            _currentHostContext2,
+            workInProgress
+          );
+        }
       }
+      return null;
     }
+    case ForwardRef:
+      return null;
+    case TimeoutComponent:
+      return null;
+    case Fragment:
+      return null;
+    case Mode:
+      return null;
+    case Profiler:
+      return null;
+    case HostPortal:
+      popHostContainer(workInProgress);
+      updateHostContainer(workInProgress);
+      return null;
+    case ContextProvider:
+      // Pop provider fiber
+      popProvider(workInProgress);
+      return null;
+    case ContextConsumer:
+      return null;
+    // Error cases
+    case IndeterminateComponent:
+      invariant(
+        false,
+        "An indeterminate component should have become determinate before " +
+          "completing. This error is likely caused by a bug in React. Please " +
+          "file an issue."
+      );
+    // eslint-disable-next-line no-fallthrough
+    default:
+      invariant(
+        false,
+        "Unknown unit of work tag. This error is likely caused by a bug in " +
+          "React. Please file an issue."
+      );
+  }
+}
 
-    cursor.current = valueStack[index];
+// Module provided by RN:
+/**
+ * Intercept lifecycle errors and ensure they are shown with the correct stack
+ * trace within the native redbox component.
+ */
+function showErrorDialog(capturedError) {
+  var componentStack = capturedError.componentStack,
+    error = capturedError.error;
 
-    valueStack[index] = null;
+  var errorToHandle = void 0;
 
-    {
-      fiberStack[index] = null;
-    }
+  // Typically Errors are thrown but eg strings or null can be thrown as well.
+  if (error instanceof Error) {
+    var message = error.message,
+      name = error.name;
 
-    index--;
-  }
+    var summary = message ? name + ": " + message : name;
 
-  function push(cursor, value, fiber) {
-    index++;
+    errorToHandle = error;
 
-    valueStack[index] = cursor.current;
+    try {
+      errorToHandle.message =
+        summary + "\n\nThis error is located at:" + componentStack;
+    } catch (e) {}
+  } else if (typeof error === "string") {
+    errorToHandle = new Error(
+      error + "\n\nThis error is located at:" + componentStack
+    );
+  } else {
+    errorToHandle = new Error("Unspecified error at:" + componentStack);
+  }
 
-    {
-      fiberStack[index] = fiber;
-    }
+  ExceptionsManager.handleException(errorToHandle, false);
 
-    cursor.current = value;
-  }
+  // Return false here to prevent ReactFiberErrorLogger default behavior of
+  // logging error details to console.error. Calls to console.error are
+  // automatically routed to the native redbox controller, which we've already
+  // done above by calling ExceptionsManager.
+  return false;
+}
 
-  function checkThatStackIsEmpty() {
-    {
-      if (index !== -1) {
-        warning(
-          false,
-          "Expected an empty stack. Something was not reset properly."
-        );
-      }
-    }
-  }
+function logCapturedError(capturedError) {
+  var logError = showErrorDialog(capturedError);
 
-  function resetStackAfterFatalErrorInDev() {
-    {
-      index = -1;
-      valueStack.length = 0;
-      fiberStack.length = 0;
-    }
+  // Allow injected showErrorDialog() to prevent default console.error logging.
+  // This enables renderers like ReactNative to better manage redbox behavior.
+  if (logError === false) {
+    return;
   }
 
-  return {
-    createCursor: createCursor,
-    isEmpty: isEmpty,
-    pop: pop,
-    push: push,
-    checkThatStackIsEmpty: checkThatStackIsEmpty,
-    resetStackAfterFatalErrorInDev: resetStackAfterFatalErrorInDev
-  };
-};
-
-var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
-var hasCaughtError = ReactErrorUtils.hasCaughtError;
-var clearCaughtError = ReactErrorUtils.clearCaughtError;
+  var error = capturedError.error;
+  var suppressLogging = error && error.suppressReactErrorLogging;
+  if (suppressLogging) {
+    return;
+  }
 
-var didWarnAboutStateTransition = void 0;
-var didWarnSetStateChildContext = void 0;
-var warnAboutUpdateOnUnmounted = void 0;
-var warnAboutInvalidUpdates = void 0;
+  {
+    var componentName = capturedError.componentName,
+      componentStack = capturedError.componentStack,
+      errorBoundaryName = capturedError.errorBoundaryName,
+      errorBoundaryFound = capturedError.errorBoundaryFound,
+      willRetry = capturedError.willRetry;
 
-{
-  didWarnAboutStateTransition = false;
-  didWarnSetStateChildContext = false;
-  var didWarnStateUpdateForUnmountedComponent = {};
+    var componentNameMessage = componentName
+      ? "The above error occurred in the <" + componentName + "> component:"
+      : "The above error occurred in one of your React components:";
 
-  warnAboutUpdateOnUnmounted = function(fiber) {
-    // We show the whole stack but dedupe on the top component's name because
-    // the problematic code almost always lies inside that component.
-    var componentName = getComponentName(fiber) || "ReactClass";
-    if (didWarnStateUpdateForUnmountedComponent[componentName]) {
-      return;
+    var errorBoundaryMessage = void 0;
+    // errorBoundaryFound check is sufficient; errorBoundaryName check is to satisfy Flow.
+    if (errorBoundaryFound && errorBoundaryName) {
+      if (willRetry) {
+        errorBoundaryMessage =
+          "React will try to recreate this component tree from scratch " +
+          ("using the error boundary you provided, " + errorBoundaryName + ".");
+      } else {
+        errorBoundaryMessage =
+          "This error was initially handled by the error boundary " +
+          errorBoundaryName +
+          ".\n" +
+          "Recreating the tree from scratch failed so React will unmount the tree.";
+      }
+    } else {
+      errorBoundaryMessage =
+        "Consider adding an error boundary to your tree to customize error handling behavior.\n" +
+        "Visit https://fb.me/react-error-boundaries to learn more about error boundaries.";
     }
-    warning(
-      false,
-      "Can't call setState (or forceUpdate) on an unmounted component. This " +
-        "is a no-op, but it indicates a memory leak in your application. To " +
-        "fix, cancel all subscriptions and asynchronous tasks in the " +
-        "componentWillUnmount method.%s",
-      getStackAddendumByWorkInProgressFiber(fiber)
-    );
-    didWarnStateUpdateForUnmountedComponent[componentName] = true;
-  };
+    var combinedMessage =
+      "" +
+      componentNameMessage +
+      componentStack +
+      "\n\n" +
+      ("" + errorBoundaryMessage);
 
-  warnAboutInvalidUpdates = function(instance) {
-    switch (ReactDebugCurrentFiber.phase) {
-      case "getChildContext":
-        if (didWarnSetStateChildContext) {
-          return;
-        }
-        warning(
-          false,
-          "setState(...): Cannot call setState() inside getChildContext()"
-        );
-        didWarnSetStateChildContext = true;
-        break;
-      case "render":
-        if (didWarnAboutStateTransition) {
-          return;
-        }
-        warning(
-          false,
-          "Cannot update during an existing state transition (such as within " +
-            "`render` or another component's constructor). Render methods should " +
-            "be a pure function of props and state; constructor side-effects are " +
-            "an anti-pattern, but can be moved to `componentWillMount`."
-        );
-        didWarnAboutStateTransition = true;
-        break;
-    }
-  };
+    // In development, we provide our own message with just the component stack.
+    // We don't include the original error message and JS stack because the browser
+    // has already printed it. Even if the application swallows the error, it is still
+    // displayed by the browser thanks to the DEV-only fake event trick in ReactErrorUtils.
+    console.error(combinedMessage);
+  }
 }
 
-var ReactFiberScheduler = function(config) {
-  var now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit;
-
-  var stack = ReactFiberStack();
-  var hostContext = ReactFiberHostContext(config, stack);
-  var legacyContext = ReactFiberLegacyContext(stack);
-  var newContext = ReactFiberNewContext(stack, config.isPrimaryRenderer);
-  var profilerTimer = createProfilerTimer(now);
-  var popHostContext = hostContext.popHostContext,
-    popHostContainer = hostContext.popHostContainer;
-  var popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popLegacyContextProvider = legacyContext.popContextProvider;
-  var popProvider = newContext.popProvider;
-
-  var hydrationContext = ReactFiberHydrationContext(config);
-
-  var _ReactFiberBeginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      profilerTimer,
-      recalculateCurrentTime
-    ),
-    beginWork = _ReactFiberBeginWork.beginWork;
-
-  var _ReactFiberCompleteWo = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      hydrationContext,
-      profilerTimer
-    ),
-    completeWork = _ReactFiberCompleteWo.completeWork;
-
-  var _ReactFiberUnwindWork = ReactFiberUnwindWork(
-      config,
-      hostContext,
-      legacyContext,
-      newContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      recalculateCurrentTime,
-      markLegacyErrorBoundaryAsFailed,
-      isAlreadyFailedLegacyErrorBoundary,
-      onUncaughtError,
-      profilerTimer,
-      suspendRoot,
-      retrySuspendedRoot
-    ),
-    throwException = _ReactFiberUnwindWork.throwException,
-    unwindWork = _ReactFiberUnwindWork.unwindWork,
-    unwindInterruptedWork = _ReactFiberUnwindWork.unwindInterruptedWork,
-    createRootErrorUpdate = _ReactFiberUnwindWork.createRootErrorUpdate,
-    createClassErrorUpdate = _ReactFiberUnwindWork.createClassErrorUpdate;
-
-  var _ReactFiberCommitWork = ReactFiberCommitWork(
-      config,
-      onCommitPhaseError,
-      scheduleWork,
-      computeExpirationForFiber,
-      markLegacyErrorBoundaryAsFailed,
-      recalculateCurrentTime
-    ),
-    commitBeforeMutationLifeCycles =
-      _ReactFiberCommitWork.commitBeforeMutationLifeCycles,
-    commitResetTextContent = _ReactFiberCommitWork.commitResetTextContent,
-    commitPlacement = _ReactFiberCommitWork.commitPlacement,
-    commitDeletion = _ReactFiberCommitWork.commitDeletion,
-    commitWork = _ReactFiberCommitWork.commitWork,
-    commitLifeCycles = _ReactFiberCommitWork.commitLifeCycles,
-    commitAttachRef = _ReactFiberCommitWork.commitAttachRef,
-    commitDetachRef = _ReactFiberCommitWork.commitDetachRef;
-
-  var checkActualRenderTimeStackEmpty =
-      profilerTimer.checkActualRenderTimeStackEmpty,
-    pauseActualRenderTimerIfRunning =
-      profilerTimer.pauseActualRenderTimerIfRunning,
-    recordElapsedBaseRenderTimeIfRunning =
-      profilerTimer.recordElapsedBaseRenderTimeIfRunning,
-    resetActualRenderTimer = profilerTimer.resetActualRenderTimer,
-    resumeActualRenderTimerIfPaused =
-      profilerTimer.resumeActualRenderTimerIfPaused,
-    startBaseRenderTimer = profilerTimer.startBaseRenderTimer,
-    stopBaseRenderTimerIfRunning = profilerTimer.stopBaseRenderTimerIfRunning;
-
-  // Represents the current time in ms.
-
-  var originalStartTimeMs = now();
-  var mostRecentCurrentTime = msToExpirationTime(0);
-  var mostRecentCurrentTimeMs = originalStartTimeMs;
-
-  // Used to ensure computeUniqueAsyncExpiration is monotonically increases.
-  var lastUniqueAsyncExpiration = 0;
-
-  // Represents the expiration time that incoming updates should use. (If this
-  // is NoWork, use the default strategy: async updates in async mode, sync
-  // updates in sync mode.)
-  var expirationContext = NoWork;
-
-  var isWorking = false;
-
-  // The next work in progress fiber that we're currently working on.
-  var nextUnitOfWork = null;
-  var nextRoot = null;
-  // The time at which we're currently rendering work.
-  var nextRenderExpirationTime = NoWork;
-  var nextLatestTimeoutMs = -1;
-  var nextRenderIsExpired = false;
-
-  // The next fiber with an effect that we're currently committing.
-  var nextEffect = null;
-
-  var isCommitting = false;
-
-  var isRootReadyForCommit = false;
-
-  var legacyErrorBoundariesThatAlreadyFailed = null;
-
-  // Used for performance tracking.
-  var interruptedBy = null;
-
-  var stashedWorkInProgressProperties = void 0;
-  var replayUnitOfWork = void 0;
-  var isReplayingFailedUnitOfWork = void 0;
-  var originalReplayError = void 0;
-  var rethrowOriginalError = void 0;
-  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-    stashedWorkInProgressProperties = null;
-    isReplayingFailedUnitOfWork = false;
-    originalReplayError = null;
-    replayUnitOfWork = function(failedUnitOfWork, thrownValue, isAsync) {
-      if (
-        thrownValue !== null &&
-        typeof thrownValue === "object" &&
-        typeof thrownValue.then === "function"
-      ) {
-        // Don't replay promises. Treat everything else like an error.
-        // TODO: Need to figure out a different strategy if/when we add
-        // support for catching other types.
-        return;
-      }
-
-      // Restore the original state of the work-in-progress
-      if (stashedWorkInProgressProperties === null) {
-        // This should never happen. Don't throw because this code is DEV-only.
-        warning(
-          false,
-          "Could not replay rendering after an error. This is likely a bug in React. " +
-            "Please file an issue."
-        );
-        return;
-      }
-      assignFiberPropertiesInDEV(
-        failedUnitOfWork,
-        stashedWorkInProgressProperties
-      );
+var invokeGuardedCallback$3 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError$1 = ReactErrorUtils.hasCaughtError;
+var clearCaughtError$1 = ReactErrorUtils.clearCaughtError;
 
-      switch (failedUnitOfWork.tag) {
-        case HostRoot:
-          popHostContainer(failedUnitOfWork);
-          popTopLevelLegacyContextObject(failedUnitOfWork);
-          break;
-        case HostComponent:
-          popHostContext(failedUnitOfWork);
-          break;
-        case ClassComponent:
-          popLegacyContextProvider(failedUnitOfWork);
-          break;
-        case HostPortal:
-          popHostContainer(failedUnitOfWork);
-          break;
-        case ContextProvider:
-          popProvider(failedUnitOfWork);
-          break;
-      }
-      // Replay the begin phase.
-      isReplayingFailedUnitOfWork = true;
-      originalReplayError = thrownValue;
-      invokeGuardedCallback$2(null, workLoop, null, isAsync);
-      isReplayingFailedUnitOfWork = false;
-      originalReplayError = null;
-      if (hasCaughtError()) {
-        clearCaughtError();
+var didWarnAboutUndefinedSnapshotBeforeUpdate = null;
+{
+  didWarnAboutUndefinedSnapshotBeforeUpdate = new Set();
+}
 
-        if (enableProfilerTimer) {
-          // Stop "base" render timer again (after the re-thrown error).
-          stopBaseRenderTimerIfRunning();
-        }
-      } else {
-        // If the begin phase did not fail the second time, set this pointer
-        // back to the original value.
-        nextUnitOfWork = failedUnitOfWork;
-      }
-    };
-    rethrowOriginalError = function() {
-      throw originalReplayError;
-    };
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source;
+  var stack = errorInfo.stack;
+  if (stack === null && source !== null) {
+    stack = getStackAddendumByWorkInProgressFiber(source);
   }
 
-  function resetStack() {
-    if (nextUnitOfWork !== null) {
-      var interruptedWork = nextUnitOfWork.return;
-      while (interruptedWork !== null) {
-        unwindInterruptedWork(interruptedWork);
-        interruptedWork = interruptedWork.return;
-      }
-    }
+  var capturedError = {
+    componentName: source !== null ? getComponentName(source) : null,
+    componentStack: stack !== null ? stack : "",
+    error: errorInfo.value,
+    errorBoundary: null,
+    errorBoundaryName: null,
+    errorBoundaryFound: false,
+    willRetry: false
+  };
 
-    {
-      ReactStrictModeWarnings.discardPendingWarnings();
-      stack.checkThatStackIsEmpty();
+  if (boundary !== null && boundary.tag === ClassComponent) {
+    capturedError.errorBoundary = boundary.stateNode;
+    capturedError.errorBoundaryName = getComponentName(boundary);
+    capturedError.errorBoundaryFound = true;
+    capturedError.willRetry = true;
+  }
+
+  try {
+    logCapturedError(capturedError);
+  } catch (e) {
+    // Prevent cycle if logCapturedError() throws.
+    // A cycle may still occur if logCapturedError renders a component that throws.
+    var suppressLogging = e && e.suppressReactErrorLogging;
+    if (!suppressLogging) {
+      console.error(e);
     }
+  }
+}
 
-    nextRoot = null;
-    nextRenderExpirationTime = NoWork;
-    nextLatestTimeoutMs = -1;
-    nextRenderIsExpired = false;
-    nextUnitOfWork = null;
+var callComponentWillUnmountWithTimer = function(current, instance) {
+  startPhaseTimer(current, "componentWillUnmount");
+  instance.props = current.memoizedProps;
+  instance.state = current.memoizedState;
+  instance.componentWillUnmount();
+  stopPhaseTimer();
+};
 
-    isRootReadyForCommit = false;
+// Capture errors so they don't interrupt unmounting.
+function safelyCallComponentWillUnmount(current, instance) {
+  {
+    invokeGuardedCallback$3(
+      null,
+      callComponentWillUnmountWithTimer,
+      null,
+      current,
+      instance
+    );
+    if (hasCaughtError$1()) {
+      var unmountError = clearCaughtError$1();
+      captureCommitPhaseError(current, unmountError);
+    }
   }
+}
 
-  function commitAllHostEffects() {
-    while (nextEffect !== null) {
+function safelyDetachRef(current) {
+  var ref = current.ref;
+  if (ref !== null) {
+    if (typeof ref === "function") {
       {
-        ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
-      }
-      recordEffect();
-
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & ContentReset) {
-        commitResetTextContent(nextEffect);
-      }
-
-      if (effectTag & Ref) {
-        var current = nextEffect.alternate;
-        if (current !== null) {
-          commitDetachRef(current);
+        invokeGuardedCallback$3(null, ref, null, null);
+        if (hasCaughtError$1()) {
+          var refError = clearCaughtError$1();
+          captureCommitPhaseError(current, refError);
         }
       }
+    } else {
+      ref.current = null;
+    }
+  }
+}
 
-      // The following switch statement is only concerned about placement,
-      // updates, and deletions. To avoid needing to add a case for every
-      // possible bitmap value, we remove the secondary effects from the
-      // effect tag and switch on that value.
-      var primaryEffectTag = effectTag & (Placement | Update | Deletion);
-      switch (primaryEffectTag) {
-        case Placement: {
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          // TODO: findDOMNode doesn't rely on this any more but isMounted
-          // does and isMounted is deprecated anyway so we should be able
-          // to kill this.
-          nextEffect.effectTag &= ~Placement;
-          break;
-        }
-        case PlacementAndUpdate: {
-          // Placement
-          commitPlacement(nextEffect);
-          // Clear the "placement" from effect tag so that we know that this is inserted, before
-          // any life-cycles like componentDidMount gets called.
-          nextEffect.effectTag &= ~Placement;
-
-          // Update
-          var _current = nextEffect.alternate;
-          commitWork(_current, nextEffect);
-          break;
-        }
-        case Update: {
-          var _current2 = nextEffect.alternate;
-          commitWork(_current2, nextEffect);
-          break;
-        }
-        case Deletion: {
-          commitDeletion(nextEffect);
-          break;
+function commitBeforeMutationLifeCycles(current, finishedWork) {
+  switch (finishedWork.tag) {
+    case ClassComponent: {
+      if (finishedWork.effectTag & Snapshot) {
+        if (current !== null) {
+          var prevProps = current.memoizedProps;
+          var prevState = current.memoizedState;
+          startPhaseTimer(finishedWork, "getSnapshotBeforeUpdate");
+          var instance = finishedWork.stateNode;
+          instance.props = finishedWork.memoizedProps;
+          instance.state = finishedWork.memoizedState;
+          var snapshot = instance.getSnapshotBeforeUpdate(prevProps, prevState);
+          {
+            var didWarnSet = didWarnAboutUndefinedSnapshotBeforeUpdate;
+            if (snapshot === undefined && !didWarnSet.has(finishedWork.type)) {
+              didWarnSet.add(finishedWork.type);
+              warning(
+                false,
+                "%s.getSnapshotBeforeUpdate(): A snapshot value (or null) " +
+                  "must be returned. You have returned undefined.",
+                getComponentName(finishedWork)
+              );
+            }
+          }
+          instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+          stopPhaseTimer();
         }
       }
-      nextEffect = nextEffect.nextEffect;
+      return;
     }
-
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
+    case HostRoot:
+    case HostComponent:
+    case HostText:
+    case HostPortal:
+      // Nothing to do for these component types
+      return;
+    default: {
+      invariant(
+        false,
+        "This unit of work tag should not have side-effects. This error is " +
+          "likely caused by a bug in React. Please file an issue."
+      );
     }
   }
+}
 
-  function commitBeforeMutationLifecycles() {
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & Snapshot) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitBeforeMutationLifeCycles(current, nextEffect);
+function commitLifeCycles(
+  finishedRoot,
+  current,
+  finishedWork,
+  currentTime,
+  committedExpirationTime
+) {
+  switch (finishedWork.tag) {
+    case ClassComponent: {
+      var instance = finishedWork.stateNode;
+      if (finishedWork.effectTag & Update) {
+        if (current === null) {
+          startPhaseTimer(finishedWork, "componentDidMount");
+          instance.props = finishedWork.memoizedProps;
+          instance.state = finishedWork.memoizedState;
+          instance.componentDidMount();
+          stopPhaseTimer();
+        } else {
+          var prevProps = current.memoizedProps;
+          var prevState = current.memoizedState;
+          startPhaseTimer(finishedWork, "componentDidUpdate");
+          instance.props = finishedWork.memoizedProps;
+          instance.state = finishedWork.memoizedState;
+          instance.componentDidUpdate(
+            prevProps,
+            prevState,
+            instance.__reactInternalSnapshotBeforeUpdate
+          );
+          stopPhaseTimer();
+        }
       }
-
-      // Don't cleanup effects yet;
-      // This will be done by commitAllLifeCycles()
-      nextEffect = nextEffect.nextEffect;
-    }
-  }
-
-  function commitAllLifeCycles(
-    finishedRoot,
-    currentTime,
-    committedExpirationTime
-  ) {
-    {
-      ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
-
-      if (warnAboutDeprecatedLifecycles) {
-        ReactStrictModeWarnings.flushPendingDeprecationWarnings();
+      var updateQueue = finishedWork.updateQueue;
+      if (updateQueue !== null) {
+        instance.props = finishedWork.memoizedProps;
+        instance.state = finishedWork.memoizedState;
+        commitUpdateQueue(
+          finishedWork,
+          updateQueue,
+          instance,
+          committedExpirationTime
+        );
       }
+      return;
     }
-    while (nextEffect !== null) {
-      var effectTag = nextEffect.effectTag;
-
-      if (effectTag & (Update | Callback)) {
-        recordEffect();
-        var current = nextEffect.alternate;
-        commitLifeCycles(
-          finishedRoot,
-          current,
-          nextEffect,
-          currentTime,
+    case HostRoot: {
+      var _updateQueue = finishedWork.updateQueue;
+      if (_updateQueue !== null) {
+        var _instance = null;
+        if (finishedWork.child !== null) {
+          switch (finishedWork.child.tag) {
+            case HostComponent:
+              _instance = getPublicInstance(finishedWork.child.stateNode);
+              break;
+            case ClassComponent:
+              _instance = finishedWork.child.stateNode;
+              break;
+          }
+        }
+        commitUpdateQueue(
+          finishedWork,
+          _updateQueue,
+          _instance,
           committedExpirationTime
         );
       }
+      return;
+    }
+    case HostComponent: {
+      var _instance2 = finishedWork.stateNode;
 
-      if (effectTag & Ref) {
-        recordEffect();
-        commitAttachRef(nextEffect);
+      // Renderers may schedule work to be done after host components are mounted
+      // (eg DOM renderer may schedule auto-focus for inputs and form controls).
+      // These effects should only be committed when components are first mounted,
+      // aka when there is no current/alternate.
+      if (current === null && finishedWork.effectTag & Update) {
+        var type = finishedWork.type;
+        var props = finishedWork.memoizedProps;
       }
 
-      var next = nextEffect.nextEffect;
-      // Ensure that we clean these up so that we don't accidentally keep them.
-      // I'm not actually sure this matters because we can't reset firstEffect
-      // and lastEffect since they're on every node, not just the effectful
-      // ones. So we have to clean everything as we reuse nodes anyway.
-      nextEffect.nextEffect = null;
-      // Ensure that we reset the effectTag here so that we can rely on effect
-      // tags to reason about the current life-cycle.
-      nextEffect = next;
+      return;
+    }
+    case HostText: {
+      // We have no life-cycles associated with text.
+      return;
+    }
+    case HostPortal: {
+      // We have no life-cycles associated with portals.
+      return;
+    }
+    case Profiler: {
+      // We have no life-cycles associated with Profiler.
+      return;
+    }
+    case TimeoutComponent: {
+      // We have no life-cycles associated with Timeouts.
+      return;
+    }
+    default: {
+      invariant(
+        false,
+        "This unit of work tag should not have side-effects. This error is " +
+          "likely caused by a bug in React. Please file an issue."
+      );
     }
   }
+}
 
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      legacyErrorBoundariesThatAlreadyFailed !== null &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
-  }
-
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    if (legacyErrorBoundariesThatAlreadyFailed === null) {
-      legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
+function commitAttachRef(finishedWork) {
+  var ref = finishedWork.ref;
+  if (ref !== null) {
+    var instance = finishedWork.stateNode;
+    var instanceToUse = void 0;
+    switch (finishedWork.tag) {
+      case HostComponent:
+        instanceToUse = getPublicInstance(instance);
+        break;
+      default:
+        instanceToUse = instance;
+    }
+    if (typeof ref === "function") {
+      ref(instanceToUse);
     } else {
-      legacyErrorBoundariesThatAlreadyFailed.add(instance);
+      {
+        if (!ref.hasOwnProperty("current")) {
+          warning(
+            false,
+            "Unexpected ref object provided for %s. " +
+              "Use either a ref-setter function or React.createRef().%s",
+            getComponentName(finishedWork),
+            getStackAddendumByWorkInProgressFiber(finishedWork)
+          );
+        }
+      }
+
+      ref.current = instanceToUse;
     }
   }
+}
 
-  function commitRoot(finishedWork) {
-    isWorking = true;
-    isCommitting = true;
-    startCommitTimer();
-
-    var root = finishedWork.stateNode;
-    invariant(
-      root.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug " +
-        "related to the return field. This error is likely caused by a bug " +
-        "in React. Please file an issue."
-    );
-    var committedExpirationTime = root.pendingCommitExpirationTime;
-    invariant(
-      committedExpirationTime !== NoWork,
-      "Cannot commit an incomplete root. This error is likely caused by a " +
-        "bug in React. Please file an issue."
-    );
-    root.pendingCommitExpirationTime = NoWork;
-
-    var currentTime = recalculateCurrentTime();
-
-    // Reset this to null before calling lifecycles
-    ReactCurrentOwner.current = null;
-
-    var firstEffect = void 0;
-    if (finishedWork.effectTag > PerformedWork) {
-      // A fiber's effect list consists only of its children, not itself. So if
-      // the root has an effect, we need to add it to the end of the list. The
-      // resulting list is the set that would belong to the root's parent, if
-      // it had one; that is, all the effects in the tree including the root.
-      if (finishedWork.lastEffect !== null) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        firstEffect = finishedWork.firstEffect;
-      } else {
-        firstEffect = finishedWork;
-      }
+function commitDetachRef(current) {
+  var currentRef = current.ref;
+  if (currentRef !== null) {
+    if (typeof currentRef === "function") {
+      currentRef(null);
     } else {
-      // There is no effect on the root.
-      firstEffect = finishedWork.firstEffect;
+      currentRef.current = null;
     }
+  }
+}
 
-    prepareForCommit(root.containerInfo);
+// User-originating errors (lifecycles and refs) should not interrupt
+// deletion, so don't let them throw. Host-originating errors should
+// interrupt deletion, so it's okay
+function commitUnmount(current) {
+  if (typeof onCommitUnmount === "function") {
+    onCommitUnmount(current);
+  }
 
-    // Invoke instances of getSnapshotBeforeUpdate before mutation.
-    nextEffect = firstEffect;
-    startCommitSnapshotEffectsTimer();
-    while (nextEffect !== null) {
-      var didError = false;
-      var error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
-        if (hasCaughtError()) {
-          didError = true;
-          error = clearCaughtError();
-        }
+  switch (current.tag) {
+    case ClassComponent: {
+      safelyDetachRef(current);
+      var instance = current.stateNode;
+      if (typeof instance.componentWillUnmount === "function") {
+        safelyCallComponentWillUnmount(current, instance);
       }
-      if (didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
+      return;
+    }
+    case HostComponent: {
+      safelyDetachRef(current);
+      return;
+    }
+    case HostPortal: {
+      // TODO: this is recursive.
+      // We are also not using this parent because
+      // the portal will get pushed immediately.
+      if (supportsMutation) {
+        unmountHostComponents(current);
+      } else if (supportsPersistence) {
+        emptyPortalContainer(current);
       }
+      return;
     }
-    stopCommitSnapshotEffectsTimer();
+  }
+}
 
-    // Commit all the side-effects within a tree. We'll do this in two passes.
-    // The first pass performs all the host insertions, updates, deletions and
-    // ref unmounts.
-    nextEffect = firstEffect;
-    startCommitHostEffectsTimer();
-    while (nextEffect !== null) {
-      var _didError = false;
-      var _error = void 0;
-      {
-        invokeGuardedCallback$2(null, commitAllHostEffects, null);
-        if (hasCaughtError()) {
-          _didError = true;
-          _error = clearCaughtError();
-        }
-      }
-      if (_didError) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error);
-        // Clean-up
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
+function commitNestedUnmounts(root) {
+  // While we're inside a removed host node we don't want to call
+  // removeChild on the inner nodes because they're removed by the top
+  // call anyway. We also want to call componentWillUnmount on all
+  // composites before this host node is removed from the tree. Therefore
+  var node = root;
+  while (true) {
+    commitUnmount(node);
+    // Visit children because they may contain more composite or host nodes.
+    // Skip portals because commitUnmount() currently visits them recursively.
+    if (
+      node.child !== null &&
+      // If we use mutation we drill down into portals using commitUnmount above.
+      // If we don't use mutation we drill down into portals here instead.
+      (!supportsMutation || node.tag !== HostPortal)
+    ) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === root) {
+      return;
+    }
+    while (node.sibling === null) {
+      if (node.return === null || node.return === root) {
+        return;
       }
+      node = node.return;
     }
-    stopCommitHostEffectsTimer();
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+}
 
-    resetAfterCommit(root.containerInfo);
+function detachFiber(current) {
+  // Cut off the return pointers to disconnect it from the tree. Ideally, we
+  // should clear the child pointer of the parent alternate to let this
+  // get GC:ed but we don't know which for sure which parent is the current
+  // one so we'll settle for GC:ing the subtree of this child. This child
+  // itself will be GC:ed when the parent updates the next time.
+  current.return = null;
+  current.child = null;
+  if (current.alternate) {
+    current.alternate.child = null;
+    current.alternate.return = null;
+  }
+}
 
-    // The work-in-progress tree is now the current tree. This must come after
-    // the first pass of the commit phase, so that the previous tree is still
-    // current during componentWillUnmount, but before the second pass, so that
-    // the finished work is current during componentDidMount/Update.
-    root.current = finishedWork;
+function emptyPortalContainer(current) {
+  if (!supportsPersistence) {
+    return;
+  }
 
-    // In the second pass we'll perform all life-cycles and ref callbacks.
-    // Life-cycles happen as a separate pass so that all placements, updates,
-    // and deletions in the entire tree have already been invoked.
-    // This pass also triggers any renderer-specific initial effects.
-    nextEffect = firstEffect;
-    startCommitLifeCyclesTimer();
-    while (nextEffect !== null) {
-      var _didError2 = false;
-      var _error2 = void 0;
-      {
-        invokeGuardedCallback$2(
-          null,
-          commitAllLifeCycles,
-          null,
-          root,
-          currentTime,
-          committedExpirationTime
-        );
-        if (hasCaughtError()) {
-          _didError2 = true;
-          _error2 = clearCaughtError();
-        }
-      }
-      if (_didError2) {
-        invariant(
-          nextEffect !== null,
-          "Should have next effect. This error is likely caused by a bug " +
-            "in React. Please file an issue."
-        );
-        onCommitPhaseError(nextEffect, _error2);
-        if (nextEffect !== null) {
-          nextEffect = nextEffect.nextEffect;
-        }
-      }
-    }
+  var portal = current.stateNode;
+  var containerInfo = portal.containerInfo;
 
-    if (enableProfilerTimer) {
-      {
-        checkActualRenderTimeStackEmpty();
-      }
-      resetActualRenderTimer();
-    }
+  var emptyChildSet = createContainerChildSet(containerInfo);
+  replaceContainerChildren(containerInfo, emptyChildSet);
+}
 
-    isCommitting = false;
-    isWorking = false;
-    stopCommitLifeCyclesTimer();
-    stopCommitTimer();
-    if (typeof onCommitRoot === "function") {
-      onCommitRoot(finishedWork.stateNode);
+function commitContainer(finishedWork) {
+  if (!supportsPersistence) {
+    return;
+  }
+
+  switch (finishedWork.tag) {
+    case ClassComponent: {
+      return;
+    }
+    case HostComponent: {
+      return;
     }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
+    case HostText: {
+      return;
     }
+    case HostRoot:
+    case HostPortal: {
+      var portalOrRoot = finishedWork.stateNode;
+      var containerInfo = portalOrRoot.containerInfo,
+        _pendingChildren = portalOrRoot.pendingChildren;
 
-    markCommittedPriorityLevels(root, currentTime, root.current.expirationTime);
-    var remainingTime = findNextPendingPriorityLevel(root);
-    if (remainingTime === NoWork) {
-      // If there's no remaining work, we can clear the set of already failed
-      // error boundaries.
-      legacyErrorBoundariesThatAlreadyFailed = null;
+      replaceContainerChildren(containerInfo, _pendingChildren);
+      return;
+    }
+    default: {
+      invariant(
+        false,
+        "This unit of work tag should not have side-effects. This error is " +
+          "likely caused by a bug in React. Please file an issue."
+      );
     }
-    return remainingTime;
   }
+}
 
-  function resetExpirationTime(workInProgress, renderTime) {
-    if (renderTime !== Never && workInProgress.expirationTime === Never) {
-      // The children of this component are hidden. Don't bubble their
-      // expiration times.
-      return;
+function getHostParentFiber(fiber) {
+  var parent = fiber.return;
+  while (parent !== null) {
+    if (isHostParent(parent)) {
+      return parent;
     }
+    parent = parent.return;
+  }
+  invariant(
+    false,
+    "Expected to find a host parent. This error is likely caused by a bug " +
+      "in React. Please file an issue."
+  );
+}
 
-    // Check for pending updates.
-    var newExpirationTime = NoWork;
-    switch (workInProgress.tag) {
-      case HostRoot:
-      case ClassComponent: {
-        var updateQueue = workInProgress.updateQueue;
-        if (updateQueue !== null) {
-          newExpirationTime = updateQueue.expirationTime;
-        }
+function isHostParent(fiber) {
+  return (
+    fiber.tag === HostComponent ||
+    fiber.tag === HostRoot ||
+    fiber.tag === HostPortal
+  );
+}
+
+function getHostSibling(fiber) {
+  // We're going to search forward into the tree until we find a sibling host
+  // node. Unfortunately, if multiple insertions are done in a row we have to
+  // search past them. This leads to exponential search for the next sibling.
+  var node = fiber;
+  siblings: while (true) {
+    // If we didn't find anything, let's try the next sibling.
+    while (node.sibling === null) {
+      if (node.return === null || isHostParent(node.return)) {
+        // If we pop out of the root or hit the parent the fiber we are the
+        // last sibling.
+        return null;
       }
+      node = node.return;
     }
-
-    // TODO: Calls need to visit stateNode
-
-    // Bubble up the earliest expiration time.
-    // (And "base" render timers if that feature flag is enabled)
-    if (enableProfilerTimer && workInProgress.mode & ProfileMode) {
-      var treeBaseTime = workInProgress.selfBaseTime;
-      var child = workInProgress.child;
-      while (child !== null) {
-        treeBaseTime += child.treeBaseTime;
-        if (
-          child.expirationTime !== NoWork &&
-          (newExpirationTime === NoWork ||
-            newExpirationTime > child.expirationTime)
-        ) {
-          newExpirationTime = child.expirationTime;
-        }
-        child = child.sibling;
+    node.sibling.return = node.return;
+    node = node.sibling;
+    while (node.tag !== HostComponent && node.tag !== HostText) {
+      // If it is not host node and, we might have a host node inside it.
+      // Try to search down until we find one.
+      if (node.effectTag & Placement) {
+        // If we don't have a child, try the siblings instead.
+        continue siblings;
       }
-      workInProgress.treeBaseTime = treeBaseTime;
-    } else {
-      var _child = workInProgress.child;
-      while (_child !== null) {
-        if (
-          _child.expirationTime !== NoWork &&
-          (newExpirationTime === NoWork ||
-            newExpirationTime > _child.expirationTime)
-        ) {
-          newExpirationTime = _child.expirationTime;
-        }
-        _child = _child.sibling;
+      // If we don't have a child, try the siblings instead.
+      // We also skip portals because they are not part of this host tree.
+      if (node.child === null || node.tag === HostPortal) {
+        continue siblings;
+      } else {
+        node.child.return = node;
+        node = node.child;
       }
     }
-
-    workInProgress.expirationTime = newExpirationTime;
+    // Check if this host node is stable or about to be placed.
+    if (!(node.effectTag & Placement)) {
+      // Found it!
+      return node.stateNode;
+    }
   }
+}
 
-  function completeUnitOfWork(workInProgress) {
-    // Attempt to complete the current unit of work, then move to the
-    // next sibling. If there are no more siblings, return to the
-    // parent fiber.
-    while (true) {
-      // The current, flushed, state of this fiber is the alternate.
-      // Ideally nothing should rely on this, but relying on it here
-      // means that we don't need an additional field on the work in
-      // progress.
-      var current = workInProgress.alternate;
-      {
-        ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
-      }
-
-      var returnFiber = workInProgress.return;
-      var siblingFiber = workInProgress.sibling;
-
-      if ((workInProgress.effectTag & Incomplete) === NoEffect) {
-        // This fiber completed.
-        var next = completeWork(
-          current,
-          workInProgress,
-          nextRenderExpirationTime
-        );
-        stopWorkTimer(workInProgress);
-        resetExpirationTime(workInProgress, nextRenderExpirationTime);
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
-
-        if (next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
-          }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          return next;
-        }
-
-        if (
-          returnFiber !== null &&
-          // Do not append effects to parents if a sibling failed to complete
-          (returnFiber.effectTag & Incomplete) === NoEffect
-        ) {
-          // Append all the effects of the subtree and this fiber onto the effect
-          // list of the parent. The completion order of the children affects the
-          // side-effect order.
-          if (returnFiber.firstEffect === null) {
-            returnFiber.firstEffect = workInProgress.firstEffect;
-          }
-          if (workInProgress.lastEffect !== null) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
-            }
-            returnFiber.lastEffect = workInProgress.lastEffect;
-          }
-
-          // If this fiber had side-effects, we append it AFTER the children's
-          // side-effects. We can perform certain side-effects earlier if
-          // needed, by doing multiple passes over the effect list. We don't want
-          // to schedule our own side-effect on our own list because if end up
-          // reusing children we'll schedule this effect onto itself since we're
-          // at the end.
-          var effectTag = workInProgress.effectTag;
-          // Skip both NoWork and PerformedWork tags when creating the effect list.
-          // PerformedWork effect is read by React DevTools but shouldn't be committed.
-          if (effectTag > PerformedWork) {
-            if (returnFiber.lastEffect !== null) {
-              returnFiber.lastEffect.nextEffect = workInProgress;
-            } else {
-              returnFiber.firstEffect = workInProgress;
-            }
-            returnFiber.lastEffect = workInProgress;
-          }
-        }
+function commitPlacement(finishedWork) {
+  if (!supportsMutation) {
+    return;
+  }
 
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
-        }
+  // Recursively insert all host nodes into the parent.
+  var parentFiber = getHostParentFiber(finishedWork);
+  var parent = void 0;
+  var isContainer = void 0;
+  switch (parentFiber.tag) {
+    case HostComponent:
+      parent = parentFiber.stateNode;
+      isContainer = false;
+      break;
+    case HostRoot:
+      parent = parentFiber.stateNode.containerInfo;
+      isContainer = true;
+      break;
+    case HostPortal:
+      parent = parentFiber.stateNode.containerInfo;
+      isContainer = true;
+      break;
+    default:
+      invariant(
+        false,
+        "Invalid host parent fiber. This error is likely caused by a bug " +
+          "in React. Please file an issue."
+      );
+  }
+  if (parentFiber.effectTag & ContentReset) {
+    // Reset the text content of the parent before doing any insertions
+    parentFiber.effectTag &= ~ContentReset;
+  }
 
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
+  var before = getHostSibling(finishedWork);
+  // We only have the top Fiber that was inserted but we need recurse down its
+  // children to find all the terminal nodes.
+  var node = finishedWork;
+  while (true) {
+    if (node.tag === HostComponent || node.tag === HostText) {
+      if (before) {
+        if (isContainer) {
+          insertInContainerBefore(parent, node.stateNode, before);
         } else {
-          // We've reached the root.
-          isRootReadyForCommit = true;
-          return null;
+          insertBefore(parent, node.stateNode, before);
         }
       } else {
-        // This fiber did not complete because something threw. Pop values off
-        // the stack without entering the complete phase. If this is a boundary,
-        // capture values if possible.
-        var _next = unwindWork(
-          workInProgress,
-          nextRenderIsExpired,
-          nextRenderExpirationTime
-        );
-        // Because this fiber did not complete, don't reset its expiration time.
-        if (workInProgress.effectTag & DidCapture) {
-          // Restarting an error boundary
-          stopFailedWorkTimer(workInProgress);
-        } else {
-          stopWorkTimer(workInProgress);
-        }
-
-        {
-          ReactDebugCurrentFiber.resetCurrentFiber();
-        }
-
-        if (_next !== null) {
-          stopWorkTimer(workInProgress);
-          if (true && ReactFiberInstrumentation_1.debugTool) {
-            ReactFiberInstrumentation_1.debugTool.onCompleteWork(
-              workInProgress
-            );
-          }
-          // If completing this work spawned new work, do that next. We'll come
-          // back here again.
-          // Since we're restarting, remove anything that is not a host effect
-          // from the effect tag.
-          _next.effectTag &= HostEffectMask;
-          return _next;
-        }
-
-        if (returnFiber !== null) {
-          // Mark the parent fiber as incomplete and clear its effect list.
-          returnFiber.firstEffect = returnFiber.lastEffect = null;
-          returnFiber.effectTag |= Incomplete;
-        }
-
-        if (true && ReactFiberInstrumentation_1.debugTool) {
-          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
-        }
-
-        if (siblingFiber !== null) {
-          // If there is more work to do in this returnFiber, do that next.
-          return siblingFiber;
-        } else if (returnFiber !== null) {
-          // If there's no more work in this returnFiber. Complete the returnFiber.
-          workInProgress = returnFiber;
-          continue;
+        if (isContainer) {
+          appendChildToContainer(parent, node.stateNode);
         } else {
-          return null;
+          appendChild(parent, node.stateNode);
         }
       }
+    } else if (node.tag === HostPortal) {
+      // If the insertion itself is a portal, then we don't want to traverse
+      // down its children. Instead, we'll get insertions from each child in
+      // the portal directly.
+    } else if (node.child !== null) {
+      node.child.return = node;
+      node = node.child;
+      continue;
     }
-
-    // Without this explicit null return Flow complains of invalid return type
-    // TODO Remove the above while(true) loop
-    // eslint-disable-next-line no-unreachable
-    return null;
-  }
-
-  function performUnitOfWork(workInProgress) {
-    // The current, flushed, state of this fiber is the alternate.
-    // Ideally nothing should rely on this, but relying on it here
-    // means that we don't need an additional field on the work in
-    // progress.
-    var current = workInProgress.alternate;
-
-    // See if beginning this work spawns more work.
-    startWorkTimer(workInProgress);
-    {
-      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+    if (node === finishedWork) {
+      return;
     }
-
-    if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-      stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
-        stashedWorkInProgressProperties,
-        workInProgress
-      );
+    while (node.sibling === null) {
+      if (node.return === null || node.return === finishedWork) {
+        return;
+      }
+      node = node.return;
     }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+}
 
-    var next = void 0;
-    if (enableProfilerTimer) {
-      if (workInProgress.mode & ProfileMode) {
-        startBaseRenderTimer();
-      }
+function unmountHostComponents(current) {
+  // We only have the top Fiber that was inserted but we need recurse down its
+  var node = current;
 
-      next = beginWork(current, workInProgress, nextRenderExpirationTime);
+  // Each iteration, currentParent is populated with node's host parent if not
+  // currentParentIsValid.
+  var currentParentIsValid = false;
+  var currentParent = void 0;
+  var currentParentIsContainer = void 0;
 
-      if (workInProgress.mode & ProfileMode) {
-        // Update "base" time if the render wasn't bailed out on.
-        recordElapsedBaseRenderTimeIfRunning(workInProgress);
-        stopBaseRenderTimerIfRunning();
+  while (true) {
+    if (!currentParentIsValid) {
+      var parent = node.return;
+      findParent: while (true) {
+        invariant(
+          parent !== null,
+          "Expected to find a host parent. This error is likely caused by " +
+            "a bug in React. Please file an issue."
+        );
+        switch (parent.tag) {
+          case HostComponent:
+            currentParent = parent.stateNode;
+            currentParentIsContainer = false;
+            break findParent;
+          case HostRoot:
+            currentParent = parent.stateNode.containerInfo;
+            currentParentIsContainer = true;
+            break findParent;
+          case HostPortal:
+            currentParent = parent.stateNode.containerInfo;
+            currentParentIsContainer = true;
+            break findParent;
+        }
+        parent = parent.return;
       }
-    } else {
-      next = beginWork(current, workInProgress, nextRenderExpirationTime);
+      currentParentIsValid = true;
     }
 
-    {
-      ReactDebugCurrentFiber.resetCurrentFiber();
-      if (isReplayingFailedUnitOfWork) {
-        // Currently replaying a failed unit of work. This should be unreachable,
-        // because the render phase is meant to be idempotent, and it should
-        // have thrown again. Since it didn't, rethrow the original error, so
-        // React's internal stack is not misaligned.
-        rethrowOriginalError();
+    if (node.tag === HostComponent || node.tag === HostText) {
+      commitNestedUnmounts(node);
+      // After all the children have unmounted, it is now safe to remove the
+      // node from the tree.
+      if (currentParentIsContainer) {
+        removeChildFromContainer(currentParent, node.stateNode);
+      } else {
+        removeChild(currentParent, node.stateNode);
+      }
+      // Don't visit children because we already visited them.
+    } else if (node.tag === HostPortal) {
+      // When we go into a portal, it becomes the parent to remove from.
+      // We will reassign it back when we pop the portal on the way up.
+      currentParent = node.stateNode.containerInfo;
+      // Visit children because portals might contain host components.
+      if (node.child !== null) {
+        node.child.return = node;
+        node = node.child;
+        continue;
+      }
+    } else {
+      commitUnmount(node);
+      // Visit children because we may find more host components below.
+      if (node.child !== null) {
+        node.child.return = node;
+        node = node.child;
+        continue;
       }
     }
-    if (true && ReactFiberInstrumentation_1.debugTool) {
-      ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
+    if (node === current) {
+      return;
     }
-
-    if (next === null) {
-      // If this doesn't spawn new work, complete the current work.
-      next = completeUnitOfWork(workInProgress);
+    while (node.sibling === null) {
+      if (node.return === null || node.return === current) {
+        return;
+      }
+      node = node.return;
+      if (node.tag === HostPortal) {
+        // When we go out of the portal, we need to restore the parent.
+        // Since we don't keep a stack of them, we will search for it.
+        currentParentIsValid = false;
+      }
     }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+}
 
-    ReactCurrentOwner.current = null;
+function commitDeletion(current) {
+  if (supportsMutation) {
+    // Recursively delete all host nodes from the parent.
+    // Detach refs and call componentWillUnmount() on the whole subtree.
+    unmountHostComponents(current);
+  } else {
+    // Detach refs and call componentWillUnmount() on the whole subtree.
+    commitNestedUnmounts(current);
+  }
+  detachFiber(current);
+}
 
-    return next;
+function commitWork(current, finishedWork) {
+  if (!supportsMutation) {
+    commitContainer(finishedWork);
+    return;
   }
 
-  function workLoop(isAsync) {
-    if (!isAsync) {
-      // Flush all expired work.
-      while (nextUnitOfWork !== null) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      }
-    } else {
-      // Flush asynchronous work until the deadline runs out of time.
-      while (nextUnitOfWork !== null && !shouldYield()) {
-        nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+  switch (finishedWork.tag) {
+    case ClassComponent: {
+      return;
+    }
+    case HostComponent: {
+      var instance = finishedWork.stateNode;
+      if (instance != null) {
+        // Commit the work prepared earlier.
+        var newProps = finishedWork.memoizedProps;
+        // For hydration we reuse the update path but we treat the oldProps
+        // as the newProps. The updatePayload will contain the real change in
+        // this case.
+        var oldProps = current !== null ? current.memoizedProps : newProps;
+        var type = finishedWork.type;
+        // TODO: Type the updateQueue to be specific to host components.
+        var updatePayload = finishedWork.updateQueue;
+        finishedWork.updateQueue = null;
+        if (updatePayload !== null) {
+          commitUpdate(
+            instance,
+            updatePayload,
+            type,
+            oldProps,
+            newProps,
+            finishedWork
+          );
+        }
       }
-
+      return;
+    }
+    case HostText: {
+      invariant(
+        finishedWork.stateNode !== null,
+        "This should have a text node initialized. This error is likely " +
+          "caused by a bug in React. Please file an issue."
+      );
+      var textInstance = finishedWork.stateNode;
+      var newText = finishedWork.memoizedProps;
+      // For hydration we reuse the update path but we treat the oldProps
+      // as the newProps. The updatePayload will contain the real change in
+      // this case.
+      var oldText = current !== null ? current.memoizedProps : newText;
+      commitTextUpdate(textInstance, oldText, newText);
+      return;
+    }
+    case HostRoot: {
+      return;
+    }
+    case Profiler: {
       if (enableProfilerTimer) {
-        // If we didn't finish, pause the "actual" render timer.
-        // We'll restart it when we resume work.
-        pauseActualRenderTimerIfRunning();
+        var onRender = finishedWork.memoizedProps.onRender;
+        onRender(
+          finishedWork.memoizedProps.id,
+          current === null ? "mount" : "update",
+          finishedWork.actualDuration,
+          finishedWork.treeBaseTime,
+          finishedWork.actualStartTime,
+          getCommitTime()
+        );
       }
+      return;
     }
-  }
-
-  function renderRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
-    );
-    isWorking = true;
-
-    // Check if we're starting from a fresh stack, or if we're resuming from
-    // previously yielded work.
-    if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      nextUnitOfWork === null
-    ) {
-      // Reset the stack and start working from the root.
-      resetStack();
-      nextRoot = root;
-      nextRenderExpirationTime = expirationTime;
-      nextLatestTimeoutMs = -1;
-      nextUnitOfWork = createWorkInProgress(
-        nextRoot.current,
-        null,
-        nextRenderExpirationTime
+    case TimeoutComponent: {
+      return;
+    }
+    default: {
+      invariant(
+        false,
+        "This unit of work tag should not have side-effects. This error is " +
+          "likely caused by a bug in React. Please file an issue."
       );
-      root.pendingCommitExpirationTime = NoWork;
     }
+  }
+}
 
-    var didFatal = false;
-
-    nextRenderIsExpired =
-      !isAsync || nextRenderExpirationTime <= mostRecentCurrentTime;
-
-    startWorkLoopTimer(nextUnitOfWork);
-
-    do {
-      try {
-        workLoop(isAsync);
-      } catch (thrownValue) {
-        if (enableProfilerTimer) {
-          // Stop "base" render timer in the event of an error.
-          stopBaseRenderTimerIfRunning();
-        }
-
-        if (nextUnitOfWork === null) {
-          // This is a fatal error.
-          didFatal = true;
-          onUncaughtError(thrownValue);
-        } else {
-          {
-            // Reset global debug state
-            // We assume this is defined in DEV
-            resetCurrentlyProcessingQueue();
-          }
-
-          var failedUnitOfWork = nextUnitOfWork;
-          if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
-            replayUnitOfWork(failedUnitOfWork, thrownValue, isAsync);
-          }
-
-          // TODO: we already know this isn't true in some cases.
-          // At least this shows a nicer error message until we figure out the cause.
-          // https://github.com/facebook/react/issues/12449#issuecomment-386727431
-          invariant(
-            nextUnitOfWork !== null,
-            "Failed to replay rendering after an error. This " +
-              "is likely caused by a bug in React. Please file an issue " +
-              "with a reproducing case to help us find it."
-          );
+function commitResetTextContent(current) {
+  if (!supportsMutation) {
+    return;
+  }
+  resetTextContent(current.stateNode);
+}
 
-          var sourceFiber = nextUnitOfWork;
-          var returnFiber = sourceFiber.return;
-          if (returnFiber === null) {
-            // This is the root. The root could capture its own errors. However,
-            // we don't know if it errors before or after we pushed the host
-            // context. This information is needed to avoid a stack mismatch.
-            // Because we're not sure, treat this as a fatal error. We could track
-            // which phase it fails in, but doesn't seem worth it. At least
-            // for now.
-            didFatal = true;
-            onUncaughtError(thrownValue);
-            break;
-          }
-          throwException(
-            root,
-            returnFiber,
-            sourceFiber,
-            thrownValue,
-            nextRenderIsExpired,
-            nextRenderExpirationTime,
-            mostRecentCurrentTimeMs
-          );
-          nextUnitOfWork = completeUnitOfWork(sourceFiber);
-        }
-      }
-      break;
-    } while (true);
+function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+  var update = createUpdate(expirationTime);
+  // Unmount the root by rendering null.
+  update.tag = CaptureUpdate;
+  // Caution: React DevTools currently depends on this property
+  // being called "element".
+  update.payload = { element: null };
+  var error = errorInfo.value;
+  update.callback = function() {
+    onUncaughtError(error);
+    logError(fiber, errorInfo);
+  };
+  return update;
+}
 
-    // We're done performing work. Time to clean up.
-    var didCompleteRoot = false;
-    isWorking = false;
+function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+  var update = createUpdate(expirationTime);
+  update.tag = CaptureUpdate;
+  var getDerivedStateFromCatch = fiber.type.getDerivedStateFromCatch;
+  if (
+    enableGetDerivedStateFromCatch &&
+    typeof getDerivedStateFromCatch === "function"
+  ) {
+    var error = errorInfo.value;
+    update.payload = function() {
+      return getDerivedStateFromCatch(error);
+    };
+  }
 
-    // Yield back to main thread.
-    if (didFatal) {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There was a fatal error.
-      {
-        stack.resetStackAfterFatalErrorInDev();
-      }
-      return null;
-    } else if (nextUnitOfWork === null) {
-      // We reached the root.
-      if (isRootReadyForCommit) {
-        didCompleteRoot = true;
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        // The root successfully completed. It's ready for commit.
-        root.pendingCommitExpirationTime = expirationTime;
-        var finishedWork = root.current.alternate;
-        return finishedWork;
-      } else {
-        // The root did not complete.
-        stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-        interruptedBy = null;
-        invariant(
-          !nextRenderIsExpired,
-          "Expired work should have completed. This error is likely caused " +
-            "by a bug in React. Please file an issue."
-        );
-        markSuspendedPriorityLevel(root, expirationTime);
-        if (nextLatestTimeoutMs >= 0) {
-          setTimeout(function() {
-            retrySuspendedRoot(root, expirationTime);
-          }, nextLatestTimeoutMs);
-        }
-        var firstUnblockedExpirationTime = findNextPendingPriorityLevel(root);
-        onBlock(firstUnblockedExpirationTime);
-        return null;
-      }
-    } else {
-      stopWorkLoopTimer(interruptedBy, didCompleteRoot);
-      interruptedBy = null;
-      // There's more work to do, but we ran out of time. Yield back to
-      // the renderer.
-      return null;
-    }
+  var inst = fiber.stateNode;
+  if (inst !== null && typeof inst.componentDidCatch === "function") {
+    update.callback = function callback() {
+      if (
+        !enableGetDerivedStateFromCatch ||
+        getDerivedStateFromCatch !== "function"
+      ) {
+        // To preserve the preexisting retry behavior of error boundaries,
+        // we keep track of which ones already failed during this batch.
+        // This gets reset before we yield back to the browser.
+        // TODO: Warn in strict mode if getDerivedStateFromCatch is
+        // not defined.
+        markLegacyErrorBoundaryAsFailed(this);
+      }
+      var error = errorInfo.value;
+      var stack = errorInfo.stack;
+      logError(fiber, errorInfo);
+      this.componentDidCatch(error, {
+        componentStack: stack !== null ? stack : ""
+      });
+    };
   }
+  return update;
+}
 
-  function dispatch(sourceFiber, value, expirationTime) {
-    invariant(
-      !isWorking || isCommitting,
-      "dispatch: Cannot dispatch during the render phase."
-    );
+function schedulePing(finishedWork) {
+  // Once the promise resolves, we should try rendering the non-
+  // placeholder state again.
+  var currentTime = recalculateCurrentTime();
+  var expirationTime = computeExpirationForFiber(currentTime, finishedWork);
+  var recoveryUpdate = createUpdate(expirationTime);
+  enqueueUpdate(finishedWork, recoveryUpdate, expirationTime);
+  scheduleWork(finishedWork, expirationTime);
+}
+
+function throwException(
+  root,
+  returnFiber,
+  sourceFiber,
+  value,
+  renderExpirationTime,
+  currentTimeMs
+) {
+  // The source fiber did not complete.
+  sourceFiber.effectTag |= Incomplete;
+  // Its effect list is no longer valid.
+  sourceFiber.firstEffect = sourceFiber.lastEffect = null;
 
-    var fiber = sourceFiber.return;
-    while (fiber !== null) {
-      switch (fiber.tag) {
-        case ClassComponent:
-          var ctor = fiber.type;
-          var instance = fiber.stateNode;
-          if (
-            typeof ctor.getDerivedStateFromCatch === "function" ||
-            (typeof instance.componentDidCatch === "function" &&
-              !isAlreadyFailedLegacyErrorBoundary(instance))
+  if (
+    enableSuspense &&
+    value !== null &&
+    typeof value === "object" &&
+    typeof value.then === "function"
+  ) {
+    // This is a thenable.
+    var thenable = value;
+
+    // TODO: Should use the earliest known expiration time
+    var expirationTimeMs = expirationTimeToMs(renderExpirationTime);
+    var startTimeMs = expirationTimeMs - 5000;
+    var elapsedMs = currentTimeMs - startTimeMs;
+    if (elapsedMs < 0) {
+      elapsedMs = 0;
+    }
+    var remainingTimeMs = expirationTimeMs - currentTimeMs;
+
+    // Find the earliest timeout of all the timeouts in the ancestor path.
+    // TODO: Alternatively, we could store the earliest timeout on the context
+    // stack, rather than searching on every suspend.
+    var _workInProgress = returnFiber;
+    var earliestTimeoutMs = -1;
+    searchForEarliestTimeout: do {
+      if (_workInProgress.tag === TimeoutComponent) {
+        var current = _workInProgress.alternate;
+        if (current !== null && current.memoizedState === true) {
+          // A parent Timeout already committed in a placeholder state. We
+          // need to handle this promise immediately. In other words, we
+          // should never suspend inside a tree that already expired.
+          earliestTimeoutMs = 0;
+          break searchForEarliestTimeout;
+        }
+        var timeoutPropMs = _workInProgress.pendingProps.ms;
+        if (typeof timeoutPropMs === "number") {
+          if (timeoutPropMs <= 0) {
+            earliestTimeoutMs = 0;
+            break searchForEarliestTimeout;
+          } else if (
+            earliestTimeoutMs === -1 ||
+            timeoutPropMs < earliestTimeoutMs
           ) {
-            var errorInfo = createCapturedValue(value, sourceFiber);
-            var update = createClassErrorUpdate(
-              fiber,
-              errorInfo,
-              expirationTime
-            );
-            enqueueUpdate(fiber, update, expirationTime);
-            scheduleWork(fiber, expirationTime);
-            return;
+            earliestTimeoutMs = timeoutPropMs;
           }
-          break;
-        case HostRoot: {
-          var _errorInfo = createCapturedValue(value, sourceFiber);
-          var _update = createRootErrorUpdate(
-            fiber,
-            _errorInfo,
-            expirationTime
-          );
-          enqueueUpdate(fiber, _update, expirationTime);
-          scheduleWork(fiber, expirationTime);
-          return;
+        } else if (earliestTimeoutMs === -1) {
+          earliestTimeoutMs = remainingTimeMs;
         }
       }
-      fiber = fiber.return;
-    }
+      _workInProgress = _workInProgress.return;
+    } while (_workInProgress !== null);
 
-    if (sourceFiber.tag === HostRoot) {
-      // Error was thrown at the root. There is no parent, so the root
-      // itself should capture it.
-      var rootFiber = sourceFiber;
-      var _errorInfo2 = createCapturedValue(value, rootFiber);
-      var _update2 = createRootErrorUpdate(
-        rootFiber,
-        _errorInfo2,
-        expirationTime
-      );
-      enqueueUpdate(rootFiber, _update2, expirationTime);
-      scheduleWork(rootFiber, expirationTime);
-    }
-  }
+    // Compute the remaining time until the timeout.
+    var msUntilTimeout = earliestTimeoutMs - elapsedMs;
 
-  function onCommitPhaseError(fiber, error) {
-    return dispatch(fiber, error, Sync);
+    if (renderExpirationTime === Never || msUntilTimeout > 0) {
+      // There's still time remaining.
+      markTimeout(root, thenable, msUntilTimeout, renderExpirationTime);
+      var onResolveOrReject = function() {
+        retrySuspendedRoot(root, renderExpirationTime);
+      };
+      thenable.then(onResolveOrReject, onResolveOrReject);
+      return;
+    } else {
+      // No time remaining. Need to fallback to placeholder.
+      // Find the nearest timeout that can be retried.
+      _workInProgress = returnFiber;
+      do {
+        switch (_workInProgress.tag) {
+          case HostRoot: {
+            // The root expired, but no fallback was provided. Throw a
+            // helpful error.
+            var message =
+              renderExpirationTime === Sync
+                ? "A synchronous update was suspended, but no fallback UI " +
+                  "was provided."
+                : "An update was suspended for longer than the timeout, " +
+                  "but no fallback UI was provided.";
+            value = new Error(message);
+            break;
+          }
+          case TimeoutComponent: {
+            if ((_workInProgress.effectTag & DidCapture) === NoEffect) {
+              _workInProgress.effectTag |= ShouldCapture;
+              var _onResolveOrReject = schedulePing.bind(null, _workInProgress);
+              thenable.then(_onResolveOrReject, _onResolveOrReject);
+              return;
+            }
+            // Already captured during this render. Continue to the next
+            // Timeout ancestor.
+            break;
+          }
+        }
+        _workInProgress = _workInProgress.return;
+      } while (_workInProgress !== null);
+    }
+  } else {
+    // This is an error.
+    markError(root);
+    if (
+      // Retry (at the same priority) one more time before handling the error.
+      // The retry will flush synchronously. (Unless we're already rendering
+      // synchronously, in which case move to the next check.)
+      (!root.didError && renderExpirationTime !== Sync) ||
+      // There's lower priority work. If so, it may have the effect of fixing
+      // the exception that was just thrown.
+      hasLowerPriorityWork(root, renderExpirationTime)
+    ) {
+      return;
+    }
   }
 
-  function computeAsyncExpiration(currentTime) {
-    // Given the current clock time, returns an expiration time. We use rounding
-    // to batch like updates together.
-    // Should complete within ~1000ms. 1200ms max.
-    var expirationMs = 5000;
-    var bucketSizeMs = 250;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
-  }
+  // We didn't find a boundary that could handle this type of exception. Start
+  // over and traverse parent path again, this time treating the exception
+  // as an error.
+  value = createCapturedValue(value, sourceFiber);
+  var workInProgress = returnFiber;
+  do {
+    switch (workInProgress.tag) {
+      case HostRoot: {
+        var _errorInfo = value;
+        workInProgress.effectTag |= ShouldCapture;
+        var update = createRootErrorUpdate(
+          workInProgress,
+          _errorInfo,
+          renderExpirationTime
+        );
+        enqueueCapturedUpdate(workInProgress, update, renderExpirationTime);
+        return;
+      }
+      case ClassComponent:
+        // Capture and retry
+        var errorInfo = value;
+        var ctor = workInProgress.type;
+        var instance = workInProgress.stateNode;
+        if (
+          (workInProgress.effectTag & DidCapture) === NoEffect &&
+          ((typeof ctor.getDerivedStateFromCatch === "function" &&
+            enableGetDerivedStateFromCatch) ||
+            (instance !== null &&
+              typeof instance.componentDidCatch === "function" &&
+              !isAlreadyFailedLegacyErrorBoundary(instance)))
+        ) {
+          workInProgress.effectTag |= ShouldCapture;
+          // Schedule the error boundary to re-render using updated state
+          var _update = createClassErrorUpdate(
+            workInProgress,
+            errorInfo,
+            renderExpirationTime
+          );
+          enqueueCapturedUpdate(workInProgress, _update, renderExpirationTime);
+          return;
+        }
+        break;
+      default:
+        break;
+    }
+    workInProgress = workInProgress.return;
+  } while (workInProgress !== null);
+}
 
-  function computeInteractiveExpiration(currentTime) {
-    var expirationMs = void 0;
-    // We intentionally set a higher expiration time for interactive updates in
-    // dev than in production.
-    // If the main thread is being blocked so long that you hit the expiration,
-    // it's a problem that could be solved with better scheduling.
-    // People will be more likely to notice this and fix it with the long
-    // expiration time in development.
-    // In production we opt for better UX at the risk of masking scheduling
-    // problems, by expiring fast.
-    {
-      // Should complete within ~500ms. 600ms max.
-      expirationMs = 500;
+function unwindWork(workInProgress, renderExpirationTime) {
+  if (enableProfilerTimer) {
+    if (workInProgress.mode & ProfileMode) {
+      recordElapsedActualRenderTime(workInProgress);
     }
-    var bucketSizeMs = 100;
-    return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
   }
 
-  // Creates a unique async expiration time.
-  function computeUniqueAsyncExpiration() {
-    var currentTime = recalculateCurrentTime();
-    var result = computeAsyncExpiration(currentTime);
-    if (result <= lastUniqueAsyncExpiration) {
-      // Since we assume the current time monotonically increases, we only hit
-      // this branch when computeUniqueAsyncExpiration is fired multiple times
-      // within a 200ms window (or whatever the async bucket size is).
-      result = lastUniqueAsyncExpiration + 1;
-    }
-    lastUniqueAsyncExpiration = result;
-    return lastUniqueAsyncExpiration;
-  }
-
-  function computeExpirationForFiber(currentTime, fiber) {
-    var expirationTime = void 0;
-    if (expirationContext !== NoWork) {
-      // An explicit expiration context was set;
-      expirationTime = expirationContext;
-    } else if (isWorking) {
-      if (isCommitting) {
-        // Updates that occur during the commit phase should have sync priority
-        // by default.
-        expirationTime = Sync;
-      } else {
-        // Updates during the render phase should expire at the same time as
-        // the work that is being rendered.
-        expirationTime = nextRenderExpirationTime;
+  switch (workInProgress.tag) {
+    case ClassComponent: {
+      popContextProvider(workInProgress);
+      var effectTag = workInProgress.effectTag;
+      if (effectTag & ShouldCapture) {
+        workInProgress.effectTag = (effectTag & ~ShouldCapture) | DidCapture;
+        return workInProgress;
       }
-    } else {
-      // No explicit expiration context was set, and we're not currently
-      // performing work. Calculate a new expiration time.
-      if (fiber.mode & AsyncMode) {
-        if (isBatchingInteractiveUpdates) {
-          // This is an interactive update
-          expirationTime = computeInteractiveExpiration(currentTime);
-        } else {
-          // This is an async update
-          expirationTime = computeAsyncExpiration(currentTime);
-        }
-      } else {
-        // This is a sync update
-        expirationTime = Sync;
+      return null;
+    }
+    case HostRoot: {
+      popHostContainer(workInProgress);
+      popTopLevelContextObject(workInProgress);
+      var _effectTag = workInProgress.effectTag;
+      if (_effectTag & ShouldCapture) {
+        workInProgress.effectTag = (_effectTag & ~ShouldCapture) | DidCapture;
+        return workInProgress;
       }
+      return null;
     }
-    if (isBatchingInteractiveUpdates) {
-      // This is an interactive update. Keep track of the lowest pending
-      // interactive expiration time. This allows us to synchronously flush
-      // all interactive updates when needed.
-      if (
-        lowestPendingInteractiveExpirationTime === NoWork ||
-        expirationTime > lowestPendingInteractiveExpirationTime
-      ) {
-        lowestPendingInteractiveExpirationTime = expirationTime;
+    case HostComponent: {
+      popHostContext(workInProgress);
+      return null;
+    }
+    case TimeoutComponent: {
+      var _effectTag2 = workInProgress.effectTag;
+      if (_effectTag2 & ShouldCapture) {
+        workInProgress.effectTag = (_effectTag2 & ~ShouldCapture) | DidCapture;
+        return workInProgress;
       }
+      return null;
     }
-    return expirationTime;
+    case HostPortal:
+      popHostContainer(workInProgress);
+      return null;
+    case ContextProvider:
+      popProvider(workInProgress);
+      return null;
+    default:
+      return null;
   }
+}
 
-  // TODO: Rename this to scheduleTimeout or something
-  function suspendRoot(root, thenable, timeoutMs, suspendedTime) {
-    // Schedule the timeout.
-    if (timeoutMs >= 0 && nextLatestTimeoutMs < timeoutMs) {
-      nextLatestTimeoutMs = timeoutMs;
+function unwindInterruptedWork(interruptedWork) {
+  if (enableProfilerTimer) {
+    if (interruptedWork.mode & ProfileMode) {
+      // Resume in case we're picking up on work that was paused.
+      resumeActualRenderTimerIfPaused();
+      recordElapsedActualRenderTime(interruptedWork);
     }
   }
 
-  function retrySuspendedRoot(root, suspendedTime) {
-    markPingedPriorityLevel(root, suspendedTime);
-    var retryTime = findNextPendingPriorityLevel(root);
-    if (retryTime !== NoWork) {
-      requestRetry(root, retryTime);
+  switch (interruptedWork.tag) {
+    case ClassComponent: {
+      popContextProvider(interruptedWork);
+      break;
+    }
+    case HostRoot: {
+      popHostContainer(interruptedWork);
+      popTopLevelContextObject(interruptedWork);
+      break;
+    }
+    case HostComponent: {
+      popHostContext(interruptedWork);
+      break;
     }
+    case HostPortal:
+      popHostContainer(interruptedWork);
+      break;
+    case ContextProvider:
+      popProvider(interruptedWork);
+      break;
+    default:
+      break;
   }
+}
+
+var invokeGuardedCallback$2 = ReactErrorUtils.invokeGuardedCallback;
+var hasCaughtError = ReactErrorUtils.hasCaughtError;
+var clearCaughtError = ReactErrorUtils.clearCaughtError;
 
-  function scheduleWork(fiber, expirationTime) {
-    recordScheduleUpdate();
+var didWarnAboutStateTransition = void 0;
+var didWarnSetStateChildContext = void 0;
+var warnAboutUpdateOnUnmounted = void 0;
+var warnAboutInvalidUpdates = void 0;
 
-    {
-      if (fiber.tag === ClassComponent) {
-        var instance = fiber.stateNode;
-        warnAboutInvalidUpdates(instance);
-      }
+{
+  didWarnAboutStateTransition = false;
+  didWarnSetStateChildContext = false;
+  var didWarnStateUpdateForUnmountedComponent = {};
+
+  warnAboutUpdateOnUnmounted = function(fiber) {
+    // We show the whole stack but dedupe on the top component's name because
+    // the problematic code almost always lies inside that component.
+    var componentName = getComponentName(fiber) || "ReactClass";
+    if (didWarnStateUpdateForUnmountedComponent[componentName]) {
+      return;
     }
+    warning(
+      false,
+      "Can't call setState (or forceUpdate) on an unmounted component. This " +
+        "is a no-op, but it indicates a memory leak in your application. To " +
+        "fix, cancel all subscriptions and asynchronous tasks in the " +
+        "componentWillUnmount method.%s",
+      getStackAddendumByWorkInProgressFiber(fiber)
+    );
+    didWarnStateUpdateForUnmountedComponent[componentName] = true;
+  };
 
-    var node = fiber;
-    while (node !== null) {
-      // Walk the parent path to the root and update each node's
-      // expiration time.
-      if (
-        node.expirationTime === NoWork ||
-        node.expirationTime > expirationTime
-      ) {
-        node.expirationTime = expirationTime;
-      }
-      if (node.alternate !== null) {
-        if (
-          node.alternate.expirationTime === NoWork ||
-          node.alternate.expirationTime > expirationTime
-        ) {
-          node.alternate.expirationTime = expirationTime;
+  warnAboutInvalidUpdates = function(instance) {
+    switch (ReactDebugCurrentFiber.phase) {
+      case "getChildContext":
+        if (didWarnSetStateChildContext) {
+          return;
         }
-      }
-      if (node.return === null) {
-        if (node.tag === HostRoot) {
-          var root = node.stateNode;
-          if (
-            !isWorking &&
-            nextRenderExpirationTime !== NoWork &&
-            expirationTime < nextRenderExpirationTime
-          ) {
-            // This is an interruption. (Used for performance tracking.)
-            interruptedBy = fiber;
-            resetStack();
-          }
-          markPendingPriorityLevel(root, expirationTime);
-          var nextExpirationTimeToWorkOn = findNextPendingPriorityLevel(root);
-          if (
-            // If we're in the render phase, we don't need to schedule this root
-            // for an update, because we'll do it before we exit...
-            !isWorking ||
-            isCommitting ||
-            // ...unless this is a different root than the one we're rendering.
-            nextRoot !== root
-          ) {
-            requestWork(root, nextExpirationTimeToWorkOn);
-          }
-          if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
-            invariant(
-              false,
-              "Maximum update depth exceeded. This can happen when a " +
-                "component repeatedly calls setState inside " +
-                "componentWillUpdate or componentDidUpdate. React limits " +
-                "the number of nested updates to prevent infinite loops."
-            );
-          }
-        } else {
-          {
-            if (fiber.tag === ClassComponent) {
-              warnAboutUpdateOnUnmounted(fiber);
-            }
-          }
+        warning(
+          false,
+          "setState(...): Cannot call setState() inside getChildContext()"
+        );
+        didWarnSetStateChildContext = true;
+        break;
+      case "render":
+        if (didWarnAboutStateTransition) {
           return;
         }
-      }
-      node = node.return;
-    }
-  }
-
-  function recalculateCurrentTime() {
-    // Subtract initial time so it fits inside 32bits
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
-    return mostRecentCurrentTime;
-  }
-
-  function deferredUpdates(fn) {
-    var previousExpirationContext = expirationContext;
-    var currentTime = recalculateCurrentTime();
-    expirationContext = computeAsyncExpiration(currentTime);
-    try {
-      return fn();
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = Sync;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
+        warning(
+          false,
+          "Cannot update during an existing state transition (such as within " +
+            "`render` or another component's constructor). Render methods should " +
+            "be a pure function of props and state; constructor side-effects are " +
+            "an anti-pattern, but can be moved to `componentWillMount`."
+        );
+        didWarnAboutStateTransition = true;
+        break;
     }
-  }
-
-  // TODO: Everything below this is written as if it has been lifted to the
-  // renderers. I'll do this in a follow-up.
+  };
+}
 
-  // Linked-list of roots
-  var firstScheduledRoot = null;
-  var lastScheduledRoot = null;
+// Represents the current time in ms.
+var originalStartTimeMs = now();
+var mostRecentCurrentTime = msToExpirationTime(0);
+var mostRecentCurrentTimeMs = originalStartTimeMs;
 
-  var callbackExpirationTime = NoWork;
-  var callbackID = -1;
-  var isRendering = false;
-  var nextFlushedRoot = null;
-  var nextFlushedExpirationTime = NoWork;
-  var lowestPendingInteractiveExpirationTime = NoWork;
-  var deadlineDidExpire = false;
-  var hasUnhandledError = false;
-  var unhandledError = null;
-  var deadline = null;
+// Used to ensure computeUniqueAsyncExpiration is monotonically increases.
+var lastUniqueAsyncExpiration = 0;
 
-  var isBatchingUpdates = false;
-  var isUnbatchingUpdates = false;
-  var isBatchingInteractiveUpdates = false;
+// Represents the expiration time that incoming updates should use. (If this
+// is NoWork, use the default strategy: async updates in async mode, sync
+// updates in sync mode.)
+var expirationContext = NoWork;
 
-  var completedBatches = null;
+var isWorking = false;
 
-  // Use these to prevent an infinite loop of nested updates
-  var NESTED_UPDATE_LIMIT = 1000;
-  var nestedUpdateCount = 0;
+// The next work in progress fiber that we're currently working on.
+var nextUnitOfWork = null;
+var nextRoot = null;
+// The time at which we're currently rendering work.
+var nextRenderExpirationTime = NoWork;
+var nextLatestTimeoutMs = -1;
+var nextRenderDidError = false;
 
-  var timeHeuristicForUnitOfWork = 1;
+// The next fiber with an effect that we're currently committing.
+var nextEffect = null;
 
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (callbackExpirationTime !== NoWork) {
-      // A callback is already scheduled. Check its expiration time (timeout).
-      if (expirationTime > callbackExpirationTime) {
-        // Existing callback has sufficient timeout. Exit.
-        return;
-      } else {
-        // Existing callback has insufficient timeout. Cancel and schedule a
-        // new one.
-        cancelDeferredCallback(callbackID);
-      }
-      // The request callback timer is already running. Don't start a new one.
-    } else {
-      startRequestCallbackTimer();
-    }
+var isCommitting$1 = false;
 
-    // Compute a timeout for the given expiration time.
-    var currentMs = now() - originalStartTimeMs;
-    var expirationMs = expirationTimeToMs(expirationTime);
-    var timeout = expirationMs - currentMs;
+var legacyErrorBoundariesThatAlreadyFailed = null;
 
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: timeout
-    });
-  }
+// Used for performance tracking.
+var interruptedBy = null;
 
-  function requestRetry(root, expirationTime) {
+var stashedWorkInProgressProperties = void 0;
+var replayUnitOfWork = void 0;
+var isReplayingFailedUnitOfWork = void 0;
+var originalReplayError = void 0;
+var rethrowOriginalError = void 0;
+if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+  stashedWorkInProgressProperties = null;
+  isReplayingFailedUnitOfWork = false;
+  originalReplayError = null;
+  replayUnitOfWork = function(failedUnitOfWork, thrownValue, isYieldy) {
     if (
-      root.remainingExpirationTime === NoWork ||
-      root.remainingExpirationTime < expirationTime
+      thrownValue !== null &&
+      typeof thrownValue === "object" &&
+      typeof thrownValue.then === "function"
     ) {
-      // For a retry, only update the remaining expiration time if it has a
-      // *lower priority* than the existing value. This is because, on a retry,
-      // we should attempt to coalesce as much as possible.
-      requestWork(root, expirationTime);
-    }
-  }
-
-  // requestWork is called by the scheduler whenever a root receives an update.
-  // It's up to the renderer to call renderRoot at some point in the future.
-  function requestWork(root, expirationTime) {
-    addRootToSchedule(root, expirationTime);
-
-    if (isRendering) {
-      // Prevent reentrancy. Remaining work will be scheduled at the end of
-      // the currently rendering batch.
+      // Don't replay promises. Treat everything else like an error.
+      // TODO: Need to figure out a different strategy if/when we add
+      // support for catching other types.
       return;
     }
 
-    if (isBatchingUpdates) {
-      // Flush work at the end of the batch.
-      if (isUnbatchingUpdates) {
-        // ...unless we're inside unbatchedUpdates, in which case we should
-        // flush it now.
-        nextFlushedRoot = root;
-        nextFlushedExpirationTime = Sync;
-        performWorkOnRoot(root, Sync, false);
-      }
+    // Restore the original state of the work-in-progress
+    if (stashedWorkInProgressProperties === null) {
+      // This should never happen. Don't throw because this code is DEV-only.
+      warning(
+        false,
+        "Could not replay rendering after an error. This is likely a bug in React. " +
+          "Please file an issue."
+      );
       return;
     }
+    assignFiberPropertiesInDEV(
+      failedUnitOfWork,
+      stashedWorkInProgressProperties
+    );
 
-    // TODO: Get rid of Sync and use current time?
-    if (expirationTime === Sync) {
-      performSyncWork();
-    } else {
-      scheduleCallbackWithExpiration(expirationTime);
-    }
-  }
-
-  function addRootToSchedule(root, expirationTime) {
-    // Add the root to the schedule.
-    // Check if this root is already part of the schedule.
-    if (root.nextScheduledRoot === null) {
-      // This root is not already scheduled. Add it.
-      root.remainingExpirationTime = expirationTime;
-      if (lastScheduledRoot === null) {
-        firstScheduledRoot = lastScheduledRoot = root;
-        root.nextScheduledRoot = root;
-      } else {
-        lastScheduledRoot.nextScheduledRoot = root;
-        lastScheduledRoot = root;
-        lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-      }
-    } else {
-      // This root is already scheduled, but its priority may have increased.
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        remainingExpirationTime === NoWork ||
-        expirationTime < remainingExpirationTime
-      ) {
-        // Update the priority.
-        root.remainingExpirationTime = expirationTime;
-      }
+    switch (failedUnitOfWork.tag) {
+      case HostRoot:
+        popHostContainer(failedUnitOfWork);
+        popTopLevelContextObject(failedUnitOfWork);
+        break;
+      case HostComponent:
+        popHostContext(failedUnitOfWork);
+        break;
+      case ClassComponent:
+        popContextProvider(failedUnitOfWork);
+        break;
+      case HostPortal:
+        popHostContainer(failedUnitOfWork);
+        break;
+      case ContextProvider:
+        popProvider(failedUnitOfWork);
+        break;
     }
-  }
-
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = NoWork;
-    var highestPriorityRoot = null;
-    if (lastScheduledRoot !== null) {
-      var previousScheduledRoot = lastScheduledRoot;
-      var root = firstScheduledRoot;
-      while (root !== null) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (remainingExpirationTime === NoWork) {
-          // This root no longer has work. Remove it from the scheduler.
+    // Replay the begin phase.
+    isReplayingFailedUnitOfWork = true;
+    originalReplayError = thrownValue;
+    invokeGuardedCallback$2(null, workLoop, null, isYieldy);
+    isReplayingFailedUnitOfWork = false;
+    originalReplayError = null;
+    if (hasCaughtError()) {
+      clearCaughtError();
 
-          // TODO: This check is redudant, but Flow is confused by the branch
-          // below where we set lastScheduledRoot to null, even though we break
-          // from the loop right after.
-          invariant(
-            previousScheduledRoot !== null && lastScheduledRoot !== null,
-            "Should have a previous and last root. This error is likely " +
-              "caused by a bug in React. Please file an issue."
-          );
-          if (root === root.nextScheduledRoot) {
-            // This is the only root in the list.
-            root.nextScheduledRoot = null;
-            firstScheduledRoot = lastScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot) {
-            // This is the first root in the list.
-            var next = root.nextScheduledRoot;
-            firstScheduledRoot = next;
-            lastScheduledRoot.nextScheduledRoot = next;
-            root.nextScheduledRoot = null;
-          } else if (root === lastScheduledRoot) {
-            // This is the last root in the list.
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else {
-            previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
-            root.nextScheduledRoot = null;
-          }
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            highestPriorityWork === NoWork ||
-            remainingExpirationTime < highestPriorityWork
-          ) {
-            // Update the priority, if it's higher
-            highestPriorityWork = remainingExpirationTime;
-            highestPriorityRoot = root;
-          }
-          if (root === lastScheduledRoot) {
-            break;
-          }
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
+      if (enableProfilerTimer) {
+        if (failedUnitOfWork.mode & ProfileMode) {
+          recordElapsedActualRenderTime(failedUnitOfWork);
         }
+
+        // Stop "base" render timer again (after the re-thrown error).
+        stopBaseRenderTimerIfRunning();
       }
+    } else {
+      // If the begin phase did not fail the second time, set this pointer
+      // back to the original value.
+      nextUnitOfWork = failedUnitOfWork;
     }
+  };
+  rethrowOriginalError = function() {
+    throw originalReplayError;
+  };
+}
 
-    // If the next root is the same as the previous root, this is a nested
-    // update. To prevent an infinite loop, increment the nested update count.
-    var previousFlushedRoot = nextFlushedRoot;
-    if (
-      previousFlushedRoot !== null &&
-      previousFlushedRoot === highestPriorityRoot &&
-      highestPriorityWork === Sync
-    ) {
-      nestedUpdateCount++;
-    } else {
-      // Reset whenever we switch roots.
-      nestedUpdateCount = 0;
+function resetStack() {
+  if (nextUnitOfWork !== null) {
+    var interruptedWork = nextUnitOfWork.return;
+    while (interruptedWork !== null) {
+      unwindInterruptedWork(interruptedWork);
+      interruptedWork = interruptedWork.return;
     }
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
   }
 
-  function performAsyncWork(dl) {
-    performWork(NoWork, true, dl);
+  {
+    ReactStrictModeWarnings.discardPendingWarnings();
+    checkThatStackIsEmpty();
   }
 
-  function performSyncWork() {
-    performWork(Sync, false, null);
-  }
+  nextRoot = null;
+  nextRenderExpirationTime = NoWork;
+  nextLatestTimeoutMs = -1;
+  nextRenderDidError = false;
+  nextUnitOfWork = null;
+}
 
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
+function commitAllHostEffects() {
+  while (nextEffect !== null) {
+    {
+      ReactDebugCurrentFiber.setCurrentFiber(nextEffect);
+    }
+    recordEffect();
 
-    // Keep working on roots until there's no more work, or until the we reach
-    // the deadline.
-    findHighestPriorityRoot();
+    var effectTag = nextEffect.effectTag;
 
-    if (enableProfilerTimer) {
-      resumeActualRenderTimerIfPaused();
+    if (effectTag & ContentReset) {
+      commitResetTextContent(nextEffect);
     }
 
-    if (enableUserTimingAPI && deadline !== null) {
-      var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
-      var timeout = expirationTimeToMs(nextFlushedExpirationTime);
-      stopRequestCallbackTimer(didExpire, timeout);
+    if (effectTag & Ref) {
+      var current = nextEffect.alternate;
+      if (current !== null) {
+        commitDetachRef(current);
+      }
     }
 
-    if (isAsync) {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime)
-      ) {
-        recalculateCurrentTime();
-        performWorkOnRoot(
-          nextFlushedRoot,
-          nextFlushedExpirationTime,
-          !deadlineDidExpire
-        );
-        findHighestPriorityRoot();
+    // The following switch statement is only concerned about placement,
+    // updates, and deletions. To avoid needing to add a case for every
+    // possible bitmap value, we remove the secondary effects from the
+    // effect tag and switch on that value.
+    var primaryEffectTag = effectTag & (Placement | Update | Deletion);
+    switch (primaryEffectTag) {
+      case Placement: {
+        commitPlacement(nextEffect);
+        // Clear the "placement" from effect tag so that we know that this is inserted, before
+        // any life-cycles like componentDidMount gets called.
+        // TODO: findDOMNode doesn't rely on this any more but isMounted
+        // does and isMounted is deprecated anyway so we should be able
+        // to kill this.
+        nextEffect.effectTag &= ~Placement;
+        break;
       }
-    } else {
-      while (
-        nextFlushedRoot !== null &&
-        nextFlushedExpirationTime !== NoWork &&
-        (minExpirationTime === NoWork ||
-          minExpirationTime >= nextFlushedExpirationTime)
-      ) {
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
-        findHighestPriorityRoot();
+      case PlacementAndUpdate: {
+        // Placement
+        commitPlacement(nextEffect);
+        // Clear the "placement" from effect tag so that we know that this is inserted, before
+        // any life-cycles like componentDidMount gets called.
+        nextEffect.effectTag &= ~Placement;
+
+        // Update
+        var _current = nextEffect.alternate;
+        commitWork(_current, nextEffect);
+        break;
+      }
+      case Update: {
+        var _current2 = nextEffect.alternate;
+        commitWork(_current2, nextEffect);
+        break;
+      }
+      case Deletion: {
+        commitDeletion(nextEffect);
+        break;
       }
     }
+    nextEffect = nextEffect.nextEffect;
+  }
 
-    // We're done flushing work. Either we ran out of time in this callback,
-    // or there's no more work left with sufficient priority.
-
-    // If we're inside a callback, set this to false since we just completed it.
-    if (deadline !== null) {
-      callbackExpirationTime = NoWork;
-      callbackID = -1;
-    }
-    // If there's work left over, schedule a new callback.
-    if (nextFlushedExpirationTime !== NoWork) {
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
-    }
+  {
+    ReactDebugCurrentFiber.resetCurrentFiber();
+  }
+}
 
-    // Clean-up.
-    deadline = null;
-    deadlineDidExpire = false;
+function commitBeforeMutationLifecycles() {
+  while (nextEffect !== null) {
+    var effectTag = nextEffect.effectTag;
 
-    finishRendering();
-  }
+    if (effectTag & Snapshot) {
+      recordEffect();
+      var current = nextEffect.alternate;
+      commitBeforeMutationLifeCycles(current, nextEffect);
+    }
 
-  function flushRoot(root, expirationTime) {
-    invariant(
-      !isRendering,
-      "work.commit(): Cannot commit while already rendering. This likely " +
-        "means you attempted to commit from inside a lifecycle method."
-    );
-    // Perform work on root as if the given expiration time is the current time.
-    // This has the effect of synchronously flushing all work up to and
-    // including the given time.
-    nextFlushedRoot = root;
-    nextFlushedExpirationTime = expirationTime;
-    performWorkOnRoot(root, expirationTime, false);
-    // Flush any sync work that was scheduled by lifecycles
-    performSyncWork();
-    finishRendering();
+    // Don't cleanup effects yet;
+    // This will be done by commitAllLifeCycles()
+    nextEffect = nextEffect.nextEffect;
   }
+}
 
-  function finishRendering() {
-    nestedUpdateCount = 0;
+function commitAllLifeCycles(
+  finishedRoot,
+  currentTime,
+  committedExpirationTime
+) {
+  {
+    ReactStrictModeWarnings.flushPendingUnsafeLifecycleWarnings();
 
-    if (completedBatches !== null) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          if (!hasUnhandledError) {
-            hasUnhandledError = true;
-            unhandledError = error;
-          }
-        }
-      }
+    if (warnAboutDeprecatedLifecycles) {
+      ReactStrictModeWarnings.flushPendingDeprecationWarnings();
     }
 
-    if (hasUnhandledError) {
-      var error = unhandledError;
-      unhandledError = null;
-      hasUnhandledError = false;
-      throw error;
+    if (warnAboutLegacyContextAPI) {
+      ReactStrictModeWarnings.flushLegacyContextWarning();
     }
   }
+  while (nextEffect !== null) {
+    var effectTag = nextEffect.effectTag;
 
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused " +
-        "by a bug in React. Please file an issue."
-    );
-
-    isRendering = true;
+    if (effectTag & (Update | Callback)) {
+      recordEffect();
+      var current = nextEffect.alternate;
+      commitLifeCycles(
+        finishedRoot,
+        current,
+        nextEffect,
+        currentTime,
+        committedExpirationTime
+      );
+    }
 
-    // Check if this is async work or sync/expired work.
-    if (!isAsync) {
-      // Flush sync work.
-      var finishedWork = root.finishedWork;
-      if (finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot(root, finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        finishedWork = renderRoot(root, expirationTime, false);
-        if (finishedWork !== null) {
-          // We've completed the root. Commit it.
-          completeRoot(root, finishedWork, expirationTime);
-        }
-      }
-    } else {
-      // Flush async work.
-      var _finishedWork = root.finishedWork;
-      if (_finishedWork !== null) {
-        // This root is already complete. We can commit it.
-        completeRoot(root, _finishedWork, expirationTime);
-      } else {
-        root.finishedWork = null;
-        _finishedWork = renderRoot(root, expirationTime, true);
-        if (_finishedWork !== null) {
-          // We've completed the root. Check the deadline one more time
-          // before committing.
-          if (!shouldYield()) {
-            // Still time left. Commit the root.
-            completeRoot(root, _finishedWork, expirationTime);
-          } else {
-            // There's no time left. Mark this root as complete. We'll come
-            // back and commit it later.
-            root.finishedWork = _finishedWork;
-
-            if (enableProfilerTimer) {
-              // If we didn't finish, pause the "actual" render timer.
-              // We'll restart it when we resume work.
-              pauseActualRenderTimerIfRunning();
-            }
-          }
-        }
-      }
+    if (effectTag & Ref) {
+      recordEffect();
+      commitAttachRef(nextEffect);
     }
 
-    isRendering = false;
+    var next = nextEffect.nextEffect;
+    // Ensure that we clean these up so that we don't accidentally keep them.
+    // I'm not actually sure this matters because we can't reset firstEffect
+    // and lastEffect since they're on every node, not just the effectful
+    // ones. So we have to clean everything as we reuse nodes anyway.
+    nextEffect.nextEffect = null;
+    // Ensure that we reset the effectTag here so that we can rely on effect
+    // tags to reason about the current life-cycle.
+    nextEffect = next;
   }
+}
 
-  function completeRoot(root, finishedWork, expirationTime) {
-    // Check if there's a batch that matches this expiration time.
-    var firstBatch = root.firstBatch;
-    if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
-      if (completedBatches === null) {
-        completedBatches = [firstBatch];
-      } else {
-        completedBatches.push(firstBatch);
-      }
-      if (firstBatch._defer) {
-        // This root is blocked from committing by a batch. Unschedule it until
-        // we receive another update.
-        root.finishedWork = finishedWork;
-        root.remainingExpirationTime = NoWork;
-        return;
-      }
-    }
+function isAlreadyFailedLegacyErrorBoundary(instance) {
+  return (
+    legacyErrorBoundariesThatAlreadyFailed !== null &&
+    legacyErrorBoundariesThatAlreadyFailed.has(instance)
+  );
+}
 
-    // Commit the root.
-    root.finishedWork = null;
-    root.remainingExpirationTime = commitRoot(finishedWork);
+function markLegacyErrorBoundaryAsFailed(instance) {
+  if (legacyErrorBoundariesThatAlreadyFailed === null) {
+    legacyErrorBoundariesThatAlreadyFailed = new Set([instance]);
+  } else {
+    legacyErrorBoundariesThatAlreadyFailed.add(instance);
   }
+}
 
-  // When working on async work, the reconciler asks the renderer if it should
-  // yield execution. For DOM, we implement this with requestIdleCallback.
-  function shouldYield() {
-    if (deadline === null) {
-      return false;
-    }
-    if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
-      // Disregard deadline.didTimeout. Only expired work should be flushed
-      // during a timeout. This path is only hit for non-expired work.
-      return false;
-    }
-    deadlineDidExpire = true;
-    return true;
-  }
+function commitRoot(root, finishedWork) {
+  isWorking = true;
+  isCommitting$1 = true;
+  startCommitTimer();
 
-  function onUncaughtError(error) {
-    invariant(
-      nextFlushedRoot !== null,
-      "Should be working on a root. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-    // Unschedule this root so we don't work on it again until there's
-    // another update.
-    nextFlushedRoot.remainingExpirationTime = NoWork;
-    if (!hasUnhandledError) {
-      hasUnhandledError = true;
-      unhandledError = error;
+  invariant(
+    root.current !== finishedWork,
+    "Cannot commit the same tree as before. This is probably a bug " +
+      "related to the return field. This error is likely caused by a bug " +
+      "in React. Please file an issue."
+  );
+  var committedExpirationTime = root.pendingCommitExpirationTime;
+  invariant(
+    committedExpirationTime !== NoWork,
+    "Cannot commit an incomplete root. This error is likely caused by a " +
+      "bug in React. Please file an issue."
+  );
+  root.pendingCommitExpirationTime = NoWork;
+
+  // Update the pending priority levels to account for the work that we are
+  // about to commit. This needs to happen before calling the lifecycles, since
+  // they may schedule additional updates.
+  var earliestRemainingTime = finishedWork.expirationTime;
+  var currentTime = recalculateCurrentTime();
+  markCommittedPriorityLevels(root, currentTime, earliestRemainingTime);
+
+  // Reset this to null before calling lifecycles
+  ReactCurrentOwner.current = null;
+
+  var firstEffect = void 0;
+  if (finishedWork.effectTag > PerformedWork) {
+    // A fiber's effect list consists only of its children, not itself. So if
+    // the root has an effect, we need to add it to the end of the list. The
+    // resulting list is the set that would belong to the root's parent, if
+    // it had one; that is, all the effects in the tree including the root.
+    if (finishedWork.lastEffect !== null) {
+      finishedWork.lastEffect.nextEffect = finishedWork;
+      firstEffect = finishedWork.firstEffect;
+    } else {
+      firstEffect = finishedWork;
     }
+  } else {
+    // There is no effect on the root.
+    firstEffect = finishedWork.firstEffect;
   }
 
-  function onBlock(remainingExpirationTime) {
-    invariant(
-      nextFlushedRoot !== null,
-      "Should be working on a root. This error is likely caused by a bug in " +
-        "React. Please file an issue."
-    );
-    // This root was blocked. Unschedule it until there's another update.
-    nextFlushedRoot.remainingExpirationTime = remainingExpirationTime;
-  }
+  prepareForCommit(root.containerInfo);
 
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function batchedUpdates(fn, a) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return fn(a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
+  // Invoke instances of getSnapshotBeforeUpdate before mutation.
+  nextEffect = firstEffect;
+  startCommitSnapshotEffectsTimer();
+  while (nextEffect !== null) {
+    var didError = false;
+    var error = void 0;
+    {
+      invokeGuardedCallback$2(null, commitBeforeMutationLifecycles, null);
+      if (hasCaughtError()) {
+        didError = true;
+        error = clearCaughtError();
       }
     }
-  }
-
-  // TODO: Batching should be implemented at the renderer level, not inside
-  // the reconciler.
-  function unbatchedUpdates(fn, a) {
-    if (isBatchingUpdates && !isUnbatchingUpdates) {
-      isUnbatchingUpdates = true;
-      try {
-        return fn(a);
-      } finally {
-        isUnbatchingUpdates = false;
+    if (didError) {
+      invariant(
+        nextEffect !== null,
+        "Should have next effect. This error is likely caused by a bug " +
+          "in React. Please file an issue."
+      );
+      captureCommitPhaseError(nextEffect, error);
+      // Clean-up
+      if (nextEffect !== null) {
+        nextEffect = nextEffect.nextEffect;
       }
     }
-    return fn(a);
   }
+  stopCommitSnapshotEffectsTimer();
 
-  // TODO: Batching should be implemented at the renderer level, not within
-  // the reconciler.
-  function flushSync(fn, a) {
-    invariant(
-      !isRendering,
-      "flushSync was called from inside a lifecycle method. It cannot be " +
-        "called when React is already rendering."
-    );
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      return syncUpdates(fn, a);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      performSyncWork();
+  if (enableProfilerTimer) {
+    // Mark the current commit time to be shared by all Profilers in this batch.
+    // This enables them to be grouped later.
+    recordCommitTime();
+  }
+
+  // Commit all the side-effects within a tree. We'll do this in two passes.
+  // The first pass performs all the host insertions, updates, deletions and
+  // ref unmounts.
+  nextEffect = firstEffect;
+  startCommitHostEffectsTimer();
+  while (nextEffect !== null) {
+    var _didError = false;
+    var _error = void 0;
+    {
+      invokeGuardedCallback$2(null, commitAllHostEffects, null);
+      if (hasCaughtError()) {
+        _didError = true;
+        _error = clearCaughtError();
+      }
+    }
+    if (_didError) {
+      invariant(
+        nextEffect !== null,
+        "Should have next effect. This error is likely caused by a bug " +
+          "in React. Please file an issue."
+      );
+      captureCommitPhaseError(nextEffect, _error);
+      // Clean-up
+      if (nextEffect !== null) {
+        nextEffect = nextEffect.nextEffect;
+      }
     }
   }
+  stopCommitHostEffectsTimer();
+
+  resetAfterCommit(root.containerInfo);
 
-  function interactiveUpdates(fn, a, b) {
-    if (isBatchingInteractiveUpdates) {
-      return fn(a, b);
+  // The work-in-progress tree is now the current tree. This must come after
+  // the first pass of the commit phase, so that the previous tree is still
+  // current during componentWillUnmount, but before the second pass, so that
+  // the finished work is current during componentDidMount/Update.
+  root.current = finishedWork;
+
+  // In the second pass we'll perform all life-cycles and ref callbacks.
+  // Life-cycles happen as a separate pass so that all placements, updates,
+  // and deletions in the entire tree have already been invoked.
+  // This pass also triggers any renderer-specific initial effects.
+  nextEffect = firstEffect;
+  startCommitLifeCyclesTimer();
+  while (nextEffect !== null) {
+    var _didError2 = false;
+    var _error2 = void 0;
+    {
+      invokeGuardedCallback$2(
+        null,
+        commitAllLifeCycles,
+        null,
+        root,
+        currentTime,
+        committedExpirationTime
+      );
+      if (hasCaughtError()) {
+        _didError2 = true;
+        _error2 = clearCaughtError();
+      }
     }
-    // If there are any pending interactive updates, synchronously flush them.
-    // This needs to happen before we read any handlers, because the effect of
-    // the previous event may influence which handlers are called during
-    // this event.
-    if (
-      !isBatchingUpdates &&
-      !isRendering &&
-      lowestPendingInteractiveExpirationTime !== NoWork
-    ) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
-    }
-    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingInteractiveUpdates = true;
-    isBatchingUpdates = true;
-    try {
-      return fn(a, b);
-    } finally {
-      isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performSyncWork();
+    if (_didError2) {
+      invariant(
+        nextEffect !== null,
+        "Should have next effect. This error is likely caused by a bug " +
+          "in React. Please file an issue."
+      );
+      captureCommitPhaseError(nextEffect, _error2);
+      if (nextEffect !== null) {
+        nextEffect = nextEffect.nextEffect;
       }
     }
   }
 
-  function flushInteractiveUpdates() {
-    if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
-      // Synchronously flush pending interactive updates.
-      performWork(lowestPendingInteractiveExpirationTime, false, null);
-      lowestPendingInteractiveExpirationTime = NoWork;
+  if (enableProfilerTimer) {
+    {
+      checkActualRenderTimeStackEmpty();
     }
+    resetActualRenderTimer();
   }
 
-  function flushControlled(fn) {
-    var previousIsBatchingUpdates = isBatchingUpdates;
-    isBatchingUpdates = true;
-    try {
-      syncUpdates(fn);
-    } finally {
-      isBatchingUpdates = previousIsBatchingUpdates;
-      if (!isBatchingUpdates && !isRendering) {
-        performWork(Sync, false, null);
-      }
-    }
+  isCommitting$1 = false;
+  isWorking = false;
+  stopCommitLifeCyclesTimer();
+  stopCommitTimer();
+  if (typeof onCommitRoot === "function") {
+    onCommitRoot(finishedWork.stateNode);
+  }
+  if (true && ReactFiberInstrumentation_1.debugTool) {
+    ReactFiberInstrumentation_1.debugTool.onCommitWork(finishedWork);
   }
 
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: flushRoot,
-    batchedUpdates: batchedUpdates,
-    unbatchedUpdates: unbatchedUpdates,
-    flushSync: flushSync,
-    flushControlled: flushControlled,
-    deferredUpdates: deferredUpdates,
-    syncUpdates: syncUpdates,
-    interactiveUpdates: interactiveUpdates,
-    flushInteractiveUpdates: flushInteractiveUpdates,
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
-    legacyContext: legacyContext
-  };
-};
-
-var didWarnAboutNestedUpdates = void 0;
-
-{
-  didWarnAboutNestedUpdates = false;
+  var expirationTime = root.expirationTime;
+  if (expirationTime === NoWork) {
+    // If there's no remaining work, we can clear the set of already failed
+    // error boundaries.
+    legacyErrorBoundariesThatAlreadyFailed = null;
+  }
+  onCommit(root, expirationTime);
 }
 
-// 0 is PROD, 1 is DEV.
-// Might add PROFILE later.
+function resetExpirationTime(workInProgress, renderTime) {
+  if (renderTime !== Never && workInProgress.expirationTime === Never) {
+    // The children of this component are hidden. Don't bubble their
+    // expiration times.
+    return;
+  }
 
-var ReactFiberReconciler$1 = function(config) {
-  var getPublicInstance = config.getPublicInstance;
-
-  var _ReactFiberScheduler = ReactFiberScheduler(config),
-    computeUniqueAsyncExpiration =
-      _ReactFiberScheduler.computeUniqueAsyncExpiration,
-    recalculateCurrentTime = _ReactFiberScheduler.recalculateCurrentTime,
-    computeExpirationForFiber = _ReactFiberScheduler.computeExpirationForFiber,
-    scheduleWork = _ReactFiberScheduler.scheduleWork,
-    requestWork = _ReactFiberScheduler.requestWork,
-    flushRoot = _ReactFiberScheduler.flushRoot,
-    batchedUpdates = _ReactFiberScheduler.batchedUpdates,
-    unbatchedUpdates = _ReactFiberScheduler.unbatchedUpdates,
-    flushSync = _ReactFiberScheduler.flushSync,
-    flushControlled = _ReactFiberScheduler.flushControlled,
-    deferredUpdates = _ReactFiberScheduler.deferredUpdates,
-    syncUpdates = _ReactFiberScheduler.syncUpdates,
-    interactiveUpdates = _ReactFiberScheduler.interactiveUpdates,
-    flushInteractiveUpdates = _ReactFiberScheduler.flushInteractiveUpdates,
-    legacyContext = _ReactFiberScheduler.legacyContext;
-
-  var findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
-
-  function getContextForSubtree(parentComponent) {
-    if (!parentComponent) {
-      return emptyObject;
-    }
-
-    var fiber = get$1(parentComponent);
-    var parentContext = findCurrentUnmaskedContext(fiber);
-    return isContextProvider(fiber)
-      ? processChildContext(fiber, parentContext)
-      : parentContext;
-  }
-
-  function scheduleRootUpdate(current, element, expirationTime, callback) {
-    {
-      if (
-        ReactDebugCurrentFiber.phase === "render" &&
-        ReactDebugCurrentFiber.current !== null &&
-        !didWarnAboutNestedUpdates
-      ) {
-        didWarnAboutNestedUpdates = true;
-        warning(
-          false,
-          "Render methods should be a pure function of props and state; " +
-            "triggering nested component updates from render is not allowed. " +
-            "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
-            "Check the render method of %s.",
-          getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
-        );
+  // Check for pending updates.
+  var newExpirationTime = NoWork;
+  switch (workInProgress.tag) {
+    case HostRoot:
+    case ClassComponent: {
+      var updateQueue = workInProgress.updateQueue;
+      if (updateQueue !== null) {
+        newExpirationTime = updateQueue.expirationTime;
       }
     }
-
-    var update = createUpdate(expirationTime);
-    // Caution: React DevTools currently depends on this property
-    // being called "element".
-    update.payload = { element: element };
-
-    callback = callback === undefined ? null : callback;
-    if (callback !== null) {
-      !(typeof callback === "function")
-        ? warning(
-            false,
-            "render(...): Expected the last optional `callback` argument to be a " +
-              "function. Instead received: %s.",
-            callback
-          )
-        : void 0;
-      update.callback = callback;
-    }
-    enqueueUpdate(current, update, expirationTime);
-
-    scheduleWork(current, expirationTime);
-    return expirationTime;
   }
 
-  function updateContainerAtExpirationTime(
-    element,
-    container,
-    parentComponent,
-    expirationTime,
-    callback
-  ) {
-    // TODO: If this is a nested container, this won't be the root.
-    var current = container.current;
+  // TODO: Calls need to visit stateNode
 
-    {
-      if (ReactFiberInstrumentation_1.debugTool) {
-        if (current.alternate === null) {
-          ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
-        } else if (element === null) {
-          ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
-        } else {
-          ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
-        }
+  // Bubble up the earliest expiration time.
+  // (And "base" render timers if that feature flag is enabled)
+  if (enableProfilerTimer && workInProgress.mode & ProfileMode) {
+    var treeBaseTime = workInProgress.selfBaseTime;
+    var child = workInProgress.child;
+    while (child !== null) {
+      treeBaseTime += child.treeBaseTime;
+      if (
+        child.expirationTime !== NoWork &&
+        (newExpirationTime === NoWork ||
+          newExpirationTime > child.expirationTime)
+      ) {
+        newExpirationTime = child.expirationTime;
       }
+      child = child.sibling;
     }
-
-    var context = getContextForSubtree(parentComponent);
-    if (container.context === null) {
-      container.context = context;
-    } else {
-      container.pendingContext = context;
-    }
-
-    return scheduleRootUpdate(current, element, expirationTime, callback);
-  }
-
-  function findHostInstance(component) {
-    var fiber = get$1(component);
-    if (fiber === undefined) {
-      if (typeof component.render === "function") {
-        invariant(false, "Unable to find node on an unmounted component.");
-      } else {
-        invariant(
-          false,
-          "Argument appears to not be a ReactComponent. Keys: %s",
-          Object.keys(component)
-        );
+    workInProgress.treeBaseTime = treeBaseTime;
+  } else {
+    var _child = workInProgress.child;
+    while (_child !== null) {
+      if (
+        _child.expirationTime !== NoWork &&
+        (newExpirationTime === NoWork ||
+          newExpirationTime > _child.expirationTime)
+      ) {
+        newExpirationTime = _child.expirationTime;
       }
+      _child = _child.sibling;
     }
-    var hostFiber = findCurrentHostFiber(fiber);
-    if (hostFiber === null) {
-      return null;
-    }
-    return hostFiber.stateNode;
   }
 
-  return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      return createFiberRoot(containerInfo, isAsync, hydrate);
-    },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current;
-      var currentTime = recalculateCurrentTime();
-      var expirationTime = computeExpirationForFiber(currentTime, current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        expirationTime,
-        callback
-      );
-    },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
-    ) {
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        expirationTime,
-        callback
-      );
-    },
-
-    flushRoot: flushRoot,
-
-    requestWork: requestWork,
+  workInProgress.expirationTime = newExpirationTime;
+}
 
-    computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+function completeUnitOfWork(workInProgress) {
+  // Attempt to complete the current unit of work, then move to the
+  // next sibling. If there are no more siblings, return to the
+  // parent fiber.
+  while (true) {
+    // The current, flushed, state of this fiber is the alternate.
+    // Ideally nothing should rely on this, but relying on it here
+    // means that we don't need an additional field on the work in
+    // progress.
+    var current = workInProgress.alternate;
+    {
+      ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+    }
 
-    batchedUpdates: batchedUpdates,
+    var returnFiber = workInProgress.return;
+    var siblingFiber = workInProgress.sibling;
 
-    unbatchedUpdates: unbatchedUpdates,
+    if ((workInProgress.effectTag & Incomplete) === NoEffect) {
+      // This fiber completed.
+      var next = completeWork(
+        current,
+        workInProgress,
+        nextRenderExpirationTime
+      );
+      stopWorkTimer(workInProgress);
+      resetExpirationTime(workInProgress, nextRenderExpirationTime);
+      {
+        ReactDebugCurrentFiber.resetCurrentFiber();
+      }
 
-    deferredUpdates: deferredUpdates,
+      if (next !== null) {
+        stopWorkTimer(workInProgress);
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+        }
+        // If completing this work spawned new work, do that next. We'll come
+        // back here again.
+        return next;
+      }
 
-    syncUpdates: syncUpdates,
+      if (
+        returnFiber !== null &&
+        // Do not append effects to parents if a sibling failed to complete
+        (returnFiber.effectTag & Incomplete) === NoEffect
+      ) {
+        // Append all the effects of the subtree and this fiber onto the effect
+        // list of the parent. The completion order of the children affects the
+        // side-effect order.
+        if (returnFiber.firstEffect === null) {
+          returnFiber.firstEffect = workInProgress.firstEffect;
+        }
+        if (workInProgress.lastEffect !== null) {
+          if (returnFiber.lastEffect !== null) {
+            returnFiber.lastEffect.nextEffect = workInProgress.firstEffect;
+          }
+          returnFiber.lastEffect = workInProgress.lastEffect;
+        }
 
-    interactiveUpdates: interactiveUpdates,
+        // If this fiber had side-effects, we append it AFTER the children's
+        // side-effects. We can perform certain side-effects earlier if
+        // needed, by doing multiple passes over the effect list. We don't want
+        // to schedule our own side-effect on our own list because if end up
+        // reusing children we'll schedule this effect onto itself since we're
+        // at the end.
+        var effectTag = workInProgress.effectTag;
+        // Skip both NoWork and PerformedWork tags when creating the effect list.
+        // PerformedWork effect is read by React DevTools but shouldn't be committed.
+        if (effectTag > PerformedWork) {
+          if (returnFiber.lastEffect !== null) {
+            returnFiber.lastEffect.nextEffect = workInProgress;
+          } else {
+            returnFiber.firstEffect = workInProgress;
+          }
+          returnFiber.lastEffect = workInProgress;
+        }
+      }
 
-    flushInteractiveUpdates: flushInteractiveUpdates,
+      if (true && ReactFiberInstrumentation_1.debugTool) {
+        ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+      }
 
-    flushControlled: flushControlled,
+      if (siblingFiber !== null) {
+        // If there is more work to do in this returnFiber, do that next.
+        return siblingFiber;
+      } else if (returnFiber !== null) {
+        // If there's no more work in this returnFiber. Complete the returnFiber.
+        workInProgress = returnFiber;
+        continue;
+      } else {
+        // We've reached the root.
+        return null;
+      }
+    } else {
+      // This fiber did not complete because something threw. Pop values off
+      // the stack without entering the complete phase. If this is a boundary,
+      // capture values if possible.
+      var _next = unwindWork(workInProgress, nextRenderExpirationTime);
+      // Because this fiber did not complete, don't reset its expiration time.
+      if (workInProgress.effectTag & DidCapture) {
+        // Restarting an error boundary
+        stopFailedWorkTimer(workInProgress);
+      } else {
+        stopWorkTimer(workInProgress);
+      }
 
-    flushSync: flushSync,
+      {
+        ReactDebugCurrentFiber.resetCurrentFiber();
+      }
 
-    getPublicRootInstance: function(container) {
-      var containerFiber = container.current;
-      if (!containerFiber.child) {
-        return null;
+      if (_next !== null) {
+        stopWorkTimer(workInProgress);
+        if (true && ReactFiberInstrumentation_1.debugTool) {
+          ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+        }
+        // If completing this work spawned new work, do that next. We'll come
+        // back here again.
+        // Since we're restarting, remove anything that is not a host effect
+        // from the effect tag.
+        _next.effectTag &= HostEffectMask;
+        return _next;
       }
-      switch (containerFiber.child.tag) {
-        case HostComponent:
-          return getPublicInstance(containerFiber.child.stateNode);
-        default:
-          return containerFiber.child.stateNode;
+
+      if (returnFiber !== null) {
+        // Mark the parent fiber as incomplete and clear its effect list.
+        returnFiber.firstEffect = returnFiber.lastEffect = null;
+        returnFiber.effectTag |= Incomplete;
       }
-    },
 
-    findHostInstance: findHostInstance,
+      if (true && ReactFiberInstrumentation_1.debugTool) {
+        ReactFiberInstrumentation_1.debugTool.onCompleteWork(workInProgress);
+      }
 
-    findHostInstanceWithNoPortals: function(fiber) {
-      var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
-      if (hostFiber === null) {
+      if (siblingFiber !== null) {
+        // If there is more work to do in this returnFiber, do that next.
+        return siblingFiber;
+      } else if (returnFiber !== null) {
+        // If there's no more work in this returnFiber. Complete the returnFiber.
+        workInProgress = returnFiber;
+        continue;
+      } else {
         return null;
       }
-      return hostFiber.stateNode;
-    },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            var hostFiber = findCurrentHostFiber(fiber);
-            if (hostFiber === null) {
-              return null;
-            }
-            return hostFiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            if (!findFiberByHostInstance) {
-              // Might not be implemented by the renderer.
-              return null;
-            }
-            return findFiberByHostInstance(instance);
-          }
-        })
-      );
     }
-  };
-};
+  }
 
-var ReactFiberReconciler$2 = Object.freeze({
-  default: ReactFiberReconciler$1
-});
+  // Without this explicit null return Flow complains of invalid return type
+  // TODO Remove the above while(true) loop
+  // eslint-disable-next-line no-unreachable
+  return null;
+}
 
-var ReactFiberReconciler$3 =
-  (ReactFiberReconciler$2 && ReactFiberReconciler$1) || ReactFiberReconciler$2;
+function performUnitOfWork(workInProgress) {
+  // The current, flushed, state of this fiber is the alternate.
+  // Ideally nothing should rely on this, but relying on it here
+  // means that we don't need an additional field on the work in
+  // progress.
+  var current = workInProgress.alternate;
 
-// TODO: bundle Flow types with the package.
+  // See if beginning this work spawns more work.
+  startWorkTimer(workInProgress);
+  {
+    ReactDebugCurrentFiber.setCurrentFiber(workInProgress);
+  }
 
-// TODO: decide on the top-level export form.
-// This is hacky but makes it work with both Rollup and Jest.
-var reactReconciler = ReactFiberReconciler$3.default
-  ? ReactFiberReconciler$3.default
-  : ReactFiberReconciler$3;
+  if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+    stashedWorkInProgressProperties = assignFiberPropertiesInDEV(
+      stashedWorkInProgressProperties,
+      workInProgress
+    );
+  }
 
-function createPortal(
-  children,
-  containerInfo,
-  // TODO: figure out the API for cross-renderer implementation.
-  implementation
-) {
-  var key =
-    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
+  var next = void 0;
+  if (enableProfilerTimer) {
+    if (workInProgress.mode & ProfileMode) {
+      startBaseRenderTimer();
+    }
 
-  return {
-    // This tag allow us to uniquely identify this as a React Portal
-    $$typeof: REACT_PORTAL_TYPE,
-    key: key == null ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
-}
+    next = beginWork(current, workInProgress, nextRenderExpirationTime);
 
-// TODO: this is special because it gets imported during build.
+    if (workInProgress.mode & ProfileMode) {
+      // Update "base" time if the render wasn't bailed out on.
+      recordElapsedBaseRenderTimeIfRunning(workInProgress);
+      stopBaseRenderTimerIfRunning();
+    }
+  } else {
+    next = beginWork(current, workInProgress, nextRenderExpirationTime);
+  }
 
-var ReactVersion = "16.3.2";
+  {
+    ReactDebugCurrentFiber.resetCurrentFiber();
+    if (isReplayingFailedUnitOfWork) {
+      // Currently replaying a failed unit of work. This should be unreachable,
+      // because the render phase is meant to be idempotent, and it should
+      // have thrown again. Since it didn't, rethrow the original error, so
+      // React's internal stack is not misaligned.
+      rethrowOriginalError();
+    }
+  }
+  if (true && ReactFiberInstrumentation_1.debugTool) {
+    ReactFiberInstrumentation_1.debugTool.onBeginWork(workInProgress);
+  }
 
-// Modules provided by RN:
-var emptyObject$1 = {};
+  if (next === null) {
+    // If this doesn't spawn new work, complete the current work.
+    next = completeUnitOfWork(workInProgress);
+  }
 
-/**
- * Create a payload that contains all the updates between two sets of props.
- *
- * These helpers are all encapsulated into a single module, because they use
- * mutation as a performance optimization which leads to subtle shared
- * dependencies between the code paths. To avoid this mutable state leaking
- * across modules, I've kept them isolated to this module.
- */
+  ReactCurrentOwner.current = null;
 
-// Tracks removed keys
-var removedKeys = null;
-var removedKeyCount = 0;
+  return next;
+}
 
-function defaultDiffer(prevProp, nextProp) {
-  if (typeof nextProp !== "object" || nextProp === null) {
-    // Scalars have already been checked for equality
-    return true;
+function workLoop(isYieldy) {
+  if (!isYieldy) {
+    // Flush work without yielding
+    while (nextUnitOfWork !== null) {
+      nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+    }
   } else {
-    // For objects and arrays, the default diffing algorithm is a deep compare
-    return deepDiffer(prevProp, nextProp);
+    // Flush asynchronous work until the deadline runs out of time.
+    while (nextUnitOfWork !== null && !shouldYield()) {
+      nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+    }
+
+    if (enableProfilerTimer) {
+      // If we didn't finish, pause the "actual" render timer.
+      // We'll restart it when we resume work.
+      pauseActualRenderTimerIfRunning();
+    }
   }
 }
 
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node)) {
-    var i = node.length;
-    while (i-- && removedKeyCount > 0) {
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
-    }
-  } else if (node && removedKeyCount > 0) {
-    var obj = node;
-    for (var propKey in removedKeys) {
-      if (!removedKeys[propKey]) {
-        continue;
-      }
-      var _nextProp = obj[propKey];
-      if (_nextProp === undefined) {
-        continue;
-      }
+function renderRoot(root, isYieldy) {
+  invariant(
+    !isWorking,
+    "renderRoot was called recursively. This error is likely caused " +
+      "by a bug in React. Please file an issue."
+  );
+  isWorking = true;
 
-      var attributeConfig = validAttributes[propKey];
-      if (!attributeConfig) {
-        continue; // not a valid native prop
-      }
+  var expirationTime = root.nextExpirationTimeToWorkOn;
 
-      if (typeof _nextProp === "function") {
-        _nextProp = true;
-      }
-      if (typeof _nextProp === "undefined") {
-        _nextProp = null;
+  // Check if we're starting from a fresh stack, or if we're resuming from
+  // previously yielded work.
+  if (
+    expirationTime !== nextRenderExpirationTime ||
+    root !== nextRoot ||
+    nextUnitOfWork === null
+  ) {
+    // Reset the stack and start working from the root.
+    resetStack();
+    nextRoot = root;
+    nextRenderExpirationTime = expirationTime;
+    nextLatestTimeoutMs = -1;
+    nextRenderDidError = false;
+    nextUnitOfWork = createWorkInProgress(
+      nextRoot.current,
+      null,
+      nextRenderExpirationTime
+    );
+    root.pendingCommitExpirationTime = NoWork;
+  }
+
+  var didFatal = false;
+
+  startWorkLoopTimer(nextUnitOfWork);
+
+  do {
+    try {
+      workLoop(isYieldy);
+    } catch (thrownValue) {
+      if (enableProfilerTimer) {
+        // Stop "base" render timer in the event of an error.
+        stopBaseRenderTimerIfRunning();
       }
 
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = _nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(_nextProp)
-            : _nextProp;
-        updatePayload[propKey] = nextValue;
+      if (nextUnitOfWork === null) {
+        // This is a fatal error.
+        didFatal = true;
+        onUncaughtError(thrownValue);
+      } else {
+        {
+          // Reset global debug state
+          // We assume this is defined in DEV
+          resetCurrentlyProcessingQueue();
+        }
+
+        var failedUnitOfWork = nextUnitOfWork;
+        if (true && replayFailedUnitOfWorkWithInvokeGuardedCallback) {
+          replayUnitOfWork(failedUnitOfWork, thrownValue, isYieldy);
+        }
+
+        // TODO: we already know this isn't true in some cases.
+        // At least this shows a nicer error message until we figure out the cause.
+        // https://github.com/facebook/react/issues/12449#issuecomment-386727431
+        invariant(
+          nextUnitOfWork !== null,
+          "Failed to replay rendering after an error. This " +
+            "is likely caused by a bug in React. Please file an issue " +
+            "with a reproducing case to help us find it."
+        );
+
+        var sourceFiber = nextUnitOfWork;
+        var returnFiber = sourceFiber.return;
+        if (returnFiber === null) {
+          // This is the root. The root could capture its own errors. However,
+          // we don't know if it errors before or after we pushed the host
+          // context. This information is needed to avoid a stack mismatch.
+          // Because we're not sure, treat this as a fatal error. We could track
+          // which phase it fails in, but doesn't seem worth it. At least
+          // for now.
+          didFatal = true;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        throwException(
+          root,
+          returnFiber,
+          sourceFiber,
+          thrownValue,
+          nextRenderExpirationTime,
+          mostRecentCurrentTimeMs
+        );
+        nextUnitOfWork = completeUnitOfWork(sourceFiber);
       }
-      removedKeys[propKey] = false;
-      removedKeyCount--;
     }
-  }
-}
-
-function diffNestedArrayProperty(
-  updatePayload,
-  prevArray,
-  nextArray,
-  validAttributes
-) {
-  var minLength =
-    prevArray.length < nextArray.length ? prevArray.length : nextArray.length;
-  var i = void 0;
-  for (i = 0; i < minLength; i++) {
-    // Diff any items in the array in the forward direction. Repeated keys
-    // will be overwritten by later values.
-    updatePayload = diffNestedProperty(
-      updatePayload,
-      prevArray[i],
-      nextArray[i],
-      validAttributes
-    );
-  }
-  for (; i < prevArray.length; i++) {
-    // Clear out all remaining properties.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevArray[i],
-      validAttributes
-    );
-  }
-  for (; i < nextArray.length; i++) {
-    // Add all remaining properties.
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextArray[i],
-      validAttributes
-    );
-  }
-  return updatePayload;
-}
+    break;
+  } while (true);
 
-function diffNestedProperty(
-  updatePayload,
-  prevProp,
-  nextProp,
-  validAttributes
-) {
-  if (!updatePayload && prevProp === nextProp) {
-    // If no properties have been added, then we can bail out quickly on object
-    // equality.
-    return updatePayload;
-  }
+  // We're done performing work. Time to clean up.
+  isWorking = false;
 
-  if (!prevProp || !nextProp) {
-    if (nextProp) {
-      return addNestedProperty(updatePayload, nextProp, validAttributes);
+  // Yield back to main thread.
+  if (didFatal) {
+    var didCompleteRoot = false;
+    stopWorkLoopTimer(interruptedBy, didCompleteRoot);
+    interruptedBy = null;
+    // There was a fatal error.
+    {
+      resetStackAfterFatalErrorInDev();
     }
-    if (prevProp) {
-      return clearNestedProperty(updatePayload, prevProp, validAttributes);
+    onFatal(root);
+  } else if (nextUnitOfWork === null) {
+    // We reached the root.
+    var rootWorkInProgress = root.current.alternate;
+    invariant(
+      rootWorkInProgress !== null,
+      "Finished root should have a work-in-progress. This error is likely " +
+        "caused by a bug in React. Please file an issue."
+    );
+    if ((rootWorkInProgress.effectTag & Incomplete) === NoEffect) {
+      var _didCompleteRoot = true;
+      stopWorkLoopTimer(interruptedBy, _didCompleteRoot);
+      interruptedBy = null;
+      // The root successfully completed.
+      onComplete(root, rootWorkInProgress, expirationTime);
+    } else {
+      // The root did not complete.
+      var _didCompleteRoot2 = false;
+      stopWorkLoopTimer(interruptedBy, _didCompleteRoot2);
+      interruptedBy = null;
+      markSuspendedPriorityLevel(root, expirationTime, nextRenderDidError);
+      var suspendedExpirationTime = expirationTime;
+      var newExpirationTime = root.expirationTime;
+      onSuspend(
+        root,
+        suspendedExpirationTime,
+        newExpirationTime,
+        nextLatestTimeoutMs
+      );
     }
-    return updatePayload;
+  } else {
+    var _didCompleteRoot3 = false;
+    stopWorkLoopTimer(interruptedBy, _didCompleteRoot3);
+    interruptedBy = null;
+    onYield(root);
   }
+}
 
-  if (!Array.isArray(prevProp) && !Array.isArray(nextProp)) {
-    // Both are leaves, we can diff the leaves.
-    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
-  }
+function dispatch(sourceFiber, value, expirationTime) {
+  invariant(
+    !isWorking || isCommitting$1,
+    "dispatch: Cannot dispatch during the render phase."
+  );
 
-  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
-    // Both are arrays, we can diff the arrays.
-    return diffNestedArrayProperty(
-      updatePayload,
-      prevProp,
-      nextProp,
-      validAttributes
-    );
+  var fiber = sourceFiber.return;
+  while (fiber !== null) {
+    switch (fiber.tag) {
+      case ClassComponent:
+        var ctor = fiber.type;
+        var instance = fiber.stateNode;
+        if (
+          typeof ctor.getDerivedStateFromCatch === "function" ||
+          (typeof instance.componentDidCatch === "function" &&
+            !isAlreadyFailedLegacyErrorBoundary(instance))
+        ) {
+          var errorInfo = createCapturedValue(value, sourceFiber);
+          var update = createClassErrorUpdate(fiber, errorInfo, expirationTime);
+          enqueueUpdate(fiber, update, expirationTime);
+          scheduleWork(fiber, expirationTime);
+          return;
+        }
+        break;
+      case HostRoot: {
+        var _errorInfo = createCapturedValue(value, sourceFiber);
+        var _update = createRootErrorUpdate(fiber, _errorInfo, expirationTime);
+        enqueueUpdate(fiber, _update, expirationTime);
+        scheduleWork(fiber, expirationTime);
+        return;
+      }
+    }
+    fiber = fiber.return;
   }
 
-  if (Array.isArray(prevProp)) {
-    return diffProperties(
-      updatePayload,
-      // $FlowFixMe - We know that this is always an object when the input is.
-      flattenStyle(prevProp),
-      // $FlowFixMe - We know that this isn't an array because of above flow.
-      nextProp,
-      validAttributes
+  if (sourceFiber.tag === HostRoot) {
+    // Error was thrown at the root. There is no parent, so the root
+    // itself should capture it.
+    var rootFiber = sourceFiber;
+    var _errorInfo2 = createCapturedValue(value, rootFiber);
+    var _update2 = createRootErrorUpdate(
+      rootFiber,
+      _errorInfo2,
+      expirationTime
     );
+    enqueueUpdate(rootFiber, _update2, expirationTime);
+    scheduleWork(rootFiber, expirationTime);
   }
+}
 
-  return diffProperties(
-    updatePayload,
-    prevProp,
-    // $FlowFixMe - We know that this is always an object when the input is.
-    flattenStyle(nextProp),
-    validAttributes
-  );
+function captureCommitPhaseError(fiber, error) {
+  return dispatch(fiber, error, Sync);
 }
 
-/**
- * addNestedProperty takes a single set of props and valid attribute
- * attribute configurations. It processes each prop and adds it to the
- * updatePayload.
- */
-function addNestedProperty(updatePayload, nextProp, validAttributes) {
-  if (!nextProp) {
-    return updatePayload;
-  }
+function computeAsyncExpiration(currentTime) {
+  // Given the current clock time, returns an expiration time. We use rounding
+  // to batch like updates together.
+  // Should complete within ~5000ms. 5250ms max.
+  var expirationMs = 5000;
+  var bucketSizeMs = 250;
+  return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+}
 
-  if (!Array.isArray(nextProp)) {
-    // Add each property of the leaf.
-    return addProperties(updatePayload, nextProp, validAttributes);
+function computeInteractiveExpiration(currentTime) {
+  var expirationMs = void 0;
+  // We intentionally set a higher expiration time for interactive updates in
+  // dev than in production.
+  // If the main thread is being blocked so long that you hit the expiration,
+  // it's a problem that could be solved with better scheduling.
+  // People will be more likely to notice this and fix it with the long
+  // expiration time in development.
+  // In production we opt for better UX at the risk of masking scheduling
+  // problems, by expiring fast.
+  {
+    // Should complete within ~500ms. 600ms max.
+    expirationMs = 500;
+  }
+  var bucketSizeMs = 100;
+  return computeExpirationBucket(currentTime, expirationMs, bucketSizeMs);
+}
+
+// Creates a unique async expiration time.
+function computeUniqueAsyncExpiration() {
+  var currentTime = recalculateCurrentTime();
+  var result = computeAsyncExpiration(currentTime);
+  if (result <= lastUniqueAsyncExpiration) {
+    // Since we assume the current time monotonically increases, we only hit
+    // this branch when computeUniqueAsyncExpiration is fired multiple times
+    // within a 200ms window (or whatever the async bucket size is).
+    result = lastUniqueAsyncExpiration + 1;
+  }
+  lastUniqueAsyncExpiration = result;
+  return lastUniqueAsyncExpiration;
+}
+
+function computeExpirationForFiber(currentTime, fiber) {
+  var expirationTime = void 0;
+  if (expirationContext !== NoWork) {
+    // An explicit expiration context was set;
+    expirationTime = expirationContext;
+  } else if (isWorking) {
+    if (isCommitting$1) {
+      // Updates that occur during the commit phase should have sync priority
+      // by default.
+      expirationTime = Sync;
+    } else {
+      // Updates during the render phase should expire at the same time as
+      // the work that is being rendered.
+      expirationTime = nextRenderExpirationTime;
+    }
+  } else {
+    // No explicit expiration context was set, and we're not currently
+    // performing work. Calculate a new expiration time.
+    if (fiber.mode & AsyncMode) {
+      if (isBatchingInteractiveUpdates) {
+        // This is an interactive update
+        expirationTime = computeInteractiveExpiration(currentTime);
+      } else {
+        // This is an async update
+        expirationTime = computeAsyncExpiration(currentTime);
+      }
+    } else {
+      // This is a sync update
+      expirationTime = Sync;
+    }
   }
-
-  for (var i = 0; i < nextProp.length; i++) {
-    // Add all the properties of the array.
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextProp[i],
-      validAttributes
-    );
+  if (isBatchingInteractiveUpdates) {
+    // This is an interactive update. Keep track of the lowest pending
+    // interactive expiration time. This allows us to synchronously flush
+    // all interactive updates when needed.
+    if (
+      lowestPendingInteractiveExpirationTime === NoWork ||
+      expirationTime > lowestPendingInteractiveExpirationTime
+    ) {
+      lowestPendingInteractiveExpirationTime = expirationTime;
+    }
   }
-
-  return updatePayload;
+  return expirationTime;
 }
 
-/**
- * clearNestedProperty takes a single set of props and valid attributes. It
- * adds a null sentinel to the updatePayload, for each prop key.
- */
-function clearNestedProperty(updatePayload, prevProp, validAttributes) {
-  if (!prevProp) {
-    return updatePayload;
+function markTimeout(root, thenable, timeoutMs, suspendedTime) {
+  // Schedule the timeout.
+  if (timeoutMs >= 0 && nextLatestTimeoutMs < timeoutMs) {
+    nextLatestTimeoutMs = timeoutMs;
   }
+}
 
-  if (!Array.isArray(prevProp)) {
-    // Add each property of the leaf.
-    return clearProperties(updatePayload, prevProp, validAttributes);
-  }
+function markError(root) {
+  nextRenderDidError = true;
+}
 
-  for (var i = 0; i < prevProp.length; i++) {
-    // Add all the properties of the array.
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevProp[i],
-      validAttributes
-    );
+function retrySuspendedRoot(root, suspendedTime) {
+  markPingedPriorityLevel(root, suspendedTime);
+  var retryTime = root.expirationTime;
+  if (retryTime !== NoWork) {
+    requestWork(root, retryTime);
   }
-  return updatePayload;
 }
 
-/**
- * diffProperties takes two sets of props and a set of valid attributes
- * and write to updatePayload the values that changed or were deleted.
- * If no updatePayload is provided, a new one is created and returned if
- * anything changed.
- */
-function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
-  var attributeConfig = void 0;
-  var nextProp = void 0;
-  var prevProp = void 0;
+function scheduleWork(fiber, expirationTime) {
+  recordScheduleUpdate();
 
-  for (var propKey in nextProps) {
-    attributeConfig = validAttributes[propKey];
-    if (!attributeConfig) {
-      continue; // not a valid native prop
+  {
+    if (fiber.tag === ClassComponent) {
+      var instance = fiber.stateNode;
+      warnAboutInvalidUpdates(instance);
     }
+  }
 
-    prevProp = prevProps[propKey];
-    nextProp = nextProps[propKey];
-
-    // functions are converted to booleans as markers that the associated
-    // events should be sent from native.
-    if (typeof nextProp === "function") {
-      nextProp = true;
-      // If nextProp is not a function, then don't bother changing prevProp
-      // since nextProp will win and go into the updatePayload regardless.
-      if (typeof prevProp === "function") {
-        prevProp = true;
+  var node = fiber;
+  while (node !== null) {
+    // Walk the parent path to the root and update each node's
+    // expiration time.
+    if (
+      node.expirationTime === NoWork ||
+      node.expirationTime > expirationTime
+    ) {
+      node.expirationTime = expirationTime;
+    }
+    if (node.alternate !== null) {
+      if (
+        node.alternate.expirationTime === NoWork ||
+        node.alternate.expirationTime > expirationTime
+      ) {
+        node.alternate.expirationTime = expirationTime;
       }
     }
-
-    // An explicit value of undefined is treated as a null because it overrides
-    // any other preceding value.
-    if (typeof nextProp === "undefined") {
-      nextProp = null;
-      if (typeof prevProp === "undefined") {
-        prevProp = null;
+    if (node.return === null) {
+      if (node.tag === HostRoot) {
+        var root = node.stateNode;
+        if (
+          !isWorking &&
+          nextRenderExpirationTime !== NoWork &&
+          expirationTime < nextRenderExpirationTime
+        ) {
+          // This is an interruption. (Used for performance tracking.)
+          interruptedBy = fiber;
+          resetStack();
+        }
+        markPendingPriorityLevel(root, expirationTime);
+        if (
+          // If we're in the render phase, we don't need to schedule this root
+          // for an update, because we'll do it before we exit...
+          !isWorking ||
+          isCommitting$1 ||
+          // ...unless this is a different root than the one we're rendering.
+          nextRoot !== root
+        ) {
+          var rootExpirationTime = root.expirationTime;
+          requestWork(root, rootExpirationTime);
+        }
+        if (nestedUpdateCount > NESTED_UPDATE_LIMIT) {
+          invariant(
+            false,
+            "Maximum update depth exceeded. This can happen when a " +
+              "component repeatedly calls setState inside " +
+              "componentWillUpdate or componentDidUpdate. React limits " +
+              "the number of nested updates to prevent infinite loops."
+          );
+        }
+      } else {
+        {
+          if (fiber.tag === ClassComponent) {
+            warnAboutUpdateOnUnmounted(fiber);
+          }
+        }
+        return;
       }
     }
+    node = node.return;
+  }
+}
 
-    if (removedKeys) {
-      removedKeys[propKey] = false;
-    }
+function recalculateCurrentTime() {
+  // Subtract initial time so it fits inside 32bits
+  mostRecentCurrentTimeMs = now() - originalStartTimeMs;
+  mostRecentCurrentTime = msToExpirationTime(mostRecentCurrentTimeMs);
+  return mostRecentCurrentTime;
+}
 
-    if (updatePayload && updatePayload[propKey] !== undefined) {
-      // Something else already triggered an update to this key because another
-      // value diffed. Since we're now later in the nested arrays our value is
-      // more important so we need to calculate it and override the existing
-      // value. It doesn't matter if nothing changed, we'll set it anyway.
+function deferredUpdates(fn) {
+  var previousExpirationContext = expirationContext;
+  var currentTime = recalculateCurrentTime();
+  expirationContext = computeAsyncExpiration(currentTime);
+  try {
+    return fn();
+  } finally {
+    expirationContext = previousExpirationContext;
+  }
+}
+function syncUpdates(fn, a, b, c, d) {
+  var previousExpirationContext = expirationContext;
+  expirationContext = Sync;
+  try {
+    return fn(a, b, c, d);
+  } finally {
+    expirationContext = previousExpirationContext;
+  }
+}
 
-      // Pattern match on: attributeConfig
-      if (typeof attributeConfig !== "object") {
-        // case: !Object is the default case
-        updatePayload[propKey] = nextProp;
-      } else if (
-        typeof attributeConfig.diff === "function" ||
-        typeof attributeConfig.process === "function"
-      ) {
-        // case: CustomAttributeConfiguration
-        var nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(nextProp)
-            : nextProp;
-        updatePayload[propKey] = nextValue;
-      }
-      continue;
-    }
+// TODO: Everything below this is written as if it has been lifted to the
+// renderers. I'll do this in a follow-up.
 
-    if (prevProp === nextProp) {
-      continue; // nothing changed
-    }
+// Linked-list of roots
+var firstScheduledRoot = null;
+var lastScheduledRoot = null;
 
-    // Pattern match on: attributeConfig
-    if (typeof attributeConfig !== "object") {
-      // case: !Object is the default case
-      if (defaultDiffer(prevProp, nextProp)) {
-        // a normal leaf has changed
-        (updatePayload || (updatePayload = {}))[propKey] = nextProp;
-      }
-    } else if (
-      typeof attributeConfig.diff === "function" ||
-      typeof attributeConfig.process === "function"
-    ) {
-      // case: CustomAttributeConfiguration
-      var shouldUpdate =
-        prevProp === undefined ||
-        (typeof attributeConfig.diff === "function"
-          ? attributeConfig.diff(prevProp, nextProp)
-          : defaultDiffer(prevProp, nextProp));
-      if (shouldUpdate) {
-        var _nextValue =
-          typeof attributeConfig.process === "function"
-            ? attributeConfig.process(nextProp)
-            : nextProp;
-        (updatePayload || (updatePayload = {}))[propKey] = _nextValue;
-      }
-    } else {
-      // default: fallthrough case when nested properties are defined
-      removedKeys = null;
-      removedKeyCount = 0;
-      // We think that attributeConfig is not CustomAttributeConfiguration at
-      // this point so we assume it must be AttributeConfiguration.
-      updatePayload = diffNestedProperty(
-        updatePayload,
-        prevProp,
-        nextProp,
-        attributeConfig
-      );
-      if (removedKeyCount > 0 && updatePayload) {
-        restoreDeletedValuesInNestedArray(
-          updatePayload,
-          nextProp,
-          attributeConfig
-        );
-        removedKeys = null;
-      }
-    }
-  }
+var callbackExpirationTime = NoWork;
+var callbackID = void 0;
+var isRendering = false;
+var nextFlushedRoot = null;
+var nextFlushedExpirationTime = NoWork;
+var lowestPendingInteractiveExpirationTime = NoWork;
+var deadlineDidExpire = false;
+var hasUnhandledError = false;
+var unhandledError = null;
+var deadline = null;
 
-  // Also iterate through all the previous props to catch any that have been
-  // removed and make sure native gets the signal so it can reset them to the
-  // default.
-  for (var _propKey in prevProps) {
-    if (nextProps[_propKey] !== undefined) {
-      continue; // we've already covered this key in the previous pass
-    }
-    attributeConfig = validAttributes[_propKey];
-    if (!attributeConfig) {
-      continue; // not a valid native prop
-    }
+var isBatchingUpdates = false;
+var isUnbatchingUpdates = false;
+var isBatchingInteractiveUpdates = false;
 
-    if (updatePayload && updatePayload[_propKey] !== undefined) {
-      // This was already updated to a diff result earlier.
-      continue;
-    }
+var completedBatches = null;
 
-    prevProp = prevProps[_propKey];
-    if (prevProp === undefined) {
-      continue; // was already empty anyway
-    }
-    // Pattern match on: attributeConfig
-    if (
-      typeof attributeConfig !== "object" ||
-      typeof attributeConfig.diff === "function" ||
-      typeof attributeConfig.process === "function"
-    ) {
-      // case: CustomAttributeConfiguration | !Object
-      // Flag the leaf property for removal by sending a sentinel.
-      (updatePayload || (updatePayload = {}))[_propKey] = null;
-      if (!removedKeys) {
-        removedKeys = {};
-      }
-      if (!removedKeys[_propKey]) {
-        removedKeys[_propKey] = true;
-        removedKeyCount++;
+// Use these to prevent an infinite loop of nested updates
+var NESTED_UPDATE_LIMIT = 1000;
+var nestedUpdateCount = 0;
+
+var timeHeuristicForUnitOfWork = 1;
+
+function scheduleCallbackWithExpirationTime(expirationTime) {
+  if (callbackExpirationTime !== NoWork) {
+    // A callback is already scheduled. Check its expiration time (timeout).
+    if (expirationTime > callbackExpirationTime) {
+      // Existing callback has sufficient timeout. Exit.
+      return;
+    } else {
+      if (callbackID !== null) {
+        // Existing callback has insufficient timeout. Cancel and schedule a
+        // new one.
+        cancelDeferredCallback(callbackID);
       }
-    } else {
-      // default:
-      // This is a nested attribute configuration where all the properties
-      // were removed so we need to go through and clear out all of them.
-      updatePayload = clearNestedProperty(
-        updatePayload,
-        prevProp,
-        attributeConfig
-      );
     }
+    // The request callback timer is already running. Don't start a new one.
+  } else {
+    startRequestCallbackTimer();
   }
-  return updatePayload;
+
+  callbackExpirationTime = expirationTime;
+  var currentMs = now() - originalStartTimeMs;
+  var expirationTimeMs = expirationTimeToMs(expirationTime);
+  var timeout = expirationTimeMs - currentMs;
+  callbackID = scheduleDeferredCallback(performAsyncWork, { timeout: timeout });
 }
 
-/**
- * addProperties adds all the valid props to the payload after being processed.
- */
-function addProperties(updatePayload, props, validAttributes) {
-  // TODO: Fast path
-  return diffProperties(updatePayload, emptyObject$1, props, validAttributes);
+// For every call to renderRoot, one of onFatal, onComplete, onSuspend, and
+// onYield is called upon exiting. We use these in lieu of returning a tuple.
+// I've also chosen not to inline them into renderRoot because these will
+// eventually be lifted into the renderer.
+function onFatal(root) {
+  root.finishedWork = null;
 }
 
-/**
- * clearProperties clears all the previous props by adding a null sentinel
- * to the payload for each valid key.
- */
-function clearProperties(updatePayload, prevProps, validAttributes) {
-  // TODO: Fast path
-  return diffProperties(
-    updatePayload,
-    prevProps,
-    emptyObject$1,
-    validAttributes
-  );
+function onComplete(root, finishedWork, expirationTime) {
+  root.pendingCommitExpirationTime = expirationTime;
+  root.finishedWork = finishedWork;
 }
 
-function create(props, validAttributes) {
-  return addProperties(
-    null, // updatePayload
-    props,
-    validAttributes
-  );
+function onSuspend(root, suspendedExpirationTime, expirationTime, timeoutMs) {
+  if (timeoutMs >= 0) {
+    var suspendedRoot = root;
+    setTimeout(function() {
+      retrySuspendedRoot(suspendedRoot, suspendedExpirationTime);
+    }, timeoutMs);
+  }
+  root.expirationTime = expirationTime;
 }
 
-function diff(prevProps, nextProps, validAttributes) {
-  return diffProperties(
-    null, // updatePayload
-    prevProps,
-    nextProps,
-    validAttributes
-  );
+function onYield(root) {
+  root.finishedWork = null;
 }
 
-/**
- * In the future, we should cleanup callbacks by cancelling them instead of
- * using this.
- */
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (!callback) {
-      return undefined;
-    }
-    if (typeof context.__isMounted === "boolean") {
-      // TODO(gaearon): this is gross and should be removed.
-      // It is currently necessary because View uses createClass,
-      // and so any measure() calls on View (which are done by React
-      // DevTools) trigger the isMounted() deprecation warning.
-      if (!context.__isMounted) {
-        return undefined;
-      }
-      // The else branch is important so that we don't
-      // trigger the deprecation warning by calling isMounted.
-    } else if (typeof context.isMounted === "function") {
-      if (!context.isMounted()) {
-        return undefined;
-      }
-    }
-    return callback.apply(context, arguments);
-  };
+function onCommit(root, expirationTime) {
+  root.expirationTime = expirationTime;
+  root.finishedWork = null;
 }
 
-function throwOnStylesProp(component, props) {
-  if (props.styles !== undefined) {
-    var owner = component._owner || null;
-    var name = component.constructor.displayName;
-    var msg =
-      "`styles` is not a supported property of `" +
-      name +
-      "`, did " +
-      "you mean `style` (singular)?";
-    if (owner && owner.constructor && owner.constructor.displayName) {
-      msg +=
-        "\n\nCheck the `" +
-        owner.constructor.displayName +
-        "` parent " +
-        " component.";
-    }
-    throw new Error(msg);
+// requestWork is called by the scheduler whenever a root receives an update.
+// It's up to the renderer to call renderRoot at some point in the future.
+function requestWork(root, expirationTime) {
+  addRootToSchedule(root, expirationTime);
+
+  if (isRendering) {
+    // Prevent reentrancy. Remaining work will be scheduled at the end of
+    // the currently rendering batch.
+    return;
   }
-}
 
-function warnForStyleProps(props, validAttributes) {
-  for (var key in validAttributes.style) {
-    if (!(validAttributes[key] || props[key] === undefined)) {
-      console.error(
-        "You are setting the style `{ " +
-          key +
-          ": ... }` as a prop. You " +
-          "should nest it in a style object. " +
-          "E.g. `{ style: { " +
-          key +
-          ": ... } }`"
-      );
+  if (isBatchingUpdates) {
+    // Flush work at the end of the batch.
+    if (isUnbatchingUpdates) {
+      // ...unless we're inside unbatchedUpdates, in which case we should
+      // flush it now.
+      nextFlushedRoot = root;
+      nextFlushedExpirationTime = Sync;
+      performWorkOnRoot(root, Sync, false);
     }
+    return;
+  }
+
+  // TODO: Get rid of Sync and use current time?
+  if (expirationTime === Sync) {
+    performSyncWork();
+  } else {
+    scheduleCallbackWithExpirationTime(expirationTime);
   }
 }
 
-function _classCallCheck(instance, Constructor) {
-  if (!(instance instanceof Constructor)) {
-    throw new TypeError("Cannot call a class as a function");
+function addRootToSchedule(root, expirationTime) {
+  // Add the root to the schedule.
+  // Check if this root is already part of the schedule.
+  if (root.nextScheduledRoot === null) {
+    // This root is not already scheduled. Add it.
+    root.expirationTime = expirationTime;
+    if (lastScheduledRoot === null) {
+      firstScheduledRoot = lastScheduledRoot = root;
+      root.nextScheduledRoot = root;
+    } else {
+      lastScheduledRoot.nextScheduledRoot = root;
+      lastScheduledRoot = root;
+      lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+    }
+  } else {
+    // This root is already scheduled, but its priority may have increased.
+    var remainingExpirationTime = root.expirationTime;
+    if (
+      remainingExpirationTime === NoWork ||
+      expirationTime < remainingExpirationTime
+    ) {
+      // Update the priority.
+      root.expirationTime = expirationTime;
+    }
   }
 }
 
-// Modules provided by RN:
-/**
- * This component defines the same methods as NativeMethodsMixin but without the
- * findNodeHandle wrapper. This wrapper is unnecessary for HostComponent views
- * and would also result in a circular require.js dependency (since
- * ReactNativeFiber depends on this component and NativeMethodsMixin depends on
- * ReactNativeFiber).
- */
+function findHighestPriorityRoot() {
+  var highestPriorityWork = NoWork;
+  var highestPriorityRoot = null;
+  if (lastScheduledRoot !== null) {
+    var previousScheduledRoot = lastScheduledRoot;
+    var root = firstScheduledRoot;
+    while (root !== null) {
+      var remainingExpirationTime = root.expirationTime;
+      if (remainingExpirationTime === NoWork) {
+        // This root no longer has work. Remove it from the scheduler.
 
-var ReactNativeFiberHostComponent = (function() {
-  function ReactNativeFiberHostComponent(tag, viewConfig) {
-    _classCallCheck(this, ReactNativeFiberHostComponent);
+        // TODO: This check is redudant, but Flow is confused by the branch
+        // below where we set lastScheduledRoot to null, even though we break
+        // from the loop right after.
+        invariant(
+          previousScheduledRoot !== null && lastScheduledRoot !== null,
+          "Should have a previous and last root. This error is likely " +
+            "caused by a bug in React. Please file an issue."
+        );
+        if (root === root.nextScheduledRoot) {
+          // This is the only root in the list.
+          root.nextScheduledRoot = null;
+          firstScheduledRoot = lastScheduledRoot = null;
+          break;
+        } else if (root === firstScheduledRoot) {
+          // This is the first root in the list.
+          var next = root.nextScheduledRoot;
+          firstScheduledRoot = next;
+          lastScheduledRoot.nextScheduledRoot = next;
+          root.nextScheduledRoot = null;
+        } else if (root === lastScheduledRoot) {
+          // This is the last root in the list.
+          lastScheduledRoot = previousScheduledRoot;
+          lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+          root.nextScheduledRoot = null;
+          break;
+        } else {
+          previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot;
+          root.nextScheduledRoot = null;
+        }
+        root = previousScheduledRoot.nextScheduledRoot;
+      } else {
+        if (
+          highestPriorityWork === NoWork ||
+          remainingExpirationTime < highestPriorityWork
+        ) {
+          // Update the priority, if it's higher
+          highestPriorityWork = remainingExpirationTime;
+          highestPriorityRoot = root;
+        }
+        if (root === lastScheduledRoot) {
+          break;
+        }
+        previousScheduledRoot = root;
+        root = root.nextScheduledRoot;
+      }
+    }
+  }
 
-    this._nativeTag = tag;
-    this._children = [];
-    this.viewConfig = viewConfig;
+  // If the next root is the same as the previous root, this is a nested
+  // update. To prevent an infinite loop, increment the nested update count.
+  var previousFlushedRoot = nextFlushedRoot;
+  if (
+    previousFlushedRoot !== null &&
+    previousFlushedRoot === highestPriorityRoot &&
+    highestPriorityWork === Sync
+  ) {
+    nestedUpdateCount++;
+  } else {
+    // Reset whenever we switch roots.
+    nestedUpdateCount = 0;
   }
+  nextFlushedRoot = highestPriorityRoot;
+  nextFlushedExpirationTime = highestPriorityWork;
+}
 
-  ReactNativeFiberHostComponent.prototype.blur = function blur() {
-    TextInputState.blurTextInput(this._nativeTag);
-  };
+function performAsyncWork(dl) {
+  performWork(NoWork, dl);
+}
 
-  ReactNativeFiberHostComponent.prototype.focus = function focus() {
-    TextInputState.focusTextInput(this._nativeTag);
-  };
+function performSyncWork() {
+  performWork(Sync, null);
+}
 
-  ReactNativeFiberHostComponent.prototype.measure = function measure(callback) {
-    UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-  };
+function performWork(minExpirationTime, dl) {
+  deadline = dl;
 
-  ReactNativeFiberHostComponent.prototype.measureInWindow = function measureInWindow(
-    callback
-  ) {
-    UIManager.measureInWindow(
-      this._nativeTag,
-      mountSafeCallback(this, callback)
-    );
-  };
+  // Keep working on roots until there's no more work, or until the we reach
+  // the deadline.
+  findHighestPriorityRoot();
 
-  ReactNativeFiberHostComponent.prototype.measureLayout = function measureLayout(
-    relativeToNativeNode,
-    onSuccess,
-    onFail /* currently unused */
-  ) {
-    UIManager.measureLayout(
-      this._nativeTag,
-      relativeToNativeNode,
-      mountSafeCallback(this, onFail),
-      mountSafeCallback(this, onSuccess)
-    );
-  };
+  if (enableProfilerTimer) {
+    resumeActualRenderTimerIfPaused();
+  }
 
-  ReactNativeFiberHostComponent.prototype.setNativeProps = function setNativeProps(
-    nativeProps
-  ) {
-    {
-      warnForStyleProps(nativeProps, this.viewConfig.validAttributes);
+  if (enableUserTimingAPI && deadline !== null) {
+    var didExpire = nextFlushedExpirationTime < recalculateCurrentTime();
+    var timeout = expirationTimeToMs(nextFlushedExpirationTime);
+    stopRequestCallbackTimer(didExpire, timeout);
+  }
+
+  if (deadline !== null) {
+    while (
+      nextFlushedRoot !== null &&
+      nextFlushedExpirationTime !== NoWork &&
+      (minExpirationTime === NoWork ||
+        minExpirationTime >= nextFlushedExpirationTime) &&
+      (!deadlineDidExpire ||
+        recalculateCurrentTime() >= nextFlushedExpirationTime)
+    ) {
+      recalculateCurrentTime();
+      performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, true);
+      findHighestPriorityRoot();
+    }
+  } else {
+    while (
+      nextFlushedRoot !== null &&
+      nextFlushedExpirationTime !== NoWork &&
+      (minExpirationTime === NoWork ||
+        minExpirationTime >= nextFlushedExpirationTime)
+    ) {
+      performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, false);
+      findHighestPriorityRoot();
     }
+  }
 
-    var updatePayload = create(nativeProps, this.viewConfig.validAttributes);
+  // We're done flushing work. Either we ran out of time in this callback,
+  // or there's no more work left with sufficient priority.
 
-    // Avoid the overhead of bridge calls if there's no update.
-    // This is an expensive no-op for Android, and causes an unnecessary
-    // view invalidation for certain components (eg RCTTextInput) on iOS.
-    if (updatePayload != null) {
-      UIManager.updateView(
-        this._nativeTag,
-        this.viewConfig.uiViewClassName,
-        updatePayload
-      );
-    }
-  };
+  // If we're inside a callback, set this to false since we just completed it.
+  if (deadline !== null) {
+    callbackExpirationTime = NoWork;
+    callbackID = null;
+  }
+  // If there's work left over, schedule a new callback.
+  if (nextFlushedExpirationTime !== NoWork) {
+    scheduleCallbackWithExpirationTime(nextFlushedExpirationTime);
+  }
 
-  return ReactNativeFiberHostComponent;
-})();
+  // Clean-up.
+  deadline = null;
+  deadlineDidExpire = false;
 
-var hasNativePerformanceNow =
-  typeof performance === "object" && typeof performance.now === "function";
+  finishRendering();
+}
 
-var now = hasNativePerformanceNow
-  ? function() {
-      return performance.now();
+function flushRoot(root, expirationTime) {
+  invariant(
+    !isRendering,
+    "work.commit(): Cannot commit while already rendering. This likely " +
+      "means you attempted to commit from inside a lifecycle method."
+  );
+  // Perform work on root as if the given expiration time is the current time.
+  // This has the effect of synchronously flushing all work up to and
+  // including the given time.
+  nextFlushedRoot = root;
+  nextFlushedExpirationTime = expirationTime;
+  performWorkOnRoot(root, expirationTime, false);
+  // Flush any sync work that was scheduled by lifecycles
+  performSyncWork();
+  finishRendering();
+}
+
+function finishRendering() {
+  nestedUpdateCount = 0;
+
+  if (completedBatches !== null) {
+    var batches = completedBatches;
+    completedBatches = null;
+    for (var i = 0; i < batches.length; i++) {
+      var batch = batches[i];
+      try {
+        batch._onComplete();
+      } catch (error) {
+        if (!hasUnhandledError) {
+          hasUnhandledError = true;
+          unhandledError = error;
+        }
+      }
     }
-  : function() {
-      return Date.now();
-    };
+  }
 
-var scheduledCallback = null;
-var frameDeadline = 0;
+  if (hasUnhandledError) {
+    var error = unhandledError;
+    unhandledError = null;
+    hasUnhandledError = false;
+    throw error;
+  }
+}
 
-var frameDeadlineObject = {
-  timeRemaining: function() {
-    return frameDeadline - now();
-  },
-  didTimeout: false
-};
+function performWorkOnRoot(root, expirationTime, isYieldy) {
+  invariant(
+    !isRendering,
+    "performWorkOnRoot was called recursively. This error is likely caused " +
+      "by a bug in React. Please file an issue."
+  );
+
+  isRendering = true;
+
+  // Check if this is async work or sync/expired work.
+  if (!isYieldy) {
+    // Flush work without yielding.
+    var finishedWork = root.finishedWork;
+    if (finishedWork !== null) {
+      // This root is already complete. We can commit it.
+      completeRoot(root, finishedWork, expirationTime);
+    } else {
+      root.finishedWork = null;
+      renderRoot(root, false);
+      finishedWork = root.finishedWork;
+      if (finishedWork !== null) {
+        // We've completed the root. Commit it.
+        completeRoot(root, finishedWork, expirationTime);
+      }
+    }
+  } else {
+    // Flush async work.
+    var _finishedWork = root.finishedWork;
+    if (_finishedWork !== null) {
+      // This root is already complete. We can commit it.
+      completeRoot(root, _finishedWork, expirationTime);
+    } else {
+      root.finishedWork = null;
+      renderRoot(root, true);
+      _finishedWork = root.finishedWork;
+      if (_finishedWork !== null) {
+        // We've completed the root. Check the deadline one more time
+        // before committing.
+        if (!shouldYield()) {
+          // Still time left. Commit the root.
+          completeRoot(root, _finishedWork, expirationTime);
+        } else {
+          // There's no time left. Mark this root as complete. We'll come
+          // back and commit it later.
+          root.finishedWork = _finishedWork;
+
+          if (enableProfilerTimer) {
+            // If we didn't finish, pause the "actual" render timer.
+            // We'll restart it when we resume work.
+            pauseActualRenderTimerIfRunning();
+          }
+        }
+      }
+    }
+  }
 
-function setTimeoutCallback() {
-  // TODO (bvaughn) Hard-coded 5ms unblocks initial async testing.
-  // React API probably changing to boolean rather than time remaining.
-  // Longer-term plan is to rewrite this using shared memory,
-  // And just return the value of the bit as the boolean.
-  frameDeadline = now() + 5;
+  isRendering = false;
+}
 
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  if (callback !== null) {
-    callback(frameDeadlineObject);
+function completeRoot(root, finishedWork, expirationTime) {
+  // Check if there's a batch that matches this expiration time.
+  var firstBatch = root.firstBatch;
+  if (firstBatch !== null && firstBatch._expirationTime <= expirationTime) {
+    if (completedBatches === null) {
+      completedBatches = [firstBatch];
+    } else {
+      completedBatches.push(firstBatch);
+    }
+    if (firstBatch._defer) {
+      // This root is blocked from committing by a batch. Unschedule it until
+      // we receive another update.
+      root.finishedWork = finishedWork;
+      root.expirationTime = NoWork;
+      return;
+    }
   }
+
+  // Commit the root.
+  root.finishedWork = null;
+  commitRoot(root, finishedWork);
 }
 
-// RN has a poor polyfill for requestIdleCallback so we aren't using it.
-// This implementation is only intended for short-term use anyway.
-// We also don't implement cancel functionality b'c Fiber doesn't currently need it.
-function scheduleDeferredCallback(callback) {
-  // We assume only one callback is scheduled at a time b'c that's how Fiber works.
-  scheduledCallback = callback;
-  return setTimeout(setTimeoutCallback, 1);
+// When working on async work, the reconciler asks the renderer if it should
+// yield execution. For DOM, we implement this with requestIdleCallback.
+function shouldYield() {
+  if (deadline === null || deadlineDidExpire) {
+    return false;
+  }
+  if (deadline.timeRemaining() > timeHeuristicForUnitOfWork) {
+    // Disregard deadline.didTimeout. Only expired work should be flushed
+    // during a timeout. This path is only hit for non-expired work.
+    return false;
+  }
+  deadlineDidExpire = true;
+  return true;
 }
 
-function cancelDeferredCallback(callbackID) {
-  scheduledCallback = null;
-  clearTimeout(callbackID);
+function onUncaughtError(error) {
+  invariant(
+    nextFlushedRoot !== null,
+    "Should be working on a root. This error is likely caused by a bug in " +
+      "React. Please file an issue."
+  );
+  // Unschedule this root so we don't work on it again until there's
+  // another update.
+  nextFlushedRoot.expirationTime = NoWork;
+  if (!hasUnhandledError) {
+    hasUnhandledError = true;
+    unhandledError = error;
+  }
 }
 
-// Modules provided by RN:
-// Counter for uniquely identifying views.
-// % 10 === 1 means it is a rootTag.
-// % 2 === 0 means it is a Fabric tag.
-var nextReactTag = 3;
-function allocateTag() {
-  var tag = nextReactTag;
-  if (tag % 10 === 1) {
-    tag += 2;
+// TODO: Batching should be implemented at the renderer level, not inside
+// the reconciler.
+function batchedUpdates$1(fn, a) {
+  var previousIsBatchingUpdates = isBatchingUpdates;
+  isBatchingUpdates = true;
+  try {
+    return fn(a);
+  } finally {
+    isBatchingUpdates = previousIsBatchingUpdates;
+    if (!isBatchingUpdates && !isRendering) {
+      performSyncWork();
+    }
   }
-  nextReactTag = tag + 2;
-  return tag;
 }
 
-function recursivelyUncacheFiberNode(node) {
-  if (typeof node === "number") {
-    // Leaf node (eg text)
-    uncacheFiberNode(node);
-  } else {
-    uncacheFiberNode(node._nativeTag);
+// TODO: Batching should be implemented at the renderer level, not inside
+// the reconciler.
+function unbatchedUpdates(fn, a) {
+  if (isBatchingUpdates && !isUnbatchingUpdates) {
+    isUnbatchingUpdates = true;
+    try {
+      return fn(a);
+    } finally {
+      isUnbatchingUpdates = false;
+    }
+  }
+  return fn(a);
+}
 
-    node._children.forEach(recursivelyUncacheFiberNode);
+// TODO: Batching should be implemented at the renderer level, not within
+// the reconciler.
+function flushSync(fn, a) {
+  invariant(
+    !isRendering,
+    "flushSync was called from inside a lifecycle method. It cannot be " +
+      "called when React is already rendering."
+  );
+  var previousIsBatchingUpdates = isBatchingUpdates;
+  isBatchingUpdates = true;
+  try {
+    return syncUpdates(fn, a);
+  } finally {
+    isBatchingUpdates = previousIsBatchingUpdates;
+    performSyncWork();
   }
 }
 
-var ReactNativeHostConfig = {
-  appendInitialChild: function(parentInstance, child) {
-    parentInstance._children.push(child);
-  },
-  createInstance: function(
-    type,
-    props,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
+function interactiveUpdates$1(fn, a, b) {
+  if (isBatchingInteractiveUpdates) {
+    return fn(a, b);
+  }
+  // If there are any pending interactive updates, synchronously flush them.
+  // This needs to happen before we read any handlers, because the effect of
+  // the previous event may influence which handlers are called during
+  // this event.
+  if (
+    !isBatchingUpdates &&
+    !isRendering &&
+    lowestPendingInteractiveExpirationTime !== NoWork
   ) {
-    var tag = allocateTag();
-    var viewConfig = ReactNativeViewConfigRegistry.get(type);
+    // Synchronously flush pending interactive updates.
+    performWork(lowestPendingInteractiveExpirationTime, null);
+    lowestPendingInteractiveExpirationTime = NoWork;
+  }
+  var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates;
+  var previousIsBatchingUpdates = isBatchingUpdates;
+  isBatchingInteractiveUpdates = true;
+  isBatchingUpdates = true;
+  try {
+    return fn(a, b);
+  } finally {
+    isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates;
+    isBatchingUpdates = previousIsBatchingUpdates;
+    if (!isBatchingUpdates && !isRendering) {
+      performSyncWork();
+    }
+  }
+}
 
-    {
-      for (var key in viewConfig.validAttributes) {
-        if (props.hasOwnProperty(key)) {
-          deepFreezeAndThrowOnMutationInDev(props[key]);
-        }
-      }
+function flushInteractiveUpdates$1() {
+  if (!isRendering && lowestPendingInteractiveExpirationTime !== NoWork) {
+    // Synchronously flush pending interactive updates.
+    performWork(lowestPendingInteractiveExpirationTime, null);
+    lowestPendingInteractiveExpirationTime = NoWork;
+  }
+}
+
+function flushControlled(fn) {
+  var previousIsBatchingUpdates = isBatchingUpdates;
+  isBatchingUpdates = true;
+  try {
+    syncUpdates(fn);
+  } finally {
+    isBatchingUpdates = previousIsBatchingUpdates;
+    if (!isBatchingUpdates && !isRendering) {
+      performWork(Sync, null);
     }
+  }
+}
 
-    invariant(
-      type !== "RCTView" || !hostContext.isInAParentText,
-      "Nesting of <View> within <Text> is not currently supported."
-    );
+// 0 is PROD, 1 is DEV.
+// Might add PROFILE later.
 
-    var updatePayload = create(props, viewConfig.validAttributes);
+var didWarnAboutNestedUpdates = void 0;
 
-    UIManager.createView(
-      tag, // reactTag
-      viewConfig.uiViewClassName, // viewName
-      rootContainerInstance, // rootTag
-      updatePayload // props
-    );
+{
+  didWarnAboutNestedUpdates = false;
+}
 
-    var component = new ReactNativeFiberHostComponent(tag, viewConfig);
+function getContextForSubtree(parentComponent) {
+  if (!parentComponent) {
+    return emptyObject;
+  }
 
-    precacheFiberNode(internalInstanceHandle, tag);
-    updateFiberProps(tag, props);
+  var fiber = get$1(parentComponent);
+  var parentContext = findCurrentUnmaskedContext(fiber);
+  return isContextProvider(fiber)
+    ? processChildContext(fiber, parentContext)
+    : parentContext;
+}
 
-    // Not sure how to avoid this cast. Flow is okay if the component is defined
-    // in the same file but if it's external it can't see the types.
-    return component;
-  },
-  createTextInstance: function(
-    text,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    invariant(
-      hostContext.isInAParentText,
-      "Text strings must be rendered within a <Text> component."
-    );
+function scheduleRootUpdate(current, element, expirationTime, callback) {
+  {
+    if (
+      ReactDebugCurrentFiber.phase === "render" &&
+      ReactDebugCurrentFiber.current !== null &&
+      !didWarnAboutNestedUpdates
+    ) {
+      didWarnAboutNestedUpdates = true;
+      warning(
+        false,
+        "Render methods should be a pure function of props and state; " +
+          "triggering nested component updates from render is not allowed. " +
+          "If necessary, trigger nested updates in componentDidUpdate.\n\n" +
+          "Check the render method of %s.",
+        getComponentName(ReactDebugCurrentFiber.current) || "Unknown"
+      );
+    }
+  }
 
-    var tag = allocateTag();
+  var update = createUpdate(expirationTime);
+  // Caution: React DevTools currently depends on this property
+  // being called "element".
+  update.payload = { element: element };
 
-    UIManager.createView(
-      tag, // reactTag
-      "RCTRawText", // viewName
-      rootContainerInstance, // rootTag
-      { text: text } // props
-    );
+  callback = callback === undefined ? null : callback;
+  if (callback !== null) {
+    !(typeof callback === "function")
+      ? warning(
+          false,
+          "render(...): Expected the last optional `callback` argument to be a " +
+            "function. Instead received: %s.",
+          callback
+        )
+      : void 0;
+    update.callback = callback;
+  }
+  enqueueUpdate(current, update, expirationTime);
 
-    precacheFiberNode(internalInstanceHandle, tag);
+  scheduleWork(current, expirationTime);
+  return expirationTime;
+}
 
-    return tag;
-  },
-  finalizeInitialChildren: function(
-    parentInstance,
-    type,
-    props,
-    rootContainerInstance
-  ) {
-    // Don't send a no-op message over the bridge.
-    if (parentInstance._children.length === 0) {
-      return false;
+function updateContainerAtExpirationTime(
+  element,
+  container,
+  parentComponent,
+  expirationTime,
+  callback
+) {
+  // TODO: If this is a nested container, this won't be the root.
+  var current = container.current;
+
+  {
+    if (ReactFiberInstrumentation_1.debugTool) {
+      if (current.alternate === null) {
+        ReactFiberInstrumentation_1.debugTool.onMountContainer(container);
+      } else if (element === null) {
+        ReactFiberInstrumentation_1.debugTool.onUnmountContainer(container);
+      } else {
+        ReactFiberInstrumentation_1.debugTool.onUpdateContainer(container);
+      }
     }
+  }
 
-    // Map from child objects to native tags.
-    // Either way we need to pass a copy of the Array to prevent it from being frozen.
-    var nativeTags = parentInstance._children.map(function(child) {
-      return typeof child === "number"
-        ? child // Leaf node (eg text)
-        : child._nativeTag;
-    });
+  var context = getContextForSubtree(parentComponent);
+  if (container.context === null) {
+    container.context = context;
+  } else {
+    container.pendingContext = context;
+  }
 
-    UIManager.setChildren(
-      parentInstance._nativeTag, // containerTag
-      nativeTags // reactTags
-    );
+  return scheduleRootUpdate(current, element, expirationTime, callback);
+}
 
-    return false;
-  },
-  getRootHostContext: function(rootContainerInstance) {
-    return { isInAParentText: false };
-  },
-  getChildHostContext: function(parentHostContext, type) {
-    var prevIsInAParentText = parentHostContext.isInAParentText;
-    var isInAParentText =
-      type === "AndroidTextInput" || // Android
-      type === "RCTMultilineTextInputView" || // iOS
-      type === "RCTSinglelineTextInputView" || // iOS
-      type === "RCTText" ||
-      type === "RCTVirtualText";
-
-    if (prevIsInAParentText !== isInAParentText) {
-      return { isInAParentText: isInAParentText };
+function findHostInstance$1(component) {
+  var fiber = get$1(component);
+  if (fiber === undefined) {
+    if (typeof component.render === "function") {
+      invariant(false, "Unable to find node on an unmounted component.");
     } else {
-      return parentHostContext;
+      invariant(
+        false,
+        "Argument appears to not be a ReactComponent. Keys: %s",
+        Object.keys(component)
+      );
     }
-  },
-  getPublicInstance: function(instance) {
-    return instance;
-  },
+  }
+  var hostFiber = findCurrentHostFiber(fiber);
+  if (hostFiber === null) {
+    return null;
+  }
+  return hostFiber.stateNode;
+}
 
-  now: now,
+function createContainer(containerInfo, isAsync, hydrate) {
+  return createFiberRoot(containerInfo, isAsync, hydrate);
+}
 
-  isPrimaryRenderer: true,
+function updateContainer(element, container, parentComponent, callback) {
+  var current = container.current;
+  var currentTime = recalculateCurrentTime();
+  var expirationTime = computeExpirationForFiber(currentTime, current);
+  return updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    expirationTime,
+    callback
+  );
+}
 
-  prepareForCommit: function() {
-    // Noop
-  },
-  prepareUpdate: function(
-    instance,
-    type,
-    oldProps,
-    newProps,
-    rootContainerInstance,
-    hostContext
-  ) {
-    return emptyObject;
-  },
-  resetAfterCommit: function() {
-    // Noop
-  },
+function getPublicRootInstance(container) {
+  var containerFiber = container.current;
+  if (!containerFiber.child) {
+    return null;
+  }
+  switch (containerFiber.child.tag) {
+    case HostComponent:
+      return getPublicInstance(containerFiber.child.stateNode);
+    default:
+      return containerFiber.child.stateNode;
+  }
+}
 
-  scheduleDeferredCallback: scheduleDeferredCallback,
-  cancelDeferredCallback: cancelDeferredCallback,
+function findHostInstanceWithNoPortals(fiber) {
+  var hostFiber = findCurrentHostFiberWithNoPortals(fiber);
+  if (hostFiber === null) {
+    return null;
+  }
+  return hostFiber.stateNode;
+}
 
-  shouldDeprioritizeSubtree: function(type, props) {
-    return false;
-  },
-  shouldSetTextContent: function(type, props) {
-    // TODO (bvaughn) Revisit this decision.
-    // Always returning false simplifies the createInstance() implementation,
-    // But creates an additional child Fiber for raw text children.
-    // No additional native views are created though.
-    // It's not clear to me which is better so I'm deferring for now.
-    // More context @ github.com/facebook/react/pull/8560#discussion_r92111303
-    return false;
-  },
+function injectIntoDevTools(devToolsConfig) {
+  var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
 
-  mutation: {
-    appendChild: function(parentInstance, child) {
-      var childTag = typeof child === "number" ? child : child._nativeTag;
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
-
-      if (index >= 0) {
-        children.splice(index, 1);
-        children.push(child);
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerTag
-          [index], // moveFromIndices
-          [children.length - 1], // moveToIndices
-          [], // addChildReactTags
-          [], // addAtIndices
-          [] // removeAtIndices
-        );
-      } else {
-        children.push(child);
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerTag
-          [], // moveFromIndices
-          [], // moveToIndices
-          [childTag], // addChildReactTags
-          [children.length - 1], // addAtIndices
-          [] // removeAtIndices
-        );
+  return injectInternals(
+    Object.assign({}, devToolsConfig, {
+      findHostInstanceByFiber: function(fiber) {
+        var hostFiber = findCurrentHostFiber(fiber);
+        if (hostFiber === null) {
+          return null;
+        }
+        return hostFiber.stateNode;
+      },
+      findFiberByHostInstance: function(instance) {
+        if (!findFiberByHostInstance) {
+          // Might not be implemented by the renderer.
+          return null;
+        }
+        return findFiberByHostInstance(instance);
       }
-    },
-    appendChildToContainer: function(parentInstance, child) {
-      var childTag = typeof child === "number" ? child : child._nativeTag;
-      UIManager.setChildren(
-        parentInstance, // containerTag
-        [childTag] // reactTags
-      );
-    },
-    commitTextUpdate: function(textInstance, oldText, newText) {
-      UIManager.updateView(
-        textInstance, // reactTag
-        "RCTRawText", // viewName
-        { text: newText } // props
-      );
-    },
-    commitMount: function(instance, type, newProps, internalInstanceHandle) {
-      // Noop
-    },
-    commitUpdate: function(
-      instance,
-      updatePayloadTODO,
-      type,
-      oldProps,
-      newProps,
-      internalInstanceHandle
-    ) {
-      var viewConfig = instance.viewConfig;
+    })
+  );
+}
 
-      updateFiberProps(instance._nativeTag, newProps);
+// This file intentionally does *not* have the Flow annotation.
+// Don't add it. See `./inline-typed.js` for an explanation.
+
+var ReactNativeFiberRenderer = Object.freeze({
+  updateContainerAtExpirationTime: updateContainerAtExpirationTime,
+  createContainer: createContainer,
+  updateContainer: updateContainer,
+  flushRoot: flushRoot,
+  requestWork: requestWork,
+  computeUniqueAsyncExpiration: computeUniqueAsyncExpiration,
+  batchedUpdates: batchedUpdates$1,
+  unbatchedUpdates: unbatchedUpdates,
+  deferredUpdates: deferredUpdates,
+  syncUpdates: syncUpdates,
+  interactiveUpdates: interactiveUpdates$1,
+  flushInteractiveUpdates: flushInteractiveUpdates$1,
+  flushControlled: flushControlled,
+  flushSync: flushSync,
+  getPublicRootInstance: getPublicRootInstance,
+  findHostInstance: findHostInstance$1,
+  findHostInstanceWithNoPortals: findHostInstanceWithNoPortals,
+  injectIntoDevTools: injectIntoDevTools
+});
 
-      var updatePayload = diff(oldProps, newProps, viewConfig.validAttributes);
+function createPortal(
+  children,
+  containerInfo,
+  // TODO: figure out the API for cross-renderer implementation.
+  implementation
+) {
+  var key =
+    arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : null;
 
-      // Avoid the overhead of bridge calls if there's no update.
-      // This is an expensive no-op for Android, and causes an unnecessary
-      // view invalidation for certain components (eg RCTTextInput) on iOS.
-      if (updatePayload != null) {
-        UIManager.updateView(
-          instance._nativeTag, // reactTag
-          viewConfig.uiViewClassName, // viewName
-          updatePayload // props
-        );
-      }
-    },
-    insertBefore: function(parentInstance, child, beforeChild) {
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
-
-      // Move existing child or add new child?
-      if (index >= 0) {
-        children.splice(index, 1);
-        var beforeChildIndex = children.indexOf(beforeChild);
-        children.splice(beforeChildIndex, 0, child);
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerID
-          [index], // moveFromIndices
-          [beforeChildIndex], // moveToIndices
-          [], // addChildReactTags
-          [], // addAtIndices
-          [] // removeAtIndices
-        );
-      } else {
-        var _beforeChildIndex = children.indexOf(beforeChild);
-        children.splice(_beforeChildIndex, 0, child);
-
-        var childTag = typeof child === "number" ? child : child._nativeTag;
-
-        UIManager.manageChildren(
-          parentInstance._nativeTag, // containerID
-          [], // moveFromIndices
-          [], // moveToIndices
-          [childTag], // addChildReactTags
-          [_beforeChildIndex], // addAtIndices
-          [] // removeAtIndices
-        );
-      }
-    },
-    insertInContainerBefore: function(parentInstance, child, beforeChild) {
-      // TODO (bvaughn): Remove this check when...
-      // We create a wrapper object for the container in ReactNative render()
-      // Or we refactor to remove wrapper objects entirely.
-      // For more info on pros/cons see PR #8560 description.
-      invariant(
-        typeof parentInstance !== "number",
-        "Container does not support insertBefore operation"
-      );
-    },
-    removeChild: function(parentInstance, child) {
-      recursivelyUncacheFiberNode(child);
-      var children = parentInstance._children;
-      var index = children.indexOf(child);
-
-      children.splice(index, 1);
-
-      UIManager.manageChildren(
-        parentInstance._nativeTag, // containerID
-        [], // moveFromIndices
-        [], // moveToIndices
-        [], // addChildReactTags
-        [], // addAtIndices
-        [index] // removeAtIndices
-      );
-    },
-    removeChildFromContainer: function(parentInstance, child) {
-      recursivelyUncacheFiberNode(child);
-      UIManager.manageChildren(
-        parentInstance, // containerID
-        [], // moveFromIndices
-        [], // moveToIndices
-        [], // addChildReactTags
-        [], // addAtIndices
-        [0] // removeAtIndices
-      );
-    },
-    resetTextContent: function(instance) {
-      // Noop
-    }
-  }
-};
+  return {
+    // This tag allow us to uniquely identify this as a React Portal
+    $$typeof: REACT_PORTAL_TYPE,
+    key: key == null ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+
+// TODO: this is special because it gets imported during build.
+
+var ReactVersion = "16.4.1";
 
 // Modules provided by RN:
 var NativeMethodsMixin = function(findNodeHandle, findHostInstance) {
@@ -15112,9 +14851,7 @@ var getInspectorDataForViewTag = void 0;
 }
 
 // Module provided by RN:
-var ReactNativeFiberRenderer = reactReconciler(ReactNativeHostConfig);
-
-var findHostInstance = ReactNativeFiberRenderer.findHostInstance;
+var findHostInstance = findHostInstance$1;
 
 function findNodeHandle(componentOrHandle) {
   {
@@ -15182,22 +14919,18 @@ var ReactNativeRenderer = {
     if (!root) {
       // TODO (bvaughn): If we decide to keep the wrapper component,
       // We could create a wrapper for containerTag as well to reduce special casing.
-      root = ReactNativeFiberRenderer.createContainer(
-        containerTag,
-        false,
-        false
-      );
+      root = createContainer(containerTag, false, false);
       roots.set(containerTag, root);
     }
-    ReactNativeFiberRenderer.updateContainer(element, root, null, callback);
+    updateContainer(element, root, null, callback);
 
-    return ReactNativeFiberRenderer.getPublicRootInstance(root);
+    return getPublicRootInstance(root);
   },
   unmountComponentAtNode: function(containerTag) {
     var root = roots.get(containerTag);
     if (root) {
       // TODO: Is it safe to reset this now or should I wait since this unmount could be deferred?
-      ReactNativeFiberRenderer.updateContainer(null, root, null, function() {
+      updateContainer(null, root, null, function() {
         roots.delete(containerTag);
       });
     }
@@ -15220,13 +14953,11 @@ var ReactNativeRenderer = {
   __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
     // Used as a mixin in many createClass-based components
     NativeMethodsMixin: NativeMethodsMixin(findNodeHandle, findHostInstance),
-    // Used by react-native-github/Libraries/ components
-    ReactNativeComponentTree: ReactNativeComponentTree, // ScrollResponder
     computeComponentStackForErrorReporting: computeComponentStackForErrorReporting
   }
 };
 
-ReactNativeFiberRenderer.injectIntoDevTools({
+injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 1,
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
index 52c14c46bfc3..24da20e3ba42 100644
--- a/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-prod.js
@@ -13,17 +13,15 @@
 "use strict";
 require("InitializeCore");
 var invariant = require("fbjs/lib/invariant"),
-  emptyFunction = require("fbjs/lib/emptyFunction"),
   ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
   UIManager = require("UIManager"),
   RCTEventEmitter = require("RCTEventEmitter"),
   React = require("react"),
   emptyObject = require("fbjs/lib/emptyObject"),
-  shallowEqual = require("fbjs/lib/shallowEqual"),
-  ExceptionsManager = require("ExceptionsManager"),
   deepDiffer = require("deepDiffer"),
   flattenStyle = require("flattenStyle"),
-  TextInputState = require("TextInputState");
+  TextInputState = require("TextInputState"),
+  ExceptionsManager = require("ExceptionsManager");
 function invokeGuardedCallback(name, func, context, a, b, c, d, e, f) {
   this._hasCaughtError = !1;
   this._caughtError = null;
@@ -350,21 +348,14 @@ function accumulateDirectDispatchesSingle(event) {
   }
 }
 var shouldBeReleasedProperties = "dispatchConfig _targetInst nativeEvent isDefaultPrevented isPropagationStopped _dispatchListeners _dispatchInstances".split(
-    " "
-  ),
-  EventInterface = {
-    type: null,
-    target: null,
-    currentTarget: emptyFunction.thatReturnsNull,
-    eventPhase: null,
-    bubbles: null,
-    cancelable: null,
-    timeStamp: function(event) {
-      return event.timeStamp || Date.now();
-    },
-    defaultPrevented: null,
-    isTrusted: null
-  };
+  " "
+);
+function functionThatReturnsTrue() {
+  return !0;
+}
+function functionThatReturnsFalse() {
+  return !1;
+}
 function SyntheticEvent(
   dispatchConfig,
   targetInst,
@@ -385,9 +376,9 @@ function SyntheticEvent(
   this.isDefaultPrevented = (null != nativeEvent.defaultPrevented
   ? nativeEvent.defaultPrevented
   : !1 === nativeEvent.returnValue)
-    ? emptyFunction.thatReturnsTrue
-    : emptyFunction.thatReturnsFalse;
-  this.isPropagationStopped = emptyFunction.thatReturnsFalse;
+    ? functionThatReturnsTrue
+    : functionThatReturnsFalse;
+  this.isPropagationStopped = functionThatReturnsFalse;
   return this;
 }
 Object.assign(SyntheticEvent.prototype, {
@@ -398,7 +389,7 @@ Object.assign(SyntheticEvent.prototype, {
       (event.preventDefault
         ? event.preventDefault()
         : "unknown" !== typeof event.returnValue && (event.returnValue = !1),
-      (this.isDefaultPrevented = emptyFunction.thatReturnsTrue));
+      (this.isDefaultPrevented = functionThatReturnsTrue));
   },
   stopPropagation: function() {
     var event = this.nativeEvent;
@@ -406,12 +397,12 @@ Object.assign(SyntheticEvent.prototype, {
       (event.stopPropagation
         ? event.stopPropagation()
         : "unknown" !== typeof event.cancelBubble && (event.cancelBubble = !0),
-      (this.isPropagationStopped = emptyFunction.thatReturnsTrue));
+      (this.isPropagationStopped = functionThatReturnsTrue));
   },
   persist: function() {
-    this.isPersistent = emptyFunction.thatReturnsTrue;
+    this.isPersistent = functionThatReturnsTrue;
   },
-  isPersistent: emptyFunction.thatReturnsFalse,
+  isPersistent: functionThatReturnsFalse,
   destructor: function() {
     var Interface = this.constructor.Interface,
       propName;
@@ -424,7 +415,21 @@ Object.assign(SyntheticEvent.prototype, {
       this[shouldBeReleasedProperties[Interface]] = null;
   }
 });
-SyntheticEvent.Interface = EventInterface;
+SyntheticEvent.Interface = {
+  type: null,
+  target: null,
+  currentTarget: function() {
+    return null;
+  },
+  eventPhase: null,
+  bubbles: null,
+  cancelable: null,
+  timeStamp: function(event) {
+    return event.timeStamp || Date.now();
+  },
+  defaultPrevented: null,
+  isTrusted: null
+};
 SyntheticEvent.extend = function(Interface) {
   function E() {}
   function Class() {
@@ -984,56 +989,45 @@ var eventTypes$1 = {
       else return null;
       return topLevelType;
     }
-  },
-  instanceCache = {},
-  instanceProps = {};
-function uncacheFiberNode(tag) {
-  delete instanceCache[tag];
-  delete instanceProps[tag];
-}
-function getInstanceFromTag(tag) {
-  return "number" === typeof tag ? instanceCache[tag] || null : tag;
-}
-var ReactNativeComponentTree = Object.freeze({
-  precacheFiberNode: function(hostInst, tag) {
-    instanceCache[tag] = hostInst;
-  },
-  uncacheFiberNode: uncacheFiberNode,
-  getClosestInstanceFromNode: getInstanceFromTag,
-  getInstanceFromNode: getInstanceFromTag,
-  getNodeFromInstance: function(inst) {
-    var tag = inst.stateNode._nativeTag;
-    void 0 === tag && (tag = inst.stateNode.canonical._nativeTag);
-    invariant(tag, "All native instances should have a tag.");
-    return tag;
-  },
-  getFiberCurrentPropsFromNode: function(stateNode) {
-    return instanceProps[stateNode._nativeTag] || null;
-  },
-  updateFiberProps: function(tag, props) {
-    instanceProps[tag] = props;
-  }
-});
+  };
 injection.injectEventPluginOrder([
   "ResponderEventPlugin",
   "ReactNativeBridgeEventPlugin"
 ]);
-getFiberCurrentPropsFromNode =
-  ReactNativeComponentTree.getFiberCurrentPropsFromNode;
-getInstanceFromNode = ReactNativeComponentTree.getInstanceFromNode;
-getNodeFromInstance = ReactNativeComponentTree.getNodeFromInstance;
-ResponderEventPlugin.injection.injectGlobalResponderHandler({
-  onChange: function(from, to, blockNativeResponder) {
-    null !== to
-      ? UIManager.setJSResponder(to.stateNode._nativeTag, blockNativeResponder)
-      : UIManager.clearJSResponder();
-  }
-});
 injection.injectEventPluginsByName({
   ResponderEventPlugin: ResponderEventPlugin,
   ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
 });
-var restoreTarget = null,
+var instanceCache = {},
+  instanceProps = {};
+function uncacheFiberNode(tag) {
+  delete instanceCache[tag];
+  delete instanceProps[tag];
+}
+function getInstanceFromTag(tag) {
+  return instanceCache[tag] || null;
+}
+var ReactNativeComponentTree = {
+    precacheFiberNode: function(hostInst, tag) {
+      instanceCache[tag] = hostInst;
+    },
+    uncacheFiberNode: uncacheFiberNode,
+    getClosestInstanceFromNode: getInstanceFromTag,
+    getInstanceFromNode: getInstanceFromTag,
+    getNodeFromInstance: function(inst) {
+      var tag = inst.stateNode._nativeTag;
+      void 0 === tag && (tag = inst.stateNode.canonical._nativeTag);
+      invariant(tag, "All native instances should have a tag.");
+      return tag;
+    },
+    getFiberCurrentPropsFromNode: function(stateNode) {
+      return instanceProps[stateNode._nativeTag] || null;
+    },
+    updateFiberProps: function(tag, props) {
+      instanceProps[tag] = props;
+    }
+  },
+  restoreTarget = null,
   restoreQueue = null;
 function restoreStateOfTarget(target) {
   if ((target = getInstanceFromNode(target))) {
@@ -1100,7 +1094,7 @@ function _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam) {
       ReactErrorUtils.rethrowCaughtError());
   });
 }
-var ReactNativeEventEmitter = Object.freeze({
+RCTEventEmitter.register({
   getListener: getListener,
   registrationNames: registrationNameModules,
   _receiveRootNodeIDEvent: _receiveRootNodeIDEvent,
@@ -1140,7 +1134,17 @@ var ReactNativeEventEmitter = Object.freeze({
     }
   }
 });
-RCTEventEmitter.register(ReactNativeEventEmitter);
+getFiberCurrentPropsFromNode =
+  ReactNativeComponentTree.getFiberCurrentPropsFromNode;
+getInstanceFromNode = ReactNativeComponentTree.getInstanceFromNode;
+getNodeFromInstance = ReactNativeComponentTree.getNodeFromInstance;
+ResponderEventPlugin.injection.injectGlobalResponderHandler({
+  onChange: function(from, to, blockNativeResponder) {
+    null !== to
+      ? UIManager.setJSResponder(to.stateNode._nativeTag, blockNativeResponder)
+      : UIManager.clearJSResponder();
+  }
+});
 var ReactCurrentOwner =
     React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner,
   hasSymbol = "function" === typeof Symbol && Symbol.for,
@@ -1182,6 +1186,8 @@ function getComponentName(fiber) {
       return "Context.Provider";
     case REACT_STRICT_MODE_TYPE:
       return "StrictMode";
+    case REACT_TIMEOUT_TYPE:
+      return "Timeout";
   }
   if ("object" === typeof type && null !== type)
     switch (type.$$typeof) {
@@ -1203,11 +1209,6 @@ function isFiberMountedImpl(fiber) {
   }
   return 3 === node.tag ? 2 : 3;
 }
-function isMounted(component) {
-  return (component = component._reactInternalFiber)
-    ? 2 === isFiberMountedImpl(component)
-    : !1;
-}
 function assertIsMounted(fiber) {
   invariant(
     2 === isFiberMountedImpl(fiber),
@@ -1322,170 +1323,343 @@ function findCurrentHostFiberWithNoPortals(parent) {
   }
   return null;
 }
-function FiberNode(tag, pendingProps, key, mode) {
-  this.tag = tag;
-  this.key = key;
-  this.sibling = this.child = this.return = this.stateNode = this.type = null;
-  this.index = 0;
-  this.ref = null;
-  this.pendingProps = pendingProps;
-  this.memoizedState = this.updateQueue = this.memoizedProps = null;
-  this.mode = mode;
-  this.effectTag = 0;
-  this.lastEffect = this.firstEffect = this.nextEffect = null;
-  this.expirationTime = 0;
-  this.alternate = null;
-}
-function createWorkInProgress(current, pendingProps, expirationTime) {
-  var workInProgress = current.alternate;
-  null === workInProgress
-    ? ((workInProgress = new FiberNode(
-        current.tag,
-        pendingProps,
-        current.key,
-        current.mode
-      )),
-      (workInProgress.type = current.type),
-      (workInProgress.stateNode = current.stateNode),
-      (workInProgress.alternate = current),
-      (current.alternate = workInProgress))
-    : ((workInProgress.pendingProps = pendingProps),
-      (workInProgress.effectTag = 0),
-      (workInProgress.nextEffect = null),
-      (workInProgress.firstEffect = null),
-      (workInProgress.lastEffect = null));
-  workInProgress.expirationTime = expirationTime;
-  workInProgress.child = current.child;
-  workInProgress.memoizedProps = current.memoizedProps;
-  workInProgress.memoizedState = current.memoizedState;
-  workInProgress.updateQueue = current.updateQueue;
-  workInProgress.sibling = current.sibling;
-  workInProgress.index = current.index;
-  workInProgress.ref = current.ref;
-  return workInProgress;
-}
-function createFiberFromElement(element, mode, expirationTime) {
-  var type = element.type,
-    key = element.key;
-  element = element.props;
-  if ("function" === typeof type)
-    var fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
-  else if ("string" === typeof type) fiberTag = 5;
-  else
-    switch (type) {
-      case REACT_FRAGMENT_TYPE:
-        return createFiberFromFragment(
-          element.children,
-          mode,
-          expirationTime,
-          key
-        );
-      case REACT_ASYNC_MODE_TYPE:
-        fiberTag = 11;
-        mode |= 3;
-        break;
-      case REACT_STRICT_MODE_TYPE:
-        fiberTag = 11;
-        mode |= 2;
-        break;
-      case REACT_PROFILER_TYPE:
-        return (
-          (type = new FiberNode(15, element, key, mode | 4)),
-          (type.type = REACT_PROFILER_TYPE),
-          (type.expirationTime = expirationTime),
-          (type.stateNode = { duration: 0, startTime: 0 }),
-          type
-        );
-      case REACT_TIMEOUT_TYPE:
-        fiberTag = 16;
-        mode |= 2;
-        break;
-      default:
-        a: {
-          switch ("object" === typeof type && null !== type
-            ? type.$$typeof
-            : null) {
-            case REACT_PROVIDER_TYPE:
-              fiberTag = 13;
-              break a;
-            case REACT_CONTEXT_TYPE:
-              fiberTag = 12;
-              break a;
-            case REACT_FORWARD_REF_TYPE:
-              fiberTag = 14;
-              break a;
-            default:
-              invariant(
-                !1,
-                "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
-                null == type ? type : typeof type,
-                ""
-              );
+var emptyObject$1 = {},
+  removedKeys = null,
+  removedKeyCount = 0;
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node))
+    for (var i = node.length; i-- && 0 < removedKeyCount; )
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+  else if (node && 0 < removedKeyCount)
+    for (i in removedKeys)
+      if (removedKeys[i]) {
+        var _nextProp = node[i];
+        if (void 0 !== _nextProp) {
+          var attributeConfig = validAttributes[i];
+          if (attributeConfig) {
+            "function" === typeof _nextProp && (_nextProp = !0);
+            "undefined" === typeof _nextProp && (_nextProp = null);
+            if ("object" !== typeof attributeConfig)
+              updatePayload[i] = _nextProp;
+            else if (
+              "function" === typeof attributeConfig.diff ||
+              "function" === typeof attributeConfig.process
+            )
+              (_nextProp =
+                "function" === typeof attributeConfig.process
+                  ? attributeConfig.process(_nextProp)
+                  : _nextProp),
+                (updatePayload[i] = _nextProp);
+            removedKeys[i] = !1;
+            removedKeyCount--;
           }
-          fiberTag = void 0;
         }
-    }
-  mode = new FiberNode(fiberTag, element, key, mode);
-  mode.type = type;
-  mode.expirationTime = expirationTime;
-  return mode;
-}
-function createFiberFromFragment(elements, mode, expirationTime, key) {
-  elements = new FiberNode(10, elements, key, mode);
-  elements.expirationTime = expirationTime;
-  return elements;
-}
-function createFiberFromText(content, mode, expirationTime) {
-  content = new FiberNode(6, content, null, mode);
-  content.expirationTime = expirationTime;
-  return content;
-}
-function createFiberFromPortal(portal, mode, expirationTime) {
-  mode = new FiberNode(
-    4,
-    null !== portal.children ? portal.children : [],
-    portal.key,
-    mode
-  );
-  mode.expirationTime = expirationTime;
-  mode.stateNode = {
-    containerInfo: portal.containerInfo,
-    pendingChildren: null,
-    implementation: portal.implementation
-  };
-  return mode;
-}
-var onCommitFiberRoot = null,
-  onCommitFiberUnmount = null;
-function catchErrors(fn) {
-  return function(arg) {
-    try {
-      return fn(arg);
-    } catch (err) {}
-  };
-}
-function injectInternals(internals) {
-  if ("undefined" === typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) return !1;
-  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
-  if (hook.isDisabled || !hook.supportsFiber) return !0;
-  try {
-    var rendererID = hook.inject(internals);
-    onCommitFiberRoot = catchErrors(function(root) {
-      return hook.onCommitFiberRoot(rendererID, root);
-    });
-    onCommitFiberUnmount = catchErrors(function(fiber) {
-      return hook.onCommitFiberUnmount(rendererID, fiber);
-    });
-  } catch (err) {}
-  return !0;
-}
-function onCommitRoot(root) {
-  "function" === typeof onCommitFiberRoot && onCommitFiberRoot(root);
-}
-function onCommitUnmount(fiber) {
-  "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
+      }
 }
-function getStackAddendumByWorkInProgressFiber(workInProgress) {
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) return updatePayload;
+  if (!prevProp || !nextProp)
+    return nextProp
+      ? addNestedProperty(updatePayload, nextProp, validAttributes)
+      : prevProp
+        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
+        : updatePayload;
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    var minLength =
+        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
+      i;
+    for (i = 0; i < minLength; i++)
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp[i],
+        nextProp[i],
+        validAttributes
+      );
+    for (; i < prevProp.length; i++)
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp[i],
+        validAttributes
+      );
+    for (; i < nextProp.length; i++)
+      updatePayload = addNestedProperty(
+        updatePayload,
+        nextProp[i],
+        validAttributes
+      );
+    return updatePayload;
+  }
+  return Array.isArray(prevProp)
+    ? diffProperties(
+        updatePayload,
+        flattenStyle(prevProp),
+        nextProp,
+        validAttributes
+      )
+    : diffProperties(
+        updatePayload,
+        prevProp,
+        flattenStyle(nextProp),
+        validAttributes
+      );
+}
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) return updatePayload;
+  if (!Array.isArray(nextProp))
+    return diffProperties(
+      updatePayload,
+      emptyObject$1,
+      nextProp,
+      validAttributes
+    );
+  for (var i = 0; i < nextProp.length; i++)
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) return updatePayload;
+  if (!Array.isArray(prevProp))
+    return diffProperties(
+      updatePayload,
+      prevProp,
+      emptyObject$1,
+      validAttributes
+    );
+  for (var i = 0; i < prevProp.length; i++)
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig, propKey;
+  for (propKey in nextProps)
+    if ((attributeConfig = validAttributes[propKey])) {
+      var prevProp = prevProps[propKey];
+      var nextProp = nextProps[propKey];
+      "function" === typeof nextProp &&
+        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
+      "undefined" === typeof nextProp &&
+        ((nextProp = null),
+        "undefined" === typeof prevProp && (prevProp = null));
+      removedKeys && (removedKeys[propKey] = !1);
+      if (updatePayload && void 0 !== updatePayload[propKey])
+        if ("object" !== typeof attributeConfig)
+          updatePayload[propKey] = nextProp;
+        else {
+          if (
+            "function" === typeof attributeConfig.diff ||
+            "function" === typeof attributeConfig.process
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              (updatePayload[propKey] = attributeConfig);
+        }
+      else if (prevProp !== nextProp)
+        if ("object" !== typeof attributeConfig)
+          ("object" !== typeof nextProp ||
+            null === nextProp ||
+            deepDiffer(prevProp, nextProp)) &&
+            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
+        else if (
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+        ) {
+          if (
+            void 0 === prevProp ||
+            ("function" === typeof attributeConfig.diff
+              ? attributeConfig.diff(prevProp, nextProp)
+              : "object" !== typeof nextProp ||
+                null === nextProp ||
+                deepDiffer(prevProp, nextProp))
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              ((updatePayload || (updatePayload = {}))[
+                propKey
+              ] = attributeConfig);
+        } else
+          (removedKeys = null),
+            (removedKeyCount = 0),
+            (updatePayload = diffNestedProperty(
+              updatePayload,
+              prevProp,
+              nextProp,
+              attributeConfig
+            )),
+            0 < removedKeyCount &&
+              updatePayload &&
+              (restoreDeletedValuesInNestedArray(
+                updatePayload,
+                nextProp,
+                attributeConfig
+              ),
+              (removedKeys = null));
+    }
+  for (var _propKey in prevProps)
+    void 0 === nextProps[_propKey] &&
+      (!(attributeConfig = validAttributes[_propKey]) ||
+        (updatePayload && void 0 !== updatePayload[_propKey]) ||
+        ((prevProp = prevProps[_propKey]),
+        void 0 !== prevProp &&
+          ("object" !== typeof attributeConfig ||
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
+              removedKeys || (removedKeys = {}),
+              removedKeys[_propKey] ||
+                ((removedKeys[_propKey] = !0), removedKeyCount++))
+            : (updatePayload = clearNestedProperty(
+                updatePayload,
+                prevProp,
+                attributeConfig
+              )))));
+  return updatePayload;
+}
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (callback) {
+      if ("boolean" === typeof context.__isMounted) {
+        if (!context.__isMounted) return;
+      } else if (
+        "function" === typeof context.isMounted &&
+        !context.isMounted()
+      )
+        return;
+      return callback.apply(context, arguments);
+    }
+  };
+}
+var ReactNativeFiberHostComponent = (function() {
+    function ReactNativeFiberHostComponent(tag, viewConfig) {
+      if (!(this instanceof ReactNativeFiberHostComponent))
+        throw new TypeError("Cannot call a class as a function");
+      this._nativeTag = tag;
+      this._children = [];
+      this.viewConfig = viewConfig;
+    }
+    ReactNativeFiberHostComponent.prototype.blur = function() {
+      TextInputState.blurTextInput(this._nativeTag);
+    };
+    ReactNativeFiberHostComponent.prototype.focus = function() {
+      TextInputState.focusTextInput(this._nativeTag);
+    };
+    ReactNativeFiberHostComponent.prototype.measure = function(callback) {
+      UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+    };
+    ReactNativeFiberHostComponent.prototype.measureInWindow = function(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        this._nativeTag,
+        mountSafeCallback(this, callback)
+      );
+    };
+    ReactNativeFiberHostComponent.prototype.measureLayout = function(
+      relativeToNativeNode,
+      onSuccess,
+      onFail
+    ) {
+      UIManager.measureLayout(
+        this._nativeTag,
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
+    ReactNativeFiberHostComponent.prototype.setNativeProps = function(
+      nativeProps
+    ) {
+      nativeProps = diffProperties(
+        null,
+        emptyObject$1,
+        nativeProps,
+        this.viewConfig.validAttributes
+      );
+      null != nativeProps &&
+        UIManager.updateView(
+          this._nativeTag,
+          this.viewConfig.uiViewClassName,
+          nativeProps
+        );
+    };
+    return ReactNativeFiberHostComponent;
+  })(),
+  now$1 =
+    "object" === typeof performance && "function" === typeof performance.now
+      ? function() {
+          return performance.now();
+        }
+      : function() {
+          return Date.now();
+        },
+  scheduledCallback = null,
+  frameDeadline = 0,
+  frameDeadlineObject = {
+    timeRemaining: function() {
+      return frameDeadline - now$1();
+    },
+    didTimeout: !1
+  };
+function setTimeoutCallback() {
+  frameDeadline = now$1() + 5;
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  null !== callback && callback(frameDeadlineObject);
+}
+function shim$1() {
+  invariant(
+    !1,
+    "The current renderer does not support hyration. This error is likely caused by a bug in React. Please file an issue."
+  );
+}
+var nextReactTag = 3;
+function allocateTag() {
+  var tag = nextReactTag;
+  1 === tag % 10 && (tag += 2);
+  nextReactTag = tag + 2;
+  return tag;
+}
+function recursivelyUncacheFiberNode(node) {
+  "number" === typeof node
+    ? uncacheFiberNode(node)
+    : (uncacheFiberNode(node._nativeTag),
+      node._children.forEach(recursivelyUncacheFiberNode));
+}
+function finalizeInitialChildren(parentInstance) {
+  if (0 === parentInstance._children.length) return !1;
+  var nativeTags = parentInstance._children.map(function(child) {
+    return "number" === typeof child ? child : child._nativeTag;
+  });
+  UIManager.setChildren(parentInstance._nativeTag, nativeTags);
+  return !1;
+}
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
   var info = "";
   do {
     a: switch (workInProgress.tag) {
@@ -1518,20 +1692,325 @@ function getStackAddendumByWorkInProgressFiber(workInProgress) {
   } while (workInProgress);
   return info;
 }
-function createProfilerTimer() {
-  return {
-    checkActualRenderTimeStackEmpty: function() {},
-    markActualRenderTimeStarted: function() {},
-    pauseActualRenderTimerIfRunning: function() {},
-    recordElapsedActualRenderTime: function() {},
-    resetActualRenderTimer: function() {},
-    resumeActualRenderTimerIfPaused: function() {},
-    recordElapsedBaseRenderTimeIfRunning: function() {},
-    startBaseRenderTimer: function() {},
-    stopBaseRenderTimerIfRunning: function() {}
+new Set();
+var valueStack = [],
+  index = -1;
+function createCursor(defaultValue) {
+  return { current: defaultValue };
+}
+function pop(cursor) {
+  0 > index ||
+    ((cursor.current = valueStack[index]), (valueStack[index] = null), index--);
+}
+function push(cursor, value) {
+  index++;
+  valueStack[index] = cursor.current;
+  cursor.current = value;
+}
+var contextStackCursor = createCursor(emptyObject),
+  didPerformWorkStackCursor = createCursor(!1),
+  previousContext = emptyObject;
+function getUnmaskedContext(workInProgress) {
+  return isContextProvider(workInProgress)
+    ? previousContext
+    : contextStackCursor.current;
+}
+function getMaskedContext(workInProgress, unmaskedContext) {
+  var contextTypes = workInProgress.type.contextTypes;
+  if (!contextTypes) return emptyObject;
+  var instance = workInProgress.stateNode;
+  if (
+    instance &&
+    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+  )
+    return instance.__reactInternalMemoizedMaskedChildContext;
+  var context = {},
+    key;
+  for (key in contextTypes) context[key] = unmaskedContext[key];
+  instance &&
+    ((workInProgress = workInProgress.stateNode),
+    (workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext),
+    (workInProgress.__reactInternalMemoizedMaskedChildContext = context));
+  return context;
+}
+function isContextProvider(fiber) {
+  return 2 === fiber.tag && null != fiber.type.childContextTypes;
+}
+function popContextProvider(fiber) {
+  isContextProvider(fiber) &&
+    (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
+}
+function popTopLevelContextObject(fiber) {
+  pop(didPerformWorkStackCursor, fiber);
+  pop(contextStackCursor, fiber);
+}
+function pushTopLevelContextObject(fiber, context, didChange) {
+  invariant(
+    contextStackCursor.current === emptyObject,
+    "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
+  );
+  push(contextStackCursor, context, fiber);
+  push(didPerformWorkStackCursor, didChange, fiber);
+}
+function processChildContext(fiber, parentContext) {
+  var instance = fiber.stateNode,
+    childContextTypes = fiber.type.childContextTypes;
+  if ("function" !== typeof instance.getChildContext) return parentContext;
+  instance = instance.getChildContext();
+  for (var contextKey in instance)
+    invariant(
+      contextKey in childContextTypes,
+      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+      getComponentName(fiber) || "Unknown",
+      contextKey
+    );
+  return Object.assign({}, parentContext, instance);
+}
+function pushContextProvider(workInProgress) {
+  if (!isContextProvider(workInProgress)) return !1;
+  var instance = workInProgress.stateNode;
+  instance =
+    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+    emptyObject;
+  previousContext = contextStackCursor.current;
+  push(contextStackCursor, instance, workInProgress);
+  push(
+    didPerformWorkStackCursor,
+    didPerformWorkStackCursor.current,
+    workInProgress
+  );
+  return !0;
+}
+function invalidateContextProvider(workInProgress, didChange) {
+  var instance = workInProgress.stateNode;
+  invariant(
+    instance,
+    "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+  );
+  if (didChange) {
+    var mergedContext = processChildContext(workInProgress, previousContext);
+    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+    pop(didPerformWorkStackCursor, workInProgress);
+    pop(contextStackCursor, workInProgress);
+    push(contextStackCursor, mergedContext, workInProgress);
+  } else pop(didPerformWorkStackCursor, workInProgress);
+  push(didPerformWorkStackCursor, didChange, workInProgress);
+}
+function FiberNode(tag, pendingProps, key, mode) {
+  this.tag = tag;
+  this.key = key;
+  this.sibling = this.child = this.return = this.stateNode = this.type = null;
+  this.index = 0;
+  this.ref = null;
+  this.pendingProps = pendingProps;
+  this.memoizedState = this.updateQueue = this.memoizedProps = null;
+  this.mode = mode;
+  this.effectTag = 0;
+  this.lastEffect = this.firstEffect = this.nextEffect = null;
+  this.expirationTime = 0;
+  this.alternate = null;
+}
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  null === workInProgress
+    ? ((workInProgress = new FiberNode(
+        current.tag,
+        pendingProps,
+        current.key,
+        current.mode
+      )),
+      (workInProgress.type = current.type),
+      (workInProgress.stateNode = current.stateNode),
+      (workInProgress.alternate = current),
+      (current.alternate = workInProgress))
+    : ((workInProgress.pendingProps = pendingProps),
+      (workInProgress.effectTag = 0),
+      (workInProgress.nextEffect = null),
+      (workInProgress.firstEffect = null),
+      (workInProgress.lastEffect = null));
+  workInProgress.expirationTime = expirationTime;
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+  return workInProgress;
+}
+function createFiberFromElement(element, mode, expirationTime) {
+  var type = element.type,
+    key = element.key;
+  element = element.props;
+  if ("function" === typeof type)
+    var fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
+  else if ("string" === typeof type) fiberTag = 5;
+  else
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          element.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 3;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 2;
+        break;
+      case REACT_PROFILER_TYPE:
+        return (
+          (type = new FiberNode(15, element, key, mode | 4)),
+          (type.type = REACT_PROFILER_TYPE),
+          (type.expirationTime = expirationTime),
+          type
+        );
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = 16;
+        mode |= 2;
+        break;
+      default:
+        a: {
+          switch ("object" === typeof type && null !== type
+            ? type.$$typeof
+            : null) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = 13;
+              break a;
+            case REACT_CONTEXT_TYPE:
+              fiberTag = 12;
+              break a;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = 14;
+              break a;
+            default:
+              invariant(
+                !1,
+                "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
+                null == type ? type : typeof type,
+                ""
+              );
+          }
+          fiberTag = void 0;
+        }
+    }
+  mode = new FiberNode(fiberTag, element, key, mode);
+  mode.type = type;
+  mode.expirationTime = expirationTime;
+  return mode;
+}
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  elements = new FiberNode(10, elements, key, mode);
+  elements.expirationTime = expirationTime;
+  return elements;
+}
+function createFiberFromText(content, mode, expirationTime) {
+  content = new FiberNode(6, content, null, mode);
+  content.expirationTime = expirationTime;
+  return content;
+}
+function createFiberFromPortal(portal, mode, expirationTime) {
+  mode = new FiberNode(
+    4,
+    null !== portal.children ? portal.children : [],
+    portal.key,
+    mode
+  );
+  mode.expirationTime = expirationTime;
+  mode.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null,
+    implementation: portal.implementation
   };
+  return mode;
+}
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
+  containerInfo = {
+    current: isAsync,
+    containerInfo: containerInfo,
+    pendingChildren: null,
+    earliestPendingTime: 0,
+    latestPendingTime: 0,
+    earliestSuspendedTime: 0,
+    latestSuspendedTime: 0,
+    latestPingedTime: 0,
+    didError: !1,
+    pendingCommitExpirationTime: 0,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    nextExpirationTimeToWorkOn: 0,
+    expirationTime: 0,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  return (isAsync.stateNode = containerInfo);
+}
+var onCommitFiberRoot = null,
+  onCommitFiberUnmount = null;
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {}
+  };
+}
+function injectInternals(internals) {
+  if ("undefined" === typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) return !1;
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled || !hook.supportsFiber) return !0;
+  try {
+    var rendererID = hook.inject(internals);
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {}
+  return !0;
+}
+function onCommitRoot(root) {
+  "function" === typeof onCommitFiberRoot && onCommitFiberRoot(root);
+}
+function onCommitUnmount(fiber) {
+  "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
+}
+function markPendingPriorityLevel(root, expirationTime) {
+  root.didError = !1;
+  var earliestPendingTime = root.earliestPendingTime;
+  0 === earliestPendingTime
+    ? (root.earliestPendingTime = root.latestPendingTime = expirationTime)
+    : earliestPendingTime > expirationTime
+      ? (root.earliestPendingTime = expirationTime)
+      : root.latestPendingTime < expirationTime &&
+        (root.latestPendingTime = expirationTime);
+  findNextPendingPriorityLevel(root);
+}
+function findNextPendingPriorityLevel(root) {
+  var earliestSuspendedTime = root.earliestSuspendedTime,
+    earliestPendingTime = root.earliestPendingTime;
+  if (0 === earliestSuspendedTime)
+    var nextExpirationTimeToWorkOn = (earliestSuspendedTime = earliestPendingTime);
+  else
+    0 !== earliestPendingTime
+      ? ((nextExpirationTimeToWorkOn = earliestPendingTime),
+        (earliestSuspendedTime =
+          earliestSuspendedTime < earliestPendingTime
+            ? earliestSuspendedTime
+            : earliestPendingTime))
+      : (nextExpirationTimeToWorkOn = earliestSuspendedTime =
+          root.latestPingedTime);
+  root.didError && (earliestSuspendedTime = 1);
+  root.nextExpirationTimeToWorkOn = nextExpirationTimeToWorkOn;
+  root.expirationTime = earliestSuspendedTime;
 }
-new Set();
 var hasForceUpdate = !1;
 function createUpdateQueue(baseState) {
   return {
@@ -1784,10 +2263,89 @@ function commitUpdateQueue(finishedWork, finishedQueue, instance) {
     null !== finishedWork;
 
   )
-    (finishedQueue = finishedWork.callback),
-      null !== finishedQueue &&
-        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
-      (finishedWork = finishedWork.nextEffect);
+    (finishedQueue = finishedWork.callback),
+      null !== finishedQueue &&
+        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
+      (finishedWork = finishedWork.nextEffect);
+}
+function createCapturedValue(value, source) {
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
+var providerCursor = createCursor(null),
+  valueCursor = createCursor(null),
+  changedBitsCursor = createCursor(0);
+function pushProvider(providerFiber) {
+  var context = providerFiber.type._context;
+  push(changedBitsCursor, context._changedBits, providerFiber);
+  push(valueCursor, context._currentValue, providerFiber);
+  push(providerCursor, providerFiber, providerFiber);
+  context._currentValue = providerFiber.pendingProps.value;
+  context._changedBits = providerFiber.stateNode;
+}
+function popProvider(providerFiber) {
+  var changedBits = changedBitsCursor.current,
+    currentValue = valueCursor.current;
+  pop(providerCursor, providerFiber);
+  pop(valueCursor, providerFiber);
+  pop(changedBitsCursor, providerFiber);
+  providerFiber = providerFiber.type._context;
+  providerFiber._currentValue = currentValue;
+  providerFiber._changedBits = changedBits;
+}
+var NO_CONTEXT = {},
+  contextStackCursor$1 = createCursor(NO_CONTEXT),
+  contextFiberStackCursor = createCursor(NO_CONTEXT),
+  rootInstanceStackCursor = createCursor(NO_CONTEXT);
+function requiredContext(c) {
+  invariant(
+    c !== NO_CONTEXT,
+    "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
+  );
+  return c;
+}
+function pushHostContainer(fiber, nextRootInstance) {
+  push(rootInstanceStackCursor, nextRootInstance, fiber);
+  push(contextFiberStackCursor, fiber, fiber);
+  push(contextStackCursor$1, NO_CONTEXT, fiber);
+  pop(contextStackCursor$1, fiber);
+  push(contextStackCursor$1, { isInAParentText: !1 }, fiber);
+}
+function popHostContainer(fiber) {
+  pop(contextStackCursor$1, fiber);
+  pop(contextFiberStackCursor, fiber);
+  pop(rootInstanceStackCursor, fiber);
+}
+function popHostContext(fiber) {
+  contextFiberStackCursor.current === fiber &&
+    (pop(contextStackCursor$1, fiber), pop(contextFiberStackCursor, fiber));
+}
+var hasOwnProperty = Object.prototype.hasOwnProperty;
+function is(x, y) {
+  return x === y ? 0 !== x || 0 !== y || 1 / x === 1 / y : x !== x && y !== y;
+}
+function shallowEqual(objA, objB) {
+  if (is(objA, objB)) return !0;
+  if (
+    "object" !== typeof objA ||
+    null === objA ||
+    "object" !== typeof objB ||
+    null === objB
+  )
+    return !1;
+  var keysA = Object.keys(objA),
+    keysB = Object.keys(objB);
+  if (keysA.length !== keysB.length) return !1;
+  for (keysB = 0; keysB < keysA.length; keysB++)
+    if (
+      !hasOwnProperty.call(objB, keysA[keysB]) ||
+      !is(objA[keysA[keysB]], objB[keysA[keysB]])
+    )
+      return !1;
+  return !0;
 }
 function applyDerivedStateFromProps(
   workInProgress,
@@ -1806,351 +2364,120 @@ function applyDerivedStateFromProps(
     0 === workInProgress.expirationTime &&
     (workInProgress.baseState = prevState);
 }
-function ReactFiberClassComponent(
-  legacyContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  memoizeProps,
-  memoizeState,
-  recalculateCurrentTime
-) {
-  function checkShouldComponentUpdate(
-    workInProgress,
-    oldProps,
-    newProps,
-    oldState,
-    newState,
-    newContext
-  ) {
-    var instance = workInProgress.stateNode;
-    workInProgress = workInProgress.type;
-    return "function" === typeof instance.shouldComponentUpdate
-      ? instance.shouldComponentUpdate(newProps, newState, newContext)
-      : workInProgress.prototype &&
-        workInProgress.prototype.isPureReactComponent
-        ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
-        : !0;
-  }
-  function adoptClassInstance(workInProgress, instance) {
-    instance.updater = classComponentUpdater;
-    workInProgress.stateNode = instance;
-    instance._reactInternalFiber = workInProgress;
-  }
-  function callComponentWillReceiveProps(
-    workInProgress,
-    instance,
-    newProps,
-    newContext
-  ) {
-    workInProgress = instance.state;
-    "function" === typeof instance.componentWillReceiveProps &&
-      instance.componentWillReceiveProps(newProps, newContext);
-    "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
-      instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
-    instance.state !== workInProgress &&
-      classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+var classComponentUpdater = {
+  isMounted: function(component) {
+    return (component = component._reactInternalFiber)
+      ? 2 === isFiberMountedImpl(component)
+      : !1;
+  },
+  enqueueSetState: function(inst, payload, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.payload = payload;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  },
+  enqueueReplaceState: function(inst, payload, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.tag = 1;
+    update.payload = payload;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  },
+  enqueueForceUpdate: function(inst, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.tag = 2;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
   }
-  var cacheContext = legacyContext.cacheContext,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    isContextConsumer = legacyContext.isContextConsumer,
-    hasContextChanged = legacyContext.hasContextChanged,
-    classComponentUpdater = {
-      isMounted: isMounted,
-      enqueueSetState: function(inst, payload, callback) {
-        inst = inst._reactInternalFiber;
-        var currentTime = recalculateCurrentTime();
-        currentTime = computeExpirationForFiber(currentTime, inst);
-        var update = createUpdate(currentTime);
-        update.payload = payload;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, currentTime);
-        scheduleWork(inst, currentTime);
-      },
-      enqueueReplaceState: function(inst, payload, callback) {
-        inst = inst._reactInternalFiber;
-        var currentTime = recalculateCurrentTime();
-        currentTime = computeExpirationForFiber(currentTime, inst);
-        var update = createUpdate(currentTime);
-        update.tag = 1;
-        update.payload = payload;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, currentTime);
-        scheduleWork(inst, currentTime);
-      },
-      enqueueForceUpdate: function(inst, callback) {
-        inst = inst._reactInternalFiber;
-        var currentTime = recalculateCurrentTime();
-        currentTime = computeExpirationForFiber(currentTime, inst);
-        var update = createUpdate(currentTime);
-        update.tag = 2;
-        void 0 !== callback &&
-          null !== callback &&
-          (update.callback = callback);
-        enqueueUpdate(inst, update, currentTime);
-        scheduleWork(inst, currentTime);
-      }
-    };
-  return {
-    adoptClassInstance: adoptClassInstance,
-    constructClassInstance: function(workInProgress, props) {
-      var ctor = workInProgress.type,
-        unmaskedContext = getUnmaskedContext(workInProgress),
-        needsContext = isContextConsumer(workInProgress),
-        context = needsContext
-          ? getMaskedContext(workInProgress, unmaskedContext)
-          : emptyObject;
-      props = new ctor(props, context);
-      workInProgress.memoizedState =
-        null !== props.state && void 0 !== props.state ? props.state : null;
-      adoptClassInstance(workInProgress, props);
-      needsContext && cacheContext(workInProgress, unmaskedContext, context);
-      return props;
-    },
-    mountClassInstance: function(workInProgress, renderExpirationTime) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        props = workInProgress.pendingProps,
-        unmaskedContext = getUnmaskedContext(workInProgress);
-      instance.props = props;
-      instance.state = workInProgress.memoizedState;
-      instance.refs = emptyObject;
-      instance.context = getMaskedContext(workInProgress, unmaskedContext);
-      unmaskedContext = workInProgress.updateQueue;
-      null !== unmaskedContext &&
-        (processUpdateQueue(
-          workInProgress,
-          unmaskedContext,
-          props,
-          instance,
-          renderExpirationTime
-        ),
-        (instance.state = workInProgress.memoizedState));
-      unmaskedContext = workInProgress.type.getDerivedStateFromProps;
-      "function" === typeof unmaskedContext &&
-        (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
-        (instance.state = workInProgress.memoizedState));
-      "function" === typeof ctor.getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate ||
-        ("function" !== typeof instance.UNSAFE_componentWillMount &&
-          "function" !== typeof instance.componentWillMount) ||
-        ((ctor = instance.state),
-        "function" === typeof instance.componentWillMount &&
-          instance.componentWillMount(),
-        "function" === typeof instance.UNSAFE_componentWillMount &&
-          instance.UNSAFE_componentWillMount(),
-        ctor !== instance.state &&
-          classComponentUpdater.enqueueReplaceState(
-            instance,
-            instance.state,
-            null
-          ),
-        (unmaskedContext = workInProgress.updateQueue),
-        null !== unmaskedContext &&
-          (processUpdateQueue(
-            workInProgress,
-            unmaskedContext,
-            props,
-            instance,
-            renderExpirationTime
-          ),
-          (instance.state = workInProgress.memoizedState)));
-      "function" === typeof instance.componentDidMount &&
-        (workInProgress.effectTag |= 4);
-    },
-    resumeMountClassInstance: function(workInProgress, renderExpirationTime) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps;
-      instance.props = oldProps;
-      var oldContext = instance.context,
-        newUnmaskedContext = getUnmaskedContext(workInProgress);
-      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
-      (ctor =
-        "function" === typeof getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate) ||
-        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-          "function" !== typeof instance.componentWillReceiveProps) ||
-        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
-          callComponentWillReceiveProps(
-            workInProgress,
-            instance,
-            newProps,
-            newUnmaskedContext
-          ));
-      hasForceUpdate = !1;
-      var oldState = workInProgress.memoizedState;
-      oldContext = instance.state = oldState;
-      var updateQueue = workInProgress.updateQueue;
-      null !== updateQueue &&
-        (processUpdateQueue(
-          workInProgress,
-          updateQueue,
-          newProps,
-          instance,
-          renderExpirationTime
-        ),
-        (oldContext = workInProgress.memoizedState));
-      if (
-        oldProps === newProps &&
-        oldState === oldContext &&
-        !hasContextChanged() &&
-        !hasForceUpdate
-      )
-        return (
-          "function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4),
-          !1
-        );
-      "function" === typeof getDerivedStateFromProps &&
-        (applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        ),
-        (oldContext = workInProgress.memoizedState));
-      (renderExpirationTime =
-        hasForceUpdate ||
-        checkShouldComponentUpdate(
-          workInProgress,
-          oldProps,
-          newProps,
-          oldState,
-          oldContext,
-          newUnmaskedContext
-        ))
-        ? (ctor ||
-            ("function" !== typeof instance.UNSAFE_componentWillMount &&
-              "function" !== typeof instance.componentWillMount) ||
-            ("function" === typeof instance.componentWillMount &&
-              instance.componentWillMount(),
-            "function" === typeof instance.UNSAFE_componentWillMount &&
-              instance.UNSAFE_componentWillMount()),
-          "function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4))
-        : ("function" === typeof instance.componentDidMount &&
-            (workInProgress.effectTag |= 4),
-          (workInProgress.memoizedProps = newProps),
-          (workInProgress.memoizedState = oldContext));
-      instance.props = newProps;
-      instance.state = oldContext;
-      instance.context = newUnmaskedContext;
-      return renderExpirationTime;
-    },
-    updateClassInstance: function(
-      current,
+};
+function checkShouldComponentUpdate(
+  workInProgress,
+  oldProps,
+  newProps,
+  oldState,
+  newState,
+  newContext
+) {
+  var instance = workInProgress.stateNode;
+  workInProgress = workInProgress.type;
+  return "function" === typeof instance.shouldComponentUpdate
+    ? instance.shouldComponentUpdate(newProps, newState, newContext)
+    : workInProgress.prototype && workInProgress.prototype.isPureReactComponent
+      ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+      : !0;
+}
+function callComponentWillReceiveProps(
+  workInProgress,
+  instance,
+  newProps,
+  newContext
+) {
+  workInProgress = instance.state;
+  "function" === typeof instance.componentWillReceiveProps &&
+    instance.componentWillReceiveProps(newProps, newContext);
+  "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
+    instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+  instance.state !== workInProgress &&
+    classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+}
+function mountClassInstance(workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type,
+    instance = workInProgress.stateNode,
+    props = workInProgress.pendingProps,
+    unmaskedContext = getUnmaskedContext(workInProgress);
+  instance.props = props;
+  instance.state = workInProgress.memoizedState;
+  instance.refs = emptyObject;
+  instance.context = getMaskedContext(workInProgress, unmaskedContext);
+  unmaskedContext = workInProgress.updateQueue;
+  null !== unmaskedContext &&
+    (processUpdateQueue(
       workInProgress,
+      unmaskedContext,
+      props,
+      instance,
       renderExpirationTime
-    ) {
-      var ctor = workInProgress.type,
-        instance = workInProgress.stateNode,
-        oldProps = workInProgress.memoizedProps,
-        newProps = workInProgress.pendingProps;
-      instance.props = oldProps;
-      var oldContext = instance.context,
-        newUnmaskedContext = getUnmaskedContext(workInProgress);
-      newUnmaskedContext = getMaskedContext(workInProgress, newUnmaskedContext);
-      var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
-      (ctor =
-        "function" === typeof getDerivedStateFromProps ||
-        "function" === typeof instance.getSnapshotBeforeUpdate) ||
-        ("function" !== typeof instance.UNSAFE_componentWillReceiveProps &&
-          "function" !== typeof instance.componentWillReceiveProps) ||
-        ((oldProps !== newProps || oldContext !== newUnmaskedContext) &&
-          callComponentWillReceiveProps(
-            workInProgress,
-            instance,
-            newProps,
-            newUnmaskedContext
-          ));
-      hasForceUpdate = !1;
-      oldContext = workInProgress.memoizedState;
-      var newState = (instance.state = oldContext),
-        updateQueue = workInProgress.updateQueue;
-      null !== updateQueue &&
-        (processUpdateQueue(
-          workInProgress,
-          updateQueue,
-          newProps,
-          instance,
-          renderExpirationTime
-        ),
-        (newState = workInProgress.memoizedState));
-      if (
-        oldProps === newProps &&
-        oldContext === newState &&
-        !hasContextChanged() &&
-        !hasForceUpdate
-      )
-        return (
-          "function" !== typeof instance.componentDidUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 4),
-          "function" !== typeof instance.getSnapshotBeforeUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 256),
-          !1
-        );
-      "function" === typeof getDerivedStateFromProps &&
-        (applyDerivedStateFromProps(
-          workInProgress,
-          getDerivedStateFromProps,
-          newProps
-        ),
-        (newState = workInProgress.memoizedState));
-      (renderExpirationTime =
-        hasForceUpdate ||
-        checkShouldComponentUpdate(
-          workInProgress,
-          oldProps,
-          newProps,
-          oldContext,
-          newState,
-          newUnmaskedContext
-        ))
-        ? (ctor ||
-            ("function" !== typeof instance.UNSAFE_componentWillUpdate &&
-              "function" !== typeof instance.componentWillUpdate) ||
-            ("function" === typeof instance.componentWillUpdate &&
-              instance.componentWillUpdate(
-                newProps,
-                newState,
-                newUnmaskedContext
-              ),
-            "function" === typeof instance.UNSAFE_componentWillUpdate &&
-              instance.UNSAFE_componentWillUpdate(
-                newProps,
-                newState,
-                newUnmaskedContext
-              )),
-          "function" === typeof instance.componentDidUpdate &&
-            (workInProgress.effectTag |= 4),
-          "function" === typeof instance.getSnapshotBeforeUpdate &&
-            (workInProgress.effectTag |= 256))
-        : ("function" !== typeof instance.componentDidUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 4),
-          "function" !== typeof instance.getSnapshotBeforeUpdate ||
-            (oldProps === current.memoizedProps &&
-              oldContext === current.memoizedState) ||
-            (workInProgress.effectTag |= 256),
-          (workInProgress.memoizedProps = newProps),
-          (workInProgress.memoizedState = newState));
-      instance.props = newProps;
-      instance.state = newState;
-      instance.context = newUnmaskedContext;
-      return renderExpirationTime;
-    }
-  };
+    ),
+    (instance.state = workInProgress.memoizedState));
+  unmaskedContext = workInProgress.type.getDerivedStateFromProps;
+  "function" === typeof unmaskedContext &&
+    (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+    (instance.state = workInProgress.memoizedState));
+  "function" === typeof ctor.getDerivedStateFromProps ||
+    "function" === typeof instance.getSnapshotBeforeUpdate ||
+    ("function" !== typeof instance.UNSAFE_componentWillMount &&
+      "function" !== typeof instance.componentWillMount) ||
+    ((ctor = instance.state),
+    "function" === typeof instance.componentWillMount &&
+      instance.componentWillMount(),
+    "function" === typeof instance.UNSAFE_componentWillMount &&
+      instance.UNSAFE_componentWillMount(),
+    ctor !== instance.state &&
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null),
+    (unmaskedContext = workInProgress.updateQueue),
+    null !== unmaskedContext &&
+      (processUpdateQueue(
+        workInProgress,
+        unmaskedContext,
+        props,
+        instance,
+        renderExpirationTime
+      ),
+      (instance.state = workInProgress.memoizedState)));
+  "function" === typeof instance.componentDidMount &&
+    (workInProgress.effectTag |= 4);
 }
 var isArray$1 = Array.isArray;
 function coerceRef(returnFiber, current, element) {
@@ -2178,6 +2505,7 @@ function coerceRef(returnFiber, current, element) {
       if (
         null !== current &&
         null !== current.ref &&
+        "function" === typeof current.ref &&
         current.ref._stringRef === stringRef
       )
         return current.ref;
@@ -2673,27 +3001,35 @@ function ChildReconciler(shouldTrackSideEffects) {
     return iteratorFn;
   }
   return function(returnFiber, currentFirstChild, newChild, expirationTime) {
-    "object" === typeof newChild &&
+    var isUnkeyedTopLevelFragment =
+      "object" === typeof newChild &&
       null !== newChild &&
       newChild.type === REACT_FRAGMENT_TYPE &&
-      null === newChild.key &&
-      (newChild = newChild.props.children);
+      null === newChild.key;
+    isUnkeyedTopLevelFragment && (newChild = newChild.props.children);
     var isObject = "object" === typeof newChild && null !== newChild;
     if (isObject)
       switch (newChild.$$typeof) {
         case REACT_ELEMENT_TYPE:
           a: {
-            var key = newChild.key;
-            for (isObject = currentFirstChild; null !== isObject; ) {
-              if (isObject.key === key)
+            isObject = newChild.key;
+            for (
+              isUnkeyedTopLevelFragment = currentFirstChild;
+              null !== isUnkeyedTopLevelFragment;
+
+            ) {
+              if (isUnkeyedTopLevelFragment.key === isObject)
                 if (
-                  10 === isObject.tag
+                  10 === isUnkeyedTopLevelFragment.tag
                     ? newChild.type === REACT_FRAGMENT_TYPE
-                    : isObject.type === newChild.type
+                    : isUnkeyedTopLevelFragment.type === newChild.type
                 ) {
-                  deleteRemainingChildren(returnFiber, isObject.sibling);
+                  deleteRemainingChildren(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment.sibling
+                  );
                   currentFirstChild = useFiber(
-                    isObject,
+                    isUnkeyedTopLevelFragment,
                     newChild.type === REACT_FRAGMENT_TYPE
                       ? newChild.props.children
                       : newChild.props,
@@ -2701,18 +3037,21 @@ function ChildReconciler(shouldTrackSideEffects) {
                   );
                   currentFirstChild.ref = coerceRef(
                     returnFiber,
-                    isObject,
+                    isUnkeyedTopLevelFragment,
                     newChild
                   );
                   currentFirstChild.return = returnFiber;
                   returnFiber = currentFirstChild;
                   break a;
                 } else {
-                  deleteRemainingChildren(returnFiber, isObject);
+                  deleteRemainingChildren(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment
+                  );
                   break;
                 }
-              else deleteChild(returnFiber, isObject);
-              isObject = isObject.sibling;
+              else deleteChild(returnFiber, isUnkeyedTopLevelFragment);
+              isUnkeyedTopLevelFragment = isUnkeyedTopLevelFragment.sibling;
             }
             newChild.type === REACT_FRAGMENT_TYPE
               ? ((currentFirstChild = createFiberFromFragment(
@@ -2739,8 +3078,12 @@ function ChildReconciler(shouldTrackSideEffects) {
           return placeSingleChild(returnFiber);
         case REACT_PORTAL_TYPE:
           a: {
-            for (isObject = newChild.key; null !== currentFirstChild; ) {
-              if (currentFirstChild.key === isObject)
+            for (
+              isUnkeyedTopLevelFragment = newChild.key;
+              null !== currentFirstChild;
+
+            ) {
+              if (currentFirstChild.key === isUnkeyedTopLevelFragment)
                 if (
                   4 === currentFirstChild.tag &&
                   currentFirstChild.stateNode.containerInfo ===
@@ -2814,7 +3157,7 @@ function ChildReconciler(shouldTrackSideEffects) {
         expirationTime
       );
     isObject && throwOnInvalidObjectType(returnFiber, newChild);
-    if ("undefined" === typeof newChild)
+    if ("undefined" === typeof newChild && !isUnkeyedTopLevelFragment)
       switch (returnFiber.tag) {
         case 2:
         case 1:
@@ -2829,184 +3172,234 @@ function ChildReconciler(shouldTrackSideEffects) {
   };
 }
 var reconcileChildFibers = ChildReconciler(!0),
-  mountChildFibers = ChildReconciler(!1);
-function ReactFiberBeginWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  profilerTimer,
-  recalculateCurrentTime
-) {
-  function reconcileChildren(current, workInProgress, nextChildren) {
-    reconcileChildrenAtExpirationTime(
-      current,
-      workInProgress,
-      nextChildren,
-      workInProgress.expirationTime
-    );
-  }
-  function reconcileChildrenAtExpirationTime(
-    current,
-    workInProgress,
-    nextChildren,
-    renderExpirationTime
-  ) {
-    workInProgress.child =
-      null === current
-        ? mountChildFibers(
-            workInProgress,
-            null,
-            nextChildren,
-            renderExpirationTime
-          )
-        : reconcileChildFibers(
-            workInProgress,
-            current.child,
-            nextChildren,
-            renderExpirationTime
-          );
+  mountChildFibers = ChildReconciler(!1),
+  hydrationParentFiber = null,
+  nextHydratableInstance = null,
+  isHydrating = !1;
+function tryHydrate(fiber, nextInstance) {
+  switch (fiber.tag) {
+    case 5:
+      return (
+        (nextInstance = shim$1(nextInstance, fiber.type, fiber.pendingProps)),
+        null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+      );
+    case 6:
+      return (
+        (nextInstance = shim$1(nextInstance, fiber.pendingProps)),
+        null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+      );
+    default:
+      return !1;
   }
-  function markRef(current, workInProgress) {
-    var ref = workInProgress.ref;
-    if (
-      (null === current && null !== ref) ||
-      (null !== current && current.ref !== ref)
-    )
-      workInProgress.effectTag |= 128;
+}
+function tryToClaimNextHydratableInstance(fiber$jscomp$0) {
+  if (isHydrating) {
+    var nextInstance = nextHydratableInstance;
+    if (nextInstance) {
+      var firstAttemptedInstance = nextInstance;
+      if (!tryHydrate(fiber$jscomp$0, nextInstance)) {
+        nextInstance = shim$1(firstAttemptedInstance);
+        if (!nextInstance || !tryHydrate(fiber$jscomp$0, nextInstance)) {
+          fiber$jscomp$0.effectTag |= 2;
+          isHydrating = !1;
+          hydrationParentFiber = fiber$jscomp$0;
+          return;
+        }
+        var returnFiber = hydrationParentFiber,
+          fiber = new FiberNode(5, null, null, 0);
+        fiber.type = "DELETED";
+        fiber.stateNode = firstAttemptedInstance;
+        fiber.return = returnFiber;
+        fiber.effectTag = 8;
+        null !== returnFiber.lastEffect
+          ? ((returnFiber.lastEffect.nextEffect = fiber),
+            (returnFiber.lastEffect = fiber))
+          : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
+      }
+      hydrationParentFiber = fiber$jscomp$0;
+      nextHydratableInstance = shim$1(nextInstance);
+    } else
+      (fiber$jscomp$0.effectTag |= 2),
+        (isHydrating = !1),
+        (hydrationParentFiber = fiber$jscomp$0);
   }
-  function finishClassComponent(
+}
+function reconcileChildren(current, workInProgress, nextChildren) {
+  reconcileChildrenAtExpirationTime(
     current,
     workInProgress,
-    shouldUpdate,
-    hasContext,
-    renderExpirationTime
-  ) {
-    markRef(current, workInProgress);
-    var didCaptureError = 0 !== (workInProgress.effectTag & 64);
-    if (!shouldUpdate && !didCaptureError)
-      return (
-        hasContext && invalidateContextProvider(workInProgress, !1),
-        bailoutOnAlreadyFinishedWork(current, workInProgress)
-      );
-    shouldUpdate = workInProgress.stateNode;
-    ReactCurrentOwner.current = workInProgress;
-    var nextChildren = didCaptureError ? null : shouldUpdate.render();
-    workInProgress.effectTag |= 1;
-    didCaptureError &&
-      (reconcileChildrenAtExpirationTime(
-        current,
-        workInProgress,
-        null,
-        renderExpirationTime
-      ),
-      (workInProgress.child = null));
-    reconcileChildrenAtExpirationTime(
+    nextChildren,
+    workInProgress.expirationTime
+  );
+}
+function reconcileChildrenAtExpirationTime(
+  current,
+  workInProgress,
+  nextChildren,
+  renderExpirationTime
+) {
+  workInProgress.child =
+    null === current
+      ? mountChildFibers(
+          workInProgress,
+          null,
+          nextChildren,
+          renderExpirationTime
+        )
+      : reconcileChildFibers(
+          workInProgress,
+          current.child,
+          nextChildren,
+          renderExpirationTime
+        );
+}
+function markRef(current, workInProgress) {
+  var ref = workInProgress.ref;
+  if (
+    (null === current && null !== ref) ||
+    (null !== current && current.ref !== ref)
+  )
+    workInProgress.effectTag |= 128;
+}
+function finishClassComponent(
+  current,
+  workInProgress,
+  shouldUpdate,
+  hasContext,
+  renderExpirationTime
+) {
+  markRef(current, workInProgress);
+  var didCaptureError = 0 !== (workInProgress.effectTag & 64);
+  if (!shouldUpdate && !didCaptureError)
+    return (
+      hasContext && invalidateContextProvider(workInProgress, !1),
+      bailoutOnAlreadyFinishedWork(current, workInProgress)
+    );
+  shouldUpdate = workInProgress.stateNode;
+  ReactCurrentOwner.current = workInProgress;
+  var nextChildren = didCaptureError ? null : shouldUpdate.render();
+  workInProgress.effectTag |= 1;
+  didCaptureError &&
+    (reconcileChildrenAtExpirationTime(
       current,
       workInProgress,
-      nextChildren,
+      null,
       renderExpirationTime
-    );
-    workInProgress.memoizedState = shouldUpdate.state;
-    workInProgress.memoizedProps = shouldUpdate.props;
-    hasContext && invalidateContextProvider(workInProgress, !0);
-    return workInProgress.child;
-  }
-  function pushHostRootContext(workInProgress) {
-    var root = workInProgress.stateNode;
-    root.pendingContext
-      ? pushTopLevelContextObject(
-          workInProgress,
-          root.pendingContext,
-          root.pendingContext !== root.context
-        )
-      : root.context &&
-        pushTopLevelContextObject(workInProgress, root.context, !1);
-    pushHostContainer(workInProgress, root.containerInfo);
-  }
-  function propagateContextChange(
+    ),
+    (workInProgress.child = null));
+  reconcileChildrenAtExpirationTime(
+    current,
     workInProgress,
-    context,
-    changedBits,
+    nextChildren,
     renderExpirationTime
-  ) {
-    var fiber = workInProgress.child;
-    null !== fiber && (fiber.return = workInProgress);
-    for (; null !== fiber; ) {
-      switch (fiber.tag) {
-        case 12:
-          var nextFiber = fiber.stateNode | 0;
-          if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
-            for (nextFiber = fiber; null !== nextFiber; ) {
-              var alternate = nextFiber.alternate;
-              if (
-                0 === nextFiber.expirationTime ||
-                nextFiber.expirationTime > renderExpirationTime
-              )
-                (nextFiber.expirationTime = renderExpirationTime),
-                  null !== alternate &&
-                    (0 === alternate.expirationTime ||
-                      alternate.expirationTime > renderExpirationTime) &&
-                    (alternate.expirationTime = renderExpirationTime);
-              else if (
+  );
+  workInProgress.memoizedState = shouldUpdate.state;
+  workInProgress.memoizedProps = shouldUpdate.props;
+  hasContext && invalidateContextProvider(workInProgress, !0);
+  return workInProgress.child;
+}
+function pushHostRootContext(workInProgress) {
+  var root = workInProgress.stateNode;
+  root.pendingContext
+    ? pushTopLevelContextObject(
+        workInProgress,
+        root.pendingContext,
+        root.pendingContext !== root.context
+      )
+    : root.context &&
+      pushTopLevelContextObject(workInProgress, root.context, !1);
+  pushHostContainer(workInProgress, root.containerInfo);
+}
+function propagateContextChange(
+  workInProgress,
+  context,
+  changedBits,
+  renderExpirationTime
+) {
+  var fiber = workInProgress.child;
+  null !== fiber && (fiber.return = workInProgress);
+  for (; null !== fiber; ) {
+    switch (fiber.tag) {
+      case 12:
+        var nextFiber = fiber.stateNode | 0;
+        if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
+          for (nextFiber = fiber; null !== nextFiber; ) {
+            var alternate = nextFiber.alternate;
+            if (
+              0 === nextFiber.expirationTime ||
+              nextFiber.expirationTime > renderExpirationTime
+            )
+              (nextFiber.expirationTime = renderExpirationTime),
                 null !== alternate &&
-                (0 === alternate.expirationTime ||
-                  alternate.expirationTime > renderExpirationTime)
-              )
-                alternate.expirationTime = renderExpirationTime;
-              else break;
-              nextFiber = nextFiber.return;
-            }
-            nextFiber = null;
-          } else nextFiber = fiber.child;
+                  (0 === alternate.expirationTime ||
+                    alternate.expirationTime > renderExpirationTime) &&
+                  (alternate.expirationTime = renderExpirationTime);
+            else if (
+              null !== alternate &&
+              (0 === alternate.expirationTime ||
+                alternate.expirationTime > renderExpirationTime)
+            )
+              alternate.expirationTime = renderExpirationTime;
+            else break;
+            nextFiber = nextFiber.return;
+          }
+          nextFiber = null;
+        } else nextFiber = fiber.child;
+        break;
+      case 13:
+        nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+        break;
+      default:
+        nextFiber = fiber.child;
+    }
+    if (null !== nextFiber) nextFiber.return = fiber;
+    else
+      for (nextFiber = fiber; null !== nextFiber; ) {
+        if (nextFiber === workInProgress) {
+          nextFiber = null;
           break;
-        case 13:
-          nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+        }
+        fiber = nextFiber.sibling;
+        if (null !== fiber) {
+          fiber.return = nextFiber.return;
+          nextFiber = fiber;
           break;
-        default:
-          nextFiber = fiber.child;
-      }
-      if (null !== nextFiber) nextFiber.return = fiber;
-      else
-        for (nextFiber = fiber; null !== nextFiber; ) {
-          if (nextFiber === workInProgress) {
-            nextFiber = null;
-            break;
-          }
-          fiber = nextFiber.sibling;
-          if (null !== fiber) {
-            fiber.return = nextFiber.return;
-            nextFiber = fiber;
-            break;
-          }
-          nextFiber = nextFiber.return;
         }
-      fiber = nextFiber;
-    }
+        nextFiber = nextFiber.return;
+      }
+    fiber = nextFiber;
   }
-  function updateContextProvider(
-    current,
-    workInProgress,
-    renderExpirationTime
-  ) {
-    var context = workInProgress.type._context,
-      newProps = workInProgress.pendingProps,
-      oldProps = workInProgress.memoizedProps,
-      canBailOnProps = !0;
-    if (hasLegacyContextChanged()) canBailOnProps = !1;
-    else if (oldProps === newProps)
+}
+function updateContextProvider(current, workInProgress, renderExpirationTime) {
+  var context = workInProgress.type._context,
+    newProps = workInProgress.pendingProps,
+    oldProps = workInProgress.memoizedProps,
+    canBailOnProps = !0;
+  if (didPerformWorkStackCursor.current) canBailOnProps = !1;
+  else if (oldProps === newProps)
+    return (
+      (workInProgress.stateNode = 0),
+      pushProvider(workInProgress),
+      bailoutOnAlreadyFinishedWork(current, workInProgress)
+    );
+  var newValue = newProps.value;
+  workInProgress.memoizedProps = newProps;
+  if (null === oldProps) newValue = 1073741823;
+  else if (oldProps.value === newProps.value) {
+    if (oldProps.children === newProps.children && canBailOnProps)
       return (
         (workInProgress.stateNode = 0),
         pushProvider(workInProgress),
         bailoutOnAlreadyFinishedWork(current, workInProgress)
       );
-    var newValue = newProps.value;
-    workInProgress.memoizedProps = newProps;
-    if (null === oldProps) newValue = 1073741823;
-    else if (oldProps.value === newProps.value) {
+    newValue = 0;
+  } else {
+    var oldValue = oldProps.value;
+    if (
+      (oldValue === newValue &&
+        (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
+      (oldValue !== oldValue && newValue !== newValue)
+    ) {
       if (oldProps.children === newProps.children && canBailOnProps)
         return (
           (workInProgress.stateNode = 0),
@@ -3014,684 +3407,710 @@ function ReactFiberBeginWork(
           bailoutOnAlreadyFinishedWork(current, workInProgress)
         );
       newValue = 0;
-    } else {
-      var oldValue = oldProps.value;
-      if (
-        (oldValue === newValue &&
-          (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
-        (oldValue !== oldValue && newValue !== newValue)
-      ) {
-        if (oldProps.children === newProps.children && canBailOnProps)
-          return (
-            (workInProgress.stateNode = 0),
-            pushProvider(workInProgress),
-            bailoutOnAlreadyFinishedWork(current, workInProgress)
-          );
-        newValue = 0;
-      } else if (
-        ((newValue =
-          "function" === typeof context._calculateChangedBits
-            ? context._calculateChangedBits(oldValue, newValue)
-            : 1073741823),
-        (newValue |= 0),
-        0 === newValue)
-      ) {
-        if (oldProps.children === newProps.children && canBailOnProps)
-          return (
-            (workInProgress.stateNode = 0),
-            pushProvider(workInProgress),
-            bailoutOnAlreadyFinishedWork(current, workInProgress)
-          );
-      } else
-        propagateContextChange(
+    } else if (
+      ((newValue =
+        "function" === typeof context._calculateChangedBits
+          ? context._calculateChangedBits(oldValue, newValue)
+          : 1073741823),
+      (newValue |= 0),
+      0 === newValue)
+    ) {
+      if (oldProps.children === newProps.children && canBailOnProps)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+    } else
+      propagateContextChange(
+        workInProgress,
+        context,
+        newValue,
+        renderExpirationTime
+      );
+  }
+  workInProgress.stateNode = newValue;
+  pushProvider(workInProgress);
+  reconcileChildren(current, workInProgress, newProps.children);
+  return workInProgress.child;
+}
+function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+  invariant(
+    null === current || workInProgress.child === current.child,
+    "Resuming work not yet implemented."
+  );
+  if (null !== workInProgress.child) {
+    current = workInProgress.child;
+    var newChild = createWorkInProgress(
+      current,
+      current.pendingProps,
+      current.expirationTime
+    );
+    workInProgress.child = newChild;
+    for (newChild.return = workInProgress; null !== current.sibling; )
+      (current = current.sibling),
+        (newChild = newChild.sibling = createWorkInProgress(
+          current,
+          current.pendingProps,
+          current.expirationTime
+        )),
+        (newChild.return = workInProgress);
+    newChild.sibling = null;
+  }
+  return workInProgress.child;
+}
+function beginWork(current, workInProgress, renderExpirationTime) {
+  if (
+    0 === workInProgress.expirationTime ||
+    workInProgress.expirationTime > renderExpirationTime
+  ) {
+    switch (workInProgress.tag) {
+      case 3:
+        pushHostRootContext(workInProgress);
+        break;
+      case 2:
+        pushContextProvider(workInProgress);
+        break;
+      case 4:
+        pushHostContainer(
           workInProgress,
-          context,
-          newValue,
-          renderExpirationTime
+          workInProgress.stateNode.containerInfo
         );
+        break;
+      case 13:
+        pushProvider(workInProgress);
     }
-    workInProgress.stateNode = newValue;
-    pushProvider(workInProgress);
-    reconcileChildren(current, workInProgress, newProps.children);
-    return workInProgress.child;
+    return null;
   }
-  function bailoutOnAlreadyFinishedWork(current, workInProgress) {
-    invariant(
-      null === current || workInProgress.child === current.child,
-      "Resuming work not yet implemented."
-    );
-    if (null !== workInProgress.child) {
-      current = workInProgress.child;
-      var newChild = createWorkInProgress(
-        current,
-        current.pendingProps,
-        current.expirationTime
+  switch (workInProgress.tag) {
+    case 0:
+      invariant(
+        null === current,
+        "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
       );
-      workInProgress.child = newChild;
-      for (newChild.return = workInProgress; null !== current.sibling; )
-        (current = current.sibling),
-          (newChild = newChild.sibling = createWorkInProgress(
+      var fn = workInProgress.type,
+        props = workInProgress.pendingProps,
+        unmaskedContext = getUnmaskedContext(workInProgress);
+      unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
+      fn = fn(props, unmaskedContext);
+      workInProgress.effectTag |= 1;
+      "object" === typeof fn &&
+      null !== fn &&
+      "function" === typeof fn.render &&
+      void 0 === fn.$$typeof
+        ? ((unmaskedContext = workInProgress.type),
+          (workInProgress.tag = 2),
+          (workInProgress.memoizedState =
+            null !== fn.state && void 0 !== fn.state ? fn.state : null),
+          (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
+          "function" === typeof unmaskedContext &&
+            applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+          (props = pushContextProvider(workInProgress)),
+          (fn.updater = classComponentUpdater),
+          (workInProgress.stateNode = fn),
+          (fn._reactInternalFiber = workInProgress),
+          mountClassInstance(workInProgress, renderExpirationTime),
+          (current = finishClassComponent(
             current,
-            current.pendingProps,
-            current.expirationTime
-          )),
-          (newChild.return = workInProgress);
-      newChild.sibling = null;
-    }
-    return workInProgress.child;
-  }
-  var shouldSetTextContent = config.shouldSetTextContent,
-    shouldDeprioritizeSubtree = config.shouldDeprioritizeSubtree,
-    pushHostContext = hostContext.pushHostContext,
-    pushHostContainer = hostContext.pushHostContainer,
-    pushProvider = newContext.pushProvider,
-    getContextCurrentValue = newContext.getContextCurrentValue,
-    getContextChangedBits = newContext.getContextChangedBits,
-    getMaskedContext = legacyContext.getMaskedContext,
-    getUnmaskedContext = legacyContext.getUnmaskedContext,
-    hasLegacyContextChanged = legacyContext.hasContextChanged,
-    pushLegacyContextProvider = legacyContext.pushContextProvider,
-    pushTopLevelContextObject = legacyContext.pushTopLevelContextObject,
-    invalidateContextProvider = legacyContext.invalidateContextProvider,
-    enterHydrationState = hydrationContext.enterHydrationState,
-    resetHydrationState = hydrationContext.resetHydrationState,
-    tryToClaimNextHydratableInstance =
-      hydrationContext.tryToClaimNextHydratableInstance;
-  config = ReactFiberClassComponent(
-    legacyContext,
-    scheduleWork,
-    computeExpirationForFiber,
-    function(workInProgress, nextProps) {
-      workInProgress.memoizedProps = nextProps;
-    },
-    function(workInProgress, nextState) {
-      workInProgress.memoizedState = nextState;
-    },
-    recalculateCurrentTime
-  );
-  var adoptClassInstance = config.adoptClassInstance,
-    constructClassInstance = config.constructClassInstance,
-    mountClassInstance = config.mountClassInstance,
-    resumeMountClassInstance = config.resumeMountClassInstance,
-    updateClassInstance = config.updateClassInstance;
-  return {
-    beginWork: function(current, workInProgress, renderExpirationTime) {
-      if (
-        0 === workInProgress.expirationTime ||
-        workInProgress.expirationTime > renderExpirationTime
-      ) {
-        switch (workInProgress.tag) {
-          case 3:
-            pushHostRootContext(workInProgress);
-            break;
-          case 2:
-            pushLegacyContextProvider(workInProgress);
-            break;
-          case 4:
-            pushHostContainer(
+            workInProgress,
+            !0,
+            props,
+            renderExpirationTime
+          )))
+        : ((workInProgress.tag = 1),
+          reconcileChildren(current, workInProgress, fn),
+          (workInProgress.memoizedProps = props),
+          (current = workInProgress.child));
+      return current;
+    case 1:
+      return (
+        (props = workInProgress.type),
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime
+          ? ((fn = getUnmaskedContext(workInProgress)),
+            (fn = getMaskedContext(workInProgress, fn)),
+            (props = props(renderExpirationTime, fn)),
+            (workInProgress.effectTag |= 1),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 2:
+      props = pushContextProvider(workInProgress);
+      if (null === current)
+        if (null === workInProgress.stateNode) {
+          var props$jscomp$0 = workInProgress.pendingProps,
+            ctor = workInProgress.type;
+          fn = getUnmaskedContext(workInProgress);
+          var needsContext =
+            2 === workInProgress.tag &&
+            null != workInProgress.type.contextTypes;
+          unmaskedContext = needsContext
+            ? getMaskedContext(workInProgress, fn)
+            : emptyObject;
+          props$jscomp$0 = new ctor(props$jscomp$0, unmaskedContext);
+          workInProgress.memoizedState =
+            null !== props$jscomp$0.state && void 0 !== props$jscomp$0.state
+              ? props$jscomp$0.state
+              : null;
+          props$jscomp$0.updater = classComponentUpdater;
+          workInProgress.stateNode = props$jscomp$0;
+          props$jscomp$0._reactInternalFiber = workInProgress;
+          needsContext &&
+            ((needsContext = workInProgress.stateNode),
+            (needsContext.__reactInternalMemoizedUnmaskedChildContext = fn),
+            (needsContext.__reactInternalMemoizedMaskedChildContext = unmaskedContext));
+          mountClassInstance(workInProgress, renderExpirationTime);
+          fn = !0;
+        } else {
+          ctor = workInProgress.type;
+          fn = workInProgress.stateNode;
+          needsContext = workInProgress.memoizedProps;
+          unmaskedContext = workInProgress.pendingProps;
+          fn.props = needsContext;
+          var oldContext = fn.context;
+          props$jscomp$0 = getUnmaskedContext(workInProgress);
+          props$jscomp$0 = getMaskedContext(workInProgress, props$jscomp$0);
+          var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
+          (ctor =
+            "function" === typeof getDerivedStateFromProps ||
+            "function" === typeof fn.getSnapshotBeforeUpdate) ||
+            ("function" !== typeof fn.UNSAFE_componentWillReceiveProps &&
+              "function" !== typeof fn.componentWillReceiveProps) ||
+            ((needsContext !== unmaskedContext ||
+              oldContext !== props$jscomp$0) &&
+              callComponentWillReceiveProps(
+                workInProgress,
+                fn,
+                unmaskedContext,
+                props$jscomp$0
+              ));
+          hasForceUpdate = !1;
+          var oldState = workInProgress.memoizedState;
+          oldContext = fn.state = oldState;
+          var updateQueue = workInProgress.updateQueue;
+          null !== updateQueue &&
+            (processUpdateQueue(
               workInProgress,
-              workInProgress.stateNode.containerInfo
-            );
-            break;
-          case 13:
-            pushProvider(workInProgress);
-        }
-        return null;
-      }
-      switch (workInProgress.tag) {
-        case 0:
-          invariant(
-            null === current,
-            "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
-          );
-          var fn = workInProgress.type,
-            props = workInProgress.pendingProps,
-            unmaskedContext = getUnmaskedContext(workInProgress);
-          unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
-          fn = fn(props, unmaskedContext);
-          workInProgress.effectTag |= 1;
-          "object" === typeof fn &&
-          null !== fn &&
-          "function" === typeof fn.render &&
-          void 0 === fn.$$typeof
-            ? ((unmaskedContext = workInProgress.type),
-              (workInProgress.tag = 2),
-              (workInProgress.memoizedState =
-                null !== fn.state && void 0 !== fn.state ? fn.state : null),
-              (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
-              "function" === typeof unmaskedContext &&
-                applyDerivedStateFromProps(
+              updateQueue,
+              unmaskedContext,
+              fn,
+              renderExpirationTime
+            ),
+            (oldContext = workInProgress.memoizedState));
+          needsContext !== unmaskedContext ||
+          oldState !== oldContext ||
+          didPerformWorkStackCursor.current ||
+          hasForceUpdate
+            ? ("function" === typeof getDerivedStateFromProps &&
+                (applyDerivedStateFromProps(
                   workInProgress,
-                  unmaskedContext,
-                  props
+                  getDerivedStateFromProps,
+                  unmaskedContext
                 ),
-              (props = pushLegacyContextProvider(workInProgress)),
-              adoptClassInstance(workInProgress, fn),
-              mountClassInstance(workInProgress, renderExpirationTime),
-              (current = finishClassComponent(
-                current,
-                workInProgress,
-                !0,
-                props,
-                renderExpirationTime
-              )))
-            : ((workInProgress.tag = 1),
-              reconcileChildren(current, workInProgress, fn),
-              (workInProgress.memoizedProps = props),
-              (current = workInProgress.child));
-          return current;
-        case 1:
-          return (
-            (props = workInProgress.type),
-            (renderExpirationTime = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime
-              ? ((fn = getUnmaskedContext(workInProgress)),
-                (fn = getMaskedContext(workInProgress, fn)),
-                (props = props(renderExpirationTime, fn)),
-                (workInProgress.effectTag |= 1),
-                reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 2:
-          return (
-            (props = pushLegacyContextProvider(workInProgress)),
-            null === current
-              ? null === workInProgress.stateNode
-                ? (constructClassInstance(
-                    workInProgress,
-                    workInProgress.pendingProps,
-                    renderExpirationTime
-                  ),
-                  mountClassInstance(workInProgress, renderExpirationTime),
-                  (fn = !0))
-                : (fn = resumeMountClassInstance(
-                    workInProgress,
-                    renderExpirationTime
-                  ))
-              : (fn = updateClassInstance(
-                  current,
+                (oldContext = workInProgress.memoizedState)),
+              (needsContext =
+                hasForceUpdate ||
+                checkShouldComponentUpdate(
                   workInProgress,
-                  renderExpirationTime
-                )),
-            finishClassComponent(
-              current,
+                  needsContext,
+                  unmaskedContext,
+                  oldState,
+                  oldContext,
+                  props$jscomp$0
+                ))
+                ? (ctor ||
+                    ("function" !== typeof fn.UNSAFE_componentWillMount &&
+                      "function" !== typeof fn.componentWillMount) ||
+                    ("function" === typeof fn.componentWillMount &&
+                      fn.componentWillMount(),
+                    "function" === typeof fn.UNSAFE_componentWillMount &&
+                      fn.UNSAFE_componentWillMount()),
+                  "function" === typeof fn.componentDidMount &&
+                    (workInProgress.effectTag |= 4))
+                : ("function" === typeof fn.componentDidMount &&
+                    (workInProgress.effectTag |= 4),
+                  (workInProgress.memoizedProps = unmaskedContext),
+                  (workInProgress.memoizedState = oldContext)),
+              (fn.props = unmaskedContext),
+              (fn.state = oldContext),
+              (fn.context = props$jscomp$0),
+              (fn = needsContext))
+            : ("function" === typeof fn.componentDidMount &&
+                (workInProgress.effectTag |= 4),
+              (fn = !1));
+        }
+      else
+        (ctor = workInProgress.type),
+          (fn = workInProgress.stateNode),
+          (unmaskedContext = workInProgress.memoizedProps),
+          (needsContext = workInProgress.pendingProps),
+          (fn.props = unmaskedContext),
+          (oldContext = fn.context),
+          (props$jscomp$0 = getUnmaskedContext(workInProgress)),
+          (props$jscomp$0 = getMaskedContext(workInProgress, props$jscomp$0)),
+          (getDerivedStateFromProps = ctor.getDerivedStateFromProps),
+          (ctor =
+            "function" === typeof getDerivedStateFromProps ||
+            "function" === typeof fn.getSnapshotBeforeUpdate) ||
+            ("function" !== typeof fn.UNSAFE_componentWillReceiveProps &&
+              "function" !== typeof fn.componentWillReceiveProps) ||
+            ((unmaskedContext !== needsContext ||
+              oldContext !== props$jscomp$0) &&
+              callComponentWillReceiveProps(
+                workInProgress,
+                fn,
+                needsContext,
+                props$jscomp$0
+              )),
+          (hasForceUpdate = !1),
+          (oldContext = workInProgress.memoizedState),
+          (oldState = fn.state = oldContext),
+          (updateQueue = workInProgress.updateQueue),
+          null !== updateQueue &&
+            (processUpdateQueue(
               workInProgress,
+              updateQueue,
+              needsContext,
               fn,
-              props,
               renderExpirationTime
-            )
-          );
-        case 3:
-          return (
-            pushHostRootContext(workInProgress),
-            (props = workInProgress.updateQueue),
-            null !== props
-              ? ((fn = workInProgress.memoizedState),
-                (fn = null !== fn ? fn.element : null),
-                processUpdateQueue(
+            ),
+            (oldState = workInProgress.memoizedState)),
+          unmaskedContext !== needsContext ||
+          oldContext !== oldState ||
+          didPerformWorkStackCursor.current ||
+          hasForceUpdate
+            ? ("function" === typeof getDerivedStateFromProps &&
+                (applyDerivedStateFromProps(
                   workInProgress,
-                  props,
-                  workInProgress.pendingProps,
-                  null,
-                  renderExpirationTime
+                  getDerivedStateFromProps,
+                  needsContext
                 ),
-                (props = workInProgress.memoizedState.element),
-                props === fn
-                  ? (resetHydrationState(),
-                    (current = bailoutOnAlreadyFinishedWork(
-                      current,
-                      workInProgress
-                    )))
-                  : ((fn = workInProgress.stateNode),
-                    (null === current || null === current.child) &&
-                    fn.hydrate &&
-                    enterHydrationState(workInProgress)
-                      ? ((workInProgress.effectTag |= 2),
-                        (workInProgress.child = mountChildFibers(
-                          workInProgress,
-                          null,
-                          props,
-                          renderExpirationTime
-                        )))
-                      : (resetHydrationState(),
-                        reconcileChildren(current, workInProgress, props)),
-                    (current = workInProgress.child)))
-              : (resetHydrationState(),
-                (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                ))),
-            current
-          );
-        case 5:
-          a: {
-            pushHostContext(workInProgress);
-            null === current &&
-              tryToClaimNextHydratableInstance(workInProgress);
-            props = workInProgress.type;
-            var memoizedProps = workInProgress.memoizedProps;
-            fn = workInProgress.pendingProps;
-            unmaskedContext = null !== current ? current.memoizedProps : null;
-            if (!hasLegacyContextChanged() && memoizedProps === fn) {
-              if (
-                (memoizedProps =
-                  workInProgress.mode & 1 &&
-                  shouldDeprioritizeSubtree(props, fn))
-              )
-                workInProgress.expirationTime = 1073741823;
-              if (!memoizedProps || 1073741823 !== renderExpirationTime) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-            }
-            memoizedProps = fn.children;
-            shouldSetTextContent(props, fn)
-              ? (memoizedProps = null)
-              : unmaskedContext &&
-                shouldSetTextContent(props, unmaskedContext) &&
-                (workInProgress.effectTag |= 16);
-            markRef(current, workInProgress);
-            1073741823 !== renderExpirationTime &&
-            workInProgress.mode & 1 &&
-            shouldDeprioritizeSubtree(props, fn)
-              ? ((workInProgress.expirationTime = 1073741823),
-                (workInProgress.memoizedProps = fn),
-                (current = null))
-              : (reconcileChildren(current, workInProgress, memoizedProps),
-                (workInProgress.memoizedProps = fn),
-                (current = workInProgress.child));
-          }
-          return current;
-        case 6:
-          return (
-            null === current &&
-              tryToClaimNextHydratableInstance(workInProgress),
-            (workInProgress.memoizedProps = workInProgress.pendingProps),
-            null
-          );
-        case 16:
-          return null;
-        case 4:
-          return (
-            pushHostContainer(
+                (oldState = workInProgress.memoizedState)),
+              (getDerivedStateFromProps =
+                hasForceUpdate ||
+                checkShouldComponentUpdate(
+                  workInProgress,
+                  unmaskedContext,
+                  needsContext,
+                  oldContext,
+                  oldState,
+                  props$jscomp$0
+                ))
+                ? (ctor ||
+                    ("function" !== typeof fn.UNSAFE_componentWillUpdate &&
+                      "function" !== typeof fn.componentWillUpdate) ||
+                    ("function" === typeof fn.componentWillUpdate &&
+                      fn.componentWillUpdate(
+                        needsContext,
+                        oldState,
+                        props$jscomp$0
+                      ),
+                    "function" === typeof fn.UNSAFE_componentWillUpdate &&
+                      fn.UNSAFE_componentWillUpdate(
+                        needsContext,
+                        oldState,
+                        props$jscomp$0
+                      )),
+                  "function" === typeof fn.componentDidUpdate &&
+                    (workInProgress.effectTag |= 4),
+                  "function" === typeof fn.getSnapshotBeforeUpdate &&
+                    (workInProgress.effectTag |= 256))
+                : ("function" !== typeof fn.componentDidUpdate ||
+                    (unmaskedContext === current.memoizedProps &&
+                      oldContext === current.memoizedState) ||
+                    (workInProgress.effectTag |= 4),
+                  "function" !== typeof fn.getSnapshotBeforeUpdate ||
+                    (unmaskedContext === current.memoizedProps &&
+                      oldContext === current.memoizedState) ||
+                    (workInProgress.effectTag |= 256),
+                  (workInProgress.memoizedProps = needsContext),
+                  (workInProgress.memoizedState = oldState)),
+              (fn.props = needsContext),
+              (fn.state = oldState),
+              (fn.context = props$jscomp$0),
+              (fn = getDerivedStateFromProps))
+            : ("function" !== typeof fn.componentDidUpdate ||
+                (unmaskedContext === current.memoizedProps &&
+                  oldContext === current.memoizedState) ||
+                (workInProgress.effectTag |= 4),
+              "function" !== typeof fn.getSnapshotBeforeUpdate ||
+                (unmaskedContext === current.memoizedProps &&
+                  oldContext === current.memoizedState) ||
+                (workInProgress.effectTag |= 256),
+              (fn = !1));
+      return finishClassComponent(
+        current,
+        workInProgress,
+        fn,
+        props,
+        renderExpirationTime
+      );
+    case 3:
+      return (
+        pushHostRootContext(workInProgress),
+        (props = workInProgress.updateQueue),
+        null !== props
+          ? ((fn = workInProgress.memoizedState),
+            (fn = null !== fn ? fn.element : null),
+            processUpdateQueue(
               workInProgress,
-              workInProgress.stateNode.containerInfo
+              props,
+              workInProgress.pendingProps,
+              null,
+              renderExpirationTime
             ),
-            (props = workInProgress.pendingProps),
-            hasLegacyContextChanged() || workInProgress.memoizedProps !== props
-              ? (null === current
-                  ? (workInProgress.child = reconcileChildFibers(
-                      workInProgress,
-                      null,
-                      props,
-                      renderExpirationTime
-                    ))
-                  : reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = props),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 14:
-          return (
-            (props = workInProgress.type.render),
-            (renderExpirationTime = workInProgress.pendingProps),
-            (fn = workInProgress.ref),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime ||
-            fn !== (null !== current ? current.ref : null)
-              ? ((props = props(renderExpirationTime, fn)),
-                reconcileChildren(current, workInProgress, props),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
+            (renderExpirationTime = workInProgress.memoizedState.element),
+            renderExpirationTime === fn
+              ? (current = bailoutOnAlreadyFinishedWork(
                   current,
                   workInProgress
-                )),
-            current
-          );
-        case 10:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps),
-            hasLegacyContextChanged() ||
-            workInProgress.memoizedProps !== renderExpirationTime
-              ? (reconcileChildren(
+                ))
+              : (reconcileChildren(
                   current,
                   workInProgress,
                   renderExpirationTime
                 ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 11:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps.children),
-            hasLegacyContextChanged() ||
-            (null !== renderExpirationTime &&
-              workInProgress.memoizedProps !== renderExpirationTime)
-              ? (reconcileChildren(
-                  current,
+                (current = workInProgress.child)))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 5:
+      return (
+        requiredContext(rootInstanceStackCursor.current),
+        (renderExpirationTime = requiredContext(contextStackCursor$1.current)),
+        (props = workInProgress.type),
+        (props =
+          "AndroidTextInput" === props ||
+          "RCTMultilineTextInputView" === props ||
+          "RCTSinglelineTextInputView" === props ||
+          "RCTText" === props ||
+          "RCTVirtualText" === props),
+        (props =
+          renderExpirationTime.isInAParentText !== props
+            ? { isInAParentText: props }
+            : renderExpirationTime),
+        renderExpirationTime !== props &&
+          (push(contextFiberStackCursor, workInProgress, workInProgress),
+          push(contextStackCursor$1, props, workInProgress)),
+        null === current && tryToClaimNextHydratableInstance(workInProgress),
+        (props = workInProgress.memoizedProps),
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current || props !== renderExpirationTime
+          ? ((props = renderExpirationTime.children),
+            markRef(current, workInProgress),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 6:
+      return (
+        null === current && tryToClaimNextHydratableInstance(workInProgress),
+        (workInProgress.memoizedProps = workInProgress.pendingProps),
+        null
+      );
+    case 16:
+      return null;
+    case 4:
+      return (
+        pushHostContainer(
+          workInProgress,
+          workInProgress.stateNode.containerInfo
+        ),
+        (props = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== props
+          ? (null === current
+              ? (workInProgress.child = reconcileChildFibers(
                   workInProgress,
+                  null,
+                  props,
                   renderExpirationTime
-                ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child))
-              : (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
-                )),
-            current
-          );
-        case 15:
-          return (
-            (renderExpirationTime = workInProgress.pendingProps),
-            workInProgress.memoizedProps === renderExpirationTime
-              ? (current = bailoutOnAlreadyFinishedWork(
-                  current,
-                  workInProgress
                 ))
-              : (reconcileChildren(
-                  current,
-                  workInProgress,
-                  renderExpirationTime.children
-                ),
-                (workInProgress.memoizedProps = renderExpirationTime),
-                (current = workInProgress.child)),
-            current
-          );
-        case 13:
-          return updateContextProvider(
-            current,
+              : reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = props),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 14:
+      return (
+        (props = workInProgress.type.render),
+        (renderExpirationTime = workInProgress.pendingProps),
+        (fn = workInProgress.ref),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime ||
+        fn !== (null !== current ? current.ref : null)
+          ? ((props = props(renderExpirationTime, fn)),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 10:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime
+          ? (reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 11:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps.children),
+        didPerformWorkStackCursor.current ||
+        (null !== renderExpirationTime &&
+          workInProgress.memoizedProps !== renderExpirationTime)
+          ? (reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 15:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps),
+        workInProgress.memoizedProps === renderExpirationTime
+          ? (current = bailoutOnAlreadyFinishedWork(current, workInProgress))
+          : (reconcileChildren(
+              current,
+              workInProgress,
+              renderExpirationTime.children
+            ),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child)),
+        current
+      );
+    case 13:
+      return updateContextProvider(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case 12:
+      a: if (
+        ((fn = workInProgress.type),
+        (unmaskedContext = workInProgress.pendingProps),
+        (needsContext = workInProgress.memoizedProps),
+        (props = fn._currentValue),
+        (props$jscomp$0 = fn._changedBits),
+        didPerformWorkStackCursor.current ||
+          0 !== props$jscomp$0 ||
+          needsContext !== unmaskedContext)
+      ) {
+        workInProgress.memoizedProps = unmaskedContext;
+        ctor = unmaskedContext.unstable_observedBits;
+        if (void 0 === ctor || null === ctor) ctor = 1073741823;
+        workInProgress.stateNode = ctor;
+        if (0 !== (props$jscomp$0 & ctor))
+          propagateContextChange(
             workInProgress,
+            fn,
+            props$jscomp$0,
             renderExpirationTime
           );
-        case 12:
-          a: {
-            fn = workInProgress.type;
-            unmaskedContext = workInProgress.pendingProps;
-            memoizedProps = workInProgress.memoizedProps;
-            props = getContextCurrentValue(fn);
-            var changedBits = getContextChangedBits(fn);
-            if (
-              hasLegacyContextChanged() ||
-              0 !== changedBits ||
-              memoizedProps !== unmaskedContext
-            ) {
-              workInProgress.memoizedProps = unmaskedContext;
-              var observedBits = unmaskedContext.unstable_observedBits;
-              if (void 0 === observedBits || null === observedBits)
-                observedBits = 1073741823;
-              workInProgress.stateNode = observedBits;
-              if (0 !== (changedBits & observedBits))
-                propagateContextChange(
-                  workInProgress,
-                  fn,
-                  changedBits,
-                  renderExpirationTime
-                );
-              else if (memoizedProps === unmaskedContext) {
-                current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-                break a;
-              }
-              renderExpirationTime = unmaskedContext.children;
-              renderExpirationTime = renderExpirationTime(props);
-              workInProgress.effectTag |= 1;
-              reconcileChildren(current, workInProgress, renderExpirationTime);
-              current = workInProgress.child;
-            } else
-              current = bailoutOnAlreadyFinishedWork(current, workInProgress);
-          }
-          return current;
-        default:
-          invariant(
-            !1,
-            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    }
-  };
+        else if (needsContext === unmaskedContext) {
+          current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          break a;
+        }
+        renderExpirationTime = unmaskedContext.children;
+        renderExpirationTime = renderExpirationTime(props);
+        workInProgress.effectTag |= 1;
+        reconcileChildren(current, workInProgress, renderExpirationTime);
+        current = workInProgress.child;
+      } else current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+      return current;
+    default:
+      invariant(
+        !1,
+        "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
 }
-function ReactFiberCompleteWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  hydrationContext
-) {
-  function markUpdate(workInProgress) {
+var updateHostContainer = void 0,
+  updateHostComponent$1 = void 0,
+  updateHostText$1 = void 0;
+updateHostContainer = function() {};
+updateHostComponent$1 = function(current, workInProgress, updatePayload) {
+  if ((workInProgress.updateQueue = updatePayload))
     workInProgress.effectTag |= 4;
-  }
-  var createInstance = config.createInstance,
-    createTextInstance = config.createTextInstance,
-    appendInitialChild = config.appendInitialChild,
-    finalizeInitialChildren = config.finalizeInitialChildren,
-    prepareUpdate = config.prepareUpdate,
-    persistence = config.persistence,
-    getRootHostContainer = hostContext.getRootHostContainer,
-    popHostContext = hostContext.popHostContext,
-    getHostContext = hostContext.getHostContext,
-    popHostContainer = hostContext.popHostContainer,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider,
-    prepareToHydrateHostInstance =
-      hydrationContext.prepareToHydrateHostInstance,
-    prepareToHydrateHostTextInstance =
-      hydrationContext.prepareToHydrateHostTextInstance,
-    popHydrationState = hydrationContext.popHydrationState,
-    updateHostContainer = void 0,
-    updateHostComponent = void 0,
-    updateHostText = void 0;
-  config.mutation
-    ? ((updateHostContainer = function() {}),
-      (updateHostComponent = function(current, workInProgress, updatePayload) {
-        (workInProgress.updateQueue = updatePayload) &&
-          markUpdate(workInProgress);
-      }),
-      (updateHostText = function(current, workInProgress, oldText, newText) {
-        oldText !== newText && markUpdate(workInProgress);
-      }))
-    : persistence
-      ? invariant(!1, "Persistent reconciler is disabled.")
-      : invariant(!1, "Noop reconciler is disabled.");
-  return {
-    completeWork: function(current, workInProgress) {
-      var newProps = workInProgress.pendingProps;
-      switch (workInProgress.tag) {
-        case 1:
-          return null;
-        case 2:
-          return popLegacyContextProvider(workInProgress), null;
-        case 3:
-          popHostContainer(workInProgress);
-          popTopLevelLegacyContextObject(workInProgress);
-          newProps = workInProgress.stateNode;
-          newProps.pendingContext &&
-            ((newProps.context = newProps.pendingContext),
-            (newProps.pendingContext = null));
-          if (null === current || null === current.child)
-            popHydrationState(workInProgress), (workInProgress.effectTag &= -3);
-          updateHostContainer(workInProgress);
-          return null;
-        case 5:
-          popHostContext(workInProgress);
-          var rootContainerInstance = getRootHostContainer(),
-            type = workInProgress.type;
-          if (null !== current && null != workInProgress.stateNode) {
-            var oldProps = current.memoizedProps,
-              instance = workInProgress.stateNode,
-              currentHostContext = getHostContext();
-            instance = prepareUpdate(
-              instance,
-              type,
-              oldProps,
-              newProps,
-              rootContainerInstance,
-              currentHostContext
-            );
-            updateHostComponent(
-              current,
-              workInProgress,
-              instance,
-              type,
-              oldProps,
-              newProps,
-              rootContainerInstance,
-              currentHostContext
-            );
-            current.ref !== workInProgress.ref &&
-              (workInProgress.effectTag |= 128);
-          } else {
-            if (!newProps)
-              return (
-                invariant(
-                  null !== workInProgress.stateNode,
-                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
-                ),
-                null
-              );
-            current = getHostContext();
-            if (popHydrationState(workInProgress))
-              prepareToHydrateHostInstance(
-                workInProgress,
-                rootContainerInstance,
-                current
-              ) && markUpdate(workInProgress);
-            else {
-              oldProps = createInstance(
-                type,
-                newProps,
-                rootContainerInstance,
-                current,
-                workInProgress
-              );
-              a: for (
-                currentHostContext = workInProgress.child;
-                null !== currentHostContext;
-
-              ) {
-                if (
-                  5 === currentHostContext.tag ||
-                  6 === currentHostContext.tag
-                )
-                  appendInitialChild(oldProps, currentHostContext.stateNode);
-                else if (
-                  4 !== currentHostContext.tag &&
-                  null !== currentHostContext.child
-                ) {
-                  currentHostContext.child.return = currentHostContext;
-                  currentHostContext = currentHostContext.child;
-                  continue;
-                }
-                if (currentHostContext === workInProgress) break;
-                for (; null === currentHostContext.sibling; ) {
-                  if (
-                    null === currentHostContext.return ||
-                    currentHostContext.return === workInProgress
-                  )
-                    break a;
-                  currentHostContext = currentHostContext.return;
-                }
-                currentHostContext.sibling.return = currentHostContext.return;
-                currentHostContext = currentHostContext.sibling;
-              }
-              finalizeInitialChildren(
-                oldProps,
-                type,
-                newProps,
-                rootContainerInstance,
-                current
-              ) && markUpdate(workInProgress);
-              workInProgress.stateNode = oldProps;
-            }
-            null !== workInProgress.ref && (workInProgress.effectTag |= 128);
-          }
-          return null;
-        case 6:
-          if (current && null != workInProgress.stateNode)
-            updateHostText(
-              current,
-              workInProgress,
-              current.memoizedProps,
-              newProps
-            );
-          else {
-            if ("string" !== typeof newProps)
-              return (
-                invariant(
-                  null !== workInProgress.stateNode,
-                  "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
-                ),
-                null
-              );
-            rootContainerInstance = getRootHostContainer();
-            type = getHostContext();
-            popHydrationState(workInProgress)
-              ? prepareToHydrateHostTextInstance(workInProgress) &&
-                markUpdate(workInProgress)
-              : (workInProgress.stateNode = createTextInstance(
-                  newProps,
-                  rootContainerInstance,
-                  type,
-                  workInProgress
-                ));
+};
+updateHostText$1 = function(current, workInProgress, oldText, newText) {
+  oldText !== newText && (workInProgress.effectTag |= 4);
+};
+function completeWork(current, workInProgress) {
+  var newProps = workInProgress.pendingProps;
+  switch (workInProgress.tag) {
+    case 1:
+      return null;
+    case 2:
+      return popContextProvider(workInProgress), null;
+    case 3:
+      popHostContainer(workInProgress);
+      popTopLevelContextObject(workInProgress);
+      newProps = workInProgress.stateNode;
+      newProps.pendingContext &&
+        ((newProps.context = newProps.pendingContext),
+        (newProps.pendingContext = null));
+      if (null === current || null === current.child)
+        workInProgress.effectTag &= -3;
+      updateHostContainer(workInProgress);
+      return null;
+    case 5:
+      popHostContext(workInProgress);
+      var rootContainerInstance = requiredContext(
+          rootInstanceStackCursor.current
+        ),
+        type = workInProgress.type;
+      if (null !== current && null != workInProgress.stateNode) {
+        var oldProps = current.memoizedProps,
+          currentHostContext = requiredContext(contextStackCursor$1.current);
+        updateHostComponent$1(
+          current,
+          workInProgress,
+          emptyObject,
+          type,
+          oldProps,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        );
+        current.ref !== workInProgress.ref && (workInProgress.effectTag |= 128);
+      } else {
+        if (!newProps)
+          return (
+            invariant(
+              null !== workInProgress.stateNode,
+              "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+            ),
+            null
+          );
+        current = requiredContext(contextStackCursor$1.current);
+        oldProps = allocateTag();
+        currentHostContext = ReactNativeViewConfigRegistry.get(type);
+        invariant(
+          "RCTView" !== type || !current.isInAParentText,
+          "Nesting of <View> within <Text> is not currently supported."
+        );
+        var updatePayload = diffProperties(
+          null,
+          emptyObject$1,
+          newProps,
+          currentHostContext.validAttributes
+        );
+        UIManager.createView(
+          oldProps,
+          currentHostContext.uiViewClassName,
+          rootContainerInstance,
+          updatePayload
+        );
+        currentHostContext = new ReactNativeFiberHostComponent(
+          oldProps,
+          currentHostContext
+        );
+        instanceCache[oldProps] = workInProgress;
+        instanceProps[oldProps] = newProps;
+        a: for (oldProps = workInProgress.child; null !== oldProps; ) {
+          if (5 === oldProps.tag || 6 === oldProps.tag)
+            currentHostContext._children.push(oldProps.stateNode);
+          else if (4 !== oldProps.tag && null !== oldProps.child) {
+            oldProps.child.return = oldProps;
+            oldProps = oldProps.child;
+            continue;
           }
-          return null;
-        case 14:
-          return null;
-        case 16:
-          return null;
-        case 10:
-          return null;
-        case 11:
-          return null;
-        case 15:
-          return null;
-        case 4:
+          if (oldProps === workInProgress) break;
+          for (; null === oldProps.sibling; ) {
+            if (null === oldProps.return || oldProps.return === workInProgress)
+              break a;
+            oldProps = oldProps.return;
+          }
+          oldProps.sibling.return = oldProps.return;
+          oldProps = oldProps.sibling;
+        }
+        finalizeInitialChildren(
+          currentHostContext,
+          type,
+          newProps,
+          rootContainerInstance,
+          current
+        ) && (workInProgress.effectTag |= 4);
+        workInProgress.stateNode = currentHostContext;
+        null !== workInProgress.ref && (workInProgress.effectTag |= 128);
+      }
+      return null;
+    case 6:
+      if (current && null != workInProgress.stateNode)
+        updateHostText$1(
+          current,
+          workInProgress,
+          current.memoizedProps,
+          newProps
+        );
+      else {
+        if ("string" !== typeof newProps)
           return (
-            popHostContainer(workInProgress),
-            updateHostContainer(workInProgress),
+            invariant(
+              null !== workInProgress.stateNode,
+              "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+            ),
             null
           );
-        case 13:
-          return popProvider(workInProgress), null;
-        case 12:
-          return null;
-        case 0:
-          invariant(
-            !1,
-            "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
-          );
-        default:
-          invariant(
-            !1,
-            "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
-          );
+        rootContainerInstance = requiredContext(
+          rootInstanceStackCursor.current
+        );
+        type = requiredContext(contextStackCursor$1.current);
+        invariant(
+          type.isInAParentText,
+          "Text strings must be rendered within a <Text> component."
+        );
+        type = allocateTag();
+        UIManager.createView(type, "RCTRawText", rootContainerInstance, {
+          text: newProps
+        });
+        instanceCache[type] = workInProgress;
+        workInProgress.stateNode = type;
       }
-    }
-  };
-}
-function createCapturedValue(value, source) {
-  return {
-    value: value,
-    source: source,
-    stack: getStackAddendumByWorkInProgressFiber(source)
-  };
+      return null;
+    case 14:
+      return null;
+    case 16:
+      return null;
+    case 10:
+      return null;
+    case 11:
+      return null;
+    case 15:
+      return null;
+    case 4:
+      return (
+        popHostContainer(workInProgress),
+        updateHostContainer(workInProgress),
+        null
+      );
+    case 13:
+      return popProvider(workInProgress), null;
+    case 12:
+      return null;
+    case 0:
+      invariant(
+        !1,
+        "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
+      );
+    default:
+      invariant(
+        !1,
+        "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
 }
 function logError(boundary, errorInfo) {
   var source = errorInfo.source,
@@ -3704,2544 +4123,1510 @@ function logError(boundary, errorInfo) {
   errorInfo = errorInfo.value;
   null !== boundary && 2 === boundary.tag && getComponentName(boundary);
   try {
-    if (errorInfo instanceof Error) {
-      var message = errorInfo.message,
-        name = errorInfo.name;
-      var errorToHandle = errorInfo;
-      try {
-        errorToHandle.message =
-          (message ? name + ": " + message : name) +
-          "\n\nThis error is located at:" +
-          source;
-      } catch (e) {}
-    } else
-      errorToHandle =
-        "string" === typeof errorInfo
-          ? Error(errorInfo + "\n\nThis error is located at:" + source)
-          : Error("Unspecified error at:" + source);
-    ExceptionsManager.handleException(errorToHandle, !1);
-  } catch (e) {
-    (e && e.suppressReactErrorLogging) || console.error(e);
-  }
-}
-function ReactFiberCommitWork(config, captureError) {
-  function safelyDetachRef(current) {
-    var ref = current.ref;
-    if (null !== ref)
-      if ("function" === typeof ref)
-        try {
-          ref(null);
-        } catch (refError) {
-          captureError(current, refError);
-        }
-      else ref.current = null;
-  }
-  function commitUnmount(current) {
-    "function" === typeof onCommitUnmount && onCommitUnmount(current);
-    switch (current.tag) {
-      case 2:
-        safelyDetachRef(current);
-        var _instance6 = current.stateNode;
-        if ("function" === typeof _instance6.componentWillUnmount)
-          try {
-            (_instance6.props = current.memoizedProps),
-              (_instance6.state = current.memoizedState),
-              _instance6.componentWillUnmount();
-          } catch (unmountError) {
-            captureError(current, unmountError);
-          }
-        break;
-      case 5:
-        safelyDetachRef(current);
-        break;
-      case 4:
-        mutation && unmountHostComponents(current);
-    }
-  }
-  function isHostParent(fiber) {
-    return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
-  }
-  function unmountHostComponents(current) {
-    for (
-      var node = current,
-        currentParentIsValid = !1,
-        currentParent = void 0,
-        currentParentIsContainer = void 0;
-      ;
-
-    ) {
-      if (!currentParentIsValid) {
-        currentParentIsValid = node.return;
-        a: for (;;) {
-          invariant(
-            null !== currentParentIsValid,
-            "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
-          );
-          switch (currentParentIsValid.tag) {
-            case 5:
-              currentParent = currentParentIsValid.stateNode;
-              currentParentIsContainer = !1;
-              break a;
-            case 3:
-              currentParent = currentParentIsValid.stateNode.containerInfo;
-              currentParentIsContainer = !0;
-              break a;
-            case 4:
-              currentParent = currentParentIsValid.stateNode.containerInfo;
-              currentParentIsContainer = !0;
-              break a;
-          }
-          currentParentIsValid = currentParentIsValid.return;
-        }
-        currentParentIsValid = !0;
-      }
-      if (5 === node.tag || 6 === node.tag) {
-        a: for (var root = node, node$jscomp$0 = root; ; )
-          if (
-            (commitUnmount(node$jscomp$0),
-            null === node$jscomp$0.child ||
-              (mutation && 4 === node$jscomp$0.tag))
-          ) {
-            if (node$jscomp$0 === root) break;
-            for (; null === node$jscomp$0.sibling; ) {
-              if (
-                null === node$jscomp$0.return ||
-                node$jscomp$0.return === root
-              )
-                break a;
-              node$jscomp$0 = node$jscomp$0.return;
-            }
-            node$jscomp$0.sibling.return = node$jscomp$0.return;
-            node$jscomp$0 = node$jscomp$0.sibling;
-          } else
-            (node$jscomp$0.child.return = node$jscomp$0),
-              (node$jscomp$0 = node$jscomp$0.child);
-        currentParentIsContainer
-          ? removeChildFromContainer(currentParent, node.stateNode)
-          : removeChild(currentParent, node.stateNode);
-      } else if (
-        (4 === node.tag
-          ? (currentParent = node.stateNode.containerInfo)
-          : commitUnmount(node),
-        null !== node.child)
-      ) {
-        node.child.return = node;
-        node = node.child;
-        continue;
-      }
-      if (node === current) break;
-      for (; null === node.sibling; ) {
-        if (null === node.return || node.return === current) return;
-        node = node.return;
-        4 === node.tag && (currentParentIsValid = !1);
-      }
-      node.sibling.return = node.return;
-      node = node.sibling;
-    }
-  }
-  var getPublicInstance = config.getPublicInstance,
-    mutation = config.mutation;
-  config = config.persistence;
-  mutation ||
-    (config
-      ? invariant(!1, "Persistent reconciler is disabled.")
-      : invariant(!1, "Noop reconciler is disabled."));
-  var commitMount = mutation.commitMount,
-    commitUpdate = mutation.commitUpdate,
-    resetTextContent = mutation.resetTextContent,
-    commitTextUpdate = mutation.commitTextUpdate,
-    appendChild = mutation.appendChild,
-    appendChildToContainer = mutation.appendChildToContainer,
-    insertBefore = mutation.insertBefore,
-    insertInContainerBefore = mutation.insertInContainerBefore,
-    removeChild = mutation.removeChild,
-    removeChildFromContainer = mutation.removeChildFromContainer;
-  return {
-    commitBeforeMutationLifeCycles: function(current, finishedWork) {
-      switch (finishedWork.tag) {
-        case 2:
-          if (finishedWork.effectTag & 256 && null !== current) {
-            var prevProps = current.memoizedProps,
-              prevState = current.memoizedState;
-            current = finishedWork.stateNode;
-            current.props = finishedWork.memoizedProps;
-            current.state = finishedWork.memoizedState;
-            finishedWork = current.getSnapshotBeforeUpdate(
-              prevProps,
-              prevState
-            );
-            current.__reactInternalSnapshotBeforeUpdate = finishedWork;
-          }
-          break;
-        case 3:
-        case 5:
-        case 6:
-        case 4:
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitResetTextContent: function(current) {
-      resetTextContent(current.stateNode);
-    },
-    commitPlacement: function(finishedWork) {
-      a: {
-        for (var parent = finishedWork.return; null !== parent; ) {
-          if (isHostParent(parent)) {
-            var parentFiber = parent;
-            break a;
-          }
-          parent = parent.return;
-        }
-        invariant(
-          !1,
-          "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
-        );
-        parentFiber = void 0;
-      }
-      var isContainer = (parent = void 0);
-      switch (parentFiber.tag) {
-        case 5:
-          parent = parentFiber.stateNode;
-          isContainer = !1;
-          break;
-        case 3:
-          parent = parentFiber.stateNode.containerInfo;
-          isContainer = !0;
-          break;
-        case 4:
-          parent = parentFiber.stateNode.containerInfo;
-          isContainer = !0;
-          break;
-        default:
-          invariant(
-            !1,
-            "Invalid host parent fiber. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-      parentFiber.effectTag & 16 &&
-        (resetTextContent(parent), (parentFiber.effectTag &= -17));
-      a: b: for (parentFiber = finishedWork; ; ) {
-        for (; null === parentFiber.sibling; ) {
-          if (null === parentFiber.return || isHostParent(parentFiber.return)) {
-            parentFiber = null;
-            break a;
-          }
-          parentFiber = parentFiber.return;
-        }
-        parentFiber.sibling.return = parentFiber.return;
-        for (
-          parentFiber = parentFiber.sibling;
-          5 !== parentFiber.tag && 6 !== parentFiber.tag;
-
-        ) {
-          if (parentFiber.effectTag & 2) continue b;
-          if (null === parentFiber.child || 4 === parentFiber.tag) continue b;
-          else
-            (parentFiber.child.return = parentFiber),
-              (parentFiber = parentFiber.child);
-        }
-        if (!(parentFiber.effectTag & 2)) {
-          parentFiber = parentFiber.stateNode;
-          break a;
-        }
-      }
-      for (var node = finishedWork; ; ) {
-        if (5 === node.tag || 6 === node.tag)
-          parentFiber
-            ? isContainer
-              ? insertInContainerBefore(parent, node.stateNode, parentFiber)
-              : insertBefore(parent, node.stateNode, parentFiber)
-            : isContainer
-              ? appendChildToContainer(parent, node.stateNode)
-              : appendChild(parent, node.stateNode);
-        else if (4 !== node.tag && null !== node.child) {
-          node.child.return = node;
-          node = node.child;
-          continue;
-        }
-        if (node === finishedWork) break;
-        for (; null === node.sibling; ) {
-          if (null === node.return || node.return === finishedWork) return;
-          node = node.return;
-        }
-        node.sibling.return = node.return;
-        node = node.sibling;
-      }
-    },
-    commitDeletion: function(current) {
-      unmountHostComponents(current);
-      current.return = null;
-      current.child = null;
-      current.alternate &&
-        ((current.alternate.child = null), (current.alternate.return = null));
-    },
-    commitWork: function(current, finishedWork) {
-      switch (finishedWork.tag) {
-        case 2:
-          break;
-        case 5:
-          var _instance7 = finishedWork.stateNode;
-          if (null != _instance7) {
-            var newProps = finishedWork.memoizedProps;
-            current = null !== current ? current.memoizedProps : newProps;
-            var type = finishedWork.type,
-              updatePayload = finishedWork.updateQueue;
-            finishedWork.updateQueue = null;
-            null !== updatePayload &&
-              commitUpdate(
-                _instance7,
-                updatePayload,
-                type,
-                current,
-                newProps,
-                finishedWork
-              );
-          }
-          break;
-        case 6:
-          invariant(
-            null !== finishedWork.stateNode,
-            "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
-          );
-          _instance7 = finishedWork.memoizedProps;
-          commitTextUpdate(
-            finishedWork.stateNode,
-            null !== current ? current.memoizedProps : _instance7,
-            _instance7
-          );
-          break;
-        case 3:
-          break;
-        case 15:
-          break;
-        case 16:
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitLifeCycles: function(
-      finishedRoot,
-      current,
-      finishedWork,
-      currentTime,
-      committedExpirationTime
-    ) {
-      switch (finishedWork.tag) {
-        case 2:
-          finishedRoot = finishedWork.stateNode;
-          finishedWork.effectTag & 4 &&
-            (null === current
-              ? ((finishedRoot.props = finishedWork.memoizedProps),
-                (finishedRoot.state = finishedWork.memoizedState),
-                finishedRoot.componentDidMount())
-              : ((currentTime = current.memoizedProps),
-                (current = current.memoizedState),
-                (finishedRoot.props = finishedWork.memoizedProps),
-                (finishedRoot.state = finishedWork.memoizedState),
-                finishedRoot.componentDidUpdate(
-                  currentTime,
-                  current,
-                  finishedRoot.__reactInternalSnapshotBeforeUpdate
-                )));
-          current = finishedWork.updateQueue;
-          null !== current &&
-            ((finishedRoot.props = finishedWork.memoizedProps),
-            (finishedRoot.state = finishedWork.memoizedState),
-            commitUpdateQueue(
-              finishedWork,
-              current,
-              finishedRoot,
-              committedExpirationTime
-            ));
-          break;
-        case 3:
-          current = finishedWork.updateQueue;
-          if (null !== current) {
-            finishedRoot = null;
-            if (null !== finishedWork.child)
-              switch (finishedWork.child.tag) {
-                case 5:
-                  finishedRoot = getPublicInstance(
-                    finishedWork.child.stateNode
-                  );
-                  break;
-                case 2:
-                  finishedRoot = finishedWork.child.stateNode;
-              }
-            commitUpdateQueue(
-              finishedWork,
-              current,
-              finishedRoot,
-              committedExpirationTime
-            );
-          }
-          break;
-        case 5:
-          committedExpirationTime = finishedWork.stateNode;
-          null === current &&
-            finishedWork.effectTag & 4 &&
-            commitMount(
-              committedExpirationTime,
-              finishedWork.type,
-              finishedWork.memoizedProps,
-              finishedWork
-            );
-          break;
-        case 6:
-          break;
-        case 4:
-          break;
-        case 15:
-          break;
-        case 16:
-          break;
-        default:
-          invariant(
-            !1,
-            "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
-          );
-      }
-    },
-    commitAttachRef: function(finishedWork) {
-      var ref = finishedWork.ref;
-      if (null !== ref) {
-        var _instance5 = finishedWork.stateNode;
-        switch (finishedWork.tag) {
-          case 5:
-            finishedWork = getPublicInstance(_instance5);
-            break;
-          default:
-            finishedWork = _instance5;
-        }
-        "function" === typeof ref
-          ? ref(finishedWork)
-          : (ref.current = finishedWork);
-      }
-    },
-    commitDetachRef: function(current) {
-      current = current.ref;
-      null !== current &&
-        ("function" === typeof current
-          ? current(null)
-          : (current.current = null));
-    }
-  };
-}
-function ReactFiberUnwindWork(
-  config,
-  hostContext,
-  legacyContext,
-  newContext,
-  scheduleWork,
-  computeExpirationForFiber,
-  recalculateCurrentTime,
-  markLegacyErrorBoundaryAsFailed,
-  isAlreadyFailedLegacyErrorBoundary,
-  onUncaughtError
-) {
-  function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
-    expirationTime = createUpdate(expirationTime);
-    expirationTime.tag = 3;
-    expirationTime.payload = { element: null };
-    var error = errorInfo.value;
-    expirationTime.callback = function() {
-      onUncaughtError(error);
-      logError(fiber, errorInfo);
-    };
-    return expirationTime;
-  }
-  function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
-    expirationTime = createUpdate(expirationTime);
-    expirationTime.tag = 3;
-    var inst = fiber.stateNode;
-    null !== inst &&
-      "function" === typeof inst.componentDidCatch &&
-      (expirationTime.callback = function() {
-        markLegacyErrorBoundaryAsFailed(this);
-        var error = errorInfo.value,
-          stack = errorInfo.stack;
-        logError(fiber, errorInfo);
-        this.componentDidCatch(error, {
-          componentStack: null !== stack ? stack : ""
-        });
-      });
-    return expirationTime;
-  }
-  var popHostContainer = hostContext.popHostContainer,
-    popHostContext = hostContext.popHostContext,
-    popLegacyContextProvider = legacyContext.popContextProvider,
-    popTopLevelLegacyContextObject = legacyContext.popTopLevelContextObject,
-    popProvider = newContext.popProvider;
-  return {
-    throwException: function(
-      root,
-      returnFiber,
-      sourceFiber,
-      value,
-      renderIsExpired,
-      renderExpirationTime
-    ) {
-      sourceFiber.effectTag |= 512;
-      sourceFiber.firstEffect = sourceFiber.lastEffect = null;
-      value = createCapturedValue(value, sourceFiber);
-      root = returnFiber;
-      do {
-        switch (root.tag) {
-          case 3:
-            root.effectTag |= 1024;
-            value = createRootErrorUpdate(root, value, renderExpirationTime);
-            enqueueCapturedUpdate(root, value, renderExpirationTime);
-            return;
-          case 2:
-            if (
-              ((returnFiber = value),
-              (sourceFiber = root.stateNode),
-              0 === (root.effectTag & 64) &&
-                null !== sourceFiber &&
-                "function" === typeof sourceFiber.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(sourceFiber))
-            ) {
-              root.effectTag |= 1024;
-              value = createClassErrorUpdate(
-                root,
-                returnFiber,
-                renderExpirationTime
-              );
-              enqueueCapturedUpdate(root, value, renderExpirationTime);
-              return;
-            }
-        }
-        root = root.return;
-      } while (null !== root);
-    },
-    unwindWork: function(workInProgress) {
-      switch (workInProgress.tag) {
-        case 2:
-          popLegacyContextProvider(workInProgress);
-          var effectTag = workInProgress.effectTag;
-          return effectTag & 1024
-            ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-              workInProgress)
-            : null;
-        case 3:
-          return (
-            popHostContainer(workInProgress),
-            popTopLevelLegacyContextObject(workInProgress),
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 5:
-          return popHostContext(workInProgress), null;
-        case 16:
-          return (
-            (effectTag = workInProgress.effectTag),
-            effectTag & 1024
-              ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
-                workInProgress)
-              : null
-          );
-        case 4:
-          return popHostContainer(workInProgress), null;
-        case 13:
-          return popProvider(workInProgress), null;
-        default:
-          return null;
-      }
-    },
-    unwindInterruptedWork: function(interruptedWork) {
-      switch (interruptedWork.tag) {
-        case 2:
-          popLegacyContextProvider(interruptedWork);
-          break;
-        case 3:
-          popHostContainer(interruptedWork);
-          popTopLevelLegacyContextObject(interruptedWork);
-          break;
-        case 5:
-          popHostContext(interruptedWork);
-          break;
-        case 4:
-          popHostContainer(interruptedWork);
-          break;
-        case 13:
-          popProvider(interruptedWork);
+    if (errorInfo instanceof Error) {
+      var message = errorInfo.message,
+        name = errorInfo.name;
+      var errorToHandle = errorInfo;
+      try {
+        errorToHandle.message =
+          (message ? name + ": " + message : name) +
+          "\n\nThis error is located at:" +
+          source;
+      } catch (e) {}
+    } else
+      errorToHandle =
+        "string" === typeof errorInfo
+          ? Error(errorInfo + "\n\nThis error is located at:" + source)
+          : Error("Unspecified error at:" + source);
+    ExceptionsManager.handleException(errorToHandle, !1);
+  } catch (e) {
+    (e && e.suppressReactErrorLogging) || console.error(e);
+  }
+}
+function safelyDetachRef(current) {
+  var ref = current.ref;
+  if (null !== ref)
+    if ("function" === typeof ref)
+      try {
+        ref(null);
+      } catch (refError) {
+        captureCommitPhaseError(current, refError);
       }
-    },
-    createRootErrorUpdate: createRootErrorUpdate,
-    createClassErrorUpdate: createClassErrorUpdate
-  };
+    else ref.current = null;
+}
+function commitUnmount(current) {
+  "function" === typeof onCommitUnmount && onCommitUnmount(current);
+  switch (current.tag) {
+    case 2:
+      safelyDetachRef(current);
+      var instance = current.stateNode;
+      if ("function" === typeof instance.componentWillUnmount)
+        try {
+          (instance.props = current.memoizedProps),
+            (instance.state = current.memoizedState),
+            instance.componentWillUnmount();
+        } catch (unmountError) {
+          captureCommitPhaseError(current, unmountError);
+        }
+      break;
+    case 5:
+      safelyDetachRef(current);
+      break;
+    case 4:
+      unmountHostComponents(current);
+  }
+}
+function isHostParent(fiber) {
+  return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
 }
-var NO_CONTEXT = {};
-function ReactFiberHostContext(config, stack) {
-  function requiredContext(c) {
+function commitPlacement(finishedWork) {
+  a: {
+    for (var parent = finishedWork.return; null !== parent; ) {
+      if (isHostParent(parent)) {
+        var parentFiber = parent;
+        break a;
+      }
+      parent = parent.return;
+    }
     invariant(
-      c !== NO_CONTEXT,
-      "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
+      !1,
+      "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
     );
-    return c;
+    parentFiber = void 0;
   }
-  var getChildHostContext = config.getChildHostContext,
-    getRootHostContext = config.getRootHostContext;
-  config = stack.createCursor;
-  var push = stack.push,
-    pop = stack.pop,
-    contextStackCursor = config(NO_CONTEXT),
-    contextFiberStackCursor = config(NO_CONTEXT),
-    rootInstanceStackCursor = config(NO_CONTEXT);
-  return {
-    getHostContext: function() {
-      return requiredContext(contextStackCursor.current);
-    },
-    getRootHostContainer: function() {
-      return requiredContext(rootInstanceStackCursor.current);
-    },
-    popHostContainer: function(fiber) {
-      pop(contextStackCursor, fiber);
-      pop(contextFiberStackCursor, fiber);
-      pop(rootInstanceStackCursor, fiber);
-    },
-    popHostContext: function(fiber) {
-      contextFiberStackCursor.current === fiber &&
-        (pop(contextStackCursor, fiber), pop(contextFiberStackCursor, fiber));
-    },
-    pushHostContainer: function(fiber, nextRootInstance) {
-      push(rootInstanceStackCursor, nextRootInstance, fiber);
-      push(contextFiberStackCursor, fiber, fiber);
-      push(contextStackCursor, NO_CONTEXT, fiber);
-      nextRootInstance = getRootHostContext(nextRootInstance);
-      pop(contextStackCursor, fiber);
-      push(contextStackCursor, nextRootInstance, fiber);
-    },
-    pushHostContext: function(fiber) {
-      var rootInstance = requiredContext(rootInstanceStackCursor.current),
-        context = requiredContext(contextStackCursor.current);
-      rootInstance = getChildHostContext(context, fiber.type, rootInstance);
-      context !== rootInstance &&
-        (push(contextFiberStackCursor, fiber, fiber),
-        push(contextStackCursor, rootInstance, fiber));
-    }
-  };
-}
-function ReactFiberHydrationContext(config) {
-  function deleteHydratableInstance(returnFiber, instance) {
-    var fiber = new FiberNode(5, null, null, 0);
-    fiber.type = "DELETED";
-    fiber.stateNode = instance;
-    fiber.return = returnFiber;
-    fiber.effectTag = 8;
-    null !== returnFiber.lastEffect
-      ? ((returnFiber.lastEffect.nextEffect = fiber),
-        (returnFiber.lastEffect = fiber))
-      : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
+  var isContainer = (parent = void 0);
+  switch (parentFiber.tag) {
+    case 5:
+      parent = parentFiber.stateNode;
+      isContainer = !1;
+      break;
+    case 3:
+      parent = parentFiber.stateNode.containerInfo;
+      isContainer = !0;
+      break;
+    case 4:
+      parent = parentFiber.stateNode.containerInfo;
+      isContainer = !0;
+      break;
+    default:
+      invariant(
+        !1,
+        "Invalid host parent fiber. This error is likely caused by a bug in React. Please file an issue."
+      );
   }
-  function tryHydrate(fiber, nextInstance) {
-    switch (fiber.tag) {
-      case 5:
-        return (
-          (nextInstance = canHydrateInstance(
-            nextInstance,
-            fiber.type,
-            fiber.pendingProps
-          )),
-          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
-        );
-      case 6:
-        return (
-          (nextInstance = canHydrateTextInstance(
-            nextInstance,
-            fiber.pendingProps
-          )),
-          null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
-        );
-      default:
-        return !1;
+  parentFiber.effectTag & 16 && (parentFiber.effectTag &= -17);
+  a: b: for (parentFiber = finishedWork; ; ) {
+    for (; null === parentFiber.sibling; ) {
+      if (null === parentFiber.return || isHostParent(parentFiber.return)) {
+        parentFiber = null;
+        break a;
+      }
+      parentFiber = parentFiber.return;
     }
-  }
-  function popToNextHostParent(fiber) {
+    parentFiber.sibling.return = parentFiber.return;
     for (
-      fiber = fiber.return;
-      null !== fiber && 5 !== fiber.tag && 3 !== fiber.tag;
+      parentFiber = parentFiber.sibling;
+      5 !== parentFiber.tag && 6 !== parentFiber.tag;
 
-    )
-      fiber = fiber.return;
-    hydrationParentFiber = fiber;
+    ) {
+      if (parentFiber.effectTag & 2) continue b;
+      if (null === parentFiber.child || 4 === parentFiber.tag) continue b;
+      else
+        (parentFiber.child.return = parentFiber),
+          (parentFiber = parentFiber.child);
+    }
+    if (!(parentFiber.effectTag & 2)) {
+      parentFiber = parentFiber.stateNode;
+      break a;
+    }
   }
-  var shouldSetTextContent = config.shouldSetTextContent;
-  config = config.hydration;
-  if (!config)
-    return {
-      enterHydrationState: function() {
-        return !1;
-      },
-      resetHydrationState: function() {},
-      tryToClaimNextHydratableInstance: function() {},
-      prepareToHydrateHostInstance: function() {
-        invariant(
-          !1,
-          "Expected prepareToHydrateHostInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
-        );
-      },
-      prepareToHydrateHostTextInstance: function() {
+  for (var node = finishedWork; ; ) {
+    if (5 === node.tag || 6 === node.tag)
+      if (parentFiber)
+        if (isContainer)
+          invariant(
+            "number" !== typeof parent,
+            "Container does not support insertBefore operation"
+          );
+        else {
+          var parentInstance = parent,
+            child = node.stateNode,
+            beforeChild = parentFiber,
+            children = parentInstance._children,
+            index = children.indexOf(child);
+          0 <= index
+            ? (children.splice(index, 1),
+              (beforeChild = children.indexOf(beforeChild)),
+              children.splice(beforeChild, 0, child),
+              UIManager.manageChildren(
+                parentInstance._nativeTag,
+                [index],
+                [beforeChild],
+                [],
+                [],
+                []
+              ))
+            : ((index = children.indexOf(beforeChild)),
+              children.splice(index, 0, child),
+              UIManager.manageChildren(
+                parentInstance._nativeTag,
+                [],
+                [],
+                ["number" === typeof child ? child : child._nativeTag],
+                [index],
+                []
+              ));
+        }
+      else
+        isContainer
+          ? ((parentInstance = node.stateNode),
+            UIManager.setChildren(parent, [
+              "number" === typeof parentInstance
+                ? parentInstance
+                : parentInstance._nativeTag
+            ]))
+          : ((parentInstance = parent),
+            (child = node.stateNode),
+            (children = "number" === typeof child ? child : child._nativeTag),
+            (index = parentInstance._children),
+            (beforeChild = index.indexOf(child)),
+            0 <= beforeChild
+              ? (index.splice(beforeChild, 1),
+                index.push(child),
+                UIManager.manageChildren(
+                  parentInstance._nativeTag,
+                  [beforeChild],
+                  [index.length - 1],
+                  [],
+                  [],
+                  []
+                ))
+              : (index.push(child),
+                UIManager.manageChildren(
+                  parentInstance._nativeTag,
+                  [],
+                  [],
+                  [children],
+                  [index.length - 1],
+                  []
+                )));
+    else if (4 !== node.tag && null !== node.child) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === finishedWork) break;
+    for (; null === node.sibling; ) {
+      if (null === node.return || node.return === finishedWork) return;
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+}
+function unmountHostComponents(current) {
+  for (
+    var node = current,
+      currentParentIsValid = !1,
+      currentParent = void 0,
+      currentParentIsContainer = void 0;
+    ;
+
+  ) {
+    if (!currentParentIsValid) {
+      currentParentIsValid = node.return;
+      a: for (;;) {
         invariant(
-          !1,
-          "Expected prepareToHydrateHostTextInstance() to never be called. This error is likely caused by a bug in React. Please file an issue."
+          null !== currentParentIsValid,
+          "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
         );
-      },
-      popHydrationState: function() {
-        return !1;
+        switch (currentParentIsValid.tag) {
+          case 5:
+            currentParent = currentParentIsValid.stateNode;
+            currentParentIsContainer = !1;
+            break a;
+          case 3:
+            currentParent = currentParentIsValid.stateNode.containerInfo;
+            currentParentIsContainer = !0;
+            break a;
+          case 4:
+            currentParent = currentParentIsValid.stateNode.containerInfo;
+            currentParentIsContainer = !0;
+            break a;
+        }
+        currentParentIsValid = currentParentIsValid.return;
       }
-    };
-  var canHydrateInstance = config.canHydrateInstance,
-    canHydrateTextInstance = config.canHydrateTextInstance,
-    getNextHydratableSibling = config.getNextHydratableSibling,
-    getFirstHydratableChild = config.getFirstHydratableChild,
-    hydrateInstance = config.hydrateInstance,
-    hydrateTextInstance = config.hydrateTextInstance,
-    hydrationParentFiber = null,
-    nextHydratableInstance = null,
-    isHydrating = !1;
-  return {
-    enterHydrationState: function(fiber) {
-      nextHydratableInstance = getFirstHydratableChild(
-        fiber.stateNode.containerInfo
-      );
-      hydrationParentFiber = fiber;
-      return (isHydrating = !0);
-    },
-    resetHydrationState: function() {
-      nextHydratableInstance = hydrationParentFiber = null;
-      isHydrating = !1;
-    },
-    tryToClaimNextHydratableInstance: function(fiber) {
-      if (isHydrating) {
-        var nextInstance = nextHydratableInstance;
-        if (nextInstance) {
-          if (!tryHydrate(fiber, nextInstance)) {
-            nextInstance = getNextHydratableSibling(nextInstance);
-            if (!nextInstance || !tryHydrate(fiber, nextInstance)) {
-              fiber.effectTag |= 2;
-              isHydrating = !1;
-              hydrationParentFiber = fiber;
-              return;
-            }
-            deleteHydratableInstance(
-              hydrationParentFiber,
-              nextHydratableInstance
-            );
+      currentParentIsValid = !0;
+    }
+    if (5 === node.tag || 6 === node.tag) {
+      a: for (var root = node, node$jscomp$0 = root; ; )
+        if (
+          (commitUnmount(node$jscomp$0),
+          null !== node$jscomp$0.child && 4 !== node$jscomp$0.tag)
+        )
+          (node$jscomp$0.child.return = node$jscomp$0),
+            (node$jscomp$0 = node$jscomp$0.child);
+        else {
+          if (node$jscomp$0 === root) break;
+          for (; null === node$jscomp$0.sibling; ) {
+            if (null === node$jscomp$0.return || node$jscomp$0.return === root)
+              break a;
+            node$jscomp$0 = node$jscomp$0.return;
           }
-          hydrationParentFiber = fiber;
-          nextHydratableInstance = getFirstHydratableChild(nextInstance);
-        } else
-          (fiber.effectTag |= 2),
-            (isHydrating = !1),
-            (hydrationParentFiber = fiber);
+          node$jscomp$0.sibling.return = node$jscomp$0.return;
+          node$jscomp$0 = node$jscomp$0.sibling;
+        }
+      if (currentParentIsContainer)
+        (root = currentParent),
+          recursivelyUncacheFiberNode(node.stateNode),
+          UIManager.manageChildren(root, [], [], [], [], [0]);
+      else {
+        root = currentParent;
+        var child = node.stateNode;
+        recursivelyUncacheFiberNode(child);
+        node$jscomp$0 = root._children;
+        child = node$jscomp$0.indexOf(child);
+        node$jscomp$0.splice(child, 1);
+        UIManager.manageChildren(root._nativeTag, [], [], [], [], [child]);
       }
-    },
-    prepareToHydrateHostInstance: function(
-      fiber,
-      rootContainerInstance,
-      hostContext
+    } else if (
+      (4 === node.tag
+        ? (currentParent = node.stateNode.containerInfo)
+        : commitUnmount(node),
+      null !== node.child)
     ) {
-      rootContainerInstance = hydrateInstance(
-        fiber.stateNode,
-        fiber.type,
-        fiber.memoizedProps,
-        rootContainerInstance,
-        hostContext,
-        fiber
-      );
-      fiber.updateQueue = rootContainerInstance;
-      return null !== rootContainerInstance ? !0 : !1;
-    },
-    prepareToHydrateHostTextInstance: function(fiber) {
-      return hydrateTextInstance(fiber.stateNode, fiber.memoizedProps, fiber);
-    },
-    popHydrationState: function(fiber) {
-      if (fiber !== hydrationParentFiber) return !1;
-      if (!isHydrating)
-        return popToNextHostParent(fiber), (isHydrating = !0), !1;
-      var type = fiber.type;
-      if (
-        5 !== fiber.tag ||
-        ("head" !== type &&
-          "body" !== type &&
-          !shouldSetTextContent(type, fiber.memoizedProps))
-      )
-        for (type = nextHydratableInstance; type; )
-          deleteHydratableInstance(fiber, type),
-            (type = getNextHydratableSibling(type));
-      popToNextHostParent(fiber);
-      nextHydratableInstance = hydrationParentFiber
-        ? getNextHydratableSibling(fiber.stateNode)
-        : null;
-      return !0;
+      node.child.return = node;
+      node = node.child;
+      continue;
     }
-  };
-}
-function ReactFiberLegacyContext(stack) {
-  function cacheContext(workInProgress, unmaskedContext, maskedContext) {
-    workInProgress = workInProgress.stateNode;
-    workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext;
-    workInProgress.__reactInternalMemoizedMaskedChildContext = maskedContext;
-  }
-  function isContextProvider(fiber) {
-    return 2 === fiber.tag && null != fiber.type.childContextTypes;
-  }
-  function processChildContext(fiber, parentContext) {
-    var instance = fiber.stateNode,
-      childContextTypes = fiber.type.childContextTypes;
-    if ("function" !== typeof instance.getChildContext) return parentContext;
-    instance = instance.getChildContext();
-    for (var contextKey in instance)
-      invariant(
-        contextKey in childContextTypes,
-        '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
-        getComponentName(fiber) || "Unknown",
-        contextKey
-      );
-    return Object.assign({}, parentContext, instance);
+    if (node === current) break;
+    for (; null === node.sibling; ) {
+      if (null === node.return || node.return === current) return;
+      node = node.return;
+      4 === node.tag && (currentParentIsValid = !1);
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
   }
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop,
-    contextStackCursor = createCursor(emptyObject),
-    didPerformWorkStackCursor = createCursor(!1),
-    previousContext = emptyObject;
-  return {
-    getUnmaskedContext: function(workInProgress) {
-      return isContextProvider(workInProgress)
-        ? previousContext
-        : contextStackCursor.current;
-    },
-    cacheContext: cacheContext,
-    getMaskedContext: function(workInProgress, unmaskedContext) {
-      var contextTypes = workInProgress.type.contextTypes;
-      if (!contextTypes) return emptyObject;
-      var instance = workInProgress.stateNode;
-      if (
-        instance &&
-        instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
-      )
-        return instance.__reactInternalMemoizedMaskedChildContext;
-      var context = {},
-        key;
-      for (key in contextTypes) context[key] = unmaskedContext[key];
-      instance && cacheContext(workInProgress, unmaskedContext, context);
-      return context;
-    },
-    hasContextChanged: function() {
-      return didPerformWorkStackCursor.current;
-    },
-    isContextConsumer: function(fiber) {
-      return 2 === fiber.tag && null != fiber.type.contextTypes;
-    },
-    isContextProvider: isContextProvider,
-    popContextProvider: function(fiber) {
-      isContextProvider(fiber) &&
-        (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
-    },
-    popTopLevelContextObject: function(fiber) {
-      pop(didPerformWorkStackCursor, fiber);
-      pop(contextStackCursor, fiber);
-    },
-    pushTopLevelContextObject: function(fiber, context, didChange) {
+}
+function commitWork(current, finishedWork) {
+  switch (finishedWork.tag) {
+    case 2:
+      break;
+    case 5:
+      var instance = finishedWork.stateNode;
+      if (null != instance) {
+        var newProps = finishedWork.memoizedProps;
+        current = null !== current ? current.memoizedProps : newProps;
+        var updatePayload = finishedWork.updateQueue;
+        finishedWork.updateQueue = null;
+        null !== updatePayload &&
+          ((finishedWork = instance.viewConfig),
+          (instanceProps[instance._nativeTag] = newProps),
+          (newProps = diffProperties(
+            null,
+            current,
+            newProps,
+            finishedWork.validAttributes
+          )),
+          null != newProps &&
+            UIManager.updateView(
+              instance._nativeTag,
+              finishedWork.uiViewClassName,
+              newProps
+            ));
+      }
+      break;
+    case 6:
       invariant(
-        null == contextStackCursor.cursor,
-        "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
-      );
-      push(contextStackCursor, context, fiber);
-      push(didPerformWorkStackCursor, didChange, fiber);
-    },
-    processChildContext: processChildContext,
-    pushContextProvider: function(workInProgress) {
-      if (!isContextProvider(workInProgress)) return !1;
-      var instance = workInProgress.stateNode;
-      instance =
-        (instance && instance.__reactInternalMemoizedMergedChildContext) ||
-        emptyObject;
-      previousContext = contextStackCursor.current;
-      push(contextStackCursor, instance, workInProgress);
-      push(
-        didPerformWorkStackCursor,
-        didPerformWorkStackCursor.current,
-        workInProgress
+        null !== finishedWork.stateNode,
+        "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
       );
-      return !0;
-    },
-    invalidateContextProvider: function(workInProgress, didChange) {
-      var instance = workInProgress.stateNode;
+      UIManager.updateView(finishedWork.stateNode, "RCTRawText", {
+        text: finishedWork.memoizedProps
+      });
+      break;
+    case 3:
+      break;
+    case 15:
+      break;
+    case 16:
+      break;
+    default:
       invariant(
-        instance,
-        "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+        !1,
+        "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
       );
-      if (didChange) {
-        var mergedContext = processChildContext(
-          workInProgress,
-          previousContext
-        );
-        instance.__reactInternalMemoizedMergedChildContext = mergedContext;
-        pop(didPerformWorkStackCursor, workInProgress);
-        pop(contextStackCursor, workInProgress);
-        push(contextStackCursor, mergedContext, workInProgress);
-      } else pop(didPerformWorkStackCursor, workInProgress);
-      push(didPerformWorkStackCursor, didChange, workInProgress);
-    },
-    findCurrentUnmaskedContext: function(fiber) {
-      for (
-        invariant(
-          2 === isFiberMountedImpl(fiber) && 2 === fiber.tag,
-          "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
-        );
-        3 !== fiber.tag;
-
-      ) {
-        if (isContextProvider(fiber))
-          return fiber.stateNode.__reactInternalMemoizedMergedChildContext;
-        fiber = fiber.return;
-        invariant(
-          fiber,
-          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
-        );
-      }
-      return fiber.stateNode.context;
-    }
-  };
+  }
 }
-function ReactFiberNewContext(stack, isPrimaryRenderer) {
-  var createCursor = stack.createCursor,
-    push = stack.push,
-    pop = stack.pop,
-    providerCursor = createCursor(null),
-    valueCursor = createCursor(null),
-    changedBitsCursor = createCursor(0);
-  return {
-    pushProvider: function(providerFiber) {
-      var context = providerFiber.type._context;
-      isPrimaryRenderer
-        ? (push(changedBitsCursor, context._changedBits, providerFiber),
-          push(valueCursor, context._currentValue, providerFiber),
-          push(providerCursor, providerFiber, providerFiber),
-          (context._currentValue = providerFiber.pendingProps.value),
-          (context._changedBits = providerFiber.stateNode))
-        : (push(changedBitsCursor, context._changedBits2, providerFiber),
-          push(valueCursor, context._currentValue2, providerFiber),
-          push(providerCursor, providerFiber, providerFiber),
-          (context._currentValue2 = providerFiber.pendingProps.value),
-          (context._changedBits2 = providerFiber.stateNode));
-    },
-    popProvider: function(providerFiber) {
-      var changedBits = changedBitsCursor.current,
-        currentValue = valueCursor.current;
-      pop(providerCursor, providerFiber);
-      pop(valueCursor, providerFiber);
-      pop(changedBitsCursor, providerFiber);
-      providerFiber = providerFiber.type._context;
-      isPrimaryRenderer
-        ? ((providerFiber._currentValue = currentValue),
-          (providerFiber._changedBits = changedBits))
-        : ((providerFiber._currentValue2 = currentValue),
-          (providerFiber._changedBits2 = changedBits));
-    },
-    getContextCurrentValue: function(context) {
-      return isPrimaryRenderer ? context._currentValue : context._currentValue2;
-    },
-    getContextChangedBits: function(context) {
-      return isPrimaryRenderer ? context._changedBits : context._changedBits2;
-    }
+function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+  expirationTime = createUpdate(expirationTime);
+  expirationTime.tag = 3;
+  expirationTime.payload = { element: null };
+  var error = errorInfo.value;
+  expirationTime.callback = function() {
+    onUncaughtError(error);
+    logError(fiber, errorInfo);
   };
+  return expirationTime;
 }
-function ReactFiberStack() {
-  var valueStack = [],
-    index = -1;
-  return {
-    createCursor: function(defaultValue) {
-      return { current: defaultValue };
-    },
-    isEmpty: function() {
-      return -1 === index;
-    },
-    pop: function(cursor) {
-      0 > index ||
-        ((cursor.current = valueStack[index]),
-        (valueStack[index] = null),
-        index--);
-    },
-    push: function(cursor, value) {
-      index++;
-      valueStack[index] = cursor.current;
-      cursor.current = value;
-    },
-    checkThatStackIsEmpty: function() {},
-    resetStackAfterFatalErrorInDev: function() {}
-  };
+function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+  expirationTime = createUpdate(expirationTime);
+  expirationTime.tag = 3;
+  var inst = fiber.stateNode;
+  null !== inst &&
+    "function" === typeof inst.componentDidCatch &&
+    (expirationTime.callback = function() {
+      null === legacyErrorBoundariesThatAlreadyFailed
+        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([this]))
+        : legacyErrorBoundariesThatAlreadyFailed.add(this);
+      var error = errorInfo.value,
+        stack = errorInfo.stack;
+      logError(fiber, errorInfo);
+      this.componentDidCatch(error, {
+        componentStack: null !== stack ? stack : ""
+      });
+    });
+  return expirationTime;
 }
-function ReactFiberScheduler(config) {
-  function resetStack() {
-    if (null !== nextUnitOfWork)
-      for (
-        var interruptedWork = nextUnitOfWork.return;
-        null !== interruptedWork;
-
-      )
-        unwindInterruptedWork(interruptedWork),
-          (interruptedWork = interruptedWork.return);
-    nextRoot = null;
-    nextRenderExpirationTime = 0;
-    nextLatestTimeoutMs = -1;
-    nextRenderIsExpired = !1;
-    nextUnitOfWork = null;
-    isRootReadyForCommit = !1;
-  }
-  function isAlreadyFailedLegacyErrorBoundary(instance) {
-    return (
-      null !== legacyErrorBoundariesThatAlreadyFailed &&
-      legacyErrorBoundariesThatAlreadyFailed.has(instance)
-    );
-  }
-  function markLegacyErrorBoundaryAsFailed(instance) {
-    null === legacyErrorBoundariesThatAlreadyFailed
-      ? (legacyErrorBoundariesThatAlreadyFailed = new Set([instance]))
-      : legacyErrorBoundariesThatAlreadyFailed.add(instance);
+function unwindWork(workInProgress) {
+  switch (workInProgress.tag) {
+    case 2:
+      popContextProvider(workInProgress);
+      var effectTag = workInProgress.effectTag;
+      return effectTag & 1024
+        ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+          workInProgress)
+        : null;
+    case 3:
+      return (
+        popHostContainer(workInProgress),
+        popTopLevelContextObject(workInProgress),
+        (effectTag = workInProgress.effectTag),
+        effectTag & 1024
+          ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+            workInProgress)
+          : null
+      );
+    case 5:
+      return popHostContext(workInProgress), null;
+    case 16:
+      return (
+        (effectTag = workInProgress.effectTag),
+        effectTag & 1024
+          ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+            workInProgress)
+          : null
+      );
+    case 4:
+      return popHostContainer(workInProgress), null;
+    case 13:
+      return popProvider(workInProgress), null;
+    default:
+      return null;
   }
-  function completeUnitOfWork(workInProgress$jscomp$0) {
-    for (;;) {
-      var current = workInProgress$jscomp$0.alternate,
-        returnFiber = workInProgress$jscomp$0.return,
-        siblingFiber = workInProgress$jscomp$0.sibling;
-      if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
-        current = completeWork(
-          current,
-          workInProgress$jscomp$0,
-          nextRenderExpirationTime
-        );
-        var workInProgress = workInProgress$jscomp$0;
-        if (
-          1073741823 === nextRenderExpirationTime ||
-          1073741823 !== workInProgress.expirationTime
-        ) {
-          var newExpirationTime = 0;
-          switch (workInProgress.tag) {
-            case 3:
-            case 2:
-              var updateQueue = workInProgress.updateQueue;
-              null !== updateQueue &&
-                (newExpirationTime = updateQueue.expirationTime);
-          }
-          for (updateQueue = workInProgress.child; null !== updateQueue; )
-            0 !== updateQueue.expirationTime &&
-              (0 === newExpirationTime ||
-                newExpirationTime > updateQueue.expirationTime) &&
-              (newExpirationTime = updateQueue.expirationTime),
-              (updateQueue = updateQueue.sibling);
-          workInProgress.expirationTime = newExpirationTime;
-        }
-        if (null !== current) return current;
-        null !== returnFiber &&
-          0 === (returnFiber.effectTag & 512) &&
-          (null === returnFiber.firstEffect &&
-            (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
-          null !== workInProgress$jscomp$0.lastEffect &&
-            (null !== returnFiber.lastEffect &&
-              (returnFiber.lastEffect.nextEffect =
-                workInProgress$jscomp$0.firstEffect),
-            (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
-          1 < workInProgress$jscomp$0.effectTag &&
-            (null !== returnFiber.lastEffect
-              ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
-              : (returnFiber.firstEffect = workInProgress$jscomp$0),
-            (returnFiber.lastEffect = workInProgress$jscomp$0)));
-        if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
-        else {
-          isRootReadyForCommit = !0;
+}
+var originalStartTimeMs = now$1(),
+  mostRecentCurrentTime = 2,
+  mostRecentCurrentTimeMs = originalStartTimeMs,
+  lastUniqueAsyncExpiration = 0,
+  expirationContext = 0,
+  isWorking = !1,
+  nextUnitOfWork = null,
+  nextRoot = null,
+  nextRenderExpirationTime = 0,
+  nextLatestTimeoutMs = -1,
+  nextRenderDidError = !1,
+  nextEffect = null,
+  isCommitting$1 = !1,
+  legacyErrorBoundariesThatAlreadyFailed = null;
+function resetStack() {
+  if (null !== nextUnitOfWork)
+    for (
+      var interruptedWork = nextUnitOfWork.return;
+      null !== interruptedWork;
+
+    ) {
+      var interruptedWork$jscomp$0 = interruptedWork;
+      switch (interruptedWork$jscomp$0.tag) {
+        case 2:
+          popContextProvider(interruptedWork$jscomp$0);
           break;
-        }
-      } else {
-        workInProgress$jscomp$0 = unwindWork(
-          workInProgress$jscomp$0,
-          nextRenderIsExpired,
-          nextRenderExpirationTime
-        );
-        if (null !== workInProgress$jscomp$0)
-          return (
-            (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
-          );
-        null !== returnFiber &&
-          ((returnFiber.firstEffect = returnFiber.lastEffect = null),
-          (returnFiber.effectTag |= 512));
-        if (null !== siblingFiber) return siblingFiber;
-        if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
-        else break;
+        case 3:
+          popHostContainer(interruptedWork$jscomp$0);
+          popTopLevelContextObject(interruptedWork$jscomp$0);
+          break;
+        case 5:
+          popHostContext(interruptedWork$jscomp$0);
+          break;
+        case 4:
+          popHostContainer(interruptedWork$jscomp$0);
+          break;
+        case 13:
+          popProvider(interruptedWork$jscomp$0);
       }
+      interruptedWork = interruptedWork.return;
     }
-    return null;
-  }
-  function performUnitOfWork(workInProgress) {
-    var next = beginWork(
-      workInProgress.alternate,
-      workInProgress,
-      nextRenderExpirationTime
-    );
-    null === next && (next = completeUnitOfWork(workInProgress));
-    ReactCurrentOwner.current = null;
-    return next;
-  }
-  function renderRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isWorking,
-      "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
-    );
-    isWorking = !0;
-    if (
-      expirationTime !== nextRenderExpirationTime ||
-      root !== nextRoot ||
-      null === nextUnitOfWork
-    )
-      resetStack(),
-        (nextRoot = root),
-        (nextRenderExpirationTime = expirationTime),
-        (nextLatestTimeoutMs = -1),
-        (nextUnitOfWork = createWorkInProgress(
-          nextRoot.current,
-          null,
-          nextRenderExpirationTime
-        )),
-        (root.pendingCommitExpirationTime = 0);
-    var didFatal = !1;
-    nextRenderIsExpired =
-      !isAsync || nextRenderExpirationTime <= mostRecentCurrentTime;
-    do {
-      try {
-        if (isAsync)
-          for (; null !== nextUnitOfWork && !shouldYield(); )
-            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-        else
-          for (; null !== nextUnitOfWork; )
-            nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
-      } catch (thrownValue) {
-        if (null === nextUnitOfWork)
-          (didFatal = !0), onUncaughtError(thrownValue);
-        else {
-          invariant(
-            null !== nextUnitOfWork,
-            "Failed to replay rendering after an error. This is likely caused by a bug in React. Please file an issue with a reproducing case to help us find it."
-          );
-          isAsync = nextUnitOfWork;
-          var returnFiber = isAsync.return;
-          if (null === returnFiber) {
-            didFatal = !0;
-            onUncaughtError(thrownValue);
-            break;
-          }
-          throwException(
-            root,
-            returnFiber,
-            isAsync,
-            thrownValue,
-            nextRenderIsExpired,
-            nextRenderExpirationTime,
-            mostRecentCurrentTimeMs
-          );
-          nextUnitOfWork = completeUnitOfWork(isAsync);
+  nextRoot = null;
+  nextRenderExpirationTime = 0;
+  nextLatestTimeoutMs = -1;
+  nextRenderDidError = !1;
+  nextUnitOfWork = null;
+}
+function completeUnitOfWork(workInProgress$jscomp$0) {
+  for (;;) {
+    var current = workInProgress$jscomp$0.alternate,
+      returnFiber = workInProgress$jscomp$0.return,
+      siblingFiber = workInProgress$jscomp$0.sibling;
+    if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
+      current = completeWork(
+        current,
+        workInProgress$jscomp$0,
+        nextRenderExpirationTime
+      );
+      var workInProgress = workInProgress$jscomp$0;
+      if (
+        1073741823 === nextRenderExpirationTime ||
+        1073741823 !== workInProgress.expirationTime
+      ) {
+        var newExpirationTime = 0;
+        switch (workInProgress.tag) {
+          case 3:
+          case 2:
+            var updateQueue = workInProgress.updateQueue;
+            null !== updateQueue &&
+              (newExpirationTime = updateQueue.expirationTime);
         }
+        for (updateQueue = workInProgress.child; null !== updateQueue; )
+          0 !== updateQueue.expirationTime &&
+            (0 === newExpirationTime ||
+              newExpirationTime > updateQueue.expirationTime) &&
+            (newExpirationTime = updateQueue.expirationTime),
+            (updateQueue = updateQueue.sibling);
+        workInProgress.expirationTime = newExpirationTime;
       }
-      break;
-    } while (1);
-    isWorking = !1;
-    if (didFatal) return null;
-    if (null === nextUnitOfWork) {
-      if (isRootReadyForCommit)
+      if (null !== current) return current;
+      null !== returnFiber &&
+        0 === (returnFiber.effectTag & 512) &&
+        (null === returnFiber.firstEffect &&
+          (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
+        null !== workInProgress$jscomp$0.lastEffect &&
+          (null !== returnFiber.lastEffect &&
+            (returnFiber.lastEffect.nextEffect =
+              workInProgress$jscomp$0.firstEffect),
+          (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
+        1 < workInProgress$jscomp$0.effectTag &&
+          (null !== returnFiber.lastEffect
+            ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
+            : (returnFiber.firstEffect = workInProgress$jscomp$0),
+          (returnFiber.lastEffect = workInProgress$jscomp$0)));
+    } else {
+      workInProgress$jscomp$0 = unwindWork(
+        workInProgress$jscomp$0,
+        nextRenderExpirationTime
+      );
+      if (null !== workInProgress$jscomp$0)
         return (
-          (root.pendingCommitExpirationTime = expirationTime),
-          root.current.alternate
+          (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
         );
-      invariant(
-        !nextRenderIsExpired,
-        "Expired work should have completed. This error is likely caused by a bug in React. Please file an issue."
-      );
-      0 <= nextLatestTimeoutMs &&
-        setTimeout(function() {
-          retrySuspendedRoot(root, expirationTime);
-        }, nextLatestTimeoutMs);
-      onBlock(root.current.expirationTime);
+      null !== returnFiber &&
+        ((returnFiber.firstEffect = returnFiber.lastEffect = null),
+        (returnFiber.effectTag |= 512));
     }
-    return null;
+    if (null !== siblingFiber) return siblingFiber;
+    if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+    else break;
   }
-  function onCommitPhaseError(fiber, error) {
-    var JSCompiler_inline_result;
-    a: {
-      invariant(
-        !isWorking || isCommitting,
-        "dispatch: Cannot dispatch during the render phase."
-      );
-      for (
-        JSCompiler_inline_result = fiber.return;
-        null !== JSCompiler_inline_result;
+  return null;
+}
+function performUnitOfWork(workInProgress) {
+  var next = beginWork(
+    workInProgress.alternate,
+    workInProgress,
+    nextRenderExpirationTime
+  );
+  null === next && (next = completeUnitOfWork(workInProgress));
+  ReactCurrentOwner.current = null;
+  return next;
+}
+function renderRoot(root$jscomp$0, isYieldy) {
+  invariant(
+    !isWorking,
+    "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+  );
+  isWorking = !0;
+  var expirationTime = root$jscomp$0.nextExpirationTimeToWorkOn;
+  if (
+    expirationTime !== nextRenderExpirationTime ||
+    root$jscomp$0 !== nextRoot ||
+    null === nextUnitOfWork
+  )
+    resetStack(),
+      (nextRoot = root$jscomp$0),
+      (nextRenderExpirationTime = expirationTime),
+      (nextLatestTimeoutMs = -1),
+      (nextRenderDidError = !1),
+      (nextUnitOfWork = createWorkInProgress(
+        nextRoot.current,
+        null,
+        nextRenderExpirationTime
+      )),
+      (root$jscomp$0.pendingCommitExpirationTime = 0);
+  var didFatal = !1;
+  do {
+    try {
+      if (isYieldy)
+        for (; null !== nextUnitOfWork && !shouldYield(); )
+          nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+      else
+        for (; null !== nextUnitOfWork; )
+          nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+    } catch (thrownValue) {
+      if (null === nextUnitOfWork)
+        (didFatal = !0), onUncaughtError(thrownValue);
+      else {
+        invariant(
+          null !== nextUnitOfWork,
+          "Failed to replay rendering after an error. This is likely caused by a bug in React. Please file an issue with a reproducing case to help us find it."
+        );
+        isYieldy = nextUnitOfWork;
+        var returnFiber = isYieldy.return;
+        if (null === returnFiber) {
+          didFatal = !0;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        a: {
+          var root = root$jscomp$0,
+            returnFiber$jscomp$0 = returnFiber,
+            sourceFiber = isYieldy,
+            value = thrownValue;
+          returnFiber = nextRenderExpirationTime;
+          sourceFiber.effectTag |= 512;
+          sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+          nextRenderDidError = !0;
+          if (
+            (root.didError || 1 === returnFiber) &&
+            (returnFiber === root.latestPendingTime ||
+              returnFiber === root.latestSuspendedTime)
+          ) {
+            value = createCapturedValue(value, sourceFiber);
+            root = returnFiber$jscomp$0;
+            do {
+              switch (root.tag) {
+                case 3:
+                  root.effectTag |= 1024;
+                  value = createRootErrorUpdate(root, value, returnFiber);
+                  enqueueCapturedUpdate(root, value, returnFiber);
+                  break a;
+                case 2:
+                  if (
+                    ((returnFiber$jscomp$0 = value),
+                    (sourceFiber = root.stateNode),
+                    0 === (root.effectTag & 64) &&
+                      null !== sourceFiber &&
+                      "function" === typeof sourceFiber.componentDidCatch &&
+                      (null === legacyErrorBoundariesThatAlreadyFailed ||
+                        !legacyErrorBoundariesThatAlreadyFailed.has(
+                          sourceFiber
+                        )))
+                  ) {
+                    root.effectTag |= 1024;
+                    value = createClassErrorUpdate(
+                      root,
+                      returnFiber$jscomp$0,
+                      returnFiber
+                    );
+                    enqueueCapturedUpdate(root, value, returnFiber);
+                    break a;
+                  }
+              }
+              root = root.return;
+            } while (null !== root);
+          }
+        }
+        nextUnitOfWork = completeUnitOfWork(isYieldy);
+      }
+    }
+    break;
+  } while (1);
+  isWorking = !1;
+  didFatal
+    ? (root$jscomp$0.finishedWork = null)
+    : null === nextUnitOfWork
+      ? ((didFatal = root$jscomp$0.current.alternate),
+        invariant(
+          null !== didFatal,
+          "Finished root should have a work-in-progress. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        0 === (didFatal.effectTag & 512)
+          ? ((root$jscomp$0.pendingCommitExpirationTime = expirationTime),
+            (root$jscomp$0.finishedWork = didFatal))
+          : (!nextRenderDidError ||
+            (expirationTime !== root$jscomp$0.latestPendingTime &&
+              expirationTime !== root$jscomp$0.latestSuspendedTime)
+              ? ((didFatal = root$jscomp$0.earliestPendingTime),
+                (isYieldy = root$jscomp$0.latestPendingTime),
+                didFatal === expirationTime
+                  ? (root$jscomp$0.earliestPendingTime =
+                      isYieldy === expirationTime
+                        ? (root$jscomp$0.latestPendingTime = 0)
+                        : isYieldy)
+                  : isYieldy === expirationTime &&
+                    (root$jscomp$0.latestPendingTime = didFatal),
+                (didFatal = root$jscomp$0.latestSuspendedTime),
+                didFatal === expirationTime &&
+                  (root$jscomp$0.latestPingedTime = 0),
+                (isYieldy = root$jscomp$0.earliestSuspendedTime),
+                0 === isYieldy
+                  ? (root$jscomp$0.earliestSuspendedTime = root$jscomp$0.latestSuspendedTime = expirationTime)
+                  : isYieldy > expirationTime
+                    ? (root$jscomp$0.earliestSuspendedTime = expirationTime)
+                    : didFatal < expirationTime &&
+                      (root$jscomp$0.latestSuspendedTime = expirationTime))
+              : (root$jscomp$0.didError = !0),
+            findNextPendingPriorityLevel(root$jscomp$0),
+            onSuspend(
+              root$jscomp$0,
+              expirationTime,
+              root$jscomp$0.expirationTime,
+              nextLatestTimeoutMs
+            )))
+      : (root$jscomp$0.finishedWork = null);
+}
+function captureCommitPhaseError(fiber, error) {
+  var JSCompiler_inline_result;
+  a: {
+    invariant(
+      !isWorking || isCommitting$1,
+      "dispatch: Cannot dispatch during the render phase."
+    );
+    for (
+      JSCompiler_inline_result = fiber.return;
+      null !== JSCompiler_inline_result;
 
-      ) {
-        switch (JSCompiler_inline_result.tag) {
-          case 2:
-            var instance = JSCompiler_inline_result.stateNode;
-            if (
-              "function" ===
-                typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
-              ("function" === typeof instance.componentDidCatch &&
-                !isAlreadyFailedLegacyErrorBoundary(instance))
-            ) {
-              fiber = createCapturedValue(error, fiber);
-              fiber = createClassErrorUpdate(
-                JSCompiler_inline_result,
-                fiber,
-                1
-              );
-              enqueueUpdate(JSCompiler_inline_result, fiber, 1);
-              scheduleWork(JSCompiler_inline_result, 1);
-              JSCompiler_inline_result = void 0;
-              break a;
-            }
-            break;
-          case 3:
+    ) {
+      switch (JSCompiler_inline_result.tag) {
+        case 2:
+          var instance = JSCompiler_inline_result.stateNode;
+          if (
+            "function" ===
+              typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
+            ("function" === typeof instance.componentDidCatch &&
+              (null === legacyErrorBoundariesThatAlreadyFailed ||
+                !legacyErrorBoundariesThatAlreadyFailed.has(instance)))
+          ) {
             fiber = createCapturedValue(error, fiber);
-            fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+            fiber = createClassErrorUpdate(JSCompiler_inline_result, fiber, 1);
             enqueueUpdate(JSCompiler_inline_result, fiber, 1);
             scheduleWork(JSCompiler_inline_result, 1);
             JSCompiler_inline_result = void 0;
             break a;
-        }
-        JSCompiler_inline_result = JSCompiler_inline_result.return;
+          }
+          break;
+        case 3:
+          fiber = createCapturedValue(error, fiber);
+          fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+          enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+          scheduleWork(JSCompiler_inline_result, 1);
+          JSCompiler_inline_result = void 0;
+          break a;
       }
-      3 === fiber.tag &&
-        ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
-        (JSCompiler_inline_result = createRootErrorUpdate(
-          fiber,
-          JSCompiler_inline_result,
-          1
-        )),
-        enqueueUpdate(fiber, JSCompiler_inline_result, 1),
-        scheduleWork(fiber, 1));
-      JSCompiler_inline_result = void 0;
-    }
-    return JSCompiler_inline_result;
-  }
-  function computeExpirationForFiber(currentTime, fiber) {
-    currentTime =
-      0 !== expirationContext
-        ? expirationContext
-        : isWorking
-          ? isCommitting ? 1 : nextRenderExpirationTime
-          : fiber.mode & 1
-            ? isBatchingInteractiveUpdates
-              ? 2 + 10 * ((((currentTime - 2 + 15) / 10) | 0) + 1)
-              : 2 + 25 * ((((currentTime - 2 + 500) / 25) | 0) + 1)
-            : 1;
-    isBatchingInteractiveUpdates &&
-      (0 === lowestPendingInteractiveExpirationTime ||
-        currentTime > lowestPendingInteractiveExpirationTime) &&
-      (lowestPendingInteractiveExpirationTime = currentTime);
-    return currentTime;
-  }
-  function retrySuspendedRoot(root) {
-    var retryTime = root.current.expirationTime;
-    0 !== retryTime &&
-      (0 === root.remainingExpirationTime ||
-        root.remainingExpirationTime < retryTime) &&
-      requestWork(root, retryTime);
-  }
-  function scheduleWork(fiber, expirationTime) {
-    for (; null !== fiber; ) {
-      if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
-        fiber.expirationTime = expirationTime;
-      null !== fiber.alternate &&
-        (0 === fiber.alternate.expirationTime ||
-          fiber.alternate.expirationTime > expirationTime) &&
-        (fiber.alternate.expirationTime = expirationTime);
-      if (null === fiber.return)
-        if (3 === fiber.tag) {
-          var root = fiber.stateNode;
-          !isWorking &&
-            0 !== nextRenderExpirationTime &&
-            expirationTime < nextRenderExpirationTime &&
-            resetStack();
-          var nextExpirationTimeToWorkOn = root.current.expirationTime;
-          (isWorking && !isCommitting && nextRoot === root) ||
-            requestWork(root, nextExpirationTimeToWorkOn);
-          nestedUpdateCount > NESTED_UPDATE_LIMIT &&
-            invariant(
-              !1,
-              "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
-            );
-        } else break;
-      fiber = fiber.return;
-    }
-  }
-  function recalculateCurrentTime() {
-    mostRecentCurrentTimeMs = now() - originalStartTimeMs;
-    return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
-  }
-  function syncUpdates(fn, a, b, c, d) {
-    var previousExpirationContext = expirationContext;
-    expirationContext = 1;
-    try {
-      return fn(a, b, c, d);
-    } finally {
-      expirationContext = previousExpirationContext;
-    }
-  }
-  function scheduleCallbackWithExpiration(expirationTime) {
-    if (0 !== callbackExpirationTime) {
-      if (expirationTime > callbackExpirationTime) return;
-      cancelDeferredCallback(callbackID);
-    }
-    var currentMs = now() - originalStartTimeMs;
-    callbackExpirationTime = expirationTime;
-    callbackID = scheduleDeferredCallback(performAsyncWork, {
-      timeout: 10 * (expirationTime - 2) - currentMs
-    });
-  }
-  function requestWork(root, expirationTime) {
-    if (null === root.nextScheduledRoot)
-      (root.remainingExpirationTime = expirationTime),
-        null === lastScheduledRoot
-          ? ((firstScheduledRoot = lastScheduledRoot = root),
-            (root.nextScheduledRoot = root))
-          : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
-            (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
-    else {
-      var remainingExpirationTime = root.remainingExpirationTime;
-      if (
-        0 === remainingExpirationTime ||
-        expirationTime < remainingExpirationTime
-      )
-        root.remainingExpirationTime = expirationTime;
+      JSCompiler_inline_result = JSCompiler_inline_result.return;
     }
-    isRendering ||
-      (isBatchingUpdates
-        ? isUnbatchingUpdates &&
-          ((nextFlushedRoot = root),
-          (nextFlushedExpirationTime = 1),
-          performWorkOnRoot(root, 1, !1))
-        : 1 === expirationTime
-          ? performSyncWork()
-          : scheduleCallbackWithExpiration(expirationTime));
+    3 === fiber.tag &&
+      ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
+      (JSCompiler_inline_result = createRootErrorUpdate(
+        fiber,
+        JSCompiler_inline_result,
+        1
+      )),
+      enqueueUpdate(fiber, JSCompiler_inline_result, 1),
+      scheduleWork(fiber, 1));
+    JSCompiler_inline_result = void 0;
   }
-  function findHighestPriorityRoot() {
-    var highestPriorityWork = 0,
-      highestPriorityRoot = null;
-    if (null !== lastScheduledRoot)
-      for (
-        var previousScheduledRoot = lastScheduledRoot,
-          root = firstScheduledRoot;
-        null !== root;
-
-      ) {
-        var remainingExpirationTime = root.remainingExpirationTime;
-        if (0 === remainingExpirationTime) {
+  return JSCompiler_inline_result;
+}
+function computeExpirationForFiber(currentTime, fiber) {
+  currentTime =
+    0 !== expirationContext
+      ? expirationContext
+      : isWorking
+        ? isCommitting$1 ? 1 : nextRenderExpirationTime
+        : fiber.mode & 1
+          ? isBatchingInteractiveUpdates
+            ? 2 + 10 * ((((currentTime - 2 + 15) / 10) | 0) + 1)
+            : 2 + 25 * ((((currentTime - 2 + 500) / 25) | 0) + 1)
+          : 1;
+  isBatchingInteractiveUpdates &&
+    (0 === lowestPendingInteractiveExpirationTime ||
+      currentTime > lowestPendingInteractiveExpirationTime) &&
+    (lowestPendingInteractiveExpirationTime = currentTime);
+  return currentTime;
+}
+function scheduleWork(fiber, expirationTime) {
+  for (; null !== fiber; ) {
+    if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
+      fiber.expirationTime = expirationTime;
+    null !== fiber.alternate &&
+      (0 === fiber.alternate.expirationTime ||
+        fiber.alternate.expirationTime > expirationTime) &&
+      (fiber.alternate.expirationTime = expirationTime);
+    if (null === fiber.return)
+      if (3 === fiber.tag) {
+        var root = fiber.stateNode;
+        !isWorking &&
+          0 !== nextRenderExpirationTime &&
+          expirationTime < nextRenderExpirationTime &&
+          resetStack();
+        markPendingPriorityLevel(root, expirationTime);
+        (isWorking && !isCommitting$1 && nextRoot === root) ||
+          requestWork(root, root.expirationTime);
+        nestedUpdateCount > NESTED_UPDATE_LIMIT &&
           invariant(
-            null !== previousScheduledRoot && null !== lastScheduledRoot,
-            "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
+            !1,
+            "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
           );
-          if (root === root.nextScheduledRoot) {
-            firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
-            break;
-          } else if (root === firstScheduledRoot)
-            (firstScheduledRoot = remainingExpirationTime =
-              root.nextScheduledRoot),
-              (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
-              (root.nextScheduledRoot = null);
-          else if (root === lastScheduledRoot) {
-            lastScheduledRoot = previousScheduledRoot;
-            lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
-            root.nextScheduledRoot = null;
-            break;
-          } else
-            (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
-              (root.nextScheduledRoot = null);
-          root = previousScheduledRoot.nextScheduledRoot;
-        } else {
-          if (
-            0 === highestPriorityWork ||
-            remainingExpirationTime < highestPriorityWork
-          )
-            (highestPriorityWork = remainingExpirationTime),
-              (highestPriorityRoot = root);
-          if (root === lastScheduledRoot) break;
-          previousScheduledRoot = root;
-          root = root.nextScheduledRoot;
-        }
-      }
-    previousScheduledRoot = nextFlushedRoot;
-    null !== previousScheduledRoot &&
-    previousScheduledRoot === highestPriorityRoot &&
-    1 === highestPriorityWork
-      ? nestedUpdateCount++
-      : (nestedUpdateCount = 0);
-    nextFlushedRoot = highestPriorityRoot;
-    nextFlushedExpirationTime = highestPriorityWork;
-  }
-  function performAsyncWork(dl) {
-    performWork(0, !0, dl);
+      } else break;
+    fiber = fiber.return;
   }
-  function performSyncWork() {
-    performWork(1, !1, null);
-  }
-  function performWork(minExpirationTime, isAsync, dl) {
-    deadline = dl;
-    findHighestPriorityRoot();
-    if (isAsync)
-      for (
-        ;
-        null !== nextFlushedRoot &&
-        0 !== nextFlushedExpirationTime &&
-        (0 === minExpirationTime ||
-          minExpirationTime >= nextFlushedExpirationTime) &&
-        (!deadlineDidExpire ||
-          recalculateCurrentTime() >= nextFlushedExpirationTime);
-
-      )
-        recalculateCurrentTime(),
-          performWorkOnRoot(
-            nextFlushedRoot,
-            nextFlushedExpirationTime,
-            !deadlineDidExpire
-          ),
-          findHighestPriorityRoot();
-    else
-      for (
-        ;
-        null !== nextFlushedRoot &&
-        0 !== nextFlushedExpirationTime &&
-        (0 === minExpirationTime ||
-          minExpirationTime >= nextFlushedExpirationTime);
-
-      )
-        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
-          findHighestPriorityRoot();
-    null !== deadline && ((callbackExpirationTime = 0), (callbackID = -1));
-    0 !== nextFlushedExpirationTime &&
-      scheduleCallbackWithExpiration(nextFlushedExpirationTime);
-    deadline = null;
-    deadlineDidExpire = !1;
-    finishRendering();
+}
+function recalculateCurrentTime() {
+  mostRecentCurrentTimeMs = now$1() - originalStartTimeMs;
+  return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
+}
+function syncUpdates(fn, a, b, c, d) {
+  var previousExpirationContext = expirationContext;
+  expirationContext = 1;
+  try {
+    return fn(a, b, c, d);
+  } finally {
+    expirationContext = previousExpirationContext;
   }
-  function finishRendering() {
-    nestedUpdateCount = 0;
-    if (null !== completedBatches) {
-      var batches = completedBatches;
-      completedBatches = null;
-      for (var i = 0; i < batches.length; i++) {
-        var batch = batches[i];
-        try {
-          batch._onComplete();
-        } catch (error) {
-          hasUnhandledError ||
-            ((hasUnhandledError = !0), (unhandledError = error));
-        }
-      }
+}
+var firstScheduledRoot = null,
+  lastScheduledRoot = null,
+  callbackExpirationTime = 0,
+  callbackID = void 0,
+  isRendering = !1,
+  nextFlushedRoot = null,
+  nextFlushedExpirationTime = 0,
+  lowestPendingInteractiveExpirationTime = 0,
+  deadlineDidExpire = !1,
+  hasUnhandledError = !1,
+  unhandledError = null,
+  deadline = null,
+  isBatchingUpdates = !1,
+  isUnbatchingUpdates = !1,
+  isBatchingInteractiveUpdates = !1,
+  completedBatches = null,
+  NESTED_UPDATE_LIMIT = 1e3,
+  nestedUpdateCount = 0,
+  timeHeuristicForUnitOfWork = 1;
+function scheduleCallbackWithExpirationTime(expirationTime) {
+  if (0 !== callbackExpirationTime) {
+    if (expirationTime > callbackExpirationTime) return;
+    if (null !== callbackID) {
+      var callbackID$jscomp$0 = callbackID;
+      scheduledCallback = null;
+      clearTimeout(callbackID$jscomp$0);
     }
-    if (hasUnhandledError)
-      throw ((batches = unhandledError),
-      (unhandledError = null),
-      (hasUnhandledError = !1),
-      batches);
-  }
-  function performWorkOnRoot(root, expirationTime, isAsync) {
-    invariant(
-      !isRendering,
-      "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
-    );
-    isRendering = !0;
-    isAsync
-      ? ((isAsync = root.finishedWork),
-        null !== isAsync
-          ? completeRoot(root, isAsync, expirationTime)
-          : ((root.finishedWork = null),
-            (isAsync = renderRoot(root, expirationTime, !0)),
-            null !== isAsync &&
-              (shouldYield()
-                ? (root.finishedWork = isAsync)
-                : completeRoot(root, isAsync, expirationTime))))
-      : ((isAsync = root.finishedWork),
-        null !== isAsync
-          ? completeRoot(root, isAsync, expirationTime)
-          : ((root.finishedWork = null),
-            (isAsync = renderRoot(root, expirationTime, !1)),
-            null !== isAsync && completeRoot(root, isAsync, expirationTime)));
-    isRendering = !1;
   }
-  function completeRoot(root, finishedWork, expirationTime) {
-    var firstBatch = root.firstBatch;
+  callbackExpirationTime = expirationTime;
+  now$1();
+  scheduledCallback = performAsyncWork;
+  callbackID = setTimeout(setTimeoutCallback, 1);
+}
+function onSuspend(root, suspendedExpirationTime, expirationTime, timeoutMs) {
+  0 <= timeoutMs &&
+    setTimeout(function() {
+      var latestSuspendedTime = root.latestSuspendedTime;
+      0 !== latestSuspendedTime &&
+        latestSuspendedTime <= suspendedExpirationTime &&
+        ((latestSuspendedTime = root.latestPingedTime),
+        0 === latestSuspendedTime ||
+          latestSuspendedTime < suspendedExpirationTime) &&
+        (root.latestPingedTime = suspendedExpirationTime);
+      findNextPendingPriorityLevel(root);
+      latestSuspendedTime = root.expirationTime;
+      0 !== latestSuspendedTime && requestWork(root, latestSuspendedTime);
+    }, timeoutMs);
+  root.expirationTime = expirationTime;
+}
+function requestWork(root, expirationTime) {
+  if (null === root.nextScheduledRoot)
+    (root.expirationTime = expirationTime),
+      null === lastScheduledRoot
+        ? ((firstScheduledRoot = lastScheduledRoot = root),
+          (root.nextScheduledRoot = root))
+        : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
+          (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
+  else {
+    var remainingExpirationTime = root.expirationTime;
     if (
-      null !== firstBatch &&
-      firstBatch._expirationTime <= expirationTime &&
-      (null === completedBatches
-        ? (completedBatches = [firstBatch])
-        : completedBatches.push(firstBatch),
-      firstBatch._defer)
-    ) {
-      root.finishedWork = finishedWork;
-      root.remainingExpirationTime = 0;
-      return;
-    }
-    root.finishedWork = null;
-    isCommitting = isWorking = !0;
-    expirationTime = finishedWork.stateNode;
-    invariant(
-      expirationTime.current !== finishedWork,
-      "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
-    );
-    firstBatch = expirationTime.pendingCommitExpirationTime;
-    invariant(
-      0 !== firstBatch,
-      "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    expirationTime.pendingCommitExpirationTime = 0;
-    var currentTime = recalculateCurrentTime();
-    ReactCurrentOwner.current = null;
-    if (1 < finishedWork.effectTag)
-      if (null !== finishedWork.lastEffect) {
-        finishedWork.lastEffect.nextEffect = finishedWork;
-        var firstEffect = finishedWork.firstEffect;
-      } else firstEffect = finishedWork;
-    else firstEffect = finishedWork.firstEffect;
-    prepareForCommit(expirationTime.containerInfo);
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      var didError = !1,
-        error = void 0;
-      try {
-        for (; null !== nextEffect; )
-          nextEffect.effectTag & 256 &&
-            commitBeforeMutationLifeCycles(nextEffect.alternate, nextEffect),
-            (nextEffect = nextEffect.nextEffect);
-      } catch (e) {
-        (didError = !0), (error = e);
-      }
-      didError &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, error),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      didError = !1;
-      error = void 0;
-      try {
-        for (; null !== nextEffect; ) {
-          var effectTag = nextEffect.effectTag;
-          effectTag & 16 && commitResetTextContent(nextEffect);
-          if (effectTag & 128) {
-            var current = nextEffect.alternate;
-            null !== current && commitDetachRef(current);
-          }
-          switch (effectTag & 14) {
-            case 2:
-              commitPlacement(nextEffect);
-              nextEffect.effectTag &= -3;
-              break;
-            case 6:
-              commitPlacement(nextEffect);
-              nextEffect.effectTag &= -3;
-              commitWork(nextEffect.alternate, nextEffect);
-              break;
-            case 4:
-              commitWork(nextEffect.alternate, nextEffect);
-              break;
-            case 8:
-              commitDeletion(nextEffect);
-          }
-          nextEffect = nextEffect.nextEffect;
-        }
-      } catch (e) {
-        (didError = !0), (error = e);
-      }
-      didError &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, error),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
-    }
-    resetAfterCommit(expirationTime.containerInfo);
-    expirationTime.current = finishedWork;
-    for (nextEffect = firstEffect; null !== nextEffect; ) {
-      effectTag = !1;
-      current = void 0;
-      try {
-        for (
-          firstEffect = expirationTime,
-            didError = currentTime,
-            error = firstBatch;
-          null !== nextEffect;
+      0 === remainingExpirationTime ||
+      expirationTime < remainingExpirationTime
+    )
+      root.expirationTime = expirationTime;
+  }
+  isRendering ||
+    (isBatchingUpdates
+      ? isUnbatchingUpdates &&
+        ((nextFlushedRoot = root),
+        (nextFlushedExpirationTime = 1),
+        performWorkOnRoot(root, 1, !1))
+      : 1 === expirationTime
+        ? performWork(1, null)
+        : scheduleCallbackWithExpirationTime(expirationTime));
+}
+function findHighestPriorityRoot() {
+  var highestPriorityWork = 0,
+    highestPriorityRoot = null;
+  if (null !== lastScheduledRoot)
+    for (
+      var previousScheduledRoot = lastScheduledRoot, root = firstScheduledRoot;
+      null !== root;
 
-        ) {
-          var effectTag$jscomp$0 = nextEffect.effectTag;
-          effectTag$jscomp$0 & 36 &&
-            commitLifeCycles(
-              firstEffect,
-              nextEffect.alternate,
-              nextEffect,
-              didError,
-              error
-            );
-          effectTag$jscomp$0 & 128 && commitAttachRef(nextEffect);
-          var next = nextEffect.nextEffect;
-          nextEffect.nextEffect = null;
-          nextEffect = next;
-        }
-      } catch (e) {
-        (effectTag = !0), (current = e);
+    ) {
+      var remainingExpirationTime = root.expirationTime;
+      if (0 === remainingExpirationTime) {
+        invariant(
+          null !== previousScheduledRoot && null !== lastScheduledRoot,
+          "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
+        );
+        if (root === root.nextScheduledRoot) {
+          firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
+          break;
+        } else if (root === firstScheduledRoot)
+          (firstScheduledRoot = remainingExpirationTime =
+            root.nextScheduledRoot),
+            (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
+            (root.nextScheduledRoot = null);
+        else if (root === lastScheduledRoot) {
+          lastScheduledRoot = previousScheduledRoot;
+          lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+          root.nextScheduledRoot = null;
+          break;
+        } else
+          (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
+            (root.nextScheduledRoot = null);
+        root = previousScheduledRoot.nextScheduledRoot;
+      } else {
+        if (
+          0 === highestPriorityWork ||
+          remainingExpirationTime < highestPriorityWork
+        )
+          (highestPriorityWork = remainingExpirationTime),
+            (highestPriorityRoot = root);
+        if (root === lastScheduledRoot) break;
+        previousScheduledRoot = root;
+        root = root.nextScheduledRoot;
       }
-      effectTag &&
-        (invariant(
-          null !== nextEffect,
-          "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
-        ),
-        onCommitPhaseError(nextEffect, current),
-        null !== nextEffect && (nextEffect = nextEffect.nextEffect));
     }
-    isWorking = isCommitting = !1;
-    "function" === typeof onCommitRoot && onCommitRoot(finishedWork.stateNode);
-    finishedWork = expirationTime.current.expirationTime;
-    0 === finishedWork && (legacyErrorBoundariesThatAlreadyFailed = null);
-    root.remainingExpirationTime = finishedWork;
-  }
-  function shouldYield() {
-    return null === deadline ||
-      deadline.timeRemaining() > timeHeuristicForUnitOfWork
-      ? !1
-      : (deadlineDidExpire = !0);
-  }
-  function onUncaughtError(error) {
-    invariant(
-      null !== nextFlushedRoot,
-      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    nextFlushedRoot.remainingExpirationTime = 0;
-    hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
-  }
-  function onBlock(remainingExpirationTime) {
-    invariant(
-      null !== nextFlushedRoot,
-      "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
-    );
-    nextFlushedRoot.remainingExpirationTime = remainingExpirationTime;
-  }
-  var now = config.now,
-    scheduleDeferredCallback = config.scheduleDeferredCallback,
-    cancelDeferredCallback = config.cancelDeferredCallback,
-    prepareForCommit = config.prepareForCommit,
-    resetAfterCommit = config.resetAfterCommit,
-    stack = ReactFiberStack(),
-    hostContext = ReactFiberHostContext(config, stack),
-    legacyContext = ReactFiberLegacyContext(stack);
-  stack = ReactFiberNewContext(stack, config.isPrimaryRenderer);
-  var profilerTimer = createProfilerTimer(now),
-    hydrationContext = ReactFiberHydrationContext(config),
-    beginWork = ReactFiberBeginWork(
-      config,
-      hostContext,
-      legacyContext,
-      stack,
-      hydrationContext,
-      scheduleWork,
-      computeExpirationForFiber,
-      profilerTimer,
-      recalculateCurrentTime
-    ).beginWork,
-    completeWork = ReactFiberCompleteWork(
-      config,
-      hostContext,
-      legacyContext,
-      stack,
-      hydrationContext,
-      profilerTimer
-    ).completeWork;
-  hostContext = ReactFiberUnwindWork(
-    config,
-    hostContext,
-    legacyContext,
-    stack,
-    scheduleWork,
-    computeExpirationForFiber,
-    recalculateCurrentTime,
-    markLegacyErrorBoundaryAsFailed,
-    isAlreadyFailedLegacyErrorBoundary,
-    onUncaughtError,
-    profilerTimer,
-    function(root, thenable, timeoutMs) {
-      0 <= timeoutMs &&
-        nextLatestTimeoutMs < timeoutMs &&
-        (nextLatestTimeoutMs = timeoutMs);
-    },
-    retrySuspendedRoot
-  );
-  var throwException = hostContext.throwException,
-    unwindWork = hostContext.unwindWork,
-    unwindInterruptedWork = hostContext.unwindInterruptedWork,
-    createRootErrorUpdate = hostContext.createRootErrorUpdate,
-    createClassErrorUpdate = hostContext.createClassErrorUpdate;
-  config = ReactFiberCommitWork(
-    config,
-    onCommitPhaseError,
-    scheduleWork,
-    computeExpirationForFiber,
-    markLegacyErrorBoundaryAsFailed,
-    recalculateCurrentTime
-  );
-  var commitBeforeMutationLifeCycles = config.commitBeforeMutationLifeCycles,
-    commitResetTextContent = config.commitResetTextContent,
-    commitPlacement = config.commitPlacement,
-    commitDeletion = config.commitDeletion,
-    commitWork = config.commitWork,
-    commitLifeCycles = config.commitLifeCycles,
-    commitAttachRef = config.commitAttachRef,
-    commitDetachRef = config.commitDetachRef,
-    originalStartTimeMs = now(),
-    mostRecentCurrentTime = 2,
-    mostRecentCurrentTimeMs = originalStartTimeMs,
-    lastUniqueAsyncExpiration = 0,
-    expirationContext = 0,
-    isWorking = !1,
-    nextUnitOfWork = null,
-    nextRoot = null,
-    nextRenderExpirationTime = 0,
-    nextLatestTimeoutMs = -1,
-    nextRenderIsExpired = !1,
-    nextEffect = null,
-    isCommitting = !1,
-    isRootReadyForCommit = !1,
-    legacyErrorBoundariesThatAlreadyFailed = null,
-    firstScheduledRoot = null,
-    lastScheduledRoot = null,
-    callbackExpirationTime = 0,
-    callbackID = -1,
-    isRendering = !1,
-    nextFlushedRoot = null,
-    nextFlushedExpirationTime = 0,
-    lowestPendingInteractiveExpirationTime = 0,
-    deadlineDidExpire = !1,
-    hasUnhandledError = !1,
-    unhandledError = null,
-    deadline = null,
-    isBatchingUpdates = !1,
-    isUnbatchingUpdates = !1,
-    isBatchingInteractiveUpdates = !1,
-    completedBatches = null,
-    NESTED_UPDATE_LIMIT = 1e3,
-    nestedUpdateCount = 0,
-    timeHeuristicForUnitOfWork = 1;
-  return {
-    recalculateCurrentTime: recalculateCurrentTime,
-    computeExpirationForFiber: computeExpirationForFiber,
-    scheduleWork: scheduleWork,
-    requestWork: requestWork,
-    flushRoot: function(root, expirationTime) {
-      invariant(
-        !isRendering,
-        "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
-      );
-      nextFlushedRoot = root;
-      nextFlushedExpirationTime = expirationTime;
-      performWorkOnRoot(root, expirationTime, !1);
-      performSyncWork();
-      finishRendering();
-    },
-    batchedUpdates: function(fn, a) {
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        return fn(a);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates) ||
-          isRendering ||
-          performSyncWork();
-      }
-    },
-    unbatchedUpdates: function(fn, a) {
-      if (isBatchingUpdates && !isUnbatchingUpdates) {
-        isUnbatchingUpdates = !0;
-        try {
-          return fn(a);
-        } finally {
-          isUnbatchingUpdates = !1;
-        }
-      }
-      return fn(a);
-    },
-    flushSync: function(fn, a) {
-      invariant(
-        !isRendering,
-        "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
-      );
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        return syncUpdates(fn, a);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates), performSyncWork();
-      }
-    },
-    flushControlled: function(fn) {
-      var previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = !0;
-      try {
-        syncUpdates(fn);
-      } finally {
-        (isBatchingUpdates = previousIsBatchingUpdates) ||
-          isRendering ||
-          performWork(1, !1, null);
-      }
-    },
-    deferredUpdates: function(fn) {
-      var previousExpirationContext = expirationContext;
-      expirationContext =
-        2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
-      try {
-        return fn();
-      } finally {
-        expirationContext = previousExpirationContext;
-      }
-    },
-    syncUpdates: syncUpdates,
-    interactiveUpdates: function(fn, a, b) {
-      if (isBatchingInteractiveUpdates) return fn(a, b);
-      isBatchingUpdates ||
-        isRendering ||
-        0 === lowestPendingInteractiveExpirationTime ||
-        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
-        (lowestPendingInteractiveExpirationTime = 0));
-      var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
-        previousIsBatchingUpdates = isBatchingUpdates;
-      isBatchingUpdates = isBatchingInteractiveUpdates = !0;
-      try {
-        return fn(a, b);
-      } finally {
-        (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
-          (isBatchingUpdates = previousIsBatchingUpdates) ||
-            isRendering ||
-            performSyncWork();
-      }
-    },
-    flushInteractiveUpdates: function() {
-      isRendering ||
-        0 === lowestPendingInteractiveExpirationTime ||
-        (performWork(lowestPendingInteractiveExpirationTime, !1, null),
-        (lowestPendingInteractiveExpirationTime = 0));
-    },
-    computeUniqueAsyncExpiration: function() {
-      var result =
-        2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
-      result <= lastUniqueAsyncExpiration &&
-        (result = lastUniqueAsyncExpiration + 1);
-      return (lastUniqueAsyncExpiration = result);
-    },
-    legacyContext: legacyContext
-  };
+  previousScheduledRoot = nextFlushedRoot;
+  null !== previousScheduledRoot &&
+  previousScheduledRoot === highestPriorityRoot &&
+  1 === highestPriorityWork
+    ? nestedUpdateCount++
+    : (nestedUpdateCount = 0);
+  nextFlushedRoot = highestPriorityRoot;
+  nextFlushedExpirationTime = highestPriorityWork;
 }
-function ReactFiberReconciler$1(config) {
-  function updateContainerAtExpirationTime(
-    element,
-    container,
-    parentComponent,
-    expirationTime,
-    callback
-  ) {
-    var current = container.current;
-    if (parentComponent) {
-      parentComponent = parentComponent._reactInternalFiber;
-      var parentContext = findCurrentUnmaskedContext(parentComponent);
-      parentComponent = isContextProvider(parentComponent)
-        ? processChildContext(parentComponent, parentContext)
-        : parentContext;
-    } else parentComponent = emptyObject;
-    null === container.context
-      ? (container.context = parentComponent)
-      : (container.pendingContext = parentComponent);
-    container = callback;
-    callback = createUpdate(expirationTime);
-    callback.payload = { element: element };
-    container = void 0 === container ? null : container;
-    null !== container && (callback.callback = container);
-    enqueueUpdate(current, callback, expirationTime);
-    scheduleWork(current, expirationTime);
-    return expirationTime;
-  }
-  var getPublicInstance = config.getPublicInstance;
-  config = ReactFiberScheduler(config);
-  var recalculateCurrentTime = config.recalculateCurrentTime,
-    computeExpirationForFiber = config.computeExpirationForFiber,
-    scheduleWork = config.scheduleWork,
-    legacyContext = config.legacyContext,
-    findCurrentUnmaskedContext = legacyContext.findCurrentUnmaskedContext,
-    isContextProvider = legacyContext.isContextProvider,
-    processChildContext = legacyContext.processChildContext;
-  return {
-    createContainer: function(containerInfo, isAsync, hydrate) {
-      isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
-      containerInfo = {
-        current: isAsync,
-        containerInfo: containerInfo,
-        pendingChildren: null,
-        earliestPendingTime: 0,
-        latestPendingTime: 0,
-        earliestSuspendedTime: 0,
-        latestSuspendedTime: 0,
-        latestPingedTime: 0,
-        pendingCommitExpirationTime: 0,
-        finishedWork: null,
-        context: null,
-        pendingContext: null,
-        hydrate: hydrate,
-        remainingExpirationTime: 0,
-        firstBatch: null,
-        nextScheduledRoot: null
-      };
-      return (isAsync.stateNode = containerInfo);
-    },
-    updateContainer: function(element, container, parentComponent, callback) {
-      var current = container.current,
-        currentTime = recalculateCurrentTime();
-      current = computeExpirationForFiber(currentTime, current);
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        current,
-        callback
-      );
-    },
-    updateContainerAtExpirationTime: function(
-      element,
-      container,
-      parentComponent,
-      expirationTime,
-      callback
-    ) {
-      return updateContainerAtExpirationTime(
-        element,
-        container,
-        parentComponent,
-        expirationTime,
-        callback
-      );
-    },
-    flushRoot: config.flushRoot,
-    requestWork: config.requestWork,
-    computeUniqueAsyncExpiration: config.computeUniqueAsyncExpiration,
-    batchedUpdates: config.batchedUpdates,
-    unbatchedUpdates: config.unbatchedUpdates,
-    deferredUpdates: config.deferredUpdates,
-    syncUpdates: config.syncUpdates,
-    interactiveUpdates: config.interactiveUpdates,
-    flushInteractiveUpdates: config.flushInteractiveUpdates,
-    flushControlled: config.flushControlled,
-    flushSync: config.flushSync,
-    getPublicRootInstance: function(container) {
-      container = container.current;
-      if (!container.child) return null;
-      switch (container.child.tag) {
-        case 5:
-          return getPublicInstance(container.child.stateNode);
-        default:
-          return container.child.stateNode;
+function performAsyncWork(dl) {
+  performWork(0, dl);
+}
+function performWork(minExpirationTime, dl) {
+  deadline = dl;
+  findHighestPriorityRoot();
+  if (null !== deadline)
+    for (
+      ;
+      null !== nextFlushedRoot &&
+      0 !== nextFlushedExpirationTime &&
+      (0 === minExpirationTime ||
+        minExpirationTime >= nextFlushedExpirationTime) &&
+      (!deadlineDidExpire ||
+        recalculateCurrentTime() >= nextFlushedExpirationTime);
+
+    )
+      recalculateCurrentTime(),
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !0),
+        findHighestPriorityRoot();
+  else
+    for (
+      ;
+      null !== nextFlushedRoot &&
+      0 !== nextFlushedExpirationTime &&
+      (0 === minExpirationTime ||
+        minExpirationTime >= nextFlushedExpirationTime);
+
+    )
+      performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
+        findHighestPriorityRoot();
+  null !== deadline && ((callbackExpirationTime = 0), (callbackID = null));
+  0 !== nextFlushedExpirationTime &&
+    scheduleCallbackWithExpirationTime(nextFlushedExpirationTime);
+  deadline = null;
+  deadlineDidExpire = !1;
+  finishRendering();
+}
+function finishRendering() {
+  nestedUpdateCount = 0;
+  if (null !== completedBatches) {
+    var batches = completedBatches;
+    completedBatches = null;
+    for (var i = 0; i < batches.length; i++) {
+      var batch = batches[i];
+      try {
+        batch._onComplete();
+      } catch (error) {
+        hasUnhandledError ||
+          ((hasUnhandledError = !0), (unhandledError = error));
       }
-    },
-    findHostInstance: function(component) {
-      var fiber = component._reactInternalFiber;
-      void 0 === fiber &&
-        ("function" === typeof component.render
-          ? invariant(!1, "Unable to find node on an unmounted component.")
-          : invariant(
-              !1,
-              "Argument appears to not be a ReactComponent. Keys: %s",
-              Object.keys(component)
-            ));
-      component = findCurrentHostFiber(fiber);
-      return null === component ? null : component.stateNode;
-    },
-    findHostInstanceWithNoPortals: function(fiber) {
-      fiber = findCurrentHostFiberWithNoPortals(fiber);
-      return null === fiber ? null : fiber.stateNode;
-    },
-    injectIntoDevTools: function(devToolsConfig) {
-      var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
-      return injectInternals(
-        Object.assign({}, devToolsConfig, {
-          findHostInstanceByFiber: function(fiber) {
-            fiber = findCurrentHostFiber(fiber);
-            return null === fiber ? null : fiber.stateNode;
-          },
-          findFiberByHostInstance: function(instance) {
-            return findFiberByHostInstance
-              ? findFiberByHostInstance(instance)
-              : null;
-          }
-        })
-      );
     }
-  };
+  }
+  if (hasUnhandledError)
+    throw ((batches = unhandledError),
+    (unhandledError = null),
+    (hasUnhandledError = !1),
+    batches);
 }
-var ReactFiberReconciler$2 = Object.freeze({ default: ReactFiberReconciler$1 }),
-  ReactFiberReconciler$3 =
-    (ReactFiberReconciler$2 && ReactFiberReconciler$1) ||
-    ReactFiberReconciler$2,
-  reactReconciler = ReactFiberReconciler$3.default
-    ? ReactFiberReconciler$3.default
-    : ReactFiberReconciler$3;
-function createPortal(children, containerInfo, implementation) {
-  var key =
-    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
-  return {
-    $$typeof: REACT_PORTAL_TYPE,
-    key: null == key ? null : "" + key,
-    children: children,
-    containerInfo: containerInfo,
-    implementation: implementation
-  };
+function performWorkOnRoot(root, expirationTime, isYieldy) {
+  invariant(
+    !isRendering,
+    "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+  );
+  isRendering = !0;
+  isYieldy
+    ? ((isYieldy = root.finishedWork),
+      null !== isYieldy
+        ? completeRoot(root, isYieldy, expirationTime)
+        : ((root.finishedWork = null),
+          renderRoot(root, !0),
+          (isYieldy = root.finishedWork),
+          null !== isYieldy &&
+            (shouldYield()
+              ? (root.finishedWork = isYieldy)
+              : completeRoot(root, isYieldy, expirationTime))))
+    : ((isYieldy = root.finishedWork),
+      null !== isYieldy
+        ? completeRoot(root, isYieldy, expirationTime)
+        : ((root.finishedWork = null),
+          renderRoot(root, !1),
+          (isYieldy = root.finishedWork),
+          null !== isYieldy && completeRoot(root, isYieldy, expirationTime)));
+  isRendering = !1;
 }
-var emptyObject$1 = {},
-  removedKeys = null,
-  removedKeyCount = 0;
-function restoreDeletedValuesInNestedArray(
-  updatePayload,
-  node,
-  validAttributes
-) {
-  if (Array.isArray(node))
-    for (var i = node.length; i-- && 0 < removedKeyCount; )
-      restoreDeletedValuesInNestedArray(
-        updatePayload,
-        node[i],
-        validAttributes
-      );
-  else if (node && 0 < removedKeyCount)
-    for (i in removedKeys)
-      if (removedKeys[i]) {
-        var _nextProp = node[i];
-        if (void 0 !== _nextProp) {
-          var attributeConfig = validAttributes[i];
-          if (attributeConfig) {
-            "function" === typeof _nextProp && (_nextProp = !0);
-            "undefined" === typeof _nextProp && (_nextProp = null);
-            if ("object" !== typeof attributeConfig)
-              updatePayload[i] = _nextProp;
-            else if (
-              "function" === typeof attributeConfig.diff ||
-              "function" === typeof attributeConfig.process
-            )
-              (_nextProp =
-                "function" === typeof attributeConfig.process
-                  ? attributeConfig.process(_nextProp)
-                  : _nextProp),
-                (updatePayload[i] = _nextProp);
-            removedKeys[i] = !1;
-            removedKeyCount--;
+function completeRoot(root, finishedWork$jscomp$0, expirationTime) {
+  var firstBatch = root.firstBatch;
+  if (
+    null !== firstBatch &&
+    firstBatch._expirationTime <= expirationTime &&
+    (null === completedBatches
+      ? (completedBatches = [firstBatch])
+      : completedBatches.push(firstBatch),
+    firstBatch._defer)
+  ) {
+    root.finishedWork = finishedWork$jscomp$0;
+    root.expirationTime = 0;
+    return;
+  }
+  root.finishedWork = null;
+  isCommitting$1 = isWorking = !0;
+  invariant(
+    root.current !== finishedWork$jscomp$0,
+    "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
+  );
+  expirationTime = root.pendingCommitExpirationTime;
+  invariant(
+    0 !== expirationTime,
+    "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
+  );
+  root.pendingCommitExpirationTime = 0;
+  firstBatch = finishedWork$jscomp$0.expirationTime;
+  recalculateCurrentTime();
+  root.didError = !1;
+  if (0 === firstBatch)
+    (root.earliestPendingTime = 0),
+      (root.latestPendingTime = 0),
+      (root.earliestSuspendedTime = 0),
+      (root.latestSuspendedTime = 0),
+      (root.latestPingedTime = 0);
+  else {
+    var latestPendingTime = root.latestPendingTime;
+    0 !== latestPendingTime &&
+      (latestPendingTime < firstBatch
+        ? (root.earliestPendingTime = root.latestPendingTime = 0)
+        : root.earliestPendingTime < firstBatch &&
+          (root.earliestPendingTime = root.latestPendingTime));
+    latestPendingTime = root.earliestSuspendedTime;
+    0 === latestPendingTime
+      ? markPendingPriorityLevel(root, firstBatch)
+      : firstBatch > root.latestSuspendedTime
+        ? ((root.earliestSuspendedTime = 0),
+          (root.latestSuspendedTime = 0),
+          (root.latestPingedTime = 0),
+          markPendingPriorityLevel(root, firstBatch))
+        : firstBatch < latestPendingTime &&
+          markPendingPriorityLevel(root, firstBatch);
+  }
+  findNextPendingPriorityLevel(root);
+  ReactCurrentOwner.current = null;
+  1 < finishedWork$jscomp$0.effectTag
+    ? null !== finishedWork$jscomp$0.lastEffect
+      ? ((finishedWork$jscomp$0.lastEffect.nextEffect = finishedWork$jscomp$0),
+        (firstBatch = finishedWork$jscomp$0.firstEffect))
+      : (firstBatch = finishedWork$jscomp$0)
+    : (firstBatch = finishedWork$jscomp$0.firstEffect);
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    latestPendingTime = !1;
+    var error = void 0;
+    try {
+      for (; null !== nextEffect; ) {
+        if (nextEffect.effectTag & 256) {
+          var current = nextEffect.alternate,
+            finishedWork = nextEffect;
+          switch (finishedWork.tag) {
+            case 2:
+              if (finishedWork.effectTag & 256 && null !== current) {
+                var prevProps = current.memoizedProps,
+                  prevState = current.memoizedState,
+                  instance = finishedWork.stateNode;
+                instance.props = finishedWork.memoizedProps;
+                instance.state = finishedWork.memoizedState;
+                var snapshot = instance.getSnapshotBeforeUpdate(
+                  prevProps,
+                  prevState
+                );
+                instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+              }
+              break;
+            case 3:
+            case 5:
+            case 6:
+            case 4:
+              break;
+            default:
+              invariant(
+                !1,
+                "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+              );
           }
         }
+        nextEffect = nextEffect.nextEffect;
       }
-}
-function diffNestedProperty(
-  updatePayload,
-  prevProp,
-  nextProp,
-  validAttributes
-) {
-  if (!updatePayload && prevProp === nextProp) return updatePayload;
-  if (!prevProp || !nextProp)
-    return nextProp
-      ? addNestedProperty(updatePayload, nextProp, validAttributes)
-      : prevProp
-        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
-        : updatePayload;
-  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
-    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
-  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
-    var minLength =
-        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
-      i;
-    for (i = 0; i < minLength; i++)
-      updatePayload = diffNestedProperty(
-        updatePayload,
-        prevProp[i],
-        nextProp[i],
-        validAttributes
-      );
-    for (; i < prevProp.length; i++)
-      updatePayload = clearNestedProperty(
-        updatePayload,
-        prevProp[i],
-        validAttributes
-      );
-    for (; i < nextProp.length; i++)
-      updatePayload = addNestedProperty(
-        updatePayload,
-        nextProp[i],
-        validAttributes
-      );
-    return updatePayload;
+    } catch (e) {
+      (latestPendingTime = !0), (error = e);
+    }
+    latestPendingTime &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, error),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
   }
-  return Array.isArray(prevProp)
-    ? diffProperties(
-        updatePayload,
-        flattenStyle(prevProp),
-        nextProp,
-        validAttributes
-      )
-    : diffProperties(
-        updatePayload,
-        prevProp,
-        flattenStyle(nextProp),
-        validAttributes
-      );
-}
-function addNestedProperty(updatePayload, nextProp, validAttributes) {
-  if (!nextProp) return updatePayload;
-  if (!Array.isArray(nextProp))
-    return diffProperties(
-      updatePayload,
-      emptyObject$1,
-      nextProp,
-      validAttributes
-    );
-  for (var i = 0; i < nextProp.length; i++)
-    updatePayload = addNestedProperty(
-      updatePayload,
-      nextProp[i],
-      validAttributes
-    );
-  return updatePayload;
-}
-function clearNestedProperty(updatePayload, prevProp, validAttributes) {
-  if (!prevProp) return updatePayload;
-  if (!Array.isArray(prevProp))
-    return diffProperties(
-      updatePayload,
-      prevProp,
-      emptyObject$1,
-      validAttributes
-    );
-  for (var i = 0; i < prevProp.length; i++)
-    updatePayload = clearNestedProperty(
-      updatePayload,
-      prevProp[i],
-      validAttributes
-    );
-  return updatePayload;
-}
-function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
-  var attributeConfig, propKey;
-  for (propKey in nextProps)
-    if ((attributeConfig = validAttributes[propKey])) {
-      var prevProp = prevProps[propKey];
-      var nextProp = nextProps[propKey];
-      "function" === typeof nextProp &&
-        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
-      "undefined" === typeof nextProp &&
-        ((nextProp = null),
-        "undefined" === typeof prevProp && (prevProp = null));
-      removedKeys && (removedKeys[propKey] = !1);
-      if (updatePayload && void 0 !== updatePayload[propKey])
-        if ("object" !== typeof attributeConfig)
-          updatePayload[propKey] = nextProp;
-        else {
-          if (
-            "function" === typeof attributeConfig.diff ||
-            "function" === typeof attributeConfig.process
-          )
-            (attributeConfig =
-              "function" === typeof attributeConfig.process
-                ? attributeConfig.process(nextProp)
-                : nextProp),
-              (updatePayload[propKey] = attributeConfig);
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    current = !1;
+    prevProps = void 0;
+    try {
+      for (; null !== nextEffect; ) {
+        var effectTag = nextEffect.effectTag;
+        if (effectTag & 128) {
+          var current$jscomp$0 = nextEffect.alternate;
+          if (null !== current$jscomp$0) {
+            var currentRef = current$jscomp$0.ref;
+            null !== currentRef &&
+              ("function" === typeof currentRef
+                ? currentRef(null)
+                : (currentRef.current = null));
+          }
         }
-      else if (prevProp !== nextProp)
-        if ("object" !== typeof attributeConfig)
-          ("object" !== typeof nextProp ||
-            null === nextProp ||
-            deepDiffer(prevProp, nextProp)) &&
-            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
-        else if (
-          "function" === typeof attributeConfig.diff ||
-          "function" === typeof attributeConfig.process
-        ) {
-          if (
-            void 0 === prevProp ||
-            ("function" === typeof attributeConfig.diff
-              ? attributeConfig.diff(prevProp, nextProp)
-              : "object" !== typeof nextProp ||
-                null === nextProp ||
-                deepDiffer(prevProp, nextProp))
-          )
-            (attributeConfig =
-              "function" === typeof attributeConfig.process
-                ? attributeConfig.process(nextProp)
-                : nextProp),
-              ((updatePayload || (updatePayload = {}))[
-                propKey
-              ] = attributeConfig);
-        } else
-          (removedKeys = null),
-            (removedKeyCount = 0),
-            (updatePayload = diffNestedProperty(
-              updatePayload,
-              prevProp,
-              nextProp,
-              attributeConfig
-            )),
-            0 < removedKeyCount &&
-              updatePayload &&
-              (restoreDeletedValuesInNestedArray(
-                updatePayload,
-                nextProp,
-                attributeConfig
-              ),
-              (removedKeys = null));
+        switch (effectTag & 14) {
+          case 2:
+            commitPlacement(nextEffect);
+            nextEffect.effectTag &= -3;
+            break;
+          case 6:
+            commitPlacement(nextEffect);
+            nextEffect.effectTag &= -3;
+            commitWork(nextEffect.alternate, nextEffect);
+            break;
+          case 4:
+            commitWork(nextEffect.alternate, nextEffect);
+            break;
+          case 8:
+            (prevState = nextEffect),
+              unmountHostComponents(prevState),
+              (prevState.return = null),
+              (prevState.child = null),
+              prevState.alternate &&
+                ((prevState.alternate.child = null),
+                (prevState.alternate.return = null));
+        }
+        nextEffect = nextEffect.nextEffect;
+      }
+    } catch (e) {
+      (current = !0), (prevProps = e);
+    }
+    current &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, prevProps),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  root.current = finishedWork$jscomp$0;
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    effectTag = !1;
+    current$jscomp$0 = void 0;
+    try {
+      for (currentRef = expirationTime; null !== nextEffect; ) {
+        var effectTag$jscomp$0 = nextEffect.effectTag;
+        if (effectTag$jscomp$0 & 36) {
+          var current$jscomp$1 = nextEffect.alternate;
+          current = nextEffect;
+          prevProps = currentRef;
+          switch (current.tag) {
+            case 2:
+              var instance$jscomp$0 = current.stateNode;
+              if (current.effectTag & 4)
+                if (null === current$jscomp$1)
+                  (instance$jscomp$0.props = current.memoizedProps),
+                    (instance$jscomp$0.state = current.memoizedState),
+                    instance$jscomp$0.componentDidMount();
+                else {
+                  var prevProps$jscomp$0 = current$jscomp$1.memoizedProps,
+                    prevState$jscomp$0 = current$jscomp$1.memoizedState;
+                  instance$jscomp$0.props = current.memoizedProps;
+                  instance$jscomp$0.state = current.memoizedState;
+                  instance$jscomp$0.componentDidUpdate(
+                    prevProps$jscomp$0,
+                    prevState$jscomp$0,
+                    instance$jscomp$0.__reactInternalSnapshotBeforeUpdate
+                  );
+                }
+              var updateQueue = current.updateQueue;
+              null !== updateQueue &&
+                ((instance$jscomp$0.props = current.memoizedProps),
+                (instance$jscomp$0.state = current.memoizedState),
+                commitUpdateQueue(
+                  current,
+                  updateQueue,
+                  instance$jscomp$0,
+                  prevProps
+                ));
+              break;
+            case 3:
+              var _updateQueue = current.updateQueue;
+              if (null !== _updateQueue) {
+                prevState = null;
+                if (null !== current.child)
+                  switch (current.child.tag) {
+                    case 5:
+                      prevState = current.child.stateNode;
+                      break;
+                    case 2:
+                      prevState = current.child.stateNode;
+                  }
+                commitUpdateQueue(current, _updateQueue, prevState, prevProps);
+              }
+              break;
+            case 5:
+              break;
+            case 6:
+              break;
+            case 4:
+              break;
+            case 15:
+              break;
+            case 16:
+              break;
+            default:
+              invariant(
+                !1,
+                "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+              );
+          }
+        }
+        if (effectTag$jscomp$0 & 128) {
+          current = void 0;
+          var ref = nextEffect.ref;
+          if (null !== ref) {
+            var instance$jscomp$1 = nextEffect.stateNode;
+            switch (nextEffect.tag) {
+              case 5:
+                current = instance$jscomp$1;
+                break;
+              default:
+                current = instance$jscomp$1;
+            }
+            "function" === typeof ref ? ref(current) : (ref.current = current);
+          }
+        }
+        var next = nextEffect.nextEffect;
+        nextEffect.nextEffect = null;
+        nextEffect = next;
+      }
+    } catch (e) {
+      (effectTag = !0), (current$jscomp$0 = e);
     }
-  for (var _propKey in prevProps)
-    void 0 === nextProps[_propKey] &&
-      (!(attributeConfig = validAttributes[_propKey]) ||
-        (updatePayload && void 0 !== updatePayload[_propKey]) ||
-        ((prevProp = prevProps[_propKey]),
-        void 0 !== prevProp &&
-          ("object" !== typeof attributeConfig ||
-          "function" === typeof attributeConfig.diff ||
-          "function" === typeof attributeConfig.process
-            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
-              removedKeys || (removedKeys = {}),
-              removedKeys[_propKey] ||
-                ((removedKeys[_propKey] = !0), removedKeyCount++))
-            : (updatePayload = clearNestedProperty(
-                updatePayload,
-                prevProp,
-                attributeConfig
-              )))));
-  return updatePayload;
+    effectTag &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, current$jscomp$0),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  isWorking = isCommitting$1 = !1;
+  "function" === typeof onCommitRoot &&
+    onCommitRoot(finishedWork$jscomp$0.stateNode);
+  finishedWork$jscomp$0 = root.expirationTime;
+  0 === finishedWork$jscomp$0 &&
+    (legacyErrorBoundariesThatAlreadyFailed = null);
+  root.expirationTime = finishedWork$jscomp$0;
+  root.finishedWork = null;
 }
-function mountSafeCallback(context, callback) {
-  return function() {
-    if (callback) {
-      if ("boolean" === typeof context.__isMounted) {
-        if (!context.__isMounted) return;
-      } else if (
-        "function" === typeof context.isMounted &&
-        !context.isMounted()
-      )
-        return;
-      return callback.apply(context, arguments);
-    }
-  };
+function shouldYield() {
+  return null === deadline ||
+    deadlineDidExpire ||
+    deadline.timeRemaining() > timeHeuristicForUnitOfWork
+    ? !1
+    : (deadlineDidExpire = !0);
 }
-var ReactNativeFiberHostComponent = (function() {
-    function ReactNativeFiberHostComponent(tag, viewConfig) {
-      if (!(this instanceof ReactNativeFiberHostComponent))
-        throw new TypeError("Cannot call a class as a function");
-      this._nativeTag = tag;
-      this._children = [];
-      this.viewConfig = viewConfig;
-    }
-    ReactNativeFiberHostComponent.prototype.blur = function() {
-      TextInputState.blurTextInput(this._nativeTag);
-    };
-    ReactNativeFiberHostComponent.prototype.focus = function() {
-      TextInputState.focusTextInput(this._nativeTag);
-    };
-    ReactNativeFiberHostComponent.prototype.measure = function(callback) {
-      UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
-    };
-    ReactNativeFiberHostComponent.prototype.measureInWindow = function(
-      callback
-    ) {
-      UIManager.measureInWindow(
-        this._nativeTag,
-        mountSafeCallback(this, callback)
-      );
-    };
-    ReactNativeFiberHostComponent.prototype.measureLayout = function(
-      relativeToNativeNode,
-      onSuccess,
-      onFail
-    ) {
-      UIManager.measureLayout(
-        this._nativeTag,
-        relativeToNativeNode,
-        mountSafeCallback(this, onFail),
-        mountSafeCallback(this, onSuccess)
-      );
-    };
-    ReactNativeFiberHostComponent.prototype.setNativeProps = function(
-      nativeProps
-    ) {
-      nativeProps = diffProperties(
-        null,
-        emptyObject$1,
-        nativeProps,
-        this.viewConfig.validAttributes
+function onUncaughtError(error) {
+  invariant(
+    null !== nextFlushedRoot,
+    "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
+  );
+  nextFlushedRoot.expirationTime = 0;
+  hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
+}
+function updateContainerAtExpirationTime(
+  element,
+  container,
+  parentComponent,
+  expirationTime,
+  callback
+) {
+  var current = container.current;
+  if (parentComponent) {
+    parentComponent = parentComponent._reactInternalFiber;
+    var parentContext;
+    b: {
+      invariant(
+        2 === isFiberMountedImpl(parentComponent) && 2 === parentComponent.tag,
+        "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
       );
-      null != nativeProps &&
-        UIManager.updateView(
-          this._nativeTag,
-          this.viewConfig.uiViewClassName,
-          nativeProps
-        );
-    };
-    return ReactNativeFiberHostComponent;
-  })(),
-  now =
-    "object" === typeof performance && "function" === typeof performance.now
-      ? function() {
-          return performance.now();
+      for (parentContext = parentComponent; 3 !== parentContext.tag; ) {
+        if (isContextProvider(parentContext)) {
+          parentContext =
+            parentContext.stateNode.__reactInternalMemoizedMergedChildContext;
+          break b;
         }
-      : function() {
-          return Date.now();
-        },
-  scheduledCallback = null,
-  frameDeadline = 0,
-  frameDeadlineObject = {
-    timeRemaining: function() {
-      return frameDeadline - now();
-    },
-    didTimeout: !1
-  };
-function setTimeoutCallback() {
-  frameDeadline = now() + 5;
-  var callback = scheduledCallback;
-  scheduledCallback = null;
-  null !== callback && callback(frameDeadlineObject);
+        parentContext = parentContext.return;
+        invariant(
+          parentContext,
+          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+      }
+      parentContext = parentContext.stateNode.context;
+    }
+    parentComponent = isContextProvider(parentComponent)
+      ? processChildContext(parentComponent, parentContext)
+      : parentContext;
+  } else parentComponent = emptyObject;
+  null === container.context
+    ? (container.context = parentComponent)
+    : (container.pendingContext = parentComponent);
+  container = callback;
+  callback = createUpdate(expirationTime);
+  callback.payload = { element: element };
+  container = void 0 === container ? null : container;
+  null !== container && (callback.callback = container);
+  enqueueUpdate(current, callback, expirationTime);
+  scheduleWork(current, expirationTime);
+  return expirationTime;
 }
-var nextReactTag = 3;
-function allocateTag() {
-  var tag = nextReactTag;
-  1 === tag % 10 && (tag += 2);
-  nextReactTag = tag + 2;
-  return tag;
+function findHostInstance$1(component) {
+  var fiber = component._reactInternalFiber;
+  void 0 === fiber &&
+    ("function" === typeof component.render
+      ? invariant(!1, "Unable to find node on an unmounted component.")
+      : invariant(
+          !1,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        ));
+  component = findCurrentHostFiber(fiber);
+  return null === component ? null : component.stateNode;
 }
-function recursivelyUncacheFiberNode(node) {
-  "number" === typeof node
-    ? uncacheFiberNode(node)
-    : (uncacheFiberNode(node._nativeTag),
-      node._children.forEach(recursivelyUncacheFiberNode));
+function updateContainer(element, container, parentComponent, callback) {
+  var current = container.current,
+    currentTime = recalculateCurrentTime();
+  current = computeExpirationForFiber(currentTime, current);
+  return updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    current,
+    callback
+  );
 }
-var ReactNativeHostConfig = {
-  appendInitialChild: function(parentInstance, child) {
-    parentInstance._children.push(child);
-  },
-  createInstance: function(
-    type,
-    props,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
-    var tag = allocateTag(),
-      viewConfig = ReactNativeViewConfigRegistry.get(type);
-    invariant(
-      "RCTView" !== type || !hostContext.isInAParentText,
-      "Nesting of <View> within <Text> is not currently supported."
-    );
-    type = diffProperties(
-      null,
-      emptyObject$1,
-      props,
-      viewConfig.validAttributes
-    );
-    UIManager.createView(
-      tag,
-      viewConfig.uiViewClassName,
-      rootContainerInstance,
-      type
-    );
-    rootContainerInstance = new ReactNativeFiberHostComponent(tag, viewConfig);
-    instanceCache[tag] = internalInstanceHandle;
-    instanceProps[tag] = props;
-    return rootContainerInstance;
+function getPublicRootInstance(container) {
+  container = container.current;
+  if (!container.child) return null;
+  switch (container.child.tag) {
+    case 5:
+      return container.child.stateNode;
+    default:
+      return container.child.stateNode;
+  }
+}
+function injectIntoDevTools(devToolsConfig) {
+  var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+  return injectInternals(
+    Object.assign({}, devToolsConfig, {
+      findHostInstanceByFiber: function(fiber) {
+        fiber = findCurrentHostFiber(fiber);
+        return null === fiber ? null : fiber.stateNode;
+      },
+      findFiberByHostInstance: function(instance) {
+        return findFiberByHostInstance
+          ? findFiberByHostInstance(instance)
+          : null;
+      }
+    })
+  );
+}
+var ReactNativeFiberRenderer = {
+  updateContainerAtExpirationTime: updateContainerAtExpirationTime,
+  createContainer: function(containerInfo, isAsync, hydrate) {
+    return createFiberRoot(containerInfo, isAsync, hydrate);
   },
-  createTextInstance: function(
-    text,
-    rootContainerInstance,
-    hostContext,
-    internalInstanceHandle
-  ) {
+  updateContainer: updateContainer,
+  flushRoot: function(root, expirationTime) {
     invariant(
-      hostContext.isInAParentText,
-      "Text strings must be rendered within a <Text> component."
+      !isRendering,
+      "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
     );
-    hostContext = allocateTag();
-    UIManager.createView(hostContext, "RCTRawText", rootContainerInstance, {
-      text: text
-    });
-    instanceCache[hostContext] = internalInstanceHandle;
-    return hostContext;
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
+    performWorkOnRoot(root, expirationTime, !1);
+    performWork(1, null);
+    finishRendering();
   },
-  finalizeInitialChildren: function(parentInstance) {
-    if (0 === parentInstance._children.length) return !1;
-    var nativeTags = parentInstance._children.map(function(child) {
-      return "number" === typeof child ? child : child._nativeTag;
-    });
-    UIManager.setChildren(parentInstance._nativeTag, nativeTags);
-    return !1;
+  requestWork: requestWork,
+  computeUniqueAsyncExpiration: function() {
+    var result =
+      2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
+    result <= lastUniqueAsyncExpiration &&
+      (result = lastUniqueAsyncExpiration + 1);
+    return (lastUniqueAsyncExpiration = result);
   },
-  getRootHostContext: function() {
-    return { isInAParentText: !1 };
+  batchedUpdates: function(fn, a) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      return fn(a);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates) ||
+        isRendering ||
+        performWork(1, null);
+    }
   },
-  getChildHostContext: function(parentHostContext, type) {
-    type =
-      "AndroidTextInput" === type ||
-      "RCTMultilineTextInputView" === type ||
-      "RCTSinglelineTextInputView" === type ||
-      "RCTText" === type ||
-      "RCTVirtualText" === type;
-    return parentHostContext.isInAParentText !== type
-      ? { isInAParentText: type }
-      : parentHostContext;
+  unbatchedUpdates: function(fn, a) {
+    if (isBatchingUpdates && !isUnbatchingUpdates) {
+      isUnbatchingUpdates = !0;
+      try {
+        return fn(a);
+      } finally {
+        isUnbatchingUpdates = !1;
+      }
+    }
+    return fn(a);
   },
-  getPublicInstance: function(instance) {
-    return instance;
+  deferredUpdates: function(fn) {
+    var previousExpirationContext = expirationContext;
+    expirationContext =
+      2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
+    try {
+      return fn();
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
   },
-  now: now,
-  isPrimaryRenderer: !0,
-  prepareForCommit: function() {},
-  prepareUpdate: function() {
-    return emptyObject;
+  syncUpdates: syncUpdates,
+  interactiveUpdates: function(fn, a, b) {
+    if (isBatchingInteractiveUpdates) return fn(a, b);
+    isBatchingUpdates ||
+      isRendering ||
+      0 === lowestPendingInteractiveExpirationTime ||
+      (performWork(lowestPendingInteractiveExpirationTime, null),
+      (lowestPendingInteractiveExpirationTime = 0));
+    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
+      previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = isBatchingInteractiveUpdates = !0;
+    try {
+      return fn(a, b);
+    } finally {
+      (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
+        (isBatchingUpdates = previousIsBatchingUpdates) ||
+          isRendering ||
+          performWork(1, null);
+    }
   },
-  resetAfterCommit: function() {},
-  scheduleDeferredCallback: function(callback) {
-    scheduledCallback = callback;
-    return setTimeout(setTimeoutCallback, 1);
+  flushInteractiveUpdates: function() {
+    isRendering ||
+      0 === lowestPendingInteractiveExpirationTime ||
+      (performWork(lowestPendingInteractiveExpirationTime, null),
+      (lowestPendingInteractiveExpirationTime = 0));
   },
-  cancelDeferredCallback: function(callbackID) {
-    scheduledCallback = null;
-    clearTimeout(callbackID);
+  flushControlled: function(fn) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      syncUpdates(fn);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates) ||
+        isRendering ||
+        performWork(1, null);
+    }
   },
-  shouldDeprioritizeSubtree: function() {
-    return !1;
+  flushSync: function(fn, a) {
+    invariant(
+      !isRendering,
+      "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
+    );
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      return syncUpdates(fn, a);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates), performWork(1, null);
+    }
   },
-  shouldSetTextContent: function() {
-    return !1;
+  getPublicRootInstance: getPublicRootInstance,
+  findHostInstance: findHostInstance$1,
+  findHostInstanceWithNoPortals: function(fiber) {
+    fiber = findCurrentHostFiberWithNoPortals(fiber);
+    return null === fiber ? null : fiber.stateNode;
   },
-  mutation: {
-    appendChild: function(parentInstance, child) {
-      var childTag = "number" === typeof child ? child : child._nativeTag,
-        children = parentInstance._children,
-        index = children.indexOf(child);
-      0 <= index
-        ? (children.splice(index, 1),
-          children.push(child),
-          UIManager.manageChildren(
-            parentInstance._nativeTag,
-            [index],
-            [children.length - 1],
-            [],
-            [],
-            []
-          ))
-        : (children.push(child),
-          UIManager.manageChildren(
-            parentInstance._nativeTag,
-            [],
-            [],
-            [childTag],
-            [children.length - 1],
-            []
-          ));
-    },
-    appendChildToContainer: function(parentInstance, child) {
-      UIManager.setChildren(parentInstance, [
-        "number" === typeof child ? child : child._nativeTag
-      ]);
-    },
-    commitTextUpdate: function(textInstance, oldText, newText) {
-      UIManager.updateView(textInstance, "RCTRawText", { text: newText });
-    },
-    commitMount: function() {},
-    commitUpdate: function(
-      instance,
-      updatePayloadTODO,
-      type,
-      oldProps,
-      newProps
-    ) {
-      updatePayloadTODO = instance.viewConfig;
-      instanceProps[instance._nativeTag] = newProps;
-      oldProps = diffProperties(
-        null,
-        oldProps,
-        newProps,
-        updatePayloadTODO.validAttributes
-      );
-      null != oldProps &&
-        UIManager.updateView(
-          instance._nativeTag,
-          updatePayloadTODO.uiViewClassName,
-          oldProps
-        );
-    },
-    insertBefore: function(parentInstance, child, beforeChild) {
-      var children = parentInstance._children,
-        index = children.indexOf(child);
-      0 <= index
-        ? (children.splice(index, 1),
-          (beforeChild = children.indexOf(beforeChild)),
-          children.splice(beforeChild, 0, child),
-          UIManager.manageChildren(
-            parentInstance._nativeTag,
-            [index],
-            [beforeChild],
-            [],
-            [],
-            []
-          ))
-        : ((index = children.indexOf(beforeChild)),
-          children.splice(index, 0, child),
-          UIManager.manageChildren(
-            parentInstance._nativeTag,
-            [],
-            [],
-            ["number" === typeof child ? child : child._nativeTag],
-            [index],
-            []
-          ));
-    },
-    insertInContainerBefore: function(parentInstance) {
-      invariant(
-        "number" !== typeof parentInstance,
-        "Container does not support insertBefore operation"
-      );
-    },
-    removeChild: function(parentInstance, child) {
-      recursivelyUncacheFiberNode(child);
-      var children = parentInstance._children;
-      child = children.indexOf(child);
-      children.splice(child, 1);
-      UIManager.manageChildren(
-        parentInstance._nativeTag,
-        [],
-        [],
-        [],
-        [],
-        [child]
-      );
-    },
-    removeChildFromContainer: function(parentInstance, child) {
-      recursivelyUncacheFiberNode(child);
-      UIManager.manageChildren(parentInstance, [], [], [], [], [0]);
-    },
-    resetTextContent: function() {}
-  }
+  injectIntoDevTools: injectIntoDevTools
 };
+function createPortal(children, containerInfo, implementation) {
+  var key =
+    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
+  return {
+    $$typeof: REACT_PORTAL_TYPE,
+    key: null == key ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
 function _inherits(subClass, superClass) {
   if ("function" !== typeof superClass && null !== superClass)
     throw new TypeError(
@@ -6265,15 +5650,13 @@ var getInspectorDataForViewTag = void 0;
 getInspectorDataForViewTag = function() {
   invariant(!1, "getInspectorDataForViewTag() is not available in production");
 };
-var ReactNativeFiberRenderer = reactReconciler(ReactNativeHostConfig),
-  findHostInstance = ReactNativeFiberRenderer.findHostInstance;
 function findNodeHandle(componentOrHandle) {
   if (null == componentOrHandle) return null;
   if ("number" === typeof componentOrHandle) return componentOrHandle;
   if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
   if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
     return componentOrHandle.canonical._nativeTag;
-  componentOrHandle = findHostInstance(componentOrHandle);
+  componentOrHandle = findHostInstance$1(componentOrHandle);
   return null == componentOrHandle
     ? componentOrHandle
     : componentOrHandle.canonical
@@ -6354,24 +5737,20 @@ var roots = new Map(),
         };
         return ReactNativeComponent;
       })(React.Component);
-    })(findNodeHandle, findHostInstance),
+    })(findNodeHandle, findHostInstance$1),
     findNodeHandle: findNodeHandle,
     render: function(element, containerTag, callback) {
       var root = roots.get(containerTag);
       root ||
-        ((root = ReactNativeFiberRenderer.createContainer(
-          containerTag,
-          !1,
-          !1
-        )),
+        ((root = createFiberRoot(containerTag, !1, !1)),
         roots.set(containerTag, root));
-      ReactNativeFiberRenderer.updateContainer(element, root, null, callback);
-      return ReactNativeFiberRenderer.getPublicRootInstance(root);
+      updateContainer(element, root, null, callback);
+      return getPublicRootInstance(root);
     },
     unmountComponentAtNode: function(containerTag) {
       var root = roots.get(containerTag);
       root &&
-        ReactNativeFiberRenderer.updateContainer(null, root, null, function() {
+        updateContainer(null, root, null, function() {
           roots.delete(containerTag);
         });
     },
@@ -6439,8 +5818,7 @@ var roots = new Map(),
             TextInputState.blurTextInput(findNodeHandle(this));
           }
         };
-      })(findNodeHandle, findHostInstance),
-      ReactNativeComponentTree: ReactNativeComponentTree,
+      })(findNodeHandle, findHostInstance$1),
       computeComponentStackForErrorReporting: function(reactTag) {
         return (reactTag = getInstanceFromTag(reactTag))
           ? getStackAddendumByWorkInProgressFiber(reactTag)
@@ -6448,14 +5826,14 @@ var roots = new Map(),
       }
     }
   };
-ReactNativeFiberRenderer.injectIntoDevTools({
+injectIntoDevTools({
   findFiberByHostInstance: getInstanceFromTag,
   getInspectorDataForViewTag: getInspectorDataForViewTag,
   bundleType: 0,
-  version: "16.3.2",
+  version: "16.4.1",
   rendererPackageName: "react-native-renderer"
 });
-var ReactNativeRenderer$2 = Object.freeze({ default: ReactNativeRenderer }),
+var ReactNativeRenderer$2 = { default: ReactNativeRenderer },
   ReactNativeRenderer$3 =
     (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
 module.exports = ReactNativeRenderer$3.default
diff --git a/Libraries/Renderer/oss/ReactNativeRenderer-profiling.js b/Libraries/Renderer/oss/ReactNativeRenderer-profiling.js
new file mode 100644
index 000000000000..1e2d9749c9e5
--- /dev/null
+++ b/Libraries/Renderer/oss/ReactNativeRenderer-profiling.js
@@ -0,0 +1,5899 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @noflow
+ * @providesModule ReactNativeRenderer-profiling
+ * @preventMunge
+ * @generated
+ */
+
+"use strict";
+require("InitializeCore");
+var invariant = require("fbjs/lib/invariant"),
+  ReactNativeViewConfigRegistry = require("ReactNativeViewConfigRegistry"),
+  UIManager = require("UIManager"),
+  RCTEventEmitter = require("RCTEventEmitter"),
+  React = require("react"),
+  emptyObject = require("fbjs/lib/emptyObject"),
+  deepDiffer = require("deepDiffer"),
+  flattenStyle = require("flattenStyle"),
+  TextInputState = require("TextInputState"),
+  ExceptionsManager = require("ExceptionsManager");
+function invokeGuardedCallback(name, func, context, a, b, c, d, e, f) {
+  this._hasCaughtError = !1;
+  this._caughtError = null;
+  var funcArgs = Array.prototype.slice.call(arguments, 3);
+  try {
+    func.apply(context, funcArgs);
+  } catch (error) {
+    (this._caughtError = error), (this._hasCaughtError = !0);
+  }
+}
+var ReactErrorUtils = {
+  _caughtError: null,
+  _hasCaughtError: !1,
+  _rethrowError: null,
+  _hasRethrowError: !1,
+  invokeGuardedCallback: function(name, func, context, a, b, c, d, e, f) {
+    invokeGuardedCallback.apply(ReactErrorUtils, arguments);
+  },
+  invokeGuardedCallbackAndCatchFirstError: function(
+    name,
+    func,
+    context,
+    a,
+    b,
+    c,
+    d,
+    e,
+    f
+  ) {
+    ReactErrorUtils.invokeGuardedCallback.apply(this, arguments);
+    if (ReactErrorUtils.hasCaughtError()) {
+      var error = ReactErrorUtils.clearCaughtError();
+      ReactErrorUtils._hasRethrowError ||
+        ((ReactErrorUtils._hasRethrowError = !0),
+        (ReactErrorUtils._rethrowError = error));
+    }
+  },
+  rethrowCaughtError: function() {
+    return rethrowCaughtError.apply(ReactErrorUtils, arguments);
+  },
+  hasCaughtError: function() {
+    return ReactErrorUtils._hasCaughtError;
+  },
+  clearCaughtError: function() {
+    if (ReactErrorUtils._hasCaughtError) {
+      var error = ReactErrorUtils._caughtError;
+      ReactErrorUtils._caughtError = null;
+      ReactErrorUtils._hasCaughtError = !1;
+      return error;
+    }
+    invariant(
+      !1,
+      "clearCaughtError was called but no error was captured. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+};
+function rethrowCaughtError() {
+  if (ReactErrorUtils._hasRethrowError) {
+    var error = ReactErrorUtils._rethrowError;
+    ReactErrorUtils._rethrowError = null;
+    ReactErrorUtils._hasRethrowError = !1;
+    throw error;
+  }
+}
+var eventPluginOrder = null,
+  namesToPlugins = {};
+function recomputePluginOrdering() {
+  if (eventPluginOrder)
+    for (var pluginName in namesToPlugins) {
+      var pluginModule = namesToPlugins[pluginName],
+        pluginIndex = eventPluginOrder.indexOf(pluginName);
+      invariant(
+        -1 < pluginIndex,
+        "EventPluginRegistry: Cannot inject event plugins that do not exist in the plugin ordering, `%s`.",
+        pluginName
+      );
+      if (!plugins[pluginIndex]) {
+        invariant(
+          pluginModule.extractEvents,
+          "EventPluginRegistry: Event plugins must implement an `extractEvents` method, but `%s` does not.",
+          pluginName
+        );
+        plugins[pluginIndex] = pluginModule;
+        pluginIndex = pluginModule.eventTypes;
+        for (var eventName in pluginIndex) {
+          var JSCompiler_inline_result = void 0;
+          var dispatchConfig = pluginIndex[eventName],
+            pluginModule$jscomp$0 = pluginModule,
+            eventName$jscomp$0 = eventName;
+          invariant(
+            !eventNameDispatchConfigs.hasOwnProperty(eventName$jscomp$0),
+            "EventPluginHub: More than one plugin attempted to publish the same event name, `%s`.",
+            eventName$jscomp$0
+          );
+          eventNameDispatchConfigs[eventName$jscomp$0] = dispatchConfig;
+          var phasedRegistrationNames = dispatchConfig.phasedRegistrationNames;
+          if (phasedRegistrationNames) {
+            for (JSCompiler_inline_result in phasedRegistrationNames)
+              phasedRegistrationNames.hasOwnProperty(
+                JSCompiler_inline_result
+              ) &&
+                publishRegistrationName(
+                  phasedRegistrationNames[JSCompiler_inline_result],
+                  pluginModule$jscomp$0,
+                  eventName$jscomp$0
+                );
+            JSCompiler_inline_result = !0;
+          } else
+            dispatchConfig.registrationName
+              ? (publishRegistrationName(
+                  dispatchConfig.registrationName,
+                  pluginModule$jscomp$0,
+                  eventName$jscomp$0
+                ),
+                (JSCompiler_inline_result = !0))
+              : (JSCompiler_inline_result = !1);
+          invariant(
+            JSCompiler_inline_result,
+            "EventPluginRegistry: Failed to publish event `%s` for plugin `%s`.",
+            eventName,
+            pluginName
+          );
+        }
+      }
+    }
+}
+function publishRegistrationName(registrationName, pluginModule) {
+  invariant(
+    !registrationNameModules[registrationName],
+    "EventPluginHub: More than one plugin attempted to publish the same registration name, `%s`.",
+    registrationName
+  );
+  registrationNameModules[registrationName] = pluginModule;
+}
+var plugins = [],
+  eventNameDispatchConfigs = {},
+  registrationNameModules = {},
+  getFiberCurrentPropsFromNode = null,
+  getInstanceFromNode = null,
+  getNodeFromInstance = null;
+function executeDispatch(event, simulated, listener, inst) {
+  simulated = event.type || "unknown-event";
+  event.currentTarget = getNodeFromInstance(inst);
+  ReactErrorUtils.invokeGuardedCallbackAndCatchFirstError(
+    simulated,
+    listener,
+    void 0,
+    event
+  );
+  event.currentTarget = null;
+}
+function executeDirectDispatch(event) {
+  var dispatchListener = event._dispatchListeners,
+    dispatchInstance = event._dispatchInstances;
+  invariant(
+    !Array.isArray(dispatchListener),
+    "executeDirectDispatch(...): Invalid `event`."
+  );
+  event.currentTarget = dispatchListener
+    ? getNodeFromInstance(dispatchInstance)
+    : null;
+  dispatchListener = dispatchListener ? dispatchListener(event) : null;
+  event.currentTarget = null;
+  event._dispatchListeners = null;
+  event._dispatchInstances = null;
+  return dispatchListener;
+}
+function accumulateInto(current, next) {
+  invariant(
+    null != next,
+    "accumulateInto(...): Accumulated items must not be null or undefined."
+  );
+  if (null == current) return next;
+  if (Array.isArray(current)) {
+    if (Array.isArray(next)) return current.push.apply(current, next), current;
+    current.push(next);
+    return current;
+  }
+  return Array.isArray(next) ? [current].concat(next) : [current, next];
+}
+function forEachAccumulated(arr, cb, scope) {
+  Array.isArray(arr) ? arr.forEach(cb, scope) : arr && cb.call(scope, arr);
+}
+var eventQueue = null;
+function executeDispatchesAndReleaseTopLevel(e) {
+  if (e) {
+    var dispatchListeners = e._dispatchListeners,
+      dispatchInstances = e._dispatchInstances;
+    if (Array.isArray(dispatchListeners))
+      for (
+        var i = 0;
+        i < dispatchListeners.length && !e.isPropagationStopped();
+        i++
+      )
+        executeDispatch(e, !1, dispatchListeners[i], dispatchInstances[i]);
+    else
+      dispatchListeners &&
+        executeDispatch(e, !1, dispatchListeners, dispatchInstances);
+    e._dispatchListeners = null;
+    e._dispatchInstances = null;
+    e.isPersistent() || e.constructor.release(e);
+  }
+}
+var injection = {
+  injectEventPluginOrder: function(injectedEventPluginOrder) {
+    invariant(
+      !eventPluginOrder,
+      "EventPluginRegistry: Cannot inject event plugin ordering more than once. You are likely trying to load more than one copy of React."
+    );
+    eventPluginOrder = Array.prototype.slice.call(injectedEventPluginOrder);
+    recomputePluginOrdering();
+  },
+  injectEventPluginsByName: function(injectedNamesToPlugins) {
+    var isOrderingDirty = !1,
+      pluginName;
+    for (pluginName in injectedNamesToPlugins)
+      if (injectedNamesToPlugins.hasOwnProperty(pluginName)) {
+        var pluginModule = injectedNamesToPlugins[pluginName];
+        (namesToPlugins.hasOwnProperty(pluginName) &&
+          namesToPlugins[pluginName] === pluginModule) ||
+          (invariant(
+            !namesToPlugins[pluginName],
+            "EventPluginRegistry: Cannot inject two different event plugins using the same name, `%s`.",
+            pluginName
+          ),
+          (namesToPlugins[pluginName] = pluginModule),
+          (isOrderingDirty = !0));
+      }
+    isOrderingDirty && recomputePluginOrdering();
+  }
+};
+function getListener(inst, registrationName) {
+  var listener = inst.stateNode;
+  if (!listener) return null;
+  var props = getFiberCurrentPropsFromNode(listener);
+  if (!props) return null;
+  listener = props[registrationName];
+  a: switch (registrationName) {
+    case "onClick":
+    case "onClickCapture":
+    case "onDoubleClick":
+    case "onDoubleClickCapture":
+    case "onMouseDown":
+    case "onMouseDownCapture":
+    case "onMouseMove":
+    case "onMouseMoveCapture":
+    case "onMouseUp":
+    case "onMouseUpCapture":
+      (props = !props.disabled) ||
+        ((inst = inst.type),
+        (props = !(
+          "button" === inst ||
+          "input" === inst ||
+          "select" === inst ||
+          "textarea" === inst
+        )));
+      inst = !props;
+      break a;
+    default:
+      inst = !1;
+  }
+  if (inst) return null;
+  invariant(
+    !listener || "function" === typeof listener,
+    "Expected `%s` listener to be a function, instead got a value of `%s` type.",
+    registrationName,
+    typeof listener
+  );
+  return listener;
+}
+function getParent(inst) {
+  do inst = inst.return;
+  while (inst && 5 !== inst.tag);
+  return inst ? inst : null;
+}
+function traverseTwoPhase(inst, fn, arg) {
+  for (var path = []; inst; ) path.push(inst), (inst = getParent(inst));
+  for (inst = path.length; 0 < inst--; ) fn(path[inst], "captured", arg);
+  for (inst = 0; inst < path.length; inst++) fn(path[inst], "bubbled", arg);
+}
+function accumulateDirectionalDispatches(inst, phase, event) {
+  if (
+    (phase = getListener(
+      inst,
+      event.dispatchConfig.phasedRegistrationNames[phase]
+    ))
+  )
+    (event._dispatchListeners = accumulateInto(
+      event._dispatchListeners,
+      phase
+    )),
+      (event._dispatchInstances = accumulateInto(
+        event._dispatchInstances,
+        inst
+      ));
+}
+function accumulateTwoPhaseDispatchesSingle(event) {
+  event &&
+    event.dispatchConfig.phasedRegistrationNames &&
+    traverseTwoPhase(event._targetInst, accumulateDirectionalDispatches, event);
+}
+function accumulateTwoPhaseDispatchesSingleSkipTarget(event) {
+  if (event && event.dispatchConfig.phasedRegistrationNames) {
+    var targetInst = event._targetInst;
+    targetInst = targetInst ? getParent(targetInst) : null;
+    traverseTwoPhase(targetInst, accumulateDirectionalDispatches, event);
+  }
+}
+function accumulateDirectDispatchesSingle(event) {
+  if (event && event.dispatchConfig.registrationName) {
+    var inst = event._targetInst;
+    if (inst && event && event.dispatchConfig.registrationName) {
+      var listener = getListener(inst, event.dispatchConfig.registrationName);
+      listener &&
+        ((event._dispatchListeners = accumulateInto(
+          event._dispatchListeners,
+          listener
+        )),
+        (event._dispatchInstances = accumulateInto(
+          event._dispatchInstances,
+          inst
+        )));
+    }
+  }
+}
+var shouldBeReleasedProperties = "dispatchConfig _targetInst nativeEvent isDefaultPrevented isPropagationStopped _dispatchListeners _dispatchInstances".split(
+  " "
+);
+function functionThatReturnsTrue() {
+  return !0;
+}
+function functionThatReturnsFalse() {
+  return !1;
+}
+function SyntheticEvent(
+  dispatchConfig,
+  targetInst,
+  nativeEvent,
+  nativeEventTarget
+) {
+  this.dispatchConfig = dispatchConfig;
+  this._targetInst = targetInst;
+  this.nativeEvent = nativeEvent;
+  dispatchConfig = this.constructor.Interface;
+  for (var propName in dispatchConfig)
+    dispatchConfig.hasOwnProperty(propName) &&
+      ((targetInst = dispatchConfig[propName])
+        ? (this[propName] = targetInst(nativeEvent))
+        : "target" === propName
+          ? (this.target = nativeEventTarget)
+          : (this[propName] = nativeEvent[propName]));
+  this.isDefaultPrevented = (null != nativeEvent.defaultPrevented
+  ? nativeEvent.defaultPrevented
+  : !1 === nativeEvent.returnValue)
+    ? functionThatReturnsTrue
+    : functionThatReturnsFalse;
+  this.isPropagationStopped = functionThatReturnsFalse;
+  return this;
+}
+Object.assign(SyntheticEvent.prototype, {
+  preventDefault: function() {
+    this.defaultPrevented = !0;
+    var event = this.nativeEvent;
+    event &&
+      (event.preventDefault
+        ? event.preventDefault()
+        : "unknown" !== typeof event.returnValue && (event.returnValue = !1),
+      (this.isDefaultPrevented = functionThatReturnsTrue));
+  },
+  stopPropagation: function() {
+    var event = this.nativeEvent;
+    event &&
+      (event.stopPropagation
+        ? event.stopPropagation()
+        : "unknown" !== typeof event.cancelBubble && (event.cancelBubble = !0),
+      (this.isPropagationStopped = functionThatReturnsTrue));
+  },
+  persist: function() {
+    this.isPersistent = functionThatReturnsTrue;
+  },
+  isPersistent: functionThatReturnsFalse,
+  destructor: function() {
+    var Interface = this.constructor.Interface,
+      propName;
+    for (propName in Interface) this[propName] = null;
+    for (
+      Interface = 0;
+      Interface < shouldBeReleasedProperties.length;
+      Interface++
+    )
+      this[shouldBeReleasedProperties[Interface]] = null;
+  }
+});
+SyntheticEvent.Interface = {
+  type: null,
+  target: null,
+  currentTarget: function() {
+    return null;
+  },
+  eventPhase: null,
+  bubbles: null,
+  cancelable: null,
+  timeStamp: function(event) {
+    return event.timeStamp || Date.now();
+  },
+  defaultPrevented: null,
+  isTrusted: null
+};
+SyntheticEvent.extend = function(Interface) {
+  function E() {}
+  function Class() {
+    return Super.apply(this, arguments);
+  }
+  var Super = this;
+  E.prototype = Super.prototype;
+  var prototype = new E();
+  Object.assign(prototype, Class.prototype);
+  Class.prototype = prototype;
+  Class.prototype.constructor = Class;
+  Class.Interface = Object.assign({}, Super.Interface, Interface);
+  Class.extend = Super.extend;
+  addEventPoolingTo(Class);
+  return Class;
+};
+addEventPoolingTo(SyntheticEvent);
+function getPooledEvent(dispatchConfig, targetInst, nativeEvent, nativeInst) {
+  if (this.eventPool.length) {
+    var instance = this.eventPool.pop();
+    this.call(instance, dispatchConfig, targetInst, nativeEvent, nativeInst);
+    return instance;
+  }
+  return new this(dispatchConfig, targetInst, nativeEvent, nativeInst);
+}
+function releasePooledEvent(event) {
+  invariant(
+    event instanceof this,
+    "Trying to release an event instance  into a pool of a different type."
+  );
+  event.destructor();
+  10 > this.eventPool.length && this.eventPool.push(event);
+}
+function addEventPoolingTo(EventConstructor) {
+  EventConstructor.eventPool = [];
+  EventConstructor.getPooled = getPooledEvent;
+  EventConstructor.release = releasePooledEvent;
+}
+var ResponderSyntheticEvent = SyntheticEvent.extend({
+  touchHistory: function() {
+    return null;
+  }
+});
+function isStartish(topLevelType) {
+  return "topTouchStart" === topLevelType;
+}
+function isMoveish(topLevelType) {
+  return "topTouchMove" === topLevelType;
+}
+var startDependencies = ["topTouchStart"],
+  moveDependencies = ["topTouchMove"],
+  endDependencies = ["topTouchCancel", "topTouchEnd"],
+  touchBank = [],
+  touchHistory = {
+    touchBank: touchBank,
+    numberActiveTouches: 0,
+    indexOfSingleActiveTouch: -1,
+    mostRecentTimeStamp: 0
+  };
+function timestampForTouch(touch) {
+  return touch.timeStamp || touch.timestamp;
+}
+function getTouchIdentifier(_ref) {
+  _ref = _ref.identifier;
+  invariant(null != _ref, "Touch object is missing identifier.");
+  return _ref;
+}
+function recordTouchStart(touch) {
+  var identifier = getTouchIdentifier(touch),
+    touchRecord = touchBank[identifier];
+  touchRecord
+    ? ((touchRecord.touchActive = !0),
+      (touchRecord.startPageX = touch.pageX),
+      (touchRecord.startPageY = touch.pageY),
+      (touchRecord.startTimeStamp = timestampForTouch(touch)),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchRecord.previousPageX = touch.pageX),
+      (touchRecord.previousPageY = touch.pageY),
+      (touchRecord.previousTimeStamp = timestampForTouch(touch)))
+    : ((touchRecord = {
+        touchActive: !0,
+        startPageX: touch.pageX,
+        startPageY: touch.pageY,
+        startTimeStamp: timestampForTouch(touch),
+        currentPageX: touch.pageX,
+        currentPageY: touch.pageY,
+        currentTimeStamp: timestampForTouch(touch),
+        previousPageX: touch.pageX,
+        previousPageY: touch.pageY,
+        previousTimeStamp: timestampForTouch(touch)
+      }),
+      (touchBank[identifier] = touchRecord));
+  touchHistory.mostRecentTimeStamp = timestampForTouch(touch);
+}
+function recordTouchMove(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  touchRecord
+    ? ((touchRecord.touchActive = !0),
+      (touchRecord.previousPageX = touchRecord.currentPageX),
+      (touchRecord.previousPageY = touchRecord.currentPageY),
+      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
+    : console.error(
+        "Cannot record touch move without a touch start.\nTouch Move: %s\n",
+        "Touch Bank: %s",
+        printTouch(touch),
+        printTouchBank()
+      );
+}
+function recordTouchEnd(touch) {
+  var touchRecord = touchBank[getTouchIdentifier(touch)];
+  touchRecord
+    ? ((touchRecord.touchActive = !1),
+      (touchRecord.previousPageX = touchRecord.currentPageX),
+      (touchRecord.previousPageY = touchRecord.currentPageY),
+      (touchRecord.previousTimeStamp = touchRecord.currentTimeStamp),
+      (touchRecord.currentPageX = touch.pageX),
+      (touchRecord.currentPageY = touch.pageY),
+      (touchRecord.currentTimeStamp = timestampForTouch(touch)),
+      (touchHistory.mostRecentTimeStamp = timestampForTouch(touch)))
+    : console.error(
+        "Cannot record touch end without a touch start.\nTouch End: %s\n",
+        "Touch Bank: %s",
+        printTouch(touch),
+        printTouchBank()
+      );
+}
+function printTouch(touch) {
+  return JSON.stringify({
+    identifier: touch.identifier,
+    pageX: touch.pageX,
+    pageY: touch.pageY,
+    timestamp: timestampForTouch(touch)
+  });
+}
+function printTouchBank() {
+  var printed = JSON.stringify(touchBank.slice(0, 20));
+  20 < touchBank.length &&
+    (printed += " (original size: " + touchBank.length + ")");
+  return printed;
+}
+var ResponderTouchHistoryStore = {
+  recordTouchTrack: function(topLevelType, nativeEvent) {
+    if (isMoveish(topLevelType))
+      nativeEvent.changedTouches.forEach(recordTouchMove);
+    else if (isStartish(topLevelType))
+      nativeEvent.changedTouches.forEach(recordTouchStart),
+        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+        1 === touchHistory.numberActiveTouches &&
+          (touchHistory.indexOfSingleActiveTouch =
+            nativeEvent.touches[0].identifier);
+    else if (
+      "topTouchEnd" === topLevelType ||
+      "topTouchCancel" === topLevelType
+    )
+      if (
+        (nativeEvent.changedTouches.forEach(recordTouchEnd),
+        (touchHistory.numberActiveTouches = nativeEvent.touches.length),
+        1 === touchHistory.numberActiveTouches)
+      )
+        for (topLevelType = 0; topLevelType < touchBank.length; topLevelType++)
+          if (
+            ((nativeEvent = touchBank[topLevelType]),
+            null != nativeEvent && nativeEvent.touchActive)
+          ) {
+            touchHistory.indexOfSingleActiveTouch = topLevelType;
+            break;
+          }
+  },
+  touchHistory: touchHistory
+};
+function accumulate(current, next) {
+  invariant(
+    null != next,
+    "accumulate(...): Accumulated items must be not be null or undefined."
+  );
+  return null == current
+    ? next
+    : Array.isArray(current)
+      ? current.concat(next)
+      : Array.isArray(next) ? [current].concat(next) : [current, next];
+}
+var responderInst = null,
+  trackedTouchCount = 0;
+function changeResponder(nextResponderInst, blockHostResponder) {
+  var oldResponderInst = responderInst;
+  responderInst = nextResponderInst;
+  if (null !== ResponderEventPlugin.GlobalResponderHandler)
+    ResponderEventPlugin.GlobalResponderHandler.onChange(
+      oldResponderInst,
+      nextResponderInst,
+      blockHostResponder
+    );
+}
+var eventTypes$1 = {
+    startShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onStartShouldSetResponder",
+        captured: "onStartShouldSetResponderCapture"
+      },
+      dependencies: startDependencies
+    },
+    scrollShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onScrollShouldSetResponder",
+        captured: "onScrollShouldSetResponderCapture"
+      },
+      dependencies: ["topScroll"]
+    },
+    selectionChangeShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onSelectionChangeShouldSetResponder",
+        captured: "onSelectionChangeShouldSetResponderCapture"
+      },
+      dependencies: ["topSelectionChange"]
+    },
+    moveShouldSetResponder: {
+      phasedRegistrationNames: {
+        bubbled: "onMoveShouldSetResponder",
+        captured: "onMoveShouldSetResponderCapture"
+      },
+      dependencies: moveDependencies
+    },
+    responderStart: {
+      registrationName: "onResponderStart",
+      dependencies: startDependencies
+    },
+    responderMove: {
+      registrationName: "onResponderMove",
+      dependencies: moveDependencies
+    },
+    responderEnd: {
+      registrationName: "onResponderEnd",
+      dependencies: endDependencies
+    },
+    responderRelease: {
+      registrationName: "onResponderRelease",
+      dependencies: endDependencies
+    },
+    responderTerminationRequest: {
+      registrationName: "onResponderTerminationRequest",
+      dependencies: []
+    },
+    responderGrant: { registrationName: "onResponderGrant", dependencies: [] },
+    responderReject: {
+      registrationName: "onResponderReject",
+      dependencies: []
+    },
+    responderTerminate: {
+      registrationName: "onResponderTerminate",
+      dependencies: []
+    }
+  },
+  ResponderEventPlugin = {
+    _getResponder: function() {
+      return responderInst;
+    },
+    eventTypes: eventTypes$1,
+    extractEvents: function(
+      topLevelType,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    ) {
+      if (isStartish(topLevelType)) trackedTouchCount += 1;
+      else if (
+        "topTouchEnd" === topLevelType ||
+        "topTouchCancel" === topLevelType
+      )
+        if (0 <= trackedTouchCount) --trackedTouchCount;
+        else
+          return (
+            console.error(
+              "Ended a touch event which was not counted in `trackedTouchCount`."
+            ),
+            null
+          );
+      ResponderTouchHistoryStore.recordTouchTrack(topLevelType, nativeEvent);
+      if (
+        targetInst &&
+        (("topScroll" === topLevelType && !nativeEvent.responderIgnoreScroll) ||
+          (0 < trackedTouchCount && "topSelectionChange" === topLevelType) ||
+          isStartish(topLevelType) ||
+          isMoveish(topLevelType))
+      ) {
+        var JSCompiler_temp = isStartish(topLevelType)
+          ? eventTypes$1.startShouldSetResponder
+          : isMoveish(topLevelType)
+            ? eventTypes$1.moveShouldSetResponder
+            : "topSelectionChange" === topLevelType
+              ? eventTypes$1.selectionChangeShouldSetResponder
+              : eventTypes$1.scrollShouldSetResponder;
+        if (responderInst)
+          b: {
+            var JSCompiler_temp$jscomp$0 = responderInst;
+            for (
+              var depthA = 0, tempA = JSCompiler_temp$jscomp$0;
+              tempA;
+              tempA = getParent(tempA)
+            )
+              depthA++;
+            tempA = 0;
+            for (var tempB = targetInst; tempB; tempB = getParent(tempB))
+              tempA++;
+            for (; 0 < depthA - tempA; )
+              (JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0)),
+                depthA--;
+            for (; 0 < tempA - depthA; )
+              (targetInst = getParent(targetInst)), tempA--;
+            for (; depthA--; ) {
+              if (
+                JSCompiler_temp$jscomp$0 === targetInst ||
+                JSCompiler_temp$jscomp$0 === targetInst.alternate
+              )
+                break b;
+              JSCompiler_temp$jscomp$0 = getParent(JSCompiler_temp$jscomp$0);
+              targetInst = getParent(targetInst);
+            }
+            JSCompiler_temp$jscomp$0 = null;
+          }
+        else JSCompiler_temp$jscomp$0 = targetInst;
+        targetInst = JSCompiler_temp$jscomp$0 === responderInst;
+        JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
+          JSCompiler_temp,
+          JSCompiler_temp$jscomp$0,
+          nativeEvent,
+          nativeEventTarget
+        );
+        JSCompiler_temp$jscomp$0.touchHistory =
+          ResponderTouchHistoryStore.touchHistory;
+        targetInst
+          ? forEachAccumulated(
+              JSCompiler_temp$jscomp$0,
+              accumulateTwoPhaseDispatchesSingleSkipTarget
+            )
+          : forEachAccumulated(
+              JSCompiler_temp$jscomp$0,
+              accumulateTwoPhaseDispatchesSingle
+            );
+        b: {
+          JSCompiler_temp = JSCompiler_temp$jscomp$0._dispatchListeners;
+          targetInst = JSCompiler_temp$jscomp$0._dispatchInstances;
+          if (Array.isArray(JSCompiler_temp))
+            for (
+              depthA = 0;
+              depthA < JSCompiler_temp.length &&
+              !JSCompiler_temp$jscomp$0.isPropagationStopped();
+              depthA++
+            ) {
+              if (
+                JSCompiler_temp[depthA](
+                  JSCompiler_temp$jscomp$0,
+                  targetInst[depthA]
+                )
+              ) {
+                JSCompiler_temp = targetInst[depthA];
+                break b;
+              }
+            }
+          else if (
+            JSCompiler_temp &&
+            JSCompiler_temp(JSCompiler_temp$jscomp$0, targetInst)
+          ) {
+            JSCompiler_temp = targetInst;
+            break b;
+          }
+          JSCompiler_temp = null;
+        }
+        JSCompiler_temp$jscomp$0._dispatchInstances = null;
+        JSCompiler_temp$jscomp$0._dispatchListeners = null;
+        JSCompiler_temp$jscomp$0.isPersistent() ||
+          JSCompiler_temp$jscomp$0.constructor.release(
+            JSCompiler_temp$jscomp$0
+          );
+        JSCompiler_temp && JSCompiler_temp !== responderInst
+          ? ((JSCompiler_temp$jscomp$0 = void 0),
+            (targetInst = ResponderSyntheticEvent.getPooled(
+              eventTypes$1.responderGrant,
+              JSCompiler_temp,
+              nativeEvent,
+              nativeEventTarget
+            )),
+            (targetInst.touchHistory = ResponderTouchHistoryStore.touchHistory),
+            forEachAccumulated(targetInst, accumulateDirectDispatchesSingle),
+            (depthA = !0 === executeDirectDispatch(targetInst)),
+            responderInst
+              ? ((tempA = ResponderSyntheticEvent.getPooled(
+                  eventTypes$1.responderTerminationRequest,
+                  responderInst,
+                  nativeEvent,
+                  nativeEventTarget
+                )),
+                (tempA.touchHistory = ResponderTouchHistoryStore.touchHistory),
+                forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
+                (tempB =
+                  !tempA._dispatchListeners || executeDirectDispatch(tempA)),
+                tempA.isPersistent() || tempA.constructor.release(tempA),
+                tempB
+                  ? ((tempA = ResponderSyntheticEvent.getPooled(
+                      eventTypes$1.responderTerminate,
+                      responderInst,
+                      nativeEvent,
+                      nativeEventTarget
+                    )),
+                    (tempA.touchHistory =
+                      ResponderTouchHistoryStore.touchHistory),
+                    forEachAccumulated(tempA, accumulateDirectDispatchesSingle),
+                    (JSCompiler_temp$jscomp$0 = accumulate(
+                      JSCompiler_temp$jscomp$0,
+                      [targetInst, tempA]
+                    )),
+                    changeResponder(JSCompiler_temp, depthA))
+                  : ((JSCompiler_temp = ResponderSyntheticEvent.getPooled(
+                      eventTypes$1.responderReject,
+                      JSCompiler_temp,
+                      nativeEvent,
+                      nativeEventTarget
+                    )),
+                    (JSCompiler_temp.touchHistory =
+                      ResponderTouchHistoryStore.touchHistory),
+                    forEachAccumulated(
+                      JSCompiler_temp,
+                      accumulateDirectDispatchesSingle
+                    ),
+                    (JSCompiler_temp$jscomp$0 = accumulate(
+                      JSCompiler_temp$jscomp$0,
+                      JSCompiler_temp
+                    ))))
+              : ((JSCompiler_temp$jscomp$0 = accumulate(
+                  JSCompiler_temp$jscomp$0,
+                  targetInst
+                )),
+                changeResponder(JSCompiler_temp, depthA)),
+            (JSCompiler_temp = JSCompiler_temp$jscomp$0))
+          : (JSCompiler_temp = null);
+      } else JSCompiler_temp = null;
+      JSCompiler_temp$jscomp$0 = responderInst && isStartish(topLevelType);
+      targetInst = responderInst && isMoveish(topLevelType);
+      depthA =
+        responderInst &&
+        ("topTouchEnd" === topLevelType || "topTouchCancel" === topLevelType);
+      if (
+        (JSCompiler_temp$jscomp$0 = JSCompiler_temp$jscomp$0
+          ? eventTypes$1.responderStart
+          : targetInst
+            ? eventTypes$1.responderMove
+            : depthA ? eventTypes$1.responderEnd : null)
+      )
+        (JSCompiler_temp$jscomp$0 = ResponderSyntheticEvent.getPooled(
+          JSCompiler_temp$jscomp$0,
+          responderInst,
+          nativeEvent,
+          nativeEventTarget
+        )),
+          (JSCompiler_temp$jscomp$0.touchHistory =
+            ResponderTouchHistoryStore.touchHistory),
+          forEachAccumulated(
+            JSCompiler_temp$jscomp$0,
+            accumulateDirectDispatchesSingle
+          ),
+          (JSCompiler_temp = accumulate(
+            JSCompiler_temp,
+            JSCompiler_temp$jscomp$0
+          ));
+      JSCompiler_temp$jscomp$0 =
+        responderInst && "topTouchCancel" === topLevelType;
+      if (
+        (topLevelType =
+          responderInst &&
+          !JSCompiler_temp$jscomp$0 &&
+          ("topTouchEnd" === topLevelType || "topTouchCancel" === topLevelType))
+      )
+        a: {
+          if ((topLevelType = nativeEvent.touches) && 0 !== topLevelType.length)
+            for (targetInst = 0; targetInst < topLevelType.length; targetInst++)
+              if (
+                ((depthA = topLevelType[targetInst].target),
+                null !== depthA && void 0 !== depthA && 0 !== depthA)
+              ) {
+                tempA = getInstanceFromNode(depthA);
+                b: {
+                  for (depthA = responderInst; tempA; ) {
+                    if (depthA === tempA || depthA === tempA.alternate) {
+                      depthA = !0;
+                      break b;
+                    }
+                    tempA = getParent(tempA);
+                  }
+                  depthA = !1;
+                }
+                if (depthA) {
+                  topLevelType = !1;
+                  break a;
+                }
+              }
+          topLevelType = !0;
+        }
+      if (
+        (topLevelType = JSCompiler_temp$jscomp$0
+          ? eventTypes$1.responderTerminate
+          : topLevelType ? eventTypes$1.responderRelease : null)
+      )
+        (nativeEvent = ResponderSyntheticEvent.getPooled(
+          topLevelType,
+          responderInst,
+          nativeEvent,
+          nativeEventTarget
+        )),
+          (nativeEvent.touchHistory = ResponderTouchHistoryStore.touchHistory),
+          forEachAccumulated(nativeEvent, accumulateDirectDispatchesSingle),
+          (JSCompiler_temp = accumulate(JSCompiler_temp, nativeEvent)),
+          changeResponder(null);
+      return JSCompiler_temp;
+    },
+    GlobalResponderHandler: null,
+    injection: {
+      injectGlobalResponderHandler: function(GlobalResponderHandler) {
+        ResponderEventPlugin.GlobalResponderHandler = GlobalResponderHandler;
+      }
+    }
+  },
+  customBubblingEventTypes$1 =
+    ReactNativeViewConfigRegistry.customBubblingEventTypes,
+  customDirectEventTypes$1 =
+    ReactNativeViewConfigRegistry.customDirectEventTypes,
+  ReactNativeBridgeEventPlugin = {
+    eventTypes: ReactNativeViewConfigRegistry.eventTypes,
+    extractEvents: function(
+      topLevelType,
+      targetInst,
+      nativeEvent,
+      nativeEventTarget
+    ) {
+      if (null == targetInst) return null;
+      var bubbleDispatchConfig = customBubblingEventTypes$1[topLevelType],
+        directDispatchConfig = customDirectEventTypes$1[topLevelType];
+      invariant(
+        bubbleDispatchConfig || directDispatchConfig,
+        'Unsupported top level event type "%s" dispatched',
+        topLevelType
+      );
+      topLevelType = SyntheticEvent.getPooled(
+        bubbleDispatchConfig || directDispatchConfig,
+        targetInst,
+        nativeEvent,
+        nativeEventTarget
+      );
+      if (bubbleDispatchConfig)
+        forEachAccumulated(topLevelType, accumulateTwoPhaseDispatchesSingle);
+      else if (directDispatchConfig)
+        forEachAccumulated(topLevelType, accumulateDirectDispatchesSingle);
+      else return null;
+      return topLevelType;
+    }
+  };
+injection.injectEventPluginOrder([
+  "ResponderEventPlugin",
+  "ReactNativeBridgeEventPlugin"
+]);
+injection.injectEventPluginsByName({
+  ResponderEventPlugin: ResponderEventPlugin,
+  ReactNativeBridgeEventPlugin: ReactNativeBridgeEventPlugin
+});
+var instanceCache = {},
+  instanceProps = {};
+function uncacheFiberNode(tag) {
+  delete instanceCache[tag];
+  delete instanceProps[tag];
+}
+function getInstanceFromTag(tag) {
+  return instanceCache[tag] || null;
+}
+var ReactNativeComponentTree = {
+    precacheFiberNode: function(hostInst, tag) {
+      instanceCache[tag] = hostInst;
+    },
+    uncacheFiberNode: uncacheFiberNode,
+    getClosestInstanceFromNode: getInstanceFromTag,
+    getInstanceFromNode: getInstanceFromTag,
+    getNodeFromInstance: function(inst) {
+      var tag = inst.stateNode._nativeTag;
+      void 0 === tag && (tag = inst.stateNode.canonical._nativeTag);
+      invariant(tag, "All native instances should have a tag.");
+      return tag;
+    },
+    getFiberCurrentPropsFromNode: function(stateNode) {
+      return instanceProps[stateNode._nativeTag] || null;
+    },
+    updateFiberProps: function(tag, props) {
+      instanceProps[tag] = props;
+    }
+  },
+  restoreTarget = null,
+  restoreQueue = null;
+function restoreStateOfTarget(target) {
+  if ((target = getInstanceFromNode(target))) {
+    invariant(
+      null,
+      "Fiber needs to be injected to handle a fiber target for controlled events. This error is likely caused by a bug in React. Please file an issue."
+    );
+    var props = getFiberCurrentPropsFromNode(target.stateNode);
+    null.restoreControlledState(target.stateNode, target.type, props);
+  }
+}
+function _batchedUpdates(fn, bookkeeping) {
+  return fn(bookkeeping);
+}
+function _flushInteractiveUpdates() {}
+var isBatching = !1;
+function batchedUpdates(fn, bookkeeping) {
+  if (isBatching) return fn(bookkeeping);
+  isBatching = !0;
+  try {
+    return _batchedUpdates(fn, bookkeeping);
+  } finally {
+    if (((isBatching = !1), null !== restoreTarget || null !== restoreQueue))
+      if (
+        (_flushInteractiveUpdates(),
+        restoreTarget &&
+          ((bookkeeping = restoreTarget),
+          (fn = restoreQueue),
+          (restoreQueue = restoreTarget = null),
+          restoreStateOfTarget(bookkeeping),
+          fn))
+      )
+        for (bookkeeping = 0; bookkeeping < fn.length; bookkeeping++)
+          restoreStateOfTarget(fn[bookkeeping]);
+  }
+}
+var EMPTY_NATIVE_EVENT = {};
+function _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam) {
+  var nativeEvent = nativeEventParam || EMPTY_NATIVE_EVENT,
+    inst = getInstanceFromTag(rootNodeID);
+  batchedUpdates(function() {
+    var events = nativeEvent.target;
+    for (var events$jscomp$0 = null, i = 0; i < plugins.length; i++) {
+      var possiblePlugin = plugins[i];
+      possiblePlugin &&
+        (possiblePlugin = possiblePlugin.extractEvents(
+          topLevelType,
+          inst,
+          nativeEvent,
+          events
+        )) &&
+        (events$jscomp$0 = accumulateInto(events$jscomp$0, possiblePlugin));
+    }
+    events = events$jscomp$0;
+    null !== events && (eventQueue = accumulateInto(eventQueue, events));
+    events = eventQueue;
+    eventQueue = null;
+    events &&
+      (forEachAccumulated(events, executeDispatchesAndReleaseTopLevel),
+      invariant(
+        !eventQueue,
+        "processEventQueue(): Additional events were enqueued while processing an event queue. Support for this has not yet been implemented."
+      ),
+      ReactErrorUtils.rethrowCaughtError());
+  });
+}
+RCTEventEmitter.register({
+  getListener: getListener,
+  registrationNames: registrationNameModules,
+  _receiveRootNodeIDEvent: _receiveRootNodeIDEvent,
+  receiveEvent: function(rootNodeID, topLevelType, nativeEventParam) {
+    _receiveRootNodeIDEvent(rootNodeID, topLevelType, nativeEventParam);
+  },
+  receiveTouches: function(eventTopLevelType, touches, changedIndices) {
+    if (
+      "topTouchEnd" === eventTopLevelType ||
+      "topTouchCancel" === eventTopLevelType
+    ) {
+      var JSCompiler_temp = [];
+      for (var i = 0; i < changedIndices.length; i++) {
+        var index = changedIndices[i];
+        JSCompiler_temp.push(touches[index]);
+        touches[index] = null;
+      }
+      for (i = changedIndices = 0; i < touches.length; i++)
+        (index = touches[i]),
+          null !== index && (touches[changedIndices++] = index);
+      touches.length = changedIndices;
+    } else
+      for (JSCompiler_temp = [], i = 0; i < changedIndices.length; i++)
+        JSCompiler_temp.push(touches[changedIndices[i]]);
+    for (
+      changedIndices = 0;
+      changedIndices < JSCompiler_temp.length;
+      changedIndices++
+    ) {
+      i = JSCompiler_temp[changedIndices];
+      i.changedTouches = JSCompiler_temp;
+      i.touches = touches;
+      index = null;
+      var target = i.target;
+      null === target || void 0 === target || 1 > target || (index = target);
+      _receiveRootNodeIDEvent(index, eventTopLevelType, i);
+    }
+  }
+});
+getFiberCurrentPropsFromNode =
+  ReactNativeComponentTree.getFiberCurrentPropsFromNode;
+getInstanceFromNode = ReactNativeComponentTree.getInstanceFromNode;
+getNodeFromInstance = ReactNativeComponentTree.getNodeFromInstance;
+ResponderEventPlugin.injection.injectGlobalResponderHandler({
+  onChange: function(from, to, blockNativeResponder) {
+    null !== to
+      ? UIManager.setJSResponder(to.stateNode._nativeTag, blockNativeResponder)
+      : UIManager.clearJSResponder();
+  }
+});
+var ReactCurrentOwner =
+    React.__SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactCurrentOwner,
+  hasSymbol = "function" === typeof Symbol && Symbol.for,
+  REACT_ELEMENT_TYPE = hasSymbol ? Symbol.for("react.element") : 60103,
+  REACT_PORTAL_TYPE = hasSymbol ? Symbol.for("react.portal") : 60106,
+  REACT_FRAGMENT_TYPE = hasSymbol ? Symbol.for("react.fragment") : 60107,
+  REACT_STRICT_MODE_TYPE = hasSymbol ? Symbol.for("react.strict_mode") : 60108,
+  REACT_PROFILER_TYPE = hasSymbol ? Symbol.for("react.profiler") : 60114,
+  REACT_PROVIDER_TYPE = hasSymbol ? Symbol.for("react.provider") : 60109,
+  REACT_CONTEXT_TYPE = hasSymbol ? Symbol.for("react.context") : 60110,
+  REACT_ASYNC_MODE_TYPE = hasSymbol ? Symbol.for("react.async_mode") : 60111,
+  REACT_FORWARD_REF_TYPE = hasSymbol ? Symbol.for("react.forward_ref") : 60112,
+  REACT_TIMEOUT_TYPE = hasSymbol ? Symbol.for("react.timeout") : 60113,
+  MAYBE_ITERATOR_SYMBOL = "function" === typeof Symbol && Symbol.iterator;
+function getIteratorFn(maybeIterable) {
+  if (null === maybeIterable || "undefined" === typeof maybeIterable)
+    return null;
+  maybeIterable =
+    (MAYBE_ITERATOR_SYMBOL && maybeIterable[MAYBE_ITERATOR_SYMBOL]) ||
+    maybeIterable["@@iterator"];
+  return "function" === typeof maybeIterable ? maybeIterable : null;
+}
+function getComponentName(fiber) {
+  var type = fiber.type;
+  if ("function" === typeof type) return type.displayName || type.name;
+  if ("string" === typeof type) return type;
+  switch (type) {
+    case REACT_ASYNC_MODE_TYPE:
+      return "AsyncMode";
+    case REACT_CONTEXT_TYPE:
+      return "Context.Consumer";
+    case REACT_FRAGMENT_TYPE:
+      return "ReactFragment";
+    case REACT_PORTAL_TYPE:
+      return "ReactPortal";
+    case REACT_PROFILER_TYPE:
+      return "Profiler(" + fiber.pendingProps.id + ")";
+    case REACT_PROVIDER_TYPE:
+      return "Context.Provider";
+    case REACT_STRICT_MODE_TYPE:
+      return "StrictMode";
+    case REACT_TIMEOUT_TYPE:
+      return "Timeout";
+  }
+  if ("object" === typeof type && null !== type)
+    switch (type.$$typeof) {
+      case REACT_FORWARD_REF_TYPE:
+        return (
+          (fiber = type.render.displayName || type.render.name || ""),
+          "" !== fiber ? "ForwardRef(" + fiber + ")" : "ForwardRef"
+        );
+    }
+  return null;
+}
+function isFiberMountedImpl(fiber) {
+  var node = fiber;
+  if (fiber.alternate) for (; node.return; ) node = node.return;
+  else {
+    if (0 !== (node.effectTag & 2)) return 1;
+    for (; node.return; )
+      if (((node = node.return), 0 !== (node.effectTag & 2))) return 1;
+  }
+  return 3 === node.tag ? 2 : 3;
+}
+function assertIsMounted(fiber) {
+  invariant(
+    2 === isFiberMountedImpl(fiber),
+    "Unable to find node on an unmounted component."
+  );
+}
+function findCurrentFiberUsingSlowPath(fiber) {
+  var alternate = fiber.alternate;
+  if (!alternate)
+    return (
+      (alternate = isFiberMountedImpl(fiber)),
+      invariant(
+        3 !== alternate,
+        "Unable to find node on an unmounted component."
+      ),
+      1 === alternate ? null : fiber
+    );
+  for (var a = fiber, b = alternate; ; ) {
+    var parentA = a.return,
+      parentB = parentA ? parentA.alternate : null;
+    if (!parentA || !parentB) break;
+    if (parentA.child === parentB.child) {
+      for (var child = parentA.child; child; ) {
+        if (child === a) return assertIsMounted(parentA), fiber;
+        if (child === b) return assertIsMounted(parentA), alternate;
+        child = child.sibling;
+      }
+      invariant(!1, "Unable to find node on an unmounted component.");
+    }
+    if (a.return !== b.return) (a = parentA), (b = parentB);
+    else {
+      child = !1;
+      for (var _child = parentA.child; _child; ) {
+        if (_child === a) {
+          child = !0;
+          a = parentA;
+          b = parentB;
+          break;
+        }
+        if (_child === b) {
+          child = !0;
+          b = parentA;
+          a = parentB;
+          break;
+        }
+        _child = _child.sibling;
+      }
+      if (!child) {
+        for (_child = parentB.child; _child; ) {
+          if (_child === a) {
+            child = !0;
+            a = parentB;
+            b = parentA;
+            break;
+          }
+          if (_child === b) {
+            child = !0;
+            b = parentB;
+            a = parentA;
+            break;
+          }
+          _child = _child.sibling;
+        }
+        invariant(
+          child,
+          "Child was not found in either parent set. This indicates a bug in React related to the return pointer. Please file an issue."
+        );
+      }
+    }
+    invariant(
+      a.alternate === b,
+      "Return fibers should always be each others' alternates. This error is likely caused by a bug in React. Please file an issue."
+    );
+  }
+  invariant(3 === a.tag, "Unable to find node on an unmounted component.");
+  return a.stateNode.current === a ? fiber : alternate;
+}
+function findCurrentHostFiber(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child) (node.child.return = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+  return null;
+}
+function findCurrentHostFiberWithNoPortals(parent) {
+  parent = findCurrentFiberUsingSlowPath(parent);
+  if (!parent) return null;
+  for (var node = parent; ; ) {
+    if (5 === node.tag || 6 === node.tag) return node;
+    if (node.child && 4 !== node.tag)
+      (node.child.return = node), (node = node.child);
+    else {
+      if (node === parent) break;
+      for (; !node.sibling; ) {
+        if (!node.return || node.return === parent) return null;
+        node = node.return;
+      }
+      node.sibling.return = node.return;
+      node = node.sibling;
+    }
+  }
+  return null;
+}
+var emptyObject$1 = {},
+  removedKeys = null,
+  removedKeyCount = 0;
+function restoreDeletedValuesInNestedArray(
+  updatePayload,
+  node,
+  validAttributes
+) {
+  if (Array.isArray(node))
+    for (var i = node.length; i-- && 0 < removedKeyCount; )
+      restoreDeletedValuesInNestedArray(
+        updatePayload,
+        node[i],
+        validAttributes
+      );
+  else if (node && 0 < removedKeyCount)
+    for (i in removedKeys)
+      if (removedKeys[i]) {
+        var _nextProp = node[i];
+        if (void 0 !== _nextProp) {
+          var attributeConfig = validAttributes[i];
+          if (attributeConfig) {
+            "function" === typeof _nextProp && (_nextProp = !0);
+            "undefined" === typeof _nextProp && (_nextProp = null);
+            if ("object" !== typeof attributeConfig)
+              updatePayload[i] = _nextProp;
+            else if (
+              "function" === typeof attributeConfig.diff ||
+              "function" === typeof attributeConfig.process
+            )
+              (_nextProp =
+                "function" === typeof attributeConfig.process
+                  ? attributeConfig.process(_nextProp)
+                  : _nextProp),
+                (updatePayload[i] = _nextProp);
+            removedKeys[i] = !1;
+            removedKeyCount--;
+          }
+        }
+      }
+}
+function diffNestedProperty(
+  updatePayload,
+  prevProp,
+  nextProp,
+  validAttributes
+) {
+  if (!updatePayload && prevProp === nextProp) return updatePayload;
+  if (!prevProp || !nextProp)
+    return nextProp
+      ? addNestedProperty(updatePayload, nextProp, validAttributes)
+      : prevProp
+        ? clearNestedProperty(updatePayload, prevProp, validAttributes)
+        : updatePayload;
+  if (!Array.isArray(prevProp) && !Array.isArray(nextProp))
+    return diffProperties(updatePayload, prevProp, nextProp, validAttributes);
+  if (Array.isArray(prevProp) && Array.isArray(nextProp)) {
+    var minLength =
+        prevProp.length < nextProp.length ? prevProp.length : nextProp.length,
+      i;
+    for (i = 0; i < minLength; i++)
+      updatePayload = diffNestedProperty(
+        updatePayload,
+        prevProp[i],
+        nextProp[i],
+        validAttributes
+      );
+    for (; i < prevProp.length; i++)
+      updatePayload = clearNestedProperty(
+        updatePayload,
+        prevProp[i],
+        validAttributes
+      );
+    for (; i < nextProp.length; i++)
+      updatePayload = addNestedProperty(
+        updatePayload,
+        nextProp[i],
+        validAttributes
+      );
+    return updatePayload;
+  }
+  return Array.isArray(prevProp)
+    ? diffProperties(
+        updatePayload,
+        flattenStyle(prevProp),
+        nextProp,
+        validAttributes
+      )
+    : diffProperties(
+        updatePayload,
+        prevProp,
+        flattenStyle(nextProp),
+        validAttributes
+      );
+}
+function addNestedProperty(updatePayload, nextProp, validAttributes) {
+  if (!nextProp) return updatePayload;
+  if (!Array.isArray(nextProp))
+    return diffProperties(
+      updatePayload,
+      emptyObject$1,
+      nextProp,
+      validAttributes
+    );
+  for (var i = 0; i < nextProp.length; i++)
+    updatePayload = addNestedProperty(
+      updatePayload,
+      nextProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function clearNestedProperty(updatePayload, prevProp, validAttributes) {
+  if (!prevProp) return updatePayload;
+  if (!Array.isArray(prevProp))
+    return diffProperties(
+      updatePayload,
+      prevProp,
+      emptyObject$1,
+      validAttributes
+    );
+  for (var i = 0; i < prevProp.length; i++)
+    updatePayload = clearNestedProperty(
+      updatePayload,
+      prevProp[i],
+      validAttributes
+    );
+  return updatePayload;
+}
+function diffProperties(updatePayload, prevProps, nextProps, validAttributes) {
+  var attributeConfig, propKey;
+  for (propKey in nextProps)
+    if ((attributeConfig = validAttributes[propKey])) {
+      var prevProp = prevProps[propKey];
+      var nextProp = nextProps[propKey];
+      "function" === typeof nextProp &&
+        ((nextProp = !0), "function" === typeof prevProp && (prevProp = !0));
+      "undefined" === typeof nextProp &&
+        ((nextProp = null),
+        "undefined" === typeof prevProp && (prevProp = null));
+      removedKeys && (removedKeys[propKey] = !1);
+      if (updatePayload && void 0 !== updatePayload[propKey])
+        if ("object" !== typeof attributeConfig)
+          updatePayload[propKey] = nextProp;
+        else {
+          if (
+            "function" === typeof attributeConfig.diff ||
+            "function" === typeof attributeConfig.process
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              (updatePayload[propKey] = attributeConfig);
+        }
+      else if (prevProp !== nextProp)
+        if ("object" !== typeof attributeConfig)
+          ("object" !== typeof nextProp ||
+            null === nextProp ||
+            deepDiffer(prevProp, nextProp)) &&
+            ((updatePayload || (updatePayload = {}))[propKey] = nextProp);
+        else if (
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+        ) {
+          if (
+            void 0 === prevProp ||
+            ("function" === typeof attributeConfig.diff
+              ? attributeConfig.diff(prevProp, nextProp)
+              : "object" !== typeof nextProp ||
+                null === nextProp ||
+                deepDiffer(prevProp, nextProp))
+          )
+            (attributeConfig =
+              "function" === typeof attributeConfig.process
+                ? attributeConfig.process(nextProp)
+                : nextProp),
+              ((updatePayload || (updatePayload = {}))[
+                propKey
+              ] = attributeConfig);
+        } else
+          (removedKeys = null),
+            (removedKeyCount = 0),
+            (updatePayload = diffNestedProperty(
+              updatePayload,
+              prevProp,
+              nextProp,
+              attributeConfig
+            )),
+            0 < removedKeyCount &&
+              updatePayload &&
+              (restoreDeletedValuesInNestedArray(
+                updatePayload,
+                nextProp,
+                attributeConfig
+              ),
+              (removedKeys = null));
+    }
+  for (var _propKey in prevProps)
+    void 0 === nextProps[_propKey] &&
+      (!(attributeConfig = validAttributes[_propKey]) ||
+        (updatePayload && void 0 !== updatePayload[_propKey]) ||
+        ((prevProp = prevProps[_propKey]),
+        void 0 !== prevProp &&
+          ("object" !== typeof attributeConfig ||
+          "function" === typeof attributeConfig.diff ||
+          "function" === typeof attributeConfig.process
+            ? (((updatePayload || (updatePayload = {}))[_propKey] = null),
+              removedKeys || (removedKeys = {}),
+              removedKeys[_propKey] ||
+                ((removedKeys[_propKey] = !0), removedKeyCount++))
+            : (updatePayload = clearNestedProperty(
+                updatePayload,
+                prevProp,
+                attributeConfig
+              )))));
+  return updatePayload;
+}
+function mountSafeCallback(context, callback) {
+  return function() {
+    if (callback) {
+      if ("boolean" === typeof context.__isMounted) {
+        if (!context.__isMounted) return;
+      } else if (
+        "function" === typeof context.isMounted &&
+        !context.isMounted()
+      )
+        return;
+      return callback.apply(context, arguments);
+    }
+  };
+}
+var ReactNativeFiberHostComponent = (function() {
+    function ReactNativeFiberHostComponent(tag, viewConfig) {
+      if (!(this instanceof ReactNativeFiberHostComponent))
+        throw new TypeError("Cannot call a class as a function");
+      this._nativeTag = tag;
+      this._children = [];
+      this.viewConfig = viewConfig;
+    }
+    ReactNativeFiberHostComponent.prototype.blur = function() {
+      TextInputState.blurTextInput(this._nativeTag);
+    };
+    ReactNativeFiberHostComponent.prototype.focus = function() {
+      TextInputState.focusTextInput(this._nativeTag);
+    };
+    ReactNativeFiberHostComponent.prototype.measure = function(callback) {
+      UIManager.measure(this._nativeTag, mountSafeCallback(this, callback));
+    };
+    ReactNativeFiberHostComponent.prototype.measureInWindow = function(
+      callback
+    ) {
+      UIManager.measureInWindow(
+        this._nativeTag,
+        mountSafeCallback(this, callback)
+      );
+    };
+    ReactNativeFiberHostComponent.prototype.measureLayout = function(
+      relativeToNativeNode,
+      onSuccess,
+      onFail
+    ) {
+      UIManager.measureLayout(
+        this._nativeTag,
+        relativeToNativeNode,
+        mountSafeCallback(this, onFail),
+        mountSafeCallback(this, onSuccess)
+      );
+    };
+    ReactNativeFiberHostComponent.prototype.setNativeProps = function(
+      nativeProps
+    ) {
+      nativeProps = diffProperties(
+        null,
+        emptyObject$1,
+        nativeProps,
+        this.viewConfig.validAttributes
+      );
+      null != nativeProps &&
+        UIManager.updateView(
+          this._nativeTag,
+          this.viewConfig.uiViewClassName,
+          nativeProps
+        );
+    };
+    return ReactNativeFiberHostComponent;
+  })(),
+  now$1 =
+    "object" === typeof performance && "function" === typeof performance.now
+      ? function() {
+          return performance.now();
+        }
+      : function() {
+          return Date.now();
+        },
+  scheduledCallback = null,
+  frameDeadline = 0,
+  frameDeadlineObject = {
+    timeRemaining: function() {
+      return frameDeadline - now$1();
+    },
+    didTimeout: !1
+  };
+function setTimeoutCallback() {
+  frameDeadline = now$1() + 5;
+  var callback = scheduledCallback;
+  scheduledCallback = null;
+  null !== callback && callback(frameDeadlineObject);
+}
+function shim$1() {
+  invariant(
+    !1,
+    "The current renderer does not support hyration. This error is likely caused by a bug in React. Please file an issue."
+  );
+}
+var nextReactTag = 3;
+function allocateTag() {
+  var tag = nextReactTag;
+  1 === tag % 10 && (tag += 2);
+  nextReactTag = tag + 2;
+  return tag;
+}
+function recursivelyUncacheFiberNode(node) {
+  "number" === typeof node
+    ? uncacheFiberNode(node)
+    : (uncacheFiberNode(node._nativeTag),
+      node._children.forEach(recursivelyUncacheFiberNode));
+}
+function finalizeInitialChildren(parentInstance) {
+  if (0 === parentInstance._children.length) return !1;
+  var nativeTags = parentInstance._children.map(function(child) {
+    return "number" === typeof child ? child : child._nativeTag;
+  });
+  UIManager.setChildren(parentInstance._nativeTag, nativeTags);
+  return !1;
+}
+function getStackAddendumByWorkInProgressFiber(workInProgress) {
+  var info = "";
+  do {
+    a: switch (workInProgress.tag) {
+      case 0:
+      case 1:
+      case 2:
+      case 5:
+        var owner = workInProgress._debugOwner,
+          source = workInProgress._debugSource;
+        var JSCompiler_inline_result = getComponentName(workInProgress);
+        var ownerName = null;
+        owner && (ownerName = getComponentName(owner));
+        owner = source;
+        JSCompiler_inline_result =
+          "\n    in " +
+          (JSCompiler_inline_result || "Unknown") +
+          (owner
+            ? " (at " +
+              owner.fileName.replace(/^.*[\\\/]/, "") +
+              ":" +
+              owner.lineNumber +
+              ")"
+            : ownerName ? " (created by " + ownerName + ")" : "");
+        break a;
+      default:
+        JSCompiler_inline_result = "";
+    }
+    info += JSCompiler_inline_result;
+    workInProgress = workInProgress.return;
+  } while (workInProgress);
+  return info;
+}
+new Set();
+var valueStack = [],
+  index = -1;
+function createCursor(defaultValue) {
+  return { current: defaultValue };
+}
+function pop(cursor) {
+  0 > index ||
+    ((cursor.current = valueStack[index]), (valueStack[index] = null), index--);
+}
+function push(cursor, value) {
+  index++;
+  valueStack[index] = cursor.current;
+  cursor.current = value;
+}
+var contextStackCursor = createCursor(emptyObject),
+  didPerformWorkStackCursor = createCursor(!1),
+  previousContext = emptyObject;
+function getUnmaskedContext(workInProgress) {
+  return isContextProvider(workInProgress)
+    ? previousContext
+    : contextStackCursor.current;
+}
+function getMaskedContext(workInProgress, unmaskedContext) {
+  var contextTypes = workInProgress.type.contextTypes;
+  if (!contextTypes) return emptyObject;
+  var instance = workInProgress.stateNode;
+  if (
+    instance &&
+    instance.__reactInternalMemoizedUnmaskedChildContext === unmaskedContext
+  )
+    return instance.__reactInternalMemoizedMaskedChildContext;
+  var context = {},
+    key;
+  for (key in contextTypes) context[key] = unmaskedContext[key];
+  instance &&
+    ((workInProgress = workInProgress.stateNode),
+    (workInProgress.__reactInternalMemoizedUnmaskedChildContext = unmaskedContext),
+    (workInProgress.__reactInternalMemoizedMaskedChildContext = context));
+  return context;
+}
+function isContextProvider(fiber) {
+  return 2 === fiber.tag && null != fiber.type.childContextTypes;
+}
+function popContextProvider(fiber) {
+  isContextProvider(fiber) &&
+    (pop(didPerformWorkStackCursor, fiber), pop(contextStackCursor, fiber));
+}
+function popTopLevelContextObject(fiber) {
+  pop(didPerformWorkStackCursor, fiber);
+  pop(contextStackCursor, fiber);
+}
+function pushTopLevelContextObject(fiber, context, didChange) {
+  invariant(
+    contextStackCursor.current === emptyObject,
+    "Unexpected context found on stack. This error is likely caused by a bug in React. Please file an issue."
+  );
+  push(contextStackCursor, context, fiber);
+  push(didPerformWorkStackCursor, didChange, fiber);
+}
+function processChildContext(fiber, parentContext) {
+  var instance = fiber.stateNode,
+    childContextTypes = fiber.type.childContextTypes;
+  if ("function" !== typeof instance.getChildContext) return parentContext;
+  instance = instance.getChildContext();
+  for (var contextKey in instance)
+    invariant(
+      contextKey in childContextTypes,
+      '%s.getChildContext(): key "%s" is not defined in childContextTypes.',
+      getComponentName(fiber) || "Unknown",
+      contextKey
+    );
+  return Object.assign({}, parentContext, instance);
+}
+function pushContextProvider(workInProgress) {
+  if (!isContextProvider(workInProgress)) return !1;
+  var instance = workInProgress.stateNode;
+  instance =
+    (instance && instance.__reactInternalMemoizedMergedChildContext) ||
+    emptyObject;
+  previousContext = contextStackCursor.current;
+  push(contextStackCursor, instance, workInProgress);
+  push(
+    didPerformWorkStackCursor,
+    didPerformWorkStackCursor.current,
+    workInProgress
+  );
+  return !0;
+}
+function invalidateContextProvider(workInProgress, didChange) {
+  var instance = workInProgress.stateNode;
+  invariant(
+    instance,
+    "Expected to have an instance by this point. This error is likely caused by a bug in React. Please file an issue."
+  );
+  if (didChange) {
+    var mergedContext = processChildContext(workInProgress, previousContext);
+    instance.__reactInternalMemoizedMergedChildContext = mergedContext;
+    pop(didPerformWorkStackCursor, workInProgress);
+    pop(contextStackCursor, workInProgress);
+    push(contextStackCursor, mergedContext, workInProgress);
+  } else pop(didPerformWorkStackCursor, workInProgress);
+  push(didPerformWorkStackCursor, didChange, workInProgress);
+}
+function FiberNode(tag, pendingProps, key, mode) {
+  this.tag = tag;
+  this.key = key;
+  this.sibling = this.child = this.return = this.stateNode = this.type = null;
+  this.index = 0;
+  this.ref = null;
+  this.pendingProps = pendingProps;
+  this.memoizedState = this.updateQueue = this.memoizedProps = null;
+  this.mode = mode;
+  this.effectTag = 0;
+  this.lastEffect = this.firstEffect = this.nextEffect = null;
+  this.expirationTime = 0;
+  this.alternate = null;
+  this.treeBaseTime = this.selfBaseTime = this.actualStartTime = this.actualDuration = 0;
+}
+function createWorkInProgress(current, pendingProps, expirationTime) {
+  var workInProgress = current.alternate;
+  null === workInProgress
+    ? ((workInProgress = new FiberNode(
+        current.tag,
+        pendingProps,
+        current.key,
+        current.mode
+      )),
+      (workInProgress.type = current.type),
+      (workInProgress.stateNode = current.stateNode),
+      (workInProgress.alternate = current),
+      (current.alternate = workInProgress))
+    : ((workInProgress.pendingProps = pendingProps),
+      (workInProgress.effectTag = 0),
+      (workInProgress.nextEffect = null),
+      (workInProgress.firstEffect = null),
+      (workInProgress.lastEffect = null),
+      (workInProgress.actualDuration = 0),
+      (workInProgress.actualStartTime = 0));
+  workInProgress.expirationTime = expirationTime;
+  workInProgress.child = current.child;
+  workInProgress.memoizedProps = current.memoizedProps;
+  workInProgress.memoizedState = current.memoizedState;
+  workInProgress.updateQueue = current.updateQueue;
+  workInProgress.sibling = current.sibling;
+  workInProgress.index = current.index;
+  workInProgress.ref = current.ref;
+  workInProgress.selfBaseTime = current.selfBaseTime;
+  workInProgress.treeBaseTime = current.treeBaseTime;
+  return workInProgress;
+}
+function createFiberFromElement(element, mode, expirationTime) {
+  var type = element.type,
+    key = element.key;
+  element = element.props;
+  if ("function" === typeof type)
+    var fiberTag = type.prototype && type.prototype.isReactComponent ? 2 : 0;
+  else if ("string" === typeof type) fiberTag = 5;
+  else
+    switch (type) {
+      case REACT_FRAGMENT_TYPE:
+        return createFiberFromFragment(
+          element.children,
+          mode,
+          expirationTime,
+          key
+        );
+      case REACT_ASYNC_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 3;
+        break;
+      case REACT_STRICT_MODE_TYPE:
+        fiberTag = 11;
+        mode |= 2;
+        break;
+      case REACT_PROFILER_TYPE:
+        return (
+          (type = new FiberNode(15, element, key, mode | 4)),
+          (type.type = REACT_PROFILER_TYPE),
+          (type.expirationTime = expirationTime),
+          type
+        );
+      case REACT_TIMEOUT_TYPE:
+        fiberTag = 16;
+        mode |= 2;
+        break;
+      default:
+        a: {
+          switch ("object" === typeof type && null !== type
+            ? type.$$typeof
+            : null) {
+            case REACT_PROVIDER_TYPE:
+              fiberTag = 13;
+              break a;
+            case REACT_CONTEXT_TYPE:
+              fiberTag = 12;
+              break a;
+            case REACT_FORWARD_REF_TYPE:
+              fiberTag = 14;
+              break a;
+            default:
+              invariant(
+                !1,
+                "Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s",
+                null == type ? type : typeof type,
+                ""
+              );
+          }
+          fiberTag = void 0;
+        }
+    }
+  mode = new FiberNode(fiberTag, element, key, mode);
+  mode.type = type;
+  mode.expirationTime = expirationTime;
+  return mode;
+}
+function createFiberFromFragment(elements, mode, expirationTime, key) {
+  elements = new FiberNode(10, elements, key, mode);
+  elements.expirationTime = expirationTime;
+  return elements;
+}
+function createFiberFromText(content, mode, expirationTime) {
+  content = new FiberNode(6, content, null, mode);
+  content.expirationTime = expirationTime;
+  return content;
+}
+function createFiberFromPortal(portal, mode, expirationTime) {
+  mode = new FiberNode(
+    4,
+    null !== portal.children ? portal.children : [],
+    portal.key,
+    mode
+  );
+  mode.expirationTime = expirationTime;
+  mode.stateNode = {
+    containerInfo: portal.containerInfo,
+    pendingChildren: null,
+    implementation: portal.implementation
+  };
+  return mode;
+}
+function createFiberRoot(containerInfo, isAsync, hydrate) {
+  isAsync = new FiberNode(3, null, null, isAsync ? 3 : 0);
+  containerInfo = {
+    current: isAsync,
+    containerInfo: containerInfo,
+    pendingChildren: null,
+    earliestPendingTime: 0,
+    latestPendingTime: 0,
+    earliestSuspendedTime: 0,
+    latestSuspendedTime: 0,
+    latestPingedTime: 0,
+    didError: !1,
+    pendingCommitExpirationTime: 0,
+    finishedWork: null,
+    context: null,
+    pendingContext: null,
+    hydrate: hydrate,
+    nextExpirationTimeToWorkOn: 0,
+    expirationTime: 0,
+    firstBatch: null,
+    nextScheduledRoot: null
+  };
+  return (isAsync.stateNode = containerInfo);
+}
+var onCommitFiberRoot = null,
+  onCommitFiberUnmount = null;
+function catchErrors(fn) {
+  return function(arg) {
+    try {
+      return fn(arg);
+    } catch (err) {}
+  };
+}
+function injectInternals(internals) {
+  if ("undefined" === typeof __REACT_DEVTOOLS_GLOBAL_HOOK__) return !1;
+  var hook = __REACT_DEVTOOLS_GLOBAL_HOOK__;
+  if (hook.isDisabled || !hook.supportsFiber) return !0;
+  try {
+    var rendererID = hook.inject(internals);
+    onCommitFiberRoot = catchErrors(function(root) {
+      return hook.onCommitFiberRoot(rendererID, root);
+    });
+    onCommitFiberUnmount = catchErrors(function(fiber) {
+      return hook.onCommitFiberUnmount(rendererID, fiber);
+    });
+  } catch (err) {}
+  return !0;
+}
+function onCommitRoot(root) {
+  "function" === typeof onCommitFiberRoot && onCommitFiberRoot(root);
+}
+function onCommitUnmount(fiber) {
+  "function" === typeof onCommitFiberUnmount && onCommitFiberUnmount(fiber);
+}
+function markPendingPriorityLevel(root, expirationTime) {
+  root.didError = !1;
+  var earliestPendingTime = root.earliestPendingTime;
+  0 === earliestPendingTime
+    ? (root.earliestPendingTime = root.latestPendingTime = expirationTime)
+    : earliestPendingTime > expirationTime
+      ? (root.earliestPendingTime = expirationTime)
+      : root.latestPendingTime < expirationTime &&
+        (root.latestPendingTime = expirationTime);
+  findNextPendingPriorityLevel(root);
+}
+function findNextPendingPriorityLevel(root) {
+  var earliestSuspendedTime = root.earliestSuspendedTime,
+    earliestPendingTime = root.earliestPendingTime;
+  if (0 === earliestSuspendedTime)
+    var nextExpirationTimeToWorkOn = (earliestSuspendedTime = earliestPendingTime);
+  else
+    0 !== earliestPendingTime
+      ? ((nextExpirationTimeToWorkOn = earliestPendingTime),
+        (earliestSuspendedTime =
+          earliestSuspendedTime < earliestPendingTime
+            ? earliestSuspendedTime
+            : earliestPendingTime))
+      : (nextExpirationTimeToWorkOn = earliestSuspendedTime =
+          root.latestPingedTime);
+  root.didError && (earliestSuspendedTime = 1);
+  root.nextExpirationTimeToWorkOn = nextExpirationTimeToWorkOn;
+  root.expirationTime = earliestSuspendedTime;
+}
+var hasForceUpdate = !1;
+function createUpdateQueue(baseState) {
+  return {
+    expirationTime: 0,
+    baseState: baseState,
+    firstUpdate: null,
+    lastUpdate: null,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function cloneUpdateQueue(currentQueue) {
+  return {
+    expirationTime: currentQueue.expirationTime,
+    baseState: currentQueue.baseState,
+    firstUpdate: currentQueue.firstUpdate,
+    lastUpdate: currentQueue.lastUpdate,
+    firstCapturedUpdate: null,
+    lastCapturedUpdate: null,
+    firstEffect: null,
+    lastEffect: null,
+    firstCapturedEffect: null,
+    lastCapturedEffect: null
+  };
+}
+function createUpdate(expirationTime) {
+  return {
+    expirationTime: expirationTime,
+    tag: 0,
+    payload: null,
+    callback: null,
+    next: null,
+    nextEffect: null
+  };
+}
+function appendUpdateToQueue(queue, update, expirationTime) {
+  null === queue.lastUpdate
+    ? (queue.firstUpdate = queue.lastUpdate = update)
+    : ((queue.lastUpdate.next = update), (queue.lastUpdate = update));
+  if (0 === queue.expirationTime || queue.expirationTime > expirationTime)
+    queue.expirationTime = expirationTime;
+}
+function enqueueUpdate(fiber, update, expirationTime) {
+  var alternate = fiber.alternate;
+  if (null === alternate) {
+    var queue1 = fiber.updateQueue;
+    var queue2 = null;
+    null === queue1 &&
+      (queue1 = fiber.updateQueue = createUpdateQueue(fiber.memoizedState));
+  } else
+    (queue1 = fiber.updateQueue),
+      (queue2 = alternate.updateQueue),
+      null === queue1
+        ? null === queue2
+          ? ((queue1 = fiber.updateQueue = createUpdateQueue(
+              fiber.memoizedState
+            )),
+            (queue2 = alternate.updateQueue = createUpdateQueue(
+              alternate.memoizedState
+            )))
+          : (queue1 = fiber.updateQueue = cloneUpdateQueue(queue2))
+        : null === queue2 &&
+          (queue2 = alternate.updateQueue = cloneUpdateQueue(queue1));
+  null === queue2 || queue1 === queue2
+    ? appendUpdateToQueue(queue1, update, expirationTime)
+    : null === queue1.lastUpdate || null === queue2.lastUpdate
+      ? (appendUpdateToQueue(queue1, update, expirationTime),
+        appendUpdateToQueue(queue2, update, expirationTime))
+      : (appendUpdateToQueue(queue1, update, expirationTime),
+        (queue2.lastUpdate = update));
+}
+function enqueueCapturedUpdate(workInProgress, update, renderExpirationTime) {
+  var workInProgressQueue = workInProgress.updateQueue;
+  workInProgressQueue =
+    null === workInProgressQueue
+      ? (workInProgress.updateQueue = createUpdateQueue(
+          workInProgress.memoizedState
+        ))
+      : ensureWorkInProgressQueueIsAClone(workInProgress, workInProgressQueue);
+  null === workInProgressQueue.lastCapturedUpdate
+    ? (workInProgressQueue.firstCapturedUpdate = workInProgressQueue.lastCapturedUpdate = update)
+    : ((workInProgressQueue.lastCapturedUpdate.next = update),
+      (workInProgressQueue.lastCapturedUpdate = update));
+  if (
+    0 === workInProgressQueue.expirationTime ||
+    workInProgressQueue.expirationTime > renderExpirationTime
+  )
+    workInProgressQueue.expirationTime = renderExpirationTime;
+}
+function ensureWorkInProgressQueueIsAClone(workInProgress, queue) {
+  var current = workInProgress.alternate;
+  null !== current &&
+    queue === current.updateQueue &&
+    (queue = workInProgress.updateQueue = cloneUpdateQueue(queue));
+  return queue;
+}
+function getStateFromUpdate(
+  workInProgress,
+  queue,
+  update,
+  prevState,
+  nextProps,
+  instance
+) {
+  switch (update.tag) {
+    case 1:
+      return (
+        (workInProgress = update.payload),
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress
+      );
+    case 3:
+      workInProgress.effectTag = (workInProgress.effectTag & -1025) | 64;
+    case 0:
+      workInProgress = update.payload;
+      nextProps =
+        "function" === typeof workInProgress
+          ? workInProgress.call(instance, prevState, nextProps)
+          : workInProgress;
+      if (null === nextProps || void 0 === nextProps) break;
+      return Object.assign({}, prevState, nextProps);
+    case 2:
+      hasForceUpdate = !0;
+  }
+  return prevState;
+}
+function processUpdateQueue(
+  workInProgress,
+  queue,
+  props,
+  instance,
+  renderExpirationTime
+) {
+  hasForceUpdate = !1;
+  if (
+    !(0 === queue.expirationTime || queue.expirationTime > renderExpirationTime)
+  ) {
+    queue = ensureWorkInProgressQueueIsAClone(workInProgress, queue);
+    for (
+      var newBaseState = queue.baseState,
+        newFirstUpdate = null,
+        newExpirationTime = 0,
+        update = queue.firstUpdate,
+        resultState = newBaseState;
+      null !== update;
+
+    ) {
+      var updateExpirationTime = update.expirationTime;
+      if (updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === newFirstUpdate &&
+            ((newFirstUpdate = update), (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > updateExpirationTime)
+        )
+          newExpirationTime = updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
+          update,
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastEffect
+              ? (queue.firstEffect = queue.lastEffect = update)
+              : ((queue.lastEffect.nextEffect = update),
+                (queue.lastEffect = update)));
+      update = update.next;
+    }
+    updateExpirationTime = null;
+    for (update = queue.firstCapturedUpdate; null !== update; ) {
+      var _updateExpirationTime = update.expirationTime;
+      if (_updateExpirationTime > renderExpirationTime) {
+        if (
+          (null === updateExpirationTime &&
+            ((updateExpirationTime = update),
+            null === newFirstUpdate && (newBaseState = resultState)),
+          0 === newExpirationTime || newExpirationTime > _updateExpirationTime)
+        )
+          newExpirationTime = _updateExpirationTime;
+      } else
+        (resultState = getStateFromUpdate(
+          workInProgress,
+          queue,
+          update,
+          resultState,
+          props,
+          instance
+        )),
+          null !== update.callback &&
+            ((workInProgress.effectTag |= 32),
+            (update.nextEffect = null),
+            null === queue.lastCapturedEffect
+              ? (queue.firstCapturedEffect = queue.lastCapturedEffect = update)
+              : ((queue.lastCapturedEffect.nextEffect = update),
+                (queue.lastCapturedEffect = update)));
+      update = update.next;
+    }
+    null === newFirstUpdate && (queue.lastUpdate = null);
+    null === updateExpirationTime
+      ? (queue.lastCapturedUpdate = null)
+      : (workInProgress.effectTag |= 32);
+    null === newFirstUpdate &&
+      null === updateExpirationTime &&
+      (newBaseState = resultState);
+    queue.baseState = newBaseState;
+    queue.firstUpdate = newFirstUpdate;
+    queue.firstCapturedUpdate = updateExpirationTime;
+    queue.expirationTime = newExpirationTime;
+    workInProgress.memoizedState = resultState;
+  }
+}
+function callCallback(callback, context) {
+  invariant(
+    "function" === typeof callback,
+    "Invalid argument passed as callback. Expected a function. Instead received: %s",
+    callback
+  );
+  callback.call(context);
+}
+function commitUpdateQueue(finishedWork, finishedQueue, instance) {
+  null !== finishedQueue.firstCapturedUpdate &&
+    (null !== finishedQueue.lastUpdate &&
+      ((finishedQueue.lastUpdate.next = finishedQueue.firstCapturedUpdate),
+      (finishedQueue.lastUpdate = finishedQueue.lastCapturedUpdate)),
+    (finishedQueue.firstCapturedUpdate = finishedQueue.lastCapturedUpdate = null));
+  finishedWork = finishedQueue.firstEffect;
+  for (
+    finishedQueue.firstEffect = finishedQueue.lastEffect = null;
+    null !== finishedWork;
+
+  ) {
+    var _callback3 = finishedWork.callback;
+    null !== _callback3 &&
+      ((finishedWork.callback = null), callCallback(_callback3, instance));
+    finishedWork = finishedWork.nextEffect;
+  }
+  finishedWork = finishedQueue.firstCapturedEffect;
+  for (
+    finishedQueue.firstCapturedEffect = finishedQueue.lastCapturedEffect = null;
+    null !== finishedWork;
+
+  )
+    (finishedQueue = finishedWork.callback),
+      null !== finishedQueue &&
+        ((finishedWork.callback = null), callCallback(finishedQueue, instance)),
+      (finishedWork = finishedWork.nextEffect);
+}
+function createCapturedValue(value, source) {
+  return {
+    value: value,
+    source: source,
+    stack: getStackAddendumByWorkInProgressFiber(source)
+  };
+}
+var providerCursor = createCursor(null),
+  valueCursor = createCursor(null),
+  changedBitsCursor = createCursor(0);
+function pushProvider(providerFiber) {
+  var context = providerFiber.type._context;
+  push(changedBitsCursor, context._changedBits, providerFiber);
+  push(valueCursor, context._currentValue, providerFiber);
+  push(providerCursor, providerFiber, providerFiber);
+  context._currentValue = providerFiber.pendingProps.value;
+  context._changedBits = providerFiber.stateNode;
+}
+function popProvider(providerFiber) {
+  var changedBits = changedBitsCursor.current,
+    currentValue = valueCursor.current;
+  pop(providerCursor, providerFiber);
+  pop(valueCursor, providerFiber);
+  pop(changedBitsCursor, providerFiber);
+  providerFiber = providerFiber.type._context;
+  providerFiber._currentValue = currentValue;
+  providerFiber._changedBits = changedBits;
+}
+var NO_CONTEXT = {},
+  contextStackCursor$1 = createCursor(NO_CONTEXT),
+  contextFiberStackCursor = createCursor(NO_CONTEXT),
+  rootInstanceStackCursor = createCursor(NO_CONTEXT);
+function requiredContext(c) {
+  invariant(
+    c !== NO_CONTEXT,
+    "Expected host context to exist. This error is likely caused by a bug in React. Please file an issue."
+  );
+  return c;
+}
+function pushHostContainer(fiber, nextRootInstance) {
+  push(rootInstanceStackCursor, nextRootInstance, fiber);
+  push(contextFiberStackCursor, fiber, fiber);
+  push(contextStackCursor$1, NO_CONTEXT, fiber);
+  pop(contextStackCursor$1, fiber);
+  push(contextStackCursor$1, { isInAParentText: !1 }, fiber);
+}
+function popHostContainer(fiber) {
+  pop(contextStackCursor$1, fiber);
+  pop(contextFiberStackCursor, fiber);
+  pop(rootInstanceStackCursor, fiber);
+}
+function popHostContext(fiber) {
+  contextFiberStackCursor.current === fiber &&
+    (pop(contextStackCursor$1, fiber), pop(contextFiberStackCursor, fiber));
+}
+var commitTime = 0,
+  timerPausedAt = 0,
+  totalElapsedPauseTime = 0;
+function recordElapsedActualRenderTime(fiber) {
+  fiber.actualDuration = now$1() - totalElapsedPauseTime - fiber.actualDuration;
+}
+function resumeActualRenderTimerIfPaused() {
+  0 < timerPausedAt &&
+    ((totalElapsedPauseTime += now$1() - timerPausedAt), (timerPausedAt = 0));
+}
+var baseStartTime = -1,
+  hasOwnProperty = Object.prototype.hasOwnProperty;
+function is(x, y) {
+  return x === y ? 0 !== x || 0 !== y || 1 / x === 1 / y : x !== x && y !== y;
+}
+function shallowEqual(objA, objB) {
+  if (is(objA, objB)) return !0;
+  if (
+    "object" !== typeof objA ||
+    null === objA ||
+    "object" !== typeof objB ||
+    null === objB
+  )
+    return !1;
+  var keysA = Object.keys(objA),
+    keysB = Object.keys(objB);
+  if (keysA.length !== keysB.length) return !1;
+  for (keysB = 0; keysB < keysA.length; keysB++)
+    if (
+      !hasOwnProperty.call(objB, keysA[keysB]) ||
+      !is(objA[keysA[keysB]], objB[keysA[keysB]])
+    )
+      return !1;
+  return !0;
+}
+function applyDerivedStateFromProps(
+  workInProgress,
+  getDerivedStateFromProps,
+  nextProps
+) {
+  var prevState = workInProgress.memoizedState;
+  getDerivedStateFromProps = getDerivedStateFromProps(nextProps, prevState);
+  prevState =
+    null === getDerivedStateFromProps || void 0 === getDerivedStateFromProps
+      ? prevState
+      : Object.assign({}, prevState, getDerivedStateFromProps);
+  workInProgress.memoizedState = prevState;
+  workInProgress = workInProgress.updateQueue;
+  null !== workInProgress &&
+    0 === workInProgress.expirationTime &&
+    (workInProgress.baseState = prevState);
+}
+var classComponentUpdater = {
+  isMounted: function(component) {
+    return (component = component._reactInternalFiber)
+      ? 2 === isFiberMountedImpl(component)
+      : !1;
+  },
+  enqueueSetState: function(inst, payload, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.payload = payload;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  },
+  enqueueReplaceState: function(inst, payload, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.tag = 1;
+    update.payload = payload;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  },
+  enqueueForceUpdate: function(inst, callback) {
+    inst = inst._reactInternalFiber;
+    var currentTime = recalculateCurrentTime();
+    currentTime = computeExpirationForFiber(currentTime, inst);
+    var update = createUpdate(currentTime);
+    update.tag = 2;
+    void 0 !== callback && null !== callback && (update.callback = callback);
+    enqueueUpdate(inst, update, currentTime);
+    scheduleWork(inst, currentTime);
+  }
+};
+function checkShouldComponentUpdate(
+  workInProgress,
+  oldProps,
+  newProps,
+  oldState,
+  newState,
+  newContext
+) {
+  var instance = workInProgress.stateNode;
+  workInProgress = workInProgress.type;
+  return "function" === typeof instance.shouldComponentUpdate
+    ? instance.shouldComponentUpdate(newProps, newState, newContext)
+    : workInProgress.prototype && workInProgress.prototype.isPureReactComponent
+      ? !shallowEqual(oldProps, newProps) || !shallowEqual(oldState, newState)
+      : !0;
+}
+function callComponentWillReceiveProps(
+  workInProgress,
+  instance,
+  newProps,
+  newContext
+) {
+  workInProgress = instance.state;
+  "function" === typeof instance.componentWillReceiveProps &&
+    instance.componentWillReceiveProps(newProps, newContext);
+  "function" === typeof instance.UNSAFE_componentWillReceiveProps &&
+    instance.UNSAFE_componentWillReceiveProps(newProps, newContext);
+  instance.state !== workInProgress &&
+    classComponentUpdater.enqueueReplaceState(instance, instance.state, null);
+}
+function mountClassInstance(workInProgress, renderExpirationTime) {
+  var ctor = workInProgress.type,
+    instance = workInProgress.stateNode,
+    props = workInProgress.pendingProps,
+    unmaskedContext = getUnmaskedContext(workInProgress);
+  instance.props = props;
+  instance.state = workInProgress.memoizedState;
+  instance.refs = emptyObject;
+  instance.context = getMaskedContext(workInProgress, unmaskedContext);
+  unmaskedContext = workInProgress.updateQueue;
+  null !== unmaskedContext &&
+    (processUpdateQueue(
+      workInProgress,
+      unmaskedContext,
+      props,
+      instance,
+      renderExpirationTime
+    ),
+    (instance.state = workInProgress.memoizedState));
+  unmaskedContext = workInProgress.type.getDerivedStateFromProps;
+  "function" === typeof unmaskedContext &&
+    (applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+    (instance.state = workInProgress.memoizedState));
+  "function" === typeof ctor.getDerivedStateFromProps ||
+    "function" === typeof instance.getSnapshotBeforeUpdate ||
+    ("function" !== typeof instance.UNSAFE_componentWillMount &&
+      "function" !== typeof instance.componentWillMount) ||
+    ((ctor = instance.state),
+    "function" === typeof instance.componentWillMount &&
+      instance.componentWillMount(),
+    "function" === typeof instance.UNSAFE_componentWillMount &&
+      instance.UNSAFE_componentWillMount(),
+    ctor !== instance.state &&
+      classComponentUpdater.enqueueReplaceState(instance, instance.state, null),
+    (unmaskedContext = workInProgress.updateQueue),
+    null !== unmaskedContext &&
+      (processUpdateQueue(
+        workInProgress,
+        unmaskedContext,
+        props,
+        instance,
+        renderExpirationTime
+      ),
+      (instance.state = workInProgress.memoizedState)));
+  "function" === typeof instance.componentDidMount &&
+    (workInProgress.effectTag |= 4);
+}
+var isArray$1 = Array.isArray;
+function coerceRef(returnFiber, current, element) {
+  returnFiber = element.ref;
+  if (
+    null !== returnFiber &&
+    "function" !== typeof returnFiber &&
+    "object" !== typeof returnFiber
+  ) {
+    if (element._owner) {
+      element = element._owner;
+      var inst = void 0;
+      element &&
+        (invariant(
+          2 === element.tag,
+          "Stateless function components cannot have refs."
+        ),
+        (inst = element.stateNode));
+      invariant(
+        inst,
+        "Missing owner for string ref %s. This error is likely caused by a bug in React. Please file an issue.",
+        returnFiber
+      );
+      var stringRef = "" + returnFiber;
+      if (
+        null !== current &&
+        null !== current.ref &&
+        "function" === typeof current.ref &&
+        current.ref._stringRef === stringRef
+      )
+        return current.ref;
+      current = function(value) {
+        var refs = inst.refs === emptyObject ? (inst.refs = {}) : inst.refs;
+        null === value ? delete refs[stringRef] : (refs[stringRef] = value);
+      };
+      current._stringRef = stringRef;
+      return current;
+    }
+    invariant(
+      "string" === typeof returnFiber,
+      "Expected ref to be a function or a string."
+    );
+    invariant(
+      element._owner,
+      "Element ref was specified as a string (%s) but no owner was set. This could happen for one of the following reasons:\n1. You may be adding a ref to a functional component\n2. You may be adding a ref to a component that was not created inside a component's render method\n3. You have multiple copies of React loaded\nSee https://fb.me/react-refs-must-have-owner for more information.",
+      returnFiber
+    );
+  }
+  return returnFiber;
+}
+function throwOnInvalidObjectType(returnFiber, newChild) {
+  "textarea" !== returnFiber.type &&
+    invariant(
+      !1,
+      "Objects are not valid as a React child (found: %s).%s",
+      "[object Object]" === Object.prototype.toString.call(newChild)
+        ? "object with keys {" + Object.keys(newChild).join(", ") + "}"
+        : newChild,
+      ""
+    );
+}
+function ChildReconciler(shouldTrackSideEffects) {
+  function deleteChild(returnFiber, childToDelete) {
+    if (shouldTrackSideEffects) {
+      var last = returnFiber.lastEffect;
+      null !== last
+        ? ((last.nextEffect = childToDelete),
+          (returnFiber.lastEffect = childToDelete))
+        : (returnFiber.firstEffect = returnFiber.lastEffect = childToDelete);
+      childToDelete.nextEffect = null;
+      childToDelete.effectTag = 8;
+    }
+  }
+  function deleteRemainingChildren(returnFiber, currentFirstChild) {
+    if (!shouldTrackSideEffects) return null;
+    for (; null !== currentFirstChild; )
+      deleteChild(returnFiber, currentFirstChild),
+        (currentFirstChild = currentFirstChild.sibling);
+    return null;
+  }
+  function mapRemainingChildren(returnFiber, currentFirstChild) {
+    for (returnFiber = new Map(); null !== currentFirstChild; )
+      null !== currentFirstChild.key
+        ? returnFiber.set(currentFirstChild.key, currentFirstChild)
+        : returnFiber.set(currentFirstChild.index, currentFirstChild),
+        (currentFirstChild = currentFirstChild.sibling);
+    return returnFiber;
+  }
+  function useFiber(fiber, pendingProps, expirationTime) {
+    fiber = createWorkInProgress(fiber, pendingProps, expirationTime);
+    fiber.index = 0;
+    fiber.sibling = null;
+    return fiber;
+  }
+  function placeChild(newFiber, lastPlacedIndex, newIndex) {
+    newFiber.index = newIndex;
+    if (!shouldTrackSideEffects) return lastPlacedIndex;
+    newIndex = newFiber.alternate;
+    if (null !== newIndex)
+      return (
+        (newIndex = newIndex.index),
+        newIndex < lastPlacedIndex
+          ? ((newFiber.effectTag = 2), lastPlacedIndex)
+          : newIndex
+      );
+    newFiber.effectTag = 2;
+    return lastPlacedIndex;
+  }
+  function placeSingleChild(newFiber) {
+    shouldTrackSideEffects &&
+      null === newFiber.alternate &&
+      (newFiber.effectTag = 2);
+    return newFiber;
+  }
+  function updateTextNode(returnFiber, current, textContent, expirationTime) {
+    if (null === current || 6 !== current.tag)
+      return (
+        (current = createFiberFromText(
+          textContent,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (current.return = returnFiber),
+        current
+      );
+    current = useFiber(current, textContent, expirationTime);
+    current.return = returnFiber;
+    return current;
+  }
+  function updateElement(returnFiber, current, element, expirationTime) {
+    if (null !== current && current.type === element.type)
+      return (
+        (expirationTime = useFiber(current, element.props, expirationTime)),
+        (expirationTime.ref = coerceRef(returnFiber, current, element)),
+        (expirationTime.return = returnFiber),
+        expirationTime
+      );
+    expirationTime = createFiberFromElement(
+      element,
+      returnFiber.mode,
+      expirationTime
+    );
+    expirationTime.ref = coerceRef(returnFiber, current, element);
+    expirationTime.return = returnFiber;
+    return expirationTime;
+  }
+  function updatePortal(returnFiber, current, portal, expirationTime) {
+    if (
+      null === current ||
+      4 !== current.tag ||
+      current.stateNode.containerInfo !== portal.containerInfo ||
+      current.stateNode.implementation !== portal.implementation
+    )
+      return (
+        (current = createFiberFromPortal(
+          portal,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (current.return = returnFiber),
+        current
+      );
+    current = useFiber(current, portal.children || [], expirationTime);
+    current.return = returnFiber;
+    return current;
+  }
+  function updateFragment(returnFiber, current, fragment, expirationTime, key) {
+    if (null === current || 10 !== current.tag)
+      return (
+        (current = createFiberFromFragment(
+          fragment,
+          returnFiber.mode,
+          expirationTime,
+          key
+        )),
+        (current.return = returnFiber),
+        current
+      );
+    current = useFiber(current, fragment, expirationTime);
+    current.return = returnFiber;
+    return current;
+  }
+  function createChild(returnFiber, newChild, expirationTime) {
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (newChild = createFiberFromText(
+          "" + newChild,
+          returnFiber.mode,
+          expirationTime
+        )),
+        (newChild.return = returnFiber),
+        newChild
+      );
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return (
+            (expirationTime = createFiberFromElement(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (expirationTime.ref = coerceRef(returnFiber, null, newChild)),
+            (expirationTime.return = returnFiber),
+            expirationTime
+          );
+        case REACT_PORTAL_TYPE:
+          return (
+            (newChild = createFiberFromPortal(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (newChild.return = returnFiber),
+            newChild
+          );
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return (
+          (newChild = createFiberFromFragment(
+            newChild,
+            returnFiber.mode,
+            expirationTime,
+            null
+          )),
+          (newChild.return = returnFiber),
+          newChild
+        );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function updateSlot(returnFiber, oldFiber, newChild, expirationTime) {
+    var key = null !== oldFiber ? oldFiber.key : null;
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return null !== key
+        ? null
+        : updateTextNode(returnFiber, oldFiber, "" + newChild, expirationTime);
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return newChild.key === key
+            ? newChild.type === REACT_FRAGMENT_TYPE
+              ? updateFragment(
+                  returnFiber,
+                  oldFiber,
+                  newChild.props.children,
+                  expirationTime,
+                  key
+                )
+              : updateElement(returnFiber, oldFiber, newChild, expirationTime)
+            : null;
+        case REACT_PORTAL_TYPE:
+          return newChild.key === key
+            ? updatePortal(returnFiber, oldFiber, newChild, expirationTime)
+            : null;
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return null !== key
+          ? null
+          : updateFragment(
+              returnFiber,
+              oldFiber,
+              newChild,
+              expirationTime,
+              null
+            );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function updateFromMap(
+    existingChildren,
+    returnFiber,
+    newIdx,
+    newChild,
+    expirationTime
+  ) {
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (existingChildren = existingChildren.get(newIdx) || null),
+        updateTextNode(
+          returnFiber,
+          existingChildren,
+          "" + newChild,
+          expirationTime
+        )
+      );
+    if ("object" === typeof newChild && null !== newChild) {
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          return (
+            (existingChildren =
+              existingChildren.get(
+                null === newChild.key ? newIdx : newChild.key
+              ) || null),
+            newChild.type === REACT_FRAGMENT_TYPE
+              ? updateFragment(
+                  returnFiber,
+                  existingChildren,
+                  newChild.props.children,
+                  expirationTime,
+                  newChild.key
+                )
+              : updateElement(
+                  returnFiber,
+                  existingChildren,
+                  newChild,
+                  expirationTime
+                )
+          );
+        case REACT_PORTAL_TYPE:
+          return (
+            (existingChildren =
+              existingChildren.get(
+                null === newChild.key ? newIdx : newChild.key
+              ) || null),
+            updatePortal(
+              returnFiber,
+              existingChildren,
+              newChild,
+              expirationTime
+            )
+          );
+      }
+      if (isArray$1(newChild) || getIteratorFn(newChild))
+        return (
+          (existingChildren = existingChildren.get(newIdx) || null),
+          updateFragment(
+            returnFiber,
+            existingChildren,
+            newChild,
+            expirationTime,
+            null
+          )
+        );
+      throwOnInvalidObjectType(returnFiber, newChild);
+    }
+    return null;
+  }
+  function reconcileChildrenArray(
+    returnFiber,
+    currentFirstChild,
+    newChildren,
+    expirationTime
+  ) {
+    for (
+      var resultingFirstChild = null,
+        previousNewFiber = null,
+        oldFiber = currentFirstChild,
+        newIdx = (currentFirstChild = 0),
+        nextOldFiber = null;
+      null !== oldFiber && newIdx < newChildren.length;
+      newIdx++
+    ) {
+      oldFiber.index > newIdx
+        ? ((nextOldFiber = oldFiber), (oldFiber = null))
+        : (nextOldFiber = oldFiber.sibling);
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        newChildren[newIdx],
+        expirationTime
+      );
+      if (null === newFiber) {
+        null === oldFiber && (oldFiber = nextOldFiber);
+        break;
+      }
+      shouldTrackSideEffects &&
+        oldFiber &&
+        null === newFiber.alternate &&
+        deleteChild(returnFiber, oldFiber);
+      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
+      null === previousNewFiber
+        ? (resultingFirstChild = newFiber)
+        : (previousNewFiber.sibling = newFiber);
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+    if (newIdx === newChildren.length)
+      return (
+        deleteRemainingChildren(returnFiber, oldFiber), resultingFirstChild
+      );
+    if (null === oldFiber) {
+      for (; newIdx < newChildren.length; newIdx++)
+        if (
+          (oldFiber = createChild(
+            returnFiber,
+            newChildren[newIdx],
+            expirationTime
+          ))
+        )
+          (currentFirstChild = placeChild(oldFiber, currentFirstChild, newIdx)),
+            null === previousNewFiber
+              ? (resultingFirstChild = oldFiber)
+              : (previousNewFiber.sibling = oldFiber),
+            (previousNewFiber = oldFiber);
+      return resultingFirstChild;
+    }
+    for (
+      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
+      newIdx < newChildren.length;
+      newIdx++
+    )
+      if (
+        (nextOldFiber = updateFromMap(
+          oldFiber,
+          returnFiber,
+          newIdx,
+          newChildren[newIdx],
+          expirationTime
+        ))
+      )
+        shouldTrackSideEffects &&
+          null !== nextOldFiber.alternate &&
+          oldFiber.delete(
+            null === nextOldFiber.key ? newIdx : nextOldFiber.key
+          ),
+          (currentFirstChild = placeChild(
+            nextOldFiber,
+            currentFirstChild,
+            newIdx
+          )),
+          null === previousNewFiber
+            ? (resultingFirstChild = nextOldFiber)
+            : (previousNewFiber.sibling = nextOldFiber),
+          (previousNewFiber = nextOldFiber);
+    shouldTrackSideEffects &&
+      oldFiber.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    return resultingFirstChild;
+  }
+  function reconcileChildrenIterator(
+    returnFiber,
+    currentFirstChild,
+    newChildrenIterable,
+    expirationTime
+  ) {
+    var iteratorFn = getIteratorFn(newChildrenIterable);
+    invariant(
+      "function" === typeof iteratorFn,
+      "An object is not an iterable. This error is likely caused by a bug in React. Please file an issue."
+    );
+    newChildrenIterable = iteratorFn.call(newChildrenIterable);
+    invariant(
+      null != newChildrenIterable,
+      "An iterable object provided no iterator."
+    );
+    for (
+      var previousNewFiber = (iteratorFn = null),
+        oldFiber = currentFirstChild,
+        newIdx = (currentFirstChild = 0),
+        nextOldFiber = null,
+        step = newChildrenIterable.next();
+      null !== oldFiber && !step.done;
+      newIdx++, step = newChildrenIterable.next()
+    ) {
+      oldFiber.index > newIdx
+        ? ((nextOldFiber = oldFiber), (oldFiber = null))
+        : (nextOldFiber = oldFiber.sibling);
+      var newFiber = updateSlot(
+        returnFiber,
+        oldFiber,
+        step.value,
+        expirationTime
+      );
+      if (null === newFiber) {
+        oldFiber || (oldFiber = nextOldFiber);
+        break;
+      }
+      shouldTrackSideEffects &&
+        oldFiber &&
+        null === newFiber.alternate &&
+        deleteChild(returnFiber, oldFiber);
+      currentFirstChild = placeChild(newFiber, currentFirstChild, newIdx);
+      null === previousNewFiber
+        ? (iteratorFn = newFiber)
+        : (previousNewFiber.sibling = newFiber);
+      previousNewFiber = newFiber;
+      oldFiber = nextOldFiber;
+    }
+    if (step.done)
+      return deleteRemainingChildren(returnFiber, oldFiber), iteratorFn;
+    if (null === oldFiber) {
+      for (; !step.done; newIdx++, step = newChildrenIterable.next())
+        (step = createChild(returnFiber, step.value, expirationTime)),
+          null !== step &&
+            ((currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+            null === previousNewFiber
+              ? (iteratorFn = step)
+              : (previousNewFiber.sibling = step),
+            (previousNewFiber = step));
+      return iteratorFn;
+    }
+    for (
+      oldFiber = mapRemainingChildren(returnFiber, oldFiber);
+      !step.done;
+      newIdx++, step = newChildrenIterable.next()
+    )
+      (step = updateFromMap(
+        oldFiber,
+        returnFiber,
+        newIdx,
+        step.value,
+        expirationTime
+      )),
+        null !== step &&
+          (shouldTrackSideEffects &&
+            null !== step.alternate &&
+            oldFiber.delete(null === step.key ? newIdx : step.key),
+          (currentFirstChild = placeChild(step, currentFirstChild, newIdx)),
+          null === previousNewFiber
+            ? (iteratorFn = step)
+            : (previousNewFiber.sibling = step),
+          (previousNewFiber = step));
+    shouldTrackSideEffects &&
+      oldFiber.forEach(function(child) {
+        return deleteChild(returnFiber, child);
+      });
+    return iteratorFn;
+  }
+  return function(returnFiber, currentFirstChild, newChild, expirationTime) {
+    var isUnkeyedTopLevelFragment =
+      "object" === typeof newChild &&
+      null !== newChild &&
+      newChild.type === REACT_FRAGMENT_TYPE &&
+      null === newChild.key;
+    isUnkeyedTopLevelFragment && (newChild = newChild.props.children);
+    var isObject = "object" === typeof newChild && null !== newChild;
+    if (isObject)
+      switch (newChild.$$typeof) {
+        case REACT_ELEMENT_TYPE:
+          a: {
+            isObject = newChild.key;
+            for (
+              isUnkeyedTopLevelFragment = currentFirstChild;
+              null !== isUnkeyedTopLevelFragment;
+
+            ) {
+              if (isUnkeyedTopLevelFragment.key === isObject)
+                if (
+                  10 === isUnkeyedTopLevelFragment.tag
+                    ? newChild.type === REACT_FRAGMENT_TYPE
+                    : isUnkeyedTopLevelFragment.type === newChild.type
+                ) {
+                  deleteRemainingChildren(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment.sibling
+                  );
+                  currentFirstChild = useFiber(
+                    isUnkeyedTopLevelFragment,
+                    newChild.type === REACT_FRAGMENT_TYPE
+                      ? newChild.props.children
+                      : newChild.props,
+                    expirationTime
+                  );
+                  currentFirstChild.ref = coerceRef(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment,
+                    newChild
+                  );
+                  currentFirstChild.return = returnFiber;
+                  returnFiber = currentFirstChild;
+                  break a;
+                } else {
+                  deleteRemainingChildren(
+                    returnFiber,
+                    isUnkeyedTopLevelFragment
+                  );
+                  break;
+                }
+              else deleteChild(returnFiber, isUnkeyedTopLevelFragment);
+              isUnkeyedTopLevelFragment = isUnkeyedTopLevelFragment.sibling;
+            }
+            newChild.type === REACT_FRAGMENT_TYPE
+              ? ((currentFirstChild = createFiberFromFragment(
+                  newChild.props.children,
+                  returnFiber.mode,
+                  expirationTime,
+                  newChild.key
+                )),
+                (currentFirstChild.return = returnFiber),
+                (returnFiber = currentFirstChild))
+              : ((expirationTime = createFiberFromElement(
+                  newChild,
+                  returnFiber.mode,
+                  expirationTime
+                )),
+                (expirationTime.ref = coerceRef(
+                  returnFiber,
+                  currentFirstChild,
+                  newChild
+                )),
+                (expirationTime.return = returnFiber),
+                (returnFiber = expirationTime));
+          }
+          return placeSingleChild(returnFiber);
+        case REACT_PORTAL_TYPE:
+          a: {
+            for (
+              isUnkeyedTopLevelFragment = newChild.key;
+              null !== currentFirstChild;
+
+            ) {
+              if (currentFirstChild.key === isUnkeyedTopLevelFragment)
+                if (
+                  4 === currentFirstChild.tag &&
+                  currentFirstChild.stateNode.containerInfo ===
+                    newChild.containerInfo &&
+                  currentFirstChild.stateNode.implementation ===
+                    newChild.implementation
+                ) {
+                  deleteRemainingChildren(
+                    returnFiber,
+                    currentFirstChild.sibling
+                  );
+                  currentFirstChild = useFiber(
+                    currentFirstChild,
+                    newChild.children || [],
+                    expirationTime
+                  );
+                  currentFirstChild.return = returnFiber;
+                  returnFiber = currentFirstChild;
+                  break a;
+                } else {
+                  deleteRemainingChildren(returnFiber, currentFirstChild);
+                  break;
+                }
+              else deleteChild(returnFiber, currentFirstChild);
+              currentFirstChild = currentFirstChild.sibling;
+            }
+            currentFirstChild = createFiberFromPortal(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            );
+            currentFirstChild.return = returnFiber;
+            returnFiber = currentFirstChild;
+          }
+          return placeSingleChild(returnFiber);
+      }
+    if ("string" === typeof newChild || "number" === typeof newChild)
+      return (
+        (newChild = "" + newChild),
+        null !== currentFirstChild && 6 === currentFirstChild.tag
+          ? (deleteRemainingChildren(returnFiber, currentFirstChild.sibling),
+            (currentFirstChild = useFiber(
+              currentFirstChild,
+              newChild,
+              expirationTime
+            )),
+            (currentFirstChild.return = returnFiber),
+            (returnFiber = currentFirstChild))
+          : (deleteRemainingChildren(returnFiber, currentFirstChild),
+            (currentFirstChild = createFiberFromText(
+              newChild,
+              returnFiber.mode,
+              expirationTime
+            )),
+            (currentFirstChild.return = returnFiber),
+            (returnFiber = currentFirstChild)),
+        placeSingleChild(returnFiber)
+      );
+    if (isArray$1(newChild))
+      return reconcileChildrenArray(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    if (getIteratorFn(newChild))
+      return reconcileChildrenIterator(
+        returnFiber,
+        currentFirstChild,
+        newChild,
+        expirationTime
+      );
+    isObject && throwOnInvalidObjectType(returnFiber, newChild);
+    if ("undefined" === typeof newChild && !isUnkeyedTopLevelFragment)
+      switch (returnFiber.tag) {
+        case 2:
+        case 1:
+          (expirationTime = returnFiber.type),
+            invariant(
+              !1,
+              "%s(...): Nothing was returned from render. This usually means a return statement is missing. Or, to render nothing, return null.",
+              expirationTime.displayName || expirationTime.name || "Component"
+            );
+      }
+    return deleteRemainingChildren(returnFiber, currentFirstChild);
+  };
+}
+var reconcileChildFibers = ChildReconciler(!0),
+  mountChildFibers = ChildReconciler(!1),
+  hydrationParentFiber = null,
+  nextHydratableInstance = null,
+  isHydrating = !1;
+function tryHydrate(fiber, nextInstance) {
+  switch (fiber.tag) {
+    case 5:
+      return (
+        (nextInstance = shim$1(nextInstance, fiber.type, fiber.pendingProps)),
+        null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+      );
+    case 6:
+      return (
+        (nextInstance = shim$1(nextInstance, fiber.pendingProps)),
+        null !== nextInstance ? ((fiber.stateNode = nextInstance), !0) : !1
+      );
+    default:
+      return !1;
+  }
+}
+function tryToClaimNextHydratableInstance(fiber$jscomp$0) {
+  if (isHydrating) {
+    var nextInstance = nextHydratableInstance;
+    if (nextInstance) {
+      var firstAttemptedInstance = nextInstance;
+      if (!tryHydrate(fiber$jscomp$0, nextInstance)) {
+        nextInstance = shim$1(firstAttemptedInstance);
+        if (!nextInstance || !tryHydrate(fiber$jscomp$0, nextInstance)) {
+          fiber$jscomp$0.effectTag |= 2;
+          isHydrating = !1;
+          hydrationParentFiber = fiber$jscomp$0;
+          return;
+        }
+        var returnFiber = hydrationParentFiber,
+          fiber = new FiberNode(5, null, null, 0);
+        fiber.type = "DELETED";
+        fiber.stateNode = firstAttemptedInstance;
+        fiber.return = returnFiber;
+        fiber.effectTag = 8;
+        null !== returnFiber.lastEffect
+          ? ((returnFiber.lastEffect.nextEffect = fiber),
+            (returnFiber.lastEffect = fiber))
+          : (returnFiber.firstEffect = returnFiber.lastEffect = fiber);
+      }
+      hydrationParentFiber = fiber$jscomp$0;
+      nextHydratableInstance = shim$1(nextInstance);
+    } else
+      (fiber$jscomp$0.effectTag |= 2),
+        (isHydrating = !1),
+        (hydrationParentFiber = fiber$jscomp$0);
+  }
+}
+function reconcileChildren(current, workInProgress, nextChildren) {
+  reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    workInProgress.expirationTime
+  );
+}
+function reconcileChildrenAtExpirationTime(
+  current,
+  workInProgress,
+  nextChildren,
+  renderExpirationTime
+) {
+  workInProgress.child =
+    null === current
+      ? mountChildFibers(
+          workInProgress,
+          null,
+          nextChildren,
+          renderExpirationTime
+        )
+      : reconcileChildFibers(
+          workInProgress,
+          current.child,
+          nextChildren,
+          renderExpirationTime
+        );
+}
+function markRef(current, workInProgress) {
+  var ref = workInProgress.ref;
+  if (
+    (null === current && null !== ref) ||
+    (null !== current && current.ref !== ref)
+  )
+    workInProgress.effectTag |= 128;
+}
+function finishClassComponent(
+  current,
+  workInProgress,
+  shouldUpdate,
+  hasContext,
+  renderExpirationTime
+) {
+  markRef(current, workInProgress);
+  var didCaptureError = 0 !== (workInProgress.effectTag & 64);
+  if (!shouldUpdate && !didCaptureError)
+    return (
+      hasContext && invalidateContextProvider(workInProgress, !1),
+      bailoutOnAlreadyFinishedWork(current, workInProgress)
+    );
+  shouldUpdate = workInProgress.stateNode;
+  ReactCurrentOwner.current = workInProgress;
+  if (didCaptureError) {
+    var nextChildren = null;
+    baseStartTime = -1;
+  } else nextChildren = shouldUpdate.render();
+  workInProgress.effectTag |= 1;
+  didCaptureError &&
+    (reconcileChildrenAtExpirationTime(
+      current,
+      workInProgress,
+      null,
+      renderExpirationTime
+    ),
+    (workInProgress.child = null));
+  reconcileChildrenAtExpirationTime(
+    current,
+    workInProgress,
+    nextChildren,
+    renderExpirationTime
+  );
+  workInProgress.memoizedState = shouldUpdate.state;
+  workInProgress.memoizedProps = shouldUpdate.props;
+  hasContext && invalidateContextProvider(workInProgress, !0);
+  return workInProgress.child;
+}
+function pushHostRootContext(workInProgress) {
+  var root = workInProgress.stateNode;
+  root.pendingContext
+    ? pushTopLevelContextObject(
+        workInProgress,
+        root.pendingContext,
+        root.pendingContext !== root.context
+      )
+    : root.context &&
+      pushTopLevelContextObject(workInProgress, root.context, !1);
+  pushHostContainer(workInProgress, root.containerInfo);
+}
+function propagateContextChange(
+  workInProgress,
+  context,
+  changedBits,
+  renderExpirationTime
+) {
+  var fiber = workInProgress.child;
+  null !== fiber && (fiber.return = workInProgress);
+  for (; null !== fiber; ) {
+    switch (fiber.tag) {
+      case 12:
+        var nextFiber = fiber.stateNode | 0;
+        if (fiber.type === context && 0 !== (nextFiber & changedBits)) {
+          for (nextFiber = fiber; null !== nextFiber; ) {
+            var alternate = nextFiber.alternate;
+            if (
+              0 === nextFiber.expirationTime ||
+              nextFiber.expirationTime > renderExpirationTime
+            )
+              (nextFiber.expirationTime = renderExpirationTime),
+                null !== alternate &&
+                  (0 === alternate.expirationTime ||
+                    alternate.expirationTime > renderExpirationTime) &&
+                  (alternate.expirationTime = renderExpirationTime);
+            else if (
+              null !== alternate &&
+              (0 === alternate.expirationTime ||
+                alternate.expirationTime > renderExpirationTime)
+            )
+              alternate.expirationTime = renderExpirationTime;
+            else break;
+            nextFiber = nextFiber.return;
+          }
+          nextFiber = null;
+        } else nextFiber = fiber.child;
+        break;
+      case 13:
+        nextFiber = fiber.type === workInProgress.type ? null : fiber.child;
+        break;
+      default:
+        nextFiber = fiber.child;
+    }
+    if (null !== nextFiber) nextFiber.return = fiber;
+    else
+      for (nextFiber = fiber; null !== nextFiber; ) {
+        if (nextFiber === workInProgress) {
+          nextFiber = null;
+          break;
+        }
+        fiber = nextFiber.sibling;
+        if (null !== fiber) {
+          fiber.return = nextFiber.return;
+          nextFiber = fiber;
+          break;
+        }
+        nextFiber = nextFiber.return;
+      }
+    fiber = nextFiber;
+  }
+}
+function updateContextProvider(current, workInProgress, renderExpirationTime) {
+  var context = workInProgress.type._context,
+    newProps = workInProgress.pendingProps,
+    oldProps = workInProgress.memoizedProps,
+    canBailOnProps = !0;
+  if (didPerformWorkStackCursor.current) canBailOnProps = !1;
+  else if (oldProps === newProps)
+    return (
+      (workInProgress.stateNode = 0),
+      pushProvider(workInProgress),
+      bailoutOnAlreadyFinishedWork(current, workInProgress)
+    );
+  var newValue = newProps.value;
+  workInProgress.memoizedProps = newProps;
+  if (null === oldProps) newValue = 1073741823;
+  else if (oldProps.value === newProps.value) {
+    if (oldProps.children === newProps.children && canBailOnProps)
+      return (
+        (workInProgress.stateNode = 0),
+        pushProvider(workInProgress),
+        bailoutOnAlreadyFinishedWork(current, workInProgress)
+      );
+    newValue = 0;
+  } else {
+    var oldValue = oldProps.value;
+    if (
+      (oldValue === newValue &&
+        (0 !== oldValue || 1 / oldValue === 1 / newValue)) ||
+      (oldValue !== oldValue && newValue !== newValue)
+    ) {
+      if (oldProps.children === newProps.children && canBailOnProps)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+      newValue = 0;
+    } else if (
+      ((newValue =
+        "function" === typeof context._calculateChangedBits
+          ? context._calculateChangedBits(oldValue, newValue)
+          : 1073741823),
+      (newValue |= 0),
+      0 === newValue)
+    ) {
+      if (oldProps.children === newProps.children && canBailOnProps)
+        return (
+          (workInProgress.stateNode = 0),
+          pushProvider(workInProgress),
+          bailoutOnAlreadyFinishedWork(current, workInProgress)
+        );
+    } else
+      propagateContextChange(
+        workInProgress,
+        context,
+        newValue,
+        renderExpirationTime
+      );
+  }
+  workInProgress.stateNode = newValue;
+  pushProvider(workInProgress);
+  reconcileChildren(current, workInProgress, newProps.children);
+  return workInProgress.child;
+}
+function bailoutOnAlreadyFinishedWork(current, workInProgress) {
+  baseStartTime = -1;
+  invariant(
+    null === current || workInProgress.child === current.child,
+    "Resuming work not yet implemented."
+  );
+  if (null !== workInProgress.child) {
+    current = workInProgress.child;
+    var newChild = createWorkInProgress(
+      current,
+      current.pendingProps,
+      current.expirationTime
+    );
+    workInProgress.child = newChild;
+    for (newChild.return = workInProgress; null !== current.sibling; )
+      (current = current.sibling),
+        (newChild = newChild.sibling = createWorkInProgress(
+          current,
+          current.pendingProps,
+          current.expirationTime
+        )),
+        (newChild.return = workInProgress);
+    newChild.sibling = null;
+  }
+  return workInProgress.child;
+}
+function beginWork(current, workInProgress, renderExpirationTime) {
+  workInProgress.mode & 4 &&
+    ((workInProgress.actualDuration =
+      now$1() - workInProgress.actualDuration - totalElapsedPauseTime),
+    (workInProgress.actualStartTime = now$1()));
+  if (
+    0 === workInProgress.expirationTime ||
+    workInProgress.expirationTime > renderExpirationTime
+  ) {
+    baseStartTime = -1;
+    switch (workInProgress.tag) {
+      case 3:
+        pushHostRootContext(workInProgress);
+        break;
+      case 2:
+        pushContextProvider(workInProgress);
+        break;
+      case 4:
+        pushHostContainer(
+          workInProgress,
+          workInProgress.stateNode.containerInfo
+        );
+        break;
+      case 13:
+        pushProvider(workInProgress);
+    }
+    return null;
+  }
+  switch (workInProgress.tag) {
+    case 0:
+      invariant(
+        null === current,
+        "An indeterminate component should never have mounted. This error is likely caused by a bug in React. Please file an issue."
+      );
+      var fn = workInProgress.type,
+        props = workInProgress.pendingProps,
+        unmaskedContext = getUnmaskedContext(workInProgress);
+      unmaskedContext = getMaskedContext(workInProgress, unmaskedContext);
+      fn = fn(props, unmaskedContext);
+      workInProgress.effectTag |= 1;
+      "object" === typeof fn &&
+      null !== fn &&
+      "function" === typeof fn.render &&
+      void 0 === fn.$$typeof
+        ? ((unmaskedContext = workInProgress.type),
+          (workInProgress.tag = 2),
+          (workInProgress.memoizedState =
+            null !== fn.state && void 0 !== fn.state ? fn.state : null),
+          (unmaskedContext = unmaskedContext.getDerivedStateFromProps),
+          "function" === typeof unmaskedContext &&
+            applyDerivedStateFromProps(workInProgress, unmaskedContext, props),
+          (props = pushContextProvider(workInProgress)),
+          (fn.updater = classComponentUpdater),
+          (workInProgress.stateNode = fn),
+          (fn._reactInternalFiber = workInProgress),
+          mountClassInstance(workInProgress, renderExpirationTime),
+          (current = finishClassComponent(
+            current,
+            workInProgress,
+            !0,
+            props,
+            renderExpirationTime
+          )))
+        : ((workInProgress.tag = 1),
+          reconcileChildren(current, workInProgress, fn),
+          (workInProgress.memoizedProps = props),
+          (current = workInProgress.child));
+      return current;
+    case 1:
+      return (
+        (props = workInProgress.type),
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime
+          ? ((fn = getUnmaskedContext(workInProgress)),
+            (fn = getMaskedContext(workInProgress, fn)),
+            (props = props(renderExpirationTime, fn)),
+            (workInProgress.effectTag |= 1),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 2:
+      props = pushContextProvider(workInProgress);
+      if (null === current)
+        if (null === workInProgress.stateNode) {
+          var props$jscomp$0 = workInProgress.pendingProps,
+            ctor = workInProgress.type;
+          fn = getUnmaskedContext(workInProgress);
+          var needsContext =
+            2 === workInProgress.tag &&
+            null != workInProgress.type.contextTypes;
+          unmaskedContext = needsContext
+            ? getMaskedContext(workInProgress, fn)
+            : emptyObject;
+          props$jscomp$0 = new ctor(props$jscomp$0, unmaskedContext);
+          workInProgress.memoizedState =
+            null !== props$jscomp$0.state && void 0 !== props$jscomp$0.state
+              ? props$jscomp$0.state
+              : null;
+          props$jscomp$0.updater = classComponentUpdater;
+          workInProgress.stateNode = props$jscomp$0;
+          props$jscomp$0._reactInternalFiber = workInProgress;
+          needsContext &&
+            ((needsContext = workInProgress.stateNode),
+            (needsContext.__reactInternalMemoizedUnmaskedChildContext = fn),
+            (needsContext.__reactInternalMemoizedMaskedChildContext = unmaskedContext));
+          mountClassInstance(workInProgress, renderExpirationTime);
+          fn = !0;
+        } else {
+          ctor = workInProgress.type;
+          fn = workInProgress.stateNode;
+          needsContext = workInProgress.memoizedProps;
+          unmaskedContext = workInProgress.pendingProps;
+          fn.props = needsContext;
+          var oldContext = fn.context;
+          props$jscomp$0 = getUnmaskedContext(workInProgress);
+          props$jscomp$0 = getMaskedContext(workInProgress, props$jscomp$0);
+          var getDerivedStateFromProps = ctor.getDerivedStateFromProps;
+          (ctor =
+            "function" === typeof getDerivedStateFromProps ||
+            "function" === typeof fn.getSnapshotBeforeUpdate) ||
+            ("function" !== typeof fn.UNSAFE_componentWillReceiveProps &&
+              "function" !== typeof fn.componentWillReceiveProps) ||
+            ((needsContext !== unmaskedContext ||
+              oldContext !== props$jscomp$0) &&
+              callComponentWillReceiveProps(
+                workInProgress,
+                fn,
+                unmaskedContext,
+                props$jscomp$0
+              ));
+          hasForceUpdate = !1;
+          var oldState = workInProgress.memoizedState;
+          oldContext = fn.state = oldState;
+          var updateQueue = workInProgress.updateQueue;
+          null !== updateQueue &&
+            (processUpdateQueue(
+              workInProgress,
+              updateQueue,
+              unmaskedContext,
+              fn,
+              renderExpirationTime
+            ),
+            (oldContext = workInProgress.memoizedState));
+          needsContext !== unmaskedContext ||
+          oldState !== oldContext ||
+          didPerformWorkStackCursor.current ||
+          hasForceUpdate
+            ? ("function" === typeof getDerivedStateFromProps &&
+                (applyDerivedStateFromProps(
+                  workInProgress,
+                  getDerivedStateFromProps,
+                  unmaskedContext
+                ),
+                (oldContext = workInProgress.memoizedState)),
+              (needsContext =
+                hasForceUpdate ||
+                checkShouldComponentUpdate(
+                  workInProgress,
+                  needsContext,
+                  unmaskedContext,
+                  oldState,
+                  oldContext,
+                  props$jscomp$0
+                ))
+                ? (ctor ||
+                    ("function" !== typeof fn.UNSAFE_componentWillMount &&
+                      "function" !== typeof fn.componentWillMount) ||
+                    ("function" === typeof fn.componentWillMount &&
+                      fn.componentWillMount(),
+                    "function" === typeof fn.UNSAFE_componentWillMount &&
+                      fn.UNSAFE_componentWillMount()),
+                  "function" === typeof fn.componentDidMount &&
+                    (workInProgress.effectTag |= 4))
+                : ("function" === typeof fn.componentDidMount &&
+                    (workInProgress.effectTag |= 4),
+                  (workInProgress.memoizedProps = unmaskedContext),
+                  (workInProgress.memoizedState = oldContext)),
+              (fn.props = unmaskedContext),
+              (fn.state = oldContext),
+              (fn.context = props$jscomp$0),
+              (fn = needsContext))
+            : ("function" === typeof fn.componentDidMount &&
+                (workInProgress.effectTag |= 4),
+              (fn = !1));
+        }
+      else
+        (ctor = workInProgress.type),
+          (fn = workInProgress.stateNode),
+          (unmaskedContext = workInProgress.memoizedProps),
+          (needsContext = workInProgress.pendingProps),
+          (fn.props = unmaskedContext),
+          (oldContext = fn.context),
+          (props$jscomp$0 = getUnmaskedContext(workInProgress)),
+          (props$jscomp$0 = getMaskedContext(workInProgress, props$jscomp$0)),
+          (getDerivedStateFromProps = ctor.getDerivedStateFromProps),
+          (ctor =
+            "function" === typeof getDerivedStateFromProps ||
+            "function" === typeof fn.getSnapshotBeforeUpdate) ||
+            ("function" !== typeof fn.UNSAFE_componentWillReceiveProps &&
+              "function" !== typeof fn.componentWillReceiveProps) ||
+            ((unmaskedContext !== needsContext ||
+              oldContext !== props$jscomp$0) &&
+              callComponentWillReceiveProps(
+                workInProgress,
+                fn,
+                needsContext,
+                props$jscomp$0
+              )),
+          (hasForceUpdate = !1),
+          (oldContext = workInProgress.memoizedState),
+          (oldState = fn.state = oldContext),
+          (updateQueue = workInProgress.updateQueue),
+          null !== updateQueue &&
+            (processUpdateQueue(
+              workInProgress,
+              updateQueue,
+              needsContext,
+              fn,
+              renderExpirationTime
+            ),
+            (oldState = workInProgress.memoizedState)),
+          unmaskedContext !== needsContext ||
+          oldContext !== oldState ||
+          didPerformWorkStackCursor.current ||
+          hasForceUpdate
+            ? ("function" === typeof getDerivedStateFromProps &&
+                (applyDerivedStateFromProps(
+                  workInProgress,
+                  getDerivedStateFromProps,
+                  needsContext
+                ),
+                (oldState = workInProgress.memoizedState)),
+              (getDerivedStateFromProps =
+                hasForceUpdate ||
+                checkShouldComponentUpdate(
+                  workInProgress,
+                  unmaskedContext,
+                  needsContext,
+                  oldContext,
+                  oldState,
+                  props$jscomp$0
+                ))
+                ? (ctor ||
+                    ("function" !== typeof fn.UNSAFE_componentWillUpdate &&
+                      "function" !== typeof fn.componentWillUpdate) ||
+                    ("function" === typeof fn.componentWillUpdate &&
+                      fn.componentWillUpdate(
+                        needsContext,
+                        oldState,
+                        props$jscomp$0
+                      ),
+                    "function" === typeof fn.UNSAFE_componentWillUpdate &&
+                      fn.UNSAFE_componentWillUpdate(
+                        needsContext,
+                        oldState,
+                        props$jscomp$0
+                      )),
+                  "function" === typeof fn.componentDidUpdate &&
+                    (workInProgress.effectTag |= 4),
+                  "function" === typeof fn.getSnapshotBeforeUpdate &&
+                    (workInProgress.effectTag |= 256))
+                : ("function" !== typeof fn.componentDidUpdate ||
+                    (unmaskedContext === current.memoizedProps &&
+                      oldContext === current.memoizedState) ||
+                    (workInProgress.effectTag |= 4),
+                  "function" !== typeof fn.getSnapshotBeforeUpdate ||
+                    (unmaskedContext === current.memoizedProps &&
+                      oldContext === current.memoizedState) ||
+                    (workInProgress.effectTag |= 256),
+                  (workInProgress.memoizedProps = needsContext),
+                  (workInProgress.memoizedState = oldState)),
+              (fn.props = needsContext),
+              (fn.state = oldState),
+              (fn.context = props$jscomp$0),
+              (fn = getDerivedStateFromProps))
+            : ("function" !== typeof fn.componentDidUpdate ||
+                (unmaskedContext === current.memoizedProps &&
+                  oldContext === current.memoizedState) ||
+                (workInProgress.effectTag |= 4),
+              "function" !== typeof fn.getSnapshotBeforeUpdate ||
+                (unmaskedContext === current.memoizedProps &&
+                  oldContext === current.memoizedState) ||
+                (workInProgress.effectTag |= 256),
+              (fn = !1));
+      return finishClassComponent(
+        current,
+        workInProgress,
+        fn,
+        props,
+        renderExpirationTime
+      );
+    case 3:
+      return (
+        pushHostRootContext(workInProgress),
+        (props = workInProgress.updateQueue),
+        null !== props
+          ? ((fn = workInProgress.memoizedState),
+            (fn = null !== fn ? fn.element : null),
+            processUpdateQueue(
+              workInProgress,
+              props,
+              workInProgress.pendingProps,
+              null,
+              renderExpirationTime
+            ),
+            (renderExpirationTime = workInProgress.memoizedState.element),
+            renderExpirationTime === fn
+              ? (current = bailoutOnAlreadyFinishedWork(
+                  current,
+                  workInProgress
+                ))
+              : (reconcileChildren(
+                  current,
+                  workInProgress,
+                  renderExpirationTime
+                ),
+                (current = workInProgress.child)))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 5:
+      return (
+        requiredContext(rootInstanceStackCursor.current),
+        (renderExpirationTime = requiredContext(contextStackCursor$1.current)),
+        (props = workInProgress.type),
+        (props =
+          "AndroidTextInput" === props ||
+          "RCTMultilineTextInputView" === props ||
+          "RCTSinglelineTextInputView" === props ||
+          "RCTText" === props ||
+          "RCTVirtualText" === props),
+        (props =
+          renderExpirationTime.isInAParentText !== props
+            ? { isInAParentText: props }
+            : renderExpirationTime),
+        renderExpirationTime !== props &&
+          (push(contextFiberStackCursor, workInProgress, workInProgress),
+          push(contextStackCursor$1, props, workInProgress)),
+        null === current && tryToClaimNextHydratableInstance(workInProgress),
+        (props = workInProgress.memoizedProps),
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current || props !== renderExpirationTime
+          ? ((props = renderExpirationTime.children),
+            markRef(current, workInProgress),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 6:
+      return (
+        null === current && tryToClaimNextHydratableInstance(workInProgress),
+        (workInProgress.memoizedProps = workInProgress.pendingProps),
+        null
+      );
+    case 16:
+      return null;
+    case 4:
+      return (
+        pushHostContainer(
+          workInProgress,
+          workInProgress.stateNode.containerInfo
+        ),
+        (props = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== props
+          ? (null === current
+              ? (workInProgress.child = reconcileChildFibers(
+                  workInProgress,
+                  null,
+                  props,
+                  renderExpirationTime
+                ))
+              : reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = props),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 14:
+      return (
+        (props = workInProgress.type.render),
+        (renderExpirationTime = workInProgress.pendingProps),
+        (fn = workInProgress.ref),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime ||
+        fn !== (null !== current ? current.ref : null)
+          ? ((props = props(renderExpirationTime, fn)),
+            reconcileChildren(current, workInProgress, props),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 10:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps),
+        didPerformWorkStackCursor.current ||
+        workInProgress.memoizedProps !== renderExpirationTime
+          ? (reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 11:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps.children),
+        didPerformWorkStackCursor.current ||
+        (null !== renderExpirationTime &&
+          workInProgress.memoizedProps !== renderExpirationTime)
+          ? (reconcileChildren(current, workInProgress, renderExpirationTime),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child))
+          : (current = bailoutOnAlreadyFinishedWork(current, workInProgress)),
+        current
+      );
+    case 15:
+      return (
+        (renderExpirationTime = workInProgress.pendingProps),
+        (workInProgress.effectTag |= 4),
+        workInProgress.memoizedProps === renderExpirationTime
+          ? (current = bailoutOnAlreadyFinishedWork(current, workInProgress))
+          : (reconcileChildren(
+              current,
+              workInProgress,
+              renderExpirationTime.children
+            ),
+            (workInProgress.memoizedProps = renderExpirationTime),
+            (current = workInProgress.child)),
+        current
+      );
+    case 13:
+      return updateContextProvider(
+        current,
+        workInProgress,
+        renderExpirationTime
+      );
+    case 12:
+      a: if (
+        ((fn = workInProgress.type),
+        (unmaskedContext = workInProgress.pendingProps),
+        (needsContext = workInProgress.memoizedProps),
+        (props = fn._currentValue),
+        (props$jscomp$0 = fn._changedBits),
+        didPerformWorkStackCursor.current ||
+          0 !== props$jscomp$0 ||
+          needsContext !== unmaskedContext)
+      ) {
+        workInProgress.memoizedProps = unmaskedContext;
+        ctor = unmaskedContext.unstable_observedBits;
+        if (void 0 === ctor || null === ctor) ctor = 1073741823;
+        workInProgress.stateNode = ctor;
+        if (0 !== (props$jscomp$0 & ctor))
+          propagateContextChange(
+            workInProgress,
+            fn,
+            props$jscomp$0,
+            renderExpirationTime
+          );
+        else if (needsContext === unmaskedContext) {
+          current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+          break a;
+        }
+        renderExpirationTime = unmaskedContext.children;
+        renderExpirationTime = renderExpirationTime(props);
+        workInProgress.effectTag |= 1;
+        reconcileChildren(current, workInProgress, renderExpirationTime);
+        current = workInProgress.child;
+      } else current = bailoutOnAlreadyFinishedWork(current, workInProgress);
+      return current;
+    default:
+      invariant(
+        !1,
+        "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
+}
+var updateHostContainer = void 0,
+  updateHostComponent$1 = void 0,
+  updateHostText$1 = void 0;
+updateHostContainer = function() {};
+updateHostComponent$1 = function(current, workInProgress, updatePayload) {
+  if ((workInProgress.updateQueue = updatePayload))
+    workInProgress.effectTag |= 4;
+};
+updateHostText$1 = function(current, workInProgress, oldText, newText) {
+  oldText !== newText && (workInProgress.effectTag |= 4);
+};
+function completeWork(current, workInProgress) {
+  var newProps = workInProgress.pendingProps;
+  workInProgress.mode & 4 && recordElapsedActualRenderTime(workInProgress);
+  switch (workInProgress.tag) {
+    case 1:
+      return null;
+    case 2:
+      return popContextProvider(workInProgress), null;
+    case 3:
+      popHostContainer(workInProgress);
+      popTopLevelContextObject(workInProgress);
+      newProps = workInProgress.stateNode;
+      newProps.pendingContext &&
+        ((newProps.context = newProps.pendingContext),
+        (newProps.pendingContext = null));
+      if (null === current || null === current.child)
+        workInProgress.effectTag &= -3;
+      updateHostContainer(workInProgress);
+      return null;
+    case 5:
+      popHostContext(workInProgress);
+      var rootContainerInstance = requiredContext(
+          rootInstanceStackCursor.current
+        ),
+        type = workInProgress.type;
+      if (null !== current && null != workInProgress.stateNode) {
+        var oldProps = current.memoizedProps,
+          currentHostContext = requiredContext(contextStackCursor$1.current);
+        updateHostComponent$1(
+          current,
+          workInProgress,
+          emptyObject,
+          type,
+          oldProps,
+          newProps,
+          rootContainerInstance,
+          currentHostContext
+        );
+        current.ref !== workInProgress.ref && (workInProgress.effectTag |= 128);
+      } else {
+        if (!newProps)
+          return (
+            invariant(
+              null !== workInProgress.stateNode,
+              "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+            ),
+            null
+          );
+        current = requiredContext(contextStackCursor$1.current);
+        oldProps = allocateTag();
+        currentHostContext = ReactNativeViewConfigRegistry.get(type);
+        invariant(
+          "RCTView" !== type || !current.isInAParentText,
+          "Nesting of <View> within <Text> is not currently supported."
+        );
+        var updatePayload = diffProperties(
+          null,
+          emptyObject$1,
+          newProps,
+          currentHostContext.validAttributes
+        );
+        UIManager.createView(
+          oldProps,
+          currentHostContext.uiViewClassName,
+          rootContainerInstance,
+          updatePayload
+        );
+        currentHostContext = new ReactNativeFiberHostComponent(
+          oldProps,
+          currentHostContext
+        );
+        instanceCache[oldProps] = workInProgress;
+        instanceProps[oldProps] = newProps;
+        a: for (oldProps = workInProgress.child; null !== oldProps; ) {
+          if (5 === oldProps.tag || 6 === oldProps.tag)
+            currentHostContext._children.push(oldProps.stateNode);
+          else if (4 !== oldProps.tag && null !== oldProps.child) {
+            oldProps.child.return = oldProps;
+            oldProps = oldProps.child;
+            continue;
+          }
+          if (oldProps === workInProgress) break;
+          for (; null === oldProps.sibling; ) {
+            if (null === oldProps.return || oldProps.return === workInProgress)
+              break a;
+            oldProps = oldProps.return;
+          }
+          oldProps.sibling.return = oldProps.return;
+          oldProps = oldProps.sibling;
+        }
+        finalizeInitialChildren(
+          currentHostContext,
+          type,
+          newProps,
+          rootContainerInstance,
+          current
+        ) && (workInProgress.effectTag |= 4);
+        workInProgress.stateNode = currentHostContext;
+        null !== workInProgress.ref && (workInProgress.effectTag |= 128);
+      }
+      return null;
+    case 6:
+      if (current && null != workInProgress.stateNode)
+        updateHostText$1(
+          current,
+          workInProgress,
+          current.memoizedProps,
+          newProps
+        );
+      else {
+        if ("string" !== typeof newProps)
+          return (
+            invariant(
+              null !== workInProgress.stateNode,
+              "We must have new props for new mounts. This error is likely caused by a bug in React. Please file an issue."
+            ),
+            null
+          );
+        rootContainerInstance = requiredContext(
+          rootInstanceStackCursor.current
+        );
+        type = requiredContext(contextStackCursor$1.current);
+        invariant(
+          type.isInAParentText,
+          "Text strings must be rendered within a <Text> component."
+        );
+        type = allocateTag();
+        UIManager.createView(type, "RCTRawText", rootContainerInstance, {
+          text: newProps
+        });
+        instanceCache[type] = workInProgress;
+        workInProgress.stateNode = type;
+      }
+      return null;
+    case 14:
+      return null;
+    case 16:
+      return null;
+    case 10:
+      return null;
+    case 11:
+      return null;
+    case 15:
+      return null;
+    case 4:
+      return (
+        popHostContainer(workInProgress),
+        updateHostContainer(workInProgress),
+        null
+      );
+    case 13:
+      return popProvider(workInProgress), null;
+    case 12:
+      return null;
+    case 0:
+      invariant(
+        !1,
+        "An indeterminate component should have become determinate before completing. This error is likely caused by a bug in React. Please file an issue."
+      );
+    default:
+      invariant(
+        !1,
+        "Unknown unit of work tag. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
+}
+function logError(boundary, errorInfo) {
+  var source = errorInfo.source,
+    stack = errorInfo.stack;
+  null === stack &&
+    null !== source &&
+    (stack = getStackAddendumByWorkInProgressFiber(source));
+  null !== source && getComponentName(source);
+  source = null !== stack ? stack : "";
+  errorInfo = errorInfo.value;
+  null !== boundary && 2 === boundary.tag && getComponentName(boundary);
+  try {
+    if (errorInfo instanceof Error) {
+      var message = errorInfo.message,
+        name = errorInfo.name;
+      var errorToHandle = errorInfo;
+      try {
+        errorToHandle.message =
+          (message ? name + ": " + message : name) +
+          "\n\nThis error is located at:" +
+          source;
+      } catch (e) {}
+    } else
+      errorToHandle =
+        "string" === typeof errorInfo
+          ? Error(errorInfo + "\n\nThis error is located at:" + source)
+          : Error("Unspecified error at:" + source);
+    ExceptionsManager.handleException(errorToHandle, !1);
+  } catch (e) {
+    (e && e.suppressReactErrorLogging) || console.error(e);
+  }
+}
+function safelyDetachRef(current) {
+  var ref = current.ref;
+  if (null !== ref)
+    if ("function" === typeof ref)
+      try {
+        ref(null);
+      } catch (refError) {
+        captureCommitPhaseError(current, refError);
+      }
+    else ref.current = null;
+}
+function commitUnmount(current) {
+  "function" === typeof onCommitUnmount && onCommitUnmount(current);
+  switch (current.tag) {
+    case 2:
+      safelyDetachRef(current);
+      var instance = current.stateNode;
+      if ("function" === typeof instance.componentWillUnmount)
+        try {
+          (instance.props = current.memoizedProps),
+            (instance.state = current.memoizedState),
+            instance.componentWillUnmount();
+        } catch (unmountError) {
+          captureCommitPhaseError(current, unmountError);
+        }
+      break;
+    case 5:
+      safelyDetachRef(current);
+      break;
+    case 4:
+      unmountHostComponents(current);
+  }
+}
+function isHostParent(fiber) {
+  return 5 === fiber.tag || 3 === fiber.tag || 4 === fiber.tag;
+}
+function commitPlacement(finishedWork) {
+  a: {
+    for (var parent = finishedWork.return; null !== parent; ) {
+      if (isHostParent(parent)) {
+        var parentFiber = parent;
+        break a;
+      }
+      parent = parent.return;
+    }
+    invariant(
+      !1,
+      "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
+    );
+    parentFiber = void 0;
+  }
+  var isContainer = (parent = void 0);
+  switch (parentFiber.tag) {
+    case 5:
+      parent = parentFiber.stateNode;
+      isContainer = !1;
+      break;
+    case 3:
+      parent = parentFiber.stateNode.containerInfo;
+      isContainer = !0;
+      break;
+    case 4:
+      parent = parentFiber.stateNode.containerInfo;
+      isContainer = !0;
+      break;
+    default:
+      invariant(
+        !1,
+        "Invalid host parent fiber. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
+  parentFiber.effectTag & 16 && (parentFiber.effectTag &= -17);
+  a: b: for (parentFiber = finishedWork; ; ) {
+    for (; null === parentFiber.sibling; ) {
+      if (null === parentFiber.return || isHostParent(parentFiber.return)) {
+        parentFiber = null;
+        break a;
+      }
+      parentFiber = parentFiber.return;
+    }
+    parentFiber.sibling.return = parentFiber.return;
+    for (
+      parentFiber = parentFiber.sibling;
+      5 !== parentFiber.tag && 6 !== parentFiber.tag;
+
+    ) {
+      if (parentFiber.effectTag & 2) continue b;
+      if (null === parentFiber.child || 4 === parentFiber.tag) continue b;
+      else
+        (parentFiber.child.return = parentFiber),
+          (parentFiber = parentFiber.child);
+    }
+    if (!(parentFiber.effectTag & 2)) {
+      parentFiber = parentFiber.stateNode;
+      break a;
+    }
+  }
+  for (var node = finishedWork; ; ) {
+    if (5 === node.tag || 6 === node.tag)
+      if (parentFiber)
+        if (isContainer)
+          invariant(
+            "number" !== typeof parent,
+            "Container does not support insertBefore operation"
+          );
+        else {
+          var parentInstance = parent,
+            child = node.stateNode,
+            beforeChild = parentFiber,
+            children = parentInstance._children,
+            index = children.indexOf(child);
+          0 <= index
+            ? (children.splice(index, 1),
+              (beforeChild = children.indexOf(beforeChild)),
+              children.splice(beforeChild, 0, child),
+              UIManager.manageChildren(
+                parentInstance._nativeTag,
+                [index],
+                [beforeChild],
+                [],
+                [],
+                []
+              ))
+            : ((index = children.indexOf(beforeChild)),
+              children.splice(index, 0, child),
+              UIManager.manageChildren(
+                parentInstance._nativeTag,
+                [],
+                [],
+                ["number" === typeof child ? child : child._nativeTag],
+                [index],
+                []
+              ));
+        }
+      else
+        isContainer
+          ? ((parentInstance = node.stateNode),
+            UIManager.setChildren(parent, [
+              "number" === typeof parentInstance
+                ? parentInstance
+                : parentInstance._nativeTag
+            ]))
+          : ((parentInstance = parent),
+            (child = node.stateNode),
+            (children = "number" === typeof child ? child : child._nativeTag),
+            (index = parentInstance._children),
+            (beforeChild = index.indexOf(child)),
+            0 <= beforeChild
+              ? (index.splice(beforeChild, 1),
+                index.push(child),
+                UIManager.manageChildren(
+                  parentInstance._nativeTag,
+                  [beforeChild],
+                  [index.length - 1],
+                  [],
+                  [],
+                  []
+                ))
+              : (index.push(child),
+                UIManager.manageChildren(
+                  parentInstance._nativeTag,
+                  [],
+                  [],
+                  [children],
+                  [index.length - 1],
+                  []
+                )));
+    else if (4 !== node.tag && null !== node.child) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === finishedWork) break;
+    for (; null === node.sibling; ) {
+      if (null === node.return || node.return === finishedWork) return;
+      node = node.return;
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+}
+function unmountHostComponents(current) {
+  for (
+    var node = current,
+      currentParentIsValid = !1,
+      currentParent = void 0,
+      currentParentIsContainer = void 0;
+    ;
+
+  ) {
+    if (!currentParentIsValid) {
+      currentParentIsValid = node.return;
+      a: for (;;) {
+        invariant(
+          null !== currentParentIsValid,
+          "Expected to find a host parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+        switch (currentParentIsValid.tag) {
+          case 5:
+            currentParent = currentParentIsValid.stateNode;
+            currentParentIsContainer = !1;
+            break a;
+          case 3:
+            currentParent = currentParentIsValid.stateNode.containerInfo;
+            currentParentIsContainer = !0;
+            break a;
+          case 4:
+            currentParent = currentParentIsValid.stateNode.containerInfo;
+            currentParentIsContainer = !0;
+            break a;
+        }
+        currentParentIsValid = currentParentIsValid.return;
+      }
+      currentParentIsValid = !0;
+    }
+    if (5 === node.tag || 6 === node.tag) {
+      a: for (var root = node, node$jscomp$0 = root; ; )
+        if (
+          (commitUnmount(node$jscomp$0),
+          null !== node$jscomp$0.child && 4 !== node$jscomp$0.tag)
+        )
+          (node$jscomp$0.child.return = node$jscomp$0),
+            (node$jscomp$0 = node$jscomp$0.child);
+        else {
+          if (node$jscomp$0 === root) break;
+          for (; null === node$jscomp$0.sibling; ) {
+            if (null === node$jscomp$0.return || node$jscomp$0.return === root)
+              break a;
+            node$jscomp$0 = node$jscomp$0.return;
+          }
+          node$jscomp$0.sibling.return = node$jscomp$0.return;
+          node$jscomp$0 = node$jscomp$0.sibling;
+        }
+      if (currentParentIsContainer)
+        (root = currentParent),
+          recursivelyUncacheFiberNode(node.stateNode),
+          UIManager.manageChildren(root, [], [], [], [], [0]);
+      else {
+        root = currentParent;
+        var child = node.stateNode;
+        recursivelyUncacheFiberNode(child);
+        node$jscomp$0 = root._children;
+        child = node$jscomp$0.indexOf(child);
+        node$jscomp$0.splice(child, 1);
+        UIManager.manageChildren(root._nativeTag, [], [], [], [], [child]);
+      }
+    } else if (
+      (4 === node.tag
+        ? (currentParent = node.stateNode.containerInfo)
+        : commitUnmount(node),
+      null !== node.child)
+    ) {
+      node.child.return = node;
+      node = node.child;
+      continue;
+    }
+    if (node === current) break;
+    for (; null === node.sibling; ) {
+      if (null === node.return || node.return === current) return;
+      node = node.return;
+      4 === node.tag && (currentParentIsValid = !1);
+    }
+    node.sibling.return = node.return;
+    node = node.sibling;
+  }
+}
+function commitWork(current, finishedWork) {
+  switch (finishedWork.tag) {
+    case 2:
+      break;
+    case 5:
+      var instance = finishedWork.stateNode;
+      if (null != instance) {
+        var newProps = finishedWork.memoizedProps;
+        current = null !== current ? current.memoizedProps : newProps;
+        var updatePayload = finishedWork.updateQueue;
+        finishedWork.updateQueue = null;
+        null !== updatePayload &&
+          ((finishedWork = instance.viewConfig),
+          (instanceProps[instance._nativeTag] = newProps),
+          (newProps = diffProperties(
+            null,
+            current,
+            newProps,
+            finishedWork.validAttributes
+          )),
+          null != newProps &&
+            UIManager.updateView(
+              instance._nativeTag,
+              finishedWork.uiViewClassName,
+              newProps
+            ));
+      }
+      break;
+    case 6:
+      invariant(
+        null !== finishedWork.stateNode,
+        "This should have a text node initialized. This error is likely caused by a bug in React. Please file an issue."
+      );
+      UIManager.updateView(finishedWork.stateNode, "RCTRawText", {
+        text: finishedWork.memoizedProps
+      });
+      break;
+    case 3:
+      break;
+    case 15:
+      instance = finishedWork.memoizedProps.onRender;
+      instance(
+        finishedWork.memoizedProps.id,
+        null === current ? "mount" : "update",
+        finishedWork.actualDuration,
+        finishedWork.treeBaseTime,
+        finishedWork.actualStartTime,
+        commitTime
+      );
+      break;
+    case 16:
+      break;
+    default:
+      invariant(
+        !1,
+        "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+      );
+  }
+}
+function createRootErrorUpdate(fiber, errorInfo, expirationTime) {
+  expirationTime = createUpdate(expirationTime);
+  expirationTime.tag = 3;
+  expirationTime.payload = { element: null };
+  var error = errorInfo.value;
+  expirationTime.callback = function() {
+    onUncaughtError(error);
+    logError(fiber, errorInfo);
+  };
+  return expirationTime;
+}
+function createClassErrorUpdate(fiber, errorInfo, expirationTime) {
+  expirationTime = createUpdate(expirationTime);
+  expirationTime.tag = 3;
+  var inst = fiber.stateNode;
+  null !== inst &&
+    "function" === typeof inst.componentDidCatch &&
+    (expirationTime.callback = function() {
+      null === legacyErrorBoundariesThatAlreadyFailed
+        ? (legacyErrorBoundariesThatAlreadyFailed = new Set([this]))
+        : legacyErrorBoundariesThatAlreadyFailed.add(this);
+      var error = errorInfo.value,
+        stack = errorInfo.stack;
+      logError(fiber, errorInfo);
+      this.componentDidCatch(error, {
+        componentStack: null !== stack ? stack : ""
+      });
+    });
+  return expirationTime;
+}
+function unwindWork(workInProgress) {
+  workInProgress.mode & 4 && recordElapsedActualRenderTime(workInProgress);
+  switch (workInProgress.tag) {
+    case 2:
+      popContextProvider(workInProgress);
+      var effectTag = workInProgress.effectTag;
+      return effectTag & 1024
+        ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+          workInProgress)
+        : null;
+    case 3:
+      return (
+        popHostContainer(workInProgress),
+        popTopLevelContextObject(workInProgress),
+        (effectTag = workInProgress.effectTag),
+        effectTag & 1024
+          ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+            workInProgress)
+          : null
+      );
+    case 5:
+      return popHostContext(workInProgress), null;
+    case 16:
+      return (
+        (effectTag = workInProgress.effectTag),
+        effectTag & 1024
+          ? ((workInProgress.effectTag = (effectTag & -1025) | 64),
+            workInProgress)
+          : null
+      );
+    case 4:
+      return popHostContainer(workInProgress), null;
+    case 13:
+      return popProvider(workInProgress), null;
+    default:
+      return null;
+  }
+}
+var originalStartTimeMs = now$1(),
+  mostRecentCurrentTime = 2,
+  mostRecentCurrentTimeMs = originalStartTimeMs,
+  lastUniqueAsyncExpiration = 0,
+  expirationContext = 0,
+  isWorking = !1,
+  nextUnitOfWork = null,
+  nextRoot = null,
+  nextRenderExpirationTime = 0,
+  nextLatestTimeoutMs = -1,
+  nextRenderDidError = !1,
+  nextEffect = null,
+  isCommitting$1 = !1,
+  legacyErrorBoundariesThatAlreadyFailed = null;
+function resetStack() {
+  if (null !== nextUnitOfWork)
+    for (
+      var interruptedWork = nextUnitOfWork.return;
+      null !== interruptedWork;
+
+    ) {
+      var interruptedWork$jscomp$0 = interruptedWork;
+      interruptedWork$jscomp$0.mode & 4 &&
+        (resumeActualRenderTimerIfPaused(),
+        recordElapsedActualRenderTime(interruptedWork$jscomp$0));
+      switch (interruptedWork$jscomp$0.tag) {
+        case 2:
+          popContextProvider(interruptedWork$jscomp$0);
+          break;
+        case 3:
+          popHostContainer(interruptedWork$jscomp$0);
+          popTopLevelContextObject(interruptedWork$jscomp$0);
+          break;
+        case 5:
+          popHostContext(interruptedWork$jscomp$0);
+          break;
+        case 4:
+          popHostContainer(interruptedWork$jscomp$0);
+          break;
+        case 13:
+          popProvider(interruptedWork$jscomp$0);
+      }
+      interruptedWork = interruptedWork.return;
+    }
+  nextRoot = null;
+  nextRenderExpirationTime = 0;
+  nextLatestTimeoutMs = -1;
+  nextRenderDidError = !1;
+  nextUnitOfWork = null;
+}
+function completeUnitOfWork(workInProgress$jscomp$0) {
+  for (;;) {
+    var current = workInProgress$jscomp$0.alternate,
+      returnFiber = workInProgress$jscomp$0.return,
+      siblingFiber = workInProgress$jscomp$0.sibling;
+    if (0 === (workInProgress$jscomp$0.effectTag & 512)) {
+      current = completeWork(
+        current,
+        workInProgress$jscomp$0,
+        nextRenderExpirationTime
+      );
+      var workInProgress = workInProgress$jscomp$0;
+      if (
+        1073741823 === nextRenderExpirationTime ||
+        1073741823 !== workInProgress.expirationTime
+      ) {
+        var newExpirationTime = 0;
+        switch (workInProgress.tag) {
+          case 3:
+          case 2:
+            var updateQueue = workInProgress.updateQueue;
+            null !== updateQueue &&
+              (newExpirationTime = updateQueue.expirationTime);
+        }
+        if (workInProgress.mode & 4) {
+          updateQueue = workInProgress.selfBaseTime;
+          for (var child = workInProgress.child; null !== child; )
+            (updateQueue += child.treeBaseTime),
+              0 !== child.expirationTime &&
+                (0 === newExpirationTime ||
+                  newExpirationTime > child.expirationTime) &&
+                (newExpirationTime = child.expirationTime),
+              (child = child.sibling);
+          workInProgress.treeBaseTime = updateQueue;
+        } else
+          for (updateQueue = workInProgress.child; null !== updateQueue; )
+            0 !== updateQueue.expirationTime &&
+              (0 === newExpirationTime ||
+                newExpirationTime > updateQueue.expirationTime) &&
+              (newExpirationTime = updateQueue.expirationTime),
+              (updateQueue = updateQueue.sibling);
+        workInProgress.expirationTime = newExpirationTime;
+      }
+      if (null !== current) return current;
+      null !== returnFiber &&
+        0 === (returnFiber.effectTag & 512) &&
+        (null === returnFiber.firstEffect &&
+          (returnFiber.firstEffect = workInProgress$jscomp$0.firstEffect),
+        null !== workInProgress$jscomp$0.lastEffect &&
+          (null !== returnFiber.lastEffect &&
+            (returnFiber.lastEffect.nextEffect =
+              workInProgress$jscomp$0.firstEffect),
+          (returnFiber.lastEffect = workInProgress$jscomp$0.lastEffect)),
+        1 < workInProgress$jscomp$0.effectTag &&
+          (null !== returnFiber.lastEffect
+            ? (returnFiber.lastEffect.nextEffect = workInProgress$jscomp$0)
+            : (returnFiber.firstEffect = workInProgress$jscomp$0),
+          (returnFiber.lastEffect = workInProgress$jscomp$0)));
+    } else {
+      workInProgress$jscomp$0 = unwindWork(
+        workInProgress$jscomp$0,
+        nextRenderExpirationTime
+      );
+      if (null !== workInProgress$jscomp$0)
+        return (
+          (workInProgress$jscomp$0.effectTag &= 511), workInProgress$jscomp$0
+        );
+      null !== returnFiber &&
+        ((returnFiber.firstEffect = returnFiber.lastEffect = null),
+        (returnFiber.effectTag |= 512));
+    }
+    if (null !== siblingFiber) return siblingFiber;
+    if (null !== returnFiber) workInProgress$jscomp$0 = returnFiber;
+    else break;
+  }
+  return null;
+}
+function performUnitOfWork(workInProgress) {
+  var current = workInProgress.alternate;
+  workInProgress.mode & 4 && (baseStartTime = now$1());
+  current = beginWork(current, workInProgress, nextRenderExpirationTime);
+  workInProgress.mode & 4 &&
+    (-1 !== baseStartTime &&
+      (workInProgress.selfBaseTime = now$1() - baseStartTime),
+    (baseStartTime = -1));
+  null === current && (current = completeUnitOfWork(workInProgress));
+  ReactCurrentOwner.current = null;
+  return current;
+}
+function renderRoot(root$jscomp$0, isYieldy) {
+  invariant(
+    !isWorking,
+    "renderRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+  );
+  isWorking = !0;
+  var expirationTime = root$jscomp$0.nextExpirationTimeToWorkOn;
+  if (
+    expirationTime !== nextRenderExpirationTime ||
+    root$jscomp$0 !== nextRoot ||
+    null === nextUnitOfWork
+  )
+    resetStack(),
+      (nextRoot = root$jscomp$0),
+      (nextRenderExpirationTime = expirationTime),
+      (nextLatestTimeoutMs = -1),
+      (nextRenderDidError = !1),
+      (nextUnitOfWork = createWorkInProgress(
+        nextRoot.current,
+        null,
+        nextRenderExpirationTime
+      )),
+      (root$jscomp$0.pendingCommitExpirationTime = 0);
+  var didFatal = !1;
+  do {
+    try {
+      if (isYieldy) {
+        for (; null !== nextUnitOfWork && !shouldYield(); )
+          nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+        0 === timerPausedAt && (timerPausedAt = now$1());
+      } else
+        for (; null !== nextUnitOfWork; )
+          nextUnitOfWork = performUnitOfWork(nextUnitOfWork);
+    } catch (thrownValue) {
+      if (((baseStartTime = -1), null === nextUnitOfWork))
+        (didFatal = !0), onUncaughtError(thrownValue);
+      else {
+        invariant(
+          null !== nextUnitOfWork,
+          "Failed to replay rendering after an error. This is likely caused by a bug in React. Please file an issue with a reproducing case to help us find it."
+        );
+        isYieldy = nextUnitOfWork;
+        var returnFiber = isYieldy.return;
+        if (null === returnFiber) {
+          didFatal = !0;
+          onUncaughtError(thrownValue);
+          break;
+        }
+        a: {
+          var root = root$jscomp$0,
+            returnFiber$jscomp$0 = returnFiber,
+            sourceFiber = isYieldy,
+            value = thrownValue;
+          returnFiber = nextRenderExpirationTime;
+          sourceFiber.effectTag |= 512;
+          sourceFiber.firstEffect = sourceFiber.lastEffect = null;
+          nextRenderDidError = !0;
+          if (
+            (root.didError || 1 === returnFiber) &&
+            (returnFiber === root.latestPendingTime ||
+              returnFiber === root.latestSuspendedTime)
+          ) {
+            value = createCapturedValue(value, sourceFiber);
+            root = returnFiber$jscomp$0;
+            do {
+              switch (root.tag) {
+                case 3:
+                  root.effectTag |= 1024;
+                  value = createRootErrorUpdate(root, value, returnFiber);
+                  enqueueCapturedUpdate(root, value, returnFiber);
+                  break a;
+                case 2:
+                  if (
+                    ((returnFiber$jscomp$0 = value),
+                    (sourceFiber = root.stateNode),
+                    0 === (root.effectTag & 64) &&
+                      null !== sourceFiber &&
+                      "function" === typeof sourceFiber.componentDidCatch &&
+                      (null === legacyErrorBoundariesThatAlreadyFailed ||
+                        !legacyErrorBoundariesThatAlreadyFailed.has(
+                          sourceFiber
+                        )))
+                  ) {
+                    root.effectTag |= 1024;
+                    value = createClassErrorUpdate(
+                      root,
+                      returnFiber$jscomp$0,
+                      returnFiber
+                    );
+                    enqueueCapturedUpdate(root, value, returnFiber);
+                    break a;
+                  }
+              }
+              root = root.return;
+            } while (null !== root);
+          }
+        }
+        nextUnitOfWork = completeUnitOfWork(isYieldy);
+      }
+    }
+    break;
+  } while (1);
+  isWorking = !1;
+  didFatal
+    ? (root$jscomp$0.finishedWork = null)
+    : null === nextUnitOfWork
+      ? ((didFatal = root$jscomp$0.current.alternate),
+        invariant(
+          null !== didFatal,
+          "Finished root should have a work-in-progress. This error is likely caused by a bug in React. Please file an issue."
+        ),
+        0 === (didFatal.effectTag & 512)
+          ? ((root$jscomp$0.pendingCommitExpirationTime = expirationTime),
+            (root$jscomp$0.finishedWork = didFatal))
+          : (!nextRenderDidError ||
+            (expirationTime !== root$jscomp$0.latestPendingTime &&
+              expirationTime !== root$jscomp$0.latestSuspendedTime)
+              ? ((didFatal = root$jscomp$0.earliestPendingTime),
+                (isYieldy = root$jscomp$0.latestPendingTime),
+                didFatal === expirationTime
+                  ? (root$jscomp$0.earliestPendingTime =
+                      isYieldy === expirationTime
+                        ? (root$jscomp$0.latestPendingTime = 0)
+                        : isYieldy)
+                  : isYieldy === expirationTime &&
+                    (root$jscomp$0.latestPendingTime = didFatal),
+                (didFatal = root$jscomp$0.latestSuspendedTime),
+                didFatal === expirationTime &&
+                  (root$jscomp$0.latestPingedTime = 0),
+                (isYieldy = root$jscomp$0.earliestSuspendedTime),
+                0 === isYieldy
+                  ? (root$jscomp$0.earliestSuspendedTime = root$jscomp$0.latestSuspendedTime = expirationTime)
+                  : isYieldy > expirationTime
+                    ? (root$jscomp$0.earliestSuspendedTime = expirationTime)
+                    : didFatal < expirationTime &&
+                      (root$jscomp$0.latestSuspendedTime = expirationTime))
+              : (root$jscomp$0.didError = !0),
+            findNextPendingPriorityLevel(root$jscomp$0),
+            onSuspend(
+              root$jscomp$0,
+              expirationTime,
+              root$jscomp$0.expirationTime,
+              nextLatestTimeoutMs
+            )))
+      : (root$jscomp$0.finishedWork = null);
+}
+function captureCommitPhaseError(fiber, error) {
+  var JSCompiler_inline_result;
+  a: {
+    invariant(
+      !isWorking || isCommitting$1,
+      "dispatch: Cannot dispatch during the render phase."
+    );
+    for (
+      JSCompiler_inline_result = fiber.return;
+      null !== JSCompiler_inline_result;
+
+    ) {
+      switch (JSCompiler_inline_result.tag) {
+        case 2:
+          var instance = JSCompiler_inline_result.stateNode;
+          if (
+            "function" ===
+              typeof JSCompiler_inline_result.type.getDerivedStateFromCatch ||
+            ("function" === typeof instance.componentDidCatch &&
+              (null === legacyErrorBoundariesThatAlreadyFailed ||
+                !legacyErrorBoundariesThatAlreadyFailed.has(instance)))
+          ) {
+            fiber = createCapturedValue(error, fiber);
+            fiber = createClassErrorUpdate(JSCompiler_inline_result, fiber, 1);
+            enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+            scheduleWork(JSCompiler_inline_result, 1);
+            JSCompiler_inline_result = void 0;
+            break a;
+          }
+          break;
+        case 3:
+          fiber = createCapturedValue(error, fiber);
+          fiber = createRootErrorUpdate(JSCompiler_inline_result, fiber, 1);
+          enqueueUpdate(JSCompiler_inline_result, fiber, 1);
+          scheduleWork(JSCompiler_inline_result, 1);
+          JSCompiler_inline_result = void 0;
+          break a;
+      }
+      JSCompiler_inline_result = JSCompiler_inline_result.return;
+    }
+    3 === fiber.tag &&
+      ((JSCompiler_inline_result = createCapturedValue(error, fiber)),
+      (JSCompiler_inline_result = createRootErrorUpdate(
+        fiber,
+        JSCompiler_inline_result,
+        1
+      )),
+      enqueueUpdate(fiber, JSCompiler_inline_result, 1),
+      scheduleWork(fiber, 1));
+    JSCompiler_inline_result = void 0;
+  }
+  return JSCompiler_inline_result;
+}
+function computeExpirationForFiber(currentTime, fiber) {
+  currentTime =
+    0 !== expirationContext
+      ? expirationContext
+      : isWorking
+        ? isCommitting$1 ? 1 : nextRenderExpirationTime
+        : fiber.mode & 1
+          ? isBatchingInteractiveUpdates
+            ? 2 + 10 * ((((currentTime - 2 + 15) / 10) | 0) + 1)
+            : 2 + 25 * ((((currentTime - 2 + 500) / 25) | 0) + 1)
+          : 1;
+  isBatchingInteractiveUpdates &&
+    (0 === lowestPendingInteractiveExpirationTime ||
+      currentTime > lowestPendingInteractiveExpirationTime) &&
+    (lowestPendingInteractiveExpirationTime = currentTime);
+  return currentTime;
+}
+function scheduleWork(fiber, expirationTime) {
+  for (; null !== fiber; ) {
+    if (0 === fiber.expirationTime || fiber.expirationTime > expirationTime)
+      fiber.expirationTime = expirationTime;
+    null !== fiber.alternate &&
+      (0 === fiber.alternate.expirationTime ||
+        fiber.alternate.expirationTime > expirationTime) &&
+      (fiber.alternate.expirationTime = expirationTime);
+    if (null === fiber.return)
+      if (3 === fiber.tag) {
+        var root = fiber.stateNode;
+        !isWorking &&
+          0 !== nextRenderExpirationTime &&
+          expirationTime < nextRenderExpirationTime &&
+          resetStack();
+        markPendingPriorityLevel(root, expirationTime);
+        (isWorking && !isCommitting$1 && nextRoot === root) ||
+          requestWork(root, root.expirationTime);
+        nestedUpdateCount > NESTED_UPDATE_LIMIT &&
+          invariant(
+            !1,
+            "Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops."
+          );
+      } else break;
+    fiber = fiber.return;
+  }
+}
+function recalculateCurrentTime() {
+  mostRecentCurrentTimeMs = now$1() - originalStartTimeMs;
+  return (mostRecentCurrentTime = ((mostRecentCurrentTimeMs / 10) | 0) + 2);
+}
+function syncUpdates(fn, a, b, c, d) {
+  var previousExpirationContext = expirationContext;
+  expirationContext = 1;
+  try {
+    return fn(a, b, c, d);
+  } finally {
+    expirationContext = previousExpirationContext;
+  }
+}
+var firstScheduledRoot = null,
+  lastScheduledRoot = null,
+  callbackExpirationTime = 0,
+  callbackID = void 0,
+  isRendering = !1,
+  nextFlushedRoot = null,
+  nextFlushedExpirationTime = 0,
+  lowestPendingInteractiveExpirationTime = 0,
+  deadlineDidExpire = !1,
+  hasUnhandledError = !1,
+  unhandledError = null,
+  deadline = null,
+  isBatchingUpdates = !1,
+  isUnbatchingUpdates = !1,
+  isBatchingInteractiveUpdates = !1,
+  completedBatches = null,
+  NESTED_UPDATE_LIMIT = 1e3,
+  nestedUpdateCount = 0,
+  timeHeuristicForUnitOfWork = 1;
+function scheduleCallbackWithExpirationTime(expirationTime) {
+  if (0 !== callbackExpirationTime) {
+    if (expirationTime > callbackExpirationTime) return;
+    if (null !== callbackID) {
+      var callbackID$jscomp$0 = callbackID;
+      scheduledCallback = null;
+      clearTimeout(callbackID$jscomp$0);
+    }
+  }
+  callbackExpirationTime = expirationTime;
+  now$1();
+  scheduledCallback = performAsyncWork;
+  callbackID = setTimeout(setTimeoutCallback, 1);
+}
+function onSuspend(root, suspendedExpirationTime, expirationTime, timeoutMs) {
+  0 <= timeoutMs &&
+    setTimeout(function() {
+      var latestSuspendedTime = root.latestSuspendedTime;
+      0 !== latestSuspendedTime &&
+        latestSuspendedTime <= suspendedExpirationTime &&
+        ((latestSuspendedTime = root.latestPingedTime),
+        0 === latestSuspendedTime ||
+          latestSuspendedTime < suspendedExpirationTime) &&
+        (root.latestPingedTime = suspendedExpirationTime);
+      findNextPendingPriorityLevel(root);
+      latestSuspendedTime = root.expirationTime;
+      0 !== latestSuspendedTime && requestWork(root, latestSuspendedTime);
+    }, timeoutMs);
+  root.expirationTime = expirationTime;
+}
+function requestWork(root, expirationTime) {
+  if (null === root.nextScheduledRoot)
+    (root.expirationTime = expirationTime),
+      null === lastScheduledRoot
+        ? ((firstScheduledRoot = lastScheduledRoot = root),
+          (root.nextScheduledRoot = root))
+        : ((lastScheduledRoot = lastScheduledRoot.nextScheduledRoot = root),
+          (lastScheduledRoot.nextScheduledRoot = firstScheduledRoot));
+  else {
+    var remainingExpirationTime = root.expirationTime;
+    if (
+      0 === remainingExpirationTime ||
+      expirationTime < remainingExpirationTime
+    )
+      root.expirationTime = expirationTime;
+  }
+  isRendering ||
+    (isBatchingUpdates
+      ? isUnbatchingUpdates &&
+        ((nextFlushedRoot = root),
+        (nextFlushedExpirationTime = 1),
+        performWorkOnRoot(root, 1, !1))
+      : 1 === expirationTime
+        ? performWork(1, null)
+        : scheduleCallbackWithExpirationTime(expirationTime));
+}
+function findHighestPriorityRoot() {
+  var highestPriorityWork = 0,
+    highestPriorityRoot = null;
+  if (null !== lastScheduledRoot)
+    for (
+      var previousScheduledRoot = lastScheduledRoot, root = firstScheduledRoot;
+      null !== root;
+
+    ) {
+      var remainingExpirationTime = root.expirationTime;
+      if (0 === remainingExpirationTime) {
+        invariant(
+          null !== previousScheduledRoot && null !== lastScheduledRoot,
+          "Should have a previous and last root. This error is likely caused by a bug in React. Please file an issue."
+        );
+        if (root === root.nextScheduledRoot) {
+          firstScheduledRoot = lastScheduledRoot = root.nextScheduledRoot = null;
+          break;
+        } else if (root === firstScheduledRoot)
+          (firstScheduledRoot = remainingExpirationTime =
+            root.nextScheduledRoot),
+            (lastScheduledRoot.nextScheduledRoot = remainingExpirationTime),
+            (root.nextScheduledRoot = null);
+        else if (root === lastScheduledRoot) {
+          lastScheduledRoot = previousScheduledRoot;
+          lastScheduledRoot.nextScheduledRoot = firstScheduledRoot;
+          root.nextScheduledRoot = null;
+          break;
+        } else
+          (previousScheduledRoot.nextScheduledRoot = root.nextScheduledRoot),
+            (root.nextScheduledRoot = null);
+        root = previousScheduledRoot.nextScheduledRoot;
+      } else {
+        if (
+          0 === highestPriorityWork ||
+          remainingExpirationTime < highestPriorityWork
+        )
+          (highestPriorityWork = remainingExpirationTime),
+            (highestPriorityRoot = root);
+        if (root === lastScheduledRoot) break;
+        previousScheduledRoot = root;
+        root = root.nextScheduledRoot;
+      }
+    }
+  previousScheduledRoot = nextFlushedRoot;
+  null !== previousScheduledRoot &&
+  previousScheduledRoot === highestPriorityRoot &&
+  1 === highestPriorityWork
+    ? nestedUpdateCount++
+    : (nestedUpdateCount = 0);
+  nextFlushedRoot = highestPriorityRoot;
+  nextFlushedExpirationTime = highestPriorityWork;
+}
+function performAsyncWork(dl) {
+  performWork(0, dl);
+}
+function performWork(minExpirationTime, dl) {
+  deadline = dl;
+  findHighestPriorityRoot();
+  resumeActualRenderTimerIfPaused();
+  if (null !== deadline)
+    for (
+      ;
+      null !== nextFlushedRoot &&
+      0 !== nextFlushedExpirationTime &&
+      (0 === minExpirationTime ||
+        minExpirationTime >= nextFlushedExpirationTime) &&
+      (!deadlineDidExpire ||
+        recalculateCurrentTime() >= nextFlushedExpirationTime);
+
+    )
+      recalculateCurrentTime(),
+        performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !0),
+        findHighestPriorityRoot();
+  else
+    for (
+      ;
+      null !== nextFlushedRoot &&
+      0 !== nextFlushedExpirationTime &&
+      (0 === minExpirationTime ||
+        minExpirationTime >= nextFlushedExpirationTime);
+
+    )
+      performWorkOnRoot(nextFlushedRoot, nextFlushedExpirationTime, !1),
+        findHighestPriorityRoot();
+  null !== deadline && ((callbackExpirationTime = 0), (callbackID = null));
+  0 !== nextFlushedExpirationTime &&
+    scheduleCallbackWithExpirationTime(nextFlushedExpirationTime);
+  deadline = null;
+  deadlineDidExpire = !1;
+  finishRendering();
+}
+function finishRendering() {
+  nestedUpdateCount = 0;
+  if (null !== completedBatches) {
+    var batches = completedBatches;
+    completedBatches = null;
+    for (var i = 0; i < batches.length; i++) {
+      var batch = batches[i];
+      try {
+        batch._onComplete();
+      } catch (error) {
+        hasUnhandledError ||
+          ((hasUnhandledError = !0), (unhandledError = error));
+      }
+    }
+  }
+  if (hasUnhandledError)
+    throw ((batches = unhandledError),
+    (unhandledError = null),
+    (hasUnhandledError = !1),
+    batches);
+}
+function performWorkOnRoot(root, expirationTime, isYieldy) {
+  invariant(
+    !isRendering,
+    "performWorkOnRoot was called recursively. This error is likely caused by a bug in React. Please file an issue."
+  );
+  isRendering = !0;
+  isYieldy
+    ? ((isYieldy = root.finishedWork),
+      null !== isYieldy
+        ? completeRoot(root, isYieldy, expirationTime)
+        : ((root.finishedWork = null),
+          renderRoot(root, !0),
+          (isYieldy = root.finishedWork),
+          null !== isYieldy &&
+            (shouldYield()
+              ? ((root.finishedWork = isYieldy),
+                0 === timerPausedAt && (timerPausedAt = now$1()))
+              : completeRoot(root, isYieldy, expirationTime))))
+    : ((isYieldy = root.finishedWork),
+      null !== isYieldy
+        ? completeRoot(root, isYieldy, expirationTime)
+        : ((root.finishedWork = null),
+          renderRoot(root, !1),
+          (isYieldy = root.finishedWork),
+          null !== isYieldy && completeRoot(root, isYieldy, expirationTime)));
+  isRendering = !1;
+}
+function completeRoot(root, finishedWork$jscomp$0, expirationTime) {
+  var firstBatch = root.firstBatch;
+  if (
+    null !== firstBatch &&
+    firstBatch._expirationTime <= expirationTime &&
+    (null === completedBatches
+      ? (completedBatches = [firstBatch])
+      : completedBatches.push(firstBatch),
+    firstBatch._defer)
+  ) {
+    root.finishedWork = finishedWork$jscomp$0;
+    root.expirationTime = 0;
+    return;
+  }
+  root.finishedWork = null;
+  isCommitting$1 = isWorking = !0;
+  invariant(
+    root.current !== finishedWork$jscomp$0,
+    "Cannot commit the same tree as before. This is probably a bug related to the return field. This error is likely caused by a bug in React. Please file an issue."
+  );
+  expirationTime = root.pendingCommitExpirationTime;
+  invariant(
+    0 !== expirationTime,
+    "Cannot commit an incomplete root. This error is likely caused by a bug in React. Please file an issue."
+  );
+  root.pendingCommitExpirationTime = 0;
+  firstBatch = finishedWork$jscomp$0.expirationTime;
+  recalculateCurrentTime();
+  root.didError = !1;
+  if (0 === firstBatch)
+    (root.earliestPendingTime = 0),
+      (root.latestPendingTime = 0),
+      (root.earliestSuspendedTime = 0),
+      (root.latestSuspendedTime = 0),
+      (root.latestPingedTime = 0);
+  else {
+    var latestPendingTime = root.latestPendingTime;
+    0 !== latestPendingTime &&
+      (latestPendingTime < firstBatch
+        ? (root.earliestPendingTime = root.latestPendingTime = 0)
+        : root.earliestPendingTime < firstBatch &&
+          (root.earliestPendingTime = root.latestPendingTime));
+    latestPendingTime = root.earliestSuspendedTime;
+    0 === latestPendingTime
+      ? markPendingPriorityLevel(root, firstBatch)
+      : firstBatch > root.latestSuspendedTime
+        ? ((root.earliestSuspendedTime = 0),
+          (root.latestSuspendedTime = 0),
+          (root.latestPingedTime = 0),
+          markPendingPriorityLevel(root, firstBatch))
+        : firstBatch < latestPendingTime &&
+          markPendingPriorityLevel(root, firstBatch);
+  }
+  findNextPendingPriorityLevel(root);
+  ReactCurrentOwner.current = null;
+  1 < finishedWork$jscomp$0.effectTag
+    ? null !== finishedWork$jscomp$0.lastEffect
+      ? ((finishedWork$jscomp$0.lastEffect.nextEffect = finishedWork$jscomp$0),
+        (firstBatch = finishedWork$jscomp$0.firstEffect))
+      : (firstBatch = finishedWork$jscomp$0)
+    : (firstBatch = finishedWork$jscomp$0.firstEffect);
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    latestPendingTime = !1;
+    var error = void 0;
+    try {
+      for (; null !== nextEffect; ) {
+        if (nextEffect.effectTag & 256) {
+          var current = nextEffect.alternate,
+            finishedWork = nextEffect;
+          switch (finishedWork.tag) {
+            case 2:
+              if (finishedWork.effectTag & 256 && null !== current) {
+                var prevProps = current.memoizedProps,
+                  prevState = current.memoizedState,
+                  instance = finishedWork.stateNode;
+                instance.props = finishedWork.memoizedProps;
+                instance.state = finishedWork.memoizedState;
+                var snapshot = instance.getSnapshotBeforeUpdate(
+                  prevProps,
+                  prevState
+                );
+                instance.__reactInternalSnapshotBeforeUpdate = snapshot;
+              }
+              break;
+            case 3:
+            case 5:
+            case 6:
+            case 4:
+              break;
+            default:
+              invariant(
+                !1,
+                "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+              );
+          }
+        }
+        nextEffect = nextEffect.nextEffect;
+      }
+    } catch (e) {
+      (latestPendingTime = !0), (error = e);
+    }
+    latestPendingTime &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, error),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  commitTime = now$1();
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    current = !1;
+    prevProps = void 0;
+    try {
+      for (; null !== nextEffect; ) {
+        var effectTag = nextEffect.effectTag;
+        if (effectTag & 128) {
+          var current$jscomp$0 = nextEffect.alternate;
+          if (null !== current$jscomp$0) {
+            var currentRef = current$jscomp$0.ref;
+            null !== currentRef &&
+              ("function" === typeof currentRef
+                ? currentRef(null)
+                : (currentRef.current = null));
+          }
+        }
+        switch (effectTag & 14) {
+          case 2:
+            commitPlacement(nextEffect);
+            nextEffect.effectTag &= -3;
+            break;
+          case 6:
+            commitPlacement(nextEffect);
+            nextEffect.effectTag &= -3;
+            commitWork(nextEffect.alternate, nextEffect);
+            break;
+          case 4:
+            commitWork(nextEffect.alternate, nextEffect);
+            break;
+          case 8:
+            (prevState = nextEffect),
+              unmountHostComponents(prevState),
+              (prevState.return = null),
+              (prevState.child = null),
+              prevState.alternate &&
+                ((prevState.alternate.child = null),
+                (prevState.alternate.return = null));
+        }
+        nextEffect = nextEffect.nextEffect;
+      }
+    } catch (e) {
+      (current = !0), (prevProps = e);
+    }
+    current &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, prevProps),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  root.current = finishedWork$jscomp$0;
+  for (nextEffect = firstBatch; null !== nextEffect; ) {
+    effectTag = !1;
+    current$jscomp$0 = void 0;
+    try {
+      for (currentRef = expirationTime; null !== nextEffect; ) {
+        var effectTag$jscomp$0 = nextEffect.effectTag;
+        if (effectTag$jscomp$0 & 36) {
+          var current$jscomp$1 = nextEffect.alternate;
+          current = nextEffect;
+          prevProps = currentRef;
+          switch (current.tag) {
+            case 2:
+              var instance$jscomp$0 = current.stateNode;
+              if (current.effectTag & 4)
+                if (null === current$jscomp$1)
+                  (instance$jscomp$0.props = current.memoizedProps),
+                    (instance$jscomp$0.state = current.memoizedState),
+                    instance$jscomp$0.componentDidMount();
+                else {
+                  var prevProps$jscomp$0 = current$jscomp$1.memoizedProps,
+                    prevState$jscomp$0 = current$jscomp$1.memoizedState;
+                  instance$jscomp$0.props = current.memoizedProps;
+                  instance$jscomp$0.state = current.memoizedState;
+                  instance$jscomp$0.componentDidUpdate(
+                    prevProps$jscomp$0,
+                    prevState$jscomp$0,
+                    instance$jscomp$0.__reactInternalSnapshotBeforeUpdate
+                  );
+                }
+              var updateQueue = current.updateQueue;
+              null !== updateQueue &&
+                ((instance$jscomp$0.props = current.memoizedProps),
+                (instance$jscomp$0.state = current.memoizedState),
+                commitUpdateQueue(
+                  current,
+                  updateQueue,
+                  instance$jscomp$0,
+                  prevProps
+                ));
+              break;
+            case 3:
+              var _updateQueue = current.updateQueue;
+              if (null !== _updateQueue) {
+                prevState = null;
+                if (null !== current.child)
+                  switch (current.child.tag) {
+                    case 5:
+                      prevState = current.child.stateNode;
+                      break;
+                    case 2:
+                      prevState = current.child.stateNode;
+                  }
+                commitUpdateQueue(current, _updateQueue, prevState, prevProps);
+              }
+              break;
+            case 5:
+              break;
+            case 6:
+              break;
+            case 4:
+              break;
+            case 15:
+              break;
+            case 16:
+              break;
+            default:
+              invariant(
+                !1,
+                "This unit of work tag should not have side-effects. This error is likely caused by a bug in React. Please file an issue."
+              );
+          }
+        }
+        if (effectTag$jscomp$0 & 128) {
+          current = void 0;
+          var ref = nextEffect.ref;
+          if (null !== ref) {
+            var instance$jscomp$1 = nextEffect.stateNode;
+            switch (nextEffect.tag) {
+              case 5:
+                current = instance$jscomp$1;
+                break;
+              default:
+                current = instance$jscomp$1;
+            }
+            "function" === typeof ref ? ref(current) : (ref.current = current);
+          }
+        }
+        var next = nextEffect.nextEffect;
+        nextEffect.nextEffect = null;
+        nextEffect = next;
+      }
+    } catch (e) {
+      (effectTag = !0), (current$jscomp$0 = e);
+    }
+    effectTag &&
+      (invariant(
+        null !== nextEffect,
+        "Should have next effect. This error is likely caused by a bug in React. Please file an issue."
+      ),
+      captureCommitPhaseError(nextEffect, current$jscomp$0),
+      null !== nextEffect && (nextEffect = nextEffect.nextEffect));
+  }
+  totalElapsedPauseTime = 0;
+  isWorking = isCommitting$1 = !1;
+  "function" === typeof onCommitRoot &&
+    onCommitRoot(finishedWork$jscomp$0.stateNode);
+  finishedWork$jscomp$0 = root.expirationTime;
+  0 === finishedWork$jscomp$0 &&
+    (legacyErrorBoundariesThatAlreadyFailed = null);
+  root.expirationTime = finishedWork$jscomp$0;
+  root.finishedWork = null;
+}
+function shouldYield() {
+  return null === deadline ||
+    deadlineDidExpire ||
+    deadline.timeRemaining() > timeHeuristicForUnitOfWork
+    ? !1
+    : (deadlineDidExpire = !0);
+}
+function onUncaughtError(error) {
+  invariant(
+    null !== nextFlushedRoot,
+    "Should be working on a root. This error is likely caused by a bug in React. Please file an issue."
+  );
+  nextFlushedRoot.expirationTime = 0;
+  hasUnhandledError || ((hasUnhandledError = !0), (unhandledError = error));
+}
+function updateContainerAtExpirationTime(
+  element,
+  container,
+  parentComponent,
+  expirationTime,
+  callback
+) {
+  var current = container.current;
+  if (parentComponent) {
+    parentComponent = parentComponent._reactInternalFiber;
+    var parentContext;
+    b: {
+      invariant(
+        2 === isFiberMountedImpl(parentComponent) && 2 === parentComponent.tag,
+        "Expected subtree parent to be a mounted class component. This error is likely caused by a bug in React. Please file an issue."
+      );
+      for (parentContext = parentComponent; 3 !== parentContext.tag; ) {
+        if (isContextProvider(parentContext)) {
+          parentContext =
+            parentContext.stateNode.__reactInternalMemoizedMergedChildContext;
+          break b;
+        }
+        parentContext = parentContext.return;
+        invariant(
+          parentContext,
+          "Found unexpected detached subtree parent. This error is likely caused by a bug in React. Please file an issue."
+        );
+      }
+      parentContext = parentContext.stateNode.context;
+    }
+    parentComponent = isContextProvider(parentComponent)
+      ? processChildContext(parentComponent, parentContext)
+      : parentContext;
+  } else parentComponent = emptyObject;
+  null === container.context
+    ? (container.context = parentComponent)
+    : (container.pendingContext = parentComponent);
+  container = callback;
+  callback = createUpdate(expirationTime);
+  callback.payload = { element: element };
+  container = void 0 === container ? null : container;
+  null !== container && (callback.callback = container);
+  enqueueUpdate(current, callback, expirationTime);
+  scheduleWork(current, expirationTime);
+  return expirationTime;
+}
+function findHostInstance$1(component) {
+  var fiber = component._reactInternalFiber;
+  void 0 === fiber &&
+    ("function" === typeof component.render
+      ? invariant(!1, "Unable to find node on an unmounted component.")
+      : invariant(
+          !1,
+          "Argument appears to not be a ReactComponent. Keys: %s",
+          Object.keys(component)
+        ));
+  component = findCurrentHostFiber(fiber);
+  return null === component ? null : component.stateNode;
+}
+function updateContainer(element, container, parentComponent, callback) {
+  var current = container.current,
+    currentTime = recalculateCurrentTime();
+  current = computeExpirationForFiber(currentTime, current);
+  return updateContainerAtExpirationTime(
+    element,
+    container,
+    parentComponent,
+    current,
+    callback
+  );
+}
+function getPublicRootInstance(container) {
+  container = container.current;
+  if (!container.child) return null;
+  switch (container.child.tag) {
+    case 5:
+      return container.child.stateNode;
+    default:
+      return container.child.stateNode;
+  }
+}
+function injectIntoDevTools(devToolsConfig) {
+  var findFiberByHostInstance = devToolsConfig.findFiberByHostInstance;
+  return injectInternals(
+    Object.assign({}, devToolsConfig, {
+      findHostInstanceByFiber: function(fiber) {
+        fiber = findCurrentHostFiber(fiber);
+        return null === fiber ? null : fiber.stateNode;
+      },
+      findFiberByHostInstance: function(instance) {
+        return findFiberByHostInstance
+          ? findFiberByHostInstance(instance)
+          : null;
+      }
+    })
+  );
+}
+var ReactNativeFiberRenderer = {
+  updateContainerAtExpirationTime: updateContainerAtExpirationTime,
+  createContainer: function(containerInfo, isAsync, hydrate) {
+    return createFiberRoot(containerInfo, isAsync, hydrate);
+  },
+  updateContainer: updateContainer,
+  flushRoot: function(root, expirationTime) {
+    invariant(
+      !isRendering,
+      "work.commit(): Cannot commit while already rendering. This likely means you attempted to commit from inside a lifecycle method."
+    );
+    nextFlushedRoot = root;
+    nextFlushedExpirationTime = expirationTime;
+    performWorkOnRoot(root, expirationTime, !1);
+    performWork(1, null);
+    finishRendering();
+  },
+  requestWork: requestWork,
+  computeUniqueAsyncExpiration: function() {
+    var result =
+      2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
+    result <= lastUniqueAsyncExpiration &&
+      (result = lastUniqueAsyncExpiration + 1);
+    return (lastUniqueAsyncExpiration = result);
+  },
+  batchedUpdates: function(fn, a) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      return fn(a);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates) ||
+        isRendering ||
+        performWork(1, null);
+    }
+  },
+  unbatchedUpdates: function(fn, a) {
+    if (isBatchingUpdates && !isUnbatchingUpdates) {
+      isUnbatchingUpdates = !0;
+      try {
+        return fn(a);
+      } finally {
+        isUnbatchingUpdates = !1;
+      }
+    }
+    return fn(a);
+  },
+  deferredUpdates: function(fn) {
+    var previousExpirationContext = expirationContext;
+    expirationContext =
+      2 + 25 * ((((recalculateCurrentTime() - 2 + 500) / 25) | 0) + 1);
+    try {
+      return fn();
+    } finally {
+      expirationContext = previousExpirationContext;
+    }
+  },
+  syncUpdates: syncUpdates,
+  interactiveUpdates: function(fn, a, b) {
+    if (isBatchingInteractiveUpdates) return fn(a, b);
+    isBatchingUpdates ||
+      isRendering ||
+      0 === lowestPendingInteractiveExpirationTime ||
+      (performWork(lowestPendingInteractiveExpirationTime, null),
+      (lowestPendingInteractiveExpirationTime = 0));
+    var previousIsBatchingInteractiveUpdates = isBatchingInteractiveUpdates,
+      previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = isBatchingInteractiveUpdates = !0;
+    try {
+      return fn(a, b);
+    } finally {
+      (isBatchingInteractiveUpdates = previousIsBatchingInteractiveUpdates),
+        (isBatchingUpdates = previousIsBatchingUpdates) ||
+          isRendering ||
+          performWork(1, null);
+    }
+  },
+  flushInteractiveUpdates: function() {
+    isRendering ||
+      0 === lowestPendingInteractiveExpirationTime ||
+      (performWork(lowestPendingInteractiveExpirationTime, null),
+      (lowestPendingInteractiveExpirationTime = 0));
+  },
+  flushControlled: function(fn) {
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      syncUpdates(fn);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates) ||
+        isRendering ||
+        performWork(1, null);
+    }
+  },
+  flushSync: function(fn, a) {
+    invariant(
+      !isRendering,
+      "flushSync was called from inside a lifecycle method. It cannot be called when React is already rendering."
+    );
+    var previousIsBatchingUpdates = isBatchingUpdates;
+    isBatchingUpdates = !0;
+    try {
+      return syncUpdates(fn, a);
+    } finally {
+      (isBatchingUpdates = previousIsBatchingUpdates), performWork(1, null);
+    }
+  },
+  getPublicRootInstance: getPublicRootInstance,
+  findHostInstance: findHostInstance$1,
+  findHostInstanceWithNoPortals: function(fiber) {
+    fiber = findCurrentHostFiberWithNoPortals(fiber);
+    return null === fiber ? null : fiber.stateNode;
+  },
+  injectIntoDevTools: injectIntoDevTools
+};
+function createPortal(children, containerInfo, implementation) {
+  var key =
+    3 < arguments.length && void 0 !== arguments[3] ? arguments[3] : null;
+  return {
+    $$typeof: REACT_PORTAL_TYPE,
+    key: null == key ? null : "" + key,
+    children: children,
+    containerInfo: containerInfo,
+    implementation: implementation
+  };
+}
+function _inherits(subClass, superClass) {
+  if ("function" !== typeof superClass && null !== superClass)
+    throw new TypeError(
+      "Super expression must either be null or a function, not " +
+        typeof superClass
+    );
+  subClass.prototype = Object.create(superClass && superClass.prototype, {
+    constructor: {
+      value: subClass,
+      enumerable: !1,
+      writable: !0,
+      configurable: !0
+    }
+  });
+  superClass &&
+    (Object.setPrototypeOf
+      ? Object.setPrototypeOf(subClass, superClass)
+      : (subClass.__proto__ = superClass));
+}
+var getInspectorDataForViewTag = void 0;
+getInspectorDataForViewTag = function() {
+  invariant(!1, "getInspectorDataForViewTag() is not available in production");
+};
+function findNodeHandle(componentOrHandle) {
+  if (null == componentOrHandle) return null;
+  if ("number" === typeof componentOrHandle) return componentOrHandle;
+  if (componentOrHandle._nativeTag) return componentOrHandle._nativeTag;
+  if (componentOrHandle.canonical && componentOrHandle.canonical._nativeTag)
+    return componentOrHandle.canonical._nativeTag;
+  componentOrHandle = findHostInstance$1(componentOrHandle);
+  return null == componentOrHandle
+    ? componentOrHandle
+    : componentOrHandle.canonical
+      ? componentOrHandle.canonical._nativeTag
+      : componentOrHandle._nativeTag;
+}
+_batchedUpdates = ReactNativeFiberRenderer.batchedUpdates;
+_flushInteractiveUpdates = ReactNativeFiberRenderer.flushInteractiveUpdates;
+var roots = new Map(),
+  ReactNativeRenderer = {
+    NativeComponent: (function(findNodeHandle, findHostInstance) {
+      return (function(_React$Component) {
+        function ReactNativeComponent() {
+          if (!(this instanceof ReactNativeComponent))
+            throw new TypeError("Cannot call a class as a function");
+          var call = _React$Component.apply(this, arguments);
+          if (!this)
+            throw new ReferenceError(
+              "this hasn't been initialised - super() hasn't been called"
+            );
+          return !call ||
+            ("object" !== typeof call && "function" !== typeof call)
+            ? this
+            : call;
+        }
+        _inherits(ReactNativeComponent, _React$Component);
+        ReactNativeComponent.prototype.blur = function() {
+          TextInputState.blurTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.focus = function() {
+          TextInputState.focusTextInput(findNodeHandle(this));
+        };
+        ReactNativeComponent.prototype.measure = function(callback) {
+          UIManager.measure(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureInWindow = function(callback) {
+          UIManager.measureInWindow(
+            findNodeHandle(this),
+            mountSafeCallback(this, callback)
+          );
+        };
+        ReactNativeComponent.prototype.measureLayout = function(
+          relativeToNativeNode,
+          onSuccess,
+          onFail
+        ) {
+          UIManager.measureLayout(
+            findNodeHandle(this),
+            relativeToNativeNode,
+            mountSafeCallback(this, onFail),
+            mountSafeCallback(this, onSuccess)
+          );
+        };
+        ReactNativeComponent.prototype.setNativeProps = function(nativeProps) {
+          var maybeInstance = void 0;
+          try {
+            maybeInstance = findHostInstance(this);
+          } catch (error) {}
+          if (null != maybeInstance) {
+            var viewConfig =
+              maybeInstance.viewConfig || maybeInstance.canonical.viewConfig;
+            nativeProps = diffProperties(
+              null,
+              emptyObject$1,
+              nativeProps,
+              viewConfig.validAttributes
+            );
+            null != nativeProps &&
+              UIManager.updateView(
+                maybeInstance._nativeTag,
+                viewConfig.uiViewClassName,
+                nativeProps
+              );
+          }
+        };
+        return ReactNativeComponent;
+      })(React.Component);
+    })(findNodeHandle, findHostInstance$1),
+    findNodeHandle: findNodeHandle,
+    render: function(element, containerTag, callback) {
+      var root = roots.get(containerTag);
+      root ||
+        ((root = createFiberRoot(containerTag, !1, !1)),
+        roots.set(containerTag, root));
+      updateContainer(element, root, null, callback);
+      return getPublicRootInstance(root);
+    },
+    unmountComponentAtNode: function(containerTag) {
+      var root = roots.get(containerTag);
+      root &&
+        updateContainer(null, root, null, function() {
+          roots.delete(containerTag);
+        });
+    },
+    unmountComponentAtNodeAndRemoveContainer: function(containerTag) {
+      ReactNativeRenderer.unmountComponentAtNode(containerTag);
+      UIManager.removeRootView(containerTag);
+    },
+    createPortal: function(children, containerTag) {
+      return createPortal(
+        children,
+        containerTag,
+        null,
+        2 < arguments.length && void 0 !== arguments[2] ? arguments[2] : null
+      );
+    },
+    unstable_batchedUpdates: batchedUpdates,
+    __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED: {
+      NativeMethodsMixin: (function(findNodeHandle, findHostInstance) {
+        return {
+          measure: function(callback) {
+            UIManager.measure(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureInWindow: function(callback) {
+            UIManager.measureInWindow(
+              findNodeHandle(this),
+              mountSafeCallback(this, callback)
+            );
+          },
+          measureLayout: function(relativeToNativeNode, onSuccess, onFail) {
+            UIManager.measureLayout(
+              findNodeHandle(this),
+              relativeToNativeNode,
+              mountSafeCallback(this, onFail),
+              mountSafeCallback(this, onSuccess)
+            );
+          },
+          setNativeProps: function(nativeProps) {
+            var maybeInstance = void 0;
+            try {
+              maybeInstance = findHostInstance(this);
+            } catch (error) {}
+            if (null != maybeInstance) {
+              var viewConfig = maybeInstance.viewConfig;
+              nativeProps = diffProperties(
+                null,
+                emptyObject$1,
+                nativeProps,
+                viewConfig.validAttributes
+              );
+              null != nativeProps &&
+                UIManager.updateView(
+                  maybeInstance._nativeTag,
+                  viewConfig.uiViewClassName,
+                  nativeProps
+                );
+            }
+          },
+          focus: function() {
+            TextInputState.focusTextInput(findNodeHandle(this));
+          },
+          blur: function() {
+            TextInputState.blurTextInput(findNodeHandle(this));
+          }
+        };
+      })(findNodeHandle, findHostInstance$1),
+      computeComponentStackForErrorReporting: function(reactTag) {
+        return (reactTag = getInstanceFromTag(reactTag))
+          ? getStackAddendumByWorkInProgressFiber(reactTag)
+          : "";
+      }
+    }
+  };
+injectIntoDevTools({
+  findFiberByHostInstance: getInstanceFromTag,
+  getInspectorDataForViewTag: getInspectorDataForViewTag,
+  bundleType: 0,
+  version: "16.4.1",
+  rendererPackageName: "react-native-renderer"
+});
+var ReactNativeRenderer$2 = { default: ReactNativeRenderer },
+  ReactNativeRenderer$3 =
+    (ReactNativeRenderer$2 && ReactNativeRenderer) || ReactNativeRenderer$2;
+module.exports = ReactNativeRenderer$3.default
+  ? ReactNativeRenderer$3.default
+  : ReactNativeRenderer$3;
diff --git a/Libraries/Renderer/shims/ReactNativeComponentTree.js b/Libraries/Renderer/shims/ReactNativeComponentTree.js
deleted file mode 100644
index 702b621a5e46..000000000000
--- a/Libraries/Renderer/shims/ReactNativeComponentTree.js
+++ /dev/null
@@ -1,18 +0,0 @@
-/**
- * Copyright (c) 2013-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- * @flow
- */
-
-'use strict';
-
-const {
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED,
-} = require('ReactNative');
-
-module.exports =
-  __SECRET_INTERNALS_DO_NOT_USE_OR_YOU_WILL_BE_FIRED.ReactNativeComponentTree;
diff --git a/Libraries/Renderer/shims/ReactNativeTypes.js b/Libraries/Renderer/shims/ReactNativeTypes.js
index c38b0b44ebcf..991aa338e770 100644
--- a/Libraries/Renderer/shims/ReactNativeTypes.js
+++ b/Libraries/Renderer/shims/ReactNativeTypes.js
@@ -89,7 +89,6 @@ export type NativeMethodsMixinType = {
 
 type SecretInternalsType = {
   NativeMethodsMixin: NativeMethodsMixinType,
-  ReactNativeComponentTree: any,
   computeComponentStackForErrorReporting(tag: number): string,
   // TODO (bvaughn) Decide which additional types to expose here?
   // And how much information to fill in for the above types.
@@ -97,7 +96,6 @@ type SecretInternalsType = {
 
 type SecretInternalsFabricType = {
   NativeMethodsMixin: NativeMethodsMixinType,
-  ReactNativeComponentTree: any,
 };
 
 /**
diff --git a/package.json b/package.json
index f6d00306385f..e8f5a895c96d 100644
--- a/package.json
+++ b/package.json
@@ -143,7 +143,7 @@
     "react-native": "local-cli/wrong-react-native.js"
   },
   "peerDependencies": {
-    "react": "16.3.2"
+    "react": "16.4.1"
   },
   "dependencies": {
     "absolute-path": "^0.0.0",
@@ -216,8 +216,8 @@
     "jest": "23.1.0",
     "jest-junit": "4.0.0",
     "prettier": "1.13.4",
-    "react": "16.3.2",
-    "react-test-renderer": "16.3.2",
+    "react": "16.4.1",
+    "react-test-renderer": "16.4.1",
     "shelljs": "^0.7.8",
     "sinon": "^2.2.0"
   }

From 045688bc28ee08a722e2a1521d51f1f3293e46a2 Mon Sep 17 00:00:00 2001
From: Sho Ikeda <suicaicoca@gmail.com>
Date: Sat, 16 Jun 2018 01:28:35 -0700
Subject: [PATCH 0832/1109] Fix Stable release date of 0.58.0 (#19751)

Summary:
See https://github.com/facebook/react-native/pull/19715#discussion_r195620169 for the details.

hramos
Closes https://github.com/facebook/react-native/pull/19751

Differential Revision: D8466070

Pulled By: hramos

fbshipit-source-id: 569e84119ac927e393889ad2c2f38d2b982aa6e8
---
 Releases.md | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Releases.md b/Releases.md
index cd6948ae13e3..0e9492cfda0c 100644
--- a/Releases.md
+++ b/Releases.md
@@ -17,7 +17,7 @@ React Native follows a monthly release train. Every month, a new branch created
 |  ...    |       ...           |      ...         |
 | 0.56.0  | 1st of June         | 1st of July      |
 | 0.57.0  | 1st of July         | 1st of August    |
-| 0.58.0  | 1st of August       | 1st of October   |
+| 0.58.0  | 1st of August       | 1st of September |
 | ...     | ...                 | ...              |
 
 -------------------

From 9e4a4323b19f78fe2b5b8c870156d9cb783d4455 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Sat, 16 Jun 2018 01:29:30 -0700
Subject: [PATCH 0833/1109] limit ndk jobs for RNTester on CI (#19755)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
Limit number of NDK jobs of ReactAndroid on CI using $BUILD_THREADS environment variable. Otherwise, it was spawning 32 jobs while building RNTester, which caused in OOM or unexpected failure.

CI: https://circleci.com/gh/dulmandakh/react-native/387

Android CI is green again 😍
Closes https://github.com/facebook/react-native/pull/19755

Differential Revision: D8466069

Pulled By: hramos

fbshipit-source-id: fd507d12c8e93f718e047719daa68aa25c37bfb2
---
 .circleci/config.yml | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 1985e9c89de4..2a459a0ba775 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -569,7 +569,7 @@ jobs:
       - run:
           name: Build Android RNTester
           command: |
-            ./gradlew RNTester:android:app:assembleRelease
+            ./gradlew RNTester:android:app:assembleRelease -Pjobs=$BUILD_THREADS
 
       # Collect Results
       - run: *collect-android-test-results

From 15f84420f0c53f53f11a93b609385ca741379898 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Sat, 16 Jun 2018 15:49:31 -0700
Subject: [PATCH 0834/1109] Enable CocoaPods tests, add parallelism (#19764)

Summary:
Enable CocoaPods test, iOS e2e.
Use parallelism to run several tests simultaneously within the same machine.

Circle CI
Closes https://github.com/facebook/react-native/pull/19764

Differential Revision: D8471955

Pulled By: hramos

fbshipit-source-id: c484fd6c66fb2d0d2305ced29e34cb305f73fb55
---
 .circleci/config.yml | 128 ++++++++++++++++++++++---------------------
 1 file changed, 65 insertions(+), 63 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 2a459a0ba775..5c79711b5d77 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -203,13 +203,17 @@ aliases:
   # eslint sometimes runs into trouble generating the reports
   - &run-lint-checks
     name: Lint code
-    command: scripts/circleci/exec_swallow_error.sh yarn lint --format junit -o ~/react-native/reports/junit/eslint/results.xml
-    when: always
+    command: |
+      if [ $((0 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        scripts/circleci/exec_swallow_error.sh yarn lint --format junit -o ~/react-native/reports/junit/eslint/results.xml
+      fi
 
   - &run-flow-checks
     name: Check for errors in code using Flow
-    command: yarn flow check
-    when: always
+    command: |
+      if [ $((0 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        yarn flow check
+      fi
 
   - &run-sanity-checks
     name: Sanity checks
@@ -281,31 +285,64 @@ aliases:
 
   - &boot-simulator-iphone
     name: Boot iPhone Simulator
-    command: xcrun simctl boot "iPhone 5s" || true
+    command: |
+      if [ $((0 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        xcrun simctl boot "iPhone 5s" || true
+      fi
 
   - &boot-simulator-appletv
     name: Boot Apple TV Simulator
-    command: xcrun simctl boot "Apple TV" || true
+    command: |
+      if [ $((1 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        xcrun simctl boot "Apple TV" || true
+      fi
 
   - &run-objc-ios-tests
     name: iOS Test Suite
-    command: ./scripts/objc-test-ios.sh test
+    command: |
+      if [ $((0 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        ./scripts/objc-test-ios.sh test
+      fi
 
   - &run-objc-tvos-tests
     name: tvOS Test Suite
-    command: ./scripts/objc-test-tvos.sh test
+    command: |
+      if [ $((1 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        ./scripts/objc-test-tvos.sh test
+      fi
+
+  - &run-podspec-tests
+    name: Test CocoaPods
+    command: |
+      if [ $((2 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        ./scripts/process-podspecs.sh
+      fi
 
   - &run-e2e-tests
     name: End-to-End Test Suite
-    command: node ./scripts/run-ci-e2e-tests.js --ios --tvos --js --retries 3;
+    command: node ./scripts/run-ci-e2e-tests.js --android --ios --tvos --js --retries 3;
 
   - &run-objc-ios-e2e-tests
     name: iOS End-to-End Test Suite
-    command: node ./scripts/run-ci-e2e-tests.js --ios --retries 3;
+    command: |
+      if [ $((0 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        node ./scripts/run-ci-e2e-tests.js --ios --retries 3;
+      fi
 
   - &run-objc-tvos-e2e-tests
     name: tvOS End-to-End Test Suite
-    command: node ./scripts/run-ci-e2e-tests.js --tvos --js --retries 3;
+    command: |
+      if [ $((1 % CIRCLE_NODE_TOTAL)) -eq "$CIRCLE_NODE_INDEX" ]; then
+        node ./scripts/run-ci-e2e-tests.js --tvos --js --retries 3;
+      fi
+
+  - &run-android-e2e-tests
+    name: Android End-to-End Test Suite
+    command: node ./scripts/run-ci-e2e-tests.js --android --retries 3;
+
+  - &run-js-e2e-tests
+    name: JavaScript End-to-End Test Suite
+    command: node ./scripts/run-ci-e2e-tests.js --js --retries 3;
 
 defaults: &defaults
   working_directory: ~/react-native
@@ -339,7 +376,6 @@ macos_defaults: &macos_defaults
 
 version: 2
 jobs:
-
   # Set up a Node environment for downstream jobs
   checkout_code:
     <<: *js_defaults
@@ -386,30 +422,21 @@ jobs:
       - store_test_results:
           path: ~/react-native/reports/junit
 
-  # Runs unit tests on iOS devices
-  test_ios:
+  # Runs unit tests on iOS and Apple TV devices
+  test_objc:
     <<: *macos_defaults
+    parallelism: 3
     steps:
       - attach_workspace:
           at: ~/react-native
 
       - run: *boot-simulator-iphone
-      - run: brew install watchman
-      - run: *run-objc-ios-tests
-
-      - store_test_results:
-          path: ~/react-native/reports/junit
-
-  # Runs unit tests on tvOS devices
-  test_tvos:
-    <<: *macos_defaults
-    steps:
-      - attach_workspace:
-          at: ~/react-native
-
       - run: *boot-simulator-appletv
       - run: brew install watchman
+
+      - run: *run-objc-ios-tests
       - run: *run-objc-tvos-tests
+      - run: *run-podspec-tests
 
       - store_test_results:
           path: ~/react-native/reports/junit
@@ -417,11 +444,13 @@ jobs:
   # Runs end to end tests
   test_end_to_end:
     <<: *macos_defaults
+    parallelism: 2
     steps:
       - attach_workspace:
           at: ~/react-native
 
       - run: *boot-simulator-iphone
+      - run: *boot-simulator-appletv
 
       - run:
           name: Configure Environment Variables
@@ -437,19 +466,12 @@ jobs:
             node -v
 
       - run: *run-objc-ios-e2e-tests
+      # Disabled for now
+      # - run: *run-objc-tvos-e2e-tests
 
       - store_test_results:
           path: ~/react-native/reports/junit
 
-  # Checks podspec
-  test_podspec:
-    <<: *macos_defaults
-    steps:
-      - attach_workspace:
-          at: ~/react-native
-
-      - run: ./scripts/process-podspecs.sh
-
   # Publishes new version onto npm
   publish_npm_package:
     <<: *android_defaults
@@ -571,6 +593,10 @@ jobs:
           command: |
             ./gradlew RNTester:android:app:assembleRelease -Pjobs=$BUILD_THREADS
 
+      # Run Android end-to-end tests
+      # Disabled
+      # - run: *run-android-e2e-tests
+
       # Collect Results
       - run: *collect-android-test-results
       - store_test_results:
@@ -626,7 +652,6 @@ workflows:
 
   tests:
     jobs:
-
       # Checkout repo and run Yarn
       - checkout_code:
           filters: *filter-ignore-gh-pages
@@ -650,11 +675,7 @@ workflows:
             - checkout_code
 
       # Test iOS & tvOS
-      - test_ios:
-          filters: *filter-ignore-gh-pages
-          requires:
-            - checkout_code
-      - test_tvos:
+      - test_objc:
           filters: *filter-ignore-gh-pages
           requires:
             - checkout_code
@@ -674,8 +695,8 @@ workflows:
               only: /v[0-9]+(\.[0-9]+)*(\-rc(\.[0-9]+)?)?/
           requires:
             - test_javascript
-            - test_ios
-            - test_tvos
+            - test_objc
+            - test_android
             - test_end_to_end
             - analyze
 
@@ -691,22 +712,3 @@ workflows:
           filters: *filter-ignore-master-stable
           requires:
             - checkout_code
-
-
-  # These tests are flaky or are yet to be fixed. They are placed on their own
-  # workflow to avoid marking benign PRs as broken.
-  # To run them, uncomment the entire block and open a PR (do not merge).
-  # Once a test is fixed, move the test definition to the 'tests' workflow.
-  # disabled_tests:
-  #   jobs:
-  #     # Checkout repo and run Yarn (pre-req, should succeed)
-  #     - checkout_code:
-  #         filters: *filter-ignore-gh-pages
-
-  #     # The following were DISABLED because they have not run since
-  #     # the migration from Travis, and they have broken since then,
-  #     # CocoaPods
-  #     - test_podspec:
-  #         filters: *filter-ignore-gh-pages
-  #         requires:
-  #           - checkout_code

From a7e8e72c511833dd250e2680eb7fdc53e43155b0 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sun, 17 Jun 2018 11:41:09 -0700
Subject: [PATCH 0835/1109] Moving more logs from Log -> Flog

Reviewed By: fkgozali

Differential Revision: D8433247

fbshipit-source-id: e666fbf2abb81697ba6fb508c149af8a1a2035f1
---
 .../com/facebook/react/fabric/FabricUIManager.java     |  1 -
 .../main/java/com/facebook/react/fabric/Scheduler.java |  6 +++---
 .../react/fabric/events/FabricEventEmitter.java        | 10 ++++------
 .../react/uimanager/NativeViewHierarchyManager.java    |  6 +++---
 4 files changed, 10 insertions(+), 13 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index d6b7fd97f5cb..7a3586df1651 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -20,7 +20,6 @@
 import com.facebook.infer.annotation.Assertions;
 import com.facebook.proguard.annotations.DoNotStrip;
 import com.facebook.react.bridge.JavaScriptContextHolder;
-import com.facebook.react.bridge.PerformanceCounter;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
index 9fb7bddb394d..fb199435f99b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/Scheduler.java
@@ -1,6 +1,6 @@
 package com.facebook.react.fabric;
 
-import android.util.Log;
+import com.facebook.common.logging.FLog;
 import com.facebook.react.bridge.ReactContext;
 import java.util.concurrent.ExecutorService;
 import java.util.concurrent.LinkedBlockingDeque;
@@ -56,7 +56,7 @@ public void run() {
               try {
                 work.run();
               } catch (Exception ex) {
-                Log.w(TAG, "Exception running work in JS.", ex);
+                FLog.w(TAG, "Exception running work in JS.", ex);
                 throw ex;
               }
             }
@@ -66,7 +66,7 @@ public void run() {
     } catch (RejectedExecutionException ex) {
       // This can happen if a Work is scheduled when the Scheduler is being shutdown.
       // For now, we log and do not take any action.
-      Log.i(TAG, "Unable to schedule task.");
+      FLog.i(TAG, "Unable to schedule task.");
     }
   }
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
index 0077b953dc45..4a705bb75055 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
@@ -15,8 +15,8 @@
 
 import android.annotation.TargetApi;
 import android.os.Build;
-import android.util.Log;
 import android.util.Pair;
+import com.facebook.common.logging.FLog;
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.WritableArray;
@@ -29,8 +29,6 @@
 import com.facebook.react.uimanager.IllegalViewOperationException;
 import com.facebook.react.uimanager.events.RCTEventEmitter;
 import java.io.Closeable;
-import java.io.IOException;
-import java.util.Arrays;
 import java.util.HashSet;
 import java.util.Set;
 import javax.annotation.Nullable;
@@ -54,7 +52,7 @@ public void receiveEvent(int reactTag, String eventName, @Nullable WritableMap p
       long eventTarget = mFabricUIManager.createEventTarget(reactTag);
       mScheduler.scheduleWork(new FabricUIManagerWork(eventTarget, eventName, params));
     } catch (IllegalViewOperationException e) {
-      Log.e(TAG, "Unable to emmit event for tag " + reactTag, e);
+      FLog.e(TAG, "Unable to emmit event for tag " + reactTag, e);
     }
   }
 
@@ -79,7 +77,7 @@ public void run() {
       try {
         mFabricUIManager.invoke(mEventTarget, mEventName, mParams);
       } catch (Throwable t) {
-        Log.e(TAG, "Error sending event " + mEventName, t);
+        FLog.e(TAG, "Error sending event " + mEventName, t);
         //TODO: manage exception properly
       } finally{
         mFabricUIManager.releaseEventTarget(mEventTarget);
@@ -109,7 +107,7 @@ public void receiveTouches(String eventTopLevelType, WritableArray touches,
       int rootNodeID = 0;
       int target = nativeEvent.getInt(TARGET_KEY);
       if (target < 1) {
-        Log.e(TAG,"A view is reporting that a touch occurred on tag zero.");
+        FLog.e(TAG,"A view is reporting that a touch occurred on tag zero.");
       } else {
         rootNodeID = target;
       }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
index 8fe0c5cdd3dd..3e7d56a5e29f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/NativeViewHierarchyManager.java
@@ -10,7 +10,7 @@
 import android.annotation.TargetApi;
 import android.content.res.Resources;
 import android.os.Build;
-import android.util.Log;
+import com.facebook.common.logging.FLog;
 import android.util.SparseArray;
 import android.util.SparseBooleanArray;
 import android.view.Menu;
@@ -123,7 +123,7 @@ public synchronized void updateInstanceHandle(int tag, long instanceHandle) {
     try {
       updateInstanceHandle(resolveView(tag), instanceHandle);
     } catch (IllegalViewOperationException e) {
-      Log.e(TAG, "Unable to update properties for view tag " + tag, e);
+      FLog.e(TAG, "Unable to update properties for view tag " + tag, e);
     }
   }
 
@@ -138,7 +138,7 @@ public synchronized void updateProperties(int tag, ReactStylesDiffMap props) {
         viewManager.updateProperties(viewToUpdate, props);
       }
     } catch (IllegalViewOperationException e) {
-      Log.e(TAG, "Unable to update properties for view tag " + tag, e);
+      FLog.e(TAG, "Unable to update properties for view tag " + tag, e);
     }
   }
 

From 936de607b185c2c9411e5268a6ce4014ad179a79 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sun, 17 Jun 2018 11:41:10 -0700
Subject: [PATCH 0836/1109] Add support to receive null payload in events

Reviewed By: shergin

Differential Revision: D8439118

fbshipit-source-id: a45da18765d58f6e32d34e2e57f3a6a64daccf71
---
 .../main/java/com/facebook/react/fabric/FabricUIManager.java   | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 7a3586df1651..4cb25a51c7c6 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -639,6 +639,9 @@ public void invoke(long eventTarget, String name, WritableMap params) {
         TAG,
         "Dispatching event for target: " + eventTarget);
     }
+    if (params == null) {
+      params = new WritableNativeMap();
+    }
     mBinding.dispatchEventToTarget(mJSContext.get(), mEventHandlerPointer, eventTarget, name, (WritableNativeMap) params);
   }
 

From e15a7610840a3c7f91d153d86f631c1d2debbd0b Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sun, 17 Jun 2018 11:41:12 -0700
Subject: [PATCH 0837/1109] Add noop support for setJSResponder /
 clearJSReponder API methods

Reviewed By: fkgozali

Differential Revision: D8458980

fbshipit-source-id: 2411fb8106288f65cabdef12917d0f5086d1723a
---
 .../java/com/facebook/react/bridge/UIManager.java  |  5 +++++
 .../com/facebook/react/fabric/FabricUIManager.java | 14 ++++++++++++++
 .../facebook/react/uimanager/UIManagerModule.java  | 11 +++++++++++
 3 files changed, 30 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
index e1f778b8c30a..e08133ded256 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/UIManager.java
@@ -27,4 +27,9 @@ public interface UIManager extends JSIModule, PerformanceCounter {
    * @param commandArgs {@link ReadableArray} parameters associated with the command
    */
   void dispatchCommand(int reactTag, int commandId, @Nullable ReadableArray commandArgs);
+
+  void setJSResponder(int reactTag, boolean blockNativeResponder);
+
+  void clearJSResponder();
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 4cb25a51c7c6..d72e6cc8b45f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -10,6 +10,7 @@
 import static android.view.View.MeasureSpec.AT_MOST;
 import static android.view.View.MeasureSpec.EXACTLY;
 import static android.view.View.MeasureSpec.UNSPECIFIED;
+import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
 import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 
 import android.os.SystemClock;
@@ -21,6 +22,7 @@
 import com.facebook.proguard.annotations.DoNotStrip;
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
+import com.facebook.react.bridge.ReactMethod;
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.ReadableNativeMap;
@@ -39,11 +41,13 @@
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.ReactStylesDiffMap;
 import com.facebook.react.uimanager.ThemedReactContext;
+import com.facebook.react.uimanager.UIManagerHelper;
 import com.facebook.react.uimanager.UIViewOperationQueue;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
+import com.facebook.react.uimanager.common.ViewUtil;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.systrace.Systrace;
 import com.facebook.systrace.SystraceMessage;
@@ -645,6 +649,16 @@ public void invoke(long eventTarget, String name, WritableMap params) {
     mBinding.dispatchEventToTarget(mJSContext.get(), mEventHandlerPointer, eventTarget, name, (WritableNativeMap) params);
   }
 
+  @Override
+  public void setJSResponder(int reactTag, boolean blockNativeResponder) {
+    // TODO: Do nothing for now
+  }
+
+  @Override
+  public void clearJSResponder() {
+    // TODO: Do nothing for now
+  }
+
   @Override
   public void initialize() {
     FabricEventEmitter eventEmitter =
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index f35511c3395b..1ac393b06fa7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -10,6 +10,7 @@
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_END;
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_START;
 import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
+import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 
 import android.content.ComponentCallbacks2;
 import android.content.Context;
@@ -39,6 +40,7 @@
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
+import com.facebook.react.uimanager.common.UIManagerType;
 import com.facebook.react.uimanager.common.ViewUtil;
 import com.facebook.react.uimanager.debug.NotThreadSafeViewHierarchyUpdateDebugListener;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -585,11 +587,20 @@ public void removeAnimation(int reactTag, int animationID) {
     mUIImplementation.removeAnimation(reactTag, animationID);
   }
 
+  @Override
   @ReactMethod
   public void setJSResponder(int reactTag, boolean blockNativeResponder) {
+    //TODO: this is a temporary approach to support ViewManagerCommands in Fabric until
+    // the dispatchViewManagerCommand() method is supported by Fabric JS API.
+    int uiManagerType = ViewUtil.getUIManagerType(reactTag);
+    if (uiManagerType != DEFAULT) {
+      UIManagerHelper.getUIManager(getReactApplicationContext(), uiManagerType).setJSResponder(reactTag, blockNativeResponder);
+    }
+
     mUIImplementation.setJSResponder(reactTag, blockNativeResponder);
   }
 
+  @Override
   @ReactMethod
   public void clearJSResponder() {
     mUIImplementation.clearJSResponder();

From e23a91e67bd4c9b51c0415fd784ba12b35ea8e97 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 17 Jun 2018 21:35:51 -0700
Subject: [PATCH 0838/1109] `Invalid JS responder` error was promoted to
 warning

Summary:
Given async nature of RN, it is quite possible situation, hence it should not be a redbox.
And in Fabric it happends all the time which makes debugging painful.

Reviewed By: mdvacca

Differential Revision: D8473511

fbshipit-source-id: cfe7a1d3d105fde3b23db4c4c07b99864215c94c
---
 React/Modules/RCTUIManager.m | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/Modules/RCTUIManager.m b/React/Modules/RCTUIManager.m
index 49b0f774e3cd..217c43a481b2 100644
--- a/React/Modules/RCTUIManager.m
+++ b/React/Modules/RCTUIManager.m
@@ -1473,7 +1473,7 @@ static void RCTMeasureLayout(RCTShadowView *view,
   [self addUIBlock:^(__unused RCTUIManager *uiManager, NSDictionary<NSNumber *, UIView *> *viewRegistry) {
     _jsResponder = viewRegistry[reactTag];
     if (!_jsResponder) {
-      RCTLogError(@"Invalid view set to be the JS responder - tag %@", reactTag);
+      RCTLogWarn(@"Invalid view set to be the JS responder - tag %@", reactTag);
     }
   }];
 }

From 3b20a1670309bca79f81c50156726419608b59e8 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 17 Jun 2018 21:35:53 -0700
Subject: [PATCH 0839/1109] Fabric: Fixed error in parsing `position` style

Summary: This style/prop is called `position` (not `positionType`) in RN/JS API.

Reviewed By: mdvacca

Differential Revision: D8473509

fbshipit-source-id: f381189e05e6b618f3c74f1bc4610e737981b388
---
 ReactCommon/fabric/view/propsConversions.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/view/propsConversions.h b/ReactCommon/fabric/view/propsConversions.h
index b21ccbcae1b6..8a8cfe099a59 100644
--- a/ReactCommon/fabric/view/propsConversions.h
+++ b/ReactCommon/fabric/view/propsConversions.h
@@ -53,7 +53,7 @@ static YGStyle convertRawProp(const RawProps &rawProps, const YGStyle &defaultVa
   yogaStyle.alignContent = convertRawProp(rawProps, "alignContent", defaultValue.alignContent);
   yogaStyle.alignItems = convertRawProp(rawProps, "alignItems", defaultValue.alignItems);
   yogaStyle.alignSelf = convertRawProp(rawProps, "alignSelf", defaultValue.alignSelf);
-  yogaStyle.positionType = convertRawProp(rawProps, "positionType", defaultValue.positionType);
+  yogaStyle.positionType = convertRawProp(rawProps, "position", defaultValue.positionType);
   yogaStyle.flexWrap = convertRawProp(rawProps, "flexWrap", defaultValue.flexWrap);
   yogaStyle.overflow = convertRawProp(rawProps, "overflow", defaultValue.overflow);
   yogaStyle.display = convertRawProp(rawProps, "display", defaultValue.display);

From dca2067b71a62466194f4b58b89bf54d9ca362a2 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 17 Jun 2018 21:35:55 -0700
Subject: [PATCH 0840/1109] Fabric: Fixed error in parsing
 translateX/translateY prop

Summary: Quite trivial.

Reviewed By: mdvacca

Differential Revision: D8473513

fbshipit-source-id: 5d20244cbaae5ea69c79379e9894adb05cef2eb5
---
 ReactCommon/fabric/view/conversions.h | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/view/conversions.h b/ReactCommon/fabric/view/conversions.h
index 10dc24de7767..e3fd02eada90 100644
--- a/ReactCommon/fabric/view/conversions.h
+++ b/ReactCommon/fabric/view/conversions.h
@@ -262,9 +262,9 @@ inline void fromDynamic(const folly::dynamic &value, Transform &result) {
     } else if (operation == "translate") {
       transformMatrix = transformMatrix * Transform::Translate(parameters[0].asDouble(), parameters[1].asDouble(), 0);
     } else if (operation == "translateX") {
-      transformMatrix = transformMatrix * Transform::Translate(parameters[0].asDouble(), 0, 0);
+      transformMatrix = transformMatrix * Transform::Translate(parameters.asDouble(), 0, 0);
     } else if (operation == "translateY") {
-      transformMatrix = transformMatrix * Transform::Translate(0, parameters[0].asDouble(), 0);
+      transformMatrix = transformMatrix * Transform::Translate(0, parameters.asDouble(), 0);
     } else if (operation == "skewX") {
       transformMatrix = transformMatrix * Transform::Skew(parameters.asDouble(), 0);
     } else if (operation == "skewY") {

From c1e0ea9d38fa4e1a440b212244eac8bcac87e280 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 17 Jun 2018 21:35:57 -0700
Subject: [PATCH 0841/1109] Fabric: Fixed erratum in "borderRadius" prop name

Summary: Trivial.

Reviewed By: mdvacca

Differential Revision: D8473506

fbshipit-source-id: ce2888edc1052f39a042904c02b3ac347feedbba
---
 ReactCommon/fabric/view/ViewProps.cpp | 2 +-
 ReactCommon/fabric/view/ViewProps.h   | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index 5a123f9c99d2..b6d37f5f02ff 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -25,7 +25,7 @@ ViewProps::ViewProps(const ViewProps &sourceProps, const RawProps &rawProps):
   foregroundColor(convertRawProp(rawProps, "foregroundColor", sourceProps.foregroundColor)),
   backgroundColor(convertRawProp(rawProps, "backgroundColor", sourceProps.backgroundColor)),
   borderWidth(convertRawProp(rawProps, "borderWidth", sourceProps.borderWidth)),
-  borderRadus(convertRawProp(rawProps, "borderRadus", sourceProps.borderRadus)),
+  borderRadius(convertRawProp(rawProps, "borderRadius", sourceProps.borderRadius)),
   borderColor(convertRawProp(rawProps, "borderColor", sourceProps.borderColor)),
   borderStyle(convertRawProp(rawProps, "borderStyle", sourceProps.borderStyle)),
   shadowColor(convertRawProp(rawProps, "shadowColor", sourceProps.shadowColor)),
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
index 472966e6e700..5806f1eb320f 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -41,7 +41,7 @@ class ViewProps:
 
   // Borders
   const EdgeInsets borderWidth {};
-  const CornerInsets borderRadus {};
+  const CornerInsets borderRadius {};
   const SharedColor borderColor {};
   const BorderStyle borderStyle {};
 

From d92601be05457d3bbe436f9362aa283e817e1b15 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 17 Jun 2018 21:36:00 -0700
Subject: [PATCH 0842/1109] Fabric: Improved parsing EdgeInsets and
 CornerInsets styles

Summary: In case if it's just a number, it is treated as unified insets now.

Reviewed By: mdvacca

Differential Revision: D8473510

fbshipit-source-id: 1034377bc3e4abe55778c2f182360345419f00d5
---
 ReactCommon/fabric/graphics/conversions.h | 10 ++++++++++
 1 file changed, 10 insertions(+)

diff --git a/ReactCommon/fabric/graphics/conversions.h b/ReactCommon/fabric/graphics/conversions.h
index 7c79d0b38d39..d2adc857c03f 100644
--- a/ReactCommon/fabric/graphics/conversions.h
+++ b/ReactCommon/fabric/graphics/conversions.h
@@ -84,6 +84,11 @@ inline void fromDynamic(const folly::dynamic &value, Size &result) {
 }
 
 inline void fromDynamic(const folly::dynamic &value, EdgeInsets &result) {
+  if (value.isNumber()) {
+    const Float number = value.asDouble();
+    result = EdgeInsets {number, number, number, number};
+    return;
+  }
   if (value.isObject()) {
     result = EdgeInsets {
       (Float)value["top"].asDouble(),
@@ -106,6 +111,11 @@ inline void fromDynamic(const folly::dynamic &value, EdgeInsets &result) {
 }
 
 inline void fromDynamic(const folly::dynamic &value, CornerInsets &result) {
+  if (value.isNumber()) {
+    const Float number = value.asDouble();
+    result = CornerInsets {number, number, number, number};
+    return;
+  }
   if (value.isObject()) {
     result = CornerInsets {
       (Float)value["topLeft"].asDouble(),

From 310a2850c55fef194d54fcb7ea4649ed0e800deb Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 17 Jun 2018 21:36:02 -0700
Subject: [PATCH 0843/1109] Fabric: Universal `fromDynamic` for
 `std::vector<...>`

Summary:
Now, if `fromDynamic` is defined for some type, `fromDynamic` for `std::vector` of this type is also will be defined.
We need this for parsing `ImageSources` (a vector of `ImageSource`) type.

Reviewed By: fkgozali

Differential Revision: D8473508

fbshipit-source-id: d8dc8e3a3273f35b76c7132c553130762f768394
---
 ReactCommon/fabric/core/propsConversions.h | 10 ++++++++++
 1 file changed, 10 insertions(+)

diff --git a/ReactCommon/fabric/core/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
index bf2f96f6c908..0c259129d0ed 100644
--- a/ReactCommon/fabric/core/propsConversions.h
+++ b/ReactCommon/fabric/core/propsConversions.h
@@ -24,6 +24,16 @@ inline void fromDynamic(const folly::dynamic &value, int &result) {
 }
 inline void fromDynamic(const folly::dynamic &value, std::string &result) { result = value.getString(); }
 
+template <typename T>
+inline void fromDynamic(const folly::dynamic &value, std::vector<T> &result) {
+  result.clear();
+  T itemResult;
+  for (auto &itemValue : value) {
+    fromDynamic(itemValue, itemResult);
+    result.push_back(itemResult);
+  }
+}
+
 template <typename T>
 inline T convertRawProp(
   const RawProps &rawProps,

From a1302392577789faab79dad0cb39b147464e0e42 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Micha=C5=82=20Mokijewski?= <hello@naf.gl>
Date: Sun, 17 Jun 2018 22:52:00 -0700
Subject: [PATCH 0844/1109] Make run-ios command play nicely with multiple
 Xcode versions (#19781)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
I started using Xcode 10 beta and spotted that even though react-native cli is using cli tools from Xcode 10 for building it tries to open simulator from Xcode 9.4. Turned out that path to simulator app is hardcoded and doesn’t care about active developer directory.

1. You have to have more than one Xcode version (ie. 9.4 and 10 beta).
2. Change active developer directory to Xcode beta (`xcode-select -s /Applications/Xcode-beta.app/Contents/Developer`).
3. Without fix `react-native run-ios` will open simulator from Xcode 9.4, with fix it'll open simulator from active developer directory.

[CLI][IOS] [BUGFIX] [./local-cli] - use simulator from active developer directory
Closes https://github.com/facebook/react-native/pull/19781

Differential Revision: D8475915

Pulled By: TheSavior

fbshipit-source-id: d607f1f9eb9e565d4a017c21de50b5e569d171f9
---
 local-cli/runIOS/runIOS.js | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/local-cli/runIOS/runIOS.js b/local-cli/runIOS/runIOS.js
index f78700fffbc1..dfabb92b894a 100644
--- a/local-cli/runIOS/runIOS.js
+++ b/local-cli/runIOS/runIOS.js
@@ -160,8 +160,11 @@ function runOnSimulator(xcodeProject, args, scheme) {
      * it will not boot the "default" device, but the one we set. If the app is already running,
      * this flag has no effect.
      */
+    const activeDeveloperDir = child_process
+      .execFileSync('xcode-select', ['-p'], {encoding: 'utf8'})
+      .trim();
     child_process.execFileSync('open', [
-      '/Applications/Xcode.app/Contents/Developer/Applications/Simulator.app',
+      `${activeDeveloperDir}/Applications/Simulator.app`,
       '--args',
       '-CurrentDeviceUDID',
       selectedSimulator.udid,

From 2f53573d4f6eb529dee23236cf67b438e0256665 Mon Sep 17 00:00:00 2001
From: Dmitry Zakharov <comfly@fb.com>
Date: Mon, 18 Jun 2018 07:37:23 -0700
Subject: [PATCH 0845/1109] Fix Modules concurrent access

Reviewed By: fkgozali

Differential Revision: D8379392

fbshipit-source-id: 72495950ea5fcf37f5b1cc3413666879dfc81e5c
---
 React/Base/RCTBridge.m | 12 ++++++++++--
 1 file changed, 10 insertions(+), 2 deletions(-)

diff --git a/React/Base/RCTBridge.m b/React/Base/RCTBridge.m
index 4f85966d9712..f62074723c58 100644
--- a/React/Base/RCTBridge.m
+++ b/React/Base/RCTBridge.m
@@ -34,9 +34,14 @@
 NSString *const RCTBridgeDidDownloadScriptNotificationBridgeDescriptionKey = @"bridgeDescription";
 
 static NSMutableArray<Class> *RCTModuleClasses;
+static dispatch_queue_t RCTModuleClassesSyncQueue;
 NSArray<Class> *RCTGetModuleClasses(void)
 {
-  return RCTModuleClasses;
+  __block NSArray<Class> *result;
+  dispatch_sync(RCTModuleClassesSyncQueue, ^{
+    result = [RCTModuleClasses copy];
+  });
+  return result;
 }
 
 void RCTFBQuickPerformanceLoggerConfigureHooks(__unused JSGlobalContextRef ctx) { }
@@ -51,6 +56,7 @@ void RCTRegisterModule(Class moduleClass)
   static dispatch_once_t onceToken;
   dispatch_once(&onceToken, ^{
     RCTModuleClasses = [NSMutableArray new];
+    RCTModuleClassesSyncQueue = dispatch_queue_create("com.facebook.react.ModuleClassesSyncQueue", DISPATCH_QUEUE_CONCURRENT);
   });
 
   RCTAssert([moduleClass conformsToProtocol:@protocol(RCTBridgeModule)],
@@ -58,7 +64,9 @@ void RCTRegisterModule(Class moduleClass)
             moduleClass);
 
   // Register module
-  [RCTModuleClasses addObject:moduleClass];
+  dispatch_barrier_async(RCTModuleClassesSyncQueue, ^{
+    [RCTModuleClasses addObject:moduleClass];
+  });
 }
 
 /**

From 59b5743187c7df080c83634134a825e50ca0c3b2 Mon Sep 17 00:00:00 2001
From: Pavlos Vinieratos <pvinis@mac-pro.localdomain>
Date: Mon, 18 Jun 2018 10:52:30 -0700
Subject: [PATCH 0846/1109] Update Xcode projects (#19574)

Summary:
A few people have been complaining, including me, that when we compile a react native project, there are a lot of warnings from xcode, suggesting to update the project build settings to the new recommendations.

I took the liberty to actually update the xcode projects, so we can finally have these gone, as well as replace some deprecated methods with the new suggested ones.

I made two react native projects, one with the regular react native and the other one using this branch.
Left is before, right is after:
![screen shot 2018-06-05 at 15 44 34](https://user-images.githubusercontent.com/100233/40979899-6aba12da-68d7-11e8-8630-6c3009b6dc24.png)

[IOS] [MINOR] [Xcode] - updated the Xcode projects with the latest suggestions from Xcode 9.3, and replaced a few deprecated methods of iOS with their new replacements.
Closes https://github.com/facebook/react-native/pull/19574

Differential Revision: D8489006

Pulled By: hramos

fbshipit-source-id: 2922b2e76aca6883c4f5d04e9c511b9fc1029583
---
 Libraries/ART/ART.xcodeproj/project.pbxproj   | 25 ++++++++++++++++-
 .../RCTActionSheet.xcodeproj/project.pbxproj  | 25 ++++++++++++++++-
 .../Blob/RCTBlob.xcodeproj/project.pbxproj    | 22 ++++++++++++++-
 .../RCTCameraRoll.xcodeproj/project.pbxproj   | 23 +++++++++++++++-
 .../RCTGeolocation.xcodeproj/project.pbxproj  | 23 +++++++++++++++-
 .../Image/RCTImage.xcodeproj/project.pbxproj  | 16 ++++++++++-
 .../RCTLinking.xcodeproj/project.pbxproj      | 23 +++++++++++++++-
 .../RCTAnimation.xcodeproj/project.pbxproj    | 22 ++++++++++++++-
 .../RCTNetwork.xcodeproj/project.pbxproj      | 16 ++++++++++-
 .../project.pbxproj                           | 23 +++++++++++++++-
 .../RCTTest/RCTTest.xcodeproj/project.pbxproj | 23 +++++++++++++++-
 .../RCTSettings.xcodeproj/project.pbxproj     | 23 +++++++++++++++-
 .../Text/RCTText.xcodeproj/project.pbxproj    | 27 ++++++++++++++++---
 .../RCTVibration.xcodeproj/project.pbxproj    | 23 +++++++++++++++-
 .../RCTWebSocket.xcodeproj/project.pbxproj    | 21 ++++++++++++++-
 RNTester/RNTester.xcodeproj/project.pbxproj   | 14 +++++++++-
 .../xcschemes/RNTester-tvOS.xcscheme          |  2 +-
 .../xcshareddata/xcschemes/RNTester.xcscheme  |  2 +-
 .../RNTesterPods.xcodeproj/project.pbxproj    | 14 +++++++++-
 React/React.xcodeproj/project.pbxproj         | 22 +++++++++++----
 20 files changed, 363 insertions(+), 26 deletions(-)

diff --git a/Libraries/ART/ART.xcodeproj/project.pbxproj b/Libraries/ART/ART.xcodeproj/project.pbxproj
index b1cafee230d1..2aec17b1d792 100644
--- a/Libraries/ART/ART.xcodeproj/project.pbxproj
+++ b/Libraries/ART/ART.xcodeproj/project.pbxproj
@@ -245,7 +245,7 @@
 		0CF68AB91AF0540F00FF9E5C /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0620;
+				LastUpgradeCheck = 0940;
 				TargetAttributes = {
 					0CF68AC01AF0540F00FF9E5C = {
 						CreatedOnToolsVersion = 6.2;
@@ -336,19 +336,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -377,19 +389,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_UNDECLARED_SELECTOR = YES;
diff --git a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
index a639137bb7bb..c71f89bdd8c4 100644
--- a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
+++ b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B511DA1A9E6C8500147676 = {
@@ -106,19 +106,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -153,19 +165,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj b/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
index 316c157dec50..8bb32fec7b57 100755
--- a/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
+++ b/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
@@ -145,7 +145,7 @@
 		358F4ECF1D1E81A9004DF814 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0730;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					358F4ED61D1E81A9004DF814 = {
@@ -206,13 +206,23 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
@@ -251,13 +261,23 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
diff --git a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
index 1132021a60d4..618dbab44ae8 100644
--- a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
+++ b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
@@ -100,7 +100,7 @@
 		58B511551A9E6B3D00147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B5115C1A9E6B3D00147676 = {
@@ -148,20 +148,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -197,20 +208,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj b/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
index b1e18399c683..c0754118087a 100644
--- a/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
+++ b/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B511DA1A9E6C8500147676 = {
@@ -106,20 +106,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -154,20 +165,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Image/RCTImage.xcodeproj/project.pbxproj b/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
index 0af0af8f1ee6..bbf4d7104224 100644
--- a/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
+++ b/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
@@ -251,7 +251,7 @@
 		58B511551A9E6B3D00147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0810;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28391D9B042B00D4039D = {
@@ -365,15 +365,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -417,15 +424,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj b/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
index b56dcc67b984..34003d2a6016 100644
--- a/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
+++ b/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
@@ -79,7 +79,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28461D9B043800D4039D = {
@@ -171,20 +171,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -218,20 +229,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_SHADOW = YES;
diff --git a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
index f17225d61632..d74745fb037b 100644
--- a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
+++ b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
@@ -409,7 +409,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0730;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A281F1D9B03D100D4039D = {
@@ -534,14 +534,23 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
@@ -549,6 +558,7 @@
 				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -584,20 +594,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj b/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
index e5a2fc78cfb0..20cf3cf1dcdc 100644
--- a/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
+++ b/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
@@ -109,7 +109,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0810;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28531D9B044C00D4039D = {
@@ -211,15 +211,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -263,15 +270,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj b/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
index e709c21454fe..7bca7034655f 100644
--- a/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
+++ b/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
@@ -121,7 +121,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					3D05745E1DE6004600184BB4 = {
@@ -217,20 +217,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = "DEBUG=1";
 				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
@@ -262,20 +273,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_PREPROCESSOR_DEFINITIONS = "";
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
diff --git a/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj b/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
index f2c7c371cd81..e3f848a5cb27 100644
--- a/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
+++ b/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
@@ -192,7 +192,7 @@
 		580C37671AB104AF0015E709 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A286D1D9B047700D4039D = {
@@ -296,20 +296,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -344,20 +355,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj b/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
index fd0b9c5e4e47..2366798e5856 100644
--- a/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
+++ b/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
@@ -79,7 +79,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28601D9B046600D4039D = {
@@ -171,20 +171,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -219,20 +230,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Text/RCTText.xcodeproj/project.pbxproj b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
index c882c8843e3c..d3205e5ee16e 100644
--- a/Libraries/Text/RCTText.xcodeproj/project.pbxproj
+++ b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
@@ -103,9 +103,9 @@
 		5956B1A6200FF35C008D9D16 /* RCTUITextField.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B103200FEBA9008D9D16 /* RCTUITextField.m */; };
 		5956B1A7200FF35C008D9D16 /* RCTVirtualTextShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */; };
 		5956B1A8200FF35C008D9D16 /* RCTVirtualTextViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12B200FEBAA008D9D16 /* RCTVirtualTextViewManager.m */; };
-		5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */; };
 		5970936920845EFC00D163A7 /* RCTTextTransform.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5970936820845DDE00D163A7 /* RCTTextTransform.h */; };
 		5970936A20845F0600D163A7 /* RCTTextTransform.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5970936820845DDE00D163A7 /* RCTTextTransform.h */; };
+		5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */; };
 		8F2807C7202D2B6B005D65E6 /* RCTInputAccessoryViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */; };
 		8F2807C8202D2B6B005D65E6 /* RCTInputAccessoryView.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */; };
 		8F2807C9202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C5202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m */; };
@@ -237,9 +237,9 @@
 		5956B12D200FEBAA008D9D16 /* RCTVirtualTextViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTVirtualTextViewManager.h; sourceTree = "<group>"; };
 		5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTVirtualTextShadowView.m; sourceTree = "<group>"; };
 		5956B12F200FEBAA008D9D16 /* RCTConvert+Text.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "RCTConvert+Text.m"; sourceTree = "<group>"; };
+		5970936820845DDE00D163A7 /* RCTTextTransform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTTextTransform.h; sourceTree = "<group>"; };
 		5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryShadowView.m; sourceTree = "<group>"; };
 		5C245F38205E216A00D936E9 /* RCTInputAccessoryShadowView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryShadowView.h; sourceTree = "<group>"; };
-		5970936820845DDE00D163A7 /* RCTTextTransform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTTextTransform.h; sourceTree = "<group>"; };
 		8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryViewManager.m; sourceTree = "<group>"; };
 		8F2807C2202D2B6A005D65E6 /* RCTInputAccessoryViewContent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryViewContent.h; sourceTree = "<group>"; };
 		8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryView.m; sourceTree = "<group>"; };
@@ -422,7 +422,7 @@
 		58B511931A9E6C1200147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A287A1D9B048500D4039D = {
@@ -562,20 +562,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -610,20 +621,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj b/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
index 46ee2d4a7fe8..4e0099553eed 100644
--- a/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
+++ b/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		832C81781AAF6DEF007FA2F7 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0620;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					832C817F1AAF6DEF007FA2F7 = {
@@ -105,20 +105,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -152,20 +163,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
index f5e60eb16698..406890ccc9f9 100644
--- a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
+++ b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
@@ -218,7 +218,7 @@
 		3C86DF3E1ADF2C930047B81A /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0630;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28871D9B049200D4039D = {
@@ -343,19 +343,29 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
 				GCC_NO_COMMON_BLOCKS = YES;
@@ -393,14 +403,23 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
diff --git a/RNTester/RNTester.xcodeproj/project.pbxproj b/RNTester/RNTester.xcodeproj/project.pbxproj
index 06921b5616f1..51cef6ad024e 100644
--- a/RNTester/RNTester.xcodeproj/project.pbxproj
+++ b/RNTester/RNTester.xcodeproj/project.pbxproj
@@ -1144,7 +1144,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0820;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					004D289D1AAF61C70097A701 = {
@@ -2091,7 +2091,9 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -2100,9 +2102,13 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -2159,7 +2165,9 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -2168,9 +2176,13 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
index 95e17856e3e5..0c3555d5cfc2 100644
--- a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
+++ b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <Scheme
-   LastUpgradeVersion = "0820"
+   LastUpgradeVersion = "0940"
    version = "1.3">
    <BuildAction
       parallelizeBuildables = "NO"
diff --git a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
index 93f81fdc17a4..b3d01b135672 100644
--- a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
+++ b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <Scheme
-   LastUpgradeVersion = "0820"
+   LastUpgradeVersion = "0940"
    version = "1.3">
    <BuildAction
       parallelizeBuildables = "NO"
diff --git a/RNTester/RNTesterPods.xcodeproj/project.pbxproj b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
index 0620810141cf..1802a7d7a733 100644
--- a/RNTester/RNTesterPods.xcodeproj/project.pbxproj
+++ b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
@@ -203,7 +203,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0820;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					13B07F861A680F5B00A75B9A = {
@@ -415,7 +415,9 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -424,9 +426,13 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -483,7 +489,9 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -492,9 +500,13 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index d008bf9e2145..b0b6cc74e336 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -265,7 +265,6 @@
 		2D16E68E1FA4FD3900B85C8A /* RCTTVNavigationEventEmitter.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D0B842D1EC0B51200B2BD8E /* RCTTVNavigationEventEmitter.h */; };
 		2D1D83CD1F74E2CE00615550 /* libprivatedata-tvOS.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 9936F32F1F5F2E5B0010BF04 /* libprivatedata-tvOS.a */; };
 		2D1D83CE1F74E2DA00615550 /* libdouble-conversion.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 3D383D621EBD27B9005632C8 /* libdouble-conversion.a */; };
-		2D1D83EF1F74E76C00615550 /* RCTModalManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 91076A871F743AB00081B4FA /* RCTModalManager.m */; };
 		2D3B5E931D9B087300451313 /* RCTErrorInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = 3EDCA8A41D3591E700450C31 /* RCTErrorInfo.m */; };
 		2D3B5E941D9B087900451313 /* RCTBundleURLProvider.m in Sources */ = {isa = PBXBuildFile; fileRef = 68EFE4ED1CF6EB3900A1DE13 /* RCTBundleURLProvider.m */; };
 		2D3B5E951D9B087C00451313 /* RCTAssert.m in Sources */ = {isa = PBXBuildFile; fileRef = 83CBBA4B1A601E3B00E9B192 /* RCTAssert.m */; };
@@ -334,7 +333,6 @@
 		2D3B5EF11D9B09E700451313 /* UIView+React.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E067541A70F44B002CDEE1 /* UIView+React.m */; };
 		2D74EAFA1DAE9590003B751B /* RCTMultipartDataTask.m in Sources */ = {isa = PBXBuildFile; fileRef = 006FC4131D9B20820057AAAD /* RCTMultipartDataTask.m */; };
 		2D8C2E331DA40441000EE098 /* RCTMultipartStreamReader.m in Sources */ = {isa = PBXBuildFile; fileRef = 001BFCCF1D8381DE008E587E /* RCTMultipartStreamReader.m */; };
-		2DCCC3151FE48142007C5315 /* RCTRedBoxExtraDataViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = FEFAAC9C1FDB89B40057BBE0 /* RCTRedBoxExtraDataViewController.m */; };
 		2DD0EFE11DA84F2800B0C975 /* RCTStatusBarManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 13723B4F1A82FD3C00F88898 /* RCTStatusBarManager.m */; };
 		352DCFF01D19F4C20056D623 /* RCTI18nUtil.m in Sources */ = {isa = PBXBuildFile; fileRef = 352DCFEF1D19F4C20056D623 /* RCTI18nUtil.m */; };
 		369123E11DDC75850095B341 /* RCTJSCSamplingProfiler.m in Sources */ = {isa = PBXBuildFile; fileRef = 369123E01DDC75850095B341 /* RCTJSCSamplingProfiler.m */; };
@@ -3974,7 +3972,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0810;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					139D7E871E25C6D100323FB7 = {
@@ -4232,7 +4230,6 @@
 				C606692F1F3CC60500E67165 /* RCTModuleMethod.mm in Sources */,
 				2D3B5E9F1D9B08AF00451313 /* RCTKeyCommands.m in Sources */,
 				2D3B5EA51D9B08C700451313 /* RCTRootView.m in Sources */,
-				2DCCC3151FE48142007C5315 /* RCTRedBoxExtraDataViewController.m in Sources */,
 				13134C871E296B2A00B9F3CB /* RCTCxxBridge.mm in Sources */,
 				CF2731C31E7B8DF30044CA4F /* RCTDeviceInfo.m in Sources */,
 				599FAA3F1FB274980058CCF6 /* RCTSurfaceRootShadowView.m in Sources */,
@@ -4272,7 +4269,6 @@
 				2D3B5EC61D9B095000451313 /* RCTProfileTrampoline-x86_64.S in Sources */,
 				2D3B5EA61D9B08CA00451313 /* RCTTouchEvent.m in Sources */,
 				2D8C2E331DA40441000EE098 /* RCTMultipartStreamReader.m in Sources */,
-				2D1D83EF1F74E76C00615550 /* RCTModalManager.m in Sources */,
 				59EDBCBC1FDF4E0C003573DE /* RCTScrollViewManager.m in Sources */,
 				59EDBCB01FDF4E0C003573DE /* RCTScrollContentView.m in Sources */,
 				2D3B5EF01D9B09E300451313 /* RCTWrapperViewController.m in Sources */,
@@ -5109,14 +5105,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -5165,14 +5169,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;

From aaddbee29ef93c20b6f881def680ba30ce344a58 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Mon, 18 Jun 2018 12:10:39 -0700
Subject: [PATCH 0847/1109] Revert D8489006: [react-native][PR] Update Xcode
 projects

Differential Revision:
D8489006

Original commit changeset: 2922b2e76aca

fbshipit-source-id: 84ba633b7e9a33b32e0a1347ebe6ca8bb1b02441
---
 Libraries/ART/ART.xcodeproj/project.pbxproj   | 25 +----------------
 .../RCTActionSheet.xcodeproj/project.pbxproj  | 25 +----------------
 .../Blob/RCTBlob.xcodeproj/project.pbxproj    | 22 +--------------
 .../RCTCameraRoll.xcodeproj/project.pbxproj   | 23 +---------------
 .../RCTGeolocation.xcodeproj/project.pbxproj  | 23 +---------------
 .../Image/RCTImage.xcodeproj/project.pbxproj  | 16 +----------
 .../RCTLinking.xcodeproj/project.pbxproj      | 23 +---------------
 .../RCTAnimation.xcodeproj/project.pbxproj    | 22 +--------------
 .../RCTNetwork.xcodeproj/project.pbxproj      | 16 +----------
 .../project.pbxproj                           | 23 +---------------
 .../RCTTest/RCTTest.xcodeproj/project.pbxproj | 23 +---------------
 .../RCTSettings.xcodeproj/project.pbxproj     | 23 +---------------
 .../Text/RCTText.xcodeproj/project.pbxproj    | 27 +++----------------
 .../RCTVibration.xcodeproj/project.pbxproj    | 23 +---------------
 .../RCTWebSocket.xcodeproj/project.pbxproj    | 21 +--------------
 RNTester/RNTester.xcodeproj/project.pbxproj   | 14 +---------
 .../xcschemes/RNTester-tvOS.xcscheme          |  2 +-
 .../xcshareddata/xcschemes/RNTester.xcscheme  |  2 +-
 .../RNTesterPods.xcodeproj/project.pbxproj    | 14 +---------
 React/React.xcodeproj/project.pbxproj         | 22 ++++-----------
 20 files changed, 26 insertions(+), 363 deletions(-)

diff --git a/Libraries/ART/ART.xcodeproj/project.pbxproj b/Libraries/ART/ART.xcodeproj/project.pbxproj
index 2aec17b1d792..b1cafee230d1 100644
--- a/Libraries/ART/ART.xcodeproj/project.pbxproj
+++ b/Libraries/ART/ART.xcodeproj/project.pbxproj
@@ -245,7 +245,7 @@
 		0CF68AB91AF0540F00FF9E5C /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0620;
 				TargetAttributes = {
 					0CF68AC01AF0540F00FF9E5C = {
 						CreatedOnToolsVersion = 6.2;
@@ -336,31 +336,19 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -389,30 +377,19 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_UNDECLARED_SELECTOR = YES;
diff --git a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
index c71f89bdd8c4..a639137bb7bb 100644
--- a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
+++ b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0610;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B511DA1A9E6C8500147676 = {
@@ -106,31 +106,19 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -165,30 +153,19 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj b/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
index 8bb32fec7b57..316c157dec50 100755
--- a/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
+++ b/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
@@ -145,7 +145,7 @@
 		358F4ECF1D1E81A9004DF814 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0730;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					358F4ED61D1E81A9004DF814 = {
@@ -206,23 +206,13 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
@@ -261,23 +251,13 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
diff --git a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
index 618dbab44ae8..1132021a60d4 100644
--- a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
+++ b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
@@ -100,7 +100,7 @@
 		58B511551A9E6B3D00147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0610;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B5115C1A9E6B3D00147676 = {
@@ -148,31 +148,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -208,30 +197,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj b/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
index c0754118087a..b1e18399c683 100644
--- a/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
+++ b/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0610;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B511DA1A9E6C8500147676 = {
@@ -106,31 +106,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -165,30 +154,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Image/RCTImage.xcodeproj/project.pbxproj b/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
index bbf4d7104224..0af0af8f1ee6 100644
--- a/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
+++ b/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
@@ -251,7 +251,7 @@
 		58B511551A9E6B3D00147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0810;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28391D9B042B00D4039D = {
@@ -365,22 +365,15 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -424,22 +417,15 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj b/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
index 34003d2a6016..b56dcc67b984 100644
--- a/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
+++ b/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
@@ -79,7 +79,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0610;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28461D9B043800D4039D = {
@@ -171,31 +171,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -229,30 +218,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_SHADOW = YES;
diff --git a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
index d74745fb037b..f17225d61632 100644
--- a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
+++ b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
@@ -409,7 +409,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0730;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A281F1D9B03D100D4039D = {
@@ -534,23 +534,14 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
@@ -558,7 +549,6 @@
 				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -594,30 +584,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj b/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
index 20cf3cf1dcdc..e5a2fc78cfb0 100644
--- a/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
+++ b/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
@@ -109,7 +109,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0810;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28531D9B044C00D4039D = {
@@ -211,22 +211,15 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -270,22 +263,15 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj b/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
index 7bca7034655f..e709c21454fe 100644
--- a/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
+++ b/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
@@ -121,7 +121,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0610;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					3D05745E1DE6004600184BB4 = {
@@ -217,31 +217,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = "DEBUG=1";
 				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
@@ -273,30 +262,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_PREPROCESSOR_DEFINITIONS = "";
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
diff --git a/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj b/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
index e3f848a5cb27..f2c7c371cd81 100644
--- a/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
+++ b/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
@@ -192,7 +192,7 @@
 		580C37671AB104AF0015E709 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0610;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A286D1D9B047700D4039D = {
@@ -296,31 +296,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -355,30 +344,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj b/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
index 2366798e5856..fd0b9c5e4e47 100644
--- a/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
+++ b/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
@@ -79,7 +79,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0610;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28601D9B046600D4039D = {
@@ -171,31 +171,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -230,30 +219,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Text/RCTText.xcodeproj/project.pbxproj b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
index d3205e5ee16e..c882c8843e3c 100644
--- a/Libraries/Text/RCTText.xcodeproj/project.pbxproj
+++ b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
@@ -103,9 +103,9 @@
 		5956B1A6200FF35C008D9D16 /* RCTUITextField.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B103200FEBA9008D9D16 /* RCTUITextField.m */; };
 		5956B1A7200FF35C008D9D16 /* RCTVirtualTextShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */; };
 		5956B1A8200FF35C008D9D16 /* RCTVirtualTextViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12B200FEBAA008D9D16 /* RCTVirtualTextViewManager.m */; };
+		5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */; };
 		5970936920845EFC00D163A7 /* RCTTextTransform.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5970936820845DDE00D163A7 /* RCTTextTransform.h */; };
 		5970936A20845F0600D163A7 /* RCTTextTransform.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5970936820845DDE00D163A7 /* RCTTextTransform.h */; };
-		5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */; };
 		8F2807C7202D2B6B005D65E6 /* RCTInputAccessoryViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */; };
 		8F2807C8202D2B6B005D65E6 /* RCTInputAccessoryView.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */; };
 		8F2807C9202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C5202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m */; };
@@ -237,9 +237,9 @@
 		5956B12D200FEBAA008D9D16 /* RCTVirtualTextViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTVirtualTextViewManager.h; sourceTree = "<group>"; };
 		5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTVirtualTextShadowView.m; sourceTree = "<group>"; };
 		5956B12F200FEBAA008D9D16 /* RCTConvert+Text.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "RCTConvert+Text.m"; sourceTree = "<group>"; };
-		5970936820845DDE00D163A7 /* RCTTextTransform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTTextTransform.h; sourceTree = "<group>"; };
 		5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryShadowView.m; sourceTree = "<group>"; };
 		5C245F38205E216A00D936E9 /* RCTInputAccessoryShadowView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryShadowView.h; sourceTree = "<group>"; };
+		5970936820845DDE00D163A7 /* RCTTextTransform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTTextTransform.h; sourceTree = "<group>"; };
 		8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryViewManager.m; sourceTree = "<group>"; };
 		8F2807C2202D2B6A005D65E6 /* RCTInputAccessoryViewContent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryViewContent.h; sourceTree = "<group>"; };
 		8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryView.m; sourceTree = "<group>"; };
@@ -422,7 +422,7 @@
 		58B511931A9E6C1200147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0610;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A287A1D9B048500D4039D = {
@@ -562,31 +562,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -621,30 +610,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj b/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
index 4e0099553eed..46ee2d4a7fe8 100644
--- a/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
+++ b/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		832C81781AAF6DEF007FA2F7 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0620;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					832C817F1AAF6DEF007FA2F7 = {
@@ -105,31 +105,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -163,30 +152,20 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
-				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
index 406890ccc9f9..f5e60eb16698 100644
--- a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
+++ b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
@@ -218,7 +218,7 @@
 		3C86DF3E1ADF2C930047B81A /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0630;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28871D9B049200D4039D = {
@@ -343,29 +343,19 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
-				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
 				GCC_NO_COMMON_BLOCKS = YES;
@@ -403,23 +393,14 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
-				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
-				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
diff --git a/RNTester/RNTester.xcodeproj/project.pbxproj b/RNTester/RNTester.xcodeproj/project.pbxproj
index 51cef6ad024e..06921b5616f1 100644
--- a/RNTester/RNTester.xcodeproj/project.pbxproj
+++ b/RNTester/RNTester.xcodeproj/project.pbxproj
@@ -1144,7 +1144,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0820;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					004D289D1AAF61C70097A701 = {
@@ -2091,9 +2091,7 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -2102,13 +2100,9 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -2165,9 +2159,7 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -2176,13 +2168,9 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
index 0c3555d5cfc2..95e17856e3e5 100644
--- a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
+++ b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <Scheme
-   LastUpgradeVersion = "0940"
+   LastUpgradeVersion = "0820"
    version = "1.3">
    <BuildAction
       parallelizeBuildables = "NO"
diff --git a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
index b3d01b135672..93f81fdc17a4 100644
--- a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
+++ b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <Scheme
-   LastUpgradeVersion = "0940"
+   LastUpgradeVersion = "0820"
    version = "1.3">
    <BuildAction
       parallelizeBuildables = "NO"
diff --git a/RNTester/RNTesterPods.xcodeproj/project.pbxproj b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
index 1802a7d7a733..0620810141cf 100644
--- a/RNTester/RNTesterPods.xcodeproj/project.pbxproj
+++ b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
@@ -203,7 +203,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0820;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					13B07F861A680F5B00A75B9A = {
@@ -415,9 +415,7 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -426,13 +424,9 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -489,9 +483,7 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -500,13 +492,9 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index b0b6cc74e336..d008bf9e2145 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -265,6 +265,7 @@
 		2D16E68E1FA4FD3900B85C8A /* RCTTVNavigationEventEmitter.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D0B842D1EC0B51200B2BD8E /* RCTTVNavigationEventEmitter.h */; };
 		2D1D83CD1F74E2CE00615550 /* libprivatedata-tvOS.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 9936F32F1F5F2E5B0010BF04 /* libprivatedata-tvOS.a */; };
 		2D1D83CE1F74E2DA00615550 /* libdouble-conversion.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 3D383D621EBD27B9005632C8 /* libdouble-conversion.a */; };
+		2D1D83EF1F74E76C00615550 /* RCTModalManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 91076A871F743AB00081B4FA /* RCTModalManager.m */; };
 		2D3B5E931D9B087300451313 /* RCTErrorInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = 3EDCA8A41D3591E700450C31 /* RCTErrorInfo.m */; };
 		2D3B5E941D9B087900451313 /* RCTBundleURLProvider.m in Sources */ = {isa = PBXBuildFile; fileRef = 68EFE4ED1CF6EB3900A1DE13 /* RCTBundleURLProvider.m */; };
 		2D3B5E951D9B087C00451313 /* RCTAssert.m in Sources */ = {isa = PBXBuildFile; fileRef = 83CBBA4B1A601E3B00E9B192 /* RCTAssert.m */; };
@@ -333,6 +334,7 @@
 		2D3B5EF11D9B09E700451313 /* UIView+React.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E067541A70F44B002CDEE1 /* UIView+React.m */; };
 		2D74EAFA1DAE9590003B751B /* RCTMultipartDataTask.m in Sources */ = {isa = PBXBuildFile; fileRef = 006FC4131D9B20820057AAAD /* RCTMultipartDataTask.m */; };
 		2D8C2E331DA40441000EE098 /* RCTMultipartStreamReader.m in Sources */ = {isa = PBXBuildFile; fileRef = 001BFCCF1D8381DE008E587E /* RCTMultipartStreamReader.m */; };
+		2DCCC3151FE48142007C5315 /* RCTRedBoxExtraDataViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = FEFAAC9C1FDB89B40057BBE0 /* RCTRedBoxExtraDataViewController.m */; };
 		2DD0EFE11DA84F2800B0C975 /* RCTStatusBarManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 13723B4F1A82FD3C00F88898 /* RCTStatusBarManager.m */; };
 		352DCFF01D19F4C20056D623 /* RCTI18nUtil.m in Sources */ = {isa = PBXBuildFile; fileRef = 352DCFEF1D19F4C20056D623 /* RCTI18nUtil.m */; };
 		369123E11DDC75850095B341 /* RCTJSCSamplingProfiler.m in Sources */ = {isa = PBXBuildFile; fileRef = 369123E01DDC75850095B341 /* RCTJSCSamplingProfiler.m */; };
@@ -3972,7 +3974,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0940;
+				LastUpgradeCheck = 0810;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					139D7E871E25C6D100323FB7 = {
@@ -4230,6 +4232,7 @@
 				C606692F1F3CC60500E67165 /* RCTModuleMethod.mm in Sources */,
 				2D3B5E9F1D9B08AF00451313 /* RCTKeyCommands.m in Sources */,
 				2D3B5EA51D9B08C700451313 /* RCTRootView.m in Sources */,
+				2DCCC3151FE48142007C5315 /* RCTRedBoxExtraDataViewController.m in Sources */,
 				13134C871E296B2A00B9F3CB /* RCTCxxBridge.mm in Sources */,
 				CF2731C31E7B8DF30044CA4F /* RCTDeviceInfo.m in Sources */,
 				599FAA3F1FB274980058CCF6 /* RCTSurfaceRootShadowView.m in Sources */,
@@ -4269,6 +4272,7 @@
 				2D3B5EC61D9B095000451313 /* RCTProfileTrampoline-x86_64.S in Sources */,
 				2D3B5EA61D9B08CA00451313 /* RCTTouchEvent.m in Sources */,
 				2D8C2E331DA40441000EE098 /* RCTMultipartStreamReader.m in Sources */,
+				2D1D83EF1F74E76C00615550 /* RCTModalManager.m in Sources */,
 				59EDBCBC1FDF4E0C003573DE /* RCTScrollViewManager.m in Sources */,
 				59EDBCB01FDF4E0C003573DE /* RCTScrollContentView.m in Sources */,
 				2D3B5EF01D9B09E300451313 /* RCTWrapperViewController.m in Sources */,
@@ -5105,22 +5109,14 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -5169,22 +5165,14 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
-				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
-				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
-				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
-				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
-				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
-				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
-				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
-				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;

From 843a433e87b0ccaa64ab70d07e22bffbabad8045 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Mon, 18 Jun 2018 15:53:57 -0700
Subject: [PATCH 0848/1109] Update react-native init's flowconfig

Summary:
Fixes https://github.com/facebook/react-native/issues/19766

On a clean project flow was complaining about `Cannot resolve module X` because of the removal of `providesModule`. This resolves the errors.

Reviewed By: rubennorte

Differential Revision: D8500303

fbshipit-source-id: 4e129ee4382f8ff36ab126e9f6c6530254cd382e
---
 local-cli/templates/HelloWorld/_flowconfig | 13 +++++++++++++
 1 file changed, 13 insertions(+)

diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 2f3267d3164c..f99d3024b467 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -30,6 +30,19 @@ node_modules/react-native/flow-github/
 emoji=true
 
 module.system=haste
+module.system.haste.use_name_reducers=true
+# get basename
+module.system.haste.name_reducers='^.*/\([a-zA-Z0-9$_.-]+\.js\(\.flow\)?\)$' -> '\1'
+# strip .js or .js.flow suffix
+module.system.haste.name_reducers='^\(.*\)\.js\(\.flow\)?$' -> '\1'
+# strip .ios suffix
+module.system.haste.name_reducers='^\(.*\)\.ios$' -> '\1'
+module.system.haste.name_reducers='^\(.*\)\.android$' -> '\1'
+module.system.haste.name_reducers='^\(.*\)\.native$' -> '\1'
+module.system.haste.paths.blacklist=.*/__tests__/.*
+module.system.haste.paths.blacklist=.*/__mocks__/.*
+module.system.haste.paths.blacklist=<PROJECT_ROOT>/node_modules/react-native/Libraries/Animated/src/polyfills/.*
+module.system.haste.paths.whitelist=<PROJECT_ROOT>/node_modules/react-native/Libraries/.*
 
 munge_underscores=true
 

From 9a59428468afbf3d76fd2d61abafe17e88101b09 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Mon, 18 Jun 2018 22:53:53 -0700
Subject: [PATCH 0849/1109] Fabric: Fixed `Identity Transform` matrix literal

Summary:
@public
As Janic janicduplessis mentioned on GH the literal should be slightly different.
https://github.com/facebook/react-native/commit/8df7d516006041ff703d68ea277795ff758572ff#r29390543

And here is prooflink: https://developer.apple.com/documentation/quartzcore/calayer/identity_transform?language=objc

Thanks Janic!

Created from Diffusion's 'Open in Editor' feature.

Reviewed By: fkgozali

Differential Revision: D8508559

fbshipit-source-id: 7427be36e041bf500bee1e06d2293f7b5ea8cf21
---
 ReactCommon/fabric/view/primitives.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/view/primitives.h b/ReactCommon/fabric/view/primitives.h
index 3e57f4bf8592..f7814c041529 100644
--- a/ReactCommon/fabric/view/primitives.h
+++ b/ReactCommon/fabric/view/primitives.h
@@ -14,7 +14,7 @@ namespace react {
 
 struct Transform {
   std::array<Float, 16> matrix {{
-    0, 0, 0, 0,
+    1, 0, 0, 0,
     0, 1, 0, 0,
     0, 0, 1, 0,
     0, 0, 0, 1

From e11cdc917c131dcd11ef06872c01d6f1917409ef Mon Sep 17 00:00:00 2001
From: Hoa Dinh <dvh@fb.com>
Date: Mon, 18 Jun 2018 23:45:21 -0700
Subject: [PATCH 0850/1109] Fixed RCTAssert nullability

Summary:
```
Apps/Instagram/AppLibraries/IGReactKit/IGReactKit/IGReactRouteHelpers.m:54:5: error: implicit conversion from nullable pointer 'NSString * _Nullable' to non-nullable pointer type 'NSString * _Nonnull' [-Werror,-Wnullable-to-nonnull-conversion]
    RCTAssert(!(title != nil && logoAsTitle), @"Screen navigationOptions cannot have both title and logoAsTitle.");
    ^
Apps/Instagram/AppLibraries/IGReactKit/IGReactKit/IGReactRouteHelpers.m:54:5: error: implicit conversion from nullable pointer 'NSString * _Nullable' to non-nullable pointer type 'NSString * _Nonnull' [-Werror,-Wnullable-to-nonnull-conversion]
/data/sandcastle/boxes/trunk-hg-fbobjc-fbsource/xplat/js/react-native-github/React/Base/RCTAssert.h:28:14: note: expanded from macro 'RCTAssert'
        file:@(__FILE__) lineNumber:__LINE__ description:__VA_ARGS__]; \

```

Reviewed By: zats

Differential Revision: D8509133

fbshipit-source-id: ae7027efc18716193c86fbeeec74d41d1879797f
---
 React/Base/RCTAssert.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/Base/RCTAssert.h b/React/Base/RCTAssert.h
index 5e60a7b206a4..95d210a5e0ce 100644
--- a/React/Base/RCTAssert.h
+++ b/React/Base/RCTAssert.h
@@ -25,7 +25,7 @@ RCT_EXTERN BOOL RCTIsMainQueue(void);
     _RCTAssertFormat(#condition, __FILE__, __LINE__, __func__, __VA_ARGS__); \
     if (RCT_NSASSERT) { \
       [[NSAssertionHandler currentHandler] handleFailureInFunction:@(__func__) \
-        file:@(__FILE__) lineNumber:__LINE__ description:__VA_ARGS__]; \
+        file:(NSString * _Nonnull)@(__FILE__) lineNumber:__LINE__ description:__VA_ARGS__]; \
     } \
   } \
 } while (false)

From 5f9a2117bfa96cc834b53c1a410e938174772968 Mon Sep 17 00:00:00 2001
From: Pavlos Vinieratos <pvinis@mac-pro.localdomain>
Date: Tue, 19 Jun 2018 02:08:23 -0700
Subject: [PATCH 0851/1109] Remove some methods that have `NS_UNAVAILABLE` set
 (#19790)

Summary:
These lines were causing erros with the e2e tests on ios.
There are some methods that are not going to be called, and some definitions that are not correct.

needed for #19574.

we will run the e2e tests.

[INTERNAL] [MINOR] [Tests] - Fix some definitions.
Closes https://github.com/facebook/react-native/pull/19790

Differential Revision: D8509228

Pulled By: hramos

fbshipit-source-id: 78650e347db52305a587e3461ac56877e3c79062
---
 .../Text/TextInput/Multiline/RCTMultilineTextInputView.m    | 3 ---
 Libraries/Text/TextInput/Multiline/RCTUITextView.m          | 6 ------
 .../Text/TextInput/Singleline/RCTSinglelineTextInputView.m  | 3 ---
 Libraries/Text/TextInput/Singleline/RCTUITextField.m        | 6 ------
 4 files changed, 18 deletions(-)

diff --git a/Libraries/Text/TextInput/Multiline/RCTMultilineTextInputView.m b/Libraries/Text/TextInput/Multiline/RCTMultilineTextInputView.m
index b2d3cbe894c9..334fc5a1254b 100644
--- a/Libraries/Text/TextInput/Multiline/RCTMultilineTextInputView.m
+++ b/Libraries/Text/TextInput/Multiline/RCTMultilineTextInputView.m
@@ -40,9 +40,6 @@ - (instancetype)initWithBridge:(RCTBridge *)bridge
   return self;
 }
 
-RCT_NOT_IMPLEMENTED(- (instancetype)initWithFrame:(CGRect)frame)
-RCT_NOT_IMPLEMENTED(- (instancetype)initWithCoder:(NSCoder *)coder)
-
 - (id<RCTBackedTextInputViewProtocol>)backedTextInputView
 {
   return _backedTextInputView;
diff --git a/Libraries/Text/TextInput/Multiline/RCTUITextView.m b/Libraries/Text/TextInput/Multiline/RCTUITextView.m
index 992a1a8abfc6..ddfd1c27f50d 100644
--- a/Libraries/Text/TextInput/Multiline/RCTUITextView.m
+++ b/Libraries/Text/TextInput/Multiline/RCTUITextView.m
@@ -108,12 +108,6 @@ - (void)setTextAlignment:(NSTextAlignment)textAlignment
   _placeholderView.textAlignment = textAlignment;
 }
 
-- (void)setText:(NSString *)text
-{
-  [super setText:text];
-  [self textDidChange];
-}
-
 - (void)setAttributedText:(NSAttributedString *)attributedText
 {
   [super setAttributedText:attributedText];
diff --git a/Libraries/Text/TextInput/Singleline/RCTSinglelineTextInputView.m b/Libraries/Text/TextInput/Singleline/RCTSinglelineTextInputView.m
index d3e29b266aad..0a4b9944c0d7 100644
--- a/Libraries/Text/TextInput/Singleline/RCTSinglelineTextInputView.m
+++ b/Libraries/Text/TextInput/Singleline/RCTSinglelineTextInputView.m
@@ -32,9 +32,6 @@ - (instancetype)initWithBridge:(RCTBridge *)bridge
   return self;
 }
 
-RCT_NOT_IMPLEMENTED(- (instancetype)initWithFrame:(CGRect)frame)
-RCT_NOT_IMPLEMENTED(- (instancetype)initWithCoder:(NSCoder *)coder)
-
 - (id<RCTBackedTextInputViewProtocol>)backedTextInputView
 {
   return _backedTextInputView;
diff --git a/Libraries/Text/TextInput/Singleline/RCTUITextField.m b/Libraries/Text/TextInput/Singleline/RCTUITextField.m
index 83e7603ae835..84e2528f83ff 100644
--- a/Libraries/Text/TextInput/Singleline/RCTUITextField.m
+++ b/Libraries/Text/TextInput/Singleline/RCTUITextField.m
@@ -121,12 +121,6 @@ - (CGRect)editingRectForBounds:(CGRect)bounds
 
 #pragma mark - Overrides
 
-- (void)setSelectedTextRange:(UITextRange *)selectedTextRange
-{
-  [super setSelectedTextRange:selectedTextRange];
-  [_textInputDelegateAdapter selectedTextRangeWasSet];
-}
-
 - (void)setSelectedTextRange:(UITextRange *)selectedTextRange notifyDelegate:(BOOL)notifyDelegate
 {
   if (!notifyDelegate) {

From c6a52b6db6d620f0b555abbd9ca7ade38e396cbc Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 19 Jun 2018 10:33:16 -0700
Subject: [PATCH 0852/1109] Fix setJSResponder for Fabric

Summary:
Before this fix, ReactNative screens that uses the Fabric renderer crashes when an event is dispatched. The root cause of the bug is that React JS executes the setJSResponder method in UIManagerModule, but this method is not implemented yet in Fabric.

This fix will have to be picked into current RC to fix events into the City Guides screen running the Fabric experiment

Reviewed By: fkgozali

Differential Revision: D8515300

fbshipit-source-id: 40fe2f77987470abed8164f848680a911efa4bd2
---
 .../com/facebook/react/uimanager/UIManagerModule.java     | 8 ++------
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 1ac393b06fa7..ed98ab9a0a68 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -10,7 +10,6 @@
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_END;
 import static com.facebook.react.bridge.ReactMarkerConstants.CREATE_UI_MANAGER_MODULE_CONSTANTS_START;
 import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
-import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 
 import android.content.ComponentCallbacks2;
 import android.content.Context;
@@ -25,9 +24,7 @@
 import com.facebook.react.bridge.GuardedRunnable;
 import com.facebook.react.bridge.LifecycleEventListener;
 import com.facebook.react.bridge.OnBatchCompleteListener;
-import com.facebook.react.bridge.PerformanceCounter;
 import com.facebook.react.bridge.ReactApplicationContext;
-import com.facebook.react.bridge.ReactContext;
 import com.facebook.react.bridge.ReactContextBaseJavaModule;
 import com.facebook.react.bridge.ReactMarker;
 import com.facebook.react.bridge.ReactMethod;
@@ -40,7 +37,6 @@
 import com.facebook.react.module.annotations.ReactModule;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
-import com.facebook.react.uimanager.common.UIManagerType;
 import com.facebook.react.uimanager.common.ViewUtil;
 import com.facebook.react.uimanager.debug.NotThreadSafeViewHierarchyUpdateDebugListener;
 import com.facebook.react.uimanager.events.EventDispatcher;
@@ -595,9 +591,9 @@ public void setJSResponder(int reactTag, boolean blockNativeResponder) {
     int uiManagerType = ViewUtil.getUIManagerType(reactTag);
     if (uiManagerType != DEFAULT) {
       UIManagerHelper.getUIManager(getReactApplicationContext(), uiManagerType).setJSResponder(reactTag, blockNativeResponder);
+    } else {
+      mUIImplementation.setJSResponder(reactTag, blockNativeResponder);
     }
-
-    mUIImplementation.setJSResponder(reactTag, blockNativeResponder);
   }
 
   @Override

From d7e0fe2c2c0cf8412d97ae16d0627c1111b59bf8 Mon Sep 17 00:00:00 2001
From: Jeff Thomas <jeffdthomas@fb.com>
Date: Tue, 19 Jun 2018 13:18:51 -0700
Subject: [PATCH 0853/1109] AssetsLibrary.framework --> Photos.framework;
 ReactNative stuff

Summary:
AssetsLibrary.framework --> Photos.framework;  ReactNative

Port RN off of AssetsLibrary where trivial, lazy load AssetsLibrary where remaining.

Reviewed By: fkgozali

Differential Revision: D7999924

fbshipit-source-id: 1d48a2d820984564459ed43680cd3f601399d352
---
 .../RCTAssetsLibraryRequestHandler.m          | 16 ++++-
 Libraries/CameraRoll/RCTCameraRollManager.m   | 65 ++++++++++++++-----
 2 files changed, 63 insertions(+), 18 deletions(-)

diff --git a/Libraries/CameraRoll/RCTAssetsLibraryRequestHandler.m b/Libraries/CameraRoll/RCTAssetsLibraryRequestHandler.m
index e9637d7c4c16..9721b392b80f 100644
--- a/Libraries/CameraRoll/RCTAssetsLibraryRequestHandler.m
+++ b/Libraries/CameraRoll/RCTAssetsLibraryRequestHandler.m
@@ -8,6 +8,8 @@
 #import "RCTAssetsLibraryRequestHandler.h"
 
 #import <stdatomic.h>
+#import <dlfcn.h>
+#import <objc/runtime.h>
 
 #import <AssetsLibrary/AssetsLibrary.h>
 #import <MobileCoreServices/MobileCoreServices.h>
@@ -23,10 +25,20 @@ @implementation RCTAssetsLibraryRequestHandler
 RCT_EXPORT_MODULE()
 
 @synthesize bridge = _bridge;
-
+static Class _ALAssetsLibrary = nil;
+static void ensureAssetsLibLoaded(void)
+{
+  static dispatch_once_t onceToken;
+  dispatch_once(&onceToken, ^{
+    void * handle = dlopen("/System/Library/Frameworks/AssetsLibrary.framework/AssetsLibrary", RTLD_LAZY);
+#pragma unused(handle)
+    _ALAssetsLibrary = objc_getClass("ALAssetsLibrary");
+  });
+}
 - (ALAssetsLibrary *)assetsLibrary
 {
-  return _assetsLibrary ?: (_assetsLibrary = [ALAssetsLibrary new]);
+  ensureAssetsLibLoaded();
+  return _assetsLibrary ?: (_assetsLibrary = [_ALAssetsLibrary new]);
 }
 
 #pragma mark - RCTURLRequestHandler
diff --git a/Libraries/CameraRoll/RCTCameraRollManager.m b/Libraries/CameraRoll/RCTCameraRollManager.m
index b5d9a85dadb4..e6e397392bd1 100644
--- a/Libraries/CameraRoll/RCTCameraRollManager.m
+++ b/Libraries/CameraRoll/RCTCameraRollManager.m
@@ -11,6 +11,8 @@
 #import <Foundation/Foundation.h>
 #import <UIKit/UIKit.h>
 #import <Photos/Photos.h>
+#import <dlfcn.h>
+#import <objc/runtime.h>
 
 #import <React/RCTBridge.h>
 #import <React/RCTConvert.h>
@@ -44,22 +46,52 @@ @implementation RCTConvert (ALAssetGroup)
 
 }), ALAssetsGroupSavedPhotos, integerValue)
 
+static Class _ALAssetsFilter = nil;
+static NSString *_ALAssetsGroupPropertyName = nil;
+static NSString *_ALAssetPropertyAssetURL = nil;
+static NSString *_ALAssetPropertyLocation = nil;
+static NSString *_ALAssetPropertyDate = nil;
+static NSString *_ALAssetPropertyType = nil;
+static NSString *_ALAssetPropertyDuration = nil;
+static NSString *_ALAssetTypeVideo = nil;
+static NSString *lookupNSString(void * handle, const char * name)
+{
+  void ** sym = dlsym(handle, name);
+  return (__bridge NSString *)(sym ? *sym : nil);
+}
+static void ensureAssetsLibLoaded(void)
+{
+  static dispatch_once_t onceToken;
+  dispatch_once(&onceToken, ^{
+    void * handle = dlopen("/System/Library/Frameworks/AssetsLibrary.framework/AssetsLibrary", RTLD_LAZY);
+    RCTAssert(handle != NULL, @"Unable to load AssetsLibrary.framework.");
+    _ALAssetsFilter = objc_getClass("ALAssetsFilter");
+    _ALAssetsGroupPropertyName = lookupNSString(handle, "ALAssetsGroupPropertyName");
+    _ALAssetPropertyAssetURL = lookupNSString(handle, "ALAssetPropertyAssetURL");
+    _ALAssetPropertyLocation = lookupNSString(handle, "ALAssetPropertyLocation");
+    _ALAssetPropertyDate = lookupNSString(handle, "ALAssetPropertyDate");
+    _ALAssetPropertyType = lookupNSString(handle, "ALAssetPropertyType");
+    _ALAssetPropertyDuration = lookupNSString(handle, "ALAssetPropertyDuration");
+    _ALAssetTypeVideo = lookupNSString(handle, "ALAssetTypeVideo");
+  });
+}
+
 + (ALAssetsFilter *)ALAssetsFilter:(id)json
 {
   static NSDictionary<NSString *, ALAssetsFilter *> *options;
   static dispatch_once_t onceToken;
   dispatch_once(&onceToken, ^{
+    ensureAssetsLibLoaded();
     options = @{
-
       // New values
-      @"photos": [ALAssetsFilter allPhotos],
-      @"videos": [ALAssetsFilter allVideos],
-      @"all": [ALAssetsFilter allAssets],
+      @"photos": [_ALAssetsFilter allPhotos],
+      @"videos": [_ALAssetsFilter allVideos],
+      @"all": [_ALAssetsFilter allAssets],
 
       // Legacy values
-      @"Photos": [ALAssetsFilter allPhotos],
-      @"Videos": [ALAssetsFilter allVideos],
-      @"All": [ALAssetsFilter allAssets],
+      @"Photos": [_ALAssetsFilter allPhotos],
+      @"Videos": [_ALAssetsFilter allVideos],
+      @"All": [_ALAssetsFilter allAssets],
     };
   });
 
@@ -68,7 +100,7 @@ + (ALAssetsFilter *)ALAssetsFilter:(id)json
     RCTLogError(@"Invalid filter option: '%@'. Expected one of 'photos',"
                 "'videos' or 'all'.", json);
   }
-  return filter ?: [ALAssetsFilter allPhotos];
+  return filter ?: [_ALAssetsFilter allPhotos];
 }
 
 @end
@@ -149,6 +181,7 @@ static void RCTResolvePromise(RCTPromiseResolveBlock resolve,
 {
   checkPhotoLibraryConfig();
 
+  ensureAssetsLibLoaded();
   NSUInteger first = [RCTConvert NSInteger:params[@"first"]];
   NSString *afterCursor = [RCTConvert NSString:params[@"after"]];
   NSString *groupName = [RCTConvert NSString:params[@"groupName"]];
@@ -161,12 +194,12 @@ static void RCTResolvePromise(RCTPromiseResolveBlock resolve,
   NSMutableArray<NSDictionary<NSString *, id> *> *assets = [NSMutableArray new];
 
   [_bridge.assetsLibrary enumerateGroupsWithTypes:groupTypes usingBlock:^(ALAssetsGroup *group, BOOL *stopGroups) {
-    if (group && (groupName == nil || [groupName isEqualToString:[group valueForProperty:ALAssetsGroupPropertyName]])) {
+    if (group && (groupName == nil || [groupName isEqualToString:[group valueForProperty:_ALAssetsGroupPropertyName]])) {
 
       [group setAssetsFilter:assetType];
       [group enumerateAssetsWithOptions:NSEnumerationReverse usingBlock:^(ALAsset *result, NSUInteger index, BOOL *stopAssets) {
         if (result) {
-          NSString *uri = ((NSURL *)[result valueForProperty:ALAssetPropertyAssetURL]).absoluteString;
+          NSString *uri = ((NSURL *)[result valueForProperty:_ALAssetPropertyAssetURL]).absoluteString;
           if (afterCursor && !foundAfter) {
             if ([afterCursor isEqualToString:uri]) {
               foundAfter = YES;
@@ -183,18 +216,18 @@ static void RCTResolvePromise(RCTPromiseResolveBlock resolve,
             return;
           }
           CGSize dimensions = [result defaultRepresentation].dimensions;
-          CLLocation *loc = [result valueForProperty:ALAssetPropertyLocation];
-          NSDate *date = [result valueForProperty:ALAssetPropertyDate];
+          CLLocation *loc = [result valueForProperty:_ALAssetPropertyLocation];
+          NSDate *date = [result valueForProperty:_ALAssetPropertyDate];
           NSString *filename = [result defaultRepresentation].filename;
           int64_t duration = 0;
-          if ([[result valueForProperty:ALAssetPropertyType] isEqualToString:ALAssetTypeVideo]) {
-            duration = [[result valueForProperty:ALAssetPropertyDuration] intValue];
+          if ([[result valueForProperty:_ALAssetPropertyType] isEqualToString:_ALAssetTypeVideo]) {
+            duration = [[result valueForProperty:_ALAssetPropertyDuration] intValue];
           }
 
           [assets addObject:@{
             @"node": @{
-              @"type": [result valueForProperty:ALAssetPropertyType],
-              @"group_name": [group valueForProperty:ALAssetsGroupPropertyName],
+              @"type": [result valueForProperty:_ALAssetPropertyType],
+              @"group_name": [group valueForProperty:_ALAssetsGroupPropertyName],
               @"image": @{
                 @"uri": uri,
                 @"filename" : filename ?: [NSNull null],

From c5ce7626977a7650e8dce335f2ce78b94839a2a8 Mon Sep 17 00:00:00 2001
From: Alexey Kureev <kureev@fb.com>
Date: Tue, 19 Jun 2018 13:45:17 -0700
Subject: [PATCH 0854/1109] Replace projectRoots with projectRoot + watchRoots

Summary:
We use projectRoots to limit crawling of jest-haste-map in large codebases. Since this implies multiple projects roots, it makes it very hard (or impossible) to reliably cache dependency resolutions.

If we can replace this with a single project root and a set of watch roots, we can have relative path resolutions for all dependencies which van be cached.

Reviewed By: rafeca

Differential Revision: D8450498

fbshipit-source-id: 830c21e847c3236e42d5414a8587508cb73864bd
---
 local-cli/bundle/buildBundle.js                      |  4 ++--
 local-cli/dependencies/dependencies.js               | 12 +++++++-----
 local-cli/server/middleware/getDevToolsMiddleware.js |  4 ++--
 .../middleware/openStackFrameInEditorMiddleware.js   |  4 ++--
 local-cli/server/runServer.js                        |  6 ++++--
 local-cli/server/server.js                           |  9 ++++++---
 6 files changed, 23 insertions(+), 16 deletions(-)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index 818ddec9cbcd..d1e422d4d0b3 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -75,7 +75,6 @@ async function buildBundle(
       : defaultProvidesModuleNodeModules;
 
   const terminal = new Terminal(process.stdout);
-
   const server = new Server({
     asyncRequireModulePath: config.getAsyncRequireModulePath(),
     assetExts: defaultAssetExts.concat(assetExts),
@@ -96,7 +95,7 @@ async function buildBundle(
     platforms: defaultPlatforms.concat(platforms),
     postMinifyProcess: config.postMinifyProcess,
     postProcessBundleSourcemap: config.postProcessBundleSourcemap,
-    projectRoots: config.getProjectRoots(),
+    projectRoot: config.getProjectRoot(),
     providesModuleNodeModules: providesModuleNodeModules,
     reporter: new TerminalReporter(terminal),
     resetCache: args.resetCache,
@@ -104,6 +103,7 @@ async function buildBundle(
     sourceExts: sourceExts.concat(defaultSourceExts),
     transformModulePath: transformModulePath,
     watch: false,
+    watchFolders: config.getWatchFolders(),
     workerPath: config.getWorkerPath && config.getWorkerPath(),
   });
 
diff --git a/local-cli/dependencies/dependencies.js b/local-cli/dependencies/dependencies.js
index 543e15e21d9e..baa6ec4a7a4d 100644
--- a/local-cli/dependencies/dependencies.js
+++ b/local-cli/dependencies/dependencies.js
@@ -34,7 +34,7 @@ function dependencies(argv, config, args, packagerInstance) {
   const packageOpts = {
     assetRegistryPath: ASSET_REGISTRY_PATH,
     cacheStores: [],
-    projectRoots: config.getProjectRoots(),
+    projectRoot: config.getProjectRoot(),
     blacklistRE: config.getBlacklistRE(),
     dynamicDepsInPackages: config.dynamicDepsInPackages,
     getPolyfills: config.getPolyfills,
@@ -44,12 +44,14 @@ function dependencies(argv, config, args, packagerInstance) {
     transformModulePath: transformModulePath,
     extraNodeModules: config.extraNodeModules,
     verbose: config.verbose,
+    watchFolders: config.getWatchFolders(),
     workerPath: config.getWorkerPath(),
   };
 
-  const relativePath = packageOpts.projectRoots.map(root =>
-    path.relative(root, rootModuleAbsolutePath),
-  )[0];
+  const relativePath = path.relative(
+    packageOpts.projectRoot,
+    rootModuleAbsolutePath,
+  );
 
   const options = {
     platform: args.platform,
@@ -75,7 +77,7 @@ function dependencies(argv, config, args, packagerInstance) {
         // (a) JS code to not depend on anything outside this directory, or
         // (b) Come up with a way to declare this dependency in Buck.
         const isInsideProjectRoots =
-          packageOpts.projectRoots.filter(root => modulePath.startsWith(root))
+          packageOpts.watchFolders.filter(root => modulePath.startsWith(root))
             .length > 0;
 
         if (isInsideProjectRoots) {
diff --git a/local-cli/server/middleware/getDevToolsMiddleware.js b/local-cli/server/middleware/getDevToolsMiddleware.js
index 4a01d964d3fd..23ca15ee5a38 100644
--- a/local-cli/server/middleware/getDevToolsMiddleware.js
+++ b/local-cli/server/middleware/getDevToolsMiddleware.js
@@ -23,11 +23,11 @@ function escapePath(pathname) {
   return '"' + pathname + '"';
 }
 
-function launchDevTools({host, projectRoots}, isChromeConnected) {
+function launchDevTools({host, watchFolders}, isChromeConnected) {
   // Explicit config always wins
   var customDebugger = process.env.REACT_DEBUGGER;
   if (customDebugger) {
-    var projects = projectRoots.map(escapePath).join(' ');
+    var projects = watchFolders.map(escapePath).join(' ');
     var command = customDebugger + ' ' + projects;
     console.log('Starting custom debugger by executing: ' + command);
     exec(command, function(error, stdout, stderr) {
diff --git a/local-cli/server/middleware/openStackFrameInEditorMiddleware.js b/local-cli/server/middleware/openStackFrameInEditorMiddleware.js
index 290969ac6f40..f285489ec20f 100644
--- a/local-cli/server/middleware/openStackFrameInEditorMiddleware.js
+++ b/local-cli/server/middleware/openStackFrameInEditorMiddleware.js
@@ -11,11 +11,11 @@
 
 const launchEditor = require('../util/launchEditor');
 
-module.exports = function({projectRoots}) {
+module.exports = function({watchFolders}) {
   return function(req, res, next) {
     if (req.url === '/open-stack-frame') {
       const frame = JSON.parse(req.rawBody);
-      launchEditor(frame.file, frame.lineNumber, projectRoots);
+      launchEditor(frame.file, frame.lineNumber, watchFolders);
       res.end('OK');
     } else {
       next();
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 0bd092cf4420..e2a0b10bfca6 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -60,6 +60,7 @@ export type Args = {|
   +resetCache: boolean,
   +sourceExts: $ReadOnlyArray<string>,
   +verbose: boolean,
+  +watchFolders: $ReadOnlyArray<string>,
 |};
 
 function runServer(
@@ -100,7 +101,7 @@ function runServer(
     .use(indexPageMiddleware)
     .use(packagerServer.processRequest.bind(packagerServer));
 
-  args.projectRoots.forEach(root => app.use(serveStatic(root)));
+  args.watchFolders.forEach(root => app.use(serveStatic(root)));
 
   app.use(morgan('combined')).use(errorhandler());
 
@@ -196,7 +197,7 @@ function getPackagerServer(args, config, reporter) {
     polyfillModuleNames: config.getPolyfillModuleNames(),
     postMinifyProcess: config.postMinifyProcess,
     postProcessBundleSourcemap: config.postProcessBundleSourcemap,
-    projectRoots: args.projectRoots,
+    projectRoot: config.getProjectRoot(),
     providesModuleNodeModules: providesModuleNodeModules,
     reporter,
     resetCache: args.resetCache,
@@ -205,6 +206,7 @@ function getPackagerServer(args, config, reporter) {
     transformModulePath: transformModulePath,
     verbose: args.verbose,
     watch: !args.nonPersistent,
+    watchFolders: config.getWatchFolders(),
     workerPath: config.getWorkerPath(),
   });
 }
diff --git a/local-cli/server/server.js b/local-cli/server/server.js
index b1b3851b3ff7..d4d977a61555 100644
--- a/local-cli/server/server.js
+++ b/local-cli/server/server.js
@@ -75,10 +75,13 @@ module.exports = {
       default: [],
     },
     {
-      command: '--projectRoots [list]',
-      description: 'override the root(s) to be used by the packager',
+      command: '--watchFolders [list]',
+      description:
+        'Sepcify any additional folders to be added to the watch list',
       parse: (val: string) => val.split(','),
-      default: (config: ConfigT) => config.getProjectRoots(),
+      default: (config: ConfigT) => {
+        return config.getProjectRoots ? config.getProjectRoots() : undefined;
+      },
     },
     {
       command: '--assetExts [list]',

From 76eebce3c20152fdd5386ec405524d0810770eea Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Tue, 19 Jun 2018 14:13:03 -0700
Subject: [PATCH 0855/1109] Fix more forwardRef displayNames

Summary:
See https://reactjs.org/docs/forwarding-refs.html#displaying-a-custom-name-in-devtools

reapply of D8342904

Reviewed By: yungsters

Differential Revision: D8465006

fbshipit-source-id: f196f39b9b1c9bbe16a845667ebbdb21953a5848
---
 .../ActivityIndicator/ActivityIndicator.js    |  20 +--
 .../ProgressBarAndroid.android.js             | 134 ++++++++----------
 Libraries/Components/Slider/Slider.js         |   1 -
 Libraries/Components/View/View.js             |   1 -
 Libraries/Text/Text.js                        |   1 -
 5 files changed, 67 insertions(+), 90 deletions(-)

diff --git a/Libraries/Components/ActivityIndicator/ActivityIndicator.js b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
index f2a648797eb0..abe6a75af947 100644
--- a/Libraries/Components/ActivityIndicator/ActivityIndicator.js
+++ b/Libraries/Components/ActivityIndicator/ActivityIndicator.js
@@ -70,12 +70,10 @@ type Props = $ReadOnly<{|
  * See http://facebook.github.io/react-native/docs/activityindicator.html
  */
 const ActivityIndicator = (
-  props: $ReadOnly<{|
-    ...Props,
-    forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
-  |}>,
+  props: Props,
+  forwardedRef?: ?React.Ref<'RCTActivityIndicatorView'>,
 ) => {
-  const {onLayout, style, forwardedRef, ...restProps} = props;
+  const {onLayout, style, ...restProps} = props;
   let sizeStyle;
 
   switch (props.size) {
@@ -99,16 +97,19 @@ const ActivityIndicator = (
   };
 
   return (
-    <View onLayout={onLayout} style={[styles.container, style]}>
+    <View
+      onLayout={onLayout}
+      style={StyleSheet.compose(
+        styles.container,
+        style,
+      )}>
       <RCTActivityIndicator {...nativeProps} />
     </View>
   );
 };
 
 // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
-const ActivityIndicatorWithRef = React.forwardRef((props: Props, ref) => {
-  return <ActivityIndicator {...props} forwardedRef={ref} />;
-});
+const ActivityIndicatorWithRef = React.forwardRef(ActivityIndicator);
 
 ActivityIndicatorWithRef.defaultProps = {
   animating: true,
@@ -116,7 +117,6 @@ ActivityIndicatorWithRef.defaultProps = {
   hidesWhenStopped: true,
   size: 'small',
 };
-ActivityIndicatorWithRef.displayName = 'ActivityIndicator';
 
 const styles = StyleSheet.create({
   container: {
diff --git a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
index 7ea083dd0f19..f343e2e54520 100644
--- a/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
+++ b/Libraries/Components/ProgressBarAndroid/ProgressBarAndroid.android.js
@@ -4,41 +4,60 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
+ * @flow
  * @format
  */
 
 'use strict';
 
-const ColorPropType = require('ColorPropType');
-const PropTypes = require('prop-types');
 const React = require('React');
-const ViewPropTypes = require('ViewPropTypes');
 
 const requireNativeComponent = require('requireNativeComponent');
 
-const STYLE_ATTRIBUTES = [
-  'Horizontal',
-  'Normal',
-  'Small',
-  'Large',
-  'Inverse',
-  'SmallInverse',
-  'LargeInverse',
-];
+import type {NativeComponent} from 'ReactNative';
+import type {ViewProps} from 'ViewPropTypes';
 
-const indeterminateType = function(props, propName, componentName, ...rest) {
-  const checker = function() {
-    const indeterminate = props[propName];
-    const styleAttr = props.styleAttr;
-    if (!indeterminate && styleAttr !== 'Horizontal') {
-      return new Error(
-        'indeterminate=false is only valid for styleAttr=Horizontal',
-      );
-    }
-  };
+const AndroidProgressBar = requireNativeComponent('AndroidProgressBar');
 
-  return PropTypes.bool(props, propName, componentName, ...rest) || checker();
-};
+type Props = $ReadOnly<{|
+  ...ViewProps,
+
+  /**
+   * Style of the ProgressBar and whether it shows indeterminate progress (e.g. spinner).
+   *
+   * `indeterminate` can only be false if `styleAttr` is Horizontal, and requires a
+   * `progress` value.
+   */
+  ...
+    | {|
+        styleAttr: 'Horizontal',
+        indeterminate: false,
+        progress: number,
+      |}
+    | {|
+        typeAttr:
+          | 'Horizontal'
+          | 'Normal'
+          | 'Small'
+          | 'Large'
+          | 'Inverse'
+          | 'SmallInverse'
+          | 'LargeInverse',
+        indeterminate: true,
+      |},
+  /**
+   * Whether to show the ProgressBar (true, the default) or hide it (false).
+   */
+  animating?: ?boolean,
+  /**
+   * Color of the progress bar.
+   */
+  color?: ?string,
+  /**
+   * Used to locate this view in end-to-end tests.
+   */
+  testID?: ?string,
+|}>;
 
 /**
  * React component that wraps the Android-only `ProgressBar`. This component is
@@ -63,59 +82,20 @@ const indeterminateType = function(props, propName, componentName, ...rest) {
  * },
  * ```
  */
-class ProgressBarAndroid extends React.Component {
-  static propTypes = {
-    ...ViewPropTypes,
-
-    /**
-     * Style of the ProgressBar. One of:
-     *
-     * - Horizontal
-     * - Normal (default)
-     * - Small
-     * - Large
-     * - Inverse
-     * - SmallInverse
-     * - LargeInverse
-     */
-    styleAttr: PropTypes.oneOf(STYLE_ATTRIBUTES),
-    /**
-     * Whether to show the ProgressBar (true, the default) or hide it (false).
-     */
-    animating: PropTypes.bool,
-    /**
-     * If the progress bar will show indeterminate progress. Note that this
-     * can only be false if styleAttr is Horizontal.
-     */
-    indeterminate: indeterminateType,
-    /**
-     * The progress value (between 0 and 1).
-     */
-    progress: PropTypes.number,
-    /**
-     * Color of the progress bar.
-     */
-    color: ColorPropType,
-    /**
-     * Used to locate this view in end-to-end tests.
-     */
-    testID: PropTypes.string,
-  };
-
-  static defaultProps = {
-    styleAttr: 'Normal',
-    indeterminate: true,
-    animating: true,
-  };
+const ProgressBarAndroid = (
+  props: Props,
+  forwardedRef: ?React.Ref<'AndroidProgressBar'>,
+) => {
+  return <AndroidProgressBar {...props} ref={forwardedRef} />;
+};
 
-  render() {
-    const {forwardedRef, ...props} = this.props;
-    return <AndroidProgressBar {...props} ref={forwardedRef} />;
-  }
-}
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+const ProgressBarAndroidToExport = React.forwardRef(ProgressBarAndroid);
 
-const AndroidProgressBar = requireNativeComponent('AndroidProgressBar');
+ProgressBarAndroidToExport.defaultProps = {
+  styleAttr: 'Normal',
+  indeterminate: true,
+  animating: true,
+};
 
-module.exports = React.forwardRef((props, ref) => (
-  <ProgressBarAndroid {...props} forwardedRef={ref} />
-));
+module.exports = (ProgressBarAndroidToExport: Class<NativeComponent<Props>>);
diff --git a/Libraries/Components/Slider/Slider.js b/Libraries/Components/Slider/Slider.js
index d9efe0170d8d..7f18a2d3b35e 100644
--- a/Libraries/Components/Slider/Slider.js
+++ b/Libraries/Components/Slider/Slider.js
@@ -250,7 +250,6 @@ SliderWithRef.defaultProps = {
   maximumValue: 1,
   step: 0,
 };
-SliderWithRef.displayName = 'Slider';
 
 let styles;
 if (Platform.OS === 'ios') {
diff --git a/Libraries/Components/View/View.js b/Libraries/Components/View/View.js
index ed420338c243..2cfa05a8c118 100644
--- a/Libraries/Components/View/View.js
+++ b/Libraries/Components/View/View.js
@@ -45,7 +45,6 @@ if (__DEV__) {
       </TextAncestor.Consumer>
     );
   };
-  View.displayName = 'View'; // TODO(T30332650) remove bug workaround
   // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
   ViewToExport = React.forwardRef(View);
 }
diff --git a/Libraries/Text/Text.js b/Libraries/Text/Text.js
index aaa283a6dafa..2a0a939f876a 100644
--- a/Libraries/Text/Text.js
+++ b/Libraries/Text/Text.js
@@ -267,7 +267,6 @@ const Text = (
 ) => {
   return <TouchableText {...props} forwardedRef={forwardedRef} />;
 };
-Text.displayName = 'Text'; // TODO(T30332650) remove bug workaround
 // $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
 const TextToExport = React.forwardRef(Text);
 

From 73c4df219a45cd448ed971e847122c9f09524dab Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 19 Jun 2018 14:35:28 -0700
Subject: [PATCH 0856/1109] Avoid loading FabricUIManager from UIManagerModule
 in setJSResponder method

Summary:
In D8515300 we used the uiManagerType to call the setJSResponder method in UIImplementation or FabricUIManager.
There is a small chance that one of the reactTags received by parameter belongs to a View that is not managed by ReactNative, in that case we could be try to use FabricUIManager from UIManagerModule when Fabric is not running yet, causing a RN crash.
The fix consists in keep calling the UIImplementation.setJSResponder() method for any reactTag, and then perform a NOOP if the ReactShadowNode can not be found.

Reviewed By: fkgozali

Differential Revision: D8518192

fbshipit-source-id: 954fdd5dbed758ef73c16dad7da6b59ed83fe46a
---
 .../com/facebook/react/uimanager/UIImplementation.java   | 8 +++++++-
 .../com/facebook/react/uimanager/UIManagerModule.java    | 9 +--------
 2 files changed, 8 insertions(+), 9 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
index c1adee2e6cca..2baee93cee94 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java
@@ -776,8 +776,14 @@ public void configureNextLayoutAnimation(
   }
 
   public void setJSResponder(int reactTag, boolean blockNativeResponder) {
-    assertViewExists(reactTag, "setJSResponder");
     ReactShadowNode node = mShadowNodeRegistry.getNode(reactTag);
+
+    if (node == null) {
+      //TODO: this should only happen when using Fabric renderer. This is a temporary approach
+      //and it will be refactored when fabric supports JS Responder.
+      return;
+    }
+
     while (node.isVirtual() || node.isLayoutOnly()) {
       node = node.getParent();
     }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index ed98ab9a0a68..7c03ec96bba8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -586,14 +586,7 @@ public void removeAnimation(int reactTag, int animationID) {
   @Override
   @ReactMethod
   public void setJSResponder(int reactTag, boolean blockNativeResponder) {
-    //TODO: this is a temporary approach to support ViewManagerCommands in Fabric until
-    // the dispatchViewManagerCommand() method is supported by Fabric JS API.
-    int uiManagerType = ViewUtil.getUIManagerType(reactTag);
-    if (uiManagerType != DEFAULT) {
-      UIManagerHelper.getUIManager(getReactApplicationContext(), uiManagerType).setJSResponder(reactTag, blockNativeResponder);
-    } else {
-      mUIImplementation.setJSResponder(reactTag, blockNativeResponder);
-    }
+    mUIImplementation.setJSResponder(reactTag, blockNativeResponder);
   }
 
   @Override

From 7b9b1559a7f6719c3c9ad8e894fcdd99ed109afe Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 19 Jun 2018 18:38:47 -0700
Subject: [PATCH 0857/1109] iOS: Avoid double reload event when reloading JS

Summary:
@public
The bridge may send the reload event twice when reloading JS in some rare condition. The 2nd one was actually when the "new" bridge wasn't valid yet, so log an error if that happens. This may happen if the connection to Metro server gets into a weird state. Restarting Metro would solve the problem.

The issue was that `RCTBridgeWillReloadNotification` fired twice for each reload with metro connected.

Reviewed By: mmmulani

Differential Revision: D8509448

fbshipit-source-id: 647fb98c0a97503409a10451b8f152145947ae20
---
 React/CxxBridge/RCTCxxBridge.mm          | 3 +++
 React/Fabric/RCTSurfacePresenter.mm      | 5 +++++
 React/Fabric/Surface/RCTFabricSurface.mm | 2 ++
 3 files changed, 10 insertions(+)

diff --git a/React/CxxBridge/RCTCxxBridge.mm b/React/CxxBridge/RCTCxxBridge.mm
index 42c3fdbf565a..184612f1c1fc 100644
--- a/React/CxxBridge/RCTCxxBridge.mm
+++ b/React/CxxBridge/RCTCxxBridge.mm
@@ -876,6 +876,9 @@ - (void)setUp {}
 
 - (void)reload
 {
+  if (!_valid) {
+    RCTLogError(@"Attempting to reload bridge before it's valid: %@. Try restarting the development server if connected.", self);
+  }
   [_parentBridge reload];
 }
 
diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
index 9c9c15955bbb..2c2f01c93bbe 100644
--- a/React/Fabric/RCTSurfacePresenter.mm
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -61,6 +61,11 @@ - (instancetype)initWithBridge:(RCTBridge *)bridge
   return self;
 }
 
+- (void)dealloc
+{
+  [[NSNotificationCenter defaultCenter] removeObserver:self];
+}
+
 - (void)schedulerDidComputeMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions rootTag:(ReactTag)rootTag
 {
   [_mountingManager mutateComponentViewTreeWithMutationInstructions:instructions
diff --git a/React/Fabric/Surface/RCTFabricSurface.mm b/React/Fabric/Surface/RCTFabricSurface.mm
index 267ef61c0251..5d8f5a1ed5e8 100644
--- a/React/Fabric/Surface/RCTFabricSurface.mm
+++ b/React/Fabric/Surface/RCTFabricSurface.mm
@@ -90,6 +90,8 @@ - (instancetype)initWithSurfacePresenter:(RCTSurfacePresenter *)surfacePresenter
 
 - (void)dealloc
 {
+  [[NSNotificationCenter defaultCenter] removeObserver:self];
+
   [self _stop];
 }
 

From e7256a777e0b41e3e6bda02a0d475d18775d4924 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Tue, 19 Jun 2018 18:38:49 -0700
Subject: [PATCH 0858/1109] fix up double surface registration on JS load

Summary:
@public
When JS first starts up, Fabric surface end up double registering itself, causing events to not work. So let's guard it so that registration happens only on reload case.

Reviewed By: shergin

Differential Revision: D8521002

fbshipit-source-id: 441f121786e860dc10e959e940b411c2afaf96dc
---
 React/Fabric/Surface/RCTFabricSurface.mm | 24 +++++++++++++++---------
 1 file changed, 15 insertions(+), 9 deletions(-)

diff --git a/React/Fabric/Surface/RCTFabricSurface.mm b/React/Fabric/Surface/RCTFabricSurface.mm
index 5d8f5a1ed5e8..a779dc55d300 100644
--- a/React/Fabric/Surface/RCTFabricSurface.mm
+++ b/React/Fabric/Surface/RCTFabricSurface.mm
@@ -298,16 +298,22 @@ - (void)handleJavaScriptDidLoadNotification:(NSNotification *)notification
 {
   // TODO: Move the bridge lifecycle handling up to the RCTSurfacePresenter.
 
-  // Note: this covers only JS reloads.
-  [self _setStage:RCTSurfaceStageModuleDidLoad];
-  [self _run];
+  // Note: this covers both JS reloads and initial load after the bridge starts.
+  // When it's not a reload, surface should already be running since we run it immediately in the initializer, so do
+  // nothing.
+  // When it's a reload, we rely on the `RCTJavaScriptWillStartLoadingNotification` notification to reset the stage,
+  // then we need to run the surface and update its size.
+  if (!RCTSurfaceStageIsRunning(_stage)) {
+    [self _setStage:RCTSurfaceStageModuleDidLoad];
+    [self _run];
 
-  // After a reload surfacePresenter needs to know the last min/max size for this surface, because the surface hosting
-  // view was already attached to the ViewController's view.
-  // TODO: Find a better automatic way.
-  [_surfacePresenter setMinimumSize:_minimumSize
-                        maximumSize:_maximumSize
-                            surface:self];
+    // After a reload surfacePresenter needs to know the last min/max size for this surface, because the surface hosting
+    // view was already attached to the ViewController's view.
+    // TODO: Find a better automatic way.
+    [_surfacePresenter setMinimumSize:_minimumSize
+                          maximumSize:_maximumSize
+                              surface:self];
+  }
 }
 
 @end

From 66aeeff2f9f509736311e1b6e2920e763e0ab5f4 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Tue, 19 Jun 2018 21:28:00 -0700
Subject: [PATCH 0859/1109] Include static properties in jest mocks for core
 components

Summary: This is necessary to provide things like `Image.prefetch` in Jest tests. Previously this only gave access to propTypes.

Reviewed By: sahrens

Differential Revision: D8526494

fbshipit-source-id: 11d49d95d6edf3f75c90438e0b629f5345bc980d
---
 jest/mockComponent.js | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/jest/mockComponent.js b/jest/mockComponent.js
index 3f98a160d5c9..e94d467a6116 100644
--- a/jest/mockComponent.js
+++ b/jest/mockComponent.js
@@ -48,9 +48,9 @@ module.exports = (moduleName, instanceMethods) => {
     }
   };
 
-  if (RealComponent.propTypes != null) {
-    Component.propTypes = RealComponent.propTypes;
-  }
+  Object.keys(RealComponent).forEach(classStatic => {
+    Component[classStatic] = RealComponent[classStatic];
+  });
 
   if (instanceMethods != null) {
     Object.assign(Component.prototype, instanceMethods);

From 2455fd662bbc60683621941b464abf45db3d0289 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Tue, 19 Jun 2018 21:28:02 -0700
Subject: [PATCH 0860/1109] Tightening the flow types for Image

Reviewed By: sahrens

Differential Revision: D8529116

fbshipit-source-id: 5ce4a7737d8837ca9a9c94054e1d1182fb38c094
---
 Libraries/Image/ImageProps.js | 58 ++++++++++++++++++++++++++---------
 RNTester/js/ImageExample.js   |  1 -
 2 files changed, 43 insertions(+), 16 deletions(-)

diff --git a/Libraries/Image/ImageProps.js b/Libraries/Image/ImageProps.js
index 46d367fccf8c..54f6250e1f14 100644
--- a/Libraries/Image/ImageProps.js
+++ b/Libraries/Image/ImageProps.js
@@ -16,35 +16,63 @@ const ImageStylePropTypes = require('ImageStylePropTypes');
 const PropTypes = require('prop-types');
 const StyleSheetPropType = require('StyleSheetPropType');
 
+import type {DimensionValue} from 'StyleSheetTypes';
+import type {ViewProps} from 'ViewPropTypes';
 import type {ImageSource} from 'ImageSource';
 import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
-import type {LayoutEvent, SyntheticEvent} from 'CoreEventTypes';
+import type {SyntheticEvent} from 'CoreEventTypes';
 import type {ImageStyleProp} from 'StyleSheet';
 
-export type ImageProps = {
-  accessible?: boolean,
-  accessibilityLabel?: ?(string | Array<any> | any),
+type OnLoadEvent = SyntheticEvent<
+  $ReadOnly<{|
+    // Only on Android
+    uri?: string,
+
+    source: $ReadOnly<{|
+      width: number,
+      height: number,
+      url: string,
+    |}>,
+  |}>,
+>;
+
+type IOSImageProps = $ReadOnly<{|
+  defaultSource?: ?ImageSource,
+  onPartialLoad?: ?() => void,
+  onProgress?: ?(
+    event: SyntheticEvent<$ReadOnly<{|loaded: number, total: number|}>>,
+  ) => void,
+|}>;
+
+type AndroidImageProps = $ReadOnly<{|
+  loadingIndicatorSource?: ?(number | $ReadOnly<{|uri: string|}>),
+  progressiveRenderingEnabled?: ?boolean,
+  fadeDuration?: ?number,
+|}>;
+
+export type ImageProps = {|
+  ...ViewProps,
+  ...IOSImageProps,
+  ...AndroidImageProps,
   blurRadius?: number,
   capInsets?: ?EdgeInsetsProp,
 
   onError?: ?(event: SyntheticEvent<$ReadOnly<{||}>>) => void,
-  onLayout?: ?(event: LayoutEvent) => void,
-  onLoad?: ?() => void,
+  onLoad?: ?(event: OnLoadEvent) => void,
   onLoadEnd?: ?() => void,
   onLoadStart?: ?() => void,
   resizeMethod?: ?('auto' | 'resize' | 'scale'),
-  resizeMode?: ?('cover' | 'contain' | 'stretch' | 'repeat' | 'center'),
   source?: ?ImageSource,
   style?: ImageStyleProp,
-  testID?: ?string,
 
-  // ios
-  defaultSource?: ?ImageSource,
-  onPartialLoad?: ?() => void,
-  onProgress?: ?(
-    event: SyntheticEvent<$ReadOnly<{|loaded: number, total: number|}>>,
-  ) => void,
-};
+  // Can be set via props or style, for now
+  height?: DimensionValue,
+  width?: DimensionValue,
+  resizeMode?: ?('cover' | 'contain' | 'stretch' | 'repeat' | 'center'),
+
+  src?: empty,
+  children?: empty,
+|};
 
 module.exports = {
   /**
diff --git a/RNTester/js/ImageExample.js b/RNTester/js/ImageExample.js
index 5465b6608117..fdabeae355dd 100644
--- a/RNTester/js/ImageExample.js
+++ b/RNTester/js/ImageExample.js
@@ -60,7 +60,6 @@ var NetworkImageCallbackExample = createReactClass({
             this._loadEventFired(`✔ onLoadStart (+${new Date() - mountTime}ms)`)
           }
           onLoad={event => {
-            // Currently this image source feature is only available on iOS.
             if (event.nativeEvent.source) {
               const url = event.nativeEvent.source.url;
               this._loadEventFired(

From 64d9c487331f2b38ea17b5dbc27738210110e560 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Tue, 19 Jun 2018 21:28:04 -0700
Subject: [PATCH 0861/1109] Image from createReactClass -> ES6 Class

Summary: These are the flow errors that resulted from this diff: P59723027

Reviewed By: sahrens

Differential Revision: D8454977

fbshipit-source-id: e10901d3ecfc541b25f2fefb18702629f0bbab71
---
 Libraries/Image/Image.ios.js   | 202 +++++++++++++++++----------------
 Libraries/Image/ImageSource.js |  12 +-
 2 files changed, 113 insertions(+), 101 deletions(-)

diff --git a/Libraries/Image/Image.ios.js b/Libraries/Image/Image.ios.js
index e3f153242df8..da786c2c133e 100644
--- a/Libraries/Image/Image.ios.js
+++ b/Libraries/Image/Image.ios.js
@@ -10,13 +10,11 @@
 'use strict';
 
 const ImageProps = require('ImageProps');
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const NativeModules = require('NativeModules');
 const React = require('React');
-const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
+const ReactNative = require('ReactNative');
 const StyleSheet = require('StyleSheet');
 
-const createReactClass = require('create-react-class');
 const flattenStyle = require('flattenStyle');
 const requireNativeComponent = require('requireNativeComponent');
 const resolveAssetSource = require('resolveAssetSource');
@@ -25,6 +23,36 @@ const ImageViewManager = NativeModules.ImageViewManager;
 
 const RCTImageView = requireNativeComponent('RCTImageView');
 
+import type {ImageProps as ImagePropsType} from 'ImageProps';
+
+function getSize(
+  uri: string,
+  success: (width: number, height: number) => void,
+  failure?: (error: any) => void,
+) {
+  ImageViewManager.getSize(
+    uri,
+    success,
+    failure ||
+      function() {
+        console.warn('Failed to get size for image: ' + uri);
+      },
+  );
+}
+
+function prefetch(url: string) {
+  return ImageViewManager.prefetchImage(url);
+}
+
+declare class ImageComponentType extends ReactNative.NativeComponent<
+  ImagePropsType,
+> {
+  static getSize: typeof getSize;
+  static prefetch: typeof prefetch;
+  static resolveAssetSource: typeof resolveAssetSource;
+  static propTypes: typeof ImageProps;
+}
+
 /**
  * A React component for displaying different types of images,
  * including network images, static resources, temporary local images, and
@@ -32,108 +60,84 @@ const RCTImageView = requireNativeComponent('RCTImageView');
  *
  * See https://facebook.github.io/react-native/docs/image.html
  */
-const Image = createReactClass({
-  displayName: 'Image',
-  propTypes: ImageProps,
-
-  statics: {
-    /**
-     * Retrieve the width and height (in pixels) of an image prior to displaying it.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#getsize
-     */
-    getSize: function(
-      uri: string,
-      success: (width: number, height: number) => void,
-      failure?: (error: any) => void,
-    ) {
-      ImageViewManager.getSize(
-        uri,
-        success,
-        failure ||
-          function() {
-            console.warn('Failed to get size for image: ' + uri);
-          },
-      );
-    },
-    /**
-     * Prefetches a remote image for later use by downloading it to the disk
-     * cache.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#prefetch
-     */
-    prefetch(url: string) {
-      return ImageViewManager.prefetchImage(url);
-    },
-    /**
-     * Resolves an asset reference into an object.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#resolveassetsource
-     */
-    resolveAssetSource: resolveAssetSource,
-  },
+let Image = (
+  props: ImagePropsType,
+  forwardedRef: ?React.Ref<'RCTImageView'>,
+) => {
+  const source = resolveAssetSource(props.source) || {
+    uri: undefined,
+    width: undefined,
+    height: undefined,
+  };
+
+  let sources;
+  let style;
+  if (Array.isArray(source)) {
+    style = flattenStyle([styles.base, props.style]) || {};
+    sources = source;
+  } else {
+    const {width, height, uri} = source;
+    style = flattenStyle([{width, height}, styles.base, props.style]) || {};
+    sources = [source];
+
+    if (uri === '') {
+      console.warn('source.uri should not be an empty string');
+    }
+  }
 
-  mixins: [NativeMethodsMixin],
+  const resizeMode = props.resizeMode || (style || {}).resizeMode || 'cover'; // Workaround for flow bug t7737108
+  const tintColor = (style || {}).tintColor; // Workaround for flow bug t7737108
 
-  /**
-   * `NativeMethodsMixin` will look for this when invoking `setNativeProps`. We
-   * make `this` look like an actual native component class.
-   */
-  viewConfig: {
-    uiViewClassName: 'UIView',
-    validAttributes: ReactNativeViewAttributes.UIView,
-  },
+  if (props.src != null) {
+    console.warn(
+      'The <Image> component requires a `source` property rather than `src`.',
+    );
+  }
 
-  render: function() {
-    const source = resolveAssetSource(this.props.source) || {
-      uri: undefined,
-      width: undefined,
-      height: undefined,
-    };
-
-    let sources;
-    let style;
-    if (Array.isArray(source)) {
-      style = flattenStyle([styles.base, this.props.style]) || {};
-      sources = source;
-    } else {
-      const {width, height, uri} = source;
-      style =
-        flattenStyle([{width, height}, styles.base, this.props.style]) || {};
-      sources = [source];
-
-      if (uri === '') {
-        console.warn('source.uri should not be an empty string');
-      }
-    }
+  if (props.children != null) {
+    throw new Error(
+      'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.',
+    );
+  }
+
+  return (
+    <RCTImageView
+      {...props}
+      ref={forwardedRef}
+      style={style}
+      resizeMode={resizeMode}
+      tintColor={tintColor}
+      source={sources}
+    />
+  );
+};
+
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+Image = React.forwardRef(Image);
 
-    const resizeMode =
-      this.props.resizeMode || (style || {}).resizeMode || 'cover'; // Workaround for flow bug t7737108
-    const tintColor = (style || {}).tintColor; // Workaround for flow bug t7737108
+/**
+ * Retrieve the width and height (in pixels) of an image prior to displaying it.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#getsize
+ */
+Image.getSize = getSize;
 
-    if (this.props.src) {
-      console.warn(
-        'The <Image> component requires a `source` property rather than `src`.',
-      );
-    }
+/**
+ * Prefetches a remote image for later use by downloading it to the disk
+ * cache.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#prefetch
+ */
+Image.prefetch = prefetch;
 
-    if (this.props.children) {
-      throw new Error(
-        'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.',
-      );
-    }
+/**
+ * Resolves an asset reference into an object.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#resolveassetsource
+ */
+Image.resolveAssetSource = resolveAssetSource;
 
-    return (
-      <RCTImageView
-        {...this.props}
-        style={style}
-        resizeMode={resizeMode}
-        tintColor={tintColor}
-        source={sources}
-      />
-    );
-  },
-});
+Image.propTypes = ImageProps;
 
 const styles = StyleSheet.create({
   base: {
@@ -141,4 +145,4 @@ const styles = StyleSheet.create({
   },
 });
 
-module.exports = Image;
+module.exports = (Image: Class<ImageComponentType>);
diff --git a/Libraries/Image/ImageSource.js b/Libraries/Image/ImageSource.js
index 8338d5feb24a..5c3c84df9012 100644
--- a/Libraries/Image/ImageSource.js
+++ b/Libraries/Image/ImageSource.js
@@ -10,7 +10,11 @@
 'use strict';
 
 // This is to sync with ImageSourcePropTypes.js.
-type ImageURISource = $ReadOnly<{|
+// We explicitly don't want this to be strict so that we can pass in objects
+// that might have more keys. This also has to be inexact to support taking
+// instances of classes like FBIcon.
+// https://fburl.com/8lynhvtw
+type ImageURISource = $ReadOnly<{
   uri?: ?string,
   bundle?: ?string,
   method?: ?string,
@@ -20,6 +24,10 @@ type ImageURISource = $ReadOnly<{|
   width?: ?number,
   height?: ?number,
   scale?: ?number,
-|}>;
+}>;
 
+// We have to export any because of an issue in Flow with objects that come from Relay:
+// https://fburl.com/8ljo5tmr
+// https://fb.facebook.com/groups/flow/permalink/1824103160971624/
+// $FlowFixMe T26861415
 export type ImageSource = ImageURISource | number | Array<ImageURISource>;

From 35e233661d991cce084681f8ad72d3008b793529 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Tue, 19 Jun 2018 23:02:50 -0700
Subject: [PATCH 0862/1109] Remove unnecessary object check

Reviewed By: sahrens

Differential Revision: D8529727

fbshipit-source-id: 6b3659d3cdea70931a30e22a6acfd140091e8ad7
---
 Libraries/Image/Image.ios.js | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/Image/Image.ios.js b/Libraries/Image/Image.ios.js
index da786c2c133e..fc13dd1a46dc 100644
--- a/Libraries/Image/Image.ios.js
+++ b/Libraries/Image/Image.ios.js
@@ -85,8 +85,8 @@ let Image = (
     }
   }
 
-  const resizeMode = props.resizeMode || (style || {}).resizeMode || 'cover'; // Workaround for flow bug t7737108
-  const tintColor = (style || {}).tintColor; // Workaround for flow bug t7737108
+  const resizeMode = props.resizeMode || style.resizeMode;
+  const tintColor = style.tintColor;
 
   if (props.src != null) {
     console.warn(

From eccf536ee99eb722cb10622a7492ea8b36a8cee8 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?=
 <165856+hramos@users.noreply.github.com>
Date: Tue, 19 Jun 2018 23:33:39 -0700
Subject: [PATCH 0863/1109] Update PULL_REQUEST_TEMPLATE.md (#19813)

Summary:
Use colon after Test Plan to ensure the plan is copied to Facebook's internal Phabricator instance successfully.
Closes https://github.com/facebook/react-native/pull/19813

Differential Revision: D8530181

Pulled By: hramos

fbshipit-source-id: 83be6ecaca54a3c6fd4e47b08b8632976f5635aa
---
 .github/PULL_REQUEST_TEMPLATE.md | 30 +++++++-----------------------
 1 file changed, 7 insertions(+), 23 deletions(-)

diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md
index 93f140001bd7..2ae837de23e7 100644
--- a/.github/PULL_REQUEST_TEMPLATE.md
+++ b/.github/PULL_REQUEST_TEMPLATE.md
@@ -1,31 +1,15 @@
 Thank you for sending the PR! We appreciate you spending the time to work on these changes. 
 Help us understand your motivation by explaining why you decided to make this change.
 
-<!-- 
-  Required: Write your motivation here.
-  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
--->
-
-## Test Plan
-
-<!-- 
-  Required: Write your test plan here. If you changed any code, please provide us with 
-  clear instructions on how you verified your changes work. Bonus points for screenshots and videos! 
--->
+If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
 
-## Related PRs
+Test Plan:
+----------
+Write your test plan here. If you changed any code, please provide us with clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
 
-<!-- 
-  Does this PR require a documentation change? 
-  Create a PR at https://github.com/facebook/react-native-website and add a link to it here.
--->
-
-## Release Notes
-
-<!-- 
-  Required. 
-  Help reviewers and the release process by writing your own release notes. See below for an example.
--->
+Release Notes:
+--------------
+Help reviewers and the release process by writing your own release notes. See below for an example.
 
 [CATEGORY] [TYPE] [LOCATION] - Message
 

From 12410f3e4ad9bb629b891dafeffdeeef9c114fb3 Mon Sep 17 00:00:00 2001
From: Pavlos Vinieratos <pvinis@mac-pro.localdomain>
Date: Tue, 19 Jun 2018 23:43:39 -0700
Subject: [PATCH 0864/1109] Update Xcode projects (#19574)

Summary:
@public
A few people have been complaining, including me, that when we compile a react native project, there are a lot of warnings from xcode, suggesting to update the project build settings to the new recommendations.

I took the liberty to actually update the xcode projects, so we can finally have these gone, as well as replace some deprecated methods with the new suggested ones.

[IOS] [MINOR] [Xcode] - updated the Xcode projects with the latest suggestions from Xcode 9.3, and replaced a few deprecated methods of iOS with their new replacements.
Closes https://github.com/facebook/react-native/pull/19574

Reviewed By: shergin

Differential Revision: D8530135

Pulled By: hramos

fbshipit-source-id: b9c9ede0e07760cb2207caa6b468bd5c241848dc
---
 Libraries/ART/ART.xcodeproj/project.pbxproj   | 25 ++++++++++++++++-
 .../RCTActionSheet.xcodeproj/project.pbxproj  | 25 ++++++++++++++++-
 .../Blob/RCTBlob.xcodeproj/project.pbxproj    | 22 ++++++++++++++-
 .../RCTCameraRoll.xcodeproj/project.pbxproj   | 23 +++++++++++++++-
 .../RCTGeolocation.xcodeproj/project.pbxproj  | 23 +++++++++++++++-
 .../Image/RCTImage.xcodeproj/project.pbxproj  | 16 ++++++++++-
 .../RCTLinking.xcodeproj/project.pbxproj      | 23 +++++++++++++++-
 .../RCTAnimation.xcodeproj/project.pbxproj    | 22 ++++++++++++++-
 .../RCTNetwork.xcodeproj/project.pbxproj      | 16 ++++++++++-
 .../project.pbxproj                           | 23 +++++++++++++++-
 .../RCTTest/RCTTest.xcodeproj/project.pbxproj | 23 +++++++++++++++-
 .../RCTSettings.xcodeproj/project.pbxproj     | 23 +++++++++++++++-
 .../Text/RCTText.xcodeproj/project.pbxproj    | 27 ++++++++++++++++---
 .../RCTVibration.xcodeproj/project.pbxproj    | 23 +++++++++++++++-
 .../RCTWebSocket.xcodeproj/project.pbxproj    | 21 ++++++++++++++-
 RNTester/RNTester.xcodeproj/project.pbxproj   | 14 +++++++++-
 .../xcschemes/RNTester-tvOS.xcscheme          |  2 +-
 .../xcshareddata/xcschemes/RNTester.xcscheme  |  2 +-
 .../RNTesterPods.xcodeproj/project.pbxproj    | 14 +++++++++-
 React/React.xcodeproj/project.pbxproj         | 22 +++++++++++----
 20 files changed, 363 insertions(+), 26 deletions(-)

diff --git a/Libraries/ART/ART.xcodeproj/project.pbxproj b/Libraries/ART/ART.xcodeproj/project.pbxproj
index b1cafee230d1..2aec17b1d792 100644
--- a/Libraries/ART/ART.xcodeproj/project.pbxproj
+++ b/Libraries/ART/ART.xcodeproj/project.pbxproj
@@ -245,7 +245,7 @@
 		0CF68AB91AF0540F00FF9E5C /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0620;
+				LastUpgradeCheck = 0940;
 				TargetAttributes = {
 					0CF68AC01AF0540F00FF9E5C = {
 						CreatedOnToolsVersion = 6.2;
@@ -336,19 +336,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -377,19 +389,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_UNDECLARED_SELECTOR = YES;
diff --git a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
index a639137bb7bb..c71f89bdd8c4 100644
--- a/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
+++ b/Libraries/ActionSheetIOS/RCTActionSheet.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B511DA1A9E6C8500147676 = {
@@ -106,19 +106,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -153,19 +165,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj b/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
index 316c157dec50..8bb32fec7b57 100755
--- a/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
+++ b/Libraries/Blob/RCTBlob.xcodeproj/project.pbxproj
@@ -145,7 +145,7 @@
 		358F4ECF1D1E81A9004DF814 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0730;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					358F4ED61D1E81A9004DF814 = {
@@ -206,13 +206,23 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
@@ -251,13 +261,23 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
diff --git a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
index 1132021a60d4..618dbab44ae8 100644
--- a/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
+++ b/Libraries/CameraRoll/RCTCameraRoll.xcodeproj/project.pbxproj
@@ -100,7 +100,7 @@
 		58B511551A9E6B3D00147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B5115C1A9E6B3D00147676 = {
@@ -148,20 +148,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -197,20 +208,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj b/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
index b1e18399c683..c0754118087a 100644
--- a/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
+++ b/Libraries/Geolocation/RCTGeolocation.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					58B511DA1A9E6C8500147676 = {
@@ -106,20 +106,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -154,20 +165,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Image/RCTImage.xcodeproj/project.pbxproj b/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
index 0af0af8f1ee6..bbf4d7104224 100644
--- a/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
+++ b/Libraries/Image/RCTImage.xcodeproj/project.pbxproj
@@ -251,7 +251,7 @@
 		58B511551A9E6B3D00147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0810;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28391D9B042B00D4039D = {
@@ -365,15 +365,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -417,15 +424,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj b/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
index b56dcc67b984..34003d2a6016 100644
--- a/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
+++ b/Libraries/LinkingIOS/RCTLinking.xcodeproj/project.pbxproj
@@ -79,7 +79,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28461D9B043800D4039D = {
@@ -171,20 +171,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -218,20 +229,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_SHADOW = YES;
diff --git a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
index f17225d61632..d74745fb037b 100644
--- a/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
+++ b/Libraries/NativeAnimation/RCTAnimation.xcodeproj/project.pbxproj
@@ -409,7 +409,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0730;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A281F1D9B03D100D4039D = {
@@ -534,14 +534,23 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
@@ -549,6 +558,7 @@
 				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -584,20 +594,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj b/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
index e5a2fc78cfb0..20cf3cf1dcdc 100644
--- a/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
+++ b/Libraries/Network/RCTNetwork.xcodeproj/project.pbxproj
@@ -109,7 +109,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0810;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28531D9B044C00D4039D = {
@@ -211,15 +211,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -263,15 +270,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj b/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
index e709c21454fe..7bca7034655f 100644
--- a/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
+++ b/Libraries/PushNotificationIOS/RCTPushNotification.xcodeproj/project.pbxproj
@@ -121,7 +121,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					3D05745E1DE6004600184BB4 = {
@@ -217,20 +217,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = "DEBUG=1";
 				GCC_SYMBOLS_PRIVATE_EXTERN = NO;
@@ -262,20 +273,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_PREPROCESSOR_DEFINITIONS = "";
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
diff --git a/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj b/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
index f2c7c371cd81..e3f848a5cb27 100644
--- a/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
+++ b/Libraries/RCTTest/RCTTest.xcodeproj/project.pbxproj
@@ -192,7 +192,7 @@
 		580C37671AB104AF0015E709 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A286D1D9B047700D4039D = {
@@ -296,20 +296,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -344,20 +355,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj b/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
index fd0b9c5e4e47..2366798e5856 100644
--- a/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
+++ b/Libraries/Settings/RCTSettings.xcodeproj/project.pbxproj
@@ -79,7 +79,7 @@
 		58B511D31A9E6C8500147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28601D9B046600D4039D = {
@@ -171,20 +171,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -219,20 +230,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Text/RCTText.xcodeproj/project.pbxproj b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
index c882c8843e3c..d3205e5ee16e 100644
--- a/Libraries/Text/RCTText.xcodeproj/project.pbxproj
+++ b/Libraries/Text/RCTText.xcodeproj/project.pbxproj
@@ -103,9 +103,9 @@
 		5956B1A6200FF35C008D9D16 /* RCTUITextField.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B103200FEBA9008D9D16 /* RCTUITextField.m */; };
 		5956B1A7200FF35C008D9D16 /* RCTVirtualTextShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */; };
 		5956B1A8200FF35C008D9D16 /* RCTVirtualTextViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 5956B12B200FEBAA008D9D16 /* RCTVirtualTextViewManager.m */; };
-		5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */; };
 		5970936920845EFC00D163A7 /* RCTTextTransform.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5970936820845DDE00D163A7 /* RCTTextTransform.h */; };
 		5970936A20845F0600D163A7 /* RCTTextTransform.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 5970936820845DDE00D163A7 /* RCTTextTransform.h */; };
+		5C245F39205E216A00D936E9 /* RCTInputAccessoryShadowView.m in Sources */ = {isa = PBXBuildFile; fileRef = 5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */; };
 		8F2807C7202D2B6B005D65E6 /* RCTInputAccessoryViewManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */; };
 		8F2807C8202D2B6B005D65E6 /* RCTInputAccessoryView.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */; };
 		8F2807C9202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m in Sources */ = {isa = PBXBuildFile; fileRef = 8F2807C5202D2B6B005D65E6 /* RCTInputAccessoryViewContent.m */; };
@@ -237,9 +237,9 @@
 		5956B12D200FEBAA008D9D16 /* RCTVirtualTextViewManager.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTVirtualTextViewManager.h; sourceTree = "<group>"; };
 		5956B12E200FEBAA008D9D16 /* RCTVirtualTextShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTVirtualTextShadowView.m; sourceTree = "<group>"; };
 		5956B12F200FEBAA008D9D16 /* RCTConvert+Text.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "RCTConvert+Text.m"; sourceTree = "<group>"; };
+		5970936820845DDE00D163A7 /* RCTTextTransform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTTextTransform.h; sourceTree = "<group>"; };
 		5C245F37205E216A00D936E9 /* RCTInputAccessoryShadowView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryShadowView.m; sourceTree = "<group>"; };
 		5C245F38205E216A00D936E9 /* RCTInputAccessoryShadowView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryShadowView.h; sourceTree = "<group>"; };
-		5970936820845DDE00D163A7 /* RCTTextTransform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTTextTransform.h; sourceTree = "<group>"; };
 		8F2807C1202D2B6A005D65E6 /* RCTInputAccessoryViewManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryViewManager.m; sourceTree = "<group>"; };
 		8F2807C2202D2B6A005D65E6 /* RCTInputAccessoryViewContent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RCTInputAccessoryViewContent.h; sourceTree = "<group>"; };
 		8F2807C3202D2B6A005D65E6 /* RCTInputAccessoryView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = RCTInputAccessoryView.m; sourceTree = "<group>"; };
@@ -422,7 +422,7 @@
 		58B511931A9E6C1200147676 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0610;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A287A1D9B048500D4039D = {
@@ -562,20 +562,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -610,20 +621,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = YES;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj b/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
index 46ee2d4a7fe8..4e0099553eed 100644
--- a/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
+++ b/Libraries/Vibration/RCTVibration.xcodeproj/project.pbxproj
@@ -61,7 +61,7 @@
 		832C81781AAF6DEF007FA2F7 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0620;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					832C817F1AAF6DEF007FA2F7 = {
@@ -105,20 +105,31 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_OPTIMIZATION_LEVEL = 0;
 				GCC_PREPROCESSOR_DEFINITIONS = (
 					"DEBUG=1",
@@ -152,20 +163,30 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				ENABLE_NS_ASSERTIONS = NO;
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
+				GCC_NO_COMMON_BLOCKS = YES;
 				GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
 				GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
 				GCC_WARN_INITIALIZER_NOT_FULLY_BRACKETED = YES;
diff --git a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
index f5e60eb16698..406890ccc9f9 100644
--- a/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
+++ b/Libraries/WebSocket/RCTWebSocket.xcodeproj/project.pbxproj
@@ -218,7 +218,7 @@
 		3C86DF3E1ADF2C930047B81A /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0630;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					2D2A28871D9B049200D4039D = {
@@ -343,19 +343,29 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
 				DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
 				ENABLE_STRICT_OBJC_MSGSEND = YES;
+				ENABLE_TESTABILITY = YES;
 				GCC_C_LANGUAGE_STANDARD = gnu99;
 				GCC_DYNAMIC_NO_PIC = NO;
 				GCC_NO_COMMON_BLOCKS = YES;
@@ -393,14 +403,23 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
+				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
+				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
 				COPY_PHASE_STRIP = NO;
diff --git a/RNTester/RNTester.xcodeproj/project.pbxproj b/RNTester/RNTester.xcodeproj/project.pbxproj
index 06921b5616f1..51cef6ad024e 100644
--- a/RNTester/RNTester.xcodeproj/project.pbxproj
+++ b/RNTester/RNTester.xcodeproj/project.pbxproj
@@ -1144,7 +1144,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0820;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					004D289D1AAF61C70097A701 = {
@@ -2091,7 +2091,9 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -2100,9 +2102,13 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -2159,7 +2165,9 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -2168,9 +2176,13 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
index 95e17856e3e5..0c3555d5cfc2 100644
--- a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
+++ b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester-tvOS.xcscheme
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <Scheme
-   LastUpgradeVersion = "0820"
+   LastUpgradeVersion = "0940"
    version = "1.3">
    <BuildAction
       parallelizeBuildables = "NO"
diff --git a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
index 93f81fdc17a4..b3d01b135672 100644
--- a/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
+++ b/RNTester/RNTester.xcodeproj/xcshareddata/xcschemes/RNTester.xcscheme
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <Scheme
-   LastUpgradeVersion = "0820"
+   LastUpgradeVersion = "0940"
    version = "1.3">
    <BuildAction
       parallelizeBuildables = "NO"
diff --git a/RNTester/RNTesterPods.xcodeproj/project.pbxproj b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
index 0620810141cf..1802a7d7a733 100644
--- a/RNTester/RNTesterPods.xcodeproj/project.pbxproj
+++ b/RNTester/RNTesterPods.xcodeproj/project.pbxproj
@@ -203,7 +203,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0820;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					13B07F861A680F5B00A75B9A = {
@@ -415,7 +415,9 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -424,9 +426,13 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -483,7 +489,9 @@
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
 				CLANG_WARN_ASSIGN_ENUM = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
 				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
@@ -492,9 +500,13 @@
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
 				CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES;
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
diff --git a/React/React.xcodeproj/project.pbxproj b/React/React.xcodeproj/project.pbxproj
index d008bf9e2145..b0b6cc74e336 100644
--- a/React/React.xcodeproj/project.pbxproj
+++ b/React/React.xcodeproj/project.pbxproj
@@ -265,7 +265,6 @@
 		2D16E68E1FA4FD3900B85C8A /* RCTTVNavigationEventEmitter.h in Copy Headers */ = {isa = PBXBuildFile; fileRef = 3D0B842D1EC0B51200B2BD8E /* RCTTVNavigationEventEmitter.h */; };
 		2D1D83CD1F74E2CE00615550 /* libprivatedata-tvOS.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 9936F32F1F5F2E5B0010BF04 /* libprivatedata-tvOS.a */; };
 		2D1D83CE1F74E2DA00615550 /* libdouble-conversion.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 3D383D621EBD27B9005632C8 /* libdouble-conversion.a */; };
-		2D1D83EF1F74E76C00615550 /* RCTModalManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 91076A871F743AB00081B4FA /* RCTModalManager.m */; };
 		2D3B5E931D9B087300451313 /* RCTErrorInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = 3EDCA8A41D3591E700450C31 /* RCTErrorInfo.m */; };
 		2D3B5E941D9B087900451313 /* RCTBundleURLProvider.m in Sources */ = {isa = PBXBuildFile; fileRef = 68EFE4ED1CF6EB3900A1DE13 /* RCTBundleURLProvider.m */; };
 		2D3B5E951D9B087C00451313 /* RCTAssert.m in Sources */ = {isa = PBXBuildFile; fileRef = 83CBBA4B1A601E3B00E9B192 /* RCTAssert.m */; };
@@ -334,7 +333,6 @@
 		2D3B5EF11D9B09E700451313 /* UIView+React.m in Sources */ = {isa = PBXBuildFile; fileRef = 13E067541A70F44B002CDEE1 /* UIView+React.m */; };
 		2D74EAFA1DAE9590003B751B /* RCTMultipartDataTask.m in Sources */ = {isa = PBXBuildFile; fileRef = 006FC4131D9B20820057AAAD /* RCTMultipartDataTask.m */; };
 		2D8C2E331DA40441000EE098 /* RCTMultipartStreamReader.m in Sources */ = {isa = PBXBuildFile; fileRef = 001BFCCF1D8381DE008E587E /* RCTMultipartStreamReader.m */; };
-		2DCCC3151FE48142007C5315 /* RCTRedBoxExtraDataViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = FEFAAC9C1FDB89B40057BBE0 /* RCTRedBoxExtraDataViewController.m */; };
 		2DD0EFE11DA84F2800B0C975 /* RCTStatusBarManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 13723B4F1A82FD3C00F88898 /* RCTStatusBarManager.m */; };
 		352DCFF01D19F4C20056D623 /* RCTI18nUtil.m in Sources */ = {isa = PBXBuildFile; fileRef = 352DCFEF1D19F4C20056D623 /* RCTI18nUtil.m */; };
 		369123E11DDC75850095B341 /* RCTJSCSamplingProfiler.m in Sources */ = {isa = PBXBuildFile; fileRef = 369123E01DDC75850095B341 /* RCTJSCSamplingProfiler.m */; };
@@ -3974,7 +3972,7 @@
 		83CBB9F71A601CBA00E9B192 /* Project object */ = {
 			isa = PBXProject;
 			attributes = {
-				LastUpgradeCheck = 0810;
+				LastUpgradeCheck = 0940;
 				ORGANIZATIONNAME = Facebook;
 				TargetAttributes = {
 					139D7E871E25C6D100323FB7 = {
@@ -4232,7 +4230,6 @@
 				C606692F1F3CC60500E67165 /* RCTModuleMethod.mm in Sources */,
 				2D3B5E9F1D9B08AF00451313 /* RCTKeyCommands.m in Sources */,
 				2D3B5EA51D9B08C700451313 /* RCTRootView.m in Sources */,
-				2DCCC3151FE48142007C5315 /* RCTRedBoxExtraDataViewController.m in Sources */,
 				13134C871E296B2A00B9F3CB /* RCTCxxBridge.mm in Sources */,
 				CF2731C31E7B8DF30044CA4F /* RCTDeviceInfo.m in Sources */,
 				599FAA3F1FB274980058CCF6 /* RCTSurfaceRootShadowView.m in Sources */,
@@ -4272,7 +4269,6 @@
 				2D3B5EC61D9B095000451313 /* RCTProfileTrampoline-x86_64.S in Sources */,
 				2D3B5EA61D9B08CA00451313 /* RCTTouchEvent.m in Sources */,
 				2D8C2E331DA40441000EE098 /* RCTMultipartStreamReader.m in Sources */,
-				2D1D83EF1F74E76C00615550 /* RCTModalManager.m in Sources */,
 				59EDBCBC1FDF4E0C003573DE /* RCTScrollViewManager.m in Sources */,
 				59EDBCB01FDF4E0C003573DE /* RCTScrollContentView.m in Sources */,
 				2D3B5EF01D9B09E300451313 /* RCTWrapperViewController.m in Sources */,
@@ -5109,14 +5105,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
@@ -5165,14 +5169,22 @@
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
+				CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
 				CLANG_WARN_BOOL_CONVERSION = YES;
+				CLANG_WARN_COMMA = YES;
 				CLANG_WARN_CONSTANT_CONVERSION = YES;
+				CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
 				CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
 				CLANG_WARN_EMPTY_BODY = YES;
 				CLANG_WARN_ENUM_CONVERSION = YES;
 				CLANG_WARN_INFINITE_RECURSION = YES;
 				CLANG_WARN_INT_CONVERSION = YES;
+				CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
+				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
+				CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
 				CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
+				CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
+				CLANG_WARN_STRICT_PROTOTYPES = YES;
 				CLANG_WARN_SUSPICIOUS_MOVE = YES;
 				CLANG_WARN_UNREACHABLE_CODE = YES;
 				CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;

From 9cfc2c01355c82c82b0c64215ccf55ca7a6247b1 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Tue, 19 Jun 2018 23:54:16 -0700
Subject: [PATCH 0865/1109] Add @flow-strict support to .flowconfig

Summary:
We enforce this config locally in fbsource, lets ensure our flow strict files are run the same way in the github repo.

@public

Reviewed By: sahrens

Differential Revision: D8530133

fbshipit-source-id: 18528992ad6490826431359d5d8c6acd6710a8ae
---
 .flowconfig | 23 +++++++++++++++++++++++
 1 file changed, 23 insertions(+)

diff --git a/.flowconfig b/.flowconfig
index 32624ea479b9..78fb45fa536a 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -73,5 +73,28 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowIssue\\((\\(<VERSION>\\)? *\\(site=[a-z,_]*
 suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
+[lints]
+all=warn
+
+# There is an ESLint rule for this
+unclear-type=off
+
+sketchy-null=off
+sketchy-null-number=warn
+sketchy-null-mixed=warn
+
+# This is noisy for now. We *do* still want to warn on importing types
+# from untyped files, which is covered by untyped-type-import
+untyped-import=off
+
+[strict]
+deprecated-type
+nonstrict-import
+sketchy-null
+unclear-type
+unsafe-getters-setters
+untyped-import
+untyped-type-import
+
 [version]
 ^0.74.0

From eea484297237c66ce5f513a24c31c9c6cf2182be Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 20 Jun 2018 00:35:29 -0700
Subject: [PATCH 0866/1109] Flow strictify possible files in RN core

Summary:
This was done by running the command on: https://our.intern.facebook.com/intern/wiki/Flow_Strict/

```
ag -L --ignore __snapshots__ 'flow strict$|noflow|generated|partially-generated' | ag '\.js$' | xargs ag -l 'flow' | sort > ~/temp
cat ~/temp | xargs ag -L 'flow strict' | xargs sed -i 's/flow$/flow strict/'
cat ~/temp | xargs ag -L 'flow strict$' | xargs sed -i 's/flow strict-local$/flow strict/'
until flow; do flow --json | jq -r '.errors[].message[0].path' | sort | uniq | xargs hg revert; done
```

Reviewed By: sahrens

Differential Revision: D8530207

fbshipit-source-id: c28c7ac5ed3e9b80f3d126d5f30463be8a8a744d
---
 Libraries/Animated/src/SpringConfig.js                 | 2 +-
 Libraries/Blob/BlobRegistry.js                         | 2 +-
 Libraries/Blob/BlobTypes.js                            | 2 +-
 Libraries/Blob/__mocks__/BlobModule.js                 | 2 +-
 Libraries/Blob/__mocks__/FileReaderModule.js           | 2 +-
 Libraries/BugReporting/dumpReactTree.js                | 2 +-
 Libraries/Components/View/ReactNativeViewAttributes.js | 2 +-
 Libraries/Components/View/ViewAccessibility.js         | 2 +-
 Libraries/Image/AssetRegistry.js                       | 2 +-
 Libraries/Image/RelativeImageStub.js                   | 2 +-
 Libraries/Performance/QuickPerformanceLogger.js        | 2 +-
 Libraries/ReactNative/FabricUIManager.js               | 2 +-
 Libraries/StyleSheet/EdgeInsetsPropType.js             | 2 +-
 Libraries/StyleSheet/LayoutPropTypes.js                | 2 +-
 Libraries/StyleSheet/PointPropType.js                  | 2 +-
 Libraries/Text/TextAncestor.js                         | 2 +-
 Libraries/Types/CoreEventTypes.js                      | 2 +-
 Libraries/Utilities/PlatformOS.ios.js                  | 2 +-
 Libraries/Utilities/SceneTracker.js                    | 2 +-
 Libraries/Utilities/clamp.js                           | 2 +-
 Libraries/Utilities/groupByEveryN.js                   | 2 +-
 Libraries/Utilities/logError.js                        | 2 +-
 Libraries/Utilities/mapWithSeparator.js                | 2 +-
 Libraries/YellowBox/UI/YellowBoxImageSource.js         | 2 +-
 Libraries/YellowBox/UI/YellowBoxStyle.js               | 2 +-
 Libraries/react-native/react-native-interface.js       | 2 +-
 Libraries/vendor/core/ErrorUtils.js                    | 2 +-
 Libraries/vendor/core/_shouldPolyfillES6Collection.js  | 2 +-
 RNTester/js/ImageEditingExample.js                     | 2 +-
 RNTester/js/RNTesterActions.js                         | 2 +-
 local-cli/bundle/assetPathUtils.js                     | 2 +-
 local-cli/bundle/filterPlatformAssetScales.js          | 2 +-
 local-cli/bundle/getAssetDestPathAndroid.js            | 2 +-
 local-cli/bundle/getAssetDestPathIOS.js                | 2 +-
 local-cli/core/Constants.js                            | 2 +-
 local-cli/runAndroid/adb.js                            | 2 +-
 local-cli/runIOS/findXcodeProject.js                   | 2 +-
 local-cli/runIOS/parseIOSDevicesList.js                | 2 +-
 local-cli/server/util/debugger-ui/deltaUrlToBlobUrl.js | 2 +-
 local-cli/util/findReactNativeScripts.js               | 2 +-
 local-cli/util/findSymlinkedModules.js                 | 2 +-
 41 files changed, 41 insertions(+), 41 deletions(-)

diff --git a/Libraries/Animated/src/SpringConfig.js b/Libraries/Animated/src/SpringConfig.js
index ca25a115cb09..456af9c40ec1 100644
--- a/Libraries/Animated/src/SpringConfig.js
+++ b/Libraries/Animated/src/SpringConfig.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Blob/BlobRegistry.js b/Libraries/Blob/BlobRegistry.js
index d78a9d26656e..445fe6bb8558 100644
--- a/Libraries/Blob/BlobRegistry.js
+++ b/Libraries/Blob/BlobRegistry.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 
diff --git a/Libraries/Blob/BlobTypes.js b/Libraries/Blob/BlobTypes.js
index b03922f24f32..2e5be53e1961 100644
--- a/Libraries/Blob/BlobTypes.js
+++ b/Libraries/Blob/BlobTypes.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 
diff --git a/Libraries/Blob/__mocks__/BlobModule.js b/Libraries/Blob/__mocks__/BlobModule.js
index 2542c3a9339a..e904d2929dd7 100644
--- a/Libraries/Blob/__mocks__/BlobModule.js
+++ b/Libraries/Blob/__mocks__/BlobModule.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 const BlobModule = {
diff --git a/Libraries/Blob/__mocks__/FileReaderModule.js b/Libraries/Blob/__mocks__/FileReaderModule.js
index f5ccc39d36e2..0f35aa89ace0 100644
--- a/Libraries/Blob/__mocks__/FileReaderModule.js
+++ b/Libraries/Blob/__mocks__/FileReaderModule.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 const FileReaderModule = {
diff --git a/Libraries/BugReporting/dumpReactTree.js b/Libraries/BugReporting/dumpReactTree.js
index 7cbb2530f205..ead8f4bdd76c 100644
--- a/Libraries/BugReporting/dumpReactTree.js
+++ b/Libraries/BugReporting/dumpReactTree.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Components/View/ReactNativeViewAttributes.js b/Libraries/Components/View/ReactNativeViewAttributes.js
index 7bf8117710ef..bc4ca6b3d229 100644
--- a/Libraries/Components/View/ReactNativeViewAttributes.js
+++ b/Libraries/Components/View/ReactNativeViewAttributes.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index b6e46f5b65a9..4a9ebc172a13 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Image/AssetRegistry.js b/Libraries/Image/AssetRegistry.js
index ad1b495af428..b050a9e239cd 100644
--- a/Libraries/Image/AssetRegistry.js
+++ b/Libraries/Image/AssetRegistry.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 'use strict';
diff --git a/Libraries/Image/RelativeImageStub.js b/Libraries/Image/RelativeImageStub.js
index ab845a274d27..dcdeb9b916ac 100644
--- a/Libraries/Image/RelativeImageStub.js
+++ b/Libraries/Image/RelativeImageStub.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Performance/QuickPerformanceLogger.js b/Libraries/Performance/QuickPerformanceLogger.js
index 6d50626b1fe7..abc16ab45fb2 100644
--- a/Libraries/Performance/QuickPerformanceLogger.js
+++ b/Libraries/Performance/QuickPerformanceLogger.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/ReactNative/FabricUIManager.js b/Libraries/ReactNative/FabricUIManager.js
index f1b06ede5c17..20c855b3deaf 100644
--- a/Libraries/ReactNative/FabricUIManager.js
+++ b/Libraries/ReactNative/FabricUIManager.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 'use strict';
diff --git a/Libraries/StyleSheet/EdgeInsetsPropType.js b/Libraries/StyleSheet/EdgeInsetsPropType.js
index 10a6bf6104eb..7d9ea680d8fc 100644
--- a/Libraries/StyleSheet/EdgeInsetsPropType.js
+++ b/Libraries/StyleSheet/EdgeInsetsPropType.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/StyleSheet/LayoutPropTypes.js b/Libraries/StyleSheet/LayoutPropTypes.js
index 4a12e827dde7..ce99d659a3fd 100644
--- a/Libraries/StyleSheet/LayoutPropTypes.js
+++ b/Libraries/StyleSheet/LayoutPropTypes.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/StyleSheet/PointPropType.js b/Libraries/StyleSheet/PointPropType.js
index 008c675048da..86d40b5afee2 100644
--- a/Libraries/StyleSheet/PointPropType.js
+++ b/Libraries/StyleSheet/PointPropType.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Text/TextAncestor.js b/Libraries/Text/TextAncestor.js
index 147d9763b2d6..53a109c9d88b 100644
--- a/Libraries/Text/TextAncestor.js
+++ b/Libraries/Text/TextAncestor.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 
diff --git a/Libraries/Types/CoreEventTypes.js b/Libraries/Types/CoreEventTypes.js
index ede607f0c706..0714dc2316c7 100644
--- a/Libraries/Types/CoreEventTypes.js
+++ b/Libraries/Types/CoreEventTypes.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 
diff --git a/Libraries/Utilities/PlatformOS.ios.js b/Libraries/Utilities/PlatformOS.ios.js
index 90917af1e34e..a1f28837ac36 100644
--- a/Libraries/Utilities/PlatformOS.ios.js
+++ b/Libraries/Utilities/PlatformOS.ios.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Utilities/SceneTracker.js b/Libraries/Utilities/SceneTracker.js
index 5d719d8f7b20..4928efaa4e67 100644
--- a/Libraries/Utilities/SceneTracker.js
+++ b/Libraries/Utilities/SceneTracker.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Utilities/clamp.js b/Libraries/Utilities/clamp.js
index a3f0a2c957e7..bbeb9701b696 100644
--- a/Libraries/Utilities/clamp.js
+++ b/Libraries/Utilities/clamp.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Utilities/groupByEveryN.js b/Libraries/Utilities/groupByEveryN.js
index eb7dbb8eb24c..eae0eb0a3d37 100644
--- a/Libraries/Utilities/groupByEveryN.js
+++ b/Libraries/Utilities/groupByEveryN.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 /**
diff --git a/Libraries/Utilities/logError.js b/Libraries/Utilities/logError.js
index f0ed0b63a0c0..b09a7be5e164 100644
--- a/Libraries/Utilities/logError.js
+++ b/Libraries/Utilities/logError.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/Utilities/mapWithSeparator.js b/Libraries/Utilities/mapWithSeparator.js
index f94459404a8c..776049b2ccf6 100644
--- a/Libraries/Utilities/mapWithSeparator.js
+++ b/Libraries/Utilities/mapWithSeparator.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/YellowBox/UI/YellowBoxImageSource.js b/Libraries/YellowBox/UI/YellowBoxImageSource.js
index dca95fa82316..1d3fc2e979c7 100644
--- a/Libraries/YellowBox/UI/YellowBoxImageSource.js
+++ b/Libraries/YellowBox/UI/YellowBoxImageSource.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow strict-local
+ * @flow
  * @format
  */
 
diff --git a/Libraries/YellowBox/UI/YellowBoxStyle.js b/Libraries/YellowBox/UI/YellowBoxStyle.js
index 2ceec6f28d48..32aa375e0c67 100644
--- a/Libraries/YellowBox/UI/YellowBoxStyle.js
+++ b/Libraries/YellowBox/UI/YellowBoxStyle.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow strict-local
+ * @flow strict
  * @format
  */
 
diff --git a/Libraries/react-native/react-native-interface.js b/Libraries/react-native/react-native-interface.js
index 23fa37cdab9e..6e37e8b14d6f 100644
--- a/Libraries/react-native/react-native-interface.js
+++ b/Libraries/react-native/react-native-interface.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/Libraries/vendor/core/ErrorUtils.js b/Libraries/vendor/core/ErrorUtils.js
index f64b7fdb17f5..4822d8684e0e 100644
--- a/Libraries/vendor/core/ErrorUtils.js
+++ b/Libraries/vendor/core/ErrorUtils.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 /* eslint-disable strict */
diff --git a/Libraries/vendor/core/_shouldPolyfillES6Collection.js b/Libraries/vendor/core/_shouldPolyfillES6Collection.js
index 4993fa38b435..8b027183b9cb 100644
--- a/Libraries/vendor/core/_shouldPolyfillES6Collection.js
+++ b/Libraries/vendor/core/_shouldPolyfillES6Collection.js
@@ -6,7 +6,7 @@
  *
  * @format
  * @preventMunge
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/RNTester/js/ImageEditingExample.js b/RNTester/js/ImageEditingExample.js
index 048869c26861..830e1276ef6e 100644
--- a/RNTester/js/ImageEditingExample.js
+++ b/RNTester/js/ImageEditingExample.js
@@ -5,5 +5,5 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
diff --git a/RNTester/js/RNTesterActions.js b/RNTester/js/RNTesterActions.js
index 69fc8b9ea5cc..d121569ab36a 100644
--- a/RNTester/js/RNTesterActions.js
+++ b/RNTester/js/RNTesterActions.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/local-cli/bundle/assetPathUtils.js b/local-cli/bundle/assetPathUtils.js
index 95d2f6c6939e..bcfc880ddf63 100644
--- a/local-cli/bundle/assetPathUtils.js
+++ b/local-cli/bundle/assetPathUtils.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/local-cli/bundle/filterPlatformAssetScales.js b/local-cli/bundle/filterPlatformAssetScales.js
index 0843b75dce6b..d6a9f78cced7 100644
--- a/local-cli/bundle/filterPlatformAssetScales.js
+++ b/local-cli/bundle/filterPlatformAssetScales.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 
diff --git a/local-cli/bundle/getAssetDestPathAndroid.js b/local-cli/bundle/getAssetDestPathAndroid.js
index f827e3ed9e52..316b56a4dfbb 100644
--- a/local-cli/bundle/getAssetDestPathAndroid.js
+++ b/local-cli/bundle/getAssetDestPathAndroid.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/local-cli/bundle/getAssetDestPathIOS.js b/local-cli/bundle/getAssetDestPathIOS.js
index cca4a87d773c..5e6d3a6352fb 100644
--- a/local-cli/bundle/getAssetDestPathIOS.js
+++ b/local-cli/bundle/getAssetDestPathIOS.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/local-cli/core/Constants.js b/local-cli/core/Constants.js
index 73fddbbb1035..38d6f22292c4 100644
--- a/local-cli/core/Constants.js
+++ b/local-cli/core/Constants.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 
diff --git a/local-cli/runAndroid/adb.js b/local-cli/runAndroid/adb.js
index 3c6b980d2103..310fbad04ab7 100644
--- a/local-cli/runAndroid/adb.js
+++ b/local-cli/runAndroid/adb.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 const child_process = require('child_process');
diff --git a/local-cli/runIOS/findXcodeProject.js b/local-cli/runIOS/findXcodeProject.js
index c154221b86cc..57260a37253a 100644
--- a/local-cli/runIOS/findXcodeProject.js
+++ b/local-cli/runIOS/findXcodeProject.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/local-cli/runIOS/parseIOSDevicesList.js b/local-cli/runIOS/parseIOSDevicesList.js
index a85ea352f88a..fedb42604210 100644
--- a/local-cli/runIOS/parseIOSDevicesList.js
+++ b/local-cli/runIOS/parseIOSDevicesList.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/local-cli/server/util/debugger-ui/deltaUrlToBlobUrl.js b/local-cli/server/util/debugger-ui/deltaUrlToBlobUrl.js
index d611062952aa..d916ad4e955e 100644
--- a/local-cli/server/util/debugger-ui/deltaUrlToBlobUrl.js
+++ b/local-cli/server/util/debugger-ui/deltaUrlToBlobUrl.js
@@ -4,7 +4,7 @@
  * This source code is licensed under the MIT license found in the
  * LICENSE file in the root directory of this source tree.
  *
- * @flow
+ * @flow strict
  * @format
  */
 
diff --git a/local-cli/util/findReactNativeScripts.js b/local-cli/util/findReactNativeScripts.js
index 6b5d1520623a..26e8b7decfed 100644
--- a/local-cli/util/findReactNativeScripts.js
+++ b/local-cli/util/findReactNativeScripts.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 'use strict';
diff --git a/local-cli/util/findSymlinkedModules.js b/local-cli/util/findSymlinkedModules.js
index 428ed3ead056..fd6eecdba53e 100644
--- a/local-cli/util/findSymlinkedModules.js
+++ b/local-cli/util/findSymlinkedModules.js
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow
+ * @flow strict
  */
 
 const path = require('path');

From 5ae531cba79db9f2f0c6d7ce55985a8a8f7d68cf Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 20 Jun 2018 09:39:39 -0700
Subject: [PATCH 0867/1109] Export Flow type for Image

Summary: Improving the exported type of Image on android so we can work on migrating the implementation off of createReactClass and propTypes.

Reviewed By: yungsters

Differential Revision: D8530549

fbshipit-source-id: dab0cb5034464b7939a0b04e8912bae916690e8c
---
 Libraries/Image/Image.android.js | 261 +++++++++++++++++--------------
 1 file changed, 145 insertions(+), 116 deletions(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index 350bba68ea89..ca93fab77f57 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -14,6 +14,7 @@ const ImageStylePropTypes = require('ImageStylePropTypes');
 const NativeMethodsMixin = require('NativeMethodsMixin');
 const NativeModules = require('NativeModules');
 const React = require('React');
+const ReactNative = require('ReactNative');
 const PropTypes = require('prop-types');
 const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const StyleSheet = require('StyleSheet');
@@ -32,11 +33,149 @@ const {ImageLoader} = NativeModules;
 const RKImage = requireNativeComponent('RCTImageView');
 const RCTTextInlineImage = requireNativeComponent('RCTTextInlineImage');
 
+import type {ImageProps as ImagePropsType} from 'ImageProps';
+
 let _requestId = 1;
 function generateRequestId() {
   return _requestId++;
 }
 
+const ImageProps = {
+  ...ViewPropTypes,
+  style: StyleSheetPropType(ImageStylePropTypes),
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#source
+   */
+  source: PropTypes.oneOfType([
+    PropTypes.shape({
+      uri: PropTypes.string,
+      headers: PropTypes.objectOf(PropTypes.string),
+    }),
+    // Opaque type returned by require('./image.jpg')
+    PropTypes.number,
+    // Multiple sources
+    PropTypes.arrayOf(
+      PropTypes.shape({
+        uri: PropTypes.string,
+        width: PropTypes.number,
+        height: PropTypes.number,
+        headers: PropTypes.objectOf(PropTypes.string),
+      }),
+    ),
+  ]),
+  /**
+   * blurRadius: the blur radius of the blur filter added to the image
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#blurradius
+   */
+  blurRadius: PropTypes.number,
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#defaultsource
+   */
+  defaultSource: PropTypes.number,
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#loadingindicatorsource
+   */
+  loadingIndicatorSource: PropTypes.oneOfType([
+    PropTypes.shape({
+      uri: PropTypes.string,
+    }),
+    // Opaque type returned by require('./image.jpg')
+    PropTypes.number,
+  ]),
+  progressiveRenderingEnabled: PropTypes.bool,
+  fadeDuration: PropTypes.number,
+  /**
+   * Invoked on load start
+   */
+  onLoadStart: PropTypes.func,
+  /**
+   * Invoked on load error
+   */
+  onError: PropTypes.func,
+  /**
+   * Invoked when load completes successfully
+   */
+  onLoad: PropTypes.func,
+  /**
+   * Invoked when load either succeeds or fails
+   */
+  onLoadEnd: PropTypes.func,
+  /**
+   * Used to locate this view in end-to-end tests.
+   */
+  testID: PropTypes.string,
+  /**
+   * The mechanism that should be used to resize the image when the image's dimensions
+   * differ from the image view's dimensions. Defaults to `auto`.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#resizemethod
+   */
+  resizeMethod: PropTypes.oneOf(['auto', 'resize', 'scale']),
+  /**
+   * Determines how to resize the image when the frame doesn't match the raw
+   * image dimensions.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#resizemode
+   */
+  resizeMode: PropTypes.oneOf([
+    'cover',
+    'contain',
+    'stretch',
+    'repeat',
+    'center',
+  ]),
+};
+
+function getSize(
+  url: string,
+  success: (width: number, height: number) => void,
+  failure?: (error: any) => void,
+) {
+  return ImageLoader.getSize(url)
+    .then(function(sizes) {
+      success(sizes.width, sizes.height);
+    })
+    .catch(
+      failure ||
+        function() {
+          console.warn('Failed to get size for image: ' + url);
+        },
+    );
+}
+
+function prefetch(url: string, callback: ?Function) {
+  const requestId = generateRequestId();
+  callback && callback(requestId);
+  return ImageLoader.prefetchImage(url, requestId);
+}
+
+function abortPrefetch(requestId: number) {
+  ImageLoader.abortRequest(requestId);
+}
+
+/**
+ * Perform cache interrogation.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#querycache
+ */
+async function queryCache(
+  urls: Array<string>,
+): Promise<Map<string, 'memory' | 'disk'>> {
+  return await ImageLoader.queryCache(urls);
+}
+
+declare class ImageComponentType extends ReactNative.NativeComponent<
+  ImagePropsType,
+> {
+  static getSize: typeof getSize;
+  static prefetch: typeof prefetch;
+  static abortPrefetch: typeof abortPrefetch;
+  static queryCache: typeof queryCache;
+  static resolveAssetSource: typeof resolveAssetSource;
+  static propTypes: typeof ImageProps;
+}
+
 /**
  * A React component for displaying different types of images,
  * including network images, static resources, temporary local images, and
@@ -46,110 +185,10 @@ function generateRequestId() {
  */
 const Image = createReactClass({
   displayName: 'Image',
-  propTypes: {
-    ...ViewPropTypes,
-    style: StyleSheetPropType(ImageStylePropTypes),
-    /**
-     * See https://facebook.github.io/react-native/docs/image.html#source
-     */
-    source: PropTypes.oneOfType([
-      PropTypes.shape({
-        uri: PropTypes.string,
-        headers: PropTypes.objectOf(PropTypes.string),
-      }),
-      // Opaque type returned by require('./image.jpg')
-      PropTypes.number,
-      // Multiple sources
-      PropTypes.arrayOf(
-        PropTypes.shape({
-          uri: PropTypes.string,
-          width: PropTypes.number,
-          height: PropTypes.number,
-          headers: PropTypes.objectOf(PropTypes.string),
-        }),
-      ),
-    ]),
-    /**
-     * blurRadius: the blur radius of the blur filter added to the image
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#blurradius
-     */
-    blurRadius: PropTypes.number,
-    /**
-     * See https://facebook.github.io/react-native/docs/image.html#defaultsource
-     */
-    defaultSource: PropTypes.number,
-    /**
-     * See https://facebook.github.io/react-native/docs/image.html#loadingindicatorsource
-     */
-    loadingIndicatorSource: PropTypes.oneOfType([
-      PropTypes.shape({
-        uri: PropTypes.string,
-      }),
-      // Opaque type returned by require('./image.jpg')
-      PropTypes.number,
-    ]),
-    progressiveRenderingEnabled: PropTypes.bool,
-    fadeDuration: PropTypes.number,
-    /**
-     * Invoked on load start
-     */
-    onLoadStart: PropTypes.func,
-    /**
-     * Invoked on load error
-     */
-    onError: PropTypes.func,
-    /**
-     * Invoked when load completes successfully
-     */
-    onLoad: PropTypes.func,
-    /**
-     * Invoked when load either succeeds or fails
-     */
-    onLoadEnd: PropTypes.func,
-    /**
-     * Used to locate this view in end-to-end tests.
-     */
-    testID: PropTypes.string,
-    /**
-     * The mechanism that should be used to resize the image when the image's dimensions
-     * differ from the image view's dimensions. Defaults to `auto`.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#resizemethod
-     */
-    resizeMethod: PropTypes.oneOf(['auto', 'resize', 'scale']),
-    /**
-     * Determines how to resize the image when the frame doesn't match the raw
-     * image dimensions.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#resizemode
-     */
-    resizeMode: PropTypes.oneOf([
-      'cover',
-      'contain',
-      'stretch',
-      'repeat',
-      'center',
-    ]),
-  },
+  propTypes: ImageProps,
 
   statics: {
-    getSize(
-      url: string,
-      success: (width: number, height: number) => void,
-      failure?: (error: any) => void,
-    ) {
-      return ImageLoader.getSize(url)
-        .then(function(sizes) {
-          success(sizes.width, sizes.height);
-        })
-        .catch(
-          failure ||
-            function() {
-              console.warn('Failed to get size for image: ' + url);
-            },
-        );
-    },
+    getSize,
 
     /**
      * Prefetches a remote image for later use by downloading it to the disk
@@ -157,31 +196,21 @@ const Image = createReactClass({
      *
      * See https://facebook.github.io/react-native/docs/image.html#prefetch
      */
-    prefetch(url: string, callback: ?Function) {
-      const requestId = generateRequestId();
-      callback && callback(requestId);
-      return ImageLoader.prefetchImage(url, requestId);
-    },
+    prefetch,
 
     /**
      * Abort prefetch request.
      *
      * See https://facebook.github.io/react-native/docs/image.html#abortprefetch
      */
-    abortPrefetch(requestId: number) {
-      ImageLoader.abortRequest(requestId);
-    },
+    abortPrefetch,
 
     /**
      * Perform cache interrogation.
      *
      * See https://facebook.github.io/react-native/docs/image.html#querycache
      */
-    async queryCache(
-      urls: Array<string>,
-    ): Promise<Map<string, 'memory' | 'disk'>> {
-      return await ImageLoader.queryCache(urls);
-    },
+    queryCache,
 
     /**
      * Resolves an asset reference into an object.
@@ -281,4 +310,4 @@ const styles = StyleSheet.create({
   },
 });
 
-module.exports = Image;
+module.exports = ((Image: any): Class<ImageComponentType>);

From 746b503024f223a6f123d1d4292577329cb22594 Mon Sep 17 00:00:00 2001
From: Hoa Dinh <dvh@fb.com>
Date: Wed, 20 Jun 2018 09:46:36 -0700
Subject: [PATCH 0868/1109] Fixed RCTAssert()

Reviewed By: zats

Differential Revision: D8529663

fbshipit-source-id: ddedf1daa153f25bc62db19b8e1ace32b4ab3201
---
 React/Base/RCTAssert.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/Base/RCTAssert.h b/React/Base/RCTAssert.h
index 95d210a5e0ce..6117390db448 100644
--- a/React/Base/RCTAssert.h
+++ b/React/Base/RCTAssert.h
@@ -24,7 +24,7 @@ RCT_EXTERN BOOL RCTIsMainQueue(void);
   if ((condition) == 0) { \
     _RCTAssertFormat(#condition, __FILE__, __LINE__, __func__, __VA_ARGS__); \
     if (RCT_NSASSERT) { \
-      [[NSAssertionHandler currentHandler] handleFailureInFunction:@(__func__) \
+      [[NSAssertionHandler currentHandler] handleFailureInFunction:(NSString * _Nonnull)@(__func__) \
         file:(NSString * _Nonnull)@(__FILE__) lineNumber:__LINE__ description:__VA_ARGS__]; \
     } \
   } \

From adb6929b3646985a582ce24d308db50e6af823db Mon Sep 17 00:00:00 2001
From: Hoa Dinh <dvh@fb.com>
Date: Wed, 20 Jun 2018 09:50:29 -0700
Subject: [PATCH 0869/1109] Fixed build eats

Reviewed By: skotchvail

Differential Revision: D8529938

fbshipit-source-id: 6a97d2c54757d7e75fe8731efe24704cf7fdf87c
---
 React/Views/ScrollView/RCTScrollView.m | 6 +++++-
 1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/React/Views/ScrollView/RCTScrollView.m b/React/Views/ScrollView/RCTScrollView.m
index f2d4da1ecff5..58661fa78488 100644
--- a/React/Views/ScrollView/RCTScrollView.m
+++ b/React/Views/ScrollView/RCTScrollView.m
@@ -393,7 +393,9 @@ - (instancetype)initWithEventDispatcher:(RCTEventDispatcher *)eventDispatcher
     // doesn't do weird things to UIScrollView insets automatically
     // and keeps it as an opt-in behavior.
     if ([_scrollView respondsToSelector:@selector(setContentInsetAdjustmentBehavior:)]) {
+      if (@available(iOS 11.0, *)) {
         _scrollView.contentInsetAdjustmentBehavior = UIScrollViewContentInsetAdjustmentNever;
+      }
     }
 #endif
 
@@ -1034,7 +1036,9 @@ - (void)setContentInsetAdjustmentBehavior:(UIScrollViewContentInsetAdjustmentBeh
   // `contentInsetAdjustmentBehavior` is available since iOS 11.
   if ([_scrollView respondsToSelector:@selector(setContentInsetAdjustmentBehavior:)]) {
     CGPoint contentOffset = _scrollView.contentOffset;
-    _scrollView.contentInsetAdjustmentBehavior = behavior;
+    if (@available(iOS 11.0, *)) {
+      _scrollView.contentInsetAdjustmentBehavior = behavior;
+    }
     _scrollView.contentOffset = contentOffset;
   }
 }

From 04fa721ed52316f47706f12f4121e88573ad94d7 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Wed, 20 Jun 2018 10:49:39 -0700
Subject: [PATCH 0870/1109] Bump metro@0.40.0

Summary:
@public

This new version of metro replaces the `getProjectRoots()` config param by `getProjectRoot()` (which is used as the main folder for calculating relative paths of files, etc) and `getWatchFolders()` (which is used to know which files/folder to crawl when starting metro).

More info: https://github.com/facebook/metro/commit/3bdf386d145df0aa9bc0b195ba251ddc81da081d

[skip-ci]

Reviewed By: yungsters, mmmulani

Differential Revision: D8538986

fbshipit-source-id: 2afc33950334a278364debb39f34ef0fe0535894
---
 babel-preset/package.json | 2 +-
 package.json              | 8 ++++----
 2 files changed, 5 insertions(+), 5 deletions(-)

diff --git a/babel-preset/package.json b/babel-preset/package.json
index e69445202ca8..332842f451a1 100644
--- a/babel-preset/package.json
+++ b/babel-preset/package.json
@@ -41,6 +41,6 @@
     "@babel/plugin-transform-template-literals": "7.0.0-beta.47",
     "@babel/plugin-transform-unicode-regex": "7.0.0-beta.47",
     "@babel/template": "7.0.0-beta.47",
-    "metro-babel7-plugin-react-transform": "^0.39.1"
+    "metro-babel7-plugin-react-transform": "^0.40.0"
   }
 }
diff --git a/package.json b/package.json
index e8f5a895c96d..6a2f4a243223 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.39.1",
-    "metro-babel-register": "^0.39.1",
-    "metro-core": "^0.39.1",
-    "metro-memory-fs": "^0.39.1",
+    "metro": "^0.40.0",
+    "metro-babel-register": "^0.40.0",
+    "metro-core": "^0.40.0",
+    "metro-memory-fs": "^0.40.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 4c6dece09c6cc0b9b010670408bd395759dc3a77 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 20 Jun 2018 23:47:40 -0700
Subject: [PATCH 0871/1109] Animated Example using Image

Summary: Need to test a potential issue with Animated.Image on Android. Adding a RNTester example to exercise it.

Reviewed By: yungsters

Differential Revision: D8559440

fbshipit-source-id: 4319d958de146c177cb0bd4b84679b773ce50833
---
 RNTester/js/AnimatedExample.js | 53 ++++++++++++++++++++++++++++++++++
 1 file changed, 53 insertions(+)

diff --git a/RNTester/js/AnimatedExample.js b/RNTester/js/AnimatedExample.js
index d11cbef527b0..490f70371696 100644
--- a/RNTester/js/AnimatedExample.js
+++ b/RNTester/js/AnimatedExample.js
@@ -222,6 +222,59 @@ exports.examples = [
       );
     },
   },
+  {
+    title: 'Rotating Images',
+    description: 'Simple Animated.Image rotation.',
+    render: function() {
+      this.anim = this.anim || new Animated.Value(0);
+      return (
+        <View>
+          <RNTesterButton
+            onPress={() => {
+              Animated.spring(this.anim, {
+                toValue: 0, // Returns to the start
+                velocity: 3, // Velocity makes it move
+                tension: -10, // Slow
+                friction: 1, // Oscillate a lot
+              }).start();
+            }}>
+            Press to Spin it!
+          </RNTesterButton>
+          <Animated.Image
+            source={require('./bunny.png')}
+            style={[
+              {width: 70, height: 70},
+              {
+                transform: [
+                  {
+                    scale: this.anim.interpolate({
+                      inputRange: [0, 1],
+                      outputRange: [1, 10],
+                    }),
+                  },
+                  {
+                    translateX: this.anim.interpolate({
+                      inputRange: [0, 1],
+                      outputRange: [0, 100],
+                    }),
+                  },
+                  {
+                    rotate: this.anim.interpolate({
+                      inputRange: [0, 1],
+                      outputRange: [
+                        '0deg',
+                        '360deg', // 'deg' or 'rad'
+                      ],
+                    }),
+                  },
+                ],
+              },
+            ]}
+          />
+        </View>
+      );
+    },
+  },
   {
     title: 'Continuous Interactions',
     description:

From 8de402d7542105299eb8713e10e9f1bf2e29a365 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Wed, 20 Jun 2018 23:55:00 -0700
Subject: [PATCH 0872/1109] Flow type Image.android.js

Summary: This brings Image a bit more inline with the .ios.js counterpart.

Reviewed By: yungsters

Differential Revision: D8557495

fbshipit-source-id: 263da529d1a2541b0168745c0141c3fc622a1883
---
 Libraries/Image/Image.android.js | 234 +++++++++++++++----------------
 1 file changed, 114 insertions(+), 120 deletions(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index ca93fab77f57..d0e685a5e642 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -11,18 +11,15 @@
 'use strict';
 
 const ImageStylePropTypes = require('ImageStylePropTypes');
-const NativeMethodsMixin = require('NativeMethodsMixin');
 const NativeModules = require('NativeModules');
 const React = require('React');
 const ReactNative = require('ReactNative');
 const PropTypes = require('prop-types');
-const ReactNativeViewAttributes = require('ReactNativeViewAttributes');
 const StyleSheet = require('StyleSheet');
 const StyleSheetPropType = require('StyleSheetPropType');
 const TextAncestor = require('TextAncestor');
 const ViewPropTypes = require('ViewPropTypes');
 
-const createReactClass = require('create-react-class');
 const flattenStyle = require('flattenStyle');
 const merge = require('merge');
 const requireNativeComponent = require('requireNativeComponent');
@@ -183,126 +180,123 @@ declare class ImageComponentType extends ReactNative.NativeComponent<
  *
  * See https://facebook.github.io/react-native/docs/image.html
  */
-const Image = createReactClass({
-  displayName: 'Image',
-  propTypes: ImageProps,
-
-  statics: {
-    getSize,
-
-    /**
-     * Prefetches a remote image for later use by downloading it to the disk
-     * cache
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#prefetch
-     */
-    prefetch,
-
-    /**
-     * Abort prefetch request.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#abortprefetch
-     */
-    abortPrefetch,
-
-    /**
-     * Perform cache interrogation.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#querycache
-     */
-    queryCache,
-
-    /**
-     * Resolves an asset reference into an object.
-     *
-     * See https://facebook.github.io/react-native/docs/image.html#resolveassetsource
-     */
-    resolveAssetSource: resolveAssetSource,
-  },
-
-  mixins: [NativeMethodsMixin],
-
-  /**
-   * `NativeMethodsMixin` will look for this when invoking `setNativeProps`. We
-   * make `this` look like an actual native component class.
-   */
-  viewConfig: {
-    uiViewClassName: 'RCTView',
-    validAttributes: ReactNativeViewAttributes.RCTView,
-  },
+let Image = (
+  props: ImagePropsType,
+  forwardedRef: ?React.Ref<'RCTTextInlineImage' | 'RKImage'>,
+) => {
+  const source = resolveAssetSource(props.source);
+  const defaultSource = resolveAssetSource(props.defaultSource);
+  const loadingIndicatorSource = resolveAssetSource(
+    props.loadingIndicatorSource,
+  );
+
+  // As opposed to the ios version, here we render `null` when there is no source, source.uri
+  // or source array.
+
+  if (source && source.uri === '') {
+    console.warn('source.uri should not be an empty string');
+  }
+
+  if (props.src) {
+    console.warn(
+      'The <Image> component requires a `source` property rather than `src`.',
+    );
+  }
 
-  render: function() {
-    const source = resolveAssetSource(this.props.source);
-    const defaultSource = resolveAssetSource(this.props.defaultSource);
-    const loadingIndicatorSource = resolveAssetSource(
-      this.props.loadingIndicatorSource,
+  if (props.children) {
+    throw new Error(
+      'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.',
     );
+  }
 
-    // As opposed to the ios version, here we render `null` when there is no source, source.uri
-    // or source array.
-
-    if (source && source.uri === '') {
-      console.warn('source.uri should not be an empty string');
-    }
-
-    if (this.props.src) {
-      console.warn(
-        'The <Image> component requires a `source` property rather than `src`.',
-      );
-    }
-
-    if (this.props.children) {
-      throw new Error(
-        'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.',
-      );
-    }
-
-    if (this.props.defaultSource && this.props.loadingIndicatorSource) {
-      throw new Error(
-        'The <Image> component cannot have defaultSource and loadingIndicatorSource at the same time. Please use either defaultSource or loadingIndicatorSource.',
-      );
-    }
-
-    if (!source || (!source.uri && !Array.isArray(source))) {
-      return null;
-    }
-
-    let style;
-    let sources;
-    if (source.uri) {
-      const {width, height} = source;
-      style = flattenStyle([{width, height}, styles.base, this.props.style]);
-      sources = [{uri: source.uri}];
-    } else {
-      style = flattenStyle([styles.base, this.props.style]);
-      sources = source;
-    }
-
-    const {onLoadStart, onLoad, onLoadEnd, onError} = this.props;
-    const nativeProps = merge(this.props, {
-      style,
-      shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),
-      src: sources,
-      headers: source.headers,
-      defaultSrc: defaultSource ? defaultSource.uri : null,
-      loadingIndicatorSrc: loadingIndicatorSource
-        ? loadingIndicatorSource.uri
-        : null,
-    });
-
-    return (
-      <TextAncestor.Consumer>
-        {hasTextAncestor =>
-          hasTextAncestor ? (
-            <RCTTextInlineImage {...nativeProps} />
-          ) : (
-            <RKImage {...nativeProps} />
-          )
-        }
-      </TextAncestor.Consumer>
+  if (props.defaultSource && props.loadingIndicatorSource) {
+    throw new Error(
+      'The <Image> component cannot have defaultSource and loadingIndicatorSource at the same time. Please use either defaultSource or loadingIndicatorSource.',
     );
-  },
-});
+  }
+
+  if (!source || (!source.uri && !Array.isArray(source))) {
+    return null;
+  }
+
+  let style;
+  let sources;
+  if (source.uri) {
+    const {width, height} = source;
+    style = flattenStyle([{width, height}, styles.base, props.style]);
+    sources = [{uri: source.uri}];
+  } else {
+    style = flattenStyle([styles.base, props.style]);
+    sources = source;
+  }
+
+  const {onLoadStart, onLoad, onLoadEnd, onError} = props;
+  const nativeProps = merge(props, {
+    style,
+    shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),
+    src: sources,
+    headers: source.headers,
+    defaultSrc: defaultSource ? defaultSource.uri : null,
+    loadingIndicatorSrc: loadingIndicatorSource
+      ? loadingIndicatorSource.uri
+      : null,
+    ref: forwardedRef,
+  });
+
+  return (
+    <TextAncestor.Consumer>
+      {hasTextAncestor =>
+        hasTextAncestor ? (
+          <RCTTextInlineImage {...nativeProps} />
+        ) : (
+          <RKImage {...nativeProps} />
+        )
+      }
+    </TextAncestor.Consumer>
+  );
+};
+
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+Image = React.forwardRef(Image);
+
+/**
+ * Prefetches a remote image for later use by downloading it to the disk
+ * cache
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#prefetch
+ */
+Image.getSize = getSize;
+
+/**
+ * Prefetches a remote image for later use by downloading it to the disk
+ * cache
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#prefetch
+ */
+Image.prefetch = prefetch;
+
+/**
+ * Abort prefetch request.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#abortprefetch
+ */
+Image.abortPrefetch = abortPrefetch;
+
+/**
+ * Perform cache interrogation.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#querycache
+ */
+Image.queryCache = queryCache;
+
+/**
+ * Resolves an asset reference into an object.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#resolveassetsource
+ */
+Image.resolveAssetSource = resolveAssetSource;
+
+Image.propTypes = ImageProps;
 
 const styles = StyleSheet.create({
   base: {
@@ -310,4 +304,4 @@ const styles = StyleSheet.create({
   },
 });
 
-module.exports = ((Image: any): Class<ImageComponentType>);
+module.exports = (Image: Class<ImageComponentType>);

From 886d70516eb2daaa5554599811918f16e78140cd Mon Sep 17 00:00:00 2001
From: Bowen Li <bowenli@fb.com>
Date: Thu, 21 Jun 2018 10:30:09 -0700
Subject: [PATCH 0873/1109] Adding custom view to swipeable component

Summary: as title

Reviewed By: fred2028

Differential Revision: D8550184

fbshipit-source-id: 5ba72538fae11d75a82568774dd937b4493e7292
---
 .../SwipeableQuickActionButton.js             | 39 ++++++++-----------
 1 file changed, 16 insertions(+), 23 deletions(-)

diff --git a/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js b/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
index dd002fe25974..e0ea2ce8cabd 100644
--- a/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
+++ b/Libraries/Experimental/SwipeableRow/SwipeableQuickActionButton.js
@@ -11,7 +11,6 @@
 'use strict';
 
 const Image = require('Image');
-const PropTypes = require('prop-types');
 const React = require('React');
 const Text = require('Text');
 const TouchableHighlight = require('TouchableHighlight');
@@ -27,43 +26,37 @@ import type {ImageSource} from 'ImageSource';
  */
 class SwipeableQuickActionButton extends React.Component<{
   accessibilityLabel?: string,
-  imageSource: ImageSource | number,
+  imageSource?: ?(ImageSource | number),
   imageStyle?: ?ViewPropTypes.style,
+  mainView?: ?React.Node,
   onPress?: Function,
   style?: ?ViewPropTypes.style,
   testID?: string,
   text?: ?(string | Object | Array<string | Object>),
   textStyle?: ?ViewPropTypes.style,
 }> {
-  static propTypes = {
-    accessibilityLabel: PropTypes.string,
-    imageSource: Image.propTypes.source.isRequired,
-    imageStyle: Image.propTypes.style,
-    onPress: PropTypes.func,
-    style: ViewPropTypes.style,
-    testID: PropTypes.string,
-    text: PropTypes.string,
-    textStyle: Text.propTypes.style,
-  };
-
   render(): React.Node {
-    if (!this.props.imageSource && !this.props.text) {
+    if (!this.props.imageSource && !this.props.text && !this.props.mainView) {
       return null;
     }
-
+    const mainView = this.props.mainView ? (
+      this.props.mainView
+    ) : (
+      <View style={this.props.style}>
+        <Image
+          accessibilityLabel={this.props.accessibilityLabel}
+          source={this.props.imageSource}
+          style={this.props.imageStyle}
+        />
+        <Text style={this.props.textStyle}>{this.props.text}</Text>
+      </View>
+    );
     return (
       <TouchableHighlight
         onPress={this.props.onPress}
         testID={this.props.testID}
         underlayColor="transparent">
-        <View style={this.props.style}>
-          <Image
-            accessibilityLabel={this.props.accessibilityLabel}
-            source={this.props.imageSource}
-            style={this.props.imageStyle}
-          />
-          <Text style={this.props.textStyle}>{this.props.text}</Text>
-        </View>
+        <View style={this.props.style}>{mainView}</View>
       </TouchableHighlight>
     );
   }

From 0cca01b16e8a450d0743b6ce09a93fdfeb310a82 Mon Sep 17 00:00:00 2001
From: Eli White <eliwhite@fb.com>
Date: Thu, 21 Jun 2018 11:56:37 -0700
Subject: [PATCH 0874/1109] Fix broken default for Image.ios.js resizeMode back
 to cover

Summary:
I broke this on a previous change:

https://pxl.cl/fh2n

This caused server snapshot tests to fail: https://our.intern.facebook.com/intern/testinfra/screenshots_reports?report_id=88925

Reviewed By: mmmulani

Differential Revision: D8576282

fbshipit-source-id: 03217c6b68dca63cba67f9ac04cf39bbc24e91eb
---
 Libraries/Image/Image.ios.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/Image/Image.ios.js b/Libraries/Image/Image.ios.js
index fc13dd1a46dc..82e651c03629 100644
--- a/Libraries/Image/Image.ios.js
+++ b/Libraries/Image/Image.ios.js
@@ -85,7 +85,7 @@ let Image = (
     }
   }
 
-  const resizeMode = props.resizeMode || style.resizeMode;
+  const resizeMode = props.resizeMode || style.resizeMode || 'cover';
   const tintColor = style.tintColor;
 
   if (props.src != null) {

From 20a8673b48bb68e41dbab5e6fe674cadb36c8a81 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 21 Jun 2018 14:14:59 -0700
Subject: [PATCH 0875/1109] iOS: create EventTarget when creating EventEmitter
 and keep it until the emitter is deallocated.

Summary:
@public
There are some race conditions between VM objects getting deallocated and the instanceHandle held by the eventEmitter can point to deallocated memory space, causing undefined behavior like a crash.
For now, keep a strong ref to the eventTarget inside EventEmitter to avoid that scenario. This is a temporary workaround.

Reviewed By: shergin

Differential Revision: D8576785

fbshipit-source-id: 87ef36f716270ceca906b32bb86e0046ceaca19e
---
 .../fabric/core/events/EventDispatcher.h        |  3 +++
 ReactCommon/fabric/core/events/EventEmitter.cpp | 17 +++++++++++++----
 ReactCommon/fabric/core/events/EventEmitter.h   |  1 +
 .../fabric/uimanager/FabricUIManager.cpp        |  8 ++++++++
 ReactCommon/fabric/uimanager/FabricUIManager.h  |  4 ++++
 .../uimanager/SchedulerEventDispatcher.cpp      | 11 +++++++++++
 .../fabric/uimanager/SchedulerEventDispatcher.h |  3 +++
 7 files changed, 43 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/core/events/EventDispatcher.h b/ReactCommon/fabric/core/events/EventDispatcher.h
index d241f3a2953e..0f61a010eb15 100644
--- a/ReactCommon/fabric/core/events/EventDispatcher.h
+++ b/ReactCommon/fabric/core/events/EventDispatcher.h
@@ -39,6 +39,9 @@ class EventDispatcher {
     const folly::dynamic &payload,
     const EventPriority &priority
   ) const = 0;
+
+  virtual void releaseEventTarget(const EventTarget &eventTarget) const = 0;
+
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/events/EventEmitter.cpp b/ReactCommon/fabric/core/events/EventEmitter.cpp
index ec42f0f1d195..fdb1b9889e56 100644
--- a/ReactCommon/fabric/core/events/EventEmitter.cpp
+++ b/ReactCommon/fabric/core/events/EventEmitter.cpp
@@ -15,9 +15,18 @@ namespace react {
 EventEmitter::EventEmitter(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher):
   instanceHandle_(instanceHandle),
   tag_(tag),
-  eventDispatcher_(eventDispatcher) {}
+  eventDispatcher_(eventDispatcher) {
+  if (eventDispatcher) {
+    eventTarget_ = createEventTarget();
+  }
+}
 
-EventEmitter::~EventEmitter() {}
+EventEmitter::~EventEmitter() {
+  auto &&eventDispatcher = eventDispatcher_.lock();
+  if (eventDispatcher && eventTarget_) {
+    eventDispatcher->releaseEventTarget(eventTarget_);
+  }
+}
 
 void EventEmitter::dispatchEvent(
   const std::string &type,
@@ -29,7 +38,7 @@ void EventEmitter::dispatchEvent(
     return;
   }
 
-  EventTarget eventTarget = createEventTarget();
+  assert(eventTarget_ && "Attempted to dispatch an event without an eventTarget.");
 
   // Mixing `target` into `payload`.
   assert(payload.isObject());
@@ -37,7 +46,7 @@ void EventEmitter::dispatchEvent(
   extendedPayload.merge_patch(payload);
 
   // TODO(T29610783): Reconsider using dynamic dispatch here.
-  eventDispatcher->dispatchEvent(eventTarget, type, extendedPayload, priority);
+  eventDispatcher->dispatchEvent(eventTarget_, type, extendedPayload, priority);
 }
 
 EventTarget EventEmitter::createEventTarget() const {
diff --git a/ReactCommon/fabric/core/events/EventEmitter.h b/ReactCommon/fabric/core/events/EventEmitter.h
index f63c59d73245..d854b00ba101 100644
--- a/ReactCommon/fabric/core/events/EventEmitter.h
+++ b/ReactCommon/fabric/core/events/EventEmitter.h
@@ -53,6 +53,7 @@ class EventEmitter {
   InstanceHandle instanceHandle_;
   Tag tag_;
   std::weak_ptr<const EventDispatcher> eventDispatcher_;
+  mutable EventTarget eventTarget_ {nullptr};
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 1c8f96b3db48..0c17bfc0089a 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -102,6 +102,10 @@ void FabricUIManager::setReleaseEventHandlerFunction(std::function<ReleaseEventH
   releaseEventHandlerFunction_ = releaseEventHandlerFunction;
 }
 
+void FabricUIManager::setReleaseEventTargetFunction(std::function<ReleaseEventTargetFunction> releaseEventTargetFunction) {
+  releaseEventTargetFunction_ = releaseEventTargetFunction;
+}
+
 EventTarget FabricUIManager::createEventTarget(const InstanceHandle &instanceHandle) const {
   return createEventTargetFunction_(instanceHandle);
 }
@@ -115,6 +119,10 @@ void FabricUIManager::dispatchEvent(const EventTarget &eventTarget, const std::s
   );
 }
 
+void FabricUIManager::releaseEventTarget(const EventTarget &eventTarget) const {
+  releaseEventTargetFunction_(eventTarget);
+}
+
 SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, InstanceHandle instanceHandle) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag: " << rootTag << ", props: " << props << ")";
 
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index bd16f02946c0..3f66913332f3 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -21,6 +21,7 @@ namespace react {
 using CreateEventTargetFunction = EventTarget (InstanceHandle instanceHandle);
 using DispatchEventFunction = void (EventHandler eventHandler, EventTarget eventTarget, std::string type, folly::dynamic payload);
 using ReleaseEventHandlerFunction = void (EventHandler eventHandler);
+using ReleaseEventTargetFunction = void (EventTarget eventTarget);
 
 class FabricUIManager {
 public:
@@ -46,11 +47,13 @@ class FabricUIManager {
   void setCreateEventTargetFunction(std::function<CreateEventTargetFunction> createEventTargetFunction);
   void setDispatchEventFunction(std::function<DispatchEventFunction> dispatchEventFunction);
   void setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction);
+  void setReleaseEventTargetFunction(std::function<ReleaseEventTargetFunction> releaseEventTargetFunction);
 
 #pragma mark - Native-facing Interface
 
   EventTarget createEventTarget(const InstanceHandle &instanceHandle) const;
   void dispatchEvent(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const;
+  void releaseEventTarget(const EventTarget &eventTarget) const;
 
 #pragma mark - JavaScript/React-facing Interface
 
@@ -73,6 +76,7 @@ class FabricUIManager {
   std::function<CreateEventTargetFunction> createEventTargetFunction_;
   std::function<DispatchEventFunction> dispatchEventFunction_;
   std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction_;
+  std::function<ReleaseEventTargetFunction> releaseEventTargetFunction_;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
index 11d40c1d32e5..77d6942535fb 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
@@ -27,6 +27,7 @@ void SchedulerEventDispatcher::setUIManager(std::shared_ptr<const FabricUIManage
 }
 
 EventTarget SchedulerEventDispatcher::createEventTarget(const InstanceHandle &instanceHandle) const {
+  assert(uiManager_ && "Attempted to create EventTarget after FabricUIManager dies.");
   return uiManager_->createEventTarget(instanceHandle);
 }
 
@@ -36,9 +37,19 @@ void SchedulerEventDispatcher::dispatchEvent(
   const folly::dynamic &payload,
   const EventPriority &priority
 ) const {
+  if (!uiManager_) {
+    return;
+  }
   // TODO: Schedule the event based on priority.
   uiManager_->dispatchEvent(eventTarget, normalizeEventType(type), payload);
 }
 
+void SchedulerEventDispatcher::releaseEventTarget(const EventTarget &eventTarget) const {
+  if (!uiManager_) {
+    return;
+  }
+  uiManager_->releaseEventTarget(eventTarget);
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
index bb6fd12de35e..847946b57b01 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
@@ -40,6 +40,9 @@ class SchedulerEventDispatcher final:
     const EventPriority &priority
   ) const override;
 
+
+  void releaseEventTarget(const EventTarget &eventTarget) const override;
+
 private:
 
   // TODO: consider using std::weak_ptr<> instead for better memory management.

From af226078e76785a0dce8f62f33f40fb18d99e9e1 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 21 Jun 2018 15:23:28 -0700
Subject: [PATCH 0876/1109] Added Accessibility Feature for RN to support Smart
 Inversion for photos

Summary:
@public
Added a property `accessibilityIgnoresInvertColors (boolean)`  to Views which allows the Apple API `accessibilityIgnoresInvertColors` to be used in React Native.
Now, when a user has Display: Smart Invert enabled, you can set the property to be true, and things like photos and views with the property set to true will no longer be inverted when Smart Invert is enabled.

This property can also be applied to the Image Component.

Example Use Case:

```
<Image accessibilityIgnoresInvertColors={true} />
```
```
<View accessibilityIgnoresInvertColors={true} />
```

| Before | After |
| ------ | ----- |
| ![original](https://user-images.githubusercontent.com/165856/41738737-b62c6ebc-7547-11e8-8ea3-f82239998071.jpg) | ![feeditem](https://user-images.githubusercontent.com/165856/41738749-beef6de2-7547-11e8-9771-b44e513de0fd.jpg)

Reviewed By: PeteTheHeat

Differential Revision: D8549084

fbshipit-source-id: 82a3bc73c9e6d75d6b50ba013b88127f07692641
---
 Libraries/Components/View/ViewPropTypes.js | 1 +
 React/Views/RCTViewManager.m               | 1 +
 2 files changed, 2 insertions(+)

diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 0f7dea210694..5cfcd45f24b9 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -87,6 +87,7 @@ export type ViewProps = $ReadOnly<{|
   accessibilityComponentType?: AccessibilityComponentType,
   accessibilityLiveRegion?: 'none' | 'polite' | 'assertive',
   importantForAccessibility?: 'auto' | 'yes' | 'no' | 'no-hide-descendants',
+  accessibilityIgnoresInvertColors?: boolean,
   accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
   accessibilityViewIsModal?: boolean,
   accessibilityElementsHidden?: boolean,
diff --git a/React/Views/RCTViewManager.m b/React/Views/RCTViewManager.m
index 626e923d35e5..db12c77d39b5 100644
--- a/React/Views/RCTViewManager.m
+++ b/React/Views/RCTViewManager.m
@@ -104,6 +104,7 @@ - (RCTShadowView *)shadowView
 #endif
 
 RCT_EXPORT_VIEW_PROPERTY(nativeID, NSString)
+RCT_EXPORT_VIEW_PROPERTY(accessibilityIgnoresInvertColors, BOOL)
 
 // Acessibility related properties
 RCT_REMAP_VIEW_PROPERTY(accessible, reactAccessibilityElement.isAccessibilityElement, BOOL)

From 68a245436d45ff7b5c6faee3f827d5ec07ba8f97 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 21 Jun 2018 16:35:24 -0700
Subject: [PATCH 0877/1109] Added Ignore color inversion prop to components in
 marketplace

Summary:
Added Smart Inversion Compatibility to Marketplace on iOS so that photos don't appear inverted
Added Property to View for Ignoring Color Inversion
Applied Property to Images on marketplace.

**Note: Android doesn't support smart inversion

Reviewed By: PeteTheHeat

Differential Revision: D8528543

fbshipit-source-id: 63caf592bc71e6fe9db7e70c72b56d32873be048
---
 Libraries/Image/ImageBackground.js | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/Libraries/Image/ImageBackground.js b/Libraries/Image/ImageBackground.js
index 7b86d9c5f529..a128880a1780 100644
--- a/Libraries/Image/ImageBackground.js
+++ b/Libraries/Image/ImageBackground.js
@@ -60,7 +60,10 @@ class ImageBackground extends React.Component<$FlowFixMeProps> {
     const {children, style, imageStyle, imageRef, ...props} = this.props;
 
     return (
-      <View style={style} ref={this._captureRef}>
+      <View
+        accessibilityIgnoresInvertColors={true}
+        style={style}
+        ref={this._captureRef}>
         <Image
           {...props}
           style={[

From 6264b6932a08e1cefd83c4536ff7839d91938730 Mon Sep 17 00:00:00 2001
From: Sam Goldman <samgoldman@fb.com>
Date: Thu, 21 Jun 2018 19:58:12 -0700
Subject: [PATCH 0878/1109] Deploy Flow v0.75.0 to fbsource

Summary:
bypass-lint
allow-large-files

Reviewed By: gabelevi

Differential Revision: D8579147

fbshipit-source-id: 12280dd4872551247ff9baafab3d766d3d7a544a
---
 .flowconfig                                | 2 +-
 local-cli/templates/HelloWorld/_flowconfig | 2 +-
 package.json                               | 2 +-
 3 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index 78fb45fa536a..a2afa6b93199 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -97,4 +97,4 @@ untyped-import
 untyped-type-import
 
 [version]
-^0.74.0
+^0.75.0
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index f99d3024b467..3c0adb566300 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -64,4 +64,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.74.0
+^0.75.0
diff --git a/package.json b/package.json
index 6a2f4a243223..c8be7a8d0b37 100644
--- a/package.json
+++ b/package.json
@@ -212,7 +212,7 @@
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.8.2",
     "eslint-plugin-react-native": "^3.2.1",
-    "flow-bin": "^0.74.0",
+    "flow-bin": "^0.75.0",
     "jest": "23.1.0",
     "jest-junit": "4.0.0",
     "prettier": "1.13.4",

From eff76d237b049b73664b62c73decfb6ec5ce29a1 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:26 -0700
Subject: [PATCH 0879/1109] Fabric: Using proper encoding for converting
 user-facing strings to NSString

Summary:
@public
Trivial.

Reviewed By: fkgozali

Differential Revision: D8473507

fbshipit-source-id: 49c9e66dc6b32b0a5208aeb4c2fb68fbe1f71738
---
 .../fabric/textlayoutmanager/RCTAttributedTextUtils.mm        | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
index 542b7859f071..c58a644f90e4 100644
--- a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
+++ b/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
@@ -14,7 +14,7 @@
 
 inline static UIFont *RCTEffectiveFontFromTextAttributes(const TextAttributes &textAttributes) {
   NSString *fontFamily = [NSString stringWithCString:textAttributes.fontFamily.c_str()
-                                            encoding:NSASCIIStringEncoding];
+                                            encoding:NSUTF8StringEncoding];
 
   RCTFontProperties fontProperties;
   fontProperties.family = fontFamily;
@@ -199,7 +199,7 @@ inline static CGFloat RCTEffectiveFontSizeMultiplierFromTextAttributes(const Tex
     } else {
       NSString *string =
         [NSString stringWithCString:fragment.string.c_str()
-                           encoding:NSASCIIStringEncoding];
+                           encoding:NSUTF8StringEncoding];
 
       nsAttributedStringFragment =
         [[NSAttributedString alloc] initWithString:string

From 62a458bcea8faf52650714632143fb7c7963f2be Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:27 -0700
Subject: [PATCH 0880/1109] Fabric: Using `rootTag` instead of deprecated
 `rootViewTag` in SurfacePresenter

Summary:
@public
Trivial.

Reviewed By: mdvacca

Differential Revision: D8473512

fbshipit-source-id: 7b6c160a2a1a1abcd571b0522760d49644632922
---
 React/Fabric/RCTSurfacePresenter.mm | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
index 2c2f01c93bbe..e29d4e0591d0 100644
--- a/React/Fabric/RCTSurfacePresenter.mm
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -82,17 +82,17 @@ - (void)schedulerDidRequestPreliminaryViewAllocationWithComponentName:(NSString
 - (void)registerSurface:(RCTFabricSurface *)surface
 {
   [_surfaceRegistry registerSurface:surface];
-  [_scheduler registerRootTag:surface.rootViewTag.integerValue];
+  [_scheduler registerRootTag:surface.rootTag];
   [self runSurface:surface];
 
   // FIXME: Mutation instruction MUST produce instruction for root node.
-  [_mountingManager.componentViewRegistry dequeueComponentViewWithName:@"Root" tag:surface.rootViewTag.integerValue];
+  [_mountingManager.componentViewRegistry dequeueComponentViewWithName:@"Root" tag:surface.rootTag];
 }
 
 - (void)unregisterSurface:(RCTFabricSurface *)surface
 {
   [self stopSurface:surface];
-  [_scheduler unregisterRootTag:surface.rootViewTag.integerValue];
+  [_scheduler unregisterRootTag:surface.rootTag];
   [_surfaceRegistry unregisterSurface:surface];
 }
 
@@ -132,7 +132,7 @@ - (void)setMinimumSize:(CGSize)minimumSize
 - (void)runSurface:(RCTFabricSurface *)surface
 {
   NSDictionary *applicationParameters = @{
-    @"rootTag": surface.rootViewTag,
+    @"rootTag": @(surface.rootTag),
     @"initialProps": surface.properties,
   };
 
@@ -141,7 +141,7 @@ - (void)runSurface:(RCTFabricSurface *)surface
 
 - (void)stopSurface:(RCTFabricSurface *)surface
 {
-  [_batchedBridge enqueueJSCall:@"AppRegistry" method:@"unmountApplicationComponentAtRootTag" args:@[surface.rootViewTag] completion:NULL];
+  [_batchedBridge enqueueJSCall:@"AppRegistry" method:@"unmountApplicationComponentAtRootTag" args:@[@(surface.rootTag)] completion:NULL];
 }
 
 #pragma mark - RCTMountingManagerDelegate

From a3f9ff4f93f5b26eb66ca4c23f62c029272101e2 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:29 -0700
Subject: [PATCH 0881/1109] Fabric: `pointScaleFactor` is now part of
 LayoutContext and LayoutMetrics

Summary:
@public
... and we initalize this in Surface.
We need this for requesting images with proper size/pixel-density, setup proper parameters for rasterizing CALayer's and rounding layout metric values.
Then we have to figure out how to wire this up with YGConfig.

Reviewed By: fkgozali

Differential Revision: D8475639

fbshipit-source-id: cec7af581b94efb4595dcf3f232252ce87a1fde3
---
 React/Fabric/RCTSurfacePresenter.mm                       | 3 +++
 React/Fabric/Surface/RCTFabricSurface.mm                  | 1 -
 ReactCommon/fabric/core/layout/LayoutContext.h            | 8 ++++++++
 ReactCommon/fabric/core/layout/LayoutMetrics.h            | 1 +
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 1 +
 5 files changed, 13 insertions(+), 1 deletion(-)

diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
index e29d4e0591d0..99703c2389ac 100644
--- a/React/Fabric/RCTSurfacePresenter.mm
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -17,6 +17,7 @@
 #import <React/RCTSurfaceRegistry.h>
 #import <React/RCTSurfaceView.h>
 #import <React/RCTSurfaceView+Internal.h>
+#import <React/RCTUtils.h>
 #import <fabric/core/LayoutContext.h>
 #import <fabric/core/LayoutConstraints.h>
 
@@ -106,6 +107,7 @@ - (CGSize)sizeThatFitsMinimumSize:(CGSize)minimumSize
                           surface:(RCTFabricSurface *)surface
 {
   LayoutContext layoutContext;
+  layoutContext.pointScaleFactor = RCTScreenScale();
   LayoutConstraints layoutConstraints = {};
   layoutConstraints.minimumSize = RCTSizeFromCGSize(minimumSize);
   layoutConstraints.maximumSize = RCTSizeFromCGSize(maximumSize);
@@ -120,6 +122,7 @@ - (void)setMinimumSize:(CGSize)minimumSize
                surface:(RCTFabricSurface *)surface
 {
   LayoutContext layoutContext;
+  layoutContext.pointScaleFactor = RCTScreenScale();
   LayoutConstraints layoutConstraints = {};
   layoutConstraints.minimumSize = RCTSizeFromCGSize(minimumSize);
   layoutConstraints.maximumSize = RCTSizeFromCGSize(maximumSize);
diff --git a/React/Fabric/Surface/RCTFabricSurface.mm b/React/Fabric/Surface/RCTFabricSurface.mm
index a779dc55d300..d0b93710fd9f 100644
--- a/React/Fabric/Surface/RCTFabricSurface.mm
+++ b/React/Fabric/Surface/RCTFabricSurface.mm
@@ -59,7 +59,6 @@ - (instancetype)initWithSurfacePresenter:(RCTSurfacePresenter *)surfacePresenter
                               moduleName:(NSString *)moduleName
                        initialProperties:(NSDictionary *)initialProperties
 {
-
   if (self = [super init]) {
     _surfacePresenter = surfacePresenter;
     _moduleName = moduleName;
diff --git a/ReactCommon/fabric/core/layout/LayoutContext.h b/ReactCommon/fabric/core/layout/LayoutContext.h
index d7197cd9632e..255952df41b1 100644
--- a/ReactCommon/fabric/core/layout/LayoutContext.h
+++ b/ReactCommon/fabric/core/layout/LayoutContext.h
@@ -21,6 +21,14 @@ struct LayoutContext {
    * Compound absolute position of the node relative to the root node.
    */
   Point absolutePosition {0, 0};
+
+  /*
+   * Reflects the scale factor needed to convert from the logical coordinate
+   * space into the device coordinate space of the physical screen.
+   * Some layout systems *might* use this to round layout metric values
+   * to `pixel value`.
+   */
+  Float pointScaleFactor = {1.0};
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/layout/LayoutMetrics.h b/ReactCommon/fabric/core/layout/LayoutMetrics.h
index e1c74359e8e7..5c915310a8c5 100644
--- a/ReactCommon/fabric/core/layout/LayoutMetrics.h
+++ b/ReactCommon/fabric/core/layout/LayoutMetrics.h
@@ -22,6 +22,7 @@ struct LayoutMetrics {
   EdgeInsets borderWidth {0};
   DisplayType displayType {DisplayType::Flex};
   LayoutDirection layoutDirection {LayoutDirection::Undefined};
+  Float pointScaleFactor {1.0};
 
   Rect getContentFrame() const {
     return Rect {
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index c8c66fcf66d3..6840a86c4f82 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -126,6 +126,7 @@ void YogaLayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
     auto nonConstYogaLayoutableChild = std::const_pointer_cast<YogaLayoutableShadowNode>(yogaLayoutableChild);
 
     LayoutMetrics childLayoutMetrics = layoutMetricsFromYogaNode(nonConstYogaLayoutableChild->yogaNode_);
+    childLayoutMetrics.pointScaleFactor = layoutContext.pointScaleFactor;
     nonConstYogaLayoutableChild->setLayoutMetrics(childLayoutMetrics);
   }
 }

From 0a20f470210b5dd671fb2d307ad90df8745908c5 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:31 -0700
Subject: [PATCH 0882/1109] Fabric: Proxying `pointScaleFactor` to Yoga Config

Summary:
@public
This diff changes how we store and manage Yoga Config in layoutable shadow nodes.
Previously we have `shared_ptr` to single shared yoga config (one to many relationships); now we initiate and store yoga config with yoga node (one to one relationship).
Cons:
 - Less memory efficient.
Pros:
 - Much more flexible model. Configuration can be tweaked on a per-node basis.
 - More performant. Dealing with `shared_ptr` is expensive because of atomic ref-counter. (This is not really applicable for the previous approach but would be applicable for any alternate approach where we want to have more granular control of the configuration.) Data locality is also great in the new model which should positively impact performance.
 - Simplicity. Any alternate approach where we manage sets of nodes which share the same configuration is going to be quite complex.

Reviewed By: fkgozali

Differential Revision: D8475638

fbshipit-source-id: 5d73116718ced8e4b2d31d857bb9aac69eb69f2b
---
 .../view/yoga/YogaLayoutableShadowNode.cpp    | 40 ++++++++++++-------
 .../view/yoga/YogaLayoutableShadowNode.h      |  7 +++-
 2 files changed, 31 insertions(+), 16 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 6840a86c4f82..5941baa057ba 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -19,26 +19,18 @@
 namespace facebook {
 namespace react {
 
-SharedYogaConfig YogaLayoutableShadowNode::suitableYogaConfig() {
-  static SharedYogaConfig sharedYogaConfig;
-
-  if (!sharedYogaConfig) {
-    sharedYogaConfig = std::shared_ptr<YGConfig>(YGConfigNew());
-    sharedYogaConfig->cloneNodeCallback = YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector;
-  }
-
-  return sharedYogaConfig;
-}
-
 YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   const SharedYogaStylableProps &props,
   const SharedShadowNodeSharedList &children
 ):
-  yogaNode_({}) {
+  yogaNode_({}),
+  yogaConfig_(nullptr) {
+
   assert(props);
   assert(children);
 
-  yogaNode_.setConfig(suitableYogaConfig().get());
+  initializeYogaConfig(yogaConfig_);
+  yogaNode_.setConfig(&yogaConfig_);
   yogaNode_.setStyle(props->yogaStyle);
   yogaNode_.setContext(this);
   yogaNode_.setDirty(true);
@@ -51,8 +43,11 @@ YogaLayoutableShadowNode::YogaLayoutableShadowNode(
   const SharedYogaStylableProps &props,
   const SharedShadowNodeSharedList &children
 ):
-  yogaNode_(shadowNode->yogaNode_) {
-  yogaNode_.setConfig(suitableYogaConfig().get());
+  yogaNode_(shadowNode->yogaNode_),
+  yogaConfig_(nullptr) {
+
+  initializeYogaConfig(yogaConfig_);
+  yogaNode_.setConfig(&yogaConfig_);
   yogaNode_.setContext(this);
   yogaNode_.setOwner(nullptr);
   yogaNode_.setDirty(true);
@@ -110,6 +105,17 @@ void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child)
 void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
   if (!getIsLayoutClean()) {
     ensureUnsealed();
+
+    /*
+     * In Yoga, every single Yoga Node has to have a (non-null) pointer to
+     * Yoga Config (this config can be shared between many nodes),
+     * so every node can be individually configured. This does *not* mean
+     * however that Yoga consults with every single Yoga Node Config for every
+     * config parameter. Especially in case of `pointScaleFactor`,
+     * the only value in the config of the root node is taken into account
+     * (and this is by design).
+     */
+    yogaConfig_.pointScaleFactor = layoutContext.pointScaleFactor;
     YGNodeCalculateLayout(&yogaNode_, YGUndefined, YGUndefined, YGDirectionInherit);
   }
 
@@ -244,5 +250,9 @@ void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNo
   yogaNodeRawPtr->setChildren(yogaNodeChildren);
 }
 
+void YogaLayoutableShadowNode::initializeYogaConfig(YGConfig &config) {
+  config.cloneNodeCallback = YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector;
+}
+
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index e0fc3b5e0c8b..2da836d8a99c 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -87,8 +87,13 @@ class YogaLayoutableShadowNode:
    */
   mutable YGNode yogaNode_;
 
+  /*
+   * Yoga config associated (only) with this particular node.
+   */
+  YGConfig yogaConfig_;
+
 private:
-  static SharedYogaConfig suitableYogaConfig();
+  static void initializeYogaConfig(YGConfig &config);
   static void setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode *yogaNodeRawPtr, const SharedShadowNodeSharedList &children);
   static YGNode *yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex);
   static YGSize yogaNodeMeasureCallbackConnector(YGNode *yogaNode, float width, YGMeasureMode widthMode, float height, YGMeasureMode heightMode);

From c674303dfdeca2816529aae40a374a6e55792005 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:34 -0700
Subject: [PATCH 0883/1109] Fabric: Introducing `ContextContainer`

Summary:
@public
`ContextContainer` is general purpose DI container for Fabric.
We need this to communicate some enviroment-specific and/or platform-specific modules down to cross-platform C++ code.
The first one will be ImageManager. Soon.

Reviewed By: fkgozali

Differential Revision: D8475636

fbshipit-source-id: 0afc65063f818d0bab736cd2c55c6fdd21b629ac
---
 React/Fabric/RCTScheduler.mm                  |  5 ++-
 .../SampleComponentDescriptorFactor.cpp       |  6 ++-
 .../uimanager/ComponentDescriptorFactory.h    |  3 +-
 .../fabric/uimanager/ContextContainer.cpp     | 22 ++++++++++
 .../fabric/uimanager/ContextContainer.h       | 40 +++++++++++++++++++
 ReactCommon/fabric/uimanager/Scheduler.cpp    |  5 ++-
 ReactCommon/fabric/uimanager/Scheduler.h      |  4 +-
 7 files changed, 79 insertions(+), 6 deletions(-)
 create mode 100644 ReactCommon/fabric/uimanager/ContextContainer.cpp
 create mode 100644 ReactCommon/fabric/uimanager/ContextContainer.h

diff --git a/React/Fabric/RCTScheduler.mm b/React/Fabric/RCTScheduler.mm
index fcd1a9d8b86d..79cae1c130db 100644
--- a/React/Fabric/RCTScheduler.mm
+++ b/React/Fabric/RCTScheduler.mm
@@ -7,6 +7,7 @@
 
 #import "RCTScheduler.h"
 
+#import <fabric/uimanager/ContextContainer.h>
 #import <fabric/uimanager/Scheduler.h>
 #import <fabric/uimanager/SchedulerDelegate.h>
 
@@ -41,7 +42,9 @@ - (instancetype)init
 {
   if (self = [super init]) {
     _delegateProxy = std::make_shared<SchedulerDelegateProxy>((__bridge void *)self);
-    _scheduler = std::make_shared<Scheduler>();
+
+    SharedContextContainer contextContainer = std::make_shared<ContextContainer>();
+    _scheduler = std::make_shared<Scheduler>(contextContainer);
     _scheduler->setDelegate(_delegateProxy.get());
   }
 
diff --git a/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp b/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
index 28a8a8b29790..b3066e58f9be 100644
--- a/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
+++ b/ReactCommon/fabric/sample/SampleComponentDescriptorFactor.cpp
@@ -7,6 +7,7 @@
 
 #include <fabric/uimanager/ComponentDescriptorFactory.h>
 #include <fabric/uimanager/ComponentDescriptorRegistry.h>
+#include <fabric/uimanager/ContextContainer.h>
 
 namespace facebook {
 namespace react {
@@ -14,7 +15,10 @@ namespace react {
 /**
  * This is a sample implementation. Each app should provide its own.
  */
-SharedComponentDescriptorRegistry ComponentDescriptorFactory::buildRegistry(const SharedEventDispatcher &eventDispatcher) {
+SharedComponentDescriptorRegistry ComponentDescriptorFactory::buildRegistry(
+  const SharedEventDispatcher &eventDispatcher,
+  const SharedContextContainer &contextContainer
+) {
   auto registry = std::make_shared<ComponentDescriptorRegistry>();
   return registry;
 }
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h b/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
index ea6ef34ac6ca..d4c4b965cec0 100644
--- a/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
@@ -11,6 +11,7 @@
 
 #include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/EventDispatcher.h>
+#include <fabric/uimanager/ContextContainer.h>
 
 #include "ComponentDescriptorRegistry.h"
 
@@ -25,7 +26,7 @@ namespace react {
 class ComponentDescriptorFactory {
 
 public:
-  static SharedComponentDescriptorRegistry buildRegistry(const SharedEventDispatcher &eventDispatcher);
+  static SharedComponentDescriptorRegistry buildRegistry(const SharedEventDispatcher &eventDispatcher, const SharedContextContainer &contextContainer);
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/ContextContainer.cpp b/ReactCommon/fabric/uimanager/ContextContainer.cpp
new file mode 100644
index 000000000000..ef2ceb473dc5
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/ContextContainer.cpp
@@ -0,0 +1,22 @@
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
+
+#include "ContextContainer.h"
+
+namespace facebook {
+namespace react {
+
+void ContextContainer::registerInstance(const ClassHandle &handle, SharedInstance instance) {
+  std::lock_guard<std::mutex> lock(mutex_);
+  instances_.insert({handle, instance});
+}
+
+const ContextContainer::SharedInstance &ContextContainer::at(const ClassHandle &handle) const {
+  std::lock_guard<std::mutex> lock(mutex_);
+  return instances_.at(handle);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/ContextContainer.h b/ReactCommon/fabric/uimanager/ContextContainer.h
new file mode 100644
index 000000000000..bec29b6bf45d
--- /dev/null
+++ b/ReactCommon/fabric/uimanager/ContextContainer.h
@@ -0,0 +1,40 @@
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
+
+#pragma once
+
+#include <memory>
+#include <mutex>
+#include <typeindex>
+#include <typeinfo>
+#include <unordered_map>
+
+namespace facebook {
+namespace react {
+
+class ContextContainer;
+
+using SharedContextContainer = std::shared_ptr<ContextContainer>;
+
+/*
+ * General purpose dependecy injection container.
+ */
+class ContextContainer final {
+
+public:
+  using ClassHandle = std::type_index;
+  using SharedInstance = std::shared_ptr<void>;
+
+  void registerInstance(const ClassHandle &handle, SharedInstance instance);
+
+  const SharedInstance &at(const ClassHandle &handle) const;
+
+private:
+  std::unordered_map<ClassHandle, SharedInstance> instances_;
+  mutable std::mutex mutex_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index bcb89f0ad8ba..8a5f2f6e2d27 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -22,9 +22,10 @@
 namespace facebook {
 namespace react {
 
-Scheduler::Scheduler() {
+Scheduler::Scheduler(const SharedContextContainer &contextContainer):
+  contextContainer_(contextContainer) {
   auto &&eventDispatcher = std::make_shared<SchedulerEventDispatcher>();
-  auto &&componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry(eventDispatcher);
+  auto &&componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry(eventDispatcher, contextContainer);
 
   uiManager_ = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
   uiManager_->setDelegate(this);
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index 6b6fae79dc1a..036d3cef4865 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -9,6 +9,7 @@
 
 #include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/LayoutConstraints.h>
+#include <fabric/uimanager/ContextContainer.h>
 #include <fabric/uimanager/SchedulerDelegate.h>
 #include <fabric/uimanager/SchedulerEventDispatcher.h>
 #include <fabric/uimanager/UIManagerDelegate.h>
@@ -31,7 +32,7 @@ class Scheduler final:
 
 public:
 
-  Scheduler();
+  Scheduler(const SharedContextContainer &contextContainer);
   ~Scheduler();
 
 #pragma mark - Shadow Tree Management
@@ -74,6 +75,7 @@ class Scheduler final:
   std::shared_ptr<FabricUIManager> uiManager_;
   std::unordered_map<Tag, SharedShadowTree> shadowTreeRegistry_;
   SharedSchedulerEventDispatcher eventDispatcher_;
+  SharedContextContainer contextContainer_;
 };
 
 } // namespace react

From eabf29e3203e073e15022301d72b0dc61f3efdc1 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:36 -0700
Subject: [PATCH 0884/1109] Fabric: Getting rid of many `auto &&`

Summary:
@public
After reading about move-semantic and rvalue refs I realized that we (I) definitely overuse  `auto &&` (aka universal reference) construction. Even if this is harmless, does not look good and idiomatic.
Whenever I used that from a semantical point of view I always meant  "I need an alias for this" which is actually "read-only reference" which is `const auto &`.
This is also fit good to our policy where "everything is const (immutable) by default".
Hence I change that to how it should be.

Reviewed By: fkgozali

Differential Revision: D8475637

fbshipit-source-id: 0a691ededa0e798db8ffa053bff0f400913ab7b8
---
 .../RCTActivityIndicatorViewComponentView.mm  |  2 +-
 .../Switch/RCTSwitchComponentView.mm          |  2 +-
 React/Fabric/RCTSurfaceTouchHandler.mm        | 12 +++++------
 .../ConcreteComponentDescriptor.h             |  4 ++--
 .../fabric/core/events/EventEmitter.cpp       |  4 ++--
 ReactCommon/fabric/core/propsConversions.h    |  8 ++++----
 .../scrollview/ScrollViewShadowNode.cpp       |  4 ++--
 .../text/basetext/BaseTextShadowNode.cpp      |  2 +-
 ReactCommon/fabric/uimanager/Scheduler.cpp    | 18 ++++++++---------
 ReactCommon/fabric/uimanager/ShadowTree.cpp   | 20 +++++++++----------
 .../fabric/view/ConcreteViewShadowNode.h      |  2 +-
 ReactCommon/fabric/view/ViewEventEmitter.cpp  |  4 ++--
 ReactCommon/fabric/view/ViewProps.cpp         |  2 +-
 ReactCommon/fabric/view/conversions.h         |  6 +++---
 14 files changed, 45 insertions(+), 45 deletions(-)

diff --git a/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
index b0905c9bd61b..e275169a1c38 100644
--- a/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
@@ -30,7 +30,7 @@ - (instancetype)initWithFrame:(CGRect)frame
     _activityIndicatorView = [[UIActivityIndicatorView alloc] initWithFrame:self.bounds];
     _activityIndicatorView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
 
-    auto &&defaultProps = ActivityIndicatorViewProps();
+    const auto &defaultProps = ActivityIndicatorViewProps();
 
     if (defaultProps.animating) {
       [_activityIndicatorView startAnimating];
diff --git a/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.mm b/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.mm
index ec54418bfd86..f58ac227c430 100644
--- a/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/Switch/RCTSwitchComponentView.mm
@@ -26,7 +26,7 @@ - (instancetype)initWithFrame:(CGRect)frame
                  action:@selector(onChange:)
        forControlEvents:UIControlEventValueChanged];
 
-    auto &&defaultProps = SwitchProps();
+    const auto &defaultProps = SwitchProps();
 
     _switchView.on = defaultProps.value;
 
diff --git a/React/Fabric/RCTSurfaceTouchHandler.mm b/React/Fabric/RCTSurfaceTouchHandler.mm
index b668da0d8b57..c26f15bb74bf 100644
--- a/React/Fabric/RCTSurfaceTouchHandler.mm
+++ b/React/Fabric/RCTSurfaceTouchHandler.mm
@@ -191,7 +191,7 @@ - (void)detachFromView:(UIView *)view
 - (void)_registerTouches:(NSSet<UITouch *> *)touches
 {
   for (UITouch *touch in touches) {
-    auto &&activeTouch = CreateTouchWithUITouch(touch, _rootComponentView);
+    auto activeTouch = CreateTouchWithUITouch(touch, _rootComponentView);
     activeTouch.touch.identifier = _identifierPool.dequeue();
     _activeTouches.emplace(touch, activeTouch);
   }
@@ -207,7 +207,7 @@ - (void)_updateTouches:(NSSet<UITouch *> *)touches
 - (void)_unregisterTouches:(NSSet<UITouch *> *)touches
 {
   for (UITouch *touch in touches) {
-    auto &&activeTouch = _activeTouches[touch];
+    const auto &activeTouch = _activeTouches[touch];
     _identifierPool.enqueue(activeTouch.touch.identifier);
     _activeTouches.erase(touch);
   }
@@ -221,7 +221,7 @@ - (void)_dispatchTouches:(NSSet<UITouch *> *)touches eventType:(RCTTouchEventTyp
   BOOL isEndishEventType = eventType == RCTTouchEventTypeTouchEnd || eventType == RCTTouchEventTypeTouchCancel;
 
   for (UITouch *touch in touches) {
-    auto &&activeTouch = _activeTouches[touch];
+    const auto &activeTouch = _activeTouches[touch];
 
     if (!activeTouch.eventEmitter) {
       continue;
@@ -232,7 +232,7 @@ - (void)_dispatchTouches:(NSSet<UITouch *> *)touches eventType:(RCTTouchEventTyp
     uniqueEventEmitter.insert(activeTouch.eventEmitter);
   }
 
-  for (auto &&pair : _activeTouches) {
+  for (const auto &pair : _activeTouches) {
     if (!pair.second.eventEmitter) {
       continue;
     }
@@ -247,10 +247,10 @@ - (void)_dispatchTouches:(NSSet<UITouch *> *)touches eventType:(RCTTouchEventTyp
     event.touches.insert(pair.second.touch);
   }
 
-  for (auto &&eventEmitter : uniqueEventEmitter) {
+  for (const auto &eventEmitter : uniqueEventEmitter) {
     event.targetTouches.clear();
 
-    for (auto &&pair : _activeTouches) {
+    for (const auto &pair : _activeTouches) {
       if (pair.second.eventEmitter == eventEmitter) {
         event.targetTouches.insert(pair.second.touch);
       }
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 4af3582c1795..2f1f7fcd9e03 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -64,7 +64,7 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     assert(std::dynamic_pointer_cast<const ConcreteProps>(props));
     assert(std::dynamic_pointer_cast<const ConcreteEventEmitter>(eventEmitter));
 
-    auto &&shadowNode = std::make_shared<ShadowNodeT>(
+    const auto &shadowNode = std::make_shared<ShadowNodeT>(
       tag,
       rootTag,
       std::static_pointer_cast<const ConcreteProps>(props),
@@ -85,7 +85,7 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   ) const override {
     assert(std::dynamic_pointer_cast<const ShadowNodeT>(sourceShadowNode));
 
-    auto &&shadowNode = std::make_shared<ShadowNodeT>(
+    const auto &shadowNode = std::make_shared<ShadowNodeT>(
       std::static_pointer_cast<const ShadowNodeT>(sourceShadowNode),
       std::static_pointer_cast<const ConcreteProps>(props),
       std::static_pointer_cast<const ConcreteEventEmitter>(eventEmitter),
diff --git a/ReactCommon/fabric/core/events/EventEmitter.cpp b/ReactCommon/fabric/core/events/EventEmitter.cpp
index fdb1b9889e56..9c61be13f0a0 100644
--- a/ReactCommon/fabric/core/events/EventEmitter.cpp
+++ b/ReactCommon/fabric/core/events/EventEmitter.cpp
@@ -33,7 +33,7 @@ void EventEmitter::dispatchEvent(
   const folly::dynamic &payload,
   const EventPriority &priority
 ) const {
-  auto &&eventDispatcher = eventDispatcher_.lock();
+  const auto &eventDispatcher = eventDispatcher_.lock();
   if (!eventDispatcher) {
     return;
   }
@@ -50,7 +50,7 @@ void EventEmitter::dispatchEvent(
 }
 
 EventTarget EventEmitter::createEventTarget() const {
-  auto &&eventDispatcher = eventDispatcher_.lock();
+  const auto &eventDispatcher = eventDispatcher_.lock();
   assert(eventDispatcher);
   return eventDispatcher->createEventTarget(instanceHandle_);
 }
diff --git a/ReactCommon/fabric/core/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
index 0c259129d0ed..f255d6c80e71 100644
--- a/ReactCommon/fabric/core/propsConversions.h
+++ b/ReactCommon/fabric/core/propsConversions.h
@@ -41,12 +41,12 @@ inline T convertRawProp(
   const T &sourceValue,
   const T &defaultValue = T()
 ) {
-  auto &&iterator = rawProps.find(name);
+  const auto &iterator = rawProps.find(name);
   if (iterator == rawProps.end()) {
     return sourceValue;
   }
 
-  auto &&value = iterator->second;
+  const auto &value = iterator->second;
 
   // Special case: `null` always means `the prop was removed, use default value`.
   if (value.isNull()) {
@@ -65,12 +65,12 @@ inline static folly::Optional<T> convertRawProp(
   const folly::Optional<T> &sourceValue,
   const folly::Optional<T> &defaultValue = {}
 ) {
-  auto &&iterator = rawProps.find(name);
+  const auto &iterator = rawProps.find(name);
   if (iterator == rawProps.end()) {
     return sourceValue;
   }
 
-  auto &&value = iterator->second;
+  const auto &value = iterator->second;
 
   // Special case: `null` always means `the prop was removed, use default value`.
   if (value.isNull()) {
diff --git a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
index 2d3efaa8945b..5662889f2e8b 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
+++ b/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
@@ -22,11 +22,11 @@ void ScrollViewShadowNode::updateLocalData() {
   ensureUnsealed();
 
   Rect contentBoundingRect;
-  for (auto &&childNode : getLayoutableChildNodes()) {
+  for (const auto &childNode : getLayoutableChildNodes()) {
     contentBoundingRect.unionInPlace(childNode->getLayoutMetrics().frame);
   }
 
-  auto &&localData = std::make_shared<const ScrollViewLocalData>(contentBoundingRect);
+  const auto &localData = std::make_shared<const ScrollViewLocalData>(contentBoundingRect);
   setLocalData(localData);
 }
 
diff --git a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
index d812d242c060..61e4c65f3fdb 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
+++ b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
@@ -25,7 +25,7 @@ AttributedString BaseTextShadowNode::getAttributedString(
 
   AttributedString attributedString;
 
-  for (auto &&childNode : *childNodes) {
+  for (const auto &childNode : *childNodes) {
     // RawShadowNode
     SharedRawTextShadowNode rawTextShadowNode = std::dynamic_pointer_cast<const RawTextShadowNode>(childNode);
     if (rawTextShadowNode) {
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index 8a5f2f6e2d27..c7e3f51100a3 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -24,8 +24,8 @@ namespace react {
 
 Scheduler::Scheduler(const SharedContextContainer &contextContainer):
   contextContainer_(contextContainer) {
-  auto &&eventDispatcher = std::make_shared<SchedulerEventDispatcher>();
-  auto &&componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry(eventDispatcher, contextContainer);
+  const auto &eventDispatcher = std::make_shared<SchedulerEventDispatcher>();
+  const auto &componentDescriptorRegistry = ComponentDescriptorFactory::buildRegistry(eventDispatcher, contextContainer);
 
   uiManager_ = std::make_shared<FabricUIManager>(componentDescriptorRegistry);
   uiManager_->setDelegate(this);
@@ -40,27 +40,27 @@ Scheduler::~Scheduler() {
 }
 
 void Scheduler::registerRootTag(Tag rootTag) {
-  auto &&shadowTree = std::make_shared<ShadowTree>(rootTag);
+  const auto &shadowTree = std::make_shared<ShadowTree>(rootTag);
   shadowTree->setDelegate(this);
   shadowTreeRegistry_.insert({rootTag, shadowTree});
 }
 
 void Scheduler::unregisterRootTag(Tag rootTag) {
-  auto &&iterator = shadowTreeRegistry_.find(rootTag);
-  auto &&shadowTree = iterator->second;
+  const auto &iterator = shadowTreeRegistry_.find(rootTag);
+  const auto &shadowTree = iterator->second;
   assert(shadowTree);
   shadowTree->setDelegate(nullptr);
   shadowTreeRegistry_.erase(iterator);
 }
 
 Size Scheduler::measure(const Tag &rootTag, const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const {
-  auto &&shadowTree = shadowTreeRegistry_.at(rootTag);
+  const auto &shadowTree = shadowTreeRegistry_.at(rootTag);
   assert(shadowTree);
   return shadowTree->measure(layoutConstraints, layoutContext);
 }
 
 void Scheduler::constraintLayout(const Tag &rootTag, const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) {
-  auto &&shadowTree = shadowTreeRegistry_.at(rootTag);
+  const auto &shadowTree = shadowTreeRegistry_.at(rootTag);
   assert(shadowTree);
   return shadowTree->constraintLayout(layoutConstraints, layoutContext);
 }
@@ -86,8 +86,8 @@ void Scheduler::shadowTreeDidCommit(const SharedShadowTree &shadowTree, const Tr
 #pragma mark - UIManagerDelegate
 
 void Scheduler::uiManagerDidFinishTransaction(Tag rootTag, const SharedShadowNodeUnsharedList &rootChildNodes) {
-  auto &&iterator = shadowTreeRegistry_.find(rootTag);
-  auto &&shadowTree = iterator->second;
+  const auto &iterator = shadowTreeRegistry_.find(rootTag);
+  const auto &shadowTree = iterator->second;
   assert(shadowTree);
   return shadowTree->complete(rootChildNodes);
 }
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index bc19c1b329bf..55e9b5038628 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -18,7 +18,7 @@ namespace react {
 ShadowTree::ShadowTree(Tag rootTag):
   rootTag_(rootTag) {
 
-  auto &&noopEventEmitter = std::make_shared<const ViewEventEmitter>(nullptr, rootTag, nullptr);
+  const auto &noopEventEmitter = std::make_shared<const ViewEventEmitter>(nullptr, rootTag, nullptr);
   rootShadowNode_ = std::make_shared<RootShadowNode>(
     rootTag,
     rootTag,
@@ -50,7 +50,7 @@ void ShadowTree::constraintLayout(const LayoutConstraints &layoutConstraints, co
 
 UnsharedRootShadowNode ShadowTree::cloneRootShadowNode(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const {
   auto oldRootShadowNode = rootShadowNode_;
-  auto &&props = std::make_shared<const RootProps>(*oldRootShadowNode->getProps(), layoutConstraints, layoutContext);
+  const auto &props = std::make_shared<const RootProps>(*oldRootShadowNode->getProps(), layoutConstraints, layoutContext);
   auto newRootShadowNode = std::make_shared<RootShadowNode>(oldRootShadowNode, props, nullptr, nullptr);
   return newRootShadowNode;
 }
@@ -99,32 +99,32 @@ bool ShadowTree::commit(const SharedRootShadowNode &newRootShadowNode) {
 }
 
 void ShadowTree::emitLayoutEvents(const TreeMutationInstructionList &instructions) {
-  for (auto &&instruction : instructions) {
-    auto &&type = instruction.getType();
+  for (const auto &instruction : instructions) {
+    const auto &type = instruction.getType();
 
     // Only `Insertion` and `Replacement` instructions can affect layout metrics.
     if (
         type == TreeMutationInstruction::Insertion ||
         type == TreeMutationInstruction::Replacement
     ) {
-      auto &&newShadowNode = instruction.getNewChildNode();
-      auto &&eventEmitter = newShadowNode->getEventEmitter();
-      auto &&viewEventEmitter = std::dynamic_pointer_cast<const ViewEventEmitter>(eventEmitter);
+      const auto &newShadowNode = instruction.getNewChildNode();
+      const auto &eventEmitter = newShadowNode->getEventEmitter();
+      const auto &viewEventEmitter = std::dynamic_pointer_cast<const ViewEventEmitter>(eventEmitter);
 
       // Checking if particular shadow node supports `onLayout` event (part of `ViewEventEmitter`).
       if (viewEventEmitter) {
         // Now we know that both (old and new) shadow nodes must be `LayoutableShadowNode` subclasses.
         assert(std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode));
         // TODO(T29661055): Consider using `std::reinterpret_pointer_cast`.
-        auto &&newLayoutableShadowNode =
+        const auto &newLayoutableShadowNode =
           std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode);
 
         // In case if we have `oldShadowNode`, we have to check that layout metrics have changed.
         if (type == TreeMutationInstruction::Replacement) {
-          auto &&oldShadowNode = instruction.getOldChildNode();
+          const auto &oldShadowNode = instruction.getOldChildNode();
           assert(std::dynamic_pointer_cast<const LayoutableShadowNode>(oldShadowNode));
           // TODO(T29661055): Consider using `std::reinterpret_pointer_cast`.
-          auto &&oldLayoutableShadowNode =
+          const auto &oldLayoutableShadowNode =
             std::dynamic_pointer_cast<const LayoutableShadowNode>(oldShadowNode);
 
           if (oldLayoutableShadowNode->getLayoutMetrics() == newLayoutableShadowNode->getLayoutMetrics()) {
diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
index dc898dcdd7bc..c65f9ea060d4 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -131,7 +131,7 @@ class ConcreteViewShadowNode:
       return false;
     }
 
-    auto &&other = static_cast<const ConcreteViewShadowNode&>(rhs);
+    const auto &other = static_cast<const ConcreteViewShadowNode&>(rhs);
     return getLayoutMetrics() == other.getLayoutMetrics();
   }
 
diff --git a/ReactCommon/fabric/view/ViewEventEmitter.cpp b/ReactCommon/fabric/view/ViewEventEmitter.cpp
index fe1b246db983..643b0b017847 100644
--- a/ReactCommon/fabric/view/ViewEventEmitter.cpp
+++ b/ReactCommon/fabric/view/ViewEventEmitter.cpp
@@ -28,7 +28,7 @@ void ViewEventEmitter::onAccessibilityMagicTap() const {
 
 void ViewEventEmitter::onLayout(const LayoutMetrics &layoutMetrics) const {
   folly::dynamic payload = folly::dynamic::object();
-  auto &&frame = layoutMetrics.frame;
+  const auto &frame = layoutMetrics.frame;
   payload["layout"] = folly::dynamic::object
     ("x", frame.origin.x)
     ("y", frame.origin.y)
@@ -57,7 +57,7 @@ static folly::dynamic touchPayload(const Touch &touch) {
 
 static folly::dynamic touchesPayload(const Touches &touches) {
   folly::dynamic array = folly::dynamic::array();
-  for (auto &&touch : touches) {
+  for (const auto &touch : touches) {
     array.push_back(touchPayload(touch));
   }
   return array;
diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index b6d37f5f02ff..bdccfedc4cd9 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -42,7 +42,7 @@ ViewProps::ViewProps(const ViewProps &sourceProps, const RawProps &rawProps):
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList ViewProps::getDebugProps() const {
-  auto &&defaultViewProps = ViewProps();
+  const auto &defaultViewProps = ViewProps();
 
   return
     AccessibilityProps::getDebugProps() +
diff --git a/ReactCommon/fabric/view/conversions.h b/ReactCommon/fabric/view/conversions.h
index e3fd02eada90..64f1478d4d63 100644
--- a/ReactCommon/fabric/view/conversions.h
+++ b/ReactCommon/fabric/view/conversions.h
@@ -230,11 +230,11 @@ inline void fromDynamic(const folly::dynamic &value, YGFloatOptional &result) {
 inline void fromDynamic(const folly::dynamic &value, Transform &result) {
   assert(value.isArray());
   Transform transformMatrix;
-  for (auto &&tranformConfiguration : value) {
+  for (const auto &tranformConfiguration : value) {
     assert(tranformConfiguration.isObject());
     auto pair = *tranformConfiguration.items().begin();
-    auto &&operation = pair.first.asString();
-    auto &&parameters = pair.second;
+    const auto &operation = pair.first.asString();
+    const auto &parameters = pair.second;
 
     if (operation == "matrix") {
       assert(parameters.isArray());

From 979ea2094e74ae8da0288fd5038f1f2838bd7763 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:38 -0700
Subject: [PATCH 0885/1109] Fabric: Introducing ImageManager

Summary:
@public
ImageManager coordinates all work related to loading image bitmaps for <Image> component.
The particular iOS implementation uses RCTImageLoader from RCTImage module under the hood.

Reviewed By: fkgozali

Differential Revision: D8526571

fbshipit-source-id: a0d927972d30113eed6e0cd169fceee17610181d
---
 React/Fabric/RCTScheduler.mm                  |   7 +
 ReactCommon/fabric/imagemanager/BUCK          | 121 ++++++++++++++++++
 .../fabric/imagemanager/ImageManager.h        |  38 ++++++
 .../fabric/imagemanager/ImageRequest.cpp      |  49 +++++++
 .../fabric/imagemanager/ImageRequest.h        |  87 +++++++++++++
 .../fabric/imagemanager/ImageResponse.cpp     |  21 +++
 .../fabric/imagemanager/ImageResponse.h       |  28 ++++
 .../platform/android/ImageManager.cpp         |  26 ++++
 .../imagemanager/platform/ios/ImageManager.mm |  32 +++++
 .../platform/ios/RCTImageManager.h            |  28 ++++
 .../platform/ios/RCTImageManager.mm           |  68 ++++++++++
 .../ios/RCTImagePrimitivesConversions.h       |  59 +++++++++
 ReactCommon/fabric/imagemanager/primitives.h  |  55 ++++++++
 .../imagemanager/tests/ImageManagerTest.cpp   |  18 +++
 14 files changed, 637 insertions(+)
 create mode 100644 ReactCommon/fabric/imagemanager/BUCK
 create mode 100644 ReactCommon/fabric/imagemanager/ImageManager.h
 create mode 100644 ReactCommon/fabric/imagemanager/ImageRequest.cpp
 create mode 100644 ReactCommon/fabric/imagemanager/ImageRequest.h
 create mode 100644 ReactCommon/fabric/imagemanager/ImageResponse.cpp
 create mode 100644 ReactCommon/fabric/imagemanager/ImageResponse.h
 create mode 100644 ReactCommon/fabric/imagemanager/platform/android/ImageManager.cpp
 create mode 100644 ReactCommon/fabric/imagemanager/platform/ios/ImageManager.mm
 create mode 100644 ReactCommon/fabric/imagemanager/platform/ios/RCTImageManager.h
 create mode 100644 ReactCommon/fabric/imagemanager/platform/ios/RCTImageManager.mm
 create mode 100644 ReactCommon/fabric/imagemanager/platform/ios/RCTImagePrimitivesConversions.h
 create mode 100644 ReactCommon/fabric/imagemanager/primitives.h
 create mode 100644 ReactCommon/fabric/imagemanager/tests/ImageManagerTest.cpp

diff --git a/React/Fabric/RCTScheduler.mm b/React/Fabric/RCTScheduler.mm
index 79cae1c130db..0e1d5313b706 100644
--- a/React/Fabric/RCTScheduler.mm
+++ b/React/Fabric/RCTScheduler.mm
@@ -7,9 +7,12 @@
 
 #import "RCTScheduler.h"
 
+#import <fabric/imagemanager/ImageManager.h>
 #import <fabric/uimanager/ContextContainer.h>
 #import <fabric/uimanager/Scheduler.h>
 #import <fabric/uimanager/SchedulerDelegate.h>
+#import <React/RCTImageLoader.h>
+#import <React/RCTBridge+Private.h>
 
 #import "RCTConversions.h"
 
@@ -44,6 +47,10 @@ - (instancetype)init
     _delegateProxy = std::make_shared<SchedulerDelegateProxy>((__bridge void *)self);
 
     SharedContextContainer contextContainer = std::make_shared<ContextContainer>();
+
+    void *imageLoader = (__bridge void *)[[RCTBridge currentBridge] imageLoader];
+    contextContainer->registerInstance(typeid(ImageManager), std::make_shared<ImageManager>(imageLoader));
+
     _scheduler = std::make_shared<Scheduler>(contextContainer);
     _scheduler->setDelegate(_delegateProxy.get());
   }
diff --git a/ReactCommon/fabric/imagemanager/BUCK b/ReactCommon/fabric/imagemanager/BUCK
new file mode 100644
index 000000000000..0b83274c9a24
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/BUCK
@@ -0,0 +1,121 @@
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+
+rn_xplat_cxx_library(
+    name = "imagemanager",
+    srcs = glob(
+        [
+            "*.cpp",
+        ],
+        exclude = glob(["tests/**/*.cpp"]),
+    ),
+    header_namespace = "",
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbandroid_exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/imagemanager",
+    ),
+    fbandroid_headers = subdir_glob(
+        [
+            ("", "*.h"),
+            ("platform/android", "**/*.h"),
+        ],
+        prefix = "",
+    ),
+    fbandroid_srcs = glob(
+        [
+            "platform/android/**/*.cpp",
+        ],
+    ),
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    force_static = True,
+    frameworks = [
+        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
+        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
+        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
+    ],
+    ios_deps = [
+        "xplat//js:RCTImage",
+        "xplat//js/react-native-github:RCTCxxBridge",
+    ],
+    ios_exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+            ("platform/ios", "RCTImagePrimitivesConversions.h"),
+        ],
+        prefix = "fabric/imagemanager",
+    ),
+    ios_headers = subdir_glob(
+        [
+            ("", "*.h"),
+            ("platform/ios", "**/*.h"),
+        ],
+        prefix = "",
+    ),
+    ios_srcs = glob(
+        [
+            "platform/ios/**/*.cpp",
+            "platform/ios/**/*.mm",
+        ],
+    ),
+    macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:futures",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":imagemanager",
+        ],
+    )
diff --git a/ReactCommon/fabric/imagemanager/ImageManager.h b/ReactCommon/fabric/imagemanager/ImageManager.h
new file mode 100644
index 000000000000..d3f37d0ff11b
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/ImageManager.h
@@ -0,0 +1,38 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/imagemanager/ImageRequest.h>
+#include <fabric/imagemanager/primitives.h>
+
+namespace facebook {
+namespace react {
+
+class ImageManager;
+
+using SharedImageManager = std::shared_ptr<ImageManager>;
+
+/*
+ * Cross platform facade for iOS-specific RCTImageManager.
+ */
+class ImageManager {
+public:
+
+  ImageManager(void *platformSpecificCounterpart);
+  ~ImageManager();
+
+  ImageRequest requestImage(const ImageSource &imageSource) const;
+
+private:
+  void *self_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/imagemanager/ImageRequest.cpp b/ReactCommon/fabric/imagemanager/ImageRequest.cpp
new file mode 100644
index 000000000000..e023f444d9c6
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/ImageRequest.cpp
@@ -0,0 +1,49 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ImageRequest.h"
+
+namespace facebook {
+namespace react {
+
+class ImageRequest::ImageNoLongerNeededException:
+  public std::logic_error {
+public:
+  ImageNoLongerNeededException():
+    std::logic_error("Image no longer needed.") {}
+};
+
+ImageRequest::ImageRequest(const ImageSource &imageSource, folly::Future<ImageResponse> &&responseFuture):
+  imageSource_(imageSource),
+  responseFutureSplitter_(folly::splitFuture(std::move(responseFuture))) {}
+
+ImageRequest::ImageRequest(ImageRequest &&other) noexcept:
+  imageSource_(std::move(other.imageSource_)),
+  responseFutureSplitter_(std::move(other.responseFutureSplitter_)) {
+    other.moved_ = true;
+  };
+
+ImageRequest::~ImageRequest() {
+  if (!moved_) {
+    auto future = responseFutureSplitter_.getFuture();
+    if (!future.isReady()) {
+      future.raise(ImageNoLongerNeededException());
+    }
+  }
+}
+
+folly::Future<ImageResponse> ImageRequest::getResponseFuture() const {
+  if (moved_) {
+    abort();
+  }
+
+  std::lock_guard<std::mutex> lock(mutex_);
+  return responseFutureSplitter_.getFuture();
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/imagemanager/ImageRequest.h b/ReactCommon/fabric/imagemanager/ImageRequest.h
new file mode 100644
index 000000000000..7d593f7be6c2
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/ImageRequest.h
@@ -0,0 +1,87 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <mutex>
+
+#include <fabric/imagemanager/ImageResponse.h>
+#include <fabric/imagemanager/primitives.h>
+#include <folly/futures/Future.h>
+#include <folly/futures/FutureSplitter.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Represents ongoing request for an image resource.
+ * The separate object must be constructed for every single separate
+ * image request. The object cannot be copied because it would make managing of
+ * event listeners hard and inefficient; the object can be moved though.
+ * To subscribe for notifications use `getResponseFuture()` method.
+ * Destroy to cancel the underlying request.
+ */
+class ImageRequest final {
+
+public:
+
+  /*
+   * The exception which is thrown when `ImageRequest` is being deallocated
+   * if the future is not ready yet.
+   */
+  class ImageNoLongerNeededException;
+
+  /*
+   * `ImageRequest` is constructed with `ImageSource` and
+   * `ImageResponse` future which must be moved in inside the object.
+   */
+  ImageRequest(const ImageSource &imageSource, folly::Future<ImageResponse> &&responseFuture);
+
+  /*
+   * The move constructor.
+   */
+  ImageRequest(ImageRequest &&other) noexcept;
+
+  /*
+   * `ImageRequest` does not support copying by design.
+   */
+  ImageRequest(const ImageRequest &) = delete;
+
+  ~ImageRequest();
+
+  /*
+   * Creates and returns a *new* future object with promised `ImageResponse`
+   * result. Multiple consumers can call this method many times to create
+   * their own subscriptions to promised value.
+   */
+  folly::Future<ImageResponse> getResponseFuture() const;
+
+private:
+
+  /*
+   * Mutext to protect an access to the future.
+   */
+  mutable std::mutex mutex_;
+
+  /*
+   * Image source assosiated with the request.
+   */
+  ImageSource imageSource_;
+
+  /*
+   * Future splitter powers factory-like `getResponseFuture()` method.
+   */
+  mutable folly::FutureSplitter<ImageResponse> responseFutureSplitter_;
+
+  /*
+   * Indicates that the object was moved and hence cannot be used anymore.
+   */
+  bool moved_ {false};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/imagemanager/ImageResponse.cpp b/ReactCommon/fabric/imagemanager/ImageResponse.cpp
new file mode 100644
index 000000000000..39cea6218840
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/ImageResponse.cpp
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ImageResponse.h"
+
+namespace facebook {
+namespace react {
+
+ImageResponse::ImageResponse(const std::shared_ptr<void> &image):
+  image_(image) {}
+
+std::shared_ptr<void> ImageResponse::getImage() const {
+  return image_;
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/imagemanager/ImageResponse.h b/ReactCommon/fabric/imagemanager/ImageResponse.h
new file mode 100644
index 000000000000..1ce66af6c939
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/ImageResponse.h
@@ -0,0 +1,28 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <memory>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Represents retrieved image bitmap and any assotiated platform-specific info.
+ */
+class ImageResponse final {
+
+public:
+  ImageResponse(const std::shared_ptr<void> &image);
+
+  std::shared_ptr<void> getImage() const;
+
+private:
+  std::shared_ptr<void> image_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/imagemanager/platform/android/ImageManager.cpp b/ReactCommon/fabric/imagemanager/platform/android/ImageManager.cpp
new file mode 100644
index 000000000000..b1381eb0c5b5
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/platform/android/ImageManager.cpp
@@ -0,0 +1,26 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ImageManager.h"
+
+namespace facebook {
+namespace react {
+
+ImageManager::ImageManager(void *platformSpecificCounterpart) {
+  // Not implemented.
+}
+
+ImageManager::~ImageManager() {
+  // Not implemented.
+}
+
+ImageRequest ImageManager::requestImage(const ImageSource &imageSource) const {
+  // Not implemented.
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/imagemanager/platform/ios/ImageManager.mm b/ReactCommon/fabric/imagemanager/platform/ios/ImageManager.mm
new file mode 100644
index 000000000000..55281935cc7c
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/platform/ios/ImageManager.mm
@@ -0,0 +1,32 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ImageManager.h"
+
+#import <React/RCTImageLoader.h>
+
+#import "RCTImageManager.h"
+
+namespace facebook {
+namespace react {
+
+ImageManager::ImageManager(void *platformSpecificCounterpart) {
+  self_ = (__bridge_retained void *)[[RCTImageManager alloc] initWithImageLoader:(__bridge_transfer RCTImageLoader *)platformSpecificCounterpart];
+}
+
+ImageManager::~ImageManager() {
+  CFRelease(self_);
+  self_ = nullptr;
+}
+
+ImageRequest ImageManager::requestImage(const ImageSource &imageSource) const {
+  RCTImageManager *imageManager = (__bridge RCTImageManager *)self_;
+  return [imageManager requestImage:imageSource];
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/imagemanager/platform/ios/RCTImageManager.h b/ReactCommon/fabric/imagemanager/platform/ios/RCTImageManager.h
new file mode 100644
index 000000000000..45d6d0a1a6f6
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/platform/ios/RCTImageManager.h
@@ -0,0 +1,28 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <fabric/imagemanager/ImageRequest.h>
+#import <fabric/imagemanager/primitives.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class RCTImageLoader;
+
+/**
+ * iOS-specific ImageManager.
+ */
+@interface RCTImageManager : NSObject
+
+- (instancetype)initWithImageLoader:(RCTImageLoader *)imageLoader;
+
+- (facebook::react::ImageRequest)requestImage:(const facebook::react::ImageSource &)imageSource;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/ReactCommon/fabric/imagemanager/platform/ios/RCTImageManager.mm b/ReactCommon/fabric/imagemanager/platform/ios/RCTImageManager.mm
new file mode 100644
index 000000000000..4adc90b722b2
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/platform/ios/RCTImageManager.mm
@@ -0,0 +1,68 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTImageManager.h"
+
+#import <folly/futures/Future.h>
+#import <folly/futures/Promise.h>
+
+#import <React/RCTImageLoader.h>
+
+#import "RCTImagePrimitivesConversions.h"
+
+using namespace facebook::react;
+
+@implementation RCTImageManager
+{
+  RCTImageLoader *_imageLoader;
+}
+
+- (instancetype)initWithImageLoader:(RCTImageLoader *)imageLoader
+{
+  if (self = [super init]) {
+    _imageLoader = imageLoader;
+  }
+
+  return self;
+}
+
+- (ImageRequest)requestImage:(const ImageSource &)imageSource
+{
+  __block auto promise = folly::Promise<ImageResponse>();
+
+  NSURLRequest *request = NSURLRequestFromImageSource(imageSource);
+
+  auto completionBlock = ^(NSError *error, UIImage *image) {
+    auto imageResponse = ImageResponse(std::shared_ptr<void>((__bridge_retained void *)image, CFRelease));
+    promise.setValue(std::move(imageResponse));
+  };
+
+  auto interruptBlock = ^(const folly::exception_wrapper &exceptionWrapper) {
+    if (!promise.isFulfilled()) {
+      promise.setException(exceptionWrapper);
+    }
+  };
+
+  RCTImageLoaderCancellationBlock cancellationBlock =
+    [_imageLoader loadImageWithURLRequest:request
+                                     size:CGSizeMake(imageSource.size.width, imageSource.size.height)
+                                    scale:imageSource.scale
+                                  clipped:YES
+                               resizeMode:RCTResizeModeStretch
+                            progressBlock:nil
+                         partialLoadBlock:nil
+                          completionBlock:completionBlock];
+
+  promise.setInterruptHandler([cancellationBlock, interruptBlock](const folly::exception_wrapper &exceptionWrapper) {
+    cancellationBlock();
+    interruptBlock(exceptionWrapper);
+  });
+
+  return ImageRequest(imageSource, promise.getFuture());
+}
+
+@end
diff --git a/ReactCommon/fabric/imagemanager/platform/ios/RCTImagePrimitivesConversions.h b/ReactCommon/fabric/imagemanager/platform/ios/RCTImagePrimitivesConversions.h
new file mode 100644
index 000000000000..8683a00894da
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/platform/ios/RCTImagePrimitivesConversions.h
@@ -0,0 +1,59 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <fabric/imagemanager/primitives.h>
+#import <React/RCTImageLoader.h>
+
+using namespace facebook::react;
+
+inline static RCTResizeMode RCTResizeModeFromImageResizeMode(ImageResizeMode imageResizeMode) {
+  switch (imageResizeMode) {
+    case ImageResizeMode::Cover: return RCTResizeModeCover;
+    case ImageResizeMode::Contain: return RCTResizeModeContain;
+    case ImageResizeMode::Stretch: return RCTResizeModeStretch;
+    case ImageResizeMode::Center: return RCTResizeModeCenter;
+    case ImageResizeMode::Repeat: return RCTResizeModeRepeat;
+  }
+}
+
+inline std::string toString(const ImageResizeMode &value) {
+  switch (value) {
+    case ImageResizeMode::Cover: return "cover";
+    case ImageResizeMode::Contain: return "contain";
+    case ImageResizeMode::Stretch: return "stretch";
+    case ImageResizeMode::Center: return "center";
+    case ImageResizeMode::Repeat: return "repeat";
+  }
+}
+
+inline static NSURLRequest *NSURLRequestFromImageSource(const ImageSource &imageSource) {
+
+  NSString *urlString = [NSString stringWithCString:imageSource.uri.c_str()
+                                           encoding:NSASCIIStringEncoding];
+
+  if (!imageSource.bundle.empty()) {
+    NSString *bundle = [NSString stringWithCString:imageSource.bundle.c_str()
+                                          encoding:NSASCIIStringEncoding];
+    urlString = [NSString stringWithFormat:@"%@.bundle/%@", bundle, urlString];
+  }
+
+  NSURL *url = [[NSURL alloc] initWithString:urlString];
+
+  NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url];
+
+  /*
+  // TODO(shergin): To be implemented.
+  request.HTTPBody = ...;
+  request.HTTPMethod = ...;
+  request.cachePolicy = ...;
+  request.allHTTPHeaderFields = ...;
+  */
+
+  return [request copy];
+}
diff --git a/ReactCommon/fabric/imagemanager/primitives.h b/ReactCommon/fabric/imagemanager/primitives.h
new file mode 100644
index 000000000000..21932693ad84
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/primitives.h
@@ -0,0 +1,55 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <string>
+#include <vector>
+
+#include <fabric/graphics/Geometry.h>
+
+namespace facebook {
+namespace react {
+
+class ImageSource {
+
+public:
+  enum class Type {
+    Invalid,
+    Remote,
+    Local
+  };
+
+  Type type {};
+  std::string uri {};
+  std::string bundle {};
+  Float scale {3};
+  Size size {0};
+
+  bool operator==(const ImageSource &rhs) const {
+    return
+      std::tie(this->type, this->uri) ==
+      std::tie(rhs.type, rhs.uri);
+  }
+
+  bool operator!=(const ImageSource &rhs) const {
+    return !(*this == rhs);
+  }
+};
+
+using ImageSources = std::vector<ImageSource>;
+
+enum class ImageResizeMode {
+  Cover,
+  Contain,
+  Stretch,
+  Center,
+  Repeat,
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/imagemanager/tests/ImageManagerTest.cpp b/ReactCommon/fabric/imagemanager/tests/ImageManagerTest.cpp
new file mode 100644
index 000000000000..b872b698a839
--- /dev/null
+++ b/ReactCommon/fabric/imagemanager/tests/ImageManagerTest.cpp
@@ -0,0 +1,18 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+#include <fabric/imagemanager/ImageManager.h>
+
+using namespace facebook::react;
+
+TEST(ImageManagerTest, testSomething) {
+  // TODO:
+}

From b09457b4d299b5024277986f9953920a43093ac8 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:40 -0700
Subject: [PATCH 0886/1109] Fabric: <Image> component, xplat part

Summary:
@public
This diff implements basics of cross-platform part of <Image> component.
Known issues:
- Events does not work yet.
- Some quite specific image source parameters (like custom http headers) are not supported yet.

Reviewed By: fkgozali

Differential Revision: D8526575

fbshipit-source-id: ecc97d9fda2b2e65bb1b079af057f8e176a161e5
---
 ReactCommon/fabric/components/image/BUCK      | 80 ++++++++++++++++
 .../image/ImageComponentDescriptor.h          | 46 ++++++++++
 .../components/image/ImageEventEmitter.cpp    | 38 ++++++++
 .../components/image/ImageEventEmitter.h      | 29 ++++++
 .../components/image/ImageLocalData.cpp       | 37 ++++++++
 .../fabric/components/image/ImageLocalData.h  | 57 ++++++++++++
 .../fabric/components/image/ImageProps.cpp    | 25 +++++
 .../fabric/components/image/ImageProps.h      | 34 +++++++
 .../components/image/ImageShadowNode.cpp      | 91 +++++++++++++++++++
 .../fabric/components/image/ImageShadowNode.h | 53 +++++++++++
 .../fabric/components/image/conversions.h     | 90 ++++++++++++++++++
 .../components/image/tests/ImageTest.cpp      | 14 +++
 .../fabric/uimanager/FabricUIManager.cpp      |  4 +
 13 files changed, 598 insertions(+)
 create mode 100644 ReactCommon/fabric/components/image/BUCK
 create mode 100644 ReactCommon/fabric/components/image/ImageComponentDescriptor.h
 create mode 100644 ReactCommon/fabric/components/image/ImageEventEmitter.cpp
 create mode 100644 ReactCommon/fabric/components/image/ImageEventEmitter.h
 create mode 100644 ReactCommon/fabric/components/image/ImageLocalData.cpp
 create mode 100644 ReactCommon/fabric/components/image/ImageLocalData.h
 create mode 100644 ReactCommon/fabric/components/image/ImageProps.cpp
 create mode 100644 ReactCommon/fabric/components/image/ImageProps.h
 create mode 100644 ReactCommon/fabric/components/image/ImageShadowNode.cpp
 create mode 100644 ReactCommon/fabric/components/image/ImageShadowNode.h
 create mode 100644 ReactCommon/fabric/components/image/conversions.h
 create mode 100644 ReactCommon/fabric/components/image/tests/ImageTest.cpp

diff --git a/ReactCommon/fabric/components/image/BUCK b/ReactCommon/fabric/components/image/BUCK
new file mode 100644
index 000000000000..5cc0aed42715
--- /dev/null
+++ b/ReactCommon/fabric/components/image/BUCK
@@ -0,0 +1,80 @@
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+
+rn_xplat_cxx_library(
+    name = "image",
+    srcs = glob(
+        ["**/*.cpp"],
+        exclude = glob(["tests/**/*.cpp"]),
+    ),
+    headers = [],
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/components/image",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:futures",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+        react_native_xplat_target("fabric/imagemanager:imagemanager"),
+        react_native_xplat_target("fabric/view:view"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":image",
+        ],
+    )
diff --git a/ReactCommon/fabric/components/image/ImageComponentDescriptor.h b/ReactCommon/fabric/components/image/ImageComponentDescriptor.h
new file mode 100644
index 000000000000..b2219e4495b2
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageComponentDescriptor.h
@@ -0,0 +1,46 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/components/image/ImageShadowNode.h>
+#include <fabric/core/ConcreteComponentDescriptor.h>
+#include <fabric/imagemanager/ImageManager.h>
+#include <fabric/uimanager/ContextContainer.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Descriptor for <Image> component.
+ */
+class ImageComponentDescriptor final:
+  public ConcreteComponentDescriptor<ImageShadowNode> {
+
+public:
+  ImageComponentDescriptor(SharedEventDispatcher eventDispatcher, const SharedContextContainer &contextContainer):
+    ConcreteComponentDescriptor(eventDispatcher),
+    imageManager_(std::static_pointer_cast<ImageManager>(contextContainer->at(typeid(ImageManager)))) {}
+
+  void adopt(UnsharedShadowNode shadowNode) const override {
+    ConcreteComponentDescriptor::adopt(shadowNode);
+
+    assert(std::dynamic_pointer_cast<ImageShadowNode>(shadowNode));
+    auto imageShadowNode = std::static_pointer_cast<ImageShadowNode>(shadowNode);
+
+    // `ImageShadowNode` uses `ImageManager` to initiate image loading and
+    // communicate the loading state and results to mounting layer.
+    imageShadowNode->setImageManager(imageManager_);
+  }
+
+private:
+  const SharedImageManager imageManager_;
+};
+
+} // namespace react
+} // namespace facebook
+
diff --git a/ReactCommon/fabric/components/image/ImageEventEmitter.cpp b/ReactCommon/fabric/components/image/ImageEventEmitter.cpp
new file mode 100644
index 000000000000..85ba6114ebc2
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageEventEmitter.cpp
@@ -0,0 +1,38 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ImageEventEmitter.h"
+
+namespace facebook {
+namespace react {
+
+void ImageEventEmitter::onLoadStart() const {
+  dispatchEvent("loadStart");
+}
+
+void ImageEventEmitter::onLoad() const {
+  dispatchEvent("load");
+}
+
+void ImageEventEmitter::onLoadEnd() const {
+  dispatchEvent("loadEnd");
+}
+
+void ImageEventEmitter::onProgress() const {
+  dispatchEvent("progress");
+}
+
+void ImageEventEmitter::onError() const {
+  dispatchEvent("error");
+}
+
+void ImageEventEmitter::onPartialLoad() const {
+  dispatchEvent("partialLoad");
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/ImageEventEmitter.h b/ReactCommon/fabric/components/image/ImageEventEmitter.h
new file mode 100644
index 000000000000..f06fb837efd3
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageEventEmitter.h
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+#pragma once
+
+#include <fabric/view/ViewEventEmitter.h>
+
+namespace facebook {
+namespace react {
+
+class ImageEventEmitter:
+  public ViewEventEmitter {
+
+public:
+  using ViewEventEmitter::ViewEventEmitter;
+
+  void onLoadStart() const;
+  void onLoad() const;
+  void onLoadEnd() const;
+  void onProgress() const;
+  void onError() const;
+  void onPartialLoad() const;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/ImageLocalData.cpp b/ReactCommon/fabric/components/image/ImageLocalData.cpp
new file mode 100644
index 000000000000..7ce5429da5f4
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageLocalData.cpp
@@ -0,0 +1,37 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "ImageLocalData.h"
+
+#include <fabric/components/image/conversions.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
+
+namespace facebook {
+namespace react {
+
+ImageSource ImageLocalData::getImageSource() const {
+  return imageSource_;
+}
+
+const ImageRequest &ImageLocalData::getImageRequest() const {
+  return imageRequest_;
+}
+
+#pragma mark - DebugStringConvertible
+
+std::string ImageLocalData::getDebugName() const {
+  return "ImageLocalData";
+}
+
+SharedDebugStringConvertibleList ImageLocalData::getDebugProps() const {
+  return {
+    debugStringConvertibleItem("imageSource", imageSource_)
+  };
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/ImageLocalData.h b/ReactCommon/fabric/components/image/ImageLocalData.h
new file mode 100644
index 000000000000..5a3d1a75dfaa
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageLocalData.h
@@ -0,0 +1,57 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/core/LocalData.h>
+#include <fabric/imagemanager/primitives.h>
+#include <fabric/imagemanager/ImageRequest.h>
+
+namespace facebook {
+namespace react {
+
+class ImageLocalData;
+
+using SharedImageLocalData = std::shared_ptr<const ImageLocalData>;
+
+/*
+ * LocalData for <Image> component.
+ * Represents the image request state and (possible) retrieved image bitmap.
+ */
+class ImageLocalData:
+  public LocalData {
+
+public:
+
+  ImageLocalData(const ImageSource &imageSource, ImageRequest imageRequest):
+    imageSource_(imageSource),
+    imageRequest_(std::move(imageRequest)) {};
+
+  /*
+   * Returns stored ImageSource object.
+   */
+  ImageSource getImageSource() const;
+
+  /*
+   * Exposes for reading stored `ImageRequest` object.
+   * `ImageRequest` object cannot be copied or moved from `ImageLocalData`.
+   */
+  const ImageRequest &getImageRequest() const;
+
+#pragma mark - DebugStringConvertible
+
+  std::string getDebugName() const override;
+  SharedDebugStringConvertibleList getDebugProps() const override;
+
+private:
+
+  ImageSource imageSource_;
+  ImageRequest imageRequest_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/ImageProps.cpp b/ReactCommon/fabric/components/image/ImageProps.cpp
new file mode 100644
index 000000000000..8e09e551710b
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageProps.cpp
@@ -0,0 +1,25 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/components/image/conversions.h>
+#include <fabric/components/image/ImageProps.h>
+#include <fabric/core/propsConversions.h>
+
+namespace facebook {
+namespace react {
+
+ImageProps::ImageProps(const ImageProps &sourceProps, const RawProps &rawProps):
+  ViewProps(sourceProps, rawProps),
+  sources(convertRawProp(rawProps, "source", sourceProps.sources)),
+  defaultSources(convertRawProp(rawProps, "defaultSource", sourceProps.defaultSources)),
+  resizeMode(convertRawProp(rawProps, "resizeMode", sourceProps.resizeMode, ImageResizeMode::Stretch)),
+  blurRadius(convertRawProp(rawProps, "blurRadius", sourceProps.blurRadius)),
+  capInsets(convertRawProp(rawProps, "capInsets", sourceProps.capInsets)),
+  tintColor(convertRawProp(rawProps, "tintColor", sourceProps.tintColor)) {}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/ImageProps.h b/ReactCommon/fabric/components/image/ImageProps.h
new file mode 100644
index 000000000000..6d772d1c99e2
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageProps.h
@@ -0,0 +1,34 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <fabric/graphics/Color.h>
+#include <fabric/imagemanager/primitives.h>
+#include <fabric/view/ViewProps.h>
+
+namespace facebook {
+namespace react {
+
+// TODO (T28334063): Consider for codegen.
+class ImageProps final:
+  public ViewProps {
+
+public:
+  ImageProps() = default;
+  ImageProps(const ImageProps &sourceProps, const RawProps &rawProps);
+
+#pragma mark - Props
+
+  const ImageSources sources {};
+  const ImageSources defaultSources {};
+  const ImageResizeMode resizeMode {ImageResizeMode::Stretch};
+  const Float blurRadius {};
+  const EdgeInsets capInsets {};
+  const SharedColor tintColor {};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/ImageShadowNode.cpp b/ReactCommon/fabric/components/image/ImageShadowNode.cpp
new file mode 100644
index 000000000000..c9849fb347e7
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageShadowNode.cpp
@@ -0,0 +1,91 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <cstdlib>
+
+#include <fabric/components/image/ImageShadowNode.h>
+#include <fabric/components/image/ImageLocalData.h>
+#include <fabric/core/LayoutContext.h>
+
+namespace facebook {
+namespace react {
+
+ComponentName ImageShadowNode::getComponentName() const {
+  return ComponentName("Image");
+}
+
+void ImageShadowNode::setImageManager(const SharedImageManager &imageManager) {
+  ensureUnsealed();
+  imageManager_ = imageManager;
+}
+
+void ImageShadowNode::updateLocalData() {
+  const auto &imageSource = getImageSource();
+  const auto &currentLocalData = getLocalData();
+  if (currentLocalData) {
+    assert(std::dynamic_pointer_cast<const ImageLocalData>(currentLocalData));
+    auto currentImageLocalData = std::static_pointer_cast<const ImageLocalData>(currentLocalData);
+    if (currentImageLocalData->getImageSource() == imageSource) {
+      // Same `imageSource` is already in `localData`,
+      // no need to (re)request an image resource.
+      return;
+    }
+  }
+
+  // Now we are about to mutate the Shadow Node.
+  ensureUnsealed();
+
+  auto imageRequest = imageManager_->requestImage(imageSource);
+  auto imageLocalData = std::make_shared<ImageLocalData>(imageSource, std::move(imageRequest));
+  setLocalData(imageLocalData);
+}
+
+ImageSource ImageShadowNode::getImageSource() const {
+  auto sources = getProps()->sources;
+
+  if (sources.size() == 0) {
+    return {.type = ImageSource::Type::Invalid};
+  }
+
+  if (sources.size() == 1) {
+    return sources[0];
+  }
+
+  auto layoutMetrics = getLayoutMetrics();
+  auto size = layoutMetrics.getContentFrame().size;
+  auto scale = layoutMetrics.pointScaleFactor;
+  auto targetImageArea = size.width * size.height * scale * scale;
+  auto bestFit = kFloatMax;
+
+  ImageSource bestSource;
+
+  for (const auto &source : sources) {
+    auto sourceSize = source.size;
+    auto sourceScale = source.scale == 0 ? scale : source.scale;
+    auto sourceArea =
+      sourceSize.width * sourceSize.height * sourceScale * sourceScale;
+
+    auto fit = std::abs(1 - (sourceArea / targetImageArea));
+
+    if (fit < bestFit) {
+      bestFit = fit;
+      bestSource = source;
+    }
+  }
+
+  return bestSource;
+}
+
+#pragma mark - LayoutableShadowNode
+
+void ImageShadowNode::layout(LayoutContext layoutContext) {
+  updateLocalData();
+  ConcreteViewShadowNode::layout(layoutContext);
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/ImageShadowNode.h b/ReactCommon/fabric/components/image/ImageShadowNode.h
new file mode 100644
index 000000000000..2c2d39bfc228
--- /dev/null
+++ b/ReactCommon/fabric/components/image/ImageShadowNode.h
@@ -0,0 +1,53 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/components/image/ImageEventEmitter.h>
+#include <fabric/components/image/ImageProps.h>
+#include <fabric/imagemanager/ImageManager.h>
+#include <fabric/imagemanager/primitives.h>
+#include <fabric/view/ConcreteViewShadowNode.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * `ShadowNode` for <Image> component.
+ */
+class ImageShadowNode final:
+  public ConcreteViewShadowNode<ImageProps, ImageEventEmitter> {
+
+public:
+
+  using ConcreteViewShadowNode::ConcreteViewShadowNode;
+
+  ComponentName getComponentName() const override;
+
+  /*
+   * Associates a shared `ImageManager` with the node.
+   */
+  void setImageManager(const SharedImageManager &imageManager);
+
+#pragma mark - LayoutableShadowNode
+
+  void layout(LayoutContext layoutContext) override;
+
+private:
+
+  /*
+   * (Re)Creates a `LocalData` object (with `ImageRequest`) if needed.
+   */
+  void updateLocalData();
+
+  ImageSource getImageSource() const;
+
+  SharedImageManager imageManager_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/conversions.h b/ReactCommon/fabric/components/image/conversions.h
new file mode 100644
index 000000000000..3ec3674efd5c
--- /dev/null
+++ b/ReactCommon/fabric/components/image/conversions.h
@@ -0,0 +1,90 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <fabric/imagemanager/primitives.h>
+#include <fabric/graphics/conversions.h>
+#include <folly/dynamic.h>
+
+namespace facebook {
+namespace react {
+
+inline void fromDynamic(const folly::dynamic &value, ImageSource &result) {
+  if (value.isString()) {
+    result = {
+      .type = ImageSource::Type::Remote,
+      .uri = value.asString()
+    };
+    return;
+  }
+
+  if (value.isObject()) {
+    result = {};
+
+    result.type = ImageSource::Type::Remote;
+
+    if (value.count("__packager_asset")) {
+      result.type = ImageSource::Type::Local;
+    }
+
+    if (value.count("width") && value.count("height")) {
+      fromDynamic(value, result.size);
+    }
+
+    if (value.count("scale")) {
+      result.scale = (Float)value["scale"].asDouble();
+    } else {
+      result.scale = value.count("deprecated") ? 0.0 : 1.0;
+    }
+
+    if (value.count("url")) {
+      result.uri = value["url"].asString();
+    }
+
+    if (value.count("uri")) {
+      result.uri = value["uri"].asString();
+    }
+
+    if (value.count("bundle")) {
+      result.bundle = value["bundle"].asString();
+      result.type = ImageSource::Type::Local;
+    }
+
+    return;
+  }
+
+  abort();
+}
+
+inline std::string toString(const ImageSource &value) {
+  return "{uri: " + value.uri + "}";
+}
+
+inline void fromDynamic(const folly::dynamic &value, ImageResizeMode &result) {
+  assert(value.isString());
+  auto stringValue = value.asString();
+  if (stringValue == "cover") { result = ImageResizeMode::Cover; return; }
+  if (stringValue == "contain") { result = ImageResizeMode::Contain; return; }
+  if (stringValue == "stretch") { result = ImageResizeMode::Stretch; return; }
+  if (stringValue == "center") { result = ImageResizeMode::Center; return; }
+  if (stringValue == "repeat") { result = ImageResizeMode::Repeat; return; }
+  abort();
+}
+
+inline std::string toString(const ImageResizeMode &value) {
+  switch (value) {
+    case ImageResizeMode::Cover: return "cover";
+    case ImageResizeMode::Contain: return "contain";
+    case ImageResizeMode::Stretch: return "stretch";
+    case ImageResizeMode::Center: return "center";
+    case ImageResizeMode::Repeat: return "repeat";
+  }
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/components/image/tests/ImageTest.cpp b/ReactCommon/fabric/components/image/tests/ImageTest.cpp
new file mode 100644
index 000000000000..a55a5783d83c
--- /dev/null
+++ b/ReactCommon/fabric/components/image/tests/ImageTest.cpp
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+TEST(SwitchTest, testSomething) {
+  // TODO
+}
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 0c17bfc0089a..8f71c6418786 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -60,6 +60,10 @@ static const std::string componentNameByReactViewName(std::string viewName) {
     return "Text";
   }
 
+  if (viewName == "ImageView") {
+    return "Image";
+  }
+
   // We need this temporarly for testing purposes until we have proper
   // implementation of core components: <Image>, <ScrollContentView>.
   if (

From f6aa5db0e4bdc0edd07de85f76560a522ea38646 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:42 -0700
Subject: [PATCH 0887/1109] Fabric: RCTImageComponentView

Summary:
@public
This is iOS-specific implementation of <Image> view.
Not all props and features are supported yet.
Known issues:
 - Animated GIFs;
 - CA transitions during image appearance.

Reviewed By: mdvacca

Differential Revision: D8526570

fbshipit-source-id: a4b1dca583b139b8a09431565a79f051fae67a36
---
 .../Image/RCTImageComponentView.h             |  21 ++++
 .../Image/RCTImageComponentView.mm            | 106 ++++++++++++++++++
 React/Fabric/Utils/MainQueueExecutor.h        |  23 ++++
 React/Fabric/Utils/MainQueueExecutor.mm       |  29 +++++
 4 files changed, 179 insertions(+)
 create mode 100644 React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.h
 create mode 100644 React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.mm
 create mode 100644 React/Fabric/Utils/MainQueueExecutor.h
 create mode 100644 React/Fabric/Utils/MainQueueExecutor.mm

diff --git a/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.h b/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.h
new file mode 100644
index 000000000000..a9bcf7d392b9
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.h
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import <UIKit/UIKit.h>
+
+#import <React/RCTViewComponentView.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/**
+ * UIView class for root <Image> component.
+ */
+@interface RCTImageComponentView : RCTViewComponentView
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.mm b/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.mm
new file mode 100644
index 000000000000..9e8cb4de4856
--- /dev/null
+++ b/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.mm
@@ -0,0 +1,106 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#import "RCTImageComponentView.h"
+
+#import <fabric/components/image/ImageEventEmitter.h>
+#import <fabric/components/image/ImageLocalData.h>
+#import <fabric/components/image/ImageProps.h>
+#import <fabric/imagemanager/ImageRequest.h>
+#import <fabric/imagemanager/ImageResponse.h>
+#import <fabric/imagemanager/RCTImagePrimitivesConversions.h>
+
+#import "RCTConversions.h"
+#import "MainQueueExecutor.h"
+
+using namespace facebook::react;
+
+@implementation RCTImageComponentView {
+  UIImageView *_imageView;
+  SharedImageLocalData _imageLocalData;
+}
+
+- (instancetype)initWithFrame:(CGRect)frame
+{
+  if (self = [super initWithFrame:frame]) {
+    _imageView = [[UIImageView alloc] initWithFrame:self.bounds];
+    _imageView.clipsToBounds = YES;
+
+    auto defaultProps = ImageProps();
+    _imageView.contentMode = (UIViewContentMode)RCTResizeModeFromImageResizeMode(defaultProps.resizeMode);
+
+    self.contentView = _imageView;
+  }
+
+  return self;
+}
+
+- (void)updateProps:(SharedProps)props oldProps:(SharedProps)oldProps
+{
+  if (!oldProps) {
+    oldProps = _props ?: std::make_shared<const ImageProps>();
+  }
+  _props = props;
+
+  [super updateProps:props oldProps:oldProps];
+
+  const auto &oldImageProps = *std::dynamic_pointer_cast<const ImageProps>(oldProps);
+  const auto &newImageProps = *std::dynamic_pointer_cast<const ImageProps>(props);
+
+  // `resizeMode`
+  if (oldImageProps.resizeMode != newImageProps.resizeMode) {
+    if (newImageProps.resizeMode == ImageResizeMode::Repeat) {
+      // Repeat resize mode is handled by the UIImage. Use scale to fill
+      // so the repeated image fills the UIImageView.
+      _imageView.contentMode = UIViewContentModeScaleToFill;
+    } else {
+      _imageView.contentMode = (UIViewContentMode)RCTResizeModeFromImageResizeMode(newImageProps.resizeMode);
+    }
+  }
+
+  // `tintColor`
+  if (oldImageProps.tintColor != newImageProps.tintColor) {
+    _imageView.tintColor = [UIColor colorWithCGColor:newImageProps.tintColor.get()];
+  }
+}
+
+- (void)updateLocalData:(SharedLocalData)localData
+           oldLocalData:(SharedLocalData)oldLocalData
+{
+  _imageLocalData = std::static_pointer_cast<const ImageLocalData>(localData);
+  assert(_imageLocalData);
+  auto future = _imageLocalData->getImageRequest().getResponseFuture();
+  future.via(&MainQueueExecutor::instance()).then([self](ImageResponse &&imageResponse) {
+    self.image = (__bridge_transfer UIImage *)imageResponse.getImage().get();
+  });
+}
+
+- (void)setImage:(UIImage *)image
+{
+  const auto &imageProps = *std::static_pointer_cast<const ImageProps>(_props);
+
+  if (imageProps.tintColor) {
+    image = [image imageWithRenderingMode:UIImageRenderingModeAlwaysTemplate];
+  }
+
+  if (imageProps.resizeMode == ImageResizeMode::Repeat) {
+    image = [image resizableImageWithCapInsets:RCTUIEdgeInsetsFromEdgeInsets(imageProps.capInsets)
+                                  resizingMode:UIImageResizingModeTile];
+  } else if (imageProps.capInsets != EdgeInsets()) {
+    // Applying capInsets of 0 will switch the "resizingMode" of the image to "tile" which is undesired.
+    image = [image resizableImageWithCapInsets:RCTUIEdgeInsetsFromEdgeInsets(imageProps.capInsets)
+                                  resizingMode:UIImageResizingModeStretch];
+  }
+
+  _imageView.image = image;
+
+  // Apply trilinear filtering to smooth out mis-sized images.
+  _imageView.layer.minificationFilter = kCAFilterTrilinear;
+  _imageView.layer.magnificationFilter = kCAFilterTrilinear;
+}
+
+@end
diff --git a/React/Fabric/Utils/MainQueueExecutor.h b/React/Fabric/Utils/MainQueueExecutor.h
new file mode 100644
index 000000000000..b43a6d7cdb4c
--- /dev/null
+++ b/React/Fabric/Utils/MainQueueExecutor.h
@@ -0,0 +1,23 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <folly/Executor.h>
+
+namespace facebook {
+namespace react {
+
+class MainQueueExecutor:
+  public folly::Executor {
+
+public:
+  static MainQueueExecutor &instance();
+
+  void add(folly::Func function) override;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/React/Fabric/Utils/MainQueueExecutor.mm b/React/Fabric/Utils/MainQueueExecutor.mm
new file mode 100644
index 000000000000..a80d3be1b3e5
--- /dev/null
+++ b/React/Fabric/Utils/MainQueueExecutor.mm
@@ -0,0 +1,29 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "MainQueueExecutor.h"
+
+#include <dispatch/dispatch.h>
+#include <folly/Indestructible.h>
+
+namespace facebook {
+namespace react {
+
+MainQueueExecutor &MainQueueExecutor::instance() {
+  static auto instance = folly::Indestructible<MainQueueExecutor>{};
+  return *instance;
+}
+
+void MainQueueExecutor::add(folly::Func function) {
+  __block folly::Func blockFunction = std::move(function);
+  dispatch_async(dispatch_get_main_queue(), ^{
+    blockFunction();
+  });
+}
+
+} // namespace react
+} // namespace facebook

From 8ef539e0c2918ba307e02ec7cb85081987ffb0ca Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 07:28:44 -0700
Subject: [PATCH 0888/1109] Fabric: `fromDynamic`: Parsing vector type when
 source has no array

Summary:
@public
If some prop has `std::vector` type, it possible that on JS side we want to pass just one element of the array.
And in this case we sometimes drop array initialization (`[]`) part, so instead of passing `[{x:1, y:1}]` we pass `{x:1, y:1}`.
This diff adds support for that.

Reviewed By: mdvacca

Differential Revision: D8526572

fbshipit-source-id: 33d4369ac48cac3eb1c534f477d8259e76e0c547
---
 ReactCommon/fabric/core/propsConversions.h | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/ReactCommon/fabric/core/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
index f255d6c80e71..c5efbe3d4564 100644
--- a/ReactCommon/fabric/core/propsConversions.h
+++ b/ReactCommon/fabric/core/propsConversions.h
@@ -26,6 +26,13 @@ inline void fromDynamic(const folly::dynamic &value, std::string &result) { resu
 
 template <typename T>
 inline void fromDynamic(const folly::dynamic &value, std::vector<T> &result) {
+  if (!value.isArray()) {
+    T itemResult;
+    fromDynamic(value, itemResult);
+    result = {itemResult};
+    return;
+  }
+
   result.clear();
   T itemResult;
   for (auto &itemValue : value) {

From 33ba5e8fa26a3e8f32e386f377107a7a03743360 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 22 Jun 2018 08:09:48 -0700
Subject: [PATCH 0889/1109] Stop using projectRoots from RN cli

Summary:
This diff tries to fix an issue that started appearing in RN master when the latest metro version is used (more info here: https://github.com/facebook/react-native/commit/c5ce7626977a7650e8dce335f2ce78b94839a2a8#commitcomment-29443117).

The problem is that RN is still reading `projectRoots` from the Metro config and trying to call `concat()` on them. Latest Metro sets the default `projectRoots` to null, so this fails.

Also, a couple other things have been done:

* Make sure that the `projectRoot` and `watchFolder` objects from args are passed to Metro (so they contain the overrides from the CLI arguments).
* Add a `--projectRoot` CLI arg, replacing the `--root` one (this is not actually needed, since it does the same as `--watchFolders`

Differential Revision: D8567229

fbshipit-source-id: 3b76fd8e23d201a4097e9dfba3a512d64f348cb0
---
 local-cli/server/runServer.js |  6 +++---
 local-cli/server/server.js    | 22 +++++++++-------------
 2 files changed, 12 insertions(+), 16 deletions(-)

diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index e2a0b10bfca6..e2d57d4b1ebc 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -56,7 +56,7 @@ export type Args = {|
   +nonPersistent: boolean,
   +platforms: $ReadOnlyArray<string>,
   +port: number,
-  +projectRoots: $ReadOnlyArray<string>,
+  +projectRoot: string,
   +resetCache: boolean,
   +sourceExts: $ReadOnlyArray<string>,
   +verbose: boolean,
@@ -197,7 +197,7 @@ function getPackagerServer(args, config, reporter) {
     polyfillModuleNames: config.getPolyfillModuleNames(),
     postMinifyProcess: config.postMinifyProcess,
     postProcessBundleSourcemap: config.postProcessBundleSourcemap,
-    projectRoot: config.getProjectRoot(),
+    projectRoot: args.projectRoot,
     providesModuleNodeModules: providesModuleNodeModules,
     reporter,
     resetCache: args.resetCache,
@@ -206,7 +206,7 @@ function getPackagerServer(args, config, reporter) {
     transformModulePath: transformModulePath,
     verbose: args.verbose,
     watch: !args.nonPersistent,
-    watchFolders: config.getWatchFolders(),
+    watchFolders: args.watchFolders,
     workerPath: config.getWorkerPath(),
   });
 }
diff --git a/local-cli/server/server.js b/local-cli/server/server.js
index d4d977a61555..f74f7f16a79b 100644
--- a/local-cli/server/server.js
+++ b/local-cli/server/server.js
@@ -10,7 +10,6 @@
 
 'use strict';
 
-const path = require('path');
 const runServer = require('./runServer');
 
 import type {RNConfig} from '../core';
@@ -20,15 +19,12 @@ import type {Args as RunServerArgs} from './runServer';
 /**
  * Starts the React Native Packager Server.
  */
-function server(argv: mixed, config: RNConfig, allArgs: Object) {
-  const {root, ...args} = allArgs;
-  args.projectRoots = args.projectRoots.concat(root);
-
+function server(argv: mixed, config: RNConfig, args: Object) {
   const startedCallback = logReporter => {
     logReporter.update({
       type: 'initialize_started',
       port: args.port,
-      projectRoots: args.projectRoots,
+      projectRoots: args.watchFolders,
     });
 
     process.on('uncaughtException', error => {
@@ -68,19 +64,19 @@ module.exports = {
       default: '',
     },
     {
-      command: '--root [list]',
-      description:
-        'add another root(s) to be used by the packager in this project',
-      parse: (val: string) => val.split(',').map(root => path.resolve(root)),
-      default: [],
+      command: '--projectRoot [string]',
+      description: 'Specify the main project root',
+      default: (config: ConfigT) => {
+        return config.getProjectRoot();
+      },
     },
     {
       command: '--watchFolders [list]',
       description:
-        'Sepcify any additional folders to be added to the watch list',
+        'Specify any additional folders to be added to the watch list',
       parse: (val: string) => val.split(','),
       default: (config: ConfigT) => {
-        return config.getProjectRoots ? config.getProjectRoots() : undefined;
+        return config.getWatchFolders();
       },
     },
     {

From 74627d48339150a98bd8f66019f4b5bc8f42a1ee Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Fri, 22 Jun 2018 10:56:52 -0700
Subject: [PATCH 0890/1109] Revert D8528543: Added Ignore color inversion prop
 to components in marketplace

Differential Revision:
D8528543

Original commit changeset: 63caf592bc71

fbshipit-source-id: 7bfcfbba744ac1e15753f52aebe104f53e5e9d5f
---
 Libraries/Image/ImageBackground.js | 5 +----
 1 file changed, 1 insertion(+), 4 deletions(-)

diff --git a/Libraries/Image/ImageBackground.js b/Libraries/Image/ImageBackground.js
index a128880a1780..7b86d9c5f529 100644
--- a/Libraries/Image/ImageBackground.js
+++ b/Libraries/Image/ImageBackground.js
@@ -60,10 +60,7 @@ class ImageBackground extends React.Component<$FlowFixMeProps> {
     const {children, style, imageStyle, imageRef, ...props} = this.props;
 
     return (
-      <View
-        accessibilityIgnoresInvertColors={true}
-        style={style}
-        ref={this._captureRef}>
+      <View style={style} ref={this._captureRef}>
         <Image
           {...props}
           style={[

From f19c36116c8ef61c043fd77c599906f59585da6c Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 22 Jun 2018 11:29:05 -0700
Subject: [PATCH 0891/1109] Clean-up parent / owner reference of children
 during clonning

Summary: This diff cleans up the parent / owner references for children of ReactShadowNode / YogaNode during cloning. The reason of this behavior is to avoid retaining every generation of trees during cloning. This fixes a memory leak detected when running the ProgressBarExample.android.js in catalyst app

Reviewed By: fkgozali

Differential Revision: D8019894

fbshipit-source-id: b0d38f0c836ffec534f64fa1adbd7511ecf3473d
---
 .../react/uimanager/ReactShadowNodeImpl.java     | 16 ++++++++++++++--
 .../main/java/com/facebook/yoga/YogaNode.java    | 12 +++++++++---
 ReactCommon/yoga/yoga/Yoga.cpp                   | 12 ++++++++----
 3 files changed, 31 insertions(+), 9 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 35406a11aa01..6a334c3a7834 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -193,12 +193,24 @@ public ReactShadowNodeImpl mutableCopy(long instanceHandle) {
       // Virtual ReactShadowNode do not have a YogaNode associated
       copy.mYogaNode = null;
     }
-    copy.mNativeChildren = mNativeChildren == null ? null : new ArrayList<>(mNativeChildren);
     copy.mTotalNativeChildren = mTotalNativeChildren;
-    copy.mChildren = mChildren == null ? null : new ArrayList<>(mChildren);
+    copy.mNativeChildren = copyChildren(mNativeChildren);
+    copy.mChildren = copyChildren(mChildren);
+
     return copy;
   }
 
+  @Nullable
+  private ArrayList<ReactShadowNodeImpl> copyChildren(@Nullable List<ReactShadowNodeImpl> list){
+    ArrayList<ReactShadowNodeImpl> result = list == null ? null : new ArrayList<>(list);
+    if (result != null) {
+      for (ReactShadowNodeImpl child : result) {
+        child.mParent = null;
+      }
+    }
+    return result;
+  }
+
   @Override
   public ReactShadowNodeImpl mutableCopyWithNewChildren(long instanceHandle) {
     ReactShadowNodeImpl copy = copy();
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index 90caf8f81e01..f8b895b1663a 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -1,8 +1,9 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
 
 package com.facebook.yoga;
@@ -185,6 +186,11 @@ public YogaNode clone() {
       clonedYogaNode.mOwner = null;
       clonedYogaNode.mChildren =
           mChildren != null ? (List<YogaNode>) ((ArrayList) mChildren).clone() : null;
+      if (clonedYogaNode.mChildren != null) {
+        for (YogaNode child : clonedYogaNode.mChildren) {
+          child.mOwner = null;
+        }
+      }
       return clonedYogaNode;
     } catch (CloneNotSupportedException ex) {
       // This class implements Cloneable, this should not happen
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index c6a8ffd2ea1e..3c83ce080c75 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1,8 +1,9 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
 
 #include "Yoga.h"
@@ -243,6 +244,9 @@ YGNodeRef YGNodeClone(YGNodeRef oldNode) {
       oldNode->getConfig(),
       node != nullptr,
       "Could not allocate memory for node");
+  for (auto &item : oldNode->getChildren()) {
+    item->setOwner(nullptr);
+  }
   gNodeInstanceCount++;
   node->setOwner(nullptr);
   return node;

From 001e217f33894bdbad9c788b29a653d23907b96e Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 22 Jun 2018 11:29:07 -0700
Subject: [PATCH 0892/1109] Introduce "Sealing" of ReactShadowNodes

Summary: This diff introduces the concept of "Seal" ReactShadowNodes. This new field will be used to guarantee immutability of commited ReactShodow Nodes.

Reviewed By: fkgozali

Differential Revision: D8552709

fbshipit-source-id: dfd95730f10341af0dd762f8a8aa186563cf33e9
---
 .../facebook/react/fabric/FabricUIManager.java |  9 +++------
 .../react/uimanager/ReactShadowNode.java       | 12 ++++++++++++
 .../react/uimanager/ReactShadowNodeImpl.java   | 12 ++++++++++++
 .../react/fabric/FabricUIManagerTest.java      | 18 ++++++++++++++++++
 4 files changed, 45 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index d72e6cc8b45f..a5a719cc1940 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -10,7 +10,6 @@
 import static android.view.View.MeasureSpec.AT_MOST;
 import static android.view.View.MeasureSpec.EXACTLY;
 import static android.view.View.MeasureSpec.UNSPECIFIED;
-import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
 import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 
 import android.os.SystemClock;
@@ -22,7 +21,6 @@
 import com.facebook.proguard.annotations.DoNotStrip;
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.ReactApplicationContext;
-import com.facebook.react.bridge.ReactMethod;
 import com.facebook.react.bridge.ReadableArray;
 import com.facebook.react.bridge.ReadableMap;
 import com.facebook.react.bridge.ReadableNativeMap;
@@ -41,13 +39,11 @@
 import com.facebook.react.uimanager.ReactShadowNodeImpl;
 import com.facebook.react.uimanager.ReactStylesDiffMap;
 import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIManagerHelper;
 import com.facebook.react.uimanager.UIViewOperationQueue;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
-import com.facebook.react.uimanager.common.ViewUtil;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.systrace.Systrace;
 import com.facebook.systrace.SystraceMessage;
@@ -295,10 +291,10 @@ public void appendChild(ReactShadowNode parent, ReactShadowNode child) {
       "FabricUIManager.appendChild")
       .flush();
     try {
-      // If the child to append is shared with another tree (child.getParent() != null),
+      // If the child to append was already committed (child.isSealed()),
       // then we add a mutation of it. In the future this will be performed by FabricJS / Fiber.
       //TODO: T27926878 avoid cloning shared child
-      if (child.getParent() != null) {
+      if (child.isSealed()) {
         child = child.mutableCopy(child.getInstanceHandle());
       }
       parent.addChildAt(child, parent.getChildCount());
@@ -474,6 +470,7 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
     // and we do not need to hold references to the previous tree anymore
     node.setOriginalReactShadowNode(null);
     node.markUpdateSeen();
+    node.markAsSealed();
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
index ed134e2160b7..3f78d8af5e3f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
@@ -377,4 +377,16 @@ public interface ReactShadowNode<T extends ReactShadowNode> {
   long getInstanceHandle();
 
   void setInstanceHandle(long instanceHandle);
+
+  /**
+   * Mark this {@link ReactShadowNode} as sealed. This means that the node was already committed
+   * and it should not be updated anymore.
+   */
+  void markAsSealed();
+
+  /**
+   * @return a {@link boolean} that represents if the {@link ReactShadowNode} is sealed.
+   */
+  boolean isSealed();
+
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index 6a334c3a7834..dffd372662ce 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -128,6 +128,7 @@ public YogaNode cloneNode(YogaNode oldYogaNode,
 
   private @Nullable ReactStylesDiffMap mNewProps;
   private long mInstanceHandle;
+  private boolean mIsSealed = false;
 
   public ReactShadowNodeImpl() {
     mDefaultPadding = new Spacing(0);
@@ -164,6 +165,7 @@ protected ReactShadowNodeImpl(ReactShadowNodeImpl original) {
     mNewProps = null;
     mParent = null;
     mOriginalReactShadowNode = original;
+    mIsSealed = false;
   }
 
   private void replaceChild(ReactShadowNodeImpl newNode, int childIndex) {
@@ -1147,4 +1149,14 @@ public long getInstanceHandle() {
   public void setInstanceHandle(long instanceHandle) {
     mInstanceHandle = instanceHandle;
   }
+
+  @Override
+  public void markAsSealed() {
+    mIsSealed = true;
+  }
+
+  @Override
+  public boolean isSealed() {
+    return mIsSealed;
+  }
 }
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index ba6b10c8c3fd..ee7e96fb2f06 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -233,6 +233,24 @@ public void testCompleteRoot() {
     mFabricUIManager.completeRoot(rootTag, children);
   }
 
+  @Test
+  public void testSealReactShadowNode() {
+    ReactRootView rootView =
+      new ReactRootView(RuntimeEnvironment.application.getApplicationContext());
+    int rootTag = mFabricUIManager.addRootView(rootView);
+    String viewClass = ReactViewManager.REACT_CLASS;
+
+    ReactShadowNode container = mFabricUIManager.createNode(6, viewClass, rootTag, null, randomInstanceHandle());
+    List<ReactShadowNode> childSet = mFabricUIManager.createChildSet(rootTag);
+    mFabricUIManager.appendChildToSet(childSet, container);
+
+    assertThat(container.isSealed()).isFalse();
+
+    mFabricUIManager.completeRoot(rootTag, childSet);
+
+    assertThat(container.isSealed()).isTrue();
+  }
+
   /**
    * Tests that cloned text nodes will not share measure functions
    */

From 93b568cc510c09ffa03b86a0c7605885580c852c Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 22 Jun 2018 11:29:09 -0700
Subject: [PATCH 0893/1109] Add sealing assertion in fabric

Summary: This diff checks if ReactShadowNode is sealed before updaing it.

Reviewed By: fkgozali

Differential Revision: D8584768

fbshipit-source-id: 64163d4bf124263d92153f68914c617f007fd90d
---
 .../react/fabric/FabricUIManager.java         | 19 +++---
 .../react/uimanager/ReactShadowNodeImpl.java  | 61 +++++++++++++++++++
 2 files changed, 73 insertions(+), 7 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index a5a719cc1940..05ce4025e3ad 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -451,7 +451,7 @@ private void applyUpdatesRecursive(ReactShadowNode node, float absoluteX, float
     }
 
     int tag = node.getReactTag();
-    if (mRootShadowNodeRegistry.getNode(tag) == null) {
+    if (getRootNode(tag) == null) {
       boolean frameDidChange =
           node.dispatchUpdates(absoluteX, absoluteY, mUIViewOperationQueue, null);
       // Notify JS about layout event if requested
@@ -511,13 +511,16 @@ public void onSizeChanged(final int width, final int height, int oldW, int oldH)
 
   @Override
   @DoNotStrip
-  public void updateRootLayoutSpecs(int rootViewTag, int widthMeasureSpec, int heightMeasureSpec) {
-    ReactShadowNode rootNode = mRootShadowNodeRegistry.getNode(rootViewTag);
+  public synchronized void updateRootLayoutSpecs(int rootViewTag, int widthMeasureSpec, int heightMeasureSpec) {
+    ReactShadowNode rootNode = getRootNode(rootViewTag);
     if (rootNode == null) {
       FLog.w(ReactConstants.TAG, "Tried to update non-existent root tag: " + rootViewTag);
       return;
     }
-    updateRootView(rootNode, widthMeasureSpec, heightMeasureSpec);
+
+    ReactShadowNode newRootNode = rootNode.mutableCopy(rootNode.getInstanceHandle());
+    updateRootView(newRootNode, widthMeasureSpec, heightMeasureSpec);
+    mRootShadowNodeRegistry.replaceNode(newRootNode);
   }
 
   /**
@@ -526,18 +529,20 @@ public void updateRootLayoutSpecs(int rootViewTag, int widthMeasureSpec, int hei
    * //TODO: change synchronization to integrate with new #render loop.
    */
   private synchronized void updateRootSize(int rootTag, int newWidth, int newHeight) {
-    ReactShadowNode rootNode = mRootShadowNodeRegistry.getNode(rootTag);
+    ReactShadowNode rootNode = getRootNode(rootTag);
     if (rootNode == null) {
       FLog.w(
         ReactConstants.TAG,
         "Tried to update size of non-existent tag: " + rootTag);
       return;
     }
+
+    ReactShadowNode newRootNode = rootNode.mutableCopy(rootNode.getInstanceHandle());
     int newWidthSpec = View.MeasureSpec.makeMeasureSpec(newWidth, View.MeasureSpec.EXACTLY);
     int newHeightSpec = View.MeasureSpec.makeMeasureSpec(newHeight, View.MeasureSpec.EXACTLY);
-    updateRootView(rootNode, newWidthSpec, newHeightSpec);
+    updateRootView(newRootNode, newWidthSpec, newHeightSpec);
 
-    completeRoot(rootTag, rootNode.getChildrenList());
+    completeRoot(rootTag, newRootNode.getChildrenList());
   }
 
   public void removeRootView(int rootTag) {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index dffd372662ce..d6075b7dbf76 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -299,6 +299,7 @@ public final boolean hasUpdates() {
 
   @Override
   public final void markUpdateSeen() {
+    assertNotSealed();
     mNodeUpdated = false;
     if (hasNewLayout()) {
       markLayoutSeen();
@@ -324,6 +325,7 @@ public final boolean hasUnseenUpdates() {
 
   @Override
   public void dirty() {
+    assertNotSealed();
     if (!isVirtual()) {
       mYogaNode.dirty();
     }
@@ -336,6 +338,7 @@ public final boolean isDirty() {
 
   @Override
   public void addChildAt(ReactShadowNodeImpl child, int i) {
+    assertNotSealed();
     if (mChildren == null) {
       mChildren = new ArrayList<>(4);
     }
@@ -367,6 +370,7 @@ public void addChildAt(ReactShadowNodeImpl child, int i) {
 
   @Override
   public ReactShadowNodeImpl removeChildAt(int i) {
+    assertNotSealed();
     if (mChildren == null) {
       throw new ArrayIndexOutOfBoundsException(
         "Index " + i + " out of bounds: node has no children");
@@ -539,6 +543,7 @@ public final int getReactTag() {
 
   @Override
   public void setReactTag(int reactTag) {
+    assertNotSealed();
     mReactTag = reactTag;
   }
 
@@ -550,11 +555,13 @@ public final int getRootTag() {
 
   @Override
   public final void setRootTag(int rootTag) {
+    assertNotSealed();
     mRootTag = rootTag;
   }
 
   @Override
   public final void setViewClassName(String viewClassName) {
+    assertNotSealed();
     mViewClassName = viewClassName;
   }
 
@@ -596,6 +603,7 @@ public final boolean hasNewLayout() {
 
   @Override
   public final void markLayoutSeen() {
+    assertNotSealed();
     if (mYogaNode != null) {
       mYogaNode.markLayoutSeen();
     }
@@ -607,6 +615,7 @@ public final void markLayoutSeen() {
    */
   @Override
   public final void addNativeChildAt(ReactShadowNodeImpl child, int nativeIndex) {
+    assertNotSealed();
     Assertions.assertCondition(!mIsLayoutOnly);
     Assertions.assertCondition(!child.mIsLayoutOnly);
 
@@ -658,6 +667,7 @@ public final int indexOfNativeChild(ReactShadowNodeImpl nativeChild) {
    */
   @Override
   public final void setIsLayoutOnly(boolean isLayoutOnly) {
+    assertNotSealed();
     Assertions.assertCondition(getParent() == null, "Must remove from no opt parent first");
     Assertions.assertCondition(mNativeParent == null, "Must remove from native parent first");
     Assertions.assertCondition(getNativeChildCount() == 0, "Must remove all native children first");
@@ -806,6 +816,7 @@ public final YogaDirection getLayoutDirection() {
 
   @Override
   public void setLayoutDirection(YogaDirection direction) {
+    assertNotSealed();
     mYogaNode.setDirection(direction);
   }
 
@@ -816,36 +827,43 @@ public final YogaValue getStyleWidth() {
 
   @Override
   public void setStyleWidth(float widthPx) {
+    assertNotSealed();
     mYogaNode.setWidth(widthPx);
   }
 
   @Override
   public void setStyleWidthPercent(float percent) {
+    assertNotSealed();
     mYogaNode.setWidthPercent(percent);
   }
 
   @Override
   public void setStyleWidthAuto() {
+    assertNotSealed();
     mYogaNode.setWidthAuto();
   }
 
   @Override
   public void setStyleMinWidth(float widthPx) {
+    assertNotSealed();
     mYogaNode.setMinWidth(widthPx);
   }
 
   @Override
   public void setStyleMinWidthPercent(float percent) {
+    assertNotSealed();
     mYogaNode.setMinWidthPercent(percent);
   }
 
   @Override
   public void setStyleMaxWidth(float widthPx) {
+    assertNotSealed();
     mYogaNode.setMaxWidth(widthPx);
   }
 
   @Override
   public void setStyleMaxWidthPercent(float percent) {
+    assertNotSealed();
     mYogaNode.setMaxWidthPercent(percent);
   }
 
@@ -856,126 +874,151 @@ public final YogaValue getStyleHeight() {
 
   @Override
   public void setStyleHeight(float heightPx) {
+    assertNotSealed();
     mYogaNode.setHeight(heightPx);
   }
 
   @Override
   public void setStyleHeightPercent(float percent) {
+    assertNotSealed();
     mYogaNode.setHeightPercent(percent);
   }
 
   @Override
   public void setStyleHeightAuto() {
+    assertNotSealed();
     mYogaNode.setHeightAuto();
   }
 
   @Override
   public void setStyleMinHeight(float widthPx) {
+    assertNotSealed();
     mYogaNode.setMinHeight(widthPx);
   }
 
   @Override
   public void setStyleMinHeightPercent(float percent) {
+    assertNotSealed();
     mYogaNode.setMinHeightPercent(percent);
   }
 
   @Override
   public void setStyleMaxHeight(float widthPx) {
+    assertNotSealed();
     mYogaNode.setMaxHeight(widthPx);
   }
 
   @Override
   public void setStyleMaxHeightPercent(float percent) {
+    assertNotSealed();
     mYogaNode.setMaxHeightPercent(percent);
   }
 
   @Override
   public void setFlex(float flex) {
+    assertNotSealed();
     mYogaNode.setFlex(flex);
   }
 
   @Override
   public void setFlexGrow(float flexGrow) {
+    assertNotSealed();
     mYogaNode.setFlexGrow(flexGrow);
   }
 
   @Override
   public void setFlexShrink(float flexShrink) {
+    assertNotSealed();
     mYogaNode.setFlexShrink(flexShrink);
   }
 
   @Override
   public void setFlexBasis(float flexBasis) {
+    assertNotSealed();
     mYogaNode.setFlexBasis(flexBasis);
   }
 
   @Override
   public void setFlexBasisAuto() {
+    assertNotSealed();
     mYogaNode.setFlexBasisAuto();
   }
 
   @Override
   public void setFlexBasisPercent(float percent) {
+    assertNotSealed();
     mYogaNode.setFlexBasisPercent(percent);
   }
 
   @Override
   public void setStyleAspectRatio(float aspectRatio) {
+    assertNotSealed();
     mYogaNode.setAspectRatio(aspectRatio);
   }
 
   @Override
   public void setFlexDirection(YogaFlexDirection flexDirection) {
+    assertNotSealed();
     mYogaNode.setFlexDirection(flexDirection);
   }
 
   @Override
   public void setFlexWrap(YogaWrap wrap) {
+    assertNotSealed();
     mYogaNode.setWrap(wrap);
   }
 
   @Override
   public void setAlignSelf(YogaAlign alignSelf) {
+    assertNotSealed();
     mYogaNode.setAlignSelf(alignSelf);
   }
 
   @Override
   public void setAlignItems(YogaAlign alignItems) {
+    assertNotSealed();
     mYogaNode.setAlignItems(alignItems);
   }
 
   @Override
   public void setAlignContent(YogaAlign alignContent) {
+    assertNotSealed();
     mYogaNode.setAlignContent(alignContent);
   }
 
   @Override
   public void setJustifyContent(YogaJustify justifyContent) {
+    assertNotSealed();
     mYogaNode.setJustifyContent(justifyContent);
   }
 
   @Override
   public void setOverflow(YogaOverflow overflow) {
+    assertNotSealed();
     mYogaNode.setOverflow(overflow);
   }
 
   @Override
   public void setDisplay(YogaDisplay display) {
+    assertNotSealed();
     mYogaNode.setDisplay(display);
   }
 
   @Override
   public void setMargin(int spacingType, float margin) {
+    assertNotSealed();
     mYogaNode.setMargin(YogaEdge.fromInt(spacingType), margin);
   }
 
   @Override
   public void setMarginPercent(int spacingType, float percent) {
+    assertNotSealed();
     mYogaNode.setMarginPercent(YogaEdge.fromInt(spacingType), percent);
   }
 
   @Override
   public void setMarginAuto(int spacingType) {
+    assertNotSealed();
     mYogaNode.setMarginAuto(YogaEdge.fromInt(spacingType));
   }
 
@@ -991,12 +1034,14 @@ public final YogaValue getStylePadding(int spacingType) {
 
   @Override
   public void setDefaultPadding(int spacingType, float padding) {
+    assertNotSealed();
     mDefaultPadding.set(spacingType, padding);
     updatePadding();
   }
 
   @Override
   public void setPadding(int spacingType, float padding) {
+    assertNotSealed();
     mPadding[spacingType] = padding;
     mPaddingIsPercent[spacingType] = false;
     updatePadding();
@@ -1004,12 +1049,14 @@ public void setPadding(int spacingType, float padding) {
 
   @Override
   public void setPaddingPercent(int spacingType, float percent) {
+    assertNotSealed();
     mPadding[spacingType] = percent;
     mPaddingIsPercent[spacingType] = !YogaConstants.isUndefined(percent);
     updatePadding();
   }
 
   private void updatePadding() {
+    assertNotSealed();
     for (int spacingType = Spacing.LEFT; spacingType <= Spacing.ALL; spacingType++) {
       if (spacingType == Spacing.LEFT
           || spacingType == Spacing.RIGHT
@@ -1045,36 +1092,43 @@ private void updatePadding() {
 
   @Override
   public void setBorder(int spacingType, float borderWidth) {
+    assertNotSealed();
     mYogaNode.setBorder(YogaEdge.fromInt(spacingType), borderWidth);
   }
 
   @Override
   public void setPosition(int spacingType, float position) {
+    assertNotSealed();
     mYogaNode.setPosition(YogaEdge.fromInt(spacingType), position);
   }
 
   @Override
   public void setPositionPercent(int spacingType, float percent) {
+    assertNotSealed();
     mYogaNode.setPositionPercent(YogaEdge.fromInt(spacingType), percent);
   }
 
   @Override
   public void setPositionType(YogaPositionType positionType) {
+    assertNotSealed();
     mYogaNode.setPositionType(positionType);
   }
 
   @Override
   public void setShouldNotifyOnLayout(boolean shouldNotifyOnLayout) {
+    assertNotSealed();
     mShouldNotifyOnLayout = shouldNotifyOnLayout;
   }
 
   @Override
   public void setBaselineFunction(YogaBaselineFunction baselineFunction) {
+    assertNotSealed();
     mYogaNode.setBaselineFunction(baselineFunction);
   }
 
   @Override
   public void setMeasureFunction(YogaMeasureFunction measureFunction) {
+    assertNotSealed();
     mYogaNode.setMeasureFunction(measureFunction);
   }
 
@@ -1147,6 +1201,7 @@ public long getInstanceHandle() {
 
   @Override
   public void setInstanceHandle(long instanceHandle) {
+    assertNotSealed();
     mInstanceHandle = instanceHandle;
   }
 
@@ -1159,4 +1214,10 @@ public void markAsSealed() {
   public boolean isSealed() {
     return mIsSealed;
   }
+
+  private void assertNotSealed() {
+    if (mIsSealed) {
+      throw new IllegalStateException("Can not modify sealed node " + toString());
+    }
+  }
 }

From 3ea4a3309fd08c25e47591f1d32b6f02fb44cd3f Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 11:53:44 -0700
Subject: [PATCH 0894/1109] Fabric: Conversion functions between NSString and
 std::string

Summary:
@public
Trivial. It's also nice this we have a default encoding now.

Reviewed By: fkgozali

Differential Revision: D8528919

fbshipit-source-id: 0853eca828f22ead1a337fea3d7a2fc9a48e84c8
---
 .../Mounting/ComponentViews/View/RCTViewComponentView.mm  | 6 +++---
 React/Fabric/Mounting/RCTMountingManager.mm               | 7 +++----
 React/Fabric/RCTConversions.h                             | 8 ++++++++
 React/Fabric/RCTScheduler.mm                              | 2 +-
 4 files changed, 15 insertions(+), 8 deletions(-)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index 763f7a3d81bb..dad8a5f49d7a 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -129,8 +129,8 @@ - (void)updateProps:(SharedProps)props
 
   // `nativeId`
   if (oldViewProps.nativeId != newViewProps.nativeId) {
-    self.nativeId = [NSString stringWithCString:newViewProps.nativeId.c_str()
-                                       encoding:NSASCIIStringEncoding];
+    self.nativeId = RCTNSStringFromString(newViewProps.nativeId);
+  }
   }
 }
 
@@ -165,7 +165,7 @@ - (BOOL)accessibilityPerformMagicTap
 
 - (BOOL)didActivateAccessibilityCustomAction:(UIAccessibilityCustomAction *)action
 {
-  _eventEmitter->onAccessibilityAction([action.name cStringUsingEncoding:NSASCIIStringEncoding]);
+  _eventEmitter->onAccessibilityAction(RCTStringFromNSString(action.name));
   return YES;
 }
 
diff --git a/React/Fabric/Mounting/RCTMountingManager.mm b/React/Fabric/Mounting/RCTMountingManager.mm
index 8df452c0c5b2..5aa0fa501239 100644
--- a/React/Fabric/Mounting/RCTMountingManager.mm
+++ b/React/Fabric/Mounting/RCTMountingManager.mm
@@ -16,6 +16,7 @@
 #import "RCTMountItemProtocol.h"
 
 #import "RCTCreateMountItem.h"
+#import "RCTConversions.h"
 #import "RCTDeleteMountItem.h"
 #import "RCTInsertMountItem.h"
 #import "RCTRemoveMountItem.h"
@@ -46,8 +47,7 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
   for (auto instruction : instructions) {
     switch (instruction.getType()) {
       case TreeMutationInstruction::Creation: {
-        NSString *componentName = [NSString stringWithCString:instruction.getNewChildNode()->getComponentName().c_str()
-                                                     encoding:NSASCIIStringEncoding];
+        NSString *componentName = RCTNSStringFromString(instruction.getNewChildNode()->getComponentName(), NSASCIIStringEncoding);
         RCTCreateMountItem *mountItem =
           [[RCTCreateMountItem alloc] initWithComponentName:componentName
                                                         tag:instruction.getNewChildNode()->getTag()];
@@ -56,8 +56,7 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
       }
 
       case TreeMutationInstruction::Deletion: {
-        NSString *componentName = [NSString stringWithCString:instruction.getOldChildNode()->getComponentName().c_str()
-                                                     encoding:NSASCIIStringEncoding];
+        NSString *componentName = RCTNSStringFromString(instruction.getOldChildNode()->getComponentName(), NSASCIIStringEncoding);
         RCTDeleteMountItem *mountItem =
           [[RCTDeleteMountItem alloc] initWithComponentName:componentName
                                                         tag:instruction.getOldChildNode()->getTag()];
diff --git a/React/Fabric/RCTConversions.h b/React/Fabric/RCTConversions.h
index 2fe12e105076..10cb38fb8994 100644
--- a/React/Fabric/RCTConversions.h
+++ b/React/Fabric/RCTConversions.h
@@ -11,6 +11,14 @@
 #import <fabric/graphics/Geometry.h>
 #import <fabric/view/primitives.h>
 
+inline NSString *_Nullable RCTNSStringFromString(const std::string &string, const NSStringEncoding &encoding = NSUTF8StringEncoding) {
+  return [NSString stringWithCString:string.c_str() encoding:encoding];
+}
+
+inline std::string RCTStringFromNSString(NSString *string, const NSStringEncoding &encoding = NSUTF8StringEncoding) {
+  return [string cStringUsingEncoding:encoding];
+}
+
 inline UIColor *_Nullable RCTUIColorFromSharedColor(const facebook::react::SharedColor &sharedColor) {
   return sharedColor ? [UIColor colorWithCGColor:sharedColor.get()] : nil;
 }
diff --git a/React/Fabric/RCTScheduler.mm b/React/Fabric/RCTScheduler.mm
index 0e1d5313b706..ce1d3b420180 100644
--- a/React/Fabric/RCTScheduler.mm
+++ b/React/Fabric/RCTScheduler.mm
@@ -29,7 +29,7 @@ void schedulerDidComputeMutationInstructions(Tag rootTag, const TreeMutationInst
 
   void schedulerDidRequestPreliminaryViewAllocation(ComponentName componentName) override {
     RCTScheduler *scheduler = (__bridge RCTScheduler *)scheduler_;
-    [scheduler.delegate schedulerDidRequestPreliminaryViewAllocationWithComponentName:[NSString stringWithCString:componentName.c_str() encoding:NSASCIIStringEncoding]];
+    [scheduler.delegate schedulerDidRequestPreliminaryViewAllocationWithComponentName:RCTNSStringFromString(componentName, NSASCIIStringEncoding)];
   }
 
 private:

From ad78971569357b82d06cec1135bb5d21d749f6ed Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 11:53:46 -0700
Subject: [PATCH 0895/1109] Fabric: Added support of
 `accessibilityCustomActions` for <View>

Summary:
@public
Another small but important piece of Accessibility Support.

Reviewed By: mdvacca

Differential Revision: D8528921

fbshipit-source-id: d4ba87bab702d76a90e9ddb751999193243cdc74
---
 .../View/RCTViewComponentView.h               | 10 ++++
 .../View/RCTViewComponentView.mm              | 58 +++++++++++++++++++
 .../view/accessibility/AccessibilityProps.h   |  2 +-
 3 files changed, 69 insertions(+), 1 deletion(-)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index 507c09056fbd..d43973049dc7 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -51,6 +51,16 @@ NS_ASSUME_NONNULL_BEGIN
  */
 @property (nonatomic, strong, nullable) UIColor *foregroundColor;
 
+/**
+ * Returns the object - usually (sub)view - which represents this
+ * component view in terms of accessibility.
+ * All accessibility properties will be applied to this object.
+ * May be overridden in subclass which needs to be accessiblitywise
+ * transparent in favour of some subview.
+ * Defaults to `self`.
+ */
+@property (nonatomic, strong, nullable, readonly) NSObject *accessibilityElement;
+
 /**
  * Insets used when hit testing inside this view.
  */
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index dad8a5f49d7a..52876c87be9a 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -131,6 +131,10 @@ - (void)updateProps:(SharedProps)props
   if (oldViewProps.nativeId != newViewProps.nativeId) {
     self.nativeId = RCTNSStringFromString(newViewProps.nativeId);
   }
+
+  // `accessible`
+  if (oldViewProps.accessible != newViewProps.accessible) {
+    self.accessibilityElement.isAccessibilityElement = newViewProps.accessible;
   }
 }
 
@@ -146,11 +150,65 @@ - (void)updateLayoutMetrics:(LayoutMetrics)layoutMetrics
   _layoutMetrics = layoutMetrics;
 
   [super updateLayoutMetrics:layoutMetrics oldLayoutMetrics:oldLayoutMetrics];
+}
+
+- (void)invalidateBorder
+{
+  const auto &props = *std::dynamic_pointer_cast<const ViewProps>(_props);
+
+  bool useCoreAnimationBorderRendering =
+    props.borderStyle == BorderStyle::Solid &&
+    props.borderWidth.isUniformed() &&
+    props.borderRadius.isUniformed();
+
+  CALayer *layer = self.layer;
+  if (_isCoreAnimationBorderRenderingEnabled != useCoreAnimationBorderRendering) {
+    _isCoreAnimationBorderRenderingEnabled = useCoreAnimationBorderRendering;
+    if (!useCoreAnimationBorderRendering) {
+      layer.borderWidth = 0;
+      layer.borderColor = nil;
+      layer.cornerRadius = 0;
+    }
+  }
+
+  if (useCoreAnimationBorderRendering) {
+    layer.borderWidth = (CGFloat)props.borderWidth.left;
+    layer.borderColor = RCTCGColorRefFromSharedColor(props.borderColor);
+    layer.cornerRadius = (CGFloat)props.borderRadius.topLeft;
+    _contentView.layer.cornerRadius = (CGFloat)props.borderRadius.topLeft;
+    _contentView.layer.masksToBounds = YES;
+  } else {
+    // Not supported yet.
+  }
+}
 
+#pragma mark - Accessibility
+
+- (NSObject *)accessibilityElement
+{
+  return self;
 }
 
 #pragma mark - Accessibility Events
 
+- (NSArray<UIAccessibilityCustomAction *> *)accessibilityCustomActions
+{
+  const auto &accessibilityProps = *std::dynamic_pointer_cast<const AccessibilityProps>(_props);
+
+  if (accessibilityProps.accessibilityActions.size() == 0) {
+    return nil;
+  }
+
+  NSMutableArray<UIAccessibilityCustomAction *> *customActions = [NSMutableArray array];
+  for (const auto &accessibilityAction : accessibilityProps.accessibilityActions) {
+    [customActions addObject:[[UIAccessibilityCustomAction alloc] initWithName:RCTNSStringFromString(accessibilityAction)
+                                                                        target:self
+                                                                      selector:@selector(didActivateAccessibilityCustomAction:)]];
+  }
+
+  return [customActions copy];
+}
+
 - (BOOL)accessibilityActivate
 {
   _eventEmitter->onAccessibilityTap();
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h b/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
index c19881dfb871..931edc8d3009 100644
--- a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
+++ b/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
@@ -30,7 +30,7 @@ class AccessibilityProps:
 #pragma mark - Props
 
   const bool accessible {true};
-  const std::string accessibilityActions {""};
+  const std::vector<std::string> accessibilityActions {};
   const std::string accessibilityLabel {""};
   const AccessibilityTraits accessibilityTraits {AccessibilityTraits::None};
   const bool accessibilityViewIsModal {false};

From 803c14bd980d0bd9c8973d2fbd4534d934f474a4 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 11:53:48 -0700
Subject: [PATCH 0896/1109] Fabric: Support for uniformed borders of <View>

Summary:
@public
For now we only support trivial uniformed (all sides are equal) border rendering (which can be direclty mapped to CALayer features).
Support of the more complex and fancy borders is comming soon.

Reviewed By: mdvacca

Differential Revision: D8528923

fbshipit-source-id: 0883cdc2b855fc63d399e1a93010f259f0628f48
---
 .../View/RCTViewComponentView.mm              | 19 ++++++++++++++++---
 ReactCommon/fabric/graphics/Geometry.h        | 12 ++++++++++++
 2 files changed, 28 insertions(+), 3 deletions(-)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index 52876c87be9a..61ce1ccdc235 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -15,6 +15,10 @@
 using namespace facebook::react;
 
 @implementation RCTViewComponentView
+{
+  BOOL _isCoreAnimationBorderRenderingEnabled;
+}
+
 - (void)setContentView:(UIView *)contentView
 {
   if (_contentView) {
@@ -116,7 +120,6 @@ - (void)updateProps:(SharedProps)props
     self.layer.allowsEdgeAntialiasing = newViewProps.transform != Transform::Identity();
   }
 
-  // TODO: Implement all sutable non-layout <View> props.
   // `hitSlop`
   if (oldViewProps.hitSlop != newViewProps.hitSlop) {
     self.hitTestEdgeInsets = RCTUIEdgeInsetsFromEdgeInsets(newViewProps.hitSlop);
@@ -127,6 +130,16 @@ - (void)updateProps:(SharedProps)props
     self.layer.zPosition = (CGFloat)newViewProps.zIndex;
   }
 
+  // `border`
+  if (
+    oldViewProps.borderWidth != newViewProps.borderWidth ||
+    oldViewProps.borderStyle != newViewProps.borderStyle ||
+    oldViewProps.borderRadius != newViewProps.borderRadius ||
+    oldViewProps.borderColor != newViewProps.borderColor
+  ) {
+    [self invalidateBorder];
+  }
+
   // `nativeId`
   if (oldViewProps.nativeId != newViewProps.nativeId) {
     self.nativeId = RCTNSStringFromString(newViewProps.nativeId);
@@ -158,8 +171,8 @@ - (void)invalidateBorder
 
   bool useCoreAnimationBorderRendering =
     props.borderStyle == BorderStyle::Solid &&
-    props.borderWidth.isUniformed() &&
-    props.borderRadius.isUniformed();
+    props.borderWidth.isUniform() &&
+    props.borderRadius.isUniform();
 
   CALayer *layer = self.layer;
   if (_isCoreAnimationBorderRenderingEnabled != useCoreAnimationBorderRendering) {
diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index e44dba31ea4f..6e97ae851af2 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -123,6 +123,12 @@ struct EdgeInsets {
   bool operator !=(const EdgeInsets& rhs) const {
     return !(*this == rhs);
   }
+
+  bool isUniform() const {
+    return left == top &&
+      left == right &&
+      left == bottom;
+  }
 };
 
 /*
@@ -143,6 +149,12 @@ struct CornerInsets {
   bool operator !=(const CornerInsets& rhs) const {
     return !(*this == rhs);
   }
+
+  bool isUniform() const {
+    return topLeft == topRight &&
+      topLeft == bottomLeft &&
+      topLeft == bottomRight;
+  }
 };
 
 } // namespace react

From 36c052ad966f4e12c4df102523fee5efee09d427 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 11:53:50 -0700
Subject: [PATCH 0897/1109] Fabric: Default support of `displayType` and
 `layoutDirection` layout metrics

Summary:
@public
Quite trivial.

Reviewed By: mdvacca

Differential Revision: D8528922

fbshipit-source-id: 1e21f988317eecc7aa659fd9b51600b9e2b7d69f
---
 .../Mounting/UIView+ComponentViewProtocol.mm  | 27 +++++++++++++------
 .../fabric/core/primitives/Sealable.cpp       |  8 +++---
 ReactCommon/fabric/core/primitives/Sealable.h |  8 +++---
 3 files changed, 27 insertions(+), 16 deletions(-)

diff --git a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
index eeb64581167f..579f4572309a 100644
--- a/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
+++ b/React/Fabric/Mounting/UIView+ComponentViewProtocol.mm
@@ -10,6 +10,8 @@
 #import <React/RCTAssert.h>
 #import "RCTConversions.h"
 
+using namespace facebook::react;
+
 @implementation UIView (ComponentViewProtocol)
 
 - (void)mountChildComponentView:(UIView<RCTComponentViewProtocol> *)childComponentView
@@ -25,31 +27,40 @@ - (void)unmountChildComponentView:(UIView<RCTComponentViewProtocol> *)childCompo
   [childComponentView removeFromSuperview];
 }
 
-- (void)updateProps:(facebook::react::SharedProps)props
-           oldProps:(facebook::react::SharedProps)oldProps
+- (void)updateProps:(SharedProps)props
+           oldProps:(SharedProps)oldProps
 {
   // Default implementation does nothing.
 }
 
-- (void)updateEventEmitter:(facebook::react::SharedEventEmitter)eventEmitter
+- (void)updateEventEmitter:(SharedEventEmitter)eventEmitter
 {
   // Default implementation does nothing.
 }
 
-- (void)updateLocalData:(facebook::react::SharedLocalData)localData
-           oldLocalData:(facebook::react::SharedLocalData)oldLocalData
+- (void)updateLocalData:(SharedLocalData)localData
+           oldLocalData:(SharedLocalData)oldLocalData
 {
   // Default implementation does nothing.
 }
 
-- (void)updateLayoutMetrics:(facebook::react::LayoutMetrics)layoutMetrics
-           oldLayoutMetrics:(facebook::react::LayoutMetrics)oldLayoutMetrics
+- (void)updateLayoutMetrics:(LayoutMetrics)layoutMetrics
+           oldLayoutMetrics:(LayoutMetrics)oldLayoutMetrics
 {
   if (layoutMetrics.frame != oldLayoutMetrics.frame) {
     self.frame = RCTCGRectFromRect(layoutMetrics.frame);
   }
 
-  // TODO: Apply another layout metrics here.
+  if (layoutMetrics.layoutDirection != oldLayoutMetrics.layoutDirection) {
+    self.semanticContentAttribute =
+      layoutMetrics.layoutDirection == LayoutDirection::RightToLeft ?
+        UISemanticContentAttributeForceRightToLeft :
+        UISemanticContentAttributeForceLeftToRight;
+  }
+
+  if (layoutMetrics.displayType != oldLayoutMetrics.displayType) {
+    self.hidden = layoutMetrics.displayType == DisplayType::None;
+  }
 }
 
 - (void)prepareForRecycle
diff --git a/ReactCommon/fabric/core/primitives/Sealable.cpp b/ReactCommon/fabric/core/primitives/Sealable.cpp
index a93f640db531..a44181ee125b 100644
--- a/ReactCommon/fabric/core/primitives/Sealable.cpp
+++ b/ReactCommon/fabric/core/primitives/Sealable.cpp
@@ -26,18 +26,18 @@ namespace react {
 
 Sealable::Sealable(): sealed_(false) {}
 
-Sealable::Sealable(const Sealable& other): sealed_(false) {};
+Sealable::Sealable(const Sealable &other): sealed_(false) {};
 
-Sealable::Sealable(Sealable&& other) noexcept: sealed_(false) {};
+Sealable::Sealable(Sealable &&other) noexcept: sealed_(false) {};
 
 Sealable::~Sealable() noexcept {};
 
-Sealable& Sealable::operator= (const Sealable& other) {
+Sealable &Sealable::operator=(const Sealable &other) {
   ensureUnsealed();
   return *this;
 }
 
-Sealable& Sealable::operator= (Sealable&& other) noexcept {
+Sealable &Sealable::operator=(Sealable &&other) noexcept {
   ensureUnsealed();
   return *this;
 };
diff --git a/ReactCommon/fabric/core/primitives/Sealable.h b/ReactCommon/fabric/core/primitives/Sealable.h
index 7f07819a1ff7..8cc3c6ed946d 100644
--- a/ReactCommon/fabric/core/primitives/Sealable.h
+++ b/ReactCommon/fabric/core/primitives/Sealable.h
@@ -43,11 +43,11 @@ namespace react {
 class Sealable {
 public:
   Sealable();
-  Sealable(const Sealable& other);
-  Sealable(Sealable&& other) noexcept;
+  Sealable(const Sealable &other);
+  Sealable(Sealable &&other) noexcept;
   ~Sealable() noexcept;
-  Sealable& operator=(const Sealable& other);
-  Sealable& operator=(Sealable&& other) noexcept;
+  Sealable &operator=(const Sealable &other);
+  Sealable &operator=(Sealable &&other) noexcept;
 
   /*
    * Seals the object. This operation is irreversible;

From af75d93dad16300741c76aaa36e8787a6939c7e3 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 11:53:53 -0700
Subject: [PATCH 0898/1109] Fabric: Bunch of unimplemented yet component was
 aliased to <View>

Summary:
@public
We need this temporary for testing until we support them all.

Reviewed By: mdvacca

Differential Revision: D8552361

fbshipit-source-id: 25f48cebcf5a665a24b92803dd7738f947ca74b2
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 9 +++++++--
 1 file changed, 7 insertions(+), 2 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 8f71c6418786..22aee62d6de5 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -65,9 +65,14 @@ static const std::string componentNameByReactViewName(std::string viewName) {
   }
 
   // We need this temporarly for testing purposes until we have proper
-  // implementation of core components: <Image>, <ScrollContentView>.
+  // implementation of core components: <ReactPerformanceLoggerFlag>,
+  // <SafeAreaView>, and etc.
   if (
-    viewName == "ImageView" ||
+    viewName == "ReactPerformanceLoggerFlag" ||
+    viewName == "SinglelineTextInputView" ||
+    viewName == "MultilineTextInputView" ||
+    viewName == "RefreshControl" ||
+    viewName == "SafeAreaView" ||
     viewName == "ScrollContentView"
   ) {
     return "View";

From 48b9a6f887c09f78944053a6658106a01dc20fea Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 11:53:55 -0700
Subject: [PATCH 0899/1109] Fabric: Temporary experimental integration between
 old and new UIManagers

Summary:
@public
We need this to enable measuring, responder-chain management and another features powered by UIManager commands.
As soon we have Fabric specifc command-delivery pipeline this must be reverted.

Reviewed By: fkgozali

Differential Revision: D8552360

fbshipit-source-id: d56e12d38c32d8ad98cb230671bac1f35e87e647
---
 .../Mounting/RCTComponentViewRegistry.mm      | 64 +++++++++++++++++++
 1 file changed, 64 insertions(+)

diff --git a/React/Fabric/Mounting/RCTComponentViewRegistry.mm b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
index 83b0afb85a9d..635a8e1dc923 100644
--- a/React/Fabric/Mounting/RCTComponentViewRegistry.mm
+++ b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
@@ -10,6 +10,60 @@
 #import <Foundation/NSMapTable.h>
 #import <React/RCTAssert.h>
 
+#define LEGACY_UIMANAGER_INTEGRATION_ENABLED 1
+
+#ifdef LEGACY_UIMANAGER_INTEGRATION_ENABLED
+
+#import <React/RCTUIManager.h>
+#import <React/RCTBridge+Private.h>
+
+/**
+ * Warning: This is a total hack and temporary solution.
+ * Unless we have a pure Fabric-based implementation of UIManager commands
+ * delivery pipeline, we have to leverage existing infra. This code tricks
+ * legacy UIManager by registering all Fabric-managed views in it,
+ * hence existing command-delivery infra can reach "foreign" views using
+ * the old pipeline.
+ */
+@interface RCTUIManager ()
+- (NSMutableDictionary<NSNumber *, UIView *> *)viewRegistry;
+@end
+
+@interface RCTUIManager (Hack)
+
++ (void)registerView:(UIView *)view;
++ (void)unregisterView:(UIView *)view;
+
+@end
+
+@implementation RCTUIManager (Hack)
+
++ (void)registerView:(UIView *)view
+{
+  if (!view) {
+    return;
+  }
+
+  RCTUIManager *uiManager = [[RCTBridge currentBridge] uiManager];
+  view.reactTag = @(view.tag);
+  [uiManager.viewRegistry setObject:view forKey:@(view.tag)];
+}
+
++ (void)unregisterView:(UIView *)view
+{
+  if (!view) {
+    return;
+  }
+
+  RCTUIManager *uiManager = [[RCTBridge currentBridge] uiManager];
+  view.reactTag = nil;
+  [uiManager.viewRegistry removeObjectForKey:@(view.tag)];
+}
+
+@end
+
+#endif
+
 const NSInteger RCTComponentViewRegistryRecyclePoolMaxSize = 256;
 
 @implementation RCTComponentViewRegistry {
@@ -37,6 +91,11 @@ - (instancetype)init
     [self _dequeueComponentViewWithName:componentName];
   componentView.tag = tag;
   [_registry setObject:componentView forKey:(__bridge id)(void *)tag];
+
+#ifdef LEGACY_UIMANAGER_INTEGRATION_ENABLED
+  [RCTUIManager registerView:componentView];
+#endif
+
   return componentView;
 }
 
@@ -45,6 +104,11 @@ - (void)enqueueComponentViewWithName:(NSString *)componentName
                        componentView:(UIView<RCTComponentViewProtocol> *)componentView
 {
   RCTAssertMainQueue();
+
+#ifdef LEGACY_UIMANAGER_INTEGRATION_ENABLED
+  [RCTUIManager unregisterView:componentView];
+#endif
+
   [_registry removeObjectForKey:(__bridge id)(void *)tag];
   componentView.tag = 0;
   [self _enqueueComponentViewWithName:componentName componentView:componentView];

From 483c45cff06e16d166ded634a257cceaddcf5024 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 11:54:01 -0700
Subject: [PATCH 0900/1109] Fabric: Shadow node shallowing was removed from
 preventive cloning in UIManager

Summary:
@public
We do preventing cloning in UIManager especially to add a layer to Shadow Node source chain,
so apparently there is no point illuminate that by calling `shallowSourceNode`.

Reviewed By: fkgozali

Differential Revision: D8585163

fbshipit-source-id: 3743edc30bf2183c420fd79ce1e59d68ceaa278b
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 1 -
 1 file changed, 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 22aee62d6de5..caf2713ac7a5 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -234,7 +234,6 @@ void FabricUIManager::appendChild(const SharedShadowNode &parentShadowNode, cons
     auto childComponentDescriptor = (*componentDescriptorRegistry_)[childShadowNode];
     auto clonedChildShadowNode = childComponentDescriptor->cloneShadowNode(childShadowNode);
     auto nonConstClonedChildShadowNode = std::const_pointer_cast<ShadowNode>(clonedChildShadowNode);
-    nonConstClonedChildShadowNode->shallowSourceNode();
     componentDescriptor->appendChild(parentShadowNode, clonedChildShadowNode);
     return;
   }

From b1c4fee6af956e03b2a199dbf32f90414e14c22c Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 11:54:03 -0700
Subject: [PATCH 0901/1109] Fabric: Consistency assurance asserts in
 RCTComponentViewRegistry

Summary:
@public
We have found that because of some bugs Mounting Manager can request creation of views with same tag several times (which should not happen).
Now, we can fail earlier in such cases.

Reviewed By: fkgozali

Differential Revision: D8585164

fbshipit-source-id: 63c6391de5adfe711552918a20a18396f54ec201
---
 React/Fabric/Mounting/RCTComponentViewRegistry.mm | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/React/Fabric/Mounting/RCTComponentViewRegistry.mm b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
index 635a8e1dc923..81816f1ea30b 100644
--- a/React/Fabric/Mounting/RCTComponentViewRegistry.mm
+++ b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
@@ -87,6 +87,10 @@ - (instancetype)init
                                                                tag:(ReactTag)tag
 {
   RCTAssertMainQueue();
+
+  RCTAssert(![_registry objectForKey:(__bridge id)(void *)tag],
+    @"RCTComponentViewRegistry: Attempt to dequeue already registered component.");
+
   UIView<RCTComponentViewProtocol> *componentView =
     [self _dequeueComponentViewWithName:componentName];
   componentView.tag = tag;
@@ -105,6 +109,9 @@ - (void)enqueueComponentViewWithName:(NSString *)componentName
 {
   RCTAssertMainQueue();
 
+  RCTAssert([_registry objectForKey:(__bridge id)(void *)tag],
+    @"RCTComponentViewRegistry: Attempt to enqueue unregistered component.");
+
 #ifdef LEGACY_UIMANAGER_INTEGRATION_ENABLED
   [RCTUIManager unregisterView:componentView];
 #endif

From 250cc3c594551f1e8661e9afc9d8521b07b08ba4 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 15:33:30 -0700
Subject: [PATCH 0902/1109] Fabric: Fixed order of instructions in
 Differentiator

Summary:
@public
Previously Differentiator might generate some `remove` instruction that refers to already `deleted` node. That diffs fixes that.

Reviewed By: fkgozali

Differential Revision: D8596536

fbshipit-source-id: 88117962f93e52167dbcb6525f2cc36758a367e7
---
 ReactCommon/fabric/uimanager/Differentiator.cpp | 13 +++++++------
 1 file changed, 7 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/Differentiator.cpp b/ReactCommon/fabric/uimanager/Differentiator.cpp
index b180587eed88..6e27fa753527 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.cpp
+++ b/ReactCommon/fabric/uimanager/Differentiator.cpp
@@ -39,6 +39,7 @@ static void calculateMutationInstructions(
   TreeMutationInstructionList removeInstructions = {};
   TreeMutationInstructionList replaceInstructions = {};
   TreeMutationInstructionList downwardInstructions = {};
+  TreeMutationInstructionList destructionDownwardInstructions = {};
 
   // Stage 1: Collectings Updates
   for (index = 0; index < oldChildNodes->size() && index < newChildNodes->size(); index++) {
@@ -62,7 +63,7 @@ static void calculateMutationInstructions(
     }
 
     calculateMutationInstructions(
-      downwardInstructions,
+      *(newChildNode->getChildren()->size() ? &downwardInstructions : &destructionDownwardInstructions),
       oldChildNode,
       oldChildNode->getChildren(),
       newChildNode->getChildren()
@@ -90,7 +91,7 @@ static void calculateMutationInstructions(
       newChildSourceNode ? newChildSourceNode->getChildren() : ShadowNode::emptySharedShadowNodeSharedList();
 
     calculateMutationInstructions(
-      downwardInstructions,
+      *(newChildNode->getChildren()->size() ? &downwardInstructions : &destructionDownwardInstructions),
       newChildNode,
       newChildSourceChildNodes,
       newChildNode->getChildren()
@@ -125,7 +126,7 @@ static void calculateMutationInstructions(
       );
 
       calculateMutationInstructions(
-        downwardInstructions,
+        destructionDownwardInstructions,
         oldChildNode,
         oldChildNode->getChildren(),
         ShadowNode::emptySharedShadowNodeSharedList()
@@ -149,15 +150,15 @@ static void calculateMutationInstructions(
   }
 
   // All instructions in an optimal order:
+  instructions.insert(instructions.end(), destructionDownwardInstructions.begin(), destructionDownwardInstructions.end());
   instructions.insert(instructions.end(), replaceInstructions.begin(), replaceInstructions.end());
   instructions.insert(instructions.end(), removeInstructions.begin(), removeInstructions.end());
-  instructions.insert(instructions.end(), deleteInstructions.begin(), deleteInstructions.end());
   instructions.insert(instructions.end(), createInstructions.begin(), createInstructions.end());
-  instructions.insert(instructions.end(), insertInstructions.begin(), insertInstructions.end());
   instructions.insert(instructions.end(), downwardInstructions.begin(), downwardInstructions.end());
+  instructions.insert(instructions.end(), insertInstructions.begin(), insertInstructions.end());
+  instructions.insert(instructions.end(), deleteInstructions.begin(), deleteInstructions.end());
 }
 
-
 void calculateMutationInstructions(
   TreeMutationInstructionList &instructions,
   SharedShadowNode oldRootShadowNode,

From 6942408a474af80560497193f73c9e60bf272263 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 22 Jun 2018 18:31:42 -0700
Subject: [PATCH 0903/1109] Fabric: Dispatching `onLayout` events to only nodes
 which requested it

Summary:
@public
The current Fabric architecture, in general, does not support "subscribing" for events, so all kinds of events are always delivered no matter have JavaScript components `on`-handlers for them or not.
At this point, we are not sure should it be this way or not. But we are sure that for some extremely noisy events (like onLayout) we have to make an exception right now (otherwise overall performance will suffer).
So, this diff implements that for `onLayout`.

Reviewed By: fkgozali

Differential Revision: D8597408

fbshipit-source-id: 6933b7cb96e24f0660bd7850b625ff27e3146a2b
---
 ReactCommon/fabric/uimanager/ShadowTree.cpp | 7 +++++++
 ReactCommon/fabric/view/ViewProps.cpp       | 3 ++-
 ReactCommon/fabric/view/ViewProps.h         | 1 +
 3 files changed, 10 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 55e9b5038628..5dd54ecfa933 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -115,6 +115,13 @@ void ShadowTree::emitLayoutEvents(const TreeMutationInstructionList &instruction
       if (viewEventEmitter) {
         // Now we know that both (old and new) shadow nodes must be `LayoutableShadowNode` subclasses.
         assert(std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode));
+
+        // Checking if the `onLayout` event was requested for the particular Shadow Node.
+        const auto &viewProps = std::dynamic_pointer_cast<const ViewProps>(newShadowNode->getProps());
+        if (viewProps && !viewProps->onLayout) {
+          continue;
+        }
+
         // TODO(T29661055): Consider using `std::reinterpret_pointer_cast`.
         const auto &newLayoutableShadowNode =
           std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode);
diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index bdccfedc4cd9..73cc4702f0b1 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -37,7 +37,8 @@ ViewProps::ViewProps(const ViewProps &sourceProps, const RawProps &rawProps):
   shouldRasterize(convertRawProp(rawProps, "shouldRasterize", sourceProps.shouldRasterize)),
   zIndex(convertRawProp(rawProps, "zIndex", sourceProps.zIndex)),
   pointerEvents(convertRawProp(rawProps, "pointerEvents", sourceProps.pointerEvents)),
-  hitSlop(convertRawProp(rawProps, "hitSlop", sourceProps.hitSlop)) {};
+  hitSlop(convertRawProp(rawProps, "hitSlop", sourceProps.hitSlop)),
+  onLayout(convertRawProp(rawProps, "onLayout", sourceProps.onLayout)) {};
 
 #pragma mark - DebugStringConvertible
 
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
index 5806f1eb320f..2a15323e2fbe 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -60,6 +60,7 @@ class ViewProps:
   // Events
   const PointerEventsMode pointerEvents {};
   const EdgeInsets hitSlop {};
+  const bool onLayout {false};
 
 #pragma mark - DebugStringConvertible
 

From 0b2cee59d21231c10ca6f16570c23a18f9c16b05 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Sat, 23 Jun 2018 13:28:33 -0700
Subject: [PATCH 0904/1109] Update screen-layout props during diffing

Summary: This diff optimizes the delivery of onLayout event and re-lauout of views when ReactShadow nodes are updated. This only affects Fabric rendering.

Reviewed By: shergin

Differential Revision: D8601659

fbshipit-source-id: 3e33521e53170320ea952003fada5297a7605934
---
 .../react/fabric/FabricReconciler.java        | 24 +++++++++++--------
 .../react/uimanager/ReactShadowNode.java      |  1 +
 .../react/uimanager/ReactShadowNodeImpl.java  |  8 +++++++
 3 files changed, 23 insertions(+), 10 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index 41784624288d..e01e0c9d6831 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -73,7 +73,7 @@ private void manageChildren(
       if (prevNode.getReactTag() != newNode.getReactTag()) {
         break;
       }
-      enqueueUpdateProperties(newNode);
+      enqueueUpdateProperties(newNode, prevNode);
       manageChildren(prevNode, prevNode.getChildrenList(), newNode.getChildrenList());
       newNode.setOriginalReactShadowNode(null);
     }
@@ -88,7 +88,7 @@ private void manageChildren(
     for (int k = firstRemovedOrAddedViewIndex; k < newList.size(); k++) {
       ReactShadowNode newNode = newList.get(k);
       if (newNode.isVirtual()) continue;
-      enqueueUpdateProperties(newNode);
+      enqueueUpdateProperties(newNode, null);
       viewsToAdd.add(new ViewAtIndex(newNode.getReactTag(), k));
       List previousChildrenList = newNode.getOriginalReactShadowNode() == null ? null : newNode.getOriginalReactShadowNode().getChildrenList();
       manageChildren(newNode, previousChildrenList, newNode.getChildrenList());
@@ -131,24 +131,28 @@ private void manageChildren(
     }
   }
 
-  private void enqueueUpdateProperties(ReactShadowNode node) {
-    int reactTag = node.getReactTag();
+  private void enqueueUpdateProperties(ReactShadowNode newNode, ReactShadowNode prevNode) {
+    int reactTag = newNode.getReactTag();
     if (DEBUG) {
       FLog.d(
         TAG,
         "manageChildren.enqueueUpdateProperties " +
           "\n\ttag: " + reactTag +
-          "\n\tviewClass: " + node.getViewClass() +
-          "\n\tinstanceHandle: " + node.getInstanceHandle() +
-          "\n\tnewProps: " + node.getNewProps());
+          "\n\tviewClass: " + newNode.getViewClass() +
+          "\n\tinstanceHandle: " + newNode.getInstanceHandle() +
+          "\n\tnewProps: " + newNode.getNewProps());
     }
 
-    if (node.getNewProps() != null) {
+    if (prevNode != null) {
+      newNode.updateScreenLayout(prevNode);
+    }
+
+    if (newNode.getNewProps() != null) {
       uiViewOperationQueue.enqueueUpdateProperties(
-        reactTag, node.getViewClass(), node.getNewProps());
+        reactTag, newNode.getViewClass(), newNode.getNewProps());
     }
 
     uiViewOperationQueue.enqueueUpdateInstanceHandle(
-      reactTag, node.getInstanceHandle());
+      reactTag, newNode.getInstanceHandle());
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
index 3f78d8af5e3f..ac5780df2ec9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNode.java
@@ -389,4 +389,5 @@ public interface ReactShadowNode<T extends ReactShadowNode> {
    */
   boolean isSealed();
 
+  void updateScreenLayout(ReactShadowNode prevNode);
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index d6075b7dbf76..ed988f1cc556 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -1220,4 +1220,12 @@ private void assertNotSealed() {
       throw new IllegalStateException("Can not modify sealed node " + toString());
     }
   }
+
+  public void updateScreenLayout(ReactShadowNode prevNode) {
+    assertNotSealed();
+    mScreenHeight = prevNode.getScreenHeight();
+    mScreenWidth = prevNode.getScreenWidth();
+    mScreenX = prevNode.getScreenX();
+    mScreenY = prevNode.getScreenY();
+  }
 }

From 346ac75ed6c4026cc779e9082c1a87b4570ef273 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Sat, 23 Jun 2018 18:23:21 -0700
Subject: [PATCH 0905/1109] Fix deprecated glob usage.

Summary: https://our.intern.facebook.com/intern/wiki/Buck/python-to-skylark/

Differential Revision: D8595731

fbshipit-source-id: 0e3046a7fd2a25e9b13462713ae9a008ad546770
---
 ReactAndroid/src/main/java/com/facebook/react/common/BUCK | 2 +-
 ReactAndroid/src/main/jni/first-party/fb/BUCK             | 1 +
 ReactCommon/cxxreact/BUCK                                 | 5 +++--
 ReactCommon/fabric/activityindicator/BUCK                 | 1 +
 ReactCommon/fabric/attributedstring/BUCK                  | 5 +++--
 ReactCommon/fabric/components/image/BUCK                  | 1 +
 ReactCommon/fabric/components/switch/BUCK                 | 1 +
 ReactCommon/fabric/core/BUCK                              | 5 +++--
 ReactCommon/fabric/debug/BUCK                             | 5 +++--
 ReactCommon/fabric/graphics/BUCK                          | 5 +++--
 ReactCommon/fabric/imagemanager/BUCK                      | 1 +
 ReactCommon/fabric/scrollview/BUCK                        | 5 +++--
 ReactCommon/fabric/text/BUCK                              | 5 +++--
 ReactCommon/fabric/textlayoutmanager/BUCK                 | 5 +++--
 ReactCommon/fabric/uimanager/BUCK                         | 5 +++--
 ReactCommon/fabric/view/BUCK                              | 5 +++--
 ReactCommon/jsinspector/BUCK                              | 3 ++-
 ReactCommon/privatedata/BUCK                              | 1 +
 18 files changed, 39 insertions(+), 22 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/common/BUCK b/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
index 3cdee118da4f..829e1069830b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/common/BUCK
@@ -8,7 +8,7 @@ rn_android_library(
     name = "common",
     srcs = glob(
         ["**/*.java"],
-        excludes = SUB_PROJECTS,
+        exclude = SUB_PROJECTS,
     ),
     provided_deps = [
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
diff --git a/ReactAndroid/src/main/jni/first-party/fb/BUCK b/ReactAndroid/src/main/jni/first-party/fb/BUCK
index a63df0b4b2e5..f5f74a41c1cf 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/BUCK
+++ b/ReactAndroid/src/main/jni/first-party/fb/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "JNI_TARGET", "cxx_library")
 
 # This target is only used in open source
diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 12bd664f293a..06bf8adbdaf4 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//ReactNative:DEFS.bzl", "ANDROID", "ANDROID_JSC_DEPS", "APPLE", "APPLE_JSC_DEPS", "IS_OSS_BUILD", "get_android_inspector_flags", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 CXX_LIBRARY_COMPILER_FLAGS = [
@@ -113,14 +114,14 @@ rn_xplat_cxx_library(
     name = "bridge",
     srcs = glob(
         ["*.cpp"],
-        excludes = [
+        exclude = [
             "JSBigString.cpp",
             "SampleCxxModule.cpp",
         ],
     ),
     headers = glob(
         ["*.h"],
-        excludes = CXXREACT_PUBLIC_HEADERS,
+        exclude = CXXREACT_PUBLIC_HEADERS,
     ),
     header_namespace = "",
     exported_headers = dict([
diff --git a/ReactCommon/fabric/activityindicator/BUCK b/ReactCommon/fabric/activityindicator/BUCK
index 708c5fe41eb5..952cb7977ff0 100644
--- a/ReactCommon/fabric/activityindicator/BUCK
+++ b/ReactCommon/fabric/activityindicator/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
diff --git a/ReactCommon/fabric/attributedstring/BUCK b/ReactCommon/fabric/attributedstring/BUCK
index 8f2c481cb177..61b897ba9d31 100644
--- a/ReactCommon/fabric/attributedstring/BUCK
+++ b/ReactCommon/fabric/attributedstring/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -12,11 +13,11 @@ rn_xplat_cxx_library(
     name = "attributedstring",
     srcs = glob(
         ["**/*.cpp"],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/fabric/components/image/BUCK b/ReactCommon/fabric/components/image/BUCK
index 5cc0aed42715..fccf34aeb43d 100644
--- a/ReactCommon/fabric/components/image/BUCK
+++ b/ReactCommon/fabric/components/image/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
diff --git a/ReactCommon/fabric/components/switch/BUCK b/ReactCommon/fabric/components/switch/BUCK
index 8a4a27ff3253..b2a4f8c1d691 100644
--- a/ReactCommon/fabric/components/switch/BUCK
+++ b/ReactCommon/fabric/components/switch/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index a444f0726802..f663ff3590ed 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -12,11 +13,11 @@ rn_xplat_cxx_library(
     name = "core",
     srcs = glob(
         ["**/*.cpp"],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index 8bdc3602d502..c16bedf03817 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -12,11 +13,11 @@ rn_xplat_cxx_library(
     name = "debug",
     srcs = glob(
         ["**/*.cpp"],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index ed4891382ef2..e0b337da1cd7 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -12,11 +13,11 @@ rn_xplat_cxx_library(
     name = "graphics",
     srcs = glob(
         ["**/*.cpp"],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/fabric/imagemanager/BUCK b/ReactCommon/fabric/imagemanager/BUCK
index 0b83274c9a24..a42904ea45fb 100644
--- a/ReactCommon/fabric/imagemanager/BUCK
+++ b/ReactCommon/fabric/imagemanager/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
diff --git a/ReactCommon/fabric/scrollview/BUCK b/ReactCommon/fabric/scrollview/BUCK
index ed66b72142d1..1f20c65532f1 100644
--- a/ReactCommon/fabric/scrollview/BUCK
+++ b/ReactCommon/fabric/scrollview/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -12,11 +13,11 @@ rn_xplat_cxx_library(
     name = "scrollview",
     srcs = glob(
         ["**/*.cpp"],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/fabric/text/BUCK b/ReactCommon/fabric/text/BUCK
index b6450f454450..e8dc5e5971c5 100644
--- a/ReactCommon/fabric/text/BUCK
+++ b/ReactCommon/fabric/text/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -12,11 +13,11 @@ rn_xplat_cxx_library(
     name = "text",
     srcs = glob(
         ["**/*.cpp"],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/fabric/textlayoutmanager/BUCK b/ReactCommon/fabric/textlayoutmanager/BUCK
index 26f57ef0e908..0095affa737f 100644
--- a/ReactCommon/fabric/textlayoutmanager/BUCK
+++ b/ReactCommon/fabric/textlayoutmanager/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -15,11 +16,11 @@ rn_xplat_cxx_library(
             "**/*.cpp",
             "**/*.mm",
         ],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 2bd48978112f..1b091a56325f 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -12,11 +13,11 @@ rn_xplat_cxx_library(
     name = "uimanager",
     srcs = glob(
         ["**/*.cpp"],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index a641805444c7..42ea4a7a5d07 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
 load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
@@ -12,11 +13,11 @@ rn_xplat_cxx_library(
     name = "view",
     srcs = glob(
         ["**/*.cpp"],
-        excludes = glob(["tests/**/*.cpp"]),
+        exclude = glob(["tests/**/*.cpp"]),
     ),
     headers = glob(
         ["**/*.h"],
-        excludes = glob(["tests/**/*.h"]),
+        exclude = glob(["tests/**/*.h"]),
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
diff --git a/ReactCommon/jsinspector/BUCK b/ReactCommon/jsinspector/BUCK
index f50840b71dd8..ceb0293f71eb 100644
--- a/ReactCommon/jsinspector/BUCK
+++ b/ReactCommon/jsinspector/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library")
 
 EXPORTED_HEADERS = [
@@ -13,7 +14,7 @@ rn_xplat_cxx_library(
         [
             ("", "*.h"),
         ],
-        excludes = EXPORTED_HEADERS,
+        exclude = EXPORTED_HEADERS,
         prefix = "jsinspector",
     ),
     header_namespace = "",
diff --git a/ReactCommon/privatedata/BUCK b/ReactCommon/privatedata/BUCK
index 79983f49d07d..abd0de4d498e 100644
--- a/ReactCommon/privatedata/BUCK
+++ b/ReactCommon/privatedata/BUCK
@@ -1,3 +1,4 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//ReactNative:DEFS.bzl", "rn_xplat_cxx_library")
 
 rn_xplat_cxx_library(

From 802a371c9254aee87567eacb697c942e7c0f65d2 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sat, 23 Jun 2018 19:10:08 -0700
Subject: [PATCH 0906/1109] Fabric: Fixed missed default value in parsing
 constructor of ViewProps

Summary:
@public
It fixes a problem when some Views got disaper after they have non-zero opacity.

Reviewed By: mdvacca

Differential Revision: D8601600

fbshipit-source-id: 3da3ee591d4a685a8d7a56b15519d4d5cae4a031
---
 ReactCommon/fabric/view/ViewProps.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/view/ViewProps.cpp
index 73cc4702f0b1..36d33216098b 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/view/ViewProps.cpp
@@ -21,7 +21,7 @@ ViewProps::ViewProps(const YGStyle &yogaStyle):
 ViewProps::ViewProps(const ViewProps &sourceProps, const RawProps &rawProps):
   Props(sourceProps, rawProps),
   YogaStylableProps(sourceProps, rawProps),
-  opacity(convertRawProp(rawProps, "opacity", sourceProps.opacity)),
+  opacity(convertRawProp(rawProps, "opacity", sourceProps.opacity, (Float)1.0)),
   foregroundColor(convertRawProp(rawProps, "foregroundColor", sourceProps.foregroundColor)),
   backgroundColor(convertRawProp(rawProps, "backgroundColor", sourceProps.backgroundColor)),
   borderWidth(convertRawProp(rawProps, "borderWidth", sourceProps.borderWidth)),

From 0644785ad3d467478aaf94d45429d7d17fddd679 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Sat, 23 Jun 2018 19:59:32 -0700
Subject: [PATCH 0907/1109] Fix deprecated glob attribute usage.

Summary: https://our.intern.facebook.com/intern/wiki/Buck/python-to-skylark/

Differential Revision: D8601889

fbshipit-source-id: f95ed015c7fe0d15cca826829ff30d0e6372eafa
---
 ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK | 2 +-
 ReactAndroid/src/main/jni/react/jni/BUCK                     | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
index 99dbb6328f36..1090e3ce6b0c 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BUCK
@@ -9,7 +9,7 @@ rn_android_library(
             "events/*.java",
             "layoutanimation/*.java",
         ],
-        excludes = ["DisplayMetricsHolder.java"],
+        exclude = ["DisplayMetricsHolder.java"],
     ),
     provided_deps = [
         react_native_dep("third-party/android/support/v4:lib-support-v4"),
diff --git a/ReactAndroid/src/main/jni/react/jni/BUCK b/ReactAndroid/src/main/jni/react/jni/BUCK
index 905cc22462db..affc4b4e3c8e 100644
--- a/ReactAndroid/src/main/jni/react/jni/BUCK
+++ b/ReactAndroid/src/main/jni/react/jni/BUCK
@@ -26,7 +26,7 @@ rn_xplat_cxx_library(
     srcs = glob(["*.cpp"]),
     headers = glob(
         ["*.h"],
-        excludes = EXPORTED_HEADERS,
+        exclude = EXPORTED_HEADERS,
     ),
     header_namespace = "react/jni",
     exported_headers = EXPORTED_HEADERS,

From 22d068a108919bc6345b2d98b3db1f0f85a2ce7f Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Sun, 24 Jun 2018 10:35:20 -0700
Subject: [PATCH 0908/1109] Revert D8549084: Added Accessibility Feature for RN
 to support Smart Inversion for photos

Differential Revision:
D8549084

Original commit changeset: 82a3bc73c9e6

fbshipit-source-id: 8dca4efe701058710187828d64a055278ff585ab
---
 Libraries/Components/View/ViewPropTypes.js | 1 -
 React/Views/RCTViewManager.m               | 1 -
 2 files changed, 2 deletions(-)

diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 5cfcd45f24b9..0f7dea210694 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -87,7 +87,6 @@ export type ViewProps = $ReadOnly<{|
   accessibilityComponentType?: AccessibilityComponentType,
   accessibilityLiveRegion?: 'none' | 'polite' | 'assertive',
   importantForAccessibility?: 'auto' | 'yes' | 'no' | 'no-hide-descendants',
-  accessibilityIgnoresInvertColors?: boolean,
   accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
   accessibilityViewIsModal?: boolean,
   accessibilityElementsHidden?: boolean,
diff --git a/React/Views/RCTViewManager.m b/React/Views/RCTViewManager.m
index db12c77d39b5..626e923d35e5 100644
--- a/React/Views/RCTViewManager.m
+++ b/React/Views/RCTViewManager.m
@@ -104,7 +104,6 @@ - (RCTShadowView *)shadowView
 #endif
 
 RCT_EXPORT_VIEW_PROPERTY(nativeID, NSString)
-RCT_EXPORT_VIEW_PROPERTY(accessibilityIgnoresInvertColors, BOOL)
 
 // Acessibility related properties
 RCT_REMAP_VIEW_PROPERTY(accessible, reactAccessibilityElement.isAccessibilityElement, BOOL)

From 1dced3448a11f0fe9ab7a3fd98063b98fe552f60 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Sun, 24 Jun 2018 14:02:26 -0700
Subject: [PATCH 0909/1109] iOS: implement <PerformanceLoggerFlag> component

Summary: This is basic impl of <PerformanceLoggerFlag> component without any layout/mounting computation, just TTI.

Reviewed By: shergin, mdvacca

Differential Revision: D8598983

fbshipit-source-id: b938753d6396088735cbbeab26d69c9aaa45608e
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index caf2713ac7a5..06bbeb944493 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -65,10 +65,8 @@ static const std::string componentNameByReactViewName(std::string viewName) {
   }
 
   // We need this temporarly for testing purposes until we have proper
-  // implementation of core components: <ReactPerformanceLoggerFlag>,
-  // <SafeAreaView>, and etc.
+  // implementation of core components.
   if (
-    viewName == "ReactPerformanceLoggerFlag" ||
     viewName == "SinglelineTextInputView" ||
     viewName == "MultilineTextInputView" ||
     viewName == "RefreshControl" ||

From 71cd2d79ec3f4cd836b22a3cb8b363b8fd48855a Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Sun, 24 Jun 2018 14:34:00 -0700
Subject: [PATCH 0910/1109] Move conditional logic into corresponding build
 defs.

Summary:
Conditional `load`s are not allowed in Skylark. The logic
that belongs to different environments has to be part of environment
specific build defs and include as part of cell resolution or CI
configuration.
More context: https://buckbuild.com/concept/skylark.html

Differential Revision: D8604673

fbshipit-source-id: 385f2e155c4d80219e6ed3a2e0a82c909ebabb13
---
 ReactCommon/cxxreact/BUCK   | 22 ++++++----------------
 ReactCommon/jschelpers/BUCK |  4 ++--
 ReactNative/DEFS.bzl        | 11 ++++++++++-
 3 files changed, 18 insertions(+), 19 deletions(-)

diff --git a/ReactCommon/cxxreact/BUCK b/ReactCommon/cxxreact/BUCK
index 06bf8adbdaf4..b24c56a3c8f1 100644
--- a/ReactCommon/cxxreact/BUCK
+++ b/ReactCommon/cxxreact/BUCK
@@ -1,21 +1,11 @@
 load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
-load("//ReactNative:DEFS.bzl", "ANDROID", "ANDROID_JSC_DEPS", "APPLE", "APPLE_JSC_DEPS", "IS_OSS_BUILD", "get_android_inspector_flags", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
+load("//ReactNative:DEFS.bzl", "ANDROID", "ANDROID_JSC_DEPS", "APPLE", "get_apple_compiler_flags", "APPLE_JSC_DEPS", "get_debug_preprocessor_flags", "IS_OSS_BUILD", "get_android_inspector_flags", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
 CXX_LIBRARY_COMPILER_FLAGS = [
     "-std=c++14",
     "-Wall",
 ]
 
-APPLE_COMPILER_FLAGS = []
-
-DEBUG_PREPROCESSOR_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_debug_preprocessor_flags", "get_static_library_ios_flags")
-
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
-    DEBUG_PREPROCESSOR_FLAGS = get_debug_preprocessor_flags()
-
 rn_xplat_cxx_library(
     name = "module",
     header_namespace = "",
@@ -28,7 +18,7 @@ rn_xplat_cxx_library(
         prefix = "cxxreact",
     ),
     compiler_flags = CXX_LIBRARY_COMPILER_FLAGS,
-    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_compiler_flags = get_apple_compiler_flags(),
     force_static = True,
     visibility = [
         "PUBLIC",
@@ -52,7 +42,7 @@ rn_xplat_cxx_library(
         "-fexceptions",
         "-frtti",
     ],
-    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_compiler_flags = get_apple_compiler_flags(),
     force_static = True,
     visibility = [
         "PUBLIC",
@@ -73,7 +63,7 @@ rn_xplat_cxx_library(
         "-fno-omit-frame-pointer",
         "-fexceptions",
     ],
-    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_compiler_flags = get_apple_compiler_flags(),
     soname = "libxplat_react_module_samplemodule.$(ext)",
     visibility = [
         "PUBLIC",
@@ -141,13 +131,13 @@ rn_xplat_cxx_library(
         "-DWITH_JSC_MEMORY_PRESSURE=1",
         "-DWITH_FB_MEMORY_PROFILING=1",
     ],
-    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_compiler_flags = get_apple_compiler_flags(),
     fbobjc_deps = APPLE_JSC_DEPS,
     fbobjc_force_static = True,
     fbobjc_frameworks = [
         "$SDKROOT/System/Library/Frameworks/JavaScriptCore.framework",
     ],
-    fbobjc_preprocessor_flags = DEBUG_PREPROCESSOR_FLAGS + get_apple_inspector_flags(),
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     force_static = True,
     macosx_tests_override = [],
     platforms = (ANDROID, APPLE),
diff --git a/ReactCommon/jschelpers/BUCK b/ReactCommon/jschelpers/BUCK
index 9f3c8261714c..7739b8f7dc54 100644
--- a/ReactCommon/jschelpers/BUCK
+++ b/ReactCommon/jschelpers/BUCK
@@ -13,11 +13,11 @@ rn_xplat_cxx_library(
     name = "jscinternalhelpers",
     srcs = glob(
         ["*.cpp"],
-        excludes = ["systemJSCWrapper.cpp"],
+        exclude = ["systemJSCWrapper.cpp"],
     ),
     headers = glob(
         ["*.h"],
-        excludes = EXPORTED_HEADERS,
+        exclude = EXPORTED_HEADERS,
     ),
     header_namespace = "",
     exported_headers = dict([
diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index b0c85a1aaf7e..0909ede22362 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -6,12 +6,21 @@ This lets us build React Native:
 """
 # @lint-ignore-every SKYLINT BUCKRESTRICTEDSYNTAX
 
+_DEBUG_PREPROCESSOR_FLAGS = []
+
+_APPLE_COMPILER_FLAGS = []
+
+def get_debug_preprocessor_flags():
+    return _DEBUG_PREPROCESSOR_FLAGS
+
+def get_apple_compiler_flags():
+    return _APPLE_COMPILER_FLAGS
+
 IS_OSS_BUILD = True
 
 GLOG_DEP = "//ReactAndroid/build/third-party-ndk/glog:glog"
 
 INSPECTOR_FLAGS = []
-DEBUG_PREPROCESSOR_FLAGS = []
 
 APPLE_JSC_INTERNAL_DEPS = []
 APPLE_JSC_DEPS = []

From fe3bd9a65c9781e21f1b8e7e71672338bf8eb0c6 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Mon, 25 Jun 2018 09:29:27 -0700
Subject: [PATCH 0911/1109] Skylarkify ReactNative OSS build defs.

Summary:
Skylark parser will not allow access to file system other
than through `glob` and environment variables. The logic was also
making assumption about `buck-out` layout structure which is not
specified and as such is subject to change at any time without any
announcement.

Differential Revision: D8604721

fbshipit-source-id: 90826b4d5709580aad3092d0331d0e84e493c3b8
---
 ReactNative/DEFS.bzl | 50 +++++++++++++-------------------------------
 1 file changed, 14 insertions(+), 36 deletions(-)

diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index 0909ede22362..d7f28dfc1ae1 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -23,34 +23,36 @@ GLOG_DEP = "//ReactAndroid/build/third-party-ndk/glog:glog"
 INSPECTOR_FLAGS = []
 
 APPLE_JSC_INTERNAL_DEPS = []
+
 APPLE_JSC_DEPS = []
 
 ANDROID_JSC_INTERNAL_DEPS = [
-    '//native/third-party/jsc:jsc',
-    '//native/third-party/jsc:jsc_legacy_profiler',
+    "//native/third-party/jsc:jsc",
+    "//native/third-party/jsc:jsc_legacy_profiler",
 ]
+
 ANDROID_JSC_DEPS = ANDROID_JSC_INTERNAL_DEPS
+
 ANDROID = "Android"
+
 APPLE = ""
 
-YOGA_TARGET = '//ReactAndroid/src/main/java/com/facebook:yoga'
-FBGLOGINIT_TARGET = '//ReactAndroid/src/main/jni/first-party/fbgloginit:fbgloginit'
-FBJNI_TARGET = '//ReactAndroid/src/main/jni/first-party/fb:jni'
-JNI_TARGET = '//ReactAndroid/src/main/jni/first-party/jni-hack:jni-hack'
-KEYSTORE_TARGET = '//keystores:debug'
+YOGA_TARGET = "//ReactAndroid/src/main/java/com/facebook:yoga"
+
+FBGLOGINIT_TARGET = "//ReactAndroid/src/main/jni/first-party/fbgloginit:fbgloginit"
+
+FBJNI_TARGET = "//ReactAndroid/src/main/jni/first-party/fb:jni"
 
-with allow_unsafe_import():
-    import os
+JNI_TARGET = "//ReactAndroid/src/main/jni/first-party/jni-hack:jni-hack"
 
+KEYSTORE_TARGET = "//keystores:debug"
 
 def get_apple_inspector_flags():
     return []
 
-
 def get_android_inspector_flags():
     return []
 
-
 # Building is not supported in OSS right now
 def rn_xplat_cxx_library(name, **kwargs):
     new_kwargs = {
@@ -65,33 +67,27 @@ def rn_xplat_cxx_library(name, **kwargs):
         **new_kwargs
     )
 
-
 # Example: react_native_target('java/com/facebook/react/common:common')
 def react_native_target(path):
     return '//ReactAndroid/src/main/' + path
 
-
 # Example: react_native_xplat_target('bridge:bridge')
 def react_native_xplat_target(path):
     return '//ReactCommon/' + path
 
-
 # Example: react_native_tests_target('java/com/facebook/react/modules:modules')
 def react_native_tests_target(path):
     return '//ReactAndroid/src/test/' + path
 
-
 # Example: react_native_integration_tests_target('java/com/facebook/react/testing:testing')
 def react_native_integration_tests_target(path):
     return '//ReactAndroid/src/androidTest/' + path
 
-
 # Helper for referring to non-RN code from RN OSS code.
 # Example: react_native_dep('java/com/facebook/systrace:systrace')
 def react_native_dep(path):
     return '//ReactAndroid/src/main/' + path
 
-
 # React property preprocessor
 def rn_android_library(name, deps=[], plugins=[], *args, **kwargs):
 
@@ -119,45 +115,33 @@ def rn_android_library(name, deps=[], plugins=[], *args, **kwargs):
 
     native.android_library(name=name, deps=deps, plugins=plugins, *args, **kwargs)
 
-
 def rn_android_binary(*args, **kwargs):
     native.android_binary(*args, **kwargs)
 
-
 def rn_android_build_config(*args, **kwargs):
     native.android_build_config(*args, **kwargs)
 
-
 def rn_android_resource(*args, **kwargs):
     native.android_resource(*args, **kwargs)
 
-
 def rn_android_prebuilt_aar(*args, **kwargs):
     native.android_prebuilt_aar(*args, **kwargs)
 
-
 def rn_java_library(*args, **kwargs):
     native.java_library(*args, **kwargs)
 
-
 def rn_java_annotation_processor(*args, **kwargs):
     native.java_annotation_processor(*args, **kwargs)
 
-
 def rn_prebuilt_native_library(*args, **kwargs):
     native.prebuilt_native_library(*args, **kwargs)
 
-
 def rn_prebuilt_jar(*args, **kwargs):
     native.prebuilt_jar(*args, **kwargs)
 
-
 def rn_robolectric_test(name, srcs, vm_args=None, *args, **kwargs):
     vm_args = vm_args or []
 
-    # We may need to create buck-out/gen/ if we're running after buck clean.
-    tmp = 'buck-out/gen/' + get_base_path(
-    ) + '/__java_test_' + name + '_output__'
     extra_vm_args = [
         '-XX:+UseConcMarkSweepGC',  # required by -XX:+CMSClassUnloadingEnabled
         '-XX:+CMSClassUnloadingEnabled',
@@ -168,13 +152,8 @@ def rn_robolectric_test(name, srcs, vm_args=None, *args, **kwargs):
         '-XX:MaxPermSize=620m',
         '-Drobolectric.offline=true',
     ]
-    if os.path.isdir("/dev/shm") and 'CIRCLECI' not in os.environ:
+    if native.read_config("user", "use_dev_shm"):
         extra_vm_args.append('-Djava.io.tmpdir=/dev/shm')
-    else:
-        extra_vm_args.append(
-            '-Djava.io.tmpdir=%s' %
-            os.path.join(os.path.abspath('.'), 'buck-out/bin')
-        )
 
     # RN tests use  Powermock, which means they get their own ClassLoaders.
     # Because the yoga native library (or any native library) can only be loaded into one
@@ -193,7 +172,6 @@ def rn_robolectric_test(name, srcs, vm_args=None, *args, **kwargs):
         **kwargs
     )
 
-
 def cxx_library(allow_jni_merging=None, **kwargs):
     args = {
         k: v

From b3fe69cac2d60e11f00385897c84f4689fbf9082 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Mon, 25 Jun 2018 11:01:18 -0700
Subject: [PATCH 0912/1109] Fix external cell reference in OSS build.

Reviewed By: hramos

Differential Revision: D8615578

fbshipit-source-id: 22a0382956adc3c2cb0d25f756cd5fad11564559
---
 ReactAndroid/src/main/jni/first-party/fb/BUCK |  3 +-
 ReactNative/DEFS.bzl                          | 81 +++++++++++++++++++
 2 files changed, 82 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/jni/first-party/fb/BUCK b/ReactAndroid/src/main/jni/first-party/fb/BUCK
index f5f74a41c1cf..c25f868d73ea 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/BUCK
+++ b/ReactAndroid/src/main/jni/first-party/fb/BUCK
@@ -1,5 +1,4 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "JNI_TARGET", "cxx_library")
+load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "JNI_TARGET", "cxx_library", "subdir_glob")
 
 # This target is only used in open source
 if IS_OSS_BUILD:
diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index d7f28dfc1ae1..711688eb4f9f 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -179,3 +179,84 @@ def cxx_library(allow_jni_merging=None, **kwargs):
         if not (k.startswith("fbandroid_") or k.startswith("fbobjc_"))
     }
     native.cxx_library(**args)
+
+def _paths_join(path, *others):
+  """Joins one or more path components."""
+  result = path
+
+  for p in others:
+    if p.startswith("/"):  # absolute
+      result = p
+    elif not result or result.endswith("/"):
+      result += p
+    else:
+      result += "/" + p
+
+  return result
+
+def subdir_glob(glob_specs, exclude = None, prefix = ""):
+    """Returns a dict of sub-directory relative paths to full paths.
+
+    The subdir_glob() function is useful for defining header maps for C/C++
+    libraries which should be relative the given sub-directory.
+    Given a list of tuples, the form of (relative-sub-directory, glob-pattern),
+    it returns a dict of sub-directory relative paths to full paths.
+
+    Please refer to native.glob() for explanations and examples of the pattern.
+
+    Args:
+      glob_specs: The array of tuples in form of
+        (relative-sub-directory, glob-pattern inside relative-sub-directory).
+        type: List[Tuple[str, str]]
+      exclude: A list of patterns to identify files that should be removed
+        from the set specified by the first argument. Defaults to [].
+        type: Optional[List[str]]
+      prefix: If is not None, prepends it to each key in the dictionary.
+        Defaults to None.
+        type: Optional[str]
+
+    Returns:
+      A dict of sub-directory relative paths to full paths.
+    """
+    if exclude == None:
+        exclude = []
+
+    results = []
+
+    for dirpath, glob_pattern in glob_specs:
+        results.append(
+            _single_subdir_glob(dirpath, glob_pattern, exclude, prefix),
+        )
+
+    return _merge_maps(*results)
+
+def _merge_maps(*file_maps):
+    result = {}
+    for file_map in file_maps:
+        for key in file_map:
+            if key in result and result[key] != file_map[key]:
+                fail(
+                    "Conflicting files in file search paths. " +
+                    "\"%s\" maps to both \"%s\" and \"%s\"." %
+                    (key, result[key], file_map[key]),
+                )
+
+            result[key] = file_map[key]
+
+    return result
+
+def _single_subdir_glob(dirpath, glob_pattern, exclude = None, prefix = None):
+    if exclude == None:
+        exclude = []
+    results = {}
+    files = native.glob([_paths_join(dirpath, glob_pattern)], exclude = exclude)
+    for f in files:
+        if dirpath:
+            key = f[len(dirpath) + 1:]
+        else:
+            key = f
+        if prefix:
+            key = _paths_join(prefix, key)
+        results[key] = f
+
+    return results

From 5c2720b089dd0fb277771b0ac8b0e7788c493e5d Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Mon, 25 Jun 2018 13:57:15 -0700
Subject: [PATCH 0913/1109] Fix deprecated glob usage.

Summary: https://buckbuild.com/skylark/generated/glob.html

Reviewed By: styurin

Differential Revision: D8606487

fbshipit-source-id: 7a9c9cdc86b5f080328fb9af027dfbdc52e86508
---
 .../src/main/java/com/facebook/react/views/imagehelper/BUCK     | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
index 310841c6df43..98227e605a5a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/imagehelper/BUCK
@@ -4,7 +4,7 @@ rn_android_library(
     name = "imagehelper",
     srcs = glob(
         ["*.java"],
-        excludes = ["MultiSourceHelper.java"],
+        exclude = ["MultiSourceHelper.java"],
     ),
     visibility = [
         "PUBLIC",

From 77a9cba0c0fef8bdddaf4d78ac65a03205e093e7 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Mon, 25 Jun 2018 15:47:29 -0700
Subject: [PATCH 0914/1109] Image with null source should still respect `style`

Summary: Android RN image with source null returns null.

Reviewed By: yungsters

Differential Revision: D8576087

fbshipit-source-id: 685ed967e301ed2bf6417225bd88e2be3fe3cfd2
---
 Libraries/Image/Image.android.js              | 607 +++++++++---------
 .../react/views/image/ReactImageView.java     | 181 +++---
 2 files changed, 393 insertions(+), 395 deletions(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index d0e685a5e642..514673968c07 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -1,307 +1,300 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @flow
- * @format
- */
-
-'use strict';
-
-const ImageStylePropTypes = require('ImageStylePropTypes');
-const NativeModules = require('NativeModules');
-const React = require('React');
-const ReactNative = require('ReactNative');
-const PropTypes = require('prop-types');
-const StyleSheet = require('StyleSheet');
-const StyleSheetPropType = require('StyleSheetPropType');
-const TextAncestor = require('TextAncestor');
-const ViewPropTypes = require('ViewPropTypes');
-
-const flattenStyle = require('flattenStyle');
-const merge = require('merge');
-const requireNativeComponent = require('requireNativeComponent');
-const resolveAssetSource = require('resolveAssetSource');
-
-const {ImageLoader} = NativeModules;
-
-const RKImage = requireNativeComponent('RCTImageView');
-const RCTTextInlineImage = requireNativeComponent('RCTTextInlineImage');
-
-import type {ImageProps as ImagePropsType} from 'ImageProps';
-
-let _requestId = 1;
-function generateRequestId() {
-  return _requestId++;
-}
-
-const ImageProps = {
-  ...ViewPropTypes,
-  style: StyleSheetPropType(ImageStylePropTypes),
-  /**
-   * See https://facebook.github.io/react-native/docs/image.html#source
-   */
-  source: PropTypes.oneOfType([
-    PropTypes.shape({
-      uri: PropTypes.string,
-      headers: PropTypes.objectOf(PropTypes.string),
-    }),
-    // Opaque type returned by require('./image.jpg')
-    PropTypes.number,
-    // Multiple sources
-    PropTypes.arrayOf(
-      PropTypes.shape({
-        uri: PropTypes.string,
-        width: PropTypes.number,
-        height: PropTypes.number,
-        headers: PropTypes.objectOf(PropTypes.string),
-      }),
-    ),
-  ]),
-  /**
-   * blurRadius: the blur radius of the blur filter added to the image
-   *
-   * See https://facebook.github.io/react-native/docs/image.html#blurradius
-   */
-  blurRadius: PropTypes.number,
-  /**
-   * See https://facebook.github.io/react-native/docs/image.html#defaultsource
-   */
-  defaultSource: PropTypes.number,
-  /**
-   * See https://facebook.github.io/react-native/docs/image.html#loadingindicatorsource
-   */
-  loadingIndicatorSource: PropTypes.oneOfType([
-    PropTypes.shape({
-      uri: PropTypes.string,
-    }),
-    // Opaque type returned by require('./image.jpg')
-    PropTypes.number,
-  ]),
-  progressiveRenderingEnabled: PropTypes.bool,
-  fadeDuration: PropTypes.number,
-  /**
-   * Invoked on load start
-   */
-  onLoadStart: PropTypes.func,
-  /**
-   * Invoked on load error
-   */
-  onError: PropTypes.func,
-  /**
-   * Invoked when load completes successfully
-   */
-  onLoad: PropTypes.func,
-  /**
-   * Invoked when load either succeeds or fails
-   */
-  onLoadEnd: PropTypes.func,
-  /**
-   * Used to locate this view in end-to-end tests.
-   */
-  testID: PropTypes.string,
-  /**
-   * The mechanism that should be used to resize the image when the image's dimensions
-   * differ from the image view's dimensions. Defaults to `auto`.
-   *
-   * See https://facebook.github.io/react-native/docs/image.html#resizemethod
-   */
-  resizeMethod: PropTypes.oneOf(['auto', 'resize', 'scale']),
-  /**
-   * Determines how to resize the image when the frame doesn't match the raw
-   * image dimensions.
-   *
-   * See https://facebook.github.io/react-native/docs/image.html#resizemode
-   */
-  resizeMode: PropTypes.oneOf([
-    'cover',
-    'contain',
-    'stretch',
-    'repeat',
-    'center',
-  ]),
-};
-
-function getSize(
-  url: string,
-  success: (width: number, height: number) => void,
-  failure?: (error: any) => void,
-) {
-  return ImageLoader.getSize(url)
-    .then(function(sizes) {
-      success(sizes.width, sizes.height);
-    })
-    .catch(
-      failure ||
-        function() {
-          console.warn('Failed to get size for image: ' + url);
-        },
-    );
-}
-
-function prefetch(url: string, callback: ?Function) {
-  const requestId = generateRequestId();
-  callback && callback(requestId);
-  return ImageLoader.prefetchImage(url, requestId);
-}
-
-function abortPrefetch(requestId: number) {
-  ImageLoader.abortRequest(requestId);
-}
-
-/**
- * Perform cache interrogation.
- *
- * See https://facebook.github.io/react-native/docs/image.html#querycache
- */
-async function queryCache(
-  urls: Array<string>,
-): Promise<Map<string, 'memory' | 'disk'>> {
-  return await ImageLoader.queryCache(urls);
-}
-
-declare class ImageComponentType extends ReactNative.NativeComponent<
-  ImagePropsType,
-> {
-  static getSize: typeof getSize;
-  static prefetch: typeof prefetch;
-  static abortPrefetch: typeof abortPrefetch;
-  static queryCache: typeof queryCache;
-  static resolveAssetSource: typeof resolveAssetSource;
-  static propTypes: typeof ImageProps;
-}
-
-/**
- * A React component for displaying different types of images,
- * including network images, static resources, temporary local images, and
- * images from local disk, such as the camera roll.
- *
- * See https://facebook.github.io/react-native/docs/image.html
- */
-let Image = (
-  props: ImagePropsType,
-  forwardedRef: ?React.Ref<'RCTTextInlineImage' | 'RKImage'>,
-) => {
-  const source = resolveAssetSource(props.source);
-  const defaultSource = resolveAssetSource(props.defaultSource);
-  const loadingIndicatorSource = resolveAssetSource(
-    props.loadingIndicatorSource,
-  );
-
-  // As opposed to the ios version, here we render `null` when there is no source, source.uri
-  // or source array.
-
-  if (source && source.uri === '') {
-    console.warn('source.uri should not be an empty string');
-  }
-
-  if (props.src) {
-    console.warn(
-      'The <Image> component requires a `source` property rather than `src`.',
-    );
-  }
-
-  if (props.children) {
-    throw new Error(
-      'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.',
-    );
-  }
-
-  if (props.defaultSource && props.loadingIndicatorSource) {
-    throw new Error(
-      'The <Image> component cannot have defaultSource and loadingIndicatorSource at the same time. Please use either defaultSource or loadingIndicatorSource.',
-    );
-  }
-
-  if (!source || (!source.uri && !Array.isArray(source))) {
-    return null;
-  }
-
-  let style;
-  let sources;
-  if (source.uri) {
-    const {width, height} = source;
-    style = flattenStyle([{width, height}, styles.base, props.style]);
-    sources = [{uri: source.uri}];
-  } else {
-    style = flattenStyle([styles.base, props.style]);
-    sources = source;
-  }
-
-  const {onLoadStart, onLoad, onLoadEnd, onError} = props;
-  const nativeProps = merge(props, {
-    style,
-    shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),
-    src: sources,
-    headers: source.headers,
-    defaultSrc: defaultSource ? defaultSource.uri : null,
-    loadingIndicatorSrc: loadingIndicatorSource
-      ? loadingIndicatorSource.uri
-      : null,
-    ref: forwardedRef,
-  });
-
-  return (
-    <TextAncestor.Consumer>
-      {hasTextAncestor =>
-        hasTextAncestor ? (
-          <RCTTextInlineImage {...nativeProps} />
-        ) : (
-          <RKImage {...nativeProps} />
-        )
-      }
-    </TextAncestor.Consumer>
-  );
-};
-
-// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
-Image = React.forwardRef(Image);
-
-/**
- * Prefetches a remote image for later use by downloading it to the disk
- * cache
- *
- * See https://facebook.github.io/react-native/docs/image.html#prefetch
- */
-Image.getSize = getSize;
-
-/**
- * Prefetches a remote image for later use by downloading it to the disk
- * cache
- *
- * See https://facebook.github.io/react-native/docs/image.html#prefetch
- */
-Image.prefetch = prefetch;
-
-/**
- * Abort prefetch request.
- *
- * See https://facebook.github.io/react-native/docs/image.html#abortprefetch
- */
-Image.abortPrefetch = abortPrefetch;
-
-/**
- * Perform cache interrogation.
- *
- * See https://facebook.github.io/react-native/docs/image.html#querycache
- */
-Image.queryCache = queryCache;
-
-/**
- * Resolves an asset reference into an object.
- *
- * See https://facebook.github.io/react-native/docs/image.html#resolveassetsource
- */
-Image.resolveAssetSource = resolveAssetSource;
-
-Image.propTypes = ImageProps;
-
-const styles = StyleSheet.create({
-  base: {
-    overflow: 'hidden',
-  },
-});
-
-module.exports = (Image: Class<ImageComponentType>);
+/**	
+ * Copyright (c) 2015-present, Facebook, Inc.	
+ *	
+ * This source code is licensed under the MIT license found in the	
+ * LICENSE file in the root directory of this source tree.	
+ *	
+ * @flow	
+ * @format	
+ */	
+	
+'use strict';	
+	
+const ImageStylePropTypes = require('ImageStylePropTypes');	
+const NativeModules = require('NativeModules');	
+const React = require('React');	
+const ReactNative = require('ReactNative');	
+const PropTypes = require('prop-types');	
+const StyleSheet = require('StyleSheet');	
+const StyleSheetPropType = require('StyleSheetPropType');	
+const TextAncestor = require('TextAncestor');	
+const ViewPropTypes = require('ViewPropTypes');	
+	
+const flattenStyle = require('flattenStyle');	
+const merge = require('merge');	
+const requireNativeComponent = require('requireNativeComponent');	
+const resolveAssetSource = require('resolveAssetSource');	
+	
+const {ImageLoader} = NativeModules;	
+	
+const RKImage = requireNativeComponent('RCTImageView');	
+const RCTTextInlineImage = requireNativeComponent('RCTTextInlineImage');	
+	
+import type {ImageProps as ImagePropsType} from 'ImageProps';	
+	
+let _requestId = 1;	
+function generateRequestId() {	
+  return _requestId++;	
+}	
+	
+const ImageProps = {	
+  ...ViewPropTypes,	
+  style: StyleSheetPropType(ImageStylePropTypes),	
+  /**	
+   * See https://facebook.github.io/react-native/docs/image.html#source	
+   */	
+  source: PropTypes.oneOfType([	
+    PropTypes.shape({	
+      uri: PropTypes.string,	
+      headers: PropTypes.objectOf(PropTypes.string),	
+    }),	
+    // Opaque type returned by require('./image.jpg')	
+    PropTypes.number,	
+    // Multiple sources	
+    PropTypes.arrayOf(	
+      PropTypes.shape({	
+        uri: PropTypes.string,	
+        width: PropTypes.number,	
+        height: PropTypes.number,	
+        headers: PropTypes.objectOf(PropTypes.string),	
+      }),	
+    ),	
+  ]),	
+  /**	
+   * blurRadius: the blur radius of the blur filter added to the image	
+   *	
+   * See https://facebook.github.io/react-native/docs/image.html#blurradius	
+   */	
+  blurRadius: PropTypes.number,	
+  /**	
+   * See https://facebook.github.io/react-native/docs/image.html#defaultsource	
+   */	
+  defaultSource: PropTypes.number,	
+  /**	
+   * See https://facebook.github.io/react-native/docs/image.html#loadingindicatorsource	
+   */	
+  loadingIndicatorSource: PropTypes.oneOfType([	
+    PropTypes.shape({	
+      uri: PropTypes.string,	
+    }),	
+    // Opaque type returned by require('./image.jpg')	
+    PropTypes.number,	
+  ]),	
+  progressiveRenderingEnabled: PropTypes.bool,	
+  fadeDuration: PropTypes.number,	
+  /**	
+   * Invoked on load start	
+   */	
+  onLoadStart: PropTypes.func,	
+  /**	
+   * Invoked on load error	
+   */	
+  onError: PropTypes.func,	
+  /**	
+   * Invoked when load completes successfully	
+   */	
+  onLoad: PropTypes.func,	
+  /**	
+   * Invoked when load either succeeds or fails	
+   */	
+  onLoadEnd: PropTypes.func,	
+  /**	
+   * Used to locate this view in end-to-end tests.	
+   */	
+  testID: PropTypes.string,	
+  /**	
+   * The mechanism that should be used to resize the image when the image's dimensions	
+   * differ from the image view's dimensions. Defaults to `auto`.	
+   *	
+   * See https://facebook.github.io/react-native/docs/image.html#resizemethod	
+   */	
+  resizeMethod: PropTypes.oneOf(['auto', 'resize', 'scale']),	
+  /**	
+   * Determines how to resize the image when the frame doesn't match the raw	
+   * image dimensions.	
+   *	
+   * See https://facebook.github.io/react-native/docs/image.html#resizemode	
+   */	
+  resizeMode: PropTypes.oneOf([	
+    'cover',	
+    'contain',	
+    'stretch',	
+    'repeat',	
+    'center',	
+  ]),	
+};	
+	
+function getSize(	
+  url: string,	
+  success: (width: number, height: number) => void,	
+  failure?: (error: any) => void,	
+) {	
+  return ImageLoader.getSize(url)	
+    .then(function(sizes) {	
+      success(sizes.width, sizes.height);	
+    })	
+    .catch(	
+      failure ||	
+        function() {	
+          console.warn('Failed to get size for image: ' + url);	
+        },	
+    );	
+}	
+	
+function prefetch(url: string, callback: ?Function) {	
+  const requestId = generateRequestId();	
+  callback && callback(requestId);	
+  return ImageLoader.prefetchImage(url, requestId);	
+}	
+	
+function abortPrefetch(requestId: number) {	
+  ImageLoader.abortRequest(requestId);	
+}	
+	
+/**	
+ * Perform cache interrogation.	
+ *	
+ * See https://facebook.github.io/react-native/docs/image.html#querycache	
+ */	
+async function queryCache(	
+  urls: Array<string>,	
+): Promise<Map<string, 'memory' | 'disk'>> {	
+  return await ImageLoader.queryCache(urls);	
+}	
+	
+declare class ImageComponentType extends ReactNative.NativeComponent<	
+  ImagePropsType,	
+> {	
+  static getSize: typeof getSize;	
+  static prefetch: typeof prefetch;	
+  static abortPrefetch: typeof abortPrefetch;	
+  static queryCache: typeof queryCache;	
+  static resolveAssetSource: typeof resolveAssetSource;	
+  static propTypes: typeof ImageProps;	
+}	
+	
+/**	
+ * A React component for displaying different types of images,	
+ * including network images, static resources, temporary local images, and	
+ * images from local disk, such as the camera roll.	
+ *	
+ * See https://facebook.github.io/react-native/docs/image.html	
+ */	
+let Image = (	
+  props: ImagePropsType,	
+  forwardedRef: ?React.Ref<'RCTTextInlineImage' | 'RKImage'>,	
+) => {	
+  const source = resolveAssetSource(props.source);	
+  const defaultSource = resolveAssetSource(props.defaultSource);	
+  const loadingIndicatorSource = resolveAssetSource(	
+    props.loadingIndicatorSource,	
+  );	
+	
+  if (source && source.uri === '') {	
+    console.warn('source.uri should not be an empty string');	
+  }	
+	
+  if (props.src) {	
+    console.warn(	
+      'The <Image> component requires a `source` property rather than `src`.',	
+    );	
+  }	
+	
+  if (props.children) {	
+    throw new Error(	
+      'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.',	
+    );	
+  }	
+	
+  if (props.defaultSource && props.loadingIndicatorSource) {	
+    throw new Error(	
+      'The <Image> component cannot have defaultSource and loadingIndicatorSource at the same time. Please use either defaultSource or loadingIndicatorSource.',	
+    );	
+  }	
+		
+  let style;	
+  let sources;	
+  if (source?.uri != null) {	
+    const {width, height} = source;	
+    style = flattenStyle([{width, height}, styles.base, props.style]);	
+    sources = [{uri: source.uri}];	
+  } else {	
+    style = flattenStyle([styles.base, props.style]);	
+    sources = source;	
+  }	
+	
+  const {onLoadStart, onLoad, onLoadEnd, onError} = props;	
+  const nativeProps = merge(props, {	
+    style,	
+    shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),	
+    src: sources,	
+    headers: source?.headers,	
+    defaultSrc: defaultSource ? defaultSource.uri : null,	
+    loadingIndicatorSrc: loadingIndicatorSource	
+      ? loadingIndicatorSource.uri	
+      : null,	
+    ref: forwardedRef,	
+  });	
+	
+  return (	
+    <TextAncestor.Consumer>	
+      {hasTextAncestor =>	
+        hasTextAncestor ? (	
+          <RCTTextInlineImage {...nativeProps} />	
+        ) : (	
+          <RKImage {...nativeProps} />	
+        )	
+      }	
+    </TextAncestor.Consumer>	
+  );	
+};	
+	
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.	
+Image = React.forwardRef(Image);	
+	
+/**	
+ * Prefetches a remote image for later use by downloading it to the disk	
+ * cache	
+ *	
+ * See https://facebook.github.io/react-native/docs/image.html#prefetch	
+ */	
+Image.getSize = getSize;	
+	
+/**	
+ * Prefetches a remote image for later use by downloading it to the disk	
+ * cache	
+ *	
+ * See https://facebook.github.io/react-native/docs/image.html#prefetch	
+ */	
+Image.prefetch = prefetch;	
+	
+/**	
+ * Abort prefetch request.	
+ *	
+ * See https://facebook.github.io/react-native/docs/image.html#abortprefetch	
+ */	
+Image.abortPrefetch = abortPrefetch;	
+	
+/**	
+ * Perform cache interrogation.	
+ *	
+ * See https://facebook.github.io/react-native/docs/image.html#querycache	
+ */	
+Image.queryCache = queryCache;	
+	
+/**	
+ * Resolves an asset reference into an object.	
+ *	
+ * See https://facebook.github.io/react-native/docs/image.html#resolveassetsource	
+ */	
+Image.resolveAssetSource = resolveAssetSource;	
+	
+Image.propTypes = ImageProps;	
+	
+const styles = StyleSheet.create({	
+  base: {	
+    overflow: 'hidden',	
+  },	
+});	
+	
+module.exports = (Image: Class<ImageComponentType>);
\ No newline at end of file
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index 440bf3f2c775..7fdd4057047e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -1,9 +1,9 @@
 /**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
+* Copyright (c) 2015-present, Facebook, Inc.
+*
+* This source code is licensed under the MIT license found in the
+* LICENSE file in the root directory of this source tree.
+*/
 
 package com.facebook.react.views.image;
 
@@ -63,26 +63,29 @@
 import javax.annotation.Nullable;
 
 /**
- * Wrapper class around Fresco's GenericDraweeView, enabling persisting props across multiple view
- * update and consistent processing of both static and network images.
- */
+* Wrapper class around Fresco's GenericDraweeView, enabling persisting props across multiple view
+* update and consistent processing of both static and network images.
+*/
 public class ReactImageView extends GenericDraweeView {
 
   public static final int REMOTE_IMAGE_FADE_DURATION_MS = 300;
 
+  public static final String REMOTE_TRANSPARENT_BITMAP_URI =
+  "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAQAAAC1HAwCAAAAC0lEQVR42mNkYAAAAAYAAjCB0C8AAAAASUVORK5CYII=";
+
   private static float[] sComputedCornerRadii = new float[4];
 
   /*
-   * Implementation note re rounded corners:
-   *
-   * Fresco's built-in rounded corners only work for 'cover' resize mode -
-   * this is a limitation in Android itself. Fresco has a workaround for this, but
-   * it requires knowing the background color.
-   *
-   * So for the other modes, we use a postprocessor.
-   * Because the postprocessor uses a modified bitmap, that would just get cropped in
-   * 'cover' mode, so we fall back to Fresco's normal implementation.
-   */
+  * Implementation note re rounded corners:
+  *
+  * Fresco's built-in rounded corners only work for 'cover' resize mode -
+  * this is a limitation in Android itself. Fresco has a workaround for this, but
+  * it requires knowing the background color.
+  *
+  * So for the other modes, we use a postprocessor.
+  * Because the postprocessor uses a modified bitmap, that would just get cropped in
+  * 'cover' mode, so we fall back to Fresco's normal implementation.
+  */
   private static final Matrix sMatrix = new Matrix();
   private static final Matrix sInverse = new Matrix();
   private ImageResizeMethod mResizeMethod = ImageResizeMethod.AUTO;
@@ -91,12 +94,12 @@ private class RoundedCornerPostprocessor extends BasePostprocessor {
 
     void getRadii(Bitmap source, float[] computedCornerRadii, float[] mappedRadii) {
       mScaleType.getTransform(
-        sMatrix,
-        new Rect(0, 0, source.getWidth(), source.getHeight()),
-        source.getWidth(),
-        source.getHeight(),
-        0.0f,
-        0.0f);
+      sMatrix,
+      new Rect(0, 0, source.getWidth(), source.getHeight()),
+      source.getWidth(),
+      source.getHeight(),
+      0.0f,
+      0.0f);
       sMatrix.invert(sInverse);
 
       mappedRadii[0] = sInverse.mapRadius(computedCornerRadii[0]);
@@ -118,9 +121,9 @@ public void process(Bitmap output, Bitmap source) {
 
       output.setHasAlpha(true);
       if (FloatUtil.floatsEqual(sComputedCornerRadii[0], 0f) &&
-        FloatUtil.floatsEqual(sComputedCornerRadii[1], 0f) &&
-        FloatUtil.floatsEqual(sComputedCornerRadii[2], 0f) &&
-        FloatUtil.floatsEqual(sComputedCornerRadii[3], 0f)) {
+      FloatUtil.floatsEqual(sComputedCornerRadii[1], 0f) &&
+      FloatUtil.floatsEqual(sComputedCornerRadii[2], 0f) &&
+      FloatUtil.floatsEqual(sComputedCornerRadii[3], 0f)) {
         super.process(output, source);
         return;
       }
@@ -136,9 +139,9 @@ public void process(Bitmap output, Bitmap source) {
       Path pathForBorderRadius = new Path();
 
       pathForBorderRadius.addRoundRect(
-        new RectF(0, 0, source.getWidth(), source.getHeight()),
-        radii,
-        Path.Direction.CW);
+      new RectF(0, 0, source.getWidth(), source.getHeight()),
+      radii,
+      Path.Direction.CW);
 
       canvas.drawPath(pathForBorderRadius, paint);
     }
@@ -154,12 +157,12 @@ public CloseableReference<Bitmap> process(Bitmap source, PlatformBitmapFactory b
       final Rect destRect = new Rect(0, 0, getWidth(), getHeight());
 
       mScaleType.getTransform(
-        sTileMatrix,
-        destRect,
-        source.getWidth(),
-        source.getHeight(),
-        0.0f,
-        0.0f);
+      sTileMatrix,
+      destRect,
+      source.getWidth(),
+      source.getHeight(),
+      0.0f,
+      0.0f);
 
       Paint paint = new Paint();
       paint.setAntiAlias(true);
@@ -209,15 +212,15 @@ public CloseableReference<Bitmap> process(Bitmap source, PlatformBitmapFactory b
   // We can't specify rounding in XML, so have to do so here
   private static GenericDraweeHierarchy buildHierarchy(Context context) {
     return new GenericDraweeHierarchyBuilder(context.getResources())
-      .setRoundingParams(RoundingParams.fromCornersRadius(0))
-      .build();
+    .setRoundingParams(RoundingParams.fromCornersRadius(0))
+    .build();
   }
 
   public ReactImageView(
-    Context context,
-    AbstractDraweeControllerBuilder draweeControllerBuilder,
-    @Nullable GlobalImageLoadListener globalImageLoadListener,
-    @Nullable Object callerContext) {
+  Context context,
+  AbstractDraweeControllerBuilder draweeControllerBuilder,
+  @Nullable GlobalImageLoadListener globalImageLoadListener,
+  @Nullable Object callerContext) {
     super(context, buildHierarchy(context));
     mScaleType = ImageResizeMode.defaultValue();
     mDraweeControllerBuilder = draweeControllerBuilder;
@@ -238,29 +241,29 @@ public void setShouldNotifyLoadEvents(boolean shouldNotify) {
         @Override
         public void onSubmit(String id, Object callerContext) {
           mEventDispatcher.dispatchEvent(
-            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_START));
+          new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_START));
         }
 
         @Override
         public void onFinalImageSet(
-          String id,
-          @Nullable final ImageInfo imageInfo,
-          @Nullable Animatable animatable) {
+        String id,
+        @Nullable final ImageInfo imageInfo,
+        @Nullable Animatable animatable) {
           if (imageInfo != null) {
             mEventDispatcher.dispatchEvent(
-              new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD,
-                mImageSource.getSource(), imageInfo.getWidth(), imageInfo.getHeight()));
+            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD,
+            mImageSource.getSource(), imageInfo.getWidth(), imageInfo.getHeight()));
             mEventDispatcher.dispatchEvent(
-              new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_END));
+            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_END));
           }
         }
 
         @Override
         public void onFailure(String id, Throwable throwable) {
           mEventDispatcher.dispatchEvent(
-            new ImageLoadEvent(getId(), ImageLoadEvent.ON_ERROR));
+          new ImageLoadEvent(getId(), ImageLoadEvent.ON_ERROR));
           mEventDispatcher.dispatchEvent(
-            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_END));
+          new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_END));
         }
       };
     }
@@ -338,7 +341,10 @@ public void setResizeMethod(ImageResizeMethod resizeMethod) {
 
   public void setSource(@Nullable ReadableArray sources) {
     mSources.clear();
-    if (sources != null && sources.size() != 0) {
+    if (sources == null || sources.size() == 0) {
+      ImageSource imageSource = new ImageSource(getContext(), REMOTE_TRANSPARENT_BITMAP_URI);
+      mSources.add(imageSource);
+    } else {
       // Optimize for the case where we have just one uri, case in which we don't need the sizes
       if (sources.size() == 1) {
         ReadableMap source = sources.getMap(0);
@@ -353,10 +359,10 @@ public void setSource(@Nullable ReadableArray sources) {
           ReadableMap source = sources.getMap(idx);
           String uri = source.getString("uri");
           ImageSource imageSource = new ImageSource(
-            getContext(),
-            uri,
-            source.getDouble("width"),
-            source.getDouble("height"));
+          getContext(),
+          uri,
+          source.getDouble("width"),
+          source.getDouble("height"));
           mSources.add(imageSource);
           if (Uri.EMPTY.equals(imageSource.getUri())) {
             warnImageSource(uri);
@@ -375,7 +381,7 @@ public void setDefaultSource(@Nullable String name) {
   public void setLoadingIndicatorSource(@Nullable String name) {
     Drawable drawable = ResourceDrawableIdHelper.getInstance().getResourceDrawable(getContext(), name);
     mLoadingImageDrawable =
-      drawable != null ? (Drawable) new AutoRotateDrawable(drawable, 1000) : null;
+    drawable != null ? (Drawable) new AutoRotateDrawable(drawable, 1000) : null;
     mIsDirty = true;
   }
 
@@ -440,8 +446,8 @@ public void maybeUpdateView() {
     }
 
     boolean usePostprocessorScaling =
-      mScaleType != ScalingUtils.ScaleType.CENTER_CROP &&
-        mScaleType != ScalingUtils.ScaleType.FOCUS_CROP;
+    mScaleType != ScalingUtils.ScaleType.CENTER_CROP &&
+    mScaleType != ScalingUtils.ScaleType.FOCUS_CROP;
 
     RoundingParams roundingParams = hierarchy.getRoundingParams();
 
@@ -468,9 +474,9 @@ public void maybeUpdateView() {
     }
     hierarchy.setRoundingParams(roundingParams);
     hierarchy.setFadeDuration(
-      mFadeDurationMs >= 0
-        ? mFadeDurationMs
-        : mImageSource.isResource() ? 0 : REMOTE_IMAGE_FADE_DURATION_MS);
+    mFadeDurationMs >= 0
+    ? mFadeDurationMs
+    : mImageSource.isResource() ? 0 : REMOTE_IMAGE_FADE_DURATION_MS);
 
     List<Postprocessor> postprocessors = new LinkedList<>();
     if (usePostprocessorScaling) {
@@ -487,10 +493,10 @@ public void maybeUpdateView() {
     ResizeOptions resizeOptions = doResize ? new ResizeOptions(getWidth(), getHeight()) : null;
 
     ImageRequestBuilder imageRequestBuilder = ImageRequestBuilder.newBuilderWithSource(mImageSource.getUri())
-      .setPostprocessor(postprocessor)
-      .setResizeOptions(resizeOptions)
-      .setAutoRotateEnabled(true)
-      .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled);
+    .setPostprocessor(postprocessor)
+    .setResizeOptions(resizeOptions)
+    .setAutoRotateEnabled(true)
+    .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled);
 
     ImageRequest imageRequest = ReactNetworkImageRequest.fromBuilderWithHeaders(imageRequestBuilder, mHeaders);
 
@@ -502,19 +508,19 @@ public void maybeUpdateView() {
     mDraweeControllerBuilder.reset();
 
     mDraweeControllerBuilder
-      .setAutoPlayAnimations(true)
-      .setCallerContext(mCallerContext)
-      .setOldController(getController())
-      .setImageRequest(imageRequest);
+    .setAutoPlayAnimations(true)
+    .setCallerContext(mCallerContext)
+    .setOldController(getController())
+    .setImageRequest(imageRequest);
 
     if (mCachedImageSource != null) {
       ImageRequest cachedImageRequest =
-        ImageRequestBuilder.newBuilderWithSource(mCachedImageSource.getUri())
-          .setPostprocessor(postprocessor)
-          .setResizeOptions(resizeOptions)
-          .setAutoRotateEnabled(true)
-          .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled)
-          .build();
+      ImageRequestBuilder.newBuilderWithSource(mCachedImageSource.getUri())
+      .setPostprocessor(postprocessor)
+      .setResizeOptions(resizeOptions)
+      .setAutoRotateEnabled(true)
+      .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled)
+      .build();
       mDraweeControllerBuilder.setLowResImageRequest(cachedImageRequest);
     }
 
@@ -554,8 +560,8 @@ protected void onSizeChanged(int w, int h, int oldw, int oldh) {
   }
 
   /**
-   * ReactImageViews only render a single image.
-   */
+  * ReactImageViews only render a single image.
+  */
   @Override
   public boolean hasOverlappingRendering() {
     return false;
@@ -572,11 +578,11 @@ private boolean isTiled() {
   private void setSourceImage() {
     mImageSource = null;
     if (mSources.isEmpty()) {
-      return;
-    }
-    if (hasMultipleSources()) {
+      ImageSource imageSource = new ImageSource(getContext(), REMOTE_TRANSPARENT_BITMAP_URI);
+      mSources.add(imageSource);
+    } else if (hasMultipleSources()) {
       MultiSourceResult multiSource =
-        MultiSourceHelper.getBestSourceForSize(getWidth(), getHeight(), mSources);
+      MultiSourceHelper.getBestSourceForSize(getWidth(), getHeight(), mSources);
       mImageSource = multiSource.getBestResult();
       mCachedImageSource = multiSource.getBestResultInCache();
       return;
@@ -591,8 +597,8 @@ private boolean shouldResize(ImageSource imageSource) {
     // has no control over the original size
     if (mResizeMethod == ImageResizeMethod.AUTO) {
       return
-        UriUtil.isLocalContentUri(imageSource.getUri()) ||
-          UriUtil.isLocalFileUri(imageSource.getUri());
+      UriUtil.isLocalContentUri(imageSource.getUri()) ||
+      UriUtil.isLocalFileUri(imageSource.getUri());
     } else if (mResizeMethod == ImageResizeMethod.RESIZE) {
       return true;
     } else {
@@ -603,10 +609,9 @@ private boolean shouldResize(ImageSource imageSource) {
   private void warnImageSource(String uri) {
     if (ReactBuildConfig.DEBUG) {
       Toast.makeText(
-        getContext(),
-        "Warning: Image source \"" + uri + "\" doesn't exist",
-        Toast.LENGTH_SHORT).show();
+      getContext(),
+      "Warning: Image source \"" + uri + "\" doesn't exist",
+      Toast.LENGTH_SHORT).show();
     }
   }
 }
-

From bdf0eadab31c7cd390b41bfc41a9c1dd88b4dbfb Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Mon, 25 Jun 2018 15:55:33 -0700
Subject: [PATCH 0915/1109] Revert D8576087: [RN][Android] Image with null
 source should still respect `style`

Differential Revision:
D8576087

Original commit changeset: 685ed967e301

fbshipit-source-id: 97a8ab9757a2f5a0d72bbc1e020354c306e48a15
---
 Libraries/Image/Image.android.js              | 607 +++++++++---------
 .../react/views/image/ReactImageView.java     | 181 +++---
 2 files changed, 395 insertions(+), 393 deletions(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index 514673968c07..d0e685a5e642 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -1,300 +1,307 @@
-/**	
- * Copyright (c) 2015-present, Facebook, Inc.	
- *	
- * This source code is licensed under the MIT license found in the	
- * LICENSE file in the root directory of this source tree.	
- *	
- * @flow	
- * @format	
- */	
-	
-'use strict';	
-	
-const ImageStylePropTypes = require('ImageStylePropTypes');	
-const NativeModules = require('NativeModules');	
-const React = require('React');	
-const ReactNative = require('ReactNative');	
-const PropTypes = require('prop-types');	
-const StyleSheet = require('StyleSheet');	
-const StyleSheetPropType = require('StyleSheetPropType');	
-const TextAncestor = require('TextAncestor');	
-const ViewPropTypes = require('ViewPropTypes');	
-	
-const flattenStyle = require('flattenStyle');	
-const merge = require('merge');	
-const requireNativeComponent = require('requireNativeComponent');	
-const resolveAssetSource = require('resolveAssetSource');	
-	
-const {ImageLoader} = NativeModules;	
-	
-const RKImage = requireNativeComponent('RCTImageView');	
-const RCTTextInlineImage = requireNativeComponent('RCTTextInlineImage');	
-	
-import type {ImageProps as ImagePropsType} from 'ImageProps';	
-	
-let _requestId = 1;	
-function generateRequestId() {	
-  return _requestId++;	
-}	
-	
-const ImageProps = {	
-  ...ViewPropTypes,	
-  style: StyleSheetPropType(ImageStylePropTypes),	
-  /**	
-   * See https://facebook.github.io/react-native/docs/image.html#source	
-   */	
-  source: PropTypes.oneOfType([	
-    PropTypes.shape({	
-      uri: PropTypes.string,	
-      headers: PropTypes.objectOf(PropTypes.string),	
-    }),	
-    // Opaque type returned by require('./image.jpg')	
-    PropTypes.number,	
-    // Multiple sources	
-    PropTypes.arrayOf(	
-      PropTypes.shape({	
-        uri: PropTypes.string,	
-        width: PropTypes.number,	
-        height: PropTypes.number,	
-        headers: PropTypes.objectOf(PropTypes.string),	
-      }),	
-    ),	
-  ]),	
-  /**	
-   * blurRadius: the blur radius of the blur filter added to the image	
-   *	
-   * See https://facebook.github.io/react-native/docs/image.html#blurradius	
-   */	
-  blurRadius: PropTypes.number,	
-  /**	
-   * See https://facebook.github.io/react-native/docs/image.html#defaultsource	
-   */	
-  defaultSource: PropTypes.number,	
-  /**	
-   * See https://facebook.github.io/react-native/docs/image.html#loadingindicatorsource	
-   */	
-  loadingIndicatorSource: PropTypes.oneOfType([	
-    PropTypes.shape({	
-      uri: PropTypes.string,	
-    }),	
-    // Opaque type returned by require('./image.jpg')	
-    PropTypes.number,	
-  ]),	
-  progressiveRenderingEnabled: PropTypes.bool,	
-  fadeDuration: PropTypes.number,	
-  /**	
-   * Invoked on load start	
-   */	
-  onLoadStart: PropTypes.func,	
-  /**	
-   * Invoked on load error	
-   */	
-  onError: PropTypes.func,	
-  /**	
-   * Invoked when load completes successfully	
-   */	
-  onLoad: PropTypes.func,	
-  /**	
-   * Invoked when load either succeeds or fails	
-   */	
-  onLoadEnd: PropTypes.func,	
-  /**	
-   * Used to locate this view in end-to-end tests.	
-   */	
-  testID: PropTypes.string,	
-  /**	
-   * The mechanism that should be used to resize the image when the image's dimensions	
-   * differ from the image view's dimensions. Defaults to `auto`.	
-   *	
-   * See https://facebook.github.io/react-native/docs/image.html#resizemethod	
-   */	
-  resizeMethod: PropTypes.oneOf(['auto', 'resize', 'scale']),	
-  /**	
-   * Determines how to resize the image when the frame doesn't match the raw	
-   * image dimensions.	
-   *	
-   * See https://facebook.github.io/react-native/docs/image.html#resizemode	
-   */	
-  resizeMode: PropTypes.oneOf([	
-    'cover',	
-    'contain',	
-    'stretch',	
-    'repeat',	
-    'center',	
-  ]),	
-};	
-	
-function getSize(	
-  url: string,	
-  success: (width: number, height: number) => void,	
-  failure?: (error: any) => void,	
-) {	
-  return ImageLoader.getSize(url)	
-    .then(function(sizes) {	
-      success(sizes.width, sizes.height);	
-    })	
-    .catch(	
-      failure ||	
-        function() {	
-          console.warn('Failed to get size for image: ' + url);	
-        },	
-    );	
-}	
-	
-function prefetch(url: string, callback: ?Function) {	
-  const requestId = generateRequestId();	
-  callback && callback(requestId);	
-  return ImageLoader.prefetchImage(url, requestId);	
-}	
-	
-function abortPrefetch(requestId: number) {	
-  ImageLoader.abortRequest(requestId);	
-}	
-	
-/**	
- * Perform cache interrogation.	
- *	
- * See https://facebook.github.io/react-native/docs/image.html#querycache	
- */	
-async function queryCache(	
-  urls: Array<string>,	
-): Promise<Map<string, 'memory' | 'disk'>> {	
-  return await ImageLoader.queryCache(urls);	
-}	
-	
-declare class ImageComponentType extends ReactNative.NativeComponent<	
-  ImagePropsType,	
-> {	
-  static getSize: typeof getSize;	
-  static prefetch: typeof prefetch;	
-  static abortPrefetch: typeof abortPrefetch;	
-  static queryCache: typeof queryCache;	
-  static resolveAssetSource: typeof resolveAssetSource;	
-  static propTypes: typeof ImageProps;	
-}	
-	
-/**	
- * A React component for displaying different types of images,	
- * including network images, static resources, temporary local images, and	
- * images from local disk, such as the camera roll.	
- *	
- * See https://facebook.github.io/react-native/docs/image.html	
- */	
-let Image = (	
-  props: ImagePropsType,	
-  forwardedRef: ?React.Ref<'RCTTextInlineImage' | 'RKImage'>,	
-) => {	
-  const source = resolveAssetSource(props.source);	
-  const defaultSource = resolveAssetSource(props.defaultSource);	
-  const loadingIndicatorSource = resolveAssetSource(	
-    props.loadingIndicatorSource,	
-  );	
-	
-  if (source && source.uri === '') {	
-    console.warn('source.uri should not be an empty string');	
-  }	
-	
-  if (props.src) {	
-    console.warn(	
-      'The <Image> component requires a `source` property rather than `src`.',	
-    );	
-  }	
-	
-  if (props.children) {	
-    throw new Error(	
-      'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.',	
-    );	
-  }	
-	
-  if (props.defaultSource && props.loadingIndicatorSource) {	
-    throw new Error(	
-      'The <Image> component cannot have defaultSource and loadingIndicatorSource at the same time. Please use either defaultSource or loadingIndicatorSource.',	
-    );	
-  }	
-		
-  let style;	
-  let sources;	
-  if (source?.uri != null) {	
-    const {width, height} = source;	
-    style = flattenStyle([{width, height}, styles.base, props.style]);	
-    sources = [{uri: source.uri}];	
-  } else {	
-    style = flattenStyle([styles.base, props.style]);	
-    sources = source;	
-  }	
-	
-  const {onLoadStart, onLoad, onLoadEnd, onError} = props;	
-  const nativeProps = merge(props, {	
-    style,	
-    shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),	
-    src: sources,	
-    headers: source?.headers,	
-    defaultSrc: defaultSource ? defaultSource.uri : null,	
-    loadingIndicatorSrc: loadingIndicatorSource	
-      ? loadingIndicatorSource.uri	
-      : null,	
-    ref: forwardedRef,	
-  });	
-	
-  return (	
-    <TextAncestor.Consumer>	
-      {hasTextAncestor =>	
-        hasTextAncestor ? (	
-          <RCTTextInlineImage {...nativeProps} />	
-        ) : (	
-          <RKImage {...nativeProps} />	
-        )	
-      }	
-    </TextAncestor.Consumer>	
-  );	
-};	
-	
-// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.	
-Image = React.forwardRef(Image);	
-	
-/**	
- * Prefetches a remote image for later use by downloading it to the disk	
- * cache	
- *	
- * See https://facebook.github.io/react-native/docs/image.html#prefetch	
- */	
-Image.getSize = getSize;	
-	
-/**	
- * Prefetches a remote image for later use by downloading it to the disk	
- * cache	
- *	
- * See https://facebook.github.io/react-native/docs/image.html#prefetch	
- */	
-Image.prefetch = prefetch;	
-	
-/**	
- * Abort prefetch request.	
- *	
- * See https://facebook.github.io/react-native/docs/image.html#abortprefetch	
- */	
-Image.abortPrefetch = abortPrefetch;	
-	
-/**	
- * Perform cache interrogation.	
- *	
- * See https://facebook.github.io/react-native/docs/image.html#querycache	
- */	
-Image.queryCache = queryCache;	
-	
-/**	
- * Resolves an asset reference into an object.	
- *	
- * See https://facebook.github.io/react-native/docs/image.html#resolveassetsource	
- */	
-Image.resolveAssetSource = resolveAssetSource;	
-	
-Image.propTypes = ImageProps;	
-	
-const styles = StyleSheet.create({	
-  base: {	
-    overflow: 'hidden',	
-  },	
-});	
-	
-module.exports = (Image: Class<ImageComponentType>);
\ No newline at end of file
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow
+ * @format
+ */
+
+'use strict';
+
+const ImageStylePropTypes = require('ImageStylePropTypes');
+const NativeModules = require('NativeModules');
+const React = require('React');
+const ReactNative = require('ReactNative');
+const PropTypes = require('prop-types');
+const StyleSheet = require('StyleSheet');
+const StyleSheetPropType = require('StyleSheetPropType');
+const TextAncestor = require('TextAncestor');
+const ViewPropTypes = require('ViewPropTypes');
+
+const flattenStyle = require('flattenStyle');
+const merge = require('merge');
+const requireNativeComponent = require('requireNativeComponent');
+const resolveAssetSource = require('resolveAssetSource');
+
+const {ImageLoader} = NativeModules;
+
+const RKImage = requireNativeComponent('RCTImageView');
+const RCTTextInlineImage = requireNativeComponent('RCTTextInlineImage');
+
+import type {ImageProps as ImagePropsType} from 'ImageProps';
+
+let _requestId = 1;
+function generateRequestId() {
+  return _requestId++;
+}
+
+const ImageProps = {
+  ...ViewPropTypes,
+  style: StyleSheetPropType(ImageStylePropTypes),
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#source
+   */
+  source: PropTypes.oneOfType([
+    PropTypes.shape({
+      uri: PropTypes.string,
+      headers: PropTypes.objectOf(PropTypes.string),
+    }),
+    // Opaque type returned by require('./image.jpg')
+    PropTypes.number,
+    // Multiple sources
+    PropTypes.arrayOf(
+      PropTypes.shape({
+        uri: PropTypes.string,
+        width: PropTypes.number,
+        height: PropTypes.number,
+        headers: PropTypes.objectOf(PropTypes.string),
+      }),
+    ),
+  ]),
+  /**
+   * blurRadius: the blur radius of the blur filter added to the image
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#blurradius
+   */
+  blurRadius: PropTypes.number,
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#defaultsource
+   */
+  defaultSource: PropTypes.number,
+  /**
+   * See https://facebook.github.io/react-native/docs/image.html#loadingindicatorsource
+   */
+  loadingIndicatorSource: PropTypes.oneOfType([
+    PropTypes.shape({
+      uri: PropTypes.string,
+    }),
+    // Opaque type returned by require('./image.jpg')
+    PropTypes.number,
+  ]),
+  progressiveRenderingEnabled: PropTypes.bool,
+  fadeDuration: PropTypes.number,
+  /**
+   * Invoked on load start
+   */
+  onLoadStart: PropTypes.func,
+  /**
+   * Invoked on load error
+   */
+  onError: PropTypes.func,
+  /**
+   * Invoked when load completes successfully
+   */
+  onLoad: PropTypes.func,
+  /**
+   * Invoked when load either succeeds or fails
+   */
+  onLoadEnd: PropTypes.func,
+  /**
+   * Used to locate this view in end-to-end tests.
+   */
+  testID: PropTypes.string,
+  /**
+   * The mechanism that should be used to resize the image when the image's dimensions
+   * differ from the image view's dimensions. Defaults to `auto`.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#resizemethod
+   */
+  resizeMethod: PropTypes.oneOf(['auto', 'resize', 'scale']),
+  /**
+   * Determines how to resize the image when the frame doesn't match the raw
+   * image dimensions.
+   *
+   * See https://facebook.github.io/react-native/docs/image.html#resizemode
+   */
+  resizeMode: PropTypes.oneOf([
+    'cover',
+    'contain',
+    'stretch',
+    'repeat',
+    'center',
+  ]),
+};
+
+function getSize(
+  url: string,
+  success: (width: number, height: number) => void,
+  failure?: (error: any) => void,
+) {
+  return ImageLoader.getSize(url)
+    .then(function(sizes) {
+      success(sizes.width, sizes.height);
+    })
+    .catch(
+      failure ||
+        function() {
+          console.warn('Failed to get size for image: ' + url);
+        },
+    );
+}
+
+function prefetch(url: string, callback: ?Function) {
+  const requestId = generateRequestId();
+  callback && callback(requestId);
+  return ImageLoader.prefetchImage(url, requestId);
+}
+
+function abortPrefetch(requestId: number) {
+  ImageLoader.abortRequest(requestId);
+}
+
+/**
+ * Perform cache interrogation.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#querycache
+ */
+async function queryCache(
+  urls: Array<string>,
+): Promise<Map<string, 'memory' | 'disk'>> {
+  return await ImageLoader.queryCache(urls);
+}
+
+declare class ImageComponentType extends ReactNative.NativeComponent<
+  ImagePropsType,
+> {
+  static getSize: typeof getSize;
+  static prefetch: typeof prefetch;
+  static abortPrefetch: typeof abortPrefetch;
+  static queryCache: typeof queryCache;
+  static resolveAssetSource: typeof resolveAssetSource;
+  static propTypes: typeof ImageProps;
+}
+
+/**
+ * A React component for displaying different types of images,
+ * including network images, static resources, temporary local images, and
+ * images from local disk, such as the camera roll.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html
+ */
+let Image = (
+  props: ImagePropsType,
+  forwardedRef: ?React.Ref<'RCTTextInlineImage' | 'RKImage'>,
+) => {
+  const source = resolveAssetSource(props.source);
+  const defaultSource = resolveAssetSource(props.defaultSource);
+  const loadingIndicatorSource = resolveAssetSource(
+    props.loadingIndicatorSource,
+  );
+
+  // As opposed to the ios version, here we render `null` when there is no source, source.uri
+  // or source array.
+
+  if (source && source.uri === '') {
+    console.warn('source.uri should not be an empty string');
+  }
+
+  if (props.src) {
+    console.warn(
+      'The <Image> component requires a `source` property rather than `src`.',
+    );
+  }
+
+  if (props.children) {
+    throw new Error(
+      'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.',
+    );
+  }
+
+  if (props.defaultSource && props.loadingIndicatorSource) {
+    throw new Error(
+      'The <Image> component cannot have defaultSource and loadingIndicatorSource at the same time. Please use either defaultSource or loadingIndicatorSource.',
+    );
+  }
+
+  if (!source || (!source.uri && !Array.isArray(source))) {
+    return null;
+  }
+
+  let style;
+  let sources;
+  if (source.uri) {
+    const {width, height} = source;
+    style = flattenStyle([{width, height}, styles.base, props.style]);
+    sources = [{uri: source.uri}];
+  } else {
+    style = flattenStyle([styles.base, props.style]);
+    sources = source;
+  }
+
+  const {onLoadStart, onLoad, onLoadEnd, onError} = props;
+  const nativeProps = merge(props, {
+    style,
+    shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),
+    src: sources,
+    headers: source.headers,
+    defaultSrc: defaultSource ? defaultSource.uri : null,
+    loadingIndicatorSrc: loadingIndicatorSource
+      ? loadingIndicatorSource.uri
+      : null,
+    ref: forwardedRef,
+  });
+
+  return (
+    <TextAncestor.Consumer>
+      {hasTextAncestor =>
+        hasTextAncestor ? (
+          <RCTTextInlineImage {...nativeProps} />
+        ) : (
+          <RKImage {...nativeProps} />
+        )
+      }
+    </TextAncestor.Consumer>
+  );
+};
+
+// $FlowFixMe - TODO T29156721 `React.forwardRef` is not defined in Flow, yet.
+Image = React.forwardRef(Image);
+
+/**
+ * Prefetches a remote image for later use by downloading it to the disk
+ * cache
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#prefetch
+ */
+Image.getSize = getSize;
+
+/**
+ * Prefetches a remote image for later use by downloading it to the disk
+ * cache
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#prefetch
+ */
+Image.prefetch = prefetch;
+
+/**
+ * Abort prefetch request.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#abortprefetch
+ */
+Image.abortPrefetch = abortPrefetch;
+
+/**
+ * Perform cache interrogation.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#querycache
+ */
+Image.queryCache = queryCache;
+
+/**
+ * Resolves an asset reference into an object.
+ *
+ * See https://facebook.github.io/react-native/docs/image.html#resolveassetsource
+ */
+Image.resolveAssetSource = resolveAssetSource;
+
+Image.propTypes = ImageProps;
+
+const styles = StyleSheet.create({
+  base: {
+    overflow: 'hidden',
+  },
+});
+
+module.exports = (Image: Class<ImageComponentType>);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index 7fdd4057047e..440bf3f2c775 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -1,9 +1,9 @@
 /**
-* Copyright (c) 2015-present, Facebook, Inc.
-*
-* This source code is licensed under the MIT license found in the
-* LICENSE file in the root directory of this source tree.
-*/
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
 
 package com.facebook.react.views.image;
 
@@ -63,29 +63,26 @@
 import javax.annotation.Nullable;
 
 /**
-* Wrapper class around Fresco's GenericDraweeView, enabling persisting props across multiple view
-* update and consistent processing of both static and network images.
-*/
+ * Wrapper class around Fresco's GenericDraweeView, enabling persisting props across multiple view
+ * update and consistent processing of both static and network images.
+ */
 public class ReactImageView extends GenericDraweeView {
 
   public static final int REMOTE_IMAGE_FADE_DURATION_MS = 300;
 
-  public static final String REMOTE_TRANSPARENT_BITMAP_URI =
-  "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAQAAAC1HAwCAAAAC0lEQVR42mNkYAAAAAYAAjCB0C8AAAAASUVORK5CYII=";
-
   private static float[] sComputedCornerRadii = new float[4];
 
   /*
-  * Implementation note re rounded corners:
-  *
-  * Fresco's built-in rounded corners only work for 'cover' resize mode -
-  * this is a limitation in Android itself. Fresco has a workaround for this, but
-  * it requires knowing the background color.
-  *
-  * So for the other modes, we use a postprocessor.
-  * Because the postprocessor uses a modified bitmap, that would just get cropped in
-  * 'cover' mode, so we fall back to Fresco's normal implementation.
-  */
+   * Implementation note re rounded corners:
+   *
+   * Fresco's built-in rounded corners only work for 'cover' resize mode -
+   * this is a limitation in Android itself. Fresco has a workaround for this, but
+   * it requires knowing the background color.
+   *
+   * So for the other modes, we use a postprocessor.
+   * Because the postprocessor uses a modified bitmap, that would just get cropped in
+   * 'cover' mode, so we fall back to Fresco's normal implementation.
+   */
   private static final Matrix sMatrix = new Matrix();
   private static final Matrix sInverse = new Matrix();
   private ImageResizeMethod mResizeMethod = ImageResizeMethod.AUTO;
@@ -94,12 +91,12 @@ private class RoundedCornerPostprocessor extends BasePostprocessor {
 
     void getRadii(Bitmap source, float[] computedCornerRadii, float[] mappedRadii) {
       mScaleType.getTransform(
-      sMatrix,
-      new Rect(0, 0, source.getWidth(), source.getHeight()),
-      source.getWidth(),
-      source.getHeight(),
-      0.0f,
-      0.0f);
+        sMatrix,
+        new Rect(0, 0, source.getWidth(), source.getHeight()),
+        source.getWidth(),
+        source.getHeight(),
+        0.0f,
+        0.0f);
       sMatrix.invert(sInverse);
 
       mappedRadii[0] = sInverse.mapRadius(computedCornerRadii[0]);
@@ -121,9 +118,9 @@ public void process(Bitmap output, Bitmap source) {
 
       output.setHasAlpha(true);
       if (FloatUtil.floatsEqual(sComputedCornerRadii[0], 0f) &&
-      FloatUtil.floatsEqual(sComputedCornerRadii[1], 0f) &&
-      FloatUtil.floatsEqual(sComputedCornerRadii[2], 0f) &&
-      FloatUtil.floatsEqual(sComputedCornerRadii[3], 0f)) {
+        FloatUtil.floatsEqual(sComputedCornerRadii[1], 0f) &&
+        FloatUtil.floatsEqual(sComputedCornerRadii[2], 0f) &&
+        FloatUtil.floatsEqual(sComputedCornerRadii[3], 0f)) {
         super.process(output, source);
         return;
       }
@@ -139,9 +136,9 @@ public void process(Bitmap output, Bitmap source) {
       Path pathForBorderRadius = new Path();
 
       pathForBorderRadius.addRoundRect(
-      new RectF(0, 0, source.getWidth(), source.getHeight()),
-      radii,
-      Path.Direction.CW);
+        new RectF(0, 0, source.getWidth(), source.getHeight()),
+        radii,
+        Path.Direction.CW);
 
       canvas.drawPath(pathForBorderRadius, paint);
     }
@@ -157,12 +154,12 @@ public CloseableReference<Bitmap> process(Bitmap source, PlatformBitmapFactory b
       final Rect destRect = new Rect(0, 0, getWidth(), getHeight());
 
       mScaleType.getTransform(
-      sTileMatrix,
-      destRect,
-      source.getWidth(),
-      source.getHeight(),
-      0.0f,
-      0.0f);
+        sTileMatrix,
+        destRect,
+        source.getWidth(),
+        source.getHeight(),
+        0.0f,
+        0.0f);
 
       Paint paint = new Paint();
       paint.setAntiAlias(true);
@@ -212,15 +209,15 @@ public CloseableReference<Bitmap> process(Bitmap source, PlatformBitmapFactory b
   // We can't specify rounding in XML, so have to do so here
   private static GenericDraweeHierarchy buildHierarchy(Context context) {
     return new GenericDraweeHierarchyBuilder(context.getResources())
-    .setRoundingParams(RoundingParams.fromCornersRadius(0))
-    .build();
+      .setRoundingParams(RoundingParams.fromCornersRadius(0))
+      .build();
   }
 
   public ReactImageView(
-  Context context,
-  AbstractDraweeControllerBuilder draweeControllerBuilder,
-  @Nullable GlobalImageLoadListener globalImageLoadListener,
-  @Nullable Object callerContext) {
+    Context context,
+    AbstractDraweeControllerBuilder draweeControllerBuilder,
+    @Nullable GlobalImageLoadListener globalImageLoadListener,
+    @Nullable Object callerContext) {
     super(context, buildHierarchy(context));
     mScaleType = ImageResizeMode.defaultValue();
     mDraweeControllerBuilder = draweeControllerBuilder;
@@ -241,29 +238,29 @@ public void setShouldNotifyLoadEvents(boolean shouldNotify) {
         @Override
         public void onSubmit(String id, Object callerContext) {
           mEventDispatcher.dispatchEvent(
-          new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_START));
+            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_START));
         }
 
         @Override
         public void onFinalImageSet(
-        String id,
-        @Nullable final ImageInfo imageInfo,
-        @Nullable Animatable animatable) {
+          String id,
+          @Nullable final ImageInfo imageInfo,
+          @Nullable Animatable animatable) {
           if (imageInfo != null) {
             mEventDispatcher.dispatchEvent(
-            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD,
-            mImageSource.getSource(), imageInfo.getWidth(), imageInfo.getHeight()));
+              new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD,
+                mImageSource.getSource(), imageInfo.getWidth(), imageInfo.getHeight()));
             mEventDispatcher.dispatchEvent(
-            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_END));
+              new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_END));
           }
         }
 
         @Override
         public void onFailure(String id, Throwable throwable) {
           mEventDispatcher.dispatchEvent(
-          new ImageLoadEvent(getId(), ImageLoadEvent.ON_ERROR));
+            new ImageLoadEvent(getId(), ImageLoadEvent.ON_ERROR));
           mEventDispatcher.dispatchEvent(
-          new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_END));
+            new ImageLoadEvent(getId(), ImageLoadEvent.ON_LOAD_END));
         }
       };
     }
@@ -341,10 +338,7 @@ public void setResizeMethod(ImageResizeMethod resizeMethod) {
 
   public void setSource(@Nullable ReadableArray sources) {
     mSources.clear();
-    if (sources == null || sources.size() == 0) {
-      ImageSource imageSource = new ImageSource(getContext(), REMOTE_TRANSPARENT_BITMAP_URI);
-      mSources.add(imageSource);
-    } else {
+    if (sources != null && sources.size() != 0) {
       // Optimize for the case where we have just one uri, case in which we don't need the sizes
       if (sources.size() == 1) {
         ReadableMap source = sources.getMap(0);
@@ -359,10 +353,10 @@ public void setSource(@Nullable ReadableArray sources) {
           ReadableMap source = sources.getMap(idx);
           String uri = source.getString("uri");
           ImageSource imageSource = new ImageSource(
-          getContext(),
-          uri,
-          source.getDouble("width"),
-          source.getDouble("height"));
+            getContext(),
+            uri,
+            source.getDouble("width"),
+            source.getDouble("height"));
           mSources.add(imageSource);
           if (Uri.EMPTY.equals(imageSource.getUri())) {
             warnImageSource(uri);
@@ -381,7 +375,7 @@ public void setDefaultSource(@Nullable String name) {
   public void setLoadingIndicatorSource(@Nullable String name) {
     Drawable drawable = ResourceDrawableIdHelper.getInstance().getResourceDrawable(getContext(), name);
     mLoadingImageDrawable =
-    drawable != null ? (Drawable) new AutoRotateDrawable(drawable, 1000) : null;
+      drawable != null ? (Drawable) new AutoRotateDrawable(drawable, 1000) : null;
     mIsDirty = true;
   }
 
@@ -446,8 +440,8 @@ public void maybeUpdateView() {
     }
 
     boolean usePostprocessorScaling =
-    mScaleType != ScalingUtils.ScaleType.CENTER_CROP &&
-    mScaleType != ScalingUtils.ScaleType.FOCUS_CROP;
+      mScaleType != ScalingUtils.ScaleType.CENTER_CROP &&
+        mScaleType != ScalingUtils.ScaleType.FOCUS_CROP;
 
     RoundingParams roundingParams = hierarchy.getRoundingParams();
 
@@ -474,9 +468,9 @@ public void maybeUpdateView() {
     }
     hierarchy.setRoundingParams(roundingParams);
     hierarchy.setFadeDuration(
-    mFadeDurationMs >= 0
-    ? mFadeDurationMs
-    : mImageSource.isResource() ? 0 : REMOTE_IMAGE_FADE_DURATION_MS);
+      mFadeDurationMs >= 0
+        ? mFadeDurationMs
+        : mImageSource.isResource() ? 0 : REMOTE_IMAGE_FADE_DURATION_MS);
 
     List<Postprocessor> postprocessors = new LinkedList<>();
     if (usePostprocessorScaling) {
@@ -493,10 +487,10 @@ public void maybeUpdateView() {
     ResizeOptions resizeOptions = doResize ? new ResizeOptions(getWidth(), getHeight()) : null;
 
     ImageRequestBuilder imageRequestBuilder = ImageRequestBuilder.newBuilderWithSource(mImageSource.getUri())
-    .setPostprocessor(postprocessor)
-    .setResizeOptions(resizeOptions)
-    .setAutoRotateEnabled(true)
-    .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled);
+      .setPostprocessor(postprocessor)
+      .setResizeOptions(resizeOptions)
+      .setAutoRotateEnabled(true)
+      .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled);
 
     ImageRequest imageRequest = ReactNetworkImageRequest.fromBuilderWithHeaders(imageRequestBuilder, mHeaders);
 
@@ -508,19 +502,19 @@ public void maybeUpdateView() {
     mDraweeControllerBuilder.reset();
 
     mDraweeControllerBuilder
-    .setAutoPlayAnimations(true)
-    .setCallerContext(mCallerContext)
-    .setOldController(getController())
-    .setImageRequest(imageRequest);
+      .setAutoPlayAnimations(true)
+      .setCallerContext(mCallerContext)
+      .setOldController(getController())
+      .setImageRequest(imageRequest);
 
     if (mCachedImageSource != null) {
       ImageRequest cachedImageRequest =
-      ImageRequestBuilder.newBuilderWithSource(mCachedImageSource.getUri())
-      .setPostprocessor(postprocessor)
-      .setResizeOptions(resizeOptions)
-      .setAutoRotateEnabled(true)
-      .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled)
-      .build();
+        ImageRequestBuilder.newBuilderWithSource(mCachedImageSource.getUri())
+          .setPostprocessor(postprocessor)
+          .setResizeOptions(resizeOptions)
+          .setAutoRotateEnabled(true)
+          .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled)
+          .build();
       mDraweeControllerBuilder.setLowResImageRequest(cachedImageRequest);
     }
 
@@ -560,8 +554,8 @@ protected void onSizeChanged(int w, int h, int oldw, int oldh) {
   }
 
   /**
-  * ReactImageViews only render a single image.
-  */
+   * ReactImageViews only render a single image.
+   */
   @Override
   public boolean hasOverlappingRendering() {
     return false;
@@ -578,11 +572,11 @@ private boolean isTiled() {
   private void setSourceImage() {
     mImageSource = null;
     if (mSources.isEmpty()) {
-      ImageSource imageSource = new ImageSource(getContext(), REMOTE_TRANSPARENT_BITMAP_URI);
-      mSources.add(imageSource);
-    } else if (hasMultipleSources()) {
+      return;
+    }
+    if (hasMultipleSources()) {
       MultiSourceResult multiSource =
-      MultiSourceHelper.getBestSourceForSize(getWidth(), getHeight(), mSources);
+        MultiSourceHelper.getBestSourceForSize(getWidth(), getHeight(), mSources);
       mImageSource = multiSource.getBestResult();
       mCachedImageSource = multiSource.getBestResultInCache();
       return;
@@ -597,8 +591,8 @@ private boolean shouldResize(ImageSource imageSource) {
     // has no control over the original size
     if (mResizeMethod == ImageResizeMethod.AUTO) {
       return
-      UriUtil.isLocalContentUri(imageSource.getUri()) ||
-      UriUtil.isLocalFileUri(imageSource.getUri());
+        UriUtil.isLocalContentUri(imageSource.getUri()) ||
+          UriUtil.isLocalFileUri(imageSource.getUri());
     } else if (mResizeMethod == ImageResizeMethod.RESIZE) {
       return true;
     } else {
@@ -609,9 +603,10 @@ private boolean shouldResize(ImageSource imageSource) {
   private void warnImageSource(String uri) {
     if (ReactBuildConfig.DEBUG) {
       Toast.makeText(
-      getContext(),
-      "Warning: Image source \"" + uri + "\" doesn't exist",
-      Toast.LENGTH_SHORT).show();
+        getContext(),
+        "Warning: Image source \"" + uri + "\" doesn't exist",
+        Toast.LENGTH_SHORT).show();
     }
   }
 }
+

From b569154ae633d7f3c6b4f148b108f05aef742bf9 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Mon, 25 Jun 2018 16:49:20 -0700
Subject: [PATCH 0916/1109] bump build tools to 26.0.3 (#19831)

Summary:
This will bump android build tools to 26.0.3, and will remove warning about newer version of build tools in Android Studio, thus improve developer experience.
Closes https://github.com/facebook/react-native/pull/19831

Differential Revision: D8620094

Pulled By: hramos

fbshipit-source-id: fa1c6739bb7556736c1b323acea88fe87e82f4d7
---
 RNTester/android/app/build.gradle                       | 2 +-
 ReactAndroid/build.gradle                               | 2 +-
 local-cli/templates/HelloWorld/android/app/build.gradle | 2 +-
 scripts/.tests.env                                      | 2 +-
 4 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index fdaa2753034b..df3944cfb72e 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -85,7 +85,7 @@ def enableProguardInReleaseBuilds = true
 
 android {
     compileSdkVersion 26
-    buildToolsVersion "26.0.2"
+    buildToolsVersion "26.0.3"
 
     defaultConfig {
         applicationId "com.facebook.react.uiapp"
diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 601071cdec1f..3b9f7189ef91 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -246,7 +246,7 @@ task packageReactNdkLibsForBuck(dependsOn: packageReactNdkLibs, type: Copy) {
 
 android {
     compileSdkVersion 26
-    buildToolsVersion "26.0.2"
+    buildToolsVersion "26.0.3"
 
     defaultConfig {
         minSdkVersion 16
diff --git a/local-cli/templates/HelloWorld/android/app/build.gradle b/local-cli/templates/HelloWorld/android/app/build.gradle
index 2fad86f24a06..131424b8c333 100644
--- a/local-cli/templates/HelloWorld/android/app/build.gradle
+++ b/local-cli/templates/HelloWorld/android/app/build.gradle
@@ -95,7 +95,7 @@ def enableProguardInReleaseBuilds = false
 
 android {
     compileSdkVersion 26
-    buildToolsVersion "26.0.2"
+    buildToolsVersion "26.0.3"
 
     defaultConfig {
         applicationId "com.helloworld"
diff --git a/scripts/.tests.env b/scripts/.tests.env
index 83e38520d58b..e9d918ec476e 100644
--- a/scripts/.tests.env
+++ b/scripts/.tests.env
@@ -4,7 +4,7 @@
 
 ## ANDROID ##
 # Android SDK Build Tools revision
-export ANDROID_SDK_BUILD_TOOLS_REVISION=26.0.2
+export ANDROID_SDK_BUILD_TOOLS_REVISION=26.0.3
 # Android API Level we build with
 export ANDROID_SDK_BUILD_API_LEVEL="26"
 # Google APIs for Android level

From b5dc45420a0d3aa54d2d2075d7f14ff1835df78a Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Mon, 25 Jun 2018 17:07:35 -0700
Subject: [PATCH 0917/1109] bump NDK APP_PLATFORM to android-16 (#19830)

Summary:
This PR will bump NDK APP_PLATFORM to android-16. Below is the excerpt from NDK documentation

> This variable contains the minimum Android platform version you want to support. For example, a value of android-15 specifies that your library uses APIs that are not available below Android 4.0.3 (API level 15) and can't be used on devices running a lower platform version. For a complete list of platform names and corresponding Android system images, see Android NDK Native APIs.
Closes https://github.com/facebook/react-native/pull/19830

Differential Revision: D8620017

Pulled By: hramos

fbshipit-source-id: 0b5578f130938e3ddae03fb855784193183243cf
---
 ReactAndroid/src/main/jni/Application.mk | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/jni/Application.mk b/ReactAndroid/src/main/jni/Application.mk
index 2a1e94dc0494..4f1b600b595b 100644
--- a/ReactAndroid/src/main/jni/Application.mk
+++ b/ReactAndroid/src/main/jni/Application.mk
@@ -1,7 +1,7 @@
 APP_BUILD_SCRIPT := Android.mk
 
 APP_ABI := armeabi-v7a x86
-APP_PLATFORM := android-9
+APP_PLATFORM := android-16
 
 APP_MK_DIR := $(dir $(lastword $(MAKEFILE_LIST)))
 

From 86fb5213aebf29bab1f4ec50cf7a3217a23f188c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Mon, 25 Jun 2018 17:10:39 -0700
Subject: [PATCH 0918/1109] Bump Buck to v2018.06.25.01 (#19882)

Summary:
Fixes #19881
Closes https://github.com/facebook/react-native/pull/19882

Differential Revision: D8627994

Pulled By: hramos

fbshipit-source-id: ae43f2dd8dd5fac88590eeb4dddb18ebe5085359
---
 .circleci/config.yml                  | 6 +++---
 ContainerShip/Dockerfile.android-base | 2 +-
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 5c79711b5d77..4803f45845c7 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -67,12 +67,12 @@ aliases:
 
   - &restore-cache-buck
     keys:
-      - v3-buck-{{ arch }}-v2018.03.26.01
+      - v3-buck-{{ arch }}-v2018.06.25.01
   - &save-cache-buck
     paths:
       - ~/buck
       - ~/okbuck
-    key: v3-buck-{{ arch }}-v2018.03.26.01
+    key: v3-buck-{{ arch }}-v2018.06.25.01
 
   - &restore-cache-watchman
     keys:
@@ -145,7 +145,7 @@ aliases:
     name: Install BUCK
     command: |
       if [[ ! -e ~/buck ]]; then
-        git clone https://github.com/facebook/buck.git ~/buck --branch v2018.03.26.01 --depth=1
+        git clone https://github.com/facebook/buck.git ~/buck --branch v2018.06.25.01 --depth=1
       fi
       cd ~/buck && ant
       buck --version
diff --git a/ContainerShip/Dockerfile.android-base b/ContainerShip/Dockerfile.android-base
index b630b396e959..78cb4dc22ca4 100644
--- a/ContainerShip/Dockerfile.android-base
+++ b/ContainerShip/Dockerfile.android-base
@@ -20,7 +20,7 @@ LABEL maintainer="Héctor Ramos <hector@fb.com>"
 ARG SDK_VERSION=sdk-tools-linux-3859397.zip
 ARG ANDROID_BUILD_VERSION=26
 ARG ANDROID_TOOLS_VERSION=26.0.3
-ARG BUCK_VERSION=v2018.03.26.01
+ARG BUCK_VERSION=v2018.06.25.01
 ARG NDK_VERSION=10e
 ARG NODE_VERSION=8.10.0
 ARG WATCHMAN_VERSION=4.9.0

From 60827c63387cd7d5b9679461ea41926211a7bf6d Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Mon, 25 Jun 2018 17:14:58 -0700
Subject: [PATCH 0919/1109] use same signing config for debug build (#19760)

Summary:
use same signing config for debug build
pass all current ci.
none
 [GENERAL] [INTERNAL] [RNTester] - use same signing config for debug build .
Closes https://github.com/facebook/react-native/pull/19760

Differential Revision: D8623409

Pulled By: hramos

fbshipit-source-id: 420842db3f954101ee8f771aaf0b021bea385741
---
 RNTester/android/app/build.gradle | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index df3944cfb72e..42c3eb81c59f 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -114,6 +114,9 @@ android {
         }
     }
     buildTypes {
+        debug {
+            signingConfig signingConfigs.release
+        }
         release {
             minifyEnabled enableProguardInReleaseBuilds
             proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'

From 6bbc1b7b9631e9c284eda5a7a4dd48efefcac1ff Mon Sep 17 00:00:00 2001
From: iyegoroff <iegoroff@gmail.com>
Date: Mon, 25 Jun 2018 18:11:33 -0700
Subject: [PATCH 0920/1109] Show packager error stack (#19705)

Summary:
Motivation: get more info from packager errors to easier debug them

add `throw new Error('error')` here https://github.com/iyegoroff/react-native/blob/635f2740c28da594f236d4227b6450fddef4b599/local-cli/cliEntry.js#L116 and run
`react-native start` to see error stack
<!--
  Required: Write your test plan here. If you changed any code, please provide us with
  clear instructions on how you verified your changes work. Bonus points for screenshots and videos!
-->
[CLI] [ENHANCEMENT] [local-cli/cliEntry.js] - Show packager error stack

<!--
  **INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

    CATEGORY
  [----------]      TYPE
  [ CLI      ] [-------------]    LOCATION
  [ DOCS     ] [ BREAKING    ] [-------------]
  [ GENERAL  ] [ BUGFIX      ] [ {Component} ]
  [ INTERNAL ] [ ENHANCEMENT ] [ {Filename}  ]
  [ IOS      ] [ FEATURE     ] [ {Directory} ]   |-----------|
  [ ANDROID  ] [ MINOR       ] [ {Framework} ] - | {Message} |
  [----------] [-------------] [-------------]   |-----------|

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
Closes https://github.com/facebook/react-native/pull/19705

Differential Revision: D8628322

Pulled By: hramos

fbshipit-source-id: 531217addea122d9761e4f5dd5c666a3b4b56a38
---
 local-cli/cliEntry.js | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/local-cli/cliEntry.js b/local-cli/cliEntry.js
index 952ccd29bcf7..d342e9ed0d53 100644
--- a/local-cli/cliEntry.js
+++ b/local-cli/cliEntry.js
@@ -38,6 +38,10 @@ const handleError = err => {
   console.error();
   console.error(err.message || err);
   console.error();
+  if (err.stack) {
+    console.error(err.stack);
+    console.error();
+  }
   process.exit(1);
 };
 

From a07b66026da6168f59aafb808cd625ab868a6d00 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 25 Jun 2018 21:41:04 -0700
Subject: [PATCH 0921/1109] Improve performance for node reordering in
 FabricReconciler

Summary: This diff improves performance of re-layout and delivery of OnLayout events for Fabric surfaces.

Reviewed By: fkgozali

Differential Revision: D8622718

fbshipit-source-id: 703b6c3ca70b570e8fb79ae1c1e8d9e8fcd38658
---
 .../main/java/com/facebook/react/fabric/FabricReconciler.java   | 2 +-
 .../java/com/facebook/react/uimanager/ReactShadowNodeImpl.java  | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
index e01e0c9d6831..de87cb2c55d4 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricReconciler.java
@@ -88,7 +88,7 @@ private void manageChildren(
     for (int k = firstRemovedOrAddedViewIndex; k < newList.size(); k++) {
       ReactShadowNode newNode = newList.get(k);
       if (newNode.isVirtual()) continue;
-      enqueueUpdateProperties(newNode, null);
+      enqueueUpdateProperties(newNode, newNode.getOriginalReactShadowNode());
       viewsToAdd.add(new ViewAtIndex(newNode.getReactTag(), k));
       List previousChildrenList = newNode.getOriginalReactShadowNode() == null ? null : newNode.getOriginalReactShadowNode().getChildrenList();
       manageChildren(newNode, previousChildrenList, newNode.getChildrenList());
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
index ed988f1cc556..706e005d0eee 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ReactShadowNodeImpl.java
@@ -1221,8 +1221,8 @@ private void assertNotSealed() {
     }
   }
 
+  @Override
   public void updateScreenLayout(ReactShadowNode prevNode) {
-    assertNotSealed();
     mScreenHeight = prevNode.getScreenHeight();
     mScreenWidth = prevNode.getScreenWidth();
     mScreenX = prevNode.getScreenX();

From fb2ec1ea47c53c2e7b873acb1cb46192ac74274e Mon Sep 17 00:00:00 2001
From: Pascal Hartig <realpassy@fb.com>
Date: Tue, 26 Jun 2018 04:57:04 -0700
Subject: [PATCH 0922/1109] Upgrade fbjni

Summary:
Sync fbjni with `libaries/fbjni`.

This includes a hack to fix a deadlock we found for cmake-debug variants only. This still gets us back in sync with other fbjni consumers which is going to save us trouble in the future if Yoga ever wants to make use of a newer feature.

Manual changes made in addition to the hand-crafted CMakeLists and cxx buck rules:

- `jni::isObjectRefType` has SDK lookup disabled.
- `fbjni/` path is changed back to `fb/` to retain compatibility with Yoga.

Reviewed By: priteshrnandgaonkar

Differential Revision: D8531991

fbshipit-source-id: 776f519e2e5f9bea37f55990348f7ed81c4860b4
---
 .../src/main/jni/first-party/yogajni/jni/YGJNI.cpp     | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
index 69cbb38115c4..2bc0ee8bd21b 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #include <fb/fbjni.h>
 #include <yoga/YGNode.h>
 #include <yoga/Yoga.h>

From 14cd15ef54dc944fcb090eba924e4c92db14a445 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Tue, 26 Jun 2018 07:38:22 -0700
Subject: [PATCH 0923/1109] Enforce component name

Summary: When snapshotting, do not get affected by the building process.

Reviewed By: rafeca

Differential Revision: D8638527

fbshipit-source-id: 8335fc55c0c85f2ff110db338a5000c7af4b29aa
---
 jest/mockComponent.js | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/jest/mockComponent.js b/jest/mockComponent.js
index e94d467a6116..fdd89e82d740 100644
--- a/jest/mockComponent.js
+++ b/jest/mockComponent.js
@@ -17,6 +17,8 @@ module.exports = (moduleName, instanceMethods) => {
     typeof RealComponent === 'function' ? RealComponent : React.Component;
 
   const Component = class extends SuperClass {
+    static displayName = 'Component';
+
     render() {
       const name =
         RealComponent.displayName ||

From 04366a9867f73accf21c69ad6d5d6dd726696ef4 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Tue, 26 Jun 2018 10:40:48 -0700
Subject: [PATCH 0924/1109] clean buck binary_jar warnings (#19769)

Summary:
This PR clears buck binary_jar warnings on CI.

CI is green https://circleci.com/gh/dulmandakh/react-native/458

Will see no binary_jar warnings on CI
Closes https://github.com/facebook/react-native/pull/19769

Reviewed By: mdvacca

Differential Revision: D8474558

Pulled By: hramos

fbshipit-source-id: a1e34a749218a6f87576475e49cbab52b0d3fafb
---
 .../src/test/java/com/facebook/powermock/BUCK | 48 +++++++-------
 .../libraries/fresco/fresco-react-native/BUCK |  4 +-
 .../src/main/libraries/textlayoutbuilder/BUCK |  4 +-
 .../android/support-annotations/BUCK          |  4 +-
 .../main/third-party/android/support/v4/BUCK  | 64 +++++++++----------
 .../src/main/third-party/java/asm/BUCK        | 20 +++---
 .../src/main/third-party/java/fest/BUCK       |  8 +--
 .../src/main/third-party/java/javapoet/BUCK   |  4 +-
 .../src/main/third-party/java/jsr-305/BUCK    |  4 +-
 .../src/main/third-party/java/jsr-330/BUCK    |  4 +-
 .../src/main/third-party/java/junit/BUCK      |  8 +--
 .../src/main/third-party/java/mockito/BUCK    |  8 +--
 .../src/main/third-party/java/okhttp/BUCK     |  8 +--
 .../src/main/third-party/java/okio/BUCK       |  4 +-
 .../java/robolectric3/robolectric/BUCK        | 60 ++++++++---------
 .../src/main/third-party/java/sqlite/BUCK     |  4 +-
 16 files changed, 128 insertions(+), 128 deletions(-)

diff --git a/ReactAndroid/src/main/libraries/fbcore/src/test/java/com/facebook/powermock/BUCK b/ReactAndroid/src/main/libraries/fbcore/src/test/java/com/facebook/powermock/BUCK
index c4360ce160f0..768455a12142 100644
--- a/ReactAndroid/src/main/libraries/fbcore/src/test/java/com/facebook/powermock/BUCK
+++ b/ReactAndroid/src/main/libraries/fbcore/src/test/java/com/facebook/powermock/BUCK
@@ -21,144 +21,144 @@ rn_android_library(
 
 rn_prebuilt_jar(
     name = "powermock-core",
-    binary_jar = ":download-powermock-core",
+    binary_jar = ":download-powermock-core.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-powermock-core",
+    name = "download-powermock-core.jar",
     sha1 = "ea04e79244e19dcf0c3ccf6863c5b028b4b58c9c",
     url = "mvn:org.powermock:powermock-core:jar:1.6.2",
 )
 
 rn_prebuilt_jar(
     name = "powermock-api-mockito",
-    binary_jar = ":download-powermock-api-mockito",
+    binary_jar = ":download-powermock-api-mockito.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-powermock-api-mockito",
+    name = "download-powermock-api-mockito.jar",
     sha1 = "c213230ae20a7b422f3d622a261d0e3427d2464c",
     url = "mvn:org.powermock:powermock-api-mockito:jar:1.6.2",
 )
 
 rn_prebuilt_jar(
     name = "powermock-api-support",
-    binary_jar = ":download-powermock-api-support",
+    binary_jar = ":download-powermock-api-support.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-powermock-api-support",
+    name = "download-powermock-api-support.jar",
     sha1 = "93b21413b4ee99b7bc0dd34e1416fdca96866aaf",
     url = "mvn:org.powermock:powermock-api-support:jar:1.6.2",
 )
 
 rn_prebuilt_jar(
     name = "powermock-module-junit4-rule",
-    binary_jar = ":download-powermock-module-junit4-rule",
+    binary_jar = ":download-powermock-module-junit4-rule.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-powermock-module-junit4-rule",
+    name = "download-powermock-module-junit4-rule.jar",
     sha1 = "4847638c5729b9f203e21144b0bdb5d34d888473",
     url = "mvn:org.powermock:powermock-module-junit4-rule:jar:1.6.2",
 )
 
 rn_prebuilt_jar(
     name = "powermock-classloading-xstream",
-    binary_jar = ":download-powermock-classloading-xstream",
+    binary_jar = ":download-powermock-classloading-xstream.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-powermock-classloading-xstream",
+    name = "download-powermock-classloading-xstream.jar",
     sha1 = "3ced31cd7024fe365b9f3c8082d22c02434577da",
     url = "mvn:org.powermock:powermock-classloading-xstream:jar:1.6.2",
 )
 
 rn_prebuilt_jar(
     name = "powermock-classloading-base",
-    binary_jar = ":download-powermock-classloading-base",
+    binary_jar = ":download-powermock-classloading-base.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-powermock-classloading-base",
+    name = "download-powermock-classloading-base.jar",
     sha1 = "c8bfc10731a02d3b241892cf2c334a754d473ca7",
     url = "mvn:org.powermock:powermock-classloading-base:jar:1.6.2",
 )
 
 rn_prebuilt_jar(
     name = "xstream",
-    binary_jar = ":download-xstream",
+    binary_jar = ":download-xstream.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-xstream",
+    name = "download-xstream.jar",
     sha1 = "97e5013f391487cce4de6b0eebcde21549e91872",
     url = "mvn:com.thoughtworks.xstream:xstream:jar:1.4.2",
 )
 
 rn_prebuilt_jar(
     name = "powermock-reflect",
-    binary_jar = ":download-powermock-reflect",
+    binary_jar = ":download-powermock-reflect.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-powermock-reflect",
+    name = "download-powermock-reflect.jar",
     sha1 = "1af1bbd1207c3ecdcf64973e6f9d57dcd17cc145",
     url = "mvn:org.powermock:powermock-reflect:jar:1.6.2",
 )
 
 rn_prebuilt_jar(
     name = "javassist",
-    binary_jar = ":download-javassist",
+    binary_jar = ":download-javassist.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-javassist",
+    name = "download-javassist.jar",
     sha1 = "a9cbcdfb7e9f86fbc74d3afae65f2248bfbf82a0",
     url = "mvn:org.javassist:javassist:jar:3.20.0-GA",
 )
 
 rn_prebuilt_jar(
     name = "mockito-all",
-    binary_jar = ":download-mockito-all",
+    binary_jar = ":download-mockito-all.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-mockito-all",
+    name = "download-mockito-all.jar",
     sha1 = "539df70269cc254a58cccc5d8e43286b4a73bf30",
     url = "mvn:org.mockito:mockito-all:jar:1.10.19",
 )
 
 rn_prebuilt_jar(
     name = "xmlpull",
-    binary_jar = ":download-xmlpull",
+    binary_jar = ":download-xmlpull.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-xmlpull",
+    name = "download-xmlpull.jar",
     sha1 = "2b8e230d2ab644e4ecaa94db7cdedbc40c805dfa",
     url = "mvn:xmlpull:xmlpull:jar:1.1.3.1",
 )
 
 rn_prebuilt_jar(
     name = "xpp3",
-    binary_jar = ":download-xpp3",
+    binary_jar = ":download-xpp3.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-xpp3",
+    name = "download-xpp3.jar",
     sha1 = "19d4e90b43059058f6e056f794f0ea4030d60b86",
     url = "mvn:xpp3:xpp3_min:jar:1.1.4c",
 )
diff --git a/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK b/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
index db1216a0fea1..e81c585b889e 100644
--- a/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
+++ b/ReactAndroid/src/main/libraries/fresco/fresco-react-native/BUCK
@@ -60,12 +60,12 @@ remote_file(
 
 rn_prebuilt_jar(
     name = "bolts",
-    binary_jar = ":download-bolts",
+    binary_jar = ":download-bolts.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-bolts",
+    name = "download-bolts.jar",
     sha1 = "d85884acf6810a3bbbecb587f239005cbc846dc4",
     url = "mvn:com.parse.bolts:bolts-tasks:jar:1.4.0",
 )
diff --git a/ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK b/ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK
index 748dfff536a6..60baf8edc408 100644
--- a/ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK
+++ b/ReactAndroid/src/main/libraries/textlayoutbuilder/BUCK
@@ -23,12 +23,12 @@ remote_file(
 
 rn_prebuilt_jar(
     name = "staticlayoutproxy",
-    binary_jar = ":staticlayoutproxy-jar",
+    binary_jar = ":staticlayoutproxy.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "staticlayoutproxy-jar",
+    name = "staticlayoutproxy.jar",
     sha1 = "f162442a19fff13995fbd51ba414d9ee05579080",
     url = "mvn:com.facebook.fbui.textlayoutbuilder:staticlayout-proxy:jar:1.0",
 )
diff --git a/ReactAndroid/src/main/third-party/android/support-annotations/BUCK b/ReactAndroid/src/main/third-party/android/support-annotations/BUCK
index dcffb71746b6..cad12896cee5 100644
--- a/ReactAndroid/src/main/third-party/android/support-annotations/BUCK
+++ b/ReactAndroid/src/main/third-party/android/support-annotations/BUCK
@@ -1,11 +1,11 @@
 prebuilt_jar(
     name = "android-support-annotations",
-    binary_jar = ":support-annotations-binary-aar",
+    binary_jar = ":support-annotations-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "support-annotations-binary-aar",
+    name = "support-annotations-binary.jar",
     sha1 = "0814258103cf26a15fcc26ecce35f5b7d24b73f8",
     url = "mvn:com.android.support:support-annotations:jar:26.1.0",
 )
diff --git a/ReactAndroid/src/main/third-party/android/support/v4/BUCK b/ReactAndroid/src/main/third-party/android/support/v4/BUCK
index 39f58e962842..e816510b9a80 100644
--- a/ReactAndroid/src/main/third-party/android/support/v4/BUCK
+++ b/ReactAndroid/src/main/third-party/android/support/v4/BUCK
@@ -1,26 +1,26 @@
 android_library(
     name = "lib-support-v4",
+    visibility = ["PUBLIC"],
     exported_deps = [
-      ":lib-support-v4-support-compat",
-      ":lib-support-v4-support-core-utils",
-      ":lib-support-v4-support-core-ui",
-      ":lib-support-v4-support-media-compat",
-      ":lib-support-v4-support-fragment",
-      ":android-lifecycle-runtime",
-      ":android-lifecycle-common.jar",
-      ":android-lifecycle-core.jar"
+        ":android-lifecycle-common",
+        ":android-lifecycle-core",
+        ":android-lifecycle-runtime",
+        ":lib-support-v4-support-compat",
+        ":lib-support-v4-support-core-ui",
+        ":lib-support-v4-support-core-utils",
+        ":lib-support-v4-support-fragment",
+        ":lib-support-v4-support-media-compat",
     ],
-    visibility = ["PUBLIC"],
 )
 
 prebuilt_jar(
-    name = "android-lifecycle-common.jar",
-    binary_jar = ":android-lifecycle-common-jar"
+    name = "android-lifecycle-common",
+    binary_jar = ":android-lifecycle-common.jar",
 )
 
 prebuilt_jar(
-    name = "android-lifecycle-core.jar",
-    binary_jar = ":android-lifecycle-core-jar"
+    name = "android-lifecycle-core",
+    binary_jar = ":android-lifecycle-core.jar",
 )
 
 android_prebuilt_aar(
@@ -54,21 +54,21 @@ android_prebuilt_aar(
 )
 
 remote_file(
-  name = "android-lifecycle-runtime-aar",
-  sha1 = "30c60a8a357ee1321ffd0c9f08ef54b24045cd10",
-  url = "mvn:android.arch.lifecycle:runtime:aar:1.0.0"
+    name = "android-lifecycle-runtime-aar",
+    sha1 = "30c60a8a357ee1321ffd0c9f08ef54b24045cd10",
+    url = "mvn:android.arch.lifecycle:runtime:aar:1.0.0",
 )
 
 remote_file(
-  name = "android-lifecycle-common-jar",
-  sha1 = "e414a4cb28434e25c4f6aa71426eb20cf4874ae9",
-  url = "mvn:android.arch.lifecycle:common:jar:1.0.0"
+    name = "android-lifecycle-common.jar",
+    sha1 = "e414a4cb28434e25c4f6aa71426eb20cf4874ae9",
+    url = "mvn:android.arch.lifecycle:common:jar:1.0.0",
 )
 
 remote_file(
-  name = "android-lifecycle-core-jar",
-  sha1 = "a2d487452376193fc8c103dd2b9bd5f2b1b44563",
-  url = "mvn:android.arch.core:common:jar:1.0.0"
+    name = "android-lifecycle-core.jar",
+    sha1 = "a2d487452376193fc8c103dd2b9bd5f2b1b44563",
+    url = "mvn:android.arch.core:common:jar:1.0.0",
 )
 
 remote_file(
@@ -84,19 +84,19 @@ remote_file(
 )
 
 remote_file(
-  name = "lib-support-v4-support-core-ui-aar",
-  sha1 = "e306308d54052a1ded7bf9c2f5c2fdf5152a1f22",
-  url = "mvn:com.android.support:support-core-ui:aar:26.1.0",
+    name = "lib-support-v4-support-core-ui-aar",
+    sha1 = "e306308d54052a1ded7bf9c2f5c2fdf5152a1f22",
+    url = "mvn:com.android.support:support-core-ui:aar:26.1.0",
 )
 
 remote_file(
-  name = "lib-support-v4-support-media-compat-aar",
-  sha1 = "09fb587f27cde19aa8f2e50c5c9ee645d9aec44d",
-  url = "mvn:com.android.support:support-media-compat:aar:26.1.0",
+    name = "lib-support-v4-support-media-compat-aar",
+    sha1 = "09fb587f27cde19aa8f2e50c5c9ee645d9aec44d",
+    url = "mvn:com.android.support:support-media-compat:aar:26.1.0",
 )
 
 remote_file(
-  name = "lib-support-v4-support-fragment-aar",
-  sha1 = "ddacf369bb98dd6558606558de8ddcd53895cf91",
-  url = "mvn:com.android.support:support-fragment:aar:26.1.0",
-)
\ No newline at end of file
+    name = "lib-support-v4-support-fragment-aar",
+    sha1 = "ddacf369bb98dd6558606558de8ddcd53895cf91",
+    url = "mvn:com.android.support:support-fragment:aar:26.1.0",
+)
diff --git a/ReactAndroid/src/main/third-party/java/asm/BUCK b/ReactAndroid/src/main/third-party/java/asm/BUCK
index 856081a83fd0..ab6a14a06d6c 100644
--- a/ReactAndroid/src/main/third-party/java/asm/BUCK
+++ b/ReactAndroid/src/main/third-party/java/asm/BUCK
@@ -14,60 +14,60 @@ rn_android_library(
 
 rn_prebuilt_jar(
     name = "asm-core",
-    binary_jar = ":download-asm",
+    binary_jar = ":download-asm.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-asm",
+    name = "download-asm.jar",
     sha1 = "2fd56467a018aafe6ec6a73ccba520be4a7e1565",
     url = "mvn:org.ow2.asm:asm:jar:5.0.1",
 )
 
 rn_prebuilt_jar(
     name = "asm-commons",
-    binary_jar = ":download-asm-commons",
+    binary_jar = ":download-asm-commons.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-asm-commons",
+    name = "download-asm-commons.jar",
     sha1 = "7b7147a390a93a14d2edfdcf3f7b0e87a0939c3e",
     url = "mvn:org.ow2.asm:asm-commons:jar:5.0.1",
 )
 
 rn_prebuilt_jar(
     name = "asm-tree",
-    binary_jar = ":download-asm-tree",
+    binary_jar = ":download-asm-tree.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-asm-tree",
+    name = "download-asm-tree.jar",
     sha1 = "1b1e6e9d869acd704056d0a4223071a511c619e6",
     url = "mvn:org.ow2.asm:asm-tree:jar:5.0.1",
 )
 
 rn_prebuilt_jar(
     name = "asm-util",
-    binary_jar = ":download-asm-util",
+    binary_jar = ":download-asm-util.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-asm-util",
+    name = "download-asm-util.jar",
     sha1 = "7c8caddfbd0b2d7b844f8fcc75175b9cb9cf4724",
     url = "mvn:org.ow2.asm:asm-util:jar:5.0.1",
 )
 
 rn_prebuilt_jar(
     name = "asm-analysis",
-    binary_jar = ":download-asm-analysis",
+    binary_jar = ":download-asm-analysis.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-asm-analysis",
+    name = "download-asm-analysis.jar",
     sha1 = "e286fbee48efacb4e7c175f7948d9d8b2ab52352",
     url = "mvn:org.ow2.asm:asm-analysis:jar:5.0.1",
 )
diff --git a/ReactAndroid/src/main/third-party/java/fest/BUCK b/ReactAndroid/src/main/third-party/java/fest/BUCK
index 576ff7eddd53..49161934e04f 100644
--- a/ReactAndroid/src/main/third-party/java/fest/BUCK
+++ b/ReactAndroid/src/main/third-party/java/fest/BUCK
@@ -11,24 +11,24 @@ rn_android_library(
 
 rn_prebuilt_jar(
     name = "fest-core",
-    binary_jar = ":fest-binary-jar",
+    binary_jar = ":fest-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "fest-binary-jar",
+    name = "fest-binary.jar",
     sha1 = "cb7c91cf614901928ae405f19d9bcdedf82781db",
     url = "mvn:org.easytesting:fest-assert-core:jar:2.0M10",
 )
 
 rn_prebuilt_jar(
     name = "fest-util",
-    binary_jar = ":fest-util-binary-jar",
+    binary_jar = ":fest-util-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "fest-util-binary-jar",
+    name = "fest-util-binary.jar",
     sha1 = "c4a8d7305b23b8d043be12c979813b096df11f44",
     url = "mvn:org.easytesting:fest-util:jar:1.2.5",
 )
diff --git a/ReactAndroid/src/main/third-party/java/javapoet/BUCK b/ReactAndroid/src/main/third-party/java/javapoet/BUCK
index 00541500c3c7..769b174f34e5 100644
--- a/ReactAndroid/src/main/third-party/java/javapoet/BUCK
+++ b/ReactAndroid/src/main/third-party/java/javapoet/BUCK
@@ -1,11 +1,11 @@
 prebuilt_jar(
     name = "javapoet",
-    binary_jar = ":jsr305-binary-jar",
+    binary_jar = ":jsr305-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "jsr305-binary-jar",
+    name = "jsr305-binary.jar",
     sha1 = "ad3ba65c1788f4d814a4da056323e2b84412fb3c",
     url = "mvn:com.squareup:javapoet:jar:1.2.0",
 )
diff --git a/ReactAndroid/src/main/third-party/java/jsr-305/BUCK b/ReactAndroid/src/main/third-party/java/jsr-305/BUCK
index f6a5d730f664..4db6df5554c2 100644
--- a/ReactAndroid/src/main/third-party/java/jsr-305/BUCK
+++ b/ReactAndroid/src/main/third-party/java/jsr-305/BUCK
@@ -1,11 +1,11 @@
 prebuilt_jar(
     name = "jsr-305",
-    binary_jar = ":jsr305-binary-jar",
+    binary_jar = ":jsr305-binary.jar",
     visibility = ["PUBLIC"],
 )
 
 remote_file(
-    name = "jsr305-binary-jar",
+    name = "jsr305-binary.jar",
     sha1 = "5871fb60dc68d67da54a663c3fd636a10a532948",
     url = "mvn:com.google.code.findbugs:jsr305:jar:3.0.0",
 )
diff --git a/ReactAndroid/src/main/third-party/java/jsr-330/BUCK b/ReactAndroid/src/main/third-party/java/jsr-330/BUCK
index 79a1f76bec92..def136484a75 100644
--- a/ReactAndroid/src/main/third-party/java/jsr-330/BUCK
+++ b/ReactAndroid/src/main/third-party/java/jsr-330/BUCK
@@ -1,11 +1,11 @@
 prebuilt_jar(
     name = "jsr-330",
-    binary_jar = ":jsr330-binary-jar",
+    binary_jar = ":jsr330-binary.jar",
     visibility = ["PUBLIC"],
 )
 
 remote_file(
-    name = "jsr330-binary-jar",
+    name = "jsr330-binary.jar",
     sha1 = "6975da39a7040257bd51d21a231b76c915872d38",
     url = "mvn:javax.inject:javax.inject:jar:1",
 )
diff --git a/ReactAndroid/src/main/third-party/java/junit/BUCK b/ReactAndroid/src/main/third-party/java/junit/BUCK
index fd5e5c1a32a8..f2f71cd04644 100644
--- a/ReactAndroid/src/main/third-party/java/junit/BUCK
+++ b/ReactAndroid/src/main/third-party/java/junit/BUCK
@@ -11,24 +11,24 @@ rn_android_library(
 
 rn_prebuilt_jar(
     name = "junit-core",
-    binary_jar = ":download-junit",
+    binary_jar = ":download-junit.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-junit",
+    name = "download-junit.jar",
     sha1 = "2973d150c0dc1fefe998f834810d68f278ea58ec",
     url = "mvn:junit:junit:jar:4.12",
 )
 
 rn_prebuilt_jar(
     name = "hamcrest",
-    binary_jar = ":download-hamcrest",
+    binary_jar = ":download-hamcrest.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-hamcrest",
+    name = "download-hamcrest.jar",
     sha1 = "63a21ebc981131004ad02e0434e799fd7f3a8d5a",
     url = "mvn:org.hamcrest:hamcrest-all:jar:1.3",
 )
diff --git a/ReactAndroid/src/main/third-party/java/mockito/BUCK b/ReactAndroid/src/main/third-party/java/mockito/BUCK
index 70db14c6ac2e..06e0686fa0a0 100644
--- a/ReactAndroid/src/main/third-party/java/mockito/BUCK
+++ b/ReactAndroid/src/main/third-party/java/mockito/BUCK
@@ -11,24 +11,24 @@ rn_android_library(
 
 rn_prebuilt_jar(
     name = "mockito-core",
-    binary_jar = ":mockito-binary-jar",
+    binary_jar = ":mockito-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "mockito-binary-jar",
+    name = "mockito-binary.jar",
     sha1 = "e8546f5bef4e061d8dd73895b4e8f40e3fe6effe",
     url = "mvn:org.mockito:mockito-core:jar:1.10.19",
 )
 
 rn_prebuilt_jar(
     name = "objenesis",
-    binary_jar = ":objenesis-binary-jar",
+    binary_jar = ":objenesis-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "objenesis-binary-jar",
+    name = "objenesis-binary.jar",
     sha1 = "87c0ea803b69252868d09308b4618f766f135a96",
     url = "mvn:org.objenesis:objenesis:jar:2.1",
 )
diff --git a/ReactAndroid/src/main/third-party/java/okhttp/BUCK b/ReactAndroid/src/main/third-party/java/okhttp/BUCK
index 549c3f457862..64dc55f36c99 100644
--- a/ReactAndroid/src/main/third-party/java/okhttp/BUCK
+++ b/ReactAndroid/src/main/third-party/java/okhttp/BUCK
@@ -1,23 +1,23 @@
 prebuilt_jar(
     name = "okhttp3",
-    binary_jar = ":okhttp3-binary-jar",
+    binary_jar = ":okhttp3-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "okhttp3-binary-jar",
+    name = "okhttp3-binary.jar",
     sha1 = "7ef0f1d95bf4c0b3ba30bbae25e0e562b05cf75e",
     url = "mvn:com.squareup.okhttp3:okhttp:jar:3.10.0",
 )
 
 prebuilt_jar(
     name = "okhttp3-urlconnection",
-    binary_jar = ":okhttp3-urlconnection-binary-jar",
+    binary_jar = ":okhttp3-urlconnection-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "okhttp3-urlconnection-binary-jar",
+    name = "okhttp3-urlconnection-binary.jar",
     sha1 = "ec614c05825ddd2267677a99f585d3913474b125",
     url = "mvn:com.squareup.okhttp3:okhttp-urlconnection:jar:3.10.0",
 )
diff --git a/ReactAndroid/src/main/third-party/java/okio/BUCK b/ReactAndroid/src/main/third-party/java/okio/BUCK
index eef6fb6cc50b..1219ad4697cf 100644
--- a/ReactAndroid/src/main/third-party/java/okio/BUCK
+++ b/ReactAndroid/src/main/third-party/java/okio/BUCK
@@ -1,11 +1,11 @@
 prebuilt_jar(
     name = "okio",
-    binary_jar = ":okio-binary-jar",
+    binary_jar = ":okio-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "okio-binary-jar",
+    name = "okio-binary.jar",
     sha1 = "102d7be47241d781ef95f1581d414b0943053130",
     url = "mvn:com.squareup.okio:okio:jar:1.14.0",
 )
diff --git a/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK b/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
index 87946208aa5d..1df19014bcd2 100644
--- a/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
+++ b/ReactAndroid/src/main/third-party/java/robolectric3/robolectric/BUCK
@@ -22,158 +22,158 @@ rn_android_library(
 
 rn_prebuilt_jar(
     name = "robolectric-core",
-    binary_jar = ":robolectric-binary-jar",
+    binary_jar = ":robolectric-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "robolectric-binary-jar",
+    name = "robolectric-binary.jar",
     sha1 = "f888cea3bc1a24110e315eb9827ab593610ea62f",
     url = "mvn:org.robolectric:robolectric:jar:3.0",
 )
 
 rn_prebuilt_jar(
     name = "robolectric-resources",
-    binary_jar = ":robolectric-resources-binary-jar",
+    binary_jar = ":robolectric-resources-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "robolectric-resources-binary-jar",
+    name = "robolectric-resources-binary.jar",
     sha1 = "1ab609054aab67cd13a434567467f4b4774f2465",
     url = "mvn:org.robolectric:robolectric-resources:jar:3.0",
 )
 
 rn_prebuilt_jar(
     name = "robolectric-annotations",
-    binary_jar = ":robolectric-annotations-binary-jar",
+    binary_jar = ":robolectric-annotations-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "robolectric-annotations-binary-jar",
+    name = "robolectric-annotations-binary.jar",
     sha1 = "2a6cfc072d7680694c1ff893c5dc8fec33163110",
     url = "mvn:org.robolectric:robolectric-annotations:jar:3.0",
 )
 
 rn_prebuilt_jar(
     name = "robolectric-utils",
-    binary_jar = ":robolectric-utils-binary-jar",
+    binary_jar = ":robolectric-utils-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "robolectric-utils-binary-jar",
+    name = "robolectric-utils-binary.jar",
     sha1 = "4bcecd8115fe7296088bb1636e6cbd7ae8927392",
     url = "mvn:org.robolectric:robolectric-utils:jar:3.0",
 )
 
 rn_prebuilt_jar(
     name = "bouncycastle",
-    binary_jar = ":bouncycastle-binary-jar",
+    binary_jar = ":bouncycastle-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "bouncycastle-binary-jar",
+    name = "bouncycastle-binary.jar",
     sha1 = "ce091790943599535cbb4de8ede84535b0c1260c",
     url = "mvn:org.bouncycastle:bcprov-jdk16:jar:1.46",
 )
 
 rn_prebuilt_jar(
     name = "vtd-xml",
-    binary_jar = ":vtd-xml-binary-jar",
+    binary_jar = ":vtd-xml-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "vtd-xml-binary-jar",
+    name = "vtd-xml-binary.jar",
     sha1 = "ee5bcf62c1acf76434ee9f1c67a840bafef72a6d",
     url = "mvn:com.ximpleware:vtd-xml:jar:2.11",
 )
 
 rn_prebuilt_jar(
     name = "icu",
-    binary_jar = ":icu-binary-jar",
+    binary_jar = ":icu-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "icu-binary-jar",
+    name = "icu-binary.jar",
     sha1 = "786d9055d4ca8c1aab4a7d4ac8283f973fd7e41f",
     url = "mvn:com.ibm.icu:icu4j:jar:53.1",
 )
 
 rn_prebuilt_jar(
     name = "android-all-4.1.2_r1-robolectric-0",  # name defines filename used by robolectric in runtime
-    binary_jar = ":robolectric-android-all-binary-jar",
+    binary_jar = ":robolectric-android-all-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 # This new rule will make the .jar file appear in the "right" location,
 # though that may change in the future
 export_file(
-    name = "robolectric-android-all-binary-jar",
-    src = ":robolectric-android-all-binary-remote-jar",
+    name = "robolectric-android-all-binary.jar",
+    src = ":robolectric-android-all-binary-remote.jar",
     out = "../android-all-4.1.2_r1-robolectric-0.jar",  # name defines filename used by robolectric in runtime
 )
 
 remote_file(
-    name = "robolectric-android-all-binary-remote-jar",
+    name = "robolectric-android-all-binary-remote.jar",
     sha1 = "aecc8ce5119a25fcea1cdf8285469c9d1261a352",
     url = "mvn:org.robolectric:android-all:jar:4.1.2_r1-robolectric-0",
 )
 
 rn_prebuilt_jar(
     name = "json-20080701",  # name defines filename used by robolectric in runtime
-    binary_jar = ":json-jar",
+    binary_jar = ":json.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 export_file(
-    name = "json-jar",
-    src = ":json-remote-jar",
+    name = "json.jar",
+    src = ":json-remote.jar",
     out = "../json-20080701.jar",  # name defines filename used by robolectric in runtime
 )
 
 remote_file(
-    name = "json-remote-jar",
+    name = "json-remote.jar",
     sha1 = "d652f102185530c93b66158b1859f35d45687258",
     url = "mvn:org.json:json:jar:20080701",
 )
 
 rn_prebuilt_jar(
     name = "tagsoup-1.2",  # name defines filename used by robolectric in runtime
-    binary_jar = ":tagsoup-jar",
+    binary_jar = ":tagsoup.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 export_file(
-    name = "tagsoup-jar",
-    src = ":tagsoup-remote-jar",
+    name = "tagsoup.jar",
+    src = ":tagsoup-remote.jar",
     out = "../tagsoup-1.2.jar",  # name defines filename used by robolectric in runtime
 )
 
 remote_file(
-    name = "tagsoup-remote-jar",
+    name = "tagsoup-remote.jar",
     sha1 = "639fd364750d7363c85797dc944b4a80f78fa684",
     url = "mvn:org.ccil.cowan.tagsoup:tagsoup:jar:1.2",
 )
 
 rn_prebuilt_jar(
     name = "shadows-core-3.0-16",  # name defines filename used by robolectric in runtime
-    binary_jar = ":robolectric-shadows-binary-jar",
+    binary_jar = ":robolectric-shadows-binary.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 export_file(
-    name = "robolectric-shadows-binary-jar",
-    src = ":robolectric-shadows-binary-remote-jar",
+    name = "robolectric-shadows-binary.jar",
+    src = ":robolectric-shadows-binary-remote.jar",
     out = "../shadows-core-3.0-16.jar",  # name defines filename used by robolectric in runtime
 )
 
 remote_file(
-    name = "robolectric-shadows-binary-remote-jar",
+    name = "robolectric-shadows-binary-remote.jar",
     sha1 = "39d7a856bf91640b1a6d044333336a2b3f3c198f",
     url = "https://repo1.maven.org/maven2/org/robolectric/shadows-core/3.0/shadows-core-3.0-16.jar",
 )
diff --git a/ReactAndroid/src/main/third-party/java/sqlite/BUCK b/ReactAndroid/src/main/third-party/java/sqlite/BUCK
index 419bc9ed4f70..a739fae9f85a 100644
--- a/ReactAndroid/src/main/third-party/java/sqlite/BUCK
+++ b/ReactAndroid/src/main/third-party/java/sqlite/BUCK
@@ -10,12 +10,12 @@ rn_android_library(
 
 rn_prebuilt_jar(
     name = "sqlite4java",
-    binary_jar = ":download-sqlite4java",
+    binary_jar = ":download-sqlite4java.jar",
     visibility = ["//ReactAndroid/..."],
 )
 
 remote_file(
-    name = "download-sqlite4java",
+    name = "download-sqlite4java.jar",
     sha1 = "745a7e2f35fdbe6336922e0d492c979dbbfa74fb",
     url = "mvn:com.almworks.sqlite4java:sqlite4java:jar:0.282",
 )

From 4ad13075c3e763a914675d62e7a9836bb3700ad3 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Tue, 26 Jun 2018 10:52:38 -0700
Subject: [PATCH 0925/1109] Image with null source should still respect `style`

Summary: D8576087 has all the details. Merge conflict messed up the diff hence a new one.

Reviewed By: yungsters

Differential Revision: D8628053

fbshipit-source-id: 8b211864f8f9d6b56f9469396eaa1d8291bbb56f
---
 Libraries/Image/Image.android.js                  | 11 ++---------
 .../react/views/image/ReactImageView.java         | 15 ++++++++++-----
 2 files changed, 12 insertions(+), 14 deletions(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index d0e685a5e642..6f0a312e97ef 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -190,9 +190,6 @@ let Image = (
     props.loadingIndicatorSource,
   );
 
-  // As opposed to the ios version, here we render `null` when there is no source, source.uri
-  // or source array.
-
   if (source && source.uri === '') {
     console.warn('source.uri should not be an empty string');
   }
@@ -215,13 +212,9 @@ let Image = (
     );
   }
 
-  if (!source || (!source.uri && !Array.isArray(source))) {
-    return null;
-  }
-
   let style;
   let sources;
-  if (source.uri) {
+  if (source?.uri != null) {
     const {width, height} = source;
     style = flattenStyle([{width, height}, styles.base, props.style]);
     sources = [{uri: source.uri}];
@@ -235,7 +228,7 @@ let Image = (
     style,
     shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),
     src: sources,
-    headers: source.headers,
+    headers: source?.headers,
     defaultSrc: defaultSource ? defaultSource.uri : null,
     loadingIndicatorSrc: loadingIndicatorSource
       ? loadingIndicatorSource.uri
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index 440bf3f2c775..cf7a1580fcb0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -70,6 +70,9 @@ public class ReactImageView extends GenericDraweeView {
 
   public static final int REMOTE_IMAGE_FADE_DURATION_MS = 300;
 
+  public static final String REMOTE_TRANSPARENT_BITMAP_URI =
+  "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAQAAAC1HAwCAAAAC0lEQVR42mNkYAAAAAYAAjCB0C8AAAAASUVORK5CYII=";
+
   private static float[] sComputedCornerRadii = new float[4];
 
   /*
@@ -338,7 +341,10 @@ public void setResizeMethod(ImageResizeMethod resizeMethod) {
 
   public void setSource(@Nullable ReadableArray sources) {
     mSources.clear();
-    if (sources != null && sources.size() != 0) {
+    if (sources == null || sources.size() == 0) {
+      ImageSource imageSource = new ImageSource(getContext(), REMOTE_TRANSPARENT_BITMAP_URI);
+      mSources.add(imageSource);
+    } else {
       // Optimize for the case where we have just one uri, case in which we don't need the sizes
       if (sources.size() == 1) {
         ReadableMap source = sources.getMap(0);
@@ -572,9 +578,9 @@ private boolean isTiled() {
   private void setSourceImage() {
     mImageSource = null;
     if (mSources.isEmpty()) {
-      return;
-    }
-    if (hasMultipleSources()) {
+      ImageSource imageSource = new ImageSource(getContext(), REMOTE_TRANSPARENT_BITMAP_URI);
+       mSources.add(imageSource);
+     } else if (hasMultipleSources()) {
       MultiSourceResult multiSource =
         MultiSourceHelper.getBestSourceForSize(getWidth(), getHeight(), mSources);
       mImageSource = multiSource.getBestResult();
@@ -609,4 +615,3 @@ private void warnImageSource(String uri) {
     }
   }
 }
-

From 8ce758f48adc263924db0349d3b7059e52fc0be7 Mon Sep 17 00:00:00 2001
From: Sergei Dryganets <sergeyd@microsoft.com>
Date: Tue, 26 Jun 2018 10:54:50 -0700
Subject: [PATCH 0926/1109] Android ndk-build fix for ndk-r14+ (#18814)

Summary:
According to [ndk release notes](https://github.com/android-ndk/ndk/wiki/Changelog-r14-beta1#ndk-build) flag APP_ALLOW_MISSING_DEPS should be set to true in order to fix ndk-build tool.

If it builds it will work. On older ndk flag is ignored.

[ANDROID] [MINOR] [Application.mk]  - build with android-ndk-14+ supported
Closes https://github.com/facebook/react-native/pull/18814

Differential Revision: D8643513

Pulled By: hramos

fbshipit-source-id: d96f8c039a754b9b95839f0a0bd98fcfdaf39bd4
---
 ReactAndroid/src/main/jni/react/jni/Android.mk | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/jni/react/jni/Android.mk b/ReactAndroid/src/main/jni/react/jni/Android.mk
index 8fe31894cdff..9e7dcb7a39b8 100644
--- a/ReactAndroid/src/main/jni/react/jni/Android.mk
+++ b/ReactAndroid/src/main/jni/react/jni/Android.mk
@@ -37,7 +37,7 @@ LOCAL_CFLAGS += $(CXX11_FLAGS)
 LOCAL_EXPORT_CPPFLAGS := $(CXX11_FLAGS)
 
 LOCAL_LDLIBS += -landroid
-LOCAL_SHARED_LIBRARIES := libfolly_json libfbjni libjsc libglog_init libyoga libprivatedata
+LOCAL_SHARED_LIBRARIES := libfolly_json libfb libjsc libglog_init libyoga libprivatedata
 LOCAL_STATIC_LIBRARIES := libreactnative
 
 include $(BUILD_SHARED_LIBRARY)

From 97bc0c03bad96e43cc927650175bf36bd5f0dc74 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 26 Jun 2018 11:32:53 -0700
Subject: [PATCH 0927/1109] Fabric: `fromDynamic` for float numbers was moved
 to `core` module

Summary:
@public
Otherwise, it can mess with implementation for `int`s and causes some errors where `float` implementation was requested but `int` was applied.

Reviewed By: mdvacca

Differential Revision: D8601752

fbshipit-source-id: cfe51b7785ff29ee4ad88f0f1cbfed335557d5ef
---
 ReactCommon/fabric/core/propsConversions.h | 2 ++
 ReactCommon/fabric/graphics/conversions.h  | 4 ----
 2 files changed, 2 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/core/propsConversions.h b/ReactCommon/fabric/core/propsConversions.h
index c5efbe3d4564..350eb017e753 100644
--- a/ReactCommon/fabric/core/propsConversions.h
+++ b/ReactCommon/fabric/core/propsConversions.h
@@ -22,6 +22,8 @@ inline void fromDynamic(const folly::dynamic &value, int &result) {
   // So this always converts the value to int64 instead.
   result = value.asInt();
 }
+inline void fromDynamic(const folly::dynamic &value, float &result) { result = (float)value.asDouble(); }
+inline void fromDynamic(const folly::dynamic &value, double &result) { result = value.asDouble(); }
 inline void fromDynamic(const folly::dynamic &value, std::string &result) { result = value.getString(); }
 
 template <typename T>
diff --git a/ReactCommon/fabric/graphics/conversions.h b/ReactCommon/fabric/graphics/conversions.h
index d2adc857c03f..3d5cc4275289 100644
--- a/ReactCommon/fabric/graphics/conversions.h
+++ b/ReactCommon/fabric/graphics/conversions.h
@@ -55,10 +55,6 @@ inline std::string toString(const SharedColor &value) {
 
 #pragma mark - Geometry
 
-inline void fromDynamic(const folly::dynamic &value, Float &result) {
-  result = value.asDouble();
-}
-
 inline void fromDynamic(const folly::dynamic &value, Point &result) {
   if (value.isObject()) {
     result = Point {(Float)value["x"].asDouble(), (Float)value["y"].asDouble()};

From d629e4b0e5407b99600d297c01c52e8a95406867 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 26 Jun 2018 11:32:55 -0700
Subject: [PATCH 0928/1109] Fabric: Releasing image bitmap as part of
 `prepareForRecycle`

Summary:
@public
When some `RCTImageComponentView` is going to be recycled, it makes sense to free an associated bitmap because it will not be reused anyways.

Reviewed By: mdvacca

Differential Revision: D8601751

fbshipit-source-id: 1318622b66460b8e5588a4420c91c516fe2b1106
---
 .../ComponentViews/Image/RCTImageComponentView.mm      | 10 ++++++++++
 1 file changed, 10 insertions(+)

diff --git a/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.mm b/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.mm
index 9e8cb4de4856..cb8dcd7fc0ec 100644
--- a/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/Image/RCTImageComponentView.mm
@@ -39,6 +39,8 @@ - (instancetype)initWithFrame:(CGRect)frame
   return self;
 }
 
+#pragma mark - RCTComponentViewProtocol
+
 - (void)updateProps:(SharedProps)props oldProps:(SharedProps)oldProps
 {
   if (!oldProps) {
@@ -79,6 +81,14 @@ - (void)updateLocalData:(SharedLocalData)localData
   });
 }
 
+- (void)prepareForRecycle
+{
+  [super prepareForRecycle];
+  _imageView.image = nil;
+}
+
+#pragma mark - Other
+
 - (void)setImage:(UIImage *)image
 {
   const auto &imageProps = *std::static_pointer_cast<const ImageProps>(_props);

From 80f7891287b10d63158210ae3ba4c78f67edaeb3 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 26 Jun 2018 11:32:57 -0700
Subject: [PATCH 0929/1109] Fabric: Embracing non-trivial default values of
 some Props

Summary:
@public
This is follow up for D8601600 and D8247652 (the last one has detailed explanation of the problem).
From this commit I propose that we have to follow simple rule:
If some prop has a default value which differs from the default value of its type, we have to specify it as {<value>} in .h file and explicitly in .m file, for all other props the default value must not be specified explicitly (in .h files it must be specified as {}).
The reason is that we have to embrase those cases and establish behaviour: if we change the default value in .h file, it always means that we have to change the value in .cpp file too.

Reviewed By: fkgozali

Differential Revision: D8601776

fbshipit-source-id: 3379aace4e2d72febb2b942a3da1cb24decf54be
---
 .../attributedstring/ParagraphAttributes.h    |  6 ++---
 .../fabric/scrollview/ScrollViewProps.cpp     | 26 +++++++++----------
 .../fabric/scrollview/ScrollViewProps.h       | 18 ++++++-------
 .../fabric/text/paragraph/ParagraphProps.cpp  |  4 +--
 .../fabric/text/paragraph/ParagraphProps.h    |  2 +-
 .../fabric/text/rawtext/RawTextProps.h        |  2 +-
 ReactCommon/fabric/view/ViewProps.h           | 16 ++++++------
 7 files changed, 37 insertions(+), 37 deletions(-)

diff --git a/ReactCommon/fabric/attributedstring/ParagraphAttributes.h b/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
index b6271999a2d7..9feaea20b50c 100644
--- a/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
+++ b/ReactCommon/fabric/attributedstring/ParagraphAttributes.h
@@ -36,18 +36,18 @@ class ParagraphAttributes:
    * Maximum number of lines which paragraph can take.
    * Zero value represents "no limit".
    */
-  int maximumNumberOfLines {0};
+  int maximumNumberOfLines {};
 
   /*
    * In case if a text cannot fit given boundaries, defines a place where
    * an ellipsize should be placed.
    */
-  EllipsizeMode ellipsizeMode {EllipsizeMode::Clip};
+  EllipsizeMode ellipsizeMode {};
 
   /*
    * Enables font size adjustment to fit constrained boundaries.
    */
-  bool adjustsFontSizeToFit {false};
+  bool adjustsFontSizeToFit {};
 
   /*
    * In case of font size adjustment enabled, defines minimum and maximum
diff --git a/ReactCommon/fabric/scrollview/ScrollViewProps.cpp b/ReactCommon/fabric/scrollview/ScrollViewProps.cpp
index 1e4004d06189..c3b1b4e7a7ed 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewProps.cpp
+++ b/ReactCommon/fabric/scrollview/ScrollViewProps.cpp
@@ -18,27 +18,27 @@ namespace react {
 
 ScrollViewProps::ScrollViewProps(const ScrollViewProps &sourceProps, const RawProps &rawProps):
   ViewProps(sourceProps, rawProps),
-  alwaysBounceHorizontal(convertRawProp(rawProps, "alwaysBounceHorizontal", sourceProps.alwaysBounceHorizontal)),
-  alwaysBounceVertical(convertRawProp(rawProps, "alwaysBounceVertical", sourceProps.alwaysBounceVertical)),
-  bounces(convertRawProp(rawProps, "bounces", sourceProps.bounces)),
-  bouncesZoom(convertRawProp(rawProps, "bouncesZoom", sourceProps.bouncesZoom)),
+  alwaysBounceHorizontal(convertRawProp(rawProps, "alwaysBounceHorizontal", sourceProps.alwaysBounceHorizontal, true)),
+  alwaysBounceVertical(convertRawProp(rawProps, "alwaysBounceVertical", sourceProps.alwaysBounceVertical, true)),
+  bounces(convertRawProp(rawProps, "bounces", sourceProps.bounces, true)),
+  bouncesZoom(convertRawProp(rawProps, "bouncesZoom", sourceProps.bouncesZoom, true)),
   canCancelContentTouches(convertRawProp(rawProps, "canCancelContentTouches", sourceProps.canCancelContentTouches)),
   centerContent(convertRawProp(rawProps, "centerContent", sourceProps.centerContent)),
   automaticallyAdjustContentInsets(convertRawProp(rawProps, "automaticallyAdjustContentInsets", sourceProps.automaticallyAdjustContentInsets)),
-  decelerationRate(convertRawProp(rawProps, "decelerationRate", sourceProps.decelerationRate)),
+  decelerationRate(convertRawProp(rawProps, "decelerationRate", sourceProps.decelerationRate, (Float)0.998)),
   directionalLockEnabled(convertRawProp(rawProps, "directionalLockEnabled", sourceProps.directionalLockEnabled)),
   indicatorStyle(convertRawProp(rawProps, "indicatorStyle", sourceProps.indicatorStyle)),
   keyboardDismissMode(convertRawProp(rawProps, "keyboardDismissMode", sourceProps.keyboardDismissMode)),
-  maximumZoomScale(convertRawProp(rawProps, "maximumZoomScale", sourceProps.maximumZoomScale)),
-  minimumZoomScale(convertRawProp(rawProps, "minimumZoomScale", sourceProps.minimumZoomScale)),
-  scrollEnabled(convertRawProp(rawProps, "scrollEnabled", sourceProps.scrollEnabled)),
+  maximumZoomScale(convertRawProp(rawProps, "maximumZoomScale", sourceProps.maximumZoomScale, (Float)1.0)),
+  minimumZoomScale(convertRawProp(rawProps, "minimumZoomScale", sourceProps.minimumZoomScale, (Float)1.0)),
+  scrollEnabled(convertRawProp(rawProps, "scrollEnabled", sourceProps.scrollEnabled, true)),
   pagingEnabled(convertRawProp(rawProps, "pagingEnabled", sourceProps.pagingEnabled)),
-  pinchGestureEnabled(convertRawProp(rawProps, "pinchGestureEnabled", sourceProps.pinchGestureEnabled)),
-  scrollsToTop(convertRawProp(rawProps, "scrollsToTop", sourceProps.scrollsToTop)),
-  showsHorizontalScrollIndicator(convertRawProp(rawProps, "showsHorizontalScrollIndicator", sourceProps.showsHorizontalScrollIndicator)),
-  showsVerticalScrollIndicator(convertRawProp(rawProps, "showsVerticalScrollIndicator", sourceProps.showsVerticalScrollIndicator)),
+  pinchGestureEnabled(convertRawProp(rawProps, "pinchGestureEnabled", sourceProps.pinchGestureEnabled, true)),
+  scrollsToTop(convertRawProp(rawProps, "scrollsToTop", sourceProps.scrollsToTop, true)),
+  showsHorizontalScrollIndicator(convertRawProp(rawProps, "showsHorizontalScrollIndicator", sourceProps.showsHorizontalScrollIndicator, true)),
+  showsVerticalScrollIndicator(convertRawProp(rawProps, "showsVerticalScrollIndicator", sourceProps.showsVerticalScrollIndicator, true)),
   scrollEventThrottle(convertRawProp(rawProps, "scrollEventThrottle", sourceProps.scrollEventThrottle)),
-  zoomScale(convertRawProp(rawProps, "zoomScale", sourceProps.zoomScale)),
+  zoomScale(convertRawProp(rawProps, "zoomScale", sourceProps.zoomScale, (Float)1.0)),
   contentInset(convertRawProp(rawProps, "contentInset", sourceProps.contentInset)),
   scrollIndicatorInsets(convertRawProp(rawProps, "scrollIndicatorInsets", sourceProps.scrollIndicatorInsets)),
   snapToInterval(convertRawProp(rawProps, "snapToInterval", sourceProps.snapToInterval)),
diff --git a/ReactCommon/fabric/scrollview/ScrollViewProps.h b/ReactCommon/fabric/scrollview/ScrollViewProps.h
index 190332c2fe91..219902470cb8 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewProps.h
+++ b/ReactCommon/fabric/scrollview/ScrollViewProps.h
@@ -28,26 +28,26 @@ class ScrollViewProps final:
   const bool bounces {true};
   const bool bouncesZoom {true};
   const bool canCancelContentTouches {true};
-  const bool centerContent {false};
-  const bool automaticallyAdjustContentInsets  {false};
+  const bool centerContent {};
+  const bool automaticallyAdjustContentInsets  {};
   const Float decelerationRate {0.998};
-  const bool directionalLockEnabled {false};
-  const ScrollViewIndicatorStyle indicatorStyle {ScrollViewIndicatorStyle::Default};
-  const ScrollViewKeyboardDismissMode keyboardDismissMode {ScrollViewKeyboardDismissMode::None};
+  const bool directionalLockEnabled {};
+  const ScrollViewIndicatorStyle indicatorStyle {};
+  const ScrollViewKeyboardDismissMode keyboardDismissMode {};
   const Float maximumZoomScale {1.0};
   const Float minimumZoomScale {1.0};
   const bool scrollEnabled {true};
-  const bool pagingEnabled {false};
+  const bool pagingEnabled {};
   const bool pinchGestureEnabled {true};
   const bool scrollsToTop {true};
   const bool showsHorizontalScrollIndicator {true};
   const bool showsVerticalScrollIndicator {true};
-  const Float scrollEventThrottle {0};
+  const Float scrollEventThrottle {};
   const Float zoomScale {1.0};
   const EdgeInsets contentInset {};
   const EdgeInsets scrollIndicatorInsets {};
-  const int snapToInterval {0};
-  const ScrollViewSnapToAlignment snapToAlignment {ScrollViewSnapToAlignment::Start};
+  const int snapToInterval {};
+  const ScrollViewSnapToAlignment snapToAlignment {};
 
 #pragma mark - DebugStringConvertible
 
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
index a6ea79c6e71e..ca4ff847c05e 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
@@ -20,8 +20,8 @@ static ParagraphAttributes convertRawProp(const RawProps &rawProps, const Paragr
   paragraphAttributes.maximumNumberOfLines = convertRawProp(rawProps, "numberOfLines", defaultParagraphAttributes.maximumNumberOfLines);
   paragraphAttributes.ellipsizeMode = convertRawProp(rawProps, "ellipsizeMode", defaultParagraphAttributes.ellipsizeMode);
   paragraphAttributes.adjustsFontSizeToFit = convertRawProp(rawProps, "adjustsFontSizeToFit", defaultParagraphAttributes.adjustsFontSizeToFit);
-  paragraphAttributes.minimumFontSize = convertRawProp(rawProps, "minimumFontSize", defaultParagraphAttributes.minimumFontSize);
-  paragraphAttributes.maximumFontSize = convertRawProp(rawProps, "maximumFontSize", defaultParagraphAttributes.maximumFontSize);
+  paragraphAttributes.minimumFontSize = convertRawProp(rawProps, "minimumFontSize", defaultParagraphAttributes.minimumFontSize, std::numeric_limits<Float>::quiet_NaN());
+  paragraphAttributes.maximumFontSize = convertRawProp(rawProps, "maximumFontSize", defaultParagraphAttributes.maximumFontSize, std::numeric_limits<Float>::quiet_NaN());
 
   return paragraphAttributes;
 }
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.h b/ReactCommon/fabric/text/paragraph/ParagraphProps.h
index a31e1c3585b4..5877be6cb86d 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.h
+++ b/ReactCommon/fabric/text/paragraph/ParagraphProps.h
@@ -45,7 +45,7 @@ class ParagraphProps:
   /*
    * Defines can the text be selected (and copied) or not.
    */
-  const bool isSelectable {false};
+  const bool isSelectable {};
 
 #pragma mark - DebugStringConvertible
 
diff --git a/ReactCommon/fabric/text/rawtext/RawTextProps.h b/ReactCommon/fabric/text/rawtext/RawTextProps.h
index 37ba902ee219..45f1f3d01dee 100644
--- a/ReactCommon/fabric/text/rawtext/RawTextProps.h
+++ b/ReactCommon/fabric/text/rawtext/RawTextProps.h
@@ -29,7 +29,7 @@ class RawTextProps:
 
 #pragma mark - Props
 
-  const std::string text {""};
+  const std::string text {};
 
 #pragma mark - DebugStringConvertible
 
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/view/ViewProps.h
index 2a15323e2fbe..a533b051ff89 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/view/ViewProps.h
@@ -35,9 +35,9 @@ class ViewProps:
 #pragma mark - Props
 
   // Color
-  const Float opacity {1};
-  const SharedColor foregroundColor {nullptr};
-  const SharedColor backgroundColor {nullptr};
+  const Float opacity {1.0};
+  const SharedColor foregroundColor {};
+  const SharedColor backgroundColor {};
 
   // Borders
   const EdgeInsets borderWidth {};
@@ -46,21 +46,21 @@ class ViewProps:
   const BorderStyle borderStyle {};
 
   // Shadow
-  const SharedColor shadowColor {nullptr};
+  const SharedColor shadowColor {};
   const Size shadowOffset {};
   const Float shadowOpacity {};
   const Float shadowRadius {};
 
   // Transform
   const Transform transform {};
-  const bool backfaceVisibility {false};
-  const bool shouldRasterize {false};
-  const int zIndex {0};
+  const bool backfaceVisibility {};
+  const bool shouldRasterize {};
+  const int zIndex {};
 
   // Events
   const PointerEventsMode pointerEvents {};
   const EdgeInsets hitSlop {};
-  const bool onLayout {false};
+  const bool onLayout {};
 
 #pragma mark - DebugStringConvertible
 

From 8b6f1c37ce6276f14c6113b834ebca3c042a3552 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 26 Jun 2018 13:31:04 -0700
Subject: [PATCH 0930/1109] RN: Fix Element Inspector w/ Negative Margins

Summary:
There is a bug with the React Native element inspector when the inspected element has negative margins because negative margins actually subtract from the content width and height. This fixes the bug.

@public

Reviewed By: TheSavior

Differential Revision: D8607389

fbshipit-source-id: 2cea0d9160b5437fe775b2ba25373072bafd70b9
---
 Libraries/Inspector/ElementBox.js | 55 +++++++++++++++++++------------
 1 file changed, 34 insertions(+), 21 deletions(-)

diff --git a/Libraries/Inspector/ElementBox.js b/Libraries/Inspector/ElementBox.js
index e43233fb0dce..dea05dad7378 100644
--- a/Libraries/Inspector/ElementBox.js
+++ b/Libraries/Inspector/ElementBox.js
@@ -10,38 +10,51 @@
 
 'use strict';
 
+const BorderBox = require('BorderBox');
 const React = require('React');
-const View = require('View');
 const StyleSheet = require('StyleSheet');
-const BorderBox = require('BorderBox');
-const resolveBoxStyle = require('resolveBoxStyle');
+const View = require('View');
 
 const flattenStyle = require('flattenStyle');
+const resolveBoxStyle = require('resolveBoxStyle');
 
 class ElementBox extends React.Component<$FlowFixMeProps> {
   render() {
     const style = flattenStyle(this.props.style) || {};
     const margin = resolveBoxStyle('margin', style);
     const padding = resolveBoxStyle('padding', style);
-    let frameStyle = this.props.frame;
-    if (margin) {
-      frameStyle = {
-        top: frameStyle.top - margin.top,
-        left: frameStyle.left - margin.left,
-        height: frameStyle.height + margin.top + margin.bottom,
-        width: frameStyle.width + margin.left + margin.right,
-      };
-    }
-    let contentStyle = {
+
+    const frameStyle = {...this.props.frame};
+    const contentStyle = {
       width: this.props.frame.width,
       height: this.props.frame.height,
     };
-    if (padding) {
-      contentStyle = {
-        width: contentStyle.width - padding.left - padding.right,
-        height: contentStyle.height - padding.top - padding.bottom,
-      };
+
+    if (margin != null) {
+      frameStyle.top -= margin.top;
+      frameStyle.left -= margin.left;
+      frameStyle.height += margin.top + margin.bottom;
+      frameStyle.width += margin.left + margin.right;
+
+      if (margin.top < 0) {
+        contentStyle.height += margin.top;
+      }
+      if (margin.bottom < 0) {
+        contentStyle.height += margin.bottom;
+      }
+      if (margin.left < 0) {
+        contentStyle.width += margin.left;
+      }
+      if (margin.right < 0) {
+        contentStyle.width += margin.right;
+      }
     }
+
+    if (padding != null) {
+      contentStyle.width -= padding.left + padding.right;
+      contentStyle.height -= padding.top + padding.bottom;
+    }
+
     return (
       <View style={[styles.frame, frameStyle]} pointerEvents="none">
         <BorderBox box={margin} style={styles.margin}>
@@ -59,13 +72,13 @@ const styles = StyleSheet.create({
     position: 'absolute',
   },
   content: {
-    backgroundColor: 'rgba(200, 230, 255, 0.8)',
+    backgroundColor: 'rgba(200, 230, 255, 0.8)', // blue
   },
   padding: {
-    borderColor: 'rgba(77, 255, 0, 0.3)',
+    borderColor: 'rgba(77, 255, 0, 0.3)', // green
   },
   margin: {
-    borderColor: 'rgba(255, 132, 0, 0.3)',
+    borderColor: 'rgba(255, 132, 0, 0.3)', // orange
   },
 });
 

From 537a99539b4a0fd1f12f086451827615c4705126 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 26 Jun 2018 13:31:05 -0700
Subject: [PATCH 0931/1109] YellowBox: Fix Off-By-1 Content Rendering Bug

Summary:
Fixes an off-by-one bug that was causing trailing single characters to be truncated from YellowBox.

This snuck in during the revamp of YellowBox. Whoops!

@public

Reviewed By: TheSavior

Differential Revision: D8607388

fbshipit-source-id: d0efac4dec361456ef58347a60eb1486a888624a
---
 Libraries/YellowBox/Data/YellowBoxCategory.js |  2 +-
 .../Data/__tests__/YellowBoxCategory-test.js  | 85 +++++++++++++++++
 .../YellowBoxCategory-test.js.snap            | 95 +++++++++++++++++++
 3 files changed, 181 insertions(+), 1 deletion(-)
 create mode 100644 Libraries/YellowBox/Data/__tests__/__snapshots__/YellowBoxCategory-test.js.snap

diff --git a/Libraries/YellowBox/Data/YellowBoxCategory.js b/Libraries/YellowBox/Data/YellowBoxCategory.js
index 5e22fa96bdf7..b0c5984ce950 100644
--- a/Libraries/YellowBox/Data/YellowBoxCategory.js
+++ b/Libraries/YellowBox/Data/YellowBoxCategory.js
@@ -134,7 +134,7 @@ const YellowBoxCategory = {
       0,
     );
 
-    if (lastOffset < content.length - 1) {
+    if (lastOffset < content.length) {
       const lastPart = content.substr(lastOffset);
       elements.push(<Text key="-1">{lastPart}</Text>);
     }
diff --git a/Libraries/YellowBox/Data/__tests__/YellowBoxCategory-test.js b/Libraries/YellowBox/Data/__tests__/YellowBoxCategory-test.js
index 5c7ab61b409a..e835485ec1b5 100644
--- a/Libraries/YellowBox/Data/__tests__/YellowBoxCategory-test.js
+++ b/Libraries/YellowBox/Data/__tests__/YellowBoxCategory-test.js
@@ -97,4 +97,89 @@ describe('YellowBoxCategory', () => {
       },
     });
   });
+
+  it('renders content with no substitutions', () => {
+    expect(
+      YellowBoxCategory.render(
+        {content: 'A', substitutions: []},
+        {fontWeight: 'bold'},
+      ),
+    ).toMatchSnapshot();
+  });
+
+  it('renders a single substitution', () => {
+    expect(
+      YellowBoxCategory.render(
+        {
+          content: '"A"',
+          substitutions: [
+            {
+              length: 3,
+              offset: 0,
+            },
+          ],
+        },
+        {fontWeight: 'bold'},
+      ),
+    ).toMatchSnapshot();
+  });
+
+  it('renders multiple substitutions', () => {
+    expect(
+      YellowBoxCategory.render(
+        {
+          content: '"A" "B" "C"',
+          substitutions: [
+            {
+              length: 3,
+              offset: 0,
+            },
+            {
+              length: 3,
+              offset: 4,
+            },
+            {
+              length: 3,
+              offset: 8,
+            },
+          ],
+        },
+        {fontWeight: 'bold'},
+      ),
+    ).toMatchSnapshot();
+  });
+
+  it('renders substitutions with leading content', () => {
+    expect(
+      YellowBoxCategory.render(
+        {
+          content: '!"A"',
+          substitutions: [
+            {
+              length: 3,
+              offset: 1,
+            },
+          ],
+        },
+        {fontWeight: 'bold'},
+      ),
+    ).toMatchSnapshot();
+  });
+
+  it('renders substitutions with trailing content', () => {
+    expect(
+      YellowBoxCategory.render(
+        {
+          content: '"A"!',
+          substitutions: [
+            {
+              length: 3,
+              offset: 0,
+            },
+          ],
+        },
+        {fontWeight: 'bold'},
+      ),
+    ).toMatchSnapshot();
+  });
 });
diff --git a/Libraries/YellowBox/Data/__tests__/__snapshots__/YellowBoxCategory-test.js.snap b/Libraries/YellowBox/Data/__tests__/__snapshots__/YellowBoxCategory-test.js.snap
new file mode 100644
index 000000000000..ee88875c3717
--- /dev/null
+++ b/Libraries/YellowBox/Data/__tests__/__snapshots__/YellowBoxCategory-test.js.snap
@@ -0,0 +1,95 @@
+// Jest Snapshot v1, https://goo.gl/fbAQLP
+
+exports[`YellowBoxCategory renders a single substitution 1`] = `
+Array [
+  <Component
+    style={
+      Object {
+        "fontWeight": "bold",
+      }
+    }
+  >
+    "A"
+  </Component>,
+]
+`;
+
+exports[`YellowBoxCategory renders content with no substitutions 1`] = `
+Array [
+  <Component>
+    A
+  </Component>,
+]
+`;
+
+exports[`YellowBoxCategory renders multiple substitutions 1`] = `
+Array [
+  <Component
+    style={
+      Object {
+        "fontWeight": "bold",
+      }
+    }
+  >
+    "A"
+  </Component>,
+  <Component>
+     
+  </Component>,
+  <Component
+    style={
+      Object {
+        "fontWeight": "bold",
+      }
+    }
+  >
+    "B"
+  </Component>,
+  <Component>
+     
+  </Component>,
+  <Component
+    style={
+      Object {
+        "fontWeight": "bold",
+      }
+    }
+  >
+    "C"
+  </Component>,
+]
+`;
+
+exports[`YellowBoxCategory renders substitutions with leading content 1`] = `
+Array [
+  <Component>
+    !
+  </Component>,
+  <Component
+    style={
+      Object {
+        "fontWeight": "bold",
+      }
+    }
+  >
+    "A"
+  </Component>,
+]
+`;
+
+exports[`YellowBoxCategory renders substitutions with trailing content 1`] = `
+Array [
+  <Component
+    style={
+      Object {
+        "fontWeight": "bold",
+      }
+    }
+  >
+    "A"
+  </Component>,
+  <Component>
+    !
+  </Component>,
+]
+`;

From bfea0e5524e281c6cbf938299fa254f103dd45c6 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 26 Jun 2018 13:31:07 -0700
Subject: [PATCH 0932/1109] RN: Fix Element Inspector w/ Start + End Styles

Summary:
Fixes how the element inspector displays start and end styles (e.g. `marginStart` or `paddingEnd`).

@public

Reviewed By: TheSavior

Differential Revision: D8607581

fbshipit-source-id: e949927fd86e9b21a8ecf26fbf3e4863ad1486bd
---
 Libraries/Inspector/resolveBoxStyle.js | 121 ++++++++++++++++++-------
 1 file changed, 88 insertions(+), 33 deletions(-)

diff --git a/Libraries/Inspector/resolveBoxStyle.js b/Libraries/Inspector/resolveBoxStyle.js
index 0a0e58e120f6..767b9edbc5f0 100644
--- a/Libraries/Inspector/resolveBoxStyle.js
+++ b/Libraries/Inspector/resolveBoxStyle.js
@@ -10,48 +10,103 @@
 
 'use strict';
 
+const I18nManager = require('I18nManager');
+
 /**
- * Resolve a style property into it's component parts, e.g.
+ * Resolve a style property into its component parts.
+ *
+ * For example:
  *
- * resolveProperties('margin', {margin: 5, marginBottom: 10})
- * ->
- * {top: 5, left: 5, right: 5, bottom: 10}
+ *   > resolveProperties('margin', {margin: 5, marginBottom: 10})
+ *   {top: 5, left: 5, right: 5, bottom: 10}
  *
- * If none are set, returns false.
+ * If no parts exist, this returns null.
  */
-function resolveBoxStyle(prefix: string, style: Object): ?Object {
-  const res = {};
-  const subs = ['top', 'left', 'bottom', 'right'];
-  let set = false;
-  subs.forEach(sub => {
-    res[sub] = style[prefix] || 0;
-  });
-  if (style[prefix]) {
-    set = true;
-  }
-  if (style[prefix + 'Vertical']) {
-    res.top = res.bottom = style[prefix + 'Vertical'];
-    set = true;
+function resolveBoxStyle(
+  prefix: string,
+  style: Object,
+): ?$ReadOnly<{|
+  bottom: number,
+  left: number,
+  right: number,
+  top: number,
+|}> {
+  let hasParts = false;
+  const result = {
+    bottom: 0,
+    left: 0,
+    right: 0,
+    top: 0,
+  };
+
+  // TODO: Fix issues with multiple properties affecting the same side.
+
+  const styleForAll = style[prefix];
+  if (styleForAll != null) {
+    for (const key of Object.keys(result)) {
+      result[key] = styleForAll;
+    }
+    hasParts = true;
   }
-  if (style[prefix + 'Horizontal']) {
-    res.left = res.right = style[prefix + 'Horizontal'];
-    set = true;
+
+  const styleForHorizontal = style[prefix + 'Horizontal'];
+  if (styleForHorizontal != null) {
+    result.left = styleForHorizontal;
+    result.right = styleForHorizontal;
+    hasParts = true;
+  } else {
+    const styleForLeft = style[prefix + 'Left'];
+    if (styleForLeft != null) {
+      result.left = styleForLeft;
+      hasParts = true;
+    }
+
+    const styleForRight = style[prefix + 'Right'];
+    if (styleForRight != null) {
+      result.right = styleForRight;
+      hasParts = true;
+    }
+
+    const styleForEnd = style[prefix + 'End'];
+    if (styleForEnd != null) {
+      if (I18nManager.isRTL && I18nManager.doLeftAndRightSwapInRTL) {
+        result.left = styleForEnd;
+      } else {
+        result.right = styleForEnd;
+      }
+      hasParts = true;
+    }
+    const styleForStart = style[prefix + 'Start'];
+    if (styleForStart != null) {
+      if (I18nManager.isRTL && I18nManager.doLeftAndRightSwapInRTL) {
+        result.right = styleForStart;
+      } else {
+        result.left = styleForStart;
+      }
+      hasParts = true;
+    }
   }
-  subs.forEach(sub => {
-    const val = style[prefix + capFirst(sub)];
-    if (val) {
-      res[sub] = val;
-      set = true;
+
+  const styleForVertical = style[prefix + 'Vertical'];
+  if (styleForVertical != null) {
+    result.bottom = styleForVertical;
+    result.top = styleForVertical;
+    hasParts = true;
+  } else {
+    const styleForBottom = style[prefix + 'Bottom'];
+    if (styleForBottom != null) {
+      result.bottom = styleForBottom;
+      hasParts = true;
+    }
+
+    const styleForTop = style[prefix + 'Top'];
+    if (styleForTop != null) {
+      result.top = styleForTop;
+      hasParts = true;
     }
-  });
-  if (!set) {
-    return;
   }
-  return res;
-}
 
-function capFirst(text) {
-  return text[0].toUpperCase() + text.slice(1);
+  return hasParts ? result : null;
 }
 
 module.exports = resolveBoxStyle;

From 569061dd8384a86cd27719b8b068360d8379f4c3 Mon Sep 17 00:00:00 2001
From: Douglas <dlowder@salesforce.com>
Date: Tue, 26 Jun 2018 17:38:09 -0700
Subject: [PATCH 0933/1109] Suppress spurious warning about RCTCxxModule
 (#19880)

Summary:
<!--
  Required: Write your motivation here.
  If this PR fixes an issue, type "Fixes #issueNumber" to automatically close the issue when the PR is merged.
-->

On a relatively stock / default setup of RN on iOS you'll see the warning "Class RCTCxxModule was not exported. Did you forget to use RCT_EXPORT_MODULE()?" pop up on every launch. This change resolves that issue.

Fixes #14806 .

This supersedes PR #19794 .

Try a fresh project by following the RN iOS tutorial, and observe that there are no more warnings after making this change.

[IOS] [MINOR] [CxxBridge] - Fix "Class RCTCxxModule was not exported"
Closes https://github.com/facebook/react-native/pull/19880

Differential Revision: D8653809

Pulled By: hramos

fbshipit-source-id: c48529c2d74ddd40a90bc0e06e405078e25b72e3
---
 React/Base/RCTBridge.m | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/React/Base/RCTBridge.m b/React/Base/RCTBridge.m
index f62074723c58..acfc09dd376c 100644
--- a/React/Base/RCTBridge.m
+++ b/React/Base/RCTBridge.m
@@ -106,6 +106,9 @@ void RCTVerifyAllModulesExported(NSArray *extraModules)
 
   for (unsigned int i = 0; i < classCount; i++) {
     Class cls = classes[i];
+    if (strncmp(class_getName(cls), "RCTCxxModule", strlen("RCTCxxModule")) == 0) {
+      continue;
+    }
     Class superclass = cls;
     while (superclass) {
       if (class_conformsToProtocol(superclass, @protocol(RCTBridgeModule))) {

From c972a5c298d8da26d583bbfa0f0713ef382692ba Mon Sep 17 00:00:00 2001
From: Alexey Kureev <kureev@fb.com>
Date: Tue, 26 Jun 2018 18:53:42 -0700
Subject: [PATCH 0934/1109] Fix: D8450498 breaks test_end_to_end job (#19910)

Summary:
Closes https://github.com/facebook/react-native/pull/19910

Because of the way react-native local-cli communicates with metro, getWatchFolders function was always returning an empty array that triggered an error.

Reviewed By: hramos

Differential Revision: D8650733

fbshipit-source-id: 502ca469cdbfa04dab5127c1e330dc1d34fc02f8
---
 local-cli/util/Config.js | 1 +
 1 file changed, 1 insertion(+)

diff --git a/local-cli/util/Config.js b/local-cli/util/Config.js
index bc7ba4716cdb..2e78e5041eb4 100644
--- a/local-cli/util/Config.js
+++ b/local-cli/util/Config.js
@@ -78,6 +78,7 @@ const Config = {
     ],
     getProjectRoots,
     getPolyfills,
+    getWatchFolders: () => [getProjectPath()],
     getResolverMainFields: () => ['react-native', 'browser', 'main'],
     getTransformModulePath: () =>
       require.resolve('metro/src/reactNativeTransformer'),

From a373bf705df46f31c660e25fd965868a56fee98d Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 26 Jun 2018 23:44:55 -0700
Subject: [PATCH 0935/1109] Remove implementation of Nodes (react/flat package)

Summary:
This diff removes the Nodes implementation from the source code. Why I'm deleting this code:
- I enabled nodes in catalyst app and it doesn't render even the first screen (see error images)
- This code is not being used at all inside facebook
- The last relevant commit I found was done in April 2017.
- Deleting this code make it easy to do refactors, as we don't have to modify this code.

When rendering an Image:
{F131075074}

When clicking on "RELOAD":
{F131075075}

Based on these errors I assume that this is not being used in Open Source. CC @[121800083:hramos]

Reviewed By: hramos

Differential Revision: D8640978

fbshipit-source-id: 243ee6440ebdbd24fd9f3daadc1066fd8487d9cc
---
 .../react/flat/AbstractDrawBorder.java        |  130 --
 .../react/flat/AbstractDrawCommand.java       |  299 ----
 .../com/facebook/react/flat/AndroidView.java  |   33 -
 .../react/flat/AttachDetachListener.java      |   28 -
 .../main/java/com/facebook/react/flat/BUCK    |   38 -
 .../react/flat/BitmapUpdateListener.java      |   16 -
 .../flat/ClippingDrawCommandManager.java      |  650 ---------
 .../react/flat/DrawBackgroundColor.java       |   31 -
 .../com/facebook/react/flat/DrawBorder.java   |  458 -------
 .../com/facebook/react/flat/DrawCommand.java  |   44 -
 .../react/flat/DrawCommandManager.java        |  156 ---
 .../com/facebook/react/flat/DrawImage.java    |   67 -
 .../react/flat/DrawImageWithDrawee.java       |  315 -----
 .../facebook/react/flat/DrawTextLayout.java   |   59 -
 .../com/facebook/react/flat/DrawView.java     |  233 ----
 .../react/flat/DraweeRequestHelper.java       |   80 --
 .../com/facebook/react/flat/ElementsList.java |  198 ---
 .../react/flat/FlatARTSurfaceViewManager.java |   60 -
 .../flat/FlatARTSurfaceViewShadowNode.java    |  143 --
 .../react/flat/FlatMeasuredViewGroup.java     |   24 -
 .../flat/FlatNativeViewHierarchyManager.java  |  261 ----
 .../react/flat/FlatReactModalShadowNode.java  |  105 --
 .../react/flat/FlatRootShadowNode.java        |   19 -
 .../react/flat/FlatRootViewManager.java       |   20 -
 .../facebook/react/flat/FlatShadowNode.java   |  570 --------
 .../react/flat/FlatTextShadowNode.java        |   81 --
 .../react/flat/FlatUIImplementation.java      |  608 ---------
 .../react/flat/FlatUIViewOperationQueue.java  |  527 --------
 .../facebook/react/flat/FlatViewGroup.java    | 1197 -----------------
 .../facebook/react/flat/FlatViewManager.java  |   29 -
 .../facebook/react/flat/FontStylingSpan.java  |  207 ---
 .../react/flat/HitSlopNodeRegion.java         |   56 -
 .../flat/HorizontalDrawCommandManager.java    |  124 --
 .../flat/InlineImageSpanWithPipeline.java     |  164 ---
 .../com/facebook/react/flat/MoveProxy.java    |  168 ---
 .../react/flat/NativeViewWrapper.java         |  130 --
 .../com/facebook/react/flat/NodeRegion.java   |  133 --
 .../react/flat/PipelineRequestHelper.java     |  186 ---
 .../com/facebook/react/flat/RCTImageView.java |  151 ---
 .../react/flat/RCTImageViewManager.java       |   67 -
 .../react/flat/RCTModalHostManager.java       |   26 -
 .../com/facebook/react/flat/RCTRawText.java   |   54 -
 .../react/flat/RCTRawTextManager.java         |   31 -
 .../java/com/facebook/react/flat/RCTText.java |  360 -----
 .../react/flat/RCTTextInlineImage.java        |   88 --
 .../react/flat/RCTTextInlineImageManager.java |   31 -
 .../com/facebook/react/flat/RCTTextInput.java |  191 ---
 .../react/flat/RCTTextInputManager.java       |   25 -
 .../facebook/react/flat/RCTTextManager.java   |   31 -
 .../java/com/facebook/react/flat/RCTView.java |  185 ---
 .../facebook/react/flat/RCTViewManager.java   |  140 --
 .../react/flat/RCTViewPagerManager.java       |   29 -
 .../facebook/react/flat/RCTVirtualText.java   |  307 -----
 .../react/flat/RCTVirtualTextManager.java     |   31 -
 .../java/com/facebook/react/flat/README.md    |   49 -
 .../facebook/react/flat/ShadowStyleSpan.java  |   72 -
 .../com/facebook/react/flat/StateBuilder.java |  729 ----------
 .../facebook/react/flat/TextNodeRegion.java   |   84 --
 .../facebook/react/flat/TypefaceCache.java    |  115 --
 .../flat/VerticalDrawCommandManager.java      |  124 --
 .../com/facebook/react/flat/ViewResolver.java |   14 -
 .../react/flat/VirtualViewManager.java        |   27 -
 .../main/java/com/facebook/react/shell/BUCK   |    1 -
 .../react/shell/MainReactPackage.java         |   50 +-
 64 files changed, 11 insertions(+), 10648 deletions(-)
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/AbstractDrawBorder.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/AbstractDrawCommand.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/AndroidView.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/AttachDetachListener.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/BUCK
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/BitmapUpdateListener.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/ClippingDrawCommandManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DrawBackgroundColor.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DrawBorder.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DrawCommand.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DrawCommandManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DrawImage.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DrawImageWithDrawee.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DrawTextLayout.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DrawView.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/DraweeRequestHelper.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/ElementsList.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatMeasuredViewGroup.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatNativeViewHierarchyManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatReactModalShadowNode.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatRootShadowNode.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatRootViewManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatShadowNode.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatTextShadowNode.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatUIImplementation.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatUIViewOperationQueue.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/FontStylingSpan.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/HitSlopNodeRegion.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/HorizontalDrawCommandManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/InlineImageSpanWithPipeline.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/MoveProxy.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/NativeViewWrapper.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/NodeRegion.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/PipelineRequestHelper.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTImageView.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTImageViewManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTModalHostManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTRawText.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTRawTextManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTText.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInlineImage.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInlineImageManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInput.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInputManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTView.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTViewManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTViewPagerManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTVirtualText.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/RCTVirtualTextManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/README.md
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/ShadowStyleSpan.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/StateBuilder.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/TextNodeRegion.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/TypefaceCache.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/VerticalDrawCommandManager.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/ViewResolver.java
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/flat/VirtualViewManager.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/AbstractDrawBorder.java b/ReactAndroid/src/main/java/com/facebook/react/flat/AbstractDrawBorder.java
deleted file mode 100644
index 9ebbf1baabcf..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/AbstractDrawBorder.java
+++ /dev/null
@@ -1,130 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.PathEffect;
-import android.graphics.RectF;
-
-/**
- * Base class for border drawing operations (used by DrawImage and DrawBorder). Draws rectangular or
- * rounded border along the rectangle, defined by the bounding box of the AbstractDrawCommand.
- */
-/* package */ abstract class AbstractDrawBorder extends AbstractDrawCommand {
-
-  private static final Paint PAINT = new Paint(Paint.ANTI_ALIAS_FLAG);
-  private static final RectF TMP_RECT = new RectF();
-  private static final int BORDER_PATH_DIRTY = 1 << 0;
-
-  static {
-    PAINT.setStyle(Paint.Style.STROKE);
-  }
-
-  private int mSetPropertiesFlag;
-  private int mBorderColor = Color.BLACK;
-  private float mBorderWidth;
-  private float mBorderRadius;
-  private @Nullable Path mPathForBorderRadius;
-
-  public final void setBorderWidth(float borderWidth) {
-    mBorderWidth = borderWidth;
-    setFlag(BORDER_PATH_DIRTY);
-  }
-
-  public final float getBorderWidth() {
-    return mBorderWidth;
-  }
-
-  public void setBorderRadius(float borderRadius) {
-    mBorderRadius = borderRadius;
-    setFlag(BORDER_PATH_DIRTY);
-  }
-
-  public final float getBorderRadius() {
-    return mBorderRadius;
-  }
-
-  public final void setBorderColor(int borderColor) {
-    mBorderColor = borderColor;
-  }
-
-  public final int getBorderColor() {
-    return mBorderColor;
-  }
-
-  @Override
-  protected void onBoundsChanged() {
-    setFlag(BORDER_PATH_DIRTY);
-  }
-
-  protected final void drawBorders(Canvas canvas) {
-    if (mBorderWidth < 0.5f) {
-      return;
-    }
-
-    if (mBorderColor == 0) {
-      return;
-    }
-
-    PAINT.setColor(mBorderColor);
-    PAINT.setStrokeWidth(mBorderWidth);
-    PAINT.setPathEffect(getPathEffectForBorderStyle());
-    canvas.drawPath(getPathForBorderRadius(), PAINT);
-  }
-
-  protected final void updatePath(Path path, float correction) {
-    path.reset();
-
-    TMP_RECT.set(
-        getLeft() + correction,
-        getTop() + correction,
-        getRight() - correction,
-        getBottom() - correction);
-
-    path.addRoundRect(
-        TMP_RECT,
-        mBorderRadius,
-        mBorderRadius,
-        Path.Direction.CW);
-  }
-
-  protected @Nullable PathEffect getPathEffectForBorderStyle() {
-    return null;
-  }
-
-  protected final boolean isFlagSet(int mask) {
-    return (mSetPropertiesFlag & mask) == mask;
-  }
-
-  protected final void setFlag(int mask) {
-    mSetPropertiesFlag |= mask;
-  }
-
-  protected final void resetFlag(int mask) {
-    mSetPropertiesFlag &= ~mask;
-  }
-
-  protected final Path getPathForBorderRadius() {
-    if (isFlagSet(BORDER_PATH_DIRTY)) {
-      if (mPathForBorderRadius == null) {
-        mPathForBorderRadius = new Path();
-      }
-
-      updatePath(mPathForBorderRadius, mBorderWidth * 0.5f);
-
-      resetFlag(BORDER_PATH_DIRTY);
-    }
-
-    return mPathForBorderRadius;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/AbstractDrawCommand.java b/ReactAndroid/src/main/java/com/facebook/react/flat/AbstractDrawCommand.java
deleted file mode 100644
index fd924b8d1104..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/AbstractDrawCommand.java
+++ /dev/null
@@ -1,299 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Typeface;
-
-/**
- * Base class for all DrawCommands. Becomes immutable once it has its bounds set. Until then, a
- * subclass is able to mutate any of its properties (e.g. updating Layout in DrawTextLayout).
- *
- * The idea is to be able to reuse unmodified objects when we build up DrawCommands before we ship
- * them to UI thread, but we can only do that if DrawCommands are immutable.
- */
-/* package */ abstract class AbstractDrawCommand extends DrawCommand implements Cloneable {
-
-  private float mLeft;
-  private float mTop;
-  private float mRight;
-  private float mBottom;
-  private boolean mFrozen;
-
-  protected boolean mNeedsClipping;
-  private float mClipLeft;
-  private float mClipTop;
-  private float mClipRight;
-  private float mClipBottom;
-
-  // Used to draw highlights in debug draw.
-  private static Paint sDebugHighlightRed;
-  private static Paint sDebugHighlightYellow;
-  private static Paint sDebugHighlightOverlayText;
-
-  public final boolean clipBoundsMatch(
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    return mClipLeft == clipLeft && mClipTop == clipTop
-        && mClipRight == clipRight && mClipBottom == clipBottom;
-  }
-
-  protected final void setClipBounds(
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    mClipLeft = clipLeft;
-    mClipTop = clipTop;
-    mClipRight = clipRight;
-    mClipBottom = clipBottom;
-    // We put this check here to not clip when we have the default [-infinity, infinity] bounds,
-    // since clipRect in those cases is essentially no-op anyway. This is needed to fix a bug that
-    // shows up during screenshot testing. Note that checking one side is enough, since if one side
-    // is infinite, all sides will be infinite, since we only set infinite for all sides at the
-    // same time - conversely, if one side is finite, all sides will be finite.
-    mNeedsClipping = mClipLeft != Float.NEGATIVE_INFINITY;
-  }
-
-  public final float getClipLeft() {
-    return mClipLeft;
-  }
-
-  public final float getClipTop() {
-    return mClipTop;
-  }
-
-  public final float getClipRight() {
-    return mClipRight;
-  }
-
-  public final float getClipBottom() {
-    return mClipBottom;
-  }
-
-  protected void applyClipping(Canvas canvas) {
-    canvas.clipRect(mClipLeft, mClipTop, mClipRight, mClipBottom);
-  }
-
-  /**
-   * Don't override this unless you need to do custom clipping in a draw command.  Otherwise just
-   * override onPreDraw and onDraw.
-   */
-  @Override
-  public void draw(FlatViewGroup parent, Canvas canvas) {
-    onPreDraw(parent, canvas);
-    if (mNeedsClipping && shouldClip()) {
-      canvas.save(Canvas.CLIP_SAVE_FLAG);
-      applyClipping(canvas);
-      onDraw(canvas);
-      canvas.restore();
-    } else {
-      onDraw(canvas);
-    }
-  }
-
-  protected static int getDebugBorderColor() {
-    return Color.CYAN;
-  }
-
-  protected String getDebugName() {
-    return getClass().getSimpleName().substring(4);
-  }
-
-  private void initDebugHighlightResources(FlatViewGroup parent) {
-    if (sDebugHighlightRed == null) {
-      sDebugHighlightRed = new Paint();
-      sDebugHighlightRed.setARGB(75, 255, 0, 0);
-    }
-    if (sDebugHighlightYellow == null) {
-      sDebugHighlightYellow = new Paint();
-      sDebugHighlightYellow.setARGB(100, 255, 204, 0);
-    }
-    if (sDebugHighlightOverlayText == null) {
-      sDebugHighlightOverlayText = new Paint();
-      sDebugHighlightOverlayText.setAntiAlias(true);
-      sDebugHighlightOverlayText.setARGB(200, 50, 50, 50);
-      sDebugHighlightOverlayText.setTextAlign(Paint.Align.RIGHT);
-      sDebugHighlightOverlayText.setTypeface(Typeface.MONOSPACE);
-      sDebugHighlightOverlayText.setTextSize(parent.dipsToPixels(9));
-    }
-  }
-
-  private void debugDrawHighlightRect(Canvas canvas, Paint paint, String text) {
-    canvas.drawRect(getLeft(), getTop(), getRight(), getBottom(), paint);
-    canvas.drawText(text, getRight() - 5, getBottom() - 5, sDebugHighlightOverlayText);
-  }
-
-  protected void debugDrawWarningHighlight(Canvas canvas, String text) {
-    debugDrawHighlightRect(canvas, sDebugHighlightRed, text);
-  }
-
-  protected void debugDrawCautionHighlight(Canvas canvas, String text) {
-    debugDrawHighlightRect(canvas, sDebugHighlightYellow, text);
-  }
-
-  @Override
-  public final void debugDraw(FlatViewGroup parent, Canvas canvas) {
-    onDebugDraw(parent, canvas);
-    if (FlatViewGroup.DEBUG_HIGHLIGHT_PERFORMANCE_ISSUES) {
-      initDebugHighlightResources(parent);
-      onDebugDrawHighlight(canvas);
-    }
-  }
-
-  protected void onDebugDraw(FlatViewGroup parent, Canvas canvas) {
-    parent.debugDrawNamedRect(
-        canvas,
-        getDebugBorderColor(),
-        getDebugName(),
-        mLeft,
-        mTop,
-        mRight,
-        mBottom);
-  }
-
-  protected void onDebugDrawHighlight(Canvas canvas) {
-  }
-
-  protected void onPreDraw(FlatViewGroup parent, Canvas canvas) {
-  }
-
-  /**
-   * Updates boundaries of the AbstractDrawCommand and freezes it.
-   * Will return a frozen copy if the current AbstractDrawCommand cannot be mutated.
-   *
-   * This should not be called on a DrawView, as the DrawView is modified on UI thread.  Use
-   * DrawView.collectDrawView instead to avoid race conditions.
-   */
-  public AbstractDrawCommand updateBoundsAndFreeze(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    if (mFrozen) {
-      // see if we can reuse it
-      boolean boundsMatch = boundsMatch(left, top, right, bottom);
-      boolean clipBoundsMatch = clipBoundsMatch(clipLeft, clipTop, clipRight, clipBottom);
-      if (boundsMatch && clipBoundsMatch) {
-        return this;
-      }
-
-      try {
-        AbstractDrawCommand copy = (AbstractDrawCommand) clone();
-        if (!boundsMatch) {
-          copy.setBounds(left, top, right, bottom);
-        }
-        if (!clipBoundsMatch) {
-          copy.setClipBounds(clipLeft, clipTop, clipRight, clipBottom);
-        }
-        return copy;
-      } catch (CloneNotSupportedException e) {
-        // This should not happen since AbstractDrawCommand implements Cloneable
-        throw new RuntimeException(e);
-      }
-    }
-
-    setBounds(left, top, right, bottom);
-    setClipBounds(clipLeft, clipTop, clipRight, clipBottom);
-    mFrozen = true;
-    return this;
-  }
-
-  /**
-   * Returns a non-frozen shallow copy of AbstractDrawCommand as defined by {@link Object#clone()}.
-   */
-  public final AbstractDrawCommand mutableCopy() {
-    try {
-      AbstractDrawCommand copy = (AbstractDrawCommand) super.clone();
-      copy.mFrozen = false;
-      return copy;
-    } catch (CloneNotSupportedException e) {
-      // should not happen since we implement Cloneable
-      throw new RuntimeException(e);
-    }
-  }
-
-  /**
-   * Returns whether this object was frozen and thus cannot be mutated.
-   */
-  public final boolean isFrozen() {
-    return mFrozen;
-  }
-
-  /**
-   * Mark this object as frozen, indicating that it should not be mutated.
-   */
-  public final void freeze() {
-    mFrozen = true;
-  }
-
-  /**
-   * Left position of this DrawCommand relative to the hosting View.
-   */
-  public final float getLeft() {
-    return mLeft;
-  }
-
-  /**
-   * Top position of this DrawCommand relative to the hosting View.
-   */
-  public final float getTop() {
-    return mTop;
-  }
-
-  /**
-   * Right position of this DrawCommand relative to the hosting View.
-   */
-  public final float getRight() {
-    return mRight;
-  }
-
-  /**
-   * Bottom position of this DrawCommand relative to the hosting View.
-   */
-  public final float getBottom() {
-    return mBottom;
-  }
-
-  protected abstract void onDraw(Canvas canvas);
-
-  protected boolean shouldClip() {
-    return mLeft < getClipLeft() || mTop < getClipTop() ||
-        mRight > getClipRight() || mBottom > getClipBottom();
-  }
-
-  protected void onBoundsChanged() {
-  }
-
-  /**
-   * Updates boundaries of this DrawCommand.
-   */
-  protected final void setBounds(float left, float top, float right, float bottom) {
-    mLeft = left;
-    mTop = top;
-    mRight = right;
-    mBottom = bottom;
-
-    onBoundsChanged();
-  }
-
-  /**
-   * Returns true if boundaries match and don't need to be updated. False otherwise.
-   */
-  protected final boolean boundsMatch(float left, float top, float right, float bottom) {
-    return mLeft == left && mTop == top && mRight == right && mBottom == bottom;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/AndroidView.java b/ReactAndroid/src/main/java/com/facebook/react/flat/AndroidView.java
deleted file mode 100644
index 9658620aced6..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/AndroidView.java
+++ /dev/null
@@ -1,33 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-interface AndroidView {
-
-  /**
-   * Whether or not custom layout is needed for the children
-   * @return a boolean representing whether custom layout is needed
-   */
-  boolean needsCustomLayoutForChildren();
-
-  /**
-   * Did the padding change
-   * @return a boolean representing whether the padding changed
-   */
-  boolean isPaddingChanged();
-
-  /**
-   * Reset the padding changed internal state
-   */
-  void resetPaddingChanged();
-
-  /**
-   * Get the padding for a certain spacingType defined in com.facebook.yoga.Spacing
-   */
-  float getPadding(int spacingType);
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/AttachDetachListener.java b/ReactAndroid/src/main/java/com/facebook/react/flat/AttachDetachListener.java
deleted file mode 100644
index 1498380f3edb..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/AttachDetachListener.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-/**
- * An interface that DrawCommands need to implement into order to receive
- * {@link android.view.View#onAttachedToWindow()} and
- * {@link android.view.View#onDetachedFromWindow()} events.
- */
-/* package */ interface AttachDetachListener {
-  public static final AttachDetachListener[] EMPTY_ARRAY = new AttachDetachListener[0];
-
-  /**
-   * Called when a DrawCommand is being attached to a visible View hierarchy.
-   * @param callback a WeakReference to a View that provides invalidate() helper method.
-   */
-  public void onAttached(FlatViewGroup.InvalidateCallback callback);
-
-  /**
-   * Called when a DrawCommand is being detached from a visible View hierarchy.
-   */
-  public void onDetached();
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/BUCK b/ReactAndroid/src/main/java/com/facebook/react/flat/BUCK
deleted file mode 100644
index bff3b936667b..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/BUCK
+++ /dev/null
@@ -1,38 +0,0 @@
-load("//ReactNative:DEFS.bzl", "YOGA_TARGET", "react_native_dep", "react_native_target", "rn_android_library")
-
-rn_android_library(
-    name = "flat",
-    srcs = glob(["*.java"]),
-    provided_deps = [
-        react_native_dep("third-party/android/support/v4:lib-support-v4"),
-    ],
-    visibility = [
-        "PUBLIC",
-    ],
-    deps = [
-        YOGA_TARGET,
-        react_native_dep("libraries/fbcore/src/main/java/com/facebook/common/logging:logging"),
-        react_native_dep("libraries/fresco/fresco-react-native:fbcore"),
-        react_native_dep("libraries/fresco/fresco-react-native:fresco-drawee"),
-        react_native_dep("libraries/fresco/fresco-react-native:fresco-react-native"),
-        react_native_dep("libraries/fresco/fresco-react-native:imagepipeline"),
-        react_native_dep("libraries/textlayoutbuilder:textlayoutbuilder"),
-        react_native_dep("third-party/java/infer-annotations:infer-annotations"),
-        react_native_dep("third-party/java/jsr-305:jsr-305"),
-        react_native_target("java/com/facebook/react/bridge:bridge"),
-        react_native_target("java/com/facebook/react/common:common"),
-        react_native_target("java/com/facebook/react/modules/fresco:fresco"),
-        react_native_target("java/com/facebook/react/modules/i18nmanager:i18nmanager"),
-        react_native_target("java/com/facebook/react/touch:touch"),
-        react_native_target("java/com/facebook/react/uimanager:uimanager"),
-        react_native_target("java/com/facebook/react/uimanager/annotations:annotations"),
-        react_native_target("java/com/facebook/react/views/art:art"),
-        react_native_target("java/com/facebook/react/views/image:image"),
-        react_native_target("java/com/facebook/react/views/imagehelper:withmultisource"),
-        react_native_target("java/com/facebook/react/views/modal:modal"),
-        react_native_target("java/com/facebook/react/views/text:text"),
-        react_native_target("java/com/facebook/react/views/textinput:textinput"),
-        react_native_target("java/com/facebook/react/views/view:view"),
-        react_native_target("java/com/facebook/react/views/viewpager:viewpager"),
-    ],
-)
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/BitmapUpdateListener.java b/ReactAndroid/src/main/java/com/facebook/react/flat/BitmapUpdateListener.java
deleted file mode 100644
index 3eeb4888d3e3..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/BitmapUpdateListener.java
+++ /dev/null
@@ -1,16 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Bitmap;
-
-/* package */ interface BitmapUpdateListener {
-  public void onSecondaryAttach(Bitmap bitmap);
-  public void onBitmapReady(Bitmap bitmap);
-  public void onImageLoadEvent(int imageLoadEvent);
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/ClippingDrawCommandManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/ClippingDrawCommandManager.java
deleted file mode 100644
index 390f8f9225e8..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/ClippingDrawCommandManager.java
+++ /dev/null
@@ -1,650 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-
-import android.graphics.Canvas;
-import android.graphics.Rect;
-import android.util.SparseArray;
-import android.util.SparseIntArray;
-import android.view.View;
-import android.view.animation.Animation;
-
-import com.facebook.common.logging.FLog;
-import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.uimanager.ReactClippingViewGroup;
-import com.facebook.react.uimanager.ReactClippingViewGroupHelper;
-
-/**
- * Abstract class for a {@link DrawCommandManager} with directional clipping.  Allows support for
- * vertical and horizontal clipping by implementing abstract methods.
- *
- * Uses two dynamic programming arrays to efficiently update which views and commands are onscreen,
- * while not having to sort the incoming draw commands.  The draw commands are loosely sorted, as
- * they represent a flattening of the normal view hierarchy, and we use that information to quickly
- * find children that should be considered onscreen.  One array keeps track of, for each index, the
- * maximum bottom position that occurs at or before that index; the other keeps track of the
- * minimum top position that occurs at or after that index. Given the following children:
- *
- *       +---------------------------------+    0 (Y coordinate)
- *       | 0                               |
- *       |  +-----------+                  |   10
- *       |  | 1         |                  |
- *       |  |           | +--------------+ |   20
- *       |  |           | | 3            | |
- *       |  +-----------+ |              | |   30
- *       |                |              | |
- *       |  +-----------+ |              | |   40
- *       |  | 2         | |              | |
- *       |  |           | +--------------+ |   50
- *       |  |           |                  |
- *       |  +-----------+                  |   60
- *       |                                 |
- *       +---------------------------------+   70
- *
- *          +-----------+                      80
- *          | 4         |
- *          |           | +--------------+     90
- *          |           | | 6            |
- *          +-----------+ |              |    100
- *                        |              |
- *          +-----------+ |              |    110
- *          | 5         | |              |
- *          |           | +--------------+    120
- *          |           |
- *          +-----------+                     130
- *
- * The two arrays are:
- *                 0   1   2   3    4    5    6
- *   Max Bottom: [70, 70, 70, 70, 100, 130, 130]
- *   Min Top:    [ 0,  0,  0,  0,  80,  90,  90]
- *
- * We can then binary search for the first max bottom that is above our rect, and the first min top
- * that is below our rect.
- *
- * If the top and bottom of the rect are 55 and 85, respectively, we will start drawing at index 0
- * and stop at index 4.
- *
- *       +---------------------------------+    0 (Y coordinate)
- *       | 0                               |
- *       |  +-----------+                  |   10
- *       |  | 1         |                  |
- *       |  |           | +--------------+ |   20
- *       |  |           | | 3            | |
- *       |  +-----------+ |              | |   30
- *       |                |              | |
- *       |  +-----------+ |              | |   40
- *       |  | 2         | |              | |
- *       |  |           | +--------------+ |   50
- *   -  -| -| -  -  -  -| -  -  -  -  -  - |-  -  -
- *       |  +-----------+                  |   60
- *       |                                 |
- *       +---------------------------------+   70
- *
- *          +-----------+                      80
- *   -  -  -| 4 -  -  - | -  -  -  -  -  -  -  -  -
- *          |           | +--------------+     90
- *          |           | | 6            |
- *          +-----------+ |              |    100
- *                        |              |
- *          +-----------+ |              |    110
- *          | 5         | |              |
- *          |           | +--------------+    120
- *          |           |
- *          +-----------+                     130
- *
- * If the top and bottom are 75 and 105 respectively, we will start drawing at index 4 and stop at
- * index 6.
- *
- *       +---------------------------------+    0 (Y coordinate)
- *       | 0                               |
- *       |  +-----------+                  |   10
- *       |  | 1         |                  |
- *       |  |           | +--------------+ |   20
- *       |  |           | | 3            | |
- *       |  +-----------+ |              | |   30
- *       |                |              | |
- *       |  +-----------+ |              | |   40
- *       |  | 2         | |              | |
- *       |  |           | +--------------+ |   50
- *       |  |           |                  |
- *       |  +-----------+                  |   60
- *       |                                 |
- *       +---------------------------------+   70
- *   -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -
- *          +-----------+                      80
- *          | 4         |
- *          |           | +--------------+     90
- *          |           | | 6            |
- *          +-----------+ |              |    100
- *   -  -  -  -  -  -  -  |-  -  -  -  - |  -  -  -
- *          +-----------+ |              |    110
- *          | 5         | |              |
- *          |           | +--------------+    120
- *          |           |
- *          +-----------+                     130
- *
- * While this doesn't map exactly to all of the commands that could be clipped, it means that
- * children which contain other children (a pretty common case when flattening views) are clipped
- * or unclipped as one logical unit.  This has the side effect of minimizing the amount of
- * invalidates coming from minor clipping rect adjustments.  The underlying dynamic programming
- * arrays can be calculated off the UI thread in O(n) time, requiring just two passes through the
- * command array.
- *
- * We do a similar optimization when searching for matching node regions, as node regions are
- * loosely sorted as well when clipping.
- */
-/* package */ abstract class ClippingDrawCommandManager extends DrawCommandManager {
-
-  private static final String TAG = ClippingDrawCommandManager.class.getSimpleName();
-
-  private final FlatViewGroup mFlatViewGroup;
-  private DrawCommand[] mDrawCommands = DrawCommand.EMPTY_ARRAY;
-  protected float[] mCommandMaxBottom = StateBuilder.EMPTY_FLOAT_ARRAY;
-  protected float[] mCommandMinTop = StateBuilder.EMPTY_FLOAT_ARRAY;
-
-  private NodeRegion[] mNodeRegions = NodeRegion.EMPTY_ARRAY;
-  protected float[] mRegionMaxBottom = StateBuilder.EMPTY_FLOAT_ARRAY;
-  protected float[] mRegionMinTop = StateBuilder.EMPTY_FLOAT_ARRAY;
-
-  // Onscreen bounds of draw command array.
-  private int mStart;
-  private int mStop;
-
-  // Mapping of ids to index position within the draw command array.  O(log n) lookups should be
-  // less in our case because of the large constant overhead and auto boxing of the map.
-  private SparseIntArray mDrawViewIndexMap = StateBuilder.EMPTY_SPARSE_INT;
-  // Map of views that are currently clipped.
-  private final SparseArray<View> mClippedSubviews = new SparseArray<>();
-
-  protected final Rect mClippingRect = new Rect();
-
-  // Used in updating the clipping rect, as sometimes we want to detach all views, which means we
-  // need to temporarily store the views we are detaching and removing.  These are always of size
-  // 0, except when used in update clipping rect.
-  private final SparseArray<View> mViewsToRemove = new SparseArray<>();
-  private final ArrayList<View> mViewsToKeep = new ArrayList<>();
-
-  // Currently clipping ViewGroups
-  private final ArrayList<ReactClippingViewGroup> mClippingViewGroups = new ArrayList<>();
-
-  ClippingDrawCommandManager(FlatViewGroup flatViewGroup, DrawCommand[] drawCommands) {
-    mFlatViewGroup = flatViewGroup;
-    initialSetup(drawCommands);
-  }
-
-  /**
-   * Initially setup this instance.  Makes sure the draw commands are mounted, and that our
-   * clipping rect reflects our current bounds.
-   *
-   * @param drawCommands The list of current draw commands.  In current implementations, this will
-   *   always be DrawCommand.EMPTY_ARRAY
-   */
-  private void initialSetup(DrawCommand[] drawCommands) {
-    mountDrawCommands(
-        drawCommands,
-        mDrawViewIndexMap,
-        mCommandMaxBottom,
-        mCommandMinTop,
-        true);
-    updateClippingRect();
-  }
-
-  /**
-   * @return index of the first command that could be on the screen.
-   */
-  abstract int commandStartIndex();
-
-  /**
-   * @return index of the first command that is guaranteed to be off the screen, starting from the
-   *   given start.
-   */
-  abstract int commandStopIndex(int start);
-
-  /**
-   * @return index of the first region that is guaranteed to be outside of the bounds for touch.
-   */
-  abstract int regionStopIndex(float touchX, float touchY);
-
-  /**
-   * Whether an index and all indices before it are guaranteed to be out of bounds for the current
-   * touch.
-   *
-   * @param index The region index to check.
-   * @param touchX X coordinate.
-   * @param touchY Y coordinate.
-   * @return true if the index and all before it are out of bounds.
-   */
-  abstract boolean regionAboveTouch(int index, float touchX, float touchY);
-
-  @Override
-  public void mountDrawCommands(
-      DrawCommand[] drawCommands,
-      SparseIntArray drawViewIndexMap,
-      float[] maxBottom,
-      float[] minTop,
-      boolean willMountViews) {
-    mDrawCommands = drawCommands;
-    mCommandMaxBottom = maxBottom;
-    mCommandMinTop = minTop;
-    mDrawViewIndexMap = drawViewIndexMap;
-    if (mClippingRect.bottom != mClippingRect.top) {
-      mStart = commandStartIndex();
-      mStop = commandStopIndex(mStart);
-      if (!willMountViews) {
-        // If we are not mounting views, we still need to update view indices and positions.  It is
-        // possible that a child changed size and we still need new clipping even though we are not
-        // mounting views.
-        updateClippingToCurrentRect();
-      }
-    }
-  }
-
-  @Override
-  public void mountNodeRegions(NodeRegion[] nodeRegions, float[] maxBottom, float[] minTop) {
-    mNodeRegions = nodeRegions;
-    mRegionMaxBottom = maxBottom;
-    mRegionMinTop = minTop;
-  }
-
-  @Override
-  public @Nullable NodeRegion virtualNodeRegionWithinBounds(float touchX, float touchY) {
-    int i = regionStopIndex(touchX, touchY);
-    while (i-- > 0) {
-      NodeRegion nodeRegion = mNodeRegions[i];
-      if (!nodeRegion.mIsVirtual) {
-        // only interested in virtual nodes
-        continue;
-      }
-      if (regionAboveTouch(i, touchX, touchY)) {
-        break;
-      }
-      if (nodeRegion.withinBounds(touchX, touchY)) {
-        return nodeRegion;
-      }
-    }
-
-    return null;
-  }
-
-  @Override
-  public @Nullable NodeRegion anyNodeRegionWithinBounds(float touchX, float touchY) {
-    int i = regionStopIndex(touchX, touchY);
-    while (i-- > 0) {
-      NodeRegion nodeRegion = mNodeRegions[i];
-      if (regionAboveTouch(i, touchX, touchY)) {
-        break;
-      }
-      if (nodeRegion.withinBounds(touchX, touchY)) {
-        return nodeRegion;
-      }
-    }
-
-    return null;
-  }
-
-  private void clip(int id, View view) {
-    mClippedSubviews.put(id, view);
-  }
-
-  private void unclip(int id) {
-    mClippedSubviews.remove(id);
-  }
-
-  private boolean isClipped(int id) {
-    return mClippedSubviews.get(id) != null;
-  }
-
-  private boolean isNotClipped(int id) {
-    return mClippedSubviews.get(id) == null;
-  }
-
-  @Override
-  void onClippedViewDropped(View view) {
-    unclip(view.getId());
-    mFlatViewGroup.removeDetachedView(view);
-  }
-
-  @Override
-  public void mountViews(ViewResolver viewResolver, int[] viewsToAdd, int[] viewsToDetach) {
-    mClippingViewGroups.clear();
-    for (int viewToAdd : viewsToAdd) {
-      // Views that are just temporarily detached are marked with a negative value.
-      boolean newView = viewToAdd > 0;
-      if (!newView) {
-        viewToAdd = -viewToAdd;
-      }
-
-      int commandArrayIndex = mDrawViewIndexMap.get(viewToAdd);
-      DrawView drawView = (DrawView) mDrawCommands[commandArrayIndex];
-      View view = viewResolver.getView(drawView.reactTag);
-      ensureViewHasNoParent(view);
-
-      // these views need to support recursive clipping of subviews
-      if (view instanceof ReactClippingViewGroup &&
-          ((ReactClippingViewGroup) view).getRemoveClippedSubviews()) {
-        mClippingViewGroups.add((ReactClippingViewGroup) view);
-      }
-
-      if (newView) {
-        // This view was not previously attached to this parent.
-        drawView.mWasMounted = true;
-        if (animating(view) || withinBounds(commandArrayIndex)) {
-          // View should be drawn.  This view can't currently be clipped because it wasn't
-          // previously attached to this parent.
-          mFlatViewGroup.addViewInLayout(view);
-        } else {
-          clip(drawView.reactTag, view);
-        }
-      } else {
-        // This view was previously attached, and just temporarily detached.
-        if (drawView.mWasMounted) {
-          // The DrawView has been mounted before.
-          if (isNotClipped(drawView.reactTag)) {
-            // The DrawView is not clipped.  Attach it.
-            mFlatViewGroup.attachViewToParent(view);
-          }
-          // else The DrawView has been previously mounted and is clipped, so don't attach it.
-        } else {
-          // We are mounting it, so lets get this part out of the way.
-          drawView.mWasMounted = true;
-          // The DrawView has not been mounted before, which means the bounds changed and triggered
-          // a new DrawView when it was collected from the shadow node.  We have a view with the
-          // same id temporarily detached, but its bounds have changed.
-          if (animating(view) || withinBounds(commandArrayIndex)) {
-            // View should be drawn.
-            if (isClipped(drawView.reactTag)) {
-              // View was clipped, so add it.
-              mFlatViewGroup.addViewInLayout(view);
-              unclip(drawView.reactTag);
-            } else {
-              // View was just temporarily removed, so attach it.  We already know it isn't clipped,
-              // so no need to unclip it.
-              mFlatViewGroup.attachViewToParent(view);
-            }
-          } else {
-            // View should be clipped.
-            if (isNotClipped(drawView.reactTag)) {
-              // View was onscreen.
-              mFlatViewGroup.removeDetachedView(view);
-              clip(drawView.reactTag, view);
-            }
-            // else view is already clipped and not within bounds.
-          }
-        }
-      }
-    }
-
-    for (int viewToDetach : viewsToDetach) {
-      View view = viewResolver.getView(viewToDetach);
-      if (view.getParent() != null) {
-        throw new RuntimeException("Trying to remove view not owned by FlatViewGroup");
-      } else {
-        mFlatViewGroup.removeDetachedView(view);
-      }
-      // The view isn't clipped anymore, but gone entirely.
-      unclip(viewToDetach);
-    }
-  }
-
-  /**
-   * Returns true if a view is currently animating.
-   */
-  private static boolean animating(View view) {
-    Animation animation = view.getAnimation();
-    return animation != null && !animation.hasEnded();
-  }
-
-  /**
-   * Returns true if a command index is currently onscreen.
-   */
-  private boolean withinBounds(int i) {
-    return mStart <= i && i < mStop;
-  }
-
-  @Override
-  public boolean updateClippingRect() {
-    ReactClippingViewGroupHelper.calculateClippingRect(mFlatViewGroup, mClippingRect);
-    if (mFlatViewGroup.getParent() == null || mClippingRect.top == mClippingRect.bottom) {
-      // If we are unparented or are clipping to an empty rect, no op.  Return false so we don't
-      // invalidate.
-      return false;
-    }
-
-    int start = commandStartIndex();
-    int stop = commandStopIndex(start);
-    if (mStart <= start && stop <= mStop) {
-      // We would only be removing children, don't invalidate and don't bother changing the
-      // attached children.
-      updateClippingRecursively();
-      return false;
-    }
-
-    mStart = start;
-    mStop = stop;
-
-    updateClippingToCurrentRect();
-    updateClippingRecursively();
-    return true;
-  }
-
-  private void updateClippingRecursively() {
-    for (int i = 0, children = mClippingViewGroups.size(); i < children; i++) {
-      ReactClippingViewGroup view = mClippingViewGroups.get(i);
-      if (isNotClipped(((View) view).getId())) {
-        view.updateClippingRect();
-      }
-    }
-  }
-
-  /**
-   * Used either after we have updated the current rect, or when we have mounted new commands and
-   * the rect hasn't changed.  Updates the clipping after mStart and mStop have been set to the
-   * correct values.  For draw commands, this is all it takes to update the command mounting, as
-   * draw commands are only attached in a conceptual sense, and don't rely on the android view
-   * hierarchy.
-   *
-   * For native children, we have to walk through our current views and remove any that are no
-   * longer on screen, and add those that are newly on screen.  As an optimization for fling, if we
-   * are removing two or more native views we instead detachAllViews from the {@link FlatViewGroup}
-   * and re-attach or add as needed.
-   *
-   * This approximation is roughly correct, as we tend to add and remove the same amount of views,
-   * and each add and remove pair is O(n); detachAllViews and re-attach requires two passes, so
-   * using this once we are removing more than two native views is a good breakpoint.
-   */
-  private void updateClippingToCurrentRect() {
-    for (int i = 0, size = mFlatViewGroup.getChildCount(); i < size; i++) {
-      View view = mFlatViewGroup.getChildAt(i);
-      int index = mDrawViewIndexMap.get(view.getId());
-      if (withinBounds(index) || animating(view)) {
-        mViewsToKeep.add(view);
-      } else {
-        mViewsToRemove.append(i, view);
-        clip(view.getId(), view);
-      }
-    }
-
-    int removeSize = mViewsToRemove.size();
-    boolean removeAll = removeSize > 2;
-
-    if (removeAll) {
-      // Detach all, as we are changing quite a few views, whether flinging or otherwise.
-      mFlatViewGroup.detachAllViewsFromParent();
-
-      for (int i = 0; i < removeSize; i++) {
-        mFlatViewGroup.removeDetachedView(mViewsToRemove.valueAt(i));
-      }
-    } else {
-      // Simple clipping sweep, as we are changing relatively few views.
-      while (removeSize-- > 0) {
-        mFlatViewGroup.removeViewsInLayout(mViewsToRemove.keyAt(removeSize), 1);
-      }
-    }
-    mViewsToRemove.clear();
-
-    int current = mStart;
-    int childIndex = 0;
-
-    for (int i = 0, size = mViewsToKeep.size(); i < size; i++) {
-      View view = mViewsToKeep.get(i);
-      int commandIndex = mDrawViewIndexMap.get(view.getId());
-      if (current <= commandIndex) {
-        while (current != commandIndex) {
-          if (mDrawCommands[current] instanceof DrawView) {
-            DrawView drawView = (DrawView) mDrawCommands[current];
-            mFlatViewGroup.addViewInLayout(
-                Assertions.assumeNotNull(mClippedSubviews.get(drawView.reactTag)),
-                childIndex++);
-            unclip(drawView.reactTag);
-          }
-          current++;
-        }
-        // We are currently at the command index, but we want to increment beyond it.
-        current++;
-      }
-      if (removeAll) {
-        mFlatViewGroup.attachViewToParent(view, childIndex);
-      }
-      // We want to make sure we increment the child index even if we didn't detach it to maintain
-      // order.
-      childIndex++;
-    }
-    mViewsToKeep.clear();
-
-    while (current < mStop) {
-      if (mDrawCommands[current] instanceof DrawView) {
-        DrawView drawView = (DrawView) mDrawCommands[current];
-        mFlatViewGroup.addViewInLayout(
-            Assertions.assumeNotNull(mClippedSubviews.get(drawView.reactTag)),
-            childIndex++);
-        unclip(drawView.reactTag);
-      }
-      current++;
-    }
-  }
-
-  @Override
-  public void getClippingRect(Rect outClippingRect) {
-    outClippingRect.set(mClippingRect);
-  }
-
-  @Override
-  public SparseArray<View> getDetachedViews() {
-    return mClippedSubviews;
-  }
-
-  /**
-   * Draws the unclipped commands on the given canvas.  This would be much simpler if we didn't
-   * have to worry about animating views, as we could simply:
-   *
-   *   for (int i = start; i < stop; i++) {
-   *     drawCommands[i].draw(...);
-   *   }
-   *
-   * This is complicated however by animating views, which may occur before or after the current
-   * clipping rect.  Consider the following array:
-   *
-   *   +--------------+
-   *   |  DrawView    | 0
-   *   | *animating*  |
-   *   +--------------+
-   *   | DrawCommmand | 1
-   *   |  *clipped*   |
-   *   +--------------+
-   *   | DrawCommand  | 2 start
-   *   |              |
-   *   +--------------+
-   *   | DrawCommand  | 3
-   *   |              |
-   *   +--------------+
-   *   |  DrawView    | 4
-   *   |              |
-   *   +--------------+
-   *   |  DrawView    | 5 stop
-   *   |  *clipped*   |
-   *   +--------------+
-   *   |  DrawView    | 6
-   *   | *animating*  |
-   *   +--------------+
-   *
-   * 2, 3, and 4 are onscreen according to bounds, while 0 and 6 are onscreen according to
-   * animation.  We have to walk through the attached children making sure to draw any draw
-   * commands that should be drawn before that draw view, as well as making sure not to draw any
-   * draw commands that are out of bounds.
-   *
-   * @param canvas The canvas to draw on.
-   */
-  @Override
-  public void draw(Canvas canvas) {
-    int commandIndex = mStart;
-    int size = mFlatViewGroup.getChildCount();
-
-    // Iterate through the children, making sure that we draw any draw commands we haven't drawn
-    // that should happen before the next draw view.
-    for (int i = 0; i < size; i++) {
-      // This is the command index of the next view that we need to draw.  Since a view might be
-      // animating, this view is either before all the commands onscreen, onscreen, or after the
-      // onscreen commands.
-      int viewIndex = mDrawViewIndexMap.get(mFlatViewGroup.getChildAt(i).getId());
-      if (mStop < viewIndex) {
-        // The current view is outside of the viewport bounds.  We want to draw all the commands
-        // up to the stop, then draw all the views outside the viewport bounds.
-        while (commandIndex < mStop) {
-          mDrawCommands[commandIndex++].draw(mFlatViewGroup, canvas);
-        }
-        // We are now out of commands to draw, so we could just draw the remaining attached
-        // children, but the for loop logic will draw the rest anyway.
-      } else if (commandIndex <= viewIndex) {
-        // The viewIndex is within our onscreen bounds (or == stop).  We want to draw all the
-        // commands from the current position to the current view, inclusive.
-        while (commandIndex < viewIndex) {
-          mDrawCommands[commandIndex++].draw(mFlatViewGroup, canvas);
-        }
-        // Command index now == viewIndex, so increment beyond it.
-        commandIndex++;
-      }
-      mDrawCommands[viewIndex].draw(mFlatViewGroup, canvas);
-    }
-
-    // If we get here, it means we have drawn all the views, now just draw the remaining draw
-    // commands.
-    while (commandIndex < mStop) {
-      DrawCommand command = mDrawCommands[commandIndex++];
-      if (command instanceof DrawView) {
-        // We should never have more DrawView commands at this point. But in case we do, fail safely
-        // by ignoring the DrawView command
-        FLog.w(
-            TAG,
-            "Unexpected DrawView command at index " + (commandIndex-1) + " with mStop=" +
-              mStop + ". " + Arrays.toString(mDrawCommands));
-        continue;
-      }
-      command.draw(mFlatViewGroup, canvas);
-    }
-  }
-
-  @Override
-  void debugDraw(Canvas canvas) {
-    // Draws clipped draw commands, but does not draw clipped views.
-    for (DrawCommand drawCommand : mDrawCommands) {
-      if (drawCommand instanceof DrawView) {
-        if (isNotClipped(((DrawView) drawCommand).reactTag)) {
-          drawCommand.debugDraw(mFlatViewGroup, canvas);
-        }
-        // else, don't draw, and don't increment index
-      } else {
-        drawCommand.debugDraw(mFlatViewGroup, canvas);
-      }
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawBackgroundColor.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DrawBackgroundColor.java
deleted file mode 100644
index ec9291180d7b..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawBackgroundColor.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Canvas;
-import android.graphics.Paint;
-
-/**
- * Draws background for a FlatShadowNode as a solid rectangle.
- */
-/* package */ final class DrawBackgroundColor extends AbstractDrawCommand {
-
-  private static final Paint PAINT = new Paint();
-
-  private final int mBackgroundColor;
-
-  /* package */ DrawBackgroundColor(int backgroundColor) {
-    mBackgroundColor = backgroundColor;
-  }
-
-  @Override
-  public void onDraw(Canvas canvas) {
-    PAINT.setColor(mBackgroundColor);
-    canvas.drawRect(getLeft(), getTop(), getRight(), getBottom(), PAINT);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawBorder.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DrawBorder.java
deleted file mode 100644
index d48b3d326c2a..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawBorder.java
+++ /dev/null
@@ -1,458 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.DashPathEffect;
-import android.graphics.Paint;
-import android.graphics.Path;
-
-import com.facebook.react.uimanager.Spacing;
-
-/* package */ final class DrawBorder extends AbstractDrawBorder {
-
-  private static final Paint PAINT = new Paint(Paint.ANTI_ALIAS_FLAG);
-  private static final float[] TMP_FLOAT_ARRAY = new float[4];
-
-  private static final int BORDER_STYLE_SOLID = 0;
-  private static final int BORDER_STYLE_DOTTED = 1;
-  private static final int BORDER_STYLE_DASHED = 2;
-
-  private static final int BORDER_LEFT_COLOR_SET = 1 << 1;
-  private static final int BORDER_TOP_COLOR_SET = 1 << 2;
-  private static final int BORDER_RIGHT_COLOR_SET = 1 << 3;
-  private static final int BORDER_BOTTOM_COLOR_SET = 1 << 4;
-  private static final int BORDER_PATH_EFFECT_DIRTY = 1 << 5;
-
-  // ~0 == 0xFFFFFFFF, all bits set to 1.
-  private static final int ALL_BITS_SET = ~0;
-  // 0 == 0x00000000, all bits set to 0.
-  private static final int ALL_BITS_UNSET = 0;
-
-  private float mBorderLeftWidth;
-  private float mBorderTopWidth;
-  private float mBorderRightWidth;
-  private float mBorderBottomWidth;
-
-  private int mBorderLeftColor;
-  private int mBorderTopColor;
-  private int mBorderRightColor;
-  private int mBorderBottomColor;
-
-  private int mBorderStyle = BORDER_STYLE_SOLID;
-
-  private int mBackgroundColor;
-
-  private @Nullable DashPathEffect mPathEffectForBorderStyle;
-  private @Nullable Path mPathForBorder;
-
-  public void setBorderWidth(int position, float borderWidth) {
-    switch (position) {
-      case Spacing.LEFT:
-        mBorderLeftWidth = borderWidth;
-        break;
-      case Spacing.TOP:
-        mBorderTopWidth = borderWidth;
-        break;
-      case Spacing.RIGHT:
-        mBorderRightWidth = borderWidth;
-        break;
-      case Spacing.BOTTOM:
-        mBorderBottomWidth = borderWidth;
-        break;
-      case Spacing.ALL:
-        setBorderWidth(borderWidth);
-        break;
-    }
-  }
-
-  public float getBorderWidth(int position) {
-    switch (position) {
-      case Spacing.LEFT:
-        return mBorderLeftWidth;
-      case Spacing.TOP:
-        return mBorderTopWidth;
-      case Spacing.RIGHT:
-        return mBorderRightWidth;
-      case Spacing.BOTTOM:
-        return mBorderBottomWidth;
-      case Spacing.ALL:
-        return getBorderWidth();
-    }
-
-    return 0.0f;
-  }
-
-  public void setBorderStyle(@Nullable String style) {
-    if ("dotted".equals(style)) {
-      mBorderStyle = BORDER_STYLE_DOTTED;
-    } else if ("dashed".equals(style)) {
-      mBorderStyle = BORDER_STYLE_DASHED;
-    } else {
-      mBorderStyle = BORDER_STYLE_SOLID;
-    }
-
-    setFlag(BORDER_PATH_EFFECT_DIRTY);
-  }
-
-  public void resetBorderColor(int position) {
-    switch (position) {
-      case Spacing.LEFT:
-        resetFlag(BORDER_LEFT_COLOR_SET);
-        break;
-      case Spacing.TOP:
-        resetFlag(BORDER_TOP_COLOR_SET);
-        break;
-      case Spacing.RIGHT:
-        resetFlag(BORDER_RIGHT_COLOR_SET);
-        break;
-      case Spacing.BOTTOM:
-        resetFlag(BORDER_BOTTOM_COLOR_SET);
-        break;
-      case Spacing.ALL:
-        setBorderColor(Color.BLACK);
-        break;
-    }
-  }
-
-  public void setBorderColor(int position, int borderColor) {
-    switch (position) {
-      case Spacing.LEFT:
-        mBorderLeftColor = borderColor;
-        setFlag(BORDER_LEFT_COLOR_SET);
-        break;
-      case Spacing.TOP:
-        mBorderTopColor = borderColor;
-        setFlag(BORDER_TOP_COLOR_SET);
-        break;
-      case Spacing.RIGHT:
-        mBorderRightColor = borderColor;
-        setFlag(BORDER_RIGHT_COLOR_SET);
-        break;
-      case Spacing.BOTTOM:
-        mBorderBottomColor = borderColor;
-        setFlag(BORDER_BOTTOM_COLOR_SET);
-        break;
-      case Spacing.ALL:
-        setBorderColor(borderColor);
-        break;
-    }
-  }
-
-  public int getBorderColor(int position) {
-    int defaultColor = getBorderColor();
-    switch (position) {
-      case Spacing.LEFT:
-        return resolveBorderColor(BORDER_LEFT_COLOR_SET, mBorderLeftColor, defaultColor);
-      case Spacing.TOP:
-        return resolveBorderColor(BORDER_TOP_COLOR_SET, mBorderTopColor, defaultColor);
-      case Spacing.RIGHT:
-        return resolveBorderColor(BORDER_RIGHT_COLOR_SET, mBorderRightColor, defaultColor);
-      case Spacing.BOTTOM:
-        return resolveBorderColor(BORDER_BOTTOM_COLOR_SET, mBorderBottomColor, defaultColor);
-      case Spacing.ALL:
-        return defaultColor;
-    }
-
-    return defaultColor;
-  }
-
-  public void setBackgroundColor(int backgroundColor) {
-    mBackgroundColor = backgroundColor;
-  }
-
-  public int getBackgroundColor() {
-    return mBackgroundColor;
-  }
-
-  @Override
-  protected void onDraw(Canvas canvas) {
-    if (getBorderRadius() >= 0.5f || getPathEffectForBorderStyle() != null) {
-      drawRoundedBorders(canvas);
-    } else {
-      drawRectangularBorders(canvas);
-    }
-  }
-
-  @Override
-  protected @Nullable DashPathEffect getPathEffectForBorderStyle() {
-    if (isFlagSet(BORDER_PATH_EFFECT_DIRTY)) {
-      switch (mBorderStyle) {
-        case BORDER_STYLE_DOTTED:
-          mPathEffectForBorderStyle = createDashPathEffect(getBorderWidth());
-          break;
-
-        case BORDER_STYLE_DASHED:
-          mPathEffectForBorderStyle = createDashPathEffect(getBorderWidth() * 3);
-          break;
-
-        default:
-          mPathEffectForBorderStyle = null;
-          break;
-      }
-
-      resetFlag(BORDER_PATH_EFFECT_DIRTY);
-    }
-
-    return mPathEffectForBorderStyle;
-  }
-
-  private void drawRoundedBorders(Canvas canvas) {
-    if (mBackgroundColor != 0) {
-      PAINT.setColor(mBackgroundColor);
-      canvas.drawPath(getPathForBorderRadius(), PAINT);
-    }
-
-    drawBorders(canvas);
-  }
-
-  /**
-   * Quickly determine if all the set border colors are equal.  Bitwise AND all the set colors
-   * together, then OR them all together.  If the AND and the OR are the same, then the colors
-   * are compatible, so return this color.
-   *
-   * Used to avoid expensive path creation and expensive calls to canvas.drawPath
-   *
-   * @return A compatible border color, or zero if the border colors are not compatible.
-   */
-  private static int fastBorderCompatibleColorOrZero(
-      float borderLeft,
-      float borderTop,
-      float borderRight,
-      float borderBottom,
-      int colorLeft,
-      int colorTop,
-      int colorRight,
-      int colorBottom) {
-    int andSmear = (borderLeft > 0 ? colorLeft : ALL_BITS_SET) &
-        (borderTop > 0 ? colorTop : ALL_BITS_SET) &
-        (borderRight > 0 ? colorRight : ALL_BITS_SET) &
-        (borderBottom > 0 ? colorBottom : ALL_BITS_SET);
-    int orSmear = (borderLeft > 0 ? colorLeft : ALL_BITS_UNSET) |
-        (borderTop > 0 ? colorTop : ALL_BITS_UNSET) |
-        (borderRight > 0 ? colorRight : ALL_BITS_UNSET) |
-        (borderBottom > 0 ? colorBottom : ALL_BITS_UNSET);
-    return andSmear == orSmear ? andSmear : 0;
-  }
-
-  private void drawRectangularBorders(Canvas canvas) {
-    int defaultColor = getBorderColor();
-    float defaultWidth = getBorderWidth();
-
-    float top = getTop();
-    float borderTop = resolveWidth(mBorderTopWidth, defaultWidth);
-    float topInset = top + borderTop;
-    int topColor = resolveBorderColor(BORDER_TOP_COLOR_SET, mBorderTopColor, defaultColor);
-
-    float bottom = getBottom();
-    float borderBottom = resolveWidth(mBorderBottomWidth, defaultWidth);
-    float bottomInset = bottom - borderBottom;
-    int bottomColor = resolveBorderColor(BORDER_BOTTOM_COLOR_SET, mBorderBottomColor, defaultColor);
-
-    float left = getLeft();
-    float borderLeft = resolveWidth(mBorderLeftWidth, defaultWidth);
-    float leftInset = left + borderLeft;
-    int leftColor = resolveBorderColor(BORDER_LEFT_COLOR_SET, mBorderLeftColor, defaultColor);
-
-    float right = getRight();
-    float borderRight = resolveWidth(mBorderRightWidth, defaultWidth);
-    float rightInset = right - borderRight;
-    int rightColor = resolveBorderColor(BORDER_RIGHT_COLOR_SET, mBorderRightColor, defaultColor);
-
-    // Check for fast path to border drawing.
-    int fastBorderColor = fastBorderCompatibleColorOrZero(
-        borderLeft,
-        borderTop,
-        borderRight,
-        borderBottom,
-        leftColor,
-        topColor,
-        rightColor,
-        bottomColor);
-    if (fastBorderColor != 0) {
-      // Fast border color draw.
-      if (Color.alpha(fastBorderColor) != 0) {
-        // Border color is not transparent.
-
-        // Draw center.
-        if (Color.alpha(mBackgroundColor) != 0) {
-          PAINT.setColor(mBackgroundColor);
-          if (Color.alpha(fastBorderColor) == 255) {
-            // The border will draw over the edges, so only draw the inset background.
-            canvas.drawRect(leftInset, topInset, rightInset, bottomInset, PAINT);
-          } else {
-            // The border is opaque, so we have to draw the entire background color.
-            canvas.drawRect(left, top, right, bottom, PAINT);
-          }
-        }
-
-        PAINT.setColor(fastBorderColor);
-        if (borderLeft > 0) {
-          canvas.drawRect(left, top, leftInset, bottom - borderBottom, PAINT);
-        }
-        if (borderTop > 0) {
-          canvas.drawRect(left + borderLeft, top, right, topInset, PAINT);
-        }
-        if (borderRight > 0) {
-          canvas.drawRect(rightInset, top + borderTop, right, bottom, PAINT);
-        }
-        if (borderBottom > 0) {
-          canvas.drawRect(left, bottomInset, right - borderRight, bottom, PAINT);
-        }
-      }
-    } else {
-      if (mPathForBorder == null) {
-        mPathForBorder = new Path();
-      }
-
-      // Draw center.  Any of the borders might be opaque or transparent, so we need to draw this.
-      if (Color.alpha(mBackgroundColor) != 0) {
-        PAINT.setColor(mBackgroundColor);
-        canvas.drawRect(left, top, right, bottom, PAINT);
-      }
-
-      // Draw top.
-      if (borderTop != 0 && Color.alpha(topColor) != 0) {
-        PAINT.setColor(topColor);
-        updatePathForTopBorder(
-            mPathForBorder,
-            top,
-            topInset,
-            left,
-            leftInset,
-            right,
-            rightInset);
-        canvas.drawPath(mPathForBorder, PAINT);
-      }
-
-      // Draw bottom.
-      if (borderBottom != 0 && Color.alpha(bottomColor) != 0) {
-        PAINT.setColor(bottomColor);
-        updatePathForBottomBorder(
-            mPathForBorder,
-            bottom,
-            bottomInset,
-            left,
-            leftInset,
-            right,
-            rightInset);
-        canvas.drawPath(mPathForBorder, PAINT);
-      }
-
-      // Draw left.
-      if (borderLeft != 0 && Color.alpha(leftColor) != 0) {
-        PAINT.setColor(leftColor);
-        updatePathForLeftBorder(
-            mPathForBorder,
-            top,
-            topInset,
-            bottom,
-            bottomInset,
-            left,
-            leftInset);
-        canvas.drawPath(mPathForBorder, PAINT);
-      }
-
-      // Draw right.
-      if (borderRight != 0 && Color.alpha(rightColor) != 0) {
-        PAINT.setColor(rightColor);
-        updatePathForRightBorder(
-            mPathForBorder,
-            top,
-            topInset,
-            bottom,
-            bottomInset,
-            right,
-            rightInset);
-        canvas.drawPath(mPathForBorder, PAINT);
-      }
-    }
-  }
-
-  private static void updatePathForTopBorder(
-      Path path,
-      float top,
-      float topInset,
-      float left,
-      float leftInset,
-      float right,
-      float rightInset) {
-    path.reset();
-    path.moveTo(left, top);
-    path.lineTo(leftInset, topInset);
-    path.lineTo(rightInset, topInset);
-    path.lineTo(right, top);
-    path.lineTo(left, top);
-  }
-
-  private static void updatePathForBottomBorder(
-      Path path,
-      float bottom,
-      float bottomInset,
-      float left,
-      float leftInset,
-      float right,
-      float rightInset) {
-    path.reset();
-    path.moveTo(left, bottom);
-    path.lineTo(right, bottom);
-    path.lineTo(rightInset, bottomInset);
-    path.lineTo(leftInset, bottomInset);
-    path.lineTo(left, bottom);
-  }
-
-  private static void updatePathForLeftBorder(
-      Path path,
-      float top,
-      float topInset,
-      float bottom,
-      float bottomInset,
-      float left,
-      float leftInset) {
-    path.reset();
-    path.moveTo(left, top);
-    path.lineTo(leftInset, topInset);
-    path.lineTo(leftInset, bottomInset);
-    path.lineTo(left, bottom);
-    path.lineTo(left, top);
-  }
-
-  private static void updatePathForRightBorder(
-      Path path,
-      float top,
-      float topInset,
-      float bottom,
-      float bottomInset,
-      float right,
-      float rightInset) {
-    path.reset();
-    path.moveTo(right, top);
-    path.lineTo(right, bottom);
-    path.lineTo(rightInset, bottomInset);
-    path.lineTo(rightInset, topInset);
-    path.lineTo(right, top);
-  }
-
-  private int resolveBorderColor(int flag, int color, int defaultColor) {
-    return isFlagSet(flag) ? color : defaultColor;
-  }
-
-  private static float resolveWidth(float width, float defaultWidth) {
-    return (width == 0 || /* check for NaN */ width != width) ? defaultWidth : width;
-  }
-
-  private static DashPathEffect createDashPathEffect(float borderWidth) {
-    for (int i = 0; i < 4; ++i) {
-      TMP_FLOAT_ARRAY[i] = borderWidth;
-    }
-    return new DashPathEffect(TMP_FLOAT_ARRAY, 0);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawCommand.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DrawCommand.java
deleted file mode 100644
index b7f2d5f41f90..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawCommand.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Canvas;
-
-/**
- * DrawCommand is an interface that shadow nodes need to implement to do the drawing.
- * Instances of DrawCommand are created in background thread and passed to UI thread.
- * Once a DrawCommand is shared with UI thread, it can no longer be mutated in background thread.
- */
-public abstract class DrawCommand {
-  // used by StateBuilder, FlatViewGroup and FlatShadowNode
-  /* package */ static final DrawCommand[] EMPTY_ARRAY = new DrawCommand[0];
-
-  /**
-   * Performs drawing into the given canvas.
-   *
-   * @param parent The parent to get child information from, if needed
-   * @param canvas The canvas to draw into
-   */
-  abstract void draw(FlatViewGroup parent, Canvas canvas);
-
-  /**
-   * Performs debug bounds drawing into the given canvas.
-   *
-   * @param parent The parent to get child information from, if needed
-   * @param canvas The canvas to draw into
-   */
-  abstract void debugDraw(FlatViewGroup parent, Canvas canvas);
-
-  abstract float getLeft();
-
-  abstract float getTop();
-
-  abstract float getRight();
-
-  abstract float getBottom();
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawCommandManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DrawCommandManager.java
deleted file mode 100644
index bdab8db25e86..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawCommandManager.java
+++ /dev/null
@@ -1,156 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Canvas;
-import android.graphics.Rect;
-import android.util.SparseArray;
-import android.util.SparseIntArray;
-import android.view.View;
-import android.view.ViewParent;
-
-/**
- * Underlying logic which handles draw commands, views and node regions when clipping in a
- * {@link FlatViewGroup}.
- */
-/* package */ abstract class DrawCommandManager {
-
-  /**
-   * Mount a set of draw commands to this manager.  The order the commands are given is the order in
-   * which they should be drawn.  If any of the commands are new DrawViews, then mountViews will be
-   * called after by the UIManager.
-   *
-   * @param drawCommands The draw commands to mount.
-   * @param drawViewIndexMap Mapping of ids to index position within the draw command array.
-   * @param maxBottom At each index i, the maximum bottom value (or right value in the case of
-   *   horizontal clipping) value of all draw commands at or below i.
-   * @param minTop At each index i, the minimum top value (or left value in the case of horizontal
-   *   clipping) value of all draw commands at or below i.
-   * @param willMountViews Whether we are going to also receive a mountViews command in this state
-   *   cycle.
-   */
-  abstract void mountDrawCommands(
-      DrawCommand[] drawCommands,
-      SparseIntArray drawViewIndexMap,
-      float[] maxBottom,
-      float[] minTop,
-      boolean willMountViews);
-
-  /**
-   * Add and detach a set of views.  The views added here will already have a DrawView passed in
-   * mountDrawCommands.
-   *
-   * @param viewResolver
-   * @param viewsToAdd The views to add, by tag.  If this is a new view, this will be reactTag,
-   *     otherwise it will be -reactTag.  This allows to optimize when we have already attached
-   *     views.
-   * @param viewsToDetach The views to detach, by tag.  These will all be positive.
-   */
-  abstract void mountViews(ViewResolver viewResolver, int[] viewsToAdd, int[] viewsToDetach);
-
-  /**
-   * Get the current clipping rect and adjust clipping so that when draw is dispatched we do as
-   * little work as possible.
-   *
-   * @return true if the FlatViewGroup should invalidate.
-   */
-  abstract boolean updateClippingRect();
-
-  /**
-   * Sets an input rect to match the bounds of our current clipping rect.
-   *
-   * @param outClippingRect Set the out
-   */
-  abstract void getClippingRect(Rect outClippingRect);
-
-  /**
-   * Return the views that are currently detached, so they can be cleaned up when we are.
-   *
-   * @return A collection of the currently detached views.
-   */
-  abstract SparseArray<View> getDetachedViews();
-
-  /**
-   * Draw the relevant items.  This should do as little work as possible.
-   *
-   * @param canvas The canvas to draw on.
-   */
-  abstract void draw(Canvas canvas);
-
-  /**
-   * Draws layout bounds for debug.
-   *
-   * @param canvas The canvas to draw on.
-   */
-  abstract void debugDraw(Canvas canvas);
-
-  /**
-   * Mount node regions, which are the hit boxes of the shadow node children of this FlatViewGroup,
-   * though some may not have a corresponding draw command.
-   *
-   * @param nodeRegions Array of node regions to mount.
-   * @param maxBottom At each index i, the maximum bottom value (or right value in the case of
-   *   horizontal clipping) value of all node regions at or below i.
-   * @param minTop At each index i, the minimum top value (or left value in the case of horizontal
-   *   clipping) value of all draw commands at or below i.
-   */
-  abstract void mountNodeRegions(NodeRegion[] nodeRegions, float[] maxBottom, float[] minTop);
-
-  /**
-   * Find a matching node region for a touch.
-   *
-   * @param touchX X coordinate of touch.
-   * @param touchY Y coordinate of touch.
-   * @return Matching node region, or null if none are found.
-   */
-  abstract @Nullable NodeRegion anyNodeRegionWithinBounds(float touchX, float touchY);
-
-  /**
-   * Find a matching virtual node region for a touch.
-   *
-   * @param touchX X coordinate of touch.
-   * @param touchY Y coordinate of touch.
-   * @return Matching node region, or null if none are found.
-   */
-  abstract @Nullable NodeRegion virtualNodeRegionWithinBounds(float touchX, float touchY);
-
-  /**
-   * Event that is fired when a clipped view is dropped.
-   *
-   * @param view the view that is dropped
-   */
-  abstract void onClippedViewDropped(View view);
-
-  /**
-   * Throw a runtime exception if a view we are trying to attach is already parented.
-   *
-   * @param view The view to check.
-   */
-  protected static void ensureViewHasNoParent(View view) {
-    ViewParent oldParent = view.getParent();
-    if (oldParent != null) {
-      throw new RuntimeException(
-          "Cannot add view " + view + " to DrawCommandManager while it has a parent " + oldParent);
-    }
-  }
-
-  /**
-   * Get a draw command manager that will clip vertically (The view scrolls up and down).
-   *
-   * @param flatViewGroup FlatViewGroup to use for drawing.
-   * @param drawCommands List of commands to mount.
-   * @return Vertically clipping draw command manager.
-   */
-  static DrawCommandManager getVerticalClippingInstance(
-      FlatViewGroup flatViewGroup,
-      DrawCommand[] drawCommands) {
-    return new VerticalDrawCommandManager(flatViewGroup, drawCommands);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawImage.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DrawImage.java
deleted file mode 100644
index 05b9503d0ede..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawImage.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.content.Context;
-
-import com.facebook.drawee.drawable.ScalingUtils.ScaleType;
-import com.facebook.react.bridge.ReadableArray;
-
-/**
- * Common interface for DrawImageWithDrawee.
- */
-/* package */ interface DrawImage extends AttachDetachListener {
-  /**
-   * Returns true if an image source was assigned to the DrawImage.
-   * A DrawImage with no source will not draw anything.
-   */
-  boolean hasImageRequest();
-
-  /**
-   * Assigns a new image source to the DrawImage, or null to clear the image request.
-   */
-  void setSource(Context context, @Nullable ReadableArray sources);
-
-  /**
-   * Assigns a tint color to apply to the image drawn.
-   */
-  void setTintColor(int tintColor);
-
-  /**
-   * Assigns a scale type to draw to the image with.
-   */
-  void setScaleType(ScaleType scaleType);
-
-  /**
-   * Returns a scale type to draw to the image with.
-   */
-  ScaleType getScaleType();
-
-  /**
-   * React tag used for dispatching ImageLoadEvents, or 0 to ignore events.
-   */
-  void setReactTag(int reactTag);
-
-  void setBorderWidth(float borderWidth);
-
-  float getBorderWidth();
-
-  void setBorderRadius(float borderRadius);
-
-  float getBorderRadius();
-
-  void setBorderColor(int borderColor);
-
-  int getBorderColor();
-
-  void setFadeDuration(int fadeDuration);
-
-  void setProgressiveRenderingEnabled(boolean enabled);
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawImageWithDrawee.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DrawImageWithDrawee.java
deleted file mode 100644
index 8797cce68e83..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawImageWithDrawee.java
+++ /dev/null
@@ -1,315 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.PorterDuff;
-import android.graphics.PorterDuffColorFilter;
-import android.graphics.drawable.Animatable;
-import android.net.Uri;
-import com.facebook.drawee.controller.ControllerListener;
-import com.facebook.drawee.drawable.ScalingUtils.ScaleType;
-import com.facebook.drawee.generic.GenericDraweeHierarchy;
-import com.facebook.drawee.generic.RoundingParams;
-import com.facebook.imagepipeline.common.ResizeOptions;
-import com.facebook.imagepipeline.request.ImageRequest;
-import com.facebook.imagepipeline.request.ImageRequestBuilder;
-import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.bridge.ReadableMap;
-import com.facebook.react.views.image.GlobalImageLoadListener;
-import com.facebook.react.views.image.ImageLoadEvent;
-import com.facebook.react.views.image.ImageResizeMode;
-import com.facebook.react.views.image.ReactImageView;
-import com.facebook.react.views.imagehelper.ImageSource;
-import com.facebook.react.views.imagehelper.MultiSourceHelper;
-import com.facebook.react.views.imagehelper.MultiSourceHelper.MultiSourceResult;
-import java.util.LinkedList;
-import java.util.List;
-import javax.annotation.Nullable;
-
-/**
- * DrawImageWithDrawee is a DrawCommand that can draw a local or remote image.
- * It uses DraweeRequestHelper internally to fetch and cache the images.
- */
-/* package */ final class DrawImageWithDrawee extends AbstractDrawCommand
-    implements DrawImage, ControllerListener {
-  private static final String LOCAL_FILE_SCHEME = "file";
-  private static final String LOCAL_CONTENT_SCHEME = "content";
-
-  private final List<ImageSource> mSources = new LinkedList<>();
-  private final @Nullable GlobalImageLoadListener mGlobalImageLoadListener;
-  private @Nullable DraweeRequestHelper mRequestHelper;
-  private @Nullable PorterDuffColorFilter mColorFilter;
-  private ScaleType mScaleType = ImageResizeMode.defaultValue();
-  private float mBorderWidth;
-  private float mBorderRadius;
-  private int mBorderColor;
-  private int mReactTag;
-  private boolean mProgressiveRenderingEnabled;
-  private int mFadeDuration = ReactImageView.REMOTE_IMAGE_FADE_DURATION_MS;
-  private @Nullable FlatViewGroup.InvalidateCallback mCallback;
-
-  public DrawImageWithDrawee(@Nullable GlobalImageLoadListener globalImageLoadListener) {
-    mGlobalImageLoadListener = globalImageLoadListener;
-  }
-
-  @Override
-  public boolean hasImageRequest() {
-    return !mSources.isEmpty();
-  }
-
-  @Override
-  public void setSource(Context context, @Nullable ReadableArray sources) {
-    mSources.clear();
-    if (sources != null && sources.size() != 0) {
-      // Optimize for the case where we have just one uri, case in which we don't need the sizes
-      if (sources.size() == 1) {
-        ReadableMap source = sources.getMap(0);
-        mSources.add(new ImageSource(context, source.getString("uri")));
-      } else {
-        for (int idx = 0; idx < sources.size(); idx++) {
-          ReadableMap source = sources.getMap(idx);
-          mSources.add(new ImageSource(
-              context,
-              source.getString("uri"),
-              source.getDouble("width"),
-              source.getDouble("height")));
-        }
-      }
-    }
-  }
-
-  @Override
-  public void setTintColor(int tintColor) {
-    if (tintColor == 0) {
-      mColorFilter = null;
-    } else {
-      mColorFilter = new PorterDuffColorFilter(tintColor, PorterDuff.Mode.SRC_ATOP);
-    }
-  }
-
-  @Override
-  public void setScaleType(ScaleType scaleType) {
-    mScaleType = scaleType;
-  }
-
-  @Override
-  public ScaleType getScaleType() {
-    return mScaleType;
-  }
-
-  @Override
-  public void setBorderWidth(float borderWidth) {
-    mBorderWidth = borderWidth;
-  }
-
-  @Override
-  public float getBorderWidth() {
-    return mBorderWidth;
-  }
-
-  @Override
-  public void setBorderRadius(float borderRadius) {
-    mBorderRadius = borderRadius;
-  }
-
-  @Override
-  public float getBorderRadius() {
-    return mBorderRadius;
-  }
-
-  @Override
-  public void setBorderColor(int borderColor) {
-    mBorderColor = borderColor;
-  }
-
-  @Override
-  public int getBorderColor() {
-    return mBorderColor;
-  }
-
-  @Override
-  public void setFadeDuration(int fadeDuration) {
-    mFadeDuration = fadeDuration;
-  }
-
-  @Override
-  public void setProgressiveRenderingEnabled(boolean enabled) {
-    mProgressiveRenderingEnabled = enabled;
-  }
-
-  @Override
-  public void setReactTag(int reactTag) {
-    mReactTag = reactTag;
-  }
-
-  @Override
-  public void onDraw(Canvas canvas) {
-    if (mRequestHelper != null) {
-      mRequestHelper.getDrawable().draw(canvas);
-    }
-  }
-
-  @Override
-  public void onAttached(FlatViewGroup.InvalidateCallback callback) {
-    mCallback = callback;
-
-    if (mRequestHelper == null) {
-      // this is here to help us debug t12048319, in which we have a null request helper on attach
-      throw new RuntimeException(
-          "No DraweeRequestHelper - width: " +
-              (getRight() - getLeft()) +
-              " - height: " + (getBottom() - getTop() +
-              " - number of sources: " + mSources.size()));
-    }
-
-    GenericDraweeHierarchy hierarchy = mRequestHelper.getHierarchy();
-
-    RoundingParams roundingParams = hierarchy.getRoundingParams();
-    if (shouldDisplayBorder()) {
-      if (roundingParams == null) {
-        roundingParams = new RoundingParams();
-      }
-
-      roundingParams.setBorder(mBorderColor, mBorderWidth);
-      roundingParams.setCornersRadius(mBorderRadius);
-
-      // changes won't take effect until we re-apply rounding params, so do it now.
-      hierarchy.setRoundingParams(roundingParams);
-    } else if (roundingParams != null) {
-      // clear rounding params
-      hierarchy.setRoundingParams(null);
-    }
-
-    hierarchy.setActualImageScaleType(mScaleType);
-    hierarchy.setActualImageColorFilter(mColorFilter);
-    hierarchy.setFadeDuration(mFadeDuration);
-
-    hierarchy.getTopLevelDrawable().setBounds(
-        Math.round(getLeft()),
-        Math.round(getTop()),
-        Math.round(getRight()),
-        Math.round(getBottom()));
-
-    mRequestHelper.attach(callback);
-  }
-
-  @Override
-  public void onDetached() {
-    if (mRequestHelper != null) {
-      mRequestHelper.detach();
-    }
-  }
-
-  @Override
-  public void onSubmit(String id, Object callerContext) {
-    if (mCallback != null && mReactTag != 0) {
-      mCallback.dispatchImageLoadEvent(mReactTag, ImageLoadEvent.ON_LOAD_START);
-    }
-  }
-
-  @Override
-  public void onFinalImageSet(
-      String id,
-      @Nullable Object imageInfo,
-      @Nullable Animatable animatable) {
-    if (mCallback != null && mReactTag != 0) {
-      mCallback.dispatchImageLoadEvent(mReactTag, ImageLoadEvent.ON_LOAD);
-      mCallback.dispatchImageLoadEvent(mReactTag, ImageLoadEvent.ON_LOAD_END);
-    }
-  }
-
-  @Override
-  public void onIntermediateImageSet(String id, @Nullable Object imageInfo) {
-  }
-
-  @Override
-  public void onIntermediateImageFailed(String id, Throwable throwable) {
-  }
-
-  @Override
-  public void onFailure(String id, Throwable throwable) {
-    if (mCallback != null && mReactTag != 0) {
-      mCallback.dispatchImageLoadEvent(mReactTag, ImageLoadEvent.ON_ERROR);
-      mCallback.dispatchImageLoadEvent(mReactTag, ImageLoadEvent.ON_LOAD_END);
-    }
-  }
-
-  @Override
-  public void onRelease(String id) {
-  }
-
-  @Override
-  protected void onBoundsChanged() {
-    super.onBoundsChanged();
-    computeRequestHelper();
-  }
-
-  private void computeRequestHelper() {
-    MultiSourceResult multiSource = MultiSourceHelper.getBestSourceForSize(
-        Math.round(getRight() - getLeft()),
-        Math.round(getBottom() - getTop()),
-        mSources);
-    ImageSource source = multiSource.getBestResult();
-    ImageSource cachedSource = multiSource.getBestResultInCache();
-    if (source == null) {
-      mRequestHelper = null;
-      return;
-    }
-
-    ResizeOptions resizeOptions = null;
-    if (shouldResize(source)) {
-      final int width = (int) (getRight() - getLeft());
-      final int height = (int) (getBottom() - getTop());
-      resizeOptions = new ResizeOptions(width, height);
-    }
-
-    ImageRequest imageRequest = ImageRequestBuilder.newBuilderWithSource(source.getUri())
-        .setResizeOptions(resizeOptions)
-        .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled)
-        .build();
-    if (mGlobalImageLoadListener != null) {
-      mGlobalImageLoadListener.onLoadAttempt(source.getUri());
-    }
-
-    ImageRequest cachedImageRequest = null;
-    if (cachedSource != null) {
-      cachedImageRequest = ImageRequestBuilder.newBuilderWithSource(cachedSource.getUri())
-          .setResizeOptions(resizeOptions)
-          .setProgressiveRenderingEnabled(mProgressiveRenderingEnabled)
-          .build();
-    }
-    mRequestHelper = new
-      DraweeRequestHelper(Assertions.assertNotNull(imageRequest), cachedImageRequest, this);
-  }
-
-  private boolean shouldDisplayBorder() {
-    return mBorderColor != 0 || mBorderRadius >= 0.5f;
-  }
-
-  private static boolean shouldResize(ImageSource imageSource) {
-    // Resizing is inferior to scaling. See http://frescolib.org/docs/resizing-rotating.html
-    // We resize here only for images likely to be from the device's camera, where the app developer
-    // has no control over the original size
-    Uri uri = imageSource.getUri();
-    String type = uri == null ? null : uri.getScheme();
-    // one day, we can replace this with what non-Nodes does, which is:
-    // UriUtil.isLocalContentUri || UriUtil.isLocalFileUri
-    // not doing this just to save including eyt another BUCK dependency
-    return LOCAL_FILE_SCHEME.equals(type) || LOCAL_CONTENT_SCHEME.equals(type);
-  }
-
-  @Override
-  protected void onDebugDrawHighlight(Canvas canvas) {
-    if (mCallback != null) {
-      debugDrawCautionHighlight(canvas, "Invalidate Drawee");
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawTextLayout.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DrawTextLayout.java
deleted file mode 100644
index 495a53e0d068..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawTextLayout.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Canvas;
-import android.text.Layout;
-
-import com.facebook.fbui.textlayoutbuilder.util.LayoutMeasureUtil;
-
-/**
- * DrawTextLayout is a DrawCommand that draw {@link Layout}.
- */
-/* package */ final class DrawTextLayout extends AbstractDrawCommand {
-
-  private Layout mLayout;
-  private float mLayoutWidth;
-  private float mLayoutHeight;
-
-  /* package */ DrawTextLayout(Layout layout) {
-    setLayout(layout);
-  }
-
-  /**
-   * Assigns a new {@link Layout} to draw.
-   */
-  public void setLayout(Layout layout) {
-    mLayout = layout;
-    mLayoutWidth = layout.getWidth();
-    mLayoutHeight = LayoutMeasureUtil.getHeight(layout);
-  }
-
-  public Layout getLayout() {
-    return mLayout;
-  }
-
-  public float getLayoutWidth() {
-    // mLayout.getWidth() doesn't return correct width of the text Layout
-    return mLayoutWidth;
-  }
-
-  public float getLayoutHeight() {
-    return mLayoutHeight;
-  }
-
-  @Override
-  protected void onDraw(Canvas canvas) {
-    float left = getLeft();
-    float top = getTop();
-
-    canvas.translate(left, top);
-    mLayout.draw(canvas);
-    canvas.translate(-left, -top);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawView.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DrawView.java
deleted file mode 100644
index e2bdce5fb952..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DrawView.java
+++ /dev/null
@@ -1,233 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Canvas;
-import android.graphics.Path;
-import android.graphics.RectF;
-
-/* package */ final class DrawView extends AbstractDrawCommand {
-  public static final DrawView[] EMPTY_ARRAY = new DrawView[0];
-  // the minimum rounded clipping value before we actually do rounded clipping
-  /* package */ static final float MINIMUM_ROUNDED_CLIPPING_VALUE = 0.5f;
-  private final RectF TMP_RECT = new RectF();
-
-  /* package */ final int reactTag;
-  // Indicates whether this DrawView has been previously mounted to a clipping FlatViewGroup.  This
-  // lets us know that the bounds haven't changed, as a bounds change would trigger a new DrawView,
-  // which will set this to false for the new DrawView.  This is safe, despite the dual access with
-  // FlatViewGroup, because the FlatViewGroup copy is only ever modified by the FlatViewGroup.
-  // Changing how this boolean is used should be handled with caution, as race conditions are the
-  // quickest way to create unreproducible super bugs.
-  /* package */ boolean mWasMounted;
-
-  // the clipping radius - if this is greater than MINIMUM_ROUNDED_CLIPPING_VALUE, we clip using
-  // a rounded path, otherwise we clip in a rectangular fashion.
-  private float mClipRadius;
-
-  // the path to clip against if we're doing path clipping for rounded borders.
-  @Nullable private Path mPath;
-
-  // These should only ever be set from within the DrawView, they serve to provide clipping bounds
-  // for FlatViewGroups, which have strange clipping when it comes to overflow: visible.  They are
-  // left package protected to speed up direct access.  For overflow visible, these are the adjusted
-  // bounds while taking overflowing elements into account, other wise they are just the regular
-  // bounds of the view.
-  /* package */ float mLogicalLeft;
-  /* package */ float mLogicalTop;
-  /* package */ float mLogicalRight;
-  /* package */ float mLogicalBottom;
-
-  public DrawView(int reactTag) {
-    this.reactTag = reactTag;
-  }
-
-  /**
-   * Similar to updateBoundsAndFreeze, but thread safe as the mounting flag is modified on the UI
-   * thread.
-   *
-   * @return A DrawView with the passed bounds and clipping bounds.  If we can use the same
-   *     DrawView, it will just be this, otherwise it will be a frozen copy.
-   */
-  public DrawView collectDrawView(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float logicalLeft,
-      float logicalTop,
-      float logicalRight,
-      float logicalBottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom,
-      float clipRadius) {
-    if (!isFrozen()) {
-      // We haven't collected this draw view yet, so we can just set everything.
-      setBounds(left, top, right, bottom);
-      setClipBounds(clipLeft, clipTop, clipRight, clipBottom);
-      setClipRadius(clipRadius);
-      setLogicalBounds(logicalLeft, logicalTop, logicalRight, logicalBottom);
-      freeze();
-      return this;
-    }
-
-    boolean boundsMatch = boundsMatch(left, top, right, bottom);
-    boolean clipBoundsMatch = clipBoundsMatch(clipLeft, clipTop, clipRight, clipBottom);
-    boolean clipRadiusMatch = mClipRadius == clipRadius;
-    boolean logicalBoundsMatch =
-        logicalBoundsMatch(logicalLeft, logicalTop, logicalRight, logicalBottom);
-
-    // See if we can reuse the draw view.
-    if (boundsMatch && clipBoundsMatch && clipRadiusMatch && logicalBoundsMatch) {
-      return this;
-    }
-
-    DrawView drawView = (DrawView) mutableCopy();
-
-    if (!boundsMatch) {
-      drawView.setBounds(left, top, right, bottom);
-    }
-
-    if (!clipBoundsMatch) {
-      drawView.setClipBounds(clipLeft, clipTop, clipRight, clipBottom);
-    }
-
-    if (!logicalBoundsMatch) {
-      drawView.setLogicalBounds(logicalLeft, logicalTop, logicalRight, logicalBottom);
-    }
-
-    if (!clipRadiusMatch || !boundsMatch) {
-      // If the bounds change, we need to update the clip path.
-      drawView.setClipRadius(clipRadius);
-    }
-
-    // It is very important that we unset this, as our spec is that newly created DrawViews
-    // are handled differently by the FlatViewGroup.  This is needed because clone() maintains
-    // the previous state.
-    drawView.mWasMounted = false;
-
-    drawView.freeze();
-
-    return drawView;
-  }
-
-  private boolean logicalBoundsMatch(float left, float top, float right, float bottom) {
-    return left == mLogicalLeft && top == mLogicalTop &&
-        right == mLogicalRight && bottom == mLogicalBottom;
-  }
-
-  private void setLogicalBounds(float left, float top, float right, float bottom) {
-    // Do rounding up front and off of the UI thread.
-    mLogicalLeft = left;
-    mLogicalTop = top;
-    mLogicalRight = right;
-    mLogicalBottom = bottom;
-  }
-
-  @Override
-  public void draw(FlatViewGroup parent, Canvas canvas) {
-    onPreDraw(parent, canvas);
-    if (mNeedsClipping || mClipRadius > MINIMUM_ROUNDED_CLIPPING_VALUE) {
-      canvas.save(Canvas.CLIP_SAVE_FLAG);
-      applyClipping(canvas);
-      parent.drawNextChild(canvas);
-      canvas.restore();
-    } else {
-      parent.drawNextChild(canvas);
-    }
-  }
-
-  /**
-   * Set the clip radius.  Should only be called when the clip radius is first set or when it
-   * changes, in order to avoid extra work.
-   *
-   * @param clipRadius The new clip radius.
-   */
-  void setClipRadius(float clipRadius) {
-    mClipRadius = clipRadius;
-    if (clipRadius > MINIMUM_ROUNDED_CLIPPING_VALUE) {
-      // update the path that we'll clip based on
-      updateClipPath();
-    } else {
-      mPath = null;
-    }
-  }
-
-  /**
-   * Update the path with which we'll clip this view
-   */
-  private void updateClipPath() {
-    mPath = new Path();
-
-    TMP_RECT.set(
-        getLeft(),
-        getTop(),
-        getRight(),
-        getBottom());
-
-    // set the path
-    mPath.addRoundRect(
-        TMP_RECT,
-        mClipRadius,
-        mClipRadius,
-        Path.Direction.CW);
-  }
-
-  @Override
-  protected void applyClipping(Canvas canvas) {
-    // only clip using a path if our radius is greater than some minimum threshold, because
-    // clipPath is more expensive than clipRect.
-    if (mClipRadius > MINIMUM_ROUNDED_CLIPPING_VALUE) {
-      canvas.clipPath(mPath);
-    } else {
-      super.applyClipping(canvas);
-    }
-  }
-
-  @Override
-  protected void onDraw(Canvas canvas) {
-    // no op as we override draw.
-  }
-
-  @Override
-  protected void onDebugDraw(FlatViewGroup parent, Canvas canvas) {
-    parent.debugDrawNextChild(canvas);
-  }
-
-  @Override
-  protected void onDebugDrawHighlight(Canvas canvas) {
-    if (mPath != null) {
-      debugDrawWarningHighlight(canvas, "borderRadius: " + mClipRadius);
-    } else if (!boundsMatch(mLogicalLeft, mLogicalTop, mLogicalRight, mLogicalBottom)) {
-      StringBuilder warn = new StringBuilder("Overflow: { ");
-      String[] names = { "left: ", "top: ", "right: ", "bottom: "};
-      int i = 0;
-      float[] offsets = new float[4];
-      offsets[i++] = getLeft() - mLogicalLeft;
-      offsets[i++] = getTop() - mLogicalTop;
-      offsets[i++] = mLogicalRight - getRight();
-      offsets[i++] = mLogicalBottom - getBottom();
-
-      for (i = 0; i < 4; i++) {
-        if (offsets[i] != 0f) {
-          warn.append(names[i]);
-          warn.append(offsets[i]);
-          warn.append(", ");
-        }
-      }
-
-      warn.append("}");
-
-      debugDrawCautionHighlight(canvas, warn.toString());
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/DraweeRequestHelper.java b/ReactAndroid/src/main/java/com/facebook/react/flat/DraweeRequestHelper.java
deleted file mode 100644
index bf32f740395e..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/DraweeRequestHelper.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.content.res.Resources;
-import android.graphics.drawable.Drawable;
-
-import com.facebook.drawee.controller.AbstractDraweeControllerBuilder;
-import com.facebook.drawee.controller.ControllerListener;
-import com.facebook.drawee.generic.GenericDraweeHierarchy;
-import com.facebook.drawee.generic.GenericDraweeHierarchyBuilder;
-import com.facebook.drawee.interfaces.DraweeController;
-import com.facebook.imagepipeline.request.ImageRequest;
-import com.facebook.infer.annotation.Assertions;
-
-/* package */ final class DraweeRequestHelper {
-
-  private static GenericDraweeHierarchyBuilder sHierarchyBuilder;
-  private static AbstractDraweeControllerBuilder sControllerBuilder;
-
-  /* package */ static void setResources(Resources resources) {
-    sHierarchyBuilder = new GenericDraweeHierarchyBuilder(resources);
-  }
-
-  /* package */ static void setDraweeControllerBuilder(AbstractDraweeControllerBuilder builder) {
-    sControllerBuilder = builder;
-  }
-
-  private final DraweeController mDraweeController;
-  private int mAttachCounter;
-
-  /* package */ DraweeRequestHelper(
-      ImageRequest imageRequest,
-      @Nullable ImageRequest cachedImageRequest,
-      ControllerListener listener) {
-    AbstractDraweeControllerBuilder controllerBuilder = sControllerBuilder
-        .setImageRequest(imageRequest)
-        .setCallerContext(RCTImageView.getCallerContext())
-        .setControllerListener(listener);
-
-    if (cachedImageRequest != null) {
-      controllerBuilder.setLowResImageRequest(cachedImageRequest);
-    }
-    DraweeController controller = controllerBuilder.build();
-
-    controller.setHierarchy(sHierarchyBuilder.build());
-
-    mDraweeController = controller;
-  }
-
-  /* package */ void attach(FlatViewGroup.InvalidateCallback callback) {
-    ++mAttachCounter;
-    if (mAttachCounter == 1) {
-      getDrawable().setCallback(callback.get());
-      mDraweeController.onAttach();
-    }
-  }
-
-  /* package */ void detach() {
-    --mAttachCounter;
-    if (mAttachCounter == 0) {
-      mDraweeController.onDetach();
-    }
-  }
-
-  /* package */ GenericDraweeHierarchy getHierarchy() {
-    return (GenericDraweeHierarchy) Assertions.assumeNotNull(mDraweeController.getHierarchy());
-  }
-
-  /* package */ Drawable getDrawable() {
-    return getHierarchy().getTopLevelDrawable();
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/ElementsList.java b/ReactAndroid/src/main/java/com/facebook/react/flat/ElementsList.java
deleted file mode 100644
index e741cde43306..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/ElementsList.java
+++ /dev/null
@@ -1,198 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import java.util.ArrayDeque;
-import java.util.ArrayList;
-import java.lang.reflect.Array;
-
-/**
- * Diffing scope stack class that supports 3 main operations: start(), add() an element and
- * finish().
- *
- * When started, it takes a baseline array to compare to. When adding a new element, it checks
- * whether a corresponding element in baseline array is the same. On finish(), it will return null
- * if baseline array contains exactly the same elements that were added with a sequence of add()
- * calls, or a new array of the recorded elements:
- *
- * Example 1:
- * -----
- *   start([A])
- *   add(A)
- *   finish() -> null (because [A] == [A])
- *
- * Example 2:
- * ----
- *   start([A])
- *   add(B)
- *   finish() -> [B] (because [A] != [B])
- *
- * Example 3:
- * ----
- *   start([A])
- *   add(B)
- *   add(A)
- *   finish() -> [B, A] (because [B, A] != [A])
- *
- * Example 4:
- * ----
- *   start([A, B])
- *   add(B)
- *   add(A)
- *   finish() -> [B, A] (because [B, A] != [A, B])
- *
- * It is important that start/finish can be nested:
- * ----
- *   start([A])
- *   add(A)
- *     start([B])
- *     add(B)
- *     finish() -> null
- *   add(C)
- *   finish() -> [A, C]
- *
- * StateBuilder is using this class to check if e.g. a DrawCommand list for a given View needs to be
- * updated.
- */
-/* package */ final class ElementsList<E> {
-
-  private static final class Scope {
-    Object[] elements;
-    int index;
-    int size;
-  }
-
-  // List of scopes.  These are never cleared, but instead recycled when a new scope is needed at
-  // a given depth.
-  private final ArrayList<Scope> mScopesStack = new ArrayList<>();
-  // Working list of all new elements we are gathering across scopes.  Whenever we get a call to
-  // finish() we pop the new elements off the collection, either discarding them if there was no
-  // change from the base or accumulating and returning them as a list of new elements.
-  private final ArrayDeque<E> mElements = new ArrayDeque<>();
-  private final E[] mEmptyArray;
-  private Scope mCurrentScope = null;
-  private int mScopeIndex = 0;
-
-  public ElementsList(E[] emptyArray) {
-    mEmptyArray = emptyArray;
-    mScopesStack.add(mCurrentScope);
-  }
-
-  /**
-   * Starts a new scope.
-   */
-  public void start(Object[] elements) {
-    pushScope();
-
-    Scope scope = getCurrentScope();
-    scope.elements = elements;
-    scope.index = 0;
-    scope.size = mElements.size();
-  }
-
-  /**
-   * Finish current scope, returning null if there were no changes recorded, or a new array
-   * containing all the newly recorded elements otherwise.
-   */
-  public E[] finish() {
-    Scope scope = getCurrentScope();
-    popScope();
-
-    E[] result = null;
-    int size = mElements.size() - scope.size;
-    if (scope.index != scope.elements.length) {
-      result = extractElements(size);
-    } else {
-      // downsize
-      for (int i = 0; i < size; ++i) {
-        mElements.pollLast();
-      }
-    }
-
-    // To prevent resource leaks.
-    scope.elements = null;
-
-    return result;
-  }
-
-  /**
-   * Adds a new element to the list.  This method can be optimized to avoid inserts on same
-   * elements, but would involve copying from scope.elements when we extract elements.
-   */
-  public void add(E element) {
-    Scope scope = getCurrentScope();
-
-    if (scope.index < scope.elements.length &&
-        scope.elements[scope.index] == element) {
-      ++scope.index;
-    } else {
-      scope.index = Integer.MAX_VALUE;
-    }
-
-    mElements.add(element);
-  }
-
-  /**
-   * Resets all references to elements in our new stack to null to avoid memory leaks.
-   */
-  public void clear() {
-    if (getCurrentScope() != null) {
-      throw new RuntimeException("Must call finish() for every start() call being made.");
-    }
-    mElements.clear();
-  }
-
-  /**
-   * Extracts last size elements into an array.  Used to extract our new array of items from our
-   * stack when the new items != old items.
-   */
-  private E[] extractElements(int size) {
-    if (size == 0) {
-      // avoid allocating empty array
-      return mEmptyArray;
-    }
-
-    E[] elements = (E[]) Array.newInstance(mEmptyArray.getClass().getComponentType(), size);
-    for (int i = size - 1; i >= 0; --i) {
-      elements[i] = mElements.pollLast();
-    }
-
-    return elements;
-  }
-
-  /**
-   * Saves current scope in a stack.
-   */
-  private void pushScope() {
-    ++mScopeIndex;
-    if (mScopeIndex == mScopesStack.size()) {
-      // We reached a new deepest scope, we need to create a scope for this depth.
-      mCurrentScope = new Scope();
-      mScopesStack.add(mCurrentScope);
-    } else {
-      // We have had a scope at this depth before, lets recycle it.
-      mCurrentScope = mScopesStack.get(mScopeIndex);
-    }
-  }
-
-  /**
-   * Restores last saved current scope.  Doesn't actually remove the scope, as scopes are
-   * recycled.
-   */
-  private void popScope() {
-    --mScopeIndex;
-    mCurrentScope = mScopesStack.get(mScopeIndex);
-  }
-
-  /**
-   * Returns current scope.
-   */
-  private Scope getCurrentScope() {
-    return mCurrentScope;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
deleted file mode 100644
index f6382b80befc..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewManager.java
+++ /dev/null
@@ -1,60 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.react.uimanager.BaseViewManager;
-import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.views.art.ARTSurfaceView;
-import com.facebook.yoga.YogaMeasureFunction;
-import com.facebook.yoga.YogaMeasureMode;
-import com.facebook.yoga.YogaNode;
-
-public class FlatARTSurfaceViewManager extends
-  BaseViewManager<ARTSurfaceView, FlatARTSurfaceViewShadowNode> {
-
-  /* package */ static final String REACT_CLASS = "ARTSurfaceView";
-
-  private static final YogaMeasureFunction MEASURE_FUNCTION = new YogaMeasureFunction() {
-    @Override
-    public long measure(
-      YogaNode node,
-      float width,
-      YogaMeasureMode widthMode,
-      float height,
-      YogaMeasureMode heightMode) {
-      throw new IllegalStateException("SurfaceView should have explicit width and height set");
-    }
-  };
-
-  @Override
-  public String getName() {
-    return REACT_CLASS;
-  }
-
-  @Override
-  public FlatARTSurfaceViewShadowNode createShadowNodeInstance() {
-    FlatARTSurfaceViewShadowNode node = new FlatARTSurfaceViewShadowNode();
-    node.setMeasureFunction(MEASURE_FUNCTION);
-    return node;
-  }
-
-  @Override
-  public Class<FlatARTSurfaceViewShadowNode> getShadowNodeClass() {
-    return FlatARTSurfaceViewShadowNode.class;
-  }
-
-  @Override
-  protected ARTSurfaceView createViewInstance(ThemedReactContext reactContext) {
-    return new ARTSurfaceView(reactContext);
-  }
-
-  @Override
-  public void updateExtraData(ARTSurfaceView root, Object extraData) {
-    root.setSurfaceTextureListener((FlatARTSurfaceViewShadowNode) extraData);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
deleted file mode 100644
index 09fa6a42a429..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatARTSurfaceViewShadowNode.java
+++ /dev/null
@@ -1,143 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.PorterDuff;
-import android.graphics.SurfaceTexture;
-import android.util.Log;
-import android.view.Surface;
-import android.view.TextureView;
-
-import com.facebook.react.common.ReactConstants;
-import com.facebook.react.uimanager.ReactShadowNode;
-import com.facebook.react.uimanager.UIViewOperationQueue;
-import com.facebook.react.views.art.ARTVirtualNode;
-import com.facebook.yoga.YogaValue;
-import com.facebook.yoga.YogaUnit;
-
-/* package */ class FlatARTSurfaceViewShadowNode extends FlatShadowNode
-    implements AndroidView, TextureView.SurfaceTextureListener {
-  private boolean mPaddingChanged = false;
-  private @Nullable Surface mSurface;
-
-  /* package */ FlatARTSurfaceViewShadowNode() {
-    forceMountToView();
-    forceMountChildrenToView();
-  }
-
-  @Override
-  public boolean isVirtual() {
-    return false;
-  }
-
-  @Override
-  public boolean isVirtualAnchor() {
-    return true;
-  }
-
-  @Override
-  public void onCollectExtraUpdates(UIViewOperationQueue uiUpdater) {
-    super.onCollectExtraUpdates(uiUpdater);
-    drawOutput();
-    uiUpdater.enqueueUpdateExtraData(getReactTag(), this);
-  }
-
-  private void drawOutput() {
-    if (mSurface == null || !mSurface.isValid()) {
-      markChildrenUpdatesSeen(this);
-      return;
-    }
-
-    try {
-      Canvas canvas = mSurface.lockCanvas(null);
-      canvas.drawColor(Color.TRANSPARENT, PorterDuff.Mode.CLEAR);
-
-      Paint paint = new Paint();
-      for (int i = 0; i < getChildCount(); i++) {
-        ARTVirtualNode child = (ARTVirtualNode) getChildAt(i);
-        child.draw(canvas, paint, 1f);
-        child.markUpdateSeen();
-      }
-
-      if (mSurface == null) {
-        return;
-      }
-
-      mSurface.unlockCanvasAndPost(canvas);
-    } catch (IllegalArgumentException | IllegalStateException e) {
-      Log.e(ReactConstants.TAG, e.getClass().getSimpleName() + " in Surface.unlockCanvasAndPost");
-    }
-  }
-
-  private void markChildrenUpdatesSeen(ReactShadowNode shadowNode) {
-    for (int i = 0; i < shadowNode.getChildCount(); i++) {
-      ReactShadowNode child = shadowNode.getChildAt(i);
-      child.markUpdateSeen();
-      markChildrenUpdatesSeen(child);
-    }
-  }
-
-  @Override
-  public boolean needsCustomLayoutForChildren() {
-    return false;
-  }
-
-  @Override
-  public boolean isPaddingChanged() {
-    return mPaddingChanged;
-  }
-
-  @Override
-  public void resetPaddingChanged() {
-    mPaddingChanged = false;
-  }
-
-  @Override
-  public void setPadding(int spacingType, float padding) {
-    YogaValue current = getStylePadding(spacingType);
-    if (current.unit != YogaUnit.POINT || current.value != padding) {
-      super.setPadding(spacingType, padding);
-      mPaddingChanged = true;
-      markUpdated();
-    }
-  }
-
-  @Override
-  public void setPaddingPercent(int spacingType, float percent) {
-    YogaValue current = getStylePadding(spacingType);
-    if (current.unit != YogaUnit.PERCENT || current.value != percent) {
-      super.setPadding(spacingType, percent);
-      mPaddingChanged = true;
-      markUpdated();
-    }
-  }
-
-  @Override
-  public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) {
-    mSurface = new Surface(surface);
-    drawOutput();
-  }
-
-  @Override
-  public boolean onSurfaceTextureDestroyed(SurfaceTexture surface) {
-    surface.release();
-    mSurface = null;
-    return true;
-  }
-
-  @Override
-  public void onSurfaceTextureSizeChanged(SurfaceTexture surface, int width, int height) {}
-
-  @Override
-  public void onSurfaceTextureUpdated(SurfaceTexture surface) {}
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatMeasuredViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatMeasuredViewGroup.java
deleted file mode 100644
index 7e7ee2e46ac4..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatMeasuredViewGroup.java
+++ /dev/null
@@ -1,24 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Rect;
-
-/**
- * Helper interface to provide measuring of FlatViewGroup when needed.  We don't override onMeasure
- * for FlatViewGroup, which means that draw commands don't contributed to the measured width and
- * height.  This allows us to expose our calculated dimensions taking into account draw commands,
- * without changing the visibility of the FlatViewGroup.
- */
-public interface FlatMeasuredViewGroup {
-  /**
-   * @return A rect consisting of the left, top, right, and bottommost edge among all children,
-   *   including draw commands.
-   */
-  Rect measureWithCommands();
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatNativeViewHierarchyManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatNativeViewHierarchyManager.java
deleted file mode 100644
index ac1e0aadde92..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatNativeViewHierarchyManager.java
+++ /dev/null
@@ -1,261 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import java.util.ArrayList;
-import java.util.List;
-
-import android.util.SparseArray;
-import android.util.SparseIntArray;
-import android.view.View;
-import android.view.View.MeasureSpec;
-import android.view.ViewGroup;
-
-import com.facebook.react.uimanager.NativeViewHierarchyManager;
-import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
-import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.ViewGroupManager;
-import com.facebook.react.uimanager.ViewManagerRegistry;
-
-/**
- * FlatNativeViewHierarchyManager is the only class that performs View manipulations. All of this
- * class methods can only be called from UI thread by {@link FlatUIViewOperationQueue}.
- */
-/* package */ final class FlatNativeViewHierarchyManager extends NativeViewHierarchyManager
-    implements ViewResolver {
-
-  /* package */ FlatNativeViewHierarchyManager(ViewManagerRegistry viewManagers) {
-    super(viewManagers, new FlatRootViewManager());
-  }
-
-  @Override
-  public View getView(int reactTag) {
-    return super.resolveView(reactTag);
-  }
-
-  @Override
-  public void addRootView(
-      int tag,
-      SizeMonitoringFrameLayout view,
-      ThemedReactContext themedContext) {
-    FlatViewGroup root = new FlatViewGroup(themedContext);
-    view.addView(root);
-
-    // When unmounting, ReactInstanceManager.detachViewFromInstance() will check id of the
-    // top-level View (SizeMonitoringFrameLayout) and pass it back to JS. We want that View's id to
-    // be set, otherwise NativeViewHierarchyManager will not be able to cleanup properly.
-    view.setId(tag);
-
-    addRootViewGroup(tag, root, themedContext);
-  }
-
-  /**
-   * Updates DrawCommands and AttachDetachListeners of a FlatViewGroup specified by a reactTag.
-   *
-   * @param reactTag reactTag to lookup FlatViewGroup by
-   * @param drawCommands if non-null, new draw commands to execute during the drawing.
-   * @param listeners if non-null, new attach-detach listeners.
-   */
-  /* package */ void updateMountState(
-      int reactTag,
-      @Nullable DrawCommand[] drawCommands,
-      @Nullable AttachDetachListener[] listeners,
-      @Nullable NodeRegion[] nodeRegions) {
-    FlatViewGroup view = (FlatViewGroup) resolveView(reactTag);
-    if (drawCommands != null) {
-      view.mountDrawCommands(drawCommands);
-    }
-    if (listeners != null) {
-      view.mountAttachDetachListeners(listeners);
-    }
-    if (nodeRegions != null) {
-      view.mountNodeRegions(nodeRegions);
-    }
-  }
-
-  /**
-   * Updates DrawCommands and AttachDetachListeners of a clipping FlatViewGroup specified by a
-   * reactTag.
-   *
-   * @param reactTag The react tag to lookup FlatViewGroup by.
-   * @param drawCommands If non-null, new draw commands to execute during the drawing.
-   * @param drawViewIndexMap Mapping of react tags to the index of the corresponding DrawView
-   *   command in the draw command array.
-   * @param commandMaxBot At each index i, the maximum bottom value (or right value in the case of
-   *   horizontal clipping) value of all draw commands at or below i.
-   * @param commandMinTop At each index i, the minimum top value (or left value in the case of
-   *   horizontal clipping) value of all draw commands at or below i.
-   * @param listeners If non-null, new attach-detach listeners.
-   * @param nodeRegions Node regions to mount.
-   * @param regionMaxBot At each index i, the maximum bottom value (or right value in the case of
-   *   horizontal clipping) value of all node regions at or below i.
-   * @param regionMinTop At each index i, the minimum top value (or left value in the case of
-   *   horizontal clipping) value of all draw commands at or below i.
-   * @param willMountViews Whether we are going to also send a mountViews command in this state
-   *   cycle.
-   */
-  /* package */ void updateClippingMountState(
-      int reactTag,
-      @Nullable DrawCommand[] drawCommands,
-      SparseIntArray drawViewIndexMap,
-      float[] commandMaxBot,
-      float[] commandMinTop,
-      @Nullable AttachDetachListener[] listeners,
-      @Nullable NodeRegion[] nodeRegions,
-      float[] regionMaxBot,
-      float[] regionMinTop,
-      boolean willMountViews) {
-    FlatViewGroup view = (FlatViewGroup) resolveView(reactTag);
-    if (drawCommands != null) {
-      view.mountClippingDrawCommands(
-          drawCommands,
-          drawViewIndexMap,
-          commandMaxBot,
-          commandMinTop,
-          willMountViews);
-    }
-    if (listeners != null) {
-      view.mountAttachDetachListeners(listeners);
-    }
-    if (nodeRegions != null) {
-      view.mountClippingNodeRegions(nodeRegions, regionMaxBot, regionMinTop);
-    }
-  }
-
-  /* package */ void updateViewGroup(int reactTag, int[] viewsToAdd, int[] viewsToDetach) {
-    View view = resolveView(reactTag);
-    if (view instanceof FlatViewGroup) {
-      ((FlatViewGroup) view).mountViews(this, viewsToAdd, viewsToDetach);
-      return;
-    }
-
-    ViewGroup viewGroup = (ViewGroup) view;
-    ViewGroupManager viewManager = (ViewGroupManager) resolveViewManager(reactTag);
-    List<View> listOfViews = new ArrayList<>(viewsToAdd.length);
-
-    // batch the set of additions - some view managers can take advantage of the batching to
-    // decrease operations, etc.
-    for (int viewIdToAdd : viewsToAdd) {
-      int tag = Math.abs(viewIdToAdd);
-      listOfViews.add(resolveView(tag));
-    }
-    viewManager.addViews(viewGroup, listOfViews);
-  }
-
-  /**
-   * Updates View bounds, possibly re-measuring and re-layouting it if the size changed.
-   *
-   * @param reactTag reactTag to lookup a View by
-   * @param left left coordinate relative to parent
-   * @param top top coordinate relative to parent
-   * @param right right coordinate relative to parent
-   * @param bottom bottom coordinate relative to parent
-   */
-  /* package */ void updateViewBounds(int reactTag, int left, int top, int right, int bottom) {
-    View view = resolveView(reactTag);
-    int width = right - left;
-    int height = bottom - top;
-    if (view.getWidth() != width || view.getHeight() != height) {
-      // size changed, we need to measure and layout the View
-      view.measure(
-          MeasureSpec.makeMeasureSpec(width, MeasureSpec.EXACTLY),
-          MeasureSpec.makeMeasureSpec(height, MeasureSpec.EXACTLY));
-      view.layout(left, top, right, bottom);
-    } else {
-      // same size, only location changed, there is a faster route.
-      view.offsetLeftAndRight(left - view.getLeft());
-      view.offsetTopAndBottom(top - view.getTop());
-    }
-  }
-
-  /* package */ void setPadding(
-      int reactTag,
-      int paddingLeft,
-      int paddingTop,
-      int paddingRight,
-      int paddingBottom) {
-    resolveView(reactTag).setPadding(paddingLeft, paddingTop, paddingRight, paddingBottom);
-  }
-
-  /* package */ void dropViews(SparseIntArray viewsToDrop) {
-    for (int i = 0, count = viewsToDrop.size(); i < count; i++) {
-      int viewToDrop = viewsToDrop.keyAt(i);
-      View view = null;
-      if (viewToDrop > 0) {
-        try {
-          view = resolveView(viewToDrop);
-          dropView(view);
-        } catch (Exception e) {
-          // the view is already dropped, nothing we can do
-        }
-      } else {
-        // Root views are noted with a negative tag from StateBuilder.
-        removeRootView(-viewToDrop);
-      }
-
-      int parentTag = viewsToDrop.valueAt(i);
-      // this only happens for clipped, non-root views - clipped because there is no parent, and
-      // not a root view (because we explicitly pass -1 for root views).
-      if (parentTag > 0 && view != null && view.getParent() == null) {
-        // this can only happen if the parent exists (if the parent were removed first, it'd also
-        // remove the child, so trying to explicitly remove the child afterwards would crash at
-        // the resolveView call above) - we also explicitly check for a null parent, implying that
-        // we are either clipped (or that we already removed the child from its parent, in which
-        // case this will essentially be a no-op).
-        View parent = resolveView(parentTag);
-        if (parent instanceof FlatViewGroup) {
-          ((FlatViewGroup) parent).onViewDropped(view);
-        }
-      }
-    }
-  }
-
-  @Override
-  protected void dropView(View view) {
-    super.dropView(view);
-
-    // As a result of removeClippedSubviews, some views have strong references but are not attached
-    // to a parent. consequently, when the parent gets removed, these Views don't get cleaned up,
-    // because they aren't children (they also aren't removed from mTagsToViews, thus causing a
-    // leak). To solve this, we ask for said detached views and explicitly drop them.
-    if (view instanceof FlatViewGroup) {
-      FlatViewGroup flatViewGroup = (FlatViewGroup) view;
-      if (flatViewGroup.getRemoveClippedSubviews()) {
-        SparseArray<View> detachedViews = flatViewGroup.getDetachedViews();
-        for (int i = 0, size = detachedViews.size(); i < size; i++) {
-          View detachedChild = detachedViews.valueAt(i);
-          try {
-             dropView(detachedChild);
-          } catch (Exception e) {
-             // if the view is already dropped, ignore any exceptions
-             // in reality, we should find out the edge cases that cause
-             // this to happen and properly fix them.
-          }
-          // trigger onDetachedFromWindow and clean up this detached/clipped view
-          flatViewGroup.removeDetachedView(detachedChild);
-        }
-      }
-    }
-  }
-
-  /* package */ void detachAllChildrenFromViews(int[] viewsToDetachAllChildrenFrom) {
-    for (int viewTag : viewsToDetachAllChildrenFrom) {
-      View view = resolveView(viewTag);
-      if (view instanceof FlatViewGroup) {
-        ((FlatViewGroup) view).detachAllViewsFromParent();
-        continue;
-      }
-
-      ViewGroup viewGroup = (ViewGroup) view;
-      ViewGroupManager viewManager = (ViewGroupManager) resolveViewManager(viewTag);
-      viewManager.removeAllViews(viewGroup);
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatReactModalShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatReactModalShadowNode.java
deleted file mode 100644
index 01191247c84e..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatReactModalShadowNode.java
+++ /dev/null
@@ -1,105 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.graphics.Point;
-import android.view.Display;
-import android.view.Surface;
-import android.view.WindowManager;
-import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import com.facebook.yoga.YogaUnit;
-import com.facebook.yoga.YogaValue;
-
-/**
- * FlatReactModalShadowNode
- *
- * This is a Nodes specific shadow node for modals. This is required because we wrap any
- * non-FlatShadowNode node in a NativeViewWrapper. In the case of a modal shadow node, we need
- * to treat it as its own node so that we can add the custom measurement behavior that is there
- * in the non-Nodes version when we add a child.
- *
- * {@see {@link com.facebook.react.views.modal.ModalHostShadowNode}}
- */
-class FlatReactModalShadowNode extends FlatShadowNode implements AndroidView {
-
-  private final Point mMinPoint = new Point();
-  private final Point mMaxPoint = new Point();
-  private boolean mPaddingChanged;
-
-  FlatReactModalShadowNode() {
-    forceMountToView();
-    forceMountChildrenToView();
-  }
-
-  /**
-   * We need to set the styleWidth and styleHeight of the one child (represented by the <View/>
-   * within the <RCTModalHostView/> in Modal.js. This needs to fill the entire window.
-   */
-  @Override
-  @TargetApi(16)
-  public void addChildAt(ReactShadowNodeImpl child, int i) {
-    super.addChildAt(child, i);
-
-    Context context = getThemedContext();
-    WindowManager wm = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
-    Display display = wm.getDefaultDisplay();
-    // getCurrentSizeRange will return the min and max width and height that the window can be
-    display.getCurrentSizeRange(mMinPoint, mMaxPoint);
-
-    int width, height;
-    int rotation = display.getRotation();
-    if (rotation == Surface.ROTATION_0 || rotation == Surface.ROTATION_180) {
-      // If we are vertical the width value comes from min width and height comes from max height
-      width = mMinPoint.x;
-      height = mMaxPoint.y;
-    } else {
-      // If we are horizontal the width value comes from max width and height comes from min height
-      width = mMaxPoint.x;
-      height = mMinPoint.y;
-    }
-    child.setStyleWidth(width);
-    child.setStyleHeight(height);
-  }
-
-  @Override
-  public boolean needsCustomLayoutForChildren() {
-    return false;
-  }
-
-  @Override
-  public boolean isPaddingChanged() {
-    return mPaddingChanged;
-  }
-
-  @Override
-  public void resetPaddingChanged() {
-    mPaddingChanged = false;
-  }
-
-  @Override
-  public void setPadding(int spacingType, float padding) {
-    YogaValue current = getStylePadding(spacingType);
-    if (current.unit != YogaUnit.POINT || current.value != padding) {
-      super.setPadding(spacingType, padding);
-      mPaddingChanged = true;
-      markUpdated();
-    }
-  }
-
-  @Override
-  public void setPaddingPercent(int spacingType, float percent) {
-    YogaValue current = getStylePadding(spacingType);
-    if (current.unit != YogaUnit.PERCENT || current.value != percent) {
-      super.setPadding(spacingType, percent);
-      mPaddingChanged = true;
-      markUpdated();
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatRootShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatRootShadowNode.java
deleted file mode 100644
index b60ab205b7a4..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatRootShadowNode.java
+++ /dev/null
@@ -1,19 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-/**
- * Root node of the shadow node hierarchy. Currently, the only node that can actually map to a View.
- */
-/* package */ final class FlatRootShadowNode extends FlatShadowNode {
-
-  /* package */ FlatRootShadowNode() {
-    forceMountToView();
-    signalBackingViewIsCreated();
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatRootViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatRootViewManager.java
deleted file mode 100644
index 929c8ce81836..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatRootViewManager.java
+++ /dev/null
@@ -1,20 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.view.ViewGroup;
-
-import com.facebook.react.uimanager.RootViewManager;
-
-/* package */ class FlatRootViewManager extends RootViewManager {
-
-  @Override
-  public void removeAllViews(ViewGroup parent) {
-    parent.removeAllViewsInLayout();
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatShadowNode.java
deleted file mode 100644
index 9f96433b8094..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatShadowNode.java
+++ /dev/null
@@ -1,570 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Rect;
-import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.uimanager.LayoutShadowNode;
-import com.facebook.react.uimanager.OnLayoutEvent;
-import com.facebook.react.uimanager.ReactClippingViewGroupHelper;
-import com.facebook.react.uimanager.ReactShadowNode;
-import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import com.facebook.react.uimanager.ReactStylesDiffMap;
-import com.facebook.react.uimanager.ViewProps;
-import com.facebook.react.uimanager.annotations.ReactProp;
-import javax.annotation.Nullable;
-
-/**
- * FlatShadowNode is a base class for all shadow node used in FlatUIImplementation. It extends
- * {@link LayoutShadowNode} by adding an ability to prepare DrawCommands off the UI thread.
- */
-/* package */ class FlatShadowNode extends LayoutShadowNode {
-
-  /* package */ static final FlatShadowNode[] EMPTY_ARRAY = new FlatShadowNode[0];
-
-  private static final String PROP_OPACITY = "opacity";
-  private static final String PROP_RENDER_TO_HARDWARE_TEXTURE = "renderToHardwareTextureAndroid";
-  private static final String PROP_ACCESSIBILITY_LABEL = "accessibilityLabel";
-  private static final String PROP_ACCESSIBILITY_COMPONENT_TYPE = "accessibilityComponentType";
-  private static final String PROP_ACCESSIBILITY_LIVE_REGION = "accessibilityLiveRegion";
-  private static final String PROP_IMPORTANT_FOR_ACCESSIBILITY = "importantForAccessibility";
-  private static final String PROP_TEST_ID = "testID";
-  private static final String PROP_TRANSFORM = "transform";
-  protected static final String PROP_REMOVE_CLIPPED_SUBVIEWS =
-      ReactClippingViewGroupHelper.PROP_REMOVE_CLIPPED_SUBVIEWS;
-  protected static final String PROP_HORIZONTAL = "horizontal";
-  private static final Rect LOGICAL_OFFSET_EMPTY = new Rect();
-  // When we first initialize a backing view, we create a view we are going to throw away anyway,
-  // so instead initialize with a shared view.
-  private static final DrawView EMPTY_DRAW_VIEW = new DrawView(0);
-
-  private DrawCommand[] mDrawCommands = DrawCommand.EMPTY_ARRAY;
-  private AttachDetachListener[] mAttachDetachListeners = AttachDetachListener.EMPTY_ARRAY;
-  private NodeRegion[] mNodeRegions = NodeRegion.EMPTY_ARRAY;
-  private FlatShadowNode[] mNativeChildren = FlatShadowNode.EMPTY_ARRAY;
-  private NodeRegion mNodeRegion = NodeRegion.EMPTY;
-  private int mNativeParentTag;
-  private int mViewLeft;
-  private int mViewTop;
-  private int mViewRight;
-  private int mViewBottom;
-  private boolean mBackingViewIsCreated;
-  private @Nullable DrawView mDrawView;
-  private @Nullable DrawBackgroundColor mDrawBackground;
-  private boolean mIsUpdated = true;
-  private boolean mForceMountChildrenToView;
-  private float mClipLeft;
-  private float mClipTop;
-  private float mClipRight;
-  private float mClipBottom;
-
-  // Used to track whether any of the NodeRegions overflow this Node. This is used to determine
-  // whether or not we can detach this Node in the context of a container with
-  // setRemoveClippedSubviews enabled.
-  private boolean mOverflowsContainer;
-  // this Rect contains the offset to get the "logical bounds" (i.e. bounds that include taking
-  // into account overflow visible).
-  private Rect mLogicalOffset = LOGICAL_OFFSET_EMPTY;
-
-  // last OnLayoutEvent info, only used when shouldNotifyOnLayout() is true.
-  private int mLayoutX;
-  private int mLayoutY;
-  private int mLayoutWidth;
-  private int mLayoutHeight;
-
-  // clip radius
-  float mClipRadius;
-  boolean mClipToBounds = false;
-
-  /* package */ void handleUpdateProperties(ReactStylesDiffMap styles) {
-    if (!mountsToView()) {
-      // Make sure we mount this FlatShadowNode to a View if any of these properties are present.
-      if (styles.hasKey(PROP_OPACITY) ||
-          styles.hasKey(PROP_RENDER_TO_HARDWARE_TEXTURE) ||
-          styles.hasKey(PROP_TEST_ID) ||
-          styles.hasKey(PROP_ACCESSIBILITY_LABEL) ||
-          styles.hasKey(PROP_ACCESSIBILITY_COMPONENT_TYPE) ||
-          styles.hasKey(PROP_ACCESSIBILITY_LIVE_REGION) ||
-          styles.hasKey(PROP_TRANSFORM) ||
-          styles.hasKey(PROP_IMPORTANT_FOR_ACCESSIBILITY) ||
-          styles.hasKey(PROP_REMOVE_CLIPPED_SUBVIEWS)) {
-        forceMountToView();
-      }
-    }
-  }
-
-  /* package */ final void forceMountChildrenToView() {
-    if (mForceMountChildrenToView) {
-      return;
-    }
-
-    mForceMountChildrenToView = true;
-    for (int i = 0, childCount = getChildCount(); i != childCount; ++i) {
-      ReactShadowNode child = getChildAt(i);
-      if (child instanceof FlatShadowNode) {
-        ((FlatShadowNode) child).forceMountToView();
-      }
-    }
-  }
-
-  /**
-   * Collects DrawCommands produced by this FlatShadowNode.
-   */
-  protected void collectState(
-      StateBuilder stateBuilder,
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    if (mDrawBackground != null) {
-      mDrawBackground = (DrawBackgroundColor) mDrawBackground.updateBoundsAndFreeze(
-          left,
-          top,
-          right,
-          bottom,
-          clipLeft,
-          clipTop,
-          clipRight,
-          clipBottom);
-      stateBuilder.addDrawCommand(mDrawBackground);
-    }
-  }
-
-  /**
-   * Return whether or not this node draws anything
-   *
-   * This is used to decide whether or not to collect the NodeRegion for this node. This ensures
-   * that any FlatShadowNode that does not emit any DrawCommands should not bother handling touch
-   * (i.e. if it draws absolutely nothing, it is, for all intents and purposes, a layout only node).
-   *
-   * @return whether or not this is node draws anything
-   */
-  boolean doesDraw() {
-    // if it mounts to view or draws a background, we can collect it - otherwise, no, unless a
-    // child suggests some alternative behavior
-    return mDrawView != null || mDrawBackground != null;
-  }
-
-  @ReactProp(name = ViewProps.BACKGROUND_COLOR)
-  public void setBackgroundColor(int backgroundColor) {
-    mDrawBackground = (backgroundColor == 0) ? null : new DrawBackgroundColor(backgroundColor);
-    invalidate();
-  }
-
-  @Override
-  public void setOverflow(String overflow) {
-    super.setOverflow(overflow);
-    mClipToBounds = "hidden".equals(overflow);
-    if (mClipToBounds) {
-      mOverflowsContainer = false;
-      if (mClipRadius > DrawView.MINIMUM_ROUNDED_CLIPPING_VALUE) {
-        // mount to a view if we are overflow: hidden and are clipping, so that we can do one
-        // clipPath to clip all the children of this node (both DrawCommands and Views).
-        forceMountToView();
-      }
-    } else {
-      updateOverflowsContainer();
-    }
-    invalidate();
-  }
-
-  public final boolean clipToBounds() {
-    return mClipToBounds;
-  }
-
-  @Override
-  public final int getScreenX() {
-    return mViewLeft;
-  }
-
-  @Override
-  public final int getScreenY() {
-    return mViewTop;
-  }
-
-  @Override
-  public final int getScreenWidth() {
-    if (mountsToView()) {
-      return mViewRight - mViewLeft;
-    } else {
-      return Math.round(mNodeRegion.getRight() - mNodeRegion.getLeft());
-    }
-  }
-
-  @Override
-  public final int getScreenHeight() {
-    if (mountsToView()) {
-      return mViewBottom - mViewTop;
-    } else {
-      return Math.round(mNodeRegion.getBottom() - mNodeRegion.getTop());
-    }
-  }
-
-  @Override
-  public void addChildAt(ReactShadowNodeImpl child, int i) {
-    super.addChildAt(child, i);
-    if (mForceMountChildrenToView && child instanceof FlatShadowNode) {
-      ((FlatShadowNode) child).forceMountToView();
-    }
-  }
-
-  /**
-   * Marks root node as updated to trigger a StateBuilder pass to collect DrawCommands for the node
-   * tree. Use it when FlatShadowNode is updated but doesn't require a layout pass (e.g. background
-   * color is changed).
-   */
-  protected final void invalidate() {
-    FlatShadowNode node = this;
-
-    while (true) {
-      if (node.mountsToView()) {
-        if (node.mIsUpdated) {
-          // already updated
-          return;
-        }
-
-        node.mIsUpdated = true;
-      }
-
-      ReactShadowNode parent = node.getParent();
-      if (parent == null) {
-        // not attached to a hierarchy yet
-        return;
-      }
-
-      node = (FlatShadowNode) parent;
-    }
-  }
-
-  @Override
-  public void markUpdated() {
-    super.markUpdated();
-    mIsUpdated = true;
-    invalidate();
-  }
-
-  /* package */ final boolean isUpdated() {
-    return mIsUpdated;
-  }
-
-  /* package */ final void resetUpdated() {
-    mIsUpdated = false;
-  }
-
-  /* package */ final boolean clipBoundsChanged(
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    return mClipLeft != clipLeft || mClipTop != clipTop ||
-        mClipRight != clipRight || mClipBottom != clipBottom;
-  }
-
-  /* package */ final void setClipBounds(
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    mClipLeft = clipLeft;
-    mClipTop = clipTop;
-    mClipRight = clipRight;
-    mClipBottom = clipBottom;
-  }
-
-  /**
-   * Returns an array of DrawCommands to perform during the View's draw pass.
-   */
-  /* package */ final DrawCommand[] getDrawCommands() {
-    return mDrawCommands;
-  }
-
-  /**
-   * Sets an array of DrawCommands to perform during the View's draw pass. StateBuilder uses old
-   * draw commands to compare to new draw commands and see if the View needs to be redrawn.
-   */
-  /* package */ final void setDrawCommands(DrawCommand[] drawCommands) {
-    mDrawCommands = drawCommands;
-  }
-
-  /**
-   * Sets an array of AttachDetachListeners to call onAttach/onDetach when they are attached to or
-   * detached from a View that this shadow node maps to.
-   */
-  /* package */ final void setAttachDetachListeners(AttachDetachListener[] listeners) {
-    mAttachDetachListeners = listeners;
-  }
-
-  /**
-   * Returns an array of AttachDetachListeners associated with this shadow node.
-   */
-  /* package */ final AttachDetachListener[] getAttachDetachListeners() {
-    return mAttachDetachListeners;
-  }
-
-  /* package */ final FlatShadowNode[] getNativeChildren() {
-    return mNativeChildren;
-  }
-
-  /* package */ final void setNativeChildren(FlatShadowNode[] nativeChildren) {
-    mNativeChildren = nativeChildren;
-  }
-
-  /* package */ final int getNativeParentTag() {
-    return mNativeParentTag;
-  }
-
-  /* package */ final void setNativeParentTag(int nativeParentTag) {
-    mNativeParentTag = nativeParentTag;
-  }
-
-  /* package */ final NodeRegion[] getNodeRegions() {
-    return mNodeRegions;
-  }
-
-  /* package */ final void setNodeRegions(NodeRegion[] nodeRegion) {
-    mNodeRegions = nodeRegion;
-    updateOverflowsContainer();
-  }
-
-  /* package */ final void updateOverflowsContainer() {
-    boolean overflowsContainer = false;
-    int width = (int) (mNodeRegion.getRight() - mNodeRegion.getLeft());
-    int height = (int) (mNodeRegion.getBottom() - mNodeRegion.getTop());
-
-    float leftBound = 0;
-    float rightBound = width;
-    float topBound = 0;
-    float bottomBound = height;
-    Rect logicalOffset = null;
-
-    // when we are overflow:visible, we try to figure out if any of the children are outside
-    // of the bounds of this view. since NodeRegion bounds are relative to their parent (i.e.
-    // 0, 0 is always the start), we see how much outside of the bounds we are (negative left
-    // or top, or bottom that's more than height or right that's more than width). we set these
-    // offsets in mLogicalOffset for being able to more intelligently determine whether or not
-    // to clip certain subviews.
-    if (!mClipToBounds && height > 0 && width > 0) {
-      for (NodeRegion region : mNodeRegions) {
-        if (region.getLeft() < leftBound) {
-          leftBound = region.getLeft();
-          overflowsContainer = true;
-        }
-
-        if (region.getRight() > rightBound) {
-          rightBound = region.getRight();
-          overflowsContainer = true;
-        }
-
-        if (region.getTop() < topBound) {
-          topBound = region.getTop();
-          overflowsContainer = true;
-        }
-
-        if (region.getBottom() > bottomBound) {
-          bottomBound = region.getBottom();
-          overflowsContainer = true;
-        }
-      }
-
-      if (overflowsContainer) {
-        logicalOffset = new Rect(
-            (int) leftBound,
-            (int) topBound,
-            (int) (rightBound - width),
-            (int) (bottomBound - height));
-      }
-    }
-
-    // if we don't overflow, let's check if any of the immediate children overflow.
-    // this is "indirectly recursive," since this method is called when setNodeRegions is called,
-    // and the children call setNodeRegions before their parent. consequently, when a node deep
-    // inside the tree overflows, its immediate parent has mOverflowsContainer set to true, and,
-    // by extension, so do all of its ancestors, sufficing here to only check the immediate
-    // child's mOverflowsContainer value instead of recursively asking if each child overflows its
-    // container.
-    if (!overflowsContainer && mNodeRegion != NodeRegion.EMPTY) {
-      int children = getChildCount();
-      for (int i = 0; i < children; i++) {
-        ReactShadowNode node = getChildAt(i);
-        if (node instanceof FlatShadowNode && ((FlatShadowNode) node).mOverflowsContainer) {
-          Rect childLogicalOffset = ((FlatShadowNode) node).mLogicalOffset;
-          if (logicalOffset == null) {
-            logicalOffset = new Rect();
-          }
-          // TODO: t11674025 - improve this - a grandparent may end up having smaller logical
-          // bounds than its children (because the grandparent's size may be larger than that of
-          // its child, so the grandchild overflows its parent but not its grandparent). currently,
-          // if a 100x100 view has a 5x5 view, and inside it has a 10x10 view, the inner most view
-          // overflows its parent but not its grandparent - the logical bounds on the grandparent
-          // will still be 5x5 (because they're inherited from the child's logical bounds). this
-          // has the effect of causing us to clip 5px later than we really have to.
-          logicalOffset.union(childLogicalOffset);
-          overflowsContainer = true;
-        }
-      }
-    }
-
-    // if things changed, notify the parent(s) about said changes - while in many cases, this will
-    // be extra work (since we process this for the parents after the children), in some cases,
-    // we may have no new node regions in the parent, but have a new node region in the child, and,
-    // as a result, the parent may not get the correct value for overflows container.
-    if (mOverflowsContainer != overflowsContainer) {
-      mOverflowsContainer = overflowsContainer;
-      mLogicalOffset = logicalOffset == null ? LOGICAL_OFFSET_EMPTY : logicalOffset;
-    }
-  }
-
-  /* package */ void updateNodeRegion(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      boolean isVirtual) {
-    if (!mNodeRegion.matches(left, top, right, bottom, isVirtual)) {
-      setNodeRegion(new NodeRegion(left, top, right, bottom, getReactTag(), isVirtual));
-    }
-  }
-
-  protected final void setNodeRegion(NodeRegion nodeRegion) {
-    mNodeRegion = nodeRegion;
-    updateOverflowsContainer();
-  }
-
-  /* package */ final NodeRegion getNodeRegion() {
-    return mNodeRegion;
-  }
-
-  /**
-   * Sets boundaries of the View that this node maps to relative to the parent left/top coordinate.
-   */
-  /* package */ final void setViewBounds(int left, int top, int right, int bottom) {
-    mViewLeft = left;
-    mViewTop = top;
-    mViewRight = right;
-    mViewBottom = bottom;
-  }
-
-  /**
-   * Left position of the View this node maps to relative to the parent View.
-   */
-  /* package */ final int getViewLeft() {
-    return mViewLeft;
-  }
-
-  /**
-   * Top position of the View this node maps to relative to the parent View.
-   */
-  /* package */ final int getViewTop() {
-    return mViewTop;
-  }
-
-  /**
-   * Right position of the View this node maps to relative to the parent View.
-   */
-  /* package */ final int getViewRight() {
-    return mViewRight;
-  }
-
-  /**
-   * Bottom position of the View this node maps to relative to the parent View.
-   */
-  /* package */ final int getViewBottom() {
-    return mViewBottom;
-  }
-
-  /* package */ final void forceMountToView() {
-    if (isVirtual()) {
-      return;
-    }
-
-    if (mDrawView == null) {
-      // Create a new DrawView, but we might not know our react tag yet, so set it to 0 in the
-      // meantime.
-      mDrawView = EMPTY_DRAW_VIEW;
-      invalidate();
-
-      // reset NodeRegion to allow it getting garbage-collected
-      mNodeRegion = NodeRegion.EMPTY;
-    }
-  }
-
-  /* package */ final DrawView collectDrawView(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    Assertions.assumeNotNull(mDrawView);
-    if (mDrawView == EMPTY_DRAW_VIEW) {
-      // This is the first time we have collected this DrawView, but we have to create a new
-      // DrawView anyway, as reactTag is final, and our DrawView instance is the static copy.
-      mDrawView = new DrawView(getReactTag());
-    }
-
-    // avoid path clipping if overflow: visible
-    float clipRadius = mClipToBounds ? mClipRadius : 0.0f;
-    // We have the correct react tag, but we may need a new copy with updated bounds.  If the bounds
-    // match or were never set, the same view is returned.
-    mDrawView = mDrawView.collectDrawView(
-        left,
-        top,
-        right,
-        bottom,
-        left + mLogicalOffset.left,
-        top + mLogicalOffset.top,
-        right + mLogicalOffset.right,
-        bottom + mLogicalOffset.bottom,
-        clipLeft,
-        clipTop,
-        clipRight,
-        clipBottom,
-        clipRadius);
-    return mDrawView;
-  }
-
-  @Nullable
-  /* package */ final OnLayoutEvent obtainLayoutEvent(int x, int y, int width, int height) {
-    if (mLayoutX == x && mLayoutY == y && mLayoutWidth == width && mLayoutHeight == height) {
-      return null;
-    }
-
-    mLayoutX = x;
-    mLayoutY = y;
-    mLayoutWidth = width;
-    mLayoutHeight = height;
-
-    return OnLayoutEvent.obtain(getReactTag(), x, y, width, height);
-  }
-
-  /* package */ final boolean mountsToView() {
-    return mDrawView != null;
-  }
-
-  /* package */ final boolean isBackingViewCreated() {
-    return mBackingViewIsCreated;
-  }
-
-  /* package */ final void signalBackingViewIsCreated() {
-    mBackingViewIsCreated = true;
-  }
-
-  public boolean clipsSubviews() {
-    return false;
-  }
-
-  public boolean isHorizontal() {
-    return false;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatTextShadowNode.java
deleted file mode 100644
index 90a349d2e573..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatTextShadowNode.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.text.SpannableStringBuilder;
-
-import com.facebook.react.uimanager.ReactShadowNode;
-
-/**
- * Base class for RCTVirtualText and RCTRawText.
- */
-/* package */ abstract class FlatTextShadowNode extends FlatShadowNode {
-
-  // these 2 are only used between collectText() and applySpans() calls.
-  private int mTextBegin;
-  private int mTextEnd;
-
-  /**
-   * Propagates changes up to RCTText without dirtying current node.
-   */
-  protected void notifyChanged(boolean shouldRemeasure) {
-    ReactShadowNode parent = getParent();
-    if (parent instanceof FlatTextShadowNode) {
-      ((FlatTextShadowNode) parent).notifyChanged(shouldRemeasure);
-    }
-  }
-
-  @Override
-  public boolean isVirtual() {
-    return true;
-  }
-
-  /**
-   * Recursively visits FlatTextShadowNode and its children,
-   * appending text to SpannableStringBuilder.
-   */
-  /* package */ final void collectText(SpannableStringBuilder builder) {
-    mTextBegin = builder.length();
-    performCollectText(builder);
-    mTextEnd = builder.length();
-  }
-
-  /**
-   * Whether or not to allow empty spans to be set
-   * This is used to bypass an optimization in {@code applySpans} that skips applying spans if
-   * there is no text (since, for TextInput, for example, we want to apply the span even if there
-   * is no text so that newly typed text gets styled properly).
-   *
-   * @return a boolean representing whether or not we should allow empty spans
-   */
-  /* package */ boolean shouldAllowEmptySpans() {
-    return false;
-  }
-
-  /* package */ boolean isEditable() {
-    return false;
-  }
-
-  /**
-   * Recursively visits FlatTextShadowNode and its children,
-   * applying spans to SpannableStringBuilder.
-   */
-  /* package */ final void applySpans(SpannableStringBuilder builder, boolean isEditable) {
-    if (mTextBegin != mTextEnd || shouldAllowEmptySpans()) {
-      performApplySpans(builder, mTextBegin, mTextEnd, isEditable);
-    }
-  }
-
-  protected abstract void performCollectText(SpannableStringBuilder builder);
-  protected abstract void performApplySpans(
-      SpannableStringBuilder builder,
-      int begin,
-      int end,
-      boolean isEditable);
-  protected abstract void performCollectAttachDetachListeners(StateBuilder stateBuilder);
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatUIImplementation.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatUIImplementation.java
deleted file mode 100644
index 74174d2b6ab5..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatUIImplementation.java
+++ /dev/null
@@ -1,608 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.Callback;
-import com.facebook.react.bridge.ReactApplicationContext;
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.modules.fresco.FrescoModule;
-import com.facebook.react.modules.i18nmanager.I18nUtil;
-import com.facebook.react.uimanager.ReactShadowNode;
-import com.facebook.react.uimanager.ReactStylesDiffMap;
-import com.facebook.react.uimanager.UIImplementation;
-import com.facebook.react.uimanager.ViewManager;
-import com.facebook.react.uimanager.ViewManagerRegistry;
-import com.facebook.react.uimanager.events.EventDispatcher;
-import com.facebook.yoga.YogaDirection;
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import javax.annotation.Nullable;
-
-/**
- * FlatUIImplementation builds on top of UIImplementation and allows pre-creating everything
- * required for drawing (DrawCommands) and touching (NodeRegions) views in background thread
- * for faster drawing and interactions.
- */
-public class FlatUIImplementation extends UIImplementation {
-
-  private static final Map<String, Class<? extends ViewManager>> flatManagerClassMap;
-
-  static {
-    flatManagerClassMap = new HashMap<>();
-    flatManagerClassMap.put(RCTViewManager.REACT_CLASS, RCTViewManager.class);
-    flatManagerClassMap.put(RCTTextManager.REACT_CLASS, RCTTextManager.class);
-    flatManagerClassMap.put(RCTRawTextManager.REACT_CLASS, RCTRawTextManager.class);
-    flatManagerClassMap.put(RCTVirtualTextManager.REACT_CLASS, RCTVirtualTextManager.class);
-    flatManagerClassMap.put(RCTTextInlineImageManager.REACT_CLASS, RCTTextInlineImageManager.class);
-    flatManagerClassMap.put(RCTImageViewManager.REACT_CLASS, RCTImageViewManager.class);
-    flatManagerClassMap.put(RCTTextInputManager.REACT_CLASS, RCTTextInputManager.class);
-    flatManagerClassMap.put(RCTViewPagerManager.REACT_CLASS, RCTViewPagerManager.class);
-    flatManagerClassMap.put(FlatARTSurfaceViewManager.REACT_CLASS, FlatARTSurfaceViewManager.class);
-    flatManagerClassMap.put(RCTModalHostManager.REACT_CLASS, RCTModalHostManager.class);
-  }
-
-  /**
-   * Build the map of view managers, checking that the managers FlatUI requires are correctly
-   * overridden.
-   */
-  private static Map<String, ViewManager> buildViewManagerMap(List<ViewManager> viewManagers) {
-    Map<String, ViewManager> viewManagerMap = new HashMap<>();
-    for (ViewManager viewManager : viewManagers) {
-      viewManagerMap.put(viewManager.getName(), viewManager);
-    }
-    for (Map.Entry<String, Class<? extends ViewManager>> entry : flatManagerClassMap.entrySet()) {
-      String name = entry.getKey();
-      ViewManager maybeFlatViewManager = viewManagerMap.get(name);
-      if (maybeFlatViewManager == null) {
-        // We don't have a view manager for this name in the package, no need to add one.
-        continue;
-      }
-
-      Class<? extends ViewManager> flatClazz = entry.getValue();
-      if (maybeFlatViewManager.getClass() != flatClazz) {
-        // If we have instances that have flat equivalents, override them.
-        try {
-          viewManagerMap.put(name, flatClazz.newInstance());
-        } catch (IllegalAccessException e) {
-          throw new RuntimeException("Unable to access flat class for " + name, e);
-        } catch (InstantiationException e) {
-          throw new RuntimeException("Unable to instantiate flat class for " + name, e);
-        }
-      }
-    }
-    return viewManagerMap;
-  }
-
-  public static FlatUIImplementation createInstance(
-      ReactApplicationContext reactContext,
-      List<ViewManager> viewManagers,
-      EventDispatcher eventDispatcher,
-      boolean memoryImprovementEnabled,
-      int minTimeLeftInFrameForNonBatchedOperationMs) {
-
-    Map<String, ViewManager> viewManagerMap = buildViewManagerMap(viewManagers);
-
-    RCTImageViewManager imageViewManager =
-      (RCTImageViewManager) viewManagerMap.get(RCTImageViewManager.REACT_CLASS);
-    if (imageViewManager != null) {
-      Object callerContext = imageViewManager.getCallerContext();
-      if (callerContext != null) {
-        RCTImageView.setCallerContext(callerContext);
-      }
-    }
-    DraweeRequestHelper.setResources(reactContext.getResources());
-
-    TypefaceCache.setAssetManager(reactContext.getAssets());
-
-    ViewManagerRegistry viewManagerRegistry = new ViewManagerRegistry(viewManagerMap);
-    FlatNativeViewHierarchyManager nativeViewHierarchyManager = new FlatNativeViewHierarchyManager(
-      viewManagerRegistry);
-    FlatUIViewOperationQueue operationsQueue =
-        new FlatUIViewOperationQueue(
-            reactContext, nativeViewHierarchyManager, minTimeLeftInFrameForNonBatchedOperationMs);
-    return new FlatUIImplementation(
-      reactContext,
-      imageViewManager,
-      viewManagerRegistry,
-      operationsQueue,
-      eventDispatcher,
-      memoryImprovementEnabled
-    );
-  }
-
-  /**
-   * Helper class that sorts moveTo/moveFrom arrays passed to #manageChildren().
-   * Not used outside of the said method.
-   */
-  private final MoveProxy mMoveProxy = new MoveProxy();
-  private final ReactApplicationContext mReactContext;
-  private @Nullable RCTImageViewManager mRCTImageViewManager;
-  private final StateBuilder mStateBuilder;
-  private final boolean mMemoryImprovementEnabled;
-
-  private FlatUIImplementation(
-      ReactApplicationContext reactContext,
-      @Nullable RCTImageViewManager rctImageViewManager,
-      ViewManagerRegistry viewManagers,
-      FlatUIViewOperationQueue operationsQueue,
-      EventDispatcher eventDispatcher,
-      boolean memoryImprovementEnabled) {
-    super(reactContext, viewManagers, operationsQueue, eventDispatcher);
-    mReactContext = reactContext;
-    mRCTImageViewManager = rctImageViewManager;
-    mStateBuilder = new StateBuilder(operationsQueue);
-    mMemoryImprovementEnabled = memoryImprovementEnabled;
-  }
-
-  @Override
-  protected ReactShadowNode createRootShadowNode() {
-    if (mRCTImageViewManager != null) {
-      // This is not the best place to initialize DraweeRequestHelper, but order of module
-      // initialization is undefined, and this is pretty much the earliest when we are guarantied
-      // that Fresco is initialized and DraweeControllerBuilder can be queried. This also happens
-      // relatively rarely to have any performance considerations.
-      mReactContext.getNativeModule(FrescoModule.class); // initialize Fresco
-      DraweeRequestHelper.setDraweeControllerBuilder(
-        mRCTImageViewManager.getDraweeControllerBuilder());
-      mRCTImageViewManager = null;
-    }
-
-    ReactShadowNode node = new FlatRootShadowNode();
-    I18nUtil sharedI18nUtilInstance = I18nUtil.getInstance();
-    if (sharedI18nUtilInstance.isRTL(mReactContext)) {
-      node.setLayoutDirection(YogaDirection.RTL);
-    }
-    return node;
-  }
-
-  @Override
-  protected ReactShadowNode createShadowNode(String className) {
-    ReactShadowNode cssNode = super.createShadowNode(className);
-    if (cssNode instanceof FlatShadowNode || cssNode.isVirtual()) {
-      return cssNode;
-    }
-
-    ViewManager viewManager = resolveViewManager(className);
-    return new NativeViewWrapper(viewManager);
-  }
-
-  @Override
-  protected void handleCreateView(
-    ReactShadowNode cssNode,
-    int rootViewTag,
-    @Nullable ReactStylesDiffMap styles) {
-    if (cssNode instanceof FlatShadowNode) {
-      FlatShadowNode node = (FlatShadowNode) cssNode;
-
-      if (styles != null) {
-        node.handleUpdateProperties(styles);
-      }
-
-      if (node.mountsToView()) {
-        mStateBuilder.enqueueCreateOrUpdateView(node, styles);
-      }
-    } else {
-      super.handleCreateView(cssNode, rootViewTag, styles);
-    }
-  }
-
-  @Override
-  protected void handleUpdateView(
-    ReactShadowNode cssNode,
-    String className,
-    ReactStylesDiffMap styles) {
-    if (cssNode instanceof FlatShadowNode) {
-      FlatShadowNode node = (FlatShadowNode) cssNode;
-
-      node.handleUpdateProperties(styles);
-
-      if (node.mountsToView()) {
-        mStateBuilder.enqueueCreateOrUpdateView(node, styles);
-      }
-    } else {
-      super.handleUpdateView(cssNode, className, styles);
-    }
-  }
-
-  @Override
-  public void manageChildren(
-    int viewTag,
-    @Nullable ReadableArray moveFrom,
-    @Nullable ReadableArray moveTo,
-    @Nullable ReadableArray addChildTags,
-    @Nullable ReadableArray addAtIndices,
-    @Nullable ReadableArray removeFrom) {
-
-    ReactShadowNode parentNode = resolveShadowNode(viewTag);
-
-    // moveFrom and removeFrom are defined in original order before any mutations.
-    removeChildren(parentNode, moveFrom, moveTo, removeFrom);
-
-    // moveTo and addAtIndices are defined in final order after all the mutations applied.
-    addChildren(parentNode, addChildTags, addAtIndices);
-  }
-
-  @Override
-  public void setChildren(
-    int viewTag,
-    ReadableArray children) {
-
-    ReactShadowNode parentNode = resolveShadowNode(viewTag);
-
-    for (int i = 0; i < children.size(); i++) {
-      ReactShadowNode addToChild = resolveShadowNode(children.getInt(i));
-      addChildAt(parentNode, addToChild, i, i - 1);
-    }
-  }
-
-  @Override
-  public void measure(int reactTag, Callback callback) {
-    measureHelper(reactTag, false, callback);
-  }
-
-  private void measureHelper(int reactTag, boolean relativeToWindow, Callback callback) {
-    FlatShadowNode node = (FlatShadowNode) resolveShadowNode(reactTag);
-    if (node.mountsToView()) {
-      mStateBuilder.ensureBackingViewIsCreated(node);
-      if (relativeToWindow) {
-        super.measureInWindow(reactTag, callback);
-      } else {
-        super.measure(reactTag, callback);
-      }
-      return;
-    }
-
-    // virtual nodes do not have values for width and height, so get these values
-    // from the first non-virtual parent node
-    while (node != null && node.isVirtual()) {
-      node = (FlatShadowNode) node.getParent();
-    }
-
-    if (node == null) {
-      // everything is virtual, this shouldn't happen so just silently return
-      return;
-    }
-
-    float width = node.getLayoutWidth();
-    float height = node.getLayoutHeight();
-
-    boolean nodeMountsToView = node.mountsToView();
-    // this is to avoid double-counting xInParent and yInParent when we visit
-    // the while loop, below.
-    float xInParent = nodeMountsToView ? node.getLayoutX() : 0;
-    float yInParent = nodeMountsToView ? node.getLayoutY() : 0;
-
-    while (!node.mountsToView()) {
-      if (!node.isVirtual()) {
-        xInParent += node.getLayoutX();
-        yInParent += node.getLayoutY();
-      }
-
-      node = Assertions.assumeNotNull((FlatShadowNode) node.getParent());
-    }
-
-    float parentWidth = node.getLayoutWidth();
-    float parentHeight = node.getLayoutHeight();
-
-    FlatUIViewOperationQueue operationsQueue = mStateBuilder.getOperationsQueue();
-    operationsQueue.enqueueMeasureVirtualView(
-      node.getReactTag(),
-      xInParent / parentWidth,
-      yInParent / parentHeight,
-      width / parentWidth,
-      height / parentHeight,
-      relativeToWindow,
-      callback);
-  }
-
-  private void ensureMountsToViewAndBackingViewIsCreated(int reactTag) {
-    FlatShadowNode node = (FlatShadowNode) resolveShadowNode(reactTag);
-    if (node.isBackingViewCreated()) {
-      return;
-    }
-    node.forceMountToView();
-    mStateBuilder.ensureBackingViewIsCreated(node);
-  }
-
-  @Override
-  public void findSubviewIn(int reactTag, float targetX, float targetY, Callback callback) {
-    ensureMountsToViewAndBackingViewIsCreated(reactTag);
-    super.findSubviewIn(reactTag, targetX, targetY, callback);
-  }
-
-  @Override
-  public void measureInWindow(int reactTag, Callback callback) {
-    measureHelper(reactTag, true, callback);
-  }
-
-  @Override
-  public void addAnimation(int reactTag, int animationID, Callback onSuccess) {
-    ensureMountsToViewAndBackingViewIsCreated(reactTag);
-    super.addAnimation(reactTag, animationID, onSuccess);
-  }
-
-  @Override
-  public void dispatchViewManagerCommand(int reactTag, int commandId, ReadableArray commandArgs) {
-    // Make sure that our target view is actually a view, then delay command dispatch until after
-    // we have updated the view hierarchy.
-    ensureMountsToViewAndBackingViewIsCreated(reactTag);
-    mStateBuilder.enqueueViewManagerCommand(reactTag, commandId, commandArgs);
-  }
-
-  @Override
-  public void showPopupMenu(int reactTag, ReadableArray items, Callback error, Callback success) {
-    ensureMountsToViewAndBackingViewIsCreated(reactTag);
-    super.showPopupMenu(reactTag, items, error, success);
-  }
-
-  @Override
-  public void sendAccessibilityEvent(int reactTag, int eventType) {
-    ensureMountsToViewAndBackingViewIsCreated(reactTag);
-    super.sendAccessibilityEvent(reactTag, eventType);
-  }
-
-  /**
-   * Removes all children defined by moveFrom and removeFrom from a given parent,
-   * preparing elements in moveFrom to be re-added at proper index.
-   */
-  private void removeChildren(
-    ReactShadowNode parentNode,
-    @Nullable ReadableArray moveFrom,
-    @Nullable ReadableArray moveTo,
-    @Nullable ReadableArray removeFrom) {
-
-    int prevIndex = Integer.MAX_VALUE;
-
-    mMoveProxy.setup(moveFrom, moveTo);
-
-    int moveFromIndex = mMoveProxy.size() - 1;
-    int moveFromChildIndex = (moveFromIndex == -1) ? -1 : mMoveProxy.getMoveFrom(moveFromIndex);
-
-    int numToRemove = removeFrom == null ? 0 : removeFrom.size();
-    int[] indicesToRemove = new int[numToRemove];
-    if (numToRemove > 0) {
-      Assertions.assertNotNull(removeFrom);
-      for (int i = 0; i < numToRemove; i++) {
-        int indexToRemove = removeFrom.getInt(i);
-        indicesToRemove[i] = indexToRemove;
-      }
-    }
-
-    // this isn't guaranteed to be sorted actually
-    Arrays.sort(indicesToRemove);
-
-    int removeFromIndex;
-    int removeFromChildIndex;
-    if (removeFrom == null) {
-      removeFromIndex = -1;
-      removeFromChildIndex = -1;
-    } else {
-      removeFromIndex = indicesToRemove.length - 1;
-      removeFromChildIndex = indicesToRemove[removeFromIndex];
-    }
-
-    // both moveFrom and removeFrom are already sorted, but combined order is not sorted. Use
-    // a merge step from mergesort to walk over both arrays and extract elements in sorted order.
-
-    while (true) {
-      if (moveFromChildIndex > removeFromChildIndex) {
-        moveChild(removeChildAt(parentNode, moveFromChildIndex, prevIndex), moveFromIndex);
-        prevIndex = moveFromChildIndex;
-
-        --moveFromIndex;
-        moveFromChildIndex = (moveFromIndex == -1) ? -1 : mMoveProxy.getMoveFrom(moveFromIndex);
-      } else if (removeFromChildIndex > moveFromChildIndex) {
-        removeChild(removeChildAt(parentNode, removeFromChildIndex, prevIndex), parentNode);
-        prevIndex = removeFromChildIndex;
-
-        --removeFromIndex;
-        removeFromChildIndex = (removeFromIndex == -1) ? -1 : indicesToRemove[removeFromIndex];
-      } else {
-        // moveFromChildIndex == removeFromChildIndex can only be if both are equal to -1
-        // which means that we exhausted both arrays, and all children are removed.
-        break;
-      }
-    }
-  }
-
-  /**
-   * Unregisters given element and all of its children from ShadowNodeRegistry,
-   * and drops all Views used by it and its children.
-   */
-  private void removeChild(ReactShadowNode child, ReactShadowNode parentNode) {
-    dropNativeViews(child, parentNode);
-    removeShadowNode(child);
-  }
-
-  private void dropNativeViews(ReactShadowNode child, ReactShadowNode parentNode) {
-    if (child instanceof FlatShadowNode) {
-      FlatShadowNode node = (FlatShadowNode) child;
-      if (node.mountsToView() && node.isBackingViewCreated()) {
-        int tag = -1;
-
-        // this tag is used to remove the reference to this dropping view if it it's clipped.
-        // we need to figure out the correct "view parent" tag to do this. note that this is
-        // not necessarily getParent().getReactTag(), since getParent() may represent something
-        // that's not a View - we need to find the first View (what would represent
-        // view.getParent() on the ui thread), which is what this code is finding.
-        ReactShadowNode tmpNode = parentNode;
-        while (tmpNode != null) {
-          if (tmpNode instanceof FlatShadowNode) {
-            FlatShadowNode flatTmpNode = (FlatShadowNode) tmpNode;
-            if (flatTmpNode.mountsToView() && flatTmpNode.isBackingViewCreated() &&
-              flatTmpNode.getParent() != null) {
-              tag = flatTmpNode.getReactTag();
-              break;
-            }
-          }
-          tmpNode = tmpNode.getParent();
-        }
-
-        // this will recursively drop all subviews
-        mStateBuilder.dropView(node, tag);
-        return;
-      }
-    }
-
-    for (int i = 0, childCount = child.getChildCount(); i != childCount; ++i) {
-      dropNativeViews(child.getChildAt(i), child);
-    }
-  }
-
-  /**
-   * Prepares a given element to be moved to a new position.
-   */
-  private void moveChild(ReactShadowNode child, int moveFromIndex) {
-    mMoveProxy.setChildMoveFrom(moveFromIndex, child);
-  }
-
-  /**
-   * Adds all children from addChildTags and moveFrom/moveTo.
-   */
-  private void addChildren(
-    ReactShadowNode parentNode,
-    @Nullable ReadableArray addChildTags,
-    @Nullable ReadableArray addAtIndices) {
-
-    int prevIndex = -1;
-
-    int moveToIndex;
-    int moveToChildIndex;
-    if (mMoveProxy.size() == 0) {
-      moveToIndex = Integer.MAX_VALUE;
-      moveToChildIndex = Integer.MAX_VALUE;
-    } else {
-      moveToIndex = 0;
-      moveToChildIndex = mMoveProxy.getMoveTo(0);
-    }
-
-    int numNodesToAdd;
-    int addToIndex;
-    int addToChildIndex;
-    if (addAtIndices == null) {
-      numNodesToAdd = 0;
-      addToIndex = Integer.MAX_VALUE;
-      addToChildIndex = Integer.MAX_VALUE;
-    } else {
-      numNodesToAdd = addAtIndices.size();
-      addToIndex = 0;
-      addToChildIndex = addAtIndices.getInt(0);
-    }
-
-    // both mMoveProxy and addChildTags are already sorted, but combined order is not sorted. Use
-    // a merge step from mergesort to walk over both arrays and extract elements in sorted order.
-
-    while (true) {
-      if (addToChildIndex < moveToChildIndex) {
-        ReactShadowNode addToChild = resolveShadowNode(addChildTags.getInt(addToIndex));
-        addChildAt(parentNode, addToChild, addToChildIndex, prevIndex);
-        prevIndex = addToChildIndex;
-
-        ++addToIndex;
-        if (addToIndex == numNodesToAdd) {
-          addToChildIndex = Integer.MAX_VALUE;
-        } else {
-          addToChildIndex = addAtIndices.getInt(addToIndex);
-        }
-      } else if (moveToChildIndex < addToChildIndex) {
-        ReactShadowNode moveToChild = mMoveProxy.getChildMoveTo(moveToIndex);
-        addChildAt(parentNode, moveToChild, moveToChildIndex, prevIndex);
-        prevIndex = moveToChildIndex;
-
-        ++moveToIndex;
-        if (moveToIndex == mMoveProxy.size()) {
-          moveToChildIndex = Integer.MAX_VALUE;
-        } else {
-          moveToChildIndex = mMoveProxy.getMoveTo(moveToIndex);
-        }
-      } else {
-        // moveToChildIndex == addToChildIndex can only be if both are equal to Integer.MAX_VALUE
-        // which means that we exhausted both arrays, and all children are added.
-        break;
-      }
-    }
-  }
-
-  /**
-   * Removes a child from parent, verifying that we are removing in descending order.
-   */
-  private static ReactShadowNode removeChildAt(
-    ReactShadowNode parentNode,
-    int index,
-    int prevIndex) {
-    if (index >= prevIndex) {
-      throw new RuntimeException(
-        "Invariant failure, needs sorting! " + index + " >= " + prevIndex);
-    }
-
-    return parentNode.removeChildAt(index);
-  }
-
-  /**
-   * Adds a child to parent, verifying that we are adding in ascending order.
-   */
-  private static void addChildAt(
-    ReactShadowNode parentNode,
-    ReactShadowNode childNode,
-    int index,
-    int prevIndex) {
-    if (index <= prevIndex) {
-      throw new RuntimeException(
-        "Invariant failure, needs sorting! " + index + " <= " + prevIndex);
-    }
-
-    parentNode.addChildAt(childNode, index);
-  }
-
-  @Override
-  protected void updateViewHierarchy() {
-    super.updateViewHierarchy();
-    mStateBuilder.afterUpdateViewHierarchy(mEventDispatcher);
-  }
-
-  @Override
-  protected void applyUpdatesRecursive(
-    ReactShadowNode cssNode,
-    float absoluteX,
-    float absoluteY) {
-    mStateBuilder.applyUpdates((FlatRootShadowNode) cssNode);
-  }
-
-  @Override
-  public void removeRootView(int rootViewTag) {
-    if (mMemoryImprovementEnabled) {
-      removeRootShadowNode(rootViewTag);
-    }
-    mStateBuilder.removeRootView(rootViewTag);
-  }
-
-  @Override
-  public void setJSResponder(int possiblyVirtualReactTag, boolean blockNativeResponder) {
-    ReactShadowNode node = resolveShadowNode(possiblyVirtualReactTag);
-    while (node.isVirtual()) {
-      node = node.getParent();
-    }
-    int tag = node.getReactTag();
-
-    // if the node in question doesn't mount to a View, find the first parent that does mount to
-    // a View. without this, we'll crash when we try to set the JSResponder, since part of that
-    // is to find the parent view and ask it to not intercept touch events.
-    while (node instanceof FlatShadowNode && !((FlatShadowNode) node).mountsToView()) {
-      node = node.getParent();
-    }
-
-    FlatUIViewOperationQueue operationsQueue = mStateBuilder.getOperationsQueue();
-    operationsQueue.enqueueSetJSResponder(
-      node == null ? tag : node.getReactTag(),
-      possiblyVirtualReactTag,
-      blockNativeResponder);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatUIViewOperationQueue.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatUIViewOperationQueue.java
deleted file mode 100644
index 3806e2ebc602..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatUIViewOperationQueue.java
+++ /dev/null
@@ -1,527 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.react.uimanager.UIViewOperationQueue;
-import android.util.SparseIntArray;
-import android.view.View;
-import android.view.ViewGroup;
-import com.facebook.react.bridge.Callback;
-import com.facebook.react.bridge.ReactApplicationContext;
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.uimanager.IllegalViewOperationException;
-import com.facebook.react.uimanager.NoSuchNativeViewException;
-import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.TouchTargetHelper;
-import com.facebook.react.uimanager.UIViewOperationQueue;
-import java.util.ArrayList;
-import javax.annotation.Nullable;
-
-/**
- * FlatUIViewOperationQueue extends {@link UIViewOperationQueue} to add
- * FlatUIImplementation-specific methods that need to run in UI thread.
- */
-/* package */ final class FlatUIViewOperationQueue extends UIViewOperationQueue {
-
-  private static final int[] MEASURE_BUFFER = new int[4];
-
-  private final FlatNativeViewHierarchyManager mNativeViewHierarchyManager;
-  private final ProcessLayoutRequests mProcessLayoutRequests = new ProcessLayoutRequests();
-
-  private final class ProcessLayoutRequests implements UIViewOperationQueue.UIOperation {
-    @Override
-    public void execute() {
-      FlatViewGroup.processLayoutRequests();
-    }
-  }
-
-  /**
-   * UIOperation that updates DrawCommands for a View defined by reactTag.
-   */
-  private final class UpdateMountState implements UIViewOperationQueue.UIOperation {
-
-    private final int mReactTag;
-    private final @Nullable DrawCommand[] mDrawCommands;
-    private final @Nullable AttachDetachListener[] mAttachDetachListeners;
-    private final @Nullable NodeRegion[] mNodeRegions;
-
-    private UpdateMountState(
-        int reactTag,
-        @Nullable DrawCommand[] drawCommands,
-        @Nullable AttachDetachListener[] listeners,
-        @Nullable NodeRegion[] nodeRegions) {
-      mReactTag = reactTag;
-      mDrawCommands = drawCommands;
-      mAttachDetachListeners = listeners;
-      mNodeRegions = nodeRegions;
-    }
-
-    @Override
-    public void execute() {
-      mNativeViewHierarchyManager.updateMountState(
-          mReactTag,
-          mDrawCommands,
-          mAttachDetachListeners,
-          mNodeRegions);
-    }
-  }
-
-  /**
-   * UIOperation that updates DrawCommands for a View defined by reactTag.
-   */
-  private final class UpdateClippingMountState implements UIViewOperationQueue.UIOperation {
-
-    private final int mReactTag;
-    private final @Nullable DrawCommand[] mDrawCommands;
-    private final SparseIntArray mDrawViewIndexMap;
-    private final float[] mCommandMaxBot;
-    private final float[] mCommandMinTop;
-    private final @Nullable AttachDetachListener[] mAttachDetachListeners;
-    private final @Nullable NodeRegion[] mNodeRegions;
-    private final float[] mRegionMaxBot;
-    private final float[] mRegionMinTop;
-    private final boolean mWillMountViews;
-
-    private UpdateClippingMountState(
-        int reactTag,
-        @Nullable DrawCommand[] drawCommands,
-        SparseIntArray drawViewIndexMap,
-        float[] commandMaxBot,
-        float[] commandMinTop,
-        @Nullable AttachDetachListener[] listeners,
-        @Nullable NodeRegion[] nodeRegions,
-        float[] regionMaxBot,
-        float[] regionMinTop,
-        boolean willMountViews) {
-      mReactTag = reactTag;
-      mDrawCommands = drawCommands;
-      mDrawViewIndexMap = drawViewIndexMap;
-      mCommandMaxBot = commandMaxBot;
-      mCommandMinTop = commandMinTop;
-      mAttachDetachListeners = listeners;
-      mNodeRegions = nodeRegions;
-      mRegionMaxBot = regionMaxBot;
-      mRegionMinTop = regionMinTop;
-      mWillMountViews = willMountViews;
-    }
-
-    @Override
-    public void execute() {
-      mNativeViewHierarchyManager.updateClippingMountState(
-          mReactTag,
-          mDrawCommands,
-          mDrawViewIndexMap,
-          mCommandMaxBot,
-          mCommandMinTop,
-          mAttachDetachListeners,
-          mNodeRegions,
-          mRegionMaxBot,
-          mRegionMinTop,
-          mWillMountViews);
-    }
-  }
-
-  private final class UpdateViewGroup implements UIViewOperationQueue.UIOperation {
-
-    private final int mReactTag;
-    private final int[] mViewsToAdd;
-    private final int[] mViewsToDetach;
-
-    private UpdateViewGroup(int reactTag, int[] viewsToAdd, int[] viewsToDetach) {
-      mReactTag = reactTag;
-      mViewsToAdd = viewsToAdd;
-      mViewsToDetach = viewsToDetach;
-    }
-
-    @Override
-    public void execute() {
-      mNativeViewHierarchyManager.updateViewGroup(mReactTag, mViewsToAdd, mViewsToDetach);
-    }
-  }
-
-  /**
-   * UIOperation that updates View bounds for a View defined by reactTag.
-   */
-  public final class UpdateViewBounds implements UIViewOperationQueue.UIOperation {
-
-    private final int mReactTag;
-    private final int mLeft;
-    private final int mTop;
-    private final int mRight;
-    private final int mBottom;
-
-    private UpdateViewBounds(int reactTag, int left, int top, int right, int bottom) {
-      mReactTag = reactTag;
-      mLeft = left;
-      mTop = top;
-      mRight = right;
-      mBottom = bottom;
-    }
-
-    @Override
-    public void execute() {
-      mNativeViewHierarchyManager.updateViewBounds(mReactTag, mLeft, mTop, mRight, mBottom);
-    }
-  }
-
-  private final class SetPadding implements UIViewOperationQueue.UIOperation {
-
-    private final int mReactTag;
-    private final int mPaddingLeft;
-    private final int mPaddingTop;
-    private final int mPaddingRight;
-    private final int mPaddingBottom;
-
-    private SetPadding(
-        int reactTag,
-        int paddingLeft,
-        int paddingTop,
-        int paddingRight,
-        int paddingBottom) {
-      mReactTag = reactTag;
-      mPaddingLeft = paddingLeft;
-      mPaddingTop = paddingTop;
-      mPaddingRight = paddingRight;
-      mPaddingBottom = paddingBottom;
-    }
-
-    @Override
-    public void execute() {
-      mNativeViewHierarchyManager.setPadding(
-          mReactTag,
-          mPaddingLeft,
-          mPaddingTop,
-          mPaddingRight,
-          mPaddingBottom);
-    }
-  }
-
-  private final class DropViews implements UIViewOperationQueue.UIOperation {
-
-    private final SparseIntArray mViewsToDrop;
-
-    private DropViews(ArrayList<Integer> viewsToDrop, ArrayList<Integer> parentsForViewsToDrop) {
-      SparseIntArray sparseIntArray = new SparseIntArray();
-      for (int i = 0, count = viewsToDrop.size(); i < count; i++) {
-        sparseIntArray.put(viewsToDrop.get(i), parentsForViewsToDrop.get(i));
-      }
-      mViewsToDrop = sparseIntArray;
-    }
-
-    @Override
-    public void execute() {
-      mNativeViewHierarchyManager.dropViews(mViewsToDrop);
-    }
-  }
-
-  private final class MeasureVirtualView implements UIViewOperationQueue.UIOperation {
-
-    private final int mReactTag;
-    private final float mScaledX;
-    private final float mScaledY;
-    private final float mScaledWidth;
-    private final float mScaledHeight;
-    private final Callback mCallback;
-    private final boolean mRelativeToWindow;
-
-    private MeasureVirtualView(
-        int reactTag,
-        float scaledX,
-        float scaledY,
-        float scaledWidth,
-        float scaledHeight,
-        boolean relativeToWindow,
-        Callback callback) {
-      mReactTag = reactTag;
-      mScaledX = scaledX;
-      mScaledY = scaledY;
-      mScaledWidth = scaledWidth;
-      mScaledHeight = scaledHeight;
-      mCallback = callback;
-      mRelativeToWindow = relativeToWindow;
-    }
-
-    @Override
-    public void execute() {
-      try {
-        // Measure native View
-        if (mRelativeToWindow) {
-          // relative to the window
-          mNativeViewHierarchyManager.measureInWindow(mReactTag, MEASURE_BUFFER);
-        } else {
-          // relative to the root view
-          mNativeViewHierarchyManager.measure(mReactTag, MEASURE_BUFFER);
-        }
-      } catch (NoSuchNativeViewException noSuchNativeViewException) {
-        // Invoke with no args to signal failure and to allow JS to clean up the callback
-        // handle.
-        mCallback.invoke();
-        return;
-      }
-
-      float nativeViewX = MEASURE_BUFFER[0];
-      float nativeViewY = MEASURE_BUFFER[1];
-      float nativeViewWidth = MEASURE_BUFFER[2];
-      float nativeViewHeight = MEASURE_BUFFER[3];
-
-      // Calculate size of the virtual child inside native View.
-      float x = PixelUtil.toDIPFromPixel(mScaledX * nativeViewWidth + nativeViewX);
-      float y = PixelUtil.toDIPFromPixel(mScaledY * nativeViewHeight + nativeViewY);
-      float width = PixelUtil.toDIPFromPixel(mScaledWidth * nativeViewWidth);
-      float height = PixelUtil.toDIPFromPixel(mScaledHeight * nativeViewHeight);
-
-      if (mRelativeToWindow) {
-        mCallback.invoke(x, y, width, height);
-      } else {
-        mCallback.invoke(0, 0, width, height, x, y);
-      }
-    }
-  }
-
-  public final class DetachAllChildrenFromViews implements UIViewOperationQueue.UIOperation {
-    private @Nullable int[] mViewsToDetachAllChildrenFrom;
-
-    public void setViewsToDetachAllChildrenFrom(int[] viewsToDetachAllChildrenFrom) {
-      mViewsToDetachAllChildrenFrom = viewsToDetachAllChildrenFrom;
-    }
-
-    @Override
-    public void execute() {
-      mNativeViewHierarchyManager.detachAllChildrenFromViews(mViewsToDetachAllChildrenFrom);
-    }
-  }
-
-  private final class FindTargetForTouchOperation implements UIViewOperationQueue.UIOperation {
-
-    private final int mReactTag;
-    private final float mTargetX;
-    private final float mTargetY;
-    private final Callback mCallback;
-    private final int[] NATIVE_VIEW_BUFFER = new int[1];
-
-    private FindTargetForTouchOperation(
-        final int reactTag,
-        final float targetX,
-        final float targetY,
-        final Callback callback) {
-      super();
-      mReactTag = reactTag;
-      mTargetX = targetX;
-      mTargetY = targetY;
-      mCallback = callback;
-    }
-
-    @Override
-    public void execute() {
-      try {
-        mNativeViewHierarchyManager.measure(mReactTag, MEASURE_BUFFER);
-      } catch (IllegalViewOperationException e) {
-        mCallback.invoke();
-        return;
-      }
-
-      // Because React coordinates are relative to root container, and measure() operates
-      // on screen coordinates, we need to offset values using root container location.
-      final float containerX = (float) MEASURE_BUFFER[0];
-      final float containerY = (float) MEASURE_BUFFER[1];
-
-      View view = mNativeViewHierarchyManager.getView(mReactTag);
-      final int touchTargetReactTag = TouchTargetHelper.findTargetTagForTouch(
-          mTargetX,
-          mTargetY,
-          (ViewGroup) view,
-          NATIVE_VIEW_BUFFER);
-
-      try {
-        mNativeViewHierarchyManager.measure(
-            NATIVE_VIEW_BUFFER[0],
-            MEASURE_BUFFER);
-      } catch (IllegalViewOperationException e) {
-        mCallback.invoke();
-        return;
-      }
-
-      NodeRegion region = NodeRegion.EMPTY;
-      boolean isNativeView = NATIVE_VIEW_BUFFER[0] == touchTargetReactTag;
-      if (!isNativeView) {
-        // NATIVE_VIEW_BUFFER[0] is a FlatViewGroup, touchTargetReactTag is the touch target and
-        // isn't an Android View - try to get its NodeRegion
-        view = mNativeViewHierarchyManager.getView(NATIVE_VIEW_BUFFER[0]);
-        if (view instanceof FlatViewGroup) {
-          region = ((FlatViewGroup) view).getNodeRegionForTag(mReactTag);
-        }
-      }
-
-      int resultTag = region == NodeRegion.EMPTY ? touchTargetReactTag : region.mTag;
-      float x = PixelUtil.toDIPFromPixel(region.getLeft() + MEASURE_BUFFER[0] - containerX);
-      float y = PixelUtil.toDIPFromPixel(region.getTop() + MEASURE_BUFFER[1] - containerY);
-      float width = PixelUtil.toDIPFromPixel(isNativeView ?
-          MEASURE_BUFFER[2] : region.getRight() - region.getLeft());
-      float height = PixelUtil.toDIPFromPixel(isNativeView ?
-          MEASURE_BUFFER[3] : region.getBottom() - region.getTop());
-      mCallback.invoke(resultTag, x, y, width, height);
-    }
-  }
-
-  /**
-   * Used to delay view manager command dispatch until after the view hierarchy is updated.
-   * Mirrors command operation dispatch, but is only used in Nodes for view manager commands.
-   */
-  public final class ViewManagerCommand implements UIViewOperationQueue.UIOperation {
-
-    private final int mReactTag;
-    private final int mCommand;
-    private final @Nullable ReadableArray mArgs;
-
-    public ViewManagerCommand(
-        int reactTag,
-        int command,
-        @Nullable ReadableArray args) {
-      mReactTag = reactTag;
-      mCommand = command;
-      mArgs = args;
-    }
-
-    @Override
-    public void execute() {
-      mNativeViewHierarchyManager.dispatchCommand(mReactTag, mCommand, mArgs);
-    }
-  }
-
-  public FlatUIViewOperationQueue(
-      ReactApplicationContext reactContext,
-      FlatNativeViewHierarchyManager nativeViewHierarchyManager,
-      int minTimeLeftInFrameForNonBatchedOperationMs) {
-    super(reactContext, nativeViewHierarchyManager, minTimeLeftInFrameForNonBatchedOperationMs);
-
-    mNativeViewHierarchyManager = nativeViewHierarchyManager;
-  }
-
-  /**
-   * Enqueues a new UIOperation that will update DrawCommands for a View defined by reactTag.
-   */
-  public void enqueueUpdateMountState(
-      int reactTag,
-      @Nullable DrawCommand[] drawCommands,
-      @Nullable AttachDetachListener[] listeners,
-      @Nullable NodeRegion[] nodeRegions) {
-    enqueueUIOperation(new UpdateMountState(
-        reactTag,
-        drawCommands,
-        listeners,
-        nodeRegions));
-  }
-
-  /**
-   * Enqueues a new UIOperation that will update DrawCommands for a View defined by reactTag.
-   */
-  public void enqueueUpdateClippingMountState(
-      int reactTag,
-      @Nullable DrawCommand[] drawCommands,
-      SparseIntArray drawViewIndexMap,
-      float[] commandMaxBot,
-      float[] commandMinTop,
-      @Nullable AttachDetachListener[] listeners,
-      @Nullable NodeRegion[] nodeRegions,
-      float[] regionMaxBot,
-      float[] regionMinTop,
-      boolean willMountViews) {
-    enqueueUIOperation(new UpdateClippingMountState(
-        reactTag,
-        drawCommands,
-        drawViewIndexMap,
-        commandMaxBot,
-        commandMinTop,
-        listeners,
-        nodeRegions,
-        regionMaxBot,
-        regionMinTop,
-        willMountViews));
-  }
-
-  public void enqueueUpdateViewGroup(int reactTag, int[] viewsToAdd, int[] viewsToDetach) {
-    enqueueUIOperation(new UpdateViewGroup(reactTag, viewsToAdd, viewsToDetach));
-  }
-
-  /**
-   * Creates a new UIOperation that will update View bounds for a View defined by reactTag.
-   */
-  public UpdateViewBounds createUpdateViewBounds(
-      int reactTag,
-      int left,
-      int top,
-      int right,
-      int bottom) {
-    return new UpdateViewBounds(reactTag, left, top, right, bottom);
-  }
-
-  public ViewManagerCommand createViewManagerCommand(
-      int reactTag,
-      int command,
-      @Nullable ReadableArray args) {
-    return new ViewManagerCommand(reactTag, command, args);
-  }
-
-  /* package */ void enqueueFlatUIOperation(UIViewOperationQueue.UIOperation operation) {
-    enqueueUIOperation(operation);
-  }
-
-  public void enqueueSetPadding(
-      int reactTag,
-      int paddingLeft,
-      int paddingTop,
-      int paddingRight,
-      int paddingBottom) {
-    enqueueUIOperation(
-        new SetPadding(reactTag, paddingLeft, paddingTop, paddingRight, paddingBottom));
-  }
-
-  public void enqueueDropViews(
-      ArrayList<Integer> viewsToDrop,
-      ArrayList<Integer> parentsOfViewsToDrop) {
-    enqueueUIOperation(new DropViews(viewsToDrop, parentsOfViewsToDrop));
-  }
-
-  public void enqueueMeasureVirtualView(
-      int reactTag,
-      float scaledX,
-      float scaledY,
-      float scaledWidth,
-      float scaledHeight,
-      boolean relativeToWindow,
-      Callback callback) {
-    enqueueUIOperation(new MeasureVirtualView(
-        reactTag,
-        scaledX,
-        scaledY,
-        scaledWidth,
-        scaledHeight,
-        relativeToWindow,
-        callback));
-  }
-
-  public void enqueueProcessLayoutRequests() {
-    enqueueUIOperation(mProcessLayoutRequests);
-  }
-
-  public DetachAllChildrenFromViews enqueueDetachAllChildrenFromViews() {
-    DetachAllChildrenFromViews op = new DetachAllChildrenFromViews();
-    enqueueUIOperation(op);
-    return op;
-  }
-
-  @Override
-  public void enqueueFindTargetForTouch(
-      final int reactTag,
-      final float targetX,
-      final float targetY,
-      final Callback callback) {
-    enqueueUIOperation(
-        new FindTargetForTouchOperation(reactTag, targetX, targetY, callback));
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
deleted file mode 100644
index eb5f4cf15615..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewGroup.java
+++ /dev/null
@@ -1,1197 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.graphics.Typeface;
-import android.graphics.drawable.Drawable;
-import android.util.SparseArray;
-import android.util.SparseIntArray;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewParent;
-import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.ReactContext;
-import com.facebook.react.bridge.SoftAssertions;
-import com.facebook.react.touch.OnInterceptTouchEventListener;
-import com.facebook.react.touch.ReactHitSlopView;
-import com.facebook.react.touch.ReactInterceptingViewGroup;
-import com.facebook.react.uimanager.PointerEvents;
-import com.facebook.react.uimanager.ReactClippingViewGroup;
-import com.facebook.react.uimanager.ReactCompoundViewGroup;
-import com.facebook.react.uimanager.ReactPointerEventsView;
-import com.facebook.react.uimanager.UIManagerModule;
-import com.facebook.react.uimanager.events.EventDispatcher;
-import com.facebook.react.views.image.ImageLoadEvent;
-import java.lang.ref.WeakReference;
-import java.util.ArrayList;
-import javax.annotation.Nullable;
-
-/**
- * A view that the {@link FlatShadowNode} hierarchy maps to.  Can mount and draw native views as
- * well as draw commands.  We reuse some of Android's ViewGroup logic, but in Nodes we try to
- * minimize the amount of shadow nodes that map to native children, so we have a lot of logic
- * specific to draw commands.
- *
- * In a very simple case with no Android children, the FlatViewGroup will receive:
- *
- *   flatViewGroup.mountDrawCommands(...);
- *   flatViewGroup.dispatchDraw(...);
- *
- * The draw commands are mounted, then draw iterates through and draws them one by one.
- *
- * In a simple case where there are native children:
- *
- *   flatViewGroup.mountDrawCommands(...);
- *   flatViewGroup.detachAllViewsFromParent(...);
- *   flatViewGroup.mountViews(...);
- *   flatViewGroup.dispatchDraw(...);
- *
- * Draw commands are mounted, with a draw view command for each mounted view.  As an optimization
- * we then detach all views from the FlatViewGroup, then allow mountViews to selectively reattach
- * and add views in order.  We do this as adding a single view is a O(n) operation (On average you
- * have to move all the views in the array to the right one position), as is dropping and re-adding
- * all views (One pass to clear the array and one pass to re-attach detached children and add new
- * children).
- *
- * FlatViewGroups also have arrays of node regions, which are little more than a rects that
- * represents a touch target.  Native views contain their own touch logic, but not all react tags
- * map to native views.  We use node regions to find touch targets among commands as well as nodes
- * which map to native views.
- *
- * In the case of clipping, much of the underlying logic for is handled by
- * {@link DrawCommandManager}.  This lets us separate logic, while also allowing us to save on
- * memory for data structures only used in clipping.  In a case of a clipping FlatViewGroup which
- * is scrolling:
- *
- *   flatViewGroup.setRemoveClippedSubviews(true);
- *   flatViewGroup.mountClippingDrawCommands(...);
- *   flatViewGroup.detachAllViewsFromParent(...);
- *   flatViewGroup.mountViews(...);
- *   flatViewGroup.updateClippingRect(...);
- *   flatViewGroup.dispatchDraw(...);
- *   flatViewGroup.updateClippingRect(...);
- *   flatViewGroup.dispatchDraw(...);
- *   flatViewGroup.updateClippingRect(...);
- *   flatViewGroup.dispatchDraw(...);
- *
- * Setting remove clipped subviews creates a {@link DrawCommandManager} to handle clipping, which
- * allows the rest of the methods to simply call in to draw command manager to handle the clipping
- * logic.
- */
-/* package */ final class FlatViewGroup extends ViewGroup
-    implements ReactInterceptingViewGroup, ReactClippingViewGroup,
-    ReactCompoundViewGroup, ReactHitSlopView, ReactPointerEventsView, FlatMeasuredViewGroup {
-  /**
-   * Helper class that allows our AttachDetachListeners to invalidate the hosting View.  When a
-   * listener gets an attach it is passed an invalidate callback for the FlatViewGroup it is being
-   * attached to.
-   */
-  static final class InvalidateCallback extends WeakReference<FlatViewGroup> {
-
-    private InvalidateCallback(FlatViewGroup view) {
-      super(view);
-    }
-
-    /**
-     * Propagates invalidate() call up to the hosting View (if it's still alive)
-     */
-    public void invalidate() {
-      FlatViewGroup view = get();
-      if (view != null) {
-        view.invalidate();
-      }
-    }
-
-    /**
-     * Propagates image load events to javascript if the hosting view is still alive.
-     *
-     * @param reactTag The view id.
-     * @param imageLoadEvent The event type.
-     */
-    public void dispatchImageLoadEvent(int reactTag, int imageLoadEvent) {
-      FlatViewGroup view = get();
-      if (view == null) {
-        return;
-      }
-
-      ReactContext reactContext = ((ReactContext) view.getContext());
-      reactContext.getNativeModule(UIManagerModule.class).getEventDispatcher().dispatchEvent(
-          new ImageLoadEvent(reactTag, imageLoadEvent));
-    }
-  }
-
-  // Draws the name of the draw commands at the bottom right corner of it's bounds.
-  private static final boolean DEBUG_DRAW_TEXT = false;
-  // Draws colored rectangles over known performance issues.
-  /* package */ static final boolean DEBUG_HIGHLIGHT_PERFORMANCE_ISSUES = false;
-  // Force layout bounds drawing.  This can also be enabled by turning on layout bounds in Android.
-  private static final boolean DEBUG_DRAW = DEBUG_DRAW_TEXT || DEBUG_HIGHLIGHT_PERFORMANCE_ISSUES;
-  // Resources for debug drawing.
-  private boolean mAndroidDebugDraw;
-  private static Paint sDebugTextPaint;
-  private static Paint sDebugTextBackgroundPaint;
-  private static Paint sDebugRectPaint;
-  private static Paint sDebugCornerPaint;
-  private static Rect sDebugRect;
-
-  private static final ArrayList<FlatViewGroup> LAYOUT_REQUESTS = new ArrayList<>();
-  private static final Rect VIEW_BOUNDS = new Rect();
-
-  // An invalidate callback singleton for this FlatViewGroup.
-  private @Nullable InvalidateCallback mInvalidateCallback;
-  private DrawCommand[] mDrawCommands = DrawCommand.EMPTY_ARRAY;
-  private AttachDetachListener[] mAttachDetachListeners = AttachDetachListener.EMPTY_ARRAY;
-  private NodeRegion[] mNodeRegions = NodeRegion.EMPTY_ARRAY;
-
-  // The index of the next native child to draw.  This is used in dispatchDraw to check that we are
-  // actually drawing all of our attached children, then is reset to 0.
-  private int mDrawChildIndex = 0;
-  private boolean mIsAttached = false;
-  private boolean mIsLayoutRequested = false;
-  private boolean mNeedsOffscreenAlphaCompositing = false;
-  private Drawable mHotspot;
-  private PointerEvents mPointerEvents = PointerEvents.AUTO;
-  private long mLastTouchDownTime;
-  private @Nullable OnInterceptTouchEventListener mOnInterceptTouchEventListener;
-
-  private static final SparseArray<View> EMPTY_DETACHED_VIEWS = new SparseArray<>(0);
-  // Provides clipping, drawing and node region finding logic if subview clipping is enabled.
-  private @Nullable DrawCommandManager mDrawCommandManager;
-
-  private @Nullable Rect mHitSlopRect;
-
-  /* package */ FlatViewGroup(Context context) {
-    super(context);
-    setClipChildren(false);
-  }
-
-  @Override
-  protected void detachAllViewsFromParent() {
-    super.detachAllViewsFromParent();
-  }
-
-  @Override
-  @SuppressLint("MissingSuperCall")
-  public void requestLayout() {
-    if (mIsLayoutRequested) {
-      return;
-    }
-
-    mIsLayoutRequested = true;
-    LAYOUT_REQUESTS.add(this);
-  }
-
-  @Override
-  public int reactTagForTouch(float touchX, float touchY) {
-    /*
-     * Make sure we don't find any children if the pointer events are set to BOX_ONLY.
-     * There is no need to special-case any other modes, because if PointerEvents are set to:
-     * a) PointerEvents.AUTO - all children are included, nothing to exclude
-     * b) PointerEvents.NONE - this method will NOT be executed, because the View will be filtered
-     *    out by TouchTargetHelper.
-     * c) PointerEvents.BOX_NONE - TouchTargetHelper will make sure that {@link #reactTagForTouch()}
-     *     doesn't return getId().
-     */
-    SoftAssertions.assertCondition(
-        mPointerEvents != PointerEvents.NONE,
-        "TouchTargetHelper should not allow calling this method when pointer events are NONE");
-
-    if (mPointerEvents != PointerEvents.BOX_ONLY) {
-      NodeRegion nodeRegion = virtualNodeRegionWithinBounds(touchX, touchY);
-      if (nodeRegion != null) {
-        return nodeRegion.getReactTag(touchX, touchY);
-      }
-    }
-
-    // no children found
-    return getId();
-  }
-
-  @Override
-  public boolean interceptsTouchEvent(float touchX, float touchY) {
-    NodeRegion nodeRegion = anyNodeRegionWithinBounds(touchX, touchY);
-    return nodeRegion != null && nodeRegion.mIsVirtual;
-  }
-
-  /**
-   * Secretly Overrides the hidden ViewGroup.onDebugDraw method.  This is hidden in the Android
-   * ViewGroup, but still gets called in super.dispatchDraw.  Overriding here allows us to draw
-   * layout bounds for Nodes when android is drawing layout bounds.
-   */
-  protected void onDebugDraw(Canvas canvas) {
-    // Android is drawing layout bounds, so we should as well.
-    mAndroidDebugDraw = true;
-  }
-
-  /**
-   * Draw FlatViewGroup on a canvas.  Also checks that all children are drawn, as a draw view calls
-   * back to the FlatViewGroup to draw each child.
-   *
-   * @param canvas The canvas to draw on.
-   */
-  @Override
-  public void dispatchDraw(Canvas canvas) {
-    mAndroidDebugDraw = false;
-    super.dispatchDraw(canvas);
-
-    if (mDrawCommandManager != null) {
-      mDrawCommandManager.draw(canvas);
-    } else {
-      for (DrawCommand drawCommand : mDrawCommands) {
-        drawCommand.draw(this, canvas);
-      }
-    }
-
-    if (mDrawChildIndex != getChildCount()) {
-      throw new RuntimeException(
-          "Did not draw all children: " + mDrawChildIndex + " / " + getChildCount());
-    }
-    mDrawChildIndex = 0;
-
-    if (DEBUG_DRAW || mAndroidDebugDraw) {
-      initDebugDrawResources();
-      debugDraw(canvas);
-    }
-
-    if (mHotspot != null) {
-      mHotspot.draw(canvas);
-    }
-  }
-
-  /**
-   * Draws layout bounds for debug.  Optionally can draw the name of the DrawCommand so you can
-   * distinguish commands easier.
-   *
-   * @param canvas The canvas to draw on.
-   */
-  private void debugDraw(Canvas canvas) {
-    if (mDrawCommandManager != null) {
-      mDrawCommandManager.debugDraw(canvas);
-    } else {
-      for (DrawCommand drawCommand : mDrawCommands) {
-        drawCommand.debugDraw(this, canvas);
-      }
-    }
-    mDrawChildIndex = 0;
-  }
-
-  /**
-   * This override exists to suppress the default drawing behaviour of the ViewGroup.  dispatchDraw
-   * calls super.dispatchDraw, which lets Android perform some of our child management logic.
-   * super.dispatchDraw then calls our drawChild, which is suppressed.
-   *
-   * dispatchDraw within the FlatViewGroup then calls super.drawChild, which actually draws the
-   * child.
-   *
-   *   // Pseudocode example.
-   *   Class FlatViewGroup {
-   *     void dispatchDraw() {
-   *       super.dispatchDraw(); // Eventually calls our drawChild, which is a no op.
-   *       super.drawChild();    // Calls the actual drawChild.
-   *     }
-   *
-   *     boolean drawChild(...) {
-   *       // No op.
-   *     }
-   *   }
-   *
-   *   Class ViewGroup {
-   *     void dispatchDraw() {
-   *       drawChild(); // No op.
-   *     }
-   *
-   *     boolean drawChild(...) {
-   *       getChildAt(...).draw();
-   *     }
-   *   }
-   *
-   * @return false, as we are suppressing drawChild.
-   */
-  @Override
-  protected boolean drawChild(Canvas canvas, View child, long drawingTime) {
-    // suppress
-    // no drawing -> no invalidate -> return false
-    return false;
-  }
-
-  /**
-   * Draw layout bounds for the next child.
-   *
-   * @param canvas The canvas to draw on.
-   */
-  /* package */ void debugDrawNextChild(Canvas canvas) {
-    View child = getChildAt(mDrawChildIndex);
-    // Draw FlatViewGroups a different color than regular child views.
-    int color = child instanceof FlatViewGroup ? Color.DKGRAY : Color.RED;
-    debugDrawRect(
-        canvas,
-        color,
-        child.getLeft(),
-        child.getTop(),
-        child.getRight(),
-        child.getBottom());
-    ++mDrawChildIndex;
-  }
-
-  // Used in debug drawing.
-  /* package */ int dipsToPixels(int dips) {
-    float scale = getResources().getDisplayMetrics().density;
-    return (int) (dips * scale + 0.5f);
-  }
-
-  // Used in debug drawing.
-  private static void fillRect(Canvas canvas, Paint paint, float x1, float y1, float x2, float y2) {
-    if (x1 != x2 && y1 != y2) {
-      if (x1 > x2) {
-        float tmp = x1; x1 = x2; x2 = tmp;
-      }
-      if (y1 > y2) {
-        float tmp = y1; y1 = y2; y2 = tmp;
-      }
-      canvas.drawRect(x1, y1, x2, y2, paint);
-    }
-  }
-
-  // Used in debug drawing.
-  private static int sign(float x) {
-    return (x >= 0) ? 1 : -1;
-  }
-
-  // Used in debug drawing.
-  private static void drawCorner(
-      Canvas c,
-      Paint paint,
-      float x1,
-      float y1,
-      float dx,
-      float dy,
-      float lw) {
-    fillRect(c, paint, x1, y1, x1 + dx, y1 + lw * sign(dy));
-    fillRect(c, paint, x1, y1, x1 + lw * sign(dx), y1 + dy);
-  }
-
-  // Used in debug drawing.
-  private static void drawRectCorners(
-      Canvas canvas,
-      float x1,
-      float y1,
-      float x2,
-      float y2,
-      Paint paint,
-      int lineLength,
-      int lineWidth) {
-    drawCorner(canvas, paint, x1, y1, lineLength, lineLength, lineWidth);
-    drawCorner(canvas, paint, x1, y2, lineLength, -lineLength, lineWidth);
-    drawCorner(canvas, paint, x2, y1, -lineLength, lineLength, lineWidth);
-    drawCorner(canvas, paint, x2, y2, -lineLength, -lineLength, lineWidth);
-  }
-
-  /**
-   * Makes sure that we only initialize one instance of each of our layout bounds drawing
-   * resources.
-   */
-  private void initDebugDrawResources() {
-    if (sDebugTextPaint == null) {
-      sDebugTextPaint = new Paint();
-      sDebugTextPaint.setTextAlign(Paint.Align.RIGHT);
-      sDebugTextPaint.setTextSize(dipsToPixels(9));
-      sDebugTextPaint.setTypeface(Typeface.MONOSPACE);
-      sDebugTextPaint.setAntiAlias(true);
-      sDebugTextPaint.setColor(Color.RED);
-    }
-    if (sDebugTextBackgroundPaint == null) {
-      sDebugTextBackgroundPaint = new Paint();
-      sDebugTextBackgroundPaint.setColor(Color.WHITE);
-      sDebugTextBackgroundPaint.setAlpha(200);
-      sDebugTextBackgroundPaint.setStyle(Paint.Style.FILL);
-    }
-    if (sDebugRectPaint == null) {
-      sDebugRectPaint = new Paint();
-      sDebugRectPaint.setAlpha(100);
-      sDebugRectPaint.setStyle(Paint.Style.STROKE);
-    }
-    if (sDebugCornerPaint == null) {
-      sDebugCornerPaint = new Paint();
-      sDebugCornerPaint.setAlpha(200);
-      sDebugCornerPaint.setColor(Color.rgb(63, 127, 255));
-      sDebugCornerPaint.setStyle(Paint.Style.FILL);
-    }
-    if (sDebugRect == null) {
-      sDebugRect = new Rect();
-    }
-  }
-
-  /**
-   * Used in drawing layout bounds, draws a layout bounds rectangle similar to the Android default
-   * implementation, with a specifiable border color.
-   *
-   * @param canvas The canvas to draw on.
-   * @param color The border color of the layout bounds.
-   * @param left Left bound of the rectangle.
-   * @param top Top bound of the rectangle.
-   * @param right Right bound of the rectangle.
-   * @param bottom Bottom bound of the rectangle.
-   */
-  private void debugDrawRect(
-      Canvas canvas,
-      int color,
-      float left,
-      float top,
-      float right,
-      float bottom) {
-    debugDrawNamedRect(canvas, color, "", left, top, right, bottom);
-  }
-
-  /**
-   * Used in drawing layout bounds, draws a layout bounds rectangle similar to the Android default
-   * implementation, with a specifiable border color.  Also draws a name text in the bottom right
-   * corner of the rectangle if DEBUG_DRAW_TEXT is set.
-   *
-   * @param canvas The canvas to draw on.
-   * @param color The border color of the layout bounds.
-   * @param name Name to be drawn on top of the rectangle if DEBUG_DRAW_TEXT is set.
-   * @param left Left bound of the rectangle.
-   * @param top Top bound of the rectangle.
-   * @param right Right bound of the rectangle.
-   * @param bottom Bottom bound of the rectangle.
-   */
-  /* package */ void debugDrawNamedRect(
-      Canvas canvas,
-      int color,
-      String name,
-      float left,
-      float top,
-      float right,
-      float bottom) {
-    if (DEBUG_DRAW_TEXT && !name.isEmpty()) {
-      sDebugTextPaint.getTextBounds(name, 0, name.length(), sDebugRect);
-      int inset = dipsToPixels(2);
-      float textRight = right - inset - 1;
-      float textBottom = bottom - inset - 1;
-      canvas.drawRect(
-          textRight - sDebugRect.right - inset,
-          textBottom + sDebugRect.top - inset,
-          textRight + inset,
-          textBottom + inset,
-          sDebugTextBackgroundPaint);
-      canvas.drawText(name, textRight, textBottom, sDebugTextPaint);
-    }
-    // Retain the alpha component.
-    sDebugRectPaint.setColor((sDebugRectPaint.getColor() & 0xFF000000) | (color & 0x00FFFFFF));
-    sDebugRectPaint.setAlpha(100);
-    canvas.drawRect(
-        left,
-        top,
-        right - 1,
-        bottom - 1,
-        sDebugRectPaint);
-    drawRectCorners(
-        canvas,
-        left,
-        top,
-        right,
-        bottom,
-        sDebugCornerPaint,
-        dipsToPixels(8),
-        dipsToPixels(1));
-  }
-
-  @Override
-  protected void onLayout(boolean changed, int l, int t, int r, int b) {
-    // nothing to do here
-  }
-
-  @Override
-  @SuppressLint("MissingSuperCall")
-  protected boolean verifyDrawable(Drawable who) {
-    return true;
-  }
-
-  @Override
-  protected void onAttachedToWindow() {
-    if (mIsAttached) {
-      // This is possible, unfortunately.
-      return;
-    }
-
-    mIsAttached = true;
-
-    super.onAttachedToWindow();
-    dispatchOnAttached(mAttachDetachListeners);
-
-    // This is a no op if we aren't clipping, so let updateClippingRect handle the check for us.
-    updateClippingRect();
-  }
-
-  @Override
-  protected void onDetachedFromWindow() {
-    if (!mIsAttached) {
-      throw new RuntimeException("Double detach");
-    }
-
-    mIsAttached = false;
-
-    super.onDetachedFromWindow();
-    dispatchOnDetached(mAttachDetachListeners);
-  }
-
-  @Override
-  protected void onSizeChanged(int w, int h, int oldw, int oldh) {
-    if (mHotspot != null) {
-      mHotspot.setBounds(0, 0, w, h);
-      invalidate();
-    }
-
-    // This is a no op if we aren't clipping, so let updateClippingRect handle the check for us.
-    updateClippingRect();
-  }
-
-  @Override
-  public void dispatchDrawableHotspotChanged(float x, float y) {
-    if (mHotspot != null) {
-      mHotspot.setHotspot(x, y);
-      invalidate();
-    }
-  }
-
-  @Override
-  protected void drawableStateChanged() {
-    super.drawableStateChanged();
-
-    if (mHotspot != null && mHotspot.isStateful()) {
-        mHotspot.setState(getDrawableState());
-    }
-  }
-
-  @Override
-  public void jumpDrawablesToCurrentState() {
-    super.jumpDrawablesToCurrentState();
-    if (mHotspot != null) {
-        mHotspot.jumpToCurrentState();
-    }
-  }
-
-  @Override
-  public void invalidate() {
-    // By default, invalidate() only invalidates the View's boundaries, which works great in most
-    // cases but may fail with overflow: visible (i.e. View clipping disabled) when View width or
-    // height is 0. This is because invalidate() has an optimization where it will not invalidate
-    // empty Views at all. A quick fix is to invalidate a slightly larger region to make sure we
-    // never hit that optimization.
-    //
-    // Another thing to note is that this may not work correctly with software rendering because
-    // in software, Android tracks dirty regions to redraw. We would need to collect information
-    // about all children boundaries (recursively) to track dirty region precisely.
-    invalidate(0, 0, getWidth() + 1, getHeight() + 1);
-  }
-
-  /**
-   * We override this to allow developers to determine whether they need offscreen alpha compositing
-   * or not. See the documentation of needsOffscreenAlphaCompositing in View.js.
-   */
-  @Override
-  public boolean hasOverlappingRendering() {
-    return mNeedsOffscreenAlphaCompositing;
-  }
-
-  @Override
-  public void setOnInterceptTouchEventListener(OnInterceptTouchEventListener listener) {
-    mOnInterceptTouchEventListener = listener;
-  }
-
-  @Override
-  public boolean onInterceptTouchEvent(MotionEvent ev) {
-    final long downTime = ev.getDownTime();
-    if (downTime != mLastTouchDownTime) {
-      mLastTouchDownTime = downTime;
-      if (interceptsTouchEvent(ev.getX(), ev.getY())) {
-        return true;
-      }
-    }
-
-    if (mOnInterceptTouchEventListener != null &&
-        mOnInterceptTouchEventListener.onInterceptTouchEvent(this, ev)) {
-      return true;
-    }
-    // We intercept the touch event if the children are not supposed to receive it.
-    if (mPointerEvents == PointerEvents.NONE || mPointerEvents == PointerEvents.BOX_ONLY) {
-      return true;
-    }
-    return super.onInterceptTouchEvent(ev);
-  }
-
-  @Override
-  public boolean onTouchEvent(MotionEvent ev) {
-    // We do not accept the touch event if this view is not supposed to receive it.
-    if (mPointerEvents == PointerEvents.NONE) {
-      return false;
-    }
-
-    if (mPointerEvents == PointerEvents.BOX_NONE) {
-      // We cannot always return false here because some child nodes could be flatten into this View
-      NodeRegion nodeRegion = virtualNodeRegionWithinBounds(ev.getX(), ev.getY());
-      if (nodeRegion == null) {
-        // no child to handle this touch event, bailing out.
-        return false;
-      }
-    }
-
-    // The root view always assumes any view that was tapped wants the touch
-    // and sends the event to JS as such.
-    // We don't need to do bubbling in native (it's already happening in JS).
-    // For an explanation of bubbling and capturing, see
-    // http://javascript.info/tutorial/bubbling-and-capturing#capturing
-    return true;
-  }
-
-  @Override
-  public PointerEvents getPointerEvents() {
-    return mPointerEvents;
-  }
-
-  /*package*/ void setPointerEvents(PointerEvents pointerEvents) {
-    mPointerEvents = pointerEvents;
-  }
-
-  /**
-   * See the documentation of needsOffscreenAlphaCompositing in View.js.
-   */
-  /* package */ void setNeedsOffscreenAlphaCompositing(boolean needsOffscreenAlphaCompositing) {
-    mNeedsOffscreenAlphaCompositing = needsOffscreenAlphaCompositing;
-  }
-
-  /* package */ void setHotspot(Drawable hotspot) {
-    if (mHotspot != null) {
-      mHotspot.setCallback(null);
-      unscheduleDrawable(mHotspot);
-    }
-
-    if (hotspot != null) {
-      hotspot.setCallback(this);
-      if (hotspot.isStateful()) {
-        hotspot.setState(getDrawableState());
-      }
-    }
-
-    mHotspot = hotspot;
-    invalidate();
-  }
-
-  /**
-   * Draws the next child of the FlatViewGroup.  Each draw view calls FlatViewGroup.drawNextChild,
-   * which keeps track of the current child index to draw.
-   *
-   * @param canvas The canvas to draw on.
-   */
-  /* package */ void drawNextChild(Canvas canvas) {
-    View child = getChildAt(mDrawChildIndex);
-    if (child instanceof FlatViewGroup) {
-      super.drawChild(canvas, child, getDrawingTime());
-    } else {
-      // Make sure non-React Views clip properly.
-      canvas.save(Canvas.CLIP_SAVE_FLAG);
-      child.getHitRect(VIEW_BOUNDS);
-      canvas.clipRect(VIEW_BOUNDS);
-      super.drawChild(canvas, child, getDrawingTime());
-      canvas.restore();
-    }
-
-    ++mDrawChildIndex;
-  }
-
-  /**
-   * Mount a list of draw commands to this FlatViewGroup.  Draw commands sometimes map to a view,
-   * as in the case of {@link DrawView}, and sometimes to a simple canvas operation.  We only
-   * receive a call to mount draw commands when our commands have changed, so we always invalidate.
-   *
-   * A call to mount draw commands will only be followed by a call to mount views if the draw view
-   * commands within the draw command array have changed since last mount.
-   *
-   * @param drawCommands The draw commands to mount.
-   */
-  /* package */ void mountDrawCommands(DrawCommand[] drawCommands) {
-    mDrawCommands = drawCommands;
-    invalidate();
-  }
-
-  /**
-   * Mount a list of draw commands to this FlatViewGroup, which is clipping subviews.  Clipping
-   * logic is handled by a {@link DrawCommandManager}, which provides a better explanation of
-   * these arguments and logic.
-   *
-   * A call to mount draw commands will only be followed by a call to mount views if the draw view
-   * commands within the draw command array have changed since last mount, which is indicated here
-   * by willMountViews.
-   *
-   * @param drawCommands The draw commands to mount.
-   * @param drawViewIndexMap See {@link DrawCommandManager}.
-   * @param maxBottom See {@link DrawCommandManager}.
-   * @param minTop See {@link DrawCommandManager}.
-   * @param willMountViews True if we will also receive a mountViews call.  If we are going to
-   *   receive a call to mount views, that will take care of updating the commands that are
-   *   currently onscreen, otherwise we need to update the onscreen commands.
-   */
-  /* package */ void mountClippingDrawCommands(
-      DrawCommand[] drawCommands,
-      SparseIntArray drawViewIndexMap,
-      float[] maxBottom,
-      float[] minTop,
-      boolean willMountViews) {
-    Assertions.assertNotNull(mDrawCommandManager).mountDrawCommands(
-        drawCommands,
-        drawViewIndexMap,
-        maxBottom,
-        minTop,
-        willMountViews);
-    invalidate();
-  }
-
-  /**
-   * Handle a subview being dropped
-   * In most cases, we are informed about a subview being dropped via mountViews, but in some
-   * cases (such as when both the child and parent get explicit removes in the same frame),
-   * we may not find out, so this is called when the child is dropped so the parent can clean up
-   * strong references to the child.
-   *
-   * @param view the view being dropped
-   */
-  void onViewDropped(View view) {
-    if (mDrawCommandManager != null) {
-      // for now, we only care about clearing clipped subview references
-      mDrawCommandManager.onClippedViewDropped(view);
-    }
-  }
-
-  /**
-   * Return the NodeRegion which matches a reactTag, or EMPTY if none match.
-   *
-   * @param reactTag The reactTag to look for
-   * @return The matching NodeRegion, or NodeRegion.EMPTY if none match.
-   */
-  /* package */ NodeRegion getNodeRegionForTag(int reactTag) {
-    for (NodeRegion region : mNodeRegions) {
-      if (region.matchesTag(reactTag)) {
-        return region;
-      }
-    }
-    return NodeRegion.EMPTY;
-  }
-
-  /**
-   * Return a list of FlatViewGroups that are detached (due to being clipped) but that we have a
-   * strong reference to. This is used by the FlatNativeViewHierarchyManager to explicitly clean up
-   * those views when removing this parent.
-   *
-   * @return A Collection of Views to clean up.
-   */
-  /* package */ SparseArray<View> getDetachedViews() {
-    if (mDrawCommandManager == null) {
-      return EMPTY_DETACHED_VIEWS;
-    }
-    return mDrawCommandManager.getDetachedViews();
-  }
-
-  /**
-   * Remove the detached view from the parent
-   * This is used in the DrawCommandManagers and during cleanup to trigger onDetachedFromWindow on
-   * any views that were in a temporary detached state due to them being clipped. This is called
-   * for cleanup of said views by FlatNativeViewHierarchyManager.
-   *
-   * @param view the detached View to remove
-   */
-  void removeDetachedView(View view) {
-    removeDetachedView(view, false);
-  }
-
-  @Override
-  public void removeAllViewsInLayout() {
-    // whenever we want to remove all views in a layout, we also want to remove all the
-    // DrawCommands, otherwise, we can have a mismatch between the DrawView DrawCommands
-    // and the Views to draw (note that because removeAllViewsInLayout doesn't call invalidate,
-    // we don't actually need to modify mDrawCommands, but we do it just in case).
-    mDrawCommands = DrawCommand.EMPTY_ARRAY;
-    super.removeAllViewsInLayout();
-  }
-
-  /**
-   * Mounts attach detach listeners to a FlatViewGroup.  The Nodes spec states that children and
-   * commands deal gracefully with multiple attaches and detaches, and as long as:
-   *
-   *   attachCount - detachCount > 0
-   *
-   * Then children still consider themselves as attached.
-   *
-   * @param listeners The listeners to mount.
-   */
-  /* package */ void mountAttachDetachListeners(AttachDetachListener[] listeners) {
-    if (mIsAttached) {
-      // Ordering of the following 2 statements is very important. While logically it makes sense to
-      // detach old listeners first, and only then attach new listeners, this is not very efficient,
-      // because a listener can be in both lists. In this case, it will be detached first and then
-      // re-attached immediately. This is undesirable for a couple of reasons:
-      // 1) performance. Detaching is slow because it may cancel an ongoing network request
-      // 2) it may cause flicker: an image that was already loaded may get unloaded.
-      //
-      // For this reason, we are attaching new listeners first. What this means is that listeners
-      // that are in both lists need to gracefully handle a secondary attach and detach events,
-      // (i.e. onAttach() being called when already attached, followed by a detach that should be
-      // ignored) turning them into no-ops. This will result in no performance loss and no flicker,
-      // because ongoing network requests don't get cancelled.
-      dispatchOnAttached(listeners);
-      dispatchOnDetached(mAttachDetachListeners);
-    }
-    mAttachDetachListeners = listeners;
-  }
-
-  /**
-   * Mount node regions to a FlatViewGroup.  A node region is a touch target for a react tag.  As
-   * not all react tags map to a view, we use node regions to determine whether a non-native region
-   * should receive a touch.
-   *
-   * @param nodeRegions The node regions to mount.
-   */
-  /* package */ void mountNodeRegions(NodeRegion[] nodeRegions) {
-    mNodeRegions = nodeRegions;
-  }
-
-  /**
-   * Mount node regions in clipping.  See {@link DrawCommandManager} for more complete
-   * documentation.
-   *
-   * @param nodeRegions The node regions to mount.
-   * @param maxBottom See {@link DrawCommandManager}.
-   * @param minTop See {@link DrawCommandManager}.
-   */
-  /* package */ void mountClippingNodeRegions(
-      NodeRegion[] nodeRegions,
-      float[] maxBottom,
-      float[] minTop) {
-    mNodeRegions = nodeRegions;
-    Assertions.assertNotNull(mDrawCommandManager).mountNodeRegions(nodeRegions, maxBottom, minTop);
-  }
-
-  /**
-   * Mount a list of views to add, and dismount a list of views to detach.  Ids will not appear in
-   * both lists, aka:
-   *   Set(viewsToAdd + viewsToDetach).size() == viewsToAdd.length + viewsToDetach.length
-   *
-   * Every time we get any change in the views in a FlatViewGroup, we detach all views first, then
-   * reattach / remove them as needed.  viewsToAdd is odd in that the ids also specify whether
-   * the view is new to us, or if we were already the parent.  If it is new to us, then the id has
-   * a positive value, otherwise we are already the parent, but it was previously detached, since
-   * we detach everything when anything changes.
-   *
-   * The reason we detach everything is that a single detach is on the order of O(n), as in the
-   * average case we have to move half of the views one position to the right, and a single add is
-   * the same.  Removing all views is also on the order of O(n), as you delete everything backward
-   * from the end, while adding a new set of views is also on the order of O(n), as you just add
-   * them all back in order.  ArrayLists are weird.
-   *
-   * @param viewResolver Resolves the views from their id.
-   * @param viewsToAdd id of views to add if they weren't just attached to us, or -id if they are
-   *     just being reattached.
-   * @param viewsToDetach id of views that we don't own anymore.  They either moved to a new parent,
-   *     or are being removed entirely.
-   */
-  /* package */ void mountViews(ViewResolver viewResolver, int[] viewsToAdd, int[] viewsToDetach) {
-    if (mDrawCommandManager != null) {
-      mDrawCommandManager.mountViews(viewResolver, viewsToAdd, viewsToDetach);
-    } else {
-      for (int viewToAdd : viewsToAdd) {
-        if (viewToAdd > 0) {
-          View view = viewResolver.getView(viewToAdd);
-          ensureViewHasNoParent(view);
-          addViewInLayout(view);
-        } else {
-          View view = viewResolver.getView(-viewToAdd);
-          ensureViewHasNoParent(view);
-          // We aren't clipping, so attach all the things, clipping is handled by the draw command
-          // manager, if we have one.
-          attachViewToParent(view);
-        }
-      }
-
-      for (int viewToDetach : viewsToDetach) {
-        View view = viewResolver.getView(viewToDetach);
-        if (view.getParent() != null) {
-          throw new RuntimeException("Trying to remove view not owned by FlatViewGroup");
-        } else {
-          removeDetachedView(view, false);
-        }
-      }
-    }
-
-    invalidate();
-  }
-
-  /**
-   * Exposes the protected addViewInLayout call for the {@link DrawCommandManager}.
-   *
-   * @param view The view to add.
-   */
-  /* package */ void addViewInLayout(View view) {
-    addViewInLayout(view, -1, ensureLayoutParams(view.getLayoutParams()), true);
-  }
-
-  /**
-   * Exposes the protected addViewInLayout call for the {@link DrawCommandManager}.
-   *
-   * @param view The view to add.
-   * @param index The index position at which to add this child.
-   */
-  /* package */ void addViewInLayout(View view, int index) {
-    addViewInLayout(view, index, ensureLayoutParams(view.getLayoutParams()), true);
-  }
-
-  /**
-   * Exposes the protected attachViewToParent call for the {@link DrawCommandManager}.
-   *
-   * @param view The view to attach.
-   */
-  /* package */ void attachViewToParent(View view) {
-    attachViewToParent(view, -1, ensureLayoutParams(view.getLayoutParams()));
-  }
-
-  /**
-   * Exposes the protected attachViewToParent call for the {@link DrawCommandManager}.
-   *
-   * @param view The view to attach.
-   * @param index The index position at which to attach this child.
-   */
-  /* package */ void attachViewToParent(View view, int index) {
-    attachViewToParent(view, index, ensureLayoutParams(view.getLayoutParams()));
-  }
-
-  private void processLayoutRequest() {
-    mIsLayoutRequested = false;
-    for (int i = 0, childCount = getChildCount(); i != childCount; ++i) {
-      View child = getChildAt(i);
-      if (!child.isLayoutRequested()) {
-        continue;
-      }
-
-      child.measure(
-        MeasureSpec.makeMeasureSpec(child.getWidth(), MeasureSpec.EXACTLY),
-        MeasureSpec.makeMeasureSpec(child.getHeight(), MeasureSpec.EXACTLY));
-      child.layout(child.getLeft(), child.getTop(), child.getRight(), child.getBottom());
-    }
-  }
-
-  /**
-   * Called after the view hierarchy is updated in {@link StateBuilder}, to process all the
-   * FlatViewGroups that have requested layout.
-   */
-  /* package */ static void processLayoutRequests() {
-    for (int i = 0, numLayoutRequests = LAYOUT_REQUESTS.size(); i != numLayoutRequests; ++i) {
-      FlatViewGroup flatViewGroup = LAYOUT_REQUESTS.get(i);
-      flatViewGroup.processLayoutRequest();
-    }
-    LAYOUT_REQUESTS.clear();
-  }
-
-  // Helper method for measure functionality provided by MeasuredViewGroup.
-  @Override
-  public Rect measureWithCommands() {
-    int childCount = getChildCount();
-    if (childCount == 0 && mDrawCommands.length == 0) {
-      return new Rect(0, 0, 0, 0);
-    }
-    int left = Integer.MAX_VALUE;
-    int top = Integer.MAX_VALUE;
-    int right = Integer.MIN_VALUE;
-    int bottom = Integer.MIN_VALUE;
-    for (int i = 0; i < childCount; i++) {
-      // This is technically a dupe, since the DrawView has its bounds, but leaving in to handle if
-      // the View is animating or rebelling against the DrawView bounds for some reason.
-      View child = getChildAt(i);
-      left = Math.min(left, child.getLeft());
-      top = Math.min(top, child.getTop());
-      right = Math.max(right, child.getRight());
-      bottom = Math.max(bottom, child.getBottom());
-    }
-
-    for (DrawCommand mDrawCommand : mDrawCommands) {
-      if (!(mDrawCommand instanceof AbstractDrawCommand)) {
-        continue;
-      }
-      AbstractDrawCommand drawCommand = (AbstractDrawCommand) mDrawCommand;
-      left = Math.min(left, Math.round(drawCommand.getLeft()));
-      top = Math.min(top, Math.round(drawCommand.getTop()));
-      right = Math.max(right, Math.round(drawCommand.getRight()));
-      bottom = Math.max(bottom, Math.round(drawCommand.getBottom()));
-    }
-    return new Rect(left, top, right, bottom);
-  }
-
-  /**
-   * Searches for a virtual node region matching the specified x and y touch.  Virtual in this case
-   * means simply that the node region represents a command, rather than a native view.
-   *
-   * @param touchX The touch x coordinate.
-   * @param touchY The touch y coordinate.
-   * @return A virtual node region matching the specified touch, or null if no regions match.
-   */
-  private @Nullable NodeRegion virtualNodeRegionWithinBounds(float touchX, float touchY) {
-    if (mDrawCommandManager != null) {
-      return mDrawCommandManager.virtualNodeRegionWithinBounds(touchX, touchY);
-    }
-    for (int i = mNodeRegions.length - 1; i >= 0; --i) {
-      NodeRegion nodeRegion = mNodeRegions[i];
-      if (!nodeRegion.mIsVirtual) {
-        // only interested in virtual nodes
-        continue;
-      }
-      if (nodeRegion.withinBounds(touchX, touchY)) {
-        return nodeRegion;
-      }
-    }
-
-    return null;
-  }
-
-  /**
-   * Searches for a node region matching the specified x and y touch.  Will search regions which
-   * representing both commands and native views.
-   *
-   * @param touchX The touch x coordinate.
-   * @param touchY The touch y coordinate.
-   * @return A node region matching the specified touch, or null if no regions match.
-   */
-  private @Nullable NodeRegion anyNodeRegionWithinBounds(float touchX, float touchY) {
-    if (mDrawCommandManager != null) {
-      return mDrawCommandManager.anyNodeRegionWithinBounds(touchX, touchY);
-    }
-    for (int i = mNodeRegions.length - 1; i >= 0; --i) {
-      NodeRegion nodeRegion = mNodeRegions[i];
-      if (nodeRegion.withinBounds(touchX, touchY)) {
-        return nodeRegion;
-      }
-    }
-
-    return null;
-  }
-
-  private static void ensureViewHasNoParent(View view) {
-    ViewParent oldParent = view.getParent();
-    if (oldParent != null) {
-      throw new RuntimeException(
-          "Cannot add view " + view + " to FlatViewGroup while it has a parent " + oldParent);
-    }
-  }
-
-  /**
-   * Propagate attach to a list of listeners, passing a callback by which they can invalidate.
-   *
-   * @param listeners List of listeners to attach.
-   */
-  private void dispatchOnAttached(AttachDetachListener[] listeners) {
-    int numListeners = listeners.length;
-    if (numListeners == 0) {
-      return;
-    }
-
-    InvalidateCallback callback = getInvalidateCallback();
-    for (AttachDetachListener listener : listeners) {
-      listener.onAttached(callback);
-    }
-  }
-
-  /**
-   * Get an invalidate callback singleton for this view instance.
-   *
-   * @return Invalidate callback singleton.
-   */
-  private InvalidateCallback getInvalidateCallback() {
-    if (mInvalidateCallback == null) {
-      mInvalidateCallback = new InvalidateCallback(this);
-    }
-    return mInvalidateCallback;
-  }
-
-  /**
-   * Propagate detach to a list of listeners.
-   *
-   * @param listeners List of listeners to detach.
-   */
-  private static void dispatchOnDetached(AttachDetachListener[] listeners) {
-    for (AttachDetachListener listener : listeners) {
-      listener.onDetached();
-    }
-  }
-
-  private ViewGroup.LayoutParams ensureLayoutParams(ViewGroup.LayoutParams lp) {
-    if (checkLayoutParams(lp)) {
-      return lp;
-    }
-    return generateDefaultLayoutParams();
-  }
-
-  @Override
-  public void updateClippingRect() {
-    if (mDrawCommandManager == null) {
-      // Don't update the clipping rect if we aren't clipping.
-      return;
-    }
-    if (mDrawCommandManager.updateClippingRect()) {
-      // Manager says something changed.
-      invalidate();
-    }
-  }
-
-  @Override
-  public void getClippingRect(Rect outClippingRect) {
-    if (mDrawCommandManager == null) {
-      // We could call outClippingRect.set(null) here, but throw in case the underlying React Native
-      // behaviour changes without us knowing.
-      throw new RuntimeException(
-          "Trying to get the clipping rect for a non-clipping FlatViewGroup");
-    }
-     mDrawCommandManager.getClippingRect(outClippingRect);
-  }
-
-  @Override
-  public void setRemoveClippedSubviews(boolean removeClippedSubviews) {
-    boolean currentlyClipping = getRemoveClippedSubviews();
-    if (removeClippedSubviews == currentlyClipping) {
-      // We aren't changing state, so don't do anything.
-      return;
-    }
-    if (currentlyClipping) {
-      // Trying to go from a clipping to a non-clipping state, not currently supported by Nodes.
-      // If this is an issue, let us know, but currently there does not seem to be a good case for
-      // supporting this.
-      throw new RuntimeException(
-          "Trying to transition FlatViewGroup from clipping to non-clipping state");
-    }
-    mDrawCommandManager = DrawCommandManager.getVerticalClippingInstance(this, mDrawCommands);
-    mDrawCommands = DrawCommand.EMPTY_ARRAY;
-    // We don't need an invalidate here because this can't cause new views to come onscreen, since
-    // everything was unclipped.
-  }
-
-  @Override
-  public boolean getRemoveClippedSubviews() {
-    return mDrawCommandManager != null;
-  }
-
-  @Override
-  public @Nullable Rect getHitSlopRect() {
-    return mHitSlopRect;
-  }
-
-  /* package */ void setHitSlopRect(@Nullable Rect rect) {
-    mHitSlopRect = rect;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewManager.java
deleted file mode 100644
index 8969b67243b8..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FlatViewManager.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.ViewGroupManager;
-
-abstract class FlatViewManager extends ViewGroupManager<FlatViewGroup> {
-
-  @Override
-  protected FlatViewGroup createViewInstance(ThemedReactContext reactContext) {
-    return new FlatViewGroup(reactContext);
-  }
-
-  @Override
-  public void setBackgroundColor(FlatViewGroup view, int backgroundColor) {
-    // suppress
-  }
-
-  @Override
-  public void removeAllViews(FlatViewGroup parent) {
-    parent.removeAllViewsInLayout();
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/FontStylingSpan.java b/ReactAndroid/src/main/java/com/facebook/react/flat/FontStylingSpan.java
deleted file mode 100644
index d7490984da72..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/FontStylingSpan.java
+++ /dev/null
@@ -1,207 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Color;
-import android.graphics.Typeface;
-import android.text.TextPaint;
-import android.text.style.MetricAffectingSpan;
-
-/* package */ final class FontStylingSpan extends MetricAffectingSpan {
-
-  /* package */ static final FontStylingSpan INSTANCE = new FontStylingSpan(
-      Color.BLACK /* mTextColor */,
-      0 /* mBackgroundColor */,
-      -1 /* mFontSize */,
-      -1 /* mFontStyle */,
-      -1 /* mFontWeight */,
-      false /* mHasUnderline */,
-      false /* mHasStrikeThrough */,
-      null /* mFontFamily */,
-      true /* mFrozen */);
-
-  // text property
-  private double mTextColor;
-  private int mBackgroundColor;
-  private boolean mHasUnderline;
-  private boolean mHasStrikeThrough;
-
-  // font properties
-  private int mFontSize;
-  private int mFontStyle;
-  private int mFontWeight;
-  private @Nullable String mFontFamily;
-
-  // whether or not mutation is allowed.
-  private boolean mFrozen;
-
-  FontStylingSpan() {
-  }
-
-  private FontStylingSpan(
-      double textColor,
-      int backgroundColor,
-      int fontSize,
-      int fontStyle,
-      int fontWeight,
-      boolean hasUnderline,
-      boolean hasStrikeThrough,
-      @Nullable String fontFamily,
-      boolean frozen) {
-    mTextColor = textColor;
-    mBackgroundColor = backgroundColor;
-    mFontSize = fontSize;
-    mFontStyle = fontStyle;
-    mFontWeight = fontWeight;
-    mHasUnderline = hasUnderline;
-    mHasStrikeThrough = hasStrikeThrough;
-    mFontFamily = fontFamily;
-    mFrozen = frozen;
-  }
-
-  /* package */ FontStylingSpan mutableCopy() {
-    return new FontStylingSpan(
-        mTextColor,
-        mBackgroundColor,
-        mFontSize,
-        mFontStyle,
-        mFontWeight,
-        mHasUnderline,
-        mHasStrikeThrough,
-        mFontFamily,
-        false);
-  }
-
-  /* package */ boolean isFrozen() {
-    return mFrozen;
-  }
-
-  /* package */ void freeze() {
-    mFrozen = true;
-  }
-
-  /* package */ double getTextColor() {
-    return mTextColor;
-  }
-
-  /* package */ void setTextColor(double textColor) {
-    mTextColor = textColor;
-  }
-
-  /* package */ int getBackgroundColor() {
-    return mBackgroundColor;
-  }
-
-  /* package */ void setBackgroundColor(int backgroundColor) {
-    mBackgroundColor = backgroundColor;
-  }
-
-  /* package */ int getFontSize() {
-    return mFontSize;
-  }
-
-  /* package */ void setFontSize(int fontSize) {
-    mFontSize = fontSize;
-  }
-
-  /* package */ int getFontStyle() {
-    return mFontStyle;
-  }
-
-  /* package */ void setFontStyle(int fontStyle) {
-    mFontStyle = fontStyle;
-  }
-
-  /* package */ int getFontWeight() {
-    return mFontWeight;
-  }
-
-  /* package */ void setFontWeight(int fontWeight) {
-    mFontWeight = fontWeight;
-  }
-
-  /* package */ @Nullable String getFontFamily() {
-    return mFontFamily;
-  }
-
-  /* package */ void setFontFamily(@Nullable String fontFamily) {
-    mFontFamily = fontFamily;
-  }
-
-  /* package */ boolean hasUnderline() {
-    return mHasUnderline;
-  }
-
-  /* package */ void setHasUnderline(boolean hasUnderline) {
-    mHasUnderline = hasUnderline;
-  }
-
-  /* package */ boolean hasStrikeThrough() {
-    return mHasStrikeThrough;
-  }
-
-  /* package */ void setHasStrikeThrough(boolean hasStrikeThrough) {
-    mHasStrikeThrough = hasStrikeThrough;
-  }
-
-  @Override
-  public void updateDrawState(TextPaint ds) {
-    if (!Double.isNaN(mTextColor)) {
-      ds.setColor((int) mTextColor);
-    }
-
-    ds.bgColor = mBackgroundColor;
-    ds.setUnderlineText(mHasUnderline);
-    ds.setStrikeThruText(mHasStrikeThrough);
-    updateMeasureState(ds);
-  }
-
-  @Override
-  public void updateMeasureState(TextPaint ds) {
-    if (mFontSize != -1) {
-      ds.setTextSize(mFontSize);
-    }
-
-    updateTypeface(ds);
-  }
-
-  private int getNewStyle(int oldStyle) {
-    int newStyle = oldStyle;
-    if (mFontStyle != -1) {
-      newStyle = (newStyle & ~Typeface.ITALIC) | mFontStyle;
-    }
-
-    if (mFontWeight != -1) {
-      newStyle = (newStyle & ~Typeface.BOLD) | mFontWeight;
-    }
-
-    return newStyle;
-  }
-
-  private void updateTypeface(TextPaint ds) {
-    Typeface typeface = ds.getTypeface();
-
-    int oldStyle = (typeface == null) ? 0 : typeface.getStyle();
-    int newStyle = getNewStyle(oldStyle);
-
-    if (oldStyle == newStyle && mFontFamily == null) {
-      // nothing to do
-      return;
-    }
-
-    if (mFontFamily != null) {
-      typeface = TypefaceCache.getTypeface(mFontFamily, newStyle);
-    } else {
-      typeface = TypefaceCache.getTypeface(typeface, newStyle);
-    }
-
-    ds.setTypeface(typeface);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/HitSlopNodeRegion.java b/ReactAndroid/src/main/java/com/facebook/react/flat/HitSlopNodeRegion.java
deleted file mode 100644
index 09bb2f90cb52..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/HitSlopNodeRegion.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Rect;
-
-/**
- * NodeRegion that has a hit slop.
- */
-/* package */ final class HitSlopNodeRegion extends NodeRegion {
-
-  private final Rect mHitSlop;
-
-  HitSlopNodeRegion(
-      Rect hitSlop,
-      float left,
-      float top,
-      float right,
-      float bottom,
-      int tag,
-      boolean isVirtual) {
-    super(left, top, right, bottom, tag, isVirtual);
-    mHitSlop = hitSlop;
-  }
-
-  @Override
-  /* package */ float getTouchableLeft() {
-    return getLeft() - mHitSlop.left;
-  }
-
-  @Override
-  /* package */ float getTouchableTop() {
-    return getTop() - mHitSlop.top;
-  }
-
-  @Override
-  /* package */ float getTouchableRight() {
-    return getRight() + mHitSlop.right;
-  }
-
-  @Override
-  /* package */ float getTouchableBottom() {
-    return getBottom() + mHitSlop.bottom;
-  }
-
-  @Override
-  /* package */ boolean withinBounds(float touchX, float touchY) {
-    return getTouchableLeft() <= touchX && touchX < getTouchableRight() &&
-        getTouchableTop() <= touchY && touchY < getTouchableBottom();
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/HorizontalDrawCommandManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/HorizontalDrawCommandManager.java
deleted file mode 100644
index 9621c9b3ebeb..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/HorizontalDrawCommandManager.java
+++ /dev/null
@@ -1,124 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import java.util.Arrays;
-
-import android.util.SparseIntArray;
-
-/**
- * {@link DrawCommandManager} with horizontal clipping (The view scrolls left and right).
- */
-/* package */ final class HorizontalDrawCommandManager extends ClippingDrawCommandManager {
-
-  /* package */ HorizontalDrawCommandManager(
-      FlatViewGroup flatViewGroup,
-      DrawCommand[] drawCommands) {
-    super(flatViewGroup, drawCommands);
-  }
-
-  @Override
-  int commandStartIndex() {
-    int start = Arrays.binarySearch(mCommandMaxBottom, mClippingRect.left);
-    // We don't care whether we matched or not, but positive indices are helpful. The binary search
-    // returns ~index in the case that it isn't a match, so reverse that here.
-    return start < 0 ? ~start : start;
-  }
-
-  @Override
-  int commandStopIndex(int start) {
-    int stop = Arrays.binarySearch(
-        mCommandMinTop,
-        start,
-        mCommandMinTop.length,
-        mClippingRect.right);
-    // We don't care whether we matched or not, but positive indices are helpful. The binary search
-    // returns ~index in the case that it isn't a match, so reverse that here.
-    return stop < 0 ? ~stop : stop;
-  }
-
-  @Override
-  int regionStopIndex(float touchX, float touchY) {
-    int stop = Arrays.binarySearch(mRegionMinTop, touchX + 0.0001f);
-    // We don't care whether we matched or not, but positive indices are helpful. The binary search
-    // returns ~index in the case that it isn't a match, so reverse that here.
-    return stop < 0 ? ~stop : stop;
-  }
-
-  @Override
-  boolean regionAboveTouch(int index, float touchX, float touchY) {
-    return mRegionMaxBottom[index] < touchX;
-  }
-
-  /**
-   * Populates the max and min arrays for a given set of node regions.
-   *
-   * This should never be called from the UI thread, as the reason it exists is to do work off the
-   * UI thread.
-   *
-   * @param regions The regions that will eventually be mounted.
-   * @param maxRight  At each index i, the maximum right value of all regions at or below i.
-   * @param minLeft  At each index i, the minimum left value of all regions at or below i.
-   */
-  public static void fillMaxMinArrays(NodeRegion[] regions, float[] maxRight, float[] minLeft) {
-    float last = 0;
-    for (int i = 0; i < regions.length; i++) {
-      last = Math.max(last, regions[i].getTouchableRight());
-      maxRight[i] = last;
-    }
-    for (int i = regions.length - 1; i >= 0; i--) {
-      last = Math.min(last, regions[i].getTouchableLeft());
-      minLeft[i] = last;
-    }
-  }
-
-  /**
-   * Populates the max and min arrays for a given set of draw commands.  Also populates a mapping of
-   * react tags to their index position in the command array.
-   *
-   * This should never be called from the UI thread, as the reason it exists is to do work off the
-   * UI thread.
-   *
-   * @param commands The draw commands that will eventually be mounted.
-   * @param maxRight At each index i, the maximum right value of all draw commands at or below i.
-   * @param minLeft At each index i, the minimum left value of all draw commands at or below i.
-   * @param drawViewIndexMap Mapping of ids to index position within the draw command array.
-   */
-  public static void fillMaxMinArrays(
-      DrawCommand[] commands,
-      float[] maxRight,
-      float[] minLeft,
-      SparseIntArray drawViewIndexMap) {
-    float last = 0;
-    // Loop through the DrawCommands, keeping track of the maximum we've seen if we only iterated
-    // through items up to this position.
-    for (int i = 0; i < commands.length; i++) {
-      if (commands[i] instanceof DrawView) {
-        DrawView drawView = (DrawView) commands[i];
-        // These will generally be roughly sorted by id, so try to insert at the end if possible.
-        drawViewIndexMap.append(drawView.reactTag, i);
-        last = Math.max(last, drawView.mLogicalRight);
-      } else {
-        last = Math.max(last, commands[i].getRight());
-      }
-      maxRight[i] = last;
-    }
-    // Intentionally leave last as it was, since it's at the maximum bottom position we've seen so
-    // far, we can use it again.
-
-    // Loop through backwards, keeping track of the minimum we've seen at this position.
-    for (int i = commands.length - 1; i >= 0; i--) {
-      if (commands[i] instanceof DrawView) {
-        last = Math.min(last, ((DrawView) commands[i]).mLogicalLeft);
-      } else {
-        last = Math.min(last, commands[i].getLeft());
-      }
-      minLeft[i] = last;
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/InlineImageSpanWithPipeline.java b/ReactAndroid/src/main/java/com/facebook/react/flat/InlineImageSpanWithPipeline.java
deleted file mode 100644
index 9f7aca9a7201..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/InlineImageSpanWithPipeline.java
+++ /dev/null
@@ -1,164 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.RectF;
-import android.text.style.ReplacementSpan;
-
-import com.facebook.imagepipeline.request.ImageRequest;
-import com.facebook.infer.annotation.Assertions;
-
-/* package */ final class InlineImageSpanWithPipeline extends ReplacementSpan
-    implements AttachDetachListener, BitmapUpdateListener {
-
-  private static final RectF TMP_RECT = new RectF();
-
-  private @Nullable PipelineRequestHelper mRequestHelper;
-  private @Nullable FlatViewGroup.InvalidateCallback mCallback;
-  private float mWidth;
-  private float mHeight;
-  private boolean mFrozen;
-
-  /* package */ InlineImageSpanWithPipeline() {
-    this(null, Float.NaN, Float.NaN);
-  }
-
-  private InlineImageSpanWithPipeline(
-      @Nullable PipelineRequestHelper requestHelper,
-      float width,
-      float height) {
-    mRequestHelper = requestHelper;
-    mWidth = width;
-    mHeight = height;
-  }
-
-  /* package */ InlineImageSpanWithPipeline mutableCopy() {
-    return new InlineImageSpanWithPipeline(mRequestHelper, mWidth, mHeight);
-  }
-
-  /* package */ boolean hasImageRequest() {
-    return mRequestHelper != null;
-  }
-
-  /**
-   * Assigns a new image request to the DrawImage, or null to clear the image request.
-   */
-  /* package */ void setImageRequest(@Nullable ImageRequest imageRequest) {
-    if (imageRequest == null) {
-      mRequestHelper = null;
-    } else {
-      mRequestHelper = new PipelineRequestHelper(imageRequest);
-    }
-  }
-
-  /* package */ float getWidth() {
-    return mWidth;
-  }
-
-  /* package */ void setWidth(float width) {
-    mWidth = width;
-  }
-
-  /* package */ float getHeight() {
-    return mHeight;
-  }
-
-  /* package */ void setHeight(float height) {
-    mHeight = height;
-  }
-
-  /* package */ void freeze() {
-    mFrozen = true;
-  }
-
-  /* package */ boolean isFrozen() {
-    return mFrozen;
-  }
-
-  @Override
-  public void onSecondaryAttach(Bitmap bitmap) {
-    // We don't know if width or height changed, so invalidate just in case.
-    Assertions.assumeNotNull(mCallback).invalidate();
-  }
-
-  @Override
-  public void onBitmapReady(Bitmap bitmap) {
-    // Bitmap is now ready, draw it.
-    Assertions.assumeNotNull(mCallback).invalidate();
-  }
-
-  @Override
-  public void onImageLoadEvent(int imageLoadEvent) {
-    // ignore
-  }
-
-  @Override
-  public void onAttached(FlatViewGroup.InvalidateCallback callback) {
-    mCallback = callback;
-
-    if (mRequestHelper != null) {
-      mRequestHelper.attach(this);
-    }
-  }
-
-  @Override
-  public void onDetached() {
-    if (mRequestHelper != null) {
-      mRequestHelper.detach();
-
-      if (mRequestHelper.isDetached()) {
-        // optional
-        mCallback = null;
-      }
-    }
-  }
-
-  @Override
-  public int getSize(Paint paint, CharSequence text, int start, int end, Paint.FontMetricsInt fm) {
-    if (fm != null) {
-      fm.ascent = -Math.round(mHeight);
-      fm.descent = 0;
-
-      fm.top = fm.ascent;
-      fm.bottom = 0;
-    }
-
-    return Math.round(mWidth);
-  }
-
-  @Override
-  public void draw(
-      Canvas canvas,
-      CharSequence text,
-      int start,
-      int end,
-      float x,
-      int top,
-      int y,
-      int bottom,
-      Paint paint) {
-    if (mRequestHelper == null) {
-      return;
-    }
-
-    Bitmap bitmap = mRequestHelper.getBitmap();
-    if (bitmap == null) {
-      return;
-    }
-
-    float bottomFloat = (float) bottom - paint.getFontMetricsInt().descent;
-    TMP_RECT.set(x, bottomFloat - mHeight, x + mWidth, bottomFloat);
-
-    canvas.drawBitmap(bitmap, null, TMP_RECT, paint);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/MoveProxy.java b/ReactAndroid/src/main/java/com/facebook/react/flat/MoveProxy.java
deleted file mode 100644
index 6f786b80f854..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/MoveProxy.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.uimanager.ReactShadowNode;
-import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import javax.annotation.Nullable;
-
-/**
- * Helper class that sorts moveFrom/moveTo arrays in lockstep.
- */
-/* package */ final class MoveProxy {
-
-  private @Nullable ReadableArray mMoveTo;
-  private int mSize;
-  private int[] mMapping = new int[8];
-  private ReactShadowNode[] mChildren = new ReactShadowNodeImpl[4];
-
-  /**
-   * Returns size of underlying moveTo/moveFrom arrays
-   */
-  public int size() {
-    return mSize;
-  }
-
-  /**
-   * Assigns ith child that we want to move if moveFrom was sorted.
-   */
-  public void setChildMoveFrom(int moveFromIndex, ReactShadowNode node) {
-    mChildren[moveFromToIndex(moveFromIndex)] = node;
-  }
-
-  /**
-   * Returns ith child that we want to move if moveTo was sorted.
-   */
-  public ReactShadowNode getChildMoveTo(int moveToIndex) {
-    return mChildren[moveToToIndex(moveToIndex)];
-  }
-
-  /**
-   * Returns index of the ith child that we want to move if moveFrom was sorted
-   */
-  public int getMoveFrom(int moveFromIndex) {
-    return moveFromToValue(moveFromIndex);
-  }
-
-  /**
-   * Returns index of the ith child that we want to move to if moveTo was sorted
-   */
-  public int getMoveTo(int moveToIndex) {
-    return moveToToValue(moveToIndex);
-  }
-
-  /**
-   * Initialize MoveProxy with given moveFrom and moveTo arrays.
-   */
-  public void setup(ReadableArray moveFrom, ReadableArray moveTo) {
-    mMoveTo = moveTo;
-
-    if (moveFrom == null) {
-      setSize(0);
-      return;
-    }
-
-    int size = moveFrom.size();
-    int requiredSpace = size + size;
-    if (mMapping.length < requiredSpace) {
-      mMapping = new int[requiredSpace];
-      mChildren = new FlatShadowNode[size];
-    }
-
-    setSize(size);
-
-    // Array contains data in the following way:
-    // [ k0, v0, k1, v1, k2, v2, ... ]
-    //
-    // where vi = moveFrom.getInt(ki)
-
-    // We don't technically *need* to store vi, but they are accessed so often that it makes sense
-    // to cache it instead of calling ReadableArray.getInt() all the time.
-
-    // Sorting algorithm will reorder ki/vi pairs in such a way that vi < v(i+1)
-
-    // Code below is an insertion sort, adapted from DualPivotQuicksort.doSort()
-
-    // At each step i, we got the following data:
-
-    // [k0, v0, k1, v2, .. k(i-1), v(i-1), unused...]
-    // where v0 < v1 < v2 ... < v(i-1)
-    //
-    // This holds true for step i = 0 (array of size one is sorted)
-    // Again, k0 = 0, v0 = moveFrom.getInt(k0)
-    setKeyValue(0, 0, moveFrom.getInt(0));
-
-    // At each of the next steps, we grab a new key and walk back until we find first key that is
-    // less than current, shifting key/value pairs if they are larger than current key.
-    for (int i = 1; i < size; i++) {
-      // this is our next key
-      int current = moveFrom.getInt(i);
-
-      // this loop will find correct position for it
-      int j;
-
-      // At this point, array is like this: [ k0, v0, k1, v1, k2, v2, ..., k(i-1), v(i-1), ... ]
-      for (j = i - 1; j >= 0; j--) {
-        if (moveFromToValue(j) < current) {
-          break;
-        }
-
-        // value at index j is < current value, shift that value and its key
-        setKeyValue(j + 1, moveFromToIndex(j), moveFromToValue(j));
-      }
-
-      setKeyValue(j + 1, i, current);
-    }
-  }
-
-  /**
-   * Returns index of ith key in array.
-   */
-  private static int k(int i) {
-    return i * 2;
-  }
-
-  /**
-   * Returns index of ith value in array.
-   */
-  private static int v(int i) {
-    return i * 2 + 1;
-  }
-
-  private void setKeyValue(int index, int key, int value) {
-    mMapping[k(index)] = key;
-    mMapping[v(index)] = value;
-  }
-
-  private int moveFromToIndex(int index) {
-    return mMapping[k(index)];
-  }
-
-  private int moveFromToValue(int index) {
-    return mMapping[v(index)];
-  }
-
-  private static int moveToToIndex(int index) {
-    return index;
-  }
-
-  private int moveToToValue(int index) {
-    return Assertions.assumeNotNull(mMoveTo).getInt(index);
-  }
-
-  private void setSize(int newSize) {
-    // reset references to null when shrinking to avoid memory leaks
-    for (int i = newSize; i < mSize; ++i) {
-      mChildren[i] = null;
-    }
-
-    mSize = newSize;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/NativeViewWrapper.java b/ReactAndroid/src/main/java/com/facebook/react/flat/NativeViewWrapper.java
deleted file mode 100644
index a930f7504daa..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/NativeViewWrapper.java
+++ /dev/null
@@ -1,130 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.react.uimanager.ReactShadowNode;
-import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import com.facebook.react.uimanager.ReactStylesDiffMap;
-import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIViewOperationQueue;
-import com.facebook.react.uimanager.ViewGroupManager;
-import com.facebook.react.uimanager.ViewManager;
-import com.facebook.yoga.YogaMeasureFunction;
-import com.facebook.yoga.YogaUnit;
-import com.facebook.yoga.YogaValue;
-import javax.annotation.Nullable;
-
-/* package */ final class NativeViewWrapper extends FlatShadowNode implements AndroidView {
-
-  @Nullable
-  private final ReactShadowNode mReactShadowNode;
-  private final boolean mNeedsCustomLayoutForChildren;
-  private boolean mPaddingChanged = false;
-  private boolean mForceMountGrandChildrenToView;
-
-  /* package */ NativeViewWrapper(ViewManager viewManager) {
-    ReactShadowNode reactShadowNode = viewManager.createShadowNodeInstance();
-    if (reactShadowNode instanceof YogaMeasureFunction) {
-      mReactShadowNode = reactShadowNode;
-      setMeasureFunction((YogaMeasureFunction) reactShadowNode);
-    } else {
-      mReactShadowNode = null;
-    }
-
-    if (viewManager instanceof ViewGroupManager) {
-      ViewGroupManager viewGroupManager = (ViewGroupManager) viewManager;
-      mNeedsCustomLayoutForChildren = viewGroupManager.needsCustomLayoutForChildren();
-      mForceMountGrandChildrenToView = viewGroupManager.shouldPromoteGrandchildren();
-    } else {
-      mNeedsCustomLayoutForChildren = false;
-    }
-
-    forceMountToView();
-    forceMountChildrenToView();
-  }
-
-  @Override
-  public boolean needsCustomLayoutForChildren() {
-    return mNeedsCustomLayoutForChildren;
-  }
-
-  @Override
-  public boolean isPaddingChanged() {
-    return mPaddingChanged;
-  }
-
-  @Override
-  public void resetPaddingChanged() {
-    mPaddingChanged = false;
-  }
-
-  @Override
-  public void setBackgroundColor(int backgroundColor) {
-    // suppress, this is handled by a ViewManager
-  }
-
-  @Override
-  public void setReactTag(int reactTag) {
-    super.setReactTag(reactTag);
-    if (mReactShadowNode != null) {
-      mReactShadowNode.setReactTag(reactTag);
-    }
-  }
-
-  @Override
-  public void setThemedContext(ThemedReactContext themedContext) {
-    super.setThemedContext(themedContext);
-
-    if (mReactShadowNode != null) {
-      mReactShadowNode.setThemedContext(themedContext);
-    }
-  }
-
-  @Override
-  /* package*/ void handleUpdateProperties(ReactStylesDiffMap styles) {
-    if (mReactShadowNode != null) {
-      mReactShadowNode.updateProperties(styles);
-    }
-  }
-
-  @Override
-  public void addChildAt(ReactShadowNodeImpl child, int i) {
-    super.addChildAt(child, i);
-    if (mForceMountGrandChildrenToView && child instanceof FlatShadowNode) {
-      ((FlatShadowNode) child).forceMountChildrenToView();
-    }
-  }
-
-  @Override
-  public void setPadding(int spacingType, float padding) {
-    YogaValue current = getStylePadding(spacingType);
-    if (current.unit != YogaUnit.POINT || current.value != padding) {
-      super.setPadding(spacingType, padding);
-      mPaddingChanged = true;
-      markUpdated();
-    }
-  }
-
-  @Override
-  public void setPaddingPercent(int spacingType, float percent) {
-    YogaValue current = getStylePadding(spacingType);
-    if (current.unit != YogaUnit.PERCENT || current.value != percent) {
-      super.setPadding(spacingType, percent);
-      mPaddingChanged = true;
-      markUpdated();
-    }
-  }
-
-  @Override
-  public void onCollectExtraUpdates(UIViewOperationQueue uiViewOperationQueue) {
-    if (mReactShadowNode != null && mReactShadowNode.hasUnseenUpdates()) {
-      mReactShadowNode.onCollectExtraUpdates(uiViewOperationQueue);
-      markUpdateSeen();
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/NodeRegion.java b/ReactAndroid/src/main/java/com/facebook/react/flat/NodeRegion.java
deleted file mode 100644
index 41169f7f2de4..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/NodeRegion.java
+++ /dev/null
@@ -1,133 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-/* package */ class NodeRegion {
-  /* package */ static final NodeRegion[] EMPTY_ARRAY = new NodeRegion[0];
-  /* package */ static final NodeRegion EMPTY = new NodeRegion(0, 0, 0, 0, -1, false);
-
-  private final float mLeft;
-  private final float mTop;
-  private final float mRight;
-  private final float mBottom;
-  /* package */ final int mTag;
-  /* package */ final boolean mIsVirtual;
-
-  /* package */ NodeRegion(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      int tag,
-      boolean isVirtual) {
-    mLeft = left;
-    mTop = top;
-    mRight = right;
-    mBottom = bottom;
-    mTag = tag;
-    mIsVirtual = isVirtual;
-  }
-
-  /* package */ final boolean matches(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      boolean isVirtual) {
-    return left == mLeft && top == mTop && right == mRight && bottom == mBottom &&
-        isVirtual == mIsVirtual;
-  }
-
-  /**
-   * The left bound of the underlying node.
-   *
-   * @return The node bound.
-   */
-  /* package */ final float getLeft() {
-    return mLeft;
-  }
-
-  /**
-   * The top bound of the underlying node.
-   *
-   * @return The node bound.
-   */
-  /* package */ final float getTop() {
-    return mTop;
-  }
-
-  /**
-   * The right bound of the underlying node.
-   *
-   * @return The node bound.
-   */
-  /* package */ final float getRight() {
-    return mRight;
-  }
-
-  /**
-   * The bottom bound of the underlying node.
-   *
-   * @return The node bound.
-   */
-  /* package */ final float getBottom() {
-    return mBottom;
-  }
-
-  /**
-   * The left bound of the region for the purpose of touch.  This is usually the bound of the
-   * underlying node, except in the case of hit slop.
-   *
-   * @return The touch bound.
-   */
-  /* package */ float getTouchableLeft() {
-    return getLeft();
-  }
-
-  /**
-   * The top bound of the region for the purpose of touch.  This is usually the bound of the
-   * underlying node, except in the case of hit slop.
-   *
-   * @return The touch bound.
-   */
-  /* package */ float getTouchableTop() {
-    return getTop();
-  }
-
-  /**
-   * The right bound of the region for the purpose of touch.  This is usually the bound of the
-   * underlying node, except in the case of hit slop.
-   *
-   * @return The touch bound.
-   */
-  /* package */ float getTouchableRight() {
-    return getRight();
-  }
-
-  /**
-   * The bottom bound of the region for the purpose of touch.  This is usually the bound of the
-   * underlying node, except in the case of hit slop.
-   *
-   * @return The touch bound.
-   */
-  /* package */ float getTouchableBottom() {
-    return getBottom();
-  }
-
-  /* package */ boolean withinBounds(float touchX, float touchY) {
-    return mLeft <= touchX && touchX < mRight && mTop <= touchY && touchY < mBottom;
-  }
-
-  /* package */ int getReactTag(float touchX, float touchY) {
-    return mTag;
-  }
-
-  /* package */ boolean matchesTag(int tag) {
-    return mTag == tag;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/PipelineRequestHelper.java b/ReactAndroid/src/main/java/com/facebook/react/flat/PipelineRequestHelper.java
deleted file mode 100644
index 77b4fb0dcd9d..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/PipelineRequestHelper.java
+++ /dev/null
@@ -1,186 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Bitmap;
-
-import com.facebook.common.executors.UiThreadImmediateExecutorService;
-import com.facebook.common.references.CloseableReference;
-import com.facebook.datasource.DataSource;
-import com.facebook.datasource.DataSubscriber;
-import com.facebook.imagepipeline.core.ImagePipeline;
-import com.facebook.imagepipeline.core.ImagePipelineFactory;
-import com.facebook.imagepipeline.image.CloseableBitmap;
-import com.facebook.imagepipeline.image.CloseableImage;
-import com.facebook.imagepipeline.request.ImageRequest;
-import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.views.image.ImageLoadEvent;
-
-/**
- * Helper class for DrawImage that helps manage fetch requests through ImagePipeline.
- *
- * Request states this class can be in:
- * 1) mDataSource == null, mImageRef == null : request has not be started, was canceled or failed.
- * 2) mDataSource != null, mImageRef == null : request is in progress.
- * 3) mDataSource == null, mImageRef != null : request successfully finished.
- * 4) mDataSource != null, mImageRef != null : invalid state (should never happen)
- */
-/* package */ final class PipelineRequestHelper
-    implements DataSubscriber<CloseableReference<CloseableImage>> {
-
-  private final ImageRequest mImageRequest;
-  private @Nullable BitmapUpdateListener mBitmapUpdateListener;
-  private @Nullable DataSource<CloseableReference<CloseableImage>> mDataSource;
-  private @Nullable CloseableReference<CloseableImage> mImageRef;
-  private int mAttachCounter;
-
-  /* package */ PipelineRequestHelper(ImageRequest imageRequest) {
-    mImageRequest = imageRequest;
-  }
-
-  /* package */ void attach(BitmapUpdateListener listener) {
-    mBitmapUpdateListener = listener;
-
-    mAttachCounter++;
-    if (mAttachCounter != 1) {
-      // this is a secondary attach, ignore it, only updating Bitmap boundaries if needed.
-      Bitmap bitmap = getBitmap();
-      if (bitmap != null) {
-        listener.onSecondaryAttach(bitmap);
-      }
-      return;
-    }
-
-    listener.onImageLoadEvent(ImageLoadEvent.ON_LOAD_START);
-
-    Assertions.assertCondition(mDataSource == null);
-    Assertions.assertCondition(mImageRef == null);
-
-    // Submit the request
-    ImagePipeline imagePipeline = ImagePipelineFactory.getInstance().getImagePipeline();
-    mDataSource = imagePipeline.fetchDecodedImage(mImageRequest, RCTImageView.getCallerContext());
-    mDataSource.subscribe(this, UiThreadImmediateExecutorService.getInstance());
-  }
-
-  /**
-   * Returns whether detach() was primary, false otherwise.
-   */
-  /* package */ void detach() {
-    --mAttachCounter;
-    if (mAttachCounter != 0) {
-      // this is a secondary detach, ignore it
-      return;
-    }
-
-    if (mDataSource != null) {
-      mDataSource.close();
-      mDataSource = null;
-    }
-
-    if (mImageRef != null) {
-      mImageRef.close();
-      mImageRef = null;
-    }
-
-    mBitmapUpdateListener = null;
-  }
-
-  /**
-   * Returns an unsafe bitmap reference. Do not assign the result of this method to anything other
-   * than a local variable, or it will no longer work with the reference count goes to zero.
-   */
-  /* package */ @Nullable Bitmap getBitmap() {
-    if (mImageRef == null) {
-      return null;
-    }
-
-    CloseableImage closeableImage = mImageRef.get();
-    if (!(closeableImage instanceof CloseableBitmap)) {
-      mImageRef.close();
-      mImageRef = null;
-      return null;
-    }
-
-    return ((CloseableBitmap) closeableImage).getUnderlyingBitmap();
-  }
-
-  /* package */ boolean isDetached() {
-    return mAttachCounter == 0;
-  }
-
-  @Override
-  public void onNewResult(DataSource<CloseableReference<CloseableImage>> dataSource) {
-    if (!dataSource.isFinished()) {
-      // only interested in final image, no need to close the dataSource
-      return;
-    }
-
-    try {
-      if (mDataSource != dataSource) {
-        // Shouldn't ever happen, but let's be safe (dataSource got closed by callback still fired?)
-        return;
-      }
-
-      mDataSource = null;
-
-      CloseableReference<CloseableImage> imageReference = dataSource.getResult();
-      if (imageReference == null) {
-        // Shouldn't ever happen, but let's be safe (dataSource got closed by callback still fired?)
-        return;
-      }
-
-      CloseableImage image = imageReference.get();
-      if (!(image instanceof CloseableBitmap)) {
-        // only bitmaps are supported
-        imageReference.close();
-        return;
-      }
-
-      mImageRef = imageReference;
-
-      Bitmap bitmap = getBitmap();
-      if (bitmap == null) {
-        // Shouldn't ever happen, but let's be safe.
-        return;
-      }
-
-      BitmapUpdateListener listener = Assertions.assumeNotNull(mBitmapUpdateListener);
-      listener.onBitmapReady(bitmap);
-      listener.onImageLoadEvent(ImageLoadEvent.ON_LOAD);
-      listener.onImageLoadEvent(ImageLoadEvent.ON_LOAD_END);
-    } finally {
-      dataSource.close();
-    }
-  }
-
-  @Override
-  public void onFailure(DataSource<CloseableReference<CloseableImage>> dataSource) {
-    if (mDataSource == dataSource) {
-      Assertions.assumeNotNull(mBitmapUpdateListener).onImageLoadEvent(ImageLoadEvent.ON_ERROR);
-      Assertions.assumeNotNull(mBitmapUpdateListener).onImageLoadEvent(ImageLoadEvent.ON_LOAD_END);
-      mDataSource = null;
-    }
-
-    dataSource.close();
-  }
-
-  @Override
-  public void onCancellation(DataSource<CloseableReference<CloseableImage>> dataSource) {
-    if (mDataSource == dataSource) {
-      mDataSource = null;
-    }
-
-    dataSource.close();
-  }
-
-  @Override
-  public void onProgressUpdate(DataSource<CloseableReference<CloseableImage>> dataSource) {
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTImageView.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTImageView.java
deleted file mode 100644
index 7b74a130b496..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTImageView.java
+++ /dev/null
@@ -1,151 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import com.facebook.drawee.drawable.ScalingUtils.ScaleType;
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.Spacing;
-import com.facebook.react.uimanager.ViewProps;
-import com.facebook.react.uimanager.annotations.ReactProp;
-import com.facebook.react.views.image.ImageResizeMode;
-
-/**
- * RCTImageView is a top-level node for Image. It can display either a remote image
- * (source must start with http:// or https://) or a local resource (a BitmapDrawable).
- */
-/* package */ class RCTImageView<T extends AbstractDrawCommand & DrawImage> extends FlatShadowNode {
-
-  static Object sCallerContext = RCTImageView.class;
-
-  /**
-   * Assigns a CallerContext to execute network requests with.
-   */
-  /* package */ static void setCallerContext(Object callerContext) {
-    sCallerContext = callerContext;
-  }
-
-  /* package */ static Object getCallerContext() {
-    return sCallerContext;
-  }
-
-  private T mDrawImage;
-
-  /* package */ RCTImageView(T drawImage) {
-    mDrawImage = drawImage;
-  }
-
-  @Override
-  protected void collectState(
-      StateBuilder stateBuilder,
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    super.collectState(
-        stateBuilder,
-        left,
-        top,
-        right,
-        bottom,
-        clipLeft,
-        clipTop,
-        clipRight,
-        clipBottom);
-
-    if (mDrawImage.hasImageRequest()) {
-      mDrawImage = (T) mDrawImage.updateBoundsAndFreeze(
-          left,
-          top,
-          right,
-          bottom,
-          clipLeft,
-          clipTop,
-          clipRight,
-          clipBottom);
-      stateBuilder.addDrawCommand(mDrawImage);
-      stateBuilder.addAttachDetachListener(mDrawImage);
-    }
-  }
-
-  @Override
-  boolean doesDraw() {
-    return mDrawImage.hasImageRequest() || super.doesDraw();
-  }
-
-  @ReactProp(name = "shouldNotifyLoadEvents")
-  public void setShouldNotifyLoadEvents(boolean shouldNotifyLoadEvents) {
-    getMutableDrawImage().setReactTag(shouldNotifyLoadEvents ? getReactTag() : 0);
-  }
-
-  @ReactProp(name = "src")
-  public void setSource(@Nullable ReadableArray sources) {
-    getMutableDrawImage().setSource(getThemedContext(), sources);
-  }
-
-  @ReactProp(name = "tintColor")
-  public void setTintColor(int tintColor) {
-    getMutableDrawImage().setTintColor(tintColor);
-  }
-
-  @ReactProp(name = ViewProps.RESIZE_MODE)
-  public void setResizeMode(@Nullable String resizeMode) {
-    ScaleType scaleType = ImageResizeMode.toScaleType(resizeMode);
-    if (mDrawImage.getScaleType() != scaleType) {
-      getMutableDrawImage().setScaleType(scaleType);
-    }
-  }
-
-  @ReactProp(name = "borderColor", customType = "Color")
-  public void setBorderColor(int borderColor) {
-    if (mDrawImage.getBorderColor() != borderColor) {
-      getMutableDrawImage().setBorderColor(borderColor);
-    }
-  }
-
-  @Override
-  public void setBorder(int spacingType, float borderWidth) {
-    super.setBorder(spacingType, borderWidth);
-
-    if (spacingType == Spacing.ALL && mDrawImage.getBorderWidth() != borderWidth) {
-      getMutableDrawImage().setBorderWidth(borderWidth);
-    }
-  }
-
-  @ReactProp(name = "borderRadius")
-  public void setBorderRadius(float borderRadius) {
-    if (mDrawImage.getBorderRadius() != borderRadius) {
-      getMutableDrawImage().setBorderRadius(PixelUtil.toPixelFromDIP(borderRadius));
-    }
-  }
-
-  @ReactProp(name = "fadeDuration")
-  public void setFadeDuration(int durationMs) {
-    getMutableDrawImage().setFadeDuration(durationMs);
-  }
-
-  @ReactProp(name = "progressiveRenderingEnabled")
-  public void setProgressiveRenderingEnabled(boolean enabled) {
-    getMutableDrawImage().setProgressiveRenderingEnabled(enabled);
-  }
-
-  private T getMutableDrawImage() {
-    if (mDrawImage.isFrozen()) {
-      mDrawImage = (T) mDrawImage.mutableCopy();
-      invalidate();
-    }
-
-    return mDrawImage;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTImageViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTImageViewManager.java
deleted file mode 100644
index 6d7dcd494e8b..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTImageViewManager.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.drawee.backends.pipeline.Fresco;
-import com.facebook.drawee.controller.AbstractDraweeControllerBuilder;
-import com.facebook.react.views.image.GlobalImageLoadListener;
-import javax.annotation.Nullable;
-
-public final class RCTImageViewManager extends FlatViewManager {
-
-  /* package */ static final String REACT_CLASS = "RCTImageView";
-
-  private @Nullable AbstractDraweeControllerBuilder mDraweeControllerBuilder;
-  private @Nullable GlobalImageLoadListener mGlobalImageLoadListener;
-  private final @Nullable Object mCallerContext;
-
-  public RCTImageViewManager() {
-    this(null, null);
-  }
-
-  public RCTImageViewManager(
-    AbstractDraweeControllerBuilder draweeControllerBuilder,
-    Object callerContext) {
-    this(draweeControllerBuilder, null, callerContext);
-  }
-
-  public RCTImageViewManager(
-      AbstractDraweeControllerBuilder draweeControllerBuilder,
-      @Nullable GlobalImageLoadListener globalImageLoadListener,
-      Object callerContext) {
-    mDraweeControllerBuilder = draweeControllerBuilder;
-    mGlobalImageLoadListener = globalImageLoadListener;
-    mCallerContext = callerContext;
-  }
-
-  @Override
-  public String getName() {
-    return REACT_CLASS;
-  }
-
-  @Override
-  public RCTImageView createShadowNodeInstance() {
-    return new RCTImageView(new DrawImageWithDrawee(mGlobalImageLoadListener));
-  }
-
-  @Override
-  public Class<RCTImageView> getShadowNodeClass() {
-    return RCTImageView.class;
-  }
-
-  public AbstractDraweeControllerBuilder getDraweeControllerBuilder() {
-    if (mDraweeControllerBuilder == null) {
-      mDraweeControllerBuilder = Fresco.newDraweeControllerBuilder();
-    }
-    return mDraweeControllerBuilder;
-  }
-
-  public Object getCallerContext() {
-    return mCallerContext;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTModalHostManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTModalHostManager.java
deleted file mode 100644
index 1b49f57534db..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTModalHostManager.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.react.uimanager.LayoutShadowNode;
-import com.facebook.react.views.modal.ReactModalHostManager;
-
-public class RCTModalHostManager extends ReactModalHostManager {
-
-  /* package */ static final String REACT_CLASS = ReactModalHostManager.REACT_CLASS;
-
-  @Override
-  public LayoutShadowNode createShadowNodeInstance() {
-    return new FlatReactModalShadowNode();
-  }
-
-  @Override
-  public Class<? extends LayoutShadowNode> getShadowNodeClass() {
-    return FlatReactModalShadowNode.class;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTRawText.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTRawText.java
deleted file mode 100644
index f0a8d1d33861..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTRawText.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.text.Spannable;
-import android.text.SpannableStringBuilder;
-
-import com.facebook.react.uimanager.annotations.ReactProp;
-
-/**
- * RCTRawText is a FlatTextShadowNode that can only contain raw text (but not styling).
- */
-/* package */ final class RCTRawText extends FlatTextShadowNode {
-
-  private @Nullable String mText;
-
-  @Override
-  protected void performCollectText(SpannableStringBuilder builder) {
-    if (mText != null) {
-      builder.append(mText);
-    }
-  }
-
-  @Override
-  protected void performApplySpans(
-      SpannableStringBuilder builder,
-      int begin,
-      int end,
-      boolean isEditable) {
-    builder.setSpan(
-        this,
-        begin,
-        end,
-        Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
-  }
-
-  @Override
-  protected void performCollectAttachDetachListeners(StateBuilder stateBuilder) {
-    // nothing to do
-  }
-
-  @ReactProp(name = "text")
-  public void setText(@Nullable String text) {
-    mText = text;
-    notifyChanged(true);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTRawTextManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTRawTextManager.java
deleted file mode 100644
index c1695c507489..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTRawTextManager.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-/**
- * ViewManager that creates instances of RCTRawText.
- */
-public final class RCTRawTextManager extends VirtualViewManager<RCTRawText> {
-
-  /* package */ static final String REACT_CLASS = "RCTRawText";
-
-  @Override
-  public String getName() {
-    return REACT_CLASS;
-  }
-
-  @Override
-  public RCTRawText createShadowNodeInstance() {
-    return new RCTRawText();
-  }
-
-  @Override
-  public Class<RCTRawText> getShadowNodeClass() {
-    return RCTRawText.class;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTText.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTText.java
deleted file mode 100644
index 683aabf6d6f7..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTText.java
+++ /dev/null
@@ -1,360 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.support.v4.text.TextDirectionHeuristicsCompat;
-import android.text.Layout;
-import android.text.TextUtils;
-import android.view.Gravity;
-
-import com.facebook.yoga.YogaDirection;
-import com.facebook.yoga.YogaMeasureMode;
-import com.facebook.yoga.YogaMeasureFunction;
-import com.facebook.yoga.YogaNode;
-import com.facebook.yoga.YogaMeasureOutput;
-import com.facebook.fbui.textlayoutbuilder.TextLayoutBuilder;
-import com.facebook.fbui.textlayoutbuilder.glyphwarmer.GlyphWarmerImpl;
-import com.facebook.react.bridge.JSApplicationIllegalArgumentException;
-import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.Spacing;
-import com.facebook.react.uimanager.ViewDefaults;
-import com.facebook.react.uimanager.ViewProps;
-import com.facebook.react.uimanager.annotations.ReactProp;
-
-/**
- * RCTText is a top-level node for text. It extends {@link RCTVirtualText} because it can contain
- * styling information, but has the following differences:
- *
- * a) RCTText is not a virtual node, and can be measured and laid out.
- * b) when no font size is specified, a font size of ViewDefaults#FONT_SIZE_SP is assumed.
- */
-/* package */ final class RCTText extends RCTVirtualText implements YogaMeasureFunction {
-
-  // index of left and right in the Layout.Alignment enum since the base values are @hide
-  private static final int ALIGNMENT_LEFT = 3;
-  private static final int ALIGNMENT_RIGHT = 4;
-
-  // We set every value we use every time we use the layout builder, so we can get away with only
-  // using a single instance.
-  private static final TextLayoutBuilder sTextLayoutBuilder =
-      new TextLayoutBuilder()
-          .setShouldCacheLayout(false)
-          .setShouldWarmText(true)
-          .setGlyphWarmer(new GlyphWarmerImpl());
-
-  private @Nullable CharSequence mText;
-  private @Nullable DrawTextLayout mDrawCommand;
-  private float mSpacingMult = 1.0f;
-  private float mSpacingAdd = 0.0f;
-  private int mNumberOfLines = Integer.MAX_VALUE;
-  private int mAlignment = Gravity.NO_GRAVITY;
-  private boolean mIncludeFontPadding = true;
-
-  public RCTText() {
-    setMeasureFunction(this);
-    getSpan().setFontSize(getDefaultFontSize());
-  }
-
-  @Override
-  public boolean isVirtual() {
-    return false;
-  }
-
-  @Override
-  public boolean isVirtualAnchor() {
-    return true;
-  }
-
-  @Override
-  public long measure(
-      YogaNode node,
-      float width,
-      YogaMeasureMode widthMode,
-      float height,
-      YogaMeasureMode heightMode) {
-
-    CharSequence text = getText();
-    if (TextUtils.isEmpty(text)) {
-      // to indicate that we don't have anything to display
-      mText = null;
-      return YogaMeasureOutput.make(0, 0);
-    } else {
-      mText = text;
-    }
-
-    Layout layout = createTextLayout(
-        (int) Math.ceil(width),
-        widthMode,
-        TextUtils.TruncateAt.END,
-        mIncludeFontPadding,
-        mNumberOfLines,
-        mNumberOfLines == 1,
-        text,
-        getFontSize(),
-        mSpacingAdd,
-        mSpacingMult,
-        getFontStyle(),
-        getAlignment());
-
-    if (mDrawCommand != null && !mDrawCommand.isFrozen()) {
-      mDrawCommand.setLayout(layout);
-    } else {
-      mDrawCommand = new DrawTextLayout(layout);
-    }
-
-    return YogaMeasureOutput.make(mDrawCommand.getLayoutWidth(), mDrawCommand.getLayoutHeight());
-  }
-
-  @Override
-  protected void collectState(
-      StateBuilder stateBuilder,
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-
-    super.collectState(
-        stateBuilder,
-        left,
-        top,
-        right,
-        bottom,
-        clipLeft,
-        clipTop,
-        clipRight,
-        clipBottom);
-
-    if (mText == null) {
-      // as an optimization, LayoutEngine may not call measure in certain cases, such as when the
-      // dimensions are already defined. in these cases, we should still draw the text.
-      if (bottom - top > 0 && right - left > 0) {
-        CharSequence text = getText();
-        if (!TextUtils.isEmpty(text)) {
-          mText = text;
-        }
-      }
-
-      if (mText == null) {
-        // nothing to draw (empty text).
-        return;
-      }
-    }
-
-    boolean updateNodeRegion = false;
-    if (mDrawCommand == null) {
-      mDrawCommand = new DrawTextLayout(createTextLayout(
-          (int) Math.ceil(right - left),
-          YogaMeasureMode.EXACTLY,
-          TextUtils.TruncateAt.END,
-          mIncludeFontPadding,
-          mNumberOfLines,
-          mNumberOfLines == 1,
-          mText,
-          getFontSize(),
-          mSpacingAdd,
-          mSpacingMult,
-          getFontStyle(),
-          getAlignment()));
-      updateNodeRegion = true;
-    }
-
-    left += getPadding(Spacing.LEFT);
-    top += getPadding(Spacing.TOP);
-
-    // these are actual right/bottom coordinates where this DrawCommand will draw.
-    right = left + mDrawCommand.getLayoutWidth();
-    bottom = top + mDrawCommand.getLayoutHeight();
-
-    mDrawCommand = (DrawTextLayout) mDrawCommand.updateBoundsAndFreeze(
-        left,
-        top,
-        right,
-        bottom,
-        clipLeft,
-        clipTop,
-        clipRight,
-        clipBottom);
-    stateBuilder.addDrawCommand(mDrawCommand);
-
-    if (updateNodeRegion) {
-      NodeRegion nodeRegion = getNodeRegion();
-      if (nodeRegion instanceof TextNodeRegion) {
-        ((TextNodeRegion) nodeRegion).setLayout(mDrawCommand.getLayout());
-      }
-    }
-
-    performCollectAttachDetachListeners(stateBuilder);
-  }
-
-  @Override
-  boolean doesDraw() {
-    // assume text always draws - this is a performance optimization to avoid having to
-    // getText() when layout was skipped and when collectState wasn't yet called
-    return true;
-  }
-
-  @ReactProp(name = ViewProps.LINE_HEIGHT, defaultDouble = Double.NaN)
-  public void setLineHeight(double lineHeight) {
-    if (Double.isNaN(lineHeight)) {
-      mSpacingMult = 1.0f;
-      mSpacingAdd = 0.0f;
-    } else {
-      mSpacingMult = 0.0f;
-      mSpacingAdd = PixelUtil.toPixelFromSP((float) lineHeight);
-    }
-    notifyChanged(true);
-  }
-
-  @ReactProp(name = ViewProps.NUMBER_OF_LINES, defaultInt = Integer.MAX_VALUE)
-  public void setNumberOfLines(int numberOfLines) {
-    mNumberOfLines = numberOfLines;
-    notifyChanged(true);
-  }
-
-  @ReactProp(name = ViewProps.INCLUDE_FONT_PADDING, defaultBoolean = true)
-  public void setIncludeFontPadding(boolean includepad) {
-    mIncludeFontPadding = includepad;
-  }
-
-  @Override
-  /* package */ void updateNodeRegion(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      boolean isVirtual) {
-
-    NodeRegion nodeRegion = getNodeRegion();
-    if (mDrawCommand == null) {
-      if (!nodeRegion.matches(left, top, right, bottom, isVirtual)) {
-        setNodeRegion(new TextNodeRegion(left, top, right, bottom, getReactTag(), isVirtual, null));
-      }
-      return;
-    }
-
-    Layout layout = null;
-
-    if (nodeRegion instanceof TextNodeRegion) {
-      layout = ((TextNodeRegion) nodeRegion).getLayout();
-    }
-
-    Layout newLayout = mDrawCommand.getLayout();
-    if (!nodeRegion.matches(left, top, right, bottom, isVirtual) || layout != newLayout) {
-      setNodeRegion(
-          new TextNodeRegion(left, top, right, bottom, getReactTag(), isVirtual, newLayout));
-    }
-  }
-
-  @Override
-  protected int getDefaultFontSize() {
-    // top-level <Text /> should always specify font size.
-    return fontSizeFromSp(ViewDefaults.FONT_SIZE_SP);
-  }
-
-  @Override
-  protected void notifyChanged(boolean shouldRemeasure) {
-    // Future patch: should only recreate Layout if shouldRemeasure is false
-    dirty();
-  }
-
-  @ReactProp(name = ViewProps.TEXT_ALIGN)
-  public void setTextAlign(@Nullable String textAlign) {
-    if (textAlign == null || "auto".equals(textAlign)) {
-      mAlignment = Gravity.NO_GRAVITY;
-    } else if ("left".equals(textAlign)) {
-      // left and right may yield potentially different results (relative to non-nodes) in cases
-      // when supportsRTL="true" in the manifest.
-      mAlignment = Gravity.LEFT;
-    } else if ("right".equals(textAlign)) {
-      mAlignment = Gravity.RIGHT;
-    } else if ("center".equals(textAlign)) {
-      mAlignment = Gravity.CENTER;
-    } else {
-      throw new JSApplicationIllegalArgumentException("Invalid textAlign: " + textAlign);
-    }
-
-    notifyChanged(false);
-  }
-
-  public Layout.Alignment getAlignment() {
-    boolean isRtl = getLayoutDirection() == YogaDirection.RTL;
-    switch (mAlignment) {
-      // Layout.Alignment.RIGHT and Layout.Alignment.LEFT are @hide :(
-      case Gravity.LEFT:
-        int index = isRtl ? ALIGNMENT_RIGHT : ALIGNMENT_LEFT;
-        return Layout.Alignment.values()[index];
-      case Gravity.RIGHT:
-        index = isRtl ? ALIGNMENT_LEFT : ALIGNMENT_RIGHT;
-        return Layout.Alignment.values()[index];
-      case Gravity.CENTER:
-        return Layout.Alignment.ALIGN_CENTER;
-      case Gravity.NO_GRAVITY:
-      default:
-        return Layout.Alignment.ALIGN_NORMAL;
-    }
-  }
-
-  private static Layout createTextLayout(
-      int width,
-      YogaMeasureMode widthMode,
-      TextUtils.TruncateAt ellipsize,
-      boolean shouldIncludeFontPadding,
-      int maxLines,
-      boolean isSingleLine,
-      CharSequence text,
-      int textSize,
-      float extraSpacing,
-      float spacingMultiplier,
-      int textStyle,
-      Layout.Alignment textAlignment) {
-    Layout newLayout;
-
-    final @TextLayoutBuilder.MeasureMode int textMeasureMode;
-    switch (widthMode) {
-      case UNDEFINED:
-        textMeasureMode = TextLayoutBuilder.MEASURE_MODE_UNSPECIFIED;
-        break;
-      case EXACTLY:
-        textMeasureMode = TextLayoutBuilder.MEASURE_MODE_EXACTLY;
-        break;
-      case AT_MOST:
-        textMeasureMode = TextLayoutBuilder.MEASURE_MODE_AT_MOST;
-        break;
-      default:
-        throw new IllegalStateException("Unexpected size mode: " + widthMode);
-    }
-
-    sTextLayoutBuilder
-        .setEllipsize(ellipsize)
-        .setMaxLines(maxLines)
-        .setSingleLine(isSingleLine)
-        .setText(text)
-        .setTextSize(textSize)
-        .setWidth(width, textMeasureMode);
-
-    sTextLayoutBuilder.setTextStyle(textStyle);
-
-    sTextLayoutBuilder.setTextDirection(TextDirectionHeuristicsCompat.FIRSTSTRONG_LTR);
-    sTextLayoutBuilder.setIncludeFontPadding(shouldIncludeFontPadding);
-    sTextLayoutBuilder.setTextSpacingExtra(extraSpacing);
-    sTextLayoutBuilder.setTextSpacingMultiplier(spacingMultiplier);
-    sTextLayoutBuilder.setAlignment(textAlignment);
-
-    newLayout = sTextLayoutBuilder.build();
-
-    sTextLayoutBuilder.setText(null);
-
-    return newLayout;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInlineImage.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInlineImage.java
deleted file mode 100644
index 728df41d51d4..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInlineImage.java
+++ /dev/null
@@ -1,88 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.text.SpannableStringBuilder;
-import android.text.Spanned;
-
-import com.facebook.imagepipeline.request.ImageRequestBuilder;
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.uimanager.annotations.ReactProp;
-import com.facebook.react.views.imagehelper.ImageSource;
-
-/**
- * RCTTextInlineImage
- */
-/* package */ class RCTTextInlineImage extends FlatTextShadowNode {
-
-  private InlineImageSpanWithPipeline mInlineImageSpan = new InlineImageSpanWithPipeline();
-
-  @Override
-  public void setStyleWidth(float width) {
-    super.setStyleWidth(width);
-
-    if (mInlineImageSpan.getWidth() != width) {
-      getMutableSpan().setWidth(width);
-      notifyChanged(true);
-    }
-  }
-
-  @Override
-  public void setStyleHeight(float height) {
-    super.setStyleHeight(height);
-
-    if (mInlineImageSpan.getHeight() != height) {
-      getMutableSpan().setHeight(height);
-      notifyChanged(true);
-    }
-  }
-
-  @Override
-  protected void performCollectText(SpannableStringBuilder builder) {
-    builder.append("I");
-  }
-
-  @Override
-  protected void performApplySpans(
-      SpannableStringBuilder builder,
-      int begin,
-      int end,
-      boolean isEditable) {
-    mInlineImageSpan.freeze();
-    builder.setSpan(
-        mInlineImageSpan,
-        begin,
-        end,
-        Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
-  }
-
-  @Override
-  protected void performCollectAttachDetachListeners(StateBuilder stateBuilder) {
-    // mInlineImageSpan should already be frozen so no need to freeze it again
-    stateBuilder.addAttachDetachListener(mInlineImageSpan);
-  }
-
-  @ReactProp(name = "src")
-  public void setSource(@Nullable ReadableArray sources) {
-    final String source =
-        (sources == null || sources.size() == 0) ? null : sources.getMap(0).getString("uri");
-    final ImageSource imageSource = source == null ? null :
-        new ImageSource(getThemedContext(), source);
-    getMutableSpan().setImageRequest(imageSource == null ? null :
-        ImageRequestBuilder.newBuilderWithSource(imageSource.getUri()).build());
-  }
-
-  private InlineImageSpanWithPipeline getMutableSpan() {
-    if (mInlineImageSpan.isFrozen()) {
-      mInlineImageSpan = mInlineImageSpan.mutableCopy();
-    }
-    return mInlineImageSpan;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInlineImageManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInlineImageManager.java
deleted file mode 100644
index f670378585e5..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInlineImageManager.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-/**
- * ViewManager that creates instances of RCTTextInlineImage.
- */
-public final class RCTTextInlineImageManager extends VirtualViewManager<RCTTextInlineImage> {
-
-  /* package */ static final String REACT_CLASS = "RCTTextInlineImage";
-
-  @Override
-  public String getName() {
-    return REACT_CLASS;
-  }
-
-  @Override
-  public RCTTextInlineImage createShadowNodeInstance() {
-    return new RCTTextInlineImage();
-  }
-
-  @Override
-  public Class<RCTTextInlineImage> getShadowNodeClass() {
-    return RCTTextInlineImage.class;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInput.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInput.java
deleted file mode 100644
index 77d3cd9a33b3..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInput.java
+++ /dev/null
@@ -1,191 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import static com.facebook.react.views.text.ReactRawTextShadowNode.PROP_TEXT;
-import static com.facebook.react.views.text.ReactTextShadowNode.UNSET;
-
-import android.annotation.TargetApi;
-import android.os.Build;
-import android.text.SpannableStringBuilder;
-import android.util.TypedValue;
-import android.view.ViewGroup;
-import android.widget.EditText;
-import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.Spacing;
-import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.UIViewOperationQueue;
-import com.facebook.react.uimanager.ViewDefaults;
-import com.facebook.react.uimanager.ViewProps;
-import com.facebook.react.uimanager.annotations.ReactProp;
-import com.facebook.react.views.text.ReactTextUpdate;
-import com.facebook.react.views.view.MeasureUtil;
-import com.facebook.yoga.YogaMeasureFunction;
-import com.facebook.yoga.YogaMeasureMode;
-import com.facebook.yoga.YogaMeasureOutput;
-import com.facebook.yoga.YogaNode;
-import javax.annotation.Nullable;
-
-public class RCTTextInput extends RCTVirtualText implements AndroidView, YogaMeasureFunction {
-
-  @Nullable private String mText;
-  private int mJsEventCount = UNSET;
-  private boolean mPaddingChanged = false;
-  private int mNumberOfLines = UNSET;
-  private @Nullable EditText mEditText;
-
-  public RCTTextInput() {
-    forceMountToView();
-    setMeasureFunction(this);
-  }
-
-  @Override
-  protected void notifyChanged(boolean shouldRemeasure) {
-    super.notifyChanged(shouldRemeasure);
-    // needed to trigger onCollectExtraUpdates
-    markUpdated();
-  }
-
-  @TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR1)
-  @Override
-  public void setThemedContext(ThemedReactContext themedContext) {
-    super.setThemedContext(themedContext);
-
-    mEditText = new EditText(themedContext);
-    // This is needed to fix an android bug since 4.4.3 which will throw an NPE in measure,
-    // setting the layoutParams fixes it: https://code.google.com/p/android/issues/detail?id=75877
-    mEditText.setLayoutParams(
-        new ViewGroup.LayoutParams(
-            ViewGroup.LayoutParams.WRAP_CONTENT,
-            ViewGroup.LayoutParams.WRAP_CONTENT));
-
-    setDefaultPadding(Spacing.START, mEditText.getPaddingStart());
-    setDefaultPadding(Spacing.TOP, mEditText.getPaddingTop());
-    setDefaultPadding(Spacing.END, mEditText.getPaddingEnd());
-    setDefaultPadding(Spacing.BOTTOM, mEditText.getPaddingBottom());
-    mEditText.setPadding(0, 0, 0, 0);
-  }
-
-  @Override
-  public long measure(
-      YogaNode node,
-      float width,
-      YogaMeasureMode widthMode,
-      float height,
-      YogaMeasureMode heightMode) {
-    // measure() should never be called before setThemedContext()
-    EditText editText = Assertions.assertNotNull(mEditText);
-
-    int fontSize = getFontSize();
-    editText.setTextSize(
-        TypedValue.COMPLEX_UNIT_PX,
-        fontSize == UNSET ?
-            (int) Math.ceil(PixelUtil.toPixelFromSP(ViewDefaults.FONT_SIZE_SP)) : fontSize);
-
-    if (mNumberOfLines != UNSET) {
-      editText.setLines(mNumberOfLines);
-    }
-
-    editText.measure(
-        MeasureUtil.getMeasureSpec(width, widthMode),
-        MeasureUtil.getMeasureSpec(height, heightMode));
-    return YogaMeasureOutput.make(editText.getMeasuredWidth(), editText.getMeasuredHeight());
-  }
-
-  @Override
-  public boolean isVirtual() {
-    return false;
-  }
-
-  @Override
-  public boolean isVirtualAnchor() {
-    return true;
-  }
-
-  @Override
-  public void setBackgroundColor(int backgroundColor) {
-    // suppress, this is handled by a ViewManager
-  }
-
-  @Override
-  public void onCollectExtraUpdates(UIViewOperationQueue uiViewOperationQueue) {
-    super.onCollectExtraUpdates(uiViewOperationQueue);
-    if (mJsEventCount != UNSET) {
-      ReactTextUpdate reactTextUpdate =
-          new ReactTextUpdate(
-              getText(),
-              mJsEventCount,
-              false,
-              getPadding(Spacing.START),
-              getPadding(Spacing.TOP),
-              getPadding(Spacing.END),
-              getPadding(Spacing.BOTTOM),
-              UNSET);
-      // TODO: the Float.NaN should be replaced with the real line height see D3592781
-      uiViewOperationQueue.enqueueUpdateExtraData(getReactTag(), reactTextUpdate);
-    }
-  }
-
-  @ReactProp(name = "mostRecentEventCount")
-  public void setMostRecentEventCount(int mostRecentEventCount) {
-    mJsEventCount = mostRecentEventCount;
-  }
-
-  @ReactProp(name = ViewProps.NUMBER_OF_LINES, defaultInt = Integer.MAX_VALUE)
-  public void setNumberOfLines(int numberOfLines) {
-    mNumberOfLines = numberOfLines;
-    notifyChanged(true);
-  }
-
-  @ReactProp(name = PROP_TEXT)
-  public void setText(@Nullable String text) {
-    mText = text;
-    notifyChanged(true);
-  }
-
-  @Override
-  public void setPadding(int spacingType, float padding) {
-    super.setPadding(spacingType, padding);
-    mPaddingChanged = true;
-    dirty();
-  }
-
-  @Override
-  public boolean isPaddingChanged() {
-    return mPaddingChanged;
-  }
-
-  @Override
-  public void resetPaddingChanged() {
-    mPaddingChanged = false;
-  }
-
-  @Override
-  boolean shouldAllowEmptySpans() {
-    return true;
-  }
-
-  @Override
-  boolean isEditable() {
-    return true;
-  }
-
-  @Override
-  protected void performCollectText(SpannableStringBuilder builder) {
-    if (mText != null) {
-      builder.append(mText);
-    }
-    super.performCollectText(builder);
-  }
-
-  @Override
-  public boolean needsCustomLayoutForChildren() {
-    return false;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInputManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInputManager.java
deleted file mode 100644
index 62fe19960cba..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextInputManager.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import com.facebook.react.views.textinput.ReactTextInputManager;
-
-public class RCTTextInputManager extends ReactTextInputManager {
-
-  /* package */ static final String REACT_CLASS = ReactTextInputManager.REACT_CLASS;
-
-  @Override
-  public RCTTextInput createShadowNodeInstance() {
-    return new RCTTextInput();
-  }
-
-  @Override
-  public Class<RCTTextInput> getShadowNodeClass() {
-    return RCTTextInput.class;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextManager.java
deleted file mode 100644
index 77ec1fb256e2..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTTextManager.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-/**
- * ViewManager that creates instances of RCTText.
- */
-public final class RCTTextManager extends FlatViewManager {
-
-  /* package */ static final String REACT_CLASS = "RCTText";
-
-  @Override
-  public String getName() {
-    return REACT_CLASS;
-  }
-
-  @Override
-  public RCTText createShadowNodeInstance() {
-    return new RCTText();
-  }
-
-  @Override
-  public Class<RCTText> getShadowNodeClass() {
-    return RCTText.class;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTView.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTView.java
deleted file mode 100644
index 2beaa2230ce6..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTView.java
+++ /dev/null
@@ -1,185 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.graphics.Rect;
-
-import com.facebook.react.bridge.ReadableMap;
-import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.Spacing;
-import com.facebook.react.uimanager.ReactStylesDiffMap;
-import com.facebook.react.uimanager.annotations.ReactProp;
-import com.facebook.react.uimanager.annotations.ReactPropGroup;
-
-/**
- * Node for a react View.
- */
-/* package */ final class RCTView extends FlatShadowNode {
-  private static final int[] SPACING_TYPES = {
-      Spacing.ALL, Spacing.LEFT, Spacing.RIGHT, Spacing.TOP, Spacing.BOTTOM,
-  };
-
-  private @Nullable DrawBorder mDrawBorder;
-
-  boolean mRemoveClippedSubviews;
-  boolean mHorizontal;
-
-  private @Nullable Rect mHitSlop;
-
-  @Override
-  /* package */ void handleUpdateProperties(ReactStylesDiffMap styles) {
-    mRemoveClippedSubviews = mRemoveClippedSubviews ||
-        (styles.hasKey(PROP_REMOVE_CLIPPED_SUBVIEWS) &&
-            styles.getBoolean(PROP_REMOVE_CLIPPED_SUBVIEWS, false));
-
-    if (mRemoveClippedSubviews) {
-      mHorizontal = mHorizontal ||
-          (styles.hasKey(PROP_HORIZONTAL) && styles.getBoolean(PROP_HORIZONTAL, false));
-    }
-
-    super.handleUpdateProperties(styles);
-  }
-
-  @Override
-  protected void collectState(
-      StateBuilder stateBuilder,
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    super.collectState(
-        stateBuilder,
-        left,
-        top,
-        right,
-        bottom,
-        clipLeft,
-        clipTop,
-        clipRight,
-        clipBottom);
-
-    if (mDrawBorder != null) {
-      mDrawBorder = (DrawBorder) mDrawBorder.updateBoundsAndFreeze(
-          left,
-          top,
-          right,
-          bottom,
-          clipLeft,
-          clipTop,
-          clipRight,
-          clipBottom);
-      stateBuilder.addDrawCommand(mDrawBorder);
-    }
-  }
-
-  @Override
-  boolean doesDraw() {
-    return mDrawBorder != null || super.doesDraw();
-  }
-
-  @Override
-  public void setBackgroundColor(int backgroundColor) {
-    getMutableBorder().setBackgroundColor(backgroundColor);
-  }
-
-  @Override
-  public void setBorderWidths(int index, float borderWidth) {
-    super.setBorderWidths(index, borderWidth);
-
-    int type = SPACING_TYPES[index];
-    getMutableBorder().setBorderWidth(type, PixelUtil.toPixelFromDIP(borderWidth));
-  }
-
-  @ReactProp(name = "nativeBackgroundAndroid")
-  public void setHotspot(@Nullable ReadableMap bg) {
-    if (bg != null) {
-      forceMountToView();
-    }
-  }
-
-  @ReactPropGroup(names = {
-      "borderColor", "borderLeftColor", "borderRightColor", "borderTopColor", "borderBottomColor"
-  }, customType = "Color", defaultDouble = Double.NaN)
-  public void setBorderColor(int index, double color) {
-    int type = SPACING_TYPES[index];
-    if (Double.isNaN(color)) {
-      getMutableBorder().resetBorderColor(type);
-    } else {
-      getMutableBorder().setBorderColor(type, (int) color);
-    }
-  }
-
-  @ReactProp(name = "borderRadius")
-  public void setBorderRadius(float borderRadius) {
-    mClipRadius = borderRadius;
-    if (mClipToBounds && borderRadius > DrawView.MINIMUM_ROUNDED_CLIPPING_VALUE) {
-      // mount to a view if we are overflow: hidden and are clipping, so that we can do one
-      // clipPath to clip all the children of this node (both DrawCommands and Views).
-      forceMountToView();
-    }
-    getMutableBorder().setBorderRadius(PixelUtil.toPixelFromDIP(borderRadius));
-  }
-
-  @ReactProp(name = "borderStyle")
-  public void setBorderStyle(@Nullable String borderStyle) {
-    getMutableBorder().setBorderStyle(borderStyle);
-  }
-
-  @ReactProp(name = "hitSlop")
-  public void setHitSlop(@Nullable ReadableMap hitSlop) {
-    if (hitSlop == null) {
-      mHitSlop = null;
-    } else {
-      mHitSlop = new Rect(
-          (int) PixelUtil.toPixelFromDIP(hitSlop.getDouble("left")),
-          (int) PixelUtil.toPixelFromDIP(hitSlop.getDouble("top")),
-          (int) PixelUtil.toPixelFromDIP(hitSlop.getDouble("right")),
-          (int) PixelUtil.toPixelFromDIP(hitSlop.getDouble("bottom")));
-    }
-  }
-
-  @ReactProp(name = "pointerEvents")
-  public void setPointerEvents(@Nullable String pointerEventsStr) {
-    forceMountToView();
-  }
-
-  @Override
-  /* package */ void updateNodeRegion(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      boolean isVirtual) {
-    if (!getNodeRegion().matches(left, top, right, bottom, isVirtual)) {
-      setNodeRegion(mHitSlop == null ?
-          new NodeRegion(left, top, right, bottom, getReactTag(), isVirtual) :
-          new HitSlopNodeRegion(mHitSlop, left, top, right, bottom, getReactTag(), isVirtual));
-    }
-  }
-
-  private DrawBorder getMutableBorder() {
-    if (mDrawBorder == null) {
-      mDrawBorder = new DrawBorder();
-    } else if (mDrawBorder.isFrozen()) {
-      mDrawBorder = (DrawBorder) mDrawBorder.mutableCopy();
-    }
-    invalidate();
-    return mDrawBorder;
-  }
-
-  @Override
-  public boolean clipsSubviews() {
-    return mRemoveClippedSubviews;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTViewManager.java
deleted file mode 100644
index 2e08dde5d211..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTViewManager.java
+++ /dev/null
@@ -1,140 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Rect;
-import android.os.Build;
-import com.facebook.react.bridge.JSApplicationIllegalArgumentException;
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.bridge.ReadableMap;
-import com.facebook.react.common.MapBuilder;
-import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.PointerEvents;
-import com.facebook.react.uimanager.ReactClippingViewGroupHelper;
-import com.facebook.react.uimanager.ViewProps;
-import com.facebook.react.uimanager.annotations.ReactProp;
-import com.facebook.react.views.view.ReactDrawableHelper;
-
-import javax.annotation.Nullable;
-import java.util.Map;
-
-/**
- * ViewManager that creates instances of RCTView.
- */
-public final class RCTViewManager extends FlatViewManager {
-
-  /* package */ static final String REACT_CLASS = ViewProps.VIEW_CLASS_NAME;
-
-  private static final int[] TMP_INT_ARRAY = new int[2];
-
-  private static final int CMD_HOTSPOT_UPDATE = 1;
-  private static final int CMD_SET_PRESSED = 2;
-
-  @Override
-  public String getName() {
-    return REACT_CLASS;
-  }
-
-  public Map<String, Integer> getCommandsMap() {
-    return MapBuilder.of("hotspotUpdate", CMD_HOTSPOT_UPDATE, "setPressed", CMD_SET_PRESSED);
-  }
-
-  @Override
-  public RCTView createShadowNodeInstance() {
-    return new RCTView();
-  }
-
-  @Override
-  public Class<RCTView> getShadowNodeClass() {
-    return RCTView.class;
-  }
-
-  @ReactProp(name = "nativeBackgroundAndroid")
-  public void setHotspot(FlatViewGroup view, @Nullable ReadableMap bg) {
-    view.setHotspot(bg == null ?
-      null : ReactDrawableHelper.createDrawableFromJSDescription(view.getContext(), bg));
-  }
-
-  @Override
-  public void receiveCommand(
-    FlatViewGroup view,
-    int commandId,
-    @Nullable ReadableArray args) {
-    switch (commandId) {
-      case CMD_HOTSPOT_UPDATE: {
-        if (args == null || args.size() != 2) {
-          throw new JSApplicationIllegalArgumentException(
-            "Illegal number of arguments for 'updateHotspot' command");
-        }
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-          view.getLocationOnScreen(TMP_INT_ARRAY);
-          float x = PixelUtil.toPixelFromDIP(args.getDouble(0)) - TMP_INT_ARRAY[0];
-          float y = PixelUtil.toPixelFromDIP(args.getDouble(1)) - TMP_INT_ARRAY[1];
-          view.drawableHotspotChanged(x, y);
-        }
-        break;
-      }
-      case CMD_SET_PRESSED: {
-        if (args == null || args.size() != 1) {
-          throw new JSApplicationIllegalArgumentException(
-            "Illegal number of arguments for 'setPressed' command");
-        }
-        view.setPressed(args.getBoolean(0));
-        break;
-      }
-    }
-  }
-
-  @ReactProp(name = ViewProps.NEEDS_OFFSCREEN_ALPHA_COMPOSITING)
-  public void setNeedsOffscreenAlphaCompositing(
-    FlatViewGroup view,
-    boolean needsOffscreenAlphaCompositing) {
-    view.setNeedsOffscreenAlphaCompositing(needsOffscreenAlphaCompositing);
-  }
-
-  @ReactProp(name = "pointerEvents")
-  public void setPointerEvents(FlatViewGroup view, @Nullable String pointerEventsStr) {
-    view.setPointerEvents(parsePointerEvents(pointerEventsStr));
-  }
-
-  @ReactProp(name = ReactClippingViewGroupHelper.PROP_REMOVE_CLIPPED_SUBVIEWS)
-  public void setRemoveClippedSubviews(FlatViewGroup view, boolean removeClippedSubviews) {
-    view.setRemoveClippedSubviews(removeClippedSubviews);
-  }
-
-  private static PointerEvents parsePointerEvents(@Nullable String pointerEventsStr) {
-    if (pointerEventsStr != null) {
-      switch (pointerEventsStr) {
-        case "none":
-          return PointerEvents.NONE;
-        case "auto":
-          return PointerEvents.AUTO;
-        case "box-none":
-          return PointerEvents.BOX_NONE;
-        case "box-only":
-          return PointerEvents.BOX_ONLY;
-      }
-    }
-    // default or invalid
-    return PointerEvents.AUTO;
-  }
-
-  @ReactProp(name = "hitSlop")
-  public void setHitSlop(FlatViewGroup view, @Nullable ReadableMap hitSlop) {
-    if (hitSlop == null) {
-      view.setHitSlopRect(null);
-    } else {
-      view.setHitSlopRect(new Rect(
-        (int) PixelUtil.toPixelFromDIP(hitSlop.getDouble("left")),
-        (int) PixelUtil.toPixelFromDIP(hitSlop.getDouble("top")),
-        (int) PixelUtil.toPixelFromDIP(hitSlop.getDouble("right")),
-        (int) PixelUtil.toPixelFromDIP(hitSlop.getDouble("bottom"))
-      ));
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTViewPagerManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTViewPagerManager.java
deleted file mode 100644
index 23b00fe19843..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTViewPagerManager.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.view.View;
-import com.facebook.react.views.viewpager.ReactViewPager;
-import com.facebook.react.views.viewpager.ReactViewPagerManager;
-
-import java.util.List;
-
-public class RCTViewPagerManager extends ReactViewPagerManager {
-
-  /* package */ static final String REACT_CLASS = ReactViewPagerManager.REACT_CLASS;
-
-  @Override
-  public void addViews(ReactViewPager parent, List<View> views) {
-    parent.setViews(views);
-  }
-
-  @Override
-  public void removeAllViews(ReactViewPager parent) {
-    parent.removeAllViewsFromAdapter();
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTVirtualText.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTVirtualText.java
deleted file mode 100644
index 1c0bcee7913a..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTVirtualText.java
+++ /dev/null
@@ -1,307 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.graphics.Typeface;
-import android.text.Spannable;
-import android.text.SpannableStringBuilder;
-import android.text.TextUtils;
-import com.facebook.react.bridge.ReadableMap;
-import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.ReactShadowNodeImpl;
-import com.facebook.react.uimanager.ViewProps;
-import com.facebook.react.uimanager.annotations.ReactProp;
-import javax.annotation.Nullable;
-
-/**
- * RCTVirtualText is a {@link FlatTextShadowNode} that can contain font styling information.
- */
-/* package */ class RCTVirtualText extends FlatTextShadowNode {
-
-  private static final String BOLD = "bold";
-  private static final String ITALIC = "italic";
-  private static final String NORMAL = "normal";
-
-  private static final String PROP_SHADOW_OFFSET = "textShadowOffset";
-  private static final String PROP_SHADOW_RADIUS = "textShadowRadius";
-  private static final String PROP_SHADOW_COLOR = "textShadowColor";
-  private static final int DEFAULT_TEXT_SHADOW_COLOR = 0x55000000;
-
-  private FontStylingSpan mFontStylingSpan = FontStylingSpan.INSTANCE;
-  private ShadowStyleSpan mShadowStyleSpan = ShadowStyleSpan.INSTANCE;
-
-  @Override
-  public void addChildAt(ReactShadowNodeImpl child, int i) {
-    super.addChildAt(child, i);
-    notifyChanged(true);
-  }
-
-  @Override
-  protected void performCollectText(SpannableStringBuilder builder) {
-    for (int i = 0, childCount = getChildCount(); i < childCount; ++i) {
-      FlatTextShadowNode child = (FlatTextShadowNode) getChildAt(i);
-      child.collectText(builder);
-    }
-  }
-
-  @Override
-  protected void performApplySpans(SpannableStringBuilder builder, int begin, int end, boolean isEditable) {
-    mFontStylingSpan.freeze();
-
-    // All spans will automatically extend to the right of the text, but not the left - except
-    // for spans that start at the beginning of the text.
-    final int flag;
-    if (isEditable) {
-      flag = Spannable.SPAN_EXCLUSIVE_EXCLUSIVE;
-    } else {
-      flag = begin == 0 ?
-          Spannable.SPAN_INCLUSIVE_INCLUSIVE :
-          Spannable.SPAN_EXCLUSIVE_INCLUSIVE;
-    }
-
-    builder.setSpan(
-        mFontStylingSpan,
-        begin,
-        end,
-        flag);
-
-    if (mShadowStyleSpan.getColor() != 0 && mShadowStyleSpan.getRadius() != 0) {
-      mShadowStyleSpan.freeze();
-
-      builder.setSpan(
-          mShadowStyleSpan,
-          begin,
-          end,
-          flag);
-    }
-
-    for (int i = 0, childCount = getChildCount(); i < childCount; ++i) {
-      FlatTextShadowNode child = (FlatTextShadowNode) getChildAt(i);
-      child.applySpans(builder, isEditable);
-    }
-  }
-
-  @Override
-  protected void performCollectAttachDetachListeners(StateBuilder stateBuilder) {
-    for (int i = 0, childCount = getChildCount(); i < childCount; ++i) {
-      FlatTextShadowNode child = (FlatTextShadowNode) getChildAt(i);
-      child.performCollectAttachDetachListeners(stateBuilder);
-    }
-  }
-
-  @ReactProp(name = ViewProps.FONT_SIZE, defaultFloat = Float.NaN)
-  public void setFontSize(float fontSizeSp) {
-    final int fontSize;
-    if (Float.isNaN(fontSizeSp)) {
-      fontSize = getDefaultFontSize();
-    } else {
-      fontSize = fontSizeFromSp(fontSizeSp);
-    }
-
-    if (mFontStylingSpan.getFontSize() != fontSize) {
-      getSpan().setFontSize(fontSize);
-      notifyChanged(true);
-    }
-  }
-
-  @ReactProp(name = ViewProps.COLOR, defaultDouble = Double.NaN)
-  public void setColor(double textColor) {
-    if (mFontStylingSpan.getTextColor() != textColor) {
-      getSpan().setTextColor(textColor);
-      notifyChanged(false);
-    }
-  }
-
-  @Override
-  public void setBackgroundColor(int backgroundColor) {
-    if (isVirtual()) {
-      // for nested Text elements, we want to apply background color to the text only
-      // e.g. Hello <style backgroundColor=red>World</style>, "World" will have red background color
-      if (mFontStylingSpan.getBackgroundColor() != backgroundColor) {
-        getSpan().setBackgroundColor(backgroundColor);
-        notifyChanged(false);
-      }
-    } else {
-      // for top-level Text element, background needs to be applied for the entire shadow node
-      //
-      // For example: <Text style={flex:1}>Hello World</Text>
-      // "Hello World" may only occupy e.g. 200 pixels, but the node may be measured at e.g. 500px.
-      // In this case, we want background to be 500px wide as well, and this is exactly what
-      // FlatShadowNode does.
-      super.setBackgroundColor(backgroundColor);
-    }
-  }
-
-  @ReactProp(name = ViewProps.FONT_FAMILY)
-  public void setFontFamily(@Nullable String fontFamily) {
-    if (!TextUtils.equals(mFontStylingSpan.getFontFamily(), fontFamily)) {
-      getSpan().setFontFamily(fontFamily);
-      notifyChanged(true);
-    }
-  }
-
-  @ReactProp(name = ViewProps.FONT_WEIGHT)
-  public void setFontWeight(@Nullable String fontWeightString) {
-    final int fontWeight;
-    if (fontWeightString == null) {
-      fontWeight = -1;
-    } else if (BOLD.equals(fontWeightString)) {
-      fontWeight = Typeface.BOLD;
-    } else if (NORMAL.equals(fontWeightString)) {
-      fontWeight = Typeface.NORMAL;
-    } else {
-      int fontWeightNumeric = parseNumericFontWeight(fontWeightString);
-      if (fontWeightNumeric == -1) {
-        throw new RuntimeException("invalid font weight " + fontWeightString);
-      }
-      fontWeight = fontWeightNumeric >= 500 ? Typeface.BOLD : Typeface.NORMAL;
-    }
-
-    if (mFontStylingSpan.getFontWeight() != fontWeight) {
-      getSpan().setFontWeight(fontWeight);
-      notifyChanged(true);
-    }
-  }
-
-  @ReactProp(name = ViewProps.TEXT_DECORATION_LINE)
-  public void setTextDecorationLine(@Nullable String textDecorationLineString) {
-    boolean isUnderlineTextDecorationSet = false;
-    boolean isLineThroughTextDecorationSet = false;
-    if (textDecorationLineString != null) {
-      for (String textDecorationLineSubString : textDecorationLineString.split(" ")) {
-        if ("underline".equals(textDecorationLineSubString)) {
-          isUnderlineTextDecorationSet = true;
-        } else if ("line-through".equals(textDecorationLineSubString)) {
-          isLineThroughTextDecorationSet = true;
-        }
-      }
-    }
-
-    if (isUnderlineTextDecorationSet != mFontStylingSpan.hasUnderline() ||
-        isLineThroughTextDecorationSet != mFontStylingSpan.hasStrikeThrough()) {
-      FontStylingSpan span = getSpan();
-      span.setHasUnderline(isUnderlineTextDecorationSet);
-      span.setHasStrikeThrough(isLineThroughTextDecorationSet);
-      notifyChanged(true);
-    }
-  }
-
-  @ReactProp(name = ViewProps.FONT_STYLE)
-  public void setFontStyle(@Nullable String fontStyleString) {
-    final int fontStyle;
-    if (fontStyleString == null) {
-      fontStyle = -1;
-    } else if (ITALIC.equals(fontStyleString)) {
-      fontStyle = Typeface.ITALIC;
-    } else if (NORMAL.equals(fontStyleString)) {
-      fontStyle = Typeface.NORMAL;
-    } else {
-      throw new RuntimeException("invalid font style " + fontStyleString);
-    }
-
-    if (mFontStylingSpan.getFontStyle() != fontStyle) {
-      getSpan().setFontStyle(fontStyle);
-      notifyChanged(true);
-    }
-  }
-
-  @ReactProp(name = PROP_SHADOW_OFFSET)
-  public void setTextShadowOffset(@Nullable ReadableMap offsetMap) {
-    float dx = 0;
-    float dy = 0;
-    if (offsetMap != null) {
-      if (offsetMap.hasKey("width")) {
-        dx = PixelUtil.toPixelFromDIP(offsetMap.getDouble("width"));
-      }
-      if (offsetMap.hasKey("height")) {
-        dy = PixelUtil.toPixelFromDIP(offsetMap.getDouble("height"));
-      }
-    }
-
-    if (!mShadowStyleSpan.offsetMatches(dx, dy)) {
-      getShadowSpan().setOffset(dx, dy);
-      notifyChanged(false);
-    }
-  }
-
-  @ReactProp(name = PROP_SHADOW_RADIUS)
-  public void setTextShadowRadius(float textShadowRadius) {
-    textShadowRadius = PixelUtil.toPixelFromDIP(textShadowRadius);
-    if (mShadowStyleSpan.getRadius() != textShadowRadius) {
-      getShadowSpan().setRadius(textShadowRadius);
-      notifyChanged(false);
-    }
-  }
-
-  @ReactProp(name = PROP_SHADOW_COLOR, defaultInt = DEFAULT_TEXT_SHADOW_COLOR, customType = "Color")
-  public void setTextShadowColor(int textShadowColor) {
-    if (mShadowStyleSpan.getColor() != textShadowColor) {
-      getShadowSpan().setColor(textShadowColor);
-      notifyChanged(false);
-    }
-  }
-
-  /**
-   * Returns font size for this node.
-   * When called on RCTText, this value is never -1 (unset).
-   */
-  protected final int getFontSize() {
-    return mFontStylingSpan.getFontSize();
-  }
-  /**
-   * Returns font style for this node.
-   */
-  protected final int getFontStyle() {
-    int style = mFontStylingSpan.getFontStyle();
-    return style >= 0 ? style : Typeface.NORMAL;
-  }
-
-  protected int getDefaultFontSize() {
-    return -1;
-  }
-
-  /* package */ static int fontSizeFromSp(float sp) {
-    return (int) Math.ceil(PixelUtil.toPixelFromSP(sp));
-  }
-
-  protected final FontStylingSpan getSpan() {
-    if (mFontStylingSpan.isFrozen()) {
-      mFontStylingSpan = mFontStylingSpan.mutableCopy();
-    }
-    return mFontStylingSpan;
-  }
-
-  /**
-   * Returns a new SpannableStringBuilder that includes all the text and styling information to
-   * create the Layout.
-   */
-  /* package */ final SpannableStringBuilder getText() {
-    SpannableStringBuilder sb = new SpannableStringBuilder();
-    collectText(sb);
-    applySpans(sb, isEditable());
-    return sb;
-  }
-
-  private final ShadowStyleSpan getShadowSpan() {
-    if (mShadowStyleSpan.isFrozen()) {
-      mShadowStyleSpan = mShadowStyleSpan.mutableCopy();
-    }
-    return mShadowStyleSpan;
-  }
-
-  /**
-   * Return -1 if the input string is not a valid numeric fontWeight (100, 200, ..., 900), otherwise
-   * return the weight.
-   */
-  private static int parseNumericFontWeight(String fontWeightString) {
-    // This should be much faster than using regex to verify input and Integer.parseInt
-    return fontWeightString.length() == 3 && fontWeightString.endsWith("00")
-        && fontWeightString.charAt(0) <= '9' && fontWeightString.charAt(0) >= '1' ?
-        100 * (fontWeightString.charAt(0) - '0') : -1;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTVirtualTextManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/RCTVirtualTextManager.java
deleted file mode 100644
index 0c1ff3fd9786..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/RCTVirtualTextManager.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-/**
- * ViewManager that creates instances of RCTVirtualText.
- */
-public final class RCTVirtualTextManager extends VirtualViewManager<RCTVirtualText> {
-
-  /* package */ static final String REACT_CLASS = "RCTVirtualText";
-
-  @Override
-  public String getName() {
-    return REACT_CLASS;
-  }
-
-  @Override
-  public RCTVirtualText createShadowNodeInstance() {
-    return new RCTVirtualText();
-  }
-
-  @Override
-  public Class<RCTVirtualText> getShadowNodeClass() {
-    return RCTVirtualText.class;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/README.md b/ReactAndroid/src/main/java/com/facebook/react/flat/README.md
deleted file mode 100644
index f9fc580c0212..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/README.md
+++ /dev/null
@@ -1,49 +0,0 @@
-# Nodes
-
-Nodes is an experimental, alternate version of
-[UIImplementation](https://github.com/facebook/react-native/blob/master/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java) for ReactNative on Android. It has two main advantages over the existing `UIImplementation`:
-
-1. Support for `overflow:visible` on Android.
-2. More efficient generation of view hierarchies.
-
-The intention is to ultimately replace the existing `UIImplementation` on
-Android with Nodes (after all the issues are ironed out).
-
-## How to test
-
-In a subclass of `ReactNativeHost`, add this:
-
-```java
-@Override
-protected UIImplementationProvider getUIImplementationProvider() {
-  return new FlatUIImplementationProvider();
-}
-```
-
-## How it Works
-
-The existing
-[UIImplementation](https://github.com/facebook/react-native/blob/master/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementation.java) maps all non-layout tags to `View`s (resulting in an almost 1:1 mapping of tags
-to Views, with the exception of some optimizations for layout only tags that
-don't draw content). Nodes, on the other hand, maps react tags to a set of
-`DrawCommand`s. In other words, an `<image>` tag will often be mapped to a
-`Drawable` instead of an `ImageView` and a `<text>` tag will be mapped to a
-`Layout` instead of a `TextView`. This helps flatten the resulting `View`
-hierarchy.
-
-There are situations where `DrawCommand`s are promoted to `View`s:
-
-1. Existing Android components that are wrapped by React Native (for example, 
-`ViewPager`, `ScrollView`, etc).
-2. When using a `View` is more optimal (for example, `opacity`, to avoid
-unnecessary invalidations).
-3. To facilitate the implementation of certain features (accessibility,
-transforms, etc).
-
-This means that existing custom `ViewManager`s should continue to work as they
-did with the existing `UIImplementation`.
-
-## Limitations and Known Issues
-
-- `LayoutAnimation`s are not yet supported
-- `zIndex` is not yet supported
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/ShadowStyleSpan.java b/ReactAndroid/src/main/java/com/facebook/react/flat/ShadowStyleSpan.java
deleted file mode 100644
index a0435b409ba8..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/ShadowStyleSpan.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.text.TextPaint;
-import android.text.style.CharacterStyle;
-
-/* package */ final class ShadowStyleSpan extends CharacterStyle {
-
-  /* package */ static final ShadowStyleSpan INSTANCE = new ShadowStyleSpan(0, 0, 0, 0, true);
-
-  private float mDx;
-  private float mDy;
-  private float mRadius;
-  private int mColor;
-  private boolean mFrozen;
-
-  private ShadowStyleSpan(float dx, float dy, float radius, int color, boolean frozen) {
-    mDx = dx;
-    mDy = dy;
-    mRadius = radius;
-    mColor = color;
-    mFrozen = frozen;
-  }
-
-  public boolean offsetMatches(float dx, float dy) {
-    return mDx == dx && mDy == dy;
-  }
-
-  public void setOffset(float dx, float dy) {
-    mDx = dx;
-    mDy = dy;
-  }
-
-  public float getRadius() {
-    return mRadius;
-  }
-
-  public void setRadius(float radius) {
-    mRadius = radius;
-  }
-
-  public int getColor() {
-    return mColor;
-  }
-
-  public void setColor(int color) {
-    mColor = color;
-  }
-
-  /* package */ ShadowStyleSpan mutableCopy() {
-    return new ShadowStyleSpan(mDx, mDy, mRadius, mColor, false);
-  }
-
-  /* package */ boolean isFrozen() {
-    return mFrozen;
-  }
-
-  /* package */ void freeze() {
-    mFrozen = true;
-  }
-
-  @Override
-  public void updateDrawState(TextPaint textPaint) {
-    textPaint.setShadowLayer(mRadius, mDx, mDy, mColor);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/StateBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/flat/StateBuilder.java
deleted file mode 100644
index 301a488581c8..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/StateBuilder.java
+++ /dev/null
@@ -1,729 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import java.util.ArrayList;
-
-import android.util.SparseIntArray;
-
-import com.facebook.react.bridge.ReadableArray;
-import com.facebook.react.uimanager.OnLayoutEvent;
-import com.facebook.react.uimanager.Spacing;
-import com.facebook.react.uimanager.ReactShadowNode;
-import com.facebook.react.uimanager.ReactStylesDiffMap;
-import com.facebook.react.uimanager.UIViewOperationQueue;
-import com.facebook.react.uimanager.events.EventDispatcher;
-
-/**
- * Shadow node hierarchy by itself cannot display UI, it is only a representation of what UI should
- * be from JavaScript perspective. StateBuilder is a helper class that walks the shadow node tree
- * and collects information into an operation queue that is run on the UI thread and applied to the
- * non-shadow hierarchy of Views that Android can finally display.
- */
-/* package */ final class StateBuilder {
-  /* package */ static final float[] EMPTY_FLOAT_ARRAY = new float[0];
-  /* package */ static final SparseIntArray EMPTY_SPARSE_INT = new SparseIntArray();
-
-  private static final boolean SKIP_UP_TO_DATE_NODES = true;
-
-  // Optimization to avoid re-allocating zero length arrays.
-  private static final int[] EMPTY_INT_ARRAY = new int[0];
-
-  private final FlatUIViewOperationQueue mOperationsQueue;
-
-  private final ElementsList<DrawCommand> mDrawCommands =
-      new ElementsList<>(DrawCommand.EMPTY_ARRAY);
-  private final ElementsList<AttachDetachListener> mAttachDetachListeners =
-      new ElementsList<>(AttachDetachListener.EMPTY_ARRAY);
-  private final ElementsList<NodeRegion> mNodeRegions =
-      new ElementsList<>(NodeRegion.EMPTY_ARRAY);
-  private final ElementsList<FlatShadowNode> mNativeChildren =
-      new ElementsList<>(FlatShadowNode.EMPTY_ARRAY);
-
-  private final ArrayList<FlatShadowNode> mViewsToDetachAllChildrenFrom = new ArrayList<>();
-  private final ArrayList<FlatShadowNode> mViewsToDetach = new ArrayList<>();
-  private final ArrayList<Integer> mViewsToDrop = new ArrayList<>();
-  private final ArrayList<Integer> mParentsForViewsToDrop = new ArrayList<>();
-  private final ArrayList<OnLayoutEvent> mOnLayoutEvents = new ArrayList<>();
-  private final ArrayList<UIViewOperationQueue.UIOperation> mUpdateViewBoundsOperations =
-      new ArrayList<>();
-  private final ArrayList<UIViewOperationQueue.UIOperation> mViewManagerCommands =
-      new ArrayList<>();
-
-  private @Nullable FlatUIViewOperationQueue.DetachAllChildrenFromViews mDetachAllChildrenFromViews;
-
-  /* package */ StateBuilder(FlatUIViewOperationQueue operationsQueue) {
-    mOperationsQueue = operationsQueue;
-  }
-
-  /* package */ FlatUIViewOperationQueue getOperationsQueue() {
-    return mOperationsQueue;
-  }
-
-  /**
-   * Given a root of the laid-out shadow node hierarchy, walks the tree and generates arrays from
-   * element lists that are mounted in the UI thread to FlatViewGroups to handle drawing, touch,
-   * and other logic.
-   */
-  /* package */ void applyUpdates(FlatShadowNode node) {
-    float width = node.getLayoutWidth();
-    float height = node.getLayoutHeight();
-    float left = node.getLayoutX();
-    float top = node.getLayoutY();
-    float right = left + width;
-    float bottom = top + height;
-
-    collectStateForMountableNode(
-        node,
-        left,
-        top,
-        right,
-        bottom,
-        Float.NEGATIVE_INFINITY,
-        Float.NEGATIVE_INFINITY,
-        Float.POSITIVE_INFINITY,
-        Float.POSITIVE_INFINITY);
-
-    updateViewBounds(node, left, top, right, bottom);
-  }
-
-  /**
-   * Run after the shadow node hierarchy is updated.  Detaches all children from Views that are
-   * changing their native children, updates views, and dispatches commands before discarding any
-   * dropped views.
-   *
-   * @param eventDispatcher Dispatcher for onLayout events.
-   */
-  void afterUpdateViewHierarchy(EventDispatcher eventDispatcher) {
-    if (mDetachAllChildrenFromViews != null) {
-      int[] viewsToDetachAllChildrenFrom = collectViewTags(mViewsToDetachAllChildrenFrom);
-      mViewsToDetachAllChildrenFrom.clear();
-
-      mDetachAllChildrenFromViews.setViewsToDetachAllChildrenFrom(viewsToDetachAllChildrenFrom);
-      mDetachAllChildrenFromViews = null;
-    }
-
-    for (int i = 0, size = mUpdateViewBoundsOperations.size(); i != size; ++i) {
-      mOperationsQueue.enqueueFlatUIOperation(mUpdateViewBoundsOperations.get(i));
-    }
-    mUpdateViewBoundsOperations.clear();
-
-    // Process view manager commands after bounds operations, so that any UI operations have already
-    // happened before we actually dispatch the view manager command.  This prevents things like
-    // commands going to empty parents and views not yet being created.
-    for (int i = 0, size = mViewManagerCommands.size(); i != size; i++) {
-      mOperationsQueue.enqueueFlatUIOperation(mViewManagerCommands.get(i));
-    }
-    mViewManagerCommands.clear();
-
-    // This could be more efficient if EventDispatcher had a batch mode
-    // to avoid multiple synchronized calls.
-    for (int i = 0, size = mOnLayoutEvents.size(); i != size; ++i) {
-      eventDispatcher.dispatchEvent(mOnLayoutEvents.get(i));
-    }
-    mOnLayoutEvents.clear();
-
-    if (mViewsToDrop.size() > 0) {
-      mOperationsQueue.enqueueDropViews(mViewsToDrop, mParentsForViewsToDrop);
-      mViewsToDrop.clear();
-      mParentsForViewsToDrop.clear();
-    }
-
-    mOperationsQueue.enqueueProcessLayoutRequests();
-  }
-
-  /* package */ void removeRootView(int rootViewTag) {
-    // Note root view tags with a negative value.
-    mViewsToDrop.add(-rootViewTag);
-    mParentsForViewsToDrop.add(-1);
-  }
-
-  /**
-   * Adds a draw command to the element list for the current scope.  Allows collectState within the
-   * shadow node to add commands.
-   *
-   * @param drawCommand The draw command to add.
-   */
-  /* package */ void addDrawCommand(AbstractDrawCommand drawCommand) {
-    mDrawCommands.add(drawCommand);
-  }
-
-  /**
-   * Adds a listener to the element list for the current scope.  Allows collectState within the
-   * shadow node to add listeners.
-   *
-   * @param listener The listener to add
-   */
-  /* package */ void addAttachDetachListener(AttachDetachListener listener) {
-    mAttachDetachListeners.add(listener);
-  }
-
-  /**
-   * Adds a command for a view manager to the queue.  We have to delay adding it to the operations
-   * queue until we have added our view moves, creations and updates.
-   *
-   * @param reactTag The react tag of the command target.
-   * @param commandId ID of the command.
-   * @param commandArgs Arguments for the command.
-   */
-  /* package */ void enqueueViewManagerCommand(
-      int reactTag,
-      int commandId,
-      ReadableArray commandArgs) {
-    mViewManagerCommands.add(
-        mOperationsQueue.createViewManagerCommand(reactTag, commandId, commandArgs));
-  }
-
-  /**
-   * Create a backing view for a node, or update the backing view if it has already been created.
-   *
-   * @param node The node to create the backing view for.
-   * @param styles Styles for the view.
-   */
-  /* package */ void enqueueCreateOrUpdateView(
-      FlatShadowNode node,
-      @Nullable ReactStylesDiffMap styles) {
-    if (node.isBackingViewCreated()) {
-      // If the View is already created, make sure to propagate the new styles.
-      mOperationsQueue.enqueueUpdateProperties(
-          node.getReactTag(),
-          node.getViewClass(),
-          styles);
-    } else {
-      mOperationsQueue.enqueueCreateView(
-          node.getThemedContext(),
-          node.getReactTag(),
-          node.getViewClass(),
-          styles);
-
-      node.signalBackingViewIsCreated();
-    }
-  }
-
-  /**
-   * Create a backing view for a node if not already created.
-   *
-   * @param node The node to create the backing view for.
-   */
-  /* package */ void ensureBackingViewIsCreated(FlatShadowNode node) {
-    if (node.isBackingViewCreated()) {
-      return;
-    }
-
-    int tag = node.getReactTag();
-    mOperationsQueue.enqueueCreateView(node.getThemedContext(), tag, node.getViewClass(), null);
-
-    node.signalBackingViewIsCreated();
-  }
-
-  /**
-   * Enqueue dropping of the view for a node that has a backing view.  Used in conjunction with
-   * remove the node from the shadow hierarchy.
-   *
-   * @param node The node to drop the backing view for.
-   */
-  /* package */ void dropView(FlatShadowNode node, int parentReactTag) {
-    mViewsToDrop.add(node.getReactTag());
-    mParentsForViewsToDrop.add(parentReactTag);
-  }
-
-  /**
-   * Adds a node region to the element list for the current scope.  Allows collectState to add
-   * regions.
-   *
-   * @param node The node to add a region for.
-   * @param left Bound of the region.
-   * @param top Bound of the region.
-   * @param right Bound of the region.
-   * @param bottom Bound of the region.
-   * @param isVirtual True if the region does not map to a native view.  Used to determine touch
-   *   targets.
-   */
-  private void addNodeRegion(
-      FlatShadowNode node,
-      float left,
-      float top,
-      float right,
-      float bottom,
-      boolean isVirtual) {
-    if (left == right || top == bottom) {
-      // no point in adding an empty NodeRegion
-      return;
-    }
-
-    node.updateNodeRegion(left, top, right, bottom, isVirtual);
-    if (node.doesDraw()) {
-      mNodeRegions.add(node.getNodeRegion());
-    }
-  }
-
-  /**
-   * Adds a native child to the element list for the current scope.  Allows collectState to add
-   * native children.
-   *
-   * @param nativeChild The view-backed native child to add.
-   */
-  private void addNativeChild(FlatShadowNode nativeChild) {
-    mNativeChildren.add(nativeChild);
-  }
-
-  /**
-   * Updates boundaries of a View that a give nodes maps to.
-   */
-  private void updateViewBounds(
-      FlatShadowNode node,
-      float left,
-      float top,
-      float right,
-      float bottom) {
-    int viewLeft = Math.round(left);
-    int viewTop = Math.round(top);
-    int viewRight = Math.round(right);
-    int viewBottom = Math.round(bottom);
-    if (node.getViewLeft() == viewLeft && node.getViewTop() == viewTop &&
-        node.getViewRight() == viewRight && node.getViewBottom() == viewBottom) {
-      // nothing changed.
-      return;
-    }
-
-    // this will optionally measure and layout the View this node maps to.
-    node.setViewBounds(viewLeft, viewTop, viewRight, viewBottom);
-    int tag = node.getReactTag();
-
-    mUpdateViewBoundsOperations.add(
-        mOperationsQueue.createUpdateViewBounds(tag, viewLeft, viewTop, viewRight, viewBottom));
-  }
-
-  /**
-   * Collects state (Draw commands, listeners, regions, native children) for a given node that will
-   * mount to a View. Returns true if this node or any of its descendants that mount to View
-   * generated any updates.
-   */
-  private boolean collectStateForMountableNode(
-      FlatShadowNode node,
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom) {
-    boolean hasUpdates = node.hasNewLayout();
-
-    boolean expectingUpdate = hasUpdates || node.isUpdated() || node.hasUnseenUpdates() ||
-        node.clipBoundsChanged(clipLeft, clipTop, clipRight, clipBottom);
-    if (SKIP_UP_TO_DATE_NODES && !expectingUpdate) {
-      return false;
-    }
-
-    node.setClipBounds(clipLeft, clipTop, clipRight, clipBottom);
-
-    mDrawCommands.start(node.getDrawCommands());
-    mAttachDetachListeners.start(node.getAttachDetachListeners());
-    mNodeRegions.start(node.getNodeRegions());
-    mNativeChildren.start(node.getNativeChildren());
-
-    boolean isAndroidView = false;
-    boolean needsCustomLayoutForChildren = false;
-    if (node instanceof AndroidView) {
-      AndroidView androidView = (AndroidView) node;
-      updateViewPadding(androidView, node.getReactTag());
-
-      isAndroidView = true;
-      needsCustomLayoutForChildren = androidView.needsCustomLayoutForChildren();
-
-      // AndroidView might scroll (e.g. ScrollView) so we need to reset clip bounds here
-      // Otherwise, we might scroll clipped content. If AndroidView doesn't scroll, this is still
-      // harmless, because AndroidView will do its own clipping anyway.
-      clipLeft = Float.NEGATIVE_INFINITY;
-      clipTop = Float.NEGATIVE_INFINITY;
-      clipRight = Float.POSITIVE_INFINITY;
-      clipBottom = Float.POSITIVE_INFINITY;
-    }
-
-    if (!isAndroidView && node.isVirtualAnchor()) {
-      // If RCTText is mounted to View, virtual children will not receive any touch events
-      // because they don't get added to nodeRegions, so nodeRegions will be empty and
-      // FlatViewGroup.reactTagForTouch() will always return RCTText's id. To fix the issue,
-      // manually add nodeRegion so it will have exactly one NodeRegion, and virtual nodes will
-      // be able to receive touch events.
-      addNodeRegion(node, left, top, right, bottom, true);
-    }
-
-    boolean descendantUpdated = collectStateRecursively(
-        node,
-        left,
-        top,
-        right,
-        bottom,
-        clipLeft,
-        clipTop,
-        clipRight,
-        clipBottom,
-        isAndroidView,
-        needsCustomLayoutForChildren);
-
-    boolean shouldUpdateMountState = false;
-    final DrawCommand[] drawCommands = mDrawCommands.finish();
-    if (drawCommands != null) {
-      shouldUpdateMountState = true;
-      node.setDrawCommands(drawCommands);
-    }
-
-    final AttachDetachListener[] listeners = mAttachDetachListeners.finish();
-    if (listeners != null) {
-      shouldUpdateMountState = true;
-      node.setAttachDetachListeners(listeners);
-    }
-
-    final NodeRegion[] nodeRegions = mNodeRegions.finish();
-    if (nodeRegions != null) {
-      shouldUpdateMountState = true;
-      node.setNodeRegions(nodeRegions);
-    } else if (descendantUpdated) {
-      // one of the descendant's value for overflows container may have changed, so
-      // we still need to update ours.
-      node.updateOverflowsContainer();
-    }
-
-    // We need to finish the native children so that we can process clipping FlatViewGroup.
-    final FlatShadowNode[] nativeChildren = mNativeChildren.finish();
-    if (shouldUpdateMountState) {
-      if (node.clipsSubviews()) {
-        // Node is a clipping FlatViewGroup, so lets do some calculations off the UI thread.
-        // DrawCommandManager has a better explanation of the data incoming from these calculations,
-        // and is where they are actually used.
-        float[] commandMaxBottom = EMPTY_FLOAT_ARRAY;
-        float[] commandMinTop = EMPTY_FLOAT_ARRAY;
-        SparseIntArray drawViewIndexMap = EMPTY_SPARSE_INT;
-        if (drawCommands != null) {
-          drawViewIndexMap = new SparseIntArray();
-
-          commandMaxBottom = new float[drawCommands.length];
-          commandMinTop = new float[drawCommands.length];
-
-          if (node.isHorizontal()) {
-            HorizontalDrawCommandManager
-                .fillMaxMinArrays(drawCommands, commandMaxBottom, commandMinTop, drawViewIndexMap);
-          } else {
-            VerticalDrawCommandManager
-                .fillMaxMinArrays(drawCommands, commandMaxBottom, commandMinTop, drawViewIndexMap);
-          }
-        }
-        float[] regionMaxBottom = EMPTY_FLOAT_ARRAY;
-        float[] regionMinTop = EMPTY_FLOAT_ARRAY;
-        if (nodeRegions != null) {
-          regionMaxBottom = new float[nodeRegions.length];
-          regionMinTop = new float[nodeRegions.length];
-
-          if (node.isHorizontal()) {
-            HorizontalDrawCommandManager
-                .fillMaxMinArrays(nodeRegions, regionMaxBottom, regionMinTop);
-          } else {
-            VerticalDrawCommandManager
-                .fillMaxMinArrays(nodeRegions, regionMaxBottom, regionMinTop);
-          }
-        }
-
-        boolean willMountViews = nativeChildren != null;
-        mOperationsQueue.enqueueUpdateClippingMountState(
-            node.getReactTag(),
-            drawCommands,
-            drawViewIndexMap,
-            commandMaxBottom,
-            commandMinTop,
-            listeners,
-            nodeRegions,
-            regionMaxBottom,
-            regionMinTop,
-            willMountViews);
-      } else {
-        mOperationsQueue.enqueueUpdateMountState(
-            node.getReactTag(),
-            drawCommands,
-            listeners,
-            nodeRegions);
-      }
-    }
-
-    if (node.hasUnseenUpdates()) {
-      node.onCollectExtraUpdates(mOperationsQueue);
-      node.markUpdateSeen();
-    }
-
-    if (nativeChildren != null) {
-      updateNativeChildren(node, node.getNativeChildren(), nativeChildren);
-    }
-
-    boolean updated = shouldUpdateMountState || nativeChildren != null || descendantUpdated;
-
-    if (!expectingUpdate && updated) {
-      throw new RuntimeException("Node " + node.getReactTag() + " updated unexpectedly.");
-    }
-
-    return updated;
-  }
-
-  /**
-   * Handles updating the children of a node when they change.  Updates the shadow node and
-   * enqueues state updates that will eventually be run on the UI thread.
-   *
-   * @param node The node to update native children for.
-   * @param oldNativeChildren The previously mounted native children.
-   * @param newNativeChildren The newly mounted native children.
-   */
-  private void updateNativeChildren(
-      FlatShadowNode node,
-      FlatShadowNode[] oldNativeChildren,
-      FlatShadowNode[] newNativeChildren) {
-
-    node.setNativeChildren(newNativeChildren);
-
-    if (mDetachAllChildrenFromViews == null) {
-      mDetachAllChildrenFromViews = mOperationsQueue.enqueueDetachAllChildrenFromViews();
-    }
-
-    if (oldNativeChildren.length != 0) {
-      mViewsToDetachAllChildrenFrom.add(node);
-    }
-
-    int tag = node.getReactTag();
-    int numViewsToAdd = newNativeChildren.length;
-    final int[] viewsToAdd;
-    if (numViewsToAdd == 0) {
-      viewsToAdd = EMPTY_INT_ARRAY;
-    } else {
-      viewsToAdd = new int[numViewsToAdd];
-      int i = 0;
-      for (FlatShadowNode child : newNativeChildren) {
-        if (child.getNativeParentTag() == tag) {
-          viewsToAdd[i] = -child.getReactTag();
-        } else {
-          viewsToAdd[i] = child.getReactTag();
-        }
-        // all views we add are first start detached
-        child.setNativeParentTag(-1);
-        ++i;
-      }
-    }
-
-    // Populate an array of views to detach.
-    // These views still have their native parent set as opposed to being reset to -1
-    for (FlatShadowNode child : oldNativeChildren) {
-      if (child.getNativeParentTag() == tag) {
-        // View is attached to old parent and needs to be removed.
-        mViewsToDetach.add(child);
-        child.setNativeParentTag(-1);
-      }
-    }
-
-    final int[] viewsToDetach = collectViewTags(mViewsToDetach);
-    mViewsToDetach.clear();
-
-    // restore correct parent tag
-    for (FlatShadowNode child : newNativeChildren) {
-      child.setNativeParentTag(tag);
-    }
-
-    mOperationsQueue.enqueueUpdateViewGroup(tag, viewsToAdd, viewsToDetach);
-  }
-
-  /**
-   * Recursively walks node tree from a given node and collects draw commands, listeners, node
-   * regions and native children.  Calls collect state on the node, then processNodeAndCollectState
-   * for the recursion.
-   */
-  private boolean collectStateRecursively(
-      FlatShadowNode node,
-      float left,
-      float top,
-      float right,
-      float bottom,
-      float clipLeft,
-      float clipTop,
-      float clipRight,
-      float clipBottom,
-      boolean isAndroidView,
-      boolean needsCustomLayoutForChildren) {
-    if (node.hasNewLayout()) {
-      node.markLayoutSeen();
-    }
-
-    float roundedLeft = roundToPixel(left);
-    float roundedTop = roundToPixel(top);
-    float roundedRight = roundToPixel(right);
-    float roundedBottom = roundToPixel(bottom);
-
-    // notify JS about layout event if requested
-    if (node.shouldNotifyOnLayout()) {
-      OnLayoutEvent layoutEvent = node.obtainLayoutEvent(
-          Math.round(node.getLayoutX()),
-          Math.round(node.getLayoutY()),
-          (int) (roundedRight - roundedLeft),
-          (int) (roundedBottom - roundedTop));
-      if (layoutEvent != null) {
-        mOnLayoutEvents.add(layoutEvent);
-      }
-    }
-
-    if (node.clipToBounds()) {
-      clipLeft = Math.max(left, clipLeft);
-      clipTop = Math.max(top, clipTop);
-      clipRight = Math.min(right, clipRight);
-      clipBottom = Math.min(bottom, clipBottom);
-    }
-
-    node.collectState(
-        this,
-        roundedLeft,
-        roundedTop,
-        roundedRight,
-        roundedBottom,
-        roundToPixel(clipLeft),
-        roundToPixel(clipTop),
-        roundToPixel(clipRight),
-        clipBottom);
-
-    boolean updated = false;
-    for (int i = 0, childCount = node.getChildCount(); i != childCount; ++i) {
-      ReactShadowNode child = node.getChildAt(i);
-      if (child.isVirtual()) {
-        continue;
-      }
-
-      updated |= processNodeAndCollectState(
-          (FlatShadowNode) child,
-          left,
-          top,
-          clipLeft,
-          clipTop,
-          clipRight,
-          clipBottom,
-          isAndroidView,
-          needsCustomLayoutForChildren);
-    }
-
-    node.resetUpdated();
-
-    return updated;
-  }
-
-  /**
-   * Collects state and enqueues View boundary updates for a given node tree.  Returns true if
-   * this node or any of its descendants that mount to View generated any updates.
-   */
-  private boolean processNodeAndCollectState(
-      FlatShadowNode node,
-      float parentLeft,
-      float parentTop,
-      float parentClipLeft,
-      float parentClipTop,
-      float parentClipRight,
-      float parentClipBottom,
-      boolean parentIsAndroidView,
-      boolean needsCustomLayout) {
-    float width = node.getLayoutWidth();
-    float height = node.getLayoutHeight();
-
-    float left = parentLeft + node.getLayoutX();
-    float top = parentTop + node.getLayoutY();
-    float right = left + width;
-    float bottom = top + height;
-
-    boolean mountsToView = node.mountsToView();
-
-    final boolean updated;
-
-    if (!parentIsAndroidView) {
-      addNodeRegion(node, left, top, right, bottom, !mountsToView);
-    }
-
-    if (mountsToView) {
-      ensureBackingViewIsCreated(node);
-
-      addNativeChild(node);
-      updated = collectStateForMountableNode(
-          node,
-          0, // left - left
-          0, // top - top
-          right - left,
-          bottom - top,
-          parentClipLeft - left,
-          parentClipTop - top,
-          parentClipRight - left,
-          parentClipBottom - top);
-
-      if (!parentIsAndroidView) {
-        mDrawCommands.add(node.collectDrawView(
-            left,
-            top,
-            right,
-            bottom,
-            parentClipLeft,
-            parentClipTop,
-            parentClipRight,
-            parentClipBottom));
-      }
-
-      if (!needsCustomLayout) {
-        updateViewBounds(node, left, top, right, bottom);
-      }
-    } else {
-      updated = collectStateRecursively(
-          node,
-          left,
-          top,
-          right,
-          bottom,
-          parentClipLeft,
-          parentClipTop,
-          parentClipRight,
-          parentClipBottom,
-          false,
-          false);
-    }
-
-    return updated;
-  }
-
-  private void updateViewPadding(AndroidView androidView, int reactTag) {
-    if (androidView.isPaddingChanged()) {
-      mOperationsQueue.enqueueSetPadding(
-          reactTag,
-          Math.round(androidView.getPadding(Spacing.LEFT)),
-          Math.round(androidView.getPadding(Spacing.TOP)),
-          Math.round(androidView.getPadding(Spacing.RIGHT)),
-          Math.round(androidView.getPadding(Spacing.BOTTOM)));
-      androidView.resetPaddingChanged();
-    }
-  }
-
-  private static int[] collectViewTags(ArrayList<FlatShadowNode> views) {
-    int numViews = views.size();
-    if (numViews == 0) {
-      return EMPTY_INT_ARRAY;
-    }
-
-    int[] viewTags = new int[numViews];
-    for (int i = 0; i < numViews; ++i) {
-      viewTags[i] = views.get(i).getReactTag();
-    }
-
-    return viewTags;
-  }
-
-  /**
-   * This is what Math.round() does, except it returns float.
-   */
-  private static float roundToPixel(float pos) {
-    return (float) Math.floor(pos + 0.5f);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/TextNodeRegion.java b/ReactAndroid/src/main/java/com/facebook/react/flat/TextNodeRegion.java
deleted file mode 100644
index 9440ebc08351..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/TextNodeRegion.java
+++ /dev/null
@@ -1,84 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import android.text.Layout;
-import android.text.Spanned;
-
-/* package */ final class TextNodeRegion extends NodeRegion {
-  private @Nullable Layout mLayout;
-
-  /* package */ TextNodeRegion(
-      float left,
-      float top,
-      float right,
-      float bottom,
-      int tag,
-      boolean isVirtual,
-      @Nullable Layout layout) {
-    super(left, top, right, bottom, tag, isVirtual);
-    mLayout = layout;
-  }
-
-  public void setLayout(Layout layout) {
-    mLayout = layout;
-  }
-
-  /* package */ @Nullable Layout getLayout() {
-    return mLayout;
-  }
-
-  /* package */ int getReactTag(float touchX, float touchY) {
-    if (mLayout != null) {
-      CharSequence text = mLayout.getText();
-      if (text instanceof Spanned) {
-        int y = Math.round(touchY - getTop());
-        if (y >= mLayout.getLineTop(0) && y < mLayout.getLineBottom(mLayout.getLineCount() - 1)) {
-          float x = Math.round(touchX - getLeft());
-          int line = mLayout.getLineForVertical(y);
-
-          if (mLayout.getLineLeft(line) <= x && x <= mLayout.getLineRight(line)) {
-            int off = mLayout.getOffsetForHorizontal(line, x);
-
-            Spanned spanned = (Spanned) text;
-            RCTRawText[] link = spanned.getSpans(off, off, RCTRawText.class);
-
-            if (link.length != 0) {
-              return link[0].getReactTag();
-            }
-          }
-        }
-      }
-    }
-
-    return super.getReactTag(touchX, touchY);
-  }
-
-  @Override
-  boolean matchesTag(int tag) {
-    if (super.matchesTag(tag)) {
-      return true;
-    }
-
-    if (mLayout != null) {
-      CharSequence text = mLayout.getText();
-      if (text instanceof Spanned) {
-        Spanned spannedText = (Spanned) text;
-        RCTRawText[] spans = spannedText.getSpans(0, text.length(), RCTRawText.class);
-        for (RCTRawText span : spans) {
-          if (span.getReactTag() == tag) {
-            return true;
-          }
-        }
-      }
-    }
-    return false;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/TypefaceCache.java b/ReactAndroid/src/main/java/com/facebook/react/flat/TypefaceCache.java
deleted file mode 100644
index c684af4adaaa..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/TypefaceCache.java
+++ /dev/null
@@ -1,115 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import javax.annotation.Nullable;
-
-import java.util.HashMap;
-
-import android.content.res.AssetManager;
-import android.graphics.Typeface;
-
-import com.facebook.infer.annotation.Assertions;
-
-/**
- * TypefaceCache provides methods to resolve typeface from font family, or existing typeface
- * with a different style.
- */
-/* package */ final class TypefaceCache {
-
-  private static final int MAX_STYLES = 4; // NORMAL = 0, BOLD = 1, ITALIC = 2, BOLD_ITALIC = 3
-
-  private static final HashMap<String, Typeface[]> FONTFAMILY_CACHE = new HashMap<>();
-  private static final HashMap<Typeface, Typeface[]> TYPEFACE_CACHE = new HashMap<>();
-
-  private static final String[] EXTENSIONS = {
-      "",
-      "_bold",
-      "_italic",
-      "_bold_italic"};
-  private static final String[] FILE_EXTENSIONS = {".ttf", ".otf"};
-  private static final String FONTS_ASSET_PATH = "fonts/";
-
-  @Nullable private static AssetManager sAssetManager = null;
-
-  public static void setAssetManager(AssetManager assetManager) {
-    sAssetManager = assetManager;
-  }
-
-  /**
-   * Returns a Typeface for a given a FontFamily and style.
-   */
-  public static Typeface getTypeface(String fontFamily, int style) {
-    Typeface[] cache = FONTFAMILY_CACHE.get(fontFamily);
-    if (cache == null) {
-      // cache is empty, create one.
-      cache = new Typeface[MAX_STYLES];
-      FONTFAMILY_CACHE.put(fontFamily, cache);
-    } else if (cache[style] != null) {
-      // return cached value.
-      return cache[style];
-    }
-
-    Typeface typeface = createTypeface(fontFamily, style);
-    cache[style] = typeface;
-    TYPEFACE_CACHE.put(typeface, cache);
-    return typeface;
-  }
-
-  private static Typeface createTypeface(String fontFamilyName, int style) {
-    String extension = EXTENSIONS[style];
-    StringBuilder fileNameBuffer = new StringBuilder(32)
-        .append(FONTS_ASSET_PATH)
-        .append(fontFamilyName)
-        .append(extension);
-    int length = fileNameBuffer.length();
-    for (String fileExtension : FILE_EXTENSIONS) {
-      String fileName = fileNameBuffer.append(fileExtension).toString();
-      try {
-        return Typeface.createFromAsset(sAssetManager, fileName);
-      } catch (RuntimeException e) {
-        // unfortunately Typeface.createFromAsset throws an exception instead of returning null
-        // if the typeface doesn't exist
-        fileNameBuffer.setLength(length);
-      }
-    }
-    return Assertions.assumeNotNull(Typeface.create(fontFamilyName, style));
-  }
-
-  /**
-   * Returns a derivative of a given Typeface with a different style.
-   */
-  public static Typeface getTypeface(Typeface typeface, int style) {
-    if (typeface == null) {
-      return Typeface.defaultFromStyle(style);
-    }
-
-    Typeface[] cache = TYPEFACE_CACHE.get(typeface);
-    if (cache == null) {
-      // This should not happen because all Typefaces are coming from TypefaceCache,
-      // and thus should be registered in TYPEFACE_CACHE.
-      // If we get here, it's a bug and one of the 2 scenarios happened:
-      // a) TypefaceCache created a Typeface and didn't put it into TYPEFACE_CACHE.
-      // b) someone else created a Typeface bypassing TypefaceCache so it's not registered here.
-      //
-      // If it's not registered, we can just register it manually for consistency, and so that
-      // next time someone requests a un unknown Typeface, it's already cached and we don't create
-      // extra copies.
-      cache = new Typeface[MAX_STYLES];
-      cache[typeface.getStyle()] = typeface;
-    } else if (cache[style] != null) {
-      // return cached value.
-      return cache[style];
-    }
-
-    typeface = Typeface.create(typeface, style);
-    cache[style] = typeface;
-    TYPEFACE_CACHE.put(typeface, cache);
-    return typeface;
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/VerticalDrawCommandManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/VerticalDrawCommandManager.java
deleted file mode 100644
index 9cf730fcbc44..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/VerticalDrawCommandManager.java
+++ /dev/null
@@ -1,124 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import java.util.Arrays;
-
-import android.util.SparseIntArray;
-
-/**
- * {@link DrawCommandManager} with vertical clipping (The view scrolls up and down).
- */
-/* package */ final class VerticalDrawCommandManager extends ClippingDrawCommandManager {
-
-  /* package */ VerticalDrawCommandManager(
-      FlatViewGroup flatViewGroup,
-      DrawCommand[] drawCommands) {
-    super(flatViewGroup, drawCommands);
-  }
-
-  @Override
-  int commandStartIndex() {
-    int start = Arrays.binarySearch(mCommandMaxBottom, mClippingRect.top);
-    // We don't care whether we matched or not, but positive indices are helpful. The binary search
-    // returns ~index in the case that it isn't a match, so reverse that here.
-    return start < 0 ? ~start : start;
-  }
-
-  @Override
-  int commandStopIndex(int start) {
-    int stop = Arrays.binarySearch(
-        mCommandMinTop,
-        start,
-        mCommandMinTop.length,
-        mClippingRect.bottom);
-    // We don't care whether we matched or not, but positive indices are helpful. The binary search
-    // returns ~index in the case that it isn't a match, so reverse that here.
-    return stop < 0 ? ~stop : stop;
-  }
-
-  @Override
-  int regionStopIndex(float touchX, float touchY) {
-    int stop = Arrays.binarySearch(mRegionMinTop, touchY + 0.0001f);
-    // We don't care whether we matched or not, but positive indices are helpful. The binary search
-    // returns ~index in the case that it isn't a match, so reverse that here.
-    return stop < 0 ? ~stop : stop;
-  }
-
-  @Override
-  boolean regionAboveTouch(int index, float touchX, float touchY) {
-    return mRegionMaxBottom[index] < touchY;
-  }
-
-  /**
-   * Populates the max and min arrays for a given set of node regions.
-   *
-   * This should never be called from the UI thread, as the reason it exists is to do work off the
-   * UI thread.
-   *
-   * @param regions The regions that will eventually be mounted.
-   * @param maxBottom  At each index i, the maximum bottom value of all regions at or below i.
-   * @param minTop  At each index i, the minimum top value of all regions at or below i.
-   */
-  public static void fillMaxMinArrays(NodeRegion[] regions, float[] maxBottom, float[] minTop) {
-    float last = 0;
-    for (int i = 0; i < regions.length; i++) {
-      last = Math.max(last, regions[i].getTouchableBottom());
-      maxBottom[i] = last;
-    }
-    for (int i = regions.length - 1; i >= 0; i--) {
-      last = Math.min(last, regions[i].getTouchableTop());
-      minTop[i] = last;
-    }
-  }
-
-  /**
-   * Populates the max and min arrays for a given set of draw commands.  Also populates a mapping of
-   * react tags to their index position in the command array.
-   *
-   * This should never be called from the UI thread, as the reason it exists is to do work off the
-   * UI thread.
-   *
-   * @param commands The draw commands that will eventually be mounted.
-   * @param maxBottom At each index i, the maximum bottom value of all draw commands at or below i.
-   * @param minTop At each index i, the minimum top value of all draw commands at or below i.
-   * @param drawViewIndexMap Mapping of ids to index position within the draw command array.
-   */
-  public static void fillMaxMinArrays(
-      DrawCommand[] commands,
-      float[] maxBottom,
-      float[] minTop,
-      SparseIntArray drawViewIndexMap) {
-    float last = 0;
-    // Loop through the DrawCommands, keeping track of the maximum we've seen if we only iterated
-    // through items up to this position.
-    for (int i = 0; i < commands.length; i++) {
-      if (commands[i] instanceof DrawView) {
-        DrawView drawView = (DrawView) commands[i];
-        // These will generally be roughly sorted by id, so try to insert at the end if possible.
-        drawViewIndexMap.append(drawView.reactTag, i);
-        last = Math.max(last, drawView.mLogicalBottom);
-      } else {
-        last = Math.max(last, commands[i].getBottom());
-      }
-      maxBottom[i] = last;
-    }
-    // Intentionally leave last as it was, since it's at the maximum bottom position we've seen so
-    // far, we can use it again.
-
-    // Loop through backwards, keeping track of the minimum we've seen at this position.
-    for (int i = commands.length - 1; i >= 0; i--) {
-      if (commands[i] instanceof DrawView) {
-        last = Math.min(last, ((DrawView) commands[i]).mLogicalTop);
-      } else {
-        last = Math.min(last, commands[i].getTop());
-      }
-      minTop[i] = last;
-    }
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/ViewResolver.java b/ReactAndroid/src/main/java/com/facebook/react/flat/ViewResolver.java
deleted file mode 100644
index 1d742ec8f1ee..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/ViewResolver.java
+++ /dev/null
@@ -1,14 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.view.View;
-
-public interface ViewResolver {
-  public View getView(int tag);
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/flat/VirtualViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/flat/VirtualViewManager.java
deleted file mode 100644
index dc382fea10f9..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/flat/VirtualViewManager.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.flat;
-
-import android.view.View;
-
-import com.facebook.react.uimanager.ThemedReactContext;
-import com.facebook.react.uimanager.ViewManager;
-
-/**
- * Base class to ViewManagers that don't map to a View.
- */
-abstract class VirtualViewManager<C extends FlatShadowNode> extends ViewManager<View, C> {
-  @Override
-  protected View createViewInstance(ThemedReactContext reactContext) {
-    throw new RuntimeException(getName() + " doesn't map to a View");
-  }
-
-  @Override
-  public void updateExtraData(View root, Object extraData) {
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/shell/BUCK b/ReactAndroid/src/main/java/com/facebook/react/shell/BUCK
index 93d4cab86b29..c7293b6cd400 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/shell/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/shell/BUCK
@@ -19,7 +19,6 @@ rn_android_library(
         react_native_target("java/com/facebook/react/bridge:bridge"),
         react_native_target("java/com/facebook/react/common:common"),
         react_native_target("java/com/facebook/react/devsupport:devsupport"),
-        react_native_target("java/com/facebook/react/flat:flat"),
         react_native_target("java/com/facebook/react/module/model:model"),
         react_native_target("java/com/facebook/react/modules/accessibilityinfo:accessibilityinfo"),
         react_native_target("java/com/facebook/react/modules/appstate:appstate"),
diff --git a/ReactAndroid/src/main/java/com/facebook/react/shell/MainReactPackage.java b/ReactAndroid/src/main/java/com/facebook/react/shell/MainReactPackage.java
index aa8193d08e4d..5e1ebd5c33a9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/shell/MainReactPackage.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/shell/MainReactPackage.java
@@ -7,23 +7,11 @@
 
 package com.facebook.react.shell;
 
-import android.content.SharedPreferences;
-import android.preference.PreferenceManager;
 import com.facebook.react.LazyReactPackage;
 import com.facebook.react.animated.NativeAnimatedModule;
 import com.facebook.react.bridge.ModuleSpec;
 import com.facebook.react.bridge.NativeModule;
 import com.facebook.react.bridge.ReactApplicationContext;
-import com.facebook.react.flat.FlatARTSurfaceViewManager;
-import com.facebook.react.flat.RCTImageViewManager;
-import com.facebook.react.flat.RCTModalHostManager;
-import com.facebook.react.flat.RCTRawTextManager;
-import com.facebook.react.flat.RCTTextInlineImageManager;
-import com.facebook.react.flat.RCTTextInputManager;
-import com.facebook.react.flat.RCTTextManager;
-import com.facebook.react.flat.RCTViewManager;
-import com.facebook.react.flat.RCTViewPagerManager;
-import com.facebook.react.flat.RCTVirtualTextManager;
 import com.facebook.react.module.model.ReactModuleInfoProvider;
 import com.facebook.react.modules.accessibilityinfo.AccessibilityInfoModule;
 import com.facebook.react.modules.appstate.AppStateModule;
@@ -332,33 +320,17 @@ public List<ViewManager> createViewManagers(ReactApplicationContext reactContext
     viewManagers.add(new ReactWebViewManager());
     viewManagers.add(new SwipeRefreshLayoutManager());
 
-    SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(reactContext);
-    boolean useFlatUi = preferences.getBoolean("flat_uiimplementation", false);
-    if (useFlatUi) {
-      // Flat managers
-      viewManagers.add(new FlatARTSurfaceViewManager());
-      viewManagers.add(new RCTTextInlineImageManager());
-      viewManagers.add(new RCTImageViewManager());
-      viewManagers.add(new RCTModalHostManager());
-      viewManagers.add(new RCTRawTextManager());
-      viewManagers.add(new RCTTextInputManager());
-      viewManagers.add(new RCTTextManager());
-      viewManagers.add(new RCTViewManager());
-      viewManagers.add(new RCTViewPagerManager());
-      viewManagers.add(new RCTVirtualTextManager());
-    } else {
-      // Native equivalents
-      viewManagers.add(new ARTSurfaceViewManager());
-      viewManagers.add(new FrescoBasedReactTextInlineImageViewManager());
-      viewManagers.add(new ReactImageManager());
-      viewManagers.add(new ReactModalHostManager());
-      viewManagers.add(new ReactRawTextManager());
-      viewManagers.add(new ReactTextInputManager());
-      viewManagers.add(new ReactTextViewManager());
-      viewManagers.add(new ReactViewManager());
-      viewManagers.add(new ReactViewPagerManager());
-      viewManagers.add(new ReactVirtualTextViewManager());
-    }
+    // Native equivalents
+    viewManagers.add(new ARTSurfaceViewManager());
+    viewManagers.add(new FrescoBasedReactTextInlineImageViewManager());
+    viewManagers.add(new ReactImageManager());
+    viewManagers.add(new ReactModalHostManager());
+    viewManagers.add(new ReactRawTextManager());
+    viewManagers.add(new ReactTextInputManager());
+    viewManagers.add(new ReactTextViewManager());
+    viewManagers.add(new ReactViewManager());
+    viewManagers.add(new ReactViewPagerManager());
+    viewManagers.add(new ReactVirtualTextViewManager());
 
     return viewManagers;
   }

From 506f92083806e91a90d9a213bcdd05ab3b2ba888 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 26 Jun 2018 23:44:57 -0700
Subject: [PATCH 0936/1109] Remove UIImplementationProvider class and refactor
 UIManagerModule

Summary:
@public
This diff deprecates and deletes the UIImplementationProvider class.

It is not required to create an UIImplementation provider anymore, from now on the UIImplementation is created inside the UIManagerModule.

If you are using the UIImplementationProvider to create a ReactInstanceManager
e.g.:

```
    ReactInstanceManager =
        getReactInstanceManagerBuilder()
            ...
            .setUIImplementationProvider(...)
            ...
            .build();
```

Then you should just remove that line:
```
    ReactInstanceManager =
        getReactInstanceManagerBuilder()
            .set.....
            .build();
```

Reviewed By: achen1

Differential Revision: D8650376

fbshipit-source-id: 8d883295d8bf6578a99685edf6a2a84c6d0df0cf
---
 .../react/testing/ReactAppTestActivity.java   | 37 +++--------------
 ...alystNativeJSToJavaParametersTestCase.java |  3 +-
 ...talystNativeJavaToJSArgumentsTestCase.java |  3 +-
 ...ystNativeJavaToJSReturnValuesTestCase.java |  3 +-
 .../tests/CatalystUIManagerTestCase.java      |  3 +-
 .../facebook/react/tests/JSLocaleTest.java    | 15 +++----
 .../react/tests/ProgressBarTestCase.java      |  3 +-
 .../react/tests/ViewRenderingTestCase.java    |  3 +-
 .../facebook/react/CoreModulesPackage.java    |  6 ---
 .../facebook/react/ReactInstanceManager.java  |  4 --
 .../react/ReactInstanceManagerBuilder.java    | 22 +---------
 .../com/facebook/react/ReactNativeHost.java   | 21 ++--------
 .../uimanager/UIImplementationProvider.java   | 40 -------------------
 .../react/uimanager/UIManagerModule.java      |  6 +--
 .../uimanager/ReactPropConstantsTest.java     |  2 +-
 .../UIManagerModuleConstantsTest.java         | 23 +++--------
 .../react/uimanager/UIManagerModuleTest.java  |  2 +-
 .../react/views/text/ReactTextTest.java       |  3 +-
 .../react/views/textinput/TextInputTest.java  |  3 +-
 19 files changed, 35 insertions(+), 167 deletions(-)
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementationProvider.java

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index 77b211217796..5ca48fcf6437 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -37,11 +37,10 @@
 import com.facebook.react.shell.MainReactPackage;
 import com.facebook.react.testing.idledetection.ReactBridgeIdleSignaler;
 import com.facebook.react.testing.idledetection.ReactIdleDetectionUtil;
-import com.facebook.react.uimanager.events.EventDispatcher;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewManagerRegistry;
+import com.facebook.react.uimanager.events.EventDispatcher;
 import java.util.Arrays;
 import java.util.List;
 import java.util.concurrent.CountDownLatch;
@@ -139,16 +138,11 @@ public void loadApp(String appKey, ReactInstanceSpecForTest spec, boolean enable
     loadApp(appKey, spec, null, DEFAULT_BUNDLE_NAME, enableDevSupport);
   }
 
-  public void loadApp(String appKey, ReactInstanceSpecForTest spec, String bundleName) {
-    loadApp(appKey, spec, null, bundleName, false /* = useDevSupport */);
-  }
-
   public void loadApp(
     String appKey,
     ReactInstanceSpecForTest spec,
-    String bundleName,
-    UIImplementationProvider uiImplementationProvider) {
-    loadApp(appKey, spec, null, bundleName, false /* = useDevSupport */, uiImplementationProvider);
+    String bundleName) {
+    loadApp(appKey, spec, null, bundleName, false /* = useDevSupport */);
   }
 
   public void resetRootViewForScreenshotTests() {
@@ -165,23 +159,13 @@ public void resetRootViewForScreenshotTests() {
     mScreenshotingFrameLayout.addView(mReactRootView);
   }
 
-  public void loadApp(
-      String appKey,
-      ReactInstanceSpecForTest spec,
-      @Nullable Bundle initialProps,
-      String bundleName,
-      boolean useDevSupport) {
-    loadApp(appKey, spec, initialProps, bundleName, useDevSupport, null);
-  }
-
   public void loadApp(
     String appKey,
     ReactInstanceSpecForTest spec,
     @Nullable Bundle initialProps,
     String bundleName,
-    boolean useDevSupport,
-    UIImplementationProvider uiImplementationProvider) {
-    loadBundle(spec, bundleName, useDevSupport, uiImplementationProvider);
+    boolean useDevSupport) {
+    loadBundle(spec, bundleName, useDevSupport);
     renderComponent(appKey, initialProps);
   }
 
@@ -217,14 +201,6 @@ public void loadBundle(
       ReactInstanceSpecForTest spec,
       String bundleName,
       boolean useDevSupport) {
-    loadBundle(spec, bundleName, useDevSupport, null);
-  }
-
-  public void loadBundle(
-      ReactInstanceSpecForTest spec,
-      String bundleName,
-      boolean useDevSupport,
-      UIImplementationProvider uiImplementationProvider) {
 
     mBridgeIdleSignaler = new ReactBridgeIdleSignaler();
 
@@ -277,8 +253,7 @@ public FabricUIManager get() {
                       };
                     }
                   });
-              }})
-        .setUIImplementationProvider(uiImplementationProvider);
+              }});
 
     final CountDownLatch latch = new CountDownLatch(1);
     runOnUiThread(new Runnable() {
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJSToJavaParametersTestCase.java b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJSToJavaParametersTestCase.java
index 00dee97df81c..a2d42bb1a661 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJSToJavaParametersTestCase.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJSToJavaParametersTestCase.java
@@ -29,7 +29,6 @@
 import com.facebook.react.testing.FakeWebSocketModule;
 import com.facebook.react.testing.ReactIntegrationTestCase;
 import com.facebook.react.testing.ReactTestHelper;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.views.view.ReactViewManager;
@@ -85,7 +84,7 @@ protected void setUp() throws Exception {
     List<ViewManager> viewManagers = Arrays.<ViewManager>asList(
         new ReactViewManager());
     final UIManagerModule mUIManager =
-        new UIManagerModule(getContext(), viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(getContext(), viewManagers, 0);
     UiThreadUtil.runOnUiThread(
         new Runnable() {
           @Override
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJavaToJSArgumentsTestCase.java b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJavaToJSArgumentsTestCase.java
index dec91a4ea544..3ba5bc1989b0 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJavaToJSArgumentsTestCase.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJavaToJSArgumentsTestCase.java
@@ -21,7 +21,6 @@
 import com.facebook.react.testing.FakeWebSocketModule;
 import com.facebook.react.testing.ReactIntegrationTestCase;
 import com.facebook.react.testing.ReactTestHelper;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.views.view.ReactViewManager;
@@ -62,7 +61,7 @@ protected void setUp() throws Exception {
     List<ViewManager> viewManagers = Arrays.<ViewManager>asList(
         new ReactViewManager());
     final UIManagerModule mUIManager =
-        new UIManagerModule(getContext(), viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(getContext(), viewManagers, 0);
     UiThreadUtil.runOnUiThread(
         new Runnable() {
           @Override
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJavaToJSReturnValuesTestCase.java b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJavaToJSReturnValuesTestCase.java
index 0430858c6cf4..63a2ff0a7278 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJavaToJSReturnValuesTestCase.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystNativeJavaToJSReturnValuesTestCase.java
@@ -22,7 +22,6 @@
 import com.facebook.react.testing.FakeWebSocketModule;
 import com.facebook.react.testing.ReactIntegrationTestCase;
 import com.facebook.react.testing.ReactTestHelper;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import java.util.ArrayList;
@@ -112,7 +111,7 @@ protected void setUp() throws Exception {
 
     final UIManagerModule mUIManager =
         new UIManagerModule(
-            getContext(), new ArrayList<ViewManager>(), new UIImplementationProvider(), 0);
+            getContext(), new ArrayList<ViewManager>(), 0);
 
     mAssertModule = new AssertModule();
 
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystUIManagerTestCase.java b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystUIManagerTestCase.java
index 4d58d579139d..895b1df15509 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystUIManagerTestCase.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/CatalystUIManagerTestCase.java
@@ -22,7 +22,6 @@
 import com.facebook.react.testing.ReactIntegrationTestCase;
 import com.facebook.react.testing.ReactTestHelper;
 import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.views.text.ReactRawTextManager;
@@ -77,7 +76,7 @@ protected void setUp() throws Exception {
         new ReactTextViewManager(),
         new ReactRawTextManager());
     uiManager =
-        new UIManagerModule(getContext(), viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(getContext(), viewManagers, 0);
     UiThreadUtil.runOnUiThread(new Runnable() {
       @Override
       public void run() {
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/JSLocaleTest.java b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/JSLocaleTest.java
index 5e0b9ff62f67..85eeb6c584fb 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/JSLocaleTest.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/JSLocaleTest.java
@@ -7,22 +7,20 @@
 
 package com.facebook.react.tests;
 
-import java.util.Arrays;
-import java.util.List;
-
-import com.facebook.react.testing.FakeWebSocketModule;
-import com.facebook.react.testing.ReactIntegrationTestCase;
-import com.facebook.react.testing.ReactTestHelper;
-import com.facebook.react.testing.StringRecordingModule;
 import com.facebook.react.bridge.CatalystInstance;
 import com.facebook.react.bridge.JavaScriptModule;
 import com.facebook.react.bridge.UiThreadUtil;
 import com.facebook.react.modules.appstate.AppStateModule;
 import com.facebook.react.modules.deviceinfo.DeviceInfoModule;
-import com.facebook.react.uimanager.UIImplementationProvider;
+import com.facebook.react.testing.FakeWebSocketModule;
+import com.facebook.react.testing.ReactIntegrationTestCase;
+import com.facebook.react.testing.ReactTestHelper;
+import com.facebook.react.testing.StringRecordingModule;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.views.view.ReactViewManager;
+import java.util.Arrays;
+import java.util.List;
 
 /**
  * Test locale-based functionality of JS VM
@@ -47,7 +45,6 @@ protected void setUp() throws Exception {
     final UIManagerModule mUIManager = new UIManagerModule(
         getContext(),
         viewManagers,
-        new UIImplementationProvider(),
         0);
     UiThreadUtil.runOnUiThread(
         new Runnable() {
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/ProgressBarTestCase.java b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/ProgressBarTestCase.java
index 70dd287164bd..eae42334412f 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/ProgressBarTestCase.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/ProgressBarTestCase.java
@@ -24,7 +24,6 @@
 import com.facebook.react.testing.FakeWebSocketModule;
 import com.facebook.react.testing.ReactIntegrationTestCase;
 import com.facebook.react.testing.ReactTestHelper;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.views.progressbar.ReactProgressBarViewManager;
@@ -68,7 +67,7 @@ protected void setUp() throws Exception {
         new ReactViewManager(),
         new ReactProgressBarViewManager());
     mUIManager =
-        new UIManagerModule(getContext(), viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(getContext(), viewManagers, 0);
     UiThreadUtil.runOnUiThread(
         new Runnable() {
           @Override
diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/ViewRenderingTestCase.java b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/ViewRenderingTestCase.java
index 73412bc21239..1b28762be590 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/ViewRenderingTestCase.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/ViewRenderingTestCase.java
@@ -21,7 +21,6 @@
 import com.facebook.react.testing.ReactIntegrationTestCase;
 import com.facebook.react.testing.ReactTestHelper;
 import com.facebook.react.uimanager.PixelUtil;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.views.view.ReactViewGroup;
@@ -49,7 +48,7 @@ protected void setUp() throws Exception {
 
     List<ViewManager> viewManagers = Arrays.<ViewManager>asList(new ReactViewManager());
     final UIManagerModule uiManager =
-        new UIManagerModule(getContext(), viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(getContext(), viewManagers, 0);
     UiThreadUtil.runOnUiThread(
         new Runnable() {
           @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/CoreModulesPackage.java b/ReactAndroid/src/main/java/com/facebook/react/CoreModulesPackage.java
index c6a778a6745e..1b3d4c10fa6f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/CoreModulesPackage.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/CoreModulesPackage.java
@@ -26,7 +26,6 @@
 import com.facebook.react.modules.debug.SourceCodeModule;
 import com.facebook.react.modules.deviceinfo.DeviceInfoModule;
 import com.facebook.react.modules.systeminfo.AndroidInfoModule;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.systrace.Systrace;
@@ -54,19 +53,16 @@
 
   private final ReactInstanceManager mReactInstanceManager;
   private final DefaultHardwareBackBtnHandler mHardwareBackBtnHandler;
-  private final UIImplementationProvider mUIImplementationProvider;
   private final boolean mLazyViewManagersEnabled;
   private final int mMinTimeLeftInFrameForNonBatchedOperationMs;
 
   CoreModulesPackage(
       ReactInstanceManager reactInstanceManager,
       DefaultHardwareBackBtnHandler hardwareBackBtnHandler,
-      UIImplementationProvider uiImplementationProvider,
       boolean lazyViewManagersEnabled,
       int minTimeLeftInFrameForNonBatchedOperationMs) {
     mReactInstanceManager = reactInstanceManager;
     mHardwareBackBtnHandler = hardwareBackBtnHandler;
-    mUIImplementationProvider = uiImplementationProvider;
     mLazyViewManagersEnabled = lazyViewManagersEnabled;
     mMinTimeLeftInFrameForNonBatchedOperationMs = minTimeLeftInFrameForNonBatchedOperationMs;
   }
@@ -165,13 +161,11 @@ public List<String> getViewManagerNames() {
         return new UIManagerModule(
             reactContext,
             resolver,
-            mUIImplementationProvider,
             mMinTimeLeftInFrameForNonBatchedOperationMs);
       } else {
         return new UIManagerModule(
             reactContext,
             mReactInstanceManager.getOrCreateViewManagers(reactContext),
-            mUIImplementationProvider,
             mMinTimeLeftInFrameForNonBatchedOperationMs);
       }
     } finally {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 35c188eb707a..680abe831ac9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -79,10 +79,8 @@
 import com.facebook.react.modules.debug.interfaces.DeveloperSettings;
 import com.facebook.react.modules.fabric.ReactFabric;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerHelper;
 import com.facebook.react.uimanager.ViewManager;
-import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.react.views.imagehelper.ResourceDrawableIdHelper;
 import com.facebook.soloader.SoLoader;
 import com.facebook.systrace.Systrace;
@@ -200,7 +198,6 @@ public static ReactInstanceManagerBuilder builder() {
     boolean useDeveloperSupport,
     @Nullable NotThreadSafeBridgeIdleDebugListener bridgeIdleDebugListener,
     LifecycleState initialLifecycleState,
-    UIImplementationProvider uiImplementationProvider,
     NativeModuleCallExceptionHandler nativeModuleCallExceptionHandler,
     @Nullable RedBoxHandler redBoxHandler,
     boolean lazyNativeModulesEnabled,
@@ -248,7 +245,6 @@ public void invokeDefaultOnBackPressed() {
                   ReactInstanceManager.this.invokeDefaultOnBackPressed();
                 }
               },
-              uiImplementationProvider,
               lazyViewManagersEnabled,
               minTimeLeftInFrameForNonBatchedOperationMs));
       if (mUseDeveloperSupport) {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
index d90f08f75c80..e57d5d809d9d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
@@ -10,9 +10,9 @@
 import android.app.Activity;
 import android.app.Application;
 import com.facebook.infer.annotation.Assertions;
-import com.facebook.react.bridge.JSIModulePackage;
 import com.facebook.react.bridge.JSBundleLoader;
 import com.facebook.react.bridge.JSCJavaScriptExecutorFactory;
+import com.facebook.react.bridge.JSIModulePackage;
 import com.facebook.react.bridge.JavaScriptExecutorFactory;
 import com.facebook.react.bridge.NativeModuleCallExceptionHandler;
 import com.facebook.react.bridge.NotThreadSafeBridgeIdleDebugListener;
@@ -21,7 +21,6 @@
 import com.facebook.react.devsupport.interfaces.DevBundleDownloadListener;
 import com.facebook.react.devsupport.interfaces.DevSupportManager;
 import com.facebook.react.modules.core.DefaultHardwareBackBtnHandler;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import java.util.ArrayList;
 import java.util.List;
 import javax.annotation.Nullable;
@@ -40,7 +39,6 @@ public class ReactInstanceManagerBuilder {
   private @Nullable Application mApplication;
   private boolean mUseDeveloperSupport;
   private @Nullable LifecycleState mInitialLifecycleState;
-  private @Nullable UIImplementationProvider mUIImplementationProvider;
   private @Nullable NativeModuleCallExceptionHandler mNativeModuleCallExceptionHandler;
   private @Nullable Activity mCurrentActivity;
   private @Nullable DefaultHardwareBackBtnHandler mDefaultHardwareBackBtnHandler;
@@ -56,16 +54,6 @@ public class ReactInstanceManagerBuilder {
   /* package protected */ ReactInstanceManagerBuilder() {
   }
 
-  /**
-   * Sets a provider of {@link UIImplementation}.
-   * Uses default provider if null is passed.
-   */
-  public ReactInstanceManagerBuilder setUIImplementationProvider(
-    @Nullable UIImplementationProvider uiImplementationProvider) {
-    mUIImplementationProvider = uiImplementationProvider;
-    return this;
-  }
-
   public ReactInstanceManagerBuilder setJSIModulesPackage(
     @Nullable JSIModulePackage jsiModulePackage) {
     mJSIModulesPackage = jsiModulePackage;
@@ -251,11 +239,6 @@ public ReactInstanceManager build() {
       mJSMainModulePath != null || mJSBundleAssetUrl != null || mJSBundleLoader != null,
       "Either MainModulePath or JS Bundle File needs to be provided");
 
-    if (mUIImplementationProvider == null) {
-      // create default UIImplementationProvider if the provided one is null.
-      mUIImplementationProvider = new UIImplementationProvider();
-    }
-
     // We use the name of the device and the app for debugging & metrics
     String appName = mApplication.getPackageName();
     String deviceName = getFriendlyDeviceName();
@@ -276,7 +259,6 @@ public ReactInstanceManager build() {
         mUseDeveloperSupport,
         mBridgeIdleDebugListener,
         Assertions.assertNotNull(mInitialLifecycleState, "Initial lifecycle state was not set"),
-        mUIImplementationProvider,
         mNativeModuleCallExceptionHandler,
         mRedBoxHandler,
         mLazyNativeModulesEnabled,
@@ -284,6 +266,6 @@ public ReactInstanceManager build() {
         mDevBundleDownloadListener,
         mMinNumShakes,
         mMinTimeLeftInFrameForNonBatchedOperationMs,
-      mJSIModulesPackage);
+        mJSIModulesPackage);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactNativeHost.java b/ReactAndroid/src/main/java/com/facebook/react/ReactNativeHost.java
index 2efa28daaacd..b408d9e2ebaf 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactNativeHost.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactNativeHost.java
@@ -7,20 +7,16 @@
 
 package com.facebook.react;
 
-import com.facebook.react.bridge.JSIModulePackage;
-import javax.annotation.Nullable;
-
-import java.util.List;
-
 import android.app.Application;
-
 import com.facebook.infer.annotation.Assertions;
+import com.facebook.react.bridge.JSIModulePackage;
 import com.facebook.react.bridge.JavaScriptExecutorFactory;
 import com.facebook.react.bridge.ReactMarker;
 import com.facebook.react.bridge.ReactMarkerConstants;
 import com.facebook.react.common.LifecycleState;
 import com.facebook.react.devsupport.RedBoxHandler;
-import com.facebook.react.uimanager.UIImplementationProvider;
+import java.util.List;
+import javax.annotation.Nullable;
 
 /**
  * Simple class that holds an instance of {@link ReactInstanceManager}. This can be used in your
@@ -74,7 +70,6 @@ protected ReactInstanceManager createReactInstanceManager() {
       .setUseDeveloperSupport(getUseDeveloperSupport())
       .setRedBoxHandler(getRedBoxHandler())
       .setJavaScriptExecutorFactory(getJavaScriptExecutorFactory())
-      .setUIImplementationProvider(getUIImplementationProvider())
       .setJSIModulesPackage(getJSIModulePackage())
       .setInitialLifecycleState(LifecycleState.BEFORE_CREATE);
 
@@ -112,16 +107,6 @@ protected final Application getApplication() {
     return mApplication;
   }
 
-  /**
-   * Get the {@link UIImplementationProvider} to use. Override this method if you want to use a
-   * custom UI implementation.
-   *
-   * Note: this is very advanced functionality, in 99% of cases you don't need to override this.
-   */
-  protected UIImplementationProvider getUIImplementationProvider() {
-    return new UIImplementationProvider();
-  }
-
   protected @Nullable
   JSIModulePackage getJSIModulePackage() {
     return null;
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementationProvider.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementationProvider.java
deleted file mode 100644
index 51e0d66e93b9..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIImplementationProvider.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-package com.facebook.react.uimanager;
-
-import com.facebook.react.bridge.ReactApplicationContext;
-import com.facebook.react.uimanager.events.EventDispatcher;
-import java.util.List;
-
-/**
- * Provides UIImplementation to use in {@link UIManagerModule}.
- */
-public class UIImplementationProvider {
-  public UIImplementation createUIImplementation(
-      ReactApplicationContext reactContext,
-      UIManagerModule.ViewManagerResolver viewManagerResolver,
-      EventDispatcher eventDispatcher,
-      int minTimeLeftInFrameForNonBatchedOperationMs) {
-    return new UIImplementation(
-        reactContext,
-        viewManagerResolver,
-        eventDispatcher,
-        minTimeLeftInFrameForNonBatchedOperationMs);
-  }
-  
-  public UIImplementation createUIImplementation(
-      ReactApplicationContext reactContext,
-      List<ViewManager> viewManagerList,
-      EventDispatcher eventDispatcher,
-      int minTimeLeftInFrameForNonBatchedOperationMs) {
-    return new UIImplementation(
-        reactContext,
-        viewManagerList,
-        eventDispatcher,
-        minTimeLeftInFrameForNonBatchedOperationMs);
-  }
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
index 7c03ec96bba8..6be73b4e981b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModule.java
@@ -124,7 +124,6 @@ public interface CustomEventNamesResolver {
   public UIManagerModule(
       ReactApplicationContext reactContext,
       ViewManagerResolver viewManagerResolver,
-      UIImplementationProvider uiImplementationProvider,
       int minTimeLeftInFrameForNonBatchedOperationMs) {
     super(reactContext);
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
@@ -132,7 +131,7 @@ public UIManagerModule(
     mModuleConstants = createConstants(viewManagerResolver);
     mCustomDirectEvents = UIManagerModuleConstants.getDirectEventTypeConstants();
     mUIImplementation =
-        uiImplementationProvider.createUIImplementation(
+        new UIImplementation(
             reactContext,
             viewManagerResolver,
             mEventDispatcher,
@@ -144,7 +143,6 @@ public UIManagerModule(
   public UIManagerModule(
       ReactApplicationContext reactContext,
       List<ViewManager> viewManagersList,
-      UIImplementationProvider uiImplementationProvider,
       int minTimeLeftInFrameForNonBatchedOperationMs) {
     super(reactContext);
     DisplayMetricsHolder.initDisplayMetricsIfNotInitialized(reactContext);
@@ -152,7 +150,7 @@ public UIManagerModule(
     mCustomDirectEvents = MapBuilder.newHashMap();
     mModuleConstants = createConstants(viewManagersList, null, mCustomDirectEvents);
     mUIImplementation =
-        uiImplementationProvider.createUIImplementation(
+        new UIImplementation(
             reactContext,
             viewManagersList,
             mEventDispatcher,
diff --git a/ReactAndroid/src/test/java/com/facebook/react/uimanager/ReactPropConstantsTest.java b/ReactAndroid/src/test/java/com/facebook/react/uimanager/ReactPropConstantsTest.java
index a4ee1a39056d..1b84c06d9f04 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/uimanager/ReactPropConstantsTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/uimanager/ReactPropConstantsTest.java
@@ -141,7 +141,7 @@ public void testNativePropsIncludeCorrectTypes() {
     List<ViewManager> viewManagers = Arrays.<ViewManager>asList(new ViewManagerUnderTest());
     ReactApplicationContext reactContext = new ReactApplicationContext(RuntimeEnvironment.application);
     UIManagerModule uiManagerModule =
-        new UIManagerModule(reactContext, viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(reactContext, viewManagers, 0);
     Map<String, String> constants =
         (Map) valueAtPath(uiManagerModule.getConstants(), "SomeView", "NativeProps");
     assertThat(constants).isEqualTo(
diff --git a/ReactAndroid/src/test/java/com/facebook/react/uimanager/UIManagerModuleConstantsTest.java b/ReactAndroid/src/test/java/com/facebook/react/uimanager/UIManagerModuleConstantsTest.java
index 40a8c68b4669..1435875650b0 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/uimanager/UIManagerModuleConstantsTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/uimanager/UIManagerModuleConstantsTest.java
@@ -8,14 +8,11 @@
 package com.facebook.react.uimanager;
 
 import static org.fest.assertions.api.Assertions.assertThat;
-import static org.mockito.Matchers.any;
-import static org.mockito.Matchers.anyInt;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.when;
 
 import com.facebook.react.bridge.ReactApplicationContext;
 import com.facebook.react.common.MapBuilder;
-import com.facebook.react.uimanager.events.EventDispatcher;
 import java.util.Arrays;
 import java.util.List;
 import java.util.Map;
@@ -49,25 +46,17 @@ public class UIManagerModuleConstantsTest {
   private static final Map TWIRL_DIRECT_EVENT_MAP = MapBuilder.of("registrationName", "onTwirl");
 
   private ReactApplicationContext mReactContext;
-  private UIImplementationProvider mUIImplementationProvider;
 
   @Before
   public void setUp() {
     mReactContext = new ReactApplicationContext(RuntimeEnvironment.application);
-    mUIImplementationProvider = mock(UIImplementationProvider.class);
-    when(mUIImplementationProvider.createUIImplementation(
-            any(ReactApplicationContext.class),
-            any(List.class),
-            any(EventDispatcher.class),
-            anyInt()))
-        .thenReturn(mock(UIImplementation.class));
   }
 
   @Test
   public void testNoCustomConstants() {
     List<ViewManager> viewManagers = Arrays.asList(mock(ViewManager.class));
     UIManagerModule uiManagerModule =
-        new UIManagerModule(mReactContext, viewManagers, mUIImplementationProvider, 0);
+        new UIManagerModule(mReactContext, viewManagers, 0);
     Map<String, Object> constants = uiManagerModule.getConstants();
     assertThat(constants)
         .containsKey(CUSTOM_BUBBLING_EVENT_TYPES)
@@ -82,7 +71,7 @@ public void testCustomBubblingEvents() {
     when(mockViewManager.getExportedCustomBubblingEventTypeConstants())
         .thenReturn(MapBuilder.of("onTwirl", TWIRL_BUBBLING_EVENT_MAP));
     UIManagerModule uiManagerModule =
-        new UIManagerModule(mReactContext, viewManagers, mUIImplementationProvider, 0);
+        new UIManagerModule(mReactContext, viewManagers, 0);
     Map<String, Object> constants = uiManagerModule.getConstants();
     assertThat((Map) constants.get(CUSTOM_BUBBLING_EVENT_TYPES))
         .contains(MapEntry.entry("onTwirl", TWIRL_BUBBLING_EVENT_MAP))
@@ -96,7 +85,7 @@ public void testCustomDirectEvents() {
     when(mockViewManager.getExportedCustomDirectEventTypeConstants())
         .thenReturn(MapBuilder.of("onTwirl", TWIRL_DIRECT_EVENT_MAP));
     UIManagerModule uiManagerModule =
-        new UIManagerModule(mReactContext, viewManagers, mUIImplementationProvider, 0);
+        new UIManagerModule(mReactContext, viewManagers, 0);
     Map<String, Object> constants = uiManagerModule.getConstants();
     assertThat((Map) constants.get(CUSTOM_DIRECT_EVENT_TYPES))
         .contains(MapEntry.entry("onTwirl", TWIRL_DIRECT_EVENT_MAP))
@@ -111,7 +100,7 @@ public void testCustomViewConstants() {
     when(mockViewManager.getExportedViewConstants())
         .thenReturn(MapBuilder.of("PhotoSizeType", MapBuilder.of("Small", 1, "Large", 2)));
     UIManagerModule uiManagerModule =
-        new UIManagerModule(mReactContext, viewManagers, mUIImplementationProvider, 0);
+        new UIManagerModule(mReactContext, viewManagers, 0);
     Map<String, Object> constants = uiManagerModule.getConstants();
     assertThat(constants).containsKey("RedPandaPhotoOfTheDayView");
     assertThat((Map) constants.get("RedPandaPhotoOfTheDayView")).containsKey("Constants");
@@ -127,7 +116,7 @@ public void testNativeProps() {
     when(mockViewManager.getNativeProps())
         .thenReturn(MapBuilder.of("fooProp", "number"));
     UIManagerModule uiManagerModule =
-        new UIManagerModule(mReactContext, viewManagers, mUIImplementationProvider, 0);
+        new UIManagerModule(mReactContext, viewManagers, 0);
     Map<String, Object> constants = uiManagerModule.getConstants();
     assertThat((String) valueAtPath(constants, "SomeView", "NativeProps", "fooProp"))
         .isEqualTo("number");
@@ -159,7 +148,7 @@ public void testMergeConstants() {
 
     List<ViewManager> viewManagers = Arrays.asList(managerX, managerY);
     UIManagerModule uiManagerModule =
-        new UIManagerModule(mReactContext, viewManagers, mUIImplementationProvider, 0);
+        new UIManagerModule(mReactContext, viewManagers, 0);
     Map<String, Object> constants = uiManagerModule.getConstants();
     assertThat((Map) constants.get(CUSTOM_DIRECT_EVENT_TYPES)).containsKey("onTwirl");
 
diff --git a/ReactAndroid/src/test/java/com/facebook/react/uimanager/UIManagerModuleTest.java b/ReactAndroid/src/test/java/com/facebook/react/uimanager/UIManagerModuleTest.java
index 6a90e84b628c..b38ca784d901 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/uimanager/UIManagerModuleTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/uimanager/UIManagerModuleTest.java
@@ -814,7 +814,7 @@ private UIManagerModule getUIManagerModule() {
         new ReactTextViewManager(),
         new ReactRawTextManager());
     UIManagerModule uiManagerModule =
-        new UIManagerModule(mReactContext, viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(mReactContext, viewManagers, 0);
     uiManagerModule.onHostResume();
     return uiManagerModule;
   }
diff --git a/ReactAndroid/src/test/java/com/facebook/react/views/text/ReactTextTest.java b/ReactAndroid/src/test/java/com/facebook/react/views/text/ReactTextTest.java
index 2c14111e4acd..cb113637326a 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/views/text/ReactTextTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/views/text/ReactTextTest.java
@@ -31,7 +31,6 @@
 import com.facebook.react.bridge.ReactTestHelper;
 import com.facebook.react.modules.core.ChoreographerCompat;
 import com.facebook.react.modules.core.ReactChoreographer;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewProps;
@@ -428,7 +427,7 @@ public UIManagerModule getUIManagerModule() {
             new ReactRawTextManager(),
         });
     UIManagerModule uiManagerModule =
-        new UIManagerModule(reactContext, viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(reactContext, viewManagers, 0);
     uiManagerModule.onHostResume();
     return uiManagerModule;
   }
diff --git a/ReactAndroid/src/test/java/com/facebook/react/views/textinput/TextInputTest.java b/ReactAndroid/src/test/java/com/facebook/react/views/textinput/TextInputTest.java
index 988482eeabde..c9794d7d00cf 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/views/textinput/TextInputTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/views/textinput/TextInputTest.java
@@ -21,7 +21,6 @@
 import com.facebook.react.bridge.ReactTestHelper;
 import com.facebook.react.modules.core.ChoreographerCompat;
 import com.facebook.react.modules.core.ReactChoreographer;
-import com.facebook.react.uimanager.UIImplementationProvider;
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.ViewManager;
 import com.facebook.react.uimanager.ViewProps;
@@ -178,7 +177,7 @@ public UIManagerModule getUIManagerModule() {
             new ReactTextInputManager(),
         });
     UIManagerModule uiManagerModule =
-        new UIManagerModule(reactContext, viewManagers, new UIImplementationProvider(), 0);
+        new UIManagerModule(reactContext, viewManagers, 0);
     uiManagerModule.onHostResume();
     return uiManagerModule;
   }

From 5bf3476133f6b5320ddc544d4e0339ed26315e93 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Wed, 27 Jun 2018 03:22:49 -0700
Subject: [PATCH 0937/1109] Upgrade Prettier to 1.13.6 on fbsource

Reviewed By: zertosh

Differential Revision: D8638504

fbshipit-source-id: c6991b2e884e14868ddc1d9047a78191219d673f
---
 Libraries/Components/Touchable/Touchable.js |  4 ++--
 Libraries/vendor/core/whatwg-fetch.js       | 14 +++++++-------
 package.json                                |  2 +-
 3 files changed, 10 insertions(+), 10 deletions(-)

diff --git a/Libraries/Components/Touchable/Touchable.js b/Libraries/Components/Touchable/Touchable.js
index 6a8fa3cb5d82..3f1874c8aac4 100644
--- a/Libraries/Components/Touchable/Touchable.js
+++ b/Libraries/Components/Touchable/Touchable.js
@@ -533,7 +533,7 @@ const TouchableMixin = {
    * focused at a time, in which case there may have been a previously focused
    * element that was blurred just prior to this.
    */
-  touchableHandleFocus: function (e: Event) {
+  touchableHandleFocus: function(e: Event) {
     this.props.onFocus && this.props.onFocus(e);
   },
 
@@ -543,7 +543,7 @@ const TouchableMixin = {
    * no longer has focus. Most platforms only support a single element being
    * focused at a time, in which case the focus may have moved to another.
    */
-  touchableHandleBlur: function (e: Event) {
+  touchableHandleBlur: function(e: Event) {
     this.props.onBlur && this.props.onBlur(e);
   },
 
diff --git a/Libraries/vendor/core/whatwg-fetch.js b/Libraries/vendor/core/whatwg-fetch.js
index cdfa4fc69a44..febc54dac8dd 100644
--- a/Libraries/vendor/core/whatwg-fetch.js
+++ b/Libraries/vendor/core/whatwg-fetch.js
@@ -1,11 +1,11 @@
 /**
-* Copyright (c) 2015-present, Facebook, Inc.
-*
-* This source code is licensed under the MIT license found in the
-* LICENSE file in the root directory of this source tree.
-*
-* @format
-*/
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @format
+ */
 
 // Fork of https://github.com/github/fetch/blob/master/fetch.js that does not
 // use reponseType: 'blob' by default. RN already has specific native implementations
diff --git a/package.json b/package.json
index c8be7a8d0b37..61bebba34f53 100644
--- a/package.json
+++ b/package.json
@@ -215,7 +215,7 @@
     "flow-bin": "^0.75.0",
     "jest": "23.1.0",
     "jest-junit": "4.0.0",
-    "prettier": "1.13.4",
+    "prettier": "1.13.6",
     "react": "16.4.1",
     "react-test-renderer": "16.4.1",
     "shelljs": "^0.7.8",

From 770dd38bbbec20e40e4895d512da19af20e0d0d0 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Wed, 27 Jun 2018 11:09:20 -0700
Subject: [PATCH 0938/1109] Upgrading Metro to 0.39.2

Summary: Upgrade to v0.39.2

Reviewed By: rafeca

Differential Revision: D8664421

fbshipit-source-id: 9c71928ab45cb7ef8f882d25cfca1ff0b1687039
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 61bebba34f53..8606e59c1dbc 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.40.0",
-    "metro-babel-register": "^0.40.0",
-    "metro-core": "^0.40.0",
-    "metro-memory-fs": "^0.40.0",
+    "metro": "^0.40.1",
+    "metro-babel-register": "^0.40.1",
+    "metro-core": "^0.40.1",
+    "metro-memory-fs": "^0.40.1",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From f32032e4607b1b269a4d9b6c7efa07f5545ae73e Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Wed, 27 Jun 2018 11:42:53 -0700
Subject: [PATCH 0939/1109] bump double conversion to 1.1.6 (#19885)

Summary:
bump double conversion to 1.1.6.

Version 1.1.2 added ARM 64 support, so it's a step to add support for 64bit in RN.
Closes https://github.com/facebook/react-native/pull/19885

Differential Revision: D8662108

Pulled By: hramos

fbshipit-source-id: 446d83eab4df90efed9c08eac912e7f857b7f253
---
 ReactAndroid/build.gradle | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 3b9f7189ef91..7f18e145e1fb 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -22,7 +22,7 @@ def thirdPartyNdkDir = new File("$buildDir/third-party-ndk")
 
 // You need to have following folders in this directory:
 //   - boost_1_63_0
-//   - double-conversion-1.1.1
+//   - double-conversion-1.1.6
 //   - folly-deprecate-dynamic-initializer
 //   - glog-0.3.3
 //   - jsc-headers
@@ -57,16 +57,16 @@ task prepareBoost(dependsOn: boostPath ? [] : [downloadBoost], type: Copy) {
 }
 
 task downloadDoubleConversion(dependsOn: createNativeDepsDirectories, type: Download) {
-    src 'https://github.com/google/double-conversion/archive/v1.1.1.tar.gz'
+    src 'https://github.com/google/double-conversion/archive/v1.1.6.tar.gz'
     onlyIfNewer true
     overwrite false
-    dest new File(downloadsDir, 'double-conversion-1.1.1.tar.gz')
+    dest new File(downloadsDir, 'double-conversion-1.1.6.tar.gz')
 }
 
 task prepareDoubleConversion(dependsOn: dependenciesPath ? [] : [downloadDoubleConversion], type: Copy) {
     from dependenciesPath ?: tarTree(downloadDoubleConversion.dest)
     from 'src/main/jni/third-party/double-conversion/Android.mk'
-    include 'double-conversion-1.1.1/src/**/*', 'Android.mk'
+    include 'double-conversion-1.1.6/src/**/*', 'Android.mk'
     filesMatching('*/src/**/*', {fname -> fname.path = "double-conversion/${fname.name}"})
     includeEmptyDirs = false
     into "$thirdPartyNdkDir/double-conversion"

From 0d78415d7ffce9e4963f26a939003b0831f05fe5 Mon Sep 17 00:00:00 2001
From: Gregory Menezes <gregoryfontenele@gmail.com>
Date: Wed, 27 Jun 2018 11:55:26 -0700
Subject: [PATCH 0940/1109] Update buck website

Summary: Closes https://github.com/facebook/react-native/pull/19930

Differential Revision: D8663544

Pulled By: hramos

fbshipit-source-id: 09202851f2be7ea103057a7286aa960add536775
---
 scripts/validate-android-test-env.sh | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/scripts/validate-android-test-env.sh b/scripts/validate-android-test-env.sh
index 7ec0b668c84d..a4b97c6d0f0d 100755
--- a/scripts/validate-android-test-env.sh
+++ b/scripts/validate-android-test-env.sh
@@ -10,7 +10,7 @@
 # Check that Buck is working.
 if [ -z "$(which buck)" ]; then
   echo "You need to install Buck."
-  echo "See https://buckbuild.com/setup/install.html for instructions."
+  echo "See https://buckbuild.com/setup/getting_started.html for instructions."
   exit 1
 fi
 

From b5fca806059e628edb504cb1bacf62e89ee6f102 Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Wed, 27 Jun 2018 11:57:41 -0700
Subject: [PATCH 0941/1109] bump glog to 0.3.5 (#19890)

Summary:
bump glog to 0.3.5.

Version 0.3.4 added support for libc++ or clang. Starting with revision 11, Android NDK recommends and defaults to clang, so it'll add support for it.

notable changes in 0.3.4 and 0.3.5:
* add libc++ support
* reduce dynamic allocation from 3 to 1 per log message
* style fix for C++11
* Add CMake support
Closes https://github.com/facebook/react-native/pull/19890

Differential Revision: D8662179

Pulled By: hramos

fbshipit-source-id: ae2554d36e5b922e8649fc2ac7afc273a34cc127
---
 ReactAndroid/build.gradle                      |  8 ++++----
 .../src/main/jni/third-party/glog/Android.mk   | 18 +++++++++---------
 .../src/main/jni/third-party/glog/config.h     |  9 ++++++---
 3 files changed, 19 insertions(+), 16 deletions(-)

diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index 7f18e145e1fb..bcaf798f869c 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -24,7 +24,7 @@ def thirdPartyNdkDir = new File("$buildDir/third-party-ndk")
 //   - boost_1_63_0
 //   - double-conversion-1.1.6
 //   - folly-deprecate-dynamic-initializer
-//   - glog-0.3.3
+//   - glog-0.3.5
 //   - jsc-headers
 def dependenciesPath = System.getenv("REACT_NATIVE_DEPENDENCIES")
 
@@ -89,10 +89,10 @@ task prepareFolly(dependsOn: dependenciesPath ? [] : [downloadFolly], type: Copy
 }
 
 task downloadGlog(dependsOn: createNativeDepsDirectories, type: Download) {
-    src 'https://github.com/google/glog/archive/v0.3.3.tar.gz'
+    src 'https://github.com/google/glog/archive/v0.3.5.tar.gz'
     onlyIfNewer true
     overwrite false
-    dest new File(downloadsDir, 'glog-0.3.3.tar.gz')
+    dest new File(downloadsDir, 'glog-0.3.5.tar.gz')
 }
 
 // Prepare glog sources to be compiled, this task will perform steps that normally should've been
@@ -100,7 +100,7 @@ task downloadGlog(dependsOn: createNativeDepsDirectories, type: Download) {
 task prepareGlog(dependsOn: dependenciesPath ? [] : [downloadGlog], type: Copy) {
     from dependenciesPath ?: tarTree(downloadGlog.dest)
     from 'src/main/jni/third-party/glog/'
-    include 'glog-0.3.3/src/**/*', 'Android.mk', 'config.h'
+    include 'glog-0.3.5/src/**/*', 'Android.mk', 'config.h'
     includeEmptyDirs = false
     filesMatching('**/*.h.in') {
         filter(ReplaceTokens, tokens: [
diff --git a/ReactAndroid/src/main/jni/third-party/glog/Android.mk b/ReactAndroid/src/main/jni/third-party/glog/Android.mk
index 96478acbe922..01a14538c038 100644
--- a/ReactAndroid/src/main/jni/third-party/glog/Android.mk
+++ b/ReactAndroid/src/main/jni/third-party/glog/Android.mk
@@ -3,17 +3,17 @@ LOCAL_PATH:= $(call my-dir)
 include $(CLEAR_VARS)
 
 LOCAL_SRC_FILES := \
-  glog-0.3.3/src/demangle.cc \
-  glog-0.3.3/src/logging.cc \
-  glog-0.3.3/src/raw_logging.cc \
-  glog-0.3.3/src/signalhandler.cc \
-  glog-0.3.3/src/symbolize.cc \
-  glog-0.3.3/src/utilities.cc \
-  glog-0.3.3/src/vlog_is_on.cc
+  glog-0.3.5/src/demangle.cc \
+  glog-0.3.5/src/logging.cc \
+  glog-0.3.5/src/raw_logging.cc \
+  glog-0.3.5/src/signalhandler.cc \
+  glog-0.3.5/src/symbolize.cc \
+  glog-0.3.5/src/utilities.cc \
+  glog-0.3.5/src/vlog_is_on.cc
 
-LOCAL_C_INCLUDES += $(LOCAL_PATH) $(LOCAL_PATH)/.. $(LOCAL_PATH)/glog-0.3.3/src/
+LOCAL_C_INCLUDES += $(LOCAL_PATH) $(LOCAL_PATH)/.. $(LOCAL_PATH)/glog-0.3.5/src/
 
-LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/.. $(LOCAL_PATH)/glog-0.3.3/src/
+LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/.. $(LOCAL_PATH)/glog-0.3.5/src/
 
 LOCAL_CFLAGS += \
   -Wall \
diff --git a/ReactAndroid/src/main/jni/third-party/glog/config.h b/ReactAndroid/src/main/jni/third-party/glog/config.h
index 1e20b0da7a57..ab05c5a7e192 100644
--- a/ReactAndroid/src/main/jni/third-party/glog/config.h
+++ b/ReactAndroid/src/main/jni/third-party/glog/config.h
@@ -49,6 +49,9 @@
 /* define if the compiler implements namespaces */
 #define HAVE_NAMESPACES 1
 
+/* NDK android-16 provides ssize_t pread(int, void*, size_t, off_t) */
+#define HAVE_PREAD 1
+
 /* Define if you have POSIX threads libraries and header files. */
 #define HAVE_PTHREAD 1
 
@@ -132,7 +135,7 @@
 #define PACKAGE_NAME "glog"
 
 /* Define to the full name and version of this package. */
-#define PACKAGE_STRING "glog 0.3.3"
+#define PACKAGE_STRING "glog 0.3.5"
 
 /* Define to the one symbol short name of this package. */
 #define PACKAGE_TARNAME "glog"
@@ -141,7 +144,7 @@
 #define PACKAGE_URL ""
 
 /* Define to the version of this package. */
-#define PACKAGE_VERSION "0.3.3"
+#define PACKAGE_VERSION "0.3.5"
 
 /* How to access the PC from a struct ucontext */
 /* #undef PC_FROM_UCONTEXT */
@@ -163,7 +166,7 @@
 #define TEST_SRC_DIR "."
 
 /* Version number of package */
-#define VERSION "0.3.3"
+#define VERSION "0.3.5"
 
 /* Stops putting the code inside the Google namespace */
 #define _END_GOOGLE_NAMESPACE_ }

From bc2f12c68cf8cfdf8c060354e84392fd9a3645d8 Mon Sep 17 00:00:00 2001
From: Tim Wang <timwangdev@gmail.com>
Date: Wed, 27 Jun 2018 12:57:55 -0700
Subject: [PATCH 0942/1109] Upgrade Jest to version 23.2.0 (#19876)

Summary:
@public

[Jest 23.2.0](https://github.com/facebook/jest/blob/master/CHANGELOG.md#2320) landed fix for `MockNativeMethods` access in react-native jest preset.

[GENERAL] [BUGFIX] [./package.json] - Upgrade Jest to version 23.2.0 and resolve `MockNativeMethods` access in `react-native` jest preset.

Closes https://github.com/facebook/react-native/pull/19876

Reviewed By: mjesun

Differential Revision: D8618905

Pulled By: hramos

fbshipit-source-id: 8463868b1e5dbcf430c76c0551e58d38e4c85a04
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index 8606e59c1dbc..d25acb175634 100644
--- a/package.json
+++ b/package.json
@@ -213,8 +213,8 @@
     "eslint-plugin-react": "7.8.2",
     "eslint-plugin-react-native": "^3.2.1",
     "flow-bin": "^0.75.0",
-    "jest": "23.1.0",
-    "jest-junit": "4.0.0",
+    "jest": "23.2.0",
+    "jest-junit": "5.1.0",
     "prettier": "1.13.6",
     "react": "16.4.1",
     "react-test-renderer": "16.4.1",

From b3ef1c3a5645793ef42d25bb16ef023a743a1f9f Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Wed, 27 Jun 2018 15:17:50 -0700
Subject: [PATCH 0943/1109] android: allow registering custom packager command
 handlers

Summary:
@public
Apps may need to listen for custom commands via the packager connection. This allows registering such listeners.

Reviewed By: raluca-elena

Differential Revision: D8654477

fbshipit-source-id: 5f17298a88fec31b8939236fef48ee46c0ba2ee8
---
 .../src/main/java/com/facebook/react/BUCK        |  3 +++
 .../com/facebook/react/ReactInstanceManager.java |  8 ++++++--
 .../react/ReactInstanceManagerBuilder.java       | 12 +++++++++++-
 .../react/devsupport/DevServerHelper.java        | 11 +++++++++++
 .../devsupport/DevSupportManagerFactory.java     | 14 ++++++++++----
 .../react/devsupport/DevSupportManagerImpl.java  | 16 ++++++++++++++--
 6 files changed, 55 insertions(+), 9 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/BUCK b/ReactAndroid/src/main/java/com/facebook/react/BUCK
index b9ed1bd4fd15..743bb34bb694 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/BUCK
@@ -35,4 +35,7 @@ rn_android_library(
         react_native_target("java/com/facebook/react/uimanager:uimanager"),
         react_native_target("java/com/facebook/react/views/imagehelper:imagehelper"),
     ],
+    exported_deps = [
+        react_native_target("java/com/facebook/react/packagerconnection:packagerconnection"),
+    ],
 )
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index 680abe831ac9..e5b3bae44123 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -78,6 +78,7 @@
 import com.facebook.react.modules.core.ReactChoreographer;
 import com.facebook.react.modules.debug.interfaces.DeveloperSettings;
 import com.facebook.react.modules.fabric.ReactFabric;
+import com.facebook.react.packagerconnection.RequestHandler;
 import com.facebook.react.uimanager.DisplayMetricsHolder;
 import com.facebook.react.uimanager.UIManagerHelper;
 import com.facebook.react.uimanager.ViewManager;
@@ -90,6 +91,7 @@
 import java.util.Collections;
 import java.util.HashSet;
 import java.util.List;
+import java.util.Map;
 import java.util.Set;
 import javax.annotation.Nullable;
 
@@ -205,7 +207,8 @@ public static ReactInstanceManagerBuilder builder() {
     @Nullable DevBundleDownloadListener devBundleDownloadListener,
     int minNumShakes,
     int minTimeLeftInFrameForNonBatchedOperationMs,
-    @Nullable JSIModulePackage jsiModulePackage) {
+    @Nullable JSIModulePackage jsiModulePackage,
+    @Nullable Map<String, RequestHandler> customPackagerCommandHandlers) {
     Log.d(ReactConstants.TAG, "ReactInstanceManager.ctor()");
     initializeSoLoaderIfNecessary(applicationContext);
 
@@ -227,7 +230,8 @@ public static ReactInstanceManagerBuilder builder() {
             useDeveloperSupport,
             redBoxHandler,
             devBundleDownloadListener,
-            minNumShakes);
+            minNumShakes,
+            customPackagerCommandHandlers);
     mBridgeIdleDebugListener = bridgeIdleDebugListener;
     mLifecycleState = initialLifecycleState;
     mMemoryPressureRouter = new MemoryPressureRouter(applicationContext);
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
index e57d5d809d9d..42a4a7476a41 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManagerBuilder.java
@@ -21,8 +21,10 @@
 import com.facebook.react.devsupport.interfaces.DevBundleDownloadListener;
 import com.facebook.react.devsupport.interfaces.DevSupportManager;
 import com.facebook.react.modules.core.DefaultHardwareBackBtnHandler;
+import com.facebook.react.packagerconnection.RequestHandler;
 import java.util.ArrayList;
 import java.util.List;
+import java.util.Map;
 import javax.annotation.Nullable;
 
 /**
@@ -50,6 +52,7 @@ public class ReactInstanceManagerBuilder {
   private int mMinNumShakes = 1;
   private int mMinTimeLeftInFrameForNonBatchedOperationMs = -1;
   private @Nullable JSIModulePackage mJSIModulesPackage;
+  private @Nullable Map<String, RequestHandler> mCustomPackagerCommandHandlers;
 
   /* package protected */ ReactInstanceManagerBuilder() {
   }
@@ -216,6 +219,12 @@ public ReactInstanceManagerBuilder setMinTimeLeftInFrameForNonBatchedOperationMs
     return this;
   }
 
+  public ReactInstanceManagerBuilder setCustomPackagerCommandHandlers(
+      Map<String, RequestHandler> customPackagerCommandHandlers) {
+    mCustomPackagerCommandHandlers = customPackagerCommandHandlers;
+    return this;
+  }
+
   /**
    * Instantiates a new {@link ReactInstanceManager}.
    * Before calling {@code build}, the following must be called:
@@ -266,6 +275,7 @@ public ReactInstanceManager build() {
         mDevBundleDownloadListener,
         mMinNumShakes,
         mMinTimeLeftInFrameForNonBatchedOperationMs,
-        mJSIModulesPackage);
+        mJSIModulesPackage,
+        mCustomPackagerCommandHandlers);
   }
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
index 3fb603f9c519..bcf803aa6f97 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
@@ -81,6 +81,13 @@ public interface PackagerCommandListener {
     void onPackagerReloadCommand();
     void onPackagerDevMenuCommand();
     void onCaptureHeapCommand(final Responder responder);
+
+    // Allow apps to provide listeners for custom packager commands.
+    @Nullable Map<String, RequestHandler> customCommandHandlers();
+  }
+
+  public interface PackagerCustomCommandProvider {
+
   }
 
   public interface SymbolicationListener {
@@ -162,6 +169,10 @@ public void onRequest(@Nullable Object params, Responder responder) {
             commandListener.onCaptureHeapCommand(responder);
           }
         });
+        Map<String, RequestHandler> customHandlers = commandListener.customCommandHandlers();
+        if (customHandlers != null) {
+          handlers.putAll(customHandlers);
+        }
         handlers.putAll(new FileIoHandler().handlers());
 
         ConnectionCallback onPackagerConnectedCallback =
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerFactory.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerFactory.java
index 59cc883375c9..590db9362dd9 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerFactory.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerFactory.java
@@ -11,8 +11,10 @@
 
 import com.facebook.react.devsupport.interfaces.DevBundleDownloadListener;
 import com.facebook.react.devsupport.interfaces.DevSupportManager;
+import com.facebook.react.packagerconnection.RequestHandler;
 
 import java.lang.reflect.Constructor;
+import java.util.Map;
 
 import javax.annotation.Nullable;
 
@@ -41,7 +43,8 @@ public static DevSupportManager create(
       enableOnCreate,
       null,
       null,
-      minNumShakes);
+      minNumShakes,
+      null);
   }
 
   public static DevSupportManager create(
@@ -51,7 +54,8 @@ public static DevSupportManager create(
     boolean enableOnCreate,
     @Nullable RedBoxHandler redBoxHandler,
     @Nullable DevBundleDownloadListener devBundleDownloadListener,
-    int minNumShakes) {
+    int minNumShakes,
+    @Nullable Map<String, RequestHandler> customPackagerCommandHandlers) {
     if (!enableOnCreate) {
       return new DisabledDevSupportManager();
     }
@@ -74,7 +78,8 @@ public static DevSupportManager create(
           boolean.class,
           RedBoxHandler.class,
           DevBundleDownloadListener.class,
-          int.class);
+          int.class,
+          Map.class);
       return (DevSupportManager) constructor.newInstance(
         applicationContext,
         reactInstanceManagerHelper,
@@ -82,7 +87,8 @@ public static DevSupportManager create(
         true,
         redBoxHandler,
         devBundleDownloadListener,
-        minNumShakes);
+        minNumShakes,
+        customPackagerCommandHandlers);
     } catch (Exception e) {
       throw new RuntimeException(
         "Requested enabled DevSupportManager, but DevSupportManagerImpl class was not found" +
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
index b951ef2ff222..8764597391f8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevSupportManagerImpl.java
@@ -60,6 +60,7 @@
 import java.util.LinkedHashMap;
 import java.util.List;
 import java.util.Locale;
+import java.util.Map;
 import java.util.concurrent.ExecutionException;
 import java.util.concurrent.TimeUnit;
 import java.util.concurrent.TimeoutException;
@@ -150,6 +151,8 @@ private enum ErrorType {
 
   private InspectorPackagerConnection.BundleStatus mBundleStatus;
 
+  private @Nullable Map<String, RequestHandler> mCustomPackagerCommandHandlers;
+
   private static class JscProfileTask extends AsyncTask<String, Void, Void> {
     private static final MediaType JSON =
       MediaType.parse("application/json; charset=utf-8");
@@ -196,7 +199,8 @@ public DevSupportManagerImpl(
       enableOnCreate,
       null,
       null,
-      minNumShakes);
+      minNumShakes,
+      null);
   }
 
   public DevSupportManagerImpl(
@@ -206,7 +210,8 @@ public DevSupportManagerImpl(
       boolean enableOnCreate,
       @Nullable RedBoxHandler redBoxHandler,
       @Nullable DevBundleDownloadListener devBundleDownloadListener,
-      int minNumShakes) {
+      int minNumShakes,
+      @Nullable Map<String, RequestHandler> customPackagerCommandHandlers) {
     mReactInstanceManagerHelper = reactInstanceManagerHelper;
     mApplicationContext = applicationContext;
     mJSAppBundleName = packagerPathForJSBundleName;
@@ -232,6 +237,8 @@ public void onShake() {
       }
     }, minNumShakes);
 
+    mCustomPackagerCommandHandlers = customPackagerCommandHandlers;
+
     // Prepare reload APP broadcast receiver (will be registered/unregistered from #reload)
     mReloadAppBroadcastReceiver = new BroadcastReceiver() {
       @Override
@@ -841,6 +848,11 @@ public void run() {
     });
   }
 
+  @Override
+  public @Nullable Map<String, RequestHandler> customCommandHandlers() {
+    return mCustomPackagerCommandHandlers;
+  }
+
   private void handleCaptureHeap(final Responder responder) {
     if (mCurrentContext == null) {
       return;

From 5017b86b525e3ef6023f0f8a88e6fd1cf98024e0 Mon Sep 17 00:00:00 2001
From: Greg Price <gnprice@gmail.com>
Date: Wed, 27 Jun 2018 19:55:27 -0700
Subject: [PATCH 0944/1109] Fix extreme TextInput slowness on Android (#19645)

Summary:
This reverts 5898817fc "Implement letterSpacing on Android >= 5.0".
Testing shows that that commit is the cause of #19126, where in a
controlled TextInput after some text is first added, then deleted,
further interaction with the TextInput becomes extremely slow.

Fixes #19126.

Tried the repro case from #19126 without this change, then with it.
The issue reproduces, then doesn't.
Closes https://github.com/facebook/react-native/pull/19645

Differential Revision: D8675230

Pulled By: hramos

fbshipit-source-id: e2c2d352ee781898721b2dff4738572d1a6b7471
---
 .../com/facebook/react/views/text/ReactBaseTextShadowNode.java  | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactBaseTextShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactBaseTextShadowNode.java
index 075c5be23edf..f6a8885d12f2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactBaseTextShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactBaseTextShadowNode.java
@@ -119,7 +119,7 @@ private static void buildSpannedFromShadowNode(
                 start, end, new BackgroundColorSpan(textShadowNode.mBackgroundColor)));
       }
       if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-        if (textShadowNode.mLetterSpacing != Float.NaN) {
+        if (!Float.isNaN(textShadowNode.mLetterSpacing)) {
           ops.add(new SetSpanOperation(
             start,
             end,

From 0a3055d98a36e49746144e883edc7e20afec4fcb Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Wed, 27 Jun 2018 20:25:32 -0700
Subject: [PATCH 0945/1109] gradle to set project-wide properties (#19845)

Summary:
Change HelloWorld app template to use project-wide properties. See https://developer.android.com/studio/build/gradle-tips#configure-project-wide-properties.

RN community and third-party native module developers adopted this, so it'll make RN package development and usage easy.

CI is green https://circleci.com/gh/dulmandakh/react-native/507
Closes https://github.com/facebook/react-native/pull/19845

Differential Revision: D8675341

Pulled By: hramos

fbshipit-source-id: 4ed06cd7ef7ae70f153d7f335ef8a9d1371f6ce0
---
 .../templates/HelloWorld/android/app/build.gradle      | 10 +++++-----
 local-cli/templates/HelloWorld/android/build.gradle    |  8 ++++++++
 2 files changed, 13 insertions(+), 5 deletions(-)

diff --git a/local-cli/templates/HelloWorld/android/app/build.gradle b/local-cli/templates/HelloWorld/android/app/build.gradle
index 131424b8c333..31a0da9a576e 100644
--- a/local-cli/templates/HelloWorld/android/app/build.gradle
+++ b/local-cli/templates/HelloWorld/android/app/build.gradle
@@ -94,13 +94,13 @@ def enableSeparateBuildPerCPUArchitecture = false
 def enableProguardInReleaseBuilds = false
 
 android {
-    compileSdkVersion 26
-    buildToolsVersion "26.0.3"
+    compileSdkVersion rootProject.ext.compileSdkVersion
+    buildToolsVersion rootProject.ext.buildToolsVersion
 
     defaultConfig {
         applicationId "com.helloworld"
-        minSdkVersion 16
-        targetSdkVersion 22
+        minSdkVersion rootProject.ext.minSdkVersion
+        targetSdkVersion rootProject.ext.targetSdkVersion
         versionCode 1
         versionName "1.0"
         ndk {
@@ -138,7 +138,7 @@ android {
 
 dependencies {
     compile fileTree(dir: "libs", include: ["*.jar"])
-    compile "com.android.support:appcompat-v7:26.1.0"
+    compile "com.android.support:appcompat-v7:${rootProject.ext.supportLibVersion}"
     compile "com.facebook.react:react-native:+"  // From node_modules
 }
 
diff --git a/local-cli/templates/HelloWorld/android/build.gradle b/local-cli/templates/HelloWorld/android/build.gradle
index 225b5f682d0f..49569e4db5f7 100644
--- a/local-cli/templates/HelloWorld/android/build.gradle
+++ b/local-cli/templates/HelloWorld/android/build.gradle
@@ -30,3 +30,11 @@ allprojects {
         }
     }
 }
+
+ext {
+    buildToolsVersion = "26.0.3"
+    minSdkVersion = 16
+    compileSdkVersion = 26
+    targetSdkVersion = 26
+    supportLibVersion = "26.1.0"
+}

From 6110a4cc75bf8f285ff091cc175b9ebf737f88fc Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Thu, 28 Jun 2018 01:16:43 -0700
Subject: [PATCH 0946/1109] RN: Add Support for `overflow` on Android

Summary:
Adds support for the `overflow` style property on React Native for Android.

This switches overflowing views to be visible by default with the ability to override this at the container level using `overflow: 'hidden'`. This is the same behavior as React Native on iOS.

One major caveat to this solution is that it uses `setClipChildren` which does not extend the hit target to the overflow draw regions. While this is a pitfall, the current state of React Native on Android where `overflow` is hidden by default (which is the opposite of iOS) is also a huge pitfall. But I think this moves us in the right direction because where you *don't* need the touch behavior, you are now able to leverage overflow draws.

Reviewed By: himabindugadupudi

Differential Revision: D8666509

fbshipit-source-id: 5e98e658e16188414016260224caa696b4fbd390
---
 .../src/main/java/com/facebook/react/uimanager/ViewProps.java | 4 ++--
 .../java/com/facebook/react/views/view/ReactViewGroup.java    | 2 ++
 2 files changed, 4 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
index f85236d4842d..15ea0c6d40ea 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
@@ -254,8 +254,8 @@ public static boolean isLayoutOnly(ReadableMap map, String prop) {
           return map.isNull(BORDER_RIGHT_WIDTH) || map.getDouble(BORDER_RIGHT_WIDTH) == 0d;
         case BORDER_BOTTOM_WIDTH:
           return map.isNull(BORDER_BOTTOM_WIDTH) || map.getDouble(BORDER_BOTTOM_WIDTH) == 0d;
-        case OVERFLOW: // We do nothing with this right now.
-          return true;
+        case OVERFLOW:
+          return map.isNull(OVERFLOW) || map.getString(OVERFLOW) == "visible";
         default:
           return false;
       }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index 1915b6eb48fb..74b14bae8cc5 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -112,6 +112,7 @@ public void onLayoutChange(
 
   public ReactViewGroup(Context context) {
     super(context);
+    setClipChildren(false);
     mDrawingOrderHelper = new ViewGroupDrawingOrderHelper(this);
   }
 
@@ -638,6 +639,7 @@ public void setHitSlopRect(@Nullable Rect rect) {
   }
 
   public void setOverflow(String overflow) {
+    setClipChildren(mOverflow == "hidden");
     mOverflow = overflow;
     invalidate();
   }

From bfb68c09ee88c6e1d91d3b54c01746f9a98c7c6c Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Thu, 28 Jun 2018 11:18:55 -0700
Subject: [PATCH 0947/1109] android targetSdkVersion is 26 (#19944)

Summary:
This PR sets gradle targetSdkVersion to 26, which will satisfy new requirements from Play Store. Also removed redundant config from manifest files.
Closes https://github.com/facebook/react-native/pull/19944

Differential Revision: D8679682

Pulled By: hramos

fbshipit-source-id: 5c900d47be1d8b81ce340e38a05d9b309da143c3
---
 RNTester/android/app/build.gradle                 | 2 +-
 RNTester/android/app/src/main/AndroidManifest.xml | 8 +-------
 ReactAndroid/build.gradle                         | 2 +-
 ReactAndroid/src/androidTest/AndroidManifest.xml  | 5 +----
 4 files changed, 4 insertions(+), 13 deletions(-)

diff --git a/RNTester/android/app/build.gradle b/RNTester/android/app/build.gradle
index 42c3eb81c59f..4722633e7c4b 100644
--- a/RNTester/android/app/build.gradle
+++ b/RNTester/android/app/build.gradle
@@ -90,7 +90,7 @@ android {
     defaultConfig {
         applicationId "com.facebook.react.uiapp"
         minSdkVersion 16
-        targetSdkVersion 23
+        targetSdkVersion 26
         versionCode 1
         versionName "1.0"
         ndk {
diff --git a/RNTester/android/app/src/main/AndroidManifest.xml b/RNTester/android/app/src/main/AndroidManifest.xml
index 0bde8735a3a8..11234b0552f7 100644
--- a/RNTester/android/app/src/main/AndroidManifest.xml
+++ b/RNTester/android/app/src/main/AndroidManifest.xml
@@ -1,9 +1,7 @@
 <?xml version="1.0" encoding="utf-8"?>
 <manifest
   xmlns:android="http://schemas.android.com/apk/res/android"
-  package="com.facebook.react.uiapp"
-  android:versionCode="1"
-  android:versionName="1.0">
+  package="com.facebook.react.uiapp">
 
   <uses-permission android:name="android.permission.INTERNET" />
   <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
@@ -16,10 +14,6 @@
   <uses-permission android:name="android.permission.CAMERA"/>
   <uses-permission android:name="android.permission.READ_CALENDAR"/>
 
-  <uses-sdk
-    android:minSdkVersion="16"
-    android:targetSdkVersion="23" />
-
   <!--
   android:icon is used to display launcher icon on mobile devices.
   android:banner is used to display a rectangular banned launcher icon on Android TV devices.
diff --git a/ReactAndroid/build.gradle b/ReactAndroid/build.gradle
index bcaf798f869c..dc0734a95349 100644
--- a/ReactAndroid/build.gradle
+++ b/ReactAndroid/build.gradle
@@ -250,7 +250,7 @@ android {
 
     defaultConfig {
         minSdkVersion 16
-        targetSdkVersion 22
+        targetSdkVersion 26
         versionCode 1
         versionName "1.0"
 
diff --git a/ReactAndroid/src/androidTest/AndroidManifest.xml b/ReactAndroid/src/androidTest/AndroidManifest.xml
index f6ce0fa0511c..62c744e8f895 100644
--- a/ReactAndroid/src/androidTest/AndroidManifest.xml
+++ b/ReactAndroid/src/androidTest/AndroidManifest.xml
@@ -1,9 +1,6 @@
 <?xml version="1.0" encoding="utf-8"?>
 <manifest xmlns:android="http://schemas.android.com/apk/res/android"
-          package="com.facebook.react.tests.gradle"
-          android:versionCode="1"
-          android:versionName="1.0" >
-  <uses-sdk android:targetSdkVersion="7" />
+          package="com.facebook.react.tests.gradle">
   <supports-screens android:anyDensity="true" />
   <uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
   <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

From 75a0273de21948b0b959263100f09111f738ec35 Mon Sep 17 00:00:00 2001
From: mmacdougall <mmacdougall@etsy.com>
Date: Thu, 28 Jun 2018 11:26:46 -0700
Subject: [PATCH 0948/1109] - Correct fishhook import in
 RCTReconnectingWebSocket Fixes #16039 (#16271)

Summary:
RCTReconnectingWebSocket is not compiling correctly because of an incorrect import (https://github.com/facebook/react-native/issues/16039).

Everything build and run as usual.

[IOS] [BUGFIX] [Fishhook] - Correct fishhook import in RCTReconnectingWebSocket Fixes #16039
Closes https://github.com/facebook/react-native/pull/16271

Differential Revision: D8679758

Pulled By: hramos

fbshipit-source-id: b05dda3a01a68ace87f11889b84ce6b323e5c16a
---
 Libraries/WebSocket/RCTReconnectingWebSocket.m | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/Libraries/WebSocket/RCTReconnectingWebSocket.m b/Libraries/WebSocket/RCTReconnectingWebSocket.m
index c0f0988cf72e..522eca0eabf4 100644
--- a/Libraries/WebSocket/RCTReconnectingWebSocket.m
+++ b/Libraries/WebSocket/RCTReconnectingWebSocket.m
@@ -9,7 +9,12 @@
 
 #import <React/RCTConvert.h>
 #import <React/RCTDefines.h>
+
+#if __has_include(<React/fishhook.h>)
+#import <React/fishhook.h>
+#else
 #import <fishhook/fishhook.h>
+#endif
 
 #if __has_include(<os/log.h>) && defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 100300 /* __IPHONE_10_3 */
 #import <os/log.h>

From 5f8b44fd227e20fc51bc16de80d6582adf78fc7b Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 28 Jun 2018 11:56:53 -0700
Subject: [PATCH 0949/1109] added check for iOS 11 on ignore inverted colors

Summary:
Added Check for iOS 11 before setting property for `accessibilityIgnoreInvertColor`

Builds on top of
https://our.intern.facebook.com/intern/diff/D8549084/

Reviewed By: shergin

Differential Revision: D8599698

fbshipit-source-id: c5cc26b4c1c20fb9cca5bfe7143fa9dcb217a2d7
---
 React/Views/RCTViewManager.m |  1 +
 React/Views/UIView+React.h   |  6 ++++++
 React/Views/UIView+React.m   | 19 +++++++++++++++++++
 3 files changed, 26 insertions(+)

diff --git a/React/Views/RCTViewManager.m b/React/Views/RCTViewManager.m
index 626e923d35e5..ede084d1a5fb 100644
--- a/React/Views/RCTViewManager.m
+++ b/React/Views/RCTViewManager.m
@@ -112,6 +112,7 @@ - (RCTShadowView *)shadowView
 RCT_REMAP_VIEW_PROPERTY(accessibilityTraits, reactAccessibilityElement.accessibilityTraits, UIAccessibilityTraits)
 RCT_REMAP_VIEW_PROPERTY(accessibilityViewIsModal, reactAccessibilityElement.accessibilityViewIsModal, BOOL)
 RCT_REMAP_VIEW_PROPERTY(accessibilityElementsHidden, reactAccessibilityElement.accessibilityElementsHidden, BOOL)
+RCT_REMAP_VIEW_PROPERTY(accessibilityIgnoresInvertColors, reactAccessibilityElement.shouldAccessibilityIgnoresInvertColors, BOOL)
 RCT_REMAP_VIEW_PROPERTY(onAccessibilityAction, reactAccessibilityElement.onAccessibilityAction, RCTDirectEventBlock)
 RCT_REMAP_VIEW_PROPERTY(onAccessibilityTap, reactAccessibilityElement.onAccessibilityTap, RCTDirectEventBlock)
 RCT_REMAP_VIEW_PROPERTY(onMagicTap, reactAccessibilityElement.onMagicTap, RCTDirectEventBlock)
diff --git a/React/Views/UIView+React.h b/React/Views/UIView+React.h
index 94de7aae7531..3d0ac2c5af7a 100644
--- a/React/Views/UIView+React.h
+++ b/React/Views/UIView+React.h
@@ -27,6 +27,12 @@
  */
 @property (nonatomic, copy) NSString *nativeID;
 
+/**
+ * Determines whether or not a view should ignore inverted colors or not. Used to set
+ * UIView property accessibilityIgnoresInvertColors in iOS 11+.
+ */
+@property (nonatomic, assign) BOOL shouldAccessibilityIgnoresInvertColors;
+
 /**
  * Layout direction of the view.
  * Internally backed to `semanticContentAttribute` property.
diff --git a/React/Views/UIView+React.m b/React/Views/UIView+React.m
index 22d14f82c4a3..613083b4c440 100644
--- a/React/Views/UIView+React.m
+++ b/React/Views/UIView+React.m
@@ -35,6 +35,25 @@ - (void)setNativeID:(NSNumber *)nativeID
   objc_setAssociatedObject(self, @selector(nativeID), nativeID, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
 }
 
+- (BOOL)shouldAccessibilityIgnoresInvertColors
+{
+#if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
+    if (@available(iOS 11.0, *)) {
+        return self.accessibilityIgnoresInvertColors;
+    }
+#endif
+    return NO;
+}
+
+- (void)setShouldAccessibilityIgnoresInvertColors:(BOOL)shouldAccessibilityIgnoresInvertColors
+{
+#if defined(__IPHONE_OS_VERSION_MAX_ALLOWED) && __IPHONE_OS_VERSION_MAX_ALLOWED >= 110000 /* __IPHONE_11_0 */
+    if (@available(iOS 11.0, *)) {
+        self.accessibilityIgnoresInvertColors = shouldAccessibilityIgnoresInvertColors;
+    }
+#endif
+}
+
 - (BOOL)isReactRootView
 {
   return RCTIsReactRootView(self.reactTag);

From 3cd0737fe2dce9df29822854bfbfaf2f22346c69 Mon Sep 17 00:00:00 2001
From: Ian Henshaw <ian@thehenshaws.net>
Date: Thu, 28 Jun 2018 14:02:34 -0700
Subject: [PATCH 0950/1109] Fix for 17497 (#17498)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
Changed runAndroid.js to generate .packager.bat and launchPackager.ba…t to call it to setup the environment variable

<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

Trying to use react-native on a Windows box with a virus killer that runs on port 8081...

(Write your test plan here. If you changed any code, please provide us with clear instructions on how you verified your changes work. Bonus points for screenshots and videos!)
1) Start an android emulator
2) on a react-native project (with the changes), run `react-native run-android --port 9988`.
3) When the packager starts, verify that it states the correct port in the terminal window.
4) verify that the application correctly starts in the Emulator.

(If this PR adds or changes functionality, please take some time to update the docs at https://github.com/facebook/react-native-website, and link to your PR here.)

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[CATEGORY] [TYPE] [LOCATION] - MESSAGE

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->
[INTERNAL] [BUGFIX] [./scripts] - Fixed runAndroid to enable the use of a package on port <> 8081 for Windows.
Closes https://github.com/facebook/react-native/pull/17498

Differential Revision: D8682067

Pulled By: hramos

fbshipit-source-id: 6604b827077b3a6a2da9914c1fd36dad6ef30e43
---
 local-cli/runAndroid/runAndroid.js | 20 +++++++++++++++-----
 scripts/launchPackager.bat         |  1 +
 2 files changed, 16 insertions(+), 5 deletions(-)

diff --git a/local-cli/runAndroid/runAndroid.js b/local-cli/runAndroid/runAndroid.js
index 234530c10415..cd21b6ac29cf 100644
--- a/local-cli/runAndroid/runAndroid.js
+++ b/local-cli/runAndroid/runAndroid.js
@@ -349,25 +349,35 @@ function runOnAllDevices(
 }
 
 function startServerInNewWindow(port) {
-  const scriptFile = /^win/.test(process.platform)
+  // set up OS-specific filenames and commands
+  const isWindows = /^win/.test(process.platform);
+  const scriptFile = isWindows
     ? 'launchPackager.bat'
     : 'launchPackager.command';
+  const packagerEnvFilename = isWindows
+    ? '.packager.bat'
+    : '.packager.env';
+  const portExportContent = isWindows
+    ? `set RCT_METRO_PORT=${port}`
+    : `export RCT_METRO_PORT=${port}`;
+
+  // set up the launchpackager.(command|bat) file
   const scriptsDir = path.resolve(__dirname, '..', '..', 'scripts');
   const launchPackagerScript = path.resolve(scriptsDir, scriptFile);
   const procConfig = {cwd: scriptsDir};
   const terminal = process.env.REACT_TERMINAL;
 
-  // setup the .packager.env file to ensure the packager starts on the right port
+  // set up the .packager.(env|bat) file to ensure the packager starts on the right port
   const packagerEnvFile = path.join(
     __dirname,
     '..',
     '..',
     'scripts',
-    '.packager.env',
+    packagerEnvFilename
   );
-  const content = `export RCT_METRO_PORT=${port}`;
+  
   // ensure we overwrite file by passing the 'w' flag
-  fs.writeFileSync(packagerEnvFile, content, {encoding: 'utf8', flag: 'w'});
+  fs.writeFileSync(packagerEnvFile, portExportContent, {encoding: 'utf8', flag: 'w'});
 
   if (process.platform === 'darwin') {
     if (terminal) {
diff --git a/scripts/launchPackager.bat b/scripts/launchPackager.bat
index 09f1de987370..b85ecc6822ce 100644
--- a/scripts/launchPackager.bat
+++ b/scripts/launchPackager.bat
@@ -5,6 +5,7 @@
 
 @echo off
 title Metro Bundler
+call .packager.bat
 node "%~dp0..\local-cli\cli.js" start
 pause
 exit

From e131fffb37a545363daf11735a0243165b57f63f Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Micha=C5=82=20Mokijewski?= <hello@naf.gl>
Date: Thu, 28 Jun 2018 15:18:55 -0700
Subject: [PATCH 0951/1109] fix undefined_arch error in Xcode 10 beta (#19841)

Summary:
Fixes #19774

I spotted that in  Xcode 10 beta `CURRENT_ARCH` is set to string `undefined_arch`.  This PR will add fallback based on platform name (simulators are `x86_64` and everything since iPhone 5s is `arm64`).
Closes https://github.com/facebook/react-native/pull/19841

Differential Revision: D8619897

Pulled By: hramos

fbshipit-source-id: ed2ebaca105c6dcb40099f1a4aebe34d0660130c
---
 scripts/ios-configure-glog.sh | 13 ++++++++++++-
 1 file changed, 12 insertions(+), 1 deletion(-)

diff --git a/scripts/ios-configure-glog.sh b/scripts/ios-configure-glog.sh
index e6a15febb907..3840fc4ebc71 100755
--- a/scripts/ios-configure-glog.sh
+++ b/scripts/ios-configure-glog.sh
@@ -2,7 +2,18 @@
 set -e
 
 PLATFORM_NAME="${PLATFORM_NAME:-iphoneos}"
-CURRENT_ARCH="${CURRENT_ARCH:-armv7}"
+CURRENT_ARCH="${CURRENT_ARCH}"
+
+if [ -z "$CURRENT_ARCH" ] || [ "$CURRENT_ARCH" == "undefined_arch" ]; then
+    # Xcode 10 beta sets CURRENT_ARCH to "undefined_arch", this leads to incorrect linker arg.
+    # it's better to rely on platform name as fallback because architecture differs between simulator and device
+
+    if [[ "$PLATFORM_NAME" == *"simulator"* ]]; then
+        CURRENT_ARCH="x86_64"
+    else 
+        CURRENT_ARCH="armv7"
+    fi
+fi
 
 export CC="$(xcrun -find -sdk $PLATFORM_NAME cc) -arch $CURRENT_ARCH -isysroot $(xcrun -sdk $PLATFORM_NAME --show-sdk-path)"
 export CXX="$CC"

From dbc23466b3ec63453ca57e6e24e1efd23c104b8f Mon Sep 17 00:00:00 2001
From: Shane Osbourne <shane.osbourne8@gmail.com>
Date: Thu, 28 Jun 2018 15:24:25 -0700
Subject: [PATCH 0952/1109] =?UTF-8?q?fix:=20account=20for=20`ListHeaderCom?=
 =?UTF-8?q?ponent`=20length=20when=20calculating=20offset=E2=80=A6=20(#174?=
 =?UTF-8?q?15)?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
… in VirtualizedList - fixes #16612

Issue is detailed in #16612

<!--
Thank you for sending the PR! We appreciate you spending the time to work on these changes.

Help us understand your motivation by explaining why you decided to make this change.

You can learn more about contributing to React Native here: http://facebook.github.io/react-native/docs/contributing.html

Happy contributing!

-->

I need `onViewableItemsChanged` to account for the length of any ListHeaderComponents

I couldn't find any tests that currently cover the use-case of a VirtualizedList + ListComponent + scroll with onViewableItemsChanged, so I have not added any tests - all previous tests pass however.

<!--
Help reviewers and the release process by writing your own release notes

**INTERNAL and MINOR tagged notes will not be included in the next version's final release notes.**

  CATEGORY
[----------]        TYPE
[ CLI      ]   [-------------]      LOCATION
[ DOCS     ]   [ BREAKING    ]   [-------------]
[ GENERAL  ]   [ BUGFIX      ]   [-{Component}-]
[ INTERNAL ]   [ ENHANCEMENT ]   [ {File}      ]
[ IOS      ]   [ FEATURE     ]   [ {Directory} ]   |-----------|
[ ANDROID  ]   [ MINOR       ]   [ {Framework} ] - | {Message} |
[----------]   [-------------]   [-------------]   |-----------|

[CATEGORY] [TYPE] [LOCATION] - MESSAGE

 EXAMPLES:

 [IOS] [BREAKING] [FlatList] - Change a thing that breaks other things
 [ANDROID] [BUGFIX] [TextInput] - Did a thing to TextInput
 [CLI] [FEATURE] [local-cli/info/info.js] - CLI easier to do things with
 [DOCS] [BUGFIX] [GettingStarted.md] - Accidentally a thing/word
 [GENERAL] [ENHANCEMENT] [Yoga] - Added new yoga thing/position
 [INTERNAL] [FEATURE] [./scripts] - Added thing to script that nobody will see
-->

[GENERAL][BUGFIX][VirtualizedList] - account for `ListHeaderComponent` length
Closes https://github.com/facebook/react-native/pull/17415

Differential Revision: D8683555

Pulled By: hramos

fbshipit-source-id: 05df7b79c16e3c07c12468e782f3c4b0bdce7403
---
 Libraries/Lists/VirtualizedList.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 56364823f06d..47b6b5f083e1 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -1217,7 +1217,9 @@ class VirtualizedList extends React.PureComponent<Props, State> {
   }
 
   _selectOffset(metrics: $ReadOnly<{x: number, y: number}>): number {
-    return !this.props.horizontal ? metrics.y : metrics.x;
+    return (
+      (!this.props.horizontal ? metrics.y : metrics.x) - this._headerLength
+    );
   }
 
   _maybeCallOnEndReached() {

From 519b0c319f946df607e6e02bb6cf8113040ddc57 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Thu, 28 Jun 2018 15:49:07 -0700
Subject: [PATCH 0953/1109] Move babel-preset-react-native to metro repository

Summary:
@public

From now, `babel-preset-react-native` is going to be called `metro-react-native-babel-preset` and it's going to use the same versioning system that other metro packages.

This solves a few problems:

* Automated publishing of this package: Currently we have to publish this package manually from the RN repository, so it's hard to make changes to `babel-preset-react-native` and have them available on `metro` (the plugin version has to be manually updated, the package has to be manually published to npm and metro has to be change to depend on the new version).
* Transforming package code before publishing: By being in Metro repository, we're going to transform its source code before publishing it to npm automatically using the same infra as other metro packages, which is going to prevent issues like the current one with Node v6 due to trailing commas added by prettier: https://circleci.com/gh/facebook/metro/2125
* Workspace usage: Now, this package is not going to be installed via npm internally, but instead be used directly from the yarn workspace.

Reviewed By: mjesun

Differential Revision: D8677254

fbshipit-source-id: 14abdd218af64056625c5a997458bfe51d2101bc
---
 babel-preset/README.md                        |  31 ----
 babel-preset/configs/hmr.js                   |  42 ------
 babel-preset/configs/main.js                  | 132 ------------------
 babel-preset/index.js                         |  12 --
 babel-preset/lib/resolvePlugins.js            |  42 ------
 babel-preset/package.json                     |  46 ------
 babel-preset/plugins.js                       |  37 -----
 .../transforms/transform-symbol-member.js     |  67 ---------
 8 files changed, 409 deletions(-)
 delete mode 100644 babel-preset/README.md
 delete mode 100644 babel-preset/configs/hmr.js
 delete mode 100644 babel-preset/configs/main.js
 delete mode 100644 babel-preset/index.js
 delete mode 100644 babel-preset/lib/resolvePlugins.js
 delete mode 100644 babel-preset/package.json
 delete mode 100644 babel-preset/plugins.js
 delete mode 100644 babel-preset/transforms/transform-symbol-member.js

diff --git a/babel-preset/README.md b/babel-preset/README.md
deleted file mode 100644
index eaab8477ea6d..000000000000
--- a/babel-preset/README.md
+++ /dev/null
@@ -1,31 +0,0 @@
-# babel-preset-react-native
-
-Babel presets for React Native applications. React Native itself uses this Babel preset by default when transforming your app's source code.
-
-If you wish to use a custom Babel configuration by writing a `.babelrc` file in your project's root directory, you must specify all the plugins necessary to transform your code. React Native does not apply its default Babel configuration in this case. So, to make your life easier, you can use this preset to get the default configuration and then specify more plugins that run before it.
-
-## Usage
-
-As mentioned above, you only need to use this preset if you are writing a custom `.babelrc` file.
-
-### Installation
-
-Install `babel-preset-react-native` in your app:
-```sh
-npm i babel-preset-react-native --save-dev
-```
-
-### Configuring Babel
-
-Then, create a file called `.babelrc` in your project's root directory. The existence of this `.babelrc` file will tell React Native to use your custom Babel configuration instead of its own. Then load this preset:
-```
-{
-  "presets": ["react-native"]
-}
-```
-
-You can further customize your Babel configuration by specifying plugins and other options. See [Babel's `.babelrc` documentation](https://babeljs.io/docs/usage/babelrc/) to learn more.
-
-## Help and Support
-
-If you get stuck configuring Babel, please ask a question on Stack Overflow or find a consultant for help. If you discover a bug, please open up an issue.
diff --git a/babel-preset/configs/hmr.js b/babel-preset/configs/hmr.js
deleted file mode 100644
index 05b305c09e6c..000000000000
--- a/babel-preset/configs/hmr.js
+++ /dev/null
@@ -1,42 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- */
-'use strict';
-
-var path = require('path');
-
-var hmrTransform = 'react-transform-hmr/lib/index.js';
-var transformPath = require.resolve(hmrTransform);
-
-module.exports = function(options, filename) {
-  var transform = filename
-    ? './' + path.relative(path.dirname(filename), transformPath) // packager can't handle absolute paths
-    : hmrTransform;
-
-  // Fix the module path to use '/' on Windows.
-  if (path.sep === '\\') {
-    transform = transform.replace(/\\/g, '/');
-  }
-
-  return {
-    plugins: [
-      [
-        require('metro-babel7-plugin-react-transform'),
-        {
-          transforms: [
-            {
-              transform: transform,
-              imports: ['react'],
-              locals: ['module'],
-            },
-          ],
-        },
-      ],
-    ],
-  };
-};
diff --git a/babel-preset/configs/main.js b/babel-preset/configs/main.js
deleted file mode 100644
index 526d6f7f909d..000000000000
--- a/babel-preset/configs/main.js
+++ /dev/null
@@ -1,132 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- */
-
-'use strict';
-
-const defaultPlugins = [
-  [require('@babel/plugin-transform-block-scoping')],
-  // the flow strip types plugin must go BEFORE class properties!
-  // there'll be a test case that fails if you don't.
-  [require('@babel/plugin-transform-flow-strip-types')],
-  [
-    require('@babel/plugin-proposal-class-properties'),
-    // use `this.foo = bar` instead of `this.defineProperty('foo', ...)`
-    {loose: true},
-  ],
-  [require('@babel/plugin-transform-computed-properties')],
-  [require('@babel/plugin-transform-destructuring')],
-  [require('@babel/plugin-transform-function-name')],
-  [require('@babel/plugin-transform-literals')],
-  [require('@babel/plugin-transform-parameters')],
-  [require('@babel/plugin-transform-shorthand-properties')],
-  [require('@babel/plugin-transform-react-jsx')],
-  [require('@babel/plugin-transform-regenerator')],
-  [require('@babel/plugin-transform-sticky-regex')],
-  [require('@babel/plugin-transform-unicode-regex')],
-  [
-    require('@babel/plugin-transform-modules-commonjs'),
-    {
-      strict: false,
-      strictMode: false, // prevent "use strict" injections
-      allowTopLevelThis: true, // dont rewrite global `this` -> `undefined`
-    },
-  ],
-];
-
-const es2015ArrowFunctions = [
-  require('@babel/plugin-transform-arrow-functions'),
-];
-const es2015Classes = [require('@babel/plugin-transform-classes')];
-const es2015ForOf = [require('@babel/plugin-transform-for-of'), {loose: true}];
-const es2015Spread = [require('@babel/plugin-transform-spread')];
-const es2015TemplateLiterals = [
-  require('@babel/plugin-transform-template-literals'),
-  {loose: true}, // dont 'a'.concat('b'), just use 'a'+'b'
-];
-const exponentiationOperator = [
-  require('@babel/plugin-transform-exponentiation-operator'),
-];
-const objectAssign = [require('@babel/plugin-transform-object-assign')];
-const objectRestSpread = [require('@babel/plugin-proposal-object-rest-spread')];
-const optionalChaining = [require('@babel/plugin-proposal-optional-chaining')];
-const reactDisplayName = [
-  require('@babel/plugin-transform-react-display-name'),
-];
-const reactJsxSource = [require('@babel/plugin-transform-react-jsx-source')];
-const symbolMember = [require('../transforms/transform-symbol-member')];
-
-const getPreset = (src, options) => {
-  const isNull = src === null || src === undefined;
-  const hasClass = isNull || src.indexOf('class') !== -1;
-  const hasForOf =
-    isNull || (src.indexOf('for') !== -1 && src.indexOf('of') !== -1);
-
-  const extraPlugins = [];
-
-  if (hasClass) {
-    extraPlugins.push(es2015Classes);
-  }
-  if (isNull || src.indexOf('=>') !== -1) {
-    extraPlugins.push(es2015ArrowFunctions);
-  }
-  if (isNull || hasClass || src.indexOf('...') !== -1) {
-    extraPlugins.push(es2015Spread);
-    extraPlugins.push(objectRestSpread);
-  }
-  if (isNull || src.indexOf('`') !== -1) {
-    extraPlugins.push(es2015TemplateLiterals);
-  }
-  if (isNull || src.indexOf('**') !== -1) {
-    extraPlugins.push(exponentiationOperator);
-  }
-  if (isNull || src.indexOf('Object.assign') !== -1) {
-    extraPlugins.push(objectAssign);
-  }
-  if (hasForOf) {
-    extraPlugins.push(es2015ForOf);
-  }
-  if (hasForOf || src.indexOf('Symbol') !== -1) {
-    extraPlugins.push(symbolMember);
-  }
-  if (
-    isNull ||
-    src.indexOf('React.createClass') !== -1 ||
-    src.indexOf('createReactClass') !== -1
-  ) {
-    extraPlugins.push(reactDisplayName);
-  }
-  if (isNull || src.indexOf('?.') !== -1) {
-    extraPlugins.push(optionalChaining);
-  }
-
-  if (options && options.dev) {
-    extraPlugins.push(reactJsxSource);
-  }
-
-  return {
-    comments: false,
-    compact: true,
-    plugins: defaultPlugins.concat(extraPlugins),
-  };
-};
-
-const base = getPreset(null);
-const devTools = getPreset(null, {dev: true});
-
-module.exports = options => {
-  if (options.withDevTools == null) {
-    const env = process.env.BABEL_ENV || process.env.NODE_ENV;
-    if (!env || env === 'development') {
-      return devTools;
-    }
-  }
-  return base;
-};
-
-module.exports.getPreset = getPreset;
diff --git a/babel-preset/index.js b/babel-preset/index.js
deleted file mode 100644
index 2209567af269..000000000000
--- a/babel-preset/index.js
+++ /dev/null
@@ -1,12 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- */
-
-'use strict';
-
-module.exports = require('./configs/main');
diff --git a/babel-preset/lib/resolvePlugins.js b/babel-preset/lib/resolvePlugins.js
deleted file mode 100644
index 0291c94e70f8..000000000000
--- a/babel-preset/lib/resolvePlugins.js
+++ /dev/null
@@ -1,42 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- */
-'use strict';
-
-/**
- * Manually resolve all default Babel plugins.
- * `babel.transform` will attempt to resolve all base plugins relative to
- * the file it's compiling. This makes sure that we're using the plugins
- * installed in the react-native package.
- */
-function resolvePlugins(plugins, prefix) {
-  return plugins.map(plugin => resolvePlugin(plugin, prefix));
-}
-
-/**
- * Manually resolve a single Babel plugin.
- */
-function resolvePlugin(plugin, prefix = '@babel/plugin-') {
-  // Normalise plugin to an array.
-  if (!Array.isArray(plugin)) {
-    plugin = [plugin];
-  }
-  // Only resolve the plugin if it's a string reference.
-  if (typeof plugin[0] === 'string') {
-    plugin[0] = require(prefix + plugin[0]);
-    plugin[0] = plugin[0].__esModule ? plugin[0].default : plugin[0];
-  }
-  return plugin;
-}
-
-module.exports = resolvePlugins;
-module.exports.resolvePlugin = resolvePlugin;
-module.exports.resolvePluginAs = (prefix, plugin) =>
-  resolvePlugin(plugin, prefix);
-module.exports.resolvePluginsAs = (prefix, plugins) =>
-  resolvePlugins(plugins, prefix);
diff --git a/babel-preset/package.json b/babel-preset/package.json
deleted file mode 100644
index 332842f451a1..000000000000
--- a/babel-preset/package.json
+++ /dev/null
@@ -1,46 +0,0 @@
-{
-  "name": "babel-preset-react-native",
-  "version": "5.0.2",
-  "description": "Babel preset for React Native applications",
-  "main": "index.js",
-  "repository": "https://github.com/facebook/react-native/tree/master/babel-preset",
-  "keywords": [
-    "babel",
-    "preset",
-    "react-native"
-  ],
-  "license": "MIT",
-  "bugs": {
-    "url": "https://github.com/facebook/react-native/issues"
-  },
-  "homepage": "https://github.com/facebook/react-native/tree/master/babel-preset/README.md",
-  "dependencies": {
-    "@babel/plugin-proposal-class-properties": "7.0.0-beta.47",
-    "@babel/plugin-proposal-object-rest-spread": "7.0.0-beta.47",
-    "@babel/plugin-proposal-optional-chaining": "7.0.0-beta.47",
-    "@babel/plugin-transform-arrow-functions": "7.0.0-beta.47",
-    "@babel/plugin-transform-block-scoping": "7.0.0-beta.47",
-    "@babel/plugin-transform-classes": "7.0.0-beta.47",
-    "@babel/plugin-transform-computed-properties": "7.0.0-beta.47",
-    "@babel/plugin-transform-destructuring": "7.0.0-beta.47",
-    "@babel/plugin-transform-exponentiation-operator": "7.0.0-beta.47",
-    "@babel/plugin-transform-flow-strip-types": "7.0.0-beta.47",
-    "@babel/plugin-transform-for-of": "7.0.0-beta.47",
-    "@babel/plugin-transform-function-name": "7.0.0-beta.47",
-    "@babel/plugin-transform-literals": "7.0.0-beta.47",
-    "@babel/plugin-transform-modules-commonjs": "7.0.0-beta.47",
-    "@babel/plugin-transform-object-assign": "7.0.0-beta.47",
-    "@babel/plugin-transform-parameters": "7.0.0-beta.47",
-    "@babel/plugin-transform-react-display-name": "7.0.0-beta.47",
-    "@babel/plugin-transform-react-jsx": "7.0.0-beta.47",
-    "@babel/plugin-transform-react-jsx-source": "7.0.0-beta.47",
-    "@babel/plugin-transform-regenerator": "7.0.0-beta.47",
-    "@babel/plugin-transform-shorthand-properties": "7.0.0-beta.47",
-    "@babel/plugin-transform-spread": "7.0.0-beta.47",
-    "@babel/plugin-transform-sticky-regex": "7.0.0-beta.47",
-    "@babel/plugin-transform-template-literals": "7.0.0-beta.47",
-    "@babel/plugin-transform-unicode-regex": "7.0.0-beta.47",
-    "@babel/template": "7.0.0-beta.47",
-    "metro-babel7-plugin-react-transform": "^0.40.0"
-  }
-}
diff --git a/babel-preset/plugins.js b/babel-preset/plugins.js
deleted file mode 100644
index b53d23bbe4fc..000000000000
--- a/babel-preset/plugins.js
+++ /dev/null
@@ -1,37 +0,0 @@
-/**
- * Copyright (c) 2015-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @flow
- * @format
- */
-'use strict';
-
-module.exports = {
-  '@babel/plugin-proposal-class-properties': require('@babel/plugin-proposal-class-properties'),
-  '@babel/plugin-proposal-object-rest-spread': require('@babel/plugin-proposal-object-rest-spread'),
-  '@babel/plugin-transform-arrow-functions': require('@babel/plugin-transform-arrow-functions'),
-  '@babel/plugin-transform-block-scoping': require('@babel/plugin-transform-block-scoping'),
-  '@babel/plugin-transform-classes': require('@babel/plugin-transform-classes'),
-  '@babel/plugin-transform-computed-properties': require('@babel/plugin-transform-computed-properties'),
-  '@babel/plugin-transform-destructuring': require('@babel/plugin-transform-destructuring'),
-  '@babel/plugin-transform-exponentiation-operator': require('@babel/plugin-transform-exponentiation-operator'),
-  '@babel/plugin-transform-flow-strip-types': require('@babel/plugin-transform-flow-strip-types'),
-  '@babel/plugin-transform-for-of': require('@babel/plugin-transform-for-of'),
-  '@babel/plugin-transform-function-name': require('@babel/plugin-transform-function-name'),
-  '@babel/plugin-transform-literals': require('@babel/plugin-transform-literals'),
-  '@babel/plugin-transform-modules-commonjs': require('@babel/plugin-transform-modules-commonjs'),
-  '@babel/plugin-transform-object-assign': require('@babel/plugin-transform-object-assign'),
-  '@babel/plugin-transform-parameters': require('@babel/plugin-transform-parameters'),
-  '@babel/plugin-transform-shorthand-properties': require('@babel/plugin-transform-shorthand-properties'),
-  '@babel/plugin-transform-react-display-name': require('@babel/plugin-transform-react-display-name'),
-  '@babel/plugin-transform-react-jsx': require('@babel/plugin-transform-react-jsx'),
-  '@babel/plugin-transform-react-jsx-source': require('@babel/plugin-transform-react-jsx-source'),
-  '@babel/plugin-transform-regenerator': require('@babel/plugin-transform-regenerator'),
-  '@babel/plugin-transform-spread': require('@babel/plugin-transform-spread'),
-  '@babel/plugin-transform-sticky-regex': require('@babel/plugin-transform-sticky-regex'),
-  '@babel/plugin-transform-unicode-regex': require('@babel/plugin-transform-unicode-regex'),
-  '@babel/plugin-transform-template-literals': require('@babel/plugin-transform-template-literals'),
-};
diff --git a/babel-preset/transforms/transform-symbol-member.js b/babel-preset/transforms/transform-symbol-member.js
deleted file mode 100644
index 3cf5f5faf9f7..000000000000
--- a/babel-preset/transforms/transform-symbol-member.js
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * Copyright (c) 2004-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- *
- * @format
- */
-
-'use strict';
-
-/*eslint consistent-return: 0*/
-
-/**
- * Transforms function properties of the `Symbol` into
- * the presence check, and fallback string "@@<name>".
- *
- * Example:
- *
- *   Symbol.iterator;
- *
- * Transformed to:
- *
- *   typeof Symbol.iterator === 'function' ? Symbol.iterator : '@@iterator';
- */
-module.exports = function symbolMember(babel) {
-  const t = babel.types;
-
-  return {
-    visitor: {
-      MemberExpression(path) {
-        if (!isAppropriateMember(path)) {
-          return;
-        }
-
-        let node = path.node;
-
-        path.replaceWith(
-          t.conditionalExpression(
-            t.binaryExpression(
-              '===',
-              t.unaryExpression('typeof', t.identifier('Symbol'), true),
-              t.stringLiteral('function'),
-            ),
-            node,
-            t.stringLiteral(`@@${node.property.name}`),
-          ),
-        );
-
-        // We should stop to avoid infinite recursion, since Babel
-        // traverses replaced path, and again would hit our transform.
-        path.stop();
-      },
-    },
-  };
-};
-
-function isAppropriateMember(path) {
-  let node = path.node;
-
-  return (
-    path.parentPath.type !== 'AssignmentExpression' &&
-    node.object.type === 'Identifier' &&
-    node.object.name === 'Symbol' &&
-    node.property.type === 'Identifier'
-  );
-}

From 2f3f1b02cdea6a8ec55ec467d0336ce60f4b7feb Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Thu, 28 Jun 2018 22:38:42 -0700
Subject: [PATCH 0954/1109] Avoid cleaning up Owner of YGNode during clonning

Summary:
This diff refactors the cloning mechanism for YogaNode used from Fabric UI renderer and RN iOS graphs.
Previously, we were cleaning the owner of the child's cloned node inside the C++ implementation of YogaNode. This was a mistake because this modified the last commited YogaTree, causing side effect in RN iOS graphs.

Reviewed By: shergin

Differential Revision: D8672627

fbshipit-source-id: c9902d00690e0361fd58aed84b506c42258bd995
---
 .../src/main/java/com/facebook/yoga/YogaNode.java     | 10 ++++++++++
 .../src/main/jni/first-party/yogajni/jni/YGJNI.cpp    | 11 +++++++++++
 ReactCommon/yoga/yoga/Yoga.cpp                        |  3 ---
 3 files changed, 21 insertions(+), 3 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
index f8b895b1663a..1565d4bbdd35 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNode.java
@@ -175,6 +175,8 @@ public void addSharedChildAt(YogaNode child, int i) {
     jni_YGNodeInsertSharedChild(mNativePointer, child.mNativePointer, i);
   }
 
+  private native void jni_YGNodeSetOwner(long nativePointer, long newOwnerNativePointer);
+
   private native long jni_YGNodeClone(long nativePointer, Object newNode);
 
   @Override
@@ -182,6 +184,14 @@ public YogaNode clone() {
     try {
       YogaNode clonedYogaNode = (YogaNode) super.clone();
       long clonedNativePointer = jni_YGNodeClone(mNativePointer, clonedYogaNode);
+
+      if (mChildren != null) {
+        for (YogaNode child : mChildren) {
+          child.jni_YGNodeSetOwner(child.mNativePointer, 0);
+          child.mOwner = null;
+        }
+      }
+
       clonedYogaNode.mNativePointer = clonedNativePointer;
       clonedYogaNode.mOwner = null;
       clonedYogaNode.mChildren =
diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
index 2bc0ee8bd21b..5649ef7ea70e 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
@@ -268,6 +268,16 @@ jlong jni_YGNodeNewWithConfig(alias_ref<jobject> thiz, jlong configPointer) {
   return reinterpret_cast<jlong>(node);
 }
 
+void jni_YGNodeSetOwner(
+    alias_ref<jobject> thiz,
+    jlong nativePointer,
+    jlong newOwnerNativePointer) {
+  const YGNodeRef node = _jlong2YGNodeRef(nativePointer);
+  const YGNodeRef newOwnerNode = _jlong2YGNodeRef(newOwnerNativePointer);
+
+  node->setOwner(newOwnerNode);
+}
+
 jlong jni_YGNodeClone(
     alias_ref<jobject> thiz,
     jlong nativePointer,
@@ -667,6 +677,7 @@ jint JNI_OnLoad(JavaVM *vm, void *) {
             YGMakeNativeMethod(jni_YGNodeGetInstanceCount),
             YGMakeNativeMethod(jni_YGNodePrint),
             YGMakeNativeMethod(jni_YGNodeClone),
+            YGMakeNativeMethod(jni_YGNodeSetOwner),
         });
     registerNatives(
         "com/facebook/yoga/YogaConfig",
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 3c83ce080c75..e5d1aabb0489 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -244,9 +244,6 @@ YGNodeRef YGNodeClone(YGNodeRef oldNode) {
       oldNode->getConfig(),
       node != nullptr,
       "Could not allocate memory for node");
-  for (auto &item : oldNode->getChildren()) {
-    item->setOwner(nullptr);
-  }
   gNodeInstanceCount++;
   node->setOwner(nullptr);
   return node;

From b283dcdd3e315fdb3f81caec327a645efc8efe0d Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Fri, 29 Jun 2018 12:06:49 -0700
Subject: [PATCH 0955/1109] RNTester: Cleanup ViewExample.js

Summary: Minor cleanup of ViewExample.js in the RNTester.

Reviewed By: sahrens

Differential Revision: D8690133

fbshipit-source-id: d034f6d215679dac7f19fab90729bb7e7ef39edd
---
 RNTester/js/ViewExample.js | 267 +++++++++++++++++++++----------------
 1 file changed, 151 insertions(+), 116 deletions(-)

diff --git a/RNTester/js/ViewExample.js b/RNTester/js/ViewExample.js
index 1cc4ad686772..ffa5bd3d2bde 100644
--- a/RNTester/js/ViewExample.js
+++ b/RNTester/js/ViewExample.js
@@ -10,110 +10,11 @@
 
 'use strict';
 
-var React = require('react');
-var ReactNative = require('react-native');
-var {StyleSheet, Text, View} = ReactNative;
-var TouchableWithoutFeedback = require('TouchableWithoutFeedback');
+/* eslint-disable react-native/no-inline-styles */
 
-var styles = StyleSheet.create({
-  box: {
-    backgroundColor: '#527FE4',
-    borderColor: '#000033',
-    borderWidth: 1,
-  },
-  zIndex: {
-    justifyContent: 'space-around',
-    width: 100,
-    height: 50,
-    marginTop: -10,
-  },
-});
-
-class ViewBorderStyleExample extends React.Component<{}, $FlowFixMeState> {
-  state = {
-    showBorder: true,
-  };
-
-  render() {
-    return (
-      <TouchableWithoutFeedback onPress={this._handlePress}>
-        <View>
-          <View
-            style={{
-              borderWidth: 1,
-              borderStyle: this.state.showBorder ? 'dashed' : null,
-              padding: 5,
-            }}>
-            <Text style={{fontSize: 11}}>Dashed border style</Text>
-          </View>
-          <View
-            style={{
-              marginTop: 5,
-              borderWidth: 1,
-              borderRadius: 5,
-              borderStyle: this.state.showBorder ? 'dotted' : null,
-              padding: 5,
-            }}>
-            <Text style={{fontSize: 11}}>Dotted border style</Text>
-          </View>
-        </View>
-      </TouchableWithoutFeedback>
-    );
-  }
-
-  _handlePress = () => {
-    this.setState({showBorder: !this.state.showBorder});
-  };
-}
-
-class ZIndexExample extends React.Component<{}, $FlowFixMeState> {
-  state = {
-    flipped: false,
-  };
-
-  render() {
-    const indices = this.state.flipped ? [-1, 0, 1, 2] : [2, 1, 0, -1];
-    return (
-      <TouchableWithoutFeedback onPress={this._handlePress}>
-        <View>
-          <Text style={{paddingBottom: 10}}>Tap to flip sorting order</Text>
-          <View
-            style={[
-              styles.zIndex,
-              {marginTop: 0, backgroundColor: '#E57373', zIndex: indices[0]},
-            ]}>
-            <Text>ZIndex {indices[0]}</Text>
-          </View>
-          <View
-            style={[
-              styles.zIndex,
-              {marginLeft: 50, backgroundColor: '#FFF176', zIndex: indices[1]},
-            ]}>
-            <Text>ZIndex {indices[1]}</Text>
-          </View>
-          <View
-            style={[
-              styles.zIndex,
-              {marginLeft: 100, backgroundColor: '#81C784', zIndex: indices[2]},
-            ]}>
-            <Text>ZIndex {indices[2]}</Text>
-          </View>
-          <View
-            style={[
-              styles.zIndex,
-              {marginLeft: 150, backgroundColor: '#64B5F6', zIndex: indices[3]},
-            ]}>
-            <Text>ZIndex {indices[3]}</Text>
-          </View>
-        </View>
-      </TouchableWithoutFeedback>
-    );
-  }
-
-  _handlePress = () => {
-    this.setState({flipped: !this.state.flipped});
-  };
-}
+const React = require('react');
+const {StyleSheet, Text, View} = require('react-native');
+const TouchableWithoutFeedback = require('TouchableWithoutFeedback');
 
 exports.title = '<View>';
 exports.description =
@@ -124,7 +25,7 @@ exports.displayName = 'ViewExample';
 exports.examples = [
   {
     title: 'Background Color',
-    render: function() {
+    render() {
       return (
         <View style={{backgroundColor: '#527FE4', padding: 5}}>
           <Text style={{fontSize: 11}}>Blue background</Text>
@@ -134,7 +35,7 @@ exports.examples = [
   },
   {
     title: 'Border',
-    render: function() {
+    render() {
       return (
         <View style={{borderColor: '#527FE4', borderWidth: 5, padding: 10}}>
           <Text style={{fontSize: 11}}>5px blue border</Text>
@@ -144,7 +45,14 @@ exports.examples = [
   },
   {
     title: 'Padding/Margin',
-    render: function() {
+    render() {
+      const styles = StyleSheet.create({
+        box: {
+          backgroundColor: '#527FE4',
+          borderColor: '#000033',
+          borderWidth: 1,
+        },
+      });
       return (
         <View style={{borderColor: '#bb0000', borderWidth: 0.5}}>
           <View style={[styles.box, {padding: 5}]}>
@@ -167,7 +75,7 @@ exports.examples = [
   },
   {
     title: 'Border Radius',
-    render: function() {
+    render() {
       return (
         <View style={{borderWidth: 0.5, borderRadius: 5, padding: 5}}>
           <Text style={{fontSize: 11}}>
@@ -180,13 +88,54 @@ exports.examples = [
   },
   {
     title: 'Border Style',
-    render: function() {
+    render() {
+      type Props = $ReadOnly<{||}>;
+      type State = {|
+        showBorder: boolean,
+      |};
+
+      class ViewBorderStyleExample extends React.Component<Props, State> {
+        state = {
+          showBorder: true,
+        };
+
+        render() {
+          return (
+            <TouchableWithoutFeedback onPress={this._handlePress}>
+              <View>
+                <View
+                  style={{
+                    borderWidth: 1,
+                    borderStyle: this.state.showBorder ? 'dashed' : null,
+                    padding: 5,
+                  }}>
+                  <Text style={{fontSize: 11}}>Dashed border style</Text>
+                </View>
+                <View
+                  style={{
+                    marginTop: 5,
+                    borderWidth: 1,
+                    borderRadius: 5,
+                    borderStyle: this.state.showBorder ? 'dotted' : null,
+                    padding: 5,
+                  }}>
+                  <Text style={{fontSize: 11}}>Dotted border style</Text>
+                </View>
+              </View>
+            </TouchableWithoutFeedback>
+          );
+        }
+
+        _handlePress = () => {
+          this.setState({showBorder: !this.state.showBorder});
+        };
+      }
       return <ViewBorderStyleExample />;
     },
   },
   {
     title: 'Circle with Border Radius',
-    render: function() {
+    render() {
       return (
         <View
           style={{borderRadius: 10, borderWidth: 1, width: 20, height: 20}}
@@ -196,24 +145,30 @@ exports.examples = [
   },
   {
     title: 'Overflow',
-    render: function() {
+    render() {
       return (
         <View style={{flexDirection: 'row'}}>
           <View
             style={{
-              width: 95,
+              borderWidth: 0.5,
               height: 10,
-              marginRight: 10,
               marginBottom: 5,
+              marginRight: 10,
               overflow: 'hidden',
-              borderWidth: 0.5,
+              width: 95,
             }}>
             <View style={{width: 200, height: 20}}>
               <Text>Overflow hidden</Text>
             </View>
           </View>
           <View
-            style={{width: 95, height: 10, marginBottom: 5, borderWidth: 0.5}}>
+            style={{
+              borderWidth: 0.5,
+              height: 10,
+              marginBottom: 5,
+              marginRight: 10,
+              width: 95,
+            }}>
             <View style={{width: 200, height: 20}}>
               <Text>Overflow visible</Text>
             </View>
@@ -224,7 +179,7 @@ exports.examples = [
   },
   {
     title: 'Opacity',
-    render: function() {
+    render() {
       return (
         <View>
           <View style={{opacity: 0}}>
@@ -254,7 +209,87 @@ exports.examples = [
   },
   {
     title: 'ZIndex',
-    render: function() {
+    render() {
+      type Props = $ReadOnly<{||}>;
+      type State = {|
+        flipped: boolean,
+      |};
+
+      const styles = StyleSheet.create({
+        zIndex: {
+          justifyContent: 'space-around',
+          width: 100,
+          height: 50,
+          marginTop: -10,
+        },
+      });
+
+      class ZIndexExample extends React.Component<Props, State> {
+        state = {
+          flipped: false,
+        };
+
+        render() {
+          const indices = this.state.flipped ? [-1, 0, 1, 2] : [2, 1, 0, -1];
+          return (
+            <TouchableWithoutFeedback onPress={this._handlePress}>
+              <View>
+                <Text style={{paddingBottom: 10}}>
+                  Tap to flip sorting order
+                </Text>
+                <View
+                  style={[
+                    styles.zIndex,
+                    {
+                      marginTop: 0,
+                      backgroundColor: '#E57373',
+                      zIndex: indices[0],
+                    },
+                  ]}>
+                  <Text>ZIndex {indices[0]}</Text>
+                </View>
+                <View
+                  style={[
+                    styles.zIndex,
+                    {
+                      marginLeft: 50,
+                      backgroundColor: '#FFF176',
+                      zIndex: indices[1],
+                    },
+                  ]}>
+                  <Text>ZIndex {indices[1]}</Text>
+                </View>
+                <View
+                  style={[
+                    styles.zIndex,
+                    {
+                      marginLeft: 100,
+                      backgroundColor: '#81C784',
+                      zIndex: indices[2],
+                    },
+                  ]}>
+                  <Text>ZIndex {indices[2]}</Text>
+                </View>
+                <View
+                  style={[
+                    styles.zIndex,
+                    {
+                      marginLeft: 150,
+                      backgroundColor: '#64B5F6',
+                      zIndex: indices[3],
+                    },
+                  ]}>
+                  <Text>ZIndex {indices[3]}</Text>
+                </View>
+              </View>
+            </TouchableWithoutFeedback>
+          );
+        }
+
+        _handlePress = () => {
+          this.setState({flipped: !this.state.flipped});
+        };
+      }
       return <ZIndexExample />;
     },
   },

From d9fa1d70dcf70764f0e308353fbac344c515db74 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Fri, 29 Jun 2018 12:06:52 -0700
Subject: [PATCH 0956/1109] RNTester: Better View Overflow Example

Summary:
Improves the examples in `ViewExample.js` that tests overflow behavior. Notable:

- Test view flattening behavior by setting `overflow` on views that only have other layout-only styles.
- Test the default behavior when `overflow` is not set at all.

Reviewed By: achen1

Differential Revision: D8690560

fbshipit-source-id: 6320ef51305952d13bf5724b369651fdfd32ff21
---
 RNTester/js/ViewExample.js | 48 +++++++++++++++++++++-----------------
 1 file changed, 27 insertions(+), 21 deletions(-)

diff --git a/RNTester/js/ViewExample.js b/RNTester/js/ViewExample.js
index ffa5bd3d2bde..5115a08d5ac7 100644
--- a/RNTester/js/ViewExample.js
+++ b/RNTester/js/ViewExample.js
@@ -146,31 +146,37 @@ exports.examples = [
   {
     title: 'Overflow',
     render() {
+      const styles = StyleSheet.create({
+        container: {
+          borderWidth: StyleSheet.hairlineWidth,
+          height: 12,
+          marginBottom: 8,
+          marginEnd: 16,
+          width: 95,
+        },
+        content: {
+          height: 20,
+          width: 200,
+        },
+      });
+
+      // NOTE: The <View> that sets `overflow` should only have other layout
+      // styles so that we can accurately test view flattening optimizations.
       return (
         <View style={{flexDirection: 'row'}}>
-          <View
-            style={{
-              borderWidth: 0.5,
-              height: 10,
-              marginBottom: 5,
-              marginRight: 10,
-              overflow: 'hidden',
-              width: 95,
-            }}>
-            <View style={{width: 200, height: 20}}>
-              <Text>Overflow hidden</Text>
+          <View style={styles.container}>
+            <View style={[StyleSheet.absoluteFill]}>
+              <Text style={styles.content}>undefined</Text>
             </View>
           </View>
-          <View
-            style={{
-              borderWidth: 0.5,
-              height: 10,
-              marginBottom: 5,
-              marginRight: 10,
-              width: 95,
-            }}>
-            <View style={{width: 200, height: 20}}>
-              <Text>Overflow visible</Text>
+          <View style={styles.container}>
+            <View style={[StyleSheet.absoluteFill, {overflow: 'hidden'}]}>
+              <Text style={styles.content}>hidden</Text>
+            </View>
+          </View>
+          <View style={styles.container}>
+            <View style={[StyleSheet.absoluteFill, {overflow: 'visible'}]}>
+              <Text style={styles.content}>visible</Text>
             </View>
           </View>
         </View>

From f090840f452a0fb8ddb9d7cdd657c419ca627c1c Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Fri, 29 Jun 2018 12:06:54 -0700
Subject: [PATCH 0957/1109] RN: Revert D8666509
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Summary:
Reverts D8666509. Unfortunately, I misunderstood `setClipChildren` on Android.

When set on a `ViewGroup`, `setClipChildren` configures whether its //children// — not itself — are clipped to their bounds. This is unlike `overflow` (as it behaves on iOS) which configures whether the view itself is clipped to its bounds.

But they are definitely related. In theory, I think we could implement `overflow` using `setClipChildren` by:

- Setting `setClipChildren(false)` by default. (This part, I got right.)
- When `overflow` is set to `hidden` on a `View`, we create an extra `ViewGroup` (child) within the normal `ViewGroup` (parent). Then, we can set `setClipChildren(true)` on the parent `ViewGroup` which will cause the child `ViewGroup` to be clipped to its bounds.

However, I think the tricky thing will be to create the child `ViewGroup` without incurring unintentional side effects.

I need to decide whether or not this is worth trying. The alternative is to add a new `clipChildren` boolean prop that is Android-only, but I really hate further bifurcating the platform. But for now, I am reverting my mistake.

Reviewed By: achen1

Differential Revision: D8690551

fbshipit-source-id: 1ba3bbcc5458ffbd5c475430ea0382b3fd0916b2
---
 .../src/main/java/com/facebook/react/uimanager/ViewProps.java | 4 ++--
 .../java/com/facebook/react/views/view/ReactViewGroup.java    | 2 --
 2 files changed, 2 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
index 15ea0c6d40ea..f85236d4842d 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
@@ -254,8 +254,8 @@ public static boolean isLayoutOnly(ReadableMap map, String prop) {
           return map.isNull(BORDER_RIGHT_WIDTH) || map.getDouble(BORDER_RIGHT_WIDTH) == 0d;
         case BORDER_BOTTOM_WIDTH:
           return map.isNull(BORDER_BOTTOM_WIDTH) || map.getDouble(BORDER_BOTTOM_WIDTH) == 0d;
-        case OVERFLOW:
-          return map.isNull(OVERFLOW) || map.getString(OVERFLOW) == "visible";
+        case OVERFLOW: // We do nothing with this right now.
+          return true;
         default:
           return false;
       }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index 74b14bae8cc5..1915b6eb48fb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -112,7 +112,6 @@ public void onLayoutChange(
 
   public ReactViewGroup(Context context) {
     super(context);
-    setClipChildren(false);
     mDrawingOrderHelper = new ViewGroupDrawingOrderHelper(this);
   }
 
@@ -639,7 +638,6 @@ public void setHitSlopRect(@Nullable Rect rect) {
   }
 
   public void setOverflow(String overflow) {
-    setClipChildren(mOverflow == "hidden");
     mOverflow = overflow;
     invalidate();
   }

From cfce6ee9d7002da6803eeeb297c5e288470c4e84 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Fri, 29 Jun 2018 12:07:00 -0700
Subject: [PATCH 0958/1109] RN: Android Constants for Overflow Style

Summary:
Tidies up the hardcoded strings for referencing the `overflow` style values.

Also, the `OVERFLOW` case in the optimized view flattening code path is unnecessary because `OVERFLOW` is already in the `LAYOUT_ONLY_PROPS` set.

Reviewed By: achen1

Differential Revision: D8690804

fbshipit-source-id: 3befbe93ed761e57e45f9b50e59bffc8a29a407f
---
 .../main/java/com/facebook/react/uimanager/ViewProps.java    | 5 +++--
 .../java/com/facebook/react/views/view/ReactViewGroup.java   | 5 +++--
 2 files changed, 6 insertions(+), 4 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
index f85236d4842d..11f09b0b6805 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
@@ -74,6 +74,9 @@ public class ViewProps {
   public static final String MIN_HEIGHT = "minHeight";
   public static final String MAX_HEIGHT = "maxHeight";
 
+  public static final String HIDDEN = "hidden";
+  public static final String VISIBLE = "visible";
+
   public static final String ASPECT_RATIO = "aspectRatio";
 
   // Props that sometimes may prevent us from collapsing views
@@ -254,8 +257,6 @@ public static boolean isLayoutOnly(ReadableMap map, String prop) {
           return map.isNull(BORDER_RIGHT_WIDTH) || map.getDouble(BORDER_RIGHT_WIDTH) == 0d;
         case BORDER_BOTTOM_WIDTH:
           return map.isNull(BORDER_BOTTOM_WIDTH) || map.getDouble(BORDER_BOTTOM_WIDTH) == 0d;
-        case OVERFLOW: // We do nothing with this right now.
-          return true;
         default:
           return false;
       }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index 1915b6eb48fb..8d6a2abea8c1 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -37,6 +37,7 @@
 import com.facebook.react.uimanager.RootView;
 import com.facebook.react.uimanager.RootViewUtil;
 import com.facebook.react.uimanager.ViewGroupDrawingOrderHelper;
+import com.facebook.react.uimanager.ViewProps;
 import com.facebook.yoga.YogaConstants;
 import javax.annotation.Nullable;
 
@@ -682,12 +683,12 @@ protected void dispatchDraw(Canvas canvas) {
   private void dispatchOverflowDraw(Canvas canvas) {
     if (mOverflow != null) {
       switch (mOverflow) {
-        case "visible":
+        case ViewProps.VISIBLE:
           if (mPath != null) {
             mPath.rewind();
           }
           break;
-        case "hidden":
+        case ViewProps.HIDDEN:
           if (mReactBackgroundDrawable != null) {
             float left = 0f;
             float top = 0f;

From b81c8b51fc6fe3c2dece72e3fe500e175613c5d4 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Fri, 29 Jun 2018 12:07:02 -0700
Subject: [PATCH 0959/1109] RN: Add Support for `overflow` on Android (Take 2)

Summary:
Adds support for the `overflow` style property on React Native for Android.

This is the second attempt to do this. See https://github.com/facebook/react-native/commit/6110a4cc75bf8f285ff091cc175b9ebf737f88fc (D8666509) for the first attempt.

Similar to the first attempt, this sets `setClipChildren(false)` by default on all `ViewGroup` instances. However, this differs in how it implements `overflow: hidden`. Instead of conditionally setting `setClipChildren`, this manually clips children to the `ViewGroup`'s bounds  (which was incidentally what we were doing for background + border radius already).

Reviewed By: achen1

Differential Revision: D8690805

fbshipit-source-id: 58757825cd9d138c18c8758918d85b4ca1915f87
---
 .../facebook/react/uimanager/ViewProps.java   | 11 +++++-----
 .../react/views/view/ReactViewGroup.java      | 20 ++++++++++++-------
 2 files changed, 19 insertions(+), 12 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
index 11f09b0b6805..29ed6e96c0e0 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
@@ -24,7 +24,6 @@ public class ViewProps {
   public static final String ALIGN_ITEMS = "alignItems";
   public static final String ALIGN_SELF = "alignSelf";
   public static final String ALIGN_CONTENT = "alignContent";
-  public static final String OVERFLOW = "overflow";
   public static final String DISPLAY = "display";
   public static final String BOTTOM = "bottom";
   public static final String COLLAPSABLE = "collapsable";
@@ -74,9 +73,6 @@ public class ViewProps {
   public static final String MIN_HEIGHT = "minHeight";
   public static final String MAX_HEIGHT = "maxHeight";
 
-  public static final String HIDDEN = "hidden";
-  public static final String VISIBLE = "visible";
-
   public static final String ASPECT_RATIO = "aspectRatio";
 
   // Props that sometimes may prevent us from collapsing views
@@ -103,6 +99,10 @@ public class ViewProps {
   public static final String TEXT_DECORATION_LINE = "textDecorationLine";
   public static final String TEXT_BREAK_STRATEGY = "textBreakStrategy";
   public static final String OPACITY = "opacity";
+  public static final String OVERFLOW = "overflow";
+
+  public static final String HIDDEN = "hidden";
+  public static final String VISIBLE = "visible";
 
   public static final String ALLOW_FONT_SCALING = "allowFontScaling";
   public static final String INCLUDE_FONT_PADDING = "includeFontPadding";
@@ -169,7 +169,6 @@ public class ViewProps {
               FLEX_SHRINK,
               FLEX_WRAP,
               JUSTIFY_CONTENT,
-              OVERFLOW,
               ALIGN_CONTENT,
               DISPLAY,
 
@@ -257,6 +256,8 @@ public static boolean isLayoutOnly(ReadableMap map, String prop) {
           return map.isNull(BORDER_RIGHT_WIDTH) || map.getDouble(BORDER_RIGHT_WIDTH) == 0d;
         case BORDER_BOTTOM_WIDTH:
           return map.isNull(BORDER_BOTTOM_WIDTH) || map.getDouble(BORDER_BOTTOM_WIDTH) == 0d;
+        case OVERFLOW:
+          return map.isNull(OVERFLOW) || VISIBLE.equals(map.getString(OVERFLOW));
         default:
           return false;
       }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index 8d6a2abea8c1..bdd522bd2a60 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -113,6 +113,7 @@ public void onLayoutChange(
 
   public ReactViewGroup(Context context) {
     super(context);
+    setClipChildren(false);
     mDrawingOrderHelper = new ViewGroupDrawingOrderHelper(this);
   }
 
@@ -689,12 +690,14 @@ private void dispatchOverflowDraw(Canvas canvas) {
           }
           break;
         case ViewProps.HIDDEN:
-          if (mReactBackgroundDrawable != null) {
-            float left = 0f;
-            float top = 0f;
-            float right = getWidth();
-            float bottom = getHeight();
+          float left = 0f;
+          float top = 0f;
+          float right = getWidth();
+          float bottom = getHeight();
+
+          boolean hasClipPath = false;
 
+          if (mReactBackgroundDrawable != null) {
             final RectF borderWidth = mReactBackgroundDrawable.getDirectionAwareBorderInsets();
 
             if (borderWidth.top > 0
@@ -817,10 +820,13 @@ private void dispatchOverflowDraw(Canvas canvas) {
                 },
                 Path.Direction.CW);
               canvas.clipPath(mPath);
-            } else {
-              canvas.clipRect(new RectF(left, top, right, bottom));
+              hasClipPath = true;
             }
           }
+
+          if (!hasClipPath) {
+            canvas.clipRect(new RectF(left, top, right, bottom));
+          }
           break;
         default:
           break;

From 712c2ed5d2f0e2988c3cff276b05c50b7f408ce2 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 29 Jun 2018 12:09:57 -0700
Subject: [PATCH 0960/1109] Fabric: Getting rid of `std::to_string()`

Summary:
@public
Suddenly, it is not supported on Android.
Luckelly `folly:to<std::string>()` is as good as `std::to_string()`.

Reviewed By: mdvacca

Differential Revision: D8655538

fbshipit-source-id: 2b3b970f6a261253aaa6b22dba8338dc66b7195d
---
 ReactCommon/fabric/attributedstring/conversions.h        | 2 +-
 ReactCommon/fabric/core/shadownode/ShadowNode.cpp        | 4 ++--
 ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp | 6 +++---
 3 files changed, 6 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/fabric/attributedstring/conversions.h b/ReactCommon/fabric/attributedstring/conversions.h
index 478d423517f0..7e63dc1a431c 100644
--- a/ReactCommon/fabric/attributedstring/conversions.h
+++ b/ReactCommon/fabric/attributedstring/conversions.h
@@ -50,7 +50,7 @@ inline void fromDynamic(const folly::dynamic &value, FontWeight &result) {
 }
 
 inline std::string toString(const FontWeight &fontWeight) {
-  return std::to_string((int)fontWeight);
+  return folly::to<std::string>((int)fontWeight);
 }
 
 inline void fromDynamic(const folly::dynamic &value, FontStyle &result) {
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 54e1465eb19e..ccb7fc1cdd0a 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -162,7 +162,7 @@ std::string ShadowNode::getDebugName() const {
 }
 
 std::string ShadowNode::getDebugValue() const {
-  return "r" + std::to_string(revision_) + (getSealed() ? "/sealed" : "");
+  return "r" + folly::to<std::string>(revision_) + (getSealed() ? "/sealed" : "");
 }
 
 SharedDebugStringConvertibleList ShadowNode::getDebugChildren() const {
@@ -181,7 +181,7 @@ SharedDebugStringConvertibleList ShadowNode::getDebugChildren() const {
 SharedDebugStringConvertibleList ShadowNode::getDebugProps() const {
   SharedDebugStringConvertibleList list = {};
 
-  list.push_back(std::make_shared<DebugStringConvertibleItem>("tag", std::to_string(tag_)));
+  list.push_back(std::make_shared<DebugStringConvertibleItem>("tag", folly::to<std::string>(tag_)));
 
   SharedShadowNode sourceNode = getSourceNode();
   if (sourceNode) {
diff --git a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
index fd728dd7a417..c5f07453749c 100644
--- a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
+++ b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
@@ -166,20 +166,20 @@ SharedDebugStringConvertibleList TreeMutationInstruction::getDebugProps() const
       return SharedDebugStringConvertibleList {
         std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("childNode", newChildNode_->getDebugDescription(options)),
-        std::make_shared<DebugStringConvertibleItem>("index", std::to_string(index_))
+        std::make_shared<DebugStringConvertibleItem>("index", folly::to<std::string>(index_))
       };
     case Removal:
       return SharedDebugStringConvertibleList {
         std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("childNode", oldChildNode_->getDebugDescription(options)),
-        std::make_shared<DebugStringConvertibleItem>("index", std::to_string(index_))
+        std::make_shared<DebugStringConvertibleItem>("index", folly::to<std::string>(index_))
       };
     case Replacement:
       return SharedDebugStringConvertibleList {
         std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("oldChildNode", oldChildNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("newChildNode", newChildNode_->getDebugDescription(options)),
-        std::make_shared<DebugStringConvertibleItem>("index", std::to_string(index_))
+        std::make_shared<DebugStringConvertibleItem>("index", folly::to<std::string>(index_))
       };
   }
 }

From 62f9ced099fee68cac7bed6d6e3516acd826508a Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 29 Jun 2018 12:09:59 -0700
Subject: [PATCH 0961/1109] Fabric: Subtle changes that make GCC compiler happy

Summary:
@public
Most of them are legit issues which should not be compilable anyways (but Clang tolerates thems).

Reviewed By: mdvacca

Differential Revision: D8655539

fbshipit-source-id: 645729fb9d6a120ce1ab2b07542abcdacd72320d
---
 ReactCommon/fabric/core/layout/LayoutableShadowNode.h   | 3 ++-
 ReactCommon/fabric/core/shadownode/ShadowNode.cpp       | 2 ++
 ReactCommon/fabric/debug/DebugStringConvertible.h       | 3 ++-
 ReactCommon/fabric/debug/DebugStringConvertibleItem.h   | 2 ++
 ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp | 9 ++++-----
 ReactCommon/fabric/uimanager/Differentiator.cpp         | 2 +-
 ReactCommon/fabric/uimanager/ShadowTree.h               | 3 +--
 ReactCommon/fabric/view/root/RootProps.cpp              | 3 +--
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h | 2 +-
 9 files changed, 16 insertions(+), 13 deletions(-)

diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
index d664498779dc..3958f6c5ce52 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
@@ -10,6 +10,7 @@
 #include <array>
 #include <cmath>
 #include <vector>
+#include <memory>
 
 #include <fabric/core/LayoutMetrics.h>
 #include <fabric/core/Sealable.h>
@@ -23,7 +24,7 @@ struct LayoutContext;
 
 class LayoutableShadowNode;
 using SharedLayoutableShadowNode = std::shared_ptr<const LayoutableShadowNode>;
-using SharedLayoutableShadowNodeList = std::vector<const SharedLayoutableShadowNode>;
+using SharedLayoutableShadowNodeList = std::vector<SharedLayoutableShadowNode>;
 using LayoutableShadowNodeIterator = std::iterator<std::input_iterator_tag, const SharedLayoutableShadowNode>;
 
 /*
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index ccb7fc1cdd0a..b2182bcd570d 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -7,6 +7,8 @@
 
 #include "ShadowNode.h"
 
+#include <string>
+
 #include <fabric/debug/DebugStringConvertible.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
 
diff --git a/ReactCommon/fabric/debug/DebugStringConvertible.h b/ReactCommon/fabric/debug/DebugStringConvertible.h
index 8ef96d8882fd..d911072987a7 100644
--- a/ReactCommon/fabric/debug/DebugStringConvertible.h
+++ b/ReactCommon/fabric/debug/DebugStringConvertible.h
@@ -8,6 +8,7 @@
 #pragma once
 
 #include <string>
+#include <memory>
 #include <vector>
 
 namespace facebook {
@@ -16,7 +17,7 @@ namespace react {
 class DebugStringConvertible;
 
 using SharedDebugStringConvertible = std::shared_ptr<const DebugStringConvertible>;
-using SharedDebugStringConvertibleList = std::vector<const SharedDebugStringConvertible>;
+using SharedDebugStringConvertibleList = std::vector<SharedDebugStringConvertible>;
 
 struct DebugStringConvertibleOptions {
   bool format {true};
diff --git a/ReactCommon/fabric/debug/DebugStringConvertibleItem.h b/ReactCommon/fabric/debug/DebugStringConvertibleItem.h
index 257ea1db2bc0..e0499cff0502 100644
--- a/ReactCommon/fabric/debug/DebugStringConvertibleItem.h
+++ b/ReactCommon/fabric/debug/DebugStringConvertibleItem.h
@@ -7,6 +7,8 @@
 
 #pragma once
 
+#include <string>
+
 #include <fabric/debug/DebugStringConvertible.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
index 61e4c65f3fdb..f2f2d08a7ee8 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
+++ b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
@@ -8,11 +8,10 @@
 #include "BaseTextShadowNode.h"
 
 #include <fabric/debug/DebugStringConvertibleItem.h>
-
-#include "RawTextShadowNode.h"
-#include "RawTextProps.h"
-#include "TextShadowNode.h"
-#include "TextProps.h"
+#include <fabric/text/RawTextShadowNode.h>
+#include <fabric/text/RawTextProps.h>
+#include <fabric/text/TextShadowNode.h>
+#include <fabric/text/TextProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/uimanager/Differentiator.cpp b/ReactCommon/fabric/uimanager/Differentiator.cpp
index 6e27fa753527..7a2c9a4f613a 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.cpp
+++ b/ReactCommon/fabric/uimanager/Differentiator.cpp
@@ -30,7 +30,7 @@ static void calculateMutationInstructions(
     return;
   }
 
-  std::unordered_set<Tag> insertedTags = {};
+  std::unordered_set<Tag> insertedTags;
   int index = 0;
 
   TreeMutationInstructionList createInstructions = {};
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.h b/ReactCommon/fabric/uimanager/ShadowTree.h
index d056e4b56224..3bb6af8b44dc 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.h
+++ b/ReactCommon/fabric/uimanager/ShadowTree.h
@@ -7,7 +7,6 @@
 
 #include <memory>
 #include <mutex>
-#include <stdatomic.h>
 
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/core/ReactPrimitives.h>
@@ -84,7 +83,7 @@ class ShadowTree final:
   const Tag rootTag_;
   SharedRootShadowNode rootShadowNode_;
   ShadowTreeDelegate *delegate_;
-  mutable std::mutex commitMutex_ {};
+  mutable std::mutex commitMutex_;
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/view/root/RootProps.cpp b/ReactCommon/fabric/view/root/RootProps.cpp
index ec7260b539ef..fe9f711d3ac2 100644
--- a/ReactCommon/fabric/view/root/RootProps.cpp
+++ b/ReactCommon/fabric/view/root/RootProps.cpp
@@ -8,8 +8,7 @@
 #include "RootProps.h"
 
 #include <fabric/view/conversions.h>
-
-#include "YogaLayoutableShadowNode.h"
+#include <fabric/view/YogaLayoutableShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
index 2da836d8a99c..c35b812af77e 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
@@ -26,7 +26,7 @@ class YogaLayoutableShadowNode;
 using SharedYogaConfig = std::shared_ptr<YGConfig>;
 
 using SharedYogaLayoutableShadowNode = std::shared_ptr<const YogaLayoutableShadowNode>;
-using SharedYogaLayoutableShadowNodeList = std::vector<const SharedYogaLayoutableShadowNode>;
+using SharedYogaLayoutableShadowNodeList = std::vector<SharedYogaLayoutableShadowNode>;
 using SharedYogaLayoutableShadowNodeSharedList = std::shared_ptr<const SharedYogaLayoutableShadowNodeList>;
 
 class YogaLayoutableShadowNode:

From 7b1bd4d4f3169de5777c953cb16c40fc844136c6 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Fri, 29 Jun 2018 12:48:38 -0700
Subject: [PATCH 0962/1109] remove useless config in circle ci (#19980)

Summary:
The gradle path is unnecessary.
pass all current ci.
none
 [GENERAL] [INTERNAL] [CI] - remove useless config in circle ci.
Closes https://github.com/facebook/react-native/pull/19980

Differential Revision: D8700298

Pulled By: hramos

fbshipit-source-id: ed50cab035f0d78dc482023460692a2ce137fb48
---
 .circleci/config.yml | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/.circleci/config.yml b/.circleci/config.yml
index 4803f45845c7..336b4dbf2008 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -176,7 +176,7 @@ aliases:
   - &configure-android-path
     name: Configure Environment Variables
     command: |
-      echo 'export PATH=${ANDROID_NDK}:~/react-native/gradle-2.9/bin:~/buck/bin:$PATH' >> $BASH_ENV
+      echo 'export PATH=${ANDROID_NDK}:~/buck/bin:$PATH' >> $BASH_ENV
       source $BASH_ENV
 
   - &install-android-packages

From 5d9326be29be8688f2238c72c18a9037f983c77d Mon Sep 17 00:00:00 2001
From: Sebastian Markbage <sema@fb.com>
Date: Fri, 29 Jun 2018 15:30:30 -0700
Subject: [PATCH 0963/1109] Remove instanceHandle, pass event target instead +
 add dispatchToEmptyTarget

Summary:
Removes the concept of instance handle. Instead we pass the event target
to createNode and don't pass it to subsequent clones.

The life time of the event target is managed by native (the event emitter).
It has to be released manually.

Reviewed By: shergin

Differential Revision: D8688330

fbshipit-source-id: e11b61f147ea9ca4dfb453fe07063ed06f24b7ac
---
 .../facebook/react/fabric/FabricBinding.java  |  9 ++-
 .../react/fabric/FabricUIManager.java         | 31 ++++----
 .../fabric/events/FabricEventEmitter.java     |  7 +-
 .../react/fabric/jsc/FabricJSCBinding.java    | 11 ++-
 .../react/fabric/jsc/jni/FabricJSCBinding.cpp | 72 +++++++++++--------
 .../react/fabric/jsc/jni/FabricJSCBinding.h   |  9 ++-
 .../react/fabric/FabricUIManagerTest.java     | 31 +++-----
 .../componentdescriptor/ComponentDescriptor.h |  2 +-
 .../ConcreteComponentDescriptor.h             |  4 +-
 .../fabric/core/events/EventDispatcher.h      |  2 -
 .../fabric/core/events/EventEmitter.cpp       | 13 +---
 ReactCommon/fabric/core/events/EventEmitter.h |  7 +-
 .../fabric/uimanager/FabricUIManager.cpp      | 40 ++++++-----
 .../fabric/uimanager/FabricUIManager.h        | 26 +++----
 .../uimanager/SchedulerEventDispatcher.cpp    | 10 +--
 .../uimanager/SchedulerEventDispatcher.h      |  2 -
 16 files changed, 134 insertions(+), 142 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
index 0636c17c24ef..4db39a42522f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
@@ -14,12 +14,17 @@ public interface FabricBinding {
 
   void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule);
 
-  long createEventTarget(long jsContextNativePointer, long instanceHandlePointer);
-
   void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
 
   void releaseEventHandler(long jsContextNativePointer, long eventHandlerPointer);
 
+  void dispatchEventToEmptyTarget(
+    long jsContextNativePointer,
+    long eventHandlerPointer,
+    String type,
+    NativeMap payload
+  );
+
   void dispatchEventToTarget(
     long jsContextNativePointer,
     long eventHandlerPointer,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 05ce4025e3ad..87d1850e6742 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -106,7 +106,7 @@ public void setBinding(FabricBinding binding) {
   @Nullable
   @DoNotStrip
   public ReactShadowNode createNode(
-      int reactTag, String viewName, int rootTag, ReadableNativeMap props, long instanceHandle) {
+      int reactTag, String viewName, int rootTag, ReadableNativeMap props, long eventTarget) {
     if (DEBUG) {
       FLog.d(TAG, "createNode \n\ttag: " + reactTag +
           "\n\tviewName: " + viewName +
@@ -119,7 +119,7 @@ public ReactShadowNode createNode(
       ReactShadowNode rootNode = getRootNode(rootTag);
       node.setRootTag(rootNode.getReactTag());
       node.setViewClassName(viewName);
-      node.setInstanceHandle(instanceHandle);
+      node.setInstanceHandle(eventTarget);
       node.setReactTag(reactTag);
       node.setThemedContext(rootNode.getThemedContext());
 
@@ -157,7 +157,7 @@ private ReactStylesDiffMap updateProps(ReactShadowNode node, @Nullable ReadableN
    */
   @Nullable
   @DoNotStrip
-  public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
+  public ReactShadowNode cloneNode(ReactShadowNode node) {
     if (DEBUG) {
       FLog.d(TAG, "cloneNode \n\tnode: " + node);
     }
@@ -166,7 +166,7 @@ public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
       "FabricUIManager.cloneNode")
       .flush();
     try {
-      ReactShadowNode clone = node.mutableCopy(instanceHandle);
+      ReactShadowNode clone = node.mutableCopy(node.getInstanceHandle());
       assertReactShadowNodeCopy(node, clone);
       return clone;
     } catch (Throwable t) {
@@ -184,7 +184,7 @@ public ReactShadowNode cloneNode(ReactShadowNode node, long instanceHandle) {
    */
   @Nullable
   @DoNotStrip
-  public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long instanceHandle) {
+  public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node) {
     if (DEBUG) {
       FLog.d(TAG, "cloneNodeWithNewChildren \n\tnode: " + node);
     }
@@ -193,7 +193,7 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long insta
       "FabricUIManager.cloneNodeWithNewChildren")
       .flush();
     try {
-      ReactShadowNode clone = node.mutableCopyWithNewChildren(instanceHandle);
+      ReactShadowNode clone = node.mutableCopyWithNewChildren(node.getInstanceHandle());
       assertReactShadowNodeCopy(node, clone);
       return clone;
     } catch (Throwable t) {
@@ -212,7 +212,7 @@ public ReactShadowNode cloneNodeWithNewChildren(ReactShadowNode node, long insta
   @Nullable
   @DoNotStrip
   public ReactShadowNode cloneNodeWithNewProps(
-      ReactShadowNode node, @Nullable ReadableNativeMap newProps, long instanceHandle) {
+      ReactShadowNode node, @Nullable ReadableNativeMap newProps) {
     if (DEBUG) {
       FLog.d(TAG, "cloneNodeWithNewProps \n\tnode: " + node + "\n\tprops: " + newProps);
     }
@@ -221,7 +221,7 @@ public ReactShadowNode cloneNodeWithNewProps(
       "FabricUIManager.cloneNodeWithNewProps")
       .flush();
     try {
-      ReactShadowNode clone = node.mutableCopyWithNewProps(instanceHandle,
+      ReactShadowNode clone = node.mutableCopyWithNewProps(node.getInstanceHandle(),
             newProps == null ? null : new ReactStylesDiffMap(newProps));
       assertReactShadowNodeCopy(node, clone);
       return clone;
@@ -242,7 +242,7 @@ public ReactShadowNode cloneNodeWithNewProps(
   @Nullable
   @DoNotStrip
   public ReactShadowNode cloneNodeWithNewChildrenAndProps(
-      ReactShadowNode node, ReadableNativeMap newProps, long instanceHandle) {
+      ReactShadowNode node, ReadableNativeMap newProps) {
     if (DEBUG) {
       FLog.d(TAG, "cloneNodeWithNewChildrenAndProps \n\tnode: " + node + "\n\tnewProps: " + newProps);
     }
@@ -252,7 +252,7 @@ public ReactShadowNode cloneNodeWithNewChildrenAndProps(
       .flush();
     try {
       ReactShadowNode clone =
-          node.mutableCopyWithNewChildrenAndProps(instanceHandle,
+          node.mutableCopyWithNewChildrenAndProps(node.getInstanceHandle(),
               newProps == null ? null : new ReactStylesDiffMap(newProps));
       assertReactShadowNodeCopy(node, clone);
       return clone;
@@ -610,16 +610,9 @@ private void handleException(ReactShadowNode node, Throwable t) {
 
   @Nullable
   @DoNotStrip
-  public long createEventTarget(int reactTag) {
+  public long getEventTarget(int reactTag) {
     long instanceHandle = mNativeViewHierarchyManager.getInstanceHandle(reactTag);
-    long context = mJSContext.get();
-    long eventTarget = mBinding.createEventTarget(context, instanceHandle);
-    if (DEBUG) {
-      FLog.d(
-        TAG,
-        "Created EventTarget: " + eventTarget + " for tag: " + reactTag + " with instanceHandle: " + instanceHandle);
-    }
-    return eventTarget;
+    return instanceHandle;
   }
 
   @DoNotStrip
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
index 4a705bb75055..2d1c01d86922 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/events/FabricEventEmitter.java
@@ -49,7 +49,7 @@ public FabricEventEmitter(ReactApplicationContext context, FabricUIManager fabri
   @Override
   public void receiveEvent(int reactTag, String eventName, @Nullable WritableMap params) {
     try {
-      long eventTarget = mFabricUIManager.createEventTarget(reactTag);
+      long eventTarget = mFabricUIManager.getEventTarget(reactTag);
       mScheduler.scheduleWork(new FabricUIManagerWork(eventTarget, eventName, params));
     } catch (IllegalViewOperationException e) {
       FLog.e(TAG, "Unable to emmit event for tag " + reactTag, e);
@@ -80,7 +80,10 @@ public void run() {
         FLog.e(TAG, "Error sending event " + mEventName, t);
         //TODO: manage exception properly
       } finally{
-        mFabricUIManager.releaseEventTarget(mEventTarget);
+        // TODO(dvacca): We need to only release this after all shadow nodes
+        // have been released. The easiest way would be to adopt the event
+        // emitter approach from the C++ Fabric. For now, we'll just leak.
+        // mFabricUIManager.releaseEventTarget(mEventTarget);
       }
     }
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
index 38bbbfe636fa..92e82d41e51e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
@@ -28,15 +28,20 @@ public class FabricJSCBinding implements FabricBinding {
 
   private static native HybridData initHybrid();
 
-  @Override
-  public native long createEventTarget(long jsContextNativePointer, long instanceHandlePointer);
-
   @Override
   public native void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
 
   @Override
   public native void releaseEventHandler(long jsContextNativePointer, long eventHandlerPointer);
 
+  @Override
+  public native void dispatchEventToEmptyTarget(
+    long jsContextNativePointer,
+    long eventHandlerPointer,
+    String type,
+    NativeMap payload
+  );
+
   @Override
   public native void dispatchEventToTarget(
     long jsContextNativePointer,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
index 9b18298562c6..5717c930b682 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.cpp
@@ -103,9 +103,9 @@ JSValueRef createNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisOb
   int rootTag = (int)JSC_JSValueToNumber(ctx, arguments[2], NULL);
   auto props = JSC_JSValueIsNull(ctx, arguments[3]) ? local_ref<ReadableNativeMap::jhybridobject>(nullptr) :
                JSValueToReadableMapViaJSON(ctx, arguments[3]);;
-  auto instanceHandle = (void *)arguments[4];
+  auto eventTarget = (void *)arguments[4];
 
-  auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get(), (jlong)instanceHandle);
+  auto node = createNode(manager, reactTag, viewName.get(), rootTag, props.get(), (jlong)eventTarget);
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(node.get()));
 }
@@ -117,11 +117,10 @@ JSValueRef cloneNode(JSContextRef ctx, JSObjectRef function, JSObjectRef thisObj
 
   static auto cloneNode =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, jlong)>("cloneNode");
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject)>("cloneNode");
 
   auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
-  auto instanceHandle = (void *)arguments[1];
-  auto newNode = cloneNode(manager, previousNode.get(), (jlong)instanceHandle);
+  auto newNode = cloneNode(manager, previousNode.get());
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
 }
@@ -133,11 +132,10 @@ JSValueRef cloneNodeWithNewChildren(JSContextRef ctx, JSObjectRef function, JSOb
 
   static auto cloneNodeWithNewChildren =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, jlong)>("cloneNodeWithNewChildren");
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject)>("cloneNodeWithNewChildren");
 
   auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
-  auto instanceHandle = (void *)arguments[1];
-  auto newNode = cloneNodeWithNewChildren(manager, previousNode.get(), (jlong)instanceHandle);
+  auto newNode = cloneNodeWithNewChildren(manager, previousNode.get());
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
 }
@@ -149,12 +147,11 @@ JSValueRef cloneNodeWithNewProps(JSContextRef ctx, JSObjectRef function, JSObjec
 
   static auto cloneNodeWithNewProps =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject, jlong)>("cloneNodeWithNewProps");
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject)>("cloneNodeWithNewProps");
 
   auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
   auto props = JSValueToReadableMapViaJSON(ctx, arguments[1]);
-  auto instanceHandle = (void *)arguments[2];
-  auto newNode = cloneNodeWithNewProps(manager, previousNode.get(), props.get(), (jlong)instanceHandle);
+  auto newNode = cloneNodeWithNewProps(manager, previousNode.get(), props.get());
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
 }
@@ -166,12 +163,11 @@ JSValueRef cloneNodeWithNewChildrenAndProps(JSContextRef ctx, JSObjectRef functi
 
   static auto cloneNodeWithNewChildrenAndProps =
     jni::findClassStatic("com/facebook/react/fabric/FabricUIManager")
-      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject, jlong)>("cloneNodeWithNewChildrenAndProps");
+      ->getMethod<alias_ref<JShadowNode>(JShadowNode::javaobject, ReadableNativeMap::javaobject)>("cloneNodeWithNewChildrenAndProps");
 
   auto previousNode = JSValueToJShadowNode(ctx, arguments[0]);
   auto props = JSValueToReadableMapViaJSON(ctx, arguments[1]);
-  auto instanceHandle = (void *)arguments[2];
-  auto newNode = cloneNodeWithNewChildrenAndProps(manager, previousNode.get(), props.get(), (jlong)instanceHandle);
+  auto newNode = cloneNodeWithNewChildrenAndProps(manager, previousNode.get(), props.get());
 
   return JSC_JSObjectMake(ctx, classRef, makePlainGlobalRef(newNode.get()));
 }
@@ -293,25 +289,11 @@ jni::local_ref<FabricJSCBinding::jhybriddata> FabricJSCBinding::initHybrid(
   return makeCxxInstance();
 }
 
-jlong FabricJSCBinding::createEventTarget(
-  jlong jsContextNativePointer,
-  jlong instanceHandlePointer
-) {
-  JSContextRef context = (JSContextRef)jsContextNativePointer;
-  JSValueRef value = (JSValueRef)instanceHandlePointer;
-  // Retain a strong reference to this object.
-  JSC_JSValueProtect(context, value);
-  return (jlong)((void *)value);
-}
-
 void FabricJSCBinding::releaseEventTarget(
   jlong jsContextNativePointer,
   jlong eventTargetPointer
 ) {
-  JSContextRef context = (JSContextRef)jsContextNativePointer;
-  JSValueRef value = (JSValueRef)((void *)eventTargetPointer);
-  // Release this object.
-  JSC_JSValueUnprotect(context, value);
+  // This is now a noop.
 }
 
 void FabricJSCBinding::releaseEventHandler(
@@ -324,6 +306,36 @@ void FabricJSCBinding::releaseEventHandler(
   JSC_JSValueUnprotect(context, value);
 }
 
+void FabricJSCBinding::dispatchEventToEmptyTarget(
+  jlong jsContextNativePointer,
+  jlong eventHandlerPointer,
+  std::string type,
+  NativeMap *payloadMap
+) {
+  JSContextRef context = (JSContextRef)jsContextNativePointer;
+  JSObjectRef eventHandler = (JSObjectRef)((void *)eventHandlerPointer);
+  JSValueRef eventTarget = JSC_JSValueMakeNull(context);
+
+  JSObjectRef thisArg = (JSObjectRef)JSC_JSValueMakeUndefined(context);
+  JSStringRef typeStr = JSC_JSStringCreateWithUTF8CString(context, type.c_str());
+  JSValueRef typeRef = JSC_JSValueMakeString(context, typeStr);
+  JSC_JSStringRelease(context, typeStr);
+  JSValueRef payloadRef = ReadableMapToJSValueViaJSON(context, payloadMap);
+  JSValueRef args[] = {eventTarget, typeRef, payloadRef};
+  JSValueRef exn;
+  JSValueRef result = JSC_JSObjectCallAsFunction(
+    context,
+    eventHandler,
+    thisArg,
+    3,
+    args,
+    &exn
+  );
+  if (!result) {
+    // TODO: Handle error in exn
+  }
+}
+
 void FabricJSCBinding::dispatchEventToTarget(
   jlong jsContextNativePointer,
   jlong eventHandlerPointer,
@@ -392,9 +404,9 @@ void FabricJSCBinding::registerNatives() {
   registerHybrid({
     makeNativeMethod("initHybrid", FabricJSCBinding::initHybrid),
     makeNativeMethod("installFabric", FabricJSCBinding::installFabric),
-    makeNativeMethod("createEventTarget", FabricJSCBinding::createEventTarget),
     makeNativeMethod("releaseEventTarget", FabricJSCBinding::releaseEventTarget),
     makeNativeMethod("releaseEventHandler", FabricJSCBinding::releaseEventHandler),
+    makeNativeMethod("dispatchEventToEmptyTarget", FabricJSCBinding::dispatchEventToEmptyTarget),
     makeNativeMethod("dispatchEventToTarget", FabricJSCBinding::dispatchEventToTarget),
   });
 }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
index 40b7cbd1681f..d47a0bb584d8 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/jni/FabricJSCBinding.h
@@ -27,12 +27,17 @@ class FabricJSCBinding : public jni::HybridClass<FabricJSCBinding> {
 
   static jni::local_ref<jhybriddata> initHybrid(jni::alias_ref<jclass>);
 
-  jlong createEventTarget(jlong jsContextNativePointer, jlong instanceHandlePointer);
-
   void releaseEventTarget(jlong jsContextNativePointer, jlong eventTargetPointer);
 
   void releaseEventHandler(jlong jsContextNativePointer, jlong eventHandlerPointer);
 
+  void dispatchEventToEmptyTarget(
+    jlong jsContextNativePointer,
+    jlong eventHandlerPointer,
+    std::string type,
+    NativeMap *payload
+  );
+
   void dispatchEventToTarget(
     jlong jsContextNativePointer,
     jlong eventHandlerPointer,
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
index ee7e96fb2f06..93f601c5ffaf 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/FabricUIManagerTest.java
@@ -103,7 +103,7 @@ public void testCloneNode() {
     ReactShadowNode child = createViewNode();
     node.addChildAt(child, 0);
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, 0);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node);
 
     assertThat(clonedNode).isNotSameAs(node);
     assertThat(clonedNode.getOriginalReactShadowNode()).isSameAs(node);
@@ -112,27 +112,12 @@ public void testCloneNode() {
     assertThat(clonedNode.getChildAt(0)).isEqualTo(child);
   }
 
-
-  @Test
-  public void testCloneWithInstanceHandle() {
-    ReactShadowNode node = createViewNode();
-
-    long oldInstanceHandle = node.getInstanceHandle();
-    long newInstanceHandle = oldInstanceHandle + 1;
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, newInstanceHandle);
-
-    assertThat(clonedNode).isNotSameAs(node);
-    assertThat(clonedNode.getInstanceHandle()).isSameAs(newInstanceHandle);
-    assertThat(node.getInstanceHandle()).isSameAs(oldInstanceHandle);
-  }
-
-
   @Test
   public void testDefaultSpacingCloning() {
     ReactShadowNode node = createViewNode();
     node.setDefaultPadding(Spacing.LEFT, 10);
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node, 0);
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNode(node);
 
     node.setDefaultPadding(Spacing.LEFT, 20);
     assertThat(clonedNode.getStylePadding(Spacing.LEFT).value).isEqualTo(10f, Offset.offset(0.01f));
@@ -165,7 +150,7 @@ public void testCloneNodeWithNewChildren() {
     ReactShadowNode child = createViewNode();
     node.addChildAt(child, 0);
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node, randomInstanceHandle());
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildren(node);
 
     assertThat(clonedNode.getChildCount()).isZero();
     assertSameFields(clonedNode, node);
@@ -176,7 +161,7 @@ public void testCloneNodeWithNewProps() {
     ReactShadowNode node = createViewNode();
     ReadableNativeMap props = null; // TODO(ayc): Figure out how to create a Native map from tests.
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props, randomInstanceHandle());
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewProps(node, props);
   }
 
   @Test
@@ -184,7 +169,7 @@ public void testCloneNodeWithNewChildrenAndProps() {
     ReactShadowNode node = createViewNode();
     ReadableNativeMap props = null;
 
-    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props, randomInstanceHandle());
+    ReactShadowNode clonedNode = mFabricUIManager.cloneNodeWithNewChildrenAndProps(node, props);
 
     assertThat(clonedNode.getChildCount()).isZero();
   }
@@ -299,10 +284,10 @@ public void testRemoveOriginalNodeReferences() {
     mFabricUIManager.appendChildToSet(childSet, container);
     mFabricUIManager.completeRoot(rootTag, childSet);
 
-    ReactShadowNode aaClone = mFabricUIManager.cloneNodeWithNewProps(aa, null, 0);
-    ReactShadowNode aClone = mFabricUIManager.cloneNodeWithNewChildren(a, 0);
+    ReactShadowNode aaClone = mFabricUIManager.cloneNodeWithNewProps(aa, null);
+    ReactShadowNode aClone = mFabricUIManager.cloneNodeWithNewChildren(a);
     mFabricUIManager.appendChild(aClone, aaClone);
-    ReactShadowNode containerClone = mFabricUIManager.cloneNodeWithNewChildren(container, 0);
+    ReactShadowNode containerClone = mFabricUIManager.cloneNodeWithNewChildren(container);
     mFabricUIManager.appendChild(containerClone, b);
     mFabricUIManager.appendChild(containerClone, aClone);
     List<ReactShadowNode> childSet2 = mFabricUIManager.createChildSet(rootTag);
diff --git a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
index 1718860b4343..53312ed2fb95 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
@@ -85,7 +85,7 @@ class ComponentDescriptor {
    * shadow nodes.
    */
   virtual SharedEventEmitter createEventEmitter(
-    const InstanceHandle &instanceHandle,
+    const EventTarget &eventTarget,
     const Tag &tag
   ) const = 0;
 };
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 2f1f7fcd9e03..82801a7753f3 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -113,10 +113,10 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
   };
 
   virtual SharedEventEmitter createEventEmitter(
-    const InstanceHandle &instanceHandle,
+    const EventTarget &eventTarget,
     const Tag &tag
   ) const override {
-    return std::make_shared<ConcreteEventEmitter>(instanceHandle, tag, eventDispatcher_);
+    return std::make_shared<ConcreteEventEmitter>(eventTarget, tag, eventDispatcher_);
   }
 
 protected:
diff --git a/ReactCommon/fabric/core/events/EventDispatcher.h b/ReactCommon/fabric/core/events/EventDispatcher.h
index 0f61a010eb15..11ba3580850e 100644
--- a/ReactCommon/fabric/core/events/EventDispatcher.h
+++ b/ReactCommon/fabric/core/events/EventDispatcher.h
@@ -28,8 +28,6 @@ class EventDispatcher {
 
 public:
 
-  virtual EventTarget createEventTarget(const InstanceHandle &instanceHandle) const = 0;
-
   /*
    * Dispatches "raw" event using some event-delivery infrastructure.
    */
diff --git a/ReactCommon/fabric/core/events/EventEmitter.cpp b/ReactCommon/fabric/core/events/EventEmitter.cpp
index 9c61be13f0a0..2e99199eea70 100644
--- a/ReactCommon/fabric/core/events/EventEmitter.cpp
+++ b/ReactCommon/fabric/core/events/EventEmitter.cpp
@@ -12,13 +12,10 @@
 namespace facebook {
 namespace react {
 
-EventEmitter::EventEmitter(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher):
-  instanceHandle_(instanceHandle),
+EventEmitter::EventEmitter(const EventTarget &eventTarget, const Tag &tag, const SharedEventDispatcher &eventDispatcher):
+  eventTarget_(eventTarget),
   tag_(tag),
   eventDispatcher_(eventDispatcher) {
-  if (eventDispatcher) {
-    eventTarget_ = createEventTarget();
-  }
 }
 
 EventEmitter::~EventEmitter() {
@@ -49,11 +46,5 @@ void EventEmitter::dispatchEvent(
   eventDispatcher->dispatchEvent(eventTarget_, type, extendedPayload, priority);
 }
 
-EventTarget EventEmitter::createEventTarget() const {
-  const auto &eventDispatcher = eventDispatcher_.lock();
-  assert(eventDispatcher);
-  return eventDispatcher->createEventTarget(instanceHandle_);
-}
-
 } // namespace react
 } // namespace facebook
diff --git a/ReactCommon/fabric/core/events/EventEmitter.h b/ReactCommon/fabric/core/events/EventEmitter.h
index d854b00ba101..3876be111c09 100644
--- a/ReactCommon/fabric/core/events/EventEmitter.h
+++ b/ReactCommon/fabric/core/events/EventEmitter.h
@@ -31,7 +31,7 @@ using SharedEventEmitter = std::shared_ptr<const EventEmitter>;
 class EventEmitter {
 
 public:
-  EventEmitter(const InstanceHandle &instanceHandle, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
+  EventEmitter(const EventTarget &eventTarget, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
   virtual ~EventEmitter();
 
 protected:
@@ -48,12 +48,9 @@ class EventEmitter {
 
 private:
 
-  EventTarget createEventTarget() const;
-
-  InstanceHandle instanceHandle_;
+  mutable EventTarget eventTarget_ {nullptr};
   Tag tag_;
   std::weak_ptr<const EventDispatcher> eventDispatcher_;
-  mutable EventTarget eventTarget_ {nullptr};
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 06bbeb944493..463c537bcdbf 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -97,12 +97,12 @@ UIManagerDelegate *FabricUIManager::getDelegate() {
   return delegate_;
 }
 
-void FabricUIManager::setCreateEventTargetFunction(std::function<CreateEventTargetFunction> createEventTargetFunction) {
-  createEventTargetFunction_ = createEventTargetFunction;
+void FabricUIManager::setDispatchEventToEmptyTargetFunction(std::function<DispatchEventToEmptyTargetFunction> dispatchEventFunction) {
+  dispatchEventToEmptyTargetFunction_ = dispatchEventFunction;
 }
 
-void FabricUIManager::setDispatchEventFunction(std::function<DispatchEventFunction> dispatchEventFunction) {
-  dispatchEventFunction_ = dispatchEventFunction;
+void FabricUIManager::setDispatchEventToTargetFunction(std::function<DispatchEventToTargetFunction> dispatchEventFunction) {
+  dispatchEventToTargetFunction_ = dispatchEventFunction;
 }
 
 void FabricUIManager::setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction) {
@@ -113,12 +113,16 @@ void FabricUIManager::setReleaseEventTargetFunction(std::function<ReleaseEventTa
   releaseEventTargetFunction_ = releaseEventTargetFunction;
 }
 
-EventTarget FabricUIManager::createEventTarget(const InstanceHandle &instanceHandle) const {
-  return createEventTargetFunction_(instanceHandle);
+void FabricUIManager::dispatchEventToEmptyTarget(const std::string &type, const folly::dynamic &payload) const {
+  dispatchEventToEmptyTargetFunction_(
+    eventHandler_,
+    const_cast<std::string &>(type),
+    const_cast<folly::dynamic &>(payload)
+  );
 }
 
-void FabricUIManager::dispatchEvent(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const {
-  dispatchEventFunction_(
+void FabricUIManager::dispatchEventToTarget(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const {
+  dispatchEventToTargetFunction_(
     eventHandler_,
     eventTarget,
     const_cast<std::string &>(type),
@@ -130,7 +134,7 @@ void FabricUIManager::releaseEventTarget(const EventTarget &eventTarget) const {
   releaseEventTargetFunction_(eventTarget);
 }
 
-SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, InstanceHandle instanceHandle) {
+SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int rootTag, folly::dynamic props, EventTarget eventTarget) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::createNode(tag: " << tag << ", name: " << viewName << ", rootTag: " << rootTag << ", props: " << props << ")";
 
   ComponentName componentName = componentNameByReactViewName(viewName);
@@ -141,7 +145,7 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
     componentDescriptor->createShadowNode(
       tag,
       rootTag,
-      componentDescriptor->createEventEmitter(instanceHandle, tag),
+      componentDescriptor->createEventEmitter(eventTarget, tag),
       componentDescriptor->cloneProps(nullptr, rawProps)
     );
 
@@ -154,7 +158,7 @@ SharedShadowNode FabricUIManager::createNode(int tag, std::string viewName, int
   return shadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode, InstanceHandle instanceHandle) {
+SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNode(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
 
@@ -162,7 +166,7 @@ SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode,
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
-      componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
+      componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
       nullptr
     );
 
@@ -170,7 +174,7 @@ SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode,
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode, InstanceHandle instanceHandle) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNode &shadowNode) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildren(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   // Assuming semantic: Cloning with same props but empty children.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
@@ -179,7 +183,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
-      componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
+      componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
@@ -187,7 +191,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props, InstanceHandle instanceHandle) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with same children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
@@ -197,7 +201,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
-      componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
+      componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
       nullptr
     );
 
@@ -205,7 +209,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
   return clonedShadowNode;
 }
 
-SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props, InstanceHandle instanceHandle) {
+SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedShadowNode &shadowNode, folly::dynamic props) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::cloneNodeWithNewChildrenAndProps(shadowNode: " << shadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", props: " << props << ")";
   // Assuming semantic: Cloning with empty children and specified props.
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[shadowNode];
@@ -215,7 +219,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
-      componentDescriptor->createEventEmitter(instanceHandle, shadowNode->getTag()),
+      componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.h b/ReactCommon/fabric/uimanager/FabricUIManager.h
index 3f66913332f3..e33501e3197a 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.h
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.h
@@ -18,8 +18,8 @@
 namespace facebook {
 namespace react {
 
-using CreateEventTargetFunction = EventTarget (InstanceHandle instanceHandle);
-using DispatchEventFunction = void (EventHandler eventHandler, EventTarget eventTarget, std::string type, folly::dynamic payload);
+using DispatchEventToEmptyTargetFunction = void (EventHandler eventHandler, std::string type, folly::dynamic payload);
+using DispatchEventToTargetFunction = void (EventHandler eventHandler, EventTarget eventTarget, std::string type, folly::dynamic payload);
 using ReleaseEventHandlerFunction = void (EventHandler eventHandler);
 using ReleaseEventTargetFunction = void (EventTarget eventTarget);
 
@@ -44,24 +44,24 @@ class FabricUIManager {
   /*
    * Registers callback functions.
    */
-  void setCreateEventTargetFunction(std::function<CreateEventTargetFunction> createEventTargetFunction);
-  void setDispatchEventFunction(std::function<DispatchEventFunction> dispatchEventFunction);
+  void setDispatchEventToEmptyTargetFunction(std::function<DispatchEventToEmptyTargetFunction> dispatchEventFunction);
+  void setDispatchEventToTargetFunction(std::function<DispatchEventToTargetFunction> dispatchEventFunction);
   void setReleaseEventHandlerFunction(std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction);
   void setReleaseEventTargetFunction(std::function<ReleaseEventTargetFunction> releaseEventTargetFunction);
 
 #pragma mark - Native-facing Interface
 
-  EventTarget createEventTarget(const InstanceHandle &instanceHandle) const;
-  void dispatchEvent(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const;
+  void dispatchEventToEmptyTarget(const std::string &type, const folly::dynamic &payload) const;
+  void dispatchEventToTarget(const EventTarget &eventTarget, const std::string &type, const folly::dynamic &payload) const;
   void releaseEventTarget(const EventTarget &eventTarget) const;
 
 #pragma mark - JavaScript/React-facing Interface
 
-  SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, InstanceHandle instanceHandle);
-  SharedShadowNode cloneNode(const SharedShadowNode &node, InstanceHandle instanceHandle);
-  SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node, InstanceHandle instanceHandle);
-  SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props, InstanceHandle instanceHandle);
-  SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps, InstanceHandle instanceHandle);
+  SharedShadowNode createNode(Tag reactTag, std::string viewName, Tag rootTag, folly::dynamic props, EventTarget eventTarget);
+  SharedShadowNode cloneNode(const SharedShadowNode &node);
+  SharedShadowNode cloneNodeWithNewChildren(const SharedShadowNode &node);
+  SharedShadowNode cloneNodeWithNewProps(const SharedShadowNode &node, folly::dynamic props);
+  SharedShadowNode cloneNodeWithNewChildrenAndProps(const SharedShadowNode &node, folly::dynamic newProps);
   void appendChild(const SharedShadowNode &parentNode, const SharedShadowNode &childNode);
   SharedShadowNodeUnsharedList createChildSet(Tag rootTag);
   void appendChildToSet(const SharedShadowNodeUnsharedList &childSet, const SharedShadowNode &childNode);
@@ -73,8 +73,8 @@ class FabricUIManager {
   SharedComponentDescriptorRegistry componentDescriptorRegistry_;
   UIManagerDelegate *delegate_;
   EventHandler eventHandler_;
-  std::function<CreateEventTargetFunction> createEventTargetFunction_;
-  std::function<DispatchEventFunction> dispatchEventFunction_;
+  std::function<DispatchEventToEmptyTargetFunction> dispatchEventToEmptyTargetFunction_;
+  std::function<DispatchEventToTargetFunction> dispatchEventToTargetFunction_;
   std::function<ReleaseEventHandlerFunction> releaseEventHandlerFunction_;
   std::function<ReleaseEventTargetFunction> releaseEventTargetFunction_;
 };
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
index 77d6942535fb..f261499326ba 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.cpp
@@ -26,11 +26,6 @@ void SchedulerEventDispatcher::setUIManager(std::shared_ptr<const FabricUIManage
   uiManager_ = uiManager;
 }
 
-EventTarget SchedulerEventDispatcher::createEventTarget(const InstanceHandle &instanceHandle) const {
-  assert(uiManager_ && "Attempted to create EventTarget after FabricUIManager dies.");
-  return uiManager_->createEventTarget(instanceHandle);
-}
-
 void SchedulerEventDispatcher::dispatchEvent(
   const EventTarget &eventTarget,
   const std::string &type,
@@ -41,14 +36,15 @@ void SchedulerEventDispatcher::dispatchEvent(
     return;
   }
   // TODO: Schedule the event based on priority.
-  uiManager_->dispatchEvent(eventTarget, normalizeEventType(type), payload);
+  uiManager_->dispatchEventToTarget(eventTarget, normalizeEventType(type), payload);
 }
 
 void SchedulerEventDispatcher::releaseEventTarget(const EventTarget &eventTarget) const {
   if (!uiManager_) {
     return;
   }
-  uiManager_->releaseEventTarget(eventTarget);
+  // TODO(shergin): This needs to move to the destructor of EventEmitter. For now we'll leak.
+  // uiManager_->releaseEventTarget(eventTarget);
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
index 847946b57b01..e89735ad9981 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
@@ -31,8 +31,6 @@ class SchedulerEventDispatcher final:
 
 #pragma mark - EventDispatcher
 
-  EventTarget createEventTarget(const InstanceHandle &instanceHandle) const override;
-
   void dispatchEvent(
     const EventTarget &eventTarget,
     const std::string &type,

From 2166d2bb797d2c5fcbff6d3b96f6530989c2e96f Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 29 Jun 2018 19:57:43 -0700
Subject: [PATCH 0964/1109] Fabric: Trivial implementation of prelumiary view
 allocation on iOS

Summary:
@public
We have this feature in the current version of RN, so it would be nice to support that in Fabric as well. This should save us tens of ms of views creation during mounting.
And that's quite easy to do!

Reviewed By: fkgozali

Differential Revision: D8701992

fbshipit-source-id: 4e3049df009ffd65bb43043de388e81795e5e559
---
 React/Fabric/Mounting/RCTComponentViewRegistry.h  | 5 +++++
 React/Fabric/Mounting/RCTComponentViewRegistry.mm | 9 ++++++++-
 React/Fabric/Mounting/RCTMountingManager.h        | 8 ++++++++
 React/Fabric/Mounting/RCTMountingManager.mm       | 7 +++++++
 React/Fabric/RCTScheduler.h                       | 2 +-
 React/Fabric/RCTSurfacePresenter.mm               | 7 +++++--
 6 files changed, 34 insertions(+), 4 deletions(-)

diff --git a/React/Fabric/Mounting/RCTComponentViewRegistry.h b/React/Fabric/Mounting/RCTComponentViewRegistry.h
index 1e747b124da1..a563270999ce 100644
--- a/React/Fabric/Mounting/RCTComponentViewRegistry.h
+++ b/React/Fabric/Mounting/RCTComponentViewRegistry.h
@@ -43,6 +43,11 @@ NS_ASSUME_NONNULL_BEGIN
  */
 - (ReactTag)tagByComponentView:(UIView<RCTComponentViewProtocol> *)componentView;
 
+/**
+ * Creates a component view with a given type and puts it to the recycle pool.
+ */
+- (void)preliminaryCreateComponentViewWithName:(NSString *)componentName;
+
 @end
 
 NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/RCTComponentViewRegistry.mm b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
index 81816f1ea30b..6edbeb75d59b 100644
--- a/React/Fabric/Mounting/RCTComponentViewRegistry.mm
+++ b/React/Fabric/Mounting/RCTComponentViewRegistry.mm
@@ -64,7 +64,7 @@ + (void)unregisterView:(UIView *)view
 
 #endif
 
-const NSInteger RCTComponentViewRegistryRecyclePoolMaxSize = 256;
+const NSInteger RCTComponentViewRegistryRecyclePoolMaxSize = 1024;
 
 @implementation RCTComponentViewRegistry {
   NSMapTable<id, UIView<RCTComponentViewProtocol> *> *_registry;
@@ -121,6 +121,13 @@ - (void)enqueueComponentViewWithName:(NSString *)componentName
   [self _enqueueComponentViewWithName:componentName componentView:componentView];
 }
 
+- (void)preliminaryCreateComponentViewWithName:(NSString *)componentName
+{
+  RCTAssertMainQueue();
+  [self _enqueueComponentViewWithName:componentName
+                        componentView:[self _createComponentViewWithName:componentName]];
+}
+
 - (UIView<RCTComponentViewProtocol> *)componentViewByTag:(ReactTag)tag
 {
   RCTAssertMainQueue();
diff --git a/React/Fabric/Mounting/RCTMountingManager.h b/React/Fabric/Mounting/RCTMountingManager.h
index bf66ac7f5757..89a90ccb7160 100644
--- a/React/Fabric/Mounting/RCTMountingManager.h
+++ b/React/Fabric/Mounting/RCTMountingManager.h
@@ -26,10 +26,18 @@ NS_ASSUME_NONNULL_BEGIN
 /**
  * Transfroms mutation insturctions to mount items and execute them.
  * The order of mutation tnstructions matters.
+ * Can be called from any thread.
  */
 - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions
                                                 rootTag:(ReactTag)rootTag;
 
+/**
+ * Suggests preliminary creation of a component view of given type.
+ * The receiver is free to ignore the request.
+ * Can be called from any thread.
+ */
+- (void)preliminaryCreateComponentViewWithName:(NSString *)componentName;
+
 @end
 
 NS_ASSUME_NONNULL_END
diff --git a/React/Fabric/Mounting/RCTMountingManager.mm b/React/Fabric/Mounting/RCTMountingManager.mm
index 5aa0fa501239..90366db34902 100644
--- a/React/Fabric/Mounting/RCTMountingManager.mm
+++ b/React/Fabric/Mounting/RCTMountingManager.mm
@@ -181,4 +181,11 @@ - (void)_performMountItems:(NSArray<RCTMountItemProtocol> *)mountItems
   [self.delegate mountingManager:self didMountComponentsWithRootTag:rootTag];
 }
 
+- (void)preliminaryCreateComponentViewWithName:(NSString *)componentName
+{
+  RCTExecuteOnMainQueue(^{
+    [self->_componentViewRegistry preliminaryCreateComponentViewWithName:componentName];
+  });
+}
+
 @end
diff --git a/React/Fabric/RCTScheduler.h b/React/Fabric/RCTScheduler.h
index e6a730b788ca..6814046871d7 100644
--- a/React/Fabric/RCTScheduler.h
+++ b/React/Fabric/RCTScheduler.h
@@ -19,7 +19,7 @@ NS_ASSUME_NONNULL_BEGIN
 @class RCTMountingManager;
 
 /**
- * Exacly same semantic as `facebook::react::SchedulerDelegate`.
+ * Exactly same semantic as `facebook::react::SchedulerDelegate`.
  */
 @protocol RCTSchedulerDelegate
 
diff --git a/React/Fabric/RCTSurfacePresenter.mm b/React/Fabric/RCTSurfacePresenter.mm
index 99703c2389ac..e3223804d2c0 100644
--- a/React/Fabric/RCTSurfacePresenter.mm
+++ b/React/Fabric/RCTSurfacePresenter.mm
@@ -67,7 +67,10 @@ - (void)dealloc
   [[NSNotificationCenter defaultCenter] removeObserver:self];
 }
 
-- (void)schedulerDidComputeMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions rootTag:(ReactTag)rootTag
+#pragma mark - RCTSchedulerDelegate
+
+- (void)schedulerDidComputeMutationInstructions:(facebook::react::TreeMutationInstructionList)instructions
+                                        rootTag:(ReactTag)rootTag
 {
   [_mountingManager mutateComponentViewTreeWithMutationInstructions:instructions
                                                             rootTag:rootTag];
@@ -75,7 +78,7 @@ - (void)schedulerDidComputeMutationInstructions:(facebook::react::TreeMutationIn
 
 - (void)schedulerDidRequestPreliminaryViewAllocationWithComponentName:(NSString *)componentName
 {
-  // TODO: To be implemeted.
+  [_mountingManager preliminaryCreateComponentViewWithName:componentName];
 }
 
 #pragma mark - Internal Surface-dedicated Interface

From 6dcadca71282a9a4cbe58e2ea50c0ba0e946a814 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Sun, 1 Jul 2018 16:16:52 -0700
Subject: [PATCH 0965/1109] Add back ImageEditingExample example (#19972)

Summary:
add back missing file.
pass all current ci.
none
 [GENERAL] [INTERNAL] [RNTester] - Add back ImageEditingExample example.
Closes https://github.com/facebook/react-native/pull/19972

Differential Revision: D8711888

Pulled By: TheSavior

fbshipit-source-id: 14070bfbf747f7f59c4039981a9bc83c1c10862b
---
 RNTester/js/ImageEditingExample.js | 303 ++++++++++++++++++++++++++++-
 1 file changed, 302 insertions(+), 1 deletion(-)

diff --git a/RNTester/js/ImageEditingExample.js b/RNTester/js/ImageEditingExample.js
index 830e1276ef6e..0bc25ce26d77 100644
--- a/RNTester/js/ImageEditingExample.js
+++ b/RNTester/js/ImageEditingExample.js
@@ -5,5 +5,306 @@
  * LICENSE file in the root directory of this source tree.
  *
  * @format
- * @flow strict
+ * @flow
  */
+'use strict';
+
+var React = require('react');
+var ReactNative = require('react-native');
+var {
+  CameraRoll,
+  Image,
+  ImageEditor,
+  Platform,
+  ScrollView,
+  StyleSheet,
+  Text,
+  TouchableHighlight,
+  View,
+} = ReactNative;
+
+var PAGE_SIZE = 20;
+
+type ImageOffset = {
+  x: number,
+  y: number,
+};
+
+type ImageSize = {
+  width: number,
+  height: number,
+};
+
+type ImageCropData = {
+  offset: ImageOffset,
+  size: ImageSize,
+  displaySize?: ?ImageSize,
+  resizeMode?: ?any,
+};
+
+class SquareImageCropper extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+  state: any;
+  _isMounted: boolean;
+  _transformData: ImageCropData;
+
+  constructor(props) {
+    super(props);
+    this._isMounted = true;
+    this.state = {
+      randomPhoto: null,
+      measuredSize: null,
+      croppedImageURI: null,
+      cropError: null,
+    };
+    this._fetchRandomPhoto();
+  }
+
+  async _fetchRandomPhoto() {
+    try {
+      const data = await CameraRoll.getPhotos({first: PAGE_SIZE});
+      if (!this._isMounted) {
+        return;
+      }
+      var edges = data.edges;
+      var edge = edges[Math.floor(Math.random() * edges.length)];
+      var randomPhoto = edge && edge.node && edge.node.image;
+      if (randomPhoto) {
+        this.setState({randomPhoto});
+      }
+    } catch (error) {
+      console.warn("Can't get a photo from camera roll", error);
+    }
+  }
+
+  componentWillUnmount() {
+    this._isMounted = false;
+  }
+
+  render() {
+    if (!this.state.measuredSize) {
+      return (
+        <View
+          style={styles.container}
+          onLayout={event => {
+            var measuredWidth = event.nativeEvent.layout.width;
+            if (!measuredWidth) {
+              return;
+            }
+            this.setState({
+              measuredSize: {width: measuredWidth, height: measuredWidth},
+            });
+          }}
+        />
+      );
+    }
+
+    if (!this.state.croppedImageURI) {
+      return this._renderImageCropper();
+    }
+    return this._renderCroppedImage();
+  }
+
+  _renderImageCropper() {
+    if (!this.state.randomPhoto) {
+      return <View style={styles.container} />;
+    }
+    var error = null;
+    if (this.state.cropError) {
+      error = <Text>{this.state.cropError.message}</Text>;
+    }
+    return (
+      <View style={styles.container}>
+        <Text>Drag the image within the square to crop:</Text>
+        <ImageCropper
+          image={this.state.randomPhoto}
+          size={this.state.measuredSize}
+          style={[styles.imageCropper, this.state.measuredSize]}
+          onTransformDataChange={data => (this._transformData = data)}
+        />
+        <TouchableHighlight
+          style={styles.cropButtonTouchable}
+          onPress={this._crop.bind(this)}>
+          <View style={styles.cropButton}>
+            <Text style={styles.cropButtonLabel}>Crop</Text>
+          </View>
+        </TouchableHighlight>
+        {error}
+      </View>
+    );
+  }
+
+  _renderCroppedImage() {
+    return (
+      <View style={styles.container}>
+        <Text>Here is the cropped image:</Text>
+        <Image
+          source={{uri: this.state.croppedImageURI}}
+          style={[styles.imageCropper, this.state.measuredSize]}
+        />
+        <TouchableHighlight
+          style={styles.cropButtonTouchable}
+          onPress={this._reset.bind(this)}>
+          <View style={styles.cropButton}>
+            <Text style={styles.cropButtonLabel}>Try again</Text>
+          </View>
+        </TouchableHighlight>
+      </View>
+    );
+  }
+
+  _crop() {
+    ImageEditor.cropImage(
+      this.state.randomPhoto.uri,
+      this._transformData,
+      croppedImageURI => this.setState({croppedImageURI}),
+      cropError => this.setState({cropError}),
+    );
+  }
+
+  _reset() {
+    this.setState({
+      randomPhoto: null,
+      croppedImageURI: null,
+      cropError: null,
+    });
+    this._fetchRandomPhoto();
+  }
+}
+
+class ImageCropper extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
+  _contentOffset: ImageOffset;
+  _maximumZoomScale: number;
+  _minimumZoomScale: number;
+  _scaledImageSize: ImageSize;
+  _horizontal: boolean;
+
+  componentWillMount() {
+    // Scale an image to the minimum size that is large enough to completely
+    // fill the crop box.
+    var widthRatio = this.props.image.width / this.props.size.width;
+    var heightRatio = this.props.image.height / this.props.size.height;
+    this._horizontal = widthRatio > heightRatio;
+    if (this._horizontal) {
+      this._scaledImageSize = {
+        width: this.props.image.width / heightRatio,
+        height: this.props.size.height,
+      };
+    } else {
+      this._scaledImageSize = {
+        width: this.props.size.width,
+        height: this.props.image.height / widthRatio,
+      };
+      if (Platform.OS === 'android') {
+        // hack to work around Android ScrollView a) not supporting zoom, and
+        // b) not supporting vertical scrolling when nested inside another
+        // vertical ScrollView (which it is, when displayed inside UIExplorer)
+        this._scaledImageSize.width *= 2;
+        this._scaledImageSize.height *= 2;
+        this._horizontal = true;
+      }
+    }
+    this._contentOffset = {
+      x: (this._scaledImageSize.width - this.props.size.width) / 2,
+      y: (this._scaledImageSize.height - this.props.size.height) / 2,
+    };
+    this._maximumZoomScale = Math.min(
+      this.props.image.width / this._scaledImageSize.width,
+      this.props.image.height / this._scaledImageSize.height,
+    );
+    this._minimumZoomScale = Math.max(
+      this.props.size.width / this._scaledImageSize.width,
+      this.props.size.height / this._scaledImageSize.height,
+    );
+    this._updateTransformData(
+      this._contentOffset,
+      this._scaledImageSize,
+      this.props.size,
+    );
+  }
+
+  _onScroll(event) {
+    this._updateTransformData(
+      event.nativeEvent.contentOffset,
+      event.nativeEvent.contentSize,
+      event.nativeEvent.layoutMeasurement,
+    );
+  }
+
+  _updateTransformData(offset, scaledImageSize, croppedImageSize) {
+    var offsetRatioX = offset.x / scaledImageSize.width;
+    var offsetRatioY = offset.y / scaledImageSize.height;
+    var sizeRatioX = croppedImageSize.width / scaledImageSize.width;
+    var sizeRatioY = croppedImageSize.height / scaledImageSize.height;
+
+    var cropData: ImageCropData = {
+      offset: {
+        x: this.props.image.width * offsetRatioX,
+        y: this.props.image.height * offsetRatioY,
+      },
+      size: {
+        width: this.props.image.width * sizeRatioX,
+        height: this.props.image.height * sizeRatioY,
+      },
+    };
+    this.props.onTransformDataChange &&
+      this.props.onTransformDataChange(cropData);
+  }
+
+  render() {
+    return (
+      <ScrollView
+        alwaysBounceVertical={true}
+        automaticallyAdjustContentInsets={false}
+        contentOffset={this._contentOffset}
+        decelerationRate="fast"
+        horizontal={this._horizontal}
+        maximumZoomScale={this._maximumZoomScale}
+        minimumZoomScale={this._minimumZoomScale}
+        onMomentumScrollEnd={this._onScroll.bind(this)}
+        onScrollEndDrag={this._onScroll.bind(this)}
+        showsHorizontalScrollIndicator={false}
+        showsVerticalScrollIndicator={false}
+        style={this.props.style}
+        scrollEventThrottle={16}>
+        <Image source={this.props.image} style={this._scaledImageSize} />
+      </ScrollView>
+    );
+  }
+}
+
+exports.framework = 'React';
+exports.title = 'ImageEditor';
+exports.description = 'Cropping and scaling with ImageEditor';
+exports.examples = [
+  {
+    title: 'Image Cropping',
+    render() {
+      return <SquareImageCropper />;
+    },
+  },
+];
+
+var styles = StyleSheet.create({
+  container: {
+    flex: 1,
+    alignSelf: 'stretch',
+  },
+  imageCropper: {
+    alignSelf: 'center',
+    marginTop: 12,
+  },
+  cropButtonTouchable: {
+    alignSelf: 'center',
+    marginTop: 12,
+  },
+  cropButton: {
+    padding: 12,
+    backgroundColor: 'blue',
+    borderRadius: 4,
+  },
+  cropButtonLabel: {
+    color: 'white',
+    fontSize: 16,
+    fontWeight: '500',
+  },
+});

From 6a16bec882cba809bdf9027367b76f6543b6617d Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Sun, 1 Jul 2018 16:30:40 -0700
Subject: [PATCH 0966/1109] RN: Fix Drawing Rect for ReactScrollView

Summary:
Fixes `ReactScrollView` so that it respects the drawing rect (i.e. the bounding box of the element).

In JavaScript, this is the backing view for `ScrollView` (vertical) on Android.

Reviewed By: fadinghorse

Differential Revision: D8710256

fbshipit-source-id: f3bd96e39b8569cfcb21e486944b70fdb57c12b6
---
 .../src/main/java/com/facebook/react/uimanager/ViewProps.java  | 1 +
 .../java/com/facebook/react/views/scroll/ReactScrollView.java  | 3 +++
 2 files changed, 4 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
index 29ed6e96c0e0..0a353a6b0f24 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
@@ -102,6 +102,7 @@ public class ViewProps {
   public static final String OVERFLOW = "overflow";
 
   public static final String HIDDEN = "hidden";
+  public static final String SCROLL = "scroll";
   public static final String VISIBLE = "visible";
 
   public static final String ALLOW_FONT_SCALING = "allowFontScaling";
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollView.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollView.java
index acf3458ef5f0..57b401cd6fbf 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollView.java
@@ -47,6 +47,7 @@ public class ReactScrollView extends ScrollView implements ReactClippingViewGrou
   private final OnScrollDispatchHelper mOnScrollDispatchHelper = new OnScrollDispatchHelper();
   private final @Nullable OverScroller mScroller;
   private final VelocityHelper mVelocityHelper = new VelocityHelper();
+  private final Rect mRect = new Rect(); // for reuse to avoid allocation
 
   private @Nullable Rect mClippingRect;
   private boolean mDoneFlinging;
@@ -351,6 +352,8 @@ public void draw(Canvas canvas) {
         mEndBackground.draw(canvas);
       }
     }
+    getDrawingRect(mRect);
+    canvas.clipRect(mRect);
     super.draw(canvas);
   }
 

From 5786db3a26c2d28863901a354602290aa4af7f77 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 1 Jul 2018 21:22:21 -0700
Subject: [PATCH 0967/1109] Fabric: Making `fabric/graphics` compilable on
 Android

Summary:
@public
This compiles but this does not work.
To make it actually work we have to implement all missing functions in `Color.cpp` and co.

Reviewed By: fkgozali

Differential Revision: D8655537

fbshipit-source-id: 564fb7131445af81cf05407239dc6ba870cf6b83
---
 ReactCommon/fabric/graphics/BUCK              | 40 ++++++++++++++++---
 ReactCommon/fabric/graphics/ColorComponents.h | 21 ++++++++++
 ReactCommon/fabric/graphics/Geometry.h        | 16 +-------
 .../graphics/platform/android/Color.cpp       | 24 +++++++++++
 .../fabric/graphics/platform/android/Color.h  | 24 +++++++++++
 .../fabric/graphics/platform/android/Float.h  | 28 +++++++++++++
 .../graphics/{ => platform/ios}/Color.cpp     |  3 --
 .../graphics/{ => platform/ios}/Color.h       | 12 ++----
 .../fabric/graphics/platform/ios/Float.h      | 29 ++++++++++++++
 9 files changed, 166 insertions(+), 31 deletions(-)
 create mode 100644 ReactCommon/fabric/graphics/ColorComponents.h
 create mode 100644 ReactCommon/fabric/graphics/platform/android/Color.cpp
 create mode 100644 ReactCommon/fabric/graphics/platform/android/Color.h
 create mode 100644 ReactCommon/fabric/graphics/platform/android/Float.h
 rename ReactCommon/fabric/graphics/{ => platform/ios}/Color.cpp (91%)
 rename ReactCommon/fabric/graphics/{ => platform/ios}/Color.h (77%)
 create mode 100644 ReactCommon/fabric/graphics/platform/ios/Float.h

diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index e0b337da1cd7..78061adc618b 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -12,12 +12,15 @@ if not IS_OSS_BUILD:
 rn_xplat_cxx_library(
     name = "graphics",
     srcs = glob(
-        ["**/*.cpp"],
-        exclude = glob(["tests/**/*.cpp"]),
+        [
+            "*.cpp",
+        ],
     ),
-    headers = glob(
-        ["**/*.h"],
-        exclude = glob(["tests/**/*.h"]),
+    headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "",
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
@@ -32,6 +35,17 @@ rn_xplat_cxx_library(
         "-std=c++14",
         "-Wall",
     ],
+    fbandroid_exported_headers = subdir_glob(
+        [
+            ("platform/android", "**/*.h"),
+        ],
+        prefix = "fabric/graphics",
+    ),
+    fbandroid_srcs = glob(
+        [
+            "platform/android/**/*.cpp",
+        ],
+    ),
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     fbobjc_tests = [
@@ -43,6 +57,22 @@ rn_xplat_cxx_library(
         "$SDKROOT/System/Library/Frameworks/Foundation.framework",
         "$SDKROOT/System/Library/Frameworks/UIKit.framework",
     ],
+    ios_deps = [
+        "xplat//js:RCTImage",
+        "xplat//js/react-native-github:RCTCxxBridge",
+    ],
+    ios_exported_headers = subdir_glob(
+        [
+            ("platform/ios", "*.h"),
+        ],
+        prefix = "fabric/graphics",
+    ),
+    ios_srcs = glob(
+        [
+            "platform/ios/**/*.cpp",
+            "platform/ios/**/*.mm",
+        ],
+    ),
     macosx_tests_override = [],
     platforms = (ANDROID, APPLE),
     preprocessor_flags = [
diff --git a/ReactCommon/fabric/graphics/ColorComponents.h b/ReactCommon/fabric/graphics/ColorComponents.h
new file mode 100644
index 000000000000..489e1888668f
--- /dev/null
+++ b/ReactCommon/fabric/graphics/ColorComponents.h
@@ -0,0 +1,21 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+namespace facebook {
+namespace react {
+
+struct ColorComponents {
+  float red {0};
+  float green {0};
+  float blue {0};
+  float alpha {0};
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/Geometry.h b/ReactCommon/fabric/graphics/Geometry.h
index 6e97ae851af2..3db79088609d 100644
--- a/ReactCommon/fabric/graphics/Geometry.h
+++ b/ReactCommon/fabric/graphics/Geometry.h
@@ -8,25 +8,11 @@
 #include <algorithm>
 #include <tuple>
 
-#include <CoreGraphics/CGBase.h>
+#include <fabric/graphics/Float.h>
 
 namespace facebook {
 namespace react {
 
-/*
- * Exact type of float numbers which ideally should match a type behing
- * platform- and chip-architecture-specific float type.
- */
-using Float = CGFloat;
-
-/*
- * Large positive number signifies that the `Float` values is `undefined`.
- */
-const Float kFloatUndefined = CGFLOAT_MAX;
-
-const Float kFloatMax = CGFLOAT_MAX;
-const Float kFloatMin = CGFLOAT_MIN;
-
 /*
  * Point
  */
diff --git a/ReactCommon/fabric/graphics/platform/android/Color.cpp b/ReactCommon/fabric/graphics/platform/android/Color.cpp
new file mode 100644
index 000000000000..3511eeb3be86
--- /dev/null
+++ b/ReactCommon/fabric/graphics/platform/android/Color.cpp
@@ -0,0 +1,24 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "Color.h"
+
+namespace facebook {
+namespace react {
+
+SharedColor colorFromComponents(ColorComponents components) {
+  // Not implemented.
+  return {};
+}
+
+ColorComponents colorComponentsFromColor(SharedColor color) {
+  // Not implemented.
+  return {};
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/platform/android/Color.h b/ReactCommon/fabric/graphics/platform/android/Color.h
new file mode 100644
index 000000000000..761af1d2de05
--- /dev/null
+++ b/ReactCommon/fabric/graphics/platform/android/Color.h
@@ -0,0 +1,24 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/graphics/ColorComponents.h>
+
+namespace facebook {
+namespace react {
+
+using Color = float;
+using SharedColor = std::shared_ptr<Color>;
+
+SharedColor colorFromComponents(ColorComponents components);
+ColorComponents colorComponentsFromColor(SharedColor color);
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/platform/android/Float.h b/ReactCommon/fabric/graphics/platform/android/Float.h
new file mode 100644
index 000000000000..8351a8923223
--- /dev/null
+++ b/ReactCommon/fabric/graphics/platform/android/Float.h
@@ -0,0 +1,28 @@
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
+
+#pragma once
+
+#include <limits>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Exact type of float numbers which ideally should match a type behing
+ * platform- and chip-architecture-specific float type.
+ */
+using Float = float;
+
+/*
+ * Large positive number signifies that the `Float` values is `undefined`.
+ */
+const Float kFloatUndefined = std::numeric_limits<Float>::max();
+
+const Float kFloatMax = std::numeric_limits<Float>::max();
+const Float kFloatMin = std::numeric_limits<Float>::min();
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/graphics/Color.cpp b/ReactCommon/fabric/graphics/platform/ios/Color.cpp
similarity index 91%
rename from ReactCommon/fabric/graphics/Color.cpp
rename to ReactCommon/fabric/graphics/platform/ios/Color.cpp
index 151e2923a403..db03a0f4af29 100644
--- a/ReactCommon/fabric/graphics/Color.cpp
+++ b/ReactCommon/fabric/graphics/platform/ios/Color.cpp
@@ -6,9 +6,6 @@
  */
 
 #include "Color.h"
-#include <CoreGraphics/CoreGraphics.h>
-#include <CoreGraphics/CGColor.h>
-#include <cassert>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/graphics/Color.h b/ReactCommon/fabric/graphics/platform/ios/Color.h
similarity index 77%
rename from ReactCommon/fabric/graphics/Color.h
rename to ReactCommon/fabric/graphics/platform/ios/Color.h
index f7622d213bae..019663e734cc 100644
--- a/ReactCommon/fabric/graphics/Color.h
+++ b/ReactCommon/fabric/graphics/platform/ios/Color.h
@@ -7,22 +7,18 @@
 
 #pragma once
 
-#include <CoreGraphics/CoreGraphics.h>
 #include <memory>
 
+#include <fabric/graphics/Float.h>
+
+#include <fabric/graphics/ColorComponents.h>
+
 namespace facebook {
 namespace react {
 
 using Color = CGColor;
 using SharedColor = std::shared_ptr<Color>;
 
-struct ColorComponents {
-  float red {0};
-  float green {0};
-  float blue {0};
-  float alpha {0};
-};
-
 SharedColor colorFromComponents(ColorComponents components);
 ColorComponents colorComponentsFromColor(SharedColor color);
 
diff --git a/ReactCommon/fabric/graphics/platform/ios/Float.h b/ReactCommon/fabric/graphics/platform/ios/Float.h
new file mode 100644
index 000000000000..fec03a6846d1
--- /dev/null
+++ b/ReactCommon/fabric/graphics/platform/ios/Float.h
@@ -0,0 +1,29 @@
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
+
+#pragma once
+
+#include <limits>
+#include <CoreGraphics/CoreGraphics.h>
+
+namespace facebook {
+namespace react {
+
+/*
+ * Exact type of float numbers which ideally should match a type behing
+ * platform- and chip-architecture-specific float type.
+ */
+using Float = CGFloat;
+
+/*
+ * Large positive number signifies that the `Float` values is `undefined`.
+ */
+const Float kFloatUndefined = std::numeric_limits<Float>::max();
+
+const Float kFloatMax = std::numeric_limits<Float>::max();
+const Float kFloatMin = std::numeric_limits<Float>::min();
+
+} // namespace react
+} // namespace facebook

From ee535fafe3edc6026928a5ebbdda78147f8992a0 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 1 Jul 2018 21:22:22 -0700
Subject: [PATCH 0968/1109] Fabric: Making `fabric/textlayoutmanager`
 compilable on Android

Summary:
@public
This compiles, but it works only on iOS for now.

Reviewed By: mdvacca

Differential Revision: D8655540

fbshipit-source-id: 7e9a73fadb317dd62298af6f347344ac4229a8a5
---
 ReactCommon/fabric/textlayoutmanager/BUCK     | 50 ++++++++++++++---
 .../platform/android/TextLayoutManager.cpp    | 33 ++++++++++++
 .../platform/android/TextLayoutManager.h      | 54 +++++++++++++++++++
 .../ios}/NSTextStorage+FontScaling.h          |  0
 .../ios}/NSTextStorage+FontScaling.m          |  0
 .../ios}/RCTAttributedTextUtils.h             |  0
 .../ios}/RCTAttributedTextUtils.mm            |  0
 .../{ => platform/ios}/RCTFontProperties.h    |  0
 .../{ => platform/ios}/RCTFontUtils.h         |  0
 .../{ => platform/ios}/RCTFontUtils.mm        |  0
 .../{ => platform/ios}/RCTTextLayoutManager.h |  0
 .../ios}/RCTTextLayoutManager.mm              |  0
 .../ios}/RCTTextPrimitivesConversions.h       |  0
 .../{ => platform/ios}/TextLayoutManager.h    |  0
 .../{ => platform/ios}/TextLayoutManager.mm   |  0
 15 files changed, 131 insertions(+), 6 deletions(-)
 create mode 100644 ReactCommon/fabric/textlayoutmanager/platform/android/TextLayoutManager.cpp
 create mode 100644 ReactCommon/fabric/textlayoutmanager/platform/android/TextLayoutManager.h
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/NSTextStorage+FontScaling.h (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/NSTextStorage+FontScaling.m (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/RCTAttributedTextUtils.h (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/RCTAttributedTextUtils.mm (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/RCTFontProperties.h (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/RCTFontUtils.h (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/RCTFontUtils.mm (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/RCTTextLayoutManager.h (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/RCTTextLayoutManager.mm (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/RCTTextPrimitivesConversions.h (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/TextLayoutManager.h (100%)
 rename ReactCommon/fabric/textlayoutmanager/{ => platform/ios}/TextLayoutManager.mm (100%)

diff --git a/ReactCommon/fabric/textlayoutmanager/BUCK b/ReactCommon/fabric/textlayoutmanager/BUCK
index 0095affa737f..3ea41084b11d 100644
--- a/ReactCommon/fabric/textlayoutmanager/BUCK
+++ b/ReactCommon/fabric/textlayoutmanager/BUCK
@@ -13,14 +13,14 @@ rn_xplat_cxx_library(
     name = "textlayoutmanager",
     srcs = glob(
         [
-            "**/*.cpp",
-            "**/*.mm",
+            "*.cpp",
         ],
-        exclude = glob(["tests/**/*.cpp"]),
     ),
-    headers = glob(
-        ["**/*.h"],
-        exclude = glob(["tests/**/*.h"]),
+    headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "",
     ),
     header_namespace = "",
     exported_headers = subdir_glob(
@@ -35,6 +35,24 @@ rn_xplat_cxx_library(
         "-std=c++14",
         "-Wall",
     ],
+    fbandroid_exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+            ("platform/android", "*.h"),
+        ],
+        prefix = "fabric/textlayoutmanager",
+    ),
+    fbandroid_headers = subdir_glob(
+        [
+            ("platform/android", "**/*.h"),
+        ],
+        prefix = "",
+    ),
+    fbandroid_srcs = glob(
+        [
+            "platform/android/**/*.cpp",
+        ],
+    ),
     fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
     fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
     fbobjc_tests = [
@@ -46,6 +64,26 @@ rn_xplat_cxx_library(
         "$SDKROOT/System/Library/Frameworks/Foundation.framework",
         "$SDKROOT/System/Library/Frameworks/UIKit.framework",
     ],
+    ios_deps = [
+    ],
+    ios_exported_headers = subdir_glob(
+        [
+            ("platform/ios", "*.h"),
+        ],
+        prefix = "fabric/textlayoutmanager",
+    ),
+    ios_headers = subdir_glob(
+        [
+            ("platform/ios", "**/*.h"),
+        ],
+        prefix = "",
+    ),
+    ios_srcs = glob(
+        [
+            "platform/ios/**/*.cpp",
+            "platform/ios/**/*.mm",
+        ],
+    ),
     macosx_tests_override = [],
     platforms = (ANDROID, APPLE),
     preprocessor_flags = [
diff --git a/ReactCommon/fabric/textlayoutmanager/platform/android/TextLayoutManager.cpp b/ReactCommon/fabric/textlayoutmanager/platform/android/TextLayoutManager.cpp
new file mode 100644
index 000000000000..fd98bfa6b708
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/platform/android/TextLayoutManager.cpp
@@ -0,0 +1,33 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include "TextLayoutManager.h"
+
+namespace facebook {
+namespace react {
+
+TextLayoutManager::TextLayoutManager() {
+}
+
+TextLayoutManager::~TextLayoutManager() {
+}
+
+void *TextLayoutManager::getNativeTextLayoutManager() const {
+  return self_;
+}
+
+Size TextLayoutManager::measure(
+  AttributedString attributedString,
+  ParagraphAttributes paragraphAttributes,
+  LayoutConstraints layoutConstraints
+) const {
+  // Not implemented.
+  return {};
+}
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/textlayoutmanager/platform/android/TextLayoutManager.h b/ReactCommon/fabric/textlayoutmanager/platform/android/TextLayoutManager.h
new file mode 100644
index 000000000000..9da164f30f84
--- /dev/null
+++ b/ReactCommon/fabric/textlayoutmanager/platform/android/TextLayoutManager.h
@@ -0,0 +1,54 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#pragma once
+
+#include <memory>
+
+#include <fabric/attributedstring/AttributedString.h>
+#include <fabric/attributedstring/ParagraphAttributes.h>
+#include <fabric/core/LayoutConstraints.h>
+
+namespace facebook {
+namespace react {
+
+class TextLayoutManager;
+
+using SharedTextLayoutManager = std::shared_ptr<const TextLayoutManager>;
+
+/*
+ * Cross platform facade for Android-specific TextLayoutManager.
+ */
+class TextLayoutManager {
+
+public:
+
+  TextLayoutManager();
+  ~TextLayoutManager();
+
+  /*
+   * Measures `attributedString` using native text rendering infrastructure.
+   */
+  Size measure(
+    AttributedString attributedString,
+    ParagraphAttributes paragraphAttributes,
+    LayoutConstraints layoutConstraints
+  ) const;
+
+  /*
+   * Returns an opaque pointer to platform-specific TextLayoutManager.
+   * Is used on a native views layer to delegate text rendering to the manager.
+   */
+  void *getNativeTextLayoutManager() const;
+
+private:
+  
+  void *self_;
+};
+
+} // namespace react
+} // namespace facebook
diff --git a/ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.h b/ReactCommon/fabric/textlayoutmanager/platform/ios/NSTextStorage+FontScaling.h
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.h
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/NSTextStorage+FontScaling.h
diff --git a/ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.m b/ReactCommon/fabric/textlayoutmanager/platform/ios/NSTextStorage+FontScaling.m
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/NSTextStorage+FontScaling.m
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/NSTextStorage+FontScaling.m
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.h b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTAttributedTextUtils.h
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.h
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/RCTAttributedTextUtils.h
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTAttributedTextUtils.mm
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/RCTAttributedTextUtils.mm
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/RCTAttributedTextUtils.mm
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTFontProperties.h b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTFontProperties.h
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/RCTFontProperties.h
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/RCTFontProperties.h
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.h b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTFontUtils.h
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/RCTFontUtils.h
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/RCTFontUtils.h
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTFontUtils.mm
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/RCTFontUtils.mm
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/RCTFontUtils.mm
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.h b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTTextLayoutManager.h
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.h
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/RCTTextLayoutManager.h
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTTextLayoutManager.mm
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/RCTTextLayoutManager.mm
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/RCTTextLayoutManager.mm
diff --git a/ReactCommon/fabric/textlayoutmanager/RCTTextPrimitivesConversions.h b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTTextPrimitivesConversions.h
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/RCTTextPrimitivesConversions.h
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/RCTTextPrimitivesConversions.h
diff --git a/ReactCommon/fabric/textlayoutmanager/TextLayoutManager.h b/ReactCommon/fabric/textlayoutmanager/platform/ios/TextLayoutManager.h
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/TextLayoutManager.h
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/TextLayoutManager.h
diff --git a/ReactCommon/fabric/textlayoutmanager/TextLayoutManager.mm b/ReactCommon/fabric/textlayoutmanager/platform/ios/TextLayoutManager.mm
similarity index 100%
rename from ReactCommon/fabric/textlayoutmanager/TextLayoutManager.mm
rename to ReactCommon/fabric/textlayoutmanager/platform/ios/TextLayoutManager.mm

From c4a66a89a28152cd4b81e2b0f80ab3aac34d6872 Mon Sep 17 00:00:00 2001
From: Alexey Kureev <kureev@fb.com>
Date: Mon, 2 Jul 2018 09:33:08 -0700
Subject: [PATCH 0969/1109] Code clean-ups and createServer migration

Summary:
Scope of the diff:

1. Middleware
`react-native-github/local-cli` and `react-native-internal-cli` uses a very similar set of middlewares (internal cli extends github version), so I decided to move it to a standalone file (middleware manager) in order to remove duplications and increase readability.

2. Types
Seems that after Flow upgrade to version 0.68 there were many type issues to resolve, so all of them were auto-mocked. This is fine, but I'd like to see Flow assists me with `Metro.createServer` -> `Metro.runServer` migration. Hence, I decided to resolve flow mocks, related to runServer.

3. `runServer` signature
In `react-native-github` repo I cleaned up `runServer` signature by removing `startCallback` and `readyCallback` from the function parameters and moved them to `runServer` instead.

4. Replace `createServer` by `runServer`
In `react-native-github` repo, `createServer` has been replaced by `runServer`. __Some of arguments are not mapped__.

Note that this diff will partially break argument mapping. This is intentional. @[100000044482482:ives] will fix it with a new config package.

Reviewed By: mjesun

Differential Revision: D8711717

fbshipit-source-id: a843ab576360ff7242099910d8f25a9cb0a388c0
---
 .../server/middleware/MiddlewareManager.js    |  70 +++++++
 .../middleware/getDevToolsMiddleware.js       |   4 +-
 local-cli/server/runServer.js                 | 190 ++++--------------
 local-cli/server/server.js                    |  28 +--
 4 files changed, 113 insertions(+), 179 deletions(-)
 create mode 100644 local-cli/server/middleware/MiddlewareManager.js

diff --git a/local-cli/server/middleware/MiddlewareManager.js b/local-cli/server/middleware/MiddlewareManager.js
new file mode 100644
index 000000000000..78b69c777ab2
--- /dev/null
+++ b/local-cli/server/middleware/MiddlewareManager.js
@@ -0,0 +1,70 @@
+/**
+ * Copyright (c) 2013-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @strict
+ * @flow
+ */
+
+const compression = require('compression');
+const connect = require('connect');
+const errorhandler = require('errorhandler');
+const morgan = require('morgan');
+const path = require('path');
+const serveStatic = require('serve-static');
+const WebSocketServer = require('ws').Server;
+
+const indexPageMiddleware = require('./indexPage');
+const copyToClipBoardMiddleware = require('./copyToClipBoardMiddleware');
+const loadRawBodyMiddleware = require('./loadRawBodyMiddleware');
+const openStackFrameInEditorMiddleware = require('./openStackFrameInEditorMiddleware');
+const statusPageMiddleware = require('./statusPageMiddleware.js');
+const systraceProfileMiddleware = require('./systraceProfileMiddleware.js');
+const getDevToolsMiddleware = require('./getDevToolsMiddleware');
+
+type Options = {
+  +watchFolders: $ReadOnlyArray<string>,
+  +host?: string,
+}
+
+type WebSocketProxy = {
+  server: WebSocketServer,
+  isChromeConnected: () => boolean,
+};
+type Connect = any;
+
+module.exports = class MiddlewareManager {
+  app: Connect;
+  options: Options;
+
+  constructor(options: Options) {
+    const debuggerUIFolder = path.join(__dirname, 'util', 'debugger-ui');
+
+    this.options = options;
+    this.app = connect()
+      .use(loadRawBodyMiddleware)
+      .use(compression())
+      .use('/debugger-ui', serveStatic(debuggerUIFolder))
+      .use(openStackFrameInEditorMiddleware(this.options))
+      .use(copyToClipBoardMiddleware)
+      .use(statusPageMiddleware)
+      .use(systraceProfileMiddleware)
+      .use(indexPageMiddleware)
+      .use(morgan('combined'))
+      .use(errorhandler());
+  }
+
+  serveStatic = (folder: string) => {
+    this.app.use(serveStatic(folder));
+  };
+
+  getConnectInstance = () => this.app;
+
+  attachDevToolsSocket = (socket: WebSocketProxy) => {
+    this.app.use(
+      getDevToolsMiddleware(this.options, () => socket.isChromeConnected()),
+    );
+  };
+};
diff --git a/local-cli/server/middleware/getDevToolsMiddleware.js b/local-cli/server/middleware/getDevToolsMiddleware.js
index 23ca15ee5a38..77aab8df9578 100644
--- a/local-cli/server/middleware/getDevToolsMiddleware.js
+++ b/local-cli/server/middleware/getDevToolsMiddleware.js
@@ -27,8 +27,8 @@ function launchDevTools({host, watchFolders}, isChromeConnected) {
   // Explicit config always wins
   var customDebugger = process.env.REACT_DEBUGGER;
   if (customDebugger) {
-    var projects = watchFolders.map(escapePath).join(' ');
-    var command = customDebugger + ' ' + projects;
+    var folders = watchFolders.map(escapePath).join(' ');
+    var command = customDebugger + ' ' + folders;
     console.log('Starting custom debugger by executing: ' + command);
     exec(command, function(error, stdout, stderr) {
       if (error !== null) {
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index e2d57d4b1ebc..59f822f44dad 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -14,132 +14,69 @@ require('../../setupBabel')();
 
 const Metro = require('metro');
 
-const HmrServer = require('metro/src/HmrServer');
-
 const {Terminal} = require('metro-core');
 
-const attachWebsocketServer = require('metro/src/lib/attachWebsocketServer');
-const compression = require('compression');
-const connect = require('connect');
-const copyToClipBoardMiddleware = require('./middleware/copyToClipBoardMiddleware');
-const defaultAssetExts = Metro.defaults.assetExts;
-const defaultSourceExts = Metro.defaults.sourceExts;
-const defaultPlatforms = Metro.defaults.platforms;
-const defaultProvidesModuleNodeModules =
-  Metro.defaults.providesModuleNodeModules;
-const errorhandler = require('errorhandler');
-const fs = require('fs');
-const getDevToolsMiddleware = require('./middleware/getDevToolsMiddleware');
-const http = require('http');
-const https = require('https');
-const indexPageMiddleware = require('./middleware/indexPage');
-const loadRawBodyMiddleware = require('./middleware/loadRawBodyMiddleware');
-const messageSocket = require('./util/messageSocket.js');
-const morgan = require('morgan');
-const openStackFrameInEditorMiddleware = require('./middleware/openStackFrameInEditorMiddleware');
 const path = require('path');
-const serveStatic = require('serve-static');
-const statusPageMiddleware = require('./middleware/statusPageMiddleware.js');
-const systraceProfileMiddleware = require('./middleware/systraceProfileMiddleware.js');
-const webSocketProxy = require('./util/webSocketProxy.js');
-
-const {ASSET_REGISTRY_PATH} = require('../core/Constants');
+const MiddlewareManager = require('./middleware/MiddlewareManager');
 
 import type {ConfigT} from 'metro';
-/* $FlowFixMe(site=react_native_oss) */
-import type {Reporter} from 'metro/src/lib/reporting';
 
 export type Args = {|
   +assetExts: $ReadOnlyArray<string>,
+  +cert: string,
+  +customLogReporterPath?: string,
   +host: string,
+  +https: boolean,
   +maxWorkers: number,
+  +key: string,
   +nonPersistent: boolean,
   +platforms: $ReadOnlyArray<string>,
   +port: number,
   +projectRoot: string,
+  +providesModuleNodeModules: Array<string>,
   +resetCache: boolean,
   +sourceExts: $ReadOnlyArray<string>,
+  +transformer?: string,
   +verbose: boolean,
   +watchFolders: $ReadOnlyArray<string>,
 |};
 
-function runServer(
-  args: Args,
-  config: ConfigT,
-  // FIXME: this is weird design. The top-level should pass down a custom
-  // reporter rather than passing it up as argument to an event.
-  startedCallback: (reporter: Reporter) => mixed,
-  readyCallback: (reporter: Reporter) => mixed,
-) {
-  var wsProxy = null;
-  var ms = null;
-
+async function runServer(args: Args, config: ConfigT) {
   const terminal = new Terminal(process.stdout);
-  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
-   * found when Flow v0.68 was deployed. To see the error delete this comment
-   * and run Flow. */
   const ReporterImpl = getReporterImpl(args.customLogReporterPath || null);
   const reporter = new ReporterImpl(terminal);
-  const packagerServer = getPackagerServer(args, config, reporter);
-  startedCallback(reporter);
-
-  const app = connect()
-    .use(loadRawBodyMiddleware)
-    .use(compression())
-    .use(
-      '/debugger-ui',
-      serveStatic(path.join(__dirname, 'util', 'debugger-ui')),
-    )
-    .use(
-      getDevToolsMiddleware(args, () => wsProxy && wsProxy.isChromeConnected()),
-    )
-    .use(getDevToolsMiddleware(args, () => ms && ms.isChromeConnected()))
-    .use(openStackFrameInEditorMiddleware(args))
-    .use(copyToClipBoardMiddleware)
-    .use(statusPageMiddleware)
-    .use(systraceProfileMiddleware)
-    .use(indexPageMiddleware)
-    .use(packagerServer.processRequest.bind(packagerServer));
-
-  args.watchFolders.forEach(root => app.use(serveStatic(root)));
-
-  app.use(morgan('combined')).use(errorhandler());
-
-  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
-   * found when Flow v0.68 was deployed. To see the error delete this comment
-   * and run Flow. */
-  if (args.https && (!args.key || !args.cert)) {
-    throw new Error('Cannot use https without specifying key and cert options');
-  }
-
-  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
-   * found when Flow v0.68 was deployed. To see the error delete this comment
-   * and run Flow. */
-  const serverInstance = args.https
-    ? https.createServer(
-        {
-          key: fs.readFileSync(args.key),
-          cert: fs.readFileSync(args.cert),
-        },
-        app,
-      )
-    : http.createServer(app);
-
-  serverInstance.listen(args.port, args.host, 511, function() {
-    attachWebsocketServer({
-      httpServer: serverInstance,
-      path: '/hot',
-      websocketServer: new HmrServer(packagerServer),
-    });
-
-    wsProxy = webSocketProxy.attachToServer(serverInstance, '/debugger-proxy');
-    ms = messageSocket.attachToServer(serverInstance, '/message');
-    readyCallback(reporter);
+  const middlewareManager = new MiddlewareManager(args);
+
+  args.watchFolders.forEach(middlewareManager.serveStatic);
+
+  const serverInstance = await Metro.runServer({
+    config: {
+      ...config,
+      hmrEnabled: true,
+      maxWorkers: args.maxWorkers,
+      reporter,
+      secure: args.https,
+      secureKey: args.key,
+      secureCert: args.cert,
+      transformModulePath: args.transformer
+        ? path.resolve(args.transformer)
+        : config.getTransformModulePath(),
+      watch: !args.nonPersistent,
+    },
   });
-  // Disable any kind of automatic timeout behavior for incoming
-  // requests in case it takes the packager more than the default
-  // timeout of 120 seconds to respond to a request.
-  serverInstance.timeout = 0;
+
+  // In Node 8, the default keep-alive for an HTTP connection is 5 seconds. In
+  // early versions of Node 8, this was implemented in a buggy way which caused
+  // some HTTP responses (like those containing large JS bundles) to be
+  // terminated early.
+  //
+  // As a workaround, arbitrarily increase the keep-alive from 5 to 30 seconds,
+  // which should be enough to send even the largest of JS bundles.
+  //
+  // For more info: https://github.com/nodejs/node/issues/13391
+  //
+  // $FlowFixMe
+  serverInstance.keepAliveTimeout = 30000;
 }
 
 function getReporterImpl(customLogReporterPath: ?string) {
@@ -162,53 +99,4 @@ function getReporterImpl(customLogReporterPath: ?string) {
   }
 }
 
-function getPackagerServer(args, config, reporter) {
-  /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an error
-   * found when Flow v0.68 was deployed. To see the error delete this comment
-   * and run Flow. */
-  const transformModulePath = args.transformer
-    ? path.resolve(args.transformer)
-    : config.getTransformModulePath();
-
-  const providesModuleNodeModules =
-    /* $FlowFixMe(>=0.68.0 site=react_native_fb) This comment suppresses an
-     * error found when Flow v0.68 was deployed. To see the error delete this
-     * comment and run Flow. */
-    args.providesModuleNodeModules || defaultProvidesModuleNodeModules;
-
-  return Metro.createServer({
-    asyncRequireModulePath: config.getAsyncRequireModulePath(),
-    assetExts: defaultAssetExts.concat(args.assetExts),
-    assetRegistryPath: ASSET_REGISTRY_PATH,
-    blacklistRE: config.getBlacklistRE(),
-    cacheStores: config.cacheStores,
-    cacheVersion: '3',
-    enableBabelRCLookup: config.getEnableBabelRCLookup(),
-    extraNodeModules: config.extraNodeModules,
-    dynamicDepsInPackages: config.dynamicDepsInPackages,
-    getModulesRunBeforeMainModule: config.getModulesRunBeforeMainModule,
-    getPolyfills: config.getPolyfills,
-    getResolverMainFields: config.getResolverMainFields,
-    getRunModuleStatement: config.getRunModuleStatement,
-    getTransformOptions: config.getTransformOptions,
-    hasteImplModulePath: config.hasteImplModulePath,
-    maxWorkers: args.maxWorkers,
-    platforms: defaultPlatforms.concat(args.platforms),
-    polyfillModuleNames: config.getPolyfillModuleNames(),
-    postMinifyProcess: config.postMinifyProcess,
-    postProcessBundleSourcemap: config.postProcessBundleSourcemap,
-    projectRoot: args.projectRoot,
-    providesModuleNodeModules: providesModuleNodeModules,
-    reporter,
-    resetCache: args.resetCache,
-    resolveRequest: config.resolveRequest,
-    sourceExts: args.sourceExts.concat(defaultSourceExts),
-    transformModulePath: transformModulePath,
-    verbose: args.verbose,
-    watch: !args.nonPersistent,
-    watchFolders: args.watchFolders,
-    workerPath: config.getWorkerPath(),
-  });
-}
-
 module.exports = runServer;
diff --git a/local-cli/server/server.js b/local-cli/server/server.js
index f74f7f16a79b..42423f558375 100644
--- a/local-cli/server/server.js
+++ b/local-cli/server/server.js
@@ -19,34 +19,10 @@ import type {Args as RunServerArgs} from './runServer';
 /**
  * Starts the React Native Packager Server.
  */
-function server(argv: mixed, config: RNConfig, args: Object) {
-  const startedCallback = logReporter => {
-    logReporter.update({
-      type: 'initialize_started',
-      port: args.port,
-      projectRoots: args.watchFolders,
-    });
-
-    process.on('uncaughtException', error => {
-      logReporter.update({
-        type: 'initialize_failed',
-        port: args.port,
-        error,
-      });
-
-      process.exit(11);
-    });
-  };
-
-  const readyCallback = logReporter => {
-    logReporter.update({
-      type: 'initialize_done',
-    });
-  };
-  const runServerArgs: RunServerArgs = args;
+function server(argv: mixed, config: RNConfig, args: RunServerArgs) {
   /* $FlowFixMe(site=react_native_fb) ConfigT shouldn't be extendable. */
   const configT: ConfigT = config;
-  runServer(runServerArgs, configT, startedCallback, readyCallback);
+  runServer(args, configT);
 }
 
 module.exports = {

From 27a38dedf1af3295a535c5f72e3e7443c07c1075 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Mon, 2 Jul 2018 09:52:04 -0700
Subject: [PATCH 0970/1109] Enable View flatening optimization by default

Summary: This diff enables view flattening optimizations by default

Reviewed By: wwjholmes, yungsters

Differential Revision: D8699050

fbshipit-source-id: d37d06fe330e223c49a0788e85f6338fd056fd19
---
 .../facebook/react/uimanager/ViewProps.java   | 78 +++++++++----------
 1 file changed, 36 insertions(+), 42 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
index 0a353a6b0f24..58e67ccb7524 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
@@ -212,8 +212,6 @@ public class ViewProps {
               PADDING_START,
               PADDING_END));
 
-  public static boolean sIsOptimizationsEnabled;
-
   public static boolean isLayoutOnly(ReadableMap map, String prop) {
     if (LAYOUT_ONLY_PROPS.contains(prop)) {
       return true;
@@ -222,47 +220,43 @@ public static boolean isLayoutOnly(ReadableMap map, String prop) {
       return AUTO.equals(value) || BOX_NONE.equals(value);
     }
 
-
-    if (sIsOptimizationsEnabled) {
-      switch (prop) {
-        case OPACITY:
-          // null opacity behaves like opacity = 1
-          // Ignore if explicitly set to default opacity.
-          return map.isNull(OPACITY) || map.getDouble(OPACITY) == 1d;
-        case BORDER_RADIUS: // Without a background color or border width set, a border won't show.
-          if (map.hasKey(BACKGROUND_COLOR) && map.getInt(BACKGROUND_COLOR) != Color.TRANSPARENT) {
-            return false;
-          }
-          if (map.hasKey(BORDER_WIDTH)
-            && !map.isNull(BORDER_WIDTH)
-            && map.getDouble(BORDER_WIDTH) != 0d) {
-            return false;
-          }
-          return true;
-        case BORDER_LEFT_COLOR:
-          return map.getInt(BORDER_LEFT_COLOR) == Color.TRANSPARENT;
-        case BORDER_RIGHT_COLOR:
-          return map.getInt(BORDER_RIGHT_COLOR) == Color.TRANSPARENT;
-        case BORDER_TOP_COLOR:
-          return map.getInt(BORDER_TOP_COLOR) == Color.TRANSPARENT;
-        case BORDER_BOTTOM_COLOR:
-          return map.getInt(BORDER_BOTTOM_COLOR) == Color.TRANSPARENT;
-        case BORDER_WIDTH:
-          return map.isNull(BORDER_WIDTH) || map.getDouble(BORDER_WIDTH) == 0d;
-        case BORDER_LEFT_WIDTH:
-          return map.isNull(BORDER_LEFT_WIDTH) || map.getDouble(BORDER_LEFT_WIDTH) == 0d;
-        case BORDER_TOP_WIDTH:
-          return map.isNull(BORDER_TOP_WIDTH) || map.getDouble(BORDER_TOP_WIDTH) == 0d;
-        case BORDER_RIGHT_WIDTH:
-          return map.isNull(BORDER_RIGHT_WIDTH) || map.getDouble(BORDER_RIGHT_WIDTH) == 0d;
-        case BORDER_BOTTOM_WIDTH:
-          return map.isNull(BORDER_BOTTOM_WIDTH) || map.getDouble(BORDER_BOTTOM_WIDTH) == 0d;
-        case OVERFLOW:
-          return map.isNull(OVERFLOW) || VISIBLE.equals(map.getString(OVERFLOW));
-        default:
+    switch (prop) {
+      case OPACITY:
+        // null opacity behaves like opacity = 1
+        // Ignore if explicitly set to default opacity.
+        return map.isNull(OPACITY) || map.getDouble(OPACITY) == 1d;
+      case BORDER_RADIUS: // Without a background color or border width set, a border won't show.
+        if (map.hasKey(BACKGROUND_COLOR) && map.getInt(BACKGROUND_COLOR) != Color.TRANSPARENT) {
           return false;
+        }
+        if (map.hasKey(BORDER_WIDTH)
+          && !map.isNull(BORDER_WIDTH)
+          && map.getDouble(BORDER_WIDTH) != 0d) {
+          return false;
+        }
+        return true;
+      case BORDER_LEFT_COLOR:
+        return map.getInt(BORDER_LEFT_COLOR) == Color.TRANSPARENT;
+      case BORDER_RIGHT_COLOR:
+        return map.getInt(BORDER_RIGHT_COLOR) == Color.TRANSPARENT;
+      case BORDER_TOP_COLOR:
+        return map.getInt(BORDER_TOP_COLOR) == Color.TRANSPARENT;
+      case BORDER_BOTTOM_COLOR:
+        return map.getInt(BORDER_BOTTOM_COLOR) == Color.TRANSPARENT;
+      case BORDER_WIDTH:
+        return map.isNull(BORDER_WIDTH) || map.getDouble(BORDER_WIDTH) == 0d;
+      case BORDER_LEFT_WIDTH:
+        return map.isNull(BORDER_LEFT_WIDTH) || map.getDouble(BORDER_LEFT_WIDTH) == 0d;
+      case BORDER_TOP_WIDTH:
+        return map.isNull(BORDER_TOP_WIDTH) || map.getDouble(BORDER_TOP_WIDTH) == 0d;
+      case BORDER_RIGHT_WIDTH:
+        return map.isNull(BORDER_RIGHT_WIDTH) || map.getDouble(BORDER_RIGHT_WIDTH) == 0d;
+      case BORDER_BOTTOM_WIDTH:
+        return map.isNull(BORDER_BOTTOM_WIDTH) || map.getDouble(BORDER_BOTTOM_WIDTH) == 0d;
+      case OVERFLOW:
+        return map.isNull(OVERFLOW) || VISIBLE.equals(map.getString(OVERFLOW));
+      default:
+        return false;
       }
-    }
-    return false;
   }
 }

From fdce93845514a781d01da8cc2c944dbb571f3012 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Mon, 2 Jul 2018 10:41:17 -0700
Subject: [PATCH 0971/1109] fix missing prettier file (#20001)

Summary:
fix missing prettier file
pass all current ci.
https://github.com/facebook/react-native/pull/19987
 [GENERAL] [INTERNAL] [TOOL] - fix missing prettier file.
Closes https://github.com/facebook/react-native/pull/20001

Differential Revision: D8714374

Pulled By: hramos

fbshipit-source-id: acdcb5d84c56d26c55f6262a0a98aefe786de8cb
---
 Libraries/polyfills/babelHelpers.js |  3 +--
 local-cli/runAndroid/runAndroid.js  | 13 +++++++------
 2 files changed, 8 insertions(+), 8 deletions(-)

diff --git a/Libraries/polyfills/babelHelpers.js b/Libraries/polyfills/babelHelpers.js
index 991b4fbfbdb2..f831deaa842f 100644
--- a/Libraries/polyfills/babelHelpers.js
+++ b/Libraries/polyfills/babelHelpers.js
@@ -197,8 +197,7 @@ babelHelpers.get = function _get(target, property, receiver = target) {
   }
 
   return desc.value;
-}
-
+};
 
 // ### inherits ###
 
diff --git a/local-cli/runAndroid/runAndroid.js b/local-cli/runAndroid/runAndroid.js
index cd21b6ac29cf..6835c97bcb0b 100644
--- a/local-cli/runAndroid/runAndroid.js
+++ b/local-cli/runAndroid/runAndroid.js
@@ -354,9 +354,7 @@ function startServerInNewWindow(port) {
   const scriptFile = isWindows
     ? 'launchPackager.bat'
     : 'launchPackager.command';
-  const packagerEnvFilename = isWindows
-    ? '.packager.bat'
-    : '.packager.env';
+  const packagerEnvFilename = isWindows ? '.packager.bat' : '.packager.env';
   const portExportContent = isWindows
     ? `set RCT_METRO_PORT=${port}`
     : `export RCT_METRO_PORT=${port}`;
@@ -373,11 +371,14 @@ function startServerInNewWindow(port) {
     '..',
     '..',
     'scripts',
-    packagerEnvFilename
+    packagerEnvFilename,
   );
-  
+
   // ensure we overwrite file by passing the 'w' flag
-  fs.writeFileSync(packagerEnvFile, portExportContent, {encoding: 'utf8', flag: 'w'});
+  fs.writeFileSync(packagerEnvFile, portExportContent, {
+    encoding: 'utf8',
+    flag: 'w',
+  });
 
   if (process.platform === 'darwin') {
     if (terminal) {

From 54942746d4037e1153e14fcfc95e4edc772d296a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rub=C3=A9n=20Norte?= <rubennorte@fb.com>
Date: Mon, 2 Jul 2018 11:05:31 -0700
Subject: [PATCH 0972/1109] Hotfix to include react-native-windows in hasteImpl
 accepted paths (#20007)

Summary:
Closes https://github.com/facebook/react-native/pull/20007

We removed support for providesModule annotations and maintained support for Haste names in installed modules via `providesModuleNodeModules`, but our default `hasteImpl` doesn't take them into account. We need to find a better way to override core components from plugins but meanwhile this adds an exception for react-native-windows in the default `hasteImpl` to unblock their upgrade to the latest RC.

Fixes https://github.com/facebook/metro/issues/188

Reviewed By: mjesun

Differential Revision: D8695207

fbshipit-source-id: 2ad6cb1e93e600880a148776ac45f6ebd7d205d3
---
 jest/hasteImpl.js       | 12 ++++++++----
 local-cli/core/index.js |  8 ++++++++
 2 files changed, 16 insertions(+), 4 deletions(-)

diff --git a/jest/hasteImpl.js b/jest/hasteImpl.js
index 568f7e8df0d0..e72fa4f37b26 100644
--- a/jest/hasteImpl.js
+++ b/jest/hasteImpl.js
@@ -12,7 +12,10 @@
 
 const path = require('path');
 
-const ROOT = path.join(__dirname, '..');
+const ROOTS = [
+  path.resolve(__dirname, '..') + path.sep,
+  path.resolve(__dirname, '../../react-native-windows') + path.sep,
+];
 
 const BLACKLISTED_PATTERNS /*: Array<RegExp> */ = [
   /.*\/__(mocks|tests)__\/.*/,
@@ -33,7 +36,7 @@ const NAME_REDUCERS /*: Array<[RegExp, string]> */ = [
   // strip .js/.js.flow suffix
   [/^(.*)\.js(\.flow)?$/, '$1'],
   // strip .android/.ios/.native/.web suffix
-  [/^(.*)\.(android|ios|native|web)$/, '$1'],
+  [/^(.*)\.(android|ios|native|web|windows)$/, '$1'],
 ];
 
 const haste = {
@@ -63,11 +66,12 @@ function isHastePath(filePath /*: string */) /*: boolean */ {
     return false;
   }
 
-  if (!filePath.startsWith(ROOT)) {
+  const root = ROOTS.find(r => filePath.startsWith(r));
+  if (!root) {
     return false;
   }
 
-  filePath = filePath.substr(ROOT.length + 1);
+  filePath = filePath.substr(root.length);
   if (BLACKLISTED_PATTERNS.some(pattern => pattern.test(filePath))) {
     return false;
   }
diff --git a/local-cli/core/index.js b/local-cli/core/index.js
index d2b3399d177b..4d94aaebef4b 100644
--- a/local-cli/core/index.js
+++ b/local-cli/core/index.js
@@ -72,6 +72,14 @@ const pluginPlatforms = plugins.platforms.reduce((acc, pathToPlatforms) => {
 const defaultRNConfig = {
   hasteImplModulePath: require.resolve('../../jest/hasteImpl'),
 
+  getPlatforms(): Array<string> {
+    return ['ios', 'android', 'windows', 'web'];
+  },
+
+  getProvidesModuleNodeModules(): Array<string> {
+    return ['react-native', 'react-native-windows'];
+  },
+
   getProjectCommands(): Array<CommandT> {
     const commands = plugins.commands.map(pathToCommands => {
       const name = pathToCommands.split(path.sep)[0];

From db2159d0b3fd57556383eff68d32d32246dd9081 Mon Sep 17 00:00:00 2001
From: Yunyu Lin <yyl@fb.com>
Date: Mon, 2 Jul 2018 13:26:38 -0700
Subject: [PATCH 0973/1109] Fix some classes of incorrect Flow errors for
 Animated

Summary: Replace the union with a spread

Reviewed By: blairvanderhoof

Differential Revision: D8715694

fbshipit-source-id: 3b1ce893a065bfc7395b576e485a79f09bacc999
---
 Libraries/Animated/src/Animated.js | 8 ++------
 1 file changed, 2 insertions(+), 6 deletions(-)

diff --git a/Libraries/Animated/src/Animated.js b/Libraries/Animated/src/Animated.js
index f25d2a0796a1..8678b21f14b8 100644
--- a/Libraries/Animated/src/Animated.js
+++ b/Libraries/Animated/src/Animated.js
@@ -16,14 +16,10 @@ const ScrollView = require('ScrollView');
 const Text = require('Text');
 const View = require('View');
 
-const Animated = {
+module.exports = {
+  ...AnimatedImplementation,
   View: AnimatedImplementation.createAnimatedComponent(View),
   Text: AnimatedImplementation.createAnimatedComponent(Text),
   Image: AnimatedImplementation.createAnimatedComponent(Image),
   ScrollView: AnimatedImplementation.createAnimatedComponent(ScrollView),
 };
-
-Object.assign((Animated: Object), AnimatedImplementation);
-
-module.exports = ((Animated: any): typeof AnimatedImplementation &
-  typeof Animated);

From 3b29274cc1dc335fd810cbbef0e32123d8257704 Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Mon, 2 Jul 2018 14:41:49 -0700
Subject: [PATCH 0974/1109] Remove the deprecated `isIPhoneX_deprecated`
 constant (#19920)

Summary:
Cleanup the `isIPhoneX_deprecated` constant which was said to be removed by June 1st 2018.
Closes https://github.com/facebook/react-native/pull/19920

Differential Revision: D8714400

Pulled By: hramos

fbshipit-source-id: 0b0b3a2d7b8098baf0474afea230780c79b2fe14
---
 RNTester/js/SafeAreaViewExample.js | 24 ------------------------
 React/Modules/RCTDeviceInfo.m      | 21 ---------------------
 2 files changed, 45 deletions(-)

diff --git a/RNTester/js/SafeAreaViewExample.js b/RNTester/js/SafeAreaViewExample.js
index 927a26651a4f..0af1d1f1f99a 100644
--- a/RNTester/js/SafeAreaViewExample.js
+++ b/RNTester/js/SafeAreaViewExample.js
@@ -64,21 +64,6 @@ class SafeAreaViewExample extends React.Component<
   }
 }
 
-class IsIPhoneXExample extends React.Component<{}> {
-  render() {
-    return (
-      <View>
-        <Text>
-          Is this an iPhone X:{' '}
-          {DeviceInfo.isIPhoneX_deprecated
-            ? 'Yeah!'
-            : 'Nope. (Or `isIPhoneX_deprecated` was already removed.)'}
-        </Text>
-      </View>
-    );
-  }
-}
-
 exports.examples = [
   {
     title: '<SafeAreaView> Example',
@@ -86,15 +71,6 @@ exports.examples = [
       'SafeAreaView automatically applies paddings reflect the portion of the view that is not covered by other (special) ancestor views.',
     render: () => <SafeAreaViewExample />,
   },
-  {
-    title: 'isIPhoneX_deprecated Example',
-    description:
-      '`DeviceInfo.isIPhoneX_deprecated` returns true only on iPhone X. ' +
-      'Note: This prop is deprecated and will be removed right after June 01, 2018. ' +
-      'Please use this only for a quick and temporary solution. ' +
-      'Use <SafeAreaView> instead.',
-    render: () => <IsIPhoneXExample />,
-  },
 ];
 
 var styles = StyleSheet.create({
diff --git a/React/Modules/RCTDeviceInfo.m b/React/Modules/RCTDeviceInfo.m
index 20e53d55af61..7db187e3063d 100644
--- a/React/Modules/RCTDeviceInfo.m
+++ b/React/Modules/RCTDeviceInfo.m
@@ -51,22 +51,6 @@ - (void)setBridge:(RCTBridge *)bridge
 #endif
 }
 
-static BOOL RCTIsIPhoneX() {
-  static BOOL isIPhoneX = NO;
-  static dispatch_once_t onceToken;
-
-  dispatch_once(&onceToken, ^{
-    RCTAssertMainQueue();
-
-    isIPhoneX = CGSizeEqualToSize(
-      [UIScreen mainScreen].nativeBounds.size,
-      CGSizeMake(1125, 2436)
-    );
-  });
-
-  return isIPhoneX;
-}
-
 static NSDictionary *RCTExportedDimensions(RCTBridge *bridge)
 {
   RCTAssertMainQueue();
@@ -102,11 +86,6 @@ - (void)invalidate
 {
   return @{
     @"Dimensions": RCTExportedDimensions(_bridge),
-    // Note:
-    // This prop is deprecated and will be removed right after June 01, 2018.
-    // Please use this only for a quick and temporary solution.
-    // Use <SafeAreaView> instead.
-    @"isIPhoneX_deprecated": @(RCTIsIPhoneX()),
   };
 }
 

From 18d3648fa8a3e3fd978e981327672b3a0af4c748 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Mon, 2 Jul 2018 14:42:39 -0700
Subject: [PATCH 0975/1109] Simplify `yarn prettier` and make it work on
 windows (#19987)

Summary:
make prettier script works on windows
pass all current ci.
none
 [GENERAL] [INTERNAL] [Script] - make prettier script works on windows.
Closes https://github.com/facebook/react-native/pull/19987

Differential Revision: D8714381

Pulled By: hramos

fbshipit-source-id: 0e5c5a6a5817094edd47918eb57d7f5a281560d6
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index d25acb175634..d25b34bab2aa 100644
--- a/package.json
+++ b/package.json
@@ -126,7 +126,7 @@
     "test-ci": "JEST_JUNIT_OUTPUT=\"reports/junit/js-test-results.xml\" jest --maxWorkers=2 --ci --testResultsProcessor=\"jest-junit\"",
     "flow": "flow",
     "lint": "eslint .",
-    "prettier": "find . -name node_modules -prune -or -name '*.js' -print | xargs prettier --write",
+    "prettier": "prettier \"./**/*.js\" --write",
     "start": "/usr/bin/env bash -c './scripts/packager.sh \"$@\" || true' --",
     "docker-setup-android": "docker pull reactnativeci/android-base:latest",
     "docker-build-android-base": "docker build -t reactnativeci/android-base -f ContainerShip/Dockerfile.android-base .",

From a09c464585e7141bf631a988e25464c86c93a192 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Mon, 2 Jul 2018 17:23:48 -0700
Subject: [PATCH 0976/1109] iOS: avoid crash because of null eventTarget

Summary: We were supposed to pass in proper eventEmitter, but passed in one with null eventTarget instead, causing assertion failures when dispatching event.

Reviewed By: sebmarkbage, shergin

Differential Revision: D8720793

fbshipit-source-id: 891f3b2a2c76a6dd3e40039623c6e86991aad50b
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 463c537bcdbf..23dd8f8c60bb 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -166,7 +166,7 @@ SharedShadowNode FabricUIManager::cloneNode(const SharedShadowNode &shadowNode)
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
-      componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
+      shadowNode->getEventEmitter(),
       nullptr
     );
 
@@ -183,7 +183,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildren(const SharedShadowNod
     componentDescriptor->cloneShadowNode(
       shadowNode,
       nullptr,
-      componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
+      shadowNode->getEventEmitter(),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 
@@ -201,7 +201,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewProps(const SharedShadowNode &
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
-      componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
+      shadowNode->getEventEmitter(),
       nullptr
     );
 
@@ -219,7 +219,7 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
     componentDescriptor->cloneShadowNode(
       shadowNode,
       componentDescriptor->cloneProps(shadowNode->getProps(), rawProps),
-      componentDescriptor->createEventEmitter(nullptr /*TODO(shergin)*/, shadowNode->getTag()),
+      shadowNode->getEventEmitter(),
       ShadowNode::emptySharedShadowNodeSharedList()
     );
 

From c1831d50cfd35b7a7393e50bc71d8389b36021ce Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Dar=C3=ADo=20Here=C3=B1=C3=BA?= <magallania@gmail.com>
Date: Mon, 2 Jul 2018 20:17:47 -0700
Subject: [PATCH 0977/1109] Typo in DockerTests.md (#20009)

Summary:
[DOCS] [BUGFIX] [DockerTests.md] - Typo on string #038
Closes https://github.com/facebook/react-native/pull/20009

Differential Revision: D8721811

Pulled By: TheSavior

fbshipit-source-id: e678c74fd89bc0c0e9db48590e1911d23bc4d339
---
 DockerTests.md | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/DockerTests.md b/DockerTests.md
index 790d19527869..f1714db87a0a 100644
--- a/DockerTests.md
+++ b/DockerTests.md
@@ -35,7 +35,7 @@ There are two Dockerfiles for use with the Android codebase.
 
 The `Dockerfile.android-base` contains all the necessary prerequisites required to run the React Android tests. It is
 separated out into a separate Dockerfile because these are dependencies that rarely change and also because it is quite
-a beastly image since it contains all the Android depedencies for running android and the emulators (~9GB).
+a beastly image since it contains all the Android dependencies for running android and the emulators (~9GB).
 
 The good news is you should rarely have to build or pull down the base image! All iterative code updates happen as
 part of the `Dockerfile.android` image build.

From bbdc12eda7dec135799b7f4c41fe678180970dd2 Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 3 Jul 2018 00:24:18 -0700
Subject: [PATCH 0978/1109] RN: Add Overflow Visible Kill Switch (Android)

Summary:
Adds a kill switch that reverts the default behavior of `overflow` to be hidden again. The intent of this kill switch is to give applications more time to migrate if necessary (e.g. if they are depending on third party packages with native components that are not compatible with `overflow` being visible by default).

To use the flag, simply set:

  import com.facebook.react.views.view.ReactViewGroup;

  // Somewhere in the initialization of your application.
  ReactViewGroup.sDefaultOverflowHidden = true;

Reviewed By: achen1

Differential Revision: D8718963

fbshipit-source-id: 0eb9aee45dfe04e9ae34d86e3bedcd30a185ef82
---
 .../com/facebook/react/views/view/ReactViewGroup.java  | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index bdd522bd2a60..e8afaa935745 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -49,6 +49,11 @@ public class ReactViewGroup extends ViewGroup implements
     ReactInterceptingViewGroup, ReactClippingViewGroup, ReactPointerEventsView, ReactHitSlopView,
     ReactZIndexedViewGroup {
 
+  /**
+   * Kill switch to make overflow hidden by default. This flag will eventually be removed.
+   */
+  public static boolean sDefaultOverflowHidden;
+
   private static final int ARRAY_CAPACITY_INCREMENT = 12;
   private static final int DEFAULT_BACKGROUND_COLOR = Color.TRANSPARENT;
   private static final LayoutParams sDefaultLayoutParam = new ViewGroup.LayoutParams(0, 0);
@@ -113,7 +118,10 @@ public void onLayoutChange(
 
   public ReactViewGroup(Context context) {
     super(context);
-    setClipChildren(false);
+    // TODO: Remove this check after a couple public releases.
+    if (!sDefaultOverflowHidden) {
+      setClipChildren(false);
+    }
     mDrawingOrderHelper = new ViewGroupDrawingOrderHelper(this);
   }
 

From ba56725eb8fa905986095fa828f2fcfcb1b61838 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Tue, 3 Jul 2018 08:42:49 -0700
Subject: [PATCH 0979/1109] Upgrade eslint to v5.0.1 on xplat

Summary:
@public

Upgrades eslint to v5.0.1

Updated `eslint-plugin-eslint-comments`, which was necessary for eslint 5

Disabled the `prefer-const` rule while we wait for https://github.com/eslint/eslint/issues/10520 to be fixed/published.

Reviewed By: zertosh

Differential Revision: D8692838

fbshipit-source-id: fa0cae3e299af2350c8c30ceb94d70740ee84eab
---
 package.json | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/package.json b/package.json
index d25b34bab2aa..ef7f978438e2 100644
--- a/package.json
+++ b/package.json
@@ -203,10 +203,10 @@
     "async": "^2.4.0",
     "babel-eslint": "8.2.1",
     "babel-generator": "^6.26.0",
-    "eslint": "4.17.0",
+    "eslint": "5.0.1",
     "eslint-config-fb-strict": "22.1.0",
     "eslint-config-fbjs": "2.0.1",
-    "eslint-plugin-eslint-comments": "2.0.2",
+    "eslint-plugin-eslint-comments": "^3.0.1",
     "eslint-plugin-flowtype": "2.43.0",
     "eslint-plugin-jest": "21.8.0",
     "eslint-plugin-prettier": "2.6.0",

From bbc8bb1f9d6b9f99d7bdca09f553c4015555bd51 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Tue, 3 Jul 2018 13:44:54 -0700
Subject: [PATCH 0980/1109] Do not use morgan internally

Summary: `morgan` produces non-json output, which affects `js1 run` when ran with the `--json` flag.

Reviewed By: Kureev

Differential Revision: D8724830

fbshipit-source-id: 11377f6ef39341c658a7f905383398423a721630
---
 local-cli/server/middleware/MiddlewareManager.js | 5 ++---
 local-cli/server/runServer.js                    | 3 +++
 2 files changed, 5 insertions(+), 3 deletions(-)

diff --git a/local-cli/server/middleware/MiddlewareManager.js b/local-cli/server/middleware/MiddlewareManager.js
index 78b69c777ab2..25fe213c287d 100644
--- a/local-cli/server/middleware/MiddlewareManager.js
+++ b/local-cli/server/middleware/MiddlewareManager.js
@@ -11,7 +11,6 @@
 const compression = require('compression');
 const connect = require('connect');
 const errorhandler = require('errorhandler');
-const morgan = require('morgan');
 const path = require('path');
 const serveStatic = require('serve-static');
 const WebSocketServer = require('ws').Server;
@@ -33,7 +32,8 @@ type WebSocketProxy = {
   server: WebSocketServer,
   isChromeConnected: () => boolean,
 };
-type Connect = any;
+
+type Connect = $Call<connect>;
 
 module.exports = class MiddlewareManager {
   app: Connect;
@@ -52,7 +52,6 @@ module.exports = class MiddlewareManager {
       .use(statusPageMiddleware)
       .use(systraceProfileMiddleware)
       .use(indexPageMiddleware)
-      .use(morgan('combined'))
       .use(errorhandler());
   }
 
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 59f822f44dad..f5a94b739588 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -16,6 +16,7 @@ const Metro = require('metro');
 
 const {Terminal} = require('metro-core');
 
+const morgan = require('morgan');
 const path = require('path');
 const MiddlewareManager = require('./middleware/MiddlewareManager');
 
@@ -47,6 +48,8 @@ async function runServer(args: Args, config: ConfigT) {
   const reporter = new ReporterImpl(terminal);
   const middlewareManager = new MiddlewareManager(args);
 
+  middlewareManager.getConnectInstance().use(morgan('combined'));
+
   args.watchFolders.forEach(middlewareManager.serveStatic);
 
   const serverInstance = await Metro.runServer({

From 28c7ccf785132458fce32c234ce777a6fe475c93 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Tue, 3 Jul 2018 15:31:48 -0700
Subject: [PATCH 0981/1109] Image source without uri should return null.

Summary: When image source doesn't have uri and is neither an array, it should return null.

Reviewed By: yungsters

Differential Revision: D8728688

fbshipit-source-id: 915c4f3f450907ee3435ac99b1fe9849738766da
---
 Libraries/Image/Image.android.js | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index 6f0a312e97ef..ec25a4ee1eeb 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -212,6 +212,10 @@ let Image = (
     );
   }
 
+  if (!source.uri && !Array.isArray(source)) {
+    return null;
+  }
+
   let style;
   let sources;
   if (source?.uri != null) {

From 33d20da41b814a2fb9ba02cbab8b61a819cad95b Mon Sep 17 00:00:00 2001
From: Dulmandakh <dulmandakh@gmail.com>
Date: Tue, 3 Jul 2018 18:12:38 -0700
Subject: [PATCH 0982/1109] @allow-large-files [react-native][PR] Upgrade
 Gradle to 4.4 (#19899)

Summary:
Bump gradle to 4.4, version used by android studio 3.x and gradle plugin 3.x. This will help make migration easier and smoother.

CI: https://circleci.com/gh/dulmandakh/react-native/591

FYI: I found that gradle 4.8 works fine with gradle plugin 2.3, but gradle plugin 3.x displays warnings and asks to disable on demand configuration.
Closes https://github.com/facebook/react-native/pull/19899

Reviewed By: fkgozali

Differential Revision: D8697929

Pulled By: hramos

fbshipit-source-id: 21eb625ee1e4a1fa02aa22de4c36a07269ca467b
---
 gradle/wrapper/gradle-wrapper.properties                        | 2 +-
 .../HelloWorld/android/gradle/wrapper/gradle-wrapper.properties | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
index ec9c72459fa2..e318290e619b 100644
--- a/gradle/wrapper/gradle-wrapper.properties
+++ b/gradle/wrapper/gradle-wrapper.properties
@@ -3,4 +3,4 @@ distributionBase=GRADLE_USER_HOME
 distributionPath=wrapper/dists
 zipStoreBase=GRADLE_USER_HOME
 zipStorePath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-3.5.1-all.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-4.4-all.zip
diff --git a/local-cli/templates/HelloWorld/android/gradle/wrapper/gradle-wrapper.properties b/local-cli/templates/HelloWorld/android/gradle/wrapper/gradle-wrapper.properties
index 81a86e213401..b6517bb1d165 100644
--- a/local-cli/templates/HelloWorld/android/gradle/wrapper/gradle-wrapper.properties
+++ b/local-cli/templates/HelloWorld/android/gradle/wrapper/gradle-wrapper.properties
@@ -2,4 +2,4 @@ distributionBase=GRADLE_USER_HOME
 distributionPath=wrapper/dists
 zipStoreBase=GRADLE_USER_HOME
 zipStorePath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-3.5.1-all.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-4.4-all.zip

From 079bf3f2067cb268b60e75cd9e1bc51a9c85359c Mon Sep 17 00:00:00 2001
From: Zdravko Nikolovski <zdravko.nikolovski@netcetera.com>
Date: Tue, 3 Jul 2018 18:13:06 -0700
Subject: [PATCH 0983/1109] Packager linking when using custom debug
 configuration on iOS device (#16451)

Summary:
In many projects we have different environments that we connect to. For these environments (for example: Test, Staging, Production) we have custom configurations (Debug and Release). While this is not a problem on Android, it is a problem on iOS. With the current implementation of the react-native-xcode.sh script, when using a custom Debug configuration, the app started on iOS device, can't contact the Packager. This pull request solves this issue.

Connect a real device, start the app with a custom debug configuration in Xcode. Shake and Reload.

[IOS][BUGFIX][./scripts/react-native-xcode.sh] Add support for connecting to the Packager when running the iOS app on device when using custom Debug configuration.
Closes https://github.com/facebook/react-native/pull/16451

Differential Revision: D8730537

Pulled By: hramos

fbshipit-source-id: a36007776e8fe9e401c38015040abd2c2bbd7c58
---
 scripts/react-native-xcode.sh | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/scripts/react-native-xcode.sh b/scripts/react-native-xcode.sh
index 7194c2a1856c..88ea804a8063 100755
--- a/scripts/react-native-xcode.sh
+++ b/scripts/react-native-xcode.sh
@@ -94,7 +94,7 @@ type $NODE_BINARY >/dev/null 2>&1 || nodejs_not_found
 set -x
 DEST=$CONFIGURATION_BUILD_DIR/$UNLOCALIZED_RESOURCES_FOLDER_PATH
 
-if [[ "$CONFIGURATION" = "Debug" && ! "$PLATFORM_NAME" == *simulator ]]; then
+if [[ "$CONFIGURATION" = *Debug* && ! "$PLATFORM_NAME" == *simulator ]]; then
   IP=$(ipconfig getifaddr en0)
   if [ -z "$IP" ]; then
     IP=$(ifconfig | grep 'inet ' | grep -v ' 127.' | cut -d\   -f2  | awk 'NR==1{print $1}')

From 50675404873c1ffac0deedc51fe745168051148b Mon Sep 17 00:00:00 2001
From: Alexey Kureev <kureev@fb.com>
Date: Tue, 3 Jul 2018 23:45:28 -0700
Subject: [PATCH 0984/1109] Fix react-native CLI (internal and external one)

Summary:
- Fix wrong debugger-ui path
- Override host and port using args

Reviewed By: yungsters

Differential Revision: D8731159

fbshipit-source-id: ca8ad76a02eda9e0b9cdb1a952aa5631d660868f
---
 local-cli/server/middleware/MiddlewareManager.js | 2 +-
 local-cli/server/runServer.js                    | 2 ++
 2 files changed, 3 insertions(+), 1 deletion(-)

diff --git a/local-cli/server/middleware/MiddlewareManager.js b/local-cli/server/middleware/MiddlewareManager.js
index 25fe213c287d..5402caf6f8ed 100644
--- a/local-cli/server/middleware/MiddlewareManager.js
+++ b/local-cli/server/middleware/MiddlewareManager.js
@@ -40,7 +40,7 @@ module.exports = class MiddlewareManager {
   options: Options;
 
   constructor(options: Options) {
-    const debuggerUIFolder = path.join(__dirname, 'util', 'debugger-ui');
+    const debuggerUIFolder = path.join(__dirname, '..', 'util', 'debugger-ui');
 
     this.options = options;
     this.app = connect()
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index f5a94b739588..7dfaaed72a18 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -66,6 +66,8 @@ async function runServer(args: Args, config: ConfigT) {
         : config.getTransformModulePath(),
       watch: !args.nonPersistent,
     },
+    host: args.host,
+    port: args.port,
   });
 
   // In Node 8, the default keep-alive for an HTTP connection is 5 seconds. In

From fff43614aa5185e9815a0b42ab2c1d8299ce1fc7 Mon Sep 17 00:00:00 2001
From: Kevin Gozali <fkg@fb.com>
Date: Thu, 5 Jul 2018 13:59:44 -0700
Subject: [PATCH 0985/1109] android: disable `setClipChildren(false)` until RN
 ART issue is resolved

Summary:
It looks like for some reason when ReactViewGroup uses setClipChildren(false), the ReactNativeARTSurface no longer redraws when its width is expanded.

Disable this new overflow behavior until the underlying issue is fixed.

Reviewed By: achen1

Differential Revision: D8739003

fbshipit-source-id: ffae0e3eb0cd8ce385eae33a87b5ba0325cae3c4
---
 .../java/com/facebook/react/views/view/ReactViewGroup.java     | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index e8afaa935745..f3942754ec98 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -51,8 +51,9 @@ public class ReactViewGroup extends ViewGroup implements
 
   /**
    * Kill switch to make overflow hidden by default. This flag will eventually be removed.
+   * TODO (T31096050): Sets this back to `false` until ReactNativeARTSurface issue is resolved.
    */
-  public static boolean sDefaultOverflowHidden;
+  public static boolean sDefaultOverflowHidden = true;
 
   private static final int ARRAY_CAPACITY_INCREMENT = 12;
   private static final int DEFAULT_BACKGROUND_COLOR = Color.TRANSPARENT;

From 2424ef5654cffbe8c62465325c4c04eb00b40c01 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Thu, 5 Jul 2018 15:08:10 -0700
Subject: [PATCH 0986/1109] Move ScrollView prop comments from propTypes to
 flow types

Summary: Next step: make propTypes `__DEV__` only.

Reviewed By: TheSavior

Differential Revision: D8721300

fbshipit-source-id: 066b495836a87ea92d370728911e7b7ba6566c53
---
 Libraries/Components/ScrollView/ScrollView.js | 676 +++++++++---------
 1 file changed, 338 insertions(+), 338 deletions(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index a2be38422765..cec27cc67fff 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -76,49 +76,263 @@ type TouchableProps = $ReadOnly<{|
 |}>;
 
 type IOSProps = $ReadOnly<{|
+  /**
+   * Controls whether iOS should automatically adjust the content inset
+   * for scroll views that are placed behind a navigation bar or
+   * tab bar/ toolbar. The default value is true.
+   * @platform ios
+   */
   automaticallyAdjustContentInsets?: ?boolean,
+  /**
+   * The amount by which the scroll view content is inset from the edges
+   * of the scroll view. Defaults to `{top: 0, left: 0, bottom: 0, right: 0}`.
+   * @platform ios
+   */
   contentInset?: ?EdgeInsetsProp,
+  /**
+   * Used to manually set the starting scroll offset.
+   * The default value is `{x: 0, y: 0}`.
+   * @platform ios
+   */
   contentOffset?: ?PointProp,
+  /**
+   * When true, the scroll view bounces when it reaches the end of the
+   * content if the content is larger then the scroll view along the axis of
+   * the scroll direction. When false, it disables all bouncing even if
+   * the `alwaysBounce*` props are true. The default value is true.
+   * @platform ios
+   */
   bounces?: ?boolean,
+  /**
+   * When true, gestures can drive zoom past min/max and the zoom will animate
+   * to the min/max value at gesture end, otherwise the zoom will not exceed
+   * the limits.
+   * @platform ios
+   */
   bouncesZoom?: ?boolean,
+  /**
+   * When true, the scroll view bounces horizontally when it reaches the end
+   * even if the content is smaller than the scroll view itself. The default
+   * value is true when `horizontal={true}` and false otherwise.
+   * @platform ios
+   */
   alwaysBounceHorizontal?: ?boolean,
+  /**
+   * When true, the scroll view bounces vertically when it reaches the end
+   * even if the content is smaller than the scroll view itself. The default
+   * value is false when `horizontal={true}` and true otherwise.
+   * @platform ios
+   */
   alwaysBounceVertical?: ?boolean,
+  /**
+   * When true, the scroll view automatically centers the content when the
+   * content is smaller than the scroll view bounds; when the content is
+   * larger than the scroll view, this property has no effect. The default
+   * value is false.
+   * @platform ios
+   */
   centerContent?: ?boolean,
+  /**
+   * A floating-point number that determines how quickly the scroll view
+   * decelerates after the user lifts their finger. You may also use string
+   * shortcuts `"normal"` and `"fast"` which match the underlying iOS settings
+   * for `UIScrollViewDecelerationRateNormal` and
+   * `UIScrollViewDecelerationRateFast` respectively.
+   *
+   *   - `'normal'`: 0.998 (the default)
+   *   - `'fast'`: 0.99
+   *
+   * @platform ios
+   */
   decelerationRate?: ?('fast' | 'normal' | number),
+  /**
+   * The style of the scroll indicators.
+   *
+   *   - `'default'` (the default), same as `black`.
+   *   - `'black'`, scroll indicator is black. This style is good against a light background.
+   *   - `'white'`, scroll indicator is white. This style is good against a dark background.
+   *
+   * @platform ios
+   */
   indicatorStyle?: ?('default' | 'black' | 'white'),
+  /**
+   * When true, the ScrollView will try to lock to only vertical or horizontal
+   * scrolling while dragging.  The default value is false.
+   * @platform ios
+   */
   directionalLockEnabled?: ?boolean,
+  /**
+   * When false, once tracking starts, won't try to drag if the touch moves.
+   * The default value is true.
+   * @platform ios
+   */
   canCancelContentTouches?: ?boolean,
+  /**
+   * When set, the scroll view will adjust the scroll position so that the first child that is
+   * currently visible and at or beyond `minIndexForVisible` will not change position. This is
+   * useful for lists that are loading content in both directions, e.g. a chat thread, where new
+   * messages coming in might otherwise cause the scroll position to jump. A value of 0 is common,
+   * but other values such as 1 can be used to skip loading spinners or other content that should
+   * not maintain position.
+   *
+   * The optional `autoscrollToTopThreshold` can be used to make the content automatically scroll
+   * to the top after making the adjustment if the user was within the threshold of the top before
+   * the adjustment was made. This is also useful for chat-like applications where you want to see
+   * new messages scroll into place, but not if the user has scrolled up a ways and it would be
+   * disruptive to scroll a bunch.
+   *
+   * Caveat 1: Reordering elements in the scrollview with this enabled will probably cause
+   * jumpiness and jank. It can be fixed, but there are currently no plans to do so. For now,
+   * don't re-order the content of any ScrollViews or Lists that use this feature.
+   *
+   * Caveat 2: This simply uses `contentOffset` and `frame.origin` in native code to compute
+   * visibility. Occlusion, transforms, and other complexity won't be taken into account as to
+   * whether content is "visible" or not.
+   *
+   * @platform ios
+   */
   maintainVisibleContentPosition?: ?$ReadOnly<{|
     minIndexForVisible: number,
     autoscrollToTopThreshold?: ?number,
   |}>,
+  /**
+   * The maximum allowed zoom scale. The default value is 1.0.
+   * @platform ios
+   */
   maximumZoomScale?: ?number,
+  /**
+   * The minimum allowed zoom scale. The default value is 1.0.
+   * @platform ios
+   */
   minimumZoomScale?: ?number,
+  /**
+   * When true, ScrollView allows use of pinch gestures to zoom in and out.
+   * The default value is true.
+   * @platform ios
+   */
   pinchGestureEnabled?: ?boolean,
+  /**
+   * This controls how often the scroll event will be fired while scrolling
+   * (as a time interval in ms). A lower number yields better accuracy for code
+   * that is tracking the scroll position, but can lead to scroll performance
+   * problems due to the volume of information being send over the bridge.
+   * You will not notice a difference between values set between 1-16 as the
+   * JS run loop is synced to the screen refresh rate. If you do not need precise
+   * scroll position tracking, set this value higher to limit the information
+   * being sent across the bridge. The default value is zero, which results in
+   * the scroll event being sent only once each time the view is scrolled.
+   * @platform ios
+   */
   scrollEventThrottle?: ?number,
+  /**
+   * The amount by which the scroll view indicators are inset from the edges
+   * of the scroll view. This should normally be set to the same value as
+   * the `contentInset`. Defaults to `{0, 0, 0, 0}`.
+   * @platform ios
+   */
   scrollIndicatorInsets?: ?EdgeInsetsProp,
+  /**
+   * When true, the scroll view scrolls to top when the status bar is tapped.
+   * The default value is true.
+   * @platform ios
+   */
   scrollsToTop?: ?boolean,
+  /**
+   * When true, shows a horizontal scroll indicator.
+   * The default value is true.
+   */
   showsHorizontalScrollIndicator?: ?boolean,
+  /**
+   * When `snapToInterval` is set, `snapToAlignment` will define the relationship
+   * of the snapping to the scroll view.
+   *
+   *   - `'start'` (the default) will align the snap at the left (horizontal) or top (vertical)
+   *   - `'center'` will align the snap in the center
+   *   - `'end'` will align the snap at the right (horizontal) or bottom (vertical)
+   *
+   * @platform ios
+   */
   snapToAlignment?: ?('start' | 'center' | 'end'),
+  /**
+   * The current scale of the scroll view content. The default value is 1.0.
+   * @platform ios
+   */
   zoomScale?: ?number,
+  /**
+   * This property specifies how the safe area insets are used to modify the
+   * content area of the scroll view. The default value of this property is
+   * "never". Available on iOS 11 and later.
+   * @platform ios
+   */
   contentInsetAdjustmentBehavior?: ?(
     | 'automatic'
     | 'scrollableAxes'
     | 'never'
     | 'always'
   ),
+  /**
+   * When true, ScrollView will emit updateChildFrames data in scroll events,
+   * otherwise will not compute or emit child frame data.  This only exists
+   * to support legacy issues, `onLayout` should be used instead to retrieve
+   * frame data.
+   * The default value is false.
+   * @platform ios
+   */
   DEPRECATED_sendUpdatedChildFrames?: ?boolean,
 |}>;
 
 type AndroidProps = $ReadOnly<{|
+  /**
+   * Enables nested scrolling for Android API level 21+.
+   * Nested scrolling is supported by default on iOS
+   * @platform android
+   */
   nestedScrollEnabled?: ?boolean,
+  /**
+   * Sometimes a scrollview takes up more space than its content fills. When this is
+   * the case, this prop will fill the rest of the scrollview with a color to avoid setting
+   * a background and creating unnecessary overdraw. This is an advanced optimization
+   * that is not needed in the general case.
+   * @platform android
+   */
   endFillColor?: ?ColorValue,
+  /**
+   * Tag used to log scroll performance on this scroll view. Will force
+   * momentum events to be turned on (see sendMomentumEvents). This doesn't do
+   * anything out of the box and you need to implement a custom native
+   * FpsListener for it to be useful.
+   * @platform android
+   */
   scrollPerfTag?: ?string,
+  /**
+   * Used to override default value of overScroll mode.
+   *
+   * Possible values:
+   *
+   *  - `'auto'` - Default value, allow a user to over-scroll
+   *    this view only if the content is large enough to meaningfully scroll.
+   *  - `'always'` - Always allow a user to over-scroll this view.
+   *  - `'never'` - Never allow a user to over-scroll this view.
+   *
+   * @platform android
+   */
   overScrollMode?: ?('auto' | 'always' | 'never'),
 |}>;
 
 type VRProps = $ReadOnly<{|
-  scrollBarThumbImage?: ?($ReadOnly<{||}> | number),
+  /**
+   * Optionally an image can be used for the scroll bar thumb. This will
+   * override the color. While the image is loading or the image fails to
+   * load the color will be used instead. Use an alpha of 0 in the color
+   * to avoid seeing it while the image is loading.
+   *
+   * - `uri` - a string representing the resource identifier for the image, which
+   * should be either a local file path or the name of a static image resource
+   * - `number` - Opaque type returned by something like
+   * `import IMAGE from './image.jpg'`.
+   * @platform vr
+   */
+  scrollBarThumbImage?: ?($ReadOnly<{||}> | number), // Opaque type returned by import IMAGE from './image.jpg'
 |}>;
 
 export type Props = $ReadOnly<{|
@@ -128,30 +342,153 @@ export type Props = $ReadOnly<{|
   ...AndroidProps,
   ...VRProps,
 
+  /**
+   * These styles will be applied to the scroll view content container which
+   * wraps all of the child views. Example:
+   *
+   * ```
+   * return (
+   *   <ScrollView contentContainerStyle={styles.contentContainer}>
+   *   </ScrollView>
+   * );
+   * ...
+   * const styles = StyleSheet.create({
+   *   contentContainer: {
+   *     paddingVertical: 20
+   *   }
+   * });
+   * ```
+   */
   contentContainerStyle?: ?ViewStyleProp,
+  /**
+   * When true, the scroll view's children are arranged horizontally in a row
+   * instead of vertically in a column. The default value is false.
+   */
   horizontal?: ?boolean,
+  /**
+   * If sticky headers should stick at the bottom instead of the top of the
+   * ScrollView. This is usually used with inverted ScrollViews.
+   */
   invertStickyHeaders?: ?boolean,
+  /**
+   * Determines whether the keyboard gets dismissed in response to a drag.
+   *
+   * *Cross platform*
+   *
+   *   - `'none'` (the default), drags do not dismiss the keyboard.
+   *   - `'on-drag'`, the keyboard is dismissed when a drag begins.
+   *
+   * *iOS Only*
+   *
+   *   - `'interactive'`, the keyboard is dismissed interactively with the drag and moves in
+   *     synchrony with the touch; dragging upwards cancels the dismissal.
+   *     On android this is not supported and it will have the same behavior as 'none'.
+   */
   keyboardDismissMode?: ?(
     | 'none' // default
     | 'on-drag' // cross-platform
     | 'interactive'
   ), // ios only
+  /**
+   * Determines when the keyboard should stay visible after a tap.
+   *
+   *   - `'never'` (the default), tapping outside of the focused text input when the keyboard
+   *     is up dismisses the keyboard. When this happens, children won't receive the tap.
+   *   - `'always'`, the keyboard will not dismiss automatically, and the scroll view will not
+   *     catch taps, but children of the scroll view can catch taps.
+   *   - `'handled'`, the keyboard will not dismiss automatically when the tap was handled by
+   *     a children, (or captured by an ancestor).
+   *   - `false`, deprecated, use 'never' instead
+   *   - `true`, deprecated, use 'always' instead
+   */
   // $FlowFixMe Issues found when typing ScrollView
   keyboardShouldPersistTaps?: ?('always' | 'never' | 'handled' | false | true),
+  /**
+   * Called when the momentum scroll starts (scroll which occurs as the ScrollView glides to a stop).
+   */
   onMomentumScrollBegin?: ?Function,
+  /**
+   * Called when the momentum scroll ends (scroll which occurs as the ScrollView glides to a stop).
+   */
   onMomentumScrollEnd?: ?Function,
 
+  /**
+   * Fires at most once per frame during scrolling. The frequency of the
+   * events can be controlled using the `scrollEventThrottle` prop.
+   */
   onScroll?: ?Function,
+  /**
+   * Called when the user begins to drag the scroll view.
+   */
   onScrollBeginDrag?: ?Function,
+  /**
+   * Called when the user stops dragging the scroll view and it either stops
+   * or begins to glide.
+   */
   onScrollEndDrag?: ?Function,
+  /**
+   * Called when scrollable content view of the ScrollView changes.
+   *
+   * Handler function is passed the content width and content height as parameters:
+   * `(contentWidth, contentHeight)`
+   *
+   * It's implemented using onLayout handler attached to the content container
+   * which this ScrollView renders.
+   */
   onContentSizeChange?: ?Function,
   onKeyboardDidShow?: (event: PressEvent) => void,
+  /**
+   * When true, the scroll view stops on multiples of the scroll view's size
+   * when scrolling. This can be used for horizontal pagination. The default
+   * value is false.
+   *
+   * Note: Vertical pagination is not supported on Android.
+   */
   pagingEnabled?: ?boolean,
+  /**
+   * When false, the view cannot be scrolled via touch interaction.
+   * The default value is true.
+   *
+   * Note that the view can always be scrolled by calling `scrollTo`.
+   */
   scrollEnabled?: ?boolean,
+  /**
+   * When true, shows a vertical scroll indicator.
+   * The default value is true.
+   */
   showsVerticalScrollIndicator?: ?boolean,
+  /**
+   * An array of child indices determining which children get docked to the
+   * top of the screen when scrolling. For example, passing
+   * `stickyHeaderIndices={[0]}` will cause the first child to be fixed to the
+   * top of the scroll view. This property is not supported in conjunction
+   * with `horizontal={true}`.
+   */
   stickyHeaderIndices?: ?$ReadOnlyArray<number>,
+  /**
+   * When set, causes the scroll view to stop at multiples of the value of
+   * `snapToInterval`. This can be used for paginating through children
+   * that have lengths smaller than the scroll view. Typically used in
+   * combination with `snapToAlignment` and `decelerationRate="fast"` on ios.
+   * Overrides less configurable `pagingEnabled` prop.
+   *
+   * Supported for horizontal scrollview on android.
+   */
   snapToInterval?: ?number,
+  /**
+   * Experimental: When true, offscreen child views (whose `overflow` value is
+   * `hidden`) are removed from their native backing superview when offscreen.
+   * This can improve scrolling performance on long lists. The default value is
+   * true.
+   */
   removeClippedSubviews?: ?boolean,
+  /**
+   * A RefreshControl component, used to provide pull-to-refresh
+   * functionality for the ScrollView. Only works for vertical ScrollViews
+   * (`horizontal` prop must be `false`).
+   *
+   * See [RefreshControl](docs/refreshcontrol.html).
+   */
   refreshControl?: ?React.Element<any>,
   style?: ?ViewStyleProp,
   children?: React.Node,
@@ -196,163 +533,33 @@ const ScrollView = createReactClass({
   displayName: 'ScrollView',
   propTypes: {
     ...ViewPropTypes,
-    /**
-     * Controls whether iOS should automatically adjust the content inset
-     * for scroll views that are placed behind a navigation bar or
-     * tab bar/ toolbar. The default value is true.
-     * @platform ios
-     */
     automaticallyAdjustContentInsets: PropTypes.bool,
-    /**
-     * The amount by which the scroll view content is inset from the edges
-     * of the scroll view. Defaults to `{top: 0, left: 0, bottom: 0, right: 0}`.
-     * @platform ios
-     */
     contentInset: EdgeInsetsPropType,
-    /**
-     * Used to manually set the starting scroll offset.
-     * The default value is `{x: 0, y: 0}`.
-     * @platform ios
-     */
     contentOffset: PointPropType,
-    /**
-     * When true, the scroll view bounces when it reaches the end of the
-     * content if the content is larger then the scroll view along the axis of
-     * the scroll direction. When false, it disables all bouncing even if
-     * the `alwaysBounce*` props are true. The default value is true.
-     * @platform ios
-     */
     bounces: PropTypes.bool,
-    /**
-     * When true, gestures can drive zoom past min/max and the zoom will animate
-     * to the min/max value at gesture end, otherwise the zoom will not exceed
-     * the limits.
-     * @platform ios
-     */
     bouncesZoom: PropTypes.bool,
-    /**
-     * When true, the scroll view bounces horizontally when it reaches the end
-     * even if the content is smaller than the scroll view itself. The default
-     * value is true when `horizontal={true}` and false otherwise.
-     * @platform ios
-     */
     alwaysBounceHorizontal: PropTypes.bool,
-    /**
-     * When true, the scroll view bounces vertically when it reaches the end
-     * even if the content is smaller than the scroll view itself. The default
-     * value is false when `horizontal={true}` and true otherwise.
-     * @platform ios
-     */
     alwaysBounceVertical: PropTypes.bool,
-    /**
-     * When true, the scroll view automatically centers the content when the
-     * content is smaller than the scroll view bounds; when the content is
-     * larger than the scroll view, this property has no effect. The default
-     * value is false.
-     * @platform ios
-     */
     centerContent: PropTypes.bool,
-    /**
-     * These styles will be applied to the scroll view content container which
-     * wraps all of the child views. Example:
-     *
-     * ```
-     * return (
-     *   <ScrollView contentContainerStyle={styles.contentContainer}>
-     *   </ScrollView>
-     * );
-     * ...
-     * const styles = StyleSheet.create({
-     *   contentContainer: {
-     *     paddingVertical: 20
-     *   }
-     * });
-     * ```
-     */
     contentContainerStyle: StyleSheetPropType(ViewStylePropTypes),
-    /**
-     * A floating-point number that determines how quickly the scroll view
-     * decelerates after the user lifts their finger. You may also use string
-     * shortcuts `"normal"` and `"fast"` which match the underlying iOS settings
-     * for `UIScrollViewDecelerationRateNormal` and
-     * `UIScrollViewDecelerationRateFast` respectively.
-     *
-     *   - `'normal'`: 0.998 (the default)
-     *   - `'fast'`: 0.99
-     *
-     * @platform ios
-     */
     decelerationRate: PropTypes.oneOfType([
       PropTypes.oneOf(['fast', 'normal']),
       PropTypes.number,
     ]),
-    /**
-     * When true, the scroll view's children are arranged horizontally in a row
-     * instead of vertically in a column. The default value is false.
-     */
     horizontal: PropTypes.bool,
-    /**
-     * The style of the scroll indicators.
-     *
-     *   - `'default'` (the default), same as `black`.
-     *   - `'black'`, scroll indicator is black. This style is good against a light background.
-     *   - `'white'`, scroll indicator is white. This style is good against a dark background.
-     *
-     * @platform ios
-     */
     indicatorStyle: PropTypes.oneOf([
       'default', // default
       'black',
       'white',
     ]),
-    /**
-     * If sticky headers should stick at the bottom instead of the top of the
-     * ScrollView. This is usually used with inverted ScrollViews.
-     */
     invertStickyHeaders: PropTypes.bool,
-    /**
-     * When true, the ScrollView will try to lock to only vertical or horizontal
-     * scrolling while dragging.  The default value is false.
-     * @platform ios
-     */
     directionalLockEnabled: PropTypes.bool,
-    /**
-     * When false, once tracking starts, won't try to drag if the touch moves.
-     * The default value is true.
-     * @platform ios
-     */
     canCancelContentTouches: PropTypes.bool,
-    /**
-     * Determines whether the keyboard gets dismissed in response to a drag.
-     *
-     * *Cross platform*
-     *
-     *   - `'none'` (the default), drags do not dismiss the keyboard.
-     *   - `'on-drag'`, the keyboard is dismissed when a drag begins.
-     *
-     * *iOS Only*
-     *
-     *   - `'interactive'`, the keyboard is dismissed interactively with the drag and moves in
-     *     synchrony with the touch; dragging upwards cancels the dismissal.
-     *     On android this is not supported and it will have the same behavior as 'none'.
-     */
     keyboardDismissMode: PropTypes.oneOf([
       'none', // default
       'on-drag', // Cross-platform
       'interactive', // iOS-only
     ]),
-    /**
-     * Determines when the keyboard should stay visible after a tap.
-     *
-     *   - `'never'` (the default), tapping outside of the focused text input when the keyboard
-     *     is up dismisses the keyboard. When this happens, children won't receive the tap.
-     *   - `'always'`, the keyboard will not dismiss automatically, and the scroll view will not
-     *     catch taps, but children of the scroll view can catch taps.
-     *   - `'handled'`, the keyboard will not dismiss automatically when the tap was handled by
-     *     a children, (or captured by an ancestor).
-     *   - `false`, deprecated, use 'never' instead
-     *   - `true`, deprecated, use 'always' instead
-     */
     keyboardShouldPersistTaps: PropTypes.oneOf([
       'always',
       'never',
@@ -360,257 +567,50 @@ const ScrollView = createReactClass({
       false,
       true,
     ]),
-    /**
-     * When set, the scroll view will adjust the scroll position so that the first child that is
-     * currently visible and at or beyond `minIndexForVisible` will not change position. This is
-     * useful for lists that are loading content in both directions, e.g. a chat thread, where new
-     * messages coming in might otherwise cause the scroll position to jump. A value of 0 is common,
-     * but other values such as 1 can be used to skip loading spinners or other content that should
-     * not maintain position.
-     *
-     * The optional `autoscrollToTopThreshold` can be used to make the content automatically scroll
-     * to the top after making the adjustment if the user was within the threshold of the top before
-     * the adjustment was made. This is also useful for chat-like applications where you want to see
-     * new messages scroll into place, but not if the user has scrolled up a ways and it would be
-     * disruptive to scroll a bunch.
-     *
-     * Caveat 1: Reordering elements in the scrollview with this enabled will probably cause
-     * jumpiness and jank. It can be fixed, but there are currently no plans to do so. For now,
-     * don't re-order the content of any ScrollViews or Lists that use this feature.
-     *
-     * Caveat 2: This simply uses `contentOffset` and `frame.origin` in native code to compute
-     * visibility. Occlusion, transforms, and other complexity won't be taken into account as to
-     * whether content is "visible" or not.
-     *
-     * @platform ios
-     */
     maintainVisibleContentPosition: PropTypes.shape({
       minIndexForVisible: PropTypes.number.isRequired,
       autoscrollToTopThreshold: PropTypes.number,
     }),
-    /**
-     * The maximum allowed zoom scale. The default value is 1.0.
-     * @platform ios
-     */
     maximumZoomScale: PropTypes.number,
-    /**
-     * The minimum allowed zoom scale. The default value is 1.0.
-     * @platform ios
-     */
     minimumZoomScale: PropTypes.number,
-    /**
-     * Enables nested scrolling for Android API level 21+.
-     * Nested scrolling is supported by default on iOS
-     * @platform android
-     */
     nestedScrollEnabled: PropTypes.bool,
-    /**
-     * Called when the momentum scroll starts (scroll which occurs as the ScrollView glides to a stop).
-     */
     onMomentumScrollBegin: PropTypes.func,
-    /**
-     * Called when the momentum scroll ends (scroll which occurs as the ScrollView glides to a stop).
-     */
     onMomentumScrollEnd: PropTypes.func,
-    /**
-     * Fires at most once per frame during scrolling. The frequency of the
-     * events can be controlled using the `scrollEventThrottle` prop.
-     */
     onScroll: PropTypes.func,
-    /**
-     * Called when the user begins to drag the scroll view.
-     */
     onScrollBeginDrag: PropTypes.func,
-    /**
-     * Called when the user stops dragging the scroll view and it either stops
-     * or begins to glide.
-     */
     onScrollEndDrag: PropTypes.func,
-    /**
-     * Called when scrollable content view of the ScrollView changes.
-     *
-     * Handler function is passed the content width and content height as parameters:
-     * `(contentWidth, contentHeight)`
-     *
-     * It's implemented using onLayout handler attached to the content container
-     * which this ScrollView renders.
-     */
     onContentSizeChange: PropTypes.func,
-    /**
-     * When true, the scroll view stops on multiples of the scroll view's size
-     * when scrolling. This can be used for horizontal pagination. The default
-     * value is false.
-     *
-     * Note: Vertical pagination is not supported on Android.
-     */
     pagingEnabled: PropTypes.bool,
-    /**
-     * When true, ScrollView allows use of pinch gestures to zoom in and out.
-     * The default value is true.
-     * @platform ios
-     */
     pinchGestureEnabled: PropTypes.bool,
-    /**
-     * When false, the view cannot be scrolled via touch interaction.
-     * The default value is true.
-     *
-     * Note that the view can always be scrolled by calling `scrollTo`.
-     */
     scrollEnabled: PropTypes.bool,
-    /**
-     * This controls how often the scroll event will be fired while scrolling
-     * (as a time interval in ms). A lower number yields better accuracy for code
-     * that is tracking the scroll position, but can lead to scroll performance
-     * problems due to the volume of information being send over the bridge.
-     * You will not notice a difference between values set between 1-16 as the
-     * JS run loop is synced to the screen refresh rate. If you do not need precise
-     * scroll position tracking, set this value higher to limit the information
-     * being sent across the bridge. The default value is zero, which results in
-     * the scroll event being sent only once each time the view is scrolled.
-     * @platform ios
-     */
     scrollEventThrottle: PropTypes.number,
-    /**
-     * The amount by which the scroll view indicators are inset from the edges
-     * of the scroll view. This should normally be set to the same value as
-     * the `contentInset`. Defaults to `{0, 0, 0, 0}`.
-     * @platform ios
-     */
     scrollIndicatorInsets: EdgeInsetsPropType,
-    /**
-     * When true, the scroll view scrolls to top when the status bar is tapped.
-     * The default value is true.
-     * @platform ios
-     */
     scrollsToTop: PropTypes.bool,
-    /**
-     * When true, shows a horizontal scroll indicator.
-     * The default value is true.
-     */
     showsHorizontalScrollIndicator: PropTypes.bool,
-    /**
-     * When true, shows a vertical scroll indicator.
-     * The default value is true.
-     */
     showsVerticalScrollIndicator: PropTypes.bool,
-    /**
-     * An array of child indices determining which children get docked to the
-     * top of the screen when scrolling. For example, passing
-     * `stickyHeaderIndices={[0]}` will cause the first child to be fixed to the
-     * top of the scroll view. This property is not supported in conjunction
-     * with `horizontal={true}`.
-     */
     stickyHeaderIndices: PropTypes.arrayOf(PropTypes.number),
-    /**
-     * When set, causes the scroll view to stop at multiples of the value of
-     * `snapToInterval`. This can be used for paginating through children
-     * that have lengths smaller than the scroll view. Typically used in
-     * combination with `snapToAlignment` and `decelerationRate="fast"` on ios.
-     * Overrides less configurable `pagingEnabled` prop.
-     *
-     * Supported for horizontal scrollview on android.
-     */
     snapToInterval: PropTypes.number,
-    /**
-     * When `snapToInterval` is set, `snapToAlignment` will define the relationship
-     * of the snapping to the scroll view.
-     *
-     *   - `'start'` (the default) will align the snap at the left (horizontal) or top (vertical)
-     *   - `'center'` will align the snap in the center
-     *   - `'end'` will align the snap at the right (horizontal) or bottom (vertical)
-     *
-     * @platform ios
-     */
     snapToAlignment: PropTypes.oneOf([
       'start', // default
       'center',
       'end',
     ]),
-    /**
-     * Experimental: When true, offscreen child views (whose `overflow` value is
-     * `hidden`) are removed from their native backing superview when offscreen.
-     * This can improve scrolling performance on long lists. The default value is
-     * true.
-     */
     removeClippedSubviews: PropTypes.bool,
-    /**
-     * The current scale of the scroll view content. The default value is 1.0.
-     * @platform ios
-     */
     zoomScale: PropTypes.number,
-    /**
-     * This property specifies how the safe area insets are used to modify the
-     * content area of the scroll view. The default value of this property is
-     * "never". Available on iOS 11 and later.
-     * @platform ios
-     */
     contentInsetAdjustmentBehavior: PropTypes.oneOf([
       'automatic',
       'scrollableAxes',
       'never', // default
       'always',
     ]),
-    /**
-     * A RefreshControl component, used to provide pull-to-refresh
-     * functionality for the ScrollView. Only works for vertical ScrollViews
-     * (`horizontal` prop must be `false`).
-     *
-     * See [RefreshControl](docs/refreshcontrol.html).
-     */
     refreshControl: PropTypes.element,
 
-    /**
-     * Sometimes a scrollview takes up more space than its content fills. When this is
-     * the case, this prop will fill the rest of the scrollview with a color to avoid setting
-     * a background and creating unnecessary overdraw. This is an advanced optimization
-     * that is not needed in the general case.
-     * @platform android
-     */
     endFillColor: ColorPropType,
 
-    /**
-     * Tag used to log scroll performance on this scroll view. Will force
-     * momentum events to be turned on (see sendMomentumEvents). This doesn't do
-     * anything out of the box and you need to implement a custom native
-     * FpsListener for it to be useful.
-     * @platform android
-     */
     scrollPerfTag: PropTypes.string,
 
-    /**
-     * Used to override default value of overScroll mode.
-     *
-     * Possible values:
-     *
-     *  - `'auto'` - Default value, allow a user to over-scroll
-     *    this view only if the content is large enough to meaningfully scroll.
-     *  - `'always'` - Always allow a user to over-scroll this view.
-     *  - `'never'` - Never allow a user to over-scroll this view.
-     *
-     * @platform android
-     */
     overScrollMode: PropTypes.oneOf(['auto', 'always', 'never']),
-    /**
-     * When true, ScrollView will emit updateChildFrames data in scroll events,
-     * otherwise will not compute or emit child frame data.  This only exists
-     * to support legacy issues, `onLayout` should be used instead to retrieve
-     * frame data.
-     * The default value is false.
-     * @platform ios
-     */
     DEPRECATED_sendUpdatedChildFrames: PropTypes.bool,
-    /**
-     * Optionally an image can be used for the scroll bar thumb. This will
-     * override the color. While the image is loading or the image fails to
-     * load the color will be used instead. Use an alpha of 0 in the color
-     * to avoid seeing it while the image is loading.
-     *
-     * - `uri` - a string representing the resource identifier for the image, which
-     * should be either a local file path or the name of a static image resource
-     * - `number` - Opaque type returned by something like
-     * `import IMAGE from './image.jpg'`.
-     * @platform vr
-     */
     scrollBarThumbImage: PropTypes.oneOfType([
       PropTypes.shape({
         uri: PropTypes.string,

From f40de0e467815062c9bc61e645a835006b58c574 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Thu, 5 Jul 2018 15:08:11 -0700
Subject: [PATCH 0987/1109] Fix some ScrollView lint

Summary: $title

Reviewed By: TheSavior

Differential Revision: D8721334

fbshipit-source-id: 1aad238da9b8efdef6e2f3f1f2effd213fa9c3aa
---
 Libraries/Components/ScrollView/ScrollView.js | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index cec27cc67fff..6ad41c6b7cc3 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -875,7 +875,7 @@ const ScrollView = createReactClass({
       ScrollViewClass = RCTScrollView;
       ScrollContentContainerViewClass = RCTScrollContentView;
       warning(
-        !this.props.snapToInterval || !this.props.pagingEnabled,
+        this.props.snapToInterval != null || !this.props.pagingEnabled,
         'snapToInterval is currently ignored when pagingEnabled is true.',
       );
     }
@@ -1028,7 +1028,7 @@ const ScrollView = createReactClass({
     };
 
     const {decelerationRate} = this.props;
-    if (decelerationRate) {
+    if (decelerationRate != null) {
       props.decelerationRate = processDecelerationRate(decelerationRate);
     }
 

From 5b6ff01764502c88848867c7e04cab969da384a2 Mon Sep 17 00:00:00 2001
From: Spencer Ahrens <sahrens@fb.com>
Date: Thu, 5 Jul 2018 15:08:13 -0700
Subject: [PATCH 0988/1109] Remove ScrollView.propTypes

Summary:
We're unifying on flow types, and propTypes require non-trivial resources to initialize in aggregate.

Some open source code might depend on extracting ScrollView.propTypes which will now fail. To fix, simplly remove these dependencies and use flow or typescript for verifying correct prop usage instead.

Reviewed By: TheSavior

Differential Revision: D8726371

fbshipit-source-id: 19e9540794db97a9e356615b544759a0753fd68c
---
 .../ScrollView/InternalScrollViewType.js      |   3 +-
 Libraries/Components/ScrollView/ScrollView.js | 110 +-------
 Libraries/Components/WebView/WebView.ios.js   |   5 +-
 Libraries/Lists/ListView/ListView.js          | 239 ++++++++----------
 4 files changed, 112 insertions(+), 245 deletions(-)

diff --git a/Libraries/Components/ScrollView/InternalScrollViewType.js b/Libraries/Components/ScrollView/InternalScrollViewType.js
index a1d42bb46a6d..471e25d9a5da 100644
--- a/Libraries/Components/ScrollView/InternalScrollViewType.js
+++ b/Libraries/Components/ScrollView/InternalScrollViewType.js
@@ -22,7 +22,8 @@ class InternalScrollViewType<Props> extends ReactNative.NativeComponent<Props> {
   ) {}
 
   flashScrollIndicators() {}
-  scrollToEnd(options?: {animated?: boolean}) {}
+  propTypes: empty;
+  scrollToEnd(options?: ?{animated?: boolean}) {}
   scrollWithoutAnimationTo(y: number = 0, x: number = 0) {}
 
   getScrollResponder(): any {}
diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 6ad41c6b7cc3..7665527f5ad8 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -11,20 +11,13 @@
 'use strict';
 
 const AnimatedImplementation = require('AnimatedImplementation');
-const ColorPropType = require('ColorPropType');
-const EdgeInsetsPropType = require('EdgeInsetsPropType');
 const Platform = require('Platform');
-const PointPropType = require('PointPropType');
-const PropTypes = require('prop-types');
 const React = require('React');
 const ReactNative = require('ReactNative');
 const ScrollResponder = require('ScrollResponder');
 const ScrollViewStickyHeader = require('ScrollViewStickyHeader');
 const StyleSheet = require('StyleSheet');
-const StyleSheetPropType = require('StyleSheetPropType');
 const View = require('View');
-const ViewPropTypes = require('ViewPropTypes');
-const ViewStylePropTypes = require('ViewStylePropTypes');
 const InternalScrollViewType = require('InternalScrollViewType');
 
 const createReactClass = require('create-react-class');
@@ -531,95 +524,6 @@ export type Props = $ReadOnly<{|
  */
 const ScrollView = createReactClass({
   displayName: 'ScrollView',
-  propTypes: {
-    ...ViewPropTypes,
-    automaticallyAdjustContentInsets: PropTypes.bool,
-    contentInset: EdgeInsetsPropType,
-    contentOffset: PointPropType,
-    bounces: PropTypes.bool,
-    bouncesZoom: PropTypes.bool,
-    alwaysBounceHorizontal: PropTypes.bool,
-    alwaysBounceVertical: PropTypes.bool,
-    centerContent: PropTypes.bool,
-    contentContainerStyle: StyleSheetPropType(ViewStylePropTypes),
-    decelerationRate: PropTypes.oneOfType([
-      PropTypes.oneOf(['fast', 'normal']),
-      PropTypes.number,
-    ]),
-    horizontal: PropTypes.bool,
-    indicatorStyle: PropTypes.oneOf([
-      'default', // default
-      'black',
-      'white',
-    ]),
-    invertStickyHeaders: PropTypes.bool,
-    directionalLockEnabled: PropTypes.bool,
-    canCancelContentTouches: PropTypes.bool,
-    keyboardDismissMode: PropTypes.oneOf([
-      'none', // default
-      'on-drag', // Cross-platform
-      'interactive', // iOS-only
-    ]),
-    keyboardShouldPersistTaps: PropTypes.oneOf([
-      'always',
-      'never',
-      'handled',
-      false,
-      true,
-    ]),
-    maintainVisibleContentPosition: PropTypes.shape({
-      minIndexForVisible: PropTypes.number.isRequired,
-      autoscrollToTopThreshold: PropTypes.number,
-    }),
-    maximumZoomScale: PropTypes.number,
-    minimumZoomScale: PropTypes.number,
-    nestedScrollEnabled: PropTypes.bool,
-    onMomentumScrollBegin: PropTypes.func,
-    onMomentumScrollEnd: PropTypes.func,
-    onScroll: PropTypes.func,
-    onScrollBeginDrag: PropTypes.func,
-    onScrollEndDrag: PropTypes.func,
-    onContentSizeChange: PropTypes.func,
-    pagingEnabled: PropTypes.bool,
-    pinchGestureEnabled: PropTypes.bool,
-    scrollEnabled: PropTypes.bool,
-    scrollEventThrottle: PropTypes.number,
-    scrollIndicatorInsets: EdgeInsetsPropType,
-    scrollsToTop: PropTypes.bool,
-    showsHorizontalScrollIndicator: PropTypes.bool,
-    showsVerticalScrollIndicator: PropTypes.bool,
-    stickyHeaderIndices: PropTypes.arrayOf(PropTypes.number),
-    snapToInterval: PropTypes.number,
-    snapToAlignment: PropTypes.oneOf([
-      'start', // default
-      'center',
-      'end',
-    ]),
-    removeClippedSubviews: PropTypes.bool,
-    zoomScale: PropTypes.number,
-    contentInsetAdjustmentBehavior: PropTypes.oneOf([
-      'automatic',
-      'scrollableAxes',
-      'never', // default
-      'always',
-    ]),
-    refreshControl: PropTypes.element,
-
-    endFillColor: ColorPropType,
-
-    scrollPerfTag: PropTypes.string,
-
-    overScrollMode: PropTypes.oneOf(['auto', 'always', 'never']),
-    DEPRECATED_sendUpdatedChildFrames: PropTypes.bool,
-    scrollBarThumbImage: PropTypes.oneOfType([
-      PropTypes.shape({
-        uri: PropTypes.string,
-      }),
-      // Opaque type returned by import IMAGE from './image.jpg'
-      PropTypes.number,
-    ]),
-  },
-
   mixins: [ScrollResponder.Mixin],
 
   _scrollAnimatedValue: (new AnimatedImplementation.Value(
@@ -637,11 +541,9 @@ const ScrollView = createReactClass({
 
   UNSAFE_componentWillMount: function() {
     this._scrollAnimatedValue = new AnimatedImplementation.Value(
-      // $FlowFixMe
       this.props.contentOffset ? this.props.contentOffset.y : 0,
     );
     this._scrollAnimatedValue.setOffset(
-      // $FlowFixMe
       this.props.contentInset ? this.props.contentInset.top : 0,
     );
     this._stickyHeaderRefs = new Map();
@@ -784,7 +686,6 @@ const ScrollView = createReactClass({
     if (!this.props.stickyHeaderIndices) {
       return;
     }
-    // $FlowFixMe Invalid prop usage
     const childArray = React.Children.toArray(this.props.children);
     if (key !== this._getKeyForIndex(index, childArray)) {
       // ignore stale layout update
@@ -794,10 +695,8 @@ const ScrollView = createReactClass({
     const layoutY = event.nativeEvent.layout.y;
     this._headerLayoutYs.set(key, layoutY);
 
-    // $FlowFixMe Invalid prop usage
     const indexOfIndex = this.props.stickyHeaderIndices.indexOf(index);
     const previousHeaderIndex = this.props.stickyHeaderIndices[
-      // $FlowFixMe Invalid prop usage
       indexOfIndex - 1
     ];
     if (previousHeaderIndex != null) {
@@ -918,16 +817,13 @@ const ScrollView = createReactClass({
     const hasStickyHeaders =
       stickyHeaderIndices && stickyHeaderIndices.length > 0;
     const childArray =
-      // $FlowFixMe Invalid prop usage
       hasStickyHeaders && React.Children.toArray(this.props.children);
     const children = hasStickyHeaders
       ? // $FlowFixMe Invalid prop usage
         childArray.map((child, index) => {
-          // $FlowFixMe Invalid prop usage
           const indexOfIndex = child ? stickyHeaderIndices.indexOf(index) : -1;
           if (indexOfIndex > -1) {
             const key = child.key;
-            // $FlowFixMe Invalid prop usage
             const nextIndex = stickyHeaderIndices[indexOfIndex + 1];
             return (
               <ScrollViewStickyHeader
@@ -949,8 +845,7 @@ const ScrollView = createReactClass({
             return child;
           }
         })
-      : // $FlowFixMe Invalid prop usage
-        this.props.children;
+      : this.props.children;
     const contentContainer = (
       <ScrollContentContainerViewClass
         {...contentSizeChangeProps}
@@ -1039,7 +934,6 @@ const ScrollView = createReactClass({
         // On iOS the RefreshControl is a child of the ScrollView.
         // tvOS lacks native support for RefreshControl, so don't include it in that case
         return (
-          // $FlowFixMe Invalid prop usage
           <ScrollViewClass {...props} ref={this._setScrollViewRef}>
             {Platform.isTV ? null : refreshControl}
             {contentContainer}
@@ -1058,7 +952,6 @@ const ScrollView = createReactClass({
           <ScrollViewClass
             {...props}
             style={baseStyle}
-            // $FlowFixMe Invalid prop usage
             ref={this._setScrollViewRef}>
             {contentContainer}
           </ScrollViewClass>,
@@ -1066,7 +959,6 @@ const ScrollView = createReactClass({
       }
     }
     return (
-      // $FlowFixMe Invalid prop usage
       <ScrollViewClass {...props} ref={this._setScrollViewRef}>
         {contentContainer}
       </ScrollViewClass>
diff --git a/Libraries/Components/WebView/WebView.ios.js b/Libraries/Components/WebView/WebView.ios.js
index ca91bc3b877e..56290df97bcf 100644
--- a/Libraries/Components/WebView/WebView.ios.js
+++ b/Libraries/Components/WebView/WebView.ios.js
@@ -203,7 +203,10 @@ class WebView extends React.Component {
      *   - fast: 0.99 (the default for iOS web view)
      * @platform ios
      */
-    decelerationRate: ScrollView.propTypes.decelerationRate,
+    decelerationRate: PropTypes.oneOfType([
+      PropTypes.oneOf(['fast', 'normal']),
+      PropTypes.number,
+    ]),
     /**
      * Boolean value that determines whether scrolling is enabled in the
      * `WebView`. The default value is `true`.
diff --git a/Libraries/Lists/ListView/ListView.js b/Libraries/Lists/ListView/ListView.js
index 10ab9aef3101..bed5dbda2e2f 100644
--- a/Libraries/Lists/ListView/ListView.js
+++ b/Libraries/Lists/ListView/ListView.js
@@ -13,7 +13,6 @@ const InternalListViewType = require('InternalListViewType');
 const ListViewDataSource = require('ListViewDataSource');
 const Platform = require('Platform');
 const React = require('React');
-const PropTypes = require('prop-types');
 const ReactNative = require('ReactNative');
 const RCTScrollViewManager = require('NativeModules').ScrollViewManager;
 const ScrollView = require('ScrollView');
@@ -37,22 +36,124 @@ const DEFAULT_SCROLL_CALLBACK_THROTTLE = 50;
 type Props = $ReadOnly<{|
   ...ScrollViewProps,
 
+  /**
+   * An instance of [ListView.DataSource](docs/listviewdatasource.html) to use
+   */
   dataSource: ListViewDataSource,
+  /**
+   * (sectionID, rowID, adjacentRowHighlighted) => renderable
+   *
+   * If provided, a renderable component to be rendered as the separator
+   * below each row but not the last row if there is a section header below.
+   * Take a sectionID and rowID of the row above and whether its adjacent row
+   * is highlighted.
+   */
   renderSeparator?: ?Function,
+  /**
+   * (rowData, sectionID, rowID, highlightRow) => renderable
+   *
+   * Takes a data entry from the data source and its ids and should return
+   * a renderable component to be rendered as the row. By default the data
+   * is exactly what was put into the data source, but it's also possible to
+   * provide custom extractors. ListView can be notified when a row is
+   * being highlighted by calling `highlightRow(sectionID, rowID)`. This
+   * sets a boolean value of adjacentRowHighlighted in renderSeparator, allowing you
+   * to control the separators above and below the highlighted row. The highlighted
+   * state of a row can be reset by calling highlightRow(null).
+   */
   renderRow: Function,
+  /**
+   * How many rows to render on initial component mount. Use this to make
+   * it so that the first screen worth of data appears at one time instead of
+   * over the course of multiple frames.
+   */
   initialListSize?: ?number,
+  /**
+   * Called when all rows have been rendered and the list has been scrolled
+   * to within onEndReachedThreshold of the bottom. The native scroll
+   * event is provided.
+   */
   onEndReached?: ?Function,
+  /**
+   * Threshold in pixels (virtual, not physical) for calling onEndReached.
+   */
   onEndReachedThreshold?: ?number,
+  /**
+   * Number of rows to render per event loop. Note: if your 'rows' are actually
+   * cells, i.e. they don't span the full width of your view (as in the
+   * ListViewGridLayoutExample), you should set the pageSize to be a multiple
+   * of the number of cells per row, otherwise you're likely to see gaps at
+   * the edge of the ListView as new pages are loaded.
+   */
   pageSize?: ?number,
+  /**
+   * () => renderable
+   *
+   * The header and footer are always rendered (if these props are provided)
+   * on every render pass. If they are expensive to re-render, wrap them
+   * in StaticContainer or other mechanism as appropriate. Footer is always
+   * at the bottom of the list, and header at the top, on every render pass.
+   * In a horizontal ListView, the header is rendered on the left and the
+   * footer on the right.
+   */
   renderFooter?: ?Function,
   renderHeader?: ?Function,
+  /**
+   * (sectionData, sectionID) => renderable
+   *
+   * If provided, a header is rendered for this section.
+   */
   renderSectionHeader?: ?Function,
+  /**
+   * (props) => renderable
+   *
+   * A function that returns the scrollable component in which the list rows
+   * are rendered. Defaults to returning a ScrollView with the given props.
+   */
   renderScrollComponent?: ?Function,
+  /**
+   * How early to start rendering rows before they come on screen, in
+   * pixels.
+   */
   scrollRenderAheadDistance?: ?number,
+  /**
+   * (visibleRows, changedRows) => void
+   *
+   * Called when the set of visible rows changes. `visibleRows` maps
+   * { sectionID: { rowID: true }} for all the visible rows, and
+   * `changedRows` maps { sectionID: { rowID: true | false }} for the rows
+   * that have changed their visibility, with true indicating visible, and
+   * false indicating the view has moved out of view.
+   */
   onChangeVisibleRows?: ?Function,
+  /**
+   * A performance optimization for improving scroll perf of
+   * large lists, used in conjunction with overflow: 'hidden' on the row
+   * containers. This is enabled by default.
+   */
   removeClippedSubviews?: ?boolean,
+  /**
+   * Makes the sections headers sticky. The sticky behavior means that it
+   * will scroll with the content at the top of the section until it reaches
+   * the top of the screen, at which point it will stick to the top until it
+   * is pushed off the screen by the next section header. This property is
+   * not supported in conjunction with `horizontal={true}`. Only enabled by
+   * default on iOS because of typical platform standards.
+   */
   stickySectionHeadersEnabled?: ?boolean,
+  /**
+   * An array of child indices determining which children get docked to the
+   * top of the screen when scrolling. For example, passing
+   * `stickyHeaderIndices={[0]}` will cause the first child to be fixed to the
+   * top of the scroll view. This property is not supported in conjunction
+   * with `horizontal={true}`.
+   */
   stickyHeaderIndices?: ?$ReadOnlyArray<number>,
+  /**
+   * Flag indicating whether empty section headers should be rendered. In the future release
+   * empty section headers will be rendered by default, and the flag will be deprecated.
+   * If empty sections are not desired to be rendered their indices should be excluded from sectionID object.
+   */
   enableEmptySections?: ?boolean,
 |}>;
 
@@ -128,136 +229,6 @@ const ListView = createReactClass({
     DataSource: ListViewDataSource,
   },
 
-  /**
-   * You must provide a renderRow function. If you omit any of the other render
-   * functions, ListView will simply skip rendering them.
-   *
-   * - renderRow(rowData, sectionID, rowID, highlightRow);
-   * - renderSectionHeader(sectionData, sectionID);
-   */
-  propTypes: {
-    ...ScrollView.propTypes,
-    /**
-     * An instance of [ListView.DataSource](docs/listviewdatasource.html) to use
-     */
-    dataSource: PropTypes.instanceOf(ListViewDataSource).isRequired,
-    /**
-     * (sectionID, rowID, adjacentRowHighlighted) => renderable
-     *
-     * If provided, a renderable component to be rendered as the separator
-     * below each row but not the last row if there is a section header below.
-     * Take a sectionID and rowID of the row above and whether its adjacent row
-     * is highlighted.
-     */
-    renderSeparator: PropTypes.func,
-    /**
-     * (rowData, sectionID, rowID, highlightRow) => renderable
-     *
-     * Takes a data entry from the data source and its ids and should return
-     * a renderable component to be rendered as the row. By default the data
-     * is exactly what was put into the data source, but it's also possible to
-     * provide custom extractors. ListView can be notified when a row is
-     * being highlighted by calling `highlightRow(sectionID, rowID)`. This
-     * sets a boolean value of adjacentRowHighlighted in renderSeparator, allowing you
-     * to control the separators above and below the highlighted row. The highlighted
-     * state of a row can be reset by calling highlightRow(null).
-     */
-    renderRow: PropTypes.func.isRequired,
-    /**
-     * How many rows to render on initial component mount. Use this to make
-     * it so that the first screen worth of data appears at one time instead of
-     * over the course of multiple frames.
-     */
-    initialListSize: PropTypes.number.isRequired,
-    /**
-     * Called when all rows have been rendered and the list has been scrolled
-     * to within onEndReachedThreshold of the bottom. The native scroll
-     * event is provided.
-     */
-    onEndReached: PropTypes.func,
-    /**
-     * Threshold in pixels (virtual, not physical) for calling onEndReached.
-     */
-    onEndReachedThreshold: PropTypes.number.isRequired,
-    /**
-     * Number of rows to render per event loop. Note: if your 'rows' are actually
-     * cells, i.e. they don't span the full width of your view (as in the
-     * ListViewGridLayoutExample), you should set the pageSize to be a multiple
-     * of the number of cells per row, otherwise you're likely to see gaps at
-     * the edge of the ListView as new pages are loaded.
-     */
-    pageSize: PropTypes.number.isRequired,
-    /**
-     * () => renderable
-     *
-     * The header and footer are always rendered (if these props are provided)
-     * on every render pass. If they are expensive to re-render, wrap them
-     * in StaticContainer or other mechanism as appropriate. Footer is always
-     * at the bottom of the list, and header at the top, on every render pass.
-     * In a horizontal ListView, the header is rendered on the left and the
-     * footer on the right.
-     */
-    renderFooter: PropTypes.func,
-    renderHeader: PropTypes.func,
-    /**
-     * (sectionData, sectionID) => renderable
-     *
-     * If provided, a header is rendered for this section.
-     */
-    renderSectionHeader: PropTypes.func,
-    /**
-     * (props) => renderable
-     *
-     * A function that returns the scrollable component in which the list rows
-     * are rendered. Defaults to returning a ScrollView with the given props.
-     */
-    renderScrollComponent: PropTypes.func.isRequired,
-    /**
-     * How early to start rendering rows before they come on screen, in
-     * pixels.
-     */
-    scrollRenderAheadDistance: PropTypes.number.isRequired,
-    /**
-     * (visibleRows, changedRows) => void
-     *
-     * Called when the set of visible rows changes. `visibleRows` maps
-     * { sectionID: { rowID: true }} for all the visible rows, and
-     * `changedRows` maps { sectionID: { rowID: true | false }} for the rows
-     * that have changed their visibility, with true indicating visible, and
-     * false indicating the view has moved out of view.
-     */
-    onChangeVisibleRows: PropTypes.func,
-    /**
-     * A performance optimization for improving scroll perf of
-     * large lists, used in conjunction with overflow: 'hidden' on the row
-     * containers. This is enabled by default.
-     */
-    removeClippedSubviews: PropTypes.bool,
-    /**
-     * Makes the sections headers sticky. The sticky behavior means that it
-     * will scroll with the content at the top of the section until it reaches
-     * the top of the screen, at which point it will stick to the top until it
-     * is pushed off the screen by the next section header. This property is
-     * not supported in conjunction with `horizontal={true}`. Only enabled by
-     * default on iOS because of typical platform standards.
-     */
-    stickySectionHeadersEnabled: PropTypes.bool,
-    /**
-     * An array of child indices determining which children get docked to the
-     * top of the screen when scrolling. For example, passing
-     * `stickyHeaderIndices={[0]}` will cause the first child to be fixed to the
-     * top of the scroll view. This property is not supported in conjunction
-     * with `horizontal={true}`.
-     */
-    stickyHeaderIndices: PropTypes.arrayOf(PropTypes.number).isRequired,
-    /**
-     * Flag indicating whether empty section headers should be rendered. In the future release
-     * empty section headers will be rendered by default, and the flag will be deprecated.
-     * If empty sections are not desired to be rendered their indices should be excluded from sectionID object.
-     */
-    enableEmptySections: PropTypes.bool,
-  },
-
   /**
    * Exports some data, e.g. for perf investigations or analytics.
    */
@@ -296,7 +267,7 @@ const ListView = createReactClass({
    *
    * See `ScrollView#scrollTo`.
    */
-  scrollTo: function(...args: Array<mixed>) {
+  scrollTo: function(...args: any) {
     if (this._scrollComponent && this._scrollComponent.scrollTo) {
       this._scrollComponent.scrollTo(...args);
     }
@@ -312,7 +283,7 @@ const ListView = createReactClass({
    *
    * See `ScrollView#scrollToEnd`.
    */
-  scrollToEnd: function(options?: ?{animated?: ?boolean}) {
+  scrollToEnd: function(options?: ?{animated?: boolean}) {
     if (this._scrollComponent) {
       if (this._scrollComponent.scrollToEnd) {
         this._scrollComponent.scrollToEnd(options);
@@ -366,7 +337,7 @@ const ListView = createReactClass({
   },
 
   getInnerViewNode: function() {
-    return this._scrollComponent.getInnerViewNode();
+    return this._scrollComponent && this._scrollComponent.getInnerViewNode();
   },
 
   UNSAFE_componentWillMount: function() {

From 46ffb106278425631c26049fa50b185e90789c9c Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Thu, 5 Jul 2018 15:08:41 -0700
Subject: [PATCH 0989/1109] Fix null source bug in Image view while accessing
 source's uri

Summary: Fix null source bug in Image view while accessing source's uri

Reviewed By: achen1

Differential Revision: D8739379

fbshipit-source-id: 0338b19135fa8af9ebe599cabbc9e321fb0906a5
---
 Libraries/Image/Image.android.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index ec25a4ee1eeb..99636169f4c9 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -212,7 +212,7 @@ let Image = (
     );
   }
 
-  if (!source.uri && !Array.isArray(source)) {
+  if (source && !source?.uri && !Array.isArray(source)) {
     return null;
   }
 

From 0f4926598aa4c3532949572f8c7c7a20b568e47a Mon Sep 17 00:00:00 2001
From: Florian Schoellhammer <fschoellhammer@fb.com>
Date: Thu, 5 Jul 2018 19:10:28 -0700
Subject: [PATCH 0990/1109] Back out "[react-native][PR] Remove the deprecated
 `isIPhoneX_deprecated` constant"

Summary:
Original commit changeset: 0b0b3a2d7b80

Reverting D8714400 which removed the `isIPhoneX_deprecated` flag, which is still widely used across the RN codebase https://fburl.com/biggrep/16jg5bzn

Reviewed By: hramos

Differential Revision: D8743401

fbshipit-source-id: cfc44bdd8019eda41e67ca573b20be417d121d12
---
 RNTester/js/SafeAreaViewExample.js | 24 ++++++++++++++++++++++++
 React/Modules/RCTDeviceInfo.m      | 21 +++++++++++++++++++++
 2 files changed, 45 insertions(+)

diff --git a/RNTester/js/SafeAreaViewExample.js b/RNTester/js/SafeAreaViewExample.js
index 0af1d1f1f99a..927a26651a4f 100644
--- a/RNTester/js/SafeAreaViewExample.js
+++ b/RNTester/js/SafeAreaViewExample.js
@@ -64,6 +64,21 @@ class SafeAreaViewExample extends React.Component<
   }
 }
 
+class IsIPhoneXExample extends React.Component<{}> {
+  render() {
+    return (
+      <View>
+        <Text>
+          Is this an iPhone X:{' '}
+          {DeviceInfo.isIPhoneX_deprecated
+            ? 'Yeah!'
+            : 'Nope. (Or `isIPhoneX_deprecated` was already removed.)'}
+        </Text>
+      </View>
+    );
+  }
+}
+
 exports.examples = [
   {
     title: '<SafeAreaView> Example',
@@ -71,6 +86,15 @@ exports.examples = [
       'SafeAreaView automatically applies paddings reflect the portion of the view that is not covered by other (special) ancestor views.',
     render: () => <SafeAreaViewExample />,
   },
+  {
+    title: 'isIPhoneX_deprecated Example',
+    description:
+      '`DeviceInfo.isIPhoneX_deprecated` returns true only on iPhone X. ' +
+      'Note: This prop is deprecated and will be removed right after June 01, 2018. ' +
+      'Please use this only for a quick and temporary solution. ' +
+      'Use <SafeAreaView> instead.',
+    render: () => <IsIPhoneXExample />,
+  },
 ];
 
 var styles = StyleSheet.create({
diff --git a/React/Modules/RCTDeviceInfo.m b/React/Modules/RCTDeviceInfo.m
index 7db187e3063d..20e53d55af61 100644
--- a/React/Modules/RCTDeviceInfo.m
+++ b/React/Modules/RCTDeviceInfo.m
@@ -51,6 +51,22 @@ - (void)setBridge:(RCTBridge *)bridge
 #endif
 }
 
+static BOOL RCTIsIPhoneX() {
+  static BOOL isIPhoneX = NO;
+  static dispatch_once_t onceToken;
+
+  dispatch_once(&onceToken, ^{
+    RCTAssertMainQueue();
+
+    isIPhoneX = CGSizeEqualToSize(
+      [UIScreen mainScreen].nativeBounds.size,
+      CGSizeMake(1125, 2436)
+    );
+  });
+
+  return isIPhoneX;
+}
+
 static NSDictionary *RCTExportedDimensions(RCTBridge *bridge)
 {
   RCTAssertMainQueue();
@@ -86,6 +102,11 @@ - (void)invalidate
 {
   return @{
     @"Dimensions": RCTExportedDimensions(_bridge),
+    // Note:
+    // This prop is deprecated and will be removed right after June 01, 2018.
+    // Please use this only for a quick and temporary solution.
+    // Use <SafeAreaView> instead.
+    @"isIPhoneX_deprecated": @(RCTIsIPhoneX()),
   };
 }
 

From ac09261a4cb543ee30b38d1ebdc57046f2d7c406 Mon Sep 17 00:00:00 2001
From: Yan Soares Couto <yancouto@fb.com>
Date: Fri, 6 Jul 2018 04:16:19 -0700
Subject: [PATCH 0991/1109] downloadBundleFromURL with an optional starting
 Request.Builder

Summary: This makes it possible to specify an optional Request.Builder when calling `downloadBundleFromURL` (the old method still works as usual).

Reviewed By: davidaurelio

Differential Revision: D8691303

fbshipit-source-id: 2fb2aecd3506355c6b3a72457a7bb9acfd03b18d
---
 .../react/devsupport/BundleDownloader.java    | 23 ++++++++++++++-----
 .../react/devsupport/DevServerHelper.java     | 10 ++++++++
 2 files changed, 27 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
index e64d02edbb97..cf35c8a6ce94 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/BundleDownloader.java
@@ -104,14 +104,25 @@ public BundleDownloader(OkHttpClient client) {
   }
 
   public void downloadBundleFromURL(
-    final DevBundleDownloadListener callback,
-    final File outputFile,
-    final String bundleURL,
-    final @Nullable BundleInfo bundleInfo,
-    final BundleDeltaClient.ClientType clientType) {
+      final DevBundleDownloadListener callback,
+      final File outputFile,
+      final String bundleURL,
+      final @Nullable BundleInfo bundleInfo,
+      final BundleDeltaClient.ClientType clientType) {
+    downloadBundleFromURL(
+        callback, outputFile, bundleURL, bundleInfo, clientType, new Request.Builder());
+  }
+
+  public void downloadBundleFromURL(
+      final DevBundleDownloadListener callback,
+      final File outputFile,
+      final String bundleURL,
+      final @Nullable BundleInfo bundleInfo,
+      final BundleDeltaClient.ClientType clientType,
+      Request.Builder requestBuilder) {
 
     final Request request =
-        new Request.Builder()
+        requestBuilder
             .url(formatBundleUrl(bundleURL, clientType))
             // FIXME: there is a bug that makes MultipartStreamReader to never find the end of the
             // multipart message. This temporarily disables the multipart mode to work around it,
diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
index bcf803aa6f97..b1342c0555e7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
@@ -382,6 +382,16 @@ public void downloadBundleFromURL(
     mBundleDownloader.downloadBundleFromURL(callback, outputFile, bundleURL, bundleInfo, getDeltaClientType());
   }
 
+  public void downloadBundleFromURL(
+      DevBundleDownloadListener callback,
+      File outputFile,
+      String bundleURL,
+      BundleDownloader.BundleInfo bundleInfo,
+      Request.Builder requestBuilder) {
+    mBundleDownloader.downloadBundleFromURL(
+        callback, outputFile, bundleURL, bundleInfo, getDeltaClientType(), requestBuilder);
+  }
+
   private BundleDeltaClient.ClientType getDeltaClientType() {
     if (mSettings.isBundleDeltasCppEnabled()) {
       return BundleDeltaClient.ClientType.NATIVE;

From 6292e2707ae1d26949dea66a202216857f279802 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Fri, 6 Jul 2018 09:12:56 -0700
Subject: [PATCH 0992/1109] Revert order of Remove Mount Item operations

Summary: Revert the order of "remove mount items", to ensure views are removed from high index to low index.

Reviewed By: shergin

Differential Revision: D8742796

fbshipit-source-id: 6e04c39386d290bf3958ee83256d4fbe23e2c4ca
---
 ReactCommon/fabric/uimanager/Differentiator.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/Differentiator.cpp b/ReactCommon/fabric/uimanager/Differentiator.cpp
index 7a2c9a4f613a..2d451b19fae6 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.cpp
+++ b/ReactCommon/fabric/uimanager/Differentiator.cpp
@@ -152,7 +152,7 @@ static void calculateMutationInstructions(
   // All instructions in an optimal order:
   instructions.insert(instructions.end(), destructionDownwardInstructions.begin(), destructionDownwardInstructions.end());
   instructions.insert(instructions.end(), replaceInstructions.begin(), replaceInstructions.end());
-  instructions.insert(instructions.end(), removeInstructions.begin(), removeInstructions.end());
+  instructions.insert(instructions.end(), removeInstructions.rbegin(), removeInstructions.rend());
   instructions.insert(instructions.end(), createInstructions.begin(), createInstructions.end());
   instructions.insert(instructions.end(), downwardInstructions.begin(), downwardInstructions.end());
   instructions.insert(instructions.end(), insertInstructions.begin(), insertInstructions.end());

From 816d302e98cb14224f8bb2772299f87777a26ef8 Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Fri, 6 Jul 2018 12:23:52 -0700
Subject: [PATCH 0993/1109] Reverting image source null so the fix can go all
 once later

Summary: Image source null which is in RC D8628053 has a bug which has a fix but didn't make to RC. Reverting so it can be cleaned up before going in RC.

Reviewed By: achen1

Differential Revision: D8751687

fbshipit-source-id: e08b23a031455be23047880871813bdc840542dd
---
 Libraries/Image/Image.android.js                  |  9 ++++++---
 .../react/views/image/ReactImageView.java         | 15 +++++----------
 2 files changed, 11 insertions(+), 13 deletions(-)

diff --git a/Libraries/Image/Image.android.js b/Libraries/Image/Image.android.js
index 99636169f4c9..d0e685a5e642 100644
--- a/Libraries/Image/Image.android.js
+++ b/Libraries/Image/Image.android.js
@@ -190,6 +190,9 @@ let Image = (
     props.loadingIndicatorSource,
   );
 
+  // As opposed to the ios version, here we render `null` when there is no source, source.uri
+  // or source array.
+
   if (source && source.uri === '') {
     console.warn('source.uri should not be an empty string');
   }
@@ -212,13 +215,13 @@ let Image = (
     );
   }
 
-  if (source && !source?.uri && !Array.isArray(source)) {
+  if (!source || (!source.uri && !Array.isArray(source))) {
     return null;
   }
 
   let style;
   let sources;
-  if (source?.uri != null) {
+  if (source.uri) {
     const {width, height} = source;
     style = flattenStyle([{width, height}, styles.base, props.style]);
     sources = [{uri: source.uri}];
@@ -232,7 +235,7 @@ let Image = (
     style,
     shouldNotifyLoadEvents: !!(onLoadStart || onLoad || onLoadEnd || onError),
     src: sources,
-    headers: source?.headers,
+    headers: source.headers,
     defaultSrc: defaultSource ? defaultSource.uri : null,
     loadingIndicatorSrc: loadingIndicatorSource
       ? loadingIndicatorSource.uri
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
index cf7a1580fcb0..91817b955b21 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/ReactImageView.java
@@ -1,3 +1,4 @@
+
 /**
  * Copyright (c) 2015-present, Facebook, Inc.
  *
@@ -70,9 +71,6 @@ public class ReactImageView extends GenericDraweeView {
 
   public static final int REMOTE_IMAGE_FADE_DURATION_MS = 300;
 
-  public static final String REMOTE_TRANSPARENT_BITMAP_URI =
-  "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAQAAAC1HAwCAAAAC0lEQVR42mNkYAAAAAYAAjCB0C8AAAAASUVORK5CYII=";
-
   private static float[] sComputedCornerRadii = new float[4];
 
   /*
@@ -341,10 +339,7 @@ public void setResizeMethod(ImageResizeMethod resizeMethod) {
 
   public void setSource(@Nullable ReadableArray sources) {
     mSources.clear();
-    if (sources == null || sources.size() == 0) {
-      ImageSource imageSource = new ImageSource(getContext(), REMOTE_TRANSPARENT_BITMAP_URI);
-      mSources.add(imageSource);
-    } else {
+    if (sources != null && sources.size() != 0) {
       // Optimize for the case where we have just one uri, case in which we don't need the sizes
       if (sources.size() == 1) {
         ReadableMap source = sources.getMap(0);
@@ -578,9 +573,9 @@ private boolean isTiled() {
   private void setSourceImage() {
     mImageSource = null;
     if (mSources.isEmpty()) {
-      ImageSource imageSource = new ImageSource(getContext(), REMOTE_TRANSPARENT_BITMAP_URI);
-       mSources.add(imageSource);
-     } else if (hasMultipleSources()) {
+      return;
+    }
+    if (hasMultipleSources()) {
       MultiSourceResult multiSource =
         MultiSourceHelper.getBestSourceForSize(getWidth(), getHeight(), mSources);
       mImageSource = multiSource.getBestResult();

From de09fd53bd41716142364e769e72b363bb3d3405 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Fri, 6 Jul 2018 12:31:09 -0700
Subject: [PATCH 0994/1109] Remove setJSEntryPoint from ReactRootView

Summary:
Doesn't look like it was ever used according to diffgrep https://our.intern.facebook.com/intern/diffgrep/?author=&expand_all=false&filepath=&matcher=strmatch&query=setJSEntryPoint&repo=fbsource&rev_type=all&result_size=3&search_order=2&source&target=added%20or%20removed

axe is this okay?

Differential Revision: D8730783

fbshipit-source-id: 1e6b9e8fbd50c108a24b592793060a5344f1d0b1
---
 .../facebook/react/ReactInstanceManager.java  |  2 +-
 .../com/facebook/react/ReactRootView.java     | 38 +++----------------
 2 files changed, 6 insertions(+), 34 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
index e5b3bae44123..075ba03ea260 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactInstanceManager.java
@@ -1016,7 +1016,7 @@ private void attachRootViewToInstance(
     UIManager uiManagerModule = UIManagerHelper.getUIManager(mCurrentReactContext, rootView.getUIManagerType());
     final int rootTag = uiManagerModule.addRootView(rootView);
     rootView.setRootViewTag(rootTag);
-    rootView.invokeJSEntryPoint();
+    rootView.runApplication();
     Systrace.beginAsyncSection(
       TRACE_TAG_REACT_JAVA_BRIDGE,
       "pre_rootView.onAttachedToReactInstance",
diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 5f8ff1699f14..6e8a92f60368 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -7,9 +7,9 @@
 
 package com.facebook.react;
 
-import static com.facebook.systrace.Systrace.TRACE_TAG_REACT_JAVA_BRIDGE;
-import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
 import static com.facebook.react.uimanager.common.UIManagerType.DEFAULT;
+import static com.facebook.react.uimanager.common.UIManagerType.FABRIC;
+import static com.facebook.systrace.Systrace.TRACE_TAG_REACT_JAVA_BRIDGE;
 
 import android.content.Context;
 import android.graphics.Canvas;
@@ -50,9 +50,9 @@
 import com.facebook.react.uimanager.UIManagerModule;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
+import com.facebook.react.uimanager.common.UIManagerType;
 import com.facebook.react.uimanager.events.EventDispatcher;
 import com.facebook.systrace.Systrace;
-import com.facebook.react.uimanager.common.UIManagerType;
 import javax.annotation.Nullable;
 
 /**
@@ -93,7 +93,6 @@ public interface ReactRootViewEventListener {
   private boolean mWasMeasured = false;
   private int mWidthMeasureSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED);
   private int mHeightMeasureSpec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED);
-  private @Nullable Runnable mJSEntryPoint;
   private @UIManagerType int mUIManagerType = DEFAULT;
 
   public ReactRootView(Context context) {
@@ -454,7 +453,7 @@ public void setAppProperties(@Nullable Bundle appProperties) {
     UiThreadUtil.assertOnUiThread();
     mAppProperties = appProperties;
     if (getRootViewTag() != 0) {
-      invokeJSEntryPoint();
+      runApplication();
     }
   }
 
@@ -462,34 +461,7 @@ public void setAppProperties(@Nullable Bundle appProperties) {
    * Calls into JS to start the React application. Can be called multiple times with the
    * same rootTag, which will re-render the application from the root.
    */
-  /*package */ void invokeJSEntryPoint() {
-    if (mJSEntryPoint == null) {
-      defaultJSEntryPoint();
-    } else {
-      mJSEntryPoint.run();
-    }
-  }
-
-  /**
-   * Set a custom entry point for invoking JS. By default, this is AppRegistry.runApplication
-   * @param jsEntryPoint
-   */
-  public void setJSEntryPoint(Runnable jsEntryPoint) {
-    mJSEntryPoint = jsEntryPoint;
-  }
-
-  public void invokeDefaultJSEntryPoint(@Nullable Bundle appProperties) {
-    UiThreadUtil.assertOnUiThread();
-    if (appProperties != null) {
-      mAppProperties = appProperties;
-    }
-    defaultJSEntryPoint();
-  }
-
-  /**
-   * Calls the default entry point into JS which is AppRegistry.runApplication()
-   */
-  private void defaultJSEntryPoint() {
+  /* package */ void runApplication() {
       Systrace.beginSection(TRACE_TAG_REACT_JAVA_BRIDGE, "ReactRootView.runApplication");
       try {
         if (mReactInstanceManager == null || !mIsAttachedToInstance) {

From e0e9c1549e9f4bf15060dd40764c838865fa593f Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 6 Jul 2018 14:34:38 -0700
Subject: [PATCH 0995/1109] Fabric: Improved prettyprinting of
 TreeMutationInstruction

Summary:
@public
Quite trivial... and nice.

Reviewed By: mdvacca

Differential Revision: D8709951

fbshipit-source-id: 63e53eb85361fe3a0a0ecd7f21bf4c7db049d5bf
---
 .../uimanager/TreeMutationInstruction.cpp       | 17 ++++++++++++++++-
 .../fabric/uimanager/TreeMutationInstruction.h  |  1 +
 2 files changed, 17 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
index c5f07453749c..630e13202d1b 100644
--- a/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
+++ b/ReactCommon/fabric/uimanager/TreeMutationInstruction.cpp
@@ -150,6 +150,21 @@ std::string TreeMutationInstruction::getDebugName() const {
   }
 };
 
+std::string TreeMutationInstruction::getDebugValue() const {
+  switch (type_) {
+    case Creation:
+      return "[*" + folly::to<std::string>(newChildNode_->getTag()) + "]";
+    case Deletion:
+      return "[~" + folly::to<std::string>(oldChildNode_->getTag()) + "]";
+    case Insertion:
+      return "[" + folly::to<std::string>(newChildNode_->getTag()) + "->" + folly::to<std::string>(parentNode_->getTag()) + "]";
+    case Removal:
+      return "[" + folly::to<std::string>(oldChildNode_->getTag()) + "<~" + folly::to<std::string>(parentNode_->getTag()) + "]";
+    case Replacement:
+      return "[=" + folly::to<std::string>(oldChildNode_->getTag()) + "]";
+  }
+};
+
 SharedDebugStringConvertibleList TreeMutationInstruction::getDebugProps() const {
   DebugStringConvertibleOptions options = {.maximumDepth = 1, .format = false};
 
@@ -176,7 +191,7 @@ SharedDebugStringConvertibleList TreeMutationInstruction::getDebugProps() const
       };
     case Replacement:
       return SharedDebugStringConvertibleList {
-        std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_->getDebugDescription(options)),
+        std::make_shared<DebugStringConvertibleItem>("parentNode", parentNode_ ? parentNode_->getDebugDescription(options) : "nullptr"),
         std::make_shared<DebugStringConvertibleItem>("oldChildNode", oldChildNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("newChildNode", newChildNode_->getDebugDescription(options)),
         std::make_shared<DebugStringConvertibleItem>("index", folly::to<std::string>(index_))
diff --git a/ReactCommon/fabric/uimanager/TreeMutationInstruction.h b/ReactCommon/fabric/uimanager/TreeMutationInstruction.h
index 920cd27f87cb..c27e6f71f353 100644
--- a/ReactCommon/fabric/uimanager/TreeMutationInstruction.h
+++ b/ReactCommon/fabric/uimanager/TreeMutationInstruction.h
@@ -96,6 +96,7 @@ class TreeMutationInstruction:
 #pragma mark - DebugStringConvertible
 
   std::string getDebugName() const override;
+  std::string getDebugValue() const override;
   SharedDebugStringConvertibleList getDebugProps() const override;
 
 private:

From e8ec1cb16ade2221666b2a2257c2e6892ac54b67 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Fri, 6 Jul 2018 14:34:40 -0700
Subject: [PATCH 0996/1109] Fabric: The diffing algorithm does not use source
 nodes anymore

Summary:
@public
... and it's as efficient as it was before.

The previous version of the algorithm used `sourceNode` reference to know the previous state of the node to call the algorithm recursively.
That wasn't so good because of several reasons:
 - It was fragile because we had two different sources of the truth of the "previous state of the tree": committed tree and source node pointer;
 - We had to store weak pointers to source nodes inside cloned nodes. That is not free in terms of performance;
 - The old approach introduced a constraint that all previously used and now reinserted nodes must be cloned to update source node (otherwise, the algorithm would regenerate instructions recreating already existing subtrees);
 - That cloning required access to `isSealed` flag which is supposed to be a debug-only thing (that actually affects performance and must be compile-out for release builds).

The new approach compares nodes with same react tag and naturally cloning-artifacts resilient.

Yes, the new approach uses a map of inserted nodes, but the previous one already had it (otherwise there is no way to tell which nodes should be "deleted"). And anyway, this is a very little map that exists for a very little period of time.

Reviewed By: mdvacca

Differential Revision: D8709953

fbshipit-source-id: 027abb326cf45f00f7bb0bbd7c4e612578268c66
---
 .../fabric/uimanager/Differentiator.cpp       | 65 ++++++++++++-------
 1 file changed, 41 insertions(+), 24 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/Differentiator.cpp b/ReactCommon/fabric/uimanager/Differentiator.cpp
index 2d451b19fae6..641a33a39ff0 100644
--- a/ReactCommon/fabric/uimanager/Differentiator.cpp
+++ b/ReactCommon/fabric/uimanager/Differentiator.cpp
@@ -30,7 +30,7 @@ static void calculateMutationInstructions(
     return;
   }
 
-  std::unordered_set<Tag> insertedTags;
+  std::unordered_map<Tag, SharedShadowNode> insertedNodes;
   int index = 0;
 
   TreeMutationInstructionList createInstructions = {};
@@ -43,8 +43,8 @@ static void calculateMutationInstructions(
 
   // Stage 1: Collectings Updates
   for (index = 0; index < oldChildNodes->size() && index < newChildNodes->size(); index++) {
-    SharedShadowNode oldChildNode = oldChildNodes->at(index);
-    SharedShadowNode newChildNode = newChildNodes->at(index);
+    const auto &oldChildNode = oldChildNodes->at(index);
+    const auto &newChildNode = newChildNodes->at(index);
 
     if (oldChildNode->getTag() != newChildNode->getTag()) {
       // Totally different nodes, updating is impossible.
@@ -74,7 +74,7 @@ static void calculateMutationInstructions(
 
   // Stage 2: Collectings Insertions
   for (; index < newChildNodes->size(); index++) {
-    SharedShadowNode newChildNode = newChildNodes->at(index);
+    const auto &newChildNode = newChildNodes->at(index);
 
     insertInstructions.push_back(
       TreeMutationInstruction::Insert(
@@ -84,23 +84,12 @@ static void calculateMutationInstructions(
       )
     );
 
-    insertedTags.insert(newChildNode->getTag());
-
-    SharedShadowNode newChildSourceNode = newChildNode->getSourceNode();
-    SharedShadowNodeSharedList newChildSourceChildNodes =
-      newChildSourceNode ? newChildSourceNode->getChildren() : ShadowNode::emptySharedShadowNodeSharedList();
-
-    calculateMutationInstructions(
-      *(newChildNode->getChildren()->size() ? &downwardInstructions : &destructionDownwardInstructions),
-      newChildNode,
-      newChildSourceChildNodes,
-      newChildNode->getChildren()
-    );
+    insertedNodes.insert({newChildNode->getTag(), newChildNode});
   }
 
   // Stage 3: Collectings Deletions and Removals
   for (index = lastIndexAfterFirstStage; index < oldChildNodes->size(); index++) {
-    SharedShadowNode oldChildNode = oldChildNodes->at(index);
+    const auto &oldChildNode = oldChildNodes->at(index);
 
     // Even if the old node was (re)inserted, we have to generate `remove`
     // instruction.
@@ -112,12 +101,11 @@ static void calculateMutationInstructions(
       )
     );
 
-    auto numberOfRemovedTags = insertedTags.erase(oldChildNode->getTag());
-    assert(numberOfRemovedTags == 0 || numberOfRemovedTags == 1);
+    const auto &it = insertedNodes.find(oldChildNode->getTag());
 
-    if (numberOfRemovedTags == 0) {
-      // The old node was *not* (re)inserted,
-      // so we have to generate `delete` instruction and apply the algorithm
+    if (it == insertedNodes.end()) {
+      // The old node was *not* (re)inserted.
+      // We have to generate `delete` instruction and apply the algorithm
       // recursively.
       deleteInstructions.push_back(
         TreeMutationInstruction::Delete(
@@ -125,19 +113,41 @@ static void calculateMutationInstructions(
         )
       );
 
+      // We also have to call the algorithm recursively to clean up the entire
+      // subtree starting from the removed node.
       calculateMutationInstructions(
         destructionDownwardInstructions,
         oldChildNode,
         oldChildNode->getChildren(),
         ShadowNode::emptySharedShadowNodeSharedList()
       );
+    } else {
+      // The old node *was* (re)inserted.
+      // We have to call the algorithm recursively if the inserted node
+      // is *not* the same as removed one.
+      const auto &newChildNode = it->second;
+      if (newChildNode != oldChildNode) {
+        calculateMutationInstructions(
+          *(newChildNode->getChildren()->size() ? &downwardInstructions : &destructionDownwardInstructions),
+          newChildNode,
+          oldChildNode->getChildren(),
+          newChildNode->getChildren()
+        );
+      }
+
+      // In any case we have to remove the node from `insertedNodes` as
+      // indication that the node was actually removed (which means that
+      // the node existed before), hence we don't have to generate
+      // `create` instruction.
+      insertedNodes.erase(it);
     }
   }
 
   // Stage 4: Collectings Creations
   for (index = lastIndexAfterFirstStage; index < newChildNodes->size(); index++) {
-    SharedShadowNode newChildNode = newChildNodes->at(index);
-    if (insertedTags.find(newChildNode->getTag()) == insertedTags.end()) {
+    const auto &newChildNode = newChildNodes->at(index);
+
+    if (insertedNodes.find(newChildNode->getTag()) == insertedNodes.end()) {
       // The new node was (re)inserted, so there is no need to create it.
       continue;
     }
@@ -147,6 +157,13 @@ static void calculateMutationInstructions(
         newChildNode
       )
     );
+
+    calculateMutationInstructions(
+      downwardInstructions,
+      newChildNode,
+      ShadowNode::emptySharedShadowNodeSharedList(),
+      newChildNode->getChildren()
+    );
   }
 
   // All instructions in an optimal order:

From 604bcfa4a83396c402ba8beaa13f40d05d6e9f5c Mon Sep 17 00:00:00 2001
From: Konstantin Raev <bestander@fb.com>
Date: Fri, 6 Jul 2018 19:21:16 -0700
Subject: [PATCH 0997/1109] =?UTF-8?q?Revert=20D8683555:=20[react-native][P?=
 =?UTF-8?q?R]=20fix:=20account=20for=20`ListHeaderComponent`=20length=20wh?=
 =?UTF-8?q?en=20calculating=20offset=E2=80=A6?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Differential Revision:
D8683555

Original commit changeset: 05df7b79c16e

fbshipit-source-id: 6deb14b99fe04e67e264455ff92a5d8c1c2dd406
---
 Libraries/Lists/VirtualizedList.js | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 47b6b5f083e1..56364823f06d 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -1217,9 +1217,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
   }
 
   _selectOffset(metrics: $ReadOnly<{x: number, y: number}>): number {
-    return (
-      (!this.props.horizontal ? metrics.y : metrics.x) - this._headerLength
-    );
+    return !this.props.horizontal ? metrics.y : metrics.x;
   }
 
   _maybeCallOnEndReached() {

From b99609e9d242e5aaa2b0f14c08e8805b8903bc83 Mon Sep 17 00:00:00 2001
From: Wen-Chien Chen <wencchen@fb.com>
Date: Sun, 8 Jul 2018 00:18:31 -0700
Subject: [PATCH 0998/1109] Fix ScrollView logspew

Summary: There was an inverted expression leading to logspew. Fix this.

Reviewed By: TheSavior

Differential Revision: D8758023

fbshipit-source-id: 7a83c68db6c95f2b5db6dcc7d7780fc66321b49e
---
 Libraries/Components/ScrollView/ScrollView.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 7665527f5ad8..27dd34f49f75 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -774,7 +774,7 @@ const ScrollView = createReactClass({
       ScrollViewClass = RCTScrollView;
       ScrollContentContainerViewClass = RCTScrollContentView;
       warning(
-        this.props.snapToInterval != null || !this.props.pagingEnabled,
+        this.props.snapToInterval == null || !this.props.pagingEnabled,
         'snapToInterval is currently ignored when pagingEnabled is true.',
       );
     }

From 781f1816101507b45bb1d93a4393c07aa7b24d26 Mon Sep 17 00:00:00 2001
From: Wenting Hu <wentinghu@fb.com>
Date: Sun, 8 Jul 2018 13:06:38 -0700
Subject: [PATCH 0999/1109] Back out "[react-native][PR] Remove the deprecated
 `isIPhoneX_deprecated` constant"

Summary:
Original commit changeset: 0b0b3a2d7b80

This constant is still in use at Facebook. Its removal has been pushed to sometime in the future.

Reviewed By: mdvacca

Differential Revision: D8721213

fbshipit-source-id: d1197c96804e4d2dc96be27421e5248a2394cdac
---
 RNTester/js/SafeAreaViewExample.js | 4 ++--
 React/Modules/RCTDeviceInfo.m      | 2 +-
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/RNTester/js/SafeAreaViewExample.js b/RNTester/js/SafeAreaViewExample.js
index 927a26651a4f..be7ce97fa3b6 100644
--- a/RNTester/js/SafeAreaViewExample.js
+++ b/RNTester/js/SafeAreaViewExample.js
@@ -90,8 +90,8 @@ exports.examples = [
     title: 'isIPhoneX_deprecated Example',
     description:
       '`DeviceInfo.isIPhoneX_deprecated` returns true only on iPhone X. ' +
-      'Note: This prop is deprecated and will be removed right after June 01, 2018. ' +
-      'Please use this only for a quick and temporary solution. ' +
+      'Note: This prop is deprecated and will be removed in a future ' +
+      'release. Please use this only for a quick and temporary solution. ' +
       'Use <SafeAreaView> instead.',
     render: () => <IsIPhoneXExample />,
   },
diff --git a/React/Modules/RCTDeviceInfo.m b/React/Modules/RCTDeviceInfo.m
index 20e53d55af61..72803f3e121d 100644
--- a/React/Modules/RCTDeviceInfo.m
+++ b/React/Modules/RCTDeviceInfo.m
@@ -103,7 +103,7 @@ - (void)invalidate
   return @{
     @"Dimensions": RCTExportedDimensions(_bridge),
     // Note:
-    // This prop is deprecated and will be removed right after June 01, 2018.
+    // This prop is deprecated and will be removed in a future release.
     // Please use this only for a quick and temporary solution.
     // Use <SafeAreaView> instead.
     @"isIPhoneX_deprecated": @(RCTIsIPhoneX()),

From fc94f959625043d83830cca5db3456bd89e99536 Mon Sep 17 00:00:00 2001
From: Yan Soares Couto <yancouto@fb.com>
Date: Mon, 9 Jul 2018 03:21:05 -0700
Subject: [PATCH 1000/1109] Enable RCTDevLoadingView with another flag

Reviewed By: javache

Differential Revision: D8723591

fbshipit-source-id: 196cecd73ba0e1a1d34ec9a775cf03a25f352401
---
 React/DevSupport/RCTDevLoadingView.m | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/React/DevSupport/RCTDevLoadingView.m b/React/DevSupport/RCTDevLoadingView.m
index 6d67c9d80a6e..15480ad6a693 100644
--- a/React/DevSupport/RCTDevLoadingView.m
+++ b/React/DevSupport/RCTDevLoadingView.m
@@ -14,7 +14,7 @@
 #import "RCTModalHostViewController.h"
 #import "RCTUtils.h"
 
-#if RCT_DEV
+#if RCT_DEV | RCT_ENABLE_LOADING_VIEW
 
 static BOOL isEnabled = YES;
 

From eac34e30215d88b5fe9056f9678275b894032636 Mon Sep 17 00:00:00 2001
From: Gabe Levi <gabe@fb.com>
Date: Mon, 9 Jul 2018 08:06:58 -0700
Subject: [PATCH 1001/1109] Flow v0.76.0

Summary: No new errors in this version. Just removed a bunch of unused suppressions

Reviewed By: TheSavior

Differential Revision: D8754160

fbshipit-source-id: 2f02240b6d65edecba5d9ed603c7703462547a7f
---
 .flowconfig                                   | 2 +-
 Libraries/Components/ScrollView/ScrollView.js | 2 +-
 Libraries/Utilities/PerformanceLogger.js      | 3 ---
 local-cli/server/runServer.js                 | 2 +-
 local-cli/templates/HelloWorld/_flowconfig    | 2 +-
 package.json                                  | 2 +-
 6 files changed, 5 insertions(+), 8 deletions(-)

diff --git a/.flowconfig b/.flowconfig
index a2afa6b93199..7ba7b7ccf41d 100644
--- a/.flowconfig
+++ b/.flowconfig
@@ -97,4 +97,4 @@ untyped-import
 untyped-type-import
 
 [version]
-^0.75.0
+^0.76.0
diff --git a/Libraries/Components/ScrollView/ScrollView.js b/Libraries/Components/ScrollView/ScrollView.js
index 27dd34f49f75..9f0688e87489 100644
--- a/Libraries/Components/ScrollView/ScrollView.js
+++ b/Libraries/Components/ScrollView/ScrollView.js
@@ -394,7 +394,7 @@ export type Props = $ReadOnly<{|
    *   - `false`, deprecated, use 'never' instead
    *   - `true`, deprecated, use 'always' instead
    */
-  // $FlowFixMe Issues found when typing ScrollView
+  // $FlowFixMe(site=react_native_fb) Issues found when typing ScrollView
   keyboardShouldPersistTaps?: ?('always' | 'never' | 'handled' | false | true),
   /**
    * Called when the momentum scroll starts (scroll which occurs as the ScrollView glides to a stop).
diff --git a/Libraries/Utilities/PerformanceLogger.js b/Libraries/Utilities/PerformanceLogger.js
index 203e24125879..8bd1cc638a2b 100644
--- a/Libraries/Utilities/PerformanceLogger.js
+++ b/Libraries/Utilities/PerformanceLogger.js
@@ -13,9 +13,6 @@ const Systrace = require('Systrace');
 
 const infoLog = require('infoLog');
 const performanceNow =
-  /* $FlowFixMe(>=0.54.0 site=react_native_oss) This comment suppresses an
-   * error found when Flow v0.54 was deployed. To see the error delete this
-   * comment and run Flow. */
   global.nativeQPLTimestamp ||
   global.nativePerformanceNow ||
   require('fbjs/lib/performanceNow');
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 7dfaaed72a18..7f660bde298f 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -80,7 +80,7 @@ async function runServer(args: Args, config: ConfigT) {
   //
   // For more info: https://github.com/nodejs/node/issues/13391
   //
-  // $FlowFixMe
+  // $FlowFixMe (site=react_native_fb)
   serverInstance.keepAliveTimeout = 30000;
 }
 
diff --git a/local-cli/templates/HelloWorld/_flowconfig b/local-cli/templates/HelloWorld/_flowconfig
index 3c0adb566300..db178bd0c093 100644
--- a/local-cli/templates/HelloWorld/_flowconfig
+++ b/local-cli/templates/HelloWorld/_flowconfig
@@ -64,4 +64,4 @@ suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
 suppress_comment=\\(.\\|\n\\)*\\$FlowExpectedError
 
 [version]
-^0.75.0
+^0.76.0
diff --git a/package.json b/package.json
index ef7f978438e2..5c9be70aeb23 100644
--- a/package.json
+++ b/package.json
@@ -212,7 +212,7 @@
     "eslint-plugin-prettier": "2.6.0",
     "eslint-plugin-react": "7.8.2",
     "eslint-plugin-react-native": "^3.2.1",
-    "flow-bin": "^0.75.0",
+    "flow-bin": "^0.76.0",
     "jest": "23.2.0",
     "jest-junit": "5.1.0",
     "prettier": "1.13.6",

From abf1188de225e4b7d36ecbad316af92ca29c85c2 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rub=C3=A9n=20Norte?= <rubennorte@fb.com>
Date: Mon, 9 Jul 2018 09:13:06 -0700
Subject: [PATCH 1002/1109] Upgraded babel-eslint to v9.0.0-beta.2 with better
 support for Flow

Summary: Upgraded the library to fix an error in Babel causing wrong unused variable errors.

Differential Revision: D8765952

fbshipit-source-id: 352d1bb50ada76caed247bf9aa4521eff2d510e9
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 5c9be70aeb23..3c408150a84b 100644
--- a/package.json
+++ b/package.json
@@ -201,7 +201,7 @@
   "devDependencies": {
     "@babel/core": "7.0.0-beta.47",
     "async": "^2.4.0",
-    "babel-eslint": "8.2.1",
+    "babel-eslint": "9.0.0-beta.2",
     "babel-generator": "^6.26.0",
     "eslint": "5.0.1",
     "eslint-config-fb-strict": "22.1.0",

From 5aa040dfb780c09a6efa5d3072232dea775d432f Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Mon, 9 Jul 2018 10:50:53 -0700
Subject: [PATCH 1003/1109] added property accessibility IgnoresInvertColors to
 proptypes

Summary: Added property accessibilityIgnoresInvertColors to ViewPropTypes.

Reviewed By: PeteTheHeat

Differential Revision: D8735443

fbshipit-source-id: ac526779b7f92ceab074de75a2bf61752e7e90c6
---
 Libraries/Components/View/ViewPropTypes.js | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 0f7dea210694..5cfcd45f24b9 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -87,6 +87,7 @@ export type ViewProps = $ReadOnly<{|
   accessibilityComponentType?: AccessibilityComponentType,
   accessibilityLiveRegion?: 'none' | 'polite' | 'assertive',
   importantForAccessibility?: 'auto' | 'yes' | 'no' | 'no-hide-descendants',
+  accessibilityIgnoresInvertColors?: boolean,
   accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
   accessibilityViewIsModal?: boolean,
   accessibilityElementsHidden?: boolean,

From 0f2f0cad41f632d1dbb0c676d5edea5db62eb01c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rub=C3=A9n=20Norte?= <rubennorte@fb.com>
Date: Mon, 9 Jul 2018 12:31:17 -0700
Subject: [PATCH 1004/1109] Upgrade ESLint to 5.1.0

Summary:
This release fixes several issues. Most importantly for us:

- https://github.com/eslint/eslint/issues/10560
- https://github.com/eslint/eslint/issues/10512

Differential Revision: D8767118

fbshipit-source-id: 2048829d780b5f0f2f607114f803c8d0c3e02ca7
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 3c408150a84b..7b8fd82f628b 100644
--- a/package.json
+++ b/package.json
@@ -203,7 +203,7 @@
     "async": "^2.4.0",
     "babel-eslint": "9.0.0-beta.2",
     "babel-generator": "^6.26.0",
-    "eslint": "5.0.1",
+    "eslint": "5.1.0",
     "eslint-config-fb-strict": "22.1.0",
     "eslint-config-fbjs": "2.0.1",
     "eslint-plugin-eslint-comments": "^3.0.1",

From a69c3303474e08eb0a3b428d261bb38714db1378 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 10 Jul 2018 03:55:58 -0700
Subject: [PATCH 1005/1109] Bump metro@0.42.0

Summary:
@public
[skip-ci]

Differential Revision: D8773719

fbshipit-source-id: d05f7060a45751ed14dc5479ff1135f35a38c432
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 7b8fd82f628b..79ed118dda48 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.40.1",
-    "metro-babel-register": "^0.40.1",
-    "metro-core": "^0.40.1",
-    "metro-memory-fs": "^0.40.1",
+    "metro": "^0.42.0",
+    "metro-babel-register": "^0.42.0",
+    "metro-core": "^0.42.0",
+    "metro-memory-fs": "^0.42.0",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From 1bb2bead8bef850037c8b72209cd72a442572821 Mon Sep 17 00:00:00 2001
From: Noam Schachter <noams@fb.com>
Date: Tue, 10 Jul 2018 08:19:01 -0700
Subject: [PATCH 1006/1109] Fixing Crush on SDK 15 (ICS) on
 ReactTextInputLocalData

Summary:
We had a crush reprot from Loadstone (manual tests) for RN standalone app on ICS, see:
https://our.intern.facebook.com/intern/tasks/view_inline_attachment/?attachment_id=2296063267087587&fbid=314266832445741

Seems like we are using TextView.getMinLines and TextView.getMaxLines - both added in SDK 16, witought a propert guard. see:
https://developer.android.com/reference/android/widget/TextView#getMinLines()
https://developer.android.com/reference/android/widget/TextView#getMaxLines()

Reviewed By: shergin

Differential Revision: D8763942

fbshipit-source-id: a56a6fc3e575b8ea97ddab983561df878b2f341c
---
 .../react/views/textinput/ReactTextInputLocalData.java | 10 ++++++++--
 1 file changed, 8 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputLocalData.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputLocalData.java
index 3940e4f7c620..ce7b2725bb69 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputLocalData.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputLocalData.java
@@ -25,10 +25,16 @@ public final class ReactTextInputLocalData {
   public ReactTextInputLocalData(EditText editText) {
     mText = new SpannableStringBuilder(editText.getText());
     mTextSize = editText.getTextSize();
-    mMinLines = editText.getMinLines();
-    mMaxLines = editText.getMaxLines();
     mInputType = editText.getInputType();
 
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+      mMinLines = editText.getMinLines();
+      mMaxLines = editText.getMaxLines();
+    } else {
+      mMinLines = 1;
+      mMaxLines = 1;
+    }
+
     if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
       mBreakStrategy = editText.getBreakStrategy();
     } else {

From 1ee6396c566f038a1081796c77a1ecad6a24cef6 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 10 Jul 2018 08:50:42 -0700
Subject: [PATCH 1007/1109] Bump metro@0.42.1

Summary:
@public

[skip-ci]

Reviewed By: mjesun

Differential Revision: D8781445

fbshipit-source-id: 32f2cbfeadbd2fb763078a046b779a16359c8bbd
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 79ed118dda48..acd729198cbb 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.42.0",
-    "metro-babel-register": "^0.42.0",
-    "metro-core": "^0.42.0",
-    "metro-memory-fs": "^0.42.0",
+    "metro": "^0.42.1",
+    "metro-babel-register": "^0.42.1",
+    "metro-core": "^0.42.1",
+    "metro-memory-fs": "^0.42.1",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From ef3d8b23c35246d4e088d532c41723e06b688f1b Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Tue, 10 Jul 2018 11:14:51 -0700
Subject: [PATCH 1008/1109] Unreverting Marketplace change for Inverted Color
 Ignorance

Summary:
Un-reverted Diff D8528543

Context:
Diff itself is the exact same as the old one. There's actually nothing wrong with this diff,
it was originally reverted because of iOS compatibility issue on exposing `accessibilityIgnoresInvertcolors` API to javascript, which has now been handled and fixed in this D8599698.
This means I can now set the property `accessibilityIgnoresInvertColors`

--------------------------
Added Smart Inversion Compatibility to Marketplace on iOS so that photos don't appear inverted
Added Property to View for Ignoring Color Inversion
Applied Property to Images on marketplace.

**Note: Android doesn't support smart inversion

Reviewed By: PeteTheHeat

Differential Revision: D8737594

fbshipit-source-id: 86080d45dec773ede4d3828fcda8870f546df691
---
 Libraries/Image/ImageBackground.js | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/Libraries/Image/ImageBackground.js b/Libraries/Image/ImageBackground.js
index 7b86d9c5f529..a128880a1780 100644
--- a/Libraries/Image/ImageBackground.js
+++ b/Libraries/Image/ImageBackground.js
@@ -60,7 +60,10 @@ class ImageBackground extends React.Component<$FlowFixMeProps> {
     const {children, style, imageStyle, imageRef, ...props} = this.props;
 
     return (
-      <View style={style} ref={this._captureRef}>
+      <View
+        accessibilityIgnoresInvertColors={true}
+        style={style}
+        ref={this._captureRef}>
         <Image
           {...props}
           style={[

From c27b495a89e71ff13959eb4c34605a527514fa1e Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Tue, 10 Jul 2018 12:09:02 -0700
Subject: [PATCH 1009/1109] added accessibilityRole Prop, added functionality
 support for role on android

Summary:
Added a new property to View for Accessibility called `accessibilityRole`. This property merges functionality of existing properties: `accessibilityTraits` (iOS) and `accessibilityComponentType` (android).

Currently, nine values are supported with equivalent behavior as `accessibilityTraits` (iOS) when `accessibilityRole` is set on iOS Voiceover and Android TalkBack

```
  | 'none'
  | 'button'
  | 'link'
  | 'search'
  | 'image'
  | 'keyboardkey'
  | 'text'
  | 'adjustable'
  | 'tabbar'
```
They currently support similar behavior on talkback on Android and voice over on iOS
Does not break functionality of existing properties, but have not tested for behavior of setting both this one and the old one.

* iOS - I added a property accessibilityRoles, and basically remapped it to the same thing as accessibilityTraits. I also added in enum mappings for keyboardkey and tabbar.
* Android - Also added a property accessibilityRoles, from the Android side. For the underlying native functionality, I built a helper class that is based off of AccessibilityRolesUtil.java from the accessibility team. Biggest changes made are that I defined my own enums if needed, and also set some properties to match the functionality of iOS Accessibility Traits. I also handled the logic for switch/case statements of setting roles for the android side on this file. Also, I currently haven't localized strings for setRoleDescription, but plan to.
* Javascript - I added a view property accessibilityRoles in ViewPropTypes.

Reviewed By: blavalla

Differential Revision: D8756225

fbshipit-source-id: e03eec40cce86042551764f433e1defe7ee41b35
---
 .../Components/View/ViewAccessibility.js      |  16 +++
 Libraries/Components/View/ViewPropTypes.js    |   9 ++
 React/Views/RCTViewManager.m                  |   3 +
 .../uimanager/AccessibilityRoleUtil.java      | 121 ++++++++++++++++++
 .../react/uimanager/BaseViewManager.java      |   6 +
 5 files changed, 155 insertions(+)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java

diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index 4a9ebc172a13..a12528fad5fc 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -39,6 +39,14 @@ export type AccessibilityComponentType =
   | 'radiobutton_checked'
   | 'radiobutton_unchecked';
 
+export type AccessibilityRole =
+  | 'none'
+  | 'button'
+  | 'image'
+  | 'keyboardkey'
+  | 'text'
+  | 'tabbar';
+
 module.exports = {
   AccessibilityTraits: [
     'none',
@@ -65,4 +73,12 @@ module.exports = {
     'radiobutton_checked',
     'radiobutton_unchecked',
   ],
+  AccessibilityRoles: [
+    'none',
+    'button',
+    'image',
+    'keyboardkey',
+    'text',
+    'tabbar',
+  ],
 };
diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 5cfcd45f24b9..73a39cf255fc 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -20,11 +20,13 @@ const ViewStylePropTypes = require('ViewStylePropTypes');
 const {
   AccessibilityComponentTypes,
   AccessibilityTraits,
+  AccessibilityRoles,
 } = require('ViewAccessibility');
 
 import type {
   AccessibilityComponentType,
   AccessibilityTrait,
+  AccessibilityRole,
 } from 'ViewAccessibility';
 import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
 import type {TVViewProps} from 'TVViewPropTypes';
@@ -89,6 +91,7 @@ export type ViewProps = $ReadOnly<{|
   importantForAccessibility?: 'auto' | 'yes' | 'no' | 'no-hide-descendants',
   accessibilityIgnoresInvertColors?: boolean,
   accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
+  accessibilityRole?: AccessibilityRole,
   accessibilityViewIsModal?: boolean,
   accessibilityElementsHidden?: boolean,
   children?: ?React.Node,
@@ -139,6 +142,12 @@ module.exports = {
    */
   accessibilityComponentType: PropTypes.oneOf(AccessibilityComponentTypes),
 
+  /**
+   * Indicates to accessibility services to treat UI component like a
+   * native one. Merging accessibilityComponentType and accessibilityTraits.
+   */
+  accessibilityRole: PropTypes.oneOf(AccessibilityRoles),
+
   /**
    * Indicates to accessibility services whether the user should be notified
    * when this view changes. Works for Android API >= 19 only.
diff --git a/React/Views/RCTViewManager.m b/React/Views/RCTViewManager.m
index ede084d1a5fb..4443f525a6ab 100644
--- a/React/Views/RCTViewManager.m
+++ b/React/Views/RCTViewManager.m
@@ -33,9 +33,11 @@ @implementation RCTConvert(UIAccessibilityTraits)
   @"header": @(UIAccessibilityTraitHeader),
   @"search": @(UIAccessibilityTraitSearchField),
   @"image": @(UIAccessibilityTraitImage),
+  @"tabbar": @(UIAccessibilityTraitTabBar),
   @"selected": @(UIAccessibilityTraitSelected),
   @"plays": @(UIAccessibilityTraitPlaysSound),
   @"key": @(UIAccessibilityTraitKeyboardKey),
+  @"keyboardkey": @(UIAccessibilityTraitKeyboardKey),
   @"text": @(UIAccessibilityTraitStaticText),
   @"summary": @(UIAccessibilityTraitSummaryElement),
   @"disabled": @(UIAccessibilityTraitNotEnabled),
@@ -110,6 +112,7 @@ - (RCTShadowView *)shadowView
 RCT_REMAP_VIEW_PROPERTY(accessibilityActions, reactAccessibilityElement.accessibilityActions, NSString)
 RCT_REMAP_VIEW_PROPERTY(accessibilityLabel, reactAccessibilityElement.accessibilityLabel, NSString)
 RCT_REMAP_VIEW_PROPERTY(accessibilityTraits, reactAccessibilityElement.accessibilityTraits, UIAccessibilityTraits)
+RCT_REMAP_VIEW_PROPERTY(accessibilityRole, reactAccessibilityElement.accessibilityTraits, UIAccessibilityTraits)
 RCT_REMAP_VIEW_PROPERTY(accessibilityViewIsModal, reactAccessibilityElement.accessibilityViewIsModal, BOOL)
 RCT_REMAP_VIEW_PROPERTY(accessibilityElementsHidden, reactAccessibilityElement.accessibilityElementsHidden, BOOL)
 RCT_REMAP_VIEW_PROPERTY(accessibilityIgnoresInvertColors, reactAccessibilityElement.shouldAccessibilityIgnoresInvertColors, BOOL)
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
new file mode 100644
index 000000000000..f063925a23b8
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
@@ -0,0 +1,121 @@
+// Copyright (c) 2004-present, Facebook, Inc.
+
+// This source code is licensed under the MIT license found in the
+// LICENSE file in the root directory of this source tree.
+
+package com.facebook.react.uimanager;
+
+import android.annotation.TargetApi;
+import android.os.Build;
+import android.support.v4.view.AccessibilityDelegateCompat;
+import android.support.v4.view.ViewCompat;
+import android.support.v4.view.accessibility.AccessibilityNodeInfoCompat;
+import android.view.View;
+import android.view.accessibility.AccessibilityNodeInfo;
+import javax.annotation.Nullable;
+
+/**
+ * Utility class that handles the addition of a "role" for accessibility to either a View or
+ * AccessibilityNodeInfo.
+ */
+
+public class AccessibilityRoleUtil {
+
+  /**
+   * These roles are defined by Google's TalkBack screen reader, and this list should be kept up to
+   * date with their implementation. Details can be seen in their source code here:
+   *
+   * <p>https://github.com/google/talkback/blob/master/utils/src/main/java/Role.java
+   */
+
+  public enum AccessibilityRole {
+    NONE(null),
+    BUTTON("android.widget.Button"),
+    IMAGE("android.widget.ImageView"),
+    KEYBOARD_KEY("android.inputmethodservice.Keyboard$Key"),
+    TEXT("android.widget.ViewGroup"),
+    TAB_BAR("android.widget.TabWidget");
+
+    @Nullable private final String mValue;
+
+    AccessibilityRole(String type) {
+      mValue = type;
+    }
+
+    @Nullable
+    public String getValue() {
+      return mValue;
+    }
+
+    public static AccessibilityRole fromValue(String value) {
+      for (AccessibilityRole role : AccessibilityRole.values()) {
+        if (role.getValue() != null && role.getValue().equals(value)) {
+          return role;
+        }
+      }
+      return AccessibilityRole.NONE;
+    }
+  }
+
+  private AccessibilityRoleUtil() {
+    // No instances
+  }
+
+  public static void setRole(View view, final AccessibilityRole role) {
+    // if a view already has an accessibility delegate, replacing it could cause problems,
+    // so leave it alone.
+    if (!ViewCompat.hasAccessibilityDelegate(view)) {
+      ViewCompat.setAccessibilityDelegate(
+        view,
+        new AccessibilityDelegateCompat() {
+          @Override
+          public void onInitializeAccessibilityNodeInfo(
+            View host, AccessibilityNodeInfoCompat info) {
+            super.onInitializeAccessibilityNodeInfo(host, info);
+            setRole(info, role);
+          }
+        });
+    }
+  }
+
+  public static void setRole(AccessibilityNodeInfoCompat nodeInfo, final AccessibilityRole role) {
+    nodeInfo.setClassName(role.getValue());
+  }
+
+  /**
+   * Variables and methods for setting accessibilityRole on view properties.
+   */
+  private static final String NONE = "none";
+  private static final String BUTTON = "button";
+  private static final String IMAGE = "image";
+  private static final String KEYBOARDKEY = "keyboardkey";
+  private static final String TEXT = "text";
+  private static final String TABBAR = "tabbar";
+
+  public static void updateAccessibilityRole(View view, String role) {
+    if (role == null) {
+      view.setAccessibilityDelegate(null);
+    }
+    switch (role) {
+      case NONE:
+        break;
+      case BUTTON:
+        setRole(view, AccessibilityRoleUtil.AccessibilityRole.BUTTON);
+        break;
+      case IMAGE:
+        setRole(view, AccessibilityRoleUtil.AccessibilityRole.IMAGE);
+        break;
+      case KEYBOARDKEY:
+        setRole(view, AccessibilityRoleUtil.AccessibilityRole.KEYBOARD_KEY);
+        break;
+      case TEXT:
+        setRole(view, AccessibilityRoleUtil.AccessibilityRole.TEXT);
+        break;
+      case TABBAR:
+        setRole(view, AccessibilityRoleUtil.AccessibilityRole.TAB_BAR);
+        break;
+      default:
+        view.setAccessibilityDelegate(null);
+    }
+  }
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
index 0fb71f1aa1a6..5b4c312ea581 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
@@ -29,6 +29,7 @@ public abstract class BaseViewManager<T extends View, C extends LayoutShadowNode
   private static final String PROP_ACCESSIBILITY_LABEL = "accessibilityLabel";
   private static final String PROP_ACCESSIBILITY_COMPONENT_TYPE = "accessibilityComponentType";
   private static final String PROP_ACCESSIBILITY_LIVE_REGION = "accessibilityLiveRegion";
+  private static final String PROP_ACCESSIBILITY_ROLE = "accessibilityRole";
   private static final String PROP_IMPORTANT_FOR_ACCESSIBILITY = "importantForAccessibility";
 
   // DEPRECATED
@@ -117,6 +118,11 @@ public void setAccessibilityComponentType(T view, String accessibilityComponentT
     AccessibilityHelper.updateAccessibilityComponentType(view, accessibilityComponentType);
   }
 
+  @ReactProp(name = PROP_ACCESSIBILITY_ROLE)
+  public void setAccessibilityRole(T view, String accessibilityRole) {
+    AccessibilityRoleUtil.updateAccessibilityRole(view, accessibilityRole);
+  }
+
   @ReactProp(name = PROP_IMPORTANT_FOR_ACCESSIBILITY)
   public void setImportantForAccessibility(T view, String importantForAccessibility) {
     if (importantForAccessibility == null || importantForAccessibility.equals("auto")) {

From 7abbd703d4188b564bdc0f9ad82f02312ce180cb Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Wed, 11 Jul 2018 04:09:39 -0700
Subject: [PATCH 1010/1109] Lint / reformat `YGJNI.cpp`

Summary:
Run clangformat on `YGJNI.cpp`

@public

Reviewed By: priteshrnandgaonkar

Differential Revision: D8785660

fbshipit-source-id: 9748a5297e7b55e897de0280a79c2ea6ae1c1298
---
 .../jni/first-party/yogajni/jni/YGJNI.cpp     | 393 +++++++++++-------
 1 file changed, 233 insertions(+), 160 deletions(-)

diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
index 5649ef7ea70e..1d6f464cc88d 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
@@ -33,13 +33,17 @@ struct YGConfigContext {
   }
 };
 
-static inline weak_ref<JYogaNode> *YGNodeJobject(YGNodeRef node) {
+static inline weak_ref<JYogaNode>* YGNodeJobject(YGNodeRef node) {
   return reinterpret_cast<weak_ref<JYogaNode>*>(node->getContext());
 }
 
-static void YGTransferLayoutDirection(YGNodeRef node, alias_ref<jobject> javaNode) {
-  static auto layoutDirectionField = javaNode->getClass()->getField<jint>("mLayoutDirection");
-  javaNode->setFieldValue(layoutDirectionField, static_cast<jint>(YGNodeLayoutGetDirection(node)));
+static void YGTransferLayoutDirection(
+    YGNodeRef node,
+    alias_ref<jobject> javaNode) {
+  static auto layoutDirectionField =
+      javaNode->getClass()->getField<jint>("mLayoutDirection");
+  javaNode->setFieldValue(
+      layoutDirectionField, static_cast<jint>(YGNodeLayoutGetDirection(node)));
 }
 
 static void YGTransferLayoutOutputsRecursive(YGNodeRef root) {
@@ -50,23 +54,37 @@ static void YGTransferLayoutOutputsRecursive(YGNodeRef root) {
       static auto leftField = obj->getClass()->getField<jfloat>("mLeft");
       static auto topField = obj->getClass()->getField<jfloat>("mTop");
 
-      static auto marginLeftField = obj->getClass()->getField<jfloat>("mMarginLeft");
-      static auto marginTopField = obj->getClass()->getField<jfloat>("mMarginTop");
-      static auto marginRightField = obj->getClass()->getField<jfloat>("mMarginRight");
-      static auto marginBottomField = obj->getClass()->getField<jfloat>("mMarginBottom");
-
-      static auto paddingLeftField = obj->getClass()->getField<jfloat>("mPaddingLeft");
-      static auto paddingTopField = obj->getClass()->getField<jfloat>("mPaddingTop");
-      static auto paddingRightField = obj->getClass()->getField<jfloat>("mPaddingRight");
-      static auto paddingBottomField = obj->getClass()->getField<jfloat>("mPaddingBottom");
-
-      static auto borderLeftField = obj->getClass()->getField<jfloat>("mBorderLeft");
-      static auto borderTopField = obj->getClass()->getField<jfloat>("mBorderTop");
-      static auto borderRightField = obj->getClass()->getField<jfloat>("mBorderRight");
-      static auto borderBottomField = obj->getClass()->getField<jfloat>("mBorderBottom");
-
-      static auto edgeSetFlagField = obj->getClass()->getField<jint>("mEdgeSetFlag");
-      static auto hasNewLayoutField = obj->getClass()->getField<jboolean>("mHasNewLayout");
+      static auto marginLeftField =
+          obj->getClass()->getField<jfloat>("mMarginLeft");
+      static auto marginTopField =
+          obj->getClass()->getField<jfloat>("mMarginTop");
+      static auto marginRightField =
+          obj->getClass()->getField<jfloat>("mMarginRight");
+      static auto marginBottomField =
+          obj->getClass()->getField<jfloat>("mMarginBottom");
+
+      static auto paddingLeftField =
+          obj->getClass()->getField<jfloat>("mPaddingLeft");
+      static auto paddingTopField =
+          obj->getClass()->getField<jfloat>("mPaddingTop");
+      static auto paddingRightField =
+          obj->getClass()->getField<jfloat>("mPaddingRight");
+      static auto paddingBottomField =
+          obj->getClass()->getField<jfloat>("mPaddingBottom");
+
+      static auto borderLeftField =
+          obj->getClass()->getField<jfloat>("mBorderLeft");
+      static auto borderTopField =
+          obj->getClass()->getField<jfloat>("mBorderTop");
+      static auto borderRightField =
+          obj->getClass()->getField<jfloat>("mBorderRight");
+      static auto borderBottomField =
+          obj->getClass()->getField<jfloat>("mBorderBottom");
+
+      static auto edgeSetFlagField =
+          obj->getClass()->getField<jint>("mEdgeSetFlag");
+      static auto hasNewLayoutField =
+          obj->getClass()->getField<jboolean>("mHasNewLayout");
       static auto doesLegacyStretchBehaviour =
           obj->getClass()->getField<jboolean>(
               "mDoesLegacyStretchFlagAffectsLayout");
@@ -76,7 +94,7 @@ static void YGTransferLayoutOutputsRecursive(YGNodeRef root) {
       const int PADDING = 2;
       const int BORDER = 4;
 
-      int hasEdgeSetFlag = (int) obj->getFieldValue(edgeSetFlagField);
+      int hasEdgeSetFlag = (int)obj->getFieldValue(edgeSetFlagField);
 
       obj->setFieldValue(widthField, YGNodeLayoutGetWidth(root));
       obj->setFieldValue(heightField, YGNodeLayoutGetHeight(root));
@@ -98,17 +116,25 @@ static void YGTransferLayoutOutputsRecursive(YGNodeRef root) {
       }
 
       if ((hasEdgeSetFlag & PADDING) == PADDING) {
-        obj->setFieldValue(paddingLeftField, YGNodeLayoutGetPadding(root, YGEdgeLeft));
-        obj->setFieldValue(paddingTopField, YGNodeLayoutGetPadding(root, YGEdgeTop));
-        obj->setFieldValue(paddingRightField, YGNodeLayoutGetPadding(root, YGEdgeRight));
-        obj->setFieldValue(paddingBottomField, YGNodeLayoutGetPadding(root, YGEdgeBottom));
+        obj->setFieldValue(
+            paddingLeftField, YGNodeLayoutGetPadding(root, YGEdgeLeft));
+        obj->setFieldValue(
+            paddingTopField, YGNodeLayoutGetPadding(root, YGEdgeTop));
+        obj->setFieldValue(
+            paddingRightField, YGNodeLayoutGetPadding(root, YGEdgeRight));
+        obj->setFieldValue(
+            paddingBottomField, YGNodeLayoutGetPadding(root, YGEdgeBottom));
       }
 
       if ((hasEdgeSetFlag & BORDER) == BORDER) {
-        obj->setFieldValue(borderLeftField, YGNodeLayoutGetBorder(root, YGEdgeLeft));
-        obj->setFieldValue(borderTopField, YGNodeLayoutGetBorder(root, YGEdgeTop));
-        obj->setFieldValue(borderRightField, YGNodeLayoutGetBorder(root, YGEdgeRight));
-        obj->setFieldValue(borderBottomField, YGNodeLayoutGetBorder(root, YGEdgeBottom));
+        obj->setFieldValue(
+            borderLeftField, YGNodeLayoutGetBorder(root, YGEdgeLeft));
+        obj->setFieldValue(
+            borderTopField, YGNodeLayoutGetBorder(root, YGEdgeTop));
+        obj->setFieldValue(
+            borderRightField, YGNodeLayoutGetBorder(root, YGEdgeRight));
+        obj->setFieldValue(
+            borderBottomField, YGNodeLayoutGetBorder(root, YGEdgeBottom));
       }
 
       obj->setFieldValue<jboolean>(hasNewLayoutField, true);
@@ -119,7 +145,10 @@ static void YGTransferLayoutOutputsRecursive(YGNodeRef root) {
         YGTransferLayoutOutputsRecursive(YGNodeGetChild(root, i));
       }
     } else {
-      YGLog(root, YGLogLevelError, "Java YGNode was GCed during layout calculation\n");
+      YGLog(
+          root,
+          YGLogLevelError,
+          "Java YGNode was GCed during layout calculation\n");
     }
   }
 }
@@ -128,14 +157,18 @@ static void YGPrint(YGNodeRef node) {
   if (auto obj = YGNodeJobject(node)->lockLocal()) {
     cout << obj->toString() << endl;
   } else {
-    YGLog(node, YGLogLevelError, "Java YGNode was GCed during layout calculation\n");
+    YGLog(
+        node,
+        YGLogLevelError,
+        "Java YGNode was GCed during layout calculation\n");
   }
 }
 
 static float YGJNIBaselineFunc(YGNodeRef node, float width, float height) {
   if (auto obj = YGNodeJobject(node)->lockLocal()) {
-    static auto baselineFunc = findClassStatic("com/facebook/yoga/YogaNode")
-                                   ->getMethod<jfloat(jfloat, jfloat)>("baseline");
+    static auto baselineFunc =
+        findClassStatic("com/facebook/yoga/YogaNode")
+            ->getMethod<jfloat(jfloat, jfloat)>("baseline");
     return baselineFunc(obj, width, height);
   } else {
     return height;
@@ -150,20 +183,17 @@ static inline YGConfigRef _jlong2YGConfigRef(jlong addr) {
   return reinterpret_cast<YGConfigRef>(static_cast<intptr_t>(addr));
 }
 
-static YGNodeRef YGJNIOnNodeClonedFunc(
-    YGNodeRef oldNode,
-    YGNodeRef owner,
-    int childIndex) {
+static YGNodeRef
+YGJNIOnNodeClonedFunc(YGNodeRef oldNode, YGNodeRef owner, int childIndex) {
   auto config = oldNode->getConfig();
   if (!config) {
     return nullptr;
   }
 
-  static auto onNodeClonedFunc = findClassStatic("com/facebook/yoga/YogaConfig")
-                                     ->getMethod<alias_ref<JYogaNode>(
-                                         local_ref<JYogaNode>,
-                                         local_ref<JYogaNode>,
-                                         jint)>("cloneNode");
+  static auto onNodeClonedFunc =
+      findClassStatic("com/facebook/yoga/YogaConfig")
+          ->getMethod<alias_ref<JYogaNode>(
+              local_ref<JYogaNode>, local_ref<JYogaNode>, jint)>("cloneNode");
 
   auto context = reinterpret_cast<YGConfigContext*>(YGConfigGetContext(config));
   auto javaConfig = context->config;
@@ -174,15 +204,12 @@ static YGNodeRef YGJNIOnNodeClonedFunc(
       YGNodeJobject(owner)->lockLocal(),
       childIndex);
 
-  static auto replaceChild = findClassStatic("com/facebook/yoga/YogaNode")
-                                     ->getMethod<jlong(
-                                         local_ref<JYogaNode>,
-                                         jint)>("replaceChild");
+  static auto replaceChild =
+      findClassStatic("com/facebook/yoga/YogaNode")
+          ->getMethod<jlong(local_ref<JYogaNode>, jint)>("replaceChild");
 
-  jlong newNodeNativePointer = replaceChild(
-      YGNodeJobject(owner)->lockLocal(),
-      newNode,
-      childIndex);
+  jlong newNodeNativePointer =
+      replaceChild(YGNodeJobject(owner)->lockLocal(), newNode, childIndex);
 
   return _jlong2YGNodeRef(newNodeNativePointer);
 }
@@ -194,24 +221,30 @@ static YGSize YGJNIMeasureFunc(
     float height,
     YGMeasureMode heightMode) {
   if (auto obj = YGNodeJobject(node)->lockLocal()) {
-    static auto measureFunc = findClassStatic("com/facebook/yoga/YogaNode")
-                                  ->getMethod<jlong(jfloat, jint, jfloat, jint)>("measure");
+    static auto measureFunc =
+        findClassStatic("com/facebook/yoga/YogaNode")
+            ->getMethod<jlong(jfloat, jint, jfloat, jint)>("measure");
 
     YGTransferLayoutDirection(node, obj);
-    const auto measureResult = measureFunc(obj, width, widthMode, height, heightMode);
+    const auto measureResult =
+        measureFunc(obj, width, widthMode, height, heightMode);
 
-    static_assert(sizeof(measureResult) == 8,
-                  "Expected measureResult to be 8 bytes, or two 32 bit ints");
+    static_assert(
+        sizeof(measureResult) == 8,
+        "Expected measureResult to be 8 bytes, or two 32 bit ints");
 
     int32_t wBits = 0xFFFFFFFF & (measureResult >> 32);
     int32_t hBits = 0xFFFFFFFF & measureResult;
 
-    const float *measuredWidth = reinterpret_cast<float *>(&wBits);
-    const float *measuredHeight = reinterpret_cast<float *>(&hBits);
+    const float* measuredWidth = reinterpret_cast<float*>(&wBits);
+    const float* measuredHeight = reinterpret_cast<float*>(&hBits);
 
     return YGSize{*measuredWidth, *measuredHeight};
   } else {
-    YGLog(node, YGLogLevelError, "Java YGNode was GCed during layout calculation\n");
+    YGLog(
+        node,
+        YGLogLevelError,
+        "Java YGNode was GCed during layout calculation\n");
     return YGSize{
         widthMode == YGMeasureModeUndefined ? 0 : width,
         heightMode == YGMeasureModeUndefined ? 0 : height,
@@ -223,24 +256,28 @@ struct JYogaLogLevel : public JavaClass<JYogaLogLevel> {
   static constexpr auto kJavaDescriptor = "Lcom/facebook/yoga/YogaLogLevel;";
 };
 
-static int YGJNILogFunc(const YGConfigRef config,
-                        const YGNodeRef node,
-                        YGLogLevel level,
-                        const char *format,
-                        va_list args) {
+static int YGJNILogFunc(
+    const YGConfigRef config,
+    const YGNodeRef node,
+    YGLogLevel level,
+    const char* format,
+    va_list args) {
   int result = vsnprintf(NULL, 0, format, args);
   std::vector<char> buffer(1 + result);
   vsnprintf(buffer.data(), buffer.size(), format, args);
 
   static auto logFunc =
       findClassStatic("com/facebook/yoga/YogaLogger")
-          ->getMethod<void(local_ref<JYogaNode>, local_ref<JYogaLogLevel>, jstring)>("log");
+          ->getMethod<void(
+              local_ref<JYogaNode>, local_ref<JYogaLogLevel>, jstring)>("log");
 
   static auto logLevelFromInt =
-      JYogaLogLevel::javaClassStatic()->getStaticMethod<JYogaLogLevel::javaobject(jint)>("fromInt");
+      JYogaLogLevel::javaClassStatic()
+          ->getStaticMethod<JYogaLogLevel::javaobject(jint)>("fromInt");
 
   if (auto obj = YGNodeJobject(node)->lockLocal()) {
-    auto jlogger = reinterpret_cast<global_ref<jobject> *>(YGConfigGetContext(config));
+    auto jlogger =
+        reinterpret_cast<global_ref<jobject>*>(YGConfigGetContext(config));
     logFunc(
         jlogger->get(),
         obj,
@@ -309,13 +346,19 @@ void jni_YGNodeReset(alias_ref<jobject> thiz, jlong nativePointer) {
 
 void jni_YGNodePrint(alias_ref<jobject> thiz, jlong nativePointer) {
   const YGNodeRef node = _jlong2YGNodeRef(nativePointer);
-  YGNodePrint(node,
-              (YGPrintOptions)(YGPrintOptionsStyle | YGPrintOptionsLayout |
-                               YGPrintOptionsChildren));
+  YGNodePrint(
+      node,
+      (YGPrintOptions)(
+          YGPrintOptionsStyle | YGPrintOptionsLayout | YGPrintOptionsChildren));
 }
 
-void jni_YGNodeInsertChild(alias_ref<jobject>, jlong nativePointer, jlong childPointer, jint index) {
-  YGNodeInsertChild(_jlong2YGNodeRef(nativePointer), _jlong2YGNodeRef(childPointer), index);
+void jni_YGNodeInsertChild(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jlong childPointer,
+    jint index) {
+  YGNodeInsertChild(
+      _jlong2YGNodeRef(nativePointer), _jlong2YGNodeRef(childPointer), index);
 }
 
 void jni_YGNodeInsertSharedChild(
@@ -327,19 +370,25 @@ void jni_YGNodeInsertSharedChild(
       _jlong2YGNodeRef(nativePointer), _jlong2YGNodeRef(childPointer), index);
 }
 
-void jni_YGNodeRemoveChild(alias_ref<jobject>, jlong nativePointer, jlong childPointer) {
-  YGNodeRemoveChild(_jlong2YGNodeRef(nativePointer), _jlong2YGNodeRef(childPointer));
+void jni_YGNodeRemoveChild(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jlong childPointer) {
+  YGNodeRemoveChild(
+      _jlong2YGNodeRef(nativePointer), _jlong2YGNodeRef(childPointer));
 }
 
-void jni_YGNodeCalculateLayout(alias_ref<jobject>,
-                               jlong nativePointer,
-                               jfloat width,
-                               jfloat height) {
+void jni_YGNodeCalculateLayout(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jfloat width,
+    jfloat height) {
   const YGNodeRef root = _jlong2YGNodeRef(nativePointer);
-  YGNodeCalculateLayout(root,
-                        static_cast<float>(width),
-                        static_cast<float>(height),
-                        YGNodeStyleGetDirection(_jlong2YGNodeRef(nativePointer)));
+  YGNodeCalculateLayout(
+      root,
+      static_cast<float>(width),
+      static_cast<float>(height),
+      YGNodeStyleGetDirection(_jlong2YGNodeRef(nativePointer)));
   YGTransferLayoutOutputsRecursive(root);
 }
 
@@ -357,20 +406,28 @@ jboolean jni_YGNodeIsDirty(alias_ref<jobject>, jlong nativePointer) {
   return (jboolean)_jlong2YGNodeRef(nativePointer)->isDirty();
 }
 
-void jni_YGNodeSetHasMeasureFunc(alias_ref<jobject>, jlong nativePointer, jboolean hasMeasureFunc) {
+void jni_YGNodeSetHasMeasureFunc(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jboolean hasMeasureFunc) {
   _jlong2YGNodeRef(nativePointer)
       ->setMeasureFunc(hasMeasureFunc ? YGJNIMeasureFunc : nullptr);
 }
 
-void jni_YGNodeSetHasBaselineFunc(alias_ref<jobject>,
-                                  jlong nativePointer,
-                                  jboolean hasBaselineFunc) {
+void jni_YGNodeSetHasBaselineFunc(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jboolean hasBaselineFunc) {
   _jlong2YGNodeRef(nativePointer)
       ->setBaseLineFunc(hasBaselineFunc ? YGJNIBaselineFunc : nullptr);
 }
 
-void jni_YGNodeCopyStyle(alias_ref<jobject>, jlong dstNativePointer, jlong srcNativePointer) {
-  YGNodeCopyStyle(_jlong2YGNodeRef(dstNativePointer), _jlong2YGNodeRef(srcNativePointer));
+void jni_YGNodeCopyStyle(
+    alias_ref<jobject>,
+    jlong dstNativePointer,
+    jlong srcNativePointer) {
+  YGNodeCopyStyle(
+      _jlong2YGNodeRef(dstNativePointer), _jlong2YGNodeRef(srcNativePointer));
 }
 
 struct JYogaValue : public JavaClass<JYogaValue> {
@@ -392,67 +449,76 @@ struct JYogaValue : public JavaClass<JYogaValue> {
         _jlong2YGNodeRef(nativePointer), static_cast<type>(value));            \
   }
 
-#define YG_NODE_JNI_STYLE_UNIT_PROP(name)                                                         \
-  local_ref<jobject> jni_YGNodeStyleGet##name(alias_ref<jobject>, jlong nativePointer) {          \
-    return JYogaValue::create(YGNodeStyleGet##name(_jlong2YGNodeRef(nativePointer)));             \
-  }                                                                                               \
-                                                                                                  \
-  void jni_YGNodeStyleSet##name(alias_ref<jobject>, jlong nativePointer, jfloat value) {          \
-    YGNodeStyleSet##name(_jlong2YGNodeRef(nativePointer), static_cast<float>(value));             \
-  }                                                                                               \
-                                                                                                  \
-  void jni_YGNodeStyleSet##name##Percent(alias_ref<jobject>, jlong nativePointer, jfloat value) { \
-    YGNodeStyleSet##name##Percent(_jlong2YGNodeRef(nativePointer), static_cast<float>(value));    \
+#define YG_NODE_JNI_STYLE_UNIT_PROP(name)                            \
+  local_ref<jobject> jni_YGNodeStyleGet##name(                       \
+      alias_ref<jobject>, jlong nativePointer) {                     \
+    return JYogaValue::create(                                       \
+        YGNodeStyleGet##name(_jlong2YGNodeRef(nativePointer)));      \
+  }                                                                  \
+                                                                     \
+  void jni_YGNodeStyleSet##name(                                     \
+      alias_ref<jobject>, jlong nativePointer, jfloat value) {       \
+    YGNodeStyleSet##name(                                            \
+        _jlong2YGNodeRef(nativePointer), static_cast<float>(value)); \
+  }                                                                  \
+                                                                     \
+  void jni_YGNodeStyleSet##name##Percent(                            \
+      alias_ref<jobject>, jlong nativePointer, jfloat value) {       \
+    YGNodeStyleSet##name##Percent(                                   \
+        _jlong2YGNodeRef(nativePointer), static_cast<float>(value)); \
   }
 
-#define YG_NODE_JNI_STYLE_UNIT_PROP_AUTO(name)                                   \
-  YG_NODE_JNI_STYLE_UNIT_PROP(name)                                              \
-  void jni_YGNodeStyleSet##name##Auto(alias_ref<jobject>, jlong nativePointer) { \
-    YGNodeStyleSet##name##Auto(_jlong2YGNodeRef(nativePointer));                 \
+#define YG_NODE_JNI_STYLE_UNIT_PROP_AUTO(name)                   \
+  YG_NODE_JNI_STYLE_UNIT_PROP(name)                              \
+  void jni_YGNodeStyleSet##name##Auto(                           \
+      alias_ref<jobject>, jlong nativePointer) {                 \
+    YGNodeStyleSet##name##Auto(_jlong2YGNodeRef(nativePointer)); \
   }
 
-#define YG_NODE_JNI_STYLE_EDGE_PROP(javatype, type, name)                                 \
-  javatype jni_YGNodeStyleGet##name(alias_ref<jobject>, jlong nativePointer, jint edge) { \
-    return (javatype) YGNodeStyleGet##name(_jlong2YGNodeRef(nativePointer),               \
-                                           static_cast<YGEdge>(edge));                    \
-  }                                                                                       \
-                                                                                          \
-  void jni_YGNodeStyleSet##name(alias_ref<jobject>,                                       \
-                                jlong nativePointer,                                      \
-                                jint edge,                                                \
-                                javatype value) {                                         \
-    YGNodeStyleSet##name(_jlong2YGNodeRef(nativePointer),                                 \
-                         static_cast<YGEdge>(edge),                                       \
-                         static_cast<type>(value));                                       \
+#define YG_NODE_JNI_STYLE_EDGE_PROP(javatype, type, name)                   \
+  javatype jni_YGNodeStyleGet##name(                                        \
+      alias_ref<jobject>, jlong nativePointer, jint edge) {                 \
+    return (javatype)YGNodeStyleGet##name(                                  \
+        _jlong2YGNodeRef(nativePointer), static_cast<YGEdge>(edge));        \
+  }                                                                         \
+                                                                            \
+  void jni_YGNodeStyleSet##name(                                            \
+      alias_ref<jobject>, jlong nativePointer, jint edge, javatype value) { \
+    YGNodeStyleSet##name(                                                   \
+        _jlong2YGNodeRef(nativePointer),                                    \
+        static_cast<YGEdge>(edge),                                          \
+        static_cast<type>(value));                                          \
   }
 
-#define YG_NODE_JNI_STYLE_EDGE_UNIT_PROP(name)                                                      \
-  local_ref<jobject> jni_YGNodeStyleGet##name(alias_ref<jobject>,                                   \
-                                              jlong nativePointer,                                  \
-                                              jint edge) {                                          \
-    return JYogaValue::create(                                                                      \
-        YGNodeStyleGet##name(_jlong2YGNodeRef(nativePointer), static_cast<YGEdge>(edge)));          \
-  }                                                                                                 \
-                                                                                                    \
-  void jni_YGNodeStyleSet##name(alias_ref<jobject>, jlong nativePointer, jint edge, jfloat value) { \
-    YGNodeStyleSet##name(_jlong2YGNodeRef(nativePointer),                                           \
-                         static_cast<YGEdge>(edge),                                                 \
-                         static_cast<float>(value));                                                \
-  }                                                                                                 \
-                                                                                                    \
-  void jni_YGNodeStyleSet##name##Percent(alias_ref<jobject>,                                        \
-                                         jlong nativePointer,                                       \
-                                         jint edge,                                                 \
-                                         jfloat value) {                                            \
-    YGNodeStyleSet##name##Percent(_jlong2YGNodeRef(nativePointer),                                  \
-                                  static_cast<YGEdge>(edge),                                        \
-                                  static_cast<float>(value));                                       \
+#define YG_NODE_JNI_STYLE_EDGE_UNIT_PROP(name)                            \
+  local_ref<jobject> jni_YGNodeStyleGet##name(                            \
+      alias_ref<jobject>, jlong nativePointer, jint edge) {               \
+    return JYogaValue::create(YGNodeStyleGet##name(                       \
+        _jlong2YGNodeRef(nativePointer), static_cast<YGEdge>(edge)));     \
+  }                                                                       \
+                                                                          \
+  void jni_YGNodeStyleSet##name(                                          \
+      alias_ref<jobject>, jlong nativePointer, jint edge, jfloat value) { \
+    YGNodeStyleSet##name(                                                 \
+        _jlong2YGNodeRef(nativePointer),                                  \
+        static_cast<YGEdge>(edge),                                        \
+        static_cast<float>(value));                                       \
+  }                                                                       \
+                                                                          \
+  void jni_YGNodeStyleSet##name##Percent(                                 \
+      alias_ref<jobject>, jlong nativePointer, jint edge, jfloat value) { \
+    YGNodeStyleSet##name##Percent(                                        \
+        _jlong2YGNodeRef(nativePointer),                                  \
+        static_cast<YGEdge>(edge),                                        \
+        static_cast<float>(value));                                       \
   }
 
-#define YG_NODE_JNI_STYLE_EDGE_UNIT_PROP_AUTO(name)                                         \
-  YG_NODE_JNI_STYLE_EDGE_UNIT_PROP(name)                                                    \
-  void jni_YGNodeStyleSet##name##Auto(alias_ref<jobject>, jlong nativePointer, jint edge) { \
-    YGNodeStyleSet##name##Auto(_jlong2YGNodeRef(nativePointer), static_cast<YGEdge>(edge)); \
+#define YG_NODE_JNI_STYLE_EDGE_UNIT_PROP_AUTO(name)                  \
+  YG_NODE_JNI_STYLE_EDGE_UNIT_PROP(name)                             \
+  void jni_YGNodeStyleSet##name##Auto(                               \
+      alias_ref<jobject>, jlong nativePointer, jint edge) {          \
+    YGNodeStyleSet##name##Auto(                                      \
+        _jlong2YGNodeRef(nativePointer), static_cast<YGEdge>(edge)); \
   }
 
 YG_NODE_JNI_STYLE_PROP(jint, YGDirection, Direction);
@@ -466,8 +532,12 @@ YG_NODE_JNI_STYLE_PROP(jint, YGWrap, FlexWrap);
 YG_NODE_JNI_STYLE_PROP(jint, YGOverflow, Overflow);
 YG_NODE_JNI_STYLE_PROP(jint, YGDisplay, Display);
 
-void jni_YGNodeStyleSetFlex(alias_ref<jobject>, jlong nativePointer, jfloat value) {
-  YGNodeStyleSetFlex(_jlong2YGNodeRef(nativePointer), static_cast<float>(value));
+void jni_YGNodeStyleSetFlex(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jfloat value) {
+  YGNodeStyleSetFlex(
+      _jlong2YGNodeRef(nativePointer), static_cast<float>(value));
 }
 YG_NODE_JNI_STYLE_PROP(jfloat, float, FlexGrow);
 YG_NODE_JNI_STYLE_PROP(jfloat, float, FlexShrink);
@@ -501,14 +571,14 @@ void jni_YGConfigFree(alias_ref<jobject>, jlong nativePointer) {
   YGConfigFree(config);
 }
 
-void jni_YGConfigSetExperimentalFeatureEnabled(alias_ref<jobject>,
-                                               jlong nativePointer,
-                                               jint feature,
-                                               jboolean enabled) {
+void jni_YGConfigSetExperimentalFeatureEnabled(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jint feature,
+    jboolean enabled) {
   const YGConfigRef config = _jlong2YGConfigRef(nativePointer);
-  YGConfigSetExperimentalFeatureEnabled(config,
-                                        static_cast<YGExperimentalFeature>(feature),
-                                        enabled);
+  YGConfigSetExperimentalFeatureEnabled(
+      config, static_cast<YGExperimentalFeature>(feature), enabled);
 }
 
 void jni_YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
@@ -519,23 +589,26 @@ void jni_YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
   YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(config, enabled);
 }
 
-void jni_YGConfigSetUseWebDefaults(alias_ref<jobject>,
-                                   jlong nativePointer,
-                                   jboolean useWebDefaults) {
+void jni_YGConfigSetUseWebDefaults(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jboolean useWebDefaults) {
   const YGConfigRef config = _jlong2YGConfigRef(nativePointer);
   YGConfigSetUseWebDefaults(config, useWebDefaults);
 }
 
-void jni_YGConfigSetPointScaleFactor(alias_ref<jobject>,
-                                     jlong nativePointer,
-                                     jfloat pixelsInPoint) {
+void jni_YGConfigSetPointScaleFactor(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jfloat pixelsInPoint) {
   const YGConfigRef config = _jlong2YGConfigRef(nativePointer);
   YGConfigSetPointScaleFactor(config, pixelsInPoint);
 }
 
-void jni_YGConfigSetUseLegacyStretchBehaviour(alias_ref<jobject>,
-                                              jlong nativePointer,
-                                              jboolean useLegacyStretchBehaviour) {
+void jni_YGConfigSetUseLegacyStretchBehaviour(
+    alias_ref<jobject>,
+    jlong nativePointer,
+    jboolean useLegacyStretchBehaviour) {
   const YGConfigRef config = _jlong2YGConfigRef(nativePointer);
   YGConfigSetUseLegacyStretchBehaviour(config, useLegacyStretchBehaviour);
 }
@@ -592,7 +665,7 @@ jint jni_YGNodeGetInstanceCount(alias_ref<jclass> clazz) {
 
 #define YGMakeNativeMethod(name) makeNativeMethod(#name, name)
 
-jint JNI_OnLoad(JavaVM *vm, void *) {
+jint JNI_OnLoad(JavaVM* vm, void*) {
   return initialize(vm, [] {
     registerNatives(
         "com/facebook/yoga/YogaNode",

From 1535ecfa548cab2a4fa4500b446897733cde3014 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Wed, 11 Jul 2018 04:09:40 -0700
Subject: [PATCH 1011/1109] guards instead of nested if

Summary:
Replaces two nested if-blocks with guards. This is intended to help with restructuring this function in follow-ups.

@public

Reviewed By: priteshrnandgaonkar

Differential Revision: D8785659

fbshipit-source-id: 7b9d63e9814b83b999397c016ad67ad348bb0f72
---
 .../jni/first-party/yogajni/jni/YGJNI.cpp     | 204 +++++++++---------
 1 file changed, 101 insertions(+), 103 deletions(-)

diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
index 1d6f464cc88d..0b5520558a18 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/jni/YGJNI.cpp
@@ -47,109 +47,107 @@ static void YGTransferLayoutDirection(
 }
 
 static void YGTransferLayoutOutputsRecursive(YGNodeRef root) {
-  if (root->getHasNewLayout()) {
-    if (auto obj = YGNodeJobject(root)->lockLocal()) {
-      static auto widthField = obj->getClass()->getField<jfloat>("mWidth");
-      static auto heightField = obj->getClass()->getField<jfloat>("mHeight");
-      static auto leftField = obj->getClass()->getField<jfloat>("mLeft");
-      static auto topField = obj->getClass()->getField<jfloat>("mTop");
-
-      static auto marginLeftField =
-          obj->getClass()->getField<jfloat>("mMarginLeft");
-      static auto marginTopField =
-          obj->getClass()->getField<jfloat>("mMarginTop");
-      static auto marginRightField =
-          obj->getClass()->getField<jfloat>("mMarginRight");
-      static auto marginBottomField =
-          obj->getClass()->getField<jfloat>("mMarginBottom");
-
-      static auto paddingLeftField =
-          obj->getClass()->getField<jfloat>("mPaddingLeft");
-      static auto paddingTopField =
-          obj->getClass()->getField<jfloat>("mPaddingTop");
-      static auto paddingRightField =
-          obj->getClass()->getField<jfloat>("mPaddingRight");
-      static auto paddingBottomField =
-          obj->getClass()->getField<jfloat>("mPaddingBottom");
-
-      static auto borderLeftField =
-          obj->getClass()->getField<jfloat>("mBorderLeft");
-      static auto borderTopField =
-          obj->getClass()->getField<jfloat>("mBorderTop");
-      static auto borderRightField =
-          obj->getClass()->getField<jfloat>("mBorderRight");
-      static auto borderBottomField =
-          obj->getClass()->getField<jfloat>("mBorderBottom");
-
-      static auto edgeSetFlagField =
-          obj->getClass()->getField<jint>("mEdgeSetFlag");
-      static auto hasNewLayoutField =
-          obj->getClass()->getField<jboolean>("mHasNewLayout");
-      static auto doesLegacyStretchBehaviour =
-          obj->getClass()->getField<jboolean>(
-              "mDoesLegacyStretchFlagAffectsLayout");
-
-      /* Those flags needs be in sync with YogaNode.java */
-      const int MARGIN = 1;
-      const int PADDING = 2;
-      const int BORDER = 4;
-
-      int hasEdgeSetFlag = (int)obj->getFieldValue(edgeSetFlagField);
-
-      obj->setFieldValue(widthField, YGNodeLayoutGetWidth(root));
-      obj->setFieldValue(heightField, YGNodeLayoutGetHeight(root));
-      obj->setFieldValue(leftField, YGNodeLayoutGetLeft(root));
-      obj->setFieldValue(topField, YGNodeLayoutGetTop(root));
-      obj->setFieldValue<jboolean>(
-          doesLegacyStretchBehaviour,
-          YGNodeLayoutGetDidLegacyStretchFlagAffectLayout(root));
-
-      if ((hasEdgeSetFlag & MARGIN) == MARGIN) {
-        obj->setFieldValue(
-            marginLeftField, YGNodeLayoutGetMargin(root, YGEdgeLeft));
-        obj->setFieldValue(
-            marginTopField, YGNodeLayoutGetMargin(root, YGEdgeTop));
-        obj->setFieldValue(
-            marginRightField, YGNodeLayoutGetMargin(root, YGEdgeRight));
-        obj->setFieldValue(
-            marginBottomField, YGNodeLayoutGetMargin(root, YGEdgeBottom));
-      }
-
-      if ((hasEdgeSetFlag & PADDING) == PADDING) {
-        obj->setFieldValue(
-            paddingLeftField, YGNodeLayoutGetPadding(root, YGEdgeLeft));
-        obj->setFieldValue(
-            paddingTopField, YGNodeLayoutGetPadding(root, YGEdgeTop));
-        obj->setFieldValue(
-            paddingRightField, YGNodeLayoutGetPadding(root, YGEdgeRight));
-        obj->setFieldValue(
-            paddingBottomField, YGNodeLayoutGetPadding(root, YGEdgeBottom));
-      }
-
-      if ((hasEdgeSetFlag & BORDER) == BORDER) {
-        obj->setFieldValue(
-            borderLeftField, YGNodeLayoutGetBorder(root, YGEdgeLeft));
-        obj->setFieldValue(
-            borderTopField, YGNodeLayoutGetBorder(root, YGEdgeTop));
-        obj->setFieldValue(
-            borderRightField, YGNodeLayoutGetBorder(root, YGEdgeRight));
-        obj->setFieldValue(
-            borderBottomField, YGNodeLayoutGetBorder(root, YGEdgeBottom));
-      }
-
-      obj->setFieldValue<jboolean>(hasNewLayoutField, true);
-      YGTransferLayoutDirection(root, obj);
-      root->setHasNewLayout(false);
-
-      for (uint32_t i = 0; i < YGNodeGetChildCount(root); i++) {
-        YGTransferLayoutOutputsRecursive(YGNodeGetChild(root, i));
-      }
-    } else {
-      YGLog(
-          root,
-          YGLogLevelError,
-          "Java YGNode was GCed during layout calculation\n");
-    }
+  if (!root->getHasNewLayout()) {
+    return;
+  }
+  auto obj = YGNodeJobject(root)->lockLocal();
+  if (!obj) {
+    YGLog(
+        root,
+        YGLogLevelError,
+        "Java YGNode was GCed during layout calculation\n");
+    return;
+  }
+
+  static auto widthField = obj->getClass()->getField<jfloat>("mWidth");
+  static auto heightField = obj->getClass()->getField<jfloat>("mHeight");
+  static auto leftField = obj->getClass()->getField<jfloat>("mLeft");
+  static auto topField = obj->getClass()->getField<jfloat>("mTop");
+
+  static auto marginLeftField =
+      obj->getClass()->getField<jfloat>("mMarginLeft");
+  static auto marginTopField = obj->getClass()->getField<jfloat>("mMarginTop");
+  static auto marginRightField =
+      obj->getClass()->getField<jfloat>("mMarginRight");
+  static auto marginBottomField =
+      obj->getClass()->getField<jfloat>("mMarginBottom");
+
+  static auto paddingLeftField =
+      obj->getClass()->getField<jfloat>("mPaddingLeft");
+  static auto paddingTopField =
+      obj->getClass()->getField<jfloat>("mPaddingTop");
+  static auto paddingRightField =
+      obj->getClass()->getField<jfloat>("mPaddingRight");
+  static auto paddingBottomField =
+      obj->getClass()->getField<jfloat>("mPaddingBottom");
+
+  static auto borderLeftField =
+      obj->getClass()->getField<jfloat>("mBorderLeft");
+  static auto borderTopField = obj->getClass()->getField<jfloat>("mBorderTop");
+  static auto borderRightField =
+      obj->getClass()->getField<jfloat>("mBorderRight");
+  static auto borderBottomField =
+      obj->getClass()->getField<jfloat>("mBorderBottom");
+
+  static auto edgeSetFlagField =
+      obj->getClass()->getField<jint>("mEdgeSetFlag");
+  static auto hasNewLayoutField =
+      obj->getClass()->getField<jboolean>("mHasNewLayout");
+  static auto doesLegacyStretchBehaviour = obj->getClass()->getField<jboolean>(
+      "mDoesLegacyStretchFlagAffectsLayout");
+
+  /* Those flags needs be in sync with YogaNode.java */
+  const int MARGIN = 1;
+  const int PADDING = 2;
+  const int BORDER = 4;
+
+  int hasEdgeSetFlag = (int)obj->getFieldValue(edgeSetFlagField);
+
+  obj->setFieldValue(widthField, YGNodeLayoutGetWidth(root));
+  obj->setFieldValue(heightField, YGNodeLayoutGetHeight(root));
+  obj->setFieldValue(leftField, YGNodeLayoutGetLeft(root));
+  obj->setFieldValue(topField, YGNodeLayoutGetTop(root));
+  obj->setFieldValue<jboolean>(
+      doesLegacyStretchBehaviour,
+      YGNodeLayoutGetDidLegacyStretchFlagAffectLayout(root));
+
+  if ((hasEdgeSetFlag & MARGIN) == MARGIN) {
+    obj->setFieldValue(
+        marginLeftField, YGNodeLayoutGetMargin(root, YGEdgeLeft));
+    obj->setFieldValue(marginTopField, YGNodeLayoutGetMargin(root, YGEdgeTop));
+    obj->setFieldValue(
+        marginRightField, YGNodeLayoutGetMargin(root, YGEdgeRight));
+    obj->setFieldValue(
+        marginBottomField, YGNodeLayoutGetMargin(root, YGEdgeBottom));
+  }
+
+  if ((hasEdgeSetFlag & PADDING) == PADDING) {
+    obj->setFieldValue(
+        paddingLeftField, YGNodeLayoutGetPadding(root, YGEdgeLeft));
+    obj->setFieldValue(
+        paddingTopField, YGNodeLayoutGetPadding(root, YGEdgeTop));
+    obj->setFieldValue(
+        paddingRightField, YGNodeLayoutGetPadding(root, YGEdgeRight));
+    obj->setFieldValue(
+        paddingBottomField, YGNodeLayoutGetPadding(root, YGEdgeBottom));
+  }
+
+  if ((hasEdgeSetFlag & BORDER) == BORDER) {
+    obj->setFieldValue(
+        borderLeftField, YGNodeLayoutGetBorder(root, YGEdgeLeft));
+    obj->setFieldValue(borderTopField, YGNodeLayoutGetBorder(root, YGEdgeTop));
+    obj->setFieldValue(
+        borderRightField, YGNodeLayoutGetBorder(root, YGEdgeRight));
+    obj->setFieldValue(
+        borderBottomField, YGNodeLayoutGetBorder(root, YGEdgeBottom));
+  }
+
+  obj->setFieldValue<jboolean>(hasNewLayoutField, true);
+  YGTransferLayoutDirection(root, obj);
+  root->setHasNewLayout(false);
+
+  for (uint32_t i = 0; i < YGNodeGetChildCount(root); i++) {
+    YGTransferLayoutOutputsRecursive(YGNodeGetChild(root, i));
   }
 }
 

From 578b0b2a51fc0c2aba5d27cdd5335396d5351463 Mon Sep 17 00:00:00 2001
From: Martin Sherburn <mns@oculus.com>
Date: Wed, 11 Jul 2018 04:18:34 -0700
Subject: [PATCH 1012/1109] Fixed issue with reloading bundle from remote
 debugger

Summary: This is a follow up to D8316215. That diff had a flaw in that once appExecuted was set to true it would never be reset back to false. This fixes that so if another bundle is loaded after the first one it will work.

Reviewed By: rafeca

Differential Revision: D8661523

fbshipit-source-id: 5f6024102248383f64952fd33b37368732d5f900
---
 local-cli/server/util/debugger-ui/index.html | 1 +
 1 file changed, 1 insertion(+)

diff --git a/local-cli/server/util/debugger-ui/index.html b/local-cli/server/util/debugger-ui/index.html
index 8a7f2b3206fe..c4f825145acb 100644
--- a/local-cli/server/util/debugger-ui/index.html
+++ b/local-cli/server/util/debugger-ui/index.html
@@ -179,6 +179,7 @@
         shutdownJSRuntime();
         Page.setState({status: {type: 'disconnected'}});
       } else if (object.method === 'executeApplicationScript') {
+        appExecuted = false;
         worker.postMessage({
           ...object,
           url: await getBlobUrl(object.url),

From 90a408ea6ff7833e33b4058f490073e04460d00b Mon Sep 17 00:00:00 2001
From: Pritesh Nandgaonkar <prit91@fb.com>
Date: Wed, 11 Jul 2018 05:55:02 -0700
Subject: [PATCH 1013/1109] Fix SingleFlex Child condition

Summary:
Fixes the improper `singleFlexChild` optimization. In the case when all the childs have `flex-grow:0 flex-grow:0` except one child with `flex-grow:1 flex-shrink:1`, then one can simply measure all the non-flexing children and then give the flexing child all the remaining space.

Also added a test case which reproduced the bug

Reviewed By: IanChilds

Differential Revision: D8782684

fbshipit-source-id: ffd4d35b6122f82111b987540efb23bd2a8da5a2
---
 ReactCommon/yoga/yoga/Yoga.cpp | 15 ++++++++-------
 1 file changed, 8 insertions(+), 7 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index e5d1aabb0489..3684aae4fd50 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1788,16 +1788,17 @@ static void YGNodeComputeFlexBasisForChildren(
   // child to exactly match the remaining space
   if (measureModeMainDim == YGMeasureModeExactly) {
     for (auto child : children) {
-      if (singleFlexChild != nullptr) {
-        if (child->isNodeFlexible()) {
-          // There is already a flexible child, abort
+      if (child->isNodeFlexible()) {
+        if (singleFlexChild != nullptr ||
+            YGFloatsEqual(child->resolveFlexGrow(), 0.0f) ||
+            YGFloatsEqual(child->resolveFlexShrink(), 0.0f)) {
+          // There is already a flexible child, or this flexible child doesn't
+          // have flexGrow and flexShrink, abort
           singleFlexChild = nullptr;
           break;
+        } else {
+          singleFlexChild = child;
         }
-      } else if (
-          child->resolveFlexGrow() > 0.0f &&
-          child->resolveFlexShrink() > 0.0f) {
-        singleFlexChild = child;
       }
     }
   }

From 00936a003cf619e4836e2c205fd24e695e8c97d5 Mon Sep 17 00:00:00 2001
From: Miguel Jimenez Esun <mjimenez@fb.com>
Date: Wed, 11 Jul 2018 06:36:44 -0700
Subject: [PATCH 1014/1109] Upgrade Jest to v23.4.0

Summary: Upgrade Jest to the latest version.

Differential Revision: D8784710

fbshipit-source-id: 2319bf0d11506c1c0ad0506ba38a76e07f8feb3b
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index acd729198cbb..66ba68b1f42b 100644
--- a/package.json
+++ b/package.json
@@ -213,7 +213,7 @@
     "eslint-plugin-react": "7.8.2",
     "eslint-plugin-react-native": "^3.2.1",
     "flow-bin": "^0.76.0",
-    "jest": "23.2.0",
+    "jest": "23.4.0",
     "jest-junit": "5.1.0",
     "prettier": "1.13.6",
     "react": "16.4.1",

From 48584547180cf97177132eed8fcad390b12a2677 Mon Sep 17 00:00:00 2001
From: Scott Wolchok <swolchok@fb.com>
Date: Wed, 11 Jul 2018 08:51:31 -0700
Subject: [PATCH 1015/1109] Remove unused YGNode::*nextChild

Summary: This linked list was never used, and YGNodeDeepClone was doing scary things to maintain it.

Reviewed By: davidaurelio

Differential Revision: D8792864

fbshipit-source-id: c578fabe65c837f0791aa9ac3e18f31d93691abd
---
 ReactCommon/yoga/yoga/YGNode.cpp | 13 -------------
 ReactCommon/yoga/yoga/YGNode.h   |  4 ----
 ReactCommon/yoga/yoga/Yoga.cpp   |  4 ----
 3 files changed, 21 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 16f9e4d0092e..67d991a4a2c6 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -69,10 +69,6 @@ YGNodeRef YGNode::getChild(uint32_t index) const {
   return children_.at(index);
 }
 
-YGNodeRef YGNode::getNextChild() const {
-  return nextChild_;
-}
-
 YGConfigRef YGNode::getConfig() const {
   return config_;
 }
@@ -249,10 +245,6 @@ void YGNode::setChildren(const YGVector& children) {
   children_ = children;
 }
 
-void YGNode::setNextChild(YGNodeRef nextChild) {
-  nextChild_ = nextChild;
-}
-
 void YGNode::replaceChild(YGNodeRef child, uint32_t index) {
   children_[index] = child;
 }
@@ -405,7 +397,6 @@ YGNode::YGNode()
       lineIndex_(0),
       owner_(nullptr),
       children_(YGVector()),
-      nextChild_(nullptr),
       config_(nullptr),
       isDirty_(false),
       resolvedDimensions_({{YGValueUndefined, YGValueUndefined}}) {}
@@ -423,7 +414,6 @@ YGNode::YGNode(const YGNode& node)
       lineIndex_(node.lineIndex_),
       owner_(node.owner_),
       children_(node.children_),
-      nextChild_(node.nextChild_),
       config_(node.config_),
       isDirty_(node.isDirty_),
       resolvedDimensions_(node.resolvedDimensions_) {}
@@ -445,7 +435,6 @@ YGNode::YGNode(
     uint32_t lineIndex,
     YGNodeRef owner,
     const YGVector& children,
-    YGNodeRef nextChild,
     YGConfigRef config,
     bool isDirty,
     std::array<YGValue, 2> resolvedDimensions)
@@ -461,7 +450,6 @@ YGNode::YGNode(
       lineIndex_(lineIndex),
       owner_(owner),
       children_(children),
-      nextChild_(nextChild),
       config_(config),
       isDirty_(isDirty),
       resolvedDimensions_(resolvedDimensions) {}
@@ -487,7 +475,6 @@ YGNode& YGNode::operator=(const YGNode& node) {
   lineIndex_ = node.getLineIndex();
   owner_ = node.getOwner();
   children_ = node.getChildren();
-  nextChild_ = node.getNextChild();
   config_ = node.getConfig();
   isDirty_ = node.isDirty();
   resolvedDimensions_ = node.getResolvedDimensions();
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index e3562bb60529..e4d50dcf8c45 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -26,7 +26,6 @@ struct YGNode {
   uint32_t lineIndex_;
   YGNodeRef owner_;
   YGVector children_;
-  YGNodeRef nextChild_;
   YGConfigRef config_;
   bool isDirty_;
   std::array<YGValue, 2> resolvedDimensions_;
@@ -54,7 +53,6 @@ struct YGNode {
       uint32_t lineIndex,
       YGNodeRef owner,
       const YGVector& children,
-      YGNodeRef nextChild,
       YGConfigRef config,
       bool isDirty,
       std::array<YGValue, 2> resolvedDimensions);
@@ -83,7 +81,6 @@ struct YGNode {
   YGVector getChildren() const;
   uint32_t getChildrenCount() const;
   YGNodeRef getChild(uint32_t index) const;
-  YGNodeRef getNextChild() const;
   YGConfigRef getConfig() const;
   bool isDirty() const;
   std::array<YGValue, 2> getResolvedDimensions() const;
@@ -136,7 +133,6 @@ struct YGNode {
   void setLineIndex(uint32_t lineIndex);
   void setOwner(YGNodeRef owner);
   void setChildren(const YGVector& children);
-  void setNextChild(YGNodeRef nextChild);
   void setConfig(YGConfigRef config);
   void setDirty(bool isDirty);
   void setLayoutLastOwnerDirection(YGDirection direction);
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 3684aae4fd50..5b5a90888cea 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -275,10 +275,6 @@ static YGNodeRef YGNodeDeepClone(YGNodeRef oldNode) {
     node->setConfig(YGConfigClone(*(oldNode->getConfig())));
   }
 
-  if (oldNode->getNextChild() != nullptr) {
-    node->setNextChild(YGNodeDeepClone(oldNode->getNextChild()));
-  }
-
   return node;
 }
 

From 40cdda3166bf3373f87b61a5d5ce3a356d52a4b6 Mon Sep 17 00:00:00 2001
From: Scott Wolchok <swolchok@fb.com>
Date: Wed, 11 Jul 2018 08:51:33 -0700
Subject: [PATCH 1016/1109] Inline simple YGNode getters/setters

Summary: Simple getters/setters are usually inlined like this.

Reviewed By: priteshrnandgaonkar, davidaurelio

Differential Revision: D8793588

fbshipit-source-id: 436bd54880e41a5e403e3f4ae0d9dd4a413df79c
---
 ReactCommon/yoga/yoga/YGNode.cpp | 130 -----------------------
 ReactCommon/yoga/yoga/YGNode.h   | 175 +++++++++++++++++++++++++------
 2 files changed, 142 insertions(+), 163 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 67d991a4a2c6..13571a9d62fb 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -9,82 +9,6 @@
 #include <iostream>
 #include "Utils.h"
 
-void* YGNode::getContext() const {
-  return context_;
-}
-
-YGPrintFunc YGNode::getPrintFunc() const {
-  return print_;
-}
-
-bool YGNode::getHasNewLayout() const {
-  return hasNewLayout_;
-}
-
-YGNodeType YGNode::getNodeType() const {
-  return nodeType_;
-}
-
-YGMeasureFunc YGNode::getMeasure() const {
-  return measure_;
-}
-
-YGBaselineFunc YGNode::getBaseline() const {
-  return baseline_;
-}
-
-YGDirtiedFunc YGNode::getDirtied() const {
-  return dirtied_;
-}
-
-YGStyle& YGNode::getStyle() {
-  return style_;
-}
-
-YGLayout& YGNode::getLayout() {
-  return layout_;
-}
-
-uint32_t YGNode::getLineIndex() const {
-  return lineIndex_;
-}
-
-YGNodeRef YGNode::getOwner() const {
-  return owner_;
-}
-
-YGNodeRef YGNode::getParent() const {
-  return getOwner();
-}
-
-YGVector YGNode::getChildren() const {
-  return children_;
-}
-
-uint32_t YGNode::getChildrenCount() const {
-  return static_cast<uint32_t>(children_.size());
-}
-
-YGNodeRef YGNode::getChild(uint32_t index) const {
-  return children_.at(index);
-}
-
-YGConfigRef YGNode::getConfig() const {
-  return config_;
-}
-
-bool YGNode::isDirty() const {
-  return isDirty_;
-}
-
-YGValue YGNode::getResolvedDimension(int index) {
-  return resolvedDimensions_[index];
-}
-
-std::array<YGValue, 2> YGNode::getResolvedDimensions() const {
-  return resolvedDimensions_;
-}
-
 YGFloatOptional YGNode::getLeadingPosition(
     const YGFlexDirection& axis,
     const float& axisSize) const {
@@ -173,29 +97,7 @@ YGFloatOptional YGNode::getMarginForAxis(
 
 // Setters
 
-void YGNode::setContext(void* context) {
-  context_ = context;
-}
-
-void YGNode::setPrintFunc(YGPrintFunc printFunc) {
-  print_ = printFunc;
-}
-
-void YGNode::setHasNewLayout(bool hasNewLayout) {
-  hasNewLayout_ = hasNewLayout;
-}
-
-void YGNode::setNodeType(YGNodeType nodeType) {
-  nodeType_ = nodeType;
-}
-
-void YGNode::setStyleFlexDirection(YGFlexDirection direction) {
-  style_.flexDirection = direction;
-}
 
-void YGNode::setStyleAlignContent(YGAlign alignContent) {
-  style_.alignContent = alignContent;
-}
 
 void YGNode::setMeasureFunc(YGMeasureFunc measureFunc) {
   if (measureFunc == nullptr) {
@@ -217,34 +119,6 @@ void YGNode::setMeasureFunc(YGMeasureFunc measureFunc) {
   measure_ = measureFunc;
 }
 
-void YGNode::setBaseLineFunc(YGBaselineFunc baseLineFunc) {
-  baseline_ = baseLineFunc;
-}
-
-void YGNode::setDirtiedFunc(YGDirtiedFunc dirtiedFunc) {
-  dirtied_ = dirtiedFunc;
-}
-
-void YGNode::setStyle(const YGStyle& style) {
-  style_ = style;
-}
-
-void YGNode::setLayout(const YGLayout& layout) {
-  layout_ = layout;
-}
-
-void YGNode::setLineIndex(uint32_t lineIndex) {
-  lineIndex_ = lineIndex;
-}
-
-void YGNode::setOwner(YGNodeRef owner) {
-  owner_ = owner;
-}
-
-void YGNode::setChildren(const YGVector& children) {
-  children_ = children;
-}
-
 void YGNode::replaceChild(YGNodeRef child, uint32_t index) {
   children_[index] = child;
 }
@@ -257,10 +131,6 @@ void YGNode::insertChild(YGNodeRef child, uint32_t index) {
   children_.insert(children_.begin() + index, child);
 }
 
-void YGNode::setConfig(YGConfigRef config) {
-  config_ = config;
-}
-
 void YGNode::setDirty(bool isDirty) {
   if (isDirty == isDirty_) {
     return;
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index e4d50dcf8c45..ab302e06727e 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -58,33 +58,97 @@ struct YGNode {
       std::array<YGValue, 2> resolvedDimensions);
 
   // Getters
-  void* getContext() const;
-  YGPrintFunc getPrintFunc() const;
-  bool getHasNewLayout() const;
-  YGNodeType getNodeType() const;
-  YGMeasureFunc getMeasure() const;
-  YGBaselineFunc getBaseline() const;
-  YGDirtiedFunc getDirtied() const;
+  void* getContext() const {
+    return context_;
+  }
+
+  YGPrintFunc getPrintFunc() const {
+    return print_;
+  }
+
+  bool getHasNewLayout() const {
+    return hasNewLayout_;
+  }
+  
+  YGNodeType getNodeType() const {
+    return nodeType_;
+  }
+  
+  YGMeasureFunc getMeasure() const {
+    return measure_;
+  }
+  
+  YGBaselineFunc getBaseline() const {
+    return baseline_;
+  }
+  
+  YGDirtiedFunc getDirtied() const {
+    return dirtied_;
+  }
+  
   // For Performance reasons passing as reference.
-  YGStyle& getStyle();
+  YGStyle& getStyle() {
+    return style_;
+  }
+
+  const YGStyle& getStyle() const {
+    return style_;
+  }
+
   // For Performance reasons passing as reference.
-  YGLayout& getLayout();
-  uint32_t getLineIndex() const;
+  YGLayout& getLayout() {
+    return layout_;
+  }
+
+  const YGLayout& getLayout() const {
+    return layout_;
+  }
+  
+  uint32_t getLineIndex() const {
+    return lineIndex_;
+  }
+  
   // returns the YGNodeRef that owns this YGNode. An owner is used to identify
   // the YogaTree that a YGNode belongs to.
   // This method will return the parent of the YGNode when a YGNode only belongs
   // to one YogaTree or nullptr when the YGNode is shared between two or more
   // YogaTrees.
-  YGNodeRef getOwner() const;
+  YGNodeRef getOwner() const {
+    return owner_;
+  }
+  
   // Deprecated, use getOwner() instead.
-  YGNodeRef getParent() const;
-  YGVector getChildren() const;
-  uint32_t getChildrenCount() const;
-  YGNodeRef getChild(uint32_t index) const;
-  YGConfigRef getConfig() const;
-  bool isDirty() const;
-  std::array<YGValue, 2> getResolvedDimensions() const;
-  YGValue getResolvedDimension(int index);
+  YGNodeRef getParent() const {
+    return getOwner();
+  }
+  
+  YGVector getChildren() const {
+    return children_;
+  }
+  
+  uint32_t getChildrenCount() const {
+    return static_cast<uint32_t>(children_.size());
+  }
+  
+  YGNodeRef getChild(uint32_t index) const {
+    return children_.at(index);
+  }
+
+  YGConfigRef getConfig() const {
+    return config_;
+  }
+  
+  bool isDirty() const {
+    return isDirty_;
+  }
+  
+  std::array<YGValue, 2> getResolvedDimensions() const {
+    return resolvedDimensions_;
+  }
+  
+  YGValue getResolvedDimension(int index) const {
+    return resolvedDimensions_[index];
+  }
 
   // Methods related to positions, margin, padding and border
   YGFloatOptional getLeadingPosition(const YGFlexDirection& axis,
@@ -119,21 +183,66 @@ struct YGNode {
       const float& widthSize) const;
   // Setters
 
-  void setContext(void* context);
-  void setPrintFunc(YGPrintFunc printFunc);
-  void setHasNewLayout(bool hasNewLayout);
-  void setNodeType(YGNodeType nodeTye);
+  void setContext(void* context) {
+    context_ = context;
+  }
+
+  void setPrintFunc(YGPrintFunc printFunc) {
+    print_ = printFunc;
+  }
+
+  void setHasNewLayout(bool hasNewLayout) {
+    hasNewLayout_ = hasNewLayout;
+  }
+  
+  void setNodeType(YGNodeType nodeType) {
+    nodeType_ = nodeType;
+  }
+
+  void setStyleFlexDirection(YGFlexDirection direction) {
+    style_.flexDirection = direction;
+  }
+
+  void setStyleAlignContent(YGAlign alignContent) {
+    style_.alignContent = alignContent;
+  }
+
   void setMeasureFunc(YGMeasureFunc measureFunc);
-  void setBaseLineFunc(YGBaselineFunc baseLineFunc);
-  void setDirtiedFunc(YGDirtiedFunc dirtiedFunc);
-  void setStyle(const YGStyle& style);
-  void setStyleFlexDirection(YGFlexDirection direction);
-  void setStyleAlignContent(YGAlign alignContent);
-  void setLayout(const YGLayout& layout);
-  void setLineIndex(uint32_t lineIndex);
-  void setOwner(YGNodeRef owner);
-  void setChildren(const YGVector& children);
-  void setConfig(YGConfigRef config);
+
+  void setBaseLineFunc(YGBaselineFunc baseLineFunc) {
+    baseline_ = baseLineFunc;
+  }
+
+  void setDirtiedFunc(YGDirtiedFunc dirtiedFunc) {
+    dirtied_ = dirtiedFunc;
+  }
+
+  void setStyle(const YGStyle& style) {
+    style_ = style;
+  }
+  
+  void setLayout(const YGLayout& layout) {
+    layout_ = layout;
+  }
+  
+  void setLineIndex(uint32_t lineIndex) {
+    lineIndex_ = lineIndex;
+  }
+  
+  void setOwner(YGNodeRef owner) {
+    owner_ = owner;
+  }
+
+  void setChildren(const YGVector& children) {
+    children_ = children;
+  }
+
+  // TODO: rvalue override for setChildren
+  
+  void setConfig(YGConfigRef config) {
+    config_ = config;
+  }
+
   void setDirty(bool isDirty);
   void setLayoutLastOwnerDirection(YGDirection direction);
   void setLayoutComputedFlexBasis(const YGFloatOptional& computedFlexBasis);

From a08e8d07d07f25ece69cc319ad1baeba241f0804 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Wed, 11 Jul 2018 09:33:24 -0700
Subject: [PATCH 1017/1109] Lint java files

Summary:
@public

Applies lint auto-fixes to java files.

Reviewed By: priteshrnandgaonkar

Differential Revision: D8803814

fbshipit-source-id: 2e4dc285b233091a9fbadf38fc22dd6e36f11f8e
---
 .../src/main/java/com/facebook/yoga/YogaAlign.java        | 8 ++++----
 .../main/java/com/facebook/yoga/YogaBaselineFunction.java | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaConfig.java       | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaConstants.java    | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaDimension.java    | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaDirection.java    | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaDisplay.java      | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaEdge.java         | 8 ++++----
 .../java/com/facebook/yoga/YogaExperimentalFeature.java   | 8 ++++----
 .../main/java/com/facebook/yoga/YogaFlexDirection.java    | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaJustify.java      | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaLogLevel.java     | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaLogger.java       | 8 ++++----
 .../main/java/com/facebook/yoga/YogaMeasureFunction.java  | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaMeasureMode.java  | 8 ++++----
 .../main/java/com/facebook/yoga/YogaMeasureOutput.java    | 8 ++++----
 .../java/com/facebook/yoga/YogaNodeCloneFunction.java     | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaNodeType.java     | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaOverflow.java     | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaPositionType.java | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaPrintOptions.java | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaUnit.java         | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaValue.java        | 8 ++++----
 .../src/main/java/com/facebook/yoga/YogaWrap.java         | 8 ++++----
 24 files changed, 96 insertions(+), 96 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaAlign.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaAlign.java
index bea5aebda8ea..5687ab9d0a02 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaAlign.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaAlign.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaBaselineFunction.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaBaselineFunction.java
index 9ec41e7eae44..20feae330e70 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaBaselineFunction.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaBaselineFunction.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
index 12aa0d8e4a27..128f53285089 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConfig.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConstants.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConstants.java
index 4e081ce49a0e..68c5c982069b 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaConstants.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaConstants.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 public class YogaConstants {
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaDimension.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaDimension.java
index b0d89226d286..3a950e014dbc 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaDimension.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaDimension.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaDirection.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaDirection.java
index dd6444e12ea7..ccd46e84a621 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaDirection.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaDirection.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaDisplay.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaDisplay.java
index e6e52aadef9a..75c2b687d93f 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaDisplay.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaDisplay.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaEdge.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaEdge.java
index 053490dabfb0..36a893f66cb6 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaEdge.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaEdge.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaExperimentalFeature.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaExperimentalFeature.java
index a8a4be1432a5..790bd0566e6e 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaExperimentalFeature.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaExperimentalFeature.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaFlexDirection.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaFlexDirection.java
index cf192d6c07ac..5c66d92fc4fc 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaFlexDirection.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaFlexDirection.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaJustify.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaJustify.java
index 9e15dc4a9528..13d3a0014574 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaJustify.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaJustify.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaLogLevel.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaLogLevel.java
index 458e1b950ebb..0cf7f70c37f2 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaLogLevel.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaLogLevel.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaLogger.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaLogger.java
index 66f62c89d717..6d1a6a1e9dc4 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaLogger.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaLogger.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureFunction.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureFunction.java
index 2d2b304d3f96..cc54caeca7fc 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureFunction.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureFunction.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureMode.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureMode.java
index 9719377630fa..5cfc24a4b322 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureMode.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureMode.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureOutput.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureOutput.java
index 1d2141d12a05..e68af410dd58 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureOutput.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaMeasureOutput.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 /**
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeCloneFunction.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeCloneFunction.java
index 0733776a7e37..ccf7f5c5c659 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeCloneFunction.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeCloneFunction.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2017-present, Facebook, Inc.
+ *  Copyright (c) 2017-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeType.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeType.java
index fb767b0587ee..7eb7246c5bac 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeType.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeType.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaOverflow.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaOverflow.java
index 9563d3036410..85bc8b20a79a 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaOverflow.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaOverflow.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaPositionType.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaPositionType.java
index be42a999231a..17073f471544 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaPositionType.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaPositionType.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaPrintOptions.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaPrintOptions.java
index 5a804adf4552..3b59960dfcc0 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaPrintOptions.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaPrintOptions.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaUnit.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaUnit.java
index 8eb2b31680a5..e4002dd09ab6 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaUnit.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaUnit.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaValue.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaValue.java
index a99d56418905..c0bb6e224aeb 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaValue.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaValue.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;
diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaWrap.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaWrap.java
index 1eaa9f7ad6f2..3c10dd3aed6a 100644
--- a/ReactAndroid/src/main/java/com/facebook/yoga/YogaWrap.java
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaWrap.java
@@ -1,10 +1,10 @@
 /*
- * Copyright (c) 2014-present, Facebook, Inc.
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 package com.facebook.yoga;
 
 import com.facebook.proguard.annotations.DoNotStrip;

From 78137bc31a92538ea19dd47754d1bb75a9c6a4a1 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Wed, 11 Jul 2018 10:45:16 -0700
Subject: [PATCH 1018/1109] Update deprecated glob usages.

Summary: https://our.intern.facebook.com/intern/wiki/Buck/python-to-skylark/

Reviewed By: davidaurelio

Differential Revision: D8795050

fbshipit-source-id: 1599a0a9ddd9af54a86884291945a93b91ba31bd
---
 .../src/androidTest/java/com/facebook/react/testing/BUCK        | 2 +-
 ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK  | 2 +-
 ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK       | 2 +-
 3 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
index 647a303619a1..8b61c439ef52 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/BUCK
@@ -4,7 +4,7 @@ rn_android_library(
     name = "testing",
     srcs = glob(
         ["**/*.java"],
-        excludes = [
+        exclude = [
             "idledetection/**/*.java",
             "network/**/*.java",
         ],
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK b/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
index ead269cd5d25..f3b7d905472b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/image/BUCK
@@ -24,7 +24,7 @@ rn_android_library(
     name = "image",
     srcs = glob(
         ["*.java"],
-        excludes = IMAGE_EVENT_FILES,
+        exclude = IMAGE_EVENT_FILES,
     ),
     provided_deps = [
         react_native_dep("third-party/android/support-annotations:android-support-annotations"),
diff --git a/ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK b/ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK
index b92de1b5f551..7a5779042234 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/bridge/BUCK
@@ -8,7 +8,7 @@ rn_android_library(
     name = "testhelpers",
     srcs = glob(
         ["*.java"],
-        excludes = STANDARD_TEST_SRCS,
+        exclude = STANDARD_TEST_SRCS,
     ),
     visibility = [
         "PUBLIC",

From f0d35904c9a1454569bd4b797bec305c843f9bda Mon Sep 17 00:00:00 2001
From: slorber <lorber.sebastien@gmail.com>
Date: Wed, 11 Jul 2018 22:27:11 -0700
Subject: [PATCH 1019/1109] Add missing tests for Animated.forkEvent (#20111)

Summary:
`forkEvent` is generally used to intercept an existing listener and add a new js listener to it, considering the original listener can be null/js/Animated.event(). I added tests to ensure the 3 cases of the implementation are all covered.
Pull Request resolved: https://github.com/facebook/react-native/pull/20111

Differential Revision: D8817500

Pulled By: hramos

fbshipit-source-id: 1a20b6f73e2d47bbefccd31378764909a45e89bb
---
 .../Animated/src/__tests__/Animated-test.js   | 20 ++++++++++++++++++-
 1 file changed, 19 insertions(+), 1 deletion(-)

diff --git a/Libraries/Animated/src/__tests__/Animated-test.js b/Libraries/Animated/src/__tests__/Animated-test.js
index 1c2066bfdc5e..6c5ef66b14a1 100644
--- a/Libraries/Animated/src/__tests__/Animated-test.js
+++ b/Libraries/Animated/src/__tests__/Animated-test.js
@@ -572,7 +572,7 @@ describe('Animated tests', () => {
       expect(listener.mock.calls.length).toBe(1);
       expect(listener).toBeCalledWith({foo: 42});
     });
-    it('should call forked event listeners', () => {
+    it('should call forked event listeners, with Animated.event() listener', () => {
       const value = new Animated.Value(0);
       const listener = jest.fn();
       const handler = Animated.event([{foo: value}], {listener});
@@ -585,6 +585,24 @@ describe('Animated tests', () => {
       expect(listener2.mock.calls.length).toBe(1);
       expect(listener2).toBeCalledWith({foo: 42});
     });
+    it('should call forked event listeners, with js listener', () => {
+      const listener = jest.fn();
+      const listener2 = jest.fn();
+      const forkedHandler = Animated.forkEvent(listener, listener2);
+      forkedHandler({foo: 42});
+      expect(listener.mock.calls.length).toBe(1);
+      expect(listener).toBeCalledWith({foo: 42});
+      expect(listener2.mock.calls.length).toBe(1);
+      expect(listener2).toBeCalledWith({foo: 42});
+    });
+    it('should call forked event listeners, with undefined listener', () => {
+      const listener = undefined;
+      const listener2 = jest.fn();
+      const forkedHandler = Animated.forkEvent(listener, listener2);
+      forkedHandler({foo: 42});
+      expect(listener2.mock.calls.length).toBe(1);
+      expect(listener2).toBeCalledWith({foo: 42});
+    });
   });
 
   describe('Animated Interactions', () => {

From b5f027dd7790195235bcfb670c895928879aff53 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 12 Jul 2018 07:55:17 -0700
Subject: [PATCH 1020/1109] Add `YogaNodeProperties` interface

Summary:
`YogaNodeProperties` will serve as abstraction over JNI adapters / storage backends in follow-ups.

@public

Reviewed By: IanChilds

Differential Revision: D8818805

fbshipit-source-id: 7998a56daebea60dd13b07228dffdf14be852554
---
 .../com/facebook/yoga/YogaNodeProperties.java | 167 ++++++++++++++++++
 1 file changed, 167 insertions(+)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeProperties.java

diff --git a/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeProperties.java b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeProperties.java
new file mode 100644
index 000000000000..fbad2ea26e52
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/yoga/YogaNodeProperties.java
@@ -0,0 +1,167 @@
+/*
+ *  Copyright (c) 2018-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
+ *
+ */
+package com.facebook.yoga;
+
+public interface YogaNodeProperties {
+
+  YogaNodeProperties clone(YogaNode node);
+
+  long getNativePointer();
+
+  void onAfterCalculateLayout();
+
+  void reset();
+
+  boolean hasNewLayout();
+
+  boolean isDirty();
+
+  void markLayoutSeen();
+
+  YogaDirection getStyleDirection();
+
+  void setDirection(YogaDirection direction);
+
+  YogaFlexDirection getFlexDirection();
+
+  void setFlexDirection(YogaFlexDirection flexDirection);
+
+  YogaJustify getJustifyContent();
+
+  void setJustifyContent(YogaJustify justifyContent);
+
+  YogaAlign getAlignItems();
+
+  void setAlignItems(YogaAlign alignItems);
+
+  YogaAlign getAlignSelf();
+
+  void setAlignSelf(YogaAlign alignSelf);
+
+  YogaAlign getAlignContent();
+
+  void setAlignContent(YogaAlign alignContent);
+
+  YogaPositionType getPositionType();
+
+  void setPositionType(YogaPositionType positionType);
+
+  void setWrap(YogaWrap flexWrap);
+
+  YogaOverflow getOverflow();
+
+  void setOverflow(YogaOverflow overflow);
+
+  YogaDisplay getDisplay();
+
+  void setDisplay(YogaDisplay display);
+
+  void setFlex(float flex);
+
+  float getFlexGrow();
+
+  void setFlexGrow(float flexGrow);
+
+  float getFlexShrink();
+
+  void setFlexShrink(float flexShrink);
+
+  YogaValue getFlexBasis();
+
+  void setFlexBasis(float flexBasis);
+
+  void setFlexBasisPercent(float percent);
+
+  void setFlexBasisAuto();
+
+  YogaValue getMargin(YogaEdge edge);
+
+  void setMargin(YogaEdge edge, float margin);
+
+  void setMarginPercent(YogaEdge edge, float percent);
+
+  void setMarginAuto(YogaEdge edge);
+
+  YogaValue getPadding(YogaEdge edge);
+
+  void setPadding(YogaEdge edge, float padding);
+
+  void setPaddingPercent(YogaEdge edge, float percent);
+
+  float getBorder(YogaEdge edge);
+
+  void setBorder(YogaEdge edge, float border);
+
+  YogaValue getPosition(YogaEdge edge);
+
+  void setPosition(YogaEdge edge, float position);
+
+  void setPositionPercent(YogaEdge edge, float percent);
+
+  YogaValue getWidth();
+
+  void setWidth(float width);
+
+  void setWidthPercent(float percent);
+
+  void setWidthAuto();
+
+  YogaValue getHeight();
+
+  void setHeight(float height);
+
+  void setHeightPercent(float percent);
+
+  void setHeightAuto();
+
+  YogaValue getMinWidth();
+
+  void setMinWidth(float minWidth);
+
+  void setMinWidthPercent(float percent);
+
+  YogaValue getMinHeight();
+
+  void setMinHeight(float minHeight);
+
+  void setMinHeightPercent(float percent);
+
+  YogaValue getMaxWidth();
+
+  void setMaxWidth(float maxWidth);
+
+  void setMaxWidthPercent(float percent);
+
+  YogaValue getMaxHeight();
+
+  void setMaxHeight(float maxheight);
+
+  void setMaxHeightPercent(float percent);
+
+  float getAspectRatio();
+
+  void setAspectRatio(float aspectRatio);
+
+  float getLayoutX();
+
+  float getLayoutY();
+
+  float getLayoutWidth();
+
+  float getLayoutHeight();
+
+  boolean getDoesLegacyStretchFlagAffectsLayout();
+
+  float getLayoutMargin(YogaEdge edge);
+
+  float getLayoutPadding(YogaEdge edge);
+
+  float getLayoutBorder(YogaEdge edge);
+
+  YogaDirection getLayoutDirection();
+}

From d756d94b3a7e2812f17f549c57767ac63734b49c Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Thu, 12 Jul 2018 07:58:40 -0700
Subject: [PATCH 1021/1109] RN: Workaround for ReactNativeART on Android

Summary:
Brings back the fix for `overflow: hidden` on Android by implementing a workaround for a bug with `ReactNativeART`.

The ReactNativeART bug is that changes in the canvas due to a resize of the `Surface` are not properly reflected on Android. I have verified that the correct props are being computed and passed to the shadow nodes and that the `ARTSurfaceView`'s canvas is indeed updated. But for some reason, the paint is not updated.

This workaround is to simply unmount and remount `Surface` on Android. It sucks and we should eventually fix it.

Reviewed By: achen1

Differential Revision: D8818010

fbshipit-source-id: 71d1927580b6bde7263fd241797d4655140b5f34
---
 Libraries/ART/ReactNativeART.js                      | 12 ++++++++----
 .../facebook/react/views/view/ReactViewGroup.java    |  3 +--
 2 files changed, 9 insertions(+), 6 deletions(-)

diff --git a/Libraries/ART/ReactNativeART.js b/Libraries/ART/ReactNativeART.js
index 760b5ff809de..cf56028b102c 100644
--- a/Libraries/ART/ReactNativeART.js
+++ b/Libraries/ART/ReactNativeART.js
@@ -11,6 +11,7 @@
 
 const Color = require('art/core/color');
 const Path = require('ARTSerializablePath');
+const Platform = require('Platform');
 const Transform = require('art/core/transform');
 
 const React = require('React');
@@ -150,11 +151,14 @@ class Surface extends React.Component {
   }
 
   render() {
-    const props = this.props;
-    const w = extractNumber(props.width, 0);
-    const h = extractNumber(props.height, 0);
+    const height = extractNumber(this.props.height, 0);
+    const width = extractNumber(this.props.width, 0);
+
+    // WORKAROUND: Android bug in which canvas does not reflect size changes.
+    const key = Platform.OS === 'android' ? height + ',' + width : null;
+
     return (
-      <NativeSurfaceView style={[props.style, {width: w, height: h}]}>
+      <NativeSurfaceView key={key} style={[this.props.style, {height, width}]}>
         {this.props.children}
       </NativeSurfaceView>
     );
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index f3942754ec98..e8afaa935745 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -51,9 +51,8 @@ public class ReactViewGroup extends ViewGroup implements
 
   /**
    * Kill switch to make overflow hidden by default. This flag will eventually be removed.
-   * TODO (T31096050): Sets this back to `false` until ReactNativeARTSurface issue is resolved.
    */
-  public static boolean sDefaultOverflowHidden = true;
+  public static boolean sDefaultOverflowHidden;
 
   private static final int ARRAY_CAPACITY_INCREMENT = 12;
   private static final int DEFAULT_BACKGROUND_COLOR = Color.TRANSPARENT;

From 7eb419d4bfd9076eaf27103756b735eb3d92e629 Mon Sep 17 00:00:00 2001
From: Scott Wolchok <swolchok@fb.com>
Date: Thu, 12 Jul 2018 08:40:52 -0700
Subject: [PATCH 1022/1109] Tidy up YGFloatOptional

Summary: Just some convention/weird style things. `float` should be passed by value, weird use of ?: operator instead of ||.

Reviewed By: priteshrnandgaonkar

Differential Revision: D8804407

fbshipit-source-id: e0d67363ccde36ec5bccec7497ed0ffd364b3fcf
---
 ReactCommon/yoga/yoga/YGFloatOptional.cpp | 33 +++++++++--------------
 ReactCommon/yoga/yoga/YGFloatOptional.h   | 25 ++++++++++-------
 2 files changed, 27 insertions(+), 31 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.cpp b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
index 00bfc71e2df2..ceee1dc28176 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.cpp
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
@@ -1,16 +1,16 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #include "YGFloatOptional.h"
 #include <cstdlib>
 #include <iostream>
 #include "Yoga.h"
 
-YGFloatOptional::YGFloatOptional(const float& value) {
+YGFloatOptional::YGFloatOptional(float value) {
   if (YGFloatIsUndefined(value)) {
     isUndefined_ = true;
     value_ = 0;
@@ -31,18 +31,9 @@ const float& YGFloatOptional::getValue() const {
   return value_;
 }
 
-void YGFloatOptional::setValue(const float& val) {
-  value_ = val;
-  isUndefined_ = false;
-}
-
-const bool& YGFloatOptional::isUndefined() const {
-  return isUndefined_;
-}
-
 bool YGFloatOptional::operator==(const YGFloatOptional& op) const {
   if (isUndefined_ == op.isUndefined()) {
-    return isUndefined_ ? true : value_ == op.getValue();
+    return isUndefined_ || value_ == op.getValue();
   }
   return false;
 }
@@ -51,14 +42,14 @@ bool YGFloatOptional::operator!=(const YGFloatOptional& op) const {
   return !(*this == op);
 }
 
-bool YGFloatOptional::operator==(const float& val) const {
+bool YGFloatOptional::operator==(float val) const {
   if (YGFloatIsUndefined(val) == isUndefined_) {
-    return isUndefined_ ? true : val == value_;
+    return isUndefined_ || val == value_;
   }
   return false;
 }
 
-bool YGFloatOptional::operator!=(const float& val) const {
+bool YGFloatOptional::operator!=(float val) const {
   return !(*this == val);
 }
 
@@ -84,9 +75,9 @@ bool YGFloatOptional::operator<(const YGFloatOptional& op) const {
 }
 
 bool YGFloatOptional::operator>=(const YGFloatOptional& op) const {
-  return *this == op ? true : *this > op;
+  return *this == op || *this > op;
 }
 
 bool YGFloatOptional::operator<=(const YGFloatOptional& op) const {
-  return *this == op ? true : *this < op;
+  return *this == op || *this < op;
 }
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.h b/ReactCommon/yoga/yoga/YGFloatOptional.h
index 21af2a806198..d426d8491ec4 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.h
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.h
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #pragma once
 
 struct YGFloatOptional {
@@ -13,7 +13,7 @@ struct YGFloatOptional {
   bool isUndefined_;
 
  public:
-  explicit YGFloatOptional(const float& value);
+  explicit YGFloatOptional(float value);
   explicit YGFloatOptional();
 
   // Program will terminate if the value of an undefined is accessed. Please
@@ -22,9 +22,14 @@ struct YGFloatOptional {
   const float& getValue() const;
 
   // Sets the value of float optional, and thus isUndefined is assigned false.
-  void setValue(const float& val);
+  void setValue(float val) {
+    value_ = val;
+    isUndefined_ = false;
+  }
 
-  const bool& isUndefined() const;
+  bool isUndefined() const {
+    return isUndefined_;
+  }
 
   YGFloatOptional operator+(const YGFloatOptional& op);
   bool operator>(const YGFloatOptional& op) const;
@@ -34,6 +39,6 @@ struct YGFloatOptional {
   bool operator==(const YGFloatOptional& op) const;
   bool operator!=(const YGFloatOptional& op) const;
 
-  bool operator==(const float& val) const;
-  bool operator!=(const float& val) const;
+  bool operator==(float val) const;
+  bool operator!=(float val) const;
 };

From 934c50fbe07e49391ba27c3469f99bec65e48d39 Mon Sep 17 00:00:00 2001
From: Mehdi Mulani <mehdi@fb.com>
Date: Thu, 12 Jul 2018 10:30:27 -0700
Subject: [PATCH 1023/1109] Fix crash in RCTImagePicker on iOS

Summary:
@public
Apparently if you select images really quickly, the app will crash.

Reviewed By: shergin

Differential Revision: D8796730

fbshipit-source-id: 81a652d9c8997ee9e83bbee3378954a6718a9b5d
---
 Libraries/CameraRoll/RCTImagePickerManager.m | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/Libraries/CameraRoll/RCTImagePickerManager.m b/Libraries/CameraRoll/RCTImagePickerManager.m
index 1ee31752f2a9..4da2a6490b95 100644
--- a/Libraries/CameraRoll/RCTImagePickerManager.m
+++ b/Libraries/CameraRoll/RCTImagePickerManager.m
@@ -153,6 +153,11 @@ - (void)_presentPicker:(UIImagePickerController *)imagePicker
 - (void)_dismissPicker:(UIImagePickerController *)picker args:(NSArray *)args
 {
   NSUInteger index = [_pickers indexOfObject:picker];
+  if (index == NSNotFound) {
+    // This happens if the user selects multiple items in succession.
+    return;
+  }
+
   RCTResponseSenderBlock successCallback = _pickerCallbacks[index];
   RCTResponseSenderBlock cancelCallback = _pickerCancelCallbacks[index];
 

From f39d0923c78686118a5d268c0e659d2608d28df0 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 12 Jul 2018 12:25:07 -0700
Subject: [PATCH 1024/1109] removed tabbar for iOS 9 compatibility issues

Summary: Removed Accessibility Trait TabBar for iOS compatibility Issues, since tabbar is only available on iOS 10+

Reviewed By: PeteTheHeat

Differential Revision: D8822469

fbshipit-source-id: 34bf00eb930f631a5a4effa0a4159da07c1573f6
---
 Libraries/Components/View/ViewAccessibility.js             | 4 +---
 React/Views/RCTViewManager.m                               | 1 -
 .../facebook/react/uimanager/AccessibilityRoleUtil.java    | 7 +------
 3 files changed, 2 insertions(+), 10 deletions(-)

diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index a12528fad5fc..17ed43140e46 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -44,8 +44,7 @@ export type AccessibilityRole =
   | 'button'
   | 'image'
   | 'keyboardkey'
-  | 'text'
-  | 'tabbar';
+  | 'text';
 
 module.exports = {
   AccessibilityTraits: [
@@ -79,6 +78,5 @@ module.exports = {
     'image',
     'keyboardkey',
     'text',
-    'tabbar',
   ],
 };
diff --git a/React/Views/RCTViewManager.m b/React/Views/RCTViewManager.m
index 4443f525a6ab..602dd280d512 100644
--- a/React/Views/RCTViewManager.m
+++ b/React/Views/RCTViewManager.m
@@ -33,7 +33,6 @@ @implementation RCTConvert(UIAccessibilityTraits)
   @"header": @(UIAccessibilityTraitHeader),
   @"search": @(UIAccessibilityTraitSearchField),
   @"image": @(UIAccessibilityTraitImage),
-  @"tabbar": @(UIAccessibilityTraitTabBar),
   @"selected": @(UIAccessibilityTraitSelected),
   @"plays": @(UIAccessibilityTraitPlaysSound),
   @"key": @(UIAccessibilityTraitKeyboardKey),
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
index f063925a23b8..1635f604596b 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
@@ -33,8 +33,7 @@ public enum AccessibilityRole {
     BUTTON("android.widget.Button"),
     IMAGE("android.widget.ImageView"),
     KEYBOARD_KEY("android.inputmethodservice.Keyboard$Key"),
-    TEXT("android.widget.ViewGroup"),
-    TAB_BAR("android.widget.TabWidget");
+    TEXT("android.widget.ViewGroup");
 
     @Nullable private final String mValue;
 
@@ -90,7 +89,6 @@ public static void setRole(AccessibilityNodeInfoCompat nodeInfo, final Accessibi
   private static final String IMAGE = "image";
   private static final String KEYBOARDKEY = "keyboardkey";
   private static final String TEXT = "text";
-  private static final String TABBAR = "tabbar";
 
   public static void updateAccessibilityRole(View view, String role) {
     if (role == null) {
@@ -111,9 +109,6 @@ public static void updateAccessibilityRole(View view, String role) {
       case TEXT:
         setRole(view, AccessibilityRoleUtil.AccessibilityRole.TEXT);
         break;
-      case TABBAR:
-        setRole(view, AccessibilityRoleUtil.AccessibilityRole.TAB_BAR);
-        break;
       default:
         view.setAccessibilityDelegate(null);
     }

From 724c7498b6f10f6fd03eb217160508001fb1c5b3 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rub=C3=A9n=20Norte?= <rubennorte@fb.com>
Date: Thu, 12 Jul 2018 12:33:34 -0700
Subject: [PATCH 1025/1109] Upgraded Babel to v7.0.0-beta.48

Summary:
This is the same version we're using on www. It has support for new Flow syntax and we need it on fbsource too.

allow_many_files
allow-large-files

Differential Revision: D8819980

fbshipit-source-id: 736d6d93ad879311e638da00873ca2acf42d1422
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 66ba68b1f42b..61fcd31221a3 100644
--- a/package.json
+++ b/package.json
@@ -199,7 +199,7 @@
     "yargs": "^9.0.0"
   },
   "devDependencies": {
-    "@babel/core": "7.0.0-beta.47",
+    "@babel/core": "7.0.0-beta.48",
     "async": "^2.4.0",
     "babel-eslint": "9.0.0-beta.2",
     "babel-generator": "^6.26.0",

From 8ee60e9b0dd53701d07862571990132cf4832b5e Mon Sep 17 00:00:00 2001
From: Yuanda Tang <yuandatang@fb.com>
Date: Thu, 12 Jul 2018 13:06:44 -0700
Subject: [PATCH 1026/1109] Cleanup clang compiler warnings

Summary:
Cleanup clang compiler warnings.
The last version delete some variables that still used in code.
Fix the problem and try to launch again.

Reviewed By: hershi

Differential Revision: D8704442

fbshipit-source-id: 8bd37fc9f2b27104fe15c4c8b8323e2bfd8c1060
---
 ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp | 1 -
 1 file changed, 1 deletion(-)

diff --git a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
index 10a3fb826823..fdb0f5544a3e 100644
--- a/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
+++ b/ReactAndroid/src/main/jni/react/jni/CatalystInstanceImpl.cpp
@@ -42,7 +42,6 @@ namespace {
 
 class Exception : public jni::JavaClass<Exception> {
  public:
-  static auto constexpr kJavaDescriptor = "Ljava/lang/Exception;";
 };
 
 class JInstanceCallback : public InstanceCallback {

From a2675ced4efe0df7745bf38908efa41d4d7a9841 Mon Sep 17 00:00:00 2001
From: Michael Ficaro <mficaro@fb.com>
Date: Thu, 12 Jul 2018 13:36:50 -0700
Subject: [PATCH 1027/1109] Adding new styling props to
 FlatList/VirtualizedList for ListHeaderComponent and ListFooterComponent

Summary:
We ran into a problem trying to style the optional prop `ListHeaderComponent` in the `FlatList` library component. Essentially we wanted to make `ListHeaderComponent` a flex item that filled all of the empty space in the list if there was any. Unfortunately the `ListHeaderComponent` is later wrapped in a `View` that blocked our styling. The `View` component was necessary as it added styling to handle inverting the `FlatList`. Similarly `ListFooterComponent` was handled the same way.

We came up the simple solution of adding two new optional props, `ListHeaderComponentStyle` and `ListFooterComponentStyle`, that are of type `ViewStyleProp` that allow users to pass in styling for `ListHeaderComponent` and `ListFooterComponent`.

With this change we were able to do something like the following to get the header component to fill all empty space in the `FlatList`.

```
<FlatList
    ...
    contentContainerStyle={{flexGrow: 1}}
    ListHeaderComponent={<View style={{flex: 1}} />}
    ListHeaderComponentStyle={{flexGrow: 1}}
    ...
/>
```
This solution will give users a lot more freedom when working with headers and footers.

Reviewed By: sahrens

Differential Revision: D8777038

fbshipit-source-id: f34116ce68548ea70223e639d0f84a099327f6b3
---
 Libraries/Lists/FlatList.js                   | 10 +++++++-
 Libraries/Lists/VirtualizedList.js            | 24 ++++++++++++++++---
 .../__snapshots__/FlatList-test.js.snap       |  2 --
 .../__snapshots__/SectionList-test.js.snap    |  2 --
 .../VirtualizedList-test.js.snap              |  2 --
 5 files changed, 30 insertions(+), 10 deletions(-)

diff --git a/Libraries/Lists/FlatList.js b/Libraries/Lists/FlatList.js
index cfa4ae858088..adebd267f7f6 100644
--- a/Libraries/Lists/FlatList.js
+++ b/Libraries/Lists/FlatList.js
@@ -18,7 +18,7 @@ const StyleSheet = require('StyleSheet');
 
 const invariant = require('fbjs/lib/invariant');
 
-import type {DangerouslyImpreciseStyleProp} from 'StyleSheet';
+import type {DangerouslyImpreciseStyleProp, ViewStyleProp} from 'StyleSheet';
 import type {
   ViewabilityConfig,
   ViewToken,
@@ -88,11 +88,19 @@ type OptionalProps<ItemT> = {
    * a rendered element.
    */
   ListFooterComponent?: ?(React.ComponentType<any> | React.Element<any>),
+  /**
+   * Styling for internal View for ListFooterComponent
+   */
+  ListFooterComponentStyle?: ViewStyleProp,
   /**
    * Rendered at the top of all the items. Can be a React Component Class, a render function, or
    * a rendered element.
    */
   ListHeaderComponent?: ?(React.ComponentType<any> | React.Element<any>),
+  /**
+   * Styling for internal View for ListHeaderComponent
+   */
+  ListHeaderComponentStyle?: ViewStyleProp,
   /**
    * Optional custom style for multi-item rows generated when numColumns > 1.
    */
diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index 56364823f06d..ba9224c4665f 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -31,7 +31,7 @@ const warning = require('fbjs/lib/warning');
 
 const {computeWindowedRenderLimits} = require('VirtualizeUtils');
 
-import type {DangerouslyImpreciseStyleProp} from 'StyleSheet';
+import type {DangerouslyImpreciseStyleProp, ViewStyleProp} from 'StyleSheet';
 import type {
   ViewabilityConfig,
   ViewToken,
@@ -124,11 +124,19 @@ type OptionalProps = {
    * a rendered element.
    */
   ListFooterComponent?: ?(React.ComponentType<any> | React.Element<any>),
+  /**
+   * Styling for internal View for ListFooterComponent
+   */
+  ListFooterComponentStyle?: ViewStyleProp,
   /**
    * Rendered at the top of all the items. Can be a React Component Class, a render function, or
    * a rendered element.
    */
   ListHeaderComponent?: ?(React.ComponentType<any> | React.Element<any>),
+  /**
+   * Styling for internal View for ListHeaderComponent
+   */
+  ListHeaderComponentStyle?: ViewStyleProp,
   /**
    * A unique identifier for this list. If there are multiple VirtualizedLists at the same level of
    * nesting within another VirtualizedList, this key is necessary for virtualization to
@@ -756,7 +764,12 @@ class VirtualizedList extends React.PureComponent<Props, State> {
         <VirtualizedCellWrapper
           cellKey={this._getCellKey() + '-header'}
           key="$header">
-          <View onLayout={this._onLayoutHeader} style={inversionStyle}>
+          <View
+            onLayout={this._onLayoutHeader}
+            style={StyleSheet.compose(
+              inversionStyle,
+              this.props.ListHeaderComponentStyle,
+            )}>
             {
               // $FlowFixMe - Typing ReactNativeComponent revealed errors
               element
@@ -892,7 +905,12 @@ class VirtualizedList extends React.PureComponent<Props, State> {
         <VirtualizedCellWrapper
           cellKey={this._getCellKey() + '-footer'}
           key="$footer">
-          <View onLayout={this._onLayoutFooter} style={inversionStyle}>
+          <View
+            onLayout={this._onLayoutFooter}
+            style={StyleSheet.compose(
+              inversionStyle,
+              this.props.ListFooterComponentStyle,
+            )}>
             {
               // $FlowFixMe - Typing ReactNativeComponent revealed errors
               element
diff --git a/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap b/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
index d6d008065b24..7f523be29ac8 100644
--- a/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
+++ b/Libraries/Lists/__tests__/__snapshots__/FlatList-test.js.snap
@@ -60,7 +60,6 @@ exports[`FlatList renders all the bells and whistles 1`] = `
   <View>
     <View
       onLayout={[Function]}
-      style={null}
     >
       <header />
     </View>
@@ -119,7 +118,6 @@ exports[`FlatList renders all the bells and whistles 1`] = `
     </View>
     <View
       onLayout={[Function]}
-      style={null}
     >
       <footer />
     </View>
diff --git a/Libraries/Lists/__tests__/__snapshots__/SectionList-test.js.snap b/Libraries/Lists/__tests__/__snapshots__/SectionList-test.js.snap
index f47dd4e8d626..b15b3cb3dd71 100644
--- a/Libraries/Lists/__tests__/__snapshots__/SectionList-test.js.snap
+++ b/Libraries/Lists/__tests__/__snapshots__/SectionList-test.js.snap
@@ -341,7 +341,6 @@ exports[`SectionList renders all the bells and whistles 1`] = `
   <View>
     <View
       onLayout={[Function]}
-      style={null}
     >
       <header
         v=""
@@ -484,7 +483,6 @@ exports[`SectionList renders all the bells and whistles 1`] = `
     </View>
     <View
       onLayout={[Function]}
-      style={null}
     >
       <footer
         v=""
diff --git a/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap b/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
index cb1a86d71805..2ae233201f72 100644
--- a/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
+++ b/Libraries/Lists/__tests__/__snapshots__/VirtualizedList-test.js.snap
@@ -665,14 +665,12 @@ exports[`VirtualizedList renders empty list with empty component 1`] = `
   <View>
     <View
       onLayout={[Function]}
-      style={null}
     >
       <header />
     </View>
     <empty />
     <View
       onLayout={[Function]}
-      style={null}
     >
       <footer />
     </View>

From 6ed6bffe4ea0f42a400a8939e45fc99e6de8286d Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Thu, 12 Jul 2018 16:25:40 -0700
Subject: [PATCH 1028/1109] RN: Ignore Unused Rest Property Siblings

Summary:
Configures ESLint to allow unused variables that are the sibling of a rest property.

For example:

```
// It is okay for `type` to be unused.
const {type, ...coords} = data;
```

Reviewed By: TheSavior

Differential Revision: D8779952

fbshipit-source-id: 1f7b756a75d9363b85e05209ce2a9bb536c5d4da
---
 .eslintrc | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/.eslintrc b/.eslintrc
index 395f7d824349..e05c065a0bb4 100644
--- a/.eslintrc
+++ b/.eslintrc
@@ -143,7 +143,7 @@
     "no-undef": 2,                   // disallow use of undeclared variables unless mentioned in a /*global */ block
     "no-undefined": 0,               // disallow use of undefined variable (off by default)
     "no-undef-init": 1,              // disallow use of undefined when initializing variables
-    "no-unused-vars": [1, {"vars": "all", "args": "none"}], // disallow declaration of variables that are not used in the code
+    "no-unused-vars": [1, {"vars": "all", "args": "none", ignoreRestSiblings: true}], // disallow declaration of variables that are not used in the code
     "no-use-before-define": 0,       // disallow use of variables before they are defined
 
   // Node.js

From d0b86ecb4f33d6b10a99062f050a4d659db4ddfc Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 12 Jul 2018 23:35:56 -0700
Subject: [PATCH 1029/1109] added in the three roles: search, adjustable, link
 that require localization

Summary:
Added in props for three more roles:
link, search, and adjustable

Reviewed By: blavalla

Differential Revision: D8788186

fbshipit-source-id: acd1d667a43bea753964d128bd4525ece90d06b3
---
 Libraries/Components/View/ViewAccessibility.js | 8 +++++++-
 1 file changed, 7 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index 17ed43140e46..410994b2b208 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -42,9 +42,12 @@ export type AccessibilityComponentType =
 export type AccessibilityRole =
   | 'none'
   | 'button'
+  | 'link'
+  | 'search'
   | 'image'
   | 'keyboardkey'
-  | 'text';
+  | 'text'
+  | 'adjustable';
 
 module.exports = {
   AccessibilityTraits: [
@@ -75,8 +78,11 @@ module.exports = {
   AccessibilityRoles: [
     'none',
     'button',
+    'link',
+    'search',
     'image',
     'keyboardkey',
     'text',
+    'adjustable',
   ],
 };

From e7391438093cd5dd5033204cdce62e66509e66e1 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 12 Jul 2018 23:35:57 -0700
Subject: [PATCH 1030/1109] added in the three roles: search, adjustable, link
 that require localization

Summary:
Added the android functionality for those three roles: search, adjustable, and link.
Until React Native internal framework ports internationalization and localization of strings, I'll handle localization by allowing an extra prop to be passed in that can override talkback's description in another language if needed.

Reviewed By: blavalla

Differential Revision: D8807692

fbshipit-source-id: b51877d187cb6cb663d65d6b4d072e6dc52a2d03
---
 .../uimanager/AccessibilityRoleUtil.java      | 50 +++++++++----------
 1 file changed, 24 insertions(+), 26 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
index 1635f604596b..86095befc24f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
@@ -31,9 +31,12 @@ public class AccessibilityRoleUtil {
   public enum AccessibilityRole {
     NONE(null),
     BUTTON("android.widget.Button"),
+    LINK("android.widget.Button"),
+    SEARCH("android.widget.EditText"),
     IMAGE("android.widget.ImageView"),
-    KEYBOARD_KEY("android.inputmethodservice.Keyboard$Key"),
-    TEXT("android.widget.ViewGroup");
+    KEYBOARDKEY("android.inputmethodservice.Keyboard$Key"),
+    TEXT("android.widget.ViewGroup"),
+    ADJUSTABLE("android.widget.SeekBar");
 
     @Nullable private final String mValue;
 
@@ -79,38 +82,33 @@ public void onInitializeAccessibilityNodeInfo(
 
   public static void setRole(AccessibilityNodeInfoCompat nodeInfo, final AccessibilityRole role) {
     nodeInfo.setClassName(role.getValue());
+    if (role.equals(AccessibilityRole.LINK)) {
+      nodeInfo.setRoleDescription("Link");
+    }
+    if (role.equals(AccessibilityRole.SEARCH)) {
+      nodeInfo.setRoleDescription("Search Field");
+    }
+    if (role.equals(AccessibilityRole.IMAGE)) {
+      nodeInfo.setRoleDescription("Image");
+    }
+    if (role.equals(AccessibilityRole.ADJUSTABLE)) {
+      nodeInfo.setRoleDescription("Adjustable");
+    }
   }
-
+  
   /**
    * Variables and methods for setting accessibilityRole on view properties.
    */
-  private static final String NONE = "none";
-  private static final String BUTTON = "button";
-  private static final String IMAGE = "image";
-  private static final String KEYBOARDKEY = "keyboardkey";
-  private static final String TEXT = "text";
-
   public static void updateAccessibilityRole(View view, String role) {
     if (role == null) {
       view.setAccessibilityDelegate(null);
     }
-    switch (role) {
-      case NONE:
-        break;
-      case BUTTON:
-        setRole(view, AccessibilityRoleUtil.AccessibilityRole.BUTTON);
-        break;
-      case IMAGE:
-        setRole(view, AccessibilityRoleUtil.AccessibilityRole.IMAGE);
-        break;
-      case KEYBOARDKEY:
-        setRole(view, AccessibilityRoleUtil.AccessibilityRole.KEYBOARD_KEY);
-        break;
-      case TEXT:
-        setRole(view, AccessibilityRoleUtil.AccessibilityRole.TEXT);
-        break;
-      default:
-        view.setAccessibilityDelegate(null);
+    try {
+      setRole(view, AccessibilityRole.valueOf(role.toUpperCase()));
+    } catch (NullPointerException e) {
+      view.setAccessibilityDelegate(null);
+    } catch (IllegalArgumentException e) {
+      view.setAccessibilityDelegate(null);
     }
   }
 }

From e589595bc93077ff2607fa978c42e109449b80d4 Mon Sep 17 00:00:00 2001
From: Scott Wolchok <swolchok@fb.com>
Date: Fri, 13 Jul 2018 12:34:46 -0700
Subject: [PATCH 1031/1109] YGNode::getChildren() should return const ref

Summary:
It's wasteful to do it by value. I'm fairly sure this is
safe, especially because
https://github.com/facebook/yoga/commit/fbd332dee86237cae6f9c9bae8ea9a7bbe7c7d87#diff-ade2a4bbd6582e2898cbd9e0fa142ab5R215
shows that we did access by reference before.

Reviewed By: priteshrnandgaonkar, davidaurelio

Differential Revision: D8822697

fbshipit-source-id: 791bcf0fa37453f67795af727c85c8adce3b0f69
---
 ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp | 2 +-
 ReactCommon/yoga/yoga/YGNode.h                            | 6 +-----
 ReactCommon/yoga/yoga/Yoga.cpp                            | 8 ++++----
 3 files changed, 6 insertions(+), 10 deletions(-)

diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 5941baa057ba..69ed311158a1 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -94,7 +94,7 @@ void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child)
 
   auto yogaNodeRawPtr = &yogaNode_;
   auto childYogaNodeRawPtr = &child->yogaNode_;
-  yogaNodeRawPtr->insertChild(childYogaNodeRawPtr, yogaNodeRawPtr->getChildrenCount());
+  yogaNodeRawPtr->insertChild(childYogaNodeRawPtr, yogaNodeRawPtr->getChildren().size());
 
   if (childYogaNodeRawPtr->getOwner() == nullptr) {
     child->ensureUnsealed();
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index ab302e06727e..c204d4600b15 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -122,14 +122,10 @@ struct YGNode {
     return getOwner();
   }
   
-  YGVector getChildren() const {
+  const YGVector& getChildren() const {
     return children_;
   }
   
-  uint32_t getChildrenCount() const {
-    return static_cast<uint32_t>(children_.size());
-  }
-  
   YGNodeRef getChild(uint32_t index) const {
     return children_.at(index);
   }
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 5b5a90888cea..df186c7c3a67 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -264,7 +264,7 @@ static YGNodeRef YGNodeDeepClone(YGNodeRef oldNode) {
   YGVector vec = YGVector();
   vec.reserve(oldNode->getChildren().size());
   YGNodeRef childNode = nullptr;
-  for (auto& item : oldNode->getChildren()) {
+  for (auto* item : oldNode->getChildren()) {
     childNode = YGNodeDeepClone(item);
     childNode->setOwner(node);
     vec.push_back(childNode);
@@ -301,8 +301,8 @@ static void YGConfigFreeRecursive(const YGNodeRef root) {
     delete root->getConfig();
   }
   // Delete configs recursively for childrens
-  for (uint32_t i = 0; i < root->getChildrenCount(); ++i) {
-    YGConfigFreeRecursive(root->getChild(i));
+  for (auto* child : root->getChildren()) {
+    YGConfigFreeRecursive(child);
   }
 }
 
@@ -1868,7 +1868,7 @@ static YGCollectFlexItemsRowValues YGCalculateCollectFlexItemsRowValues(
 
   // Add items to the current line until it's full or we run out of items.
   uint32_t endOfLineIndex = startOfLineIndex;
-  for (; endOfLineIndex < node->getChildrenCount(); endOfLineIndex++) {
+  for (; endOfLineIndex < node->getChildren().size(); endOfLineIndex++) {
     const YGNodeRef child = node->getChild(endOfLineIndex);
     if (child->getStyle().display == YGDisplayNone ||
         child->getStyle().positionType == YGPositionTypeAbsolute) {

From 727ee92de5b3ba7bb641f452482d7800f05131bd Mon Sep 17 00:00:00 2001
From: Scott Wolchok <swolchok@fb.com>
Date: Fri, 13 Jul 2018 12:34:49 -0700
Subject: [PATCH 1032/1109] Tidy up YGFloatOptional further

Summary: I missed these two things: inline default ctor, getValue() should return a float.

Reviewed By: priteshrnandgaonkar

Differential Revision: D8826640

fbshipit-source-id: e6324dea0268ef276e6fa1722e72dffb5241e676
---
 ReactCommon/yoga/yoga/YGFloatOptional.cpp | 4 +---
 ReactCommon/yoga/yoga/YGFloatOptional.h   | 4 ++--
 2 files changed, 3 insertions(+), 5 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.cpp b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
index ceee1dc28176..d3407fa23cbb 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.cpp
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
@@ -20,9 +20,7 @@ YGFloatOptional::YGFloatOptional(float value) {
   }
 }
 
-YGFloatOptional::YGFloatOptional() : value_(0), isUndefined_(true) {}
-
-const float& YGFloatOptional::getValue() const {
+float YGFloatOptional::getValue() const {
   if (isUndefined_) {
     // Abort, accessing a value of an undefined float optional
     std::cerr << "Tried to get value of an undefined YGFloatOptional\n";
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.h b/ReactCommon/yoga/yoga/YGFloatOptional.h
index d426d8491ec4..114f3577a92c 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.h
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.h
@@ -14,12 +14,12 @@ struct YGFloatOptional {
 
  public:
   explicit YGFloatOptional(float value);
-  explicit YGFloatOptional();
+  explicit YGFloatOptional() : value_(0), isUndefined_(true) {}
 
   // Program will terminate if the value of an undefined is accessed. Please
   // make sure to check if the optional is defined before calling this function.
   // To check if float optional is defined, use `isUndefined()`.
-  const float& getValue() const;
+  float getValue() const;
 
   // Sets the value of float optional, and thus isUndefined is assigned false.
   void setValue(float val) {

From 6ab52ff90d9ddf3e88dbe9619c8672bf13e6c85e Mon Sep 17 00:00:00 2001
From: Scott Wolchok <swolchok@fb.com>
Date: Fri, 13 Jul 2018 12:34:51 -0700
Subject: [PATCH 1033/1109] Remove some unnecessary `const float &` uses

Summary: Holding floats by reference is unnecessary at best and may be detrimental to performance.

Reviewed By: davidaurelio

Differential Revision: D8826496

fbshipit-source-id: 2391f8aa26ebfbb440f6e4b7d57975be688f791c
---
 ReactCommon/yoga/yoga/Yoga.cpp | 12 ++++++------
 1 file changed, 6 insertions(+), 6 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index df186c7c3a67..1ea109e29353 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -1249,9 +1249,9 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
     childWidthMeasureMode = YGMeasureModeUndefined;
     childHeightMeasureMode = YGMeasureModeUndefined;
 
-    const float& marginRow = YGUnwrapFloatOptional(
+    auto marginRow = YGUnwrapFloatOptional(
         child->getMarginForAxis(YGFlexDirectionRow, ownerWidth));
-    const float& marginColumn = YGUnwrapFloatOptional(
+    auto marginColumn = YGUnwrapFloatOptional(
         child->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
 
     if (isRowStyleDimDefined) {
@@ -1377,9 +1377,9 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
   YGMeasureMode childWidthMeasureMode = YGMeasureModeUndefined;
   YGMeasureMode childHeightMeasureMode = YGMeasureModeUndefined;
 
-  const float& marginRow =
+  auto marginRow =
       YGUnwrapFloatOptional(child->getMarginForAxis(YGFlexDirectionRow, width));
-  const float& marginColumn = YGUnwrapFloatOptional(
+  auto marginColumn = YGUnwrapFloatOptional(
       child->getMarginForAxis(YGFlexDirectionColumn, width));
 
   if (YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, width)) {
@@ -1679,9 +1679,9 @@ static bool YGNodeFixedSizeSetMeasuredDimensions(const YGNodeRef node,
        heightMeasureMode == YGMeasureModeAtMost && availableHeight <= 0.0f) ||
       (widthMeasureMode == YGMeasureModeExactly &&
        heightMeasureMode == YGMeasureModeExactly)) {
-    const float& marginAxisColumn = YGUnwrapFloatOptional(
+    auto marginAxisColumn = YGUnwrapFloatOptional(
         node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
-    const float& marginAxisRow = YGUnwrapFloatOptional(
+    auto marginAxisRow = YGUnwrapFloatOptional(
         node->getMarginForAxis(YGFlexDirectionRow, ownerWidth));
 
     node->setLayoutMeasuredDimension(

From 6b1d99686d09ec6a73ecc440b785ee74cc972ac1 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Fri, 13 Jul 2018 14:54:02 -0700
Subject: [PATCH 1034/1109] Skylarkify jni_instrumentation_test.

Summary: https://our.intern.facebook.com/intern/wiki/Buck/python-to-skylark/

Reviewed By: mzlee

Differential Revision: D8842575

fbshipit-source-id: 2de5efa8b00397e751f6c213b8c8630deea21f00
---
 ReactCommon/cxxreact/tests/BUCK | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactCommon/cxxreact/tests/BUCK b/ReactCommon/cxxreact/tests/BUCK
index f7a3416fd486..389a909f1a80 100644
--- a/ReactCommon/cxxreact/tests/BUCK
+++ b/ReactCommon/cxxreact/tests/BUCK
@@ -12,7 +12,7 @@ TEST_SRCS = [
 
 if not IS_OSS_BUILD:
     load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-    load("@xplat//configurations/buck/android:jni_instrumentation_test", "jni_instrumentation_test_lib")
+    load("@xplat//configurations/buck/android:jni_instrumentation_test.bzl", "jni_instrumentation_test_lib")
     load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
 
     jni_instrumentation_test_lib(

From 662c5bfd264d7f4c2f5ce2ec6e500257cbe451c2 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Sat, 14 Jul 2018 17:22:26 -0700
Subject: [PATCH 1035/1109] Skylarkify ReactNative build defs.

Summary: https://buckbuild.com/concept/skylark.html

Reviewed By: mzlee

Differential Revision: D8823004

fbshipit-source-id: 164be349782862bf83f5bdf2c869bf10713d5dfe
---
 ReactAndroid/src/main/jni/first-party/fb/BUCK | 53 +++++++------
 .../src/main/jni/first-party/yogajni/BUCK     | 41 +++++-----
 .../src/main/jni/third-party/android-ndk/BUCK | 24 ------
 .../test/java/com/facebook/react/fabric/BUCK  | 77 +++++++++----------
 ReactNative/DEFS.bzl                          |  3 +
 5 files changed, 89 insertions(+), 109 deletions(-)
 delete mode 100644 ReactAndroid/src/main/jni/third-party/android-ndk/BUCK

diff --git a/ReactAndroid/src/main/jni/first-party/fb/BUCK b/ReactAndroid/src/main/jni/first-party/fb/BUCK
index c25f868d73ea..a5c9dc0ab6cf 100644
--- a/ReactAndroid/src/main/jni/first-party/fb/BUCK
+++ b/ReactAndroid/src/main/jni/first-party/fb/BUCK
@@ -1,27 +1,30 @@
-load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "JNI_TARGET", "cxx_library", "subdir_glob")
+load("//ReactNative:DEFS.bzl", "JNI_TARGET", "subdir_glob", "oss_cxx_library")
 
 # This target is only used in open source
-if IS_OSS_BUILD:
-    cxx_library(
-        name = "jni",
-        soname = "libfb.$(ext)",
-        srcs = glob(["*.cpp", "jni/*.cpp", "lyra/*.cpp"]),
-        header_namespace = "",
-        compiler_flags = [
-            "-fno-omit-frame-pointer",
-            "-fexceptions",
-            "-Wall",
-            "-Werror",
-            "-std=c++11",
-            "-DDISABLE_CPUCAP",
-            "-DDISABLE_XPLAT",
-        ],
-        exported_headers = subdir_glob([
-            ("include", "fb/**/*.h"),
-            ("include", "jni/*.h"),
-        ]),
-        deps = [
-            JNI_TARGET,
-        ],
-        visibility = ["PUBLIC"],
-    )
+oss_cxx_library(
+    name = "jni",
+    srcs = glob([
+        "*.cpp",
+        "jni/*.cpp",
+        "lyra/*.cpp",
+    ]),
+    header_namespace = "",
+    exported_headers = subdir_glob([
+        ("include", "fb/**/*.h"),
+        ("include", "jni/*.h"),
+    ]),
+    compiler_flags = [
+        "-fno-omit-frame-pointer",
+        "-fexceptions",
+        "-Wall",
+        "-Werror",
+        "-std=c++11",
+        "-DDISABLE_CPUCAP",
+        "-DDISABLE_XPLAT",
+    ],
+    soname = "libfb.$(ext)",
+    visibility = ["PUBLIC"],
+    deps = [
+        JNI_TARGET,
+    ],
+)
diff --git a/ReactAndroid/src/main/jni/first-party/yogajni/BUCK b/ReactAndroid/src/main/jni/first-party/yogajni/BUCK
index 2bf3af1fb2f1..0297303fb1a1 100644
--- a/ReactAndroid/src/main/jni/first-party/yogajni/BUCK
+++ b/ReactAndroid/src/main/jni/first-party/yogajni/BUCK
@@ -1,23 +1,22 @@
-load("//ReactNative:DEFS.bzl", "FBJNI_TARGET", "IS_OSS_BUILD", "cxx_library")
+load("//ReactNative:DEFS.bzl", "FBJNI_TARGET", "oss_cxx_library")
 
 # This target is only used in open source
-if IS_OSS_BUILD:
-    cxx_library(
-        name = "jni",
-        soname = "libyoga.$(ext)",
-        srcs = glob(["jni/*.cpp"]),
-        header_namespace = "",
-        compiler_flags = [
-            "-fno-omit-frame-pointer",
-            "-fexceptions",
-            "-Wall",
-            "-Werror",
-            "-O3",
-            "-std=c++11",
-        ],
-        deps = [
-            "//ReactCommon/yoga:yoga",
-            FBJNI_TARGET,
-        ],
-        visibility = ["PUBLIC"],
-    )
+oss_cxx_library(
+    name = "jni",
+    srcs = glob(["jni/*.cpp"]),
+    header_namespace = "",
+    compiler_flags = [
+        "-fno-omit-frame-pointer",
+        "-fexceptions",
+        "-Wall",
+        "-Werror",
+        "-O3",
+        "-std=c++11",
+    ],
+    soname = "libyoga.$(ext)",
+    visibility = ["PUBLIC"],
+    deps = [
+        "//ReactCommon/yoga:yoga",
+        FBJNI_TARGET,
+    ],
+)
diff --git a/ReactAndroid/src/main/jni/third-party/android-ndk/BUCK b/ReactAndroid/src/main/jni/third-party/android-ndk/BUCK
deleted file mode 100644
index dc57bd80dc85..000000000000
--- a/ReactAndroid/src/main/jni/third-party/android-ndk/BUCK
+++ /dev/null
@@ -1,24 +0,0 @@
-# NOTE(agallagher): The platform should really be responsible for providing
-# this type of implicit dependency.  As it is now, we need to setup a dummy
-# rules to model the Android NDK's built in libraries.
-
-LIBS = (
-    "android",
-    "EGL",
-    "GLESv2",
-    "jnigraphics",
-    "log",
-    "z",
-)
-
-for lib in LIBS:
-    prebuilt_cxx_library(
-        name = lib,
-        header_only = True,
-        exported_platform_linker_flags = [
-            ("android.*", ["-l" + lib]),
-        ],
-        visibility = [
-            "PUBLIC",
-        ],
-    )
diff --git a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
index 874e64a7ec8a..688ffe6726ae 100644
--- a/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
+++ b/ReactAndroid/src/test/java/com/facebook/react/fabric/BUCK
@@ -1,41 +1,40 @@
 load("//ReactNative:DEFS.bzl", "IS_OSS_BUILD", "YOGA_TARGET", "react_native_dep", "react_native_target", "react_native_tests_target", "rn_robolectric_test")
 
-if not IS_OSS_BUILD:
-    rn_robolectric_test(
-        name = "fabric",
-        srcs = glob(["**/*.java"]),
-        contacts = ["oncall+fbandroid_sheriff@xmail.facebook.com"],
-        resources = glob([
-            "**/*.txt",
-            "**/*.json",
-        ]),
-        visibility = [
-            "PUBLIC",
-        ],
-        deps = [
-            "xplat//yoga/java:java",
-            react_native_dep("third-party/java/assertj:assertj-core"),
-            react_native_dep("third-party/java/fest:fest"),
-            react_native_dep("third-party/java/fest:fest_android"),
-            react_native_dep("third-party/java/guava:guava"),
-            react_native_dep("third-party/java/jackson:jackson"),
-            react_native_dep("third-party/java/jsr-305:jsr-305"),
-            react_native_dep("third-party/java/jsr-330:jsr-330"),
-            react_native_dep("third-party/java/junit:junit"),
-            react_native_dep("third-party/java/mockito:mockito"),
-            react_native_dep("third-party/java/robolectric3/robolectric:robolectric"),
-            react_native_dep("libraries/fbcore/src/test/java/com/facebook/powermock:powermock"),
-            react_native_dep("libraries/soloader/java/com/facebook/soloader:soloader"),
-            react_native_dep("third-party/android/support/v4:lib-support-v4"),
-            react_native_target("java/com/facebook/react:react"),
-            react_native_target("java/com/facebook/react/bridge:bridge"),
-            react_native_target("java/com/facebook/react/common:common"),
-            react_native_target("java/com/facebook/react/fabric:fabric"),
-            react_native_target("java/com/facebook/react/modules/core:core"),
-            react_native_target("java/com/facebook/react/uimanager:uimanager"),
-            react_native_target("java/com/facebook/react/views/text:text"),
-            react_native_target("java/com/facebook/react/views/view:view"),
-            react_native_target("java/com/facebook/react/views/progressbar:progressbar"),
-            react_native_tests_target("java/com/facebook/react/bridge:testhelpers"),
-        ],
-    )
+rn_robolectric_test(
+    name = "fabric",
+    srcs = glob(["**/*.java"]),
+    contacts = ["oncall+fbandroid_sheriff@xmail.facebook.com"],
+    resources = glob([
+        "**/*.txt",
+        "**/*.json",
+    ]),
+    visibility = [
+        "PUBLIC",
+    ],
+    deps = [
+        "xplat//yoga/java:java",
+        react_native_dep("third-party/java/assertj:assertj-core"),
+        react_native_dep("third-party/java/fest:fest"),
+        react_native_dep("third-party/java/fest:fest_android"),
+        react_native_dep("third-party/java/guava:guava"),
+        react_native_dep("third-party/java/jackson:jackson"),
+        react_native_dep("third-party/java/jsr-305:jsr-305"),
+        react_native_dep("third-party/java/jsr-330:jsr-330"),
+        react_native_dep("third-party/java/junit:junit"),
+        react_native_dep("third-party/java/mockito:mockito"),
+        react_native_dep("third-party/java/robolectric3/robolectric:robolectric"),
+        react_native_dep("libraries/fbcore/src/test/java/com/facebook/powermock:powermock"),
+        react_native_dep("libraries/soloader/java/com/facebook/soloader:soloader"),
+        react_native_dep("third-party/android/support/v4:lib-support-v4"),
+        react_native_target("java/com/facebook/react:react"),
+        react_native_target("java/com/facebook/react/bridge:bridge"),
+        react_native_target("java/com/facebook/react/common:common"),
+        react_native_target("java/com/facebook/react/fabric:fabric"),
+        react_native_target("java/com/facebook/react/modules/core:core"),
+        react_native_target("java/com/facebook/react/uimanager:uimanager"),
+        react_native_target("java/com/facebook/react/views/text:text"),
+        react_native_target("java/com/facebook/react/views/view:view"),
+        react_native_target("java/com/facebook/react/views/progressbar:progressbar"),
+        react_native_tests_target("java/com/facebook/react/bridge:testhelpers"),
+    ],
+) if not IS_OSS_BUILD else None
diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index 711688eb4f9f..451675f2862f 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -260,3 +260,6 @@ def _single_subdir_glob(dirpath, glob_pattern, exclude = None, prefix = None):
         results[key] = f
 
     return results
+
+def oss_cxx_library(**kwargs):
+    cxx_library(**kwargs)

From 12d98db901036e789072a03d5657b14d5cb2bd82 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Sat, 14 Jul 2018 18:21:39 -0700
Subject: [PATCH 1036/1109] Fix conditional load usage.

Summary:
Conditional `load` statements are not allowed in new Buck build file parser - Skylark.
https://buckbuild.com/concept/skylark.html

Reviewed By: mzlee

Differential Revision: D8842756

fbshipit-source-id: f22dff00f594978e4cab5736268ad3225182c39b
---
 ReactCommon/cxxreact/tests/BUCK           | 89 ++++++++++++-----------
 ReactCommon/fabric/activityindicator/BUCK | 48 +++++-------
 ReactCommon/fabric/attributedstring/BUCK  | 59 +++++++--------
 ReactCommon/fabric/components/image/BUCK  | 59 +++++++--------
 ReactCommon/fabric/components/switch/BUCK | 59 +++++++--------
 ReactCommon/fabric/core/BUCK              | 49 +++++--------
 ReactCommon/fabric/debug/BUCK             | 66 +++++++++--------
 ReactCommon/fabric/graphics/BUCK          | 59 +++++++--------
 ReactCommon/fabric/imagemanager/BUCK      | 59 +++++++--------
 ReactCommon/fabric/scrollview/BUCK        | 59 +++++++--------
 ReactCommon/fabric/text/BUCK              | 59 +++++++--------
 ReactCommon/fabric/textlayoutmanager/BUCK | 59 +++++++--------
 ReactCommon/fabric/uimanager/BUCK         | 59 +++++++--------
 ReactCommon/fabric/view/BUCK              | 59 +++++++--------
 ReactNative/DEFS.bzl                      |  8 ++
 15 files changed, 429 insertions(+), 421 deletions(-)

diff --git a/ReactCommon/cxxreact/tests/BUCK b/ReactCommon/cxxreact/tests/BUCK
index 389a909f1a80..24acdd3ad4c5 100644
--- a/ReactCommon/cxxreact/tests/BUCK
+++ b/ReactCommon/cxxreact/tests/BUCK
@@ -1,4 +1,12 @@
-load("//ReactNative:DEFS.bzl", "ANDROID_JSC_DEPS", "APPLE_JSC_DEPS", "IS_OSS_BUILD", "react_native_xplat_target")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID_JSC_DEPS",
+    "APPLE",
+    "APPLE_JSC_DEPS",
+    "react_native_xplat_target",
+    "jni_instrumentation_test_lib",
+    "fb_xplat_cxx_test",
+)
 
 TEST_SRCS = [
     "RecoverableErrorTest.cpp",
@@ -10,46 +18,41 @@ TEST_SRCS = [
     "value.cpp",
 ]
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-    load("@xplat//configurations/buck/android:jni_instrumentation_test.bzl", "jni_instrumentation_test_lib")
-    load("@xplat//configurations/buck:default_platform_defs.bzl", "APPLE")
+jni_instrumentation_test_lib(
+    name = "tests",
+    srcs = TEST_SRCS,
+    class_under_test = "com/facebook/react/XplatBridgeTest",
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+    ],
+    soname = "libxplat-bridge.so",
+    visibility = [
+        "fbandroid//instrumentation_tests/...",
+    ],
+    deps = [
+        "xplat//third-party/linker_lib:android",
+        "xplat//third-party/gmock:gtest",
+        react_native_xplat_target("cxxreact:bridge"),
+    ] + ANDROID_JSC_DEPS,
+)
 
-    jni_instrumentation_test_lib(
-        name = "tests",
-        class_under_test = "com/facebook/react/XplatBridgeTest",
-        soname = "libxplat-bridge.so",
-        srcs = TEST_SRCS,
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-        ],
-        deps = [
-            "xplat//third-party/linker_lib:android",
-            "xplat//third-party/gmock:gtest",
-            react_native_xplat_target("cxxreact:bridge"),
-        ] + ANDROID_JSC_DEPS,
-        visibility = [
-            "fbandroid//instrumentation_tests/...",
-        ],
-    )
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = TEST_SRCS,
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            react_native_xplat_target("cxxreact:bridge"),
-            react_native_xplat_target("jschelpers:jschelpers"),
-        ] + APPLE_JSC_DEPS,
-        visibility = [
-            react_native_xplat_target("cxxreact/..."),
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = TEST_SRCS,
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+    ],
+    platforms = APPLE,
+    visibility = [
+        react_native_xplat_target("cxxreact/..."),
+    ],
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        react_native_xplat_target("cxxreact:bridge"),
+        react_native_xplat_target("jschelpers:jschelpers"),
+    ] + APPLE_JSC_DEPS,
+)
diff --git a/ReactCommon/fabric/activityindicator/BUCK b/ReactCommon/fabric/activityindicator/BUCK
index 952cb7977ff0..aa4cd53f6971 100644
--- a/ReactCommon/fabric/activityindicator/BUCK
+++ b/ReactCommon/fabric/activityindicator/BUCK
@@ -1,13 +1,7 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "subdir_glob", "fb_xplat_cxx_test", "get_apple_compiler_flags", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
-
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "activityindicator",
@@ -56,24 +50,20 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":activityindicator",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":activityindicator",
+    ],
+)
diff --git a/ReactCommon/fabric/attributedstring/BUCK b/ReactCommon/fabric/attributedstring/BUCK
index 61b897ba9d31..0be5eb78c18c 100644
--- a/ReactCommon/fabric/attributedstring/BUCK
+++ b/ReactCommon/fabric/attributedstring/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "get_apple_compiler_flags",
+    "subdir_glob",
+    "fb_xplat_cxx_test",
+    "rn_xplat_cxx_library",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "attributedstring",
@@ -58,24 +62,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":attributedstring",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":attributedstring",
+    ],
+)
diff --git a/ReactCommon/fabric/components/image/BUCK b/ReactCommon/fabric/components/image/BUCK
index fccf34aeb43d..896bd5ff0e11 100644
--- a/ReactCommon/fabric/components/image/BUCK
+++ b/ReactCommon/fabric/components/image/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "image",
@@ -58,24 +62,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":image",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":image",
+    ],
+)
diff --git a/ReactCommon/fabric/components/switch/BUCK b/ReactCommon/fabric/components/switch/BUCK
index b2a4f8c1d691..3026a706193f 100644
--- a/ReactCommon/fabric/components/switch/BUCK
+++ b/ReactCommon/fabric/components/switch/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "get_apple_compiler_flags",
+    "subdir_glob",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "fb_xplat_cxx_test",
+    "rn_xplat_cxx_library",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "switch",
@@ -56,24 +60,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":switch",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":switch",
+    ],
+)
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index f663ff3590ed..112cb850ec82 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -1,13 +1,7 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "subdir_glob", "fb_xplat_cxx_test", "get_apple_compiler_flags", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
 
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
-
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "core",
@@ -62,24 +56,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":core",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":core",
+    ],
+)
diff --git a/ReactCommon/fabric/debug/BUCK b/ReactCommon/fabric/debug/BUCK
index c16bedf03817..c17aa3d4a456 100644
--- a/ReactCommon/fabric/debug/BUCK
+++ b/ReactCommon/fabric/debug/BUCK
@@ -1,13 +1,22 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
-load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//configurations/buck/apple:flag_defs.bzl",
+    "OBJC_ARC_PREPROCESSOR_FLAGS",
+    "get_application_ios_flags",
+    "get_debug_preprocessor_flags",
+)
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "debug",
@@ -54,24 +63,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":debug",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":debug",
+    ],
+)
diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index 78061adc618b..0f8a26ff31df 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "graphics",
@@ -90,24 +94,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":graphics",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":graphics",
+    ],
+)
diff --git a/ReactCommon/fabric/imagemanager/BUCK b/ReactCommon/fabric/imagemanager/BUCK
index a42904ea45fb..a1f7b3059351 100644
--- a/ReactCommon/fabric/imagemanager/BUCK
+++ b/ReactCommon/fabric/imagemanager/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "get_apple_inspector_flags",
+    "get_apple_compiler_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "fb_xplat_cxx_test",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "imagemanager",
@@ -99,24 +103,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":imagemanager",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":imagemanager",
+    ],
+)
diff --git a/ReactCommon/fabric/scrollview/BUCK b/ReactCommon/fabric/scrollview/BUCK
index 1f20c65532f1..d7343182b5ac 100644
--- a/ReactCommon/fabric/scrollview/BUCK
+++ b/ReactCommon/fabric/scrollview/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "scrollview",
@@ -60,24 +64,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":scrollview",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":scrollview",
+    ],
+)
diff --git a/ReactCommon/fabric/text/BUCK b/ReactCommon/fabric/text/BUCK
index e8dc5e5971c5..dd51a9b5b6bd 100644
--- a/ReactCommon/fabric/text/BUCK
+++ b/ReactCommon/fabric/text/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "text",
@@ -66,24 +70,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":text",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":text",
+    ],
+)
diff --git a/ReactCommon/fabric/textlayoutmanager/BUCK b/ReactCommon/fabric/textlayoutmanager/BUCK
index 3ea41084b11d..9fb4a464f827 100644
--- a/ReactCommon/fabric/textlayoutmanager/BUCK
+++ b/ReactCommon/fabric/textlayoutmanager/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "textlayoutmanager",
@@ -106,24 +110,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":textlayoutmanager",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":textlayoutmanager",
+    ],
+)
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 1b091a56325f..c7bc58bc42e7 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "uimanager",
@@ -61,24 +65,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":uimanager",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":uimanager",
+    ],
+)
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/view/BUCK
index 42ea4a7a5d07..54dc9ef2032e 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/view/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "view",
@@ -62,24 +66,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":view",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":view",
+    ],
+)
diff --git a/ReactNative/DEFS.bzl b/ReactNative/DEFS.bzl
index 451675f2862f..1f50344f63f1 100644
--- a/ReactNative/DEFS.bzl
+++ b/ReactNative/DEFS.bzl
@@ -263,3 +263,11 @@ def _single_subdir_glob(dirpath, glob_pattern, exclude = None, prefix = None):
 
 def oss_cxx_library(**kwargs):
     cxx_library(**kwargs)
+
+def jni_instrumentation_test_lib(**kwargs):
+    """A noop stub for OSS build."""
+    pass
+
+def fb_xplat_cxx_test(**kwargs):
+    """A noop stub for OSS build."""
+    pass

From e1cca18d0081f803013fe60d38d89f7f44dafca0 Mon Sep 17 00:00:00 2001
From: Pavlos Vinieratos <pvinis@mac-pro.localdomain>
Date: Sun, 15 Jul 2018 00:06:49 -0700
Subject: [PATCH 1037/1109] Replace deprecated `UILineBreakModeWordWrap` with
 `NSLineBreakByWordWrapping` (#19791)

Summary:
Replace deprecated enum values with the modern ones.

N/A

[INTERNAL] [DEPRECATION] [Red box text wrapping] - Replaced deprecated values with supported ones.
Pull Request resolved: https://github.com/facebook/react-native/pull/19791

Differential Revision: D8851755

Pulled By: hramos

fbshipit-source-id: 7315f199ff748078dec4efb96254bcdb0756e1ba
---
 React/Modules/RCTRedBoxExtraDataViewController.m | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/React/Modules/RCTRedBoxExtraDataViewController.m b/React/Modules/RCTRedBoxExtraDataViewController.m
index 94d371249b9b..f4ca54e40813 100644
--- a/React/Modules/RCTRedBoxExtraDataViewController.m
+++ b/React/Modules/RCTRedBoxExtraDataViewController.m
@@ -43,7 +43,7 @@ - (instancetype)initWithStyle:(UITableViewCellStyle)style
         self.keyLabel.textColor = [UIColor whiteColor];
         self.keyLabel.numberOfLines = 0;
 #if !TARGET_OS_TV
-        self.keyLabel.lineBreakMode = UILineBreakModeWordWrap;
+        self.keyLabel.lineBreakMode = NSLineBreakByWordWrapping;
         self.keyLabel.font = [UIFont fontWithName:@"Menlo-Regular" size:12.0f];
 #endif
         self.valueLabel = [UILabel new];
@@ -63,7 +63,7 @@ - (instancetype)initWithStyle:(UITableViewCellStyle)style
         self.valueLabel.textColor = [UIColor whiteColor];
         self.valueLabel.numberOfLines = 0;
 #if !TARGET_OS_TV
-        self.valueLabel.lineBreakMode = UILineBreakModeWordWrap;
+        self.valueLabel.lineBreakMode = NSLineBreakByWordWrapping;
         self.valueLabel.font = [UIFont fontWithName:@"Menlo-Regular" size:12.0f];
 #endif
     }

From fcd72bf34a4789260815b4e76e701d438c3f3cdd Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:16 -0700
Subject: [PATCH 1038/1109] Fabric: Generalizing cloning of YogaLayoutable
 approach

Summary:
@public
Non-null owner pointer in Yoga node indicates that this node is already being used by some other subtree, so it must be cloned in case of possible (re)layout.
Theoretically, this node must/can be cloned by Yoga right before applying a new layout to this node, but Yoga has a special optimization that uses that fact that Yoga always cloning *all* children of a particular node altogether. This is not true for React; to meet React and Yoga worlds we double check the owner pointer in `addChild` and clone node preliminary if needed.
See also the previous diff for more context.

Reviewed By: mdvacca

Differential Revision: D8709952

fbshipit-source-id: 84ef0faa0f1d9cc9a8136b550cf325bc20508d53
---
 ReactCommon/fabric/uimanager/FabricUIManager.cpp     | 10 ----------
 .../fabric/view/yoga/YogaLayoutableShadowNode.cpp    | 12 ++++++++----
 2 files changed, 8 insertions(+), 14 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 23dd8f8c60bb..9e20dd056361 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -230,16 +230,6 @@ SharedShadowNode FabricUIManager::cloneNodeWithNewChildrenAndProps(const SharedS
 void FabricUIManager::appendChild(const SharedShadowNode &parentShadowNode, const SharedShadowNode &childShadowNode) {
   isLoggingEnabled && LOG(INFO) << "FabricUIManager::appendChild(parentShadowNode: " << parentShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ", childShadowNode: " << childShadowNode->getDebugDescription(DebugStringConvertibleOptions {.format = false}) << ")";
   const SharedComponentDescriptor &componentDescriptor = (*componentDescriptorRegistry_)[parentShadowNode];
-
-  // TODO: Remove this after we move this to JS side.
-  if (childShadowNode->getSealed()) {
-    auto childComponentDescriptor = (*componentDescriptorRegistry_)[childShadowNode];
-    auto clonedChildShadowNode = childComponentDescriptor->cloneShadowNode(childShadowNode);
-    auto nonConstClonedChildShadowNode = std::const_pointer_cast<ShadowNode>(clonedChildShadowNode);
-    componentDescriptor->appendChild(parentShadowNode, clonedChildShadowNode);
-    return;
-  }
-
   componentDescriptor->appendChild(parentShadowNode, childShadowNode);
 }
 
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
index 69ed311158a1..34b0f372fa84 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
@@ -94,12 +94,16 @@ void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child)
 
   auto yogaNodeRawPtr = &yogaNode_;
   auto childYogaNodeRawPtr = &child->yogaNode_;
-  yogaNodeRawPtr->insertChild(childYogaNodeRawPtr, yogaNodeRawPtr->getChildren().size());
 
-  if (childYogaNodeRawPtr->getOwner() == nullptr) {
-    child->ensureUnsealed();
-    childYogaNodeRawPtr->setOwner(yogaNodeRawPtr);
+  if (childYogaNodeRawPtr->getOwner() != nullptr) {
+    child = std::static_pointer_cast<const YogaLayoutableShadowNode>(cloneAndReplaceChild(child));
+    childYogaNodeRawPtr = &child->yogaNode_;
   }
+
+  child->ensureUnsealed();
+  childYogaNodeRawPtr->setOwner(yogaNodeRawPtr);
+
+  yogaNodeRawPtr->insertChild(childYogaNodeRawPtr, yogaNodeRawPtr->getChildren().size());
 }
 
 void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {

From e78bf723bff914dae5bb0da6280d5eb15c2ae293 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:17 -0700
Subject: [PATCH 1039/1109] Fabric: Removed last two plactical usages of
 `ShadowNode::sourceNode_`

Summary:
@public
 * In case of `ShadowTree` we just pass original old node as a `commit` method argument;
 * In case of `ConcreteViewShadowNode` we just don't need that because diffing algorithm does not use that information anymore.

Reviewed By: mdvacca

Differential Revision: D8753906

fbshipit-source-id: b8555083c7e72e9b3c0f9a8065745946d4cf44c7
---
 ReactCommon/fabric/uimanager/ShadowTree.cpp      |  6 +++---
 ReactCommon/fabric/uimanager/ShadowTree.h        |  2 +-
 ReactCommon/fabric/view/ConcreteViewShadowNode.h | 15 ---------------
 3 files changed, 4 insertions(+), 19 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/ShadowTree.cpp b/ReactCommon/fabric/uimanager/ShadowTree.cpp
index 5dd54ecfa933..d179d9dcad1f 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.cpp
+++ b/ReactCommon/fabric/uimanager/ShadowTree.cpp
@@ -78,7 +78,7 @@ void ShadowTree::complete(UnsharedRootShadowNode newRootShadowNode) {
     newRootShadowNode
   );
 
-  if (commit(newRootShadowNode)) {
+  if (commit(oldRootShadowNode, newRootShadowNode)) {
     emitLayoutEvents(instructions);
 
     if (delegate_) {
@@ -87,10 +87,10 @@ void ShadowTree::complete(UnsharedRootShadowNode newRootShadowNode) {
   }
 }
 
-bool ShadowTree::commit(const SharedRootShadowNode &newRootShadowNode) {
+bool ShadowTree::commit(const SharedRootShadowNode &oldRootShadowNode, const SharedRootShadowNode &newRootShadowNode) {
   std::lock_guard<std::mutex> lock(commitMutex_);
 
-  if (newRootShadowNode->getSourceNode() != rootShadowNode_) {
+  if (oldRootShadowNode != rootShadowNode_) {
     return false;
   }
 
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.h b/ReactCommon/fabric/uimanager/ShadowTree.h
index 3bb6af8b44dc..26927fc8b631 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.h
+++ b/ReactCommon/fabric/uimanager/ShadowTree.h
@@ -77,7 +77,7 @@ class ShadowTree final:
 
   UnsharedRootShadowNode cloneRootShadowNode(const LayoutConstraints &layoutConstraints, const LayoutContext &layoutContext) const;
   void complete(UnsharedRootShadowNode newRootShadowNode);
-  bool commit(const SharedRootShadowNode &newRootShadowNode);
+  bool commit(const SharedRootShadowNode &oldRootShadowNode, const SharedRootShadowNode &newRootShadowNode);
   void emitLayoutEvents(const TreeMutationInstructionList &instructions);
 
   const Tag rootTag_;
diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
index c65f9ea060d4..38f0c966deff 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/view/ConcreteViewShadowNode.h
@@ -105,21 +105,6 @@ class ConcreteViewShadowNode:
     auto childShadowNode = std::dynamic_pointer_cast<const ShadowNode>(child);
     assert(childShadowNode);
     auto childShadowNodeClone = childShadowNode->clone();
-
-    // This is overloading of `SharedLayoutableShadowNode::cloneAndReplaceChild`,
-    // the method is used to clone some node as a preparation for future mutation
-    // caused by relayout.
-    // Because those changes are not requested by UIManager, they add a layer
-    // of node generation (between the committed stage and new proposed stage).
-    // That additional layer confuses the Diffing algorithm which uses
-    // `sourceNode` for referencing the previous (aka committed) stage
-    // of the tree to produce mutation instructions.
-    // In other words, if we don't compensate this change here,
-    // the Diffing algorithm will compare wrong trees
-    // ("new-but-not-laid-out-yet vs. new" instead of "committed vs. new").
-    auto nonConstChildShadowNodeClone = std::const_pointer_cast<ShadowNode>(childShadowNodeClone);
-    nonConstChildShadowNodeClone->shallowSourceNode();
-
     ShadowNode::replaceChild(childShadowNode, childShadowNodeClone);
     return std::dynamic_pointer_cast<const LayoutableShadowNode>(childShadowNodeClone);
   }

From 7a7f9601bcb680f1f4f7e2d25a38726ed81cd66b Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:19 -0700
Subject: [PATCH 1040/1109] Fabric: ShadowNode::getSourceNode() was finally
 removed

Summary:
@public
Trivial.

Reviewed By: mdvacca

Differential Revision: D8753905

fbshipit-source-id: 0a0e351dc0f8ff52e685c7d7dc79d0185cfac711
---
 .../fabric/core/shadownode/ShadowNode.cpp     | 40 +++----------------
 .../fabric/core/shadownode/ShadowNode.h       | 19 ---------
 .../fabric/core/tests/ShadowNodeTest.cpp      | 32 ++-------------
 3 files changed, 9 insertions(+), 82 deletions(-)

diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index b2182bcd570d..a9dc88ff614e 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -10,7 +10,7 @@
 #include <string>
 
 #include <fabric/debug/DebugStringConvertible.h>
-#include <fabric/debug/DebugStringConvertibleItem.h>
+#include <fabric/debug/debugStringConvertibleUtils.h>
 
 namespace facebook {
 namespace react {
@@ -49,7 +49,6 @@ ShadowNode::ShadowNode(
   props_(props ? props : shadowNode->props_),
   eventEmitter_(eventEmitter ? eventEmitter : shadowNode->eventEmitter_),
   children_(std::make_shared<SharedShadowNodeList>(*(children ? children : shadowNode->children_))),
-  sourceNode_(shadowNode),
   localData_(shadowNode->localData_),
   cloneFunction_(shadowNode->cloneFunction_),
   revision_(shadowNode->revision_ + 1) {}
@@ -84,10 +83,6 @@ Tag ShadowNode::getRootTag() const {
   return rootTag_;
 }
 
-SharedShadowNode ShadowNode::getSourceNode() const {
-  return sourceNode_.lock();
-}
-
 SharedLocalData ShadowNode::getLocalData() const {
   return localData_;
 }
@@ -122,24 +117,11 @@ void ShadowNode::replaceChild(const SharedShadowNode &oldChild, const SharedShad
   std::replace(nonConstChildren->begin(), nonConstChildren->end(), oldChild, newChild);
 }
 
-void ShadowNode::clearSourceNode() {
-  ensureUnsealed();
-  sourceNode_.reset();
-}
-
 void ShadowNode::setLocalData(const SharedLocalData &localData) {
   ensureUnsealed();
   localData_ = localData;
 }
 
-void ShadowNode::shallowSourceNode() {
-  ensureUnsealed();
-
-  auto sourceNode = sourceNode_.lock();
-  assert(sourceNode);
-  sourceNode_ = sourceNode->getSourceNode();
-}
-
 #pragma mark - Equality
 
 bool ShadowNode::operator==(const ShadowNode& rhs) const {
@@ -181,21 +163,11 @@ SharedDebugStringConvertibleList ShadowNode::getDebugChildren() const {
 }
 
 SharedDebugStringConvertibleList ShadowNode::getDebugProps() const {
-  SharedDebugStringConvertibleList list = {};
-
-  list.push_back(std::make_shared<DebugStringConvertibleItem>("tag", folly::to<std::string>(tag_)));
-
-  SharedShadowNode sourceNode = getSourceNode();
-  if (sourceNode) {
-    list.push_back(std::make_shared<DebugStringConvertibleItem>(
-      "source",
-      sourceNode->getDebugDescription({.maximumDepth = 1, .format = false})
-    ));
-  }
-
-  SharedDebugStringConvertibleList propsList = props_->getDebugProps();
-  std::move(propsList.begin(), propsList.end(), std::back_inserter(list));
-  return list;
+  return
+    props_->getDebugProps() +
+    SharedDebugStringConvertibleList {
+      debugStringConvertibleItem("tag", folly::to<std::string>(tag_))
+    };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index a526fd698692..65f0596937f0 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -28,7 +28,6 @@ using UnsharedShadowNode = std::shared_ptr<ShadowNode>;
 using SharedShadowNodeList = std::vector<std::shared_ptr<const ShadowNode>>;
 using SharedShadowNodeSharedList = std::shared_ptr<const SharedShadowNodeList>;
 using SharedShadowNodeUnsharedList = std::shared_ptr<SharedShadowNodeList>;
-using WeakShadowNode = std::weak_ptr<const ShadowNode>;
 
 using ShadowNodeCloneFunction = std::function<SharedShadowNode(
   const SharedShadowNode &shadowNode,
@@ -81,14 +80,6 @@ class ShadowNode:
   Tag getTag() const;
   Tag getRootTag() const;
 
-  /*
-   * Returns the node which was used as a prototype in clone constructor.
-   * The node is held as a weak reference so that the method may return
-   * `nullptr` in cases where the node was constructed using the explicit
-   * constructor or the node was already deallocated.
-   */
-  SharedShadowNode getSourceNode() const;
-
   /*
    * Returns a local data associated with the node.
    * `LocalData` object might be used for data exchange between native view and
@@ -111,15 +102,6 @@ class ShadowNode:
    */
   void setLocalData(const SharedLocalData &localData);
 
-  /*
-   * Replaces the current source node with its source node.
-   * This method might be used for illuminating side-effects caused by the last
-   * cloning operation which are not desirable from the diffing algorithm
-   * perspective.
-   * The node must be unsealed at this point.
-   */
-  void shallowSourceNode();
-
 #pragma mark - Equality
 
   /*
@@ -145,7 +127,6 @@ class ShadowNode:
   SharedProps props_;
   SharedEventEmitter eventEmitter_;
   SharedShadowNodeSharedList children_;
-  WeakShadowNode sourceNode_;
   SharedLocalData localData_;
 
 private:
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index a1f7d16b6ffa..2cf1347af893 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -37,7 +37,6 @@ TEST(ShadowNodeTest, handleShadowNodeCreation) {
   ASSERT_EQ(node->getEventEmitter(), nullptr);
   TestShadowNode *nodePtr = node.get();
   ASSERT_EQ(node->getComponentHandle(), typeid(*nodePtr).hash_code());
-  ASSERT_EQ(node->getSourceNode(), nullptr);
   ASSERT_EQ(node->getChildren()->size(), 0);
 
   ASSERT_STREQ(node->getProps()->nativeId.c_str(), "testNativeID");
@@ -55,7 +54,6 @@ TEST(ShadowNodeTest, handleShadowNodeSimpleCloning) {
   ASSERT_EQ(node->getTag(), 9);
   ASSERT_EQ(node->getRootTag(), 1);
   ASSERT_EQ(node->getEventEmitter(), nullptr);
-  ASSERT_EQ(node2->getSourceNode(), node);
 }
 
 TEST(ShadowNodeTest, handleShadowNodeMutation) {
@@ -85,35 +83,11 @@ TEST(ShadowNodeTest, handleShadowNodeMutation) {
   ASSERT_TRUE(node4->getSealed());
 
   // No more mutation after sealing.
-  EXPECT_THROW(node4->clearSourceNode(), std::runtime_error);
+  EXPECT_THROW(node4->setLocalData(nullptr), std::runtime_error);
 
   auto node5 = std::make_shared<TestShadowNode>(node4, nullptr, nullptr, nullptr);
-  node5->clearSourceNode();
-  ASSERT_EQ(node5->getSourceNode(), nullptr);
-}
-
-TEST(ShadowNodeTest, handleSourceNode) {
-  auto nodeFirstGeneration = std::make_shared<TestShadowNode>(9, 1, std::make_shared<const TestProps>(), nullptr, ShadowNode::emptySharedShadowNodeSharedList(), nullptr);
-  auto nodeSecondGeneration = std::make_shared<TestShadowNode>(nodeFirstGeneration, nullptr, nullptr, nullptr);
-  auto nodeThirdGeneration = std::make_shared<TestShadowNode>(nodeSecondGeneration, nullptr, nullptr, nullptr);
-  auto nodeForthGeneration = std::make_shared<TestShadowNode>(nodeThirdGeneration, nullptr, nullptr, nullptr);
-
-  // Ensure established shource nodes structure.
-  ASSERT_EQ(nodeForthGeneration->getSourceNode(), nodeThirdGeneration);
-  ASSERT_EQ(nodeThirdGeneration->getSourceNode(), nodeSecondGeneration);
-  ASSERT_EQ(nodeSecondGeneration->getSourceNode(), nodeFirstGeneration);
-
-  // Shallow source node for the forth generation node.
-  nodeForthGeneration->shallowSourceNode();
-  ASSERT_EQ(nodeForthGeneration->getSourceNode(), nodeSecondGeneration);
-
-  // Shallow it one more time.
-  nodeForthGeneration->shallowSourceNode();
-  ASSERT_EQ(nodeForthGeneration->getSourceNode(), nodeFirstGeneration);
-
-  // Ensure that 3th and 2nd were not affected.
-  ASSERT_EQ(nodeThirdGeneration->getSourceNode(), nodeSecondGeneration);
-  ASSERT_EQ(nodeSecondGeneration->getSourceNode(), nodeFirstGeneration);
+  node5->setLocalData(nullptr);
+  ASSERT_EQ(node5->getLocalData(), nullptr);
 }
 
 TEST(ShadowNodeTest, handleCloneFunction) {

From 0532e01d69539dfb26a4acc997fe23a181e63847 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:22 -0700
Subject: [PATCH 1041/1109] Fabric: Enhancements in ContextContainer

Summary:
@public
Everything is better with C++ templates.
In this cases templates allow us to remove additional parameters and casts on the callsite.

Reviewed By: mdvacca

Differential Revision: D8754523

fbshipit-source-id: 2340b2cd96ab0a60d54d9aa30dea3c072b951a8a
---
 React/Fabric/RCTScheduler.mm                  |  2 +-
 .../image/ImageComponentDescriptor.h          |  2 +-
 .../fabric/uimanager/ContextContainer.cpp     | 22 -------------------
 .../fabric/uimanager/ContextContainer.h       | 19 ++++++++++------
 4 files changed, 14 insertions(+), 31 deletions(-)
 delete mode 100644 ReactCommon/fabric/uimanager/ContextContainer.cpp

diff --git a/React/Fabric/RCTScheduler.mm b/React/Fabric/RCTScheduler.mm
index ce1d3b420180..3f441b1c25bb 100644
--- a/React/Fabric/RCTScheduler.mm
+++ b/React/Fabric/RCTScheduler.mm
@@ -49,7 +49,7 @@ - (instancetype)init
     SharedContextContainer contextContainer = std::make_shared<ContextContainer>();
 
     void *imageLoader = (__bridge void *)[[RCTBridge currentBridge] imageLoader];
-    contextContainer->registerInstance(typeid(ImageManager), std::make_shared<ImageManager>(imageLoader));
+    contextContainer->registerInstance(std::make_shared<ImageManager>(imageLoader));
 
     _scheduler = std::make_shared<Scheduler>(contextContainer);
     _scheduler->setDelegate(_delegateProxy.get());
diff --git a/ReactCommon/fabric/components/image/ImageComponentDescriptor.h b/ReactCommon/fabric/components/image/ImageComponentDescriptor.h
index b2219e4495b2..8ce4a15821fb 100644
--- a/ReactCommon/fabric/components/image/ImageComponentDescriptor.h
+++ b/ReactCommon/fabric/components/image/ImageComponentDescriptor.h
@@ -24,7 +24,7 @@ class ImageComponentDescriptor final:
 public:
   ImageComponentDescriptor(SharedEventDispatcher eventDispatcher, const SharedContextContainer &contextContainer):
     ConcreteComponentDescriptor(eventDispatcher),
-    imageManager_(std::static_pointer_cast<ImageManager>(contextContainer->at(typeid(ImageManager)))) {}
+    imageManager_(contextContainer->getInstance<ImageManager>()) {}
 
   void adopt(UnsharedShadowNode shadowNode) const override {
     ConcreteComponentDescriptor::adopt(shadowNode);
diff --git a/ReactCommon/fabric/uimanager/ContextContainer.cpp b/ReactCommon/fabric/uimanager/ContextContainer.cpp
deleted file mode 100644
index ef2ceb473dc5..000000000000
--- a/ReactCommon/fabric/uimanager/ContextContainer.cpp
+++ /dev/null
@@ -1,22 +0,0 @@
-// Copyright (c) 2004-present, Facebook, Inc.
-
-// This source code is licensed under the MIT license found in the
-// LICENSE file in the root directory of this source tree.
-
-#include "ContextContainer.h"
-
-namespace facebook {
-namespace react {
-
-void ContextContainer::registerInstance(const ClassHandle &handle, SharedInstance instance) {
-  std::lock_guard<std::mutex> lock(mutex_);
-  instances_.insert({handle, instance});
-}
-
-const ContextContainer::SharedInstance &ContextContainer::at(const ClassHandle &handle) const {
-  std::lock_guard<std::mutex> lock(mutex_);
-  return instances_.at(handle);
-}
-
-} // namespace react
-} // namespace facebook
diff --git a/ReactCommon/fabric/uimanager/ContextContainer.h b/ReactCommon/fabric/uimanager/ContextContainer.h
index bec29b6bf45d..30e055c85206 100644
--- a/ReactCommon/fabric/uimanager/ContextContainer.h
+++ b/ReactCommon/fabric/uimanager/ContextContainer.h
@@ -24,15 +24,20 @@ using SharedContextContainer = std::shared_ptr<ContextContainer>;
 class ContextContainer final {
 
 public:
-  using ClassHandle = std::type_index;
-  using SharedInstance = std::shared_ptr<void>;
-
-  void registerInstance(const ClassHandle &handle, SharedInstance instance);
-
-  const SharedInstance &at(const ClassHandle &handle) const;
+  template<typename T>
+  void registerInstance(std::shared_ptr<T> instance) {
+    std::lock_guard<std::mutex> lock(mutex_);
+    instances_.insert({std::type_index(typeid(T)), instance});
+  }
+
+  template<typename T>
+  std::shared_ptr<T> getInstance() const {
+    std::lock_guard<std::mutex> lock(mutex_);
+    return std::static_pointer_cast<T>(instances_.at(std::type_index(typeid(T))));
+  }
 
 private:
-  std::unordered_map<ClassHandle, SharedInstance> instances_;
+  std::unordered_map<std::type_index, std::shared_ptr<void>> instances_;
   mutable std::mutex mutex_;
 };
 

From 2c28310267e68d3ac75615d27e22126202bd5411 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:24 -0700
Subject: [PATCH 1042/1109] Fabric: Computed attributed string caching inside
 <Paragraph>

Summary:
@public
Quite trivial. We had to have this from the day one.
We don't need cache invalidation policy because all subtree is immutable.

Reviewed By: mdvacca

Differential Revision: D8709973

fbshipit-source-id: bd7fcf0ae1dcb23894321cb5d16da18cb1ab788f
---
 ReactCommon/fabric/attributedstring/AttributedString.h    | 1 -
 ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp   | 2 --
 ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp | 7 ++++++-
 ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h   | 7 +++++++
 4 files changed, 13 insertions(+), 4 deletions(-)

diff --git a/ReactCommon/fabric/attributedstring/AttributedString.h b/ReactCommon/fabric/attributedstring/AttributedString.h
index 07cc47603e45..4fa5ac9b4666 100644
--- a/ReactCommon/fabric/attributedstring/AttributedString.h
+++ b/ReactCommon/fabric/attributedstring/AttributedString.h
@@ -72,4 +72,3 @@ class AttributedString:
 
 } // namespace react
 } // namespace facebook
-
diff --git a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
index f2f2d08a7ee8..ec97f412444f 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
+++ b/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
@@ -20,8 +20,6 @@ AttributedString BaseTextShadowNode::getAttributedString(
   const TextAttributes &textAttributes,
   const SharedShadowNodeSharedList &childNodes
 ) const {
-  // TODO: Implement caching.
-
   AttributedString attributedString;
 
   for (const auto &childNode : *childNodes) {
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
index e7b6513ba235..99222fc317fd 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
+++ b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
@@ -19,7 +19,12 @@ ComponentName ParagraphShadowNode::getComponentName() const {
 }
 
 AttributedString ParagraphShadowNode::getAttributedString() const {
-  return BaseTextShadowNode::getAttributedString(getProps()->textAttributes, getChildren());
+  if (!cachedAttributedString_.has_value()) {
+    cachedAttributedString_ =
+      BaseTextShadowNode::getAttributedString(getProps()->textAttributes, getChildren());
+  }
+
+  return cachedAttributedString_.value();
 }
 
 void ParagraphShadowNode::setTextLayoutManager(SharedTextLayoutManager textLayoutManager) {
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
index df16aee1b797..f7b1ea4fd2a6 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
+++ b/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
@@ -14,6 +14,7 @@
 #include <fabric/text/TextShadowNode.h>
 #include <fabric/textlayoutmanager/TextLayoutManager.h>
 #include <fabric/view/ConcreteViewShadowNode.h>
+#include <folly/Optional.h>
 
 namespace facebook {
 namespace react {
@@ -63,6 +64,12 @@ class ParagraphShadowNode:
   void updateLocalData();
 
   SharedTextLayoutManager textLayoutManager_;
+
+  /*
+   * Cached attributed string that represents the content of the subtree started
+   * from the node.
+   */
+  mutable folly::Optional<AttributedString> cachedAttributedString_ {};
 };
 
 } // namespace react

From ecbe9acbaaa94daade6baf629965d6b6be2383b6 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:26 -0700
Subject: [PATCH 1043/1109] Fabric: `text` module was moved to `components`
 subdirectory

Summary:
@public
Trivial. We move all components into `/components/` subdirectory.

Reviewed By: mdvacca

Differential Revision: D8757014

fbshipit-source-id: 9db94d38fe027e9125d017a17cbd4cf79f0bcf88
---
 .../ComponentViews/Text/RCTParagraphComponentView.mm      | 4 ++--
 ReactCommon/fabric/{ => components}/text/BUCK             | 2 +-
 .../{ => components}/text/basetext/BaseTextProps.cpp      | 0
 .../fabric/{ => components}/text/basetext/BaseTextProps.h | 0
 .../{ => components}/text/basetext/BaseTextShadowNode.cpp | 8 ++++----
 .../{ => components}/text/basetext/BaseTextShadowNode.h   | 0
 .../text/paragraph/ParagraphComponentDescriptor.h         | 2 +-
 .../text/paragraph/ParagraphLocalData.cpp                 | 0
 .../{ => components}/text/paragraph/ParagraphLocalData.h  | 0
 .../{ => components}/text/paragraph/ParagraphProps.cpp    | 0
 .../{ => components}/text/paragraph/ParagraphProps.h      | 2 +-
 .../text/paragraph/ParagraphShadowNode.cpp                | 0
 .../{ => components}/text/paragraph/ParagraphShadowNode.h | 4 ++--
 .../text/rawtext/RawTextComponentDescriptor.h             | 2 +-
 .../fabric/{ => components}/text/rawtext/RawTextProps.cpp | 0
 .../fabric/{ => components}/text/rawtext/RawTextProps.h   | 0
 .../{ => components}/text/rawtext/RawTextShadowNode.cpp   | 0
 .../{ => components}/text/rawtext/RawTextShadowNode.h     | 2 +-
 .../fabric/{ => components}/text/tests/TextTest.cpp       | 0
 .../{ => components}/text/text/TextComponentDescriptor.h  | 2 +-
 .../fabric/{ => components}/text/text/TextProps.cpp       | 0
 ReactCommon/fabric/{ => components}/text/text/TextProps.h | 2 +-
 .../fabric/{ => components}/text/text/TextShadowNode.cpp  | 0
 .../fabric/{ => components}/text/text/TextShadowNode.h    | 6 +++---
 ReactCommon/fabric/uimanager/BUCK                         | 3 +--
 ReactCommon/fabric/uimanager/Scheduler.cpp                | 6 +++---
 26 files changed, 22 insertions(+), 23 deletions(-)
 rename ReactCommon/fabric/{ => components}/text/BUCK (98%)
 rename ReactCommon/fabric/{ => components}/text/basetext/BaseTextProps.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/basetext/BaseTextProps.h (100%)
 rename ReactCommon/fabric/{ => components}/text/basetext/BaseTextShadowNode.cpp (89%)
 rename ReactCommon/fabric/{ => components}/text/basetext/BaseTextShadowNode.h (100%)
 rename ReactCommon/fabric/{ => components}/text/paragraph/ParagraphComponentDescriptor.h (96%)
 rename ReactCommon/fabric/{ => components}/text/paragraph/ParagraphLocalData.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/paragraph/ParagraphLocalData.h (100%)
 rename ReactCommon/fabric/{ => components}/text/paragraph/ParagraphProps.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/paragraph/ParagraphProps.h (96%)
 rename ReactCommon/fabric/{ => components}/text/paragraph/ParagraphShadowNode.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/paragraph/ParagraphShadowNode.h (95%)
 rename ReactCommon/fabric/{ => components}/text/rawtext/RawTextComponentDescriptor.h (88%)
 rename ReactCommon/fabric/{ => components}/text/rawtext/RawTextProps.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/rawtext/RawTextProps.h (100%)
 rename ReactCommon/fabric/{ => components}/text/rawtext/RawTextShadowNode.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/rawtext/RawTextShadowNode.h (94%)
 rename ReactCommon/fabric/{ => components}/text/tests/TextTest.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/text/TextComponentDescriptor.h (89%)
 rename ReactCommon/fabric/{ => components}/text/text/TextProps.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/text/TextProps.h (94%)
 rename ReactCommon/fabric/{ => components}/text/text/TextShadowNode.cpp (100%)
 rename ReactCommon/fabric/{ => components}/text/text/TextShadowNode.h (83%)

diff --git a/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm b/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm
index 770913113ec3..ecdc55569cfb 100644
--- a/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm
@@ -7,10 +7,10 @@
 
 #import "RCTParagraphComponentView.h"
 
+#import <fabric/components/text/ParagraphLocalData.h>
+#import <fabric/components/text/ParagraphProps.h>
 #import <fabric/core/LocalData.h>
 #import <fabric/graphics/Geometry.h>
-#import <fabric/text/ParagraphLocalData.h>
-#import <fabric/text/ParagraphProps.h>
 #import <fabric/textlayoutmanager/TextLayoutManager.h>
 #import <fabric/textlayoutmanager/RCTTextLayoutManager.h>
 #import "RCTConversions.h"
diff --git a/ReactCommon/fabric/text/BUCK b/ReactCommon/fabric/components/text/BUCK
similarity index 98%
rename from ReactCommon/fabric/text/BUCK
rename to ReactCommon/fabric/components/text/BUCK
index dd51a9b5b6bd..c9711245d753 100644
--- a/ReactCommon/fabric/text/BUCK
+++ b/ReactCommon/fabric/components/text/BUCK
@@ -32,7 +32,7 @@ rn_xplat_cxx_library(
             ("text", "*.h"),
             ("rawtext", "*.h"),
         ],
-        prefix = "fabric/text",
+        prefix = "fabric/components/text",
     ),
     compiler_flags = [
         "-fexceptions",
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.cpp b/ReactCommon/fabric/components/text/basetext/BaseTextProps.cpp
similarity index 100%
rename from ReactCommon/fabric/text/basetext/BaseTextProps.cpp
rename to ReactCommon/fabric/components/text/basetext/BaseTextProps.cpp
diff --git a/ReactCommon/fabric/text/basetext/BaseTextProps.h b/ReactCommon/fabric/components/text/basetext/BaseTextProps.h
similarity index 100%
rename from ReactCommon/fabric/text/basetext/BaseTextProps.h
rename to ReactCommon/fabric/components/text/basetext/BaseTextProps.h
diff --git a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp b/ReactCommon/fabric/components/text/basetext/BaseTextShadowNode.cpp
similarity index 89%
rename from ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
rename to ReactCommon/fabric/components/text/basetext/BaseTextShadowNode.cpp
index ec97f412444f..6f7c0333b148 100644
--- a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.cpp
+++ b/ReactCommon/fabric/components/text/basetext/BaseTextShadowNode.cpp
@@ -7,11 +7,11 @@
 
 #include "BaseTextShadowNode.h"
 
+#include <fabric/components/text/RawTextShadowNode.h>
+#include <fabric/components/text/RawTextProps.h>
+#include <fabric/components/text/TextShadowNode.h>
+#include <fabric/components/text/TextProps.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/text/RawTextShadowNode.h>
-#include <fabric/text/RawTextProps.h>
-#include <fabric/text/TextShadowNode.h>
-#include <fabric/text/TextProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/basetext/BaseTextShadowNode.h b/ReactCommon/fabric/components/text/basetext/BaseTextShadowNode.h
similarity index 100%
rename from ReactCommon/fabric/text/basetext/BaseTextShadowNode.h
rename to ReactCommon/fabric/components/text/basetext/BaseTextShadowNode.h
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h b/ReactCommon/fabric/components/text/paragraph/ParagraphComponentDescriptor.h
similarity index 96%
rename from ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
rename to ReactCommon/fabric/components/text/paragraph/ParagraphComponentDescriptor.h
index 71e6b8adaa92..3d9074cbcade 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphComponentDescriptor.h
+++ b/ReactCommon/fabric/components/text/paragraph/ParagraphComponentDescriptor.h
@@ -7,8 +7,8 @@
 
 #pragma once
 
+#include <fabric/components/text/ParagraphShadowNode.h>
 #include <fabric/core/ConcreteComponentDescriptor.h>
-#include <fabric/text/ParagraphShadowNode.h>
 #include <fabric/textlayoutmanager/TextLayoutManager.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp b/ReactCommon/fabric/components/text/paragraph/ParagraphLocalData.cpp
similarity index 100%
rename from ReactCommon/fabric/text/paragraph/ParagraphLocalData.cpp
rename to ReactCommon/fabric/components/text/paragraph/ParagraphLocalData.cpp
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphLocalData.h b/ReactCommon/fabric/components/text/paragraph/ParagraphLocalData.h
similarity index 100%
rename from ReactCommon/fabric/text/paragraph/ParagraphLocalData.h
rename to ReactCommon/fabric/components/text/paragraph/ParagraphLocalData.h
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.cpp b/ReactCommon/fabric/components/text/paragraph/ParagraphProps.cpp
similarity index 100%
rename from ReactCommon/fabric/text/paragraph/ParagraphProps.cpp
rename to ReactCommon/fabric/components/text/paragraph/ParagraphProps.cpp
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphProps.h b/ReactCommon/fabric/components/text/paragraph/ParagraphProps.h
similarity index 96%
rename from ReactCommon/fabric/text/paragraph/ParagraphProps.h
rename to ReactCommon/fabric/components/text/paragraph/ParagraphProps.h
index 5877be6cb86d..f31789eacbe0 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphProps.h
+++ b/ReactCommon/fabric/components/text/paragraph/ParagraphProps.h
@@ -11,8 +11,8 @@
 #include <memory>
 
 #include <fabric/attributedstring/ParagraphAttributes.h>
+#include <fabric/components/text/BaseTextProps.h>
 #include <fabric/core/Props.h>
-#include <fabric/text/BaseTextProps.h>
 #include <fabric/view/ViewProps.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp b/ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.cpp
similarity index 100%
rename from ReactCommon/fabric/text/paragraph/ParagraphShadowNode.cpp
rename to ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.cpp
diff --git a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h b/ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.h
similarity index 95%
rename from ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
rename to ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.h
index f7b1ea4fd2a6..c18be91d7b43 100644
--- a/ReactCommon/fabric/text/paragraph/ParagraphShadowNode.h
+++ b/ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.h
@@ -7,11 +7,11 @@
 
 #pragma once
 
+#include <fabric/components/text/ParagraphProps.h>
+#include <fabric/components/text/TextShadowNode.h>
 #include <fabric/core/ConcreteShadowNode.h>
 #include <fabric/core/ShadowNode.h>
 #include <fabric/core/LayoutContext.h>
-#include <fabric/text/ParagraphProps.h>
-#include <fabric/text/TextShadowNode.h>
 #include <fabric/textlayoutmanager/TextLayoutManager.h>
 #include <fabric/view/ConcreteViewShadowNode.h>
 #include <folly/Optional.h>
diff --git a/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h b/ReactCommon/fabric/components/text/rawtext/RawTextComponentDescriptor.h
similarity index 88%
rename from ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h
rename to ReactCommon/fabric/components/text/rawtext/RawTextComponentDescriptor.h
index ca2ccdbe1cf9..4d53805a3c17 100644
--- a/ReactCommon/fabric/text/rawtext/RawTextComponentDescriptor.h
+++ b/ReactCommon/fabric/components/text/rawtext/RawTextComponentDescriptor.h
@@ -7,8 +7,8 @@
 
 #pragma once
 
+#include <fabric/components/text/RawTextShadowNode.h>
 #include <fabric/core/ConcreteComponentDescriptor.h>
-#include <fabric/text/RawTextShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/rawtext/RawTextProps.cpp b/ReactCommon/fabric/components/text/rawtext/RawTextProps.cpp
similarity index 100%
rename from ReactCommon/fabric/text/rawtext/RawTextProps.cpp
rename to ReactCommon/fabric/components/text/rawtext/RawTextProps.cpp
diff --git a/ReactCommon/fabric/text/rawtext/RawTextProps.h b/ReactCommon/fabric/components/text/rawtext/RawTextProps.h
similarity index 100%
rename from ReactCommon/fabric/text/rawtext/RawTextProps.h
rename to ReactCommon/fabric/components/text/rawtext/RawTextProps.h
diff --git a/ReactCommon/fabric/text/rawtext/RawTextShadowNode.cpp b/ReactCommon/fabric/components/text/rawtext/RawTextShadowNode.cpp
similarity index 100%
rename from ReactCommon/fabric/text/rawtext/RawTextShadowNode.cpp
rename to ReactCommon/fabric/components/text/rawtext/RawTextShadowNode.cpp
diff --git a/ReactCommon/fabric/text/rawtext/RawTextShadowNode.h b/ReactCommon/fabric/components/text/rawtext/RawTextShadowNode.h
similarity index 94%
rename from ReactCommon/fabric/text/rawtext/RawTextShadowNode.h
rename to ReactCommon/fabric/components/text/rawtext/RawTextShadowNode.h
index f4a2e2ffceba..5d37e86e911a 100644
--- a/ReactCommon/fabric/text/rawtext/RawTextShadowNode.h
+++ b/ReactCommon/fabric/components/text/rawtext/RawTextShadowNode.h
@@ -9,9 +9,9 @@
 
 #include <memory>
 
+#include <fabric/components/text/RawTextProps.h>
 #include <fabric/core/ConcreteShadowNode.h>
 #include <fabric/core/ShadowNode.h>
-#include <fabric/text/RawTextProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/tests/TextTest.cpp b/ReactCommon/fabric/components/text/tests/TextTest.cpp
similarity index 100%
rename from ReactCommon/fabric/text/tests/TextTest.cpp
rename to ReactCommon/fabric/components/text/tests/TextTest.cpp
diff --git a/ReactCommon/fabric/text/text/TextComponentDescriptor.h b/ReactCommon/fabric/components/text/text/TextComponentDescriptor.h
similarity index 89%
rename from ReactCommon/fabric/text/text/TextComponentDescriptor.h
rename to ReactCommon/fabric/components/text/text/TextComponentDescriptor.h
index 5abb428e33de..af8d9f12c543 100644
--- a/ReactCommon/fabric/text/text/TextComponentDescriptor.h
+++ b/ReactCommon/fabric/components/text/text/TextComponentDescriptor.h
@@ -7,8 +7,8 @@
 
 #pragma once
 
+#include <fabric/components/text/TextShadowNode.h>
 #include <fabric/core/ConcreteComponentDescriptor.h>
-#include <fabric/text/TextShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/text/TextProps.cpp b/ReactCommon/fabric/components/text/text/TextProps.cpp
similarity index 100%
rename from ReactCommon/fabric/text/text/TextProps.cpp
rename to ReactCommon/fabric/components/text/text/TextProps.cpp
diff --git a/ReactCommon/fabric/text/text/TextProps.h b/ReactCommon/fabric/components/text/text/TextProps.h
similarity index 94%
rename from ReactCommon/fabric/text/text/TextProps.h
rename to ReactCommon/fabric/components/text/text/TextProps.h
index b42050731740..9213b0dfc139 100644
--- a/ReactCommon/fabric/text/text/TextProps.h
+++ b/ReactCommon/fabric/components/text/text/TextProps.h
@@ -8,10 +8,10 @@
 #pragma once
 
 #include <fabric/attributedstring/TextAttributes.h>
+#include <fabric/components/text/BaseTextProps.h>
 #include <fabric/core/Props.h>
 #include <fabric/graphics/Color.h>
 #include <fabric/graphics/Geometry.h>
-#include <fabric/text/BaseTextProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/text/text/TextShadowNode.cpp b/ReactCommon/fabric/components/text/text/TextShadowNode.cpp
similarity index 100%
rename from ReactCommon/fabric/text/text/TextShadowNode.cpp
rename to ReactCommon/fabric/components/text/text/TextShadowNode.cpp
diff --git a/ReactCommon/fabric/text/text/TextShadowNode.h b/ReactCommon/fabric/components/text/text/TextShadowNode.h
similarity index 83%
rename from ReactCommon/fabric/text/text/TextShadowNode.h
rename to ReactCommon/fabric/components/text/text/TextShadowNode.h
index 12c73e1a17e3..f9e584f51f95 100644
--- a/ReactCommon/fabric/text/text/TextShadowNode.h
+++ b/ReactCommon/fabric/components/text/text/TextShadowNode.h
@@ -9,11 +9,11 @@
 
 #include <fabric/attributedstring/AttributedString.h>
 #include <fabric/attributedstring/TextAttributes.h>
+#include <fabric/components/text/BaseTextShadowNode.h>
+#include <fabric/components/text/TextProps.h>
+#include <fabric/components/text/TextShadowNode.h>
 #include <fabric/core/ConcreteShadowNode.h>
 #include <fabric/core/ShadowNode.h>
-#include <fabric/text/BaseTextShadowNode.h>
-#include <fabric/text/TextProps.h>
-#include <fabric/text/TextShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index c7bc58bc42e7..52c3d1f6eb87 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -56,12 +56,11 @@ rn_xplat_cxx_library(
         "xplat//folly:memory",
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
+        react_native_xplat_target("fabric/components/text:text"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/debug:debug"),
-        react_native_xplat_target("fabric/text:text"),
         react_native_xplat_target("fabric/view:view"),
         react_native_xplat_target("fabric/scrollview:scrollview"),
-        react_native_xplat_target("fabric/text:text"),
     ],
 )
 
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index c7e3f51100a3..d42adc224d26 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -5,11 +5,11 @@
 
 #include "Scheduler.h"
 
+#include <fabric/components/text/ParagraphComponentDescriptor.h>
+#include <fabric/components/text/RawTextComponentDescriptor.h>
+#include <fabric/components/text/TextComponentDescriptor.h>
 #include <fabric/core/LayoutContext.h>
 #include <fabric/scrollview/ScrollViewComponentDescriptor.h>
-#include <fabric/text/ParagraphComponentDescriptor.h>
-#include <fabric/text/RawTextComponentDescriptor.h>
-#include <fabric/text/TextComponentDescriptor.h>
 #include <fabric/uimanager/ComponentDescriptorRegistry.h>
 #include <fabric/uimanager/FabricUIManager.h>
 #include <fabric/view/ViewComponentDescriptor.h>

From b42e674c2f9050770dfa8441171e86c40ae800b7 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:28 -0700
Subject: [PATCH 1044/1109] Fabric: `scrollview` module was moved to
 `components` subdirectory

Summary:
@public
Trivial. We move all components into `/components/` subdirectory.

Reviewed By: mdvacca

Differential Revision: D8757013

fbshipit-source-id: fe3021862b3a4f8f0799b0dfaf6d3039f8582a7f
---
 .../ComponentViews/ScrollView/RCTScrollViewComponentView.mm | 6 +++---
 ReactCommon/fabric/{ => components}/scrollview/BUCK         | 2 +-
 .../scrollview/ScrollViewComponentDescriptor.h              | 2 +-
 .../{ => components}/scrollview/ScrollViewEventEmitter.cpp  | 0
 .../{ => components}/scrollview/ScrollViewEventEmitter.h    | 0
 .../{ => components}/scrollview/ScrollViewLocalData.cpp     | 0
 .../{ => components}/scrollview/ScrollViewLocalData.h       | 0
 .../fabric/{ => components}/scrollview/ScrollViewProps.cpp  | 4 ++--
 .../fabric/{ => components}/scrollview/ScrollViewProps.h    | 2 +-
 .../{ => components}/scrollview/ScrollViewShadowNode.cpp    | 0
 .../{ => components}/scrollview/ScrollViewShadowNode.h      | 4 ++--
 .../fabric/{ => components}/scrollview/conversions.h        | 2 +-
 ReactCommon/fabric/{ => components}/scrollview/primitives.h | 0
 .../{ => components}/scrollview/tests/ScrollViewTest.cpp    | 0
 ReactCommon/fabric/uimanager/BUCK                           | 2 +-
 ReactCommon/fabric/uimanager/Scheduler.cpp                  | 2 +-
 16 files changed, 13 insertions(+), 13 deletions(-)
 rename ReactCommon/fabric/{ => components}/scrollview/BUCK (97%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewComponentDescriptor.h (87%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewEventEmitter.cpp (100%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewEventEmitter.h (100%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewLocalData.cpp (100%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewLocalData.h (100%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewProps.cpp (99%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewProps.h (96%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewShadowNode.cpp (100%)
 rename ReactCommon/fabric/{ => components}/scrollview/ScrollViewShadowNode.h (88%)
 rename ReactCommon/fabric/{ => components}/scrollview/conversions.h (97%)
 rename ReactCommon/fabric/{ => components}/scrollview/primitives.h (100%)
 rename ReactCommon/fabric/{ => components}/scrollview/tests/ScrollViewTest.cpp (100%)

diff --git a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
index 90e47e77f5d6..018f45b834e8 100644
--- a/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm
@@ -8,10 +8,10 @@
 #import "RCTScrollViewComponentView.h"
 
 #import <React/RCTAssert.h>
+#import <fabric/components/scrollview/ScrollViewLocalData.h>
+#import <fabric/components/scrollview/ScrollViewProps.h>
+#import <fabric/components/scrollview/ScrollViewEventEmitter.h>
 #import <fabric/graphics/Geometry.h>
-#import <fabric/scrollview/ScrollViewLocalData.h>
-#import <fabric/scrollview/ScrollViewProps.h>
-#import <fabric/scrollview/ScrollViewEventEmitter.h>
 
 #import "RCTConversions.h"
 #import "RCTEnhancedScrollView.h"
diff --git a/ReactCommon/fabric/scrollview/BUCK b/ReactCommon/fabric/components/scrollview/BUCK
similarity index 97%
rename from ReactCommon/fabric/scrollview/BUCK
rename to ReactCommon/fabric/components/scrollview/BUCK
index d7343182b5ac..007249e5f68e 100644
--- a/ReactCommon/fabric/scrollview/BUCK
+++ b/ReactCommon/fabric/components/scrollview/BUCK
@@ -28,7 +28,7 @@ rn_xplat_cxx_library(
         [
             ("", "*.h"),
         ],
-        prefix = "fabric/scrollview",
+        prefix = "fabric/components/scrollview",
     ),
     compiler_flags = [
         "-fexceptions",
diff --git a/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h b/ReactCommon/fabric/components/scrollview/ScrollViewComponentDescriptor.h
similarity index 87%
rename from ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h
rename to ReactCommon/fabric/components/scrollview/ScrollViewComponentDescriptor.h
index b1c075980ff6..9b7b3737735c 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewComponentDescriptor.h
+++ b/ReactCommon/fabric/components/scrollview/ScrollViewComponentDescriptor.h
@@ -7,8 +7,8 @@
 
 #pragma once
 
+#include <fabric/components/scrollview/ScrollViewShadowNode.h>
 #include <fabric/core/ConcreteComponentDescriptor.h>
-#include <fabric/scrollview/ScrollViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/scrollview/ScrollViewEventEmitter.cpp b/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.cpp
similarity index 100%
rename from ReactCommon/fabric/scrollview/ScrollViewEventEmitter.cpp
rename to ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.cpp
diff --git a/ReactCommon/fabric/scrollview/ScrollViewEventEmitter.h b/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h
similarity index 100%
rename from ReactCommon/fabric/scrollview/ScrollViewEventEmitter.h
rename to ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h
diff --git a/ReactCommon/fabric/scrollview/ScrollViewLocalData.cpp b/ReactCommon/fabric/components/scrollview/ScrollViewLocalData.cpp
similarity index 100%
rename from ReactCommon/fabric/scrollview/ScrollViewLocalData.cpp
rename to ReactCommon/fabric/components/scrollview/ScrollViewLocalData.cpp
diff --git a/ReactCommon/fabric/scrollview/ScrollViewLocalData.h b/ReactCommon/fabric/components/scrollview/ScrollViewLocalData.h
similarity index 100%
rename from ReactCommon/fabric/scrollview/ScrollViewLocalData.h
rename to ReactCommon/fabric/components/scrollview/ScrollViewLocalData.h
diff --git a/ReactCommon/fabric/scrollview/ScrollViewProps.cpp b/ReactCommon/fabric/components/scrollview/ScrollViewProps.cpp
similarity index 99%
rename from ReactCommon/fabric/scrollview/ScrollViewProps.cpp
rename to ReactCommon/fabric/components/scrollview/ScrollViewProps.cpp
index c3b1b4e7a7ed..cdee74966e67 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewProps.cpp
+++ b/ReactCommon/fabric/components/scrollview/ScrollViewProps.cpp
@@ -7,9 +7,9 @@
 
 #include "ScrollViewProps.h"
 
-#include <fabric/graphics/conversions.h>
-#include <fabric/scrollview/conversions.h>
+#include <fabric/components/scrollview/conversions.h>
 #include <fabric/debug/debugStringConvertibleUtils.h>
+#include <fabric/graphics/conversions.h>
 
 #include <fabric/core/propsConversions.h>
 
diff --git a/ReactCommon/fabric/scrollview/ScrollViewProps.h b/ReactCommon/fabric/components/scrollview/ScrollViewProps.h
similarity index 96%
rename from ReactCommon/fabric/scrollview/ScrollViewProps.h
rename to ReactCommon/fabric/components/scrollview/ScrollViewProps.h
index 219902470cb8..ff5562a6a3ba 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewProps.h
+++ b/ReactCommon/fabric/components/scrollview/ScrollViewProps.h
@@ -7,7 +7,7 @@
 
 #pragma once
 
-#include <fabric/scrollview/primitives.h>
+#include <fabric/components/scrollview/primitives.h>
 #include <fabric/view/ViewProps.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp b/ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.cpp
similarity index 100%
rename from ReactCommon/fabric/scrollview/ScrollViewShadowNode.cpp
rename to ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.cpp
diff --git a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h b/ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.h
similarity index 88%
rename from ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
rename to ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.h
index c2db4ed66c8f..1c8f77830cb2 100644
--- a/ReactCommon/fabric/scrollview/ScrollViewShadowNode.h
+++ b/ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.h
@@ -9,9 +9,9 @@
 
 #include <memory>
 
+#include <fabric/components/scrollview/ScrollViewEventEmitter.h>
+#include <fabric/components/scrollview/ScrollViewProps.h>
 #include <fabric/core/LayoutContext.h>
-#include <fabric/scrollview/ScrollViewEventEmitter.h>
-#include <fabric/scrollview/ScrollViewProps.h>
 #include <fabric/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/scrollview/conversions.h b/ReactCommon/fabric/components/scrollview/conversions.h
similarity index 97%
rename from ReactCommon/fabric/scrollview/conversions.h
rename to ReactCommon/fabric/components/scrollview/conversions.h
index e0fc07a6c50b..e7f6ba0f4ea7 100644
--- a/ReactCommon/fabric/scrollview/conversions.h
+++ b/ReactCommon/fabric/components/scrollview/conversions.h
@@ -7,7 +7,7 @@
 
 #pragma once
 
-#include <fabric/scrollview/primitives.h>
+#include <fabric/components/scrollview/primitives.h>
 #include <folly/dynamic.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/scrollview/primitives.h b/ReactCommon/fabric/components/scrollview/primitives.h
similarity index 100%
rename from ReactCommon/fabric/scrollview/primitives.h
rename to ReactCommon/fabric/components/scrollview/primitives.h
diff --git a/ReactCommon/fabric/scrollview/tests/ScrollViewTest.cpp b/ReactCommon/fabric/components/scrollview/tests/ScrollViewTest.cpp
similarity index 100%
rename from ReactCommon/fabric/scrollview/tests/ScrollViewTest.cpp
rename to ReactCommon/fabric/components/scrollview/tests/ScrollViewTest.cpp
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 52c3d1f6eb87..49af8f32ce9e 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -56,11 +56,11 @@ rn_xplat_cxx_library(
         "xplat//folly:memory",
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
+        react_native_xplat_target("fabric/components/scrollview:scrollview"),
         react_native_xplat_target("fabric/components/text:text"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/view:view"),
-        react_native_xplat_target("fabric/scrollview:scrollview"),
     ],
 )
 
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index d42adc224d26..027f7cade8c6 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -5,11 +5,11 @@
 
 #include "Scheduler.h"
 
+#include <fabric/components/scrollview/ScrollViewComponentDescriptor.h>
 #include <fabric/components/text/ParagraphComponentDescriptor.h>
 #include <fabric/components/text/RawTextComponentDescriptor.h>
 #include <fabric/components/text/TextComponentDescriptor.h>
 #include <fabric/core/LayoutContext.h>
-#include <fabric/scrollview/ScrollViewComponentDescriptor.h>
 #include <fabric/uimanager/ComponentDescriptorRegistry.h>
 #include <fabric/uimanager/FabricUIManager.h>
 #include <fabric/view/ViewComponentDescriptor.h>

From 57b0e68a2c965b7e7f0b1278eeb5828282c71f93 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:31 -0700
Subject: [PATCH 1045/1109] Fabric: `view` module was moved to `components`
 subdirectory

Summary:
@public
Trivial. We move all components into `/components/` subdirectory.

Reviewed By: mdvacca

Differential Revision: D8757011

fbshipit-source-id: 6a7da09e01184d41d37a1e1782c20d3c79371ae3
---
 .../Mounting/ComponentViews/View/RCTViewComponentView.h   | 2 +-
 .../Mounting/ComponentViews/View/RCTViewComponentView.mm  | 4 ++--
 React/Fabric/RCTConversions.h                             | 2 +-
 React/Fabric/RCTSurfaceTouchHandler.mm                    | 2 +-
 .../fabric/activityindicator/ActivityIndicatorViewProps.h | 2 +-
 .../activityindicator/ActivityIndicatorViewShadowNode.h   | 2 +-
 ReactCommon/fabric/activityindicator/BUCK                 | 2 +-
 ReactCommon/fabric/components/image/BUCK                  | 2 +-
 ReactCommon/fabric/components/image/ImageEventEmitter.h   | 2 +-
 ReactCommon/fabric/components/image/ImageProps.h          | 2 +-
 ReactCommon/fabric/components/image/ImageShadowNode.h     | 2 +-
 ReactCommon/fabric/components/scrollview/BUCK             | 2 +-
 .../fabric/components/scrollview/ScrollViewEventEmitter.h | 2 +-
 .../fabric/components/scrollview/ScrollViewProps.h        | 2 +-
 .../fabric/components/scrollview/ScrollViewShadowNode.h   | 2 +-
 ReactCommon/fabric/components/switch/BUCK                 | 2 +-
 ReactCommon/fabric/components/switch/SwitchEventEmitter.h | 2 +-
 ReactCommon/fabric/components/switch/SwitchProps.h        | 2 +-
 ReactCommon/fabric/components/switch/SwitchShadowNode.h   | 2 +-
 ReactCommon/fabric/components/text/BUCK                   | 2 +-
 .../fabric/components/text/paragraph/ParagraphProps.h     | 2 +-
 .../components/text/paragraph/ParagraphShadowNode.h       | 2 +-
 ReactCommon/fabric/{ => components}/view/BUCK             | 2 +-
 .../fabric/{ => components}/view/ConcreteViewShadowNode.h | 8 ++++----
 .../{ => components}/view/ViewComponentDescriptor.h       | 2 +-
 .../fabric/{ => components}/view/ViewEventEmitter.cpp     | 0
 .../fabric/{ => components}/view/ViewEventEmitter.h       | 0
 ReactCommon/fabric/{ => components}/view/ViewProps.cpp    | 2 +-
 ReactCommon/fabric/{ => components}/view/ViewProps.h      | 6 +++---
 .../fabric/{ => components}/view/ViewShadowNode.cpp       | 0
 ReactCommon/fabric/{ => components}/view/ViewShadowNode.h | 4 ++--
 .../view/accessibility/AccessibilityPrimitives.h          | 2 ++
 .../view/accessibility/AccessibilityProps.cpp             | 0
 .../view/accessibility/AccessibilityProps.h               | 2 +-
 .../view/accessibility/AccessibleShadowNode.cpp           | 0
 .../view/accessibility/AccessibleShadowNode.h             | 2 +-
 .../view/accessibility/accessibilityValuesConversions.cpp | 0
 .../view/accessibility/accessibilityValuesConversions.h   | 3 +--
 ReactCommon/fabric/{ => components}/view/conversions.h    | 2 +-
 ReactCommon/fabric/{ => components}/view/primitives.h     | 1 +
 .../fabric/{ => components}/view/propsConversions.h       | 2 +-
 .../fabric/{ => components}/view/root/RootProps.cpp       | 4 ++--
 ReactCommon/fabric/{ => components}/view/root/RootProps.h | 2 +-
 .../fabric/{ => components}/view/root/RootShadowNode.cpp  | 2 +-
 .../fabric/{ => components}/view/root/RootShadowNode.h    | 4 ++--
 .../fabric/{ => components}/view/tests/ViewTest.cpp       | 2 +-
 .../view/yoga/YogaLayoutableShadowNode.cpp                | 2 +-
 .../{ => components}/view/yoga/YogaLayoutableShadowNode.h | 2 +-
 .../{ => components}/view/yoga/YogaStylableProps.cpp      | 4 ++--
 .../fabric/{ => components}/view/yoga/YogaStylableProps.h | 0
 ReactCommon/fabric/uimanager/BUCK                         | 2 +-
 ReactCommon/fabric/uimanager/FabricUIManager.cpp          | 6 +++---
 ReactCommon/fabric/uimanager/Scheduler.cpp                | 6 +++---
 ReactCommon/fabric/uimanager/Scheduler.h                  | 4 ++--
 ReactCommon/fabric/uimanager/ShadowTree.h                 | 2 +-
 55 files changed, 64 insertions(+), 62 deletions(-)
 rename ReactCommon/fabric/{ => components}/view/BUCK (98%)
 rename ReactCommon/fabric/{ => components}/view/ConcreteViewShadowNode.h (95%)
 rename ReactCommon/fabric/{ => components}/view/ViewComponentDescriptor.h (89%)
 rename ReactCommon/fabric/{ => components}/view/ViewEventEmitter.cpp (100%)
 rename ReactCommon/fabric/{ => components}/view/ViewEventEmitter.h (100%)
 rename ReactCommon/fabric/{ => components}/view/ViewProps.cpp (98%)
 rename ReactCommon/fabric/{ => components}/view/ViewProps.h (90%)
 rename ReactCommon/fabric/{ => components}/view/ViewShadowNode.cpp (100%)
 rename ReactCommon/fabric/{ => components}/view/ViewShadowNode.h (85%)
 rename ReactCommon/fabric/{ => components}/view/accessibility/AccessibilityPrimitives.h (97%)
 rename ReactCommon/fabric/{ => components}/view/accessibility/AccessibilityProps.cpp (100%)
 rename ReactCommon/fabric/{ => components}/view/accessibility/AccessibilityProps.h (94%)
 rename ReactCommon/fabric/{ => components}/view/accessibility/AccessibleShadowNode.cpp (100%)
 rename ReactCommon/fabric/{ => components}/view/accessibility/AccessibleShadowNode.h (93%)
 rename ReactCommon/fabric/{ => components}/view/accessibility/accessibilityValuesConversions.cpp (100%)
 rename ReactCommon/fabric/{ => components}/view/accessibility/accessibilityValuesConversions.h (86%)
 rename ReactCommon/fabric/{ => components}/view/conversions.h (99%)
 rename ReactCommon/fabric/{ => components}/view/primitives.h (99%)
 rename ReactCommon/fabric/{ => components}/view/propsConversions.h (98%)
 rename ReactCommon/fabric/{ => components}/view/root/RootProps.cpp (91%)
 rename ReactCommon/fabric/{ => components}/view/root/RootProps.h (94%)
 rename ReactCommon/fabric/{ => components}/view/root/RootShadowNode.cpp (93%)
 rename ReactCommon/fabric/{ => components}/view/root/RootShadowNode.h (90%)
 rename ReactCommon/fabric/{ => components}/view/tests/ViewTest.cpp (83%)
 rename ReactCommon/fabric/{ => components}/view/yoga/YogaLayoutableShadowNode.cpp (99%)
 rename ReactCommon/fabric/{ => components}/view/yoga/YogaLayoutableShadowNode.h (98%)
 rename ReactCommon/fabric/{ => components}/view/yoga/YogaStylableProps.cpp (96%)
 rename ReactCommon/fabric/{ => components}/view/yoga/YogaStylableProps.h (100%)

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index d43973049dc7..2fa543e88583 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -12,7 +12,7 @@
 #import <fabric/core/EventEmitter.h>
 #import <fabric/core/LayoutMetrics.h>
 #import <fabric/core/Props.h>
-#import <fabric/view/ViewEventEmitter.h>
+#import <fabric/components/view/ViewEventEmitter.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
index 61ce1ccdc235..7b1538f9db48 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm
@@ -7,8 +7,8 @@
 
 #import "RCTViewComponentView.h"
 
-#import <fabric/view/ViewProps.h>
-#import <fabric/view/ViewEventEmitter.h>
+#import <fabric/components/view/ViewProps.h>
+#import <fabric/components/view/ViewEventEmitter.h>
 
 #import "RCTConversions.h"
 
diff --git a/React/Fabric/RCTConversions.h b/React/Fabric/RCTConversions.h
index 10cb38fb8994..e38cd04febf1 100644
--- a/React/Fabric/RCTConversions.h
+++ b/React/Fabric/RCTConversions.h
@@ -7,9 +7,9 @@
 
 #import <UIKit/UIKit.h>
 
+#import <fabric/components/view/primitives.h>
 #import <fabric/graphics/Color.h>
 #import <fabric/graphics/Geometry.h>
-#import <fabric/view/primitives.h>
 
 inline NSString *_Nullable RCTNSStringFromString(const std::string &string, const NSStringEncoding &encoding = NSUTF8StringEncoding) {
   return [NSString stringWithCString:string.c_str() encoding:encoding];
diff --git a/React/Fabric/RCTSurfaceTouchHandler.mm b/React/Fabric/RCTSurfaceTouchHandler.mm
index c26f15bb74bf..5695211236b2 100644
--- a/React/Fabric/RCTSurfaceTouchHandler.mm
+++ b/React/Fabric/RCTSurfaceTouchHandler.mm
@@ -8,7 +8,7 @@
 #import "RCTSurfaceTouchHandler.h"
 
 #import <UIKit/UIGestureRecognizerSubclass.h>
-#import <fabric/view/ViewEventEmitter.h>
+#import <fabric/components/view/ViewEventEmitter.h>
 #import <React/RCTUtils.h>
 #import <React/RCTViewComponentView.h>
 
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h
index 470d86e7dc88..7b128b308426 100644
--- a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h
+++ b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h
@@ -6,8 +6,8 @@
  */
 
 #include <fabric/activityindicator/primitives.h>
+#include <fabric/components/view/ViewProps.h>
 #include <fabric/graphics/Color.h>
-#include <fabric/view/ViewProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h
index 2cb71f2a7d66..0e57b37f7df0 100644
--- a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h
+++ b/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h
@@ -8,7 +8,7 @@
 #pragma once
 
 #include <fabric/activityindicator/ActivityIndicatorViewProps.h>
-#include <fabric/view/ConcreteViewShadowNode.h>
+#include <fabric/components/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/activityindicator/BUCK b/ReactCommon/fabric/activityindicator/BUCK
index aa4cd53f6971..3131363a7d58 100644
--- a/ReactCommon/fabric/activityindicator/BUCK
+++ b/ReactCommon/fabric/activityindicator/BUCK
@@ -46,7 +46,7 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/graphics:graphics"),
-        react_native_xplat_target("fabric/view:view"),
+        react_native_xplat_target("fabric/components/view:view"),
     ],
 )
 
diff --git a/ReactCommon/fabric/components/image/BUCK b/ReactCommon/fabric/components/image/BUCK
index 896bd5ff0e11..51b83be2f897 100644
--- a/ReactCommon/fabric/components/image/BUCK
+++ b/ReactCommon/fabric/components/image/BUCK
@@ -58,7 +58,7 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/graphics:graphics"),
         react_native_xplat_target("fabric/imagemanager:imagemanager"),
-        react_native_xplat_target("fabric/view:view"),
+        react_native_xplat_target("fabric/components/view:view"),
     ],
 )
 
diff --git a/ReactCommon/fabric/components/image/ImageEventEmitter.h b/ReactCommon/fabric/components/image/ImageEventEmitter.h
index f06fb837efd3..4cb2625aebd2 100644
--- a/ReactCommon/fabric/components/image/ImageEventEmitter.h
+++ b/ReactCommon/fabric/components/image/ImageEventEmitter.h
@@ -6,7 +6,7 @@
  */
 #pragma once
 
-#include <fabric/view/ViewEventEmitter.h>
+#include <fabric/components/view/ViewEventEmitter.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/image/ImageProps.h b/ReactCommon/fabric/components/image/ImageProps.h
index 6d772d1c99e2..fb17248179e3 100644
--- a/ReactCommon/fabric/components/image/ImageProps.h
+++ b/ReactCommon/fabric/components/image/ImageProps.h
@@ -5,9 +5,9 @@
  * LICENSE file in the root directory of this source tree.
  */
 
+#include <fabric/components/view/ViewProps.h>
 #include <fabric/graphics/Color.h>
 #include <fabric/imagemanager/primitives.h>
-#include <fabric/view/ViewProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/image/ImageShadowNode.h b/ReactCommon/fabric/components/image/ImageShadowNode.h
index 2c2d39bfc228..f8148c94dc62 100644
--- a/ReactCommon/fabric/components/image/ImageShadowNode.h
+++ b/ReactCommon/fabric/components/image/ImageShadowNode.h
@@ -9,9 +9,9 @@
 
 #include <fabric/components/image/ImageEventEmitter.h>
 #include <fabric/components/image/ImageProps.h>
+#include <fabric/components/view/ConcreteViewShadowNode.h>
 #include <fabric/imagemanager/ImageManager.h>
 #include <fabric/imagemanager/primitives.h>
-#include <fabric/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/scrollview/BUCK b/ReactCommon/fabric/components/scrollview/BUCK
index 007249e5f68e..e340c2945348 100644
--- a/ReactCommon/fabric/components/scrollview/BUCK
+++ b/ReactCommon/fabric/components/scrollview/BUCK
@@ -60,7 +60,7 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/graphics:graphics"),
-        react_native_xplat_target("fabric/view:view"),
+        react_native_xplat_target("fabric/components/view:view"),
     ],
 )
 
diff --git a/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h b/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h
index c9bd52543ad2..e72c47b1d335 100644
--- a/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h
+++ b/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h
@@ -8,9 +8,9 @@
 
 #include <memory>
 
+#include <fabric/components/view/ViewEventEmitter.h>
 #include <fabric/graphics/Geometry.h>
 #include <fabric/core/EventEmitter.h>
-#include <fabric/view/ViewEventEmitter.h>
 
 #include <folly/dynamic.h>
 
diff --git a/ReactCommon/fabric/components/scrollview/ScrollViewProps.h b/ReactCommon/fabric/components/scrollview/ScrollViewProps.h
index ff5562a6a3ba..5ad6d08b9c9c 100644
--- a/ReactCommon/fabric/components/scrollview/ScrollViewProps.h
+++ b/ReactCommon/fabric/components/scrollview/ScrollViewProps.h
@@ -8,7 +8,7 @@
 #pragma once
 
 #include <fabric/components/scrollview/primitives.h>
-#include <fabric/view/ViewProps.h>
+#include <fabric/components/view/ViewProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.h b/ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.h
index 1c8f77830cb2..aa4ed58df208 100644
--- a/ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.h
+++ b/ReactCommon/fabric/components/scrollview/ScrollViewShadowNode.h
@@ -11,8 +11,8 @@
 
 #include <fabric/components/scrollview/ScrollViewEventEmitter.h>
 #include <fabric/components/scrollview/ScrollViewProps.h>
+#include <fabric/components/view/ConcreteViewShadowNode.h>
 #include <fabric/core/LayoutContext.h>
-#include <fabric/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/switch/BUCK b/ReactCommon/fabric/components/switch/BUCK
index 3026a706193f..52d146dc4cf2 100644
--- a/ReactCommon/fabric/components/switch/BUCK
+++ b/ReactCommon/fabric/components/switch/BUCK
@@ -56,7 +56,7 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/graphics:graphics"),
-        react_native_xplat_target("fabric/view:view"),
+        react_native_xplat_target("fabric/components/view:view"),
     ],
 )
 
diff --git a/ReactCommon/fabric/components/switch/SwitchEventEmitter.h b/ReactCommon/fabric/components/switch/SwitchEventEmitter.h
index 2f1cf3733fd6..6e2a0c68d172 100644
--- a/ReactCommon/fabric/components/switch/SwitchEventEmitter.h
+++ b/ReactCommon/fabric/components/switch/SwitchEventEmitter.h
@@ -6,7 +6,7 @@
  */
 #pragma once
 
-#include <fabric/view/ViewEventEmitter.h>
+#include <fabric/components/view/ViewEventEmitter.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/switch/SwitchProps.h b/ReactCommon/fabric/components/switch/SwitchProps.h
index 6ddac619b4b4..83f4aa21266c 100644
--- a/ReactCommon/fabric/components/switch/SwitchProps.h
+++ b/ReactCommon/fabric/components/switch/SwitchProps.h
@@ -5,8 +5,8 @@
  * LICENSE file in the root directory of this source tree.
  */
 
+#include <fabric/components/view/ViewProps.h>
 #include <fabric/graphics/Color.h>
-#include <fabric/view/ViewProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/switch/SwitchShadowNode.h b/ReactCommon/fabric/components/switch/SwitchShadowNode.h
index b94256c74d2a..be4d6f5e751f 100644
--- a/ReactCommon/fabric/components/switch/SwitchShadowNode.h
+++ b/ReactCommon/fabric/components/switch/SwitchShadowNode.h
@@ -9,7 +9,7 @@
 
 #include <fabric/components/switch/SwitchEventEmitter.h>
 #include <fabric/components/switch/SwitchProps.h>
-#include <fabric/view/ConcreteViewShadowNode.h>
+#include <fabric/components/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/text/BUCK b/ReactCommon/fabric/components/text/BUCK
index c9711245d753..fdba22d649a5 100644
--- a/ReactCommon/fabric/components/text/BUCK
+++ b/ReactCommon/fabric/components/text/BUCK
@@ -66,7 +66,7 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/debug:debug"),
         react_native_xplat_target("fabric/graphics:graphics"),
         react_native_xplat_target("fabric/textlayoutmanager:textlayoutmanager"),
-        react_native_xplat_target("fabric/view:view"),
+        react_native_xplat_target("fabric/components/view:view"),
     ],
 )
 
diff --git a/ReactCommon/fabric/components/text/paragraph/ParagraphProps.h b/ReactCommon/fabric/components/text/paragraph/ParagraphProps.h
index f31789eacbe0..f7e533d2095f 100644
--- a/ReactCommon/fabric/components/text/paragraph/ParagraphProps.h
+++ b/ReactCommon/fabric/components/text/paragraph/ParagraphProps.h
@@ -12,8 +12,8 @@
 
 #include <fabric/attributedstring/ParagraphAttributes.h>
 #include <fabric/components/text/BaseTextProps.h>
+#include <fabric/components/view/ViewProps.h>
 #include <fabric/core/Props.h>
-#include <fabric/view/ViewProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.h b/ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.h
index c18be91d7b43..bb81b91755a9 100644
--- a/ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.h
+++ b/ReactCommon/fabric/components/text/paragraph/ParagraphShadowNode.h
@@ -9,11 +9,11 @@
 
 #include <fabric/components/text/ParagraphProps.h>
 #include <fabric/components/text/TextShadowNode.h>
+#include <fabric/components/view/ConcreteViewShadowNode.h>
 #include <fabric/core/ConcreteShadowNode.h>
 #include <fabric/core/ShadowNode.h>
 #include <fabric/core/LayoutContext.h>
 #include <fabric/textlayoutmanager/TextLayoutManager.h>
-#include <fabric/view/ConcreteViewShadowNode.h>
 #include <folly/Optional.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/view/BUCK b/ReactCommon/fabric/components/view/BUCK
similarity index 98%
rename from ReactCommon/fabric/view/BUCK
rename to ReactCommon/fabric/components/view/BUCK
index 54dc9ef2032e..0aa0b6b3c7f5 100644
--- a/ReactCommon/fabric/view/BUCK
+++ b/ReactCommon/fabric/components/view/BUCK
@@ -31,7 +31,7 @@ rn_xplat_cxx_library(
             ("root", "*.h"),
             ("yoga", "*.h"),
         ],
-        prefix = "fabric/view",
+        prefix = "fabric/components/view",
     ),
     compiler_flags = [
         "-fexceptions",
diff --git a/ReactCommon/fabric/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
similarity index 95%
rename from ReactCommon/fabric/view/ConcreteViewShadowNode.h
rename to ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
index 38f0c966deff..db7b9a660173 100644
--- a/ReactCommon/fabric/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
@@ -7,14 +7,14 @@
 
 #pragma once
 
+#include <fabric/components/view/AccessibleShadowNode.h>
+#include <fabric/components/view/ViewEventEmitter.h>
+#include <fabric/components/view/ViewProps.h>
+#include <fabric/components/view/YogaLayoutableShadowNode.h>
 #include <fabric/core/ConcreteShadowNode.h>
 #include <fabric/core/LayoutableShadowNode.h>
 #include <fabric/core/ShadowNode.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/view/AccessibleShadowNode.h>
-#include <fabric/view/ViewEventEmitter.h>
-#include <fabric/view/ViewProps.h>
-#include <fabric/view/YogaLayoutableShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/ViewComponentDescriptor.h b/ReactCommon/fabric/components/view/ViewComponentDescriptor.h
similarity index 89%
rename from ReactCommon/fabric/view/ViewComponentDescriptor.h
rename to ReactCommon/fabric/components/view/ViewComponentDescriptor.h
index 4c25d8b943b6..47cbe2e575c0 100644
--- a/ReactCommon/fabric/view/ViewComponentDescriptor.h
+++ b/ReactCommon/fabric/components/view/ViewComponentDescriptor.h
@@ -7,8 +7,8 @@
 
 #pragma once
 
+#include <fabric/components/view/ViewShadowNode.h>
 #include <fabric/core/ConcreteComponentDescriptor.h>
-#include <fabric/view/ViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/ViewEventEmitter.cpp b/ReactCommon/fabric/components/view/ViewEventEmitter.cpp
similarity index 100%
rename from ReactCommon/fabric/view/ViewEventEmitter.cpp
rename to ReactCommon/fabric/components/view/ViewEventEmitter.cpp
diff --git a/ReactCommon/fabric/view/ViewEventEmitter.h b/ReactCommon/fabric/components/view/ViewEventEmitter.h
similarity index 100%
rename from ReactCommon/fabric/view/ViewEventEmitter.h
rename to ReactCommon/fabric/components/view/ViewEventEmitter.h
diff --git a/ReactCommon/fabric/view/ViewProps.cpp b/ReactCommon/fabric/components/view/ViewProps.cpp
similarity index 98%
rename from ReactCommon/fabric/view/ViewProps.cpp
rename to ReactCommon/fabric/components/view/ViewProps.cpp
index 36d33216098b..72af1c675c03 100644
--- a/ReactCommon/fabric/view/ViewProps.cpp
+++ b/ReactCommon/fabric/components/view/ViewProps.cpp
@@ -7,10 +7,10 @@
 
 #include "ViewProps.h"
 
+#include <fabric/components/view/conversions.h>
 #include <fabric/core/propsConversions.h>
 #include <fabric/debug/debugStringConvertibleUtils.h>
 #include <fabric/graphics/conversions.h>
-#include <fabric/view/conversions.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/ViewProps.h b/ReactCommon/fabric/components/view/ViewProps.h
similarity index 90%
rename from ReactCommon/fabric/view/ViewProps.h
rename to ReactCommon/fabric/components/view/ViewProps.h
index a533b051ff89..d9d9e6143b28 100644
--- a/ReactCommon/fabric/view/ViewProps.h
+++ b/ReactCommon/fabric/components/view/ViewProps.h
@@ -7,12 +7,12 @@
 
 #pragma once
 
+#include <fabric/components/view/AccessibilityProps.h>
+#include <fabric/components/view/primitives.h>
+#include <fabric/components/view/YogaStylableProps.h>
 #include <fabric/core/Props.h>
 #include <fabric/graphics/Geometry.h>
 #include <fabric/graphics/Color.h>
-#include <fabric/view/AccessibilityProps.h>
-#include <fabric/view/primitives.h>
-#include <fabric/view/YogaStylableProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/ViewShadowNode.cpp b/ReactCommon/fabric/components/view/ViewShadowNode.cpp
similarity index 100%
rename from ReactCommon/fabric/view/ViewShadowNode.cpp
rename to ReactCommon/fabric/components/view/ViewShadowNode.cpp
diff --git a/ReactCommon/fabric/view/ViewShadowNode.h b/ReactCommon/fabric/components/view/ViewShadowNode.h
similarity index 85%
rename from ReactCommon/fabric/view/ViewShadowNode.h
rename to ReactCommon/fabric/components/view/ViewShadowNode.h
index a406f34de8a9..8fa20ebad825 100644
--- a/ReactCommon/fabric/view/ViewShadowNode.h
+++ b/ReactCommon/fabric/components/view/ViewShadowNode.h
@@ -9,8 +9,8 @@
 
 #include <memory>
 
-#include <fabric/view/ViewProps.h>
-#include <fabric/view/ConcreteViewShadowNode.h>
+#include <fabric/components/view/ViewProps.h>
+#include <fabric/components/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityPrimitives.h b/ReactCommon/fabric/components/view/accessibility/AccessibilityPrimitives.h
similarity index 97%
rename from ReactCommon/fabric/view/accessibility/AccessibilityPrimitives.h
rename to ReactCommon/fabric/components/view/accessibility/AccessibilityPrimitives.h
index 60e73f1c485b..01ddabb9ea7e 100644
--- a/ReactCommon/fabric/view/accessibility/AccessibilityPrimitives.h
+++ b/ReactCommon/fabric/components/view/accessibility/AccessibilityPrimitives.h
@@ -7,6 +7,8 @@
 
 #pragma once
 
+#include <cinttypes>
+
 namespace facebook {
 namespace react {
 
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp b/ReactCommon/fabric/components/view/accessibility/AccessibilityProps.cpp
similarity index 100%
rename from ReactCommon/fabric/view/accessibility/AccessibilityProps.cpp
rename to ReactCommon/fabric/components/view/accessibility/AccessibilityProps.cpp
diff --git a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h b/ReactCommon/fabric/components/view/accessibility/AccessibilityProps.h
similarity index 94%
rename from ReactCommon/fabric/view/accessibility/AccessibilityProps.h
rename to ReactCommon/fabric/components/view/accessibility/AccessibilityProps.h
index 931edc8d3009..d1682c687168 100644
--- a/ReactCommon/fabric/view/accessibility/AccessibilityProps.h
+++ b/ReactCommon/fabric/components/view/accessibility/AccessibilityProps.h
@@ -7,10 +7,10 @@
 
 #pragma once
 
+#include <fabric/components/view/AccessibilityPrimitives.h>
 #include <fabric/core/Props.h>
 #include <fabric/core/ReactPrimitives.h>
 #include <fabric/debug/DebugStringConvertible.h>
-#include <fabric/view/AccessibilityPrimitives.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.cpp b/ReactCommon/fabric/components/view/accessibility/AccessibleShadowNode.cpp
similarity index 100%
rename from ReactCommon/fabric/view/accessibility/AccessibleShadowNode.cpp
rename to ReactCommon/fabric/components/view/accessibility/AccessibleShadowNode.cpp
diff --git a/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.h b/ReactCommon/fabric/components/view/accessibility/AccessibleShadowNode.h
similarity index 93%
rename from ReactCommon/fabric/view/accessibility/AccessibleShadowNode.h
rename to ReactCommon/fabric/components/view/accessibility/AccessibleShadowNode.h
index 1fa8316ba6d4..f893b0dcdca4 100644
--- a/ReactCommon/fabric/view/accessibility/AccessibleShadowNode.h
+++ b/ReactCommon/fabric/components/view/accessibility/AccessibleShadowNode.h
@@ -9,8 +9,8 @@
 
 #include <memory>
 
+#include <fabric/components/view/AccessibilityProps.h>
 #include <fabric/core/ShadowNode.h>
-#include <fabric/view/AccessibilityProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.cpp b/ReactCommon/fabric/components/view/accessibility/accessibilityValuesConversions.cpp
similarity index 100%
rename from ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.cpp
rename to ReactCommon/fabric/components/view/accessibility/accessibilityValuesConversions.cpp
diff --git a/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.h b/ReactCommon/fabric/components/view/accessibility/accessibilityValuesConversions.h
similarity index 86%
rename from ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.h
rename to ReactCommon/fabric/components/view/accessibility/accessibilityValuesConversions.h
index 7240a7cd9aa6..97913d3e2663 100644
--- a/ReactCommon/fabric/view/accessibility/accessibilityValuesConversions.h
+++ b/ReactCommon/fabric/components/view/accessibility/accessibilityValuesConversions.h
@@ -7,10 +7,9 @@
 
 #pragma once
 
+#include <fabric/components/view/AccessibilityPrimitives.h>
 #include <folly/dynamic.h>
 
-#include <fabric/view/AccessibilityPrimitives.h>
-
 namespace facebook {
 namespace react {
 
diff --git a/ReactCommon/fabric/view/conversions.h b/ReactCommon/fabric/components/view/conversions.h
similarity index 99%
rename from ReactCommon/fabric/view/conversions.h
rename to ReactCommon/fabric/components/view/conversions.h
index 64f1478d4d63..e34b65f1c3ea 100644
--- a/ReactCommon/fabric/view/conversions.h
+++ b/ReactCommon/fabric/components/view/conversions.h
@@ -7,9 +7,9 @@
 
 #pragma once
 
+#include <fabric/components/view/primitives.h>
 #include <fabric/core/LayoutMetrics.h>
 #include <fabric/graphics/Geometry.h>
-#include <fabric/view/primitives.h>
 #include <folly/dynamic.h>
 #include <folly/Conv.h>
 #include <yoga/Yoga.h>
diff --git a/ReactCommon/fabric/view/primitives.h b/ReactCommon/fabric/components/view/primitives.h
similarity index 99%
rename from ReactCommon/fabric/view/primitives.h
rename to ReactCommon/fabric/components/view/primitives.h
index f7814c041529..c7239ec3e9c9 100644
--- a/ReactCommon/fabric/view/primitives.h
+++ b/ReactCommon/fabric/components/view/primitives.h
@@ -8,6 +8,7 @@
 #pragma once
 
 #include <cmath>
+#include <fabric/graphics/Geometry.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/propsConversions.h b/ReactCommon/fabric/components/view/propsConversions.h
similarity index 98%
rename from ReactCommon/fabric/view/propsConversions.h
rename to ReactCommon/fabric/components/view/propsConversions.h
index 8a8cfe099a59..80146b59fe8c 100644
--- a/ReactCommon/fabric/view/propsConversions.h
+++ b/ReactCommon/fabric/components/view/propsConversions.h
@@ -7,8 +7,8 @@
 
 #pragma once
 
+#include <fabric/components/view/conversions.h>
 #include <fabric/core/propsConversions.h>
-#include <fabric/view/conversions.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/root/RootProps.cpp b/ReactCommon/fabric/components/view/root/RootProps.cpp
similarity index 91%
rename from ReactCommon/fabric/view/root/RootProps.cpp
rename to ReactCommon/fabric/components/view/root/RootProps.cpp
index fe9f711d3ac2..f3c65e38db8c 100644
--- a/ReactCommon/fabric/view/root/RootProps.cpp
+++ b/ReactCommon/fabric/components/view/root/RootProps.cpp
@@ -7,8 +7,8 @@
 
 #include "RootProps.h"
 
-#include <fabric/view/conversions.h>
-#include <fabric/view/YogaLayoutableShadowNode.h>
+#include <fabric/components/view/conversions.h>
+#include <fabric/components/view/YogaLayoutableShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/root/RootProps.h b/ReactCommon/fabric/components/view/root/RootProps.h
similarity index 94%
rename from ReactCommon/fabric/view/root/RootProps.h
rename to ReactCommon/fabric/components/view/root/RootProps.h
index f26c53c71815..b6c4a2ae58f4 100644
--- a/ReactCommon/fabric/view/root/RootProps.h
+++ b/ReactCommon/fabric/components/view/root/RootProps.h
@@ -9,9 +9,9 @@
 
 #include <memory>
 
+#include <fabric/components/view/ViewProps.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/core/LayoutContext.h>
-#include <fabric/view/ViewProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/root/RootShadowNode.cpp b/ReactCommon/fabric/components/view/root/RootShadowNode.cpp
similarity index 93%
rename from ReactCommon/fabric/view/root/RootShadowNode.cpp
rename to ReactCommon/fabric/components/view/root/RootShadowNode.cpp
index 970eb8db7766..045be456914a 100644
--- a/ReactCommon/fabric/view/root/RootShadowNode.cpp
+++ b/ReactCommon/fabric/components/view/root/RootShadowNode.cpp
@@ -7,7 +7,7 @@
 
 #include "RootShadowNode.h"
 
-#include <fabric/view/conversions.h>
+#include <fabric/components/view/conversions.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/root/RootShadowNode.h b/ReactCommon/fabric/components/view/root/RootShadowNode.h
similarity index 90%
rename from ReactCommon/fabric/view/root/RootShadowNode.h
rename to ReactCommon/fabric/components/view/root/RootShadowNode.h
index 6508fa587218..535b8bdb8870 100644
--- a/ReactCommon/fabric/view/root/RootShadowNode.h
+++ b/ReactCommon/fabric/components/view/root/RootShadowNode.h
@@ -9,9 +9,9 @@
 
 #include <memory>
 
+#include <fabric/components/view/RootProps.h>
+#include <fabric/components/view/ConcreteViewShadowNode.h>
 #include <fabric/core/LayoutContext.h>
-#include <fabric/view/RootProps.h>
-#include <fabric/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/tests/ViewTest.cpp b/ReactCommon/fabric/components/view/tests/ViewTest.cpp
similarity index 83%
rename from ReactCommon/fabric/view/tests/ViewTest.cpp
rename to ReactCommon/fabric/components/view/tests/ViewTest.cpp
index 6ea577d8fa52..af1468dc6234 100644
--- a/ReactCommon/fabric/view/tests/ViewTest.cpp
+++ b/ReactCommon/fabric/components/view/tests/ViewTest.cpp
@@ -7,7 +7,7 @@
 
 #include <memory>
 
-#include <fabric/view/ViewComponentDescriptor.h>
+#include <fabric/components/view/ViewComponentDescriptor.h>
 #include <gtest/gtest.h>
 
 using namespace facebook::react;
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
similarity index 99%
rename from ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
rename to ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
index 34b0f372fa84..7106ccf65755 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
@@ -10,10 +10,10 @@
 #include <algorithm>
 #include <memory>
 
+#include <fabric/components/view/conversions.h>
 #include <fabric/core/LayoutContext.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/view/conversions.h>
 #include <yoga/Yoga.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.h
similarity index 98%
rename from ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
rename to ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.h
index c35b812af77e..a61b20c3a7ca 100644
--- a/ReactCommon/fabric/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.h
@@ -12,11 +12,11 @@
 
 #include <yoga/YGNode.h>
 
+#include <fabric/components/view/YogaStylableProps.h>
 #include <fabric/core/LayoutableShadowNode.h>
 #include <fabric/core/Sealable.h>
 #include <fabric/core/ShadowNode.h>
 #include <fabric/debug/DebugStringConvertible.h>
-#include <fabric/view/YogaStylableProps.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp b/ReactCommon/fabric/components/view/yoga/YogaStylableProps.cpp
similarity index 96%
rename from ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
rename to ReactCommon/fabric/components/view/yoga/YogaStylableProps.cpp
index d89686b5366e..165c7195cbe0 100644
--- a/ReactCommon/fabric/view/yoga/YogaStylableProps.cpp
+++ b/ReactCommon/fabric/components/view/yoga/YogaStylableProps.cpp
@@ -7,9 +7,9 @@
 
 #include "YogaStylableProps.h"
 
-#include <fabric/view/conversions.h>
+#include <fabric/components/view/conversions.h>
 #include <fabric/core/propsConversions.h>
-#include <fabric/view/propsConversions.h>
+#include <fabric/components/view/propsConversions.h>
 #include <fabric/debug/debugStringConvertibleUtils.h>
 #include <yoga/YGNode.h>
 #include <yoga/Yoga.h>
diff --git a/ReactCommon/fabric/view/yoga/YogaStylableProps.h b/ReactCommon/fabric/components/view/yoga/YogaStylableProps.h
similarity index 100%
rename from ReactCommon/fabric/view/yoga/YogaStylableProps.h
rename to ReactCommon/fabric/components/view/yoga/YogaStylableProps.h
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 49af8f32ce9e..727fbbd0c060 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -60,7 +60,7 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/components/text:text"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/debug:debug"),
-        react_native_xplat_target("fabric/view:view"),
+        react_native_xplat_target("fabric/components/view:view"),
     ],
 )
 
diff --git a/ReactCommon/fabric/uimanager/FabricUIManager.cpp b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
index 9e20dd056361..0d6511d6ea14 100644
--- a/ReactCommon/fabric/uimanager/FabricUIManager.cpp
+++ b/ReactCommon/fabric/uimanager/FabricUIManager.cpp
@@ -9,13 +9,13 @@
 
 #include <glog/logging.h>
 
+#include <fabric/components/view/ViewComponentDescriptor.h>
+#include <fabric/components/view/ViewProps.h>
+#include <fabric/components/view/ViewShadowNode.h>
 #include <fabric/core/componentDescriptor.h>
 #include <fabric/core/LayoutContext.h>
 #include <fabric/debug/DebugStringConvertible.h>
 #include <fabric/debug/DebugStringConvertibleItem.h>
-#include <fabric/view/ViewComponentDescriptor.h>
-#include <fabric/view/ViewProps.h>
-#include <fabric/view/ViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index 027f7cade8c6..ad1b42d75881 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -9,12 +9,12 @@
 #include <fabric/components/text/ParagraphComponentDescriptor.h>
 #include <fabric/components/text/RawTextComponentDescriptor.h>
 #include <fabric/components/text/TextComponentDescriptor.h>
+#include <fabric/components/view/ViewComponentDescriptor.h>
+#include <fabric/components/view/ViewProps.h>
+#include <fabric/components/view/ViewShadowNode.h>
 #include <fabric/core/LayoutContext.h>
 #include <fabric/uimanager/ComponentDescriptorRegistry.h>
 #include <fabric/uimanager/FabricUIManager.h>
-#include <fabric/view/ViewComponentDescriptor.h>
-#include <fabric/view/ViewProps.h>
-#include <fabric/view/ViewShadowNode.h>
 
 #include "ComponentDescriptorFactory.h"
 #include "Differentiator.h"
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index 036d3cef4865..ed13ba2de301 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -7,6 +7,8 @@
 
 #include <memory>
 
+#include <fabric/components/view/ViewShadowNode.h>
+#include <fabric/components/view/RootShadowNode.h>
 #include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/uimanager/ContextContainer.h>
@@ -15,8 +17,6 @@
 #include <fabric/uimanager/UIManagerDelegate.h>
 #include <fabric/uimanager/ShadowTree.h>
 #include <fabric/uimanager/ShadowTreeDelegate.h>
-#include <fabric/view/ViewShadowNode.h>
-#include <fabric/view/RootShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.h b/ReactCommon/fabric/uimanager/ShadowTree.h
index 26927fc8b631..f9bb361d6a54 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.h
+++ b/ReactCommon/fabric/uimanager/ShadowTree.h
@@ -8,11 +8,11 @@
 #include <memory>
 #include <mutex>
 
+#include <fabric/components/view/RootShadowNode.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/core/ReactPrimitives.h>
 #include <fabric/core/ShadowNode.h>
 #include <fabric/uimanager/ShadowTreeDelegate.h>
-#include <fabric/view/RootShadowNode.h>
 
 namespace facebook {
 namespace react {

From 95bd4a0a9e073cd11d0e686422a0482aa7a14be2 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:33 -0700
Subject: [PATCH 1046/1109] Fabric: `activityindicator` module was moved to
 `components` subdirectory

Summary:
@public
Trivial. We move all components into `/components/` subdirectory.

Reviewed By: mdvacca

Differential Revision: D8757015

fbshipit-source-id: 9b676728bf1aa4aa14345fa11a5b4a1f9f7ed472
---
 .../RCTActivityIndicatorViewComponentView.mm                  | 2 +-
 .../ActivityIndicatorViewComponentDescriptor.h                | 2 +-
 .../activityindicator/ActivityIndicatorViewProps.cpp          | 4 ++--
 .../activityindicator/ActivityIndicatorViewProps.h            | 2 +-
 .../activityindicator/ActivityIndicatorViewShadowNode.cpp     | 2 +-
 .../activityindicator/ActivityIndicatorViewShadowNode.h       | 2 +-
 ReactCommon/fabric/{ => components}/activityindicator/BUCK    | 2 +-
 .../fabric/{ => components}/activityindicator/conversions.h   | 2 +-
 .../fabric/{ => components}/activityindicator/primitives.h    | 0
 .../activityindicator/tests/ActivityIndicatorViewTest.cpp     | 0
 10 files changed, 9 insertions(+), 9 deletions(-)
 rename ReactCommon/fabric/{ => components}/activityindicator/ActivityIndicatorViewComponentDescriptor.h (84%)
 rename ReactCommon/fabric/{ => components}/activityindicator/ActivityIndicatorViewProps.cpp (84%)
 rename ReactCommon/fabric/{ => components}/activityindicator/ActivityIndicatorViewProps.h (93%)
 rename ReactCommon/fabric/{ => components}/activityindicator/ActivityIndicatorViewShadowNode.cpp (83%)
 rename ReactCommon/fabric/{ => components}/activityindicator/ActivityIndicatorViewShadowNode.h (89%)
 rename ReactCommon/fabric/{ => components}/activityindicator/BUCK (97%)
 rename ReactCommon/fabric/{ => components}/activityindicator/conversions.h (93%)
 rename ReactCommon/fabric/{ => components}/activityindicator/primitives.h (100%)
 rename ReactCommon/fabric/{ => components}/activityindicator/tests/ActivityIndicatorViewTest.cpp (100%)

diff --git a/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm b/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
index e275169a1c38..2e883cb0c9cb 100644
--- a/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/ActivityIndicator/RCTActivityIndicatorViewComponentView.mm
@@ -7,7 +7,7 @@
 
 #import "RCTActivityIndicatorViewComponentView.h"
 
-#import <fabric/activityindicator/ActivityIndicatorViewProps.h>
+#import <fabric/components/activityindicator/ActivityIndicatorViewProps.h>
 
 using namespace facebook::react;
 
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewComponentDescriptor.h b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewComponentDescriptor.h
similarity index 84%
rename from ReactCommon/fabric/activityindicator/ActivityIndicatorViewComponentDescriptor.h
rename to ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewComponentDescriptor.h
index 933b8ad59950..81ce66cacda6 100644
--- a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewComponentDescriptor.h
+++ b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewComponentDescriptor.h
@@ -7,7 +7,7 @@
 
 #pragma once
 
-#include <fabric/activityindicator/ActivityIndicatorViewShadowNode.h>
+#include <fabric/components/activityindicator/ActivityIndicatorViewShadowNode.h>
 #include <fabric/core/ConcreteComponentDescriptor.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.cpp b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewProps.cpp
similarity index 84%
rename from ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.cpp
rename to ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewProps.cpp
index cfe19d0eef69..5f0441f3bee2 100644
--- a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.cpp
+++ b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewProps.cpp
@@ -5,8 +5,8 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#include <fabric/activityindicator/ActivityIndicatorViewProps.h>
-#include <fabric/activityindicator/conversions.h>
+#include <fabric/components/activityindicator/ActivityIndicatorViewProps.h>
+#include <fabric/components/activityindicator/conversions.h>
 #include <fabric/core/propsConversions.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewProps.h
similarity index 93%
rename from ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h
rename to ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewProps.h
index 7b128b308426..5a960642e82e 100644
--- a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewProps.h
+++ b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewProps.h
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#include <fabric/activityindicator/primitives.h>
+#include <fabric/components/activityindicator/primitives.h>
 #include <fabric/components/view/ViewProps.h>
 #include <fabric/graphics/Color.h>
 
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.cpp b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewShadowNode.cpp
similarity index 83%
rename from ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.cpp
rename to ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewShadowNode.cpp
index d6a512930a9c..a19b2f717cfd 100644
--- a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.cpp
+++ b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewShadowNode.cpp
@@ -5,7 +5,7 @@
  * LICENSE file in the root directory of this source tree.
  */
 
-#include <fabric/activityindicator/ActivityIndicatorViewShadowNode.h>
+#include <fabric/components/activityindicator/ActivityIndicatorViewShadowNode.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewShadowNode.h
similarity index 89%
rename from ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h
rename to ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewShadowNode.h
index 0e57b37f7df0..c93462d8403c 100644
--- a/ReactCommon/fabric/activityindicator/ActivityIndicatorViewShadowNode.h
+++ b/ReactCommon/fabric/components/activityindicator/ActivityIndicatorViewShadowNode.h
@@ -7,7 +7,7 @@
 
 #pragma once
 
-#include <fabric/activityindicator/ActivityIndicatorViewProps.h>
+#include <fabric/components/activityindicator/ActivityIndicatorViewProps.h>
 #include <fabric/components/view/ConcreteViewShadowNode.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/activityindicator/BUCK b/ReactCommon/fabric/components/activityindicator/BUCK
similarity index 97%
rename from ReactCommon/fabric/activityindicator/BUCK
rename to ReactCommon/fabric/components/activityindicator/BUCK
index 3131363a7d58..279f207d8014 100644
--- a/ReactCommon/fabric/activityindicator/BUCK
+++ b/ReactCommon/fabric/components/activityindicator/BUCK
@@ -15,7 +15,7 @@ rn_xplat_cxx_library(
         [
             ("", "*.h"),
         ],
-        prefix = "fabric/activityindicator",
+        prefix = "fabric/components/activityindicator",
     ),
     compiler_flags = [
         "-fexceptions",
diff --git a/ReactCommon/fabric/activityindicator/conversions.h b/ReactCommon/fabric/components/activityindicator/conversions.h
similarity index 93%
rename from ReactCommon/fabric/activityindicator/conversions.h
rename to ReactCommon/fabric/components/activityindicator/conversions.h
index 33b56b05fa9c..6d04cca3196b 100644
--- a/ReactCommon/fabric/activityindicator/conversions.h
+++ b/ReactCommon/fabric/components/activityindicator/conversions.h
@@ -7,7 +7,7 @@
 
 #pragma once
 
-#include <fabric/activityindicator/primitives.h>
+#include <fabric/components/activityindicator/primitives.h>
 #include <folly/dynamic.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/activityindicator/primitives.h b/ReactCommon/fabric/components/activityindicator/primitives.h
similarity index 100%
rename from ReactCommon/fabric/activityindicator/primitives.h
rename to ReactCommon/fabric/components/activityindicator/primitives.h
diff --git a/ReactCommon/fabric/activityindicator/tests/ActivityIndicatorViewTest.cpp b/ReactCommon/fabric/components/activityindicator/tests/ActivityIndicatorViewTest.cpp
similarity index 100%
rename from ReactCommon/fabric/activityindicator/tests/ActivityIndicatorViewTest.cpp
rename to ReactCommon/fabric/components/activityindicator/tests/ActivityIndicatorViewTest.cpp

From e9e20e6c8335f27af8469cd23cb7ba079b0422f9 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Sun, 15 Jul 2018 16:46:35 -0700
Subject: [PATCH 1047/1109] Fabric: <Root> component was decoupled from <View>

Summary:
@public
There is no reason to have it inside View; it deserves that.

Reviewed By: mdvacca

Differential Revision: D8757012

fbshipit-source-id: 881b54008b51614cd203ab97811494fa7c30e4ef
---
 ReactCommon/fabric/components/root/BUCK       | 79 +++++++++++++++++++
 .../components/{view => }/root/RootProps.cpp  |  0
 .../components/{view => }/root/RootProps.h    |  0
 .../{view => }/root/RootShadowNode.cpp        |  0
 .../{view => }/root/RootShadowNode.h          |  2 +-
 .../root/tests/RootShadowNodeTest.cpp         | 14 ++++
 ReactCommon/fabric/uimanager/BUCK             |  5 +-
 ReactCommon/fabric/uimanager/Scheduler.cpp    |  7 --
 ReactCommon/fabric/uimanager/Scheduler.h      |  2 -
 ReactCommon/fabric/uimanager/ShadowTree.h     |  2 +-
 10 files changed, 97 insertions(+), 14 deletions(-)
 create mode 100644 ReactCommon/fabric/components/root/BUCK
 rename ReactCommon/fabric/components/{view => }/root/RootProps.cpp (100%)
 rename ReactCommon/fabric/components/{view => }/root/RootProps.h (100%)
 rename ReactCommon/fabric/components/{view => }/root/RootShadowNode.cpp (100%)
 rename ReactCommon/fabric/components/{view => }/root/RootShadowNode.h (95%)
 create mode 100644 ReactCommon/fabric/components/root/tests/RootShadowNodeTest.cpp

diff --git a/ReactCommon/fabric/components/root/BUCK b/ReactCommon/fabric/components/root/BUCK
new file mode 100644
index 000000000000..d25d012e708b
--- /dev/null
+++ b/ReactCommon/fabric/components/root/BUCK
@@ -0,0 +1,79 @@
+load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
+
+APPLE_COMPILER_FLAGS = []
+
+if not IS_OSS_BUILD:
+    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+
+    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+
+rn_xplat_cxx_library(
+    name = "root",
+    srcs = glob(
+        ["**/*.cpp"],
+        exclude = glob(["tests/**/*.cpp"]),
+    ),
+    headers = [],
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/components/root",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        "xplat//yoga:yoga",
+        react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/core:core"),
+        react_native_xplat_target("fabric/graphics:graphics"),
+        react_native_xplat_target("fabric/components/view:view"),
+    ],
+)
+
+if not IS_OSS_BUILD:
+    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
+
+    fb_xplat_cxx_test(
+        name = "tests",
+        srcs = glob(["tests/**/*.cpp"]),
+        headers = glob(["tests/**/*.h"]),
+        contacts = ["oncall+react_native@xmail.facebook.com"],
+        compiler_flags = [
+            "-fexceptions",
+            "-frtti",
+            "-std=c++14",
+            "-Wall",
+        ],
+        platforms = APPLE,
+        deps = [
+            "xplat//folly:molly",
+            "xplat//third-party/gmock:gtest",
+            ":root",
+        ],
+    )
diff --git a/ReactCommon/fabric/components/view/root/RootProps.cpp b/ReactCommon/fabric/components/root/RootProps.cpp
similarity index 100%
rename from ReactCommon/fabric/components/view/root/RootProps.cpp
rename to ReactCommon/fabric/components/root/RootProps.cpp
diff --git a/ReactCommon/fabric/components/view/root/RootProps.h b/ReactCommon/fabric/components/root/RootProps.h
similarity index 100%
rename from ReactCommon/fabric/components/view/root/RootProps.h
rename to ReactCommon/fabric/components/root/RootProps.h
diff --git a/ReactCommon/fabric/components/view/root/RootShadowNode.cpp b/ReactCommon/fabric/components/root/RootShadowNode.cpp
similarity index 100%
rename from ReactCommon/fabric/components/view/root/RootShadowNode.cpp
rename to ReactCommon/fabric/components/root/RootShadowNode.cpp
diff --git a/ReactCommon/fabric/components/view/root/RootShadowNode.h b/ReactCommon/fabric/components/root/RootShadowNode.h
similarity index 95%
rename from ReactCommon/fabric/components/view/root/RootShadowNode.h
rename to ReactCommon/fabric/components/root/RootShadowNode.h
index 535b8bdb8870..b6d96db38da1 100644
--- a/ReactCommon/fabric/components/view/root/RootShadowNode.h
+++ b/ReactCommon/fabric/components/root/RootShadowNode.h
@@ -9,7 +9,7 @@
 
 #include <memory>
 
-#include <fabric/components/view/RootProps.h>
+#include <fabric/components/root/RootProps.h>
 #include <fabric/components/view/ConcreteViewShadowNode.h>
 #include <fabric/core/LayoutContext.h>
 
diff --git a/ReactCommon/fabric/components/root/tests/RootShadowNodeTest.cpp b/ReactCommon/fabric/components/root/tests/RootShadowNodeTest.cpp
new file mode 100644
index 000000000000..776da172dc0f
--- /dev/null
+++ b/ReactCommon/fabric/components/root/tests/RootShadowNodeTest.cpp
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+TEST(RootShadowNodeTest, testSomething) {
+  // TODO
+}
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 727fbbd0c060..6776c72b7c79 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -56,11 +56,10 @@ rn_xplat_cxx_library(
         "xplat//folly:memory",
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
-        react_native_xplat_target("fabric/components/scrollview:scrollview"),
-        react_native_xplat_target("fabric/components/text:text"),
+        react_native_xplat_target("fabric/components/root:root"),
+        react_native_xplat_target("fabric/components/view:view"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/debug:debug"),
-        react_native_xplat_target("fabric/components/view:view"),
     ],
 )
 
diff --git a/ReactCommon/fabric/uimanager/Scheduler.cpp b/ReactCommon/fabric/uimanager/Scheduler.cpp
index ad1b42d75881..08b1980bba04 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.cpp
+++ b/ReactCommon/fabric/uimanager/Scheduler.cpp
@@ -5,13 +5,6 @@
 
 #include "Scheduler.h"
 
-#include <fabric/components/scrollview/ScrollViewComponentDescriptor.h>
-#include <fabric/components/text/ParagraphComponentDescriptor.h>
-#include <fabric/components/text/RawTextComponentDescriptor.h>
-#include <fabric/components/text/TextComponentDescriptor.h>
-#include <fabric/components/view/ViewComponentDescriptor.h>
-#include <fabric/components/view/ViewProps.h>
-#include <fabric/components/view/ViewShadowNode.h>
 #include <fabric/core/LayoutContext.h>
 #include <fabric/uimanager/ComponentDescriptorRegistry.h>
 #include <fabric/uimanager/FabricUIManager.h>
diff --git a/ReactCommon/fabric/uimanager/Scheduler.h b/ReactCommon/fabric/uimanager/Scheduler.h
index ed13ba2de301..f603b5778adb 100644
--- a/ReactCommon/fabric/uimanager/Scheduler.h
+++ b/ReactCommon/fabric/uimanager/Scheduler.h
@@ -7,8 +7,6 @@
 
 #include <memory>
 
-#include <fabric/components/view/ViewShadowNode.h>
-#include <fabric/components/view/RootShadowNode.h>
 #include <fabric/core/ComponentDescriptor.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/uimanager/ContextContainer.h>
diff --git a/ReactCommon/fabric/uimanager/ShadowTree.h b/ReactCommon/fabric/uimanager/ShadowTree.h
index f9bb361d6a54..4366fc8d4510 100644
--- a/ReactCommon/fabric/uimanager/ShadowTree.h
+++ b/ReactCommon/fabric/uimanager/ShadowTree.h
@@ -8,7 +8,7 @@
 #include <memory>
 #include <mutex>
 
-#include <fabric/components/view/RootShadowNode.h>
+#include <fabric/components/root/RootShadowNode.h>
 #include <fabric/core/LayoutConstraints.h>
 #include <fabric/core/ReactPrimitives.h>
 #include <fabric/core/ShadowNode.h>

From 9d5bd507372c7b63e59a94383c3e3091d96409de Mon Sep 17 00:00:00 2001
From: Umair Ansari <umair@brivity.com>
Date: Mon, 16 Jul 2018 10:59:58 -0700
Subject: [PATCH 1048/1109] - Invalid use of destructuring

Summary: Pull Request resolved: https://github.com/facebook/react-native/pull/20178

Differential Revision: D8860733

Pulled By: TheSavior

fbshipit-source-id: ec4aa3050755652106dec9ea245394314c862e97
---
 jest/preprocessor.js | 10 ++++++----
 1 file changed, 6 insertions(+), 4 deletions(-)

diff --git a/jest/preprocessor.js b/jest/preprocessor.js
index b9ae6faf22af..6c71b795ed6d 100644
--- a/jest/preprocessor.js
+++ b/jest/preprocessor.js
@@ -41,10 +41,12 @@ module.exports = {
       // node specific transforms only
       return babelTransformSync(
         src,
-        Object.assign(
-          {filename: file},
-          {sourceType: 'script', ...nodeOptions, ast: false},
-        ),
+        {
+          filename: file,
+          sourceType: 'script',
+          ...nodeOptions,
+          ast: false
+        },
       ).code;
     }
 

From 123b3e1a8eac0dcd2efd9083ab69aa4f154bb009 Mon Sep 17 00:00:00 2001
From: "Andrew Chen (Eng)" <ayc@fb.com>
Date: Mon, 16 Jul 2018 11:12:05 -0700
Subject: [PATCH 1049/1109] Fix JSLocaleTest

Summary: becausereasons

Reviewed By: mdvacca

Differential Revision: D8838902

fbshipit-source-id: 0c6ca5ccde0439cacfa02771b2d99f26aa86f573
---
 .../androidTest/java/com/facebook/react/tests/JSLocaleTest.java | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/JSLocaleTest.java b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/JSLocaleTest.java
index 85eeb6c584fb..e78a25522f10 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/tests/JSLocaleTest.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/tests/JSLocaleTest.java
@@ -11,6 +11,7 @@
 import com.facebook.react.bridge.JavaScriptModule;
 import com.facebook.react.bridge.UiThreadUtil;
 import com.facebook.react.modules.appstate.AppStateModule;
+import com.facebook.react.modules.core.ReactChoreographer;
 import com.facebook.react.modules.deviceinfo.DeviceInfoModule;
 import com.facebook.react.testing.FakeWebSocketModule;
 import com.facebook.react.testing.ReactIntegrationTestCase;
@@ -50,6 +51,7 @@ protected void setUp() throws Exception {
         new Runnable() {
           @Override
           public void run() {
+            ReactChoreographer.initialize();
             mUIManager.onHostResume();
           }
         });

From ecd8802c1faef183c8f6dcec4f42ae4e3011bd1d Mon Sep 17 00:00:00 2001
From: Nurzhan Bakibayev <hypuk@fb.com>
Date: Mon, 16 Jul 2018 12:40:12 -0700
Subject: [PATCH 1050/1109] Add @DoNotStrip to RemoteConnection methods

Summary: Add DoNotStrip to RemoteConnection methods

Reviewed By: alexeylang

Differential Revision: D8861729

fbshipit-source-id: d2b339f49dd25379dec6620d367786a9df02d28b
---
 .../src/main/java/com/facebook/react/bridge/Inspector.java      | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/bridge/Inspector.java b/ReactAndroid/src/main/java/com/facebook/react/bridge/Inspector.java
index 8cac13506402..2c37980fff56 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/bridge/Inspector.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/bridge/Inspector.java
@@ -86,7 +86,9 @@ private Page(int id, String title, String vm) {
 
   @DoNotStrip
   public interface RemoteConnection {
+    @DoNotStrip
     void onMessage(String message);
+    @DoNotStrip
     void onDisconnect();
   }
 

From 10ebcbcf450f3fa4457b335d91abba8c8f12237d Mon Sep 17 00:00:00 2001
From: Peter Argany <petetheheat@fb.com>
Date: Mon, 16 Jul 2018 13:13:03 -0700
Subject: [PATCH 1051/1109] Added ImageEditor comment to clarify image access
 policy.

Summary:
ImageEditor.cropImage creates a temporary file when downloading images https://fburl.com/07r68w9s

This temporary file can be stored on external storage on android. External storage is accessible to any other application on the device, which could possibly leak images.

Using external storage may be unavoidable. I've voiced my opinion and solicited others on T31548988. Once a good policy is agreed upon, we can implement it.

For now, I'm adding this comment to make it explicit how images are cached.

Reviewed By: achen1

Differential Revision: D8837808

fbshipit-source-id: 02341bc94a1c95340390a713b76fe85603fd8f1b
---
 Libraries/Image/ImageEditor.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/Libraries/Image/ImageEditor.js b/Libraries/Image/ImageEditor.js
index 66504b501293..65edcccf1220 100644
--- a/Libraries/Image/ImageEditor.js
+++ b/Libraries/Image/ImageEditor.js
@@ -50,7 +50,9 @@ class ImageEditor {
   /**
    * Crop the image specified by the URI param. If URI points to a remote
    * image, it will be downloaded automatically. If the image cannot be
-   * loaded/downloaded, the failure callback will be called.
+   * loaded/downloaded, the failure callback will be called. On Android, a
+   * downloaded image may be cached in external storage, a publicly accessible
+   * location, if it has more available space than internal storage.
    *
    * If the cropping process is successful, the resultant cropped image
    * will be stored in the ImageStore, and the URI returned in the success

From 10b603fdd34919f72304720c25d1420668a6213a Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Mon, 16 Jul 2018 18:38:37 -0700
Subject: [PATCH 1052/1109] added image button as option for accessibility role

Summary:
Because we're now separating accessibilityTraits into accessibilityRole and accessibilityState, we're going to only allow one role to be set, and allow one preset combinations of roles that make sense.

This diff adds image button as a role.

Reviewed By: PeteTheHeat

Differential Revision: D8846958

fbshipit-source-id: dad3783654b20abeb29767cdad7450d1896058c2
---
 Libraries/Components/View/ViewAccessibility.js | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index 410994b2b208..66988382a205 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -47,7 +47,8 @@ export type AccessibilityRole =
   | 'image'
   | 'keyboardkey'
   | 'text'
-  | 'adjustable';
+  | 'adjustable'
+  | 'imagebutton';
 
 module.exports = {
   AccessibilityTraits: [
@@ -84,5 +85,6 @@ module.exports = {
     'keyboardkey',
     'text',
     'adjustable',
+    'imagebutton',
   ],
 };

From d9eeae91a08123c3a458704869acd6f637fc4c53 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Mon, 16 Jul 2018 18:38:39 -0700
Subject: [PATCH 1053/1109] added image button role on iOS

Summary:
Because we're now separating accessibilityTraits into accessibilityRole and accessibilityState, we're going to only allow one role to be set, and allow on preset combinations of roles that make sense.

This change adds iOS functionality to the role image button because a popular accessibilityTrait combination is image and button.

Reviewed By: ikenwoo

Differential Revision: D8847012

fbshipit-source-id: da386dbf82cb3854d14c228a1116da9f4067fe93
---
 React/Views/RCTViewManager.m | 1 +
 1 file changed, 1 insertion(+)

diff --git a/React/Views/RCTViewManager.m b/React/Views/RCTViewManager.m
index 602dd280d512..8e36a7e66cd6 100644
--- a/React/Views/RCTViewManager.m
+++ b/React/Views/RCTViewManager.m
@@ -33,6 +33,7 @@ @implementation RCTConvert(UIAccessibilityTraits)
   @"header": @(UIAccessibilityTraitHeader),
   @"search": @(UIAccessibilityTraitSearchField),
   @"image": @(UIAccessibilityTraitImage),
+  @"imagebutton": @(UIAccessibilityTraitImage | UIAccessibilityTraitButton),
   @"selected": @(UIAccessibilityTraitSelected),
   @"plays": @(UIAccessibilityTraitPlaysSound),
   @"key": @(UIAccessibilityTraitKeyboardKey),

From 3cfa7ae69847cc3b687930346016b248f2427864 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Mon, 16 Jul 2018 19:01:27 -0700
Subject: [PATCH 1054/1109] Added in Prop for CurrentViewState

Summary:
Added in a prop for CurrentViewState that is used to set the state of the current view for both accessibility and regular view settings..

Ex:
AccessibilityRole = "button"
CurrentViewState = ['selected']

This will trigger talk back/voiceover to announce both the role and the state.

Unlike Accessibility Role, Accessibility States can take on more than one form, and are passed in an array.
Ex: AccessibilityState = ['selected', 'disabled']

Currently, two options are available: selected and disabled

Reviewed By: PeteTheHeat

Differential Revision: D8837848

fbshipit-source-id: ca30c950a2aa713813be8577ea4fa9ba9bfc698a
---
 Libraries/Components/View/ViewAccessibility.js | 7 +++++++
 Libraries/Components/View/ViewPropTypes.js     | 8 +++++++-
 2 files changed, 14 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index 66988382a205..420c3c10790d 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -50,6 +50,12 @@ export type AccessibilityRole =
   | 'adjustable'
   | 'imagebutton';
 
+export type CurrentViewState = 'selected' | 'disabled';
+
+export type CurrentViewStates =
+  | CurrentViewState
+  | $ReadOnlyArray<CurrentViewState>;
+
 module.exports = {
   AccessibilityTraits: [
     'none',
@@ -87,4 +93,5 @@ module.exports = {
     'adjustable',
     'imagebutton',
   ],
+  CurrentViewStates: ['selected', 'disabled'],
 };
diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 73a39cf255fc..1e0f328d99ad 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -21,12 +21,14 @@ const {
   AccessibilityComponentTypes,
   AccessibilityTraits,
   AccessibilityRoles,
+  CurrentViewStates,
 } = require('ViewAccessibility');
 
 import type {
   AccessibilityComponentType,
   AccessibilityTrait,
   AccessibilityRole,
+  CurrentViewState,
 } from 'ViewAccessibility';
 import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
 import type {TVViewProps} from 'TVViewPropTypes';
@@ -92,6 +94,7 @@ export type ViewProps = $ReadOnly<{|
   accessibilityIgnoresInvertColors?: boolean,
   accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
   accessibilityRole?: AccessibilityRole,
+  currentViewStates?: Array<CurrentViewState>,
   accessibilityViewIsModal?: boolean,
   accessibilityElementsHidden?: boolean,
   children?: ?React.Node,
@@ -144,10 +147,13 @@ module.exports = {
 
   /**
    * Indicates to accessibility services to treat UI component like a
-   * native one. Merging accessibilityComponentType and accessibilityTraits.
    */
   accessibilityRole: PropTypes.oneOf(AccessibilityRoles),
 
+  /**
+   * Indicates to accessibility services that UI Component is in a specific State.
+   */
+  currentViewStates: PropTypes.arrayOf(PropTypes.oneOf(CurrentViewStates)),
   /**
    * Indicates to accessibility services whether the user should be notified
    * when this view changes. Works for Android API >= 19 only.

From 5acb7211bb211e0ef48334630ddccbb3f0ffa2da Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Mon, 16 Jul 2018 19:11:49 -0700
Subject: [PATCH 1055/1109] added header and summary options for roles

Summary: Added options for summary and header on accessibilityRoles

Reviewed By: PeteTheHeat

Differential Revision: D8866086

fbshipit-source-id: 83bfca678d2308f809e8630b7158a2b4a740c13d
---
 Libraries/Components/View/ViewAccessibility.js | 6 +++++-
 1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index 420c3c10790d..0deca1586012 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -48,7 +48,9 @@ export type AccessibilityRole =
   | 'keyboardkey'
   | 'text'
   | 'adjustable'
-  | 'imagebutton';
+  | 'imagebutton'
+  | 'header'
+  | 'summary';
 
 export type CurrentViewState = 'selected' | 'disabled';
 
@@ -92,6 +94,8 @@ module.exports = {
     'text',
     'adjustable',
     'imagebutton',
+    'header',
+    'summary',
   ],
   CurrentViewStates: ['selected', 'disabled'],
 };

From 5741f771562962110e105114a2c65def4baa805b Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Mon, 16 Jul 2018 19:14:06 -0700
Subject: [PATCH 1056/1109] added image button role on android

Summary:
Because we're now separating accessibilityTraits into accessibilityRole and accessibilityState, we're going to only allow one role to be set, and allow on preset combinations of roles that make sense.

This adds android functionality for an added role that is image button.

Reviewed By: blavalla

Differential Revision: D8846987

fbshipit-source-id: 9fe36828f63b05bd2c9cf9680204b1995d678342
---
 .../com/facebook/react/uimanager/AccessibilityRoleUtil.java  | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
index 86095befc24f..949e009d86fe 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
@@ -34,6 +34,7 @@ public enum AccessibilityRole {
     LINK("android.widget.Button"),
     SEARCH("android.widget.EditText"),
     IMAGE("android.widget.ImageView"),
+    IMAGEBUTTON("android.widget.ImageView"),
     KEYBOARDKEY("android.inputmethodservice.Keyboard$Key"),
     TEXT("android.widget.ViewGroup"),
     ADJUSTABLE("android.widget.SeekBar");
@@ -91,6 +92,10 @@ public static void setRole(AccessibilityNodeInfoCompat nodeInfo, final Accessibi
     if (role.equals(AccessibilityRole.IMAGE)) {
       nodeInfo.setRoleDescription("Image");
     }
+    if (role.equals(AccessibilityRole.IMAGEBUTTON)) {
+      nodeInfo.setRoleDescription("Button Image");
+      nodeInfo.setClickable(true);
+    }
     if (role.equals(AccessibilityRole.ADJUSTABLE)) {
       nodeInfo.setRoleDescription("Adjustable");
     }

From a87b9db3dc3942ecb6e41f374368a74e9729ea6a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Robert=20H=C3=B6nig?= <robhoenig@gmail.com>
Date: Mon, 16 Jul 2018 22:19:09 -0700
Subject: [PATCH 1057/1109] Fix wrong time unit in dev server OKHttp client.
 (#19817)

Summary:
The keep-alive-duration for the connection pool for mOnChangePollingClient
is a number in milliseconds, but was mistakenly given in minutes. This mistake
was introduced in 6bbaff2944d.

I discovered this by chance while lurking around in the codebase.
Pull Request resolved: https://github.com/facebook/react-native/pull/19817

Differential Revision: D8873138

Pulled By: hramos

fbshipit-source-id: c81c1952721449442f18a0c2373f8b2780403749
---
 .../java/com/facebook/react/devsupport/DevServerHelper.java     | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
index b1342c0555e7..255a895fcb1a 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/devsupport/DevServerHelper.java
@@ -539,7 +539,7 @@ public void startPollingOnChangeEndpoint(
     mOnChangePollingEnabled = true;
     mOnServerContentChangeListener = onServerContentChangeListener;
     mOnChangePollingClient = new OkHttpClient.Builder()
-        .connectionPool(new ConnectionPool(1, LONG_POLL_KEEP_ALIVE_DURATION_MS, TimeUnit.MINUTES))
+        .connectionPool(new ConnectionPool(1, LONG_POLL_KEEP_ALIVE_DURATION_MS, TimeUnit.MILLISECONDS))
         .connectTimeout(HTTP_CONNECT_TIMEOUT_MS, TimeUnit.MILLISECONDS)
         .build();
     enqueueOnChangeEndpointLongPolling();

From 46164324cd39711dc78a46246f194a12b4e56a0b Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 17 Jul 2018 01:35:01 -0700
Subject: [PATCH 1058/1109] Exclude ios dependencies from Android build in
 fabric C++

Summary: This diff updates the buck dependencies from fabric to allow cross platform usage

Reviewed By: shergin

Differential Revision: D8755155

fbshipit-source-id: 8501463bb22e5b86e6ad8b6c9f621251c6b6d55a
---
 ReactCommon/fabric/graphics/BUCK          | 10 +++++-----
 ReactCommon/fabric/imagemanager/BUCK      | 10 +++++-----
 ReactCommon/fabric/textlayoutmanager/BUCK | 10 +++++-----
 3 files changed, 15 insertions(+), 15 deletions(-)

diff --git a/ReactCommon/fabric/graphics/BUCK b/ReactCommon/fabric/graphics/BUCK
index 0f8a26ff31df..12ff295f636d 100644
--- a/ReactCommon/fabric/graphics/BUCK
+++ b/ReactCommon/fabric/graphics/BUCK
@@ -56,11 +56,6 @@ rn_xplat_cxx_library(
         ":tests",
     ],
     force_static = True,
-    frameworks = [
-        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
-        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
-        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
-    ],
     ios_deps = [
         "xplat//js:RCTImage",
         "xplat//js/react-native-github:RCTCxxBridge",
@@ -71,6 +66,11 @@ rn_xplat_cxx_library(
         ],
         prefix = "fabric/graphics",
     ),
+    ios_frameworks = [
+        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
+        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
+        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
+    ],
     ios_srcs = glob(
         [
             "platform/ios/**/*.cpp",
diff --git a/ReactCommon/fabric/imagemanager/BUCK b/ReactCommon/fabric/imagemanager/BUCK
index a1f7b3059351..af83b9579c35 100644
--- a/ReactCommon/fabric/imagemanager/BUCK
+++ b/ReactCommon/fabric/imagemanager/BUCK
@@ -52,11 +52,6 @@ rn_xplat_cxx_library(
         ":tests",
     ],
     force_static = True,
-    frameworks = [
-        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
-        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
-        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
-    ],
     ios_deps = [
         "xplat//js:RCTImage",
         "xplat//js/react-native-github:RCTCxxBridge",
@@ -68,6 +63,11 @@ rn_xplat_cxx_library(
         ],
         prefix = "fabric/imagemanager",
     ),
+    ios_frameworks = [
+        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
+        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
+        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
+    ],
     ios_headers = subdir_glob(
         [
             ("", "*.h"),
diff --git a/ReactCommon/fabric/textlayoutmanager/BUCK b/ReactCommon/fabric/textlayoutmanager/BUCK
index 9fb4a464f827..46dd3eb0885b 100644
--- a/ReactCommon/fabric/textlayoutmanager/BUCK
+++ b/ReactCommon/fabric/textlayoutmanager/BUCK
@@ -63,11 +63,6 @@ rn_xplat_cxx_library(
         ":tests",
     ],
     force_static = True,
-    frameworks = [
-        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
-        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
-        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
-    ],
     ios_deps = [
     ],
     ios_exported_headers = subdir_glob(
@@ -76,6 +71,11 @@ rn_xplat_cxx_library(
         ],
         prefix = "fabric/textlayoutmanager",
     ),
+    ios_frameworks = [
+        "$SDKROOT/System/Library/Frameworks/CoreGraphics.framework",
+        "$SDKROOT/System/Library/Frameworks/Foundation.framework",
+        "$SDKROOT/System/Library/Frameworks/UIKit.framework",
+    ],
     ios_headers = subdir_glob(
         [
             ("platform/ios", "**/*.h"),

From e155e78451ec4e736169dbd6889919d9283d3806 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 17 Jul 2018 01:35:10 -0700
Subject: [PATCH 1059/1109] Create CXX Binding

Summary: This diff creates the C++ base classes for Fabric and it integrates them into the starting process of Fabric inside Catalyst App

Reviewed By: shergin

Differential Revision: D8786185

fbshipit-source-id: d04208f0781387424fc0ddf7a6e5d46a6bd61f66
---
 .../com/facebook/react/fabric/FabricBinder.java    | 14 ++++++++++++++
 .../com/facebook/react/fabric/FabricBinding.java   |  3 ++-
 .../com/facebook/react/fabric/FabricUIManager.java |  3 ++-
 .../react/fabric/jsc/FabricJSCBinding.java         |  4 +++-
 4 files changed, 21 insertions(+), 3 deletions(-)
 create mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
new file mode 100644
index 000000000000..e72eceb2b8f7
--- /dev/null
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+package com.facebook.react.fabric;
+
+public interface FabricBinder {
+
+  void setBinding(FabricBinding binding);
+
+}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
index 4db39a42522f..f5e251532661 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
@@ -9,10 +9,11 @@
 
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.NativeMap;
+import com.facebook.react.bridge.UIManager;
 
 public interface FabricBinding {
 
-  void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule);
+  void installFabric(JavaScriptContextHolder jsContext, FabricBinder fabricBinder);
 
   void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 87d1850e6742..345e214c091e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -60,7 +60,7 @@
  */
 @SuppressWarnings("unused") // used from JNI
 @DoNotStrip
-public class FabricUIManager implements UIManager, JSHandler {
+public class FabricUIManager implements UIManager, JSHandler, FabricBinder {
 
   private static final String TAG = FabricUIManager.class.getSimpleName();
   private static final boolean DEBUG = ReactBuildConfig.DEBUG || PrinterHolder.getPrinter().shouldDisplayLogMessage(ReactDebugOverlayTags.FABRIC_UI_MANAGER);
@@ -98,6 +98,7 @@ public FabricUIManager(
     mJSContext = jsContext;
   }
 
+  @Override
   public void setBinding(FabricBinding binding) {
     mBinding = binding;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
index 92e82d41e51e..fb1748204c27 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
@@ -10,6 +10,8 @@
 import com.facebook.jni.HybridData;
 import com.facebook.proguard.annotations.DoNotStrip;
 import com.facebook.react.bridge.JavaScriptContextHolder;
+import com.facebook.react.bridge.UIManager;
+import com.facebook.react.fabric.FabricBinder;
 import com.facebook.react.fabric.FabricBinding;
 import com.facebook.react.fabric.FabricUIManager;
 import com.facebook.react.bridge.NativeMap;
@@ -58,7 +60,7 @@ public FabricJSCBinding() {
   }
 
   @Override
-  public void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule) {
+  public void installFabric(JavaScriptContextHolder jsContext, FabricBinder fabricModule) {
     fabricModule.setBinding(this);
     installFabric(jsContext.get(), fabricModule);
   }

From 6c8b68183d1c2bfca0340e312575717d362d3b28 Mon Sep 17 00:00:00 2001
From: David Vacca <dvacca@fb.com>
Date: Tue, 17 Jul 2018 01:35:12 -0700
Subject: [PATCH 1060/1109] Initialize FabricXX C++ code and register rootview

Summary: This diff initializes Fabric C++ UIManager code from java, it also registers android RootViews inside C++.

Reviewed By: shergin

Differential Revision: D8794819

fbshipit-source-id: b4d1d0958a3f8e01d4a51be957d9a2e2f442489e
---
 .../src/main/java/com/facebook/react/fabric/FabricBinder.java | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
index e72eceb2b8f7..9b6163d7eeed 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
@@ -7,8 +7,8 @@
 
 package com.facebook.react.fabric;
 
-public interface FabricBinder {
+public interface FabricBinder<T extends FabricBinding> {
 
-  void setBinding(FabricBinding binding);
+  void setBinding(T binding);
 
 }

From 51cf9eb3e823a13304570b352b81734f069c18c3 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 17 Jul 2018 03:14:47 -0700
Subject: [PATCH 1061/1109] Upgrade jest to 23.4.1

Summary:
This includes https://github.com/facebook/jest/commit/8b8f5bc40efc658c3dc8bc83de592293e245f37c, which improves the watchman query to calculate the initial haste map to be much faster under Eden.

**Time to initialize Metro after resetting jest-haste-map cache (Eden checkout)**

* Before this diff: 3m14 (sometimes taking up to 15min!! after rebasing)
* With this diff: 12s (quite constant after rebasing)

(16X improvement)

**Time to initialize Metro with a warm jest-haste-map cache (Eden checkout)**

* Before this diff: 1.1s
* With this diff: 1.1s

(I haven't seen meaningful perf changes in non-eden checkouts)

Reviewed By: mjesun

Differential Revision: D8857820

fbshipit-source-id: 5ce9da04a69bd02d121a8efe65bf369c7fa1e834
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index 61fcd31221a3..2ae553d549f3 100644
--- a/package.json
+++ b/package.json
@@ -213,7 +213,7 @@
     "eslint-plugin-react": "7.8.2",
     "eslint-plugin-react-native": "^3.2.1",
     "flow-bin": "^0.76.0",
-    "jest": "23.4.0",
+    "jest": "23.4.1",
     "jest-junit": "5.1.0",
     "prettier": "1.13.6",
     "react": "16.4.1",

From 8ef90df28c038651bc1bc33efaa8e1be9c2e45f5 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 17 Jul 2018 03:14:57 -0700
Subject: [PATCH 1062/1109] Clean metro server correctly after bundle errors

Summary:
This is a very similar fix than D8858846, but done in the RN CLI (soon we'll be able to just call `Metro.runBuild()` from RN which will remove this duplication).

This actually fixes the issues in the integtration tests (t31612131). It's just funny that two unrelated problems that are caused by the same issue located in two different places have been reported at the same time.

Differential Revision: D8859276

fbshipit-source-id: 805e111a406f2a7c1b3df3ab02accf4c4041a464
---
 local-cli/bundle/buildBundle.js | 34 ++++++++++++++++-----------------
 1 file changed, 17 insertions(+), 17 deletions(-)

diff --git a/local-cli/bundle/buildBundle.js b/local-cli/bundle/buildBundle.js
index d1e422d4d0b3..66d86462171d 100644
--- a/local-cli/bundle/buildBundle.js
+++ b/local-cli/bundle/buildBundle.js
@@ -107,23 +107,23 @@ async function buildBundle(
     workerPath: config.getWorkerPath && config.getWorkerPath(),
   });
 
-  const bundle = await output.build(server, requestOpts);
-
-  await output.save(bundle, args, log);
-
-  // Save the assets of the bundle
-  const outputAssets = await server.getAssets({
-    ...Server.DEFAULT_BUNDLE_OPTIONS,
-    ...requestOpts,
-    bundleType: 'todo',
-  });
-
-  // When we're done saving bundle output and the assets, we're done.
-  const assets = await saveAssets(outputAssets, args.platform, args.assetsDest);
-
-  server.end();
-
-  return assets;
+  try {
+    const bundle = await output.build(server, requestOpts);
+
+    await output.save(bundle, args, log);
+
+    // Save the assets of the bundle
+    const outputAssets = await server.getAssets({
+      ...Server.DEFAULT_BUNDLE_OPTIONS,
+      ...requestOpts,
+      bundleType: 'todo',
+    });
+
+    // When we're done saving bundle output and the assets, we're done.
+    return await saveAssets(outputAssets, args.platform, args.assetsDest);
+  } finally {
+    server.end();
+  }
 }
 
 module.exports = buildBundle;

From bf22d904fe0fa84b9e1ec91e9d4dede7c3dfc37c Mon Sep 17 00:00:00 2001
From: Ben Blackburne <bpb@fb.com>
Date: Tue, 17 Jul 2018 03:25:16 -0700
Subject: [PATCH 1063/1109] Revert D8794819: [fabric][android] Initialize
 FabricXX C++ code and register rootview

Differential Revision:
D8794819

Original commit changeset: b4d1d0958a3f

fbshipit-source-id: a984be9a31601644fb2d20a831f4e27075f24f7f
---
 .../src/main/java/com/facebook/react/fabric/FabricBinder.java | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
index 9b6163d7eeed..e72eceb2b8f7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
@@ -7,8 +7,8 @@
 
 package com.facebook.react.fabric;
 
-public interface FabricBinder<T extends FabricBinding> {
+public interface FabricBinder {
 
-  void setBinding(T binding);
+  void setBinding(FabricBinding binding);
 
 }

From f5f27b368785ac61e563d758e05bd8f0d8ff2eb8 Mon Sep 17 00:00:00 2001
From: Ben Blackburne <bpb@fb.com>
Date: Tue, 17 Jul 2018 03:25:18 -0700
Subject: [PATCH 1064/1109] Revert D8786185: [fabric][android] Create CXX
 Binding

Differential Revision:
D8786185

Original commit changeset: d04208f07813

fbshipit-source-id: 1fc1648146ea9784bb364c4e56e8664bb8bb655f
---
 .../com/facebook/react/fabric/FabricBinder.java    | 14 --------------
 .../com/facebook/react/fabric/FabricBinding.java   |  3 +--
 .../com/facebook/react/fabric/FabricUIManager.java |  3 +--
 .../react/fabric/jsc/FabricJSCBinding.java         |  4 +---
 4 files changed, 3 insertions(+), 21 deletions(-)
 delete mode 100644 ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java

diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
deleted file mode 100644
index e72eceb2b8f7..000000000000
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinder.java
+++ /dev/null
@@ -1,14 +0,0 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
- *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
- */
-
-package com.facebook.react.fabric;
-
-public interface FabricBinder {
-
-  void setBinding(FabricBinding binding);
-
-}
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
index f5e251532661..4db39a42522f 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricBinding.java
@@ -9,11 +9,10 @@
 
 import com.facebook.react.bridge.JavaScriptContextHolder;
 import com.facebook.react.bridge.NativeMap;
-import com.facebook.react.bridge.UIManager;
 
 public interface FabricBinding {
 
-  void installFabric(JavaScriptContextHolder jsContext, FabricBinder fabricBinder);
+  void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule);
 
   void releaseEventTarget(long jsContextNativePointer, long eventTargetPointer);
 
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
index 345e214c091e..87d1850e6742 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/FabricUIManager.java
@@ -60,7 +60,7 @@
  */
 @SuppressWarnings("unused") // used from JNI
 @DoNotStrip
-public class FabricUIManager implements UIManager, JSHandler, FabricBinder {
+public class FabricUIManager implements UIManager, JSHandler {
 
   private static final String TAG = FabricUIManager.class.getSimpleName();
   private static final boolean DEBUG = ReactBuildConfig.DEBUG || PrinterHolder.getPrinter().shouldDisplayLogMessage(ReactDebugOverlayTags.FABRIC_UI_MANAGER);
@@ -98,7 +98,6 @@ public FabricUIManager(
     mJSContext = jsContext;
   }
 
-  @Override
   public void setBinding(FabricBinding binding) {
     mBinding = binding;
   }
diff --git a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
index fb1748204c27..92e82d41e51e 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/fabric/jsc/FabricJSCBinding.java
@@ -10,8 +10,6 @@
 import com.facebook.jni.HybridData;
 import com.facebook.proguard.annotations.DoNotStrip;
 import com.facebook.react.bridge.JavaScriptContextHolder;
-import com.facebook.react.bridge.UIManager;
-import com.facebook.react.fabric.FabricBinder;
 import com.facebook.react.fabric.FabricBinding;
 import com.facebook.react.fabric.FabricUIManager;
 import com.facebook.react.bridge.NativeMap;
@@ -60,7 +58,7 @@ public FabricJSCBinding() {
   }
 
   @Override
-  public void installFabric(JavaScriptContextHolder jsContext, FabricBinder fabricModule) {
+  public void installFabric(JavaScriptContextHolder jsContext, FabricUIManager fabricModule) {
     fabricModule.setBinding(this);
     installFabric(jsContext.get(), fabricModule);
   }

From edf71005b5a4d7cfb09eae14f5765d30b9c5704e Mon Sep 17 00:00:00 2001
From: Yan Soares Couto <yancouto@fb.com>
Date: Tue, 17 Jul 2018 07:03:21 -0700
Subject: [PATCH 1065/1109] Hiding pre-bundled notification when not on dev
 mode

Summary: Notification "loading from pre-bundled file" won't show up anymore on non-dev mode.

Reviewed By: adamjernst

Differential Revision: D8874556

fbshipit-source-id: 8bfa63691beb65d16617409533f7a38dc00dc310
---
 React/DevSupport/RCTDevLoadingView.m | 6 +++++-
 1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/React/DevSupport/RCTDevLoadingView.m b/React/DevSupport/RCTDevLoadingView.m
index 15480ad6a693..d0e1bb074ebc 100644
--- a/React/DevSupport/RCTDevLoadingView.m
+++ b/React/DevSupport/RCTDevLoadingView.m
@@ -72,7 +72,7 @@ - (void)setBridge:(RCTBridge *)bridge
     self->_showDate = [NSDate date];
     if (!self->_window && !RCTRunningInTestEnvironment()) {
       CGSize screenSize = [UIScreen mainScreen].bounds.size;
-      
+
       if (@available(iOS 11.0, *)) {
         UIWindow *window = UIApplication.sharedApplication.keyWindow;
         self->_window = [[UIWindow alloc] initWithFrame:CGRectMake(0, 0, screenSize.width, window.safeAreaInsets.top + 30)];
@@ -131,6 +131,10 @@ - (void)showWithURL:(NSURL *)URL
   UIColor *backgroundColor;
   NSString *source;
   if (URL.fileURL) {
+    // If dev mode is not enabled, we don't want to show this kind of notification
+#if !RCT_DEV
+    return;
+#endif
     color = [UIColor grayColor];
     backgroundColor = [UIColor blackColor];
     source = @"pre-bundled file";

From c1d0ccde0f6f8615fce077ef7ee0867a14ca0fb7 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Tue, 17 Jul 2018 15:58:22 -0700
Subject: [PATCH 1066/1109] added android functionality for currentViewStates

Summary:
Added native android support for the prop accessibilityStates.

If 'selected' is passed in, it calls view.setSelected(true)
If 'disabled' is passed in, it calls view.setEnabled(false)

If both are passed in, both are set on the view.

Reviewed By: blavalla

Differential Revision: D8838407

fbshipit-source-id: a942dabcdc5d9e35f0316465e97317739a8b4b25
---
 .../react/uimanager/AccessibilityRoleUtil.java    |  3 ++-
 .../facebook/react/uimanager/BaseViewManager.java | 15 +++++++++++++++
 2 files changed, 17 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
index 949e009d86fe..b7cbf95bd7f5 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/AccessibilityRoleUtil.java
@@ -12,6 +12,7 @@
 import android.support.v4.view.accessibility.AccessibilityNodeInfoCompat;
 import android.view.View;
 import android.view.accessibility.AccessibilityNodeInfo;
+import com.facebook.react.bridge.ReadableArray;
 import javax.annotation.Nullable;
 
 /**
@@ -102,7 +103,7 @@ public static void setRole(AccessibilityNodeInfoCompat nodeInfo, final Accessibi
   }
   
   /**
-   * Variables and methods for setting accessibilityRole on view properties.
+   * Method for setting accessibilityRole on view properties.
    */
   public static void updateAccessibilityRole(View view, String role) {
     if (role == null) {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
index 5b4c312ea581..1aa6882b3d38 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
@@ -30,6 +30,7 @@ public abstract class BaseViewManager<T extends View, C extends LayoutShadowNode
   private static final String PROP_ACCESSIBILITY_COMPONENT_TYPE = "accessibilityComponentType";
   private static final String PROP_ACCESSIBILITY_LIVE_REGION = "accessibilityLiveRegion";
   private static final String PROP_ACCESSIBILITY_ROLE = "accessibilityRole";
+  private static final String PROP_CURRENT_VIEW_STATES = "currentViewStates";
   private static final String PROP_IMPORTANT_FOR_ACCESSIBILITY = "importantForAccessibility";
 
   // DEPRECATED
@@ -123,6 +124,20 @@ public void setAccessibilityRole(T view, String accessibilityRole) {
     AccessibilityRoleUtil.updateAccessibilityRole(view, accessibilityRole);
   }
 
+  @ReactProp(name = PROP_CURRENT_VIEW_STATES)
+  public void setViewStates(T view, ReadableArray currentViewStates) {
+    view.setSelected(false);
+    view.setEnabled(true);
+    for (int i = 0; i < currentViewStates.size(); i++) {
+      String state = currentViewStates.getString(i);
+      if (state.equals("selected")) {
+        view.setSelected(true);
+      } else if (state.equals("disabled")) {
+        view.setEnabled(false);
+      }
+    }
+  }
+
   @ReactProp(name = PROP_IMPORTANT_FOR_ACCESSIBILITY)
   public void setImportantForAccessibility(T view, String importantForAccessibility) {
     if (importantForAccessibility == null || importantForAccessibility.equals("auto")) {

From 679bff2658071dcc5dd10ee847d711d669f46d82 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Tue, 17 Jul 2018 15:58:24 -0700
Subject: [PATCH 1067/1109] added native iOS functionality for prop
 currentViewStates

Summary:
Added Native iOS functionality for prop currentViewStates.

On iOS, this property modifies both the view property userInteractionEnabled and also adds corresponding UIAccessibilityTraits to the view.

If disabled is passed in, userInteractionEnabled of the view will be set to false.

The value that is passed into currentviewStates is converted to a UIAccessibilityTrait Enum and masked in with existing UIAccessibilityTraits on that native view.

The native implementation for accessibilityRole is also changed to also mask new UIAccessibilityTraits with existing ones.

Reviewed By: PeteTheHeat

Differential Revision: D8842691

fbshipit-source-id: 919267300c70efed93a7a92377a0178bd8885eb5
---
 React/Views/RCTViewManager.m | 16 +++++++++++++++-
 1 file changed, 15 insertions(+), 1 deletion(-)

diff --git a/React/Views/RCTViewManager.m b/React/Views/RCTViewManager.m
index 8e36a7e66cd6..29767a90e312 100644
--- a/React/Views/RCTViewManager.m
+++ b/React/Views/RCTViewManager.m
@@ -112,7 +112,6 @@ - (RCTShadowView *)shadowView
 RCT_REMAP_VIEW_PROPERTY(accessibilityActions, reactAccessibilityElement.accessibilityActions, NSString)
 RCT_REMAP_VIEW_PROPERTY(accessibilityLabel, reactAccessibilityElement.accessibilityLabel, NSString)
 RCT_REMAP_VIEW_PROPERTY(accessibilityTraits, reactAccessibilityElement.accessibilityTraits, UIAccessibilityTraits)
-RCT_REMAP_VIEW_PROPERTY(accessibilityRole, reactAccessibilityElement.accessibilityTraits, UIAccessibilityTraits)
 RCT_REMAP_VIEW_PROPERTY(accessibilityViewIsModal, reactAccessibilityElement.accessibilityViewIsModal, BOOL)
 RCT_REMAP_VIEW_PROPERTY(accessibilityElementsHidden, reactAccessibilityElement.accessibilityElementsHidden, BOOL)
 RCT_REMAP_VIEW_PROPERTY(accessibilityIgnoresInvertColors, reactAccessibilityElement.shouldAccessibilityIgnoresInvertColors, BOOL)
@@ -149,6 +148,21 @@ - (RCTShadowView *)shadowView
   view.layer.allowsEdgeAntialiasing = !CATransform3DIsIdentity(view.layer.transform);
 }
 
+RCT_CUSTOM_VIEW_PROPERTY(accessibilityRole, UIAccessibilityTraits, RCTView)
+{
+    view.reactAccessibilityElement.accessibilityTraits |= json ? [RCTConvert UIAccessibilityTraits:json] : defaultView.accessibilityTraits;
+}
+
+RCT_CUSTOM_VIEW_PROPERTY(currentViewStates, UIAccessibilityTraits, RCTView)
+{
+    UIAccessibilityTraits traits = json ? [RCTConvert UIAccessibilityTraits:json] : defaultView.accessibilityTraits;
+    view.reactAccessibilityElement.accessibilityTraits |= traits;
+    if (traits == UIAccessibilityTraitNotEnabled || traits == (UIAccessibilityTraitNotEnabled | UIAccessibilityTraitSelected))
+    {
+        view.userInteractionEnabled = NO;
+    } 
+}
+
 RCT_CUSTOM_VIEW_PROPERTY(pointerEvents, RCTPointerEvents, RCTView)
 {
   if ([view respondsToSelector:@selector(setPointerEvents:)]) {

From 3ac86c366c91f8d62f0128057019b94a783b4249 Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Tue, 17 Jul 2018 16:26:47 -0700
Subject: [PATCH 1068/1109] Fix hasteImpl path checks on Windows machines

Summary:
@public

This fixes https://github.com/facebook/metro/issues/181

Reviewed By: mjesun

Differential Revision: D8880071

fbshipit-source-id: 27e232baa7f39a938af86de810ff5357f777e858
---
 jest/__tests__/hasteImpl-test.js | 93 ++++++++++++++++++++++++++++++++
 jest/hasteImpl.js                |  8 +--
 2 files changed, 97 insertions(+), 4 deletions(-)
 create mode 100644 jest/__tests__/hasteImpl-test.js

diff --git a/jest/__tests__/hasteImpl-test.js b/jest/__tests__/hasteImpl-test.js
new file mode 100644
index 000000000000..de493aa9a153
--- /dev/null
+++ b/jest/__tests__/hasteImpl-test.js
@@ -0,0 +1,93 @@
+/**
+ * Copyright (c) 2014-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @format
+ * @emails oncall+js_foundation
+ */
+
+'use strict';
+
+const path = require('path');
+
+const {getHasteName} = require('../hasteImpl');
+
+function getPath(...parts) {
+  return path.join(__dirname, '..', '..', ...parts);
+}
+
+it('returns the correct haste name for a RN library file', () => {
+  expect(
+    getHasteName(
+      getPath(
+        'Libraries',
+        'Components',
+        'AccessibilityInfo',
+        'AccessibilityInfo.js',
+      ),
+    ),
+  ).toEqual('AccessibilityInfo');
+});
+
+it('returns the correct haste name for a file with a platform suffix', () => {
+  for (const platform of ['android', 'ios', 'native', 'web', 'windows']) {
+    expect(
+      getHasteName(
+        getPath(
+          'Libraries',
+          'Components',
+          'AccessibilityInfo',
+          `AccessibilityInfo.${platform}.js`,
+        ),
+      ),
+    ).toEqual('AccessibilityInfo');
+  }
+});
+
+it('returns the correct haste name for a file with a flow suffix', () => {
+  expect(
+    getHasteName(
+      getPath(
+        'Libraries',
+        'Components',
+        'AccessibilityInfo',
+        'AccessibilityInfo.ios.js.flow',
+      ),
+    ),
+  ).toEqual('AccessibilityInfo');
+});
+
+it('does not calculate the haste name for a file that is not JS', () => {
+  expect(
+    getHasteName(
+      getPath(
+        'Libraries',
+        'Components',
+        'AccessibilityInfo',
+        'AccessibilityInfo.txt',
+      ),
+    ),
+  ).toBe(undefined);
+});
+
+it('does not calculate the haste name for a file outside of RN', () => {
+  expect(
+    getHasteName(getPath('..', 'Libraries', 'AccessibilityInfo.txt')),
+  ).toBe(undefined);
+});
+
+it('does not calculate the haste name for a blacklisted file', () => {
+  expect(
+    getHasteName(
+      getPath(
+        'Libraries',
+        'Components',
+        '__mocks__',
+        'AccessibilityInfo',
+        'AccessibilityInfo.js',
+      ),
+    ),
+  ).toBe(undefined);
+});
diff --git a/jest/hasteImpl.js b/jest/hasteImpl.js
index e72fa4f37b26..8f02881c51bf 100644
--- a/jest/hasteImpl.js
+++ b/jest/hasteImpl.js
@@ -18,9 +18,9 @@ const ROOTS = [
 ];
 
 const BLACKLISTED_PATTERNS /*: Array<RegExp> */ = [
-  /.*\/__(mocks|tests)__\/.*/,
-  /^Libraries\/Animated\/src\/polyfills\/.*/,
-  /^Libraries\/Renderer\/fb\/.*/,
+  /.*[\\\/]__(mocks|tests)__[\\\/].*/,
+  /^Libraries[\\\/]Animated[\\\/]src[\\\/]polyfills[\\\/].*/,
+  /^Libraries[\\\/]Renderer[\\\/]fb[\\\/].*/,
 ];
 
 const WHITELISTED_PREFIXES /*: Array<string> */ = [
@@ -32,7 +32,7 @@ const WHITELISTED_PREFIXES /*: Array<string> */ = [
 
 const NAME_REDUCERS /*: Array<[RegExp, string]> */ = [
   // extract basename
-  [/^(?:.*\/)?([a-zA-Z0-9$_.-]+)$/, '$1'],
+  [/^(?:.*[\\\/])?([a-zA-Z0-9$_.-]+)$/, '$1'],
   // strip .js/.js.flow suffix
   [/^(.*)\.js(\.flow)?$/, '$1'],
   // strip .android/.ios/.native/.web suffix

From c68c3a53d452850414c0dec0fcb4a361a76b9878 Mon Sep 17 00:00:00 2001
From: Taras Tsugrii <ttsugrii@fb.com>
Date: Tue, 17 Jul 2018 17:18:15 -0700
Subject: [PATCH 1069/1109] Fix invalid build file syntax.

Summary: https://buckbuild.com/concept/skylark.html

Reviewed By: shergin

Differential Revision: D8878696

fbshipit-source-id: 33db539701fa84e7391be643f3eabb7e0224aa0b
---
 ReactCommon/fabric/components/root/BUCK | 59 +++++++++++++------------
 1 file changed, 30 insertions(+), 29 deletions(-)

diff --git a/ReactCommon/fabric/components/root/BUCK b/ReactCommon/fabric/components/root/BUCK
index d25d012e708b..0b022a649151 100644
--- a/ReactCommon/fabric/components/root/BUCK
+++ b/ReactCommon/fabric/components/root/BUCK
@@ -1,13 +1,17 @@
-load("@xplat//tools/build_defs:glob_defs.bzl", "subdir_glob")
 load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
-load("//ReactNative:DEFS.bzl", "ANDROID", "APPLE", "IS_OSS_BUILD", "get_apple_inspector_flags", "react_native_xplat_target", "rn_xplat_cxx_library")
-
-APPLE_COMPILER_FLAGS = []
-
-if not IS_OSS_BUILD:
-    load("@xplat//configurations/buck/apple:flag_defs.bzl", "flags", "get_static_library_ios_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "subdir_glob",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+)
 
-    APPLE_COMPILER_FLAGS = flags.get_flag_value(get_static_library_ios_flags(), "compiler_flags")
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
 
 rn_xplat_cxx_library(
     name = "root",
@@ -56,24 +60,21 @@ rn_xplat_cxx_library(
     ],
 )
 
-if not IS_OSS_BUILD:
-    load("@xplat//build_defs:fb_xplat_cxx_test.bzl", "fb_xplat_cxx_test")
-
-    fb_xplat_cxx_test(
-        name = "tests",
-        srcs = glob(["tests/**/*.cpp"]),
-        headers = glob(["tests/**/*.h"]),
-        contacts = ["oncall+react_native@xmail.facebook.com"],
-        compiler_flags = [
-            "-fexceptions",
-            "-frtti",
-            "-std=c++14",
-            "-Wall",
-        ],
-        platforms = APPLE,
-        deps = [
-            "xplat//folly:molly",
-            "xplat//third-party/gmock:gtest",
-            ":root",
-        ],
-    )
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":root",
+    ],
+)

From 732c3a4f4e2ce5f748969d12e0a7f5803e8260ba Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 17 Jul 2018 17:51:17 -0700
Subject: [PATCH 1070/1109] Fabric: Propper support for `accessibilityLabel` in
 RCTParagraphComponentView

Summary:
@public
This approach is basically copying exising implementation that we have in RCTTextView (D5806097).
Changes in `AttributedString` is quite trivial.

Reviewed By: mdvacca

Differential Revision: D8740000

fbshipit-source-id: 276afdf93d777f7ccb99ca8ee5a18a880de2acbf
---
 .../Text/RCTParagraphComponentView.mm            | 16 ++++++++++++++++
 .../fabric/attributedstring/AttributedString.cpp |  8 ++++++++
 .../fabric/attributedstring/AttributedString.h   |  5 +++++
 3 files changed, 29 insertions(+)

diff --git a/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm b/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm
index ecdc55569cfb..d9e55caf1e7d 100644
--- a/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm
+++ b/React/Fabric/Mounting/ComponentViews/Text/RCTParagraphComponentView.mm
@@ -68,4 +68,20 @@ - (void)drawRect:(CGRect)rect
                                           frame:frame];
 }
 
+#pragma mark - Accessibility
+
+- (NSString *)accessibilityLabel
+{
+  NSString *superAccessibilityLabel = [super accessibilityLabel];
+  if (superAccessibilityLabel) {
+    return superAccessibilityLabel;
+  }
+
+  if (!_paragraphLocalData) {
+    return nil;
+  }
+
+  return RCTNSStringFromString(_paragraphLocalData->getAttributedString().getString());
+}
+
 @end
diff --git a/ReactCommon/fabric/attributedstring/AttributedString.cpp b/ReactCommon/fabric/attributedstring/AttributedString.cpp
index b5eb74af1aa2..094b28ed074f 100644
--- a/ReactCommon/fabric/attributedstring/AttributedString.cpp
+++ b/ReactCommon/fabric/attributedstring/AttributedString.cpp
@@ -39,6 +39,14 @@ const std::vector<Fragment> &AttributedString::getFragments() const {
   return fragments_;
 }
 
+std::string AttributedString::getString() const {
+  std::string string;
+  for (const auto &fragment : fragments_) {
+    string += fragment.string;
+  }
+  return string;
+}
+
 #pragma mark - DebugStringConvertible
 
 SharedDebugStringConvertibleList AttributedString::getDebugChildren() const {
diff --git a/ReactCommon/fabric/attributedstring/AttributedString.h b/ReactCommon/fabric/attributedstring/AttributedString.h
index 4fa5ac9b4666..560560cebbcf 100644
--- a/ReactCommon/fabric/attributedstring/AttributedString.h
+++ b/ReactCommon/fabric/attributedstring/AttributedString.h
@@ -61,6 +61,11 @@ class AttributedString:
    */
   const Fragments &getFragments() const;
 
+  /*
+   * Returns a string constructed from all strings in all fragments.
+   */
+  std::string getString() const;
+
 #pragma mark - DebugStringConvertible
 
   SharedDebugStringConvertibleList getDebugChildren() const override;

From 50a481d23ae72a434849d2c85007e411b0c2bb1f Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Tue, 17 Jul 2018 17:54:27 -0700
Subject: [PATCH 1071/1109] RN: Refine `StyleSheet.compose` Flow Type

Summary:
Refines `StyleSheet.compose` so that subtypes of `DangerouslyImpreciseStyleProp` can flow through the function call without losing their type.

This makes it so that if you supply two `ViewStyleProp` types, you will get a `ViewStyleProp` type out of it.

Reviewed By: TheSavior

Differential Revision: D8851699

fbshipit-source-id: e38e572e363a71fddf63d6b6bf5a96b3cdae5915
---
 Libraries/StyleSheet/StyleSheet.js            | 10 +--
 .../__flowtests__/StyleSheet-flowtest.js      | 82 +++++++++++++++++++
 2 files changed, 87 insertions(+), 5 deletions(-)
 create mode 100644 Libraries/StyleSheet/__flowtests__/StyleSheet-flowtest.js

diff --git a/Libraries/StyleSheet/StyleSheet.js b/Libraries/StyleSheet/StyleSheet.js
index 4384ce9dbfc0..f06337e2867c 100644
--- a/Libraries/StyleSheet/StyleSheet.js
+++ b/Libraries/StyleSheet/StyleSheet.js
@@ -272,12 +272,12 @@ module.exports = {
    * array, saving allocations and maintaining reference equality for
    * PureComponent checks.
    */
-  compose(
-    style1: ?DangerouslyImpreciseStyleProp,
-    style2: ?DangerouslyImpreciseStyleProp,
-  ): ?DangerouslyImpreciseStyleProp {
+  compose<T: DangerouslyImpreciseStyleProp>(
+    style1: ?T,
+    style2: ?T,
+  ): ?T | $ReadOnlyArray<T> {
     if (style1 != null && style2 != null) {
-      return [style1, style2];
+      return ([style1, style2]: $ReadOnlyArray<T>);
     } else {
       return style1 != null ? style1 : style2;
     }
diff --git a/Libraries/StyleSheet/__flowtests__/StyleSheet-flowtest.js b/Libraries/StyleSheet/__flowtests__/StyleSheet-flowtest.js
new file mode 100644
index 000000000000..d4d5e5f3594f
--- /dev/null
+++ b/Libraries/StyleSheet/__flowtests__/StyleSheet-flowtest.js
@@ -0,0 +1,82 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @flow strict-local
+ * @format
+ */
+
+'use strict';
+
+const StyleSheet = require('StyleSheet');
+
+import type {ImageStyleProp, TextStyleProp} from 'StyleSheet';
+
+const imageStyle = {tintColor: 'rgb(0, 0, 0)'};
+const textStyle = {color: 'rgb(0, 0, 0)'};
+
+module.exports = {
+  testGoodCompose() {
+    (StyleSheet.compose(
+      imageStyle,
+      imageStyle,
+    ): ImageStyleProp);
+
+    (StyleSheet.compose(
+      textStyle,
+      textStyle,
+    ): TextStyleProp);
+
+    (StyleSheet.compose(
+      null,
+      null,
+    ): TextStyleProp);
+
+    (StyleSheet.compose(
+      textStyle,
+      null,
+    ): TextStyleProp);
+
+    (StyleSheet.compose(
+      textStyle,
+      Math.random() < 0.5 ? textStyle : null,
+    ): TextStyleProp);
+
+    (StyleSheet.compose(
+      [textStyle],
+      null,
+    ): TextStyleProp);
+
+    (StyleSheet.compose(
+      [textStyle],
+      null,
+    ): TextStyleProp);
+
+    (StyleSheet.compose(
+      [textStyle],
+      [textStyle],
+    ): TextStyleProp);
+  },
+
+  testBadCompose() {
+    // $FlowExpectedError - Incompatible type.
+    (StyleSheet.compose(
+      textStyle,
+      textStyle,
+    ): ImageStyleProp);
+
+    (StyleSheet.compose(
+      // $FlowExpectedError - Incompatible type.
+      [textStyle],
+      null,
+    ): ImageStyleProp);
+
+    // $FlowExpectedError - Incompatible type.
+    (StyleSheet.compose(
+      Math.random() < 0.5 ? textStyle : null,
+      null,
+    ): ImageStyleProp);
+  },
+};

From 2d1fabbab23bb18377b1de9be24ab9a9a68253eb Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 17 Jul 2018 18:05:40 -0700
Subject: [PATCH 1072/1109] Fabric: `SharedColor` for Android

Summary:
@public
On Android, a color can be represented as 32 bits integer, so there is no need to instantiate complex color objects and then pass them as shared pointers.  Hense instead of using shared_ptr, we use a simple wrapper class which provides a pointer-like interface.

Reviewed By: mdvacca

Differential Revision: D8742014

fbshipit-source-id: 14109b61fd84a34989538a15bc6fe4e2a8ce83a6
---
 .../fabric/attributedstring/TextAttributes.h  |  8 ++--
 .../graphics/platform/android/Color.cpp       | 19 ++++++---
 .../fabric/graphics/platform/android/Color.h  | 42 +++++++++++++++++--
 3 files changed, 57 insertions(+), 12 deletions(-)

diff --git a/ReactCommon/fabric/attributedstring/TextAttributes.h b/ReactCommon/fabric/attributedstring/TextAttributes.h
index 584387bf5471..2b8c04982197 100644
--- a/ReactCommon/fabric/attributedstring/TextAttributes.h
+++ b/ReactCommon/fabric/attributedstring/TextAttributes.h
@@ -31,8 +31,8 @@ class TextAttributes:
 #pragma mark - Fields
 
   // Color
-  SharedColor foregroundColor {nullptr};
-  SharedColor backgroundColor {nullptr};
+  SharedColor foregroundColor {};
+  SharedColor backgroundColor {};
   Float opacity {std::numeric_limits<Float>::quiet_NaN()};
 
   // Font
@@ -51,7 +51,7 @@ class TextAttributes:
   folly::Optional<WritingDirection> baseWritingDirection {};
 
   // Decoration
-  SharedColor textDecorationColor {nullptr};
+  SharedColor textDecorationColor {};
   folly::Optional<TextDecorationLineType> textDecorationLineType {};
   folly::Optional<TextDecorationLineStyle> textDecorationLineStyle {};
   folly::Optional<TextDecorationLinePattern> textDecorationLinePattern {};
@@ -60,7 +60,7 @@ class TextAttributes:
   // TODO: Use `Point` type instead of `Size` for `textShadowOffset` attribute.
   folly::Optional<Size> textShadowOffset {};
   Float textShadowRadius {std::numeric_limits<Float>::quiet_NaN()};
-  SharedColor textShadowColor {nullptr};
+  SharedColor textShadowColor {};
 
   // Special
   folly::Optional<bool> isHighlighted {};
diff --git a/ReactCommon/fabric/graphics/platform/android/Color.cpp b/ReactCommon/fabric/graphics/platform/android/Color.cpp
index 3511eeb3be86..9a7e88ac248a 100644
--- a/ReactCommon/fabric/graphics/platform/android/Color.cpp
+++ b/ReactCommon/fabric/graphics/platform/android/Color.cpp
@@ -11,13 +11,22 @@ namespace facebook {
 namespace react {
 
 SharedColor colorFromComponents(ColorComponents components) {
-  // Not implemented.
-  return {};
+  return SharedColor(
+    ((int)components.alpha & 0xff) << 24 |
+    ((int)components.red & 0xff) << 16 |
+    ((int)components.green & 0xff) << 8 |
+    ((int)components.blue & 0xff)
+  );
 }
 
-ColorComponents colorComponentsFromColor(SharedColor color) {
-  // Not implemented.
-  return {};
+ColorComponents colorComponentsFromColor(SharedColor sharedColor) {
+  Color color = *sharedColor;
+  return ColorComponents {
+    (float)((color >> 16) & 0xff),
+    (float)((color >>  8) & 0xff),
+    (float)((color      ) & 0xff),
+    (float)((color >> 24) & 0xff)
+  };
 }
 
 } // namespace react
diff --git a/ReactCommon/fabric/graphics/platform/android/Color.h b/ReactCommon/fabric/graphics/platform/android/Color.h
index 761af1d2de05..ff6ed8ef480e 100644
--- a/ReactCommon/fabric/graphics/platform/android/Color.h
+++ b/ReactCommon/fabric/graphics/platform/android/Color.h
@@ -7,15 +7,51 @@
 
 #pragma once
 
-#include <memory>
+#include <limits>
 
 #include <fabric/graphics/ColorComponents.h>
 
 namespace facebook {
 namespace react {
 
-using Color = float;
-using SharedColor = std::shared_ptr<Color>;
+using Color = int;
+
+/*
+ * On Android, a color can be represented as 32 bits integer, so there is no need
+ * to instantiate complex color objects and then pass them as shared pointers.
+ * Hense instead of using shared_ptr, we use a simple wrapper class
+ * which provides a pointer-like interface.
+ */
+class SharedColor {
+
+public:
+  static const Color UndefinedColor = std::numeric_limits<Color>::max();
+
+  SharedColor():
+    color_(UndefinedColor) {}
+
+  SharedColor(const SharedColor &sharedColor) :
+    color_(sharedColor.color_) {}
+
+  SharedColor(Color color):
+    color_(color) {}
+
+  SharedColor &operator=(const SharedColor &sharedColor) {
+    color_ = sharedColor.color_;
+    return *this;
+  }
+
+  Color operator*() const {
+    return color_;
+  }
+
+  operator bool() const {
+    return color_ != UndefinedColor;
+  }
+
+private:
+  Color color_;
+};
 
 SharedColor colorFromComponents(ColorComponents components);
 ColorComponents colorComponentsFromColor(SharedColor color);

From e64e13fce394332ce609f0def35fa573f30138e9 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?H=C3=A9ctor=20Ramos?= <hramos@fb.com>
Date: Tue, 17 Jul 2018 20:59:53 -0700
Subject: [PATCH 1073/1109] Bump minimum Node version to 8.3 (#20236)

Summary:
Node rest/spread syntax started working without the harmony flag in 8.3 (https://github.com/facebook/react-native/pull/20178#issuecomment-404961149).

Release Notes:
[GENERAL] [BREAKING] [Node] - Bump minimum req. Node version to 8.3
Pull Request resolved: https://github.com/facebook/react-native/pull/20236

Differential Revision: D8876357

Pulled By: hramos

fbshipit-source-id: 1f5f791ef318e70c6be8b23d887a1d650a68e594
---
 local-cli/server/checkNodeVersion.js | 13 +++++--------
 package.json                         |  2 +-
 2 files changed, 6 insertions(+), 9 deletions(-)

diff --git a/local-cli/server/checkNodeVersion.js b/local-cli/server/checkNodeVersion.js
index 7eb55a6d87d7..cfc17dcf2d22 100644
--- a/local-cli/server/checkNodeVersion.js
+++ b/local-cli/server/checkNodeVersion.js
@@ -14,7 +14,7 @@ var formatBanner = require('metro-core/src/formatBanner');
 var semver = require('semver');
 
 module.exports = function() {
-  if (!semver.satisfies(process.version, '>=8')) {
+  if (!semver.satisfies(process.version, '>=8.3')) {
     var engine = semver.satisfies(process.version, '<1') ? 'Node' : 'io.js';
 
     var message =
@@ -24,15 +24,12 @@ module.exports = function() {
       process.version +
       '.\n' +
       '\n' +
-      'React Native runs on Node 8.0 or newer. There are several ways to ' +
+      'React Native runs on Node 8.3 or newer. There are several ways to ' +
       'upgrade Node.js depending on your preference.\n' +
       '\n' +
-      'nvm:       nvm install node && nvm alias default node\n' +
-      'Homebrew:  brew unlink iojs; brew install node\n' +
-      'Installer: download the Mac .pkg from https://nodejs.org/\n' +
-      '\n' +
-      'About Node.js:   https://nodejs.org\n' +
-      'Follow along at: https://github.com/facebook/react-native/issues/19226';
+      'nvm:       nvm install 8.3 --reinstall-packages-from=node\n' +
+      'Homebrew:  brew update && brew upgrade node\n' +
+      'Installer: download from https://nodejs.org/\n';
     console.log(
       formatBanner(message, {
         chalkFunction: chalk.green,
diff --git a/package.json b/package.json
index 2ae553d549f3..eceeafd5139e 100644
--- a/package.json
+++ b/package.json
@@ -8,7 +8,7 @@
     "url": "git@github.com:facebook/react-native.git"
   },
   "engines": {
-    "node": ">=8"
+    "node": ">=8.3"
   },
   "prettier": {
     "requirePragma": true,

From daa7c78055857cd2d9ea650de0c4b0f72d3f2acf Mon Sep 17 00:00:00 2001
From: Yunyu Lin <yyl@fb.com>
Date: Tue, 17 Jul 2018 22:31:07 -0700
Subject: [PATCH 1074/1109] Add FlatList and SectionList to Animated exports

Summary: There are several cases for creating an animated implementation of FlatList or SectionList (e.g. passing Animated.Event for onScroll with useNativeDriver enabled, see FlatListExample or SectionListExample), so we might as well add them to the exports.

Reviewed By: sahrens

Differential Revision: D8886446

fbshipit-source-id: 4b207500ea4d8d10de8c1b2639a5f492bc62e560
---
 Libraries/Animated/src/Animated.js               |  4 ++++
 .../src/__tests__/AnimatedNative-test.js         |  2 ++
 RNTester/js/FlatListExample.js                   |  8 +++-----
 RNTester/js/SectionListExample.js                | 16 +++-------------
 4 files changed, 12 insertions(+), 18 deletions(-)

diff --git a/Libraries/Animated/src/Animated.js b/Libraries/Animated/src/Animated.js
index 8678b21f14b8..5b831396c3fc 100644
--- a/Libraries/Animated/src/Animated.js
+++ b/Libraries/Animated/src/Animated.js
@@ -11,8 +11,10 @@
 'use strict';
 
 const AnimatedImplementation = require('AnimatedImplementation');
+const FlatList = require('FlatList');
 const Image = require('Image');
 const ScrollView = require('ScrollView');
+const SectionList = require('SectionList');
 const Text = require('Text');
 const View = require('View');
 
@@ -22,4 +24,6 @@ module.exports = {
   Text: AnimatedImplementation.createAnimatedComponent(Text),
   Image: AnimatedImplementation.createAnimatedComponent(Image),
   ScrollView: AnimatedImplementation.createAnimatedComponent(ScrollView),
+  FlatList: AnimatedImplementation.createAnimatedComponent(FlatList),
+  SectionList: AnimatedImplementation.createAnimatedComponent(SectionList),
 };
diff --git a/Libraries/Animated/src/__tests__/AnimatedNative-test.js b/Libraries/Animated/src/__tests__/AnimatedNative-test.js
index d3ff6665cbc8..f9f3836835fc 100644
--- a/Libraries/Animated/src/__tests__/AnimatedNative-test.js
+++ b/Libraries/Animated/src/__tests__/AnimatedNative-test.js
@@ -19,6 +19,8 @@ jest
   .setMock('View', ClassComponentMock)
   .setMock('Image', ClassComponentMock)
   .setMock('ScrollView', ClassComponentMock)
+  .setMock('FlatList', ClassComponentMock)
+  .setMock('SectionList', ClassComponentMock)
   .setMock('React', {Component: class {}})
   .setMock('NativeModules', {
     NativeAnimatedModule: {},
diff --git a/RNTester/js/FlatListExample.js b/RNTester/js/FlatListExample.js
index 4098934dc0b6..989b791829cf 100644
--- a/RNTester/js/FlatListExample.js
+++ b/RNTester/js/FlatListExample.js
@@ -13,7 +13,7 @@
 const Alert = require('Alert');
 const React = require('react');
 const ReactNative = require('react-native');
-const {Animated, FlatList, StyleSheet, View} = ReactNative;
+const {Animated, StyleSheet, View} = ReactNative;
 
 const RNTesterPage = require('./RNTesterPage');
 
@@ -34,8 +34,6 @@ const {
   renderSmallSwitchOption,
 } = require('./ListExampleShared');
 
-const AnimatedFlatList = Animated.createAnimatedComponent(FlatList);
-
 const VIEWABILITY_CONFIG = {
   minimumViewTime: 3000,
   viewAreaCoveragePercentThreshold: 100,
@@ -114,7 +112,7 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
             </View>
           </View>
           <SeparatorComponent />
-          <AnimatedFlatList
+          <Animated.FlatList
             ItemSeparatorComponent={ItemSeparatorComponent}
             ListHeaderComponent={<HeaderComponent />}
             ListFooterComponent={FooterComponent}
@@ -201,7 +199,7 @@ class FlatListExample extends React.PureComponent<{}, $FlowFixMeState> {
     this._listRef.getNode().recordInteraction();
     pressItem(this, key);
   };
-  _listRef: AnimatedFlatList;
+  _listRef: Animated.FlatList;
 }
 
 const styles = StyleSheet.create({
diff --git a/RNTester/js/SectionListExample.js b/RNTester/js/SectionListExample.js
index 5d3f73f70c2b..1b0e67f0cdab 100644
--- a/RNTester/js/SectionListExample.js
+++ b/RNTester/js/SectionListExample.js
@@ -12,15 +12,7 @@
 
 const React = require('react');
 const ReactNative = require('react-native');
-const {
-  Alert,
-  Animated,
-  Button,
-  SectionList,
-  StyleSheet,
-  Text,
-  View,
-} = ReactNative;
+const {Alert, Animated, Button, StyleSheet, Text, View} = ReactNative;
 
 const RNTesterPage = require('./RNTesterPage');
 
@@ -39,8 +31,6 @@ const {
   renderStackedItem,
 } = require('./ListExampleShared');
 
-const AnimatedSectionList = Animated.createAnimatedComponent(SectionList);
-
 const VIEWABILITY_CONFIG = {
   minimumViewTime: 3000,
   viewAreaCoveragePercentThreshold: 100,
@@ -90,7 +80,7 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
     {useNativeDriver: true},
   );
 
-  _sectionListRef: any;
+  _sectionListRef: Animated.SectionList;
   _captureRef = ref => {
     this._sectionListRef = ref;
   };
@@ -150,7 +140,7 @@ class SectionListExample extends React.PureComponent<{}, $FlowFixMeState> {
           </View>
         </View>
         <SeparatorComponent />
-        <AnimatedSectionList
+        <Animated.SectionList
           ref={this._captureRef}
           ListHeaderComponent={HeaderComponent}
           ListFooterComponent={FooterComponent}

From e906d4cdc928b35d2648482e7a83122004ac584d Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 17 Jul 2018 22:41:31 -0700
Subject: [PATCH 1075/1109] Simplifying child nodes management in
 YogaLayoutableShadowNode

Summary:
@public

This diff consists of many interdependent changes which support one simple idea: YogaLayoutableShadowNode is now using YGNode children to iterate on them (it previously relied on `ShadowNode::getChildren()`). All other changes are just an unavoidable consequence of that. Hence we don't need to filter child nodes every single time when we do layout anymore! The logic around `clone callback` is also drastically simpler now.
The new approach also implies that `LayoutableShadowNode` and `YogaLayoutableShadowNode` don't use `shared_ptr`s to refer to ShadowNode objects because new relationship does not imply ownership. No more `SharedShadowNode` objects in those two classes.

Reviewed By: mdvacca

Differential Revision: D8796159

fbshipit-source-id: 6f52f92d1826f3eb13b2f8a132c3ea77de155d82
---
 React/Fabric/Mounting/RCTMountingManager.mm   |   6 +-
 .../components/view/ConcreteViewShadowNode.h  |  57 +++----
 .../view/yoga/YogaLayoutableShadowNode.cpp    | 152 ++++++------------
 .../view/yoga/YogaLayoutableShadowNode.h      |  41 +++--
 .../componentdescriptor/ComponentDescriptor.h |   2 +-
 .../ConcreteComponentDescriptor.h             |   2 +-
 .../core/layout/LayoutableShadowNode.cpp      |  12 +-
 .../fabric/core/layout/LayoutableShadowNode.h |   9 +-
 .../core/shadownode/ConcreteShadowNode.h      |  15 ++
 .../fabric/core/shadownode/ShadowNode.cpp     |   2 +-
 .../fabric/core/shadownode/ShadowNode.h       |   4 +-
 .../fabric/core/tests/ShadowNodeTest.cpp      |   2 +-
 .../platform/ios/RCTAttributedTextUtils.mm    |   2 +-
 13 files changed, 119 insertions(+), 187 deletions(-)

diff --git a/React/Fabric/Mounting/RCTMountingManager.mm b/React/Fabric/Mounting/RCTMountingManager.mm
index 90366db34902..49326221f0a6 100644
--- a/React/Fabric/Mounting/RCTMountingManager.mm
+++ b/React/Fabric/Mounting/RCTMountingManager.mm
@@ -82,7 +82,7 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
         }
 
         // Layout
-        SharedLayoutableShadowNode layoutableNewShadowNode =
+        auto layoutableNewShadowNode =
           std::dynamic_pointer_cast<const LayoutableShadowNode>(instruction.getNewChildNode());
 
         if (layoutableNewShadowNode) {
@@ -141,11 +141,11 @@ - (void)mutateComponentViewTreeWithMutationInstructions:(facebook::react::TreeMu
         }
 
         // Layout
-        SharedLayoutableShadowNode layoutableOldShadowNode =
+        auto layoutableOldShadowNode =
           std::dynamic_pointer_cast<const LayoutableShadowNode>(oldShadowNode);
 
         if (layoutableOldShadowNode) {
-          SharedLayoutableShadowNode layoutableNewShadowNode =
+          auto layoutableNewShadowNode =
             std::dynamic_pointer_cast<const LayoutableShadowNode>(newShadowNode);
 
           if (layoutableOldShadowNode->getLayoutMetrics() != layoutableNewShadowNode->getLayoutMetrics()) {
diff --git a/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
index db7b9a660173..eb79d9223142 100644
--- a/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
@@ -61,10 +61,11 @@ class ConcreteViewShadowNode:
     AccessibleShadowNode(
       props
     ),
-    YogaLayoutableShadowNode(
-      props,
-      children
-    ) {};
+    YogaLayoutableShadowNode() {
+
+    YogaLayoutableShadowNode::setProps(*props);
+    YogaLayoutableShadowNode::setChildren(ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>::template getChildrenSlice<YogaLayoutableShadowNode>());
+  };
 
   ConcreteViewShadowNode(
     const SharedConcreteViewShadowNode &shadowNode,
@@ -83,30 +84,36 @@ class ConcreteViewShadowNode:
       props
     ),
     YogaLayoutableShadowNode(
-      shadowNode,
-      props,
-      children
-    ) {};
+      *shadowNode
+    ) {
+
+    if (props) {
+      YogaLayoutableShadowNode::setProps(*props);
+    }
+
+    if (children) {
+      YogaLayoutableShadowNode::setChildren(ConcreteShadowNode<ViewPropsT, ViewEventEmitterT>::template getChildrenSlice<YogaLayoutableShadowNode>());
+    }
+  };
 
   void appendChild(const SharedShadowNode &child) {
     ensureUnsealed();
 
     ShadowNode::appendChild(child);
 
-    auto yogaLayoutableChild = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(child);
+    auto nonConstChild = const_cast<ShadowNode *>(child.get());
+    auto yogaLayoutableChild = dynamic_cast<YogaLayoutableShadowNode *>(nonConstChild);
     if (yogaLayoutableChild) {
       YogaLayoutableShadowNode::appendChild(yogaLayoutableChild);
     }
   }
 
-  SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child) override {
+  LayoutableShadowNode *cloneAndReplaceChild(LayoutableShadowNode *child) override {
     ensureUnsealed();
-
-    auto childShadowNode = std::dynamic_pointer_cast<const ShadowNode>(child);
-    assert(childShadowNode);
-    auto childShadowNodeClone = childShadowNode->clone();
-    ShadowNode::replaceChild(childShadowNode, childShadowNodeClone);
-    return std::dynamic_pointer_cast<const LayoutableShadowNode>(childShadowNodeClone);
+    auto childShadowNode = static_cast<const ConcreteViewShadowNode *>(child);
+    auto clonedChildShadowNode = std::static_pointer_cast<ConcreteViewShadowNode>(childShadowNode->clone());
+    ShadowNode::replaceChild(childShadowNode->shared_from_this(), clonedChildShadowNode);
+    return clonedChildShadowNode.get();
   }
 
 #pragma mark - Equality
@@ -133,24 +140,6 @@ class ConcreteViewShadowNode:
     return list;
   }
 
-protected:
-
-#pragma mark - LayoutableShadowNode
-
-  SharedLayoutableShadowNodeList getLayoutableChildNodes() const override {
-    SharedLayoutableShadowNodeList sharedLayoutableShadowNodeList = {};
-    for (auto child : *ShadowNode::children_) {
-      const SharedLayoutableShadowNode layoutableShadowNode = std::dynamic_pointer_cast<const LayoutableShadowNode>(child);
-      if (!layoutableShadowNode) {
-        continue;
-      }
-
-      sharedLayoutableShadowNodeList.push_back(layoutableShadowNode);
-    }
-
-    return sharedLayoutableShadowNodeList;
-  }
-
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
index 7106ccf65755..df6e9d3530ab 100644
--- a/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
@@ -19,46 +19,29 @@
 namespace facebook {
 namespace react {
 
-YogaLayoutableShadowNode::YogaLayoutableShadowNode(
-  const SharedYogaStylableProps &props,
-  const SharedShadowNodeSharedList &children
-):
+YogaLayoutableShadowNode::YogaLayoutableShadowNode():
   yogaNode_({}),
   yogaConfig_(nullptr) {
 
-  assert(props);
-  assert(children);
-
   initializeYogaConfig(yogaConfig_);
+
   yogaNode_.setConfig(&yogaConfig_);
-  yogaNode_.setStyle(props->yogaStyle);
   yogaNode_.setContext(this);
   yogaNode_.setDirty(true);
-
-  YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(&yogaNode_, children);
 }
 
 YogaLayoutableShadowNode::YogaLayoutableShadowNode(
-  const SharedYogaLayoutableShadowNode &shadowNode,
-  const SharedYogaStylableProps &props,
-  const SharedShadowNodeSharedList &children
+  const YogaLayoutableShadowNode &layoutableShadowNode
 ):
-  yogaNode_(shadowNode->yogaNode_),
+  yogaNode_(layoutableShadowNode.yogaNode_),
   yogaConfig_(nullptr) {
 
   initializeYogaConfig(yogaConfig_);
+
   yogaNode_.setConfig(&yogaConfig_);
   yogaNode_.setContext(this);
   yogaNode_.setOwner(nullptr);
   yogaNode_.setDirty(true);
-
-  if (props) {
-    yogaNode_.setStyle(props->yogaStyle);
-  }
-
-  if (children) {
-    YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(&yogaNode_, children);
-  }
 }
 
 void YogaLayoutableShadowNode::cleanLayout() {
@@ -89,15 +72,16 @@ void YogaLayoutableShadowNode::enableMeasurement() {
   yogaNode_.setMeasureFunc(YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector);
 }
 
-void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child) {
+void YogaLayoutableShadowNode::appendChild(YogaLayoutableShadowNode *child) {
   ensureUnsealed();
 
   auto yogaNodeRawPtr = &yogaNode_;
   auto childYogaNodeRawPtr = &child->yogaNode_;
 
   if (childYogaNodeRawPtr->getOwner() != nullptr) {
-    child = std::static_pointer_cast<const YogaLayoutableShadowNode>(cloneAndReplaceChild(child));
+    child = static_cast<YogaLayoutableShadowNode *>(cloneAndReplaceChild(child));
     childYogaNodeRawPtr = &child->yogaNode_;
+    assert(childYogaNodeRawPtr->getOwner() == nullptr);
   }
 
   child->ensureUnsealed();
@@ -106,6 +90,17 @@ void YogaLayoutableShadowNode::appendChild(SharedYogaLayoutableShadowNode child)
   yogaNodeRawPtr->insertChild(childYogaNodeRawPtr, yogaNodeRawPtr->getChildren().size());
 }
 
+void YogaLayoutableShadowNode::setChildren(std::vector<YogaLayoutableShadowNode *> children) {
+  yogaNode_.setChildren({});
+  for (const auto &child : children) {
+    appendChild(child);
+  }
+}
+
+void YogaLayoutableShadowNode::setProps(const YogaStylableProps &props) {
+  yogaNode_.setStyle(props.yogaStyle);
+}
+
 void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
   if (!getIsLayoutClean()) {
     ensureUnsealed();
@@ -127,77 +122,47 @@ void YogaLayoutableShadowNode::layout(LayoutContext layoutContext) {
 }
 
 void YogaLayoutableShadowNode::layoutChildren(LayoutContext layoutContext) {
-  for (auto child : getLayoutableChildNodes()) {
-    auto yogaLayoutableChild = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(child);
-    if (!yogaLayoutableChild) {
-      continue;
-    }
+  for (const auto &childYogaNode : yogaNode_.getChildren()) {
+    auto childNode =
+      static_cast<YogaLayoutableShadowNode *>(childYogaNode->getContext());
 
-    auto nonConstYogaLayoutableChild = std::const_pointer_cast<YogaLayoutableShadowNode>(yogaLayoutableChild);
-
-    LayoutMetrics childLayoutMetrics = layoutMetricsFromYogaNode(nonConstYogaLayoutableChild->yogaNode_);
+    LayoutMetrics childLayoutMetrics = layoutMetricsFromYogaNode(childNode->yogaNode_);
     childLayoutMetrics.pointScaleFactor = layoutContext.pointScaleFactor;
-    nonConstYogaLayoutableChild->setLayoutMetrics(childLayoutMetrics);
+    childNode->setLayoutMetrics(childLayoutMetrics);
   }
 }
 
-#pragma mark - Yoga Connectors
-
-YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex) {
-  // We have only raw pointer to the parent shadow node, but that's enough for now.
-  YogaLayoutableShadowNode *parentShadowNodeRawPtr = (YogaLayoutableShadowNode *)parentYogaNode->getContext();
-  assert(parentShadowNodeRawPtr);
-
-  // Old child shadow node already exists but we have only raw pointer to it...
-  YogaLayoutableShadowNode *oldShadowNodeRawPtr = (YogaLayoutableShadowNode *)oldYogaNode->getContext();
-  assert(oldShadowNodeRawPtr);
-
-  // ... but we have to address this by `shared_ptr`. We cannot create a new `shared_ptr` for it because we will end up with two shared pointers to
-  // single object which will cause preluminary destroyng the object.
-
-  auto &&layoutableChildNodes = parentShadowNodeRawPtr->getLayoutableChildNodes();
-  SharedLayoutableShadowNode oldShadowNode = nullptr;
-
-  // We cannot rely on `childIndex` all the time because `childNodes` can
-  // contain non-layoutable shadow nodes, however chances are good that
-  // `childIndex` points to the right shadow node.
-
-  // Optimistic attempt (in case if `childIndex` is valid):
-  if (childIndex < layoutableChildNodes.size()) {
-    oldShadowNode = layoutableChildNodes[childIndex];
-    if (oldShadowNode.get() == oldShadowNodeRawPtr) {
-      goto found;
-    } else {
-      oldShadowNode = nullptr;
-    }
-  }
+std::vector<LayoutableShadowNode *> YogaLayoutableShadowNode::getLayoutableChildNodes() const {
+  std::vector<LayoutableShadowNode *> yogaLayoutableChildNodes;
+  yogaLayoutableChildNodes.reserve(yogaNode_.getChildren().size());
 
-  // General solution:
-  for (auto child : layoutableChildNodes) {
-    if (child.get() == oldShadowNodeRawPtr) {
-      oldShadowNode = child;
-      break;
-    }
+  for (const auto &childYogaNode : yogaNode_.getChildren()) {
+    auto childNode =
+      static_cast<YogaLayoutableShadowNode *>(childYogaNode->getContext());
+    yogaLayoutableChildNodes.push_back(childNode);
   }
 
-  assert(oldShadowNode);
-
-found:
+  return yogaLayoutableChildNodes;
+}
 
-  // The new one does not exist yet. So, we have to clone and replace this using `cloneAndReplaceChild`.
-  SharedYogaLayoutableShadowNode newShadowNode =
-    std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(parentShadowNodeRawPtr->cloneAndReplaceChild(oldShadowNode));
-  assert(newShadowNode);
+#pragma mark - Yoga Connectors
 
-  return &newShadowNode->yogaNode_;
+YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex) {
+  // At this point it is garanteed that all shadow nodes associated with yoga nodes are `YogaLayoutableShadowNode` subclasses.
+  auto parentNode =
+    static_cast<YogaLayoutableShadowNode *>(parentYogaNode->getContext());
+  auto oldNode =
+    static_cast<YogaLayoutableShadowNode *>(oldYogaNode->getContext());
+  auto clonedNode =
+    static_cast<YogaLayoutableShadowNode *>(parentNode->cloneAndReplaceChild(oldNode));
+  return &clonedNode->yogaNode_;
 }
 
 YGSize YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector(YGNode *yogaNode, float width, YGMeasureMode widthMode, float height, YGMeasureMode heightMode) {
-  YogaLayoutableShadowNode *shadowNodeRawPtr = (YogaLayoutableShadowNode *)yogaNode->getContext();
-  assert(shadowNodeRawPtr);
+  auto shadowNodeRawPtr = static_cast<YogaLayoutableShadowNode *>(yogaNode->getContext());
 
-  Size minimumSize = Size {0, 0};
-  Size maximumSize = Size {kFloatMax, kFloatMax};
+  auto minimumSize = Size {0, 0};
+  auto maximumSize = Size {kFloatMax, kFloatMax};
 
   switch (widthMode) {
     case YGMeasureModeUndefined:
@@ -223,7 +188,7 @@ YGSize YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector(YGNode *yogaNo
       break;
   }
 
-  Size size = shadowNodeRawPtr->measure(LayoutConstraints {minimumSize, maximumSize});
+  auto size = shadowNodeRawPtr->measure({minimumSize, maximumSize});
 
   return YGSize {
     yogaFloatFromFabricFloat(size.width),
@@ -231,29 +196,6 @@ YGSize YogaLayoutableShadowNode::yogaNodeMeasureCallbackConnector(YGNode *yogaNo
   };
 }
 
-void YogaLayoutableShadowNode::setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode *yogaNodeRawPtr, const SharedShadowNodeSharedList &children) {
-  auto yogaNodeChildren = YGVector();
-
-  for (const SharedShadowNode &shadowNode : *children) {
-    const SharedYogaLayoutableShadowNode yogaLayoutableShadowNode = std::dynamic_pointer_cast<const YogaLayoutableShadowNode>(shadowNode);
-
-    if (!yogaLayoutableShadowNode) {
-      continue;
-    }
-
-    auto &&childYogaNodeRawPtr = &yogaLayoutableShadowNode->yogaNode_;
-
-    yogaNodeChildren.push_back(childYogaNodeRawPtr);
-
-    if (childYogaNodeRawPtr->getOwner() == nullptr) {
-      yogaLayoutableShadowNode->ensureUnsealed();
-      childYogaNodeRawPtr->setOwner(yogaNodeRawPtr);
-    }
-  }
-
-  yogaNodeRawPtr->setChildren(yogaNodeChildren);
-}
-
 void YogaLayoutableShadowNode::initializeYogaConfig(YGConfig &config) {
   config.cloneNodeCallback = YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector;
 }
diff --git a/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.h b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.h
index a61b20c3a7ca..573f3c9640dc 100644
--- a/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.h
+++ b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.h
@@ -15,20 +15,11 @@
 #include <fabric/components/view/YogaStylableProps.h>
 #include <fabric/core/LayoutableShadowNode.h>
 #include <fabric/core/Sealable.h>
-#include <fabric/core/ShadowNode.h>
 #include <fabric/debug/DebugStringConvertible.h>
 
 namespace facebook {
 namespace react {
 
-class YogaLayoutableShadowNode;
-
-using SharedYogaConfig = std::shared_ptr<YGConfig>;
-
-using SharedYogaLayoutableShadowNode = std::shared_ptr<const YogaLayoutableShadowNode>;
-using SharedYogaLayoutableShadowNodeList = std::vector<SharedYogaLayoutableShadowNode>;
-using SharedYogaLayoutableShadowNodeSharedList = std::shared_ptr<const SharedYogaLayoutableShadowNodeList>;
-
 class YogaLayoutableShadowNode:
   public LayoutableShadowNode,
   public virtual DebugStringConvertible,
@@ -38,16 +29,9 @@ class YogaLayoutableShadowNode:
 
 #pragma mark - Constructors
 
-  YogaLayoutableShadowNode(
-    const SharedYogaStylableProps &props,
-    const SharedShadowNodeSharedList &children
-  );
+  YogaLayoutableShadowNode();
 
-  YogaLayoutableShadowNode(
-    const SharedYogaLayoutableShadowNode &shadowNode,
-    const SharedYogaStylableProps &props = nullptr,
-    const SharedShadowNodeSharedList &children = nullptr
-  );
+  YogaLayoutableShadowNode(const YogaLayoutableShadowNode &layoutableShadowNode);
 
 #pragma mark - Mutating Methods
 
@@ -59,10 +43,22 @@ class YogaLayoutableShadowNode:
 
   /*
    * Appends `child`'s Yoga node to the own Yoga node.
-   * So, it complements `ShadowNode::appendChild(...)` functionality from Yoga
-   * perspective.
+   * Complements `ShadowNode::appendChild(...)` functionality from Yoga perspective.
+   */
+  void appendChild(YogaLayoutableShadowNode *child);
+
+  /*
+   * Sets Yoga children based on collection of `YogaLayoutableShadowNode` instances.
+   * Complements `ShadowNode::setChildren(...)` functionality from Yoga perspective.
    */
-  void appendChild(SharedYogaLayoutableShadowNode child);
+  void setChildren(std::vector<YogaLayoutableShadowNode *> children);
+
+  /*
+   * Sets Yoga styles based on given `YogaStylableProps`.
+   */
+  void setProps(const YogaStylableProps &props);
+
+#pragma mark - LayoutableShadowNode
 
   void cleanLayout() override;
   void dirtyLayout() override;
@@ -79,6 +75,8 @@ class YogaLayoutableShadowNode:
   
   void layoutChildren(LayoutContext layoutContext) override;
 
+  std::vector<LayoutableShadowNode *> getLayoutableChildNodes() const override;
+
 protected:
   /*
    * All Yoga functions only accept non-const arguments, so we have to mark
@@ -94,7 +92,6 @@ class YogaLayoutableShadowNode:
 
 private:
   static void initializeYogaConfig(YGConfig &config);
-  static void setYogaNodeChildrenBasedOnShadowNodeChildren(YGNode *yogaNodeRawPtr, const SharedShadowNodeSharedList &children);
   static YGNode *yogaNodeCloneCallbackConnector(YGNode *oldYogaNode, YGNode *parentYogaNode, int childIndex);
   static YGSize yogaNodeMeasureCallbackConnector(YGNode *yogaNode, float width, YGMeasureMode widthMode, float height, YGMeasureMode heightMode);
 };
diff --git a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
index 53312ed2fb95..e550ed0358b9 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ComponentDescriptor.h
@@ -54,7 +54,7 @@ class ComponentDescriptor {
   /*
    * Clones a `ShadowNode` with optionally new `props` and/or `children`.
    */
-  virtual SharedShadowNode cloneShadowNode(
+  virtual UnsharedShadowNode cloneShadowNode(
     const SharedShadowNode &shadowNode,
     const SharedProps &props = nullptr,
     const SharedEventEmitter &eventEmitter = nullptr,
diff --git a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
index 82801a7753f3..09028d3a126c 100644
--- a/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
+++ b/ReactCommon/fabric/core/componentdescriptor/ConcreteComponentDescriptor.h
@@ -77,7 +77,7 @@ class ConcreteComponentDescriptor: public ComponentDescriptor {
     return shadowNode;
   }
 
-  SharedShadowNode cloneShadowNode(
+  UnsharedShadowNode cloneShadowNode(
     const SharedShadowNode &sourceShadowNode,
     const SharedProps &props = nullptr,
     const SharedEventEmitter &eventEmitter = nullptr,
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
index 5db399f373f7..aa296769a691 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.cpp
@@ -72,15 +72,9 @@ void LayoutableShadowNode::layout(LayoutContext layoutContext) {
     }
 
     child->ensureUnsealed();
+    child->setHasNewLayout(false);
 
-    // The assumption:
-    // All `sealed` children were replaced with not-yet-sealed clones
-    // somewhere in `layoutChildren`.
-    auto nonConstChild = std::const_pointer_cast<LayoutableShadowNode>(child);
-
-    nonConstChild->setHasNewLayout(false);
-
-    const LayoutMetrics childLayoutMetrics = nonConstChild->getLayoutMetrics();
+    const LayoutMetrics childLayoutMetrics = child->getLayoutMetrics();
     if (childLayoutMetrics.displayType == DisplayType::None) {
       continue;
     }
@@ -88,7 +82,7 @@ void LayoutableShadowNode::layout(LayoutContext layoutContext) {
     LayoutContext childLayoutContext = LayoutContext(layoutContext);
     childLayoutContext.absolutePosition += childLayoutMetrics.frame.origin;
 
-    nonConstChild->layout(layoutContext);
+    child->layout(layoutContext);
   }
 }
 
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
index 3958f6c5ce52..5eb5e8b8befa 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
@@ -22,11 +22,6 @@ namespace react {
 struct LayoutConstraints;
 struct LayoutContext;
 
-class LayoutableShadowNode;
-using SharedLayoutableShadowNode = std::shared_ptr<const LayoutableShadowNode>;
-using SharedLayoutableShadowNodeList = std::vector<SharedLayoutableShadowNode>;
-using LayoutableShadowNodeIterator = std::iterator<std::input_iterator_tag, const SharedLayoutableShadowNode>;
-
 /*
  * Describes all sufficient layout API (in approach-agnostic way)
  * which makes a concurrent layout possible.
@@ -90,13 +85,13 @@ class LayoutableShadowNode:
   /*
    * Returns layoutable children to interate on.
    */
-  virtual SharedLayoutableShadowNodeList getLayoutableChildNodes() const = 0;
+  virtual std::vector<LayoutableShadowNode *> getLayoutableChildNodes() const = 0;
 
   /*
    * In case layout algorithm needs to mutate this (probably sealed) node,
    * it has to clone and replace it in the hierarchy before to do so.
    */
-  virtual SharedLayoutableShadowNode cloneAndReplaceChild(const SharedLayoutableShadowNode &child) = 0;
+  virtual LayoutableShadowNode *cloneAndReplaceChild(LayoutableShadowNode *child) = 0;
 
   /*
    * Sets layout metrics for the shadow node.
diff --git a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
index c4f08a45a65e..cc6b7ebb022e 100644
--- a/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ConcreteShadowNode.h
@@ -77,6 +77,21 @@ class ConcreteShadowNode: public ShadowNode {
     assert(std::dynamic_pointer_cast<const PropsT>(props_));
     return std::static_pointer_cast<const PropsT>(props_);
   }
+
+  /*
+   * Returns subset of children that are inherited from `SpecificShadowNodeT`.
+   */
+  template<typename SpecificShadowNodeT>
+  std::vector<SpecificShadowNodeT *> getChildrenSlice() const {
+    std::vector<SpecificShadowNodeT *> children;
+    for (const auto &childShadowNode : *getChildren()) {
+      auto specificChildShadowNode = dynamic_cast<const SpecificShadowNodeT *>(childShadowNode.get());
+      if (specificChildShadowNode) {
+        children.push_back(const_cast<SpecificShadowNodeT *>(specificChildShadowNode));
+      }
+    }
+    return children;
+  }
 };
 
 } // namespace react
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index a9dc88ff614e..5013b14262d8 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -53,7 +53,7 @@ ShadowNode::ShadowNode(
   cloneFunction_(shadowNode->cloneFunction_),
   revision_(shadowNode->revision_ + 1) {}
 
-SharedShadowNode ShadowNode::clone(
+UnsharedShadowNode ShadowNode::clone(
   const SharedProps &props,
   const SharedShadowNodeSharedList &children
 ) const {
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 65f0596937f0..1f220f50b650 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -29,7 +29,7 @@ using SharedShadowNodeList = std::vector<std::shared_ptr<const ShadowNode>>;
 using SharedShadowNodeSharedList = std::shared_ptr<const SharedShadowNodeList>;
 using SharedShadowNodeUnsharedList = std::shared_ptr<SharedShadowNodeList>;
 
-using ShadowNodeCloneFunction = std::function<SharedShadowNode(
+using ShadowNodeCloneFunction = std::function<UnsharedShadowNode(
   const SharedShadowNode &shadowNode,
   const SharedProps &props,
   const SharedEventEmitter &eventEmitter,
@@ -64,7 +64,7 @@ class ShadowNode:
   /*
    * Clones the shadow node using stored `cloneFunction`.
    */
-  SharedShadowNode clone(
+  UnsharedShadowNode clone(
     const SharedProps &props = nullptr,
     const SharedShadowNodeSharedList &children = nullptr
   ) const;
diff --git a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
index 2cf1347af893..ddb57c8fc1b9 100644
--- a/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
+++ b/ReactCommon/fabric/core/tests/ShadowNodeTest.cpp
@@ -103,7 +103,7 @@ TEST(ShadowNodeTest, handleCloneFunction) {
     nullptr,
     ShadowNode::emptySharedShadowNodeSharedList(),
     [](const SharedShadowNode &shadowNode, const SharedProps &props, const SharedEventEmitter &eventEmitter, const SharedShadowNodeSharedList &children) {
-      return std::make_shared<const TestShadowNode>(
+      return std::make_shared<TestShadowNode>(
         std::static_pointer_cast<const TestShadowNode>(shadowNode),
         props,
         nullptr,
diff --git a/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTAttributedTextUtils.mm b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTAttributedTextUtils.mm
index c58a644f90e4..f0e112188903 100644
--- a/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTAttributedTextUtils.mm
+++ b/ReactCommon/fabric/textlayoutmanager/platform/ios/RCTAttributedTextUtils.mm
@@ -176,7 +176,7 @@ inline static CGFloat RCTEffectiveFontSizeMultiplierFromTextAttributes(const Tex
   for (auto fragment : attributedString.getFragments()) {
     NSAttributedString *nsAttributedStringFragment;
 
-    SharedLayoutableShadowNode layoutableShadowNode =
+    auto layoutableShadowNode =
       std::dynamic_pointer_cast<const LayoutableShadowNode>(fragment.shadowNode);
 
     if (layoutableShadowNode) {

From ec5b1fd259403b613100286fe73a0592b8d57781 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 17 Jul 2018 22:41:32 -0700
Subject: [PATCH 1076/1109] Fabric: Optimized ShadowNode::replaceChild() with
 `suggestedIndex` argument

Summary:
@public
In most cases callsite knows probable index of replacing child node, hence it makes sense to provide this info to `replaceChild` to illuminate O(n) search in most cases.

Reviewed By: mdvacca

Differential Revision: D8814809

fbshipit-source-id: 0edf82878a72260365e2757beb3886ad07c7464d
---
 .../fabric/components/view/ConcreteViewShadowNode.h    |  4 ++--
 .../components/view/yoga/YogaLayoutableShadowNode.cpp  |  4 ++--
 ReactCommon/fabric/core/layout/LayoutableShadowNode.h  |  2 +-
 ReactCommon/fabric/core/shadownode/ShadowNode.cpp      | 10 +++++++++-
 ReactCommon/fabric/core/shadownode/ShadowNode.h        |  2 +-
 5 files changed, 15 insertions(+), 7 deletions(-)

diff --git a/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h b/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
index eb79d9223142..0bddc1a7e739 100644
--- a/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
+++ b/ReactCommon/fabric/components/view/ConcreteViewShadowNode.h
@@ -108,11 +108,11 @@ class ConcreteViewShadowNode:
     }
   }
 
-  LayoutableShadowNode *cloneAndReplaceChild(LayoutableShadowNode *child) override {
+  LayoutableShadowNode *cloneAndReplaceChild(LayoutableShadowNode *child, int suggestedIndex = -1) override {
     ensureUnsealed();
     auto childShadowNode = static_cast<const ConcreteViewShadowNode *>(child);
     auto clonedChildShadowNode = std::static_pointer_cast<ConcreteViewShadowNode>(childShadowNode->clone());
-    ShadowNode::replaceChild(childShadowNode->shared_from_this(), clonedChildShadowNode);
+    ShadowNode::replaceChild(childShadowNode->shared_from_this(), clonedChildShadowNode, suggestedIndex);
     return clonedChildShadowNode.get();
   }
 
diff --git a/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
index df6e9d3530ab..ddfc55180b6b 100644
--- a/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
+++ b/ReactCommon/fabric/components/view/yoga/YogaLayoutableShadowNode.cpp
@@ -79,7 +79,7 @@ void YogaLayoutableShadowNode::appendChild(YogaLayoutableShadowNode *child) {
   auto childYogaNodeRawPtr = &child->yogaNode_;
 
   if (childYogaNodeRawPtr->getOwner() != nullptr) {
-    child = static_cast<YogaLayoutableShadowNode *>(cloneAndReplaceChild(child));
+    child = static_cast<YogaLayoutableShadowNode *>(cloneAndReplaceChild(child, yogaNode_.getChildren().size()));
     childYogaNodeRawPtr = &child->yogaNode_;
     assert(childYogaNodeRawPtr->getOwner() == nullptr);
   }
@@ -154,7 +154,7 @@ YGNode *YogaLayoutableShadowNode::yogaNodeCloneCallbackConnector(YGNode *oldYoga
   auto oldNode =
     static_cast<YogaLayoutableShadowNode *>(oldYogaNode->getContext());
   auto clonedNode =
-    static_cast<YogaLayoutableShadowNode *>(parentNode->cloneAndReplaceChild(oldNode));
+    static_cast<YogaLayoutableShadowNode *>(parentNode->cloneAndReplaceChild(oldNode, childIndex));
   return &clonedNode->yogaNode_;
 }
 
diff --git a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
index 5eb5e8b8befa..febc222cfeac 100644
--- a/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
+++ b/ReactCommon/fabric/core/layout/LayoutableShadowNode.h
@@ -91,7 +91,7 @@ class LayoutableShadowNode:
    * In case layout algorithm needs to mutate this (probably sealed) node,
    * it has to clone and replace it in the hierarchy before to do so.
    */
-  virtual LayoutableShadowNode *cloneAndReplaceChild(LayoutableShadowNode *child) = 0;
+  virtual LayoutableShadowNode *cloneAndReplaceChild(LayoutableShadowNode *child, int suggestedIndex = -1) = 0;
 
   /*
    * Sets layout metrics for the shadow node.
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
index 5013b14262d8..91adbc16bdac 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.cpp
@@ -110,10 +110,18 @@ void ShadowNode::appendChild(const SharedShadowNode &child) {
   nonConstChildren->push_back(child);
 }
 
-void ShadowNode::replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild) {
+void ShadowNode::replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild, int suggestedIndex) {
   ensureUnsealed();
 
   auto nonConstChildren = std::const_pointer_cast<SharedShadowNodeList>(children_);
+
+  if (suggestedIndex != -1 && suggestedIndex < nonConstChildren->size()) {
+    if (nonConstChildren->at(suggestedIndex) == oldChild) {
+      (*nonConstChildren)[suggestedIndex] = newChild;
+      return;
+    }
+  }
+
   std::replace(nonConstChildren->begin(), nonConstChildren->end(), oldChild, newChild);
 }
 
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index 1f220f50b650..a7bc76d408d2 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -93,7 +93,7 @@ class ShadowNode:
 #pragma mark - Mutating Methods
 
   void appendChild(const SharedShadowNode &child);
-  void replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild);
+  void replaceChild(const SharedShadowNode &oldChild, const SharedShadowNode &newChild, int suggestedIndex = -1);
   void clearSourceNode();
 
   /*

From 58da98149d3de4bea46c9b0c59d04f65ae80e062 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 17 Jul 2018 22:41:34 -0700
Subject: [PATCH 1077/1109] Fabric: Support for optional `key` parameter to
 register/retrieve in ContextContainer

Summary:
@public
We need this in case when we want to store several intances of the same class in the container.

Reviewed By: mdvacca

Differential Revision: D8814808

fbshipit-source-id: 78ab15d78cf3878d03bf0a45bc42b968d87435e7
---
 .../fabric/uimanager/ContextContainer.h       | 27 +++++++++++++++----
 1 file changed, 22 insertions(+), 5 deletions(-)

diff --git a/ReactCommon/fabric/uimanager/ContextContainer.h b/ReactCommon/fabric/uimanager/ContextContainer.h
index 30e055c85206..cb8209bb285b 100644
--- a/ReactCommon/fabric/uimanager/ContextContainer.h
+++ b/ReactCommon/fabric/uimanager/ContextContainer.h
@@ -24,20 +24,37 @@ using SharedContextContainer = std::shared_ptr<ContextContainer>;
 class ContextContainer final {
 
 public:
+  /*
+   * Registers an instance of the particular type `T` in the container.
+   * If `key` parameter is specified, the instance is registered
+   * by `{type, key}` pair.
+   */
   template<typename T>
-  void registerInstance(std::shared_ptr<T> instance) {
+  void registerInstance(std::shared_ptr<T> instance, const std::string &key = "") {
     std::lock_guard<std::mutex> lock(mutex_);
-    instances_.insert({std::type_index(typeid(T)), instance});
+    instances_.insert({
+      {std::type_index(typeid(T)), key},
+      instance
+    });
   }
 
+  /*
+   * Returns a previously registered instance of the particular type `T`.
+   * If `key` parameter is specified, the lookup will be performed
+   * by {type, key} pair.
+   */
   template<typename T>
-  std::shared_ptr<T> getInstance() const {
+  std::shared_ptr<T> getInstance(const std::string &key = "") const {
     std::lock_guard<std::mutex> lock(mutex_);
-    return std::static_pointer_cast<T>(instances_.at(std::type_index(typeid(T))));
+    return std::static_pointer_cast<T>(instances_.at({std::type_index(typeid(T)), key}));
   }
 
 private:
-  std::unordered_map<std::type_index, std::shared_ptr<void>> instances_;
+  std::unordered_map<
+    std::pair<std::type_index, std::string>,
+    std::shared_ptr<void>
+  > instances_;
+
   mutable std::mutex mutex_;
 };
 

From 88b861643794804f8e5b2a1ff6d9ae64a3b38b51 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 17 Jul 2018 22:41:37 -0700
Subject: [PATCH 1078/1109] Fabric: Using `unordered_map` instead of `map` for
 RawProps

Summary:
@public
We don't need to maintain an order of this collection, so using `unordered_map` is more appropriate.

Reviewed By: mdvacca

Differential Revision: D8826946

fbshipit-source-id: f6890097cc5d6a1e06f6b2cfd1b7d68a388da461
---
 ReactCommon/fabric/core/primitives/ReactPrimitives.h | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/ReactCommon/fabric/core/primitives/ReactPrimitives.h b/ReactCommon/fabric/core/primitives/ReactPrimitives.h
index 836fdb741758..065c761c9207 100644
--- a/ReactCommon/fabric/core/primitives/ReactPrimitives.h
+++ b/ReactCommon/fabric/core/primitives/ReactPrimitives.h
@@ -9,6 +9,7 @@
 
 #include <memory>
 #include <string>
+#include <unordered_map>
 
 #include <folly/dynamic.h>
 
@@ -25,7 +26,7 @@ using InstanceHandle = struct InstanceHandleDummyStruct {} *;
  * `RawProps` represents untyped map with props comes from JavaScript side.
  */
 // TODO(T26954420): Use iterator as underlying type for RawProps.
-using RawProps = std::map<std::string, folly::dynamic>;
+using RawProps = std::unordered_map<std::string, folly::dynamic>;
 using SharedRawProps = std::shared_ptr<const RawProps>;
 
 /*

From 07a4a959a7ff60b4c25c4c1057883e77a747a21d Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 17 Jul 2018 22:41:39 -0700
Subject: [PATCH 1079/1109] Fabric: Events related classes were moved to
 separate buck target

Summary:
@public
We need that because gonna add much more event-related stuff, so it deserves separate buck target.

Reviewed By: mdvacca

Differential Revision: D8831547

fbshipit-source-id: 616581b39b425a49302d5f7f86267e62b0d58389
---
 .../View/RCTViewComponentView.h               |  2 +-
 .../RCTUpdateEventEmitterMountItem.h          |  2 +-
 .../Mounting/RCTComponentViewProtocol.h       |  2 +-
 .../scrollview/ScrollViewEventEmitter.h       |  3 +-
 .../fabric/components/view/ViewEventEmitter.h |  2 +-
 ReactCommon/fabric/core/BUCK                  |  1 +
 .../fabric/core/shadownode/ShadowNode.h       |  2 +-
 ReactCommon/fabric/events/BUCK                | 80 +++++++++++++++++++
 .../{core => }/events/EventDispatcher.h       |  3 +-
 .../fabric/{core => }/events/EventEmitter.cpp |  0
 .../fabric/{core => }/events/EventEmitter.h   | 11 ++-
 .../EventPrimitives.h => events/primitives.h} |  0
 .../fabric/events/tests/EventsTest.cpp        | 14 ++++
 ReactCommon/fabric/uimanager/BUCK             |  1 +
 .../uimanager/ComponentDescriptorFactory.h    |  2 +-
 .../uimanager/SchedulerEventDispatcher.h      |  4 +-
 16 files changed, 114 insertions(+), 15 deletions(-)
 create mode 100644 ReactCommon/fabric/events/BUCK
 rename ReactCommon/fabric/{core => }/events/EventDispatcher.h (92%)
 rename ReactCommon/fabric/{core => }/events/EventEmitter.cpp (100%)
 rename ReactCommon/fabric/{core => }/events/EventEmitter.h (84%)
 rename ReactCommon/fabric/{core/events/EventPrimitives.h => events/primitives.h} (100%)
 create mode 100644 ReactCommon/fabric/events/tests/EventsTest.cpp

diff --git a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
index 2fa543e88583..9359240bedb1 100644
--- a/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
+++ b/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.h
@@ -9,10 +9,10 @@
 
 #import <React/RCTComponentViewProtocol.h>
 #import <React/UIView+ComponentViewProtocol.h>
-#import <fabric/core/EventEmitter.h>
 #import <fabric/core/LayoutMetrics.h>
 #import <fabric/core/Props.h>
 #import <fabric/components/view/ViewEventEmitter.h>
+#import <fabric/events/EventEmitter.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
diff --git a/React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.h b/React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.h
index 7db403b1dd33..1d145fe90027 100644
--- a/React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.h
+++ b/React/Fabric/Mounting/MountItems/RCTUpdateEventEmitterMountItem.h
@@ -9,7 +9,7 @@
 
 #import <React/RCTMountItemProtocol.h>
 #import <React/RCTPrimitives.h>
-#import <fabric/core/EventEmitter.h>
+#import <fabric/events/EventEmitter.h>
 
 NS_ASSUME_NONNULL_BEGIN
 
diff --git a/React/Fabric/Mounting/RCTComponentViewProtocol.h b/React/Fabric/Mounting/RCTComponentViewProtocol.h
index a426bfd081fe..2fab1ec56ad5 100644
--- a/React/Fabric/Mounting/RCTComponentViewProtocol.h
+++ b/React/Fabric/Mounting/RCTComponentViewProtocol.h
@@ -7,10 +7,10 @@
 
 #import <UIKit/UIKit.h>
 
-#import <fabric/core/EventEmitter.h>
 #import <fabric/core/LocalData.h>
 #import <fabric/core/Props.h>
 #import <fabric/core/LayoutMetrics.h>
+#import <fabric/events/EventEmitter.h>
 #import <React/RCTPrimitives.h>
 
 NS_ASSUME_NONNULL_BEGIN
diff --git a/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h b/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h
index e72c47b1d335..2c662703a726 100644
--- a/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h
+++ b/ReactCommon/fabric/components/scrollview/ScrollViewEventEmitter.h
@@ -9,9 +9,8 @@
 #include <memory>
 
 #include <fabric/components/view/ViewEventEmitter.h>
+#include <fabric/events/EventEmitter.h>
 #include <fabric/graphics/Geometry.h>
-#include <fabric/core/EventEmitter.h>
-
 #include <folly/dynamic.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/components/view/ViewEventEmitter.h b/ReactCommon/fabric/components/view/ViewEventEmitter.h
index 04af2fee6e10..97704014341e 100644
--- a/ReactCommon/fabric/components/view/ViewEventEmitter.h
+++ b/ReactCommon/fabric/components/view/ViewEventEmitter.h
@@ -8,9 +8,9 @@
 
 #include <memory>
 
-#include <fabric/core/EventEmitter.h>
 #include <fabric/core/LayoutMetrics.h>
 #include <fabric/core/ReactPrimitives.h>
+#include <fabric/events/EventEmitter.h>
 
 namespace facebook {
 namespace react {
diff --git a/ReactCommon/fabric/core/BUCK b/ReactCommon/fabric/core/BUCK
index 112cb850ec82..8aa804678635 100644
--- a/ReactCommon/fabric/core/BUCK
+++ b/ReactCommon/fabric/core/BUCK
@@ -52,6 +52,7 @@ rn_xplat_cxx_library(
         "xplat//folly:molly",
         "xplat//third-party/glog:glog",
         react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/events:events"),
         react_native_xplat_target("fabric/graphics:graphics"),
     ],
 )
diff --git a/ReactCommon/fabric/core/shadownode/ShadowNode.h b/ReactCommon/fabric/core/shadownode/ShadowNode.h
index a7bc76d408d2..173b171f8d89 100644
--- a/ReactCommon/fabric/core/shadownode/ShadowNode.h
+++ b/ReactCommon/fabric/core/shadownode/ShadowNode.h
@@ -11,11 +11,11 @@
 #include <memory>
 #include <vector>
 
-#include <fabric/core/EventEmitter.h>
 #include <fabric/core/LocalData.h>
 #include <fabric/core/Props.h>
 #include <fabric/core/ReactPrimitives.h>
 #include <fabric/core/Sealable.h>
+#include <fabric/events/EventEmitter.h>
 #include <fabric/debug/DebugStringConvertible.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/events/BUCK b/ReactCommon/fabric/events/BUCK
new file mode 100644
index 000000000000..1f1908cc7613
--- /dev/null
+++ b/ReactCommon/fabric/events/BUCK
@@ -0,0 +1,80 @@
+load("//configurations/buck/apple:flag_defs.bzl", "OBJC_ARC_PREPROCESSOR_FLAGS", "get_application_ios_flags", "get_debug_preprocessor_flags")
+load(
+    "//ReactNative:DEFS.bzl",
+    "ANDROID",
+    "APPLE",
+    "fb_xplat_cxx_test",
+    "get_apple_compiler_flags",
+    "get_apple_inspector_flags",
+    "react_native_xplat_target",
+    "rn_xplat_cxx_library",
+    "subdir_glob",
+)
+
+APPLE_COMPILER_FLAGS = get_apple_compiler_flags()
+
+rn_xplat_cxx_library(
+    name = "events",
+    srcs = glob(
+        ["**/*.cpp"],
+        exclude = glob(["tests/**/*.cpp"]),
+    ),
+    headers = glob(
+        ["**/*.h"],
+        exclude = glob(["tests/**/*.h"]),
+    ),
+    header_namespace = "",
+    exported_headers = subdir_glob(
+        [
+            ("", "*.h"),
+        ],
+        prefix = "fabric/events",
+    ),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    fbobjc_compiler_flags = APPLE_COMPILER_FLAGS,
+    fbobjc_preprocessor_flags = get_debug_preprocessor_flags() + get_apple_inspector_flags(),
+    fbobjc_tests = [
+        ":tests",
+    ],
+    force_static = True,
+    macosx_tests_override = [],
+    platforms = (ANDROID, APPLE),
+    preprocessor_flags = [
+        "-DLOG_TAG=\"ReactNative\"",
+        "-DWITH_FBSYSTRACE=1",
+    ],
+    tests = [],
+    visibility = ["PUBLIC"],
+    deps = [
+        "xplat//fbsystrace:fbsystrace",
+        "xplat//folly:headers_only",
+        "xplat//folly:memory",
+        "xplat//folly:molly",
+        "xplat//third-party/glog:glog",
+        react_native_xplat_target("fabric/debug:debug"),
+    ],
+)
+
+fb_xplat_cxx_test(
+    name = "tests",
+    srcs = glob(["tests/**/*.cpp"]),
+    headers = glob(["tests/**/*.h"]),
+    compiler_flags = [
+        "-fexceptions",
+        "-frtti",
+        "-std=c++14",
+        "-Wall",
+    ],
+    contacts = ["oncall+react_native@xmail.facebook.com"],
+    platforms = APPLE,
+    deps = [
+        "xplat//folly:molly",
+        "xplat//third-party/gmock:gtest",
+        ":events",
+    ],
+)
diff --git a/ReactCommon/fabric/core/events/EventDispatcher.h b/ReactCommon/fabric/events/EventDispatcher.h
similarity index 92%
rename from ReactCommon/fabric/core/events/EventDispatcher.h
rename to ReactCommon/fabric/events/EventDispatcher.h
index 11ba3580850e..d317e65a49fc 100644
--- a/ReactCommon/fabric/core/events/EventDispatcher.h
+++ b/ReactCommon/fabric/events/EventDispatcher.h
@@ -8,8 +8,7 @@
 
 #include <memory>
 
-#include <fabric/core/ReactPrimitives.h>
-#include <fabric/core/EventPrimitives.h>
+#include <fabric/events/primitives.h>
 #include <folly/dynamic.h>
 
 namespace facebook {
diff --git a/ReactCommon/fabric/core/events/EventEmitter.cpp b/ReactCommon/fabric/events/EventEmitter.cpp
similarity index 100%
rename from ReactCommon/fabric/core/events/EventEmitter.cpp
rename to ReactCommon/fabric/events/EventEmitter.cpp
diff --git a/ReactCommon/fabric/core/events/EventEmitter.h b/ReactCommon/fabric/events/EventEmitter.h
similarity index 84%
rename from ReactCommon/fabric/core/events/EventEmitter.h
rename to ReactCommon/fabric/events/EventEmitter.h
index 3876be111c09..f2f41732e652 100644
--- a/ReactCommon/fabric/core/events/EventEmitter.h
+++ b/ReactCommon/fabric/events/EventEmitter.h
@@ -10,9 +10,8 @@
 #include <mutex>
 
 #include <folly/dynamic.h>
-#include <fabric/core/EventDispatcher.h>
-#include <fabric/core/EventPrimitives.h>
-#include <fabric/core/ReactPrimitives.h>
+#include <fabric/events/EventDispatcher.h>
+#include <fabric/events/primitives.h>
 
 namespace facebook {
 namespace react {
@@ -30,6 +29,12 @@ using SharedEventEmitter = std::shared_ptr<const EventEmitter>;
  */
 class EventEmitter {
 
+  /*
+   * We have to repeat `Tag` type definition here because `events` module does
+   * not depend on `core` module (and should not).
+   */
+  using Tag = int32_t;
+
 public:
   EventEmitter(const EventTarget &eventTarget, const Tag &tag, const SharedEventDispatcher &eventDispatcher);
   virtual ~EventEmitter();
diff --git a/ReactCommon/fabric/core/events/EventPrimitives.h b/ReactCommon/fabric/events/primitives.h
similarity index 100%
rename from ReactCommon/fabric/core/events/EventPrimitives.h
rename to ReactCommon/fabric/events/primitives.h
diff --git a/ReactCommon/fabric/events/tests/EventsTest.cpp b/ReactCommon/fabric/events/tests/EventsTest.cpp
new file mode 100644
index 000000000000..3e626f96d06a
--- /dev/null
+++ b/ReactCommon/fabric/events/tests/EventsTest.cpp
@@ -0,0 +1,14 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ */
+
+#include <memory>
+
+#include <gtest/gtest.h>
+
+TEST(EventsTest, testSomething) {
+  // TODO
+}
diff --git a/ReactCommon/fabric/uimanager/BUCK b/ReactCommon/fabric/uimanager/BUCK
index 6776c72b7c79..44d2906e76fb 100644
--- a/ReactCommon/fabric/uimanager/BUCK
+++ b/ReactCommon/fabric/uimanager/BUCK
@@ -60,6 +60,7 @@ rn_xplat_cxx_library(
         react_native_xplat_target("fabric/components/view:view"),
         react_native_xplat_target("fabric/core:core"),
         react_native_xplat_target("fabric/debug:debug"),
+        react_native_xplat_target("fabric/events:events"),
     ],
 )
 
diff --git a/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h b/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
index d4c4b965cec0..e349760be309 100644
--- a/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
+++ b/ReactCommon/fabric/uimanager/ComponentDescriptorFactory.h
@@ -10,7 +10,7 @@
 #include <memory>
 
 #include <fabric/core/ComponentDescriptor.h>
-#include <fabric/core/EventDispatcher.h>
+#include <fabric/events/EventDispatcher.h>
 #include <fabric/uimanager/ContextContainer.h>
 
 #include "ComponentDescriptorRegistry.h"
diff --git a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
index e89735ad9981..4ce85faef0f1 100644
--- a/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
+++ b/ReactCommon/fabric/uimanager/SchedulerEventDispatcher.h
@@ -7,8 +7,8 @@
 
 #pragma once
 
-#include <fabric/core/EventDispatcher.h>
-#include <fabric/core/EventPrimitives.h>
+#include <fabric/events/EventDispatcher.h>
+#include <fabric/events/primitives.h>
 #include <fabric/uimanager/FabricUIManager.h>
 #include <folly/dynamic.h>
 

From 93954858227937a34b99f14c26292e04ea450df0 Mon Sep 17 00:00:00 2001
From: Valentin Shergin <shergin@fb.com>
Date: Tue, 17 Jul 2018 22:41:42 -0700
Subject: [PATCH 1080/1109] Fabric: ContextContainer is now able to store any
 copyable values

Summary:
@public
Previously, ContextContainer could store only `shared_ptr`s, but now it wraps all values in own `shared_ptr` container.
I wish we can use `unique_ptr` here, but apparently we cannot because `unique_ptr` does not support type-erasure (`std::unique_ptr<void>` is illigal).
Becasue ContextContainer is not supposed to be used in hot paths, the performance aspect of that does not actually matter.

Reviewed By: mdvacca

Differential Revision: D8853446

fbshipit-source-id: e5d0a5595fe44c59f1395d6ffccf9d3fed923c83
---
 .../components/image/ImageComponentDescriptor.h       |  2 +-
 ReactCommon/fabric/uimanager/ContextContainer.h       | 11 +++++++----
 2 files changed, 8 insertions(+), 5 deletions(-)

diff --git a/ReactCommon/fabric/components/image/ImageComponentDescriptor.h b/ReactCommon/fabric/components/image/ImageComponentDescriptor.h
index 8ce4a15821fb..d62104c8c21c 100644
--- a/ReactCommon/fabric/components/image/ImageComponentDescriptor.h
+++ b/ReactCommon/fabric/components/image/ImageComponentDescriptor.h
@@ -24,7 +24,7 @@ class ImageComponentDescriptor final:
 public:
   ImageComponentDescriptor(SharedEventDispatcher eventDispatcher, const SharedContextContainer &contextContainer):
     ConcreteComponentDescriptor(eventDispatcher),
-    imageManager_(contextContainer->getInstance<ImageManager>()) {}
+    imageManager_(contextContainer->getInstance<SharedImageManager>()) {}
 
   void adopt(UnsharedShadowNode shadowNode) const override {
     ConcreteComponentDescriptor::adopt(shadowNode);
diff --git a/ReactCommon/fabric/uimanager/ContextContainer.h b/ReactCommon/fabric/uimanager/ContextContainer.h
index cb8209bb285b..2dbd0fb30ed1 100644
--- a/ReactCommon/fabric/uimanager/ContextContainer.h
+++ b/ReactCommon/fabric/uimanager/ContextContainer.h
@@ -20,6 +20,7 @@ using SharedContextContainer = std::shared_ptr<ContextContainer>;
 
 /*
  * General purpose dependecy injection container.
+ * Instance types must be copyable.
  */
 class ContextContainer final {
 
@@ -30,11 +31,12 @@ class ContextContainer final {
    * by `{type, key}` pair.
    */
   template<typename T>
-  void registerInstance(std::shared_ptr<T> instance, const std::string &key = "") {
+  void registerInstance(const T &instance, const std::string &key = "") {
     std::lock_guard<std::mutex> lock(mutex_);
+
     instances_.insert({
       {std::type_index(typeid(T)), key},
-      instance
+      std::make_shared<T>(instance)
     });
   }
 
@@ -44,9 +46,10 @@ class ContextContainer final {
    * by {type, key} pair.
    */
   template<typename T>
-  std::shared_ptr<T> getInstance(const std::string &key = "") const {
+  T getInstance(const std::string &key = "") const {
     std::lock_guard<std::mutex> lock(mutex_);
-    return std::static_pointer_cast<T>(instances_.at({std::type_index(typeid(T)), key}));
+
+    return *std::static_pointer_cast<T>(instances_.at({std::type_index(typeid(T)), key}));
   }
 
 private:

From b330579204e6e9ec694db076581341243e11b10d Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Wed, 18 Jul 2018 00:57:52 -0700
Subject: [PATCH 1081/1109] Lint Utils.cpp YGLayout.cpp YGNode.cpp
 Yoga-internal.h

Summary:
@public

Auto-fixes formatting of YGLayout.cpp YGNode.cpp Yoga-internal.h

Reviewed By: astreet

Differential Revision: D8875514

fbshipit-source-id: 38d709831349c4ad015f20451421aea89fc6f007
---
 ReactCommon/yoga/yoga/Utils.cpp       | 10 +++++-----
 ReactCommon/yoga/yoga/YGLayout.cpp    | 10 +++++-----
 ReactCommon/yoga/yoga/YGNode.cpp      | 14 ++++++--------
 ReactCommon/yoga/yoga/Yoga-internal.h | 20 ++++++++++----------
 4 files changed, 26 insertions(+), 28 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.cpp b/ReactCommon/yoga/yoga/Utils.cpp
index 6fa8df823ba3..5f6c960d4bbf 100644
--- a/ReactCommon/yoga/yoga/Utils.cpp
+++ b/ReactCommon/yoga/yoga/Utils.cpp
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #include "Utils.h"
 
 YGFlexDirection YGFlexDirectionCross(
diff --git a/ReactCommon/yoga/yoga/YGLayout.cpp b/ReactCommon/yoga/yoga/YGLayout.cpp
index 6e367bd50a9b..604d7109c645 100644
--- a/ReactCommon/yoga/yoga/YGLayout.cpp
+++ b/ReactCommon/yoga/yoga/YGLayout.cpp
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #include "YGLayout.h"
 #include "Utils.h"
 
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 13571a9d62fb..9e7a182b72d8 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #include "YGNode.h"
 #include <iostream>
 #include "Utils.h"
@@ -97,8 +97,6 @@ YGFloatOptional YGNode::getMarginForAxis(
 
 // Setters
 
-
-
 void YGNode::setMeasureFunc(YGMeasureFunc measureFunc) {
   if (measureFunc == nullptr) {
     measure_ = nullptr;
@@ -396,7 +394,7 @@ void YGNode::resolveDimension() {
 YGDirection YGNode::resolveDirection(const YGDirection ownerDirection) {
   if (style_.direction == YGDirectionInherit) {
     return ownerDirection > YGDirectionInherit ? ownerDirection
-                                                : YGDirectionLTR;
+                                               : YGDirectionLTR;
   } else {
     return style_.direction;
   }
diff --git a/ReactCommon/yoga/yoga/Yoga-internal.h b/ReactCommon/yoga/yoga/Yoga-internal.h
index be1d96325b95..84c4596bc05c 100644
--- a/ReactCommon/yoga/yoga/Yoga-internal.h
+++ b/ReactCommon/yoga/yoga/Yoga-internal.h
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #pragma once
 #include <algorithm>
 #include <array>
@@ -16,10 +16,11 @@ using YGVector = std::vector<YGNodeRef>;
 
 YG_EXTERN_C_BEGIN
 
-WIN_EXPORT float YGRoundValueToPixelGrid(const float value,
-                                         const float pointScaleFactor,
-                                         const bool forceCeil,
-                                         const bool forceFloor);
+WIN_EXPORT float YGRoundValueToPixelGrid(
+    const float value,
+    const float pointScaleFactor,
+    const bool forceCeil,
+    const bool forceFloor);
 
 YG_EXTERN_C_END
 
@@ -87,7 +88,6 @@ struct YGCachedMeasurement {
 // layouts should not require more than 16 entries to fit within the cache.
 #define YG_MAX_CACHED_RESULT_COUNT 16
 
-
 static const float kDefaultFlexGrow = 0.0f;
 static const float kDefaultFlexShrink = 0.0f;
 static const float kWebDefaultFlexShrink = 1.0f;

From 04aaa01991b2b6af9587f4edb6a897e05fc5e1f8 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Wed, 18 Jul 2018 02:23:58 -0700
Subject: [PATCH 1082/1109] Make `YGFloatIsUndefined` inlineable

Summary:
@public

Makes `YGFloatIsUndefined` inlineable

Reviewed By: swolchok

Differential Revision: D8875520

fbshipit-source-id: 7ac653e002512b1a8d5f9c04e0a21381aeb02e67
---
 ReactCommon/yoga/yoga/Utils.cpp           | 18 +++++++-----
 ReactCommon/yoga/yoga/YGFloatOptional.cpp |  7 +++--
 ReactCommon/yoga/yoga/YGLayout.cpp        | 10 ++++---
 ReactCommon/yoga/yoga/YGNode.cpp          |  6 ++--
 ReactCommon/yoga/yoga/Yoga-internal.h     | 36 ++++++++++++++++++-----
 ReactCommon/yoga/yoga/Yoga.cpp            | 10 +------
 6 files changed, 54 insertions(+), 33 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Utils.cpp b/ReactCommon/yoga/yoga/Utils.cpp
index 5f6c960d4bbf..839952219d28 100644
--- a/ReactCommon/yoga/yoga/Utils.cpp
+++ b/ReactCommon/yoga/yoga/Utils.cpp
@@ -7,6 +7,8 @@
  */
 #include "Utils.h"
 
+using namespace facebook;
+
 YGFlexDirection YGFlexDirectionCross(
     const YGFlexDirection flexDirection,
     const YGDirection direction) {
@@ -16,18 +18,18 @@ YGFlexDirection YGFlexDirectionCross(
 }
 
 float YGFloatMax(const float a, const float b) {
-  if (!YGFloatIsUndefined(a) && !YGFloatIsUndefined(b)) {
+  if (!yoga::isUndefined(a) && !yoga::isUndefined(b)) {
     return fmaxf(a, b);
   }
-  return YGFloatIsUndefined(a) ? b : a;
+  return yoga::isUndefined(a) ? b : a;
 }
 
 float YGFloatMin(const float a, const float b) {
-  if (!YGFloatIsUndefined(a) && !YGFloatIsUndefined(b)) {
+  if (!yoga::isUndefined(a) && !yoga::isUndefined(b)) {
     return fminf(a, b);
   }
 
-  return YGFloatIsUndefined(a) ? b : a;
+  return yoga::isUndefined(a) ? b : a;
 }
 
 bool YGValueEqual(const YGValue a, const YGValue b) {
@@ -36,7 +38,7 @@ bool YGValueEqual(const YGValue a, const YGValue b) {
   }
 
   if (a.unit == YGUnitUndefined ||
-      (YGFloatIsUndefined(a.value) && YGFloatIsUndefined(b.value))) {
+      (yoga::isUndefined(a.value) && yoga::isUndefined(b.value))) {
     return true;
   }
 
@@ -44,14 +46,14 @@ bool YGValueEqual(const YGValue a, const YGValue b) {
 }
 
 bool YGFloatsEqual(const float a, const float b) {
-  if (!YGFloatIsUndefined(a) && !YGFloatIsUndefined(b)) {
+  if (!yoga::isUndefined(a) && !yoga::isUndefined(b)) {
     return fabs(a - b) < 0.0001f;
   }
-  return YGFloatIsUndefined(a) && YGFloatIsUndefined(b);
+  return yoga::isUndefined(a) && yoga::isUndefined(b);
 }
 
 float YGFloatSanitize(const float& val) {
-  return YGFloatIsUndefined(val) ? 0 : val;
+  return yoga::isUndefined(val) ? 0 : val;
 }
 
 float YGUnwrapFloatOptional(const YGFloatOptional& op) {
diff --git a/ReactCommon/yoga/yoga/YGFloatOptional.cpp b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
index d3407fa23cbb..cb867f3ac2fa 100644
--- a/ReactCommon/yoga/yoga/YGFloatOptional.cpp
+++ b/ReactCommon/yoga/yoga/YGFloatOptional.cpp
@@ -9,9 +9,12 @@
 #include <cstdlib>
 #include <iostream>
 #include "Yoga.h"
+#include "Yoga-internal.h"
+
+using namespace facebook;
 
 YGFloatOptional::YGFloatOptional(float value) {
-  if (YGFloatIsUndefined(value)) {
+  if (yoga::isUndefined(value)) {
     isUndefined_ = true;
     value_ = 0;
   } else {
@@ -41,7 +44,7 @@ bool YGFloatOptional::operator!=(const YGFloatOptional& op) const {
 }
 
 bool YGFloatOptional::operator==(float val) const {
-  if (YGFloatIsUndefined(val) == isUndefined_) {
+  if (yoga::isUndefined(val) == isUndefined_) {
     return isUndefined_ || val == value_;
   }
   return false;
diff --git a/ReactCommon/yoga/yoga/YGLayout.cpp b/ReactCommon/yoga/yoga/YGLayout.cpp
index 604d7109c645..dfd7be08bb10 100644
--- a/ReactCommon/yoga/yoga/YGLayout.cpp
+++ b/ReactCommon/yoga/yoga/YGLayout.cpp
@@ -8,6 +8,8 @@
 #include "YGLayout.h"
 #include "Utils.h"
 
+using namespace facebook;
+
 const std::array<float, 2> kYGDefaultDimensionValues = {
     {YGUndefined, YGUndefined}};
 
@@ -46,13 +48,13 @@ bool YGLayout::operator==(YGLayout layout) const {
     isEqual = isEqual && cachedMeasurements[i] == layout.cachedMeasurements[i];
   }
 
-  if (!YGFloatIsUndefined(measuredDimensions[0]) ||
-      !YGFloatIsUndefined(layout.measuredDimensions[0])) {
+  if (!yoga::isUndefined(measuredDimensions[0]) ||
+      !yoga::isUndefined(layout.measuredDimensions[0])) {
     isEqual =
         isEqual && (measuredDimensions[0] == layout.measuredDimensions[0]);
   }
-  if (!YGFloatIsUndefined(measuredDimensions[1]) ||
-      !YGFloatIsUndefined(layout.measuredDimensions[1])) {
+  if (!yoga::isUndefined(measuredDimensions[1]) ||
+      !yoga::isUndefined(layout.measuredDimensions[1])) {
     isEqual =
         isEqual && (measuredDimensions[1] == layout.measuredDimensions[1]);
   }
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 9e7a182b72d8..70dd655daa69 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -9,6 +9,8 @@
 #include <iostream>
 #include "Utils.h"
 
+using namespace facebook;
+
 YGFloatOptional YGNode::getLeadingPosition(
     const YGFlexDirection& axis,
     const float& axisSize) const {
@@ -500,7 +502,7 @@ bool YGNode::isNodeFlexible() {
 float YGNode::getLeadingBorder(const YGFlexDirection& axis) const {
   if (YGFlexDirectionIsRow(axis) &&
       style_.border[YGEdgeStart].unit != YGUnitUndefined &&
-      !YGFloatIsUndefined(style_.border[YGEdgeStart].value) &&
+      !yoga::isUndefined(style_.border[YGEdgeStart].value) &&
       style_.border[YGEdgeStart].value >= 0.0f) {
     return style_.border[YGEdgeStart].value;
   }
@@ -513,7 +515,7 @@ float YGNode::getLeadingBorder(const YGFlexDirection& axis) const {
 float YGNode::getTrailingBorder(const YGFlexDirection& flexDirection) const {
   if (YGFlexDirectionIsRow(flexDirection) &&
       style_.border[YGEdgeEnd].unit != YGUnitUndefined &&
-      !YGFloatIsUndefined(style_.border[YGEdgeEnd].value) &&
+      !yoga::isUndefined(style_.border[YGEdgeEnd].value) &&
       style_.border[YGEdgeEnd].value >= 0.0f) {
     return style_.border[YGEdgeEnd].value;
   }
diff --git a/ReactCommon/yoga/yoga/Yoga-internal.h b/ReactCommon/yoga/yoga/Yoga-internal.h
index 84c4596bc05c..941147e874d7 100644
--- a/ReactCommon/yoga/yoga/Yoga-internal.h
+++ b/ReactCommon/yoga/yoga/Yoga-internal.h
@@ -24,6 +24,26 @@ WIN_EXPORT float YGRoundValueToPixelGrid(
 
 YG_EXTERN_C_END
 
+namespace facebook {
+namespace yoga {
+
+inline bool isUndefined(float value) {
+  // Value of a float in the case of it being not defined is 10.1E20. Earlier
+  // it used to be NAN, the benefit of which was that if NAN is involved in any
+  // mathematical expression the result was NAN. But since we want to have
+  // `-ffast-math` flag being used by compiler which assumes that the floating
+  // point values are not NAN and Inf, we represent YGUndefined as 10.1E20. But
+  // now if YGUndefined is involved in any mathematical operations this
+  // value(10.1E20) would change. So the following check makes sure that if the
+  // value is outside a range (-10E8, 10E8) then it is undefined.
+  return value >= 10E8 || value <= -10E8;
+}
+
+} // namespace yoga
+} // namespace facebook
+
+using namespace facebook;
+
 extern const std::array<YGEdge, 4> trailing;
 extern const std::array<YGEdge, 4> leading;
 extern bool YGValueEqual(const YGValue a, const YGValue b);
@@ -63,20 +83,20 @@ struct YGCachedMeasurement {
     bool isEqual = widthMeasureMode == measurement.widthMeasureMode &&
         heightMeasureMode == measurement.heightMeasureMode;
 
-    if (!YGFloatIsUndefined(availableWidth) ||
-        !YGFloatIsUndefined(measurement.availableWidth)) {
+    if (!yoga::isUndefined(availableWidth) ||
+        !yoga::isUndefined(measurement.availableWidth)) {
       isEqual = isEqual && availableWidth == measurement.availableWidth;
     }
-    if (!YGFloatIsUndefined(availableHeight) ||
-        !YGFloatIsUndefined(measurement.availableHeight)) {
+    if (!yoga::isUndefined(availableHeight) ||
+        !yoga::isUndefined(measurement.availableHeight)) {
       isEqual = isEqual && availableHeight == measurement.availableHeight;
     }
-    if (!YGFloatIsUndefined(computedWidth) ||
-        !YGFloatIsUndefined(measurement.computedWidth)) {
+    if (!yoga::isUndefined(computedWidth) ||
+        !yoga::isUndefined(measurement.computedWidth)) {
       isEqual = isEqual && computedWidth == measurement.computedWidth;
     }
-    if (!YGFloatIsUndefined(computedHeight) ||
-        !YGFloatIsUndefined(measurement.computedHeight)) {
+    if (!yoga::isUndefined(computedHeight) ||
+        !yoga::isUndefined(measurement.computedHeight)) {
       isEqual = isEqual && computedHeight == measurement.computedHeight;
     }
 
diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index 1ea109e29353..fe419207307c 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -104,15 +104,7 @@ static int YGDefaultLog(const YGConfigRef config,
 #endif
 
 bool YGFloatIsUndefined(const float value) {
-  // Value of a float in the case of it being not defined is 10.1E20. Earlier
-  // it used to be NAN, the benefit of which was that if NAN is involved in any
-  // mathematical expression the result was NAN. But since we want to have
-  // `-ffast-math` flag being used by compiler which assumes that the floating
-  // point values are not NAN and Inf, we represent YGUndefined as 10.1E20. But
-  // now if YGUndefined is involved in any mathematical operations this
-  // value(10.1E20) would change. So the following check makes sure that if the
-  // value is outside a range (-10E8, 10E8) then it is undefined.
-  return value >= 10E8 || value <= -10E8;
+  return facebook::yoga::isUndefined(value);
 }
 
 const YGValue* YGComputedEdgeValue(

From f05943de0abfc16da41163c6b91a04ecc8de8e67 Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Wed, 18 Jul 2018 15:25:52 -0700
Subject: [PATCH 1083/1109] Fix local-cli assetRegistryPath and middlewares
 (#20162)

Summary:
This fixes some regressions with local-cli introduced in c4a66a89a28152cd4b81e2b0f80ab3aac34d6872.

- We didn't pass `assetRegistryPath` which caused the following error when loading the bundle:
```
error: bundling failed: Error: Unable to resolve module `missing-asset-registry-path` from `/Users/janic/Developer/react-native/RNTester/js/uie_thumb_normal@2x.png`: Module `missing-asset-registry-path` does not exist in the Haste module map
```
- The middlewares were not added to the metro server. This causes some packager server features to fail. The one I noticed is that the /status endpoint didn't exist anymore which causes CI to fail and also Android to not load the bundle from the packager initially. The remote debugging feature was also broken.
Pull Request resolved: https://github.com/facebook/react-native/pull/20162

Differential Revision: D8867610

Pulled By: hramos

fbshipit-source-id: 8a08b7f3175692ab6ee73c0a7c25075091ae4792
---
 .../server/middleware/MiddlewareManager.js    |  4 +--
 local-cli/server/runServer.js                 | 28 ++++++++++++++-----
 2 files changed, 23 insertions(+), 9 deletions(-)

diff --git a/local-cli/server/middleware/MiddlewareManager.js b/local-cli/server/middleware/MiddlewareManager.js
index 5402caf6f8ed..8692abdcc2ae 100644
--- a/local-cli/server/middleware/MiddlewareManager.js
+++ b/local-cli/server/middleware/MiddlewareManager.js
@@ -19,8 +19,8 @@ const indexPageMiddleware = require('./indexPage');
 const copyToClipBoardMiddleware = require('./copyToClipBoardMiddleware');
 const loadRawBodyMiddleware = require('./loadRawBodyMiddleware');
 const openStackFrameInEditorMiddleware = require('./openStackFrameInEditorMiddleware');
-const statusPageMiddleware = require('./statusPageMiddleware.js');
-const systraceProfileMiddleware = require('./systraceProfileMiddleware.js');
+const statusPageMiddleware = require('./statusPageMiddleware');
+const systraceProfileMiddleware = require('./systraceProfileMiddleware');
 const getDevToolsMiddleware = require('./getDevToolsMiddleware');
 
 type Options = {
diff --git a/local-cli/server/runServer.js b/local-cli/server/runServer.js
index 7f660bde298f..c7ea9c64a3d3 100644
--- a/local-cli/server/runServer.js
+++ b/local-cli/server/runServer.js
@@ -16,10 +16,14 @@ const Metro = require('metro');
 
 const {Terminal} = require('metro-core');
 
+const messageSocket = require('./util/messageSocket');
 const morgan = require('morgan');
 const path = require('path');
+const webSocketProxy = require('./util/webSocketProxy');
 const MiddlewareManager = require('./middleware/MiddlewareManager');
 
+const {ASSET_REGISTRY_PATH} = require('../core/Constants');
+
 import type {ConfigT} from 'metro';
 
 export type Args = {|
@@ -55,21 +59,31 @@ async function runServer(args: Args, config: ConfigT) {
   const serverInstance = await Metro.runServer({
     config: {
       ...config,
-      hmrEnabled: true,
-      maxWorkers: args.maxWorkers,
-      reporter,
-      secure: args.https,
-      secureKey: args.key,
-      secureCert: args.cert,
+      assetRegistryPath: ASSET_REGISTRY_PATH,
+      enhanceMiddleware: middleware =>
+        middlewareManager.getConnectInstance().use(middleware),
       transformModulePath: args.transformer
         ? path.resolve(args.transformer)
         : config.getTransformModulePath(),
-      watch: !args.nonPersistent,
     },
+    hmrEnabled: true,
     host: args.host,
+    maxWorkers: args.maxWorkers,
     port: args.port,
+    reporter,
+    secure: args.https,
+    secureCert: args.cert,
+    secureKey: args.key,
   });
 
+  const wsProxy = webSocketProxy.attachToServer(
+    serverInstance,
+    '/debugger-proxy',
+  );
+  const ms = messageSocket.attachToServer(serverInstance, '/message');
+  middlewareManager.attachDevToolsSocket(wsProxy);
+  middlewareManager.attachDevToolsSocket(ms);
+
   // In Node 8, the default keep-alive for an HTTP connection is 5 seconds. In
   // early versions of Node 8, this was implemented in a buggy way which caused
   // some HTTP responses (like those containing large JS bundles) to be

From 46fb04e7467d88b4f9760d86b6c08294dd4b9131 Mon Sep 17 00:00:00 2001
From: Scott Wolchok <swolchok@fb.com>
Date: Wed, 18 Jul 2018 15:45:34 -0700
Subject: [PATCH 1084/1109] Delete YGNode ctor w/arg per member

Summary: It doesn't seem to be used internally, it hurts greppability, and there are setters for these properties as needed anyway.

Reviewed By: davidaurelio

Differential Revision: D8842084

fbshipit-source-id: f0275b490e585ea94df341c97c34b441ed91c4fb
---
 ReactCommon/yoga/yoga/YGNode.cpp | 32 --------------------------------
 ReactCommon/yoga/yoga/YGNode.h   | 16 ----------------
 2 files changed, 48 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index 70dd655daa69..dda20a5533fb 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -292,38 +292,6 @@ YGNode::YGNode(const YGConfigRef newConfig) : YGNode() {
   config_ = newConfig;
 }
 
-YGNode::YGNode(
-    void* context,
-    YGPrintFunc print,
-    bool hasNewLayout,
-    YGNodeType nodeType,
-    YGMeasureFunc measure,
-    YGBaselineFunc baseline,
-    YGDirtiedFunc dirtied,
-    YGStyle style,
-    const YGLayout& layout,
-    uint32_t lineIndex,
-    YGNodeRef owner,
-    const YGVector& children,
-    YGConfigRef config,
-    bool isDirty,
-    std::array<YGValue, 2> resolvedDimensions)
-    : context_(context),
-      print_(print),
-      hasNewLayout_(hasNewLayout),
-      nodeType_(nodeType),
-      measure_(measure),
-      baseline_(baseline),
-      dirtied_(dirtied),
-      style_(style),
-      layout_(layout),
-      lineIndex_(lineIndex),
-      owner_(owner),
-      children_(children),
-      config_(config),
-      isDirty_(isDirty),
-      resolvedDimensions_(resolvedDimensions) {}
-
 YGNode& YGNode::operator=(const YGNode& node) {
   if (&node == this) {
     return *this;
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index c204d4600b15..cba72163f30b 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -40,22 +40,6 @@ struct YGNode {
   explicit YGNode(const YGConfigRef newConfig);
   YGNode(const YGNode& node);
   YGNode& operator=(const YGNode& node);
-  YGNode(
-      void* context,
-      YGPrintFunc print,
-      bool hasNewLayout,
-      YGNodeType nodeType,
-      YGMeasureFunc measure,
-      YGBaselineFunc baseline,
-      YGDirtiedFunc dirtied,
-      YGStyle style,
-      const YGLayout& layout,
-      uint32_t lineIndex,
-      YGNodeRef owner,
-      const YGVector& children,
-      YGConfigRef config,
-      bool isDirty,
-      std::array<YGValue, 2> resolvedDimensions);
 
   // Getters
   void* getContext() const {

From 165dd40beaa3e1b0cc030623118b78985ad6cbe0 Mon Sep 17 00:00:00 2001
From: Scott Wolchok <swolchok@fb.com>
Date: Wed, 18 Jul 2018 15:45:36 -0700
Subject: [PATCH 1085/1109] Explicitly default YGNode copy ctor

Summary: No need to type out the old version. This is exactly equivalent (unless I've misread and the old version did something other than memberwise copy).

Reviewed By: davidaurelio

Differential Revision: D8842326

fbshipit-source-id: c575ea4cee6caef9ea15aaf5967597385ed26ec3
---
 ReactCommon/yoga/yoga/YGNode.cpp | 17 +----------------
 1 file changed, 1 insertion(+), 16 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index dda20a5533fb..fc97e1728441 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -271,22 +271,7 @@ YGNode::YGNode()
       isDirty_(false),
       resolvedDimensions_({{YGValueUndefined, YGValueUndefined}}) {}
 
-YGNode::YGNode(const YGNode& node)
-    : context_(node.context_),
-      print_(node.print_),
-      hasNewLayout_(node.hasNewLayout_),
-      nodeType_(node.nodeType_),
-      measure_(node.measure_),
-      baseline_(node.baseline_),
-      dirtied_(node.dirtied_),
-      style_(node.style_),
-      layout_(node.layout_),
-      lineIndex_(node.lineIndex_),
-      owner_(node.owner_),
-      children_(node.children_),
-      config_(node.config_),
-      isDirty_(node.isDirty_),
-      resolvedDimensions_(node.resolvedDimensions_) {}
+YGNode::YGNode(const YGNode& node) = default;
 
 YGNode::YGNode(const YGConfigRef newConfig) : YGNode() {
   config_ = newConfig;

From 7ff7572e5c705e501ba83a0df4e623cc0ee6f42d Mon Sep 17 00:00:00 2001
From: Himabindu Gadupudi <himabindug@fb.com>
Date: Wed, 18 Jul 2018 16:57:36 -0700
Subject: [PATCH 1086/1109] Fix Android RN server snapshot tests

Summary: Trying to see what it takes to get server snapshot tests working on android. This will be landed after fixing few things.

Reviewed By: achen1

Differential Revision: D8237948

fbshipit-source-id: 926555ba752171dac4e5814f5c8e5c2c173a82c7
---
 .../react/testing/ReactAppTestActivity.java   | 168 +++++++++---------
 1 file changed, 86 insertions(+), 82 deletions(-)

diff --git a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
index 5ca48fcf6437..91b2c523dbff 100644
--- a/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
+++ b/ReactAndroid/src/androidTest/java/com/facebook/react/testing/ReactAppTestActivity.java
@@ -1,16 +1,16 @@
 /**
  * Copyright (c) 2014-present, Facebook, Inc.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
+ * <p>This source code is licensed under the MIT license found in the LICENSE file in the root
+ * directory of this source tree.
  */
-
 package com.facebook.react.testing;
 
 import static com.facebook.react.bridge.UiThreadUtil.runOnUiThread;
 
 import android.content.Intent;
 import android.graphics.Bitmap;
+import android.os.AsyncTask;
 import android.os.Bundle;
 import android.support.v4.app.FragmentActivity;
 import android.view.View;
@@ -47,6 +47,7 @@
 import java.util.concurrent.TimeUnit;
 import javax.annotation.Nullable;
 
+
 public class ReactAppTestActivity extends FragmentActivity
     implements DefaultHardwareBackBtnHandler, PermissionAwareActivity {
 
@@ -56,11 +57,10 @@ public class ReactAppTestActivity extends FragmentActivity
   private static final int ROOT_VIEW_ID = 8675309;
   // we need a bigger timeout for CI builds because they run on a slow emulator
   private static final long IDLE_TIMEOUT_MS = 120000;
-
+  private final CountDownLatch mDestroyCountDownLatch = new CountDownLatch(1);
   private CountDownLatch mLayoutEvent = new CountDownLatch(1);
   private @Nullable ReactBridgeIdleSignaler mBridgeIdleSignaler;
   private ScreenshotingFrameLayout mScreenshotingFrameLayout;
-  private final CountDownLatch mDestroyCountDownLatch = new CountDownLatch(1);
   private @Nullable ReactInstanceManager mReactInstanceManager;
   private @Nullable ReactRootView mReactRootView;
   private LifecycleState mLifecycleState = LifecycleState.BEFORE_RESUME;
@@ -138,10 +138,7 @@ public void loadApp(String appKey, ReactInstanceSpecForTest spec, boolean enable
     loadApp(appKey, spec, null, DEFAULT_BUNDLE_NAME, enableDevSupport);
   }
 
-  public void loadApp(
-    String appKey,
-    ReactInstanceSpecForTest spec,
-    String bundleName) {
+  public void loadApp(String appKey, ReactInstanceSpecForTest spec, String bundleName) {
     loadApp(appKey, spec, null, bundleName, false /* = useDevSupport */);
   }
 
@@ -160,11 +157,11 @@ public void resetRootViewForScreenshotTests() {
   }
 
   public void loadApp(
-    String appKey,
-    ReactInstanceSpecForTest spec,
-    @Nullable Bundle initialProps,
-    String bundleName,
-    boolean useDevSupport) {
+      String appKey,
+      ReactInstanceSpecForTest spec,
+      @Nullable Bundle initialProps,
+      String bundleName,
+      boolean useDevSupport) {
     loadBundle(spec, bundleName, useDevSupport);
     renderComponent(appKey, initialProps);
   }
@@ -175,32 +172,34 @@ public void renderComponent(String appKey) {
 
   public void renderComponent(final String appKey, final @Nullable Bundle initialProps) {
     final CountDownLatch currentLayoutEvent = mLayoutEvent = new CountDownLatch(1);
-    runOnUiThread(new Runnable() {
-      @Override
-      public void run() {
-        Assertions.assertNotNull(mReactRootView).getViewTreeObserver().addOnGlobalLayoutListener(
-            new ViewTreeObserver.OnGlobalLayoutListener() {
-              @Override
-              public void onGlobalLayout() {
-                currentLayoutEvent.countDown();
-              }
-            });
-        Assertions.assertNotNull(mReactRootView)
-            .startReactApplication(mReactInstanceManager, appKey, initialProps);
-      }
-    });
-    try {
-      waitForBridgeAndUIIdle();
-      waitForLayout(5000);
-    } catch (InterruptedException e) {
-      throw new RuntimeException("Layout never occurred for component " + appKey, e);
-    }
+    runOnUiThread(
+        new Runnable() {
+          @Override
+          public void run() {
+            Assertions.assertNotNull(mReactRootView)
+                .getViewTreeObserver()
+                .addOnGlobalLayoutListener(
+                    new ViewTreeObserver.OnGlobalLayoutListener() {
+                      @Override
+                      public void onGlobalLayout() {
+                        currentLayoutEvent.countDown();
+                        Assertions.assertNotNull(mReactRootView)
+                            .getViewTreeObserver()
+                            .removeGlobalOnLayoutListener(this);
+                      }
+                    });
+            Assertions.assertNotNull(mReactRootView)
+                .startReactApplication(mReactInstanceManager, appKey, initialProps);
+          }
+        });
+        try {
+          waitForBridgeAndUIIdle();
+          waitForLayout(5000);
+        } catch (InterruptedException e) {
+          throw new RuntimeException("Layout never occurred for component " + appKey, e);}
   }
 
-  public void loadBundle(
-      ReactInstanceSpecForTest spec,
-      String bundleName,
-      boolean useDevSupport) {
+  public void loadBundle(ReactInstanceSpecForTest spec, String bundleName, boolean useDevSupport) {
 
     mBridgeIdleSignaler = new ReactBridgeIdleSignaler();
 
@@ -219,7 +218,7 @@ public void loadBundle(
         // By not setting a JS module name, we force the bundle to be always loaded from
         // assets, not the devserver, even if dev mode is enabled (such as when testing redboxes).
         // This makes sense because we never run the devserver in tests.
-        //.setJSMainModuleName()
+        // .setJSMainModuleName()
         .setUseDeveloperSupport(useDevSupport)
         .setBridgeIdleDebugListener(mBridgeIdleSignaler)
         .setInitialLifecycleState(mLifecycleState)
@@ -230,43 +229,54 @@ public List<JSIModuleSpec> getJSIModules(
                   final ReactApplicationContext reactApplicationContext,
                   final JavaScriptContextHolder jsContext) {
                 return Arrays.<JSIModuleSpec>asList(
-                  new JSIModuleSpec() {
-                    @Override
-                    public Class<? extends JSIModule> getJSIModuleClass() {
-                      return UIManager.class;
-                    }
-
-                    @Override
-                    public JSIModuleProvider getJSIModuleProvider() {
-                      return new JSIModuleProvider() {
-                        @Override
-                        public FabricUIManager get() {
-                          List<ViewManager> viewManagers =
-                            mReactInstanceManager.getOrCreateViewManagers(reactApplicationContext);
-                          EventDispatcher eventDispatcher =
-                            reactApplicationContext.getNativeModule(UIManagerModule.class).getEventDispatcher();
-                          FabricUIManager fabricUIManager =
-                            new FabricUIManager(reactApplicationContext, new ViewManagerRegistry(viewManagers), jsContext, eventDispatcher);
-                          new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
-                          return fabricUIManager;
-                        }
-                      };
-                    }
-                  });
-              }});
+                    new JSIModuleSpec() {
+                      @Override
+                      public Class<? extends JSIModule> getJSIModuleClass() {
+                        return UIManager.class;
+                      }
+
+                      @Override
+                      public JSIModuleProvider getJSIModuleProvider() {
+                        return new JSIModuleProvider() {
+                          @Override
+                          public FabricUIManager get() {
+                            List<ViewManager> viewManagers =
+                                mReactInstanceManager.getOrCreateViewManagers(
+                                    reactApplicationContext);
+                            EventDispatcher eventDispatcher =
+                                reactApplicationContext
+                                    .getNativeModule(UIManagerModule.class)
+                                    .getEventDispatcher();
+                            FabricUIManager fabricUIManager =
+                                new FabricUIManager(
+                                    reactApplicationContext,
+                                    new ViewManagerRegistry(viewManagers),
+                                    jsContext,
+                                    eventDispatcher);
+                            new FabricJSCBinding().installFabric(jsContext, fabricUIManager);
+                            return fabricUIManager;
+                          }
+                        };
+                      }
+                    });
+              }
+            });
 
     final CountDownLatch latch = new CountDownLatch(1);
-    runOnUiThread(new Runnable() {
-      @Override
-      public void run() {
-        mReactInstanceManager = builder.build();
-        mReactInstanceManager.onHostResume(ReactAppTestActivity.this, ReactAppTestActivity.this);
-        latch.countDown();
-      }
-    });
+    runOnUiThread(
+        new Runnable() {
+          @Override
+          public void run() {
+            mReactInstanceManager = builder.build();
+            mReactInstanceManager.onHostResume(
+                ReactAppTestActivity.this, ReactAppTestActivity.this);
+            latch.countDown();
+          }
+        });
     try {
       latch.await(1000, TimeUnit.MILLISECONDS);
     } catch (InterruptedException e) {
+
       throw new RuntimeException(
           "ReactInstanceManager never finished initializing " + bundleName, e);
     }
@@ -286,9 +296,7 @@ public void waitForBridgeAndUIIdle() {
 
   public void waitForBridgeAndUIIdle(long timeoutMs) {
     ReactIdleDetectionUtil.waitForBridgeAndUIIdle(
-        Assertions.assertNotNull(mBridgeIdleSignaler),
-        getReactContext(),
-        timeoutMs);
+        Assertions.assertNotNull(mBridgeIdleSignaler), getReactContext(), timeoutMs);
   }
 
   public View getRootView() {
@@ -309,7 +317,7 @@ private ReactContext waitForReactContext() {
       while (true) {
         ReactContext reactContext = mReactInstanceManager.getCurrentReactContext();
         if (reactContext != null) {
-           return reactContext;
+          return reactContext;
         }
         Thread.sleep(100);
       }
@@ -323,9 +331,8 @@ public void postDelayed(Runnable r, int delayMS) {
   }
 
   /**
-   * Does not ensure that this is run on the UI thread or that the UI Looper is idle like
-   * {@link ReactAppInstrumentationTestCase#getScreenshot()}. You probably want to use that
-   * instead.
+   * Does not ensure that this is run on the UI thread or that the UI Looper is idle like {@link
+   * ReactAppInstrumentationTestCase#getScreenshot()}. You probably want to use that instead.
    */
   public Bitmap getCurrentScreenshot() {
     return mScreenshotingFrameLayout.getLastDrawnBitmap();
@@ -346,10 +353,7 @@ public void invokeDefaultOnBackPressed() {
 
   @Override
   public void onRequestPermissionsResult(
-      int requestCode,
-      String[] permissions,
-      int[] grantResults) {
-  }
+      int requestCode, String[] permissions, int[] grantResults) {}
 
   @Override
   public void requestPermissions(

From be715ec7053a77fa6c9087990a493d17c1155de2 Mon Sep 17 00:00:00 2001
From: Mats Byrkeland <matsbyr@gmail.com>
Date: Wed, 18 Jul 2018 17:13:56 -0700
Subject: [PATCH 1087/1109] Make AccessibilityInfo.setAccessibilityFocus cross
 platform (#20229)

Summary:
Currently, `AccessibilityInfo.setAccessibilityFocus` is only available on iOS. The same behaviour can be achieved on Android by dispatching the proper accessibility event. I implemented the same function for Android, to make life slightly more convenient for the developer.

Today, developers must write something like this:
```
if (Platform.OS === 'ios') {
     AccessibilityInfo.setAccessibilityFocus(reactTag)
} else {
     UIManager.sendAccessibilityEvent(reactTag, 8)
}
```

With this change, the following is enough for both Android and iOS:
```
AccessibilityInfo.setAccessibilityFocus(reactTag)
```
Pull Request resolved: https://github.com/facebook/react-native/pull/20229

Differential Revision: D8874107

Pulled By: mdvacca

fbshipit-source-id: a6ffd7bb89ce56d6d65b06419633a71dcf3d0733
---
 .../AccessibilityInfo/AccessibilityInfo.android.js  | 13 +++++++++++++
 .../AccessibilityInfo/AccessibilityInfo.ios.js      |  2 --
 .../react/uimanager/UIManagerModuleConstants.java   |  2 ++
 3 files changed, 15 insertions(+), 2 deletions(-)

diff --git a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
index dfa09b53a466..09547ea06367 100644
--- a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
+++ b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.android.js
@@ -12,6 +12,7 @@
 
 const NativeModules = require('NativeModules');
 const RCTDeviceEventEmitter = require('RCTDeviceEventEmitter');
+const UIManager = require('UIManager');
 
 const RCTAccessibilityInfo = NativeModules.AccessibilityInfo;
 
@@ -66,6 +67,18 @@ const AccessibilityInfo = {
     listener.remove();
     _subscriptions.delete(handler);
   },
+
+  /**
+   * Set accessibility focus to a react component.
+   *
+   * See http://facebook.github.io/react-native/docs/accessibilityinfo.html#setaccessibilityfocus
+   */
+  setAccessibilityFocus: function(reactTag: number): void {
+    UIManager.sendAccessibilityEvent(
+      reactTag,
+      UIManager.AccessibilityEventTypes.typeViewFocused,
+    );
+  },
 };
 
 module.exports = AccessibilityInfo;
diff --git a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
index 8f2b0aa78dc0..da1f6e4f1610 100644
--- a/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
+++ b/Libraries/Components/AccessibilityInfo/AccessibilityInfo.ios.js
@@ -93,8 +93,6 @@ const AccessibilityInfo = {
   /**
    * Set accessibility focus to a react component.
    *
-   * @platform ios
-   *
    * See http://facebook.github.io/react-native/docs/accessibilityinfo.html#setaccessibilityfocus
    */
   setAccessibilityFocus: function(reactTag: number): void {
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModuleConstants.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModuleConstants.java
index 1eea5018a8df..eb740fd081bd 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModuleConstants.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/UIManagerModuleConstants.java
@@ -134,6 +134,8 @@ public static Map<String, Object> getConstants() {
       MapBuilder.of(
           "typeWindowStateChanged",
           AccessibilityEvent.TYPE_WINDOW_STATE_CHANGED,
+          "typeViewFocused",
+          AccessibilityEvent.TYPE_VIEW_FOCUSED,
           "typeViewClicked",
           AccessibilityEvent.TYPE_VIEW_CLICKED));
 

From b9d1c832b0bb7161bcec48d655e878af609b8350 Mon Sep 17 00:00:00 2001
From: Peter van der Zee <kuvos@fb.com>
Date: Thu, 19 Jul 2018 04:48:08 -0700
Subject: [PATCH 1088/1109] Bump babel to 7 beta.54

Summary:
@public
Bump Babel to version 7 beta 54

This version has reversed the windows path denormalization so we need it to be able to fix windows paths.

Reviewed By: rafeca

Differential Revision: D8894700

fbshipit-source-id: 3ae1480b77380cae8070621d4729b21a34c4b928
---
 package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/package.json b/package.json
index eceeafd5139e..09b5ec0330eb 100644
--- a/package.json
+++ b/package.json
@@ -199,7 +199,7 @@
     "yargs": "^9.0.0"
   },
   "devDependencies": {
-    "@babel/core": "7.0.0-beta.48",
+    "@babel/core": "7.0.0-beta.54",
     "async": "^2.4.0",
     "babel-eslint": "9.0.0-beta.2",
     "babel-generator": "^6.26.0",

From e183844df548917fc666a82d728f2fe293c388ac Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Ma=C3=ABl=20Nison?= <mael@fb.com>
Date: Thu, 19 Jul 2018 05:01:23 -0700
Subject: [PATCH 1089/1109] Uniformizes how THIS_DIR is computed in xplat/js

Summary: This form of THIS_DIR resolves symlinks, which is better.

Reviewed By: davidaurelio

Differential Revision: D8661886

fbshipit-source-id: 90bf329e765d9623d103b03c5dd3b71fae9d9854
---
 IntegrationTests/launchWebSocketServer.command | 4 ++--
 runXcodeTests.sh                               | 4 ++--
 scripts/launchPackager.command                 | 4 ++--
 scripts/packager.sh                            | 4 ++--
 scripts/run-android-emulator.sh                | 2 +-
 5 files changed, 9 insertions(+), 9 deletions(-)

diff --git a/IntegrationTests/launchWebSocketServer.command b/IntegrationTests/launchWebSocketServer.command
index a6531c5f8d78..445f3fc0fa88 100755
--- a/IntegrationTests/launchWebSocketServer.command
+++ b/IntegrationTests/launchWebSocketServer.command
@@ -1,4 +1,4 @@
-#!/usr/bin/env bash
+#!/bin/bash
 
 # Copyright (c) 2015-present, Facebook, Inc.
 #
@@ -9,7 +9,7 @@
 echo -en "\033]0;Web Socket Test Server\a"
 clear
 
-THIS_DIR=$(dirname "$0")
+THIS_DIR=$(cd -P "$(dirname "$(readlink "${BASH_SOURCE[0]}" || echo "${BASH_SOURCE[0]}")")" && pwd)
 pushd "$THIS_DIR"
 ./websocket_integration_test_server.js
 popd
diff --git a/runXcodeTests.sh b/runXcodeTests.sh
index b1b6e7f4fba3..9b9b00b99ae4 100755
--- a/runXcodeTests.sh
+++ b/runXcodeTests.sh
@@ -1,7 +1,7 @@
-#!/bin/sh
+#!/bin/bash
 # This script should be run from the react-native root
 
-THIS_DIR=$(dirname "$0")
+THIS_DIR=$(cd -P "$(dirname "$(readlink "${BASH_SOURCE[0]}" || echo "${BASH_SOURCE[0]}")")" && pwd)
 source "scripts/.tests.env"
 
 if [ -n "$1" ]
diff --git a/scripts/launchPackager.command b/scripts/launchPackager.command
index b4570cd3c630..f8146dcf91a4 100755
--- a/scripts/launchPackager.command
+++ b/scripts/launchPackager.command
@@ -1,4 +1,4 @@
-#!/usr/bin/env bash
+#!/bin/bash
 
 # Copyright (c) 2015-present, Facebook, Inc.
 #
@@ -9,7 +9,7 @@
 echo -en "\033]0;Metro Bundler\a"
 clear
 
-THIS_DIR=$(dirname "$0")
+THIS_DIR=$(cd -P "$(dirname "$(readlink "${BASH_SOURCE[0]}" || echo "${BASH_SOURCE[0]}")")" && pwd)
 . "$THIS_DIR/packager.sh"
 
 echo "Process terminated. Press <enter> to close the window"
diff --git a/scripts/packager.sh b/scripts/packager.sh
index ee3966923a2b..1d33bf557e8f 100755
--- a/scripts/packager.sh
+++ b/scripts/packager.sh
@@ -1,11 +1,11 @@
-#!/usr/bin/env bash
+#!/bin/bash
 
 # Copyright (c) 2015-present, Facebook, Inc.
 #
 # This source code is licensed under the MIT license found in the
 # LICENSE file in the root directory of this source tree.
 
-THIS_DIR=$(dirname "$0")
+THIS_DIR=$(cd -P "$(dirname "$(readlink "${BASH_SOURCE[0]}" || echo "${BASH_SOURCE[0]}")")" && pwd)
 source "${THIS_DIR}/.packager.env"
 cd "$THIS_DIR/.."
 node "./local-cli/cli.js" start "$@"
diff --git a/scripts/run-android-emulator.sh b/scripts/run-android-emulator.sh
index d7307120b0ed..d2c6390d9523 100755
--- a/scripts/run-android-emulator.sh
+++ b/scripts/run-android-emulator.sh
@@ -6,7 +6,7 @@
 # virtual device configuration.
 # This is useful for running integration tests on a local machine.
 
-THIS_DIR=$(dirname "$0")
+THIS_DIR=$(cd -P "$(dirname "$(readlink "${BASH_SOURCE[0]}" || echo "${BASH_SOURCE[0]}")")" && pwd)
 
 STATE=`adb get-state`
 

From dfc7b2fd03ac412e00b486f4165cd051625df6fc Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 19 Jul 2018 09:51:23 -0700
Subject: [PATCH 1090/1109] auto-lint YGLayout.h YGNode.h YGStyle.cpp YGStyle.h

Summary:
@public

automatically applies lint fixes to  YGLayout.h YGNode.h YGStyle.cpp YGStyle.h

Reviewed By: astreet

Differential Revision: D8913432

fbshipit-source-id: 488bf25db041ddb527565c26c1762c6ee4cae736
---
 ReactCommon/yoga/yoga/YGLayout.h  | 10 +++----
 ReactCommon/yoga/yoga/YGNode.h    | 49 ++++++++++++++++---------------
 ReactCommon/yoga/yoga/YGStyle.cpp | 10 +++----
 ReactCommon/yoga/yoga/YGStyle.h   | 10 +++----
 4 files changed, 40 insertions(+), 39 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGLayout.h b/ReactCommon/yoga/yoga/YGLayout.h
index 46ca130d29bf..ebd934333e5d 100644
--- a/ReactCommon/yoga/yoga/YGLayout.h
+++ b/ReactCommon/yoga/yoga/YGLayout.h
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #pragma once
 #include "YGFloatOptional.h"
 #include "Yoga-internal.h"
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index cba72163f30b..b02c02cbfea2 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #pragma once
 #include <stdio.h>
 #include "YGConfig.h"
@@ -53,23 +53,23 @@ struct YGNode {
   bool getHasNewLayout() const {
     return hasNewLayout_;
   }
-  
+
   YGNodeType getNodeType() const {
     return nodeType_;
   }
-  
+
   YGMeasureFunc getMeasure() const {
     return measure_;
   }
-  
+
   YGBaselineFunc getBaseline() const {
     return baseline_;
   }
-  
+
   YGDirtiedFunc getDirtied() const {
     return dirtied_;
   }
-  
+
   // For Performance reasons passing as reference.
   YGStyle& getStyle() {
     return style_;
@@ -87,11 +87,11 @@ struct YGNode {
   const YGLayout& getLayout() const {
     return layout_;
   }
-  
+
   uint32_t getLineIndex() const {
     return lineIndex_;
   }
-  
+
   // returns the YGNodeRef that owns this YGNode. An owner is used to identify
   // the YogaTree that a YGNode belongs to.
   // This method will return the parent of the YGNode when a YGNode only belongs
@@ -100,16 +100,16 @@ struct YGNode {
   YGNodeRef getOwner() const {
     return owner_;
   }
-  
+
   // Deprecated, use getOwner() instead.
   YGNodeRef getParent() const {
     return getOwner();
   }
-  
+
   const YGVector& getChildren() const {
     return children_;
   }
-  
+
   YGNodeRef getChild(uint32_t index) const {
     return children_.at(index);
   }
@@ -117,21 +117,22 @@ struct YGNode {
   YGConfigRef getConfig() const {
     return config_;
   }
-  
+
   bool isDirty() const {
     return isDirty_;
   }
-  
+
   std::array<YGValue, 2> getResolvedDimensions() const {
     return resolvedDimensions_;
   }
-  
+
   YGValue getResolvedDimension(int index) const {
     return resolvedDimensions_[index];
   }
 
   // Methods related to positions, margin, padding and border
-  YGFloatOptional getLeadingPosition(const YGFlexDirection& axis,
+  YGFloatOptional getLeadingPosition(
+      const YGFlexDirection& axis,
       const float& axisSize) const;
   bool isLeadingPositionDefined(const YGFlexDirection& axis) const;
   bool isTrailingPosDefined(const YGFlexDirection& axis) const;
@@ -174,7 +175,7 @@ struct YGNode {
   void setHasNewLayout(bool hasNewLayout) {
     hasNewLayout_ = hasNewLayout;
   }
-  
+
   void setNodeType(YGNodeType nodeType) {
     nodeType_ = nodeType;
   }
@@ -200,15 +201,15 @@ struct YGNode {
   void setStyle(const YGStyle& style) {
     style_ = style;
   }
-  
+
   void setLayout(const YGLayout& layout) {
     layout_ = layout;
   }
-  
+
   void setLineIndex(uint32_t lineIndex) {
     lineIndex_ = lineIndex;
   }
-  
+
   void setOwner(YGNodeRef owner) {
     owner_ = owner;
   }
@@ -218,7 +219,7 @@ struct YGNode {
   }
 
   // TODO: rvalue override for setChildren
-  
+
   void setConfig(YGConfigRef config) {
     config_ = config;
   }
diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index 7664dcf8e59c..738d36fb0fa1 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #include "YGStyle.h"
 
 const YGValue kYGValueUndefined = {0, YGUnitUndefined};
diff --git a/ReactCommon/yoga/yoga/YGStyle.h b/ReactCommon/yoga/yoga/YGStyle.h
index f0f97bd8faf1..b18ac0a6eb87 100644
--- a/ReactCommon/yoga/yoga/YGStyle.h
+++ b/ReactCommon/yoga/yoga/YGStyle.h
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #pragma once
 #include "YGFloatOptional.h"
 #include "Yoga-internal.h"

From 1d7a24ff0cb8a06e018cd2e97bd3241513089bdc Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 19 Jul 2018 09:51:25 -0700
Subject: [PATCH 1091/1109] inline trivial constructors / methods

Summary:
@public

inlines some trivial constructors, destructors, and methods.

Reviewed By: astreet

Differential Revision: D8912691

fbshipit-source-id: 79840ef3322676deebed99391390d6c1796963b5
---
 ReactCommon/yoga/yoga/YGLayout.cpp |  4 ---
 ReactCommon/yoga/yoga/YGLayout.h   |  4 ++-
 ReactCommon/yoga/yoga/YGNode.cpp   | 28 ---------------------
 ReactCommon/yoga/yoga/YGNode.h     | 39 +++++++++++++++---------------
 ReactCommon/yoga/yoga/YGStyle.cpp  |  6 -----
 ReactCommon/yoga/yoga/YGStyle.h    |  8 +++---
 6 files changed, 28 insertions(+), 61 deletions(-)

diff --git a/ReactCommon/yoga/yoga/YGLayout.cpp b/ReactCommon/yoga/yoga/YGLayout.cpp
index dfd7be08bb10..03933ac9ab46 100644
--- a/ReactCommon/yoga/yoga/YGLayout.cpp
+++ b/ReactCommon/yoga/yoga/YGLayout.cpp
@@ -61,7 +61,3 @@ bool YGLayout::operator==(YGLayout layout) const {
 
   return isEqual;
 }
-
-bool YGLayout::operator!=(YGLayout layout) const {
-  return !(*this == layout);
-}
diff --git a/ReactCommon/yoga/yoga/YGLayout.h b/ReactCommon/yoga/yoga/YGLayout.h
index ebd934333e5d..1df905d0b80a 100644
--- a/ReactCommon/yoga/yoga/YGLayout.h
+++ b/ReactCommon/yoga/yoga/YGLayout.h
@@ -38,5 +38,7 @@ struct YGLayout {
   YGLayout();
 
   bool operator==(YGLayout layout) const;
-  bool operator!=(YGLayout layout) const;
+  bool operator!=(YGLayout layout) const {
+    return !(*this == layout);
+  }
 };
diff --git a/ReactCommon/yoga/yoga/YGNode.cpp b/ReactCommon/yoga/yoga/YGNode.cpp
index fc97e1728441..a80484f168cc 100644
--- a/ReactCommon/yoga/yoga/YGNode.cpp
+++ b/ReactCommon/yoga/yoga/YGNode.cpp
@@ -254,29 +254,6 @@ void YGNode::setPosition(
       trailing[crossAxis]);
 }
 
-YGNode::YGNode()
-    : context_(nullptr),
-      print_(nullptr),
-      hasNewLayout_(true),
-      nodeType_(YGNodeTypeDefault),
-      measure_(nullptr),
-      baseline_(nullptr),
-      dirtied_(nullptr),
-      style_(YGStyle()),
-      layout_(YGLayout()),
-      lineIndex_(0),
-      owner_(nullptr),
-      children_(YGVector()),
-      config_(nullptr),
-      isDirty_(false),
-      resolvedDimensions_({{YGValueUndefined, YGValueUndefined}}) {}
-
-YGNode::YGNode(const YGNode& node) = default;
-
-YGNode::YGNode(const YGConfigRef newConfig) : YGNode() {
-  config_ = newConfig;
-}
-
 YGNode& YGNode::operator=(const YGNode& node) {
   if (&node == this) {
     return *this;
@@ -360,11 +337,6 @@ void YGNode::clearChildren() {
   children_.shrink_to_fit();
 }
 
-YGNode::~YGNode() {
-  // All the member variables are deallocated externally, so no need to
-  // deallocate here
-}
-
 // Other Methods
 
 void YGNode::cloneChildrenIfNeeded() {
diff --git a/ReactCommon/yoga/yoga/YGNode.h b/ReactCommon/yoga/yoga/YGNode.h
index b02c02cbfea2..7120846ef731 100644
--- a/ReactCommon/yoga/yoga/YGNode.h
+++ b/ReactCommon/yoga/yoga/YGNode.h
@@ -14,31 +14,32 @@
 
 struct YGNode {
  private:
-  void* context_;
-  YGPrintFunc print_;
-  bool hasNewLayout_;
-  YGNodeType nodeType_;
-  YGMeasureFunc measure_;
-  YGBaselineFunc baseline_;
-  YGDirtiedFunc dirtied_;
-  YGStyle style_;
-  YGLayout layout_;
-  uint32_t lineIndex_;
-  YGNodeRef owner_;
-  YGVector children_;
-  YGConfigRef config_;
-  bool isDirty_;
-  std::array<YGValue, 2> resolvedDimensions_;
+  void* context_ = nullptr;
+  YGPrintFunc print_ = nullptr;
+  bool hasNewLayout_ = true;
+  YGNodeType nodeType_ = YGNodeTypeDefault;
+  YGMeasureFunc measure_ = nullptr;
+  YGBaselineFunc baseline_ = nullptr;
+  YGDirtiedFunc dirtied_ = nullptr;
+  YGStyle style_ = {};
+  YGLayout layout_ = {};
+  uint32_t lineIndex_ = 0;
+  YGNodeRef owner_ = nullptr;
+  YGVector children_ = {};
+  YGConfigRef config_ = nullptr;
+  bool isDirty_ = false;
+  std::array<YGValue, 2> resolvedDimensions_ = {
+      {YGValueUndefined, YGValueUndefined}};
 
   YGFloatOptional relativePosition(
       const YGFlexDirection& axis,
       const float& axisSize) const;
 
  public:
-  YGNode();
-  ~YGNode();
-  explicit YGNode(const YGConfigRef newConfig);
-  YGNode(const YGNode& node);
+  YGNode() = default;
+  ~YGNode() = default; // cleanup of owner/children relationships in YGNodeFree
+  explicit YGNode(const YGConfigRef newConfig) : config_(newConfig){};
+  YGNode(const YGNode& node) = default;
   YGNode& operator=(const YGNode& node);
 
   // Getters
diff --git a/ReactCommon/yoga/yoga/YGStyle.cpp b/ReactCommon/yoga/yoga/YGStyle.cpp
index 738d36fb0fa1..06d0f2a4b79c 100644
--- a/ReactCommon/yoga/yoga/YGStyle.cpp
+++ b/ReactCommon/yoga/yoga/YGStyle.cpp
@@ -98,9 +98,3 @@ bool YGStyle::operator==(const YGStyle& style) {
 
   return areNonFloatValuesEqual;
 }
-
-bool YGStyle::operator!=(YGStyle style) {
-  return !(*this == style);
-}
-
-YGStyle::~YGStyle() {}
diff --git a/ReactCommon/yoga/yoga/YGStyle.h b/ReactCommon/yoga/yoga/YGStyle.h
index b18ac0a6eb87..3f4bbd34726a 100644
--- a/ReactCommon/yoga/yoga/YGStyle.h
+++ b/ReactCommon/yoga/yoga/YGStyle.h
@@ -32,12 +32,14 @@ struct YGStyle {
   std::array<YGValue, 2> dimensions;
   std::array<YGValue, 2> minDimensions;
   std::array<YGValue, 2> maxDimensions;
+  // Yoga specific properties, not compatible with flexbox specification
   YGFloatOptional aspectRatio;
 
   YGStyle();
-  // Yoga specific properties, not compatible with flexbox specification
   bool operator==(const YGStyle& style);
 
-  bool operator!=(YGStyle style);
-  ~YGStyle();
+  bool operator!=(YGStyle style) {
+    return !(*this == style);
+  }
+  ~YGStyle() = default;
 };

From ce4c2de3a315028fa72a8ed8fb425111856b7b81 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 19 Jul 2018 09:57:04 -0700
Subject: [PATCH 1092/1109] Run lint on `Yoga.cpp`/`Yoga.h`

Summary:
@public

auto-fixes formatting for `Yoga.cpp`/`Yoga.h`.
Submitted separately to keep other diffs cleaner.

Reviewed By: astreet

Differential Revision: D8868179

fbshipit-source-id: d0667f8bb909bb5ada1263aac6e22b0a8f8875ad
---
 ReactCommon/yoga/yoga/Yoga.cpp | 1136 +++++++++++++++++++-------------
 ReactCommon/yoga/yoga/Yoga.h   |  233 ++++---
 2 files changed, 794 insertions(+), 575 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index fe419207307c..c9404dec4da6 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -29,17 +29,19 @@ __forceinline const float fmaxf(const float a, const float b) {
 #endif
 
 #ifdef ANDROID
-static int YGAndroidLog(const YGConfigRef config,
-                        const YGNodeRef node,
-                        YGLogLevel level,
-                        const char *format,
-                        va_list args);
+static int YGAndroidLog(
+    const YGConfigRef config,
+    const YGNodeRef node,
+    YGLogLevel level,
+    const char* format,
+    va_list args);
 #else
-static int YGDefaultLog(const YGConfigRef config,
-                        const YGNodeRef node,
-                        YGLogLevel level,
-                        const char *format,
-                        va_list args);
+static int YGDefaultLog(
+    const YGConfigRef config,
+    const YGNodeRef node,
+    YGLogLevel level,
+    const char* format,
+    va_list args);
 #endif
 
 const YGValue YGValueZero = {0, YGUnitPoint};
@@ -48,11 +50,12 @@ const YGValue YGValueAuto = {YGUndefined, YGUnitAuto};
 
 #ifdef ANDROID
 #include <android/log.h>
-static int YGAndroidLog(const YGConfigRef config,
-                        const YGNodeRef node,
-                        YGLogLevel level,
-                        const char *format,
-                        va_list args) {
+static int YGAndroidLog(
+    const YGConfigRef config,
+    const YGNodeRef node,
+    YGLogLevel level,
+    const char* format,
+    va_list args) {
   int androidLevel = YGLogLevelDebug;
   switch (level) {
     case YGLogLevelFatal:
@@ -80,11 +83,12 @@ static int YGAndroidLog(const YGConfigRef config,
 #else
 #define YG_UNUSED(x) (void)(x);
 
-static int YGDefaultLog(const YGConfigRef config,
-                        const YGNodeRef node,
-                        YGLogLevel level,
-                        const char *format,
-                        va_list args) {
+static int YGDefaultLog(
+    const YGConfigRef config,
+    const YGNodeRef node,
+    YGLogLevel level,
+    const char* format,
+    va_list args) {
   YG_UNUSED(config);
   YG_UNUSED(node);
   switch (level) {
@@ -120,7 +124,8 @@ const YGValue* YGComputedEdgeValue(
     return &edges[YGEdgeVertical];
   }
 
-  if ((edge == YGEdgeLeft || edge == YGEdgeRight || edge == YGEdgeStart || edge == YGEdgeEnd) &&
+  if ((edge == YGEdgeLeft || edge == YGEdgeRight || edge == YGEdgeStart ||
+       edge == YGEdgeEnd) &&
       edges[YGEdgeHorizontal].unit != YGUnitUndefined) {
     return &edges[YGEdgeHorizontal];
   }
@@ -312,9 +317,10 @@ void YGNodeFreeRecursive(const YGNodeRef root) {
 }
 
 void YGNodeReset(const YGNodeRef node) {
-  YGAssertWithNode(node,
-                   YGNodeGetChildCount(node) == 0,
-                   "Cannot reset a node which still has children attached");
+  YGAssertWithNode(
+      node,
+      YGNodeGetChildCount(node) == 0,
+      "Cannot reset a node which still has children attached");
   YGAssertWithNode(
       node,
       node->getOwner() == nullptr,
@@ -340,11 +346,11 @@ int32_t YGConfigGetInstanceCount(void) {
 }
 
 YGConfigRef YGConfigNew(void) {
-  #ifdef ANDROID
+#ifdef ANDROID
   const YGConfigRef config = new YGConfig(YGAndroidLog);
-  #else
+#else
   const YGConfigRef config = new YGConfig(YGDefaultLog);
-  #endif
+#endif
   gConfigInstanceCount++;
   return config;
 }
@@ -358,7 +364,10 @@ void YGConfigCopy(const YGConfigRef dest, const YGConfigRef src) {
   memcpy(dest, src, sizeof(YGConfig));
 }
 
-void YGNodeInsertChild(const YGNodeRef node, const YGNodeRef child, const uint32_t index) {
+void YGNodeInsertChild(
+    const YGNodeRef node,
+    const YGNodeRef child,
+    const uint32_t index) {
   YGAssertWithNode(
       node,
       child->getOwner() == nullptr,
@@ -401,8 +410,8 @@ void YGNodeRemoveChild(const YGNodeRef owner, const YGNodeRef excludedChild) {
   }
   const YGNodeRef firstChild = YGNodeGetChild(owner, 0);
   if (firstChild->getOwner() == owner) {
-    // If the first child has this node as its owner, we assume that it is already unique.
-    // We can now try to delete a child in this list.
+    // If the first child has this node as its owner, we assume that it is
+    // already unique. We can now try to delete a child in this list.
     if (owner->removeChild(excludedChild)) {
       excludedChild->setLayout(
           YGNode().getLayout()); // layout is no longer valid
@@ -411,18 +420,18 @@ void YGNodeRemoveChild(const YGNodeRef owner, const YGNodeRef excludedChild) {
     }
     return;
   }
-  // Otherwise we have to clone the node list except for the child we're trying to delete.
-  // We don't want to simply clone all children, because then the host will need to free
-  // the clone of the child that was just deleted.
+  // Otherwise we have to clone the node list except for the child we're trying
+  // to delete. We don't want to simply clone all children, because then the
+  // host will need to free the clone of the child that was just deleted.
   const YGCloneNodeFunc cloneNodeCallback =
       owner->getConfig()->cloneNodeCallback;
   uint32_t nextInsertIndex = 0;
   for (uint32_t i = 0; i < childCount; i++) {
     const YGNodeRef oldChild = owner->getChild(i);
     if (excludedChild == oldChild) {
-      // Ignore the deleted child. Don't reset its layout or owner since it is still valid
-      // in the other owner. However, since this owner has now changed, we need to mark it
-      // as dirty.
+      // Ignore the deleted child. Don't reset its layout or owner since it is
+      // still valid in the other owner. However, since this owner has now
+      // changed, we need to mark it as dirty.
       owner->markDirtyAndPropogate();
       continue;
     }
@@ -452,7 +461,8 @@ void YGNodeRemoveAllChildren(const YGNodeRef owner) {
   }
   const YGNodeRef firstChild = YGNodeGetChild(owner, 0);
   if (firstChild->getOwner() == owner) {
-    // If the first child has this node as its owner, we assume that this child set is unique.
+    // If the first child has this node as its owner, we assume that this child
+    // set is unique.
     for (uint32_t i = 0; i < childCount; i++) {
       const YGNodeRef oldChild = YGNodeGetChild(owner, i);
       oldChild->setLayout(YGNode().getLayout()); // layout is no longer valid
@@ -462,13 +472,15 @@ void YGNodeRemoveAllChildren(const YGNodeRef owner) {
     owner->markDirtyAndPropogate();
     return;
   }
-  // Otherwise, we are not the owner of the child set. We don't have to do anything to clear it.
+  // Otherwise, we are not the owner of the child set. We don't have to do
+  // anything to clear it.
   owner->setChildren(YGVector());
   owner->markDirtyAndPropogate();
 }
 
-static void YGNodeSetChildrenInternal(YGNodeRef const owner, const std::vector<YGNodeRef> &children)
-{
+static void YGNodeSetChildrenInternal(
+    YGNodeRef const owner,
+    const std::vector<YGNodeRef>& children) {
   if (!owner) {
     return;
   }
@@ -484,8 +496,10 @@ static void YGNodeSetChildrenInternal(YGNodeRef const owner, const std::vector<Y
   } else {
     if (YGNodeGetChildCount(owner) > 0) {
       for (YGNodeRef const oldChild : owner->getChildren()) {
-        // Our new children may have nodes in common with the old children. We don't reset these common nodes.
-        if (std::find(children.begin(), children.end(), oldChild) == children.end()) {
+        // Our new children may have nodes in common with the old children. We
+        // don't reset these common nodes.
+        if (std::find(children.begin(), children.end(), oldChild) ==
+            children.end()) {
           oldChild->setLayout(YGLayout());
           oldChild->setOwner(nullptr);
         }
@@ -499,13 +513,17 @@ static void YGNodeSetChildrenInternal(YGNodeRef const owner, const std::vector<Y
   }
 }
 
-void YGNodeSetChildren(YGNodeRef const owner, const YGNodeRef c[], const uint32_t count) {
+void YGNodeSetChildren(
+    YGNodeRef const owner,
+    const YGNodeRef c[],
+    const uint32_t count) {
   const YGVector children = {c, c + count};
   YGNodeSetChildrenInternal(owner, children);
 }
 
-void YGNodeSetChildren(YGNodeRef const owner, const std::vector<YGNodeRef> &children)
-{
+void YGNodeSetChildren(
+    YGNodeRef const owner,
+    const std::vector<YGNodeRef>& children) {
   YGNodeSetChildrenInternal(owner, children);
 }
 
@@ -766,12 +784,24 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
 // YG_NODE_PROPERTY_IMPL(YGNodeType, NodeType, nodeType, nodeType);
 
 YG_NODE_STYLE_PROPERTY_IMPL(YGDirection, Direction, direction, direction);
-YG_NODE_STYLE_PROPERTY_IMPL(YGFlexDirection, FlexDirection, flexDirection, flexDirection);
-YG_NODE_STYLE_PROPERTY_IMPL(YGJustify, JustifyContent, justifyContent, justifyContent);
+YG_NODE_STYLE_PROPERTY_IMPL(
+    YGFlexDirection,
+    FlexDirection,
+    flexDirection,
+    flexDirection);
+YG_NODE_STYLE_PROPERTY_IMPL(
+    YGJustify,
+    JustifyContent,
+    justifyContent,
+    justifyContent);
 YG_NODE_STYLE_PROPERTY_IMPL(YGAlign, AlignContent, alignContent, alignContent);
 YG_NODE_STYLE_PROPERTY_IMPL(YGAlign, AlignItems, alignItems, alignItems);
 YG_NODE_STYLE_PROPERTY_IMPL(YGAlign, AlignSelf, alignSelf, alignSelf);
-YG_NODE_STYLE_PROPERTY_IMPL(YGPositionType, PositionType, positionType, positionType);
+YG_NODE_STYLE_PROPERTY_IMPL(
+    YGPositionType,
+    PositionType,
+    positionType,
+    positionType);
 YG_NODE_STYLE_PROPERTY_IMPL(YGWrap, FlexWrap, flexWrap, flexWrap);
 YG_NODE_STYLE_PROPERTY_IMPL(YGOverflow, Overflow, overflow, overflow);
 YG_NODE_STYLE_PROPERTY_IMPL(YGDisplay, Display, display, display);
@@ -925,12 +955,36 @@ void YGNodeStyleSetAspectRatio(const YGNodeRef node, const float aspectRatio) {
   }
 }
 
-YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Width, width, dimensions[YGDimensionWidth]);
-YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(YGValue, Height, height, dimensions[YGDimensionHeight]);
-YG_NODE_STYLE_PROPERTY_UNIT_IMPL(YGValue, MinWidth, minWidth, minDimensions[YGDimensionWidth]);
-YG_NODE_STYLE_PROPERTY_UNIT_IMPL(YGValue, MinHeight, minHeight, minDimensions[YGDimensionHeight]);
-YG_NODE_STYLE_PROPERTY_UNIT_IMPL(YGValue, MaxWidth, maxWidth, maxDimensions[YGDimensionWidth]);
-YG_NODE_STYLE_PROPERTY_UNIT_IMPL(YGValue, MaxHeight, maxHeight, maxDimensions[YGDimensionHeight]);
+YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(
+    YGValue,
+    Width,
+    width,
+    dimensions[YGDimensionWidth]);
+YG_NODE_STYLE_PROPERTY_UNIT_AUTO_IMPL(
+    YGValue,
+    Height,
+    height,
+    dimensions[YGDimensionHeight]);
+YG_NODE_STYLE_PROPERTY_UNIT_IMPL(
+    YGValue,
+    MinWidth,
+    minWidth,
+    minDimensions[YGDimensionWidth]);
+YG_NODE_STYLE_PROPERTY_UNIT_IMPL(
+    YGValue,
+    MinHeight,
+    minHeight,
+    minDimensions[YGDimensionHeight]);
+YG_NODE_STYLE_PROPERTY_UNIT_IMPL(
+    YGValue,
+    MaxWidth,
+    maxWidth,
+    maxDimensions[YGDimensionWidth]);
+YG_NODE_STYLE_PROPERTY_UNIT_IMPL(
+    YGValue,
+    MaxHeight,
+    maxHeight,
+    maxDimensions[YGDimensionHeight]);
 YG_NODE_LAYOUT_PROPERTY_IMPL(float, Left, position[YGEdgeLeft]);
 YG_NODE_LAYOUT_PROPERTY_IMPL(float, Top, position[YGEdgeTop]);
 YG_NODE_LAYOUT_PROPERTY_IMPL(float, Right, position[YGEdgeRight]);
@@ -950,20 +1004,22 @@ bool YGNodeLayoutGetDidLegacyStretchFlagAffectLayout(const YGNodeRef node) {
 
 uint32_t gCurrentGenerationCount = 0;
 
-bool YGLayoutNodeInternal(const YGNodeRef node,
-                          const float availableWidth,
-                          const float availableHeight,
-                          const YGDirection ownerDirection,
-                          const YGMeasureMode widthMeasureMode,
-                          const YGMeasureMode heightMeasureMode,
-                          const float ownerWidth,
-                          const float ownerHeight,
-                          const bool performLayout,
-                          const char *reason,
-                          const YGConfigRef config);
-
-static void YGNodePrintInternal(const YGNodeRef node,
-                                const YGPrintOptions options) {
+bool YGLayoutNodeInternal(
+    const YGNodeRef node,
+    const float availableWidth,
+    const float availableHeight,
+    const YGDirection ownerDirection,
+    const YGMeasureMode widthMeasureMode,
+    const YGMeasureMode heightMeasureMode,
+    const float ownerWidth,
+    const float ownerHeight,
+    const bool performLayout,
+    const char* reason,
+    const YGConfigRef config);
+
+static void YGNodePrintInternal(
+    const YGNodeRef node,
+    const YGPrintOptions options) {
   std::string str;
   facebook::yoga::YGNodeToString(&str, node, options, 0);
   YGLog(node, YGLogLevelDebug, str.c_str());
@@ -988,15 +1044,18 @@ static const std::array<YGEdge, 4> pos = {{
 static const std::array<YGDimension, 4> dim = {
     {YGDimensionHeight, YGDimensionHeight, YGDimensionWidth, YGDimensionWidth}};
 
-static inline float YGNodePaddingAndBorderForAxis(const YGNodeRef node,
-                                                  const YGFlexDirection axis,
-                                                  const float widthSize) {
+static inline float YGNodePaddingAndBorderForAxis(
+    const YGNodeRef node,
+    const YGFlexDirection axis,
+    const float widthSize) {
   return YGUnwrapFloatOptional(
       node->getLeadingPaddingAndBorder(axis, widthSize) +
       node->getTrailingPaddingAndBorder(axis, widthSize));
 }
 
-static inline YGAlign YGNodeAlignItem(const YGNodeRef node, const YGNodeRef child) {
+static inline YGAlign YGNodeAlignItem(
+    const YGNodeRef node,
+    const YGNodeRef child) {
   const YGAlign align = child->getStyle().alignSelf == YGAlignAuto
       ? node->getStyle().alignItems
       : child->getStyle().alignSelf;
@@ -1013,9 +1072,10 @@ static float YGBaseline(const YGNodeRef node) {
         node,
         node->getLayout().measuredDimensions[YGDimensionWidth],
         node->getLayout().measuredDimensions[YGDimensionHeight]);
-    YGAssertWithNode(node,
-                     !YGFloatIsUndefined(baseline),
-                     "Expect custom baseline function to not return NaN");
+    YGAssertWithNode(
+        node,
+        !YGFloatIsUndefined(baseline),
+        "Expect custom baseline function to not return NaN");
     return baseline;
   }
 
@@ -1066,18 +1126,20 @@ static bool YGIsBaselineLayout(const YGNodeRef node) {
   return false;
 }
 
-static inline float YGNodeDimWithMargin(const YGNodeRef node,
-                                        const YGFlexDirection axis,
-                                        const float widthSize) {
+static inline float YGNodeDimWithMargin(
+    const YGNodeRef node,
+    const YGFlexDirection axis,
+    const float widthSize) {
   return node->getLayout().measuredDimensions[dim[axis]] +
       YGUnwrapFloatOptional(
              node->getLeadingMargin(axis, widthSize) +
              node->getTrailingMargin(axis, widthSize));
 }
 
-static inline bool YGNodeIsStyleDimDefined(const YGNodeRef node,
-                                           const YGFlexDirection axis,
-                                           const float ownerSize) {
+static inline bool YGNodeIsStyleDimDefined(
+    const YGNodeRef node,
+    const YGFlexDirection axis,
+    const float ownerSize) {
   bool isUndefined =
       YGFloatIsUndefined(node->getResolvedDimension(dim[axis]).value);
   return !(
@@ -1091,7 +1153,9 @@ static inline bool YGNodeIsStyleDimDefined(const YGNodeRef node,
         YGFloatIsUndefined(ownerSize))));
 }
 
-static inline bool YGNodeIsLayoutDimDefined(const YGNodeRef node, const YGFlexDirection axis) {
+static inline bool YGNodeIsLayoutDimDefined(
+    const YGNodeRef node,
+    const YGFlexDirection axis) {
   const float value = node->getLayout().measuredDimensions[dim[axis]];
   return !YGFloatIsUndefined(value) && value >= 0.0f;
 }
@@ -1127,23 +1191,24 @@ static YGFloatOptional YGNodeBoundAxisWithinMinAndMax(
   return YGFloatOptional(value);
 }
 
-// Like YGNodeBoundAxisWithinMinAndMax but also ensures that the value doesn't go
-// below the
-// padding and border amount.
-static inline float YGNodeBoundAxis(const YGNodeRef node,
-                                    const YGFlexDirection axis,
-                                    const float value,
-                                    const float axisSize,
-                                    const float widthSize) {
+// Like YGNodeBoundAxisWithinMinAndMax but also ensures that the value doesn't
+// go below the padding and border amount.
+static inline float YGNodeBoundAxis(
+    const YGNodeRef node,
+    const YGFlexDirection axis,
+    const float value,
+    const float axisSize,
+    const float widthSize) {
   return YGFloatMax(
       YGUnwrapFloatOptional(
           YGNodeBoundAxisWithinMinAndMax(node, axis, value, axisSize)),
       YGNodePaddingAndBorderForAxis(node, axis, widthSize));
 }
 
-static void YGNodeSetChildTrailingPosition(const YGNodeRef node,
-                                           const YGNodeRef child,
-                                           const YGFlexDirection axis) {
+static void YGNodeSetChildTrailingPosition(
+    const YGNodeRef node,
+    const YGNodeRef child,
+    const YGFlexDirection axis) {
   const float size = child->getLayout().measuredDimensions[dim[axis]];
   child->setLayoutPosition(
       node->getLayout().measuredDimensions[dim[axis]] - size -
@@ -1151,15 +1216,15 @@ static void YGNodeSetChildTrailingPosition(const YGNodeRef node,
       trailing[axis]);
 }
 
-static void YGConstrainMaxSizeForMode(const YGNodeRef node,
-                                      const enum YGFlexDirection axis,
-                                      const float ownerAxisSize,
-                                      const float ownerWidth,
-                                      YGMeasureMode *mode,
-                                      float *size) {
+static void YGConstrainMaxSizeForMode(
+    const YGNodeRef node,
+    const enum YGFlexDirection axis,
+    const float ownerAxisSize,
+    const float ownerWidth,
+    YGMeasureMode* mode,
+    float* size) {
   const YGFloatOptional maxSize =
-      YGResolveValue(
-          node->getStyle().maxDimensions[dim[axis]], ownerAxisSize) +
+      YGResolveValue(node->getStyle().maxDimensions[dim[axis]], ownerAxisSize) +
       YGFloatOptional(node->getMarginForAxis(axis, ownerWidth));
   switch (*mode) {
     case YGMeasureModeExactly:
@@ -1177,16 +1242,17 @@ static void YGConstrainMaxSizeForMode(const YGNodeRef node,
   }
 }
 
-static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
-                                           const YGNodeRef child,
-                                           const float width,
-                                           const YGMeasureMode widthMode,
-                                           const float height,
-                                           const float ownerWidth,
-                                           const float ownerHeight,
-                                           const YGMeasureMode heightMode,
-                                           const YGDirection direction,
-                                           const YGConfigRef config) {
+static void YGNodeComputeFlexBasisForChild(
+    const YGNodeRef node,
+    const YGNodeRef child,
+    const float width,
+    const YGMeasureMode widthMode,
+    const float height,
+    const float ownerWidth,
+    const float ownerHeight,
+    const YGMeasureMode heightMode,
+    const YGDirection direction,
+    const YGConfigRef config) {
   const YGFlexDirection mainAxis =
       YGResolveFlexDirection(node->getStyle().flexDirection, direction);
   const bool isMainAxisRow = YGFlexDirectionIsRow(mainAxis);
@@ -1200,7 +1266,8 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
 
   const YGFloatOptional resolvedFlexBasis =
       YGResolveValue(child->resolveFlexBasisPtr(), mainAxisownerSize);
-  const bool isRowStyleDimDefined = YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, ownerWidth);
+  const bool isRowStyleDimDefined =
+      YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, ownerWidth);
   const bool isColumnStyleDimDefined =
       YGNodeIsStyleDimDefined(child, YGFlexDirectionColumn, ownerHeight);
 
@@ -1284,7 +1351,8 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
         childHeight = marginColumn +
             (childWidth - marginRow) / child->getStyle().aspectRatio.getValue();
         childHeightMeasureMode = YGMeasureModeExactly;
-      } else if (isMainAxisRow && childHeightMeasureMode == YGMeasureModeExactly) {
+      } else if (
+          isMainAxisRow && childHeightMeasureMode == YGMeasureModeExactly) {
         childWidth = marginRow +
             (childHeight - marginColumn) *
                 child->getStyle().aspectRatio.getValue();
@@ -1296,10 +1364,13 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
     // set the cross
     // axis to be measured exactly with the available inner width
 
-    const bool hasExactWidth = !YGFloatIsUndefined(width) && widthMode == YGMeasureModeExactly;
-    const bool childWidthStretch = YGNodeAlignItem(node, child) == YGAlignStretch &&
-                                   childWidthMeasureMode != YGMeasureModeExactly;
-    if (!isMainAxisRow && !isRowStyleDimDefined && hasExactWidth && childWidthStretch) {
+    const bool hasExactWidth =
+        !YGFloatIsUndefined(width) && widthMode == YGMeasureModeExactly;
+    const bool childWidthStretch =
+        YGNodeAlignItem(node, child) == YGAlignStretch &&
+        childWidthMeasureMode != YGMeasureModeExactly;
+    if (!isMainAxisRow && !isRowStyleDimDefined && hasExactWidth &&
+        childWidthStretch) {
       childWidth = width;
       childWidthMeasureMode = YGMeasureModeExactly;
       if (!child->getStyle().aspectRatio.isUndefined()) {
@@ -1309,10 +1380,13 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
       }
     }
 
-    const bool hasExactHeight = !YGFloatIsUndefined(height) && heightMode == YGMeasureModeExactly;
-    const bool childHeightStretch = YGNodeAlignItem(node, child) == YGAlignStretch &&
-                                    childHeightMeasureMode != YGMeasureModeExactly;
-    if (isMainAxisRow && !isColumnStyleDimDefined && hasExactHeight && childHeightStretch) {
+    const bool hasExactHeight =
+        !YGFloatIsUndefined(height) && heightMode == YGMeasureModeExactly;
+    const bool childHeightStretch =
+        YGNodeAlignItem(node, child) == YGAlignStretch &&
+        childHeightMeasureMode != YGMeasureModeExactly;
+    if (isMainAxisRow && !isColumnStyleDimDefined && hasExactHeight &&
+        childHeightStretch) {
       childHeight = height;
       childHeightMeasureMode = YGMeasureModeExactly;
 
@@ -1324,26 +1398,33 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
     }
 
     YGConstrainMaxSizeForMode(
-        child, YGFlexDirectionRow, ownerWidth, ownerWidth, &childWidthMeasureMode, &childWidth);
-    YGConstrainMaxSizeForMode(child,
-                              YGFlexDirectionColumn,
-                              ownerHeight,
-                              ownerWidth,
-                              &childHeightMeasureMode,
-                              &childHeight);
+        child,
+        YGFlexDirectionRow,
+        ownerWidth,
+        ownerWidth,
+        &childWidthMeasureMode,
+        &childWidth);
+    YGConstrainMaxSizeForMode(
+        child,
+        YGFlexDirectionColumn,
+        ownerHeight,
+        ownerWidth,
+        &childHeightMeasureMode,
+        &childHeight);
 
     // Measure the child
-    YGLayoutNodeInternal(child,
-                         childWidth,
-                         childHeight,
-                         direction,
-                         childWidthMeasureMode,
-                         childHeightMeasureMode,
-                         ownerWidth,
-                         ownerHeight,
-                         false,
-                         "measure",
-                         config);
+    YGLayoutNodeInternal(
+        child,
+        childWidth,
+        childHeight,
+        direction,
+        childWidthMeasureMode,
+        childHeightMeasureMode,
+        ownerWidth,
+        ownerHeight,
+        false,
+        "measure",
+        config);
 
     child->setLayoutComputedFlexBasis(YGFloatOptional(YGFloatMax(
         child->getLayout().measuredDimensions[dim[mainAxis]],
@@ -1352,13 +1433,14 @@ static void YGNodeComputeFlexBasisForChild(const YGNodeRef node,
   child->setLayoutComputedFlexBasisGeneration(gCurrentGenerationCount);
 }
 
-static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
-                                      const YGNodeRef child,
-                                      const float width,
-                                      const YGMeasureMode widthMode,
-                                      const float height,
-                                      const YGDirection direction,
-                                      const YGConfigRef config) {
+static void YGNodeAbsoluteLayoutChild(
+    const YGNodeRef node,
+    const YGNodeRef child,
+    const float width,
+    const YGMeasureMode widthMode,
+    const float height,
+    const YGDirection direction,
+    const YGConfigRef config) {
   const YGFlexDirection mainAxis =
       YGResolveFlexDirection(node->getStyle().flexDirection, direction);
   const YGFlexDirection crossAxis = YGFlexDirectionCross(mainAxis, direction);
@@ -1375,8 +1457,8 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
       child->getMarginForAxis(YGFlexDirectionColumn, width));
 
   if (YGNodeIsStyleDimDefined(child, YGFlexDirectionRow, width)) {
-    childWidth =
-        YGUnwrapFloatOptional(YGResolveValue(child->getResolvedDimension(YGDimensionWidth), width)) +
+    childWidth = YGUnwrapFloatOptional(YGResolveValue(
+                     child->getResolvedDimension(YGDimensionWidth), width)) +
         marginRow;
   } else {
     // If the child doesn't have a specified width, compute the width based
@@ -1390,13 +1472,14 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
           YGUnwrapFloatOptional(
                        child->getLeadingPosition(YGFlexDirectionRow, width) +
                        child->getTrailingPosition(YGFlexDirectionRow, width));
-      childWidth = YGNodeBoundAxis(child, YGFlexDirectionRow, childWidth, width, width);
+      childWidth =
+          YGNodeBoundAxis(child, YGFlexDirectionRow, childWidth, width, width);
     }
   }
 
   if (YGNodeIsStyleDimDefined(child, YGFlexDirectionColumn, height)) {
-    childHeight =
-        YGUnwrapFloatOptional(YGResolveValue(child->getResolvedDimension(YGDimensionHeight), height)) +
+    childHeight = YGUnwrapFloatOptional(YGResolveValue(
+                      child->getResolvedDimension(YGDimensionHeight), height)) +
         marginColumn;
   } else {
     // If the child doesn't have a specified height, compute the height
@@ -1411,12 +1494,14 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
           YGUnwrapFloatOptional(
               child->getLeadingPosition(YGFlexDirectionColumn, height) +
               child->getTrailingPosition(YGFlexDirectionColumn, height));
-      childHeight = YGNodeBoundAxis(child, YGFlexDirectionColumn, childHeight, height, width);
+      childHeight = YGNodeBoundAxis(
+          child, YGFlexDirectionColumn, childHeight, height, width);
     }
   }
 
-  // Exactly one dimension needs to be defined for us to be able to do aspect ratio
-  // calculation. One dimension being the anchor and the other being flexible.
+  // Exactly one dimension needs to be defined for us to be able to do aspect
+  // ratio calculation. One dimension being the anchor and the other being
+  // flexible.
   if (YGFloatIsUndefined(childWidth) ^ YGFloatIsUndefined(childHeight)) {
     if (!child->getStyle().aspectRatio.isUndefined()) {
       if (YGFloatIsUndefined(childWidth)) {
@@ -1432,14 +1517,17 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
 
   // If we're still missing one or the other dimension, measure the content.
   if (YGFloatIsUndefined(childWidth) || YGFloatIsUndefined(childHeight)) {
-    childWidthMeasureMode =
-        YGFloatIsUndefined(childWidth) ? YGMeasureModeUndefined : YGMeasureModeExactly;
-    childHeightMeasureMode =
-        YGFloatIsUndefined(childHeight) ? YGMeasureModeUndefined : YGMeasureModeExactly;
-
-    // If the size of the owner is defined then try to constrain the absolute child to that size
-    // as well. This allows text within the absolute child to wrap to the size of its owner.
-    // This is the same behavior as many browsers implement.
+    childWidthMeasureMode = YGFloatIsUndefined(childWidth)
+        ? YGMeasureModeUndefined
+        : YGMeasureModeExactly;
+    childHeightMeasureMode = YGFloatIsUndefined(childHeight)
+        ? YGMeasureModeUndefined
+        : YGMeasureModeExactly;
+
+    // If the size of the owner is defined then try to constrain the absolute
+    // child to that size as well. This allows text within the absolute child to
+    // wrap to the size of its owner. This is the same behavior as many browsers
+    // implement.
     if (!isMainAxisRow && YGFloatIsUndefined(childWidth) &&
         widthMode != YGMeasureModeUndefined && !YGFloatIsUndefined(width) &&
         width > 0) {
@@ -1447,17 +1535,18 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
       childWidthMeasureMode = YGMeasureModeAtMost;
     }
 
-    YGLayoutNodeInternal(child,
-                         childWidth,
-                         childHeight,
-                         direction,
-                         childWidthMeasureMode,
-                         childHeightMeasureMode,
-                         childWidth,
-                         childHeight,
-                         false,
-                         "abs-measure",
-                         config);
+    YGLayoutNodeInternal(
+        child,
+        childWidth,
+        childHeight,
+        direction,
+        childWidthMeasureMode,
+        childHeightMeasureMode,
+        childWidth,
+        childHeight,
+        false,
+        "abs-measure",
+        config);
     childWidth = child->getLayout().measuredDimensions[YGDimensionWidth] +
         YGUnwrapFloatOptional(
                      child->getMarginForAxis(YGFlexDirectionRow, width));
@@ -1466,17 +1555,18 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
                       child->getMarginForAxis(YGFlexDirectionColumn, width));
   }
 
-  YGLayoutNodeInternal(child,
-                       childWidth,
-                       childHeight,
-                       direction,
-                       YGMeasureModeExactly,
-                       YGMeasureModeExactly,
-                       childWidth,
-                       childHeight,
-                       true,
-                       "abs-layout",
-                       config);
+  YGLayoutNodeInternal(
+      child,
+      childWidth,
+      childHeight,
+      direction,
+      YGMeasureModeExactly,
+      YGMeasureModeExactly,
+      childWidth,
+      childHeight,
+      true,
+      "abs-layout",
+      config);
 
   if (child->isTrailingPosDefined(mainAxis) &&
       !child->isLeadingPositionDefined(mainAxis)) {
@@ -1535,13 +1625,14 @@ static void YGNodeAbsoluteLayoutChild(const YGNodeRef node,
   }
 }
 
-static void YGNodeWithMeasureFuncSetMeasuredDimensions(const YGNodeRef node,
-                                                       const float availableWidth,
-                                                       const float availableHeight,
-                                                       const YGMeasureMode widthMeasureMode,
-                                                       const YGMeasureMode heightMeasureMode,
-                                                       const float ownerWidth,
-                                                       const float ownerHeight) {
+static void YGNodeWithMeasureFuncSetMeasuredDimensions(
+    const YGNodeRef node,
+    const float availableWidth,
+    const float availableHeight,
+    const YGMeasureMode widthMeasureMode,
+    const YGMeasureMode heightMeasureMode,
+    const float ownerWidth,
+    const float ownerHeight) {
   YGAssertWithNode(
       node,
       node->getMeasure() != nullptr,
@@ -1549,8 +1640,8 @@ static void YGNodeWithMeasureFuncSetMeasuredDimensions(const YGNodeRef node,
 
   const float paddingAndBorderAxisRow =
       YGNodePaddingAndBorderForAxis(node, YGFlexDirectionRow, availableWidth);
-  const float paddingAndBorderAxisColumn =
-      YGNodePaddingAndBorderForAxis(node, YGFlexDirectionColumn, availableWidth);
+  const float paddingAndBorderAxisColumn = YGNodePaddingAndBorderForAxis(
+      node, YGFlexDirectionColumn, availableWidth);
   const float marginAxisRow = YGUnwrapFloatOptional(
       node->getMarginForAxis(YGFlexDirectionRow, availableWidth));
   const float marginAxisColumn = YGUnwrapFloatOptional(
@@ -1617,13 +1708,14 @@ static void YGNodeWithMeasureFuncSetMeasuredDimensions(const YGNodeRef node,
 
 // For nodes with no children, use the available values if they were provided,
 // or the minimum size as indicated by the padding and border sizes.
-static void YGNodeEmptyContainerSetMeasuredDimensions(const YGNodeRef node,
-                                                      const float availableWidth,
-                                                      const float availableHeight,
-                                                      const YGMeasureMode widthMeasureMode,
-                                                      const YGMeasureMode heightMeasureMode,
-                                                      const float ownerWidth,
-                                                      const float ownerHeight) {
+static void YGNodeEmptyContainerSetMeasuredDimensions(
+    const YGNodeRef node,
+    const float availableWidth,
+    const float availableHeight,
+    const YGMeasureMode widthMeasureMode,
+    const YGMeasureMode heightMeasureMode,
+    const float ownerWidth,
+    const float ownerHeight) {
   const float paddingAndBorderAxisRow =
       YGNodePaddingAndBorderForAxis(node, YGFlexDirectionRow, ownerWidth);
   const float paddingAndBorderAxisColumn =
@@ -1658,13 +1750,14 @@ static void YGNodeEmptyContainerSetMeasuredDimensions(const YGNodeRef node,
       YGDimensionHeight);
 }
 
-static bool YGNodeFixedSizeSetMeasuredDimensions(const YGNodeRef node,
-                                                 const float availableWidth,
-                                                 const float availableHeight,
-                                                 const YGMeasureMode widthMeasureMode,
-                                                 const YGMeasureMode heightMeasureMode,
-                                                 const float ownerWidth,
-                                                 const float ownerHeight) {
+static bool YGNodeFixedSizeSetMeasuredDimensions(
+    const YGNodeRef node,
+    const float availableWidth,
+    const float availableHeight,
+    const YGMeasureMode widthMeasureMode,
+    const YGMeasureMode heightMeasureMode,
+    const float ownerWidth,
+    const float ownerHeight) {
   if ((!YGFloatIsUndefined(availableWidth) &&
        widthMeasureMode == YGMeasureModeAtMost && availableWidth <= 0.0f) ||
       (!YGFloatIsUndefined(availableHeight) &&
@@ -1739,12 +1832,14 @@ static float YGNodeCalculateAvailableInnerDim(
   if (!YGFloatIsUndefined(availableInnerDim)) {
     // We want to make sure our available height does not violate min and max
     // constraints
-    const YGFloatOptional minDimensionOptional = YGResolveValue(node->getStyle().minDimensions[dimension], ownerDim);
+    const YGFloatOptional minDimensionOptional =
+        YGResolveValue(node->getStyle().minDimensions[dimension], ownerDim);
     const float minInnerDim = minDimensionOptional.isUndefined()
         ? 0.0f
         : minDimensionOptional.getValue() - paddingAndBorder;
 
-    const YGFloatOptional maxDimensionOptional = YGResolveValue(node->getStyle().maxDimensions[dimension], ownerDim) ;
+    const YGFloatOptional maxDimensionOptional =
+        YGResolveValue(node->getStyle().maxDimensions[dimension], ownerDim);
 
     const float maxInnerDim = maxDimensionOptional.isUndefined()
         ? FLT_MAX
@@ -2523,37 +2618,42 @@ static void YGJustifyMainAxis(
 //      - YGMeasureModeExactly: fill available
 //      - YGMeasureModeAtMost: fit content
 //
-//    When calling YGNodelayoutImpl and YGLayoutNodeInternal, if the caller passes
-//    an available size of
-//    undefined then it must also pass a measure mode of YGMeasureModeUndefined
-//    in that dimension.
+//    When calling YGNodelayoutImpl and YGLayoutNodeInternal, if the caller
+//    passes an available size of undefined then it must also pass a measure
+//    mode of YGMeasureModeUndefined in that dimension.
 //
-static void YGNodelayoutImpl(const YGNodeRef node,
-                             const float availableWidth,
-                             const float availableHeight,
-                             const YGDirection ownerDirection,
-                             const YGMeasureMode widthMeasureMode,
-                             const YGMeasureMode heightMeasureMode,
-                             const float ownerWidth,
-                             const float ownerHeight,
-                             const bool performLayout,
-                             const YGConfigRef config) {
-  YGAssertWithNode(node,
-                   YGFloatIsUndefined(availableWidth) ? widthMeasureMode == YGMeasureModeUndefined
-                                                      : true,
-                   "availableWidth is indefinite so widthMeasureMode must be "
-                   "YGMeasureModeUndefined");
-  YGAssertWithNode(node,
-                   YGFloatIsUndefined(availableHeight) ? heightMeasureMode == YGMeasureModeUndefined
-                                                       : true,
-                   "availableHeight is indefinite so heightMeasureMode must be "
-                   "YGMeasureModeUndefined");
+static void YGNodelayoutImpl(
+    const YGNodeRef node,
+    const float availableWidth,
+    const float availableHeight,
+    const YGDirection ownerDirection,
+    const YGMeasureMode widthMeasureMode,
+    const YGMeasureMode heightMeasureMode,
+    const float ownerWidth,
+    const float ownerHeight,
+    const bool performLayout,
+    const YGConfigRef config) {
+  YGAssertWithNode(
+      node,
+      YGFloatIsUndefined(availableWidth)
+          ? widthMeasureMode == YGMeasureModeUndefined
+          : true,
+      "availableWidth is indefinite so widthMeasureMode must be "
+      "YGMeasureModeUndefined");
+  YGAssertWithNode(
+      node,
+      YGFloatIsUndefined(availableHeight)
+          ? heightMeasureMode == YGMeasureModeUndefined
+          : true,
+      "availableHeight is indefinite so heightMeasureMode must be "
+      "YGMeasureModeUndefined");
 
   // Set the resolved resolution in the node's layout.
   const YGDirection direction = node->resolveDirection(ownerDirection);
   node->setLayoutDirection(direction);
 
-  const YGFlexDirection flexRowDirection = YGResolveFlexDirection(YGFlexDirectionRow, direction);
+  const YGFlexDirection flexRowDirection =
+      YGResolveFlexDirection(YGFlexDirectionRow, direction);
   const YGFlexDirection flexColumnDirection =
       YGResolveFlexDirection(YGFlexDirectionColumn, direction);
 
@@ -2598,41 +2698,46 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       YGEdgeBottom);
 
   if (node->getMeasure() != nullptr) {
-    YGNodeWithMeasureFuncSetMeasuredDimensions(node,
-                                               availableWidth,
-                                               availableHeight,
-                                               widthMeasureMode,
-                                               heightMeasureMode,
-                                               ownerWidth,
-                                               ownerHeight);
+    YGNodeWithMeasureFuncSetMeasuredDimensions(
+        node,
+        availableWidth,
+        availableHeight,
+        widthMeasureMode,
+        heightMeasureMode,
+        ownerWidth,
+        ownerHeight);
     return;
   }
 
   const uint32_t childCount = YGNodeGetChildCount(node);
   if (childCount == 0) {
-    YGNodeEmptyContainerSetMeasuredDimensions(node,
-                                              availableWidth,
-                                              availableHeight,
-                                              widthMeasureMode,
-                                              heightMeasureMode,
-                                              ownerWidth,
-                                              ownerHeight);
+    YGNodeEmptyContainerSetMeasuredDimensions(
+        node,
+        availableWidth,
+        availableHeight,
+        widthMeasureMode,
+        heightMeasureMode,
+        ownerWidth,
+        ownerHeight);
     return;
   }
 
-  // If we're not being asked to perform a full layout we can skip the algorithm if we already know
-  // the size
-  if (!performLayout && YGNodeFixedSizeSetMeasuredDimensions(node,
-                                                             availableWidth,
-                                                             availableHeight,
-                                                             widthMeasureMode,
-                                                             heightMeasureMode,
-                                                             ownerWidth,
-                                                             ownerHeight)) {
+  // If we're not being asked to perform a full layout we can skip the algorithm
+  // if we already know the size
+  if (!performLayout &&
+      YGNodeFixedSizeSetMeasuredDimensions(
+          node,
+          availableWidth,
+          availableHeight,
+          widthMeasureMode,
+          heightMeasureMode,
+          ownerWidth,
+          ownerHeight)) {
     return;
   }
 
-  // At this point we know we're going to perform work. Ensure that each child has a mutable copy.
+  // At this point we know we're going to perform work. Ensure that each child
+  // has a mutable copy.
   node->cloneChildrenIfNeeded();
   // Reset layout flags, as they could have changed.
   node->setLayoutHadOverflow(false);
@@ -2649,12 +2754,15 @@ static void YGNodelayoutImpl(const YGNodeRef node,
 
   const float leadingPaddingAndBorderCross = YGUnwrapFloatOptional(
       node->getLeadingPaddingAndBorder(crossAxis, ownerWidth));
-  const float paddingAndBorderAxisMain = YGNodePaddingAndBorderForAxis(node, mainAxis, ownerWidth);
+  const float paddingAndBorderAxisMain =
+      YGNodePaddingAndBorderForAxis(node, mainAxis, ownerWidth);
   const float paddingAndBorderAxisCross =
       YGNodePaddingAndBorderForAxis(node, crossAxis, ownerWidth);
 
-  YGMeasureMode measureModeMainDim = isMainAxisRow ? widthMeasureMode : heightMeasureMode;
-  YGMeasureMode measureModeCrossDim = isMainAxisRow ? heightMeasureMode : widthMeasureMode;
+  YGMeasureMode measureModeMainDim =
+      isMainAxisRow ? widthMeasureMode : heightMeasureMode;
+  YGMeasureMode measureModeCrossDim =
+      isMainAxisRow ? heightMeasureMode : widthMeasureMode;
 
   const float paddingAndBorderAxisRow =
       isMainAxisRow ? paddingAndBorderAxisMain : paddingAndBorderAxisCross;
@@ -2667,13 +2775,16 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
 
   const float minInnerWidth =
-      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionWidth], ownerWidth)) -
+      YGUnwrapFloatOptional(YGResolveValue(
+          node->getStyle().minDimensions[YGDimensionWidth], ownerWidth)) -
       paddingAndBorderAxisRow;
   const float maxInnerWidth =
-      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionWidth], ownerWidth)) -
+      YGUnwrapFloatOptional(YGResolveValue(
+          node->getStyle().maxDimensions[YGDimensionWidth], ownerWidth)) -
       paddingAndBorderAxisRow;
   const float minInnerHeight =
-      YGUnwrapFloatOptional(YGResolveValue(node->getStyle().minDimensions[YGDimensionHeight], ownerHeight)) -
+      YGUnwrapFloatOptional(YGResolveValue(
+          node->getStyle().minDimensions[YGDimensionHeight], ownerHeight)) -
       paddingAndBorderAxisColumn;
   const float maxInnerHeight =
       YGUnwrapFloatOptional(YGResolveValue(
@@ -2756,7 +2867,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
     // the line length, so there's no more space left to distribute.
 
     bool sizeBasedOnContent = false;
-    // If we don't measure with exact main dimension we want to ensure we don't violate min and max
+    // If we don't measure with exact main dimension we want to ensure we don't
+    // violate min and max
     if (measureModeMainDim != YGMeasureModeExactly) {
       if (!YGFloatIsUndefined(minInnerMainDim) &&
           collectedFlexItemsValues.sizeConsumedOnCurrentLine <
@@ -2792,10 +2904,10 @@ static void YGNodelayoutImpl(const YGNodeRef node,
       collectedFlexItemsValues.remainingFreeSpace = availableInnerMainDim -
           collectedFlexItemsValues.sizeConsumedOnCurrentLine;
     } else if (collectedFlexItemsValues.sizeConsumedOnCurrentLine < 0) {
-      // availableInnerMainDim is indefinite which means the node is being sized based on its
-      // content.
-      // sizeConsumedOnCurrentLine is negative which means the node will allocate 0 points for
-      // its content. Consequently, remainingFreeSpace is 0 - sizeConsumedOnCurrentLine.
+      // availableInnerMainDim is indefinite which means the node is being sized
+      // based on its content. sizeConsumedOnCurrentLine is negative which means
+      // the node will allocate 0 points for its content. Consequently,
+      // remainingFreeSpace is 0 - sizeConsumedOnCurrentLine.
       collectedFlexItemsValues.remainingFreeSpace =
           -collectedFlexItemsValues.sizeConsumedOnCurrentLine;
     }
@@ -2897,7 +3009,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                         crossAxis, availableInnerWidth)),
                 pos[crossAxis]);
           }
-          // If leading position is not defined or calculations result in Nan, default to border + margin
+          // If leading position is not defined or calculations result in Nan,
+          // default to border + margin
           if (!isChildLeadingPosDefined ||
               YGFloatIsUndefined(child->getLayout().position[pos[crossAxis]])) {
             child->setLayoutPosition(
@@ -2923,7 +3036,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
               child->marginTrailingValue(crossAxis).unit != YGUnitAuto) {
             // If the child defines a definite size for its cross axis, there's
             // no need to stretch.
-            if (!YGNodeIsStyleDimDefined(child, crossAxis, availableInnerCrossDim)) {
+            if (!YGNodeIsStyleDimDefined(
+                    child, crossAxis, availableInnerCrossDim)) {
               float childMainSize =
                   child->getLayout().measuredDimensions[dim[mainAxis]];
               float childCrossSize =
@@ -2941,21 +3055,25 @@ static void YGNodelayoutImpl(const YGNodeRef node,
 
               YGMeasureMode childMainMeasureMode = YGMeasureModeExactly;
               YGMeasureMode childCrossMeasureMode = YGMeasureModeExactly;
-              YGConstrainMaxSizeForMode(child,
-                                        mainAxis,
-                                        availableInnerMainDim,
-                                        availableInnerWidth,
-                                        &childMainMeasureMode,
-                                        &childMainSize);
-              YGConstrainMaxSizeForMode(child,
-                                        crossAxis,
-                                        availableInnerCrossDim,
-                                        availableInnerWidth,
-                                        &childCrossMeasureMode,
-                                        &childCrossSize);
-
-              const float childWidth = isMainAxisRow ? childMainSize : childCrossSize;
-              const float childHeight = !isMainAxisRow ? childMainSize : childCrossSize;
+              YGConstrainMaxSizeForMode(
+                  child,
+                  mainAxis,
+                  availableInnerMainDim,
+                  availableInnerWidth,
+                  &childMainMeasureMode,
+                  &childMainSize);
+              YGConstrainMaxSizeForMode(
+                  child,
+                  crossAxis,
+                  availableInnerCrossDim,
+                  availableInnerWidth,
+                  &childCrossMeasureMode,
+                  &childCrossSize);
+
+              const float childWidth =
+                  isMainAxisRow ? childMainSize : childCrossSize;
+              const float childHeight =
+                  !isMainAxisRow ? childMainSize : childCrossSize;
 
               const YGMeasureMode childWidthMeasureMode =
                   YGFloatIsUndefined(childWidth) ? YGMeasureModeUndefined
@@ -3015,7 +3133,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
   // STEP 8: MULTI-LINE CONTENT ALIGNMENT
   if (performLayout && (lineCount > 1 || YGIsBaselineLayout(node)) &&
       !YGFloatIsUndefined(availableInnerCrossDim)) {
-    const float remainingAlignContentDim = availableInnerCrossDim - totalLineCrossDim;
+    const float remainingAlignContentDim =
+        availableInnerCrossDim - totalLineCrossDim;
 
     float crossDimLead = 0;
     float currentLead = leadingPaddingAndBorderCross;
@@ -3140,9 +3259,10 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                             crossAxis, availableInnerWidth)),
                     pos[crossAxis]);
 
-                // Remeasure child with the line height as it as been only measured with the
-                // owners height yet.
-                if (!YGNodeIsStyleDimDefined(child, crossAxis, availableInnerCrossDim)) {
+                // Remeasure child with the line height as it as been only
+                // measured with the owners height yet.
+                if (!YGNodeIsStyleDimDefined(
+                        child, crossAxis, availableInnerCrossDim)) {
                   const float childWidth = isMainAxisRow
                       ? (child->getLayout()
                              .measuredDimensions[YGDimensionWidth] +
@@ -3165,17 +3285,18 @@ static void YGNodelayoutImpl(const YGNodeRef node,
                             childHeight,
                             child->getLayout()
                                 .measuredDimensions[YGDimensionHeight]))) {
-                    YGLayoutNodeInternal(child,
-                                         childWidth,
-                                         childHeight,
-                                         direction,
-                                         YGMeasureModeExactly,
-                                         YGMeasureModeExactly,
-                                         availableInnerWidth,
-                                         availableInnerHeight,
-                                         true,
-                                         "multiline-stretch",
-                                         config);
+                    YGLayoutNodeInternal(
+                        child,
+                        childWidth,
+                        childHeight,
+                        direction,
+                        YGMeasureModeExactly,
+                        YGMeasureModeExactly,
+                        availableInnerWidth,
+                        availableInnerHeight,
+                        true,
+                        "multiline-stretch",
+                        config);
                   }
                 }
                 break;
@@ -3278,7 +3399,8 @@ static void YGNodelayoutImpl(const YGNodeRef node,
         dim[crossAxis]);
   }
 
-  // As we only wrapped in normal direction yet, we need to reverse the positions on wrap-reverse.
+  // As we only wrapped in normal direction yet, we need to reverse the
+  // positions on wrap-reverse.
   if (performLayout && node->getStyle().flexWrap == YGWrapWrapReverse) {
     for (uint32_t i = 0; i < childCount; i++) {
       const YGNodeRef child = YGNodeGetChild(node, i);
@@ -3309,10 +3431,10 @@ static void YGNodelayoutImpl(const YGNodeRef node,
     }
 
     // STEP 11: SETTING TRAILING POSITIONS FOR CHILDREN
-    const bool needsMainTrailingPos =
-        mainAxis == YGFlexDirectionRowReverse || mainAxis == YGFlexDirectionColumnReverse;
-    const bool needsCrossTrailingPos =
-        crossAxis == YGFlexDirectionRowReverse || crossAxis == YGFlexDirectionColumnReverse;
+    const bool needsMainTrailingPos = mainAxis == YGFlexDirectionRowReverse ||
+        mainAxis == YGFlexDirectionColumnReverse;
+    const bool needsCrossTrailingPos = crossAxis == YGFlexDirectionRowReverse ||
+        crossAxis == YGFlexDirectionColumnReverse;
 
     // Set trailing position if necessary.
     if (needsMainTrailingPos || needsCrossTrailingPos) {
@@ -3338,9 +3460,10 @@ bool gPrintTree = false;
 bool gPrintChanges = false;
 bool gPrintSkips = false;
 
-static const char *spacer = "                                                            ";
+static const char* spacer =
+    "                                                            ";
 
-static const char *YGSpacer(const unsigned long level) {
+static const char* YGSpacer(const unsigned long level) {
   const size_t spacerLen = strlen(spacer);
   if (level > spacerLen) {
     return &spacer[0];
@@ -3349,9 +3472,12 @@ static const char *YGSpacer(const unsigned long level) {
   }
 }
 
-static const char *YGMeasureModeName(const YGMeasureMode mode, const bool performLayout) {
-  const char *kMeasureModeNames[YGMeasureModeCount] = {"UNDEFINED", "EXACTLY", "AT_MOST"};
-  const char *kLayoutModeNames[YGMeasureModeCount] = {"LAY_UNDEFINED",
+static const char* YGMeasureModeName(
+    const YGMeasureMode mode,
+    const bool performLayout) {
+  const char* kMeasureModeNames[YGMeasureModeCount] = {
+      "UNDEFINED", "EXACTLY", "AT_MOST"};
+  const char* kLayoutModeNames[YGMeasureModeCount] = {"LAY_UNDEFINED",
                                                       "LAY_EXACTLY",
                                                       "LAY_AT_"
                                                       "MOST"};
@@ -3363,25 +3489,30 @@ static const char *YGMeasureModeName(const YGMeasureMode mode, const bool perfor
   return performLayout ? kLayoutModeNames[mode] : kMeasureModeNames[mode];
 }
 
-static inline bool YGMeasureModeSizeIsExactAndMatchesOldMeasuredSize(YGMeasureMode sizeMode,
-                                                                     float size,
-                                                                     float lastComputedSize) {
-  return sizeMode == YGMeasureModeExactly && YGFloatsEqual(size, lastComputedSize);
+static inline bool YGMeasureModeSizeIsExactAndMatchesOldMeasuredSize(
+    YGMeasureMode sizeMode,
+    float size,
+    float lastComputedSize) {
+  return sizeMode == YGMeasureModeExactly &&
+      YGFloatsEqual(size, lastComputedSize);
 }
 
-static inline bool YGMeasureModeOldSizeIsUnspecifiedAndStillFits(YGMeasureMode sizeMode,
-                                                                 float size,
-                                                                 YGMeasureMode lastSizeMode,
-                                                                 float lastComputedSize) {
-  return sizeMode == YGMeasureModeAtMost && lastSizeMode == YGMeasureModeUndefined &&
-         (size >= lastComputedSize || YGFloatsEqual(size, lastComputedSize));
+static inline bool YGMeasureModeOldSizeIsUnspecifiedAndStillFits(
+    YGMeasureMode sizeMode,
+    float size,
+    YGMeasureMode lastSizeMode,
+    float lastComputedSize) {
+  return sizeMode == YGMeasureModeAtMost &&
+      lastSizeMode == YGMeasureModeUndefined &&
+      (size >= lastComputedSize || YGFloatsEqual(size, lastComputedSize));
 }
 
-static inline bool YGMeasureModeNewMeasureSizeIsStricterAndStillValid(YGMeasureMode sizeMode,
-                                                                      float size,
-                                                                      YGMeasureMode lastSizeMode,
-                                                                      float lastSize,
-                                                                      float lastComputedSize) {
+static inline bool YGMeasureModeNewMeasureSizeIsStricterAndStillValid(
+    YGMeasureMode sizeMode,
+    float size,
+    YGMeasureMode lastSizeMode,
+    float lastSize,
+    float lastComputedSize) {
   return lastSizeMode == YGMeasureModeAtMost &&
       sizeMode == YGMeasureModeAtMost && !YGFloatIsUndefined(lastSize) &&
       !YGFloatIsUndefined(size) && !YGFloatIsUndefined(lastComputedSize) &&
@@ -3389,10 +3520,11 @@ static inline bool YGMeasureModeNewMeasureSizeIsStricterAndStillValid(YGMeasureM
       (lastComputedSize <= size || YGFloatsEqual(size, lastComputedSize));
 }
 
-float YGRoundValueToPixelGrid(const float value,
-                              const float pointScaleFactor,
-                              const bool forceCeil,
-                              const bool forceFloor) {
+float YGRoundValueToPixelGrid(
+    const float value,
+    const float pointScaleFactor,
+    const bool forceCeil,
+    const bool forceFloor) {
   float scaledValue = value * pointScaleFactor;
   float fractial = fmodf(scaledValue, 1.0f);
   if (YGFloatsEqual(fractial, 0)) {
@@ -3419,66 +3551,74 @@ float YGRoundValueToPixelGrid(const float value,
       : scaledValue / pointScaleFactor;
 }
 
-bool YGNodeCanUseCachedMeasurement(const YGMeasureMode widthMode,
-                                   const float width,
-                                   const YGMeasureMode heightMode,
-                                   const float height,
-                                   const YGMeasureMode lastWidthMode,
-                                   const float lastWidth,
-                                   const YGMeasureMode lastHeightMode,
-                                   const float lastHeight,
-                                   const float lastComputedWidth,
-                                   const float lastComputedHeight,
-                                   const float marginRow,
-                                   const float marginColumn,
-                                   const YGConfigRef config) {
+bool YGNodeCanUseCachedMeasurement(
+    const YGMeasureMode widthMode,
+    const float width,
+    const YGMeasureMode heightMode,
+    const float height,
+    const YGMeasureMode lastWidthMode,
+    const float lastWidth,
+    const YGMeasureMode lastHeightMode,
+    const float lastHeight,
+    const float lastComputedWidth,
+    const float lastComputedHeight,
+    const float marginRow,
+    const float marginColumn,
+    const YGConfigRef config) {
   if ((!YGFloatIsUndefined(lastComputedHeight) && lastComputedHeight < 0) ||
       (!YGFloatIsUndefined(lastComputedWidth) && lastComputedWidth < 0)) {
     return false;
   }
   bool useRoundedComparison =
       config != nullptr && config->pointScaleFactor != 0;
-  const float effectiveWidth =
-      useRoundedComparison ? YGRoundValueToPixelGrid(width, config->pointScaleFactor, false, false)
-                           : width;
-  const float effectiveHeight =
-      useRoundedComparison ? YGRoundValueToPixelGrid(height, config->pointScaleFactor, false, false)
-                           : height;
-  const float effectiveLastWidth =
-      useRoundedComparison
-          ? YGRoundValueToPixelGrid(lastWidth, config->pointScaleFactor, false, false)
-          : lastWidth;
-  const float effectiveLastHeight =
-      useRoundedComparison
-          ? YGRoundValueToPixelGrid(lastHeight, config->pointScaleFactor, false, false)
-          : lastHeight;
-
-  const bool hasSameWidthSpec =
-      lastWidthMode == widthMode && YGFloatsEqual(effectiveLastWidth, effectiveWidth);
-  const bool hasSameHeightSpec =
-      lastHeightMode == heightMode && YGFloatsEqual(effectiveLastHeight, effectiveHeight);
+  const float effectiveWidth = useRoundedComparison
+      ? YGRoundValueToPixelGrid(width, config->pointScaleFactor, false, false)
+      : width;
+  const float effectiveHeight = useRoundedComparison
+      ? YGRoundValueToPixelGrid(height, config->pointScaleFactor, false, false)
+      : height;
+  const float effectiveLastWidth = useRoundedComparison
+      ? YGRoundValueToPixelGrid(
+            lastWidth, config->pointScaleFactor, false, false)
+      : lastWidth;
+  const float effectiveLastHeight = useRoundedComparison
+      ? YGRoundValueToPixelGrid(
+            lastHeight, config->pointScaleFactor, false, false)
+      : lastHeight;
+
+  const bool hasSameWidthSpec = lastWidthMode == widthMode &&
+      YGFloatsEqual(effectiveLastWidth, effectiveWidth);
+  const bool hasSameHeightSpec = lastHeightMode == heightMode &&
+      YGFloatsEqual(effectiveLastHeight, effectiveHeight);
 
   const bool widthIsCompatible =
-      hasSameWidthSpec || YGMeasureModeSizeIsExactAndMatchesOldMeasuredSize(widthMode,
-                                                                            width - marginRow,
-                                                                            lastComputedWidth) ||
-      YGMeasureModeOldSizeIsUnspecifiedAndStillFits(widthMode,
-                                                    width - marginRow,
-                                                    lastWidthMode,
-                                                    lastComputedWidth) ||
+      hasSameWidthSpec ||
+      YGMeasureModeSizeIsExactAndMatchesOldMeasuredSize(
+          widthMode, width - marginRow, lastComputedWidth) ||
+      YGMeasureModeOldSizeIsUnspecifiedAndStillFits(
+          widthMode, width - marginRow, lastWidthMode, lastComputedWidth) ||
       YGMeasureModeNewMeasureSizeIsStricterAndStillValid(
-          widthMode, width - marginRow, lastWidthMode, lastWidth, lastComputedWidth);
+          widthMode,
+          width - marginRow,
+          lastWidthMode,
+          lastWidth,
+          lastComputedWidth);
 
   const bool heightIsCompatible =
-      hasSameHeightSpec || YGMeasureModeSizeIsExactAndMatchesOldMeasuredSize(heightMode,
-                                                                             height - marginColumn,
-                                                                             lastComputedHeight) ||
-      YGMeasureModeOldSizeIsUnspecifiedAndStillFits(heightMode,
-                                                    height - marginColumn,
-                                                    lastHeightMode,
-                                                    lastComputedHeight) ||
+      hasSameHeightSpec ||
+      YGMeasureModeSizeIsExactAndMatchesOldMeasuredSize(
+          heightMode, height - marginColumn, lastComputedHeight) ||
+      YGMeasureModeOldSizeIsUnspecifiedAndStillFits(
+          heightMode,
+          height - marginColumn,
+          lastHeightMode,
+          lastComputedHeight) ||
       YGMeasureModeNewMeasureSizeIsStricterAndStillValid(
-          heightMode, height - marginColumn, lastHeightMode, lastHeight, lastComputedHeight);
+          heightMode,
+          height - marginColumn,
+          lastHeightMode,
+          lastHeight,
+          lastComputedHeight);
 
   return widthIsCompatible && heightIsCompatible;
 }
@@ -3491,17 +3631,18 @@ bool YGNodeCanUseCachedMeasurement(const YGMeasureMode widthMode,
 //  Input parameters are the same as YGNodelayoutImpl (see above)
 //  Return parameter is true if layout was performed, false if skipped
 //
-bool YGLayoutNodeInternal(const YGNodeRef node,
-                          const float availableWidth,
-                          const float availableHeight,
-                          const YGDirection ownerDirection,
-                          const YGMeasureMode widthMeasureMode,
-                          const YGMeasureMode heightMeasureMode,
-                          const float ownerWidth,
-                          const float ownerHeight,
-                          const bool performLayout,
-                          const char *reason,
-                          const YGConfigRef config) {
+bool YGLayoutNodeInternal(
+    const YGNodeRef node,
+    const float availableWidth,
+    const float availableHeight,
+    const YGDirection ownerDirection,
+    const YGMeasureMode widthMeasureMode,
+    const YGMeasureMode heightMeasureMode,
+    const float ownerWidth,
+    const float ownerHeight,
+    const bool performLayout,
+    const char* reason,
+    const YGConfigRef config) {
   YGLayout* layout = &node->getLayout();
 
   gDepth++;
@@ -3513,8 +3654,8 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
   if (needToVisitNode) {
     // Invalidate the cached results.
     layout->nextCachedMeasurementsIndex = 0;
-    layout->cachedLayout.widthMeasureMode = (YGMeasureMode) -1;
-    layout->cachedLayout.heightMeasureMode = (YGMeasureMode) -1;
+    layout->cachedLayout.widthMeasureMode = (YGMeasureMode)-1;
+    layout->cachedLayout.heightMeasureMode = (YGMeasureMode)-1;
     layout->cachedLayout.computedWidth = -1;
     layout->cachedLayout.computedHeight = -1;
   }
@@ -3540,36 +3681,38 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
         node->getMarginForAxis(YGFlexDirectionColumn, ownerWidth));
 
     // First, try to use the layout cache.
-    if (YGNodeCanUseCachedMeasurement(widthMeasureMode,
-                                      availableWidth,
-                                      heightMeasureMode,
-                                      availableHeight,
-                                      layout->cachedLayout.widthMeasureMode,
-                                      layout->cachedLayout.availableWidth,
-                                      layout->cachedLayout.heightMeasureMode,
-                                      layout->cachedLayout.availableHeight,
-                                      layout->cachedLayout.computedWidth,
-                                      layout->cachedLayout.computedHeight,
-                                      marginAxisRow,
-                                      marginAxisColumn,
-                                      config)) {
+    if (YGNodeCanUseCachedMeasurement(
+            widthMeasureMode,
+            availableWidth,
+            heightMeasureMode,
+            availableHeight,
+            layout->cachedLayout.widthMeasureMode,
+            layout->cachedLayout.availableWidth,
+            layout->cachedLayout.heightMeasureMode,
+            layout->cachedLayout.availableHeight,
+            layout->cachedLayout.computedWidth,
+            layout->cachedLayout.computedHeight,
+            marginAxisRow,
+            marginAxisColumn,
+            config)) {
       cachedResults = &layout->cachedLayout;
     } else {
       // Try to use the measurement cache.
       for (uint32_t i = 0; i < layout->nextCachedMeasurementsIndex; i++) {
-        if (YGNodeCanUseCachedMeasurement(widthMeasureMode,
-                                          availableWidth,
-                                          heightMeasureMode,
-                                          availableHeight,
-                                          layout->cachedMeasurements[i].widthMeasureMode,
-                                          layout->cachedMeasurements[i].availableWidth,
-                                          layout->cachedMeasurements[i].heightMeasureMode,
-                                          layout->cachedMeasurements[i].availableHeight,
-                                          layout->cachedMeasurements[i].computedWidth,
-                                          layout->cachedMeasurements[i].computedHeight,
-                                          marginAxisRow,
-                                          marginAxisColumn,
-                                          config)) {
+        if (YGNodeCanUseCachedMeasurement(
+                widthMeasureMode,
+                availableWidth,
+                heightMeasureMode,
+                availableHeight,
+                layout->cachedMeasurements[i].widthMeasureMode,
+                layout->cachedMeasurements[i].availableWidth,
+                layout->cachedMeasurements[i].heightMeasureMode,
+                layout->cachedMeasurements[i].availableHeight,
+                layout->cachedMeasurements[i].computedWidth,
+                layout->cachedMeasurements[i].computedHeight,
+                marginAxisRow,
+                marginAxisColumn,
+                config)) {
           cachedResults = &layout->cachedMeasurements[i];
           break;
         }
@@ -3584,10 +3727,13 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
     }
   } else {
     for (uint32_t i = 0; i < layout->nextCachedMeasurementsIndex; i++) {
-      if (YGFloatsEqual(layout->cachedMeasurements[i].availableWidth, availableWidth) &&
-          YGFloatsEqual(layout->cachedMeasurements[i].availableHeight, availableHeight) &&
+      if (YGFloatsEqual(
+              layout->cachedMeasurements[i].availableWidth, availableWidth) &&
+          YGFloatsEqual(
+              layout->cachedMeasurements[i].availableHeight, availableHeight) &&
           layout->cachedMeasurements[i].widthMeasureMode == widthMeasureMode &&
-          layout->cachedMeasurements[i].heightMeasureMode == heightMeasureMode) {
+          layout->cachedMeasurements[i].heightMeasureMode ==
+              heightMeasureMode) {
         cachedResults = &layout->cachedMeasurements[i];
         break;
       }
@@ -3596,10 +3742,16 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
 
   if (!needToVisitNode && cachedResults != nullptr) {
     layout->measuredDimensions[YGDimensionWidth] = cachedResults->computedWidth;
-    layout->measuredDimensions[YGDimensionHeight] = cachedResults->computedHeight;
+    layout->measuredDimensions[YGDimensionHeight] =
+        cachedResults->computedHeight;
 
     if (gPrintChanges && gPrintSkips) {
-      YGLog(node, YGLogLevelVerbose, "%s%d.{[skipped] ", YGSpacer(gDepth), gDepth);
+      YGLog(
+          node,
+          YGLogLevelVerbose,
+          "%s%d.{[skipped] ",
+          YGSpacer(gDepth),
+          gDepth);
       if (node->getPrintFunc() != nullptr) {
         node->getPrintFunc()(node);
       }
@@ -3638,16 +3790,17 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
           reason);
     }
 
-    YGNodelayoutImpl(node,
-                     availableWidth,
-                     availableHeight,
-                     ownerDirection,
-                     widthMeasureMode,
-                     heightMeasureMode,
-                     ownerWidth,
-                     ownerHeight,
-                     performLayout,
-                     config);
+    YGNodelayoutImpl(
+        node,
+        availableWidth,
+        availableHeight,
+        ownerDirection,
+        widthMeasureMode,
+        heightMeasureMode,
+        ownerWidth,
+        ownerHeight,
+        performLayout,
+        config);
 
     if (gPrintChanges) {
       YGLog(
@@ -3681,13 +3834,14 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
         layout->nextCachedMeasurementsIndex = 0;
       }
 
-      YGCachedMeasurement *newCacheEntry;
+      YGCachedMeasurement* newCacheEntry;
       if (performLayout) {
         // Use the single layout cache entry.
         newCacheEntry = &layout->cachedLayout;
       } else {
         // Allocate a new measurement cache entry.
-        newCacheEntry = &layout->cachedMeasurements[layout->nextCachedMeasurementsIndex];
+        newCacheEntry =
+            &layout->cachedMeasurements[layout->nextCachedMeasurementsIndex];
         layout->nextCachedMeasurementsIndex++;
       }
 
@@ -3695,8 +3849,10 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
       newCacheEntry->availableHeight = availableHeight;
       newCacheEntry->widthMeasureMode = widthMeasureMode;
       newCacheEntry->heightMeasureMode = heightMeasureMode;
-      newCacheEntry->computedWidth = layout->measuredDimensions[YGDimensionWidth];
-      newCacheEntry->computedHeight = layout->measuredDimensions[YGDimensionHeight];
+      newCacheEntry->computedWidth =
+          layout->measuredDimensions[YGDimensionWidth];
+      newCacheEntry->computedHeight =
+          layout->measuredDimensions[YGDimensionHeight];
     }
   }
 
@@ -3717,8 +3873,13 @@ bool YGLayoutNodeInternal(const YGNodeRef node,
   return (needToVisitNode || cachedResults == nullptr);
 }
 
-void YGConfigSetPointScaleFactor(const YGConfigRef config, const float pixelsInPoint) {
-  YGAssertWithConfig(config, pixelsInPoint >= 0.0f, "Scale factor should not be less than zero");
+void YGConfigSetPointScaleFactor(
+    const YGConfigRef config,
+    const float pixelsInPoint) {
+  YGAssertWithConfig(
+      config,
+      pixelsInPoint >= 0.0f,
+      "Scale factor should not be less than zero");
 
   // We store points for Pixel as we will use it for rounding
   if (pixelsInPoint == 0.0f) {
@@ -3729,10 +3890,11 @@ void YGConfigSetPointScaleFactor(const YGConfigRef config, const float pixelsInP
   }
 }
 
-static void YGRoundToPixelGrid(const YGNodeRef node,
-                               const float pointScaleFactor,
-                               const float absoluteLeft,
-                               const float absoluteTop) {
+static void YGRoundToPixelGrid(
+    const YGNodeRef node,
+    const float pointScaleFactor,
+    const float absoluteLeft,
+    const float absoluteTop) {
   if (pointScaleFactor == 0.0f) {
     return;
   }
@@ -3749,8 +3911,8 @@ static void YGRoundToPixelGrid(const YGNodeRef node,
   const float absoluteNodeRight = absoluteNodeLeft + nodeWidth;
   const float absoluteNodeBottom = absoluteNodeTop + nodeHeight;
 
-  // If a node has a custom measure function we never want to round down its size as this could
-  // lead to unwanted text truncation.
+  // If a node has a custom measure function we never want to round down its
+  // size as this could lead to unwanted text truncation.
   const bool textRounding = node->getNodeType() == YGNodeTypeText;
 
   node->setLayoutPosition(
@@ -3761,13 +3923,15 @@ static void YGRoundToPixelGrid(const YGNodeRef node,
       YGRoundValueToPixelGrid(nodeTop, pointScaleFactor, false, textRounding),
       YGEdgeTop);
 
-  // We multiply dimension by scale factor and if the result is close to the whole number, we don't
-  // have any fraction
-  // To verify if the result is close to whole number we want to check both floor and ceil numbers
-  const bool hasFractionalWidth = !YGFloatsEqual(fmodf(nodeWidth * pointScaleFactor, 1.0), 0) &&
-                                  !YGFloatsEqual(fmodf(nodeWidth * pointScaleFactor, 1.0), 1.0);
-  const bool hasFractionalHeight = !YGFloatsEqual(fmodf(nodeHeight * pointScaleFactor, 1.0), 0) &&
-                                   !YGFloatsEqual(fmodf(nodeHeight * pointScaleFactor, 1.0), 1.0);
+  // We multiply dimension by scale factor and if the result is close to the
+  // whole number, we don't have any fraction To verify if the result is close
+  // to whole number we want to check both floor and ceil numbers
+  const bool hasFractionalWidth =
+      !YGFloatsEqual(fmodf(nodeWidth * pointScaleFactor, 1.0), 0) &&
+      !YGFloatsEqual(fmodf(nodeWidth * pointScaleFactor, 1.0), 1.0);
+  const bool hasFractionalHeight =
+      !YGFloatsEqual(fmodf(nodeHeight * pointScaleFactor, 1.0), 0) &&
+      !YGFloatsEqual(fmodf(nodeHeight * pointScaleFactor, 1.0), 1.0);
 
   node->setLayoutDimension(
       YGRoundValueToPixelGrid(
@@ -3844,7 +4008,8 @@ void YGNodeCalculateLayout(
                   node->getStyle().maxDimensions[YGDimensionHeight],
                   ownerHeight)
                   .isUndefined()) {
-    height = YGUnwrapFloatOptional(YGResolveValue(node->getStyle().maxDimensions[YGDimensionHeight], ownerHeight));
+    height = YGUnwrapFloatOptional(YGResolveValue(
+        node->getStyle().maxDimensions[YGDimensionHeight], ownerHeight));
     heightMeasureMode = YGMeasureModeAtMost;
   } else {
     height = ownerHeight;
@@ -3950,12 +4115,14 @@ void YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
   config->shouldDiffLayoutWithoutLegacyStretchBehaviour = shouldDiffLayout;
 }
 
-static void YGVLog(const YGConfigRef config,
-                   const YGNodeRef node,
-                   YGLogLevel level,
-                   const char *format,
-                   va_list args) {
-  const YGConfigRef logConfig = config != nullptr ? config : YGConfigGetDefault();
+static void YGVLog(
+    const YGConfigRef config,
+    const YGNodeRef node,
+    YGLogLevel level,
+    const char* format,
+    va_list args) {
+  const YGConfigRef logConfig =
+      config != nullptr ? config : YGConfigGetDefault();
   logConfig->logger(logConfig, node, level, format, args);
 
   if (level == YGLogLevelFatal) {
@@ -3963,14 +4130,18 @@ static void YGVLog(const YGConfigRef config,
   }
 }
 
-void YGLogWithConfig(const YGConfigRef config, YGLogLevel level, const char *format, ...) {
+void YGLogWithConfig(
+    const YGConfigRef config,
+    YGLogLevel level,
+    const char* format,
+    ...) {
   va_list args;
   va_start(args, format);
   YGVLog(config, nullptr, level, format, args);
   va_end(args);
 }
 
-void YGLog(const YGNodeRef node, YGLogLevel level, const char *format, ...) {
+void YGLog(const YGNodeRef node, YGLogLevel level, const char* format, ...) {
   va_list args;
   va_start(args, format);
   YGVLog(
@@ -3978,32 +4149,40 @@ void YGLog(const YGNodeRef node, YGLogLevel level, const char *format, ...) {
   va_end(args);
 }
 
-void YGAssert(const bool condition, const char *message) {
+void YGAssert(const bool condition, const char* message) {
   if (!condition) {
     YGLog(nullptr, YGLogLevelFatal, "%s\n", message);
   }
 }
 
-void YGAssertWithNode(const YGNodeRef node, const bool condition, const char *message) {
+void YGAssertWithNode(
+    const YGNodeRef node,
+    const bool condition,
+    const char* message) {
   if (!condition) {
     YGLog(node, YGLogLevelFatal, "%s\n", message);
   }
 }
 
-void YGAssertWithConfig(const YGConfigRef config, const bool condition, const char *message) {
+void YGAssertWithConfig(
+    const YGConfigRef config,
+    const bool condition,
+    const char* message) {
   if (!condition) {
     YGLogWithConfig(config, YGLogLevelFatal, "%s\n", message);
   }
 }
 
-void YGConfigSetExperimentalFeatureEnabled(const YGConfigRef config,
-                                           const YGExperimentalFeature feature,
-                                           const bool enabled) {
+void YGConfigSetExperimentalFeatureEnabled(
+    const YGConfigRef config,
+    const YGExperimentalFeature feature,
+    const bool enabled) {
   config->experimentalFeatures[feature] = enabled;
 }
 
-inline bool YGConfigIsExperimentalFeatureEnabled(const YGConfigRef config,
-                                                 const YGExperimentalFeature feature) {
+inline bool YGConfigIsExperimentalFeatureEnabled(
+    const YGConfigRef config,
+    const YGExperimentalFeature feature) {
   return config->experimentalFeatures[feature];
 }
 
@@ -4011,8 +4190,9 @@ void YGConfigSetUseWebDefaults(const YGConfigRef config, const bool enabled) {
   config->useWebDefaults = enabled;
 }
 
-void YGConfigSetUseLegacyStretchBehaviour(const YGConfigRef config,
-                                          const bool useLegacyStretchBehaviour) {
+void YGConfigSetUseLegacyStretchBehaviour(
+    const YGConfigRef config,
+    const bool useLegacyStretchBehaviour) {
   config->useLegacyStretchBehaviour = useLegacyStretchBehaviour;
 }
 
@@ -4020,26 +4200,32 @@ bool YGConfigGetUseWebDefaults(const YGConfigRef config) {
   return config->useWebDefaults;
 }
 
-void YGConfigSetContext(const YGConfigRef config, void *context) {
+void YGConfigSetContext(const YGConfigRef config, void* context) {
   config->context = context;
 }
 
-void *YGConfigGetContext(const YGConfigRef config) {
+void* YGConfigGetContext(const YGConfigRef config) {
   return config->context;
 }
 
-void YGConfigSetCloneNodeFunc(const YGConfigRef config, const YGCloneNodeFunc callback) {
+void YGConfigSetCloneNodeFunc(
+    const YGConfigRef config,
+    const YGCloneNodeFunc callback) {
   config->cloneNodeCallback = callback;
 }
 
-static void YGTraverseChildrenPreOrder(const YGVector& children, const std::function<void(YGNodeRef node)>& f) {
+static void YGTraverseChildrenPreOrder(
+    const YGVector& children,
+    const std::function<void(YGNodeRef node)>& f) {
   for (YGNodeRef node : children) {
     f(node);
     YGTraverseChildrenPreOrder(node->getChildren(), f);
   }
 }
 
-void YGTraversePreOrder(YGNodeRef const node, std::function<void(YGNodeRef node)>&& f) {
+void YGTraversePreOrder(
+    YGNodeRef const node,
+    std::function<void(YGNodeRef node)>&& f) {
   if (!node) {
     return;
   }
diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index a9fc89d7df4d..fee2e3286663 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -1,10 +1,10 @@
-/**
- * Copyright (c) 2014-present, Facebook, Inc.
+/*
+ *  Copyright (c) 2014-present, Facebook, Inc.
+ *
+ *  This source code is licensed under the MIT license found in the LICENSE
+ *  file in the root directory of this source tree.
  *
- * This source code is licensed under the MIT license found in the
- * LICENSE file in the root directory of this source tree.
  */
-
 #pragma once
 
 #include <assert.h>
@@ -45,23 +45,26 @@ typedef struct YGValue {
 extern const YGValue YGValueUndefined;
 extern const YGValue YGValueAuto;
 
-typedef struct YGConfig *YGConfigRef;
+typedef struct YGConfig* YGConfigRef;
 
 typedef struct YGNode* YGNodeRef;
 
-typedef YGSize (*YGMeasureFunc)(YGNodeRef node,
-                                float width,
-                                YGMeasureMode widthMode,
-                                float height,
-                                YGMeasureMode heightMode);
-typedef float (*YGBaselineFunc)(YGNodeRef node, const float width, const float height);
+typedef YGSize (*YGMeasureFunc)(
+    YGNodeRef node,
+    float width,
+    YGMeasureMode widthMode,
+    float height,
+    YGMeasureMode heightMode);
+typedef float (
+    *YGBaselineFunc)(YGNodeRef node, const float width, const float height);
 typedef void (*YGDirtiedFunc)(YGNodeRef node);
 typedef void (*YGPrintFunc)(YGNodeRef node);
-typedef int (*YGLogger)(const YGConfigRef config,
-                        const YGNodeRef node,
-                        YGLogLevel level,
-                        const char *format,
-                        va_list args);
+typedef int (*YGLogger)(
+    const YGConfigRef config,
+    const YGNodeRef node,
+    YGLogLevel level,
+    const char* format,
+    va_list args);
 typedef YGNodeRef (
     *YGCloneNodeFunc)(YGNodeRef oldNode, YGNodeRef owner, int childIndex);
 
@@ -74,9 +77,10 @@ WIN_EXPORT void YGNodeFreeRecursive(const YGNodeRef node);
 WIN_EXPORT void YGNodeReset(const YGNodeRef node);
 WIN_EXPORT int32_t YGNodeGetInstanceCount(void);
 
-WIN_EXPORT void YGNodeInsertChild(const YGNodeRef node,
-                                  const YGNodeRef child,
-                                  const uint32_t index);
+WIN_EXPORT void YGNodeInsertChild(
+    const YGNodeRef node,
+    const YGNodeRef child,
+    const uint32_t index);
 
 // This function inserts the child YGNodeRef as a children of the node received
 // by parameter and set the Owner of the child object to null. This function is
@@ -99,10 +103,11 @@ WIN_EXPORT void YGNodeSetChildren(
     const YGNodeRef children[],
     const uint32_t count);
 
-WIN_EXPORT void YGNodeCalculateLayout(const YGNodeRef node,
-                                      const float availableWidth,
-                                      const float availableHeight,
-                                      const YGDirection ownerDirection);
+WIN_EXPORT void YGNodeCalculateLayout(
+    const YGNodeRef node,
+    const float availableWidth,
+    const float availableHeight,
+    const YGDirection ownerDirection);
 
 // Mark a node as dirty. Only valid for nodes with a custom measure function
 // set.
@@ -112,70 +117,78 @@ WIN_EXPORT void YGNodeCalculateLayout(const YGNodeRef node,
 // marking manually.
 WIN_EXPORT void YGNodeMarkDirty(const YGNodeRef node);
 
-// This function marks the current node and all its descendants as dirty. This function is added to test yoga benchmarks.
-// This function is not expected to be used in production as calling `YGCalculateLayout` will cause the recalculation of each and every node.
+// This function marks the current node and all its descendants as dirty. This
+// function is added to test yoga benchmarks. This function is not expected to
+// be used in production as calling `YGCalculateLayout` will cause the
+// recalculation of each and every node.
 WIN_EXPORT void YGNodeMarkDirtyAndPropogateToDescendants(const YGNodeRef node);
 
 WIN_EXPORT void YGNodePrint(const YGNodeRef node, const YGPrintOptions options);
 
 WIN_EXPORT bool YGFloatIsUndefined(const float value);
 
-WIN_EXPORT bool YGNodeCanUseCachedMeasurement(const YGMeasureMode widthMode,
-                                              const float width,
-                                              const YGMeasureMode heightMode,
-                                              const float height,
-                                              const YGMeasureMode lastWidthMode,
-                                              const float lastWidth,
-                                              const YGMeasureMode lastHeightMode,
-                                              const float lastHeight,
-                                              const float lastComputedWidth,
-                                              const float lastComputedHeight,
-                                              const float marginRow,
-                                              const float marginColumn,
-                                              const YGConfigRef config);
-
-WIN_EXPORT void YGNodeCopyStyle(const YGNodeRef dstNode, const YGNodeRef srcNode);
+WIN_EXPORT bool YGNodeCanUseCachedMeasurement(
+    const YGMeasureMode widthMode,
+    const float width,
+    const YGMeasureMode heightMode,
+    const float height,
+    const YGMeasureMode lastWidthMode,
+    const float lastWidth,
+    const YGMeasureMode lastHeightMode,
+    const float lastHeight,
+    const float lastComputedWidth,
+    const float lastComputedHeight,
+    const float marginRow,
+    const float marginColumn,
+    const YGConfigRef config);
+
+WIN_EXPORT void YGNodeCopyStyle(
+    const YGNodeRef dstNode,
+    const YGNodeRef srcNode);
 
 #define YG_NODE_PROPERTY(type, name, paramName)                          \
   WIN_EXPORT void YGNodeSet##name(const YGNodeRef node, type paramName); \
   WIN_EXPORT type YGNodeGet##name(const YGNodeRef node);
 
-#define YG_NODE_STYLE_PROPERTY(type, name, paramName)                               \
-  WIN_EXPORT void YGNodeStyleSet##name(const YGNodeRef node, const type paramName); \
+#define YG_NODE_STYLE_PROPERTY(type, name, paramName) \
+  WIN_EXPORT void YGNodeStyleSet##name(               \
+      const YGNodeRef node, const type paramName);    \
   WIN_EXPORT type YGNodeStyleGet##name(const YGNodeRef node);
 
-#define YG_NODE_STYLE_PROPERTY_UNIT(type, name, paramName)                                    \
-  WIN_EXPORT void YGNodeStyleSet##name(const YGNodeRef node, const float paramName);          \
-  WIN_EXPORT void YGNodeStyleSet##name##Percent(const YGNodeRef node, const float paramName); \
+#define YG_NODE_STYLE_PROPERTY_UNIT(type, name, paramName) \
+  WIN_EXPORT void YGNodeStyleSet##name(                    \
+      const YGNodeRef node, const float paramName);        \
+  WIN_EXPORT void YGNodeStyleSet##name##Percent(           \
+      const YGNodeRef node, const float paramName);        \
   WIN_EXPORT type YGNodeStyleGet##name(const YGNodeRef node);
 
 #define YG_NODE_STYLE_PROPERTY_UNIT_AUTO(type, name, paramName) \
   YG_NODE_STYLE_PROPERTY_UNIT(type, name, paramName)            \
   WIN_EXPORT void YGNodeStyleSet##name##Auto(const YGNodeRef node);
 
-#define YG_NODE_STYLE_EDGE_PROPERTY(type, name, paramName)    \
-  WIN_EXPORT void YGNodeStyleSet##name(const YGNodeRef node,  \
-                                       const YGEdge edge,     \
-                                       const type paramName); \
+#define YG_NODE_STYLE_EDGE_PROPERTY(type, name, paramName)            \
+  WIN_EXPORT void YGNodeStyleSet##name(                               \
+      const YGNodeRef node, const YGEdge edge, const type paramName); \
   WIN_EXPORT type YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge);
 
-#define YG_NODE_STYLE_EDGE_PROPERTY_UNIT(type, name, paramName)         \
-  WIN_EXPORT void YGNodeStyleSet##name(const YGNodeRef node,            \
-                                       const YGEdge edge,               \
-                                       const float paramName);          \
-  WIN_EXPORT void YGNodeStyleSet##name##Percent(const YGNodeRef node,   \
-                                                const YGEdge edge,      \
-                                                const float paramName); \
-  WIN_EXPORT WIN_STRUCT(type) YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge);
+#define YG_NODE_STYLE_EDGE_PROPERTY_UNIT(type, name, paramName)        \
+  WIN_EXPORT void YGNodeStyleSet##name(                                \
+      const YGNodeRef node, const YGEdge edge, const float paramName); \
+  WIN_EXPORT void YGNodeStyleSet##name##Percent(                       \
+      const YGNodeRef node, const YGEdge edge, const float paramName); \
+  WIN_EXPORT WIN_STRUCT(type)                                          \
+      YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge);
 
 #define YG_NODE_STYLE_EDGE_PROPERTY_UNIT_AUTO(type, name) \
-  WIN_EXPORT void YGNodeStyleSet##name##Auto(const YGNodeRef node, const YGEdge edge);
+  WIN_EXPORT void YGNodeStyleSet##name##Auto(             \
+      const YGNodeRef node, const YGEdge edge);
 
 #define YG_NODE_LAYOUT_PROPERTY(type, name) \
   WIN_EXPORT type YGNodeLayoutGet##name(const YGNodeRef node);
 
 #define YG_NODE_LAYOUT_EDGE_PROPERTY(type, name) \
-  WIN_EXPORT type YGNodeLayoutGet##name(const YGNodeRef node, const YGEdge edge);
+  WIN_EXPORT type YGNodeLayoutGet##name(         \
+      const YGNodeRef node, const YGEdge edge);
 
 void* YGNodeGetContext(YGNodeRef node);
 void YGNodeSetContext(YGNodeRef node, void* context);
@@ -224,16 +237,18 @@ YG_NODE_STYLE_PROPERTY_UNIT(YGValue, MaxHeight, maxHeight);
 
 // Yoga specific properties, not compatible with flexbox specification
 // Aspect ratio control the size of the undefined dimension of a node.
-// Aspect ratio is encoded as a floating point value width/height. e.g. A value of 2 leads to a node
-// with a width twice the size of its height while a value of 0.5 gives the opposite effect.
+// Aspect ratio is encoded as a floating point value width/height. e.g. A value
+// of 2 leads to a node with a width twice the size of its height while a value
+// of 0.5 gives the opposite effect.
 //
-// - On a node with a set width/height aspect ratio control the size of the unset dimension
-// - On a node with a set flex basis aspect ratio controls the size of the node in the cross axis if
-// unset
-// - On a node with a measure function aspect ratio works as though the measure function measures
-// the flex basis
-// - On a node with flex grow/shrink aspect ratio controls the size of the node in the cross axis if
-// unset
+// - On a node with a set width/height aspect ratio control the size of the
+// unset dimension
+// - On a node with a set flex basis aspect ratio controls the size of the node
+// in the cross axis if unset
+// - On a node with a measure function aspect ratio works as though the measure
+// function measures the flex basis
+// - On a node with flex grow/shrink aspect ratio controls the size of the node
+// in the cross axis if unset
 // - Aspect ratio takes min/max dimensions into account
 YG_NODE_STYLE_PROPERTY(float, AspectRatio, aspectRatio);
 
@@ -247,37 +262,48 @@ YG_NODE_LAYOUT_PROPERTY(YGDirection, Direction);
 YG_NODE_LAYOUT_PROPERTY(bool, HadOverflow);
 bool YGNodeLayoutGetDidLegacyStretchFlagAffectLayout(const YGNodeRef node);
 
-// Get the computed values for these nodes after performing layout. If they were set using
-// point values then the returned value will be the same as YGNodeStyleGetXXX. However if
-// they were set using a percentage value then the returned value is the computed value used
-// during layout.
+// Get the computed values for these nodes after performing layout. If they were
+// set using point values then the returned value will be the same as
+// YGNodeStyleGetXXX. However if they were set using a percentage value then the
+// returned value is the computed value used during layout.
 YG_NODE_LAYOUT_EDGE_PROPERTY(float, Margin);
 YG_NODE_LAYOUT_EDGE_PROPERTY(float, Border);
 YG_NODE_LAYOUT_EDGE_PROPERTY(float, Padding);
 
 WIN_EXPORT void YGConfigSetLogger(const YGConfigRef config, YGLogger logger);
-WIN_EXPORT void YGLog(const YGNodeRef node, YGLogLevel level, const char *message, ...);
-WIN_EXPORT void YGLogWithConfig(const YGConfigRef config, YGLogLevel level, const char *format, ...);
-WIN_EXPORT void YGAssert(const bool condition, const char *message);
-WIN_EXPORT void YGAssertWithNode(const YGNodeRef node, const bool condition, const char *message);
-WIN_EXPORT void YGAssertWithConfig(const YGConfigRef config,
-                                   const bool condition,
-                                   const char *message);
+WIN_EXPORT void
+YGLog(const YGNodeRef node, YGLogLevel level, const char* message, ...);
+WIN_EXPORT void YGLogWithConfig(
+    const YGConfigRef config,
+    YGLogLevel level,
+    const char* format,
+    ...);
+WIN_EXPORT void YGAssert(const bool condition, const char* message);
+WIN_EXPORT void YGAssertWithNode(
+    const YGNodeRef node,
+    const bool condition,
+    const char* message);
+WIN_EXPORT void YGAssertWithConfig(
+    const YGConfigRef config,
+    const bool condition,
+    const char* message);
 // Set this to number of pixels in 1 point to round calculation results
 // If you want to avoid rounding - set PointScaleFactor to 0
-WIN_EXPORT void YGConfigSetPointScaleFactor(const YGConfigRef config, const float pixelsInPoint);
+WIN_EXPORT void YGConfigSetPointScaleFactor(
+    const YGConfigRef config,
+    const float pixelsInPoint);
 void YGConfigSetShouldDiffLayoutWithoutLegacyStretchBehaviour(
     const YGConfigRef config,
     const bool shouldDiffLayout);
 
-// Yoga previously had an error where containers would take the maximum space possible instead of
-// the minimum
-// like they are supposed to. In practice this resulted in implicit behaviour similar to align-self:
-// stretch;
-// Because this was such a long-standing bug we must allow legacy users to switch back to this
-// behaviour.
-WIN_EXPORT void YGConfigSetUseLegacyStretchBehaviour(const YGConfigRef config,
-                                                     const bool useLegacyStretchBehaviour);
+// Yoga previously had an error where containers would take the maximum space
+// possible instead of the minimum like they are supposed to. In practice this
+// resulted in implicit behaviour similar to align-self: stretch; Because this
+// was such a long-standing bug we must allow legacy users to switch back to
+// this behaviour.
+WIN_EXPORT void YGConfigSetUseLegacyStretchBehaviour(
+    const YGConfigRef config,
+    const bool useLegacyStretchBehaviour);
 
 // YGConfig
 WIN_EXPORT YGConfigRef YGConfigNew(void);
@@ -285,25 +311,30 @@ WIN_EXPORT void YGConfigFree(const YGConfigRef config);
 WIN_EXPORT void YGConfigCopy(const YGConfigRef dest, const YGConfigRef src);
 WIN_EXPORT int32_t YGConfigGetInstanceCount(void);
 
-WIN_EXPORT void YGConfigSetExperimentalFeatureEnabled(const YGConfigRef config,
-                                                      const YGExperimentalFeature feature,
-                                                      const bool enabled);
-WIN_EXPORT bool YGConfigIsExperimentalFeatureEnabled(const YGConfigRef config,
-                                                     const YGExperimentalFeature feature);
+WIN_EXPORT void YGConfigSetExperimentalFeatureEnabled(
+    const YGConfigRef config,
+    const YGExperimentalFeature feature,
+    const bool enabled);
+WIN_EXPORT bool YGConfigIsExperimentalFeatureEnabled(
+    const YGConfigRef config,
+    const YGExperimentalFeature feature);
 
 // Using the web defaults is the prefered configuration for new projects.
 // Usage of non web defaults should be considered as legacy.
-WIN_EXPORT void YGConfigSetUseWebDefaults(const YGConfigRef config, const bool enabled);
+WIN_EXPORT void YGConfigSetUseWebDefaults(
+    const YGConfigRef config,
+    const bool enabled);
 WIN_EXPORT bool YGConfigGetUseWebDefaults(const YGConfigRef config);
 
-WIN_EXPORT void YGConfigSetCloneNodeFunc(const YGConfigRef config,
-                                          const YGCloneNodeFunc callback);
+WIN_EXPORT void YGConfigSetCloneNodeFunc(
+    const YGConfigRef config,
+    const YGCloneNodeFunc callback);
 
 // Export only for C#
 WIN_EXPORT YGConfigRef YGConfigGetDefault(void);
 
-WIN_EXPORT void YGConfigSetContext(const YGConfigRef config, void *context);
-WIN_EXPORT void *YGConfigGetContext(const YGConfigRef config);
+WIN_EXPORT void YGConfigSetContext(const YGConfigRef config, void* context);
+WIN_EXPORT void* YGConfigGetContext(const YGConfigRef config);
 
 WIN_EXPORT float YGRoundValueToPixelGrid(
     const float value,
@@ -319,7 +350,9 @@ YG_EXTERN_C_END
 #include <vector>
 
 // Calls f on each node in the tree including the given node argument.
-extern void YGTraversePreOrder(YGNodeRef const node, std::function<void(YGNodeRef node)>&& f);
+extern void YGTraversePreOrder(
+    YGNodeRef const node,
+    std::function<void(YGNodeRef node)>&& f);
 
 extern void YGNodeSetChildren(
     YGNodeRef const owner,

From 95b7fd9de66506c86ab3c55f33ac0a27a98c3982 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 19 Jul 2018 09:57:06 -0700
Subject: [PATCH 1093/1109] Yoga.h: inline function declaring macros

Summary:
@public

Inlines macros used for declarations of `YGNodeStyle*` and `YGNodeLayout*` functions.
Benefits easier grepping and code base navigation.

Reviewed By: astreet

Differential Revision: D8868168

fbshipit-source-id: d6b1b70981a59a2214dc7d166435a1d1a844e1b7
---
 ReactCommon/yoga/yoga/Yoga.h | 261 ++++++++++++++++++++++++-----------
 1 file changed, 177 insertions(+), 84 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Yoga.h b/ReactCommon/yoga/yoga/Yoga.h
index fee2e3286663..d6b12d29a238 100644
--- a/ReactCommon/yoga/yoga/Yoga.h
+++ b/ReactCommon/yoga/yoga/Yoga.h
@@ -146,50 +146,6 @@ WIN_EXPORT void YGNodeCopyStyle(
     const YGNodeRef dstNode,
     const YGNodeRef srcNode);
 
-#define YG_NODE_PROPERTY(type, name, paramName)                          \
-  WIN_EXPORT void YGNodeSet##name(const YGNodeRef node, type paramName); \
-  WIN_EXPORT type YGNodeGet##name(const YGNodeRef node);
-
-#define YG_NODE_STYLE_PROPERTY(type, name, paramName) \
-  WIN_EXPORT void YGNodeStyleSet##name(               \
-      const YGNodeRef node, const type paramName);    \
-  WIN_EXPORT type YGNodeStyleGet##name(const YGNodeRef node);
-
-#define YG_NODE_STYLE_PROPERTY_UNIT(type, name, paramName) \
-  WIN_EXPORT void YGNodeStyleSet##name(                    \
-      const YGNodeRef node, const float paramName);        \
-  WIN_EXPORT void YGNodeStyleSet##name##Percent(           \
-      const YGNodeRef node, const float paramName);        \
-  WIN_EXPORT type YGNodeStyleGet##name(const YGNodeRef node);
-
-#define YG_NODE_STYLE_PROPERTY_UNIT_AUTO(type, name, paramName) \
-  YG_NODE_STYLE_PROPERTY_UNIT(type, name, paramName)            \
-  WIN_EXPORT void YGNodeStyleSet##name##Auto(const YGNodeRef node);
-
-#define YG_NODE_STYLE_EDGE_PROPERTY(type, name, paramName)            \
-  WIN_EXPORT void YGNodeStyleSet##name(                               \
-      const YGNodeRef node, const YGEdge edge, const type paramName); \
-  WIN_EXPORT type YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge);
-
-#define YG_NODE_STYLE_EDGE_PROPERTY_UNIT(type, name, paramName)        \
-  WIN_EXPORT void YGNodeStyleSet##name(                                \
-      const YGNodeRef node, const YGEdge edge, const float paramName); \
-  WIN_EXPORT void YGNodeStyleSet##name##Percent(                       \
-      const YGNodeRef node, const YGEdge edge, const float paramName); \
-  WIN_EXPORT WIN_STRUCT(type)                                          \
-      YGNodeStyleGet##name(const YGNodeRef node, const YGEdge edge);
-
-#define YG_NODE_STYLE_EDGE_PROPERTY_UNIT_AUTO(type, name) \
-  WIN_EXPORT void YGNodeStyleSet##name##Auto(             \
-      const YGNodeRef node, const YGEdge edge);
-
-#define YG_NODE_LAYOUT_PROPERTY(type, name) \
-  WIN_EXPORT type YGNodeLayoutGet##name(const YGNodeRef node);
-
-#define YG_NODE_LAYOUT_EDGE_PROPERTY(type, name) \
-  WIN_EXPORT type YGNodeLayoutGet##name(         \
-      const YGNodeRef node, const YGEdge edge);
-
 void* YGNodeGetContext(YGNodeRef node);
 void YGNodeSetContext(YGNodeRef node, void* context);
 YGMeasureFunc YGNodeGetMeasureFunc(YGNodeRef node);
@@ -207,33 +163,165 @@ void YGNodeSetNodeType(YGNodeRef node, YGNodeType nodeType);
 bool YGNodeIsDirty(YGNodeRef node);
 bool YGNodeLayoutGetDidUseLegacyFlag(const YGNodeRef node);
 
-YG_NODE_STYLE_PROPERTY(YGDirection, Direction, direction);
-YG_NODE_STYLE_PROPERTY(YGFlexDirection, FlexDirection, flexDirection);
-YG_NODE_STYLE_PROPERTY(YGJustify, JustifyContent, justifyContent);
-YG_NODE_STYLE_PROPERTY(YGAlign, AlignContent, alignContent);
-YG_NODE_STYLE_PROPERTY(YGAlign, AlignItems, alignItems);
-YG_NODE_STYLE_PROPERTY(YGAlign, AlignSelf, alignSelf);
-YG_NODE_STYLE_PROPERTY(YGPositionType, PositionType, positionType);
-YG_NODE_STYLE_PROPERTY(YGWrap, FlexWrap, flexWrap);
-YG_NODE_STYLE_PROPERTY(YGOverflow, Overflow, overflow);
-YG_NODE_STYLE_PROPERTY(YGDisplay, Display, display);
-YG_NODE_STYLE_PROPERTY(float, Flex, flex);
-YG_NODE_STYLE_PROPERTY(float, FlexGrow, flexGrow);
-YG_NODE_STYLE_PROPERTY(float, FlexShrink, flexShrink);
-YG_NODE_STYLE_PROPERTY_UNIT_AUTO(YGValue, FlexBasis, flexBasis);
-
-YG_NODE_STYLE_EDGE_PROPERTY_UNIT(YGValue, Position, position);
-YG_NODE_STYLE_EDGE_PROPERTY_UNIT(YGValue, Margin, margin);
-YG_NODE_STYLE_EDGE_PROPERTY_UNIT_AUTO(YGValue, Margin);
-YG_NODE_STYLE_EDGE_PROPERTY_UNIT(YGValue, Padding, padding);
-YG_NODE_STYLE_EDGE_PROPERTY(float, Border, border);
-
-YG_NODE_STYLE_PROPERTY_UNIT_AUTO(YGValue, Width, width);
-YG_NODE_STYLE_PROPERTY_UNIT_AUTO(YGValue, Height, height);
-YG_NODE_STYLE_PROPERTY_UNIT(YGValue, MinWidth, minWidth);
-YG_NODE_STYLE_PROPERTY_UNIT(YGValue, MinHeight, minHeight);
-YG_NODE_STYLE_PROPERTY_UNIT(YGValue, MaxWidth, maxWidth);
-YG_NODE_STYLE_PROPERTY_UNIT(YGValue, MaxHeight, maxHeight);
+WIN_EXPORT void YGNodeStyleSetDirection(
+    const YGNodeRef node,
+    const YGDirection direction);
+WIN_EXPORT YGDirection YGNodeStyleGetDirection(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetFlexDirection(
+    const YGNodeRef node,
+    const YGFlexDirection flexDirection);
+WIN_EXPORT YGFlexDirection YGNodeStyleGetFlexDirection(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetJustifyContent(
+    const YGNodeRef node,
+    const YGJustify justifyContent);
+WIN_EXPORT YGJustify YGNodeStyleGetJustifyContent(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetAlignContent(
+    const YGNodeRef node,
+    const YGAlign alignContent);
+WIN_EXPORT YGAlign YGNodeStyleGetAlignContent(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetAlignItems(
+    const YGNodeRef node,
+    const YGAlign alignItems);
+WIN_EXPORT YGAlign YGNodeStyleGetAlignItems(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetAlignSelf(
+    const YGNodeRef node,
+    const YGAlign alignSelf);
+WIN_EXPORT YGAlign YGNodeStyleGetAlignSelf(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetPositionType(
+    const YGNodeRef node,
+    const YGPositionType positionType);
+WIN_EXPORT YGPositionType YGNodeStyleGetPositionType(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetFlexWrap(
+    const YGNodeRef node,
+    const YGWrap flexWrap);
+WIN_EXPORT YGWrap YGNodeStyleGetFlexWrap(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetOverflow(
+    const YGNodeRef node,
+    const YGOverflow overflow);
+WIN_EXPORT YGOverflow YGNodeStyleGetOverflow(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetDisplay(
+    const YGNodeRef node,
+    const YGDisplay display);
+WIN_EXPORT YGDisplay YGNodeStyleGetDisplay(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetFlex(const YGNodeRef node, const float flex);
+WIN_EXPORT float YGNodeStyleGetFlex(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetFlexGrow(
+    const YGNodeRef node,
+    const float flexGrow);
+WIN_EXPORT float YGNodeStyleGetFlexGrow(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetFlexShrink(
+    const YGNodeRef node,
+    const float flexShrink);
+WIN_EXPORT float YGNodeStyleGetFlexShrink(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetFlexBasis(
+    const YGNodeRef node,
+    const float flexBasis);
+WIN_EXPORT void YGNodeStyleSetFlexBasisPercent(
+    const YGNodeRef node,
+    const float flexBasis);
+WIN_EXPORT void YGNodeStyleSetFlexBasisAuto(const YGNodeRef node);
+WIN_EXPORT YGValue YGNodeStyleGetFlexBasis(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetPosition(
+    const YGNodeRef node,
+    const YGEdge edge,
+    const float position);
+WIN_EXPORT void YGNodeStyleSetPositionPercent(
+    const YGNodeRef node,
+    const YGEdge edge,
+    const float position);
+WIN_EXPORT WIN_STRUCT(YGValue)
+    YGNodeStyleGetPosition(const YGNodeRef node, const YGEdge edge);
+
+WIN_EXPORT void YGNodeStyleSetMargin(
+    const YGNodeRef node,
+    const YGEdge edge,
+    const float margin);
+WIN_EXPORT void YGNodeStyleSetMarginPercent(
+    const YGNodeRef node,
+    const YGEdge edge,
+    const float margin);
+WIN_EXPORT void YGNodeStyleSetMarginAuto(
+    const YGNodeRef node,
+    const YGEdge edge);
+WIN_EXPORT YGValue
+YGNodeStyleGetMargin(const YGNodeRef node, const YGEdge edge);
+
+WIN_EXPORT void YGNodeStyleSetPadding(
+    const YGNodeRef node,
+    const YGEdge edge,
+    const float padding);
+WIN_EXPORT void YGNodeStyleSetPaddingPercent(
+    const YGNodeRef node,
+    const YGEdge edge,
+    const float padding);
+WIN_EXPORT YGValue
+YGNodeStyleGetPadding(const YGNodeRef node, const YGEdge edge);
+
+WIN_EXPORT void YGNodeStyleSetBorder(
+    const YGNodeRef node,
+    const YGEdge edge,
+    const float border);
+WIN_EXPORT float YGNodeStyleGetBorder(const YGNodeRef node, const YGEdge edge);
+
+WIN_EXPORT void YGNodeStyleSetWidth(const YGNodeRef node, const float width);
+WIN_EXPORT void YGNodeStyleSetWidthPercent(
+    const YGNodeRef node,
+    const float width);
+WIN_EXPORT void YGNodeStyleSetWidthAuto(const YGNodeRef node);
+WIN_EXPORT YGValue YGNodeStyleGetWidth(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetHeight(const YGNodeRef node, const float height);
+WIN_EXPORT void YGNodeStyleSetHeightPercent(
+    const YGNodeRef node,
+    const float height);
+WIN_EXPORT void YGNodeStyleSetHeightAuto(const YGNodeRef node);
+WIN_EXPORT YGValue YGNodeStyleGetHeight(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetMinWidth(
+    const YGNodeRef node,
+    const float minWidth);
+WIN_EXPORT void YGNodeStyleSetMinWidthPercent(
+    const YGNodeRef node,
+    const float minWidth);
+WIN_EXPORT YGValue YGNodeStyleGetMinWidth(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetMinHeight(
+    const YGNodeRef node,
+    const float minHeight);
+WIN_EXPORT void YGNodeStyleSetMinHeightPercent(
+    const YGNodeRef node,
+    const float minHeight);
+WIN_EXPORT YGValue YGNodeStyleGetMinHeight(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetMaxWidth(
+    const YGNodeRef node,
+    const float maxWidth);
+WIN_EXPORT void YGNodeStyleSetMaxWidthPercent(
+    const YGNodeRef node,
+    const float maxWidth);
+WIN_EXPORT YGValue YGNodeStyleGetMaxWidth(const YGNodeRef node);
+
+WIN_EXPORT void YGNodeStyleSetMaxHeight(
+    const YGNodeRef node,
+    const float maxHeight);
+WIN_EXPORT void YGNodeStyleSetMaxHeightPercent(
+    const YGNodeRef node,
+    const float maxHeight);
+WIN_EXPORT YGValue YGNodeStyleGetMaxHeight(const YGNodeRef node);
 
 // Yoga specific properties, not compatible with flexbox specification
 // Aspect ratio control the size of the undefined dimension of a node.
@@ -250,25 +338,30 @@ YG_NODE_STYLE_PROPERTY_UNIT(YGValue, MaxHeight, maxHeight);
 // - On a node with flex grow/shrink aspect ratio controls the size of the node
 // in the cross axis if unset
 // - Aspect ratio takes min/max dimensions into account
-YG_NODE_STYLE_PROPERTY(float, AspectRatio, aspectRatio);
-
-YG_NODE_LAYOUT_PROPERTY(float, Left);
-YG_NODE_LAYOUT_PROPERTY(float, Top);
-YG_NODE_LAYOUT_PROPERTY(float, Right);
-YG_NODE_LAYOUT_PROPERTY(float, Bottom);
-YG_NODE_LAYOUT_PROPERTY(float, Width);
-YG_NODE_LAYOUT_PROPERTY(float, Height);
-YG_NODE_LAYOUT_PROPERTY(YGDirection, Direction);
-YG_NODE_LAYOUT_PROPERTY(bool, HadOverflow);
+WIN_EXPORT void YGNodeStyleSetAspectRatio(
+    const YGNodeRef node,
+    const float aspectRatio);
+WIN_EXPORT float YGNodeStyleGetAspectRatio(const YGNodeRef node);
+
+WIN_EXPORT float YGNodeLayoutGetLeft(const YGNodeRef node);
+WIN_EXPORT float YGNodeLayoutGetTop(const YGNodeRef node);
+WIN_EXPORT float YGNodeLayoutGetRight(const YGNodeRef node);
+WIN_EXPORT float YGNodeLayoutGetBottom(const YGNodeRef node);
+WIN_EXPORT float YGNodeLayoutGetWidth(const YGNodeRef node);
+WIN_EXPORT float YGNodeLayoutGetHeight(const YGNodeRef node);
+WIN_EXPORT YGDirection YGNodeLayoutGetDirection(const YGNodeRef node);
+WIN_EXPORT bool YGNodeLayoutGetHadOverflow(const YGNodeRef node);
 bool YGNodeLayoutGetDidLegacyStretchFlagAffectLayout(const YGNodeRef node);
 
 // Get the computed values for these nodes after performing layout. If they were
 // set using point values then the returned value will be the same as
 // YGNodeStyleGetXXX. However if they were set using a percentage value then the
 // returned value is the computed value used during layout.
-YG_NODE_LAYOUT_EDGE_PROPERTY(float, Margin);
-YG_NODE_LAYOUT_EDGE_PROPERTY(float, Border);
-YG_NODE_LAYOUT_EDGE_PROPERTY(float, Padding);
+WIN_EXPORT float YGNodeLayoutGetMargin(const YGNodeRef node, const YGEdge edge);
+WIN_EXPORT float YGNodeLayoutGetBorder(const YGNodeRef node, const YGEdge edge);
+WIN_EXPORT float YGNodeLayoutGetPadding(
+    const YGNodeRef node,
+    const YGEdge edge);
 
 WIN_EXPORT void YGConfigSetLogger(const YGConfigRef config, YGLogger logger);
 WIN_EXPORT void

From 709e3bc1fef2c6863ef18a9141dea329d22e2bb0 Mon Sep 17 00:00:00 2001
From: David Aurelio <davidaurelio@fb.com>
Date: Thu, 19 Jul 2018 09:57:08 -0700
Subject: [PATCH 1094/1109] Replace `YG_NODE_STYLE_PROPERTY_IMPL` macro with
 template

Summary:
@public

Replacing the `YG_NODE_STYLE_PROPERTY_IMPL` macro with template code, in order to make code easier to edit and grep.

Reviewed By: astreet

Differential Revision: D8868184

fbshipit-source-id: f52537376fa8d4dd53aa98bb43e93279699dbdd5
---
 ReactCommon/yoga/yoga/Yoga.cpp | 139 +++++++++++++++++++++++----------
 1 file changed, 96 insertions(+), 43 deletions(-)

diff --git a/ReactCommon/yoga/yoga/Yoga.cpp b/ReactCommon/yoga/yoga/Yoga.cpp
index c9404dec4da6..c9799c3ccd55 100644
--- a/ReactCommon/yoga/yoga/Yoga.cpp
+++ b/ReactCommon/yoga/yoga/Yoga.cpp
@@ -576,16 +576,24 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
       : node->getStyle().flexShrink.getValue();
 }
 
-#define YG_NODE_STYLE_PROPERTY_SETTER_IMPL(                               \
-    type, name, paramName, instanceName)                                  \
-  void YGNodeStyleSet##name(const YGNodeRef node, const type paramName) { \
-    if (node->getStyle().instanceName != paramName) {                     \
-      YGStyle style = node->getStyle();                                   \
-      style.instanceName = paramName;                                     \
-      node->setStyle(style);                                              \
-      node->markDirtyAndPropogate();                                      \
-    }                                                                     \
+namespace {
+
+template <typename T, T YGStyle::*P>
+struct StyleProp {
+  static T get(YGNodeRef node) {
+    return node->getStyle().*P;
+  }
+  static void set(YGNodeRef node, T newValue) {
+    if (node->getStyle().*P != newValue) {
+      YGStyle style = node->getStyle();
+      style.*P = newValue;
+      node->setStyle(style);
+      node->markDirtyAndPropogate();
+    }
   }
+};
+
+} // namespace
 
 #define YG_NODE_STYLE_PROPERTY_SETTER_UNIT_IMPL(                          \
     type, name, paramName, instanceName)                                  \
@@ -661,13 +669,6 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
     }                                                                        \
   }
 
-#define YG_NODE_STYLE_PROPERTY_IMPL(type, name, paramName, instanceName)  \
-  YG_NODE_STYLE_PROPERTY_SETTER_IMPL(type, name, paramName, instanceName) \
-                                                                          \
-  type YGNodeStyleGet##name(const YGNodeRef node) {                       \
-    return node->getStyle().instanceName;                                 \
-  }
-
 #define YG_NODE_STYLE_PROPERTY_UNIT_IMPL(type, name, paramName, instanceName) \
   YG_NODE_STYLE_PROPERTY_SETTER_UNIT_IMPL(                                    \
       float, name, paramName, instanceName)                                   \
@@ -778,33 +779,85 @@ float YGNodeStyleGetFlexShrink(const YGNodeRef node) {
     return node->getLayout().instanceName[edge];                        \
   }
 
-// YG_NODE_PROPERTY_IMPL(void *, Context, context, context);
-// YG_NODE_PROPERTY_IMPL(YGPrintFunc, PrintFunc, printFunc, print);
-// YG_NODE_PROPERTY_IMPL(bool, HasNewLayout, hasNewLayout, hasNewLayout);
-// YG_NODE_PROPERTY_IMPL(YGNodeType, NodeType, nodeType, nodeType);
-
-YG_NODE_STYLE_PROPERTY_IMPL(YGDirection, Direction, direction, direction);
-YG_NODE_STYLE_PROPERTY_IMPL(
-    YGFlexDirection,
-    FlexDirection,
-    flexDirection,
-    flexDirection);
-YG_NODE_STYLE_PROPERTY_IMPL(
-    YGJustify,
-    JustifyContent,
-    justifyContent,
-    justifyContent);
-YG_NODE_STYLE_PROPERTY_IMPL(YGAlign, AlignContent, alignContent, alignContent);
-YG_NODE_STYLE_PROPERTY_IMPL(YGAlign, AlignItems, alignItems, alignItems);
-YG_NODE_STYLE_PROPERTY_IMPL(YGAlign, AlignSelf, alignSelf, alignSelf);
-YG_NODE_STYLE_PROPERTY_IMPL(
-    YGPositionType,
-    PositionType,
-    positionType,
-    positionType);
-YG_NODE_STYLE_PROPERTY_IMPL(YGWrap, FlexWrap, flexWrap, flexWrap);
-YG_NODE_STYLE_PROPERTY_IMPL(YGOverflow, Overflow, overflow, overflow);
-YG_NODE_STYLE_PROPERTY_IMPL(YGDisplay, Display, display, display);
+void YGNodeStyleSetDirection(
+    const YGNodeRef node,
+    const YGDirection direction) {
+  StyleProp<YGDirection, &YGStyle::direction>::set(node, direction);
+}
+YGDirection YGNodeStyleGetDirection(const YGNodeRef node) {
+  return StyleProp<YGDirection, &YGStyle::direction>::get(node);
+}
+
+void YGNodeStyleSetFlexDirection(
+    const YGNodeRef node,
+    const YGFlexDirection flexDirection) {
+  StyleProp<YGFlexDirection, &YGStyle::flexDirection>::set(node, flexDirection);
+}
+YGFlexDirection YGNodeStyleGetFlexDirection(const YGNodeRef node) {
+  return StyleProp<YGFlexDirection, &YGStyle::flexDirection>::get(node);
+}
+
+void YGNodeStyleSetJustifyContent(
+    const YGNodeRef node,
+    const YGJustify justifyContent) {
+  StyleProp<YGJustify, &YGStyle::justifyContent>::set(node, justifyContent);
+}
+YGJustify YGNodeStyleGetJustifyContent(const YGNodeRef node) {
+  return StyleProp<YGJustify, &YGStyle::justifyContent>::get(node);
+}
+
+void YGNodeStyleSetAlignContent(
+    const YGNodeRef node,
+    const YGAlign alignContent) {
+  StyleProp<YGAlign, &YGStyle::alignContent>::set(node, alignContent);
+}
+YGAlign YGNodeStyleGetAlignContent(const YGNodeRef node) {
+  return StyleProp<YGAlign, &YGStyle::alignContent>::get(node);
+}
+
+void YGNodeStyleSetAlignItems(const YGNodeRef node, const YGAlign alignItems) {
+  StyleProp<YGAlign, &YGStyle::alignItems>::set(node, alignItems);
+}
+YGAlign YGNodeStyleGetAlignItems(const YGNodeRef node) {
+  return StyleProp<YGAlign, &YGStyle::alignItems>::get(node);
+}
+
+void YGNodeStyleSetAlignSelf(const YGNodeRef node, const YGAlign alignSelf) {
+  StyleProp<YGAlign, &YGStyle::alignSelf>::set(node, alignSelf);
+}
+YGAlign YGNodeStyleGetAlignSelf(const YGNodeRef node) {
+  return StyleProp<YGAlign, &YGStyle::alignSelf>::get(node);
+}
+
+void YGNodeStyleSetPositionType(
+    const YGNodeRef node,
+    const YGPositionType positionType) {
+  StyleProp<YGPositionType, &YGStyle::positionType>::set(node, positionType);
+}
+YGPositionType YGNodeStyleGetPositionType(const YGNodeRef node) {
+  return StyleProp<YGPositionType, &YGStyle::positionType>::get(node);
+}
+
+void YGNodeStyleSetFlexWrap(const YGNodeRef node, const YGWrap flexWrap) {
+  StyleProp<YGWrap, &YGStyle::flexWrap>::set(node, flexWrap);
+}
+YGWrap YGNodeStyleGetFlexWrap(const YGNodeRef node) {
+  return StyleProp<YGWrap, &YGStyle::flexWrap>::get(node);
+}
+
+void YGNodeStyleSetOverflow(const YGNodeRef node, const YGOverflow overflow) {
+  StyleProp<YGOverflow, &YGStyle::overflow>::set(node, overflow);
+}
+YGOverflow YGNodeStyleGetOverflow(const YGNodeRef node) {
+  return StyleProp<YGOverflow, &YGStyle::overflow>::get(node);
+}
+
+void YGNodeStyleSetDisplay(const YGNodeRef node, const YGDisplay display) {
+  StyleProp<YGDisplay, &YGStyle::display>::set(node, display);
+}
+YGDisplay YGNodeStyleGetDisplay(const YGNodeRef node) {
+  return StyleProp<YGDisplay, &YGStyle::display>::get(node);
+}
 
 // TODO(T26792433): Change the API to accept YGFloatOptional.
 void YGNodeStyleSetFlex(const YGNodeRef node, const float flex) {

From 03036f79f7b062ae11015b33cca3dd7e4e67dda6 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 19 Jul 2018 13:47:39 -0700
Subject: [PATCH 1095/1109] Changed prop name "currentViewStates" to
 "accessibilityStates" in js (1/3)

Summary:
Context:
After discussing with @[1038750002:yungsters], `currentViewStates` is a very ambiguous name for a prop, especially because there are only two possible values. From a developer's perspective, it makes more sense to just call them `accessibilityStates` because the main use for them is to add states to Talkback and Voiceover.
Also, the actual implementation of what we're changing under the hood in Native Code is abstracted away from developers using React Native, so as long as behavior is as they would expect, it makes more sense to change the name into a clear one.

Changes in this Diff:
Changed the prop name `currentViewStates` to `accessibilityStates` in js files

Reviewed By: PeteTheHeat

Differential Revision: D8896223

fbshipit-source-id: dfdb48dce69303a347dfccd194af2fef9beb776c
---
 Libraries/Components/View/ViewAccessibility.js | 10 +++++-----
 Libraries/Components/View/ViewPropTypes.js     |  8 ++++----
 2 files changed, 9 insertions(+), 9 deletions(-)

diff --git a/Libraries/Components/View/ViewAccessibility.js b/Libraries/Components/View/ViewAccessibility.js
index 0deca1586012..c3512c42c4eb 100644
--- a/Libraries/Components/View/ViewAccessibility.js
+++ b/Libraries/Components/View/ViewAccessibility.js
@@ -52,11 +52,11 @@ export type AccessibilityRole =
   | 'header'
   | 'summary';
 
-export type CurrentViewState = 'selected' | 'disabled';
+export type AccessibilityState = 'selected' | 'disabled';
 
-export type CurrentViewStates =
-  | CurrentViewState
-  | $ReadOnlyArray<CurrentViewState>;
+export type AccessibilityStates =
+  | AccessibilityState
+  | $ReadOnlyArray<AccessibilityState>;
 
 module.exports = {
   AccessibilityTraits: [
@@ -97,5 +97,5 @@ module.exports = {
     'header',
     'summary',
   ],
-  CurrentViewStates: ['selected', 'disabled'],
+  AccessibilityStates: ['selected', 'disabled'],
 };
diff --git a/Libraries/Components/View/ViewPropTypes.js b/Libraries/Components/View/ViewPropTypes.js
index 1e0f328d99ad..de47f360030d 100644
--- a/Libraries/Components/View/ViewPropTypes.js
+++ b/Libraries/Components/View/ViewPropTypes.js
@@ -21,14 +21,14 @@ const {
   AccessibilityComponentTypes,
   AccessibilityTraits,
   AccessibilityRoles,
-  CurrentViewStates,
+  AccessibilityStates,
 } = require('ViewAccessibility');
 
 import type {
   AccessibilityComponentType,
   AccessibilityTrait,
   AccessibilityRole,
-  CurrentViewState,
+  AccessibilityState,
 } from 'ViewAccessibility';
 import type {EdgeInsetsProp} from 'EdgeInsetsPropType';
 import type {TVViewProps} from 'TVViewPropTypes';
@@ -94,7 +94,7 @@ export type ViewProps = $ReadOnly<{|
   accessibilityIgnoresInvertColors?: boolean,
   accessibilityTraits?: AccessibilityTrait | Array<AccessibilityTrait>,
   accessibilityRole?: AccessibilityRole,
-  currentViewStates?: Array<CurrentViewState>,
+  accessibilityStates?: Array<AccessibilityState>,
   accessibilityViewIsModal?: boolean,
   accessibilityElementsHidden?: boolean,
   children?: ?React.Node,
@@ -153,7 +153,7 @@ module.exports = {
   /**
    * Indicates to accessibility services that UI Component is in a specific State.
    */
-  currentViewStates: PropTypes.arrayOf(PropTypes.oneOf(CurrentViewStates)),
+  accessibilityStates: PropTypes.arrayOf(PropTypes.oneOf(AccessibilityStates)),
   /**
    * Indicates to accessibility services whether the user should be notified
    * when this view changes. Works for Android API >= 19 only.

From 3bedc78a35b9efc259299744f4134ac0e880d1ea Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 19 Jul 2018 13:47:41 -0700
Subject: [PATCH 1096/1109] Changed prop name "currentViewStates" to
 "accessibilityStates" in Android (2/3)

Summary:
Context:
After discussing with @[1038750002:yungsters], `currentViewStates` is a very ambiguous name for a prop, especially because there are only two possible values. From a developer's perspective, it makes more sense to just call them `accessibilityStates` because the main use for them is to add states to Talkback and Voiceover.
Defense for changing name in Android: The actual implementation of what we're changing under the hood in Native Code is abstracted away from developers using React Native, so as long as behavior is as they would expect, it makes more sense to change the name into a clear one regardless of how it is implemented.

Changes:
changed the Prop name from `currentViewStates` to `accessibilityStates` in the BaseViewManager file where the view property is being exposed.

Reviewed By: PeteTheHeat

Differential Revision: D8896389

fbshipit-source-id: 35dcd9239fae016b790e528947994681684bd654
---
 .../com/facebook/react/uimanager/BaseViewManager.java  | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
index 1aa6882b3d38..fe13dd51f911 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java
@@ -30,7 +30,7 @@ public abstract class BaseViewManager<T extends View, C extends LayoutShadowNode
   private static final String PROP_ACCESSIBILITY_COMPONENT_TYPE = "accessibilityComponentType";
   private static final String PROP_ACCESSIBILITY_LIVE_REGION = "accessibilityLiveRegion";
   private static final String PROP_ACCESSIBILITY_ROLE = "accessibilityRole";
-  private static final String PROP_CURRENT_VIEW_STATES = "currentViewStates";
+  private static final String PROP_ACCESSIBILITY_STATES = "accessibilityStates";
   private static final String PROP_IMPORTANT_FOR_ACCESSIBILITY = "importantForAccessibility";
 
   // DEPRECATED
@@ -124,12 +124,12 @@ public void setAccessibilityRole(T view, String accessibilityRole) {
     AccessibilityRoleUtil.updateAccessibilityRole(view, accessibilityRole);
   }
 
-  @ReactProp(name = PROP_CURRENT_VIEW_STATES)
-  public void setViewStates(T view, ReadableArray currentViewStates) {
+  @ReactProp(name = PROP_ACCESSIBILITY_STATES)
+  public void setViewStates(T view, ReadableArray accessibilityStates) {
     view.setSelected(false);
     view.setEnabled(true);
-    for (int i = 0; i < currentViewStates.size(); i++) {
-      String state = currentViewStates.getString(i);
+    for (int i = 0; i < accessibilityStates.size(); i++) {
+      String state = accessibilityStates.getString(i);
       if (state.equals("selected")) {
         view.setSelected(true);
       } else if (state.equals("disabled")) {

From ca01290d8e8fe73494f317ed9f81d339e65fdea0 Mon Sep 17 00:00:00 2001
From: Ziqi Chen <ziqichen@fb.com>
Date: Thu, 19 Jul 2018 13:47:43 -0700
Subject: [PATCH 1097/1109] changed prop name currentViewStates to
 AccessibilityStates on iOS (3/3)

Summary:
Context:
After discussing with yungsters, `currentViewStates` is a very ambiguous name for a prop, especially because there are only two possible values. From a developer's perspective, it makes more sense to just call them `accessibilityStates` because the main use for them is to add states to Talkback and Voiceover.
Also, the actual implementation of what we're changing under the hood in Native Code is abstracted away from developers using React Native, so as long as behavior is as they would expect, it makes more sense to change the name into a clear one.

Changes in this Diff:
Renamed the view property exposed to native iOS code from `currentViewStates`  to `accessibilityStates`
Also deleted setting the userInteractionEnabled view property, because we want to keep it as just an accessibility property.

Reviewed By: PeteTheHeat

Differential Revision: D8896821

fbshipit-source-id: 95674c9b7295f5b9e60994c297acdee83f6226d7
---
 React/Views/RCTViewManager.m | 9 ++-------
 1 file changed, 2 insertions(+), 7 deletions(-)

diff --git a/React/Views/RCTViewManager.m b/React/Views/RCTViewManager.m
index 29767a90e312..c0cba4611883 100644
--- a/React/Views/RCTViewManager.m
+++ b/React/Views/RCTViewManager.m
@@ -153,14 +153,9 @@ - (RCTShadowView *)shadowView
     view.reactAccessibilityElement.accessibilityTraits |= json ? [RCTConvert UIAccessibilityTraits:json] : defaultView.accessibilityTraits;
 }
 
-RCT_CUSTOM_VIEW_PROPERTY(currentViewStates, UIAccessibilityTraits, RCTView)
+RCT_CUSTOM_VIEW_PROPERTY(accessibilityStates, UIAccessibilityTraits, RCTView)
 {
-    UIAccessibilityTraits traits = json ? [RCTConvert UIAccessibilityTraits:json] : defaultView.accessibilityTraits;
-    view.reactAccessibilityElement.accessibilityTraits |= traits;
-    if (traits == UIAccessibilityTraitNotEnabled || traits == (UIAccessibilityTraitNotEnabled | UIAccessibilityTraitSelected))
-    {
-        view.userInteractionEnabled = NO;
-    } 
+    view.reactAccessibilityElement.accessibilityTraits |= json ? [RCTConvert UIAccessibilityTraits:json] : defaultView.accessibilityTraits;
 }
 
 RCT_CUSTOM_VIEW_PROPERTY(pointerEvents, RCTPointerEvents, RCTView)

From 1b2a5529558c13c257c9f371f945ef10f700d162 Mon Sep 17 00:00:00 2001
From: gengjiawen <technicalcute@gmail.com>
Date: Thu, 19 Jul 2018 15:53:08 -0700
Subject: [PATCH 1098/1109] add windows ci (#20281)

Summary:
[![Build status](https://ci.appveyor.com/api/projects/status/79bl3twr4palqmra/branch/feature/appveyor?svg=true)](https://ci.appveyor.com/project/gengjiawen/react-native/branch/master)
Add windows ci
pass all current ci.
none
 [GENERAL] [INTERNAL] [CI] - add windows ci
Pull Request resolved: https://github.com/facebook/react-native/pull/20281

Differential Revision: D8924625

Pulled By: hramos

fbshipit-source-id: 6b933a8affe7c131c0fd02694f6177885a196611
---
 README.md    |  2 +-
 appveyor.yml | 42 ++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 43 insertions(+), 1 deletion(-)
 create mode 100644 appveyor.yml

diff --git a/README.md b/README.md
index a9c12562f1a6..7823b332a12a 100644
--- a/README.md
+++ b/README.md
@@ -1,4 +1,4 @@
-# [React Native](https://facebook.github.io/react-native/) &middot;  [![Circle CI Status](https://circleci.com/gh/facebook/react-native.svg?style=shield)](https://circleci.com/gh/facebook/react-native) [![npm version](https://badge.fury.io/js/react-native.svg)](https://badge.fury.io/js/react-native) [![PRs Welcome](https://img.shields.io/badge/PRs-welcome-brightgreen.svg)](CONTRIBUTING.md#pull-requests)
+# [React Native](https://facebook.github.io/react-native/) &middot;  [![Circle CI Status](https://circleci.com/gh/facebook/react-native.svg?style=shield)](https://circleci.com/gh/facebook/react-native) [![Build status](https://ci.appveyor.com/api/projects/status/github/facebook/react-native?branch=master&svg=true)](https://ci.appveyor.com/project/facebok/react-native/branch/master) [![npm version](https://badge.fury.io/js/react-native.svg)](https://badge.fury.io/js/react-native) [![PRs Welcome](https://img.shields.io/badge/PRs-welcome-brightgreen.svg)](CONTRIBUTING.md#pull-requests)
 
 Learn once, write anywhere: Build mobile apps with React.
 
diff --git a/appveyor.yml b/appveyor.yml
new file mode 100644
index 000000000000..78559d09c3e0
--- /dev/null
+++ b/appveyor.yml
@@ -0,0 +1,42 @@
+environment:
+    ANDROID_HOME: "C:\\android-sdk-windows"
+    ANDROID_NDK: "C:\\android-sdk-windows\\android-ndk-r10e"
+    ANDROID_BUILD_VERSION: 26
+    ANDROID_TOOLS_VERSION: 26.0.3
+
+    GRADLE_OPTS: -Dorg.gradle.daemon=false
+
+    SDK_TOOLS_URL: https://dl.google.com/android/repository/sdk-tools-windows-3859397.zip
+    NDK_TOOLS_URL: https://dl.google.com/android/repository/android-ndk-r10e-windows-x86_64.zip
+
+    matrix:
+        - nodejs_version: 8
+        - nodejs_version: 10
+
+install:
+    # Install Android SDK Tools
+    - mkdir "%ANDROID_HOME%"
+    - appveyor DownloadFile "%SDK_TOOLS_URL%" -FileName "%TMP%/sdk-tools.zip"
+    - 7z x "%TMP%/sdk-tools.zip" -o"%ANDROID_HOME%" > nul
+    - set PATH=%PATH%;"%ANDROID_HOME%\tools\bin"
+
+    - yes 2> nul | sdkmanager --licenses > nul
+    - sdkmanager "system-images;android-19;google_apis;armeabi-v7a"
+    - sdkmanager "platforms;android-%ANDROID_BUILD_VERSION%"
+    - sdkmanager  "build-tools;%ANDROID_TOOLS_VERSION%"
+    - sdkmanager "add-ons;addon-google_apis-google-23"
+    - sdkmanager "extras;android;m2repository"
+
+    - appveyor DownloadFile "%NDK_TOOLS_URL%" -FileName "%TMP%/ndk.zip"
+    - 7z x "%TMP%/ndk.zip" -o"%ANDROID_HOME%" > nul
+
+    - ps: Install-Product node $env:nodejs_version
+    - node --version
+    - npm --version
+    - appveyor-retry npm install
+
+build_script:
+  - gradlew.bat RNTester:android:app:assembleRelease
+
+test_script:
+    - npm test

From de573277bf64703aefdeb52db2c2524b2c241bab Mon Sep 17 00:00:00 2001
From: Jiaqi Wu <jiaqiwu@fb.com>
Date: Thu, 19 Jul 2018 17:00:46 -0700
Subject: [PATCH 1099/1109] Fix Horizontal ScrollView's scroll position during
 layout changes

Summary: Fix the calculation of offsetX in onLayout (ReactHorizontalScrollContainerView.java) that re-positions the updated layout. A private instance variable (oldWidth) is added in order to track the width difference between consecutive updates. (Issue report: https://github.com/facebook/react-native/issues/19979)

Reviewed By: mdvacca

Differential Revision: D8772780

fbshipit-source-id: 969dcead550f4a3d24d06416b63d960492b7a124
---
 .../views/scroll/ReactHorizontalScrollContainerView.java  | 8 +++++---
 1 file changed, 5 insertions(+), 3 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java
index bcda656077c6..e23e53305a90 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollContainerView.java
@@ -14,11 +14,13 @@
 public class ReactHorizontalScrollContainerView extends ViewGroup {
 
   private int mLayoutDirection;
+  private int mCurrentWidth;
 
   public ReactHorizontalScrollContainerView(Context context) {
     super(context);
     mLayoutDirection =
         I18nUtil.getInstance().isRTL(context) ? LAYOUT_DIRECTION_RTL : LAYOUT_DIRECTION_LTR;
+    mCurrentWidth = 0;
   }
 
   @Override
@@ -32,12 +34,12 @@ protected void onLayout(boolean changed, int left, int top, int right, int botto
       setLeft(newLeft);
       setRight(newRight);
 
-      // Fix the ScrollX position when using RTL language
-      int offsetX = computeHorizontalScrollRange() - getScrollX();
-
       // Call with the present values in order to re-layout if necessary
       HorizontalScrollView parent = (HorizontalScrollView) getParent();
+      // Fix the ScrollX position when using RTL language
+      int offsetX = parent.getScrollX() + getWidth() - mCurrentWidth;
       parent.scrollTo(offsetX, parent.getScrollY());
     }
+    mCurrentWidth = getWidth();
   }
 }

From 86f24ccf71f4c41904838c8c7e13268c300fd745 Mon Sep 17 00:00:00 2001
From: Jiaqi Wu <jiaqiwu@fb.com>
Date: Thu, 19 Jul 2018 17:06:14 -0700
Subject: [PATCH 1100/1109] Fix placeholder clipping issue

Summary:
Problem: The first ReactTextInputShadowNode layout  calculation didn't consider the placeholder. When the layout with placeholder was actually being measured, its height was constraint by the previously calculated height, causing long placeholder content to be clipped.
Fix: Access the placeholder property in ReactTextInputShadowNode, set the dummyEditText's hint with placeholder before ReactTextInputShadowNode's first measurement.

Reviewed By: mdvacca

Differential Revision: D8903108

fbshipit-source-id: 8f3e518d0395ac875807f9ea989a0b5bbe4b2a26
---
 .../textinput/ReactTextInputShadowNode.java     | 17 +++++++++++++++--
 1 file changed, 15 insertions(+), 2 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
index 28c559afbc12..20807f81fbc5 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputShadowNode.java
@@ -41,9 +41,11 @@ public class ReactTextInputShadowNode extends ReactBaseTextShadowNode
   private @Nullable ReactTextInputLocalData mLocalData;
 
   @VisibleForTesting public static final String PROP_TEXT = "text";
+  @VisibleForTesting public static final String PROP_PLACEHOLDER = "placeholder";
 
   // Represents the {@code text} property only, not possible nested content.
   private @Nullable String mText = null;
+  private @Nullable String mPlaceholder = null;
 
   public ReactTextInputShadowNode() {
     mTextBreakStrategy = (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) ?
@@ -148,8 +150,9 @@ public long measure(
       }
     }
 
-
-    editText.measure(
+     // make sure the placeholder content is also being measured
+     editText.setHint(getPlaceholder());
+     editText.measure(
         MeasureUtil.getMeasureSpec(width, widthMode),
         MeasureUtil.getMeasureSpec(height, heightMode));
 
@@ -193,6 +196,16 @@ public void setText(@Nullable String text) {
     return mText;
   }
 
+  @ReactProp(name = PROP_PLACEHOLDER)
+  public void setPlaceholder(@Nullable String placeholder) {
+    mPlaceholder = placeholder;
+    markUpdated();
+  }
+
+  public @Nullable String getPlaceholder() {
+    return mPlaceholder;
+  }
+
   @Override
   public void setTextBreakStrategy(@Nullable String textBreakStrategy) {
     if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) {

From d5465a9a0a840f7e759bb8fb6679b01017eb3d05 Mon Sep 17 00:00:00 2001
From: Jiaqi Wu <jiaqiwu@fb.com>
Date: Thu, 19 Jul 2018 17:15:32 -0700
Subject: [PATCH 1101/1109] Fix ReactHorizontalScrollView overflow issue

Summary: Fix ReactHorizontalScrollView so that its children won't overflow. (Task: https://our.intern.facebook.com/intern/tasks/?t=31128239)

Reviewed By: achen1

Differential Revision: D8923947

fbshipit-source-id: 56c36b25c29a87a306d92544273603d0d086edc0
---
 .../react/views/scroll/ReactHorizontalScrollView.java     | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
index 90b9d1fc4d3a..ba6ff876c2b7 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java
@@ -38,6 +38,7 @@ public class ReactHorizontalScrollView extends HorizontalScrollView implements
 
   private final OnScrollDispatchHelper mOnScrollDispatchHelper = new OnScrollDispatchHelper();
   private final VelocityHelper mVelocityHelper = new VelocityHelper();
+  private final Rect mRect = new Rect();
 
   private boolean mActivelyScrolling;
   private @Nullable Rect mClippingRect;
@@ -102,6 +103,13 @@ public void flashScrollIndicators() {
     awakenScrollBars();
   }
 
+  @Override
+  protected void onDraw(Canvas canvas) {
+    getDrawingRect(mRect);
+    canvas.clipRect(mRect);
+    super.onDraw(canvas);
+  }
+
   @Override
   protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
     MeasureSpecAssertions.assertExplicitMeasureSpec(widthMeasureSpec, heightMeasureSpec);

From 9c71952f20cd831aa36dbe59e7b2a48794a8e108 Mon Sep 17 00:00:00 2001
From: Jiaqi Wu <jiaqiwu@fb.com>
Date: Thu, 19 Jul 2018 17:41:41 -0700
Subject: [PATCH 1102/1109] Fix overflow issue in root view

Summary:
Set clipChildren to false by default in ReactRootView.java so that Overflow: visible/hidden will work for the root view.

Moved sDefaultOverflowHidden from ReactViewGroup.java to ViewProps.java so that it can be used in both ReactViewGroup.java and ReactRootView.java.

Reviewed By: mdvacca

Differential Revision: D8727140

fbshipit-source-id: b593bed63e479cdbd22e4a025b936e6aeb28fc8c
---
 .../main/java/com/facebook/react/ReactRootView.java    | 10 ++++++++++
 .../java/com/facebook/react/uimanager/ViewProps.java   |  5 +++++
 .../com/facebook/react/views/view/ReactViewGroup.java  |  7 +------
 3 files changed, 16 insertions(+), 6 deletions(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
index 6e8a92f60368..13ed88113ae2 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/ReactRootView.java
@@ -48,6 +48,7 @@
 import com.facebook.react.uimanager.RootView;
 import com.facebook.react.uimanager.UIManagerHelper;
 import com.facebook.react.uimanager.UIManagerModule;
+import com.facebook.react.uimanager.ViewProps;
 import com.facebook.react.uimanager.common.MeasureSpecProvider;
 import com.facebook.react.uimanager.common.SizeMonitoringFrameLayout;
 import com.facebook.react.uimanager.common.UIManagerType;
@@ -97,14 +98,23 @@ public interface ReactRootViewEventListener {
 
   public ReactRootView(Context context) {
     super(context);
+    init();
   }
 
   public ReactRootView(Context context, AttributeSet attrs) {
     super(context, attrs);
+    init();
   }
 
   public ReactRootView(Context context, AttributeSet attrs, int defStyle) {
     super(context, attrs, defStyle);
+    init();
+  }
+
+  private void init() {
+    if (!ViewProps.sDefaultOverflowHidden) {
+      setClipChildren(false);
+    }
   }
 
   @Override
diff --git a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
index 58e67ccb7524..3ad6f640d1cb 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/uimanager/ViewProps.java
@@ -17,6 +17,11 @@
  */
 public class ViewProps {
 
+  /**
+   * Kill switch to make overflow hidden by default. This flag will eventually be removed.
+   */
+  public static boolean sDefaultOverflowHidden;
+
   public static final String VIEW_CLASS_NAME = "RCTView";
 
   // Layout only (only affect positions of children, causes no drawing)
diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
index e8afaa935745..ce2fa9528592 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.java
@@ -49,11 +49,6 @@ public class ReactViewGroup extends ViewGroup implements
     ReactInterceptingViewGroup, ReactClippingViewGroup, ReactPointerEventsView, ReactHitSlopView,
     ReactZIndexedViewGroup {
 
-  /**
-   * Kill switch to make overflow hidden by default. This flag will eventually be removed.
-   */
-  public static boolean sDefaultOverflowHidden;
-
   private static final int ARRAY_CAPACITY_INCREMENT = 12;
   private static final int DEFAULT_BACKGROUND_COLOR = Color.TRANSPARENT;
   private static final LayoutParams sDefaultLayoutParam = new ViewGroup.LayoutParams(0, 0);
@@ -119,7 +114,7 @@ public void onLayoutChange(
   public ReactViewGroup(Context context) {
     super(context);
     // TODO: Remove this check after a couple public releases.
-    if (!sDefaultOverflowHidden) {
+    if (!ViewProps.sDefaultOverflowHidden) {
       setClipChildren(false);
     }
     mDrawingOrderHelper = new ViewGroupDrawingOrderHelper(this);

From 7091f1560235c4df1369970e3603f214bf27cdec Mon Sep 17 00:00:00 2001
From: Tim Yung <yungsters@fb.com>
Date: Thu, 19 Jul 2018 19:00:38 -0700
Subject: [PATCH 1103/1109] RN: Move ART Canvas Workaround

Summary: Moves the `ReactNativeART` workaround to callers. There are legitimate use cases where you don't want to re-mount this component repeatedly.

Reviewed By: fkgozali

Differential Revision: D8928633

fbshipit-source-id: 0aafc1136ce9acb290e26a4f1a958819439bf2f0
---
 Libraries/ART/ReactNativeART.js | 6 +-----
 1 file changed, 1 insertion(+), 5 deletions(-)

diff --git a/Libraries/ART/ReactNativeART.js b/Libraries/ART/ReactNativeART.js
index cf56028b102c..5a08e748c838 100644
--- a/Libraries/ART/ReactNativeART.js
+++ b/Libraries/ART/ReactNativeART.js
@@ -11,7 +11,6 @@
 
 const Color = require('art/core/color');
 const Path = require('ARTSerializablePath');
-const Platform = require('Platform');
 const Transform = require('art/core/transform');
 
 const React = require('React');
@@ -154,11 +153,8 @@ class Surface extends React.Component {
     const height = extractNumber(this.props.height, 0);
     const width = extractNumber(this.props.width, 0);
 
-    // WORKAROUND: Android bug in which canvas does not reflect size changes.
-    const key = Platform.OS === 'android' ? height + ',' + width : null;
-
     return (
-      <NativeSurfaceView key={key} style={[this.props.style, {height, width}]}>
+      <NativeSurfaceView style={[this.props.style, {height, width}]}>
         {this.props.children}
       </NativeSurfaceView>
     );

From e0c73633cfc0a62df9d39991b0df65fa5875609a Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Rasmus=20K=2E=20Brosb=C3=B8l?= <rbrosboel@gmail.com>
Date: Fri, 20 Jul 2018 00:12:05 -0700
Subject: [PATCH 1104/1109] VirtualizedList: Fix spacer size calculation
 (#18105)

Summary:
See https://github.com/facebook/react-native/issues/18104

Tested the above snack with:
- stickyHeadersEnabled true/false
- initialScrollIndex set and not

Visibly verified consistent rendering.

[GENERAL] [BUGFIX] [VirtualizedList] - Fix for jumpy content when initialScrollIndex specified
Pull Request resolved: https://github.com/facebook/react-native/pull/18105

Differential Revision: D8382122

Pulled By: sahrens

fbshipit-source-id: 9421351469e8684bc61438605abbd9988b664c29
---
 Libraries/Lists/VirtualizedList.js | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/Libraries/Lists/VirtualizedList.js b/Libraries/Lists/VirtualizedList.js
index ba9224c4665f..2efbba657a85 100644
--- a/Libraries/Lists/VirtualizedList.js
+++ b/Libraries/Lists/VirtualizedList.js
@@ -805,8 +805,7 @@ class VirtualizedList extends React.PureComponent<Props, State> {
             if (stickyIndicesFromProps.has(ii + stickyOffset)) {
               const initBlock = this._getFrameMetricsApprox(lastInitialIndex);
               const stickyBlock = this._getFrameMetricsApprox(ii);
-              const leadSpace =
-                stickyBlock.offset - (initBlock.offset + initBlock.length);
+              const leadSpace = stickyBlock.offset - initBlock.offset;
               cells.push(
                 <View key="$sticky_lead" style={{[spacerKey]: leadSpace}} />,
               );

From 583cb137b8e7a63486766f6ef242d7214bf24f2e Mon Sep 17 00:00:00 2001
From: Rafael Oleza <rafeca@fb.com>
Date: Fri, 20 Jul 2018 07:01:05 -0700
Subject: [PATCH 1105/1109] Bump metro@0.42.2

Summary:
shipit

@public

[skip-ci]

Reviewed By: mjesun

Differential Revision: D8931237

fbshipit-source-id: db5bb09eb8ec01ae302cee16e4d6cb229f8244c9
---
 package.json | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/package.json b/package.json
index 09b5ec0330eb..4b2ba2ffd28b 100644
--- a/package.json
+++ b/package.json
@@ -167,10 +167,10 @@
     "graceful-fs": "^4.1.3",
     "inquirer": "^3.0.6",
     "lodash": "^4.17.5",
-    "metro": "^0.42.1",
-    "metro-babel-register": "^0.42.1",
-    "metro-core": "^0.42.1",
-    "metro-memory-fs": "^0.42.1",
+    "metro": "^0.42.2",
+    "metro-babel-register": "^0.42.2",
+    "metro-core": "^0.42.2",
+    "metro-memory-fs": "^0.42.2",
     "mime": "^1.3.4",
     "minimist": "^1.2.0",
     "mkdirp": "^0.5.1",

From ebf5aeab280f2ebc439ec39d25c48fdf1980cf73 Mon Sep 17 00:00:00 2001
From: Jean Lauliac <jeanlauliac@fb.com>
Date: Fri, 20 Jul 2018 09:17:21 -0700
Subject: [PATCH 1106/1109] BREAKING: metro: rename 'unbundle' to 'ram bundle'

Summary:
@public

Let's get rid of the "unbundle" terminology and instead use "RAM bundle", short for "Random Access Bundle" format. THIS IS A BREAKING CHANGE FOR OSS, as the command becomes `ram-bundle` instead of `unbundle`. It realy shouldn't be a command to start with (only a "format" specifier for the `bundle` command), but I don't want to do that change at this point.

Reviewed By: davidaurelio

Differential Revision: D8894433

fbshipit-source-id: 5565f9ae94c7c2d7f6b25f95ae45b64f27f6aec8
---
 local-cli/bundle/ramBundle.js | 34 ++++++++++++++++++++++++++++++++++
 local-cli/bundle/unbundle.js  | 23 ++++++++++-------------
 local-cli/commands.js         |  1 +
 3 files changed, 45 insertions(+), 13 deletions(-)
 create mode 100644 local-cli/bundle/ramBundle.js

diff --git a/local-cli/bundle/ramBundle.js b/local-cli/bundle/ramBundle.js
new file mode 100644
index 000000000000..1d85ba3c4c32
--- /dev/null
+++ b/local-cli/bundle/ramBundle.js
@@ -0,0 +1,34 @@
+/**
+ * Copyright (c) 2015-present, Facebook, Inc.
+ *
+ * This source code is licensed under the MIT license found in the
+ * LICENSE file in the root directory of this source tree.
+ *
+ * @format
+ */
+
+'use strict';
+
+const bundleWithOutput = require('./bundle').withOutput;
+const bundleCommandLineArgs = require('./bundleCommandLineArgs');
+const outputUnbundle = require('metro/src/shared/output/unbundle');
+
+/**
+ * Builds the bundle starting to look for dependencies at the given entry path.
+ */
+function ramBundle(argv, config, args) {
+  return bundleWithOutput(argv, config, args, outputUnbundle);
+}
+
+module.exports = {
+  name: 'ram-bundle',
+  description:
+    'builds javascript as a "Random Access Module" bundle for offline use',
+  func: ramBundle,
+  options: bundleCommandLineArgs.concat({
+    command: '--indexed-ram-bundle',
+    description:
+      'Force the "Indexed RAM" bundle file format, even when building for android',
+    default: false,
+  }),
+};
diff --git a/local-cli/bundle/unbundle.js b/local-cli/bundle/unbundle.js
index da4a4f70d6a8..dfc7fa2483b1 100644
--- a/local-cli/bundle/unbundle.js
+++ b/local-cli/bundle/unbundle.js
@@ -9,25 +9,22 @@
 
 'use strict';
 
-const bundleWithOutput = require('./bundle').withOutput;
 const bundleCommandLineArgs = require('./bundleCommandLineArgs');
-const outputUnbundle = require('metro/src/shared/output/unbundle');
-
-/**
- * Builds the bundle starting to look for dependencies at the given entry path.
- */
-function unbundle(argv, config, args) {
-  return bundleWithOutput(argv, config, args, outputUnbundle);
-}
 
 module.exports = {
   name: 'unbundle',
-  description: 'builds javascript as "unbundle" for offline use',
-  func: unbundle,
+  description: 'Deprecated. Renamed to `ram-bundle`.',
+  func: () => {
+    throw new Error(
+      'The `unbundle` command has been renamed `ram-bundle` to better ' +
+        'represent the actual functionality. `ram` mean "Random Access ' +
+        'Module", this particular format of bundle. Functionality remained ' +
+        'unchanged.',
+    );
+  },
   options: bundleCommandLineArgs.concat({
     command: '--indexed-unbundle',
-    description:
-      'Force indexed unbundle file format, even when building for android',
+    description: 'Deprecated. Renamed to `--indexed-ram-bundle`.',
     default: false,
   }),
 };
diff --git a/local-cli/commands.js b/local-cli/commands.js
index f75207bd3bc5..2a704aa5d446 100644
--- a/local-cli/commands.js
+++ b/local-cli/commands.js
@@ -42,6 +42,7 @@ const documentedCommands = [
   require('./library/library'),
   require('./bundle/bundle'),
   require('./bundle/unbundle'),
+  require('./bundle/ramBundle'),
   require('./eject/eject'),
   require('./link/link'),
   require('./link/unlink'),

From b4b594cec1d91c38faac11a90a787ae692e35296 Mon Sep 17 00:00:00 2001
From: Janic Duplessis <janicduplessis@gmail.com>
Date: Fri, 20 Jul 2018 16:28:04 -0700
Subject: [PATCH 1107/1109] Fix `currentlyFocusedField` by Removing `this`
 usage in TextInputState (#19834)

Summary:
I broke `currentlyFocusedField` when adding it back in ce3b7b8204dad0fd62a76a0ce66472eca4b25bc8 because `this` no longer refers to the proper object because it is assigned here https://github.com/facebook/react-native/commit/ce3b7b8204dad0fd62a76a0ce66472eca4b25bc8#diff-b48972356bc8dca4a00747d002fc3dd5R330. This code was pretty prone to breaking so I simply removed the `this` usage and rely on a top level variable instead. Also moved everything to named functions.
Pull Request resolved: https://github.com/facebook/react-native/pull/19834

Differential Revision: D8943088

Pulled By: hramos

fbshipit-source-id: 24d1470f6117138a5978fb7e467147847a9f3658
---
 .../Components/TextInput/TextInputState.js    | 121 +++++++++---------
 1 file changed, 61 insertions(+), 60 deletions(-)

diff --git a/Libraries/Components/TextInput/TextInputState.js b/Libraries/Components/TextInput/TextInputState.js
index 95cd24fbe8d2..66682e40a40a 100644
--- a/Libraries/Components/TextInput/TextInputState.js
+++ b/Libraries/Components/TextInput/TextInputState.js
@@ -18,73 +18,74 @@
 const Platform = require('Platform');
 const UIManager = require('UIManager');
 
+let currentlyFocusedID: ?number = null;
 const inputs = new Set();
 
-const TextInputState = {
-  /**
-   * Internal state
-   */
-  _currentlyFocusedID: (null: ?number),
-
-  /**
-   * Returns the ID of the currently focused text field, if one exists
-   * If no text field is focused it returns null
-   */
-  currentlyFocusedField: function(): ?number {
-    return this._currentlyFocusedID;
-  },
+/**
+ * Returns the ID of the currently focused text field, if one exists
+ * If no text field is focused it returns null
+ */
+function currentlyFocusedField(): ?number {
+  return currentlyFocusedID;
+}
 
-  /**
-   * @param {number} TextInputID id of the text field to focus
-   * Focuses the specified text field
-   * noop if the text field was already focused
-   */
-  focusTextInput: function(textFieldID: ?number) {
-    if (this._currentlyFocusedID !== textFieldID && textFieldID !== null) {
-      this._currentlyFocusedID = textFieldID;
-      if (Platform.OS === 'ios') {
-        UIManager.focus(textFieldID);
-      } else if (Platform.OS === 'android') {
-        UIManager.dispatchViewManagerCommand(
-          textFieldID,
-          UIManager.AndroidTextInput.Commands.focusTextInput,
-          null,
-        );
-      }
+/**
+ * @param {number} TextInputID id of the text field to focus
+ * Focuses the specified text field
+ * noop if the text field was already focused
+ */
+function focusTextInput(textFieldID: ?number) {
+  if (currentlyFocusedID !== textFieldID && textFieldID !== null) {
+    currentlyFocusedID = textFieldID;
+    if (Platform.OS === 'ios') {
+      UIManager.focus(textFieldID);
+    } else if (Platform.OS === 'android') {
+      UIManager.dispatchViewManagerCommand(
+        textFieldID,
+        UIManager.AndroidTextInput.Commands.focusTextInput,
+        null,
+      );
     }
-  },
+  }
+}
 
-  /**
-   * @param {number} textFieldID id of the text field to unfocus
-   * Unfocuses the specified text field
-   * noop if it wasn't focused
-   */
-  blurTextInput: function(textFieldID: ?number) {
-    if (this._currentlyFocusedID === textFieldID && textFieldID !== null) {
-      this._currentlyFocusedID = null;
-      if (Platform.OS === 'ios') {
-        UIManager.blur(textFieldID);
-      } else if (Platform.OS === 'android') {
-        UIManager.dispatchViewManagerCommand(
-          textFieldID,
-          UIManager.AndroidTextInput.Commands.blurTextInput,
-          null,
-        );
-      }
+/**
+ * @param {number} textFieldID id of the text field to unfocus
+ * Unfocuses the specified text field
+ * noop if it wasn't focused
+ */
+function blurTextInput(textFieldID: ?number) {
+  if (currentlyFocusedID === textFieldID && textFieldID !== null) {
+    currentlyFocusedID = null;
+    if (Platform.OS === 'ios') {
+      UIManager.blur(textFieldID);
+    } else if (Platform.OS === 'android') {
+      UIManager.dispatchViewManagerCommand(
+        textFieldID,
+        UIManager.AndroidTextInput.Commands.blurTextInput,
+        null,
+      );
     }
-  },
+  }
+}
 
-  registerInput: function(textFieldID: number) {
-    inputs.add(textFieldID);
-  },
+function registerInput(textFieldID: number) {
+  inputs.add(textFieldID);
+}
 
-  unregisterInput: function(textFieldID: number) {
-    inputs.delete(textFieldID);
-  },
+function unregisterInput(textFieldID: number) {
+  inputs.delete(textFieldID);
+}
 
-  isTextInput: function(textFieldID: number) {
-    return inputs.has(textFieldID);
-  },
-};
+function isTextInput(textFieldID: number) {
+  return inputs.has(textFieldID);
+}
 
-module.exports = TextInputState;
+module.exports = {
+  currentlyFocusedField,
+  focusTextInput,
+  blurTextInput,
+  registerInput,
+  unregisterInput,
+  isTextInput,
+};

From e592d6f8c7b0409ab6f0a2dbf6ebe3cea28c3e79 Mon Sep 17 00:00:00 2001
From: Valentin Schlattinger <v.schlattinger@gmail.com>
Date: Fri, 20 Jul 2018 18:59:10 -0700
Subject: [PATCH 1108/1109] fix missing selection indicator lines (#18885)

Summary:
This PR is based on https://github.com/facebook/react-native/pull/13342 by pvinis and fixes https://github.com/facebook/react-native/issues/14442.

As suggested in the discussion on the PR mentioned above, I moved the code from `React/Views/RCTPickerManager.m` to the `initWithFrame` function in `React/Views/RCTPicker.m` and verified that it still fixes the problem.

Before the change in this PR the selection indicator lines are missing when the Picker is initially added to the View and only appear after changing to a different Tab and back. This happens both in the Simulator and my real device (iPhone 6S on iOS 11.3).

![beforechange](https://user-images.githubusercontent.com/7568362/38824104-7b294cae-41a8-11e8-8609-7a647ab3adb8.png)

After the change, the indicator lines always appear. I did not notice any side effects of this change when playing around with the Picker in different configurations.

![afterchange](https://user-images.githubusercontent.com/7568362/38824109-82a5b382-41a8-11e8-8af3-ca07c8b2c30e.png)

https://github.com/facebook/react-native/pull/13342 also fixes this issue but appears to be inactive.

[IOS] [BUGFIX] [PickerIOS] - Fixed missing selection indicator lines
Pull Request resolved: https://github.com/facebook/react-native/pull/18885

Differential Revision: D8945483

Pulled By: hramos

fbshipit-source-id: 2b6c6f42559691530b062503feb24bc305f4a8af
---
 React/Views/RCTPicker.m | 1 +
 1 file changed, 1 insertion(+)

diff --git a/React/Views/RCTPicker.m b/React/Views/RCTPicker.m
index 3193417bdfdd..16f383a8f4de 100644
--- a/React/Views/RCTPicker.m
+++ b/React/Views/RCTPicker.m
@@ -23,6 +23,7 @@ - (instancetype)initWithFrame:(CGRect)frame
     _selectedIndex = NSNotFound;
     _textAlign = NSTextAlignmentCenter;
     self.delegate = self;
+    [self selectRow:0 inComponent:0 animated:YES]; // Workaround for missing selection indicator lines (see https://stackoverflow.com/questions/39564660/uipickerview-selection-indicator-not-visible-in-ios10)
   }
   return self;
 }

From abbe27ff25f8dd4278e16f66a036e263598557ec Mon Sep 17 00:00:00 2001
From: Vishwesh Jainkuniya <gitvishwesh@gmail.com>
Date: Sun, 22 Jul 2018 18:05:32 +0530
Subject: [PATCH 1109/1109] textInput: Fix placeholder is not completely
 visible on Android.

On Android, placeholder of TextInput is not completely visible.
TextInput had some default fixed width. On iOS it is perfectly
visible.

This commit makes it consistent on both the platforms.

Before:
https://user-images.githubusercontent.com/39303760/43045649-54cb45e8-8dda-11e8-9935-059ad8ee9def.png

After:
https://user-images.githubusercontent.com/39303760/43045650-54fb9428-8dda-11e8-88b8-176839d6c0a7.png

Testing code:
https://github.com/jainkuniya/TestTextInput/blob/a0a6fbb491e979fe7cc9d0a580d67790b3481eb8/App.js
---
 .../react/views/textinput/ReactTextInputLocalData.java       | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputLocalData.java b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputLocalData.java
index ce7b2725bb69..a91d72f42b72 100644
--- a/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputLocalData.java
+++ b/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputLocalData.java
@@ -21,11 +21,13 @@ public final class ReactTextInputLocalData {
   private final int mMaxLines;
   private final int mInputType;
   private final int mBreakStrategy;
+  private final  CharSequence mPlaceholder;
 
   public ReactTextInputLocalData(EditText editText) {
     mText = new SpannableStringBuilder(editText.getText());
     mTextSize = editText.getTextSize();
     mInputType = editText.getInputType();
+    mPlaceholder = editText.getHint();
 
     if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
       mMinLines = editText.getMinLines();
@@ -48,8 +50,9 @@ public void apply(EditText editText) {
     editText.setMinLines(mMinLines);
     editText.setMaxLines(mMaxLines);
     editText.setInputType(mInputType);
+    editText.setHint(mPlaceholder);
     if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
       editText.setBreakStrategy(mBreakStrategy);
     }
   }
-}
+}
\ No newline at end of file
